sources_5316/0000775000176700017670000000000011757251666011745 5ustar paulpaulsources_5316/makefile0000644000176700017670000000347411704272340013433 0ustar paulpaul# File: makefile # Makefile for Praat. # Paul Boersma, 14 January 2012 # System-dependent definitions of CC, LIBS, ICON and MAIN_ICON should be in # makefile.defs, which has to be copied and renamed # from a suitable makefile.defs.XXX file in the makefiles directory, # Perhaps that file requires some editing. include makefile.defs # Makes the Praat executable in the source directory. all: $(MAKE) -C external/gsl $(MAKE) -C external/glpk $(MAKE) -C external/mp3 $(MAKE) -C external/flac $(MAKE) -C external/portaudio $(MAKE) -C external/espeak $(MAKE) -C kar $(MAKE) -C num $(MAKE) -C sys $(MAKE) -C dwsys $(MAKE) -C stat $(MAKE) -C fon $(MAKE) -C dwtools $(MAKE) -C LPC $(MAKE) -C EEG $(MAKE) -C gram $(MAKE) -C FFNet $(MAKE) -C artsynth $(MAKE) -C contrib/ola $(MAKE) -C main main_Praat.o $(ICON) $(LINK) -o $(EXECUTABLE) main/main_Praat.o $(MAIN_ICON) fon/libfon.a \ contrib/ola/libOla.a artsynth/libartsynth.a \ FFNet/libFFNet.a gram/libgram.a EEG/libEEG.a \ LPC/libLPC.a dwtools/libdwtools.a \ fon/libfon.a stat/libstat.a dwsys/libdwsys.a \ sys/libsys.a num/libnum.a kar/libkar.a \ external/espeak/libespeak.a external/portaudio/libportaudio.a \ external/flac/libflac.a external/mp3/libmp3.a \ external/glpk/libglpk.a external/gsl/libgsl.a \ $(LIBS) clean: $(MAKE) -C external/gsl clean $(MAKE) -C external/glpk clean $(MAKE) -C external/mp3 clean $(MAKE) -C external/flac clean $(MAKE) -C external/portaudio clean $(MAKE) -C external/espeak clean $(MAKE) -C kar clean $(MAKE) -C num clean $(MAKE) -C sys clean $(MAKE) -C dwsys clean $(MAKE) -C stat clean $(MAKE) -C fon clean $(MAKE) -C dwtools clean $(MAKE) -C LPC clean $(MAKE) -C EEG clean $(MAKE) -C gram clean $(MAKE) -C FFNet clean $(MAKE) -C artsynth clean $(MAKE) -C contrib/ola clean # $(MAKE) -C main clean $(RM) praat sources_5316/EEG/0000755000176700017670000000000011741321361012322 5ustar paulpaulsources_5316/EEG/ERPWindow.cpp0000644000176700017670000002070611720240255014650 0ustar paulpaul/* ERPWindow.cpp * * Copyright (C) 2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ERPWindow.h" Thing_implement (ERPWindow, SoundEditor, 0); typedef struct { int inclination, azimuth; double topX, topY; } BiosemiLocationData; static BiosemiLocationData biosemiCapCoordinates64 [1+64] = { /* * BioSemi says: * "Spherical coordinates in degrees, * by inclination (from Cz, pos is right hemisphere, neg is left hemisphere), * and azimuth (from T7 for left hemisphere, and from T8 for the right hemisphere, pos is anti-clockwise, neg is clockwise)" */ {0,0}, { -92, -72 }, // 1 Fp1 { -92, -54 }, // 2 AF7 { -74, -65 }, // 3 AF3 { -50, -68 }, // 4 F1 { -60, -51 }, // 5 F3 { -75, -41 }, // 6 F5 { -92, -36 }, // 7 F7 { -92, -18 }, // 8 FT7 { -72, -21 }, // 9 FC5 { -50, -28 }, // 10 FC3 { -32, -45 }, // 11 FC1 { -23, 0 }, // 12 C1 { -46, 0 }, // 13 C3 { -69, 0 }, // 14 C5 { -92, 0 }, // 15 T7 { -92, 18 }, // 16 TP7 { -72, 21 }, // 17 CP5 { -50, 28 }, // 18 CP3 { -32, 45 }, // 19 CP1 { -50, 68 }, // 20 P1 { -60, 51 }, // 21 P3 { -75, 41 }, // 22 P5 { -92, 36 }, // 23 P7 {-115, 40 }, // 24 P9 { -92, 54 }, // 25 PO7 { -74, 65 }, // 26 PO3 { -92, 72 }, // 27 O1 { 115, -90 }, // 28 Iz { 92, -90 }, // 29 Oz { 69, -90 }, // 30 POz { 46, -90 }, // 31 Pz { 23, -90 }, // 32 CPz { 92, 90 }, // 33 Fpz { 92, 72 }, // 34 Fp2 { 92, 54 }, // 35 AF8 { 74, 65 }, // 36 AF4 { 69, 90 }, // 37 AFz { 46, 90 }, // 38 Fz { 50, 68 }, // 39 F2 { 60, 51 }, // 40 F4 { 75, 41 }, // 41 F6 { 92, 36 }, // 42 F8 { 92, 18 }, // 43 FT8 { 72, 21 }, // 44 FC6 { 50, 28 }, // 45 FC4 { 32, 45 }, // 46 FC2 { 23, 90 }, // 47 FCz { 0, 0 }, // 48 Cz { 23, 0 }, // 49 C2 { 46, 0 }, // 50 C4 { 69, 0 }, // 51 C6 { 92, 0 }, // 52 T8 { 92, -18 }, // 53 TP8 { 72, -21 }, // 54 CP6 { 50, -28 }, // 55 CP4 { 32, -45 }, // 56 CP2 { 50, -68 }, // 57 P2 { 60, -51 }, // 58 P4 { 75, -41 }, // 59 P6 { 92, -36 }, // 60 P8 { 115, -40 }, // 61 P10 { 92, -54 }, // 62 PO8 { 74, -65 }, // 63 PO4 { 92, -72 } // 64 O2 }; static BiosemiLocationData biosemiCapCoordinates32 [1+32] = { /* * BioSemi says: * "Spherical coordinates in degrees, * by inclination (from Cz, pos is right hemisphere, neg is left hemisphere), * and azimuth (from T7 for left hemisphere, and from T8 for the right hemisphere, pos is anti-clockwise, neg is clockwise)" */ {0,0}, { -92, -72 }, // 1 Fp1 { -74, -65 }, // 2 AF3 { -92, -36 }, // 3 F7 { -60, -51 }, // 4 F3 { -32, -45 }, // 5 FC1 { -72, -21 }, // 6 FC5 { -92, 0 }, // 7 T7 { -46, 0 }, // 8 C3 { -32, 45 }, // 9 CP1 { -72, 21 }, // 10 CP5 { -92, 36 }, // 11 P7 { -60, 51 }, // 12 P3 { 46, -90 }, // 13 Pz { -74, 65 }, // 14 PO3 { -92, 72 }, // 15 O1 { 92, -90 }, // 16 Oz { 92, -72 }, // 17 O2 { 74, -65 }, // 18 PO4 { 60, -51 }, // 19 P4 { 92, -36 }, // 20 P8 { 72, -21 }, // 21 CP6 { 32, -45 }, // 22 CP2 { 46, 0 }, // 23 C4 { 92, 0 }, // 24 T8 { 72, 21 }, // 25 FC6 { 32, 45 }, // 26 FC2 { 60, 51 }, // 27 F4 { 92, 36 }, // 28 F8 { 74, 65 }, // 29 AF4 { 92, 72 }, // 30 Fp2 { 46, 90 }, // 31 Fz { 0, 0 }, // 32 Cz }; void structERPWindow :: v_drawSelectionViewer () { ERP erp = (ERP) data; Graphics_setWindow (graphics, -1.1, 1.1, -1.01, 1.19); Graphics_setGrey (graphics, 0.85); Graphics_fillRectangle (graphics, -1.1, 1.1, -1.01, 1.19); Graphics_setColour (graphics, Graphics_BLACK); long numberOfDrawableChannels = erp -> ny >= 64 && Melder_wcsequ (erp -> d_channelNames [64], L"O2") ? 64 : erp -> ny >= 32 && Melder_wcsequ (erp -> d_channelNames [32], L"Cz") ? 32 : 0; BiosemiLocationData *biosemiLocationData = numberOfDrawableChannels == 64 ? biosemiCapCoordinates64 : numberOfDrawableChannels == 32 ? biosemiCapCoordinates32 : 0; for (long ichan = 1; ichan <= numberOfDrawableChannels; ichan ++) { double inclination = (double) biosemiLocationData [ichan]. inclination; double azimuth = (double) biosemiLocationData [ichan]. azimuth; bool rightHemisphere = inclination >= 0.0; double r = fabs (inclination / 115.0); double theta = rightHemisphere ? azimuth * (NUMpi / 180.0) : (azimuth + 180.0) * (NUMpi / 180.0); biosemiLocationData [ichan]. topX = r * cos (theta); biosemiLocationData [ichan]. topY = r * sin (theta); } long n = 201; double d = 2.0 / (n - 1); autoNUMvector mean (1, numberOfDrawableChannels); for (long ichan = 1; ichan <= numberOfDrawableChannels; ichan ++) { mean [ichan] = startSelection == endSelection ? Sampled_getValueAtX (erp, startSelection, ichan, 0, true) : Vector_getMean (erp, startSelection, endSelection, ichan); } autoNUMmatrix image (1, n, 1, n); for (long irow = 1; irow <= n; irow ++) { double y = -1.0 + (irow - 1) * d; for (long icol = 1; icol <= n; icol ++) { double x = -1.0 + (icol - 1) * d; if (x * x + y * y <= 1.0) { double value = NUMundefined, sum = 0.0, weight = 0.0; for (long ichan = 1; ichan <= numberOfDrawableChannels; ichan ++) { double dx = x - biosemiLocationData [ichan]. topX; double dy = y - biosemiLocationData [ichan]. topY; double distance = sqrt (dx * dx + dy * dy); if (distance < 1e-12) { value = mean [ichan]; break; } distance = distance * distance * distance * distance * distance * distance; sum += mean [ichan] / distance; weight += 1.0 / distance; } if (value == NUMundefined) value = sum == 0.0 ? 0.0 : sum / weight; image [irow] [icol] = value; } } } double minimum = 0.0, maximum = 0.0; for (long irow = 1; irow <= n; irow ++) { for (long icol = 1; icol <= n; icol ++) { double value = image [irow] [icol]; if (value < minimum) minimum = value; else if (value > maximum) maximum = value; } } double absoluteExtremum = - minimum > maximum ? - minimum : maximum; for (long irow = 1; irow <= n; irow ++) { double y = -1.0 + (irow - 1) * d; for (long icol = 1; icol <= n; icol ++) { double x = -1.0 + (icol - 1) * d; if (x * x + y * y > 1.0) { image [irow] [icol] = -0.625 * absoluteExtremum; } } } Graphics_image (graphics, image.peek(), 1, n, -1.0-0.5/n, 1.0+0.5/n, 1, n, -1.0-0.5/n, 1.0+0.5/n, - absoluteExtremum, absoluteExtremum); Graphics_setLineWidth (graphics, 2.0); /* * Nose. */ Graphics_setGrey (graphics, 0.5); {// scope double x [3] = { -0.08, 0.0, 0.08 }, y [3] = { 0.99, 1.18, 0.99 }; Graphics_fillArea (graphics, 3, x, y); } Graphics_setColour (graphics, Graphics_BLACK); Graphics_line (graphics, -0.08, 0.99, 0.0, 1.18); Graphics_line (graphics, 0.08, 0.99, 0.0, 1.18); /* * Ears. */ Graphics_setGrey (graphics, 0.5); Graphics_fillRectangle (graphics, -1.09, -1.00, -0.08, 0.08); Graphics_fillRectangle (graphics, 1.09, 1.00, -0.08, 0.08); Graphics_setColour (graphics, Graphics_BLACK); Graphics_line (graphics, -0.99, 0.08, -1.09, 0.08); Graphics_line (graphics, -1.09, 0.08, -1.09, -0.08); Graphics_line (graphics, -1.09, -0.08, -0.99, -0.08); Graphics_line (graphics, 0.99, 0.08, 1.09, 0.08); Graphics_line (graphics, 1.09, 0.08, 1.09, -0.08); Graphics_line (graphics, 1.09, -0.08, 0.99, -0.08); /* * Scalp. */ Graphics_ellipse (graphics, -1.0, 1.0, -1.0, 1.0); Graphics_setLineWidth (graphics, 1.0); } ERPWindow ERPWindow_create (GuiObject parent, const wchar *title, ERP data) { Melder_assert (data != NULL); try { autoERPWindow me = Thing_new (ERPWindow); me -> structSoundEditor :: f_init (parent, title, data); return me.transfer(); } catch (MelderError) { Melder_throw ("ERP window not created."); } } /* End of file ERPWindow.cpp */ sources_5316/EEG/Makefile0000644000176700017670000000107111720552776013776 0ustar paulpaul# Makefile of the library "EEG" # Paul Boersma, 20 February 2012 include ../makefile.defs CPPFLAGS = -I ../num -I ../kar -I ../sys -I ../dwsys -I ../stat -I ../dwtools -I ../fon OBJECTS = EEG.o EEGWindow.o ERPTier.o ERP.o ERPWindow.o \ praat_EEG.o manual_EEG.o .PHONY: all clean all: libEEG.a clean: $(RM) $(OBJECTS) $(RM) libEEG.a libEEG.a: $(OBJECTS) touch libEEG.a rm libEEG.a ar cq libEEG.a $(OBJECTS) $(RANLIB) libEEG.a $(OBJECTS): *.h ../num/NUM.h ../kar/*.h ../sys/*.h ../dwsys/*.h ../stat/*.h ../dwtools/*.h ../fon/*.h sources_5316/EEG/EEGWindow.cpp0000644000176700017670000000644111741321361014623 0ustar paulpaul/* EEGWindow.cpp * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "EEGWindow.h" #include "EditorM.h" Thing_implement (EEGWindow, TextGridEditor, 0); void EEGWindow_preferences (void) { } static void menu_cb_EEGWindowHelp (EDITOR_ARGS) { EDITOR_IAM (EEGWindow); Melder_help (L"EEG window"); } void structEEGWindow :: v_createMenus () { EEGWindow_Parent :: v_createMenus (); } void structEEGWindow :: v_createHelpMenuItems (EditorMenu menu) { TextGridEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"EEGWindow help", '?', menu_cb_EEGWindowHelp); } const wchar * structEEGWindow :: v_getChannelName (long channelNumber) { Melder_assert (d_eeg != NULL); return d_eeg -> d_channelNames [channelNumber]; } void structEEGWindow :: f_init (GuiObject parent, const wchar *title, EEG eeg) { d_eeg = eeg; // before initing, because initing will already draw! structTextGridEditor :: f_init (parent, title, eeg -> d_textgrid, eeg -> d_sound, false, NULL); } static void menu_cb_ExtractSelectedEEG_preserveTimes (EDITOR_ARGS) { EDITOR_IAM (EEGWindow); if (my endSelection <= my startSelection) Melder_throw ("No selection."); autoEEG extract = my d_eeg -> f_extractPart (my startSelection, my endSelection, true); my broadcastPublication (extract.transfer()); } static void menu_cb_ExtractSelectedEEG_timeFromZero (EDITOR_ARGS) { EDITOR_IAM (EEGWindow); if (my endSelection <= my startSelection) Melder_throw ("No selection."); autoEEG extract = my d_eeg -> f_extractPart (my startSelection, my endSelection, false); my broadcastPublication (extract.transfer()); } void structEEGWindow :: v_createMenuItems_file_extract (EditorMenu menu) { EEGWindow_Parent :: v_createMenuItems_file_extract (menu); d_extractSelectedEEGPreserveTimesButton = EditorMenu_addCommand (menu, L"Extract selected EEG (preserve times)", 0, menu_cb_ExtractSelectedEEG_preserveTimes); d_extractSelectedEEGTimeFromZeroButton = EditorMenu_addCommand (menu, L"Extract selected EEG (time from zero)", 0, menu_cb_ExtractSelectedEEG_timeFromZero); } void structEEGWindow :: v_updateMenuItems_file () { EEGWindow_Parent :: v_updateMenuItems_file (); GuiObject_setSensitive (d_extractSelectedEEGPreserveTimesButton, endSelection > startSelection); GuiObject_setSensitive (d_extractSelectedEEGTimeFromZeroButton, endSelection > startSelection); } EEGWindow EEGWindow_create (GuiObject parent, const wchar *title, EEG eeg) { try { autoEEGWindow me = Thing_new (EEGWindow); my f_init (parent, title, eeg); return me.transfer(); } catch (MelderError) { Melder_throw ("EEG window not created."); } } /* End of file EEGWindow.cpp */ sources_5316/EEG/ERP.cpp0000644000176700017670000000643611665145167013502 0ustar paulpaul/* ERP.cpp * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ERP.h" #include "oo_DESTROY.h" #include "ERP_def.h" #include "oo_COPY.h" #include "ERP_def.h" #include "oo_EQUAL.h" #include "ERP_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "ERP_def.h" #include "oo_WRITE_TEXT.h" #include "ERP_def.h" #include "oo_READ_TEXT.h" #include "ERP_def.h" #include "oo_WRITE_BINARY.h" #include "ERP_def.h" #include "oo_READ_BINARY.h" #include "ERP_def.h" #include "oo_DESCRIPTION.h" #include "ERP_def.h" /********** class ERPTier **********/ Thing_implement (ERP, Sound, 2); long structERP :: f_getChannelNumber (const wchar *channelName) { for (long ichan = 1; ichan <= ny; ichan ++) { if (Melder_wcsequ (d_channelNames [ichan], channelName)) { return ichan; } } return 0; } void structERP :: f_draw (Graphics graphics, long channelNumber, double tmin, double tmax, double vmin, double vmax, bool garnish) { if (channelNumber < 1 || channelNumber > this -> ny) return; /* * Automatic domain. */ if (tmin == tmax) { tmin = this -> xmin; tmax = this -> xmax; } /* * Domain expressed in sample numbers. */ long ixmin, ixmax; Matrix_getWindowSamplesX (this, tmin, tmax, & ixmin, & ixmax); /* * Automatic vertical range. */ if (vmin == vmax) { Matrix_getWindowExtrema (this, ixmin, ixmax, 1, this -> ny, & vmin, & vmax); if (vmin == vmax) { vmin -= 1.0; vmax += 1.0; } } /* * Set coordinates for drawing. */ Graphics_setInner (graphics); Graphics_setWindow (graphics, tmin, tmax, vmin, vmax); Graphics_function (graphics, this -> z [channelNumber], ixmin, ixmax, Matrix_columnToX (this, ixmin), Matrix_columnToX (this, ixmax)); Graphics_unsetInner (graphics); if (garnish) { Graphics_drawInnerBox (graphics); Graphics_textTop (graphics, true, Melder_wcscat (L"Channel ", d_channelNames [channelNumber])); Graphics_textBottom (graphics, true, L"Time (s)"); Graphics_marksBottom (graphics, 2, true, true, false); if (0.0 > tmin && 0.0 < tmax) Graphics_markBottom (graphics, 0.0, true, true, true, NULL); Graphics_markLeft (graphics, vmin, true, true, false, NULL); Graphics_markLeft (graphics, vmax, true, true, false, NULL); Graphics_markBottom (graphics, 0.0, true, true, true, NULL); if (vmin != 0.0 && vmax != 0.0 && (vmin > 0.0) != (vmax > 0.0)) { Graphics_markLeft (graphics, 0.0, true, true, true, NULL); } } } void structERP :: f_draw (Graphics graphics, const wchar *channelName, double tmin, double tmax, double vmin, double vmax, bool garnish) { f_draw (graphics, f_getChannelNumber (channelName), tmin, tmax, vmin, vmax, garnish); } /* End of file ERP.cpp */ sources_5316/EEG/EEG.h0000644000176700017670000000202311727456300013076 0ustar paulpaul#ifndef _EEG_h_ #define _EEG_h_ /* EEG.h * * Copyright (C) 2011-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sound.h" #include "TextGrid.h" #include "EEG_def.h" oo_CLASS_CREATE (EEG, Function); EEG EEG_create (double tmin, double tmax); EEG EEG_readFromBdfFile (MelderFile file); EEG EEGs_concatenate (Collection me); /* End of file EEG.h */ #endif sources_5316/EEG/ERP_def.h0000644000176700017670000000236611665123417013755 0ustar paulpaul/* ERP_def.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT ERP oo_DEFINE_CLASS (ERP, Sound) oo_STRING_VECTOR (d_channelNames, ny) #if oo_DECLARING // functions: public: long f_getChannelNumber (const wchar *channelName); void f_draw (Graphics graphics, long channelNumber, double tmin, double tmax, double vmin, double vmax, bool garnish); void f_draw (Graphics graphics, const wchar *channelName, double tmin, double tmax, double vmin, double vmax, bool garnish); #endif oo_END_CLASS (ERP) #undef ooSTRUCT /* End of file ERP_def.h */ sources_5316/EEG/ERPTier.cpp0000644000176700017670000002757511734345227014331 0ustar paulpaul/* ERPTier.cpp * * Copyright (C) 2011-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ERPTier.h" #include "oo_DESTROY.h" #include "ERPTier_def.h" #include "oo_COPY.h" #include "ERPTier_def.h" #include "oo_EQUAL.h" #include "ERPTier_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "ERPTier_def.h" #include "oo_WRITE_TEXT.h" #include "ERPTier_def.h" #include "oo_READ_TEXT.h" #include "ERPTier_def.h" #include "oo_WRITE_BINARY.h" #include "ERPTier_def.h" #include "oo_READ_BINARY.h" #include "ERPTier_def.h" #include "oo_DESCRIPTION.h" #include "ERPTier_def.h" /***** ERPPoint *****/ Thing_implement (ERPPoint, AnyPoint, 0); /***** ERPTier *****/ Thing_implement (ERPTier, Function, 0); void structERPTier :: v_shiftX (double xfrom, double xto) { ERPTier_Parent :: v_shiftX (xfrom, xto); //if (d_sound != NULL) Function_shiftXTo (d_sound, xfrom, xto); //if (d_textgrid != NULL) Function_shiftXTo (d_textgrid, xfrom, xto); } void structERPTier :: v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto) { ERPTier_Parent :: v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); //if (d_sound != NULL) d_sound -> v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); //if (d_textgrid != NULL) d_textgrid -> v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); } long structERPTier :: f_getChannelNumber (const wchar *channelName) { for (long ichan = 1; ichan <= d_numberOfChannels; ichan ++) { if (Melder_wcsequ (d_channelNames [ichan], channelName)) { return ichan; } } return 0; } double structERPTier :: f_getMean (long pointNumber, long channelNumber, double tmin, double tmax) { if (pointNumber < 1 || pointNumber > d_events -> size) return NUMundefined; if (channelNumber < 1 || channelNumber > d_numberOfChannels) return NUMundefined; ERPPoint point = f_peekEvent (pointNumber); return Vector_getMean (point -> d_erp, tmin, tmax, channelNumber); } double structERPTier :: f_getMean (long pointNumber, const wchar *channelName, double tmin, double tmax) { return f_getMean (pointNumber, f_getChannelNumber (channelName), tmin, tmax); } ERPTier EEG_to_ERPTier (EEG me, double fromTime, double toTime, int markerBit) { try { autoERPTier thee = Thing_new (ERPTier); Function_init (thee.peek(), fromTime, toTime); thy d_numberOfChannels = my d_numberOfChannels - my f_getNumberOfExtraSensors (); thy d_channelNames = NUMvector (1, thy d_numberOfChannels); for (long ichan = 1; ichan <= thy d_numberOfChannels; ichan ++) { thy d_channelNames [ichan] = Melder_wcsdup (my d_channelNames [ichan]); } autoPointProcess events = TextGrid_getStartingPoints (my d_textgrid, markerBit, kMelder_string_EQUAL_TO, L"1"); long numberOfEvents = events -> nt; thy d_events = SortedSetOfDouble_create (); double soundDuration = toTime - fromTime; double samplingPeriod = my d_sound -> dx; long numberOfSamples = floor (soundDuration / samplingPeriod) + 1; if (numberOfSamples < 1) Melder_throw (L"Time window too short."); double midTime = 0.5 * (fromTime + toTime); double soundPhysicalDuration = numberOfSamples * samplingPeriod; double firstTime = midTime - 0.5 * soundPhysicalDuration + 0.5 * samplingPeriod; // distribute the samples evenly over the time domain for (long ievent = 1; ievent <= numberOfEvents; ievent ++) { double eegEventTime = events -> t [ievent]; autoERPPoint event = Thing_new (ERPPoint); event -> number = eegEventTime; event -> d_erp = Sound_create (thy d_numberOfChannels, fromTime, toTime, numberOfSamples, samplingPeriod, firstTime); double erpEventTime = 0.0; double eegSample = 1 + (eegEventTime - my d_sound -> x1) / samplingPeriod; double erpSample = 1 + (erpEventTime - firstTime) / samplingPeriod; long sampleDifference = round (eegSample - erpSample); for (long ichannel = 1; ichannel <= thy d_numberOfChannels; ichannel ++) { for (long isample = 1; isample <= numberOfSamples; isample ++) { long jsample = isample + sampleDifference; event -> d_erp -> z [ichannel] [isample] = jsample < 1 || jsample > my d_sound -> nx ? 0.0 : my d_sound -> z [ichannel] [jsample]; } } Collection_addItem (thy d_events, event.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": ERP analysis not performed."); } } void structERPTier :: f_subtractBaseline (double tmin, double tmax) { long numberOfEvents = d_events -> size; if (numberOfEvents < 1) return; // nothing to do ERPPoint firstEvent = f_peekEvent (1); long numberOfChannels = firstEvent -> d_erp -> ny; long numberOfSamples = firstEvent -> d_erp -> nx; for (long ievent = 1; ievent <= numberOfEvents; ievent ++) { ERPPoint event = f_peekEvent (ievent); for (long ichannel = 1; ichannel <= numberOfChannels; ichannel ++) { double mean = Vector_getMean (event -> d_erp, tmin, tmax, ichannel); double *channel = event -> d_erp -> z [ichannel]; for (long isample = 1; isample <= numberOfSamples; isample ++) { channel [isample] -= mean; } } } } void structERPTier :: f_rejectArtefacts (double threshold) { long numberOfEvents = d_events -> size; if (numberOfEvents < 1) return; // nothing to do ERPPoint firstEvent = f_peekEvent (1); long numberOfChannels = firstEvent -> d_erp -> ny; long numberOfSamples = firstEvent -> d_erp -> nx; if (numberOfSamples < 1) return; // nothing to do for (long ievent = numberOfEvents; ievent >= 1; ievent --) { // cycle down because of removal ERPPoint event = f_peekEvent (ievent); double minimum = event -> d_erp -> z [1] [1]; double maximum = minimum; for (long ichannel = 1; ichannel <= (numberOfChannels & ~ 15); ichannel ++) { double *channel = event -> d_erp -> z [ichannel]; for (long isample = 1; isample <= numberOfSamples; isample ++) { double value = channel [isample]; if (value < minimum) minimum = value; if (value > maximum) maximum = value; } } if (minimum < - threshold || maximum > threshold) { Collection_removeItem (d_events, ievent); } } } ERP structERPTier :: f_extractERP (long eventNumber) { try { long numberOfEvents = d_events -> size; if (numberOfEvents < 1) Melder_throw ("No events."); f_checkEventNumber (eventNumber); ERPPoint event = f_peekEvent (eventNumber); long numberOfChannels = event -> d_erp -> ny; long numberOfSamples = event -> d_erp -> nx; autoERP thee = Thing_new (ERP); event -> d_erp -> structSound :: v_copy (thee.peek()); for (long ichannel = 1; ichannel <= numberOfChannels; ichannel ++) { double *oldChannel = event -> d_erp -> z [ichannel]; double *newChannel = thy z [ichannel]; for (long isample = 1; isample <= numberOfSamples; isample ++) { newChannel [isample] = oldChannel [isample]; } } thy d_channelNames = NUMvector (1, thy ny); for (long ichan = 1; ichan <= thy ny; ichan ++) { thy d_channelNames [ichan] = Melder_wcsdup (d_channelNames [ichan]); } return thee.transfer(); } catch (MelderError) { Melder_throw (this, ": ERP not extracted."); } } ERP structERPTier :: f_toERP_mean () { try { long numberOfEvents = d_events -> size; if (numberOfEvents < 1) Melder_throw ("No events."); ERPPoint firstEvent = f_peekEvent (1); long numberOfChannels = firstEvent -> d_erp -> ny; long numberOfSamples = firstEvent -> d_erp -> nx; autoERP mean = Thing_new (ERP); firstEvent -> d_erp -> structSound :: v_copy (mean.peek()); for (long ievent = 2; ievent <= numberOfEvents; ievent ++) { ERPPoint event = f_peekEvent (ievent); for (long ichannel = 1; ichannel <= numberOfChannels; ichannel ++) { double *erpChannel = event -> d_erp -> z [ichannel]; double *meanChannel = mean -> z [ichannel]; for (long isample = 1; isample <= numberOfSamples; isample ++) { meanChannel [isample] += erpChannel [isample]; } } } double factor = 1.0 / numberOfEvents; for (long ichannel = 1; ichannel <= numberOfChannels; ichannel ++) { double *meanChannel = mean -> z [ichannel]; for (long isample = 1; isample <= numberOfSamples; isample ++) { meanChannel [isample] *= factor; } } mean -> d_channelNames = NUMvector (1, mean -> ny); for (long ichan = 1; ichan <= mean -> ny; ichan ++) { mean -> d_channelNames [ichan] = Melder_wcsdup (d_channelNames [ichan]); } return mean.transfer(); } catch (MelderError) { Melder_throw (this, ": mean not computed."); } } ERPTier structERPTier :: f_extractEventsWhereColumn_number (Table table, long columnNumber, int which_Melder_NUMBER, double criterion) { try { Table_checkSpecifiedColumnNumberWithinRange (table, columnNumber); Table_numericize_Assert (table, columnNumber); // extraction should work even if cells are not defined if (d_events -> size != table -> rows -> size) Melder_throw (this, " & ", table, ": the number of rows in the table (", table -> rows -> size, ") doesn't match the number of events (", d_events -> size, ")."); autoERPTier thee = Thing_new (ERPTier); Function_init (thee.peek(), this -> xmin, this -> xmax); thy d_numberOfChannels = this -> d_numberOfChannels; thy d_channelNames = NUMvector (1, thy d_numberOfChannels); for (long ichan = 1; ichan <= thy d_numberOfChannels; ichan ++) { thy d_channelNames [ichan] = Melder_wcsdup (this -> d_channelNames [ichan]); } thy d_events = SortedSetOfDouble_create (); for (long ievent = 1; ievent <= d_events -> size; ievent ++) { ERPPoint oldEvent = this -> f_peekEvent (ievent); TableRow row = table -> f_peekRow (ievent); if (Melder_numberMatchesCriterion (row -> cells [columnNumber]. number, which_Melder_NUMBER, criterion)) { autoERPPoint newEvent = Data_copy (oldEvent); Collection_addItem (thy d_events, newEvent.transfer()); } } if (thy d_events -> size == 0) { Melder_warning ("No event matches criterion."); } return thee.transfer(); } catch (MelderError) { Melder_throw (this, ": events not extracted."); } } ERPTier structERPTier :: f_extractEventsWhereColumn_string (Table table, long columnNumber, int which_Melder_STRING, const wchar *criterion) { try { Table_checkSpecifiedColumnNumberWithinRange (table, columnNumber); if (d_events -> size != table -> rows -> size) Melder_throw (this, " & ", table, ": the number of rows in the table (", table -> rows -> size, ") doesn't match the number of events (", d_events -> size, ")."); autoERPTier thee = Thing_new (ERPTier); Function_init (thee.peek(), this -> xmin, this -> xmax); thy d_numberOfChannels = this -> d_numberOfChannels; thy d_channelNames = NUMvector (1, thy d_numberOfChannels); for (long ichan = 1; ichan <= thy d_numberOfChannels; ichan ++) { thy d_channelNames [ichan] = Melder_wcsdup (this -> d_channelNames [ichan]); } thy d_events = SortedSetOfDouble_create (); for (long ievent = 1; ievent <= d_events -> size; ievent ++) { ERPPoint oldEvent = this -> f_peekEvent (ievent); TableRow row = table -> f_peekRow (ievent); if (Melder_stringMatchesCriterion (row -> cells [columnNumber]. string, which_Melder_STRING, criterion)) { autoERPPoint newEvent = Data_copy (oldEvent); Collection_addItem (thy d_events, newEvent.transfer()); } } if (thy d_events -> size == 0) { Melder_warning ("No event matches criterion."); } return thee.transfer(); } catch (MelderError) { Melder_throw (this, ": events not extracted."); } } /* End of file ERPTier.cpp */ sources_5316/EEG/ERPTier_def.h0000644000176700017670000000506511734344777014613 0ustar paulpaul/* ERPTier_def.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT ERPPoint oo_DEFINE_CLASS (ERPPoint, AnyPoint) oo_OBJECT (Sound, 2, d_erp) oo_END_CLASS (ERPPoint) #undef ooSTRUCT #define ooSTRUCT ERPTier oo_DEFINE_CLASS (ERPTier, Function) oo_COLLECTION (SortedSetOfDouble, d_events, ERPPoint, 0) oo_LONG (d_numberOfChannels) oo_STRING_VECTOR (d_channelNames, d_numberOfChannels) #if oo_DECLARING // functions: public: void f_init (double tmin, double tmax); long f_getChannelNumber (const wchar *channelName); void f_checkEventNumber (long eventNumber) { if (eventNumber < 1) Melder_throw ("The specified event number is ", eventNumber, " but should have been positive."); if (eventNumber > d_events -> size) Melder_throw ("The specified event number (", eventNumber, ") exceeds the number of events (", d_events -> size, ")."); } ERPPoint f_peekEvent (long i) { return static_cast (d_events -> item [i]); } double f_getMean (long pointNumber, long channelNumber, double tmin, double tmax); double f_getMean (long pointNumber, const wchar *channelName, double tmin, double tmax); void f_subtractBaseline (double tmin, double tmax); void f_rejectArtefacts (double threshold); ERP f_extractERP (long pointNumber); ERP f_toERP_mean (); ERPTier f_extractEventsWhereColumn_number (Table table, long columnNumber, int which_Melder_NUMBER, double criterion); ERPTier f_extractEventsWhereColumn_string (Table table, long columnNumber, int which_Melder_STRING, const wchar *criterion); // overridden methods: protected: virtual int v_domainQuantity () { return MelderQuantity_TIME_SECONDS; } virtual void v_shiftX (double xfrom, double xto); virtual void v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto); #endif oo_END_CLASS (ERPTier) #undef ooSTRUCT /* End of file ERPTier_def.h */ sources_5316/EEG/ERP.h0000644000176700017670000000156611665145033013136 0ustar paulpaul#ifndef _ERP_h_ #define _ERP_h_ /* ERP.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sound.h" #include "ERP_def.h" oo_CLASS_CREATE (ERP, Sound); /* End of file ERP.h */ #endif sources_5316/EEG/praat_EEG.cpp0000644000176700017670000005602611741314665014637 0ustar paulpaul/* praat_EEG.cpp * * Copyright (C) 2011-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "praat.h" #include "EEGWindow.h" #include "ERPWindow.h" #include "ERPTier.h" #include "SpectrumEditor.h" #undef iam #define iam iam_LOOP /***** EEG *****/ DIRECT (EEGs_concatenate) autoCollection eegs = praat_getSelectedObjects (); autoEEG thee = EEGs_concatenate (eegs.peek()); praat_new (thee.transfer(), L"chain"); END DIRECT (EEG_detrend) LOOP { iam (EEG); my f_detrend (); praat_dataChanged (me); } END FORM (EEG_editExternalElectrodeNames, L"Edit external electrode names", 0) WORD (L"External electrode 1", L"EXG1") WORD (L"External electrode 2", L"EXG2") WORD (L"External electrode 3", L"EXG3") WORD (L"External electrode 4", L"EXG4") WORD (L"External electrode 5", L"EXG5") WORD (L"External electrode 6", L"EXG6") WORD (L"External electrode 7", L"EXG7") WORD (L"External electrode 8", L"EXG8") OK int IOBJECT; LOOP { iam (EEG); SET_STRING (L"External electrode 1", my d_channelNames [my d_numberOfChannels - 15]) SET_STRING (L"External electrode 2", my d_channelNames [my d_numberOfChannels - 14]) SET_STRING (L"External electrode 3", my d_channelNames [my d_numberOfChannels - 13]) SET_STRING (L"External electrode 4", my d_channelNames [my d_numberOfChannels - 12]) SET_STRING (L"External electrode 5", my d_channelNames [my d_numberOfChannels - 11]) SET_STRING (L"External electrode 6", my d_channelNames [my d_numberOfChannels - 10]) SET_STRING (L"External electrode 7", my d_channelNames [my d_numberOfChannels - 9]) SET_STRING (L"External electrode 8", my d_channelNames [my d_numberOfChannels - 8]) } DO LOOP { iam (EEG); my f_setExternalElectrodeNames (GET_STRING (L"External electrode 1"), GET_STRING (L"External electrode 2"), GET_STRING (L"External electrode 3"), GET_STRING (L"External electrode 4"), GET_STRING (L"External electrode 5"), GET_STRING (L"External electrode 6"), GET_STRING (L"External electrode 7"), GET_STRING (L"External electrode 8")); praat_dataChanged (me); } END FORM (EEG_extractChannel, L"EEG: Extract channel", 0) SENTENCE (L"Channel name", L"Cz") OK DO LOOP { iam (EEG); const wchar *channelName = GET_STRING (L"Channel name"); autoEEG thee = my f_extractChannel (channelName); praat_new (thee.transfer(), my name, L"_", channelName); } END FORM (EEG_extractPart, L"EEG: Extract part", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"1.0") BOOLEAN (L"Preserve times", 0) OK DO LOOP { iam (EEG); autoEEG thee = my f_extractPart (GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_INTEGER (L"Preserve times")); praat_new (thee.transfer(), my name, L"_part"); } END DIRECT (EEG_extractSound) LOOP { iam (EEG); if (! my d_sound) Melder_throw (me, ": I don't contain a waveform."); autoSound thee = my f_extractSound (); praat_new (thee.transfer(), NULL); } END DIRECT (EEG_extractTextGrid) LOOP { iam (EEG); if (! my d_textgrid) Melder_throw (me, ": I don't contain marks."); autoTextGrid thee = my f_extractTextGrid (); praat_new (thee.transfer(), NULL); } END FORM (EEG_filter, L"Filter", 0) REAL (L"Low frequency (Hz)", L"1.0") REAL (L"Low width (Hz)", L"0.5") REAL (L"High frequency (Hz)", L"25.0") REAL (L"High width (Hz)", L"12.5") BOOLEAN (L"Notch at 50 Hz", true) OK DO LOOP { iam (EEG); my f_filter (GET_REAL (L"Low frequency"), GET_REAL (L"Low width"), GET_REAL (L"High frequency"), GET_REAL (L"High width"), GET_INTEGER (L"Notch at 50 Hz")); praat_dataChanged (me); } END FORM (EEG_getChannelName, L"Get channel name", 0) NATURAL (L"Channel number", L"1") OK DO LOOP { iam (EEG); long channelNumber = GET_INTEGER (L"Channel number"); if (channelNumber > my d_numberOfChannels) Melder_throw (me, ": there are only ", my d_numberOfChannels, " channels."); Melder_information (my d_channelNames [channelNumber]); } END FORM (EEG_getChannelNumber, L"Get channel number", 0) WORD (L"Channel name", L"Cz") OK DO LOOP { iam (EEG); Melder_information (Melder_integer (my f_getChannelNumber (GET_STRING (L"Channel name")))); } END FORM (EEG_setChannelName, L"Set channel name", 0) NATURAL (L"Channel number", L"1") WORD (L"New name", L"BLA") OK DO LOOP { iam (EEG); my f_setChannelName (GET_INTEGER (L"Channel number"), GET_STRING (L"New name")); praat_dataChanged (me); } END FORM (EEG_setChannelToZero, L"Set channel to zero", 0) SENTENCE (L"Channel", L"Iz") OK DO LOOP { iam (EEG); my f_setChannelToZero (GET_STRING (L"Channel")); praat_dataChanged (me); } END FORM (EEG_subtractMeanChannel, L"Subtract mean channel", 0) LABEL (L"label", L"Range of reference channels:") NATURAL (L"From channel", L"1") NATURAL (L"To channel", L"32") OK DO LOOP { iam (EEG); my f_subtractMeanChannel (GET_INTEGER (L"From channel"), GET_INTEGER (L"To channel")); praat_dataChanged (me); } END FORM (EEG_subtractReference, L"Subtract reference", 0) WORD (L"Reference channel 1", L"MASL") WORD (L"Reference channel 2 (optional)", L"MASR") OK DO LOOP { iam (EEG); my f_subtractReference (GET_STRING (L"Reference channel 1"), GET_STRING (L"Reference channel 2")); praat_dataChanged (me); } END FORM (EEG_to_ERPTier, L"To ERPTier", 0) REAL (L"From time (s)", L"-0.11") REAL (L"To time (s)", L"0.39") NATURAL (L"Marker bit", L"8") OK DO LOOP { iam (EEG); int markerBit = GET_INTEGER (L"Marker bit"); autoERPTier thee = EEG_to_ERPTier (me, GET_REAL (L"From time"), GET_REAL (L"To time"), markerBit); praat_new (thee.transfer(), my name, L"_bit", Melder_integer (markerBit)); } END static void cb_EEGWindow_publication (Editor editor, void *closure, Data publication) { (void) editor; (void) closure; /* * Keep the gate for error handling. */ try { praat_new (publication, NULL); praat_updateSelection (); if (Thing_member (publication, classSpectrum) && wcsequ (Thing_getName (publication), L"slice")) { int IOBJECT; LOOP { iam (Spectrum); autoSpectrumEditor editor2 = SpectrumEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); praat_installEditor (editor2.transfer(), IOBJECT); therror } } } catch (MelderError) { Melder_flushError (NULL); } } DIRECT (EEG_viewAndEdit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot view or edit an EEG from batch."); LOOP { iam (EEG); autoEEGWindow editor = EEGWindow_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); editor -> setPublicationCallback (cb_EEGWindow_publication, NULL); praat_installEditor (editor.transfer(), IOBJECT); therror } END /***** ERP *****/ FORM (ERP_draw, L"ERP: Draw", 0) SENTENCE (L"Channel name", L"Cz") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range", L"0.0 (= all)") REAL (L"left Voltage range (V)", L"10e-6") REAL (L"right Voltage range", L"-10e-6") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (ERP); me -> f_draw (GRAPHICS, GET_STRING (L"Channel name"), GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Voltage range"), GET_REAL (L"right Voltage range"), GET_INTEGER (L"Garnish")); } END FORM (ERP_formula, L"ERP: Formula", L"ERP: Formula...") LABEL (L"label1", L"! `x' is the time in seconds, `col' is the sample number.") LABEL (L"label2", L"x = x1 ! time associated with first sample") LABEL (L"label3", L"for col from 1 to ncol") LABEL (L"label4", L" self [col] = ...") TEXTFIELD (L"formula", L"self") LABEL (L"label5", L" x = x + dx") LABEL (L"label6", L"endfor") OK DO LOOP { iam (ERP); try { Matrix_formula (me, GET_STRING (L"formula"), interpreter, NULL); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); // in case of error, the ERP may have partially changed throw; } } END FORM (ERP_formula_part, L"ERP: Formula (part)", L"ERP: Formula...") REAL (L"From time", L"0.0") REAL (L"To time", L"0.0 (= all)") NATURAL (L"From channel", L"1") NATURAL (L"To channel", L"2") TEXTFIELD (L"formula", L"2 * self") OK DO LOOP { iam (ERP); try { Matrix_formula_part (me, GET_REAL (L"From time"), GET_REAL (L"To time"), GET_INTEGER (L"From channel") - 0.5, GET_INTEGER (L"To channel") + 0.5, GET_STRING (L"formula"), interpreter, NULL); praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); // in case of error, the ERP may have partially changed throw; } } END FORM (ERP_getChannelName, L"Get channel name", 0) NATURAL (L"Channel number", L"1") OK DO LOOP { iam (ERP); long channelNumber = GET_INTEGER (L"Channel number"); if (channelNumber > my ny) Melder_throw (me, ": there are only ", my ny, " channels."); Melder_information (my d_channelNames [channelNumber]); } END FORM (ERP_getChannelNumber, L"Get channel number", 0) WORD (L"Channel name", L"Cz") OK DO LOOP { iam (ERP); Melder_information (Melder_integer (my f_getChannelNumber (GET_STRING (L"Channel name")))); } END FORM (ERP_getMaximum, L"ERP: Get maximum", L"Sound: Get maximum...") SENTENCE (L"Channel name", L"Cz") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0 (= all)") RADIO (L"Interpolation", 4) RADIOBUTTON (L"None") RADIOBUTTON (L"Parabolic") RADIOBUTTON (L"Cubic") RADIOBUTTON (L"Sinc70") RADIOBUTTON (L"Sinc700") OK DO LOOP { iam (ERP); const wchar *channelName = GET_STRING (L"Channel name"); long channelNumber = my f_getChannelNumber (channelName); if (channelNumber == 0) Melder_throw (me, ": no channel named \"", channelName, "\"."); double maximum; Vector_getMaximumAndX (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), channelNumber, GET_INTEGER (L"Interpolation") - 1, & maximum, NULL); Melder_informationReal (maximum, L"Volt"); } END FORM (ERP_getMean, L"ERP: Get mean", L"ERP: Get mean...") SENTENCE (L"Channel name", L"Cz") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0 (= all)") OK DO LOOP { iam (ERP); const wchar *channelName = GET_STRING (L"Channel name"); long channelNumber = my f_getChannelNumber (channelName); if (channelNumber == 0) Melder_throw (me, ": no channel named \"", channelName, "\"."); double mean = Vector_getMean (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), channelNumber); Melder_informationReal (mean, L"Volt"); } END FORM (ERP_getMinimum, L"ERP: Get minimum", L"Sound: Get minimum...") SENTENCE (L"Channel name", L"Cz") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0 (= all)") RADIO (L"Interpolation", 4) RADIOBUTTON (L"None") RADIOBUTTON (L"Parabolic") RADIOBUTTON (L"Cubic") RADIOBUTTON (L"Sinc70") RADIOBUTTON (L"Sinc700") OK DO LOOP { iam (ERP); const wchar *channelName = GET_STRING (L"Channel name"); long channelNumber = my f_getChannelNumber (channelName); if (channelNumber == 0) Melder_throw (me, ": no channel named \"", channelName, "\"."); double minimum; Vector_getMinimumAndX (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), channelNumber, GET_INTEGER (L"Interpolation") - 1, & minimum, NULL); Melder_informationReal (minimum, L"Volt"); } END FORM (ERP_getTimeOfMaximum, L"ERP: Get time of maximum", L"Sound: Get time of maximum...") SENTENCE (L"Channel name", L"Cz") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0 (= all)") RADIO (L"Interpolation", 4) RADIOBUTTON (L"None") RADIOBUTTON (L"Parabolic") RADIOBUTTON (L"Cubic") RADIOBUTTON (L"Sinc70") RADIOBUTTON (L"Sinc700") OK DO LOOP { iam (ERP); const wchar *channelName = GET_STRING (L"Channel name"); long channelNumber = my f_getChannelNumber (channelName); if (channelNumber == 0) Melder_throw (me, ": no channel named \"", channelName, "\"."); double timeOfMaximum; Vector_getMaximumAndX (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), channelNumber, GET_INTEGER (L"Interpolation") - 1, NULL, & timeOfMaximum); Melder_informationReal (timeOfMaximum, L"seconds"); } END FORM (ERP_getTimeOfMinimum, L"ERP: Get time of minimum", L"Sound: Get time of minimum...") SENTENCE (L"Channel name", L"Cz") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0 (= all)") RADIO (L"Interpolation", 4) RADIOBUTTON (L"None") RADIOBUTTON (L"Parabolic") RADIOBUTTON (L"Cubic") RADIOBUTTON (L"Sinc70") RADIOBUTTON (L"Sinc700") OK DO LOOP { iam (ERP); const wchar *channelName = GET_STRING (L"Channel name"); long channelNumber = my f_getChannelNumber (channelName); if (channelNumber == 0) Melder_throw (me, ": no channel named \"", channelName, "\"."); double timeOfMinimum; Vector_getMinimumAndX (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), channelNumber, GET_INTEGER (L"Interpolation") - 1, NULL, & timeOfMinimum); Melder_informationReal (timeOfMinimum, L"seconds"); } END static void cb_ERPWindow_publication (Editor editor, void *closure, Data publication) { (void) editor; (void) closure; /* * Keep the gate for error handling. */ try { praat_new (publication, NULL); praat_updateSelection (); if (Thing_member (publication, classSpectrum) && wcsequ (Thing_getName (publication), L"slice")) { int IOBJECT; LOOP { iam (Spectrum); autoSpectrumEditor editor2 = SpectrumEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); praat_installEditor (editor2.transfer(), IOBJECT); therror } } } catch (MelderError) { Melder_flushError (NULL); } } DIRECT (ERP_viewAndEdit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot view or edit an ERP from batch."); LOOP { iam (ERP); autoERPWindow editor = ERPWindow_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); editor -> setPublicationCallback (cb_ERPWindow_publication, NULL); praat_installEditor (editor.transfer(), IOBJECT); therror } END /***** ERPTier *****/ FORM (ERPTier_getChannelName, L"Get channel name", 0) NATURAL (L"Channel number", L"1") OK DO LOOP { iam (ERPTier); long channelNumber = GET_INTEGER (L"Channel number"); if (channelNumber > my d_numberOfChannels) Melder_throw (me, ": there are only ", my d_numberOfChannels, " channels."); Melder_information (my d_channelNames [channelNumber]); } END FORM (ERPTier_getChannelNumber, L"Get channel number", 0) WORD (L"Channel name", L"Cz") OK DO LOOP { iam (ERPTier); Melder_information (Melder_integer (my f_getChannelNumber (GET_STRING (L"Channel name")))); } END FORM (ERPTier_getMean, L"ERPTier: Get mean", L"ERPTier: Get mean...") NATURAL (L"Point number", L"1") SENTENCE (L"Channel name", L"Cz") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0 (= all)") OK DO LOOP { iam (ERPTier); double mean = my f_getMean (GET_INTEGER (L"Point number"), GET_STRING (L"Channel name"), GET_REAL (L"left Time range"), GET_REAL (L"right Time range")); Melder_informationReal (mean, L"Volt"); } END FORM (ERPTier_rejectArtefacts, L"Reject artefacts", 0) POSITIVE (L"Threshold (V)", L"75e-6") OK DO LOOP { iam (ERPTier); my f_rejectArtefacts (GET_REAL (L"Threshold")); praat_dataChanged (me); } END FORM (ERPTier_subtractBaseline, L"Subtract baseline", 0) REAL (L"From time (s)", L"-0.11") REAL (L"To time (s)", L"0.0") OK DO LOOP { iam (ERPTier); my f_subtractBaseline (GET_REAL (L"From time"), GET_REAL (L"To time")); praat_dataChanged (me); } END FORM (ERPTier_to_ERP, L"ERPTier: To ERP", 0) NATURAL (L"Event number", L"1") OK DO LOOP { iam (ERPTier); autoERP thee = my f_extractERP (GET_INTEGER (L"Event number")); praat_new (thee.transfer(), my name, L"_mean"); } END DIRECT (ERPTier_to_ERP_mean) LOOP { iam (ERPTier); autoERP thee = my f_toERP_mean (); praat_new (thee.transfer(), my name, L"_mean"); } END /***** ERPTier & Table *****/ FORM (ERPTier_Table_extractEventsWhereColumn_number, L"Extract events where column (number)", 0) WORD (L"Extract all events where column...", L"") RADIO_ENUM (L"...is...", kMelder_number, DEFAULT) REAL (L"...the number", L"0.0") OK DO ERPTier erpTier = FIRST (ERPTier); Table table = FIRST (Table); long columnNumber = Table_getColumnIndexFromColumnLabel (table, GET_STRING (L"Extract all events where column...")); autoERPTier thee = erpTier -> f_extractEventsWhereColumn_number (table, columnNumber, GET_ENUM (kMelder_number, L"...is..."), GET_REAL (L"...the number")); praat_new (thee.transfer(), erpTier -> name); END FORM (ERPTier_Table_extractEventsWhereColumn_text, L"Extract events where column (text)", 0) WORD (L"Extract all events where column...", L"") OPTIONMENU_ENUM (L"...", kMelder_string, DEFAULT) SENTENCE (L"...the text", L"hi") OK DO ERPTier erpTier = FIRST (ERPTier); Table table = FIRST (Table); long columnNumber = Table_getColumnIndexFromColumnLabel (table, GET_STRING (L"Extract all events where column...")); autoERPTier thee = erpTier -> f_extractEventsWhereColumn_string (table, columnNumber, GET_ENUM (kMelder_string, L"..."), GET_STRING (L"...the text")); praat_new (thee.transfer(), erpTier -> name); END /***** Help menus *****/ DIRECT (EEG_help) Melder_help (L"EEG"); END DIRECT (ERPTier_help) Melder_help (L"ERPTier"); END /***** file recognizers *****/ static Any bdfFileRecognizer (int nread, const char *header, MelderFile file) { const wchar *fileName = MelderFile_name (file); bool isBdfFile = wcsstr (fileName, L".bdf") != NULL || wcsstr (fileName, L".BDF") != NULL; bool isEdfFile = wcsstr (fileName, L".edf") != NULL || wcsstr (fileName, L".EDF") != NULL; if (nread < 512 || (! isBdfFile && ! isEdfFile)) return NULL; return EEG_readFromBdfFile (file); } /***** buttons *****/ void praat_TimeTier_query_init (ClassInfo klas); // Query buttons for time-based subclasses of AnyTier. void praat_EEG_init (void); void praat_EEG_init (void) { Thing_recognizeClassesByName (classEEG, classERPTier, classERP, NULL); Data_recognizeFileType (bdfFileRecognizer); praat_addAction1 (classEEG, 0, L"EEG help", 0, 0, DO_EEG_help); praat_addAction1 (classEEG, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_EEG_viewAndEdit); praat_addAction1 (classEEG, 0, L"Query -", 0, 0, 0); praat_addAction1 (classEEG, 0, L"Get channel name...", 0, 1, DO_EEG_getChannelName); praat_addAction1 (classEEG, 0, L"Get channel number...", 0, 1, DO_EEG_getChannelNumber); praat_addAction1 (classEEG, 0, L"Modify -", 0, 0, 0); praat_addAction1 (classEEG, 0, L"Set channel name...", 0, 1, DO_EEG_setChannelName); praat_addAction1 (classEEG, 1, L"Edit external electrode names...", 0, 1, DO_EEG_editExternalElectrodeNames); praat_addAction1 (classEEG, 0, L"-- processing --", 0, 1, DO_EEG_detrend); praat_addAction1 (classEEG, 0, L"Subtract reference...", 0, 1, DO_EEG_subtractReference); praat_addAction1 (classEEG, 0, L"Subtract mean channel...", 0, 1, DO_EEG_subtractMeanChannel); praat_addAction1 (classEEG, 0, L"Detrend", 0, 1, DO_EEG_detrend); praat_addAction1 (classEEG, 0, L"Filter...", 0, 1, DO_EEG_filter); praat_addAction1 (classEEG, 0, L"Set channel to zero...", 0, 1, DO_EEG_setChannelToZero); praat_addAction1 (classEEG, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classEEG, 0, L"Extract channel...", 0, 0, DO_EEG_extractChannel); praat_addAction1 (classEEG, 1, L"Extract part...", 0, 0, DO_EEG_extractPart); praat_addAction1 (classEEG, 0, L"To ERPTier...", 0, 0, DO_EEG_to_ERPTier); praat_addAction1 (classEEG, 0, L"Synthesize", 0, 0, 0); praat_addAction1 (classEEG, 0, L"Concatenate", 0, 0, DO_EEGs_concatenate); praat_addAction1 (classEEG, 0, L"Hack -", 0, 0, 0); praat_addAction1 (classEEG, 0, L"Extract waveforms as Sound", 0, 1, DO_EEG_extractSound); praat_addAction1 (classEEG, 0, L"Extract marks as TextGrid", 0, 1, DO_EEG_extractTextGrid); praat_addAction1 (classERP, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_ERP_viewAndEdit); praat_addAction1 (classERP, 0, L"Draw...", 0, 0, DO_ERP_draw); praat_addAction1 (classERP, 0, L"Query -", 0, 0, 0); praat_addAction1 (classERP, 0, L"Get channel name...", 0, 1, DO_ERP_getChannelName); praat_addAction1 (classERP, 0, L"Get channel number...", 0, 1, DO_ERP_getChannelNumber); praat_addAction1 (classERP, 0, L"-- get shape --", 0, 1, 0); praat_addAction1 (classERP, 0, L"Get minimum...", 0, 1, DO_ERP_getMinimum); praat_addAction1 (classERP, 0, L"Get time of minimum...", 0, 1, DO_ERP_getTimeOfMinimum); praat_addAction1 (classERP, 0, L"Get maximum...", 0, 1, DO_ERP_getMaximum); praat_addAction1 (classERP, 0, L"Get time of maximum...", 0, 1, DO_ERP_getTimeOfMaximum); praat_addAction1 (classERP, 0, L"-- get statistics --", 0, 1, 0); praat_addAction1 (classERP, 0, L"Get mean...", 0, 1, DO_ERP_getMean); praat_addAction1 (classERP, 0, L"Modify -", 0, 0, 0); praat_addAction1 (classERP, 0, L"Formula...", 0, 1, DO_ERP_formula); praat_addAction1 (classERP, 0, L"Formula (part)...", 0, 1, DO_ERP_formula_part); // praat_addAction1 (classERP, 0, L"Analyse -", 0, 0, 0); // praat_addAction1 (classERP, 0, L"To ERP (difference)", 0, 1, DO_ERP_to_ERP_difference); // praat_addAction1 (classERP, 0, L"To ERP (mean)", 0, 1, DO_ERP_to_ERP_mean); praat_addAction1 (classERPTier, 0, L"ERPTier help", 0, 0, DO_ERPTier_help); // praat_addAction1 (classERPTier, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_ERPTier_viewAndEdit); praat_addAction1 (classERPTier, 0, L"Query -", 0, 0, 0); praat_TimeTier_query_init (classERPTier); praat_addAction1 (classERPTier, 0, L"-- channel names --", 0, 1, 0); praat_addAction1 (classERPTier, 0, L"Get channel name...", 0, 1, DO_ERPTier_getChannelName); praat_addAction1 (classERPTier, 0, L"Get channel number...", 0, 1, DO_ERPTier_getChannelNumber); praat_addAction1 (classERPTier, 0, L"-- erp --", 0, 1, 0); praat_addAction1 (classERPTier, 0, L"Get mean...", 0, 1, DO_ERPTier_getMean); praat_addAction1 (classERPTier, 0, L"Modify -", 0, 0, 0); praat_addAction1 (classERPTier, 0, L"Subtract baseline...", 0, 1, DO_ERPTier_subtractBaseline); praat_addAction1 (classERPTier, 0, L"Reject artefacts...", 0, 1, DO_ERPTier_rejectArtefacts); praat_addAction1 (classERPTier, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classERPTier, 0, L"Extract ERP...", 0, 0, DO_ERPTier_to_ERP); praat_addAction1 (classERPTier, 0, L"To ERP (mean)", 0, 0, DO_ERPTier_to_ERP_mean); praat_addAction2 (classERPTier, 1, classTable, 1, L"Extract -", 0, 0, 0); praat_addAction2 (classERPTier, 1, classTable, 1, L"Extract events where column (number)...", 0, 1, DO_ERPTier_Table_extractEventsWhereColumn_number); praat_addAction2 (classERPTier, 1, classTable, 1, L"Extract events where column (text)...", 0, 1, DO_ERPTier_Table_extractEventsWhereColumn_text); } /* End of file praat_EEG.cpp */ sources_5316/EEG/EEG_def.h0000644000176700017670000000531411741313516013717 0ustar paulpaul/* EEG_def.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT EEG oo_DEFINE_CLASS (EEG, Function) oo_LONG (d_numberOfChannels) oo_STRING_VECTOR (d_channelNames, d_numberOfChannels) oo_OBJECT (Sound, 2, d_sound) oo_OBJECT (TextGrid, 0, d_textgrid) #if oo_DECLARING // functions: public: void f_init (double tmin, double tmax); long f_getChannelNumber (const wchar *channelName); void f_setChannelName (long channelNumber, const wchar *a_name); long f_getNumberOfCapElectrodes () { return (d_numberOfChannels - 1) & ~ 15L; } // BUG long f_getNumberOfExternalElectrodes () { return d_numberOfChannels - f_getNumberOfCapElectrodes () - f_getNumberOfExtraSensors (); } long f_getNumberOfExtraSensors () { return d_numberOfChannels & 1 ? 1 : 8; } // BUG void f_setExternalElectrodeNames (const wchar *nameExg1, const wchar *nameExg2, const wchar *nameExg3, const wchar *nameExg4, const wchar *nameExg5, const wchar *nameExg6, const wchar *nameExg7, const wchar *nameExg8); void f_detrend (); void f_filter (double lowFrequency, double lowWidth, double highFrequency, double highWidth, bool doNotch50Hz); void f_subtractReference (const wchar *channelNumber1, const wchar *channelNumber2); void f_subtractMeanChannel (long fromChannel, long toChannel); void f_setChannelToZero (long channelNumber); void f_setChannelToZero (const wchar *channelName); EEG f_extractChannel (long channelNumber); EEG f_extractChannel (const wchar *channelName); Sound f_extractSound () { return Data_copy (d_sound); } TextGrid f_extractTextGrid () { return Data_copy (d_textgrid); } EEG f_extractPart (double tmin, double tmax, bool preserveTimes); // overridden methods: protected: virtual void v_info (); virtual int v_domainQuantity () { return MelderQuantity_TIME_SECONDS; } virtual void v_shiftX (double xfrom, double xto); virtual void v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto); #endif oo_END_CLASS (EEG) #undef ooSTRUCT /* End of file EEG_def.h */ sources_5316/EEG/EEGWindow.h0000644000176700017670000000312111741321357014265 0ustar paulpaul#ifndef _EEGWindow_h_ #define _EEGWindow_h_ /* EEGWindow.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "TextGridEditor.h" #include "EEG.h" Thing_define (EEGWindow, TextGridEditor) { // new data: public: EEG d_eeg; GuiObject d_extractSelectedEEGPreserveTimesButton, d_extractSelectedEEGTimeFromZeroButton; // functions: public: void f_init (GuiObject parent, const wchar *title, EEG eeg); // overridden methods: protected: virtual bool v_hasAnalysis () { return false; } virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual const wchar * v_getChannelName (long channelNumber); virtual void v_createMenuItems_file_extract (EditorMenu menu); virtual void v_updateMenuItems_file (); }; EEGWindow EEGWindow_create (GuiObject parent, const wchar *title, EEG eeg); void EEGWindow_preferences (void); /* End of file EEGWindow.h */ #endif sources_5316/EEG/manual_EEG.cpp0000644000176700017670000001617011741316546015001 0ustar paulpaul/* manual_EEG.cpp * * Copyright (C) 2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" void manual_EEG_init (ManPages me); void manual_EEG_init (ManPages me) { MAN_BEGIN (L"EEG", L"ppgb", 20120511) INTRO (L"EEG means electro-encephalography: brain potentials recorded via e.g. 32 or 64 electrodes on the scalp. " "In Praat, an EEG object looks like a combination of a Sound object with e.g. 32 or 64 channels " "and a TextGrid object that marks the events.") ENTRY (L"1. How to get an EEG object in Praat") NORMAL (L"You typically create an EEG object in Praat by opening a BDF/EDF file with @@Read from file...@. " "Praat tries to read the whole file into memory, so you may want to work with a 64-bit edition of Praat " "if you want to avoid \"out of memory\" messages.") NORMAL (L"After you do ##Read from file...#, an EEG object will appear in the list of objects.") ENTRY (L"2. How to look into an EEG object") NORMAL (L"Once you have an EEG object in the list, you can click ##View & Edit# to look into it. " "You will typically see the first 8 channels, but you scroll to the other channels by clicking on the up and down arrows. " "You can scroll and zoom in the same way as in a Sound window.") NORMAL (L"The channel names that you see are often A1, A2, ... A32, B1, B2, ... B32, C1, C2, ... C32, and so on. These represent the cap electrodes. " "If the number of cap electrodes is 32, though, the channel names are Fp1, AF3, ... Cz, " "and if it is 64, the channel names are Fp1, AF7, ... O2. You can change these names with " "##Set channel name...# from the #Modify menu.") NORMAL (L"Below the cap electrodes you may see a number of channels for the external electrodes. " "These are typically named EXG1, EXG2, ... EXG8, but you can change these names with ##Edit external electrode names...# " "from the #Modify menu.") NORMAL (L"Below the external electrodes you may see a number of special channels, " "perhaps named GSR1, GSR2, Erg1, Erg2, Resp, Plet, Temp, and Status. " "These represent recordings from other sensors than the electrodes.") NORMAL (L"The Status channel is special. It is the 8-bit digital signal that you fed to your EEG apparatus. " "When reading the BDF file, Praat extracts all 8 bits from this status signal, " "and these 8 bits are shown in the EEG window as TextGrid interval tiers named S1, S2, ... S8. " "These bits are the place to mark events. For instance, in our lab we use S8 to mark any event, " "S5 to mark a \"standard\" event, and S4 to mark a \"deviant\" event.") ENTRY (L"3. What to do to an EEG object") NORMAL (L"The raw EEG signal that you have read from a file is typically quite noisy and may have a very large " "DC (direct-current) component as compared to the small vibrations that you are interested in. " "There are several ways to clean it up.") NORMAL (L"##Subtracting a reference signal.# The voltage on the whole scalp may rise and fall in time. " "You are unlikely to be interested in these global movements; instead, you are likely to be interested only " "in the voltage movements on the brain-influenced part of the scalp (the cap electrodes) " "with respect to the voltage movements on the non-brain-influenced part of the scalp (the external electrodes). " "If you have external electrode recordings that include the left and right mastoids, you can use these channels as a %%reference signal%, i.e., " "you can use ##Subtract reference...# to subtract the average of the two mastoid channels from all electrode channels (including the external electrodes themselves). " "If you have no such recordings, you can still regard the average of a range of electrode channels as a reference signal, " "and use ##Subtract mean channel...# to subtract this from each electrode channel.") NORMAL (L"##Detrending.# With #Detrend, you subtract from each electrode channel a line in such a way that the first sample and the last sample become zero. " "Detrending and reference subtraction can be performed in either order.") NORMAL (L"##Filtering.# With ##Filter...#, you band-pass filter each electrode channel. Filtering has to be done after detrending, but " "filtering and reference subtraction can be performed in either order.") ENTRY (L"4. How to do an ERP analysis") NORMAL (L"An ERP is an Event-Related Potential. Events are marked somewhere in S1, S2, ... S8. In the above example, " "we extract all the \"deviant\" events by doing ##To ERPTier...#, setting ##From time# to -0.11 seconds, " "##To Time# to 0.39 seconds, and ##Marker bit# to 4. This way, an ERPTier object appears in the list, containing " "the parts of the EEG signal that lie in a time window of [-0.11, 0.39] seconds around each event on the S4 (deviant) tier. " "Thus, if S4 contains 150 events, the resulting ERPTier will contain 150 pieces of the original EEG signal (without the extra sensors).") NORMAL (L"You are typically interested in the part of each ERP in the ERPTier after the event. " "That is, you are probably interested in how this part compares to the part not influenced by the event, " "i.e. the part before the event. To make this comparison easier, you can do ##Subtract baseline...#: " "the waveform of the ERP will be moved up or down in such a way that the average amplitude of the part between the specified times becomes zero; " "the times you will typically fill in here are the starting time of the ERP (a negative number) and the time of the event (0.0).") NORMAL (L"After you subtract the baseline, the part after the event contains the interesting part of the ERP: " "even its sign (positive or negative) is meaningful now. Some ERPs, however, will contain very large positive or negative peaks " "because of eye movements and other disturbing signals. To remove those ERPs from the ERPTier, " "do ##Reject artefacts...#, while specifying the amount by which you allow the amplitude of an ERP to go above or below zero.") NORMAL (L"Once you have an ERPTier, you can extract each of the 150 ERPs from it with ##Extract ERP...#. " "It is perhaps more interesting to compute the average of all those 150 ERPs with ##To ERP (mean)#. " "These commands put a new ERP object in the list.") NORMAL (L"Once you have an ERP object, you can look into it with ##View & Edit#. " "If you want to see in the ERP window the scalp distribution at the time of the cursor, or the average scalp distribution in the selected time stretch, " "you have to switch on ##Show selection viewer# in the #Preferences window (available from the #File menu).") MAN_END } /* End of file manual_EEG.cpp */ sources_5316/EEG/EEG.cpp0000644000176700017670000005322711741314057013443 0ustar paulpaul/* EEG.cpp * * Copyright (C) 2011-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "EEG.h" #include "Sound_and_Spectrum.h" #include "oo_DESTROY.h" #include "EEG_def.h" #include "oo_COPY.h" #include "EEG_def.h" #include "oo_EQUAL.h" #include "EEG_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "EEG_def.h" #include "oo_WRITE_TEXT.h" #include "EEG_def.h" #include "oo_READ_TEXT.h" #include "EEG_def.h" #include "oo_WRITE_BINARY.h" #include "EEG_def.h" #include "oo_READ_BINARY.h" #include "EEG_def.h" #include "oo_DESCRIPTION.h" #include "EEG_def.h" Thing_implement (EEG, Function, 0); void structEEG :: v_info () { structData :: v_info (); MelderInfo_writeLine1 (L"Time domain:"); MelderInfo_writeLine3 (L" Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine3 (L" End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine3 (L" Total duration: ", Melder_double (xmax - xmin), L" seconds"); if (d_sound != NULL) { MelderInfo_writeLine1 (L"Time sampling of the signal:"); MelderInfo_writeLine2 (L" Number of samples: ", Melder_integer (d_sound -> nx)); MelderInfo_writeLine3 (L" Sampling period: ", Melder_double (d_sound -> dx), L" seconds"); MelderInfo_writeLine3 (L" Sampling frequency: ", Melder_single (1.0 / d_sound -> dx), L" Hz"); MelderInfo_writeLine3 (L" First sample centred at: ", Melder_double (d_sound -> x1), L" seconds"); } MelderInfo_writeLine2 (L"Number of cap electrodes: ", Melder_integer (f_getNumberOfCapElectrodes ())); MelderInfo_writeLine2 (L"Number of external electrodes: ", Melder_integer (f_getNumberOfExternalElectrodes ())); MelderInfo_writeLine2 (L"Number of extra sensors: ", Melder_integer (f_getNumberOfExtraSensors ())); } void structEEG :: v_shiftX (double xfrom, double xto) { EEG_Parent :: v_shiftX (xfrom, xto); if (d_sound != NULL) Function_shiftXTo (d_sound, xfrom, xto); if (d_textgrid != NULL) Function_shiftXTo (d_textgrid, xfrom, xto); } void structEEG :: v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto) { EEG_Parent :: v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); if (d_sound != NULL) d_sound -> v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); if (d_textgrid != NULL) d_textgrid -> v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); } EEG EEG_create (double tmin, double tmax) { try { autoEEG me = Thing_new (EEG); my xmin = tmin; my xmax = tmax; return me.transfer(); } catch (MelderError) { Melder_throw ("EEG object not created."); } } long structEEG :: f_getChannelNumber (const wchar *channelName) { for (long ichan = 1; ichan <= d_numberOfChannels; ichan ++) { if (Melder_wcsequ (d_channelNames [ichan], channelName)) { return ichan; } } return 0; } EEG EEG_readFromBdfFile (MelderFile file) { try { autofile f = Melder_fopen (file, "rb"); char buffer [81]; fread (buffer, 1, 8, f); buffer [8] = '\0'; fread (buffer, 1, 80, f); buffer [80] = '\0'; //Melder_casual ("Local subject identification: \"%s\"", buffer); fread (buffer, 1, 80, f); buffer [80] = '\0'; //Melder_casual ("Local recording identification: \"%s\"", buffer); fread (buffer, 1, 8, f); buffer [8] = '\0'; //Melder_casual ("Start date of recording: \"%s\"", buffer); fread (buffer, 1, 8, f); buffer [8] = '\0'; //Melder_casual ("Start time of recording: \"%s\"", buffer); fread (buffer, 1, 8, f); buffer [8] = '\0'; long numberOfBytesInHeaderRecord = atol (buffer); //Melder_casual ("Number of bytes in header record: %ld", numberOfBytesInHeaderRecord); fread (buffer, 1, 44, f); buffer [44] = '\0'; //Melder_casual ("Version of data format: \"%s\"", buffer); fread (buffer, 1, 8, f); buffer [8] = '\0'; long numberOfDataRecords = strtol (buffer, NULL, 10); //Melder_casual ("Number of data records: %ld", numberOfDataRecords); fread (buffer, 1, 8, f); buffer [8] = '\0'; double durationOfDataRecord = atof (buffer); //Melder_casual ("Duration of a data record: \"%f\"", durationOfDataRecord); fread (buffer, 1, 4, f); buffer [4] = '\0'; long numberOfChannels = atol (buffer); //Melder_casual ("Number of channels in data record: %ld", numberOfChannels); if (numberOfBytesInHeaderRecord != (numberOfChannels + 1) * 256) Melder_throw ("Number of bytes in header record (", numberOfBytesInHeaderRecord, ") doesn't match number of channels (", numberOfChannels, ")."); autostringvector channelNames (1, numberOfChannels); for (long ichannel = 1; ichannel <= numberOfChannels; ichannel ++) { fread (buffer, 1, 16, f); buffer [16] = '\0'; // labels of the channels /* * Strip all final spaces. */ for (int i = 15; i >= 0; i --) { if (buffer [i] == ' ') { buffer [i] = '\0'; } else { break; } } channelNames [ichannel] = Melder_wcsdup (Melder_peekUtf8ToWcs (buffer)); } double samplingFrequency = NUMundefined; for (long channel = 1; channel <= numberOfChannels; channel ++) { fread (buffer, 1, 80, f); buffer [80] = '\0'; // transducer type } for (long channel = 1; channel <= numberOfChannels; channel ++) { fread (buffer, 1, 8, f); buffer [8] = '\0'; // physical dimension of channels } autoNUMvector physicalMinimum (1, numberOfChannels); for (long ichannel = 1; ichannel <= numberOfChannels; ichannel ++) { fread (buffer, 1, 8, f); buffer [8] = '\0'; physicalMinimum [ichannel] = atof (buffer); } autoNUMvector physicalMaximum (1, numberOfChannels); for (long ichannel = 1; ichannel <= numberOfChannels; ichannel ++) { fread (buffer, 1, 8, f); buffer [8] = '\0'; physicalMaximum [ichannel] = atof (buffer); } autoNUMvector digitalMinimum (1, numberOfChannels); for (long ichannel = 1; ichannel <= numberOfChannels; ichannel ++) { fread (buffer, 1, 8, f); buffer [8] = '\0'; digitalMinimum [ichannel] = atof (buffer); } autoNUMvector digitalMaximum (1, numberOfChannels); for (long ichannel = 1; ichannel <= numberOfChannels; ichannel ++) { fread (buffer, 1, 8, f); buffer [8] = '\0'; digitalMaximum [ichannel] = atof (buffer); } for (long channel = 1; channel <= numberOfChannels; channel ++) { fread (buffer, 1, 80, f); buffer [80] = '\0'; // prefiltering } long numberOfSamplesPerDataRecord = 0; for (long channel = 1; channel <= numberOfChannels; channel ++) { fread (buffer, 1, 8, f); buffer [8] = '\0'; // number of samples in each data record long numberOfSamplesInThisDataRecord = atol (buffer); if (samplingFrequency == NUMundefined) { numberOfSamplesPerDataRecord = numberOfSamplesInThisDataRecord; samplingFrequency = numberOfSamplesInThisDataRecord / durationOfDataRecord; } if (numberOfSamplesInThisDataRecord / durationOfDataRecord != samplingFrequency) Melder_throw (L"Number of samples per data record in channel ", channel, " (", numberOfSamplesInThisDataRecord, ") doesn't match sampling frequency of channel 1 (", samplingFrequency, ")."); } for (long channel = 1; channel <= numberOfChannels; channel ++) { fread (buffer, 1, 32, f); buffer [32] = '\0'; // reserved } double duration = numberOfDataRecords * durationOfDataRecord; autoEEG him = EEG_create (0, duration); his d_numberOfChannels = numberOfChannels; autoSound me = Sound_createSimple (numberOfChannels, duration, samplingFrequency); for (long record = 1; record <= numberOfDataRecords; record ++) { for (long channel = 1; channel <= numberOfChannels; channel ++) { double factor = channel == numberOfChannels ? 1.0 : physicalMinimum [channel] / digitalMinimum [channel]; if (channel < numberOfChannels - his f_getNumberOfExtraSensors ()) factor /= 1000000.0; for (long i = 1; i <= numberOfSamplesPerDataRecord; i ++) { long sample = i + (record - 1) * numberOfSamplesPerDataRecord; Melder_assert (sample <= my nx); my z [channel] [sample] = bingeti3LE (f) * factor; therror } } } autoTextGrid thee = TextGrid_create (0, duration, L"S1 S2 S3 S4 S5 S6 S7 S8", L""); for (int bit = 1; bit <= 8; bit ++) { unsigned long bitValue = 1 << (bit - 1); IntervalTier tier = (IntervalTier) thy tiers -> item [bit]; for (long i = 1; i <= my nx; i ++) { unsigned long previousValue = i == 1 ? 0 : (long) my z [numberOfChannels] [i - 1]; unsigned long thisValue = (long) my z [numberOfChannels] [i]; if ((thisValue & bitValue) != (previousValue & bitValue)) { double time = i == 1 ? 0.0 : my x1 + (i - 1.5) * my dx; if (time != 0.0) TextGrid_insertBoundary (thee.peek(), bit, time); if ((thisValue & bitValue) != 0) TextGrid_setIntervalText (thee.peek(), bit, tier -> intervals -> size, L"1"); } } } f.close (file); his d_channelNames = channelNames.transfer(); his d_sound = me.transfer(); his d_textgrid = thee.transfer(); if (his f_getNumberOfCapElectrodes () == 32) { his f_setChannelName (1, L"Fp1"); his f_setChannelName (2, L"AF3"); his f_setChannelName (3, L"F7"); his f_setChannelName (4, L"F3"); his f_setChannelName (5, L"FC1"); his f_setChannelName (6, L"FC5"); his f_setChannelName (7, L"T7"); his f_setChannelName (8, L"C3"); his f_setChannelName (9, L"CP1"); his f_setChannelName (10, L"CP5"); his f_setChannelName (11, L"P7"); his f_setChannelName (12, L"P3"); his f_setChannelName (13, L"Pz"); his f_setChannelName (14, L"PO3"); his f_setChannelName (15, L"O1"); his f_setChannelName (16, L"Oz"); his f_setChannelName (17, L"O2"); his f_setChannelName (18, L"PO4"); his f_setChannelName (19, L"P4"); his f_setChannelName (20, L"P8"); his f_setChannelName (21, L"CP6"); his f_setChannelName (22, L"CP2"); his f_setChannelName (23, L"C4"); his f_setChannelName (24, L"T8"); his f_setChannelName (25, L"FC6"); his f_setChannelName (26, L"FC2"); his f_setChannelName (27, L"F4"); his f_setChannelName (28, L"F8"); his f_setChannelName (29, L"AF4"); his f_setChannelName (30, L"Fp2"); his f_setChannelName (31, L"Fz"); his f_setChannelName (32, L"Cz"); } else if (his f_getNumberOfCapElectrodes () == 64) { his f_setChannelName (1, L"Fp1"); his f_setChannelName (2, L"AF7"); his f_setChannelName (3, L"AF3"); his f_setChannelName (4, L"F1"); his f_setChannelName (5, L"F3"); his f_setChannelName (6, L"F5"); his f_setChannelName (7, L"F7"); his f_setChannelName (8, L"FT7"); his f_setChannelName (9, L"FC5"); his f_setChannelName (10, L"FC3"); his f_setChannelName (11, L"FC1"); his f_setChannelName (12, L"C1"); his f_setChannelName (13, L"C3"); his f_setChannelName (14, L"C5"); his f_setChannelName (15, L"T7"); his f_setChannelName (16, L"TP7"); his f_setChannelName (17, L"CP5"); his f_setChannelName (18, L"CP3"); his f_setChannelName (19, L"CP1"); his f_setChannelName (20, L"P1"); his f_setChannelName (21, L"P3"); his f_setChannelName (22, L"P5"); his f_setChannelName (23, L"P7"); his f_setChannelName (24, L"P9"); his f_setChannelName (25, L"PO7"); his f_setChannelName (26, L"PO3"); his f_setChannelName (27, L"O1"); his f_setChannelName (28, L"Iz"); his f_setChannelName (29, L"Oz"); his f_setChannelName (30, L"POz"); his f_setChannelName (31, L"Pz"); his f_setChannelName (32, L"CPz"); his f_setChannelName (33, L"Fpz"); his f_setChannelName (34, L"Fp2"); his f_setChannelName (35, L"AF8"); his f_setChannelName (36, L"AF4"); his f_setChannelName (37, L"AFz"); his f_setChannelName (38, L"Fz"); his f_setChannelName (39, L"F2"); his f_setChannelName (40, L"F4"); his f_setChannelName (41, L"F6"); his f_setChannelName (42, L"F8"); his f_setChannelName (43, L"FT8"); his f_setChannelName (44, L"FC6"); his f_setChannelName (45, L"FC4"); his f_setChannelName (46, L"FC2"); his f_setChannelName (47, L"FCz"); his f_setChannelName (48, L"Cz"); his f_setChannelName (49, L"C2"); his f_setChannelName (50, L"C4"); his f_setChannelName (51, L"C6"); his f_setChannelName (52, L"T8"); his f_setChannelName (53, L"TP8"); his f_setChannelName (54, L"CP6"); his f_setChannelName (55, L"CP4"); his f_setChannelName (56, L"CP2"); his f_setChannelName (57, L"P2"); his f_setChannelName (58, L"P4"); his f_setChannelName (59, L"P6"); his f_setChannelName (60, L"P8"); his f_setChannelName (61, L"P10"); his f_setChannelName (62, L"PO8"); his f_setChannelName (63, L"PO4"); his f_setChannelName (64, L"O2"); } return him.transfer(); } catch (MelderError) { Melder_throw ("BDF file not read."); } } static void detrend (double *a, long numberOfSamples) { double firstValue = a [1], lastValue = a [numberOfSamples]; a [1] = a [numberOfSamples] = 0.0; for (long isamp = 2; isamp < numberOfSamples; isamp ++) { a [isamp] -= ((isamp - 1.0) * lastValue + (numberOfSamples - isamp) * firstValue) / (numberOfSamples - 1); } } void structEEG :: f_detrend () { for (long ichan = 1; ichan <= d_numberOfChannels - f_getNumberOfExtraSensors (); ichan ++) { detrend (d_sound -> z [ichan], d_sound -> nx); } } void structEEG :: f_filter (double lowFrequency, double lowWidth, double highFrequency, double highWidth, bool doNotch50Hz) { try { /* long nsampFFT = 1; while (nsampFFT < d_sound -> nx) nsampFFT *= 2; autoNUMfft_Table fftTable; NUMfft_Table_init (& fftTable, nsampFFT); therror */ for (long ichan = 1; ichan <= d_numberOfChannels - f_getNumberOfExtraSensors (); ichan ++) { autoSound channel = Sound_extractChannel (d_sound, ichan); autoSpectrum spec = Sound_to_Spectrum (channel.peek(), TRUE); Spectrum_passHannBand (spec.peek(), lowFrequency, 0.0, lowWidth); Spectrum_passHannBand (spec.peek(), 0.0, highFrequency, highWidth); if (doNotch50Hz) { Spectrum_stopHannBand (spec.peek(), 48.0, 52.0, 1.0); } autoSound him = Spectrum_to_Sound (spec.peek()); NUMvector_copyElements (his z [1], d_sound -> z [ichan], 1, d_sound -> nx); } } catch (MelderError) { Melder_throw (this, ": not filtered."); } } void structEEG :: f_setChannelName (long channelNumber, const wchar *a_name) { autostring l_name = Melder_wcsdup (a_name); Melder_free (d_channelNames [channelNumber]); d_channelNames [channelNumber] = l_name.transfer(); } void structEEG :: f_setExternalElectrodeNames (const wchar *nameExg1, const wchar *nameExg2, const wchar *nameExg3, const wchar *nameExg4, const wchar *nameExg5, const wchar *nameExg6, const wchar *nameExg7, const wchar *nameExg8) { if (f_getNumberOfExternalElectrodes () != 8) Melder_throw (L"There aren't 8 external electrodes."); const long firstExternalElectrode = f_getNumberOfCapElectrodes () + 1; f_setChannelName (firstExternalElectrode, nameExg1); f_setChannelName (firstExternalElectrode + 1, nameExg2); f_setChannelName (firstExternalElectrode + 2, nameExg3); f_setChannelName (firstExternalElectrode + 3, nameExg4); f_setChannelName (firstExternalElectrode + 4, nameExg5); f_setChannelName (firstExternalElectrode + 5, nameExg6); f_setChannelName (firstExternalElectrode + 6, nameExg7); f_setChannelName (firstExternalElectrode + 7, nameExg8); } void structEEG :: f_subtractReference (const wchar *channelNumber1_text, const wchar *channelNumber2_text) { long channelNumber1 = f_getChannelNumber (channelNumber1_text); if (channelNumber1 == 0) Melder_throw (this, ": no channel named \"", channelNumber1_text, "\"."); long channelNumber2 = f_getChannelNumber (channelNumber2_text); if (channelNumber2 == 0 && channelNumber2_text [0] != '\0') Melder_throw (this, ": no channel named \"", channelNumber2_text, "\"."); const long numberOfElectrodeChannels = d_numberOfChannels - f_getNumberOfExtraSensors (); for (long isamp = 1; isamp <= d_sound -> nx; isamp ++) { double referenceValue = channelNumber2 == 0 ? d_sound -> z [channelNumber1] [isamp] : 0.5 * (d_sound -> z [channelNumber1] [isamp] + d_sound -> z [channelNumber2] [isamp]); for (long ichan = 1; ichan <= numberOfElectrodeChannels; ichan ++) { d_sound -> z [ichan] [isamp] -= referenceValue; } } } void structEEG :: f_subtractMeanChannel (long fromChannel, long toChannel) { if (fromChannel < 1 || fromChannel > d_numberOfChannels) Melder_throw ("No channel ", fromChannel, "."); if (toChannel < 1 || toChannel > d_numberOfChannels) Melder_throw ("No channel ", toChannel, "."); if (fromChannel > toChannel) Melder_throw ("Channel range cannot run from ", fromChannel, " to ", toChannel, ". Please reverse."); const long numberOfElectrodeChannels = d_numberOfChannels - f_getNumberOfExtraSensors (); for (long isamp = 1; isamp <= d_sound -> nx; isamp ++) { double referenceValue = 0.0; for (long ichan = fromChannel; ichan <= toChannel; ichan ++) { referenceValue += d_sound -> z [ichan] [isamp]; } referenceValue /= (toChannel - fromChannel + 1); for (long ichan = 1; ichan <= numberOfElectrodeChannels; ichan ++) { d_sound -> z [ichan] [isamp] -= referenceValue; } } } void structEEG :: f_setChannelToZero (long channelNumber) { try { if (channelNumber < 1 || channelNumber > d_numberOfChannels) Melder_throw ("No channel ", channelNumber, "."); long numberOfSamples = d_sound -> nx; double *channel = d_sound -> z [channelNumber]; for (long isample = 1; isample <= numberOfSamples; isample ++) { channel [isample] = 0.0; } } catch (MelderError) { Melder_throw (this, ": channel ", channelNumber, " not set to zero."); } } void structEEG :: f_setChannelToZero (const wchar *channelName) { try { long channelNumber = f_getChannelNumber (channelName); if (channelNumber == 0) Melder_throw ("No channel named \"", channelName, "\"."); f_setChannelToZero (channelNumber); } catch (MelderError) { Melder_throw (this, ": channel ", channelName, " not set to zero."); } } EEG structEEG :: f_extractChannel (long channelNumber) { try { if (channelNumber < 1 || channelNumber > d_numberOfChannels) Melder_throw ("No channel ", channelNumber, "."); autoEEG thee = EEG_create (xmin, xmax); thee -> d_numberOfChannels = 1; thee -> d_channelNames = NUMvector (1, 1); thee -> d_channelNames [1] = Melder_wcsdup (d_channelNames [1]); thee -> d_sound = Sound_extractChannel (d_sound, channelNumber); thee -> d_textgrid = Data_copy (d_textgrid); return thee.transfer(); } catch (MelderError) { Melder_throw (this, ": channel ", channelNumber, " not extracted."); } } EEG structEEG :: f_extractChannel (const wchar *channelName) { try { long channelNumber = f_getChannelNumber (channelName); if (channelNumber == 0) Melder_throw ("No channel named \"", channelName, "\"."); return f_extractChannel (channelNumber); } catch (MelderError) { Melder_throw (this, ": channel ", channelName, " not extracted."); } } EEG EEGs_concatenate (Collection me) { try { if (my size < 1) Melder_throw ("Cannot concatenate zero EEG objects."); EEG first = (EEG) my item [1]; long numberOfChannels = first -> d_numberOfChannels; wchar **channelNames = first -> d_channelNames; for (long ieeg = 2; ieeg <= my size; ieeg ++) { EEG other = (EEG) my item [ieeg]; if (other -> d_numberOfChannels != numberOfChannels) Melder_throw ("The number of channels of ", other, " does not match the number of channels of ", first, "."); for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { if (! Melder_wcsequ (other -> d_channelNames [ichan], channelNames [ichan])) Melder_throw ("Channel ", ichan, " has a different name in ", other, " (", other -> d_channelNames [ichan], ") than in ", first, " (", channelNames [ichan], ")."); } } autoOrdered soundCollection = Ordered_create (); Collection_dontOwnItems (soundCollection.peek()); autoOrdered textgridCollection = Ordered_create (); Collection_dontOwnItems (textgridCollection.peek()); for (long ieeg = 1; ieeg <= my size; ieeg ++) { EEG eeg = (EEG) my item [ieeg]; Collection_addItem (soundCollection.peek(), eeg -> d_sound); Collection_addItem (textgridCollection.peek(), eeg -> d_textgrid); } autoEEG thee = Thing_new (EEG); thy d_numberOfChannels = numberOfChannels; thy d_channelNames = NUMvector (1, numberOfChannels); for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { thy d_channelNames [ichan] = Melder_wcsdup (channelNames [ichan]); } thy d_sound = Sounds_concatenate_e (soundCollection.peek(), 0.0); thy d_textgrid = TextGrids_concatenate (textgridCollection.peek()); thy xmin = thy d_textgrid -> xmin; thy xmax = thy d_textgrid -> xmax; return thee.transfer(); } catch (MelderError) { Melder_throw ("TextGrids not concatenated."); } } EEG structEEG :: f_extractPart (double tmin, double tmax, bool preserveTimes) { try { autoEEG thee = Thing_new (EEG); thy d_numberOfChannels = d_numberOfChannels; thy d_channelNames = NUMvector (1, d_numberOfChannels); for (long ichan = 1; ichan <= d_numberOfChannels; ichan ++) { thy d_channelNames [ichan] = Melder_wcsdup (d_channelNames [ichan]); } thy d_sound = Sound_extractPart (d_sound, tmin, tmax, kSound_windowShape_RECTANGULAR, 1.0, preserveTimes); thy d_textgrid = TextGrid_extractPart (d_textgrid, tmin, tmax, preserveTimes); thy xmin = thy d_textgrid -> xmin; thy xmax = thy d_textgrid -> xmax; return thee.transfer(); } catch (MelderError) { Melder_throw (this, ": part not extracted."); } } /* End of file EEG.cpp */ sources_5316/EEG/ERPWindow.h0000644000176700017670000000230211702525724014314 0ustar paulpaul#ifndef _ERPWindow_h_ #define _ERPWindow_h_ /* ERPWindow.h * * Copyright (C) 2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "SoundEditor.h" #include "ERP.h" Thing_define (ERPWindow, SoundEditor) { // overridden methods: virtual const wchar * v_getChannelName (long channelNumber) { ERP erp = (ERP) this -> data; return erp -> d_channelNames [channelNumber]; } virtual void v_drawSelectionViewer (); }; ERPWindow ERPWindow_create (GuiObject parent, const wchar *title, ERP data); /* End of file ERPWindow.h */ #endif sources_5316/EEG/ERPTier.h0000644000176700017670000000202711665640114013753 0ustar paulpaul#ifndef _ERPTier_h_ #define _ERPTier_h_ /* ERPTier.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "EEG.h" #include "ERP.h" #include "ERPTier_def.h" oo_CLASS_CREATE (ERPPoint, AnyPoint); oo_CLASS_CREATE (ERPTier, Function); ERPTier EEG_to_ERPTier (EEG me, double fromTime, double toTime, int markerBit); /* End of file ERPTier.h */ #endif sources_5316/LPC/0000755000176700017670000000000011756720047012352 5ustar paulpaulsources_5316/LPC/LPC_and_Cepstrumc.h0000644000176700017670000000240711535132164016003 0ustar paulpaul#ifndef _LPC_and_Cepstrumc_h_ #define _LPC_and_Cepstrumc_h_ /* LPC_and_Cepstrumc.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950410 djmw 20020812 GPL header djmw 20110307 Latest modification */ #include "LPC.h" #include "Cepstrumc.h" #ifdef __cplusplus extern "C" { #endif Cepstrumc LPC_to_Cepstrumc (LPC me); LPC Cepstrumc_to_LPC (Cepstrumc me); void LPC_Frame_into_Cepstrumc_Frame (LPC_Frame me, Cepstrumc_Frame thee); void Cepstrumc_Frame_into_LPC_Frame (Cepstrumc_Frame me, LPC_Frame thee); #ifdef __cplusplus } #endif #endif /* _LPC_and_Cepstrumc_h_ */ sources_5316/LPC/LPC_and_LFCC.cpp0000644000176700017670000000604311630440746015104 0ustar paulpaul/* LPC_and_LFCC.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20030205 Latest modifiation */ #include "LPC_and_LFCC.h" #include "NUM2.h" #define MIN(m,n) ((m) < (n) ? (m) : (n)) void LPC_Frame_into_CC_Frame (LPC_Frame me, CC_Frame thee) { double *c = thy c, *a = my a; thy c0 = 0.5 * log (my gain); if (my nCoefficients < 1) { return; } c[1] = -a[1]; for (long n = 2; n <= MIN (my nCoefficients, thy numberOfCoefficients); n++) { double s = 0; for (long k = 1; k < n; k++) { s += a[k] * c[n - k] * (n - k); } c[n] = -a[n] - s / n; } for (long n = my nCoefficients + 1; n <= thy numberOfCoefficients; n++) { double s = 0; for (long k = 1; k <= my nCoefficients; k++) { s += a[k] * c[n - k] * (n - k); } c[n] = - s / n; } } void CC_Frame_into_LPC_Frame (CC_Frame me, LPC_Frame thee) { long n = MIN (my numberOfCoefficients, thy nCoefficients); double *c = my c, *a = thy a; thy gain = exp (2 * my c0); if (n < 1) { return; } a[1] = -c[1]; for (long i = 2; i <= n; i++) { double ai = c[i] * i; for (long j = 1; j < i; j++) { ai += a[j] * c[i - j] * (i - j); } a[i] = -ai / i; } } LFCC LPC_to_LFCC (LPC me, long numberOfCoefficients) { try { if (numberOfCoefficients < 1) { numberOfCoefficients = my maxnCoefficients; } autoLFCC thee = LFCC_create (my xmin, my xmax, my nx, my dx, my x1, numberOfCoefficients, 0, 0.5 / my samplingPeriod); for (long i = 1; i <= my nx; i++) { CC_Frame_init (& thy frame[i], numberOfCoefficients); LPC_Frame_into_CC_Frame (& my d_frames[i], & thy frame[i]); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no LFCC created."); } } LPC LFCC_to_LPC (LFCC me, long numberOfCoefficients) { try { if (numberOfCoefficients < 1) { numberOfCoefficients = my maximumNumberOfCoefficients; } numberOfCoefficients = MIN (numberOfCoefficients, my maximumNumberOfCoefficients); autoLPC thee = LPC_create (my xmin, my xmax, my nx, my dx, my x1, numberOfCoefficients, 0.5 / my fmax); for (long i = 1; i <= my nx; i++) { LPC_Frame_init (& thy d_frames[i], numberOfCoefficients); CC_Frame_into_LPC_Frame (& my frame[i], & thy d_frames[i]); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no LPC created."); } } #undef MIN /* End of file LPC_and_LFCC.c */ sources_5316/LPC/LPC_and_Formant.cpp0000644000176700017670000001253711634154426016011 0ustar paulpaul/* LPC_and_Formant.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030616 Formant_Frame_into_LPC_Frame: remove formant with f >= Nyquist + change lpc indexing from -1..m djmw 20080122 float -> double */ #include "LPC_and_Formant.h" #include "LPC_and_Polynomial.h" #include "NUM2.h" void Formant_Frame_init (Formant_Frame me, long nFormants) { my nFormants = nFormants; if (nFormants > 0) { my formant = NUMvector (1, my nFormants); } } void Formant_Frame_scale (Formant_Frame me, double scale) { for (long i = 1; i <= my nFormants; i++) { my formant[i].frequency *= scale; my formant[i].bandwidth *= scale; } } void Roots_into_Formant_Frame (Roots me, Formant_Frame thee, double samplingFrequency, double margin) { long n = my max - my min + 1; autoNUMvector fc (1, n); autoNUMvector bc (1, n); // Determine the formants and bandwidths thy nFormants = 0; double fLow = margin, fHigh = samplingFrequency / 2 - margin; for (long i = my min; i <= my max; i++) { if (my v[i].im < 0) { continue; } double f = fabs (atan2 (my v[i].im, my v[i].re)) * samplingFrequency / 2 / NUMpi; if (f >= fLow && f <= fHigh) { /*b = - log (my v[i].re * my v[i].re + my v[i].im * my v[i].im) * samplingFrequency / 2 / NUMpi;*/ double b = - log (dcomplex_abs (my v[i])) * samplingFrequency / NUMpi; thy nFormants++; fc[thy nFormants] = f; bc[thy nFormants] = b; } } Formant_Frame_init (thee, thy nFormants); for (long i = 1; i <= thy nFormants; i++) { thy formant[i].frequency = fc[i]; thy formant[i].bandwidth = bc[i]; } } void LPC_Frame_into_Formant_Frame (LPC_Frame me, Formant_Frame thee, double samplingPeriod, double margin) { thy intensity = my gain; if (my nCoefficients == 0) { return; } autoPolynomial p = LPC_Frame_to_Polynomial (me); autoRoots r = Polynomial_to_Roots (p.peek()); Roots_fixIntoUnitCircle (r.peek()); Roots_into_Formant_Frame (r.peek(), thee, 1 / samplingPeriod, margin); } Formant LPC_to_Formant (LPC me, double margin) { try { double samplingFrequency = 1.0 / my samplingPeriod; long nmax = my maxnCoefficients, err = 0; long interval = nmax > 20 ? 1 : 10; if (nmax > 99) { Melder_throw ("We cannot find the roots of a polynomial of order > 99."); } if (margin >= samplingFrequency / 4) { Melder_throw ("Margin must be smaller than ", samplingFrequency / 4, "."); } autoFormant thee = Formant_create (my xmin, my xmax, my nx, my dx, my x1, (nmax + 1) / 2); autoMelderProgress progress (L"LPC to Formant"); for (long i = 1; i <= my nx; i++) { Formant_Frame formant = & thy d_frames[i]; LPC_Frame lpc = & my d_frames[i]; // Initialisation of Formant_Frame is taken care of in Roots_into_Formant_Frame! try { LPC_Frame_into_Formant_Frame (lpc, formant, my samplingPeriod, margin); } catch (MelderError) { Melder_clearError(); err++; } if ( (interval == 1 || (i % interval) == 1)) { Melder_progress ( (double) i / my nx, L"LPC to Formant: frame ", Melder_integer (i), L" out of ", Melder_integer (my nx), L"."); therror } } Formant_sort (thee.peek()); if (err > 0) { Melder_warning (Melder_integer (err), L" formant frames out of ", Melder_integer (my nx), L" suspect."); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Formant created."); } } void Formant_Frame_into_LPC_Frame (Formant_Frame me, LPC_Frame thee, double samplingPeriod) { long m = 2, n = 2 * my nFormants; if (my nFormants < 1) { return; } autoNUMvector lpc (-1, n); lpc[0] = 1; double nyquist = 2.0 / samplingPeriod; for (long i = 1; i <= my nFormants; i++) { double f = my formant[i].frequency; if (f > nyquist) { continue; } // D(z): 1 + p z^-1 + q z^-2 double r = exp (- NUMpi * my formant[i].bandwidth * samplingPeriod); double p = - 2 * r * cos (2 * NUMpi * f * samplingPeriod); double q = r * r; for (long j = m; j > 0; j--) { lpc[j] += p * lpc[j - 1] + q * lpc[j - 2]; } m += 2; } n = thy nCoefficients < n ? thy nCoefficients : n; for (long i = 1; i <= n ; i++) { thy a[i] = lpc[i]; } thy gain = my intensity; } LPC Formant_to_LPC (Formant me, double samplingPeriod) { try { autoLPC thee = LPC_create (my xmin, my xmax, my nx, my dx, my x1, 2 * my maxnFormants, samplingPeriod); for (long i = 1; i <= my nx; i++) { Formant_Frame f = & my d_frames[i]; LPC_Frame lpc = & thy d_frames[i]; long m = 2 * f -> nFormants; LPC_Frame_init (lpc, m); Formant_Frame_into_LPC_Frame (f, lpc, samplingPeriod); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no LPC created."); } } /* End of file LPC_and_Formant.cpp */ sources_5316/LPC/Makefile0000644000176700017670000000137311743745142014015 0ustar paulpaul# Makefile of the library "LPC" # David Weenink, 20120419 include ../makefile.defs CPPFLAGS = -I ../num -I ../dwtools -I ../fon -I ../sys -I ../dwsys -I ../stat OBJECTS = Cepstrum.o Cepstrumc.o Cepstrum_and_Spectrum.o \ LPC.o LPC_and_Cepstrumc.o LPC_and_Formant.o LPC_and_LFCC.o \ LPC_and_Polynomial.o \ LPC_to_Spectrum.o LPC_to_Spectrogram.o \ LPC_and_Tube.o \ Sound_and_LPC.o Sound_and_LPC_robust.o \ Sound_and_Cepstrum.o Tube.o \ VocalTractTier.o \ praat_LPC_init.o manual_LPC.o .PHONY: all clean all: libLPC.a clean: $(RM) $(OBJECTS) $(RM) libLPC.a libLPC.a: $(OBJECTS) touch libLPC.a rm libLPC.a ar cq libLPC.a $(OBJECTS) $(RANLIB) libLPC.a $(OBJECTS): *.h ../num/NUM.h ../dwtools/*.h ../fon/*.h ../sys/*.h ../dwsys/*.h ../stat/*.h sources_5316/LPC/LPC_and_Formant.h0000644000176700017670000000307611603542672015454 0ustar paulpaul#ifndef _LPC_and_Formant_h_ #define _LPC_and_Formant_h_ /* LPC_and_Formant.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030524 GPL header djmw 20110307 Latest modification */ #include "LPC.h" #include "Polynomial.h" #include "Formant.h" #ifdef __cplusplus extern "C" { #endif Formant LPC_to_Formant (LPC me, double margin); LPC Formant_to_LPC (Formant me, double samplingPeriod); void LPC_Frame_into_Formant_Frame (LPC_Frame me, Formant_Frame thee, double samplingPeriod, double margin); void Formant_Frame_into_LPC_Frame (Formant_Frame me, LPC_Frame thee, double samplingPeriod); void Formant_Frame_scale (Formant_Frame me, double scale); void Roots_into_Formant_Frame (Roots me, Formant_Frame thee, double samplingFrequency, double margin); void Formant_Frame_init (Formant_Frame me, long nFormants); #ifdef __cplusplus } #endif #endif /* _LPC_and_Formant_h_ */ sources_5316/LPC/Cepstrumc_def.h0000644000176700017670000000302411627367435015312 0ustar paulpaul/* Cepstrumc_def.h * * Copyright (C) 1994-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20080122 Version 1: float -> double */ #define ooSTRUCT Cepstrumc_Frame oo_DEFINE_STRUCT (Cepstrumc_Frame) oo_INT (nCoefficients) #if oo_READING_BINARY if (localVersion == 0) { oo_FLOAT_VECTOR_FROM (c, 0, nCoefficients) } else { oo_DOUBLE_VECTOR_FROM (c, 0, nCoefficients) } #else oo_DOUBLE_VECTOR_FROM (c, 0, nCoefficients) #endif oo_END_STRUCT (Cepstrumc_Frame) #undef ooSTRUCT #define ooSTRUCT Cepstrumc oo_DEFINE_CLASS (Cepstrumc, Sampled) oo_DOUBLE (samplingFrequency) /* from Sound */ oo_INT (maxnCoefficients) oo_STRUCT_VECTOR (Cepstrumc_Frame, frame, nx) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (Cepstrumc) #undef ooSTRUCT /* End of file Cepstrumc_def.h */ sources_5316/LPC/praat_LPC_init.cpp0000644000176700017670000005720511746212455015715 0ustar paulpaul/* praat_LPC_init.cpp * * Copyright (C) 1994-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030613 Latest modification djmw 20040414 Forms texts. djmw 20060428 Latest modification djmw 20061218 Changed to Melder_information format. djmw 20070902 Melder_error<1...> djmw 20071011 REQUIRE requires L"". djmw 20080313 Cepstrum_formula djmw 20100212 Analysis window length is now "Window length" */ #include #include "praat.h" #include "Cepstrumc.h" #include "Cepstrum_and_Spectrum.h" #include "DTW.h" #include "LPC.h" #include "MFCC.h" #include "LFCC.h" #include "LPC_and_Cepstrumc.h" #include "LPC_and_Formant.h" #include "LPC_and_LFCC.h" #include "LPC_and_Polynomial.h" #include "LPC_and_Tube.h" #include "LPC_to_Spectrogram.h" #include "LPC_to_Spectrum.h" #include "MelFilter_and_MFCC.h" #include "Sound_and_LPC.h" #include "Sound_and_LPC_robust.h" #include "Sound_and_Cepstrum.h" #include "Sound_to_MFCC.h" #include "VocalTractTier.h" #undef iam #define iam iam_LOOP static const wchar_t *DRAW_BUTTON = L"Draw -"; static const wchar_t *QUERY_BUTTON = L"Query -"; void praat_CC_init (ClassInfo klas); void praat_TimeFrameSampled_query_init (ClassInfo klas); int praat_Fon_formula (UiForm dia, Interpreter interpreter); /********************** Cepstrum ****************************************/ DIRECT (Cepstrum_help) Melder_help (L"Cepstrum"); END FORM (Cepstrum_draw, L"Cepstrum: Draw", L"Cepstrum: Draw...") REAL (L"Minimum quefrency", L"0.0") REAL (L"Maximum quefrency", L"0.0") REAL (L"Minimum", L"0.0") REAL (L"Maximum", L"0.0") BOOLEAN (L"Garnish", 0) OK DO autoPraatPicture picture; LOOP { iam (Cepstrum); Cepstrum_draw (me, GRAPHICS, GET_REAL (L"Minimum quefrency"), GET_REAL (L"Maximum quefrency"), GET_REAL (L"Minimum"), GET_REAL (L"Maximum"), GET_INTEGER (L"Garnish")); } END FORM (Cepstrum_formula, L"Cepstrum: Formula...", L"Cepstrum: Formula...") LABEL (L"label", L"y := y1; for row := 1 to nrow do { x := x1; " "for col := 1 to ncol do { self [row, col] := `formula' ; x := x + dx } y := y + dy }") TEXTFIELD (L"formula", L"self") OK DO praat_Fon_formula (dia, interpreter); END DIRECT (Cepstrum_to_Spectrum) LOOP { iam (Cepstrum); praat_new (Cepstrum_to_Spectrum (me), my name); } END DIRECT (Cepstrum_to_Matrix) LOOP { iam (Cepstrum); praat_new (Cepstrum_to_Matrix (me), my name); } END /********************** Cepstrumc ****************************************/ DIRECT (Cepstrumc_to_LPC) LOOP { iam (Cepstrumc); praat_new (Cepstrumc_to_LPC (me), my name); } END FORM (Cepstrumc_to_DTW, L"Cepstrumc: To DTW", L"Cepstrumc: To DTW...") LABEL (L"", L"Distance calculation between Cepstra") REAL (L"Cepstral weight", L"1.0") REAL (L"Log energy weight", L"0.0") REAL (L"Regression weight", L"0.0") REAL (L"Regression weight log energy", L"0.0") REAL (L"Window for regression coefficients (seconds)", L"0.056") LABEL (L"", L"Boundary conditions for time warp") BOOLEAN (L"Match begin positions", 0) BOOLEAN (L"Match end positions", 0) RADIO (L"Slope constraints", 1) RADIOBUTTON (L"no restriction") RADIOBUTTON (L"1/3 < slope < 3") RADIOBUTTON (L"1/2 < slope < 2") RADIOBUTTON (L"2/3 < slope < 3/2") OK DO Cepstrumc c1 = 0, c2 = 0; LOOP { iam (Cepstrumc); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); praat_new (Cepstrumc_to_DTW (c1, c2, GET_REAL (L"Cepstral weight"), GET_REAL (L"Log energy weight"), GET_REAL (L"Regression weight"), GET_REAL (L"Regression weight log energy"), GET_REAL (L"Window for regression coefficients"), GET_INTEGER (L"Match begin positions"), GET_INTEGER (L"Match end positions"), GET_INTEGER (L"Slope constraints")), c1->name, L"_", c2->name); END DIRECT (Cepstrumc_to_Matrix) LOOP { iam (Cepstrumc); praat_new (Cepstrumc_to_Matrix (me), my name); } END /******************** Formant ********************************************/ FORM (Formant_to_LPC, L"Formant: To LPC", 0) POSITIVE (L"Sampling frequency (Hz)", L"16000.0") OK DO LOOP { iam (Formant); praat_new (Formant_to_LPC (me, 1.0 / GET_REAL (L"Sampling frequency")), my name); } END /********************LFCC ********************************************/ DIRECT (LFCC_help) Melder_help (L"LFCC"); END FORM (LFCC_to_LPC, L"LFCC: To LPC", L"LFCC: To LPC...") INTEGER (L"Number of coefficients", L"0") OK DO long ncof = GET_INTEGER (L"Number of coefficients"); if (ncof < 0) { Melder_throw ("Number of coefficients must be greater or equal zero."); } LOOP { iam (LFCC); praat_new (LFCC_to_LPC (me, ncof), my name); } END /********************LPC ********************************************/ DIRECT (LPC_help) Melder_help (L"LPC"); END FORM (LPC_drawGain, L"LPC: Draw gain", L"LPC: Draw gain...") REAL (L"From time (seconds)", L"0.0") REAL (L"To time (seconds)", L"0.0 (=all)") REAL (L"Minimum gain", L"0.0") REAL (L"Maximum gain", L"0.0") BOOLEAN (L"Garnish", 1) OK DO LOOP { iam (LPC); LPC_drawGain (me, GRAPHICS, GET_REAL (L"From time"), GET_REAL (L"To time"), GET_REAL (L"Minimum gain"), GET_REAL (L"Maximum gain"), GET_INTEGER (L"Garnish")); } END DIRECT (LPC_getSamplingInterval) LOOP { iam (LPC); Melder_information (Melder_double (my samplingPeriod), L" seconds"); } END FORM (LPC_getNumberOfCoefficients, L"LPC: Get number of coefficients", L"LPC: Get number of coefficients...") NATURAL (L"Frame number", L"1") OK DO long iframe = GET_INTEGER (L"Frame number"); LOOP { iam (LPC); if (iframe > my nx) { Melder_throw ("Frame number is too large.\n\nPlease choose a number between 1 and ", my nx); } Melder_information (Melder_integer ( (my d_frames[iframe]).nCoefficients), L" coefficients"); } END FORM (LPC_drawPoles, L"LPC: Draw poles", L"LPC: Draw poles...") REAL (L"Time (seconds)", L"0.0") BOOLEAN (L"Garnish", 1) OK DO LOOP { iam (LPC); LPC_drawPoles (me, GRAPHICS, GET_REAL (L"Time"), GET_INTEGER (L"Garnish")); } END DIRECT (LPC_to_Formant) LOOP { iam (LPC); praat_new (LPC_to_Formant (me, 50), my name); } END DIRECT (LPC_to_Formant_keep_all) LOOP { iam (LPC); praat_new (LPC_to_Formant (me, 0), my name); } END FORM (LPC_to_LFCC, L"LPC: To LFCC", L"LPC: To LFCC...") INTEGER (L"Number of coefficients", L"0") OK DO long ncof = GET_INTEGER (L"Number of coefficients"); if (ncof < 0) { Melder_throw ("Number of coefficients must be greater or equal zero."); } LOOP { iam (LPC); praat_new (LPC_to_LFCC (me, ncof), my name); } END FORM (LPC_to_Polynomial, L"LPC: To Polynomial", L"LPC: To Polynomial (slice)...") REAL (L"Time (seconds)", L"0.0") OK DO LOOP { iam (LPC); praat_new (LPC_to_Polynomial (me, GET_REAL (L"Time")), my name); } END FORM (LPC_to_Spectrum, L"LPC: To Spectrum", L"LPC: To Spectrum (slice)...") REAL (L"Time (seconds)", L"0.0") REAL (L"Minimum frequency resolution (Hz)", L"20.0") REAL (L"Bandwidth reduction (Hz)", L"0.0") REAL (L"De-emphasis frequency (Hz)", L"50.0") OK DO LOOP { iam (LPC); praat_new (LPC_to_Spectrum (me, GET_REAL (L"Time"), GET_REAL (L"Minimum frequency resolution"), GET_REAL (L"Bandwidth reduction"), GET_REAL (L"De-emphasis frequency")), my name); } END FORM (LPC_to_Spectrogram, L"LPC: To Spectrogram", L"LPC: To Spectrogram...") REAL (L"Minimum frequency resolution (Hz)", L"20.0") REAL (L"Bandwidth reduction (Hz)", L"0.0") REAL (L"De-emphasis frequency (Hz)", L"50.0") OK DO LOOP { iam (LPC); praat_new (LPC_to_Spectrogram (me, GET_REAL (L"Minimum frequency resolution"), GET_REAL (L"Bandwidth reduction"), GET_REAL (L"De-emphasis frequency")), my name); } END FORM (LPC_to_VocalTract_special, L"LPC: To VocalTract", L"LPC: To VocalTract (slice, special)...") REAL (L"Time (s)", L"0.0") REAL (L"Glottal damping", L"0.1") BOOLEAN (L"Radiation damping", 1) BOOLEAN (L"Internal damping", 1) OK DO double glottalDamping = GET_REAL (L"Glottal damping"); bool radiationDamping = GET_INTEGER (L"Radiation damping"); bool internalDamping = GET_INTEGER (L"Internal damping"); LOOP { iam (LPC); praat_new (LPC_to_VocalTract (me, GET_REAL (L"Time"), glottalDamping, radiationDamping, internalDamping), my name); } END FORM (LPC_to_VocalTract, L"LPC: To VocalTract", L"LPC: To VocalTract (slice)...") REAL (L"Time (s)", L"0.0") POSITIVE (L"Length (m)", L"0.17") OK DO LOOP { iam (LPC); praat_new (LPC_to_VocalTract (me, GET_REAL (L"Time"), GET_REAL (L"Length")), my name); } END DIRECT (LPC_downto_Matrix_lpc) LOOP { iam (LPC); praat_new (LPC_downto_Matrix_lpc (me), my name, L"_lpc"); } END DIRECT (LPC_downto_Matrix_rc) LOOP { iam (LPC); praat_new (LPC_downto_Matrix_rc (me), my name, L"_rc"); } END DIRECT (LPC_downto_Matrix_area) LOOP { iam (LPC); praat_new (LPC_downto_Matrix_area (me), my name, L"_area"); } END /********************** Sound *******************************************/ FORM (Sound_to_Formant_robust, L"Sound: To Formant (robust)", L"Sound: To Formant (robust)...") REAL (L"Time step (s)", L"0.0 (= auto)") POSITIVE (L"Max. number of formants", L"5") REAL (L"Maximum formant (Hz)", L"5500 (= adult female)") POSITIVE (L"Window length (s)", L"0.025") POSITIVE (L"Pre-emphasis from (Hz)", L"50") POSITIVE (L"Number of std. dev.", L"1.5") NATURAL (L"Maximum number of iterations", L"5") REAL (L"Tolerance", L"0.000001") OK DO LOOP { iam (Sound); praat_new (Sound_to_Formant_robust (me, GET_REAL (L"Time step"), GET_REAL (L"Max. number of formants"), GET_REAL (L"Maximum formant"), GET_REAL (L"Window length"), GET_REAL (L"Pre-emphasis from"), 50.0, GET_REAL (L"Number of std. dev."), GET_INTEGER (L"Maximum number of iterations"), GET_REAL (L"Tolerance"), 1), my name); } END static void Sound_to_LPC_addCommonFields (void *dia) { LABEL (L"", L"Warning 1: for formant analysis, use \"To Formant\" instead.") LABEL (L"", L"Warning 2: if you do use \"To LPC\", you may want to resample first.") LABEL (L"", L"Click Help for more details.") LABEL (L"", L"") NATURAL (L"Prediction order", L"16") POSITIVE (L"Window length (s)", L"0.025") POSITIVE (L"Time step (s)", L"0.005") REAL (L"Pre-emphasis frequency (Hz)", L"50.0") } static void Sound_to_LPC_checkCommonFields (void *dia, long *predictionOrder, double *analysisWindowDuration, double *timeStep, double *preemphasisFrequency) { *predictionOrder = GET_INTEGER (L"Prediction order"); *analysisWindowDuration = GET_REAL (L"Window length"); *timeStep = GET_REAL (L"Time step"); *preemphasisFrequency = GET_REAL (L"Pre-emphasis frequency"); if (*preemphasisFrequency < 0.0) { Melder_throw ("Pre-emphasis frequencies cannot be negative."); } } FORM (Sound_to_LPC_auto, L"Sound: To LPC (autocorrelation)", L"Sound: To LPC (autocorrelation)...") Sound_to_LPC_addCommonFields (dia); OK DO long numberOfPoles; double analysisWindowDuration, timeStep, preemphasisFrequency; Sound_to_LPC_checkCommonFields (dia, & numberOfPoles, & analysisWindowDuration, & timeStep, &preemphasisFrequency); LOOP { iam (Sound); praat_new (Sound_to_LPC_auto (me, numberOfPoles, analysisWindowDuration, timeStep, preemphasisFrequency), my name); } END FORM (Sound_to_LPC_covar, L"Sound: To LPC (covariance)", L"Sound: To LPC (covariance)...") Sound_to_LPC_addCommonFields (dia); OK DO long numberOfPoles; double analysisWindowDuration, timeStep, preemphasisFrequency; Sound_to_LPC_checkCommonFields (dia, & numberOfPoles, & analysisWindowDuration, & timeStep, & preemphasisFrequency); LOOP { iam (Sound); praat_new (Sound_to_LPC_covar (me, numberOfPoles, analysisWindowDuration, timeStep, preemphasisFrequency), my name); } END FORM (Sound_to_LPC_burg, L"Sound: To LPC (burg)", L"Sound: To LPC (burg)...") Sound_to_LPC_addCommonFields (dia); OK DO long numberOfPoles; double analysisWindowDuration, timeStep, preemphasisFrequency; Sound_to_LPC_checkCommonFields (dia, & numberOfPoles, & analysisWindowDuration, & timeStep, & preemphasisFrequency); LOOP { iam (Sound); praat_new (Sound_to_LPC_burg (me, numberOfPoles, analysisWindowDuration, timeStep, preemphasisFrequency), my name); } END FORM (Sound_to_LPC_marple, L"Sound: To LPC (marple)", L"Sound: To LPC (marple)...") Sound_to_LPC_addCommonFields (dia); POSITIVE (L"Tolerance 1", L"1e-6") POSITIVE (L"Tolerance 2", L"1e-6") OK DO long numberOfPoles; double analysisWindowDuration, timeStep, preemphasisFrequency; Sound_to_LPC_checkCommonFields (dia, & numberOfPoles, & analysisWindowDuration, &timeStep, & preemphasisFrequency); LOOP { iam (Sound); praat_new (Sound_to_LPC_marple (me, numberOfPoles, analysisWindowDuration, timeStep, preemphasisFrequency, GET_REAL (L"Tolerance 1"), GET_REAL (L"Tolerance 2")), my name); } END FORM (Sound_to_MFCC, L"Sound: To MFCC", L"Sound: To MFCC...") NATURAL (L"Number of coefficients", L"12") POSITIVE (L"Window length (s)", L"0.015") POSITIVE (L"Time step (s)", L"0.005") LABEL (L"", L"Filter bank parameters") POSITIVE (L"Position of first filter (mel)", L"100.0") POSITIVE (L"Distance between filters (mel)", L"100.0") REAL (L"Maximum frequency (mel)", L"0.0"); OK DO long p = GET_INTEGER (L"Number of coefficients"); if (p > 24) { Melder_throw ("Number of coefficients must be < 25."); } LOOP { iam (Sound); praat_new (Sound_to_MFCC (me, p, GET_REAL (L"Window length"), GET_REAL (L"Time step"), GET_REAL (L"Position of first filter"), GET_REAL (L"Maximum frequency"), GET_REAL (L"Distance between filters")), my name); } END FORM (VocalTract_drawSegments, L"VocalTract: Draw segments", 0) POSITIVE (L"Maximum length (cm)", L"20.0") POSITIVE (L"Maximum area (cm^2)", L"90.0") BOOLEAN (L"Closed at glottis", 1) OK DO autoPraatPicture picture; double maxLength = GET_REAL (L"Maximum length") / 100; double maxArea = GET_REAL (L"Maximum area") / 10000; bool closedAtGlottis = GET_INTEGER (L"Closed at glottis"); LOOP { iam (VocalTract); VocalTract_drawSegments (me, GRAPHICS, maxLength, maxArea, closedAtGlottis); } END DIRECT (VocalTract_getLength) LOOP { iam (VocalTract); double length = my xmax - my xmin; if (length <= 0.02) { length = NUMundefined; } Melder_information (Melder_double (length), L" m"); } END FORM (VocalTract_setLength, L"", 0) POSITIVE (L"New length (m)", L"0.17") OK DO double newLength = GET_REAL (L"New length"); LOOP { iam (VocalTract); VocalTract_setLength (me, newLength); } END FORM (VocalTract_to_VocalTractTier, L"VocalTract: To VocalTractTier", 0) REAL (L"Tier start time (s)", L"0.0") REAL (L"Tier end time (s)", L"1.0") REAL (L"Insert at time (s)", L"0.5") OK DO double xmin = GET_REAL (L"Tier start time"); double xmax = GET_REAL (L"Tier end time"); double time = GET_REAL (L"Insert at time"); REQUIRE (xmin < xmax, L"The start time must be before the end time.") REQUIRE (time >= xmin and time <= xmax, L"The insert time must be between start en end time.") LOOP { iam (VocalTract); autoVocalTractTier thee = VocalTract_to_VocalTractTier (me, xmin, xmax, time); praat_new (thee.transfer(), my name); } END DIRECT (VocalTractTier_help) Melder_help (L"VocalTractTier"); END FORM (VocalTractTier_to_LPC, L"VocalTractTier: To LPC", 0) POSITIVE (L"Time step", L"0.005") OK DO LOOP { iam (VocalTractTier); praat_new (VocalTractTier_to_LPC (me, GET_REAL (L"Time step")), my name); } END FORM (VocalTractTier_to_VocalTract, L"", 0) REAL (L"Time (s)", L"0.1") OK DO double time = GET_REAL (L"Time"); LOOP { iam (VocalTractTier); praat_new (VocalTractTier_to_VocalTract (me, time), my name); } END FORM (VocalTractTier_addVocalTract, L"VocalTractTier: Add VocalTract", 0) REAL (L"Time", L"0.1") OK DO VocalTractTier me = FIRST (VocalTractTier); VocalTract thee = FIRST (VocalTract); VocalTractTier_addVocalTract (me, GET_REAL (L"Time"), thee); praat_dataChanged (me); END /******************* LPC & Sound *************************************/ FORM (LPC_and_Sound_filter, L"LPC & Sound: Filter", L"LPC & Sound: Filter...") BOOLEAN (L"Use LPC gain", 0) OK DO LPC me = FIRST (LPC); Sound s = FIRST (Sound); praat_new (LPC_and_Sound_filter (me , s, GET_INTEGER (L"Use LPC gain")), my name); END FORM (LPC_and_Sound_filterWithFilterAtTime, L"LPC & Sound: Filter with one filter at time", L"LPC & Sound: Filter with filter at time...") OPTIONMENU (L"Channel", 2) OPTION (L"Both") OPTION (L"Left") OPTION (L"Right") REAL (L"Use filter at time (s)", L"0.0") OK DO LPC me = FIRST (LPC); Sound s = FIRST (Sound); long channel = GET_INTEGER (L"Channel") - 1; praat_new (LPC_and_Sound_filterWithFilterAtTime (me , s, channel, GET_REAL (L"Use filter at time")), my name); END DIRECT (LPC_and_Sound_filterInverse) LPC me = FIRST (LPC); Sound s = FIRST (Sound); praat_new (LPC_and_Sound_filterInverse (me , s), my name); END FORM (LPC_and_Sound_filterInverseWithFilterAtTime, L"LPC & Sound: Filter (inverse) with filter at time", L"LPC & Sound: Filter (inverse) with filter at time...") OPTIONMENU (L"Channel", 2) OPTION (L"Both") OPTION (L"Left") OPTION (L"Right") REAL (L"Use filter at time (s)", L"0.0") OK DO LPC me = FIRST (LPC); Sound s = FIRST (Sound); long channel = GET_INTEGER (L"Channel") - 1; praat_new (LPC_and_Sound_filterInverseWithFilterAtTime (me , s, channel, GET_REAL (L"Use filter at time")), my name); END FORM (LPC_and_Sound_to_LPC_robust, L"Robust LPC analysis", L"LPC & Sound: To LPC (robust)...") POSITIVE (L"Window length (s)", L"0.025") POSITIVE (L"Pre-emphasis frequency (Hz)", L"50.0") POSITIVE (L"Number of std. dev.", L"1.5") NATURAL (L"Maximum number of iterations", L"5") REAL (L"Tolerance", L"0.000001") BOOLEAN (L"Variable location", 0) OK DO LPC me = FIRST (LPC); Sound s = FIRST (Sound); praat_new (LPC_and_Sound_to_LPC_robust (me, s, GET_REAL (L"Window length"), GET_REAL (L"Pre-emphasis frequency"), GET_REAL (L"Number of std. dev."), GET_INTEGER (L"Maximum number of iterations"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Variable location")), my name, L"_r"); END extern void praat_TimeTier_query_init (ClassInfo klas); extern void praat_TimeTier_modify_init (ClassInfo klas); void praat_uvafon_LPC_init (void); void praat_uvafon_LPC_init (void) { Thing_recognizeClassesByName (classCepstrumc, classLPC, classLFCC, classMFCC, classVocalTractTier, NULL); praat_addAction1 (classCepstrum, 0, L"Cepstrum help", 0, 0, DO_Cepstrum_help); praat_addAction1 (classCepstrum, 0, L"Draw...", 0, 0, DO_Cepstrum_draw); praat_addAction1 (classCepstrum, 0, L"Formula...", 0, 0, DO_Cepstrum_formula); praat_addAction1 (classCepstrum, 0, L"To Spectrum", 0, 0, DO_Cepstrum_to_Spectrum); praat_addAction1 (classCepstrum, 0, L"To Matrix", 0, 0, DO_Cepstrum_to_Matrix); praat_addAction1 (classCepstrumc, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classCepstrumc, 0, L"To LPC", 0, 0, DO_Cepstrumc_to_LPC); praat_addAction1 (classCepstrumc, 2, L"To DTW...", 0, 0, DO_Cepstrumc_to_DTW); praat_addAction1 (classCepstrumc, 0, L"Hack", 0, 0, 0); praat_addAction1 (classCepstrumc, 0, L"To Matrix", 0, 0, DO_Cepstrumc_to_Matrix); praat_addAction1 (classFormant, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classFormant, 0, L"To LPC...", 0, 0, DO_Formant_to_LPC); praat_addAction1 (classLFCC, 0, L"LFCC help", 0, 0, DO_LFCC_help); praat_CC_init (classLFCC); praat_addAction1 (classLFCC, 0, L"To LPC...", 0, 0, DO_LFCC_to_LPC); praat_addAction1 (classLPC, 0, L"LPC help", 0, 0, DO_LPC_help); praat_addAction1 (classLPC, 0, DRAW_BUTTON, 0, 0, 0); praat_addAction1 (classLPC, 0, L"Draw gain...", 0, 1, DO_LPC_drawGain); praat_addAction1 (classLPC, 0, L"Draw poles...", 0, 1, DO_LPC_drawPoles); praat_addAction1 (classLPC, 0, QUERY_BUTTON, 0, 0, 0); praat_TimeFrameSampled_query_init (classLPC); praat_addAction1 (classLPC, 1, L"Get sampling interval", 0, 1, DO_LPC_getSamplingInterval); praat_addAction1 (classLPC, 1, L"Get number of coefficients...", 0, 1, DO_LPC_getNumberOfCoefficients); praat_addAction1 (classLPC, 0, L"Extract", 0, 0, 0); praat_addAction1 (classLPC, 0, L"To Spectrum (slice)...", 0, 0, DO_LPC_to_Spectrum); praat_addAction1 (classLPC, 0, L"To VocalTract (slice)...", 0, 0, DO_LPC_to_VocalTract); praat_addAction1 (classLPC, 0, L"To VocalTract (slice, special)...", 0, 0, DO_LPC_to_VocalTract_special); praat_addAction1 (classLPC, 0, L"To Polynomial (slice)...", 0, 0, DO_LPC_to_Polynomial); praat_addAction1 (classLPC, 0, L"Down to Matrix (lpc)", 0, 0, DO_LPC_downto_Matrix_lpc); praat_addAction1 (classLPC, 0, L"Down to Matrix (rc)", 0, praat_HIDDEN, DO_LPC_downto_Matrix_rc); praat_addAction1 (classLPC, 0, L"Down to Matrix (area)", 0, praat_HIDDEN, DO_LPC_downto_Matrix_area); praat_addAction1 (classLPC, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classLPC, 0, L"To Formant", 0, 0, DO_LPC_to_Formant); praat_addAction1 (classLPC, 0, L"To Formant (keep all)", 0, 0, DO_LPC_to_Formant_keep_all); praat_addAction1 (classLPC, 0, L"To LFCC...", 0, 0, DO_LPC_to_LFCC); praat_addAction1 (classLPC, 0, L"To Spectrogram...", 0, 0, DO_LPC_to_Spectrogram); praat_addAction2 (classLPC, 1, classSound, 1, L"Analyse", 0, 0, 0); praat_addAction2 (classLPC, 1, classSound, 1, L"Filter...", 0, 0, DO_LPC_and_Sound_filter); praat_addAction2 (classLPC, 1, classSound, 1, L"Filter (inverse)", 0, 0, DO_LPC_and_Sound_filterInverse); praat_addAction2 (classLPC, 1, classSound, 1, L"To LPC (robust)...", 0, praat_HIDDEN + praat_DEPTH_1, DO_LPC_and_Sound_to_LPC_robust); praat_addAction2 (classLPC, 1, classSound, 1, L"Filter with filter at time...", 0, 0, DO_LPC_and_Sound_filterWithFilterAtTime); praat_addAction2 (classLPC, 1, classSound, 1, L"Filter (inverse) with filter at time...", 0, 0, DO_LPC_and_Sound_filterInverseWithFilterAtTime); praat_addAction1 (classSound, 0, L"To LPC (autocorrelation)...", L"To Formant (sl)...", 1, DO_Sound_to_LPC_auto); praat_addAction1 (classSound, 0, L"To LPC (covariance)...", L"To LPC (autocorrelation)...", 1, DO_Sound_to_LPC_covar); praat_addAction1 (classSound, 0, L"To LPC (burg)...", L"To LPC (covariance)...", 1, DO_Sound_to_LPC_burg); praat_addAction1 (classSound, 0, L"To LPC (marple)...", L"To LPC (burg)...", 1, DO_Sound_to_LPC_marple); praat_addAction1 (classSound, 0, L"To MFCC...", L"To LPC (marple)...", 1, DO_Sound_to_MFCC); praat_addAction1 (classSound, 0, L"To Formant (robust)...", L"To Formant (sl)...", 2, DO_Sound_to_Formant_robust); praat_addAction1 (classVocalTract, 0, L"Draw segments...", L"Draw", 0, DO_VocalTract_drawSegments); praat_addAction1 (classVocalTract, 1, L"Get length", L"Draw segments...", 0, DO_VocalTract_getLength); praat_addAction1 (classVocalTract, 1, L"Set length", L"Formula...", 0, DO_VocalTract_getLength); praat_addAction1 (classVocalTract, 0, L"To VocalTractTier...", L"To Spectrum...", 0, DO_VocalTract_to_VocalTractTier); praat_addAction1 (classVocalTractTier, 0, L"VocalTractTier help", 0, 0, DO_VocalTractTier_help); praat_addAction1 (classVocalTractTier, 0, L"Query -", 0, 0, 0); praat_TimeTier_query_init (classVocalTractTier); praat_addAction1 (classVocalTractTier, 0, L"Modify -", 0, 0, 0); praat_TimeTier_modify_init (classVocalTractTier); praat_addAction1 (classVocalTractTier, 0, L"To LPC...", 0, 0, DO_VocalTractTier_to_LPC); praat_addAction1 (classVocalTractTier, 0, L"To VocalTract...", 0, 0, DO_VocalTractTier_to_VocalTract); praat_addAction2 (classVocalTractTier, 1, classVocalTract, 1, L"Add VocalTract...", 0, 0, DO_VocalTractTier_addVocalTract); INCLUDE_MANPAGES (manual_LPC_init) } /* End of file praat_LPC_init.c */ sources_5316/LPC/LPC_and_Tube.h0000644000176700017670000000341511745305441014740 0ustar paulpaul#ifndef _LPC_and_Tube_h_ #define _LPC_and_Tube_h_ /* LPC_and_Tube.h * * Copyright (C) 1994-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030612 GPL header djmw 20110307 Latest modification */ #include "LPC.h" #include "Tube.h" #include "VocalTract.h" void LPC_Frame_into_Tube_Frame_rc (LPC_Frame me, Tube_Frame thee); void LPC_Frame_into_Tube_Frame_area (LPC_Frame me, Tube_Frame thee); VocalTract LPC_Frame_to_VocalTract (LPC_Frame me, double length); double LPC_Frame_getVTL_wakita (LPC_Frame me, double samplingPeriod, double refLength); double VocalTract_and_LPC_Frame_getMatchingLength (VocalTract me, LPC_Frame thee, double glottalDamping, bool radiationDamping, bool internalDamping); int Tube_Frame_into_LPC_Frame_area (Tube_Frame me, LPC_Frame thee); int Tube_Frame_into_LPC_Frame_rc (Tube_Frame me, LPC_Frame thee); VocalTract LPC_to_VocalTract (LPC me, double time, double length); void VocalTract_setLength (VocalTract me, double newLength); VocalTract LPC_to_VocalTract (LPC me, double time, double glottalDamping, bool radiationDamping, bool internalDamping); #endif /* _LPC_and_Tube_h_ */ sources_5316/LPC/Cepstrum_and_Spectrum.h0000644000176700017670000000053211607121356017022 0ustar paulpaul#ifndef _Cepstrum_and_Spectrum_h_ #define _Cepstrum_and_Spectrum_h_ /* David Weenink, 20010101 */ #include "Spectrum.h" #include "Cepstrum.h" #ifdef __cplusplus extern "C" { #endif Cepstrum Spectrum_to_Cepstrum (Spectrum me); Spectrum Cepstrum_to_Spectrum (Cepstrum me); #ifdef __cplusplus } #endif #endif /* _Cepstrum_and_Spectrum_h_ */ sources_5316/LPC/Sound_and_LPC.h0000644000176700017670000000674011607116446015137 0ustar paulpaul#ifndef _Sound_and_LPC_h_ #define _Sound_and_LPC_h_ /* Sound_and_LPC.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19971103 djmw 20020812 GPL header djmw 20110307 Latest modification */ #include "LPC.h" #include "Sound.h" #ifdef __cplusplus extern "C" { #endif LPC Sound_to_LPC_auto (Sound me, int predictionOrder, double analysisWidth, double dt, double preEmphasisFrequency); LPC Sound_to_LPC_covar (Sound me, int predictionOrder, double analysisWidth, double dt, double preEmphasisFrequency); LPC Sound_to_LPC_burg (Sound me, int predictionOrder, double analysisWidth, double dt, double preEmphasisFrequency); LPC Sound_to_LPC_marple (Sound me, int predictionOrder, double analysisWidth, double dt, double preEmphasisFrequency, double tol1, double tol2); /* * Function: * Calculate linear prediction coefficients according to following model: * Minimize E(m) = Sum(n=n0;n=n1; (x[n] + Sum(k=1;k=m; a[k]*x[n-k]))) * Method: * The minimization is carried out by solving the equations: * Sum(i=1;i=m; a[i]*c[i][k]) = -c[0][k] for k=1,2,...,m * where c[i][k] = Sum(n=n0;n=n1;x[n-i]*x[n-k]) * 1. Covariance: * n0=m; n1 = N-1; * c[i][k] is symmetric, positive semi-definite matrix * Markel&Gray, LP of Speech, page 221; * 2. Autocorrelation * signal is zero outside the interval; * n0=-infinity; n1=infinity * c[i][k] symmetric, positive definite Toeplitz matrix * Markel&Gray, LP of Speech, page 219; * Preconditions: * predictionOrder > 0; * preEmphasisFrequency >= 0; * * Burg method: see Numerical recipes Chapter 13. * * Marple method: see Marple, L. (1980), A new autoregressive spectrum analysis * algorithm, IEEE Trans. on ASSP 28, 441-453. * tol1 : stop iteration when E(m) / E(0) < tol1 * tol2 : stop iteration when (E(m)-E(m-1)) / E(m-1) < tol2, */ void LPC_Frame_and_Sound_filterInverse (LPC_Frame me, Sound thee, int channel); Sound LPC_and_Sound_filter (LPC me, Sound thee, int useGain); /* E(z) = X(z)A(z), A(z) = 1 + Sum (k=1, k=m, a(k)z^-k); filter: given e & a, determine x; x(n) = e(n) - Sum (k=1, m, a(k)x(n-k)) useGain determines whether the LPC-gain is used in the synthesis. */ void LPC_and_Sound_filterWithFilterAtTime_inline (LPC me, Sound thee, int channel, double time); Sound LPC_and_Sound_filterWithFilterAtTime (LPC me, Sound thee, int channel, double time); Sound LPC_and_Sound_filterInverse (LPC me, Sound thee); /* E(z) = X(z)A(z), A(z) = 1 + Sum (k=1, k=m, a(k)z^-k); filter inverse: given x & a, determine e; e(n) = x(n) + Sum (k=1, m, a(k)x(n-k)) */ Sound LPC_and_Sound_filterInverseWithFilterAtTime (LPC me, Sound thee, int channel, double time); void LPC_and_Sound_filterInverseWithFilterAtTime_inline (LPC me, Sound thee, int channel, double time); #ifdef __cplusplus } #endif #endif /* _Sound_and_LPC_h_ */ sources_5316/LPC/Sound_and_Cepstrum.cpp0000644000176700017670000000672511632232547016660 0ustar paulpaul/* Sound_and_Cepstrum.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020516 GPL header djmw 20020529 changed NUMrealft to NUM...RealFastFourierTransform_f djmw 20041124 Changed call to Sound_to_Spectrum. */ #include "Sound_and_Cepstrum.h" #include "Sound_and_Spectrum.h" #include "Cepstrum_and_Spectrum.h" #include "NUM2.h" /* Algorithm: J.B. Bednar & T.L. Watt (1985), Calculating the Complex Cepstrum without Phase Unwrapping or Integration, IEEE Trans. on ASSP 33, 1014-1017 (Does not work yet). */ Cepstrum Sound_to_Cepstrum_bw (Sound me) { try { long nfft = 2; while (nfft < my nx) { nfft *= 2; } double qmax = (my xmax - my xmin) * nfft / my nx; autoCepstrum thee = Cepstrum_create (0, qmax, nfft); autoNUMvector x (1, nfft); autoNUMvector nx (1, nfft); for (long i = 1; i <= my nx; i++) { x[i] = my z[1][i]; nx[i] = (i - 1) * x[i]; } // Step 1: Fourier transform x(n) -> X(f) // and n*x(n) -> NX(f) NUMforwardRealFastFourierTransform (x.peek() , nfft); NUMforwardRealFastFourierTransform (nx.peek(), nfft); // Step 2: Multiply {X^*(f) * NX(f)} / |X(f)|^2 // Compute Avg (ln |X(f)|) as Avg (ln |X(f)|^2) / 2. // Treat i=1 separately: x[1] * nx[1] / |x[1]|^2 double lnxa = 0; if (x[1] != 0) { lnxa = 2 * log (fabs (x[1])); x[1] = nx[1] / x[1]; } if (x[2] != 0) { lnxa = 2 * log (fabs (x[2])); x[2] = nx[2] / x[2]; } for (long i = 3; i < nfft; i += 2) { double xr = x[i], nxr = nx[i]; double xi = x[i + 1], nxi = nx[i + 1]; double xa = xr * xr + xi * xi; if (xa > 0) { x[i] = (xr * nxr + xi * nxi) / xa; x[i + 1] = (xr * nxi - xi * nxr) / xa; lnxa += log (xa); } else { x[i] = x[i + 1] = 0; } } lnxa /= 2 * nfft / 2; // Step 4: Inverse transform of complex array x // results in: n * xhat (n) NUMreverseRealFastFourierTransform (x.peek(), nfft); // Step 5: Inverse fft-correction factor: 1/nfftd2 // Divide n * xhat (n) by n for (long i = 2; i <= my nx; i++) { thy z[1][i] = x[i] / ( (i - 1) * nfft); } // Step 6: xhat[0] = Avg (ln |X(f)|) thy z[1][1] = lnxa; return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Cepstrum created."); } } /* Zijn nog niet elkaars inverse!!!!*/ Cepstrum Sound_to_Cepstrum (Sound me) { try { autoSpectrum sx = Sound_to_Spectrum (me, TRUE); autoCepstrum thee = Spectrum_to_Cepstrum (sx.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Cepstrum calculated."); } } Sound Cepstrum_to_Sound (Cepstrum me) { try { autoSpectrum sx = Cepstrum_to_Spectrum (me); autoSound thee = Spectrum_to_Sound (sx.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Sound calculated."); } } /* End of file Sound_and_Cepstrum.cpp */ sources_5316/LPC/Cepstrum_def.h0000644000176700017670000000272610745630607015151 0ustar paulpaul/* Cepstrum_def.h * * Copyright (C) 1994-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19981207 djmw 20020812 GPL header djmw 20080122 Version 1: float -> double */ #define ooSTRUCT Cepstrum_Frame oo_DEFINE_STRUCT (Cepstrum_Frame) oo_INT (nCoefficients) #if oo_READING_BINARY if (localVersion == 0) { oo_FLOAT_VECTOR_FROM (c, 0, my nCoefficients) } else { oo_DOUBLE_VECTOR_FROM (c, 0, my nCoefficients) } #else oo_DOUBLE_VECTOR_FROM (c, 0, my nCoefficients) #endif oo_END_STRUCT (Cepstrum_Frame) #undef ooSTRUCT #define ooSTRUCT Cepstrum oo_DEFINE_CLASS (Cepstrum, Sampled) oo_DOUBLE (samplingFrequency) /* from Sound */ oo_INT (maxnCoefficients) oo_STRUCT_VECTOR (Cepstrum_Frame, frame, my nx) oo_END_CLASS (Cepstrum) #undef ooSTRUCT /* End of file Cepstrum_def.h */ sources_5316/LPC/Sound_and_LPC_robust.h0000644000176700017670000000345611652232057016533 0ustar paulpaul#ifndef _Sound_and_LPC_robust_h_ #define _Sound_and_LPC_robust_h_ /* Sound_and_LPC_robust.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030815 GPL header djmw 20111027 Latest modification */ #include "LPC.h" #include "Formant.h" #include "Sound.h" void LPC_Frames_and_Sound_huber (LPC_Frame me, Sound thee, LPC_Frame him, struct huber_struct *hs); /*int LPC_Frames_and_Sound_huber (LPC_Frame me, Sound thee, LPC_Frame him, void *huber); The gnu c compiler (version 3.3.1) complaints about having two LPC_Frame types in the argument list: error: two or more data types in declaration of `LPC_Frame_and_Sound_into_LPC_Frame_huber By defining a void pointer we circumvent the complaint. */ LPC LPC_and_Sound_to_LPC_robust (LPC thee, Sound me, double analysisWidth, double preEmphasisFrequency, double k, int itermax, double tol, int wantlocation); Formant Sound_to_Formant_robust (Sound me, double dt_in, int numberOfPoles, double maximumFrequency, double halfdt_window, double preemphasisFrequency, double safetyMargin, double k, int itermax, double tol, int wantlocation); #endif /* _Sound_and_LPC_robust_h_ */ sources_5316/LPC/LPC_to_Spectrum.cpp0000644000176700017670000000765611630441041016057 0ustar paulpaul/* LPC_to_Spectrum.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020529 GPL header djmw 20020529 Changed NUMrealft to NUMforwardRealFastFourierTransform_f djmw 20030708 Added NUM2.h djmw 20080122 float -> double */ #include "LPC_to_Spectrum.h" #include "NUM2.h" /* PSD(f) = (sigma^2 T) /|1 + Sum (k=1..p, a[k] exp(-2 pi i f k T))|^2, where sigma^2 == gain, T is samplinginterval LPC-spectrum is approximately 20 dB too high (w.r.t. 25 ms spectrum from Sound) */ void LPC_Frame_into_Spectrum (LPC_Frame me, Spectrum thee, double bandwidthReduction, double deEmphasisFrequency) { if (my nCoefficients == 0) { for (long i = 1; i <= thy nx; i++) { thy z[1][i] = thy z[2][i] = 0; } return; } // When deEmphasisFrequency is effective we need 1 extra position in the fftbuffer. long nfft = 2 * (thy nx - 1), ndata = my nCoefficients + 1; double scale = 1.0 / sqrt (2 * thy xmax * thy dx); if (ndata >= nfft - 1 && (deEmphasisFrequency < thy xmax || ndata > nfft)) { Melder_throw ("Spectrum size not large enough."); } autoNUMvector fftbuffer (1, nfft); // Copy 1, a[1], ... a[p] into fftbuffer fftbuffer[1] = 1; for (long i = 2; i <= ndata; i++) { fftbuffer[i] = my a[i - 1]; } if (deEmphasisFrequency < thy xmax) { // Multiply (1, a[1] z^-1, ... a[p] z^-p) by (1 - b z^-1) double b = exp (- 2.0 * NUMpi * deEmphasisFrequency / thy xmax); ndata ++; for (long i = ndata; i > 1; i--) { fftbuffer[i] -= b * fftbuffer[i - 1]; } } /* Calculate sum (k=0..ndata; a[k] (z)^-k) along a contour with radius r: sum (k=0..ndata; a[k] (rz)^-k) = sum (k=0..ndata; (a[k]r^-k) z^-k) */ double g = exp (NUMpi * bandwidthReduction / (thy dx * nfft)); /* r = 1/g */ for (long i = 2; i <= ndata; i++) { fftbuffer[i] *= pow (g, i - 1); } /* Perform the fft. The LPC spectrum is obtained by inverting this spectrum. The imaginary parts of the frequencies 0 and Nyquist are 0. */ NUMforwardRealFastFourierTransform (fftbuffer.peek(), nfft); if (my gain > 0) { scale *= sqrt (my gain); } thy z[1][1] = scale / fftbuffer[1]; thy z[2][1] = 0; for (long i = 2; i <= nfft / 2; i++) { // We use: 1 / (a + ib) = (a - ib) / (a^2 + b^2) double re = fftbuffer[i + i - 1], im = fftbuffer[i + i]; double invSquared = scale / (re * re + im * im); thy z[1][i] = re * invSquared; thy z[2][i] = -im * invSquared; } thy z[1][thy nx] = scale / fftbuffer[2]; thy z[2][thy nx] = 0; } Spectrum LPC_to_Spectrum (LPC me, double t, double dfMin, double bandwidthReduction, double deEmphasisFrequency) { try { double samplingFrequency = 1.0 / my samplingPeriod; long nfft = 2, index = Sampled_xToNearestIndex (me, t); if (index < 1) { index = 1; } if (index > my nx) { index = my nx; } if (dfMin <= 0) { nfft = 512; dfMin = samplingFrequency / nfft; } while (samplingFrequency / nfft > dfMin || nfft <= my d_frames[index].nCoefficients) { nfft *= 2; } autoSpectrum thee = Spectrum_create (samplingFrequency / 2, nfft / 2 + 1); LPC_Frame_into_Spectrum (& my d_frames[index], thee.peek(), bandwidthReduction, deEmphasisFrequency); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Spectrum created."); } } /* End of file LPC_to_Spectrum.cpp */ sources_5316/LPC/manual_LPC.cpp0000644000176700017670000006020111745254566015036 0ustar paulpaul/* manual_LPC.c * * Copyright (C) 1994-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020422 GPL + removed "C syntax" part of manpage djmw 20101009 Latest modification */ #include "ManPagesM.h" #include "MFCC.h" void manual_LPC_init (ManPages me); void manual_LPC_init (ManPages me) { MAN_BEGIN (L"CC: Paint...", L"djmw", 20040407) INTRO (L"A command to paint the cepstral coefficients in shades of grey.") ENTRY (L"Settings") TAG (L"##From coefficient#, ##To coefficient#") DEFINITION (L"the range of coefficients that will be represented.") MAN_END MAN_BEGIN (L"CC: To DTW...", L"djmw", 19960918) INTRO (L"You can choose this command after selecting 2 objects with cepstral " "coefficients (two @MFCC's or @LFCC's). " "With this command you perform dynamic time warping. ") ENTRY (L"Algorithm") NORMAL (L"First we calculate distances between cepstral coefficients: ") LIST_ITEM (L"The distance between frame %i (from me) and %j (from thee) is:") LIST_ITEM (L" %wc \\.c %d1 + %wle \\.c %d2 + %wr \\.c %d3,") LIST_ITEM (L" where %wc, %wle & %wr are user-supplied weights and") LIST_ITEM (L" %d1 = \\su (%k=1..%nCoefficients; (%c__%ik_ - %c__%jk_)^2)") LIST_ITEM (L" %d2 = (c__%i0_ - c__%j0_)^2") LIST_ITEM (L" %d3 = \\su (%k=1..%nCoefficients; (%r__%ik_ - %r__%jk_)^2), with ") LIST_ITEM (L" %r__%ik_ the regression coefficient of the cepstral coefficients " "from the frames within a time span of %dtr seconds. " "c__%ij_ is %j-th cepstral coefficient in frame %i. ") NORMAL (L"Next we find the optimum path through the distance matrix with a " "Viterbi-algorithm.") MAN_END MAN_BEGIN (L"CC: To Matrix", L"djmw", 20011123) INTRO (L"Copies the cepstral coefficients of the selected @CC " "object to a newly created @Matrix object.") ENTRY (L"Behaviour") FORMULA (L"%z__%ji_ = %c__%ij_, with 1 \\<_ %i \\<_ %nx and " "1 \\<_ j \\<_ %numberOfCoefficients__%i_,") NORMAL (L"where %z__%ji_ is the matrix element in row %j and column %i and " "%c__%ij_ is the %j-th cepstral coefficient in frame %i.") MAN_END MAN_BEGIN (L"Cepstrum", L"djmw", 20010219) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") ENTRY (L"Description") NORMAL (L"An object of type Cepstrum represents the complex cepstrum.") MAN_END MAN_BEGIN (L"LFCC", L"djmw", 20040421) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type LFCC represents cepstral " "coefficients on a linear frequency scale as a function of time. " "The coefficients are represented in frames with constant sampling " "period.") ENTRY (L"#LFCC commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@LPC: To LFCC...") MAN_END MAN_BEGIN (L"LFCC: To LPC...", L"djmw", 20040407) INTRO (L"You can choose this command after selecting 1 or more @LFCC's.") ENTRY (L"Settings") TAG (L"##Number of coefficients") DEFINITION (L"the desired number of linear predictive coefficients.") ENTRY (L"Behaviour") NORMAL (L"The transformation from cepstral coefficients to %a-coefficients " "as described in @@Markel & Gray (1976)@.") MAN_END MAN_BEGIN (L"LPC", L"djmw", 19990610) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type LPC represents filter coefficients as a function of time. " "The coefficients are represented in frames with constant sampling period.") ENTRY (L"LPC commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@Sound: To LPC (autocorrelation)...@") LIST_ITEM (L"\\bu @@Sound: To LPC (covariance)...@") LIST_ITEM (L"\\bu @@Sound: To LPC (burg)...@") LIST_ITEM (L"\\bu @@Sound: To LPC (marple)...@") ENTRY (L"Conversion") LIST_ITEM (L"\\bu @@LPC: To LFCC...|To LFCC...@") LIST_ITEM (L"\\bu @@LPC: To Spectrogram...|To Spectrogram...@") LIST_ITEM (L"\\bu @@LPC: To Spectrum (slice)...|To Spectrum (slice)...@") LIST_ITEM (L"\\bu @@LPC: To Polynomial (slice)...|To Polynomial (slice)...@") MAN_END MAN_BEGIN (L"LPC: Draw gain...", L"djmw", 20040407) INTRO (L"You can choose this command after selecting 1 or more @LPC objects.") ENTRY (L"Settings") TAG (L"##From time (s)#, ##To time (seconds)#") DEFINITION (L"the time domain along the %x-axis.") TAG (L"##Minimum gain#, ##Maximum gain#") DEFINITION (L"the range for the %y-axis.") TAG (L"##Garnish") DEFINITION (L"determines whether to draw a bounding box and axis labels.") ENTRY (L"Behaviour") NORMAL (L"Gain will be drawn as a function of time (gain also equals the prediction error " "energy). ") MAN_END MAN_BEGIN (L"LPC: Draw poles...", L"djmw", 20040407) INTRO (L"You can choose this command after selecting 1 or more @LPC objects.") ENTRY (L"Settings") TAG (L"##Time (s)") DEFINITION (L"the time of the nearest frame.") ENTRY (L"Behaviour") NORMAL (L"The @@Roots|roots@ of the @@LPC: To Polynomial (slice)...|linear prediction " "polynomial@, constructed from the coefficients " "of the analysis frame, will be drawn in the complex plane.") MAN_END MAN_BEGIN (L"LPC: To LFCC...", L"djmw", 20040407) INTRO (L"You can choose this command after selecting 1 or more @LPC objects.") ENTRY (L"Behaviour") NORMAL (L"The transformation from a-coefficients to cepstral coefficients " "as described in @@Markel & Gray (1976)@.") ENTRY (L"Settings") TAG (L"%%Number of coefficients%") DEFINITION (L"the desired number of cepstral coefficients.") MAN_END MAN_BEGIN (L"LPC: To Matrix", L"djmw", 20011123) INTRO (L"Copies the linear prediction coefficients of the selected @LPC " "object to a newly created @Matrix object.") ENTRY (L"Behaviour") FORMULA (L"%z__%ji_ = %a__%ij_, with 1 \\<_ %i \\<_ %nx and " "1 \\<_ j \\<_ %nCoefficients__%i_,") NORMAL (L"where %z__%ji_ is the matrix element in row %j and column %i and " "%a__%ij_ is the %j-th linear prediction coefficient in frame %i.") MAN_END MAN_BEGIN (L"LPC: To Formant", L"djmw", 19970123) INTRO (L"You can choose this command after selecting 1 or more @LPC objects.") ENTRY (L"Behaviour") NORMAL (L"For each LPC_Frame, the zeros of the linear prediction polynomial are extracted. " "Zeros that are outside the unit circle are reflected into it. " "Next, formant frequencies and bandwidths are calculated from all the roots that have the " "imaginary part positive, i.e., that lie in the upper half of the unit circle. " "Formant frequencies smaller than 50 Hz or larger than (%Nyquist_frequency - 50) are discarded. " "The remaining frequencies and bandwidths are sorted " "and copied to the Formant_Frame. Finally, the %gain field of the LPC is copied to the %intensity " "field of the Formant_Frame.") ENTRY (L"Algorithm") NORMAL (L"The root finder is Laguerre's method followed by root polishing, see @@Press " "et al. (1992)@.") ENTRY (L"Warning") LIST_ITEM (L"\\bu The formant values can be very inaccurate if you did not resample the Sound " "before the LPC-analysis (consult the @@Source-filter synthesis@ tutorial).") LIST_ITEM (L"\\bu The results of the root finder may not always be accurate when more than 30 " "roots have to be found.") MAN_END MAN_BEGIN (L"LPC: To Polynomial (slice)...", L"djmw", 20040407) INTRO (L"A command that creates a Polynomial object from each selected @LPC object.") ENTRY (L"Settings") TAG (L"##Time (s)") DEFINITION (L"defines the LPC frame whose coefficents will be selected.") ENTRY (L"Behaviour") NORMAL (L"The linear prediction coefficients %a__1..%n_ of the selected LPC " "frame will be copied to polynomial coefficients %c__1..%n+1_ as follows:") FORMULA (L"%c__%i_ = %a__%n\\--%i+1_, ") FORMULA (L"%c__%n+1_ = 1") MAN_END MAN_BEGIN (L"LPC: To Spectrum (slice)...", L"djmw", 20071120) INTRO (L"You can choose this command after selecting 1 or more @LPC objects.") ENTRY (L"Settings") TAG (L"##Time (s)") DEFINITION (L"the time at which the Spectrum must be calculated.") TAG (L"##Minimum frequency resolution (Hz)") DEFINITION (L"successive frequencies in the @Spectrum " "will be maximally this distance apart.") TAG (L"##Bandwidth reduction (Hz)") DEFINITION (L"formants with small bandwidths show up very well as peaks in the spectrum because the poles " "lie close to the contour along which the spectrum is computed (the unit circle in the z-plane). " "Peak enhancement can be realized by computing the spectrum in the z-plane along a contour of radius " "%r = exp (\\-- %\\pi \\.c %bandwidthReduction / %samplingFrequency). " "This technique is also called off-axis spectrum computation. " "Negative values evaluate the spectrum on a contour %outside the unit circle and therefore result in a " "flattened spectrum.") TAG (L"##De-emphasis frequency (Hz)") DEFINITION (L"Performs de-emphasis when frequency is in the interval (0, @@Nyquist frequency@)") ENTRY (L"Algorithm") NORMAL (L"The Spectrum at time %t will be calculated from the %nearest LPC_Frame according to:") FORMULA (L"Spectrum (%f) = \\Vr(%gain\\.c%T/%df) / (1 + \\su__%k=1..%numberOfCoefficients_ %a__%k_%z^^\\--%k^),") NORMAL (L"where %T is the sampling period and %z = exp (\\--2 %\\pi %i %f %T) and %df is the distance in Hz " "between two successive components in the Spectrum.") LIST_ITEM (L"1. Allocate a large enough buffer[1..%nfft] to perform an FFT analysis.") LIST_ITEM (L"2. Make the first value of the buffer 1 and copy the prediction coefficients #a into " "the buffer. This results in buffer values: (1, %a__1_, ..., %a__%numberOfCoefficients_, 0, ..., 0).") LIST_ITEM (L"3. If ##De-emphasis frequency# is in the interval (0, %nyquistFrequency) then \"multiply\" " "the buffer with (1 - %b %z^^\\--1^), where %b = exp (\\-- %\\pi %deEmphasisFrequency %T). " "This results in buffer values: (1, %a__1_\\--%b, %a__2_\\--%b\\.c%a__1_, ..., " "%a__%numberOfCoefficients_\\--%b\\.c%a__%numberOfCoefficients\\--1_, " "\\--%b\\.c%a__%numberOfCoefficients_, 0, ..., 0). Note that the number of values in the buffer that differ from 0 " "has increased by one.") LIST_ITEM (L"4. If ##Bandwidth reduction# is greater than 0 then multiply corresponding values in the buffer by %g^^%i\\--1^ where " "%g = exp (2%\\pi %bandwidthReduction %T / %nfft), and %i is the position index in the buffer. " "%i runs from 1 to %numberOfCoefficients+1+%t, where %t equals 1 when de-emphasis was performed, " "else 0.") LIST_ITEM (L"5. Calculate the FFT spectrum of the buffer with the coefficients. This results in complex " "amplitudes (%a__%j_,%b__%j_), %j=1..%nfft/2+1.") LIST_ITEM (L"6. Calculate the LPC Spectrum by taking the inverse of the FFT spectrum, i.e., each complex " "amplitude becomes (%a__%j_,%b__%j_)^^\\--1^ = (%a__%j_,\\--%b__%j_) / (%a__%j_^2 + %b__%j_^2)") LIST_ITEM (L"7. Multiply all values with the scale factor \\Vr(%gain\\.c%T/%df).") MAN_END MAN_BEGIN (L"LPC: To Spectrogram...", L"djmw", 20040407) INTRO (L"You can choose this command after selecting 1 or more @LPC objects.") ENTRY (L"Settings") TAG (L"##Minimum frequency resolution (Hz)") DEFINITION (L"successive frequencies in the Spectrum will be maximally this distance apart") TAG (L"##Bandwidth reduction (Hz)") DEFINITION (L"formants with small bandwidths show up very well as darker regions in the spectrogram " "because the poles lie close to the contour along which a spectrum is computed (the unit circle " "in the z-plane). " "Peak enhancement can be realized by computing a spectrum in the z-plane along a contour of radius " "%r = exp (\\-- %\\pi \\.c %bandwidthReduction / %samplingFrequency).") TAG (L"##De-emphasis frequency (Hz)") DEFINITION (L"Performs de-emphasis when value is in the interval (0, @@Nyquist frequency@)") ENTRY (L"Algorithm") NORMAL (L"For each LPC_Frame the corresponding Spectrum will be calculated according to the algorithm " "explained in @@LPC: To Spectrum (slice)...@. " "For each frequency the power, i.e., the square of the complex values, will be stored in the " "corresponding area in the Spectrogram.") MAN_END MAN_BEGIN (L"LPC: To VocalTract (slice)...", L"djmw", 20050615) INTRO (L"You can choose this command after selecting 1 or more @LPC objects.") ENTRY (L"Settings") TAG (L"##Time (s)") DEFINITION (L"the time of the nearest frame, in seconds.") TAG (L"##Length (m)") DEFINITION (L"the length of the vocal tract, in metres.") /* TAG (L"##Compute length according to Wakita") DEFINITION (L"the length of the vocal tract is calculated according " "to the algorithm as described in @@Wakita (1977)@.") ENTRY (L"Behaviour") NORMAL (L"A new @VocalTract area function is calculated from the prediction coefficients in the frame. ") ENTRY (L"Warning") NORMAL (L"If ##Compute length according to Wakita# is on, the optimal length is searched for in the range from 0.1 m to " "0.25 m. This length calculation is extremely sensitive to the number of and the positions of the formants " "with respect to the @@Nyquist frequency@. For example, there is a large difference " "between the vocal tract length estimates if the highest formant is just below or just above the " "Nyquist frequency. " "The algorithm is not very reliable in vocal tract length estimation and we do not recommend using it. " )*/ MAN_END MAN_BEGIN (L"LPC & Sound: Filter...", L"djmw", 20040407) INTRO (L"A command that creates a new Sound object from one @Sound and one @LPC " "object which have been selected together.") ENTRY (L"Settings") TAG (L"##Use LPC gain") DEFINITION (L"Determines whether the gain from the LPC is used in the synthesis.") ENTRY (L"Behaviour") NORMAL (L"Filters the selected Sound by the selected LPC-filter.") NORMAL (L"When the LPC-gain is used the samples in the new Sound will be " "multiplied with the square root of the corresponding LPC-gain value.") NORMAL (L"In #Z-domain notation: #O(%z) = #H(%z) \\.c #E(%z), where " "#E(%z) is the selected filter input Sound, #H(%z) the selected LPC filter, " "and, #O(%z) the filter output (the new Sound that will appear in the List of objects).") MAN_END MAN_BEGIN (L"LPC & Sound: Filter with filter at time...", L"djmw", 20101009) INTRO (L"Filters the selected @Sound with a static filter that is formed by the filter coefficients " "from only one @LPC frame.") ENTRY (L"Settings") TAG (L"##Channel") DEFINITION (L"determines the sound channel to be filtered.") TAG (L"##Use filter at time (s)") DEFINITION (L"determines which LPC frame will be chosen to filter the sound. ") MAN_END MAN_BEGIN (L"LPC & Sound: Filter (inverse)", L"djmw", 19970126) INTRO (L"A command that creates a new Sound object from one @Sound and one @LPC " "object which have been selected together.") ENTRY (L"Behaviour") NORMAL (L"Given a filter (the selected LPC) and its output (the selected Sound), " "its input is reconstructed (the new Sound that will appear in the List of objects).") NORMAL (L"In Z-domain notation: #E(%z) = #O(%z) / #H(%z), where " "#O(%z) is the filter output Sound, #H(%z) the LPC filter, and, #E(%z) the filter " "input Sound. (Selecting this newly generated Sound and the LPC, choosing the option " "`Filter...' generates a Sound that is identical to the Sound that originated " "the LPC.)") MAN_END MAN_BEGIN (L"LPC & Sound: Filter (inverse) with filter at time...", L"djmw", 20101009) INTRO (L"%%Inverse% filters the selected @Sound with a static inverse filter that is formed by the filter coefficients " "from only one @LPC frame.") ENTRY (L"Settings") TAG (L"##Channel") DEFINITION (L"determines the sound channel to be filtered.") TAG (L"##Use filter at time (s)") DEFINITION (L"determines which LPC frame will be chosen to inverse filter the sound. ") MAN_END MAN_BEGIN (L"MFCC", L"djmw", 20010411) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type MFCC represents mel frequency cepstral coefficients " "as a function of time. The coefficients are represented in frames " "with constant sampling period.") ENTRY (L"MFCC commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@Sound: To MFCC...@") LIST_ITEM (L"\\bu @@MelFilter: To MFCC...@") MAN_END MAN_BEGIN (L"MFCC: To MelFilter...", L"djmw", 20040407) INTRO (L"A command to reconstruct @MelFilter objects from the selected @MFCC " "objects .") ENTRY (L"Settings") TAG (L"##From coefficient#, ##To coefficient#") DEFINITION (L"the range of coefficients that will be used in the reconstruction.") ENTRY (L"Details") NORMAL (L"The output of the triangular filters in a mel filter bank will be " "synthezised by applying the inverse cosine transform:") FORMULA (L"%P__%j_ = 2/N (%c__0_/2 + \\Si__%j=%from_^^%to^ %c__%i_ cos " "(%j\\pi/%N (%i-0.5)))),") NORMAL (L"where %N represents the number of filters and %c__%i_ the %i-th " "cepstral coefficient.") MAN_END MAN_BEGIN (L"Sound: To Formant (robust)...", L"djmw", 20111027) INTRO (L"A command that creates a @@Formant@ object from every selected @@Sound@. ") ENTRY (L"Settings") NORMAL (L"The settings for ##Time step (s)#, ##Maximum number of formants#, ##Maximum formant (Hz), " "##Window length (s)# and ##Pre emphasis from (Hz)# are as in @@Sound: To Formant (burg)...@. " " The following settings determine aspects of the iterative formant frequency refinement.") TAG (L"%%Number of std. dev.%,") DEFINITION (L"determines the number of standard deviation from where selective weighing of samples starts. ") TAG (L"%%Maximum number of iterations%,") DEFINITION (L"determines the maximum number of iterations allowed in the refinement step.") TAG (L"%%Tolerance%,") DEFINITION (L"detemines another stop ctriterion for the refinement step. If the relative change in variance " "between successive iterations is less then this value, iteration stops. Iteration stops whenever " "one of the two defined stop criteria is reached.") ENTRY (L"Algorithm") NORMAL (L"First the sound is downsampled to twice the maximum formant frequency. Next the LPC coefficients are determined by the autocorrelation method. Finally, in an iterative procedure as described by @@Lee (1988)@ the formant frequencies and bandwidths are refined by selectively weighting of samples values.") MAN_END MAN_BEGIN (L"Sound: LPC analysis", L"djmw", 19970126) INTRO (L"You can perform this analysis by selecting one or more @Sound objects and " "choosing the appropriate command to generate an @LPC.") NORMAL (L"The acronym LPC stands for Linear Predictive Coding.") NORMAL (L"In the LPC analysis one tries to predict %x__%n_ on the basis of the %p previous samples,") FORMULA (L"%x\\'p__%n_ = \\su %a__%k_ %x__%%n-k%_") NORMAL (L"then {%a__1_, %a__2_, ..., %a__%p_} can be chosen to minimize the prediction power %%Q__p_% where") FORMULA (L"%%Q__p_% = E[ |%x__%n_ - %x\\'p__%n_|^2].") NORMAL (L"Several different algorithms exist for minimizing %%Q__p_%:") LIST_ITEM (L"\\bu @@Sound: To LPC (autocorrelation)...|To LPC (autocorrelation)...@") LIST_ITEM (L"\\bu @@Sound: To LPC (covariance)...|To LPC (covariance)...@") LIST_ITEM (L"\\bu @@Sound: To LPC (burg)...|To LPC (burg)...@") LIST_ITEM (L"\\bu @@Sound: To LPC (marple)...|To LPC (marple)...@") MAN_END #define Sound_to_LPC_COMMON_HELP(method) \ INTRO (L"With this command you create a new @LPC from every selected @Sound, " \ "using " #method " method.") \ ENTRY (L"Warning") \ NORMAL (L"You are advised not to use this command for formant analysis. " \ "For formant analysis, instead use @@Sound: To Formant (burg)...@, " \ "which also works via LPC (linear predictive coding). This is because " \ "##Sound: To Formant (burg)...# lets you specify a maximum frequency, " \ "whereas the ##To LPC# commands automatically use the @@Nyquist frequency@ " \ "as their maximum frequency. If you do use one of the ##To LPC# commands " \ "for formant analysis, you may therefore want to downsample the sound first. " \ "For instance, if you want five formants below 5500 Hz but your Sound has a sampling frequency " \ "of 44100 Hz, you have to downsample the sound to 11000 Hz with the @@Sound: Resample...@ command. " \ "After that, you can use the ##To LPC# commands, with a prediction order of 10 or 11.") \ ENTRY (L"Settings") \ TAG (L"##Prediction order#") \ DEFINITION (L"the number of linear prediction coefficients, also called the %%number of poles%. " \ "Choose this number at least twice as large as the number of spectral peaks that you want " \ "to detect.") \ TAG (L"##Analysis window duration (s)") \ DEFINITION (L"the effective duration of each analysis frame, in seconds.") \ TAG (L"##Time step (s)") \ DEFINITION (L"the time step between two consecutive analysis frames.") \ TAG (L"##Pre-emphasis frequency (Hz)") \ DEFINITION (L"a +6dB / octave filtering will be applied above this frequency. " \ "A pre-emphasis frequency of 48.47 Hz for a signal with a sampling frequency of 10 kHz " \ "approximately corresponds to a value of %a = 0.97 for the filter %y__%n_ = %x__%n_ - %a \\.c %x__%n-1_. " \ "The relation between %a and the pre-emphasis frequency is: " \ "%a = exp (\\--2\\.c%\\pi\\.c%preemphasisFrequency/%samplingFrequency). " \ "If you do not want pre-emphasis, choose a frequency greater than the @@Nyquist frequency@.") MAN_BEGIN (L"Sound: To LPC (autocorrelation)...", L"David Weenink & Paul Boersma", 20040407) Sound_to_LPC_COMMON_HELP ("the autocorrelation") ENTRY (L"Algorithm") NORMAL (L"The autocorrelation algorithm is decribed in @@Markel & Gray (1976)@.") MAN_END MAN_BEGIN (L"Sound: To LPC (covariance)...", L"David Weenink & Paul Boersma", 20040407) Sound_to_LPC_COMMON_HELP ("the covariance") ENTRY (L"Algorithm") NORMAL (L"The covariance algorithm is decribed in @@Markel & Gray (1976)@.") MAN_END MAN_BEGIN (L"Sound: To LPC (marple)...", L"djmw", 19970126) Sound_to_LPC_COMMON_HELP ("Marple's") TAG (L"##Tolerance 1") DEFINITION (L"stop the iteration when %E(%m) / %E(0) < %%Tolerance 1%, where %E(%m) is the " "prediction error for order %m.") TAG (L"##Tolerance 2") DEFINITION (L"stop the iteration when (%E(%m) - %E(%m-1)) / %E(%m-1) < %%Tolerance 2.") ENTRY (L"Algorithm") NORMAL (L"The algorithm is described in @@Marple (1980)@.") MAN_END MAN_BEGIN (L"Sound: To LPC (burg)...", L"David Weenink & Paul Boersma", 20040407) Sound_to_LPC_COMMON_HELP ("Burg's") ENTRY (L"Algorithm") NORMAL (L"Burg's algorithm is described in @@Anderson (1978)@") MAN_END MAN_BEGIN (L"Sound: To MFCC...", L"djmw", 20010410) INTRO (L"A command that creates a @MFCC object from every selected @Sound " "object.") NORMAL (L"The analysis proceeds in two steps:") LIST_ITEM (L"1. We perform a filter bank analysis on a mel frequency scale " "(see @@Sound: To MelFilter...@ for details).") LIST_ITEM (L"2. We convert the filter values to mel frequency cepstral " "coefficients (see @@MelFilter: To MFCC...@ for details).") MAN_END MAN_BEGIN (L"VocalTractTier", L"djmw", 20120423) INTRO (L"One of the @@types of objects@ in Praat. A VocalTractTier objects contains a number of (%time, %VocalTract) points, where a @@VocalTract@ represents the area function of the vocal tract expressed as m^^2^, running from the glottis to the lips.") MAN_END MAN_BEGIN (L"Anderson (1978)", L"djmw", 20030701) NORMAL (L"N. Anderson (1978): \"On the calculation of filter coefficients for " "maximum entropy spectral analysis.\" In Childers: %%Modern Spectrum Analysis%, " "IEEE Press: 252\\--255.") MAN_END MAN_BEGIN (L"Lee (1988)", L"djmw", 20111027) NORMAL (L"C.-H. Lee (1988): \"On Robust Linear Prediction of Speech.\", %%IEEE Trans. on ASSP #36: 642\\--649.") MAN_END MAN_BEGIN (L"Markel & Gray (1976)", L"djmw", 19980114) NORMAL (L"J.D. Markel & A.H. Gray, Jr. (1976): %%Linear Prediction of Speech.% " "Springer Verlag, Berlin.") MAN_END MAN_BEGIN (L"Marple (1980)", L"djmw", 19980114) NORMAL (L"L. Marple (1980): \"A new autoregressive spectrum analysis algorithm.\" " "%%IEEE Trans. on ASSP% #28, 441\\--454.") MAN_END MAN_BEGIN (L"Wakita (1977)", L"djmw", 19980114) NORMAL (L"H. Wakita (1977): \"Normalization of vowels by vocal-tract " "length and its application to vowel identification.\" %%IEEE Trans. on ASSP% " "#25: 183\\--192.") MAN_END } /* BUGS: 19980217 djmw LPC_and_Sound_filter ilast was not always defined. 19980322 djmw Sound_into_LPC_Frame_auto did not return (nCoefficients == 0) when (r[1] == 0). */ /* End of file manual_LPC.c */ sources_5316/LPC/LPC_to_Spectrum.h0000644000176700017670000000276411603613777015540 0ustar paulpaul#ifndef _LPC_to_Spectrum_h_ #define _LPC_to_Spectrum_h_ /* LPC_to_Spectrum.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19980224 djmw 20020812 GPL header djmw 20110702 Latest modification */ #include "LPC.h" #include "Spectrum.h" #ifdef __cplusplus extern "C" { #endif void LPC_Frame_into_Spectrum (LPC_Frame me, Spectrum thee, double bandwidthReduction, double deEmphasisFrequency); Spectrum LPC_to_Spectrum (LPC me, double t, double dfMin, double bandwidthReduction, double deEmphasisFrequency); Spectrum LPC_to_Spectrum2 (LPC me, double t, double dfMin, double bandwidthReduction); /* if(dfMin >= 0) df <= dfMin else df = NyquistFrequency / 512 */ /* integration radius r = exp (- pi * bandwidthReduction / samplingFrequency) */ #ifdef __cplusplus } #endif #endif /* _LPC_and_Spectrum_h_ */ sources_5316/LPC/LPC_and_Tube.cpp0000664000176700017670000002122111745613144015272 0ustar paulpaul/* LPC_and_Tube.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020612 GPL header djmw 20041020 struct Tube_Frame -> struct structTube_Frame; struct LPC_Frame -> struct structLPC_Frame; struct Formant_Frame->struct structFormant_Frame djmw 20051005 Always make a VocalTract with length 0.01 m when wakita_length==NUMundefined. */ #include "LPC_and_Tube.h" #include "LPC_and_Formant.h" #include "LPC_to_Spectrum.h" #include "SpectrumTier.h" #include "VocalTract_to_Spectrum.h" #include "NUM2.h" // IEEE: Programs fo digital signal processing section 4.3 LPTRN void LPC_Frame_into_Tube_Frame_rc (LPC_Frame me, Tube_Frame thee) { long p = my nCoefficients; Melder_assert (p <= thy nSegments); //TODO autoNUMvector b (1, p); autoNUMvector a (1, p); for (long i = 1; i <= p; i++) { a[i] = my a[i]; } double *rc = thy c; for (long m = p; m > 0; m--) { rc[m] = a[m]; if (fabs (rc[m]) > 1) { Melder_throw ("Relection coefficient [", Melder_integer(m), "] larger 1."); // TODO kan er geen Tube worden gemaakt? } for (long i = 1; i < m; i++) { b[i] = a[i]; } for (long i = 1; i < m; i++) { a[i] = (b[i] - rc[m] * b[m - i]) / (1.0 - rc[m] * rc[m]); } } } void LPC_Frame_into_Tube_Frame_area (LPC_Frame me, Tube_Frame thee) { struct structTube_Frame rc_struct = { 0 }; Tube_Frame rc = & rc_struct; Tube_Frame_init (rc, my nCoefficients, thy length); LPC_Frame_into_Tube_Frame_rc (me, rc); Tube_Frames_rc_into_area (rc, thee); rc -> destroy (); } double VocalTract_and_LPC_Frame_getMatchingLength (VocalTract me, LPC_Frame thee, double glottalDamping, bool radiationDamping, bool internalDamping) { try { // match the average distance between the first two formants in the VocaTract and the LPC spectrum long numberOfFrequencies = 1000; double maximumFrequency = 5000; autoSpectrum vts = VocalTract_to_Spectrum (me, numberOfFrequencies, maximumFrequency, glottalDamping, radiationDamping, internalDamping); double samplingFrequency = 1000.0 * my nx; autoSpectrum lps = Spectrum_create (0.5 * samplingFrequency, numberOfFrequencies); LPC_Frame_into_Spectrum (thee, lps.peek(), 0, 50); autoSpectrumTier vtst = Spectrum_to_SpectrumTier_peaks (vts.peek()); autoSpectrumTier lpst = Spectrum_to_SpectrumTier_peaks (lps.peek()); RealPoint point = vtst -> f_peekPoint (1); double vt_f1 = point -> number; point = vtst -> f_peekPoint (2); double vt_f2 = point -> number; point = lpst -> f_peekPoint (1); double lp_f1 = point -> number; point = lpst -> f_peekPoint (2); double lp_f2 = point -> number; double df1 = lp_f1 - vt_f1, df2 = lp_f2 - vt_f2, df = 0.5 * (df1 + df2); double dl = - df / lp_f2; return my dx * my nx * (1 + dl); } catch (MelderError) { Melder_throw (L"Length could not be determined from VocalTract and LPC_Frame."); } } double LPC_Frame_getVTL_wakita (LPC_Frame me, double samplingPeriod, double refLength) { struct structLPC_Frame lpc_struct; LPC_Frame lpc = & lpc_struct; struct structFormant_Frame f_struct; Formant_Frame f = & f_struct; struct structTube_Frame rc_struct, af_struct; Tube_Frame rc = & rc_struct, af = & af_struct; try { long m = my nCoefficients; double length, dlength = 0.001, wakita_length = NUMundefined; double varMin = 1e38; memset (& lpc_struct, 0, sizeof (lpc_struct)); memset (& f_struct, 0, sizeof (f_struct)); memset (& rc_struct, 0, sizeof (rc_struct)); memset (& af_struct, 0, sizeof (af_struct)); LPC_Frame_init (lpc, m); Tube_Frame_init (rc, m, refLength); Tube_Frame_init (af, m, refLength); // Step 2 LPC_Frame_into_Formant_Frame (me, f, samplingPeriod, 0); // LPC_Frame_into_Formant_Frame performs the Formant_Frame_init !! if (f -> nFormants < 1) { Melder_throw ("Not enough formants."); } double *area = af -> c; double lmin = length = 0.10; double plength = refLength; while (length <= 0.25) { // Step 3 double fscale = plength / length; for (long i = 1; i <= f -> nFormants; i++) { f -> formant[i].frequency *= fscale; f -> formant[i].bandwidth *= fscale; } /* 20000125: Bovenstaande schaling van f1/b1 kan ook gedaan worden door MGfb_to_a (f, b, nf, samplingFrequency*length/refLength, a1) De berekening is extreem gevoelig voor de samplefrequentie: een zelfde stel f,b waardes geven andere lengtes afhankelijk van Fs. Ook het weglaten van een hogere formant heeft consekwenties. De refLength zou eigenlijk vast moeten liggen op refLength=c*aantalFormanten/Fs waarbij c=340 m/s (geluidssnelheid). Bij Fs=10000 zou aantalFormanten=5 zijn en refLength -> 0.17 m */ // step 4 Formant_Frame_into_LPC_Frame (f, lpc, samplingPeriod); // step 5 rc -> length = length; LPC_Frame_into_Tube_Frame_rc (lpc, rc); // step 6.1 Tube_Frames_rc_into_area (rc, af); // step 6.2 Log(areas) double logSum = 0; for (long i = 1; i <= af -> nSegments; i++) { area[i] = log (area[i]); logSum += area[i]; } // step 6.3 and 7 double var = 0; for (long i = 1; i <= af -> nSegments; i++) { double delta = area[i] - logSum / af -> nSegments; var += delta * delta; } if (var < varMin) { lmin = length; varMin = var; } plength = length; length += dlength; } wakita_length = lmin; f -> destroy (); lpc -> destroy (); rc -> destroy (); af -> destroy (); return wakita_length; } catch (MelderError) { f -> destroy (); lpc -> destroy (); rc -> destroy (); af -> destroy (); return NUMundefined; } } int Tube_Frame_into_LPC_Frame_area (Tube_Frame me, LPC_Frame thee) { (void) me; (void) thee; return 0; } int Tube_Frame_into_LPC_Frame_rc (Tube_Frame me, LPC_Frame thee) { (void) me; (void) thee; return 0; } void VocalTract_setLength (VocalTract me, double newLength) { my xmax = newLength; my dx = newLength / my nx; my x1 = 0.5 * my dx; } VocalTract LPC_to_VocalTract (LPC me, double time, double glottalDamping, bool radiationDamping, bool internalDamping) { try { long iframe = Sampled_xToIndex (me, time); if (iframe < 1) { iframe = 1; } if (iframe > my nx) { iframe = my nx; } LPC_Frame lpc = & my d_frames[iframe]; autoVocalTract thee = LPC_Frame_to_VocalTract (lpc, 0.17); double length = VocalTract_and_LPC_Frame_getMatchingLength (thee.peek(), lpc, glottalDamping, radiationDamping, internalDamping); VocalTract_setLength (thee.peek(), length); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no VocalTract created."); } } VocalTract LPC_Frame_to_VocalTract2 (LPC_Frame me, double length) { struct structTube_Frame area_struct = { 0 }; Tube_Frame area = & area_struct; try { long m = my nCoefficients; Tube_Frame_init (area, m, length); LPC_Frame_into_Tube_Frame_area (me, area); autoVocalTract thee = VocalTract_create (m, area -> length / m); // area[lips..glottis] (m^2) to VocalTract[glottis..lips] (m^2) for (long i = 1; i <= m; i++) { thy z[1][i] = area -> c[m + 1 - i]; } area -> destroy (); return thee.transfer(); } catch (MelderError) { area -> destroy (); Melder_throw ("No VocalTract created from LPC_Frame."); } } VocalTract LPC_Frame_to_VocalTract (LPC_Frame me, double length) { try { long m = my nCoefficients; autoNUMvector area (1, m + 1); NUMlpc_lpc_to_area (my a, m, area.peek()); autoVocalTract thee = VocalTract_create (m, length / m); // area[lips..glottis] (m^2) to VocalTract[glottis..lips] (m^2) for (long i = 1; i <= m; i++) { thy z[1][i] = area[m + 1 - i]; } return thee.transfer(); } catch (MelderError) { Melder_throw ("No VocalTract created from LPC_Frame."); } } VocalTract LPC_to_VocalTract (LPC me, double time, double length) { try { long iframe = Sampled_xToIndex (me, time); if (iframe < 1) { iframe = 1; } if (iframe > my nx) { iframe = my nx; } LPC_Frame lpc = & my d_frames[iframe]; autoVocalTract thee = LPC_Frame_to_VocalTract (lpc, length); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no VocalTract created."); } } /* End of file LPC_and_Tube.cpp */ sources_5316/LPC/VocalTractTier_def.h0000664000176700017670000000221611743747470016237 0ustar paulpaul/* VocalTractTier_def.h * * Copyright (C) 2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT VocalTractPoint oo_DEFINE_CLASS (VocalTractPoint, AnyPoint) oo_OBJECT (VocalTract, 0, d_vocalTract) oo_END_CLASS (VocalTractPoint) #undef ooSTRUCT #define ooSTRUCT VocalTractTier oo_DEFINE_CLASS (VocalTractTier, Function) oo_COLLECTION (SortedSetOfDouble, d_vocalTracts, VocalTractPoint, 0) oo_END_CLASS (VocalTractTier) #undef ooSTRUCT /* End of file VocalTract_def.h */ sources_5316/LPC/Cepstrum_and_Spectrum.cpp0000644000176700017670000000433011725072134017355 0ustar paulpaul/* Cepstrum_and_Spectrum.cpp * * Copyright (C) 1994-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20041124 Changed call to Sound_to_Spectrum. djmw 20070103 Sound interface changes djmw 20080122 float -> double */ #include "Cepstrum_and_Spectrum.h" #include "Spectrum_extensions.h" #include "Sound_and_Spectrum.h" Cepstrum Spectrum_to_Cepstrum (Spectrum me) { try { autoMatrix unwrap = Spectrum_unwrap (me); autoSpectrum sx = Data_copy (me); // Copy magnitude-squared and unwrapped phase. for (long i = 1; i <= my nx; i ++) { double xa = unwrap -> z[1][i]; sx -> z[1][i] = xa > 0 ? 0.5 * log (xa) : -300; sx -> z[2][i] = unwrap -> z[2][i]; } // Compute complex cepstrum x. autoSound x = Spectrum_to_Sound (sx.peek()); autoCepstrum thee = Cepstrum_create (0, x -> xmax - x -> xmin, x -> nx); NUMvector_copyElements (x -> z[1], thy z[1], 1, x -> nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Cepstrum created."); } } Spectrum Cepstrum_to_Spectrum (Cepstrum me) { try { autoSound x = Sound_create (1, my xmin, my xmax, my nx, my dx, my x1); NUMvector_copyElements (my z[1], x -> z[1], 1, my nx); autoSpectrum thee = Sound_to_Spectrum (x.peek(), TRUE); for (long i = 1; i <= thy nx; i++) { double ar = exp (thy z[1][i]); double ai = thy z[2][i]; thy z[1][i] = ar * cos (ai); thy z[2][i] = ar * sin (ai); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Spectrum created."); } } /* End of file Cepstrum_and_Spectrum.cpp */ sources_5316/LPC/Cepstrum.h0000644000176700017670000000427311627367257014342 0ustar paulpaul#ifndef _Cepstrum_h_ #define _Cepstrum_h_ /* Cepstrum.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010111 djmw 20020812 GPL header djmw 20110306 Latest modification. */ /* Complex Cepstrum. The complex cepstrum is a sequence of REAL numbers. It is the inverse-fourier-transformed COMPLEX logarithm of the spectrum of a (sound) signal. It is only called 'complex cepstrum' because the complex logarithm is taken. */ #include "Matrix.h" Thing_define (Cepstrum, Matrix) { }; /* xmin // Lowest quefrency. xmax // Highest quefrency. nx // Number of quefrencies. dx // Quefrency step. x1 // First quefrency. ymin = ymax = dy = y1 = 1 ny = 1 */ Cepstrum Cepstrum_create (double qmin, double qmax, long nq); /* Preconditions: qmin < qmax; nq >= 2; Postconditions: my xmin = qmin; my ymin = 1; my xmax = qmax; my ymax = 1; my nx = nq; my ny = 1; my dx = qmax / nx; my dy = 1; my x1 = my dx / 2; my y1 = 1; my z [1..ny] [1..nx] = 0.0; */ void Cepstrum_draw (Cepstrum me, Graphics g, double qmin, double qmax, double minimum, double maximum, int garnish); /* Function: draw a Cepstrum into a Graphics. Preconditions: maximum > minimum; Arguments: [qmin, qmax]: quefrencies; x domain of drawing; Autowindowing: if qmax <= qmin, x domain of drawing is [my xmin, my xmax]. [minimum, maximum]: amplitude; y range of drawing. */ Matrix Cepstrum_to_Matrix (Cepstrum me); Cepstrum Matrix_to_Cepstrum (Matrix me, long row); #endif /* _Cepstrum_h_ */ sources_5316/LPC/Tube_def.h0000644000176700017670000000227311627370204014235 0ustar paulpaul/* Tube_def.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Tube_Frame oo_DEFINE_STRUCT (Tube_Frame) oo_INT (nSegments) oo_DOUBLE (length) oo_DOUBLE_VECTOR (c, nSegments) oo_END_STRUCT (Tube_Frame) #undef ooSTRUCT #define ooSTRUCT Tube oo_DEFINE_CLASS (Tube, Sampled) oo_INT (maxnSegments) oo_STRUCT_VECTOR (Tube_Frame, frame, nx) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (Tube) #undef ooSTRUCT /* End of file Tube_def.h */ sources_5316/LPC/Sound_and_LPC.cpp0000644000176700017670000004435111750476377015505 0ustar paulpaul/* Sound_and_LPC.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020625 GPL header djmw corrected a bug in Sound_into_LPC_Frame_marple that could crash praat when signal has only zero samples. djmw 20040303 Removed warning in Sound_to_LPC. djmw 20070103 Sound interface changes djmw 20080122 float -> double djmw 20101009 Filter and inverseFilter with one frame. */ #include "Sound_and_LPC.h" #include "Sound_extensions.h" #include "Vector.h" #include "Spectrum.h" #include "NUM2.h" #define LPC_METHOD_AUTO 1 #define LPC_METHOD_COVAR 2 #define LPC_METHOD_BURG 3 #define LPC_METHOD_MARPLE 4 /* Markel&Gray, LP of S, page 219 work[1..3*m+2] r = & work[1]; // r[1..m+1] a= & work[m+1+1]; // a[1..m+1] rc = & work[m+1+m+1+1]; // rc[1..m] for (i=1; i<= m+1+m+1+m;i++) work[i] = 0; */ #define LPC_METHOD_AUTO_WINDOW_CORRECTION 1 static void LPC_Frame_and_Sound_filter (LPC_Frame me, Sound thee, int channel) { double *y = thy z[channel], *a = my a; for (long i = 1; i <= thy nx; i++) { long m = i > my nCoefficients ? my nCoefficients : i - 1; for (long j = 1; j <= m; j++) { y[i] -= a[j] * y[i - j]; } } } void LPC_Frame_and_Sound_filterInverse (LPC_Frame me, Sound thee, int channel) { double *x = thy z[channel]; autoNUMvector y (0L, my nCoefficients); for (long i = 1; i <= thy nx; i++) { y[0] = x[i]; for (long j = 1; j <= my nCoefficients; j++) { x[i] += my a[j] * y[j]; } for (long j = my nCoefficients; j > 0; j--) { y[j] = y[j - 1]; } } } static int Sound_into_LPC_Frame_auto (Sound me, LPC_Frame thee) { long i = 1; // For error condition at end long m = thy nCoefficients; autoNUMvector r (1, m + 1); autoNUMvector a (1, m + 1); autoNUMvector rc (1, m); double *x = my z[1]; for (i = 1; i <= m + 1; i++) { for (long j = 1; j <= my nx - i + 1; j++) { r[i] += x[j] * x[j + i - 1]; } } if (r[1] == 0) { i = 1; /* ! */ goto end; } a[1] = 1; a[2] = rc[1] = - r[2] / r[1]; thy gain = r[1] + r[2] * rc[1]; for (i = 2; i <= m; i++) { double s = 0; for (long j = 1; j <= i; j++) { s += r[i - j + 2] * a[j]; } rc[i] = - s / thy gain; for (long j = 2; j <= i / 2 + 1; j++) { double at = a[j] + rc[i] * a[i - j + 2]; a[i - j + 2] += rc[i] * a[j]; a[j] = at; } a[i + 1] = rc[i]; thy gain += rc[i] * s; if (thy gain <= 0) { goto end; } } end: i--; for (long j = 1; j <= i; j++) { thy a[j] = a[j + 1]; } if (i == m) { return 1; } thy nCoefficients = i; for (long j = i + 1; j <= m; j++) { thy a[j] = 0; } return 0; // Melder_warning ("Less coefficienst than asked for."); } /* Markel&Gray, LP of S, page 221 work[1..m(m+1)/2+m+m+1+m+m+1] b = & work[1] grc = & work[m*(m+1)/2+1]; a = & work[m*(m+1)/2+m+1]; beta = & work [m+1)/2+m+m+1+1]; cc = & work[m+1)/2+m+m+1+m+1] for (i=1; i<=m(m+1)/2+m+m+1+m+m+1;i++) work[i] = 0; */ static int Sound_into_LPC_Frame_covar (Sound me, LPC_Frame thee) { long i = 1, n = my nx, m = thy nCoefficients; double *x = my z[1]; autoNUMvector b (1, m * (m + 1) / 2); autoNUMvector grc (1, m); autoNUMvector a (1, m + 1); autoNUMvector beta (1, m); autoNUMvector cc (1, m + 1); thy gain = 0; for (i = m + 1; i <= n; i++) { thy gain += x[i] * x[i]; cc[1] += x[i] * x[i - 1]; cc[2] += x[i - 1] * x[i - 1]; } if (thy gain == 0) { i = 1; /* ! */ goto end; } b[1] = 1; beta[1] = cc[2]; a[1] = 1; a[2] = grc[1] = -cc[1] / cc[2]; thy gain += grc[1] * cc[1]; for (i = 2; i <= m; i++) { /*130*/ double s = 0; /* 20 */ for (long j = 1; j <= i; j++) { cc[i - j + 2] = cc[i - j + 1] + x[m - i + 1] * x[m - i + j] - x[n - i + 1] * x[n - i + j]; } cc[1] = 0; for (long j = m + 1; j <= n; j++) { cc[1] += x[j - i] * x[j]; /* 30 */ } b[i * (i + 1) / 2] = 1; for (long j = 1; j <= i - 1; j++) { /* 70 */ double gam = 0; if (beta[j] < 0) { goto end; } else if (beta[j] == 0) { continue; } for (long k = 1; k <= j; k++) { gam += cc[k + 1] * b[j * (j - 1) / 2 + k]; /*50*/ } gam /= beta[j]; for (long k = 1; k <= j; k++) { b[i * (i - 1) / 2 + k] -= gam * b[j * (j - 1) / 2 + k]; /*60*/ } } beta[i] = 0; for (long j = 1; j <= i; j++) { beta[i] += cc[j + 1] * b[i * (i - 1) / 2 + j]; /*80*/ } if (beta[i] <= 0) { goto end; } for (long j = 1; j <= i; j++) { s += cc[j] * a[j]; /*100*/ } grc[i] = -s / beta[i]; for (long j = 2; j <= i; j++) { a[j] += grc[i] * b[i * (i - 1) / 2 + j - 1]; /*110*/ } a[i + 1] = grc[i]; s = grc[i] * grc[i] * beta[i]; thy gain -= s; if (thy gain <= 0) { goto end; } } end: i--; for (long j = 1; j <= i; j++) { thy a[j] = a[j + 1]; } if (i == m) { return 1; } thy nCoefficients = i; for (long j = i + 1; j <= m; j++) { thy a[j] = 0; } return 0; // Melder_warning ("Less coefficienst than asked for."); } static int Sound_into_LPC_Frame_burg (Sound me, LPC_Frame thee) { int status = NUMburg (my z[1], my nx, thy a, thy nCoefficients, &thy gain); thy gain *= my nx; for (long i = 1; i <= thy nCoefficients; i++) { thy a[i] = -thy a[i]; } return status; } static int Sound_into_LPC_Frame_marple (Sound me, LPC_Frame thee, double tol1, double tol2) { long m = 1, n = my nx, mmax = thy nCoefficients; int status = 1; double *a = thy a, *x = my z[1]; autoNUMvector c (1, mmax + 1); autoNUMvector d (1, mmax + 1); autoNUMvector r (1, mmax + 1); double e0 = 0; for (long k = 1; k <= n; k++) { e0 += x[k] * x[k]; } e0 *= 2; if (e0 == 0) { m = 0; thy gain *= 0.5; /* because e0 is twice the energy */ thy nCoefficients = m; return 0; // warning no signal } double q1 = 1.0 / e0; double q2 = q1 * x[1], q = q1 * x[1] * x[1], w = q1 * x[n] * x[n]; double v = q, u = w; double den = 1.0 - q - w; double q4 = 1.0 / den, q5 = 1.0 - q, q6 = 1.0 - w; double h = q2 * x[n], s = h; thy gain = e0 * den; q1 = 1.0 / thy gain; c[1] = q1 * x[1]; d[1] = q1 * x[n]; double s1 = 0.0; for (long k = 1; k <= n - 1; k++) { s1 += x[k + 1] * x[k]; } r[1] = 2.0 * s1; a[1] = - q1 * r[1]; thy gain *= (1.0 - a[1] * a[1]); while (m < mmax) { double eOld = thy gain, f = x[m + 1], b = x[n - m]; /*n-1 ->n-m*/ for (long k = 1; k <= m; k++) { /* n-1 -> n-m */ f += x[m + 1 - k] * a[k]; b += x[n - m + k] * a[k]; } q1 = 1.0 / thy gain; q2 = q1 * f; double q3 = q1 * b; for (long k = m; k >= 1; k--) { c[k + 1] = c[k] + q2 * a[k]; d[k + 1] = d[k] * q3 * a[k]; } c[1] = q2; d[1] = q3; double q7 = s * s; double y1 = f * f; double y2 = v * v; double y3 = b * b; double y4 = u * u; double y5 = 2.0 * h * s; q += y1 * q1 + q4 * (y2 * q6 + q7 * q5 + v * y5); w += y3 * q1 + q4 * (y4 * q5 + q7 * q6 + u * y5); h = s = u = v = 0; for (long k = 0; k <= m; k++) { h += x[n - m + k] * c[k + 1]; s += x[n - k] * c[k + 1]; u += x[n - k] * d[k + 1]; v += x[k + 1] * c[k + 1]; } q5 = 1.0 - q; q6 = 1.0 - w; den = q5 * q6 - h * h; if (den <= 0) { status = 2; goto end; /* 2: ill-conditioning */ } q4 = 1.0 / den; q1 *= q4; double alf = 1.0 / (1.0 + q1 * (y1 * q6 + y3 * q5 + 2.0 * h * f * b)); thy gain *= alf; y5 = h * s; double c1 = q4 * (f * q6 + b * h); double c2 = q4 * (b * q5 + h * f); double c3 = q4 * (v * q6 + y5); double c4 = q4 * (s * q5 + v * h); double c5 = q4 * (s * q6 + h * u); double c6 = q4 * (u * q5 + y5); for (long k = 1; k <= m; k++) { a[k] = alf * (a[k] + c1 * c[k + 1] + c2 * d[k + 1]); } for (long k = 1; k <= m / 2 + 1; k++) { s1 = c[k]; double s2 = d[k], s3 = c[m + 2 - k], s4 = d[m + 2 - k]; c[k] += c3 * s3 + c4 * s4; d[k] += c5 * s3 + c6 * s4; if (m + 2 - k == k) { continue; } c[m + 2 - k] += c3 * s1 + c4 * s2; d[m + 2 - k] += c5 * s1 + c6 * s2; } m++; c1 = x[n + 1 - m]; c2 = x[m]; double delta = 0; for (long k = m - 1; k >= 1; k--) { r[k + 1] = r[k] - x[n + 1 - k] * c1 - x[k] * c2; delta += r[k + 1] * a[k]; } s1 = 0.0; for (long k = 1; k <= n - m; k++) { s1 += x[k + m] * x[k]; } r[1] = 2.0 * s1; delta += r[1]; q2 = - delta / thy gain; a[m] = q2; for (long k = 1; k <= m / 2; k++) { s1 = a[k]; a[k] += q2 * a[m - k]; if (k == m - k) { continue; } a[m - k] += q2 * s1; } y1 = q2 * q2; thy gain *= 1.0 - y1; if (y1 >= 1.0) { status = 3; goto end; /* |a[m]| > 1 */ } if (thy gain < e0 * tol1) { status = 4; goto end; } if (eOld - thy gain < eOld * tol2) { status = 5; goto end; } } end: thy gain *= 0.5; /* because e0 is twice the energy */ thy nCoefficients = m; return status == 1 || status == 4 || status == 5; } static LPC _Sound_to_LPC (Sound me, int predictionOrder, double analysisWidth, double dt, double preEmphasisFrequency, int method, double tol1, double tol2) { double t1, samplingFrequency = 1.0 / my dx; double windowDuration = 2 * analysisWidth; /* gaussian window */ long nFrames, frameErrorCount = 0; if (floor (windowDuration / my dx) < predictionOrder + 1) Melder_throw ("Analysis window duration too short.\n" "For a prediction order of ", predictionOrder, " the analysis window duration has to be greater than ", my dx * (predictionOrder + 1), "Please increase the analysis window duration or lower the prediction order."); // Convenience: analyse the whole sound into one LPC_frame if (windowDuration > my dx * my nx) { windowDuration = my dx * my nx; } Sampled_shortTermAnalysis (me, windowDuration, dt, & nFrames, & t1); autoSound sound = Data_copy (me); autoSound sframe = Sound_createSimple (1, windowDuration, samplingFrequency); autoSound window = Sound_createGaussian (windowDuration, samplingFrequency); autoLPC thee = LPC_create (my xmin, my xmax, nFrames, dt, t1, predictionOrder, my dx); autoMelderProgress progress (L"LPC analysis"); if (preEmphasisFrequency < samplingFrequency / 2) { Sound_preEmphasis (sound.peek(), preEmphasisFrequency); } for (long i = 1; i <= nFrames; i++) { LPC_Frame lpcframe = (LPC_Frame) & thy d_frames[i]; double t = Sampled_indexToX (thee.peek(), i); LPC_Frame_init (lpcframe, predictionOrder); Sound_into_Sound (sound.peek(), sframe.peek(), t - windowDuration / 2); Vector_subtractMean (sframe.peek()); Sounds_multiply (sframe.peek(), window.peek()); if (method == LPC_METHOD_AUTO) { if (! Sound_into_LPC_Frame_auto (sframe.peek(), lpcframe)) { frameErrorCount++; } } else if (method == LPC_METHOD_COVAR) { if (! Sound_into_LPC_Frame_covar (sframe.peek(), lpcframe)) { frameErrorCount++; } } else if (method == LPC_METHOD_BURG) { if (! Sound_into_LPC_Frame_burg (sframe.peek(), lpcframe)) { frameErrorCount++; } } else if (method == LPC_METHOD_MARPLE) { if (! Sound_into_LPC_Frame_marple (sframe.peek(), lpcframe, tol1, tol2)) { frameErrorCount++; } } if ( (i % 10) == 1) { Melder_progress ( (double) i / nFrames, L"LPC analysis of frame ", Melder_integer (i), L" out of ", Melder_integer (nFrames), L"."); therror } } return thee.transfer(); } LPC Sound_to_LPC_auto (Sound me, int predictionOrder, double analysisWidth, double dt, double preEmphasisFrequency) { try { autoLPC thee = _Sound_to_LPC (me, predictionOrder, analysisWidth, dt, preEmphasisFrequency, LPC_METHOD_AUTO, 0, 0); return thee.transfer (); } catch (MelderError) { Melder_throw (me, ": no LPC (auto) created."); } } LPC Sound_to_LPC_covar (Sound me, int predictionOrder, double analysisWidth, double dt, double preEmphasisFrequency) { try { autoLPC thee = _Sound_to_LPC (me, predictionOrder, analysisWidth, dt, preEmphasisFrequency, LPC_METHOD_COVAR, 0, 0); return thee.transfer (); } catch (MelderError) { Melder_throw (me, ": no LPC (covar) created."); } } LPC Sound_to_LPC_burg (Sound me, int predictionOrder, double analysisWidth, double dt, double preEmphasisFrequency) { try { autoLPC thee = _Sound_to_LPC (me, predictionOrder, analysisWidth, dt, preEmphasisFrequency, LPC_METHOD_BURG, 0, 0); return thee.transfer (); } catch (MelderError) { Melder_throw (me, ": no LPC (burg) created."); } } LPC Sound_to_LPC_marple (Sound me, int predictionOrder, double analysisWidth, double dt, double preEmphasisFrequency, double tol1, double tol2) { try { autoLPC thee = _Sound_to_LPC (me, predictionOrder, analysisWidth, dt, preEmphasisFrequency, LPC_METHOD_MARPLE, tol1, tol2); return thee.transfer (); } catch (MelderError) { Melder_throw (me, ": no LPC (marple) created."); } } Sound LPC_and_Sound_filterInverse (LPC me, Sound thee) { try { if (my samplingPeriod != thy dx) { Melder_throw ("Sampling frequencies are not the same."); } if (my xmin != thy xmin || thy xmax != my xmax) { Melder_throw ("Domains of LPC and Sound are not equal."); } autoSound him = Data_copy (thee); double *e = his z[1], *x = thy z[1]; for (long i = 1; i <= his nx; i++) { double t = his x1 + (i - 1) * his dx; /* Sampled_indexToX (him, i) */ long iFrame = floor ( (t - my x1) / my dx + 1.5); /* Sampled_xToNearestIndex (me, t) */ double *a; if (iFrame < 1 || iFrame > my nx) { e[i] = 0; continue; } a = my d_frames[iFrame].a; long m = i > my d_frames[iFrame].nCoefficients ? my d_frames[iFrame].nCoefficients : i - 1; for (long j = 1; j <= m; j++) { e[i] += a[j] * x[i - j]; } } return him.transfer(); } catch (MelderError) { Melder_throw (thee, ": not inverse filtered."); } } /* gain used as a constant amplitude multiplyer within a frame of duration my dx. future alternative: convolve gain with a smoother. */ Sound LPC_and_Sound_filter (LPC me, Sound thee, int useGain) { try { double xmin = my xmin > thy xmin ? my xmin : thy xmin; double xmax = my xmax < thy xmax ? my xmax : thy xmax; if (xmin >= xmax) { Melder_throw ("Domains of Sound [", Melder_double(thy xmin), ",", Melder_double(thy xmax), "] and LPC [", Melder_double(my xmin), ",", Melder_double(my xmax), "] do not overlap."); } // resample sound if samplings don't match autoSound source = 0; if (my samplingPeriod != thy dx) { source.reset (Sound_resample (thee, 1.0 / my samplingPeriod, 50)); thee = source.peek(); // reference copy; remove at end } autoSound him = Data_copy (thee); double *x = his z[1]; long ifirst = Sampled_xToHighIndex (thee, xmin); long ilast = Sampled_xToLowIndex (thee, xmax); for (long i = ifirst; i <= ilast; i++) { double t = his x1 + (i - 1) * his dx; /* Sampled_indexToX (him, i) */ long iFrame = floor ( (t - my x1) / my dx + 1.5); /* Sampled_xToNearestIndex (me, t) */ if (iFrame < 1) { continue; } if (iFrame > my nx) { break; } double *a = my d_frames[iFrame].a; long m = i > my d_frames[iFrame].nCoefficients ? my d_frames[iFrame].nCoefficients : i - 1; for (long j = 1; j <= m; j++) { x[i] -= a[j] * x[i - j]; } } // Make samples before first frame and after last frame zero. for (long i = 1; i < ifirst; i++) { x[i] = 0; } for (long i = ilast + 1; i <= his nx; i++) { x[i] = 0; } if (useGain) { for (long i = ifirst; i <= ilast; i++) { double t = his x1 + (i - 1) * his dx; /* Sampled_indexToX (him, i) */ double riFrame = (t - my x1) / my dx + 1; /* Sampled_xToIndex (me, t); */ long iFrame = floor (riFrame); double phase = riFrame - iFrame; if (iFrame < 0 || iFrame > my nx) { x[i] = 0; } else if (iFrame == 0) { x[i] *= sqrt (my d_frames[1].gain) * phase; } else if (iFrame == my nx) { x[i] *= sqrt (my d_frames[my nx].gain) * (1 - phase); } else x[i] *= phase * sqrt (my d_frames[iFrame + 1].gain) + (1 - phase) * sqrt (my d_frames[iFrame].gain); } } return him.transfer(); } catch (MelderError) { Melder_throw (thee, ": not filtered."); } } void LPC_and_Sound_filterWithFilterAtTime_inline (LPC me, Sound thee, int channel, double time) { long frameIndex = Sampled_xToNearestIndex (me, time); if (frameIndex < 1) { frameIndex = 1; } if (frameIndex > my nx) { frameIndex = my nx; } if (channel > thy ny) { channel = 1; } if (frameIndex < 1 || frameIndex > my nx) { Melder_throw ("Frame number out of range."); } if (channel > 0) { LPC_Frame_and_Sound_filter (& (my d_frames[frameIndex]), thee, channel); } else { for (long ichan = 1; ichan <= thy ny; ichan++) { LPC_Frame_and_Sound_filter (& (my d_frames[frameIndex]), thee, ichan); } } } Sound LPC_and_Sound_filterWithFilterAtTime (LPC me, Sound thee, int channel, double time) { try { autoSound him = Data_copy (thee); LPC_and_Sound_filterWithFilterAtTime_inline (me, him.peek(), channel, time); return him.transfer(); } catch (MelderError) { Melder_throw (thee, ": not filtered."); } } void LPC_and_Sound_filterInverseWithFilterAtTime_inline (LPC me, Sound thee, int channel, double time) { try { long frameIndex = Sampled_xToNearestIndex (me, time); if (frameIndex < 1) { frameIndex = 1; } if (frameIndex > my nx) { frameIndex = my nx; } if (channel > thy ny) { channel = 1; } if (channel > 0) { LPC_Frame_and_Sound_filterInverse (& (my d_frames[frameIndex]), thee, channel); } else { for (long ichan = 1; ichan <= thy ny; ichan++) { LPC_Frame_and_Sound_filterInverse (& (my d_frames[frameIndex]), thee, ichan); } } } catch (MelderError) { Melder_throw (thee, ": not inverse filtered."); } } Sound LPC_and_Sound_filterInverseWithFilterAtTime (LPC me, Sound thee, int channel, double time) { try { autoSound him = Data_copy (thee); LPC_and_Sound_filterInverseWithFilterAtTime_inline (me, him.peek(), channel, time); return him.transfer(); } catch (MelderError) { Melder_throw (thee, ": not inverse filtered."); } } /* End of file Sound_and_LPC.cpp */ sources_5316/LPC/Tube.h0000644000176700017670000000363411627370150013421 0ustar paulpaul#ifndef _Tube_h_ #define _Tube_h_ /* Tube.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sampled.h" #include "Tube_def.h" oo_CLASS_CREATE (Tube, Sampled); /* Tube's as a function of time. Tube_frame: c[1] -> mouth c[nSegments] -> glottis. */ void Tube_Frame_init (Tube_Frame me, long nSegments, double length); void Tube_Frame_free (Tube_Frame me); void Tube_Frames_rc_into_area (Tube_Frame me, Tube_Frame thee); void Tube_init (I, double tmin, double tmax, long nt, double dt, double t1, long maxnSegments, double defaultLength); Thing_define (Area, Tube) { }; /* Areas as a function of time. units in m^2. */ void Area_init (Area me, double tmin, double tmax, long nt, double dt, double t1, long maxnSegments, double defaultLength); Area Area_create (double tmin, double tmax, long nt, double dt, double t1, long maxnSegments, double defaultLength); Thing_define (RC, Tube) { }; /* Reflection Coefficients as a function of time. */ void RC_init (RC me, double tmin, double tmax, long nt, double dt, double t1, long maxnCoefficients, double defaultLength); RC RC_create (double tmin, double tmax, long nt, double dt, double t1, long maxnCoefficients, double defaultLength); #endif // _Tube_h_ sources_5316/LPC/LPC_and_Polynomial.cpp0000644000176700017670000000301611630440776016520 0ustar paulpaul/* LPC_and_Polynomial.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header */ #include "LPC_and_Polynomial.h" Polynomial LPC_Frame_to_Polynomial (LPC_Frame me) { long degree = (long) my nCoefficients; autoPolynomial thee = Polynomial_create (-1, 1, degree); for (long i = 1; i <= degree; i++) { thy coefficients[i] = my a[degree - i + 1]; } thy coefficients[degree + 1] = 1; return thee.transfer(); } Polynomial LPC_to_Polynomial (LPC me, double time) { try { long iFrame = Sampled_xToIndex (me, time); if (iFrame < 1 || iFrame > my nx) { Melder_throw ("invalid frame number."); } autoPolynomial thee = LPC_Frame_to_Polynomial (&my d_frames[iFrame]); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ":no Polynomial created."); } } /* End of file LPC_and_Polynomial.cpp */ sources_5316/LPC/LPC.h0000644000176700017670000000325611745465263013153 0ustar paulpaul#ifndef _LPC_h_ #define _LPC_h_ /* LPC.h * * Copyright (C) 1994-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Matrix.h" #include "Graphics.h" #include "LPC_def.h" oo_CLASS_CREATE (LPC, Sampled); /* From Sampled: xmin, xmax : range of time (s) x1 : position of first frame (s) dx : step size (s) nx : number of frames */ void LPC_init (LPC me, double tmin, double tmax, long nt, double dt, double t1, int predictionOrder, double samplingPeriod); LPC LPC_create (double tmin, double tmax, long nt, double dt, double t1, int predictionOrder, double samplingPeriod); void LPC_drawGain (LPC me, Graphics g, double t1, double t2, double gmin, double gmax, int garnish); void LPC_drawPoles (LPC me, Graphics g, double time, int garnish); Matrix LPC_downto_Matrix_lpc (LPC me); Matrix LPC_downto_Matrix_rc (LPC me); Matrix LPC_downto_Matrix_area (LPC me); /******************* Frames ************************************************/ void LPC_Frame_init (LPC_Frame me, int nCoefficients); #endif /* _LPC_h_ */ sources_5316/LPC/Cepstrum.cpp0000644000176700017670000000574311725110316014655 0ustar paulpaul/* Cepstrum.cpp * * Copyright (C) 1994-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010514 djmw 20020812 GPL header djmw 20080122 Version 1: float -> double djmw 20110304 Thing_new */ #include "Cepstrum.h" #include "NUM2.h" Thing_implement (Cepstrum, Matrix, 2); Cepstrum Cepstrum_create (double qmin, double qmax, long nq) { try { autoCepstrum me = Thing_new (Cepstrum); double dx = (qmax - qmin) / nq; Matrix_init (me.peek(), qmin, qmax, nq, dx, qmin + dx / 2, 1, 1, 1, 1, 1); return me.transfer(); } catch (MelderError) { Melder_throw ("Cepstrum not created."); } } void Cepstrum_draw (Cepstrum me, Graphics g, double qmin, double qmax, double minimum, double maximum, int garnish) { int autoscaling = minimum >= maximum; Graphics_setInner (g); if (qmax <= qmin) { qmin = my xmin; qmax = my xmax; } long imin, imax; if (! Matrix_getWindowSamplesX (me, qmin, qmax, & imin, & imax)) { return; } autoNUMvector y (imin, imax); double *z = my z[1]; for (long i = imin; i <= imax; i++) { y[i] = z[i]; } if (autoscaling) { NUMvector_extrema (y.peek(), imin, imax, & minimum, & maximum); } for (long i = imin; i <= imax; i ++) { if (y[i] > maximum) { y[i] = maximum; } else if (y[i] < minimum) { y[i] = minimum; } } Graphics_setWindow (g, qmin, qmax, minimum, maximum); Graphics_function (g, y.peek(), imin, imax, Matrix_columnToX (me, imin), Matrix_columnToX (me, imax)); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Quefrency"); Graphics_marksBottom (g, 2, TRUE, TRUE, FALSE); Graphics_textLeft (g, 1, L"Amplitude"); } } Matrix Cepstrum_to_Matrix (Cepstrum me) { try { autoMatrix thee = Thing_new (Matrix); my structMatrix :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Matrix created."); } } Cepstrum Matrix_to_Cepstrum (Matrix me, long row) { try { autoCepstrum thee = Cepstrum_create (my xmin, my xmax, my nx); if (row < 0) { row = my ny + 1 - row; } if (row < 1) { row = 1; } if (row > my ny) { row = my ny; } NUMvector_copyElements (my z[row], thy z[1], 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Cepstrum created."); } } /* End of file Cepstrum.cpp */ sources_5316/LPC/LPC_and_Cepstrumc.cpp0000644000176700017670000000535211630440651016337 0ustar paulpaul/* LPC_and_Cepstrumc.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20080122 float -> double */ /* LPC_and_Cepstrumc.c */ #include "LPC_and_Cepstrumc.h" void LPC_Frame_into_Cepstrumc_Frame (LPC_Frame me, Cepstrumc_Frame thee) { long n = my nCoefficients > thy nCoefficients ? thy nCoefficients : my nCoefficients; double *c = thy c, *a = my a; c[0] = 0.5 * log (my gain); if (n == 0) { return; } c[1] = -a[1]; for (long i = 2; i <= n; i++) { c[i] = 0; for (long k = 1; k < i; k++) { c[i] += a[i - k] * c[k] * k; } c[i] = -a[i] - c[i] / i; } } void Cepstrumc_Frame_into_LPC_Frame (Cepstrumc_Frame me, LPC_Frame thee) { double *c = my c, *a = thy a; thy gain = exp (2 * c[0]); if (thy nCoefficients == 0) { return; } a[1] = -c[1]; for (long i = 2; i <= thy nCoefficients; i++) { c[i] *= i; } for (long i = 2; i <= thy nCoefficients; i++) { a[i] = c[i]; for (long j = 1 ; j < i; j++) { a[i] += a[j] * c[i - j]; } a[i] /= -i; } for (long i = 2; i <= thy nCoefficients; i++) { c[i] /= i; } } Cepstrumc LPC_to_Cepstrumc (LPC me) { try { autoCepstrumc thee = Cepstrumc_create (my xmin, my xmax, my nx, my dx, my x1, my maxnCoefficients, 1.0 / my samplingPeriod); for (long i = 1; i <= my nx; i++) { Cepstrumc_Frame_init (& thy frame[i], my d_frames[i].nCoefficients); LPC_Frame_into_Cepstrumc_Frame (& my d_frames[i], & thy frame[i]); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Cepstrum created."); } } LPC Cepstrumc_to_LPC (Cepstrumc me) { try { autoLPC thee = LPC_create (my xmin, my xmax, my nx, my dx, my x1, my maxnCoefficients, 1.0 / my samplingFrequency); for (long i = 1; i <= my nx; i++) { LPC_Frame_init (& thy d_frames[i], my frame[i].nCoefficients); Cepstrumc_Frame_into_LPC_Frame (& my frame[i], & thy d_frames[i]); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ":no LPC created."); } } /* End of file LPC_and_Cepstrumc.cpp */ sources_5316/LPC/Sound_and_Cepstrum.h0000644000176700017670000000222711607121356016313 0ustar paulpaul#ifndef _Sound_and_Cepstrum_h_ #define _Sound_and_Cepstrum_h_ /* Sound_and_Cepstrum.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20110307 Latest modification */ #include "Sound.h" #include "Cepstrum.h" #ifdef __cplusplus extern "C" { #endif Cepstrum Sound_to_Cepstrum (Sound me); Cepstrum Sound_to_Cepstrum_bw (Sound me); Sound Cepstrum_to_Sound (Cepstrum me); #ifdef __cplusplus } #endif #endif /* _Sound_and_Cepstrum_h_ */ sources_5316/LPC/LPC_to_Spectrogram.cpp0000644000176700017670000000360111606610746016542 0ustar paulpaul/* LPC_to_Spectrogram.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20080122 float -> double */ #include "LPC_to_Spectrogram.h" Spectrogram LPC_to_Spectrogram (LPC me, double dfMin, double bandwidthReduction, double deEmphasisFrequency) { try { double samplingFrequency = 1.0 / my samplingPeriod; long nfft = 2; if (dfMin <= 0) { nfft = 512; dfMin = samplingFrequency / nfft; } while (samplingFrequency / nfft > dfMin || nfft <= my maxnCoefficients) { nfft *= 2; } double freqStep = samplingFrequency / nfft; autoSpectrogram thee = (Spectrogram) Spectrogram_create (my xmin, my xmax, my nx, my dx, my x1, 0, samplingFrequency / 2, nfft / 2 + 1, freqStep, 0); for (long i = 1; i <= my nx; i++) { double t = Sampled_indexToX (me, i); autoSpectrum spec = LPC_to_Spectrum (me, t, dfMin, bandwidthReduction, deEmphasisFrequency); for (long j = 1; j <= spec -> nx; j++) { double re = spec -> z[1][j], im = spec -> z[2][j]; thy z[j][i] = re * re + im * im; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Spectrogram created."); } } /* End of file LPC_to_Spectrogram.cpp */ sources_5316/LPC/Sound_and_LPC_robust.cpp0000644000176700017670000002064711652233710017064 0ustar paulpaul/* Sound_and_LPC_robust.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030814 First version djmw 20061218 To Melder_information format djmw 20070103 Sound interface changes djmw 20080122 float -> double djmw 20101008 New LPC_Frame_filterInverse interface. djmw 20110302 Corrected a number of pointer initialisations djmw 20111027 +Sound_to_Formant_robust */ #include "LPC_and_Formant.h" #include "Sound_and_LPC.h" #include "Sound_and_LPC_robust.h" #include "Sound_extensions.h" #include "SVD.h" #include "Vector.h" #include "NUM2.h" struct huber_struct { Sound e; double k, tol, tol_svd; long iter, itermax; int wantlocation, wantscale; double location, scale; long n, p; double *w, *work; double *a; double **covar, *c; SVD svd; }; static void huber_struct_init (struct huber_struct *hs, double windowDuration, long p, double samplingFrequency, double location, int wantlocation) { hs -> w = hs -> work = hs -> a = hs -> c = 0; hs -> covar = 0; hs -> svd = 0; hs -> e = Sound_createSimple (1, windowDuration, samplingFrequency); long n = hs -> e -> nx; hs -> n = n; hs -> p = p; hs -> w = NUMvector (1, n); hs -> work = NUMvector (1, n); hs -> a = NUMvector (1, p); hs -> covar = NUMmatrix (1, p, 1, p); hs -> c = NUMvector (1, p); hs -> svd = SVD_create (p, p); hs -> wantlocation = wantlocation; if (! wantlocation) { hs -> location = location; } hs -> wantscale = 1; } static void huber_struct_destroy (struct huber_struct *hs) { forget (hs -> e); forget (hs -> svd); NUMvector_free (hs -> w, 1); NUMvector_free (hs -> work, 1); NUMvector_free (hs -> a, 1); NUMmatrix_free (hs -> covar, 1, 1); NUMvector_free (hs -> c, 1); } static void huber_struct_getWeights (struct huber_struct *hs, double *e) { double ks = hs -> k * hs -> scale; double *w = hs -> w; for (long i = 1 ; i <= hs -> n; i++) { double ei = e[i] - hs -> location; w[i] = ei > -ks && ei < ks ? 1 : ks / fabs (ei); } } static void huber_struct_getWeightedCovars (struct huber_struct *hs, double *s) { long p = hs -> p, n = hs -> n; double *w = hs -> w, **covar = hs -> covar, *c = hs -> c; for (long i = 1; i <= p; i++) { for (long j = i; j <= p; j++) { double tmp = 0; for (long k = p + 1; k <= n; k++) { tmp += s[k - j] * s[k - i] * w[k]; } covar[i][j] = covar[j][i] = tmp; } double tmp = 0; for (long k = p + 1; k <= n; k++) { tmp += s[k - i] * s[k] * w[k]; } c[i] = -tmp; } } static void huber_struct_solvelpc (struct huber_struct *hs) { SVD me = hs -> svd; double **covar = hs -> covar; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { my u[i][j] = covar[i][j]; } } SVD_setTolerance (me, hs -> tol_svd); SVD_compute (me); //long nzeros = SVD_zeroSmallSingularValues (me, 0); SVD_solve (me, hs -> c, hs -> a); } void LPC_Frames_and_Sound_huber (LPC_Frame me, Sound thee, LPC_Frame him, struct huber_struct *hs) { long p = my nCoefficients > his nCoefficients ? his nCoefficients : my nCoefficients; long n = hs -> e -> nx > thy nx ? thy nx : hs -> e -> nx; double *e = hs -> e -> z[1], *s = thy z[1]; hs -> iter = 0; hs -> scale = 1e38; hs -> p = p; double s0; do { Sound hse = hs -> e; for (long i = 1; i <= thy nx; i++) { hse -> z[1][i] = thy z[1][i]; } LPC_Frame_and_Sound_filterInverse (him, hse, 1); s0 = hs -> scale; NUMstatistics_huber (e, n, & (hs -> location), hs -> wantlocation, & (hs -> scale), hs -> wantscale, hs -> k, hs -> tol, hs -> work); huber_struct_getWeights (hs, e); huber_struct_getWeightedCovars (hs, s); // Solve C a = [-] c */ try { huber_struct_solvelpc (hs); } catch (MelderError) { // Copy the starting lpc coeffs */ for (long i = 1; i <= p; i++) { his a[i] = my a[i]; } throw MelderError(); } for (long i = 1; i <= p; i++) { his a[i] = hs -> a[i]; } (hs -> iter) ++; } while ( (hs -> iter < hs -> itermax) && (fabs (s0 - hs -> scale) > hs -> tol * s0)); } LPC LPC_and_Sound_to_LPC_robust (LPC thee, Sound me, double analysisWidth, double preEmphasisFrequency, double k, int itermax, double tol, int wantlocation) { struct huber_struct struct_huber = { 0 }; try { double t1, samplingFrequency = 1.0 / my dx, tol_svd = 0.000001; double location = 0, windowDuration = 2 * analysisWidth; /* Gaussian window */ long nFrames, frameErrorCount = 0, iter = 0; long p = thy maxnCoefficients; if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Time domains differ."); } if (my dx != thy samplingPeriod) { Melder_throw ("Sampling intervals differ."); } if (floor (windowDuration / my dx) < p + 1) { Melder_throw ("Analysis window too short."); } Sampled_shortTermAnalysis (me, windowDuration, thy dx, & nFrames, & t1); if (nFrames != thy nx || t1 != thy x1) { Melder_throw ("Incorrect retrieved analysis width"); } autoSound sound = Data_copy (me); autoSound sframe = Sound_createSimple (1, windowDuration, samplingFrequency); autoSound window = Sound_createGaussian (windowDuration, samplingFrequency); autoLPC him = Data_copy (thee); huber_struct_init (&struct_huber, windowDuration, p, samplingFrequency, location, wantlocation); struct_huber.k = k; struct_huber.tol = tol; struct_huber.tol_svd = tol_svd; struct_huber.itermax = itermax; autoMelderProgress progess (L"LPC analysis"); Sound_preEmphasis (sound.peek(), preEmphasisFrequency); for (long i = 1; i <= nFrames; i++) { LPC_Frame lpc = (LPC_Frame) & thy d_frames[i]; LPC_Frame lpcto = (LPC_Frame) & his d_frames[i]; double t = Sampled_indexToX (thee, i); Sound_into_Sound (sound.peek(), sframe.peek(), t - windowDuration / 2); Vector_subtractMean (sframe.peek()); Sounds_multiply (sframe.peek(), window.peek()); try { LPC_Frames_and_Sound_huber (lpc, sframe.peek(), lpcto, & struct_huber); } catch (MelderError) { frameErrorCount++; } iter += struct_huber.iter; if ( (i % 10) == 1) { Melder_progress ( (double) i / nFrames, L"LPC analysis of frame ", Melder_integer (i), L" out of ", Melder_integer (nFrames), L"."); therror } } if (frameErrorCount) Melder_warning (L"Results of ", Melder_integer (frameErrorCount), L" frame(s) out of ", Melder_integer (nFrames), L" could not be optimised."); MelderInfo_writeLine4 (L"Number of iterations: ", Melder_integer (iter), L"\n Average per frame: ", Melder_double (((double) iter) / nFrames)); huber_struct_destroy (&struct_huber); return him.transfer(); } catch (MelderError) { huber_struct_destroy (&struct_huber); Melder_throw (me, ": no robust LPC created."); } } Formant Sound_to_Formant_robust (Sound me, double dt_in, int numberOfPoles, double maximumFrequency, double halfdt_window, double preEmphasisFrequency, double safetyMargin, double k, int itermax, double tol, int wantlocation) { double dt = dt_in > 0.0 ? dt_in : halfdt_window / 4.0; double nyquist = 0.5 / my dx; long predictionOrder = 2 * numberOfPoles; try { autoSound sound = NULL; if (maximumFrequency <= 0.0 || fabs (maximumFrequency / nyquist - 1) < 1.0e-12) { sound.reset (Data_copy (me)); // will be modified } else { sound.reset (Sound_resample (me, maximumFrequency * 2, 50)); } autoLPC lpc = Sound_to_LPC_auto (sound.peek(), predictionOrder, halfdt_window, dt, preEmphasisFrequency); autoLPC lpcr = LPC_and_Sound_to_LPC_robust (lpc.peek(), sound.peek(), halfdt_window, preEmphasisFrequency, k, itermax, tol, wantlocation); autoFormant thee = LPC_to_Formant (lpcr.peek(), safetyMargin); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no robust Formant created."); } } /* End of file Sound_and_LPC_robust.cpp */ sources_5316/LPC/VocalTractTier.cpp0000664000176700017670000001531011745740321015741 0ustar paulpaul/* VocalTractTier.cpp * * Copyright (C) 2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "NUM2.h" #include "RealTier.h" #include "VocalTractTier.h" #include "oo_DESTROY.h" #include "VocalTractTier_def.h" #include "oo_COPY.h" #include "VocalTractTier_def.h" #include "oo_EQUAL.h" #include "VocalTractTier_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "VocalTractTier_def.h" #include "oo_WRITE_TEXT.h" #include "VocalTractTier_def.h" #include "oo_READ_TEXT.h" #include "VocalTractTier_def.h" #include "oo_WRITE_BINARY.h" #include "VocalTractTier_def.h" #include "oo_READ_BINARY.h" #include "VocalTractTier_def.h" #include "oo_DESCRIPTION.h" #include "VocalTractTier_def.h" /***** VocalTractPoint *****/ void VocalTract_drawSegments (VocalTract me, Graphics g, double maxLength, double maxArea, bool closedAtGlottis) { Graphics_setInner (g); double maxCrossection = sqrt (maxArea); Graphics_setWindow (g, 0, maxLength, -maxCrossection, maxCrossection); for (long isection = 1; isection <= my nx; isection++) { double x1 = (isection - 1) * my dx, x2 = x1 + my dx; double crosssection2 = sqrt (my z[1][isection]); Graphics_line (g, x1, crosssection2, x2, crosssection2); Graphics_line (g, x1, -crosssection2, x2, -crosssection2); if (isection > 1) { double crosssection1 = sqrt (my z[1][isection - 1]); Graphics_line (g, x1, crosssection1, x1, crosssection2); Graphics_line (g, x1, -crosssection1, x1, -crosssection2); } else if (isection == 1 and closedAtGlottis) { Graphics_line (g, x1, crosssection2, x1, -crosssection2); } } Graphics_unsetInner (g); } Thing_implement (VocalTractPoint, AnyPoint, 0); VocalTractPoint VocalTract_to_VocalTractPoint (VocalTract me, double time) { try { autoVocalTractPoint thee = Thing_new (VocalTractPoint); thy number = time; thy d_vocalTract = (VocalTract) Data_copy (me); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to VocalTractPoint."); } } /***** VocalTractTier *****/ Thing_implement (VocalTractTier, Function, 0); VocalTractTier VocalTractTier_create (double fromTime, double toTime) { try { autoVocalTractTier me = Thing_new (VocalTractTier); Function_init (me.peek(), fromTime, toTime); my d_vocalTracts = SortedSetOfDouble_create (); return me.transfer(); } catch (MelderError) { Melder_throw (": VocalTractTier not created."); } } VocalTractTier VocalTract_to_VocalTractTier (VocalTract me, double startTime, double endTime, double time) { try { autoVocalTractTier thee = VocalTractTier_create (startTime, endTime); VocalTractTier_addVocalTract (thee.peek(), time, me); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to VocalTractTier"); } } void VocalTractTier_addVocalTract (VocalTractTier me, double time, VocalTract vocaltract) { try { autoVocalTractPoint thee = VocalTract_to_VocalTractPoint (vocaltract, time); if (my d_vocalTracts -> size > 1) { VocalTractPoint vtp = (VocalTractPoint) my d_vocalTracts -> item[1]; long numberOfSections = vtp -> d_vocalTract -> nx; if (numberOfSections != vocaltract -> nx) { forget (vocaltract); Melder_throw ("The number of sections must be equal to ", Melder_integer (numberOfSections), "."); } } Collection_addItem (my d_vocalTracts, thee.transfer()); } catch (MelderError) { Melder_throw (me, ": no VocalTract added."); } } VocalTract VocalTractTier_to_VocalTract (VocalTractTier me, double time) { try { VocalTractPoint vtp = (VocalTractPoint) my d_vocalTracts -> item[1]; long numberOfSections = vtp -> d_vocalTract -> nx; autoVocalTract thee = VocalTract_create (numberOfSections, vtp -> d_vocalTract -> dx); for (long isection = 1; isection <= numberOfSections; isection++) { autoRealTier section = RealTier_create (my xmin, my xmax); for (long i = 1; i <= my d_vocalTracts -> size; i++) { VocalTractPoint vtpi = (VocalTractPoint) my d_vocalTracts -> item[i]; double areai = vtpi -> d_vocalTract -> z[1][isection]; RealTier_addPoint (section.peek(), vtpi -> number, areai); } thy z[1][isection] = RealTier_getValueAtTime (section.peek(), time); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no VocalTract created."); } } LPC VocalTractTier_to_LPC (VocalTractTier me, double timeStep) { try { if (my d_vocalTracts -> size == 0) { Melder_throw ("Empty VocalTractTier"); } long numberOfFrames = floor((my xmax - my xmin) / timeStep); VocalTractPoint vtp = (VocalTractPoint) my d_vocalTracts -> item[1]; long numberOfSections = vtp -> d_vocalTract -> nx; double samplingPeriod = 1.0 / (1000.0 * numberOfSections); autoNUMmatrix area (1, numberOfFrames, 1, numberOfSections + 1); autoNUMvector areavec (1, numberOfSections + 1); autoLPC thee = LPC_create (my xmin, my xmax, numberOfFrames, timeStep, timeStep / 2, numberOfSections, samplingPeriod); // interpolate each section for (long isection = 1; isection <= numberOfSections; isection++) { autoRealTier sectioni = RealTier_create (my xmin, my xmax); for (long i = 1; i <= my d_vocalTracts -> size; i++) { VocalTractPoint vtpi = (VocalTractPoint) my d_vocalTracts -> item[i]; double areai = vtpi -> d_vocalTract -> z[1][isection]; RealTier_addPoint (sectioni.peek(), vtpi -> number, areai); } for (long iframe = 1; iframe <= numberOfFrames; iframe++) { double time = thy x1 + (iframe - 1) * thy dx; area[iframe][isection] = RealTier_getValueAtTime (sectioni.peek(), time); area[iframe][numberOfSections + 1] = 0.0001; // normalisation is area[n+1] = 0.0001 } } for (long iframe = 1; iframe <= numberOfFrames; iframe++) { LPC_Frame frame = &thy d_frames[iframe]; LPC_Frame_init (frame, numberOfSections); for (long i = 1; i <= numberOfSections + 1; i++) { areavec[i] = area[iframe][numberOfSections + 1 - i]; } NUMlpc_area_to_lpc (areavec.peek(), numberOfSections + 1, frame -> a); frame -> gain = 1e-6; // something } return thee.transfer(); } catch (MelderError) { Melder_throw (": not converted to LPC."); } } /* End of file VocalTractTier.cpp */ sources_5316/LPC/Cepstrumc.cpp0000644000176700017670000001406211634154427015024 0ustar paulpaul/* Cepstrumc.c * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20061218 Changed info to Melder_writeLine format. djmw 20071017 oo_CAN_WRITE_AS_ENCODING.h djmw 20080122 Version 1: float -> double djmw 20110304 Thing_new */ #include "Cepstrumc.h" #include "DTW.h" #include "oo_DESTROY.h" #include "Cepstrumc_def.h" #include "oo_COPY.h" #include "Cepstrumc_def.h" #include "oo_EQUAL.h" #include "Cepstrumc_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Cepstrumc_def.h" #include "oo_WRITE_TEXT.h" #include "Cepstrumc_def.h" #include "oo_WRITE_BINARY.h" #include "Cepstrumc_def.h" #include "oo_READ_TEXT.h" #include "Cepstrumc_def.h" #include "oo_READ_BINARY.h" #include "Cepstrumc_def.h" #include "oo_DESCRIPTION.h" #include "Cepstrumc_def.h" Thing_implement (Cepstrumc, Sampled, 1); void structCepstrumc :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L" Start time: ", Melder_double (xmin)); MelderInfo_writeLine2 (L" End time: ", Melder_double (xmax)); MelderInfo_writeLine2 (L" Number of frames: ", Melder_integer (nx)); MelderInfo_writeLine2 (L" Time step: ", Melder_double (dx)); MelderInfo_writeLine2 (L" First frame at: ", Melder_double (x1)); MelderInfo_writeLine2 (L" Number of coefficients: ", Melder_integer (maxnCoefficients)); } void Cepstrumc_Frame_init (Cepstrumc_Frame me, int nCoefficients) { my c = NUMvector (0, nCoefficients); my nCoefficients = nCoefficients; } void Cepstrumc_init (Cepstrumc me, double tmin, double tmax, long nt, double dt, double t1, int nCoefficients, double samplingFrequency) { my samplingFrequency = samplingFrequency; my maxnCoefficients = nCoefficients; Sampled_init (me, tmin, tmax, nt, dt, t1); my frame = NUMvector (1, nt); } Cepstrumc Cepstrumc_create (double tmin, double tmax, long nt, double dt, double t1, int nCoefficients, double samplingFrequency) { try { autoCepstrumc me = Thing_new (Cepstrumc); Cepstrumc_init (me.peek(), tmin, tmax, nt, dt, t1, nCoefficients, samplingFrequency); return me.transfer(); } catch (MelderError) { Melder_throw ("Cepstrum not created."); } } static void regression (Cepstrumc me, long frame, double r[], long nr) { long nc = 1e6; double sumsq = 0; for (long i = 0; i <= my maxnCoefficients; i++) { r[i] = 0; } if (frame <= nr / 2 || frame >= my nx - nr / 2) { return; } for (long j = -nr / 2; j <= nr / 2; j++) { Cepstrumc_Frame f = & my frame[frame + j]; if (f->nCoefficients < nc) { nc = f->nCoefficients; } sumsq += j * j; } for (long i = 0; i <= nc; i++) { for (long j = -nr / 2; j <= nr / 2; j++) { Cepstrumc_Frame f = & my frame[frame + j]; r[i] += f->c[i] * j / sumsq / my dx; } } } DTW Cepstrumc_to_DTW (Cepstrumc me, Cepstrumc thee, double wc, double wle, double wr, double wer, double dtr, int matchStart, int matchEnd, int constraint) { try { long nr = dtr / my dx; if (my maxnCoefficients != thy maxnCoefficients) { Melder_throw ("Cepstrumc orders must be equal."); } if (wr != 0 && nr < 2) { Melder_throw ("Time window for regression coefficients too small."); } if (nr % 2 == 0) { nr++; } if (wr != 0) { Melder_casual ("Number of frames used for regression coefficients %ld", nr); } autoDTW him = DTW_create (my xmin, my xmax, my nx, my dx, my x1, thy xmin, thy xmax, thy nx, thy dx, thy x1); autoNUMvector ri (0L, my maxnCoefficients); autoNUMvector rj (0L, my maxnCoefficients); // Calculate distance matrix autoMelderProgress progress (L""); for (long i = 1; i <= my nx; i++) { Cepstrumc_Frame fi = & my frame[i]; regression (me, i, ri.peek(), nr); for (long j = 1; j <= thy nx; j++) { Cepstrumc_Frame fj = & thy frame[j]; double d, dist = 0, distr = 0; if (wc != 0) { /* cepstral distance */ for (long k = 1; k <= fj -> nCoefficients; k++) { d = fi -> c[k] - fj -> c[k]; dist += d * d; } dist *= wc; } // log energy distance d = fi -> c[0] - fj -> c[0]; dist += wle * d * d; if (wr != 0) { // regression distance regression (thee, j, rj.peek(), nr); for (long k = 1; k <= fj -> nCoefficients; k++) { d = ri[k] - rj[k]; distr += d * d; } dist += wr * distr; } if (wer != 0) { // regression on c[0]: log(energy) if (wr == 0) { regression (thee, j, rj.peek(), nr); } d = ri[0] - rj[0]; dist += wer * d * d; } dist /= wc + wle + wr + wer; his z[i][j] = sqrt (dist); // prototype along y-direction } Melder_progress ( (double) i / my nx, L"Calculate distances: frame ", Melder_integer (i), L" from ", Melder_integer (my nx), L"."); } DTW_findPath (him.peek(), matchStart, matchEnd, constraint); return him.transfer(); } catch (MelderError) { Melder_throw ("DTW not created."); } } Matrix Cepstrumc_to_Matrix (Cepstrumc me) { try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 0, my maxnCoefficients, my maxnCoefficients + 1, 1, 0); for (long i = 1; i <= my nx; i++) { Cepstrumc_Frame him = & my frame[i]; for (long j = 1; j <= his nCoefficients + 1; j++) { thy z[j][i] = his c[j - 1]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Matrix created."); } } /* End of file Cepstrumc.cpp */ sources_5316/LPC/LPC_def.h0000644000176700017670000000271411630437035013754 0ustar paulpaul/* LPC_def.h * * Copyright (C) 1994-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT LPC_Frame oo_DEFINE_STRUCT (LPC_Frame) oo_INT (nCoefficients) #if oo_READING_BINARY if (localVersion == 0) { oo_FLOAT_VECTOR (a, nCoefficients) oo_FLOAT (gain) } else { oo_DOUBLE_VECTOR (a, nCoefficients) oo_DOUBLE (gain) } #else oo_DOUBLE_VECTOR (a, nCoefficients) oo_DOUBLE (gain) #endif oo_END_STRUCT (LPC_Frame) #undef ooSTRUCT #define ooSTRUCT LPC oo_DEFINE_CLASS (LPC, Sampled) /* samplingPeriod */ oo_DOUBLE (samplingPeriod) /* from Sound */ oo_INT (maxnCoefficients) oo_STRUCT_VECTOR (LPC_Frame, d_frames, nx) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (LPC) #undef ooSTRUCT /* End of file LPC_def.h */ sources_5316/LPC/LPC_to_Spectrogram.h0000644000176700017670000000237311535132164016206 0ustar paulpaul#ifndef _LPC_to_Spectrogram_h_ #define _LPC_to_Spectrogram_h_ /* LPC_to_Spectrogram.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19980322 djmw 20020812 GPL header djmw 20110307 Latest modification */ #include "LPC.h" #include "Spectrogram.h" #include "LPC_to_Spectrum.h" #ifdef __cplusplus extern "C" { #endif Spectrogram LPC_to_Spectrogram (LPC me, double dfMin, double bandwidthReduction, double deEmphasisFrequency); /* if(dfMin >= 0) df <= dfMin else df = NyquistFrequency / 512 */ #ifdef __cplusplus } #endif #endif /* _LPC_and_Spectrogram_h_ */ sources_5316/LPC/LPC_and_Polynomial.h0000644000176700017670000000222211607121356016155 0ustar paulpaul#ifndef _LPC_and_Polynomial_h_ #define _LPC_and_Polynomial_h_ /* LPC_and_Polynomial.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19990607 djmw 20020812 GPL header djmw 20110307 Latest modification */ #include "LPC.h" #include "Polynomial.h" #ifdef __cplusplus extern "C" { #endif Polynomial LPC_to_Polynomial (LPC me, double t); Polynomial LPC_Frame_to_Polynomial (LPC_Frame me); #ifdef __cplusplus } #endif #endif /* _LPC_and_Polynomial_h_ */ sources_5316/LPC/LPC_and_LFCC.h0000644000176700017670000000353411535132164014547 0ustar paulpaul#ifndef _LPC_and_LFCC_h_ #define _LPC_and_LFCC_h_ /* LPC_and_LFCC.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20001228 djmw 20020812 GPL header djmw 20110307 Latest modification */ #include "LPC.h" #include "LFCC.h" #ifdef __cplusplus extern "C" { #endif LFCC LPC_to_LFCC (LPC me, long numberOfCoefficients); LPC LFCC_to_LPC (LFCC me, long numberOfCoefficients); void LPC_Frame_into_CC_Frame (LPC_Frame me, CC_Frame thee); /* Transformation of lp-coefficients to cepstral coefficients. The number of cepstral coefficients may be larger than the number of lp-coefficients (equation 5). Reference: Digital Signal Processing Committee (eds.), Programs for Digital Signal Processing, IEEE Press, 1979 (Formulas 4a, 4b, 4c and 5, page 4.3-2). */ void CC_Frame_into_LPC_Frame (CC_Frame me, LPC_Frame thee); /* Transformation of cepstral coefficients to lp-coefficients. The number of lp-coefficients can never exceed the number of cepstral coefficients. Reference: Digital Signal Processing Committee (eds.), Programs for Digital Signal Processing, IEEE Press, 1979 (page 4.3-6). */ #ifdef __cplusplus } #endif #endif /* _LPC_and_LFCC_h_ */ sources_5316/LPC/LPC.cpp0000644000176700017670000001364011745506156013501 0ustar paulpaul/* LPC.cpp * * Copyright (C) 1994-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20030612 Removed LPC_Frame_free djmw 20060510 LPC_drawPoles error cleared if something goes wrong. djmw 20061212 Changed info to Melder_writeLine format. djmw 20071017 oo_CAN_WRITE_AS_ENCODING.h djmw 20080122 float -> double djmw 20081223 Corrected a bug in Matrix LPC_to_Matrix (last coefficient was not copied) djmw 20110304 Thing_new */ #include "LPC_and_Polynomial.h" #include "NUM2.h" #include "oo_DESTROY.h" #include "LPC_def.h" #include "oo_COPY.h" #include "LPC_def.h" #include "oo_EQUAL.h" #include "LPC_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "LPC_def.h" #include "oo_WRITE_TEXT.h" #include "LPC_def.h" #include "oo_WRITE_BINARY.h" #include "LPC_def.h" #include "oo_READ_TEXT.h" #include "LPC_def.h" #include "oo_READ_BINARY.h" #include "LPC_def.h" #include "oo_DESCRIPTION.h" #include "LPC_def.h" Thing_implement (LPC, Sampled, 1); void structLPC :: v_info () { structData :: v_info (); MelderInfo_writeLine5 (L"Time domain: ", Melder_double (xmin), L" to ", Melder_double (xmax), L" (s)."); MelderInfo_writeLine2 (L"Prediction order: ", Melder_integer (maxnCoefficients)); MelderInfo_writeLine2 (L"Number of frames: ", Melder_integer (nx)); MelderInfo_writeLine3 (L"Time step: ", Melder_double (dx), L" (s)."); MelderInfo_writeLine3 (L"First frame at: ", Melder_double (x1), L" (s)."); } void LPC_Frame_init (LPC_Frame me, int nCoefficients) { if (nCoefficients != 0) { my a = NUMvector (1, nCoefficients); } my nCoefficients = nCoefficients; } void LPC_init (LPC me, double tmin, double tmax, long nt, double dt, double t1, int predictionOrder, double samplingPeriod) { my samplingPeriod = samplingPeriod; my maxnCoefficients = predictionOrder; Sampled_init (me, tmin, tmax, nt, dt, t1); my d_frames = NUMvector (1, nt); } LPC LPC_create (double tmin, double tmax, long nt, double dt, double t1, int predictionOrder, double samplingPeriod) { try { autoLPC me = Thing_new (LPC); LPC_init (me.peek(), tmin, tmax, nt, dt, t1, predictionOrder, samplingPeriod); return me.transfer(); } catch (MelderError) { Melder_throw ("LPC not created."); } } void LPC_drawGain (LPC me, Graphics g, double tmin, double tmax, double gmin, double gmax, int garnish) { if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } long itmin, itmax; if (! Sampled_getWindowSamples (me, tmin, tmax, & itmin, & itmax)) { return; } autoNUMvector gain (itmin, itmax); for (long iframe = itmin; iframe <= itmax; iframe++) { gain[iframe] = my d_frames[iframe].gain; } if (gmax <= gmin) { NUMvector_extrema (gain.peek(), itmin, itmax, & gmin, & gmax); } if (gmax == gmin) { gmin = 0; gmax += 0.5; } Graphics_setInner (g); Graphics_setWindow (g, tmin, tmax, gmin, gmax); for (long iframe = itmin; iframe <= itmax; iframe++) { double x = Sampled_indexToX (me, iframe); Graphics_fillCircle_mm (g, x, gain[iframe], 1.0); } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Time (seconds)"); Graphics_textLeft (g, 1, L"Gain"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } void LPC_drawPoles (LPC me, Graphics g, double time, int garnish) { autoPolynomial p = LPC_to_Polynomial (me, time); autoRoots r = Polynomial_to_Roots (p.peek()); Roots_draw (r.peek(), g, -1, 1, -1, 1, L"+", 12, garnish); } Matrix LPC_downto_Matrix_lpc (LPC me) { try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 0.5, 0.5 + my maxnCoefficients, my maxnCoefficients, 1, 1); for (long j = 1; j <= my nx; j++) { LPC_Frame lpc = & my d_frames[j]; for (long i = 1; i <= lpc -> nCoefficients; i++) { thy z[i][j] = lpc -> a[i]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Matrix with linear prediction coefficients created."); } } Matrix LPC_downto_Matrix_rc (LPC me) { try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 0.5, 0.5 + my maxnCoefficients, my maxnCoefficients, 1, 1); autoNUMvector rc (1, my maxnCoefficients); for (long j = 1; j <= my nx; j++) { LPC_Frame lpc = & my d_frames[j]; NUMlpc_lpc_to_rc (lpc -> a, lpc -> nCoefficients, rc.peek()); for (long i = 1; i <= lpc -> nCoefficients; i++) { thy z[i][j] = rc[i]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Matrix with relection coefficients created."); } } Matrix LPC_downto_Matrix_area (LPC me) { try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 0.5, 0.5 + my maxnCoefficients, my maxnCoefficients, 1, 1); autoNUMvector rc (1, my maxnCoefficients); autoNUMvector area (1, my maxnCoefficients); for (long j = 1; j <= my nx; j++) { LPC_Frame lpc = & my d_frames[j]; NUMlpc_lpc_to_rc (lpc -> a, lpc -> nCoefficients, rc.peek()); NUMlpc_rc_to_area (rc.peek(), lpc -> nCoefficients, area.peek()); for (long i = 1; i <= lpc -> nCoefficients; i++) { thy z[i][j] = area[i]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Matrix with areas created."); } } /* End of file LPC.cpp */ sources_5316/LPC/VocalTractTier.h0000664000176700017670000000315111744263421015406 0ustar paulpaul#ifndef _VocalTractTier_h_ #define _VocalTractTier_h_ /* VocalTractTier.h * * Copyright (C) 2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "AnyTier.h" #include "LPC.h" #include "VocalTract.h" #include "VocalTractTier_def.h" oo_CLASS_CREATE (VocalTractPoint, AnyPoint); oo_CLASS_CREATE (VocalTractTier, Function); void VocalTract_drawSegments (VocalTract me, Graphics g, double maxLength, double maxArea, bool closedAtGlottis); VocalTractPoint VocalTract_to_VocalTractPoint (VocalTract me, double time); VocalTractTier VocalTractTier_create (double fromTime, double toTime); VocalTractTier VocalTract_to_VocalTractTier (VocalTract me, double startTime, double endTime, double time); void VocalTractTier_addVocalTract (VocalTractTier me, double time, VocalTract thee); LPC VocalTractTier_to_LPC (VocalTractTier me, double timeStep); VocalTract VocalTractTier_to_VocalTract (VocalTractTier me, double time); /* End of file VocalTractTier.h */ #endif sources_5316/LPC/Tube.cpp0000644000176700017670000001014111745224332013744 0ustar paulpaul/* Tube.cpp * * Copyright (C) 1994-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030613 Creation djmw 20061212 Changed info to Melder_writeLine format. djmw 20110304 Thing_new */ #include "Tube.h" #include "NUM2.h" #include "oo_DESTROY.h" #include "Tube_def.h" #include "oo_COPY.h" #include "Tube_def.h" #include "oo_EQUAL.h" #include "Tube_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Tube_def.h" #include "oo_WRITE_TEXT.h" #include "Tube_def.h" #include "oo_WRITE_BINARY.h" #include "Tube_def.h" #include "oo_READ_TEXT.h" #include "Tube_def.h" #include "oo_READ_BINARY.h" #include "Tube_def.h" #include "oo_DESCRIPTION.h" #include "Tube_def.h" Thing_implement (Tube, Sampled, 0); void structTube :: v_info () { structData :: v_info (); MelderInfo_writeLine5 (L"Time domain: ", Melder_double (xmin), L" to ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine2 (L"Maximum number of segments: ", Melder_integer (maxnSegments)); MelderInfo_writeLine2 (L"Number of frames: ", Melder_integer (nx)); MelderInfo_writeLine3 (L"Time step: ", Melder_double (dx), L" seconds"); MelderInfo_writeLine3 (L"First frame at: ", Melder_double (x1), L" seconds"); } void Tube_Frame_init (Tube_Frame me, long nSegments, double length) { my nSegments = nSegments; my length = length; if (nSegments <= 0) { Melder_throw ("Number of segments must be a natural number."); } my c = NUMvector (1, nSegments); } /* Gray & Markel (1979), LPTRN */ void Tube_Frames_rc_into_area (Tube_Frame me, Tube_Frame thee) { if (my nSegments > thy nSegments) { Melder_throw ("Number of segments to big."); } double s = 0.0001; /* 1.0 cm^2 at glottis */ double *rc = my c, *area = thy c; for (long i = my nSegments; i > 0; i--) { s *= (1.0 + rc[i]) / (1.0 - rc[i]); area[i] = s; } } static void Tube_setLengths (I, double length) { iam (Tube); for (long i = 1; i <= my nx; i++) { Tube_Frame f = & my frame[i]; if (f) { f -> length = length; } } } void Tube_init (I, double tmin, double tmax, long nt, double dt, double t1, long maxnSegments, double defaultLength) { iam (Tube); my maxnSegments = maxnSegments; Sampled_init (me, tmin, tmax, nt, dt, t1); my frame = NUMvector (1, nt); Tube_setLengths (me, defaultLength); } Thing_implement (Area, Tube, 0); void Area_init (Area me, double tmin, double tmax, long nt, double dt, double t1, long maxnSegments, double defaultLength) { Tube_init (me, tmin, tmax, nt, dt, t1, maxnSegments, defaultLength); } Area Area_create (double tmin, double tmax, long nt, double dt, double t1, long maxnSegments, double defaultLength) { try { autoArea me = Thing_new (Area); Area_init (me.peek(), tmin, tmax, nt, dt, t1, maxnSegments, defaultLength); return me.transfer(); } catch (MelderError) { Melder_throw ("Area not crteated."); } } Thing_implement (RC, Tube, 0); void RC_init (RC me, double tmin, double tmax, long nt, double dt, double t1, long maxnSegments, double defaultLength) { Tube_init (me, tmin, tmax, nt, dt, t1, maxnSegments, defaultLength); } RC RC_create (double tmin, double tmax, long nt, double dt, double t1, long maxnCoefficients, double defaultLength) { try { autoRC me = Thing_new (RC); RC_init (me.peek(), tmin, tmax, nt, dt, t1, maxnCoefficients, defaultLength); return me.transfer(); } catch (MelderError) { Melder_throw ("RC not crteated."); } } /* End of file Tube.cpp */ sources_5316/LPC/Cepstrumc.h0000644000176700017670000000446211627367400014473 0ustar paulpaul#ifndef _Cepstrumc_h_ #define _Cepstrumc_h_ /* Cepstrumc.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950822 djmw 20020812 GPL header djmw 20110306 Latest modification. */ #include "Sampled.h" #include "Matrix.h" #include "Graphics.h" #include "DTW.h" #include "Cepstrumc_def.h" oo_CLASS_CREATE (Cepstrumc, Sampled); void Cepstrumc_init (Cepstrumc me, double tmin, double tmax, long nt, double dt, double t1, int nCoefficients, double samplingFrequency); Cepstrumc Cepstrumc_create (double tmin, double tmax, long nt, double dt, double t1, int nCoefficients, double samplingFrequency); /******************* Frames ************************************************/ void Cepstrumc_Frame_init (Cepstrumc_Frame me, int nCoefficients); DTW Cepstrumc_to_DTW ( Cepstrumc me, Cepstrumc thee, double wc, double wle, double wr, double wer, double dtr, int matchStart, int matchEnd, int constraint); /* 1. Calculate distances between Cepstra: Distance between frame i (from me) and j (from thee) is wc * d1 + wle * d2 + wr * d3 + wer * d4, where wc, wle, wr & wer are weights and d1 = Sum (k=1; k=nCoefficients; (c[i,k]-c[j,k])^2) d2 = (c[0,k]-c[0,k])^2 d3 = Sum (k=1; k=nCoefficients; (r[i,k]-r[j,k])^2), with r[i,k] the regression coefficient of the cepstral coefficients from the frames within a time span of 'dtr' seconds. c[i,j] is jth cepstral coefficient in frame i. d4 = regression on energy (c[0]) 2. Find optimum path through the distance matrix (see DTW). PRECONDITIONS: at least one of wc, wle, wr, wer != 0 */ Matrix Cepstrumc_to_Matrix (Cepstrumc me); #endif /* _Cepstrumc_h_ */ sources_5316/praat_xcodeproj.dmg0000644000176700017670000063667211753025147015631 0ustar paulpaulxs bb``ðM£`†LIxíÔ; Â@Ј'Hé<€ÚˆM `c'ƒ†˜ûã®ÒmÞÀ6ûfß,›gIŒi“0–릹”qf$žë‡¦h»ª«n×C]4ïv.ÃdÌ)~\ ú¿J’,=V÷󼪋ÓÈ#èû¿Ýì>Þ+KC²ÅÇ-B`è¶;Õ÷Ó–#ïãu>æ‰ÿ‰ @€ @€ @€ @€ @€ @€ @€ @€ @€ @€ @€ @€ @€ @€ @€üÀå'xì½K#Y’.V\Hª^i¥¥Ä)ÝAÏ´*3éo÷¹ÕÝ—Ï׭Ìê®YÅeìdl>22«0´ ½6ý ý„»š­‚ýi'}çáô—ù9N#ƒ¥ÉjtUF†ûq3;vìØÛ>ùäã?)ð‘ÿR)ðûÿæ“õ>ùëO~?~õŸ|òéÿüÿùÿþ«ÿøÏÿÛÿ%èÿþŸøÏ‚ÿÿ«O>ùÏñŸOÿ—O>ùOÿñÜ'…Åÿ?ùä¿üä“ÿLüRü£þFý¹ôïÿöÿçÿé¿þ__¼Q)—¯d«4¾WZ¤é‡¿ú÷ørWüö¿Àÿÿ;ý_ñóiÿ”Öû«ÿ‹ˆuOÿG®×ï‹uþGý_ñóÇ>Rà#>Rà#>Rà#>Rà#>RàƒRàÿ-ÿóüWåŸk?ý?ÄÿáƒBüôû÷OÂG>Rà#>Rà#>Rà#>Rà#>Rà#>Rà#>Rà( |ñÛw÷‹ÎÛt³¯–¿þÌyÞý¬“.§«Ù|yûëϾ=~öÛßüâ‹¿~3xýߎ:ëÅ|»ë|û}ÿË—ƒÎgÏ^¼è­×‹´3Xݯ÷»tóâÅðõ°óí—/_½î`±/F_Öùìn·[ÿý‹Ï'âñçÓÕ½xpûâÛÍjnvï¿ÄªÏðÂóÙnö¾§>S‚ ;›Ow¿ùŧ_¼Ißÿ¦7ÝÍߦßòu*ÿøõä>ýâ…øžØî6Àà7XþÏøí/ôÏÙ»‹Åê!}µšíéöðÒd³™ˆ·?Í>„?‰õúûål‘~¹šÌ¾ìî²ÇñK½jayýÆW“w/—ÛÝd9Í—ÏŸ_/HPêKÛÿáÕýd³ûÝfµ_¿Þ¤©‚¹¾@ûüKòµmg²œuÆs Úùf¿[Ì—içóô¡¸È/4m/ ÷¯'oç·“Ýj#)¬v†Æz4›ã•âÓ—ˆÞƒ×“íÁøÇí©x«#^»|‡én2_‡žàSɰ’ï;rã;j!ɵéÓl¬S¤¶b¾ /%ròC‡3ÛßϳïÒí~±ÛfD–4ï*LÓYG.ÑÑkü|0×w<_jñZ§¸~±ÓŸì¦wVY¯W«EñõK<ÅØìïöËWéV\ Çm5Þë|¹ºý`Ø_­Þàzs$/^û¹ìä`1Ùnû›ÕÃ6Ý·—òÍŽ~õg°£ƒ?¾:ÁW«ýf*ô¼™ø×r·Y-~.»:L¯÷·ýM:y³^Í—Ç d¼=¼þ³@û‡Áp5}3¹^¤ÐC…‚\Ö‡LÚùÂ…ŠÞoÖéòßíçÓ7‹÷DZ³x±£ß|º =N©||ÒM#ß¼ýYhNÔÁ—/ÛNù–KÛÕF`®jøö‹™u'Mºaºnæë.íÌèʬ¹az3ÞVxâéûšê}œ.˜¯ÞowéýçÛ9NÚa¡›Éb›¾È ÕÑ»]ºÚÁá÷¼{ÈÒ"È…Ç“·ýɘÜÌ¡hkö`›‰Ÿ¡qh]IÑèwß¿fOLR×C×s»IÏu£¤ÛõG¾3 x(ðßS ½*B7;ÄʈϞ“´•gv¤Bf¾Ùî^ÏïÓ?A[= çÛõbò>eà~Q¦ÔËYºÜÍoæ‚Q5æšTðhϼ™Á¿}¾Væýs’’_Mþ¼ÚüQy6ëAþ§8¿ñ@øìÏÚ)ðÕ|Ùü|ýñ¢[a‘%¾^ ¬¦Ám¢}‘ñcÕâþaðÍ5ôø>zûÝ 4›®–KHpÉ…Š,ØÝf/Yì°5ÙK`_ †/•Ÿ,$w2ÛÊìùñD\ïËOk²ÿ0(øW¶¯pð(îU~ܪ‹ ÞlX9û¾æåvë)I®+ü%»Én¿•æ“øcútóÉmZ|µ°A5ú½žlnÓ ±äøj2_Öm;u›©ðz3¿Ó‘O&oRm8üi¾»ËÈò÷&ÿ8YÌg’Êk6¹Iì‰kOyG*|xV… ÿÓ|¶»«<'eAvpž•Nŧ_Ð_‘¼…Pkg¢NqÒànµM—¼žl„|:¼‚}; üY¼ §à³ÜÃgëÕz¿.ѱô È…M;üîëWúƒãEúNöWëÉ4_§Ÿ¿Æþ7›Á"4¬(Ÿx/ܳÍ~ùÍFÞVôZ¹ ›ÏÒçàf Ê«ÝjÝßïvM0ƒeŸÍ—7+zÕÝêöv‘>Kk~±œrÇ"º¾~÷|§vèù6l¦wà ÈømsÐçM›‹d6×d›jWy™7¸ÿ^BÒϪ[æ›-RÄqª»cÅXWÜaÿ WLvÃPlqµì Ôá¡8,p¸Î4–_NÞ¯öðÓ(²ìÓõÃý4M•[;¿ÌE½~R7%þ%a¿‘‚ ôFai….©¿÷ÜçÎäß½“@¿\ÎÀ‹ÆýÞ ëÝd0ìÊœ®[" ž?O¾Ð;ê…n<Š"ñ? |`8~JMƒê_èºÁQ É<àà8®ãtM8ŒÜÐ÷û^Ð ¼~˜ôÝno¸Ahé@%àát}à ƒî¨çC/ÃWFc¡ ù¾Óíó‚,j/šØÁ{F•±LÙQ·ïŒGÝМá»D½`\Cƒ\õËÉuZ8 –±‡*f•5^ͧ»ý&Åé} áwP|æz/´Ó2[dëä¬ÇI«Åþ~9œì&ÅóQиäÚšDÍ ¨›ð Ȏ²|±|b>ýN‚Åo\/ùâ…ü“*ò¹ƒí¡¶~p‹o]½ÙŸÓtJ‰B´JšO«Ìiç ,:N$( KT‚%IüZ.4z·žHK+––«ÊžÃv 3ÂÀ‘fL<)3FÓT£½¸:bSŠÔx•.D¼±¢_K2HvPJö1dÑæãwU_®¡Ñúé§îçî?}Þù ìõy' ’ú§ên”>I‘ìX¼^­sÆnú˜åK? ^.§‹ý¬\ݾz˜Ã/_ÚµÒŤÍƒWwy}½‚V[~Zc’+? Ìœ>ÿݸüŠ~LJ¸ß¥¸$w›÷G\~ãM!2¬hS§j‚ªQDPU0÷!üúZ¸Ô¿]åãL-5PZfT®â»ýõuºQJN3N®ït¯Ûq|7êà–‹;]üÏI\üˉâN…kêV΀âÞehãÊŒÎnÄõWÐr¯G‘›q“®¡·ºGQºÈM¾Ì@%Á[|\Þ¦!á±¢Ž”mò¬HÆ9&g€‹Òízò¢ÄuÙtQ6¬\¿*ñ &Çýd¹Ÿ,®v0þ7sx’žOË”’„Ì$.ò$tøø%”b,¯‰×*¶ê°¾/w‹t•K— Ó€@Éé¤H“c ‰ãÛ‰Ó°:Ež|ù6Ò _Ý!NïÆ`n¾«Ü:€û`³: Df¿f÷¶ø½ ôµUIuØ2×ëâ`4è†ýqö»Ý`Äq]]ÌVÔ`Õ,1¶¤kÆêÑH|cèE±éÀú¾|) 0V})8å% Þ*ö1_‹/ùÒVÂñ/9§¼äžð<®-x¡BòQ¯ÍK•«A0‰äÒõ&} }­,) Y¸ÊDøp/î ë®™s+Іž€6‰ÜcXgãø—’eɿǾ ðŽ}Ižûc_žò¥SŽ×H’Ü*–*ê0˜ªd,d\&/Áj¿Äý-dc.+3AU iHö«/%ùUûi'©ÿÎqUÅsYÁ¬$±ªƒøxùB“¯ÕÕ'M¥Ãº$-}(? ÔiU–KÉÐÑ?´2¦ŽZÎ$ò…w®Fië~s£OwÁY\ôg kXÞjÍwMö´´¬~Æìi½¶¼üZ®m5Ͳµµ­b-uÒ¨xGƒ# [ûtpd±‘©t×?Ÿ©ô‚"{å<š WÉq‚ôH´zÔ(IuI´Ü¯6kx„ Ì-~IEF2ÓªbeÉÎ%ɾPŽIfŸf↠ÃWT$T8ŸC&C&Sí^©9<²Cî8C&¥ÚŠ8*dâWÉlj.î)FN™$°É=Çãž—øŽ3è!¬WÔBK;<*`Û&œZ±39I9…‹HØB&¹YÔ,Œ™X¯\ê—Uxª? ­AÏ*Âw\ÌúyÇó¨PAÉh˨󈘌8µ;O]ä?ßhL׉ƒ n I¢>v4¦&ŽŠúŸ88vÓ?»¼Èë¸aÒ “nÇK"‹ñýn'¾P µS ¹6Z K¤i‹é+Züv“Þ¤›M:“wAî.:øÜ½nåTËo|x3«¸½„£,ŸV @ýl âùö¶âÞv.ÿšD§˜r‡l_sºò·sd›Î¶dÝÈX[$„ë¸?t#¤²Ô\Çj?ïÒÅ Œc’´*/)ä\gì’}íF–î:¿|¡r®_|9¿ÞL6ïQA<‹,OéÑ{X¡FéÅ0}+²æ¶/‘%µ¹AêÞó¿|¡ó·/z/PZ'kZ¶/ i®°âSçù»©Î ûeÜ 9™l*’kfi[Š£ ‡çýú€—Šû:Aä;q×{ú9Hg‚$×zzMq‰NœÀÞ'eñ%DjéWó…ÚÑjÝ÷ëü±Ì‹QHÇ®Òæû5rT³ôÛÜúÅ×w)ª:e¦}çObÛDŽeg¾ììË Ò;«›ŽÌè,Wø¥ÌJØv¶ûµðbvv«Î2…dµ(ÃÞM;3é™ê¼Esçoî&»ÎÝdÛ¹NQï‘É#ñ"þN<ýÙWH&X=“ì³ÎMŠÔáMúwÏ;\í;÷{”ºÏ€=ÙÌ:ÈäÛt¦{ȳ厀|›îvÈ{PµÖ{‰¹øŒøÆTÀB$¶«Í,݈o‘Ä£p×@†áJ|µó0ßÞ‰GÈUsÚiǶs³ÚtÖ*3¾óË¿ù·¿ümucT Á?»C:÷a{2¶B¥@öG¯³+ÀªúX¹ÿs•-;ªB0ŒbDCQ{DÉA¥¡7ì#ƒ(wŸ½X„’z±Ûdz5!rÐS_|´øí‹õõ ÿ¹ŸàäO&;ü,þƒ# &X¾Rƒ W²3À_ ÒzyÆÔZRÌ–:DÙrg‚|vl©‚€BQM­KÝ\]µâÓÏe^qa­š˜LégŽrº\bþ۸ñ¸º^Ô؆ï7ŒJõ-ÒFÐq#"%z*;CpúÏ \Õ "¨Í.a™èMo®‚¦¹È ¢NÜ ÌDX»d÷(Š+÷wv6ôVèÃv¦`0­zû«°ä'Q@ OcSš5~‘ÃÓ6¿!Þ*zõ7„ïP ºûî¥íë òe½™¾þPM€<9™èÈxÜNdqÕ­ ü3:X¡¨]óQá9MrÄ#Ú•®È’„¥ÕMQ4‰mÃÁA…Y¡‚®…¹‚—h1Yo …ü.àÍ.dg×­Z7½¢¨m)ó[q5*¿‡âÛÇ òyž[ØTüPKßÔÈ]Î-n[vœ5;eQÅ(– ²ï¹–sš_Ô‡ƒÖ#"Õ;G¡_]²°™Åå$„´Ù*ñË:l”˜W¾tŒšxCË‚oJ-ßh9€rI$Ÿ=Ê•v™E¥Â'2ÅG¥®É¼—qÀ$¯+`ùÓ @ì×n¶vk¡SÛ0¡ÝÀ¨j×dë“ñµk!lê»I)9^nû OnH®þ•enY«=¨¬T³×^®æì_8rÇÓ.g¢oB¥j\Ý¡?WSÞIŒ”í’]:å+\áø{dßþˆøëd!SžTìÒkÕ«û%~5UW¬Aé”Âô/Õë¯âqiêwŸÃ V ~àµ4ýôˆÀ«»rF‘_rgZ†œ„ þ‹) WÔÁZ—³5ßÀ©Ü¶€Z ¢JG@#‘ÚÂáPÈ%È <Oú/òÅ ¥N ý¶Rw§X^ý§Ÿ\ñ ¬–ÇðJQî¨ïæÇ,L/+õûÈ Eªüf™·À–ðଘü’ë>ƨéÀùF&ýgˆè¶2“,Òu"O¡ò7"ÃEÂ-Qñ¼5øO>ƨEóÍÜs¤ÔƧä„.ê}ÚµPâ”h²ÀÛøŠ z‹Õ…k­…±"j¤¤±:T¤2†.”Qäd¹Lke4;®u°`Ç‹¬>E Q‹2 !ÛäͰf¢*©·œßO0ñ©~&×"µ\ÅçpäÖ;urÅ]}E“´£åÌSë@ÑÅÌ2Ôì„?RHU;IF“ÉÞJ!É“Œ#ha3ó!Åèv"üUÂJçÃ%ñ—ni4_¾¹ 'Aoy²™eåq©r…'= }=Km›˜ªÎ$Thú–»ë‡ëŒ{ Gá€Z]øy+D:íPŠ…™U/îø.,Œ“Œuãâã8õñR§rføÕ(C:(óê»p>„åóÍZL×ܾJweÁ,M˜ì ü~ž¢IîôîýçÉbÑ‘t«OPÆá‘§®âF,;¸KëBñ ý D‰˜×÷Ì좒*¶mqa²¥äxN_mnçYçëWß\ +¬t¨0¹„T  N´®ôHŸvIN˜½ˆQ±dIF½˜B}ºCŽ0¹ŽØ[åï,ÊýŠÌ-”‹¢‹ ¨z8õ³Ù‚B´´_&Ly½¢ôÉÉÞŽp(²ÃšÃ›_¥÷p»µ®†©¶"oRnšOP©–r'ôzìPë¼Fûã—Ó•µÝf;jÔ;\`Ø µèqûëTÇd`çóýÍÁl½Á du‡ë+> Ë´õC8NÐÁ(Õ˜žQWiLgM²çLË⾕¢¦Rή:*Bª|x”Ì%=oÙ¦K¤^q9¹Xù"È‘øeµ$EåKGª&jÕ`2ªèײ„å¨>‡Î Ûº=´Fiå(ÁÐ]U†îfTPqY4 qîaO›¢â­î·® «b*4šë&Ƭ©qD$•ÕjØò Ÿ‘ªa++µ4í$ËØø‹B½ÝýæŸ|üç#>RàCSà‹ß¾»_dã~ý™ó¼ûY']¢—>ºWþú³ï_ŸÅŸýö7¿øâ¯‡ß ^ÿã·£Ž<®o¿ïùrÐùìÙ‹½5ZŽx1|=ì|ûåËW¯;XãÅ‹Ñןu>»ÛíÖÿâÅÃÃÃó‰xêùtu/Ü¢uÿ )wïÅ gxáùl7û ŸQ«¿…ÛFƒ¿ÕAl)rzÓÝümZ˜hR¼ô2 ¦7…ËN½»X¬Ò™ºä=(ó|ìC¸¶Å…ßG ˜Eúåj2ûv²Ã CñwÒ‘¯U®Âòú¯&ï^.·»ÉrZlq™AU®÷’ŸÈôêÒ qðú‹ØçÊ ì¢FQÈ|Ž ÃO—>ÉÄ0^=d \î&  µjÓséèý0x=Ù¾ŒŸm~Áš“´§±ouÔàü…KÜ?SŒ¨yóŸÊA.2Õ‘Œ‘)"®*¹¶ìèù`xÃ<Ê©­Cx«Ù~QhN™oœYKÇtÃî*LÓY§Ô”ü烹–¸MýVš÷]¿ØéOvÓ;Ù¨#4Ó"Ù?Øf! 12J%ŒWœÐÓâf1Ÿî(¯¶a×3äÕ"¢©„Zågqοœù´¯ý,¶xÚŒÞfön4¾/‘©¦|uܵ¤·u1‡KtvÁ¸êŸË®ÊÐe!â8ÄUà³ðúÏm\Ϋé›Éõ"…¢º†[ •Ó ùÂ…²±˜óïöóé›ÅûãvU¼ØÑo>݆§uHNl.f6bùf¥÷ðÛѤ›Ù¤š5}0,Ò)^-1énu¤e½µmf؃ßM©°†9›z@Uá‰?ˆYU%X[È8Ô$ÎJ‹õ<_X>:z·+O¿ÈÔå{ÜÎÛbùüxò#J…&4G‹aq±bü`f›Ê'pKi½Ií’3[Y_çÀË‹V±HC¥FƃR²§\ ³¤&µÐË]z/DßÁ3 >,S§©g ÏÉ,sñà¯2–ÉZcJsMw8N´ E"NíóµÒAŸ7Ð’ÊOU†ùz•š<­ÑñòÃà›kDöáêíw+ ?®Ðgº“œ¨‡E%¢Ÿ¿€Håç©4x½™ÙGÆq ¾/?­ o [Ü­ÃñÐŽ Á +gß×ÜÜn½"%Éuq£å¹ ‰õÔ7àÉÃäMºTGðOóÝ]F–¿7ÁøGd›aºló&çñPÏ!a¼rUøPžÞ77ߢª1:ˆ¡C-ÉáP8¡xS~Œòäß$LŠ¿¨àÂ7*`ãAÞ)i=¸[mÓ¥. !ux`Ÿõ&!žAf\¯ž­WëýºDÉÒs«òýtøÝׯô÷Æ‹ôÝêâ+1ŸW|œ^k¦gE=K—B¹|Ö”¨zø€Óõl²œ=»­Ôehä2o>KŸƒ­5D¯v«u¿Û5Þ}6_Þ4¬z,b9ëëwÏwj.Ùóm*²jnæiuÔØÙô©Ò&Ñ#bdÎÒd›Åf¾i%²JN¹ô³*€÷ÍâÐÔ}ŸŠwŠBE0wÑ]¸J²›„€b›5–ÊŽ`®ÆmÊ($Á(*üWü~#q¾6VÏnû<ò.< ØðûÏÕªl>ÿݸüJé|”P’ÀYó|K2A¾RÏ*-‘Vö/t#_5&RJÕg[VW˜6ûI6ªÞª´®ŠLÁPæÌÉì[ß 4"Å\6( –Álu««¸uÙ¾¼Ÿlv2B›_n‘&ÉýÔ0ÃÄ®æKá(î \­:“¨Läâ㚃?D~Uí(9£”˜È'K Ý.ÆQú‘ƒÌùn7‰zÁ¸Ò—G¼£ˆWqsÕ<¨Éívq…±³B¡~ŽD•Òá)¬'Ç—ª} ÓâíüvÇnÔâ>‹ç‹xö¾|RP°`A>V¥a'¨’¯é"†ZZèreòå-´Ñk^Ý!!N Ávî|W¥žÊî1Ç.ûsN…÷µŽ‡V©tØ(ÒGNÅN ?„¢tã~·Rº ’gT×`Õ¬^ƒ9ÂêaW~ÃSDš¿Q,D*);ò%tF8þ%ï”—üS^ Ny)<å¥è”—/Iòä”/õNy©ÊKƒS^žòÒè”—Æ'¼rž¢SÎS¤xÏ"*'7R¼gy©¢N!Sn+¢¥¡”õŒÀCÕUEÞ뻥¼Sòª²”¼Å´+z²‘:î|Q­Eg’{åeä*Vup—/"ùZ]åË¥dÞtÇÏãóN|†¶‹Gé\5ÚKëzW2tÃ¥MÏÀ“KÐZW¾ 0­ê]UXÊÄ”«Ú¼vX‚ØãÕ£À®(,PTr]M/ªð¾\ö±8-õ¼9Ák®ã×í6ЮÝç»øÈ¼fH┇T€jc4 ia´²ØKÌÅgÄ7 "±]mféFVœ=I…ù/˜þóN7÷:½¤cTܸÌ`­ðŒµ¤š³ ðµ¥ürgX4“"Èq>CÀ·™%ǘ«86rqTË7Ú' A.ïå³Gš­v=(ßcíéø­Û{x †¥è^X¹£ð¸Lñï>Ç U*ÈÊáF™¤ï¾¹É®ÌD~sÝa%TvN¡IOnSër æÛ8u„ôA”Á BKòláÙ€O¢LÉj±¦|Z/–ûz]¾^ÌÕ¦4Q±üáù ¬ßÑa¼é•¢ìŸÄ%5Oü…4³ƒ>r‚$’¦ÊrBä¶ä½ûPÀä+¨0¡™ÇÎ UÎŒñåd¿œÞ¡”[VZ€Mˆsž±eÛQåE<[Â8(߉EaÄÀéáæè'A/*§©7Û£ÐKÑˆá ¿ûòû×£wðˆ.àÑûÛï!€6p”mþ®t ˆoT"éq¢-?nW‹´âN–Øàcúl½ZÂrÐ?Š-ä·‹‹¨û¹?Êúé'TR"ñ²«Ä„ø3"sä‹¿z=|ùÍÙ—6C ¸$„’}ƒù€Í–ÐmŸàX˜¾‘K‹Kãí*zäD¡žèذµDÌ ÔjNû„®9õ}Âòvq„ǯvåé]E#½áݸ6t3ßÔWû{¢¡T§Ê Ù‡1®¦öaâè‹ÃCmË Á=â.²_1’yl–ÝaÙÎ1 %zpHÙÜ#Õ¨î*ÛDz:î[ÔaÏ CA­ì(f«W¸1{´²/’:¶¤a0ý¹mHbÉ‚E†Ò9Ãò°TZ¥©-8Òz,[‚P5p”ÏŠnÍ9Ö#¼¡Vï|~Ø´õ¨3tíÖ£ÓâêÊØG¯-ª†°­­ŸÖ‘–OëØF˧EPkHú¢2¨ùéÚ†2,Þ™è²s¼ÅÛþðË`3w[1Ne¥‹3wÑ"lVº9$ÀOoêV£&8•k7÷(mIÞì.I‰Âöh Þ¬˜ÊJàUMB…Íå˜e?Ò~$×í"ø‡Ia~M3ðN[56_¾]u¯=î‚sYª©D‡-t^¬EÒÔ1Ú@nø¢&ŒA% ôSM%Û½ŸS(‚jáú¢«AŒÀ B––0 Þ$ÏîªâýŸBM'®æx¶8)4rù¶}0m;-÷9—°?îû@ ÚGŸ_áª\}>ín·ŠÓ-ßé\[yT½ÌešÍqàÖZ™ƒ^u°œH?QJÙY‡”[œk’?iq˜_$µDJüªäÊ×AÑkö+W·N¨…€‡EV"rÈÏï({5øª1ùL&¥Œ<_"Xò¥{†–dΣs&=1îÀ@6¦’ç¶Ü0ª.YØÀÚuK[ `‡’T“'ì˜;+Mšlô‘@d2±úÒ@¨»}ôI:âiËm’¯ÝâÜÖÃÑg¨ ܬɴ?*97åSòÇãyŒšæ©ÈÏ’Þ¢<™XÉ« Õ^¬ƒ=pIU EÛ4—æ\ jš¤{®²†º0+=šv]i´æsŒ·ŠìLS[ÞýTÔÅB ¾E½-‚×¥H\vÒ–•¹7¹ 65{© ¥À÷+1ÌŒbTóoäïï— ƒ)ˆ ̆S8õì®ÚN)îA›?L¶ª!?« CŸ¼Vã•’’„¤Œ¨ØÖÿõQxù²kWaBÞ›–'«hâ Q̨;Dûš‘È`„ªÝ^8QitžTÏñJ•T­iÓÜ,†D§rzñùCÍWC|²úß´ÜGSë—œlyüý°‘^ÐfE/™Û¿d49LhÀ_àÛÎhÀã…ë@Š„2rµÇÒh¥^G%$³ùÕ×[ÎVÈhqHBÄ_´:Ö2{SM ­1±§­é‡¸EGT¸F¾ßñ»É#øã)¹WRMsoñÊcªŠ1ˆWℲx’”¸8°çôFC4 ð’­CºÝ NŸOúcnâ§îŒä,˸‹?™NË…°ç9ÚÝš¹VáÊò UÛJ²z&@¹*£ؼ¸œ\Œš“ ²ÖˆDd‰ÏêbTjá•Ê¥$_¡íÌÂñÒ¡–¯ioÚ%EF þըóhæ©ëÅãÀvwäú}w€6ýþ8¨ ÃÈ@ÖO£KS›§k?ì «±U¦ÔÃ0O æÜ é¼í¯ÉE¶8W«}¨¬tbœëñ ä™Hî-ç÷¢-qý$=®õ›¾„NFÔFœÃy{™ñ1þî@AÞcï)Aø#E˜Tµów”`Bø5pPSCG3ÓЄ»ÀYÇŸVlœ*ó2ü_¦ß¢2Iü¥Û)rj~EåZ˜=ª³6:êióɬájöï·g_I »ÖÔýÊJ§5­•<¯6ЛÄ帘Owe™%QxúËà¼2‰.!Üû‘°]¨a(ÂZ,¹WÔEò¨Ž6@#ŠÛùâÞé"³Çó:X°ã_Þÿ0Зi…ù8²hWueŠ2£•ì'–,liq9yPhÙ¯1í(TEZrÓA;æ*8‚‚58º3óZ@ãÑhŒôRÓÉȯù´(L3œ£òÓ–SWÃUIr­Mb|è¶›Gϲµ}$¯ÉnÖ¥£ ¾_5TXqJ « ×A9Ú˜¡‹…|••.îZ™.&Ûm³zØR&áÓ_&§Y߬wèë´}•îʧ\hõ‡Äïçéf²™Þ½ÿ¼3Y,:’•\Mõ¼>iÑ ¤^™%JëÂEúAˆê ¯ïÈé@m” Û¶™1Ù*±[½]h 3ÙïV_¥ ô‚¢é÷f÷ryS*„ D_ sâ½&¿Ÿn­„ª’B´xrƒ°±|P¯&&S[[š4fˆäA±Ñ*¸]ÌÐ.H¹G:œíÅBTúœdÇ:[Pèî­tÑê§¼^Q¶ålÔŽrŽãÃŒÝæÊ˯Òûk45².熎HR‹ÄV!ÙcIJ(½{+Ô:¯ÑùüåtµdïpJ±jÑ£6ØuÂê†ÔW`¶Ñ÷\(oq}ÅGá™Ö¤0ÁqsQ:î;ØÁì—'M‹ŽöÖ>·öG,Y|ÅÓ(¾|/dg_â—É×’oI¾tŒÊw#ên%¨Uƒéñ4=Œkè ÝZ„¢eû(éw»"k„3R\Ï ÆÑ0pü~$¨ûëF£`4¨\`ÙÓ­®»®ŒˆÌTˆûë&•ÅâY8âŒTT·òŸcß‚²••.N Ä  D_Íåm‰#$Ü/Õ‰—K±eÛ¯Òå¾ ‘WퟫˆÓÚV½Ã”±(»£îºÍX8¡1Œf0¬g5ÄWï²Þóªá™l–ç4k mo/éDq(c ^žûùað]Îo„\< ;"æ–Ô:´fgMç¾Eˆ% ÛX“bô-R@¯~œŽ¹Cl”ªÁc¼A*¡#=È’éÇf¦Ï6Æõ|d3&žã c1]P·&ÆÑ×M‹UCÕ,çÛspE6ÓR^Ÿy3ú••ZJùbŸ}ñb½˜ow¿ùÅ'ÿùHøHøHO>yñ¢ó×ÿúW߿ǿú×ý‹Ÿ~ñ)ó Õ3êö=ó·ÆÈþÆ#T¾øUg=¹‚Os¥†•=Ÿv~õ¢óëÞùt?ìÞíôŸnÓ5Òx0©¿Ú/gÛïDû±_w>ËäWĨÜ$ÂÏÏþH²P¯ (à»Éò6•OËVÈÅß"˨ô[' âÒëâú·ÐR^*üd4^ùù„âÿš2±2w§SÆïÇsáß,â^¢Œ$ÐqJO”¨ãrNj†µgŠóÓ¤#Ï÷2LІB8i@®8á†ÃÏ HØ5a ‚x±[ÃæÀ-N„h±ƒ2•úCE”1åQZ5N×ÎË a“{vœ¹›ì¢Ácã&c”Q 2ìrŒé™x"Äáâ2ä1ˆº Ÿï¢&…Úâ~ºëýb5™1ö7‰ð]ÇGᅩ%~¶žt×÷£ÒëUc S—$ÉàS¥±X°<}G%–IOxq#ŽDÒóÌHJ¾MB„^Ã>Ž0œÍ1ƒéN–KA7ñ³ïž$°]Xp%U·1ÁïÅ6Ϧƒ@^MÉÓwQ]KŽˆn”ÀÁØÜíöùé°«s–xHû`° Š™J¯W7H‰N'@{ÚȯP‰¼Q=u,0m Á«¯ÐÅm ËÍóx<‹üZPd*N ŵn{ܦA ïÃÕ(…S ÜÚCÅ«ÅE½R ÐeÂÌLâë5à{·Úî&ë9ƒ Æ&Y¸mI„òUW‡®‚.æ{Åëz²£+”€~Ý웕Ýõ°]oVSÁò\™ä‡AFgj{½Ø³uLغ˜ZlÇ¢+¹¡/wWIàÅI$´pÊÐåžpDýMŠRﱸokŒz@}¡4@÷®+EfF¤On®Û&+¹trÏØ[ÅÉj² %YÃÉu"IÄ¢=`þ·ST57,ÖšìM›ÓÁqÃb£³Gñ½ïxØfm\uEž ¡`ùÀ õ$q üÖ¬ü&a·Á³1ô¡ % Gè@¦®Ðua -#¨?S¾;ÂDéÿâÎÍò&Žð„Y!^0q¬Á~tªsÄtµáÝ7Žð„u£7RBÍ…ýmdMŸÝÄèv-Ñ…6ýánm"ì*¢èi°§\g(éãŽpjj'FÒ‡qU…BXÀ¢2é ahsOú±ðb81&&ú`ÆF€‹Îá‚Ø—4¾òÐÌwsÜvŒ“ãÄʳéäÀ ™€‡ëfâáä8~ va¨›P‡‚TI˜¼1¶§çGC$˜¼´pè.'œ+VùŠ<ÇtÃú‘ð Öý]BA”‚Þ8Hæ#¤|båóSÒܰȀòù4ÊB¦*ö` yx]8ÜKûZ¬>÷F¹/¸ð–b>Ri‘ªº*‘69tÜc7Lbˆ€n/ñºÃ¾ß|?ÿv²ß¦,B$EÕ`J Kˆe#’ø-âK”®¸Ž[åØÓõúdÿ¥Ž8FC" |ìá8p%fÚ Á…©¥ "mDÌžÅU WÓ¥c+˜ÞæôGsr5]tÂÃ]æˆü좨)m‚Gu1|ÀØÄ]ç„Ð\Š‹,Ùì›ö¼¼RH‡è÷Ñí÷ÃÞÀ,ù:}·ûÝf>»z%B…Ïù[ìG± _x-qÂê2倯@6®ø jÛ ×žØTí¬"?‘U*Hµ×k†Ø‘T¡g”v§´ÅN)ÊÈï“û[è·wk¾ir¯®¾]á®@2òâ±Î¦ðgà𷦵³„§àÂÃÎÉÅñcíê+#‚šõvˆ0ö–ÐpL«Ä…ø0o˜µ@4wcÜ;UÒ¯¦oÿà?  …£ÕAÙ¦øfŠxLs}ÅVàïKøcøÙhøoæ ŽÉ«À7+Ffðñ‡DAü3ÃhàçË9+ćD%Á¸J|]â|;ô8þ××Ç $ôӻɆÃûh8 ÞljcÀi­­¨2ÛÀú—”‡úFÁÎ[2 \‚¨¡u’W¢:3 ôÕtu¿^¤ï®«åíÕlµÇØz"ð.€þ‰ÑNµò¢(¤ØEŠþ=øu)±“¡r!Xˆ9!÷G‰Æ‚¸·„ð̰¸A–ÐîÉ·ÂC‡BBKÐ>\ÔVœi ¸YDÓ)è‡j  ‘Ð_é‘xUF­–ÿÐHàaA°¹†M÷„ » ãYÑ]¸Ê(®¹$„ E}d¬È;`ØÀø…''?yüJm‹G wïþ,—/Wø;”º àCEøŠ\)ÞÙŸƒïÙ°‡„âØcû¸áÈ"!ô \þð= 險â+/‰øÓÕ£ß ¼›¥E–9ê™…ò³ÕnzµÝ_?2÷Xð²ôÀ ÊÚ5Pì/}¼+(uÇ€ÀíõýÛ§¦¾O)nWLU²¿ùàÞ¦÷ÌŒJ«à±²ŽÕ½ëþ¾¸ŒÀ?=åQýBH -µR~3}j¶A Ž^ß»&Êoö— ¼ò‘xþîl¦LT¤Ò“MÀ3¬ômFÆ,_ûÍjŠ*À+¿Žø'?°˜ïBò¼RòÀsjÚ¨hVÂ{Y‚O…ðÊe†ÝeWYï &‡6êÈvàiÓ0Ø$%ŠÌ\v,…é[nº`­š=€çÀ~¶AzÉòVµþnýôª—Õ”TxÞªÖß­Ÿþ¼f‘Ñ2ìH­ÊH+Ûµ™=ØyçÕnÚÏk–S^k6ÍÀo§Èô;Ý ? Ë#ÇbùHk6à/zÒ‹†2t ßl&ë''=í7F ø÷`‹x¤-iÕÆÀ7ïy—ÔY¸…‚$×kÝÆýÜR¤ÿ2ÒÊM3ð»KÐçQêA˜‘VnLÀoŸ\%ö˜^+7à/A? }–Ú"nvë§§¼hB±Vn ”ß\€¬¤z¤jÛ(¿¹µ2!¥M¬ý•&ÊoŸÞcFÛ°(g³RþéyÞÏ‚e½efàg“íþÉ)fÝÔEbª øÇðX5z©Hàmýì""$Yd…mlý †§V‰=* Çí"ÞÂ5[Èš_UoÓçg[@lš¸`‘ h£|úôw”ï’ÚAlSçAù§w}й[±M›Ÿ-7÷íúpdµ¤%Þ èm ýlóôâÆE—AŠémú¼€ýö©e%ÊõHàmú¼þéÕÔ[S”·éóø§'=^@®¢EXn/Á§±Èª²îJòšêkà{ð‘ŽâÙö"´Ò[Ù×ÖˆøKp$ä‰íkkÄüÓß±´“]_$Ëaì;ÖjŒxˆA¢²¯ð—àã¦ómúÚ1 >îÊkkÄüÓû*»´°ÑÖˆ xÞyµGÀÝ•?•"þj†eƒ%Ø×öˆ|Þ‘µÃo?²´^Ù×öˆx^|á Ðû-éµEb„žü‚±>U†®EÚiþ"‚#tþA_Û#&à™îJQ‹t³þ‚Tjw‹Ö é¨ü²\³»KÐo¸^[$Ú_Bx„06ÊóÂ#ç¨Fm7«J¿»€èjE(ål`Uéw› ˆŽ4pU¥ð ßД·êô?~€ðˆ#úkeᛦ¢é ²¹uäYàüø<VÇm€Þ¦ϧ“ûÉ»'÷Ñ>454ËËùì2 '´M7žo/zÒžÅH9 í¼dèmÊñöH‡–f›r¼ýewvàéðÚÀ¦#Oñ"âá4émºñvzÒž†Þ¦o/# N t$2 œËp“„סš•„íe8¼³ÉåˆøXëh0Êioýö"ÂùYå ðÚïjžYytŽ_?& ÖÆÚïjþéUûÌ7X¡¼Ö-MÀó\—gð?y \£5ËfØ/XÌÕ%ÕóktÆö"bù¤=8VW”ö§(“}Ì”W”ø§å“RmÛÿô¤ÏÌô’°qºÊƒc ýEÄòÉf¢c»PmLÀóbùçðûÑmXÄ ìá-¦2D®RL„¿€b;Òùát•n`†Z;ËýJ…51JÕÊ5— 'ó†̈±±ü%DÃ1€­ž‡€æê-€z•ò(à•ÓÉÄóïŸ^¥ÌævVn(år2Ãþôç•ôÚ8]år²Ï‰&ŸãŠòÉÂè5v–¿„bv*UÎÑM! ”gFÂÏBx2·ó)l„ß]_@dŠÚ¼EÊ_Fœ2£Ð¬×üÓSÞ£…îÄiby^ü<5ÉnD\QŽU—¿„8¸‡YZðVeþ"âà ”·*ó—o¢¼M›—nЌ𩱎BA1ŽMŸÿñ"BR ŒcÓ缌°-émúü—ÓI‘ªÞqÐÕ|Ï .¤“"iQ96ÅþÇÙeô^¡ï+›fÿãEwÈ6¢¦7Zxç2j5é“ksÓÿà9–øY4{—4Ä12ÏJxVÈsÀŽ!¼Ô]…FûvØ/  $ ¼M±ÿñ2º@’’Òµ9é¼»„X,YÔŽ™E6¶ðœãz«„n¼‚Ypvà9Ž39LL8VŽJH·& aî(y\mj=˜æšÊ‘ÝzŒÛµÈnȳp Ý_ Ã&Z@Ïqúx²¢¬À_D`Š–”V­þº@Ò)תÐ_FHZÚX•ùËÐåISʵêò—ÑG‘T)]«.¿½ˆ¨©Ë»V]~{}iÒ[µy@©r³G,W,3@ržKªKZߘûnþéýôH$£43Ìá¶ 7,íôÃ0+ð@y²^ 3ï­Àó"$çÐç}Z%ö¬úüeH¨~xŽžÜÔšúñ"$d÷MLH°sͰ<5¢Õu"Í6DËÙ æe¥»É|É2¿1”E€1^ÍF¬\=óÀ,/H0R+ŽIöÑ®{hÞSͤ—HÌ—«û9«Éx(f§ «%îDÔ`nì6©ÀŸN0g3îK9ýÖ4Ä_ÉЦîtÝDz;ƒ$ø`&üä¸;'ÒVUíïæÛ¿0¢ƒç𷊬>JOЮI/@?噓0ÖG*ǺÕuôéf³â̵> áiý,ÒUˤïÖ«eºÜqŽ”Å=³t®¢îuÝHú `¤Ü̯m«æMX¯¸7Á¼«æKË.ïC:©^w¼n¢ÿÍl¾å´ Å´&9ŽÞ4Ý£’ÑêDS–ªÌwdÓËVt×k#<ָǤPLJäkÞ$Møf$ 5ˆS¤]RÏ?Í—³ÕÃx3¹O;¿î|öÓO¡¢ÅçŸÆ‹©—q”‘®œjªûe7¢½ÀøñÓç˜H‰• QX3ÂvŽsÉ^Žn–m‚œ·_JÜB^²€'›ïb“•~ÝpÔo'÷÷œ :ê-L]í„÷hQkõÚû(ïbr#‹ôADjw±Ž³4‚¿ßn¹,i,)ë"¯Qq]å´j³ÌûYHßeퟴib³Qp›®îÓÝfΙ ©8߉xð{1é‚Ó-³›DÎíþþ:]8\æá*§.9ØÑ-³-ÀŸ{ð.GdzÍ<:ÜÒÄû’øœ¢%ïy×ñÈ¡–N¬Ã-fà/ø´'.6Ûwï×éælÇ:‹ƒ\‡ì`äÄ:òÒ° ‹Éz1™¦ìãËä —lâÄfã@â{%2N­[h7ÉŸÅê&_ö³íK:k<#cM¼£¡?ýÙâÓ#Å'–µ °\mî™Eaß{&§¨]é„k•Ò|ƒi¦¿ÿÀ´W|Zú$f•y}.6Âgoù>™î˜Õþõd“îVlá Ý…£;¸dSj'1ëü ös°Wõ¡ÓP³Ú¿ž0M”æÃ=¸ð0å‰Yç_¯æÛíjÉå6Ó‡t( 1»Ò7“÷‹t~{Çß,4ÇG¤ÆàØ‚TÏä7kÍ—ÀûtEnbÖœwLÇ¢d}/ÀŽØ‰ÈžLNbÖš%ì<Ê‹ààç¯ w`3üšW|Þ); KMÙ!ñát é FbÖšÒùõ~Áv|éƒT’ýÍZ³ž·~¶ÖFíºuf³8êQàçw_½€»÷§_|úé~>ؽÛé´Søår×_í—³íwéTü na©I§°` ×7Ú*žt¨gÚ åQÇü60ÒgÉ„"þšø»ôúýö.}Ë@A’ŽTž²“M½Ý…oØC+ÁÊÔ™»túæj3YÞ¦\àÍRß®*ä,g¨Tå!š³Wa_ÝCËœìæ¸pOçЗZf³ѻt™ÖPi™ÃA½`üÕÕ4ÿ{÷ºA—ç&÷É1ªÎPéœ6Lnæ ¶ËÁñ1i®Yþ·à$:*WÆáý ° ÓåÕÕ Ô„éœMt|ñ´f4¬òÝ$Ê8lFXpö@¥IF]´2l†>èº>hlØ?ñ]ì2jɨÜHYYF,P:Ç*¸”ʦ3sg"r4¦3ÒwT#a˜- þ„é] cRÏ)=߸~NÊ­B JXç™Ád1§¼fMÀÞA`‡ui¹]²y²3V¡‰fò ægcEz!Æ›±U91} Œµ®ÐHú³œ\”÷³HïÄäjg¬L­fÒÿy2]]ϹÄ÷BŒ>ã?¤ë¥u·öfð—«³_dûràÈéiÎX‹Vøùg׋xÉH˜èLú§ÆÊÂjÆ`;½Ûsªí•ƒPtl6…å\ÂÐPµp¤<=JtpÈ8\ÔF–“ÆZ›k<ÆÛÕ†­õû¨‰`±QB÷â« jÃ&ðªIµeçT‘—ïØ¦„žåæõºL?›Øºº íê–•#$åQ*4ÃxAÝ,Xû”âŒÓ¬ÄD«`o6WW÷év;ðtóE² פöDzhm¨¬Öì‚XÙs•³¡G)™®*oÀöÀåyIPãEªlž´P,(œ%ò"£NÔ¥L,דVJ ø{àÌÂ, w=™ËcAá6å(pJºÕ7»D Ȧ®'5O øç†ŠË“%R#2—Êõ¤"Ñ> ¡‚Ƥ†Ú÷ "ÛŽ‹"\µ0†ø-?“má˜NC²‘¢­Qàï¤  Z'õ¥ßÖ²+T…p5%±^ÖYBÄìK×m ø{ÑÍSW²ÖE¯%ûY@nóäþ©­2d§RÍ$ÛbÀß®Ñà“Nt×o£Ü­gœ`¶¼Ôœ$âqQHf\¹pٶ؃٠Øç ¢Í6¿j·I·|Å‚éœðHYÔFµ“ð7v}醶ˆÓíŽßM ‡xºQ’ö܉öc àoÇLçpB2È õÀ×^q¹Ü o xbž·7¤±jË}hš@Ý™^#(<]ìMßH+tHĪ?_îRxDÂíÕÕ_&œ‰¨òð€Çü íS´6gÇ`ÍÐçT>Ìc–e€4R—@„V`;mHဦg,Nr» ég‰´FgÅáÓ#Aáà&L'jL½¸ªû^ÒµãÀQ‰ŽÏ8@XŸ0pÇ´ã¥NÅ£>]ô;P@œä?mrÀ«‚möÜ]¡881Ù&ÇUíàì8LQOÂLnŒÊ{n—vžªÞjv$X]“eª.²UyÛùq®j®Ö'`ïB²Pp2ÇÒ´ëË&•Þ¸œþ-êDcÞ2ËR¤’¤z¬µØï 8À®e—¬GuU›µ8øgÀÁ7&[}n-µ¥7Ápy7œëÒöšêžÖbÂ3à1Ï’¨[Z5Q³ãp¿ºç_Óð“°n'¤¯8ÕM­|…)`¶ÖõMoEK…iÉ1´Þj.ZµŸê.m‚ö”/Ò jÖsÉŠ{XmÞl×¼>AäFpD,"¤g»§ÜaNX+¿* µ¥dÝNHŽmw{ʇÜ([z³fÀ­©òüG®Ó@uåÁ€ƒ¤ 8’‹&‹[ôŸ,PÄÉ DQ“è Š&c¾q‘Ê›u˜¥R¼à†DgrÜ”Pí© §ÓkÄãLÍ€E1ZÕñŽ@Hß }åÓv0UñÈd›!Ê vœ4ÅMÊ× {aF0|HG@_y„ztŽÀv›.¯Ñv­r‡œä^\(¢Í½¨$ é¾òª:(ën܈-2N9%Ùµ`,õ³ïRÕH duYâ kÕ•‡à´ÑÀ¼ÒP'  }eõ8(¶l"ÿj¿MïV ”A³ùÈ÷™y‘GI¸å_uPd`ÇÖ‹ô/`ÔÔ‹z Š€ŽzâP ïêy›ð9ûçNÐXÒ©áL Ô™0 €=›³üÝ‘'ºV;̪3ÑíœKC%–\ kਠfÈ!aÖE°Â)øõ a•„Ÿ­%ÅÜŽ!ÙÃS“Q‡ à÷üèìqŽ4Hž' u›yh"n3ôÌBu°g²P‚k<•Ào">rïxQòs!àSZ‘‡¶ ú3³ï2ðy¾/Ì•¡¤Žçj©ÓÌ>ê°ï.T=ñŒ3Œk#H‹ó%’ïø {ëârɹ—b¦¬e ÄLÕñÈœžš¢g:ÀëÍŠ¡å³Íÿº4Á ü7«‡éŠÓKNÑßåªÓÙÂX{öÙî¯Ït†-½Ùìö  ¥Î°Îƒ7lwð« EqçŠ5ÜažòÀ;O9Cr41ŒÐ (?©(ð=èUýgŽ‘ëÍdú&ÝÍYnR„1a{@6HP¨¨0Ò R>"·ˆU\2OÁƒkQoX«H»hà_ Tz¹c‡§8Ž0}IQðã|$´ ÿŸ„]ªê[ÀÛñEYhÀˆ„£Wàv¡fR'‰3ðq­¯ßý yF,ÐÏÑè‰öèz:µËïÖÊ%ØWWèº~9½ Mß¹ÜN1-/Cåmÿ~¾…ëät31Ó˜£éºW/T Fèí¹Ð£)»AÖØ¯ªˆ¾ná ßüÛôv²å“žmê’ŽCOMÀLü æú¼ß/vs”î c÷-«ì8Sw™®$†…GV`† ôWLjÁÍìf»Z¼=ƒ÷b‰×óÔ4Ló>œ ‡.sðPH+þ:ʸÈ3Í1£‘-I¹ ÿ…D]_j8¦y÷çðCb‚ç<ôU sWŒ» Ï6"¼vê\˜—ÅÂC$k×½‡žÎý0â!ÂÜlNr"f΄Hï$€[Z^ A]Ò¢•+˜õOûÀ@®´OMš«Ú§]ªÏÓÕòÏûÛÉ.EIÆ$!:`z³ö ­IÄõÑS¡p#{½Å´‡Õæêúæ–“Ø/oTVòüð('ÑP´mÑp¹· Pu ,f?íB ¶CÕð`+"7†ÑêxO¹ðš@߬V»­pH®ÞÏxM åµv™uƒ9‘ÕÓI›, Pí:LV‚RO±’Y1Ôû1[¦;Ö¸,G5åöÍ9„pÿ[r UÑ4³*¢9‡ß@…GŽþé"ÊóD£­÷“NEµðÖÍ =~òIûÿЩ’% ò-zf½*ÛŒs¹pFΔ`©6šz*aʲ·ì³‘ˆæè½sz¢¿ ,0Ù„ÐÃ0!“’®7ãîý5’§%Eâ0R`ûT°!™‚ éÔêTlÞøçØˆ@äqr¤lHv1÷U×þľñš£Èªc¡f•…DÑbVi€v$¦ü@—ÐZ‚Š^àзd§Ÿß™ÁœfpÊE(-Ö‡BÓæÎ†–¯¢!“™È¦7¾š©Ðp"æœ1·¨€-æ!÷÷dÚ£U¸0®E¿Bª"QS’SP*Itï¼ß£ã™ì^5`ÐòUÞÓì.€!r,(<´ÂaÁƒY! Z1r}€!ÙÜÖ×õ ‘…¾p7ÙÀÌóЀ‰ò;µÃ„£Äªýð¸QUÒ•é«©‰ ŽÞ*')3›öàn ½}ØqÆs^Mï|vzîj¯ù#d…÷–:Ìúrn: ^Õy^Ý,Vh*y:hhÁÇ" õ$=£‘Ò«ÙjùϧƒF²”ßÔÀnLÓ¹¾.71€Ï&¾è)É5ÜÐÉ™b!=³Àýžy”~ÊM—óÉO_÷Ê7€¯ã¼ÙAà³’FÜÍRÇCÁƒEU°as–+Fƒ\ösÐZ·žÐ~k«å-ÿ¨ÇÎŽ:r ÉÃb•·zø\vŽÁãtú¡·ä2.wÅáä“Ù™¾`ç.tóá\çÙÒ¤ÐÃì(œç`ÈZ&öY';ãúºÇ¾•í˜pɸÈϲ ,¥=ÊÍÚ”>ÝÜñQÏ…ÅNM¯2$.á`Tš¦¯{íÛ¹i/NÆ¥r“ÅÐÎ7â2ÎDDeÒùrØJ#yâMiç¥n·ßÌHO ¶ E˜u:}1ÆQõ5­ﯮfwq艊U:õéÓ‹!XÔérHG !OÏ0pˆ{…‰”Šè*U?Fá+It™üs5Ý_ÏÏÇÄ-¦‹É´j¿§NkÖ†¾®%ã(þ²ŸÌD·ý3àÑeޝjHxÐùXq½ƒ†ÂãÇsn†Ûe¶ƒŽ΂2æbT8’ ¥‘`zZ•um”i7áB2sÆ×é?(°2¢pF†-=A.õUòIŒ  Ê^üeÃÒ ù‘ÐÇócZ%“ú*Ù¤lä-ÍSTnÒù.Ý<ã„Öu;³˜K&‘ù}•mÒˆ…Ü‚Ó Û•o[Ã9ŒãÝü¾² aß®®YÉJªúÌe¦}£aÉ>*¼£[…ë7“å ³z‘3–n–«ýbÁé,©Ìæ @¹%‰‚Jf0£°›°<¨›aËO²Û­ßW™‡FèçËÕýé{»5;ÀˆšbÆ!p2éÞ×ý1Û Áٌ݇3éIÏ*:°;Æ„Ât»ž=[˜«ú´gX7÷4ÂñUaÑÿ ŽmŸV$úþ5H¢Ù|3ŸÞ-XÓçPæ‡Æ0]^˜S‡Ha /c#Ûé&E“æm†Æ\¼ƒA¥%lœ¾‰ë ‰BºAûmN³ä³8·r¸³?з± þwëÕµ‰©Ü]àeV)ÊC›‘X¯8í¹”Nòž º‰ÔJÚR6 p#´ ýÅ¥Ìè“ì{ˆA§#Zåš3íÀÍ‚9ƒðÇÝ€sã*$U¢6ò ä¿Üß³u"7F}ΩÚj”D¢­G'ÚT¢­in'û-§07ô°n—aÑ „9NŒÛ„¥™n]ëív¥…Ý9ÛÌëéʼäó†’ ÝaÛº ?ÎÙ‚Ǭlu݈L<×=¶(¤«û]“9î.)O¹FBàѪif$8i²Ù=ÂN>ÏЫ0‹„Þ7mÁÝ{$ã±yH¶ï?U "‡LqF—Ie4ot¢ÙdÏ=Ç17!’n4ïUj°iô°c5f9‹^ç£å!L‡™y`Øô-Û6ƒ@ç9‰bäØSàg–üÕíd3ßÝÝ3Å.5§Ëh+ÀÐ'ñ°›‹Õ-4;>l݈Öì0@Åz”W·ËÕæžiõ”!NÑÄÛ¥ÃþÐn ÈþiÊqÄJ‚¸—Ê u(ìVÂòZ;¿X8œÁkÆd‚ÎÐn'¬'°÷9có¤žÊ= ÈO'·Àn)¬'ÌBÕ³\ !].2´› ëÕ|»euúP¦2Ú}°t£€ö{é *¦›y3y¿Hç·œéH ×ðPIõf¦M¤nïö77ÈÏæš9!Ãàú]BN]ô‡:k0˜·kL:ã! DiÈèD ·#$<ø¤’=´ ;¶ÏE|¿Ë¬8éJ̳qÑC:¿F$ŠËE1ÓVöé@zhšà¤‰6ínÄðU·7抗@àhÊkCœùFpµYmïEvÁûÜa*™ O¸¢{øÓ{¦] Ð݈ю9ZB£·®AÁ3C¿z›¾_ñìJI{îíEÖ ®6Ëh?Ko&èÆÊæôn;ùâB³!4ÉNB£7ÀÏœBuÍmQH¾Ñ–X#äÛ»ûÉÒåŒ’Š§Ãœ› Ÿ¥9c¶ª‘ïoæ~'æó#_m Ä'bmÔÑÕV˜e º|ì/´ž€>è1fMÌ{³Ýp@(ÿ:úŸ|t¡êH¥­ƒ´íÕ@þ7Ëýîžv.õYóƒQsîDdUc «”›èŸ!ÀÉÚRG˜#>Å„dalàjã˲¸ŸÙ(¸#ÿ ^]q¸dÿÎÀÕzs÷ìÛËó ³—¢%¯È¦$YsÛ@Ȳٟ J§S.õ@O‹ëCx¤Ò‰ƒËÝq„|“À]lÝáRIJ§‹Mº˜ZE0Œ®D6€Î>ªìYIH3Œv¡73 ßB1Ïú]µ ¯+"þ8ß~‡T˜´óëÎg? ª‡d0Õ¯ZשYÈxW®!|‡—É]#Íd¨H£¶™ê3Ÿ¯£ÅLÇTBFà1}Ä üêž{TcŽKL„´ÊuÙ½á¨ÎÎ`2[BÅd.e g#`¿á’ÝIx£A]ÄVH ©=âÍ ¿Ø³*ŒÅ<]¼ûHºÂ‡ZEŸ)e²fñŽ-mXð žGLx2c þ;vʆîMÀ»¤9Ð& LÏšQ¦ì)A9Eº“ÊòúJS^{À›(ÏLø”>4£ëz!ÝLœP¬ƒ <àû®G«™*LóýÙz)/¿Gà€2§“© ZS\Ôd(Ð-š¸g‡d7®Èd5öÑiVH2øè^ &è¡¡°À,Õ“É/NnH3¿n³Ð=Œ‘íz *.ì®y-7ѹǤ¥íØ6,+MR]°Ù&Ð!‰Ä06çà ÅbŒ¡m߬ï—œ¢)YøåBê³X¾ëPÑÂÀ7«Æ€ÜãX‚vžý»ŠJÎtó‡&Žy;aëgìs’½œ´/5ÓÜQÈ;Z:l·«ã1æ !}Lx-ê›ä÷gPí|ãºbpbdÔA·{ Y‡Ÿ Ëî 3ôTÝ Í E”î>J1Ž”“2qê!Z=_h¾Å´*4e\QqWP.fL(p¢U d¸$Rš‡ ob†d¢Á«èbwê&øžd{]T>ÊÃÛ ÿy¦#él#†¢).Û˜Ž™èÉ«Í8ÜLÛt½âܸQ"΂ËL²ðÈÔž"!A œa޲üÂJWåþ‚‘ÈûK5àÀ#¤0àŒ|q!þ?ïødWZX2–]`Ï{Q§ à9"ÛŠ”¦±RÛš7@N­a\’üh² ’úrLsÒÜšÇE0aM¯VÌÉ@ -Ì‘¹ðA¬Ò~ ìÒ››tÉKÚTH$áé—ºá2 ÉNpb¢´Iqy¾ŽÓ™GÛ[h°D©‰òô`²jµå†!\~zç=ÝéÄÅÕsê,Œô.}hõ¹$ jp£aàÕÕV´ <=¿TÛ‚|Cs@·+2?_rü²ñª³:mÔWYjÍðﯷ¬ºüÄan‡åô m¥ëî2MÀ3›Ç. ç‚‹ÙAD¸¶¯¥LÏŸ§ë§ân÷å„LÐú*ÑD{ncÃóÀ“ÓÝÎ!©÷{²&ë’yQ›@ÇAu5»n«LôW:ÃA ó4*0Ô€ãÎ:GЦ—ŠÚHÛ»˜VYé­´]§Ó›ýrzu5™oÞcV6DZ¬$'k±n]x¼H‡ÉXy–×év›.®&÷ë«õÝdË+’@¾%Jßx¸Dt¾ãX[-Gárº:$[Íp/DVˆ‹9µJýlŠnÇâ¯PD­0˜çtßò°bY¹‚²Ôú-vµ9Ö™Ó÷ä<÷ƈ’x´8ðê¬pôÔ®Ð7°h覀 âÀÈœOé MeCª{HùnË^ Ñ+»³ÕÂZpH‡i¨gaYäÖnr5_r¢ÂÒÊôºŒ¦j.&#âÚ$¥oˆ$iešO«¹ÄIš§›=^"’Q‰û Ú¸U˜¦ïXãs¡G‚ø]c` ÷r€-ÒuÔ½,$RH2sÚ ïž$’ç8Jº,I^¡BT¡ž¤k>^J©ð5Á“¦ ¹ -ì†${ͯÐÕ˜/Q‘õļÖ¤ýP¢…ñ {‰2 i¥aÆq»†A= u¡­‘Ÿ¸ Q•¾í¢jçôÀ­8Ô ž]kkF!½M—ד=ËÝ'7 Rì@y—ì‘QóÐma.¨NWÝ1¯ˆRœmŸ Éì—PO36î…ÆÂ9P÷X›!ê¯É£ÝÂpÐh¸cV1®˜‡š0ã1.LJ>µ0Hp8ÊA4ާ› °¶ùd ¤HüÒ¡êâù•b!d ød>dÃå­ñùžaÐE¾ÈðM˜¥‹X€Ô¢tmw‹Â@A *L½fy` ’l¥K¼Û`pº«® ‡;!+Âp^âdèRo# ‹É-n f[3nT°n=Wô~¦phaL,&è|ÌJý‘œä‰ŒñæƒÝâÊs©B 4Ø·[ qqÏ6b;Ç‹,½Â?ÁC$À‘¢ö¢…Yq@ä÷'—In׸p讣èerĆˆar ¥v¤›0Rê…Nè»ä]¡+ÄÍ'd“]é ç~‡zj¹SVfÜÇ™…p ™êJVQz†‹’öPO)}$ýÕje]²Y'»ÔŸ,Ýõ ã¾è»ƒš ¤7è¼øUçv»¸Úî0)[L¼Ø"Ÿ÷z;K9ždNtQPØœ”äÑE¦«·˜C2YòGÁpÆ_H4ÈQ0¡ylAãÍ~³[mçœBVµŒ ²Ž5ÔSƒ-HÀ?ÃñYž‰™H㳯®1 ÷)³«ð3í6ìzö•ÙiE`†³À0rγ´³¸¯LO óå=³%†0»ÌZ\´A%…’ŠBXpX_M(1¹ Ý×H4”µiAã/{TæÎ̆6ç8 ‰…ž!lÁbû&eOeß ä‰P—lYØíRæìQ±Ü‹vÛë¶ Îv¸Hз›žÿjAâá<Ú3‘ɧaz†ª …s©l$He[—ÍÙ8Ç-ÍE€öZèá}”‰´î‡sH$.È5 ¢&ƒì^0#p®óÌE"!ÙŒ"+μ Ì2jáe„–ƒŸcî{^VóôOÿ柊ÿ#Ç ùdzþ¥ƒÙjU§{ ÑÕU„ö}ÆÈ˜ èÖOú\ôL37‹ÆRsPãRD¿yÅÎ'åÿ ˜J5^ õ¸<3 {áƒd`}_0¯¥´Gw¾ ‡™Õ`:ÏÜJjÇlð!!’ôÄ9ã&0è/ ®"ðèήäPyų¿¿ºZ¤oçË+^Sl°¶žÅüÈŠ¡èépmß ýnƒÂp®½é¢Ïçü"+–ò]Gº¯w «Í>ý1«‰G¼Å"g6òsãý‚õƒyªrŒF€{bÑ™Gõ˜ wDÚOÝGþ^õ̾‡Ã‰è÷lSÚ ¤ƒ¤·¯]Õq=O€~3½ç(9É ÏNöÈWY‘ý¤îd#pÅé•Êë©Ëèa/<£tÆ9º&(!–IÃÌ—o>W@:>Óðõɘ}¨>Iýà³› ¯|D¹yJ2š9Pñ“¥šßüêÖaž{T»äp˜ã„L ßŸÇÊ-Š!×q$ðèöDqü© ~WI"•½Y¡Od{FJe-‹óê“SÌ¢@KÉQ ú·èH»Ú\!«qÍI¢“,/°0 ø4K7AOG¢@»Ÿ›¡?Ç HÇå/#¢Gêc–óÍÐ#£ƒ%éÕüC6íI…8о‘fèÏtn¹¡ ˆs FžÛføWk~-×Ïì’½ÐöÃüz³b‹ûÇ:¶˜(`!ý&óF;Ád_V䨒(Ô—U3ßl÷×Jx2ä¾›ðÃðx´%ª¬ö¾…‡ÉårJe7@Ϧ>ª:„Š›ŒAÓ£$v„4“ÿ휣cM>ƒGv@‰B:`þt 2­_kÖx¬ Ùa BÁ”Yîð}Ȳû 2xx겪IÆÑªf#é§«ûõ"}Çð&À…T`¦è„Œ$Á×øWçlÊé…L#="ßD¡ÎÞ°"Ãöé+–‚Ìæ‡î„…6 š’‡Ý-yÞ) [¦*²©pgb$™hï!³™µjü‰Û£;B‰q˜Ï!Ié0DÔS¢t·lÅêE¿Ê­˜dò´@ƒ¹§$(öÃä-Ú¡ùõV4ïâ4ŒB°Uô1:Ø Z;´Z? Ì^Œš‹pÏaìœâýÌŸÐh|õ0ÞLîÕàÚŸh*Ýú¼ó”ñ݃ÊXŠ¡Fº» óÙdNQêÄN» ‘8Í9+®¨ª%ΊnÄnDâc1c,)·Ìn!Ù¬,ÒÉÓ&èï&Ì!“Bm³EK<ó*]”&[œ-tÕ@„6–BP™Àׇˆk÷ OÔbv0É>ÊáÒŒWh!kžW½‹ÊpåkiܱAxq;È3Ò-­ó†?•‹Rv²¸…À,D¾:ê|£¸¼“N”0- Ï¡º£Iª"q‡ÚÕ-¤1ªfìªi¦Þ ©KîÁHº,z]¯”™§iúl¤VÌ[rJâ3NñX∢næ²0Ýw¨*RžJ´Èz)—7m$ý½nX ±¾áø9Ä8[ô†49%b¨šMâ’µÕÑH²]¯‹‘S•³SÄà~ò&½Ú¤|<ÜÈxï%bB@¦ˆS‹pÄY®{ÓöÉæumvOjj½.ôKîë ¯äQm ‚#§ß˜è¾,‘e ¸šð–O%m—†%På4™â¦oÒ GÚÈÓêÜV”YtÒB7mwV¥nÑsŽª ½š¥ÏDäídquu›N6ì|/6jæfß’/Oz0Rø‘у±mEƒ3ŸUÚu~ȼëâ€t2¥s¾ç ÂÆ´›7.&Nq„ŽÄOcŠÈ¶´±jBØKPøWÁb{s¥Ûø3-Ô(0v4ó‘•a—Ú€cÊ¡g÷’Q‰zÖ­œ ;_Ñ <|±ês×KÆõ¡)]u)g(ªQ ÚpFœÊ+ •áuÛ2V}ᠦ«T–» »˜ôÂ\²:ºuóX=$•ÓØ•VM¯×mp]õ"g2ŒƒÑ,£2&-¡ÙfïatYxÝ{œ :—×=2~«]€¼¦^‚_f²ç8pvø³Y(NWM­z=·ž_Èe³q.䜈âŒ&d¢P¬RˆyMMÍ ]ÆOlΠ9 )Uþm¯Ωóºî.~:äJư{’ý b•¼ ÐkiB’ð ÑVœ :û˜†T’MìÉ'@N)鿆 6kа`ut#'©–êèÕA0 šX3ÉÍmµãDåªÂla%БÄJÂÍ+‘LŽvɼðjDvX€§]PwQ±Ý3—ôf‡˜Âæ. ›\Àiªàj®6RÕ!™ ¹ßeöäEçRŠÙ±!R HHÈóÆÈLð¹ÉX¢;¡9F2Ÿ£×CL¬ÎòªÝ+ç´ŠtmúOý"ÛB"X¤æ"uÐýEdƒÌFÃ;!!#r¤p 6—Lƒ^쪯(t‘<)Zäª-×.Ž£C)4ÇèK©O ɬ '‡gì~`ôK¶3©>FúfÔT3¢Õãé4\ÑŽÛR㽩cŠÓ)ùeÕu~Ñ]°C8vvˆö @-•°#šR‡}½z@ÿ~NÕ¥¼VÙ mWC#P ÿÝ][oÛF~îþ ¡/ö!&‡wcwQ³‹mÑ I»}3hYv´‘%C—¶Aþü~g†ç3ô…ãµâ—6év>žû™s1iGš€øtvQ.o8°.ÃìRiõ©ÉqÜ.v‡Õð/>°¦'JÌ'¯”z·4 ºÓfì üòi4,Ÿañ ÓJ¯#™Úåõf¶ÞÀÃÓj´Aª=2[¥´Rí…){'‡ê <¸ðæ}“È踣ONÊia²Ir˜ÞÀƒº$?3$M‚Š<5<÷ ü2T¹ Ô‰™a>=. õšFɤÀ•¹7‹d\Ð4º_7,V³«%ºn7ZòR´·~6£òæž #£IFFµ½Ýq–ä‰a5GD.cê là£ÃÓ¹§¸ §›ü%1 6$¶FÏ ni̱:ÃÓÜ/lí3BÈ*`C¨ ŸbvÙ€ã‹8èFKD\Cnz?¿»ýõlô÷Ñ׿|÷Ýa9Ùÿ¹¯~¨¾æ¿ÖûœV†î~F¯}ÿõ«ô én­ôý{#mtÄÁ_ëá#Ð3†¤á($Ž˜·!ï›y¹úˆ­JûËÅÖ ÅXñ>€ØöÑU<8ÿƒ“! 1ÖhZÏ?˜‡†ž=6¬ §³ÕÙ{¾ýÛA $%k†ù™A&˜x] Ö%I’Ne0‚HÎóœl¶w/á{yìþ@h^®'[…­Ò̓s ¿:7>{çÜO·¯J[FHšÛÙvß©3Ã}:P‡Æè‘ΡÈgÿÁ“ôÞ,Õì~í1ü_ªˆJ \…Ói–KS5{§Šh0 ÈÙÇߨ¨3D¼‚—Í^Ϩl Óº7Áœ_¨óã2Ûxþ¡ ƒ‘,= Ýq*•PY vvé“ù†/_¤TqæÅyJYw/N§yT; h)^¬·»AŠÑÃÿÂßsxìV_ÕvxZ‰Ñòpü"†ÓáM‹@Œ)Q£fn6¦Ãß•·å·ØØôr¹ÚÌ?ÜðŒïAos.¬pˆM’Õņ VZÑ~„‘O&(¨#(”7¸ÊPfÂ­× ++PHe„€h– `%¥_7—‡k$æ‡Ôz´ú÷Š}gÏPÜ»Ï3US« ý~’ŸÐAŽe•V¾¾d$O¤G‚„fTé<!í(ï˜-,¸ð°r6(ü!–ÜúI„ Xœ€~''£î=^&$Ýp_Œs‡˜•Q,!ÖÎý¾D½îä°ý}xB‹Ø0O¥çËg”Òì?¼ïug#ßÓÕ%JŒQgä‰i„ ÛôÕ? ‰°¾ÙUâp_GÀ=ï9àQ ¿Œ%m Õd² „¬ð¾èuï3:^ÏùÉN`â–R=•hØ›l²öÚÔc#å pª‹"BAôŒBN"Øûü·‹?im>ß–ÛÏMH¶Ü•ºZ1ôð»ëŸ×x"‚Y€.ç„â§ÀC í¡6,šJÙ»-×TD¾_Î÷Ú']^úÛuÕÔ}á|„ÕáÒFlX¬ñß÷èýí›9ý¿¢0Q?ürGEò‡ß«7EÅô2~®Þ\üBh”Ð)+àz1›ˆ|ì‡Ó<ˆÉzù™€3Aßs±»[”Ÿ¯Ê}‰b•ù¾ö÷uð¦WÎG¾ ¼8> á<ªËMô¡Täe>½9£z†Uå z”P–¥MõóíòÝ6¢7ÏÏG‰ 4nÑ ÙÖDoÜ6:lú@ ­Ó‰ŒôÄë aŠ’ŒáWʽ2×HSHõfþ‚SÆV¾­}ÈñÏD:ãÀc’µœÓ8Ÿ…Äñ¿`#^Ǭ©_ۂ´‚ bÄíV¶Ou*#â‹È¥Ñ@ÂysÊÖDfÔM*uMõ¨®­ÂÜ<XŸi0_'(°öï,c,Ò´ÅÐðÕ\#Å éVC !•‰úô5Ëß‘3ÊU”ŽÏOÂÄΰY–TBI N£¥Ñ`PQñ< (ñ\@Eg“<Í¥#4$©®Õž­˜ƒuŒn†56YƒêÚ CÃz6žNTˆ3mü“TMf°Í3hcŸ7&µ ¢Š?ÍÊY$o„´5'-šÄ\3oŽå²1½Ýì—׳Ûê¤+Ù®Zê<î8c*Q”Ujsƒ±ÓPº1[Ðqïç:6¹YÊ;kt©Œöú*òì<£¢ßn‚шȈ£ä$\ãr 9\úÒ?Ê—®Ba¦‡ÒʵҢ(íÔ¢>u­t .2ú×tcªl§âT$}‚.r‰eÞס’Ù€,8§ÒͨŽœ…›ø‰ àÔœ0ðç¤xå"’ùwCq¤¾^6 ‚@E‚$ lO*wÑàŽ‚²ˆYŸÄyÔ7©œFgxŸ#ê ™ñÕ5 ¯G£¥>ó([¤®¼IgÐa|ï/ƒ ººV®\*øÒ ¬f†ŽêϤ/]«k¬òãÆuR¹/‹݈:>xHýJò=F‘ðÈJŽœ MRQfDÆ(BjÁj: cäg‘d蚬ÝDÕÔ;eàO7F(ø› >ý¢¡8Â4EqÜû¹¢øãVL`u†NÃ*00É+†K0yåÊhJÙ¨d6›±\ô€ÐöIÊè™°‘áÛà°=àIŠH'¢d=Œ€G¾\‹'ª¨$Í5.%Â%ZP’ª$láœ!‚•Qýá²6ýKCOì Øå`˜bq —Gò#}äMH_Ä3§:‰1£1´X§+¢H%k$&Ïáõ÷³k`_¥^5à¯gðª(Wæä&üÑ6·V‰B•›ä'Œ˜ÜM˜R°þ²GîaRÌß°I'JÝ$š½#ôJë<£K˜³èì”a?ÝIˆº9 .›3r@o/Å¢=ôFFÌFotYO(Ó²;e)œâ3ÊQ¸ŽÛL…‡^ŽáE^|¼Íy·-ï>-ç¦k,ý%­Æ'Bñ”a£¯”©ª•Úʦ±ñFÍè²Ò9XŒ*$°¨1€½(WûåþpeªÊ©Q³w?¶J7RÓR×Z¤;aŠ˜›]Ü7=öq/öùfµ9˜’åGäÍç#ve«ÞH]˜HŽé5R‹×$ÏÔU‘Frò"]’œê›fä¬uþ£“w“Ízâ®Î%—ö·Aª ³¢Ye“°•ÑîDb­£oŒV¦½r,”˜|… üæ{o£·»«Ïg¾ìö‹Û³–—ÛrûåLÎ¥¦E’»³ñOÍK*Iù°Øþ¾œc¬ô5­¦Çg¿ª)áxMÿ4p,jF1¿üOÌ=ÄŸžµ»Ó¡ñl»C±ÿ†Õä›Õa¿ø}v3Èíq@ì$5ߤW –·(2¸Þ5̋㠸ÃO­!°#­G ËhVËf‡ÓËrrD#Ÿö"§)ê»ñújŒY•}à¢ó"C`MQ…HŸ¿“±j:š'2‘Uþ¦>…™òе$Å=Ÿ•K:S¤;Ù‚î³4Äšöô€žÍã©ØäDa?§ÇK‰P\BÓœš Êz<Þ'Ó›™u6ïD8¥AOöÓé« Zç‹N´PŽP<;Éç©ôF]/hG´…rÕÜÁ–VÞ¥Û‹†ÝÔUz¨ª--eÙ"ef>åÏ™/”ƒã:%‡gUe•¦65lµÿò¾ãújOP‡k­1 Ž’[c`?—™P™í*”CÓBj¯p~@!²^’ýŸåþÓr=Â?»Ñ\¹ø’bÇZlâ‰5ú=a Œ šª¡'Ôb«ï£J20üBÿZôH£»òiZ_c cû8xµf¯©QÇ[ë[/B9¥:®Z•ËB\û1~‘ºÔ€S5X–º†w˜Y~r…ͽW\…ÊVf¨ÔsfˇI:wS³*Ö…Âî¡1º ‰j3†NCÎÚ*?éh޶C½_ͺVööR5™„Q7Ž©ó5o˪=¨òÎÜ•* m¤¢èî»›–CŸÐb±î N›PÁ³8$’iå:±ŽÈcÎNbZßΈŒ«L)Æn±ÇÏž¶j1D¢R8ŠÝŒ„%¸FÆblö-0Eб{žãS¸ËQøAdõ]P²jM¥3A ú ª<óTZÚ18n¯O‰°;É<æF,ˆ${hÀUš6KÑàî*,¦ÊŸÉiÃxÅÛß>ÒTy-µÑòý„@£©ŠAœÒô[ðK2Oå”°kÊ3»+ÏÇ¥ ®¼TMmàyz¤X™ë£›âãZ†Ý'fžJ+µ;‹HÞlÑöfôG¹­7ûÑÕ›@¶è­£”Ý9únŒ?N R|ž™eA ö9Iéo} AÊ#ñu¢-ûŽdªÎÒZU¼Ö~ãŠgì’= 8"H™ZçDÁ;¾v@ù‰ÀUUP­±‰ŸF bF¼>uüÅÒ¨Dח޾÷e:b"\"u¨öxSëÆÂ8Ñž<Œ€SÆ€g‘¼½Ôh,S‘;fn{Žj ž5\É3à"ãêÞ—™‡×ˆ›…ã˜/ÕÂ- ¼CÜßHÆ%ó¥}pW=MŽýù´8%&Æã‚ª]NÑ|EÖ€´_Â1D£WÂ1æÊ=ngIUß®ØP®bOÆž®ÌÑh#yÁ3èÝu‹û¥¬¶Ps Ÿ¥B xc»Èº9åìÑe÷Ý ¢ŸÆ1ð Ì'›Šú‘öq¤²âÓ@tÁÿ\^-7}såØmR]4ÀPBêY%ш2Bjâ`Ä‹gÁŠ2O¢ÑLyB!í>ÝY(@0ë®~KdŽH4'(·t9Ùé%\î ¼#’fÇHáYšl(Ö@.¶wÛþÕP-É­§¸œ YŽ[×¼F3«ŸMInºuÒ]Ø¥!ź‘âˆÂÓhg5tE X›pÛ]²ðÀ!JCkå᤯Q)úAût{ÓùŠåaz ®šðúp(l_±å6C­‘?Ôš+ìt’‡®Ï(Lës ô„ÔY¨æ ªŽÕ”·à=ì1Ë ÔØY†Q¬q,²±Üy³[Q£}¹º¹¸¸,W´§W®M#êÔ7¾C«tÚW“&«ÖžjhuÍÄœöJá{­®ÌövŽ>ˆåºù, 2Žþv¹¾¸À?ö‚Ý<¤qV¼X4ieu,UÖY>…&ÏdµËsžå•:Gf¤éÌ$8»/»‹‹åúz]¢½§užƒÂì¾S7îVÈ´AǬúS5Ôteã5ø;È Ú÷…S nQø€É;’’»åíÝjñ§;º·ßB8‘؉ŽÖ‰ÒÈä¸ñeë€[ ŽÒW.¿4y*C.WÃu(odpp]‡pÛÍ)FòîÑ ÓçÓéSYE¤QšRW®Qbó …ücxÿ-þ¾Åp#Lõ -ÃÊ>)••IúÍ.ÓXèëbÅQ-¦Ì•sŒj̘99%±jt}½¼1Â<>£ ¦žu¨(±ˤ|xaЦt®±({5íÿ Txì½ë“ÛF–àûÙûW(úËÝèv/ðÎnŸ=Ž±Ü KýøVAUQ2ÇUd-Ye[Ó1ÿûþN&@"Ī’Þ¹wãîÆ¸%‘ òäy¿¿úêÓÛOoþÇ›8Ye‹õ$”³8žeÑd’®Òh™½ùã?½ù|º¿¹¹=ì?í>ýã›úãÿ/_}µßû¹úâ4/å3þj¾›—yÎßÿƒÿ‹“8ÊleÙ"‹§ÅdRNŠùd){7ÿû‡í¯OóÃᧇÍñ'ŽÆïþƒßÙ6ü©õ±¼à ílçÓE”$ñdž&“Ét9¯RùÑ?7?înO7»‡Íçí×·-»_øæÍ4qàŽyYL\Ns{>È9†zœ™ ûtò[À¾Ta¿ßí·§ÙþnvÜnNÚt¾ dY DiÇæj¼W'™|XSA”d±ÜÍ… ¦ÑopùD½ŠÓóñÓæV%„ÆW¾yS:”Ð䀤˜DýÀ§™ù°>ž˜¿7` Ø#ö'¸KÃ~ýù7o¢¬ìCzGBÐ_½8/Ã+5ØYQ¤.Ê“+ƒœ›§¹‘så$nʹš±;Bîò€Æ}p";{ÁLc—Ë#¸\H£ÞôÊp ·VÑ{ÜÞŽw‚/ßøæM:™öeiªà8šÉ_ã8Ê&ÉÔ>»2ð‚äIV!ÙQfÇÍæéæqwûô|ô1uçs¡í$éƒ|šI?ÚãdâH´ʧ¿ÔV…—Ô‡ÿ¶½}z»Ý?ûdº…¼õÄyœ6·h¶j:Š¢Rç¹Uøg´#ÑZhÏ‹ ÀBÀ†ñ]@‡± È_ÿm÷"ÁfPè•^IQ8Ò+г–Â*~á„ßÇÇã–ÿz8ºõé7oŠ´WKcq%ŠÁ’N͇5Z[4]^àU93Ï’eS\/7wÛOœÖÿ åö"µ,ûy6J§®´ oÈéÙ•ŒóÅt•DI‘NÖÅj2Y,æ‹õ\,ÑŃHû¥ÒaK‹/Ë–Y–*\eæÃôͯ ‚¸\Yôk »xo×€Òv'ì?~ó&ëÕ²QRöQQ9üØ¢ÍÅoÜÜŠ›bíÒææiûùpÜmO ÑIS¸6±ˆüî<Ñ4Ѱ¸¼> «²ð2áöñôt|~¸õó¢û)xuÀmP{IRÇüÕg%ŽùnÑ®®n9pÛx­êbõüˆÖ>œÆ±b#F©k,“–%|m8Oçżœ,ד|1ŽÓÅbF"y¬)ðóöxÚöX[ŸâýöÁ‹õÙS×ðwYŸìºþ~’ge>’h½*rX+^®³b*°>löÏ›û›§ç'øusﳌ|_QYiÞ w’ç‚׳—›årG“_ÛÇ[x á£Èqx¶÷wX m!\ÿ3 ½^]”$ê2Å2l‰Ò™´0|mw0_¿ªâNVo‰A…ã¨6ðò8¢/8ð¸€Û ¯ èÕÛ´ ‚"©¹u:Óiy=´®Së‘̲iÓ“ØðéK×:ÿ;~—ã„8Ô¥™¢<ÊÄX µA`"L ”ZÇòº@†Ç‹&WæNåIO¦ÖòZ?@Ó¦-Aj]Ìÿ[`….›°ÚpÙÅt™YO)E€\<¥JAßýòt8œ5x• xÞ-ž~}ªþòÕiûøýæg¼áùáywúxýîÿ˜üþÍä?~ÿæQœÇ¿“iZüÇ|UϼßÞÿ°Ù6Y`&¹<ÑüÆ_w§æ7²8úý›˜s:_úÛnwøe}¬ò'ÿø‡¼..ªW§¿GÒ¥Yõf»z^ާÑý_Þ¾­èkÁN ØÙDº(Í-õÂ̧D¼r oëð¥=|æx¸Þþõ~óôô§ã®E¾HEPLU®ØÅˆƒ6ù…4N¼ `>Š“Žgнÿ·Ë÷W¸ÿx±‚€¸ˆ õøq4å D¿2/$} >$¼ÛžŸ6ObñÛ¤×ëБ±ƒ¢"W)¦SA¬ã‚˜¶ÏÒ@Ãìöi÷óŸ NJ ‘ð¬BDe\ò#ÄË}ç_‘r1±ž´yþFT èò:QY”ÊåGqÊù¹ý(ÉcïéõHÕkI¦àÂâi}¢žáÃq³?}:Â`2"Æ«T°‘)M!'‚ØÂ^ÓØËk£"¢IÔ¡¨g Ò'Å$I•ó£?ätýj**Ÿz­ŒµQÑS°ÁËÝéi³?×Q„ðòtªé‰ˆ"!õî…˜øŽO"­žàè1-?ü-ŒdŒK•SÕ¶ ¥ž;›"l±ý$c´B4Iˆb\„'7ZAª¤‚íkÌçrÒ\l…òÓ´·ˆj‡º:nQEaÆ/"üû7eæw‹ÖF‹D©âº@¾Ú}Þî ìo7èõ_¯€@âÆ ËèÒWh®H½nÅÚ¨h"±“Æù½ÝYc<Ð ±Ú/Uûv¼YØAwfóÜ$¥Ÿi*Ý‘9L³ÞÝ“‰žoö?…]½·>™v~ÊO8 BuøÔ%ÜEæÜk“¯+%2% rÁÁw’¡ ’µæòuq5G0ª/ö)mr$âIDTãÔÁž¨¹ñ4IÔ+Ï øQ½ò¬À åʧeêµù¤Ò¹ã‹¾#°=: Fà |×¼¢á¨¿ã µkÞÓWŠ¢À–¿Ì»P{É\}‚ Wˆ=M|ç$‹DQ¢òž¼R¥#.ß¿îvO_~{z@áT£kåàĨٳô>st\å¶Ý â¶{1¦ñàâ¢Ô<èdéa¤˜ä˜àË×DËZ€T"îàÀ¸:¦B™läµ€±ÆjJ]„BQÔ\ƦEÊ|#¦~×a)D„MšÜP÷Öëï·uék­>‰(Mcûv_D`@X˃xVà#›ç6ç¿Ùíw¡@HÐ(šL'~h"¶Ž§ æÎ’fX3Û1  q÷ðX%¦§x%ÈóO¼`‰ÑeW@›•ÓíåÕ±=îT8žN¥,|Îw¯ªÃ;Ñ@‹³KLðæ깂€‹tk*NK]Ä¡S …¼¬¤ +-®÷d2FmTÞ sßý(É’^I*Nñ¨ÒI!1•¬ôℤÁ‰PY®a ­[ãQYŠ­€‹—åD…<ò ¡ŽLXÂõ-W1QâÓ¨Pã"è5IYµ÷ðS{ø¤ËÏ7Õáo.¬FNޏ(4‡|eëÃB¥VÇ*w°pmƆ ûùËKW1Üh%Üé‹‹äI¥d TÕÅf¬´äwïB] «##Í9/¼$1Y`/.*%Q8<½¨ëû¨È(Š8-´¨yKÂ5ªnÖ+”Lè¡äW|´Té ,”Æå×ç;¾ ï¤Y$™×OJ+}P:Þu}p›¸x$‹M f e®Æ Šìiit9ƳÄP9‰¯pÂ7á}=QM§ºJŽðwE¤^oè‚=¹cdpr›r¹QJU–¦™GˆR¿™”V:aîÄ÷kÖÅ7ûkØ·CLL•¯ªÖИ,…7Ó’§•B˜;B¨†â áÑÊô2i™ëaLs¯ZN+ñ?w|Œúðï÷_ö‡ Pøø*†Eæ7MÓJÐZÕ¡5ž?&êŒ"A¥q@†éªÆm 1ì&S?'Wj`éè`áépóÞÈÑÃgjs‘`ì{ÕçCF^ã:«ôÁÒ±îB5•DE¬¹ÛÃç/kÕõo¨Š2²ÔÍ–^‰x¢‚u¿GuŒœ/¸Îu–âñý2«ÈW6é¿Q7cÔÁ·û»mhºAäP©FïŸê¯šYMÇÔÌ^¬Ð÷»‡ÇûíÕÂNUÒ!Ñ8™kÄ S\± Ã_Ao¡¡#Šºpü{èPwÁ½2æd"gÄÖU&ݬ(rñBS/'”Ål²d”AœQ”2‹×ëÕJÚÞK]bì3â膖Í[HûJpŒšçš‰ZLˆ<Õ5'>š‹'µÃ\}¡v’$f‚'ì4•¼}A1]Ç\fi6ŸÌh?)Ös£bA€Ñ@œ8ƆH™!¡ˆÂI: ʼn)¡6¼#.š5£dIlÙh$_OÏ9ʾ븟ÔDå¨!% ”Ö8iÈÉU¶¤?|µ,g©XËqœ,23ñÂTJÚšéÚx%1˜ &¯&àÓl H,X¡—¬kíÈñóêø ·u|“ˆ8}‘ƒÞ$*TO…l»Ž_X[˜—¤v×í’óÏíùç$x<ç?w»½â( ¼Ñv®›:ÖÛš&]‡f€l|¼ðÃötØoD8 ÀJ÷(ÕB ¤ý†D#ø!Ùu×É"&¥OVä¥'“b1ËòõE4b¨I33©žÐl•Q@Äb5/u¬ª–JL³KFëdµBÛÆ1Î)dtÄ6XÝlÇP-ejm™+¢Àè =l• ˆQÞ5z’Ér1Ï&Ë8Ë—s‘CÓUnµÔŸžwËãæê%eB̬å,U ’¸ES6R‘ºO;EÜ3Öós:$•LVñ{a‘Îñ1(K©]2Íßÿåí§OO7a…ç¶0†ÂZÓUÇsòÔärº:±é@ø¡œt˜9‰×t›'ñ|c*d«x™Â»ÇÍûíqGÆðóóýæ§axH$áÍ\Õîgl€Ê™sUg…ÉP$Lñ¶ ꘯KlPɨ•Ž5a.(qAïKôÍÁÌj Të4EAi†mR¦=y —_ÔÅJ0p3¾ªK÷‡ýçÛ7¡°dQ¶šl!^#v’g¡‚BR1S²*Q¤†Fc™‹Òk›Ýºø ­ÑÌgˆÃ †ž?q$ê%hÂÊRëú¨Æþ.ðç^¢8›cÀMèŠcÚ´4£˜¦IæNJð’ßh›Õ† R¬ÙïnwÛåæi¤øaÍdµKˆJeqÜèbjæ§?;Is£™º”Ó„¹dòŽ…Y®ˆn×¢ïP…H #]¦&¿v¦¢Ó$ÓÕœò i ™,’9CÅDšV‰˜Í~¸JŒÄ€¦L¬sìèF©”!ž "›÷è…_Ú\So¡dØ Âwâ¿QÞ{ûëF"Æû S#†'Dœ¦ é„|‚3ÕÊä$é$f,a²ŒW…$D¦Y”Æ ÁÞ·ûO‡ÕÝ.в5gÏÕÂ7jÔú £éÿhŸ<[ç«Y”ÎsLsè._e«…Ñâ«ÞYœ†]»qð¢: ½å‰)‚tèÉáËi*ñyL•Šæ|Ãù×T=™óÃ8¾óRsú‹LóP9¼Ë Îáåæ…Ú7?%È€3±ˆæ“š!§ŸÌŒ3]™á2Än»G>bÍâ@{ö¨Å q›$©À!^4ÆJ¤½+OFmr9¾XB"à§üÄuÀÿå¸{bhÔyÐß+=Z†—{©òF_ªý Ÿ œÑ˜À7¦tW¨B/Ÿ`?вú)J×lMù ¢Í£Å”â·,_M—Øý¨“<1C>ß~ÞmCøHŒ8©qÎêHø2-à|Þ¡Ù¬6—[G¶õ<ŒJÑÜE>ʹñ¶Ähë?8ã§Ä‚%tg¿Ó:û´ÿì!RBì)­Î¹Ü ÑÇ…óz 0T‰3ø‡ÜP‹R*pt“ÛÂÒÐŽžaI+W.ò)6Þ£S™)GÏÉÌùVÆnJ :»û/>#ΡŸ¢21ù™w!xálžWŠ(êÄ,¥|OCjêUñ̼DLŒ2' ".V+£ã'É¢˜‰q²Zý)TÖY¨e{Ô…ó·)8a“L€ŸX`Ų•ü픩ÈÖ?DÆð&˜"…£5Ù6¸\€E´,fMØ ÃäNÕDE'(úSø„n /zKq±žzi8Œ?L T¡+òq•ïL¹–žþ§ËãÜ6c°åìñLÜ–ómÛe,L'Xò*bÃ)–Lô@b”å2‚!b†o÷öW1…s™p@k2ŸÎ§³Üø]fÕÍé*™A1c øHP¨(#मëÁ6Ó8áb€0õ“@IR3I_A”¨/,ìÊjá¨^ƒ­\IÁãä…ÕØ2aÍö'c?gD{S‡ë9x–ÈÁg³¹å9x°dÁ:äåØÿÒ`3xzR¿íÓK™mÄð[ÚM'î¹87‘%º—~9 >»±¡õœ{¼ õðôÊ*C×´¢i2—Í|ÆŒ[Éš&ËéteȦ’¹ÿë™ Ïà”©Í©–H ÓÏ´.´íá¯È½0‰@;GÃÌpÖçZ[Ã÷üðawƒýZoÁ¸Éâ+öS[<5‘îJ6`9KPÂÆÛžV6]ã;M J’@Äy!ì—¶Ò‘Ÿüb%>'R¯Æ~”Žô47´¼¡ëÁ¤ž§ê ¡2 è\Ÿã@Ë&ÑöXš7S…¶[7ã’µB ‰ôS^Há»§ÍéRÖy5’ < PD9ì'ä‹4+â6¢NÊ‹Z¢Yc!A±Ao_'!«J,>Åšw1Á×\ŒG²‘÷>n™tØ g¨ê¿‘ä„”ÈB×>pˆ™B ã1H-@’už4XRx°AfÎ0FYŠ2„QÆ:wÆ&œÖþ•8¸{È̤©l F¦Ñ´zåæ@†žÚg1Œë!1=B›PÊlNm“nx Ÿ#ýåo9¶¦˜î¯S¼hè°žãÓ§WWßíè&ñþ`]\&žHO‚Ae/„çñìÜ Ýùè嘎©Ï`Z˜òçÐIS5ažˆf>=ÃcªI†!wŸeLÛÉûVái-Ù'ꢊ ¡S„@=arã z*%˜‹¥çcn™yj€&"Ùº9ß ^ÜñJÛÌgç*ñ“ÃcŒ¯³º8£ K?~¶fe;ŽÐb\é#íª’³UY˜4#}Çg ª9>‰ÈÆí;$ÀRBÊñ oÕ}ššÐ)2ÇvÑ4§æ‹%W“…Ceï6»cÖ`m2 îÀ –½@*Oõ¨’^!+aùJ,K0³ åÌG Ä#®(„LÅÝ•ŠÐ)LDæqClbÔoÈ–‡õSÄ"]ƒ32Þ˜‰kFEOMaÏ·Lå «”¡ˆ*ˆk5VáÄaØRF"ŽÚbó°"¦ý¨“•HùŒa€ÉrµdÎìlUÎM+Ä‿μéýík-¥(l<¹ ¢¦´ #Ôû¡`Ì ¢ò5`P´-`H•F*dxÓþ≞½ƒK \ ¢.â„°n2#vµ¦‹Cˆ‡‰“ù"iT…]'ÁÂhdíììÐÿP£-L P»°ZX§˜|»`*ºŒ,c .ߖ蜫,|l0¬q9™÷èdåèS¬¤¾£‘¿=¼Ú22|x©JíÜ;äÂ6ÚIB†};cdÈÌôq™Ž­›ÏÛ'™½tïR$˜«¶l>¦2ª;ù.A¹¬Oe”çðÝÜ?oãÓÓ[˜ ôçûîžÖ¹û2Cæ\Žÿa÷`+gûÍý—Óîd=Š+uÑ•íøœ£ Âwðhׄ>ë ìqþÓ:Ô”BsÚH @¬(mÞþ7Â7.F•1>,`i –‰CDu—ËUZ)›Ól ø[§¡Dü•¨¬Ó}†9×AÃJ؆A‘ñz†íy¡»zOl8¡u=Ð}¶§N£×êÈeZ¥3ÄÂr"3XÐÙåb‘/ß^[BWs‡{¬ßM’Ÿ=F!}º†:¼»ZE ²Z3}HN‹™©ùùó‡·Ï÷O»PÒ· –Æv…öéV‚´^ŸÕæLŸß%šñ€!—‹Lz×|hñYz¡ ãRc"`òv¯ca(§×%¯4NM E©âŠ2ƒÆ-<íXñ€ÉÜì—E`Æeé‡9„½„2Ëóx¯`ªøžŠ©Bï€ÇRT­¼±´~z—f-›Ýz¡­ÃáŽ)#òUyN ’3*‘vAò¤»nÌ‘ Š8½ Ф4ç«Ë}tjeJ7»’Œš9>É‚¦L©ú£¯0Ï$h߯yÜGy8êz,<1KÒâó¸×êG:lf»y‹¤é…ì’”`ÈEŒÚæŠ+@l*R¦y»0Ú‘-´Øý­LÔÊÎT×ó8i*iz´O/@ÿùa¬‡‡M°ádµGèX\jŠ=z æúÙÃ#¦ÆøPµ³Zu» d}s3¿¥Û„¯aÜÑ(A]Û_o¶”‘P &!E/°Ý½Ž ùØ“É%bÓkrÊTKÊÑöT‘1¸CÀ|Xîg ™8*1Å€AQƒ' –yˆÎ'wçÄ*¬¤‰ÀÊ÷ï×èÙ[±ºGÉ»œRCºšXNÐ>¬ÊÒÀxbªÌóö‡Ã!pP°Á‰ ¤¤)JépJ¤CÒ] ˆ&Ñ®RWØTzJPQ`Z°¯Qhi¦â!ÇRœ2"M¬'¤Ö áw$D.Œ”TÍfT]œugÓ¥î\‡;Äè0:LjyÃ:*L¦~¨4(e—ôŸº…xýlZë4g€ÂpØë‹±^ÞBÛ¦ 4Ťb+&ݡʆTË1P„ nØ-%Ü®ˆ±“®ÿ9%¤³^2¦u¹6ÍÉbÊœ©šx7ÿ»øÑóÃá' ‰Ÿ.“*w§ %­eß;CÌ>ñIœ¬²“Ò&åŒqnk:ESæ½,3ùQ3#X.B¾¿¯ö§Ûü†ÃBÇï¶{~Ƭ?~w¸åÏ$™JyâøáË£,o¯×Ë›/¢†ùðçêËò¡°TL ÀQ¸yuàXxæî2ö•QÎ&Ö&Ǫ¡l}úÍ›^h-ä^PóÉ´ *P]`׿°^LÖ#ÃÍÄö6FÝ_jåMP¬J‘Õu±*µÃÿM|ž|ƒWÜK¸ôóËC^•6þ&ˆôöó×3é²EèÊ@ _²\Ô’.Ã…/gÇ'¾ù‰Xër{_k‚ëùÆ7D ú/-¡zá.Ó´ v ³˜1WçW 1ü@Óx×áT@µÿ€YÀØâÒÊ$Ö ^ ¦ cúEâê·±æÒ6^”·} ^>䉲£’¬4SôƒL)…rú[€ÌÌT£b¼ 3cDöB\ Àq`+|+Gý(®4’WéÐ~ú€;¯9×Ѩ¾¥ñmqìýÎ7 2mžÍR+\æö£š)©MTc&ó׆ÜBï^…IÎyT.u0lþ —Mðšx¥È’µWÇâ£5¡“þP¼ü7oYƒÇ€‹X¾l@n4^tîùÖ«ÔnÑBmÚ’ÎÅ•a7iãå_7µMåÍÑ¢{9ZR¬ò~©Mnµ‰ùèåoúø´­ö×?‚ê¨WÓ¾gÚ3éXæÙ•a „á7Nnl³k‹¯æG ×QÉM¶.Ü2Я faŒË†ÈblÀÕEÖÌë%Ì>}Úí·Ž›ýé;›:ÜÜùüê£ú$Y§ =ǹ†[¦ \d™]Öõú›;Û¸m~nÛ£‰[âÜý†4™ÇÜ¢d_°K'K)û’¯æàRÝ«‚ZÅ.ú®¿Ð6£SË­• Rj`OÌùl%#¥j´\ÑÀI'#à&5¾X›·ßä¥Ç£gáûvÎ0øŸ»ý“0ÌæÖô7âsÿWþößäŸ>ž¿ðþéËýÙ¿5½.ÏÛÙ'¶ ËÒY»ê·,Dyj*Û»íýæË| lmÌóùw>q Û#]3ò¸ñëÉ’QÄΗSÙ“¾Li4—pB MPøô¼7ïý¾ ,ÜÜØ/¼ß>}ÿü0ÿò´=ýå´½û¯ÿͰӻ§…œ«>äîóÞ§ñO÷p*O~Üù’e¦fŒ~ÚÝn>©QçI%_çÌ1üx8î>ï(\·ÿù“Iå3›—Õ©·Ôlò!ØSŠkÀkrs²µÌ•2Wȃ¹âÿ>̽Fšâ"7!„ dÌ×L¤œWêâ/ÈxØÜÝ|”mÒT<ïO¿ 1ý©bÅLûšË. ß,ªXzÒâ¼==ß Æ²?j(¨Gex'§1–ó #çf«çÜ"•ª£¾êÜ‹.ûcÈz.F"‘¬Ô° Õ_(Ìòéòi÷Ù(ËsL‡>8]‚Þƒ³áÊð»­LmgŒàçÌ®ºrÏN C'ýä¡´ÂR-Ë2xçŒòS8:ÁòO»_·¬ ¼q*³ƒ.ܳÔÇ\8dµc‡^7có[óí‘2⺙ö`d‹7óÞsSkÀÚÈÀëžJ–9@¦P­U¥?Zç.ôs‡Þ7øêÑM¾,ûð}ÇÝ:pC'äéütòùþ𑣡–átsûèdÖwîŸ?}¢)˜RboWNµïèó¡£ßy®å^i%*|<”=ÚÞO+˜ÙÛc~å4ƒ„8åüÔ²8yðZ*“º´%UVê¹£8øÊ§¬Ž ’‡çi ­“Wm×04´ÂÉÿ³¯œœ™;—äÃüDÎ ž­ìû Ð@RAz?ŒÆ¥¾Ã#V qýà¡.•¬A¤Âö8ïÁ{Íñ“ô]¸]<™¨›©†åa^Ïwvi|ÙkŽÛƒ‡^¸ÞJ2|좻á]Tþ²×"ÒîCLÙ=B'Ì>ñz?ñs¦=wèuS¸vLzMñŸ·G™INá“@‘Â./göãõÉCï<Ø:¬Kï[œé·Æ1Qä·À¶{[>Kœù@¹«ìß 8A·÷Îý9G¸k3{©P­ÂÁqÈÉTNíçÍEnµfÉäþs0ñÓýæVX›@1n* SØ«ÿއšg[âp‹Xé9:*?0®B1•܃º•Ó1’Úb·¼Ó©e"…iŠ0(¡«ýt#õAqûø"a&2iš‘AZÇ7 Oii¯Næ+a-KYgM!fg0ŽÁUI>Ü™oȲl€~½‘K*u´qæuæT¿÷Ý{p|ˆÚdnþ²Ý'nHÍÉðTåæ#*ð¥¼>cá›p¬vò]ýú»Ù↠!’ÇlK/£=}0”…lòÔ@H阆zJrVMõƒp:m«×Fuà?/hð1BþÔ3B]µÈ­®ê=ý-ø¸¹ý) Fþ3ãUAI&%Ùµ>õñ0ûYÁ“´x±`W/Û_X01Y«RÂsœQi ¸!Õö,±öaÃJ½@H.}6¤Ëè2V`iF„ >A꺽’Ž: ÑC¾{jcL½pÐþ³¹ Üñ:‘^ð˜²,M¶&´Ôð5…¹I›Ks=ã~æ¶A§^H¨;”hЪ ³‘x€:7Šy[B7–j|ìAK°© }²>!eCP½pØè}Ø6‘`ìQ~ÀuŠØWø„ÍK"tY:kÎê…‡™†Äê)C-¹ecSC‘_7™©€è 礌ˆR:•Ñ ¡±ÚÌVà‡|‚éÕä–ëCÌéd¥«Sc™:”‡Ezy© ÒwøûÇ0ªêÁU󂣎ÎÂï½÷Û~µ”ºaïèqÃÆ^úLA$¥ñHËp‰®ÉÍÎ;"^õAÅgΰ>þðƒa@¨ºL|‘f…7º`VÇÝÏT“Ð?úp8~ ±IH¸Âa6›Ï:³.DýÑh5À/»ýÝá—`¨P¤¬NJ|J“e§éÕÐo•?OÐö.Ø4¿P2¾˜î¢ì7É/ç?™€ú5Tži{ÍÏ‹î}ö9—.]§v4 Ën=Ú›¨~‚ªñQÁsÇh8¸s`%}=ê8:Pˆ=)±fD§7L¢²«åÔ¶A 3<4«ªXD*âšÑ#ÔHøÒo¬·H+@k˜Þ”îa­Lƒ¡:2g]3>R3:‰ýw^ÅQöÛë-ª Eê¼Ø$wÞäã¦(Èp vüI`B"½Xé7Ø]Pn>QÑa6©¿Z§Câðë4ÇvX{&¶!Üo²WÚ#Ôc þ uA 7¯˜èŒW6K„…ÖÑd¶NYD…gÊÈ’x"Õ¬ïíþà‰ObMéŸ$*8hÐR3mÏÞpA: ‚Þ…ÓNà¼Òµ Od:™>¹¡ÉЉ“5+2 Sµ[ –ÜPXÔßl²c°™¢ç™l6+$49ÏåbæxbbgOËåšY-PÚrQP~^.8¾™êÿ§çÝw»SèñÑË©:\—áQÈ {P4‰,ýmz‹v|ñSÖÊÈ”URRÐÇÙái` ˆfWGÑ:ZI%â0LU“¹H:çt*ÓX;)Nm%º|¸b* Àâ,:?ÒÖšj,zÖ·Xc* 28]@]·A}Ëà™0pí–rÚà4p“RB§uì×/»Ì ­²^IÖÄÕjºb z¹šeq6™¬i<7ÓŸíÀ#éÀÞí¥B9(­&!1ª­48†IÊÈѶ‘°äø¹=>$×8þ¥M~±}D-=Sׂõ’¡‡h\Ê£~_¤)Q/ ìþ<°÷Í ˆLƒAÆjRê EYpw8¢"èhPî›^æf¶ôÁps<||{¤Ódp¾ºáЏ£.³à'B[ ]}tÅAó T£Ïæï߇á¬ÖKÔ+ r×îŒ'JŒáŒhŠi…÷‚ÀA–Úœ Wàl,E‘=dºíû+ñã² u Ù;_qÀ` Œ&á˜^ª’R3"¶ Çróóîî Ð䆌¢ØM ªNlØÕ.(“È0Õ‡’ubA¡{±ÊÛå5Pbf­vЃ©ùÐzá,œMë=®ÊXW*cAù!ìÚº=î°øY/|ónóDLoÓèÌ ^¸¹/uêô° ë¼H©TÈÒ¡¯½„+ì[2IX°¨ùÉLA3v‹b¤1¤Ï Ã'Ó¼– ÍdvŒœõy×S •ÆY9Òšæ²ãî×ÿw!N6ízdôºR7²¸âB‡LÚî¥üŠ rˆê·Уȸ,1…ˆ®ùìÈFy`©›µO>@*e³vŒ˜·Û{Z)a#³˜áízh˜,ñ@£6§xbý²:¦7@Ϋ![$U©œµ‹‘à£&bKˆ‚ƒRÃÚœS&örpš|=¤dê›Ð1Z“”Þíh´¼¹%Æ1 ŠBŒLM—„rÆÁˆ’¤8Óàpÿå3[‘¯‚aHHuÁPøâp*V$ƒ‘ Õn‹CD9sO (±#ßÊþð°£g%ˆŸÏ qy™èP¹c´àò™À¤ó ‡¡Qðb2ø!M—«|bu ‹ôšèøa{:ì%Ñ‚¼ê¶ cËtKžE”"‘&ž^9¿Õ SiX½ˆÖ‹[eÓ|³ÿ) +] u‘Vf¢€¸Á†ì}..Ø\Phàe «&¦ zïÀr-ƈMCÆÊ/…ªp&ÄY‡¸úAÉŠ\VùPPè3 Y¯eyCú..xiÌu±;„ÿº C‹ÝòHQ ‘Eª¯(ó« $Ýèþ˜^üª–ë<(PÆ œ[úe„Àýæôô¯ûÃ/{ù¤š p:<oMÅפÅå[Õ”—ºÉ_þé‘zU~ýw|·y¾ÿNoN‡OO¿ù£}úôÇÅúÉ´ø:Îÿ¸8Üß®4fÄéù#É­ãÓ¥”ÖÜr´|8n¥ÿwÿ¼ùx:Ü??mÿ§|(bM‚/ò›Ìlœ¤‹Å:5ûHmåµÖâJ²×¡+G¢‘ R‘e\áû0(-¤lFXäóDVÉäLbÌÍ`G«÷ÏA¥9Æ“'ªœ¼”ù® óËÉ –²6¥CÇ&–IÜT çE²ùš*±ê•ݰë<` J›À¾ÝìwÏ8и¾ØÍ˜4;-È& ‚Ž¢j ½|¾Lò˜92oB‰é¬0X«‚æRõü„è F Q[¥Š¼| \>-íJ˜ºZ¾ïÊê?Ä&ö\ 2}ñØ|A2$®×¬p"ψI¡Öýþû›§ì0o ¥q©®Nò*«%6DÀvfÍðö?Î€Ìø[™øIÈY^ÛZ ZÞQ:°Û§`Ïðhƒã–)“U'Kh`Nò„ ŠëI Â>Ÿîon ;ùõæ&°¿À µ%Ĥ—8•©„©£•Õ=b´&Ý1ô9``'Æb’ñ‡wŸnn>RP”KQ«nu“ïçtŠeaF(gÓŠ5Ë1WY#—ɆÀ<]fk“¢ºVôƒô™J@1û¹Q`L×âÕ—¨Ó`ù)¢-FÖ‹_^2Û¤MyÐÄ*!“½^Îò^7ÃУu*”G^Nì ”§)ã ØÐOÁ®-çÄŽ^. ´)é*V=dòÑίt$äqQfódM:•H+혋i½¬Ó‘óç'&»‡écϳØM‹–0­¢ÚÄÎýv½:A@Žêqè)ì‹û^¿ù"e¯_€^.Ås€þsU®‚g 4“ê<Ó&JˆˆŒ¤@p® 郚Ê_‘S†¼%ýëÓ„ìA¦)c²œ-ËŒ‘ĤÍé3‰½ïÿò6 ÃÆ5(RnÝ!G‡¨ &X©²”8º89”uSNÎ>.ÿÉ™ !M¨ÿê?7…&»çðidÅv,uªÁɾƷT“Óà ßÀ íæxÜ| ³W"ƒ­4W÷^H¥ŒäŠ'Ø!6³˜ÙÓÂÕ/D Š0¡Ùßoh¨Ù·æ…z» Ž YU¦ú®º…–›NÈ /uâyOÎ0Æ»Ch¢YŸBe •’ïÃÑÐ6ItæÞ=§?I÷NPdÍô‚1@G‹oʺõì1Àƒ¾žÓ˜ZÎÖkn )Ó>ß?nwAµ¾Rg•Nˆ¹8\í5B}|I¹vjâdÝS¹ø•µž£O¢Û¡­Ñd×e­ú*Í᜞XŒhJ-‡É°%ê4ë–'ÈñÅj0ÇG^´‰½ù(èø¶–È»FóÔÊJ—ˆëå;ÇOãÒØçi×>7ç§$©÷üIÈõÃi&u¬+–‰ô¨íE$‡D'²Ý'uÖYßù& þê K#é¨CÔ„%W¨^Àšöž™Ú(ÿsæUn«"Õåâú¡ 0f„·÷ܵ”iÓúÇOAápA±{Yó£HýÜæ²ýòe]Ëß¡C/;tŠ]Þsf1}D&vÏükQ‹¯/̦®+¾èœ`~+`a$ɲçÐwÁ‡¦E«n|ý¡WÊ¡C©c µR?tdÌA™ç²i ì9÷ƒF5™–PÊWU…QL¯ê,]ñÀpA}r„õŒ=‡ß‚‚æFãäRÕn¯Ì§ïõKçS²¸•ToxÊ„JX‚ìçIf§˜cSéB5{ÿ¹)ƒG^Q8ìW:¢)ÃK1bžûdŠœ æüÌšÐo™ "ªÅí:– ®¡¸YÑ Ü#^2v®öœÿ1ŒâLLG Üþ Õ°ÁÌ˧láôŸ:l®©åưSÙ4–à¨B0œ &eç„\d¸—\îwCl«‚Øu£Ü¶©HQ.\Zt3 •`Í÷;ŒKÍÁJSG ½]Ý™E$~ý·ýø)„5ímSÄ&§ÝÚ¹l†Nôúװ˶"‘ ¥.Yõ¤R8-Ö&ÕN®ÙwëôsõŸ?È÷1jt \Á#ÝsËóL\~éòòLÒg×Þ?‡“ ÃÕÞ™AB§ÜÊç®I¿ÿÊe¼H »F‹"  kP‘+µ÷¶ûìDRqâи™ #h4þL ÑüT6£8i§“®#Ì-¯æ'FÙsç÷“02ÝI.À6‡Pk£ö=ÛƒEÆßè?|@2¤yÌÓt(ÃY8›’’’)º ¡æä}þÐé6„A Éq˜¹å~#7ë“è§ÇkHô„TŽvÝtјŠ‘HÓž‰cçuSžk¥c'úÉElC¡“skŸÏ»`£·I(L©©•xâ´nmЧ“Nÿ+$žEPb°¸Z~Šaz2í°’€>Q“Lr3‘ÚŸ˜Äwê¹þS ýLJ)2˜TõØû®Ÿ¼’ TLGœ#iI-»‘²™$_|>Ò‰ã‡PaZ§™3K98Ÿg÷ZYŸgwz²ë7_;ýM(>S û zQ’·"Ïë¬[”Þg <‚âE†R B¡`Ta|)÷CgÚà¨ûðúTtꜪ¢)…!—°?Id–Q ù90cd†¥•dûi‰H*róéü@'/iz©54ÙX{qyí™]°5‹ÙÎŽ£ùjM³9)›õʬ±–fíÍÇm`é¹IATÒ¸ƒ".³‘\|©+½: ‹ðe”@L¶ÿ÷œnœ±9h¥‹h–-(˜“ÿ±å R{EÌÝNF…ÔF˜49A5Ò–äCe‚ U Rw‡£Ïˆ•bIGÚ9=›Á`‹ÔsÉÌ8dæ$Ø¿(ÑŠ*:âÓ)L¨‘)ªäÅ;âM` ¿Ë bå]``ƒš´ F B5$ÅÕMQT6J9’&.¦&♑ÃhùjrBK+ ?I'Ý5N-¤ »AÅ¥Sÿ±ñ`娤P7Oi3+Ûë/ Ë£¬Õj„áƒçÝ"_sßLæàLóà?ö[*}ƒ§K˜Ã3«–”>Sdðì1kº¼´RTgÇP¹{uöW.D3áLS*ƒ§¦Ü®ç47>«NíP¸ßÞožO£Hl!YF"hJÓO­È™"‘ø2Õ+n °òÞ4Š]îý´}ºßî??ýx z'Þz.¯-ÍT2ÈÕU‘óSCÞ8;2r¬5$šzÃUõJÊZ “ʀơû*!ªÕœr³¶ÑF^Jg š=6­œíc‡$ É2°ÞãnHh[ЇD’bjžù‘]¤7Ï¿Âuãùjµ)«úSlñ DÒöðŽ:ÿúK'ç& 2{ŠX‘™—"5 Ç ¿—ŸHQ'ph®¾ç)ŽBƒ\·ÛÛC¤¹‰”1j:(žÈ¨<åä´ªqñÌ,ò_|%Ó¥¢qtYNsóðñx¸§r?˜OËIØ(Lœ—N$ÂÜ{%ΉH´gºÔ‚ONË´:{¢pƒ‡^mWªþöñ·§Ý¿êSk teްüWŸT‚}JS_‹nìÙ_ϱֈa>LC5®W´S\i$ ~SãàOÇ›{š=o>o¯bàÖkòfðÚ‰LxœZ{z‡âŸd:ŽF ÅØzij µ£ÇI*9~Eà`ÁI+m->Iud p¹@J7…Ôµ9rÜñTõ›·cEc Êx<<"ÛöèŽUðóaw» ‘òæÚó£Õ&0àäfН€ReRIy¶n5.Ýœ<ÜmˆƒÆCMG¥ôÛC ͤL&ØoVwA¹¶/ÝJææ¥OîB4¿l~ºx#!§´¥¼–\@‰Ì©òÒJ%Û¥Õ=ñçí5¢çnŸ›Á¶II*WNWX’öÐ:s,ÌÏ€Œf„²h< Ü()U¤í3—L©!G½ËŠ0¦ Íd˜€ô´Um¿¬¿¦;=PBš†P},¶ôõè¦dn&›¥u ³Aé‹É‚8ÿ"ž‘Áp vruÃápóÃj¶¼ù°úû‡QcmYÞOò1ƒWUÂa¤Ò‡áü†XËÍÙ¦ˆ¢ª¦àëTûT¯lKù€+“æpÿö÷VW‚Wö¡8gu4)tÙ—Ó× Ck[Ò&òKÓsR¢êŠØ-m¦øfsZq'Óåt¾²—ÇÍã»Û@)l§eÊÐâ~8aÎbšƒxF»t-9>CQäøäê=Çg¢öÓîéù.¿ 2ŸFƒ£"Ø_1>S[B3ˆÛÃ=#4³9†~ ͆¢:ÛŽ_t°åø›%£’€ƒÝd^8˜ê¢ ãóqõ·ª1ñqŽè2Žn‘ª3êÑOM €Ý†xŒa"‹`¢|Èwf’PS]HQiÚN¾I8‹Ü”ä›Ì°tßÔ¹™Ðl¼‘WÜžfû»1Õ@‰`C©¬4T0Èì6I,¹ D‡e”0çöâJèá6”8ÔÑh¦bÐñ`X¾B’á‘my·¿Ë …Ém ZŽÌÔ9ÒüM0øØ˸pIV*¢-b‚½ÀAS«ThpœžŸ6ø*A€ÍI5«™²Ex_ /êfGà³_£_Õ\ax‹™‹"Örš¹Ù¥‘Âö, sÙ§#ÌN6$Èpà…öžŸvl Âõ4Iib=ÁæÔlBìDd»Xx%›×BŽi ]CçÝáô$³R³¢–¯È7|jYЦà±ÔÖ¯e k³å•`àJ< ¼¿eòU 3G°d°-Žý¤ºªe2j*:Wù÷©)ÚLEx˜ABšž*BŠDjb"þeF~v©±†3¶ÕÊ•hœhƒíQ¯;úàíŽ=k _þi((€A7IæRBw¶ÍêË8Ø0¾£-g÷K^ƒtJ3T@»Ú>—âm¹%O xìþàÁ­ê' SYEÓ´êpQ*¼gÌŠIõ‡ï€|ÈtšËù¿;|#»Û¶¸'»]ýr8þt­IÛjJâ|Ê!“èïry½Cv?Of‰üàźè0E`ªÈ;‡q¾õÃ$Àå½ÃùSãf)ÐNÍà›8®9§uúR;}¸uW‰ÏBᆔ­!w4L’bB—±ÌM˜ž›-›€Îˆ¬2 ^æöËxªi4/M/ØYÆÍö›û/§Ýé ²Î¸ ‚4Š*t¯Í*UYƒih¤&3¬ÉÊ;“÷’!:¡tnK‚þ€CÎmuVœgU¸—EŠ\V*ƒ×‡/+\ìQýCs«sv‡È ôæ‘Äg|Óˆ|¬6p~¨­"0 ‰Í½ ÌePd+PÓ¹4´&aµÔJiÄ-Î+Œ/·¶ÄÀ@}®YôáxL’yž­W"úþ²“­é!¤CJN4k»ð0äØu fEL@GiC§@˘Îg@¿Ý³Þêñ¸•%W¡[e¨ Øp;$åIÙ;¤Ðx”;¼Œùÿxpót¹6eåsjÕL±Ëò»ï¼ w’qÓ|àRÊÝ•H¡I¦ÐoØ)¬0ç›sË.¬È9w€h7§.Ô Ù¥”Þ(‡¦GT²þ3CËrf„SãÌÖ/ø—·o¯æà–kùR>¨+LÎ.ŽM,†œ “³Ð¬é³% ºÄ'ôRÚFÎè2FøÍÓáæ kã$!OöO‘µP›3Ÿµoâ•rø™T¢wÿþݷ߯>„ñ‹IÓ 5§”DŸŽ6mbQÖàÂæâÆ RÝÁ¬ óæÌÒ‘„ͼ "3ü–=‡ªœxéI3äݺ !£u†)v½€ñˆéÀöä«-3û~vưï]î»ëŒœ¹(3µÔL¶é (0™Eº/ \–Lˆ†~>M«óðùiUé‹…”·Ž-œl()Œ&f««4;dâØMÃç?ûA.#¬*½±tô†I0]|ŒŽg&Åy£©×G(s‰â)‰ªñ‰Ycí•J«J›˜igL4Ò}&þn{|x–¬Shk¾)„̉ʳÝðB¥œÞ ª¿~ÙÞ_#”mð!õ#u¼Ô‡*8%¾ à ØleôlM6@»b;Wôz7T‡OÔUÉŒSn4C½}¬ÁÉŒÍ2“Śęt+§àa’‰mßÍàçï$£ï§¸|ŠIÝÑgëç2sˆžŠ¯F '88òÌŸupÔñ` QR¡& @¬ur¤aÇâ7~5ÝGpODC'‹%Á1gV$!¦féZs—•Yeõz;Ú®²"s÷j.™ bÒü׺íñVÅüé“!2}Uä+Æ Ì“ES,?™-™°c¢#«Í=¡m3dê|÷r ¨)|9©+Ç+ŠöI î9çˆ,,0f½0Ó.6±&5‡Ìd  ŠLE£„ ÙÒµ05 œ­WRâ7Ÿ/L†~ž¯çkC¶—ÕíWÑf*2ys5f“Ò^®²¬ íìÝaXqч}'/h9À¡àÉð·»=kìÿ=xö‹­w–AMÎqk‹ì»¸ƒ],žmÝÝ(ßèö 3 &´°î±Áâð@qH`>Ò:NÕóf­…¢Ù °ŠŒ•Qü­ºª¥lü£¢‡©;¨ "WÌÝ2"ä²sõjv£AE*£ûQÁ¬3¹èn²èŒŠ¬¨Õv݆š_󷌑‡avŠ•†|*‡§Ä:¢ÑÜrCÞ_èdð†Hsvßîï¶ìaODê¥òTuéÞw&ól™á=:´eN©õ…†˜PætÛÍY,Õ˜UžqRVž10Dâ¿]ŸšÁø0‡—Uç—Ã_ͳ0”áhy–/r>…xÏõËØ:åЮl ÜÝ‚÷¡ ¨ðïZÔ†ylñ}VÉËÉ[Ãø½úb°Oä5ÿÔN$ ›‚ÀÎ>}¢iéƒ øDU^ Ãärd}J?ûu-ID´JÒ­f5PHuPH=áeÖpCkܼ;nϧ§Ð1&Ö“Ÿ­GŸk{a`ö ­ÄLCRã!= S‡T¬ûàxÿ~ñ.v^Ÿ*yuö7öJlX]BLÄK Â]¾ã7â W¢ésìA(â DzÀèyÅÊ¿×"¡ÊQ=È b×X*6ötûü«¨˜-Áÿ¥¾–ª76„.L³9êãÇg¦ÿ…]¼ÝlÃì Eq^|İhïÁ1ƒåà’9t.‹üuŸ98-Ȫ"—ªÝ:Z«¤`3—N4Dξ„ô/g_öŸvŸŸ&¤fClבD…¨½Óm ”ÙxÑ@À‚åÔeq’íòÃßÂ(ÈØ­ìQÕ ©apÓINàŸjFô$&x§äÕà‚àšÀ‚¿ôýРö°ÛScZˆ—3ÅAãñéÀ‘FNô)KÈ–U$}a @ ]ÐÐ,’gÝýv/ 3EŽfœ~D!¢ÂÔ|*ú·ºoŸ5Î(RùFÑÕl‚“h¨ºoBó'Lžv›ýÛݯOÏÇÀVc":ÕIAÓBÚz¬ Û)ÂZ¤T v,,‰>Øøã y€™bÕõ]t¢•.€‹uAã·‹Y šH¯Ä[´$&ãpR#^{SH—‘ê,՚ܥ-˜¢‡+™róÄ(УGÌ& 9:µLHPr3Êѯtëí²êj,©éoE¨ÌÑÙöä—E³Ãæ–9 ÿé×î Õš³»öž=˜%sì0ãË.›š¥ê²û\>±ð(5ÄË+ÚD†L7­=ÆÐað Å®½cH”ÄÂÏÉe<Ž¢+Ø3ÌþY¤—gz8(ZÑCÐþ×Wz˜MZ̪ B’8%]ŽXEV[d1Ï‹ýùþq󸋂v 2˜Ë¿ˆõdR†¯]9ÃäÆ%Èâ9>›väÆýÇ/ChÆd,쥎C!!/´­”§²dg*Yœ’ê$ÏùKñYN¬Ê¹þÛÇ­÷†bh35P*W]÷؉qâ•Ù1~Ýü¶0)åw†d x÷Ê·ûŸCD©Rb½÷^¿r‰³ˆÏéeÔÔ£,åê;p£©„Ä)ÝÒž™ˆ ŸŠMÇ(s¹¤¹xOž†ð¨12,G¹r[Ïß²6]za "§O˜áçáÐÌZ;þ{ÏCNo¢ÇÌÑLi¾¢p”‹—h9>!Mßñɹ µƒšÙì§($†Â(9*1è–Ó._ºêDz»¶¾sûEiä#Õ|ÇgX9~JôÛ‘tÆO¦Á·OÕ§Ú‡/NX¹ý©éTò»QSXQ3JEÖ9z… |x 73 @‡ù”œø®|aUÒtI©²sè]ˆÞ9î  Eá^á¸`F¦P¹ìËsÏ|¼w8aħ"_È¥aç x»^W}N»$"–+ÆQ^°pR¢›ç~­kty󊽙äÑt(ø‰%U#…”9§ß 0èÀS;éã_6ÇÙpEÞ#,ucL2}Ü<3Tõú±RêÀ}L«d¾’1ƒ2Kè[öòîÀv1)g0^bH)œ5.õPjŠÅÂ’Õ-Àâµ%°ÈØQr÷k)ƸÀRMH á#½Ì©×GâådY"ÅKx†Ù" kr6Ö¡6¦g€C3-MûŒÍˆÆr•¹K“ˆfô«‡/LI1ݹÔ×{ò°à„ºÑÁôÿjŠ€¼*Xn¤­<й©(6`+w0ðùþp:ïS5³rBÖNÁ™šA¤'²+›¨Ú""FìˆØŠ ÞnöÏ„CƒªZ ‘ Öt•ÙC秘ÁOCŒ›4ç÷¡àKmƒ³ÿuB\ éRò50t7Æ“—-ez&»]IR€&#ìÞÉy£[3F ù‰8ÆÌ‘!rò{Ü=±M.uò {â+¤1H‘ÂÂ>^KŠóSÒ.ç—îùîùÙ˜}ÜCeƒ¦Ÿs»N.У Bæ;Î/~šËlA@)ÖLvîÓí£Lî ¶“·Ì”æ ;4p›QzŘØb†©¢“”ÙKÓ§ÿoòîÃGó?ÿôÇ7ÿãÍ?þËW_m ØŸ·³ãí»'>Çw¶øÊŽâäÿ~þÚüywçT³¿yØò5çߢË«_··Œ’øx/_Š“Ç‹é„5ÇþϒÞÃFBr—Çß/ÿÕ9 ŸN¿F“¯³Ëw>lŽŸ·O矖ÕÏãg+?w÷á`Ÿ<ñè¯ìñ†Ÿÿ=_þoòþlrúéQÂ(ߘFË9±ŒHÆç¦^̳…!ÌÅziö“—)¿Â+Í׉jË×K4˜ïëEõuóÒÛÃÝö=u·[Ü=öh/€3x¹‹ö_s’ïW»=c¤qèqx9þ¸=þå´=.qØ(;Çkæÿx~÷nþw‡¾ææ—k’ xdOÑÏÑ7ÑbÍVËœÙÌe±šÃÅr)ÍWÿÜW<-ˆiºÝ«¹Ö{M7¢+~Þ®ï7Ÿœ)ÀTgÌz¿u-îõHèIllT]»VÆÙH4P)Ý#…1Äyµ0®î Ú¨úcͲ_1À§ââ¤ý‡ú;¯‘×@žZªßóÖê8 ½õMñžÎWÒûµ?/ä=³h†¿kÆð÷jÁ>üMkø·¾÷Z­²Þíï.d@’¯3]ÝׇjÖTV8#Ebÿô: kÞÉG ô»ùÒ—Ëþ÷_>îÿ3å~ç7ö_ ¶hZáDƇZ@uaõ§ ÐwX£ßo];»ï»m ®ï{m›¡û½êÜKó'_Å–_¼_¼ýOeÊßRUÔ²ÿ+BÒ5AœÿíÿŒÎàz[â³öŽ/·~#ªáÿW,6VôU¿,³Úèroâv¶ÿ-@­„[:eæž@·µš™¾€€_§‰:œøz’lc…ÌËì_fOv•ì¶’Éÿ_0‹Zr•É\U„øÃ–jÔÍÓVÒÛ÷›ŸÅæ•è-©Úr’ÒÁ\ÇPþÆ›Ó#;ÇÕoº¯†Õ¾}Ú>Hðñ¢Ë(úaþ8qÐ,]¯ç Ù£rRÌ'K>ïýˆ²BáúÜçU¸  nÖ¿ÆÌá¾_ë~4ôkŒÐÌ2ºÍ×([gó|4ôkÅÂüZ,‹øZ¿æùhè×f¬…ÆÙ7+4«_ã‘¿/L ¾2»Z÷t¾ØWÐ|‡—k4œ| ùŽ‘ä~æùȚô®F>Ð|Çü¥ïù@ó"_ă#h¾cùÒwŒ| ñ†X8¨ÊºHc…®Æ>Ð|G-G¿cäÍwT¢ùw#áù@ó•hÿŽ‘4ßQ‰†ñïù@ó•hÿŽ‘4ßQ‰†ñïù@ókK»ìÉó‘4ÞÁtãß1öæ;*dõí88˜]`5ð@ó¢žóÕŠIø#ß1òæ;„¥^ôŽ‘4ß!,õ¢wŒ| ùa©½cäÍwK½è#h¾CT}Ï E£dûräÍwˆÊyÑ;F>Ð|Çê¥ïù@ãt‚8H>Ž»«±4ß!j»ÿŽ‘4ß!¦þ‹Þ1òæ;D4¼è#h¾CDËÞ1òæ;„m_ôŽ‘4ß!lû¢wŒ| ùQ/zÇÈšï™v3é!%KV#h¾ÃŠŸ¼cäÍwˆ PÙL¦yÚ¨7`qöqV#h¼c-6ÃKÞ1öæ;,¹OWcåÕzäÍwˆê¤Ánü;F>Ð|‡e©¼cäÍwX–j½c\Äiýòg›o¶ŒÖz³â]ÑÉ;êÊ›ïùEXù@óViÓ{1’kÖ#h¾Ã*í¼cäÍwXf~Á;F>pyöµÁÇèwŒ~ ùk­¼à#h¾Ã/xÇÈšï°†AÉÖ™QÒ˜h¾½Ü¡šï°‚ïïù@óVð½à#h¾Ã*Ô™43Ñ\²ÐGÃàÍwX…Úzd”¤dËœïuê³Í7[Ñzs¿¤” ?/…Ž·<²ˆg”ñºÁ±4ࠧȼc9ú#h¾Ãè¤E<þ#h¾Ã(¢—¼cäÍwEô’wŒ| ùÃ/yÇÈšï0”Ï;FÆ7ËhäÍwˆ"šÍÖŒ”I»#h¼C–é¾èch¾CÑKà /eÔÍwˆ"zÑ;F>Ð|‡¸Í/zÇÈšïe÷¢wŒ| ù‘‰/zÇÈšïe÷¢wŒ| ù£/zÇÈšï1ú¢wŒ| ù£/zÇÈšï1ú¢wŒ| ù£/zÇÈšï1ú¢wŒ| ùŽJŒ®ÇZ¨ñÈïá(ÇèwŒ} ù#~æC7ÊöIF>Ð|‡?/yÇÈšï0l;gU×X8F>Ð|‡aÛ—¼cäÍwrç?£áù@ó†Ü_òŽ‘4ß!føl.»FÒÕÈšïGÿEïù@ó†m_ÇÈïH Ÿ¿àch¾Ã˜K/yÇÈšï0æÒKÞ1òæ;¬øOWéÈšï°l›æc}5J …h¾Ã¨çáGêxsÉ€—¾ƒ ©Ì_Ο=’Ç>Ѐƒfÿ¾cäÍwˆ:èÀ¡FÎׯFÄ—>Û|³µ7+ÑöêŒz ù1j_ôŽ‘4ß!ÊîEïù@óÂ/zÇÈšï&xÑ;F>Ð|‡µ/zÇÈšï¥ý¢wŒ| ùQÚ/zÇÈšï¥ý¢wŒ| ùQÚ/zÇÈšï¥-ï™ý+³‘4Þ1-ÿ’wŒ} ùQÚ/zÇÈšï¨µÊØ»šŽ| ùŽZIŒ~ÇÈšï¨5ÃèwŒ| ùŽZŒ~ÇÈšï¨ÕÁèwŒ| ùŽZŒ~ÇÈšï¨ÕÁèwŒ| ùŽZŒ~ÇÈšï¨ÕÁèwŒ| ùŽZŒ~ÇÈšï¨ÕÁèwŒ| ùŽZŒ~ÇÈšï¨ÕÁèwŒ| ùŽ‘êàl–NG>ÐxGþRý1öæ;Fªƒ3Œw¥pšï©.ïù@ó#ÕÁå#h¾£R£#l|0w5ô@ó•:zäÇÈšï°ê eWí¸HM>òæ;¬:xÁ;F>Ð|‡U/xÇȪwu,å+ér½ŠéíKl5°½}=y Èš¿† éûµîGƒ¿†HéûµîG¿Fô±ï×| þbÂ6BÖ Ð÷kÝ ÖïûµîGƒ¿“÷ýZ÷£Á_ƒû~­ûÑà¯A§}¿Öýhð×`Ѿ_ë~4øk0c߯u?ü5̶¾_ë~4økh}¿Öýhð×0Åú~­ûÑà¯atõýZ÷£¡_Kq«ETÂä®|K<õþši”fæ2Ãeð »{;YMØðhç)ÊNy¦j„~f<£é~¿}’)‰u»µ¼Dþ¯šu9îQ”ÿ U{wÚð'âxöî!EBÚÜßÜÜþô­ù"38<ÀÈ÷v'ÆG¬ö2ôŽ_œÈ¿nøÁO»ÏÏG3 °zçW,²<°cþpü"CANëÃñ‡ÃÁÌÛ”#1qR†EþÎŽ|47h¯ñöAÆÔ5 ’Y½ù ­LÐlÜ4ìï¶¿Öòï6O?zÞ48‡´z‘À*³³øsÛË-þ©1›txtª Îþ ÄÃÏTç8|ã% Öóa?ËìEÆâW'2㘼ú,“ùÞÛ‘»ÎGÏOÆ"lnüó~qÜœä†Ì䀯ÐÔ Üü›a2Y´:–™)úÝûï6ŒVþÑN²üÃÄ™ê~ÈcæÍl¯ú#~ôød®ÏÑúünwxÿôÅŒ©MìÖÇö“ê‡oï7'¹Xá»÷?<ïíÙ,ùÚgïv'f(’å{¿»Ü达߫¥»;.o÷ig¦¸Þ¾Þ<>Þo¿þ»ÌxýúÞ@üõñyßüåãöáð´ý¶ê~ËÖfùñê·NÝO Cøn1Òoñ27ä7¿Å?-ç7C—ÈwìÝŽ¹4¾üö[Ôˆ@±O½òÞÌåÝ>Ÿž2 ñó°ybïôéB»æžîøðÃîq1ú›ï<ü""Ê«‰²ú™ÿå~÷ñ¯›ãŽ=ïŸ?}Úýz&FØ!†ÍÁÅõ9X¹;öÂÛ+ÔÊÎeû‹|zÿåÄ,;Éé»íÏÛûú—¯È `Ï8ÐçôÅáör“æ¬{;Pú<ZÀ;1…äîO÷‡›û¦"ûêÔ¾Dó V‡Ú¹À‡öÙ ›¾ìŸB7·ØMí àμq6 ·gÇXipÚ>~¿ù¹=nܬ,f–:S×§Óz­‡@Ú€¶¶h-2®¬ìÚÊX§ W7["cw ³3Û~*³ÐY‚Ô߯³áÅ.æ‘u0)³Óëéìò‘å·, “GòŒdY½Ì²uIµá\×sóþ‘‰à²¦=d×;ve¥º+ŸNŸY/èÀÛ&‡l ½˜½E²BÍØ¯·€eÛ_—þ›À ÚŸÐbG.bÂg¹Ü å³é§»“‚Qól£ÐÏ~³ÜÞ?m®€.–Ùh@äBôÊ¢ˆ-N<;•†Ù8°`öMdêžœRhR L»+¿äüó¡ó?nþÊðûGlÍ0\Ä)«pÇ4zbÅŠ Š]Ü\°@L“¥,™4¼—àî"ZZ¼³xì¯ÇaÆŒÈ7‹KœC;ŒTÊWtVŸ¶€¨™¶´ÛÝ>3'Œiìa83ânªo%MpÆôCÔA¬£¬Vl‰ÉÎê¯wÛF%±Rä#¢˜¥0çx­ëYõàør=¯Gkdöñ±;IÁ+[‰õ½7©(Kš½Òh+º ¬YÊò;÷…U)KšÓ¼´, ›ò¦e­][׳_Ç»+ µÞò-ŠX§R=K¼„têuÓÕoto§iH 6»ôÞŽ½6ÙAFSÿÝHõ°Wµš»  » PWI…,+e×x[ÈmöŸMÜäÂRiÞÝuÝ´°Š¼f*è¡Ï\J19{Á¼¢É”§Ún«|`㣀+ë¿Í}¸4̈‰„âKWÀùÔ,BÒÑ5Iº{’PÁ´9 Ÿÿ†h]èÊ:#ÊÉØ¹ìáh¡|`m$'ˆˆ»ŠªIwIj,×r*výyt kéx¨p7„ÍÍ–fu œp>ïˆ4*Œo¢ë£Ôë¯b¯‹P©¹í›ë ø6+ ¡[•ï@ªxjö*ÓJ¡;sEüD̘˜Åéú}‰ÿ–Pß©×áí½®×бÐJuhÄŽiõª.Ù"õ>‡Ôà\Ït퀀•Um]¶uôɤ^ˆÖ:ŸÙ<ÿë¯>áà˜ƒ~ú²ŽH´ßçdÊáWì+:Æì:ÀTÝʤAÒA‹é,6;bïb–ˆ‰ÜZ×I²J˜”—y$’ ËH+®lÝPŸ Û¸¡ìZY —`À;ÝpÈ™8YŠ|Ô«-{Ì@k),é3é¼Þî¢ Ƴe+öÕZÚ\¶¿ãI9‚³méVöœ¢ %k¿ÛB§×«µ0 ÑÑ$Óƒ±Ùz©°i!Žb”±XÑgÇy=ÙëÅì¢-îÜ®ƒŸA_Åò…—C[øñz¤5˜2Œ–¶½ÆBÖw+ø‘U—²éƹ¥6 ’N¿•¾ØJêu,+(ž¹Ó¥ù™|f^Jl¯e¾ DgÙ’'1«­{/ŽMYëN(e^—±u’+^3é vLhH†Ž B”9ê]Wp½þ~ûôuÀ™ aÆùT‹$y"XèÞM‰Q¡(²*Šä2Uæìæä7o7¤È~  •8xÕaaŠLî?¿Hi-ÝÝÃOkœys—–=<™0ò™û›Sþ?›tY ‘¤©òvtÍœ³Ëg,/ñÙK<‹íãééøürj³*>B÷(Ò[ê(Ô“DnŒ—ðé‘QÎ~³Ù×Ì®*`Yô&P¡¢!>àÒ:XØ"£ÚŽó"à6"DY}®!€E:$ԥح>â©çìß½[Ÿ:'ììp¥CíÑt¢§¯ù¼dž|—ï•ñ&ÎéÈË`ê §{ÿå{¥ýåü×ÐV˜‘¯¿{¢ÔBú¯†-¼òò*ÜZ’lï—“9Õ0zOêð²kÒµCâh(ŠòîaURÛ7ì˜ÚîOüéD5O‰¸ Œ2×͆Ûð–ó>‰8ßÊê]LËð“GÔv(`™•Š€RJx"Åßh»ýÓÈ~l!¬Ž¶:£6yä€Ù±^ˆ•8®ËPÍ•„w±âIòµÖA-kWÓñû¿¼ƒ)‚7¢¬L‹¯A]:+áaŠO¸*C†=‘Ò¨ª£#ÿȸÄpª¯wbɦôŽòSŽ–A-å9ÌÔº¯Œçrn?R•–䈥.)‘ ±O'¤AT:âFqi Ôï¹e!fµžBuÔ²MâoQêN)1I4¿·Œ8 ; œ]vimäøâ>k$|Ö+¼:Pð{¿a×àO& ÖŸå:è9Œ4S¡­Ó"0KJæÒùn‡ú%ù@ÆâÏ3|Ø)æ} EûuȳC ÕÝЂIåY¤ÖaŬi”¯B q’Å&…_`akä@AsR ‡y¥¿¶ëBBŸâÛ@Zn—]†.rG ¨šfbI^^•ȯ65²Kð£ÐÄÍ–šHƒž»’êÌÞBí )~¡K¥×Ñ9WáUƒŸÉ”x¬s»‚b„1§[Ûv>>ß,+:=RgÛ<<ÐdÚÈ^ƒñr¦ ’ÈELöœ¤RLÒå o”eBÂÓ‹1¯kÍñèÔÚ„&ªc%ôýÇ'õ3([ãé¬ñ“ᦒÍÁd3k9ÞÂ’×¾€€%c$”gÓͪç’YjJ ‹¥¼8ÛyžÙÇ+Ŷg7yZÇ5‘—PÙ¬Ûψ¬õa$I‘á…ƒ[Hòªúãö3eÅÇÕ¯!,1>^óÓÉ€t) •T¥ê±u%ocìV‘DŹÀV¦"võØû»–·×t2sj<¼8â22ž˜"ìÓL’dìâôÑæÌëá[þŠ¿L¡KqŽ`,*UÒºŒü™Ç™WU½ÿë2äÈ–Ÿtž¢xÐOxÚÚÎ1Z+3²¯Îvæu¤ëõç`Éa¬ˆ‚j`çm±5GEN!ŽD^·U´¸Ã+ ft*î·´…ìOŸh¼ Á”õïÕ˜iK™¿ÂB]±?ò(;»Ü}”ªINæm¹z*¶=GŸÖ5îîÕϽL}9ºÍMÚï H—B¡ª.x†³×Õ‚ÁËܪ*¼ádbîjAQŠ!ÚõΖ™Ð%ÿµÙœÌ·¨È©YׂÖkÃ]!¥{ ¤åu«&™ œ¢¬¨ŒÓÖ¡½‰‘ÅbDS&¦Å &E,%8µ*]ÅS)g‰b¬=6÷ÚcœÛfÇã¶j‚ ¥®þthÃeq¼e±Eœo8eF8Ü€Qaìë‹“©”úð·,”î· xÉ9š{øÄt8;_pÏ.8*ý)µ¹W7,d£njû Mì!0âT©u^…Ü—y]îöÛ4Îù´CsÜIÀÙmX4=W¤ú\’r v‚Ü„!½øÚ0Oy$Ò©Ã{mTkQ‹3ƃ]Š“dvóä]BnÆÍ±ÒLâR*ƒðJT®C»ÍÒ=ºI‹:Z኿E-þ ™Õp{Ü=ìöÌe³²CÕ8.&º@ ‡Øþ|dQ 6O›ýmëYòMÕ³óýìB¼|Ç{ðZ|¸yË1ù]zÔëéödlÜ™(Å}l:Ò>ŠQ«¯Ä.ˆµVËemÉ9®vŸ·{£¬ÂËm,1°ºv@ž–µ ×szætܯ² KÄš9µ gXPcæ…À+È.÷ÿþýâ]—c¨„[Ðì5p¨­m€ÚHõDlÙ>?sé•e82þó§¶W¨0Bh),¦£ª¾çÂo±íϪd—Ú~½ÝÙ([‘q<µ0n4ª¨LŒíÒ_‹Ìj<Ïá×»{ yç›ýO!Df‚Ðñ„C&Ž9—”â)+¦(枨¢Mδi`pÕ%-ãË’¾$ñÈ4ÙÒ+ñC ö R3ò Hνª U h2ê~£cL0ÐDŒ‰Úpq hÖƒÿïû϶VèJ5+’Õ•šŒ~€KÉôu¡qlbúì´`ðŠ{«¢®U)9Žttbs™ð²Ç©ZyþÛåû46k«¡ú¹uB‹3qʢȭZyøÛí½!ÖX­o•PíÀ@IT)ÔC&0ä~saåàoCO-©¿X"ê±ÅMëhn‹è½‚ûínðï • ¡+¸ÉN*üš’‚Ü‹&]U÷´Žï¬UIÀÙ‹˜—ꉋBÚ[“nˆÜ5um\Ÿ!9ïÔä~ò’!rA•…& ëØïÂÂUF…èa4¯î4”Sa þŸO ­½À»ÝÓí×’©Ö~Ö¬Ý(î˜ÖäÕ“P‹)‘d‡èû¾ék¯þÚöÏ×®ÚLk—ÞX!*ª»¦ä[Ô‹0¯¹J…~)!­$Q‡q$qÊ+†\™)1ÔvÙÓ÷1–-«Êy´ò½µWõ\Ç·3ì•RdêœÕ±ÐJé?uaqâ‚K‚ï®CÞ6[+©à§²s]lK|xµ`þФú +ÉRñÞi»9ß…rÀ:<p¶îÕPï7’¦¾ «?5%Ðħô ÙÏrpÂÍN2»ºûšö°±¹¨tÖÝôêÆµ€Í9Ǫz$`I½VWöq_,©t K„ÓCtií¦8ØQ¹áÑjö’èï´žr €fúc€t°éÿÀRb~¬'š:›xÙëý»o¿_}á-ëã©CèMç²»œ j'„½È‡4ƒz^ÂH9ñ°ZщÿɵŠ+mЫ×ÙÄϼæZ$Ïc €ûñŸ×=^åßÄ®¥kð‘z­Ìàà™)å‘ȃçð¦ÒÙùØQ”¶‚:ð;_i8µQüwÕÁ­ä½¨ÔRW3Äþ¼{)’öˆ7›–¿’mg<ˆV›ÉÀÜY"ã@D)xרh^R¥B¥Ø9;× ¶ öšFØ¢qS¯Tg†LK•8&2ßhÀa1‹{^yÕ„åJ!“fóÚ!Q‡ÈË 5•ØU¨#Ø¢ñþ¼Âè€þ鸻»ÉÆ2 U gŒe¯Ï¹—± qº0¬t˜Ë8±2X¢•T¯{•fb˨x—l¦ -5A“¡Mþ…£ZFxjL¸“näõ¬¡äc²Ùûh2¨´â}3®}g¬ý?Kjûß¹.fK”ió˜ aW4‘yžÔ ¨¬LP ÍÛ•ãç+Š&fM×% =vZ”ض ÌZÄ^g4NWÜsõVŠ.)ˆùÄÅylµrI¯¯61Ž¡ÞÿŒw ûI¢ª˜l óKEA¢1ت燴Œ¤vGF0)Øš?B¼Š4DÐé”Àpr0‹ê×}Â)/à;±×< •žÁi³óììžëy=Tn¤®)r…IDŽ$µq…R÷¬9·Rp:0ÚàµÈ T”#Ã5%%É1¯ëª€_Ø<¡¤J' Ò…³)³BF5¼Á¶ÜF˜HÒ§Áµ­ë¹'ë–Ý(Í· åmªÖ`Æ5Z²{ —»Âõ5Ñ35Ï&¦‡ÌöñŽlýŒ¤ü.a±¹^Í}Mêþ7Ïm ‹ð ³ZÊÖ.ŒBN©ÅV.,)Ø? b²ý5(°I[³ ìZ(åë>»âÝq³yº¡&â)°õÕØþúXbÎp¼°Èƒx WÂ*?“>n÷ôw”¥0£©uŽ´ì³ó€i‡.šw (ML@Ÿ|Ëä'ýbh%ñiúódiçä³ý—ì„ 3„l33u}ŠœRí¥žÜÔvbäT^MG%øE8ž;·«¯{kLi¦Ä!¡™Dâ½›zjµ÷n0ʶK »hÜM÷¹z/Bê©·ÃnÆ´}0#€º{z¾Û†#Ö°*BV;?v+GìšgižÉ49¦Øtɶ)›*v¦’[­'7NijÇÈö#¶n¡tëÜPz¥(\/e7#\»Ÿo‡»‹Ë:™èZ6çyÑÎá‡Ûï·3Ù'ÜÃc“Em.W,ä˜6ThêÔ§²â)J3mKª.\;¸Éà×JcÆocÓônR¯ܼ¡äš,‚>$vÄ¢“7Tµb,áK®U–$yœדm€iâS«sEY˜4‡ÝÅ­­â# Ö=讌ZÔÓiÖ[dí0-õ:Cðy$œy¾­öÕeõ@@°Ëº-§ÅË^뛢lªŸ¥Ùödh:Ðvá›n 0ø­€¿ÃÜ)C¸UÕCùM$wRO“gè:ÂL½€ß—2VC…^h˜w•†­5=‘i×Ù¹ôßÅüyŒ® xµ{öJ:z Ò# ¬„éð`Q¢%Aia«”ŠÍêÑýР•HÉóv$Ÿh2ž8¥vHšxÇäÌ”ÂÈYVç7@¯%ƒ­_8™h `zMÀªhÂÌF±“¼hæ,ÕÃ(¸ÝKil‹Œ½&rÞß­…xÀCXÍ[ÎCÇô& qcЍn^浬/ÐJгž)n„ qï@³pn¦DNk·¯â X©sš'f÷tèlѳ2Þ@7šËzŸT‹LëTžÃuPe„OΞOG¶8*cO26ÊÑe¤!߈§uwzºè·ë­PMõõi“µ• 6CÚ\·¤uC^›¹¾¡¼áÌPnMf™ÆeåvDçf%{%¦©ø­‹iAé5™+(¯¤t‰Úiʼnh"ŠÄÔ€%¾S\`R¾ÀyâgÅh³¦ =8¸Oçme­KòZ×ÍK !ãìç–R×5È#c”´ŽîÍæ¬ŸÿíÔ?ílõI`6¡ˆUhÊù©xÔˆS[¡Sׯ÷ð:fvÅ·bG¶ëíº¬ŽpŒ±ì MhE:çE®0t.)ÃFëm*fŠ«‚a lh5¦ J3<++[¢4Žz]äÌ›Z?ïÍhÕ€B$6©ÀÅÈu5ƬT•’Ù(&<9°5”H› U7°½Žä¿lއýŽ–²/aο%ûRÍÇÊNìS»ä ­Í÷½ |¸õY}êÍ4<¹¯r3oÚ¦y;ônË»‰ 3KUBH$EÍ?=ÅË"xCšµFñ—'4òíÃæó6ŒIâåê…2—LæP#p4®fZ†aãêF—&ž78RÏ^L(ö±²´pi!SÄ]aºòF-ÖºòfS¯óùíÞ̾Ž`ܤB笻RÅ÷ŒL¿6õø‰RcmäÅ÷ÔÄ@5î7Nëéž²ò1Çù‚Bé@_"ݨ*d"ôè˜UBr"#¯Y]éU|¤|5H¯dê’ÕÌz6ë„OÁ_ ⦓C¥è%ðÞ³n&C¡MuªËÝ5f ¼!Ø5-íy#®g2N —‹Sì?©×•ýnóq{&à­ŽŸâ@;òÙ²”öb…¿F¦:?ÐŽ80>Ôxø4k …ØŠ|Ä,â è‰¨2$ÑCöbPo¯Ef39P¹×"‡T®Å®ßûÎO´/¦`|µØy¥ÜKOqçy‹“CççÆë0  1œp/Uà ¨טè×4w"©ÒÁªiyfIyKt\w޹Z>”Ömæ!ö»1g((Ñ9 Z"ƒ K3„U"‡¬ e6Q˜×sýî)x¢¼«„i&¶B¿lˆçr¨ ƒÎ$‹ÔLZŒ²Á|®±ÞM>W:>›ÖÛ\š—« àk—Ò'g&Q,úI±h©Þ„DØË Ë<Nfí~ﲋ Eíu½ºçÛÍ~÷È<Ú+$ÿ¤$°œÒÃì°¦#É(;äHI™Xùq=h¬Ç‹›ÖÝ`®ß‚Øëž;`Ø"XœQÄ`DañB4dÐåŽN•J›Áû¬U XT…±}‹sæªu;^Ÿ¾š¡Å2Â0›fËK½¦z3|.W“Ô%—aí÷ÝŽ;S‹LµÌcêõê¯0cÊtWH˜¢ŸOl›¥Öã@=Ní¶^cûÌÇE;ÆÖ¿œ—Þµ‰ìµ=KÒf+˜&à_¹$ü­Õ}äCÃQæ ÷ù#¾…E£Ë\ õð˜ÕôY†Úªh'´åjáH!ÂQ¿ÿ¦Ùy5`/Š»ý“tµoO×(ÌÍÕœ3ÔкH. PE]0Ò„×)ob¢ J¨>ÐÅê[¡Xrü^ŠòºÜf4DßwDÏ Ã•Üv××p t\?ÑÉ OX° )¨"Xyåy&jkÈ1Ú¾;ê©N²‹÷>ÕàÊ8ÑS¸Uò—swL놬÷㽡PÌ2ãKÓßfñ–"ÕS)÷$w¯ÞLœRðií?È eóõNSdV“<@8çù1­{±Þ’ï^nªö…óÄðp§©~5£­Ó»¾Siö#v=Á³àå ßôzU³7Ú&O ~ë;‡?”X4')A‰=! áÉÚçÖÑñ‚r¥ì…YK΀-KWJO©Bîäø MÆ 8$ЖS“grN]H„‰)†ÜµÔEn;úmq\JA«rAFâF•8p©µ°iIïñë¹ á\jcµ¤‚]ãr©™ ª@a<~ißÖâ—äÿ­ð&i‹¼?g[P['cê`¼Ky*¿È™fûAÄ1 ÚÇ›ÕNÝ^š¶yPLÂàŽ¡º×=0°1e¡=e]!Ü4¬aY§²¨laÏ:&£@F ê'"¸ôÌ¡pžŒ²ÕHÖÐk)­®Óó”ÀÖƒéØ´‡y/V K˜Ø9ªC­‰©:W”íaR-Q”JN15<ƒÈÖßÑAþ‘Ë>ìAîLëiëø6è;~¸45ÕæDï4‰¥6¨b©JÓ(“u·Þðx_ŒGt¦  ªU?ÕFêÞË @«¹š\­b„g‡ ¢r ô«âY®ø2¤«E~oW(¡c_WFǤö¥ÿZ—U8ϨLÆÄéeg¢h9¿}D!~ƒ­"ò&¿sĪua~w¹÷¨dDI{4•dEØ¡69[ôûÎ5ê¯&²úA‡ÖâŤŭÃÐUA½³{$ÎñŒ¥fìm­äµèw¢Ý«ú±Mãâ ¶3´›KjaÛïï^—·© Ó’¦¢Õ~‚EÍÄÿ¹µµ­Å2Ë ØTŸœGmµîÇï7ï'¹&[,©.‡~»¥Æm\öxG~¸qv“¶¹7›ÜƒD@(êÒÝ…Œ)ÞHð)N‡ÆÍ>åÕ‡f3i£^@ôUð~7ØSø!º)¶Ì0úÉËÌØ$’}j›&vvôÿnïLš#9Ž=?×÷>mŽ2“©öå0T¡J¯í‰TOs³9Á@tu³ž ‹DŽl¾ûüÜ##+#2Ò#»£FsId”N_Âwÿ{Yˆíò(At „¨êB¸ÚÒ« Us7±Tl¬Ä×:BŒ¶ì[Vá>®Mz‰VՅ΄L /„I)\¢+08v 8ÖpMU';(±ÄÔO‹Yàkk7à?­ÓÛãÇ¢A@ÙHœµSiÍÏip“Þ6¨ÔÝü6JÎäL«ªNèKu\àøDõóùtp Õ»k¸‰ÒT¤ù\ÃÇe¦0™2t'zdi9žÙ›ôãÒ#ÐÒ.|à€héÙZ’²+‘ýLfýj&²~{(ó5ErjÜê¤ô@([dvý¨»ÊßHVcõ]Ljädöž ¹@À}ð·Ò̰"àYÆ:öp2ѯ¨}ûx<]@²+†6 7Éh§ðH”mÏ~r¤PÐvOé—ò;=¥€ºÖŒ9¾NæúŽE‡Ç_õlQ3ÊmØËnÓ™øUC`"áödæÏ‘wÅÛz™·sÉ#ùÓñž›¤Ekl9››µ~îèÙu×ÏX8úã.½pûk,DÑDk<0‰Çªb«´NÖ‹è17àÁ y%ÒľѶš òª¡@âÝ)‚·cÑf§rI¶*ºÑ³ Úû ×j:ÝfÄ«£ÚÇk2c2JŒ*à’Ä!gÞ¨^%;ñµnxœ“¢7¤.³3ædõÞƒ@ÞQy™l!zAýƪ­M— 7fÒ÷ñˆzÙWÉ"F‹QJÑç|T@Ctb™)4÷Љd»»&õBð}Þ>"ûO05¢½éÌ[ò'i6è½ùów»2éâGp{Cë¼ö  ;º=.O»2¦ =~ºÌ¬PµIº”0мêN…üó Yn÷ö*sÀF”{¡xŠAt)¶ä®õLeD°‘Aðe°Í  á|aÛ–Õ"&4Ô,—uPËÞõÐn#Ij-‚’jA gÒ,æx@)Áé<áR©¾ ×kÁw/x1Êꈊ+ë–tIñ]ª¯îºÒÀ«tÔß ¸àåºe¶Ìd’´ø³2óé»Ì@wõPæt´¯¤–¦öŠ\D‘Ϊ"“J’Øñ<Ó:+±sJw–l±ÉºWd«Ò±»'¸D°­™±2ôx6’ e¥V¥f—^ó‚ݤãîŠÎFçÅ:YçJ‰A8wlSµ’‚ŸÞ²dŒŸ®Ü‘vë}ƒ-ñ&‚w‘^ rg£­ 3°\d_ù‹]i÷"BÒ!²'gsF-Œ¢³XÊ d9 À–/eÍ–œËKä™áÉÞ÷iÂKåÇŒA5jm>Xq±ÒéU­¨H‡ý *.’ jšc/êq#ÙXfg)Åe•Ø·¢ADu:øOP]*8{O„;D&É®cåu“î=î¿îþV|±D \Óó=ÈT~‚Mí ©²Ç˜Ÿ¸f’ks/¾žˆÄ–NZ"¢KEÆ)ã­­óÇeÎZ¢ÏOƨþRR™qÔ’%óÇæÆqNæÍG£NæQ´³L;©±#„ÙêçÛ…Kž®HuÙ“¬¸1)×ÖL*®›XP< T1ð„@ÚúÌ‹°Ôîùjàƒ’ë€#¢2Ò^ì°`›pûÔjqÏ5ónR‡´<‰As Ø¿\èLŽ«Gô&#Ú½rÕgN øÎ@¬¹$SGíÅ&µ h)ewÍŸo“íOÔ°O¥ç£$&‡H+pçM Ãr¡ðJBXàfÅBÏ€½r%#†Ý&cØŠÚV£=èUð‘D匛IêRæ¹¼“é(Tx=oã±¾ ÷ª&­¬x2 —´bÛdTüÓéŽñ·çۻ‚U=±Þ³Kyæíwi§X‰ WúhA2núõš ã‡X•^G¦‰æm³±´èƒ¿¶M†ÊgB¥nêÃÿBg.8õ8å9—FÌLÊÊ¥Ôꩇy›Œ€;ˆùz öÁ})Êî 3ø§«É0ø§Óñîpõx{ÿû˱°¬[ýô%-ïº) ÆžeÔ”Õö”!3NGØÖ]!ÕD°ªýê‘À­¸­šdR2l™T,☠eŒÈ2%%áÏ4 a²MÎsý|zþøNC¾4‰q8ÇàcÑÔÇƒŠ‡Ï´¼êBÀ­À™±k¬ãöð©É6EMl‰˜$(äÜ‚áT9€mª1Ó}ö'#=Ûd{"8ʸûx,šÜœ8u«ÀÍ…q2K³œ±åà{–äxõ’Úà§“¹Ïø]Lj·Ét1Ť­pÇ7ÍI =|ÛtÕ™‚t5ˆ<Û¹DÓÅ:‚Ýhr(ÒŠdêwݸv ¥Ðè’ÃF¡B¥XŠY0(–‡°Ê¢˜LO(EDr2L\ b9ÛëIÝñ:ƒnØGÆÉDÐß ¸˜|™Ù£¥<Ã@œ¥ÉÀO—:õ‡“ÍtëX×®sAÞå¶r©ªÞñ–0}µô*TŽëd6ñª@1ÜIbš¬äúˆåü!„D«ý\šÏIQM^C„ÓÞŤ•HgJñ„?³–š=ÈÕWFDT{’ñ³=4Á'm2ÿ•n`‘G:™‡bZE®’ªç3ß§&¹’Õ! ©ŒŸ„Qì;à–m×_CDËÚw[öÍØ ‡h}fÒ*Sl{ä¹vVMM%ž³ì ±,.üŠ-Ù”óxSÙ­^ŧZÉâDþZF¨$xšJ„Alv’>•èäQ±.˜‡þ ¾MySÆ„Ô&kzèÏýÚôÅTa¶6{D„ð± Ýù¥n”«¯ûEÏ0+¶ ¾Ë5Vš6ÔóÄ¡¹ßù´ÁbR‰.H-oeÂÕIa£%íZ€VÙ„L)DsÜd™”æÜªÔUWÙù¶UÀt¿˜-À»²ì&¯¨Pbë¼æÅ`Ñ ÐÂÚllO]W|êÛˆ'Pð2#ù†º"i‘ï`ur©D…¤›ÉM‹E › âN°íGS ‘é»Wm2?î¨1OÑ© ØÁóà9~”ñ(nk‹ºÖ6¦uê2·Y½\¹Ø¡ï–áJª“˜$žO/2é_v¾ýepªD%Üý sf•´}0LnÏ|#᫳Š/+„Äꀘ£^ÌR者¡ÓLsŒž?ä˜^Æ×4wBj]ŒÞB²°àZšM¢K¥ÌŒñÖ=†Y.XYÕlÒHtªëî.YTð Ü‹ÉwÂåƒZÆíÜ? mÜìÞìŠg«®¯'Î kœš]²š1©D$–huLÛ¸ꡲº¶ŒIŒ2Åêt$D©îDÊŸ¬#ø¹³Ë©ÃJRö@y#j9Ýnú=°h"Ÿ¾•]YcþËÇ÷¯¹bHf°ÂRvvÉ‚BÄ«­PŸiŸ££©Œ \‡¢™úoûÔfø”ŠºBÌ)Î\‹*ÂDJëŽ9Õ]2My¸}|»½¿9üvûðtÐxóÿñî•^¹7XÄËYgÔ'™¸"õpöIbŸžoo {óÕÎÕÒ¬@Ì8 ‘3†YÜ*ƒHC¡Ú[Ð/ÈÆªØÛ:®Ä’Kµ]ÄŽA%DîA>cYVÅmcž¿eºÊŒûRÒNyv½”¥ÔÀ€—Ò§bÐnFÉdL™sÜÜñôX8À£ÝOö2¡°ÛêNG« B·×tl™)ø5qä!—Å ëî^ ~«UÝ‘í×#<zŒ¡ ­C7÷§Ï…((nàre9qœ/¨¬MŒ$¥ý›—+’8%m@7£dVæ´âáðø¶==`M?ª†’͉xëMôŒ{›¤:úë•ïÉ”ó5VŸkÊ}£ÝuŽÕõ‚²jøÍ6Ö:õâôËÁøoaW)ŸÄÒ¬&Ÿˆ5d ¤–Ÿ5šEAÀ²19Å BUíÔ{²ñBuë I òÉ’ ¯ê ˆ ¾Û€ØÉ©§ãÝëÛsá-,½±4ádƒ¥N e D³Œnš,S^ª†•¥10U‹G‚‚H]Z g|Åm$süÍ(™ºw÷r÷||*ténöFúú}A¼”VVû1Õz$ eZ«‹Iz ·ëµÉsv[—V•wéP2e ØSàЧ2‰&# Ý¼ÁØØþ\6ä@Q·"XzPí;_ËË+çw_^w¥fE£|Æl ‚yͼ”dˆûÙ¶[ögÖѵ×éÒiçV•d©8q;!­Éœñö—»RX2}'Lš…¶šùP¨Êßx‘™Ú/©Q¸ ¥ß,‚ØeúûòG´­=ƶ¦ù“ÌJŠŠœÉlSq2óðn:óCå•ÄÁ—sšÁJÖiKGÞ_¯â_56mdF’êíéþMÄ[6Ò¬5Ò¥mcÉî¥jhXYÊNr ,{bÄÀéNdN¬—UÙi—vôh6£ds»Á¢õÑŒ`ƶ—¡>«Qf`Îv.eìMOy'k™Ÿ³…’t+ÉîöÝIÊ¿)W­Qóq=VUI%ð·ì6Ø&VIQ0ðÀ1Å¥’ª å Rz’Ðd‹ÚZ RBɬ—ëÑ Cãç|8ÍööO4³GdUWNöá7£d=äúöõ¶H”žxsYç ÄÊq· h†Nܨnÿ@“B@j¾øAÿQc§•Œ®MÞš(”+rW? €®W·”~ƒÔ,›VfBýsÍŒ³7qšþ‹r8q=Žwnpä ÞîÂÛ}¡ÒÌÄÈymv£­Éݸà»efƒiJªÒ‰Û¤(k+1q35®`‚CêÔždšë9T¢@R<Ì„Y`…g_U}»#’¨ì†àÈv:mÆÉUÆzŸŸžüo™ùÐj*^Ÿ×ˆ$°½g‚J`¨e‚í XO¯;uâd¨ÑjŽ*•¤Uù‡Ñx-M>•èƒë<Äz0‰¹8œyÛŠÖfÖ ‚-2Á匞–N±ÉŒóþøòTœbhn°Â¢u«c ˜0ƒRÖøÐ=lÃI:éS"Z“9gEkL ƒyÅ•|„A)c84…f³Ê|„JÉŒ!¢4™<ÜÞýz|,¬B¹r7=SC¬ÛKö^¹³‹Ü™YnýD)¬€+VÓÝ/mÔLMqÖžh«c_u3Nÿž=%š  ³oÞÅb þ‚â¾Ýz­Bá°©@2æg¥áýíçBps»qM00aëi6PÄ~›Òox´yTßeÜ5ÁsjV,{º\0N¦ž'rï²ËˆºmDî,C™ô¢ˆvYX±)%IªÚ•ý‚éHUšÃ9|BíC"5Hf~ï+ö¨kþš[ÑkùÈv'®Ž’„.ÖÌ«bÀ©iÀcFù“dê÷þùðéð|x¼+=gÁ© ,/ |CHð!Ç€©<¡(“If•7gôRE€:}'ÖZãf’Ìúš,*ÑÉ…ì)D–9ÐRƒ?òŸÉží™>•jCÏ-h1–UmMЬºª#™N˜ï/ѯÆ,l’±”h‚5ßÈ9Lhð\÷ÑH&‡¢×ä0ƒŠ’: 3!{ß• ‘ÁÍ$‰ÉnÙË9—hž´Þ¿ùß¾ùßüóßÿíßÞŽÛ×ß^«ÿS…y”@6r¾à…ÅùOÿýŸÿÔ'­ù–L̯aì÷O‰ gcÇ9¾ÖÃÞ%óߥ¥µÏŽ JæS†YׇJŸÆÑž÷ô¿?J[§¬–§!Œ$hÁ³ üº<\ÃZ ‰Ä€ÁŸ]»û•)×D¶nšGÓ'²)*Kä˜ÏÕ)¶ä9!¾´*6 |8“lì l&>3 ˆ|9¾ oŠã±G>¦ãÖ–T…l„EdeaûN¿ã–TG2ôØ5R5ñ¹l›+‚ç—Ásò¡ï:ƒpéÞoÝU¾ë“¡Vk"A@猦ü@eïsÙ£ï…ÖÂÁ=SYhKõ>‡`ËMs÷(´a1óõ„ðåÓI줴Dþ’¥Ï]1¬›  %ÌâÇZ_? òLàXà~ãŸiºG %7£ºTArš\ÎÇÉÍÇŽ€ÍÔçuüx,ùgªM´0 ÿ”Óµ¦ °/*ŒÉöp·#éãº3—$ƒ,P9cr82¡7?÷î+|"¢:\Jõ!dõ­Xpç×®jÔšƒä$)Y0_diÎlý… .My«8КTúT'МÍÛëëéñb{H³óšgŠK+Ðl.-'º…”°É%¦Ïš­Ÿ:ˆèR#š#×-Ò|°+çaÚ6¡D“Jlæ=™Fº–sËÌY*䘵¥¸á9'蔹‰‹©½\fƒƒ ^Ìb.Ûô©s@‘°K£ ÜAרXäUüLe ý ‚KĪˆæ 8ÔR™E8=µ}X«t®¬lÍðÔç{¥—«®ÆQ™²]Ó…î³´´¦“Ûïêì2bµož·÷Z#ksžŽ!4§¦>ML1¨D ÄMP§²ÜÄœÀÁVz…DÄÙdjR8• ²¹{ØtIÔdø—ØPã]1íñ2—’I>¾¨#Þ,çëÑHÅžÒg•\ÉšÁCaÐ?ÓêhȽ©ð}PKÐè*Í{!3` Eàlz¨ÏÕΰqY f2÷m¹~ÎY¡ì%÷VÃl€ÊoèåØT¢Ú‘©{‚Õ»ÂÒµluú€ ÂP·+Íì¿ÊpÃ…ïH’y¼`\LÖ2Hhm@(ú(®ÏJYå¢é÷XB[+(¥}W™Å*ŽÿÚv¬&-?JqymHæô .è‚¶h–,1¤…,šÊ¢ƒ¡ ìsÈ{ÊœIªC—OÑJÇF©DBß\‰(™©þùùöéWY¡+aŒ–ÈÇõ²bê•LÆ3‰6 Ö‘!U¾é„2Ÿ©;« ú":KÛÅz¿üV–F\ŒG†Ø5ê1÷íï ÎÿóÛQô§ÐëJÅlŒ©ð»)ÑìYð­í>Amm׬eò{æ ®X,3+¹Q·¿‹E ¹ð¾ˆ“•EÒAm»RóP‰æÉš,rO¶IZ6“ªf@]ðÂ& )§¶­KƒEÂ!‘·Å!Ðê ÊVƒÄÇ)GWò¾WÄ|î·GÌIÖHN¯ÇO;Y¡(¾#¡ý¶³P–™žŒPaA‹5hÀê¥Uf¶’¬²š¢è ê§÷‰ó¨I¼§Æ“ÌZ$Û‡Ã}1ÒKaƒYv˜R-2íW§å%°¶“ɬ×UØNÎjoË—QIãǪ·fE6`S&"›ŠCæZ˜•7ËOr.›ïl›â³±kÂOÌ\hiZ3¶YRÖS}è©CZìñ‹ÀptªP2$r º¹}ûX¼š öˆE V ƒDýÆÎúç°W3ÀÄþöd“$œ~&X/¥4~æ†ûtZä˜ô‰~GéįèñxE…Öà†‹ 8 û³*PZ@äd¼$} §ôšÐ¹ê+H×'|‘ *…úxøå­°u ä²(TÝÇLÀL™ÏN±´ÆëÌÀ§ÓpñcÕ_cHõˆ4¼‰@:Æ©ÏwëÒ%ÔHßnMŠ.¹8Ç'¶ý{m™ØØâÅ eKÙÃTgýrR\ïLv”³VYt‘Œµ+Ezù £¿…Jk—eÕ•µ”"Ñ=Ô˜³ÅƒšOÜF;pnß›|’ùœ/Ð%mw»€2 SÇ$Ý"Y:þü2ÝóóüÜ*ýêQ³…6ë\¶ƒZ&VpÞPa„7Ñ¥¼0,\$ËÀ5¡/¯Ï‡Û‡J¥‘±&¡$8©„’AZ³ŸŽ&U"J“%]¡ôétÿûÍÍÿ~9ÝÿÞúW UÐÄ‚R_¾ö ‰Ýýñðó×¾åÇ?ÊÉçódonîN‡ç»’¯_ˆ Z£ÈÁ·¯2uWÑINçÄÇórrïEß«ÔVÄí%iõM¿4­Ÿ>±P_-§”fUr x®¥‘Î(éÆxÎÃÚ7îÒD?=Þ‚ròÕdRî’L+Û†QmSÛa&aD©I”,zIŪ¦“)WoUÓ$?þqÃFGÍ—-›I6­$YÞUµˆ« È–ççzõ "”$ÛØÜ€9÷PTÚš zŒf¢ žìzL8Ò6žµt5|JKº^›Q•ó@`žvÀ'HôeÑûñ𩤧û‰3³©¸Ì ÝNw%y)±k9Í@ž2O»¹3OmZÿþM!™Z X‚ÿH$ª^s6„*v˜“àÄv¸ŠšÕ¦£&»›»×z5áÄÞY…µ¾ýÛá¹”L•&·­Ç#Må:™¨3é¤BR%Ò,™Ót?i¯‹ ®anºßwx½ ¡S3( ˜cSŠ[岫µ\‚(t5.@¤køŠ96›0Jêoj¶t¡ò7¡îjù¸IØÇ”ê¡ÿˆC•Õ9tõø»\²+~'bÍæ&(ÜJ*‰ëLµ Éž€‡÷àŒ•*p„ÙlŠãG"ÈN·ÅÊíIÕEÇ”= =*…·5¡´S/X8›P×U¸Jz1©.ͧvÑrÑmlKÛgÈ…t•%#v?j/7TÕ‡´êMÎRÝu[ÆGƒ¯ ‚H¦x·ˆBJâÌL¿$$A TSf’Z%!©zÜ¡< ÈÝ4wÔéδº1ßõ8Kª.3`V¸ÕH«›²tù»;&ôwKïþ‚—íOÇêÁJp§æ&†ƒÎƒqÙ*&»~ÙjÛ3å·áÌÒ;³˜Îû{v¾¶¿ØÝ½ŒÉÆmZO¾`k‚Ð .l‹!ͺªï_öÉó®#©ðy¯¼Íæ_ÎÙ“?ÿR(Y™à“·iNµ,sG“è‰ñK€6µ©õÇ\B¤¦.ßíZ@G]b¬ŽæßŽkåÎú™ú/ gs(ɯ¥cXÑæLî°º£)—­ ®ÍyEw½¡ §ÓÍö¯ïÿWI «j@§ÛgzIç­'ñl2'¹¡/?!ÍìD*ï=ZLæîþxõ—r:¹¥n=mP_Mq²…@”K|HË…KcÔ–«LÚÔÊÅéIÆÔ+±[ù8;&öÃîêúR´NØx4¤«Çb3Įآ3E+—0µùBŒv™2Õ×x–É6’ÞêC]`ÕÉÙ±«æë&Q“%“òø†‰*Ê*fm<“¹›;Ä{öä‚÷âøÇ®"/˜ŽÒ ¨íÀŠíu|Kº·6•d[v¸:÷Ço-ßÍyjGç¶)ÑÓ©Ø„Í+?ÐÑ &_×Ù'Ííl[Ž©{¨–‡+C‘Òú<(înOt|ß©×pìc8àèšI¥¸ßyæI{¥5*ikb‡”–—;•Dó¾‚V¾ …•æ ¨ v.Ù‡Dï‚’îî7ÝŽ\‚z½”2Jž^Ö1{ßž±jz_% G1êq­Hq½3ê õÛ}±d5}f;ßj¬ÍÀ}1µ°\‰®sçÜÁ‡t qYÕDwù$* 8juJº#ÊüXÒ)ዜ Ø´û¯ãËíߎ©20/b²¼6 ó脵”!,À&Æ%†™;·¶J WÞ5ô¾—‹7¯‡—×—ò7À­P\£Y(£Í“óPr‘Å Rüs7Üð•wO­?¼ýr(6Ûù¤‰›6=¼0-ò>Df{㣪}ÓWQÕË·®XçÓ¨~ùÙ“TÒľ]' Q…ñæÇlÕ m ¯å©ÄÁ¼Y4Âxt6•®³h¦“×»ïøð×ò¼ƒñt3Óš/ɤڄ×E#-·1ÅŸÉ=X4’8ÅÌ)7•®·hu‰Ööjû»]¨ )kô5PØ ,c"ñôbÄXtÏä•s× £óºzî›*,k‘«©Öe¨åþ»åÙ&ÚƒÍPKç>àWl²YMÎCzî6UhÖ¢EÞ~x÷þ‡wý®D¸ ;°ÀŒ¼!ÜÌ™‚1k…Øt†QÛ++ÍÀe*xÝ mîòã‚Wưµþ ßa·©b;Ž”4»[«,±‚ö%úè§@’æs›ÕNH˜à“¢ QÁ/i©—Qwú]<2˜©Q§A·fQ8ÃÁM†ì¹>¾ìùpd‚î_QHdÁf“D9U“Gu ®ÂŠr¶•SœÝò÷Û«…ã×®ºm$80‰toDAPf5rP(Ñ­÷n!Ìè>žŽÜ/ìzOeBÑ>ƒEŸI¤*µ‡Sï?–ë$æDxŸPð½^4ÿ8)ý~ÍNäTcÀèàÙ®äi·kaõ׋:ŽˆRßîPøíïß}·û¡ôË{Œ¶iMÀÖ±E³fÞw[ïvB¿ß¾/¥PecßÎÀÀþŒpf™ûÐ.M×µ¨ÑjC¤Ø¡ù˶ ·áJu?á¸NåÝ6Q²u¼Qè!sÿ¹¸‰4Ú.Øù|ÈH®½U êÓœBy:=¿Þp*²`q"þx+bZŠE±•6‡îœhWèp.K½JA ¯2‘xKšæË§²qÜŒQl,›1üH`ÇâÈáK#Úæ ü¾xû úϹ5»{Ôâ¥6@㪠ƒžYLœ¾ª-ôB†䨙Éær¾$æþü‘#wDK)^®Óë»kïþ¼{vF©ó•ÌÑžn^Ë3[iÎΫz#I­è+ dÇìµwQ׿õùø[)•Ú–]šÀ,tm£!»Dþ1À‰ŸÖL¥ül«ºÀ@¤&2ª2æ`ݵÏ9Þ¼?±œñþùÄ©…— qÈ×.S%ÆKmI#CΉ(æÚg÷¿fñ¢P‡+éZßN2˜Õái¯Ù(œ˜ <õ?çä2?nï/8+gUFØbå='V¢kCPÏv¸ÓÌÁcÎf>;ïãR«˜ºT¢š>  ”´C¢­¶=nRÊT÷Ê䱘%ÿ·E"õ¾) ó‡çÛG€Ôek¨Py{ÄàëÌÕkywrMö‹ ¼V@C(£vI‡—54^Äþó“ùßyÒ{–‹•†àÑÅ%·5¹VZË” ³#í$ëž]ÜqS\ZZ’Ì¡«(¼óþ,àGP*bê 5«Rä0Ó ·M! îP&µ‡ô¨ªɸUµP$-§Ö@i·ó>!èš°iPÄ…ý厼ś, ‡IÙ‘¶^”Ó ¾ %yÛÑ¥3Ò¼sZ•FØšyÅÇðAÑ[q$àI tó|x9½±[\´ª¨C,ÒGâ Lì2sbF¤pMÕNe°Y(_ÉÌNžUÔã±Æ$€>0~*¦Ø{ðªÚ”,™ Ñ­U½ªh@À {ìhh 4 jD.ü’ŽÈXk‘ñ¾²²ó ½$‡gÔÒ–Z‡RgÎL€°%þ¥EDmfå±Pk·ÞJ2+Š4¿2—!‘?–ƒ'4™QËF†1ÉÃûº§NäFV1|HàÕ§O\ÏÕpâë#¥Ñ­$ e¬Ñ'¬~S (o%шˆÊf÷ÔÈÔ·ÿšz7@u¤Um«|8¦¬úcdUõ1ÂÎ ‡T~ÿÓu©x\°gæ¡ÀjfõqÉŒ‰õÜ@RW}É|Þ€{÷Ó(÷£Ê|†D~÷ã·Ÿ>½‚^ñ|(±+®—…ñn.•P:t¾Äøo-P¹Š;¸XÙŽó› ~Œª¥ˆU@ØÎúQ\•ßBŠÅa@¯ì¬–Q̇r¦Ã Yåf¸„–ðKus‘ÓájH˜ß‡€;@;ö£*säµsUMÈ}¸}ýµ„V7%PøÇuæ¦$-³Ì­îÊmU£=7 ˜æ-‹‡ÓÇ"ÖbÕ×€Ç4³Þ¤ýdu¹«]P-W"äº]· „m1{Ѐ†9)´hð"_OàãÄË&þB’„úM‰¦ÕCQ˜¥i ´h¼;Éq¼ß ä´–PQqX»å4^HüÜUMçXͽ¤uÁ/I’ja‰ï'>RiQ*ÀLdj\ÍHµwH)§—eîÄQ}eïÑé+ÁØÙ4J)õùí…éÄR?ß#î$Í¡UdˆSÔ–Ÿq² ÙÔAO]AÜüüÃóÃÛ«ƒ²),Jõø~]+Ë}~ñ$õ¾º¦‘úîñ㡼)Ÿ­\KÅ;á¤ê7'BšäXÑXR» ÚKôsxÆ¥¶}uóá \£†°ÂÆ-Õ2\n¦ªÅ´:¬ö+å,6&;3‰Y]jëYVYŸ vûêBÄq§¯Ü™)ª™hr5_Gµž êQD¶¶ý ô…6õ¨gN4ñáàÉ]æÊˆL3ó53™¯±.7(rÂ:³±4é%·gÂÙÞ@q]XzÇÁÉ¢xGE¤˜wÁ“ dÄ€?YQûÍBZzĘ†å½¾Ú¬®Fûéè8äш#ôëÑî›?ýá›ÿ@ìõÏÏÇn °HZ#ÁÚæâ¶[Sx“YÄùæš9¹"£ä'ZõÚ~k·XnÑÏýdGGe4Úíº_ é?ùõô©£”@ŠhZ±ÁTQ— §3éoÉí/ÐHÕk,›Ì›Õô’ôLƨ[X„b ƒ8lÞfЧ×Óm!ƒÄ]MiV±<«ã¶ežê]^ŠÛm“fÚ‚Sq íhÕÒ[:$N«ƒ[„A„/m½žþv]ñé©_QÄ•?+ö´1¬®‘¸tA×¶\zµcÞ³øßƒ=ûÑlò÷5¥r&îF\-Ÿcy`ôCÁ‰,cÛNŸ™åÁÙ"ÓåÜ¥é ì%•+éô¨«ç!t_í {6¹æý„t¸”ýtkbÄ€…¥ AVûYœ-êJY9WPÑ}v ûñr„Íõd¹ÛÍèöm§ ò\W»fBöTˆ®r#ÿ3mãhb²9‰C˜Ä÷Ó[r»>Tm¹W n©ï…4ﮡy5Þ &Z@ó‡Ó?¶§û·‡Â÷¬dËIìà-†Ïy.óVà2×Û‚0¤ºAÁ|´eqk¿û‹`z´¼^Ìæ‘Úí/wÇSùzš~þÜ,’QÀ³íµ°_ÚàíoßQÖÛ/ç»™ ÚŸ¿½Â ’`ä†;4¦NE (Êø€x˜)”1f6—­7M"¸Þ/Pžõ~»—jåh¼™L7KÁ¹¹UŠ·»âT‚¥@8DôÝÙA@SP]-°\ºt÷òÔ~7¹æøøn¶Ÿ^“ÕŽ¦4ÀgS!ö?¿+ZªÑÞB`5ƒ/ %¤W^ŒÈ‰R9[}¾!#ùìIê³÷‡Û×·çÃχãç_Yç,Ì:]'Ò|-œ‘Db‰­¶Ñj­"Ô³–ë•b«´¦y²Ë²ÒoˆnÊ©+ wðRÔ«©fïX“z`"¼Y*¾¾<Ëܤ– ˜n¾0R?ñ=¦ú¹Óí®£ bž"gSªt=ê\½¦_Ù…Š-´p~ÑõÙOÏoä¹EÁn5{ï§lgn€œÁ`ûb.ƒ ­ÕeûÒþþb¥ÊÜPü'zo|=Çà%gœùù“Èh­:¾¾ŒïnöŠû<–¾“ÆfVæLoAÝÊWTÂo'HS?!¾ýì'—ä ë¸‹Õ¡¾Çc\žÁ´Sex€ŽLÞciÉ%[ÛV¢6ÜØL|ü_ïo‹æºtÙß>‡À7Ú"¾!†öhùIgÈ„\ŸHþÏ¢ÞëŠ$Tù†PB艹o^A»}=|>=i&ÜÝKSó$ÅÉíDÎgu›YŽ!B¥á)Xy$P#‡(ZlèURYWÎåKØPj6ì9~J@¶æÊÂÛÒiÕ­MHŽNYɈ«¿Ü ÈÅO°ÚrçèŽ/%¥Þ {DvXÍ`CÎðˆMÝN®vãÙõf²UoDÔDŽ#Áæžû]ï¿=<œžKZyŽ‚5™—¡ŽÄ¤æ“tõš†Ÿ¿UŸÏx_Çç=(<ņqÚ±› A7‰ó´uì5áx­è7­`;Ù\ Ó q /ÙÿñöõöæãñîµôššÌJS¿çbªA‰m)=%F(@q>MÈÖ²“MŸZ—„jU&ý– BÝr±©QKï³€H©ôMLñ{ÐQ`©\òokóD?–Òª­¾ ˆ`%!)Œ§_%ç/—­z^'K”¬IØ2åa€ÿ×AÂßoŸ`\‚ ®,[oÐß³éâ2Æô·ßýþ]ݦž;»ÐS­çådF”Þ¢ç*Æ´Ö3ê(4]-?”›-IpóĘVzÎ{v!/ŸëÓZOÖUhý²XMfn8CÓ®V’%¼XnL»ZÉyG‰Ù|ûTnÜHº†âÞ¬ÖqÖáÒï‚¢ã‰æäÑœ>ïrår6Ÿ,—eUýΫ¥kø™ÖzºÁÃfµÜz»§ß5þvVµŠ®éÿ´ª¶“õܤèèõW»ZI×Ä_oVäòÝ®ßïPòjW+éšõ»ÞaÒ5#_íj%]q±ÚnÊɳ{tM…½Y­£+J/®)°7«ut9Ÿíf2-Ý8ºæÀΪRqÑåzø÷½0ºÆÿΪVÑåt¶Ÿ×¥ß•uýU­¢Ëß¼lç ·óè vbTi¸âþ»RL8ÈW›íäe6_yU\ñè ˜U:†µÊg¯ò#“ñód:¿çvcÃZM„q¥é¦U¥Ø:³®558yõ ë >Ö’÷ên-ú=*zØOÌgºÚx'0 AÛ°Ò’Õ­èçw„ô`ÌhñMã<«]¶aXiÉkw\ôϯ.;´45ßÎiZûz+Ïë$,º ¥ïŠñ^äø^Y]×sëÏ«Õâ~õéw›Ésùqµy_/ŠF»ÿyú(¿jj?®%pÀÌ/iþkYη?ƒº݈”´aí¥‹þåÅÍ¡´ì ¿ŸAÚ°ŽFQ5(i7ubDo‡ÒhÑ]»†z:ŽçKZY.'^?žßÔI`l ZØË»£>=TW{/žΩzSçc$/®Šc}çäãGùÅàŠüGïzPôn‡õ–Å_æßO^ªÒrÎÉKj ¹üzí8N4L×k×–ÉyžYfu\ÜÕ¢×+Ú_B"pqW;Ãð¡–¢¸)úY~=ºº-ni^ /®oúu¿ü¹ü´ý¯Í|6¦ ¤%m¸ÐÔÖóHëZÕyD9Ï0®5Q¶Ýö³,fý:è¼rjðŒ¿_ÑÌÿ~·ìr²º-Fo¨A«#ÎQê|Ìnû½hû‡ÊÎ/®{½¬ÈoF4â{½ËÁÕùð¶_ßOæ›Û9-[æ÷4ÞëÝJµó‹ÁhmÿPÙE6º¹èÝW—êÑ‹‹|p}S+{¬ã{Úº7ºò‡Úöy”m¥ˆ¦`£hH¬Zí–oßG­¢lkE9—¢ÈÔ¢Èå¶IËmfXÕ*„æˆi.«éûº«è‡·¯hp7ÔMëZÕMSîªß¦QUo­»E ãŒkMÜËWç]šæu~çIŠën»cM–q¥éŽÇÐÕ¥Ãm½7}šl¼#éŽG’e[+⿺l§äCY 9”€Y­ƒ=­Ç;Ȭž×‹òÓx±Z>Žg«—{ON}wÇSèUi½WÜÀkZ8´ö¤èM”zùÆZ´Êk)ßâEëy9•ô¤cëæ9x[%Z£øŽ!åÒm$ Šó0­kU2Á)zµªJ#vËÄ,ãGšêU£˜Ñª‰2/_’iinØ´Ò“‰Ç©Wm=—掶Úzñ%aXeâÕ ÛZ‘8”QÇ8§ç²ËGwlj㶌kMâGF-ríI_ª'Ú4v‹?mZWª OêzÝwÕz1_:cdÞ£­ÖzÞ k-<Ž­sÔ8b-”›Š(WÒE¢x4ÅÕ ÔÑ„ktq’çLy‰3|Zö¥ƒy¡ÄYת؃ºUÕâ¼£Šv? Ub]«bßP5]%°â(f[ת؛ÊÍVÛé¸z¹÷ö"…zƒ×A ZL˜îž¤²/Iê̱rPƒV'~¢[Ýãýó77s¼ˆu­Jæs@Uùì{R}‘÷hifôæ#[תÄUùY™ã„TÕÖµ*[ÑÿXn¦î´Ç[ת8R‡U½¸UEŒMm]«âhPõ”2ÚÍñ!Öµ*Î BªRF»9>žÚG;¯¾Âªü£Ý¤ªm´›ñÔ{ ­v öðhθéþ3£)iÊÝc=bt4Öµ*3šÖªœ‚Ä*bx°y¥‹ÒdÃû’.¿¬˜ñQ[תÌú´NˆƒöaëZ•?ŸÖ¾C—õh·Hc\iˆ¦ú çq6¿Ë—I“{´ÓÃðft˜Öµ*‰éÝåª)=sv®/.% šÖµ*³5U’, ƒYb^ë²Ûóq²vÓ’8ÅÖµ*»9ŸýYߥÄÁ€*¶®UÙ­ùœàG/%†dµúÑAD{ü~ôRBaPV‹˜ÍÙ&dX— »U‰u݇fk¶÷•;—¹”PRÕXתìÖ$ÄœK‰„U­1‡N%x»N`%‘0¤ª••ÝšM‚oPPÅÖuÚ­Ùø³:Ñhõ[ת"ZS¹WÏW’)…X5Ö•*Úü3[ãWt<6κVeµf6©^ü¬¬¬dg]«²Z3KÙ“¼²²’u­ÊlMÊîß••“ÌĺVe¶†v¿¼©Ì••’ÌØ¸Öd¶%eWNW…Çú¬}WíÚlŒì{½ýHZNÐÉvKUë>õÝÞ ð©²ò‘Yû®ÚuDkÜ+/:–l¢ªëQe¶e¹yv¯¼è@¶!J¬kUfc6 óÏJFfl\k2ÛBÅÝNÁÊEjQµu­*¦1þXcå"µªÚºVÓšg?,+idµÑ2ÛS%¬$è`‚1Úź¦e6'eA?0³‘öõü­ä ×'ÏÅeOfV%AzÝ aeZW¬n%_”KXß í6·®oä$ã ¤ÊíÙ‡Mnñì·’/5¹=;½ÂfõïØéþ“|! *a—hh·¹u—èVò…€ª„]¢¡ÝæÖ]¢[É‚ªÜ; Ø6·<-¡ÃQVÏöõˆ&·uÉB¤üûÇôº¤Ýâz&é±.CX•û±Ä0ªÑ-ûi·’3uùeÅ´ºM•ä ݪRvù†f›ÛwùäèuÀ³§ìò #Úܶsu+C€UJ”,É´®Æ;=¼1æIÊ.ß0¢Ím¬ä¤z¨vùè£ÕæÖ]>9›Våöí7fvµmÝ壗ŒÍÖøwùnÌìj»iÛå»3s *çgÓæ–8(û=ø%e›^z5ºbg^ÏB3Ûø’²¤—¬BÍn_ÓßY¡}>yÐ7V:³7¯yYÑ}>KÒe6{g^ë²Â;]*–ÂËlöμÖeÅ÷ù—$]f³wæµ.+ÂWIÓÑjõκVeEø*e×ýÆn3Ÿ3Öª¬O[ (nÌFïÌk]VŒ¯¦I¾Ënv»ï¢;IÂθJyJ!oˆv»ÔuE‹^*0T%lÐÈ+±Q­O)FVŒ¯’¶äÖ*Ù•Ò¬ÄÝÑ: ý„Q•òôd$ÁÚ´®U‰³ ”K8¥9’ÝÓºV%¾.XÎo$?1­kUâëBåÜûô*L3•,ãZ“8ºîb)îj$©ƒiýXUVp¹kºP®c¬ó×ïûPÓ¸ÖÄó/\Ìý@`Äqö®Uñü —ó>=¡}ófPÙÖµ*žF9/¬Œ^s¬Çz„y­‹g` `ÂÓ“¬Ç‘ö®Uñ •óŸÒÌz¼:´­kUæ4©ü;4YãMHUÛsЬ0çIå>û›õ8ÜEîÝÖ/Ñ4Õ»«w•õ8Ú„EîÝf}s’TþçYÃMHUÛsŠŒ.MµXùŸSd=3nTmÏ)2º‡ÃVåͲž9HÕéþLFÑÏTåͲž8ªæ!ˆò }{ŠÐ¹_÷X7ã‰jëöI8œÑmŠvG4/hZö,ùì>Ló;BÖésЬoÎ’„ç™\ð ­Ï)²¾9KžSÐ5k+±®{М&Û„((×5„XµFÁ¾9OžSdrOEPUËsЬoNÚ³wç¢rƒDHUÛsŠúƒÆä•' ®èœ™‘£õ9E&ïš[ã~N‘ÉÕ¶u=ÚíYâN‘efì§ J•¼gÞÝšOå†ÞÌ÷¹t#¼ÖeeX_vF³ÌŠ;ëZ••a}IØéË2+vì¬kUÖ<ùB›q)·d™?kÐê¬L«.›rAF·|„½Ða Z5o¾ÌŽ×e™Löæµ.+ëú’°#™eV4ÙYתÌy“pž;£;§~ëZ•9oäĵ/ Ykõ/­ç¹³ssÎ$Ü’Ñ»&«æÍÊœ+¤Ê{K¥ªNoIÈÎÍi’pKBF¬ZoIÈä…óîàõEî1p«ÜŒ%­·$dçæ,‘{ |ªÌXÒzKBvnÎÿ- Yn†6®Çº9Gêû¼©MnF±®TÉíOÁQå»7£+ò­Á.—0h]ö,ñß’ÑÇlY-ëizÍÇ*—°FÌÍÈ!w0hVö,Y»wr3pð Z“=IvJs3nÈ Z•9KRÒ«ÜŒ­o/dtç­1ªRöos3»ëš•9Gd‡ÕçÙ͸Ѿ{aΑzßÐ{ 8ËÍÀ±3¯i™Ó„ úe™±C¬kUæ­WËr¹M™„g£jÐê¸|U—Ò›rm\‰Ö(yswñõê£{øKൌkMá¹ü0£oÿx%ÉÝA]ãlg[+’|¹£!M©„>”«ƒ‚¢Ú{/<•ô ç¡#¹8¨S›Öœ$WîâD…R0…=uÝÚvJá9ü8y~v?:”;ƒº0ílkNáIÛ”JvÔæµ®ð„}¤Ïíù¾Šy‘greP7)¶­ÑgXšŒ±cD5ŠRH…]ôy­+œc=–«ç’>Pæ½_:“[ƒ:iØ×Ê™ÖãËó}¹ÈÜn!ì›_­kUá¹+åRz2ì¢*ÐÚÂùuïÀËýA=ÙôGˉ6¹Â(—B,쬥Ù\&λžè£Ø›ô)vÛ'•h᩽˜¬ÞϘ×Þ,ìÁ_­kUá|KÊ¥ôjØ…U µ…çöbõH‰—ߥÉÕB]úÀ¼ÖžÚ»‚ Ð(º„¢Ìq Z]8£²ËÕæÙ¿ ÷J°ííkeá ¾W–.ìÖUZ_x‚/ï7Pa¿~h_+ ÏîõdSnWÞ:gg{ãZSxbs±”® ûôCûJ™ÜÑ5Bד”‡gôÕÐÔÜךÂ3z½šWUýåXßrÇtg‹÷ÖµªðtÙL>/Êùã“[VØQ˜×ºÂ3eW0et…½äq Z]xÂlSöäV箞ÜÙÖŠÂs¥)•+ìÌk]áÉò±¤/&/¼·ýgƒ°W|µ®U…s)—Â+ì*ÐÚd\Òu§{øÎψe72»Œ* òšzýÅF­á©¼ÿ\=•ÜJ˜ŒaZëáäíõÉ“§O%}¹o3Y>z¿“—ÉÛï¦q­‰=ÔíéWI鋬”(ÐÖ¹s×÷móL.d4kM<®oé Ýo¯šÆõ'c÷ñFîA|[MZ-g÷– ÿw§‰#»ÅÈ*´>ž4Vaÿ7¨I»ÇÈ*´>žJwôÞ£êíY¹™›ÞÐ-w´ÙÖ•*¹Œ uRÖÖÄ툢 ìš,0¶ ­¯Ye…Kw/šœ(ûZYÌ e àšHhkkjÐêšØn”Mx1ÎV*ÐÚbD]4]Œ{ÝW¡õ5+ƒ]»ÿÁ}(©Þå§Ø[…Ö׬¢ û òå—ñ•h1ójEǽ‰_ƒiè“ ´¶˜yUM ãV÷Uh}1S‹ÎMžÝÉ9_ŒiÐÛW¡õÅL..œ@0&k9¨Diäû7¬μÏnò~L\Z7öµ²˜l…J& ‹‰L»´º˜\eSVþˆËwg=³«A«‹™VMÙz1Ñéµ­°ÙO5ZWmÝïåý˜à$hm1Sª.š/&4í«Ðú¤0½¸«V¸ûÕ¥w{!Ô¦µ‰—';{=Dʹòæk=˸ÒÄŸxôîNv!çËmI ðúÏxüãÄ{5|Îo°GÖ ÕIÚêÖÞ¸)*® ­O²»°;²^ЋЫBë“gþè}1*¿W…Ö'™‰]ØXù2ˆá÷±®Bë“ÌÄÖç=}ž_Jà«B飶&í· ûÇŸÿ¸*´¾ÈÁAçïÝ8ÒGHZa$~ï•@9ùã¨.:½Å,ç£ööÐ}Ÿ»áEN@®B³“=kh¼Ï½¯7æ—‘«Ðú$ó2õn}üúzD5Uh}’D˜úú~}²8ˆ«B닜YïÏýú"£/W¡õEFß÷~}‘Ñ—«Ðú"§þóêÙ>ø}w{JZaäô¯K»#ð•,¬1¸«DkŒtKw†ÊoÂÛ ›”ºkŽÙùÉã(þ¸Ú¼¯Öþ÷[ók†ø–z´Rö†ÙÅɉà¥ÞÕÇ5‡Ó¸ÖÄ&£$R­ÐjM›µ[{Ö]­„çj}+‚RBˆ'‹GºÔj² s°îƒ×쬢*PÚ†ì$3kÚ®®ñf×ì ¢+ÑÙQŠßÏgsÿ*òš½@Œ}­ŒsÐ@ÉéÓjQVïÝùNŒA\ ZÌëî¾Ý©s¯Ð†œDÈ««ÐúdbÓA…ޱW¯ÜºŸÏyyAWË›öµ2™ã§oûìfì]*—÷tõwR ÅgFÖ¡Ê”§·…:ÙUt’É{ 4ŠûŒ©@k“é~{ò6Äžž÷µ×|(¾Ô°­Ñ¨J½ÅÐEkõR•4WéÅw‡Š‰­DkOL‡#môžÙzQz?>žßÈ´}c]Z1÷s~ú–Ô®Ÿ?zaÞ°ÏÏé{x4ÛZwAH‘÷K9àžnhèVtúœ¶cë‘Täö¾üm{Û¸¢Ä¯e†Š=¿,¶óõµn8s ´ú ­ŽçA ìz›0®8&ØÖµªÝx<ÉÅwcýG·ã¸á8ÐÔØÖŠ8÷–Z»ÏšÜpt²­kUœsÊUÜßµ \6®5™}^ÒöçüUû ¬}­ÌìyŠà)©-Ù>$íµ­3Œ¼vaÇg8w#~WÔùTé–3Œ¨ ´6‰Åhzsî½J© §=.øKÝ¢vƵ&žïš¸û¼š8„šÆµ&^/tc¼NM´#W»!Ó¸Ò$§úç'OPš½IzY¶^»p¿¿[ð×sQhmÒ‡!m³Ä wÉþ*¨ï°­Qú4¨1- ó'uÂ_!h}i‚Í£3ȳyBfuÉ[X±uh…¼û,½xö?‘*øC;a~» ´6΀‚ÚšyB›þwÜ þJXáq5Z§8¤Ð(¬ÈxãÕ•ÄûJß3NM;Í2ê§+þ—ñ 9™¶¬Ôȃú>]©sžZM“ RÂýÃËãd[Òµl^^ñ o¨G+•ü#΂û£¶…œ€$ÒÔ£•ÊØ0”¦.“øê%ô ­S²”΄» z7´ Àöµ²ˆÑB!ˆF'Ð/þ\x ~:¤PÕ£•J4 ZH×ÉÏ\‚]}DC«ä•M°|5O9:P Äá†@¼V¡õEôCµ-ËuYméŽÕjš›ù‹áiÓR—VÑ#Êévµß?<º ×¼Ùì¸ãj´N‰×¡n90{ýûu„wVõh¥ül*ÐTïüÚôÇdY« çÍjµ­ê­ÁÕç„›ë°>©Di”ÓK]Ĥøñv™kO\¿©"­5¹AwëPŠP'½Î¡ßçû˜±uh…ϬҔ l7î§ù}¾ŸÙÔøZ‹VÉÑÌT™ð©~/®¯¦R‡VÈñÌVè>*ØïEvUÕT¡õq,³ô•êgŸî¡×MûJ´Fö–Fš:ô—í|át1ýÍ7U¤µ²?¶LlÞ{WKýÇ͸´:ñ¡†ß!u)Ž'®»ö•hâUM}÷pŒ¥P× Õq´¶é÷SJµp%J#Þ&.™Å¯ÖÞܯÏ×6›ž{óžëÐ yEgSœz7Ùû½ØŽjªÐúxGÂÖ÷Ð÷^e@÷ËEöסÆE%ÚŒr'|ѶÙÅR…Ö Jsï÷Èú”TvíÆ¬Ò!§$/é*võŒ‚î·{~¡Ëžšû‚¦ºçNwãz}J.qþ õh¥â• ‡¬ûr˜Ù‚ÑzÒº/w[…5÷s‰¿‚Ö“Íý¾Ä £ðA·»ûZ"ð›jR½-÷ [4Y­;ñ’ÓØñµh•⧃-õf[|ù ,îd}Ù?Ð¥©OŸè€…ïàGŸbfã`Lëš”øã@9~½r<[½Ü»WÁýÜåÔz]V*žÙVú°XÑ=}^ã«Ñ:eÑ`X¬–‰Xå~çX|Åz\™ÖlD2U¦1ìke²Î릙ÔÛòº@€ßμÖe¸ürL7kxÇ \¦PÅÆµ&ÿ—ããA@;ù,'t¦¦¢Õ»?¼ûû¼šÐ̳Ñ|Qþþ]TÿT>ÐßÓ Xy_^dh;®Dk”EVwÖÅÝà̹'Öµ*Yýv«ªžêÏð8}м_`¶3¯u¹U9~I …9¹væµ.3Ú¼¤ sn‰u­ÊŒ1/IƒËœ^;óZ—R^výï›’æœÚÛWÊäM‹ÀÀ”ç×I£Ìœ\Ç•hfìØ× „¦9庪ӺÍ|OÚEŸlsFvÔ¦U›ù ²sìí}ÚÍy¬S·ÀÌÅZZB[˜“ZW£uš±J $ yÏØžá»Z´J33• þ^>Y`klÍz.Ì & †‘*ïFÛJëÒLÍøv Ø›sôc'²„D­Ñ v¢16rý£i³SxĽiI’çýzæSûr€éâ} Ÿy€`¬Öv©Z[RwϾ"˜ÌÈLŽ˜d6=Øï¾óƒ ·0ð´j†„VÑÍaînf~™owÅß#[z^GÖ" È›-28™·ß dçõV?J›m¡supBoÃÿ¹ÕÛ¹f3`mœÏ›ð¾âð\œáËÔcµÙ<–êà„Ífüñò|Wè¸Ù \+àlÍüé–ÂõmÛl®p¶fã ïz¿¾h›uÞl®p¶fë½[¿ìÖuh2o¶ ·8]³ ߟÕñð¼Ù$8ñœ«Ù‚ïëãöüô¬­óf‹ÖÂ)›­9ÊÃõ·@l6 ¥*8_³=Gáýáø¬ìæÍv¡\'l6èÏ—ÝykgêáÛlÂZ8e³Ußßµel¶å:8a³aYcþsP«°ÙP\+àl͆ýe}Ú´è‚ÍÆâZAÈ6ÄÒ«°Çc‚—Ãöt:ìÕŠk¶·8]³e?®¿íŠí㓯ÙD”ªà|ÍæýôtyxØé}[³}¸ÕÀéš­ûéå©8êášÍµÎÖlÖÏmæŒóf{àås²f{þ¥ØÞa YÝåšíÁ­N×dɵ{‹&CPÙÜÐY¢lx"Û7Xi?§§n_©¦aשi‰à³^<ÓÑÀ™׿Y£±+iÌe„ɉæì9CºJçTn„D¨î‹‡5mãõœeŒPݤs*ßèrŸ¢CIj$g#HN4ヴ ã9==¯÷½¯j(g£P7ùœÌ·{-Yw¢&sv°žÌÈçd¾íkÉz5™³õdF>'ó]@&{|8j*¿F¨¼lNäÛ_&ú´¿œŸ°¯¨†rQkª$žsùÖ¯çÒî‡{.dm#ùœÌ·~Y§£‡s!kœ­‚óù~ óíŠÍå[qìuÕMê½®ìËò9™ï 2Ùóv:kq {ÞéÊXWáœÉ÷ƒS Wí½nÈHæ4¾á#4zwèm†sßÎ2˱7ÔPïde'šóøŽð¬÷jž~½“…ý#ќǷo”G=Äúõ®<$šóø&Žò¨íQ¿Þ¡‚G²“¾‘£<êȼ_ïFÁC¢™~p0².’B!µíé×;Q'šó46òý@<õëÝ'ᜩ±¡ïÏP­æ í°_ï8‰ÉçL}¯ž»ôë}%!‘lNÔØÜjÕ»H‘hÎÓØØ»‹z‚Яw ²Â9Sccï¾êÇ[½›$&#œ35¶öî«öxÙ°ßà.‰‰„s¦ÆÆeíˆkt™V8gjhrõ1™a¿ÁgÉœ¦^±'p(´ÛÅÃ~½“º çLõŠ=㜢¶Íõnʉæ<õz¥B]ýBØ ÞSݤsªúˆäŒqzzÁÅ-uÿÆe:—TÀÙêþ¬Ž´õîÊf,ã†&Ç®¾¾;Õûª³“͉ê[ü²×ž^ê}••Ìiê›eúêÐvPï§¼lNTßÈŸ×jw;¨÷QV2§©oã/0Ø`ÞwÕKKƒz'TÀÙêÛûŸu¨4¨÷RV2§©kmåÎÅpPTw-&–{Ú­N~‡ó ûÛ.²nÕ;žÃ±µ»i50 á2 ™Ôš²GDÕ:·±µºÍÒ9•âå6‡ýg}*öêS±&9©Îf£ƒš¢÷æZ›ÚO¬…N«Ó5õÖ¶lÖV×°]¿“5õÖ}ñ嬦k¶ã`WñŒ àë{ê‘ ‰ÖœM¬ÅŽcy霪©ƒÂª­õ¦cbMwë*žs5õÍÓ¹xx(öú#&ÉuÚ5lå*8_}ÿT7£õÙ1¦ª_šºÞ>¨ø¥ÓÑÃjeþÒZþ©³Ò™vpÏôõH9­v¦Î$ÆÅ2ŽÜñWïWŸmÊ¡œÊizæ|áAƒ@6'rŸPG´Õ¯ifÎåÖAYñœËõ£:.dêP+Ëv²¬xÆåNéN¸Ú¨Ìy=š¨5w6Nw¹;©ow gÎ6GÓKç:s¾ ª3S®…Êܵäi=˜¬1ç"l-’¸ Ý…ä•Íuåœ@„çþp¹ÃÙ]Æ–¡»#º çLÎ D˜v\>Ò"yý˽ÝËæDnö!Ò'µμþe+™ÓxË[Éša,/¥¯Y]u«I3œù©Â87Áq:uãùfˆcA4ç©÷mÒè g¾%d /›yg k¨M&§áÌk_&ò²9‘›ÍDú÷¥M÷êÉ=Üû¤ˆ†Zdhμö#@N6Ó¶ƒMDÓojÝpkP¿Ι¼”µä‹µr)õíÖÀéÜ &¢1W¶ÂñûºVáupB7‡©'ô.AÕ²yRù*8Ÿ›j×óµ›îú|,|sêGè¢>ÆrECG¡Ó`R#…q=zŸ_;NÚØw‘¾A‘Ëâ#€Z:ot:Lj,_מjù¼cÑñ%5¯‚óù  ž¯Í0Ij!ç$9êéZu¾´Šô>/Ôóù¾¡kÞ´òup ú¢ŽPQº‹õõ·S.| !2©ajÛ¢B1r7I¦Yå¬Ú饨<\ö›Õj½=~[!—vábá"€¬º¾&Õ¶ÝÈÝ)i&ügqÔÞ1ºä ÓFDW gtmÙ¤E­—.hƒ|NæÂÂZ²ózO¦M¹ˆ·tAZ-ܵ ÎçûFMÿ»+N§b·Z?¿¬^žÖ'õ5”¥ ê@…º1B~/Öi´"E¹Ò°tÑÛ«ˆùìu„\©ÄêÓ K$R\§¾ 5÷‚·ê³ÎK!$ šJ8£ï= ŒêóÏK&¤0VOB†¾¿$0ªo¶,]¬ÂH•p=úž’¨>ߊ\Ù¶Ï×ø7Jßî«']GCßYš)ÿKm8]\— HªƒëÑw•fÂÿ©3.œH@4•pFßUõcÆw)ŒÒ˜ñ=%Q?f|€ÐÜÿ§4f|OIaÔ+¤@JcÆw–fÊOê1ãã…fFªƒ÷GßUš ÿ¬3ç“M©„3ú®’À¨3£Ž šÕøgiÌøž’À¨3£Ž ¥1ã{J £vÌŒ:>*HÆ zKjlFy̵s°QÇGÍœ¾Ö/G¾Ë4ëÓJÐż£ŽRI+ñîÈwœfÒSñK‹£s£ŽšaKUqÍú>ÔÌ{.žŸµóŸQÇG Ͱ¾Nê{Q*©¶ø¸!•´Ú|/j&Õ¦u|äÐLIup]ú®ÓLø¿õ¾È͈¦Îè{L£Þù°!QðE#ßWõ¾È Œ‚/ùž’¨÷E>rH”|‘ï,Í”-ÖÚF<4cÊ«mxI#Ñg*£ÌQÇLj¸ö]¥Q‹Ê5^8âÔ³ºÞ;ò}¤–î¼^m÷Úƒj£®jµw­ƒÛß=µmÛõÑA]µeñ2Jc¿Û<›Oê†õ.¡ÍWÀ´6Nˆ!6;܆+Ô6°›à nUp¾„Èaƒ×!ÏwH_uQŸÞuܯˆ³&ÄN„º&8„[œÏw“š‚Â/»­ú¾ê¨›à Jup„®r¿þ¢?x>ê&ø€k œ.¡‹ÜwßÔv7Áø 8[BǸß"­©ºç%8_gKèÅ®xÆ5©õQUwìP §Lè^¡Qox\z¼ÚÉk œ.¡k ì­ÕÞ×%Êk¢³5pº„ÎQôl>2¨±\N>'KéÇãAû|åȥͫW›«€³ùh±î«è]<ål¯x6ÆæÝ½Ê,Øßì«Û«ÄÛZ[ÒKpêV<Ó˜¿Ò×ÀÕbŒ"GS³Î¾¾Ø8]Bœ‡ÏBÙ¾Zs .üVçKè¸ø¼]áᚆ$Á‰‡Õp΄îaÃh3Ùè%8ór%œ1¡Ÿø;ppéÕlâ¹ÞæŽè+àl ä±ÀÕß»õE¿2ÜKðêA-œ2¡›Ø×V¥z‘¨—àÕƒZ8eB7qå»-(¼{P §Lè,®|o©^ì%xù N™Ðc®åõ-žàñƒZ8ezù«ÚŒ'x~ÇHupÂäÞ¢åséýjƒË'Ð%÷m\ã’ý¥ÐU#›„Þ±[?Â.ª“¬\ò¿Z¾R¼uúÆn'uÔ×gG.` ¯‚ñù»ôu1ØŽ¼ËýÏ'«/û\ŠÀzȰNš0k¸’þ©¯M®6r©ÓHm=œ4!r¼’¾àQ`õÀN xEœ5!ми_êUC—h0M©¦ΙEzNµ%JˆJup„²ÅŠËCX¯A³ Ĺ:Éóúü´-.+¼I‡½Õý1!$¨VÅy"I/„n¤}VÓ&„¼"ΚÐc®"H³¡fMxEœ5!ªô"ŽëûVý !h¨VÅy_Ñ™¾ŽŸN/ú'ÌFý„@—+ãÌ ]êå°Ñ>–3rék€“ÏÉ:Å\{`ä276Àù*8_B—y9i¦\ Çz6#žs%tŒ#RÊq!A¹°ç²8ֲݪà| ñå±8é_¹„Ž x®Fç³×ÔE—§§6}.!,ðp¶„xò´mq%fär=ÖjîZ§Kˆ!Oßö›§ãá|Ô‡å.ýc=bP çLˆmR}‚ ‘K YKY®„3&t¼¹ªÞLsé!ðŒ|N–3þ³8kß!¹‘µdN>'kŒÕæ®Ñ¯C2§±Þa†S¡ÍgçÒä¾ÍíŠ@=ž¯Ó¥DÚ´ £\ÂrÙ[ëÙ¬|N–òU”p¨]ÊÑܮԆõpÒ¿×"ûÒhžâ²ÄÜKcw¯³þë|V$]ï³ëi5pÍ¥|˜ÏÉ¥£Kñ¤¾N—òe-òVŽæv“¨^ubί±»«ÙP´U§Kñí¸;|UfÜIú°vÝÎ.5(ÀWÁ[6áÛÔ/!æ¨jÌ=’6ÃM@¾²sy^­vÅçí~¥½ù7v 6Kgzê»U°zªóQ¿3'klýËú~ÆØešÅ¹œtNÕØú/ǃÚR¹l@5TN:§jlýc±Õ>´=v™j¨œtNÕØö§Ë5ÚÁ8rv4ÞŒå*Ÿ»ÇWó]§/k}[º’4+S¹µ¥x¹–*sþ?A>'s~´¦äV½Ç3F.}º[XÓŸ­tNÕØL9ÝJÜx䢀†o®ÌåÝc|ñ¯¹.|jhÆ.=O‚x®­¦Ößž_vÅWí¤“™úV¼ÉçdMíïJ®hñ¤ÝêåxÔä‹åº8qSßðRü*²®©›<4¯…S6Åh¾|ËÙä®+ÕpÎÆžƒÃéênÙä¶Å7¸ÆîõÚø0kײM^ÛKçšjêú‡ñ¨Ég‹»“¦ÆÿcÖ½jo‹°®³¦à–dUCtÜä²pÎÔÔþ~VÕä­½tNÕÔüº¿ŽªÉ[{éŒÊÝ«‹·~‹…ñ¸)T“w¦MÍî×ùušjòÔ^:×TS»_|Ãë°šÜôU<çjhy­i7xaÈe$XŒ£%ÇŠ0[EA*Ø=”® 3ëjksÛ‡„"_ÖŸ‘OÁÞì™\ÝCãÌúÕ´8íKueï×—»bƒÛnÚógc÷\mr%œÑö«Úâ_Ôë*X ‹ô•kûÜéœÊš”:ª§5âm£Z‡› žsY«RWÐ}˜ÍzÚ´85.ñ²ê‘i]m­`ÎbíJ¼Hï^Mc]lƒhÆã΄Ì1\˜Õ‰ýõî†b½£è¸W§m;w&&µNhÍvƒ8áòkìÉ®ïµ7ÉÇsÛ")òÙŒƬƒýb¦»mQÿ~ÁùYÚBÛk¯ŒÆ¥UÀÙLŸÏ:£Ê.Z™íA½eßL’ÏÉL{fIå`™ìyý©X =ŸiÕWÔÂ)Í\>CÚ躶}9ÒÄEimÆ…¦VÁùŒ©FaÜç o¸”µx,Öêq±0>*±Ng cÖÅ^ £;ÜÿN;H±¶Z=ë£zwپɖ\#´ˆeÝê[›žºAN®ƒÚÁßÅ͉:?õN[ý–¸},K¯%¤œôì8›â6£<=¬ì£=J6éYÖ šóØA5]TÏ3<¬|Æ[] >±é˲&ٜȎ£é²š(D6®ZEÖJ5ÉæD&–‚ÇÇâGh;Ðfô€ Ç¥ZÁœÅŽ‘ y¨«,פµÚ³f¨Q8c²¹Ž² I”«L.Q­’>“hÎc-A†l«I~«Å131àÔIæ4&ÖÏ2dmhLº[-§ê%sk²^ÅÓ /—RÏj‘¬ JϹ¬Ê—ªª%—pVËd¨ÑœÇZ¡¬_9Saôd’Øjy¬jÍyœ B® A?Ç­ ²§$³¬F.'q÷Ã$\ժş¹ŒÄ¦¿È2œ Iô ðØ7´v§^4çqvg(ÙÁr6Q¥†lJ,KÏÉÜèWf­èÍ6C§–É ®ZÉŒgæŒQŸŠ4·¤ŸJ$»ŽœeÍâ9—³X@¬ö'—JPËäìb½hÎãZ wÒ«<×ä|Z"×pMÂ9“³‹¸?-1Ù||Z$gds"gg’(%6Ó¬³OÆ.BkΙœÄ»÷‚–ÏL«!g#kä2›:Ëp±Jâr?iiìÉFÙœÈYI¬rU‰|²&¥~&.>k͉œ=•ù“´4.>«‘ËIœšK^Þ%<ÒÂ8 T/šó8 T=w¿QNÔ£…rF(A>'svï¯WÛì–5GËå,Q£tNålžc–¨,G äìP`ÎâlÐR²‹&=Ž–Å¡:ÁŒÅîÑbGh-­Jì^tTf™`¼XN0²†ã|‰¹jgžõÆÙòÍOÿöæo‡/Ånq¿=+ßV Á0gM‚Ë,Ùt<›t‡ƒÉdH®wÒíáEb!Œ9VèióàãúnW¬î ]XOUŒ_SçÃ"¡áƒŠkøT GlÓTñœ+·qõ¿–kóòòÞþ•ùì‰l–^cË;¦(½®VbûÛa³Þ}Ä;çÛâØªA—Éò9YÏ–Ä«BQ2mSæÝ$ÙœhàJÕèêêFÌû‰ÒËTh¾^§;Çã ¢€~Öïs•ùáørÁ¦ºªKA*î×Kå=÷{è¦B¡1ØôeÝZ™œ``=GáêLýF¹I¶˜wg¼ÄÜÎp0ŸOgÆN.~þûv@]£@05uƒ`ÎBô(‚Ev‘EÕ4 ¡æ®p,'´‡ÚÍ&´^ÓM泡÷‡#¶N/Ï'ÕXÎ!ެQr‰¦».§ÓN–#ÅÍGp3rœMˆfþñïȹ|¿úX|=ÿ|ܪ6èôq¢ô2Õr4Æß|Ùï™9Ï ›Í‹Œ¨^Ö«çõ;Hù~·;l>)_ëR ÐUr œ8•¥9J¢S:Ìg’kàtˆø©ìý+ ÃÎíãÝåËXší=ƒ…`¿Y4çAœB3䂈òhÕ„ ¿Yt‰§‡±{ãn9èLÐÛ;K¼«ÕRß2q¤Ö8±£&±!<( GØN,s¼_ãtG~9~V€ýO’ÍG}Ì}º°CXÈÞ|ˆä¸¤™HAº<¹[e±1§Ñ2uŠp΄9R”IÑ{ fAÍ¢ËEוHKÓdùœ,·%é DåkÞÍ?´ÐRžj%sš…+#éé=žH»PêVJ¢¬ “LëÍ_Q£[tlY, –t•mÎÛÏm©– ’9MÏ–ŽK4ùú\<ŽæÐ¬VG‹n‚dNûJ­Miný(Ïõ-µè×Häµ;4 ÆäM&tsf»‘³EɵpJg“hí´¬£ÌàaVv,` Zuï…3NiUp>g¥ˆâJ|»õé´}Øn šYÅi¡Bg¨Òªà|ÎVáÐ\™ï°Ø>^Žm5çÌU“pÎd,\_¨³ˆwœq‰‹åζ`Ǩ¤‡÷-¼Ô¸ãl‹,’×ïl Ö˜Êõ_·ÏÛ3Òø(=Ò.ÚÖ¨ÌYœ5¡Û.·>á‚C$;;{òBú¡;î8{’T§so!”èLÔõ—‡ß L©¿ ¡3.ɵ0ÊžýÂ.]¸éÐÍù—Ë_ \ˆÐ6iÏö•&ÙœÈ~Q·Œ´—ãz}^ ¼—E9ÔT¶×¤ÈçdÖrv» j«$ÛM¢B9ƒµš]lË–ÚËêå6]Ý&L-e]Ð+«b¼}kd±¿Rå5~_Ï×·N©A4ç±·‹ÓÿýµŒ>Æ}룚ds"k~»a´h[´µé[·Õ(œ3YcÜEvÓŠ–ÓêÖÛZ4¡õf¯©‡“:ûE·önö+ÐÞw }gË^Q'uv gÞJ¤ÎÒþò^¿¾‚$¡Æuvk%sgËh?ù¦·¼x9!½éó¦E“:{V'˜³8›$°´@q¬F.#8k5 ¢n¯»öôRlHEz¬³[©•pFgÁ²`µ°U8Ã%‹äõ;{…w¼J­…úíÚWû4p6+¥ÎæìÖ,XÃñlK,™àœ-çÌU³xÎå¬%μ6ÏÕj58ËÔ ›9kDG‡«Dïñ@öþð¼]ïZ(ËY¥¤8³Nt.¸J÷Ù$Zp9Õ ›9…+Ñù°ú`l‚¹¼Þ‚ËY«¤ÝÐÙ­y௩]éÚX¬¡³XÍâ9—³UáRl»ö:c‘É ¬µêuƒ‘WÚ€2VëíþéìÔSŠ¡µXÉ•pFkµztïÖÛ?à0ŽY~IâÐÚ­¤ 8›µ\=ºùÆÙþOˆ£©zµYËÕ$;$šNpæ¢3™õ†Ø!ÊzËåbavòœé¡s=¥Á¨?r„ Æ)%v{mEeÖùp€óÙl2›,±BÑäã‘9ÑnûŠÄΚĖ9Ã9òÁ/æÓl@¾×ëçÃ9éÌlWÛm Í1’;l”ËI&®4ÂH´‡±z2nË9r[€nóêÓ2Ä‚3]¤ìzÑŒÁâ‰ç·âtد•ç¿I/8€Þ ¶Ì±ìç=x¡^gÑ¥“„“—ùÌItVÆÈ‚/y»7‹jê…>ª¾=¹†nA›¢½ÞdL‹ntÏÅîç—‹ãQm–ýÅF2Av‰ÇìòÎËõ†ãùŒFÖh1¶ÖèçËv~\ÁÙ¢ I;tÒHÇY¹$éÕ¢‡Cìý‡ÀHO8΃¼¹4Þý뻇‡ó 9D4kgýäÂb7È-“ô–¸G€ƒq½Ù²k=\ôæ}ssû²þP·X}¼ìÖÇÞ@‰DÐÉ»Ä 8Û(¡è{åÁ™>±uÓ+àlc©(åˆ4YHu-HH½F¹œdR[Bá9Œjú R9ÅTúý_÷Û 2¼Ì×x®[ 2h\fé3Ì z>êäýÙ¨Û¥ÑåVrÖûý¡ÍѦ>U€ÉYjŒ-7Ö•V«¶âëšbJcÍ•#t¹ýüÄ*Ê|ƒ|R·?ï-&´ø1v=sáíþá ¿èÔ'¹Áä–I†ËñbÖ…‹†‹D+ŽÃEn,Óâ·÷mÎï÷IpÖ,˜±à¸ƒeA—’X4}$8RÒ ¶ÌsûKùWqºh¬G÷3':ÿz6SŒ7s4]åB¨ øþô*8âM*LùA*|_ŽÛsAÊ®Mpƒdùe²q7»ƒáx1Bþ¹ÎtØ÷dÞW^KöI,Ž;׋å“h¥Zˆ5Ba„r†iüçšžL£:‘aýsºQ4œNQ¦Ònlë(p'¢Y0gÁÍbc%‹õ‹VvfÜ÷p;§YtÀ3œŽa¼»ËÅé¨qæ|9œ˜ÈÐù®óS ,ú)wÌûcȇëJ”_&›Žáïà &‹…1È~>1÷b‹ŸÕ㇄BGuB9y¤ îUC;¸_vcPET?ÆoL ¯¤7Áu2rHAݺ`jǨ‰‹dõc·ž~Œ‹Iåúí¾;ZAi=@K)‚–&¡YoÔ`ÒЙf£ll",;ÏÃ]ÚÐA:„&I©úXöŸõÐÇi5çFu——ê4fº ÍÅôBº®´ÌzÓÅl‰ö»Ñ9ß½E€¥VØ ›§ˆyFÈ7ëåãq.ñ¬w¸ã¦á­lRï7Ùe"¼6‡…™¼Ÿ-–9æŒ½Ñ á¨W«<ûuõ÷ßÞ~\¬²«Å¯ù_æoýY5䩖앵”)çä#0\ú¸_JììÎ&&.ýÓúø|ÀlGu²ObÉÔŠeXÔFd“Co8ÔV,C2õ¢K<´eÚÅýú.Þr¢š³ñh833P2¯r*³Á¸Wß$¸ÌÒŸ-iÑ!­’õç£Ñ´‘kÿ¸`“Q}nñÜÅ3®™)ˆ%Dø¯—]¿<Ó-ݘ#¨Æs–7ÊfD4øJ)l¥á½k”Ìhp™‚Êôé´ÜM?¿œ×§òFY;=a“ì5upB¬s$*õ†Jz ]ÞÁ’Êö‘=¦¬?¬â!ûµÔ…nP"\I‘͉L/ˆi¬¸¡Á²PÝ—B.'1c“´Ê•b@°€Z)‹e´è) V†é2â§Uõ€”3±úõK<îÖ1“,ö›ov\5Ñäý¶Dùœ û­T’V4kÈT*v’¤—¨†£Q?Cì¿ÄyRj+ž›Ù†Ï¨iWãZÄdTEŸ©5t‹.Và—8¸Œƒ³è53œÇ2»3ùøî²;oÕ£ FWss–qMe¯!„ˆÑO4b9Ǥ®€¦×‚Ã8EhýèçÓšŸ»%\] HÂŽGYJ¹^²æbZí $o"â:BîFS÷¶Ë}×Ï¡×QÕ}«•)¢CýÐ :}D€YÎm,ÙS!-q ’ ö¢ Íáo4ùˆyàóóZÂ|¸XÐ*y‚h΃7H;1ýlˆ¬µiΙ\3G™¾®ž ìwà(v°Ñ~ýw‡upB×Çk=ä‡{åÅ ÓšÖ2Åu÷uUª‚ó¹žYÇ÷^™ÎÀYSU çäs27kÈθ"p)~;”Ç`  µ\u€¬ƉSuý£Edz®=F&x>œ’¬gÑY÷ž“¬ýÄŠeG:æº%õê×!L›YÓLI£§ ”Žiíq–φ¹‰/Ÿ×÷«;Jýóú÷3H茒 Ö-é…~>ÇC£ôó!ö©0(ôa>¬[/”3`Â(3lL^HÍtÌ`À¹4Èå$xLC.q_ÐUÞuƒB‚D5ßs–ySmëPþZ–JOSŠ]±ÈÃök¡z®Ûh…nô׊å:q{ˆU×°·Z­Fp¹©Ž£¢dV¶ªˆÑ¶A7vóq”Éeú@³ÔrhõW?"ú0U}ø‘VÑÇãîp‡üZ,"Ë W¹\#~ UHžðpf궉Ê›`ÎâZ”E«–¨Áô,ÕòC­Â²[+Ž}µZ¢ó*—kŶ‰V)Q{éHª:ñÃM&éöÔJ‰šKƒbs­ø!eѪś̊ƒ÷,U½øQWaÁ‰²‚&ç:ó6÷V³‚r•˵â]ŒD©t•ˆ]q$Uø!W%¡Ý>µJ¼á¬ªÄ‰åñã-¡Uˆ7›Žª>üh«pœqÖ@'ͽɬpx±\~¨E8´úðæ2ÂQÕ‡fŽÏÅÑf Wo.+$7ÁL'Øÿ‹D¾ˆV+Þ`FY*zZ$–8ÍÝZŠçÞT†N$×…`a»àÇZxãX©{žÙv˜vé*Öunõ°Ã X˜àÑÿJ³‘›¬ÎýQ½äP9L)µD¤ ìº~zCqkŠlNdÛ&Bd.:k I>N“͉¬”ˆ6/uk5IåÖŠGÜ'S’|Ü$•SX(Q´™ôåãf¹œÄš@‰dùK†ŒŒ;í¹ª¢·$šóX3ç9Š£ê "Ìî6 yéœÊšÅ(^AÝÝ­7Ÿ”†/§ËçdÖdFÉŠ¯/‡úJ•Ωll¥¢§GÖúVL•Ωlœ¥Â¦Æú^™Æô®tùœÌFžQ²Ã)3èV½Î±æ¸³ó!f(–äs2‹FÉlL-q»„§å{m-œÒFªM”8§oµ”¯­…SÚ8V¢|Ø0´Þ§Y.#ÁašXpCS‰‚—gs–x|³{Q{dÔˆ•Ê)â1ÍóýPÛ2xþ6Fa¥rŠx4óŒcÁG¼Ž¡ PpÓ% âs–xLã å érðÖÖáˆ`%×++áŒñxçÊx¸û/dU¾¦N€^ŽôN`Ñ&¼š¤JçTñèJ…,.“+í$RÃÄ:[µN„|Y?¿ÓÒ½¦N‡Jtn¾§å{]œ0•ÝüOKøº:8aÄAËp¾xXåùÜÄÍM‰VØ|¦¬ŒZ]¶¨³Ç#.ÏŽ´È÷‡/jÖWTÀÙêb®Ãqfòú%³iº|NVsy²ï3YŸªªâ¼uQãm9mŸªªâ¼ñ¨ìô´Æ•›3L;|R¥sªx$ÆÚZ9?›¾¢ÎÄBÛ£šM_Qg‹Çc!ÛÕ.jõ§¨ˆ³Æc4gµl ‚Ë,ƒÁ©w³å¹pûq€Së½euø`sßhïÅŒHp·Yp™eÔÉÈm>Čʂ~“Y)Ã#íh+wAI4.Q4‹.óÌçKd‚Bç9½¡†;÷›!yüA² % ‰ÅgÖ‹eHGƒËîmpèpQ½F$¯wó©þ%¯ÿî2´`À3 õbŽÅˆ^c˜.²!½‰³È½™¹]oïлFú7@GsHGò$éœ IÏ©TZ¢²¯cÐ}vÿRœVQ à É5p:d¹1eq;榳ôÖ )nR„s&ä¦bƒ ¦ÕñpwÑ2è 9‡_Q'D*T%­¹W³Z¨ Ùw%3œP1eèä[Ú~˜¶ýˆ¨Q:§Â›[¦¬§š¯?oï[rÑœ'CÞ*IY‹9^oË…÷Ë’¤s*g½r$0¾Q!7Øæˆg²÷ȺòϨ¶}©—ÌÙÒ™³×Wǹ}›í\z'Jw4‰]«•Ìiœ=[¶Ã¾ÒÛúQW£7gÓR*àlήQö—[ ;¶¶o¶6gÔR*àl΢á5ƒ2[±[nwØò1™WÞ-óÎ`é,[R !îdÛ1EyªKškÇãìZD&'°ÖŒž(¼ßž7OåÞÚ¾nŽ Áj¤ÈçdÖšp¹¬L†×8‘\õ;t«1²ì“EK«ÓY«6êÖ¡í[¡èìãŽ5`õ’9µU#DÌ%]Ý^LÓ7Ÿ5Uµ‚9‹µT#º¯vëÓ·(ǼÙzÿIMŒ;ÖX¥ÖÁ ­½!³B…ð»ô+k®Räs2k­FtÏrîSóªãßæ-TgÍUb%¾ñ3Ad¡XšÌǘ5ç9žS£™ªÈZœ6¢‘F£Yt™ï8N)Z>ž!'*Þ B–}“ÅÞY/mZ¶1 ¦4h ‚C–%r6£ÈdŠçK,ïÖûí Þu£üºöú¨>À:¼²–2ålÞÏñqx^‘º~gÒëg“òk´Ý«4hLâéQ¢$ñe®ë0¸B¼\N†=€aÉýŸzÖŸýuu~",œËМ“h¨­Y4çÁe]*„©G„G±@jhp7¹Ip™e>X"}í|ÚE¢VÌʰ¸„71I7§Ýjs 7̾®VÚcâc.•&žqa© óΖžqÝ?¬Vw8„¨Y%&HL]â™,‘^™Ì†”mo<˜—&³m‹t¶F(<`ÐÃt8Y Ëlw9ÏÆ9âÍ6A–æí+¬ÁíŠ9À£éÉF8Ö`S„L³>^2›w‡ØìS·Ó›Ì^À4»œ‘»@7²¦CFÇl² †¦È|N‘JÀòw¸I§›Ù«œ`©\f™xRgžá Xn¬»â¬YWÃË JH,ÆEòú‘Vþ±Â¶ ™ëf3*×½Œüt}<®¿)­­a€?ª$˜±`¸ÊEŠ5nv¨:)±Šâ¥r t ñ÷GÄ\e®!£ÄM‚9 F‰XäDGàõ*A¸T/6ä çeæÙrÙ›b´ÞFÈãîeý²ÕlZ“:0ñ2a™œ€Z%BÐéjÜ‹a BR#•SP{Ä(T€  •Iå°ãQоZ4Nb$•S` %J1PSÐ ‰QTN½¡(…ꔳi 1 ’Ê)°•¥©uA~)FAR9…QÂ(íŒÕäb$•Sø1%QLÔä§b$•Sø1%QLµŽF)H*§ðcJ èvÔ5¶ÐHå~LIjÛIAŸÑEL*§ðcJú½ÚvRL¥l§S…ÚvbÍ7N!ÙN?¦*Ÿwê^µ„F&o ?ž$eعŒZA'ú`cM"R±åîT)‚Èn/cÐÊd: 5”(V1ëGUÄÆÐÝÃWu?ˆY>+“ë 6~è×ZĬž•É b½æþùE­ƒØ(·29A¬×Яµ:ˆp+“ÄzÍÃÓgµb#ÜÊä±^C¿Öé–%2¾¬LNë5ê~0ÄÒ‚<­LNó“ôk­b#ÜÊä1ùt§Ê£Cv–Ž[‰VÎÊ䱑C¿Öê æ­LN9ۃ궰ÑAÌ7Z™œ 6rðkõ\sˆ¼àr;x©ŒKßñßkã¥a'fëˆBˆ—pö/N¡—†”É\ì“D!ÄK“Ø(¢ßkçš´>§æšxÅ1þ{í\sHÝ£ºæš“Øh"]hçšxð¯†B˜kN¢#êEo©bÖokdòñOøµÖRŬT¢7³²HsRC«²fBzk¹/Dþý±Ûmï´ßÖrýV&'ˆµ~­·“x0Ê ­É™Õ{©ˆBm'±G§ìdÌk…ÚNâ•Ö8…`'§1»º{yPÆ‘ÃnÌZ™¬O`o2B å¨Ä¶LLNû—¯ú^Ù‹ö'•SDû~¯î•8ùÓ„•Ê)âm÷Uß+ñÂ{œBè•x·5òû‹ºWÒs‚¢×Ü™L³¨]’ÞNŒT¬5^ˆýZ;Óöc‘ÃîB2¹¢=¿Öê ꃌLNë½”9Iqå‡<&I—õjer‚XÏ¥_ku³7V&'ˆÅß8À¡&ˆÙ+“ÄF~­·8åi'•SÄFQ¨í#¶ñâ‚צslâ& µ×Æ;5õR¹.b£ˆ(Ô³›AÌæy©œ":’@¡žÝ bv(„ÙÍ,Öþñ¬]â>ÜV&ÓŽ`Ç­´ƒØ¨'‚НÀ ê2Áññ¨µ“ƒØ¨·2¹b}‡~­ÕAlÄ[™œ ÖoŽº+ýä+pØ1¢W#“Äü%ôvrë^*§ˆùLú½ÞNÆÆº—Ê)b#è´QGpƒ˜ß´29Alѯµ=2æ7­LNë='ýŠVý•É b}‡~­ÔËT-S¬ßœ^Ô1$ŽÖÆH&×A´×´™Ý ccß%­9äÑžÓfv‡µú¨&ÌX纈ùÊÓ?´»ÈCõŠ0™ŒWùâ¿ÖöÈèHA¥?àùÉÁIß#c¾òddrDGЩÅzÞ¬‰~—Ô#ñìdü÷j?1ŒÚ<|›OãÁÉÅ™â<âõ'“9ü„aýæ?Þü÷ö´Æ_ïgÿ9»lw÷t4úoðçoÅþ½×'¯w©ëdòÖˆ¡óI»›<ĉr™ÀÊä±D¿Öê fõ¬Ì`D‘ÿ ·F8P{;Y‰óÌ»íþåxxTÑ̦Qr‰&ëåÃ9úP¯;[àtHgK‹9ÝZ ,ë»vJs®×ÈÅi[&Ž1BºƒOS£—vðWnÏ¿ÓÝ t¹û-¥ÔTÁh¼L¢‘Å¿F4çÁI|Ã3zã!\ZSjT5Þen”ÌhÔÌ”Y n4Û=n˜[Kzš.^˜'šZÉœÏÙ›2n>áU‹Vêâ™÷:¡œah¾ÄVìM#¸Nv‡G:Z¨cÐ$–sŒM´K™ãåé°/ž‹:K†~Û¥ˆæ.þó£j d, 4Jæ4 [†²Ì4ÿííÇE;¤à œzÑežEo í‚ Q!•OŠp΄ìP5ŶÏZ¨ ù‹’¤s*×#UÂâ”íï3̦Ûôz$ª¡«ÖÂ)ÝhŒP>ô³|jPdXª¡»IçTõçˆWÃŽ8¨ îýHÚVƒUϹê‡Íér|X# Rƒ![XY>'«:ú‰kÆUÿóþp:S®Ìí(©ËÉ”B3_… A û°9êÈ\Ço”RMrò”ýQ—Vyn:ûëVÝz“œZ/&1¬=Çû$øi¿®¥Ú‘ÓùÃïÐΈóLfI—O\ •#iÏ«+â¬ô]ÄŠh릩€UÏg³ý7 çLK€‰²$ݘ~9‡­4¨9I¯Ó‘÷Åð7ºïBE±J“dNCþe–XS½Ñ”r¶h= Esò8T«3ŒÇ&¸kÁCN¶Q4ç!›>Âòæ67—³útÆõ)½YÏñ:CrÛb’M:Ó¬×,iþ:ïÏg6ÛÞá¼}XÃKvtõ—#,¢õ9’k“[ùˆ×kLêg½‘2§iÂ9k3“JI†*K_æšaÉn‡“Ñ‚žNɧóÞrBºúµ8“!ÐçÆÉ¯ ÙDsžÌÂ¡Š ®œú2ŸË9fuÎP “oœ"8XšÏ²>VŽñ˜(2QÓåîQw65ÇÖ®ý8ÃãõßNÛS‹þL•L^WI §¬ŸMñ%KnfÔõoPâ” ©âÕ”8çÝÑ—=l¥‘ãëÏÆÃå‚úù_·ˆ07ª[oF(zUPÆ€):~>Owex»Çã/Ç‚ž€hƒø"Mz™ª7ïak¨?Ì—æÈÀl4î˜-‡ù/¿èFöæ˜SÇEòúɳ¡þüF7¨_1ÊLíäÆ"yݘåÑO‘Ü£T·õªz÷®…?5 ˜.'IçT WéKTöÙ‚óa¥#Ä@QT” œ3Qd„b?¸¶Ò•éÃû·¿.>¶è1%‰ç\uPAÚp¯r™üûÊàÃh‹‚$ñŒ‹^Z¦‚f§öÆõ‚¤ÛÇËsë7Cˆm•¿ô*8¥La: wãkÙŒ ,ðÕJåÎöà)€ Å ]Ý4Ÿ¾Wa%Âà4‹ç\Î&ájG‰Ë,t}Ÿ¦s&*A>'skN‡N¯íVZ‚3‹½ï‹ãó…Ö›´)ÕMÿræëuUq^gËj¹Äû·Ã—bçâUL`øœ%«ÍyŒ½XàõŠ2l}‹^flDLd¹þ~6Ϩ/ñÜŒà:f¥¬ºÜ¬]ùšSˆÉ^Q'ÄL%¥´fÌÐ!ªM”_&å}´Y>ö¦äƒÓ5P W~|ùT‡8ç$!f’ô2Õd¼˜Œ:³~>íMÑ£²ù >DµØâ°‘ºIl¿I,ç˜D ¨šŠ“+òiY®?[â^ Œí,7 §³ñr¶´KK8 øx8n ?MÑ wȧí¹DùœŒ¼ÈÐ@Ù;¼UúŒ¥Ú{¸µ G°%srJ Áû4%šüðŒEoåj—A!‡^+¶ÌA¸ ä.'Šx¢d{L¦ßæ‡= ÇÑÞÑQ%0ÿ¯©„3´Rq¸á£[J{MLeë„2\²?ôôv_ ÃfQkN è̆!"”3 ›ŸcÓüÖV¸N§ m€ËVu29z-Ð#s7‚öq ç6‹æ<ˆ ¨VŒK<´Ï‘Q›tŒ‘X »}¢ÉêÇÁpTÝïã!¬Ò³‡œ\úHG °‹¥ï8ž(žsA™ÄE;j·°Þˆl{kÁèEÁ’õQ„iSk»b2Ë}<ô7êvç£IŒ5¹Ù<ËæQÌõóýJõ²Í"sÌ,ã"yý8‚,ÿÎs +7EêIS?¦q‘¼þ(ìZ—UÓd1+”3DqÓéŒKµjMÌb7Áœ%ŠŽãlëËîŒ$ÊfÁ«›r³”$sšèÜ_tÏZ˜æQX©œ"J¾Ý?Ôú€{–)œTN¥Ff‚∠uÍR™ÑÇ2Nr•Ìi¢ô¸ÀA!´®“Ì;1/–sDÙ_pàuƱz5 Vä*‹f<ˆ†j ùPÙ5,s%ˆæ<ñ8ÈfÓªÑs,$DT–͉¢Ÿñy½£3sÊžƒy  ãÅr޽vá0‚L®7cÄ-:Öë 0é+y]ÜýƒãU*`ѱÕÇd†_¿À#Ï+ÿZqxÁ|•%b2AÏ6¥+éÀ>ŠÚhµÐµv).•SX­É¿W¥í%Mt­UŠKåVsòïU’2¾PÇ¥r Û+åß«À4ÖÅ¥r Û3åßO´ý¹g⺠©œÂÆd2…êL£ ksâRîQê1fð·ècdƒ„¡:C ŒZ™Œ·ö Á4˜€àþYOàFGD&'°1 ™‰PÅ^õ´µv¯ÍWEd2‚¡³T9×t©Œ ƒ*‘G¯ú]Þp½×â²Ò¢é8i”$Q-qx¢7žâR«Hõ§õñ™’žã¸‹òÐ Ø–8¥òŠ:BÂEÏâ¯Høþ€ÍW:Åh¶Ñ4'ª¡¾EÏ"&WÂÇ8Ö›ô–tòÖ¶.u:MQ³FÉŒ†îRP™%ÎÜTh–ÚK]†'ì%sê÷¸ÒÁÿ*4tÎÙzÔ}ËÜ¡H’ΩpÌ”Ãt…êqw8Ôï—¢&8R—&žsá<ÄÃÙU®wëý‡ T÷ Ô¥çL8fŠIºz×^ôÇIU8e—$S‘]˜ô‡”ï§Ò‚/Û3òëEæ Y6'¹/*EwÑ«Dx·Yqž·xªQÏ…ÓtÉ5p:c£@X¡;űØÃˆ¶€3¦*­ÆFiÍwI=Ì$i§6c¶@Ö(žsYÛ5K-ŠŒ‘ê\–4šnΙ¬åBÒ4¡O‡‹ö˜A²f«I6'²6 ¹IbDô0Z‹ž…壩” 8›µ]à nUzýÉ]¨×÷y,¦X²FñœËY/JŠ_á²ÿÕV‚.EÑhj-»VSÓbô2Ñvk?æÔ¤2¸Zv­’ê%3š±±¥x;/ˆK——½¹]¨n°åØXÐZ¹Œ+¨Ðæq(éÅfùø€[òz–‰i§ÉešÁ´;Yt²Ùט±¿¶ÌƸfK÷…}zVͱ!Š{8uBË Ã|‰‡o‘ ²‡g Êù­F²ãÙ¼¶¢ÔÊi®FFúd c}Ë)HçT ‰ÊÅàßk(aIâ9×RâÐvC‰3ÕI9sÚ·-ÁtU‘͈Z í”Òt$â±mPÇÜüÆ7,‘ñM¦A1åf£«ö*ÊU,×J¯ŽC©ì¹ÒÇE(ªºè×0´ÉxAÁûRq–’p®—A3“V;Y3QUGv 2ëƒÞK »ú@Ï“©/’–lw”[,ÏõdíV—VS¶s6PUu5®i;ÿ1+³¥7Øxß Þ¯„J¸Þlößz½9F­öl®×Þµ Îg‡Mî;¶U£è`X¿¦{•·z8©N©¤ZeŠþ9ÊY퓳º>‰ïƒ¨ÑöøHS—¤sÝå TZÙ^ÏTÕ“eA9~Hé•Ô))Í5$ÆWe¥zðø¢l?®4UÝÄb*_d5/vÚ§Môó•BLOt³—ôäØ´ÚŠùLFVÑV¥¸0:þvجwÈ@¡}JÚèÎðjw¿V+â:ŒÅbZ]ÚAŸLZÕ©¯µì{È/Œ‡›P®+1>³?Wêe êÅ‹äõ‹ñXû8LœÚ”År1þò´š'47¡œAŒ·ÜÏMN„vfi NjDùœLŒ²*%•jr3J6éœJôºË%2H«î€!~Ša”Éë}šùñ*ÃJÓg›t#¿¦!SS‰·¾"ÆŠÅÁ~[6§•¶ñD_ æ,¢}¶EÞ­ñvÐWµ¢DãÇ$sÑÚ2ï×gº@«Æ­ÍyDK*õ.5šh jjᔢEË·ïø.ê˜,±^y[Í«©…SŠâ—÷¹VmزÞ5²yÝ¢uÀOM—ÅEËá†3SLU8c¢-ÕèÒ{Ø}Ûž·Ê›è0Ÿc?Uæê±™‡Êò9™hˆ á\R›PµÂü4¡BV‘ÏÉDû]žÕX>cáœI´fjo4 :5‘Y".šóˆãì6þõÏДOÿƒNΩÄxóÌZ!ë˜ÀÈe$”¾¦:în_ %Á¾¡@Èå$â8ËwkdkzØnLÄbòÍ©‘Äþ#WÀÙÄ‘d0ÓRa7HRT99Dsq”ÏżʧŒ˜ܲPæëƒee±œCôµAf2-Š·Š “ÌiÄuBJצ…ð=&„0yÝâˆ^|Å CÓsOZ†¹·ÃC(˜±àà0¦müº † ²…ü©X#«Jr$=Üþz‰$žs‰#Ü,eÌR¶ÖÂã@S’xÎ%ŽîwóÚ6ÃÁYICF ¯[É¥,ÌZexO*ã–ݹbSìSˆ|÷»å#sžíÊ´Ô‘q^j²š}&Ú•ëkZ͈#¨$•ëC´"6#Q‰yrÑ™´~7p¹Äøíný²Þ|ÒïƒO½]æ%ÁœE´7¥:p)Lè!e±œÃêyx^ožÖÇ:ñ~ë¤$˜³ˆùÆ¢Õ‰ØGËb9‡l…·ô†l{8uÓE¶bûAϸ Ij\ÖV¶àß°.Š·Ó•*Ê|´4“ÌiÄ=J\-Ú¾¸ó¨¥³€¯O“9Ì‘Ûß|/.u”—G"5p:ÑÒeuËæV~3[ÅÎE+4w‰ù?n‹c[½!»õ,5–õ©ëM´KBY¥Þr;¶šÙªz-•?ÉßZgvŒq Ò¹¾D›ÅÊ)uåÆ{=SUOây/zßÕd›ÿln½ ‹UÁ5&ZW©°VmÖó°¡)WÀÙÄó`f&жƒ¹aϨ¸hƃUÁâ— iud‡y M¥_-Äs_†å»ô);¼%"&žëHœp.­žìðn ªêJ<Ïe®˜·îGÞ¸N‘‹æ:ç&åBZýxs¥©êÆÅüVà¼àwð}x¨Üú¾HÎ5$ÎŽX9¥’Ü(f¨"›‰ñ•YXiÛ‡ÜPf@\4ç#ªr!­z쮡©ö!1†2,¿—›]uÍaçÂ^‰'Îõ#FN!“VCvøÖUu$ÆK¥­{‘‚¡&WÀu%FMÕ¢Z}‰€$žs‰±“-xyn­0q>#HçTbÄÄÊiU%Îc*²9‘'ùe²Öz²£›uwA:£r›O̳°rZ=‰SE6'c&{UŸ@6êzaß|;9 æ,¢ß-ψՋ=Ùõ0\€S‘͉DŸ”R¶ÖÈŽãÉ2ÎS±—x×Yˆµ³ý7 Kôªø¥•¥,–kEô³¾€R!×»u"EU¢Í›§]±¦ô#-ôa5 Íu"úÖr!­^l£×ÐTu#úÕ‹9ww;0ÒBU¶'Äᤚ¸æDO[C«U¤í1é¬L¯Xëm%N áøÝ…î·ŸÌ÷šwm·­î»gëQmc]nA,Î#Ãó_BR)©Ô· a« S‰±H¹\ûœæJcÑ+×UÃ9Åx%&@«DÑcÇ+áŒbL7W@Zô>щGjàtb”#”Õ*Otç¢|N&úô÷k¬ç—ãçAñØ:4vȈIæ4¢w/•ÑêǺ´8KŦãô`1Ú0ëÔ8Æ5G9׆èß-ƒVÖ­‰Uˆ~ýz2G?”¿™”+Q\m® ÑÃßX”ú˜Øî%©êDôõWs7ä»Xí‰<|¨¯ŽÄЏÎĈ Ϊա<¸¢¤UŠqƒá\¹}3ó¹^¢¾ãm/’š;^Ó*ž¯ˆYY†R­cÛÓÒY+zí‹ñ…Õëuª×B™¶{‰€¡x®A1žà\ZµÙÎÔ@UÕ•?X&™ìj›T§á]ƬRט?tJ¥!©yÌ ‡#¯ª7qÝäFö}l¡í0QÕñJ¸öÄu™Q«@Û}’«:”c02w¤}sM?L'¶ïÄÐnÒ¹ÖäX,¤ÒªËöšz¦ªžä˜Œ·¾ntÊžËæ:’#´r)­†dëJæ4r¼V*cfá·×iJ6ûñZ8¥ÉÉåµÚ“@¬N(Çx6‡€~ ¢·KF¶$–sÈñ›+ T ©¡¨Ž916ógŸ[(C4é\¦ —BŸ¼–ЪC4Ü%©œBŒ©\–ƒêtY,çc(_@« Ñ,ß„r1fji^¦âÜð&”3ˆ‘‘ý¹V âœÐ‹äõ‹ñù±5¶¥„wêÓSq.¯„3Šñ\\«3q«‚ó‰ñ/ŒìyzŠ /‘8 eµª—dDùœLŒ‡\ÉËýöÐBab8ÄEs1²…ŠýÓÏʵ ¢ªpÎ$ÆD¶ØC‹×Ȱ®>!.šóˆÑ-„X¿t°³…ªÄè'Z'£±´²Ç» ô,úÔÀéĘèZÖÎÑë.Ã#Q>'#¥JI­ÎÄxIΨäW•®å³2˜¼:½]–É¡ =@H³×°N'G1BÙÕÏ¿.Z´ªØÔÕÃIãq}åm½KÛ¾ñ ƒËçd5Þdf™C{ò,«që%Ùœ¨ÆcR©Ò4L Vã4«Up>Ùo~HÍ%”妉æ<²ß,Òv*Ùg‚9‹ì/M‘6X&;˲\N"{J_B«Ù7Þ¤r ٺ߿ße;ÎåY¬‡“Êž1FªÔßLöñZ8¥ì%}yŒÝÛ©o½½wcÚ¬ÖÂ(å·{ü­J2È%J­&Å•‡hœP^‡(é±u(ä’u×(±\ç“=»À§UŸìÒÅ 8›¼nñRìvx^:*6m^Ìfò † žsÉ1+¨Õ—`T„s&ÑWú{³-F¨8Á ärÑK^KhÕ"ºÈ’TN!úÇïq§m&zH&™Óˆ>²TF«ÑKr9‰è']V3õºËhÉLPI*§}`«ÜjY.z¼«LN ú·ïðœZ–‹3@&™ÑÈo•Ê(ûG.ú®@.'ýÕ­ùTïûôV%ç¢5µpJÑkEÊku':®hœPô]GÊ”_pÓ¶…æÄ%æ@.'½Õµ„V;⌳$•Sˆëïë»M‹ÕO˜x·GdF¹ å â Üþ\§†YÇ/X •=º±¸~>»œÏ‡}Ë\3÷ ûw¥K‰**²¹FÄ€ ”R1îÉÒ:žª~Äæ–vW=jf¿ 4“Ìu#Æ1¥2JÍt|Dc©êEŒe6Ê“úµ…R|H€”ÅrˆQŒ/ U‡§DŠª.Äøe¾nñxì¬ã£¨á*“kAŒ]̯•*@µv«¿ZõûŸ…jomA¼g ,“Ìt!¿nV*£ÔHßöKE/îd;uÐZ'Þ¼%©\b\â~¯Õ…·]CU¢ûù¸~yÚn´õÌ~R0”¤2=LÅèçOß^Šãû67xg}o<P0gãŸ[m³xë!©´ŒKÎz(mH_ŽþÔ[ò®UÂEs½ˆ=¥\H©™®_W‰ÒTu#FF»íé¥MxØõ½6)Iå£!÷{­2¼U•ªz==erßîõ{ò³®7!DY,ׄèé}­*üØ)ªº==²–µ³ î(KzWËu!ú{_@« 1ê¹ å ¢×w?×ßÞuÅÈ'ËHbo°™VQûØP!ºrTú†Ûýg¶¿¿à%Uí*֬ﵘô’T® ÑÛ»ß+;†;=ÉæMW™œ@´›ÏÅOßéõà’T0†’TN!ÚM÷{¥\Š ™¡ÚÄ™£%X­[±šüZÐ+*²¹NÄÙc¹T»SM3—«BTýä[œMö2¦×¬n¥4§Îg.M„Œu“͈ä—ÎÞo7ç˱…ßëù%áÀã”År1nõ”]¹ç„EŠJ_vÛy̶™”£ê!!A§``oB¹ÄÕ:ûs¥ÜCoÌïz‘¼~165?^­7&G¡Z3—Q" „s&ÑÖZ¦ÝáQˆsæòŠ@WÉœF´¹–æ¹Ø_Ü{S-bƒŽ·{A·ÔÀéD{lËîþ oè¼c8¿ Àñ 8›h™-ÛK[‹ÓgbUáœI´È¶Øisܾèw fîá@±w•ds"qi 8+c’98peè!âÓ™V7Ô‘_Gœ¥‰ò9™8;xÜÒ¼^Ô_Y,çg¾€²©zâ(» e ò»†ïÅCq,p¨¼EõÄqÅEsq/³\H«q…#ÌYŇ–c»'Ž¥’TN!Æ7î÷Zeˆcç*“ˆ«qö×¥uUUì9ðá^©Wds"1Ö J)5ãR’³X˜Iæ4bäs*ö÷§Ž;Á¼Qé¦çW²‡Èå$b¼S*¡ÔJO\Œ är1Ö±¯æµ0±~9*ì-æy@#•Sˆ1£ÐêB\D¾ÊäbärÚžÛL‘üBT …«LN Æ)æ×Z ø‰IµþÊÌ(c:ÖÚrxwP0É\bLR*£ÔÈÀ;ÝKU/b òkÆúááÒ§0ãuʵ!ÆöçJE¸´("AEsÑ×ÿu«¼¸0ë‹=ÂÈc_>=û_·KÜZk¡~±”¤r ѯºõ¦ûâîÒ¢+Œ|ðôÈŠlN$Z«¼xÁC—ç²a¦×„“Áªe±œC´¿¼ÏÍaýrA͵ªéÈ>öʬ$žs‰£öÝ2ϵªYXO–xíöX“Èj—_<Ô×íS35y¼fq¼Ø›nkÜEøÁÔi¶ÞÒêßO‹]L‘88ŽÞ;‹eúL«6²± cås21 j¯­¹Œ(ËIÄ‘}½«ØB=™[ c0\4çGxžŸè°êüãßµýhæ5šš²\N"ŽiocJ·ƒpEKç§#ßB(gVyŒ Yid°µeϧF²s>ö¤r Ñx“ùK xM¡(‡Iæ4âˆoC1í“Èkç{þ„uûWÐ3·´ÅG”¿ƒà™Þ+Æ£?B;‰çýñðuû¼=Óv—¥è¦Êb¹ŽD{Cïÿ˜TÊäfL1%©œBœû,¾âLÓ+îg˜=u¸—õý¨R&W…s&Ñò…ÅtêÉÜ<–X›‹æ<âœè·Ë~_ÛéÇ÷™@?¡`Î"Úâ[­^l7`z)‹ 9°Þ"ÚÜõ¹x<·…}lëßÚ?jÏOLÝþ)·À±:8¡hÅãe·>¢ÅµÝ%Þ`T\N"ŽôìáÇŸÌ­¦‡ÃQí9ÝÕf†SΙÄ1æì;ht)Zµ"”ÏÉÄžöÛG÷תúyªYŽ»ÔÄt×Tãu_Ê¢Åö±Ø›¸åãúnWüå’zi»ÜÜÛÑ` «‚ó‰qÉ­ð‡ù{5˜‘"`N6'GæÈfW3ÙïePΩÄóåå¿¶§õ§­Md¡ÝŠË†¢¥¯ çLbSZü¡hñ¹hÎ#ÆN·9hÛ˜ÛeHfR”ÏÉDMWÄaîÕ̬ëÌ‚ †²XÎ!Z/_@×V³®0l³û&”1`AKšå™vHͼý & ¹Èë­ ~jla~8‹v¶{5‹IœE¨€³‰vçú´Lè•TÅ­?1Û©Ó‰cÝxödYW´Š‚tN%ø¿Íµíç6ñ!nòºÅ½){~8µ5v×øX´ æ,â<É­Ÿ¾a£ï³šg6òÞÒRtI8gm^)Þ°ë&ê¶Êº~Üî]®€³‰vð׿¾ÛÜíZ¼Ì4ˆ«W\N"îá\KèLòtbuϺqI*£óöÓïwë—õ擺óL'VÓII2§÷•J4Z­X]ÇYøªY·/ú <ô6z eƒ}N¢$•ëCÌYDÀ—CšfÍ\ަ°úŠ8«8{~»¿GN2ÝØœNlŒÊ4æEòúE{_ÒYÓõ…5Zšº‰ã‰UÁùD{Û¡£äñpË¡V—_ æ„‘œÇãŬUQàóóq{9Y«…4«¶«‚ó‰«tKÈPªláLm6 SY,çpÑj†Tã·2;â¾)¶KÉ<¬p“ùYkûC'·¢šäs2·ÖÝZE %ªá²Ò9•+W¡ú‚Ô§«6@n±TÌYÜ®X†ôº·¶ÃÙÊ5ò†·bqî·¼@0gqø!ËrùkqnEâ\k/ˆËb9‡³Ú!Ù¢mãÓð‡7¡œÁ©/dcŠ64Ît`ª\jvI<çr%CZÃ[ÁòVºqË!ÍM(cpïKd ô“5í@v÷e2$ˆ­äu»½®,°EÈ=´}ñ¶®M³¸VAéœÊ5gHåßoäÆN æ,nå)d¡ã%4%nÁâ€c¿½ÔJ¡`Îâ:–Èbæ˜mxü’xJÂ9“÷–A2óÊVÚqbCí”Årïµr×cçÞB’P0gñ1dñðÛ4’ó) &”Ìi¼Oä4å75Zµ•æAÏÓ*àlÞ7l×h´…¦|žZ³/ /&™Óx/…´7Kì3œ·Q‘ÛË¡CÿqÉœÆû¦€æ€—ÿòþk}ƒ{rœÜ„rg0ñxV‰?_ü¯¿f¿¨!üà´Q’Ê(Ü;Y…â�ý¸XÍÞþšý¦×ˆï½† çLÞGqÍü¶Èæm‘¼›âH¡lNä½C¢ÂÛRöÌvS–©÷ AˆÂEs·‘<6ÓA›±4õáU`3¹œÄû¨à(Åá í¿~ý©‰ƒQy¼fï•‚šýIàM+5x¿¨—‹æ<Þ3…<­¦nÑ+ë‡ ^&'pÞWÒÝí’QËŽês09¤s*çWcT¸ÉÔª­ü€Ž`ÝÄs.çC®à z.¿$„íŽRcHâ9—óM!Wé8P»ftç`é`V‰KϹœ¢C.:3ÑJMÞ_8%©ŒÂ­Mgx‘¯„ïÌåéÖìø”™HZË9œ9àgç‹û‹Úeú|•8¢V är§Á ‰u²y–ÿi¡V‹“]¡ es"g™+DÆÇ¶rF¶ˆæ<®P…m•ÿööýÇ·ùU­!gÝ*@¡lNä-upÁî¬êû°3Ð8¿Wê:7¡œÁÛå€!Ø(n1Gpïºe!Œ S¹˜Tïq£Œ»o— ‚U››PÎà-pÈ€Ó0ûÃóv½k…â",†Âes"o{¢fÿö¾×ŠÇð@5L2§q{1°U¥ŽöáýÛ_[±øÁ²”å28 s㈑àfa+?¦CŽ›TNáÖ±…É}f_ÌkCƒÐÏ|#^ )k»*S¹ž6ÃîÌmÆW^ÇóJ½»ðšÁ *ËI¼¯”IÔÛ*>ˆ ÁœÅ{Ë€eyÙ›<È­ÚÉ$áºé›Iæ4ÞS4oŸiVÙÂÞ¹{»Ù @)‹åÞCö>l+?’Øä×±¿:¹œÄ{Æ`ì•OoÅã]dÀ#HçTÞW2ªÝ·GlY¶i)gØ ¨,˜³øyKÀB×¼K+Éš ú…·¦! “Ìi¼¿hœÿh£™…[ aBÁœÅ{ÉÀRÞÞom…ãGwÐPÙœÈ{Ê€Èì¹kï¾/ÞKb"v³3W™Œóë!ÿÖ”Âì¢,–s¸æœ& ;qz?t‚™£“Èk÷:h½çÃyû° ‹ÚçÃqu,N‡ Ž„«xU x%œÑûë€Ñ ߫Ԗ~Te±œÃû¤ iÿªo(—¡ˆ±yÝÞu³¬m†ñÒ™+ø¹Òà‘+àlÞ3+“tü…ýwÉõ²a°œqʼ >ümÞ‚ÝÖšˆá&”3xÿ0ÐŇójsÀ #ºójK—­Žé"ÌY¼÷ X¨sƒ„·¨YÜ` u æ,~ÖXay^ŸŸÔ ÎïàR©Ãˆ“Rô:ÞŠ+Ææ÷‡{uÓ¸DÙ0˜–¤r ?VªÅéDo*ûH×ýa0õ4 WÁœÅ™ ‹¿(¥d¹¦»¨°ÜsTŒq»w_—.!yVÕËM0cñùƒ°RÃzÝÌÑ6PÏXA)F*§ðý5 ¸ancذ“ob\)}aE6'ò³Õèvи’ ©"œ3ùYk°ÖT¬Q &TÄa…r}8‡•Þ'_ïÐ9Žëç'n?ÑÝÊ¥ÿ?'ìt¿ù7ÿü_øëýì?g—íî)„‹?¾yÀŸ¿ø÷^1Ì—}ß:‰«ˆ/Cͳ.-ûùñuúc|ÑâÍOÿöæÏ˜™“êvË@×cHz–(½Lµéä²·!ePg—ï–S¢r©n0E{PÞî"ÑPS³hÎcG…ð,L•çá|Ц÷"x¦fÑœæ† !—h•ç|øTà>ìË‹âš.¡W'È.-;ƒ%6wæx[©OM†Q—Z Sðü©Ø|š]Îgtr“‘Ž.š$QeK”ôæPrHõÛú~{hK…¼—iÒËTÝñb>OÚØØ ô’ås²YsI¥U$õ¥sª<¡œ"&2º$ÉæDs©zO«fÃ໤ʱŸ¿/ÚGâJFÍ‚9˲¾ˆ¶qÆMbÌž¬ÂvR'’×ïTGö÷fUp'Ï‘¯È¸è" ŒÌðÌ—ÕJæ4N}a™¿ìÖª êxÈN pyíNqaí>[ä¸%ŒXmvto^ùL¦s¦åµ•qfç^#FÙ·Q… ÊzõÓDóÙΓ„¼fCV‘±W}·Bë´ìzÎ.¥Vè4ïeËî`>ë-§ˆi»ÓÂ$ò´4'|»W<Žª»å’ ’ͬëÊ`‰,B££9.¤&ÉæDÈU<ŸõG8œR"*Nt‰ô~}^¯îñ±2;ii–%Ëçds[rEˆ›®JdA#êÕ–¿¶ÎizX„…NÕx…MgK¯„1æ¦ß¡8¶HE]¾<ÑÓ+j%æ¦ï%Éçd}£þq'Ÿ¥Vþ¼>nq«± \ï5Up¾¡-Lk+¢æ>S«6tƒô  Øb,pacÎaaì_ÿÿ}Vï$Y¦½~¸K»Õ”BŒè†t=耼ªks~÷w!¶5%ã÷è!¥¾l{‡;qüƒGéØÖ”DÜâáËA"±éÛ3,ýñ!g/×™ô8ÈCzSJ¯ÛWdd?>»»Ã×Ò ¦úÖQ¾×//˜b]OAýñÍ硟ÈU\öO¾a£ãù§_¶wÇõñÛO·“S?ÅJ²Uõ’Ú_ÎE¸ÓC†RóÁ°™üƒÿJÉ;¯¤ †^ñµ¡üäOåÅÒ¾Ûõæ;ñüDé;sœÝ7úûAß)ÈOùN±XÚwæ4=BžãÄÔ­c¡î:$ðNÒ®›Rë;ðÖÿ^»6„B•IƒG×Ì7`«%ò äe¬)ùáÈõ#Ju¦|ÅîqÙM'°àlŠƒ]æ|î­/'º ð*åÖe¡{gL®•\;®þTúWÖ—„uÚa¯ëðÉžWði¿¡þНx™i³=GV‘_^þp¸û/ˆ©¬AãSÙg˜_¹èµü!æß›?e´ £Ž+jx­ÚŸl€Ùð1ße(ØššûN¿Ÿ÷{]ìNæ”i6eù€ö>¯éæ>pøÜìùÔ·ÃNèDh£U×Õ¯=êá°ÿIúÏMíA_×Oøº:@øÍj _…ÿØüMóþ²Û›uG n-fjU¾lý{´š\kÐr±Ÿ$|é “ø¥?´…[QþAÓ÷ GÓå/%æKLpr:ÎÌ©Õ÷ëí©\èdƱ;ãûƒGŸTçµ±ØyþIþEÓGŽºK¸Øùt:ÓáŠÑ¨7Ír20t¤ŸÞ ]™?_¦'˜—ÒÞ!¯«y”6Î9ö m#`«–OR°o]늼†ìy×b#8°P,à¦þC‚#T­& /áy¸†›OÔ3ð×ïÑ5ʵ%uŽùÌ Op‘HF'wø»‘ÛÊÒÀq6:ŸÐUSQçö…×Å()Ýú¶Øj{‰Q¹­, | 8n®ˆà›§õñ÷èÝÄmëJÃF0NúÆ3pöïDœ8 ÖRãeK4ô¢Ñ×Õî°\Ý.wèã?ÆóŨ\ª:­ƶèYZ©Çûúó=¾Ö´O™ºO\RYI8º@µ|Q´e\¥iâÌ']Ž–ÚÄkå÷ù_[:.àЀFT#¢ÿ®ºO×9¦£Îò#@ÁéMÓߩ˘ª´Ýë€Õh›–˜¤ŽòÿÀU¦}DÏ}D¤·“ÄßKõ¶®4lžM{ù=]®«, |dõ½Àú«Ôi.¿cW·u¥aO,ö22@q í÷ë'®²4ðÌ ´¾àÇ÷nkKC·Ë5è›Ãï©u[[:"­ÿÛÛ-·#Qôyö+RóS¦œÙŒ+³Se;Òì»Ki‰;’¨%ä$VÕþû6Ð͈’LôeUt_’Jxš pÑ-é#î0e³_<…×g^§9*bMÐÕk&úòÀWzLk‚º˜L–Ï›xýO_uœ¦º¾¯jº.ÂsèÕ&^ ÏBOjºMPÃ}YQ£žÔ0tÍ&d£ÞÊ^Ô£†n³l.êí+]Ô0tMwd¢¾¢~¦ª†¡«ΡS?ÓÕˆÏT33ytâà(袆E]Ý{}ôFñf²ÖÓ® \“Hyð ï#rQÃÐ=GF(}ô¢å0x׿ <—FwýûjÇœMU ‹ºëßW;ægÅ ðx€R\bºÈ~ýè|»øá°l€„ ýLã¡Ryô°·ÑÐU ‹º9˜á¨2ûxó0øosùõ«Ë„¤†ÅÝ©aèæbrèÔ¨ï𨛋ɠ·ÌáqŸÔ ¨Ë~Ç ÈØ}=©aè–}ÌE=ó_û6ªaè–uÌ¢S£÷uù5~¾Ã”óðÊ‹º©aQ÷<{I-ј†îyö’Zç05 Ýóì¥ h®WÅ0pϯ—ÔÒ€©aèž_/%¿NüHU C÷üzDç ¦†¡{n]ÆKf¨îyõrÛnxÉ SÃÐ=¯^¶ÌÑ%‰aàžSàrÂ7)`jºçÔãÈ£‹ªaèžSOèܰoD‚—_ :Ö+0—Ô¥ªaèžW/©y;SƒÐåðõû‹°Y¦· T£jº-32èÌl@ðl€\åíEXr™¸±˜Û"#sba ’£…¹ôÙ‹93A]ŽHP?Ø"#uf‚º‘ ~°eFhx]Ô°¾nËŒ:ÑðJv·EF\>–ùŠ5Ýyt^M@º:^Ï]§Þ“* ĸ£õŒ[h ÇZÏ(GÔ3l©‘C'fÖÎ6ÊV*§Ãh…ÕaFÔ3l©‘‰zª0ðÐá¨Ë/êÌzF9¢ž!×öùèÄÙT«'Ðlúèºu­0Ð: ^ÏmùnÔ©#L‹÷uׯ¸ “úŒëØÜÌÉaðžñ­óÍü;Í…ur¼g}ë’ or¼gåQjäMƒ÷ p}à›ïà@lL C÷ p VOM C÷ °$™EëNƒ÷,pXPÇøNƒ÷Lp Ö­M B—ã{òž†šö‘õµ³’î›±îä ¨ÏÌŽÉrûým´Zt75 ÝÌXYt#Šî3KŸfÑy«¦ˆŽæ gæ"s輤£9È™9Èapî°®jXO×)é>ÞKøî^÷êअªŠaà:åÁyÕßH¥ø˜¦£<:¯èÑE ‰z!çÝÄ™ÔAç†-º7š•ÉÀS‹î/º7š•É¡37úØÖ¬Ë¨ È¡3+ׯ\7j²èÄ ®\r1¼ó™j-™5¬ã•ëBnÐôЙ•ë€W®‹µ¹î¬\¼r]Üh)Ntx庸Ñ$Rù‘¢•k¹Ïíé©–LûHáÊuq£ ¤|̉ÛÃ¥«Ã•kq0@ÜyU÷ÈV®åúzZ¹xåZ.Pðщu%AGëJ…ñ˜éíÔÊuÀ+×…°;³éžY¹t<ê®[×Z2kxÄ+×Eáºu­%ÑÁŒ\°îv˜TKæ¡£;ñŠÂuëRt'zUƒÖH…ç׿W­¥G«Ÿvr¼çØÔj’©aèžc?Pk¦†¡{Žýp<ô±ö±&xÎ=>{æ`Ok‚çáÜÝï¹øµ@cjºçáZ2aõ|¼@Sž‡è¼iÊÔ°¨{^F<0ÑÔ t9^>o„ãÃx&š†îyøõÀDSÃÐ=Ð# YŸ)~`b1ñ<|D'~¦ø‰ÅÄóð‚Îˈ©Ö]<Ÿ5¡¹`SÃÐ=ŸÆË*ur¼ëà©&Fv4#6q<õÀÄ~`b1q<óÀD!—1ë.®o×# i£:¼/R.kôluóòAÕ°¨»n]KU¬¨(ŒM\·®¥*:|æ`1qݺ•xìx¥câúu­=ÙÑq]®Þpü:µÒqQé¸uýºÖXQQéK¡½¨3«qQé¸uý:µÒ!èp¥Ãîø®/¨•Sƒ&¥[×±S+­tÜºŽºGOÐáJÇ­ëש•ŽˆŽFÝN¬¾ç¸ÄòE®†ªöózËXVŸ¨A}ý“Eýîòô˜ô°zÛljÊiÛ§r¼­“às¹¿Žq¥UDïÄ0p[%eÁy]FÙ“†ok¥!üUþKHh¤°«†më¤61è‘|DÌm¥4_µmC¸‰ycnZXÌm•4„ý}×l«íž7ÄT}E¬ ¶Zò›Àë<½VŒèB¶rnÈ®ùFún¥I zvôýøKYÆ ­±ï›†mk¦6¯Ë$r¼³üa«¦!øµÜu}ýó‡RÈ“q[/e ‰îñ¶úÆúr¾Ù0~*nZXÄm­”Ãæ…<‘ˆ¹­–á_C uòåàjzÞ¿ÛÃx¨/5Àˆòñëf)Fž6ôå0ø¼›ïžF ¿… ÿˆïòž^š°mÚ -Û×ÓÃÞ@ÞÝÿxõhÄF¼ƒ¼Ïß>s3®==ìäýþnÞVû†4zvbxÞëë³x=§§‡áç=ÿnNú‰G´>ž÷û»¦¡Ù²zL§†¡ç s;[WõrEb?Êaðy³Ü=×ãO±&äMóž˜ö3- ;o•Ó£xa?Êaðy{ü­ªŸ_׌Ëwã@óC CÏÛc{/ò}A¨6ÞÈÝçÇ•/¿­~þOkVŸ?ìæûÕ‡}X†õ“Ôv~“ÿ Ík»¨þÝV•üÿ¯.Ûæu÷ׯŸ?üïó?~ùE~@þÏIñ¨‘þ"~þtU=¿…Uõ•€{”‚ íع/÷rpÞÙ¡P«jñ÷S;ß.+ öQ WÛûEÎ?o6b%Ë,èõ»G_ W¯øåñò¬¼ã³¤r~üa*=Š)cMRé5é¥^3Rý¶¨$Öõ’^#êmÍ(ñô¡’X#t¢šÊÑ:g_EYµõ×§§ô×õ;Ô©„.ßqüA¢4à]ôëÊl¬ŸjÎ`*ûoÎã¼ÚK”W„>""¦„ÅW—ØSÙ‹p‰Lˆ®„Œ­Ž&SùIó9hýB˜ñˤ‚ÅT—qSùá;¨òv⣮^Ž*†­–júñb”•[µ•z¾Lû‹šPå;×Ãðu7Œ/m¸~Ô =iaغpËbËv(ÂiGtÕÃðuçâ~ÑyÊþujsã`¯—WÉÙœräqnÛT—ÙøÇÇQão‚P’á¦\1Ôò»Ðfào#­y†4²¿…êU{ˆ—Ï#¿‡NkâfåWÓÿÿ毯xŽY“#7’-üÜó+dýxͦ‹ûbš3®jTêú”Õê;O´Hfdft‘ *HÖÒ׿¿îX"€á,¼Ìf¤‰s‹;ÖäxùËþ»ÿóæ»ÿüîÿe—þõnù·Ù!ý5}N‹ô´O¿ÿîþssÚçOÙé>}ÿÝ!¹\:åŸNøåû/ç~¾ä·bŸÂWé_öÙÿÝ9¹¾ÂÏ/—Ãî5»\ó—"9îvçþß«ïß)þñŸÿã¥Èoçÿúó÷ßýï÷ÿö§? †½É`0÷Öóù¼ÿÕ›LóÅê»7ÿÇŸãàéÈ@Pš EÈÓ3¯ģџÒèsáé™nAB‘^Ò+« "Í sªf;tK,2.ׄ×f‡%Q³PÙ e…é4صþåµûqáÕ?.ü~—ãGãx0YÉ’Ÿ®ƒ¤¡øh#‰ø´/‰o&uâÙéšÂÈxÍòÓn÷{ò¿÷qiT g~ I1¤Š`ðŠê† zEÓQÄ'ðúoÂPÒ†kW4K(×®µE|bpŠê"¨~ÑT¹uí"r~K$ÍʹkÁß&>‘Û„“ÛDì_ÓGnSHLš-Ö´¦ý[Òlˆúcv I±%ŠôÙE $IĬG1ä4D¿éÈ_BÒD=§c~IAôœ>LøE $MÑs:æGö[bÒd}'Ì’Ý{R 4!DÿéÄ!"IÂBÚ¢?vâhË©ü”.çds£¬¹K“#§Éú“QC ?Â6ÊŽa/ä|F‚£ÚT1æUœy8#­œåLFæL²SrxÙí“C³ïñë‹H ½þ"( ý|ÎOééš%>(Mˆtö„?žéço¢§Ä¦É’ÑÛ ­¿óÉ@,m¯5Ѿ1Ò,m zNL ;¶Ãq(`4â2k ~¼®ÙùÀèLTˆ4 rnp¾rÖu‰F£.c¯ê¿3öˆE£-]‡FÚg†Å|ݶ~/F] Ô/=6F#.ÃÇ&â_Ž¬ÞæEáÑèK/§>xL¼AW H°–~æ`àlDеPç}3‚H ,0tvÖÉüâO—h Ý!lÄ€ƒé î_(éÏ»Ý>?3 J6ºrÂÔq{e|/FS—h4êj, SI¯,;æ4yG£¯¦0ýì”1 Lš¼D£QWýK˜ºÌ”¯Úh<}Õ»4ÐÏNÇ„!rÒeTx$úÐ'¶ô6ù™#ŒÕä%º\klè(ÏEΰAKS—h4ê*Ø Wš"ÿ´Ï&“5yG£¯b§0ýËíQæÌ×j Hš‚4ˆø”0VŸ‹@£QW¾|˜úÇ,ýÄWôD}¬k¾3é§êKt'RãÐèÊ’‚ï[›ìƒ^®Šdÿ!½ÂY†Â®ÒÈÑ5,V­Ø¸ ,mô…hïóÓG˜OY …¥-Dšé„$<_òh`*ûF].x†¨¿àÔö‰‰¹#‡¥|ôf†kgiGþ?Ø«h”åX:ܸá[Ú2þp"CŒávãt…9l;`(X C+UÙíz /ÙÝî˜]Xr.ÑhÔeצ~>$P3¢ï­9Jê F]vyaêÓ—„agµ¢®ÐhÔe—¤.ëK|çDº£—Ë‘AâÒ~Lĉ8,a_$.­ÇD\шËÀa4vÞÅúÍsvÅ)º ÇØŽKT& M€ìɈI”!ã‹6éGÜÎÃÝL4*QŠœm“ 1û¸»]³CÜþÖµ‹‰L”$cŒ6IŇÈS®I!c ‚ˆoЃJ”¢Fð–1¥ø0ân*’(B:åíö}{HT¢墴ÚcvŽ_øZˆ% ‘Žy»Mö‘×4}:“&£/'§Ûe<"_èÓ!@‰BhÎ#Lv³ûŽ“(£ÉuÌ>Æ•׋0$?w g§[X·ož€#:Ç\‰-nVÞ'§ü”Ew‘}—&G.1·Éá92h)¡Ÿ ”OÕbžÓw–ú¼Ñ@yQ-"ŒìãŽÞNÕ²i•KNu¶U.™qd¿= PiR”OÕhø=•ib¥ü¨ñt·…TÑ·x*#+4Z™+¿©º¼g÷”ß9f¦J5\šå=µËy>äðŸI”K£Ž¬›6T+•ë!?½|3Yà4aʧ [‰»²i<}åK…é3W®»*•šv “‡»5ùÚ…£•ºšf ·*b÷k¬0o$ènÊ¥ QmÍBøL€ ˆŽù°Å1Ow—×¼`¬> ŽVî-nxº»ñÓ ŽF¾Åýò¬íV¢Ñ¨·8Ý@]VA®&«àhäÕ”e¸±Þ˜«¼Æ£Ño‰ÒÚÆ[ó-Pš–Ø Rs¹*•–Tƒ§‰kj¹3û~tš´Öø¢–¹5ž~#ãYh2[ã%S;šÌÊ4,I ܶ.–ûÃ}žómªá=Þî¨5ÒPRXO“f‘ÖˆCeiÕ\æ:faÓdµÆ"†,>‡Ø¥ iMTžÌ¾‚J“Ò¨L™e•&¥5ZÑ™~‹Ö‡=j\´lƒì åzÔÇh)ߦ©Üå]Z#)†Û"Äh~ÔÛ°ñ&^ÈÑ|6r¶Mžó×Ýî)òÒ¾Xß(‘H}:~2Âxm)Sd”ÂÖC†5&‹F[ö8³‰s·¼,i±s~·¿=f §<4²yÎ&°KØWöRÄï·ä ßêebÀÒÄÈH~æ^…'‹ç_ßÀ$6&M† ugSç-KÓ2²hJÅËÈ íÍ@ƒ·b© wïŠÃ’ª9m*1pI6YÊèb»»kr~/8Ü ‰B£*#†U؇ž¥póF‘fð<Ø¿sl…Dî.,mOÎRF A1¢\¢o©— $Í2BÒ¾ä±7Ÿã@,y+0qÕ…ÂEïµz^$§§ NIïà)¤S~;ÞòaÒdÈ©ÐY£Œkß«0 ¼êÿ›Èg/ÉíÂp°»â¯iä”fcùg§üoäí®g†-7†–&F eö¹rV(U~ÄJ—`â„e“Eö ÌW0<&PÚB’¬ ^¨jðš]žsªøK<}å@4T¢§¬Èö¯‡”áÞR‚I“¡œ‹F—}‘Â% Ñ‡eC…†¤‰PN…{3l™cZÀ+¤ 9;€4ʽhÀù i¥ÂD¥I‘³f)çœásS…¤ PÓ žÑqbl F_N66•ÿóvò5f G#¯f/Êþ%99ý<…G£/'›ÊžÛÍSx4ú:Vp.Ø.[’ÈîšÀéA¾úc`ÒdèX¡EÆ¿2Îñ@¨4:fh‘æÇb˜Ä«ì_aÒd踡AÆíø˜²Ö'H c…°€×/°/’³*i@’xÜBÆ aà=% ï–µHÒ¨†1áÀÝÔOÌ "M‚Žl~äŒÔŽF^G äó—¤È®¯GÖ¾è`¢Ò¤´Ç )øvÜ:$MD{¬"NyqäXe«ZD…I“Ñ'ˆ›°Øça,Tš”öˆáôXÎîÄ^)-b`Òd´Gç&rFßOÒ´Gç$þÕ*8Q_AÒ´Çç<»\8®¬hDš„ö¢H¾Òì啱U4íÄåõöüÌñÜii‡‘&¡=~¸œ_Ó‚sVOÒ´GWæi…G£ß7|J³GXvcl%"I\Ïß9Äß*¥*?m«Ô¸¯Ê|ëv€8Ën]Q܈D£¬]V?å ì«L9vc!k F"®n7 ¹­W8{ÂÔ›H(éf·sê³Íæ—h4êÍÎëZøå|ƒóz\¥nÒ4;²W®hh„›Ø+ìÑc«â‹F»Ù½8åaw"h”›XÈhÈ™),íf÷õcÂåO $åf×õŒ6°ÉëÔ1õ"& M@³û¯—ë-h”›X†o<{N":•ó}󾻨­žwÍ.ðb0<ÀP;DšéN5H(XžoVÿ=J4u¸WëÃÔ­§a£où“åoaÒdH+,ã99\ÒsÎ1tJ  M€t´<=s½xªªÑÏŽgÒÕjÀ-@ãÑ, ¯0}ý¶%S#Ðp4òÒý “W\vÏݾX[U…F£.ݰ0uèý¸Õ<þ9-Ùp5¼tÆÈ_ÓççôijÓU 0 i"¤{Áà, q¢»0—ÓDó‘ã.À  É æð_ñk‹F*繜( Q_βhhnÙBúóɸ~ßÊ.‰‡bƫ⣷I‹TÆ 9ýÙH;;1ÌÜV̼ª Me—r»€£‘WNp yæÂþôò_*/2(áöxá¸CÕ…F*ý¥r¾š©s¾`GÙ+÷+ €çŠ{QðŠVêÊí ÖwÇöºm F#®œ®q¦»Áï;n/•» Ír° -h%­œ«eëÞm–zb!Ò$ÈٯИÊsm±(v E#Ýì¿0]P,X+,ífÿ…éÞnAûŽnÆKå•j9Ïó6’õM³ÙÝbzØF²¾§f« S÷z_™gÕ¾çÆíñR{ˆÎ½Ä‚¸¼n›éµE‘Ô<áê1]({%AÅ,ýy “&C;º–àô”Š{œ•š2m¶ŸO $ÐûŸ•öÙ­`ל5ʦU+í÷ b˜ëÀY e’;:וöè%pv±JÃ=NÄJ{÷"8} %â—b¥}ýfìí›þôÇx¥}ÿf ²zr6í;ý¯´÷ß,â4‰»œ•Žšd°vKÄ ï•Ž¼Äy©n”ƒ·pçæÏéþùvÚïvIV|ÙÁ5ï “˜LÒ0¶UN^«Œ¥Ã2[‡¥ Qn^›n[·Âm•ƒ×Hÿšœpˆ¿QYACÒl œ¼&éå’vÉñ¼;¿&†«Lª:åbÓd)Wï.YÑloE[õÚ*÷ ‹aC£#0iÖQ AÆ çüJ¢œ@І³®ê)À­r)B8V¯ËÞLµÿ”få’„0œ£rMr¢ž¨Ú*— 埜Œ2 `Ò,¢D‚ŒÿþAiBÔ$2EÈ·hìÿMnìjb™"ä[4öÿ&7v5ÕLò-ûÓ;!6Q ïÃ7hì€Ii#Ê h‚E~úAiB±‰²ÇOߢ±#(M!JÑB¾Ecÿ‰ØØ'=z¤ò6»î'¬ Àgñœ‘] ÒlBNòÃGÞÉU.M=*‘ÙòZ —&‡\Òßoé‰ãFt§¶UÐ4QôHåšß"ÆW¸49ôxEfË_å.M=ja¸½Þ©k€I“AXþç[ŒþJBYþç[ŒþJBYþç[ŒþJBYþ盌þ•&…µpÏà«ÁŸ>‡?é‘ã~ŒXµàõt±i¦=faXͪM|ÑV¶&}R´rMvÙ‰c{¾!Bc’ZFŸ«p”u¬(!i"´kØ$ÞaÎpwøå°MÙ ö60MvÛqö±J µ“Õ®a³ˆó!ã¸È¨ÎùMaÒl¡ÃOÉ'–ó”•H“ ]Â& éãÖðIÒhW°I@o3q¶†' H Àé!=Â¥ IÁ4)Úýk”šu Dzˆ$ êAˆù¢YÂ?VÏ $Dšíþ5I(žy<}íö5Ò/ò‚ÓoJ H §¦›|„gâg¡RG£¯§£›è>sv§)ÂÑÈëÉçfòÜ=Ðç³@¤IÐqC«„!³ @@ÒDb‡g¸G+Û=eo_jÁÒÄbñ`5w@m€Ò„b¦—¾+wõާ¾'BÜ𒾤§Ç䯻Pf¢ÒlAˆä“ûޖuVÙD¥I!Ä*Óþ7‘"PiRÑ„’2ز.Z˜¨4)„¸¢Ìô[T°ÖšB\¡¤üsL¬0I2Ô3±…Ì’_ÑCBl¡$0z·‘fB|qH^`üàx¦³+Lš B”qHŽ)ËÍGå”f IAˆ58ž?é.Zäl6.M!ú(³ýëãb§Ê0º.M!)åœóëäT ˜&ˆ•”ùþߦ¶!,M !*Ñb8§*Lš BLÂ<{+àhä ñÈ1¹¾fém—œ^ðP!gæ@ÓD"3^?õñ[HRÀ4A„ø¤”ØßD¦ "D)ZP‘<}«jWBÓDâ-êS^|¸œÞ­–pš0BôrÎ÷¯œµNâ‘è«WL£–sþ æ¾XWuJHšBÜr¾°ž’p4ò„ˆ¥€GI 8ŒËu•4„x¥H/,¯WA—F¤I D+—Wæv iñÉ%ã>¢®i1ÉåËiÿZäׂ7`´`ibñˆ|µˆçþâ2X4@iB±ÈµÈX÷`H<}B ò¯”w§¡Ä£ÑoBø†âÕ…tÉ—=÷ÂnÜ€Å2ŽIR /¤ ·„-©½Éd0_¬¾{ó¾ÃW®/×äš]®Ùþ·Å<^žRŽhȃI’¡®Œn‘±Ï?&E–ðd2¤˜¸49Ò¥h‘óáV\óKÆð˜ŠY*Tš92·H)bŽ…Ã&‘&Af-Ž)Ë{†‰H“ ÇV OÐ:¢5K„ĤÉ8m2²Ó‘ãù5³U&M†œåh‘qÞ}›ÞÊÄ¥É!!¿ßàù˜ìÀñl¢i–$f%ãéÛ\>¤ŸxÛ‰D¤I ×kzá˜×0Úº‚¤‰ ߦ…T¨4)¤ñãÓ·p²JPšÒ(ò©ò¢ßM`T.–&†4–|âÖ$M„I`FØ}ÿÄß])Hš=~4‹¨Zkµª`IbàÎMYËéäf+0=Ób(¸£Yk°Ñì ᎛Ô'k9©Übþ¦pÏ=ꓵö^ìÀ92ÐfǧCÕ M掿z;îv‡ôcvÚq\jf¡Q:ÐéPõ>ÍÔ¯ÏN(ƒ¿‚¤‰PýO@î>a+~ F#®úF✅/ÙßUöªßñJ`h«·#±‘ŽÑ™ûÔÁX ‚3‹GŽÉz‹TEFjåmæ/Ĭž÷GŽ£´Ü¶œ»Ë…˜ìÿÏ9&é ,m`+¢\xç·>ï€Ye§Àœa‚Ô£WÑm€øáé¹gr»F`ï³y«&2/ÑhÔUL¢ž¿ô¹Šö#¶Šc´õ Kk0q5ä,gÞ:~†]bL5\BÑH«NpãVo?Áa“3ÃqF]Íe†©?ÃòQü"×Ô%ºêÅÃÔaïC?®©K4u5ù¦®MìªÉk<}pQÄ@¦ŸŸ9ÎKkòF] Eaêç"gèÑ5u‰F£®†¢0õ"ÍŽ|MU¢Ñ¨«á(Lýr{”EÂÇ߀¤‰P“« ">%ŒUç"ÐhÔÕDj˜:wák<}5Ñ@?ãØ íGF£®&0Z¨G_N°¨“ÞƒšNÔ´Eº^ê~Œ²×w G+wåGÉïóãù~Ž? Ø—x4új6 þÎZTa2„’bcÓd© ÔVYL«„¶mvw¬N'm>¿.%]m™£aivi‹xÖε9à(qÖlÒðV¤»*P[ À²Ì¬Šœ¼5¶ùþߢG²0I5~Ú𬦩â—`4âmQÓšb~ÇRòtÚ0-#+êw,!O§m¾?Ïò±f~GsmóüÕ".ÓètÇ’ñtÚæõëµ[.îwÕõ¿ŸËï$Ž£ é믆Î1¼uÉàä#C„¢€HÝàBú÷Ÿ’pÓðu·{¼È³_Ñëri¤ß$á)¹=¦{¸ïƒá¸Q©Â¥ ‘^}£O ±•D£Q—^|õ×¼Q¾:$áhä¥×ÞD^ #ÿ‘&Aúïa ñûM˜6)¢Žn† žØ(#©”×Òg\/õE58´š^ ¯LxBî$‰_U|˜4rL…u¯pf6)ØÍ”<1܃VÇ#Ñß÷wÑ:Ë÷Yš¦ÿ~ƒsZ°<ž"ùý3ž3vÿL“ ¼ÉEÂîÚ3ÃçÈ“àŽ$ UhÑ›9;øLÇäCº+Rn,QŒð=ðÙ¬q.0Zˆ:€9Q˜DÂ}p5}œÆ´I‘&‘¶£BBEˆ±xѯê"ò§ôßqi®Ìßí^Ò¤ˆ¼KÈð…ˆi©EâìCsò0Ô*(MÈV z‹þÒ i¬<‹ƒK{“šk“–$f6±ðbîG­\žwòa½øn‡E-fT.æ§*ANúÝ­èq¥‰E£-â²Å| §Êìþ³’ol±v‰E£-Bpñ`†Ö¡dðÖGQK aáû/ð¾ K´Ë§³8HW`$âà;Àö î+iõ\m E#-»ÃEßqÝ V˲X8‹·¸HaËl(&]‹»M(‹7±X(K$Z)Ë~z1pÜ(eã,Þ&¼ì¯C÷Z"$qÇ¹Ç ŠFZöÖ‹¡³÷R”¸x芧´%´ê«‡¾á<-žYºjC£«zê‘·Œá5%–F]yÅèb1òuu°Ñœ­+(iÕ?}ƒŠùÈGY[x4úªï˜:SLÐ å›<ĉ²\Ó[€Síñ?ŒxXxW¯ Ñê¸\[,`áÆužô±ÆÀ´ŠV⪒ÀÅq.éòÁ Žò®ÀhÄÕ ³ô5NýFoù±’¨aféë«‹õªIF+o5ଜ)!¨rxŸ>KY#‰.´A¬œ™] «îùf¡\bÑh«!–Üæ¨/Äæ(é‹F[…p¬ßCnÝf¡Œ84º*$Xû|=ua4c E#­zjw£&Ôhófbæ¾ê¯7¾2¯n#æ o Ñ¨«>{ë›4—ó°†Û•‰õ[õÕ[ß #®æ ,H% óÁØ[/{žÊÁÑwPÊuºÙÂÕz<]má´Þz1˜.¶xIðoù§ô°yÊ®Ñ,>%Çô»ÿ´ÊS´OŸ®y~¸¼±h´—úb>]NûãÑl6FßoÖôW=”ƒJÖ°x‹‹Ïï“ÇC SQ±¢_%,éH ~wÉo°-R,¦?ÿÇKS•ÿÓøÿûý¿ýéOƒaÅΕX¨k b#Õ¶P¬xê4´¶£#’R9QàR \µÜŸÏ{—gX—=Ÿ¿ÿ.(S¤¶ _Ql¹R'Ø]T¶ü-ß'‡÷ðÖðõ}–ñk­¯´æÏïVÐ"]B¤†¹êK}}p^CúâVT›ºQK]]Äê¹*M 6ÃJ»nÖ”™Ó£T#W½>¼?;šL§Ó8ÀÃÅp8×ǯòâ|ƒ}‚ñUUHe |ÎOoÌŸÛÚ¨ô• °‘£"ŽË z E´ê öŸ¹%w¸Êá¿/ü%ŽÇ:¡Õ ðîAGoºíAMÖëùR Ê›þ‘žr¸l¹µ2Átê!Ûg×-ÜðþˇD‰»‡Uvüû¿äÿOöoNðsvz¯FUn•z6›ÞÀÿWDÚ;³HA°^îµ^Ut«ªeË Ô®í 7Šõ&Ë®ô&³õr¬]¥¼€ýa·ã%nŒNA…TZäòåò¦žÔRÇú›ñv>í-VpÁ)Î化½éb†jÖïÿO>íÞ§Ÿ¯?ÙÝ›&‡½ï¿;$—ëO§üÓ)Pùp°PMÞ…+eiWÈ÷I›¼íd:cm‡ƒÎý,akßfòÎ Ìûìa·<4ûxÈ÷ ÒÇÝ-ãGlm4}”»úPεHˆÓ~”¯æ•ÐÞd„˜¯@ [h2–Øüöòx{†èÅoBÑÊf)€ô²-#D:v¤ÛKzЛô“þp;êÍ )÷¶ƒA¯?Çú.âÁø#Ÿã´_+­¥á‚QBÆ“LéBÞ%°‹xu+>2D¢u¬Rú#nb«¦õd“Gýyo1†áo°/6"È~€i£ÓËEöÝàêz—¾œòc–8mg£z5Ö?¡TQ5¨ápWé{¸Ã›S£Æóª«)ºÔ趶ܬ)×|÷ Æqë.—:ÕÑèû„ t¬Æ¾µåd[JyF=dX£¤DjŒc5ÒÙ;tmˆÝ¹hKJõ#Å@r°ô­NÒØ'½OOð¤ÃX.>}ÂmÁ ßQDË¡o€àUýÊ\W ¥yçB½ 5±o(Bå8À›çêB—»3Uò¯ð¼òÌäveóœñèÍ–ƒ1ìŠ[ ¶ÛÍK<ä78û„矌^”ãhW#p©Ï´|Ù&}=—½År¶œmañ¢?[M'⤈Z¸ßž”_µíV©ÍجÚ;ÏÍx=÷6ëùb„aÂ`0\×hD±¡Zns‹zìÀÄ)eèùvb›UPËTi«Ô´|Í9<8ÆÙvÚÀ8†WíA¯NOXJ$šQà¬ïäò‰©£Üž“ë+œluét‚uàV5†Ë« Q¿¦—ü”D¿òÀqꙕÖ&d;\ `×Å ·éãAÜÙj1žŠÛKD¿>Ú'±tɳ*ëG-%V½]X{=Ü7¤ƒÙ’UJéá î…H‹‚gìªã•ê°¿s[,gZWK8:O×Kìô&›©¹~¸eë"ùçÉp=>¡ï`ÝÎÅ´Ôù’[õmKð9VpŠíG°¦“ vê¿üýíóóuO ÄŸP0±JEÒo´“ÚÔ ¶8º„£¤ÛøãÍ`=§¬³sò,ž¿ÜI1Ý/ë+†]/j)ðCR¼ |AÑÙ'è|÷G“þ¸N‰Ú¤SAÑ9ðéÄw"ÅS¬w×ίg‚YªìŠ˜a£˜;½'ŠÃç(ÙV.VAógŠ„‘OÂßOÞs±N®É½W2Ü©ÂB²¬QKiÓ2œlàò&›‡x$¬·.'ý>ö|j1'9röp6h)Gf/­Öy2W0+2¡›÷ÈL?'E? Cr§Hðzk¡ˆ’Q‡õIu¿i³é¨7ØÀüÈz°™áâÍdÜ Ä@?žžsuìûÎFFPh´1§”„ž‡Ð¦c¼n}ðèÇkˆNzÓÍx³ãØæ×wÕE0-“U8\©G\åbi¯… h WìAÐÚ|‚¢Ú¥Ru~¶Œö“êC¸‰Â‘Í .ëCí‚MÃ…€•[y3Qòb–¦$]ë:li'Ããu¿i«‚(v$ÅâŽØOEvM1[F¥¦Ofíƒ6Óþ ¯¿O7p@¿×›‡Óᇀ·ùÇŒáÞ ¦Tƒ]½õ;EôsÖtÈ!¥H˜„%Dí$ùªW(Ë{õvâpUŸÏ'XªU ÕSǧ¯Üò¯R(RàÎ0”2…Õ;¿”vo»ƒAGX¤å‚¢D…k•5†;:ûÃþv3ƒ—îẔíx&â[å‡\o0›k¯,;Ç}˜–<ÿmçÓAL7˜m6Â]è W3qùŒpñgÿJR‰X5t{#BúÐ }pÀÛ1éßLÜç­QlåjºRѦ´{¤ Ö`¢ƒfQno$x7û[MÔ$€ü`*ÈÃem&y¹ç[åß¹´à,+ÔRZëÿf;+–p!× &}zËÉr²˜ŠHN:H°£¯}º(¤„¦õðÆ,•î˜ÁˆÐ>6¸çs9˜Žç¸‚TÉ+çŽÍ%Ð;GŠD+¾QÓÕd)QÏøû™Q¤Žk:ß,·P5+©ÊÃÎ Œã4£Æ+6¬ÒÚëçÔ,«éT\ŽX¯ŸÉ.Fä”Uút‰m–°¬¹€™“Åf»‚y×Ád ObÃËóÝjñËî¿þø~³[<ì6¿¬þ¶þñèm[º•ZÏxgí ÃZB›>k“¼Ç{þ!Üy’‡ð¬êLDæMŠc³`‘¯$5`JMè²Z¿DŒáâÞÁžn„Å#"¾ÛPÖ‹‚j¶Äè´A¸a·±÷'Cql{9Œ—bÞŒ}Ê‹ñåX@¥eð%ö7µ¤6-Ã%Ε,«þ× ‡ëÉd#j˜ê¿Á6ϯ:ÆIiMþáÌÄ,Å}¡NP¸„^~±‚µ]pø*…rÈíˆ7ɳô‡uÀRÖB7‘"lÓ*,nh±®œ[GP{t;‚šÛÑNC<‰ZÙéçkr©v>2Ú+lÙ-üÁ~0D׎^¶=CŸ´Ê\õ ~™Cx6Ê´+¬ŽÂãHxúk:LJ÷b¸’u°Ò†ðÊõ›JQkSMª"»g#ª¬©!D—#¸¼v:ö){¬LcàØV±(­©^;j«ØµKaxèS-0Zàë’¾F€FòȨ’Úí‹ fÓãÛU7Žw5Ùã oä»ÈM˜*RŽÛµ5àÚB?$ÈçBÈÆ‡Õ+Ù¢j¨{¾â‘¥¯±£‰fKtÈ´ÉÐ= úØ}ƒ=ƒÂ"÷tëzWWK"Xiˆ}ˆ™ÀLe%Ëö‘åÔ°l 9‰Ið¶HôVVÅ{—d…™CO†¾¡è„ý,í:#[¯Î¿^#}émÚV#xv®?X-`Ñ\¤-\Q>›C~„{xîì¥Ê 5„mïVÓÅnÊYoÖp+W‹Í|)6›¯rˆOpUÛþ‹h ÷GWµØÑ‡éóÔjÐ ûjQ'.N7èŒj+‡|åŸkÃù>iQ7žLà¨þhÛŸõ±ò‡½éjhìL¢ÍÐצÒî·ŸZŒò­5Ô“Úæ°Bmj8† §JÑn;±$ÞøÕX5(§&:éQ°n…¢&àW…D1,ÙÔÍ…!] =_´Êƒº·„3;CX/‚‘y—Š,Ä™ñðÒî%½¾ÇÝQmVƒ*m†SONEÐZ ‚í;A¿%‡[ʤHaù%•‰MCxñŒ4CGXizŸåž¾Å)9|¹dêÑŽ£U-Ð¥bœ’jý–PÐø°V¸?¿*†çÁD)¨¬•„¡z ~8¼H|Ï›UÄõ…øÏ›ÙH–ŒzÅ ²³Ø.Àç­ÔüP$çWXá¨xu,K‘›Ø¦i:ƒ7©zÛm¶5€­¤s±­bõfÒöνƒ 16ž¥ªžDÑ4lѵG7WÎ6;¡UÇ|6‡W Øø†WŽqÙX¬:§éþõáËéúš^²ÁÉ#ëq½v{ýa· &à[”,GgŸPJ½»D¢Z»¥,ª@,‰öh<…š®&¡8b §´Ýþò+ŠÉ!N Håµ² K#çpJ|Ý͆‹œ¡†=È˹\l‡íÜ_3yBˆ–~O[ƒ”öÛ¬ª_Ûìƒô7ú•JɪnŠ>­r!yx^Ù[öq]d¤]õ š4¡é/æ}ˆ›‹þ ö°Â\âx´”ÔáM³øÕ¥)«‹®ûFJ[•A 〄¸¥Žï¾U¥nP§4T¤ Gœ±äñò¦ªäHn°ž˜œÞfŸ¯7xö+æÛïk´^@Ç"¯Ö£í2ãZªFÞc5ÏmÒV0‰'ަËÕª3‡k8G;û¤¡5âvŒø–³€J‹©æ_Qh£”eƒ¦®WobñI¡uÁ(dÕ$$ꨮìaT/ÔNa3ZÀ¹u/~iÌùj5]‹ $œ7Âû-ä&GdèG,-#f"¼¤ÚkŒðp+Øîu€; á,áäžØ®õ·÷oo‡k¿áX@¥&±õ¬–ÔÖ  ˆxƒZ8ZŽ¢,[ˆÚhj¡5TqnXIÔ¦£5Tã©¥€àÊ xp4È_­þ·‡³L?(5¤·Ž™É”z6nWÇa#EÛo©*±],ö EC|ĸêÔJ ÚŸ£õÔàlK9‰U¥ fÀ*Uò€QTUÐÆ³UÕÓ¢ÀBØ´†8e^‰úÛûÀJÇ„ÁשAÙ‚œDŠ"91̆W´ëóâªóÓ¥[&StÉá(¬ëóî˜Â¦%ØvßÞþá©=C¢…²_ZûŠ"XŽZM‚ÉWù寡nõV° rÍ(jåרöËã›–i‘˜M:õ‘r¨ky…ëlné¯yÎršÞÒjC7H®HQ>iìgY›¬ôm‡RõH2‰¢gÚ¬'²Ã¢é:Ί‘@Q1kTQ9r-gµ:×ËšXj ùE㜢‘Ç^•é­}Ur‹®I½\â‹¶ÃÉ—Œ—p3ÝJÔÇäi÷ˆGµXìþá/ûÒ%HkLŒDW}ItŒ÷±9Dã¼*^M´=ÌD!¢{ñq¤¹<ƒ«Æ¡•ë0D÷)ŸàÜTìJPÑã‹=PcÝŠ ó‰^J aØUí'üœ}NᎬØå«`hdáβ&²ÑËV’%6µi,^ð4@ô’•0´’5“_²‚,±dç!²/‡ü^–ˆÎVãÐÊv¢ûz{~†iŠøU¡¢^¶Ž^Àš0±BÀøëïÉ—´Æ/`C+ßu ÝèÅ«èKwÓH·?`*^¢•¯rÝAXè†|x H„×ø$¶×k€#k)Î¥Æ+4nÐÛUÙD/^C£ôy/¸qŽ¡p% lÐã•dã­ K¬·Ao÷ ²œsC+Ù §+s‰^² †F6èé~L <²¿Ö–@4ÂAoWç½|K a¿Ç{g!âð:–04¢~orˆ[¢@!¸šÊÑkÞÇkÉÊÉçC²Çiš#¼Ž·²ÚH4Êr P†!7úÔ‚&­±h´åH -®ƒÜéjÚ‹F[Ži>Úûó¡rU9¢y©pkYL?L”íQhTåxæ£Ê0u#ÈÞ1wï@ ×Gwûó/=DŽÛã ŠVÆrT “¾\Ò"Ö©@5V¼ºß‚Ô÷PàÉþCÜQ¤"_áÑèËQ/H–cr¾’×h4êr¾'Hýß®e«4F]Îü©Ãîƒäé+^½ îjvj|…G£/ç‚ôóâ)ƒ¢±.-tèWx4úr^(H_F½°ÅR.}Duÿª†[G¥I‘sFmRà†±ŠÃ+¥D¥I‘³I>)χr|§@áèÎÂÞ¸ê øÊŽæÇÀ8…“_¾ò=œ9\.B+Û°ÿ}|3TB£ö¹p ·øÂÁVч=o= ìà ŽßC„íoÑq(MHØ//óÌÿ ÏÛrªÐˆ4 a_ý\d“kÊä®[h4êa½Ì AÀˆ0þ ã Ò$„=w¡žWá“P"Ò$„½wC‚šû`¡1i2ž¼!CÍ…°ÊИ4a¯^ËàmF=ìÑ—ÔaÆ„¯ìq~†6-: {óšºÚNÒýX Í`¤†G+ù°_f'Ü_¾²—n0±ôÃ^{IŸ+¯’Ê.ü¹Å:?t\ùJ_ Ñ¨‡=zMY>êF=ìá—Ô¥WËÈ^Ò„ýþJÛ$Ž IŽtŽjVB…ò»gØ>7>2Ö©šÀpŒ ~ÊNOù'FA& )BȯܤOl1‚…G£ß%èìê_ Ãtš&ª)n¨å\Nñ‹*¡i¢Â‘Äå5;6ä>ñ{c F==ÔªVüÙŒ: M@8n°{?†‰Œ: M@8z°ó+Ç6KÔ.Ú\é<S¨î;¾ ÔnÑh¾í÷Û¼RZà ò ‡7û>È‹÷¿æ²ˆ;ʠoà«¥´Fšô“Ao=î÷6#¼"k›-W÷psWÔCêš.uU¥†³$9im¢ÖkxÔ¹uj½šÁ)q¸Tt&/Ðþá–ý Ï%up,γäX¿¤ áfÔ~Ûßàƒ®¦6T— £ÐŸHúÛ:ý·p„œM‚«Ë¨~o•²™lÆýá|³Æ=xS{4XŠ‹DåÕ?¿[í²ßkÝf×AÝr1Ka@ä/™¢o*õA3ô=àíÞâÎUz†ñåÆr†ÕRú„¢î×GKÂ#=^¥PˆCÞ³v¹~¥@ô•©iðP2JY•ÔBÚùãÔ v«ÐÀ µ>¢è…'P/\%k˜RÝ’²|xà°£VjÓ÷ïÕ“)ªàéT5‡kÜê] ˆbïjLLGŸìnìOq*Sh„‘¡®q|ÌžØUÚ¨õ(J‡R)¾Ô\WúvÍoM3 Òþ„¢Q Ž+x½¹Ò/åì‹ æ°à¹ËÝ»ä +Ý§Ý VZ_àÁö¼[GË?Ü(8e@úJ¡¨umUñŸPl/¸ØhŽÔz2E•=7Öó6ðç3³q½ ŽÆÀW©j4Å»ã«Z­òƒËÓžZa©Ç^ÐT›Z{L»ÞL¶j ÝZÞßÛô°ÍÐl…øv»bqŒü¨®X/9šZ5Àâ å†a¹ô)WQ™Ð^9Å@'ãÞe×ý«ù²;CëÃt´ù?¢è”Ãç¤WsV¶z—¾¼À#§vUï|â·æ²ûQ]­^r”š9íÉt2°Æ Ä=åÇ ®à°§…æUW‘¡©’#áÞ 4løkzÉO¸õC”æhª¥Rª¥'xOU-ÊpYö›ËäôC]×þ¢Yއ¸ØÑÌÛ¥ 3 µþE§ 'xÖ¾²­ñ,¦|iõ·5‡i°ŽÚàw-‚§#œ íÁ¬ét¯…õF«Õv$J”‘]yµóÎ÷©àT)'µ´6A“¼™7V¯¦Ë!>"0Ý®{SœÖVcÐévŒuZBɱ€J1xGu-¥]ÊvÚG)³ùÌ’ò69eç„à€ÊëÇ8.á£Z"›>kS¼\Wchu°$½Lo6.fÂxj!÷:^¡Ms4=d©k¦7½Mà ŽàRÅív6€B˜Ó‡^kçO¿ü²»¾¢>–ˆ¢W ƒ»Ì ”{|“’7Î7qp7!Šƒ¹«€¸8ëڪ陔«ƒ!Qíûî¦ëÑvMpÞ‡wXa––þzƒÚëårØíóãùwÄîŽÑO„{àZ}/$þ _õÆð?j䟞w»G8ýw©[¯ ZI϶p©38ŒðVÐ_›ŽÖã­x—mÖ¤*[Ååš\ß?·4„ùx¶ÂBýv½˜® ¤Í'ýík ,‚k˜>¤qX¢u¬ƒõ"²R˜'µUÜr¸…uãþxÏ ÁÛ½½Ál- y-oW¸f–Ð;w#¬‚«‹2SÚ`­×¢X‚þ¦Žµ0Yª‚« 2SÚÍÇ#ðÖ‹õ|<àÊþlÚë•¿üý-Á6xÚUÁ”ÀåzSþF!¯ŽøÉGu´ÚŽCT?ÂÂa÷ó÷P-Õ‰\ƒVOaS°ßøEœøÎ¦I è¶ÚG­·üÇçÈO@i ZijÕG3vi"MbijÿÔ¥ù9zÝ|| ZijßÔG3~i~¦–¦ö ê4ŸŽçè¥)0h¥©½'ÍØ¥‰4‰uS{NušÏ¯£—¦À ”& ô›˜EìÒ4š!é…¡n Í·„YÄ.MA£ò”^#_¡£À Ñ yI˜EìÒ4š!)Ëcm ¨\A£ò †y'…B£ò’0“øž¼B¡Q yJ˜I|O^¡Ð¨†¼%Ì$þ¼“B¡Q yL˜Iüy'…B£ªgóêã¿æ§.w¡Ýÿ‡a ŽF|¦ˆÃ­@UI«œâŽB%èBµê/Þr³?$·KÜ÷T/g£ÑhËÞYÜ:X•ï%½ÒÓËõ•¥2Ûh4Ú²ožô7fµ¸@¿“DÞE¤1H4²/žà]úFéæ§ ÞFŽ?zÀµƒˆFVöÀ“\Z'ÕÝ“4Û'”²çÀc$&Ésš|ØÁö–R5Áh%«z_Øá%·tKºÄV=îüi£œÓtÿ·Ã½( Z™ªþïß2h~9]_wÇÇnõb© 5<uÕçŽíƬž¼¥Š¡g0Áh¤U;Á‹J7þ‚ù¤—ì_,ã›F¢=T=ðn|ôÒŽÛöªâ¡5¾¡êƒ!ú0è^‹Ý!9½Ü’—È—É+?¢ŽG+iÕ3O­Z}…›_.àijÔ ŒFZõÌø‚RU=ª|¢Ö†FVõÌ3k€þ˜gû4nǬ h$U¿<·JTäÀâLVH4ºª/Æ+« ð)ù¹H%¢êyñšP›âKJ¹€îÇmÈUA‘TŸ»´f d„µA)ˆv’óáh³›p\b“mø2Ül:ÁI6uÓ)\£yÉqû,ûM8Ñšns µ«[õVc˜,æó T¨Ú㑸y5Ïw¿nëÝûÍÿ}oqçÛ}6”%©žÔ6‡ˆràf`”ƒÏYrþñëï7LzL¬º ;­MÑf0ÀÅŸÃ,LÖ“åF^šY$ç×lOé(»˜ã5Ð,A?X 5pI<ªÛâªg^¯ÙõöÄÒž4w Ô«®öEæ¢Qæ>?ä7Ø—Õê¾wh;¸™WƒúEšé‰põ}ƒ%_Š4î¼·êK+j@¿¸*•"mÕ(-;‚{Íl¼Ó/ÏH¦èƒÛüL«PéeqzZÀ,!s335l¿^ÏgÝ›FÝÇœ6ûÚe£,1ý:dŠ>xħÁ®EºÏ Ø[ËÚëT ~…f:A"<òÓ$ñr+žrÚ5~½¯[ïx L¿DëŠFx°ÁŒÄ»þ»¬¥Ò¯¯J¥ˆ4Š»]³wŸSbúåÉ}ºo…ý\ç]~¹â €gÊRe‡´q½:ëŸP´ªþ‚Ö‡}‘’ÂÎuV˜^fr»¾Ù ëêpÒÇuŽÊ–ÏÝKš$Ž¥CÿÔÎ}Ñõáp ³+wxÈŸ²€* q«|³G>ÒNô‡{ÌFðJ'¾+Ðò)Aÿ;QÔ`@?»flÐ)“)Úà8Ô†ï(TÚ~Î_ÀºÙþ×œÝ ¾ÃÈ!Ðj« }C‘ ¯¿¡Tœ|©¤òJ´Ñliõ4Š$ èAÜMiH/iüíù×”çE»œ-ÊI¤¨ÂÀUÁòIe(‘“|‰P;è4k€]›öù±Í`5Ç0w2õa~¬Ò¥ž°Æ7PD›£¸,¸ÿô‚Ú Ÿ´Øo9žàÞùõª·X  ¡ÁË8«Ñg9·yY^(àõé§4Ö¹åQ;`¥6|'Ì“J‘{æAÖfÕÒ+ëÞÙÍÑ÷ß’Ëõ§Sþé´…}‰ï¿œÓïþó;IeŸãÔîìv%á¯jÕ¬&‡°\X6¬ƒ”í÷fù,Dha¸VÃU@’éöY˜¶ŒqÍÂ'J5×8«®•4\ÈVU:Eœ-Aq|ù«A\{´ÚAÏhXÎìýö3¿h:Yõ' ²‡ ´2Ø’¼\.±ó(Òx¯Ø|†½ê­sµšIYD¨=EkÕ|ú„›‘ë‰m¢–“ñrÔÓ[xs«·XŒÆsñèÞ*ßçÉ_ž‹ä˜~Ê‹-WHûºŠO0g~N‹*²·¨å]Jxør¹¦Ç7?gì&~³Õà—7Î_XºÖ?ýú·¿½ÿþ»ÿýþßþô§Áp »Pû03½\ ÆÐðzðêÞt.V³~ÂݳØËßo)B‡X3”VŠ|útÍóÃåM-Õôçÿx)òÛù¿þlK‚éZ”´‚PÇ#IÖeÊÝA++Ù¨a‰ÖG¥ƒ‰Tºµ”Êç@Kä]vʘ¦BÈŽâð‡Õ0m öÀQRþ Ü6>Á¹¢{û–ûk¬‰åh³[ô¬FÓ¬K®æà)O`Eo0ZM{ÂÕzŸÓ|,Yõ½QG<¬T…¾‰'•"kA‘Õn­Za]€6 ém—°DÏ”Žg“ÍïÕ|=ØÎpœû%½âPÀñÜl ªõCÂ'‘¢N E°ÝQÄÑ´i„òª‘ %ó&%Q[“ÖPyø¦=îýj¹£·«¾9÷›Nú˹8ËUÖäÅ)9|¹dÖÞ¡ZZÈê%ܯZ͵.&Bî_üm—ËÛkÔ™U³I8¥Y÷'#è÷·ƒá¬Žåp9o7Ø‹ü=ƒ{ë„´ŠtJÒ’è¿¶Xéƒôç3áA–ô<]Óâ\¤ðO.š%ȗܦl°¬GàhŒÖ[±S|9™öÄV›õÏ?st„ ¦Ô!ã–òW }ôþü¤¾E?jž¯¢ ¿QHÏ$éÓ(IKñ¯oß²;³&¦a ›¸´h1æÃÌñTG©ñ½Ý5߽ݮV5Ìtôy¾ ˜ã/·À­è®¼‡w?þ²yÏ*°‚ K4¿¡ˆÄ Eâ–jWä»ìºå‰Etµ© Ã"Ío"7°»EŠý¸•È3<Ì]ÜŽ»ôó5=áÂ%˜®Mè|EÐå‡uņ¾£†^!OV‚ùjl‰äÊ2’(JÔØµÂ­Ô5%ØÉˆšÀÒo 2 ­ö E¤áÖÖ'Ö|]ĘÉã!­¡:B}ÔHCÆF ‹âJÒœ";¹H(ïߥÅñ†kP_oÏÉfÒÑê¡EjðsP$©•ÈW Bí 2R@ŽœòwŠäØ×ïƒjH€ý/°6zýÂ\?q«‹וü¢YŽ}<{Riþ9?½<ˆåhޕᮣ9ü!E³Gû‡TšßƒTqŠWrÖQüŽ"X–} ÁÚÉ=I¦qIUB›†!8¢07»žÌ†SØÏº\/V£:¦Éñi×û š‚hï‘$Nö“g³órÆÕ)$ 4’‹É$öc§HS€Ðˆ.CD᪴+Üï¿LK áUˆ0±Ln‡+ÌkÄ®2ŒØþût;F~ŠkƒD¡QÝ„¨f§ç<~ÉJÕm˜*죅ß÷.úvYk|X²îÛH$Êë^ˆ2\-„‘슫`hda"Þ_kÏpËî ÷“Ä'l@ÑHšH3•2’¾«¤‡AÒEz†‰¸‚¡¨ ,ZYÃ윿‚|Lx2vmV04²ãÙèaÀf8Þô$ÁÌ¢¾\+ýLÜ¢Ô”rÜô&¢ý4ãì”Wî—¢Ù¾1K³/DZñ¦X+OÞ‡MÎY·<+R‰öå8æ§ÿÕi,@!Q…w6°Åû©NXJPhTåèå§:e¡ (4ªrÌòS±PU9Rù©ÎY¨ ‰êPö§ã)L…Z=À{:4Aû4šªõÏ­²x:Ƨ)0H4aƒªhùÐÚ¥™ž>ÆA¡(¦ áõ;—&Ã{Ÿ@QhTePè§y&C–)¾*J£ªSo©£7&,U@¡QUÍÉK5þ¸T…Du¬S/Õøã>R¥ŽûЕÊÖïkVñÇ}¤J÷Çj0õ–jüq©RÇý±L½TãûH•:îÃ믢àš©5˜Â®]†~U¡š\t¦¿_EªÔ~®cFªð6N½Tó Ö¢˜ñ3 ™D!•êTö~ªñë*R¥ÖÕ©ìüTãû¨H•ê£Neà¥ÚïqTD¡UÙø©F^’uµOõ¬¦²ðSeèòKŸÚÀb¢Á®«_…#C8äEî ©Ìd0™à‡rmLsŠl³•ª,=A[-ÛÁBÄoù>9ÀUƒ{ʰÙV÷jœi3ªÙvžÏ-Í®îSÉ–6ù›:[:ƒ¶]”f{x£•ø€Àýæ´r÷Z°ö…%&`´M«”níTQô›ÆJ·­± H€w)W-ßo±×U¢ÅÞ_ü°ÓÛã,@Ó¹t[ò2Ë0g°‡Å8TÞ£~ç¨*0‚Zì,U; (šº·GIÔß,Ádû ZvÄ9¬¯kZWÓj+óSŠÅFt•ñì¦H·[¯úÐÒlcÞÀHõ eáÂèÅdF©Ý’ö×–à@óóÆLA¹íYR'˜ÔüÖ´j(Ží²ÅQœ÷Zþa VjƒAÀn¡€ÊŒ`-E³ÁFÕ4Ë„"+ái¤*F´‚–©8Ð Ч ¸îí¢ŸÓmSAɼ1T¤·ÌÖeo$Yµ)Ð(¼qÌ£Ã2W†Ø’ËØËD›×12v™[‰”’ö/:—˺Ì2Ì™\ÞÞhEˆ‹”ãLáø‚j,¤6Ñx´{›TT=£‹_©Ç^ÿk»ý…pj¬Íc6æU†¥Ä¿)µš@ª×©yì°ÀôQ^R^½ÏÔz˜à^!Ÿ¬ð·4±ÞqZН-t/NeëS¦ÑÈ{‡3IþmË@Ÿ»g¯óõÒ¯iü½C…äÿ.¹âÕ‡Ý (3ö*0Ri¼½¯%Á¨¡ÑÔXMÂj’4Âþ1ÙÃbfµ¨fkŒÙ(›ìLŒFö‡4:`´4®ÒóßVîÒnUž¥†Ÿß­Þ˜?ÓëPÉËX¼!£•x:ý€W‹ó M˜5¼Âö1Ä@¦^âwií£[¤Á°]ÒÙYDÕ/4ŠÚ¹­SfÒõ¯ÓòzõÌëôÝt’8©âé“4žzë¡ã²Tˬ½BŒTš =MìµÉÏÛU×õGhùzè${=eêeÿ.?|9åÇŒpOò¢6±™»W‰ýMwЈïáñ¤5JæëÕ “hì½²‡¹+9ˆ-ß]k¨çî(q? éñŽ–žnGf'ë°&F~SïÈð òá{yºãíÒ,¾Ü-1þhfñ#U†PŠq¤ˆŒ*TI>à#ö¶Y½–%`Wäð„a4eþa9Æ'4UÞ‘¤ë>KwHgxköëA±¿Ñ?ÑXêi«ìý/ðv8µ(K_>§üŠ&MO›Ô¤Éš;£²tè—¿Óë©‹°|K·Cº*ÃÙòWU=ÑaQ/ævÈTæW#ª¤ñôöõÅþ\œîWâÌœ]Þ%hm¤ò¯2À–eO·X"t[Î’ZtÉXÕ‡¦*gÞ±³9$çdÿ!N‰Wy{ÊÜL´êL ÔõüQ½fk—»¢ç+ù*Éâ*{|wËF¡ìŸû(å®òu˼L°xûËŽ·„Yw[ÖHËSÎêg‹k°Œ½”qUËZv}·EVµ=žVÖnIW°µ(lïh_at[ÞUýUÞIÙ©T)´R÷†@û˜ì_“"J宲vKÝL³JÝëˆTô»-uEÎSÑ«‹t°®{Ã=óù‰[ÙÖJ¼–F#ïøœÄ¼Kç¾U ,ȤQkÂA»xÇØ"}ÉÞÒ¡YÌ\k"ì$’Qàì’§¯ÈàVÒÔ|´CžÌk:¼_Ðäx#<™ßo0ÑŸ]šÂÎ×+Bƒ+ÒÂ;˜=ü¶î”6fWg+£²·!WËÞ]r5s5(˶íDwoK]o;®ôéM{1”é¼4UŸÐÔx½n×]07—±ø‘ÆÑ;³¿‚g¹;ºDv–Bìà—^òÕl•Eª3uKÛÍÞ'Ã÷­ô½CÂju;ÅÞÿ£[#T¹zD˜‰4îÞ!aQá%{Vç°ß'‡N¶¼Ù»j|$ˆ5 NBû†‡üôœ½Ü y`®Ë:fgìJ©§“l³òf^»ˆƒ÷ª¨Y¤KŒj9ÿàaqÁU1¼~±€%¸9&–!E‡`â´H®Ó¢*Ö \@RížÂÒ¿]2¸¦°cy*S¯–2V?õ¨c_g¸ø® ÃË;änçëЯ'Óè)¨`çÛ[Öãb²öB5ê üMº´êÒ¯ ܄ֱáTž>1eµ®lÖÝŽ±kÌÎå*%Ñ\ëžÛ¢)öîŠNEoƒí®"¹y;|ŸÐÔè.9 Æì"c(2óoPeFSæíz«‚zxX½ë²)ÔsnP#¡‰CÈÚÛWhƒûÛó¯i·[­ ª,"TqÞNz󮛎\§€•­+Ä¥Ò÷v´p¹ì^_&§]Ö/3W‡¼HkÞî¶ó]‡b£Ã÷®†Ð5I‡ßê£~ÎO/b#UúùšžÐê´¶øów•xiëÏÆ;–ÈÄÚñÞ]×ëÉÜÑäý†T©6ÞáDåÇNžÌC‚LT yG‘·ë‡.›¶ÈÎ% TšÞAâmzƒtL:ÞPìËÝá¡@ÕäÞv­ÂßAI*Sï0ð^ë"iøöfïJRç”-ÔÊæHtÙtØê•©]òeÍ þñCd‚ Ê¢‚vZ£êYàÔ¢÷*Oªê™Ò³äÂF…ôt¯™ áΓ2Nö–Oªe‰€}"³AH‡±M²ZG+8iýÀY|PU޳–€_o§SZЬ~Æ÷A²+¤éû/ç7W$+s˵K@ üõ1Óý˾"g—»õ»E9XæúܦEZ¶"õúhKG{w™[™[e^K±Ê\;‘ú"‚ mÊ%¶_©ÂÆðˆ©@Ѥuz4•ƒE\YŒG™ç‚¸ò†yKÜ;|KkÛõ®Ž9×2·¤8i úhPB‡-Ý$h·õZŠE<ÔÚGÚë·¨/N_ÞgQ^Í©2¶JÝ$ Ñ#}…¼—v‡¥­‰Ù%müJ+e=ƒeÓ…ƒcÙ¬ŠTÖõìíwS-)þÞu¤Oà6é²ô-’5ÔÓ,úÁú®ãBKÀ*߿ҰíÞ³«enYÁI³Dlàõ®Íœ:´€•m:XÆ",}¯gm`ˆ¸ÚTÕ¬@淪
¼xƒÞ8–«Ó·Rª]½NìV†é¨Ç¾7tÄ©Á,ÎûCmh–mÛ?¦X×ë–5fÝ¡}›qèj©m·¼@Ûê9×êxLœ!¬ž»­ª]««þ9öºjN—62)ڭΆ¬qõŸc¯·³¿´ó¶Ê¿žDh1c¯ÛfdÔaÙ›¹†x“ë¾×«p­C_ÕÙ>¹u÷ÌÞº\ƒ ¨r¾¢Æë×ùF±‘IÚn(Ôãõ÷¢ÙÊÈØ²Žõ;Å^OçÒ¡Ê,½tÉíÃëש¼ã µÌ}ô5p­ª¯«f¢t_ê‚ ]Û-Àñà¨à%ÝÞþ™]’™\î¼Wr²·-P¯I ØÀ;_j#ui‹dÍõ4«Ñ-á;-Ÿ0ï”»z›½N»ú™ÆØë¹ÿ5)Žù çÍ¿t‚Õ2·ê“f‰Ô¯næÔa¹[Ù©Sû͉ÞG`ùÔ?“—´ûr/³µh¿ʺ|ºÁC¸ÃR–¤ìª]þfÑ µÄ‰×Sþñ$ŽõĨÕVÖv › ¤~pâu“+„.Kº$W+mówZ‰{}ä’´Œ[ÖŽîôìý%¯Ái¥ïõ…m¤ðx5Ðý`Ý÷ú¼?'é¡û^¥ÌÖ*yãW«òø{ð‰×Û•ytXÒ*CQríõsËc}JWĬmâv ¥”½nE¾Ë’.ÉÙ½ŠF­Ë^ßöçkŒÛu®v9+¨ß@Eö:°"ß.K)Õ VýdUƒ`ÿ wYƒøÛ䔣½_ÏÝ*c7ÑÒ(k¯¯meÕa™Ûù†Ù“{¯ß-žvßTùÖ˜‹7ÝD×B)q¯£­òî´¬-»†k˜Z; Õñò=ŸZÇœÅRD¤°XÒ´‹ØÉ–Ž m¼¾¹©$ÏNW Ý µk…*Å¢0€œK’ïºì9O±ëß-ÊÁ÷Ç(èb>›3[Vœþ+å·ˆÉÏžùš ØsÈ,èûŽfÑpô£‹ù!b¿æ`„mXÒ /$Ù˜±¬&é6˜«üà’ߊ=<Ô’â¡Ç`ËóÇRq[-wÛ6N¢¥#Ðéù#$3«.íaåfF²¸mà{ 1×% Û}×Ä *³éÔT,ä†üØ‘leЮµŸš²ý`¬ÅSÊõ!·ššìxò¡Ê¸f¡r¾µFÜoõte€v§6(g,Õ¥+x"\ÝóG½ûp1÷Æ7xG5v¼ÝûÇfÎV9Û V ´7p)³é°¤«<ýŒ©=ÒÜ‘¨[âº/j#c‹·õ;¥ ½Á‡Î¥Ãr.³ôÒ%—²7ΈÔÍ—ÙÚ”µFë1¼±…̹ËÒ¤ì.ZÔh{doÐë¹é{X»ïõÌœ-;Ø ÷@ñ:le6–|•§Ÿ1¹xý´˜7ÚÙyÛ싞'ÕéÑÆ¯·f`tYæ=»¢›p5Ö¡:¾ò®®ÿ–î¯y„Uß*_«¼ÍŸ µ{åõ¾T&–³ÎÑÇ•Z¯W^?ê·| ëE²§\•í½´áÿ}‘¥qx¼}[“#¹qî³ô+6ôtŽÃöò~ s"Š7i­Ýö̬d?1ØìênjØ$ÅË\Öáÿ~¾L XHd¢ªZbÛ¶Ö«&>ä@"+‘Hì/Çu¾Þ?äÿº>è?¿ÿn·zÉ¿û¿ßýy¿^m?Wë³ûóau~ÆŸ÷»ïãŸN{êåã1'ÜïþÏÓq9ü¿ßýþ»ÿþýoó›NwÞŸfÓnkœu:ãþ§7ïµgýï¾ÿ§Æówÿô=Ðÿµ9­ðÿî&ÿ±Øló÷ùc~Ìwëü÷ßmW§óŸvû/;úûÇo"åè:îÿõÙâ´ùÆ‚ë?ÿò~:_¾ÿùç’ï^5ßËó~ùá¯ÏÇË éé”"91„\º™216ýWÈø&ã$ØNYÜHH–¿-Ûfg»ÕöÛisz‹a‹ºFKý*DI Ò°^›ŽMÈd<$Ño‚ýäHŒ,þ²?>ü¸9±¹íÚ {ú—?ÞªWr~C­_Y“ ÿ,øMêzbqœ½¶›óå!ÿ¸Éó‡Íyl0÷ó¯@­7ç„Ý…ÅÚßÿ5Ü8dÄ$ÛñÃ1m*Ü GÆbXR¢…(9^3K¤Ùå¸:oö»·.›Š­T![b°æ %»áXìÊ¡²i’#µ°äY\vk©·[Tš‚!ëg!=:³Vin82›rTôB‚ÔˆÌLïå‡Ý9ß6çoo»xdÄØ$ÛñT¸/íÐm¶z¼á(™Ý׊„Á%Ç«pd„HïV»Íá²e{÷v«È¦"DK5²%«ðpê$»áXìÊUe7Ò$Gªð{„r£P\+D¹õ8\™4F"ü­ÙXß#RŽ«—7\9&v !Xb\Ì/úźåØ(f£ñ±~¢$׋ù RÄñßz€.Á0FGþ,äI ùÝIsóq¹²i Jø£ 9"æ·ÆÇüëùÇÍn"š‚ëg!ObDÌŽ¨³ŽHÜs• .!ArDL/ëeµ»¬¶Ëüë ÁäüíðÿzCAÌî…4‰DZ˜"Ž«U“ó‡W¯_8};}üU0mΤ ŽKݹ©ØM\7Ô»ïÐ`´át™´Lû]â ÁÑ&mŸŽCZùk›Ž e»Ú¿Å¡‰ìÝ¢ ­ÞĬ1ýAGã%ß]¦û¬£‡7‘˜Š!‘nÒdlL÷ÐI†s(Ä¿ƒ|o(XDÄKµh"–é4:±›õùräšÒ¿sõ qįMD1E'Êi}ÜÞÎÖ.Ëþ A›ÈaúˆBŽ[à‚ÿÒ£ºnÁO‚÷Äî=i™>¡çþŒ0ûé¼Y¿á29 ÖhD „T «fúˆ«ûõ¦‰I®K ŠRo®Ý Þƒ¿6aØt]7œ;¾CƒÑÆ›·ižî·[TlÝ v¼WªWö-Xj¢h3°ttCm‡½¦øn¬w3’¼Þ“oýõöJ:œ‹¿7Q·;.z¹¡®¯]šì6Ö²éöÏVçÕíU\ô*.ÿØ@¹pô Ÿ»¸¡f]šË¦:m›æb|Á!nµ¾ÚU º\‹¿7Q¯é@½ÜPÃ×.MvëÙt é„þx8æøç[è:ê^ ~k¢sÓ% {º¡ÞE·IÖëßô·›Óá-œŽ²_Áxøç&ê6}?ßÉ 5]ôhñÚX¿¦çñ²Z?ovM>y^év ®Åß›¨Øt8Š^n¨ãk—&»µlúïV»»ÕÓh9èX°-þÞD˦ŸQôrC-_»4Ùm¬eÓÏð}¿É·VØ·Å:m1ê˜^ǵÿÛëúD6üÝ úÊ-IEü¦¾p;fÀñîí‚%Aׂsñ÷³ºc†‹^n¨ék—&»MguÇôôîŽòAÞÂûº–Œ—$£)b‡ :¦§Wô~K={Æä„¾Š˜MÎgÓÓ»;W šWî†Qç‘¶áHˆ„ÆM?/¤rS­— Æš¿ˆ%™Ô¾éç}h¯|¥âË~…ÎÃ? ®ê6ý<ßÉ 5]ôhñÚØŠ˜¡°SŽCˆýúSŽ˜pMl»NÃÿº¾Þÿ {<Ë„†“óÂôOƒŽn¨ç°×ßõ]8¨ØØËû–6Yj`´ë´KË~ßៅ¶ó¹ðR-žo¨gÏ–4å§ÉyQ¸¦‚W\8¸¥v·øšï6»'\vm•óÛSº.H73Ô…§ª¹¿¡ž™%©åâOtÜ-|RÁåG|>Ý~ _»Z þ*X¶'p·pI †o¨WÇ”Tìõo‚ÍÔìí>`ô—Í-S9¨7¡K÷‡fü®[ÄÝAl0ô¯.þ²)zŽ8.ÿ,øN áþ®'—óù-o†Åý ôMä(|¡´7œÍ‚E9câŸïɹ]xE‚{Šw¿]^Ÿì]Œ@ü“!1ŠsΔ7Ô~ÀžÔ½üApÔ|áã ¾ßNëeÏBãáŸß mžÅõ 5íÙ’Z.ÿ(8MjØôêþˆjdž‘¼W›FѹÐsô‹ ¡jÓÁ+û¹¡¶ƒNLc ËI›žÞ»Ç}9Ñj¾]^­tÙ» þIÈP»éí!à†LηØMËžçáŸpÝ3½?ßÉ gJÑ£ÅkÓ9Ò3?÷Ýüv³$î_H l¢ó"4)l¡èꆚ—ý¦¹o< ¦WK¹Ño7²w!CüSý›~oÐÑ µöšâ»±æMñÇÕᙲÌnÈuÙ§à9ü³Ðsʪ÷‹h«˜é¸lH-oaƒ®%ç%ÉhC²yßüÈ@ïÙìö_Þˆõ²ó˜ùð¡ùû¦wþ²?oç”:òF5i!†ñkQ¦ÑÉ·otÛ®ìY2%Øhþ Lïû¾áB-z´xmjV¦Aw=/W—‡F)¯v¾âþ JâÍtnšõÎ#opÀc’HÊse¢™P¦õòûËéâÞ-Q®¤›IašSOçªÿþ•Ñò¸wKŠ+éfR˜û¯§ƒÓõ|÷¹ÁÆð÷‰QvoÉþÚĦš¸O'Ü8;—ôªYöù̃¸çfÚ6?c¯]ÎÇ|…boÀeÑu36ÍWbó°ß~[.=í·ŸN½-Ÿ²ïFŒŽ‹xþåY1ŠÙ³\®÷9ª‹ÞšOÑu36‹ð–ÍæãËì¶Êd&]ÇÍX,bY6‹›Ýãn…dþ7`²èº›Å*·Ù<ì¿,‘]ò&|^ûnÂèÜ;ÛY÷0Ë™™qwÆ×ªZâ¶ÙËM¿p¬Þ¯öju<Ÿ¾íÎÏßÛ­ê-ì¼ïð*‘òÇ[~² V¹ïq|›&¸%©…ù‚šËÛËQvkŠþÜ„{· ²Ê𕳠÷öWŸòã­¹Ýj›pï¶—¬ƒ6%÷‹ÅOùùÖ¼^9ç¿}/~iÀôÀ#¦¼›Þšåk—W†ñ—6aÖ}ªe°’†§ûÝãæÉ—½5ÛFçW¾œ÷ûíé{³MqÜWP$Îìã_n-ĵKÅzðK†½uébÖ”3¡–[ZGîîÊ(6üïý_š0è ˆdík)Å[«V÷}e Ã[?7‘Û)G¶ãâ·At+¸~iÀøÐ›“.þ¥œ!tógµ»½ »Œ ‚›aaZ,Æ©ŠÚ­µîY,»¶m¢}÷ížIísñÂ[³t*o²÷¾$˨ŒÊí=IÑ­`;ú¥ ã…-¦¨1tkuË~%ë\ôéòâH6›ì…™Œyß"Áîiúœ#õæ"èîcI¬ cT˜üKivè䂊%Ýz0d¿B„ø§&¼–Gð^T¸¿5ï²_Á{üSÞ Fð¾ß/§?ßýç-‚k—WŽÉ1þÚ„ÙÂ:ÆÌÎÿý—ìÇsëûŒÙ½þ¹ ¿Å*ùýËû>Η“~ÊÞßZɲë˜ûø×&BžL,Äûy6{DϱÑ $ë3 m ;J0ºýu,øW¿5a¿X¢"bã’»om\Â^ãò‡&\ku*}¿¿í*òq©ûFûç¸pZDœbš޾¼¬o­Ö¨ã«féZýÖD¹…ë"Ù¿ù'ÿÔ÷xeøúÁ|ý¡ ·…a•ùW¤ømP1ë|û%¨û¾J@ßtÖÏMä(,aBŽw‹›@Ééµó„$Áï D%¤ŠYWˆ²¸üo•}ÚŸÿh\ËÑ?¾ft.D1o"Ja…(wTqyÎOçÓí§—Ñ¹Åü½‰(…Í¢|¼Üç·6HeŸWÆÉ…nÀï¤ØX¡÷{ÜéÝ-M}Ðé•cr Åß›°ìg R1ƒï ¸¡³ù‡ï¾µ7víU0’k´]MüÄP\;oþq~KmƒAÑsÌ}ôc½û WIÀîÜ[vó/k¾ßpûàéûî>þðóO7Ñs,@ôc ü&܃å¶Ë"½éJ½v)xþÚ„Y¿ÓJfg›./¿lpà{óH¤îûÊ~áóXMÈ2õF²'BîwÓìÖ6ýÚ¥â<ø¥ Ã…‰” #Áb·Ù Rò!5ûªA) “)¤øÀ5ž:·–Aö«$ˆnÂa0%ÿw?ü4ÿxsîƒ^5ïâÇ&œ¶Rrþazws¾¯}j®ƒŸðì_Ëz2žÊwËÿŒ‚‘ûÛSUß äÙ¸/îx#WaV˜®AÍ¥Ãþx^¢îå-bƒ^¯Üï!¹f\6Çæúñ¦ÙWî¨[›o÷K“‰S˜<]n«Å»·žð²ß+ëôMÿÔ„÷ÂÄÞx¡¨Øm|ЩàZü½ Ë…m‰Byçãæë­y~·*{LËšp]ø^‚ë;z'êî¸_ç§Ó­y×} ¬Ÿ›ÈQ¸e‘ÛoOûÝíEº¸¿4`ßÓîè Æ‹—¡n͹ìW°ÿÔ„÷  Þ½GqkÖE·‚óè—&Œ¦Q0þñ¸¢GLQùÖ¼Ç= öõM$( ¤ˆ¼sÅñ»[î£EWŽi-ÿØ„ÓÂ. N‹+d7e6èTð+þބ嘈`2…nË-÷'õjÀ#âZÎnÅݪå1wÝ4c6IBHRѪ‰p…aÂùœÿÝmjäê´‘;¸ð ¯/¢tTLŠWÅ-×^ЩЭø{mú(Yþå¶³™»lú¿4aÐ;!’Áìñ™Ø:>"ëÖ6Ùìþ*@YI´j"”7"}ñ–ÐôöÁ•k—Šùà—z†aPœE‘ øóìÖš¿v0ÌŸ•©& qÑò6B²ûÓ/ïϸł'\nø9)ºØŽ~k¢iÿI)Y'óÆ)ßø&¬îÚm3Ízï¨/nk{/«óó­ys}6b¬]èMÝdyÙ?Üf¼¥¹>›1V¬uÁfá Šª>ßb.†¼Ý6bãȾB_±W\й1{×n›±WìOнë‹78ë ´wí¶{Åî¤Ø£Ûw·Y×g#ƺîNp†ê A€gº:Þ#–öˆ·Os\‘ùôw¨î JI ¢ìãzRw~5…ßøv:ç/ßÿ¸¹?®Žß¾_äqƒ!bHɶºÇÝÈË9ÿ¿ûýwÿýûßþæ7î¼?] k×ÍZ!E%Žк}`"êù*[á Ĥ• OÇýåKá®[Fƒt—ãéz“éößšªë@ÚeßlY]w×1ã‡ÝC~óàVÐiĺø¥ Ó®S†‹…ÁÁ 2Ào{ë®ìóÊ2é:üs~}a£ˆ_ÚFÎ(:v›¯¸À úNMãž+a°v8æë͉ž­ºõ&Rv܌ŊÑ&ía(nÍwÙŒ­ÂŒ)¶®¯Mü&Úͦ5¹=ëà¤À9iî9Fß³‹^aŸÄñõC——o<¤Üe­Í:m¿t§"ðß/›õ§ÈÌ+·¦¿CwéíÍèÿºž+v8­wk“›e“QÖZt[³>Н´ºC Æü»ïÿé»?¡4Oðsýì¥ó¦ƒ«^Üûýwuå%hÒøô7Mí*t±õYM"Õæ7 §X’‹Î|І: Z‹1Iç+e úÐcƒ:‘h]Tf®“-ª—Ñ» GZýÖD*¬h’ªƒ%£¤z<Èu3© z–TåoM¤‚! ©º8rSR÷Ÿò&ïÞL¬+AK®àÇÁ­Þ[× Ïjti¸£~kЦIˆh.ßErUoÌÃüëa»YoÎ ,µØŽQ$ÜwFsOÑ®‡ß)‹Ñ/4MSHgýÜ@¾lùzÙ4–ïý 5›þ‡å‹hÆò©ŸëäkçÃäÎç= L»ã^{æÇo†ŒŸ}“ºG·º’\,UøKæ34jOén¶èýþ Þ»¼¼4Yi·‘IPŒÅŠ~¬“¬ßšf0ñÃöhÜE0q8ôú*~1µaª³^;uÆ>ØÈ!!MôK½(s¿Ãþ¼Gy~¥(þb-_üÃÀç…ôÔz›ôI•¢y°Ø¤Ó ëä-˜ŒãÅt±hÁMmO:ÝɆ®[ÿ!I,z¦`vú‰FCÔ­—³Ávüz)#¯P @Èéš5‘²×@Ê·5bæ$¦g¤„úOF^d}K6Ìô·ŸžW"æX¿6¢AJŒÃñÒè9ÌxÃWbI‘‚MÄV‹õ¦“®(i½À §Ú(!Ìÿ„…€0I³pý­Áˆ ¬Ç›¹å¦ôÂá—¾£š0Æ?<Ó$5sªÅMšHæ÷,)ÙÏÛU}¢Ìë% =GÁ”¢ø© ÷~'’Üß!ô’wË3 ¬ÎùÓþ¸ÁYÃzKgM^`|½`ÑÆTË€)wT•ømë5*ySƒR-–mdj1Má÷8©vQé0ü»%¦ZÃå{ƒµ$is6T´®~ÚÉæíÞlÒYŒQh;øš#/zÀÇ»wùËþXêùúU,oIé*àÃú$ˆl ϤååA:YB¸om‚ã¡»iÈÅ?7‘,#ɺ\­$ËOTÕð0-ðBo“Rׯ¯Âj‚X˜E³ÁwÏ´3™:æÈ“*'è.ÖÛ›“–$&ÝL ^=Ýâú zëY#JçkÚ™ò² È’6GæðLÁ·\:ZŽ+ÍFc1íðä¶„% &×çÕqƒ;›ÿÓR„d› Òs‚ÐIŠ9Ÿ÷ÜÖøŒ’h¥Ø<ð°æww“ÿ õ¾x/Ñ¥5e@`Aÿö·h3ÉŸ6;nuM™\6Û‡»çÕ)û ‘qÛ%%Œâ–P™zâ-2J~ƒâ0RÄÑ7åœüæžHeÌлÕéZcî {£î 7äd"Oøóÿ¢Öœ£‚cJŸø%)㌗ï VI\ý³ï¢ÕêtF“Ö¤Ûí ©c6\ÌÛ|F–Ñ{ Qô~ÿ58ì¬êh‘ÍÄ}Î/õzX-WÛí~Í™@\‚;˜íî¨Cû‡ÀŒx­Ÿó#¾a`$bLVQthÚBGJžõá²Ý¯4‘i @QX$›ó3}ŠER`ÞÛùöqÿø,·Û#—{Â)–صÛë$0G|h–º‰æÏ˜Ê«ƒ+môÞèöZS\6³¹".©9’ºÓv«¾3‡·a#B¹Û‹ÁpŒóÐE·“M#Ÿ P>ÏÈ»ÇL,h,ï1#?ñ»¿ŠÚwPr7k !U2sSRÌÜ ¶Ú䓊Ðã»äÅÐ΀¡ý6qz9o¶¸¸Eû_À1“í;²ðük±Ýö„–Ô:’fÀ)Ê ¢ØÆÐŠ2X4Eb4æq0§å×›ã„:…ˆ9ÃW©=u½yŒI´{¤kµ€ôÈ4„€ &Éóâþòø-@ÆdŒ™´x%Ú˜™EÜj·+ßãÙî¥L¢o¯úO™Ãóq培Ö_·0mv\sÕ{Ê–ùz¢÷” äiw>r¢Î&Pg0í‹]¨\&nÇô9×]Š7£ÂÆQ%-­ï寉L·©’‹ÓÛ‹E»×ͧ3˜ Ä/§#6óù02Øãþ‹\™«wU¹ öƒnÖm÷íQeƒZýnk8å:zD§Þ-´:!1°€Á pÀ!ô|„y5h 0­~o6ó14ÚúçÓ„¦©=>t¨} V×jï¾pBžhæB)ó>„R®G ¢5œw´^´ð‰+Z—cè”ÝAr ÉÚBZXÔRòÐ/@«¡›Mû˜Îb2ÈŽÏß—µ, ¸5¾JÍ֑ƹ-†Ünj®Û_@eíÞdØŸÑØ çýù´àÁÐ4µŸ#^Áí!Õ>’rÚí€N¦Ó ñ K¢7ðR–å«Ñ' I„Ð8·žTµø« s‰×Wý Z̧¸v1mw{}JÐéÎ;ÃOÇ—C÷Õ+hО!\ÒnCÈ!žiM¦“þ”3_VË{8ùáQëɵ¦Œ Ý:Ü-¹ïNªïà^R1«ÐKrÊ‹:*†¦Ý:„bjBQÖ¾°Ü=„â¶Á¬÷³¤ 1¨5Ê =ãÕ³{Üð)•`~Äí὆í)HžG[ó÷½ƒk£õvs²æm“1‚<ºø°Þ®.'Ü?ÑL¹å1h ¦Nùy›ïžÎÏøfÖ·:¨rŸ0 «{¥ÒŽSé'aãýnƒ»07H"wüPu‰,‡êÄm5¯ DÞÂÖtœ¶Ün NÜp èÓ=èýÚÞ à W=$"_»«Õáèv¼îñ¥6¦dùrÜo‹«äµß—DG‚†ò»^G|IR"?m~•.+ÕT åîú1ƒñ çãr»Ú=]pEÚš]?#:¼.M|‹ïNXkš¯®Ž¡½lo°å‡c$¦Ÿk¨©Ôõ£1Ü”g ÑÌëúqÀƒ›ó_Vx4ž¤]¯Oúê+夦O×k<Äâ#Äm`æöüT»CÂ/šœ³6¦åW~&RøÆäDLá§ã”€¹‰"NLÇy[ Зã†Sv‚qasé,b×±‡6:Ël~\ëæÎ¡³š»Ï%¸ó·,ÀâÇlJçb¾°ΫKcN'„ú5̹_IØ´îWëOè<¼$ù-Ki˜û,IÂé-æ¾’°—ü¼bK.#V‹ûFIñL%*ôneXŸîk( t_ˆí˜ß´Ó¡ûp©ƒçtAOûôÓarñ-q”"ˆ]Ä«RkÅ«4ždøb{Г´T󗇾šó£ôŠzqéBŠŸô¢*FwI‹w£ó*–?½Æ®h\ÆÂé²f5½ÚÇÍgl*æ‚¥Üv9ïÉ~Ä“r”^t´°‰ š^vÔÛFN/¾ìm¤§—`6eM/À+ 6SQK/¿f†z¦£ô»y)Šé%wÚÆiœ^{’VTL#™ZQŒV–‚¥âV&ä^ ­‘qzM–ȄŻ:f½Eô&mIgút`¨øO¯Ô‚‹/›ÝÃþ‹FV-Ôýk;0—*Ž,ÒÌÀƒ>®Z³Q)«>N/ÞÓóêÈvfoL”ô²˜Žmê8½fåh)£8N/[‰¼Ž³¢^Á~|¯áÂ’‡i:°×jÝ×ñ¸ÃŠÖ,›á_ð=²˜ÀXó¾š_í½ro8û¤Þ(ý£ì e¾Ä$å–ÃTKù¥Ámlj¶«ãq…ç©&ùªHD/V< Ï€3ºéd€ï Á6Þ]Ä1ï“Ea’ €/¬‡ý‹…˜&'rÄ0c$š—¢É0Ë‹})–r¡±25¯O'CÈÔ¼FcKÈÔ̦憩¹}:ëõˆ@‡­‘óI°FRóš_5"èÄÇ<¼þP{6H¹ŠnpþêBd–RñNº/÷uémx™b‚sõIVqt× A½hJ&ë玲)  2¯¯hØ­¹£ÄíÄÐÚkv¨•Á/`•¹,Töª»ƒÔGÇÕ„-¦Z>hû²BQ„òü|8¢JÁs$Ýs]ܼŸÎ¸ú€/Û¶E§È妱-¶+;]Ï|¿#j Kg4^,~Êϲe†kÙ®%f]ÙíÒ$‚†u×+‹"áÑòÃï¦AÔ÷aÑΗˆÚâØÜl‹2K²e柚Ñuà’:÷ýnþ• 'œføvq½ª¶².OP;œVÇ}â å}Eý‹rí‘~[òஎÆm‘nð€;÷ñ8Á**L¼¢%OíLf'8žsý Aõ«ŠÇ(¥tì^)ÀeµÅJ´uåìƒæ°½•ÙÁÀMîiÃHÆO«cÐ_#‹tºðë+z8Ƭ†Âk¼XaH….ù UÁˆ3Fµæ¿Q‡¯6ÿc )©Du‘Béh'I&ýµìB‚æ³ÒÚ½’é.®ÛÝÎá ¤QgÔwW–Èx.Tàœš4çºÖœ¾’s²Ð…EÚ_ϼ¡SOp•†FuÜ0 œ»7^s« ÚX~ kQþ.r/¼T ‚¼˜‚9güÒ˜å,ßâ²ÆÕ5*pî¹–ZœA±0‰B\TñòÏ(E³ýˆÒQ\‚ÔY[jˆWÌáBÓ€d±ƒƒÍú‚ë¸j‰lÈWHë€Eaì6î:Û®uu¥§Õ[lÛ±%ÄË¿_§äÂókª ÍÊŒ© MB3Uø=1SÜZñ3F ,Ý{r#×eP3(/KAmùa7·”dþU)=B¬9¿Þ<Ö l.ð˜2fu‚¸iW’pƒ~ÊR0÷ ‹¾´È)c‚ Z){A°9ûKšTÊVƒ’i'lkGÛ˜3®­êŸ[gᚣl­`8ŒþSv¸g.Þ¢µâgŒÐmºw²† ¡ÍåXˆq…ôÄ·ÓÊïXÍ÷Ôꯎ×m¨!ªšPY Q½\ïét2õõ(\=jþ˜‰vSeÿ¡¹Ý”1H’Dý‰@j·c¡(ˆuñ%ä Ö˜#.cŒŠc+Ü ™)ÔÕ IÚðˆK¦,ÈêöÍ¥ç8¡Â¸ýA{PYõY¬(¦7÷ô`‰#zK»¥1®e¦ä[Î7tß/–×3YJ$PEwŽ’'D7CH ØOh’™? 6ÍiŒtUç¹p¦éÛÊÆC„áŽá•<áÚö”V(ƒ.fM;"•¨x 1¨ëAÔ½@8óænFõAÂë Ú ðJ§¡¼¸u×ÑÛ{EÔg6A± Ì”ÏábŽÃ9îüðs‘6VM”1jÌš”_àåÈøÎ>ç¸øÞL¦8[Ç19êú-|™k×Zö>ëà±uLzxm*ˆLÃVî¢Í~üQŒ·Ä¦F-¹ò‹hõ:‚ -ÅñígÙlذÄüe f÷ŒÚS1X»½äƒ´9sÚÃ(ØXhÓúê ºS )†‹KU¡ö ¿5‚•Y¶^(bêÎ]YøXdt¨</ÛGÅ7—ع½–xá%†­*%vm¥îy¦ßY¢gÜ•åíhbâ3•'&.;æ¦F¿ÅwUÜïúb ¦™ s×@ß®¹Ññ5¥úß®q ¦`îDÁ4 ÔÉ1Ö éÅQÿ0ŸéƪïŽÞ©y†ØH`Щïdz+”º¢xè©3/5EÀŠž^ôÚÃõ\„‘>q{”ÑbÅ?[äWŽÛ¸ÊÆ€glÈ8’Á´Z$TŠ0°-rZ£¦uzJ—‚C™Y©¦[V¶d ¡Éã„ÐT¸_M÷{‘0 ½À‰’‚ðüørÁi+ÅS¬/ˆ±éSÝ•(! ¯˜Z2ëd/WOˆP¼Çæª0ìQi3@îiß}UtÚÂõ¶±esµó'tqd.Ä› b->©¦­A·KÞ0ŒîdÂ5b€¦ÓGcú|Ø a5Om,™û~éÐ'yéxkœ¢ˆw‹ÝX£hw0ÖùgìÌû£9Ø™éM…0¡æÑ}øt¨®ZÌ££dLElQ†Møðç™Í•¹úÐZ0ÃS1 šzäY—SZ*οèÔÜ}ªËÙxý pé^)Ù¹P>Rã“ABò7v{ú†À~øØ6ùð!‚0%|v0%LŽr¤<äïÞY|:‘a ùQ¤÷•- \;"p£ïf&{ˆ!­`5GÔHHðeeŒ±$Ëñž­>o¬àki-( ”hÁØåÜ'—ž(CGŠ´`”‰DÉÂî$ëôj7‡cÞ×ìªL Ì2ª«´ÇÅ2B¡Œö47LOKˆg TBÃ01š¬$’BB–[Í"=({|ÜìrœPïNTêÊ^Ù¦ñ‚EZåe´ºÝ!&W¹Êc”â“f‡¡‹ ”nʤ ªYDºÀ‚Y ¦-!¼}@T÷$}C¦çm]b-WhlÐ6íd 7éÓEÍøÓWøit}QÓý¹w âЯ‰DVKù2\ÁJÀDg¥ ;€›fÀ§„E®åt𙓠¡9“ƒLL0fMV©ØÓЯæa<1ý#âc¡ûã1wšŠ·Ç3á·XH%ùxb.ëéôć¡ÿ"ˆÍÉ[¤¼E"Vz‹À a.Î)>jN›ÇÍš]Æ«û­ æ~ÛÀ5ÿpHEuîÏAðÈ}è¹L÷»ÇÍÓUæR~*¹þøÌˆ².N(…ÇÙïR2"$1ŠÃñÔ^â‚ÃØ)ËÂV3Lž2Töapb/xÑ ÍB¤´­ô*®49žp‘mèñ 3‡ª[ßô4a¦ ÁÚëv–„Iz´©M [Q~Éи]T¡tgòpøŒ¨…˜×öŠÂušM•©*)Ì6§õqƒòix‡Ð41¨÷è&¡`,„‰9È@án ÝÔ.@@{cŸ;¢Lù{þx6uFÎ.…?ñ£ ù¥K’^½ÜÆ(ææ¼Úáåžxî/ØÀ·[òd]sÕ?î¾»Á&aöñ/öfKrÙDž¼Ý‚±ÑodæÛó>=°›ÁYoOiBLZÃŒŸO!h}D”“=a%+Ûøv ÷OK¨`RfŽ?9"ÜÇ#A™¶âBQ¼¦”‹y„Øu‚é^Æ®V ã&7­ÁIniAÂzóÞÅ5I?vÃ`ÁûD»…ä²@; fÐ+ Ÿã˜0xì<“GÈ8&Ô kžüáÃôN¨•)">Ai(Kw5´L[RÂxü~|ŸGçƒL_D[•I2Ä” —Fj÷ëzãâDrá•Äi»…¼Ñp „AÅ´'ãºÏdµ“×÷™ˆ÷Êúb¹€ˆ¼ž9í‘q¤4®þà—l}‘ðžÇ ¸Ååbhν>‡zðpé÷³16´6ŠÂÆt"Üí÷&}Žõÿ…øOx³ðÝæëù‚Ò’qȸƒZÓŒ6’9oe85^D/²lÌg×QÃGÀ'}ÆZ¼Á×fÞTkÁ}$ϱ±Mˆ¢FÁG²Ž3ô¦½Ng:Ӭ˯4,´é´å8Ü¡VYJ öAJ¬¥`D©¥>|+SþΤ3Ä3Y0¾¸ 6ÈøÌç<^¸;mÎß±Wd\D¹MC9qL¨¤Û™÷gx'v>gx> _îÔ|ù…ë•1C‡ÉÀ«z XÞzàX¦KÝÇ®4"màõ³ *£Šaý!†xÔ€_£º"ÜWž\ÚL´˜Bã¡fh ˆ´@ %‘DÚdw{%E8èùºÒa@Òà}ÇÜë­Çc^N(¿­‰0|Æ~öã~÷äÀ‡šŽròá6¾oèpö&ˆàƒ†¹rŠœN5Þe§òåH­Uï8_æÑÈPb ø>¹KfhsæOwáo µžÞc§÷e>”õ§*«×Íyýœ²ü˜<é0Rtî̇»¦dcYôÄõD×ep‹»Î~'G)ºÈ.¿ÁS.^J⊀Š&Z›z¾&Ž©-œc.À i,}fÐ}'è@O2èÓÓc ¼ EʈŽýK·ÜfÌ\Ã%HLrs‘OÎn.½l]zÖ@1F¾€5JÇýW,®ó7A‚mÿ€£‚`Æ]ÛK ´“gn÷ïÓ}¹ï½Ïñ½‘ (°vݶ7Àå¹@»e{I8÷áhu}XÑqâCÇV­iR ˆà‰O*ÈwË:¨"nú׿Š%¼qj©µÌ ¼t5»ÜÞ5 w/ËÙeB]8KiºUKÎí^<"¬h0ƒžiT³ÈkT¶ŸO‹ÈUÃi2¥GXb J¦9¹¢Ø E™+”¶ÄN÷lA§DåÉTŒ2¨™6áŠûp÷ÃOóbš°däB2 ÖÔG,1’–J†!c¹Éß)«ÌŸ/øt$Ùøá¸kZ—…”T©H^tÀ+†( ‡¯‡òC`ñr؇ë[]Ò0zi‚3(¶!ÓÁ*&¯äe'’6ONç±yâ)d§¬eÚäÄœ£Ï\8 ÁœsT1“!WÚŽ¬X^GjbÏ}N,­"B',¥¨Í}\6Q![pÛjÆA$þ¬pç7TY2ø¬àx“b#ƒÕ¶„v§Ž©IÏ»ÈÑWh¹ÛùãÊhÐ4-#¸…ÀÐúó2£3q,3Êö.‡SÁ z¦Åb  Šñ4 óiŠÏÏ|^WxU¦}‰ûˆSUxÛwßzt·Üö,¤AÕ\0!6ØÄB±yŒ}¬Ž"å'ÀmsAðÔPóvGMø §°…”TñÔ:§NÀÁÑõ¢ƒêá|Âôçý—|«V\Alˆt §8j B‡aÆïÈr{±ÐKÞïÒôUNÄp¥÷ûí©qQuÅ™×eõçL‘ 3DÎÉ:ÁÃí|4áózøŠEÀ9R6ƒ¸cà'”—Šb@PH)Ã(,ú£Áœr«(â¿`2¨§ƒ;ÊŸŒrt‘ª…6Nž ýÉ”âz&Žƒ1•±§B)11hÜzTÕZ‰Ý†•!±;¸_ˆýóÇwxGc£&Õžu+‚n€q²ÿèKŸÛ÷+Ú•1”•’Ác”ä¨;Ȩ.Õ•2{] AôæÆ|±ßY³¤iN´‹Ïdÿ&I]¿mìGÌ„fÌ—®@ÒãùdÏ´ _Lͧæ ö¯D0–>=~PÌgq–í¾™wˆiV^‹m %z„橈¼˜­?™/x­“ §›óå!'®4"-iŒA©¸'PÓýúy›¯ø33 N°äET'‰0¨WFSv‰æ×d$-œi6ã$øþnwñ ‡CÊ]èfˆló‡ît<\NÊX1[àö³©q…‘¹1¥E½k°g.¥Ð]:±D|7cCþ­ Èã`.ãÊ.¤R¨“k5,103ŸÅmÎ3l¤ÆúƒNQWЩpäuT€A£¸1š AQᢠH<©}ÁØhÁ•äB¬¢Lñ(b–öß`ó÷´ÔÜb½›Ë.ɹäŠÖ’ŸIÜÃ]X\°Í¦\¸¿˜öºäðùöœS;WŒBQv ¨à3ÎD ”˜‚Œ@±u ”Hc#$oO$Uè*in¯u¾ÄØz‰ìijZŒ¡y׬G‘å°¸üusZ}Ú¸ƒXs<š¦³!pBwŒ1‰Ñ¢ sˆÜ°p¦]v¨¸f|2!ÓAXxˆä çC|Öãã¼O™q¥Ûym®XBZ³-?®Ž/ûÝù¨òÀž92-WˆTð…Ç Ú½N7Ë(Ú€ÊY“ Œ6à„éâé+Š¥Rº¥‘¢cjââ¡Ü^VO: ”ä¸1“’ÛÇ}£dŠ¥%×VJË=›æòšÛ¨{7­eÙÞ `Ë+Â\R>É?i‰1(™¦îÇÕ}.‹&±Ü¦¡smžM¯âšÇ§µdš„²½AÁ\Ø?žuшìZVLLn*ûía‘Íøë½ÓåÔÐk‰ÓFSœ`«A`è€>ÏA%]èwîk!74ïV»Í¡(lÙ·iBB˜Öµù‘# š½™³‰HH•ì!`÷ÕÜF¦íq)Žš%ÓìøÆŠ™lh~yøôI¾²E gŠŠ÷¢E¢`=s͇Àýfw¦Ì)„ÿ4YÓ¤ÐuÓ<'»iÂæg‡”4»ÃöföúÃù«¡k×EÈMy·ÿ¼Ñö–ÛÞ'Ú ¶¸-r;Rm%'8»íî¢? j&ÁÙåÝ ñõéåøY³CÆjèÌvâp¶– ÁœýI$cȩһ֬5Nȳìñ\çÇ;OÄÍeø¢ißeèL\Ì”=·Ýú4ÛJÞY\g5¬ÖËâÓºHÔP¦Ž;p6¤yÎ@˜]\7.=PÎRÔ 45œhîM\¥¤pPš šÎl$iV _™­Ö ìLF Í¡$¥Z\¯’Ô ZΉ°h™SUáRd¸½AÁ^Í´Á)E•º´wop^‰ ¦—¥*šs|¾‘ž¢÷.ÔÜwGöÒ`zàíÅB{xtÈÆäÎÒ¬zøÙÈ^Å6XÑžãi7S5.çÛr“|‰®x’º,q¥4³¦¨o­ùÁ7©ÁÝ-äA62mCÑ9"âÿÚÜ`ÉËKÍç ›ÇWõŠHx„fÈ4EkÍÏÐÀÉ8Œ‹i›»%ŠAZƒ`/³±iS,‹…®1îrÍZ£I§,™¬³XÌù.—ã…¼Gçäs}ÕDèUÜŒ bö 5gZ#«ô˜Áëh@9ªÓJ;¶/7/-O·P‹’ÎMÓ>xŽ/›½EE–$Ÿù¶”L»à(=n¶¨À 1¸¤;C¦TgÒÆ{¶ðÃ&È´š²«ê0¡µAÀî¢!PÒ$eúh”©LxAð[Påq0í¦c7‚tM3paÇ8„Š”Öä`€f3èÙ«œ' €EŒGE’º$ì#X5Äk:–2Xue5„tMÿÅ/ÿðÓ<š<@iãAî‚í_v8ý¦£Ý.ã3|„ üS¯”K Át…QM—õ,†j¢"Id´Ò#†šÈ UaˆV°“ʈÓ뎙Œª*X$C¬AÙ^؉’Ô<¶ùŠÊ|èà Ñvám”¹eöÂ*ÌšP<-aÛÔÍKRi¬ET°mRë ‡Èýkà}Óc(R4«Ë3MÝ6ólж×c/lH¬æ‰mA ¤¤Jñ4”‘¡x2Šñ…} Å“k%äd*zÖ@$LÐ9еÑÐDgD ³Ý¢Ïô9_ã54sÎÁ¸Ùƒ"“´ |1¯x÷ô´QÃ%]Ï'þ¥Ld¹ï[næÄ\­Dsf.Õks©:ªÑ¥ò‹ÑŒÞ¯(7ß`jsÁ§™µºx˜ÞeÖî,2§”‚ZáI%µ3À-Á†Ï­!"x¸e2æ‹WŽeBM„F ¡{ì«õè@á qÊvί¼ž^‘¶=7mÙ ?ôIo©¿Î!ê¢è¥Zµñî ¶¶V¯ÓŒ¸Ø¸ëqy¾  ‹£‘¸Í0ŸPŽvA DkÚ Ú\‹ÍW»ÝÞÔ_w.»™Gæ_¹> Ï¡{¢9ÅívÐÄ…lƒ¦@z'Œ®2Ðu\eXÀ›.ƒAžª‘¤ȈBV¸"ÜÂÿ)È#Š•£¾k,Áp‹‰aP‚=m÷§ÓêøÍÂáÆáÚ"Bæ9|Çcl¡èb ¡,jw›5•´`|ÿ­Û'÷P1yà“w­ÃçåuQwÏÙv¢ìí“Eo’JáÆàµz¾IrÌó# «°7 ]fƒ€}ä i$ŸÃØñ<ãhf+ŠP ÷` jr0 ÖL£N|Ƨõ2v#‡Å“¡°)ÜØ^µ r>xd¨1›8îÓ¸ÏôQ‚„éqê÷Ð}ÑžÈE9}{½ÁÁ6Cy½Æêç»"b½£íÜWkC‰ÄÐaæ¶²~*í_(Þ™ì82bÃôl¸ëåŠYc£ÇÌ›~ŠCáªÒeºç‡ÂL¨é|9èvÿd-Mpý3%ÑrÿW¼Ïò4Mb¦‡ãˆl›@:1‡¢ŠÖX0Qgç$É¢‡º7½(O'uiwØ›Œp‹–öí)]¹ìM§x …’µð3*ÞÅWPœ²ô݆Z;ȉ,‹³®î×›½í=M|™h¾3BËo:M®­!¸ùS¾d§»7÷û`Ð0?[Ö{ªú%Ÿˆæ m~²­uï07ÆxÏVç•æÝ\ÜTöK~Òzɯ›"Šøuú¼œÚbô©í2åJÛ.Ÿò3y¬‚Æ t=c0 ÌŸWÛ‹¬@NÊ¡ÊLœJ©Ëïu:@¢ª Á­MÛP´–"ÏpŒ‹9¼ètÇ#ο û ve)q<sü‘ºµJOưÅTÓŒ™Æ DHæXs‰n7§Ác#Ð6í†o¬úÆ›ƒ,AÖñI®÷c~-²Ew>ÇdèôPÙ*£U4Ë_ö  ºY%@Ò@E¦NYpš0‘Û׌f.êäúO¸­þ]îHtƒ%ŒÇÜ¿6½†åk§Þ³1¾kÉ<¶iLÿø UbÈíÖ#mÚÓ²½¤€j…ªæŠ÷HFc¨%­14?ì­!`–LÃ$ ‚øÂ ‘>áI£ ŽÁ´ñ¾±Ñwá߈Yç6d{Ä&¾²IÄŽ€H:ÖlÐã ùq‹®ãÈ üÂÀà„3uò$SI‰µeš=úÀ7È0À´Ò  !¬Ùï[ÔüŠ40Ø–gp$gÈÈó~…‹Ləӯ£6ÊäÑ{00ï÷_pîpy«È;Èý"’!<(™cñršÑ6 /ÀÚª.Ÿ’¦TÑ|ÙŸ7sŠÆ#Oa‰’¤Øè9U xºAO C jÛpÙ47 ˜2121/ùÉO¯¶ ì ùüW¹BÀu˜ðü É‘yr¥!_FÆn,‡T ð”û¤3é8·|2ϳ³Ún÷ëPŸ4Kæƒá³dљニ y®h:ïc f ²P eûJÞÄ׈1…Y®d]±Ã§/– -Kzå¯ûíÑÐeÃð¸-×(ð»WßÛ4Ÿæü÷\>ä÷—Ø á4‚#üΈ±Ê X”xH*ž)™+ǃ,©0Z=dæN:ãù£¦Gkƒï›˜ ¼I,²ëj°ÏûØÖÒ”á‚ût¥¬¼Æâ™ûÛÙ2tN 5œÌðò!ž6hQÊ%3t³‡ú<fýÁð2 âZk@(C® ¶ìžb׋uh:ÊžÖi¾û1‰'GØçSzs+/£F2í?E "eÿ SQ0Ñ3,EÌ&HÅà¥ìÁ!Ék=^-8Y¦ gÔœ÷Ÿ¤;ƒ%ÆLö“RRL~9":«RÙ:'Ñ+Ìi[?­^oçP©y­I·3Y`!¶úóάË%¶6‡ÕƒÅ#¶O°õÇN/Ò#Qºy÷ÁBÂQÕÈ- ­¯ŸWñ"dR(]wnŽÒͺù/(L¶Èåѹ èðÃP„¿ÅütÚ¾z»Áÿà¶[zØ«Œ×¡·%YÁÇŒ½Â飇Yf8Ž¢|4 [wÆOq¿*UQsàæl ºùòŒ°ŽÜÆhà¼r”¨=(èÐhh0†ƒ±r{'ȈÕbÎÐ~És"ba{&"tˆe‚\úÅòa¹Ç¢àp7nhƒizøãvÊô íÔBGa•ÄiF'9@Ä8ÀMD³ãØ/  nÂ,†i÷w(zÌÇÒާ"!q‹&”(¡"†‰!á4»8ƒ ‹PZ#tmÂaqÏÄ^Œ‰üz¢Ha\‹âÅ” IÍÂÙ‹ ²…Cn8£ŒÕ@“ærzF>E¤,T'Õq2‰aѲˆ—*Ö25ŽÉD뛨-ÉùÐ(?Òx½Í&æ*5ÃFýóoƒÿÁ—$öJúb…dcú ”xBõá(ƒƒNíxM;X.ï=T ÖysÄ输$¶&˃g0ÀÜ̧a«¯8;‘h¨¹Ë¢¥aë½Ãòª=ìÏëåér¯(Ò—#)3MЋ uk®útÿ_)’ƒ]Cñ)yÑ0?êiF3¨9ëWÅd~ÄçH̤Ÿ1UÔŽøaÎÐWP{6UâVxÌT‰Ûªa†Jœe¨„Á¯‰Es+¼ÕÑ0Dö«ç×s~ìÄ¥ÓBMšzœ«]®Ïk–Ô®»çƒV E©H6zÏØ¶ @i•àbI ì´ÆqO<¸aX³q~N¦¹<}Yᩆh¼Q¨¨ŽÜ7c™¢â`-Ìoº¨ÇéñÆ-ÄØÙZpÈ®…ôÊúI™VåÙš]h^Gí`Q󓲂ÚÑ|#ÕQ;K¡ÉZØI›eÜ&¯‡iM"÷ ö°:¡xS<)‘ÐW³¶Užk`æ¶ŠT½öFÍcÝz{0·E|ÛÖ3·E¸õõ0CÿuËíá cJýu«íaw|щ5<-=Ö-¶ 9‹ì&ë‰3«n±µMŽ"•{ÀÃÉ2@¸˜S³öÔÞaüš;ÎÃÉš’Hè­ƒYv‹jlÔŒ]'0õ(=I视˜µM!ß¿fmS(XSÓˉµµ0½lè^Jhß ?ùÈ `zODФgÀü*M¶¹•¢²N µó½±¹!’P3§¤_¦LZ[)>·ë¨Y[) ÚÔÃô,Aé™Z˜±•"6V3¨Õ®·_ͽA™r¿šÖ¡ÿjÜf½zY}U†9ü5¸W·zðò…I¯nùl~µquËçd«³nùœÌ/þiÝòOoyB¨S­ÍÓÚ½ºt2]!DƒjÈYûŽú¦7“½_áf¦†ŒA{›;™.îóÕÁ¬Ïhœâ×Ãôº[øuPÁ¤áB!Ͻ†˜9l¸dK0Î47þ“åB!=¾¥|ø `Ê…j#ó žšv¡¯P‡³\¨6åTT«Äúnãì¢fl<í–›[pÒ¾P·j‰é¿›¶u0ÃjSI¾2èÀÔüÇE€z˜ò…p ×¥¼Ã6Þ/«Í+`F6À)_g±u0ËB¢|=LûBôRhpVX¡ \-Ì¢V»ÜΆ/„<¿ZjFXïÓÕô/ÔF‘‹:ÙŽ–luëík~D¼>öMÚ¸¢ZMîWkónãi옵™¶‘]Ãfj†ëÛ8Á¨‡šáú6’ê ¦ÁD圵#Û­flÆm¼(]GÍó#W®¦Ãü”jTKM‡ùÛ¸S³ÂümÜ0¬ƒY*Á©W=LÛçNÝÊû‘wµ:u PÚ>#§§–GË>#¨§í3²Ìë`Ö&ŽgOja†JjלæGMõ:bærCnN V¸¾M©i•{ÿ¯'kïG’T-Ì·ÚõvúvÔã†CÔr澊[~µ0c7@®xÌš%¸kU ³¨Õ®7s_EÊn5k_ÅMµZ˜±¯¢Žx=LÛT[e£ˆ>?äEïᬇ¯´Æ¶g‘Žºhu:”ÏFÉ>ë‡Gµç(…mÛþP,3; ̆ïd´·7æ™1*t¤©Ínÿ‚”qó$[¯¿¡ŽçÛþp+«D™lzý¥€Ï›Óß4Þ€TLbÞ‚$p.wTf uÚþh+%Zþõ°ßá±uS—Þ†¤è•P“[oIÒèªÆãî¹Rì>>p^}4YüW%ÈbÑŸq%qÈ/× z#’ë“”7" ØÓ ¤4-oBª@&1oC’¸ ^ñSš¯^qO¸C|2‰U¯¸§|ÿ’#'W¥b 6S庼à™Î¶æ³zÉy˜ÉiõºsHíùS®Ô,ñ0“ ß»ãðL—X+ôS½ü¶«Ã–ïnÅ‹¡zÝy˜Å®?òJ Šû9X|Æ@B¼*[]àL’~'OhÐÕ[Ôvžî«“[T4‰V¯Å]rsÁ&UD+ÔoBR}4 (ŠS2ù¬^‘‡•égŽ«×ãa¿9PlIqY½¬Ž«oÛ|óô¬qÕ‹ªÀ™òUïggÓÖ£ÜD•6d«^M_òÍýek̳êÕäaAŸêLWJbæ9¿ÿvzÎ?GIš¶«Ï¨¦zäõÐ#Ëãj]yGd{æÖÂL'ñ¢ &3v¤¨º£Üdž¡4~L«DQÞwÙEÇúeu–ê’Ë:ØpxÇ”Š^[2.V òÆH1˜r±nqlcŒ»›œs㣱àöKÔ&!˜"ã  µèz{\9B'Ôdײ]3>„ÔT‡îNn†²‹±mÞäyþ/\^„>Îyd³Ö@ÝÈ ‘ê¶ *ÎÐØàQeÕCàËêSŽ:"œ•ŒÏMµ›„ðÕa55tßÀªï­Kubh'sÓÕ*•¢Pðõéh~Ñwè™2Zvúê*~õ¨åòo+•Öúµ^U:êà†uC²zź›V Xþ¢âÇw²Ô«—¬»sÕ«ây(WÕPÞ/†¼~õÔéy‘šî(§žiu<‹ŠKÍXþÔîkª~óªcùSGÅê©f\£©ñ©k`ÎæO=Ûp:ê؆ÓùÓÀÀúÍ«NW/û=¯Üe¦úá%°žÑîNS=š^鉜sÔ¬¥Qj÷•s.ìÆ—ýñÓé`9tð\òóÝ=Ž»”ŽÝ­–qt&tL`œ j¤›Em”aK!ÕyjÌ8ÑcÓö>S FŒb®Š¤»82n#Û»]£ãõæîƒà5‰äoÿ¦);ÓRR×ÖQÑŽ…íè¸r10Û‹žEx~˜fQ ¥×ΛÃVO^w‡¤ z8[Â9§‚âߌ±pp%ˆÞúЬKy©bñôYOqLíPÄÌX®€Æ¸C•ìù†©Í6$ twÜ ’*F d("àƒÄ`‚Éó‘âq“!ü{NY‘ª‹àƒ¶‹ƒÖ*EBÁŠ7ò½!à;ÃT¸ÌèœI׿躤Å1¹§&³ü¨9­†/|㛪ëò«èYß÷(òT'WK8P¬¿¦åózÆ(Ú7kôi}˜S‘ÕØá¸W~×Ç·*ôyÜAyÞx­¡6Y=”.I膞ü$+”Ö•/ÙEyñØçM.óŽh =9q¤XħÃ%Cc‡BQD¨‹cµxnnÔ©U—º¢Öxc[·FÜ€à‰FQÛ1ZÃá9®è} ®<'M\-T#‘ð¥Æ O«VPÿ O­á´KûX]WÓÂÙœ>¢|"°š¢óVR°'Ú‚å‰TQ£ k 2U¨«»šÝÛ%º¸h+~çT·wLõp Æj‘:A5œÆ“(‹×ÿÀ9#I2|Œ‰áãIÔÒÁbbðîi€“°Ïù“ªØ†iîLTµt°˜&L¬¯ÕN¾Ã£>YèºÂ$ãªÊÆš÷Ú%>ëÓ…®K߬F>>¤¦¡«PRƒNLaW¦¤‹ÀËÃÆZq®XI5xûb¸¡x½Äk·BUì£ÁÍ3Žcº®JG5eúÜSKù<¬H9±ÆÈ2c.ýiÜKChXw½<­Î9ïM”ý«¡v /ëá­½F$ÍBjµ X© ݱ· U¢c^Bk›—ͯ†…;›\©»*¸7/UôO÷Bd¼€aþj…>óÏHO9­­ŽÛüµ|F)nTq¾¤¢­ÑF–9¥RþßQøïðTÇýþ×›D!Z·WW‚hÿÝ‹÷'ò |4¥]µâë½JkÌ4wùê»2^K{m%ÌöÜÅñ`ýußs·Çk±ùgò€c©‡.G,kÃõŽ*.¥~®bÍC—핵uÁZVv±çn”×òÍ#½¤s¹x^Á o4bÇOq÷acϬRl@©2tùcYAÇ*¥mÏ4¿€jfÚñS/.ì Eî|£BwCôè ìSÏ]@¯¯ã'U•’~ì©ÓŸž»‹^Kž€^ÔîÆãx¸P#…£ÿ— ½ø­ó’{îÆi ß ‰{¨H£‚=ý©&kGŽzîþi-q+ ÔóÁ£:º¡ì±Íõ¤f]({ÒC%}ÞR W»?|@ÛIaÕ½Æó"~.WÀª*_£·cVÑ­¨}Ý¡jÄÕ’RÞ:½|¾¬¨õÜóI|\˜õ¯AÞoWiùÍ Ø=ŸcVA ¢àBχß*P•Bº3€´&êœÐ ˜Ugªq_k8³‚vχûªp¦nü6”‰‹UE»çÄUäò9·è?H¬:á=<Œ]3o tõúAÌìuý$æcí:ŽØ©œhµkÚw–XT>Ó­^³¶,>Ù­nM£^í‚ö¼W)À§½Õs`ÎÈžûê¬GÛóÒç¾ÕÃíå‡'JšM(«’}ÏgÀ5 n‹î4 à Ùk€=aäèÛ J"êØãt36Ä>œ1Âl‰\OjŽOrí¸ùXˆ^Ôßk’y›½ÌÙPã- âïçåúr¯/cöüçÿh rìB,^åy ,2ù •LaG*A‚_ü9êð¿2qågÎ,âY#[NKñì¬Ù`SIlz](C@—^©Â&ÆçDz|YÆÆ‚¿ØÝãT=j*¿Øxˆqs²¼ZW©V›;ê,z®Bkª9¾Ù79âÂÇ/ûÿEa¹R­i8ÓŒOW¨5 :íïOoÄ÷Yÿú` ×°øg¼Š|ÂÞ!ŽGÌ#$È»=®cªœŠò9rU`]†¢çª™â®bnÃwÜÕÔö#ÕP»EÏUC­!ë°ËóA{ô Ô‰k—´èùL•*®×¸Ø Mz®Èi%ËÜçÞê¤äžOm©¢Š9W9qòÏ?<ÕX=“è‚’¼T Qϧ¹à"jrFUä=õ|¾K ܨVÑóé.UH³bEÏÕL¥«³IŽ©’„Ö‘Ûéªpf)‰žÏz©e!zxê¯nTxÙœW©!-VkZLÿŠ—¥Öo *JÖNè¹*ª•úuu4Y¿ŸTuuqÒ:Maö>¬TšVÏ]û®ä6Qí¡çÓ«Æu›V‰Zc¯evÿ´ÂÓqÏ/‘—€CŽž{M¨šãD¹ˆý¶ë>ôÜ•óJÂ|ð™°ÇþvX•º’åz3ç¦Ví=zW–œ”ŠIeWsèÍ\H§iWtèù̳*hQAÏåú…{z¾<>ª·Ÿ05ê×íé€DR½à¯:-™5!zH­&ê;ô}Èl¤ÓC ·¬ïª⮤:Ak¸-ûãþôÜîÆê¤¬:f0[¿è¼Ø¾«E˜¤…LˆüÛ^Ù’¾«E˜„=ä+dSh½=Hph]àëûì¼”67§ç—Õ®=ÒÄÜÇf °ÓÒ@ï"$¹dŠU£¼ïcÂ)ŠO§£Š÷÷}08ú´»œŸá²j.ýjOpYà”ÛÞG]‹ªirâÖ±&ê÷éQøêãø¤ŠUsBûåàðŘ”~]'GL@¥¶ô’®ß—¦PÑjó!à Œ#þ­ÀhÓჿtè»Òƒ°*ùŠÍ}fõôªôÉšU¨½ºpß÷ñÞ*”6R>Ø[R\úþºpf{Ñ ßÇy«P_ ‹)©ÀíW•­Ò÷ÁÝ Z/:y­ïC¹I”þÞéã5p·ølöNørÈed>Ë©BQàM­&TM1GÖ0NMÂ0O‡ bYìC¶hgm$|Ü4I‹Ÿ”>.ú>Zš]v*òÐ÷Ò HW¯xM>ëç4ú=ïe&ïŒ-*¢íÚz¿ò7‚SÄ~½èEå§Â!íÐX©Q}G-ÕöÕ„ùû‡iØ=²j×|®Ь­€̳>ÂհЬ¾O¯LÓ|Dü°×ëÅU”¬à6™wÕ÷9™Dí´©¾{;­‚¦‘xDöÀßLÄàívµDG.:];çùΨ2×wÕÛ„¬æ’5tºSß'@¦Ú/—O´ëÜ®¡E$û>\:¨tZjn÷}´4…±Ï¸úîU«q ežlõý½¼(QÓØúy)ˆu Ówo`%y«8ùê»­’PóÔ¦ïãÀ)Ísª¾ÿ&A¦2œ¯šÄØÚpÞjb Ù¯,wú>Ì–BÇPN\ƒµç­×aM}9‡ j+Ì}ŠÖamy}&pjÝ,­zd}X Úì´Ë’—n"Û6˜‰a!¨ÝÈŸÿUÒÎ"éoZ§¡—{ã’`ߟÍÕÀ ‚(xL2BCêÚäI[‡QøÈÔwº£ƒÍÓ!_?^vëø|zä>å1lê"ÿéq¹ÚÕ‰vOϳÖuÁÑ‚Še0Þa]ö)„ѹçΩr¥»rƒ À¸¡ê$ô]h ú¼ÚÑZŠØ¹äÂlŒY+õ§Ž¸¤®2]>²RÔÔ§m6Fœö]ÝÂj)Õåêå°<<¯N*½¯ïŠ&¾²ʼn7™UCí9Ñ_Mî ¶Fü 3î)¶fh¢qO²5Cë(2Êj—†û‡q,\,¯ÁÐ/Õ…‚>Jø5¥ýo†Ö\ð¾ é3´æ qƒáþ7CkÞmj„6´æ=¡pu9 Ùµö'¥µ¿¿ÐDkRZø ÐJk¡Zimào04›7qþCó¢/¨{¯ÑR;å»X·ˆþNB&ÎxNIY»{]¯®ƒÈÒ ü†&¨qàžÍkDý?Ù×|Åÿ§1ûš¯øÿ4f_óÿŸÚÒ üņ&Z³öó¿hTƒ×9=7¡ˆ$.å7Úî ªŒ*\¸OÍõ‘;ÊÆºÈ¼¬õ!Q]µzà¢ÃìHzs¸Òà±Ñ´¹c¡l¬Aˆ ò¤P¢=æràÞ¢«!è±Á{þ®gžíÍÜ,£'eÚ£cù€‹ÉªÊÓÀ=‚WK×#¦©À9×4­I>¬¾P8*Ê{:¯š ‡*râ9= pzï¿iûäÜ«¡ÆHEŒÏ=³ ^†l<“¡E+µæïê ?0Rã•b*ic—oóÄ[Wú[bà^ø«/€+²ü™›e8XÓ2æÈÔ7#þ<¾rUy¨"ÇþÈ©œS–rK×[ãéâñëÈ7cGîlä¬ü¨?ÿüñ5­ã£6l> H…º•xîì¥IùÊpÔe§/Ëpta ÝWUÿ DÞS«˜œÈØSŸoî „4SóëÁš#>K¡Z*æ>± ªêŒrÄÙé¢z˜_8ÂÙà9”p‰•9ð© •ü†øˆé‘;?Ê2”µÐƒá’£ñø›k•$Í´ÂO‘¨GZ{ðÈUÿÌð9n±š£ØÌýꢫ­ |žD5ÕkÈÿÌ2TYÕòÉ}±ŠüU±J’)hñY¢'íÕÛ)…°Õek¡ÝBŸÚÑÞ¶à ¶Çø÷ùâÅ:ð—›PïXÔ‹OÁZµ-‰iÓM^}ñé!Þ®ž0«€¦Ù[Wr|«Yå7œÖX$ñ˜^oP˜ÜíÊaAvú³L?û ³¥éÿ`Éè£ÉUŽhÜÀn`*êËÀg¦Tkس¾ücW…‰>I¥YtcE³à/›(`ùïJ„‘;ËÎ2cãlxb>q¥šeàâñuGØ ¤®,`|Q4íy“_ô„*ÂN«Æc—H¥ç0rDx€òÜ.úÔ :”R/  |&L¥Èë=N‹cá>+¦Q¨¯dËQĢȑ,n;ðÉ6•œökUitär² )Úz¢à6º[ÄQÿ›EÆmä@ÐÚ×§š,>»§Z4à"B[²‡›P—£I\Ö˜´a”«§äÔØJú‹•5ôªXm`±NÏÆQÁÀ§UŃ˜tä²j²LטÅÊ=}Û­Ÿ{Ô1Ñߣ>Ǩšf€¤ázo{8ÑSîÌYWô†Òo“X¢Q¿!ÔoÅÕE¯Á„2¢†Iô:7 Šý•žV¤Š(~… ``$ÕÀ#š 4KEñí<øtûI[•F£×øåLUj ÅõØÔV‚Ìü“¿3R´ÏýþÒH5Ö<öø{#ÕPë3Ìß©Vä˜ üµ‘úÔðwFª‘æøÀß©†š'þ[¤jªÊÍÙ¤uÞ?ð×Ej ¶¬þ$}¢KK•‡º÷§¼\/–^æò›•QCtàOÕk:øt9ž÷'ý¸ßÀ§cÕÀá¼ë¯$Ÿ^U}Éu¦ÿÀ§YÕBQßY9’ŸÿT6 ü}Öða‰r™ }»Ï«špmoƒ£P½pŸ;Tƒ?}Šjí’ã³xj ç3* j²î0º›”Ú§áÔÀ¿$&ù´X˜Ú£»šøåòKr’ú´Ä:êæTóÕÀ«Wöò‹­ðb¬+¶&ðÒÚÐ'ÑOPK7Þ //±¹úO4»5^ˆË?£|±:Äú‹5°ó‘_"ë3ô÷ RXrî-Š~8M± Fi‚\ í‹¨gÎ7ÝnßOµ?}“^Õ`@ÁQWƒã%  5;ͺ óÐ' MôŒBxôE¿aÏNðVm<´DêqëcöÜó»cœZ[ìáÆ³Ú†ˆØÒ7åD?ÉÌ!Œ´—‹ M*õ°Ù=R‰Äx2ÀacRȳ²DÂ[Í ¦Q.j’@mFDzˆ«}UÄp2Ó6h¹¨OŠ®\Å5ßYÅã›¶Ú_…þŸåHïµÔA%+”2üGýcg°}•è$Àôa‡¾6wÊUAR&ÆWÀ®&²@‡(ŽÂ£–’ïZ=Ìt‚‡þ5Ëzòþìpà>‚ÒØÎûZªyOðì÷€¤È†':ô/Š¥y´œPz㳚Ã*µ €L5Øt^‡þ²4§¦“>ôïUÀLµx'$©K³æØÐ?:VAÌ–ÍWæOã0]õãC_•¿fÝê¢b{õ n…êíÊêÖÍ/zã 6kð¡”:zÖSC¤eÖ°i=e1ÔM/<¸Q·‡o±“#¾ÄCÞ6ÆšñO?TŒƒõÅ—QjLÑsÑœ züFè¢ð8¸ÃÎ:X,ªpŠ(w´½ žºU iˆÀ; f ¾¬>#A@ŧ†þË4À[“±8¾VC¥ˆ]$G‰äbèUPTñ¸ÏQ?G }|%ú‹^?>ÞT{^éë£CdJVkެWëUÎÿýûßþæ7¿Ù­^òïþïwxãšÿë' ø¯ùWÜ/Älß?í/ð6?sjü»ÿótÜ_ÿïwùoúG§ ßd[Ê®œ¯Òc]à•Öœ#ë¨ëôÙÍi…½›üǨ'& EnqVµÃßÿ5):-œfÑétu¼Gèô±è;(?™ p—«ÝïvZHè‡ß}ÿOßM÷ëýÊÄà.}aÓ ¹¡/—V6\ÌÛcÂd—‡Íþã~¿½ßMBqA¡8 Š¡¿™´Ø$’ðMO&ÀM÷ǜɚ¸yÖAÆ +Ÿƒ¢ÿý²Yú¸AN¤¢'ƺÖ{ýÐGs<@>GUûUØì´»Ó+”+qoî_=®‹yg†ÃâyoÑ!y ÕÏç½.©{¿]C)xö”š1\×ýë&!õ†3f׌fqWñ‚jæúé§]ߘ· é[ÃqµÂ]Bª`¾¹_þ¼]¥Ð öwÂÆ!¤J1oôžn©ÈE¾:_Žù_òÍÓóù„\4™\Ä@T£¦¨jjÝ ­ ù´ 9›3¯nÉé94ð,Ã(ѯ1"ˆ-$x8 ž cùÜ7’Zµ~ˆg×^J9œfSD ‹Å¨o³ÖtBÕiN5BðįüÈgÄÀ!Ì’@H*Ä&!ó%'ãÝ ±²ãnyÞ/§¸þ´?b_B6éU¹e–÷á‡ñ5}œˆµ‰5[¿.¡‡ùîájñ¿ó7½±h~û[ü6ÉŸ6;úõP\†É›Á]g [ú=aŒÔT²lÊÆC-k¤ze†ï‰HÆ7Îß­NŸ`:íÞ°7Â;]Cn@®ñ)Ú°£¸M8%íìˆ2š”\pe!KÉÍ?»"6$¹/i`±·Æd 8Øàõ”J8ÒÚ¡±è} pMðå‡CŽ·¯«;p*¯î`ùó€«ÄpQ£šn0‡ë{*ª¶Z ¡Uá*5R¼õã›h.‚­Î¼œå[>ˆL(¾Ajº€ Þ£¶ýG$VŠ‚o £«zÌ9Ñ`. haÐó@R}=isð‹ŸØïOëÌ3†-iæõØ¿ª €q7¤pÍ7Hœª›£çÀïŠ×/“r à$ííx%qsàñb(ÕQÙ“9’²§r7©ìÉÑ秊 s<BVÒÃr±§'•3;¬¡È¢ƒ;d~ù€& :‰>È !9Ix½Ž8’Ф›º>øŒ$Ý9¤lY5Š™Ú/G®~ƒ@èß Ù,Â7-©Wi/ÛZØíêtÂû€k^ÐW÷ü¦QR{xÎÐêd¿{Ü<]¨Â5gÙ¤á¦ò§€_|ì" 5ÐŒªÛâ57LTN_¤<|Ï>þ¥RcæHÍ¿®7î-r2“üÂÍ4(:‹ÕÐnfæˆù.(p°#¥UsaŽ×»Ù‡JÖÍQz‡8$?›WMЦ¦×è }ÝM³JNÍÕx·9¯Ÿq?¡‘‚Ì1&{ö´ß5쟃ël" •ظc¾Í:U²£ŠŽ…$¿°)ßæ8;S‹Ìj¬fÁìkî~øiþ±RsÐàÌqw8r‹˜õJÂæ°ø0¥¯þäšFðÈP9ÍŸßçˆP4›t(æbõððZ^ÓNÌñŸî·¨=Iv¸i7æ$˜î_àT~'¡¦¶!ÄO¿¼«œ2¨Øc£Pq,Wjßt¤WÖª­8{¸ù-ΆzBÐ`üwñg®TÅ²Ó ô;TÍ8øoÙzÇÉfF3¿í~ÜäÇ}˜:\ Ƀ¦L¼©Èð²3ö¢ó·fL ÷Á„×l=xÿ;nHÝ\7w{œ<6 n®Zú ‰›ó€-fâæ`ðû|ðBu`anŽ}àw7àÀ~×Åå¥zÃ×oª?\FU‹J êÙŽ§m%ÐT<9ð(êî‹OˆT0v”^eš˜ sòà ¦ 7Þ„7Ƚ!Aëÿ½²7s%„¥mŽEC9Ì‘(±´‡×~”Bæ¸4šcâ´’+7AaC«¸gL…?®Ž/ô¶"ìg%Øû^VOPOø,³VÛä«Å®„š#|…ÖéÉÇŽ£ä«{.ú”fØÔ÷»'¶t• ›ÃúãyUñÉ ™ãY[šÑ‹MÆhúÏ3 «Ôx¡èÁÒ°Ú•îŽû5JeU Ž Þ5¬¸šÊ>Ì5y·B@fz9â9ÝŠI†Cƒ~½üæx1¬nrá¶kŠ"Aù# ¡òp†ôÿ{û²eGŽäÊçÖWÐúiF¦–‰%“Í2‘IRdKU$[z‚á‰{ÁÂF,µÉæßçxDäÅ~<5c6Öì*²êO_4RÓðqx½SXlá‰P¥õzpØJ¾¾ìß8ËÝ’´g"zn/4Ú®K\ ÜåZvübÒAsl-ÚŽ—+´ûÒÙ\ÄÅ>x€Ž°ß˜zl‘¯A†;=F±9E¤±ÅÆsžÑCW&=ºßnt¿ÔÎC˼«“ «¬@f®¬ÊIˆº¸íÑî9ig ÿã£å'5Ü•V]ë SG¢´6Å_¶¤ýèal)ˆˆŒñÐBÝHWbe8þ'¨xF)A,.æ#[ˆøk`s…iixÆßADêæ<RÇŠÛiެKs¢üG÷¢ÁšMÞYd–÷b"õM#ܶy26ª /XYñfõÙ¼ã/yÇ­÷g\(2zgOóՎ¢/?ŸN¶£ÓŽnðÅ;GGŽnqè°MÑÓ6™±÷ñ êÆvWPÖ…Øèî¶ÀE÷äûÃlÿ²šSS7þõÒ€Ð(:¨hñÒ2|ðŽz-EÅa½:î¹!b1rvÄe鳚õ£› _‡5MíåÉéÚjN|ÇäAɱ9Ökꑚ $3†{·šK@Ѧ‘]È…E÷ÂG Ê;âžê4& úî€+WöÈÝŒkÔ•’ÒœtO½0¹EåugŸO$nFШ´¸8îðm£ë„´ÍÖ{ÊÙî ]3‚ƒ‹Š"s#(ù’¶˜etGÅÉ”" êÉD-€È¿IÁÿÔ{¸îÎ)K¦C£RÛ„^­HÄuIU ‘ Ææi`¢„Ë%¢Z­qZòÙ–<õ`ä¨áý¦^{¸³ßXÜG•RËñ£»õz1‡ŽîXQÅØ¡A˜zt«š]¾²˜ùE,îioÈ0qC½÷ˆt7âö³±ê¨£C[¨è—¹1 [½ÐM:q÷>¼g_·À}«¨áZüê®x9œqï~ùæò¶'ˆ ]ìèn¿?o·õCáKŽñ|‰ò¢‚‡í3ûÀ$¨f™û¡~ÆÃä!ì'qüx¹„mã®$KD–QÑ“òÁsÝnßÁ›€½Æ$Mÿ,Åô.NÑ-éÕs?›ÊzD–õB†ÇL’¸ßþ‚7ýÓ J.G8¨Î %èãÊr<$q÷ýE“·Ð%Iܵ.ï,.¶zqßzÁ¢&IÜÛ7$ûj+nD¢Çáõù¡¥L¢”idíè´¥ý|}ø}B—-n IT_Pqþ@ƒHÔ*BœÅü Á‚lxTíŒÌZVtÇ$A³Î8v™2ë(A&H÷ÎeÿHIÎpÔä#øju:/jÃÛŸ j^dì¸i„&(x!Ò|oEâ#[räKEÐ YÀÔï»Õ¼#ñ«”üÑ?zIÕÚ×±˜Ó&:úò=¢£kàTTóšã£.‚‘9m|æXýÅEÔÙD¢†€¼À$½‡®Š|órÏ‚í¨E¿jýߎ§¸Ëãê!Ÿ} +[ѸËãêûçôj[bÑ£öãvQ¡ûP»J&£æ‚KN²Àá^6®¦#]2šBv¡>r8X·`Ÿÿ`$ç*;fƒšºÞ†‰ ~R»ú’ƒ†+œ5vŒ°æ+à÷gæ$HPÕÍ©0)Šsí:¼É6X·šWlc²;î¢bÌ‘ƒÝ;%nÞœ›ÉûWk ÚŒ¨?Ýæ©B¡žÈ¢¿Þ=­¡›Cq;ôíK¹v„ßi^ƒLt#æO¾HMó2b¢ ¿AïðVûË»ÿdÊu°ýºÝËÿmü3C6þPÔ`¸bCþýý¿–ÓüÇ·ã÷tè&~úÀûrnÐ.ׄ6gã‚>­jÎÅÍ-Âå.„(Qsôæ€ÜQðùnÖð2¾7!qæÐÍɺA7ÁÍ鸹|\Â^L|s>nðîÚFR¾&¨ÿÄä×*ph°ÅQµøêHâ ÀQÍ‘º¹8lv§Õ²¯)ÊO fÚÑU‰¢·Åæ%Í⯆G™©)š±l©Á>°þlà{wùhýf0ÞÈõ èÎñnmªù‘oLCqá¢Ù¼à aýËp—šÀF¦o€ðY.—R>ˆÆ!$ÍëÏí¨²ÆRyïL¡¿`d®Þ 6A¦Í“ ªR_MÖ!w æ.„D†1‘1çñ3ióÚó8lS U×·)z3ûÙâks‘)áÙlBs6 ìzÎa›géÚsöâ<3Ä#MšoÌ-þâ@3 4ß™ëÛ9¬Lhs¢n 0ÂâëªLiöSŠn”n±!ÓW³–Ånê%ëÐðx„JéÚOÓGÁ´pœá¾ò²>nø:<íX©4 G 7Ë»ùJÅbMiœ’wÓ¼J1û¾8s“r±,¡Ö!G1$JðÍ¡€XÀ¡µCqj [Ò6åRÿo?›ÎÖk”áaik‡Ý‡Cå¢&ÂKÔcé¢£Ï‘Š»›©9Ï;P°( õ¢9h¦@á=FË€-Éðqp·à‘5{Ù!Ha¯º6W†ÞóÌ"‡Õö qKµ^ªE 0óâ }B™%õ+剆 ÕÞ£ZÄ!µÍEr¤Â(À¡_߉Üd®d—™Ô¥Ô2 )¹¥¶dŠËÐ5t†ÏøœZ†þp…)qュm•«ÊX€WÉQÁGJ¡"óGB¨þ‚f¥ N§ô„½Z?¶‚(NÔÁÏ»Å(ÁRO²d0}æ¬ÈçÊAEšڬ{ÝÆW'ÈVòîd0(új<·ìñVÐXqAwå¢AK²àuH:§Rtð *]Ô⽦ò¾~†.ßJ¦È{èÛ†öv¯ÏØ*†õAdÅeX<–F†uP6"º>k0þÐ1ÅÌÇ%Ô7ŽØeÁ“—¯¯BÓ'GJú]_H]¿LòùËG„ «¢¼¥ é—Ño&ÂàP1€§1V.ðw³Õáš„!8iŽãfSÑø€ç¼@VO‘ŽG#ä¢t`Î ÙIlããûµü_)ºôh(Î[´÷02x†y§èŽË UD xr´ƒã·á`üaZ¾-~™üøö{‘"GCéQ§¢½]» B‹ñ‘Ó;R×=5ñ \>‹^VŒÀÒ¨Û­Pt¯“öàtwur_ q´ÙÁµ¹˜À–C£”£N6psººâЋݤ;žàµ°¨TOJ§7†”÷eU~Þ=»~fí´Š£ƒ­mCG[×>LÊZ•tº£ ’;ã$­ÆÎ4vÏiÓçú$&.…£ì¸ƒ‹‘÷ÿ}¶>«6€ /m<AJ¯ð¯»q»­Üƒ/䤼;Èîû~Ë›…tl"}Ä/³Ø¸Ì†ƒú%¬Æ8étã<âxl ŠAcôA>”Ñ;ƒá$wâà‘£Sˆ3Žtò :ã´ªJ·‰¥…rbý½nd;P¨ÝåáE6qÄš{N–sT"fÒ)²´ÓÍàq'Ä¿ñÒ‡Z€+iU£>Þ€¯_ÇÛ°"®Ç(®ÈÑI'}TÈ—c¾;üœãƒ]I?Cvlëdœ¢^¾Àß}®×x`ÎR@~˜¡Ù]‰®ã÷óŽà]G…a›#‚×dYøäÈÈC1UhB>.„mQOO¸v}lzÆÄmkÁ»ÞžÃ!zÄðth×ì`(ߊ´qMo;•蜸^.h¿ K":ßÇæÒŽF§äz€Rd7ÜšJM“kì4>v‡ö‹ûÚ]F§àú4 ‡x]ŽNÊ`f°k 2"=%J }Òl)'r‰-j«½׺\঑¡l¸>Ã!Þg¢ø¦±Œ²Ž`Àõã|8b œ­up œ†ÃJYƦٌ΀ëvÐSQš¶3*ß¶{8‚óòžBè¡¡¸´ÐX'Ýíã=TîÀ.~žiÆ ÉØoÁxô°óÅr*Ïz lÁû¾{8S,Ô79Ý(xÏúKýôõø‚N˜úÌ“ '—q»ðsÉÈž¢(’^+Çï5ÜäñÃGý„"£Ô5… ”~íÅô¹ã™hÓF˜Çc¦¿2}8~‹vn“ÒË{‰6÷c®ô'PLW.dnÈÇv5«Ê,Pì¬@+¹ƒß.õ]8ôi¦p-ˆ9B_Ý—zˆu¤ÝÕ-ðÆ1- ‡Žiìag^᮫v&qQrŒ'Hý¿_4(fÈFŠOŒÌ¡Lëÿ±ú4e.M0ÒC.c$JŒªó Ð8¨´ñ¹UWÈ ´‚ïeìÐé2ÓÔ†½ ¾‰£ÐÒN­°„›v–2Hù³Ñ‚­vgvèR#Fow&uÍÝj{-C˜²Ìï õlpý³,m$œ}³„;E}ÿ­"ËaÙ°=ømŒå°,ù^è¨H¸0lù^h®È(˜Ká-2æZà*c¬…ï-héÐ…‘0Ój}²C‡Æö$̓š7¶§ØR¬CcG›®}܃Ib“²'k*Ÿ°#ÆáfŽÍQÛÅ2µQàË’ÿÐ4ØfÌ>¦Z ,™Š!Ülž,ý· d.S°YtÛLÎ^'o|™L1>°´Ã÷/ê mïm—?ô»Ñ‡wØ!M}ܽ¤N¾Áý`ó vcT˜X2êHü·¶–35§ÈìãgäM%Y,ÔÕóƒ£òáÝàÇÕF>’ #Hßñýè=Jð3‹Áqpo³Œ¸©û(JÏÆ·t_~†ç¯rö ÝNÏõ'ÞRÑÁ8¶ýp±ÖàÖYíOü±×ð–&ëÃKÊÁÐ_}<{R¸5}\)Þœ¿wxá ùÁ[ëD8èvà *FÖ’›ˆW`¹E£]Ø &ˆ‡IÏTHüà fg{Î3Äô¤¸žÌàfàìÙxãM_gC±¡pç ¥R _aëä"‰3bÚa8tªˆ˜Š,8SôIXJ,¼<Ö2 S-_†³¹Á¡£2Á´BÁdø¨úçÀòßäÌßYüyö©^ë•“ØpLC†ˆÔãã‘Ô ¹UœÇe0ýɼ‡ˆÚz¯~º‡" îÌq¸ÞGg·>S)Û<Šƒ¦f§Ÿ&·§§æX÷熞"¤ÊÆq‡gÕË.뉔 §›¾§Íï8§û qžÑõûpñªß)Pî½ÊPÐG¼IÙdÐë;uý>ù¨—Hš¨2$¼‹nº€¯¿Á¨{PoåS¦Kk6Ä–¡žXˆG"I1rß²I½Ùñ…ËP[Ÿ ªª†`3ÏñVãÒÓñ šž^Pti¡¯wOz¸…Ãö4ì ì õéÀ ¼ž}­]M´vH±IJÁd<¬3¯åå.´áêÑ‹U:(6ÉÉÆÃ°'Ôh¡’Q!)=5¬I·Šoðž-p1ö›3’,Y\®QÉ«úy\H…:²ÄP=ŽaŽð+Ý¡®‹±ßa•Â<Íæê=ÞÑq.àÙ&n5GÁ‹ŠÊżô;³£àµ‰Ja÷Ú‚4&v4¼Ð©4ÐûY²_™:,Æ^3©4¼è‹Ýc¨©¥«D-JhèjQÊu!Û#K|† SCÎr]Î^)œO;T4dÒšë²ÖPÁ7CÜØ”Š.mWTä»E;J9©ë{Eçóý`™Ò(r]ò:Öºèr÷Já ¾êˆäæºÔ5¬o[!7EÞ^i ^¥ê¹r|øOkLf_i˜G¹ðZ˜Yïér`=­©l}&d(ùfR€m¥?rÊjÝDlµTø¯?[ U‚.˜.aŒ¯…ã­oòöyµ]ìÔ¸'G„)–Ý©žŸê…¥Z ¦ZíµfÁt̹ª³Ð•ÍqFNqîTY,»HØÀÑœ ðfŽkŒå¢—Ê­d¶Y˜…6]B„¢hMx*QmQ@=\ׯ†œïðº©Z·‚Ã}]prw¼ÂáÕ§Þª¯‚As7@mÉ[ÜV?\ܧËÒ`¼í^õ[öQ%FS:Æ…K çuû½Ü;`~xó†ÞÊ8T€ÚjÊhX7ú6]ö=GÔÑ}³ú">7kä¼Û‚ˆÆE§Û-º}¨†¹æ¸ì=£¦ÚÔ•$øI/MÒ.)fvÁû–U×ý4½¢W!~!-Æ]©Õ‡Ê‡ð­8wëz“ÔIŠÿeI7ïMP)uSs¤:Æ'?ÿ¬„ë;üUèu™–C‘ŒA?Á}VfûãviÜfQEqÜ--'•D§$ãr”‹.l'¨Dù¯ÜI‡ÀÚ,£›ÁPÜÚÊÖ$Ž‚«·Æö¥z ¯úˆËº@ßÍ ‹óá•“.^i»&ëŽ0„mœà2.Ìÿ0;lv¨u­Zží÷Šˆ$¸#PƹT]ìt–ðõN·:BY~oe†xRÇßÕ Î’b€yö³r0ÁBɬ»N*ÞìiKÇ(ÊT)P2"*Å&éQ`ónÄ¿Ó<%¢µzÔ¿E›]Ô-LFÎŃű 4 4Ë࢑m鵿Åñ°?«Û‰R˜è ìqH8|À±%«\uâ{YŽg/xt&ðçô2fùþÕÏ+ÖV•áEzÃî¸@1‡NZå¨üF¥ì Kª£e£áb7ÆÿQ([‚ì WŘëùËñÔÇÕ7ô‰lS¿/ô ‘-èi,uûUãÞyçjGÙÆ~Y4 À¥dÜϺ „º¦8¨‡VLœÊٿ춈¦ÓÆt@ì–ÅpI6SßЗB¢çµd3 Vª5ã`X%¡ òõpÒ“sJ^í4L¾ø[(6ŒÍIø×¸×-¦ØÀ.⦮°.ÒÏ5taQÑÈ ‹`í+è'iYLGÄÑ“’’c—ýX\†‚…ïPòe½ >Ê“’«JSÆæOò´’èÉ…Œœã¶Z­ë·oèõDйCwx'¹B×GÙLq•LÛê½d©BDª¼ä‰ŒR¡rðmáj›£K…6‹ê7&¾šx§‘¨£<ôs§!ß¿=)¬¡ >Ä8 ûë.)܈Ï[Š[϶óÚ}î™ rdÆ ¶Ñ¦!$ ³…¼]“ø &Öh5?Yº×Ñ@¡p¡®&WlÜÒˆòð?ÿõþò—¿àùô—íú+^&õ~½û*¸ïЯ!ô]€ýóÝÿú®#?ú¿ÿõä‹°]|÷.ÿœ¯ä˜ŸWëÅ;IÓü^¾ûÇùù¹¼~F:üä[d£}ŠPùú‡þò—´[öqYò}Q†R•âÒýÆ?ÈãQôÀÀ ««ã ÿzGÒMâIØ€¹†nFg_åîgì$~ØÚXÒjfXa‰.C8Þ¿óõÝZ`ðÞòÝ__ú+8º êæ~ÄHÿC8l¦ä›âÜM),àÿtý³¾ ÎÝÏâ æõñþg}ß›»Ÿ•÷ØèOû67w?]É£ƒ¼n=÷Ímî~ü}ý­aÂË‹[ê÷ç5˜ “ö¾¨qå[ÀVFÿ†Û¿Ùb@üÉëºÅƒx-ÎóÓÛ»¿ûrý—ïkÄA€¢ ÃFÂs ­qÙÈw‡\L³ý¾Ù™@üWd“úW$ Éߢ([ø‹¿I‡!÷G+ßÊå¯2ì|kR{#Úï»? õQ©ö-Ò†>zלzÀîÉá"¢H^L—êÐ6ênKªž½@¿ ³$Sá >Iޝ¿û8Y»ÿOñwÝNÝý'ýÃ\:Á, 0Jq#CAÈ~; ñ— J~Ø÷¯;†\¿cPÔ~îvøöÇñÝ`',"± ZÖo²: ãEØôÜa{åÏߣ”Êå‘VÍó*“ÍmT‚ªuÜ!u²}#Íúiêîõ4ºxP¯*Â<ʘÁÝh½勘Œò}3;~”¥‡5ëxÐËÜ,ñqÿÿ“Ö°p-ü7‡šÃX¢p"“¿¢öÿÚWƒ«:Û˜´¡î&þ@õÿbò^æ+”ÿ‘Ãú9‹bsy½<>œü+éjîè¨Bß<&ŸQ°²%‰Ðcï– `Wsé âŸ) (Zax|Ó4´­|Z !äíE Lqœ}Ä»'ÚVRÁ5Ç …öyœÕ°“[kaBC¼8-ÐÀòÓŠŠ`-WEŠ>Ôkä:З&.¯D0“‹]l‹ÊJ.¢2ÒJ6àèŒL @¥áS‹á›†è·[‰Ôõl/Oòt,a`io83$n¹ø±õgõº"T&Á>—ûP›ƒ X„JÓ8¹…¨@K"âªN_[3l×L¤ (]™‡ƒ·å i}+Î}ߊƒ¨87í”[QˆÊ…ÓJ­àQpð÷ˆ8È‹=j4Œ‹¬!NÕ©_¨‰¾iÅET<‘s; QIhcÚð€f‘‰øÏwe}67_ŸN¾ŠM»å[1oÝI0 Ñ,vó—u=“ 0àÑý»‚;wmùe¾’º7|ð]Äë¦fGïþ•Ì>4#4éÅ¿WúŠÍüD÷¥õl¢gë‚–.j0Ðè÷lD÷¨4º?*ZÊX€è¹h^¯ j9<Ü/ïlZ×äÞF7îUÁà讽‚íY£Lä8þ<{ª×ÆÈÑúµ²M;o‚·Ôè¨h'i Õ~o|W¢|1btw=Ò3÷-㣟ÀÝ_ÓØáé÷r8ÌŒ‰ ^<²ì7¤Ö_Ÿ­3—Ú•˃­1è¶Y‡èî½ƨÑ-|‹¢¸yÒ§»ŠB±Xæ/ÓðIpåì³€ª*µ×#Åg‡Ê* ™YKF¢§Úÿ{ëƒbŒ'áõ1 ­™aÞ¾6œÄg×âœàm)ÂDc;òEÙ‹öªB®nO¥%/bPë<é øIúպ،Ñýw‹}EÆø<¢2¨¸†Ïî=ŒwjÓÃëí‹¢¥)Ÿzô\¡V§ó¢6]yI7zÀo´8éIüºþ|\K_惡·®ÙG–Rðžé´)ZÉ(D7ã•ÂrΪ =y¯ðù®Ft'%Õë¯+Š!2u öpÝM§ßŽÒ…±€ÃlWÛå­Ã ÑEø]¢áÇH‰ÿz\∲¯¾?¯ä‹Á%9‹~Û iôÄ/wW™dÕ=¯.hw#7}‘’™»×CÙ L!ŒËrˆŠ¹ ÓíU’¡…DÀ<“¯ÍÝ•KQâÜ=Q210ª´Död§S¢ƒVå’LšËÅi·$û pŒ/pIn{€/O;ö8’ÀᄟvQì[Ý‹ ùƒ(·5ª t9‘‰F&”¤˜v'ƒAéÎiPΞõAã'„DŽåG5O‰‹¹"ѸŒ¹Å'xTõ|וë{eág„\»ž9|P$p ’Ö‘¢ƒR½yî²e^ÕÐ вtá<+†“ª—BY#k<¹òŠ¿âŽå,çÆÜ°lÏ¢—#Ôu»• H‘Þq‰i¯¤,(8ØKQIq)(ˆon?f.•6l ´L/rïLPŸuNqûBa ¬Ê«ù|t˜/Ü/PiÓ$U‚°·[¨®h eY&)R7#Š÷H‡ŽúyWj&&ý!2EŠÒ¡ÏC³ÞOÁ=˜úO&`ûü‹K‘ÑÁÀ PØ`’Œ:cÉÄ7_M—Dè¿°æN¥¨Â‰b°P$¥”fG‘øªtr#ëÌ#q°AªïMOÒÓ0:¾²°î©Êš»P@” êîM d·ÞÏ«E«Ž„ ÐÏ&pvÒA™•®x˜fŸafŒQÒH_Â*ÉJéÎ'u PÔ¯—4+0Yͤ¥‡j'¸„ §ÃõîÀïwŸñsÞó ¶$R‚å| <+–¿‚3t‡>©¼¦ŸMz(ÓŠÒü Š5àœu°˜©+“"—¤ð†3EU^†R´¸@L%H¨%ü@b±”^”ò £|÷IëÍÐ`BvpŽÆ. U8xZCº_~â:x¡½ ­{<üwB¿Q ®/ÔPú|Ä)ˆïp½I`òiü%C[Ô€€æÀ Rʾ‹!fÚª+‰2P•BEj¯Þ®„sÙL§óÙ—=bu>" ”Â|gP€8r ‹Ýi>=žŸ(Ð &•³IÅKYç§êƒ@ó¬¢ÅÇ3Ú˜Ò™„Õ÷8®‡ÛÕgxB(®…‡A("®w£€Æ|¨ÖÍwôÅZIJÉn‚çÁ5¡³ èjk‡”.¤×t‡”h«T*UØLp ®› ]‡=_IßU—SЯXXIßú Å?:25ªêeÏWÒw~cލÀö·Á¥LAÃèÓ8~žÁQ¯Ÿ,©…/"E(|åßM“‚!R£ b*RÒ„Oãd(´¶2)éñ£Ïâdˆ5î-{ƒ‡ bc;ƒŽ¡ø:Ã(éG Vˆµ¾ˆáà³£DêécLu ˘Emð`3p}`ÌÐIXúaaY ¾96Ñ ËÁ½Þ˜„eÀnR Ú~li‡Åö°¡ßMÄ×,  Ý K9,@W5"–r \¤-åà(p&,í°8zV.ÌTS/¬Bœñø5cq4ŽÅ$œLBÁÐÔ“p2*’áÖ8¢¨HJ÷YHBÁøö#Û×¢`|ûá9´)Ðük&¾ád’eøÊ-9$Û,p› lÔ€™„³©OÃ2`&áh2 ü£ Ÿ¥1 Ë€5mRà<àÝÍ¢`0ΣDÏÅéÀoH·6yàLiª‡“aÀ”áË­ïæ7Ë‚Aec߬Ïü©œj/mf_Øg«´øja’°Ž8b¡,.¬3¾úf’°ÎøÑÜëŒ-“RœµTçãÛiصxIµHXR?«EÂðÒ9—-;£Öݬ L#µê‰ìQoåѲV`Q0|Jx©±)Ðï'¢ L ôû ·µAÀ‡5A…ÂXZÅ’ÛÆ "ClÌ,Mº~'8 Ì6F­êDPžÒ8oP¹0¡øöŒÕDœ³Í5 ó`ÎhûáØH-6¸®x‘²*Ï­–•« $£«3 ßEì:ׂ5®+eaW ‹®1@e+ÕLé >y&#¯4,V¸îØ>µø¶æ\ìÑ ô„T>] #;‡ÍÅ0&‚' NÃ²ß ®?ö»Õñ(%3õiüìf_×õêY ÔG4s‚Bl k-øé?YÅï¯Ù:o±ÀüçzõtFw¶šüÈ !ú ‡¬¶Ý²íÒ#a½]þƒ±"1,j<!M$×]‹Œ‘‘„X„RÂo•€»ú4Ec/üÆæ^ñËôáYjñrþ….áÙºì q7þj “x_Ùèáe¯„ÿüSRo§Ò«}–¨ÝÞöt DyðêâáB¡·´Ê«?“Ý $o‹LP"ÆíÙíh0FÐÒÕ& xJŸ‰±žHµ18œ¯Euþ˜ÍwO+") –óýØ"Á‘{c$Û§ >¯õ¹ç/gæC$¿ÁÆq'}OÔïZÚñúа`-„·w8º È3uK‰}÷ºBJ¥lPÛÕ÷Ó'‚7žÂCþ–+¶"܇ƒT±$$ü­$‰ðVá-—P—ø…¡Qß[¨3Ðza ½HÞjlìãêµF˜ªLQåÀ_>$á-WàÕGké}¢Oß¿­:Ƚc~‹“«Å:΋TOú¤©_3¨ -Sè)ÚHXr;òß Æyóïn9¸“ú—·D ^œ5È–Fê_àZ1xqŠÌ ƒîsl«üÛ—MÃàăŠa8¥(mŒ“ЂˆÁ‹S‹Ý}¢¹Ô?†µ"cðãn„¡îìt›œ–hAÄàÅÙDÜëfª³ü Y+2œÿPfZ0{¥nZˆÍ~±48is®õ‘Ÿ&ÿbfÌÇQ1¸q–’A%FèÑöog-ˆp^†á—6æ®AÍö“¢kã“;íš¿Ô,=õù™6öh™úÍD’>SŸ>M³™”y‘SŸ«Ù‚L—“iy¢>ö8™–GêcŸ“iy¤>8™–Gj³Ûp)ny¦„=U£–§Jê·ê¦¬Ï"IŒÓ~®¥5ZR³xì—(AÇõ;Z°ògëg”ª˜­á[¡Dü[ê]¨DÚ=¦¨™$:zZ-V\«ûFcþ‚rCÇì 7õ¯"m¨Pmì#¤žŠ¶¼â¡8ÑkPîfòè˜l¶èwÚzû„'&6þÝå.Æ×tðîE‰ø£ EE^^˜×:õ¾÷Q‚\ ¿;kìkc¨Tèr¢"%¿noد³¹zí`@èù‰¹Š qzë?ÙÂþh3< t“‚2Ч¢6ñ6'!€ò–§Õ~MåÞ§ƒ26ö'¾>”Qø“^+|2(ÇKñt}+}6(£püDOœOå¤àÆâ§Ö?'08i†.Cñ7/¨Ðq'ä(ãtX}‘çZÁ§ëSF©NÁp   ŸÅƒ4“§w€³hñ®ÿgóð+Bä¢ëø)Õ–§¾u}ô<£a\›»>öQ@yIváèïÙÓÃîó|ÇžÌPÿÖÚu²—4x°+F$c7ø…O«šÅõtÃÍé>‡d…Kàªf¢î¿«‰¯ê y˜õ«A¤“­pã×ð¾B*^˜¨!Õõñ±*KW¢šiÏn¸ík|<Ëw•=su}.\Îï Ê¥Öp ¯ŽÔ/Ôõå„„p¬8Þ ÔyøT?K‡N};‡ÞYÑC,ÿ½â” scÏwŸ¨»‹†"”ÈrÑbS`\Û„ì½EmT“ |‹•!«Cï¥óZo¸ýÕ î JÄ0ÇøkA7ø()¹Ì° ÷!]£¬Ø†oDàþq~žAˆ—ô …ëLKZ4Ü\ªÀº=3øBùdS9„‹ eËxHïJyLiÆD˵ڬ¾ñsŽ^?6­v”ü ‡rut]XXr|7÷ÎNæT×{ô}@ÄÃqnœ“pa¢ô>¹†vÓ§¥”@×õºù˜kuE*¥´ü§[cë°Û¤Ðæa÷ÕPõá.fjùéò1Qªd®Ûú3:Ù±éù¸&‹P+½[®H{ài¹À?刚†Œ­ÀQÖ–IA ôÜb‚ç{ùú„+™Þ2$ÀÓùƒâ'8ÌÌž˜me¥S·§3º0M§þwÂKÏ?ß2¹RßÞäw‹úorÑÀ3›”`…F¡t¼ aÑÁù8¨±ÝC–¦ì»IɈ;ì%^m:ôjÚC«õ6ìÔŸXC„ öÐ=½ ¡ÃG¦Ïzp޵¤bm˜wáXËsøØ£ÛîÕk *;¸³·›×pÏiÏGƒ˜ÒsøÈê"£ª¶¿ƒÛóZöØ»E1m¦u<Õôt…kp†Â!w§ÏΛ³t¸“'¼ù ÑS¨‹Ã.³=Ÿ >²hžŽ^¸W[d WE/„­Xd®¦ÉÄ1𴣯¼ô=Ÿ–4Âs¿â®Ò‚JáØë°!nüQtÍcz¾ìàhˆÜÇ(Þ}=§óóªïùÒ óXå»8y2èô°G`öYï½Þ>ºÆ®Bµ`É«!:,EgæK…ÖDª‰(‘br®p9£dZM-˜æx&¿§õça‹7íªÆõîP£?ááoT9‡ •’Ðcâ‹–$nV'ÇÝÿvúf}?„|It:¾äõa»Cˆ8{¸èùBfVÛáh^óQVV.ÿˆ­ˆ¯fÆ ™ÓÓžžh_Ö¬)Ê‘7+ؼ̤Ç^é JÄHZìùit>‹ò²^ÖÔÝÜóáæ4a­¥=§~"KoÔ²)Õ<ŽÒ€®#îùm÷8Ú+ƒ¾â”xd!;V"dÏ×M£Ë»ä™Œ=_7’°ráÁ6§bF_:Íà ‰§ÙŠZ ¾‚šMçÛŠ ‹4Ž‘oÙâ6YthÅbÓqy}Lü«ðÅ'Ìø¼>JÄÖ-8A‹{íU¶n±{x)¶w]b¯£=_åŽî²éf4%ÛpãÃW»³(YI†=Ÿc‘1S{>9†ÒqÎ\3{¾ç+àQJm2ÑËÆÜ-3[ÝlZ1nÝ0Àm"fÆ_ß'ËÐuiRöÈyêwü-ŽiˆãËy¹d-nҾϛ¡Ì÷ˆLaŸÇ¾´ä2”••>Ø÷¹3”;ÿ¯î’CÈÌî¬Ý§Ýaw|Iºl]ÃR#1ßÐØš~¸:ªðݧúëŽé¸~¸5jõr†—+:… ìÊ*·_y)sÛ©Â/›Ù6eø~xÖ&±\9ÉMÃCöK|3´Ci„ï¨Bãyy<0PßSyø¸=Ÿ^pý ,„¯§ÂBC‚]¾ú¾Œ˜ÉîóœLø|*¬¬ëùù+j?±Pʾ¯&¦²‚gž#u:öC&…¶­Æùò…ÄôáéÁiÚÐèCº“ÁîV–rÀáÁâÖá|áÃwP‡ó½çJÌSµÂ"Ô¥ƒéÆ–.DE0x*ƒÁìXÆm?ÄC0T-ÂGN_~ðÛùdøõ™jT_*L|ìßú ß~øötÙ÷…ÂFѶ„ôþÜ÷¾Ôá¸hÖÌÍ×÷õ½T'Ô‹¡"̯ÀnZøâ^:Ø‚ãþ OeƒŸãU€¾´—Ϊ³Ð51AšŸ·ÌóÖñ@Ý¥*,ãóO´b~?ãø3ÄõS¶ µ¤'¨˜ºŠ;S%0ô‘׿ix«GHÕ\Þ;˜„œ'BåÀãú!ßI§Ðî©¿žt:Kä×û•©?Dˆ´ˆ¬ê‡l'BÅ|•GŸ^·¹: óÙºÚI": ì/zO³íE¤°AâT/—5Z%S) &Ÿ¸—5b¡$%<ì—U}ž"ÔPœ=tr-¾ñ ¹ùËìÀJiB‰¢V¼ÍwpORÎZ(ƒ†3$±šmññoȵ©„3µP ûÝœU7ŒZ(hâÓB}Z£&ÀþHÝO˜}ã!%¸pØúàøbÌM—Mc䈤 ¾&!{Êâñëvþ‚ö¨®™Æ-ÀɽÊqW÷`Ü–@™jü :¯o5¿ûøv磙o÷þaÉ£‘NÈ=5=ï¾L¸EÇåͯf¼”Á Äí<}<N»#-Ü=a÷%|%éw?ÄÊT65ê„(w“ »ÐGˆP·èXåH!ºÜ ³Ÿ¢Ò½c^ë´‚ž?¨ŸÅt}ï6H?ÒƒœmP9Î͘ AÕ™6+"¢ JŸíƒš-BmNGI¶HY‚‰-2æ–µ’¡Ï-;ó=¤G¹¥·i¼èÉŽ"Ôõ'Ôt`þ²,TO2(œܤÊPKE¾_1. >¼‘Ï ˜l„GÀü±Rßñ+´;®ó¦³ðf—ãÉü~=¿œÓlè, Ê˪»áqÕÙ±S˜…×§|ü¸çðhÎägáÕI#°^,Ü¥‘…×&•Âî9áxÛZÃ#’ÊBcޤºØìôM; ž·ü±v^(aUË‚ÛP0¢„³Ì›Ý„‚‘›_¡`/dð´F®,xÙ£ W†…N-è»üJ›˜eþµ‰ð€\~kÙÁÎ>FæóŒ vðõ -¸ðž>Fƒ×ñÊB Ÿ¢û ð?Ï>Á+™žGqr3ÏrŠ÷0*È6zªç¸Q3& •{(¡ÏTå…‚=ŒÂËŒÆNf¡ )#‡IHc™ yúNï`5¯‹¼âÂLéx×?> ÷tnÛ:0>ýuÜÁçýŽ—U]×;ö”¯mà—¡*5ÎÞ¸ƒ‡#BdI…Þ'›Ž;ÇKÓ5#›ÙÇzz ¥ 2Ÿ':FóÆÍþÀo¸™ÏK× ês•e>9s,m¯ï–æ¦úÉ3jrQsÁgWŽ“Ç0®:,z3óÖ÷8A"8ã5BX=–ѨߓˆÁñd$ñ¤*¢FÌwÿòß½ýíÍ?Ï÷ûx؃ƒAËFa³® LÇÁ®¤EÂ뎅…ĬS0”iìƒï´/!÷ãªJÅN»¬Òóz?Û¯:êŽc¡úf "Õ=vH8TT¤ú°ãð ¨Èž¦G®WÙ§H(9 H€*2£HhN©f@¸yÂmª"GtL˜j2éP$\¡*’Ë *’ËœnEnõøz·B0ÄâÈOjζà$*>Š{ZªÖá´sò´TS9N“»…~ór8Mv–/ª7Ïá´ý6ÆÓöðåI5gÝx¢hc;¸Ú¹æ VER©ËUERÍ#/Ó*’j :’j©JªŽI5<6Ç‘{º'ªÅ­WOÆžhçQ|O´ó(Hº'òÞçv¯>-‰äÉ{‰‚ûÂg9RyÝá³”uL:K¹çÄ‘z‰ÌR.$ Žê¹CDqÄÚwãi»±Ù¯ùªJÑŸøˆ@RÙ‘^*’¯ªöÍnéy–2Ÿê˜ôN$µ= í,­³,ù&ñ1ÿ¤„4Kˆãޝr#W‘t?$¡$Š<Õë.Nó@JðçÂ9¡/÷Üžà€« o”Ú­"ïzÒe¨èŒ«qÍ~Uôºr÷ª¤õøöô½«2ÊàRv¸è)Bãðr±:IGMHR 2iUuÓqÏA÷AéîûÙt3›Ã󉈔't‚üH‚ ÌD¨ 4È-\ÏŸŸP9C³ªÊt"ãöª®üÞé–e¢žÎ‡úïÒ³ûtÔ§á(”1 ?½};Ýã%¾-m  ×@dx€ ØÀÃÐEáŠkìÝ•Pmô0†~7ÃËÛa;=í¦’(Ÿw8Ô¦óõ•ÉNºYŒc÷‡Ùì$QEx2šþ²žqβ|Ò…r‚פìIu¹aÚ3ËM-Íc൙-Nõx´´íò!üeB¦ äAhÝñ䊄ÀN¿[8¡¢dúžŒ4¸y óPkŒ±T:qÀFÃ.n&ã4D.¬ü¶z'QËú,úe™ cIÕϪÔ]jrx¤†ýå×7RíÞ€ŽÔ:—zÅèöPrò:v.Ô£'¾¯\ÊQ¿Â½0Øh•‰wÅÝuAÿòë÷yéxCÇ_ÔœœJá¹¹·»b·˜ÑÅL“Ò&ónlÐ B¦„Úˆ |ìaNJ­°äqg£'…¢\ÊpQCèß.5ðrõ¥V-J–aTY¹w‰ƒ >˜8h7Œú•:R8Æl¾e_¯g¨)£ZìnàŒbÕ rà‘–öÜ¢sôM*sûu{Rüܰ zZmøî–•Eúב$ÿ˸À:¼Ûß=X;D€Áw0´[» gœ‹ Kx$Y§bìUÐrŒèŒ‹qÊFwE ê>c/™±ñç{5òÃÍ»§Žþ%BøD†âHº¶˜¦CöäÞüjm@×Êë •¾a•(î‘ìƒRŽüçp€0Î[ܶ>q ’K•Ì2Ф³ÄÂêHªä*¥ŽI5‚\¢T$Õc¯3ãó¤{2ö:3ޤ'eÎXtméI‡3EÒ“’‡1ñ¢{' û=—„<ŒERIÈùŽ"©$äá\G‘Tòp®£H* EX!·+tœ«ïc¢IŠ0K„kÞáúÛ!júuqq©&ã ïÞhT=¹{|^UH<ú€P`¹Îi~ºfÞáDüŽ9ü…#ð+<ðòV5ýà w È~š'ƒÒê¯(8àôÝ‘œï›U£ÒÍú£¬HºIU"VN̉¸B½ѽ»œÎ¸Ý®P*QŸ î“ei§‹w¸2ÑÀ3I®h̶Ûo•ʼnà*(D†’!ø@¤þ‚ÊhXX¾*iÕ-ÒRÈ”‰<‹1¼Ã‹_¼ýˆÁÛãêôUgTÊ2•}—°¶*áÕ™îì!°ìæÜºé`RJˆã0ö'£.Þ­N’¥«í‹P¨Æ ºè“£ðÃì€fÇ«9 蔩§3îÂÍ㤕 ¡Lv˜VHœ»"ÞPJ©ÔA¦ƒHf–^j6º’dXŠ–å”(hüó€^ú'^ƒz.: Ñ+ ÿ¹Ø–Yxí›]Œ#W•ÇowfÂLùØ$L>” fˆØ„ÀŒ¿?6 M¹ªÜmÒívl÷Ì$ûàxºkz̸í–íîô€@^¼í+$Ä*Ò –}à‰Vì[„Љ‡<° H¼ÁŠ «Õ*û?·Ê®ªn»Ê™ÌŠÉê_£š²Ë÷œ{îïžsîGU·{ûínk§ÛÛƒ›ç·öö–;½åF°å —?yáSK§q¤ÒvºdrÉtªN$³‰D!UÈZÅå Ÿ\Þmkëú£ à)0§(¨u¶Fû'Fƒ¡5d³Æ {ÑÖõyÓ•Ï%§Éú;ƒöîn§·£Åö´ä¦h8לÓ¾h%Å„§dŒF{w¯kG1åªÈOkMckÐÙÅØqS2ìï÷¶cä]ȦÐòåN7„ëÙBiš{ÎÖh°¿c‡çÅi ú­h·*']Š ;lB§×ª ÚíhŠå¼vªl¶”J—÷{[£N¿iy¹ -Ï`x ¦ö¤ÒVcUs"›C ÿÌr)tùb![²$"kíÎÀê GƒÎÕýh 嬙¶—KÙD:2V¶¬£ºÙ¾Ú€fØ©|‚éT¢”‚÷ä¬\ÉÎHå+ƒöÞõÎV„ó‹l>íÊfÒÓd[íî¨3Úߎ1 ïf(Ùêw‘Æfã×vd#Uì œˆœ¨ "lèì¶wâZ‘Ô€,à Þ¶1pÚqP½™Ác·¿?Œ³¥iËÀÙê"R‚‡Ž2Ü\kG…£ÖQŠÔ1r#"R+@DF¨èƱDŠ×ÊÓ´Öކ1ùUì( >EK63M 2´ãDäh(˜(é\2…Q²ÍN¤[›2¶¤sét iÅ— æ„a«ÝÛF†`‰FaÊ(£•!AÌPcÄ)¬1CÖú;ÈQ­ºƒ(#3%H˜E‰4h±BfÌ--±é2æ.~#t–Û¸VwÚݘ&ˆW‹8íq{»3êG§³(þ˜Kg’ÈØ¾¸7s"Íký`•ŠÅ”dË…rù6o[©¤Nöf¿ÛÅ |-„…ÓqŠàÛ¢HÆ_‘ÝÙ‰rF± ·Ò‚! *½mçp6>-Ò‚ˆ&¿Æêæz*Fž#r)ß&M®9ƒÝ}5¸êjá2"žÆôÄo\²¢kM'“H§ó!1ãÚ5¤âæ Ý^ë"&$Rsa+*૚5bxµAk°?EÍ´ŒO¢GÙo¯§Ñ0k1Áð"ÌÔt s…€˜’AŠ";Ô‡ó4$•7áôÉt!“(gÐÓ,aÎX;l¿:ê÷£2²Ö€ÖPÿ1 «ëë³1hi°Hg1Ã;&ýB·=­ :C›Ö9øÅ1ëV#ÆD–žfÁ\.-6ØAÑ’ÇxàÛ` Ä„–FŠ4΀´Ù9;ýA'ʵ4¢QK‡Z`šÑí¶½ž/ZÓëœo Òõ{`!ýøm7MC«0ûƒƒŽŒÌ Zç 6"" ¦ÛÆ t­³¥5ÄLµÏlÄx@M¿w­³³?˜Ç툇°¦ͳ¬=b¡80ƒõ¶æÎUÒ²v äöc Ù•µ°ö‰d"…‰¼OAfm,cZ¢=²¡–XÍË1bÚ ’‰4Ó@•ÍËÚ šãC¹¬} ™©²¯ÃÏ«ëmÌŒ"5ÝtíI¬ÃB:·:îØ1 kq¯û³¡Öc½±g¼î/…RÄX¾ÖïÞìõw;Që\ Ñs3äc-Íý«ÑCz>ãy‚rB‘õ[ Ýz=Ú'²žOX¡ i‰Ú–†d=oÏÎâuÝ!• uC`z®Ý"fÉ« p]"•†ƒöõ¹Ç¬ë)ì!Sr «þ¨};Y0,1°âÜÅdÖ2²êºû:z2bÏBËJÝÅÎpXvØŒ"ÖíZVœ²ìöë ÏQeÿižÕ£Ö'n)ú$úÌ¡¸Uä„QK‹SBº²sTìàáaOdhм-î(ò¡Ú½¨–¹æ\ý©5‰Wx—ߎ•ö>–íÞzç0æ ˜# °€ŠJÔtJ×ìzòlH¬§wŒF7çoëÉBÓoÁZ¿·ƒg†èÑyö ´=®‡$e‡Ä×3ž¼Ï¯ÆuŒ$r~@Mô®Hβs²(-ÚFV¢Ó63©’!áN¨$ÏDO§´ÌOECUû\âÚãlv¦ÓZ0QÕZ Ó´À–˜£Š‚L¨!¾Ò˜Aÿ*¶šbô`5"z èßoöPjDìmH3dM*Ò2Y÷¥]œž§,Bµ §{ë­k×F­ÙŒ™7ÒÈî–mœÆ°‹%ýÖL#<¢Çûd7c¦ éb>•È'3)yBŒÌŽ.4 zZkÛ+³Ý]ÄR-–’‰“/æö{´p>iâ5 L6oç,´¹˜MçÓ:…¯÷:{ØD³Ri‹¹Ÿ—í®´‘NgMíeýÁÞ~„wdM<Å·“™|É4è& âÝÅv½ÖìD­¨³Å²]†Å…´afÑ`¼qU,¤RˆÎnhou3ÉŒ‘ÅSólFÖ¡"†ÍgëzãfotÝŠWë 7^@ÅhÌÍ¥q¶>ÔÒp[-ªû†A$Ú@µ½ý]lÅD8®q QØÝ»Þï9»NÛbjFWiñÉx¡l{«‹½‡ˆ8Õ•»}¥çÍ>®¡3ê:½ÑõÓS.윬´Òý^'bSYªM¹¸r²÷ÜsÚ7ZÝÎÕèã‰n±žWNºx(ÑÒÚ½:èwÛ1ò^›³ˆ¹@å"¿ÝÅ »Þ™Ë…œ[W®C5ºj<àЦ#HU­n»·³× c€ã‡+2}$ï­ÀGcú/šhay‘Öo·~ƒ6®Z¯Ñ’|ÉWÛNäkEeÛD_%3V)U.Ê쳘ÂòFœ¼9\é­;»ý¨÷Òµ<Œ¶Jéœì6úòÎP\Ez«%‰!Â|­.:liøÄ†€ŽùÍ1usÒ¹2PLU%qc^ûsò ™AN3ç =ÀŽa\«Lø‚¨Áx7C¼aK6—Kä iYc žòfZºÇÛŠœ@:S„ åÆMƒ/­×Iñ»· £ˆ±6™Í Y¼Ôˆg©¤»‡-ÓÀñ[1#Qbf´’\Kg_É¥þV»‹7º¶Fƒ÷³ÏËŸ@ ö{½îMlúZÎ^·s×éä-Ð=¼È%o/öv–?»œ¢_z~IFõÞör­tí”?¤(íwºÛµëí¡³7ZF£e×ëuÉnøÒ—zµe”66›­õJ£Q©®´jõæFó¥š=½p¥ZiVŒµÊËv½UÝ ×Ö^j•ê†ù‚Ý´-TPÝpõ¯æFã ©­m¼´nW›­¦Q_±›(’LœÏ¸…Ö õ ¹·ÛÞêñKÖýå*±ZãFŸ“V/r­\æœ[@lƒÍòš±"Æžs@?q¯½ëà^¸ äý3þn½–²½^üïÿ¬×Ö./5Z [ZÒÚl[Íhꎃ·ÑïXsò[ÊJµU±®Ò|Išg9N·¿ç –+Ö²±‡¿Cq߉ú»åZ{¿»\êcº²Ûöè˜ÕreeÓõ€Vi³²fµ¬J]ô<ýÌä볞~&TòYO\\ËXkV.Ùf˾Ҵ« q$H–æªQoU­MüºRµ-}ãh™ÖšQ]Ù4VР¦QµŒºøÈV±èv¢¨±«FiÍn™µª2íšöY yj P½Ù¬ýyÅ®Úh« w+m®¬ˆ_4^Z/m¬µ¹R]ÃB¢nÃÕ+—DFX¯U¹CÖ+/ëj­Ù—ì5”úf×ê¶¹±^«Àt|,W®´VmòqÒÑßÎaåŠ w¤ª£6N‘©Ú—Å3ŽzÁ”’1ÒM§µJ^¥£Ø¶àqQv×íæ&±dÝ©õ›«¶ùB«q¹ÒDA5mɧÓ5–76ë: Sêe‰;]øäÕŠ…üÒºT©77µÄœ32(`5¸q‡ÔnÕæªÝ˜1ªÀÏ&VX6bÓln$­±f[hMÅ<eú·Æªam\žú‹äR‰VØ1•° w)›ÆÚZCÜÙ¡Ú,O-½‰g< bŒÚlnLï‹Íê ÕËU¨2VÖYe|÷žQŸ.³f”t:Ö›Uý;Zg¬cpÇûÂ+„qus:ƒIzErP‰›ÙÆ£Øx»0‘.¬bÍŠáçBK³=¸Ú﹉²‚ä©I$J¨ÜmwzÜ,Œøç1ˆ GG‹M™Ã›COäuÈFÀõ)"KóH˜Í5Ù€_"NƳˆgdöpúô¹O[X€»Mùlòœûç¶rVËŽÄðúäÞÓÏU<ëÝw§§§Ñ–R¥j!ÁyÂV .Þª¢¿p¿&Vè6©n¿Üj˜õJ Ó%7Ôû˜Ò~ܬA'žÝÖmwŽçÁwD½ik‘iyyö4«a‹×`”Q¨[ÆÎ¥¿#‡"{¬­¡Ïä@ ø\ÝóŽzÆ8óÏžÄ-ïímÍšÈMºà2Þ\p®M@úòðzû!ÂñÓ=oÖ?mºœËgý¡iã\4Xp2éÇÎßñI¿^0,o_û^'_ƧÈʯÖ|Kås:ÎMY«\w¾^„~¢/\TîtvÎEˆve×;3ÇQHkex©3ìàL¡=©kžVª:ÏôÚš6½ŽãSÅVßÓlvœ1¤bîN‚šsÞÿ@éæé÷ j☡8ænâáƒ~´qU;Îg—½îNOs¿±{õÝŸ¼ðüÒ—–       »‘À…Kýîþ®3¼ ÷¯lõ·“h“Ï® r¯æ»¸NÚsѽ9ûÿ§ñÓ¢z@íéÚ$&Î#Œc]îöá¿®>½øæ­ŸwÜó­ß©½aüú&µÏ®Öû%¡kÿȤ\T »ñêGëC‡ÑzQ”N,‰VÉ:át³Î¢z/6‰ìÃÙ÷“D—ì°Žíüö)!^2.×wçtùûÑÃWÑ—zt¨v‘‰Îã7£'ÑöèÏ^ìÝt¥oB‡ö.Øõ•ïÉ}kîÿ¾óu¯è®’ûäzwŸ€g‘¢Ø¨t€ÏcGüÿðùþ=gpý0N¹ÞÇl>Bì£ÚP{”?¦=~„Ï܆¼ÿ¹7õKÆ6®â”ëÝq< 3ÎzÙSò¤;Ç8¯ýéPçT¹ëÓyâŽÓ¹¯¶î¡ø®?Ä)×»ãL%ýuB›sóɨ8“ÒJÇG¥H<#öS‘x" áæÎÙ='埜”Ÿ6›“OJÌ;¿ ¸óþpæõ3göÎΜ]úÝÒ–¾ºÔ<;uöÞ?Ÿ|ëäN¾~ò3'Õ‰ƒ{Þ¹çõÅ« uõcõ ýçm¡F                                                                                                                                                              ÷Bàp­ú¹ÃK™‡Ô3 ®Øøª^s¿ãòü3_<¥•ºüâM÷ÿÿCàÝTê{J}úc?øç{Ž´êúû_þÞ»‰þÿ–ó?‹‹{àÃ?þç=÷ʇ½ï*õOsã_¯¾âßÿãe$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$@$ð °úœ:ñšZV«åÆç”:ýÆ›·þ²ðæ­·~«pàú6.÷â<©Ôƒ¸œ9Pj÷N¿¡ðUN¥>ªÔ)ùQ÷Žû9ôÿ—}ë»ÿÉ…îM)®EÆZfÊ…”Ìú²ð jÆ©ÔYœ_ó®òýö޾…oB‰è½ý#¤O}ŠÞŸ¾Û·ä˜äœý‚ý Ýü7îâþ7âÝí“çð}Aݯjj Úø7RWÔ–ê«må(KuÔPÝðb\²Â¢dÉãŒ1Öv[W­’÷hé8+.¢Ô¢zJW«ª¬ê9µ¬­î¨m·ƒïbñ–o¡}|º©ïI«Úê>´cœµöÚ!mѧ¶`üߢ¹‹“ USñ/âØ^T§`ÙçQë>êí¡¾.î-zROŽ™¯m(õš|Ô]™'©Eäó)œ o¸Wù~Ÿ‚ ‹êác«ÒÉý>-ªL¾GŰ¯~´>äq˜­EéÄ’Øh•¬óN7ë¼7›Döá€ìûÉF¢ 'vHþ{‚”/[×wçtùûÑÃWÑ—zt¨v‘‰Îã7£'ÑöèÏ^ìÝt¥oB‡ö.Øõ•ïÉ}kîÿ¾óu¯è®’ûäzwŸ€g‘¢Ø¨t€ÏcGüÿðùþ=gpý0N¹ÞÇl>Bì£ÚP{”?¦=~„Ï܆¼ÿ¹7õKÆ6®â”ëÝq< 3ÎzÙSò¤;Ç8¯ýéPçT¹ëÓyâŽÓ¹¯¶î¡ø®?Ä)×»ãL%ýuB›sóɨ8“ÒJÇG¥H<#öS‘x" áæÎÙ='埜”Ÿ6›“OJÌ;¿ ¸óþpæõ3göÎΜ]úÝÒ–¾ºÔ<;uöÞ?Ÿ|ëäN¾~ò3'Õ‰ƒ{Þ¹çõÅ« uõcõ dfïÀÔNæ•2ÓSæ™úóƒjQ²¸|—ÙéÂ+JýWÉ~èã§hëi< ÌGàwÔ;ØÇ¿ÿÝáÁÌW•zñ¿ÿ½ç>Xòå/¿xS?¶ÑwPì[ÿðö€Wšh" ¼g«Ï©¯©©ÕrãsJ~ãÍ[YxóÖ[¿U8p}—{qžPêA\Î(µ€{§ßP ø*§RUê”ü(‡{ÇýúÿË¿¾õÝÿä ÷¦×"c-3åBJf}Yx5ãTê,ίyWù~{GHßÂ7¡DôÞþÒ§¾ EïOßí[BI                                                                                                  ¸+ü/µÚçâxíÐ1 õOímˆ@aÀ€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ ø<xíÐàùSä…PaÀ€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`À€ 0`ÀÀËÀxíС À7$H4£±ÿ  î^´â+šKRÆ%Yém¯Ôärþ½>˜ @€ @€À«À‚m8xxóÐf`i`Pdðp öb`à\xúâwÆÓo=f ýH±1 ƒâ\ÌÀÀÞRÇÀä‚0ƒH "6 Ywïâ<åÝúÙAr°˜)8õ¡‚‹Ã˜´Ù$+ÄÍPÄ' ˜ÇØ 4d.ùlžH?Èœ™PÄpÏШ resource-fork blkx Attributes 0x0050 CFName Driver Descriptor Map (DDM : 0) Data bWlzaAAAAAEAAAAAAAAAAAAAAAAAAAABAAAAAAAAAAAA AAII/////wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAIAAAAg//56eP9/AADw7L9f/38AAAAAAAAAAAAAgOy/ X/9/AAAoAAAAAAAAAAAAAAAAAAAAAKAFAAEAAAAgAAAA AAAAAOD3v1//fwAAsOy/X/9/AACKuXWJ/38AAODsv1// fwAAKAAAAAAAAAAAAAAAAAAAAIjwgwABAAAAwOy/X/9/ AAAAAAACgAAABQAAAAAAAAAAAAAAAAAAAAAAAAABAAAA AAAAAAAAAAAAAAAAFv////8AAAAAAAAAAAAAAAEAAAAA AAAAAAAAAAAAAAAWAAAAAAAAAAA= ID -1 Name Driver Descriptor Map (DDM : 0) Attributes 0x0050 CFName Apple (Apple_partition_map : 1) Data bWlzaAAAAAEAAAAAAAAAAQAAAAAAAAA/AAAAAAAAAAAA AAIIAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAIAAAAgeDHek/9/AADw7L9f/38AAAAAAAAAAAAAgOy/ X/9/AAAoAAAAAAAAAAAAAAAAAAAAAKAFAAEAAAAgAAAA AAAAAOD3v1//fwAAsOy/X/9/AACKuXWJ/38AAODsv1// fwAAKAAAAAAAAAAAAAAAAAAAAIjwgwABAAAAwOy/X/9/ AAAAAAACgAAABQAAAAAAAAAAAAAAAAAAAAAAAAA/AAAA AAAAABYAAAAAAAABHf////8AAAAAAAAAAAAAAD8AAAAA AAAAAAAAAAAAAAEzAAAAAAAAAAA= ID 0 Name Apple (Apple_partition_map : 1) Attributes 0x0050 CFName disk image (Apple_HFS : 2) Data bWlzaAAAAAEAAAAAAAAAQAAAAAAAAE0YAAAAAAAAAAAA AAIIAAAAAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAIAAAAgFovlP/9/AADw7L9f/38AAAAAAAAAAAAAgOy/ X/9/AAAoAAAAAAAAAAAAAAAAAAAAAKAFAAEAAAAgAAAA AAAAAOD3v1//fwAAsOy/X/9/AACKuXWJ/38AAODsv1// fwAAKAAAAAAAAAAAAAAAAAAAAIjwgwABAAAAwOy/X/9/ AAAAAAARf////itiZWcAAAAAAAAAAAAAAAAAAAAAAAAA AAAAATMAAAAAAAAAAIAAAAUAAAAAAAAAAAAAAAAAAAAA AAACAAAAAAAAAAEzAAAAAAAAiYSAAAAFAAAAAAAAAAAA AAIAAAAAAAAAAgAAAAAAAACKtwAAAAAAAKaNgAAABQAA AAAAAAAAAAAEAAAAAAAAAAIAAAAAAAABMUQAAAAAAAAl b4AAAAUAAAAAAAAAAAAABgAAAAAAAAACAAAAAAAAAVaz AAAAAAAAgFeAAAAFAAAAAAAAAAAAAAgAAAAAAAAAAgAA AAAAAAHXCgAAAAAAAGhTgAAABQAAAAAAAAAAAAAKAAAA AAAAAAIAAAAAAAACP10AAAAAAAC+NYAAAAUAAAAAAAAA AAAADAAAAAAAAAACAAAAAAAAAv2SAAAAAAAAH6OAAAAF AAAAAAAAAAAAAA4AAAAAAAAAAgAAAAAAAAMdNQAAAAAA AASPgAAABQAAAAAAAAAAAAAQAAAAAAAAAAEIAAAAAAAD IcQAAAAAAAACZAAAAAIAAAAAAAAAAAAAEQgAAAAAAAA8 AAAAAAAAAyQoAAAAAAAAAACAAAAFAAAAAAAAAAAAAE0I AAAAAAAAAAgAAAAAAAMkKAAAAAAAAABEAAAAAgAAAAAA AAAAAABNEAAAAAAAAAAGAAAAAAADJGwAAAAAAAAAAIAA AAUAAAAAAAAAAAAATRYAAAAAAAAAAQAAAAAAAyRsAAAA AAAAAIsAAAACAAAAAAAAAAAAAE0XAAAAAAAAAAEAAAAA AAMk9wAAAAAAAAAAf////itlbmQAAAAAAABNGAAAAAAA AAAAAAAAAAADJPcAAAAAAAAAAP////8AAAAAAAAAAAAA TRgAAAAAAAAAAAAAAAAAAyT3AAAAAAAAAAA= ID 1 Name disk image (Apple_HFS : 2) Attributes 0x0050 CFName (Apple_Free : 3) Data bWlzaAAAAAEAAAAAAABNWAAAAAAAAAAKAAAAAAAAAAAA AAAAAAAAAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAIAAAAgAAAAAP9/AADw7L9f/38AAAAAAAAAAAAAgOy/ X/9/AAAoAAAAAAAAAAAAAAAAAAAAAKAFAAEAAAAgAAAA AAAAAOD3v1//fwAAsOy/X/9/AACKuXWJ/38AAODsv1// fwAAKAAAAAAAAAAAAAAAAAAAAIjwgwABAAAAwOy/X/9/ AAAAAAACAAAAAgAAAAAAAAAAAAAAAAAAAAAAAAAKAAAA AAADJPcAAAAAAAAAAP////8AAAAAAAAAAAAAAAoAAAAA AAAAAAAAAAAAAyT3AAAAAAAAAAA= ID 2 Name (Apple_Free : 3) plst Attributes 0x0050 Data AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEAAQAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAA ID 0 Name koly$÷‹aà†mD÷žŒæâþ# ¢Ÿµµ€ì¿_ÿ(  à÷¿_ÿ°ì¿_ÿйu‰ÿàì¿_ÿ(ðì¿_ÿðì¿_ÿ$÷à °’ÂMbsources_5316/test/0000755000176700017670000000000011577217060012710 5ustar paulpaulsources_5316/test/manually/0000755000176700017670000000000011605530571014527 5ustar paulpaulsources_5316/test/manually/fileselect.praat0000644000176700017670000000006711473750706017711 0ustar paulpaula$ = chooseDirectory$ ("Kies een folder") echo <<'a$'>>sources_5316/test/manually/demoWindow.praat0000644000176700017670000000307111200614377017673 0ustar paulpaul#! Praat script guentherGjajaDemo.praat # Paul Boersma, 6 May 2009 demo Erase all demo Black demo Line width... 1 demo Times demo 12 demo Select inner viewport... 0 100 0 100 demo Axes... 0 100 0 100 demo Text... 50 centre 50 half Please give this window the right size, then click to start. demoWaitForInput ( ) # After resizing, the viewport has to be set again. demo Select inner viewport... 0 100 0 100 demo Erase all demo Draw line... 0 0 30 70 demoWaitForInput ( ) demo Erase all demo Red demo Draw line... 0 0 7 3 demo Text... 50 centre 50 half Click in the sound to stop. duration = 3 Create Sound from formula... sine Mono 0 duration 1000 sin(2*pi*20*x) demo Select outer viewport... 0 40 0 40 demo Draw... 0 0 0 0 yes curve while 1 demoWaitForInput ( ) if demoClicked ( ) # We're gonna show that demoX and demoY can look at the whole window or into a part. demo Select inner viewport... 0 100 0 100 demo Axes... 0 100 0 100 x1 = demoX ( ) y1 = demoY ( ) clickedInTheSound = 0 if x1 > 0 and x1 < 40 and y1 > 0 and y1 < 40 demo Select outer viewport... 0 40 0 40 demo Axes... 0 duration -1 1 x2 = demoX ( ) y2 = demoY ( ) clickedInTheSound = x2 > 0 and x2 < duration and y2 > -1 and y2 < 1 endif if clickedInTheSound echo Hit the sound! printline 'x2:6' 'y2:6' goto end else echo 'x1:3' 'y1:3' endif elsif demoKeyPressed ( ) key$ = demoKey$ ( ) printline Key <<'key$'>> endif endwhile label end demo Erase all demo Select inner viewport... 0 100 0 100 demo Axes... 0 100 0 100 demo Text... 50 centre 50 half You have finished. sources_5316/test/manually/formsTest.praat0000644000176700017670000000176111200614433017542 0ustar paulpaul#! Praat script formsTest.txt # Paul Boersma, 20 January 2009 echo script compression = 1 number_of_channels = 2 worth = 3 for i to 5 beginPause ("Hi") comment ("Type a lot of nonsense below.") natural ("Number of people", 10) real ("Worth", worth+1) positive ("Sampling frequency (Hz)", "44100.0 (= CD quality)") word ("hi", "hhh") sentence ("lo", "two words") text ("ko", "jkgkjhkj g gdfg dfg") boolean ("You like it?", 1) if worth < 6 choice ("Compression", compression) option ("lossless (FLAC)") option ("MP3") option ("Ogg") endif optionMenu ("Number of channels", number_of_channels) option ("mono") option ("stereo") option ("quadro") comment ("Then click Stop or one of the continuation buttons.") clicked = endPause ("Continue", "Next", "Proceed", 2) printline 'number_of_people' 'worth' 'sampling_frequency' 'clicked' printline Compression: 'compression' ('compression$') printline Number of channels: 'number_of_channels$' endfor printline endsources_5316/test/manually/guiTest.praat0000644000176700017670000000345010635730722017210 0ustar paulpaulþÿ1. To see whether the object list updates correctly:éüß Select a Sound and run the following script: Down to Matrix gfdjkghdfgj The object list may become visually empty when the error dialog appears, but should show up again when the error dialog is dismissed. If not, XmUpdateDisplay () may be incorrect or missing from error dismissal. 2. To see whether the queries in the sound window are responsive: Create Sound To TextGrid Edit together Get pitch The answer should be immediate, not wait for 3 to 7 seconds. If not, GuiWindow_drain () may be incorrect, or somebody replaced it with XmUpdateDisplay (). 3. To see whether the Info window updates with every text: echo Results: for i to 10 for j to 10 print 'j' endfor printline 'i' endfor If not, GuiWindow_drain () may be incorrect. 4.sources_5316/test/script/0000755000176700017670000000000011741106317014207 5ustar paulpaulsources_5316/test/script/arithmetic.praat0000644000176700017670000000545710367342634017413 0ustar paulpaulecho arithmetic # Paul Boersma, January 27, 2006 assert 1 + 1 = 2 assert 1 + undefined = undefined assert undefined + 4 = undefined assert undefined + undefined = undefined assert 5 * 6 = 30 assert 5 * undefined = undefined assert undefined * 6 = undefined assert undefined * undefined = undefined assert 30 / 5 = 6 assert 5 / undefined = undefined assert undefined / 6 = undefined assert undefined / undefined = undefined assert 30 / 0 = undefined assert 30 div 0 = undefined assert 30 mod 0 = undefined assert 19 - 7 = 12 assert 19 - undefined = undefined assert undefined - 7 = undefined assert undefined - undefined = undefined # From the manual (Formulas 2. Operators): assert --6 = 6 assert 2^6 = 64 assert 2^-6 = 0.015625 assert -(1+1) ^6 = -64 assert 4^3^2 = 262144 assert 4^3 ^ 2 = 262144 assert (4 ^ 3) ^ 2 = 4096 assert (-2)^6 = 64 assert -(2^6) = -64 assert -(2)^6 = -64 assert 1/4*5 = 1.25 assert 1 / 4*5 = 1.25 assert 1 / (4*5) = 0.05 assert 3 * 2 ^ 4 = 48 assert 3*2 ^ 4 = 48 assert (3 * 2) ^ 4 = 1296 assert 54 div 5 = 10 assert 54 mod 5 = 4 assert 54.3 div 5.1 = 10 assert abs (54.3 mod 5.1 - 3.3) < 1e-12 assert -54 div 5 = -11 assert -(54 div 5) = -10 assert -(54 mod 5) = -4 assert 3 * 18 div 5 = 10 assert 3 * (18 div 5) = 9 assert 3 * 18 mod 5 = 4 assert 3 * (18 mod 5) = 9 assert 54 div 5 * 3 = 30 assert 54 div (5 * 3) = 3 assert 54 mod 5 * 3 = 12 assert 54 mod (5 * 3) = 9 assert 3 - 8 + 7 = 2 assert 3 - (8 + 7) = -12 assert 3 + 8 * 7 = 59 assert (3 + 8) * 7 = 77 assert 3 + - (2 ^ 4) = -13 assert 3 + 5 / 2 + 3 = 8.5 assert (3 + 5) / (2 + 3) = 1.6 assert 1 + 1 = 2 assert 1 + 1 < 3 assert 1 + 1 <= 2 assert 1 + 1 <= 3 assert 1 + 1 > 1 assert 1 + 1 >= 2 assert 1 + 1 >= 1 assert (5 + 6 = 10) = 0 assert (5 + 6 = 11) = 1 assert (5 + 6 <> 10) = 1 assert (5 + 6 <> 11) = 0 assert (5 + 6 < 10) = 0 assert (5 + 6 < 11) = 0 assert (5 + 6 > 10) = 1 assert (5 + 6 > 11) = 0 assert (5 + 6 <= 10) = 0 assert (5 + 6 <= 11) = 1 assert (5 + 6 >= 10) = 1 assert (5 + 6 >= 11) = 1 assert (not 5 + 6 = 10) = 1 assert (not 5 + 6 = 11) = 0 x = 7 assert (x > 5 and x < 10) = 1 assert (not x <= 5 and not x >= 10) = 1 assert (not (x <= 5 or x >= 10)) = 1 assert ("hallo" = "hallo") = 1 assert ("hallo" = "hello") = 0 assert ("hallo" <> "hallo") = 0 assert ("hallo" <> "hello") = 1 assert ("hallo" < "hallo") = 0 assert ("hallo" < "hello") = 1 assert ("hello" < "hallo") = 0 assert ("hallo" > "hallo") = 0 assert ("hallo" > "hello") = 0 assert ("hello" > "hallo") = 1 assert ("hallo" <= "hallo") = 1 assert ("hallo" <= "hello") = 1 assert ("hello" <= "hallo") = 0 assert ("hallo" >= "hallo") = 1 assert ("hallo" >= "hello") = 0 assert ("hello" >= "hallo") = 1 assert "hallo" + "dag" = "hallodag" assert "hallo" + "dag" <> "hellodag" assert "hallo" - "dag" = "hallo" assert "hallodag" - "dag" = "hallo" assert left$ ("hallo", 3) = "hal" printline OKsources_5316/test/script/text100MB.praat0000644000176700017670000000070511130226672016665 0ustar paulpaul# text100MB.praat # Paul Boersma, 9 November 2008 echo Text 100 MB: stopwatch a$ = "a" for i to 8 a$ = a$ + a$ + a$ + a$ + a$ + a$ + a$ + a$ + a$ + a$ endfor t = stopwatch printline creating: 't:3' seconds stopwatch a$ > kanweg.txt t = stopwatch printline writing: 't:3' seconds stopwatch b$ < kanweg.txt t = stopwatch printline reading: 't:3' seconds stopwatch assert a$ = b$ t = stopwatch printline comparing: 't:3' seconds deleteFile ("kanweg.txt")sources_5316/test/script/script.praat0000644000176700017670000000060611130516430016537 0ustar paulpaulþÿecho script # Paul Boersma, 5 January 2009 asserterror Unknown variable:'newline$'« hg hg a = 1 asserterror Expected the end of the formula, but found a numeric variable: a = 5a printline OK sources_5316/test/script/arrays.praat0000644000176700017670000000237611564024331016547 0ustar paulpaulecho arrays... ; writeInfoLine ("arrays...") # should give a different error: ;a a=5 # should give an error: a+5 a [1] = 3 assert a [1] = 3 printline 'a[1]' ; appendInfoLine (a [1]) ; abcdefghijklmnopqrstuvwxyz ;a [12345678] a = 7 asserterror Missing expression after variable a[9]. a [a+2] = ;a [2] a [3], 5 = 7 printline 'a[3,5]', 'a[3]' a [1] = 2 b [a [1]] = 3 assert b [a [1]] = 3 printline 'b[2]' speaker$[1]="paul" printline <'speaker$[1]'> speaker$ [2] = "silke" printline <'speaker$[2]'> a$ = speaker$ [1] + " " + speaker$ [2] printline <'a$'> assert numberOfRows (zero# (5, 6)) = 5 assert numberOfColumns (zero# (5, 6)) = 6 a# = zero# (5, 6) assert numberOfRows (a#) = 5 assert a# [3, 4] = 0 c# = linear# (0, 100, 101) assert c# [98] = 97 c# = linear# (0, 100, 101, 0) assert c# [98] = 97 c# = linear# (0, 100, 100, 1) assert c# [98] = 97.5 d# = randomGauss# (c#, 20, 1) a = d# [98] b = d# [99] c = d# [100] printline 'a' 'b' 'c' d# = randomUniform# (c#, 7, 10) a = d# [98] b = d# [99] c = d# [100] printline 'a' 'b' 'c' d# = randomInteger# (c#, 7, 10) a = d# [98] b = d# [99] c = d# [100] printline 'a' 'b' 'c' ;e# = d# + c# ;speaker$# = empty$# [2] ;speaker$# [1] = "JM" ;speaker$# [2] = "PB" ;speaker$ [1] = "JM" ;speaker$ [2] = "PB" printline OK sources_5316/test/test.praat0000644000176700017670000000045711577216716014735 0ustar paulpaulErase all Times 12 Viewport... 0 6 0 6 Create simple Matrix... hundred 2 100 randomUniform(0,100) To Polygon Salesperson... 1000 Draw closed... 0 0 0 0 Create simple Matrix... circle 2 100000 ... if row=1 then cos(2*pi*col/100000) else sin(2*pi*col/100000) fi To Polygon Draw... 0 0 0 0 sources_5316/test/kanweg/0000755000176700017670000000000011104272400014145 5ustar paulpaulsources_5316/test/contrib/0000755000176700017670000000000011540154433014342 5ustar paulpaulsources_5316/test/contrib/kNN.praat0000644000176700017670000000134611552372115016067 0ustar paulpaula1 = 0 a2 = 0 a3 = 0 for i from 1 to 30 Create iris example... 0 0 select FFNet 4-3 select Pattern iris plus Categories iris To KNN Classifier... Classifier Sequential temp = Get accuracy estimate... "Leave one out" 10 Inversed squared distance a1 = a1 + (temp - a1) / i Shuffle temp = Get accuracy estimate... "10-fold cross-validation" 10 Inversed squared distance a2 = a2 + (temp - a2) / i Prune... 1 1 10 select Pattern iris plus Categories iris plus KNN Classifier temp = Evaluate... 10 Inversed squared distance a3 = a3 + (temp - a3) / i select FFNet 4-3 plus Pattern iris plus Categories iris plus KNN Classifier Remove endfor result = (a1 + a2 + a3) / 3 if result > 96 printline OK else printline Failed endif sources_5316/test/dwtools/0000755000176700017670000000000011540155226014376 5ustar paulpaulsources_5316/test/dwtools/KlattSlope.praat0000644000176700017670000000361511473727472017533 0ustar paulpaul# KlattSlope.praat # Paul Boersma, 25 November 2010 # This script tests whether a sound created with the Klatt synthesizer # is similar to a sound created with "To Sound (phonation)". openPhase = 0.7 collisionPhase = 0.03;hertzToErb(300)/35;0.03 power = 3.0 f1 = 250 b1 = 100 f2 = 3200 b2 = 100 duration = 0.8 f0start = 150 f0end = 110 ;bandwidthFormula$ = "100" bandwidthFormula$ = "(formant-0.5)*1000/10" numberOfFormants = 20 pitchTier = Create PitchTier... a 0 duration Add point... 0 f0start Add point... duration f0end pulses = To PointProcess sound = To Sound (phonation)... 44100 1.0 0.05 openPhase collisionPhase power power+1.0 ;sound = To Sound (pulse train)... 44100 1.0 0.05 2000 Filter with one formant (in-line)... f1 b1 Filter with one formant (in-line)... f2 b2 for formant from 3 to numberOfFormants Filter with one formant (in-line)... (formant-0.5)*1000 'bandwidthFormula$' endfor spectrum = To Spectrum... yes slope1 = Get band density difference... 0 1000 2000 4000 echo 'slope1:6' dB klatt = Create KlattGrid... a 0 duration numberOfFormants 0 0 0 0 0 0 Add voicing amplitude point... 0 90.0 Add pitch point... 0 f0start Add pitch point... duration f0end Add power1 point... 0 power Add power2 point... 0 power+1.0 Add open phase point... 0 openPhase Add collision phase point... 0 collisionPhase Add oral formant frequency point... 1 0 f1 Add oral formant bandwidth point... 1 0 b1 Add oral formant frequency point... 2 0 f2 Add oral formant bandwidth point... 2 0 b2 for formant from 3 to numberOfFormants Add oral formant frequency point... formant 0 (formant-0.5)*1000 Add oral formant bandwidth point... formant 0 'bandwidthFormula$' endfor ;To Sound (special)... 0 0 44100 yes yes yes yes yes yes "Powers in tiers" yes yes yes Cascade 1 numberOfFormants 1 1 0 0 0 0 0 0 0 0 0 0 0 0 yes To Sound To Spectrum... yes slope2 = Get band density difference... 0 1000 2000 4000 printline 'slope2:6' dB sources_5316/test/stat/0000755000176700017670000000000011574355743013673 5ustar paulpaulsources_5316/test/stat/logisticRegression.praat0000644000176700017670000000105111540172276020566 0ustar paulpaulecho Logistic regression # Paul Boersma, 30 November 2009 printline Spec & Dur table Read Table from table file... logisticRegression/rh.Table To logistic regression... "Spec Dur" /I/ /i/ info$ = Info intercept = extractNumber (info$, "Intercept: ") assert fixed$ (intercept, 4) = "-8.7028" ; 'intercept' spec = extractNumber (info$, "Coefficient of factor Spec: ") assert fixed$ (spec, 4) = "1.6587" ; 'spec' dur = extractNumber (info$, "Coefficient of factor Dur: ") assert fixed$ (dur, 4) = "0.6041" ; 'dur' plus Table rh Remove printline OK sources_5316/test/stat/logisticRegression/0000755000176700017670000000000011540172221017526 5ustar paulpaulsources_5316/test/stat/logisticRegression/rh.Table0000644000176700017670000000052110232007030021076 0ustar paulpaulSpec Dur /I/ /i/ 1 1 10 0 1 2 10 0 1 3 10 0 1 4 10 0 1 5 10 0 1 6 10 0 1 7 7 3 2 1 10 0 2 2 10 0 2 4 10 0 2 7 8 2 3 1 9 1 3 3 9 1 3 4 10 0 3 7 6 4 4 1 9 1 4 2 9 1 4 3 4 6 4 4 3 7 4 5 3 7 4 6 2 8 4 7 0 10 5 1 0 10 5 4 2 8 5 5 0 10 5 7 0 10 6 1 1 9 6 4 0 10 6 6 0 10 6 7 0 10 7 1 3 7 7 2 0 10 7 3 0 10 7 4 0 10 7 5 0 10 7 6 0 10 7 7 0 10 sources_5316/test/stat/logisticRegression/rh_logisticRegressionReport.txt0000644000176700017670000000572310232007736026046 0ustar paulpaulDescriptives... 175 cases have Y=0; 195 cases have Y=1. Variable Avg SD 1 4.0000 2.1181 2 4.0000 2.1181 Iteration History... -2 Log Likelihood = 511.8473 (Null Model) -2 Log Likelihood = 244.7787 -2 Log Likelihood = 199.7288 -2 Log Likelihood = 188.1922 -2 Log Likelihood = 186.7793 -2 Log Likelihood = 186.7473 -2 Log Likelihood = 186.7473 -2 Log Likelihood = 186.7473 (Converged) Overall Model Fit... Chi Square= 325.1000; df=2; p= 0.0000 Coefficients and Standard Errors... Variable Coeff. StdErr p 1 1.6587 0.1803 0.0000 2 0.6041 0.1021 0.0000 Intercept -8.7028 Odds Ratios and 95% Confidence Intervals... Variable O.R. Low -- High 1 5.2526 3.6892 7.4785 2 1.8297 1.4978 2.2352 X1 X2 n0 n1 Calc Prob 1.0000 1.0000 10 0 0.0016 1.0000 2.0000 10 0 0.0029 1.0000 3.0000 10 0 0.0053 1.0000 4.0000 10 0 0.0097 1.0000 5.0000 10 0 0.0176 1.0000 6.0000 10 0 0.0317 1.0000 7.0000 7 3 0.0565 2.0000 1.0000 10 0 0.0083 2.0000 2.0000 10 0 0.0151 2.0000 4.0000 10 0 0.0489 2.0000 7.0000 8 2 0.2393 3.0000 1.0000 9 1 0.0422 3.0000 3.0000 9 1 0.1285 3.0000 4.0000 10 0 0.2125 3.0000 7.0000 6 4 0.6230 4.0000 1.0000 9 1 0.1879 4.0000 2.0000 9 1 0.2974 4.0000 3.0000 4 6 0.4365 4.0000 4.0000 3 7 0.5863 4.0000 5.0000 3 7 0.7217 4.0000 6.0000 2 8 0.8259 4.0000 7.0000 0 10 0.8967 5.0000 1.0000 0 10 0.5486 5.0000 4.0000 2 8 0.8816 5.0000 5.0000 0 10 0.9316 5.0000 7.0000 0 10 0.9785 6.0000 1.0000 1 9 0.8646 6.0000 4.0000 0 10 0.9751 6.0000 6.0000 0 10 0.9924 6.0000 7.0000 0 10 0.9958 7.0000 1.0000 3 7 0.9710 7.0000 2.0000 0 10 0.9840 7.0000 3.0000 0 10 0.9912 7.0000 4.0000 0 10 0.9952 7.0000 5.0000 0 10 0.9973 7.0000 6.0000 0 10 0.9985 7.0000 7.0000 0 10 0.9992 sources_5316/test/stat/Table.praat0000644000176700017670000000050511542326033015734 0ustar paulpaulfor i to 100000 d'i' = i endfor d43789 = Create formant table (Weenink 1985) name$ = selected$ ("Table") stopwatch for cycle to 300 for row to 360 ;z = Table_'name$' [row, "F0"] ;z = Object_'d43789' [row, "F0"] z = object [d43789, row, "F0"] ;d34789 = Get value... row F0 endfor endfor t = stopwatch echo 't:3' 'z'sources_5316/test/stat/test.Table0000644000176700017670000000017410420775013015606 0ustar paulpaulName Gender Age Paul m ? Silke f --undefined-- Jelle m 14 Jildou f 11 Lothar m 84 Anne Marie f 71 Christel f 73 Martin m 175sources_5316/test/runAllTests.praat0000644000176700017670000000441311605533360016217 0ustar paulpaul# Praat script runAlltests.praat # Paul Boersma, 16 March 2011 # # This script runs all Praat scripts in its subdirectories, except itself. directories = Create Strings as directory list... directories . numberOfDirectories = Get number of strings for directory to numberOfDirectories printline 'directory' select Strings directories directory$ = Get string... directory printline 'directory$' if directory$ <> "manually" files = Create Strings as file list... files 'directory$'/*.praat numberOfFiles = Get number of strings for file to numberOfFiles select files file$ = Get string... file printline ### executing 'directory$'/'file$': execute 'directory$'/'file$' endfor endif endfor directories1 = Create Strings as directory list... directories1 . numberOfDirectories1 = Get number of strings for directory1 to numberOfDirectories1 select Strings directories1 directory1$ = Get string... directory1 if directory1$ <> "manually" directories2 = Create Strings as directory list... directories2 'directory1$'/* numberOfDirectories2 = Get number of strings for directory2 to numberOfDirectories2 select Strings directories2 directory2$ = Get string... directory2 files = Create Strings as file list... files 'directory1$'/'directory2$'/*.praat numberOfFiles = Get number of strings for file to numberOfFiles select files file$ = Get string... file printline ### executing 'directory1$'/'directory2$'/'file$': execute 'directory1$'/'directory2$'/'file$' endfor endfor endif endfor echo ALL PRAAT TESTS WENT OK printline line5$ = " ##### ##### ##### #####" line8$ = " ##### ##### #######" line1$ = " ###### ##### #####" line2$ = " ############## ##### #####" line4$ = " ##### ##### ##### #####" line7$ = " ##### ##### #########" line9$ = " ##### ##### #####" line3$ = " ##### ##### ##### #####" line6$ = " ##### ##### ##### #####" for line from 1 to 9 line$ = line'line'$ printline 'line$' endfor for line2 from 1 to 8 line = 9 - line2 line$ = line'line'$ printline 'line$' endfor sources_5316/test/sys/0000755000176700017670000000000011752251234013522 5ustar paulpaulsources_5316/test/sys/graphics.praat0000644000176700017670000001705611752235710016365 0ustar paulpaulþÿ# graphics.praat # Paul Boersma, 8 May 2012 Erase all Times 14 Select inner viewport... 0.1 0.4 0.1 8.9 Axes... 0 1 0 1 for i from 0 to 800 grey = i/800 Paint rectangle... 'grey' 0 1 i/801 (i+1)/801 endfor Black Draw inner box Select inner viewport... 5.6 5.9 0.1 8.9 Axes... 0 1 18 -1 Line width... 1 Draw line... 0.3 -1 0.3 18 Line width... 2 Draw line... 0.5 -1 0.5 18 Line width... 3 Draw line... 0.7 -1 0.7 18 Line width... 2 Paint rectangle... 0.5 0 3 1 2 drawColour.y = 0 procedure drawColour colour$ Paint rectangle... 'colour$' 0 1 .y .y+1 'colour$' Draw line... 1.2 .y 1.1 .y+1 Text... 1.2 left .y+0.5 half 'colour$' .y += 1 endproc call drawColour Black call drawColour White call drawColour Red call drawColour Green call drawColour Blue call drawColour Yellow call drawColour Cyan call drawColour Magenta call drawColour Maroon call drawColour Lime call drawColour Navy call drawColour Teal call drawColour Purple call drawColour Olive call drawColour Pink call drawColour Silver call drawColour Grey Black Line width... 1 Select inner viewport... 0.6 1 0.1 1.9 Axes... 0 1 0 1 Draw line... 0 0 0 1 Text... 0 Left 1.0 Top top-aligned Text... 0 Left 0.8 Half This text here is Text... 0 Left 0.6 Half left-aligned text Text... 0 Left 0.4 Half \ae\:fnd\0v \dh\ics \swz w\ef\l~. Text... 0 Left 0.2 Half many----hyphens Text... 0 Left 0.0 Bottom bottom-aligned Text... 0 Left -0.2 Bottom Kate\r<ina Text... 0 Left -0.4 Bottom KateYina Text... 0 Left -0.6 Bottom Õ\­m Select inner viewport... 2.8 3.2 0.1 1.9 Dotted line Draw line... 0.5 0 0.5 1 Solid line Text... 0.5 Centre 1.0 Top top-aligned Text... 0.5 Centre 0.8 Half This text here is Text... 0.5 Centre 0.6 Half centred text Text... 0.5 Centre 0.4 Half \aeÐnd\0v \dh\ics \swz w\ef\l~. Text... 0.5 Centre 0.2 Half many----hyphens Text... 0.5 Centre 0.0 Bottom bottom-aligned Select inner viewport... 5 5.4 0.1 1.9 Draw line... 1 0 1 1 Text... 1 Right 1.0 Top top-aligned Text... 1 Right 0.8 Half This text here is Text... 1 Right 0.6 Half right-aligned text Text... 1 Right 0.4 Half \aeÐnd\0v \dh\ics \swz w\ef\l~. Text... 1 Right 0.2 Half many----hyphens Text... 1 Right 0.0 Bottom bottom-aligned Text... 1 Right -0.2 Bottom arkada_ Text... 1 Right -0.4 Bottom -(J( Text... 1 Right -0.6 Bottom eåg, Select inner viewport... 2.5 3.5 2.6 3.6 for i to 10 Draw circle (mm)... 0.5 0.5 i endfor Blue for i to 36 .x = cos (i * pi / 18) .y = sin (i * pi / 18) Draw arrow... 0.5+0.3*.x 0.5+0.3*.y 0.5+0.7*.x 0.5+0.7*.y endfor for i from 10 to 20 Draw ellipse... 0.5-i/10 0.5+i/10 -0.3 1.3 endfor Select inner viewport... 0 6 4 5 for i to 10 Paint circle (mm)... green i/12 0.7 i Paint ellipse... pink (11.9-i)/12 (11.1-i)/12 0.3-i/30 0.3+i/30 endfor Select outer viewport... 0 6 5 5.5 Text bottom... yes Ø4ÝØ4Ý Select inner viewport... 0 6 5 6 Purple Draw rounded rectangle... 0.2 0.4 0.3 0.7 3 Paint rounded rectangle... purple 0.6 0.8 0.3 0.7 3 Select inner viewport... 0 6 6 7 call drawLines 1 0.1 call drawLines 2 0.3 call drawLines 3 0.5 call drawLines 5 0.7 procedure drawLines .width .x Line width... .width Dashed line Draw line... .x 0.65 .x+0.1 0.65 Dotted line Draw line... .x 0.55 .x+0.1 0.55 Dashed-dotted line Draw line... .x 0.45 .x+0.1 0.45 Solid line Draw line... .x 0.35 .x+0.1 0.35 endproc Line width... 1 Select inner viewport... 0.7 2.7 7 9 Create simple Matrix... hundred 2 100 randomUniform(0,100) To Polygon Salesperson... 1000 Draw closed... 0 0 0 0 Create simple Matrix... circle 2 100000 ... if row=1 then cos(2*pi*col/100000) else sin(2*pi*col/100000) fi To Polygon Draw... 0 0 0 0 Black Create simple Matrix... checker 10 10 x*y Select inner viewport... 3.3 5.3 7 9 Paint cells... 0 0 0 0 0 0 Select outer viewport... 0 6.5 0 9 Write to praat picture file... kanweg.prapic Erase all Read from praat picture file... kanweg.prapic deleteFile ("kanweg.prapic") sources_5316/test/sys/localVariables.praat0000644000176700017670000000057410367131453017505 0ustar paulpaulecho Local variables procedure add .x .y .result = .x + .y endproc procedure square .x .result = .x ^ 2 endproc procedure hypotenuse .x .y call square .x .x2 = square.result call square .y .y2 = square.result call add .x2 .y2 .result = sqrt (add.result) endproc call hypotenuse 3 4 assert hypotenuse.result = 5 assert add.result = 25 assert square.result = 16 printline OKsources_5316/test/num/0000755000176700017670000000000011540154546013506 5ustar paulpaulsources_5316/test/num/fisherQ.praat0000644000176700017670000000762111106036746016145 0ustar paulpaul# fisherQ # Paul Boersma, August 27, 2003 # April 7, 2008: more accuracy in fisherQ because of GSL (n.b. GSL not to be used in invFisherQ) # Computes a significance from zero, given a measured F value. df1 = 2 df2 = 70 f = 33.59 fisherQ = fisherQ (f, df1, df2) fisherQ$ = fixed$ (fisherQ, 20) echo fisherQ test: 'fisherQ' 'fisherQ$' assert fisherQ$ = "0.00000000005932714540" for i to 10000 assert fisherQ (randomUniform (3, 4), 1, 100000) <> undefined endfor echo invFisherQ call invFisherQ 2 70 1e-14 call invFisherQ 70 2 1e-14 call invFisherQ 1 if(windows)then(100)else(100000)fi 1e-11 if not windows call invFisherQ 1 1 1e-14 call invFisherQ 100000 1 1e-11 endif call invFisherQ 100 100 1e-9 procedure invFisherQ df1 df2 precision # Known values. assert invFisherQ (0, 'df1', 'df2') = undefined assert invFisherQ (1, 'df1', 'df2') = 0 # We should be able to draw a curve of invFisherQ. for i from 1 to 1000 assert abs (fisherQ (invFisherQ (i/1000, df1, df2), 'df1', 'df2') - 'i'/1000) < 'precision' ; 'i' 'df1' 'df2' endfor # Q near 0, i.e. F large: relative precision. for power from 4 to if windows then 147 else 150 fi q = 10 ^ -power f = invFisherQ (q, df1, df2) assert f <> undefined ; 'q' 'df1' 'df2' assert abs (fisherQ (f, 'df1', 'df2') - 'q') < 'q'*'precision'*10 ; 'f' endfor mentioned = 0 for power from if windows then 148 else 151 fi to 307 q = 10 ^ -power f = invFisherQ (q, df1, df2) if f = undefined and not mentioned printline 'df1' 'df2' 'power' mentioned = 1 endif assert f = undefined or abs (fisherQ (f, 'df1', 'df2') - 'q') < 'q'*'precision'*300 ; 'power' 'f' endfor # Q near 1, i.e. F near zero. assert abs (fisherQ (invFisherQ (0.9999, df1, df2), 'df1', 'df2') - 0.9999) < 'precision' assert abs (fisherQ (invFisherQ (0.99999, df1, df2), 'df1', 'df2') - 0.99999) < 'precision' assert abs (fisherQ (invFisherQ (0.999999, df1, df2), 'df1', 'df2') - 0.999999) < 'precision' assert abs (fisherQ (invFisherQ (0.9999999, df1, df2), 'df1', 'df2') - 0.9999999) < 'precision' assert abs (fisherQ (invFisherQ (0.99999999, df1, df2), 'df1', 'df2') - 0.99999999) < 'precision' assert abs (fisherQ (invFisherQ (0.999999999, df1, df2), 'df1', 'df2') - 0.999999999) < 'precision' # # The inverse relationship: q values from measured f values should map back to those f values. # for power to 100 f = 10 ^ -power q = fisherQ (f, df1, df2) assert q=1 or abs (invFisherQ ('q', 'df1', 'df2') - 'f') < precision endfor for f from 10 to 99 q = fisherQ (f/100, df1, df2) assert q>1-precision or abs (invFisherQ (q, 'df1', 'df2') - 'f'/100) < precision assert abs (invFisherQ (fisherQ (f/10, df1, df2), 'df1', 'df2') - 'f'/10) < f/10*precision assert abs (invFisherQ (fisherQ (f, df1, df2), 'df1', 'df2') - 'f') < f*precision assert abs (invFisherQ (fisherQ (10*f, df1, df2), 'df1', 'df2') - 10*'f') < 10*f*precision q = fisherQ (100*f, df1, df2) assert q = 0 or abs (invFisherQ ('q', 'df1', 'df2') - 100*'f') < 100*f*precision q = fisherQ (1000*f, df1, df2) assert q = 0 or abs (invFisherQ ('q', 'df1', 'df2') - 1000*'f') < 1000*f*precision endfor endproc # # Things that used to go wrong. # assert invFisherQ (0.13, 1, 1e9) <> undefined ; used to exceed 60 iterations assert invFisherQ (0.159, 2, 70) <> undefined ; used to exceed 60 iterations # # Things that still go wrong. # assert fisherQ (1, 1e19, 1e19) = undefined # # Check that we invert better than GSL does. # Debug... 29 ; set invFisherQ to GSL f = invFisherQ (0.01, 1, 10000) ; not such an unusual case assert "'f'" = "nan" or "'f'" = "NaN" Debug... 0 ; use our corrected NUMridders again f = invFisherQ (0.01, 1, 10000) ; same case assert "'f:5'" = "6.63743" # printline OK sources_5316/test/num/binomialQ.praat0000644000176700017670000000050310504277021016441 0ustar paulpaulecho binomialQ assert fixed$ (invBinomialP (0.025, 211, 1000), 6) = "0.237622" assert fixed$ (invBinomialQ (0.025, 211, 1000), 6) = "0.186092" assert abs (binomialP (invBinomialP (0.025, 211, 1000), 211, 1000) - 0.025) < 1e-14 assert abs (binomialQ (invBinomialQ (0.025, 211, 1000), 211, 1000) - 0.025) < 1e-15 printline OKsources_5316/test/num/min.praat0000644000176700017670000000177507710443126015333 0ustar paulpaul#! Praat test script min.praat # Paul Boersma, July 26, 2003 echo min assert min (5, 6) = 5 assert min (-7.8) = -7.8 assert min (3, 4, 5, 7, 2, 10) = 2 assert min (3, 4, 5, 7, 12, 10) = 3 assert min (3, 4, 5, 7, 12, 1) = 1 assert imin (5, 6) = 1 assert imin (-7.8) = 1 assert imin (3, 4, 5, 7, 2, 10) = 5 assert imin (3, 4, 5, 7, 12, 10) = 1 assert imin (3, 4, 5, 7, 12, 1) = 6 assert max (5, 6) = 6 assert max (-7.8) = -7.8 assert max (3, 4, 5, 7, 2, 10) = 10 assert max (3, 4, 5, 7, 12, 10) = 12 assert max (13, 4, 5, 7, 12, 10) = 13 assert imax (5, 6) = 2 assert imax (-7.8) = 1 assert imax (3, 4, 5, 7, 2, 10) = 6 assert imax (3, 4, 5, 7, 12, 10) = 5 assert imax (13, 4, 5, 7, 12, 10) = 1 assert min (undefined, 3) = undefined assert imin (undefined, 3) = undefined assert max (undefined, 3) = undefined assert imax (undefined, 3) = undefined assert min (3, undefined) = undefined assert imin (3, undefined) = undefined assert max (3, undefined) = undefined assert imax (3, undefined) = undefined printline OKsources_5316/test/num/mathFunctions.praat0000644000176700017670000000274110627101702017354 0ustar paulpaulecho sqrt # Paul Boersma, July 6, 2003 assert sqrt (-100) = undefined assert sqrt (0) = 0 assert sqrt (1) = 1 assert sqrt (4) = 2 assert sqrt (9) = 3 assert sqrt (123456789^2) = 123456789 assert abs (sqrt (2) ^ 2 - 2) < 1e-15 printline exp # Paul Boersma, September 20, 2006 assert exp (-10000) = 0 assert exp (0) = 1 assert exp (1) = e assert abs (1 - exp (100) / e ^ 100) < 1e-13 assert abs (1 - exp (100) * exp (-100)) < 1e-15 assert abs (1 - e ^ 100 * e ^ -100) < 1e-14 printline pow # Paul Boersma, August 27, 2003 assert 0^7 = 0 assert 7^0 = 1 ;assert 0^0 = 1 ; special choice printline ln # Paul Boersma, July 6, 2003 assert ln (-100) = undefined assert ln (0) = undefined assert ln (1) = 0 assert abs (ln (exp (100)) - 100) < 1e-13 assert abs (ln (exp (10)) - 10) < 1e-17 assert abs (ln (exp (1)) - 1) < 1e-17 assert abs (ln (exp (0.1)) - 0.1) < 1e-16 assert abs (ln (exp (0.01)) - 0.01) < 1e-15 printline lnGamma # Paul Boersma, July 13, 2003 assert lnGamma (-100) = undefined assert lnGamma (0) = undefined assert lnGamma (1) = 0 assert abs (lnGamma (e^-100) - 100) < 1e-13 assert abs (e^lnGamma(4) - 6) < 1e-13 assert abs (exp(lnGamma(4)) - 6) < 1e-13 factorial = 1 for i to 170 factorial *= i assert abs (1 - e^lnGamma('i' + 1) / factorial) < 1e-12 endfor for i from -100 to 2 x = 1.23456789 * 10^i gamma = exp (lnGamma (x)) gamma2 = exp (lnGamma (x + 1)) gamma3 = x * gamma ;printline 'gamma2' 'gamma3' assert abs (1 - gamma2 / gamma3) < 1e-13 endfor printline OKsources_5316/test/dwsys/0000755000176700017670000000000011540154505014053 5ustar paulpaulsources_5316/test/dwsys/regex.praat0000644000176700017670000000137011642267170016225 0ustar paulpaulþÿa$ = replace_regex$ ("hallo", ".", "&&", 0) assert a$ = "hhaalllloo" ; 'a$' a$ = replace_regex$ ("hQllT", ".", "&&", 0) assert a$ = "hhQQllllTT" ; 'a$' # something that went wrong when Rob compiled Praat with -O2 on mingw (20110916): s$ = "ma0" sNew$ = replace_regex$(s$, "5", "0", 0) assert sNew$ = "ma0" sNew2$ = replace_regex$(s$, "ma", "pa5", 0) assert sNew2$ = "pa50" sources_5316/test/kar/0000755000176700017670000000000011741652343013465 5ustar paulpaulsources_5316/test/kar/unicode16.praat0000644000176700017670000000767211501741010016307 0ustar paulpaulecho Unicode # Paul Boersma, 11 March 2010 # This script shouldn't just run correctly, but should also do the following things correctly: # 1. Menu command "Where am I?". # 2. Menu command "Go to line...". # 3. These can be combined by doing Command-L, then OK. # 4. Menu command "Run selection". # 5. Menu command "Paste history", both into a cursor position and overwriting. Text reading preferences... UTF-8 Text writing preferences... UTF-8 call test Text writing preferences... UTF-16 call test Text writing preferences... try ASCII, then UTF-16 call test Text writing preferences... try ISO Latin-1, then UTF-16 Text reading preferences... try UTF-8, then ISO Latin-1 call test # # Clean up. # Text writing preferences... try ASCII, then UTF-16 if macintosh Text reading preferences... try UTF-8, then MacRoman elif windows Text reading preferences... try UTF-8, then Windows Latin-1 elif unix Text reading preferences... try UTF-8, then ISO Latin-1 else exit Unknown operating system. endif procedure test assert length ("éééürtüéŋəü") = 11 ; precomposed (typed into ScriptEditor) assert length ("eÌeÌeÌürtüeÌŋəü") = 18 ; decomposed (copied from MacOS file icon) assert "ɦɑlou" + "É£ujÉ™dÉ‘x" = "ɦɑlouÉ£ujÉ™dÉ‘x" ; BMP (Unicode values up to 0xFFFF) assert left$ ("ɦɑlou", 3) = "ɦɑl" assert "ɦɑl" <> "??l" # The text I/O commands ">", ">>", and "<": deleteFile ("kanweg.txt") text$ = "adddɦɑlouÉ£ujÉ™dÉ‘xdÉ‘x" text$ > kanweg.txt text$ < kanweg.txt assert text$ = "adddɦɑlouÉ£ujÉ™dÉ‘xdÉ‘x" ; <<'text$'>> text$ >> kanweg.txt text$ < kanweg.txt assert text$ = "adddɦɑlouÉ£ujÉ™dÉ‘xdÉ‘xadddɦɑlouÉ£ujÉ™dÉ‘xdÉ‘x" ; <<'text$'>> # ASCII appending: deleteFile ("kanweg.txt") fileappend kanweg.txt abc'newline$' fileappend kanweg.txt def'newline$' fileappend kanweg.txt ghi'newline$' text$ < kanweg.txt assert text$ = "abc" + newline$ + "def" + newline$ + "ghi" + newline$ # UTF-16 appending (or UTF-8, or first ISO Latin-1 then change to UTF-16): deleteFile ("kanweg.txt") fileappend kanweg.txt Ã¥bc'newline$' fileappend kanweg.txt dëf'newline$' fileappend kanweg.txt ‘ghi’וּ'newline$' text$ < kanweg.txt assert text$ = "Ã¥bc" + newline$ + "dëf" + newline$ + "‘ghi’וּ" + newline$ # Append to file first in ASCII, then change the encoding of the whole file to UTF-16 (or UTF-8): deleteFile ("kanweg.txt") fileappend kanweg.txt abc'newline$' fileappend kanweg.txt dëf'newline$' fileappend kanweg.txt ‘ghi’וּ'newline$' text$ < kanweg.txt assert text$ = "abc" + newline$ + "dëf" + newline$ + "‘ghi’וּ" + newline$ assert fileReadable ("kanweg.txt") deleteFile ("kanweg.txt") assert not fileReadable ("kanweg.txt") # Unicode file names (precomposed source code): assert length ("kanweg_abcÃ¥bçéü.txt") = 19 ; hopefully not 21 deleteFile ("kanweg_abcÃ¥bçéü.txt") fileappend kanweg_abcÃ¥bçéü.txt hallo assert fileReadable ("kanweg_abcÃ¥bçéü.txt") deleteFile ("kanweg_abcÃ¥bçéü.txt") assert not fileReadable ("kanweg_abcÃ¥bçéü.txt") fileappend kanweg_abcÃ¥bçéü.txt hallo text$ < kanweg_abcÃ¥bçéü.txt assert text$ = "hallo" Read from file... Ã¥bçéü.wav select Sound Ã¥bçéü info$ = Info secondLine = index (info$, "Object type") header$ = left$ (mid$ (info$, secondLine, 10000), 38) assert header$ = "Object type: Sound" + newline$ + "Object name: Ã¥bçéü" + newline$ ; 'header$' Remove textgrid = Create TextGrid... 0 1 test Set interval text... 1 1 åçé Write to text file... kanweg.TextGrid textgrid2 = Read from file... kanweg.TextGrid assert objectsAreIdentical (textgrid, textgrid2) plus textgrid Remove Create Strings as file list... list *.txt n = Get number of strings for i to n fileName$ = Get string... i assert right$ (fileName$, 4) = ".txt" length = length (fileName$) printline 'length' 'fileName$' if left$ (fileName$, 10) = "kanweg_abc" assert left$ (fileName$, 15) = "kanweg_abcÃ¥bçéü" ; 'fileName$' endif deleteFile ("kanweg_abcÃ¥bçéü.txt") endfor Remove endproc printline OKsources_5316/test/kar/aÌŠbçeÌü.wav0000644000176700017670000025426410634625706020055 0ustar paulpaulRIFF¬XWAVEfmt D¬ˆXdataˆXgúÉõôþ5þ\ Œ˜Ì!½ c(±†(j6ŽBž)m*ó+‹&î?ƒU7?Ý+×OQVµ?žD'XšIÉHŽ@Œ@ß3£K0B2"ã9­A›H2ÆM<)Û218A.`,æ%Õj0@!= ^ïù™ë ™þÚÿ–ù|ìðåøTÕùß½âWäüà^ÌÙÑAÁ¢áüÉ1¾Ð¶€ÏФúÖf¶ÆÙOÊËÀ"ÔÒÇÓ¿&¯g´ÊïÐ#ʯ*œÞ¿ˆßI´éÑòÔ.ÁÏ̹éPÈY×ìÒoñ5ééîõ í˜ílû–ûÞÿÙ4ù±ßeö˜¬™ #Ä0ã$x/K9L@10TA½Aý7ž&ì+Â4?88ì<«:Þ0u3ê:Í6WHNL3žC‡)‘-š0h7SBp2 'jF4?fg&Y0A#¤(Ù6Kl!å#tò‹ÿµµ é¾ô+ÒÅéˆëä–ÕaíõÞ‡áæÛQÝxÔ{âqÞsÕcËšÃÉá¾ËM¿¹ú®+â“®2ÆÜÉ1²d¯E·@Ä—¼ÒØ”¾ÁUÅôÕ‡Ôë·ÊÍëÏ¿2×Ðë€å÷ÑÜUç_ìRö¯ëõ‰Ú”ö¼ÿÿµìþ< N ‰ÏÕ•(…4ñ#÷#Œ6;:+P[ICM8?PéIû;ß-N4å< QJ8L8YAæV=CDN$¡6Ž7¡[s3_?l7{!²1S0‘#µ&Ä4|"ŒÛ$6©²+Ì tóÿBö DúÀ²ø'Vê:àá•êHàŠÚ©æëÛéçI½µçQÌ%ì¨ÒÊ$Æ%ÕM¸·¹™Æ}ȇÇC¨w½’ʧþÀó¶"±¶å.Ï·ÂãÅËJÄö¾6Â*åøÍ}à³ÔÎÓ˜ÑPæÛèÎÙ÷ÜîõôW öhvõoù+þHvþú ªù ¥S&ƒÔ*O4 $˜.‡2(=Þ'›-®>±@»Bb<M’>mK€&­DÒ-P:T=§*ÿN½:0v?÷/vH_*$B5%Š%?ª0Æ,ú=‰'^'@2D#n'Wðö:*°ý: û @÷ú9ðXò*ÛüÝYà¡ì çÐËÝûåªÚ2Öà‘ÁìÕÅËçÀüÏQµh¹‰¿_˪¯”ɃӆÁœ¯ÁºžµQËJÌmËNÎkÎ÷ƒÆÖ»Ì½„ÞlÆÊ•ÉtÆÉÕaã¹æWçMï¢ñìòºãRþô)î”ökýq'\˜é["-](%C&•rD.r:a:6ð.š5Oa@Ä:?`0ì?eDÀDù3„G“>&EË=`#å4‘1?,u9./³5–€1G4Y/ +¦&ÿ ™B´&È)ǧÌÉÁÙ¹d¾]Áˆ±†Án׸Á8¾ÁÃñ±çÖ×ÅNÌKÌ~ÈѨäCÚå:ºþÈ„ÓAà¥ýtáµéêçwééó+þžVúqú>øÃÿž l l‡'Õ.L;<¯=Ì3p6g(®?D*È7t6C>½A„6ÕZSSzA­Q‡H/PHEù.>:Fñ?Ž2¶NX$q;ð>N-Jf&(=H+LÇ#í(Ž!~&‡ó%¦H ÿñ~þû¸aê6ãÎý¯óPò›éÒÂæwéÎéÿÛCÖcÉAâñÕZÀMËðÐȲȪ¼Ò¼Œ¿2ÐÆ²Â~¶ñ¯Þ¦©Àî°¼É,ÅãÁ5¼Â=×Û˦â¯×­Ë¢ÐµéÇä¶Óeã¡ãYÛçîÈÝÙÛðø´âVò³ë ¡™´5¾tJ6>6+E ê ß(ù/6-xCs)ù0ÕE4FEæ1T7¦B§;wAn:Lã)H2}4;ˆ?¿Kà7BQª8T4-H*<3:7œ›4 KL(Óè¨NÓ÷„àþæœ bò Uûêî†êkñ³ëHçó×lÑÜ-Ò9ŇØÀÞÃÀÅËÉ/ÄöÞÍõ=¸®Ñ½¹ÐçÉ¢­ɸÉÿÆ»ÊW½zÂÍ˱ÙÅ.ÈÔ\Óg½ˆÆRÑÞÀðÐrÛ¸çÚûóÔùòMòtëðcü`ðì ¦gü¸ŒÑ$†¡-©-Cÿ"D%xÅ4?"c=?-µ-j;ó6*Ké@¥HšFIÒ?.3÷2è11C“)a5JIA4ó-”Cì?á.Ö5s 5‚/·$ˆ€%!4Z$Ï.Î #ÄTsÿ©3É Pð‹$ÉõæôrùWìúë@ê$åñ_èÝöß>éü¢¾;Ò‚ËyàŒÁQ´âÉ)ÙH¾Ë®ï¼øË›ÀüÎb°/Äz¯˜ÆÐÉÊÍQÎÁÄ1´Ù+ÍÆøÏäѨÉbÓeÎîØçË`ØqÝJÑÅBÝÜÞCö…ß×ù¯Kéògê;òB –È)H BRÓÞ.že*LQë*ð>,E¦9+H 5K"É6j1«-Ÿ@öI8i>ƒ?sZ$:TBwC’D;FZAl?=8Þ++44ï)ý/O/c#u2/ï@/Š xñ•Éèåd ÅËç•àâåYà}èsîÏãäíFý¤Ëw߂ܿÒdÒ·ÃbÂfÐ>Ë`ÇýLj«,³ª¾ëÂËÇa¹#у«×L·¤ËyÁºµaÇGÖUŨÇöÄ&ÌŽÒ”çñÛNÙ¯Õ Ò:Ôå ÐeóÊ÷nÞÅä…ýðÍùÓçD$úÍ qŽ 3 &ì%þ*eC€*{%]?d"ÊwF¼=¯Ia@CMvTR;¬/­M7<„K-‘?rMÙ0ÂDuE¥OW:ã>?-b<Š,Ï!l,. H8SÇ+^3U-KÅ þ'´ —ò2UéîRâÁë†ë¿åîÕµßÐÕ'ãwÑ ÖÂÊìÑÞ­ÙOÐÐݾÉÓ;ȽÊÆù´û¿Æ»0ž²×…ÁJÆû´E³pÌŒËÚÐsÊç¿ê*Ã9ÙÍâÞÿÚLäíÓ¹ùáìæóîå ßIèrì•õ¡ùZ”wáK?H#`*î>CB(K*Ê-: A²@š-ÚD[2>DµJâA“=;C—0X˜;k>B8RA;ÚK=:98ÂFd0Î ?r12#ê$B/ÿ,þEÒ;¶î~K P(8 Eî·÷ùöïxgüÏë¯×œò•íñáõå]ÍÛÛQÖÂá'Á&×ÃÈÁÔXØŒÖ6·¸îÀÜÉ’ÓfÃOΛÃð²ÛѸHµ¿pÔÍÓÓ¾®È¿Å]Ðk´CΪÇLÇ'Ù„Ç–ë*ÅÊì³ÔÍãÿ÷ƒä0òÀòDÎÝq Þ—Ä-Ÿ%þñ2#]Ñ wY0k(%"â))'ê=P8É1/G`D< O‡9;§E'QÀEKß@{[—=Ï8­FWÌ4é@&+:0U5æC?&>7ÈýÚ&L î>&²QH(Zw% }ö+žZHéÄìÀÞ ò·Ò§äiجâþÌŠÙóæ–ÛðÃ}¹úȵÒs¼ÞÒßÙ›ºsÉ ±½´ ÊRÈÃĵÕp·=´ßµC×Ï̸v¶…ÉÚ̸¾‰Ì¢ånÄnҀёã˜ÌWÒ?ã=ø<×Mêçä"ð¹êñm°òù|ê! a5þ¥ 'Z"N‘!Î,F$ܾ6"ñ4ƒA^àNäO·,éMØ6_8•;KFÿB:J-Aå.ï7t6Œ=sD`+ A;1Ë0›!Ç(ßA”.t‰)W&¾«"ІK ýù‘þ–ÿýÔḠÞü:òVÌ:ïãÒíÎÏËÚÐZå ְ̑Ҥ½º½B·ÿÓ’ÚÂ9Åi¯ê²£Ÿ…ÊʰÚß¶á¾ùÈÈÆÃÅ,ÄDÂÍ×GÁùÈݸÓ›¸sÔ¥á;Î`í*øòÅçðbñÔý‰ù!ñxüû‰òþO[ú +ú4 ®wŸ3;7¡1R78»FÞ! Má<ò4è?]FŸ1°K21?‰@F?_B&CEA¾DV1LøLFG*n+oGK¥>.\<ì4E!g(-455&þ¹]O*d  ¯Æìoš÷NÏù9újæþmåô¡æúÒÝò¹áË2ÕôÈ'ÅhËDÔÀͼ¹ÌÇd´ñÑCҰ͵°4½´ª1Â¿ÈØÕEզʶӢÊ4¾¦Û­Ç­½”ÄjÏåeÏÇÖmÛ'ãkÌ·íÿýåPÿeÿ(ù‡ týOøÄãžôd 5FÅ]&, óÚ>؈=0-°FfS°*-%4B*BËC:G@Fò>ÃNm>”>í@.Fî4#38<=¢CÕ>629Ï#t')*4/’$C(7,')¯_øõ-ä Ž´óIÅÿKÜÊRèÍ+î¯õñTàÈä¼Ï®ïåÚ§Ñ ÚöÁiÔ¿ÂÁ»<о ÂÈÒíºÝË»ÆÒEº¥¿ó¿#ÃZµ0°nËÊ ²cÇWÃ\Ê-Î[ØÝÏ1ÌÎðݤ÷ ÅÉáèJÝ~ê/ßóì^õŒÚ¼üþºù úûÿ8 ¸ ‘Ê„&m(.O!eðè0"4º>ƒ/¼2Ô1Ì5‘8=,›=ÕNsHÌ.ØADV/KpI>95z5vPŒ<œ4Þ(—;–:ò7ÄV>"˜ù9l"M''*‘6ÿ#@#V>úõPæßý½:}píöõÎõìð•ÝäÆëláÔ¨Öé× Ä˜ÍâÐÅÚ*½¢¾\Ä Å¶Éù¦>ϨÆb´½W¬8­:¸×²ž½9Ì®¼·®Ãý®ÌÒXÔDÆÛÎÑØ"ípç*áÐKÛÍÂéŠðÍÝúäRóƒðJê6ã 4 }À+ÁÜz#‘ *Íh(NAÒ½7c.$6šQI-p,àIÉ?¹9/ÁAí6=5¶M5J;EÐJÏ1;L8(6p;b0Õ?§6ަ8 ·+¼¼.ò%¯"Yˆ"ÂQ ë•2þ*»€ôÈú“áû£VõìNÛpàÀÖöÑ©âÇÀÀ½¥Ç\Åš¾¨»ÇØÙj©¬:ØñÃ9Ä­·„µ й¿QÑÀÊêÁ Ë/½»>ÒϽˆ¿5ä*·‡ÑYá]¯ÙÝïÎtÝ}á9ò8à«×eèÈõçуôßqô{úÉ÷diû´ñî É"g¦(°/°!2‚EqD9w&º:ý!FK7,=n?Oü?+9 BÞAë.XMÂ/Ÿ: Dø>Ä;Â1S;òCŸ3}3£+§4] ¹6Ë"±1–8o&|í(¦€ Ryž ç Vÿ‚ð[Qú?ÞSÝ¢ÆiÛùÚçµÉsô‰ËÔé‚ÛQÁmÉšÐ7Ë™Ñ㮋²Ê°Ô®wÞ·’Ò”²u¶!Î¿'¾»‘ÍO¹~ÍgÍ)Ô§¼Ò‡ÀžÙ4»ýÇÞßìï#ÙÒã«÷žæPåõ5átç® ²ýz ·ô0 Ý @¿"Œ 9 '&?+U4z5i/¼1Â1/y-ßGnGýS”E~F%MP2ê0>BH:øO/?^.×>Ë=².—?«+>7C.‹2ê*>9†#ö-£*‹h)ç¶¹ ' ²¥Ü¯ùØø–?âÐÊ ú$ßYß ñÉêêÙÞä¿UÏÐêÒL×T×.Ý÷ÇžñÒ ¹ÛÁl³ºÜ·£Ê¾È¬´¹¹JÎúÊ:×›³4κÉÙ7¶çÄ=ÔÇÐ|àÓÜÚàåç*ݯÔÙãáøìâsñ.s÷"ßC›Í‚úÛÜ÷, ©+#M#B11&ò:Š(«#ò*ä"¥)À:6%@2¶s&‡)s/\?n*;LX+)MOM¨8¦2â4ˆICMHEFQ2I>Þ<æ?¯R˜J2;ÛAÏ4b2êDÌ3±Fƒ35rER+Ë $:?b$ª%n¢%sÆUþ0̪ô'ãHöcæ÷ôNô ìÿî5ÌÃákï?Ôàlá(×ÀøÜÝÌUÓ|÷ͻÓÁKÑfÙ7ᨲÅ@´e¹ð¹ÇÉ3¼¥á½]ݧ¶e´fÙÈÒqÅ=Õä¾ ÔwʸǢÅTÞ+îNüpï䍿 èXå%î˜ÕùoîæŒK|K Nej"$'6220&Å%ú*Ç(§0Ô47/®2ê6öBªET“O¡QÐ@Ž4C023ÌGUB×+ÃOÖ*GÌD 8/ñ)Š>è,7!“5®ï!* ¤•×ubÿ‰ý‹ç5zñ:ú ß‘ê‘Úâì.׈ê£Þ©Ý—ÚlÁhí*ÎãÎ¥ÈÖÆÓ¿Ó”ëåŰº¨†±/Ã*߇±½ÆlΔÅ}¸Ç±ûÍÞ¼‹·ÞÕ·|×D»É±LÜ°Ö ÕßÖÛ±ØWï¬çPßÝï'ûZèÿ'èü×ñ±ÕœÂ§"±G&øZù"è4Ò 6&)‘*Ã6æ6W-~- Dq:µ>˜R7ØIG,:Mq44t: EQ7§>‚3¶2ø4:U& M\?î:ï1},$~,1AV2d$w! ¹0ˆœ/÷á ÉýÀôö"œøUï½ÞÿöpäðÛøGï¡ê¼ØÍÆGЉÕÓÒ¬Çι¹±‘»Ì#¿»«’ÁëÀ}¼êºŠ·8Ök½@¾ÅÑjÇ­¬@ßîÉ%Æ¦Ç ½4ÆÓ7×TÕòÛîÍØî%í6à,Ù]ü_è!ñsñàõûùé!ƒû5Ð)õç!Ô!†v{)÷9õ¢/1/;1a2ŽC8‰G/NÓP Ld,O~Cð.ÛA/7È+)V¤:(V¥/)Gè2lOúRm0»3 #‘Ì.)3íö"Ñ(6 0(dËñò!V‰öü<õM%Ðó„óâ èúköüÏ®Ñ4öÜEàˆè«ß±ÃÆö½TÙ[ЗÍíò?¹Ž´_­j¹Ù±Îȃ°SÍþ´öÎâÏõÂ}ÄAÅ4¿KÍÇÛÈÙIÑÊ;µyã8ÂŽøPé[Ýܧç=î—úwæHðìÆÿ ‘ü æýl iÌà ¼Ã´ <eq%ºù-D÷2eMk6á=@þ3)&ÖHÀ;0IÝIf;œ<£=><ãK¡AÀOF0(Ä"¼f,Î2y8‚ ï'ûJö/ù8ã ª! .ÿp#%àû Fe Ä‹èQðèî7ðAãßÔÊÎßä<ͰڎÙÜÑÇœÏØÆ2Ê¡Æ>Ù’ª)Í‹½Á·æåÈJ¾Û¶dÄŸê¸[»ö²_µnº°´̆ӚÑòÍÊÖfÙŽÔïæéâ^ÄëÏ¢äßêï.ݽî;ú?òëûJð×üu Ô¤ µ +{%ˆ.¬ŸÔ4“$áBFü0§:Ã2[;ª?AÝ0E¨9/\ƒLáZp/C8 9¡6;NY§?„I¡RW.ð3j2t+¶-ä*HDȼA¬#}Ò#W-)ÇÅ$ˆþ© K c+Wýµû¾û@£ ä-â+&ðRÝåêλÍ[íé2̚ƫÄr×=Ös»Ñ‘³”¼kÉ1Æz²Û½žÇ­Ñ?¦›Æ ³â³P¬w΄»ϼÅNëøÒá׬ÒÃãÄØtÌÑpàÆÏæÚŽåæKç·ëî=ë+˜þí ´ÖGîÞþIOÈÌü%Õ+9û-2õ,–=;E˜/ä'L¤C–I²B»8ÌCŸ(Ç={8ïF6PÇ:l;TDæ3†Xþ)žG_û2\1j6¶56Æ)š,ö !Dyé!búI+øŠË õ¿÷P‚èð±áÇç\ÞyãUôŽõ¡ãPï?ÔMçêÍÚËÂÈ’Ò>»˜Ï)¼Gª·§ÂÎľºN¹ ¿¶Ç¦YÇÆá® ŕ޳·)¾ Ñ××ÖÙÍ×ùÍáåÅÕ5èàÙ½Û˜èbã扭ú® ½ï‘øÙ÷]:TN31 H ç´,b:s.ÛsHá#¸5_=p: >•ß220X'5<ŸFûCT©GÂDóI63-ï<K¸7E»=»9€G7#%AR3x1y¢Û G1!¼óö¸úôFsPmG ìÌܨûáÏWí¤ÚjÞkÕoÔäÅœæŸÌùÊÊ'ÊðÅtá·NʇÈl¹lÂv·4ÃêÖ©±9Ø[§ƒ¹ ÆÒ Ê¡·GÎËØÇuÄ—À5äÉÚÔÊ4òëÀ6×YÙç^èXÑëùºøgムWËûø|4aý¶ ð ©+<Ý';.)‘.L©:õ Á ô.DK3¥4«[þ0à3 9Õ:ú.¤L) @Å.'Ct,)/§>+(f:h883==Ül+µ#U š#l2B6Z ÖqbìQÊYõLóúÚ]bþÝà¤ùþëâ—î¯ëÌçÖrÞÁÇ¿JçfÙ Án¼ÈHɺ¼‰¬7Í;´·§·Ò¾/Í_ÒÏhÄ ¦UÄu³ŸÊ½Æߊ°/ßÖ¾.ÅyÒ8ôøØ¿áðÃÖžââôÀèuë‘ì‚ì÷6÷8þ]•!{É{9¦#ä |ä1 Ö$+5²LH7ñ+GAYJxD–9_=E!\4È;þ?mMm*¹MƒO]HG*®7©A³+ó-ë,'>(%²0 8(?F'€5×<ÿõ.!¹<ö6Zn>6)_ ú'ñ ñepÛçàÃèð»Ý ²Þ“Üà”ß—ÏÍÆpѷȔ̴ËÎàÇÈÙλP³=Í%½ö³ž¶Ê¿€ÄxËMÂõÕÝÅÅäö¾š½ÂàÑä½Õ3íøÏßÒgæ†â°à¥ùLë¦öáç•Þ~7ö²þœKÚR †* %S "®«8Î!ž@)À@ÏAEHw&Ö*oC¦>÷@,3„HpP›;¿N]^RSþNA4^~.€ È=%é1s;Â/î:'½'Ä;o-j­2H(Þ"!äW&çüE!r$þÁ d½í³ßJð†Í™÷®òˆìàÓâöQ˲×dÅ”ÌÐÀ•ÎJ̪»È‚²YÜö±»ÆåÂÓŪ Î{Ŷ5ÌS°™È1Ï}ËҸѮXÎ"Ò Ç¡Â Ô»Ü—ËÔ®â@Û!Òjôºç~í¦ê_óÞéGëN 1 7סþJ<ùl"hH“ ôõ:Ñ&0Œ%s*‹*¾5È!´7àBn6GØ/Ò8*<&ŸF€xHÞ=]9k'ÑG²6]B±.Ò9#-L+1«2%"õ5¥"/8 ÔC !+¬š Ãýñ=úMñðïãhÚ4à·Ý%Ý=ä†ßÇÓcÑa·È¿c¶+ÍÛ»ÒÃoÄv±Š¿TÛũƀ¶&ÃOĹíÎð½8Á{À|º^½¾Ëª¸Ä‘¼þÈkÕßËÍêÐIáÂaמҕâ…ûîTòWïÏ [5.³þø¸ {±3/R$Dl3ä"l;Zš@*Ø2Í5e2 9æ?CBH=»B Rc3š0fA¢S?G™OÑM ,N"F^B4)‚I‘A79…Còè<&1HBi4]ËÞ¾ Ñ›!mÿPývü®ýº*íóëªñºïŠãþàÞØ¶áZäoâtÆéèDÊj½7Á¥Ê±Â´ËÍ}ÏSÝjº€³èÏÅG¦°ºhÕέãºå·½ÁÃÌ½ÓÆqÖÔÁ·ºÜÈ.ÒLÌCÏñæß%ëµÛ`ÚÃáÿíWúØñ…ú´ÿãYÿ¿ïV=ü6 sÜC¡šL9T8ü#kM>§2e.º0 ;Ø3É/3/i4ÄBÓ P‰;Ú-rE@3&9÷B¸& /Ÿ=Ý9Û4¦&Z)>¼†<—½ "çÿSšøG£AÿÔêþîîRõõð4å›ðä^Ëðà»î‰Ú”à éYÐ¥ÊÏ%ËšÙ~»wÏÈÌ«ßò«±½7´êÀuÑ»ý·w© ½~ÏjÈ©¹¾ÑªÆLÁC·ù¾‘ÒóÓIØ ÝÏÚÍíÿîÍdÜúëŒöxé <õMëä]ûáùå« ò*É#,º#¢>,/–- +r/ÇRh8]9ª:3=òFÃLê;B"DqQ2q,*iLŸ'L 3);-ó4'K7©7¿72„!þÅ;¸#T* í2ÿžLü|öÕüÛñ1ñ«èVÖøñ'ìPèvÑãÛcà{ÀÚ¨ÇRË À˜¸ÆÑ˜·¢¶ý·üÅÁ¾FÇÈä¿sͰª¼>·M·°Æ)ÀàÄQ¼wʿΌ¯;Ü™ÏOÕ=Ë0ÛðרéZåëwצädèÅáNãu¡Ûlé&–; às™ÿX 4+ *¾+ç2O.¡0,J03É6Û:®4¸N >i@”K_C–K@Z<’I†Yƒ=3¡=C`H˜1È=£5à0®d>X=dC[.‹)À8I@Ïè ëC:"CÄà&°óú ,zÿüt÷öðɶ×Ïîá>Øë`ï$ê„êfé\ØðÍgåuЌҬÊÞ¿ÔÃBÌ{ƈԙÜBÇS¯2´ºjÞWÈÙ¯TÍŸÂ3º¼8Êü®Ê‹× Ú »ƒÃtϨÑ_È¥ç+¹ÑHÎÒïÏ¥ÙÎñ¹ë±ö~ëdóiùÒïÑùEý ÷åöDøº¦ÿü53/&á+Ò/é/d>¿˜2c<Lt9ÌD7*B6t:ZT.D1‘17%¼@Ê(³0Ar4ßE]C[9D7!#/ –I,,,™×!ê8C3î üÙ÷„üï –õ>ðªÿ=öÎòßîOå´îªÑ›á ÖâÙßÙËËÃÁ„Å”É꺛»'Ì]µ×‰ÍåËE¾È»5Ù"Ä È¯ËlÅ&¶VÕðÄCÃÑåÜ,áÑ‹ÍúÈÔÚwÚXÛ×èåãµÕrÛÏêþ$êŸý-ëÜõ÷ôÃ'òÜ! òŽü†¨¾û mh0(&*ý<$ÕB‡7.0W6iC'08]Ô<#LC?°E¸CïLe>=<±'K5 "-6ø@†Q#:IVœ%ë+Ê‚%e$ ')‰"€ l)¡ Å0€c . á ?è÷ùÉæÒ÷åYá\ñ’áÉØ<éó}Àaéc±ú¹åÈÔ¼âÔÅÈCÇrµ@ÛH½Ë­˜ÐN»-¶ƒ½Ý¼·ÔÞ¶¼Ä}ÂÃ3ΔÄÌ®²âÍζÎÃÃÖYǸÜïâFéÔÓã÷=®ð¥ó&ýó—ñE) ,ÿùþ$"y0E/Ä! «5k#73Á;mF÷3U@=âRÖ0VA¹@`J“ERB3lCµ7­LÿE[?T$ˆ3ÆHÅFsA”6_Nž4„Iá&&(2ø=”9~"Ü -;Ú% 7!Rÿ| ú2õûWï(ð÷øDÓ "Ê©ÝÔlÞDæRØPÔÝÒ™Ì2ØÿË„ºXÊĹÃiƾÁ4ÔòĽ¦Ê¥¿×Êî¨v¯§ÅÖʈÉäÅy¼mÛ‡®ÆææÏÔèͶ҆ßÝ­Þ½Ø3ã‡ó0ìÍî»X xð±ñ÷ŸBËÒ D ØØ A °*$›&û-³(É,XNWHt2ïDMDFT9+Eœ<‰F$3ƒ:J¥T,6æ9Ä:ƒ=‡.Õ-œA4-zG& Ï=5*8­>Z4‚/Ó+%iTü+¿ N"ËüÝð–ìŠ÷æÒ÷xèøiÕñøî9â,Ü¿óÎà ê£Î1Ú®Óš´"´Öž¿¿Ö&Ũ¸:ÂdÖþŠ­ÿÃm¹”µÀ¼qÏãÀ,Óн\¼a¯tÅ/Ç‘ÈÍÃ(²)ÐZâÖöØÉáÏ•ìÜ ]÷ê*ãâ*é—çåýðÍý¶ø™ Ô .·-š*°,a&RGã$9:Í(¯)I8H=ÿP²@ž?öAù9t7IOiM†88G U¯Cõ;Þ$¿<ôMX?+ CI*‡7î-Â(Ò+Rû$S#…"~&÷ ­×ê(©® Üœüoò˜ÿÊíÁðáâÞ)çÍËìæÌ"äÔßÔ[άÆÍžÐY¿£Á9ÎgÌ»´Ø¸±þ¾ºÎÄÀŒ½5Ш¹(ÃF²ÄÂݹð̉´´Î-Í.ÑHà€¿¥Ïç*Ù#»ÉʽíÅæ±ÞÑèç™ìåýÑAà Ûõòÿd"Óó’^ "V`&-Å;h1®(ª' @µ'‘-<;÷"€C=&:&.8ˆV)žCûfx);@ÆPÏDV–>=5³L¨JÀ5;©*3õ;/6“0%64Z%J@&¦È*wºû2"Ø F ‰%Ô¸á-æÃ ãñ‡äðäúÇ4ìåAÔTÑ“ÓÐÔÌ4ЂÇŶàñÔÅÔrËÀ¯«ÌŸÆdÃlÄ*É*ÆÃ(ÈÂùÀAÅ<ƾÐÑÒÊÓ6É|À¾ÖÎHÈ]ÞÒ Ã2æôÖqî…à·îÝ÷u÷€ÿôütåûòHîéüY®­ýyoõ‚W-è$w!þ#J! BÇ8þ77š8/è<Û4ßS‚;€2@Ê8ä1D2E¹6\Mì8bF 1É<¼Dã:õ-t,Ó5ã4¯. 8Ã,ÐÕ+ÈÄ/ ý’ÏdêûÀ’ì„ç¼¶ ‘ÛWïÛìYÛŠæéÑœæGÑöàðÛ;¯®×WÖúÃ5É¿ ÌwµÐË™·™«ÁúÉó¸øÆÆTÉÐЈ¸^¾)ÄñʺÎ÷ÄŽÑ-ÌÙÒÂ…ÖeÙYÈãÍjÙÑ ÝßñpáÈäæøí.ï&îýór÷Âüâÿ®[þúo (î.›…2¿.ƒ(Q6_8Ù2´)ÄB–2ô*ZVg]OHJ>bFÇLì3·U5~J‹[ƒ2ƒJFM–B¬MÔ1œ@g?b8i&)eLö6Á&÷._!Öx4läSeí1õšè¸ ¸üzô²énó£ë‡ä>÷¦èkî¬ÞÉßLÛb· ß×àôÕ ÍÔJÁÅiܰCÏÚ¿îÈ´€¶¹»ÐÓÀZ®^¾0Âô©3ÖóÓeɸ£ó™ÑQÄÙAÜïÙ²íEéòÜçëè×*æ$éþÅ ZUö²à£ðD(;ú2Oñ/†ò2¯"Î-,U0í:p4@1»ÜÑÑjÓÊÌ›ÍÛ¹¶è* ܗüÉêÃóÊ/ôÆÎçÚ+è ôR+¡ú_ ¸( N1+052ý%Þ,14l?O8F6oNŽG>=­RŸ1Â\„1K¸J´LSCœO*,zBž6S6ºJ~=£-³?;¿4i#*+£2pî+þ¦ Q Æ‘ W…÷ŠÆñ\Þ‚æ ödïrõ“ÚˆÍÄß áyÚ´ÔÉK¾%ÎZÞS¡øÄÊн”®ÝïÀÑÄmØOÂ±Ò À}ÀÛÀ·¹Ç­»ªˆØ»ñÀ—ÕÍ¢ÚJÏfËÑÁêÜHßsÒüðêçÊê¢lâ öcþe @S†Þ÷˜  ,ó,Â)M3 g«%[!/0sH`C©Ic.È6p>¯5®X Hj3–BåEA/Ñ@x.Ù9ºL#6RFð,^:y;I6ž0 =ÔUj9¾, Ht%;„. 2Dç.ArZöê%“þ®Öýéîê;ÝõéŒëië”õÓþ¹Ô+ßHðçß;߂ۘå2èÓ³®¹±ÌూÃúÅÇáàΈ£Ê3ÂÏ´)¦KÁ—¸®¿MÐÒÖÇ·ÈDÕÄÚßÕBÕ&ø˜ÎÃiÈhÍ•ÕaëaÏ^Ú\ò®FÒÄàké<ÞC t-¿v  J*Ï¡*´-0!«Ú(Ð)-39Æ9–4*K8:6<•U3¥5á6¢FnF8k;J:«=R)4ÓI6ÁB#8e,`:x$ 4=;€#“#.,à…·cr/q$­ Ê™u÷7×ëþãõçíÅþ*êF×løâó´âCâºÇÍÜò¢Ï©¾èÝ¿MÖ™ËYÊÝÔ¼Ù©Áv¾íÄ#Á³/ÇÉwɪ±?´,ÇÕ›Ò׃è÷ÃëÚÚ1ϼØÝ'À/ʱæ›ßaí›ÝËçwõ·Ø·óJúãù ûZòÁ ÛO#4í"× 5þ®¾Ú;$š'6è–‹,»-Œ.TM5¦L>z?Ã?¨2¢G=Kr@Û:lKß56ê9L6{KJ/v,?&q<ÿFø6¡w+; U‡"Ÿ ³ ÇGÞQPcîdÿ*÷Øõ.ùŒê­÷ŽÚËø àÏ\ÞÏÛ“ÕÏÖ³×ǺѼ¸ÆLª^ËaÊŠÇl¿’¼Ë£ÀƳÈäËó¸÷ªÙºµÍM°ÜÃÈÛî¸EɨžÌÍÕ^ð¼Ûäß ÚiÔ,Ô3ÓYçèÎïöhåŸÿ+øŽ ÷©Øù(ñƒO†.#B&Ô&u('Ÿ#_$t0¤0ÈAØ;YHg0´6EPÏ;O4PBÔ˜@¹?1DuE»L(,¿A90 KŽ=šC»5ÿ0?À?@)Øc4\£!ð'Ž m>Ù âÿ¿ó-Àè¼ÕìêÍæ³ñ^Ø%Ý AÎTñ¯ëRÄÏBâðÒ;ÓIº ¾ë¹çÙ¶ãÕ‰Êb»°u¯ûÂ`­µ«&°;×S·.´ÇÑDÉeÔfÌWµ¡¿ªË´ÒJÃȾáÝÎßËãÙÚ:ìyîÃã`åñNëéò=ú5ûN 3ìùø A  Î-CÈœ$àÐ6pš'á09DM:H?:4¬=E$ß8‘,ë?%I»OÔF>M>Ó9â3æ@YK„6Ø= =X3ºË@Á>å:•(Qõ9Ç)"r#"õ Zzá[½  §úL¾û¸ü™ûŽñü܆çøÔjêrÓ:áSÛJÞÓ4ß±ÈYÎöÏ$ËvÇÊÒÃЃ¶CĺËÒ¬QÆà±¼¼Ü·é¿þÎÞ¬k¥·eµÆEţȚ½hÊ!ÈŒÝ7ÔÏÏÊ?ã5hìJèÀçbúåém úuñ¶í¯ìÿNïS šo ¼ A¨+ÿ€"(v9Å.t*"=é9Ã3YIEM:D6ö-:¤;¶Cá9P¡9¡H¸(ï><'®1­::@ÝNä7*Z 97/Ÿ8ò¼-â0•$2½Fã òÕ `ñ#ü÷ï†ÿ8ÿ]÷Óílã)û5é_Þ´Û4á:Ü>Õ€Ü+ÒÁì&Ù!ÓjÇ·³iÍrÂ2ÀÌÄÎÕÈœÌÖÄ\Æ0Ó¥Öp¼ÈÆÌӢܜ·ß¬èÂ1Ú6ҽʮÉ#Õ(Å‹Ö.ÖrÌÔÅÛý×ÁضòÞþFÖ=øŠöz}ìKJkEV#Ç Ù/œbã"ù1Å!ø(¹8õ;a1‰08öUF4P@P/0 .á3´')%LL?6AFt>eQIð.‹5ä7PC¨,+(A,¥'¶-$(5ê 8¹ ÞÚþ#4r ê>ôÁö–ûxvå©àà×ç=úoç˜ÔžéýЃ٘Õ1ï.ÆÔÉ>ÅûшÊÈNÇÐÉòÂËI°Â»©¾£ìÊ´¶*ÀŸÍ´ºÚÒÒổµ¶Ä/ÈNË<Ô'ÎçåÖšÐeäkì@åøäÇâåÚ½íuö#åžî…f ¨u åþ  Z%f;}:'M ä4;¥-?D3øWÝCíW1G¤<´@Ì@û9Vh1ÙNçChIT=à1 1ÝQ‰0Î0“>˜#I:Ç+§*Wˆ-@)P9 ú w ‡ Ù° (!ßP÷³ Xý@ð’ßcì…ûZáêæ¼Û6ÐÐ¹Ö ÐèìÔ½ªÖÐÑNÕ‹½Ö9¾pºhÄOÁsÉD·¢³kÎ.ÐåËRÓø¹ µ³®ªjΈÕÁ!¼Ã<Ë½Ø íÕÅÆÜVåõ ãµÝ¼ÌÛÞzéJéî7ëgðÊ)ñ°ôOvŽ éR+‰%™!£ ³ƒ'­e9@õ"¢)ý'Æ=8#à6:œ l<ŠHÀI^2RŽG©5ë<òE*8Y?Å,Q;øC×UÕ6H¤/Á?2+¯4]: 2…$9ÖÀø0 ã&ð…ùÜ$ nóýyäTÛØçC÷!Ü”è9ôÄăʌ×èÕÝšÈ9ת³<È1ÒÜ×UÇÈÆñÆÇÑCÎ*Á̻ڷm¼8¶v¿ «ŠÛDËËÓ·sÑ0ÔÅÃHÃ1½>àöÏÆ”Ö>íÐ×îtëÒÿ3ëßý‡ñŽîOøÕ ž§‹¥öþÇŒ-{$@2½&(é$S0 )†;Ü8$É+®>K=ï$¹<·OaKB-°F1OíK’>¸"KÏ)?P327H(9š,€]3P”,±öÝçV+X¯»Ó _òæü. “?ûõÎýmíßétÝéù¾ê@àòí2î ÒE°lÕªÓzÔ-ß÷°ÞÄÃÉ È´ÌÃÜÌžÆ×ÆÅGů¹ÎÍóËúÈEÄäÏ¥ŒÈÏÞ–Þ÷¸6×[Øaï,ïyíDë®ßAüTâùï²ð¨ûeúDR9´’m ·q)×g/70è/Y0I"ù,g0±.Ž%ŸPÏ+pLº>µ;ÿTTÏ]3B;?©U08m>RBÇRI½7a‚/9%ù2p6¼+=Ž2š!‡"¯J Ž-¼ £ 3ž ¢úþù¬ù0ì ìFóúïŸÝ-éÆö‰ãMÂ’à¦äÒP¿àÞWƬ՚ÓÑË×Ì¿$¸„»ÁŹ»õÙÔ»:ÍêÌõ͵+ÖÁ¨ÝsÚëÄíÏ Ï×Õ°ÝTÌwÎ]Ú¬è°Þšë¤Ð ì¢ý÷ô÷¶äxóÑÿÉý|ÿ¥ñÑú^?#Šâ \!,Ã#/(ÍAù>¡)¼6>3>4W)+6;#5X¡>h:‘FOQu6‰A¥.|85Cì k:< -ÌMd$p-ÿHÁŒG;:ª6!,@ } àO V H$Â)üªûô°êõZû…Ï‚ÞLãðä:ØæÍýß}Я˃à­Ññáí¾ÄpÏÁ·í×$²Ë…¸µÉu©ÜÄïÓôÇЪ༢Êf¹,²Œâ² ×7ÝÇË`ÐÆÙíÇNØEÐnàBß(ÏýÅ“Üˆæ Ø”øË÷:óIúsë‰ü¬ýdø |î–A L+£)¡Ê0é0o/~!¶ö4o"K<Š.¬:‚B6:B=åFc=)AÃAÕ5Z2a1º:˜S)ÈKHŠ9;V=i>‹5G?µ+ù$>U.Î"Y*¿ÿÉd:¥ “ˆðÅ qù"öÿ ò®þ`éÀïóâuÓûåØNÓà׸ËHËJäÉÃ+ÝÌÊ÷Î`Ç|À5Ç ¹·ÎÕËYÊužd®'馮 ÑàÊð§Á¤¿èÖ¼Ù ×1ÉÀÕ‚Ô ¿VÔeËÊ ã<æSêóÆú´íDáså…ñƒíóò} nþ a¨"`?`­á?p"'½9Â+4X&ŒH;b;ÖLÀ0ø1õC3DÙ(õ=:>ó=?A9J5D´*ÚY*Aé.J1#5áGüAb&ö× 0Æ/óǃ"°1Oi$¤ ÿìÛòa‹ jíÉó¸ðà¸î î[ãÕSà_å°ÙGÓ?Ê%ÔßÀC»‚¼,»oÒ”ÅæÑðÆÕ„¬˜ºÔ„Ö»ŸÆ+¸8ºîµÈvͲ¸ÀÆÕÒ“áÜÉœÊðËå½7Á‰ÏÈ´ÞýÛðóÙªí“ÖÈãÄï§ópôåþmüßNù‚åüzó¿)ó¬3 ¢ Íäâ4%Ê"= 2é1‚,9æ,CJ:A .¾9"ý4¹>vE:O®@ð2äB)X>4?~:g4 /ê=‚0í"oFw'˧Ý,^û #Ðá. M&õHþùóÝþièFï“õåí›ê+ΊíuÐòÛ-çïÉÖÍè¿OËYÄ€´\ͨÔéÆÓǯÃÅ£¶×¯Ö¼’Ϻµ¦§Î8±¹Iµ‡·?Ç•ÁÄÄDߡ˶уÎÌÏ^ÐéhÊÈâ{åÎð(êÕ×®÷žý×õ,ë þÊ s ºGß§À%o!Ø ýU!­)°/Î+ßÑ@Ê?;C6Æ#ùDÚM%DøAË9ã>þ?X5ÚX&Gg8`:Ö5 J¦>7 7>Mæ4¦(¬BT-Ü$,%;Õ* +\ŒQ$Ä  vû® >°P >ÿiðbò:ùVÚfدãÅÛÛå‹Ö_Êø~ãÒÑÑíÁ‹ÅÝ:ÊÄħÈÇÆ ¤ûÊòº Ó ¼FÈÒ@ÃyÉ Ï<Å3Ã;Ñ2Æî½ÈüÈÖÞÞ䵄ØUÕ£Ç$ÞÎö¦âÇçÍû“éåîësðZò½Óçç À¤ ³î­$6G '$l>@Þ:R#Ì7ó@î"®3H3±Dy,ä3 FýA EýQð;9YäK4Ù)Md.ëÜò«l÷½‡ä~Êq<,‚ö;ÐÆ:>!Æ*U2i:|>Z>ÿ9òN›7ë>Eª@ú: 5_(\CÔ6§9ºDBG<Ë] 5dJC>¹S4K8í!á?pC3$/œø+² eÎuT+wóÍäñtþ{ñ ·ü×ßHé¬ó‹ü?Ù¬ÕäÖ³èS× ÐòÆÁàÃä«Á˼ƒ¹]³—¾Š¹9Â"Ók³‚¼¿«1Ð}Ð"¹´À)Ä0ʱËÎùÇfÊbÔſɟÔÍØÔŽãåýÅïî*øÚùmàñûÛëNMè0è3ðWÿ3  ˜¨ ?8Ï"j-%*¾02A~2),F)=X-Æ2Ï5<×7)DI@Õ;•?XP¿BÀ?0J P¦Hð;àQ:BBN;=Z8èÇBË'uy$ç$ƒ¶ i!4gÕ·ûø¯õ¤ IìÉæØøTÒä9 gÞžàÖË>Ønß4èžÉKÕ×ß̶Ê竼nïÐq±ņÉñĨ®Ç‚¼Éžà¾á¼+½?ÃPÜ|ÖkÏ+Ó‰ÆÅ寒ÌQÈaà†Øñ*ÞÙú<æ>â©é øÚæùí±3åd ® @ü*¾ ¶X g0C'$(¬3–+ (+fAÍ-»%Î4d>Ð0ÊT$K=BVD8DÓ?„7ÉEáA_?vCKˆ-™,Ê$ª*ð3XNú4a:J1ýº-¹4c+0.r "&o”н8(ÃÔñRù£îñïŸâˆ œëç7íûáGáß!ÄìÖ2Ï£àÏÙjÌ‚ÄÔÀP¶½÷¸(´”̤¹8˵}§È½HÁN̪·-Ëq×^ ¼Ù¼ßЫâ…Ó*½’¾ÇÒôÊÏPðÅã9ѳð>غñïhð([ñ€¡ó%*à ´+,ÿ]*Aä$R47Ë&ƒ)Ð9’RŽ6ã:,IÈ)‰;VOø+BG_1¢8ƒ(Cþ=I?èCv7¡9V=í;ƒ=­0VA$'°·£%”%’$ë OGùˆ‡7ìïïúQhøå÷§øêVö¬ê ΘÝ,ßÊäþßšÑÖì졾VÇ•ÃRÎ~ÄHÁLÕÀÅVØž¹Q»ÅÂH´"µ¢ªÐãÕ;·ƒÀÇÇ÷ÂN°¿Ê4Ê2ËôÏÈñÂÓ”¼ßÏûä–ááìaæ:êrárßøÓ÷—÷©ã®Øúû"ZýúOˆªwØ3).ç'È1”2dK .@7€8=1x0oJ[=J5–A€EKDº9¹C541I:ƒQ=u,@DÃ# ;³>QP¸:&HÅ.{<‘A¸#h-S "TÕ k%8úot$ËŽþNá3 «ãYæ*ÿ¬ñ{áô¸æÏ7Öôæ8Ó†ÎOÐÓ ¼ƒá®µÍÂ+·Éß„ÈãÅ"§ˆÛ[¥ãÊ6ÕÚ®vÐHÈÅö¸{Ƴ¹ÊÆžÖj× ä×˰Í;ÑåÞªÝÙÖrÇ?â¿öñDæcãËï×þÇÏüÑÙ×"¦ Ae ‡ ¯#iæI*ã=íFG9&¡.F*v4]=?%>åFEJ58+8ñOQO9>žDjA*9§<øAByF×K®(=&}1@!Ï,7€-1IV· ² žµãùïF ø ë…÷6ëÃæòçèãHèGÕØÞÕš¸'Ø͓֗ÐíÇ˜ÃÆËå·”È9Ãù°ö±¨¿ë¬ ºâÛ׺¾Óp½¼çp½‡¹ùÄ>ÓÉâã¼Ï´Á Ñ–ÕuÛöÞ‹ãwì:Ü­Ò=à±ìçñ‚ý;û•YŒjý ã-¤w;'ç´,‚m:¦0‚+å;í7ÖPHl:Ö9Î7ÖC)DÙ%’Y)Xž.ÙIN8ê0DQjJÁBãI*Gû>86ž>"7ú¦/{%…5JÈ*§©( (98d#ôø ß-1Kóø é™ã  /ëºôØ$öà+Í,ï1ö:â$ÌÖÒ;ÆùÈHÆ8Ùw¹ ʾ“¿*¾ÿµ@ÕÙØƯ¹ ½{•Æï·—ØËÆYÔÊ]Øó¬%´ÇcÅ4à Þ3Ï Ù.äšÍöÜÔ÷Žß½îømø^äèà^+#ÖøÃ&0  FÚTj'ok\,/%É-=9ê4­9n9…)¼.ABë8ïR?Së@“7aPÎF”A^E_aÄ4ªF57©5E0Ÿ&§)Ó/‹,Y4¹/Ô,jÂL9j  '@óØ +ü õŒIì¯Ù7ã•é»ñiãçÞGݰڽù½×ËÉcÇPÓ¶ÉåÐÞħ½ûÄ Ìô¬Ï–ÀzÏØÁ»4±ÓǺ½Ëà¶ÅÆaÏ<±W¿aÌá¼ñÅŒÑʧöØKåÎåìEÕ…ê>ÐbåÓæóÕê­ðôïÛü8 ÚWLá "÷96“1î.M&ÀAæ)@/}š<Ç:Ke@¬?ºÉH–]0ë+a5ž>ð+§1‡>–UµMšXÈ2U+¨Q§43.C5›!3 A'5-¬ ;’c-™³á 1¿Ö C¿ów ”û)óAÐüä†÷ÿÑmÙóØ–Õ9æ'Ñ—Ï_ÆìͼÚaÀ¸ËöÅyÆSÎÖʤкÌnµùÇÀ8¹ÿÀ;ÉFº¬¼’Χ廰¯Ų»Ý¼ÕÙ_ÓÕuÑvæäØ9ÚäñÚSØÎë°ÕêëîS÷Œ %åˆýe_3Cô3 IÍ!3ã'#  !á!c.ù2J.F·$IdH¡HT(:_G:í9TE7r%rH’-'??4è90E½@(–C™F® TÏ;-­:! ¼øôÖ PìÐÙêü'ÿÐÿWðç³èÀèïÓ+ÚãñØ(ÖÙ…Ø ½™Ä̪áöàìÚ­Îa¹çÂkÑéÏÚwÃWdžÑQ¡÷²Ì-Áã0³ÏÄëÚz¬s» ×LÅo ÑÃ<ÆÛȱÑIÙ*òZìl÷öí˜øWàÅõMí÷Wú‹û™×ý<,_s'i1[$?1ù*R!…)E#ö-¦7N B8LP-·/rIóM‹50( :?+6=¥5x,×BJ1ÂW¢A/G …/ ,åAC.æÎ,È—<+º8`ž £þýÚ‡þgõ îùšàøâQïõïË2ç4Ý{ò»Ý­ÑÊ6ÌÉSËêÈ ¿øÕÑÒ¾¿Ö˜¹|¹E¦ÅÐܺÝɇÆÛÁR¼Í¨wÌôÃÁèÏÚÃ2ºMÝ…­õ¾å¸2¯âÒ¸¸<äÿõŒêÀèàño÷ßÙTî#ß òLññç€ó^ô` óúG×!MÅýö ª?è)*%½(¹½.ž,'’913>ª-¹7‘0Ô6: @q@^5î@ï8…T¢1þ=Fþ6R;ˆ3Á9s7-08Ö<Â3O.Ë, ï ò80þ"Ðk DÎ&ÁœþñøÔæÝÿð™þáê1á]ÝÕòsãÇà‰Ý/ұиÕñÁh×þÈ$¿°ÇÇ4¹u´Ñ_еj² Æäµ¼ðÓñ¶ø½êÉ4ÕÚÊÆÆðԾ¬ض¸È ÎLÓ£ÚgÕÅì(érãÒ÷ÝñXäsâi Ëü¸öõóªsd Rvs2@ì ˜_ø 5)ô.H905%&Hz6§1 8{3p*ÝH9§#d.ç81OD±H…9åJIþ ºHÇDFR4Î6²8Ç:"'(#/.÷ñ R³-DšÏJí%n>ç9àèÝÊôÙè©óéEæÞkîÊRêÉ~×BÁCÏ*Þ]ÞúÓÈ¿†Î'ÈËÌÓ±ÇåÈ6űū¸©ÀÖÚ ±¦¼H¶ÉÏóÈ ¿¢½Å*¾¤ÐÓÖÔÏöÎøÙ¿úmÝZá>ÙGì]ÏÏõÅë!ìî „^ú1Ð?B(6‘ Á!¡&?+¯0H*+ä0O*µ4 GZIÑC#S…OcP±2)gMiQ|8¨@7C¸/Ž/´9(WD{5¦3Î<9ð;)7… Å&ø*g H “" ©…ZìèüÑÿ!üÿóÚî9çæïiéê¿é¼Ü»ß–ÝÞüÉ7â¬ØÜÁÁ¡ÑᥴÙ7ä×RÒpÎæÇm´™«@¾ ¶¶ÆfÁËÅŠ¼dÿS¸6ÁTÑ6»Ï±{Æ–Þ×éÝÎpʾÒuïÎäëÜVÔcædè4òëûzù¹ýí>ëòALï[õœ)ÀÆ'#ïtá*¼)*†<06169v9V2ë7ÉNóI-D4A.{7:M2I‘EÖMHùI“C:.+;*u=!=0:EÀ!S*¤F¦!K½!“5c%$ý © uþÖ ¯1Ðüý ß÷ôFâ›sôÚæ:ÒœÙe×ϓׇ¸¶Ò©¾ÛÄ&ÙSÐ[´û¹ŽÄ«§,̃Íûž[»cÄHºˆÊ\¸’¯®´x¿úÌÂÄZÐ÷²&Í`É7ÉSÛ&ÍNÏ3âÃØ‚Õé£Ù`Ñçíì¬é âAó™÷)I”üv ×Ü n³M+F+.°!q$Ž©1J:(2î5Õ*\7ñ9'*%_?ä2/AãDãL );:tI‚E´:fS¦RÝ7»@•Ø;?5:.<8îEÁ¼*>'¨; ¡ý¨ n‘ e 7æÿÔòøs÷$lôÄþ î?Õ†êøbÛ/áÓÞxÏMÝZØ÷ÄT»ôºwËí¼ÌÇ-Àg©¨·®»m¸·®´å¼¶'ÑeÂâ§ÞÂCºðÄg¸ÕÇ2ÃÍ<§nÒã(ØÐ+ÜÎ÷œØíôy×ÍÊ9ö“מñÝÿcö ï]ìi÷”Þ¦!y'o8<¢'}%%#$@3ý>‹=6=›Oj/Y7˜—)->JD³A :œC_9ª@©FJ=VAYE-G9íTâDŒ9¯FF=qDt/¹1Œ&®^$­ä0A¤Ê%ó­$a´÷·5õ êMTð$õ>ùôìêWðÜçÛéSÙˆÒ’Ï£Îóœ«ÙHÃÈÜΰJÙœ¿[À,Ä)Ö*ǘßóÇÈÇXÑÐLº¿ñÈ=ߌЌ½`ÀϾ³ÏpÁcéPØ ×/îïØåæõçáãð4÷IýI Øö_îs÷ÎÜвô"< nÊ`/á#Qgö6k0BBp@–5Å- ;Y=åF„Ob^oEx,m,®0L2\D¸<Þ%á0j/d8C#471.ÈÄ+j$Û8µäß- êûxúwõøÂõ¯òvå;õþîDß”ÓçÖ¨ÐÌäéÚßʰèaÑ»»˜½îÁ÷¹BÀjÎ𹟺|˯¿â§¾"ÂŒ¹É»^¯©ºW»~ÄÞÉBÊxÇ××ÑÚãjÆ^á ¿âàÂÑ^ÔÔØ«Ö÷î¤úJèàòÛã4ê¿ xñ‹¦Ùä ƒÅt `*f 4%?‰ B6ACw5pÀ/˜8BF/3ÈA1î<”:’?«C>¤;'<¾9Ü?B<î?ª=4#8x0+= 057ö(T/a/@ð,f4Þ*2 Àä%)LI1ðK‡øû á{úyûžÝÁÞQìüÛ¥ÛÉÓŸç8ãêÉqÝxЉßÒÆÃÀ±çÉ@¿2˪Æ~¸{Ы¹^ÀtÌ›É9ÙÍʺø¯ÍÃyÉ@Ū³ã܌ҀݿÚÐá×#ņۃò7Ä`Áÿä×ï²ÙÕå†ìÕñ”õ»øöyîú®ƒ3‹cR;"NÄ!²&1-¥;é=(Œ5i%,>˜,y:×:+E€8á'=R65:ë9RF-Õ'‹R6L3Þ;V4¶4%¬3²;†7+l)o(¸Ï5ž€ë -ªú©Qèrkñ#ùX5öyóäæí䣨¬ÖPÌ9ÜvÊ Ê€×ß»üÒ,¿F¾©¾ƒ¹K©nÊ(ÍÁÏ9»~ǵ­».µ5ϲРÚ'¸z¿¥ÂøÅÚÌôÀÇ·ÓXȆÐýÔÒSÚªÊîóÔì”ÌTã ¬ÝÕðüàhyù…C mï}ÿhÐk¥8Ê"}3*˜ ”$’881¥7Ç16zFD9þE`+¡.•C•B¢./–CÊ0o<ØF=N¼I•*:mÚ¥+“$Á%ÂFË8Þ+3Bê)d3•/t' "(N \óç!$|ëv!û HþÌ*þÓö­é[ôôâIþüãˆééíä¿Ú¬Ó<Ò¨Ò„¿ÍÅÍ×8ͼϣ¸ÅÐ>ÉMÀý­ãÓL¥ê¿¬ÀZÆê½O·=ʹ¶˜ÁÅÂÃÜþµvÃ/À½Ì ÑTêÜ›Ò÷¾0ïÓÝÿ•ÔAï—‚ó– âíúˆ÷³äþÉ®íŒØ&u)B ³!‡?1] ?ëL,‘(.ùB"2,«DM5Í?}GžA…1<| yM,<^1±94MÕ=µ?·Íª·÷âqÃñ¹T›»kÂ=ŇÅl¥À¿¡2·˜·ÏÕdÆ…´È2ÙÔÂ)ÕŸÀÚÙÁ\Í=È/Þß¹æ%Ìòí3ðZócÙ/ù*ÿ³ñ¦ï’,øMøoà›ø¶Sá0IæÜÊ01ë-»*(?v05.Þ8ÖT+<æN?°7 LhHKJ¿*ôE¿+p9•@4=[Hk7Aq6 5ù2 9‡6æ8®.ü1C,#2šŒ"™#· ‰«þ}ý ìõÖôÍ÷©îõªýxõœðÔsîDÝ€ï8ÑÓ¼Á{ÁQÈÎÏ¿f¿Ðâ²â-±Ìt¼ÆÌ†®ôÑ͉«ö¾"³9ÁŠÏ¾˜Â/Èß¾}ÊÖ–Ð4ÅŸÒãî4ÚCÜ5ÙóÔˆßÃçIâßðìàö|í éËñò¼e ÒåáͦK *ˆ4™)@!°#”){?ï7W4tGc4¾'E@ÿE·FÏG‡R=O.òBOƒ&B,;­4"='&¿'å65·)s9ü%Q ¹ xo)2*#"5 T |=m *gÿôàò)ýo$³üêŸÖ|ǘßäÉóö«ÞŒö×¾DçðÛäÎHÓÚ˼˳ÆA²ƒÉt¯ÐÁÙ¸³ÀõÌ1·´§G»&¿,ÈÈÑ¿Ë@Á»«gÏgÏ™³pày¿zÓ²ÐóAÇËØãBã8äÖß&Ù¢ï‘êûüHêÌû“ú2ú›º·ù¬oq0ñ©–€!ËG~7’9š'6•-Î* !7P˜5ªGxO¤J†7¸6d3;KÌM?K5>;I#Q5¶5=S8üFª5Ô+*+›FF1 ¶#©ýùU«$ ƒ.ƒ\Õ" û8óiä°àüßïÝä8Ú%æUÑ+ÞDØZ߸ÐÓ»ÒÉÁÄÁ›ÓºÛ{¾,Îs²åÂq·•Òp»¡Ã<›¹Úͮф½$ºQ¿ÚÃgµM®’Ò¶ÏzÃàëÍcÚ'È<åFÖ*ÞEåÆüõ^ûßô¬ð"økÿýÃÿ½ú[ øÅ Û'`$Ð…6™$?+—) -&4y?x1ß/93'I·H28,B‰Vâ*‚70”B-<|9Þ?Â?ãB4'Û.¢O8÷(|L[?î+ß4m&_È*8–Α  % )ä íò£ 9þ øZò‹ôBô‹ú8õ‡åŽEï3í¼É<ÊyÂGÚÎú0Ý»ÈåS¼FÆǰЊÁ-Ш·MÉÝÈuÒûÊÜ·ÍÂý·¸7È“ÜïÂ9É Ò×ËÜjÈάÄ$ÓÎܩѣðç½lî’åׯBÿÅíîèWù!ó¯úãön*ÈØµ™ ¡z$6â ™,HEŠ z7~Jš.Ó0Ü5y>ã;ÓBŠXKJ!EDC5Mp"=£5P7Ð=Î/&<ñE®*Ñ5s.¬™È;ù‚"ÿ3L'r— 6Ìí;ùb øÿþ)ðñ àáÝ5ÿRñÏäêígÝŠåÞÆòÈ–Ê[È¢ÐXĨÍìµ]ÊFÆÀ°4³ã™¢1¸E¾¾*¸\ȪÃIºzÕt³v¾n½ÕçÕÙˇÖzãêÊ~ÒãlØÝÔÕã‡Ô)âßèoî÷÷tõç @ Qý²ú ÀÜÙ –m¥ -"8D3 $ó3øF9ã36ì'ÌD5?La]NšA‘2ø[ª0>ªJÿ4ÿ>dI OB%&0?ê9–28€3 #}0H)ˆ7‚E—· úß) (]vñÕú5ÌæRhýÉÍè¹äƒÖOðzêí-ÏKÙÊØÒ­ßËŸÇ)IJÎܯÀÇ¿³áÉÆ¬°Îô²§¸áËÁRÂ2ÍÔ·EÓ°»x³¬ÂÅíÄkÅ×d·lÚåçÁÏé­æÚéíñëè³èåÊu÷û#ÿÊóó½ñ²Á ´&˜ r&Î-ZM1Ÿ'd( -ƒ=õ8æN£1n-*ŠC„Q“D BõL@…3¥>õ3í55š0éWý=5C%Z)³C:..}CÍ·/ž4LÑ#=2Nª}†Öšž/³‡ gðpñ! Éö–òïæ&ÞÜWýäîãáѡÜxÔÒ”Õ5ÀÂÎԺϹ½Ï´ÃB© ƹ­ºÅk¯ÈÆÎÀN¿m¼È¸©µ‹ÇT¶Ÿ½¾ÀCË!ç5ÌxØ/É©ß{ÝòëNÒþÚ4ãÉüû\Éhò÷>üsŽ8õ þ!©b)Å(K#/öŠ%~,O:ב=Z!³9ëQ^EDOS,JX+eCO\v7˜7W>z>KFDU=7ƒJ˜DÌAj7Û?M<©AÇ0Ú,Tl3Ï$t(À#Ke } ͼÈKþcúVþa&ùþÑ0æ÷ëçŽù:Ý­ÞêÑg¬ª×Yß'Ù»á3Í«Ð(äùÑà»RÒEÉÓ‹Ô«xµ‡´A¸Ä¸bÛÚ®¼¹Ç0¶aà§½–ÜÒ ÈˆÃÏ“Ñ_Ñs×ù÷éeãRÜäÙÄóÝéÔæ#ï S † ›û{Ù Æ# {Ñ%á1Ï5³#æ, .˜2<>0¨3hG865Xµ&FL‡aH7E\B4r!OFBW>µ3Ï9 (i+ /ª1¡§DL0}#b4Ü(‘kƒY† R Z ` l”& Íöe(+ö­Ûe{ùpÒ­àŠêŠÒ0ÎKÝaÚÎÊ¥ÛÍ1Ëè¾ßÑgÉÛ°ÿ¶˺½ÄG£«°&À¨Ãǹ]½ÁÌvÏ#Ó¨ÑÁÎÏÓEÃOÉ#Êß¾³Ü5ÉoØiÕoß”æbÑ“èó;ÚXÿ êÿ¼ãû= . å~ ”P6ˆœÌä3`.l?ýG#6Ë6Õ7Q6þ);5= D":1>OEHÍDÅ4[Aî?ØAó9QôHý1—<‹7¸8l"¯"+Ð(};[&³P,z‹- ËN~ þ…õwý¨ äð¿ñÐãÔÜmÜkðàæȘé³ßBÎBÆêº‘ÄúÊåË縩ë¿XÅâÙ¾B±­ÙªÆ¡ºZ¸_»Y´3ºÝÓJÄ–»EÕêÛ^Ö—½rå¸Ú$ì5ÑùÇûáùå+Ôqðý™îTèÁÜŽðjŽõN`ûÝ9Hmtô2[91.>F8=ô3I#07ü7¨DÈ2-K‚:kJJÉ5lNJ5Q`5%Që>°:94µ2C*µ4À/’>\W3±.ÞÓ&¼ "pÌ2Cƒ»mé˜XðoùÑëÀõôôúòß ñ^ò‚ú?Ý#Ó¹ÚêÛRæ·ÆÅ¼0ÍǹêÛN¯3ÇiÃcœ´-ÉÉÀf¬ê»¾×ÉûÙÛ°÷¸ÇÃØö»ØÈîÊ7ÏOÆGå)³JÕ”ÈmäHé8ÂŽïÉìˆí†ïúné(íëöë˜ r :òÂ}ýr%ê-&å7!Ã' /)7#Ž-¬;Á7}50Û,W3;ÉJ\)s+]çòµEÙ1гÏ_Ô¦µ]Ð÷ÒÜ·L¿È´ÏÁº ÒÚÒã¹mÍ*ØéÅ®³óÁ*àÑÔӺη«צÄÐÖ|ííÐbУá%Ùhæ™íãÐýHë«öˆ÷ç õbëÙ_fTä±g-v#É!ù§´:3'44C);Q9ìTZ"§4~B†?ÚFÕ5#@ E6ü>Æ'XYHi6èD½@t4;£7§0±6¸7.<0ÃŽHö©ZwRS ~ÇþËÿæí‹ ÛäñZÞçêØ!æ‡Å.àË¢ÃßÒß¹Ï@ÆÐ,ÖÒzÓÇ´ø».ÆœÇz»Ñ´ò¸Žµ$Û]«ìâiµÕ¹´ÏçÎcÙ(ÄÉÂÒÄ ÞuÝ[ÇŽË=Þ*Ó—ë‹âÁݦã±ÌÔäïåè•ùÂû^vëlúÂÿ'iý® *À%Dâ+2Á%3®*D7¥9§5¢<M-0ÏR8BJEj,‹H³-ËHALðSÍ8"GJ661_1D<26b6_ØK2CX$ÿÇa"0A› 6æ ý+ê IÐçÿ-ìñoÿävédú5ð,·íZ××Òä-Üáß-È ÔÛ=¿˜ÀòÄXЬÈçÇi«‚ËƘ֕· Ï¢És²þ¿½ÀÌ5Å7ɯÓe»±Ô€úþÝ<ÙæÖwÇzÓ:Ó®é¿2àQêú¶úû|ôÔà¶÷QÌ°ï² ˜!¸)¹!˜ *#b-?!õ+LÙ@t"^63E@"H_LòFf4à@¬,Í=ÞOL¥QKÛJ"WÓVø:Š6àAŒ!K:s!qA”%Õõ# 3U2•$×.–  €ÞÿÍzë%è¦ôÚð2òøé¹Ô;ÐAäæ%¼pÝ1ÑËx̶éL»!ÂlıÐòÃPÇ.ÉWË鯼1ÔÃOÅÈ'ÊÆÊDÃ´Ç ÂjÕ Æ!¿OÌ)ÇÑÒfÝÌé“ɧâ€Ü9ߎÑìé:ÞUåjíìùÉølò^ý^÷× 'õ“{sÄ-_/B.õ!«á .2+Â8/"€2¡#¨<ƒ) ?d1³6CwT9/dT¤H³.pDq(;6ý*N;BEúSÔ5å*Õ/U1Ý2Ý$1/À**ï01,Ô''°Ó’êqô &Êÿ‘çü×÷‹î‡à:Ö`áâÖ®ÙaÔÚÞ|ÓèáäÕ=¹Q·ÝÑ|Õ$Í-Çwß¶¶Åå´£™ÕîÆ¾\»EÀ\»™Ã¶#ÅX·ÝÈ⼡ؾÄAÑ|äïжÉOÐzÍjÙvÙ¼éfÜíü©õíºï•ñmùkõUéõŽ &¹{ã ð]—"'#)(22)2?.3Bè?q8~?i)¤6m3óAï(á2WN!_óBò5Ä.†YÔP6qC’>Ç=ˆ2^5}Hr6»ÿA¤=1&ŸþŽ„üµlÿÑØÁ ¤þܼè7ÿgñ]…ÖkïqëzؾԾë=ÞÂàuΙÛçºã²˜Ì4½´¼o¾VÐF·;ÐÅK¾YÁ$»ˆÆ«Æ‚ǬÄOËqÈA¸àº¤Ð±eÜÚrÃdÁJÆéÇÍ8ïFoÙµÖòØeÜóìè ç ÿžö«ç¿öû!ûsëT¾+ëÀ'fí!ï:ÒÉ&ú'/C@?`8ŸQÉ1ÞG¾3)‹Ó2qM¹58M92K•4l:õD¥80°2oSÓ-^'‚)(4ØBn084È1K—QC#À1Ò³&*"èvÑ#ò~âjð[ízZöò‚óÒãIàûíÂê‘èpò£ÿ1èõÛ!ëáÔíâ,³,Ô ÝFÐkÎ °Á"Íñ¸²¶Qµ·E¿+ÀµÊ½kÃ;³ÑÅKºÝ¼m·ÇÀ_Ö8²JÆøÑ;×sÓIó™áíÕÆŽæDÿ‚ï ä`óÉæÛøÖê¼ †!^ WÿRPÿµ"È­f“/}7ÊH**õ<Ð-¤>%©/Ô-18›J<3:°4c2>š,š..Û@B­J:CöNB“3:05,á4ô=6ÿ2Ï&G(f)- Ià C„DÝÄöÖ>ö‡Ì ë€åpà’øÞäÚóeä.á5ÞûéaÖgÖqÛåá5ÉÉÞOËÑÐÞÆ?µËÇYÄ‹ÉKà‡Ì–ÁªÍi¿IÂÂÂ\Â^Ô˅ÑCÍA´È”ÆHÒ?×iÌÞë ÆÕDðLâççÖ÷ØzêVé%ðÕûýCúùi‰ ‹<[ìuü+nüðÒ. )ÇB-¼Tâ7„._*'‰SZIê5ÔGéI©0M‡; 7U)tB¹E©F«CÃ;&J(7v6,'ÌLü:ˆ*1ÿ' W Îî‹Îju Ot%ûGí_åe÷Äÿlà ðã­ßÃà öMäÛЭÒÅÏ Ík­Õ½?Ì‹ÓÐľÈ&ÑI±¾è!ísÀÉËÞ½ó¿U¾5Ìõ°Üº$´ÒÙdÎ$Å2¹kÒà‡Å:äÖÄ»ÈÅãßHå[Ûvç{Ù”öºóãÀò–BêŽãç÷èåúù÷á’Á$­'$%? 5P¸"Õ#:KK3…/=”8f?É*¬<ü<5pWûSÏ94HØ4:à9¾C¦Q¶%ã8^=£@­6<5Á­/fcÎ<Ç/N%KÉ^q= fxÿÒTÄ4æààaºõYðEñ°Øµàà¢õHÊ)ëÙó³Ü`Úµ»´ÀÅÊ-Èç´·¸‹¹HŸ­Ç¼Ï‹Â]Å,½Ý´=ÎPìÌx»<ÖÒÜÏgÊ$Ó&ßPÐZÉìϤÎóÕ0ÄÉÏvØÔÌà¦âpðRßðùõç¼ñÏóFù. !ü lþ4už¾15[ ì"ô8Û+µ L?ó(×DØ:ù1¯?'5((!>þ`€B)AøWu9, 2çA»Gk$™Jæ>–^Ð8g? AGU@#›<ó,‘'Ó_3 23ØôP%§¯è&_õxþó' ‰îÛ õ³îèëëåÎÙdÛïÝJÔ Õ:½ÑÆáÇß¼äÆGÆ×Ëù¿šÈ඘Î8½æÉrË6Âí¼•­æ¹2ÞÇô¿ŽÆuÀÒVÅ«ÇwºçÃF×Àã{Éýưò„ÏÔöÈß ëŠéò„õúïs¦ô=  UÊýª©ÈNË /%h Å8I ·-€5À2‰!ô[¸7r'L§1!3C3²Y!;S^J¾JxH[2&>/?¤@K*_4Î?C8N-ð.Þ>R/:9î;U'þ–áÎQ  ÆßhËü«/âLãúÖÞ•éÞÜ©ºãšêãÑ(Ôô²Ò_Ë\¿­ÊáØ{ŵ¶“Ù¿,ÅíÓg´áר¼²Ï¬¬òÁA‰ÃÂ·ØÆ·Ú¿ÙÊ"ÙíÆDË`ǵۛӇԚÀ{ÜBÚzÛ¾ßæïQßVûœÞGþ™ó{þQðŽüуûtm÷ƒ%KŽ5Il  Ð.…)‡0èy6Ö/@yHÙòATO§8R"˜&5 Ú+59I2 &±?/^c\•&¤ ÚYëäÆî”ÿÑð]ï²ädùã,Ö©çŸÝ)Ù[êÒàÖ%ãØÕLÚÖЈ¼ÓÂþ¶ ¼›ÐÁÁGÄG°}¼tƮ峸Ÿ¸%Ħ»{ÅÈ‹°[ϯ̗ÕÞ<èhÕÎ^Ü2ȺÜ^¿QÖsíàÓÜ4Û»øãLæÿ]òH<ý¢Š%dö NäI¢#²"=*¥5¥;ç4p'´II4L>xO¨GT@¹<²@`=¿QM4‚80,7IT/}3v%Â#´$:'ü(#ù0‰ _ö$LŠ4tñœÿøïó{æTïíéíóìˆÒ×òˆÒ÷ӬܭàÛ[âÝ”ç¦Å‹ÔаĔ×$Ê籦wÍÀüÀ)ÃBÇ!³ô°Á5ÍÍËÞÁ†Ë ïÊÖ·Ò’ÌýÓCÖ±Î`ÛÇãêôõçøwóA;nü†Ñj fþ{ü­ÆIõ:…#K=¤%'£'´)F2ó,+â>G°4–LTê[M@µ?6 U 6ú4ªGüEÊ?+šJÍ6B^2j3Ä=)|?P(.3¿*o,ë:Z¤ E" o4 ‹ùX mÖù¼Ø‚õÉèÿË?ñ`ÓIØÜܵÜãâHÄ_Ó~Ð6Ô;ÐFº±á¹"ד´gÌÎʱêÑÄÃ3µlµÆØ¿±ÐåÏÉÔÍ4ÇôÀ.Í´"½D´¶äpÐEÚ‚ÍíÍÛ|Îké»Ð’÷$ã6ôí®,ðfßô8 èj¸ ‚"Ó$ã.—<#Ö3Ô?%):45Ð9^;o>=M`G˜,•C¼=A5m/½EÖACBF¹EL:í8÷Oá#_BS3þ4».61,:¤7Ì+%&Yû»ü g‹ˆù"r<ñzìÝòaé_Fê¿â÷jïXëýÞÞäÔ*ÆØÔ ××ÇÊÓPÒ7¶¡ßÀ±HÑ`Ï©óÂݺ%¼šÇ„Á†¾ÊÍðÈHÃÙêÐÖØ`º¥ÎKÕñÄÄyÏ)ÒVÓ1æ0ÕòØââ4ñõþØÖûïb÷øí·ø…ø„î:6 ›W l&G +t5R#;03#$47—¤1fƒ;´L=.LEK"i;*77„VV=‡<šFIè3@óNÊ2áEzJB93V$÷5þ.v9Û8Ž› $A'°‚"Æ÷εùLõc îâ „ë`ó;ïsñ=é ØdÞ­ÊÌÔHÞ†ÜÂÇÌמÌÈ[ÁżÈ֔ݵ„¥ ½£Þ´´´ÆÆ¸ÈÉ«±;ÂBÇu»ùÖßÁ¾ú½ý¸ ÓCÎûºYÅÔšâQßßÕ±å±é Ü>ÝÎáòòèoû˜´øÕû\ j+¶0ON uÉ ÀÔ)/7cGn;ë(M7 ÝA$ÙFÈ9 1×-[=&3€bž8Ä7w5»;f>ELE‘>&8C2R?zPl<Ã$2])Ö3/²õ'œ» åqõ5g>•õ‡öjö`î÷ª-ü%ïÏì–ðŒÐøÕÝÍÆÛÖà`ã¾ÕFÎÛèØ¶æÄ}ÈèÃE±OÍ¢ÓÙ¾6ÃÍ»'¿³©¹¾7Ø ¼EÆíÍÊ8ÄiÇÏÅ|Å—Á˜Ê(ã×ÏÌyÝVèõÛkÑ$ÓEã%Þˆ)ã™ýJà¼ò÷ôú ûÎ+#x0˜óÌ–.è=>)….á348ƒE¹S¼CÂGŠ0{Gx87D¯:DCH6HP:¬1¨(¦:T81*Pˆ9ó2Ö;ðµ5*æ%$¼Æ4ÙÖd#/S’ J²îc €³ù3÷©øÑíDØÏdÛÑâ!̕ޠ݂ÛñÐOÉCÆÐÈ=ÖÊ%ÚRØö»¼íÃÙÌ+¸G¸ÛÃu¨ÀÄ4³w¸ƒÁ<¿ÊѺ¬w°!ƽÔrݽÀMÉ%Ô€êÓɩخéiî½Ò¨Üpöƒêëù¦ª Œ» üoøu%Žj|Æ ºz -º/~Ù03åD×8ùS¹5äE˜CþDeäI¹I•AÅ(«"pFÕ> 8Ð(UFWM(PÂAÊEµ96$¬(K=0Ì*â"¶-Y." %&™R¡Áå<kûY•ô½ísñnöøô#çøØíá}ècá>æÿâÔ}Ђà©ÖàË,Ñ鲸n´xÆ*ÔUÚ²AÄÚTÌ*²ÁáÆVÍ=¹¼¼¾Æ²Ä‰ÃÒÝÀÅÉHÝÞÁßnÏR«Êvêõâ ÃAü ë&ð^üWõÈí ÷Îü¶î?ï ’Å\ØOv"’"“(ô+õ»&˜Aá)ÙG¥=ŸC?1!C·F±D^LBL¸>°?Ä'¥EUO"1Ž1i.ý9çMVˆTS4¢):W9«?M'ï&TDp G0lÄÉ%uý„YJÿ— ÓªØîæÖð'ë5ß®âÁèÛj×ïÎ$ÅòÐ%Î@Ð(Ç>½¬Å•×”º)À'ÀƒÃ¸Å8ÀÓÚ¸2¾ÖÇ6¹$»FÉ]Á•¥hÁ¼º"ÄŸÀ½Æ+ÍvŹÎ/Ü´àùÞ Ö-êUê!×-î(ì­óF÷Hô¤ø[ó?äþRï É'õ =a%06Ý NA†4ƒO #0a*0•JÑ> D5WcHLKéD.£EŠE9/98…Ld=û?<;i"M4'@ä#Dï'_3Á,ö;Ó¿0+&' X;kP 5ÿÔúÝ-ù€%›æ?Ø2àåËÝ7ë ë:ÖÐâG×ÎϿݺÇfÙÂÊJÖ¥V¿|Ƹl·¦<ÓļҾ.ÙáÓ¡ü¿×е2ÕÎÇÓÛôήvÊ"Ôñà}ƧáuÖmÛÒñ¬ÅÙó罹ëËæwö}“6õ«÷ îÖÞ Z~ M$Ð%s;00: >é"40›5é5Ñ+d/j;0E 7ŠL7Nk+äbÚFZ@!-X,HDÖ-þ/F±3V>ö,ö#t@C )/.'Ó%— B,Nûà U ÔY®¡üØÂë$ì–ëÜõ|÷ÃÒ‚ß ç.¿—áJÜs½3Ò;Î÷ЖËëØ&º«ÕtÅß¾ ÃFÂ~ǾÕC»/ÐùîÉ<Â_ÈÞ˱·ÿʼ͛¿¾̦ԦÝuÖ<Ú<ã;ß>Ì–Ï^èÅùáòúqøÿ{ëãîYôöÆ ÝîåïÂ+-0É-0!1$m@°@2501±0Si/Y8/;?Ê03VDîL7C:^\iAœ@n3ëDŽC›I†;Y29A8Y9O$5Ó*B+&oC'–!`ð÷¤¨ñØø—îý ùûè:œ÷öàÞç¹ßÍÞ³ÙÃä^éËàbÏûÐAÙ5Ђ¾Û¯–Ó¼¹¹¼Ñ¾”®·Ä¬Å˪ ½“ÐxÆÕÉqÔ­Å¿Aáé¾×¼©Í?È=ÆÏÖç=Ó›ÞÖæ‘ÒBÆ÷Gåë÷ØðñÄñSÜÝJñqÇ w 0 ¶!Ä)`J"ˆLú}'¿L'7"5|NÖ9«(;T86PV<Ö9—Mï8>´3qG783T¢;ÁS7+w7hQa0Á,ß*œ)±8Á=n/7àé'¦ë |µ ,W†yÝïžñPßÛ>Ø~è í®ßBÇÜÕÌÅÕØÐ×1×qÇ4½ÖzÆ@Ȳ•˶>↱Ż*Ç\¼ìÈ×ËÓ²ÐÇ@ÑC¼ƒÆKÕÃѹԼ˷Ìfèaå„Ë}âñÚPÎöMñ±éŠà[Ü“þ™í§õäõØ7±¯½žN >At5³@#;ˆ+’*!§3A9å#.=›,}(±9‚D@J,9IPE>e/CMtP|'<ð:|8^B¸D?ê43j:'È<'ø7+0ã#’ê ˜7bC&ò hòvõgbï]ø0õÄeå2èØæ`Ð`ÊÍÜÌÝ€Í[æءŒÁÝ1¸ß½>®;¼$µ‚ßÚÀ¹P³^ÄAƑī·•Ïz±­’ËÌÂÖ·ØYÛCÕ‰ÇhÎÙÕ\Þ¸ÇÝàïÃVé]Ð:èkíÝówèWõæúùü{ Rü›&8Ç3,°[ñ¤_'/p$n"×B4ý@ú,B)ò6$HB4;œI=/ý=çA’S[c7…=Ä:£26o,ÍHQ*ë!A1®%Ž& 5@=©} Ó !ï#î„)öî„ËðQù­ïýòì¬ñâËóîê7èyáŸÕJË4ÛÞÑã¨Õ£×´¹4ÇO²ÆÏ½¼”½7ÓöÌ ¿„¯ª¥²¯Þ»'‘¶Ö©¢·±ãÕ“ÅdËÿ˹ÈôÔÓ®dËNÂz¾κìçÔcØ…ä‰ÛÓþ®öúâñ­àMõ5½ïñ^ uæ" g'â'¿#õ"#!( +_+'EÔ8á0ÛM•PŒ2 9H(`&i+î:øQ5<Î@=:8506D¾Bü0g=+1É25o;©/ 5Õ;{E‡2ˆ… ¤á5/ » '(øšï¥ ^þ…ÿ;ì ä“݇߹ç!ð³éÙ¨ËKî9æ Ó¡Áè¼×[´ÛÄ—Èw¸o·¾¸³ÛÂBÉ«Ã6¹ÙÎeÁ¬È–Éî¶Ä½vÇiйԦÄÖÜËðàbÀYȽÖàäï¶ð%×TöÅÞ—Ò~óÀèâzñâxîA ðüœ@CMÄ$µz.uUÒ2Y(Û(F2ê6®GÔ7¡1”B°Aú=B@<4š:wDBÃTSI(šCDmQ×&ì7‡/D=i<£;9›1×Bþ#4\òFõ ÿ!¯+ã Õìöj^ýW?ýW› ÜôUâuäÏÖ8à»íóì‹ßÂÙ ÌÖÐǛǫØä¥¿¹‹ÌkȰîÏBºµÑ9Êd×wÆ{ÃŽÉß¹ŒÝã¼îÇQÆJÅ-¾UÖiÕÊÈBÛkÔ.Ô†ØÐÚ¬ò”ËIÛ]ë8é¼éêöxúG'û#ë*óÐ*P,A!9@>V<,)u2Ô31*—Y40GM2v51Ö?…<±FõHSEæCé1·-é9ÚR°!â,<[5ÀP#+µ3o8+e2f=,*h-Ë<£ ÿüØï¹,ë¾ìv÷»îçé[òxçpØ­×Äã%îÜØìÏÔÌÊÞÏÒM¾Ã¥Á®Å8ÂÏÂNÄéÅ`¹ŽÐY£JÂRµÕµ¶§µš¿ Ï0ÉÖÄ“ÒÜ·öÅ»×XÈ«ÖäFÁ|Åœïágì‘ÜBÒQÞðøaÝ€âòwùöçJ!AŒ#…{$—­ÍË$,@%Ž#â0Û1) 7÷*¸@ÝE¿6îE6>WAf;]HO]A2%½+œ-<=¤Ar,e-d3Ôì1Äò# *22ä”)S 1 : ? ²üí÷Üõï9ûQïôê•ê…êÜÁqÕÔÎÍcßÙË'©Àսͭt·|ØuÖ¶Ð~»NÔ<ÇT¸6µÂÁdÑ„¶¡¶£¿ZʛɂÈéËG׌ÎÈÂãÇqâÿØ"Ô·éhÉ£êùè•â3ñQÒ) ïûoôš Ùõïþ H¢ „j+*, ^*4,`å#@&'84#Ä5'„84BB¶?O3­!n<]]ò1k9ù%‚3ó:*F‹A•v5Ê:>?š67-0q%Ý" 11?¬#fŠ ß ƒa—Då‰ f¡ðŸøÞìCúÖð[ùöçßákɌוԮΠ×ÁäºÕ&ÖcâV½ÃË»ÏĮܮW°$¸ÎÏÅ¿1±ŽÌ+Æ ¿ ´zÛ×±ÉÁ}ÏÕåÏhÒÇÆÒÛŽÉФÈÚŸðí#ÛîÛ9þÛÜpúülùÆö“i ÿ†| ûŽ$Þ1¿ ø‡–2ñ)WLADª4@6Þ,b>8(tEõG(E’9J—NðBS1–8ƒ%Ç6±8S/3Í.ëF{8è?r7L6u)_C(:X|3j%‚Dûæéøb Pó>ûæñWéçùóGòèåàá9Õ@ÉEÏÓ©ÍÿÔÝ¿iÎ{ÙÊȾ1Ôò¸ ¹Ã¸®£»hÑÁ»Î¥uáó¤ÈÏ3§êÁ߿ի½ÕÇÎq‰ǖχÔZàBÒ5пÛ_áíâ—à äñ¶ôe-ënà¡ÿþ²ÿ“ ø_ãƒ(7¥–Üú o,ýE‚9rE6è¥(U6÷:Â*É:xL05”?§@¯O?E”RBˆED6þS *ü/ž8p?ó&¿#!e2ô@+ø8å -ß ˆ$˜º¿Ë$ ðÿêïûú³ýjë¨ðÊõ;Õ­Õõá¼ÈkÌBÓ?ëþÆKЯÞä¼wוº½¼¾Ã¬²òÀÈÊL¼"ÇŸÁ̳µÜ²#ÌË®$¯î¥yÓq½+ÊB¾éÍ¥ÔgۃѦґó ڟϬöøôõìYÑìíÿ éþÿ NŸì^üs.jblŸ$q Ë…ŸÜ42g&”F4<7rBc;5-¡=i>r= 5@¿6öA¥X\Dƒ>8Ä-€+í92tBÚPp1u)ñ1– *k772¹'Éa þ¹V Þóˆµg ÜùOúùrÐâ–óÝÞsÒTä_Ô¸Õ.½eÎÑ÷ábÎÈÀsºõÆuµ¸?Î\Õ·¬Ô·¿ÔjÌÙËa¼~̶z±!«ó½´Ù@ºØÐrÓ›Ú­Òöà´¸Ä`ãÊÝ´Æ6á,éŒòáeòbøLë¼û¨äÓ(ø†'Ê6 ¤:&d.Ä&vŽ(9tAì1 #í6157LP9k@]?:´2^5GëLÇY÷=_;¡BÃZ¯I§C‹B/M[LY:»<{%~/K0b8àv|&ù +‘É( A#\ ¥?ôèˆø†ÿÆèRÛÙüïVìÒÚØüÙÊÇÖÏà×ÛtãŠÏI¹ÆÅÅ̺νÎÆÖˆËoºȽ¼–«Ç[¿uÜ¿ïâMÔå¯ËÃ'»¿·Ðã®ÃñÌrˇ©Û·˜ÑØáIì«ú.áûhÚß÷)‹ò…ô@á¯r !3 |-#@1À1Ë"ì'1ñD7=šG¾<Ó@è-=ÊM@HJÛ0Ó# @(;!^o6Â>Ô.$Í6+>01¡3û3D'4=’L>)-QFÏ,n,Ó3`4„Îë~daÀáÇò¾Ý™âáü3ôûàŒè–äÕçËÝ„ÓÖÏåÕâ¯Aé쫆Ûq˱Ø'ÍÂÎ/Á8¯1̨ܲ ÏÊP³¼MÅÃ2¤rËå’/ÏÀÂÙ×ÃŧÎÊÍÃñÏØMÙàñdÚ_á„ãYäAî·ëüj9žÿÔmÕä jθÕ5A+Ç6u9°&!Bæ3Ö>5I­Ox7§6‡>g;/BI0·H¯5D>Ø>u<4m3d>„9q4‹B¿>@&Ò>_2S!ý:.?"P/'5ù#œ í¦õl¼r?ù ÷¼úóÿKô½ÈÕñø*ã{èýÄðçaíσÉEܰ¯ðÇv¼êä迆»aÈÒÎÂ5«Ý ¤¹YËÀ´ṈôÅ|Ó]®OÕú©EÆô¹³À°ÌœÃ Ø§Þ ÇÙÔ–ÖÛ´ïSìòÜ_ø­äoÙ!ßâ7ùÃü òÿ«³þ…¿%Žs A:ãíW“#Z&*0×.Ì=‚J/þC:‡Eh6d3Ì9?šDªÄTÔPv_Ù4U6%=/’8¾M<7M3ŒA©T?N7Ý?~@‡OòGd>6/1]9Ô7ôC+GW)È=Î>®5ïÝ%0³ò?Vý¦û(7ÑWWüÔüÿÑñª›ðy×ÄÝŠëòåMÀØÂY×(à(ÌXÊÌÃ×T i¿wÃKºµh¨µ±¨ªRȧ¾ÃÓÅo¹ÉÎĘ´tÊØbÒôÊ,»ŠáÙ"ÇñÆÒá#÷“îØÜÀØÏÜHö0øjðüÒkè:Aüßýäý)ƒüEÂ(À "Ë‚1ý?Y*ð6Ê(™0é-$8"%¤S¯8>,]@M6xJ±7=JûK@ 6ó9_Eï?ÔC¯]=>8 ,2â!{<+_;£!Ÿ1Ž#gœa7… ¿B© µØúúÐþÔàûŒýÐêÚñƒñžØ5äÇÞ­ÐôßoΧÊ&ä_ÊŠÍÚ·÷ÙøËÊÏÖ­ØÃÿκˬ¹!ËHºŒÂ-»ÐÅÿÃÜß>ÐlËÒ—Ú»xȨÓí»;á•ÐîjÜÒãÕùådõéÑëýŸóÌéûûKî×÷Bì@ú…Ÿ5ûÐN §ÇÿT!ñ3)Ê3!>+â@á1XHA<>>6`C…9½A;¿?j8(01hEõK4Ö@Â&OJùCf2/CèF>DÂ-è')~;!3ß:O+6J9¯ Äå û¯ „½fýZÞŒåoñ/éÎÙôåF÷mÓúØùõµÏ€ÆãÕÍ Ý€ÆyÑÆÂÛ·×*ÈúζɚÇêÂDȶ´¦Á޽@½©š¿µ³Í¶!Åð· Çt»mÏÈÅÆt»HÝÉ*Ï2ÕòÚÿÌüñ4öäâÕó(ù„÷×ø •â’ôùÿjüÐr5Ëþš2³,š#ì¤>*§°!r=HAÓ3j/<š?MCÆ6ÜN&2Kó= ?O3SCE‹2©NB5G ˜1,¾)r0Ž80ŸC¬!ƒ£.Óu!°&±§VS óÓ)J ›à×üsãlëúìâéè;Þ×ÖDì=êÃ.¿<äÍ“ÂÕÀþØPÉáÓm×óÇ Ì Æ½×TÉèÄ&ȯ É™°ÏºÔ¾»B¹ÉÏ_ÑÊtã/ÎÕÁÍ©ätÇ à7àÈÝèªâ9èçø`ðmëÔùýæ“÷1×変 £? </±ê-­+85Æ%Å1ó)t7]??/öGCJ«Pî6È,_<Â9’FL>ÛH—6¶A:O?€>\(I/?ªFEDñ!¥4Ö<³&O&Æ$!4k&¯"Æ0‰|ôç Vþòü“øtéVìWô©Õ/Þçëåâaéçá¾ÓEî’ÔIÌÓÄÅèÇØ¿Aѽ˲ØÊǽ´½E¿“Ëý ¯ýÈ´Ê ÇYµÕ:Á†ÏÁÊÍ#×&ÕÚÅ'Úc×!Ê´ÉVÕ5ÙËó«ü:Ú—éåùí”ü¶‡Ù# )Þ.öì’òLþù,‘$pû'¢.ç+y@²&s/Ð/c4f7Þ^òB¯>>)Ê<À@,@±6Ä>W@r/µFTHW8bK9²+Ã)8ÿ$6=‚+&1ÁÚ*á$çñ $"ŽTŒP1,fëëoù­æÅòÍëƒïÜß¶DÞÛЦÌtÂÛÝ ÙÖÕ½ÅÑÄÔ-ßÐÒ%É{»¿ÍÙÇ À›Ôöºa²„»º¦±ÈBϼ¾½ßËQ­’ÌRȼÇÇĽ¾FÔ­çÌÎ,àðêïßÜßìê½ò¼ÿ¬õŠëëòþwöëú@7:¨¬z —Î&H)Ö0¾‰$=Hõ4P)->,Ü SIMDÒ6ëG&³†Aû?a:œATSUKPøPG2/w>ª:Ž?á*è‘;œ%å!Ü3N&ÛÞ Ùñ¶„ ò÷_Œ6ü ú4úzìNñçå¬×â¶Ñâ­Ú"Ö²¶{ĩūÊÕÙëÈ׺ð“¶»ÃÈÂÕª¸Å«Ël¿H©'ÃoÆ™³Åú°AƾpÊ%ׯžÛÐ[ÝâÈÔä§×ëãßßvÂ{ðÊÿâø ²çgü¼ôT“]ßB8 Ç ¡ýÙ8ý/Ú(%5B'ñò379ù5Ê<„=ªD¤,µ:É2î:gLE›I;0ˆ?e4‘C9G9©2ð(û@¶3<É@m96Ž"è#Úà¨&Àc—œ)ü Üô9öšì£ïÔåIãéðÏÔ êlê ߎÍ"ѶÛ_ìPÁQßèãÂÁÿµÆVÉ~²9Ä5²¾Ìo«x¹,ÜôÇÈÍ6×*ÄQÄq¥ÂΰÂû¸Ê¸³Ø¸º€Òå ÐóËé¹P܆çàFaãl÷¨ÎTõ¦ã¬íñ¾ ÉýDþØ©ºB"f#‹)}# "b B9E{7g<#È6ŸI'¹DÏ:ML“G63U44Þ?H>BX-œ@}@ÐÐ))KhO -’<æ.Œ'"8#½*!&#'£Qì»ù ±³÷Hái$ú õáÿÜå±í؂ߔßêæ·âˆÎ5Ò–Â'ÐGÚÔ˜Àþ¿õËP¼¯®°§>Î1¾uÄ ¹ãÃâ´Î»Æ·Ã¾—Ñ×ÒÈŠÂkÛž¾{¿%ÌÙÈ£ÐGé’ãÛ¯å€ãNê²ìSÄÁؽîxÛE÷…íì/ñ l [ †.äž„×"£(!1b'Î&Ó2‚!`#Ò<ü6A&`3åYò.ÂDƒ>Àc-Ft!I0Ì ùL—.tÝ…’%—ÿ{÷ö£ }÷§ü“÷«ñ#ý óyà6ÝèÕÖÍÏÓºîÏ]Å*Õ£éØKÌÉé‹ÏæÃˆ×;í±Í«3Ãսѭ…Àz´¼ª@Êñ´^žÌHÆžå4Ëk×1ÑA¥ÐŸÝÉçéMÓ ìléÄÇá=ñ²(ëø¿íùö˜Æ oú\²² žmòY€#ÿ9¹6i+'0b&_-];6Eû&7HC<>T7¶9¿AŽ@• ' JHMEn8BÅ-(Ü,!>¼A[1ø>Ñ1t Õ/+/à*V4% =ïGù— “ àè2ê½ÜƒüþÕŸìŒÉ5ݼßÞÛáÀÈBÒ¼ Ò³!¼ÐÃúÁÅÎ#Ä{ÇàÉZÒǶ²·Ó}Âl­È³AÅ“²Šåa¾@ÇҒӼťÏ{ÊNχÚÞSéßÚ#ÏÝÔ5ßôëÜõuë¶êÍù©ê£üìã@ý¼òÖŸAó}¥"7AÌ7$*.<.Z3(N 2K;Ö?é¯<Ú6)I T}B­GE:æCõG“Dö1ÓZƒQ%=”<ùI=­>ÕD² ß.±7Þ¿@¢>ö$–I M"P8nõÿó% ãW÷Kï•ö«óþ©ñ]ÚBÜXâAöœâFêVÛòéÿÚ"״̃ÎÀÄìÒ»²½øÔ®§ê¸[¿B»Ûº«Ì²¹çÏ*Í_«‡¾ƒÉµÃÔÉØÍ—ÅnáFÇ2³fëÀÏJÜêÝÜÒ°á´ð™ëäï-ë¯ðÙq÷EaÿVW«îtp#Ѐ U/º‚'Û+[*™6ŸAÞÎ6÷;RiT&<¹L(0k<„/ó5—;ð}#È…*Š/œ+λ=4&‘-ã5õœ4-6á=æ8å8[R´DO,HÐNHS4»&·&ž_¬KÃ7?WM*Ü/ë:‘5P¨²%&3í %v5"#ÞïþA =ÿAþÌî ããÓLÓæÝôñ,ëAä«×˜ÞçèûÄCÛè˾ÕÕÑ´³—»±ÄhÍ3¬Â˹Åk±)ȺµaÄ®ÀsÞxÏMÎΞХæ‹ÎŽÐâÖ§ÞVØbΑԈÜa×Íá0à“ä­üË÷Óäºòú/û:™ÕÉ|lK_  y"é&¿%§/Ž?þ?q/ç2R=J‚&!\ >%(P5ˆ:HûDðFy8ê@kNd'¹KgH@;Ç73—C]2Ê+´D+2ô0c\".'H÷@Xüï4Ú4!Ý÷Ç ›ôkø¼ë«ßîO×úàìmòUèèªÑÐÜÿßyç¥Ñ(Ãzã®Ä„½ ¼ÎÖ«Î¥Í\ƽºç»/ÑÞ^¸G»ÊáÍŽ¸ÑÅ/³SÒ»ÈÛ¸v¸„Èa½Ö˜ÄZÍOÑ^ÛWÝ/æhì“á<îGÚ.Þsïø ¥ðÝýÊ /?~ÂÂ#¥#J!î ã æ&97þD·AD'6±173h:’*Ô?ŒB^@“K•?jLEGJã<ôEñ-ÐVÎ&ÎIh#Ï57*£< -,%®+Ê/k$[66Ë7kÈ1Ç=‡,¡)ŒübÿOù»h÷ûëíï åÜÚÀÌûÓ)ÍfçÙÝWÆËoÖiÌgÆwµ4ÚnÈÍÇÀ\Õ)ÆnÉÉ~Å÷ÂNÈÜÄ[³²­ðÅ—ÅHÏ·ÅQÅá¸sÒ—ÍÿºDÜ«×áç$äâ§Ünájî†êöõ õ½ìïè´ ú£úÇ ‹íó³# f@#ö0.¥76'î-¨-E4ÚJû)i5ÕCS/¤A Lg;¤G4öWRAH=«C¨OÏ/7°7­=‚*G3ß5h0°=‡F5Ø:Gê/W.,«;÷6J%+.{%úE²ñ×å¡ ˆÄîôöè£ã7â‘æiÌäè‡æEÖMß½Ü'À¬ÛZì·Ó#ÐêÃuÆQ¶µrÊ@¿Ë=²Þ˹©eàÌÈáÀ™»èÀ€»%³íÐõ°ãÄhÑœÈUË4Ï(â¨ÅqÈ0عÖ]Òkï7ê<å¥Ôèécßêü/ìåêú~b [Úµù‚o)“¬(Ý,…FËLv#%'y3êD}Lˆ.÷:,@Â9ü6àE£0ž@K>HG(E@C-D¯&W'ö:Š?x:ˆ@;Ž-ú5M˜'dü6³5H %ò"@:þÔ}ïû-÷lá½ðþûñšü8é[ìÄÜîèeîÒ!ábÁ‰°zÐ4ÆgÛý½ÉÁxÔ ÃÀ»¦¿óÄ'¬þ·i«oÅâÈ ®®»œ¼tÔv·+µƒÂ7ϤÆXÌÉË¡Ø<¹ÀÏÜË,ÒêÌÏ>ùˆÚãá'èhßÙÙƒØ7ÿxóvùMù-ãÎSúÌx Mü#Å!÷%I2I%…9aCP¤ 2+ ?«H[>å4•5´HÂI‹3I|\OP]Km9µD˜@[<çD¶>(Š.QDW"îE<>1ñ)¢À(Ú ñ3Q&æ[7²ýäðß2ÿÕ÷ñü·åð%øÏëí3ç„óµÓdêäÇNÔ&Ê_Ö{Ù…¸²º ŹÏk¹Ü¾0ãxËòÇz³îÔö½ºÌÜÉ ÇW×'¾XÈZÀ«Ò|ºÆ¾œÁ¨ÍÝÏ:ÚLÏ!ÐQÊɽÎÏÝîíKóbã©Øäç"Ómæ(ûþò#)ñíÂùO,F&,Q¥_,¤#i*T’C#?%2ýëA4P,.æ,7[4>WC’;K6»²_ÐQ×w¹¶Ë1µÓ ¼YÁöÝ,¾_ÑâÒØ%ô]æ¼âmÏŽÕ›âê»PÿßËZæûeÿ$`ÚôÈøeáY‚#k,´) ,’&Õ+$6Ê*8ý l7h7ÁQv-qNCØK/7K,E 3/¸LÐ'20j7p3zL¹ƒ>sFÐ)¿3ó%}*R0ê$ 3f%”0 Þ(¥ ¬+2 ÅéVúé Zá0àí?ùŸýrô ðšî¼êNÊøÌI×CàäÞïô˜ÐœÕ7Ò¥¾Q̼ÚÁÎÅU¶ÙÛ¨ܜܳžcÃR¶"Ì3¢EÍæ­ŒÁš×FÇïÊüÍ\ÃÈËÄ>ÂðÐä§Ý3Êõòðãö?ùšKóŠöòµ°3Ï*# 'ï¿"X ¼2â',¬=Ý$r"8D ;þ7Ç?†g>¹*¾?M-uB2'7.ŠO«CšAAúAZGl?íEJÕ2Û6T3u?MB.+FÁ<¹F5B;:Ú$'Ia/4?ø<¸(—Aª=„1a"a++v¼;'0ÿ# —4 è”þÎõ5õƒ¸´ýìÇçÅÙáÌè¤ÓÝø°êÉÖÜÉÈÂÊÆ}Ì븽Ì&Ê%¹œ¶¸¦ÖˆÐ‰ÄKµx®¹Í¥Á·<Ì‚»5¹+ÙLÔ‘ÇØ¿ÎÚÔîÄnÎKç¥Ú´ëGêë×øÖé€ Âö ü$ßfüã-" 0sI JËö Þ’åº^ÿ ‰,12t7ê>9®H›A¶02q:¢0F5äJr7ÈE&\;8Ná978ü>ª ¥- A›+x;79±8$I¢ Ê+â/k0A&]''%Ý %!?á^ò +äÒýpç?üáêhâ8ÍváéxÊ—èØÛgÒ}Þ`΋ÇëÏÍ>Ê+Á\½»2Ø(Ñ‚¬²Ì~—Ô½¬œ¼/Ñcý½¼¸¬Æµ¾ˆÄ”µiÖÃÝÆâÉÝÜwÝOå®Öãà†Î&éÛˆáZÇþ¼ï”Lüäò! ÑÇ ìO#hŒA) ,*±Í&ò!."£<ï554#ÅIÿ2›%ò2C*{Fä>‡5ÄJhQ<=”0oPçBÁ68Ö)n8¯BåV ,{(02#++<)&Š!†-º%-1” 3Bh ÷Wõ»ƒçtBô“ëN÷¹âé‘Óµãíè×ÐMØÒÎhØäÁsÈ2Õ8ͼ˵,Í?Á£­A¼ÙåÇê¬áÃõß?ÖÛµ¦¾0¼É&Å™ÍຠÁÎÃÅÓË#ÄëÚÅͪ˜Û}܃ßíÝÑóéèFÿÍÚNø˜î_5ûr $?õÕn)Ïå3¶|Úª3)Ë1qQÀ7’4¹)?3EÃ-M1D; CtBo;':D?¦>Æ;2Bî8û +Í0IB2&8w7P-ß$y±/S !o‡ý Gt'ü¸ý¶ôäEçÌòpñ2æ‡å{Ü;ß@Éwë Ý9ÅíÞsÏCÔÉ‘²ôÎ/Å*µOÉjÐÙËöÛH¾þ½=¼Qɼ¡¯.Ä7Êë¾ÞÐÖ´lÍÚË3È=ΓÎsÒ!ÛÔÑÄÚ4àyÒ×”òðíhæßí*ÿSô„÷\óÅÿ„÷¢ áø) ùõC() *"ÁÖ›'xB—.@…8l-µBvGÛ?½+X@mC`<Ý5ú+«< Cæ>?F±Iä@(4žQV(Ö,¤7<3 BÏH.!-Á”.(á z © B+./82y Mü½êßóÒ·ÝôžóÏèÅÊóê×jØÍ Ñ­Ï5ÊÞ˜Ñ6ÜÿÀ)Óȧ®bË"æˆÌòÖÊÏpÊùÄ®¹¡³½ÄíÅǸ ¼]̔·ÚsÎqÙ@ÅnÖ »ŒâØ:Èsåvéמ÷píiáéתòƒÝáòôEFóöò `ú–Öâ¯3G O!î"Æ1m=g,K0M3_J»E?[ù,ö<¤0Ö;5:­)Aú8uEÈI2d2 = "W:£8®9P8;/ú{(¡/¨Ò KJ Å[ü•Ùü3ù”õ Œï ÞsïXðô¶îÙ[ä7ö™ßåã•áCëeÙ1ÏÝqÐݦ Ãæ}Ì;¿tÖÌÖÒÎаÁý´_²Aš¥½ÉÚÎÝÔ«½Ô׫Ñ?ÁÊàOÁÁÕÀÚ$Ôé¸HÚ9ÒhèÞÑ<ù‡ßUêwôõþiùÿø²ÿ(T üåÿº o P¢Ô&ß7Ïn2Ð("4 /jtBe<ð5c;^39= O-¥7GÅ>B9‰-î>G-d.E8ë>#,ì(”4÷ ,'‹3e"è*©,ªM,þ}ÉCýcó)ã­õýûó´ë)÷Bà#ÝèËäøüÞpâ©ÎòÅÅoº"ÑeÄíÎÐÄW½„¨EÍ_Ÿ>ÅÖÀ$ ¤ˆºÏÛÄB¸Æ©ÀËìÃÉËsÈçËÏ¿«Ï'×6ÄËÑæq¹áÇÌÙùúãÐçï­éç í þø#Ø* îúÊ÷ å .˜|Å ó3[ý*… !,À*ž>@.ð1§-Ç.:A$A%>à4?A9ÛLFCŽS3PÉB 1‚F’9äU¯Hh:èL·+;~E-7ô¬9t ¥ &&?u*XÒ 3j È ?Pu áõtüÙéñèè¤ûØðýÛ;ë ÒÂÔâÃzÊ2à5Ö ´}ÀmÚy¶ïÀ ³îÆÿëÍòÕð¹gDZ¨»ÁźæÈ ÖùÍF¸§ÀR¼Ó³›±ˆÍÍäÅwÀâÃ]¼°ÙçÌð×Äüä—ðNáCõï‹ý^ê4øòú1 ¡ãc À¯â¡(3"* +k2B¯6:Ú/:î]ñRæ=ÍJš>I5ð8à9457±H0;UIZD˜J¹+ÛD©Fp>ÀJÒ&+0­7ô,®$Ÿ"Â÷ @F{ä9g§'¸Øÿ>ú¨àÿ©óØø›íéõÞù©ïÛ˜ÚaÞà¿ÀÏrÎÀÁ$ɦßï̹Æz¾!¿§¯ÌRÌg¼¥¾öÂs·:ÁžÁSË‹¾(ÂÑÛÆÐÃ×Ж̖ÍÛµÑiÔÑ¡«Ù”Ù-îÒëÝEõdáïÛpîDäÿ÷í’ôæòúü¬þ˸ µHvé ´ ]E,a(ú-»-a¯UK?;40N½/F¦IJH0JC¹?ã<|>™&0{)-?ÚKtFŽ%¤(t>QI˜>À+7'?„%Ø-(20” ¿!€å hÿ³òvøƒýZ ¥òíôçï@ïKè¤Ó—×{åÑÙ´Ï/ÕŽÖtØØÁ:ÓÏÜÛ?³EÄÓ¼Åê¿í»ÿ®õÓ3ÏëÀ¢‚®¹„¢JÀXº7¹Éµ´ÙUÉÆíÄ×ÔyØÜâÂÓˆÐýæºå^ö,òñýò/ñèøÃøþÔ ñMø}‘ýÝ)ó ]5:)R3[.á.L¥5;@Eh)«8á3Y"JNí9Ð@êB]00;\IÂ5+5¸>k2è-™;‘4!1s,î0À$**m&¢7ò)"¿èíb I\úiú ª3OðpñÁíÅéߌòBæ£ÐïëÎÍÚ-Õ„ÍtÛpÑOßYÌ<ÐÍ5ǯµ»à­¥²¬´»¢»ÊÔ‹¼±ÆýÒzÄ¡Êã»PÎÃØÃÃäÂμÒÛY¼wÅ Ö åõ»PÑÑ×'Ý¢Ñó‘Û/êbóíáóð“Ë¢ e œ&§! ¯ð#x(_ò!Ø…3»3{¤1Ý>Ä6{C=&Le["5.IžGœ:´> J=C4?ÃXö5?ï"GÒ?;Ÿ8Y1^$w!ç,Ë0Ù+E3+a0öOJްø)ý3Méá ìï šÓƒúGúò«æ°÷Ñßøãµé}¼ÆÜÙÄ×ò¹áÃÙ~Ë„ÐSÔfÔðÄÄ¿ÒÏ/È–´_Ĥ±Ç6¶·µ²‡´‹ÖÕa¸‘ÙäÏVÑËësÐ@ËpÚ6Òîã­éÏíþàíÜûóÐÛ¾úZú4ýPùKÎýš{ÿ A ø Ž#4j'e+ª3N$|<”3Ç9Í4@V\NCÇ3T,¬C8‡C¬?‘,á5*?gM Cƒ9Å3*;¡Eˆ3dG7®>Ž;j9›@.á>m$-¢"o&+I2ƒ Þ¯Äýg ŽúÔÝøñãðù*éÓåcñÁì}Ù-ÍsæöÅÂçLÛ“ÒÖÀÁÛ7ÛY¦ÆÝÇÔÅkՖĦƪ Ó¼±¢¿¸ÌÚ¿cÌ~Á.º³ÐV»ÏÊ¢ÓoÃЃ×öì#Ï®ÎÖ`ì¨ÑÑå•ê*ÛLæ:îöêÅ mòZ“éƒÙ+òY(Æ'!*û'm'¬&1¸,>z8á)ý*°,V<øF’>÷=Ã4L7L3óFOLä>fD ) 6>D?¹1œ9ZHŠ:y6K{*¿-m1‡'i(­G\éõÈ‚ P=üCì÷¹?÷bê^÷¾ûéø–ô=ðGåÎÒ΂Î$ÚÍÑÖÐÇØÐ¬ËÎgÈþ¿€ÏÞ½NŰÕÖ̺ÍÄ1Å”¸å¿x¹½,ϨÀïÖŒµ‰ÜÓ¹3Á½ÚÆ&ÊýÂŒÖ(ΗÔ+×ëPßýä¸ÒLñö!î¬ñpÞBØ»ô0÷@Æt O"Qu)?ý_5Ý-¦$°+83î/µ-«.9”:P5r,‹J²5g)bLÜ?’A\>Ø$½VüR 7;9Í-€1Í0Í4Ä:e7hG 8Ô0„N‹4¨,#%„Òê; f0€ØŽ šïâ zö’öòïìádá¿à*òFÙ™ÖÕÐ Ú“Ê/Ý ØÒÔï·›ÓUç„ÜȦ½ÿ¿¯2ÊíÄr°\¸S¾²¹!µ½L¾ÆÕË“ÐI!ÁcÍÌÂcíÊŒÖMÑGÐ^Ýî)Ü«î†ò×Ìç•Ú1ú7ûKúyp b.'‹DSZ/¹3z}$%” ‰.RÍIä6£/ð/®4ë@[2˜9Ë?º9‚EäA]=6š9A³<? 2|A}9m/ƒ)äKÏ-G};Ü#š!‘^#Ë-œ,“sp-ÁðWòÆõvæÂû§û­ìîó¯çvíûܰê9ÛÅ„èŠãlÒ±æ²ÎÇÂhÊÁ%¾ ­‘ÉA½Û¸¸šªÏÅN­HË|¶3³'¿¢ÎXÃnÀ-»ÒÊÊ¿GÇ_ÎÝîËÕÚûÙÔæýÒåÍ»êéÎÍù“ìÐñâù£™3ïo} U>¿"<û þx-,ç&6L,ô. 7¿"¥5°/°X@f2ö…*o3Ç7¯0Ž8¦;-B1A=²AÄ=ƒ:Ú9Æ8_:ZU2IüG7N3K4gDšBµ,ß:‹/z §!8&'1L$(3Ñ€P• –ùÑ™äé£ý…Âôcð#Ö}öyêÌÙìÜ|ïuí<ÞÖÕ,Ò…ßðÈ$«ÎÈÚØQψƯM± ½­Í³­À‘¯ÿɊŪ·6ÐSÇϽ»+ÉSÍ`½šÎŠÏuÐ{аÞÈzñõÏc¿oÞÉãÊÏJÙm oé8âÝ c$‘ìz w·râès&à%°œ#î1|é$;¥JU.‚)o)˜4Ï;ê41J•7Wv3.7Í+¯Iµ8W:âIh8sG4:CAÃ>a5¢/Y=%¾*‹Ce!-=Y(D,o2 Æö]Úi4þÝ‘ñÄê3äì}ã3ï ô4òÆÔØ áPÍÍÈ.ëqÉÔyÔâÑÇ0ÌäÙ-Ò+Éà¿}Áè»#ÃPÊh׺uº ¶ɶ À.ÇËhÈ<ÈõÓK›ÃË*¿~ÔKÙ¾ä¯äjåpê'êFÓƒçõ7ýMôúù<Ýþê]È!öi 2ö!R%¼5©+o1Ö-ý7Ð=™>Þ6÷0”QÒLî568ìGÚD8?:‹AÂaOQŸ6þ,?\5 6©O&?¡2Ù%§? M;*ä;=Ì*”*ÉDW"ÿr7¤ †ü¶ê³éèí2õqîRÊã¿÷ñçÂ)×òÏìÏÓËvÊ\űÛdÁÞÒ¹ÎýϨ¹½WÃY·iÈ7ÏçÁ³¨'»¨°íÈ® ¾4½ãÁ<ËÛlÍóÉ%ѽùâÌÉUÛíØÖíjå£ÕVí¾àäèìá˜ï~îÝ üÊõþf 5¿½Ð-¸ Q,Ê+/ë(œ/Ä5ª7.',:5BA>×9«P&BÚCQFÓ4ÓI?Q;Z>¡Dˆ\³BôU™:ü7€7©D3B4?5w!Ê-<„+4.R­Ž'ªU^"˜y U˜öþ~þ© >ülÌòÈôéÿÞéæçñ·óÙ(ìaÎéëyÞù¹„ÕcËÊÀVË Ä¼Íí©„Ï>¹¯%ÈSÇDÀRÑËjÎeÑÅÕ»0»ØååÑÉͽÆ&Õˆ®­Ì*ÂîÒ´Ô9êÛ4ÓŠå6ïMíôï¯ê øú€Sú#2‰Çê!Ýý&è& Ú\°Dì!ÖOG*Æ)=&Æ)Þ ÇÌ*Ý5êç&¯A)aH  5èU÷Ç÷kü^ílh(öXëŠÛàÝæóuçòÕWÕ»Üjì¿ßbá¾Ý·o°þÁÒÈ åòØæ´¶¢¼8½†ß½ÆäÁº¿Â)ÃðʾÓ?ÊÕÙ5¶ÔÈÌ=ÔQÓ»Ì3ΗÔ(ÍÙÖPî­ð’ß¾÷MÞ¦ínÚêÿºûÏðÉþa©¤ÿýc)r¨%+š,H$Ç3r#–00¬CÔzÅC:HO¿.”D?©C@Bj+­7+;.!OKK·8Y7u3ì<• %*™1_9kAÜ0!F‹"w-»%9*0‰6Y´0M«"¶g_4~ëÙùñ œæ;ð8°äæÝÞëp×ÅÝïÃ'Ì3ÙaßëÂtÔåÈKÁ¹:¿¶ÐðÏ­Ó¹óÇ{Ì··9·ß²œÈ1ÎS¸.Èu»iÂý˴ʽ|镯TÉŠÊ€ÏqÔݘäáÖ—ÇøöéœýRÝÛßýÕ°ú¢lþQú«*‹X,ýŠg&M!Þ",¦=–ô(aCý;C¡0KEC¬5Ý:“Oˆ0,6•F:4ø:ÿ;ï> $;ø0%/@À%”C|=ÿ5î4°Ç:ð(~dÈ N"œ!÷ !$ úØ ‹Åë!íhî%ë›ëø’ìÃê9ŲĴæ¹ÊÙÃ7òw¾ZÏj¿ÛØø·0Éò̳¶ÀÆ]ɶˇÒӦͮ§Å©¦ÅÎÈÉÀ˜µDÀs²ˆ³ÉإϑÑ#ËÏÉâzàîÕ-Ôgé9ÜTó„ÓòÄœZ Ü ûl «Q‚..æP$­”#«¥-Ê1j7$Ë;X4V%3zBKC©JÈ9 B‹9í6Ó,D,e@ÕF4A1P>Ÿ&>5œ=;Ø3ë+®K \,(1ç:Ò¤.Ñ}š"ü,â°‡ùÄåè›óØèèÃü©ôDòÍKÇàªÚÉ×¢ßqÓöÖÈÇÌ™Ùp´÷¼è¾¦Õ„ăÄU¦+¹€³»¸Á;ÌÄįàÕÈÎÊIÇÙÜcÚŸ¹TÏ0½¶ÕÅÏ1ã»á<åRÝ®ã˜Ü ÃÇ÷øå‡ðé‰ Æ„ô6þ¥ÜþÒýx0 ¹O÷”*G*^&¦@s3€H1Ö:î+ž; ,Z9!º9p%¿RÇIiCÝBE±:ù)Ó4aB\.4éH¥!½9êDs@´;¹V2%G6¼#8*/@"5ƒ&¿  ‚å`p þ°ûlù•é2â·èÃÏ®êÂÜMä.Ҹܓ¼ÍëØ1Î ¹âÝá¸Ë€¶]ÊæÄ~ºÓy»ŠÁ&Ò–¬žÂÒÂÖ÷¼ÞÇz½¿ÎŠÚ¬ØîÙ¢ÀÇäuÂÞò¾?ôÍãoá'Êîâ@ûmèè[ë"ùÏö“K ûVøm-:G‹' ™%)G 5'Û4ô=:Ê?çK=<)Rü,ûGm4YL@ü>®$6ÌBDw/À>r@02·>¨8š'Ñ-\0¤=U;·H½0{ &?¾*K",$|CŒ(Nû¸ïXüfýýÈãý\óvãœÜÒñŠØè{ê¶Ö̾eŜ΅͊´Ï¶$Ï£Ù—ÌMÐh¼ÊOÆ‚´?ÂϦ±Â·ZÏ+´¬ÍµÊ³Ä÷Á¿{Ë]Ú6Ñ·Ð…Ä*ÔûÂdܽÒÂõPéRé_ê$ߨܡó×ìN ¸ôr 2ÿüC îE°+†È %õ],1@b"K5„9ìB3Å3›= 7L@p?¸*,614¤7£/ 9;8Tª0Á6¯PœO8O{0š1/ïE=8ã6ú!í5!Öã ;ô"¦8lx=¨®âüjþ“ôsùéìÙ<æsò£ýVÓ£ÔæÚnäÙÕåØ Ë/ã¼áhÍ9´gˆÆFÄ&ôµëî²ùÅʾÍ@à'·¹}³b¶GÍÑâZ¼nºÀ(¬ÈÔŒßÏòõÙßð›óԨƷöÎæLü„òÓôíî+yîPüsO žF ±ï,‚Û${-ÏŒ)15ö6AC0®95TA8é)‚5î=VBŒL}bÕBõPHÞeíGCs0â@“&)*IÁEÍ7I0¹<D<6y$0qÖ…‹Ÿ—ü…Ñ  ü®ø¸ñ°¸ü”ãÇî¥ÙVÞßÔîÉÕ×MÕ_ÏžÕVÕSÞ·ÇoÍî¹e»%Ë-¼Å¾wÝ»ûÇ,»¿†Ì´ÅT³G¿ô²^Å·²IÁOÐX½»÷¶vÐ6Ô^ÖWűäÅÐDÕVà´ß­ãÚìüó¡õNô­ÿ§4ýð¥ä v¬ö_â7CÓ 5%R¸BÐ0ª85[¿282¾1ñT^/Ž8ëFÞ,v"!Tx3Y0Î=ý@L;pT¤; ;Aù8¿,ADC;”DX.U.:"*®,Ï$„Cùí ~ i_üà ¬ì÷í—ãêõñÝ]ŒÍ%åIé‚Ò¸Ü.â4ËpÏQ½©Ö‹¿EÛHÌ¡Âܾ{Îè·ÈÑÚØ²¡ÀÿÒȱñÌøÈã°«ÉÆ Á´¦éÎJ²%ÌNÔͯð޽ÞùÓ³àÖgêí5ù¶óÌéYè ï;ñFåáè8üSêËHûÑ •$+R7j)1(7j%&'g:K6è#Ð60W/=åD&*Ã7ë@ÀT¯C¡2áQ‡8_8"8ü;_7#C‡-hFÆ%›:§;†@×3, ÍhS-œ Ç û  U‚÷AdóŽù´ø, ¥ÝgÛ»è¹Ö+ájâaâÌQÌjÐQµëOâµs±¹ÄØÌ(Ú2ÆLÄþµ÷²C´ÅÁ±‘¾¸ È$Ëœ´Z¹ÊÌ!½(ɲËÏÐÒڒײ½wÖßÛÒ Ú?Ô+õÝÖõíî}îÒï-ù¿ýVà %Ùù©þ`Nf“ûIñ;a&Ð8i0ž8Z'c8:'¶<ÓH‚D†2ZA‹:]Jó@8Rq2ÀhcI’DÆ7T0G<‚LÊ1ã/(DÈ* 3O<!À$âAÃT!6Â!H)Ä“ãöømù¤þvû8ñ'îHé¥ãºïOò¨ÑÛã®ßUÏóáeÏðÏÊ‚×t¾ôÝ®z¹ü¼©ÆáÖq¹W¸¯ø¥%±î²néQ³'ƣά»dÃÏ¿°±&ÕúÚ:²gÃeÓåàGÉ_ÌÿÔðÞ„Üçà°é1ôÔÝ¿øQÉëëÑrüýÊ;näN}#r(&a.¬$¦7$02–8w#3.0’5IHBŽ9M4>ÇCS=Ú;˜Mx>LCY;fJçC–6‚6BR'}-è2í6ü2Ç`Ñ&;H/#°3 NX¤"Kõ4ýÉóÇôCöCðÛªå°ÝžänݵòµâòÚÁØ"ÊÖ™å²Ä0ÞV¸f×Ù¿ÕËgÈÆºÏ¶p¡é¿t¾$¿Ÿ¼"·Ó½ë¿ÙºFÆ´Ýÿ®½ÉªÉÚÑÑÈ!ÉmÕÄÚ Ö=°yèyØûãÕÜâ:ã~öµévóºòT–íøM Îö ÆOëÁ"Ç)Ê1_/ã'«3O•.ÝÒ$í3¼,Ð7‰HÁE1I ?LHÌL9,"ñêà·Ö_×-Ó†ÈEºW¸Í¾“Ï㑹ýÊçÌå¿ÛºÇ&É•¾zÙͶ+ÉõÑ(¹â¢ÏòÐåɵ Ü÷ækÔÖê2ÝËå†êüÚörèÆó7è»òX [ó! n2þ) ™DU]' Cs)¦Î$³"J.!+¨£9}3N78+*'C±K +¡C¼F¹>»WU=û6­H+T#î4e2@á'Ñ#j(§=E/Æ ÈE/^!mzLûAÖq À- €þ³BðüŒÞÇð ßNýšéÈæ ôáÔSÞÎãuÓfÞ%¹Ú[ÔtË…ÈS¡Ã¹„ºGÀIÓKÄj½ìÌXʺΚΫù³sÏóÃfÄ¢Ä&Ç:Ñ;Ê8Ç$Òõ½­Ä‰ÜrÑÝðâMÚÀí¹ìjß(ãðåëYø2+ › ÚЀþ ï(Õ)—`V!@è/àüIˆ2í.{4w5a.IÿJ ;n@>å”;M+ÌAÏIT/R61SC0FŠ*~9N-'!;9´Z’-‰|S*U†Ò 2(OvÂöj$ðáYêj‚é:üÙá\ëüýžÖ~ÅÓÄ€Ï2Çr¼>ÄSÔ÷Ð ¯¦Ë²SÊ ØDÅ%È0Ϻ¶ ƇÅWÅËÈêÅ"ÅÉÄmÓÅaßó¾A×LÉ7»Ç¸E±ÕÉŽÛÝðÍYôÓÍ*ãÑé?Ü¢ómäZìyýœ/OÛ{Š(øò;Ç&… ª&Þ#Û+ÞÅ.-$85„3¯A¸K9È<<9«%'3ÕKÃR +ÀBíE C`=XC(T³P/E 7GH74ïz(ËC/LŸTÔ3`-=Y(2/Î%J å¾9‰ Lø6Óÿjÿiünú`â|zùŸä$á”êÛ×ÀúÒ+̘ÎKιÉIÃ×ÅÐÀ{ÙjÎáÚRÄ$±4Ãy·˜ÊصîÕ=»Ðâ¶êÆ"À2Äø¼YÀ]ÎدÐÖ(µ°Ï Ô*ÕÒÎfÙdà”ÚZëæQýéî% oì×ï+Œ vü®÷h E_5"™)",¨i#1:¨&r,:Gø+º;éH¢A1á913M>T=O2¹4)7Bá8,ðA=_HKI³1Û#kOU#Ú3/NH³$$­5~ü.! Áö O þôb¿ð)ûÿáàþ½ò.æ`ð~ØäØ×Ü`à ۻÍ[ÒaÈø¼\Í#¾1Ìͽ±ÆWÕdÈξû½z¿O¸ó¾ô¸ƒÆF¼†ÄÖÞ¿¬Ë ßÔ¼c¾vÖ¨ÇûÙßµÛÖÈÓ'ä9ÇéÈsä×àÿÐà“VüýàõYù-ÿ­ x%¡r.|øU†G[(/84&2+W7 4+710P%Ž,Ì+A8Ž5QIk2ÔCŸNIO.¢AÍ5E„Cû8 LÙ9B*)å¥8´%‘2¯,ï?-ªÛœ)ä eqùø†Š÷­úúÛÊðßãüïÚ8è¯àÏÒ ÔÐóOɬÕPÞTÊÃá½°1ÀJÁ„ãO³¾æµx½ÝÃOÀ–Àõ©œÐÀË«Ã>Äù¸Ï·äÔìÔëÕJÈWÀÉÁ¾àƒÖ Ø,ãÖØVÒ­ç®þôôYÙðöÊô?þø Rÿâ Qù`²ôïI)*‡(—å48+º1i3_66+.Õ+[4Ñ+°5¬N3?¤CU˜Xü<YFQ2ºDd5ó,êGLH2V\,J=›5Î!k6¹/#;Ú:#¬*ï#w U“• ™ÿÁ,÷,«÷bÿ½xé‡Û&úbùNì˜âaÜÓÈÝ é¾Ì0ÌZÌhÎZȥŅÑß½”²kÇYÒÒ½°¶æËŸ¶ò½¾”·ü±¼Ê®ªÉ„ÂçÆ«±ËêÄ}çо‹ÎÏÍÍÐé×çä×Ù€òÎðlê¨éçÛ>þÍíûáqþµýÁ ‹ç¬ÖÒ$C&ù!*Õ!ñ$N@e,G>Ô/ÄSžHº5ê?éC÷?AÓ7q4hE,V,´BÐ-¤6òA52BR7óCY5¼?N-Ð3í7t/‹$S «"‡% † ~øY¦ÄÒ Îú•óãËí\Ù×îæÄêEÌ:àÞJظÏyÚO·>ÆÌ¥½æÝfÒùÝÛ¾îÑ™´n¼{ˉ¹Ê¿4½ðÀ}ªÎÎýÕoÕ º£³ZÅ„À[¾ÝÛ¶¸SÓ{ßLÞ5ð0ÏMÙ×à¶êÜ”ìû)ü˹ï“çOŸðA÷ÿÅÚ–ª¸Ô »1´5 ÿ+.(Ž$6&71‘AŸ=íZ¦H›A8=l;I?¨;_Nª:&42A4ºAC9¯P™aaJNsð©ÂJÖZÎ à,ͺÁ}ãwÑöÈÀ¸¿ð·_½ »°»q»C±Å¸B·¼Y¯¥¨9Æ]ÈI¶0ÄåÑcÝÏÜðëgÝ[ÈõÑ÷ÝPãiîäêÝèþï¿îUâzäþ Óì¡ùûQ¥òb€ôî*6 %*tJF@L8Û3ô=WMîSÄ:mB€=/Ý6w3CFŠK58È?Á7æD³7yVAL™BoCs6g;V=|>©1H5ƒ$h)³„'(B>1 tÅ$JªQ%‰øV }üóü¤ì4ðFÛÞrÜ•ÚñàîåWÙ¤ØÏ×tÝsÇÿÇØSâµÒ ÅO¸¾4Ï¢¸GΚ¿êȆÔåÀ È`¼ÈžÑ!½Û¸¡É0­¯ÈÌ Ü„Ð¼¶2Ì8ÖˆêôÃWèZÃýáêHèeâÛþõîø*ïêjM<ý åNó#ü6Ð+rÉ9s?Z`ØB¸%ŒP?°3l6è<ËC%SþCT:¦3‡2'HË=Ì?‹)@ÝF˜Tv@¾3¾-~C*LŽAc4Á,ôA &i+H%73'(㹄 ø"¤}&ÿ<ýÁñ'ÿphù”ééìÃäœßCøVÙDÓPËßԺ܆Èèͬ×!ÔôË)ج¶–½—¿W¶çµ£ÊwÖ–Ä»¾q¥®Ê{Ô½Ë ÎøÍ£¯<Ã>ÄÂÓÍm¼¸ÌªÐËÔÉoÆèÚ°×,ïƒÕZê´å áUðzöL³5Bßqó ±þž À!e&i%,()5Ô0<2h9 00+4+1»;“%^Fè5IÚ@ê9[*êA¤C¸GÕN”R¨]n5ÚA†*sDp2Ð4Ñ.þ-—7ë4¡(¯A<÷;Á5m)˜Ga*gþ7ÀCFô(Š9È@}8M94(#—)ù,'‚0ß&ëÍ“´«&Ž U< ìj -”àØÊùIæTþ´ç*í"çeðkëXÖîÞ^Ò'Ò½áIÒ§ÒãÄŒÛÜÉ{ÙB¾2ÁÑÆ¶ÀÇäÀ}·¼¾Å¸¸\ÁoÊÆê„ËÙÇ•ÆÖ°ÒÊË$ÜÊÎÎ×Ï?ÆÌÈéÞõáëìkënÓWê6Þ¦+ ±VýRñ ¹ÿö L!|)])Âr(à)T(°/.‚C¨Fe6YAOJKÝ) +›<Ó<ZÑ0ñ(8:5.OìKtOÒ1_Að--7L<'6?I;h7& %a$r1Ü ¤ S×!ó$m Ëá j0ý»Ù ÅÿèÜiöPálÝ¡îãáãžÙ5¾lçÎÞ]äß?¹â_ÒÈÑC°Ý¾DÈϵÖ<ÅÁܯ¯5®È=Âú¦„Çî¤ð¸´ÃϼÜÐOË,³Óà ØXÜ{ÜçÖë£ýVß}Ü:Þýdç“ ÄöUùâ"¾ö&ý ¦uo±ù–r.h$W2P¸).;CD2¾5~6v_01I=yMŸNóVz5—PÏEÐ<M[,í5 EÀ7ÜB¹",;…G/@Ú3BB”#†-å-š@Å": ¡ÅS(Ó²°tgŽþé1ðîný6ÿ²ÔãêbåhéaÍ¥âÎÚ?ÙÐÌ-ÖÝÞ@¿î ´êؾè·ô¼Î ·Ò°°´¿±6Æ(¯aÈ²Yӥó¼ ¤¶9Ï`Þ]àÔÒÃßáQԘХ֪Å"#å/ò©ã÷·ëåbñd‘úþôé*¾(4²ï(€8²(Á=A,6ð(êÿS|T¨O'D9J:8EB˜Iœ73“=ýB>¼ŽÂµ­Å»É¸Ã»É´Ñ>ÚÃâ)Øäç0örå¨ç+ë/çoåññ‰,éüâ4h;ûüü)Lf!›üÓ6>"ÿ"ê't4&3í0+`2û=X5K/ûAÿG°@îDÚ<PE¼W‰4g>ý?ŒGà[Õ]P9yDC·=Ã.ó18=5°$¿2Yã™%Ê$ViË£úþǽõöÿië#ÞØóÃíªÝké³Ñƒì~Û¢ÐÉÑ†ÆøË$áîɸ»»ÒŽÍÔÏWÇ®ÁdÇ0µf´ÏõÅcÃÙÓlÕÁ©z»¾¶¢Â¤ÀÖĻơܵÅÜÛàÙ!Íáá½zÚ³ÎßKå¼í¿éùâ±òÆö,ø‚«ý8û S–ÖaAW•‹,5£ ©,7p7F4Ë*ý3R9//O7ÜHá>GB)lI€3E_1WAT@ÝG97Ý/_5Í3JÅM*ÿ,S9Î3,9:40Ó"é2ñ ÷%?*!k8èõÉk³þièñžäˆýòëFí}æØúôõÑaÛÚ¿¯æÙbá Ø­ÔŠÁhÁ-Î’Ï{ØxÂj¶>ÍvÌc¾UÂ]µäÄuÈhÓÚʻȷ>Ä)½*¾fÂÕ4ÈïŠÙvá Ñëå:ݯãfÎæë,ÙKúÿÞõêäôóLÿ›Aþ<| ã:%u4Ø4º,÷%=;#dP.š*v6µ?d55l;zO`A;C“;äTgEYK),åX*Dd= <«0ê0eëP4=’5ñDæ<þ+>5p"D$qA'=–‡»ûùÚòŒìÊù/ôÎådÞËväi×bã÷Øcë3äøß+ÄUÖFäoËþͽPÏÌÅÏ¿ÄÏYÅ¡ÌÚ¤¤¶LÅËâ1½7´<¶ûÁΑÄ|¾Àš.ÙìÐÃ0Òã ѰÄ@Ö®Ó×Îëã*ÖtÜ'÷øÛ'Õ~ÿ…ŠöLÕ¡úZ RBÆJl~ 1 F#S&FŽJC]=l/ç8]8²DÉ*‘B‰LK¼7ø5…>Í!á4JJõC2Y™C];l?CA6à9æ<ð9$@Ñ)["%x"ã!{&M]Õ%è&mb ÿ\•æÜÿzúÆ9ð„ç¹ø•ßBðQÞÆfÔVèÃÑ1ÏßÛ™ÜNß^Û1Ä/ËÝȲÅWµ\¹ ÂÉq¿¾ÙÌîºìÌI¹Ǻ¹Ñ“Îì°Õ4Á¢Æ'ÃÒߪäÆë–Â[ÎâÔÑ!àÓç"ããÍañúò£ÿjû`µûßýÖ·uç°aK L;*(%ƒ8¾)”«)@.M31M+É4 BF2›;BDkE-?NFJKÎ:=@SQT5n?%IZ2”735sJ=@O!Ò5Ç%Ï3%&Ú7G4Ÿ'ó k*3î z3iŸ×¬!WNýUí(ý’åïqëâõùç*àåHæÛÒØNå¢ÑƒÄ(ÒXÌs¶tÍEÃ_¨½á˜º=Â:½»ÍgÑÄÇPÕôÊÊ“Éà¸fÌK½ÖÇ´CÉ$ÖÓÚL½«ÙgÉt˯ð³Ö‚¹Ôß®ÔÈÌ"ófîmêÆî„úOûñîŒâÚ R êÖ"8Ê'14 °(0P%€4-<1¦1[EÅ@(Aû/ÏJü"{J‚6ØWúE|V[CY;û/QˆO/0­0ÿD‘7='6w#|5 !%$È#!$?² £'Öÿc3D` ¿Ýôj3ô5ñrå¼éuÔõæ%Ó]í ÑÒÊ‚Ê ÃqÏ»ÒM ¼¨ÙíÚB¥`ĵËô­Á¹²9¶4Ç܇¹ ûÂ×fÂå×c× ÂT²ÃŧßôϢ̲޶Û_ë éÉëíæí1àjÿGñáóðøz”àô ¶ ñ>ò•5>Ðë2ê#ä.Gi. ?o@G4°5‰9À@è/X4a4`$^Y JîAyD;9rC|Gó.öC‘C2=êAb;*7¤]B:¹#K&¹h4nV4÷*o(V {ÿ -ö1%¸*íWò ß¾ôaßã¤ä‡Ì¿ÝÀÎÈvÕ%Ä,Ö?ßÏÆJËKã÷ÕªÒ§À~ÃmÁ€É:ÌŠÄÃO¼fÄZ´ÖµvÊEÑ{¹¸ÇÌiÒœ¿´Ä®®•Ç'ײÕ)àvÏ]؆äX×0رæÉméÓåß û‰qü ’8 f&"Q0½¹T"60%€ç>0X:D9¨Hž5C<{6rBú)¤?Bf/ÑJ”:Ù5·TMÞ2x:G÷T²HüBB1çJ‹6ªE+7Å#Ó.Lÿ<2²$%„x Ï-™ M%ßÉ—íþêâùj €ïˆúÛãâÛëåú拽jæ¿ÝàÝ™ÍdËGÊÿÃA¿yÊÐÆE½»çÃî¿·ÀW²ºbѵ¼Õ¿‚´˜²³Ñ¯§Ì«ÁîÎt¿æÅ-Ï…ÄÍÏͬÞäìíÊÓ×¹ÒZÒZëUîÙ¶ýÝvËòØôõûn~Ç ‘ óþ)z2.m h*·&ü(Ý5šM F-H‘>Á#@P*ñ4ˆ-òAÓDD[@¦O÷S:BHMKþ:9B91`KO0·OöCÏHf#ÌB17n#ä+È%Æ8'‡«4±÷ h ø§ K Kù˜ùæÊÕ*íeãÀÔåGâÁ÷ß·ì™ßôËŽÙ>ÊKâµË·¼ž¾sµú¸}Á[­ÂÂ’»ÖÙïÂÑ˵è¹I§ÈZ¼±»¶ÐcÐ(ňÑËÚúÑ¢ç‘â†ÔYÑÙº¾ä§»ìú”õ”ûfòœï°ãø.)5$ó@Žeû!à'&a¹)å6ê/Á%Y4¬=í.–<FÅ<<##:öCE9‰9nSf?H[RF>P&,ãNõ+Y/!MN9[8U"˜5.[:9+§$/ µ-R&‘Á÷µ.üCèÝšûØù¤~æ+ù¹ï¦å¯âfè¿è·Í‹ëä‚ÕÊÚÌÏéÑÎ(Á:Õ™ì|¼3¨hÑñÁ¦³šÆ¹Á*¹Ø~ÃFΤÄÖÓȶ„µ‡àžÙ§¾.ãÐÅçÊTÛºá Ò@Å’Þ Ú ÇðóüûƒèÚíDoì¯0íî[í5Vÿ´!ÄŠ…þ– ÖºÕ"L*„0k/z*ô+(2q<68ÿ<N;G(ƒAø>‘GÐ65ÿað.BhO÷8êCš52¸/83›=!4”fÏ6EÊ5Ô%Ô ª.¡ær5ývÕ³jþqÊî¹ôåä[ùjÕ™ðÎÚÁä,ׄßÚÕïË`¾~½¯ÐÚaÓ_ÞpËÆÑÇS·bÓöÑ€²/ß7¾6¸ò¾äÕ”ÃÌËË.ÑüÝÏB¿,ËFÑxÓ²ÐFÖ#Ñ'Ö/ФíäIüIÈ…è,é“Ýu æÛÿŒæîåýß*Êv É z8SJÿáP3e|ä7Â.u"Ú>ñ>m3ßQtSí;MGäKéE)<Ut=gG}?³8¶J«:¯BwB-;©0^RF.Ó>_&9ü!@n˜%~, ë%3'?õ;~‚ý·œÚ,öó½ôž¥á.ë.ð õ­Ü™â`Ú¹ÜKÌ%ÔLà±×¤ÔwÐØ´–Ò Àʱ¹»xÁl«ŸÄ˜½xÉ€È ·"ȩĺ¾IÑ?¿ÚmƺKιÈÎËÏÂÂPÍYÓ›Ìüâ¾åžá}Ôlä" ÚÒöpôíò%@=Ù!õ }ÿ¹ ”å˜.v$64'‰%26=DË.Ã7./Hœ-9NÕ=óTºB$85ê=;×3ß*P5,%+aKåGY4ý1t?1á9j!\ŒÂ0Ý'²-BT ßOxѰYóU ÿiñÓù 9úÛ"úºß7ÝÌ7Õ«Ðëà縞ÖbØ.ÁaѬ¾¦¾pÀHÖ Â¾§ª»>ÉX³hÒŒÃ,½"ÂéÆ.Â1Çæ»ÕÀ<ÕvÊÒÙeã˜Ë È©Ï-Í5ìSïñÐÓ«ðÂäÕÿ£÷‡ìŒéŸãpû«ùÙý–Ûf» ý}.è3 K n,F-·#4?õAÛKdB/CL>È2Ž2b'p66/ô8F~/c.v2MêHm=ÅH +-/Î%¢2«?z-ô+ú7&iE p|Ñ ˆÍûÅ1÷wûû!ôpüMâáñàZúÃåÖGìøÚ‘Ú¾Ö:ÏìéeØoÏÃÉ%ÂEέÈ{Ö Õ½R̛ ·× R¸‹»ÂµNÈŸÎÇ£ÅôÂ"È»Ëh½ËÙ½´¥È÷Íιè.Ò"ÓœØuî‚ùõ½à‹ï+éOþõËà—ƒçmc.vê£X k'Ž£0&*Ú)Ø&y,î+5²Ž.e4fXeG.7³4s)à2wA¶Jö@_AIJÞGh.a5ÔEV<Á2šE0Â,Ó$Ó@0;`9ÿ5¦,€*é ô%Än €WX±…3ùcÿ[çí6÷ëî¯ê«êÄæ¨ãëÜÊԔϤÛùØ¥ÏÛvçÐÈ’°üÖ*±·½ÆË·×ÊkΩöÄN¹<¾bÂ޵ƸQÀ ÒÀª¸ÀwÐäÑôݬԒϵßaã5ß*á"ÓÅê»üí¯ïKâ/é2ô”ê7ïø pþÁó åé+"þW]ë 2n< ®58«8J‘M®7­0Ê;Þ*uM‡(1K¨*ÚBƒKƒFÜKV,%A/P%?:JR.H5eCƒ A* ,+ £,–q <yå,jhø¥þ4뉥ô”ûû×ïçâhòHèvñùâ~ì™ÇÃÌì@ÚãØ‚àNÒßÒû´«ÎÈÊ»,ÆþÇï¯áÅ?ÂŒ¼§¯Ðº”ÇöÇ+µ:Í:±ÀÁNÌñÖsܵÇp¾öÙ…Î1ÇÔÙÁÚÏáÉéýîTàå‘ï€ëïöû¯ÿ×형 Ÿù‘# m¾!¤ %Ð9ÆÎ#j:Ý%ëA²=îFÊ44.7ì9Dƒ.N8°EÙO66ZæK&Gž.Á6">çIÝ3*KS´:Œ3ý*¦%¯:û#ÿô/¶(Áè*£8úü ¬/ øùtÿ&÷`áèÐâí4Þ&ÐÄÌø²á|áà.Ù&ÝÕÓŠÈÐ)Ñ9ÒáÆ·Æý²Ì°Þë°©– ǣÎ{¿º0½ô¹öÎåɺɡ¿.Ì]ÅoÜ/· »ˆÎÈÎØäßüÜ<àæã’åMéæžéPà;÷Öü!÷²üç¿´íÛ 'Ó%~f0Ñ&jÆ$:A./ö,w3[,‹*¤H§4F5³7@SÞ(¼?Ng±:’M<7%B‚3´#ÌDA>;$*FIÜ2).Ä,B3N1#³.Ÿ6Á'—"pÓ&Ó(¬Š!$ýI ˜ÿ‚ù ü³ûÁûáIõùñã èä1Ýüæ™Á{ÜCÎØÞ§Î8ÊÂaþ°«ô×ÂÊ—Ä^Èο¯¶]À›²þÝk¦ÓÉQ¼í¨áÅY¹Ïϥ̆ÙYÔMÉrסަåôÈ[ê Þàɨü’ò0âTðLéu¦ñ"ú†ä>6&ºŠ\:ªCü:á?9ÝFõ;9ýL1C3HT)>£N£473Õ0[3L(Û(ñ(x$ ¥(¤Ü"þ:- Í!šÛ5 'îù? Åð· éü¯êAø—èúð×ÙÞ×ÏÐÞæ™ÌÕÒ¢À~Ó>ÊЂíYÆ2ÎPÐÓÃÿ¼Š¹ŒºX¹ãÍ‘¾¤QºôËÔiÇz¨jÊIǪ»³º`áíÕáÓhÊ#ÖÇ·×UåFê%é›öÿëÓåºèºåùÏC®¶ä¾$W!HX(í"Ð-t*&:0à+ -¢KoC:D8G)B?‘B¹=q,¼?oDkPB­4×0±4Ê'Ò2äRÑ2;s$V8á%…74$Ö#Ÿ5ñ20+  óünL(þ‘Dÿhüñ‹íüGòŽæ²áOéhñËæÞÕNßæÐšÌ.êïæ7»ÿÑܸ»‚Ô¯¼;³!Å Â2Â¥DÇÇ–ÆLÖd¥Ì'Æÿ³YÌ%ºyº½,ÍÞÆDÅÀÂÙrè ÏÌÚ¶ãríáÆó÷èfù ðœàñÉýcþYð‚ ø “)Yêõ ðG)'E2),gþ: È%ÒG@åMz<ûE]7l,QS[- @á@œDuP1«>ûDx*LNõ?žDa$Š:ÿ&Dµ1D#Œ0ͯ9‡$b‘(‚Œ ü‰¶ úqæãùèdû"ÿòFã+á;ÚQÙ,íƒÐÞÍÐÓÕȾÒRË)ÇÕ@ä2ÈÆ¼è¶©ÅÐ?Å¡»õ¹¹ÄÄ8Ý·ÍùÎ Ë8Ñ]¸RÌÀçºä«E˨À.Ø’á…Ö®Í9êxäbÛµêRܺï‡ñä¸úäë ýüÕú)EÿòþÒýrXnmú g#/ v(¨2?Bí+‚-Þ*R?-?ìB!EîFÍ@{A~AýIKÅ5-.Aƒ>k3LTæ=<¦9ï@*4z= -v,ä-­@|?R#Yå*µ,õË4œ 4ô4õã.üçÊûöôë” èÞÛäSüàÃîç¸ßÏNßQÌ ÕÊÍÃÈÏoÑ©ÝõÈåÇh×P¶¥±çµ®½Ë·ÍŧÁiÅïºL¸ÄrÀáÖÉË"ß§ÅÔËdÓèádÒ?é@ìãëëÖwÝ*ÝÝäí2Ûãô kõâùñûGóZg*®,Ô^•Å)+]0Õ#S9Ÿ)´(K`?+H@?TBy)&1ð9~GÔ>þLÐOXS{@¿)ç-ÈC}5¦3y1è+0B1U)û#ÏN1$'"²T!§ €IûÀ ùém}P îƒíÿùMÚ­Óå{ØìÅâÕäÇì×\á\Í7¼¼Ì‚¼n­xij¼ÏÀó¾¾ÂÚÁÁµvʹƶQÎÓ§ðÂIÏ…Ä‚ËͽßÓ“Ä‹ØÕ”Òûß]ѾÙiñoáùìAè*íS-ðù'ìi 6éYËõªô é þb#­ì*n6 s--;HJs%¦+g2j0I#gJ‡)n9kGæ,=>WG9¹JU,>TR;¡Mµ>s-k@Û3&&­Á#`ÿ;þ+ *Ï,© €$:õ!i{2Ø 4 ËìNù3ôˆãçë/Ö(øÐðåŒæûðdípÇ3ØË³ÐÓìD×LÞVÑ\¾/ÐÃÂéËî¸Ç¯¿î±‹¹X¶®d¸PÍñÁÉB´Ù¾0߾߬ÜÍÎÞßDãlË’ÀñÓ¿ÛÃßVê’ÒäêÃÜúñ¢ø¶šþZ ­uWÒ '&Ò(£#Q.é@6L)/ž3€2ö4I$Í:ˆ8s7çIy?Ü3}9GcGN¿5œB;MŠ+¯>Â+òCÉ:_4ÚJŸ!=C0E»·&¼ì5Ú8V(®Š(ÿó ˜°NïPåP-çzö-í“ãŠå¼ãjà¬ÐOÕ ßKã§ØœÛ²ÚÊɽÉNÁdÞMÊoÁÑÅg·'ÕʼÌʪ̟´[­2çÒÄ[Ø3νÑIËËã½öÛ^ØÎèAØEØõÞØŒäïÒ ä–Ô,Ú|êÌíÿ° \ÜY#lÐÀG#ÂØY%Ú"ð%_1-\)g#¶854K*;9ùN}CÕF Wh6¢:/3-UNFf0²C/C´Iú5F(¾'€-›'¹3Ú*L1^"¿,§&)q(a¶EÏò–Ä w Ž, mí–ñ0òS8þpë÷÷‚×ÒÒ‚ÄßÛþ۳ƑŮÛE×yÀEÛË•ÚîÎ^ºKºU¹TÒe®o°è»S¨¥¼–¯äÄ©¸ýª«Í[Çí»|ÈʱîÑ‹ÑÆÚ‡Þñá°Å%Íiì1Û6åïêªØ¦ÜšìüŽò‹øùó˜vkþ$õ Å©”ç b$²9J&­,7ú.®;”HDJë@S;¬? @=B 9Ü;@IÍLÙ=Œ=žBî1ô9‹+_?EH­,j7†)41û,Õ+A(—(dHx 3%%Mn!@#úzýÆÿD¯ôTíóðæ(á¥Ü¨á¨Ûkëÿê ÙpÔ„ÉáÉ Å]̴¦Úý¿^ʹ4¼8½rÊÃ<­…§|·®ÇëÒ>ÈúÒÔÎp·—¹ Ê/´¹ÀªÝ¹àVÙf܉շãÐÀzÞ Ëü÷Vç«ÚYáTþ7âJ ‰üÙýZúg÷cˆÙ/ó ¤üO'SÖ.¶é6)ÿ(„5Ü8!)4GD-‘,/õ:ÚKl@Ä8™2€6šP_Z‹OTü:…2$EI3S‹ 2,H*ŸDZ7l™| ž+ºi Yômééùõü¿?Mâ}õë ã©ê±äÌ×#åÚŒÚØÒØÙÖÇBÖ•ß[ãµÑ/³lÛ0¾±Ñk¿8¹)½"±»¾!ΦÇnеÝÑž²‘ÆEÎYÈȇÁTÒ æiÅ(Ô:ËÛÃYÓÂà&מÝ4÷çÿï©÷Z÷§ãöþ1äç (Gó2Í´dÑ$s-ˆL„#2+u2(ˇGƒ)2F©NB=@+6=`7Æ<]S|:Ž,†?JéFj:++c?5Ú2E&­Sü:€>Ž'ó2Ú: !ß.H ½mN{#èBÿ]u Âý¾øàzJóö–âßËÛzÒâçäéñÜ!ÛÞÎjÃŽÓcѼÚè€ÈoÔÎÌ7Ë0Ò@ÆÆ„ËíǼ¸yÆÏÓξR·=¶l»•º ÇŽÂÏ1¾[Ù¡Î3ÒZÔÉØwÔbÞ¬Öpà¯æ—ìUäRófúÆúÎ\†Sr FúV\ý_ ÿ‚ •0Õ'+Ï' Þ8H5k7“%ÃC.R>t162IÒ3eLd0$4ù;õ=iFð/w8öCÝ2>TdHÒ;h7¶@%1(({Q7Á$†-ºò$I(ºÐ€=¯ çI ØNòaü¬VñÑÖ¶ßÃãÍïpΚæýÔ@Ùÿ¾ÎAÉNÛóÇo¿Áq»Ë¾¤ÃùÕN±fÆVÍAÌA¦IÎý²ÓeÂ2Ã*É ¸BΪàͺÕÚÔÎ̦Ñ4ÖÅÓÜì/ÇPÖJåyÖëÑÝåÚ×–èñØõô"õÜñY Ïûô¬ $J)ƒ1–±¾¦Ä(2'n5Ýì6ë<%2å#@=N7?)-J<ðLE|MŸL¹;–3Y?¾7*K›9oŠ/,çKI7Œ0œ6ˆ[/a#H"2])hÿÕ¡ Ü«ûCü÷ñø{ùßòà¶ì‹ßœÐbå†Ï÷Ë¡»9¯ÐÆ”Óæ¼€¼ŸÞ’°IàÄÖŒÐæ«Ó¾„¶ô©HÍ9Ü“À¹ÏÝÍÂV۲‚ÍÂiÅ?ÔuÕ=Ë#Ó6ÚeÙÎã4î¼Ö€ðaç‘á¾ùÓú\î„ârðÄøæ,Íöê%»!ïàÅ +J%@Ã%1%#5XGf?ž7G5W=2¶5±4@@øW’D¤;ÕMå:³D¬;6†L„CrJÕ2A3µ6?;Û=¾;ª3íÛ}$¿36(T $YÉû%MóÃÿHó«÷û×ãûí&Ü[ú-â+ÔGÜSø É¡ÊÎŒÀ1ÖöËÒÊYÔR±¤ÀB¬+Å¡À¨ÉѽָßÖ»­µÅDÇiËÖÇ*Ä)Ä¿ÂÐ\¹ØÉʜԱÏjÔwßÙÐiê6å3òHôâîÜÊ»àsÌ2üÕqBú”n»kô‰Ê*ƒ âe¯ ó4Â,~<0@J4Û=.G,t:Â,[|Rì1ÔY‡0À0Z:é?nCØ38AvEŸN&.;:7<~>J1h>7-º?,m$Ò@R `6Ž$Ä+¼&µ*^ÿ© û£ —ú –’ûßß!îHø˜ ÕÝ,å"Ï€Ý=ÑÔè‡×iíðÝQ¿ŽÌÂàÆðÎèÇÂÞÖ¾¾ûÄuÁÉ=ÃýÁºÆ­É¦!ÐØá®¾MÉèÚ@ÎáÇ ÈLÓ)Ç’É÷Ç]Õ4Ó ÝœÜYì-æfë[Ü[Þ“óì=ûÝåáòÆþçî.¤ üØýÂ%­®+A µ&H) &±8“9aCV;È3=.á<As9µ,ôG(5ï;ÓAÃ=zI1ÝLŸ<à7ÀHP@ß73S1%404<ä1:,ñ)I50ø‡9„ G(8!¨Núýà/!u rþ)âRþŠéyé’ß©ãçpäMäEÔþįºHÒ`Ç_ÊóǃʲÊÐÁ±;ÁÅ?Äû°þ°^²±ý͞ǡи=¸O¿h¸=Îhß÷ѬãÐÔrØâá2Ò’àIÇuæ½ÓÓÝìòþ=ÿ®æÑëîdÿêåÐs†´ “%Aþ!âi${+Ý!Ã/*77©4òA&E,bJX6\H¼FO}W(P£Jñ8¨GjQ1A:2^HG/v-×3,e:„@6†[7°0B"Ì 8#îÇ Ž Ü‹©Í’é÷úßgûpð"áEë¢êã’ºÌÔ˜ß;ãxÌÕüÅ ÊÁ{Ã[Ç„ÄÔ­ ¿ƒ¿t²ÑÇüÉÄÓ†Ñ'³’¼CÈ”ºfÖá½Ï¿*ÁN¿ÙØÎøÃÕĘçæÎ ¹fåÑ>óÌî=ã„àyøañÛçq CâÄ/ó2Š ¨ k¤l/ë+Z7šá5É3ê6‘/ï-77*B°E´:B4âH6R`DÈ?MxKªALK I.*i:W1bHUAß:1©;U)¶4Þ!n ïØDÿæðëR‹ 7‡ œúô{òËåŽãzÞÚ;ÂÎÝýëÈÓÐÖúÍÈÔ’½sÎFÒ#¼±¶°ÖªÂ¿É¿…¼`Ò=·q²cлκä·é¸@º}ÉÝÔ¾ÆæÈª3Ìà"шÂqáìË|Ô ßáÞרæzÒ õ9âzüÊöŠý¿üçüÿ£’øXk%| ß#¸k 4%›0Ê8G5”!Ñ/ )%(Œ)t9–%Þ+ ?)u4ç6YjK«2ßIƒ-6Ò5–FÆ8)6ð3ï.ìz}!u"_Ö`à3ý%.ÅëEð‘âþY÷Žÿþóç²âÔàã½ÙÂãäÌïÊ1ݡɹ´gÒ®ÎÆÑ?ÒSÇÑîÃ!¾ú¸M½5Æ¢¸ÛÁTÂÒ½·¹Œ¸EÂëË7ÃxÒ¶½3Ë·ÊùáзÆÄÎ̆вÓèkÚOïêTíÅíõÚ¦ûS D„eýìÀØ À­ ïÞ Ô(—(Ë(wk-F M"6k;³1/>(5L9À:´=Á*¤7©Sm;6>,G²TCä%@9^MÉÐðÅhÓ(ÉU»ñºÌfÉ´É'¥‘ÌQÄrÀÖì9ãíϵ®¿‘Ês¶lÀâåàjÛÅÖÖåa×mÕ×íVÖäñÉéCc”Óšü'ªh·Å ê)æð(k9&5œFl,©<_0n54F|=1B!<4i7$;4BLÞNú=k/CO¼@‡FzBy,'^FD_H9'()fÐ1õ3ù- "z½>#€blíØ ’ž³ð ñX ì¿Ú/îÉÑ‚ú“òÍï€Ú§Û¼ÛíÐ<ÕîËÒÍ’É˽`ÂÌǼÅ/«Â£¶ž«Ë»ÝÀ±Âd£·OÆ`к¶Ä¼É‹Â¹Ç£È²ÞâÎÇTÙ–ÒFÚ åÖÜNî â;ñ×Þ>ëÿ÷uà°ë³÷¡öý6Ö . \Qùð¬"[ýŽ`%v,ð.Mˆ5ôZ¶;¹:S:¾>î6Í;>:£Aq0bIMz9‡=çFURøHâ-J:„;=@Ê8î<š)Û"|1k,î4 :E{$Mc]'Ü"~ÞœýÀåHöªó‚úÆèùûÝ\Ù¤Û_ðÜ ô.ën×ôÈlâf¹eÐoÂîɬÕqÎïÓ¢ÖÈÒ·¾Š±í²!¾~ºóÆp»f¯ ºf³qÖ7ÏéÀl¾‰Ë,θÀMÏ€¿í·îÃ2Ô ãkηÝAΤÝrÓ÷Ö?úÕçœù,¤e^ßäö])‡U ß+  Ê=;6õ2+,;F°?I›Cƒ+ 7±5®;r+Eþ%04X/>*¸1.A}V$ö#=¢¹:$$÷ ÛõS ý¶”ûØþj©è:ï=åIçÕïÅõñà‘ðÔË$Þ4ן¸=¾ëÉøØQÚî«cħ¿º½û¹•ÅÓÅÇù¼%¸n¹x·š¼zÔ;®ç«o¹ÌVÉ_Â@ËÖÅ¿Ñ^ËLÁüä>ÔбçÇæ-ú*ÒšùøìbýÉ^òž v×ó¨)-Ã"˜G"B*;%.ñ„=42ƒB¤1#2H(3UæK˜4Ù8¡58O9Pî;¢:¹6ð).³J184¿.«<.5G8ˆOb/_;¢ÒxE9=pÕ$%a{´“ ³aþ5ß ëø÷óàë|÷`æÞpØyåÎôÓu„Â.àÂóÅíͲÅÍÅѰ׺ÎÄeÉÒϯy¸„Å»Œµ»±ºÂ^цÔÔÔ(ÏÍÒøÁ͸eÖÚÆËÎCé(ÐnàÿèÕ[ðÛ~ÛkÒ¿îvë9÷Œü}ÿ 6 ú³ýkáÌŸ@[Œ*!*ú1S$@8*`/Ó1Ø,>9º,Ò#‚6~NW¢4.L°U +;6‹3Ë]|HX9è:á.b>6GKŸ?¼8+!æ0é.e„4vA#¬#þÒš ÚÒ‚¢å‚蘒= ÂïI÷sóSŤç>ò›Ù¤Õ`èÅÔøÅïÎøùÐNɀуÎǰzËÒàºnÅÍÊ›¸)Èlнx¤DzÏÌîË¿¼æšÌÃÌ=ÔfÔêÎíÖÜÕØØ±ÎÞÈÇë5ä†ÓÙ¢ç¡ýé;ú?ütã8Ò“ü§ b Î?&3(},´…(,$§:15ƒ9é)H4¼ C*t:ö?“<È<ŒF¨>;@V×Q]>N1ªM¾3N>4E´J8 8û@ÿ$ 0?ð/é†ð&3,D>`uÖ ßìÕžê˜ýrÝIûGüjÈjéRà„×ÒÉÐN¿ªë”Í0®ðÊٽ׿¤ÎµÈT´ ¾<¼hÁز¾¾»ÀeÀ?µ“½·4Ù,Ä4Ñ€ØüÁKÐvÁGʆÏòĵÎÜÙÜ×ÍÔ¢é¨éTäÎëåùläJø`ë¼;öæé»ù¹8-_» ¹!÷u1'#Ÿ"÷0ó]:Y9s#H›2Ü;]OÇ;\1»D[?Y=a;F`CìF]?¿M@jD:B;7/(?ß9O1ý2©)¸bBô3Ã1'J,„ é ó …, êýî‰ —ùù<ýÛ¤ûUÖêï˜ÛÓìfÜÕíjÙÛáøÏ^Ñ ¿oÂÎĵƒÊá˱ÁYÆ­Ð6§>˛μy¿fŨÑΧ!ÓCÈAÃÂÏxÃùΤȷÌÄÅИÉðdžàÑÙàљΗÓðßéìþâ¯ÿçÌëçß Öã¼ {=þ‚ŽeŸ'„#þ!¯.6&ï2ƒt­I>ÔS–B,¦)5J¸Nf/N>75.“.H±@‘Nÿ6e9"0E7}5‰@û6b3ø:#$=2 %÷/c(H.&³z¾sž÷v¡ûàó"øÚèæ˜Ôåí‹ð$ð%Ù¤ßËÙâÁ ÕkÐ‚Å‹Ú ÈìÍ$ÒŸ».»jÁI¾çÁ*¼>ÀÅÆQÂ@»ëÈŽÉõÄ­À:Ü㺭Ø`Åhß(ʲÏBáã~ÝàÒöáþßÏâ î·ôÉæ.öñîzþ˜ï öéÀò´ _^æ/ê°$c/Ÿ *gÓ,Ö#¡(‘5‚"Ó-i<Ä3YS(“*N1ðAÌGêRá8×#¤4{UU1U>¨5wJ&):9žC9%D®3bFp=ü/2þ<.*,=ÿuî*ŸUÂEú&þÉ$vøIê€ öûôÓ¾ø¦ðïÞùÖ-ù»íæ âOÚMÜØÌÓ×CÒ˼¬&ϵ¾ÍÅÍ®}ÐÓÇñÖÐÍäÃÞ¦ëŸÈ´ö·KÀõÅ ¹ÏÄ5Ó¬OÏ#ÒoÀ`ðzÔ$ì™ÞüFÞŒ×ùÖ”íÅùKä†õ[ï 1éë•ó÷? ¹õ !½$¨8à(ï)ð6ê,Ö/F0´}2c+jRwA‰OhF`I7HS#!ŠF}Rå7®?#Q5? 0Ç)Ÿ:»8œ:´+ùF±;m@×)Œ>^1æ+ GX+â.¸ >˜'²÷3š2+ ë±\úÑ邸‚ô°âŒð~Ü(ß>ÛŸÜÀË$Ñäֿ͆؟޾Ñ\ÁÏÆóÔ[ÉŸøÁÝÙ羸ªÇ½1ËþÄÔÊ ·^È‚µ~ª ·jÕ ËqØÂðÉ*ÀÐʱÔІßKäJê+êÒé‹úéØõøÚíéÛc Ïèz ùHÿ å!"e%J24 ^<â+!µ*Ö@&‘F4)w< ;GË@×533ÞUæ:Ô%w3I?DèIÔL`?½4+?0â;6D9 C2ãA’2¿7ï#é1"+æ,Ô ýp _¶Á1#l´íïî‡ò‘äð^ê-Ä)á)ÌÔù×äØÜÛåØÙúݰÖ@Çx»ŽÞc¿Í±~Ó-¹È«ª¤¾[ÆœÖ$¼dضIÏÜÆ\ÊGÖ"´¨Øêä¾ÍÝrÆ)ÖWËÐÞɺäí¸Þzç)òö&úÛø5øŽõûZ _ÿ«"úøÿ.B3(–'(9(Ó'H¹(q'E#”>¼1µ9%q5\9=‡9W/cP<>â5âEU5CY 4AG¸–K‚7}Q0v9kls*Ü4J,ƒùð"F;ÈöÇþ·úçþºój ˆï¹õPë2ôoâªÙÆÕnÚpähÛ0Ø,ÚÖ¾ÁÒ‘ÒOá×Á*ÃÊìÀ¹‹ÇMÌ5´ÏÇÜåάª_³Q²y¿yʸdÃÃ(ÔsÕ¯ÛÐÚ³´Àþè¬ËÏÑçÙ=ÞÂèq×϶é‘ò ï½Ïýw[ &ó`Vl™Û@#Ý$ò<Ä+Vÿ83!†;¼VŠ@ 7Û+yF‚@ÿAÉKè"¹Fà@Î?^E†RíEkQ4+p08*q59,Z*å5«<8FN'‹2Q3’".;,8) è"Kg'h\öxÇ-×ÿëgñ±ãC÷Vô™àÅîqö¦Í£ÛŠÚ½Õ/®ã§î® ´Ú}ÖOÉŠÒ˵ѿ½¹:«ß¿ÙÀÆ¿O·>ÈãÏ0µ)¾äÄÚ¸Ö"ÛâÀÝÍ>ΔÆöÉ›ÓáÝO÷üì‡ôíáÎÎ8Ú›ß׿£ïè4Voÿ¯&޽…ž}½"· %&ƒ$÷*-à3—D%EB>Aý7aJÒ?é;=îBLH¨QØ;ßR¢'E¿'G‡0ÂD4Q|;ëNû2µ+ý:Jûº!”#3"±"ýö(þ†‰¥ÞýæñÓ E2·ìyö"ñ]ãp¾õÒçúö#åÂÛNÍ-Ò‰ÔÇ·e³cÏÏÆ¿ÓgÞÕÓZÈWÖ²¹o¿UÎâ±Î¯pÏĤƒÀº¹ÍêÜ߻аÄÛvϾÑ=Ú•Îã½nß%Ï5Ó É'ë÷æÜØÊóRùðpqEëJRõ2ú ,%q £_¾‘-¡*n/Y-µ(o)¿H°9t4B¨A’@@:7 K#9QAJœ2f$0@DA$Sí\œEÓ+“.˜!Ð$W2·:Æ*ìÛl¶ø(j5ø ½*s!@à ßL L© ø°ë÷êìÐeõ4ÞKÏÐ;ç‡×^äcÖ®ÌrËùÂŒÝäÁL°|Ã-ÂY©¶áÙÊÊٴܧ‡ÈÍÆ$¾½ÛÄbÇ—»YÃ:·Óaô¦ÈÅÇúÞóÍ ÔºÜ.ßb݋Тגö¸í|âtâVMìÚñXô”ÿ™ soÖ"®-l$Ç32W!®J&'¹:]:ñHWLGD?'^¡m?ÐDBAÞK_<;xHg962G„>\M‘;¥F 9Ý<Î3)$W Ó9Ò‚ )oŒ&! 橳ÉÊÀ/ªøøäí^á7í˜ø£ðlè]Ùªß2ÚDå'ÍÛmæIÅاÁ¹É‘Å“ÖH¼bµ¬›»G¤yÈý½‘¹°Ô¢ÊBÃÕ À…œÊš¡ÃµTÒŠ¾{Ù Ã ºj܃ßTÊ8Ö­ÇkéÓeï‰Õ\Ú÷~ü66ÝÈûâ÷ 4 Î÷7 2 _ƒ>27n¿67?¿.‚=5$Ä#˜,$@PG™D²/Ž@*:64<<;M8¸Jm>wNQ7m9æVà@Ù2>FÈL^>'GÜ3½()ÿ62¿ï i”)ø‰*þ ùɧúBþ;ïìý± Èåµã„ðóÙvë\å~Ô"Ö>Ô'ÓŒÁ¨ì:²šÀþÐ8ÄßÉÝ¿¹ÎÑ`Ä4ʬÁ˜½§5Ä£ÊWË ÖÈ»¹ÄøÅYËé¶Ý(æ—¼hûÊ8ÇRÍÀæ¢Ú`àœà‹÷)Ï¥ä\ù8Ûümêôbõ ëAë˦åOª ™¼ !m‘Àñë"&26*â;¹*Ë)s; ;Ê6£M‘@¬;¾;2u7üJ”9:=520FY;"E•6Ç*_Nì+~K=¹.+q8Î=õGÖMž^/<¥;Ž0Ò1³@2—<’9#Bµ#2ÿH§/u",!”D·!e K÷§#ì±ü-ø ú^þ]úPHùFðéïÆÙìæ$Þýå¡çJã·ÁwĽ¦ËÖ>Ó×ÀOÅ<³wΠ͹Ä«8»&ÃÒÈ·¾ûÀÒ°1®þ¸‹ÃUÁ,ÃüÀËÖ¾í‹Ê½Æ¯ÏÝȪɗÚRìÚÛséƒú©ð_ÐŽÜýDæ,åiü3ÿ!æ ,·céü$âë/V'€ä84/¥'##ˆ7-.Û:À8þ<á@G\š;ø:<WüIíVå?ç@6')Q/G07Ž4ü&.ù@š5JÝ)…¼&µ'>c6Ôç º&Œ¦ ³¨"6îÿQ ëõOópìÁðšú”õfîÙÛ.ÜWÌyÖ@ÓÃÏ,ÒõÐCÍ|¼‚×Ëú´{ÏĶK¯'Á.¹˜ÙaÕ¿•«U˰Ë[ÁÝð»ÍCά¾ñÇ À!¾«¿ŸàUÒäÜåèyÓ:Ûæêä†ð;ïú¼ãTý ö×½ÒˆùÚ§"*´!þr,‹¨%o:d;f6 6“>K C;‚RvB¹H¿A5D¿EEÔI&AMI0öD4>F"¢@ ;T/>¨4w)¨ æ&ƒ ¶ð!§ÂQaT*ó¤z:åõë·ðˆøAÜbwþ­îkö~ß”ÔÙδעÒäÕYÊNÕÛµÈDÐ ÐÞÅXɦÕZºrÓ`²¥Ì¹±# ¹·´éÁ¾ÒÛQÄrÁ@µFÈ3Â+¸…â»Í­ëÿáùÝ+×óçðÚéíâóÚZæKû¡ö¨¾ŒýPü-þƒ4$&Wê3î!'4MCbÂ+­(Í3Á1É:b1¢"ô>æ>)?¿NF‹A°G’8ð0HFWV‡CH>4F!8ÓE>®Fe* .©$pC!/³0Á—#W!p™­% ý© ô õ>Ö¢ÿVðGî•ÚŒêHàÑÔ6Ï-ÝqÜm¯ÇÆ'ÛƒÆjÂc¬ÖÌÆ½À½ÄJ°§ÄJÀ˜¥~ÃÖ¤ÚêÕ+Ðo¸ ®,Þ…½¯ ÛñÍãâårÎ!Îuä%ЪړÚB·Ý3òŠæûô8ôöúãô·þ †‹üj£‰àPƒ5®!¨#ÝýЉ-u*þ>¨65OÚ1%BÒ=öL85hB¦E“:‚.±Yø4y:(AÝI—Bµ0E6º:;F1[2O*\"ä%Ï®*$5½0ò« tÌø-íiûv¥ê¼ô„îèód٠ܽê£ßæÐ•Æôï¤ÕˆÏú³EàGË@ΉÕiÃ~Ѻc³3àî´Jµ0±•ÊÔ½ ŸvÁ¿»Jº1ÎD¼î¸ÃêÎBÏ_̰ÑíÂÒÚ+Ö·ÐÒüOèÍ]ó^ýxØçäOð—íkú«ÿo îlˆ$«u Ú¨®Å &å¡!GC5z)&6]5Fè9f1X+´C—S¨*Õ+M³L¨)SX^-CFZP§@oJ'DD_&qD? 7J36&§I& %Y&N7«nŠÝÞGH ÀûØCúÑÕÿãP ·áïøûáÓë¬Ö€ÖHÙá6ØkÊ3ËÇ—ÉÚǶxÍ´ÆE½dÎØÒÒË1¸¹fÇ®Ä߶öaÔà´@ÎÓÌ¿¾Â»m§\Ö}ÐÝÔ7¼^ÅyÞÉÙì:äðâ­ð÷©ñ,âÏþzïÌð6 uÿ(: ¹"K<9O"­#É4H8Ê21Ô/'p7 )6@³G‘E‰8yJpY:430¯7íPÕ4@²BV².à>(ñ0Ò>ˆ<•&²/U3â",=7Ž&ý7ö!Ñ!í!ù± ÍÿºéCUÔGèôü?ïœñ„ÛôÓÛ÷â˜ÑÖÃàîÇÞÔˆÌ\à éšËÇ…¶ÈË.ÞC¯ŸÇÔdµ9ÄgÄŸ¿àÄz®À³qßâ¸f¹™®åÇ6γ̬ÊùÐáÔäá¾êè~æ'ØÈåâúëÅïçŸõÝ&Vÿ¨ ÷>N ¹Æ,xŽ#µ &%7Ä*[ ³,41C7pCQ±6 BJGˆ9/<ó=ý'Ê4«+….Ä- S4©B¤@“>ù03ØEVÇ(‹$¡0k5Ž;+:#/È5´8 L x0^¸qSç^ÈŒ$` pê‹!3üCøƒ ü)ècßÅêÔÁ#ÑÍÒïÔGãçÏBæ\ÑÙUÐÍ>ÕùØ€Í3ÒìÓÆÕ Í8Ò ¯S²zÁ¥Ò嬺Ìg±õ»Á½ßç<Êz±ïÙ7ÓFá^ÉÜÇŒÔËC½ÊßÇå®Öáäoðè{æÓò-ïi÷¥Ušûgônn Y´*J"Ì ±9ý(¬'è1k5c"Ù @žLÕBá;}A‘A/Du-Ý;2=ÓDOMB!]?B@5£0 5ÓF|#«;5[(A<×4A7¯1Y&k>ÕR/èúî!ö$¨&û wó7ù ²Yö†)éò.ý©ðTõõzð´Ñ4ØÇÛ_ÑÑϳäMã÷ÓêìIÓGÁŒØÀ²–Äz©Yµ[Î6ΪÌ~Å€»Œ±nËk²ÅAÛŸµo¼¥ÏCÔBΫÆÔžÕWÈ"æöêòÙÇêáòë÷âÏòݵÿûã•øTæÆE ø » TW ?ØüH$n†8 !Ù!u-~$Ì4ò.“1o:|6’"@<¶'êJ¸2=æXVC~7--ö=©D09?i% 2dHõ0p3 ,ì&)=ýÂ3“&åè-®Ì"Š,&JŠYóøÿæ åúëù–ù¼ ²òtøÕëàßÕá ÌèPÕ#ȺŅÜÍV¼±ä¬¾ÑÇ=ÓOÅî½ÖÆvÄ©øÓCÛ¸ÀiȆÇ2­«:´åο4È£ÄÌB¾YÌsÂ,ÓÒ'È­ß“ÈçëPî^Ûûð@ö™Õ¿øsë•þúü{ÛÿS÷rI”*¶$Ó+Q"3Q,/Ì…œ;¯=5Ž&(/­JfDM#ÿ8?l/ >^F„;<ó,”M,/Ñ>²BNB­1¤:Ÿ/é2w573µ+m*;Ø8æ% 0ã 5")ISÌopÆûîê3ýôUÁêøñø éÃÏáÒÏÝá×ýÔÚâ!Ì·³(¿9ÚfÀBĶ]­XÎÃŽÔd¦~—{ָ׍ò²'¹º§©º˜È.»³ËDÒZÈüÕÐÀÖWÛÑ¿êËåXß=Ò;æ æÌôÄñ=ä;ø:àÂí#Nú YƒøÓ•½YITöí*H2±5x—-k4Ò:0+lV(¼-(_)Uè>ý?Û< H’4¯@_=†;N6ŠK‹<^?zG*RŒ'²ÐMjCµDÈ54ZJÚ,x.Ga,N5Ó/LA¥*A" ›ØÕ•#Õµ¼û^éÿ¹ìý•+ú‹ãÍ ÿ³ê¯âÐÞØÄïÀÐóȈÛýÔc˳0Âά0¿øÛJÉÌ̇«ÓË€¼h¼Ñл;Èj¾`ÇÀÁðÖUÂÒ¹|»€Ò[Ø×ØÊ­Ê`ãY¾•éCâªëÁè—÷'ç|éT ŽüløÍöÊë1óøª R@ô9< Ç)qƒ/ UI9'Ÿ+À?@J‡&¡6g0H?7D>”0”Aˆ?Dà3á(OKR=É>¡NG8ã1ý@Á5ü7ë5Ú986NO<À{(s,I/+i‰r ;ïwõ÷ vëÈó'õõôÿÝîäÔæ¸ä¯ÞëÎmÚžÇEÅÑKÙÕ¥ÏÂùÆôÇÙÀœÄ®—Î2 û¶iÄÀ²®¾€ÄHÅßÅÄÁþÂϹßÅçÐ&ËhبĽÊÕ¡á^ÓgîËá©ñ ÿvûŸìœ_þ¸éî÷Õ£Æ)Îñï.Ž&+ Ä#h‘,²1s.a.Å1N/8KC]2´B…5k?ºQ¸6÷>HP?ø*p8‘Cš+Ã+ÂA¶6@d.5AÅ&µ’2»*;Ï$RB5à5( ŠPöŽûCú÷Èý%`ý˜ø²âm÷2ÜPèœØ&Ú†ËÁÖQ×CáýÓÊšÎëÉ'ØÐÄ·½øÂIÇ{Ëå³ÕÀZʵÁëÇåÊO½¦ºSÄ\¶MÊóÑðÌKÊHÌï¿øØ××/ÅîÆ²Õ6É›öAìÜÒ"îŒèñæ‘úäç¯ê÷³¯ñ] æ^öÕçØ ¶(ü"Ê)¸(d)ë.l%d.o)DA6Œ7R3 >M4Jö1%HÏEþE 5ÑRùM;È@¦CÞ?Ä2È:*O}2~($'ðD 72Ÿw p7Ú%]ÿgú% 0 óµðÑühø1õRóÝÞØsùdФì&ÓççÜ{ÉÇvÝ5ÓÈ&·æÔ;¸EÓß¾¨Ê9¹+¸uÁ5¸÷«–Á^¯Å¦uÃ1©¸G¹ÌÞ9·ÿÕ4Æ[½,áü²XÕKÅ8ÍÔ×éÈuäÐöºæ¥þ#ô_íRÿÍùeÀø<þùÊ m+æ)c6T%ÚfÔ6a2xÏ$Ë2Ç:DIBa9¨4M#ýD>(EHDD¾H‰S€8I¹$ò4è1¶$&+--À:38@Q:&&K!2,„"˜øÍÿtŒkðÝÜûP gñPûàú3÷dð÷sÄOÛ1Í ìŸâÅàÖÈFà>ç¸ÐÅÄSµrÒ.¼®´ØÇ³Ã‡½¦ÙÖ»†¬¤¾ìŸ¤¼à ž¯¸7Ï%·àTÎÀÉÛÝŸÉüݶÜÝÖÓàÝäúìç@͉úSûOúú)õDÀý|E gÅ¢‚Ó*V# &@%´-D+Ä<ù#ì*m0,@x3:L =F+B8¿6@Y]Ki4ƒ&°;ó)ô0/,,G—(I2¶3§)‡0Ì5ݦŽ& .×-›üãL: g1ìBÿHÿuêuøSøŒ×ÒÎYÙéŒÄî·ê}¼YÌäÈÓ‡Ù—Æ9½Fε8ϋЖÕÊÄtÛ㽺ӑ͔ªeļ’­Ý½)¾…ÁÂÎâÝ ÔòÀ”ÛÃÎZÉsÕùâ¾Ûú߇æëóü»ûñÆô±ëÖûžä¯û…#wÔ![»W(™Œ$B%ùì2¾,è)H(9Ó7•+ÐF—?á=è,-,j9)3B0#Õ.Hr0ËP6*Ž1b6 Tæ&È*Ä,å&•E -ÏD/*n72óîg"^hÙ ×Ìð=Do÷gô+ð÷ÎôªïOïüÜ»ë;áßµßUâüÙxãnÚ«Ì{ÔéÐNЈ×Ýñ³ µ`ÆBÄŒËßаPÕZ¼SÑô¬‡ÇvÉÈÓƒ¾$Âc¼¼É¾ÈSà‹Í@ÈÍBäÁáòÓÑÞãÛÏå~ÛÒð}÷°÷IïÞùÓ÷Ø« ÚÆ$ %wº$ #˜4õ ¿0b)6>ž9°)4:SÙ@ý?3ÑDO'”8o4*3IHúP5·%º,øC\@ÅV1HBò.Â/h.19–0>8o$ó;"Çj yæ$äõêT ŸýO÷’úÉå¸ý?ñzô£Ôê”äæ÷íÑøÎi¾Ï×OȺÄÃÜáÄ:Þ`©èÑÏTÜK¬ Ã|»Œ¾ ¶N¸ÃÑõÌŵÈÏÓÆÇ€ÜnÆ)Ðr¶ÄÈÇËVÆ âÞÌrÒêäÂâ9í„Û³ýæä$÷Þúûü3ö¯ÿ´ÿQ @«·Ÿ¼Åí(T*-%—+­/ý5+¨/{WŠ#w9Z1c%p)BLÈH4;A”V L×Ez/F‹HÀA§':)…P<,0¬2f-*;1]E1.ó »5¯)ì'_¾ ¡ZàüÕ¤oý²÷ çuóë³êˆòÃç+Ô4öéÓÒ•ãlÓ/ÃÚÏxÃÇúÏσÄùÛÙÆ}¾¤¿1´¾Ù¸|Ñ^ÍPʸ>­å¹ø¸¼TÎjלÈÅ¿¡µõÃÓÙ(Î<ÚÐæÆàíãØßÒï›è„õCû3ñ=ërý#û ñ0õ!t4Õ ¼é!Ì,ü!fd&K˜‡êC¥6¤EL%U4`/ý14‚B ''B28=0VE‚<[?">FAç9+Þ< :4å2º,ÔK”(Õ=/sœx¹,2-«ùÿûsT î°n ÿ) bžÆð÷¼éñí†ÒÔÂÛ˜ä©×:ë‹Èš¼ÇßÇ&ÆåÖѾ¤ÌA­'²)¶0¸C§É”Àö¶ÊúËÙ½sÇëÃ*Á÷ДÈGÉŸÇ[Ê~ÁÐÇ]ÃìÒúãìÇÙìíÜñ>ämäèôúˆñmì£&÷gýçžVì? sCcÓ#½&ô,±%/ÞÄ&ºM55T3£5ÞYú=Æ3!‹AÒ<â8ƒ.ª#ËC 0At8Õ9½2GEìK6-œ5X.76n9·F¥7$)0ŸJ¨L-— ž¨þÊ—h@õ¬õâ§—ð}óÐíŽâÎÙâdêØõÏÎÂØÎÌUñǪ­ªÇй•ÄÀÖÞÇ?ǧÎú¹®Î)À£ÕŽÉé»È@ÎÀóÆLÇ{½¶²Æ‘ª ¯(ÂÙ€è4݋ӦÜÚÙ¹ëÇ]ûñ6èÇñMeëÖúnìzóõö ñaó „£øò3ð0½8†':20ô7•9Y+zGš7M@3;Ô42SCG~5d5Á?QD?â(}‹>ó4‹8¶G]4.-p#~"°%/»"Á+ƒ:£-¹í,pn" 6 Wì7 ŠýoûÜçòêNé3äùüxé9ÙÞëZöœÄ­ÙüÞ˜ÙΘÌLÝÇÂÀ±²Û'ÁéÓG¶úµoÅ‚¿ÈÓ»4¶e»AÑt·bÐ!Ä{¬S¼óË »«ÉË“¿í¶‹Á5ÜÆrОӎü!àvq«ô,ì¨ø#õÖýÏ3Õ¶*Ä%û ß%lž.—'m#ØAëJù(W,¶;|3“>^,>ý.ÛD—8 :ê.qOC7)Sz4¨@ñQlGûJo>Í5‚&&;^$54¢<À,‹Kº¿=Z(€ µcš < 1ªÿÂñáø è"àzßÕÚ¨×AñHå€ÓþÓ‡ü,ÙCÔéÅòΞÞ+ÛG½ÀÍøË,À¼Ç‡¿)Îá·‡ÎbͶ+»@¸©Ð¥É¨ÄüÓ‹ÍÉÂÖ!»æ¼*´Oâ Ó;ÆÒÒð@Þ€ßÁÏëwâ«Ô0áaô?ìçÔÏ þ W ]û™ T&ÌR‹<ŸÞH‰¢¹98ÇG7q9Oø4p$®PZF|7C4TBÁOÙ*„D18µ3Ì@]H¼YÆ7´2ˆCâ!["m"á&öÎ(v,b ÿ{ !œæÝ¡ FÈÿõ©ý'øþâ§è×øGê•é Ö¼ßØ0º‡Ö±Ý¶Ïëá0¼vÃþdžÂÎÏd¶0ÄüÖ:ˆÈP¿Y­È¹`¸êÆO¼ÓžÐÁoÎÀÏÒÅ`ÒâXËÜÛ)ÌègÕ×ìFÚçÑá³Ö, .ëôü– x €™¥fK _"'úŠ;S_C¸m@8¨/0a1‘3ØEò%phD-˜G}@AhFð9î2¼N£S¬1,QjQˆ*^:b5Ú,»59tL‘)QW".>(°nÓ*æûí\Ã6Ññ²¦ ö1 X”ìñß´ú¦úaÍçùÇdêWÎØOÒ5ΰËñњ̓ÇxÏgÔGÈíê³ÇË;³œÅ„ÃìÈ2ÃÎ)®Ç¿ª%ÉÐΉã©É©`Á¶ÖkÊ{ÔiÔ˜Ù½âKÍqáÂØ¬Ú|Ùßý÷jìò;âGæíõ@Ìþ) Zúµ¡O ª r%}ð+w*™4ê8ãi,@³0A¿)F9dJE­(¥50\\m17/6ù1‚OQ0š9ã4³(f9w.Á5¯HZ!’#`:3c%4‚"&Å/" § +Î 1ÑGzøúÅêê†üúçOãZòß’ÞÈâ×ôÐfÃå8śΚšϿÀÎIÖJÉ@ÐjÁç·Å¿D¿ÅèØÁwÁ½· Çö¶A¿Ã&ÏGÀ]µkÔÿË»ÈzÑgȉܴ¹ݱÊß‚èÜé…ìæì[ÌýîùYþ±û"ý‰–‚9%WVws$z&a I29©)Ò,#7…N=F‡A{?Ù3 21(52"GF€1ô?±@«7æ9«:£SX2Ü.Š-Êo¼õÃÊÜ‚Á|Ò’ÑbÌ÷ÕdÞ~ÌŠÚZØØ×à¬éÞíèâñíeéé÷±à²û™î{þ¹ùª·î$œo,¥òޱ+/S7 ’5*A‡7ÕZ"GbOÇ>Ÿ=d899‚C¬O_@6L>™6t1*5€%e)ñNIK1,+Ì:;5SR'wÝ>=;y8 Ì °"ßûýòþ»æåÈEöqû«ë1Ümä,ÖOϨĖÖ;ÓÈÒ³ÓmÈ¿ÔqÇÀØ'ÏBÒʸWÆãÐÙµ®ÜøÖ‹Ê Æâ¿ø°ÀÂ½í¸“ßN°W°=Î÷ÌÉœÀi¶7ڸȒåôÒüÖãÌôçQØÛ÷,àšÎxéißêùBñ‰îÈDp ®ÍãC·ýñ1Ùà%è—#ÿ ¥4A! g3ÜI*:{@Ó?8rXHñ@ÝAv;íY_AÀC¬6ö1äD¾Fy-Ñ 9¨1’2•Q .'¤2o'¾ ªM%Zn>1Œ¶ Ây pÇóhíÛþ„ø¯ÖžùÆå÷Ñ0ИÓ"É…×HÕ;؉Ì`DzÇ´áÈäÉTÄX°UÇßoÃÊv±¹ÈÝü¸Þ¶ìÄ)Ï‚¹Â$Á¾”´]µBÚ¢¿ð™áeë¼ÚÖÒï×3Ûä×¼æ#ôá>ûüéÝ cÎûïïÓ³ö,ö)í—ä+Â=8ä2&50,L=Ç.Â@;RF:%4U7/Ç?9K7ASEßKþLl5)¸8µ90/:¹-7µ0²;3å.Ä)µ˜>Ô!„"9 "®KŠÍÄi5ùD žÿÓläLâ—øìgîÙýÖ<òêטÏÇìßÀ~Èrº#ÓÐÎ"ÒRÍÏlµà§{ĆÈ'¿ÑbÊfÆÌ´îÌ6¹ Î$ÆÂ·ª°óӉش± ·‚Ǽ²ÜyØfÇTÊjÒíÛDÛ‰ï@ëvô¦è?]ârïño[ ·ÿj„õ¡ï Øb!Ü+ª./Û-ˆo6¶M®8ÑMb23@?<>M….ºGp6Û0v<ª5TT…:E‘9ˆ6^N=v8‰^©7Ë9´BI6(O@ ì1K!ˆ ‘’ –!] 0ó´ ý¸¶óÑùiûávóiþhç@á÷çãØ ÇüåÛ½ŽÚ÷ËÍâìã¢¾çÆæÈˆÚÖÏ~¾ž²ªÊ²3ĨЫºËºö·‹¿ÕÆSݧ½¹ÀqÌëÑéÃq± ÓFɬؤۂ¸Êѕݬۓ׵ïZÛ ãñXçû÷ÌÀªû4в˜|Ñr$‚….˜ÕY+fx*XCó@^5“FQ-à*»<È+Ò5¶HÊF÷9<Î*XRž7ïLYIYV,mNå7-4OÒ NE7ö*A)7ª0:!ô$¶' %öáØ°ŒòK"ø3û¯ïNßtïúèMíåóé²¾ÌÀ”ôêÈð#ÍiÇ6Ê‹ÛNÒÈÐ4Å÷ÍL¾"µâ¾7Ð/ݵÐ̱¿ð¼ º…È—ÇiÃ(ÇÚ³É_ÒtѨãaÌS³ÉÃf½Êð3æÕ§à™Óè|Þ[þéÃç¹õª¼ñM òù-ˆ?> ¯PR$8KQ"Ü@G:1Ú.)F8NN#8"Aû9p7GY@èE¼BhBSS¤9@bVF8É0#Rz66u/ J*W-5¯7øó&Ë ¾ËÐxùÏR=ùCæóïÍìúõ»óëùì†Ô éïåöÙ®Öè×ÁÊ-ÕÆûÜ,Î×ÞLΗÖɒˆÉ6·¤Ìô«NÏaµÌ¯Ö$ª,ºŸsÕ8Ïë¸ÁÎdÆýÄÖ~ܪÒeÍîÙøÙ’ÓîwÝdÙ'çÑí·äö(ë©Ð9a s.Ç!Ä+_J!Eå'| Ò4Œ(%€JÁ8²X:™+½A´>@3Y<ó9(6óB>R=yG.C»Q 8?Y"@(2¾+Õ%](J2ß+Á4ò.(å%!¢+d*ýeø£yÅYý7òº ©çC/÷òêì¶åmåäÙáÃÐÜÙ;Ô/Ôï¶üÙ¤Õ ÙŸÇ.ãGØÁªªÂŲŷÀVÎ͸BÓBÁl¼1¾u¹|¾£¹ÅǰÇËÑÀÚòÍ‚³˜Ã[̈ÄïÜ~ØHÖšð¨å“ß×ä õ»ùUôð»ñÈ ¢óŽØŒÿ&5¾#t|9Ê].R+Þ!C<ÏRÄ0 <7è û)jEXD;)š[@B.mCá>JA².¶O5/F8CFN3n@=<= 158Ž-”%K3,5<Å/°%š-ã5–¾@"%4 ®³ó«ìþï‰úÒèøLøÅÔÞÈÿÌ Ævì‡ÖTï:Í"ع¾±×ÒΈÏFÄø·²ÄÄÕ¯ÀmÉB½@½EÊœ× ¿Ä%ÇØÊsÈGÂu±&¶qÏÐÑÕÇk¼SÑ€ÈÛØA×B×sìÝÙUÚYòDåëê6ôŸúmæ¨ú’üE÷X uó`>#h*'èá0$®%º3-^€2Kd;„3Z#jüÖD¹ =†9™.*×½9;(É*q¼bÀ¡eó7½ó²ú[öâ íôzï×êÉõ‹äíÙËÓÖÍÞå‹ê¦Ö­Û0Ô;Ë!º6×=ÄB—¾xܰԥÍÔ»ÁÄw¶ Ë|Ã]ÊÓÁ1´nÈ~Ðs¹ÏÆsÁÑŸÄKÉÑ2Ë©Ò Ûoä®óýßÛ_ú òÔúö`öJÞcZå£ J ­C/‹ Ò3¡-êU/Ã!­9h;J)‹Q¶Lô,=ï9$)J÷@:ÕT’R ?!JÊ'ÇP~L¾M+”=u/fGÖ8j' ;î% &@ç·#'TŠ*N%ûÏ^? ì •ø¶ü†ù~€øåôí³Þ«àŒæ$ð!ášÏéÛçÍÍÁÂìµâ̶QÊ+ºÀÉ£ª@»Î­”ÁI¿ÏJ®‘ÊÆx¼O¨Ç©5Èš½»ÔÀu¹ÆjÓ^áàîÆéàûä,¿NÑèßùÓýñÞÙ ü€ß×ö¾ÍùíE ýi Çq¡ ¼%ñ0ò1— Š!ô!æ7C+*š%39ö-_7=-\I5:wMkC¦FYh,4b>²@Š>ÉMA¼6Í ˆCG3+µC%5¥!-„N%(Ø 7P9Õ*|pù©ú=yPô©üåJómìŽê"×=ïËâÛθØDÖÈÕÉÚ?Û‡ÀmÌÚâÓÙ]Á3É¢¬ ´M³Ã§Ì¹¥¶ÓµÐÁÆ6¶Õ¸bȻ˔ÓzË‘Éj¾ ÉÏaðëMܽéÏåÒ<Ñ5ߨóròãÃç±æËó‹ðzþøì_û.ÿ! rµ ]/™µD¶:$Þ+",2"+†.4¢A…D3“,²(›>16ø3s<%V¦Qð7Ÿ8ãqGê5B:ë2{RèK0'32u2!-û"ö!ä$¸ô¼ovYð8ü3ôyå èJê–ò¾Þ(í¤Ì…ÑÍÒ Ïsá’ÙuÇ«Äà'½‡»×ÎÆ©ÏÁHÆJÂ+½mÞŪݸ#Á¸¹ñÁLÏ€ÂÄǸţÁྐྵ¶º»y®šèIåãÚµÉÕÔÐÝøåó÷ÝàáRÔyü%âàäFV%Æý/ @š'¢â)ãì(c)n4Æ&ûë,ñ%3.¼261¦)“4@C/:þ2!FÉ?QDô@wDlGªOpO=HKWT112,ã:ÁK©) &û29'ß8c<1&TrK§3 ( Ùõøƒ ÐûœüÏÛðíTìÅî”ØæÈüÔΠ˵ּۜÝa×ÕÕOÇ|¾—Î{Ç(¼eÇ}¶·ë·*Ä,¼«ÉÚÂÀ¼¦¨¸À„ÏȪëÇP½ž¿‚Ñ%Óüº¥Í«Õ#átéÆ’æƒæ×Å­àhê4óÞÔàÙ•ð'ˆ–û*B‘£¿„ƒÇ-…"$ D8*œ?Ø%²3›Gü÷D¤:£>û=iAHP=/1ñC4µ7=Tß2374K5r6û;Ó/¨E3693âàv,Ðo·$¬ #°1Wð Ü(©1ˆ Üûüó„ÙÅóíØ÷eÝãáiåUØçæÏݨ°NÅØ¼²ÁKÄ,¼?З¶È½1ǦËY¼&Æ ÊØÏ»½oþ»N¹.·5Á®¬FÍ÷ÃëÌ à îvÉ‚ÅÓÁÛ½+ÔUíÙÒ8çôwãïìXÞÝøo œõ¯ëà r‘ Ϋ·%E2¦>#üA" 0S#!=ƒ75&0?3û=Y0B1›7GDM3,êC?N¹FtCëNì65D!3^DÏEz>±†5æ2‰EÅHj;—9@.­?†%`CA$´ B%î$cáøûñ˜˜ ÑêAíø5ôµËÄü"ò”Ü|À\ðéÜÊ]ãJÍ}Ð$¸IÝã³õ­9ÉŸ³VÊ—È× ²bÐûÎDÁYÁ/É ¶#½gÂH»pÐi²ÍÁ²ŠÔbÐxÚ}Ìéç­ÇßÝÇéFçßÛëÿØ£ôoÿjóìåñ§eö?ú÷ ™ Äòì¤#>¿"·4à7Ž$c8iì*ú4ƒ0¥II =7G-3ÏJ—;{GmPË*V35#È4*7„:!Kö@0:l6)è*n9<Ñ$ì49%©%ê3Þ"FÐø#º#`~fÍ  NÌ ùQó¶ø½øãèÀè Ûáºè<ÕsÙ"Ù\ÐÓÈäßÒÒÞó¹—ÚòÒ£ØÜ¬ Û‰ËL¿,Äʱ³ÁÀÅ(ÏX¿²–Ëï½wÅ{×YÊrµRµUºÜçpÅÊöÙaÊ#Ôhì¿ÙÖ¾ÍâcÒQéLåGÀü‚1¥ó Ð ˆ ÃÒÍ Íç%’+ WWaO).% >­1o@Z4ó0Z=þ)NFÔC„*Êa¡/·,Í3—>U:(IãPØEü9O26%¬*(÷ŽÚ'·"ã,–+fnMEº$¨Åü—õÛûIë?þõpé!ÿÜ·ìêäˆæ'à·áP×}ÙÜ4ʉÀf´ÔsÉÊÙÐÉ$»ëÁ×7Æœº¼Ê¬Í´­§w²ú°ÊUÒGÅæ­¿´%¾ÐIÖ^Ï4ÁÜ¿ËÖèŸâ5ÝGèÌüùÛLðzõþ‚ÔyCÄï@òù!V)¼"ìÉ!xxL(x-q;?%?–3u4Ï-ü'¿+5N,‰Fv1{3 0ÜFó;e/Ì:b7WH4T0í,:")Â4Ê8X;4,¢6j.ûi1¹´3„š1 ÿn k¡æ4úòöüÿÑõ è>í}×´×'ÒEÉÑ!ÉûËŽÅ?»x²„Ó/Âɱû¼«¶¢ÝäÍëÌáÒù¾íÃðÆC¾ÌÊÀÉÒÖÔ ­hÃùÂ&Ë­Û‡ÆÕÎ^Ò¤Äñà4Ü?ÌòèHÕ÷Ùœí ç÷Âï‘ý¯ígÜêÆû—QgöÒvU6($‚@7,[(}î-©1A=ž&)5*DB<§=‹F®G¥7q:ÜP»MbCýJqLaA–?LA„@V("N71D5§7ê$|*Î4=$ (¸È 6h#r#h®f"Õ½ó‚ëãôÝÏÿìõ0ø¤Dãú¥óG×_á!ïDÅÇÍÝLÛIÉT݄ɇ¿‹ËÀÈþº¶Ñ¬QǀÃÊðÇy²ê ­ÇŸÉ·Óºm˧ÊGÀœÃé×UÃŒ½jË×ÀÂáýÝBÏã1Î2îöÓ3ûväY½ú[înc÷ÿ õ6 W)¡/Î ÿ+i/+æ&0'J Kz<}2I$SM[5dKj7'[ÉBW,?ÀA”>K<îQbS­Uæ8‘8YMd==/Ï)s4K5÷GN%8ð6Â2Û1$Z $t¦ RĶPgðø½øÔñóÞé•éÜù΃ÞéÍÏHÕÉãíÆ×ÏÇOÏjËÇï±`Ëĵͺ躇·£° µX¹ÀÂO¾ÊW¹Ø·ÑìÇ8Òˆ²Š²BÌ«×ÓÊÿ×$ÃðÙèÄé|Ðhà¤ðgôŸè¸àLêçµý/â nêUù þ_& Ïä•=$A o6g(80(<÷4;+YAŒ4Œ7ÂG…PKAòS³J™<îEDv:Â?Y6¾0yKó5`R’/8¯+2Ú:5)€6‰/ çv'B+V%!Ê Æ5 pð UÉpãû÷záÐâç[Õó—âªßTÚí֨׊МԨ¡¼µ²­ÉÌÛ¿áÐåÄÑÅ9²<åÌÌ•²hÄûØâÒäÅŽÇÐ×GÁ‰©4Æ<À¬Ú.ɚƑÄwÑ»ÏÀÉuÙ¬á Ê Ø3×õìðö½û£åáùˆøu-¥ˆ \O!#'Ö–)Q!]*É4S3,!Â/—-™ChAï9Ž.|Xf@¾TŽP"7ó. K{@ŽB\JåO¡1ÇD :—&[3B"Ç;%7ê.w38?»/ì"&•'…Ÿà£y8ž»—›Hovòq Ðä™é…ßñúéñïðâ@ÊëcÄÔø¾ ×LÙéÈVÏ7À%º;ժ깻BÀ…ÆÑu°èÑÇ¿óÁ<¬­Ì·§„°­Ã ½Ë!ºƒ¸Öº`ÒдPà[Ø`ÈÙïÉëíÔ”Åv×–ÜHù:îìçñFó¤ü½N '›' 5$‘"‰ß9­Ê5Vh?z4+R¯* H$K†Hñ>ŽHq?*ZD0N:??:¡CÿM·I&1{5*ô9ÿ+¹%17ß*è&Ì)L,7(ÿ# N÷z¦Í’ýxì†çƒï¬ðÀÜÈí=üÝñ}íà×ÀÛßLÈÔrÌ ùx×ÁÕ÷½_ÏeËÖ#̲쿠³Ãʱ‰»@Á©À¶7¸®¶ÆÓÐÆò×ñÄ Ó·Ï¼Î7ЖàØè–Ó¯×CË5ãèqéÁâ=ôvÝ«ìšôÂCAðˆpñò÷ßê‡ ð!Åè&i*ÆV#4Óþ9‚--&E#1D$)|Uÿ0e7(JêDˆ5Í;Ò$á'Ï:W<æWÿH‡X´DW;:!?é<…=ó-a)Z0$‰0/'"¶ x Ç2"+kþar¼ñ ø‰hïŠYîðî3ò=å æåØâÛUåàÐÑÁÛÖØÍ³Á5Ì=̲ïÁ[¸Ò®[ºïÌÁ\³µÁºŠ¸ À¡ÎP³ÐÌ¿ÉÂÓÃíÎÏæÝÝêŸÜÊíׄûÉÌzß–ážà¯¤ðÞé@÷Öô˜96ú¯ýh P ª, B9<6’+”+= DE:'94ÃOŽFn+4Ù> O:EKH;U=l<³;•?ø.²?»;¡Fo1"Ù,»*½5"=†,%T4Q,¤3#|"ýŽæÚñ¡“øÿ'õÿ¤ýÞêFüÇäó¡ì;Ï@í}ÝrÕìãÙ|ÒͪØÞ½ŒÅrÌCÏ:É}ºØÄI°€ÆÕÇfÈïͬÈà¸YÓÞÇ{þËÑÛÇ|¾–ÃïÎ+°ÅXÓÍÓøòÛsâíÿàwÝ+ê–ãÞÝðæáÿ÷ãgóâÿþ =åAà ê  $+ @ôŠ +à7Rú#.8ø0fKË)ŠAhBáH_/R>¥8ÌG85–=è.X=á7Â9E W'0n'ì8 7>Ð&Ô'V¥+g"â-,þŠ f´ìiõvôð6òšíJéèܵßò×|Ùþó¼ã‚Þ-Ñü»ŽÛiè<¾ýÍǼ9ÁI¬çÂWÊýÃlÄißѾL¨Ê©¾Æ¶'°îÁ0½šÃº6ÀÛ¿zÚEÃsæïÎEâ ÁºÒjßöì¾ÜÞ¯ÛxÏíì<ÿìäîˆÖ wÿ¤ï÷O¼Ø1Ÿþ+ê N!/$·-”&ñ=ä-e/Ý2m+†%Á-úCg0Í9÷BGD±7+e4à;BÍZ.,ã, Fg7ª7y=ó09¹BòEU* #W5${)ð.ã.BüÞõþõã‚ÖòáÌÌ–ôùÕ¥ò»íêáßüåNå³Ë©ÈkÒ1Ê/¾ˆÐÌÔª¹‚¹‹È.·È·l»µ¾úÁú»æ´ô΢ã¶È¿ƒÖ’ɘÂ\Íqá9ïºÏ–ÌbÓÃÅÚçaÌTèªåöçYàÁìï­ç,æcaú\æç $ ýôu{3)["úJ3f3†6þ&_.ŸéR C(A€8Ò,66ÅUE8ÚL‡.£S·Yá=a=7ù; =€E_,w<Fá9w2;,í0"6|'‰+Ì Ú; ŒÆ11 Ûþd wöqÌ ã‡éÝØýèË=æÌîûÒßÁÑÈIß#ÖLÔÖ ÞJÂ’·ÍÚÎõÆÑ½Àñ¾K¼ŠÁõÁ¬ÆŠÛ“ÁÞ¸µ²'ßLjÄòÖ4¼ÑÆ‚Ï×·ïљۑ×ñ/ÞÜ‹âxøRé´Þ ø öì!ïdñ¶ÿ=Dô†Ù ­$(6v". .ó,3#d-j$r'--•!CQCv@¤*í+DP—*4Ÿ3*8'W¥:9J±=?Ô72EËC74–6`3Ê(ö3DW;¿>,ÄÍ/b u` ŒˆFËõ `úí½é’ô“ôŸØÞöqø›ÛçÞzíÑáKÊΟÅÅÄèÑS×gºý½UÌ×̚ɲԔ©Š´É!ɲ¸°ÎãÙ²„½ÐÅê»f¸ÏÁÈÜÖÒ&Ù€ÍbÙWåfð©Ü7Ø›×ç ÜöñÿåàññÊó°÷sìI5ï0þ ‘Š«)J%£&ä¤+Š(ý+î;N<<œ6á8¶<Î/r8U9»/®JPIrIâ:µ=Æ.©;Ø9ã=£7ä.|>6.272Êå5¬@^5#"815G´© V ÄàÓ ¾ò¸õ•÷<é%øï8ÿÞfï+ðîÞ?ä7ÍFñÊæ8ÉŠá?½ÑËÓæg·6Öä³:¾ÄVÁŠ¿.»:Æ—µ3ÞaÀ=¾_¬ƒËJÀsâhÐ<ϹÅQлûóºÁÍyéfåæ¿ØGæ~×cì¾òzìKò¯÷ný1ôùúgxõDà ¦2Ã$%s#¼³T7 ã6M@9A1 ;èA{?÷6Ò09ª0¦6J ,®IJKîOßGé0B LÎ2Ü6T*¢-K6:k5ÿ)ž1';"¥"=™à"#·ýNz")yõ¼ùÕn ñä­íäé<Ú.è•ø‰ìÝîqåhæ`ÖEÜëÔ÷ÈöËÞÆ¼Ä›Â¸ÑD¾üÃÈãÊø½ÞÑ¢À!°©Ç£ÆJ°¼±±È"¹J×¹µ¬·ò½¹Å…ÚHÐPß’áPâÃìlÐöÕwÔ¡çÜdøIï,ý¢DŽ“ 8z#¡8 ýйò÷%¯ò- [­?Pž+¢D":çJN?ç"V5{W/9ôÛ\ tå )ü4 HúPÿ½ÿÓü0ü­ïóøføäû…ЇÙFÔ/é-ê½Å>ä‹âÅÕDÐÎÊ«À¥×kÑÍÚÆ”Åμm»{ºsÎ/¼÷´&¼e®§À’°ÑËË¡ÌÒ¿ ÉÇBÆM¬ÐCÅÒkà8æ¶Ècå<èœé¨Û ù3çŸðåïBÿ8ÿ v.öƒ~.èy.: â2À0h"A,/7Þ2ó9u3Å8$B¾bbKœ=95¥Oh0k?]HF8òJdCA¦EK:Ç*<µ,I<:†$&)ü5è+ô ê17WÝî"”â £ .žäõ±Ìð•ýSùìã`ØRÛ\ï¯ßÕÁǯÌUÛï`ÏnÙÕÊ:ÔáŶТê¾Ä„ÔÏÒ¸åé ²°YÑÈ·îÍûªi±“¤¸Å&àzÈÚD¿ µ%àÃ՘Ȁâ²Õªþ×Ü5Ý×yðHùnøf! ü’åšýòÿ ù¸¾ðü 8i |V × .+…1ý%£ˆ<6*À+'6Aâ,Õ)¡E¨Nv^9_I»JíJ+>€KnE9û4°@Í(€[zC2™@86u4ù6ˆd€$ “þ*a ÎryS · –ýb„ýScðq ìï6õ‰õÙãHí÷ÿä:Ö2Ú|ÆãÃÖ2͂˵ÒĤª,Ì߯ëÔx¸àªɵ°}³S¾[ȧÄÚ»l¿–¿Äl«a¯åËüÃCÇDÔÿÙḚ̈ÄrÚËåÁØÙîÙ©êÜðöøû7<ç“ ' IÈ0z)ný.øü€5]+k&ú)½E%"”84">–HìIŒ.w>Ð?zJ@@õLrM„.ØIþ@H[AOÚ3‘B8P<Â)0Mî5½(¤'Ÿ#¶#ü"õ˜ú ,~iû[cÑ“ø…êñôéÛìÌÛ˓կè–ßã½Éã”Ü_Ø<ã@Ø ÑòÇÂÍ´ðÞÿÛHÃ0¸óÆÏÈÛÒ”µáª®»¬>¶Ï§ûµ)Ù;¾ºÇlÊYº*½ÍÕÙ¿\× Í±ÓäÅÒ¸ù&óç}àŽó>öø0ì>5ô–ýÝ·  õΨ@,ìØ1Ï3¹,Û-Ñ’$¯8í'J9Dx?`9š0È1JL\X-2½Aÿ. BäKµ7Ÿ>58F@Z4<\jSå+o;Ð6ñ> @æCý5l6ó$ L:Ë!Vý#üÈ%œ­ (' ¡©íÎcçú0ßñÖ ôì£îWñ±è¤â¡áïÂ`Ò;ÞªÏQßÒ˪Ã=áîÓÞ±#â¹¼h³õ©|°ø·à¶êÇæ¢$½‚¿|¹ŠÆ+ίÆ÷Ø{ÎÂЪØ`ƳÈÙ±ÕÔÕ¿ê[ÚpÞîùîüÛòÏÍãû‹þ~ïÐîDû×û ã!!%d°áá!Ú+©×!îE·=@N¿$]$/X2Å?%B9H›7Ó9ÂV®@‡0ýF–89¨4°T(9Ç?,GyFÆ9›)K*4+f2Ì-Ì&ý53Þ3ÛÐÁwð{Òðrùœã–êÌœ¹·Ù4á•ÝtÛíѸá{ܘȰÕëÁ˜¹ËÈÉUÂ]±¾ŸÀ\¬UÑüÈÀ¾ÓÐÆ½Pɿ̛Ù.Ä·ÎöÄÆ½ ÇwØŽÏîÊÓÅÎ%Ùké}×õåîì”ïÉçEøTö~Ö  ö§ ,ø'tAç´%/j6ä-¤-]*¤6(2G;9C™,˜?„IàH)WËG’;d6ðDG¹F-AD?Ä,i.p*ÊG£9{UI8/4>%Þ(ø"ä6Ì#º$$‡›¬ ~ „ð®èc v[²÷öí5÷xñê0áédäPÞålÍuè›ÒGÐWÜ_ê_Ê»Ö4Æ´¢©ÃÇN¦ ½/¼ú»$¾Ḭ̂É}ÁNÈ!×ÝÃÖÄ-µ¹¤ÙH­nã,É3Õ‡ÖNèÜàéëöÚ(Ò òíÒèÚ¨ÖEÝÙäŸÙKý–Á /cï« 6˜ ÕÿQ‚)j+ØÓœ+K6¸)“4¤•50¨2-5·HÁ81‹>¼KD4óR³ U7:àNª;Ÿ'C> LRR~Y¤:º]¿'Hæ 6.»,Î'Á*Ê&Ó(8-í2iy†2ÿGú:ûÕèˆ÷!ñãê NècíšõãâªßÂÞ6ò¯Í¿ŸÓÉOÔRºÕ:ȓ ɺÂ;¹€ÌMØÖ×^©ôÛöµwÜ ÐÊÀ™¸²È7Ð%ËÏÆÔɦŖÏÓ‹ÓÜôÌ%ïãÒÞÔìv÷‰Üàý‚àòéûÖó»ùî× "íñ¼ x ‹¶Y |(÷ý!h$*–1´;È(! {Gƒ?¦5ª7I'P?1KñIHVNGD'MÑ;]LO<º; '!)à7Ž%ƒ9[.€9·/†J‚<‡.+ #4Öä¡ ¡  ¹÷FþäþaèÃñõ,ù¸óÝå.Ó*ã7ëHà„à$à ÚÏÅ‹Í|ÝÂÓ¿»çžµˆÍYÑ9Ç Ê£ºä±a·³ÒºF´ï·d·Ê¸(ÊÉý–ÒºÒËFÓ£ØaÖ#¿PÖОãèàçêí²ý³þáçÛýáý‚³²nÀ)–‘b– $,§ ÷5"|!ÿ(¨0d<þRAB1;ñ=¥7X9 M¾L°(?³4Ö@UAòFø7ñC]CØ<¦*0×<¤6…;*ú0½4t*7;,o/>'í ÿÊôþo¹”’ð…î!þKá‡ë8êtùޏîÅáõ”ç»è4ëãÞØ¼¹ËËÄã”ÅÅÈÎ1Ô¹¸³Í­²˜ÍÛȧ¸ú¯€Æû±«·2¸èÁ¼ôÇèÉÂ'ÈáΆ¸ÕÑÉâ¾Õ¼ØÍÆŒâ¸Ù~â Òu×~Ïçî¿ïH ïêm)‰n Vàí Éï51ñQá1Î6 8£'%..ãAA~A–6èK1=Cp?™N,AÏC©Hd@!THPÜ=}H3p>©@^D 9£>ó')".Ô…!á$ÿÿEKñÉ { 9ò1 Ë ÏæB«ñÓ²õÜ«ÆYå×וéÖ)ѰÕØŠßßÚUƤÕÅ»Á¿ÊÙÆSÇbÁAÈÙÇ ±mÉ€µ…£×¸&ÇT¾¿¿wÁ¶ºòÑÈQËñÀ`ÄñËÞÅ×]ËßüÆhâÃäÓçãôûr—à`ñzöfþ<ýùð @êÝáúRT!²#|é#hz(w!è4CB(#âÂ9æCý'š'l0-BFCÕ>ë7DC6AéJè;)<šL'Cñ7"%8;5o5j:')K=¨;V,R/:!E.y@C {E‰ aÁ÷²ô`Oæhþå©ó5íõòǬëøwõØãë٤݅âõ䋽×ÜÐ5çŒÅC·Rî\ÆêÊW¹ ½È¾®»¡Á ̸ËýØÀ»Ä¶¾<Àô¶ë¸ÝÃi·sÝáĆϩÆÉ¯ ÔŸÖê§Ô¶ìË÷óö ñöåŸóCíùyò¸µ I ¹í> ‰(Ë%…E^*è0z-Æ"ù% .Þ80:+=êLž:c?•2~<Fe/Î;ìF 9ÒJT’Iê:ñH|:»;‚<þ9ï0Á%E3È(bú5Ÿ%C/QHë+Â/N.÷LÞ öD6üåõê¥ý~Øã%ïÕÂÝSäìá2ß»ÛUî—ÉŽÛ{À£ÞBÙ)¸gÑDÅ åÃå½mÕ´¸XĹÏGÕx»-¸ÿ¹gÏ®·ÏºlÒCÀŽÍʸ¿ÃÓ÷ÇÜ<ØÙ|ôtÔ¨â°ÇØ×|ÜHÛægÿØá:ãþÚôü` ç µk >ï (Xˆ%'5.Í)µ%ÂJ`"*G<ñ+û<é.zJ &ÊU±E‹<:M·G«4N9Ÿ/µ2£L<,áUØ+Ø1ª(ñ3D,´"‹)/ ,ú-E6Kf9ŽmÅŠ ; ˆû Äûñ²µÏaÍ÷á¥ß^äƒövæfٱϑÊâÒˆÕ¹Ô™ÃsÒ³Ç£Ë Ój´¬Ç—¹ß¿o°Èeºš±'Ä™´”´[ËÞ²ŠÀûÏ€ÅJÙYçγjÊ Ð¼ÑÕfæqòÓÉ^ßíï0Ý~õ3ãïò­DôÕK¢^!Q1'Q/B¥0…¯2â,U4_(ž!æ4ƒ:ACp5ü.JI2[rAî=Á;ê:ÓAB™762(?‡>‰0éQØ2%ó,ƒ(î)t Œ*«+Ì"‚ *Apªeò ñ›ˆ Ek‚þ‰ú?ñá[ó›;ßdå¿íϳÔÜÖ8ôçÑ÷×ÐÖKÒ|רÂzÀx¶ËàË¢`ÃÒÐÔÏÆÃ;¿k·ò¥P½‘®“ЄÁ¥Îλ)Â<Èr¹â‚ÑgÐ:äéÕcìÚÐè¯ç_ñDèï±ë2Wä~M‰[ƒþSð÷&11é!$#[ã-|*§ ŒX:¢1m7 7˜&DO7êÒ4z-ZOb.É.…"¨*)!Ø”Î*z ù?À { l¤ð%߸ç9ñÃï‰äTä¡êAÜŒÓänÚpÖ–ÞÜ|ݺ²»ÞÇÒÛ±¾@¼ Ã!¶hÂl½ ÅñÁ…¾§¿cÊŽÍÖgÇš¹oÀÚ¿§¾ÁÌÐðüς¿¯Þ¸ÕYÎ,͹ÞlØnéÔâÇ;[åãÿÓævÿODú6 Q M)¶Ô–A¿++j,æ5!b!2Æ&Ó&5£6?ˆ=A!C¨HB,PX„ÕÙЉ×èµÀÊ+Ù¼SӲȾFÉÊ¼ÈØÅ)É)ÃËÙ®ÇÙ¾°ÙÁÃcÛ%ÏnÜRê*Ý©Ïîú”ÙëÙðî™Ö³ÕÁïúíP÷Gý4íhxëgNò÷;æoB#Ö‹'àx§:r$œ3¾,¼(TMß44S2!AO2›5üA{bk+D8 M/MŽ:øMFŸHENßQ$æ3y'±Tî7*4ü/—8å-¬'n¿7=M.Â$ÕàP .øþG tü)ð§ì‚õýtëéjÛ=ÜL؇ã¢ÝŒÅQ¿)Ú¬ÉÚÖL߯ß¶ÏÊoÇ¢¾âÕ¿Ÿ•º9¹(ÖH´òĽº9ƺ΃¼û¶Ïeß(ÌÓÁÑFãWÆ«Ð@Í8çIÜ¥Úyõ92ïâU~åùä*µó·Ñ ã c±pÊåÓ#{%Wg0'<8"³7øDŠ8uE‚%¥5”1§HÍEˆ; Uâ55*t;ÀSZÀ"³š )’ ôH%ÿv÷ïwb#ìÈîªäVí’զܪOázàý¼…È­ÖIЩÕ|Ù¤Ñ-¹ÔÀ0½hÒ(ÍØ¶û«áÍÁ༅¶M¶é½ðÇtËMÔeÈÍ ÈžÏ¬À¾ùÚ¥ã^Õ ÕCÍOÎuæèØìpëÎð]ç”Ú îå"˜)õP <ü@ÿ2)#ÈÍ'P³!iá µý'ü,G(?,%/i7”2ê59€L/=7úKÇNÝ#¬R/3ê=H&9H¹0(´F7358A"l:.7-= (Ä5,e2!ü() ÊI­ªÿzâ³*è|ç âòÙù§â£à{Úzæ ÈXÑ[Ýöå«ÈêÒ¾ÏÛ»½[¸wâ{º¥ÓQ·z±Û¼-¾çÁÙºÃã̵ÌâÇïąѧȯ‹ÃÍ.ÌôÌíØ¦ÒÐÑcÏiæØÅ Ý…Û4äãínÓ‚ëûç®ìáò–ß¿>·kò3BQw(|2Ì$®: 2I -è›Fž5e7)7@TGî4(P2Z%=½KyAêV–GÞSÄ6A<ßF¸.Ø`RLAê1U<¬V&®>[/åÈ+ï6'ˆ$ï‰r 4ø¥åðßò,$ó@ÿ8Übõ¥àdÞõ¦ÜOÌîÍUÄ‹¹¨Â ßsÖ¸¿ÎÅ—¸9ÎÛÅóÑÔÆ¯ÎB¨÷ºŒËPÀº»{½’È¥»4Ö4Ê‚¯¥ÃêµÍáÎcØçÛ.ÔDÍ…çMØ´ï¢àÚWééù»æ÷óÙû•å6GìæÌ £ qòS#Žý#ö%-¶# %¼ˆ*o+1+*//M*G”Ë'¸52>~6¶?È:‘**>Å3î0M:×;@Œ) B³:«-ŽCH??1øn"¿ ž)ô: Ï!©ô :‡ìâ þh ŠöþØï-ÕíqðÅ´ÛÌ“º“ãmÝÞÙ¿ÖþÐÌÐɼ2½h˽Å7³]À±Õéň¯$¾Ç½bÒÖäÇ·€Â„žùÍ:ʱÑw×ZÉð²ßÀ¯Ù¥½‘êüÞçÕÕñmôÛ |â°îeýtÿïÿò ž¶’x#˜£$5#3‚+X,ô8;/ÿ09/„A9;vM¥/&>>WNH=4ùE˜)Õ9´9>GDü?™OÔ&o/ÒQ[9t?DrCD5+€9%Ì7#w = hýÂo¦ßõÎõòËú½ú"ØÆ×¬ïÁð†ÙDá§Ù1Ù³ÕhÖ‘ÆÁØTÈÇÌ»cÔFÐmÊÂ?ËÊ&Õí¼°»´*³á½£Ò›¼=ĹÔYà ʺzĽïìÁåßSÝ0Ô4ÖøÝËà[Ï¡â\éôðñKùëð@ô?ð²î7ø¯ý{ h(aÍk£4~"š Äù&~$Û,P*QÎ(m1ï3+ (•.Ð"`2ôJØ4°At4l=:@'@³7M?\J„-h:GÎO +ZORæ<èHÈ?ÞZ©D®9é0Y<=1O0Ô.õ)<¦2îT/*z+‹¿¦ z|õ±ÊöXô¼Ïñ塸í¢Ý€á“ç]Ý+õÓfÈk׈ٮÂõÑÞ2·ÜÂð×fÉȸ¢´˜Ó¾/ÇÞÀcÈd£ÕªAÈP²²ÓkÀhÒÈÓÆÔzìæ¼†±ÄÄôй;ë+Ù¨á‰Ú´àëè»éúþî—]öùõ-À÷ ¿{£ˆK Œ$å!ø/b-?þ5ô2.1úO&'3DÀP2FéIÇAf6ÔDßA„:N<ÿ5Î3|1q(ª:l7m%Í5õv'žAÛ3‹+>;~/‚ˆò/ÑY=þé¦ò›þ‰Êxû†ïšõŠþ3ÞÌJêŠÓù×Ë ÝÍëP׿òØÏöÒÛÎYË ¾е¨ðÊA·ƒ»«¡Ý»J±êµšµfÄ_¼ýËËÀPÇl¸§ÆãÃÅ8Ü[ÃvÓ!ÈÍTÖ½ãŽáDÿŒÛ è?ë ê/ÿåøÄãx …ôj '"¾úJ # ý+(œ*E/€ù;æ'6MT>L?R0'’¤<8OL¾5±4<<43ÎM•B ÌDzG#±'¹:>67@2u!Å;l%e-Ñœ º %,2\'’†Û(éñ¶ñS³ èð¢ý½èÀðõô+âÕòìã燻àßdíÁyÀ`ÃɽÙ-Ç ¿äǺ$»¸×á˱ Ï¿Ó7¼ù¯À·Å¹*º,Ã}Êæ»æÓƒ¿qÓ¤ÍnØðÕBÓjÖ­Ç)ŸðÈäjäÀïè§Ù¬Ö¬ì"Ïøyòül pÙ•›u‚•o.]ÿ$Ç"ä- >DÛ<(F³5ù#i5,CG±Jå=ð;lWI1±OLB×3ÅB=Ä;¹:ç:Ñ8¹BD(7:+h(l7›7%Ð&")Î {R ’,ôR“Süìúðç– ùÚÞäü÷#êméåÜÆàôñç×]ÍÇâ ÛÈÜÐã¡Ð€ÍÂ,·RÁôß±º¹éÌ~®Œ²a¸*Â魚Ŷ̻Íj¼¼OÂhÈäÀ¤Ä´ÊLÉ¿ÈèÆÒÚË`åØïìò£èØÎóµárç[ý‚÷Žâ ü!#R$È$D\2j%ÿ2Ç7W(½AÏ-›!ý"ô2ú&Ò-z,W3tEÄ9¸Bv8ÂQkC=&+l88â+‡%ÜR(A!$cD6H2æÙ-Y7Ð(3 )®8— `8 Š Rxº€ o\÷—÷ ßQô ÝéSÕZÎ&ùŠàßç7”Ð%âU‰МÄÀ@äÀÒ*Ítº¡ÀÒ¼IÑ(Ë„ÅͶŽÔSÆ]ÃÆ¿˱´dËÓº  ÅFʺÆ/ÐŽÑcèûá…ÞqãEë7Ô€ýñ‡à‚ìò‘ÍÜôãñZù±’ ­+ç òõŠm2’µ&õа!ñ","^ª>r8a:xFEGyWë6„J¼E=äN(EC@5ƒV¸LØ8g7ZC…#cQà3eL…0¶<¾Û%l,+/>e’æô Gq ‘ÿªú¸ø™èѪôÃ×ñ#å…æâà’ܛݪÞÜÃGÓ/ÝŽÀðÆXÈÌÑΨèٕ³Ùö¼i½iÌ ¼Ú¸Â¾ ÏTÑʵ³JÈÕëÎJÉÅÍÄÓpσ܇áüÜT֚ϬÕ׈ҨÚ5ùãmóHÝ\äãôšÿEEùr ßh„h €'4*³*Y? v0#CÁ:d Ê&x;-5Œ?tGO;)7’I[0ÙBV8Ú)™0æ:'H@øDœO²Fª>>:æBW!Ö;('GS<5ª'Ù(3t@€ ÖùK<$Ë4õô ~Óó»sâ|àJñ£ñÁÔÆçßÞ÷îUÙcÀÊKÒ°æ³âÀ7Ä³ÙØÖ–ã5ËêÒ¼µ$ÁëÁ)ëÍy»Ÿ¹ë®™½ñÇ ­¥ÄR¹ÇÆœÀY¼ÉÎÕË^±ÍÞ׸ëqÍ×'ÙäÑÚ ðÙòëÓXþ:êGèòsources_5316/test/kar/unicode.praat0000644000176700017670000002146611501733563016153 0ustar paulpaulþÿecho Unicode # Paul Boersma, 14 December 2010 # This script shouldn't just run correctly, but should also do the following things correctly: # 1. Menu command "Where am I?". # 2. Menu command "Go to line...". # 3. These can be combined by doing Command-L, then OK. # 4. Menu command "Run selection". # 5. Menu command "Paste history", both into a cursor position and overwriting. Text reading preferences... UTF-8 Text writing preferences... UTF-8 call test Text writing preferences... UTF-16 call test Text writing preferences... try ASCII, then UTF-16 call test Text writing preferences... try ISO Latin-1, then UTF-16 Text reading preferences... try UTF-8, then ISO Latin-1 call test # # Clean up. # Text writing preferences... try ASCII, then UTF-16 if macintosh Text reading preferences... try UTF-8, then MacRoman elif windows Text reading preferences... try UTF-8, then Windows Latin-1 elif unix Text reading preferences... try UTF-8, then ISO Latin-1 else exit Unknown operating system. endif procedure test assert length ("éééürtüéKYü") = 11 ; precomposed (typed into ScriptEditor) assert length ("eeeurtueKYu") = 18 ; decomposed (copied from MacOS file icon) assert "fQlou" + "cujYdQx" = "fQloucujYdQx" ; BMP (Unicode values up to 0xFFFF) assert length ("fQØ4ÝØ4ÝlouØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß ") = 21 ; non-BMP (Unicode values above 0xFFFF) assert "fQØ4ÝØ4ÝlouØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß " + "cujYØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß dQx" = "fQØ4ÝØ4ÝlouØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß cujYØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß dQx" assert left$ ("fQlou", 3) = "fQl" assert left$ ("fQØ4ÝØ4ÝlouØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß ", 3) = "fQØ4Ý" assert "fQl" <> "??l" assert right$ ("cujYdQxØßØßØß", 5) = "QxØßØßØß" assert mid$ ("fQlouØßØßØßcujYdQx", 4, 6) = "ouØßØßØßc" # The text I/O commands ">", ">>", and "<": deleteFile ("kanweg.txt") text$ = "adddfQØ4ÝØ4ÝloucujYdQxØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß dQx" text$ > kanweg.txt text$ < kanweg.txt assert text$ = "adddfQØ4ÝØ4ÝloucujYdQxØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß dQx" ; <<'text$'>> text$ >> kanweg.txt text$ < kanweg.txt assert text$ = "adddfQØ4ÝØ4ÝloucujYdQxØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß dQxadddfQØ4ÝØ4ÝloucujYdQxØßØßØßØßØßØßØßØßØßØß Øß Øß Øß Øß dQx" ; <<'text$'>> # ASCII appending: deleteFile ("kanweg.txt") fileappend kanweg.txt abc'newline$' fileappend kanweg.txt def'newline$' fileappend kanweg.txt ghi'newline$' text$ < kanweg.txt assert text$ = "abc" + newline$ + "def" + newline$ + "ghi" + newline$ # UTF-16 appending (or UTF-8, or first ISO Latin-1 then change to UTF-16): deleteFile ("kanweg.txt") fileappend kanweg.txt åbc'newline$' fileappend kanweg.txt dëf'newline$' fileappend kanweg.txt ghi û5'newline$' text$ < kanweg.txt assert text$ = "åbc" + newline$ + "dëf" + newline$ + " ghi û5" + newline$ # Append to file first in ASCII, then change the encoding of the whole file to UTF-16 (or UTF-8): deleteFile ("kanweg.txt") fileappend kanweg.txt abc'newline$' fileappend kanweg.txt dëf'newline$' fileappend kanweg.txt ghi û5'newline$' fileappend kanweg.txt ØßØßØß'newline$' text$ < kanweg.txt assert text$ = "abc" + newline$ + "dëf" + newline$ + " ghi û5" + newline$ + "ØßØßØß" + newline$ assert fileReadable ("kanweg.txt") deleteFile ("kanweg.txt") assert not fileReadable ("kanweg.txt") # Unicode file names (precomposed source code): assert length ("kanweg_abcåbçéü.txt") = 19 ; hopefully not 21 deleteFile ("kanweg_abcåbçéüØ4ÝØ4Ý.txt") fileappend kanweg_abcåbçéüØ4ÝØ4Ý.txt hallo assert fileReadable ("kanweg_abcåbçéüØ4ÝØ4Ý.txt") deleteFile ("kanweg_abcåbçéüØ4ÝØ4Ý.txt") assert not fileReadable ("kanweg_abcåbçéüØ4ÝØ4Ý.txt") fileappend kanweg_abcåbçéüØ4ÝØ4Ý.txt hallo text$ < kanweg_abcåbçéüØ4ÝØ4Ý.txt assert text$ = "hallo" Read from file... åbçéü.wav select Sound åbçéü info$ = Info secondLine = index (info$, "Object type") header$ = left$ (mid$ (info$, secondLine, 10000), 38) assert header$ = "Object type: Sound" + newline$ + "Object name: åbçéü" + newline$ ; 'header$' Remove textgrid = Create TextGrid... 0 1 test Set interval text... 1 1 åçéØßØßØß Write to text file... kanweg.TextGrid textgrid2 = Read from file... kanweg.TextGrid assert objectsAreIdentical (textgrid, textgrid2) plus textgrid Remove Create Strings as file list... list *.txt n = Get number of strings for i to n fileName$ = Get string... i assert right$ (fileName$, 4) = ".txt" length = length (fileName$) printline 'length' 'fileName$' if left$ (fileName$, 10) = "kanweg_abc" assert fileName$ = "kanweg_abcåbçéüØ4ÝØ4Ý.txt" ; 'fileName$' endif endfor Remove endproc printline OKsources_5316/test/kar/MacRoman.praat0000644000176700017670000000032410727335572016217 0ustar paulpaulecho MacRoman # Paul Boersma, December 10, 2007 ### THIS FILE SHOULD NOT BE EDITED IN PRAAT ### IT IS MEANT TO STAY IN MAC ROMAN ENCODING if macintosh Read from file... ./ŒbŽŸ.wav Remove endif printline OK sources_5316/test/fon/0000755000176700017670000000000011747341127013473 5ustar paulpaulsources_5316/test/fon/texio.praat0000644000176700017670000002347211625670160015661 0ustar paulpaulþÿecho texio # Paul Boersma, 4 July 2011 tex1 = Read from file... texio/texio1.TextGrid Write to chronological text file... kanweg.txt tex2 = Read from file... kanweg.txt assert objectsAreIdentical (tex1, tex2) Remove asserterror Found a number while looking for a string in text (line 10). ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio2.TextGrid asserterror Found a number while looking for an enumerated value in text (line 6). ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio4.TextGrid asserterror Found a string while looking for a real number in text (line 13). ...'newline$'"xmax" not read. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio3.TextGrid asserterror Found a string while looking for an integer in text (line 14). ...'newline$'Signed integer not read from text file. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio13.TextGrid asserterror Found a string while looking for an enumerated value in text (line 6). ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio12.TextGrid asserterror Found an enumerated value while looking for a string in text (line 18). ...'newline$'String "text" not read. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio5.TextGrid asserterror Found an enumerated value while looking for a real number in text (line 17). ...'newline$'"xmax" not read. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio6.TextGrid asserterror Found an enumerated value while looking for an integer in text (line 14). ...'newline$'Signed integer not read from text file. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio14.TextGrid asserterror Character x following quote (line 18). End of string or undoubled quote? ...'newline$'String "text" not read. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio15.TextGrid asserterror Early end of text detected while looking for a real number (line 21). ...'newline$'"xmax" not read. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio7.TextGrid asserterror Early end of text detected while looking for an enumerated value (line 6). ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio8.TextGrid asserterror Early end of text detected while looking for an integer (line 14). ...'newline$'Signed integer not read from text file. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio9.TextGrid asserterror Early end of text detected while looking for a string (line 18). ...'newline$'String "text" not read. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio10.TextGrid asserterror Early end of text detected while looking for a real number (line 18). ...'newline$'"xmin" not read. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio11.TextGrid asserterror Early end of text detected while reading a string (line 18). ...'newline$'String "text" not read. ...'newline$'IntervalTier not read. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio16.TextGrid asserterror Early end of text detected while reading an enumerated value (line 6). ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio17.TextGrid asserterror No matching '>' while reading an enumerated value (line 6). ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio18.TextGrid asserterror Found strange text while reading an enumerated value in text (line 6). ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio19.TextGrid asserterror "exi" is not a value of the enumerated type. ...'newline$'TextGrid not read. ...'newline$'Data not read from text file Read from file... texio/texio20.TextGrid if windows asserterror Cannot open file 'defaultDirectory$'\texio\texio99.TextGrid . Read from file... texio/texio99.TextGrid else asserterror Cannot open file 'defaultDirectory$'/texio/texio99.TextGrid . Read from file... texio/texio99.TextGrid endif printline OK sources_5316/test/fon/soundFiles.praat0000644000176700017670000000505111724703450016634 0ustar paulpaulecho Sound files... procedure test .type$ .extension$ .duration printline Testing '.type$' files... for numberOfChannels from 1 to 8 print 'numberOfChannels' channels: sound = Create Sound from formula... sound numberOfChannels 0 .duration/numberOfChannels 44100 1/4 * sin(2*pi*377*x) + randomGauss(0,0.05) Formula... round (self * 32768) / 32768 energy1 = Get energy in air Save as '.type$' file... kanweg.'.extension$' stopwatch sound2 = Read from file... kanweg.'.extension$' t = stopwatch energy2 = Get energy in air assert "'energy1:12'" = "'energy2:12'" plus sound Remove deleteFile ("kanweg." + .extension$) printline 't:4' seconds endfor endproc procedure test24 .type$ .extension$ .duration printline Testing 24-bit '.type$' files... for numberOfChannels from 1 to 8 print 'numberOfChannels' channels: sound = Create Sound from formula... sound numberOfChannels 0 .duration/numberOfChannels 44100 1/4 * sin(2*pi*377*x) + randomGauss(0,0.05) Formula... round (self * 32768*256) / (32768*256) energy1 = Get energy in air Save as 24-bit '.type$' file... kanweg.'.extension$' stopwatch sound2 = Read from file... kanweg.'.extension$' t = stopwatch energy2 = Get energy in air assert "'energy1:12'" = "'energy2:12'" plus sound Remove deleteFile ("kanweg." + .extension$) printline 't:4' seconds endfor endproc procedure test32 .type$ .extension$ .duration printline Testing 32-bit '.type$' files... for numberOfChannels from 1 to 8 print 'numberOfChannels' channels: sound = Create Sound from formula... sound numberOfChannels 0 .duration/numberOfChannels 44100 1/4 * sin(2*pi*377*x) + randomGauss(0,0.05) Formula... round (self * 32768*65536) / (32768*65536) energy1 = Get energy in air Save as 32-bit '.type$' file... kanweg.'.extension$' stopwatch sound2 = Read from file... kanweg.'.extension$' t = stopwatch energy2 = Get energy in air assert "'energy1:12'" = "'energy2:12'" plus sound Remove deleteFile ("kanweg." + .extension$) printline 't:4' seconds endfor endproc call test WAV wav 3 call test WAV wav 3 call test AIFF aiff 3 call test AIFC aifc 3 call test Next/Sun au 3 call test NIST nist 3 call test FLAC flac 3 call test WAV wav 30 call test24 WAV wav 3 call test32 WAV wav 3 procedure do Read from file... test.wav wavEnergy = Get energy in air Remove Read from file... test.flac flacEnergy = Get energy in air Remove assert "'wavEnergy:12'" = "'flacEnergy:12'" endproc printline Optimized: Debug... 0 call do printline Portable: Debug... 18 call do Debug... 0 printline OK sources_5316/test/fon/pitch.praat0000644000176700017670000000474310727341006015634 0ustar paulpaul# pitch.praat # Paul Boersma, December 10, 2007 # Tests "Sound: To Pitch..." echo Pitch test method$ = "cc" for freq from 76.1 to 106 call sineTest freq 0.1 endfor for freq from 106.1 to 226 call sineTest freq 0.01 endfor for i from 2 to 20 call sineTest i*100+77 0.02 endfor for i from 21 to 29 call sineTest i*100+77 0.1 endfor for i from 30 to 35 call sineTest i*100+77 1.0 endfor for i from 36 to 60 call sineTest i*100+77 5.0 endfor for i from 61 to 107 call sineTest i*100+77 10.0 endfor for i from 1080 to 1095 call sineTest i*10-0.1 10.0 endfor for freq from 76.1 to 136 call pulseTest freq 0.1 endfor for freq from 136.1 to 226 call pulseTest freq 0.2 endfor for i from 2 to 13 call pulseTest i*100+77 1 endfor for i from 14 to 20 call pulseTest i*100+77 2 endfor for i from 210 to 219 call pulseTest i*10+77 10 endfor for i from 22 to 30 call pulseTest i*100+77 2 endfor for i from 31 to 53 call pulseTest i*100+77 5 endfor call pulseTest 219 1 call pulseTest 220 1 method$ = "ac" for freq from 75.1 to 106 call sineTest freq 0.1 endfor for freq from 106.1 to 226 call sineTest freq 0.01 endfor for i from 2 to 105 call sineTest i*100+77 0.02 endfor for i from 106 to 107 call sineTest i*100+77 0.1 endfor for i from 1080 to 1095 call sineTest i*10-0.1 0.3 endfor for freq from 75.1 to 226 call pulseTest freq 0.03 endfor for i from 2 to 20 call pulseTest i*100+77 1 endfor for i from 210 to 219 call pulseTest i*10+77 4 endfor for i from 22 to 53 call pulseTest i*100+77 1 endfor call pulseTest 219 1 call pulseTest 220 1 # Tests above 5512.5 Hz are superfluous, # since pulses are no different from since waves then. printline Pitch test finished OK procedure sineTest pitch precision Create Sound... sound 0 1 22050 sin (2 * pi * pitch * x) call analyse precision endproc procedure pulseTest pitch precision Create PitchTier... sound 0 1 Add point... 0.5 pitch To Sound (pulse train)... 22050 1 1e-9 2000 no call analyse precision select PitchTier sound Remove endproc procedure analyse precision ;To Pitch... 0.09457464735 75 11025 noprogress To Pitch ('method$')... 0.09457464735 75 15 no 0.03 0.45 0.03 0.35 0.14 11025 minPitch = Get minimum... 0 0 Hertz None maxPitch = Get maximum... 0 0 Hertz None diff1 = minPitch - pitch diff2 = maxPitch - pitch absDiff = max (abs (diff1), abs (diff2)) relDiff = absDiff / pitch printline 'pitch' 'diff1:6' 'diff2:6' 'relDiff:3%' assert absDiff < precision ; 'pitch' 'minPitch' 'maxPitch' plus Sound sound Remove endproc sources_5316/test/fon/test.FujisakiPitch0000644000176700017670000000015707471435555017144 0ustar paulpaul"ooTextFile" "FujisakiPitch" 0 5.0 79.6 2 20 0.9 2 -0.35 0.98 0.76 1 2.25 0.72 2 0.6 0.79 0.24 1.81 2.01 0.88sources_5316/test/fon/FormantGrid.praat0000644000176700017670000000023511635436642016743 0ustar paulpaul# test/fon/FormantGrid.praat # Paul Boersma, 18 September 2011 Create FormantGrid... schwa 0 1 10 550 1100 60 50 Formula (frequencies)... self + 200 Remove sources_5316/test/fon/Sound_to_Formant.praat0000644000176700017670000000065311662675773020025 0ustar paulpaul# test/fon/Sound_to_Formant.praat # Paul Boersma, 22 November 2011 for i to 30 duration = randomUniform (0.001, 0.003) windowDuration = randomUniform (0.002, 0.005) samplingFrequency = randomUniform (16000, 96000) sound = Create Sound from formula... test 1 0 duration samplingFrequency 1/2 * sin(2*pi*377*x) + randomGauss(0,0.1) noprogress To Formant (burg)... 0.005 5 5500 windowDuration 50 plus sound Remove endfor sources_5316/test/fon/stereoFormula.praat0000644000176700017670000000252110750741134017346 0ustar paulpaulecho Stereo formulas # Paul Boersma, February 1, 2008 Create Sound from formula... test Stereo 0 1.5 44100 randomUniform (-1, 1) a = Get value at sample number... Average 100 printline 'a' b = Get value at sample number... Left 100 printline 'b' c = Get value at sample number... Right 100 printline 'c' d = Sound_test [100] d2 = object ["Sound test", 100] printline 'd' 'd2' dd = Sound_test [0, 100] dd2 = object ["Sound test", 0, 100] printline 'dd' 'dd2' ee = Sound_test [1, 100] ee2 = object ["Sound test", 1, 100] printline 'ee' 'ee2' f = Sound_test [2, 100] f2 = object ["Sound test", 2, 100] printline 'f' 'f2' assert a = d assert b = ee assert c = f assert d = dd assert a = d2 assert b = ee2 assert c = f2 assert d = dd2 a = Get value at time... Average 0.5 Linear printline 'a' b = Get value at time... Left 0.5 Linear printline 'b' c = Get value at time... Right 0.5 Linear printline 'c' d = Sound_test (0.5) d2 = object ("Sound test", 0.5) printline 'd' 'd2' dd = Sound_test (0.5, 0) dd2 = object ("Sound test", 0.5, 0) printline 'dd' 'dd2' ee = Sound_test (0.5, 1) ee2 = object ("Sound test", 0.5, 1) printline 'ee' 'ee2' f = Sound_test (0.5, 2) f2 = object ("Sound test", 0.5, 2) printline 'f' 'f2' assert a = d assert b = ee assert c = f assert d = dd assert a = d2 assert b = ee2 assert c = f2 assert d = dd2 Remove printline OK sources_5316/test/fon/test.flac0000644000176700017670000014567510620027174015313 0ustar paulpaulfLaC" »i Ä@ð¬ÇUù³¯´ho†u¥¾ñ´ï6( reference libFLAC 1.1.2 20050205ÿøY< {  ZQ•Ì+ia œ6ra%ìæaRòk=+¸›eèî'­ü“~dQQÑ#Ck 9ú¾=*xµš,u\䄸+ ¡h!05&émë G¸¸"=¤ôV¸ Il%A4ÈFÄê’áì _b¤´H!ìAJãVž R’·^­ÄՈ˞ ʃ¥ö¼Ê€…``N«`y˜Ü¢åÎH’ÒÒÑ4×$¹aZØÔ¯RˆÐþ£#™LÍ ÔŒ6˜I<´¤·Cž‚! ŽÆ@•·MKÃÁNû7½€<çø EP¦Ð]‘Nr6äM¦´Lô‘£Ø¡óI­K«4ƒ_ÆÈ8n=¸„Î2¿ ¿}\µ!Á†ñf¸Í%OûB|' ‹ ¨ª2¨TZ$b€£5Ã଀¼ß³¸ÕÅ)F2êPÜñAóGÁXT˜3i>¡¢`ûvö——Âs èß°·Öƒ°EÒ¤—hcLSàU®f£Á¨·œÜ!â»'ý©*\Cqî•9ÑHÚ:-Ùì9”UB°T˜T+NˆEÒ*[V£±iNc–N×öU%¬lê'¨étWfEv4B²¿ÄœÿÔTÞh¶mÍ«L=‚gÎ+D@GMµä—:#Â=(艚SåP³dg· Ì6KQz¶z|2ŒœyØT­ÞÕ,DXÔh×7‚š`v!¡r“—AÛT{¼x˃§èKFž“xUÈ…DkNš„‹aHÓ+²ªCÓ°™´MT0лä ‹sÂØY…º:¤üfvÏò+ÂäÂ%ÂϤsÜ R gññÛ·e{U!&S“zݾЏ•‰r$‡ªÈõ˜…lŸœþHn_z\’Í)Z7›¼D` S¯Ú#ó¡`€Å—dLóÄÊDBÃÓ-ZÖ4ø=Ü ‚ti¤J £xnÄ+üýjŠ, ›åö *Hm“"ÛÓQÔycô‹.‰¤“bŠÑ £€‰@%÷¥ø yÅÆd8!(+ ^…Ñ2V óä+'c"vdYåhìñs¤èœ•9|¡GÊW YÐÞÖðÐòGÈ#’fÊ_5”* N›ú^•%é¨>3•áy0оó9ºÆVS4h¤^Á%ÉŠß”­•4#“‡%dDئFî„ÄoÝ‹ú[Ý•42pìº|”÷ÉÎÔò(J¤*ÁŠhÑG>ÚÐÐGlS ÄH¨>.¼ÁœpúÅÛ:S´uo«Èhöùeã²E”N9à¼Ê“íá•cµv~Þì!$VÑwï-¨šßpK×TÙ“£tD©Ã:æ®%L¼MbTÓ—Ô[è9ñÿK>â''ùTZÆeÏpÀ€å‡Ýn¤ús•M¦¨„´V¦7æ$z?hÉj|BÎY©´’Vâfâ„õi—QyYYZûíÓiT9~šÅѯ™Dìp ,ͳ¾Ì­kuQ—…(nqó­JFŒ“m[6%®ôyàk¦âÓ9Oõ$b§h›*J½w!C$IÏ{¼¬ì¼Ý:RUþûHèrì_ÙBš îXsÈ)D/Ùú¨jMzÍ‘!52u<m>ª¹ANÀ“M¨Xëñ‡yǼ)3òzc…W½Ç¿TP!Ññ[5ß•MÉæ"¿êûí+Ù«˜²|²PØK;¤ZÜbf_¿}'ê‚Q»c| „ƒƒì $A†g%ØæR¸b]óŠbà'ì(pU‘©Ø…9v´ ˆ®œbJCÌê´oÏšiÇäÔÉ÷ªM»®zU†›Ñóº¡"¡Çõ/›5ÌéQnÎÖÔ»– ¤r¶ÅKu8DB"ªe÷;uþȓƹ͹BÒˆ£›á½ ¹ IZÔ•ýÔ4ŠHLC™ ® LªE`—sÊšæ8¾õ1æOR¹3vaOÇ9¹@¢8-«0Ò—‹ìÌÌfˆ¢Y£/çºQmÓÝB³k&îòÛZÚT§Æ…*k¸ y¦èeÇË ’¢ „$ú“Ãý¸º'il¦U%`òF†<µñCËNgÙšs4þù ~/„\ö–ûAcv]R—1 T¨lýØö&¹&Î×®$)°çaP…‹} r«Òøv[X°’¾¡Ú{´¿?d»Lø9ÏLYTlNA¯¦õOùo¨SLÉ Œµv‹ißÛ®UtJK…ž› ‹Èxµñœf»G+ÎjȪñn·÷±‚7 :>±nÖð•C4éìÛ*Ö±åχÙ.)ÈO56§]dR¡R6¥ób ja,~[_Ë{Ä–y¨d£©9¾“4]”ƒ1}rA'²Ì1>‡Pˆ<ׄ`œ’"óÌ”Lßâ|É»H­”­´U"Lל—7MÉùµ>ÒWíá/i>5ÔFØiDú°køé|u¥Ò‹NÚšSýƼ—lÚõ$‰^‚o®z»Ñ4“F\ô,)´Èª¥D^7˜²µxFcÏ3^ÌÙ-ØDñ‚ªÁ}‡SdSï] ¦F9#D¥nDµšVaŒëU$‘­YFDÕç6y[âF»ÿÊÕu[kü5‘2 ™ËŽ(©þ‹ìá°××Öp5´J;{TÞj1Ïq¥m¥ Š‹b[t œéç:j`‰Ûõ-¸Ðÿ÷œ+-¿~Ï…m'CNù)A=ô ÀL ì}`9i¾ä¼†Å›¥èØæUñQWg´¯$%ª³Çð0Z¼PNUãFå30—bÈPÿ¢Q0síª{Õz‡¢ÎGÈJŒÄÅëÿŸcª_LpÁ&_º,”J¼æ4ìKá§6Nz='òGŸ¢oqx“ ]$‰')Ès¬T¿G²\X|B€à€øCj”ÕFA<Ã]ÕÿÙ²fî¨XÉ—¬Ú­°ñ9­{ž"Âsú˜æþ¶B±%E„©Ð1!À¯gKÜm»Q!:gT†V?vE¹dgíoØg“•òR•ÙaIÉH¨À½ÀBØô~aZ Xª´Ñæ·,/JvM,ŽÌ‰‰H OØ|ߥsHäíYZ³0± ˆè%,-& Ø·Ùo”ðG6½¬ŸWð¨Àn‰°J"’4ƒ£âLC‚ÝUîãµÚ\¨ˆ)Û²+ À*oÓö´ d ØŒ›‰„ʾõFÓðºªU./Ä`oR„(˜R@yYG)ÏÑŽýS³í¾ö|p¬dbÑgŸ‰¸DsÛŸÍ´ãò]XèñäTÓHמÝÇÙà¡]Ún_?q7ÅÖäh#ò6òšƒÂej…”¢r-ÍÊ—åHH¾flƈK»ãÛJ­òYs]à'Š'£q‡µœøÐÌH@RNÔá¹ EE*›´BGƒìò‹K‚pdŸ €^E‚¿Øf)C¦¬¦p´›ô¦NÂbñ%”¦°[<a¢HaðhŠ_%ŠAjÚH¬jM¬ÞéZ¤zYA“Åa±¹l†ÑRÑ rx11ŒÌó5« R]<˜âb}SLÀG!ñ¨äþa;•Ç­SÉìÚOC‘NdÓ©öZ‰FÙKà‘™l5M†Â!S¬= OI—Wc±˜òƒ2€Ämµkü‹ú« W9VY‹Œ]git6•Q‰Äi¶Lj@ˆÃæùucseªB+Óz4z=ßáwk>R‰Æ&T¸ìVk ”R«Útšƒ¯Ð¦ôj­"9>›Æ§ô;²3€ÄjU¦g:ÛªŸÀ«&ÀÜšsr(/W¤±>¨²+º·QMQ¤)rKÍrŸ>!=$¬“è+p+Ê9™ç”2&Ÿ0Uá2¿NÞ¼Ž&dÚ²c–#&áò eá˜$lPв:YKÐD‚%š¥|$g„}F ®¦p…€'Á@ 7eµPNƬRø-Gàå…TШ§m‰Lè'ÁPçÍðzÀñ€zCʉèíÚ Š)ñÃúTÁ3§ì§¤a;ueóÈô°‚’@ô 2V®×AIÀùžá”BCâ! è «.`™Q¬OÏ „€„‰|D8¥8$8A]_Q€ŠžÓùvŸž¦^˜:Èáô†ÃÞ¼R¼Uå¾4F”T X¬½åp×2 À  4 Ô©Ö  É™ÇJA ßå‚TÔ¢õb.R¦Èj•&i@f{ XŸ¢KÀb0$#ZX­ôÀO„Ú"$šá²6vF±³áJ ð+$ï¢çÊÐ.K0HÁA‘ À Nœp) xµP ø†§Jo¸{@¡àdݰL€9ÒcÆ$à2"Š5L Àë€Ûˆ¸?Ä h†¼MŸh`7 ©žˆ‘Ï ~ÀcG¸6Dèt,²²0Mhý€´§cx[U‡Ù:)ä .MÁÜ0T¤€£@<¢€Ý€CÆ ß)\ŸÛ%ãØÑP1!óã-ËÁ8bLÞ“„S ÎÐ;*0 Ò†±Ù%Gr3˜ Œ\J â x/h„‹`]·Vqü*Iª$ÊÑ´V c~=oÔ¯*MP›‡”aÔ§á:‡$ÿ\I²V‘„’Bt¤XÕ…9Ü/ãG( ð©kB®SUÅýË@µ ð…‚F—Ôj’¨N©ÿ[M‹§á#- $Ÿ!•¬-AN5ÙÿÁ; ÎöþhO_–'`„¸©·1—gM£E¿FJäÔA[ùb ]ç\Åãã»mÆM¥„8 ´/}\DR¶¥Sµ¸Æ™î[Þ”OLf÷Ï>$Īœ¥XGìŸâ-ÊÁt“HÔßK`cˆ¨™ôZ,Á¥©²…â¬''¢H›Å[ï³Vežý~AãþáúH‚ÚÁLvë«§!Ó”NišF=ì*ßQE˜Hæ¾g¸Q"é& ؘ˜¼!ÌÃâˆd6½žîk_:9ºÔ+u|}*™œ£ô ;ŠW|% T*§”ÛÍÙÆºAÉ™Bù)XFKKw;œ^ŸÂÕŸê¶´©ÌO¥sÞÔjæ³ëkþ]WÅ£Þ”Ó{:*erH¥gV\}ŽÈ©x/×èlµ!ÐÓëöë¥Rñ´‡sæpÜþ6 Ë"®~@ŽØxHWøß‹.HJ®”ÄÁ"ÁIOùåè.V~yf@œˆ‚²LK¹CÎ Á¸ÄÛq<Ê¿©KÆîíû:F¢ÀU(‰ZFËòfª½aHlÕ}YjÔôüÐ9 ô*3‹QÑ[ž{óË®$‚úªÚéÈ–_’áow.ò]Îå¢õöE-‰%ŠeŠ[ñhÖ¼mÎÄ‘N¬™9¦2 2Æ×èw vŠÞÎ(4–Í™³´Ò,Ú‘¯ÃmÓ™&vÛ¼p­dô¢ga¤¼Ä:õo¸Nž–‚I<‹ª+BUÂ}u$ZSLZ’ é"·*|Yç»EmHhKã97àbx-!<ô QâU‹vIp„Ŗ®îæsà¸ôˆ$‚;6ö-mãÁ –òú†¬ØOÏä‰ãJ_1:4|Ÿó’­ã‘‰ÍÿûiˆÝåé1|ŽúÛ=ÐäêwX1ÉÆBtâã8Ì d÷k]d§ó.úZjTK¤ÜTQÄäÄþÞhÈT@„(+E_ &üBq´Ë¢TÂ$"¶ØLk,B€™³.‹i¼“YÌXDFE^õ› [Cr®È¦ÞyÔpkГ§Aùñ Žº‡‰ lFë««¸gdZ!X³O¢9 €ïæqaÜM[N•)Ðü¶þò—ѤÔzœ´›ï$ZâwŽºá;:7%…MEé]G<šç½,¯¦¡î•Ϲ1n)îv±4ÞЄ–vŠï²; "qÙ¹ô‚²¹ÚÚrÚ7oz ¹Øy qyꡟŒcÊxÏ:&ÊGÑ’¦5|k±;Íš?K«úÔ ŒÈ|±L'-“÷¸ç¤—ø$û@† µ“2ùFa`}$é" ÄPÚÍó ÃQ€KW=(aÌ,¦R"áÕMh7‘‚x#£ÒJÓ3ÅÜË…²KJ{ðÔ&ƒÙ‡¹ž‰?KA˜%0‡²éþÞÎ|ÄFââŠÕȕʔôYFwÀ˜l¼l÷.çUÒèšÊ’ 2œ³½àqÿøY;ùøò Š$vîA˜èFE S{nVS@0 Êbx_\¦ã Üf¹ú/üG¨È¶ f­J³ky{g"— ¤òþ¿9üï$ÉšJ•·v\3o3#P½&ZËÈ’!ü.… X¢Î9É¢ þï²Û͘oºÆø±âš'¶×“Úqkæ/ðäÖãJH*²~ç@h«ï$eæØ:X%ˆÿZéað>ax!„Yæ˜YX8!¨(‡Qt׌%¨"„²ªxúÐq\ÉÀ„º.€ªŽ9†5ÇBpfšH87ƒ(Òv»ŽÀD v A0ž fK ?ÕÁ€ ¨<] *€G,oÀ`21sÐÆ[+ˆÇ`xDH![74kDöÎÆÀŒðD-9…ñü£Y¸f Çhü 3‰"¨†qZŸÙ©R£é1Š.(„ãÒ19b 8òO1´5bQý]m¤”ᣠ9íò(¿-!h˹J1•<”‰e´Îcƒ)@¸Lެ¢_Pë¨ÐV¥¹$.ŸÌìøÑÒZ¥·¢«–yÀP!*Rc™žÜÓ#2t™£ï½yØ=NÁÎ$7õ·¦£g„BËïö[4gÓj¤Ó‚»-©°vÆCÇ•ÄÈÔM…ÎV]™ åß&Ú-‚—Jã…ÒžrKµa;¡€+õ>p¡Î—¶©´6 V—¥‘R™ùà5›Gßá 'íZ °œê«–ÓŒ\íDi½Ü‘ÜX  _¾³ñm¸dº2WDp¦ÈÙȃaô†b‰cl>â«mŒ19}Òl¦Á(t‘)­¬&™D2xèÀTsª¼Xáü²#`/z89¯BHRQ¿?”¿à]k¬2˜Ò_`TÌ^DX:U{â]ß`? -k$ÑèJP7mÈ®á„ÄwÀZ’/Íb~uíE`N$«ˆëà[EvUYàT«±U¡BXªIØ‘BÎgpßQ‰}˲É:*è²<'55"®$¾·$Š©vcºËìÓ°ÁøØSˆÊ†¶Iu(´Ñù—þqЯl˜cÑZÇŰ˜²²d@‚%Œ`%ǼÔ€À@.Ž`Þ^Û‹€ˆN½TMÊìðÄÁQr’q§y=]•κÂM% 7VŽþ´ß«¬*”#PÕÆžÄ'¢·AìO±ALP7µÒˆM6ñeN(zÉa}÷Ìxú=uðF“euþ+q‰¢ñÙÃn‘ŠFøTKvW*¢óJÄP*~@c§ÃÀäíY Z¥ŽA9ƒÕ40½ÛN‰:PSǶÍêçýôÇp@[RXƒ@5îZ®a Î4©v‡ÁŠDƒ IHäN ‰5 `ua5Y ´‚ p­áóµXaéŸêp®Oêg€´Õ^ÁŠÅ_¡Ÿí´å~[¸SÅÛUzÉ ºNæ·QYQÔ—ð_ @ü0ÍM¥„¹›L´jêôCq1§°Gf§¼¶`Mx£ ªuðÖ°AþT‚w<«lÇÑl!¼žŒ [²2ž%Ç·jI¨ÔýÄ®u}„jÆ‚v$H¤Òº*á%nÑ2ýâX çј1_u×þkXaRg³%¥>dе×ÛØz¸.YXN^'NoKï|‘øÍZE´•~)g×go÷µxM9ÒE¦r­’rwN¤ù½,{°ë)û‹¢ˆÏ• mc2‰p%f_èü ¯¼À&"x§Qü‰§×‘\Î6_Ñ\ޕǘ91É.g«!LÊ 8ŒV€W/í5ÊP49LJ€¬š<îU€| Ë ®[Œ0“Ñ ÒÀ;"Ãs¨æÃ,{M„€¡!Wœ>Èm,Q–\Ê´É$õ¢æIÐ G2 çÆ¥^X5ôö­Y^ér©uÇÉë1GþTR‚—7 0d_Ho+B¥E9Z˜œ£3”Df¥ÿ9¤wêj?I7¼ÓCÈÕð©0׈MuÇ}kü†D·&Ö©cRí:%5.¸s—ªpŵᑒkÎ8]Z8KAq¦W7—Rµ<òа昌A†«‘ [›G_ë(tM š¤ Óü_ã£ê­Êw1ZkFØóe›ÒK ¹ÇíšØ?JÝÀ‡oÜÿH“)N ¥ZªéÞ ðß 9q.ƒüÒcŸbœ<6KVPW\Ù»ne yŽŒç·ß#t‘ È®[Ðñwª¢<¸% éTšÿktèÈ…«}²p3²0F7YZß©óJ±ÈX6!ÜÜÉ}ÿæ ÉTÙ ¢A(Uï­:Y I‚cŸ­q¡SyjQ6¤´Bsû©p%dÌÁ+cÕ¢Õ ex¬“ì³N@J¯É4AžÒG]9¯:t|ïér\•B­}š*‘7[jšÉ <¨±‚© šïÙ¥a§z¸b“–â*­ÕÒÿ-dÚ„$<•{dË4¡y¸Çÿ ¢²Œ¯Fªáìaf´“Åoʸƪ{6ý¿%¦Ášê–y0©x<øà­‰#lä®OÚ‘V‰»øØˆŒ´Í! Yz­í“ 8ð6¯©‰ËzÞ2'>Ó\sj•YÙ‡ãHÚîÆ¡ˆâPÝt£ˆbZÙÒc$æ~›‡izÛ‹ á7,˜{ֳ尥Èr®2†“p©·XîúK çÓÞòéÕµT&½ÉÉÀ.6 @N&Oæq÷x´KÑÛ¹õ-VÈ#yP"pqMÈçC11YâjÙtW)“ÝP†iºaÌI"µ·«c¸0"S'‰úÞ{äH Áj&o¦#¡á’Ñ—ô–µ³ ý‹ѼUÔïô›'¶©âeÒ>,‚¾·ÓÀ¡kÄf8+y0Ü Â2›XÊÂŽ ê„#Ú±|SS´.-I Æ×dÁt;• ®á Æ›Ýõ梡`@z‚8ß³Z. ¨…)¾Eô½)›Q–wÍåj1žß÷h»ðÃ1«—ÄËÁ05™ÇýJ¯É‡CÕ:ÄxØI¹ÏŒŒ JQ쉴ÄOÍÐ êëií¼9¿.5ë|®¼ØæL1ño4rD„ËF{O«®…2ï‚¶×h€! LÌË„§eÝ6©Ó]Š6âÒ±‡Í½p*¾¾K7Êé>Ì%ZPì "¾ e…¬",rY¾-#Aø´¹D™Â'åmWßãÏS¦l¸:ÈãßÛù¬yŠ1±¡“±–s!Èån⣡sqaCng‰ºxJÈ-íÆûidyRð²èó’G´!‚+±¯êŸ,yÞ³ÑìäÂÇ–"”+=w)Qù¿²ÃHÝaå$Ž$¶õøñW^Ö(½fdÃh'-¼µ‰3ÊãX¹il`Ícªœ(m§¨}ˆÏ*›šK ”Ö®û?6`DHËÚËš[Ü\ö7y[˜¾ÊÌX‡BâŒ4ÓžóU7'”ueÒºÉ[6.ø{­%¢½s¡i#Õ]2Sºq,—-Й¢Û­÷~Çó%ïòZÜÏ«'„‚¢ÒWº6Jâlåe½Ëêê̘FæÊÇ`ÉpLAØŒjÒÒR &AtÐOëÈCÌiy.X$ÒR¸e4ƒ˜]*ŠõД>´&‹&vÛ• @Xc˜KìMº@fRµ Îå2l%•z\ h–áù5&p(‘úÉ)³‰;øª&9Oò•GB*‹a ´±¢=kúrÑÝ(RaÙåVm€•'ybwŠðäù™ò¢ù"gÐÂÔLƒº,tFèhRÁ¿QI>…AX<ÂV¸N–¼`쀆¼ èî"=N— š ê5ÅK{Ü.c›DòKbš#„¢r9o ío9ÙÚé"N:õq]Õãàè¹^Š?e Ó®ÛA΋B:)¡Íί9æÌ< ¾÷ÑÙhPi4°³YRæKêàù$‘#é3L„—R 6…þ®“ë‚0$#A„ !fè+À AXZ@ `ÀŠCLêÈ Fœ¾ º`Ið&È)`¢ðJµÔØD9XB]ZðÕ…¢€ÉPú%‡³ñÀ( ιᎠ×ÀÿÑuStv¼Á«¥)¼ÄÓ9(äìñ]ogA„ȸBƒWкÙÉ…ä1ˆJ@¾A(›k»^'ù;š{s/†4´¥ÞÅiŠlb²cª+oÖ¸ ƒWv·qϵ¶äáø¹(GˆOúöTÌh¨„Ã2‰3­3b1é\¢i(ïªB(r^ؔҨ%2z÷ùOÖ&#§D–+¸×šø;0=)M ¾O_öN9¾]ºe4–ÚSÍOKŽ è#J>6¸jC…†"IYò—<毢u Op3æd*ÏÒ8¥à{îMaÕ̰ºÁ0ÆQC[*Z]iì¦i½ÏV*aH-µÈ•.\Û ÄÎÒ5@pÉs¥×T݆€äIþa¤eˆÏ~‘5 aÜc`f6 d\NV|cK?ˆéañØJÍR:h,鄎5!X‹½ñK{Ø+¢ó2ã}$'V1Å É'ílÏ(‘·ó1C!®qéX Æü„M SÊíyWL$BJrs_³¿×æàü¼””®¿ª;–d‚áËQ´ƒU\¬ˆ“íRKHæÎǼ&’T]shÊBmݳ,n"R5<ƒ+x©÷$þc…ïg·¡å'ÐÈ„˜M¥ûDG’.%1!nǸ4•w=…º‘‹Ã°PÙ2Q”¯:!t\Å=…™)ÆßÛ&¶îEvx‚”¶L‹^t6¡cÂÀ¡ WtËrßlNMpQË‚¿-S”°ßJ³YÝ?9Gä4­7¦Ãë³ë“JµºTÜfO݉8²^D… æún¼(K² &U²@Fu»¶Z„¥CÓƒœß¿YÉW×M’,-v³Ó8ˆ©bI0‹…Då‘É Œ‚0×4–{o©$4Æ ðM]3¥„þ¨€¤¿B6ƒ† fwƒ ˜p­(àiΨ! „`.ÇQþ Z9DJ²Øƒ°AÀo§=øFÉΤTÛ2¼‰T$É|‹ÍÝ®û\ªª¦t‚7¸³[ ÑÄ͉YåBSl)Y+E@‚¦§R[LNm‹ûhí,$µ"Ø—IRèDž…÷”c™A!«é­…r#žâŒ7Õu…Ì5‡}XÏò² ¥q¡¹cö‹²‘Æ'(ë}qWºàL§œbzY][xž¼ò²›ðUJ)ŠÎ²Ö\ã.ÿéÙÆÞ®º1“öü¼^IT•fx’·F%jÒ¤÷7Ö•ÉÊÄœèI)p«aåi5]î2æR`[¿/^üˆšŸÒíέ†ÜZ%V" "#^ÄéîÑŒOq-ÌI˜”x@bmI²ÏÑ3*’®×Ç»ïœÚ…H£S^â¬$ïäs±ßu"×ÊÄFÕ.mN dX¤rOß"šŒ˜I^t÷ïT©;ê.T2!ÞêxZ"R{*6wYNZJOQWŽP5&‚µ~$y&Ü‚‹ Ûhꪽ´¶„±œŽm6 &‰P¨D&½ˆXFcäEB9¯yïY’£p‰\Ö²cQN°ø~ùÿú’E#–‚“ùl$}¾áý,Õ^÷³ûÖ +)'©: ±(´Ç´æø“‹ «3Q“ë1PgÎp\"ñ4[iþÛD‚‡’ Zåûë ‚S*ËÔÔþ_øØ`Ù%Î7&÷£_Jj3 !hhJ'BD·l¾§º&6DQ)}RnPŒÀõ)Šz Éa°–Q ºJô·Pgx(‡~ ÂÝ—RAjx%ÏÁ]È©#¶}‹:Kì ðt£Žc: &-Ò JѸ¡³B•Ö7e{ÿ÷ZùˆŒNÿøY2N&.&%Ý%…%9$î$p$µ2¦8N€‡çÿ@*þlx•\Â6br™hº2…a°2fè ¡är´T ¡øn¸ Ãø: Ath ¡$" ¦ây1©É¸nMB|–fJ—[ȆƒQÙ”ÞˆÆêš˜Êƒ¸ô_-ƒ„y QðZ l?ÐÄÇðÊ#ðþBÐÈΧÁØ¡-bᔾìÞJ‘p#Šá8%„ØÐQ¦*„Rƒ­ðêØx(–ÚÄA-‚ ,Œ47‰Aø<‚øÀF4 hI #P„1œÀv,±iªšÝdgÔœ©ÂXˆS¤·5Os¹4üTº2žTÞšÉK¯åæ¢ÄàQÝí#«“ÄT(ËNÄ¢ËÁ¤Â”L¶Êµ$ØiŸŸÖ9rãg¨ôìç%êd×ê<ÒSŸcÅ'—Ó¢£GÈãÃÑÛ`7­°5½§!`º!©èW¸¥Zݺg¶W{¼¬¾ó\¹¥Ø©/Î6š½«Âƒƒé“Ž¤ä°ªƒ„Ͳü¤evkfbG`ökt"%Oú 16U×›h3=>­lû«Í’…ZA«å\}ezå;yÝÈŒËÐÔW_È$f¨°1Êc@ÀS ã@Ä 3`|Hè @B Æð´C5 $§ LŽúÞ'&V»žFÅ,åà4f1¼Qô4 %ã±X†óEÐÃàj—Õ‚z°PKíÇkšâèÒ#º•ÏaœcubpÌjVn$#Ä!¸x Á¼ƒh3ƒl‘ì-‹Cд. E²ÉìÔ'™MÆ’iàS,„`ø!ˆ"9Œ@†Ahy?šN„3BãsÛm̾Šìg/;‹,Æ"É$˜¸¢Ê«ð’ÁóBÐ>ð\­Ö{f8“)ÅÉ2Hš$:õRŸ'Wí¾´|\ÎäåuÝ]7¬¾ÜB7¢îÅÿ-I€A2gtZ%Ô–µ­¤IÚïãð¬áÒªö>L,÷5b«ÿi»Dx©:K’]Êu“i¶ÛF»œ›Jæví‚'²\Ù²bò´s öÐÒ_òHŠ ,¶¾LʶÇU»LwK/µûb—™ýy£Xâäßm—?k±&«SÎzHM®Cˆ¢X5OÌ‚!°ÜO5ÆwÆ–÷fbºê¢úøÒPI¯8¬.¦­&Ñ=®ò}²p–9n»Öy6×Hý­ê(àö´W~j~¹T¶£a´ª¬îxp`;1-?°®Ü)›UmÊÍ‹¢Í3ltPèW¿j.b?Cã°Ä#ɧBkÙC §×B ¼K;Šƒ@°:‚ê¸XÆC¹èfsB'"óŸL& ÆC59¤THÂàÆJ%<5?âé8½• L¥»µOM…™ŸF·źçRjUwÍNe'|Ê`ŽÆÀZit`q?‰Çãþu~UEî×våö/ÙdH˼k¯æ¡|¹ Ä1dl ¡ˆØkãpYÂhK2¸¡H\'¿NÁ·ýôí„ÆŠy“£4W§S¢}KêB¡æ¡Fˆ'OrÕ;Eºn³È±Æa²ZxiB*A(c¸h¾Ñ©³MÀ®ØàW\CÈÀ†AH‡qÄd[LVÃvzßÅ3¸ŒÿÝrÝÆd”7ܤ)Ú Ñv@”噺q—ZMñî“&ºó•œ¿-Ù^Õ¿ÃQáÇP°Ú#§ßdisµWk÷Yöù]ÛÊñÏ“`iÕ˜0ÄX+AÓ,)GøWŒW9öG‹±*¿7^µò$Ïìûeצ—ʈ¬±RE·­n¡æ‡Lg¹÷’…¤ëi]qñ)þ}íå ª¾í«àx] ”‡§yöJá:ûlÚ+ART4·Ë£O˜*2ïÐv<š]ó¨¥t'0ÈÑrI¬YHB¥d ïÉù¹)*ï°$Åñáùtªñºà ÿÞ:7Í€ÏÐ%‚¿C¼¢Þ]­m[ØîAÂL%JÆAq8ÿVi°æ0]'¹!Xû;W¥©ÅÄòÁ¬Ãx¨•ƒZ„IÇ?^ú¥QOLÂVÿæ±ðËC¡ÕrF|ív mf„-UÃv6¼8ÿF'©OªÍ2{ñ§Þ”¢¯äêõM*«o „8 $­×ÂÙbåÊ”Gé½fc]?ã(IKi†Ž¯V]žª‘’fŠ&X°–ÝÝ mBÓ% ¯±JÕSŠ÷¢eÍAãê•̬”rZÜùº‹JjXû‰ʘ=¡ ‹n‹ë[„›«nëÂÚ³j¬†Ð„ýãÕIã˜Iª[{’Ø 1šF?Òˆ*$Ò{t– C$ Q«Ëó$5%úJèyËËD'wâ“øû㘄t—µ,kOwÅÓj”êãÑö>‹¥z;“=¢Ç"ýM9·»_ìõ± B?ÎÏ'‚ÄËäºIÍ‹iÉ/œÓôxˆ$¯.‰—2¦ñ0+Ís³eê³{fÙÌ™E*eY[Ô¾š?RRš¤âXŠÎ•1I¦£%>^¼i-•Þ莚Rß®­± gØDâòø×ÖÞÚ j P!iJJa<‘|Dd§°„‚k‘äi Ë@Œlt>xX­& Þn…wÖ7ç÷Ö£Õ¤uþ¹[?u'á<(j ÂTR×ÝÁ^ö$r³ËæOì€q¡<}¢ý4Ÿí–Di~¬ðìðž\úé…Ý/¢òÃíé¿{ Ä®óë_‚U4jq ¹gYµp¡ô¸ušÖQÂC$4‚k/C¥bï$›gù–È"pv •y²Ã*k-Ýf¯‰Y[P&Ÿ–lVÞמ{©÷¾ö¼ªµ}¸¬z?SˆÒö°TþŒâð«C;ÈÕi3Eç¾|‰ˆŠç3_IˆÓöÉñê—ü¼ü£ø%·»a“*–::Ÿîr;F©¦\S¸vÈú_ã ¦MÕsÍÛ6(J*±òSäOÆ>a‘çù8JÆlEQÞá4^?ÖÍ>ávW”oU€ î¢¸$îù1£y£tå¾iõľ 5É ?å7çñªEÑ`ÜTÑròãã³êI 4ÂÐ4ÆL lé¥yy Æ(EûŠÍ¤$tSÈjðJªh†\ÇšÕ>Ô“¢øí3Ç·IHŸ&-kࣩIS³ƒÔs=JkHŽòܼ-9Vx3׊SÓ©BÐÒkÛå¤yZI•*"JhÍÒyF'OègÍ9¬*Ò(N4 ‚ÅøŽhN—#ŽÚ.E•™l:¼³$Æ›s`Î1¤FÂB—KƜ莺0Œ ½%… ꊉ•äÙž‘m™é6ˆƒfµ.k3³½.®{AWqZ±Ï¤™%èO&&¨±lWµ×Òà%ÜEJi*·ÙˆØ¹£« $@‹U_­¦@Q†j½-iÈОm²UFU ù vp3O=yœ€×éƒ Ï4ý·B£ÜL¡Ö*²S@F;Ë-TÖ% ÃB.¼¹ogÜvŸ2GvËìJ‚ê~&µ¡Ç# Èèw¿|ÄlÑk² ,Ф<ãsÈ÷)JÅ+ÏKG…ü,ñ'J+†š²£åÏ®;Íñá6ôúÁ­ÈQF~v6ì˜Ûq”À’ÇaÃHleOæÅ½ÂøüŒÜÛíÖB-»ß†éB› zR˜©æ…×¹P}þ}¢R’¬à‚„”Ú¥­Eꤩrækn5t¨EŽ,ä?Ås´²‘ǓׯÂ|¸U8k˜ØAl)W(ÙA3|V’EGfÚ Ä„ý«PAŠëŸØ,¬‰['xlRÂu¨îèÈi”´QBO?¾=ÖTpDÛa)£øÊ`³¼Ç±J7 [–8¼·q"j53é™JnmËæOï4Eß ®®*›M¸¶Y·œ_°òÌR7š—89VœÃÒ#«è¸ZCzOðG›tuÜõ|¥¥ñÕ0 ž2 Xsëã¿[³7ê —³’»o•=Nï#ÊR9eµQ^nqÐŒìʼnp†)d›PÒ‹Dˆ¬1§ÿÎ`ˆLDîâùZ‹âE“Á¡/XiMe*+HnB·ˆïÔíšµš‚ÒVÝ]¤h7ÈâþÃÀd¹KÒ˜ì`ç0ÊÕJnN³Y’ƒ/A„þ ðâZ=éq zÁÜj» µ×ÚWêõ^¦°Ó¨ß›ú$Ï’ÞÒʽ1ÄÅ1N¸$-Jý=…ç*æ„×él›Z¡íï vDÆ ¾°u㨩k+PåÈ}—-CŒ9E® ûarPS[ëu°0ìþ\½h`ŽÀÅPðК’eš™ðïh°,ŒBÊÒo+©@S³~cξÏ1C0å#êqÖ!…:Æ*â£4 ¦!¹{:RuY=¥Âå Ò Q¼T)€˜ZIŠœ=| K‰`Ý ¶#YñrÍRAuÒ^%¾w»(…$Aö&Ñvmy΢ Z¦Œpq‚]¶]]§ZÐe¼ í"‹cü2^Êœq5+!.;ÂMvމ1ð 0Nî$pd0ÂìIêCS¥xˆØÑ)‡ÎÍ.Ýïp„lEÉ€³#’>_ã93¨‚]vORèì^墄”vÚåQ3”õ¥†3ÑeØç5Ö¬ó/rÝW±—$'Eu;#Gñ&gê±IãYYRKÂ@åÓ”`‚+¸iƒXV–O˜¯­,í 3'%¸SŒ¼R2XöZ„QHIƒ¦ã/™ ÝÒ¡/Xy¨½4\¨÷Ä›Ú~ð¤2<…ìQädT+jJÁþÃÙSlâ¨Í»²6~ÌM-'ÈceÇÀŽF7°vœ-VF é¥³CÜ®¦Y±%%ùÊPï´vÉÞ&å@¯N{Ä#ÞhøB¢<À &—®Sî§a|®VŸFj¾¬íÅ;¬HÿzS‚™§[-ù¹Å 5`Ö‰±vqõXô…«òi€ƒŽÒ·Ÿc #.“«ˆfœ«£n 1D'(àdÆÍs^¬€½âø“nj” C¦Åù ljuç¼bÁ½ð1Ré¿ë|´›8HRT`Tüq‘nìR²"!êL@I- èà‡\¡«!kQá¿•çñ˜÷MyÝ"ˆ«[^["ùÚ1~¢¹Ü•ÍHÒ°‹syÖ‚ sÀ‡(F$Ï çº&B¥@² ã‚àîkÂæ[Ä+´¤$Á«d×EÞç¡w”3ÀRÝŸ¹ †Üð%`@¹dVáÓÞ¡æô슔}‡b äŽßg=ÆcÝwQgvm±p9Þ·…ù‰»ÓåVˆŠÜÈ–]^;ƉSÖ¯«/»dPMn¯rbF­ fÈ*ùM§HÈ¡šÉ}ÇÀQÛŽXŽ1ßDX ÖæhêR8JÛ°@¡¹i^Ø'o\Ä å®Â‹mO)›]yè/’¢Æ¦òÚÏÚÛ¨}…³,SÇäÀ’¯aÉÚâ<Æy^`ÏN½‡¡˜ì#Ö¡™ì€Å޹qÊ"Ò ~ñf¬UJΪ‹Ò6€¦ˆÿøY5Nò•ð•íÙêËè#ç=èÆéÛµ< Å¿ßïÊ C‡Ô^æZ”¶½E#6¨g÷w‚l[ö}K ªŸ5Üt.‘Œ„ïüäD´ºH.õÖîÃPçZ²Ô¶óª…>!ëÈÙRo'qô…®G¼¥Í»‹Ãô\¨½NÖŽÔ»ÕüTíή~.‹«ãRÚN¤p‹ž~b²Éüìü-ë­ôQ½¨›ŽÊ8§|%ãÏ]µ“?»£~ WÂwªhmqº[ˆzµv´®Te½L¡ô‰Y}B§¨Â`^"Ù§váhÇÁº#"Š¬Ð„Ä„’'­ãêi’îZKî[ÿ«“›Ç¿õW òöN'É ö<¹ÕŸDª³¹6UÊj$@ÚhS ’nœœ¹ 6ú¤þ'D±ƒÐ"ˆDµ‚õ b”×ý=®Øb]ûJc9Mu¿­—ݸ²†1\NJ¾{àS¿Ø¿p‡%eÆþù вö’_ט̦{xîé·=VW›L¼Þ˜½emýÝìÑuºŠzTòpá|$È_‡û’@ýÖZ9‰5• æd ÐÉ&×Fë‰Ûz ÂSçŽ:_â¸Ý¢»é©à/‹bKmP_Ÿ£[Bʇ~ЇáóMÊ=çBJ©óEÃðñh»È"—I½Ç'ÃÛPõMÓJÙ§ã¿Ñ.°ÊcÞ¨8רúQù§R¹ñžÌiή–aÒ €6£2¿ŸÊéà¦'ú3bƒh^T†ùØ*‚ล°ó·gTŽ Sýò–!cDÅuAÅ6ûÞx"p±–’’£Âw¢_ßqú2Áø|m7œL¥k ^²öÍöyª«"$¤¢N³Òè¸8Aþkd$QÀ3"oVŸÖb´(·÷Eu+“w8K™œLc*…`Iº«V²GŽ€Î(ýÏa]ÎÛ&`3´™2›þmtA!3é¦ÃºŒ ƒ=Þ×SdhúŒ§YdòXÏvú£²*«¹å1cê¥è|¯VMS*wò)äue`‚±3:,¿€i.²´†‚“+\#¨ z/VtB°¯C8™-&+ç_‹l=Ã}~¦ s4­(…sõηX黤ͣ/‰qCǧ-hŒÀž"» ¹NêNpߺ-qäu:è 9“é"L„ F2—VÔ€µ)v#Wg]éþöÚŒÒöEû;)–¿Ò–õz÷gLy#ë©>Ö™îÌ[£ UpÀ„<çX2t˜1c²/¤™ÿ÷Ž?œt\èzäŒÀÀ4KìàºÈÁiZ¡ÁüæþU„7*\ƒ´!Ƽ]É'ãk~J®Íe'PÃ~aF}}Ð8"²ç‘˜úq¬SV\úå $~ÞžSå u·À¤¨²öÓ¿HÇõÿÿctú)û2bH¦ñS5ªiо‹ëQÝÂy¬¥.&Íg$z„ó¶õà±–_Pó©½ÄL¸özf©c3dÈŽÚîi|jæ£!­ð¨×jR(/5pGÿhƒÍ9e[qŠ¥H²ö¿ŽP‹œÃUZbùâhWˆo‚a¦Ü"Bà9t cWˆVèßõJsTFG îÁSÊúîÅ}°)~·3Žd[Kü|¹s– Ý»* v yÑ%Û)ØØÚ¼M´«Lƒ;ù¸’™±x£r‘Fîg«Æd}ÊBìMZyÔ[•NíÛÆŸè|\,¦Š¿|Ô N>å„ö;n»»Å›_aOTl7”ÕÑÒê½ci{jKä…•J4†°TTò8\ÐWu°+6¥>ÖôU^ë–ègQ·k#î\…[•)Rv~?ÎQ/ÙZæ1-õ ‡[vС©æ¢IÔD½Èýí!žjž2®Gs6ºñc«âJ̹¹©Wjoú±¾vfsòëñ5*$&"Ö*ô¢°[ìǵRV OÃéV` >ñ&‰B¹‘.L153±zý©H]˽½!G)˜òVQT…ãJþTKˆ‡ïi%¤É8lÕE‡,é©`v”“Ú#èG1>±(lý_•JGªšÚ|I¯M7›Ž!pË-Š ¬~°ý´–‘ÄTp'Þõåëtÿ‰Ç§{È:Ì xÓPS¯û@|„29 ‹EãnI%Hlp9 {3¯Zœx eü÷«|j¹M ¬œ²= 2sßÜY…RÞbÄ™4Ëp¡¾ƒ|ŽÊíD¨Ü À)ߤíœÂ0øhèbô Ø‘£nz×Ñd1%ôçħ]vÝQ.›E %ÑÏòó4#âøH[ÒÛš¦(ÿšÊP÷³‘eg¶rî!ÐZ?ÐõÝ)Zü[Ìq©h,®)%ºÓE`C‘È.#‚˜ñF© ’‰oX÷ç=~ÝœsàÓ*V2"î§ÚçJ½œ’Q1®<o‹Ä8ŒéPA [¦O˜_c£a¬·ƒŒLM=Òð†©uº¢VrÖRâËâÜŸ¬!¿hjM]…³ëtéS'®‰Nê3RMb„52Ë[|NÐPŽÞÉ[•èï‚XA­È•*YVÜ“²éßf…šAß@„@ÓM#"@iHò__¶±GÄ-€µæD‰¾†°…1œäû)Ç_œ%~ª~†£4S.ɳ%•€D%¯ýÑŒ'/®9-(øQ’ ³éÐÅ'{–‘î¤3ÏaÎÌERÖ;”D´{×í2}ò:Rã?UŠ¿â û{üMÇUVH mg†’!x*‹ï‘ÉŽˆr*4Z!‚ÚPLë¯,èà£aŠˆÀM¶Þ¾À\ÚăøWšr¯B^¡ub=…¶L0Eð(ð–BXK×f`C¶à¿ä B}lKSúÂŒN²Ƹ’*ñp•]¹Éo3(›aŽrùVGŒ1;/oÑ „2¯g¿¤l)â+Ȩ²¯ô¢ ø‚¯ |·LìoÁ•i´l-ò¯Œ'_Ä´h{c<ö.ðGÖ³#_\M‰ÛÜ^»òúg­·ÆÖ˃Ø[=V½&J銉/3˜˜çDÌ“ž•»úì­$C3Q&]jîdÍÍŽ[¿ÓÉçé–_ŒQ_uuÂ]”âàÚRç‰X¡$h5.k Ö¢jö™Tý³ìÁ‰ƒˆyg²¬„¹ ÌÈý¢ +JKˆ›ò¯q[;ÈœQÅÖÂaKycV«À¾¯¡ àÏZJʸ4®Y¤b<ªjc-£å7H \‡« ËžÌ@RU Ø=¿ ›­âÜ/Ú£çgWéf„ºÉ.»Ô#`±ÑÌ[Ol±~éé³]¦ªf÷Ùå"ËPnˆ)e­·$i€õOWÃ6kàK¶º!ÔS‰¼àY¨*Ž ”_$]*Ž$%=\¿:ÊX\ý•6…º!WßÏÚ£¯¥Úì¤ó=f'ãÁÉ—Ë™µYn\ø©)$=ÔOí|ïåq¾pøV¥øg· ÕôPÈbhDùã^ú 2¬¼lÞ”àE,PË?6ãG¯i½ƒtdƦ³±FK ¿´_â´¤“²ÇíNñ\‡ê@ÉwLdUqùHÊBè¢ôÑ0•Bf‰¯÷Mw“q‡cÆðQ7•EMÛ§qE‰ýTõqZAM "°›÷Å9ÐÊ0И¶¨Oê.S×fK[’ßé”|;à%ÝrÎBS”•s [nŸ6 *®¡eÇ™‰äÉm±¹8„?5¡Õ†Tž—ÂBŽàïßIP€v¥kÁÝüE4ýIã¹Ú;´þ‰þÏ@TŸ‡Úm!ëq䪔 ´ù påç_+£3ù2öxã˜®Ž™•#|9?—EˆfŒUÄqCL i!EÆ&Ɇ›wDS“jŒGœ¶½,”mGV Ûë ŒúH¼˜üjÁYã”›÷¾Ð˜2ñvZL«"oW˜“žìñA{ÿ¦,D…uÕO~íÔ!Aç†./Â’ ¥P$h¤¯“9Ï9^U§|>4êÊœ¢n*Fœ¼1·|[ÁVE‰Q8eM%Í¡Íë.ð©Æ±£Ô‘sc×åµ67¥±®8[þ*¸·ÙˆzÓçÖæ f¹¤1ÕH­‚S/.Žžë»1˜¿Qï]§‰åÔ¬ôS÷µ#]Œ(‹l$NoS¦¥‘iª£Mny™XTʉ\$»œºÐˆ=ù¯æ÷¡\Ùf“÷ˆ‘-Q» )næøc„]ÐEQpHÝZå·%!)1ÎjŽiÝ\Û$¨<âÂ)Ë•MÓB|)h`ÃÕÌm´]ª™`K{N™o×ÝS®q¥;z2uÕ°£ŸöÙ¿'¦4´¢R?bµ¡–Ï?í­~J@ˆ.³æJ2À¿Ê”«ñˆÆ6*Z©µ-¨€êP“…ô“aMz[I>³¶Ý:Ðïcè1vr1—^~¬ÅÙ“D'Ü%mW"«ÁÖh” ‡<³˜³Ö»Ö9(;RHdeØA ë'÷.ðèÂ;E,߮Жœÿ©s³4(BLd5Të$-NÐÏÄHç$€Œ&C7²±F(†ê×Ò>$xÜH\ASŸD $ô#¥&š8å4'â¾Rö;|-y[uueœ°ÍlЫ%ñÈ'ôùQ$qo‰]wêšZÔeþë²L—~Ê9yãù!R_¤ždu•'¨Gjƒ:RëUz^¤#°cm&7%–&ç„e÷Z¯¦Ý3af²QÕX·ëI)øé{% ä¢*È‘ÓÎ’rêØy0ÿ¿åŽ÷]ÔYz™lsY™?¡f Ì‘fÚ(­AmpÝfm&yË­mNX‹Ù«Dn1߈ºáŽ•Nq×±˜u“>5åLñZø21É.¨=l–Óâx7Íq(¿ó´ðwQ¶& —bQýçíÙN*.˜CD|hÕšÕKSBÉ–¢—å[Ë2B&ŽaJ3ÿ×np™RCfªª=ÍÁW¥EýáÉ}¦XÑx!"NII³”¢Rjû³ûQ±¸o"Ž_bÚ0«­^Ñ4‘’WDŽùA,-ëc|Ø—±/.¥€g³öÑþ.ä…‘nM_Àèz‰ƒÄ&,^cŽ‹Íkç¨æâŠwhG„O~'ÂñÃÅl+j/Ý_Ës¥Lý26RÅu¡š´ÉNLnøÄ|ó·‘Ñ}^*TBÓZT ϓمWÙÁ*4]_JI *TœxõòJÌZÞr+ªÒµºZòÖHF:š–†1E3•¢¥ôg£Í÷wŸ™è† IUƒ‘¬ce„÷À†jš“büÌwêS¥{aÂÚP¨ä'Áܧ¥â6«k ¾Ÿ>„ÕšäbHnéã–Š!(S9}'Â=úNÆVÎ#Ñ?ˆá‚’ñ¡"à·èêïø£1…fP”!cÊ9õ6IÚí1%SKܧðfƒ¨¾ûF™e¬ÔV°ÖØP–¯þhQ1ú·b1äb"'T]Ùã‚´ü¹a¯yyìj±•,Å(Д ¥ëœºŠÞpÃxÑJ¨` \Ãß² bB}'1¦hòþ;Ø×m õ¢E‘)Y/í³h¦w•’´¨™X ¾_§>AêZ²²_ :àÎ…F`5D0ÐÈ_Yàæ:ê0lâÍéÜÆv;¾|Eî¹}úÃÇhå!¦3'qNˆµgh6i ô~fºŠ±]}‰Rw¤)òÏÆæW.)Ãp"J°B_°b#ÏÔšÑHözÐn>¨ÿ/~bÂCÇm¾ìÅ"§î¥×ò’2âR@ØcÈE…ðÌ-j@­v¦ìÐHè ª ¸ZIS`£N²} Ô¢FƒxÇõg‡"§0Ÿ¦ÙGç>µ~R?±VœK›Fëò{oË€\˜¾·/Ùö€b¸di™â^ëd¼l"]«RL–* ]﮸éRËy5`>Ùbww¾ Uå]÷UÀˆ§,N£P˜^„JaŸÕËXq ¾#S§'wk/Ðˈ* ‚¢¥MÇ9xU ]zMä©ÿýì sÈ+*ûTÎñCÓò¸õ‹>Æ, «ÖJ{"Ô¤Ç{ƒñ ˜}}k#ôÅ—|†%fvþ3RÉfd£$wæÒ„͇Ær~é† g¤¤$Q'áñ•È(£ˆ+÷ül„ÂÒ=u~hì˜vôž­Ðµ•;pé³»ÁÄsmíœö„®.Kp‡X§ï¸†éðZÏË ˆ„Câ-a!zE…Ý\ŒçÌýŠß‡Ž€³eŽÈ°,ŸÍŠÊÓíÒ,xŒpÀ ¾Ü‹#’… FÂYU SØ”b!;¬"ÉzˆŸ VP„,BÛµƒŸûÒ~¨@XSƒë׬›gî!Q·úë¢×“ÖòJò²´f_4¡uQØC¥¡×Æ*iJ¤²8ý”#ƒ}˜L â~¿£”EZÃ!ÆÎY'd+}µ;7­Lm ÐÕŽ B&£6ü¡l/ò¬Oò=‘;eiyº ¸M“«G-UKp S*Q‹Ð\JhO…X@Cw¾ÒàÊÙŸŠ8©µ!2 BBKp•ê:Y;)D©+Z7ɉ˒’vJƒ,O³VÌÉkjÝQëCÞø½eU¯ÊDtZäˆQµ/ó¬ø•èlÄƹr’àïˆØ¶+œ¬ð[Wº¬‘¦HÁ)%¯:X`/äcoÕó44šêIžî7ïƒÜÌ  q$J£rKVA0 !-c*@ݤóÿMòµùYEsf6¿˜Ë0ù,dEÅë.‹u\²±«“m(f-Oú¢:ìJ~Ü—»…+Á*¢º½ëjÜÉ,ÊqíÔîê]ñt¦Ãƒã…gÕL(œÍ2ÏT§8'7nŠH8×¹BF÷ôý*žrWžm#ÙÉ9ò()NN_/:Ò¶`ê!ó4ƒ³»^Tê ÇkÖ9³2VJÌzzœÖ'ð¥Åvº)2/ÖsÝ’ôQÜaº¢M‘´flÄ4È„Q¹pï @]—oó†¶|ê ã#ê{G®F,Væ•Å^hýÜŒ¦lÇŠc-ÑRVÄ_ðŒ;èj9—Ä¡1ßQ¬j"åüœó¶Èº”ÛFõ¬2u§ÀPYÝ”zoÑ{Ñùw—1Áy·Š«²%Æ@ˆ¢C‹âé’€Ôhp5Ù4”X~R¯î߯V{Ê\ýÖmÝ~Ý!ÛÜÎÕ›­­#3êæCÀ¥-F£ñ¦^Ÿf1ªa ¿Ø{»$ŠRÿQŽ;ÆÊâÑ äÞ“xc-×Y[…£‡áä“X§ ,ðCqLÿ]”ȯ¥é…óJ®bðóæ>kû‚¦ºNâ=4ìä©÷ôàÝ*^ˆÝ2d“r-é‡é­ß:Ph̆º€DÚ;sI™Æ`Ð'ZŒÁ&T=%‚jT#êßJíé«ôWÛkñôfj§Qz62–RîoM/¶îÓ©2b˜ÊS9µ»A/³G:0˜Î–Crf4–èMF­ºU$«á¬,D Ñ> …påz• ÂùŠ¢¶~´¿!°Ã¡&eÈŠÌ+‰Oʽ{Ôµ´]¶;$jGwËCý*z·ƒš\>ªï’€„ cèúºÁ8Z;ƒpDŒä wY9ŸŒ ’ : bŠ¡ yÅdù´î®¸¦·W³¾kR¿¥8|›õtµJÚÖ6Lœ*j4‰gãAt†ô%maÉÜŠpƒ(R†Þ™yF*`õ)PÈî ®ò+ŠŒÊ– ¦ÈWši'4DO{uTe¥FZ W'¾Ãì£Ñ0´oï“ÚêCQ¤¢)8Ë‚üV“‰bø¼Òò›ÚÆÀ=1Ë 4ì¼óñ‘ß?¨ÀCÎðaz}c”J ÄD×¢Ú‚ãF¥Ù°`,Rþ7E¥bÂSZùœH#›Ù†‘8d ¼•RmU­Í1‡(ßfÈ›:Òb÷ÄÓ5È¿==5궃c1ìô{+Å2 Øko&¹*ÞÊ®HSI6:„R“ÉŒ˜ø™ië§Ñõi¤¦ÿ¬Ç}JþL¦uÒù|(.½:dûŽkC§Ê¿Êrw1yQ}¤„q8%µ``eàï*Õf_zæý&&÷Ȇ Ÿ^ŽÞRõÃ6¸ºè“¿—A’Î%D•ãÛ” ' ŒC1X¦Ÿñ©ªµ¯¥«1ßd\b«È‰:#QvoYm9¾Þ[Ì6ÕVò‘TøNÚAhö}#† ®$„hv6…± úÍBÀCAðäݧu¦ÒïUYjq“b|õ§©¢„2Ì‘Ž=FÙŠy‰¶{¬—d–ëµZ5‚ƒ²Â—JÄ}EÞ6›ÌOa$BáX| ÂU ƒhe A¨{D°ÂEb/œšòÒòŒ_•ùb`™"Un¨ØhÔ‰²Ï^û uÜyk²o]†ÃÒ‘Ñ­ÊŠ­£Ø“ÍóLîý­Öä»-ò MÝU/Ë¥Zú90˱dè'< †Àò<…!(‚HI(„Ö=yÍ/½Í±wD„òÒŒ–£ÁÁí‚ÝßB¡uQóóv6õ˜15)´ÿ½,•TòªÃ᪦G- e‚I¹øD'=˜Šä fŒv4߆$§W_6œF'Ì'y“›Œ¡À–ì½UQx¾”õ£¹ôJ8ò`æI/š™ôu} Å'q,¦þ_3—Τ’©P¬c“DCÁ¹¼¢12 ¯Häv3^W%z­|²Òo6mÍ ‡\ÿ†M5„Dd/¬6ÏmÞ=î¿=nÚN•~f7{ü×7X$¹Cû½qæëk#·ñZ ¬)ìj Í-ìØû§,õ¿ ®Ú>Y©mdŽÀ†LUÝ@[wcÇ[.àÑ|(|´ÿ¾_ï[µ ­Ó†Õ¡ºÇ™´H¡Ðw$Ëdnõš$»=ö`·Ûb]Ž Ê~\ò}¯ÞX¬Øo G·fÖ­¯J¡Â½úŠ1NCîŠi9”ÂUÍc8V#ôt5ŸœFEbÚ×ПÚ!GßiR!’C€Ç Û ØW…X!EnøP…¾ðE“¤™bÓ\ªué$³SÃŒ1 ¢BÀN Á k â Z/‰¤Ë:òâvs~Âu´ŒÎ@4ÉLĶ–V¾[5öwÞûì Pê[õ.ŠÎ^K&¹°FòÚÂJU(µO¤ÓùÈ€e d±¨˜T‹Æq †M7,ˆk¬ädfŽ]™:Ókm·ËTY©Åꤡ$I±6—*5Ò­'V{¨ú]]kyÙȈ(éÌ8ݾT|¯ œ•FÃQ)EáãI£w9G ÛËúñnÈéÏCÑù翯̟ÎL}r‡gU¶§x­XéÛŽåÞ2‰ØŒ)©<þäݬÞûÞñc–¦9ÒmŠòd@—äs­níá3%“Íd·›û«Ú}¹«¹ù¯Ò˯曜©ÛÐÜLÙp±sY¹,´ÎÛnmK›²áݧÑÕL®û×.T«õ¦T—$)Šd»J÷é:·L¾Z:éùôJ’BGk% ˜š›Ú¸@ÔÄdâ³lQ¶w»>œø(ÜRE’S–¯±¦b˜åË3ÎqfEšìö+b·x JDµµIí¡tnjí*½¼™Ím‚iq0޲BW,6²¨ª¨þ½úå Úµ»ß ±Lü‰‹uú½iÿfK¼ñ'JsT½c¹ÈÔÿï.r¦  `J‰,RerdMUcÈY£õõÈø"F½ëê‘ yX÷oò¿w·O7©vå,ÉökÝÂÍRÿµåwå ®TžÄ—±Øär7ž—]š[¸’ys»s<ù1uw²{;ðhùÔîŸÙÆCº^ùꕪޕ‹0•FÁͺìRïµ™&û\‰µ[D§C£wä"ç;›Þ¤1dj7Ž¡8ö%óüB#/9$¨·álrkö×;³+µÞj½BH·\%©¶2EÊq…ŠÄÑ)\ñ«¿„[:2n²âò µ"!mÆ“¼ {©œÇ›Àtã ɽIù‰wÁ_;‰¯ åwͬ®ƒw%?•Ä÷[Ë1qÔÈâ5¶ …uÓs¹…éy‰O8Ý{¦L’4Ÿg9¾t‰‘âõgi¦\µNtÉŠã{»Ûé6Jís×ÊÓÀyÓáÔùXy1/Šb² AO†Ñ=9-0› Qa´ªS À‹­yRȃÇR´ \j­«qS´Þ¥<÷Õùs0¨@óó0®/þáa‘{qÊã0œ £à»À/ÖKâ ]ˆ4Ø·‚ÖZƒeÉ€pµ_Œ×­Âvä# ó+Üz9èøkhb¶¾€4 À%'®µ @Ñ¢_Å&‚¤ƒ¬ˆü…¢çtì…K?ùfÍPA Šóí­Â,Ÿ+.—§×©ëò"þIZ¶Vd9TJ6W2¶&tò 5(±9¦ù „NY½hå@vø½‘a%¡HZ äEÓ¤¼0_èêX€ãP"7  6 €z\ ’ò¹¾»#>9tØú<=So%ça5M&.9þfssHAfXÜÜåÆ \ŽL4%zxJà2cÒ<¦áñÜ/CÈ˪– ½Ñ?µ´)dm´á )MP‹Q1Od.ÍÁO+*Q‚2& Ö\%8sé§g¥“7Ò )L kR‘]•¸yÐEcÜ£éU× é媑“ K÷´MâNbn]%¹5¶îàôÈ´0±ë, â†9·ë؇ĥÈ#ÂÑ:ˆ -ÊnNñZQRÏtZY™Èh)(B¾‹~j\L>!¥š5RâÂÅ(ܰ^ýrâ+·+Ø·ZŽ%ù(€‚CÒ‹ßÂ|Ff&í ¢„ü‘JÔjSFðZ°¹Ú ÈB"pÅ`¸L¤Á\iJ¯ Ìt eM2ýÖ°†œKÚè«NèR.ÆhKŒ·Eü»gíßXöR»&,z ÊGEÔS÷$ª.Ï4Ê’„+Ô½Xƒ(΄$ÑäZÒ…Iô!íK^ OA¬P0'ˆ ‹,BX¨H¼ìV|-f£³œ…byt¨–‹X¶»£$G¡)Zè<0éÖ9ü„Dh”à¡Ïåö)?BÉÔ»ÏXl)+ –#Òþ#§ úzåDA(¡¸+<Á7XÒ¦¨W¼VÔ²A”‰|áY‚º€Ø®*˜Šdc¡IѲxœ«ŸµäT èG³†§hå¬pÌá’ MLÒ¤!0ÁcÉȃÜjvi0]ü—ІÇiD~Vœ/\µR:â©&Å»Î݈€V±V¤ r B2\.+¢¤Æ(M]$4nj˜Á´MI])6˜xÆË}ÊÁBp¼´‰›Rõ$ÄÍY̲ØlHà‚½‹³¯zíôö5%ø˜ôX^XDÉ VÒ,/Õ¨KS”Ý$BÍ3 Û¤í!#Ø -RÉ¿.‹tøˆï2lDKª¶w3Y„,KJˆ¼¿ ‡§UB>¡.Ôª+Ë z4¼ù%æbØÉk,;XeðMˆ"ð«í Š“è ”œR½`fPËѲǪÐè9Ì> t G°?R:ßAr°#‚6‹ƒŽÛ”’õ³-)“ÖÓ¿ Í {6zs—ê])Àýˆø…D^;óT\Âj許NF.Ú3ÊzÔ2^¸T±ê@ý·‡Ê„nߨ>,µ€«éÝ…æ%ðÌLî"‡d½ˆÏT(]°&27ÐfzðJ 3?«u’VÈÏ_¦­¿'@ñ‚äx½^ ÔE£2”Ô oªZF‹ˆ†;‘IYèúžÆkIËðK)bö†4 M!b‰ÈèSèaøLua’`Kg)x\W¿ƒ—£òñ÷¹²T…,>È Ü<1žv?sóúùLh…§#·¨%§ÁºëÐÄ"š,/ (|ꬫ?SŠr‚pM¥§%)·¬×£ã•˾‡b!ä8Øîwãi®ÂæÒC¡Ž"èèI:ôþÆ̆ôÓ/dܾá'“Ÿ)i5àÔ9‰ìÈ‹"iÛ‘—ä¹:=—PFgŒß ´OAMh‰kì/rD&`f,l%*bë©ÏACóÖ° CS È©ês‹U—6·{¸3‚Öõ¤müsu+Ct”>u,ô®ÈÉÑ“!tPµ¢'6@jÎD$çIET ƒA ¬:Òp‹ ¦þðoÕH”Q¯;¯‚3$åͶMÆ-× Ln™pÁ¹…#ø¡ªÐÁú@p=ñà=A-”úFP%Ù….@/ÔÄÁËЛg@óòŒ¦[‹$w='oÒ„yî¢d…Çñ¡Z͉Á Í©ð½0B×{rXý’v,’5ÝPQáUi¬¸—2&–±KU…Q8IÀ¥9:2õ© úÌŒÚÄl½5©%2VQÒìèÑú%Gá1N'™¡;jkÎ „ûž¸Ÿò¥T ÷B{©Z Q,ŽãuVÒñ(é$äŸRp‘ ,BVȵ溣„›£3«û>mœ@FÁ_h…K/C±Ð¦ÒC§¢'¥G±·#„B›ê#¼è½siŽåaãDHA@ùÈŽšHVRN=KrÍ,ýçº"/ŸÃjXò„ÜdÏ€´z˜V# ÁÉR\’làT€I Y¹GÅiŒÝdMI—Ø®úUV'Ñ[ ÞçBV˜Ë³”ªá;D€&ºœ—³-¾XBª`iÈH`§B!|Aâ"Q;2ÄÜZ ÝP`-ÊJ£ »¬Œ1 D'c#ùŸµè—ÆvÙA÷pãÍrlo¹ýšæF“†+§He›Å¬„¡„iSM„(U˦LS*ƒ>HÞý­‡ûF”‚’èÐ6@|_ð‡óŸ‘9M÷C Zcæê øôžd|ˆþ2B[Öä‰Ê¾ñq­µ²(zPuÊ´Šz2²KI:´bñp½‚gÈtè• }á~Ú¥£äÈtp{ £éÒ^X_êï]‰?ÇGSb9ĵÿh!«ù)ë妵Ú,$ZÃA¾ñ®¿j9…‡åcâLÄVW $OöW³Î«-(Ä#*N~ÄGŒ‹x3fzâ dsY¶Ib+ë$w}©Áas\b%FŠÅ%󉜂) äDåpû­okŸV¯š´Si€Ñ浩…>†O°UhCCœQå’éì ‹•ådr^dS8›Íb³yÞR3&¿VãS[ü¸¥6Ÿ4Í7{RL…†Œq%^ AJ¦éW HÍ"÷DíSQþ0D©B‰à`unÛ¡‘¦MV«a/ÓjótmÎWÁù³«ïþ|íz²¥ÔçÁ!t§á,”MLiÔšxé´ä‰yÚ¡ÄC¸ã’v´U„ñ uìkÖé[îÞËgCûu#IVתê4¦B¥yÊw\Ÿ­03ÌpU­D_1Ô–œ»m-b…KÚ yIL¬ ‚§)aðì‰ËR=AXEv"j´Öï–c•‹–^Ò£ß`žvUˆ¨Æ x-êxEŽRN.xO‹PÏ‚b’„Ñ$.¶q8u‰yçá‰ñ=™Èbç;„xDu™èbÄ¿[tæGõŽ¡>SÜ* Ë&¾mrnG`2(7i¸ŸZ/@‹å·‹¾ï‚:ª¢tþøÓP›ö ¤BDe÷ã6…á-i¢ðÔ„WD qîYML¨DO¹CRÆ Îõ¤G]z›ç®ò% Œ<É ç˜FCæ¡ÓÀJ®1³•r–,ay˜à5ÁÝÒ8$‰ÂYÃYö' K® xò~Z‚­¾˜V”r/ñX#ÐÜ6á@µo½á Ôˆ#JÀª§ÕEgIŽ.EPtF5ˆ!Õ1Š©ô†ëø (eТآ!„u2J«Ž‹‚ ‘¡Ñâ"õÅ™‹Š^ˆ© تálâZ kà’#¡+Á­ówüx žXÍ8õ,‰a.t„ë•÷hc†yÚ2ä\¬ëÆÜ%œ"öp©9AËqO³X‚wþ›F{̨€d1£œ:ѺL@´øÿøY.NãâÛãä£ã‰â âj㮵/n”xYâdñÒ×A*@²Æí×tqË!k”¨Ùe! ®SМ¬©NÍA›èëží›G‚qæ¼JQsuvY÷ŸÄœBlè³’²ñ é[kÜŽLT„0“–ch¢Z߉J"g6ŸJ£EñnrÎšŽ©·äj)à bM/ˆêW£ÀE•$"sY¶á²wÆ_Œnþø¤š:§ÌUI²î/ewÙó ³èåî̽‡Üjá°¬*§y/“À˜–8~¬§§ó˜d ¸¶*%÷ã‚Û*Mý–eØu?^ÝȆф£;µ˜~¯F¶ôœâ8š3I¥Œ—„$pzÁ,s™|«ø…‘÷ªý%P—P¹uN[&…“ÂDåÇÈÑ8© øûüqòMo¢ðÞpŽêç ÐŒ7>:©aú€·¿Ýy‚qºÞ~ c2:R ü)ÐVFrvÆ ·-Ê´Iéæ„ Úq¬YÓ‰ªÇRßvYXqH&Žë"¹o›Õ ½xæ.$”ª‚'a â9~½žõ,È‹jÚBŒ¥rÈß#'{>Ó&QôÆžá ̱¢´mÂ,š+ÂY$;¶4èírUO-líùpL$êB±“^/N‚ä,ÏN¨o„"îcÔ!.ä5ë0!…8د*`HÓ»[ˆ[G‹¡¿¿ºR&ŽÖð¿¦ð@«áy¸¢mDÙfÚö†oˆ÷¾f K[¯3žõlሠA¥jÕBÿÑM6øWÜÔ| 5IA5ïHñCjjÕShè.ò˜q-.;¾î*”ä½síÝ$%tkXµ˜­†üº¥ÿò⹺„‘™9¬M呱Ó~–*R$œ‚¬èÿw¿G¢äÃ$](ßæK¶qˆgw¿-ç«ã]à7P‚ò2ê X²iÀ]ša©4çüþ—ÀÌ( %rQJÒ’Qa†=@Ë¥|„•·&éGXØgŠk VÒ‘U j,þU3ž_ò;åìÎâáê>“ö­Òiê©V^Ar*I‘"‹ ûë°ž†Ù¨Êl›o8»ž”Hl‡êQˆ+ÿê' 9å£1.`¡‚þãán2‚¸s¹kµÞ•g$²ÙjcãÏö±¦Èj %Ízùäøv³åE7Ö&¢‘”Áz–ÌÓ–.Ñ\«ñh.]EÏAØVWnŽËúýÜïµ@ˆ Œ•ªòÉ¥l}¡zƒØqYÝ[ꪥ·µ+Žsì‘‘¹:¸ìt.b6Ž»µ:âåd ²A„4µ¦y½c‚ôùpDÏ< ¡$вÃXŒH²,·²§×ˆX£Õù–èéy¤hQ¬H ”ì9Ö~È€’×=dåÚ5ï7Ð¾ŽŸüGšË2\ï%²¿ã#QÃï©€÷ÚÄø0f%»’§)SÍlè"P6¾ʵ®DîKÏ>(Z‰ñD™”˜QúI?”­ 5 Û™{¦Ä¡$ãù)ѳKfEEæ~%Fé¼c,´Æì‚؉e’· ¡BeÔ¢‰¢r$.b"pr×\GÅOðH¸ëE#FYñ_þbÀáõÍPPŸˆñ+dîWL‡™r^ $HŠ™|{­vMŠD”®—»¹j&“w†rü &êR´§’Ö:]¡:F‘”u)©á„iÑÆ­ù cEllÕm!Ä$Ú•€3öUU¡¶ g¿s÷´T ‚ˆÓ£‚Aôûq¶4Y8B\ðÓ¹€¶íò¸™?ÎC=¯¶«é¸5]ŒGÝmVXÿŠ÷­}º’ Ä•>¯>߆Ã%Ù­øùˆN”y¹VuÝ,)ÌœÔbgËiñí}ÏQniiÿgSŽ$õ ž-»¡©ª–ò†›ÚÞ=O’¹¤V`ܬ+ qªßçè§yXp —«^®5‹Ã%¦¯ð:I‘Ø-NYcC/É GºÖ<µäc]ÑAô0ü7Û³ÒTÝ>¡0Œ{RÕ¨0C5]qÅ@F(š ºã©2^­âgEh<(2а­{˜ónËÉ‹qv;Ë©ooÄ}I¿D=ÙIבžW˜])*}:p7¸ä.Ò¨…âØÏ-—ø¸B%¬uqûÖ&P.ƾïðöÞÆB-w±Ë¡-¦elm䆳ŸËÂëÙ]IŸÃ]U,…›tþ‚‚5ßL®ñb0ŒgOÜKšÈÅ( ï&…ŠDŒóe}wã "—zIj¾g ¤*Þþ‹–z–]E?¾áèdÊ­vI¡ÈITR”1•A ­‘§ÁnnŸds˜N¯’¿TVùÈºàŸŒV÷{ŸÊë:ýúd¿“ÓÂàÎdÙ4='KÚº± ‰:}|rx2 2{F­(Êf™2G“Ï|…n]µ‘´évPqéDeÂP0 u°Âø™c*dûÅK:âþ†Ù¬K #*o»®­àfx¾h˜È2"¤¼øˆÖ2dm~fµÅ©26î¹`>»SËøaà³=¤e%«´pꮊ֎$Î9i·Ã¥Ñ›ÏÜeí.ÊËF]I)ìÜáÜ£¢ƒ³]Ƭ\õÊÓ>Ìý3:è$”)%tmB× ´‡p†AyÞ"™_ëÒΑ%“?ÞSU;UŒqÄ_Œ"Ç9#pÇROV¬zf<¶Iz¬@ Dܘ¬Ç‰2zäëGñý ™_Ô&Ðìˆ*ÛÚ²©q;L”LE&ŠpÙíàÆ?êj …*8–Ÿ~‰Y‚¬Y6ÓôB×r4G˜{…ØžA<Ç O&â©óáÖh"[e\³ÏÛâºöhÒ„·§ãÚJû²a!ÓòLY"í›C†+§T…ði&²+.†è0ø–”ê:¥¨ƒ-•]Å`æƒxw‰ÿ=¦L§²n5ËUì$Û äœá_ÂÝ’ ¦Í`2R.‘¸gožD#°¾ŠYSÚ"éáóó-éÞaýJí}êúnÏÙ?deœ‡) SÐ’Þ¹Â$´„ŸIŠïûº…œëòoBñ$´Ã kþIUx~,* ³Ês?˜ —·¯û÷4qÀ@+X4÷ã¡åRí:DÙºî+Kòȉ‡OVj:ÒÜ$EÕÒ/ ø€¬}[‚!e¼o‡:3œÂ´t*C©^¿¯z#µ€¢™¬ÔÍ:÷¢uZÄd‚„–ë ŒøBµ]Ç ão â"³“:é¶ž×™‡‚.AâójY>ù†ˆ(‰9GbòK;Û-æ{ö ¼%A{´zT5`!F`*1UGžCcÎãE»½å•kZÔX½{4”hâXbçÔÿ¨Äz{ÐÍ™qI8å퉫7"þzv8“‚Ò¤|»g¹Ò#OD%AÒç©Í,1TE )é3½Üä^“_0ww³¬<º}9Jv¿6ïï`÷ )Š“@Ý‘!–-ÑoÞ ~ôÿYlq$}ÝM# 9ƒLØ,',î~\‰‘¶5?´T¶eì眱ó£4ͨŸÛõ.ê?Qº¶æÕ#^‰÷xËŽ‰­cúèÆz¾ƒ¸·×üçÚ…3@¯¶ÊÅR‹%Â?Z—Xª«+sÕ¤++Ú]c&<\©Ç!‰Vèñ5ܘÀÛ˕ĘB Ž™¸®Ý£õÞÄÃSÛrWù„cUΉQ¨x¢‡,M'‰bÔõ«am$.ÿ¿h·0j¬œ‰Çàlm+"[VuÔ ý®pÇ»5L_^´¦”ø*CP7 9䔯ßz}{F$mMDVÀ$fE Êæc/¹-ýØi>ÇJ§·&Ö”ë(;ÎalÝXl¬‚9cŒÄ;º¬Lc1ô¨UÓœ-2Äh³lI\:±â\ÖØ&¶²Žb t–?”Ï%Þq²ˆêà ñ"ô4概I4_6gÜ„s¨ºÊvÉx&¿[­ üÓÓ$ÝÁ#xÔÆ´"H-ÆòQ_¹¼&£7ß‹“àA­î¿¦S-‹¾LŽ™Z|LKWšV±¤·úMÐÝËœ¢´)K0‘$zø7±æc’U×eŠÉ"è|'£dVÒNèšeˆaÉ-•UÎб&Ô¨·i’iTÑDàÁÀ`)»`N+•u£I÷J©†`+ ÛKG"дB–ºäbX …Òë¹,Š=’_X _<ƒ ³‡$ÔO£0M7EŒ×˜`‹9EÃe¤—[yi0‹:͇ú¤‘X]²ëí¯t¤¹œßs¥aÄOc<éâñi™ãÏ'v[} ßôÞ²×ñu‰RlÄ"õîTÒ*Ò]KñhB3N±\ÎåÈ»{fúÔ²¼(B9œúÇmÿD" 0QŠsùâÒ‹h$þ6X¤1ê-NÚMÕ—?ǘÔ#ËëvÞ9í ãŽ-ü?‚˜A0@·¯N,D½ÁÀEµÄ“˜¾µkZ;vò,ÛjåÛB—R.¨Vº­[–+ýU ï,S†}¸·ek´ï4>Áîº%ØÄ¬‹™Ô@D™hO2¶Ì\×Wf§övštŽ2Ô¡´Í„ ­ÆÜ Œ¶ÔË×Qè*ÉŽ½÷"E5•€vœ.)ÑŠ·6IYoDQ8œ±DsÿýÓÁ™É¬ âé- ;ä: ¥›^ìµ PÓ[±ìq.á:!EȇOÆ­8[¬¡eû[Aˆ6“uÓÚÆõ¶TÄ«»÷’ãš“.il¿f¦Ë#’Y}r;ñD€G—á#ïØ¯3¢”pɈ`%Xav×Ì‘fÎAl#ðð1Q¤- ЮÇÂàˆ Â2j„~‘ÿUVGâŸIɧ®õ,ƒ9Uüxšlt¡øæÇ5T¶¥ƒÌ¹cèAIi*´È³i£èF È;¹›®‘gèºæyÁ Á%Þ‘-^qÖÄ ¼ &ƒLŸ+²µ)4Ö¨±'UfKÌñ*t¿Éta~_Ð(¬én £ª=óT*Ò‹åPµÜè,ˆ,©±š6á­AˆORô`ç9R8ªæDûæü=@ßï»Ãë^ 1Òf p]‹‚øŠg%™È…6 5Ã0&‚É×Ü/†»DÔ=f¥h²šÿX… rpšBœÂØQ˜þBH¦œHÌ %à+‡0¤Jôj]àÑ‚äGÚ“¢ö&¹zÓ¢„‹"t¹5iظTgûŶ©²35l󨯱ƒ–RÍÿ¦’2#ŒQ¯ÆÔ )A¢ë•F+“Ç„~B˜šx;žÉfé¯z (‘¶^¶+ ”ØÅ@QÂ0Öznø¬à‘p™³æÔSœK‰°QÕ>Ô£î¤H+Üܬ!1 & Ê!¬æ¸)–§I{‡'=ˆ¯ “… ! SÿÀ+ T®”ýâÀ¼ GiþëXi…¼]µþgØÁ ’•ø: DC$©ÛÜSt´Š$sß(E éÅ °kx/”ÍáéæfÆìW 0£2wÈTãaç%å…™¯ þ/Ð%«­1{iÊ´«¯³ç‡=ë7® ³†ùÝDÛH/óaåXFƒ CžñT¥ìà£e#»"๠¢½EªE«Hk ä샪œèù`á Ú`En.Ï>èli—ƹ:µª" œ¢„³ÂBZ CŸ¹ò ýò6ò$oúü "a@˜$ ý³ðâ`¥BH@4Ñq¯Åg¼“ÅÓEΑRÈC#'4JšîGñf–vj`ûÐÿ ñ {6“êX6Źº‘Xê=Ÿ†A¼D\`°C= ÀSXŠ€A ýbÙŽrê/Á$a=TµeyƒßøÎTÖ)½=ïæù6ý¤]U4²ý£¸¸)Œò\€ˆL!tp'±áãHN¥LYË9yl$Íþ¡HGmÂÓ¬ŸZ< :ÁY/«–Eõ–(çcÊPÑתÂSyt„a°…E»ç^™¨ÂZ_C}.sÒ¥JÚ¬š%á ™Â^Ë_‰“®GO‰u¹øö)½{Ñ#'7œ«l¤íŠŠ^l¢­íõœ_D·‚ÖtªÞû›²%ι:~ RÍm¥—7§sbq—²-ãB9/³W‰jÜ$ýhBh–LŸ¨¼K$^ëèA(ÇXAŽÚD¤û|o”2É1V#'ÀÖ/9‘Ø/tñIép8‚È–R Éâ‡nnx"†¢u_:tÅáÛtì C¨°¸|U.XEÒ«>KˆŠÙ2þàPˆ 5÷‘›%ÙfbªhóºÿW߈b R4< ¡pG% AÓüì=„ÔcEÖÚÒ‰w\!Eø’ïËÒnÙ@¶)ˆ(€¼M%pÎC" ! š‰W­mh.M°«[Ätæ´ÊýÖîè’7B.(° «T~¿¡¹–~Ý«‡‘`V$#UÛI/„€k`æfH0PAt?åa°&jU\Ä## ºo…ø@–c-`h]t3Ê&]°Å±5°™,‘F`¥õ *Ý»‹UßëpĶdÀD•ЇÙ  _:˜dp€Ä‰æqÕô.Ô׊&Au Ê6Ë¼ÉæŸÛ¿IýÏ|ŠÐéäïÒ× RŸ% ¼¢¼Ü?8SŒíÅêU9ô ! 8§Ôy'PB±ÐA9æ˜ 9ך ¨x *¨,ƒ!²£{ñtšØG9(U^¬ÃÒ)Fý†Çá¤%²ÏèGcN‰ÁñÕßh€Wç¨womKzw éh€—AÀý3° G¢PE‘`$Ø;„â‹Ê„9†ð)¬H'%ÑDöB¹<ôú‹O9äÄeé+!Ï”J£U æ9¤ê_9[o!1;z1—Lò`#€S…´ƒSãYPžv(–‚à{8³ ‰(Št´kÄj"©`ä« æŸ*¨–1«p³—ÈA\J l*r3hÞKä·WŸ9–[ñ°Ö=òîž:Ì5ÏYÖslL›ÓSëêÞF‡ œÚ_ >ÐýjG$ì Õk¸ˆƒ¨ªØâ€!ØÄ®T=€Ì±Æ›°(!ª”ª˜_ÊxÂ.·/D?‹®¥…º‰G )N‚a!OÇÍþÑEë;‘žjýÙ%4J”´¬\&V²‰%’0¨™VÒKÓËb°qjeòÈŽ=Єpq ƒ˜D•Ô ž4>¥éeÿêæÒÃ’ê¡ÞêfOÅÁ7ÄØÛ§O -§$³nÐu!‘|H[!<âð¼î ¥ÿøY)%.% Ñy´J\U¦’0ÜF_§Ë0ýyŸ°Þd-“¤ËŒßKÐqs ¥Fo{e²áâË$ÙÍ CµkÒøÐ“ŠJ)ö1•’ÉÕݧ>…uÛ¼ŸaÿQ÷M{²pw<ÍI“º-Cc pñ´†Å*¯y ²‡ñÀ/Kq`¼˜ G2ã®$õåp¦„AÄË˺q‹‡<žÐPD¨Äm»‚šhÈ”yïâPª)˺ÍäÝ–J›ÙójnæBžFO^á!e_A' !xÄÚ}×§,„c <ÄŠLb#â’ÌÉ,â`ënH…î ÷E uh6Y¿v¸ÄDþzw6ÂJÑDA­»Ží£¤xÅ]™qÈÅ¢a /Á"…<§Ä mj…è‘I;‘¥2g\Ã…’úgaœÿ¯Á5¼½1ϸLéE±Ücø8 ×= ÀZ7 ÎÑÇ´B1–˜ñ„%vêiÌþl‘g15²ô/‰ôÞ¤v›å–_­5I"™E4—(ÚF“Ãq‚FËâÑ µìGÓâ*äÙ!®¹SJ‚Y“}\S/Z‚ñ”}±ôdĶúj Ãh07Ë×ü5ÓÉÑ'¶èú¹xë)EÕf<„5hç ùñ`'…RôG¢q’Þ‘éÔ½jC]Æ'¥Ž–,ˆ†vzÿðã.‡Œ “Ÿ¿Më©©TO8E‰žã6yÄ^5º„›öOë IO÷8‰b”HÎ…a1ñª±(ñ_ H{½Y½g‰ªŒCšc˜B"ððØUJÒ]‹¬gN¼Š3â=‚4`hNB«AXµííe¢["™;®œgh$õ=ÄTòz&Aò5Ñáœê1Nh¿4Ëþ'cŽ^dØxî&ah• e¡“RP2 ÷c±uMR£KÜ*^ß`g€‡Ö"Èá,b&ãÐ0¤¹ªb‹¤âžŽ}DCÐCœ0¨;Ñ`J\‹s ™CÛ]¬˜BXÙ¨5SFÙ높„Jµo€%Š–¨‡—‡¨º¸˜YdÙàçÀ¸S¤à]Y–(ßT¡íI+%#®¨bró•{úB ò±%» Ѿ±õÖPJlÜOºžÓqtRUbÅf*‚‰,,Ô+ÜâÛ© ƹ¬KK )è*Ò÷†«\/ŸÍ´;Ú+K–Ú·ÞKø  ŠáÂg¤þž„5Š^Ö6äZ÷¡~œŽ¥fôïsB·pE1¼Ü­R¸Å*x€Y‘2Dùd-ù4}j‘híž:k‹Èù+ĵ*m7›l”Áó`&O€S -ÑŽ+{m[ D…r0†ÅjZ{ƒ)`ªn.ã×±ÓUqžl¦mªeä€DÑÉÃ}’x½d¶t“3å/=·èÃÇß®ÄF6(ý„S »Q¹ZïL\Ô) º{ÞrG½-Õ¬‚éœ-μcN]Öæ2.ÈÙî«f¡&W“†' U ~Û“UÛÐÒd—ê8ÀŸ [’…/Þ¼ËiûÞKôÊÏèù#°²²$2^’•÷Å’a8Ÿs6­;ïˆÃ!_§ °À{¨o¸í"Õ39Š=}‰•1 Ak‰ÖJ)¸¶ÆFªî$ùo ZyÌ ®M„“3¢Mþ-÷ÒâÙ’%ÐìE2Ä@¶±h¯ºË,Û)b˜°Ó Öù,®gH~“2ª¤Ñ†Á¸W²‡VwÊ69*4ù¨µœàØ®pŽÒ^‹ý¼ -ªÊÇèѨ\¢ÐP.³ç9j£vÁ@Ú¹#ø2F« o Ô}¼eä>f®›TBÛ¥öVÑÑFµS>dßDÊ×gü( 8YêÔ”}·£A=ÁŒ6ÎZnOÎ-Úò¤ÆØó#TÏH«NŽ$ ~å uÉiB „ðRšåÍ;a¸ ™øQ¤fâm¼Îy…jÏǵ]4Ñ”q8±'«vÝd½ 4$“È5üåŒî¡w_„´¶¶Å=ÕlR•,w×Ë? –Îý%¸ò”«l’(±¦Á9^á³ÛÞþ‹ÇÇM˜»öo¢•«ut’QŸ,ýÄ‹çZ“ö‹°ò%où¨ÍhRˆF„GÐÄÃuã5ói…ô¼ƒõ!Íj¥^hþ6Â’XS¨þ:^H2¡m<ºf‘%Oõ–âš{'êK*Û]n#>«R½ÈB×/ªòJãò¤Ðêwòë9b\™*4²„öþªòY/JòÖµ´ jjXKs /Ë…vËøTtœœš&_¡Q^VcžôLŠ”å… ¤àäÒÌòDMJ'`Å¡ç]Ö^«ÖC/—…‹8ÏÁR1—kïð¹hù4CÃÆÞÉ5ÓwöÎU”€Wáëå-•Þ¾3Y›4h{œŽ™õ®|ˆQª†V"RrA¶çžA’¾Bˆ†®4`Êøý¹1š€T"¡òû&´ˆÖÎTåC+µŒ±)Ù´J•*àCÆÈ¥‰³†X֦ʅ ”‰?m! *n£—cé-ß§:²’[åÚk66²xDIÓFêÃþVbú¯Ñ8.)šlú+¢¡úý–(½–ßúý1 iRõÆ šŠãe¢F0þ°¬ ’àe*£ùºs…b_%øf$,îþ]Î¥Å^YH½L&•'„’’ñÈh##7€‚7¡`la=†µ,X)CTîÞêù\“ú±Ñé„è ƒ(Y " ` ˜ÜÈßR¤ø_·)>'œóßú£R1Vœ—°ªè‘Ù(!•YóMõA7îM ‚¶@GnVgDâÇNÚ ‘›}EîÌje"«|Qã:Xþ†•há,Ã/›×Œ¤¸…û ¢í 0ÄóxªÖITc{%¨N–ì—í1?6bà°«nXÂð¸6c=™³ã@`"[¦PHp®FtŸ‰®>&4ǵVG àL9áC)õ#2[+‚ö³ƒq¢M±`D NÊf²(Š¹Ñ£‚­ô¹¤¥âRîØ6QBÞIÍ Tª¢‹vM‘œ`©©(l¤f]ˆÖ\b³l ¦¢Þª˜Û$ìd3(:ťÈ¢' ÂÖíBxÓ-¥Øz Hæö,ïDA¼“VFv+²P/ùÊ—­^:‘mÀ”¾V„6·×ŽFj!ŽE~gR+³‰•ÑPç070ã ‡ÕRFBT”Aà–Bœ³R€ ® ±9YCœ±X †j„ó MòwŒçtô‘×Ǻ`-JÊAE]ªD£5`R¢î3šá‘è#3±i‚t1”£Lˆ©" üCÁ:2úê²µS\fê „F ò¾²äÈNœÜš]Qw%§õd$õЋ™]D„¹dE+Ì=,:”Ã(T%:ì|'jV†¶?ìjg˜RìÈ,ˆÓü¤³0-k³ò¥£/²D®Ærm“2#m@ži–n1Z•»cA°[¢µ·ÛÅ@ä<âslÔÒžgd'4_béþ‰$ÖU\…Hð€À€;µ‰ýºT Ás ¡‘,É`:´õ9aX‘?Ú“Äq ? œ¢®I;Œ­5²hŽ,.y ‡p¿böÓcdNMükª0A5·Ÿ°¨Ô$Ð%éT!ðoyñ$M¾µ+Äz䊥qa¢$f¾ ÇââÆqôÊhÇfÖã>,‹+VøÈðV¿‚ö 'Dúº,øëž=ä!9œ9uû~°[Ì‘UƒiQ’j’®"§mäS/av;∨ó³n±¡bœÍær¡;ôëÌêÊ[¬«¸[ … ž_íMø9$΢Ëp ú9°'4.Œ¢AŠ÷ª4üZÆ]a{pÝwÌvšŒRá\d³Jüily$¢Þĸ(ž}°ªT¹²5%š ı_:ÐéˆR9šðÉ”Úþ¨*$<ÍJÏM)û`F3Øc¸÷ˆŠ‰8À3É`Ò^«¡ª;…‡($’•>b§BšYpJÆuß- ¦5´üÔ&=V9ƒZv£a›5m’H«¨ùv›œû=¢ò±š˜L€ŽC~þ²ÃÀÀE ™º­çML¸¤ùmìèì󭆔*¬(™žjaNú¨Ïâj–G5÷ÊÄô£wÙPŽ1õ™3‰ ÚQ®Œ"œ0L©«×©æ"g*³Ø6É`™Æmâã÷Hoåf‰©A¹"Ȫq¶D$86 vRV[mYÛ ÆÍmJ¬âbl…Xˆ%žê”§T±-žð= ÍR"YnêqfŽ—a¨»?nAq2”‹WÒ>žÿµ‡ÕØÙ!Cú!ù¢e Ù[}^ èƒÛ@ŸE¤àÃø0°Ì NvBPŒD›½Ñª¤n§“*N_e   ¨øLý°ø]z^/C²ïu>šé A͘éP¬Çaðqñg"°Ò=”[ÈÞž¼;‘×56Ù’¤îü€Ïc_£—ÌÛíÝx,^OË…?Š„yè(“Ö•Ÿ×RÌØÊÔh'¦N°Y®Ü¿ká·›èŒ5l:’Ûà ìÛa\TÀÃkÿgÒµÂ{ɲ‡åâƒRõS$¢JûË9¾Î¥þÎSâd1-Žzã Õàùi˜b4œ&l‡,Ju¿õѺìÕ¥dDB§ÉI,-:{™²5G¦1®íùÒ¸²~BÜ’mU…¯°†ŠübNEh¯¿ù¯Â'î"ÅTbX,÷c¤ nn3éãÊ–÷G;<äùq-ÓH¶Á™sÏØô’*pT:¡5ÑÂBb¥a5(ÝÉ×ùC!)rwܑǢÿ}¶Õ L¨=´A{3ê6-¨¹¢c³b†®Ÿ—f7‹åGÌ{I~7FZŽtû¥„ÂñÚâ* w¤iç•ÄNZ+ÙÒâÅ…:e‹šíÍ&Ç$•:l€ã&M6¨à£Nª‘Дáu"Ý&(ðr3»|^(<*I’ÆÇM‹¬¼2ðm³blÿÿHÆ&Dôß²ªi>QR÷5~T„‹ÈÊ›|]K/¹‘ßeÊtH´±ÿðJF¸¼¬…wZ£²×ihÛlHA{E·Z;²~™šoè`UÝï¶;âÀÚý}}›”!R¾Ï¬Ýá¹YƒQ0 ¼|Ly&8 U„´‚ÚDÊTKj ùu@¬O5‹ ‹×Qñà%RŽíOÎYIÌeG)Bá ô.Ÿ+X ÆæHRã"Ñ÷‰Ä8ÈdK# Lm­y#ómª°ÄK‑!Ñ%jÆ èF3–…·>Æ`'b£¥{@»UªÃ"n“Ëë ª5‡uAÍ¡d4]ÈÝŠ×H µ[£v‹òßCiK=®_q+%B+ÎìPÌJ²äq½£â…Ž ÓærPÒömN²=" ÀpV ]!Ç%É9~¹ø™ÁSÓSÞ;à>ˆ8ä¼÷’’µ¨9?eëÍüìÍ7¤‘@„'.)¨Í‡BJÚx#à¨> Æ„e$*5,Qï9ûñ ¥ÄxÍb JjjæŽØ'¹)ùe1ú", žÈT{5Ñ8„ìÒóÛËcÈÔ^¹€H6õÙÍyöÍèá Q÷pb蹋͂R‚Õ >:Hbüf0µ&g ®§ãàN#v—5|Uœ/p"VоóÀVpwûwÓôÑ4£Ò6%\R@79zÒ§áAÉ[KÞaQÚn×öDè‰;o GÃÆ¬ Ì~)um› œ‘â®ЄÙÉäIÉr@C¡˜,"ž\Qm ®ãv_¡y¬ªÝ,5IV€ø+•lîHáÕ â'‡• úëÿøYûÛû± XÁ²J™µ%Jš^>  XH´½¿$DÒÐX¯)í3©òtB ÌsQ›ëó’æ¿zªPˆÄ¬á„àĤ:YdêŠL"ŠB´„øø„ºBDì•¿G!€ó.å,ïÊÈý¡ZDžç¬4‚S ‡­‚à ¨!+²—rÒ,W‚Ôb€µ)RŒŽ.¢î7¦,6È6-^Sâ9Œ¬´+£›cPZãT l7úÞ¢ÆYÅß©;ºx…ÎÇн °ýº²¯kéýMñÝ ˆ¬E^³m:\ˆKùi)‚} ÉH¹Ø¶Ðæ’Ç~'J©Ô”BC¡pÒRÊ(¥GI1)gºøxüÇa9¢3ÕF¡²èXí .n½^,0nÌFîÉ\±½. cI(»pŠÖ˜HJ€Åج*ïmWëbI¶Ä³Qdbñx…pêzH‚ðÃætÆ6âbô'n]–އ³½;tLj0•ØLÌà<8`1 ƒNt“jš´¤—SiàÉ9Øê²ºÏ1:ftÕð/Å…MÒh¤)^ÿ9$dTD@U0™»æÞ/ç†ù)„õÇÞ—ÄfÏÊa¯xàÝ/ß¶-™³VÅŸêM Ø‘ÙHÅ2ü0bu/…üâxw"Jq%«ýÖ |æÍZ7–gÏ@ˆ@xí©&ÛÆ½2X~côÈÔv E>d³0R3<)µ-\È„(¡¡/È¢ˆhŸù{¡gB¾º5bü‰HÀô€$wh¡m×)ÑÁŠWÖ¡vàü±ƒ¨N gºYòµhÉÝfü¸-*X¦hüÒ4E7/I˜³Ñ½aBÞyÅ¿iн^aRRÃÁøaô$$”4hEzø±XÄ”û²ú!Tì™(ïÕRzMxLL!eõ²m§FA‹mÃR X@f‰‘þcUN1Pø–ÎØî‹a˜M9ƒøÉöNü§u5““&~Ææ¿ñ±¤Ä…¶äº FMìtþðã!É`0Ó6eþòšÖBgA®$†°éÇh lC+3ÞU¡’É_¿UÃj-M)¬Î³aáÞ%peyâÇüO9v%r> @Éa+èÕ;¥©àÆíwCTˆ¯˜A*{‡AaØ£ö/nÀB¸) Ó¸‹ž— €TÊ•œ¬cÊ“…dm%0hfÔB@bBê„T#~¥ÑÆç†7eÀZ&ľÄmb^ÌßÙÌi•=*´éFWýòôgç9S¦ázãõ _F :J™ËxÙÏj®‘,m]ž°9tc±Z‘/?࣯…MEþqéYgæFQ˜¥l!g–Жëû!-Ys°”Yw¨r†w׉*vÓô݉Ŏ÷ÜJS!=äæLËÞ Ü. ¡6,‰»(Àw˜)H#Y5­é ´Š5«GÀJÿôHˆÝ˜= 3Y«ù¶;ŸöTò*ZÌØ÷§ˆDÅÏ¥¹Nå6 ÕXZ@Þô­›Í¹‚!tä.c‡½šœ‰ljo¥{”(plŸ3–txT£ÆJS—‚~APgd, öCZd¯]²éñáÑ#“Ô<¬ÝÛb*)ŒäC %#Fƒ¥•—ÇY ŸvXF’U‹ÂŠ Ì¿WåÏ·ËÓâÖ–Û†X!›V©izô°Ÿ…¤Nµ"fÊ»',N®»\¹zÒ¿Š™¦¯æ©Ö¯$ŠŒIØ€QIÒ‹õ«Ôàgwqܱ¨Yü. Ä›j¨À¤£s )*–W‹+t¶õbpôD³øÝ#Ä Ú=.ãRµq9[ÂGÐpâ°&@å¾`Û-OÚŠœ—ˆ9<·kA©J¬F&|†mÙ 3ÊfXà—SÏMLžŠ†<Žwˆ¬0^€¨vé×´‡L ('LB Z"Þt)º“—iIˆª‹òDzW«L¤=hIìámL÷?jÃúµ`f\Ùʸ`0\Í¿ŽàÉ)ábþïÅA Á’Éx¡îAh‚ÖœÆçlá'B{;oÈP+4/ñÙ‚8…RuýŠÔ‹ *=$+ G „»ƒÞéWC nK®+ªF…À–7…|u|J.ÖaF/z%áks]„¬æIÕ䯾 mõ<„CVs uó{Ò­•ÿëGÅ'WÃøL%\.. 2[%d1™¥Óµ;ø¨à_yÀ'ö7¬!séÑjlZŒ3 éÅõ+CkÄ¥'ŸVIL?kI:jW•¦tH¯ E¸ÑŠnÞ-G¸ÅP䥖¿5ƒd%Œ\”¬PÆM(6Q,[FnX•vN¸Ìkº5;é±vŽaCͦ×r&͸€´²ô¥ˆÌ¢Æ¢tÁ¨ù|%ÅÛ;Õâ€!“àˆÿDsá—Ȫ©¥cy4ʪ?ÿFT fèßG,žŠ€ˆnPމŒ¢E†¨\>Ú”ø[ÓÂ]†0á!ô"oÔoü‡ê„îGDk'¢ÑZêdS¤íðxºøj˜s`Γ'áÐ ŸÇŸ ­p Îk¡FÁ,ëwšÒ§ ˜p…ÒƒÔN²öÂÀÜhwÌ7¨bD‘_ÆñW6r°7N¡1f*W¸Ι‹B±½ò¾2, Hµ‹2ê’Ê ù*ó‚7–§@§’WÁ²kŠkp®‘ BTÄø';T¼)¦í ¡ÄŠøBÄæŒ5 S¥D¼™+“<ðÈ#n‰ð$=\ä(ãB`ûi¢*œÍÀYÀ«@Žî”C ÓrdÀ€%÷fP^…|jñJ·”˜¼Ekž7A˜q˜TÜ0Ž?#~Á7"©ÏãgK²ã:(îÞÿ/hRmÈ]ywÑ.H>Ö—³€ö«!ßæ%¥VÎTB¾DE)KOТV*yÂË?L`MÞìŒ%0rè\ZóÒjƒz![iÌM£G¨HúÖ¨EMÔÕ[ºLñ*À¦Áfr¥ðÉn T+ž= _7¶Ç#~ŠâD_«‹ö^ŠÑQ ¶7YcUWètJpdÍ£ð8Gã¶9®5†c.&mŠANDŽnâ̰†¢ŽIgÑ[ì[¤d-˜š7nY’‚ G©ƒS¾Ì”Ôm³S Çœ{„|-DC­³Ï ä N”DZÜGæD\Ò¤Ú’Èí0‹´]P¹²ü+=jF'_pvE®&XÔfc9<#©·ÿ¹fÆ1BcË`x3ë2RD¤‡†¾aOÚéCï9r^RN{À¤"n†sV&§UöCY™˜Qj_^Ð#ôbTÖ¡¼¸aþù\Š“ åqásJàh¤Y— åäœ,-†5« à¾ê²:õZİŸ)f ҼΆ(«%FЪۇ(—Î hv#Ýðf±© •Fc\¦)xMd®A0n0W<…ÊŽ:ÌHkY&™0xN>Ž7éÿ÷:·/W].ò#;ÆÕõ\'í$˜|¨©>º,‘þ¸S ¹¿n ?Q ÷ܨ;kÇâÄ7Š\)Pƒo#°ä@TbHDJ¡ÓÑ$H$•¯R$Ø­#‚¹f"Ž=J`KHŒ·1×&¯ÐfT"N&¤pÄZƒ@ÕׄN–¼w‰ÝþØ¡³„ËÆ¼ÙV—<-D#•˜¨S±„!ȶ;Kz…oÅn.M‘š ÉÜ"•P–T€¬XZ¸Z"æKÎеÆ"cí;Oüô™Ý÷±BzCÐ5°Á©|/ ’aEok ’—zv’!¡'zæ®a-"›i|poê˜-–¡[1YB½ì¥*BKž¥¡AH©˜É!¡ECcÑ!í @š­æ3Ð?çÚU£ˆÕê¢;÷Z¼ð¨b ¦¦Ö5!¹» Ã#>ÌáÅâ¥á"`™=°ÊG(éä ¬ùŽeèÍÔ‹†< 0Í߇§c«Ó§Àbw[1çèØir übÚ¦fs9€9>ld!:'ɺmi}­gI_Sš= ܂öÊâ*ê±fða Eü7µñ ÆjgKäsX¥Ç1‡B2ê^èÔÖ˜p˜ ̉ˆzÀ*yu+°Ï4ŽÔ}~FZ– pùç?/Зªü‚Ä့x¦ÍøÈ_dh[O5hŒ6:mY÷”îä‘´¾.~Âr|Ê®ÆÄtC|³+2éV¶¡Á¼ î“¥F|©,fò\ËÌB#zÎlè7 ›äüðÊ#Dàð$Ê›ž½qjDF±5÷{Õ»JÄ‘l‡èåXÚ†Ö üGy’7)q,)e¹nB#TÙŠ„ŠôsØt¸ÏßLD¤Df!`˜ ùwä#ât‘Åžv­ð”}‘†¥T3à@ÖëâX•p¯äÁ1ipfgWȵIèG©oZl”ºâ/£q¦ù‰ÆŽÂ@¤:!åBÌ_Wf„¾¢ò¼žWò õ!#t©Óž(p4/HEïü–Õ¤é Öb ²½Tz•$Ne…&c@à¯ÅÒèT/1+4^sláËIDˆ³£åH3ZdDux/hf/Å›…Å2â± ›š7¡PõgQ…E%D L".+d±ȉÏMÿ¯2ëh§hbà¨)*­\–Ê×çB˜T /c4lp°¡Cµ0J¢“‡HÓ†€7m<‘šD†·Æe0'ÔÕôQù9šªg‹–2!)»¦dAÈ¡y±mç°U‹¦on$'?mŽd –5\ÅêS84½·ƒ†/í»9…ê rÊ3!é¹IIB*“=ö¥[)pè!?—¬ ±Ý¡øˆô*èúÍÏ–LHÄ23 Ä\+ˆÂôÒ¿W*#IÁ)°×c·…ÙÞ3›ì¦½j¢þñ­Ì[“WQ^3IúdA?‡*=XBP±Ç¬ %ñA‹=•'‰÷_ËwÅ|‡Ög4džªÎ×9Ii¦k³ÀàØàChDhuöµ¢–´$òâ$Èu‚m°n/xNª"^$+€JB¶-‚Ðú´ÆCWå“k­Î5&éÖ9eo"`w•®Æt=-@¾Âs¡ÀÈšÕž'©451lS_³'4É‚$J²C,5&«q‚¥¢×L êÚtÜŽiÔµçÁ»åæ. ,j®!DÍâZWêe³²b"QRqAHºbuEà\#ZWb@ßûq¼.´õfŽÔv‰ÁzïûWAƒ FÎU D¼U÷;ª§DN –ã®cÆá¦Mç¡ñ­BS^â5‰íëæõ™*F\vÑ‘~e±zšâ­ж%(·öé‹11…É»ŽPÿ|CB÷*~2"@®jI]¥Q:©C˜3Y#Âb¡D¾Ú«¼¸ö‰Mzø³*¬*üù˜‘=¿”ˆçþcïKÛ!³s½SBv'Qæ$È=„ðF‰á‰ÈÐCé¹ô(tJXNopV9ÊRd©1–§0ÚØžo¨ð–vP ¬ lRü´R—lJ»|àÑS»‘7'œÿ@s[ã@E¯‹…ÿøy Æ…Ù M™Ô7)ýýTdóH |L‹Nš2Ï'ó¤+¥µüFÕðgh ½)@"û !4@ºÆ"28n¿=ËÑ‹ÊX"+ÈTeج2½¬@å7èèB¡)Ñ4p|•§I„VàË•±­? Ç šú¯ÔjÑä‰eÚŠWc¾ƒ½¸àØýµiE„±°÷,(vtˆ=dš/ކ%)šŸ+hd´ *ëF” ^íí¦µkaP Ô¨µh‘Xü\˜ˆŠ£¶ó¨ÄºÛG ê‹9Æž“ÿûnKa?aQ/Ÿb£L¾VÁG‹?r±A,‰ÊK½´jÒÈbʬÖåá·° 9”^ÄÞ&’Š9Y1y&÷ÜY'RZýíQ\§^‰ž /ò:+!=ÓE¬ãjz3N ¼%ÿPD¹!4‡%”É:vJe-ºï<­—¹ÙÂKzêè‡(õ5•%w@'¤%mò½4n˜R™;ÊAj‚T&2¬ÎE ³&*Jèx¼òÁ«»°z—ÿøÚ˜ø1=°èøÄ¹mml!Ćˆ”´®ÐÄŸ-d®·®šOùBñÝûUÛ:yZ«tl‰HÅiÞ “É“º<µ'ë¢õöQJ2ê=بô¾VÃõÔ½2ÁçŽÛMî|ûú<$®Õº‚ e W»(I›•BpDˆ¦7—tÑH.œóƒA›b1YÞ>êÒ­§ÅÁ\‹—^¬¬àWÒRw”w„IQã×éæÔâ¿‚ð‚ü•”¬…Ȇ˄t0Ueº)9I9ä_ôž¸Spº¥3Ä,‰ªëEsâUéÒÜF¥Ü e“mct€ÿ9}Œª!«Z\4U²e· w̦}jE+–@ö8KO‹º—•ú×%Åi°èP½áœœ°`³ÚÒŒ6Bi×-×êLtäBV²[#å±vŽrI†kDíîfJ'á²Ç „*Êe¸C.B+‰Ì¥DmÁ˜p´-Ò#_êz[µOÎÃqD:0!©€æ[sMbú%fNÌ”ºýç‹u¯……8EØÙÇ(0°VŒ.ˆH&Ô<Ôù ñ!ÐåE,5*Ëæ¡I›SbÖ^{¬K²·t‡§ ×HÑz¸úñ¨ hQWìÉy{káyʺ~Ùbbm1°"$=_‰*Ñ1i2d/nû˜Œ‚…†ÌˆÇû›ÏI™ÓÃ}cܽÈí ›Q¨P7o© ©µhø¨ý߆eÐha±ú.7-XÅî\8†tž9:‹6˜8h‡õŒesóxˆnwù0¼Òï0tAÕñî°Ù"2Ztë|#6}#‘}·ÅÀµ\1 X4IBQ(ðvÍ÷]l3Qål5*jÊTÅmñðÀC1pÌÈI¡rеÙ3ååC}À€Œ5!­ê$:à'bzŒ«çÅŒ†W"L…O¼Ð&-»¼w3™A ˜$ÂE|Ç *³äÜHN‚(F "íûÓrZÂ\TMS”O®VµÁÝJ]ÈO ¶T»¶Ò‚ñUi*wæUgóhibƒ ×(ìòôdŸ—Ÿ–Ó \’c‘q)ÑhQgdð”/EVŒ’¬d–¯ì(~ —­K©àºzÛ”ÖÙ£:‰Lߟ’ì=a’QHxÜuAºk‡ ‰Rd}­:¨¼nq¹RÄϳuÔžc™1ذ+¨ªŽ–Ù˜ÙÞÄ6¦ûŸ-àZæYÀ%óÍK¨j0O›b;í?þbñ1A9âÂ,ȲQk²a ûž!X“¡Ô{ºƒVFëWÌ&/lÀ9|A_«¬º)ñbÞŒæªXòÄD?ö•5ïËÏS°“a fH=S2hEÁÑ,£0p@jÁ p@)Oì²ÄÔjÇÐÁ-Æå¾ÃY#S–¡‚ÿé1Wv(ŠÃ«x j¦®½9vwþ#3*¥l$ƒ],-ÛÙrb¯Cv å"ÄOÆÂ ß )^€ªFÎEwÐCTeµåHY0ĸ¹‰ôÂ<ÍBzˆKž`Ã¥˜±k—aXL^ü¡Ý :j<º ÕY,ÈÔ,–7Àz$½Á›¥JܪÌîQoÍSv3™‘S¨Åcdép,?Éï#ÎK»SøV« qΛ;î¯^I Zùd©šµO©óÂ$u¶ÿo{*EN嫚E¥É ÇW¸”‚s£úW%Ì¡rSôS²õÊ•ì¡"†OÓ·nù6òú©[Ó²l3UÙ³b€tÿ&5d–dFj€Ô°—t¥"±~:!2"_“6zÓv0[û—¶ðè¬/:ròe¸÷%RÞZ@F&"6]<ìz?% LK)€á½ŠïåÕ3¶4ØœDVâÏȰc€í‘ºùו-f"Ê6›Aƒ‘m„$­^Ä`€C…0×AZ£ðÃb«¶7nE®l¼·ø3ÊÙôXu€©ÐBl#O!¿5 Ñ fn}è*SŸÄ@ÔÛ‘:e¼r±Hh[óA&nÙ𤳹Zó·]bFŠR7&(;§eÉñ’Cµ„IúHm]ÿ­ŒNÁƒ"˜—¥$^<ÍŒ“¨ 1 Qª7i3 -F¥.Î i Êñ “‡¶ÎCŽÕTñ®2M¨§¤_è%ñ,öÀ‡)TÞŒbNxŒ ŒÕJ‡¤È rjlƒý2Ï¢þ·&/jà¡´Wp¡ ÑÀèb¯„âb¡ˆ é h Ó2ßRTÚÎ_§,eïW%ŠGR÷ÆøÇQñw>çÆøÇQñw?ð?ð?ð?ð=×°=Ñð=ÍÐ=Éð=Æ =ÃÀ=Â`=ÂÀ=ÁÀ=ÃÐ=Æ€=É=Ï@=Ѱ=ØÐ=Þ =è =ïð=ô=ø =ú=û=ù0=÷=ù@=ùp=ûÐ=þ>0=ÿÐ=ÿ°=ýP=ùP=÷=ó0=ð`=ëp=æð=à0=Ó`=Æà=¹ð=§€=”@=ƒ0=b@=C@=(À=à<õ@<Õ@<»À<˜à=D`=O=V€=U =XÀ=] =_@=`à=_@=Z=V`=V=Tà=Mà=K@=E`==@=2`=(À= ==€=à=à=€= €=à<õ@<ÚÀ<Å€<²À<­€<³<¿@<Ù€<ùÀ= =`=(@=6 =A =K`=XÀ=` =n=y=ƒ`=‰`=@=“`=– =— =–€=™@=–À=–`=˜=˜=—Ð=”=‘=Œ =„€=w€=g=Y@=I=5 =%à=@=@<è@<À<µ<Ÿ€<<‡@<„€<‰À<Ž@<›<µ@<΀<ãÀ<ò==€=/à=H€=j€=†=’0= =®=ºÐ=Ép=ÖÀ=â =ï0=ù>ˆ>À>> > X> >X>@>À>È> >(> > Ø> x>(>À>˜>À> È>ø>p>p>>È> >à> >0>à>`>>>À>(>˜>>`>>H>P>>P>¸>>ˆ>ð>Ø>Ø> p> >H>H>(>¨>$ø>)>,>/P>2>4à>7>:8>=>?P>@P>Bà>Cè>D€>F˜>Hˆ>K0>L€>N >Q0>R>RH>Qp>O¸>I@>E(>C>B˜>CØ>D¸>G0>Ix>J0>L >O>P0>Rˆ>R˜>RÐ>Rð>R˜>R>Q8>Qˆ>Lè>F>Bˆ>=Ø>9Ð>6 >5`>4 >5x>2>.ø>)à>&€>#Ø> H>À>È>`>Ð>>> ¸> X> > > X> > >Ð>P>>Ð>à>0>Ø>>ˆ>ˆ>°> >(>>¸> ¨> X>`>(>H>€> > P>p>X>> >x>è>À> >ø>!€>">$x>$@>$Ð>#¨>"Ð>! >0>0>ˆ>€>Ð>@>p>`>À> €> >@=õ@=æ°=Ûp=Ð =Æ=¼€=¶p=°ð=© = °=˜`=‘À=ŠP=†=‚p=~à=| =q =hÀ=bà=XÀ=Oà=G@=Aà=8à=9@=> =Fà=Rà=_@=jÀ=sà={ =€=ƒp=ƒ =Ð=„0=‡=ŒÀ=“°=˜à=š =›Ð=›p=˜p=•P=Ð=‹0=ˆÀ=…P=ƒÐ=‚`=…`=ƒð=€Ð=w@=c =Z=Qà=E@=8À=+= == <éÀ<Ç@<¡@ؾ<ð¾;X¾8о7ð¾78¾6€¾6¸¾8x¾8˜¾;¾;P¾<8¾>ˆ¾?ð¾CȾHx¾M¸¾R ¾Xè¾^@¾b¨¾fH¾iˆ¾k`¾n8¾q˜¾sÀ¾w@¾xð¾{¾|(¾|Ⱦ|@¾| ¾}ˆ¾~P¾(¾€\¾€p¾€ð¾€h¾€<¾€¾H¾}˜¾{ ¾yp¾vø¾tX¾q¨¾pp¾p¨¾nȾl¾iP¾gh¾dà¾d`¾cè¾cP¾cX¾d@¾eð¾gÀ¾i€¾j@¾jø¾l¾k¸¾l€¾mȾnP¾n¨¾nÀ¾o¾o¾n(¾mh¾o¾q@¾t@¾x°¾}ð¾Ø¾„4¾†°¾ˆ¾‰$¾‰t¾‰h¾ˆ„¾‡d¾†<¾…ˆ¾… ¾„¾„h¾ƒø¾ƒH¾ƒ¾‚|¾<¾€´¾€¤¾ ¾‚ ¾‚ྃ ¾„`¾„¼¾„P¾ƒÀ¾ƒ@¾‚4¾d¾¾¾¾€<¾~@¾{¨¾y(¾wp¾t€¾q¾m¾jp¾h¾gÀ¾gH¾f¸¾g0¾h`¾i€¾k ¾n(¾q°¾t(¾x¾}¾ ¾„T¾‡Ô¾‹0¾ŽØ¾’t¾–¾š\¾žä¾¢ô¾§4¾ªü¾­È¾°¾²¸¾´ ¾µÜ¾·Ä¾¹p¾ºô¾¼À¾¾T¾¿´¾À<¾À¾Àp¾Àœ¾Á”¾Â`¾Âè¾Ã¾Ãð¾Äø¾Ä„¾Ã„¾ÂؾÁh¾¿ ¾¼8¾¹¾¶œ¾´¾±È¾¯ø¾®(¾¬ ¾©ð¾§„¾¦T¾¥T¾ Ä¾œ´¾™ô¾—|¾”¼¾“¾“0¾’¾‘¼¾‘°¾‘,¾‘X¾’Œ¾“¼¾•ľ˜ ¾™Ô¾œ¾ž|¾ ˆ¾¢¾£h¾¤¼¾¥„¾¦¾¦ü¾§Ð¾§Ü¾§Ô¾§„¾¦ˆ¾¥h¾£ä¾¢ü¾¢4¾¡¼¾¢0¾¢`¾£X¾¤¾¤p¾¤È¾¥ ¾¦0¾¦h¾¦„¾¦œ¾¦L¾¥ô¾¥¾¥P¾¤Ì¾¤d¾¤Ü¾¥$¾¥¾¥¾¥¾¤ˆ¾£°¾¤$¾¤Ô¾¥P¾¦,¾¦è¾¨€¾ªL¾¬<¾­¼¾¯d¾°„¾±¤¾²T¾³ˆ¾´,¾µh¾µ°¾¶Ä¾¸T¾¸È¾¹8¾¹D¾¸T¾·|¾µh¾´$¾³¾²ä¾²œ¾³,¾´L¾µÐ¾·L¾¹¾»L¾¼ü¾¾Ô¾Àˆ¾ÂX¾Å ¾Ç0¾Èä¾Ê$¾Ë´¾Í¾ÎÀ¾Ïì¾Ð¾Ñ¨¾ÒD¾Ò¾ÒŒ¾ÒL¾Ò`¾Ò¾Ò¤¾Ó˜¾Ô|¾Õо×@¾Ù ¾Û¾ÜؾÞl¾ß„¾àT¾à¨¾à¼¾àؾàì¾á¾át¾áD¾àX¾ßÀ¾Þ¬¾Þ¾Ýh¾Û¸¾Û$¾ÙܾÙ¾Øh¾Øl¾Ø¼¾ØÄ¾Øì¾ØÈ¾Ø”¾×¤¾×\¾× ¾Öl¾ÖX¾Õ¸¾Õè¾Õ¤¾Ö@¾Öü¾Ø`¾Ù¸¾ÚܾÜ$¾Ýx¾Þh¾ßL¾ßȾßܾàD¾ßH¾Þl¾Ý0¾Û¬¾Ú ¾Ø ¾ÖÌ¾Õø¾Ô”¾Ó´¾Ó0¾Ò¸¾Ñô¾Ñ4¾Ñh¾Ðì¾Ðä¾Ñt¾Ñ€¾Ñ¾Ð`¾ÐX¾Ð¾Ïø¾Ï¤¾Ð¾Ð\¾Ðd¾Ðô¾Ò¾Ò ¾Ñì¾ÑX¾Ð¾Ð$¾Ïð¾Ï¤¾ÏD¾Î|¾Í¾Ë4¾ÉоÇоÅà¾Ã̾ ¾À„¾¿0¾¾¾½Ä¾½ ¾¼ˆ¾»4¾º,¾¹x¾·°¾µÈ¾´D¾²t¾°¬¾°¾®´¾­„¾¬¾«¸¾¬¾¬@¾¬¾¬°¾­h¾® ¾¯L¾°,¾±ô¾²ø¾³¸¾´h¾´\¾³´¾³,¾²¾±D¾°Œ¾¯Ø¾¯`¾¯L¾¯°¾°|¾±\¾²Œ¾³Ì¾´`¾µp¾µÄ¾¶ ¾¸ ¾¹°¾ºð¾¼|¾¾l¾À¾ÁŒ¾ÃH¾Ä|¾Æ¾Çü¾Éä¾Ê€¾Ë¾ÌŒ¾Íœ¾Ï$¾Ï¼¾Ñ ¾ÑÔ¾ÒH¾Ò¾Ò¾ÒоÓ,¾Ô¾Ô¤¾ÔľÔT¾Ó¸¾Ò̾Ò¾Ñè¾ÑD¾Ðô¾Ñ€¾Ñ„¾Ñà¾Ó8¾ÔP¾Õ€¾×¾ØØ¾ÚT¾Ûì¾Ýl¾Þоà(¾á¾á€¾áÀ¾á ¾áоáH¾àl¾ß0¾Ý¬¾Ü¾Úd¾Øx¾×¨¾Ö¾ÓؾÑð¾ÐT¾ÎD¾Ì@¾Ê|¾É<¾ÈL¾Ç¤¾Ç|¾Çì¾Éؾˀ¾Ì ¾Í8¾Ïl¾Ñ<¾Òä¾Óؾվל¾Út¾Ý¾Þ¤¾ßt¾ßľß0¾Þà¾ß¾ß¾Þ ¾Þ(¾ÝľÜì¾Üü¾Üø¾Ý¾ÝÈ¾Þ ¾Ýü¾Ýä¾Þä¾àp¾á(¾â¨¾ã,¾âì¾ã<¾ãl¾ã„¾ã ¾âl¾áp¾à@¾ß0¾Þ¾Þ4¾Þœ¾ß ¾à@¾á<¾â̾å¾çT¾éH¾ë ¾ít¾î¼¾ð€¾ñ¼¾òD¾òL¾ò¾ñؾñh¾ñ4¾ñŒ¾ñ€¾ñ¨¾ò„¾ò¬¾óP¾ôl¾ô ¾õ¾õœ¾öd¾ö˜¾ö¬¾ö\¾õ¾ôà¾ól¾ñ¾ð8¾ïL¾î¾íH¾ì@¾ê̾ê$¾çà¾åä¾ãè¾áì¾à¤¾ßx¾Þ€¾Ýè¾Ý„¾Ý ¾Üì¾Ü¾Û°¾Úð¾ÚT¾ÙоÙX¾ØÀ¾ØL¾Ø¾Øt¾Ù´¾Û¾Ü¤¾Ý¾Þh¾Þ´¾Þô¾ßȾàÔ¾á4¾áH¾á¾à4¾ßÀ¾ßp¾ßˆ¾ß`¾à¾àè¾â¤¾å4¾ç¨¾êľíd¾ïà¾ñоò˜¾òð¾óÀ¾ô¾óø¾óÀ¾ót¾òì¾ò ¾ò ¾ðX¾îd¾ìL¾é¬¾æð¾å,¾ã ¾á`¾àh¾ß¾ÝŒ¾Û$¾Ø ¾Ö¾ÒܾÏð¾Ít¾ËT¾ÊD¾É¼¾ÉL¾È¬¾ÈL¾Ç”¾Æ¼¾Æ ¾Åà¾Æ°¾Ç̾Èð¾Ê4¾Ì|¾Î0¾Ðè¾Óô¾Ö¾Ød¾Û0¾Ý\¾ß4¾á¾ã,¾ä€¾æ¾çľçð¾è¸¾èè¾èü¾é8¾é4¾éd¾é̾é4¾é¾èT¾æ\¾ä¾á¨¾Þ´¾Û€¾Øà¾ÖD¾Ó¼¾Ñ¾Î@¾ËȾɀ¾Çœ¾ÅÀ¾Ã¨¾Ât¾Á°¾Àè¾À4¾¿ ¾¾Ä¾½t¾¼ì¾¼`¾»Ø¾»ü¾¼¾¼ì¾¾@¾¿ ¾À$¾À¨¾Á4¾Áä¾Â$¾Âp¾ÂÔ¾Âl¾Â@¾Áœ¾ÀоÀȾ¿d¾¾ ¾¼˜¾»À¾ºl¾¹H¾¸„¾·Œ¾·D¾·0¾·H¾·¾¸¾·œ¾·X¾µô¾´8¾±ü¾¯œ¾­Œ¾ª”¾§¨¾¤¾¡Ü¾Ÿ ¾œ¾™Ð¾—Ⱦ–¾”̾”¾’¼¾’ ¾‘¾À¾ä¾Žœ¾œ¾‹¤¾Š°¾¾Œ”¾‰È¾‡ø¾†,¾ƒ ¾(¾{P¾wؾt0¾oÀ¾lȾið¾i°¾kоih¾lˆ¾o(¾p¾q¸¾rؾq`¾r8¾o ¾gоe¾eH¾dø¾d¸¾d€¾bð¾`H¾]ð¾[8¾Xx¾U€¾T¾R(¾PP¾N¾LؾIؾG ¾EX¾Bè¾Aˆ¾?¾?p¾=è¾? ¾@ø¾B8¾Cp¾E0¾E¾DȾA€¾?p¾<0¾90¾5¸¾1ð¾.`¾+H¾(à¾&¸¾%˜¾%P¾#¨¾#¨¾#0¾"ؾ# ¾%@¾&X¾(ˆ¾+Ⱦ/(¾1 ¾4H¾7À¾9 ¾;¾= ¾>¾?¾@€¾AÀ¾BȾD¨¾F ¾GȾI¾IоJ¨¾J`¾IP¾H°¾Fˆ¾D¾@ð¾>¾;˜¾9¨¾:À¾98¾6 ¾5`¾2ð¾1¾0à¾10¾1à¾3ˆ¾5¾6À¾98¾<¾A¸¾Hð¾Np¾Rð¾Th¾Vˆ¾W˜¾Yð¾[°¾\è¾Z`¾X˜¾Wà¾W0¾X`¾Wp¾Y¨¾Zx¾Z ¾V0¾S ¾Q¾N¾NȾKÀ¾I°¾E˜¾?ø¾>(¾>h¾A¾>¾<¾9ؾ4Ⱦ3è¾2˜¾20¾3¾5¾6¾8ˆ¾;(¾>¸¾A ¾F¾Iø¾O¾Rð¾VX¾Y¾\¾]ø¾c0¾gˆ¾k ¾p€¾u@¾y¾}°¾€D¾°¾ƒ@¾‚ð¾ƒX¾ƒ¾‚¾‚$¾¤¾€h¾€l¾H¾| ¾zˆ¾vP¾r0¾q@¾m°¾i ¾f¨¾b¸¾`¸¾^p¾\@¾Z€¾Y¾Vè¾T€¾QÀ¾P¸¾N ¾JоH`¾F ¾E˜¾E€¾Fx¾H¾Hp¾J ¾Lx¾K°¾I ¾Gà¾G˜¾FоD8¾Cð¾C¾Bh¾A ¾Ap¾BP¾Bh¾C¾A¾>ؾ;¾8H¾4¾.о*P¾%€¾ ð¾!`¾"¾¾¾о¸¾ð¾x¾X¾ è¾ P¾ 8¾¾À½û ½óà½íн耽⠽Ûà½ÖнÒ`½Í½Ê°½Çp½Å€½Â`½Â½Àн½0½¹°½´½±P½®Ð½ª½¨€½§°½¦ ½¢½ À½Ð½šð½›0½—À½—@½”0½‘€½½Œp½…À½{€½jà½Z€½P ½J@½J ½G@½I@½D ½Cà½BÀ½D`½HÀ½Là½Pà½UÀ½Zà½_ ½e€½fà½gà½k½h½h½g½gÀ½gà½i€½j½fÀ½^ ½V ½JÀ½AÀ½7 ½*`½À½ €¼ú@¼ä¼Ê€¼À€¼³@¼²¼°@¼³€¼°¼¶¼¹¼³À¼»€¼¿@¼É€¼ÕÀ¼Ø€¼æ€¼ê¼ì€¼Ù€¼¼À¼¨@¼–À¼Š€¼u¼P¼;¼/€¼,¼€¼»¹»8¸;2;t;•;„;§;¼;ø< <3€À=I@=O€=Wà=]€=`=c`=k =r@=w`=€=ˆà=‘0=•à=@=¢p=¤à=§ =¨p=¦@=¢P=Ÿ =œð=šð=šp=™`=™=—Ð=™ =›à=@=¢`=©Ð=±À=ºà=Äp=Î@=Ö°=ÞP=å=ç =éà=í`=ï=í =ì°=êP=ç =á`=Ý=ÛÐ=Ö@=ÑP=Êð=Ç= =À`=Á0=€=Äp=Æ=Ê=Êp=Ð@=Ô=Øp=Ý`=á€=å°=ì =ï=ó@=ö =÷=ö0=öP=ôÐ=ô0=ñ@=ñP=í =é€=ã@=Øð=Р=Íð=È =à=¾Ð=» =¹ =¶0=· =¹P=º=¼ =» =»@=½@=¼@=¾ =À@=¾=½=º@=¶ð=²=­P=¦ =–@=Ž=€=‘=Ž=Žà=‘à=P=¦p=©`=ª°=­0=²=°Ð=²=±°=³ =´=µ`=¶@=µ°=°ð=¯=®À=­=® =¯€=´€=¹à=½à=À =¿=¼ð=¹=·=´=²@=±À=µ`=·=¹P=¸Ð=º=¼ð=½€=¿=Åp=ÉP=Í`=Ѐ=ÕÀ=×=Ù@=Ý@=ÜÀ=Û=ÚP=ØP=Ø=Ùp=Úð=Úð=Úà=Ú°=Û0=ÛP=Ü=Ü€=Ü`=Û`=×À=Öp=Ñ =̰=Åð=¿=¹ =±P=¨0=Ÿà=™`=’=à=Œp=‰€=„ =€=}=x=o =o`=k =fÀ=l`=n=o=nà=n=l =n`=n€=iÀ=cÀ=U`=A =7 =(@=`=à=À=@=`= =`==`=@=à=À=`=="=*@=0À=8À=E=TÀ=f€=và=†`=ŒP=0=€=‘=’Ð=”0=•Ð=–Ð=–=”=• =’`=à=ŒP=‡0=ƒ0=~À=w`=q =i =a =Y`=K€=>À=0`=" == `=`<õ@<â€<à€<áÀ<ßÀ<æ€<õÀ= = À=À=@="`=&€=*à=/ =2€=1`=, =-€=,à=&à="`='@=* =0=3 =>€=G€=L`=FÀ=Jà=Gà=@€=4 =+`= <þÀ<ñÀ<Ï@<¦<;"¼K¼£À¼ç€½ ½)à½9@½L`½Z@½k ½Z`½IÀ½O`½V½cÀ½p`½~À½‰à½’P½›P½¦à½¯½¹ ½Á ½Èà½Î ½Ó½Ù½ß ½ç€½é`½é ½è½ä€½àP½Úp½Ò ½Ê@½À ½¶½­½£½œ½–€½’½Ž½‹`½‹ ½Ð½‘ð½–½› ½ ½¨P½®Ð½¸ ½Ãð½Ï½Øà½ê°¾8¾À¾¾¾ ˜¾ø¾X¾ð¾0¾!ð¾$è¾&h¾(ø¾*¾*p¾*¾)ø¾*€¾)ð¾(à¾&°¾%À¾$ ¾#ؾ"ø¾!(¾¾¾`¾¾x¾H¾¾¾˜¾€¾˜¾`¾¸¾¾h¾¾P¾`¾о`¾ȾÀ¾è¾ð¾ؾ˜¾(¾ x¾ ¸¾ À¾ ¾˜¾€½þн÷нó½ë½çнå½ãÀ½ã@½ã ½ä°½ä@½åð½èà½ë€½ò½õ@½ù@½ùP½úp½ùP½õ½òp½ì ½éP½ç€½æ°½é@½èà½ì ½ì½ì@½ê@½èÀ½ç½æ€½å€½ä€½ãp½áP½Ý°½Ý@½Ûð½×°½Ô€½Ï€½Ç ½½`½³Ð½­p½¨½¦€½¤½¡ ½ŸÐ½ ½œ ½šÀ½–@½’½Ž€½Š°½‰Ð½Œà½’0½—½œ°½ @½¡ð½¢°½ à½œ€½šP½—½•½“ ½ ½Ž ½‰€½„`½~à½q`½a ½QÀ½? ½/ ½! ½ ¼ö@¼Ñ€¼­@¼‹À¼a¼5¼¼»Û»½»¨»vºüº»&¹@;´;Ò;þ<€<€;ü;þ;ú< <<5À=D=F =J =L`=RÀ=W =a@=jà=u =~ =‚ =…Ð=‡=‰°=@=ð=“€=–Ð=—À=—à=•°=’P==Š0=„Ð=€@=y =u =z=|==„`=ˆ0=‰€=‹Ð=† =rÀ=l =x =|À=xà=z=z`=|À=€===À=‚=…=‰Ð=ð=’€=˜p=›à=ž =€=Ÿ= p=¡ð=¡=£À=¨ =ªP=®=²Ð=¼ =Ãp=Ì@=Ö=Þ=æÐ=î@=õà=ý >È>P>(>Ð>È>p>H=ÿ0=û@=û =öÐ=ôà=ð€=îP=î =é=ãp=Û=Ô`=Ì=à =¼=¸`=´`=± =´°=µp=µÀ=´ =² =­à=¨ð=¢=›=•@==‡=~ =q =\À=N=7 =%€= =À<õ<æ@<à<×€<â<âÀ<àÀ<Ù@<ÎÀ<Ë@<Ä@<Ã<Ä@<Ç@<Ï€<à<ß@<á@<ßÀ<Ö<Ö€<Ø€<Ñ<êÀ<ý€= À=@=%@=3 =:`=D`=F=Gà=R@=SÀ=U`=\ =_`=i=l`=mÀ=nÀ=lÀ=iÀ=i`=n`=rà=xà=€à=… =Š=Ð=—=›°=ŸÐ=§p=¬P=±€=·ð=½P=ÃÀ=˰=ÓP=Üð=ép=õ>ø>À>è>>¨>Ð>€>ˆ>>è>à>X>˜>˜>X>H>˜> H> H> >>à>à>@>°> >(>> €> ˆ> > Ð> ð> Ø> 0> à> à>@> >è>>¨>x>0>X>p>>!ˆ>%X>)>*Ð>,8>-0>-8>-0>,¸>-°>0H>20>4P>6À>8Ð>9 >:P>:>:Ø>:@>9`>9h>9>7¨>6È>78>7˜>8h>9(>9>8Ð>7@>8 >;><à>?P>Cp>Gh>Kè>O€>Q`>Rð>S˜>S˜>R˜>RÀ>R`>S>T(>Tx>V >W>X>Xø>[(>^Ð>b>e >hÀ>k¨>o¸>s>wØ>| >~¸>D>ƒŒ>… >ˆ(>‰ø>‹è>>Ž,>T>>¼>X>¸>‘>”>`>”> >t>‘H>‘ˆ>‘8>|>p>ô>>¸>\>”>8>0>”>\>Œ>x>ŽÜ>ŽD>ü>Žp>޼>,>‘>’€>”˜>• >˜ >˜„>™4>œ>ž >  >¢,>£ô>¥|>§d>¨ˆ>©¸>ªT>ª¬>«,>«€>¬8>¬ü>®0>¯>°l>±>²h>³ä>´è>¶ì>¸˜>»>¼ð>¾>¿Ü>Á<>Â0>Ã>Ã0>Ã<>è>Ä0>Å@>Æ >Ƹ>Çp>È >É>ɨ>Éð>Ê`>ÊÄ>ËÔ>Î,>ÐX>Ò¸>Õd>Ø>Ùð>Úä>Ül>ܰ>Ýœ>ÞÄ>àD>á@>áì>âl>âÐ>âü>âÌ>âX>â´>ã´>ät>å¼>æü>çì>èÜ>é„>ë\>ìÐ>î>îè>îŒ>îä>îx>î4>îL>îÜ>ï>î >íX>ì >ê >ç¤>äÔ>âœ>ád>àd>ßD>ÞX>ݤ>Üp>Ûœ>ÚP>ج>×D>Ö°>Ö”>Õü>ÕÐ>ÕT>ÔP>Ó>Ò\>Ñt>Ñ>Ñ>Ò<>Óø>Ö@>Ùì>Ý8>àŒ>ã¬>æp>é(>ì>îd>ð˜>òÜ>õ4>ø>ù¼>ûü>ýì>ÿH?€?þ?^?¤?æ?d? ??z?Ô?À??Ä?¨?Ž?Ê??Ò?¼???„??&?ô?È?Ê?¾?ü?è?À?†?þ?Ú?"?Ä?¦?È?Ø?Ø??(?v???Ž?h?J?Š?’?à?L?®?Ò?Ö?Z?Ò?À?J?„??Ö?”?j?r?.?Ì?T?¦>ÿØ>þ´>þ$>þD>þ(>þ¨>ÿt>ÿ¼>ÿô>ÿl>ÿh>þô>ÿ >þx>þt>þ¨>ÿX>ÿ˜??>ÿl>ýô>ýT>üÌ>ûÜ>úè>ùÐ>ù\>øD>÷¬>öÀ>õl>ôŒ>ót>ó8>ó¤>ö?Œ?J?N?ª?L>õX>éØ>ç>éð>í(>òÜ>÷ì>ùØ>øÔ>õ>ð¸>éì>åT>âÐ>ã0>åè>ë¸>òä>÷ü>ûÔ>ùÈ>ï@>àl>Ô¼>Ìô>ËÜ>Ò4>ßH>éÌ>ï>òÌ>ñô>ìô>êp>êð>êÀ>ìˆ>ò´>ùÜ?º?Ø??@?ª? &??4?T? B? Æ?0?R?f?v?þ???„?Â>ÿÔ>÷>ìà>âl>ÛÈ>ÙH>Þà>êÐ>ø?L?j?¦>õØ>ã\>Ô<>Å´>¸°>²l>´¤>¿\>Ò`>ã°>ñ”>ø >ô >è´>× >ÈÄ>Æx>Ì(>Ú¬>ï >ýü?>þ >ðp>ßÈ>˼>¼H>¹¼>½¬>Ê<>݈>ô`?6?<?V?Œ? Ø>ø|>Ûl>Íü>Ð@>Ûp>ç@>ðØ>óä>ñ >í$>çh>äD>ç@>å>ÜÈ>Ù,>ÝP>è>ûh?*?*?Ð>ù>ëD>ß(>Ô>Ï>Ë8>Ã`>ÉX>Öœ>áˆ>é¸>ñ,>î >Ùè>Ç>¹>±À>µŒ>¹>¾`>Êð>݈>çd>â”>ÚD>ÐÔ>Â|>¾ˆ>Ë >Ø€>Ý´>å`>ð„>ý?D>ýl>ïð>âP>Øä>Ëì>Ã>Í|>Üì>ã >çX>í@>êü>âÜ>à´>ßx>Ól>ÅÀ>À¨>¸`>°°>°¬>²à>¯ô>«4>¯Ô>²”>²`>¹€>Ã\>ÄŒ>ÂÈ>Ä€>Íx>ã´>ô¤>õè>êä>è >ó >ó˜>ðX>é>ßà>Ò$>Ì >×Ü>ç0>ñ8>ïì>ñ<>ó`>ä>ÏŒ>¼$>µP>´Ä>®>¥ô>žø> P>žT>š(>–¨>Žø>‹Ü>‰,>„`>‚(>€<>œ>|>œ> ¬>œp>‘´>‰>ƒt>†Ü>‘\>“˜>Žx>Ž>Œà>Œ<>–>¦¬>©> >—„>‘,><>Ž(>–x>˜ >–Œ>”°> >ˆ(>ˆØ>’D>ü>‹<>†„>~€>mx>eØ>t>ƒà>…x>y>YX>E¨>Cø>GÈ>6ð>#x>+8>H>a0>Xˆ>4¸>">1h>F@>X˜>^h>Q>B >=¨>6 >+°>5H>> >-¨>@> >18>Qh>f>n>WÀ>4`> >9x>_h>mø>]¨>@ø><8>Jˆ>H >9€>2h>$€>€>è>Ah>Gð>9(>6>3 >%>È>¸> (> Ø>˜=ü@=ÚÀ=ÞÐ=ô°>ˆ>ˆ>˜>@=óÐ> `>-@>B0>9x>+Ð>->$¨>!˜>&`>0>0€>8ø>A>@H>Vð>^È>AH> >>0p>N¸>N>-(>à>>`>(ð>*>X=ð0=å=êP=ü > >> =ò =áp=Ü=èP>Ð>P=öÀ=ä=×P=Ý=ã=÷À=ݰ=ÍÐ=ûÀ>È>>Ð=ô=þ`>°> =þP=æÀ=èp=ý> ø>x>8>=åÀ=É€=¤€=œà=¸à=à`=øp>=ü=Õ =µp= P=€=4 = =@=7 =q€=•Ð=”à=i = @< »£»ý<)=À=?À="`<™;4»´¼€¼G€¼£@½À½8€½E ½< ½" ½@½: ½4À½ @¼š€¼€¼É½ ¼ÛÀ¼i€¼;€¼»@½ à¼Ø€»Ì<9€¼t¼€¼C€»:À»R¼v¼ø½\ ½‘½ŠÐ½z ½‡`½“½“À½¤Ð½¿ð½ÑP½Ý@½î0½ø ¾H¾ p¾ €¾¾°½øð¾8¾ à¾x¾ 0½ú ¾˜¾ ø¾€¾ؾ¾*À¾/ ¾,ø¾*h¾%à¾!À¾0¾x¾ؾ 8¾è¾X¾ ø½ýÀ½òP½û@¾X¾ ˆ¾à¾X¾ ¾€¾)À¾-¾*h¾(¾" ¾оH¾p¾$@¾2`¾B0¾Jè¾I¾?p¾;˜¾?h¾Gˆ¾M¾H8¾H ¾Pؾ[¾Y°¾O(¾Ch¾2€¾# ¾#°¾-@¾4°¾:h¾:À¾1H¾'8¾¸¾p¾оp½ÿ°½í0½ôP¾¾X½ò°½îнô`½ð@½â½Ôp½Í½Ð ½ê¾ˆ¾ @¾¾ x¾(¾ X¾ ¾P¾ ¾ ø¾ ؾ ؾx¾˜¾¸¾#¾&¾%ˆ¾`¾x¾'h¾/p¾-@¾((¾%8¾$ø¾#€¾о¾¾H¾˜¾ ˆ¾8¾ ¾ˆ¾X¾о8¾0¾è¾p¾¾°¾¨¾ @¾ (¾Ⱦ¸½ïà½ß ½ä°½õP½ïp½Ù½Í½Ç½¾€½Ã°½Êp½Ï½Õ ½Ò`½Ò ½Õ0½Í ½Î½Ïà½Çн®@½ž½¨p½Æ°½àнä½ì½ð@½ã½×P½È ½½`½´½±½«À½žp½—@½ ½ƒ ½e ½:€½% ½@½`½à¼å@¼È€¼³¼Á€¼È¼×¼Ì@¼Ú@½½U½k€½M½3à½I ½„ð½§½¼P½Ä ½Êð½Ø½ã ½ï½õ@½ä ½É@½¶°½·p½Æ½Ö½åP½ð@½ëP½Ó½¿Ð½³@½´`½³0½³Ð½µ½¯À½®½²P½´½­ ½¤ ½¦À½´ ½½ ½½p½ÁÀ½Êнޠ½î ½í ½âà½à ½æ°½ï°½ÿ€¾ ¾ P¾ ¾@¾ H¾ Ⱦà¾8¾ ¾'x¾)ˆ¾(¾$°¾P¾(¾¸¾оp¾P¾!°¾%X¾'0¾'¸¾&`¾"8¾ؾ¸¾h¾P¾¸¾#X¾'è¾/¨¾/(¾>¾A¾(¾h¾ X¾ ¾ð¾À¾/(¾?H¾BÀ¾Dh¾Dà¾@˜¾7Ⱦ,ð¾"°¾$p¾1Ⱦ;à¾@0¾F¾L ¾OÀ¾MȾGȾ:¨¾-H¾%P¾& ¾0оD¾Uà¾XоPà¾K¾G¾E ¾@¾¾9p¾5Ⱦ3è¾3h¾6P¾8P¾7ø¾8¾5ø¾4P¾0X¾,°¾(h¾$ˆ¾#à¾&ؾ'à¾$¸¾à¾¾¾€½ÿ@½î ½ß°½Ó°½Ì ½Ì½Î½Èð½Á½´°½¡ ½0½@½i ½S½Oà½aÀ½|À½ ½žp½«0½®À½¬°½¦p½¢`½šP½—p½—½”དP½‹½‡p½Ð½n`½L@½/`½€½! ½8à½T€½r€½‚н†À½ƒ@½u ½b½K½4`½!À½ ¼Ù@¼—À¼>»:@< <ˆ€<Ó= `=à=5€=L€=_à=k€=p =m`=sà=‚=‹@=“ =—à=šð=Ÿð=£ð=¨`=¨Ð=£€=à=`=ž=žp=¡`=£p=¡À=œà=–ð==‹ =ˆà=ˆÐ=‰@=Š =‹°=Œ`=Š@=„P=p =K`=*`= = = =@=€==à= = à=@= €<ó€<É<®<“@P¾N ¾]x¾fоj¾fоa¾Y¨¾S ¾R¾U¾[€¾cоi¾kh¾gè¾[X¾M¨¾=ð¾.¨¾" ¾о0¾˜¾@¾8¾ X¾Ⱦ ¾˜¾½ø½ã ½Ø@½Ôà½Ö½Ö½Ó ½É€½¶p½°½…0½V@½" ¼é¼§¼€¼b¼q¼i€¼f¼U¼)€»Ò»9 9à»v¼6€¼¦¼è@½ `½½!@½  ½€½€½½% ½>@½a ½~€½Š`½Ž½ ½‰½°½ ½€°½„p½‹P½•€½›`½À½žà½¡½£à½§0½®½´½»°½¾à½¿@½½½º ½¸à½µ°½¯ð½ª½¨ ½¡ð½œ@½’@½† ½u ½eà½` ½e ½jÀ½o@½nÀ½d€½Q€½?½' ½`½  ¼ûÀ¼ç¼Í¼ž¼8€¸À<2€<Á€=`=L =rà=‡=’p=œ0=£°=¨à=±`=¹€=¾ =À=À@=» =´`=­ =©`=©0=« =® =®€=®À=­À=«à=©=¬`=²`=ºÐ=Âð=Ê =Ê`=È=Âà=»Ð=³€=®0=ª°=§ =¥=¡à=žP=š =’ð=ˆ`= =|`=€ =ƒÐ=‰ =Š =‡°=‚À=u@=c`=P`=<`=' =€= <íÀ<É€<¢@<\€;ö:Ü»z¼€¼U¼‘@¼È€½ ½"`½> ½PÀ½\ ½aà½p½~½‡@½‘ ½œÐ½©0½¸À½Ç½Ðà½×°½àн鰽õоp¾ ྾%x¾08¾7°¾>X¾E`¾H¨¾Lh¾Rx¾Y(¾b¾i¾o¨¾s¾u¸¾uؾq ¾p8¾n(¾j(¾d¾`¾\p¾Yð¾W8¾Q(¾I ¾@@¾7˜¾0@¾'H¾ ¾P¾p½Ü½¶p½“ ½R`¼ÿ€¼<‰€==``=Œp=¦°=¸Ð=Âp=Ê =ÎÐ=ÕÐ=ÝP=ç=ú€>è> 8>(>¨>`>! >(>.è>2è>3à>2 >. >(À>8> Ð=õ=Û@=Ê0=¼€=²0=« =œð=‡@=a =. <ýÀ<“À;Þº„¼€¼e€¼œÀ¼ã€½! ½bÀ½ŽÐ½£@½µ0½»p½¾ ½¶€½¥€½€½k`½:½ `½à½ ½  ½€½ ½@½)@½C ½^ ½iÀ½fÀ½\ ½V`½RÀ½D`½7@½$ ½ ¼ñ¼¢@¼%¹@<>ˆ>  > >È>¸>(> X>%P>*>-à>+0>%>X>°>h>ˆ> >€=ñà=ÜÀ=È@=´ð=¦=šP=Ð=Œð=ˆ`=à=kà=N=- = À=@=À= =à== €=à=€=À==' =L =u=Ð=£0=±Ð=·`=±Ð=¦=ž= ð=ª€=¶P=Á =Ë€=Õà=á=ë =õ>¨>x> >>+8>6>=È>D>CÈ>?ø>8È>0>%à>€>p>¨>8>>p>˜>> > 0># >%¸>&(>'H>)ˆ>,>. >0Ð>1 >-°>) >#p>è>è>h>°>Ð>ˆ> x> P> °>¨=ó=ݰ=ÌÐ=¿Ð=´=«À=¦@=¤=Ÿ°=ž0=š`=’ =ŽP=‡°=‡=‹À==’=•P=”`=“=“p=€=ŒP=Š@=ˆà=Ž€=–=£=«P=³À=¹=¼ =¼`=¸P=°=¤@=” =„p=l@=Oà=4 =`<åÀ<ŸÀ ¾2 ¾&À¾`¾8¾ P½ÿà½ç ½Çས`½ƒð½F@½`¼€:à<€<å@==7`=^ =‡Ð=œ°=¬=º0=Ã@=Ðð=Û=á=ç =ô >h>p> X>>#è>.€>6è>; >:`>:>6(>->€>h>=ëð=Ô°=À=­P=’à=~ =Qà=`<ÞÀ8> Ø>>¨>#>* >2>8Ð>>˜>D>I(>NX>T€>X˜>Z¨>Yx>TX>M8>F`>>>4ˆ>,X>%H>>˜>>  >x=ýP=óð=ëp=å=ÝP=Óà=Å`=µ=¥ð=—=‹=}À=gà=[ =Qà=V@=]À=e`=kÀ=p`=~€=‡ =–€=¨`=»Ð=ÑÀ=ç°=øp>È>> >¸>>(>>¨>%È>/ø>:8>Aè>E>CP>@>?8>?>A¨>H¨>PØ>Y>]P>^X>[Ð>R>H@>>à>7(>3Ð>20>7>=ð>BX>Bð>=È>3È>'Ø> >Ø> > >(>˜>X>à>(>>X>>ø>°>Ø>H>ð>ð> 0>0>0>¸>h>H>È> ¨>`>Ð=ý°=ø@=ó=ï=ì`=êp=è@=â=Þ°=×Ð=Ò@=Ë=ÃÐ=½@=·0=´`=±À=©Ð=ŸÀ=’ð=} =X`=/à=€<ý€<ä@<ÙÀ<É<¸€<€€;º»‚¼[¼Å½@½ ½ à½/`½<À½Ià½_ཀ`½’`½§½ºP½È½Õ½àP½êà½øp¾ø¾ ¾h¾"P¾+˜¾3ø¾=0¾Eˆ¾KȾR0¾X¸¾`¨¾j¾ux¾€|¾…`¾‰¾‹Ð¾Žd¾Œ¾Ô¾Ø¾‘¾’,¾”H¾–Ⱦ˜¨¾™„¾˜Ô¾—¬¾•\¾“¤¾‘¾ ¾ŽD¾Ž¾Ž4¾Ì¾ ¾‹T¾ˆ`¾„ð¾¾{°¾u°¾nð¾gP¾[è¾N¨¾A¾2X¾ 8¾ð½à½­À½‡½KÀ½À¼þ@¼ÆÀ¼³€¼¯À¼¯€¼¥€¼‚@¼:€<>€<”<«@<£<Ÿ€<£@<ª€<©À<£<ž@<¢€<œ@À>P>`>!À>)€>/8>1P>4X>7°>@¨>KØ>V8>`>hX>o >tè>v¸>u>oh>gÐ>c >`ð>_è>_˜>_Ø>a¨>\8>S˜>JØ>A¨>8à>/ð>)¨>&>$`>!ð> >x> X=ü=ì =Ý`=Ó`=Í`=Ñ=Ù=Ûà=âà=åð=ä=Þp=Ö =а=Ïp=Ì=Ðà=×0=ÞÀ=æ°=í =õ€=ù=íÀ=è=ç=ëP=ø >x>>è>h>è>¸>è>>€=ÿ =ùp=òð=é =Ý=΀=ÀP=²`=£À=”`=‚=X@=&`<â@<…À;Ó»|¼Q€¼¨@¼Ü¼þ½ ½&@½B ½a€½p½à½˜`½°½¢P½¦°½«ð½³€½½Ð½É°½×ð½ì ½ü ¾¸¾ ¾¾X¾À¾%`¾.о7ø¾B8¾LȾT¾\¾bà¾iˆ¾nø¾s˜¾y¾€d¾„\¾‡ì¾Šì¾T¾Œ¾„¾’(¾”<¾—¾šD¾œP¾Ÿ”¾£H¾¥L¾¦ä¾¨ˆ¾¨ ¾§À¾¦¸¾¦Ø¾§Ð¾¦ü¾¦Ì¾¥d¾¡\¾@¾˜Ø¾•0¾‘ ¾Œ¾ˆŒ¾…ľƒð¾‚¾~`¾wx¾j¾VÀ¾C0¾3ø¾(À¾x¾ؾP½é`½ÖP½Æ½ºð½¨€½—½‘½’н™½ž½¤½« ½§°½ °½ŸP½¢@½¨Ð½©½« ½µP½Ä°½ß ½ø¾¾`¾@¾&€¾8@¾J¸¾_à¾t྄P¾‹$¾’¾˜À¾ž¾¢p¾¤¤¾§t¾¬8¾° ¾µ´¾¸8¾·Ä¾µ4¾±ô¾¯¾¬H¾¨¤¾¦D¾£à¾¢¾ŸÐ¾œX¾˜ø¾‘,¾ˆX¾ ¾m ¾a@¾W¸¾R¾MоIоIÀ¾Jè¾Hè¾CȾ:h¾1ˆ¾(¾!¾¸¾€¾ p¾p¾½ú€½ðÀ½äн۰½Ö0½Õ`½Õ0½ÙP½áð½è½è½æ0½â°½Þнܰ½Ø½Ïà½ÌнÍнԠ½Úp½Þ`½ß½âP½ä½äнã0½Þ0½Ú½ÕP½Ñð½Ëà½Å ½Á ½¾½¶ ½®à½¬½­Ð½°à½® ½ª0½ªÐ½­p½±@½·@½¸À½¸@½µ0½³À½®Ð½ªp½¦ ½¡½¢½§€½°½½p½Ç€½Êð½ÍÀ½Ó0½ØP½Ü ½Üà½Ú½×½Ðà½Åཽp½®Ð½œà½ð½€Ð½e½Gà½.@½¼î@¼”À»ò:8<0€<£€<ì@=@=) =E`=_ =wÀ=Š€=–= à=«Ð=²P=µ =¶Ð=·€=»=¿= =ÅÐ=Äp=ÃÐ=ÁÀ=¹ =²=ªð=¥P=@=•à= =‰ =„p=y =i@=Y`=K@=@`=: =:€=5=6€=4À=2@=2`=3`=B€=NÀ=b€=|€=Ž`=ž=©ð=´°=¿€=È =Õ=âà=ð`=ûÐ>Ø>x>¸>8>@=üà=ø=ðp=éà=ä=â=ÛÐ=Ø=Ö`=а=Êà=Â`=»=±€=¥Ð=œÐ=’0=ŠÐ=À=m`=Q =1 = <þ€<äÀ<Õ€<Ë€<À@<¬À<–À<ˆ€˜>h> X>˜>Ð> >P>P> @>>È>ø>è> (>è>>è>>h>0> >ø>˜>ˆ>H>> >(> >À>°> =ÿp=þÀ=ÿ@>`>H>à> `>H> > >>h>ø>@> > x> 8>X>à>˜>Ð> >!>%¨>+H>2>8x>?¨>E >H>K@>LH>K0>H >C@>?X>=@>;ø>< >=>?8>A(>Bð>F>FÈ>G(>H8>Iè>K@>N¨>RÈ>Vx>[Ð>`ð>g >nX>tp>z°>€l>ƒŒ>„€>†Ä>‡ì>ˆ$>ˆÈ>ˆ˜>‰>ˆÄ>ˆ>‡Ü>‡>‡<>ˆŒ>ŠÀ>4>D>’H>“ >”¼>•>”<>“À>’ì>‘>Ž`>‹Ô>ŠL>ˆ<>†t>„€>‚ø>¸>€,>}>{ø>{`>y¨>y¨>w>sˆ>op>k€>iè>g>dP>b€>cX>cÐ>h`>oÈ>t¨>{ >>ƒÜ>†Ä>ˆÈ>Š>Šì>‹>‰¬>‡à>†>„d>‚ˆ>>~H>y>wà>w(>w˜>z >}p>€>d>À>„>¨>yÀ>rˆ>iH>`È>V`>LØ>D>< >5¸>/ð>)p>#(>Ø>>> >¨>0=þ@=ó°=ç =Ú=Í =À`=µÐ=®=©€=¥0=¢ð=£`=¦À=©p=­=²=·p=·À=¶ð=· =³à=­ =¤À=¢P==˜ð=‘`==Šà=Š =†p= =`=t@=oÀ=kà=i`=n@=m=o€=k`=X`==à= =`<Ï€<†<;½;Ÿ;L:@»4¼¼q€¼®@¼ã@½ €½  ½3€½E ½QÀ½]À½dà½r€½|ག0½|€½u`½q½eà½V ½<à½! ¼÷À¼À»Ö;p<`€<Â=à=2`=`@=‚=”P=¬= =Öà=ë`=õ =ú0=þ >H>Ø> >¸>˜>'È>,>.p>.˜>* >"°>P> 0>=ý€=ñ0=áp=Ï=´ =•`=l =0À<ïÀ<¡€X>À>è>ð>È>8>Ø> Ð>¨>H>#x>'0>'ˆ>%>!X>H>@>Ð>(>Ø>x> H>ð>€=øÀ=ç=×ð=ÇÀ=¸p=° =«Ð=§ =¢Ð=™€=‰°=q=G=€<Ü€<`> ð> @>à>`>°>'>-p>50>:p><`>=>>>B€>H`>N>Wð>dx>oH>xP>}ð>~@>y>o>gX>_˜>YH>YØ>[p>]ˆ>\>Y`>UÐ>PH>HØ>A¸>;è>8x>8>9€>>@>>à>;À>9P>60>1ø>.@>,(>*°>-Ø>3P>9Ð>@x>F>J¨>NÈ>SÐ>V>WP>Và>UÈ>Uà>U@>U¸>TÈ>S>Q0>P>OX>N¸>Kx>GÈ>C>@@>=P>9 >5h>1 >*H>">X> ˜=ø°=Ü0=Ä =µ=§à=¤ð=¥=£°= =Ž=@=d=< = =à<áÀ<Ù<ÍÀ<Å@<«À<“X>ˆ>>h>¨>È>ˆ>À>H>ˆ>°>p>À>ˆ>¸> >> (>ˆ>À>¸=ô =àp=Ó =Æ =·@=®à=§°=¡@=™ =Ž`=ƒ°=qÀ=U@=D`=3@=%€= = = <ñ<Ï@<¨@<\<{€°¾B˜¾Hà¾R`¾[è¾eоmX¾xH¾¾„ؾˆ0¾Œ¾”¾•ؾ›0¾ „¾¤|¾§œ¾ª¾¬¾«¾ª@¾¨¸¾¥˜¾ ¾˜¾Žø¾„˜¾u¾b¨¾Mð¾=`¾/X¾ ˆ¾0¾ 8½ý½é@½Óð½ÄÀ½´`½©P½¢½•𽉽oà½6¼ð¼U€:øð¾Bp¾G¾JH¾N(¾Qè¾U¾YX¾[(¾\о_Ⱦb8¾e0¾h ¾l¨¾pоt`¾x¾{¾}ð¾€l¾¾ð¾‚(¾‚Ⱦ„€¾†¤¾‡è¾ˆ4¾ˆ”¾‡ä¾‡$¾†à¾…„¾„|¾ƒˆ¾‚<¾‚¾€ì¾z`¾m`¾Y°¾CP¾+è¾è¾è½ö½ç ½Þ ½Ø°½Ñ€½Æ ½°€½•@½s ½E ½,À½-½>à½R ½Q½9འ¼|;¦<Ù=3€=X=D =<:€¼X€½ @½G@½g ½r ½}@½†ð½™Ð½· ½áP¾ ¨¾%Ⱦ:(¾EȾI8¾E¾=°¾:¾;ȾD8¾T@¾f ¾x°¾„€¾‰T¾‰¼¾„œ¾|0¾nȾdh¾^8¾X`¾Rè¾M€¾FÀ¾<˜¾00¾ 8¾ð¾ ½ñ½æ ½á`½Ú ½Îð½¾@½¥½„p½O½ ¼Á¼c¼»ž»<º`:Ì:Ì;*9лª¼&€¼j€¼“€¼¥À¼²À¼¹@¼¼À¼Å€¼Ø¼ñ½à½5À½Q½a ½ià½k ½mà½l`½yཆ𽓽Ÿ½§à½­à½¯Ð½ªP½›€½Ž@½ƒð½‚½Š0½•½›½ ½ Ð½ž`½—нŒð½€½h`½XÀ½R@½V ½Y ½P ½D½4½" ½@½½@½+ ½8 ½QÀ½h€½y`½~`½u`½p½i€½e ½f€½e€½b`½] ½RÀ½HÀ½>`½* ½ ½¼è€¼ÜÀ¼ØÀ¼ÇÀ¼™»ã< €<»@= =? =\à=w€=‡0=À=›À=ª0=À=ÛÐ=÷`>X> ¸> Ø>(> =ýà=ù =õ=÷@=ù=ýð=ù0=ë`=Ò`=³=”0=l@=? = `=`<é€<Ù€<¾€<‘@<€º@¼A€¼¾@½À½#`½=à½R€½d`½q ½‚À½Š½‹½ˆð½…½‚ð½}à½z½xÀ½t€½f ½V ½@€½ ¼õ¼´¼”€¼¼™À¼¦€¼µ¼´¼”@¼Q»¶;><6€<}ð¾3˜¾*H¾"°¾ ¾è¾¾ ྠ¾ˆ½öÀ½éнÝ0½Óà½Ò0½ÓÀ½Øp½Þ ½à ½âð½ä°½ä ½ãÀ½äÀ½æ0½è0½éà½é€½ì½î0½ð½î½î@½íÀ½îнé½â ½ÛP½Ó`½Ò ½Õ`½Ñ€½Ï½Ì€½Éð½É½À½¸°½¬à½¢ð½žà½—½–ð½™0½š`½™½`½„ ½m ½M@½=@½8 ½< ½U½n€½Š@½½¨ ½®Ð½´ ½¸ ½¸½¶ð½½à½Á ½Â°½Ê ½Ñ½ØÀ½á@½å ½æà½ëнîнó½þ0¾ؾX¾¾#°¾)X¾+(¾(¸¾%˜¾"H¾оð¾p¾ ؾ"à¾#à¾#о&8¾%0¾# ¾"P¾"ˆ¾!(¾ ¾à¾¾`¾оh¾p¾ (¾(¾`¾ø¾ 0¾"X¾'о-°¾4À¾:@¾?@¾BP¾Cø¾Fˆ¾Hx¾L ¾NÀ¾Qð¾U¨¾Wà¾XؾYȾZ¾[8¾[0¾[˜¾\0¾^À¾`ð¾bè¾f¾gˆ¾j@¾m¾p`¾s¾uø¾wÀ¾z¾{¾zȾ{¾{ؾ{x¾{€¾{0¾|À¾¾€ð¾‚`¾ƒ¸¾…¾„t¾„\¾ƒ°¾ƒX¾‚ľ‚L¾Ü¾Ø¾|¾œ¾€Ø¾€è¾€L¾о~À¾~¾¾ྀ|¾€¬¾€˜¾о€l¾h¾|è¾z`¾wоw(¾w¾x¾yо|¾}X¾€¾T¾‚ ¾ƒT¾„4¾…H¾…\¾„ä¾…X¾†¾‡¾ˆ8¾ˆ¼¾‰,¾ˆô¾‡H¾„¼¾ƒ¾¾€„¾è¾€4¾~À¾}˜¾}è¾{ˆ¾y¾v(¾qà¾p`¾o˜¾pp¾q˜¾p¾l ¾f0¾[˜¾O ¾Cо5о)辈¾p¾x¾ °¾¾@½ú½ë€½Ö@½È`½ºð½±à½®°½¯½®°½®°½¥p½”@½{€½;½`¼£@¼X¼S€¼b¼š@¼Ê@¼ñÀ¼ï¼Æ€¼–@¼K€¼¼9¼†€¼Û½"@½O€½r€½„`½Š½‰½ƒÀ½`½‚P½…€½–½§À½¶à½¿ð½Â`½À ½²½ž€½„ ½\à½@€½$@½À¼û€¼ëÀ¼ÂÀ¼¼S€»û»";H;˜;Ü;È;ª;„;< €¸>X> ø>Ø>È>#Ø>+Ø>3€>90><0>=¨>@>Cˆ>D°>F>Jx>O>S>V€>X¨>Z >WP>Q˜>KÐ>GH>D >?>:¸>5È>-Ø>&>Ø>>Ø=ú=êà=ÝP=Ò€=É =Â=¹p=±0=¦°=£@=£`=£@= @=›=—ð=“=Ž@=Œp==ð=‘ =™`=¤ð=ªp=¬À=«`=­`=²`=´Ð=µ°=¼`=ÄÐ=Ç`=ÈÀ=Æð=¿ =¹P=²P=­ =¯°=²P=¹ =Å =Íð=Õà=Û=Ü€=Þ0=Üð=Ù°=Ø=Ø =ÚP=Þ@=àÀ=á=Þ°=Ý=ÚP=Ó=Ê`=Ã=½°=¼À=¹€=¸à=¸=·p=µ`=±€=®=¨=¡=žà= =œ=ŸÐ=¤`=§ =­p=¯`=°à=´0=¶0=»=À`=È`=Ì=΀=Ó=Õ0=Õ=Ôà=Õp=Ôð=Ö=×à=×P=ØÀ=ØÐ=ÙÐ=Ù@=ØP=×À=×À=ÚÀ=Úà=Ú=ØÀ=Ö =Ò=Ï=Î =΀=Ñð=Ñ`=Îp=Ê =Ç@=Ä=ÀÐ=¼0=·`=²=± =°P=°@=³Ð=·0=¼=Æ=а=Ý=ê@=ø>@> H>@>À> °>!`> H>À>h>è>˜>`>à> > `>(> 8> > >€>0=þ =ø°=õÐ=ð@=é@=æ =ß =× =Ó=Í@=ÊÐ=Ï=Ó0=ܰ=ë€=öð>è>> >x>Ð>>>H> 0>#`>(ø>/€>6`>?P>Ið>WX>e>qè>€8>ˆ\>Ø>–H>œ¬>¢>¦@>ª>­T>®ü>°>°ð>±ä>³l>´€>µ@>µ>µp>µ$>¶>¶ø>·t>·d>·>¶$>´<>¯Ì>«T>¦¼>¡8>$>™Ä>—l>•8>’ >>L>Žè>Ž>ŒŒ>‹ >‹h>‹Ä>‹€>Š˜>‰>‡X>†Ð>‡œ>‰h>‹>L>”l>™¬>ž\>¢¨>¥ä>© >ªØ>¬ä>°@>²x>³ì>µ$>¶$>¶”>¶X>µp>´ô>´È>¶>¸<>º¼>¾€>À¬>Á>ÀT>¾D>ºØ>·ì>µ˜>´ˆ>´Œ>´”>´¼>´ì>´>²>±¼>± >²Ø>µ\>¹X>½\>Â>Ť>Çè>ÉÌ>Ê8>ÊL>˨>Í,>ÏŒ>Ót>×,>ÙŒ>Û8>Ûœ>Û\>Û¸>ÜD>ÝÈ>àÈ>ä@>ç8>ê”>ëô>ìÀ>ì€>ë0>ë>ë„>î>ñt>ôŒ>÷Œ>ùÈ>úô>ûÄ>ü>ül>ü@>ýD>ÿ˜?ª?2?>??Ž>ÿŒ>ý¤>ý<>ý€>þh>þ°>ÿœ?¸?Ì?ä?ê?†?>ÿ>þ>ýp>üH>ûd>ú<>øh>÷`>÷,>ø@>øØ>ú<>üÈ>ý„>þL>ÿ\>ÿ?? ?p?¤?€?@?–?¬?T?ö?\?À?à?$?f?<?n?†?`?t?f?`>ÿÈ>þ>ûŒ>ú>øh>ö(>ôL>ñð>ï0>ì >êÐ>éX>çÌ>åX>âð>àì>Þ>Ü>ØÐ>Õð>Òè>Ï<>˨>È>Å>ÂD>ÀT>¾ø>¾¸>¾|>¾È>¾Ü>¾¸>½T>»H>¹˜>·ð>¶>´Ø>³$>¯à>®À>­$>¬,>¬>¬”>­$>®t>°¸>³>¶,>¹(>¼Ô>Á>ÁÜ>Á˜>ì>Ĩ>Ä€>Â,>À(>À >¿À>¿˜>¿Ì>À >¿¤>À>¿h>¼H>¹ˆ>·”>³è>°>­>ªl>§¼>§À>§¤>¤ð>¢>Ÿˆ>œÄ>šä>š,>™„>™H>˜¼>˜ˆ>— >–d>“è>’,>à>>Ž >Ž˜>Žl>ø>œ>Œp>ŠÀ>‰4>ˆl>ˆ>‡¤>ˆ\>‰À>‹0>Œ<>ŒÀ>Ž>d>Ì>‘È>’Ð>”D>•>•Œ>•>•ð>–„>—>˜à>˜¸>˜l>—t>–>”ä>“¸>‘À>d> >>Œ>Џ>Š`>‰`>ˆè>ˆà>‰>Š8>‹À>Ž,>‘>”X>— >š>œð>ŸÐ>¢l>¥8>§ô>©|>ª€>¬d>­Ð>¯È>²T>µÄ>¹T>¼8>¿|>ÁÔ>Äh>Å|>Æ>ÆÜ>ÇÌ>Éô>Ëü>Îx>ÐÀ>Ò¬>Óx>Ó4>Ò8>Ñ\>Є>Ïø>Ï|>Ïô>ÑP>Óˆ>Õ>Õà>Õè>Õd>ÕH>Óè>Ô\>Ô°>Ôè>Õx>ÖP>×l>×@>×0>Õô>Ô°>Ô>Óx>Ò¨>Ò >ÑD>и>ÐÜ>ÑÜ>Ó>Ô>ÔÀ>Öh>×ä>ؼ>Ú`>ÛP>ÜÄ>Þ>ßì>âX>å|>çì>éè>ë˜>ì°>í¸>í>î>ï@>ðÌ>òÜ>õD>÷¸>ù$>ú`>ú|>ú4>ú0>úT>ü>ýp>ÿ<?Ð?ô??Œ?ô?j>ÿü>ÿ´?j?Z?d?Ž?F? ?æ?À?Î?â? ? ? ? ö? 2? º? \? ? t? T? >? ˜? ˜? Ê? Ú? â? €? ”? ? `?j?„?Ð??J? ?Ö???Â?(?ä?!Š?#V?$Â?%Þ?& ?%ê?%¨?%\?%„?%¦?&V?'?'f?'?%ˆ?#ú?!æ?ü?ð?2?>?Ì?<?º?š?î?Z?°??î?`?ú? V? ª? ?r?š?ö?z?L?Œ??l?2?Þ?À?j?$?:?&??ì??`?<?Š? ?Æ??”?J??<?ø?ž?.?ð?ú?æ?Ì?Ð?Œ?ä?b>üœ>ø>óÈ>ð8>íx>ë´>ê >éÈ>èä>çd>ä¼>âT>ÞÜ>Û„>ØÈ>Öô>Ö0>Õð>Ö>Õ´>Ô>Ó(>Ð|>Íl>ËL>ȸ>Æl>Ŭ>ÅP>Äì>Å8>Ä€>ÃH>Áx>¿H>½`>»<>¹>¸(>·˜>·d>¶Ø>¶Œ>¶Œ>·Ô>¸H>·¼>¶Ô>¶x>¶>µ>³´>³P>³>²0>°Ô>®(>¬>¨ø>¦H>£Ô> À>ž8>œˆ>›ü>›´>š$>˜@>”Ä>Ø>Œ”>‰ >… >‚Ø>€<>}x>|>z>xP>v>uP>sÐ>r€>qÀ>qp>qx>r`>r°>r0>p€>n>kÀ>j°>l0>mp>p>q >qÐ>q>p>n€>k˜>jè>kð>mØ>oà>nà>fH>`Ð>^€>Y>QÐ>Nh>JP>H˜>DP>@`>=P>:H>88>5 >/ >(À>$x>!@>0>`>8>Ð>>°> x>Ð> >x>˜>à>˜>8>È>ð>ˆ>ð> >`>8> h>#>#H>%è>'ø>)¸>-À>2Ð>5X>9È>>h>B°>H8>Nh>V >^ >fH>o>yp> >…>ˆˆ>Št>‰à>Š>‰¬>‰¸>‰¨>‰À>Š0>‰>‡(>…¤>„<>‚@>0>€x>°>~à>}Ð>zÀ>wH>th>o`>mX>jÐ>iØ>j>k°>n0>p€>rØ>wh>|>€„>Ü>‚|>‚ì>„\>†h>‡l>‡È>ˆ>‡t>‡ >…H>‚p>€„>€ >€ð>€Ø>‚œ>ƒ>†d>‡$>‡P>ˆ>‰°>ŠX>Š´>‰ä>ˆü>ˆÄ>†h>…ô>†4>†À>‡>‰ >‹œ>Œ¨>Œ >Œà>œ>’Ä>“T>”>•>•Ô>–l>–Ä>•à>”ü>”ü>”°>•H>—>™Ø>> $>£0>¦Ü>©ð>­,>°l>²Ð>µ`>¶Ø>¸<>¹>º>»<>¼t>¼¨>¼|>¼`>¼ >½¨>¾À>À(>Á>Áˆ>Áì>Áì>Âl>ÃÌ>Ĩ>Æ|>ÈP>Él>Ê >Ê„>Ë<>˰>ÌP>Í|>Ï@>Ñ>Òø>Óô>Óô>ÓÔ>ÓP>ÓX>Ò´>Ñà>Ñt>Ñ\>Ò0>Ò<>ÑÈ>Ñè>ÑD>ÐÄ>Ñ<>Ò0>Òˆ>Ó´>Ó¨>Ó¬>ÓÔ>Óä>Óè>Ó(>ÑÔ>Ðà>Ï>Ï@>Îä>Í”>ËD>Èœ>Ç”>Ř>Ãì>ÁP>¾`>»È>¹8>¶>±ä>®P>ª€>§Ð>¥Ø>£t>¡ >ŸD>ž>œð>š€>—Ð>•D>“ü>“>’ø>’Ø>“d>“°>“œ>’P>ˆ>”>ŽD>@>‹ð>‹H>Š>ˆÐ>ˆ„>ˆ>‡H>„Œ>‚¼>‚Œ>ƒd>„D>†>‡¸>ˆÌ>‰¼>Ь>‰¸>ˆ¼>ˆˆ>ˆ >ˆ,>ˆÌ>ˆ>†”>…ˆ>ƒÔ>‚x>>è>}¨>z>x`>v>r€>mÀ>jÈ>j°>lh>k°>fÈ>`ˆ>[>Y>V0>Q°>IÐ>@ >9H>4°>1À>/h>*ˆ>%0>"X> H>`>0>h>˜> >>>X>X>(>>ˆ>˜>0>p=ýp=÷Ð=ñ=ò=ôà=óÀ=õP=öP=ò=îÀ=ñ=óà=õ@=ðð=å=Ý@=Û=Ù@=Ò=È0=À@=¹°=°`=§0= 0=ž`=šp=›=œ =™0=– =’=ˆÀ=€À=rà=W =9€=(= = =@=à<ý<ÒÀ<½<Î<ö@==À=,À=5à=EÀ=Và=`@=f =gÀ=p =u`=€ =‡=Œ@= ==“€=™=£ =¨0=§p=¤ =£ð=¦Ð=© =¬=¯€=´À=¸À=¸€=¸P=¹Ð=»à=À=¿ =Á@=Ä =Å€=Å`=à= =ÀÀ=º°=³`=©@=p=”`=‰ð=à={à=wà=y@=qÀ=] =HÀ== =9À=4@=7=:`=> =EÀ=C@=2=`=`=@= =`=à=$€=7 =H=R =O =K€=S`=\ =_`=h`=m =n =q =sà=tà=zÀ=tà=c =UÀ=H€=D@===/À='`=€=  ==€<ÿ<ó€<ÐÀ<¶@<§€<²À<ÁÀ<ÓÀ<è@<û@= =)€=: =?€=C`=G =J =NÀ=[€=qà==ˆ =ˆà=ˆ=ŠÐ=P=• =›=£€=®ð=¹À=Ãð=̰=Ò =ÕÐ=Ôà=ÐÀ=ÐÀ=Ú =é@=óà=ù=þ°=ÿà=û`=ù=õp=õ=üp>>> ˜>˜>À> > 0> p>>H>H> >€>>x>p>x>>ø>ð>P>Ø>è>0>ˆ>Ø>> à> ˆ> Ø> X>(>8>Ø>> >=ÿÀ=ú=úà>@>>(> Ð> à>0>H>>>ð=þ€>H>È> à> x> `> ð> x> Ð> > Ø>>8>> >(>¸> P>0>à>€>0>ø>h>8> > ˆ>=ûp=ø=÷À=õ=ö=ø=ö0=ñ°=ðÀ=÷ =þÐ>>¨> ø>ˆ>h>@>ˆ>8>(>#È>*ˆ>/¸>4°>9È>;Ð>:(>;>@`>F>HØ>Ch>7ˆ>5>;¨>?˜>@ >?Ø>: >7À>8>8È>4˜>,ˆ>!>è>à>¨>P>x> @> ¨>è>P> >`=æà=Íà=°=Å€=а=Õà=Ë =¾ =² =¢p=”€=Œ€=‰ =Œ=– =¦0=¬À=®0=Ÿ0=Œ`=…Ð=…@==Žð=ˆÀ=t@=w@=ˆP=“ =—0=—À=–°=•P=›`=¡p=±@=ÄP=Ø€=ë=ìà=ì =ï`=÷0=ø =ñð=è0=ãP=çÀ=ï=î =æà=áð=è =ðà=è@=Ù`=Îà=Ç@=ÄÐ=¿p=³€=¦à=¨=¬ð=©À=š€=zÀ=K@=;€=; =6€=$ <ã@<Œ@<‰<™@<ª<¨<ƒ€<;Lº¼º„;*; <*€<„€<š@<<„€;Á;@:Ì:º°º:È»¼€¼A¼T€¼E¼0€¼<¼H¼„À¼ãÀ½% ½8à½2€½Gà½h ½Œp½¥ð½¤€½¡½¨ð½½ ½Ðð½Öp½×P½Ù`½å0½ô ½úнþ@¾h½ÿ€½ûP½þ€¾˜¾H¾(¾¾ €¾ Ⱦ¾¾h½øp½é°½ë0¾8¾ ˜¾À½ûP½í ½íà½ö½ÿ€½ðP½ã`½é`½ý`¾ ˜¾(¾ø¾0¾¾@¾ø¾"è¾%¨¾(ø¾+0¾.8¾.Ⱦ.¾(h¾ ¸¾ð¾x¾"`¾'è¾$ø¾ ø¾à¾!о% ¾$ؾ!о P¾%h¾-À¾4ˆ¾5¨¾4¸¾0 ¾, ¾#X¾˜¾ø¾¸¾)`¾/8¾0(¾. ¾)ˆ¾"°¾8¾è¾8¾8¾h¾"h¾-X¾8ð¾9@¾,˜¾¾h¾!ø¾2о@€¾Ip¾R8¾ZÀ¾^@¾WоR(¾XоcȾk8¾ph¾tx¾{8¾È¾‚ä¾¾0¾}ø¾~°¾@¾‚t¾…ô¾Œ¾0¾4¾Š`¾†¾„|¾ƒ°¾¬¾€ü¾„˜¾Š¾‰L¾€˜¾kо_¾^€¾bà¾k°¾rؾv(¾rp¾hp¾bX¾b°¾b¾\˜¾[ؾ[X¾\¾c˜¾g0¾aÀ¾Th¾H@¾>p¾6h¾2è¾7(¾H0¾^¸¾m¸¾oоe ¾X0¾Q¾N ¾Q¾W(¾a¾k¨¾u°¾}¾}`¾zp¾w(¾mà¾\ ¾QP¾Uh¾b€¾m¸¾s@¾sȾp¾m¾f`¾[p¾Wˆ¾ZH¾`ˆ¾_@¾Wø¾Vh¾Z¾ax¾j ¾qH¾p¨¾i¾[¾Nð¾K˜¾Ih¾H@¾NȾ_8¾kX¾dؾ](¾Y¾V¾Sx¾M@¾B¾C ¾N ¾Z¾^à¾b ¾gh¾e¾V¸¾F¾?¾?¾A¾@@¾>¾I˜¾XH¾Vè¾A ¾,¾%¾#À¾#€¾0¾¨¾¨¾ؾ¸¾X¾8¾è¾è¾¾оp¾@¾@¾ ¸¾ ø¾@¾@¾)ؾ0(¾)Ⱦ  ¾p¾€¾0¾ ø¾H¾˜¾.ؾ=˜¾:`¾1H¾*¾(À¾'¾$(¾ ¾&°¾+ð¾.0¾/ ¾/@¾+¨¾#H¾¾ X¾p½ùP½ûP¾¨¾8¾P¾¾ ½óÐ½Þ ½ã ½ÿ°¾ p¾ h¾ ؽû`½éà½÷о€¾à½ð ½Û ½Û°½á½Û@½Ï°½Ì ½Ãн¿½À ½·p½¶€½¿ ½À°½¼½³½¡0½ˆÐ½z€½]`½N ½m ½@½šÀ½¥0½«P½Ÿ½ˆ½½‰à½½¯À½Çð½Üp½åP½ð`½ô°½õ ½î0½Ùð½ÐÀ½ä¾¸¾˜¾p¾ °¾x¾x¾(½ÿ½ÿ ¾X¾ €¾x½ÿоð¾h¾ ¾ ½õÀ½è¾°¾ ¾8¾¾ X¾°¾"°¾+¨¾.°¾/0¾,˜¾'(¾&˜¾*0¾+X¾(ˆ¾$@¾¾ؾ о¾(¾¾¨½é0½Ç ½¼p½¿½Ê ½Ó@½Ï ½¾p½¯`½µP½Èà½Ð€½»P½œà½Šp½`½Ÿ½®½ªÐ½£€½¢°½¢€½ŸÀ½£p½¶P½Â€½¼à½­À½ªÀ½µ€½»@½ÊP½Ñ@½Ìà½Ï€½Îà½ÓP½Úà½Ú0½Ð½Ñà½æp½ÿ°¾ ¾ ð¾ (¾¾@¾ø¾H¾X¾ð¾ˆ¾h¾˜¾à¾"P¾#ð¾!¾¾ ø¾ `¾¾P¾#`¾*¾+(¾P¾Ⱦ °¾H¾¾h½üÀ¾°¾¨¾x¾p¾ ¾`¾¾ ˆ¾ оˆ¾˜¾+¾0 ¾7€¾9à¾2ð¾&H¾¾!¾*¾8¾E@¾K@¾D¾=0¾>¾>X¾@(¾@€¾BX¾Ip¾Iˆ¾K ¾U0¾WоMؾ>ˆ¾6@¾9 ¾E¾P@¾Tð¾V¾RؾI ¾;¸¾0¨¾.H¾6À¾=X¾D0¾R0¾Xh¾YÀ¾]X¾\¾Qp¾F¾?H¾Ap¾IȾZȾkоx ¾s¾Zˆ¾F˜¾J¾[¾^оT(¾LP¾Tˆ¾_ؾhh¾hÀ¾]ˆ¾J€¾BH¾D8¾D¨¾JH¾QоKð¾<À¾3¨¾7ˆ¾K(¾^°¾[¾Eø¾8ˆ¾:`¾>°¾=P¾AÀ¾Jè¾OH¾M@¾J¾I(¾Lx¾M ¾=ð¾-ؾ0p¾< ¾EH¾FÀ¾I¨¾O¸¾Y¨¾^ˆ¾V¾M`¾G ¾G¾J°¾O¾Yؾi¾l°¾^ ¾Uø¾_x¾l˜¾sÀ¾o`¾e¾`¨¾f0¾r0¾| ¾€ð¾€¨¾t0¾k˜¾g¾eX¾gð¾eð¾`¾ZX¾Y˜¾^è¾_ ¾WH¾Oè¾O@¾O¸¾Jø¾B¾8ð¾8è¾@ð¾H`¾Iˆ¾I0¾FP¾BH¾A ¾>X¾AؾRH¾`˜¾d¾_¾Z@¾XоXø¾`Ⱦf€¾dx¾[€¾Lˆ¾Eˆ¾Mà¾T(¾Hؾ8¨¾5P¾B8¾Ux¾UX¾H¾=À¾=оBH¾B`¾@X¾50¾+è¾3€¾;Ⱦ4¾&X¾$ˆ¾+¾$à¾`¾à¾¾¨¾оh¾(¾x¾p¾ؾ¾h¾ à¾h¾à½ý@¾ð¾à¾ ¾p¾ ¾H¾H¾ ¾ ¾ȾȾ`¾˜¾ˆ¾¾ؾ¾p¾ð¾¾о¾8¾!˜¾%0¾+¾"P¾!€¾'h¾$H¾о8¾h¾¾¾Ⱦ€¾ è¾ ¾à¾½þ½èà½Ø ½Øð½Ü`½Ø½Ò½Úð½í€½ø`½ü@½úP½àp½µp½ p½¬0½Ë½èÀ½ÿ°¾ˆ¾à¾P½ß½Ë@½äð¾P¾(¾ ð¾8¾ ð¾¾ؾ`¾¾p¾`¾ྠ8¾°¾0¾(½ý0½äP½ÏÀ½Ù½ó€¾H¾¾ؽê½àà½á½Ø`½×½ç¾ˆ¾`¾p¾p¾P½ã`½â½ü¾ ¾о ¾P¾ð¾(о.p¾P¾X½èÀ½áÀ½ö¾¾)0¾30¾*˜¾ؾ¸½ñÀ½òÀ¾¨¾8¾(¾ ¾'À¾*p¾'¾!€¾¸¾0¾X¾`¾¾'ˆ¾9¾:0¾,à¾! ¾€¾$Ⱦ(ð¾'0¾'¾'x¾$x¾ ¾ð¾ ¾(à¾;À¾?ؾ;ˆ¾7`¾/h¾ à¾X¾ ¾ؾ0¾/@¾;à¾9€¾3¾1о)H¾h¾ ½Ø0½ë@¾¾3˜¾Ap¾Hx¾D`¾3ؾ#è¾ྠp¾ @¾X¾)Ⱦ7¨¾F¾O0¾F0¾/Ⱦ"8¾À¾"p¾2°¾EP¾OȾKð¾G¾Fˆ¾Gø¾Hð¾Dð¾D¾GP¾NP¾X¸¾] ¾Z¾U¾T¾X˜¾^ø¾hx¾x¾ƒÐ¾‚4¾q¾^¾_¨¾m(¾sø¾q˜¾nоu8¾|€¾{€¾o¾] ¾TȾU@¾Y(¾cˆ¾jà¾oȾrø¾yÀ¾}P¾} ¾|`¾{`¾z(¾uȾx@¾´¾Š ¾’L¾Œ`¾L¾tˆ¾k(¾s辇`¾“$¾„¾†è¾|x¾q@¾tè¾y€¾uè¾oоgоaP¾]`¾]¾a¾XؾOˆ¾O¨¾Mˆ¾G¨¾MÀ¾Y¾XÀ¾V¾TÀ¾J¾Iø¾Vø¾Sè¾FP¾BоN ¾Yà¾S˜¾B¾5è¾9(¾Lоf ¾h@¾X ¾Vؾ[à¾e€¾w(¾~è¾~è¾€ü¾ƒ$¾‡ì¾Ü¾”X¾”`¾Ž¬¾‡˜¾‚¾„€¾¼¾™œ¾š ¾–(¾—,¾˜Ô¾—¾”¼¾’쾌¤¾†¾ŠÀ¾” ¾œ¾£È¾£ð¾š\¾Œ¾„`¾8¾„ˆ¾‰¨¾‰4¾ˆˆ¾‹(¾H¾“ ¾ŽL¾…€¾~ð¾yX¾zè¾}¾€T¾€H¾„ ¾¾’x¾“¾ ¾„оs ¾nH¾vð¾x¾ƒp¾Š|¾Œ ¾‡œ¾ƒ¾Ø¾}¸¾x¾w@¾t ¾wH¾€d¾„P¾‚оƒ,¾ˆ´¾ˆü¾‚|¾y(¾vð¾{¾„¨¾†¨¾¾„œ¾¬¾”̾ˆ¾…D¾ˆ¾…ȾŒ¾•ì¾”À¾Ž„¾Š¾‡Ì¾Œ|¾—´¾¾–ľÀ¾“ˆ¾”€¾ŒT¾„l¾ƒÄ¾ˆp¾ˆ¾“H¾’¾¨¾†(¾{ ¾h@¾c¾n¾{x¾€Ì¾ƒ¾‰d¾‹X¾†t¾|@¾lh¾d(¾dȾmX¾r˜¾oоip¾u¾„8¾ƒ8¾y¨¾dˆ¾G ¾7(¾> ¾Uà¾o`¾|¾m`¾WÀ¾Op¾T¾^x¾]¾X0¾\˜¾i(¾s¸¾wH¾xp¾v ¾y ¾u°¾k ¾h¾m0¾~¨¾„(¾z ¾d0¾dð¾zx¾€Ô¾x°¾p¾qÀ¾|¾~ð¾vð¾l¨¾ih¾uȾ ¾‰Ü¾`¾‘¾¾‡H¾ƒ¾~¾‚ˆ¾‰ì¾…<¾|0¾„Œ¾à¾–ì¾°¾‚H¾dè¾Qø¾S€¾X0¾`ø¾q8¾} ¾w¸¾a¾I°¾7`¾. ¾-¾/è¾,@¾*À¾1°¾7¾3¾)à¾) ¾-¨¾&¾о¾`¾,(¾< ¾?à¾Ap¾D¸¾K ¾Q¸¾Pˆ¾R ¾N¾MȾ[ˆ¾e8¾[ ¾Sð¾a¾i ¾k0¾k¾dè¾\h¾WX¾W ¾T¾Jˆ¾OH¾^¾hà¾t8¾H¾y¾k˜¾^x¾EH¾9оJh¾[ ¾X¸¾W¾d(¾jÀ¾e¾TX¾C¾>à¾G¾P°¾N˜¾W(¾n¾x ¾l¾ZX¾P€¾Qø¾aˆ¾r0¾x ¾vоvˆ¾qà¾j¾oh¾€€¾ˆ¾Ž<¾ŒÔ¾„¼¾€¾‡˜¾”˜¾™@¾’̾”¾’Œ¾š¾¡˜¾Ÿä¾”¼¾Ž@¾’P¾•ľ”H¾“ø¾–¾˜Ø¾”оŽÈ¾Ð¾’T¾˜¨¾–ܾ†Ð¾‚ؾ¬¾—¾–h¾Ž¾…о…œ¾Š„¾‹4¾‡D¾H¾~8¾‡(¾D¾’ܾ’´¾”ܾ˜Ô¾˜H¾”´¾’P¾“¾’¼¾”¾–,¾™X¾£è¾°(¾·H¾¶L¾¬¾¢¤¾žp¾œL¾¡\¾©Ø¾²À¾µh¾²Ô¾«¸¾ ”¾ Ü¾¤ø¾Ô¾“¾‘œ¾ Ø¾±T¾°˜¾¢Ü¾š¾›¾žÀ¾œ¾˜,¾•˜¾—@¾–€¾‘¨¾Ž¾ŽT¾ŽP¾ŒÔ¾…ä¾z¨¾”¾Œ¾Žü¾ƒd¾^x¾P¾`¸¾n8¾s ¾| ¾ˆØ¾‘L¾Ž8¾€ ¾aˆ¾[оqྴ¾ƒ@¾„H¾Š<¾ ¾È¾¾† ¾{¸¾q¾m€¾r¾H¾‰|¾ ¾Š¾…|¾€ ¾w€¾xؾƒÄ¾‰ì¾Št¾…ˆ¾ƒÔ¾ƒ¾|ؾs¾o¨¾qH¾`¾ƒÈ¾€Ô¾~H¾tؾd¾Xà¾R¨¾R`¾\ˆ¾j¾l¸¾s€¾w ¾m¨¾_¾OؾNH¾U¾V(¾Z¸¾a8¾eȾl@¾sp¾ip¾YоMx¾L¾X¨¾i`¾up¾r¾k¾f8¾f8¾_p¾W(¾Xè¾Z¸¾R°¾NȾMð¾N0¾S¾SH¾O¸¾S°¾Xð¾`(¾Wˆ¾C ¾CؾXȾlè¾a¨¾Pp¾Z8¾q@¾yоeX¾M ¾D@¾R¾fˆ¾qà¾wp¾y(¾w ¾mX¾mX¾yX¾w°¾d¸¾Y(¾e¾và¾{¨¾r`¾n¾xø¾}Ⱦk¾Hø¾Ep¾^x¾mؾið¾bÀ¾a¸¾h°¾n`¾h@¾Z¾UÀ¾b¸¾q¾y¨¾mø¾S˜¾?ؾF€¾dH¾w¨¾hȾPà¾?X¾2¾,€¾,ø¾1ð¾3X¾3¾2P¾(о)P¾8(¾D¨¾3x¾¾h¾¸¾,¾,°¾°¾X¾ h¾@¾p¾x¾о"¾è½ë°½Ð½ì`¾ À¾+¾B0¾@8¾/@¾+ˆ¾0¸¾-¾'@¾P¾Ⱦ6ؾO¾Vè¾Kø¾;h¾0¨¾*о0¾:˜¾?x¾8о-€¾.Ⱦ8оC¾Cè¾=€¾,h¾0¾h¾ø¾ˆ¾0¾8¾X¾ о*¾˜½ÿÀ½Ü`½Å½®€½ªÐ½½½Ê0½Àð½§Ð½`½Uà½-@½'`½,`½F@½k ½’p½ ½P½‰ ½i`½‚ ½‡P½°½@½†p½€½¦P½ªà½™@½“ð½¤à½²P½»ð½®½‹Ð½Š½¿Ð½ðнì½Î€½·@½°à½¹ ½Ó½ñ½þð½ö ½áP½Ë0½Á@½Ê0½Ì½¯@½¡À½ºð½Í`½Ó ½Ä½Ž ½0 ½ ½À½6`½F`½L@½;à¼î¼u€¼(»à;Å<©€<ØÀ<Ù€<*€º¸;ƒ<Å=E =G@=@<@<ªÀ=$ =a€=i@=L =;== =`@=|=e`=a@=r=[€= à<ÊÀ= =t =‘°=‚ =6€=€== <í€<ð€=$=EÀ=yÀ=¡0=¥à=y€=9=" <ô@==YÀ=–`=žP=‰=p =G =IÀ=[à=@À="à=  =< =ˆ@=­ =¬à=u`=-@=^ =‘@=ˆà=j =uÀ=‘0=š =„ð=P`=@€=_`=} =x ==‡=u@=‚=’@=~@=FÀ=5 =YÀ=Œ =½ =âÀ=Úp=ªP=À=ð=‡Ð=Ð=À=¡0=Â=ÝP=Íp=³`=©Ð=•0=’=­ð=Ï@=ì =í°=Ü=ëp>=ÿð=â =Â=À=ã=þ€>ð=ü@=ãÀ=Ó0=Ï=½0=±€=¶@=¼@=¹€=°À=Äp=ÀÐ=ŠÀ==`==à=ƒ =¸P=Æp=°=¡p=¥p=¿=¿Ð=’P=Z€=v€=Æ@> ø>8=ùp=Ø=ßÐ=åp=Í = Ð=—p=Ç >À> (>°=í =Ú°=á=á =Ø =ܰ=ðð=ÿÀ> H> ˜>0Ð>4>">€=õÀ>¸>+˜>2h>,>*à>/ >+8>ø> (> >&€>%0>è>(> p>2x>(0>  =ñð=ü>`> °> >ˆ>>>> à> >Ø>ø>ð>>* >CX>U >H>"@>Ø> >1>9°>9>7H>5P>-À>'À>#0>¸=þà=ø`>€> `>;>=h>4è>ˆ> >È> >$8>5¸>3ð>/À>6`>B >Np>Jp>1 >H> ¨>#è>I>Zø>Sð>D><è>7h>$è> >(>*H>7Ø>>Ø>@À>?h>=˜><Ø>;>-x> >*8>Ox>fP>bà>Uh>P˜>R¸>R>Cà>>H>P(>[`>\x>a€>j>]è>8˜>$8>2>R8>^è>P€>J0>PX>V8>W8>R@>KØ>Fx>M@>\€>gx>n>iP>U8>EÀ>M >]Ø>_>Z >\X>cÐ>i@>t >n¸>UÀ>Hp>UÐ>h>h°>f(>i>l>p >sp>t >kp>eX>b>`Ð>dà>mh>t@>s8>zÈ>€$>|ˆ>zP>y>|ˆ>„°>$>ˆ>‹Ü>ŒØ>“4>ž >¦´>¤h>œ>™Ä>¡Œ>§x>§>§°>ªœ>®>«ô>©°>£>¡Ì>¥Ä>¤p> Ø> D>¡”>¡ > t>Ÿ\>>š\>š>–L>è>ŽT>˜À>¢ >£>œ0>—Ì>˜h>™¸>™°>°>¥l>§„>¦>¥¼>§|>«`>ª|>¦D>©>­Ø>­À>­¤>®@>«>¨¼>¨P>¨¸>­ø>²>°Ì>«Ä>©>©è>«ü>­<>¨Ü>¥è>¦¼>©$>ªð>ªì>¯h>µÄ>²P>©ˆ>§x>®ð>¶Ü>ºð>º >¶ô>¸Ü>¼ >ºÔ>·>³”>®Ø>©>¤>£Ü>¦´>«¼>®Œ>ªì>¤Ø>¡Ü>¤Ð>§x>£ð>žŒ>Ÿø>§È>¬ì>®ð>«¤>¨œ>°¬>¾x>„>¹$>­À>¨d>§>© >¯°>¸>Àp>Æ0>ÄP>¹<>¨¨>ž >Ÿœ>¦ >®Ð>²¤>®¨>©@>¨>§„>§|>«ü>«„>¤ø> `>¸>œd> `>«Ä>²|>³0>°Ø>©Ø> ì>¼> L>¤h>¨(>§\>¤Ø>ŸT>š`>>¢ì>¤Ø>¤>Ÿô>– >“L> >¬0>°>«Œ>¡œ> ˜>­t>ºÄ>»À>²0>¦°>¦@>¬ì>²°>¶°>¸Ü>µ>±0>·t>Â$>À(>±T>¦à>®>Àè>Ô>´T>«À>¯|>¸t>½Ä>¹ >²¨>°À>¨d>ž\>¢d>©x>¬@>­ >¬À>ªt>©Ì>¨>¢¸> >™D>•À><>‰°>Œ4>—ì>œT>–Ø>’>‰>P>t>p8>qP>~@>ˆ¬>ˆh>‚„>„Ø>Š> >Œ$>…D>Ô>„œ>ŒÄ>›<>¢>l>—>h>Ž˜>‘ä>•ð>—d>’ü>è>ˆÄ>Œ@>˜Ð>ŸØ>–l>à>dp>l˜>ˆÜ>’Ä>ŒX>x>}`>„x>…˜>ƒ`>ƒ>ƒ”>…„>‡ì>‹>Œ>‡Ì>}ð>mð>o€>{>ƒL>…ˆ>‚Ä>yÐ>j0>^p>_(>m¨>tÈ>d`>U8>Z@>l¸>ä>‡|>P>]ð>Mx>Jà>BH>Fð>]ˆ>oP>sÈ>mH>^˜>N >B >8 >+°>(h>>>^˜>sH>t >_¨>>>&h>(Ø>8€>B >K0>MØ>Dð>E>HÀ>E >,0>>"°>6à>?ˆ>@p>BÀ>AH>: >2>*¨>)>2ø>G >U>F >3>:H>GÀ>D>+@>À>>:>V@>P¸>: >-p>- >2P>0ø>)¨>,>7>CX>CÈ>8ð>3ˆ>;x>Ax>7P>!> >%@>0ˆ>0>%@>>p>p>>+0>&h>X=í`=Ú =ê=ó=î =î@=âÀ=ÕÐ=á°=æ =Íð=À°=ÌÀ=Ô°=×Ð=è=ù€>€>(=ô0=Þð=Ýð>h>8> >@> x>0> H>à>!h>8>#H>,h>(à>>Ø> 8>,È>1X>h> à> À> °> >@>h> >¸=ò0=âp=çÐ=ñ€>> ¨> ø> `=öð=Ò°=Ü€=ñÐ=íð=ê@=ñà>h>h=ÿÀ=Ï=Å =ë`>Ð>H=Ûð=Ø =ÿ€> 0>¸>ˆ=üP>Ø>È>°=í€=ô =ü =ð=ÿ°> ˜>0>`=Õ€=Ï =ñp>è>#>ø>Ð=ýð> > >ˆ>è>Ð>#È>->( >@>h> ø> >°>h>>)ø>-H>!È>(>(>"Ø>& >0>¸>Ð>Ø>+¨>4ð>'X>>$x>+ð>+X>`> =÷À> @>'ˆ>@X>CÐ>1È>p>P> °>¨>Ø>H>% >.¸>2˜>*ˆ>À>¸>'ø>'h>!p>Ð>>p>È>> X>#À>'0>ð> Ø>ð>Ø>0>@>H>Ø> >x>'h>$ð> >À>'è>&H>°>P>€> >)X>0`>3(>0ˆ>4È>9ø>:À>7¸>.X>è>à>%Ø>9¸>G˜>Mà>?È>-8>'è>08>5È>0Ð>0x>=°>Tp>W°>>¨>'x>-ð>IX>Pø>EØ>9>4`>C`>Q>Oˆ>?€>6˜><>AP>Fà>BÈ>A€>8ð>-ˆ>*>*Ð>/>2Ø>+>è>Ð> >'Ð>>p>(>0>% >%x> >> >'ð>7`>- >>>¨>& >'Ð>è> (>è> x>ð>>H>°>>> à=ú=ï=÷`> > `>ð> @>> >˜=æ=ɰ=Õ>¨> p>ø>8>Ø=õÀ=ï =õ0> >>(=èp=åp>0>(>Ø=ö=Õ=Ù =è =ò=÷à>@> X> À>>È>°>8>¸=õ@=ë > >+>'è>ˆ=Ò`=³à=¿€=è=þÀ> >>À=ñÐ=¼`=™=“ð= `=±=Å`=Ã@=°°=±@=ªð=Š=c =_=R€=D@=eÀ=ƒ°=š =¥=~ <ò€<£À=À=Kà=‡ð=™`=—p=‚0=m =„p=•€=ƒ`=<€=)@=p =¶@=ÝP=Ê =ŽP=?€=4`=?@=/€= =6à=“€=±ð=p=(À<Î@=`=0 <È€;~;ð<ô=Y =tà=FÀ<å€;¿»ìº@<‚À<ÿÀ=(=. ==€=_À=b€=P€=dÀ=‰`=“Ð=“ =£=À`=Ø€=Ïð=±ð=›p=ŽP=•Ð=ž=¢ =¹P=Í=Ͱ=Ë=¾à=œ@=q =i=…=š =¹À=á°=ë =¿P=…à=Sà=k€==žÀ=œð=ž=²`=¶@=˜0=ƒÐ=š@=©0=›°=Œð=£=Ó0=ä0=Î =À=‚€= =Ç@=Øà=Ñ =Ò=áÐ=çÐ=ÔÀ=¹P=ÇP=ã =à`=È =° =×p>(>`=ÿà=È =»0=Á€=Ñ0=î`=ü@=ç=î`>ð>À=ÿ =ëP=ذ=É=Ïp=îp> >0=îà=½°=¦°=¬=ª =§ =ª@=Â@=ë >`=ø =ö€=æ =»=µp=æp> >(>>>8>è>Ð> H>(=ü°> @> > =ôÐ=ç=ûp>`>>°>p>ø>ˆ>>P>@>€>ø> ˆ>(¸>:à>/>è>è>¸> >$ˆ>7p>7À>*(>&Ø>-°>30>* >>>°> H>ø>P>Ð>¸>À> Ø>È=öà=΀=Ѐ=í`=úP=ç =Ù0=ó>=òp=Ä`=¯=Í >¨>p>0=Ø€=ÒP=Üà=ðP=ëp=Þà=õ>È>À=ù=ÀÀ=®@=±0=›ð=žÀ=Ï>ˆ>0>P=Íà=¢=”0==p`=T =p =…@=Ž =0=P=ŽÐ=a€<Û€;t;¦<Ö=L`=qÀ=C =(À=? =5€=( =2À=4`<ú<‡<ÌÀ=Q=Ÿ0=¬€={ =  = =i`=„°=yà=]à=Zà=N€=-À=%à=U=„à= =V€= <©@è¾F¾9о1(¾+¾(Ⱦ(¾оà¾)¾?À¾W¾[¾K¾8 ¾(P¾$À¾,X¾3 ¾4h¾0@¾8(¾E¸¾G¾=0¾/¾ ø¾à¾`¾ p¾-¾6ø¾7@¾0о+À¾,è¾6è¾Eà¾C¾98¾4X¾-о-h¾/ ¾4è¾E¸¾Pˆ¾Op¾C¸¾9H¾4X¾38¾4Ⱦ6¨¾<ؾE ¾Kp¾N¾W ¾d8¾e¨¾^H¾Vp¾O°¾Lx¾O¸¾]¨¾o¨¾w(¾p8¾V8¾@ø¾F¾P€¾N¾Ip¾Hˆ¾UX¾d ¾aè¾Qˆ¾Ep¾Gx¾Q€¾R¾E°¾@¸¾OP¾_X¾_8¾P@¾B¾?¨¾H(¾Q ¾Sè¾V¾Xp¾\p¾bP¾a¾`8¾_˜¾`°¾dؾh€¾t¾…¾‡\¾{8¾^h¾Nø¾c8¾€,¾„ð¾„l¾† ¾Š€¾‰Ü¾}@¾d¾X8¾Tð¾dh¾~@¾‡¤¾ˆ8¾€ ¾ep¾I@¾?¾EX¾Lè¾T¾\8¾hȾpp¾h¾Sø¾<ؾ1h¾,°¾$X¾ h¾,P¾ ¾B€¾JؾK¨¾>¾:¾DÀ¾Pà¾V@¾QX¾DȾ@h¾Eà¾Pà¾Xp¾U¨¾@ ¾.h¾$x¾&À¾6¾M¾Uè¾HP¾'Ⱦ ¾¨¾/8¾'¾X¾(¾)0¾6ؾ"h¾Ø½á ½éP½þð½û`½úð¾H¾ð½ïнŰ½¶à½¾p½Ï@½Ý@½Õ€½Õ@½îp¾€¾ H¾À½ä½Ú€½æ½ü@¾à¾ ¾ ¾½ø½ë°½í€½ý°¾ˆ¾ˆ½à ½º0½½½íð¾ Ø¾h½Û཯@½®°½Â`½¸½¬½Ãà½ï ½ûp½Ç°½¥°½º½Õ½ÞP½ÔнÉ@½ÊÀ½Õнހ½Úà½ÔP½ÍÀ½Ð°½î¾ H¾ 8¾`½ôp½ü0¾€¾ˆ¾ À¾À¾X¾¾¸¾@¾H¾¾ð¾H¾¾¾* ¾*Ⱦ@½ñp½ßð½üà¾ؾð¾ €¾¾p¾˜¾Ⱦ0¾€½ý`½æ@½æ@¾(¾¨¾ h½ô𽸠½”P½š ½¬@½¸°½Çà½È ½³p½ª½²p½»Ð½­ð½‘p½a`½< ½Ž½Û𾈾 à½Ù@½„འ½*@½P½´ ½ßà½ê@½Ðp½Á½Ú ½åP½ÊP½‘p½SÀ½…½È¾о H½ýнͽ” ½‘½±à½´ ½  ½†@½  ½íÀ¾¾½ËP½Ÿ½ Ð½´`½¾à½Á½ÈÀ½àÀ½ý¾˜½ñ°½Ëà½Âà½Ï0½Õ°½Ù½à½ýP¾ °¾¾˜½éÀ½Èð½µð½¹°½Ãà½Ùp½éà½ì ½ìà½é ½Ù½²P½vÀ½P ½ˆP½½½óнû°½À½’ ½§`½Ä ½Û€½ß½É ½´½­ð½ºÀ½ËÀ½æ ½êð½Æ ½¢p½œ€½¾p½ç°½çÀ½ÊP½§½© ½Ép½ßð½ñ½õà½ä ½Ú ½ã0½éP½÷0¾è¾À¾à¾H½þ@½ÿP¾ ˜¾X¾X¾¨¾¾¾Ⱦ(À¾%¸¾ ¾P¾00¾Að¾@p¾1€¾0¾:ؾI°¾Nx¾D ¾3ؾ1ˆ¾> ¾Hà¾K0¾H€¾Hè¾LX¾I8¾7€¾(P¾,°¾3(¾8¾2¸¾-è¾6ð¾:о.˜¾ `¾˜¾¾à¾'H¾!¾è¾+°¾>¾F¾1`¾è¾ ˆ¾€¾!¾¾ ¾-¨¾D8¾H¾7¾!¾¨¾ ¾¾+ˆ¾*ؾ*@¾0à¾C(¾VP¾S°¾:@¾((¾(è¾3°¾=x¾:¾4Ⱦ>оQ¾Y0¾HȾ1H¾#ø¾'¨¾2p¾:@¾?¾C¸¾>¾2h¾+°¾/X¾:ˆ¾=°¾1à¾-P¾9 ¾F0¾70¾°¾ ¾°¾6ø¾6¨¾#¨¾( ¾<À¾Ip¾FX¾1h¾¾p¾ è¾# ¾(¾,о0¸¾/ؾ-¾# ¾ ½î½á ½ôp¾ ˜¾0¾#¨¾ ¾€½ýP½ã0½Ò€½ÔÀ½Ú°½áp½öð¾ð¾# ¾)˜¾ ¾@½ÞÀ½àp½ñ€¾¨¾ ¾4¾?`¾;¾)`¾¾H¾¾(¾à¾$¸¾<ˆ¾TH¾[x¾FÀ¾0¾0¾ ¾h¾C ¾NH¾5𾈾о'0¾4 ¾, ¾¾P¾P¾"H¾5@¾-8¾½í€½ï0¾`¾¾ ¾¾ؾ Ø½í ½ÏP½Ë ½Ü@½îP½óà½î½éà½äнÛð½æ0½å½½p½} ½A€½k ½­Ð½Ú@½×½¹ð½¢@½œ€½¥½¢P½ˆà½e@½Ž`½Ë¾h¾p½à@½š€½ˆP½¢à½Êà½èà½Ó€½¥À½”ཧ½¿Ð½¿À½¢@½x ½[À½–à½Ü@½ûp½Ë ½[€¼Â¼ë@½\@½`½ƒ ½H ½6 ½l ½0½‚ ½@»‰€½*`½, ½/@½*€½K`½n`½i ½U`½+@¼×@¼ŒÀ¼°À¼ë@½ ½Y½LÀ¼ó€¼.ºø»Š¼S€¼ €¼°À¼¨@¼÷½( ½€¼Ü¼•€¼"¼€¼€À¼¿@¼æ€½€½: ½#`¼Ù€¼ž¼Z€¼f€¼£¼â€½3@½g ½uÀ½X ½ ¼­@¼ÜÀ½"½D@½LÀ½U ½J ½T ½j@½4 ¼ÏÀ¼’€¼º@½À½J`½}À½Š ½‰@½m½5@½ ½ À½M€½‡0½•@½u ½ ¼â@¼üÀ½½À¼â€¼Dº@¼.€¼ì@¼çÀ»¦<“<ïÀ<½€;„¼ »å;Š<‰= ="@<Ø€»“½À½ŸP½´°½ŒÐ½Cà½à½1@½Là½&@½ ½À½;à½i€½‘མà½y ¼÷»b»¾¼Ù€½e½”½N`¼‚€»›¼‡½ À½ ¼€<­@<¸»6¼®À¼Ð€¼ª€»é<¡€=I@=I <_¼t€¼Š@»™;ϼÀ¼ÈÀ¼§@»><€»J¼ý½u ½’À½mÀ½.à½@ ½~`½™½’€½\€½ ½2 ½~½š@½—€½h@½%€½+@½y ½P½”À½u`½UÀ½E@½K½H@½L`½e`½Š€½@½Žð½“0½ƒð½Z½;€½J€½‰ ½žp½žP½•нˆ ½0½‹€½§°½§0½`½\à½5½x½š½ƒ ½?À½<½‚p½ªÀ½¸`½ž ½i`½6@½5€½f€½žp½Ã0½Ü°½Õ ½­`½Šà½Œ½™½ž`½ž0½™ ½»½êÀ½ñ`½Çн• ½‹°½«½Ð`½Ä཯`½¿à½Ï½Þð½Ý½Ìð½Ê½Ð ½ÖнË@½Â€½Ñ ½ãð½ü°¾À½õ ½ÝÀ½Îà½Ó ½Ó ½Ø½æ@½ëP½Üн¾°½¹À½Ü@½ÿ ½ï`½º°½˜½— ½¦€½¿½Õ@½ÏÀ½³à½·p½³½’À½fÀ½sལ ½²@½‘`½7à½à½@€½€Ð½`½9`½'½¼°À¼Ô@½À½Jà½y½xà½là½Y½[½i€½Z ½:½E ½~ ½Ÿ½¦p½•½Ž°½Ÿ`½©€½¨@½¤Ð½´½Ìð½Î0½³à½ ½‚À½šà½½ð½Ñ ½È½´€½™½à½€½„ ½yÀ½½’€½±½Ñ@½Ñ½ªp½qÀ½K@½~À½À½Ÿ½ŒP½‚𽪀½ðp¾(½Ãp½€½m ½˜Ð½³€½´@½¿½×ð½ê`½Ø0½´€½ŠÀ½z@½½½ƒp½uÀ½‚ ½«½Ó½· ½n½[À½|½†½Ð½¡°½°p½·@½§ð½‹ð½`½ˆp½´à½Îð½¯ð½’ ½½£½±à½³À½›@½ƒÐ½‹p½Œ½ €½·½ºp½¬ð½”н™ð½¯½¾0½ºp½±Ð½±€½¶€½Å½ÂP½Å ½Ô½Úà½ä ½Ü°½Ø½Ù½ÏÀ½Æà½Á½¼p½Ã½Úð½ØÐ½È`½Ç`½Ç½Á°½¥0½§À½ËÀ½Ü€½ç0½êà½òнô½á°½ÚP½Ø`½ä ½ñ½åà½åÀ½÷½ü€½ÿ0½õÀ½ë½åÀ½Î ½Èð½Ýà½è½ë0½ì€½Ò`½ÁнÃð½Ù0½ê€½á½ÎÀ½Ô½åð½é½Ð°½² ½®`½À0½Ï½Ùp½á½Ü½¼P½¤°½®°½Ïp½Ý0½Î½·P½© ½¥½ ½¥ ½³€½Ë ½Ø½Í½Æ@½³P½@½œP½­P½Ã@½Ì½ÙP½Ý0½Âp½³à½¿½Þнí½à½ÂུP½¿ ½Ø@½ïð½úð¾8¾x½ñp½à0½Ï0½Í½Î`½Ò`½Ú½Õ½Ù ½Þà½Ì ½­@½˜Ð½Ð½‘н¨€½´ ½ª½ž`½‹½d@½J€½<@½! ½"@½EÀ½U ½C ½¼Ó@¼Õ€¼Ë@¼’@¼¼€½9@½„`½Œ½_ ¼þ@¼À½" ½nÀ½Š ½t ½?@½4½i€½›€½›€½h ½A ½h`½Š½‰@½q½D ½Nག€½•ð½€ ½F ½FÀ½p`½@½„à½YÀ½\€½•½¾@½¯ ½c`½À½_€½¿à½ãp½Áp½p½=à½i€½¥ ½½ ½¬p½’½‚À½ƒÐ½Ž@½“½‘ ½‡à½‚½‚°½€@½Š@½£0½p½`¼v¼8½@½N ½3½`½à½F`½o€½Hà½3@½*`¼Þ@¼—¼Ë½9ཽ™½eà½À½À½#`¼û¼É€¼æ¼öÀ½ @½ ½ ½ `½3`½ `¼ ;Ö¼z½@ ½J`¼ù€¼U¼žÀ½9½ð½t`½1@½@½1 ½‰ð½­0½›½6 ¼^€¼½@½p½¢ð½Žð½J@½@½@½N`½7¼Ô€¼1¼›À½Q ½§€½´Ð½§°½™`½|@½€¼„»b»Ô½`½|@½U€½  ¼Ö¼ä¼Ã»|<ÊÀ=TÀ=ZÀ<ÉÀ¼F€½€¼à€»X=€=QÀ=@À=; =a@=a<Ѽp€¼åÀ¼ <ê=n€=Šà=k =àº`¼œ¼‹»¢;V;‘<†@= = <‰@¼¼¥€¼§¼³À¼¨¼V€;H<ÐÀ=<šÀ¼l€½4 ½g½ÀºÔ<<.<(»Ý¼˜À¼Å€¼ù½ `½)`½0 ¼x<Ÿ€=<Ê»ä½À½J@½,À¼ñ¼À€»¤=À=š=˜=`»¼Á¼™À»J<†@==t€=› ==]`=N=$@ø=ð`=Ò`=Ë=É0=Á =¸0=·@=Óð>  >-€>;`>!(=ã€=ª0=¤p=¯`=»p=ç`>@>EÐ>L0>.ø>˜>ð=ëÀ=ɰ=Ñ€>€>)X>?h>B¸>>ø>60>'°>€=ú =êà> >`>0ø>-ð>@> À>x>€> è=ôà=Ò@=Ö€=×=â`>p> È>Ð=òÀ=Íp=¶°=¿p=ÛÀ=ë€=ö >>=ñð=Ä€=¤à=·€=øp>¨>#p> =êP=×=Ø@=Ýà> >p>2°>.0>°>€>0>.ˆ>4H> @> p=ú>>$Ð>O8>`À>J€>ø=õ>È>>&Ð>+>+€>5¸>BÈ>D¨>?ø>.ø>È>  >(>,p>9@>B@>A0>9Ð>7 >9Ð>9è>:0>4˜>-˜>0>D>d(>qÐ>\P>A¸>:°>E>X€>aP>Yà>\>iÈ>` >Q >Wð>k@>z˜>sÀ>Z€>I¨>PÀ>r0>†0>ƒl>iˆ>YÐ>^˜>k>wà>y>vX>x >uÀ>qØ>n`>p0>‚¸>Žt>>ƒø>ƒ¨>Š8>“|>ì>~>l >} >’„>Ÿ¤>›¼>Ž>ƒl>~˜>z>P>‹¼>’X>Œˆ>…Ü>ŠÄ>Ô>Œð>…œ>v >pˆ>|>†è>ŒÐ>‰h>‚>€x>€Ð>„>„>| >u0>w>è>‡Œ>Œˆ>ˆü>uH>ZØ>c>‚4>Šè>‡”>vH>e>fP>_>QX>P˜>c>q@>lø>aˆ>_p>a€>aˆ>]˜>T¸>J>F>I(>YP>n`>€>‚(>kð>Tp>P>Rp>` >j°>fð>aX>hØ>l >eP>dh>[Ø>L0>G¸>Oˆ>WX>S¸>F >:ð>F>[x>\p>Bˆ>/H>=€>N8>PP>Nˆ>R`>Qˆ>H˜>AÈ>?h>I>]x>mh>pˆ>o(>e¸>[P>[È>_`>YÈ>L >I>VH>fÐ>mÀ>dÈ>Z(>X€>O€>?`>A¨>Hè>G >G>Hø>L@>_>o>g>Nø>2°>$`>+>8ð>Mø>\è>_Ø>[>KØ>5X>$Ð>#ð>/>8x>?>E`>D>Hð>Nè>CÐ>-¨>à>`>* >4ø>3È>0È>5X>?À>=`>(H> >> > 0>À>(Ø>>°>G>?h>(X> h=ìð=ì>è>à>1¨>6`>`> 8> `>€>"¨>È>@=ûÀ>À>>>Ð> >Ø>%è>#P>>Ð>À>ˆ>0ˆ>/H>$h>* >=(>MÐ>Tè>Ið>= >/>!À>)ˆ>H`>Jø>Gp>A>E8>L>H(>>>; >I¨>Yð>Yˆ>M¸>B°>B(>KÐ>S >Ið>>À>? >I8>QP>R€>WÈ>aÐ>ex>`P>W >Vˆ>cÀ>q@>sh>op>kP>r>|>w¨>kX>_p>]€>_ˆ>gh>rh>x>‚Ô>„Ü>€p>px>^0>[>nø>…>‰>`>vÈ>oÐ>m8>jp>fø>V¨>H8>HØ>Mà>X¸>k@>v>`¸>30>> x>>0@>3 >08>+¨>2x>2@>%À>=ë`=Øð=ê> `>!ø>/x>/˜>!@>0>ø>˜> ¸> @>È>¨>.>:x>F`>?>&X>ð> X>X>- >:Ø>F(>R>O><`>1 >7˜>Ið>OØ>A@>,>1>GÀ>W˜>YH>IÀ><Ø>Dh>?À>.è>,p>1À>3>7Ð>5`>30>7>6Ø>8>7>.°>.(>8à>Hp>O@>DØ>0H>&>8˜>P>W8>YÀ>P>Cp>@`>Gh>T¨>[P>]>[ˆ>Xà>b¸>p`>j>N€>G >W8>i>p>b¨>V˜>T >UP>V>W >a˜>rH>tx>eø>bØ>s`>|@>rx>l°>(>Žä>”>Ž˜>…(>Ä>†>Œ>Œä>†>„ô>ì>—$>˜ô>—Ø>–ˆ>–Œ>›ä>œÄ>—>’>¬>”°>žX>¦”>«<>¨>ŸÈ>–>‹|>…¼>T>šà>£h>¢¨>š>”\>Ð>‰ˆ>‡(>Ž@>—Ð>š„>˜>‘p>’¬>•Ì>‘Ä>‡˜>‚<>‚À>†>ä>•T>—Ì>˜Ü>“>‰(>ˆ >‰H>ˆˆ>‡¬>ˆ>0>›D>Ÿ,>šœ>“<>Œð>‰<>‡x>„4>‰>˜\>§¸>­ü>¥$>•´>‹X>Œ¨>>‡h>‹¼>œ>«è>­œ>£ô>—L>‘8>D>ˆ$>€(>‰ì>›¼>¥ø>¡è>•X>Œ(>Žì>–ð>’¼>‡Ä>‡$>”„>¥d>¬0>¦à>ŸÔ>Ÿ> à>¢¨>Ÿp>›t>Ÿ”>¥(>¤>¡ä> P> >œ(>“¬>Ø>Œ>ŠÄ>‘>šD>™P>’@>…ä>ux>vð>‚Ä>„ø>…ü>Š>à>Œ”>…¬>¸>{Ø>r¸>uÈ>´>|>¼>‹t>‡ì>„À>„>p>€ >…ð>D>‘>‘Ð>H>‰ >„>ƒx>†”>‹œ>Žx>“>•H>Ž >ˆ°>Šü>‘€>“˜>Œ>‚ä>„”>¨>•>‘¨>ŠÌ>ˆ$>ˆ„>„ì>ƒ`>„À>…x>„|>‚¼>‡l>ŽØ>”°>“ä>ˆ¨>z>q¨>u°>‚@>‹˜>ŒX>‚À>€ä>‰$>è>Œ”>€ô>c°>R`>h0>„ô>Œl>Šô> >dà>_>gÐ>n8>lè>aà>V¸>QÐ>Wø>i`>rp>dX>P¸>Cè>CØ>Hx>QÐ>_ø>gØ>j0>^ˆ>Ið>Eè>M˜>T`>Vè>UÀ>UÀ>Zà>bÈ>fÈ>aÈ>S(>F¸>AØ>D>Rx>[¨>X`>Wˆ>U >N>@x>40>2X>B>S >W¨>VÐ>Wð>Wà>N >B€>F8>[>lx>oP>e>Wð>Kx>A>;ð>;Ø>=ð>?€>L>]`>l >l`>R8>1h>#>/¨>@ >Pè>d˜>o>`><è>*€>+¸>8x>J8>E>7X>4°>=à>Bˆ>7¸>,À>,À>6¨>:@>.X>&¸>+ˆ>1`>*ø>x>@=û°>>P>1X>5P>& >ø>È=ï°=ó€>h>>*@>1>)>¨>X>`>ˆ>@>!>"ð>2x>=¸>9¨>?@>R>Yˆ>Kh>4€>,>Aˆ>` >nà>kÐ>_Ø>a¸>m¸>pø>f>aÀ>fð>m >qP>h°>eÈ>gÀ>iÈ>t >}8>ƒ\>ƒ$>xØ>j>bˆ>c >a(>b˜>iH>m€>{>…0>‡L>‚€>sØ>hH>b@>fÈ>h`>nÈ>¨>†à>‰¸>‰ä>†H>€ü>|À>tØ>u°>€\>‚¬> >‚,>…ˆ>‡\>‰ø>ލ>>>‡À>†>…0>€È>|@>‚„>‡ô>l>—¼>”\>ˆ>z˜>n€>j¨>qÀ>y0>wð>{ >€ä>{À>pÈ>] >;Ø> >%ˆ>H>cP>gˆ>Y(>C >8h>1Ø>.ð>,H>#0>8>'°>68>G>V0>RØ>9°> =õ >8>>%€>&€>/ >50>3h>3@>*¨>ˆ>@=ä =è@> ˜>2>Fˆ>F>6ø>$x>ð>à>°>¸>ø>€=ñ€>˜>$°>5à>Ð=î°=äÀ>è>.ø>%€>p=ä =éÀ> ˜>#˜>6`>5È>)>Ø>(>À>ð>ø>À> à>h>)Ø>5`>'Ø>Ð> ø>H>$ >>À=è>¸>ø>h>p>ˆ=é=Ôð=Ï =Ò=áð=ô=ø =ñ =× =¸=¹ =Ùð>Ø>ø>P>@=ì€=ª=œ =»=ô =ôP=Åð=³Ð=à > ¸>è=Å0=n@=:`=c`=°=¡ð=¼=ã`=ã@=¿`=“À=@=‰Ð=–°=—p=”ð=“p=²=ïP>è=Û=®=Œp=q@=…`=•ð=–P=”p=´@=Óp=»`=…ð= <¥À<Œ€<|€= =(=@<€;»ö¼€;<^€€='€='À=Fà=t =u =4= à=G€==œ€=… == =`=À=<À=\@=v =Ÿ°=¦=c <Ó€<2€<¸À=I=ŠÐ=|@=8À=.À=] =ð=•ð=à=,@<¸Àº„º€;€<à= =•=Pà<¬€»õ¼j;<çÀ=0='À=@=9À=Š€=š =e@<Û€;; <ô€=@=§À=¦ð=~à=I=€À=¶0=×=Ôà=¯0=Žp=¡=ÎÐ=ïp=Ù@=¼ð=È`>Ð>$È>&˜> =È =§p=¿p=é0=ö=éP=æ`=ö@> > ¨=þ0=áà=«ð=†=œ=É=í=÷À=ä=Ê =½ =¾€=Ê=×P=Π=º =²à=µ =ÇÀ=Ð=Úð=ç =á0=Æð=¹=Ö =è =ã=ç@=ÓP=±à=­ =¸`=¾@=Çà=á0=ÿÐ> x>€=Îð=«°=‹ð=_à=m=´>>8=ø = =# =@=C =‰0=•°=Ž=”€=º@=ù€>  =Ù`=~À=)`=DÀ=‘°=ÖÐ=í =Ö=»€=±à=ð=Ú°=âÀ=ÊÀ=“€=[`=wÀ=¾ð=þ`=ý0=Õ =¼°=Í€=ö`=û =Ø=ÃÀ=Á=×=õP=÷>@>¸=öP=å@=ü>>%(>h=ç0=Á =Ѐ>¨>`>˜>Ð> Ø=÷ð=Ü =Êà=À =» =º0=à =í@>ð>X=øà=õð>P> È=øp=ÜP=è >À> à>=é`=ä0=ö€>>˜>€>>°=áà=Å€=Ì =Ýð=ñp>à>è>P>p>p>x>ø> 8>>˜>@=ø >x>°>-h>G>H8>/0> ø=ø>à>p>@>¨>ø>3h>@ >2€>@>ˆ>p>"`>X> è>X>ˆ>0>/x>> >;¸>.ð>x=ø =óÀ>À>6x>5>¨>P>X>-¨>I>G0>+X> @>X>È>:h>B>6x>#H>(> Ð> >$È>3Ø>Oø>_>P˜>.H>>!°>7p>@>=x>8Ð><è>F>Dp>7P>(¸>>>!¸>1 >8Ø>7p>3@>6è>3`>)˜>%>*>0€>/P>- >2>D€>Sp>N >8X>$ >+à>@À>N€>R0>N¸>VX>^ >\à>Uˆ>J >A0>F@>_>h>”>>‚ü>mp>^>]ˆ>d€>rX>ƒÔ>Ž,>‘>‰´>È>u˜>n>n(>o`>p`>lH>mð>s >p˜>vØ>~ø>|ˆ>m€>Th>A >M`>q˜>‚\>v >](>GP>>ø>E >Qx>X>_>h>l°>gÀ>Yð>Dð>2X>3ð>S >y0>…Ø>‡¸>…0>s(>_p>_H>gÐ>o>sX>u0>|À>ˆ|>”à>™l>“ø>…ð>rx>r¸>‰Ì>šØ>›Ä>,>‰>Ž(>‘`>”$>™ >šÐ>>£>¤Ì>¡$>Ÿ>Ÿ˜>›€>–t>—>žh>¬ä>¹>¸”>¬>¤,>¦Ä>§˜>¥´>¤L>¨$>¯>´p>¸ˆ>º¬>ºp>·¸>°8>«x>©d>¬Ð>·¼>¼è>µ >ª@>©8>¯ø>³\>©à>@>˜Ô> ˜>±D>·h>®ä>¡¼>•ü>‘Ì>™x>¤>¬D>² >´°>²¸>­¸>¬0>ª0>¤¤>¢h>¦>¯4>¸>½d>½À>¾ð>ÇÜ>ÇŒ>¹X>¬H>ª<>´ >Ád>ÉÜ>ÎP>ÒT>Ò>Ê4>ÀT>¸¸>¸ì>»¨>ÀÄ>ÍL>Ûè>ݨ>ÓÈ>È>½ø>¹¸>¼>»|>º8>¾H>Å>ÌÌ>Θ>„>®@>£>¤d>«8>³¤>¹>¾L>Ä>¿P>°<>©(>¦>£Ä>¢>žL>£>­Ä>·>¾Ô>½„>­œ>™ >“>žÔ>°>½>»h>µ\>´>¶Ü>¸¨>µl>°´>­`>«ô>±Ì>Àð>É8>ÃH>¼d>µh>®h>¥ô>¤ >¬ü>¸> >Çp>ÉX>Æ„>¾>µ<>®Ü>±Ì>¸(>·Ä>´>¶>¸H>·`>¹d>½Ø>¾$>¹ð>µH>­p>£Œ>¢€>ªL>±ð>»p>À(>¾ >¾<>Â>Àô>¾ˆ>¾ >½|>½ä>¾h>¿<>Á˜>¾0>¶¬>³Ì>¸p>ÃÜ>ÌŒ>ÈL>·>¦d>žŒ>œÈ>¢ø>²@>½ø>ºˆ>« >¤Ì>³¼>ÆÐ>Â,>¢À>‚”>|Ø>œ¸>¨>Óô>Ò`>Ï`>Ï >ÊÄ>¼(>¦<>”$>’˜>§´>ż>Ûä>ç´>èÌ>ÜH>É4>»´>²>­h>±X>»H>È>ÚH>ìè>ò$>â¼>Äì>¯ >®¬>¶´>¿T>È|>Ò¨>Ý(>à”>Ø„>É>½h>»H>¾°>ÀÀ>Á¤>ÂÔ>É>ÏT>ÓT>Ò>È>¸¬>±>¸È>Ç”>Î(>È>½Ø>³ô>­Ä>©8>¤0>©è>ºp>Æ”>ÃÔ>·4>¨ˆ>>”°>•„>žô>¥Œ>¦Ø>¤Ô>¡ >¤P>±<>»@>¸Ô>® >œì>Šà>‡>–¤>±ô>Çœ>È8>º„>²0>³>®è>¡°>”¸>”è>¥T>µˆ>½„>Ã`>ÆT>Â0>² >™¬>°>”ø>£”>­P>®¤>ªd>¨ˆ>®T>²L>©>œÌ>•`>˜>žð>œ€>—>—°> d>­p>±ä>¥p>‘d>ŠÈ>x>–Ð>œL>¡@>£>¥(>¥Ø>Ÿ >˜(>›È> €>¢> Ä>ž°>¢`>ª,>°x>±h>µ<>¸Ø>¶ >°Ü>¬t>±>¹ü>¿ˆ>ÁŒ>¾Ä>¹„>²>¸”>Ã(>¸>¿ˆ>¹Ô>´,>µ”>º¬>ÂÄ>Äx>¾$>³>²>Áx>ÒD>×p>ËÈ>¼€>²¬>µt>Ȭ>Ù´>Üh>Ì€>»t>Ãä>Þð>ñ@>éh>Ò”>Á”>¿P>Ë8>Øø>ßè>àä>à,>ä|>è¤>à„>Ðà>ÅT>¿d>»>½H>É>Û,>ã>×p>È >ÂŒ>¿Ü>¶ >«˜>©D>¨Ì>¯È>½ì>Èô>Å(>´˜>¦Ô>Ÿ>›¨>¡Ä>­<>·p>ºÜ>¸0>³|>²>ºà>€>¾ˆ>³ˆ>´ä>Ã>ÎÜ>Òø>Ð0>Ìð>Êø>Å0>¾> >Ö>çL>ì>äÄ>Ѱ>¼¼>²>·L>ÆH>ÒÔ>Ó>Î>Ð\>Ô@>Ö”>Í8>¸ >¦¸>¢ü>´°>Ì´>Öè>Ñô>ËH>Á>µT>«à>¢Œ>¦H>¸4>ÈÀ>ÕÈ>Ý>Ü0>Ò¤>ÇÜ>¸¬>¯$>³Ä>¾l>Í >Ù$>à>ä€>åÔ>Ú>¿h>­”>«Ð>µ >Çè>Ý>ìH>ê0>ÙD>ÄÐ>·ü>´D>¼8>Íä>Ûˆ>àÌ>Ý@>Ñè>Ê|>É>ʰ>È>Ä<>Âè>Ã@>Є>â°>ì>ä0>Ò4>Ä(>½>º>¸´>¾$>Ð>è<>ô>éà>Ô0>¸(>¨D>­`>¹>˨>Ý€>ê>ï°>èÐ>Ø8>ÄL>·Ø>²>´(>Ä >â>ôä>éà>ØÀ>Ït>ʘ>Æ„>¿˜>¸x>µô>ÀÌ>ÑÄ>Þ8>ßô>Îd>¾>¸>¹ì>Áè>Âà>¾`>¾”>¿Ð>¸d>³€>ºH>Æ>Ř>¹>µ¼>Âð>ÐX>Ë>³<>ž|>ž,>²Ä>È>Íô>È4>½ø>¾>¿Œ>³Ü>©T>© >¬¬>©D>¬¼>¿l>Ô>ج>ÃØ>®,>©¨>®¤>® >§>£œ>¨8>­à>±>»>¿„>«L>‘Ð>Ž>ž|>§œ>¢8>è>¢ä>¦À>£`>œ€>ž”>©\>ªx>¤¤>§(>³Œ>¾p>¹X>¦x> h>§T>¬|>¸8>Áè>Æ>Ð4>ÔD>ÅX>°œ>¥¤>­ >¾|>Ëð>Îì>Îð>Ô\>Öø>Ï\>¼>¸>°t>« >ª´>°¨>¹H>¾ >ļ>Ë`>É >¾¨>®|>¡¨>0>˜¤>š>§¸>¹H>½$>µŒ>¯„>®Ü>§>’<>€„>‚à>˜˜>°´>·˜>ªŒ>š>™l>¢>§Ì> ð><>ƒŒ>ˆ>œ¼>©@>¥|>Ü>™È>™¼>–è>‹>…,>Œ>—˜>”¬>Ž>ˆ”>Œ>Ž,>‰´>†>‹>—l> >¡ˆ>™ >‹@>|¸>h°>o°>ƒð>x>p>ô>”È>•ì>“Ô>Šh>‚h>À>|0>u>€ˆ>‘ >¤(>­D>ž”>„`>{@>…¼>Œx>‹><>wè>„¬>‘d>–Ô>—$>¤>‡ä>€Ð>x>¸>Œè>—$>—˜>”h>Ü>…t>‚@>‚x>ƒ¤>†À>Š>‹ >ŽX>°>ŠL>v >W@>T>r >Ø>žÈ>¦|>ŸD>>ˆ8>ˆ >…,>€H>tx>tx>…0>—ð>¨Ì>±ˆ>¥ >‰(>n>pà>†à>“È>–\>”Ô>•´>—¤>•”>l>ˆp>wØ>fx>gp>~ >‡ˆ>ˆ>ˆä>‹h>>h>†`>vx>h¸>mh>vÀ>{>€,>…´>ˆø>„t>p>Xð>Mø>K°>Y0>s>¸>€À>vÀ>l8>l>b >]>oè>‡ˆ>‹Œ>… >v¸>b(>a>k>oh>t0>|€>€\>z`>x¨>y>xˆ>t>jh>i>xø>‰x>H>†8>hX>\p> >–`>”È>€ü>[¸>RP>e>„Ä>˜>žh>—D>‡@>yˆ>ƒÌ>Ü>x>|>“ø>D>¤Ü>£X>Ÿ >šà>•ô>™T>£>§d>¢4>šØ>“ˆ>’`>“h>’à>–H>›Ü>˜Ô>ˆÀ>pà>eà>px>‚8>„ä>€4>x˜>yx>z>m8>Yˆ>Q¸>R˜>Y`>e >g>[ð>[°>hØ>nX>d8>OØ>H¨>Mp>Xà>s¸>…È>¬>ex>Pð>]€>và>…”>ƒ>o¨>hà>w8>ˆŒ>“`>–´>Œ¤>p°>Z@>]¨>m8>y°>‚à>‡>†>(>q >gÈ>X¸>=>*ø>5`>Y>r>kx>V¨>I€>D¸>>@>3`>(ð>Ø>> €>`>4°>Gè>? >% > 8=ß0=À°=É@=ò=þ =ïÀ>Ø>">:ð>2> ¨=Èð=–=¢À=Ý`> x> ¨>x>ˆ> H>>(=ÅÐ=ˆ=‰€=ª€=Ø> ø> >ø=âð=Å@=ï°> ˜=ýð=€=à=Œ =È`>h>1>+`=ð =„ð=/`=kà=£ =0=‡@=F€=H@=™À=ÉÀ=Ïp=›Ð=<˜=  =p =Œ=“ =Œ`=‚=@=†=ƒà=AÀ<ª:Œ;å=à=J =À<¨<;€¼šÀ¼›€¼ŽÀ¼ê@½l`½ŸP½‡ ¼×@<—=<¶¼=€½K ½‘н½W½¼ø@¼Å@¼;Ú;¼þÀ½£½ã ½õ½á½©½:€¼¼½ ½Œ ½Ö½ù ½ø0½ìнî½âེ½„À½F`½g ½¬À½ë ¾à½ú½Ù@½Ö0½À½ˆ€½hÀ½Œ°½¬`½º°½´ ½žÀ½Š½~½€à½y`½1@½ ½+À½k€½ŠÐ½ŠÐ½tÀ½I½EÀ½?€½"@½J ½o`½p`½…н¦Ð½Èð½Ã°½¥½‹Ð½žÀ½ÎP½Þp½Ê0½¶à½É½ìо€½ç½¸à½­À½Á0½Û°½à€½ç°½ñ½ì@½èP½Ü`½Ù0½çÀ½ýp¾ ¾¸¾X¾¸½Ýð½»°½¶Ð½í@¾P¾0 ¾.¾ø½ùÀ½ëнñ0½û ¾Ⱦ ¾ˆ¾.¾10¾#x¾оP¾¾`¾H¾¾ à¾4¾8°¾+¾`¾h¾`¾à¾¾Ⱦ¾/оEð¾Cؾ/о¸¾ؾؾH¾'è¾@x¾[(¾pȾ|`¾yоm(¾`ð¾QÀ¾E(¾IоY¾j¸¾€ ¾‡h¾‡¾8¾r¾^ð¾J¨¾=8¾=€¾N(¾h¾}Ⱦ‚`¾x¾bp¾W€¾L¨¾< ¾E€¾bè¾l¨¾X¾Jh¾\H¾s¾{ؾpX¾T¾?€¾9°¾@оW°¾vо‡,¾€0¾P0¾,¾-ؾC ¾V€¾T`¾G°¾Jà¾`€¾eð¾O¾6¾'p¾) ¾:(¾R€¾_h¾W¾<¾о ¾?0¾X°¾N¨¾/ؾ¾8¾1ð¾O¾^¸¾PH¾-ؾø¾0¾Zð¾ex¾H¾/°¾2@¾H¾V ¾[¾\À¾d¾sx¾s ¾l¾m¾lè¾f0¾\H¾VX¾O˜¾Y¾kè¾u˜¾xȾ}¾‚<¾wÀ¾Oè¾+ ¾'P¾E@¾lо„¨¾ˆô¾l¾4¾‚4¾`¾HȾEà¾VȾh0¾r@¾~ˆ¾†œ¾Šh¾Œl¾‹˜¾x¾W¾L@¾Eˆ¾@¾B ¾Zྀp¾‹¬¾ˆh¾z˜¾_¾:P¾%`¾6Ⱦ`оt¾„ ¾~˜¾€P¾ˆ¨¾‹L¾~˜¾^¨¾WȾdx¾,¾•8¾žÌ¾–¾‡ ¾}¾}¾L¾‚쾇D¾ŠØ¾‹8¾‹L¾ð¾”˜¾—l¾ŠÜ¾q ¾t¾’¾£à¾ ¼¾•оܾŒÌ¾‹ü¾‚@¾s ¾x¾“H¾¥¤¾¯d¾°Œ¾§¤¾žd¾¬¾z(¾\(¾bH¾Š¾«ä¾¼p¾´,¾¡¾X¾…¾z ¾aà¾Nx¾G˜¾Z°¾„¬¾¾«€¾£L¾†¼¾Kð¾)`¾.h¾Jø¾rо†H¾Š¾‹@¾Ž´¾,¾ƒt¾gP¾b¾s(¾¾|¾wX¾ø¾ˆÀ¾„¾‰H¾ƒt¾„$¾†¾„´¾…L¾‹t¾’€¾•°¾’H¾Ž”¾‘$¾–¾—¾–ؾ›€¾¢˜¾ªÈ¾¯ü¾«H¾›¾¨¾Žø¾™¾ ¾žt¾˜¨¾œ¨¾¢¾œü¾ˆ¾~0¾~ø¾Š´¾‘ü¾‘ྴ¾¾—°¾œ$¾”|¾…Ô¾z¾ð¾†¾‡H¾ˆÄ¾‘p¾œd¾¾‘d¾„D¾sˆ¾e¾lÀ¾„¾(¾–¼¾–,¾¨¾¾’(¾‹À¾~€¾lp¾j¾u¾t¾… ¾ˆŒ¾‰p¾ŠT¾‰¾‚8¾q°¾]`¾P¨¾M0¾Y¾o¾~€¾p¾wH¾oÀ¾mÀ¾lоk¾d¾Z`¾X¾]Ⱦiؾuè¾<¾ƒ”¾‚о‚о€Œ¾lø¾] ¾`¾r¸¾ˆT¾“(¾’ø¾ŽŒ¾‹¾†à¾|8¾iؾ^ð¾`¾u辋”¾—T¾— ¾ˆ¾px¾`è¾^8¾c¾bȾcP¾qȾ†¾’„¾–¬¾Œ¾rø¾\˜¾a°¾u(¾‚Œ¾‡|¾‰h¾‰<¾‡˜¾ƒ¾~¨¾z¾p€¾i¾m8¾{¾„¼¾…˜¾‚”¾¼¾z˜¾^ø¾EX¾DX¾\x¾xÀ¾ˆX¾Žð¾Œ¾‚€¾f°¾M@¾Bø¾L¾gȾƒ„¾ŽÌ¾•о‘̾† ¾|X¾rè¾q¸¾yø¾‚4¾†`¾Žl¾™Ì¾„¾™ ¾“¾L¾Œ¾ŒP¾H¾”X¾›ü¾ž$¾žt¾ h¾£¬¾£ˆ¾™˜¾’ ¾– ¾˜°¾•8¾ŽD¾‰D¾“¨¾£´¾«˜¾£H¾—8¾¸¾‰˜¾Ž(¾—´¾¡Ð¾¤ ¾›4¾ð¾ˆÀ¾‰à¾‘¾™À¾ d¾œ|¾ˆ¾¸¾wà¾v€¾wh¾€Ì¾ƒ„¾Ü¾xÀ¾bP¾X0¾^¾aà¾]о_à¾oP¾y(¾jȾC¾8¾˜¾H°¾xྂ(¾l0¾S¾K ¾Rh¾\ø¾ZH¾G0¾<€¾NH¾q¾‰t¾Ä¾…4¾jÀ¾K°¾Bè¾Rh¾là¾zð¾u(¾cؾYˆ¾b0¾r¾rH¾^°¾Lx¾Rؾoh¾„´¾‡ø¾ƒ”¾v ¾lȾn¾vø¾‚œ¾…,¾„ ¾ˆ¾¤¾’,¾‰à¾‚8¾‚¾„8¾„¤¾ƒL¾„оŒ ¾’¾Ž¾‚ä¾tؾt ¾}è¾¾x¨¾y˜¾€ˆ¾|оp°¾d¾ZP¾^¾f¾c˜¾j8¾v°¾y8¾g`¾E¾(¨¾è¾+¾B`¾Xؾh¸¾ið¾Zh¾F°¾@@¾F@¾E ¾@¾HH¾cÀ¾оŠÌ¾‘侑¨¾ˆ,¾jø¾N ¾P¾p0¾ˆ4¾d¾‘d¾‘ü¾”ð¾–侓ܾ‹À¾ƒ ¾z¾v¾‚|¾–侫¾«ì¾™˜¾‡X¾ƒ`¾Št¾ŒŒ¾†¼¾€¬¾u˜¾t¸¾Ü¾Œ”¾¬¾ƒ€¾\à¾<ð¾6ø¾F¸¾[¾Zh¾I(¾:ؾ4 ¾7X¾;p¾7€¾+о(¾(¾'¾3X¾A¾<ؾ%¾è½éнí¾x¾¨¾'X¾4P¾08¾*À¾-Ⱦ1€¾)¨¾¸¾@¾/¨¾Xx¾rH¾q¸¾_оNx¾C€¾?ˆ¾?¸¾J€¾Np¾EH¾9à¾6ȾDè¾YؾZ¨¾<°¾½ü¾ ð¾0¾Lˆ¾PؾF ¾6¾(è¾)h¾,ð¾1ؾ:¾@¸¾J¨¾Q0¾T`¾Q8¾>¾(€¾ؾ¨¾.`¾M°¾[à¾Tˆ¾?°¾#¾ ½êð½ã ½ü¾ð¾)è¾:ø¾2(¾#`¾ H¾H¾8½Í ½ª@½Ü€¾#€¾I ¾Fˆ¾4 ¾1о1è¾!À¾X½Þ½ã€¾@¾¸¾6ȾHø¾K¾:¾¾ x¾ °¾(¾x¾ (¾`¾ €¾x¾:ˆ¾C€¾$Ƚ뽬½¢@½°`½Ãp½Ýð¾h¾Ⱦ(ؾ¾ ½Î`½ÇÀ½ê@¾0¾À¾¨¾8¾0x¾8`¾(¾ ¨½îнë`½ü`¾ ¾P¾@¾! ¾&0¾!ˆ¾н᰽®P½® ½Ü@¾¾¨¾H¾¸½á@½«@½‘@½¥À½Êð½æ½âP½ÏP½Ï½Þ@½á ½Ó½½°½® ½´`½ÃP½Öp½îp½ÿÀ¾¾X½ø½â°½Òp½Ë°½Éð½Í½Ð0½Óð½Ö ½È€½§°½ŠÀ½‡ ½ž@½» ½Ë`½³À½—н€½H½A@½`½Ž`½¸ ½Û°½ç0½Ï𽨽‡Ð½‚€½›½Àà½Ô°½à`½ò ¾0¾¸½÷ ½Ý@½Ê ½Ê@½Ó°½è½ë€½âнäP½é€½ã€½Ñ ½¹ ½« ½¨°½´°½µ ½•0½@¼®À¼V¼óÀ½o€½žÐ½˜ ½_ ½  ¼Ñ¼½€¼¹€¼àÀ½ ½Mཙ0½¿À½ËÀ½» ½”½Y`½?`½I@½p½© ½È°½á°½í½ì ½Û½¼`½ @½Œ°½ˆ½šð½²½È ½Þ ½âà½×p½Èð½»à½¡ ½ˆp½k ½U ½l ½à½¢ ½©°½š`½}`½c€½X`½Z ½€P½›Ð½¤P½¡@½š@½šð½œ`½˜°½‰½„À½ŽP½‹Ð½‚0½]`½:À½> ½N`½T½dà½`@½< ½! ½'`½%à½à½`½ `½ `½P@½a ½O`½3€½-`½T`½ƒÐ½‰Ð½ƒ ½f ½O€½AÀ½.À½@¼û€¼à@¼íÀ¼ñ¼ÔÀ¼d€:œÀ= <Þ@<¸@<˜€<µ= =c==ŠÀ=h =8@=-@=A =J€=W€=pÀ=l@=gÀ=}=†€=„ =o€=O =Qà=†=¨°=³ð=¢==•à=® =Р=ã =à=Ó=Ö=ë@=ó`=ëP=Ü@=а=Ø=æ =ëà=Û`=ÏÐ=Óà=Ø€=Õà=Ç0=¯°=£=œp=‘ =ˆ=ˆp=а=z =P=1 =2@=)`=`<ÅÀ<•@<¤À<É<±€<œÀ<®<ø€=€<ÆÀ ˆ>°>è>0> > °>°>à>>(>>€>0>ð> p>Ð> °>  > > >X=ü€=é`=Øð=Ì@=Í =Ù =é=ï =êP=è0=åP=à°=Ú@=Ô =×P=âð=ö°> >h> È>ð>@>>=øp=ë@=ç`=äð=ê=ú>h>@=í0=Üp=ÏÐ=Ì =Îp=Ï=Ý =ìð=ý0=û=ë =ÛÐ=Ó =Ö@=àà=ëP=÷ >X>¸> > ð>P>è=ü€>¸> p>p>@>>p>(>x> ð> ¸>ð>(=úp=ý`=úÐ=ô=âp=Ô=Ï=Õp=Ü =ÛP=ÚÀ=Û=Úð=â°=ä =ÝÀ=Ö`=×`=Ù€=ßP=ëà=ù@>ð>à>=ú =õ =øÐ>À> P> ø> ¨> ø>>>>>¸> 8> è>È>à>È>¨>@>h> > ¸>>È>Ð>p>¸>x>>>(>H>p>à>>>>@>@>>>H>8>P>ð>¸>˜>è>#°>$> >8>>°>h>"`>$È>#ø>"@> €>!>$¨>(`>+Ð>-X>,˜>.À>3°>9ø><`>:>6ø>3à>1>+X>&>!È>!P>%0>% >"(>h>ð> >=õ€=ðà=í=ï=í`=ãà=ÖÀ=Ï=Ï=ÒÐ=Ñ =É=ÅP=Ëp=Ö`=Û°=Ø@=Ô=Ù°=â =ì`=ñ0=ô@=ú=ü=ú=ö€=ÿ >ð>ˆ>@>ˆ>>>0> >¸> >€>ˆ>Ð>è>P>`>˜>˜>`>H>8> Ð>$0>%ð>'˜>,H>.À>-H>*H>$p> €>`>"H>(ð>,x>-H>*°>$h>>0>˜>è>€>¨>€>˜>p>> P> x> > P>ø>p>x>`>h>À>>˜>ø>€>>p>x>X>ð> >0> ¸>  > È>>È> >0=ü=ò=ñp=ò°=é€=à=Ø=Ú@=Ý=ÞP=Ú=Ôà=ÔÐ=Р=Ìð=É0=Á0=½ =¿0=É€=Ô`=Û=Ø`=Î@=Ã=½0=·à=¾à=Ï =á@=çà=ã =ß0=Þ=á€=å=ì@=ô=û€=þ=û°=ýÀ>ˆ>P>è=ù=ë =çð=ë=î =îÐ=ì@=á =Õ=É =¾=·0=¬0=¤= p=ŸP=›Ð=à=… =ƒ°=„=ˆ0=Š=‰°=†P=€À=~ =|@=„À=Œ@=‘à=–Ð=›Ð=£=¨=¯0=°0=¸=À@=Ç`=Ì`=ÌÐ=Ôp=ßð=ç0=ê°=ñ =ú€>`>Ð> 8> ˜>@>>>¨>ø> @>$ˆ>)8>+°>(¸>!Ø>È>¨>>ø>H> > X>>ˆ=÷€=çp=× =ÊÐ=¿à=·P=®`=¢=•à=„p=n€=Y =A`=& ==€<ø<ì<âÀ<Ð<¹À<”€¼p€¼À¼˜€¼Š@¼B»¨;,<è>à> ¨>>¨> >@>à>h>H>>>h> >¸>è>!>#H>&8>'ø>(`>(@>(À>*À>.¸>/à>1 >3>4H>6 >6p>6@>9X>;Ø>?p>A>>Ø>:Ð><>9°>5@>0ˆ>.>+ø>'°>"@>h>°> >X>˜>˜>`>¨>¸>>à> >X>>>(>>à>0> > > Ø> >>>>H=ý =øà=ó0=íp=æ =Õ°=ÅÀ=»À=µ@=®=ª =¥€= Ð=šÐ=—=‘ =ŽÐ=0=“P=—ð=› =˜=p=à=›=¦à=«Ð=§°=¡`=Ð=œ€=à= =¤ =¤€=¡`=Ÿ€=—€=‘=Ž`=ŒP=Œ°=Œ`=ˆ€=‡ =„P=…Ð=Šp==”p=— =– =•Ð=’°=ð=€=€=’=“Ð=’ð=’ =‹€=…€=} =r`=i=e =`À=\ =Y`=U=N€=>=,=à=`=!À=+€=0=4@=2 =, =# =à=à=€<ò€<æ@<Ò€<µÀ<Ž€ ½H€½Rà½_`½^`½WÀ½H½; ½K½I ½Và½`½`½P€½;`½"`½ ¼ì@¼ÅÀ¼¤€¼y¼"€»¼»|ºà9 ;(;T;¼;á<;æ;Â:» »Ç¼o¼ª€¼Ç€¼ô€½ ½9 ½k@½‡ð½™p½£À½®½¾€½Ïà½Ý€½ê`½ò½íнî0½û ½ÿ0¾ð¾p¾ P¾ ¾ ¾¾¾H¾ À¾(¾0¾À¾(½ù½ñ0½è ½Ýà½Íp½º°½¨½š½‘ ½‹À½…p½~½l½]€½Gà½8 ½+`½( ½) ½.½2 ½4À½7À½7€½8`½9 ½4 ½-½ @½`½€½½à¼þ@¼è¼Ð€¼¼À¼¶À¼±€¼¬€¼§À¼¥¼²@¼ÌÀ¼÷½ €½à½%½+ ½)À½!€½ ½ `½/`½;À½F@½K ½R@½S ½K ½H ½FÀ½Q`½W½]½c€½h ½eà½\@½N@½;@½,འ½ @¼ÿ€¼í@¼Ý€¼Ø@¼Ï€¼Æ@¼©@¼‰¼2€»Ý»¦»Lº”:€;€;¶;Ï<<€ð¾@@¾@à¾?`¾>`¾:¾6h¾48¾3¾2P¾3 ¾1P¾/H¾-@¾*0¾(¾(8¾( ¾'H¾(€¾* ¾+¾+ˆ¾*à¾,ˆ¾.0¾/°¾/`¾-è¾-¾*p¾)0¾)À¾,À¾/ؾ4ˆ¾9¾=¸¾B(¾DȾHð¾M(¾P˜¾R˜¾Vh¾[¾_ð¾e`¾h`¾j0¾j0¾i(¾hø¾i¨¾k(¾n0¾pˆ¾sø¾v¾vP¾wè¾w¸¾vȾuP¾tȾu¾ux¾u¾r¸¾oH¾k¾fоaø¾\¸¾Yà¾Vè¾T8¾T(¾T`¾T¨¾Rð¾PP¾Kð¾Gè¾EX¾DؾEh¾G¾F€¾Fø¾I¾I˜¾LÀ¾NP¾OH¾Q€¾R@¾T¨¾VؾWX¾Zè¾^ ¾`ˆ¾b¾c¾dp¾h@¾jÀ¾m°¾p(¾t8¾x¨¾|`¾x¾¾`¾H¾ ¾¼¾‚¾‚(¾Ð¾€|¾~X¾|X¾y(¾tP¾n`¾gؾc°¾`0¾^H¾[8¾Y¸¾YÀ¾Z€¾[¾Z0¾Y¸¾Xø¾X ¾Z¾[À¾\è¾`¾`оb ¾b¸¾cȾd ¾eH¾gˆ¾i ¾j¸¾jp¾k€¾oh¾qÀ¾t¾w0¾yP¾}h¾€”¾‚,¾‚侃”¾„¬¾…¾†L¾†à¾‡h¾‡Ì¾‡Ì¾ˆ8¾‡Ì¾‡¾…¨¾„$¾ƒŒ¾‚H¾€ü¾~ؾy8¾t`¾op¾k¾i0¾gp¾dˆ¾`¾] ¾](¾]ˆ¾_¨¾`¾_H¾_¾^о_8¾^о^€¾^¾]Ⱦ]¾\x¾\x¾\H¾\¨¾]°¾]˜¾^0¾^¾_¾`¾`ø¾d¾fP¾i8¾lH¾o0¾o¾mˆ¾l ¾m¨¾mø¾o¾mè¾m¾o ¾oÀ¾n€¾o8¾p¾qð¾u˜¾xð¾|x¾°¾€¾‚<¾ƒH¾ƒ„¾„¾„ ¾ƒÔ¾ƒP¾Ü¾€4¾}˜¾z¾u ¾t¨¾r¸¾m`¾d ¾\ؾVx¾P€¾Lh¾I¨¾Dð¾A˜¾?0¾< ¾:Ⱦ:p¾:P¾:°¾:˜¾;˜¾<8¾ ¾AؾD¾F ¾G¾G@¾GؾI(¾IоIˆ¾J°¾I¨¾JÀ¾K˜¾K ¾J˜¾F°¾B¾=о9P¾6à¾3¾0(¾,¸¾'о"ˆ¾`¾P¾X¾ø¾ è¾8¾X½üà½ö½ô½ñ`½ðð½ñp½ö¾°¾ð¾è½þ ½üà¾È¾ ¾ø¾ H¾ ˆ¾X¾h¾¾о`¾h¾ à¾$¾'p¾*X¾,о-À¾-¾-À¾/ ¾/€¾1X¾3¾4¾6H¾8°¾;0¾?€¾AX¾C¾B ¾BP¾Bx¾C˜¾Ep¾Gp¾FؾF¾E ¾Cà¾D¸¾F8¾GH¾IP¾LÀ¾Qh¾TоX ¾[(¾[¾[ȾZ¨¾Y ¾Y@¾XH¾Y¾V°¾Sø¾Q˜¾O ¾NP¾L8¾I ¾E˜¾A(¾<о7¨¾4¨¾0Ⱦ-@¾*h¾(h¾'H¾$€¾"¨¾ 8¾@¾à¾¾à¾ð¾ؾ@¾p¾p¾H¾ ¾¾ ð¾(¾¾ð¾ؾÀ¾ ¾ ¾ 0¾ø¾¾è¾¸¾о 8¾°¾ø¾H¾ø¾0¾0¾À¾!¾$¸¾'о*¸¾, ¾.è¾0(¾.°¾-€¾)€¾%(¾"¾ˆ¾@¾0¾x¾ˆ¾о€¾ ð¾¾Ƚü€½ò½ê@½ãp½Þ½Ø0½Ò½Î°½Ìà½Ç½Âཾн½ ½¼0½¿0½Æ½Ì½Ï½Ú½ã½å€½ê½ïð½ö@½ûÀ½ð ½éÀ½ë½î ½ò½öà½ùð½þ½ü½øð½ö€½õ½öð½ö0½òp½ð ½ë°½ãp½Ú ½Ïн˽ƽý½Ð½¸Ð½´½­€½¨Ð½¦0½¢½ @½ ½ à½¢€½¥À½ª ½®0½­À½­`½«À½ª€½©à½ª ½¬½­À½¬½¨P½¤½À½”ð½€½ƒ ½z½qÀ½l½g ½a ½\ ½W`½Pà½J@½H ½E`½H½F`½J`½QÀ½UÀ½\€½[½X`½]`½_À½f€½eà½h½iÀ½n@½oÀ½p ½o ½j½a ½X@½N`½?½1½€½À½€½½½ ོû@¼ß€¼¿€¼¦À¼”€¼Š¼r¼^€¼A¼J€¼D€¼R€¼T¼f€¼f¼U¼T€¼X€¼p¼•¼ÃÀ¼ÝÀ½`½ ½#À½2@½= ½J`½V ½^à½j ½x@½~@½‚P½…p½Ð½}À½kÀ½_@½m ½gÀ½a½Pà½P ½K€½3à½( ½ À½½`½ @½ €½`½€¼ñ€¼ë@¼ÝÀ¼É€¼©€¼Š¼Q¼€»É»\º€9@¸€:ä;r;Ó<`½: ½1@½"€½@½ འ¼ö@¼ë@¼ãÀ¼â@¼Ø€¼ÍÀ¼¿¼­¼§€¼Ÿ@¼¼‡€¼Š€¼’¼š@¼¤¼žÀ¼ ¼–@¼†@¼d€¼A¼3¼:¼J€¼R¼j¼f€¼W¼C€¼%»ï»˜º€9ð:8:0:P::Œ;z;Ç<€<-<=€0>`> ˆ> >`>À> h>%°>* >. >20>4à>7€>7h>6>2à>/ø>,°>*8>%à>#> ˜>>X>(>¸>¨>°> À> È>(>X>>X>Ð>ð>ð>>=ÿ€=ÿÐ>0>è>€>0>> > ¨>h>À>È>8>À>Ð>8>¨>@>°>ø>p> >>¸>0>X> 8> €>P>à=ý@=òp=éÀ=áÐ=Øð=Ñ€=̰=Ê =Ëp=Í`=Ñ=Òð=×à=Ûð=äP=é°=ð =öÀ=û°>ˆ>Ð>p> p>È>(>€>è>x>°>X>"Ð>%ð>(Ø>*˜>)ˆ>(h>&>#X>  >Ð>p>0>>Ø>Ð>`>€>°>ˆ>>@> >>@> à> °>>h=û°=ðà=å=Û=ÐÀ=Ê0= =» =´à=®`=ªP=¦@= à=°=™€=™ =›à=0=€=ž=Ÿp=ž°=ž =ŸÐ=¡ =£=¤€=¨=ª0=¬P=®=± =²@=² =²À=±@=¯=°P=¯ =±à=µp=¸=º`=¼0=¼À=»ð=º°=¹à=¼=½=½ð=À@=¾=º0=´€=­°=§=  =˜Ð=“==Œ=†ð=€p=tÀ=hà=[€=K@==€=. =(À=$`= €=€== =@=À= = à=à=€=`= @=À=! =/ =A =P =^ =l=}@=†=p=™ð=¢ =­À=µÀ=»ð=ÁÀ=ư=Èà=ÇÐ=È0=È`=ÈP=Ê@=Ê =Éà=ÊÐ=Èp=Å`=Àð=¼=¸Ð=²°=±°=¯0=«À=«`=ª=¦P= °=› =“`=Œ€=†°=ƒ=€= =w@=s€=nà=p =h@=f=dÀ=e`=i =s =zà=€@=…À=‡`=Š =‹=Œ=‹=‰€=ˆ=‰0=ˆ°=ˆð=‰ =Š =‰Ð=‰0=‡=…Ð=‚=€€=€ =€=yÀ=t@=o€=g =aà=YÀ=X`=U =SÀ=Là=H@=Aà=:À=5@=0 =1`=,à="€=À=€=! =!`=&='`=(€=*À=, =/€=0 =+À=)='À=2=< =C=W€=l =€0==˜À=£`=¬ =´@=º`=Àà=Å`=Æ=ư=Æ@=Æ =Æ=Ã=Ãà=Å=ÇP=É=Ê=Ì =Î=Ïà=Ó=Ø=Û0=ÝÀ=Ýð=Ú=Ôð=Î =Çð= =º=³=¯€=« =¥À=£À=¡=¡P= =¢=¢à=£@=¤À=©=¬ =® =¥p=–À==‰=ƒp=`=€@=‹0=’ =“€=” =‘ =Ð=‹=‡=†°=„À=„=ƒ=‚ =~@=uÀ=n =h=`à=[ =`@=e@=o@=| =…=Š ==‘°=•=› =¡`=«€=´=¼ =Á`=Ä`=Æ =Æ€=Ë =Ï€=Îà=ËÐ=ÊÐ=È0=Ãà=½=´ð=¯=«@=¥Ð=žÀ=—à=’`=Œp=†=‚€=~@={À=|À=y@=xÀ=u€=s =v =x`=y`=xà=w =u€=q€=g =]À=Q@=E`=7 =*À="À=à= À= <ô€<î<íÀ<é@<î<ôÀ<÷<ýÀ== =@= =à= =€=à<ý@<ê€<Ø@<Æ@<ÁÀ<À<Å€<Ä€<Ô<Ú€<Ú<Þ<Õ@<Ï@<ÉÀ<ÌÀ<È<Ã@<¾€<°<œ@<ŽÀ€<€;¶:Ì»p¼ €¼Y€¼¢€¼Í¼ö@½à½À½ ½#`½!à½!À½½ ½@½  ½à½€¼ïÀ¼Ü€¼½€¼š¼q¼C¼0€¼€¼ €¼5¼L€¼Q¼l€¼À¼ÄÀ¼æ€½@½à½€½@½½% ½1½6`½9À½+½ €½ ½€½à½འ½@½ ½# ½( ½(à½-`½6€½: ½>`½@`½G`½K ½Y ½b ½h½oÀ½p ½mÀ½o@½s€½yཽ…ཌཎð½•p½›P½ž0½ ½£½¥`½¤½¨À½®@½¯ð½²`½´P½´ ½°à½²p½² ½¶ð½¶P½¹Ð½»°½¼0½¾½ºP½µÀ½²@½«½¦À½¤@½¤½¡À½¡ ½ °½Ÿ½›à½˜½”½ð½Ž@½‰à½…À½ƒ ½…À½…@½‡½‰À½‰À½‹°½p½” ½™Ð½ P½¥½«½°€½¹½Ã½É0½Ô`½Û0½ÝÀ½à@½áà½å`½è½ëP½í½ð ½óÀ½ù½ý½ÿ@½þ½ÿ0½ÿ@¾ð¾0¾ ¾à¾ؾ ð¾ 8¾à¾À¾`¾H¾ˆ¾¾ ¾˜¾¾°¾à¾˜¾ ¨¾ H¾ ¾ ¾ 0¾ ¨¾ ¨¾ x¾€¾Ⱦh½ù ½ï°½è ½å½ä½áнã½èð½ë ½ð0½ô°½öð½û¾°¾p¾ˆ¾ 0¾h¾¾(¾¾!€¾!¾è¾ˆ¾ˆ¾8¾¸¾°¾¸¾!X¾!H¾!ˆ¾!è¾"è¾#ˆ¾%@¾'°¾*x¾-0¾0¾1ø¾4€¾5˜¾6¾5p¾5¾4`¾4¾2ؾ2(¾2˜¾2ˆ¾1ˆ¾1¾/h¾-¾*¾(`¾&h¾%˜¾%À¾&¨¾*P¾-X¾0X¾3¾4(¾5¾8 ¾:¾;ð¾=H¾?€¾B¾E8¾Hˆ¾J¾K¸¾K¨¾H¾F€¾D€¾BP¾A¾>¨¾<@¾9à¾5P¾18¾+(¾% ¾ €¾P¾ð¾H¾À¾x¾ð¾¾(¾ ¾ ¾ ¾о!H¾# ¾'°¾*p¾,¨¾/h¾0€¾1à¾18¾1¸¾3ؾ7¾:¾=оB¾Cð¾F`¾F¸¾E¨¾Dh¾Aà¾>¸¾9à¾7 ¾40¾1¨¾/¸¾-h¾*`¾(ˆ¾'¾%(¾%(¾& ¾(à¾* ¾,`¾/à¾1 ¾1è¾2¨¾3¸¾4¾3 ¾3Ⱦ4ˆ¾5P¾6¾7À¾5h¾5p¾3¾1è¾0è¾0¾/ð¾/`¾/8¾.˜¾.ø¾/ˆ¾0€¾0à¾/ð¾/ˆ¾.P¾-€¾. ¾.à¾10¾4ؾ5 ¾6¾7¾7 ¾6x¾6°¾7p¾5Ⱦ4˜¾5°¾4À¾5°¾5P¾4@¾4p¾4€¾2 ¾0P¾.¨¾, ¾*ð¾*H¾) ¾(8¾'(¾& ¾$ؾ#¨¾"(¾"`¾$¾&x¾(P¾*¾*°¾+ˆ¾+p¾,ð¾,è¾-à¾.˜¾/°¾2°¾4à¾7X¾9À¾;Ⱦ=€¾=p¾<¾8¾5@¾1À¾.ؾ*à¾'è¾#p¾À¾ð¾`¾0¾¾¾¸¾à¾Ⱦx¾0¾¸¾!ؾ$p¾(ø¾/x¾18¾5¾5h¾7˜¾5Ⱦ4(¾5`¾/°¾*€¾&о$ ¾ €¾ؾ`¾X¾X¾оè¾ À¾ؾˆ¾½ÿ@½û½öнóà½ô½÷`½û€½ý€½ýà½þà½ü@½÷À½õÀ½öp½õ€½õ€½û ½ÿ0¾h¾˜¾ؾ¾°¾¾¾P¾ྠ¾ ¨¾ ྠp¾ ¾H½ýP½õ`½ëнåÀ½Ý½×À½Ñp½Êð½Á°½¹ ½± ½¦@½› ½‘@½…€½xà½q ½o`½o€½o ½l½eÀ½\ ½P€½I`½Bà½= ½7 ½9 ½> ½< ½:`½6 ½6`½-€½- ½+À½2 ½=€½K€½]`½n½½‰½’½˜À½ž ½¡°½¥°½©ð½°€½¶p½»°½Á½Ä0½Ç@½Æð½Ç€½Æð½É@½Ì@½Ð½Ð ½ÒнνÊ0½Ã½¼ ½³P½­ ½©½¦`½§`½¤À½¡P½šP½‘°½Š½`½u½g½\À½V½U ½T€½X ½Và½Tà½W€½Rà½S½SÀ½N`½K€½F ½<`½4À½(À½À½ ¼íÀ¼»¼ˆÀ¼M¼»ò»¸»Rº€¹Ð¹8€9à:x:ˆ:´:H9 :X:Ô;‡;·<€<#€<;<:à½-À½འ¼ñ¼Î@¼´À¼ À¼‰À¼p¼G€»ø»~º;R;Ê<+€À=F@=P`=U=Z`=] =e@=f€=e =` =_à=] =Z =[ =] =Z`=X`=O =E@=9=0 =' =& =+`=-€=3`=< =I€=U€=c=mÀ={à=ƒà=‰=À=˜0==Ÿ€=¦Ð=¬P=²=´=¸`=º°=»à=À =Ä =Ë =Ô=ÜÀ=å =í=ò°=õ=÷ =÷ =úð=þ>>Ð>°> È> È>H>€>Ø>¸>@>8>¨>>p>>à>>Ð>(>°>>Ø>ˆ>Ø>H>ˆ>¨>è>0>x>#À>%ð>( >-`>0>2>4À>7(>9>9P>:°>:¨>:°>;à><È>?¨>Aø>EH>H(>I>K >L>MX>MX>N@>O>O>N8>L¨>Jx>G€>BØ>?°>9P>8X>8H>9h>:x>;è>;>:¸>8 >5 >3ˆ>1€>0H>0P>0è>0È>1`>1 >0`>/ø>.¨>.Ð>0>2X>5€>8Ð>?Ð>A¸>Bø>Cð>D`>Cp>C >B°>DX>FP>H>Hh>G˜>GX>E`>C(>A >?À>>H>>H>=>;à>:>8(>5à>3è>0€>. >.°>.À>0>1h>3 >60>7P>8P>8P>6ˆ>4˜>2€>08>. >-@>-8>-@>-@>->,˜>+X>+Ð>,8>,À>-Ø>.Ð>/>. >-À>,Ð>)Ø>&ø>#>è>Ø>à>ð>@>X>> ˆ>¸>x>¨>¸>@>>(>>>>Ø>È>P>à=øð=ðP=èÀ=ã=Þp=Úð=Ö=Ô=Ï@=Î=ËÀ=Ë€=Ê`=Çp=Çð=Ê@=Ð0=Ô0=Ø=Û =Ù =Ô€=ÏP=ÊP=Æ@=Åà=Æ =Å =Ä`=ÁP=½à=»€=¶ð=²=¬0=¡à=›=“P=°=‹@=ŠP=†À=†=ˆ=†`=‡=†=†ð=ˆ =Š=ˆ=ŒP=Ž=Œà=Š=‡ =€ð=~€={=yà=zÀ=|À=°=ƒ=ƒ0=†=ˆ€=‰==’@=—=›=Ÿp=¤ =§0=©À=«à=¬@=¬@=­`=®`=°=±=²Ð=´€=· =¹=¹=·°=±=¬=§Ð=¥=¤=¢Ð=¡ =¢P= ð=ž=›@=•=@=ŠÐ=ƒ =t =g`=X=L@=>=2`=à= <þ€<ÛÀ<¸<Ÿ<”À<Š€<€<“À<€<À<†ÀX>À>`> €> > > è>(> >>H>h>X>x>À>€>€>>¨>`>¸> Ø> @>X>p>P>=ý =õ=íð=çp=â=Û=Ó0=̰=Êp=É=Ê=Ê=Ì@=Ï=Ïp=Ñ0=ÏP=Ï0=Îà=Íð=Ï=ÑÐ=Ô =Ôà=Ôp=ÔP=Ôp=Ö€=Ûà=áP=èð=òP=ûp> >è> ˆ> ˆ>h>¸>È> >>°> À> @>Ø>à>@>Ð>Ð=ÿ0=ûÐ=ü@=û=ú=ú@=ú =ú =ùÀ=û =ýp=ü =ú@=õð=ô=ñ=ïP=í°=ê=ç€=æ@=â=áð=ßÀ=Þ =Þ@=Þ =Þ0=ßà=ßP=àp=á@=á°=å =åÀ=æ =ì0=ï=ñ=ð0=ñ=ñ°=ñÀ=òP=îP=î@=í =ìð=ì=í0=îð=ïp=ï=îð=ïÐ=ï=î=ñ€=ô =õP=ù€=ù =ùÐ=ûà=ýÐ>>=ÿ =ý=ú =ùP=÷€=ò€=ñP=ñ =ð`=í`=ì€=ì=é=ç°=æ=æ=ç°=î0=ó =ú0=ý`>>8> >ˆ>=þ =ùð=õ0=ò =ðà=ì€=êð=èà=åð=åð=áà=Ý`=Ø =Öà=Ó=Р=Ìà=È@=İ=Ä`=Ä0=ÃÐ=Ã@=À=¿à=À=¼ð=¹`=·ð=¹P=¸À=»@=»Ð=¾°=ÄP=Ç€=Ê=Ëà=Ë=Ê0=Æ@=À=Á°=À =¾p=¼@=¼à=»=º=»Ð=½@=»Ð=º0=º=º=¹p=¼€=À =ð=Ì=Î@=Ñ`=Ó°=Òà=Ò=Ò@=Ó =Ô =ÒÀ=Ï=Ì€=ư=ÅP=Â=½€=¹p=¶`=´€=´@=´`=³€=´€=¶@=·=º°=¿à=À=Â= = =Á°=À=¾P=½ =»à=·à=·p=µ`=´=®P=œ =œ = à=@=–€=‘À=€=‡p=ƒ°=}€=tÀ=n@=i =g€=l€=s€=€`=†à=`=•=š=p=Ÿ=Ÿp=  =¡p=£p=§ð=ªÐ=® =±Ð=µ=· =»à=¾ =ÁÀ=À=ÄÀ=Ű=Çð=ÉÐ=Èp=ǰ=Å=Å@=À0=»=¸À=²À=®@=¬ =ªp=¨=¦`=¢à=ž0=˜ =’=‰==t@=nÀ=j =dà=`À=Y =O@=@=/À= =`= <ý<ð<é<ì€<ìÀ<ý€= =à="à=3=< =E`=F`=Fà=M€=OÀ=K€=D=A@=@à=B=B@=Q =W€=`=q€=| =€=@=€=„Ð=“@=—p=š€=¢ =¨à=¯@=³€=½p=ÅÐ=ÉÀ=а=ÔÐ=Ö=Úà=ܰ=Þ°=â =á0=Þ@=Ü`=Ù=Õ€=ÖÀ=× =Ù0=Ü€=âÀ=è =íp=ò0=ö =ù°=ý`>à>°> >€=ÿÀ=ý =ø€=÷=ôð=ñ°=ìP=è=ä=߀=Ûà=Ø=Õ@=Õ=Ô@=ÕP=Ôð=Ö =Ô =Ö =Ù=Ü=áð=ç=ëð=ðð=÷ =û@=ýÐ=ÿ>>Ð>è>8> >°>@>€>X> >ð>8>à>0>Ø> `> (> ¸> >P>à>¨>`>˜>>@>> 8>$0>((>+`>,>-@>,ˆ>,H>,>+ð>+è>+è>+ˆ>+`>+0>+>(¸>(À>(€>(°>(€>(ð>*p>,Ø>0€>2ø>5à>7Ð>8 >9ˆ>9à>9Ð>80>7>7(>6À>5 >3è>2ð>0˜>/P>-h>, >-P>.x>0>2`>3X>4>5>6è>7˜>9>;¨>=H>@>D0>Gð>K(>Mh>O€>Oð>PÈ>Rè>S(>T0>VØ>Yh>[Ð>]>]°>]¸>\>\>Z@>Y@>XØ>Yh>Yp>YÈ>Zˆ>Z0>YP>W>Up>SH>P >MÐ>K¨>HÈ>Gà>G>F¸>F0>Fˆ>Eh>D@>C>C¸>DP>Ex>F`>Hx>IP>I°>JÈ>Kh>K>LX>M>M>NX>P>QÐ>TÐ>Wˆ>XX>Xà>X0>XH>V`>TÐ>S@>Q¨>P8>NH>Lh>J`>HÀ>G˜>E¸>B€>?>;x>9ˆ>8¨>7>68>5°>3ˆ>1h>/@>+¨>)¨>'@>$Ø>"À>">#>#`>$°>%ø>)>+>-@>/˜>2p>58>8è>;x>>`>AÐ>B@>Ch>D˜>E`>F°>G¨>H>Iˆ>J>LH>Là>M€>LØ>KH>J>F0>C@>?H>;0>6ˆ>2Ð>-à>)à>$ >!(> >ð>¨>>>>>ˆ>À>p> Ø> >Ø>0>È=ü€=öà=ð=éP=ä€=Ý =×P=ÓP=ÏÀ=̰=É`=Ë=Ì=Ï =Ñà=ÕP=Õ0=ÓÐ=Õ€=Ø`=Ú0=à=â0=ä°=è =ëð=ïp=ïÀ=îà=ì=é`=ã0=Ýp=×°=Ò=Ëp=Äð=¿à=»Ð=´à=²ð=²À=´@=µ°=¸à=¹ =¸p=µ@=¯ =¥À=œ`=“ =ŠÀ=‚@=}`=q`=l`=e =\@=Q`=Aà=5À='`== <ñ€<Ü@<Ó€<ÕÀ<×@<ã@<ð@<ùÀ=`=`= `=*À=; =K@=U=` =d =d@=[À=J =;`=% = <ë€<Ï€<Å@<´À<­@<™À<‚@À=D`=O@=T =[`=bà=p`={`=ƒ0=Š€=’À=›@=ª0=¹p=É€=Øà=â=í°=õ=òP=ñÀ=î`=íP=ï =ðP=í°=ï=ë€=â =Ý =Ô0=ÆÐ=º=¸=µP=³€=ª =Ÿð=”=ˆ`=}=k =]=P=H =C =FÀ=N =W€=e€=tà=… =‘`=œÀ=ª°=¸€=Å=Ò=Û°=äp=í=ò`=ö=ö=öð=ö€=ó=ñ=í=î€=î0=ï=òÐ=ô@=õ=øP=û=ú`=úÐ=û`>À>(>H>@>ð>h>¸>ð> `> >˜>à>P>8>h>°>ø>`>Ð>P> à>=ÿ =òÀ=ãÐ=Ù0=Ï=Æ=¼0=²@=¨ =žÀ=•°=à==ŽP==‘ =•0=™P=œP=žð=¡Ð=¢°=¥=©@=©€=ªÐ=®ð=®Ð=®Ð=¯=¯ð=° =¯0=­ =­Ð=¬=­À=« =¦0= €=š@=”=‘€==‰=…€=P=|=q€=fà=b€=a`=] =\=Z =Z=[À=^ =]€=b=gÀ=l`=p`=pÀ=l =là=m€=lÀ=nÀ=l`=h =eà=c@=\À=T =H@=>à=5=$`=€=À=@<ý<í<Ü<Ì<·<¨€<’€¼B¼C€¼#€¼ €¼€»î»³»»¹:°;|;Í<½@À½R`½k@½ƒp½Ð½¢P½¬ ½²0½³p½¸ ½Åнѽ̀½Â ½¼p½Éð½ë°¾À½ú`½á½Ø½â ½è½ë`½ì½ò½÷@½íнâÀ½ÞнÝP½ÙнÎp½Â½Á`½Æp½Ã½¯0½”p½‡ð½Œ°½žà½–`½h½4À½E ½w ½†0½ƒ ½…€½–À½Ÿð½”0½‰Ð½0½¢€½´p½¶½±½´½ºÀ½° ½0½ð½”0½¥0½¬½´ ½½P½¼0½³ð½¢P½Ž@½€ð½… ½• ½¥À½¡à½‘@½†°½†°½”½—P½Ž°½ ½mÀ½pÀ½b`½W ½j ½Œ½¤à½¡p½ƒp½YÀ½Ð½©½´Ð½—½xÀ½‰ð½¡P½¯P½¥Ð½£ ½º@½Þ°½ãнÈ`½¸½Â½Í°½Ã€½¾p½ÁP½Ò½é0½ëà½ãнØ0½ÑP½ÍÀ½Ôp½ß½é½ûP¾ à¾ø¾ h½éP½ÛP½øÐ¾h¾¾ ¾ °¾ ¾¾ˆ½÷°½éP¾@¾p¾о ¾H¾!¾ø¾¾ ؾH¾°¾8¾ȾP¾(¾;˜¾=¾2ˆ¾%¾¾ è¾X¾@¾¨¾%à¾/˜¾1¸¾*P¾ð¾ à¾0¾h¾0¾оè¾ (¾¾ ¾½ó½ëÀ½Ø½¾À½Ç@½å½å ½À0½ªp½Â½äp½ì`½Á€½‚нYÀ½Ž ½«ð½´½¿Ð½Ñ€½Þ@½Ï@½¦€½Œp½– ½¡ ½£P½¬ ½ÁнÖP½Ýp½Ìн´½µ@½À ½Ã€½Í ½áÀ½ò½õ½ö¾ˆ¾è½øP½é ½òÀ¾¾¨¾p¾ X¾¨¾¨¾ؾ(¾ ¾$p¾58¾0H¾ ¾¾H¾P¾ ¾(¾ ¾¾(H¾,X¾¸¾ ½ä`½Öp½×@½Ú°½íÀ½û`¾ð½ÿ ¾x¾  ¾€½äཹ½§½¹½Ù€½ñ€¾ˆ¾p¾°½èнϽѠ½Ö½Ï ½Ë½â ¾À¾+p¾80¾$è½ýнØÀ½ë¾ ¨¾H¾%à¾(è¾$€¾h¾8¾ø¾(°¾'¸¾ P¾(¾ ¾"ؾ/¾)à¾!À¾à¾˜¾ p¾ ¨¾¨¾(¾0¾p¾˜¾ྠ(½ÿ½äà½Ñ°½Þо°¾p¾о(½ò°½Ù ½Ê@½Ó½æ½ì0½é°½èP½î½ô ½Þ ½¶€½¬ð½¿Ð½Æp½µ½Â@½ê ½ö°½æ@½Ö€½ÖнÞp½À@½š0½žP½Ç0½çÀ½ôð½ø½ò°½þP¾0½äP½Ê`½Ë0½ê¾ ¾°¾"˜¾@¾h¾X¾ о ¾¾¾оP¾"¾%¾h¾°¾ À¾.0¾)𾸾8¾Ⱦ1¾9P¾1¾-8¾:¾Dð¾G ¾GX¾N¾P¸¾Kð¾G¾Op¾a`¾hоiоc(¾Tx¾H¾E0¾L ¾Qð¾RؾP˜¾N¾Gà¾8о)¾!`¾$о.о/¾%x¾ˆ¾(¾X¾¨¾0¾X¾à¾¾è¾ ¾ˆ¾ˆ¾°¾(¾ ¾ ˜¾ ¾à¾#¾1ð¾K0¾Xp¾L ¾5°¾1о=X¾K¾S¾X(¾b¾gˆ¾i(¾cø¾Zè¾c¸¾o ¾l°¾b¾f€¾v0¾~€¾uø¾^¾N°¾R ¾c(¾sÀ¾y8¾y¾tÀ¾nH¾r ¾¾~¨¾nȾax¾]°¾Z°¾bX¾oø¾z˜¾~¨¾zx¾n ¾d¾_¾W˜¾VX¾_˜¾n0¾@¾ƒä¾ƒÀ¾u@¾\ ¾Rð¾`ؾq¾lȾd¾e¾eÀ¾a€¾`¸¾kè¾sè¾p€¾pÀ¾t`¾r8¾i¾cH¾j ¾}¾ƒ8¾~p¾{¾ƒ°¾†Ì¾x¾€ü¾ˆè¾ˆœ¾€X¾x`¾ ¾„¾ƒ˜¾|о~Ⱦ†¼¾Šd¾†¼¾ˆ¾|à¾r@¾hP¾lH¾}¨¾†œ¾‹¾,¾‡ ¾tx¾dÀ¾ox¾yp¾iоR¾HH¾Qè¾a ¾jx¾h¾cP¾ZÀ¾QоN¾Nè¾Rð¾S˜¾Q¾S0¾\ ¾`8¾\ ¾\è¾_ø¾^h¾V0¾Pˆ¾T0¾XؾU ¾P¾SP¾dp¾up¾sø¾n˜¾o¨¾n`¾jÀ¾g€¾cˆ¾hˆ¾°¾Œ4¾ŽÜ¾Šl¾…<¾„4¾„`¾|ȾsؾT¾Œ ¾¸¾¾À¾’8¾‘¸¾Žœ¾‹¾ˆˆ¾…(¾†È¾d¾’°¾’p¾Ž¾‡Ì¾x¾xp¾sؾ{ø¾„例¾˜¾”¾Ü¾ƒD¾rx¾i ¾sh¾~о‚H¾ƒ¬¾„´¾‡(¾… ¾|¾j ¾^¨¾X0¾U˜¾Yð¾hH¾€€¾Œ”¾Œp¾|¾^ð¾YP¾`€¾_¨¾Z0¾bx¾{¾„@¾L¾p¾^p¾OÀ¾Kh¾P ¾Uè¾]˜¾g¸¾oH¾eè¾S8¾O`¾Qˆ¾L ¾@`¾:¾I@¾e ¾l`¾Wؾ>¨¾98¾?`¾7¾*8¾0 ¾K@¾jp¾wx¾rȾTø¾5¾/˜¾7è¾B€¾Qp¾e0¾v°¾|@¾mx¾Z¾X ¾]ð¾YȾD¨¾8¾U¾Œ¾Š„¾ˆ¾o@¾g ¾\à¾Nð¾BؾBø¾Q˜¾]ð¾mX¾~H¾~˜¾pˆ¾\ð¾Q¾M¾OX¾ZH¾oоh¾€|¾tð¾e0¾_˜¾]h¾Ux¾PÀ¾S¾Sˆ¾Uà¾[ð¾\à¾XH¾Vè¾[è¾]ؾS0¾Bp¾C¾Nà¾Q(¾L¾Mè¾UX¾O(¾4˜¾ ¾P¾-ˆ¾EH¾aè¾j ¾T¸¾<¸¾-¨¾,Ⱦ;à¾I¸¾Jx¾Iø¾U¸¾`¾Wx¾@ð¾2¾.€¾+ð¾1 ¾Ap¾M°¾Oè¾Hp¾;°¾4ð¾7°¾;°¾6H¾$€¾ ¾ˆ¾&H¾2(¾9@¾1Ⱦ!€¾ ¾(¾ €¾X¾°¾$ˆ¾"ˆ¾h¾h¾ø¾€½ó½ðÀ¾X¾¾€¾°¾@½ÿp½ô ½é`½ñ€¾¸¾x¾ˆ¾¾ ð½ùÀ½ûð½ýÀ½ãP½½ ½·½Ù`½êнÕ½®°½´P½ê½ü½Ì`½”½—𽺽Ç0½½à½Ì½ÿ0¾ ˜¾è½ô ½Ö@½Ì0½Ú0½è ½ð྾`¾(¾ˆ¾¾à¾ø¾8½îð½Íð½Ç ½ó¾X¾ ¾p¾h½ü ½ú ¾¸¾ x¾H¾h¾ø¾è¾#ؾ*ø¾"À¾`¾°¾À¾x¾€¾0À¾1P¾-ؾ.@¾(@¾@¾(¾è¾ ¾ؾ!P¾*è¾CP¾Oо5`¾P½Ñ½ã྾ P¾¾&¨¾6¾5¾+¾À¾¸¾¾ø¾¸¾ؾ+¾3X¾4 ¾+ؾ!¾"H¾+¸¾-X¾#@¾À¾(à¾9¾LؾUà¾W˜¾N¾I°¾XP¾h¾o0¾n°¾r¾w ¾nð¾\x¾Wø¾e8¾uh¾|8¾x¾…`¾ŽL¾‹„¾s˜¾SH¾Ih¾UP¾jP¾z@¾”¾ƒd¾€@¾qÀ¾f¾a¾Y¾N0¾G(¾Eø¾K@¾TP¾Y¾V¾J°¾;¸¾9H¾?@¾E(¾Cø¾7ˆ¾/ ¾4è¾;è¾;x¾18¾+0¾4ȾJ8¾W8¾L€¾@@¾?p¾<ˆ¾(€¾€¾!p¾:ȾU0¾f ¾nȾhؾO8¾1P¾$¾.@¾B¾I¾G ¾Iؾ\ ¾p8¾qp¾^ø¾9¾À¾¾1X¾Iø¾[x¾]¾Xà¾Wp¾Lؾ<8¾3À¾3è¾>¨¾J¸¾\p¾r¸¾{p¾tÀ¾c°¾Ux¾U ¾bÀ¾t¾{À¾w¾v¾~¾¾vð¾`x¾W€¾e`¾vȾ~P¾}¾}Ⱦ‚|¾…Œ¾€d¾h ¾R(¾Hð¾Dˆ¾H¾\h¾oˆ¾z¾y(¾e ¾P¸¾@`¾:¨¾:à¾8о>à¾S¾i˜¾jè¾R€¾0À¾p¾ø¾"x¾8 ¾Ex¾E8¾;¸¾9¸¾C@¾Dè¾:¸¾.P¾&о4¸¾Tp¾hx¾j°¾bȾY€¾V¸¾[ ¾c¾e ¾f@¾n˜¾} ¾ƒp¾‚´¾x¾l¾fؾgP¾i°¾oh¾|¾€Ì¾wоk@¾] ¾W@¾TоLX¾I˜¾S`¾cˆ¾m¸¾cà¾I˜¾0h¾!ؾ$0¾+ø¾,°¾1 ¾; ¾@˜¾=¾6ˆ¾'ð¾X¾ ¸¾¾8¾+h¾.è¾+`¾'¸¾!8¾¾¾Ⱦˆ¾ P¾о"¨¾#h¾$ˆ¾#8¾Ⱦ(¾ؾ ¾$ؾ(¾+è¾&(¾!0¾à¾¨¾ ð¾P¾à¾#о-0¾,¾ оX¾ø¾@¾h¾ˆ¾%¾.à¾+¸¾'x¾*X¾'P¾h¾ ø½üp¾À¾p¾@¾ø¾ оH½ò½çp½ïྸ¾°¾X¾ؾ0¾¾ нöÀ½Ñ°½Àp½ß€¾0¾ h¾½é½âнÙP½±p½Žà½Ð½¿`½Û ½µð½‡@½ ½Ä½Ôð½®p½†P½u€½i@½] ½q ½À½¹½Â ½¥½‹`½†½|€½^À½_`½y`½½©°½©Ð½Žp½o ½o@½h½J`½ `½ €½+ ½9@½`@½Š ½¡p½—нRÀ½ ¼ÔÀ½ €½à¼¶€¼ò€½[À½‘½tའ¼Î¼Ÿ€¼d€¼¼b€¼þ€½;½(`½½à½3à½: ½8½ ¼Œ€»Ë¼C€¼ü@½Fà½]@½d@½Dའ`¼Ã€¼Ž@¼b€¼ƒ¼ÞÀ½½ À½À¼Ï€¼Z»€:„ºø¼˜@¼ØÀ¼n€;p<£À<®@;â»P» ;ƒ<”À=@=À<¶€<”À<§À=€=@À=Cà=K`=N =_à=l =Q@=* =>`=˜@=Ѱ=éÐ=â`=ÒÀ=¿=®p=¤`=¡à=« =¾`=ÐÐ=ÔP=ÉP=Êð=ÕÐ=ÔÀ=Í€=µ=ް=€€=Ÿ0=Îð=ò>Ø>H> =÷=éà=×=Ò =æ=÷ =û@=û€>>8>À>H>à>p>8>"@>,>-h>*(>.à>3P>;°>F¸>Aˆ>2°>+p>!˜>0>À>ø>&X>#Ø>Ð>ø> >,0>(0>&0>ø>>%¸> p>>p>5P>H>J>8ˆ>$h>> @>&8>,¸>5X>>à>K`>L€>= >&˜>p> >*Ø>5Ø>B0>E(>9>$x> >Ø>/h>7è>7 >+è>$°>*>6(>;°><¸>9>/ð>/ˆ>/>% >#¸>,p>0>2>8Ð>?>;(>0>#> `>.P>E0>G>E(>E>; >7>= >H>I¨>?ˆ>9ˆ>9`>= >J>V>VH>V0>Z¸>T(>K€>?>4¸>;>Y0>yØ>~¨>pð>]°>Ex>7>D8>]À>e>gX>p@>v˜>xX>tH>iø>b>^h>NH>@ >Pè>q>ƒÄ>{>b¨>\ >[˜>R8>G€>F¨>Nð>fp>€@>y¨>Z>>x>00>)`>-€>:ø>IH>R°>O`>BÈ>4>'> >(> >$Ð>18>7>7È>3ð>)>>°=ÿ>˜> À>8>"°>,˜>0È>)€>ø>H>Ø> >$ >'>0È>>È>M¸>Uˆ>EP>-8>!Ð>%°>4 >FÀ>Zx>b>]Ø>Pp>Bp>>À>F˜>U >U0>OÀ>NÐ>VX>V(>E8>;>8ˆ>:P>= >=x>;Ø>78>00>'ø>`>`>p> > è> >ˆ>Ø> È>p>ˆ>=î0=ðÀ=ø>>È>/(>0Ð>%È>À>>>H>(X>4>:è>6È>4¨>7X>=>CP>E>@°>?>@¸>E >Q>^8>X¨>F(>>P>?p>>€>6è>1@>38>5À>-Ð>&P>$`>#P>P>Ð>8>˜>'À>,>>@=ëp=íà> >h> °>˜> 0>0>°>Ø>%è>,(>"X>à>P>.>4€>3¨>+à> ø>x> >¸>(€>.à>*€>$H>&˜>$ˆ>&@>+ >(È> >>Ð>#p>'>> 0=ö=î=ûÀ>X=öÐ=â0=Ãð=³ =¸=Õ =ß=Ðp=»@=§ =Á0=Ý =Û0=Ê0=Ï`=æ=é=àP=ã€=ü0> °>À>p> >H>>>Ø>ø> ¨> P>˜>#`>Ø>H>ˆ=ùÐ=ù > p> H>&p>@> (>è> >Ø>Ø> >ð>¨> >>> à>8>Ø> > ˆ>`>ø>ˆ>È>¨>Ø> >$°>ð>È>>(> ¸>À>>"È>H>Ð>p>#P>">x> >è>$>/P>-È>+°>0Ø>9>?¨>G€>Kx>C˜>88>2(>3(>9Ð>Gx>SH>S@>F(><@>=ð>Dè>LH>I`>< >0€>7>Ih>Q>MX>?@>;˜>Eè>Mø>Lð>> >(˜>à>%à>7>FØ>R0>L(>:h>->(ˆ>'>*X>,È>*8>2>E(>Mh>>>-à>.`>:Ð>G>O(>V>Z`>[`>_`>^ >Yx>W>Uˆ>Vx>Y >Xˆ>X¸>_¸>dˆ>a >X€>P >Jø>M >L@>Hˆ>H >H˜>K¨>J>9¨>%P>¸>h>À>#h>!Ø>p>à> 8> €>Ð>`>à> ð> à>h>#¨>. >)(>!p>>  >'>*x>.>2h>7>3H>,¨>-0>3ð>9¨>9>:h>?€>;¸>4p>3p>3>;`>CH>F¸>K(>KÐ>>Ð>8à><¸>6h>(X>%>1¨>>@>2¨>˜> ¸> @>°>`> ¸=üÐ=è=Û`=â€=é€=ì =ìP=è€=à`=ÂP=µ0=Æ=Î =Çp=±=¤ =·À=Ô=Òp=¶@=°0=ÀÀ=Ò =è`=ó€=Û =º =¼`=ÜÀ>`>H=ô=ëÀ=å=á=Ûp=Ýp=à =Ûð=Çp=²=½Ð=ÎÐ=Ò@=˰=·=£°=§Ð=¸°=´€=›`=‹=‹°=•Ð=–=o`<õ<·À=€=À=!à=<ËÀ<Ð<¶€È¾Cè¾LÀ¾O ¾I0¾C°¾IP¾Ox¾Rø¾Uà¾W€¾\¾`h¾a€¾Wè¾Mp¾Qˆ¾]¸¾k ¾r`¾nX¾d¾`h¾`¾cP¾``¾^¨¾c0¾i¾mp¾n¾s0¾xˆ¾u`¾f€¾R ¾Kx¾T€¾d ¾p¾rH¾n@¾jH¾h8¾^˜¾Q@¾Mp¾K˜¾Lè¾T8¾]H¾_@¾ZؾU8¾Hà¾<€¾4X¾/¨¾2x¾A`¾P¾N°¾A`¾9ø¾2À¾*à¾#¾¾#p¾6 ¾GȾGÀ¾>è¾4¾0 ¾+¾¸¾¾((¾7ð¾B¸¾DP¾;8¾5p¾>h¾D ¾>p¾4h¾.¾40¾Bp¾O¾S8¾PH¾GX¾;Ⱦ9à¾=p¾EH¾HؾHà¾SP¾^¸¾[оNȾA¸¾8°¾5X¾;ø¾JоV ¾TؾCø¾4 ¾4¾8 ¾5¾2ø¾6¨¾?˜¾Lp¾Vh¾Y8¾Sð¾Là¾KH¾Fо@°¾?X¾B¾EX¾Ph¾^`¾aX¾Xh¾LH¾<¨¾60¾=€¾H¾JÀ¾Mp¾N ¾Oø¾RH¾LȾKH¾MؾNX¾J@¾B¾= ¾?X¾Fð¾NP¾R(¾M°¾Iè¾H¾Dø¾=h¾2€¾+¸¾'¾"ˆ¾ˆ¾"0¾:ð¾J`¾@ð¾0 ¾&`¾#¾#о+¾-X¾(0¾+X¾9x¾E0¾HоA°¾5ˆ¾0H¾-0¾$°¾p¾ˆ¾¾à¾" ¾*p¾,H¾)P¾p¾è¾ˆ¾¾ø¾¾€¾8¾P¾@¾ ¾€¾0¾p¾H½ï ½Ö°½Î ½Ï€½Âð½¶°½¶ ½Â0½ÌོP½¬à½© ½¡Ð½˜à½•P½’À½p½žp½¶À½²°½”p½‰p½•p½³ ½ÁP½¨À½—€½`½…½e ½Y½À½•@½›°½™ð½¤Ð½À`½Ã½¬p½‡@½Z ½i`½• ½´½¹À½¾@½Êp½Í`½É°½È ½É ½¼½Ÿ`½€½ƒà½«0½Ë ½ÖP½Í½Á𽯀½‹0½?€½½" ½P@½…`½™@½®½¯p½–P½Œ°½m ½%À¼ûÀ½@½6 ½_½„À½‚P½M`½à¼ôÀ¼í€½`¼õ@¼«€¼a¼°À½(½9`½À¼ÆÀ¼˜¼°@½ ½X ½½ª½³@½¤°½À½¯°½Ì ½ØP½ÕP½à½ð@½ûP½ûð½îÀ½Ûð½Ä0½«`½—½—°½­à½Åp½ÊнĀ½Ê ½Ë`½½`½¨½`½ ½­À½×à½î@½æ ½×0½Í½Ê½Úà½äн׀½ÊP½Ðp½ã0½ñÀ½ó°½ïP½äнÞ@½ãð½ì½öо ¾°¾нü½÷½ÿÀ½üà½ï½æ°½õÀ¾ ˆ¾€¾ ø¾𾸾0½ó@½ñ€½ü ¾ h¾h¾¾ ¸¾ˆ¾¾¾@½û°½ó½ÿp¾8¾ ¾0¾ ¨¾ ¾`¾ ¾ø¾@¾À¾Ⱦ˜¾h¾(¾-Ⱦ*(¾#H¾!`¾*ؾ:x¾Ið¾[¾[ ¾L¾E0¾N¾Tð¾W`¾[P¾`¾b¾a@¾cȾm¾t˜¾m€¾[À¾N8¾U¸¾mX¾€D¾€Ô¾|8¾x°¾q¾h8¾cÀ¾g@¾r ¾zX¾€¾…Ô¾œ¾qˆ¾dø¾bP¾a0¾^@¾Z¾W¸¾Y ¾_(¾\0¾O¾F¾Dø¾FÀ¾H¾F°¾G€¾N(¾Wð¾]@¾YؾY¾\¨¾XP¾T¸¾Z¾`8¾d`¾jà¾h¾Y°¾S¾Yо_ˆ¾bP¾a¾`¾dؾnоpоeð¾[¾X¾Pà¾I(¾K ¾Z(¾cø¾h0¾k¾j¾i ¾^@¾Q ¾M`¾X°¾gø¾uÀ¾€P¾|оl8¾]¾S¾QH¾R¨¾V°¾\p¾\@¾Z0¾X ¾VH¾Op¾JX¾D¾=H¾Cà¾DX¾<`¾=(¾GÀ¾U¸¾\À¾V¸¾HоF¾L€¾P€¾X¾YȾX˜¾[ð¾Zp¾Y`¾`8¾gð¾o¾~0¾}h¾s`¾wx¾€¾€´¾~¸¾|оz ¾}¸¾ƒÀ¾…,¾†,¾…¾€Ì¾xо{¾‚ø¾†¸¾„€¾€Ì¾€|¾~8¾{(¾z8¾u°¾tȾ{ྀ€¾}h¾|ˆ¾€4¾wè¾k@¾hà¾uh¾¾ƒÐ¾ƒ|¾˜¾ƒˆ¾‡Ü¾Š0¾‰|¾‡|¾ƒ¨¾{è¾y(¾H¾…œ¾t¾ŽÀ¾ˆ´¾€Ð¾|о ¾8¾x ¾r€¾s ¾u¾v¾rh¾kP¾ià¾k¾kؾp0¾s0¾mà¾`H¾Q˜¾Bؾ<¸¾> ¾E¾Oø¾SP¾N¾Gè¾Aè¾<Ⱦ=¾DX¾@ ¾7¸¾6@¾8H¾Dˆ¾Rø¾[ȾZ(¾V0¾R¾IоB¾>°¾@¨¾J˜¾Tè¾XP¾TؾNؾMؾG€¾< ¾7À¾;P¾@¾<€¾0X¾'0¾,ð¾>¾F¾B˜¾7ˆ¾. ¾/ ¾7è¾=¾:p¾6`¾0ø¾0 ¾2¾6ؾ<è¾7ø¾/ ¾+¾.ø¾0`¾(˜¾#¾%ð¾+p¾)0¾!¾ à¾%ð¾)@¾)¾(¸¾,˜¾-о&˜¾P¾¸¾ (¾% ¾/ø¾:è¾=ø¾:h¾3à¾)`¾ð¾`¾h¾x¾`¾ؾ¾¾!¾$8¾!h¾P¾¸¾ è¾à¾¨¾¾h¾ø¾& ¾2¾/`¾!è¾X¾ @¾&`¾#˜¾$¾(p¾.H¾6ˆ¾;x¾=ð¾: ¾5€¾+¾!¾"p¾)@¾.0¾+ ¾ ø¾˜¾ð¾ ¸¾# ¾ X¾x¾¾о ¾h¾ ð¾P¾ ؾ ¾¸¾!h¾+(¾  ¾x¾¾$H¾-(¾1¾0(¾,¾+8¾2¸¾?h¾G ¾Dh¾<Ⱦ1ø¾, ¾0À¾/è¾+8¾'(¾-(¾28¾3€¾5à¾.x¾  ¾P¾ ¾! ¾-è¾6è¾4à¾- ¾'ؾ!`¾¾è¾À¾˜¾˜¾(0¾+ˆ¾$Ⱦh¾p¾h¾˜¾ؾ €¾"à¾X¾ø¾(X¾.°¾+@¾(¾+@¾)¾'8¾2P¾?ؾMؾT`¾K0¾=¾6X¾7Ⱦ@H¾I(¾Jø¾G¾Eà¾DP¾=ؾ8¾1о*¾ ¨¾À¾'¾;¾9à¾"À¾ Ⱦ°¾о(¾p¾Ⱦ °¾`¾`½þ½Úð½ÃP½¼Ð½Â€½Ãð½Ì€½ãp¾¨¾ 𾘽ó ½ã ½â½éP½æ0½ÜнÜÀ½ñ ¾ ¸¾P¾¸¾ ¾¾ؾ 8¾¾x¾¸¾p¾0¾ ¾P¾ ¾"p¾!˜¾$`¾-€¾4¾+¾ ¾ (¾`¾ð¾ P¾X¾ ½þ ½î`½í½ö°½îP½æ0½ÛÀ½Ö°½É ½²½°P½¼à½ÚP½õ½÷ ½î°½ê€½ð@½ÝP½´€½ˆ½vཽ¨@½¹P½¶ ½«Ð½¥0½¡€½ ½À½o€½B ½0€½H€½À½Ìнéð½Öསнx ½W@½``½pà½n@½j`½oÀ½†ð½™½¡0½£½žÀ½–½Ž0½• ½¨@½¹P½¸ ½©À½¤½¨€½©`½ª ½¤ ½¡½¬P½¹½´ð½¢ ½‡@½2À¼î½@½J`½ƒ°½Ž@½u ½Hà½)¼É€¼d¼0¼¼¼™€½ ½8 ½Oà½< ½€¼¸¼i¼B€¼P¼™@¼À¼›À¼ª€¼“¼Z¼¼»z;":ô»<¼8€¼;€»~:ì<À=?€=%à=@=<áÀ<†€;XºÌº;ˆ<`=u`==”P=„`=Z`=$€= =,`=I =i@=…p=š=°0=Àp=·€=¡À=‡@=i=d€=t =Œ0=¤Ð=É=ä0=é@=Ì =¨Ð=  =¥p=¦À=¦=«Ð=¯0=¶P=´0=¡À=°==p€=d =R =Aà=L@=U€=LÀ=NÀ=]@=q€=r€=Tà=B€=H@=Nà=O€=Oà=f =„ =‰ =y€=a€=hÀ= =†=|à=[À=B@=F`=Sà=Q =O€=U =bÀ={=ˆ=Š@=„°=^€=) =À=4€=Và=‚=‘Ð=’p=ŽP=ƒÐ=zà=d =P =H€=Y`=v =°=r`=^À=|À=—= =T =$ =&€=EÀ=b=e =`€=^€=^ =K€=( = =À= ='€=1à=C =^ =tà=€=€`= =Ð=„=€=w`=u€=°=–P=¯Ð=¹°=­0= à=¢€=•=†°=Š`=ž=· =Å`=Ä=¸à=¼`=½P=¬°=¤0=¤`=³ =Ï0=ép=ú0>p>@>P=óÀ=ðà=þ€>Ø>À>>>(ð>-(>-Ð>-x>)ð>'>' >*€>7¨>Ex>PÈ>WX>Z >W˜>Kè>Að>:x>:È>LÀ>\è>\ >U(>O°>J°>Fà>?ˆ>5à>1Ð>3À>8¨>8Ø>4˜>+À>!°>> > è> >h>À>8>À> °>¸=øp=ëP=ãÐ=æ€=õð=ü€=þÀ>> °> >¸=áð=ÆP=½@=ÄÐ=ËP=Ðp=Ð@=Ö=ç@=ñ=î=â =Ë0=ºà=Å =ß=ù°> >h>>> > ¸>À>X>> 0>À>à>"¸>(X>+>,>, >, >, >,h>->-°>)x>">°>(>(è>.@>&p>x>p>P>°>ˆ> > >8>P> 8>%È>)€>&X>"h>"°>& >(>ˆ>¨> > è>>¸>ð> È>ˆ=íà=ã=ç`=èp=çp=Ù@=Ó°=â=æÐ=í0>P> °>P> è> 0> >˜> (>€>@>!ø>+`>.x>*€>((>!Ø>È> ˜> Ð> à>H>H>$`>&0>à>à=ô =óp>°> À> `>P=ý°>¸>P>È> @>È=ö0=õð=þ >˜>¸=÷€=ß=Ð0=Õ€=ÛÀ=ÎÀ=ÇÐ=Ê€=Ï=Ôà=Р=¾0=£ð=’=™€=µ0=Î =Ù0=Ï =ºà=«P=¨ =®À=°P=·`=Á0=ʰ=Ð=Äà=¼p=à=Õp=ÜÐ=ß=çÐ=ð =ó=ó=òp=ö>€> =ôÀ=ç=åÀ=ò =úÐ=ÿ€=û`=åð=Ð0=ÅÀ=¿P=Æð=Õ =ß=á€=Þð=Ìà=·P=®`=¬=¢p=œÐ=• =‘@=À=€=‚`=s€=p@=eà=\@=L€=R =U`=Sà=M@=; =5`=U`=l =] =4@=#=4 =H=@@= à<ˆÀ<€¸>¸>X>¸=õ€=ðð=û>@=öà=ê°=à0=Õ`=×Ð=äÀ=ìP=ð€=ëð=â`=Ñ0=Çð= =º@=»0=½p=ÂÀ=Ëð=×@=ÛÐ=Õ€=Ã@=¹0=µ=©à=›=—=š=¤P=°`=·@=·P=·=»P=±€=—p=„=„p=Ž€=—=™ =™`=˜@=™`=’À=†€=w€=w =‰`=‘ =• =– =‹=ˆ€=Š=ð=‘=‘Ð=›=§€=²ð=µ°=ªp=Ÿ@=¢€=¨à=§`=¢=ž°= P=™ =Š =‚€=„à=z@=Hà=!À=+ =K€=^=_ =Tà=NÀ=Hà=A =%`=€<úÀ=@=? =j@= ==m =d€=e@=`€=^À=S@=M@=nÀ=—ð=­=« =™Ð=~`=] =L`=NÀ=MÀ=9À=2 =>=L`=H€="<Û€<}€€=Y€=€P=Ž =€=“°=¢=ª`=­à=®€=µ=Áð=Îp=× =ÞÀ=ã°=á°=×À=ʰ=¼ =´@=¼ =ÆP=ÛÐ=ðà=øð=÷ð=ë =Üð=Öð=Ü0=è =ðp>`>(>¸> >%°>+8>)h>%¨>"è>(>,8>.8>1¨>8¸>HÈ>MH>FH>7ð>,>(p>)Ø>+x>'Ð>(>H>°>>>`>X> >>À> ¨>˜=ù=ß@=Ú =êp>> €> `>p=ü=ø@>¸>=õP=êà=î€>P> `>x>>X> ˆ> `>0> >0>0>!x>(ð>1>8p>9`>4>08>6H>C˜>Pp>Y >\¨>[P>[>P¨>GÐ>Eè>Hø>P>U>Tˆ>O¸>L>L°>IX>=¨>/¨>'>!0>%Ø>0Ø>8x>;ð>7>-p>!0>>°> p>à>>è> >> ø>ˆ=óÀ=í`=óð>0> >P=üp=ðà=ï@=íP=èÐ=èð=ñÐ=ù°=û@=ýÐ>`>P>ð>>Ð> P> 8>(>&ð>/ >*€>'H>1p>@x>Iè>I>E0>Eè>F >K8>V0>b(>dÀ>`Ð>\>[˜>^ð>^Ð>\€>Xh>O>F>DÈ>G¨>G >Ex>@>@X>E`>GÐ>CÀ>;¨>0à>#Ð>À>@>à> Ð>!p>> ð> Ð> >> ð>@>@>(>p>(>,`>,(>)>%`>#ˆ>(è>-˜>*>'Ð>*€>3€>>>D¸>F >B >8Ð>2¨>9H>Dˆ>L`>P>J@>Dà>Cè>@><°>7@><0>Gx>SÈ>Z€>[Ø>^8>\H>\>a€>eˆ>k°>sX>t˜>tð>v >v >vÀ>v€>uØ>vh>y>xx>xð>u°>v>{`>}0>xø>pH>k˜>jà>r¨>|H>‚>…<>‰>Џ>‡°>„@>‚Œ>‚P>è>„Œ>‰¤>ŒT>ŠÀ>ˆ>†¬>„d>‚8>‚,>P>€¼>‚d>ƒä>ƒ¨>‚>}`>y(>|>€€>€ì>}è>zp>z¨>~>°>Œ>ƒP>„X>†„>Šð>Ä>Ð>“>—P>š(>™°>—X>”T>”>–>›>¡@>¨>ª”>©X>¥$>¢>¡Ô>¡ì>¡ü>¢Ð>¤0>¨Ü>®ø>±¬>¯”>¬À>¨>¥ >¦¤>§T>¥<>£´>¢P>¢>¢ø>¡Ä>Ÿ`>Ÿ$> Ø>£>¤¬>¥”>¦p>§>¤>ŸP>žX>¡>£¬>£œ>¡Ô> @>¢4>¤P>¥ˆ>¤l>¡|>È>œ >œà>¡œ>¨P>­X>° >¯>¬Œ>ªˆ>©@>¨œ>©>ª(>¬(>­¤>®|>°Ì>´\>¶>´è>´¬>³T>±Œ>°L>±ð>²>±Ø>²È>°ì>¯L>®t>®Ø>®x>­>¬œ>¬4>®X>­8>ª´>©ì>«À>¯>¯<>­ä>¬„>¬Ì>­x>°$>´t>¶T>µH>³>°D>¯¨>°>°ˆ>²Ì>¶<>¸H>¸|>·8>´ >° >«ð>§t>¥t>¤x>£Ø>£T>£L>¡´>Ÿü>ŸP>žˆ>œÄ>—ø>”D>“Ô>•È>—è>˜Œ>šP>› >šŒ>˜ä>–¤>–€>–>”L>“ˆ>“Ð>•>˜d>™Ì>—l>• >“$>À>Žœ>>‘>’°>’€>¨>ˆô>ˆØ>‹ô>ˆ>“ü>—>—,>“$>T> >“<>–à>š„>œÜ>œt>›|>› >>¡8>¤x>¦D>¦ä>¦´>¤œ>¢h>¢°>¢ >¢p>£x>£0>¡ >Ÿ >žà>žˆ>ž>Ø>›\>™€>˜>˜>—ô>˜ä>œô> Ì>¡Ø>¡D>¡|>Ÿœ>œL>šÈ>œh>ž¨>ŸH>Ÿ> 4>¡0>¡>Ÿ0>œD>›8>™à>—”>•D>•0>—¼>šX>š¼>˜„>”ð>’>‘>’<>’Ô>“À>“¼>•L>•¼>•>”ì>’Ä> >ð>Žœ>È>’¨>”è>”¸>“>˜>ˆ>Œd>Œ>Ž>|>‘>“>–°>š¬>š¤>˜€>–ð>–Ä>˜@>šü>žX>¡>¦˜>«„>®|>¯ >¯,>¯>®,>«è>« >®l>²>³t>±Ô>®ü>¬>ª>©>ªˆ>¬¨>­ø>®Ø>®Ð>­Ô>ª4>¦4>¤ì>¥Ø>¨P>¨Ü>¨>¦È>£è>žÔ>˜|>“>€>P>>ø>h>`>>‹À>‹ô>,>ŒH>‹Ì>Š>‰|>ŒH> >D>ˆ>‘>’Ì>“$>”¸>–>–8>•Ð>•¬>”<>’@>‘¬>‘¼>’ä>–Ä>›¼> 4>£l>¤<> >™ü>–Ø>–`>™¤>žx>¤¸>©¼>¬Œ>­”>«Ü>¨ô>¦L>¤h>£P>¥Ì>©˜>¬È>¯>¯´>®œ>«À>©¨>¦ø>¢ >žØ>œ>›>šŒ>—<>’€>Œð>‰P>†P>ƒ(>€>|P>|¸>|8>yP>tè>s˜>wp>z >y¨>wØ>t>p¨>r¨>{`>”>ƒ˜>ƒ\>˜>€Ð>€>>>}8>x0>t(>vX>z>{ˆ>wÈ>q¸>p>nˆ>là>ið>jP>p>vØ>>€À>}8>y€>{(>|8>z˜>zp>|`>|è>{P>wð>u>n8>b>\ˆ>Z>WØ>Q¨>Rø>Oà>TÈ>[è>]X>^ >Z>Sè>J8>Bð>AÈ>F(>GX>GX>H@>Bø>=à>;¨>5Ð>/¨>*è>.¨>2@>3H>.>(>%>&>'€>%¨>#ˆ>Ø>è>ð>H>H>¨>>8> Ð> p> >˜>è>Ð>> p>> > >H>¨>(>> >è>Ð=ý =ù=ù@=ýp>˜>¸>X>¨> È>è>ð>!h>!p>p> h>°>¨>> @>+ >2ð>0ð>(¨>>ˆ>À> > Ø> À>¨>h> X> >Ø=ÿ°=óà=ðP=æÐ=Û@=Р=É@=ÀÀ=ÂÀ=Ð=ßà=èà=ëp=ê =ç =æP=íÀ=õ@=ùÀ> >h>(>(>°=þ=ø =òÐ=ï =ð€=íÐ=ç=åà=è0=õð>@>à>¸=÷p=õ€=öð=ö=õ€=ù`>p>>È>> ð>È=úÐ=ñ=óð>Ð>P>Ø> > >à>@>ð>8>> ø>%x>$è>$>#0>">#Ø>(X>+È>)˜>%p>%8>+h>3>7À>7P>0ð>* >%ˆ> À>€>! >&x>&0>'¨>, >, >)>#@>°> >!`>'>,À>,°>%>Ø> È>(è>-Ø>,È>&˜> ˜>¨>p>À>x>È>%>(ð>( >"€>ø>Ø>°> >`>˜>!P> ˜>!0>">!€>>€>à>(> >p>x>>à>ð>> >ˆ>P>Ø> Ð> À>x>Ð>=õ€=îà=á=ÒÀ=Ê=É0=Ð=×@=Ü =×à=ÒP=Ôð=Ù`=Ú =à°=ì=ÿ`>>>>¸>ð>P=þ >@>X>€>ˆ>H=ùp=ý=ý=ùð=ù =ø`=ð=ê`=ò0=÷=ñà=äÀ=×Ð=̰=É =ɰ=ð=Æ =ư=Å =Çà=Æð=É=Æ=ɰ=Íp=Ì=Ã=´P=µ0=½p=Íà=Üà=Ü =Êà=¸ =²à=º=Ï=Þ =á0=ßp=ßÐ=å=ë=ô=ý >à>ð>@>¸>H>è> ¸>> >˜>x> > À> >P>€>°>À> > ø>0=ý0>@>€> >=õ =îP=ãÐ=×=Ìð=Åp=¿@=Â=¼°=¹p=¿0=Ï=Üp=Ø=Æ@=´à=ª=ª =°`=¹ð=¶à=«à= @=˜p=’°=’=0=Šp=…=xÀ=‚P=Žð=’`=‰@=~`=†€=–=ª`=»€=Ç=É€=ÉÀ=ÑÀ=Þà=ì=ñ =ïÀ=ó@=ù°=þ€>¸>Ø> (> X>8=ü=èà=áÐ=ß=â0=ãà=å=å=ä =æP=éP=æà=Û°=ÊP=» =·`=²0=´=­à=­`=´ =»`=¼=®0= @=‘@=`=’Ð=šÀ=¨=¯°=ªÐ=Ÿ`=”à=Œà=…=‚à=…`=Š ==‘=P=’p=¡Ð=°=²à=¡=‘à=†P=p=„à=‰@=’=œ=¥ =®À=°=£ =’0=“0=¨ =¼ð=Ä=À€=Äà=Øp=ëà=ðð=ç€=Ú€=Øà=Ýp=àà=ã=åp=ò=ÿ>X>>>à>`>Ø>¨>>à>x>>Ø>è=öÐ=ì0=èð=ë€=ï@=ñ°=ï=ç=áà=á€=Ë =®À=ž`=˜`=¤Ð=ÂÀ=Ôp=ÆÀ=¬°=›=z=Xà=R€=C€=8=3À=S€=cà=bÀ=L@=!`= =  <ù@<ÔÀ<¬@<˜<Å=@=5€=< =C`=Aà=<à=0=> =]€=y@=y€=c@=U=^À=y€=„€=ƒ0=|à=v@=u=}@=†à==’ =œ°=©`=½`=Ò0=Ü =Ú`=Ö€=ã€=ñ =öp=öP=ðp=ì=õP>X>`>> =õ =éÀ=ß =ÖP=Ï@=Èð=È0=Å =Àp=¹°=°p=§ =–À=p=j=tÀ=|@=p =\ =@@=- =2`=9`=?=EÀ=K`=K€=V =m=}€=ƒÀ=~À=p=f`=w@= =¢=¥ð= = 0=¤€=¬=° =¯ =ªð=¨ð=®à=¿`=Ð=Ïp=Ä=ºp=¯Ð=¬€=°Ð=µP=¸ð=¼0=À€=Å`=Èà=¾Ð=¯ =¬À=»p=ÎÐ=Þ =ãÐ=äp=ß =Ü@=ã=í0=ó =õð=òð=ñP=ô`=ø =ÿà>0>ð> > °> P>˜>€>`> 8>  > ø>Ø>>Ø>x> 0>x>=úð=î=áÀ=Ù`=Ú=ì`>>x=ÿ0=ôÐ=î@=ëÐ=í=ö`=þ0> >P>È>X=ô =â=Ô =Ö0=Õ@=Ó=ÙP=Þ`=Ý=ØP=Ö=Ø=Ù@=Ó=ËÐ=Ñ@=á =øà>X>¨>h>>¨> 8> È>à>>$(>$Ð>!P>˜>>ˆ> >ø>0>è>`>H>ø>8>!H>! >"p>˜>x>H>Ø>°>x>!˜>% >&8>$à>"P> ˜>!0> À>€>@>˜>È>¸> @>>h> > >è=÷°=êP=ã=áP=Ý€=Û =Ý =çP=ïP=è0=Ûà=ÎP=€=Á=Å=ÎP=Þ€=èÐ=ò =ö€=úÐ=ÿð>Ø>è>(>h> ø>P>Ð>è> >è>&°>+P>/`>3 >6ø>8à>6x>2ø>-È>,ð>-P>-ø>1Ð>3À>3P>3X>1ð>2X>/°>+è>& >">$>*@>1€>7¨>5Ø>4>4ð>9È><>;>=H>Bø>Hˆ>M`>Nx>Qð>T€>W°>]p>^@>^p>]¨>^`>^ø>[H>UØ>RÀ>QP>Q8>S(>Sp>T(>P>F(>=h>9¸>>H>?`>A¨>G>Kˆ>KÈ>L€>Nà>R>X >ZØ>XP>Z8>a0>f >h€>m>qÐ>p >n>pè>sø>x€>} >€¸>€Ü>{ >w0>x@>€H>‡0>ŒØ>Ô>Ž\>Œ >‰´>…è>ƒ”>„Œ>†ð>‰0>Šð>Œ4>Ž@>Ì>$>>€>Ô>‰¸>…>„0>…¼>Œt>’>‘´> >ŒÔ>Š<>…¬>à>{>wH>w>rø>np>j¨>eH>\˜>Tà>Nè>M>OH>Px>M>F°>E`>JÐ>Q@>SÐ>SØ>TØ>TH>Tˆ>T˜>R>O>M >M`>M>N>Jp>D¨><¸>4p>18>3P>;p>>0>:x>3˜>.à>-˜>/(>1Ð>2@>0>. >,ð>)¨>'X>%>X>è>x>p>ø>à>> 0>!€>$p>'>%°>"> >˜>ø>8>P>@>Ð>@> À>Ø>(=ðà=â0=ã0=íÐ=òð=ùà=þp=ù`=í€=æP=èP=óÐ=ü°=ó =â=Ú°=Ø@=Ü@=àÀ=áP=Ù=Ð =Ì€=Ͱ=ÄÀ=µÀ=¨€=•À=‰P=Œ0=‘€=“===†`=a =;À=-=€==)`=GÀ=k =‰0=•€=’`=†€=w`=YÀ=J=^@= =“P=¨0=¾p=ÌÀ=Ì€=À=¯p=¡ =œp=¤À=²Ð=º°=Ãp=Ëð=É0=¼À=«0= `=ž=£=¦À=¡p=Ÿ =š€=‡0=[€=F€=E€=9 =$À=`<î<î€=`=!=-€= =`= @= @=* =BÀ=T@=V=Dà=1€= @= = @=€= =€= <û€<ñÀ<ç€<Ú<µÀ<†@<;Ö<"<;Ù;±;d;x;|;:´;;Ó =E`=^ =q =dà=GÀ=5=1€=. =/=5à=Bà=GÀ=8 = <ÿ@<ªÀ<1;ºä:€;û<ƒ€<³€<¸€<–@<^ >@> > 8> X> >ˆ>8>ø> >Ð>0>À>%@>$H>!>P>h>˜>> °> ˜>À>x>> >P>@>8=þà>@>8=û0=öp=÷=îÐ=êP=âÐ=Ø@=Ôà=Ô@=ØÀ=Ýð=Õà=Ȱ=¿@=²€=­P=¤=£ð=©=° =¼€=Âp=À=´`=¬ =¦p=£ =¥=§Ð=¨P=¬ =±€=¸°=Á=ǰ=Ç=Ép=É=Å0=É0=Ñ=×`=Ù=Þ0=çp=ç=ä0=Ý€=Ùà=Ý=åp=ñp=øÀ=÷Ð=è =Ñ =¿À=¼=¹ =°p=¯°=´À=¼@=¾0=¶P=¤ =ŒÐ=t`=W =J =D€=FÀ=K =W =nÀ=z=r@=W =9 = <ìÀ<þ= = =€= à=<õ@<À<…<€;»Vºø9à¹@ºh::ä;*;N:й°»Z»›»j»N:ô;½;;,;;Ø<ˆ¾>@¾:x¾4 ¾/P¾(à¾#ྀ¾ ¾Ⱦp¾ ¾@¾H¾¾À¾¾ؾ¾ ð¾x¾h¾h½ø0½îÀ½ê€½è ½éà½ê€½èн堽ãнé@½ó ½ýо¨¾X¾À¾ ؾ0¾0¾%`¾.p¾4Ⱦ8˜¾<¾?0¾Bø¾E¾Fh¾F(¾C8¾C¸¾D€¾@ ¾=p¾<¾;¾9x¾7°¾3 ¾-¾(@¾%¸¾&¾$˜¾"ˆ¾" ¾"ø¾&p¾(X¾(¾&¾$¨¾!°¾è¾ ¾ ¾H¾ ¾P¾"¾%Ⱦ(¸¾(Ⱦ'ؾ%h¾!ø¾"h¾$ˆ¾)è¾.x¾1°¾4¾60¾4¾-à¾'h¾%À¾(p¾&¾%ྀ¾P¾ø¾H¾p¾ø¾¸¾¾è¾ °¾ ¾¾ˆ¾0½ÿP½ý@¾¸¾à¾¾°½ý ½ñн氽ذ½Ë½Ã½ÂP½Äà½ÆÀ½Ç€½Ç½ÆÀ½¿À½µà½­Ð½©Ð½¯½¾P½ÌP½Ù`½çà½ñ½÷½û ½ûнü½ý½ùà½ú@½ü0½þà½þð½ü½ù ½û ¾Ð¾Ø¾`½û€½öнñ€½ð€½ï½æÀ½Þà½ØP½Ï ½Ê½Ã€½Àp½Á0½ºð½±ð½¯p½¦À½ P½œ0½ž€½™à½“`½•@½”½“½“0½™ ½ Ð½£À½Ÿ ½šà½–ཙ ½š½–དྷ ½‹@½„0½€€½v ½f@½S`½E€½FÀ½>@½0½@½ ½  ½ ½ ½à½@½½à½@½! ½ à½འ€½€½@½ ½€½`½à½`¼ù@¼ò¼ú@¼ê€¼Ñ¼·¼Ç¼Õ¼á@¼ç¼ø½½½&€½.`½2@½9à½?@½<€½A½:€½0à½7À½D ½S@½^@½g@½r½z`½~@½À½†p½0½— ½œp½ž ½¡@½¦ ½«@½¬ð½° ½·à½¸ ½·°½» ½½ ½ÄнʽËÀ½ÉP½Ä½¾ ½½`½¼Ð½· ½¬`½¥`½ à½œ°½š½™@½™p½—½˜½“À½Š ½€@½n ½eÀ½_€½[€½Và½R½Q`½T€½Tà½O ½LÀ½Mà½Q ½T`½\ ½v`½Š`½—н¢½«€½µ ½¶0½¹À½º ½¾°½Â`½Ë½Ô½ÜP½å½ð°½ø¾`¾¾ @¾ (¾x¾¾H¾¾`¾"°¾%ؾ'ø¾'˜¾%P¾"ø¾оè¾¾ ø¾ ¾H¾ؾ€¾¾½þp½ú°½÷½õP½öà½ÿ¾(¾P¾ ¾¾ð¾à¾è¾¾ ¾X¾ø¾8¾ؾ¾ ¾p¾о¾ð¾#€¾'À¾)Ⱦ*ؾ+°¾,(¾,à¾08¾28¾2ð¾2ð¾3X¾5 ¾8°¾>H¾B0¾C¨¾Bà¾Aˆ¾?P¾>0¾?¾?ˆ¾@8¾?ø¾;ð¾5x¾4(¾5x¾8¾<@¾@p¾Dh¾Aо:¾5X¾6è¾8°¾:x¾<¾;ø¾=`¾B`¾D@¾C˜¾Bx¾@˜¾?¾?о@`¾@¾?X¾?0¾A€¾EX¾K ¾O(¾L(¾Fp¾A0¾<ؾ8 ¾5ð¾4¨¾3¾/è¾-˜¾,x¾+P¾)¸¾&¾#о Ⱦ@¾ ¾0¾@¾¾¾ȾH¾#@¾%Ⱦ%¾ X¾À¾h¾¾H¾"à¾$(¾%¾%(¾%8¾%¾&о*x¾.x¾(€¾$¸¾$¾#˜¾#ð¾#ð¾$¾$`¾!¸¾ð¾ø¾°¾ð¾x¾оx¾p¾è¾8¾ ¾0¾à¾ø¾h¾€¾°¾ˆ¾ ¾p¾@¾ø¾P¾H¾(¾€¾ 8¾ ྾8¾`¾P¾ȾP¾˜¾H¾¸¾x¾h¾¾ ¾˜¾p¾ ¾ð¾€¾°¾¾ˆ¾ ¾ p¾ ¾€¾¾x¾H¾H¾˜¾¾(½ø ½ï½ë°½éнèP½äÀ½ß½Ûp½Úp½Ü½àp½ç`½íP½øÐ½û½öнîÐ½æ ½ã½ë`½õÀ¾°¾ؾP¾0¾x¾h½ýP½÷½õ`½÷`½üP¾À¾ð¾ ؾ ¾ x¾ 8¾ ˜¾x¾€¾x¾ˆ¾о¸¾¾¨¾½û½ô0½ñp½êÀ½æ½ä0½å`½å½ßÀ½Þ ½á½ßP½ÞÀ½á½ä ½ê ½î@½êà½ä0½ß½Ü@½Û@½Ý°½Þp½Û½Õ½Ò@½Ðà½Ò½Ó°½Ôà½Ó½ÑнӰ½Ó½Ø@½Ü½ß ½Þð½á°½ãнڽÕð½ÒP½Ñ`½×°½Ü@½á@½ã°½å½éð½ñà½õð½ùP¾˜¾`¾p¾x¾X¾0¾ о ¾¾à¾€¾ ð¾ (¾p¾ p¾ ¸¾`¾ð¾p¾ˆ¾ ྸ¾x¾о`¾x¾¾¾`¾¨½ÿ ½ÿ ¾°¾0¾h¾ Ⱦ¨¾X¾о€¾ð¾¨¾ð¾@¾À¾P¾à¾¸¾ø¾€¾`¾¾è¾°¾à¾h¾¸¾#x¾&(¾&¸¾%ˆ¾&¾%˜¾$H¾!°¾À¾@¾8¾ȾÀ¾p¾!¾$ˆ¾(`¾+à¾.¸¾2è¾8¸¾;X¾?0¾Bè¾Gø¾M¾N¾Ox¾Ph¾SÀ¾Wø¾Zà¾]€¾_è¾dè¾h ¾kоm˜¾m(¾n¨¾o¨¾r˜¾v¾zÀ¾}¨¾~€¾À¾H¾¨¾h¾‚0¾D¾}à¾y°¾u¾r¸¾n¾g`¾`¾Y¨¾U¾S ¾Nà¾H8¾B¾:Ⱦ4x¾1¾,À¾%¸¾¨¾H¾à¾ð¾è¾P¾ X¾ X¾h¾p¾ˆ¾ˆ¾ о°¾p¾ؾؾ¾`¾à¾¸¾ À¾"о$¾$ ¾(x¾,˜¾/ ¾4P¾6@¾3 ¾, ¾' ¾((¾*8¾,¾+ø¾+ ¾)p¾&8¾&h¾%¾"0¾ ø¾ 8¾ X¾`¾À¾¾ˆ¾`¾¨¾ˆ¾¾0¾À¾è¾ˆ¾ؾ8¾h¾h¾ (¾ H¾ X¾x¾¾оÀ¾8¾8½ú½õ€½ô0½óнõð½ø°½ùp½þ ½þ¾ˆ¾0¾@¾€¾p¾¾P¾À½ô€½ó ½ò½ó ½ó ½ôà½ò½êp½ãð½Üà½Û°½ß½åð½è ½é€½æ½áà½àð½ä@½ä°½ãнæ`½éÀ½íp½î½óp½ô`½óP½õ€½öð½ùÀ½þ ¾X¾о €¾ @¾h¾P¾¨¾x¾h¾ø¾¾h¾X¾оˆ¾¾ˆ¾H¾(¾H¾p¾ˆ¾à¾оh¾¾¾P¾ø¾0¾¾°¾X¾À¾h¾à¾ ¾ ¾ H¾ ð¾ ྠP¾ X¾ p¾ @¾à¾x¾ø¾оø¾ø¾(¾¾¾X¾¾ ¾¨¾!¸¾#X¾#¨¾#x¾$о&@¾+`¾1€¾8¾=¨¾BH¾C€¾Cø¾Dh¾Ex¾F¾Gà¾Iˆ¾O¾U˜¾Y¨¾[x¾[ ¾ZP¾YX¾UоR ¾P˜¾P¾Rp¾RȾS°¾TоVà¾V0¾T¸¾Sp¾Q0¾O¾P@¾Q¸¾P ¾M¾JоLp¾NÀ¾Pø¾OؾO¾N`¾N¾Ph¾R¾R¸¾S¾S0¾Sˆ¾Th¾Wо[H¾]0¾\P¾Zè¾ZоZ`¾Zð¾\X¾] ¾]0¾]¸¾^x¾]о[оXÀ¾V¸¾W@¾WH¾Vh¾R8¾M¾GоC°¾A¾@(¾>˜¾?ؾ@`¾?P¾=°¾:h¾7@¾4h¾-¾'H¾"x¾`¾8¾à¾@¾0¾ ˆ¾è¾@¾à¾¨¾(¾¾оP¾ø¾#°¾)€¾-X¾.¨¾.À¾/ð¾18¾4x¾8¸¾=ȾDX¾Jà¾O0¾Q ¾S¸¾T@¾T¨¾T¨¾Uh¾VH¾WоXX¾VоV8¾R¸¾OX¾Jð¾Eø¾CоC`¾C¾@ø¾>0¾;¾7p¾1p¾+¾#¾`¾ؾh¾ P¾ x¾½ú@½çp½Õ€½Å ½µ`½©ð½¡À½™@½•½™½›€½ž½P½šÐ½–P½”½“°½”ð½–`½œ ½§½²@½º`½¿@½À½Ã°½Äà½Åp½ËP½ÐÀ½Õ@½Û@½Þ½â°½è ½ìp½ìнê0½æÐ½å€½å@½æp½ä0½Ý½ÏнÁp½¯½ŸÐ½‘ ½‡@½{À½k`½] ½O ½FÀ½?À½8€½- ½%ཽ@½`½ ½à½@½`¼þ€¼ù€¼ÛÀ¼¼€¼€¼ŒÀ¼ˆ¼…@¼i€¼J€¼¼»÷»î»Ë»„»:h;¹< <1€`=7=+À=* =+`=4 =>@=@À=<=.`=%@=&€=*À=,€=.=1À=3 =2@=2 =7 =8@=8@=8@=;`=DÀ=B`=7=%À=à=à=à=`==À= == €=.=7€=?@=Gà=M`=TÀ=]=l`=yÀ=‚°=‰`===ŽP=Œ`=ŽÐ=Ð=‘°=œ=£à=§ð=«€=® =±°=µ=´°=¸€=¸=µP=°=§=¢=¢0=¤`=¥`=£P=¢= à=P=š =—P=–€=“ =“`=“=“°=à=Œ=†Ð=P=€€={=n`=c`=Y€=P=Eà=:€=* =@= <åÀ<Ð<Ç€<È€<Ò@<Ú<Þ<ÝÀ<éÀ=`=€=%=?€=X =q =ˆp=”=ŸÀ=ª°=³P=½ð=Ê=Ù€=ãÀ=ì°=ô=ý>@>@> >x>P>ˆ>˜>è> ø> Ø>È>H>x=û=õ =ëÐ=å€=à`=Þ =Ú=Ô=ÍÐ=È =İ=Áà=À=Áà=½€=»0=µ€=¯@=§ð=¤°=¤€=¤à=¦=© =¬p=°P=´`=¶°=½@=Â=Äà=ÈÀ=Ì€=ÔP=Þ°=ê =òÐ=÷=ü >@>h> `>`>`>à>`>(>X>È>€> >¸>¨>8> À> X>P>ð>@=ú@=ñp=ì0=ì =ì0=è=ã°=â€=â`=â =ß =Ù =Òð=Í =Ç0=Ä€=ÀÐ=ÁÀ=Æ=Ê@=Ï`=ÐÐ=Íà=̰=Ìð=Í`=Р=Ó =Ü@=âð=èP=ê =çà=èà=ë=ï =ð€=ïÐ=îà=ñÀ=öÐ=û`=ú =ûÀ=ÿ€>h>°>˜> > ð> È> Ø> p>€>È> @> > `> ø> > > È>`>Ð>=ÿ@=ÿ>> =þÐ=üP=úÐ=ø@=ô`=õ =õ=öP=ö€=÷°=øP=÷ð=ö@=õà=ö=öÀ=û0=ý`>Ð> >x>à>À> H> ¸> °>Ø>¸>X>À>ˆ>p>€>p>Ø>€>>à>>">$>$x>$ø>$Ð>%>$È>"ð>!Ø> (>8>>€>Ð>è>À> ˜> `>0>> ˆ>ˆ>H>>>>8>¸>>X>Ø> >x>>8>€>è>p>p> ˆ>$ð>( >-0>1H>40>4˜>30>/¨>*(>$Ð>">"0>$P>% >%¨>$>"Ð> ø> >(>X> >X>"ˆ>'>, >2H>4>7@>:(>=À>AÀ>F˜>K@>Q>V>[p>`ø>ex>h>i€>jˆ>kp>k¨>jÀ>k°>k`>jh>i >h0>f@>dð>e >cø>cˆ>b(>a >`>_8>] >Zð>XÀ>UØ>Tè>Sx>S>Rx>Q>Nà>L@>JX>I°>I>H¸>Gà>Eh>B@>AÐ>B@>Dh>Ex>Dø>CÈ>@ˆ>=8>7>2€>1ˆ>1>1p>2ø>5ð>8ø>;¸>>¸>@>@¸>?H>=ø>?H>?`>?P>@Ø>A°>BÀ>Aø>@ˆ>?P>?À>?>>8>>>@@>C8>FX>FÈ>E˜>D >B@>@0>?Ð>@¸>@`>@À>A@>B8>D >Dp>C˜>B0>A>?x>8>4X>0À>,À>(°>%È>!x>À>>˜>p>P>h>`> > ¨> p> X>`>°>x=ý =ÿ0>(>€>Ð>>°> H> ˜> ø>  > 0> Ð>0>Ð>ø>`>ð>¨>(> x> > ¨>H> =ÿÀ=÷Ð=óð=ð`=í0=çp=Þ€=Öp=Ï =ÁÀ=µð=¯`=«ð=«P=¬Ð=­ð=­°=©À=« =²°=¹ =¼ð=À=Âà=Á =Â=Á°=À`=¾ð=À=½Ð=º=·=µà=²Ð=°p=°ð=±p=³`=´ =´p=²à=µà=»=Á=ÅÐ=Ê`=Î=Ó =Ø=ÞP=á`=ä`=æ =ê0=èð=ç@=éð=ì=ïp=òÀ=õ@=ô=ñ0=ìð=ê€=é=èÀ=ép=é°=è=é@=ç0=æÀ=äÐ=ãp=áP=ßÐ=á=â=å`=ê0=í=ì`=í =ñ@=ôà=øð=úÐ=þ@>€>h> > H> °>¸>ð>>à>h>p>ø>x>Ø>X> >à>@>ø>>(>>è>¨> Ð> X>  >H> >=ý@=ù=ô@=íà=åÐ=à=Ûà=ÚP=ÖÐ=Õ`=Ï0=ÐÀ=Ïð=Ò =ÕÀ=Ù€=à=å°=íÐ=÷=ÿ€>ø>è> Ø>`>È>0> >$X>'X>(à>*È>,@>, >,@>.X>0x>4ø>9>;è>=H>>@>>><°>;ð>;>:Ð>9(>6>3 >0È>.à>,˜>*À>(x>$à>!à>h>> >@>X>>>H>`> >>> à> (>ð>@>à>P>0>€>0>>>>È>X>X>ˆ>x>H> > è>ø>˜>`>Ð>p>°>ð>> >È>è> ˆ> > >Ø>>à>Ø>>¨>˜>ð>x>¨>€>p=ý=ø@=õ=ð€=ìp=ç0=Þð=Ù=Ó=ϰ=Ë@=ÇÀ=ÄP=Âð=Â=ÃP=Ç@=É@=Ë`=ÏÐ=ÑP=Ó=Õ =×P=Û@=ß =à =ãÀ=æà=ç=æÀ=ä=á =ÞÐ=ÙÐ=ÑP=Ê@=İ=Ã@=Å€=Ì=ÑÀ=×À=Üà=ß0=á =âp=âà=á°=Þ=ß0=àÐ=ßP=Ý@=Ú=Ûà=Ý=ß0=Ü`=Ú=Ø`=Ô0=ÑÐ=Ñà=Ð`=ÐÀ=ÑÐ=ΰ=ÍÐ=Ê€=Èp=Çà=È@=Ëp=ÏÀ=Ñ€=Ñ@=Í`=Í=Ì0=Ì€=ÍP=Î=Ï0=Ïð=ÍP=Ë=ư=ÆP=À°=¿à=½ð=º =º°=¸À=¹@=¼°=¾p= =È =Í€=ÒÐ=Ö0=Ú=à=ä=ä€=ä°=ã`=á=â =ÞP=ÜÀ=ØP=Óà=Îð=ʰ=Å=Á@=ºð=µÐ=°À=­P=ª =¦=ŸÀ=—ð=’`=“@=˜`=0=¤=§=§P=¥ =¥=¥Ð=¤=¦P=ªÐ=¬€=°0=²°=µ=¶`=´°=´à=µ=¶=´°=±À=®=ª°=¦°=¡°=ž@=˜=“ð=‘p=Ž=ˆð=ƒÀ=`={ =~ =~À=€ð=„ =†ð=‰p=ˆð=… =ƒ =€°=}@=z€=~à= =| =w€=f€=Y=O@=A =3€=#À=`= `= <ö<àÀ<ÂÀ<§<@<^€<#€;§;T;;;T;(;X:pº¼»v»¼»þ¼,€¼Y¼‡À¼@¼¯À¼Å@¼Ô€¼çÀ¼ÿ@½ ½½À½'@½0 ½6@½AÀ½K½S ½[½V€½ZÀ½Wà½O`½Là½EÀ½=@½8€½3€½.À½* ½-À½.À½$À½@½ ½ €½€½ ½ ½ ½ འ½½à½`½"à½"À½ ½ €½$`½, ½7@½?€½H ½O@½T€½UÀ½V€½P€½F@½>à½<€½= ½=@½;`½A`½I`½M ½NÀ½M ½L`½@à½AÀ½>à½< ½E`½Jà½Q ½WÀ½Z½^À½a@½g ½dà½kà½z€½„@½à½•½À½¦½¯@½·€½Áp½Êp½Ô`½Ý½åнê½ñà½û¾@¾ø¾о¾¨¾ `¾ °¾°¾€¾p¾¸¾(¾X¾è¾h¾H¾P¾ˆ¾0¾ø¾¾¨¾¨¾(¾¾ ð¾ h¾ؾX½ÿ½ú€½÷À½ô0½óp½î0½å½Ûp½Ï@½ÂP½¼0½·@½²½¬½¦½¡P½š€½–°½‘Ð½Ž½‹ ½`½“½—°½½¢½¨à½®@½¶°½¾à½ÉÀ½ÙнçP½øà¾о ؾà¾ø¾x¾ؾx¾¾@¾ ྠ¨¾`¾0¾(¾¾ P¾è¾@¾P¾ð¾ð¾(¾ø¾ о @¾Ⱦ¾h¾ `¾ ¾ €¾ X¾ ¾ø¾H¾ ྠ¸¾ 8¾ p¾ P¾h¾@¾ @¾ P¾ h¾ ¾  ¾ h¾ ¾ о  ¾ ¾ˆ¾p¾¾À¾P¾ ¾ P¾(¾X¾¾p¾¨¾@¾`¾¸¾¨¾¾À¾¾p¾ ¾X¾ ¾¾ð¾¾`¾ ¾(¾ ¾(¾¸¾(¾X¾ø½ûнû°½ú ½úP½û`½ú ½ùнùà½ù ½ú`½ûP½þ¾ ¾À¾оø¾h¾о½ù`½ò ½ì@½æ½à°½á@½á½æ ½ëà½ñ ½ðP½ò°½ö½÷`½û ¾ˆ¾x¾X¾À¾0¾P¾¨¾¨¾ð¾(¾¾@¾оˆ¾¾ ˆ¾ ¾8¾x¾¾À¾p¾8¾`¾¾Ⱦ°¾`¾@¾8¾¾¨¾ 0¾  ¾ ¨¾ @¾ ¾¨¾h¾ø¾¾¸¾¨¾(¾8¾H¾ ¾ ¾@¾¾p¾Ⱦx¾ €¾ 0¾ (¾ (¾ ð¾ `¾ À¾ h¾P¾˜¾ ½ü°½ø°½ó0½í0½èð½æP½æÐ½èp½ì½îà½òð½õ@½ùнÿð¾H¾0¾ ؾ¾h¾(¾¾ ¾ ¾ ¾ Ⱦ ¨¾ H¾ؾ €¾ ¨¾"¾$¾$0¾%€¾$¨¾$@¾#€¾"p¾ À¾@¾8¾X¾h¾`¾¾è¾ ¾h¾˜¾½÷P½ñð½ð½ñ@½ñ½ìð½é ½å ½à½ß½Ùp½Òð½Î½É€½Å½¼ð½º½´½°p½­ð½®P½°€½´½»½½À½Ä`½Ë@½Ô½ßÀ½é ½ñP½û°¾H¾о H¾ ¨¾ؾ¨¾¾¾ȾP¾ ¾ ¾¾ ¾(¾ ؾ `¾À¾P¾¾ؾ½ÿ ½û€½÷`½ò°½ï@½î°½êP½æP½ä°½ãp½ßP½ÛÀ½Õ`½Ð ½É½Ã0½»`½¹½·P½¶ ½¼ ½½P½À@½Â½Ã@½ÅÀ½Ì½Ôà½ß0½ê ½ôð½ÿ ¾`¾Ⱦ (¾ ˆ¾ À¾ ྠh¾ о@¾ؾ¾è½þp½úP½÷ð½õ½ó`½ñнó0½òнñ€½ñ ½îP½î ½ëð½äà½Ý ½×`½ÏP½Éð½Ä ½¿°½»€½·p½³`½°½«°½¨ ½¦½£½¢€½ @½ p½ p½žÀ½žÀ½@½œÀ½œ0½œ@½P½Ÿ°½Ÿp½¡Ð½¥À½§ ½«ð½¯à½´ ½²`½Ä€½Ó`½Ò°½Ó½ÎнÌ0½ÆÀ½Á€½»`½·À½³`½³@½¶0½³@½³0½³½±°½°°½°@½«à½¨°½¥0½¢°½ ð½Ð½à½½½œ°½›°½€½°½Ÿ ½¥P½¨ ½© ½®À½°ð½µ½³ ½¡ ½œ ½À½ž0½ŸP½žP½œ ½›°½šà½›½›½›À½œ€½œP½°½ž ½ž`½ ½› ½šÐ½š0½œp½›°½™à½˜P½—`½”p½‘ ½p½ŒÀ½‹0½Œ@½ŒÐ½°½½‘€½“°½–°½™½€½0½ p½¤À½¨Ð½®½²`½µ ½¸Ð½»ð½»p½¼0½½ð½¿à½Â°½Å@½ÆÐ½É½Èp½É°½ÏP½Ô ½Ø ½Ù ½Ûнà½æP½ê€½ð½ò½öð½ùà½ø°½ù`½ú€½ø`½÷°½ö½õ½ñ½îp½ë0½æ0½ãÀ½â€½ßP½Ü½Úà½Û½Ù€½Úð½Ú½×½Öð½Ò½ÐP½Í`½Î½Ï€½Ò ½Õ½×P½Ù ½Ú@½Û@½Ý`½áÀ½äP½ç€½ì°½ïp½ö ½û€½üð½þ¾о¨¾è¾ X¾Ⱦè¾¾À¾¾(¾€¾ H¾#`¾$Ⱦ&¨¾*h¾.X¾0(¾2°¾5 ¾8ø¾<˜¾A¾F¾J`¾M¾Q8¾U ¾XȾ[Ⱦ_`¾aؾdоeX¾gà¾gP¾f€¾e8¾cø¾cÀ¾bx¾a¾^ؾ[оYX¾V@¾SX¾PȾMȾJ¾G¾Eà¾EÀ¾D(¾C¾Bà¾C`¾C¾DH¾DX¾EX¾E@¾EÀ¾H0¾K¾MX¾Oˆ¾R0¾SÀ¾U¾UH¾Sè¾T¾Sp¾RоP¸¾NؾLè¾Iè¾IX¾Gð¾F¨¾Eð¾D8¾BȾ@€¾>˜¾?¾>x¾>¾<Ⱦ;¾;¨¾;8¾:¾:H¾:P¾8À¾8ˆ¾7¨¾5è¾4p¾2X¾/H¾-P¾+(¾)p¾(€¾'ð¾&ؾ%h¾%Ⱦ$¾"x¾ ¾Ⱦ¾X¾X¾ø¾˜¾`¾ˆ¾!X¾$¾$°¾&¾&8¾%ؾ&x¾'à¾)H¾+0¾-¾/¾0à¾0¸¾/0¾.X¾,¾+P¾+è¾-ˆ¾.P¾/x¾/¾/°¾.è¾0X¾0¾0ˆ¾0à¾0P¾0À¾1p¾/À¾-Ⱦ-¸¾,x¾(x¾$(¾ (¾ø¾¾¾€¾ؾh¾0¾X¾ 0¾ø¾X¾¾¾¾H½ÿ0½ý0½úp½ø½õ°½õ ½ô0½ôP½ô ½ö€½÷½öн÷°½ùP½û ½û°½ü€½þ`¾¾À¾ˆ¾P¾¾8¾ ø¾ ø¾ ¾ à¾ø¾x¾¾¾ð¾¨¾€¾ð¾H¾!`¾#¾%ð¾(`¾*`¾,ø¾.°¾/ ¾/о/¾- ¾-0¾,`¾+°¾+ ¾)X¾'ؾ'ˆ¾'(¾%˜¾#¾"оH¾¾ð¾ؾо¾  ¾ ¾`¾à¾8¾ ¾оH¾¾H¾¾¾ ¾ð¾8¾À¾0¾ ½þP½ûp½øp½ô@½ñ½í@½è°½ßÀ½Ù°½Ð`½È½ÁP½¼€½·@½±€½®Ð½ª°½ªà½¨½¨À½ª°½ªà½®°½¯ ½±p½¶°½¹€½À€½Â€½Á0½¾P½»À½·Ð½´°½°0½­@½« ½ªP½¦À½¤½¤€½¢Ð½¡P½P½•`½ŒÐ½†à½‚ ½p½|€½{@½~ ½}`½| ½xÀ½tà½kÀ½dà½X½M ½Dà½9½' ½À½ ¼ã@¼À€¼®@¼’@¼¼¼h€¼c¼]€¼|€¼~¼|€¼‚@¼‰À¼›À¼µÀ¼Î@¼ê½ ½à½½%½-`½6 ½:@½;`½;`½<`½;€½8À½9½;€½8€½6 ½5½4`½/ ½&@½ à½$€½%@½,½0@½0À½5à½7 ½4@½,à½%À½ ½à¼à¼¹€¼š@¼‚¼T€¼2¼€»é»šºø:¼;²<(°¾B¾C€¾C¨¾CX¾Bˆ¾Aè¾AؾB¾BX¾DH¾DؾG¾H ¾J0¾LP¾M°¾O¨¾QÀ¾T¾WÀ¾Zؾ^(¾`P¾c`¾cؾbp¾a¾_Ⱦ]`¾\p¾Zø¾X˜¾Uð¾SÀ¾Q`¾MоL ¾I ¾H¾Fè¾EȾDè¾Ch¾B°¾@ð¾> ¾=¾:è¾:0¾9p¾8à¾88¾7à¾7 ¾6 ¾7¾8¾8`¾8(¾6À¾5 ¾5(¾5p¾4ؾ5ø¾78¾7à¾9P¾9ð¾;À¾?p¾C`¾Gh¾Jx¾L@¾LؾO¸¾Q¾SÀ¾W˜¾YÀ¾[ ¾]¾^¸¾_X¾_@¾^ˆ¾_0¾`@¾`(¾`¾^h¾\p¾[ˆ¾Y°¾X¾W¾U¾T¸¾TH¾Tð¾T ¾Qø¾NоL8¾Hè¾FÀ¾DȾAð¾?Ⱦ=Ⱦ=P¾<¾;ؾ;¾;h¾;€¾<8¾>`¾?à¾B ¾Fˆ¾K¾Op¾Sx¾VX¾Y@¾\p¾^˜¾a¾cp¾c°¾d¾d ¾bð¾b¾`@¾_¾]¾[è¾[X¾[0¾YÀ¾Y¾Y@¾Y8¾Z¾Zˆ¾[о\¸¾\ؾ_¾b¾d ¾f0¾e0¾e¨¾eh¾f¾d˜¾bÀ¾`˜¾]X¾W ¾Q¾Kh¾E8¾=à¾8h¾4X¾00¾+¨¾) ¾'Ⱦ$¾$˜¾%P¾%ˆ¾(0¾,Ⱦ1(¾5˜¾9@¾<à¾>˜¾>¾=Ⱦh¾@ȾAð¾Dh¾FÀ¾Hø¾K ¾N€¾QоU ¾Z°¾^ð¾b°¾eè¾i¸¾lp¾oˆ¾q ¾rоsȾu¾u¾tˆ¾t¾rоq¾mH¾f°¾`P¾X¸¾R¾M8¾Gà¾E˜¾Bø¾@0¾=°¾:¾7p¾4о2 ¾0à¾0 ¾0¨¾2h¾3¾3о4À¾4ˆ¾5X¾6è¾8h¾9`¾;€¾>8¾B(¾G˜¾M¾S¾UȾX`¾ZP¾Z`¾YX¾Wà¾V¾S€¾PȾN¾KÀ¾G°¾Bˆ¾=о9h¾5€¾1@¾-¾+ø¾) ¾&H¾"¸¾¨¾x¾Ⱦ ¾@¾ ˜¾¾à½ý½úнöнõ½ô½ò ½ò ½òÀ½õP½õнùð½úà½ûð½ý°½ûнûà½úð½ø`½õ°½ñ½ìà½ê`½èð½ä0½ÝнØà½Ó ½Ð½Íà½Í½Í½Ð0½Ó`½Ô@½Ø ½Ý½â°½è½éð½ë`½ì°½îнò@½öн÷€½õ ½õ0½ô@½õ½ô€½õ`½ö€½÷À½ø`½ûp½ü½û½ûP½ü½üP½þp¾(¾°¾h¾ ¾@¾¨¾h¾H¾ h¾$0¾(¸¾,¸¾0ð¾3€¾7¾:è¾>ˆ¾C¾FؾJx¾Nð¾RÀ¾VоZ¾\è¾`X¾bh¾c0¾dȾe¾e˜¾f@¾fè¾f°¾g¾g¾eH¾cè¾cP¾c¾b¾b`¾bÀ¾c¾b¾`¨¾^Ⱦ\P¾Y¾Uø¾Sx¾P ¾PX¾Nð¾N˜¾Oh¾Oø¾P(¾PP¾Q¾Q¨¾R¸¾SÀ¾U¾U@¾Vp¾Wx¾W`¾W°¾Vð¾U ¾T ¾S8¾S¾QоPè¾O(¾NÀ¾MȾL¾L¾Kà¾J¨¾I€¾IH¾Iø¾Kx¾N¾N(¾Nh¾LȾL€¾K ¾M¾LȾMx¾N˜¾Np¾Nð¾OH¾NH¾Lð¾Lp¾Jˆ¾Jè¾K°¾LÀ¾N@¾OȾOX¾P ¾M`¾M¾Jh¾G`¾D¨¾B@¾?˜¾= ¾:˜¾:8¾8p¾7P¾6@¾4ؾ4à¾4à¾6`¾6˜¾5Ⱦ5`¾5 ¾5ˆ¾4˜¾3о1ؾ/ð¾.@¾+P¾(X¾% ¾"€¾À¾Ⱦ¨¾о ¾ 0¾¾½øð½ó½ðP½ðP½ñнòà½øÐ½ü°¾ ¾0¾x¾¾p¾ (¾(¾H¾ˆ¾о X¾!о" ¾!˜¾!¾"¾#h¾%˜¾(¾+˜¾-¾-о-0¾,Ⱦ,`¾+¾+€¾+¾+ð¾-h¾-о.о.À¾-@¾*p¾&Ⱦ"¨¾Ⱦ¾à¾¾ ྘½ü°½ï@½ß0½Íð½¾€½°à½¥À½œð½–`½’À½Ž`½P½ˆ0½ƒ0½{½n½h@½b ½\À½Q½Eà½< ½/à½# ½½ ½`½`½ ½! ½" ½#@½& ½+ ½-@½/à½/@½6à½@`½Q½]½l`½{ ½à½‰°½½ð½“н–0½›½ `½¤À½¨½«°½¬Ð½­Ð½° ½²à½´°½³ ½° ½«½¦@½¡€½› ½—À½“À½°½Œ@½†`½ƒà½½€½€Ð½z`½x½uÀ½s€½sà½s ½y`½€ð½0½ƒð½†°½‰ð½ŒÀ½@½‘0½P½’€½“ཕ ½˜p½›À½œ½Ÿ½¢ ½¢@½£°½¦À½¦Ð½¦@½¦½¦€½¤ ½¥P½¥€½ °½ž½šà½•ཎ0½†½{@½h½S@½B ½/½$€½ ½@¼î€¼Ó€¼À¼¹¼µ¼©@¼°¼±@¼¹@¼¶À¼Á¼Æ@¼Î¼ä¼úÀ½ `½½*@½7À½@à½I@½R½^`½``½kà½p`½w ½`½ƒp½„ð½„@½‚@½{½o@½_à½Wà½O€½Bà½; ½5 ½*`½`½@½ ¼Ú€¼»À¼™¼v€¼6»Ïºø;@;ì<3€Ð>Ø> >>8>>"x>)>.8>3À>6È>9h>;>=>>à>? >@h>?Ø>>P>=p>;€>9P>6À>3x>/p>,Ø>+h>(0>' >'(>&ˆ>%°>%˜>%¨>#p>!`>È>h>(> >(> Ð>¸>=ûÀ=ñÀ=ê€=å=ß=ÜP=Ø =Ø=Ù0=Þ€=â=æ0=éÀ=í =î`=ïp=ôP=û>è>à> > ¨>€>>P>>`>>x>>>H>ø>è>"ˆ>%°>( >+>+ø>+x>,à>.>.>.x>0ø>00>-ø>+>(X>& >%H>%è>%ˆ>$˜>$h>$ˆ>$à>%¸>&`>'x>'È>(ð>*@>*À>)ð>)8>'˜>%ø>!ð>`>€>ø>¸>ð>>>Ø>À>@>h>h>`>>p>H>ˆ>À>Ð>>À>@>>ø>>à>¸>è>`>Ø>>Ð>à>!>"€>$h>&è>(ˆ>*(>,>-à>0Ø>3>6¨>8à>9`>9>9 >8°>9H>;@><è>=è>>È>?>?>>>=>;ˆ>:@>8P>7@>5È>4@>5 >4p>4ø>5X>4À>4x>3X>3x>30>3¸>4€>5¨>7h>5Ø>5>4(>0¸>-°>) >%ø>">!P>!> è> ¨>! >!Ø>"@>"X>#>"¸>#>#à>$p>%P>&˜>(ø>+H>,`>,à>-`>-˜>.>/>0à>2X>4H>40>3>1x>.˜>,`>)¨>'ð>&h>$@>$X>"¸> ¸>À>à>°>€>>ð>ø> ð> `>¨>Ð>=ü@=÷p=ð=ç°=â=ß =߀=à=á@=ßÐ=Þ =Ûð=×p=Ò0=Ë =Æ0=ÂP=¾=¹`=¶°=¶p=´0=³p=²p=¯0=«P=©À=¨ =¦ð=¥ =£0=¡=¢à=¡=Ÿ°=À=™p=—°=–À=”`=“°=“@=”=—à=—°=™À=˜ð=—Ð=™€=œ€=œà=ž=¡P=¢=¡`=¤0=¨`=ªð=¯`=³ =·@=¸`=¶ð=¹=¹p=¸ð=µ =²°=°=©°=§ =¦@=¢ð= 0=›p=™=š@=›=ž`=¢À=¦°=« =±p=»à=Æà=ÑÐ=Ù =áð=èp=ï°=õ°=ùÀ=ÿ>x>¸> €> ð>h>>0>ø>€>X>@>À>(>È>x>p>x>>ø> Ø> h> Ð> X> ¸> à> Ø>€>X> >¸>À>ˆ>˜>">$°>'Ø>)p>+>-`>.ˆ>0x>2>2`>3>5 >5ø>6ð>7Ø>9h>;Ð>=p>?°>B€>D >G>H˜>I°>M0>N¨>Q>S>T˜>V >V>Uh>S¸>S>QX>NX>Mˆ>I˜>Fè>Bˆ>=À>8>2À>-p>*>% >!¸>Ø>>x>P>¸>p> >8>H>X>À>è>¸>°>È>>¸>"à>%0>'¸>*>,P>/P>1¸>4Ø>6H>80>:°>?H>B¨>G@>Iˆ>J€>Kx>L¸>M¸>NÈ>O >NÐ>M>I0>E>?˜>:˜>5è>1>, >(è>%h>"ð> ð>à>°>Ð>>˜>¨>0>À>0>ð>@> >>X>>°>ð>Ð>`>¨>è>ø>8>È>@>(>è>0>è>p>@>!>">$˜>'H>'€>(H>* >+>+x>+8>*X>*è>,>.(>2>3`>3À>3>0°>/8>,P>)Ø>'H>$€>!>`>P> > >°>@=ùð=ïð=åp=Ü@=Òð=Èð=Á@=º°=²à=­ =¨@=£À=œð=“€=°=Œ =‰0=† =…€=„0=ƒ€=… =ƒ@=} =|@=x =y@=w`=oà=g€=^ =L =<à=-@=#à= = = ==`= = `= à=€=@=# =0=!`===à=À=`=€=(€=8=1@=/`=(À=)`=#À=à=`=`<éÀ<ÏÀ<»<–€€¼D€¼:€¼,€¼¼»É»xºø;;z;Ô<€<6€<;Ó;\9€ºü»,»‘»Ÿ»b¹ ;€<€ =@`=A@=EÀ=M@=P@=Sà=Xà=]`=d@=i€=g =d =_À=V€=O@=F=B =5À=,À= À= =<èÀ<×<¾€< €<‚À@½; ½;À½>À½?@½@½A`½A€½;€½6 ½% ½À½`½@½@½`½`½ ½à½!À½½@½ ¼ø@¼â@¼Î¼¾@¼µ@¼³À¼°¼©@¼¦@¼¢@¼Ÿ¼¦€¼ªÀ¼«@¼¢@¼—¼Š€¼y¼J€¼$»Ì»T:¨;ª<€¼F€¼]¼‚€¼•¼°€¼Ï€¼Ý@¼óÀ½`½ ½À½½½"à½$à½) ½+`½* ½(`½" ½½ ¼ð€¼Û¼À¼ ¼ˆÀ¼b¼<€¼)€¼»È»‘»•»~»F»º°¹`:p;;`;‘;¹;õ<€<4€=;À=:À=;€=;€=> =?à=?à=@ =Bà=G`=K=P@=W =^à=fÀ=g=i@=n€=hÀ=``=W@=RÀ=Kà=K@=OÀ=R€=UÀ=N€=F =:@=0 =%@=à=  <êÀ<º€<”À€¼0¼$¼¼¼ €¼&€¼>€¼@¼*¼(€¼€¼ »ý»Ü»°»‹»N9;v< €À==À=>`=AÀ=K€=Qà=^`=m€=}À=‡ð=P=’`=’Ð=‘=“=’=’=”=”€=”P=”0=•€=—`=˜Ð=™€=›P=Ÿ=žà=¡p=¢@=¤€=¦à=¥=£`=¡@=À=š =—P=•`=‘À=“ =– =›`= ð=¥€=¨p=©0=© =§ =¤°=¤0= 0=™`=‘€=‰ð=ƒ0=tà=fÀ=[`=R`=MÀ=J`=L€=M€=O@=Y =g@=o€=tÀ=xà=x =u€=xÀ=w =yà===„`=…°=‡p=Š =Œ=ð=’p=›0=¥P=² =À€=ÌÀ=Õ=Ü€=á@=åÀ=éð=ë€=ïà=ö =ù =üp=ÿ >ˆ>@=þ =÷à=òÀ=ðÐ=ï =ñÀ=ñ0=ôà=ôÐ=ó=ð€=ëð=æð=ã =Þ =ÛÀ=ÚÐ=Ü0=Ú=Ú=×à=ÒÐ=ΰ=Æð=Á =¼P=· =µp=³ð=¯p=¬=©P=¥à= =›€=•p=p=†=~ =v=pà=k =eà=b`=` =[@=[€=T`=T=U=V`=a@=o`={`=‚°=‰=à=’€=•P=™=›= = ==œ =™°=™p=•°=”=“à=”=”À=—@=›À=¡=¥à=ªÀ=­0=®à=¬P=«@=¥0= °=@=œ`=š=š=œà=žp= €=¢p=§=­ =´P=¹0=º=»€=»ð=¸`=¸@=²°=«À=¤À= =—€=’À=‘ =‘ =‘à=ð=ŒÐ=Œ=ˆp=‚°=}À=wÀ=s`=p`=f =^`=X`=Q =Mà=HÀ=H@=D`=C =B€=CÀ=@@=9@=1 =*À=)`=!à=€=€=`==À=À=!=- =;À=K=Xà=h =yÀ=‡ =à=œp=¤@=«P=¸`=ÃP=É=ÍÀ=Ñ=Óp=Ö`=Ø@=Ùp=Û =Ù=Öp=Ð`=Å =¾p=¶à=ª= =š°=•À=’`=’=“0=”à=š=ŸP=£=¦€=¨€=©°=« =¯À=±ð=´=¶P=·€=·ð=µÀ=³À=³=°0=¬=§ð=§à=©=­ =³à=¹@=½Ð=Â@=Æ =ÈÐ=É =Í`=ÒP=Ø=ÝÐ=á`=åð=ê=ï =ð =ø0=ÿ`>H>è>è>  >À>°>ˆ> >`>!(>%>(h>,Ø>1(>5h>9><Ð>?X>A>Bø>Cø>E >E >E0>DÐ>CP>Aà>>¸>;x>8¸>7X>5Ð>3X>0¨>-À>+ø>(ð>'>&>%>$(>"`>!>ø>>Ø>>0>@>(>H>è>È>H>€>X>À>˜> 0>!8>#P>$è>%@>'>'Ð>'X>&¸>&>%ˆ>%>$°>$ð>%H>$8>$à>$p>%h>%(>'>)>*¸>-X>/h>1¸>3ð>3è>4h>5>6>7È>8ð>:È>=h>?p>A >CP>E0>H0>J0>LÐ>NX>PH>Qà>T°>WX>Z`>^ >bÀ>f°>iÀ>mð>pØ>s>w >{€>>`>‚¼>ƒL>ƒ4>ƒ˜>ƒh>‚x>€ü>X>zÀ>sÀ>l¸>cÀ>[Ø>T>L >F >@@>;È>7p>2>.h>*Ø>'€>&>%(>#0>!È> ¨>!>!> Ø> X> x> X>X>¸>¸>à>¸>>!h>#h>%H>'€>(Ø>*è>,Ð>0(>38>5ø>9Ð><8>@P>B8>EÈ>H(>K(>Lp>N`>P0>Q8>R>S°>U>V>XØ>ZÀ>]>^8>_ >_ˆ>`>^È>]>[>X˜>UH>Qø>PX>N€>O>O >O >Ph>Pà>QX>P8>Oˆ>OH>N°>OP>P>Oø>Q >R¨>S`>Tð>Up>U°>U¸>T@>RH>Ph>MH>KÀ>KX>IÐ>I¸>J >J>L>MÈ>P€>S€>W >Zˆ>]>`>b˜>cà>e`>gÐ>i¸>lP>ox>rà>vÀ>z˜>~> >€d>H>€>‚>‚>˜>€È>€>€ >~è>~>~ø>|ø>{ð>{è>{°>{Ø>zÈ>zp>y>y`>yh>yx>yh>y>wð>uð>t>qà>oÈ>mØ>kÐ>i¸>gè>eÐ>e@>fè>g>gÀ>gÈ>g(>fX>e(>c>bè>aÈ>`>_>^>]€>^x>] >\Ø>] >Zð>X>UX>S0>Q>Pp>N>KP>Kp>Jx>Ih>Fˆ>Fˆ>Gˆ>G0>G˜>H>Kè>S>W>Zp>]X>`(>bà>e >hð>jè>k>j`>ip>jh>m >o@>q˜>r>rP>q˜>pØ>oè>p>oP>m0>j8>i€>h>f>cð>`ˆ>\p>X>Th>PÈ>Kø>I>Fð>D°>Ep>BP>?°>?>=ø>:À>9˜>:`><>=(><è>;¸>9>5ø>2>-X>)h>%˜>!>Ð>x>°>˜>@>€>¨>€> > >!˜>#(>%°>%È>%ð>%Ð>%>$€>" >!€>À>è>>>H>>È>Ø>h>Ø>@>8>>> ¨>$`>((>,È>0€>2ˆ>4P>68>7>8 >9>8Ø>8À>6ˆ>5x>3à>3>3>2¨>3ˆ>5 >6ð>9¸><˜>=è>>è>>><>9È>6p>4P>3 >20>2>28>3 >4>3˜>2h>0`>. >,p>(>%È>"@>¸>P>ø>À>8> > >€>@>ð>Ø>À>H> x> Ø> 8>`>8>>€>>#(>*ˆ>2˜>9È>A8>F°>M¸>S >W>\@>` >dè>jX>o>rð>wp>z8>}>>€p>€€>€Ì>€¬>€Ø>€Ì>°>}à>|Ø>|ø>|P>{>y@>uÀ>t>qÐ>nð>lP>jà>gð>eH>a¨>] >[ˆ>Y>WÀ>V>T@>S >Q>NØ>Kø>Hh>Fh>Dè>E>Eˆ>E >F>FÈ>F˜>Eø>E€>Ex>F>Fx>Gè>Ih>H°>Hð>Ià>J¸>L >L>K¨>Iè>Gˆ>DÐ>C>C@>Cø>D >D>Dè>E8>Eà>Fø>I>J>L>N>PÀ>R€>T(>Uø>W`>X >X(>Xè>Z8>ZH>\@>]ø>`>a0>bð>c¨>aÀ>a@>_@>]>[¨>Y >WH>V>U>U>Tx>R>Ox>M(>J0>G>D0>Aˆ>?ˆ><Ø>:€>8È>7 >7>7X>6˜>58>2ø>/Ø>-°>, >*0>((>%¨>#Ð>!H>È>Ø>>h> €> @>>8>¸>h>8>ð> ¨> >Ø>°>ˆ>x>8>>> P>"ˆ>#h>$È>$Ð>&>$x>$ >$0>#˜>#>"Ø># >$X>%€>'>(˜>*è>.@>0Ø>3¸>5È>7>7ð>8°>9¨>:X>;>;€>;x>:ˆ>8 >6€>4À>3è>1à>-˜>*¸>&ð>$>!X>8>°>>è>>Ø>¨>à> Ø> ˜>X>=þ =û@=ú=ûP=ûÐ=ü=úÀ=ú@=öÀ=öà=õÐ=õ=÷`=÷=÷=ú>(>h>Ø>˜>> 0> Ð> ˜> ø> h> ˜> À>À>ð>€>˜>È> È> ¨>¸>H>à>¸>È>!>"x>$ >%h>%p>%X>$€>$Ð>$h>#0>#€>$>$ >%ø>'¨>)X>+H>,p>- >/X>/>/€>.x>,X>)`>'X>'ˆ>&¨>(H>(`>(¸>(è>)>(>&Ø>%À>#x>!Ø>¸>Ø>8>°>P>! >"h>$ˆ>(8>+>,ø>1ð>5°>8ˆ>;>>X>?è>@ø>B>BÈ>CÐ>D >E€>G>G€>H`>Jp>Mè>Q >W>]H>aˆ>g >k(>n>r>t >uÐ>w¨>wà>x >yà>zP>y`>yè>yø>|°>~À>€ˆ>>Ä>ƒ>‚Ø>ƒX>ƒ¤>ƒ >‚è>‚T>ð>X>>€„>>>D>à>ƒD>„€>…D>… >†,>†d>‡4>‡Ì>ˆX>ˆx>ˆd>ˆ|>ˆÈ>‰H>‰¤>‰x>‰>‰œ>‰ >‰>‰>‰H>Š>Š0>Š4>Šd>Šð>‹,>‹D>‹\>‹Ø>Œœ>Œ¨> >ô>ŽŒ>X>l>’,>“Ô>•\>–¤>—>˜t>˜ˆ>˜ü>™Ð>›>›¬>œP>L>´>˜>œÜ>›Ô>›T>št>šŒ>™œ>™X>™¸>™È>š(>› >œT> >žŒ>Ÿ> 4>¡,>¢t>£Œ>¥ >¦˜>¨„>ª>¬€>®(>¯|>±>²p>³X>´ð>µì>¶Ô>¸¨>¹œ>¹ø>º0>¹Œ>¹(>¸Ì>¸ >·ø>·4>¶`>µ>³Œ>²<>±>¯Ø>¯(>®¼>­x>¬,>«h>ªÐ>ªH>©¬>©D>©>©ˆ>©´>ª>©>©P>¨Ä>¨(>§p>¦¸>¥¼>¤ä>¤>¢È>¡p>ŸÐ>L>œ>› >šà>š>šÜ>šø>›h>›Ì>›ì>œ@>œà>À>ž>žŒ>ž˜>ŸP> H>¡>¡à>¢ä>£>£>£L>£$>£0>£ >£t>£<>¢˜>¢d> Ø>Ÿ>>šX>—°>’ü>P>ä>‹¼>Š„>Š@>ˆ>†¼>…œ>…0>ƒô>ƒ„>ƒ¨>ƒ>Ø>ƒp>ƒ`>ƒ<>†x>‡`>ˆX>ˆ(>ˆD>ˆÄ>‰>‰8>ˆÐ>ˆ¨>ˆ>‡À>†È>…À>„>‚˜>€ä>}˜>yP>t˜>oˆ>i>dÈ>_X>[Ð>X0>V`>U>TH>U0>U¨>Up>Wà>X¸>YX>ZÀ>[È>]h>]Ø>`8>bX>d>e >eX>d>c>`è>`>`x>`¨>a@>a8>a>_p>\°>X¸>V >QØ>Mè>KP>I>GÈ>Fø>F¸>F8>E >E >BÐ>AX>>Ø>9x>9Ø>: >9è>>è>>ˆ>;è>9è>7H>4>1h>/Ø>.¨>-H>-x>,ð>,ˆ>,À>+ø>,>->-p>.Ø>1@>3è>70>9è>=Ð>A >D(>FP>GX>I>J >L>MP>O@>Q>Rh>Rx>R8>RP>R >P¨>N >M>K€>K8>Iè>Iè>I>H>FÀ>E>D`>D>E>E0>E0>CÐ>B¸>A°>@è>? >?h>?H>>è>@P>Aˆ>C¸>E@>DX>Dè>D>BÐ>Að>?0>>H><è>; >9>7¸>4ø>3>2@>1h>1>2x>3>5È>70>8p>:È>;0>=>?ø>BP>Dø>G8>Jø>Mà>Q>Sx>W >[è>`>c8>f >gð>hÀ>k0>mØ>pX>rx>v>zP>p>‚p>„è>‡P>‰0>Š8>‹ˆ>Œ$>Œ¨>8>>¼>¨>ŒÄ>‹P>Š >‡ì>…ä>ƒt>t>€ >}x>}(>{X>yP>x(>v>t˜>s`>r@>q >pÀ>pP>p>p>o¸>oh>p>pè>q8>q >q(>q¨>qx>p0>oX>np>lP>j >hX>h˜>j`>l>m>n>mÐ>l>lh>lÐ>kp>hÐ>eø>c>_ˆ>] >[>YP>X°>W°>X>VÀ>VØ>W(>X>Yà>\P>_0>b˜>g˜>l¨>q>v@>{€>€l>‚”>„œ>‡<>‰|>‹l>P>Ž„>>‘ >‘¬>’„>“ >“>“Ô>”l>•4>•è>–h>–ð>—(>—|>—\>–¨>•Œ>“ü>’\>ˆ>8>Šh>ˆ|>†D>„(>‚Œ>D>€T>€>Ð>€¤>Ð>‚„>ƒ >ƒ >ƒ¼>…\>†<>†Ä>†Ô>‡P>ˆD>ˆ¤>‰P>‰D>‰Ô>‰0>ˆŒ>ˆX>ˆ>‡Œ>†ì>‡T>†Ô>†€>†H>…¨>„Ô>„Ð>„Ä>„|>…>„Œ>„„>„ô>„ü>…0>„È>„>‚Ä>€¬>}>v¸>qh>k¨>dð>^(>W >Q(>K€>Fˆ>A°>> ><>8È>8>8È>8¨>8x>8à>8¨>7 >5 >3(>1€>.ˆ>,¸>+>( >& >#>è> >P>>(> ¸> ¸> > > > ¨>>Ø>=ùÐ=î0=â=Ôp=ÉP=À =¶P=¬P=¡ð=™ =Ž =‡à=`=t=fà=X`=H@=B€=@€=Bà=Eà=N =U@=[@=aÀ=i`=t€=~@=ð=ƒ`=‚Ð=P=€Ð=| =y@=x`=uÀ=yà={@=} =€ =…`=‹=À=—Ð=ž@=¥ð=¬Ð=³à=ºð=À°=°=Å`=Á°=»=³=ª@=Ÿ`=“€=Šp=€°=o@=]€=R=A@=8=" = `<ò<Ê<š@ÓGÓYÓ5ÓíÒŒÒ-ÒºÑ-ÑÁÐKÐÞÏjϸÎ4ÎÇÍwÍÍÀÌPÌÌÜË–ËoË\Ë]ËmËhËzËWËËáÊŒÊ0ʸÉ?ÉÊÈeÈÈëÇÖÇÑÇÊÇÅǿǣǯÇêÇÈUÈȦÈÉ7É‰É¿ÉæÉåÉÑÉÏÉÅÉÎÉÛÉÊ)Ê8ÊeÊjʒʆʗÊpÊAÊèÉ’ÉIÉ÷È¢ÈfÈ-ÈÈ ÈïÇ.ÈeÈ´ÈÉ}ÉøÉMÊ‚ÊÛÊË4ËR˃˳˦ËÅËÇˣˠËÀËèËêËÿËÌÌþËéËçËÃËËX˅˪ËÜË÷ËÌÌ/Ìa̼Ì3ÍŒÍ ÎˆÎ Ï}ÏßÏ4Ð\ÐнÐÞÐ3ÑuÑ¢ÑÒŽÒïÒcÓÕÓúÓSÔŸÔÜÔÕÿÔðÔûÔÔÔ¦ÔxÔ-ÔõÓƒÓBÓÓæÒéÒÓ5ÓÓ¯ÓÝÓ Ô(Ô-ÔÔáÓ©Ó]Ó ÓèÒ¤ÒÒXÒýÑ”ÑDÑáÐeÐÿÏÏ.ÏáÎ{ηÍ`ÍÍÝÌ™Ì7Ì̸ˋËnË|Ë~ËLË5ËË×ÊÏÊëÊËMËyˆ˯ËÃˠ˟ˈË2ËìÊ Ê>ÊÊÉkÉÉ¥ÈLÈöǺǠÇǘnjǮÇåÇ4È•ÈûÈgÉâÉÊ{Ê Ë„ËëËoÌðÌaͱÍíÍÎ!ÎÎŠÍ Íý̲Ì%̱ËGË Ë»ÊÊcÉ»ÈWÈ#ÈÈ4ÈHÈ>È?ÈXÈvÈÈÅÈÁÈÂȹȎÈ}ÈȇÈGÈäǶÇVÇ5ÇEÇ1Ç%ÇÇ8ÇeǤÇðÇ4ÈzÈsÈYÈ8ÈðDZÇMÇ»Æ+Æ®ÅÅ£ÄQÄàÑÃoÃmÃ|ÊæóÃàÖÃ_ÃUÃ,ÃåÂØÂ¹Â™ÂgÂZÂUÂiœÂÈÂ%ÜÃòÃ-ĀĮÄðÄMÅwÅƇÆÇ…Ç×Ç"È`ȆȟȽÈÅÈùÈÉDÉkɌɪÉÐÉíÉùÉãÉ“É?É×ÈœÈfÈSÈCÈÈËdzǮǺÇóÇÈ$ÈÈ(ÈüÇÆÇWdzÆÆOŧÄÄŒÃZÃDÃÃþÂÃÃ#ÃEÃXÃ}ÃêÃgÄíÄ•ÅDƵÆ=Ç¨ÇæÇ:ÈÈ7ÉØÉ~ÊIËÌ£Ì+Ío͑ͭÍÕÍíÍÎQÎ}ΈÎTÎ ÎÄÍsÍáÌtÌÆËËÊçÉ4É©È3ȹÇ5ÇàÆ~ÆÆÆÒÅÆÅÁŲųŧÅųźÅëÅiÆÇ–ÇSÈ ÉÈÉoÊËÀËpÌÍ ÍÎÎÏcÏ”ÏÆÏóÏÐOУÐÅÐèÐ ÑÑÜÐÅÐpÐ8Ð÷ÏÖϳχÏwÏdÏKÏeÏpÏ™ÏÌÏÎÏ'ÐXÐÚÐÑeÑ®ÑßÑÒ/Ò4Ò.Ò;ÒûÑÒ*ÒƒÒòÒÓÔÔ[ÕÖÜÖ‰×8ØúØŒÙÚ€ÚÍÚûÚQÛ}ÛœÛÐÛÜYÜ™ÜÝTÝÀÜÛÜŽÝÞuÞß¶ß–àázáâgâÂâÊâ†âÓâoâââÉá¥áÔá¹á âãNãWãaãiãpã¢ã÷ãBä™äñäPå€å»åöå?æeæÅæ çUç£çÏçèèCèèáç¹ç’çZç]çgçÐçèzèÚèIéÂé4ê—êäê)ëMëVë‹ë‹ëšë¥ëœëXë5ëïê‡êêÌéwééÌèžè\è?èèðçÈç§çkç<ççàæÆæ«æ´æÖæêæ/ç}çâç>èèËè¨èÙè,éTé¢éàéäéÚéÄéé^é(éÙè~èÉçâæ2æ¢åså/å åÂäŠäcä´äíäååôäåËä±ä¬ä:åœåàå.æ'æˆæÊæMçè;è3èßç@ènèÅègéƒé­éºéé_é@éïè›è)èÌç=çÁææ¢å5åÎä~äAäšããœâðáXáÞàJàïß”ß0ßDß*ß;ß|ßwß—ßæßåßà|à¯à6áºáØáJâÌâ+ã©ãéã2äxä°äÞä#åpåÈåéå<æ¦æôæ<çMçPç1çÿæòæ¬æqæŠæÌæç ç&çyç‚çžç³çÜçÒç¶ç³çŸçÝç%èŽè÷èné&ê¶êPëâëÔë½ëì.ì¦ì í¢í1î5îcî–îÙîÿîhïNðÂð#ñxñÞñBò“òÚò'óUó‰ó¨óÚó×óóó-ôeôÀôëôõWõxõ…õžõàõôõ#öQöMö„öŒö½öèö÷9÷¤÷$ø©ø,ù{ù®ù¯ùÆù¶ùßùáùêùÝùºù™ùyùRù)ùùÔøÉøÁø¨øÀøÀøÈøÂøÁø´ø°øÊø ùOùªùòùGú­úûœûüpüÖüþü3ý8ý?ý2ý@ý(ýý1ýýýÚü©üžüfüXüNüšü ý_ý¥ýÖýþ`þŠþ¡þ¨þ×þüþGÿ¤ÿÿÿYz•„§¼øgÈ®cò‚þp±öJ|¿ì]’»Ž ^ Ô ' N r ‡ d % ò Ï ¯ § – ™ } ’ ¾ Ô &  ® G ä k å QržÖñÒË¥zÙ ½ d  ¯ p "   ( G i   §  @ ‡ Ö [Êð4jpceMCÚ˜4 ß ‚ : í ² š c r • ©  º ´ Ô Ä â  á Ù ¤ o ! Õ j d àØ áî Õ g – « Ó  2 A V d [  ù ì Ñ ê ø H ž Þ ð Ï ™ q A $  V q •   Ï Ø ñ W • Ö  \ y ” Ô Ì ¹ ¥ … — ¯ ¯ ® « ³ µ À È Æ ¶ | g  Ë _ ð š  ƒ þ – ) þǘB èÀ}{]6cpxwpastN« ¹Bãçβ›™³ðûòïÖÓàR†Æ(¦4·fÅó  - C ] m a I R & þÅs3ö»‰I Ë\öƒèkÕŠ‚‡š×)^¦Ú4W}”‹elg7:Q€™ô<c6W?¡[ÅûÇ=˜Qjþqýbü‡û±ú6úù.ù§ø-ù²ù…ùPùâø}ø øb÷ÛöKö’õõfôîóróóÐòpòòˆñjñfñwñ¸ñûñYòÖò\óöóŸô/õÇõ?ö˜ö×ö÷J÷F÷#÷áö—öNö÷õ{õõvôÁóóròUñùïhïï>ï­îîUíâìZìÂëcë3ëáêÀê²ê¾êÁê°êÂêäê*ëHëlë…ë¡ëÛë?ìì”ì¿ìÑì÷ìÞìÎìÍìðìíìÔìéìÞìÓìàìÖì´ìÆì´ìÇìèì#íBí…íÍíûíQîiî¨îÞî-ï°ïðƒðÐðPñƒñ§ñÄñÌñÆñµñ¼ñ¡ñrñHñßð¬ðlðkðYðkð¯ðÙð6ñkñˆñ•ñlñrñ6ñ7ñ<ñ\ñtñ‡ñ˜ñ¨ñ¸ñÉñëñ%ò,òAò…ò¸òóŽó*ôÃô)õwõ˜õ·õæõö&ö6öTöœö×ö÷U÷c÷2÷Ýöö5öüõáõÕõòõ8ö[öö§öÆö÷÷h÷º÷ øuøóørùú‡ú÷ú‡û'üºüKýÑý>þ–þÎþôþ%ÿCÿXÿ…ÿÁÿÜÿ­ÿúÿ´Òþ  üþú0j Ù×É¥q/ôð×Òã P¡ñWÈ>¿Hßbº RÆíJƒŒšzwD ë•pmo—œŽv=WêÖªš•„X^@ôR‹Éö 1Qc–½ W©ñ*]p›ôÿ8 m | ~ [ % Ñ£MÍ­ÐàFƒ˜½b–eÅæÇÐÓæ !Pß( ‡ ¾ â Ø ñ    < ‚ ¥ é -  7 Ä ` à mä^Ú9j…zY ó´²mNåâ™7¹ F Á 2 Á † F  K W \ B " Þ ° T pñæp½,µ>Ô™€^ˆ‹ƒe;- >€}…XZbD«öNÂ*Ó#0?’ž«áûHcnvfNKs—ÇZ¡ýp » ý w Å   Õ < » 5 Ï —Y?Ýrõ:p‘²½œk3ó«Ió©I"Òœ|hvt¥â0QdZ^{f|œÈäÝáõF«.²1« Z‡¦§¦—¶ FŠØ4JR[H,-"õÙçó %!ècœêní}ð,^ssSXLa…ÄàeÚA´u÷rû„×Q ã h! "~"ú"B#‹#Õ#$ï#$.$@$%$$%$$$R$b$N$$$ý#$î#×#å#Î#Ì#å#×#ã#Þ#·#‘##œ#¯#Ë#A$ $&%h%&!&M&$'ƒ'(‹(ý(_)Ù)"*n*•*«*Ë*à*+?+Œ+Â+,d,š,ù,:-»-&.Á.o>ÿ>{?Ò?@@@¯@Ò@ó@2APA‡A½AêAàABâAÔAGAeABiBÞBCHCBCHCCúBäBåBßBþBôBàBÃBBmBBâAÓAäAìAìABB;BŽB„BGB4B%BEBIBpB¦B×BéBëB­BiB`B%BÂA‚AkAJA5A9AAæ@ª@S@ö?­?‰?‘?Š?ª?Ý?ï?ý?Û?Ú?½?Ã?ž??ª?Ö?æ?@@Û?}?U?3?÷>º>t>W>>ë=°=[=#=Ý<Î<é<‚=F@¥C'DUC&AV=v:Ä9|:J;·<û=v>5>F=.<{:U9´8Ì8z9î:¹<ÿ=õ>r>Ð;8/5=3÷24Ò7s:Ç;³<}<=;œ:¼:°:";­]@lAB BUCFHšH*H¡FcEC)B3B;AABBÂAaAõ?À=8;›8ò6R6¸7´:>¦@5AS@v=×85m1,.›,)-×/˜4ì8e<>=-:è512ž1 3«6È;? A¨?<ò7ï2/o.k/2b7=DžI+LFKìE>Û634Ü6Ð96<ùC•ChAA>Ñ:Ê75Å3Î2Ø0V2§5b8n:K<ƒ;z6ä1E.p,c-E.˜/¼2b7Ù9¥8‘654Ÿ0¢/È2 6m7X9!Ô/ÔOÔ ÔvÔ1Ô´ÓEÓÓíÒ—Ò ÒdÑÑòÐÑíКÐtгÐÑ ÑÆÐRйÏÏ7ÏÏÏüΓÎÎTÍÊÌjÌ(̹Ë0˾Ê`Ê ÊÏÉoÉ0ÉÁÈÞǴƨÅ-ÅîÄüÄ+ÅÅ)ÅuŸÅâÅÁÅÅjÅ2ÅHÅŸÅ?Æ}ÆhÆúÅèūŅÅCÅ­ÄuÄ«ÄųÅãÅoÅ.ÅýÄœÄlÄ&ĨæÃåÃ=Ä}ÄmÄ<Ä©ÃAÃÕÂÂyÁDÁ±ÁöÁÆÁpÁÁ÷ÀñÀçÀïÀ×ÀÒÀÁ‹ÁìÁ;ÂŽÂòÂÃÃÐÂcÂG‚ÂÀÂÁÂÿÂc×ÇÃ8òÂ$ÂuÁãÀÊÀvÀÆ¿B¿.¿¿Ý¾ ¾¤¾â¾¿ó¾æ¾,¿Ò¿ÀÀIÀÀ¶ÀÚÀÖÀ¸ÀKÀû¿Ø¿ê¿&À<À[À±ÀQÁÈÁÛÁUÂõÂtóà ăķÄÅ…ÅÆÆ:ÆåÆøÇ6ÉqÊ|ËÌ0ÌoÌÍdÍ`ÍpÍ…Í ÍyÍ[Í^ͬÍãÍÎ!ÎúÍÎvÎNÏ8ÐÕÐlÑúÑQÒPÒ ÒÅÑÑtÐ!ÐðÏâϱϯÏÊÏøÏÐ Ð7ЙÐѼÑwÒÓPÓwÓŠÓtÓnÓRÓJÓÓÛÒ­ÒÞÒMÓÝÓ;Ô¢ÔšÔpÔCÔXÔpÔ©ÔËÔïÔJÕ–Õ³Õ¡Õ~ÕbÕXÕ{ÕßÕ¤Öz×cØýØ8ÙÙ)ÙgÙåÙ'ÚLÚxÚæÚZÛrÛ#Û¦ÚPÚÿÙ³Ù3ÙíØÙñØœØ ØR×´ÖáÕcÕBÕ(Õ;Õ'ÕõÔÕÔ²ÔƒÔ»ÔÕHÕkÕÕîÕ‡ÖWר"ØØúרeØÆØ$ÙGÙðØ«ØPØí×Ëׯה×2שÖþÕjÕÛÔ2ÔmÓîÒAÒ“ÑöÐQÐrÏ ÎßÍéÌÌ/Ë}ÊZÊcÊÊÎÉ>ÉoȤÇôÆdÆöÅoÅþĤÄ(Ä»ÃRÃ4ÃêÂûÂþÂ(Ã$ÃCÃ}ÙÃÉâÃgÃû¨ÂuÂ) ÁüÀxÀð¿°¿\¿ï¾…¾l¾&¾¸½Ö¼û»"»_º¥¹Œ¸å·H·»¶¶O¶éµqµ%µî´È´f´ý³³œ³=´Ï´1µ}µñµ³¶¨·{¸g¹dºg»±¼(¾î¿ŒÁÃ_ĘÅÚÆ?È‘ÉÃÊPË¿ËNÌBͦÎûÏ[ÑáÒýÓÉÔLÕÕÕªÖ×× ×KרõØ·ÙâÙuÙ°Øñׅ׎×ç×Úס×ÅרLØØ™×äÖÜÕÕxÔÔøÓ›ÓÓºÒ÷Ò“ÓRÔ‰ÔÔ‹ÓÓ Ò(Ò¶Ñ`ÑûЩЅÐÐ\ÏpÎ\͇Ì'Ì-Ì€ÌdͣαϭÐ}ÑùÑlÒ—Ò­Ò÷Ò”Ó¶Ô,Ö‘×XØÐØèØòØÙÙÙRÙÖÙ´ÚÀۨܒÝUÞ߸ß=àþà—á â&ã‰äæ9ç.èÒèGéƒé“é6éöèééAévéõéjêóêoë„ë%ëëië$ìîìîï ðñòÅò6ó@óóqóïóµôîõýöø³øhùùòøøþööMõõ5õ™õÚõ[ö‰öö²öëöO÷‰÷ã÷øžù…úûóú9ú\ùløÓ÷”÷Ì÷Wøðø¨ù]úòú˜û›ü¡ý„þsÿ"LKÿ¬dÿ\…kŸ)´: ~ ¯ ÿ ? † 8 Þ Ö á ç  7  Î o ²Ž”ª»Æ¤E[S™A1*4@¯åâ\Î$¸MÏCO±ÿÿCþIýRüyûÌú;ú ù'ùøÂ÷·öNõ ôó@òzñ”ð¬ïÈî¢íNìýê±é‰è«çç—æ´å³ä¹ã¿âùá(áZàmß™ÞèÝfݳÜÜ“Û%ÛÃÚÚÙä׃Ö+ÕfÔÔvÔ ÕPÖÂײØÙÙXÚëÚÛ%ÜvÝ_ßúáêäQçé<ênêJêêcê‡ë“íñïwò÷ô,÷9ùÇúŽûœûªû¬ûnüÉý\ÿ0Õ V}*EŽþýÛû8ûŽú(úúÔùÛøm÷3õÃòað:îÕì-ì@ìÜìþíØîïçî îÌìXë¸éÈè¬è%é:ê@ëÃë[ëïé6è<æQä&ã¾â&ãàãËäœå¾åNåä†ãßâ“âã•äKæBè+ê¼ë†ìÚìÍìXììõë'ìÜìÍíï€ðÆñ|ò²òŸò—òÆòhó™ô%ö­÷Nùïú\üdýþ<þþ-þ4þVþ­þ.ÿ¹ÿ…ÿ“þhý_üû8ûöúûú,û\ûXû×úúóø øZ÷ ÷.÷g÷å÷øõ÷¹÷K÷¨öJö$ööïõÂõõ õ·ôEôô ô'ôVôrô¥ôõ`õ~õáõ<öÜöž÷SøÑøûøÓøªø†øŠøÜøtùúÇú]û£ûüdüÌüˆýþýÿeËa—y' à ; Ž  ˜ â  ² F Ú – “ º ê è ì Ü ¾ ™ Æ & ­ / ª ¦ ‰ . ½ 8 ã « z Y  å ª / †ã=šª{,ªƒã9ÄX·&‰¹ö7ƒÿßþVþ»ýÞüïûíú úzùùñø€øøŒ÷æö3ömõtôóòò…òóñeñ£ð’ïdîßìQëùé é5èTçëæsæ±åÛäÀãàâ âáIáEáÌáùá;â»â}ãäräÂäåÛåÌæøç éøéëlì6îòï7ò™ôÎömùüöþ&ÀÇk ' ª í ] Õ y¨‡EµL4Ý]|TÔg:Q´ £ È # º Ï t q÷OÞßÿÑþ5þýrüóúêø÷Ìõ­ôIôô˜ô¨õøö¥ø0úýúaûsû›ûŒû{ûNû¶úçù ù²øÊøùMùjùÝùFúßú{û<üwý¶þúÿà1/Ëí…Þ…qÎ' ÿ # * c ¿ + æ ¾ }¢ñT’Y÷… ªC¼f£ëv qƒpÌ „ O i ¥ φÿ_pin&Hwd/>9e¨ 3  v  ` á  ¨ e  ¸ ^ ºPïàg¹€yÿ¼pîÕÇns£Ôd·Åé1Ä4¶$n½]Ív:ѯŠ6u0Û Í ý I ¼ d A û ã ¦ * å{y¼ù) U F 1 7  ŤŽèa 0 µ < Â Æ … D J Gb¥«—ˆ ÎÿÿäýÚüÛûèúúùøÖö”õjô1óùñðMï$îUíùì™ì ìûêÖéÅèíç6çˆæÔå.å¾ä^äAä$äääÛã±ã¿ãÅãÂã¸ãÍãäää3åîåóæ,è¼é(ëTìyí¶îðŽñ‚óšõÁ÷Îùíûþ8>•È»õ}Ë À £ 4  ± zB ®«}ÐÝtL@Å¢ð A¿K Õ . õÛ{Ý5´þDý¤üü¾ûû÷ùùû÷öööqõõõÇõžö}÷lø*ù±ù¡ùAùäø¡øZøÙ÷÷b÷Z÷€÷¬÷â÷CøôøÞùûüÂýbÿèbVƒÁü"ÍÝ襁 ¨ Ë · = œ Ò¬g;cU`TAÓ’%ËU/‹§Ì‘‹©Â#TÕ?·PÕ > V P _ p °î?Ù²î+^ƒôzh † ½  {‡YÒסåÒU¹ÿG=£jçà5#ªËzCÜåzFâ¾K^¹yû´»dT¥‹ÜÅbË2ÿ6› žÞææw ‰ù• zÛ„1ðÆ§„!ë } $ ° = Ô s F  ü / íÜö‘g$âº~ÿJþìüöûWûùú…úú±ùùú÷Úö‡õ[ôwó°òûñRñyðaï,îóì¶ëêéZèOç‡æºåéäëã¾âQááߨÞÀÝ ÝgÜÜ Ü Ü»ÛuÛîÚNÚÖÙŸÙËÙÚ©ÚÛÀÛ=ÜoÜ~ÜsÜܸÜ+ÝèÝÄÞÀߊàJá"âãƒä+æÞçµéùëâî÷ñ$õ÷¢ùûüåü2ýAýBýjý÷ýÈþ }P­Œ~ª§ŒyŠqÜdÉý÷úø:õó‹ñ¯ðÚïïwîÁíì×êÍèNæøã½â>âýáâ2âlâªâ—âOâPâªâKã®äç‡éûë!îlïð?ðDðÜï3ï¾î”îôîìïïðòOó3ôõøõ7÷‚øïùMûWüBýTþúþÿàþyþnþðþ§ÿR %.n¥ÎBÓ?¡¢E Ü ~ û É P › J £ ö “ õKÌ‹›j©ŒÄÅ9f|?ù¨lMìR ý#Á˜Ê1Zpy ‚ „  ÷ -˜ l80ç*‹ö{Ç ä×£íúdýóû5‡s[5þ5ÁŒ>¤¯KÉÊÖ 6 Ö  ¾ ._Iç b ÷ À  s ì kÚXÜ€qµŠO¡Ý ×½rPú—/’Ñ è  & < F Â3‰Ó‚ÿ]þ_ýüü‡ûÎúïùôøé÷"÷zö%öÛõ•õAõÈô#ôeóò>ñ6ðiï|îžíÕì(ìTë&êé¹çgænå€ä¤ãÏâ!âáÞàçßéÞÞEÝ«ÜÜßÛvÛñÚ;ÚoÙìØØ.×­ÖGÖÞÕØÕÖRÖJÖ ÖAÖMÖ§Ö©×°ØÊÙ´Ú¸ÛûÜÝÝÞßyß4àá½â(åšçéèê‘ì%îÖïjñ›ò óQôxõöçöÓögö öÀõFõ…õõõ öÜõsõgõNõ«ôµóòwðïîí0ëøè©æädáìÞ7Ý€ÛÐÙ|Ød××Ö#ÖòÔØÓ“ÒòÑÒ³ÒƒÓÔîÔ×ÕoÖ×y× ØêØÂÙµÛêÝàLâØã åÀåFæÆæÈæ£æãæ‡ç³èÏéýêàë©ìpíRîïïXðôð³ñEòòªò­òkòáññwññÕñò5òwòó3ó#ó¶òYòòòÛñ¿ñ³ñÍñòWò«òáòBó®óîóôžôõ7õ#õòôõ]õSõ)õìôŒôtô|ô­ôÄôõYõžõçõ×õˆõ÷ô)ôˆóQó$óÍò{ò>ò2ò_òòòò¢ó)ôõ2ö!÷ó÷ØøÁùŽú@ûGü­ýÿaޱ²M+ý¾¨a  ½ % R m x ° ù " ] G =  š ¯ U Ô ^ ò’GÍJËZÑÔ¨´¦’“›väæá Ÿ K ø Š P .½;¯×§(ΉžI ½ € f ® & °  ] Í # ­k•ú“V.³["™÷iÂÿ:ÿ§þ-þºý-ýýþüõü ý:ýdý’ýžýxýeý?ýýÓüÎüÄü‰ü"übûƒú—ù¶øå÷N÷ÖöcööÃõ=õ©ôûó>ómòºñÎð$ð€ïåîQîÅíbí í§ìdì@ì#ì#ì"ì9ì8ì8ì_ì´ìãìí‚íÚíEî«î ïÍïfðüðêñôò4ônõÓö`ø‚ùuú.ûü?ý€þØÿýŒ.*ò\‡•šŽÔîº  L •  ä Ý Y æ ß  °Ùuÿÿ°þsþþ»ýŸýü¾ûûû;ûhûÂûüFüÒü|ý7þÍþŽÿ¨. Ä<z~ < Þ ä Í ž Ä | ) , 3ñn3í‹zŠêÁyß=…ý£}m¦äß³‘ic¤¥tX6÷ìô,i¼LéDD!íßÈ£‡Ë<Ó:”!µiBõ´h‰fh먔£ç%^ÁÙå=hÕYÏzôËŽV ã !±!û! "2"&"F"1""÷!ä!Ï!#"°"M#$’$è$/%G%%ð$»$E$˜#õ"“""! !¾ n ¡l55ãqîp=áŠPkz ù•d@ ÷ ±!2"…"»"Å"k"ø!†!!¢ A É2üåóT® Y p a õ8Q)Ì›‚”·þ.e{‚ÂAÕFä;z  Ò  ] á ˜ S / 6 l — Ñ ! w | o r > Ú L % Ð  Ù®ªgû¢~_Krh|[Ãïé >:½Ÿf¦ÿÒþþGýsü¬ûûúdúÓùrùùÙøløøÝ÷øUøxøÑøOùú÷ú!üÉý*ÿxÁ7“!E À * n ¶R£âiÛ¤×óùƒÎÓDV ¦‚Øð B V e†¿†ƒí•½…ùîÿôþIþëýgþòþöÿUÄ÷Ëyüfû Z á ª×K˜}gûºµ©oæñ²+iÈšeωpŒp | ‡  ½ z - ˜ ›ˆ8Ìr<™vÈ`àVhX74M¯ûÞ«pP|¦ó\º-d|MÈŽi<uŸ…|…"ÏF~<dZOpˆ¹a½TKe U Vl^¨Ì¶á®¦NŒ ÁP Ãþé ¾È#âëó);n±‚,º 7}0ÈÜx*Æ?È…V»j:ÀUÙzÒêܹ¼¨·™c&ë×oùcª4­$IBë3‹à J Q ~ O P ; Ò é áá‡d7¯LØNÝÿžÿÿ±ÿüÿI^fžÿ—ÿ¯ÿþÿMäG~‡hÔ|cœãôï…þÿHÿUþnýmü²ûHû¾úPúÔùkùþøPø¼÷L÷÷Åö4ö°õíôûóCóAòðð»ïÑîÐíí«ììÔìƒíîþîð`ñíòµôNöÒ÷cùêúgüµýÿÔÿ¹‰…p>þ¨RñÎ \ i ) Ù = | m ò € ¤ Ç ~ $h9 Çÿþoü7û1úgùÛøø[÷—öÃõ\õŽõöùö+ø}ùæú&üý*þ?ÿê̾·‡ŽÍìŽHßÐÔÅÆ¬–g³ ¹]ý£  Zÿíþnþ¢ýéüü7ûyú­ùïø[øøõ÷øWøÎømùõùlúûìûÃü…ý_þ>ÿ/²x“»¶ñ;¯2H˜«Ðù0¼`áJgÁÑW‡Òìñ¥'«HöíåР‡—žÃÐøLÙê F · ¬]©+QaÕñøéq6¤%˜J2 j t î {  ’ æ;Žª#š,™YÄ=¡¸÷ᤜxj{Â’/¹^öTŒ†}`OU>ùºK©:òÏÔçѹzá4g“ÿéþVþþîýþ:þiþOþJþ2þþ©ýý`ýTýYýBýýÖü¿ü‚ü"üÿûÂûûeûûßúâúÚú½ú›ú ú¿úÅú~ú…ú~úú†ú¡ú®ú€úIúöù”ùùŽøì÷E÷`ö‹õ¦ô{ó"òÏð]ï¾í{ìXëSê¸éJééšè*è­çäæ´åƒäFãUâ÷à¹ßÊÞôÝÿÜÛÛŠÚ4Ùß×áÖÖ\ÕúÔÕpÕÒÕšÖÿ×ÿÙBÜÚÞ]á«ãBæTèêïë:íÙî0ðlñÁò´óºôkõßõ¡öo÷øPú@üUþ>”•Ü”÷ÿ ÿKþjý½üéû¨úùM÷ŠõÞó\ò+ñÆðÁð›ðqðöï+ïîøììiëë3ëÑëzì+í îïÀï2ð]ð‡ðÒðððâðÝððð±ð”ðið<ðòïýï.ðwðñåñéòÉóŽôNõÄõöãõ¨õTõ*õ&õ[õˆõ˜õÍõöööößõ’õ{õ¥õ˜õ×õ*öyöÓö÷R÷™÷š÷w÷Ž÷øø ù…ùòù[ú§úÈúéú¼ú¿úûJûuûìûjüý’ýþ¥þêþÿìþ°þQþÕý›ýMýý¨ürü‚ü‘ü·üÚüùü:ý²ý(þ¿þPÿ)ÿÿNÿ]ÿtÿ•ÿ!D´· Haüs ± ‹ o m y É , Ä | à  a k ß E “ ¬Ä…Þ ö ˆ K  &šs“=Ú*'–^&¹:¯”ÿÿþþÙýþqþÈþÿIÿQÿtÿ¿ÿ!Šä0[rfbZrÏ a]Ös£+¹ÿ£ÿlÿöþdþæýƒýMýý þšþAÿ–ÿ–ÿ\ÿéþ\þ¿ýHýÞüÚü ýïü³ü`ü üû"ûúúfù«øª÷ìö*öpõ¼ô5ôÉóóRó)óó›ò8ò¹ñTñêð[ðïýî2îTíjìlë~ê¸ééè"è²çç·æ;æÃå]åÕä›äfää¹ãZãìâkâæátáýàŽàBàå߻߄ßvßNßàÞWÞÞóÝÛÝÞ7ÞHÞŸÞáÞßqßßÅß´àTâÊä–çƒêíãî—ð†ñòuòèòžóøô¬öcø×ùšú˜ú úkùxù1ú×ûþ¦dœÀ!@uOþ®ûÆùÇøkøø‘÷cö†ôëñ‹îGë»èGçÙæ]çJè½è‡èyçxå,ãêààÞ«Ý‘ÝÙÞzà'âsã9äôä£åPæ(çmèúéùëî¬ïðð–ñêñ^òóô¯õ¹÷ˆùCûüü:þÂþbÿ¢ÿäÿ33U Vÿ³þ+þ²ýiý5ýý ýêü ü<üqûRúxù÷ø±ø§ø‘øø1ø‘÷Ðöö‚õ"õõ[õHö÷Á÷×÷]÷¯öGö.öóõöƒö1÷ÿ÷½ø:ùnùKù3ù{ùàù`úïú6û`û.û§ú;úrù¼ø5ø øUø€ø´øÓøÌøÔøíøùjùºù ú«úoûøû^üüüáüœýÿí‘ùç¼sü¼ £ ½ vËW[åTÞ’Yt™ß“¶& 1 C bùC¦fúE;èÿ}þýÒûåúúlùÝøsøÔ÷_÷O÷q÷°÷Ñ÷ø0ø:ø\øËøKùüùû,ü0ý®ýÀý™ýfý,ý0ý¯ý^þJÿ_mú×lѦÿÿÇÿh¢‰_ÿnþUý‘ü ü±ûû;ûÅúÚùËøª÷SöúôÊóófòüñññð8ðYïrî1íÄëZê é˜çæ´äjãQâtáþàèàØàæàãàáDááâªâ ãpãÐãòãøã·ãEãèâ‡â%â6âsââ¿âãõâžâ%â~á×à5àß¿ÞüÝ1Ý3܈ÛÖÚÚ–ÙÙÐØØ9Ø Ø‹××Ö'Ö|ÕÁÔÔ'Ó1Ò4ÑCÐÏϤÎGÎÿͷͧͩ͹ÍãÍþÍÞÍ—Íf͉ÍEΒψÑ>ÓúÔaÖU×KصØÁØêØ5Ù•ÙCÚMÛ-ÜqÜܺÛpÛYÛÜâÜaÞàâááãðäååäÎâ[á†àìß·ß•ß}ßaßß.Þ)Ý%ÜýÚJÚâÙÚ…Ú©ÚµÚŸÚ¨ÚoÚ1Ú»ÙÙþØŸÙoÚrۣܜݞÞÁß©à_áœá§áá²á¯á›ážá‹á«á âgâ¼âTãÔã:äñäˆåýå0æ‘æÙæ;ç¨ç”çƒçç`æDæ=æjæÀæççFçç—ææsåÄäWä*äÈããyã/ãÇââ á|àà»ß àŽà4áÿážâ ã{ãÞãä•ä åÏåÌæ"èé·êªë\ìí~íDî,ïïï”ðcñ-òÂòÝòÄòyòòöñÑñµñ¾ñÄñ´ññ}ñbñhñ7ññÿðññ$ññgñÞñKòÊòÖòªòèòó8óaópó÷óuô2õÑõöö‘ömöZöpöúö¶÷“ø–ùú?úúXùŒø\÷'ö~õõ¶ô~ôwô‘ô"ôîóÕó^óçòtòìñ®ñ’ñCññÇððåîµíŽìŠëÕê›êéêMë·ë&ìBììåë¤ë„ë†ë9ëZëŒë¶ë¯ëÛë,ìDìNìtì&ìììûëìTìAìúëµëëJêhé¸èè¶çç/çñæ|æ(æÂåKåååäÇä¾ä™äšääzä(äâã£ã=ãã¸âNâôáŽáAááÀàŸà§àžà…à‘ààšàhààÄßhßß»ÞãÞéÞß*ßOßm߉ߊߡߙßÊ߯ßíßà(à@àààáßÕßÚßàåßàcà´àáá áþàÆà}àUàþß«ßXß+ßóÞ®Þ©ÞÇÞªÞ~Þ;ÞòÝÑݵÝÃÝ.ÞÑÞ:ßœßßßàóß(àMàCààßà;áÄáôá âòáÍáâ|â:ãä æ†çFéÃê/ìríîªîÿî˜ïWðHñœòzóQôâôõõõõ©õ¼ö$ø(úåûsýPþYþ<þ—ý×ü9üDüæü§ýiþÔþŽþæý”üîú„ùløº÷`÷g÷Ä÷ê÷Û÷¨÷ ö„õ’ôôÚóöóàôö¶÷ùüùÞúŠûüQüõüŒýYþÿ¯ÿd˜ÜȪ„§&Á9ŠÎøì&BY®84úÀC±bÖñØã¥]×N¾dUB•þŒ…[  † ‘5ØQ ùL j ˆ } ” ‘ Ä Ç ³ – b z m • š « ¶ Ê  7 è ‘ [ % Þ‰WË[Y{{p&†µq–ÒOà`ÐDê3zé„ãW¹»ÂÛÛ©®Õ ( š —  k 4 6 4  ¹  9 äÇð  – O § Ì ¶ Ö & M [ Æ M v Œ o ú • % Ú û % š Z ß ^ ° È ã Ï › ‚ ¥ ä ë Ñ ¥ 1 ¦ 9 Û Ì ˜ Ž ‰ w V  à ‰  î Ú É ý F z × ö  C c ±  † Á è 0 S P N W O ` ~ u Œ ” … | | ¬ ®   Œ b ð â è   ç ª t I à v    = s É i Ð ¤‰¨©¨˜, ˜- ÜĬŧd&â‹]”bò r 0 Ô ­ ð 3 Ë ¸o=ÀDïzÁc©lðÌê>ë¡= "ö#’%+'€()*U+¿+,<,y,Û, -P-d-\-I-€-¾-Ý-Ù-Â-‰--ó+Õ*¯)N(I'q&Û%N%ƒ$$Ó#º#…###è"Ú"ñ"à"¦"@"Ö!´!ç!Z"Æ"Ó#%k&—'ª(y)C*¶*9+,ž,û,I-‰-¥-–-\-=-2-…-.¯. /+0B00‘/¶.û-f-"-#-%-/-;--‡,o,h,¶,W-V.W/‚0i1ú1s2Ž2“2ê2K3ã3Ý4Ë5c6Î6ç6×6î67r7289Î9¥:ý:0; ;Ì:Ä:á:‡;]<#=ã=r>½>ñ>???Q?æ?U@™@Ÿ@@G@ã?i?O?`?š?¬?ç?\@f@r@u@C@ @ä??\??Ù>>>Ø=Ë=>6>>2?a?“?×?Ç?@…@¸@Ò@@A AËAÖAªA{A®AàAðAB3BB7BCB°A:A³@0@ò??ã>‚>>Š==|<Ì;(;´:V:ó9V9¼8;8‚7746|5º4Ï3ê22A1‘00¾/®/Ÿ/²/·/®/U/Ò.f.ü-€-6-É,ø+°+I+ ++%+I++.,Ä,‹-J.5/B0w0f0ë0*1 1‹0 00ð/æ/ó/0é/0Ú//b.å-ú,,B+›*ï)ð)é)<)‡(â'1'¹&‹&a&R&/&"&è%™%ú$‹$8$ä#¨#¦#›#~#g##°"M"""é!"p"Ì"#0#„#Ù#3$r$´$%B%c%d%|%¡%ä%8&.&&Ý%…%9%î$p$$Ã#D##®"˜"X":"8"E"Ž"ð"‹#d$%Ã%‡&<'ô'›(N)ý)_* *+t+ò+•,q-U./ß/u01_1†1·1ó1}2ÿ2ž304«4Þ4Í4Ž4W4!4þ3ß3ý3T4â4@5x5z5Y5R5ú45,5:5^5”5Û5Ð5Ì5}5,55Þ4ª4ˆ4Q4.474w4À4505š5ù5/6˜6Ô617†7û7–8_9û9z:æ:,;n;d;¤;Ð;3<·˜>Ÿ>>Œ>•>?\?Ï?h@ú@AÆ@z@5@ÿ?í?5@­@2AÇA#B†BóB`CçCqD EE F{F™F]F.FFºEªEŸEÌEÌEåEíEñEÀEÊEF°FµGÂHèIŠJ%K†KkKŽKLáLNrOÅP«QaRïRSõRÔR®RÂRÓR+SS³S‰SÄRýQóPþOxOOOfOžO]OÍN÷M­LXK J÷H0H}G«FÕE E9DÍC{C=C&CFCHC6CCïBàBµB’BB“B„BöA B°AAÅ@Ð@ã@AJA¥A BBüAÏA—AxA}AsAfAhAFAò@1@'?>ò<<^;í:¨:r:9:Ù9/9•8·7á626½5Œ5|5…5m5$5Ê44[3Ó2.2›1k1T1;1N1 1Ò0^0Ò/X/Ï.G. .æ-Ù-¶-£-£-õ-.ï-µ-ž--B-í,Ô,Â,Œ,5,Š++>*’)õ(0(Ž'"'ÿ&í&‰&&1%6$%#H"h!¶  ¯‚A ªzP8./LVFÒxV†®4:#Ðs]~»üÜÉÐ :ÍJŠ ªI´ô(æì§Z²¯ÚO“ܳ‡y¾ñ^¤ÌÇ `i½ÿ7¸Z«9ÍVÍÔÄÉâ.H G!"""x"‡"k"n"j"p"Œ"A"Ê!i!! L  öܺXéì«Z;BvÆ[íƒ! w Ÿ » !š!Û!ò!"Ý!È!R!œ !  < 6 § ä ™!É!Ô!"l"–"­"y"?"1"š!}!!°!Â!C"ç"*#(#8#ç#±$Õ$%B%u%›%±%x%?%?%,%R%À%v&A' (Ì(·)|*K+,´,X-¶-.@.‡.Ï./*///(/j/°/ 0@0b0{0{0›0ó0*1Ÿ12[2ƒ2¡2Ï2ì23_3Ð3B4¾4ý4ý4õ4Ô4Ö4­4x4]4W4Œ44r4z4Q414O4Œ4¢4í4ê4ë4õ4ù4ú4Ê4u484ä3Ð3¹3e3Ñ2'2å1f1û0T0˜/ò.N.‚-y,”+ *ô)v)Ý(C(Ñ'‚'<' &ô%Q%ÿ$Ç$¾$¶$Ù$ì$ç$”$"$å#‘#P#ü"Ò"‚"4"!""Ò!#!¯ £ Ù !!î!3"o"«"n"/"""" "3""¥!b!õ ž G ýµC ÂP¸YVvÙr!Æ6:)–8íQ¦K ¬FíÓ#Ò«k%À1S&.×} N<Ue!ì>TYÔ ¹ ” ! ƒ  ›  s  æ § °  “ j Œ —¹Ì@ÝÙê¿ôKô8Ù8Îf¯.·1>…« pÄÚð8 ‘ 2 ƒ w B ? m š É ø L Œ ˆ … ¾ ò  B X V : * « 6 ” × F Ÿÿ߿ʎíFé΢¸Óñ.û{:!3§$¹@‘}\›áûCiqŸ§Ö§®D"è~;ìMüÎCÙžËO¡í•LÕü9Uv܂ޭ R ° 8 ï œ ? Ë " ] N ª ”>‘ëþ¶WPÇ`à³8¦ŽÀIÉd°Ã¯Ž¡¾*›ÝæÑ;`¼Q[«GÁ#Rü¡®(rÅ:\æI2è ¹<OL>OZa»abd…× æ|ðÆŸm‡D±ã·€|Ya€c rí@µ_QM¨‘§åyQ÷–9zEa Òmñ uóûTø“‘2ýœµJψ5ý $LnÞ + X ^ º â " ' H È’Àj c Ì ã ó Æ]TÑº…: s | k U ¶   E ˆ °ÎÂös‚ƒ5|ùân‚„– î t M ÷ 8 n € Ï œ ¨ ÖZÜÙ´!1$e¨ >fÑÿßÿU UitèÆÂÁC5‘'.m]}Á`3Ôÿíÿ2´ÿÛþ~þWþvþŸþˆþpþíýqüÓú9úlúÁù¿ø9÷¡õ¸õðõqõ.ôñò™ò‹òjò­ñ¶ðSððóïðKððÍï·ï{ïïÐî§îþî`ï³ïyðeñMñùïÍîïKð.ñ"ñ—ððûðÊñjñ*ðÍî{í¡ìšìì¸ì!ì£ëKëáêšê9ê'ê?êóêéë‚ìqì´ëëaëáë$ìÆëLëeëÆëöëSëHêoéKéiéìé|ê•ë íí)ìÔêêûé<êÏêªëÙìÃí¹í9íÓì³ëUêâèØèmê]ìíÁë¦éðçÒæ¹å¨ä8äå»åæä‡ã™âóáqá™àŽßGߺßàAà*ààc߃ÞúÜôÛ3ÜhÝÞáÞß•ßÁßÚހݭÝÚ߆âä0ä¤ãŠâ¥á;á²áòâµãªã¿ãmä…ä•ä}äããÈãsåøæ2è3é£ééúæ)äIââ\ãúäàå,æàååÎã‹âJá^àTà²àáDâläÖåSå°ãIâ˜á‡áîáNâ4ã’äå·äïãäå3å¿äÑã¼â×áëáÝâžä"ææÓæøæ'æä•âeã[äÝä.å‘åXæ½çœç,æ½ä$ä¬ãã]ã)å.çèèÎçøç@èÍæ÷ä#åÜçnêNëˆëëZìËìKì%ì©ìuí9í#ìì@í†írí˜íî‰î¡î8îØìÅêûéÇêìërììíAî÷îmí%êMè´è×é½êèêë{ëþë*ë‚ê:ê êê‹ê—ë>í•îÒïkðKð‹ï¹íìNì^îÃðòÎñð²îSî¥îJðbñƒðpï„ïöðFòEòðñLòó>óÃóôþó‰ô˜ôôõó7ôÐôíõs÷,øùù“ø,÷Tö­õKõö€÷ï÷b÷/öõó9ò«ñúðµð®ðñaòôò·ñ‰ï­írìêëQì±í[ïðð5ïîQïðâï3îœíï¤ðwñêï¼íYíîUîJíªë‹ê*êêmêë-ëºê•êïêxëžì%îÆîî{í¿í ïmñ†ó9ôô^óÌòóô õ«ôróøòKô2öY÷*÷öõSõÈõÕõØõöÉõ›ôØó2ô$õTõ¨ôLô[óìò2óóóËòRò]ò÷òâò™ñðìîbî›î€ï8ï¡íWììâì¯í3í­ì$ì¶ë‚ëßë íAîÔîîöì”ë®ê›êìÇíÊî÷îï“ï4ðJïëíñìRìŒìíßíoîfîoí ìŽêìééÄè¢é7ëìàëÀêîèXç˜ænçZè=è5èûçðçµçÒæÏæŒæZååEæ/è8éÜè_çøåbå.å¥åÜæ‰èëé7ê(éUèzçºåóäÈäUä€äÒå?çèÒçÇæ§ä†âüàá¯ä-ç¿æžä&ä{åvæoåäóâèâOä°æ·çyçkç·æÆå‚æhè‹é雿*ääAçïè´è*èVèÈç£ææXæ¾æÛæqæLæBèEêòélèWç(çËæ æËä/ä.åTæççªææÅäÎâjâ<äAåämâˆáâ`ãëã:ãºálàÄßÖßzáâãUããBãÿãµäÍä#ä äåææ æ¡æ®çâèãèâçôæÏæÚæ6ç·çÌç5èÅç·åíãnã ä¸äæäáäçã0ãqãäoæOçDæ{ååæëèVé¹çQåUåýæHèFè·ç´çõçZéƒêé‡è€é5ëoëêdë´íïîí‹ìæìóí;îQírì…ì.í³í„î3ïdï,ð¢ïÄíÌìÒí\ï·ï—ïüî<ï‡ïçîÔíÍì¯ì í¥íÀì²ìÂìí&íàìYìÍëZëŸê¶ëÐëëwëFìYí3î@îÝíçíî£î ïäîï ðrñ~òqò:ò€òßòQò(ñzð<ð[ðùñ©ôùõ=õOótñð/îdíïòLó±ñ¶ïûî‚îîBîþíÅíÔí>îRï´ïdïYîŠíúíï-ð»ñóoòÈð·ï@ïÅïWñòñçñzòò‡ñÏï´í’ì2í–ïÊñ×ñ?ð¿îæíŽîï¢íæê2ê–ìuïtñäñ—ð½íÚêšé­êeíÉïäðÔðëïùî›íìë²ê ëÐëiì:ìõì4î.íëÞèºèdêÌëPìgëâêëëëqë|ìbí íäêˆèèèéêäë•í^îÅí:ìê„èÐèŸéÆé×êóìÌï}òLñíéÒçñætç…éƒë$í²îxîµìÇê é?çæ:çê¹ëhì²ëªéVçæ‚æ ç/ççâæbççç6æéäLä¿ä_å}åíä!äñâîà ßsßßá?ä ä[âáÍá&âYápààâLägåXåÛäã¤ââ¡áÈàVà\àtà”à»àGáøà“ßXÝmÛèÜ­ßoá›âƒá(Þ7ÛÜFÞqàØácáÐàCáâãÖãTä^äÝãåäæ æOæ çHæÎäèä@åhå¿æÁæ!åƒå6ç¦ç<æÄäåÀçCéÛèfæ,ãøâüä%å„äPãá#à#àÁß7ßÞ‰ÜêÚèÚUÜÞzßàÞÑÛ™Ù}ÙvÚ5ÚËÙ9ÚÑÚEÛ×ÜÞPÝýÚÿØ××iÙÜèÞàÞޖݳÝÞÝ6ÝîÛÛmÜ Þ"àÕà£àNàëßîßøÞÀÜbÛÛÜÌÞŒá7â"áà$ßaÝøÜÞ@ߊßIàáá|ááçßìÞLß5ßÓÝÁÝaßÛà"áàÖÞVÞ¹ßÙÞÕÛÍÚܯÞàŽÞÝÛ…ÚÐÚ_Ü|Ý ÞáÜÚ¾ØOÚÐÛÛàÚëÜåÞßäÝÜ.ÛyÛ–ÜvÞŒàøâžã.â‘àÍß9ß§Ý*ÝcÞxàsâ{ãgãUâ­áâÒâNáòÞ2ßËàoãçé,èDåâ€àTâåæ~å1ä_äúämäÛâ‰ááòà<áÜàJáœâþâZâ+àöÞ¬àzãbã±àËßêàÿáÈá}à"à"ákâÓâGá˜ß‰ÝèۜۼÜ.Þ@ß>à^߅ݱÞzàÝÞÈÛEÚÜnßcãÁååúäáãÙá\à áßãÊæé<ê]êêxê¨êÊééŽéÄêÜêKê.ë¦ìîtí{êlèèÒçiçŒæÉåïå¼å>æGæäYãœä‚åÝãÜâšâŸâcãsäå å€å¯ææ>ääâyáàÝàâ1äWçÆè³æœäéäå{ã¨â_ãuåŽç$èçêå-æå=âìàâµäðåÁåÏãºáìà&á/áÄá¾ââàßûÝqÜËÜÑÞúßÞÚÚ°ÙMÛÜ]ÛÙš×ØÑÚpÜlÛÚîÚÛ~ÚÊÙÌÚNÜ ÜkÛÖÙIÚLÞJß•Ü>ÚfÚ|܌ޙÞ_Ý3Ý/Þ®ß9à6Þ/ÜIÛSÛÉÚËÙîÙÓÚlÛ>ÛQÛþÚuÚªÙ×öÓ.ÒmÒùÔW×dØíة׊ÕPÓ¦ÒKÓÕÛ×É×ÂÖ‹Ø<Û™ÛÊ׫ÓÚÓI×€Ù<ÙPØ™ØõÙšÚ0Ú`Ú–Û~ÜkÜlÜË܇ޫà›ßùÜAÜ'ß1äæéã9âœálàÊÝ­ÛrÜøßÏã†äÄá“ß0ßîÞqÝØÛܼÜXÞ‰ààáPâ¿áà¡Ý¸ÜyÝ¡Þøßáåàß…ÝcÝžÞ ß@ßeàžá â×áàßËß7àeánãää«å´åoäÀâiâááKâäæ7æ^å;å©äÙãGãxâ’áÒâÆäQæ}æëäÔâRá®áâ9ã9ãäåãä©äªå'æBæ:æŽå—å æŠåâäûãåœç…ççäcâËãòå¹äØáÆàUãLæxç½å/ãÄááÛàáUâUâÕà áiãÛä`ã$á‹à´á@âáàGàâáæRç1äEâÂâ¨ãÉãêâ4âøâ½äHå©ãÎáËàAâåè0çwã áçâäåèÀépêaêÂé•éŸé¶éæêÖêûèkç‘éÝíÓïiínêjê*ìõíSî8îÒí‘ííÀëƒíEñ÷ò:ñHîŸêºçùçêêéé]êëí§ì%éæ#åæ“èëé¦êÿé­èèæèPê'êæèçƒçPèsê:ì3í!íoìúì¹í•íæëÀêmìð:ò°óõSõ'ô]óñóƒõ*÷Qù–úÅúúÎù£øÙöö+öf÷µøÞ÷‹÷%÷üö™÷(÷›õRõlöÁö²õÛôAôõC÷`÷ôóð?ñóŒôòôfôÏòçððžðëñMóìó]ó7ó õäõQô*óÆòÀó÷úû*ûMúÍùžù!úHüþ°þ ÿŦcfUÒÿƒ):"=«% JaØéà+ Ü_+¡ "´œ8¶Â .Î ^ ÌÈÑÎf å ‘=NßUá„Ú Î «jñ ŽQ® ª OƒûíÅøyª)$ ò6©ÎÊÚ ,§ ¥ } Ü  Õ × 6 S ! ß ô ÂÛÁ ·Aÿ*) 8 9è>Ä<3 ù Ó  d Ä ˜ G ¬ëï2… g   W ð ý % Ô´d _G— ý WÒ w r 8¥¶Ò« Š Ë ü©’A°\÷sMƒ\ôg?%´Ð¦½¥OTÀŒD‘¢á¡|d»_bTk´H›"6"骸øf c­Ñ„ô‡·~øÌTÎN4‰•}"_~ƒíDåIûÛí³›b¯”GïÊ\­WA|Él0B½‡CGÝF ÇçH{ϨïÀ*§¸¤»áT‹z(”׸ºÅ#’n„n«Cœ­ˆgY ‘J!‘,!I#â#÷"6#Í$ˆ'­))'q&c(Þ)ä)ì)§*€+ý*l*À(s(q))6((e(H((×'F'—&„&“%z#•#0&ˆ(Å( 'ó%&n&l&l'[)á))o)ß)Ø*Ÿ*‘)@*v+p+i++ä*/**.*~+€,3,ñ*B*z*ÿ*O+7*z)¯)I*¼*»*Ú+q-”,b*Þ)¼+·-¼.ƒ.½-7.(/µ.Å-å,¶+@*)÷(­)ï*£+»*6)w(4)Þ)ü(£'þ'ò);+¼+é*'*+,ž/¡0I.p+*ä)h*ì+.0Œ11O.**ƒ'ç'¨)´+©,ª+P**á)ß)ÿ*á*>)(n''(ñ*Ÿ,Ì,6,v*;(o'() *×)6)Õ'˜&A'»(6))ý'ˆ%Ó$( +,ã*g(&(]+±.ð.Œ,¬));+¬,¬-7.E-L,Ý-‰0 0U,¸)†+:0å0-ð*ß+.q/C.ª,0,*—'™(^*+H+0+*s**®(C'Q&p%$l" #û%'¶%€$E"ê€*È+""¡ 6!†"H# #Q!u '!1#Ï&‚(['Á%Ú#¦#y$|%Ù%¿$z#1"#4&ö'›%x Ž“7"±$#^ ¬!f!Ø Ä å a!û!Â"$#ó!¾¾ðbÓ b!± :FÎåµ™Œ§H—y ß!꾯\IÞ±êy©ÓÔTv ÃÓi„õÒÍTf»ž¡¤†‚VÜñX)TBU"_ä¡ÄrIøhx`AÈD®¤J5€òkyqo/ê2¨¨âNN2fÍ+Öª ¡9âä,] jß Ì K } ˜0%Cï ß ç”(o©|-§iâ;™+íœ8v(ͤ×#'}BU¿Œo+ È ß¤  üñ R ¶Ú ¿ ‚ ø†Å»Ù–ØJÊû³LX ò bŸß„2Ñݺy² _’–í`?©9eE[Ä&×Úûužë¢~kÌa|(ñ z9î*6ÕûÉ´×SQØ÷ÿí.Ú!n9 xæž»æè‰ûÄížD˜ýÉvŠp¤+ e™?X÷Ëý»7ó¼ù§ý¹¶ŽöÕï¾+»#Œl!ñðÓ’*ÜY0±AZò[býúú¡î¦´¯4äþ줃uÄú}E/>` 6@#\¡ùvlžH¢“i› P ®¿g{\òS¤òŇWfÅ{aY ’ Š)~¨«xáYv§7T²býñ& > ø ‰ì4 ¸Æ ?   V 4  ¯ ©ø”".;ª Y õÊ&_– w #iGX 6äJ…d Õ ª åü£ú|y·8   F9›…"ðÐͧ6–¿ÿèÿ©)µ«é KÈMþ¨üºý~ÿcNÿHüšúrûæüýaý…üšû û¸ûäû'üËü¥ýÀý¯þ·§ù™ÿŠþ½ý£ýÎþ­ñî#‹82ÿ:þgþ‚þÀþÿªýòû{ùž÷t÷™÷jøàø˜øïø©ùœúœùö°ó”óö§ùNûÃùö÷ã÷<ø¢÷^÷ÿ÷Šù(ûÛú¢ø²öÚö™ø(ùƒ÷ÑôÅóöQù@úö·ñèð9óõÞôêõ‰ùQûÌùÓöHõ“ö)ù½úõûrýúýðühûéù!ø*ø/û”ü û0ûüeþÑÿçþÔü2ûAûyü8þùoGO>öÐa­Øl(vß-XVqO}ü` çk© »HTÅý‰öówz ³k8ÿ¡þÚÿM$óÂÝÚóÖÿêþÔþÉ£¾~ ².P±Óû!Ù»ãhT„ð©má&ÍÓ^| ÿ@qìþ„&–= 2 0  ˆ ÿ  · å] à * • Ñ Û ¹ î Ä HYª œ ºõ ^Ÿ\ðì Ï é & d ƒ =¤ “ » Ï0 3 Câ Ü (Ú t Ž  ! }L • u 2‚  w åLþ‚ ³   æÄy枘òµ‹ ™ ÷ çfîÛ k É ¢ r ¤ $ º,‚hj± W g`ÀGÝZ‰Ë(ÄCMp·¬Á6Žß‘AJHPq\ò}‘îøEÛ¶fDb!V)ß*Ú—Ø»nè  Ö¥r“ 0`'F ù Ú µŽFˆ % Î ·î PyØ ä  ¿ ì ð qæJÞ C ðƒ¥Tâóõí nz¦XcŽFù¬E–£è3ˆó È Ý]íKKÏï×tn/¨N´½¥ã6¬ÉSo­Ÿ0:½ÿXÿÿúÿjÐx|ÿØýâýYþâýüüqýÂýbüû,ûü+ý~úg÷X÷ùùûËüeûújùäøNù·ùßù‹ù ø]öjöà÷ƒø—÷çöª÷¡ø°øDøùùù"ùø÷N÷¡öK÷ù±ú—ûïúcúUúvûný½û ù9úÉý÷ÿ£þ^û!ú üšÿGþÅúžú™ýô‚\žýŠú¥û"þ +“N®þ%ý ýþ½þpþÎý$þ-ÿ’þ¾ü4û úoúûHû„üÏþmÿ¹ý6üPû-ûÿú—ùfúWþ@ÚþüÙùœúOýšþþÊüÐý[í5ÿ£ýöý&ÿ3v”»þ­ýþþ—áÿóþ þîÿ qÿ÷ü<ühý$þØýüAûÈû(ýÆüžú ùÌøvøÆökõá÷Íúâù¥÷ZõXôÉö²øb÷qôÑògòTò‹ô ÷y÷Sõèôföø˜øâöÿôfõóøZüªýþlýîûæúÁùÄùÕúÅüµþZÿuþjüRûõú ûý+ý¦û~úýú û~ú%øuö[öùö)ø›øÒ÷¯öJöqöqöóõGóÛñÅôKù€ûŠùíôñòWõ}õôƒó¦ôV÷ùøÖôØòCòíòõdöµõ2ôÐô&öõÂñöî îxðRõš÷‹õ òGðzïAî¥ì¾ìþíèï8ò•ò•ðÙíËê#è=çÆèÛéžêçêþêfìÄìßêèåŽä æüèöêhëuêœéséøéûèIççZèêáëdì”ìòë]ê!ééæéˆêcê#éDçžçÙèuéFêSê êcéIçï忉ç×èué™égé+éeèLç’æ?æ åyãKã7ä2å æqæ æKä âáùá9åáç.çðå=æÒæïæUå|ãÃãÏåRççÐå®åJçéçæääøå¿ç èûæÌåƒå?åòärä¶ãàãùã äêãeãðâ}áÀÞ)Þ™à3ä!æ™ãõßÄÞåÞXÞ`݉ÝXà~ãùäbåsã8àÞòÝØßRãØæèUçcæ~åyäçâòáãåeèÓéjêuëóëvêuèpèêÊë7ë éÀèÜê6íUí®êëå³âýãkæãæëåÆägã£âÔá4áâ«á/ßÞà‰ãµä•â.àåßAà4áàáæáÈâûã½ãðâGâGâKâ›â`âøà¶àHâåÈçèçç÷æ1ç×çlæä/åÞè›êLëëgè3æcèÜêŸêçéŸèwçãçélê·ê«é-éÂèèyèYèáç,è°ç¥æ‹æ=è¾èhçäå8åÕågçóçDçäåòäKåìç3êqë(ë@é^æCåöæëÌíkìêë•í»íÚê%é³ëåïæñkñðJðQð·ï¢ïñ¥ó’ôô ó,ò¨ò¬òñ0ï·îèï¿ñXòŸñ<ð„ï,ïÝîNï€ðEñ(ñ%ðïïöñ]ô0ô!ñÅî3ïBò õõÚóô?õÂóñIð…ó¥õ`ô§òò³òlóTó£òòRò»ò$óõòñ×î™îÔï¹ð=ðPï/ï¨îHíUìnìéì8í7í€íîï~ï}í¬ê§ê˜íéðò2ð…í"ìðënìòìííïúîðî*ðœñœñ»ï+îSî±ðvô»ö^ö<õuô‚óvóÉô`õÙôCô!õéöõøú÷Aòïî¤îlò²÷û®úë÷¾ôò\ñùòïóVò«ñ[óéöbù¯÷ó¦ï·î#ð0ó¾öðöâô¶ôþõœ÷öõ$ñ>îïKóöóõºôôðótóôñ'ðmïåðBóÒó ó¥òpòÿñ+ðªîþîÍïdñqó¡ôeôÂóiòbñ6ñ2ñnñgòÛôJøù{÷'ôÃðEðÿóÞöŠõ¶óHòònó¿ô!õTôDóžñQñ–óÙõ8öô…ñ„ñ[ó‡õnõióòçð¢ð¶ñVòÍñkñðÃï¨ï„ï·ïð ðMîUì5ì‹ìîïíèêIë|ì6ìúéÂçòçÐéê¥èÊæ1æ|ç…éÏé<èäæšæðæãæuæÙæéöêjê›éÿè©éCê"é¦è-êôëMíŸí$ìëßëìŠê@è>çÔéÃíÏîíÞëàì íKêyçýæéÝë î]î>ìê¥ê¸êäé›ç6åŠå¸èûêãêŠéQè¿ègé&èÝåÚäçæ×éë ë²é¸èè‰ç.è³éŠêê¯èJèÄéVêÌè:çé*í\î ì!é+é‹ëüêhèÒæ5çÓéßìíãëœëþêfêééê`êŒënî ñæñ¹ðmîšì‹ë,ì0î+ðÍñØò´òUòéñ‘ðîŒëÍê\ì¸ïòùñèð+ï<ìnéè èÔêþìíßìûì¤ìiëoèwå‘ä(çZìúïìïìœç7æBéÏìæìëlélê í¶ïöî·ëXéYê@î(ñ ñTïýíÌí^íåìeî&ñ óNó<òñÂð ñbñ³ñAòñ°ñ)ôøôù§ø#õ\ò‡òaôÜõ8ö¯õÛõr÷Öø÷PóóïòîüñXö{÷ÒõRórñÈò¤õ²öõôôÜõ;ø"ù’ö<òIðNó$ùøüSüù ÷Æ÷»ùOú›øýöÖ÷Žûwÿ„Jý ûhúßùŸù–úýÿÙþèü6úOør÷÷@÷‡ø ú­úŸú†ú¬ú¥ùø·øUù¦ú£üÍý=ýSüû8ùšù2ü¤þÂÿvÿYþ~ý=ý_ý$ü»ú,ûüªý¼þÇþýýýfüDû/úåúšüˆýKþ3þtývüfúÃøRø?ù‡ûKýüðúÞùšùSù¯ù_ù®ø_úÁü¶ýýrû­ùøV÷l÷˜øVú°û²û”ù÷¬öSø+ûwü ü8ûbûvüxþèÿ£þOüaüZÿL¿ö„êþÿŠ$-b›ºRü„PlýIþÑ)¬@æÿëàVœL€•&驱šûǨÜvç¾E‚Ý,’;ìˆÔû ‡<˜ºzá ¢ á̈^@ñ“Î/Î  ½¶\xbeÞ• f { ‚ æ ñ Tñ ƒ¦ ˯ˆô F¾WrP'žÈmê–Ì&ÌÿŸ­Rÿ}þ@þ0þoþgÿ{ÿàüø[õqöíùùý_mÿ:û öµô3÷áùûvú™ùÎú;ûû!ú´øâörö7ø$üÿBÿšüØøÀöùöýeÿäýšûëû÷þµà¥ÿEý¾üVýÿ†JM¾þ×ýgÿÏÁýÝücý¡ÿ1›ÿ üSøÔö’ø‰úûù øpöØöùûoúø\öˆö¾øÔú¦ú7ø+ö´öUøRùÖù¨ù¾ùùÕøX÷üö÷ÍöÁ÷0ù$ú¬ùn÷öö£ö~÷í÷H÷…õõ*÷ùXú@ø_öÆ÷ú úÙ÷TõzôöµøNúTúÌøöÍó5ò¦ò*õR÷?÷gööönöGôTñêðƒó®öE÷Oõúò²ó õôóò/ò1ó_óþò“òLóØóîòÁñ5ð¨ï¦ð$òóÆòÆòòœñKñ3òôdô<òð ñUôwö†ö˜õô¬òóÂô‰ôÐôÔöÊøaøÆõÜôêöAú‰ûüùó÷ø5úÈúhû=ý¯üû©ù8ø9ø™ø8ù(ù´ø+ù0úÓù øö™õ§ö÷ öhõ|õ³õÀô1óóÂô÷Ô÷Rö!ôæòwó¸ôoöâ÷ÿ÷¾÷2øï÷ØöïôìòïòYõrø¦ù ø$öö;÷Ñ÷XõùðûïÉó÷÷—øsöÈô¼ôôòZñ}ò¸ôT÷.ø÷÷öÉ÷RøÞ÷PõÐòŽôø"ù øŸ÷óöåõùôŒôõA÷øy÷²ôóõÞö÷öÇõâôÄôLöÃ÷I÷@÷øõôYô1õ³öaöõôYôãôèô˜ô°óÛó¦ó·òRò¾ñ5òòoòó’óïó9ôÐóQòsòzóŠóóåó­õ„õDó8òñRñÓð¿ðåñ[òzò¾ñïð¢ñ¤ñð8ð ð¤ðPñ¤ñóqó"ò€ñMñ8ñÚòãóÁómòXñðñóÀò¡ñoñõòÞôõýóóiòçñ7ò;ôµõõ ó-ò ó‹ôfõ¯õö®õÈôNó€ò0óœóËô,ö;ö+õÌó?ókò-òÙóÂôôò/ñÿñÒó»ôô|òñQðÙïÑïéðýñ ó'óóÚò_ò°ònòò6ó,õsö#÷ãöxõ¾ôWõöP÷Þø¬ùúóúîúÒùSùçù@û³üªüÓü·ýý6úº÷7÷ùüýïúŠøV÷[øú`ú´øHöHö¿ø÷ù½ø`÷l÷xøßù‰ùØ÷¡öö÷ÏùÊù}ø ÷²÷2ùù°öôõåø*ûùôÉñéóé÷ú´ø®õ.ô9õàöÔ÷Ã÷÷Çöîö‚÷ß÷Õ÷ü÷\÷Íõ)÷%ûþþîû‹ùhúõûÉûÍù„ø¹ùfú­ú‡ü¤ýÔü1ú÷pöÑø ûZûåúüÚühü%üžûßûÛûýúeú•ûÀþÖ þûù­ùüVþ…ý8úá÷]øvúÖûsúa÷-õGöKúCþÜþNû ÷Ñõ÷®ùÆûûùHú®üžþ‘ýwùˆõ³ô…õjöø ûðýÿ,ÿ5ûøTù“û¨üpüôü‚ÿ+¦Ö'sþôû~ü”ÿ4ŽÙ DþiüÀþ¨t®YäÿýÔý^ÿk‘I…%äþjýdý1ý`ýSþdC k'þ[úÈøZûËÿ\P#ÿýêüü¥ûµúúþ~˜(ÿjû®ùšú<üþü\ÿî© Ësÿüü™ý›ÿ¤² ñëp"£.ÿÀ×´± äÿ&¹uÄÛÉzÅ¥&”Zivÿ¥{~7Cc™?°‚èï6±û+˜˜œ Ìæ°“^Óý±ÿsHéæ²ÿõüðüŽþ¨ÿ†ÿìýaüËûÃüóýÿ-ÿÈþ(ÿìÿ7¾ÿ5þÿûAú€û~þtf³I24ùþÖüÃûþg-~$þnþÿ…üP»÷WìdŸÿßÿGòOèNEòüüæþ÷í«8êð¨‘ÿnýâÔÝ › [ydß ü  : È dê¹ ›& ¹ “  ƒ t ? 4°l%8£ G ö · v躆߳¼›  Ð+íW߯öP¢®tì¾(8ÏP}N$ h p &.y,× k ÷ ¼ ¸jA¡H N x ‡unä¥p „ Þ îVÆ6ÐFщ.¡`šçP_Qy`Úap·Y•ÿßÙ”%Ž(H&:ä:=F“³’…:Š7V²*<€94þhSxP5FŒ!Û 1:Ó`ü2˸;Ì® #D#þ ê Ž"ß$û#Á”´¡$é'ï&†#Û ÓAT ï"–$"#w!±"õ#<#g!Ô€º!4#Z"¤  4 !!„¦áýã!"#?"©[r º"å!É¢Êâ+b(Ÿ1î01³—@Á%*Ì Š ~ŽNVÞ+”ª{†÷ñëwÄ^ÁoŽQé°Ç ÑL19í ¯­å·jyì9”2ÉÚ¸™Eðì5ôòˆâòãßVŒc¿û`{«š~òò¬€Ýzµ¼ÌTŸy«ø¬ ă¦XÖáí MÏɽ|5ÌìgLÐU™¼Ø2D½jBøñéT¥º>´à81 _î!§ƒÒt5>1·VEzd>Øô'*Pù:¯ äÑx(mîjAõkî°ñíMµ 7! ÆrßA!G"X Ùú§NßÕ¼hÂfCOâduOH¸¶  l?ïó(&ß³WhùõÂOÌàËþ«k¤[ÅRâŒ$ó>û(’#øó)8›øÝŽ8aú¬fàÛòÖÅè› Ãç8n í•j²qW RÐäç2UÓ”ªÃä3I¿[lˆO–å¹#%¦#J!q „!#9#„!=!{#É%=&ö%¢%£%ù&1'Ç%…$ë#,%–'¥)Ï**ò'…%ß"o!U#¸&Ú(ª(‚&%4$b"Ê!#ô%¡&&\$«$s%q$æ! ° „!y#U%ó%7&Ä$J""R"""ë!$" $Ñ&Ë'§&Ï$<#O"Þ! !@"&î)+I)m%Ö"*#D#Ú!ï"'ú*g+ý(Ó%N$$ " {"ï&~)z(V% #»#¼%¯$ñ!É!!%Y) +¸)õ'Å'8(ª(Ü'Ý&å'J)$)y((( 'ë$v##±"G$‘&T&$y!¯Þ± >!!€"x#%#k!n {W¹m _#/$Ý"û!0!$!\  |!Q#E$t$Ò#H"!Þ ¥!ç"ž#ä$R%ˆ#,"¿"`$æ$#¹ %!ê#D%j$³" "!";!Ø 0!^!!¯ Û!¶#,%ù$*"R5¶ æ"#° 9 I"ú#%#= vL=!#½"äœãúÇ<×:ÿ,N‹}{:ÿûFÑ>½³ŒÝ¸¸\YÙ9e×;€Ou ñ´Â†KAtõÚþüÔPÇrê²þo"~{¾ð€¬„ŒG-aõ“àPwG£ë–¼Q÷˜˜ÕHË×q,_Oè»àj+ªÄ_Yû8­H""u‹LÑè"^O·5èC1m1Üzû7·Ò8Þ´*¹ø9„§× É CQt%S)°rL!Ó!  { HÙ Ùõ¸!n"y"’!? ˜›¶ « C ‹ b!×!~"ª#$@#ð!†!L!2 ˆ¡ ý!$ï%%"SÐU8&þd9 x´{Ô±jñ%d ;Þ‰fçöÇãÆ[6ÄZ§Á°Ðô¦mhUÑ(J„³@ÑÒß¼öw0Ó–¼ÚëLß°Jœss̹#ûøþŸ¼ ;¬û ”¢x€7î‘O ú ! A‚z € ’ Ÿ ?JÈÈ  Ê ° JE_ = W½S rÓû À 64ö < úk w O 7 ! õ]± é ÇŠV_ e G D 7 ¶ _Á—2¬ïæâr”x8W”Qâÿ “Ö¼jÞÈ€ÿ~ÿ¾Wȧ1‡à­È_ù¥@:BG ÿÇþI½Þömÿuÿ…è;ÿ¢ýjý?þËÿóU ÿý5û×ú­ü)ÿ‹îÿýûGû¡üüûZùRømù¸ûDýÍü¢ûêûÇûâùÉ÷øÆúsýÝþÀþ‹ýý•û øÆöø…ûYþ<ÿãþÙüÿúÅûþü¸üüü¬ýdÿ¤ÿ þøû‚úûør÷ ø@ûðþ¬ÿýèøÄõçõÒ÷¾ù)ûéüÎýÙü;ûŒùbø;ø½øtùeû^ý*þ~þÿ+ÿþý$üûú®ûþa¸[-FÿüÃû"þ‡ŒpÀ,;€%A?¯ Ì ýJ©·ZĪô<>7¥© g<ÙÈ Zé“Öæâ±û a NeãH­âÆvéß_ ÿbãð'xV-O½1ÿSüYû;þ­ƒ ¿þbV©þ†þ{ÿ8¬vKtoX×h:ÿ´t£…¦—÷ñÿÄCqN̳þHÿyÃþ’ûûôüšþaÿ4þ:ýÿû!úÀø#ù³ùLúåûØþ*çýlùëõ-õJöÂõcôFõîønû]úã÷ßõÇó6ð3îÑðïõú†úÁ÷âô¡óíóô›ó^ñnï9ñ˜õƒùFùÒõÿò$ñ‹ðòïØïAòõÇ÷÷"ö‹óPñð´îðóVõÄõ}ô×óÜòEðæíçíHñöPù?ùù¤øö ò\ïsð ô=ùEýÂýãûAøõJò$ñüñ(óôÓô*öRùZû»ù9ôî.ìÈíkñŸó÷ógôöœögóÅíðé:ê‰ì/ïKðñzòtòñ=ïîÃì²ëí!ñzódóùñÑï‘íQíFîÜî÷ï¹ï:îMí_íšíÊììâí ð@î!ë¡ê.ë”ì„ígì^êìédêêévê{ë‰ëì-ìëèPæ-æ;çèXèÆèHçéäSãGâSä§åøäsãzââãóå1çYæòä«åÌç(êÒèFäjâæ+ìí—ê·çç‡èMêë½êêEêüêìêéÕç–æhæÉæ¤æ¯æpæïä‰áßQáòäÖåfãdà”ß«áãÖáKßߥâ=å˜äá ÝóÛKÝÞæÞ˜Þ¶ÞßÄÞÞ1ÝÍÚÙíØ´ØŠÙÚÜÙˆÙRÙÍÙg٠ذÖÿÕ^Ö$Ø ÚKÙ‹×âׂØ*ٹؼ×v×4ÙÛ(Û­ÙÀØœØÎØ«ÙçÙcÚŒÚ#ÚÄÚøÛIÜ-ÚMÖpÔp×VÜyßBÞ•ÚA×jÖÑØoÛRÜÐÛÛøÚÙÉÕ4ÕØ©ÛÝÛÛ±Ú*ÛÛlÚÚàÙ÷ڋܤÝòÝ×Ü‚ÜçÝÙßdà-ßwÞ®ÞtÞ Þߘâ'æ´çyårâqá×âÛã¹âá­áãIåZäßâÁã|æÍæiãBß߸âõãõà‹ßÚá]åáåÎâ3ßãÝ#ÝÛ;ÙÌÙ¾ÜòßåàWànß6޵ݥܤÚÙuÚAÝ1àÞßLÜÙÀÙtÜÞÜÜWÙÁ×<ÙVÚ ÚšÛ@Ü¥ÜâÜ”ÜÃÜqÝeÝFݰܰܬÜuܤÝRà×âAãáóßáÅá¥àyßrà-ã»ä«ä÷äçä©ãƒã´ä€åŒåãä)äÈãÂåƒèrê•ënê•éÌéJé–èïæeæñæÉæ%æ ç=éTè,å1ãÁââáÄß–ÞßcàÛáHâåákàÝÓØ>Ö=רÙuÛeÜÆÛÄÚòÙsÙÙ5Ø×êÖíÖ^×àØMÚÚÔ×CÕlÕ†ÖÕÕjÕQ×nÚŒÙàÔhÓ%×ÜÝÛÚÚØ¾×:רÚhÛ÷Ú“ÙåØŸÚ2Ý ÜÙ×ÕÈÕ{×JØXÙØÙÅÙ ÛÅÚØ×B×{ÖÚÕfÖ׬מ×=××ÒÖìÕáÓ®ÒXÓïÕi؅ظքÓѱњÔà×TØÖ¹Ó¤Ó_ÔòÓxÓ9ÓÛÓBÕ—ÕöÔÔéÔzÕÌÔHÔÓÔÏÔ…ÖÙ£Ú‚ØJӑϵÏ'Ó:Öv×5×ÖƒÕ´Òyε̊ÎtÒÐÔJÔ%Ó.ÒðÑÛÑÛдΟͷÎ|Ð'ÓÈÖÙTØ–ÕâÑÈÎYÏ ÒÖÓçÔíÕ^×0×Õ…ÒKÐÐ=ÑöÒ–Ó±Ó8ÔÐÔ5ÕñÔ ÔêÒâÑÒüÒÌÔVÖ•ÖžÕÜÒ¨ÐÑ ÓÔÔmÔfÒûТÐvГЦЯнЖÐGЃлÐÕÏÎͧËÌ_ÎÑ´Ñ ÐíÎ^ÏàÏDÏlÍŒËíÌÑŸÕ¼×3Ö5ÔaÔÁÕSÕ¡Ó)Ó½Ô@ØÜÜ;ÙÂ×ÊדØ|Ø>ÖŠÔÙÕîÖ\×2Ú>Ý ÞÛ°Ö9Ó ÒÞÓbÖ2ÙÜTÝ0ÜýÙoØ+Ö¿Ô7ÖÈØ9ÚíÙÈÙNÚûÙrÙòØ=ÙrÙñØ’Ù"ÛqÛ”Ù¡×ô×ÝÙ}ÛŒÛÉÚ0Ú ÙÝÖÚÔ÷Ô±Ö^Ønؼ֊Õ×ÙÚ½ÛÙyÕ#ÓÂÓûÕØàØÜØòÙiÛÛŽØƒÕ ÕåÖ ÙZÛÞÃà¨ââ)߬ÜܵÞbâÞåÛçâç ç•ç3çç)çuå¿ãwã€å>éaêèyåÒâéà›à†áápÞØÛŸÜãß´àOÞäÙןØdÜÿÝ9ÜØšÔ‹Ó^Õê×cÙÜÙIÙØÃÖ@ÖÇÕ±Ô–ÔÖÖ#ÛrÝÝöÚèØ‡×ÁÖÏÖÖ×fÚÙÜÝÝNÝZÜïÚ›ÙîØõØFÙÚÚKÜlÜ{ÜôÜÆÝxÝ&Ûì×oÖ-ØëÛKß>àˆß´ÝWÛ¶ØضÙ3Ü)Þ+ÞbÝ ÜÜ^ÛÈØ×9Ù Ý6Þ°Û»Ø5×øÕÐÔpÕJ×AØØ¾Ö Ö>ÖÏÕ3Ó~ÏAÏ ÒÂÔÿÕÕcÓ|Ò%ÒýÐÄÎuÍòÍ•Î]Ï•ÑíÒÒ-ÐjÎ Î}μÎÓϲÑëÒUÒ¾Ð/ÐèÐõÐCÑ~ÒÓPÓ\ÓÒÑnÐ+ÑêÒïÓ­ÔÃÔ·ÔíÓÒîÏÒÎÓÏ&Ò,ÓÍÑ4Ð ÐÏÏHÎŽËÐÊÍOÏVОϓ΄Í"ËyÉ–ÈkÈfÈ•ÈfËsÏÞÐ÷Í©ÇòÃÇ«ÉÐÊéÊ?ËCÌóË ÉÎÅßĮńDzÈÑÊ‹ÎßÏœÎoÌgÊ.ÊÏÊvËÍwÏ8ÒÊÓVÓ]ÑÚÎÍ¥Ì[ÎPÐѨÑÒŒÐíÌÄɲɆÌvÏîÐ*ÑÌÎyÌËØÊ~ÌÀÎÏ£ÏyÐOЫÏuϨÍÉÌ…ÌÃÌ`ÏñЉÏÇÍèÌmÌŒÌÁÍìÎÏ«ÎiÍ^ÍRÎïÍ"ÌXËÌÌ>ÏêÐ÷ÑÒyÐ'ÍøË“Í,иÒ7Ô ÔàÒAÑŽÎÂÌ@Í[ÎÊÏvÑnÒ×ÓÞՌ՗ÑÍdËŠÍ=ÑÓëÔªÕ ÕûÔý҃϶ÍàÏoÒ«Ô…Ø,Ü Ü…×ÓÐÌsÍ,Ô¦ÙËÚ’Ú‰Ú–ÙwÖ(Ò)ϸÎáÑ}×ÈÛ¡ÝvÝíÙ&Õ|ÒHÒ”ÓÕJ×!ÚŸÝäߺÝÒ×^ӧѨÑäÒmÖtچܫÝ#Ü×ÒÐÑdÔØaÚÚ¼ØN×ÕÕÑ|ÏôÏ©ÑÔ‡×6ØêÖaÕÎÓŒÑ4Ñ„ÒÎÒ¹ÓÕJÖ~ÕíÓ|ÓÓ^Ó’ÔYÕþÔ?Õg×}Ú%ÛÊØLÖ›ÕœÖÙUÚèÙ+×ÜÔâÕ ÙÚå×¥Ô ÔÔ‡ÖsØeØò×ýÕÕ Ù¤ÝóÞÜNØóÖ¢ØÛÜÙÜÞ·ß-à+ß«Ý¸Û°Ú Û™Ý,àrá«âïáÁàMßæÝ¥Ý9Þ]ßnß›ßàâáráªÞ€ÜÜcݾÞà¨áyâfáXÝ1Û×ÛÝŒÞçß”àGàüÝ}ÜÝÜÝêÜšÜhÜ?ÝHßáNá.áŽáGá`ßÝÝäáçæêêçAäðã®ä–啿ñäTâóâ^æýèéè*ç ãÍàà“ßWßpß.àáwâ_ãôá3ÞéÚ ÚZÛÛÙÌÖ›ÖÔÚ¹ß7àÂÜàØIÖãÔÇÕMرÚ.ÜÝ$Þ°à3â×ßÂÛ€ÙÓÛpàZâyâÚá²á¹â=ããã_åãååÄäæVçOæÐã*ãùäHèmêÀê)êJè¢æ;åªåËçÞèÚè¦ç%çÖé@î î¢ê æäýåÞècë|íížìCìœëëäéˆçõæÍéì~ì»ìÖìí”ë„é è¥è™é×èkéÚê4ì[í©ë˜éJéÿéééòéÍéXèàèÿêí‹í:ëWè‘ælç³é9ë/ëê&ëìì'ì¿ìUí–íâì^ëAë¬ì_íþì¼ìîýï=ïsìÚê}ê€ëûì¥î+ð6ï`ì¾éúéÌíañ?ò*ñËí³êÿéHëî­ð&ñ—ðçîsíhïçñÖñ©ï:íÕì›îãðuñoðÙïöï=ñ.ò3ð&íøëí/ï"ðnî€íáï}óÁóñ%ï¢ïkñýòÔóaô§õ:÷øžùPûúM÷ÌõDøüàý»ý1þk‡$³þþ‹þÔÿaºïY—{…ù­á„Þ+VÊ MoK¹ùÿ¡ÿßÿàÿ€€Q ‡² ÿ,þŸ€>ÊΨª *nEÒ| o ÷H c y N ó ç í ÷” Ï † Z™ÓRŠ w ÷ “`•fdä5ã¿ iÀ ™ Ù|@ª Ú è ¡ u ê ¢ . R |  ¯ zo ‘ j ‚1t5  Ú † ä ~ ýOï » ¿ÿh@ ‚§Š ê“[ áH ¤ ˜4– öK& m Úi ¸  ; « ,¬ 8 Û¾ï æÓR Ë Ø fº‰ <  p Uy(×eTÁ²¥ms  •ìsú[ ®  ² £ 2 Ôž«Ž_ Y‡Å ‚˜|¡–ChsðãX Â ß ] ® ÓHŠ/6­àæ_€ÜΈßmPèqŽL˽ ñFïÔwÞï‚<8Ï£õêkµ#æk¨ YMAÏiå™{ÿãÉ6î¯ÃŽêÀ#7$îhÝl3²Aê¤RnÔ „|ÐF×ËÔœ±T&ÈàZ å#ä#¿ ®Ò±Kõ ‹#d$m"r ³ÀÅì ‰¾dÛß‘°4¬3— Ä¥êß´/à–ø>žK~t&v!î!L!eîéúãk¦˜"8%[&þ$|!OWs"¶&ñ&Ë#D"Š#X$ %C&´&D'Ä(3)I(Â'æ'à&%Æ%š'9+E.%.+ )±)æ)m)) *ä+-".«.œ.î-,Þ*Y*4+ï-:/C-*N*þ+×,x*P'5&&(Q,Ú-¹+o(%s$^&)+ƒ,,-®,n+ +Œ*))š(…)Í+.Y/p/¼/÷1ã1V.+*-Y0w2”3•4†420..;.ê.10S3ú6j7ò42~/n./ß.Ž.’/@133¦3¡0+ä()Î*é,d.“/1Ô/,J*†)ñ(€(“'ä(q+Ç-µ/a/g+C&ä$µ'$,A/Ú.W--·-*.[--,X+ý*s,<0N2Ò0/Z-š+})()?+.ˆ0Ü1V2¡1‡/O-·+s, .ñ--‚-.Ø-Y.v/‰/|.R-\+ã( (“*|,Ü. 0ˆ//…0=0¢/ˆ/_/y/š/Ï/f0Œ/«-ó,.÷0#32À-™)£'2'¾(,~/¢.è*3)ï,´1‹0°(¥ ›.'ª0ý4˜4Ø3È3±2 /) %¦$í)o1ù6í93:7M2í.†,Z+V,Ò.2’6:;‰<¯8;1è+«+­-Õ/2ª4J7%8!6A2Z/Ò.¬/00i0µ0D2Õ3Õ4…42+.@,2.å1Š32v/ý,q+N* )z*œ.¥1õ0Í-"*A',%a%½'c)¶)5)H()O,Ð.5.ƒ+;'¸"Ç!©%},ç12¡.Œ,Å,º+l(.%:%U)b-a/Ø0•1Œ0ˆ,k&l#>%å(T+©+™*"*•+“,G*3'X%&¼' 'À%ì%(\+y,\)Y$²"Þ#´%'P(ä(J)v)Ã' &ò& (‚(1(¬'˜(‹*,Z,O-6.¨-7,+A,.â/c0±/a.,%.Ê0®0â/u. -e-«.±01‰/Â,…,^0‘4Ü5ò2 /«,]-+2m67 3Ý.ù0¼7P6ú798 89):!884U1Ù/Ä.R/d2Ë6À8Ü52£0÷/ƒ-æ*Q*3*ò+{/=2J1&-µ)Ä'ê&q(O+Ü-·. .ß,,¸. 0¢/â,9-Â0·3¾4 4<3¾2L1‚/ˆ0€5Ó9;19l4//„,Ó-’1µ4À4¤345¥5N3.®)¿(,--3º5}4Ò2F0U-ø*£(’) .02r5d7 7©4÷1+.É+ñ,›/H3I68 9u9†6Ú/e+ô*H-ú1A7;Œ:Q641ÿ--/y3â638P7z4Ÿ2A2¬221º0Ð0!4¬8; 94 1D/„.-.‰/4:=x: 5 .*X+F.ê2`7:ì;4:61ö-¤, -1€89=x:06Ý3¦2¡1æ/.}-30q4Ž7ý7™3‚/.{.z0¸0˜/¥/ô/.à,’.1f1B.o-¼04Å2Ï,Ÿ'‹'±,2}3 2~/¤/ã/÷,U*H*++Q*/+Û/5+6ö0‹+j*©+ˆ+Ä)ç(*x+E,Ç.á/Ó*t$#Ÿ'ç)Ž(z'¹(°)Ø( '¥'W*ž*))Ê)ã,œ/V.ž)(Õ)+.z0„1 45V1',i)H+Ÿ/ü2»3¼35¾5×3¯0.,È*­**,R.¨//1Ø2H2ª/Ÿ+j(L')&‚&î)R.I/c-á+·+Â)$! ¸ &&-,æ-£*¤&[&†(ó)<($ã "/'P*_)w'r&o&º%Ç"K!ã#æ%+%#%"#‹#m"„!Æ"Û%(b(C&Ð"—öü ^#Ü#=$2%{%õ$š"š p †¡" C$ )Q+¥'!ho!#Å"O ý+!Y$µ%É%)$ù!4 ÷:#É%æ%%w#]! ž é °!„"È"–#,$“"ÄèƒTv#²'Ÿ)Ñ'Á#""K! L!ü%3*b,h)J"À¸!ò$—%5%m%é%e%$"ûÏîÔâ!"9"Ú"$Z#˜!Ï­Øb m!>"!¿v&`÷0 ؇‚T ýâ!ã"C!×E"cí† L M2^"Ò#Ž! ŽH ˜%2%? wJ£1!&š'Ñ%Ð!1ó w#Þ#$þ$Q'7)Ö(è'¸&}%U&Â(Ù)(¶&â$˜$Ú$¸$’%÷&5&0"¼Ž 9! /A§17S,¤ã~vˇû®wr!k ¯°Üe!À õç#"Ø$­%)#Hµ§6¸ Å!¤!J 4ù¢_¬!RoÕ0—Èlû"0 –ýä¤Gó ” !êü[@^Rµ a , Ö O•q©Àå] ‰˜¨ ‰ ?T?/T û3ß( Þ† !l O{_2 Ó t4Bœ œ ÷ ½ È`]…Á: Æ)i>¨#å‡QÆ wÒ>Àü¡úkúõüÅÿo ÿ­üHû7ûøûOý¨þ„þ•ý’ýÅýWüø ö†÷£ü\ Ø…þ§ùãö÷Hù`ûüëüöþÚHüÏõÆñ§ðïñgõ,úýïû>÷ òfð}ð3ññÒñWô´÷ÍùÇø4õFñDïWðlòò÷óx÷ºø5÷:õUô¾ôö`÷øò÷5øvúãû¢ú¤øS÷S÷Zø¸ùÒùúîú¯ù…ø}ø£÷“õqóÅó§õC÷öóò]ó’ôpó3ñðï‡ñrô$õíóEòøñ…ñðð<ñ{ñ:òmò„ñ)ð|î©íîÉï!òEô“ô,ñ¶ììé>êídðCñíðNðgïüíì?êÚé‘ëîVïï4î·íŸíäënéêè êÔíÓï´ï$î®ìçì½ìêBç…çê‰ìåìììëñç›äçátàÆà[ââãÈå[çÆæßä©âøß&Þ9޲߽á"䫿YèPè;æãGàhßþà²ãåkælèPç£ãkâî䳿wäá…àõá}åèÊèæç å&á5Þôßúå€êEêœç0åtå ç¤æðãBã æ>éëÌê»è°åäåèFí íèêä+æê>ìYìÂéæ)ä÷åEê¡ìê¢äQãç ê¸éýæ,åähä€ã‘áœáâNâcâ:ãwä5å æÝäƒâMáçàNàqßáæŒêëXçfâÖÞÃÝ¥Ü3ÜsßäçæDç'åúâ¸á/àYÞfÝåÜÝîàåxæOçÿç¬ç¤ääßÝæÝ­à ä¶èTë'éæã£ßøÞ-àìßÖÝ-Ý-à+äåqãµß²ÚMØ|Ú8Þ]àNà­ßEß/ÞJÝ2Ý-Ý„ÜÚÚ%ÚIÝÌánáÛ×Ñ׌ډÜÍÜÝpߌáà.Û—Ö'ÔÝÓÖgØÕÛ»à{ä·ã|ÝÕäÐõÒÀ×êۜ޼àÄã1æ çªäÕÞÀØ Õ-×QÞ‚æÔê3ê¡æ¦ánÞ€Ý0ÝSÜ5Ü#ßãÀã›áànàáàÐÝŸÜ®Ý#ß÷Þ\ÞÓÞ­Þ#Ý`Û”ÚnÛ[Ü·Û{Ú;ÚJÚ ÙZ×NÕÔ.Õ?Ù–ÜBܾÙÜ×cØÖÙÖØz×ÁØžÜ:à!àSÝÛˆÛ“Ü@ÜÚ÷ØáÚ‹Þ¾ààyÞ.ÞÏݤÛçØ¼Ø§ÛïÞá_ãhâùÞöÛQÚuÚÖÛÜÛvÛÝ0àrâ½â^á£ß˜ÞÝݤÝkÝ»ÝrßÊáTäëåZæÝäâ0ààáâHâfâŽâã´äåGäÅâCá±ßßLßLßÝßaâLäþã©áëÝ6ÛBÛ]ÜÝHÞyàÅâ"äÿãCáÝ+Ú=ÚüÝñáãã9äã§ã–ãÇáyÞ_ÛUÚÜÜ¡ámäÊã[á]ß!ަݱÝÞ:ß+àÀàðáÎâYâàÑÞšÞ[ߑ߭à!äUçuçqäèàêÝDÜûÜ`ß*ãXæ¡ç€æãßMÜŒÚÛXÞuà£áÉáÁàsßhÞeÜٟظÙÛ­ÜúÜìÜ®ÜêÚÙwØcØæ××ךÙxÛXÚÔÙ²ÚoܯÝÛ×Õ.×2Ú’ÜšÝvÜÚŒ×ýÖ3ÙÜÐ݈ÝÀÛÙç×áØžÜ àá0ááÍß߉ßèà¶ãúä>äÄãFääâÛà§â çYì-ìêæäàvßzâžåœæ³åaä·äçpè7æÞá£ÝÜ³Þ¨âŠæ£ç³ådâ¢à[á…ãÏäºã®á·á*äqæ¥åâÓÞÞß,ágâ>â!áYßµÞýÞÿÝ×ÛuÛˆÝrß{ßòÞ×Þ-ßÌÞýÜzÛzÜGßeáláCà àëàÍàÞßfàêánã¶ä?ä>ãã¹â*áÙàã`çëê#ìŽê´çåäéâÂâ³ä*çøç8ç\çîç÷æˆãàM݇ۖÛõÝ¡â<æþåúáóÝ'ܧÛÛÄÚGÚ ÛÝ8ß½à@áaßGÚ:ÕÕšÙ*Þ(ßcÝÝÜQÞÕßMáiá‰ßÛÜÕÛ ßdäbè!é)çŸä³äÛæ¥èléé’èé†ê;ììë•éÞçeè^ëCïcñ0ññïëíëvéùé¨êGêÐéËêIíØí êñä·áÉáä1æçè è°æ2æWçÄè'écçÅä«äjè}í?ð‚îîéoæåå<ç>éãêÓêbêÅé®èéç«æÚåtåÙå?èðêåì í4êJæ„äoå èŽëÎîQñÆñ?ðîÃê¡è»é”ë÷ëwìï.ó\õ8òëÜæ/çléÆéÃéÈëµïòÈñ8ï)ì'éáææÀèìqîŠîîñí›îTïÐîqì¯èçgëPñ7õÜõúôÉó!òsïGìåê=ì¼ïó„ó\ñšï¨ïKïÙìñéôèþê«îñJñ:ðÞî–í˜ìÜë:ëÏëîåñõõ<òï+íwì)îìñLõìö¤õQó ñÛñ óóòæñÏò%ôõºôËó™òñðŽïuïwðÕñÙòEóaó'óýòÁò–òxó…õT÷Ž÷öNôJóÄôƒöøÀùöùù÷~ôEòñó€õƒ÷Ø÷GöòóµòúñÖð:ï ï†ð,òVó\óÅò€ñHñÓñ»ñhñÈñæòfôNõuõµô¦ô­öúEýTþ1ü„øö~öù£û¼ü ýý}ü û‘ùmöôDóNôÀö5ùú¶ùé÷nõuóåñ0ñ>ñPò:ôüõ5÷w÷QöàôvóòÒñ‰òqóBôîõy÷£øSùŸø÷ÞõeõZöøäø=ù/ùû÷Cö»õìõ\öQö:öuöo÷´÷÷C÷Ý÷ù*úúù`ùÙøþøúóúÅúÑúûÅû­ûýú~ù÷ø…ùdú•ú]ùÃ÷c÷Æ÷Ëø„ùòùŠúFûüüIü<ü­ü7þ'ë#Íh¬(æy§Ö_4ÓW妶­ÁD¾»!åèzþvýþ0¢@äëÿ4kKÿPþ…þîSùãù# 'úQÆÍF  < 'ª š-o Œ k ƒepæ1dv¼ùŸÀ— j Jøø¨³ D € C'SoØPcæ—¼ôhcØÜõ•ò‡Þ-öyábԩЬEÂj T¼†b>èhB|}`‹ ? ^ ê 29 a ´6µÄ j¾¶ ý > ˆ ^ s û 1 Ç  ‡«Ñ€’KU“$Æs¸â<˜PToÑq‡W©ìTȦ>ß|3«TUZoå#ÞÊëw Û{\ ^ 9 g C Š ô • Ò Q þ É Ü › ˜ j Z V  6à÷¡Gí ~~–jîÁ=ÙþGe£ð!;ä™SÕ„†¡¸KëØ5  n Ÿ z Ç ‰ ÿ C ™ — ´ | J ü X’äÎæé1ÝÔvvœ’Åð†þŽV”¢D«È– Ä Ò ’ ™ò¥ƒU ¤ B u /kt 9è£b‡´vO ©HÓÇ ý Ê ç ù Ò ÏÓ±²½ 2 d µzk÷A^ =Èwn.È’.%¾7ž§Ö­A'I ù W Ê µ ¬ ¹ ¯ +JÜ f v ˜ õ ¾”|ªZxŠ¿µŸÁ²÷‡ùÜ9•ˆÍäWÂÙZ—¯²béNü#R’¨¨a!I‡ª^×ó}vƒ„§`¶­L™H!• z«“Øv?ŒCß| kÁ9*¦´EM>ABXÐñÖ>l ñ ñ -  U · f » „ I › *ÆD©É©hòžqA`Æ÷DÐñšýêŒSSlIg†¾ó‰Ø©IŽÌI©V²æs]ðusîj/`ŠßOl-Øã?0BN¯K~ô&—t™áù ¦Á)+˜ ¤ Ð å © N M Ï “  Ú ó ˜ F ° † ä 9 Ó ~ î ú ~2ó à YÄA¸é»Ü1Š]º°êíÄY š à s à I  õ ½ þR;Aƒ ›e ñâLÄ m ½ 1 ‰ ó  €  v Æ Í G ÿ s«¨lÚG“ÈA õ‘'v;Yµ‚?é Kqxwz ­ þ u æ ) ^ GtÉ 1˜<à°‹@çPÅr\D$VßLd†Õ`¾©0ÐR†Üˆ = Ò ² e   ƒ » ç  ˜ µ ÿ µ M  É U · ç M ŒN# ×'F’Xyº˜Yú¸ƒÅ°üø°•¡«|/7qƒ2Œ¿ŽC®²ÿÿ^þþ+þ‚þƒþþ½ýžý×ý|þXÿV ¨!¸[ÿµL’>ã ûܦªã > / * Q Ž t - & { ì  Ö h ù¨\F?2­bú $#5*ãoßV†uÙ  !/|G y “ q Ñ ô  O — % ÷ ¯ > ª ® • À ô ò L²Næ y I ¾ ~ Ù Í £ > ( _ ¸ ß õ Ä Õ ø ¸ Ç 1  º ó %lÍ2†hBqÐ=œUà5T(\­éâÒíD—Ý!iÇÿ X×ü$`‰ÄÎÈ+{î#ÛŠZ’6¨ÂöHÍv4+S³Ì•w@ ò¥cÆR;$òÂ’IÚŽ3×b[ \ ¼ T é ¢ X ­ q  í 5  ² €   ° n ½ {  Ý È Þ J H  ø x  æÅËÆˆrE]§ñG z b ] + ÿØØ = / " ¸Xí“H)á˨tð`çÃ\€¢‘aÿ·DÊ™J×:­‹MÍAÆÿIÿêþŸþþyýYýMýþü¶ü§üküûû˜ûZû2ûû­ú/úÎù¨ù·ùØù÷ù ú¼ùiùù ùBùÀù'ú¨ù³ùIùùù|ù%úíú‹ûOüéünýþ»þDÿ‚ÿÈÿTj¼áæÂ°ÿ9ÿ"þVýâü.üû3ú¦ø÷iöÄõ õôó(òZñ×ð#ññFð ð¢ï2ï¶îî¼í½íîí7î¨îï:ïhïÛïgðíðvñ"ò)óUô€õ_öæöD÷©÷ø øùÁù?ú¥ú»ú³úúkúZúBúDú=ú7ú_ú˜úþúUûŒûÀûáûü`ü¾ü ý%ý:ýNýaýlý7ýÍü$ü”ûQûØú£ú²úôúûýú…ú"úÎù§ùnùcù£ù¿ùÊùuùHùùäø¿øÑøùŽù&ú™úû¦ûüKüŠüŸüÂüçü[ýÜý›þ#ÿZÿšÿÛÿ €¶Ï/ŒÄÆÍ½¶Œ7埈#…ÿäþ]þ þÉýˆý×üLü—û7û÷ú®úEú‰ùù|ø(øí÷º÷ž÷W÷÷îöòö ÷.÷)÷U÷t÷q÷h÷c÷i÷÷Ÿ÷“÷{÷l÷J÷÷Éösöcöwö¬öööB÷¡÷û÷søõø ùÀø}øøù÷ã÷Ò÷ú÷9øvøcøøv÷ÆöööPööö÷Æ÷z÷îöVöÝõ±õÊõöQöYöYööWöìõqõâôxôôÞó¶ó²ó™óMó)óèòÓóYôcô6ôôôüóôÑó—óó˜ó^óÅòÿñqññ’ðöïOïî9îåí‘íNíÛì€ìfì¯ì$í–íÿí<î‰î¾îïsï­ïçï%ð`ðœðŒðŒðEðìï¶ï±ï¯ï½ïð_ðtð™ð£ð«ð”ðHð?ð£ðÌðâð´ð/ðÄï^ï8ïïíîìîÒîåîíîùîïïîìîàî¾î§î“î€îNîìíœí[í íÓìì-ì½ë-ë­ê4ê¼ésé5ééÀè”èènè"èøçäçè4è®è3éyé é¶éœéÖéêXêºêýêùêüêëðê¬êŽêê¤êoê:ê êêCê]ê²êÚêÈêhêêoéßèIè»çgçâæ[æíå­å3åŸääTãôâºâºâÛâáâËâ›â:âïáá>á6áá á'áVágá]áQá]á©áâ â&ãÁãiäÄä#åyå{åtåkå¢åö傿çUçeçSçç0ç!çàæÍæhæ6ææÐå¸åkå%åå£ä<äïã®ãŽãrãøâ¨âJâûáyáëàtàà¾ß¨ß®ß˜ß‘ß~ßvߌßáß5àuàÛàvá4âãŠãúã7ä™äÉäÈä°äŸäºäÉäáäìäÀäˆäcäÿãæã¬ã©ã‡ãlãWããÜâ©â²âââÈánááÖàSàÛßußGßßÕÞœÞmÞHÞ&Þ Þ ÞòÝ Þ<Þ–Þ÷ÞßnßÁß%àÙàtáâŸâÚâãoãþãLä[äOä äþãä ä&ää&ä0ä.äGä_äqäqäwäkäJäMä:ä=äääáã€ã6ãÙâwâââOâlâKâAââCâNâââ0ââýáÂáMáâàqà àÜßqß.ßßßýÞ ß,߉ßóßMà®àLáká©áTâlãeä1åðåsæËæbçÍçèlè§è²è¶èªè­èèyèvè{è‹è‰èAèõçñçæçªçxçDççÅæNæÜådåÖääãÖâ®â â™áSá@áLá¤áÓáKâ€âñâGãIã'ã ãRã’ãAäªä9å{åDåÆåÓåæÇå¤å9æ9æiæŒçÔçaè®èûèéé é×èÝèé7éGévé…é—é¯éÈéê>êpê¸ê;ë‡ëïëWì¬ìüìíNíEí~íÍíLîÀî;ï„ïð‚ðÉðúð-ñ>ñ…ñÖñHò©òËòÀò}òGòîñ’ññ›ðð¢ï6ï¢îúí_íÛìRì‰ë ëêê¥é[éKééñè–è,èÅçnç,ççççÛæÆæÏæªæËæ¨ææŒæ­æ*ç¾çFèÖè$ééûéiêë¯ë4ì¶ì5íÁícîïµï2ð—ðÀðêðñðéðŸðÊï‚ïƒïð2ðçïŒïï—îOîõí“íýì†ìtì3ìäë~ëëµêfêHê_êHêêêÕéžéé7éêèšèèÕç ç¬ç¶ç±ççRçç%ç>ç\ç„çiç9ççÖæhæÓåfåüä›äŽä‡ä«äÌäØä÷äàä*ååÍå æ6æyæÜæMçÛçfè ékéçéXê³êóêëpë«ëùë8ìdì¾ìÄìÂìÅì¸ìÒìÒìíŒíî¢îûîï"ïEïï¿î¼îÚî!ï@ïCï ïæî™î îaí·ìaììì(ìÎëiëë©ê|ê#êûé*êPêÐê[ë¿ë/ìxìÚì1í/í†íÐíBîï§ï8ð×ð\ñÉñò}ò×òó2ó‡óÒóô.ô=ô ô ó@óó`òÇñ¨ñ`ññœðDðöðdñOññ×ð’ðaðð7ðqð˜ð¯ð‘ððÙðþðEñÉñVòóPóŸóÇó#ôsô¿ô(õsõõßõüõÿõòõØõ¤õVõõ$õ*õDõXõbõ^õ?õ$õ?õ{õÀõ$ö±ö(÷Æ÷0ørø øÃøóøùEùyù®ù»ùÕùÀùÍù­ùrùRùù(ù=ùùùÌøÑøÀø²øŽø‚ø{ø‡ø°ø÷ø>ùùúxú û:û4ûXûpû‘ûèûü‚üýeý®ýØýþCþ~þkþwþ[þXþ3þ4þVþWþOþ þ¬ýñü‰üõûcûâúnúú­ùOù ù«ø>øøÛ÷©÷ã÷ø¢øù—øÂøøøyù{ù¤ùaú¿úúú(ûmû–û´ûÝûôû:üSü‰üÚüZýØý^þÕþ7ÿ’ÿàÿþÿ9yÓ0´ .A*橆c,ïØ¥FºÿJÿâþeþËýmý ýÖüÆü“üAüüÖû«ûÉûÎûàûàûéûõû üDüMüUü|üxüÂü ýyýíý^þÔþÿMÿtÿŒÿžÿÿšÿ€ÿÿ©ÿÞÿаé'–ú‘gªÏÈl°bF.üû*H3JD/DK#Þtè{Ýÿ¥ÿ€ÿ‹ÿ{ÿpÿPÿúþªþTþþþýïý!þYþrþ”þ´þáþ#ÿlÿ¼ÿ‰yÄ#g‰Î#e¶ø>‡ÞG£Y›æ>ƒÏ0X›Úú áXW\BAH+òÓ·tJ!7*Dn–e}©Õ' ‘ º Ç ø  ù ã ¹ ­ ‹ y D D 3 * ÿ¥Uî­bê¼YÊbþ“7Àpe]”ªeF1¼“psŠ¥{È-z§ëFÂE¼ ioY,í¯Y Óšj$ØŽC'éíç3d. ãYÌ];Æ{Hà‹L4þÿÝÿüÿ$h“ÔL÷Kó™,ãcyÈ!7Jp™ª¯£¨¨Ÿn"à³_2ðåÑÀ°uau¶ë1gÊÙδ¡Ÿ‚bÜŸˆRLOTv¼ð8{Í4j§Ú ? Î Ë ° € 1 øÏ¯˜rojnKB=MIO4¹#fÇ8•öx­S«—“¶ÿNŒði§ ;™ÀÍîçÖõÞÄ»›DÔcÛMÆ=Ö]îÿ§ÿ=ÿ±þ.þ ýýÖü¸ü§ü³üÇüëüý ýïüýGýuýÏýMþ®þÿþtÿêÿ9z†b› uôJ‚°êî=W©åfý‚Z/ô‡Ü    Í«Š&öª”(σ.Ôeû ¨-—'¹| ½ÿVÿëþ:þ±ýýxüÀûƒûòúxúLú%úúþùþùìùú ú+úvúìúNû±û÷û'üSüqüwüžüÉüýLýbýƒýÀýâýÖý¸ý—ýpý…ý€ý§ýçý7þ~þšþŒþkþ\þ,þ3þRþyþ¶þÿhÿàÿ#}ÇZ{ ´Îuã&»*…˜ÂÕý#4Jr¥±±­Y ¶ŒR. þúúÉÑðQÉqÌ:³¼â|ÂÝ6 q i ‚ ž Ž r b " ü¡MýÄPÇ'¬Ä¯udBú_÷ÒÝåãý-KR<!F‘#ꬌZ2 • R *  +.ì±Dì˜ ¶DÔFœðíÁ\ÿ–G¼b«E×uö˜9åË£kZ>> øýpÆC•Íøù8Zguˆ–Ÿ®´Á—Fë§pê\Ô'œ  Ë ª · Ö  / ~ ¿ E›l»šnÙE°Ý/vËZ¾S1 ÒkÚŽf"ûú ðÖ‘ƒH42¼Vòm»P° £ * º N æ ¥ d  Û ˜ š ¾ Ó Ø é ÷ ë ê ý  0 H £ Å á  $ " ,  ù  ú  W ¦ Ã Ì ¿ « ž À Ð ß  á £ H Û y 0 ùÉo¦GÜZìuF#ìàÕº†qW?D;jž } ñ`ê`÷Ÿ * Ü \ ¿  k Ž } ƒ † … ¤ ª ž ­ ‡ V  É +  ó ¼ ¶ ¡ e ² 6 Èk9ùºœwB0&+M™×\v¢¹À°˜‰“‹’¢“p]) ΢|=ÎížgBÖª…‹gîì  0;DVe|^H>å¼aÐŒ 6 Ê D ¦  V i k d b ` 0 > Y u ‘   Ê à þ 1 € ³ Ü ß   O â  "   9 ø ² \ <   ) . 4 L ‘  ê W l ñ™7û³" 8 B  ý°ykLA0*ò®u@Ý*zåQ¢Ð Q ²  ¸ A Ê  F j h º ø î ½ ­ ƒ > Ñ O ð ´ ] ì ~ & Çi(òÞæÊÆ¬µÃËǽ¬Œ=îŠ+¹V§n Ò¸·¥¸ÓÜ÷(1:`tGõªaPjhxU='3  úÀq;ìŽ?Сc/ Ôÿ˜ÿÿ]ÿlÿ’ÿ½ÿ$gÅHp›•v}¶3ˆÿåþMþvýÌü'üûûûåúñúòúû?û^û£ûÁûìûAüŽü ý˜ýþzþŸþÅþ¿þ–þgþ^þ'þ½ýíüfüîû¹û„û>ûûÓúxúMú2ú¨ú¬ûßûüûÙûÁû¨ûfûûçú¿ú¹ú•úLú/ú úýùÅù£ù7ùïøÀø‚øø’ø†ødø1øø¢÷2÷÷©öKööÿõÏõªõ·õtõõõÚô»ô¾ôòôÙôÖô‘ô›ôcôEô=ô ô[ô¤ôÜôPõ”õ¼õ¿õäõæõõõöBöö·öñö÷b÷¤÷Æ÷¤÷¬÷÷d÷d÷E÷ùö¶öcöûõ°õPõøôpôÏómóºòMò$òüñâñªñ€ñKñ'ñöðÄðgð'ð ðð ð ðâïšïlï$ïåî¢îYî$îîÔí·íÏíýí î-îþíêíäí îKîWî€î}îZîKîkî±îðîGïÓïnðñ~ñ¯ñ·ñãñÏñqñFñýðµð‘ðOðêï’ïïZîÓíí{ì ìÐëàëìOìoì™ì‰ìJì)ìÕë×ëÏëÃë£ëëXë ë±êZêêÁépéMé>éRé^étéé¥é»é­é¯éÏéÝéê`ê½êôê3ëMëHë+ë¶êUêõéžé{éNéüè½è‚èWèè¾çYçïæ½æ‰æ‹æîæ0çpç¶çàç+èxèÄèVéÙé›ê\ëðëvìÂì÷ìíñìâìÀì›ìœìŒìLì&ì×ëŒë ë²êkêêðéÄéÙéÉé…éé½èFèÀç‚ç4ç)çKçsçÄç)èÄèézéËé êSê´êïêë[ë[ë<ëäê¼êtêêÌéÃé«é‰é€éŒé‡éoéVé.ééSéRéŸéÃéãéÿéêêê-ê!êêðéäéêê6êPê,ê$êÚéeé\é@éé é1é*ééGéméJéhéJéVéxérépé¼éöé+êlê¢ê·êÌêùêë<ëeë‹ë»ë´ë~ë1ëöê¿êªêê’êbêcêDê-ê êªédééÈè‡èPèRèèîèXéÈé%ê¤êë’ëìbì´ìúì@í?íIíDíí±ìZì)ìÅërëáêêÙé^éSé éGé{éTé ê°ê&ë|ëðëeìÔì5í•íæí#îˆîåîOïÀï ðGð“ðÂð·ðŠðHð(ð"ðð<ð„ð¤ð™ð¨ð¨ðFð ðÓïmïEïï ïïïïï¼î«î¤îÒî<ï—ï+ðªðCñ¤ñ'ò„òéòQóåónôîôœõFöìö¨÷9øwø…ø„ø‡ø øÒøù|ùµùéùúGú3úúú-úOúMú”ú—ú¢úoúú¤ùùøð÷g÷àötööåõ¥õaõøô™ôEôïó½óŒó‘óˆó‘óló<óÿòöòÓòó]óÏó>ôËô&õoõšõŠõ´õëõ[öåöW÷ê÷XøÈøùPùSù\ù?ùIùYùDùiùhùbùù¤ùÏùúZúºúû°ûIüýÝýfþÒþÿHÿ—ÿàÿóÿüÿ"-5‡· Gvt‚=þ³]«ÿ ÿ³þDþÒýKý’üëû]ûÑú5ú¹ùù–ø'ø¿÷G÷.÷%÷÷N÷E÷P÷M÷÷Á÷ö÷øZøªø­ø«ø´øãøùIùŸùïù5ú~úÞúúú#ûû½ûü.üXüXü=üúûÈû€ûDûÅúWúú·ù|ùvù2ùùêø›ølø*ø!øö÷ç÷ö÷Û÷á÷ð÷!øFø'øøøøøøø=øOøQøcøGøiøwøšøÜø"ù‰ù ú’ú û¨û<üÇü-ý}ýÙý þqþÿÿíÿiÊWì‚"Û‰)²PÅHx¦‡v)ᜄ2Òª¥½Ôö2ƒ¨Óí*4-ÿéÑÙéÓÃy*È=5[l›åL¬nß>‘üƒ Ñ ø m Å A † « ¾  J º A Ì ZÐ+Pzz¯á"zÖY¹ 0;WHG5AN2<#öòQ» QuÆïx¾¬C˜å"*VUV|™õ?© dƒ««ÈãâÇ•Oð[ö‹*  -O}ŽcW´q0  ,$ ÿÕÚK°ú7_~ŒntV‹Ê óë¬e4øÉÉ |B¼}ÔÖØ-tÆê  Ñ“PĨ§¨¨²“kz‡˜»ÚáÔ¸š;ßrý›<þ¨k‘Ï•WHaeƒ¡âùŠŒ9ç ¯ i A ô à ¼ ¸ ¦ w  ¤  C € ² ’ H õ ¥ d ^ b R F  Þ ¸ o à  ° 5 Û´¥lifpaoŠ¡‰ÅáΠrôØÏÖæ13aˆ™Ñ$ p ° ÷ J s œ ¾ Ä Ä Ö æ   - H z ‘ {  É } P @ -  %  é ´ Y  ­2¥;Àbð“ÿ…úoà|S*BOB7ÛÈ¢±Ä žÿ}7SK„Å ÙF±ü;z­í2ˆò : =  á¼uW%*Es­Þóðý   6 Œ Æ ( Ž Ç À º ³ ± ¨ ç  7 Ä  n è  . V „ ­ Ç ¿ Û Ä ¸ Ä Ë µ  4 0 1 å š g " ó ¼ t W 0  V | Æ  o ® ä 3 p ´ Ù 4{¦Þ*d”¸ð+xì0r£½ÅÄÁéíKox°°Ã•L÷›H ®jÒPßw!° 3 Ë § ‘   © Ä ñ ÷  õ ó î ß ñ  B N G E G h ¾ %·4ÝQ±íÖ¸h¼ˆZó½Ä°¡¤¢¢œº×¤_AõÛ¡xd ü â ä â ã þ õ R\bÃð%åäÒÏÉÓï÷ñïýùéBU˜’¾ÝòÙª•x(ÖÈÉ™{ii{ã:£Ö"GTQ#êŸS*ȯŽ__Ö Š n 0 Î „ K F C = 4 8 þ  Ï –  • Œ ´ ½ ë E x © ¾ ± £ d 8   ç Ä Î ° © ½ Ô ½ £ ¡   — È ; À ä  ; . $ 2 B , ñ È k U Ø — f H D F 8 H d y « þ ! " "   å Ò ¾ ~ w V A å Ê Â  Ô h  Øw;ì¦rI<dœnÖQ ¡ × ð ÷  7  ­ â  Y z ¾ ê  8 L [  ‡ { Y T  ¹ Œ , ä Ê § f . ã ‚ ¢vQ'Íz~ùs-ôÀ¤²³öa·˜á+37l~\  ¼Œáü M4 w ¨ " Ž ô 8 × ] œ M a ® Ë ë *ä Æ X l r “ È ,‚×#b›Ö6D0üÒˆyOÅIø ¾ € T Q D U O b B j É p¿z´Ýð=Gd–Èð ÞǼÆÛ,EW£êÜõ 3€è`†l’¨‘‰’~}}qlfbN›_¼ú1<:á娤}^ê­”ªÏLkƒ Ýó"u©†þe­ðþ]e†Û-z£¶·€€H(-.9QF*ò®iºuüò×ÆÑ­ˆ`wНÌ*6Ymc‹£²Ë:šñ  Ìšh5ÉLó·Pão1âǶq-èu5è›XRcl–¿"r¨óN§oÌ:Hm“¬Öõ1R‰œ°›i@ÆhéfÑZ¼<„%Ô>õàÂcRØÎ{DÛ†9Èn•HÚ u 5 ü Ë – ° Á ú  U S = X † £ #KŠ¿÷üîÀ–3× { · O þ ½ N / , D [ Ž š ‡ T ú \ Æ : ¬$ë‹c-â‹®;¸)ÆqNW]Áç+sVÝZ¨!"ÞQÛ)H®>Óµg Ú½À×Éé*_¥¤Êê:J¯¥ 4†½îÿ+P{°÷cžÕ&Xv­ãJ ¢  d w ¢ Š i 4 Ë : ñôµ‚G®a#µ­™„”uDM üö#z¥ÛƒÛ3¨, ´ £ — ˜ Ž ÛQ%æÕòÛð¸*Ò C m © ‰ U 8 ¢ ÿ A †è]è€A6q¼,§Z Ì « ˆ Q » GÙ&aioh9Ùèãñ-DP…°¦­¶e‰¨ÞÍ÷L€ó|Ê'MVìzê|Ãò,=“ ð ` à $ ‚ ì [  å  S • Å ï  + P ” ˜ ­ ï í í ð ÿ  ó Ú Ý À Ü ² c  ¤ I  ÐXàŒ7 íàÑÐÞõì>cƒ†aglfvcE/æ¡B÷¨#´F"ô´p0Ü¢Hõº¶Ðu«zÈgÂ.V”¾åÂŦk%Û•Göî¾{!á“PJJ!1<z©¡¶¯ÍÒáϺÁ·wFð¶ŽpW>/.Ö±|Q¿ÿ]ÿÿíþ¢þ}þ#þëýËýý”ý[ýNý ýÉü§üšü«üÄüÄüßü ýý%ýVýzý‰ýqý‡ýyýDýý ý(ý`ýÛýYþÿþ‚ÿëÿpÄû*JjgFôÁk£ÿYÿÿÐþƒþ|þyþ¹þçþñþÿMÿsÿ±ÿüÿ,~Í<„ÚvÑ"cŒó…£a  ãVü®½ºùS—e²žÊèÿyÿuÿ·ÿ"ƒ.Jm$ÿýü&ûIûüçü®ýÿýÊýeýºü}üjüÝüXýÛýfþÒþÿþÿÿóþØþ¹þIþ¨ý%ý™üSüKüüõûãûŽûû¶úUú³ùKùÃø.øÇ÷—÷S÷÷Îö€ööÃõÈõ0öàöš÷[ø«øÜøùù0ùùùù@úû%üýoý}ý5ý–üòûšûpûMû\ûmû`ûûžú%ú¦ù?ùÒøqøøä÷¤÷n÷ ÷îö¢öfö4öüõ(öJöVöZö#öößõyõ2õõ:õOõõÍõöõêõÝõ¬õ`õAõ:õ õÝôòô$õuõöÄö÷ø¢øùŠùèù\úçúSûÀûÊûÐûÀûeûøúxú^úNú~úÊúúúûûû×úñúþúû}û®ûìûüòûÔûäû™ü(þ=ÿ¸ÿ—ÿþùý»ýýý)ý—ýþ,þÝýký ýÌühü±û²ûTüšý-ÿ4ufB ÿ“þ§þ±þzþAþ3þ·ývüäú@ù5øÿ÷ø•øôø¦ùúúúùmù¦øÉ÷óöÛõ6õÝôÉôvô£óïò(óÖó9ôaóEñÈïZððñwòÖñwñJñ?ñßðŒð#ñÔñò+òcòóàóêó™óÏó õ¹ö÷5÷öšöÀøZúÓùCø÷Æ÷¨÷”öö½öc÷ ÷Øõ¹ô ôïô¿ôTôöô-ö!÷½ö­õ@õ¾ô+ô=ôÁôÛõ÷ñ÷¦÷¦ö¤õâõìö•÷•÷¿ö‹ö÷æ÷’øzøíøCù«ø@÷²õéõÉ÷2ùã÷oõ³ôö:øa÷ëõ õ£õÎõ\ôòÃñzó€ô×ó%óÈóôëóßòmñBñÃñ}òëò$ó¹òògñKðdîAí³îkñKòsðóí~ínîÊîlíNìÏí…ðkñ¸ïríFí¬í×ìÎëaìßíEî7íŠìíÇíVíëè_è¯é_ëÀìcîï8îËìDë êÉé¶êbìDî:ï“ïÚï¦ïcï›î`íœí€ïÇðDñòôŒó§ñ®ñýóYõ×ó¹ñ:ñèóÓ÷2ù÷AõÀôôèòò ó˜õ9÷žöîõËõ>õãó›ò)ò3ó·ô¬ôöóÈó&óäñàð¯ðŸð¯ïƒï{ðnñÔð>ï î²í•îëî îÅí;îÜírëYé÷é ìníwíVí]î[ïÝî=í÷êuê©ìLïºñ™òŒòUò$ñJðâïðqïÌîpï²ñgôõoôhòèðOï2î*ïsñóæòŸòóGóÖñ(î’êúècë#ðtòPñKîWìDëãêpëSí9ïáíêê ëVîûï`î¥ëêÄêÈëäì-îÒîkî‹í[í:íí-í¤í»îð²ñåòòjïRíFíûîÕðnò\óÏòŸñ=ñeñ{ññ¾ðò˜ô1õô™ó°ôÜóVñ•ðœñ˜ò“òòüó]ööó„ñ±ð€ðÕððúï»ñZóMóWñ€î*ì­ë8ì³ìµíÆîÎîàíýìæì–ì®ëNëìêìèë:êÂê í9î§ìßéÖèßéYê½èbç çç@æé傿çæÔãæâÆâ›ãqåþæZç|æÂå¥åíå=æçæèÎêÔëfë&êêQëOì›ì5ì«ì:îïäíìCíìî/îìjìíNîmîŒí„ìŸëÂéšæòä|æJéÆéUè æŸåûä¾ããÛâã£ä‰ã âjâ®ã0ã:á0àAá.ä*æ¼å›ãˆáÙàßàhá7â¼áà+à'âÑãJäªäµãâ­à+à±à,âã ä å5å ä:âàßßXá|ä¢ååãÝágâã]ãHãÐãéãƒâƒáðáèátá¹áàâ—ã¼â_à2ß2àžàßMÞ¢ßÁ߯ÝÙÝêßôààûÞßfà'àQÞgÝQÞžßdà¸áöâwâKàYÞ@ݵÜ=ÞqáhãâÒàÆâ½å÷æÃåÌã±âýâ–ã¨äÆå?æ#æ¢ååÝåšå|äùã|äcää3ä:åïåzååä\åýå–årãRáá-â â4â¨âããïâ àóÜIÜeݱÞóÞèÞgà…á«ßøÜÒÛþÛÐÛrÛ’ÛYÜ9ÝÞݶÞNÞ§ÜTÛdÛyÜ Þ¢ßòà…áàÇÞ<ÝšÜ܉Ü/ß±áÌâ“á&ànßßÓÞ6Þ½Þ~à¼â+äúäMåÂä÷âàßÛÜäÜà"äÖäðã äºä±ãžàðÞ­ßÿá2äæ“æìåCåMä ãâCã™åæÏålæôç¾èØæ\ãtâå+èÙèèé¹êüé˜æ²âá§áaåNé êé°çÒåZã*áxàQâ®äìäBäÇäkçýè`åß_Ýžßâãdä"æ¥ç¡çÍåBäUâ7à-àïábäÝåNææ·äâàáßbáZã äSäQåèåååDå‚ädä÷ä#åƒäEäšå²çžç$æÛ倿CæUåæmé¬ì¶ìOêWçÃã¬âiåièKêgê„èÉæ±æÁæIåþãåâç¾é0ê‚êÌéÒçJææòæŠèbé éŠè7épëLíÏì7ë»éØèÇéÐë<íÛíPî5îÊìoë¯ëóìsíáípïÐðôðïîìpìªíXï ð¶ðjñèð)ï±íïìí¢îdðAð$ðËñ&ôôjòSñ¯òõ»ô`ñ@ð:ó·ööWôó"ô7ó ðMîãî¾ðœò=ó]òvñòðÝïôîûîïÿîïï¹ïñ!óŽóÐðUíìRíóî6ð^ð‰ïQî·íóíáíí…ë¡ê¨ë”ì íˆí‘í0ìèéÖéEê8êøêXìûì£ì¬ìEìÖë£ê–çæTévïçòÂñîï¶î~í+ë@é`éŸêhíÉïÀïáî î…ìê•élé…êÎë·ë‰êUê˜ëìäêÞèeæDå å>æÊæöäÿââ*â®á á"âqäåYãSáyàà¨ÞmÜÝá—åÓæVå¶â¸à›ß'ßðßÈá>ãÝãÎä:æçAç˜ævåàä?åªæ‰è×èè[ççé êcéƒè‘èÙéšêg鹿åpæøçèoèðê0íÒë§èZå,ã'âåâæÖé~ë8ê½çàæ çÅæ|äùáÒá!äÞèhìNìÕéÁæ‘ä`äääåeæyèˆéƒé+è©ærä©á’àháŠãQå\å¨ãáˆàá?á>à¿ß"áñãåTã'á6à^àGàaßÞçßüâ»åâæoçÿæsäâ¾àÛàLãéåôç«è¤èæè$èåÍâ£â°åèéí¡í±ëüèQçYç‰èÉè˜çcç©è6ê&ëiéråñâªâ§ãÐä)åŒäŸã\ã8ã-âLà$ßSßîà€â%ããÊâânàÍßá˜âLäåfåuæÍæ”åãIâ„ãÍæóéÅëzëêjêÜéœèíç`è/éë•íiîîíYì“ê#ê”ê ëÙëíŸígíOìöëì«ë“ëoë™ë'ì{ì…ì ìeëîêƒê;ëÚëÄìëí‚î6îäì†ëZê€êæëõìAíxí3í¯ì`ë$ê‰êëµêë³ì¡î9ð¨ï’í8ì¡ìFî—ï×ð‰ññÉï î5í…íºí®í¦î”ðåòùóòïSîŸïpñÓñkòéô÷óö ôNò¡ôŒ÷÷·ó±òõ›÷Tø¶øùsøôöoôÞó§õJ÷Ÿ÷ø ùù5ø÷öeõcõ÷ƒø†øÀø­ùýúüú§ú6úþø^÷éõƒöjùëû­ü¬ûùû&ý6ü"ùïöYøûÈü‚ý7þÞþ;þü(ú½úàû9ûaú/ú@úgûÎý5ÿyþüÉùùÞøÙù¥ûòüÇý;þôý…üˆû’ûÂûÂüLþ€ÿ!ÂÿŸýü#þx¹â˜ÿ°ÿƒS¢~ÚSŸt[uÿaŠUó„  &, ñ ç F  ² æ E • ¯ ] L Ø Q ëó ï !‰Tqžq " az´¸'¸©ü®gH€­EÜjv×1Vn3F¿Ë{z_Ô†Æßò·ÎªC²Ç—«Ül´Ó.[»F¥"ôûíýä}–CÅv— þñâ¤wŽ@ãer ʦ⥲dá´5ñ1,´BÒÉÆW…pò—c&;Õ¶¯ã‡¸¡ëÓ ‰?BÍÉ2ñ cU„sGðÕÞÎ 5CÏ,°_)VìYƒàôE$š'áù~!öñ˜GV“0‰ûÔ„âÙ·±ª§:¶”ØOB»NØÓ´¦øÚËŧbJ¤¯{çÿŒŒî¡2ñ»y.Ñcã ‰¢™å¹²é ]Ù•ë¢j ã´2ÇÅÊîÐÝ(g¸ºÊŒjêZSø‚`¨·Þ¤Í¶ó¦æ[½…K<ÊÃu|/÷ÜP‰Ó‘Èd€Únò‚&aé¼Km#? 2 ‰ Z ñ  ´ z  Ú ³ £ ö `™8öxŽa)Bâûÿ5ŠSl[É‘’Ž Îh¥ »Ä>ÂA|'›R‘ _1yU{”–¾e7ØâYÉ®jCOÔýê¹v"õðosEe:ïihň¾‰,”ò-2«ès½¿žÄ¼¼âÛF…M£àK™GR¥­Ã¼ÌZàåÂLlìÔ/ò±Ï4÷‘$_¤ˆuC5ª÷íØm;޼§pšl¼ž\-uÔ%.¢ãOÃMòi•¦~5#MðwŽnrli×ezÚ—Í ¢5ÈU37h–¬wͶ (˜Âň% S ` â w  B | I ' d  * †8º ¢ Æ Ì ,i@¼P· × ¿ w ) Ý í $ » q ; } ‹ H ¶ ±»] i {ÔßÖ /@Ú¢Uÿ„ÿ<8L2ÿ˜ÿ YþBý4þ†þÒýÄýýzüêüðýÁþÿþ¡þ§þXT@ÿuLÙÏl´‹/§°Œó•B&ç•æÑvHz*þþý‹âšÚbÄ2[éÞÿþp¼Åæ3/ì.À‡Ó0  ÖX=^ã4ˆt–!וè¤ÿEý^üPýýµúHùùbù/ù†ú´üðýèýüqúùù?úÜûªýñþ=‰Âÿ>ÿŠþlþÆÿþØG|ÑÒ-ÄÎ } ` µ ²Ö<³iùa µf°!uqw>ÿoÿØÅ»´*€ýèúSù„úgý9ÿ£ÿ–ÿ·o‰þüéûÆýOÿCaU}ÿØþÉý ü¿úìúüþ ö‰ÃþÌüüþüäÿÅÿ‘Ûo¬@ä¤gy°¨ÿ–Å1}‹q]nÁÿFþ ýàþ¬Áþ]üûüûZþ,ÿjýÀúšù´øBøÁø‘øUø¶øùýøø2öô’òõñ®ò,ô,ö¦÷@÷åõ±ó òÇñIò8óaóßó|ôTôvôÂô¸óþñöðÏðaòAô%õïôvôôó…ñäïïìðôÑõõqówòòòÄñ`ñ‘ñóõ©öáõšóbñ ñwññð×ïzðèñ_ò~ñð+îÏìRì8ë#êÉêëë¬ë¼êëééèAè'èƒçhæ æÚæŠçÖææ¡åDåå€äóãÐãåRæÏåIäœâ´á5ânãóãä–ãôã+äšãÎâRâ>âšáïàTá0ã¼å‘æpålãâ·á8â·âùâ-äØåRææcæyåWää¥äYåäæpèué ê±éÔçîå*æÔçÁè¨é¤êŸë=ì’ë<éçç#è~éìéŽê ì^ìûêé©çvç™èRé3èlç2èsé?êzé²çæ™å÷åç‡èÄèRèWçåæäæ–å)ä†ä'æÉçêèUéè¦æ,åeåç|é€éìèNé¡é+é èræ3åÙä‚ådæ—æ&çêçè¿çUçóå4äÕãóäwækè:éPèÿæ¨æRæ<ææ·ågæ—æEæ5æ¸æ®çLèè"ç6æ»åJæÃæîæaçSè°é‰êë¯ëOìºë¢è´æâçüé4ë ë†ëŽêUêúê•êÑèZçææÊçOé÷éZêjëRìÏìnì$ì¬ë²êwêÖêRìcíïíïáîÝí°ì9ìöìøíÎîï:ïRï·ïñ•òóóÑó•ôžôÝó2ó;ô2õfõãõrö«öÔö ÷ö”ôÕô¹öi÷©öÎôëótõˆö ÷¯÷Óø8ùä÷¬öEöaö³õúóÇó9õŒ÷+ùµø®ö·ôdôôYó*óeó~ófó@ô öÿ÷Â÷MõFó›ò/óáóõM÷ú€ûëú~ùª÷lö õ õ›ö5÷—øÒúüvûOúù´÷Û÷•ù9û-üJüýû+üRý>þ=ýÀú5úºûåü ý?ýŸû?ù÷_õÌôµõ$öõ6ó{ò«ò÷ñüðKðAðñAò½óJõö…ö"õ©óSó¸ó^óJó*ôõ ÷&÷$õ‚òñ–ñò0ó`óRò³ñˆò[óùòÍñäðÅð ñ³ñòÁñ7ñ“ðœïêî&ï7ð‡ðð2ðñ•ñ¤ðOîpíîÂïéïúïÌðèð>ðÓî3íí©îïïžïîî8ïEðÐð ðî¼ìzíËî<ïôîÎîÁíxìHìÇìíììÿêGê»ê—ëÔë¥ê±èÂæäœä}æZç=æbåå–ää½ãØã‡ãNâmáPâˆä9æIåUâïßËßyàêààáùâˆãã¬áµà ß‹Þ™ßÏáaã¶ãÚã8ä¿ä åÌääzäæ?çaç(çÿæ*çç;æåXäÅäÞäkäöäiåÀäùãtã¤âîâÊä åÆää¶ãÎãýãeã&âæáBã äýääåÛæœæ»äãúâžâÀâÌâ8äÜåTæêäãHáìßfàyâ]äŸå×å«å*åräxäºäìä7åæµæçWè„çuçtè[èçIåhä)åææ.çpæðåýäÇäíä‚ä²äÔäùããâ:àSà”ááûßÓß)àfà¼àIàßµÞuÞ¼ÞÍßæàžàBßRÞàÞÍßáß9à›à¹àJágá„ààßSàoàóßá˜âäâSáºß ß!ßšßß ÞtÝ¡Ý!Þ߃àÛàà™Þ£ÜPÜÓÝÌßfàààìà°áŒáNá@á³á–âÄâ â…âúášáDâ÷ãÍå¥çiè<è^çæ–å=æçÃçgè]èuçìç é8é÷èoç¡å‡ä»ä:å½åÆæ½ç*èëç­æcåöäeå%æEæçlèé–èîçpèõéëbê=è@ç­çé,ê êéNè²è4éáéüé®é%écèé êŽê!êôéíê ëBë’êÚêÞëäëBëØêÞêéêmêFê-ëvì‰ìûëLëê£èAè³è„éÔêbìtí³íQí4íîîýìÎëyëÓëVì©ícî$î«í€í³íáì,ëÀéêÃëµìøë4ëë€ëòê7ê/é‘èBè¼èPéžêÝë²ëØê:êŒêáëMí"íéëŒëõë±ì€í&îNî3îBî6îEîüí)íÓë›êìëñíNíwë[êàéûénê™ê©éè çsçgèÁélêèéê™êë[ê¹ééDé1êìëöìììÌëCê#édé\êëÔë¾ì#íHí-íMìúêêgëSìÒìsííÅìðë¤ëì!ìõê*ê˜êÿê˜êÝêë¶éèEætåšæNè5éé÷çÛæ¡æçDçvçEèþèÆé®êëëˆìëèÄè¨ëgîªï†ï;ï2ïïjî”íôí ðQòËó3ôØóÁó8óÉñËïÂîMïÎðÎñàñkññ3ò4òîð©î–í îŸîîîåîyî?íqì‰ìòì:í<í6ílì²ëÍëtëPê€éŽêÌì›î´ïïVî5îüîðñ/ñ•ðññDò•òfó×ôûô2ô[ò§ð†ðñXñüð+ò¸ôw÷Iø÷|õkôžôCõ­õèõ.ö÷„øïù|ú¼ù$÷3óañ’ò“õ;øFùýøyøŽø­ø‚ø‘÷pöíõÏõö ö÷¦ö|õkô~ôdõ¿õxõjõVõ¶õðõ;õoô±ôÖõŒ÷júHüæû­ùÅ÷÷Wø¹ù¸úÚü8þ þüþÞþšýËû?úùú|û ý.þ{þ`þ›ý‰ý‘ýVý´ýLþÎþöþƒÿQ=¢ÿþ‰þÿ;&± ¿}ü\¯2›=ŒÅ åþÕþ‚R[¶ªÜ…ÿ&ÿÌÿx…Ó¦öÿ}ÿþ´ýËýþLÿ¾ÿ*Üÿ¾ŸúþÏý-þñþ)خȸbÿÂý(ýëýïÿ©šédUÜÿŸþpþ#ÿ+TÞ¶ë&eîâ2>OΑ¢½öü/‚(‡lÍÿîÿˆ>ÇŒ;¿þgý~üTüÐüàýnþ/þAþôþ—ÿžÿ½þ~þ‚ÿrB¨% ¬&# lNøèf—jI“]Ä’ÅmÇ–.–…iÿŠ5ïÏŠü+ÌB8•r¢˜‡Ö÷Ýíùª->öû—"ŒÌ!-‡þ «  Ì yK_´Ãm ïd……pÃQµ8ѵÉÿ:ž¦(¸£å" T±Õiyo–Nu4‰ó« E FÓ$ÁcIJW©   x  tH$¥ÃM C”  W l ` ½ ó e C  Û„%‘b¬fvꌔ§Bw|1JšÌ FiçÞ3Ÿ|­Ø€¤KôI¶¤·  ' å=×!…D˵“öæp  ¥!4.)ôñ\E‰Æý<ñ§A»¬e ý › Ó  ( Y k¦á r V A Ž Æ Õ Ë C F 2 ó —£N¨*<è{˜ãÒ¥º¯>àôPõ¯ëDó}>OY˜„¥öVÜñ¼:x“x6Rt¸Ç6w‡µ=h_Èì¡6D7e Ô M µ   ` té"³ ® Z ù ›írÀ„—¸‹¦˜|W c‚„””£¶/BvÅÈÎOjqBAg*¹0ËMVÄÑ•‚]`Þ¹QÞ9v‡w” ; mÓ*–Ê}&D“Eðè?lÏP;ù³:| iŒÆ<üB7–˜L*Û÷êù(c_âÓ·xù  X ¼ ì } ¨ ù N ã ? ˜ S â “ ú ® µ ‚ ì  v  « N Ç : W Í ð }00'aPTLy\"­ø¶_ \ õ o Z ù ï Î u æ À ' Í R  ø&œ‚/âd‘«ŸjÙ««a颥@g#õ””<i×ÿÿùÿåÿ¢ÿ–þ£ýòüÝü2ýþÚýÎýXýCþ©þbþ ýfüñû…ü þºÿìÿÿgÿ1ÿnþþÑý•ýÏýÿÿèp~CQòÿ`m*V¥®HÛZôþîþ›ÿ;›ÿèý~ü2ü·üôüøüŽüxüÜüý¡üÖûRûûòü2þÖþÿþ=ÿ¾ÿÿÒþÿôÿÿ"]Ï´ÿÓƒ½-½Öó â‡]éM¥BBà®ez{¾?Žºh²NŠîþžýÅüýgþˆÿªÿ­ÿÿ:þ‘ü:ûãúÈûÅýÏÿ0¬ÏÇ¡'V¶ TCe“2 û j € : £ Î ª * I l  j , x  ñ  2 N ßL U ½ L  ! T # g ( v ¶´Ò ³ Ì d õ ò l E  Å  à † ê  1¡  Yhº; r  } “ æòo® K F ø ­ Ê ˜ “¤<® ¶ =?6¿  8 ¹ ò ¹ N ”  — ( b w S ) ` œ æ ¸ # m÷«7X±(n«V } LÅ¿&  " ¤ ³ × , ¿ t ½ X 4 “ Q ž ° q   E  t u p µ  w @Gèp š – „ – , h¼¹– Z j ¹ˆ©ÿ  ° x / [ § ô ( Ž v ) ë  š ¢(NÒG]\ðù§vG +,ëªùRm$*öšjv Ð º óécvnΑðcDnûìÓ¤ÎT#ÜÓ;êþµýòýdÿÿ¾æv‚/¢1†yðñ$d#!5ÅñT^Í ¤‚u+…:§G ñí´ûÍ[ . þðl k †¨cÜsêŠ ¸ÎË2~«—ötå_—a‚ôÌêØ; ! ¦ Þ è Y  ç z ì ;| « Ê D  e ½ ²Ï o à Šl…wÔ¶g-µ]‡Ç5©Éþ’;oúÅ @AÌ 2£•óô ¢ §@PLŽÁ„2U®èJŒOb뱌B††/#,€És$•jbú½¢‘÷€–+µõâ&»~ã®&à6ŽÜýÁ1<Ö?†BÊÇôÕ›´ÝìJ¾£zª‡åÞäPé.= ¦½ÔgÆE˜’sÞÚ àÙõô¯ ¬úxuzhü.¾:¡c¾hˆÅ®Œ…!¬q³RúPpÁ—ÔTU)‘ŒHœ}–è†ïyP{ljƒ0±vk“žÔÔØÐ»Í!¶Âl¦ s\U‰… O!d"®"ì!!£ ” z #!i"#°""«!!Ž ‹ T / ™ ù ê … ¬%’ ; ½NUÃöc Ô !¡!¼"q#ô#Å$Ô%Š&l&Ö%%%¤%Á&P(*¥*V*I)…(u({((´( )7*¾+k,å+0+*C)©)Õ)O)í(”(‚(¾(q(Ø'É'6(Ä(+)e)œ)À))Ô'–'d(ë(ç(u((()b))_(r''8'g(*V+,ä+#+¢*P*'*D*Š* +i+Ÿ+3,--:-+-Õ,c,,|,¤,v,²,;,Ó++¶+ž+d+'+ +–+N+­*{*ð*Ç+Ï+y+!+3+^+ ,-•-R-À,,ê+,",³,-..Î--(,ü*Ý)]))ö(Õ(Ó(m(ÿ'Ô'¢'1'þ%%õ$r%ú%#&”&È&£&9&©% %„%%â$ô$@%&s&Û%h%É$0$§#Á#d$¬$ $j#="6"ý""$ÿ$À%Ë%É$Õ#Ã#Ï$¸%¡&7''ß&È&d'N()‘)¹)­)')š(¬(¨(œ(Þ(Ì(C(È'¸'¢'‚'v'×&`&&&ý%9&='3(v(Q(_(ç''²&'ª'Ò'Æ' (L(G(Ì''Î&x&å%Q%L%ï%–&¯&!&<%‡$F$$µ$ð$ï$S%o%G%;%±$è#|#§#2$ª$:%.%Â$æ#b###…#ß#B$Ç$¬%«&©& &¼%±%&¿&–'d(¦)á*Ÿ+È+Ë+ä+‹+ú*è*›+…,Ý,u,¿+$+†*A*¢**+~+¶+´+u+*);)v)*7**²)ú(µ'&Â$à#Ô#$þ#$Ø#@#ð"ý"K##ó"†"_"#È#$â#B$³$É$.%%Ž%t%k%%$k$o$¹$±%ï& (Û()(&¶%˜%i&ž'.)o*#+e+÷*=*“))Ô(s)f*2+Æ+í+§+ð*j*¾)ˆ(¶''À&£&Ï% $<#T"”!Ê  Š—‡*sîD5û’Ule æ × f 4 ðãã§…ËBqù7Ñœ>JÛâ0 §0e‡SNŒjþ²Ç@‘@û5_ü™}«ÔB}G^9Åëë_¼uºõ]ÕHiáÂðµq›)ÉÕCÇzn$óšÒnÂ2”I5…t]Ú™”×3wËY]^-.î öµrd^ÂQ˜ä{x-«$›û>m´ ” ,  þ Ž·¢reÜTœm¥¥Và‚-òÝp^ƒ_h¼wXo`X–.9€~9­?šÊÛ#´¼ÞÇc¯ƒfR{ y3®§mbøêT±Ð4ÏÆõ””"höä,㘖¢Û»™ÓÕ®XO¹¢PŸ{V,ó*&@0£°\„®O£<>ãA±ŠÛZxšXî, ¡ “  t Ê ~ % O – ª ÀöR #W~*êH ±)—ÐÙŸ’† ¦#pL} Ë ’ › ; j k Z ~ o i › × Á 0 E S × Þ Î Ê ® ‚ . © ù ê ÷ ý Q°IڞȗéWàtSÏBx$ PVXtfÓhЄRå=q Ï W ô Ë — ó ñ Ç ‰ d N © ¢  Ÿ n ¾  ‡ + !  §YÆ%ï& ”óhi ¦ ¸ q ˜ œ  î Àü4›èW›%kÁŽð #>YPJe•n» ¥ º v # I Þ Ö J ¶ Á ã   Ö- ¬ û ­ ö N ÎQ.V¢  õ'   .   eN”) À R ì : # 3 Š Ï @  N ‡ ¾x¨ Ž × 9W!ñ  A¼ì›U/A[møôðyº ì æ † M , G l Ë ± ÐÇ”Àžœb ‘eåS±`¬åç€ñìĘ̂öÌH3粨ênÙ* Ë – Ö #  ¦ h 8geÉU+¬ÂZœò e ô ƒ R  ›  r l P¦â…ám“Ëø.[\±hì<ö€3ºú! _   H Á ú ¯ î ö ÷ A § ý È U à  V Ž í ò Ì · í â =Gò Ä 1Ó2_/F‚þfÞ@VŠ0l'tû@[ï&ïa¯á–   ÆOóMä½Ðfã*9+B!B c T 1 • æ Ð … i € ” 9 ½  ŽëõRÕgy|£…š*óàq4fÝÌ©§)4N³/I[v¯3¤ÇœJ&ÐèS("íÔä½{¥9Ø ² Ò uõƒ¾ å (  P å è *h­ÿ;}…íŸ*š½$ýÖjìdßÏ_¹žª¿:xjk>Kö}ÔBƒH0õ»ƒž9ƒa©_¬Ï>ö®ÈεÌßi»X*'en…Å­7Éì5âqyÜC[ G&Ô¡:Ò¤. 7 tæ Ì!6#u#—#(#m"z!å #!¼!L"¼" ##ó# $Å#`#u#n"B! !o!#†$m$È#5#"k!x `éã_ÎU©“œÝ¡é²Ö¬Z(z{›‰‘“@ब¢ÀN•—Ž'jnÆOsܳå:HÔž5ë ë]/\â0Žâ¶C4S_ÇJhºÈ8ûe#3Ý/žç–Øe…=Ë2)« „ Ä ‘  È Û L \ ˆ \ •à 0  Ùf ÞhìÈK>]“X & h»ÎPòý5 ƒ ç Ì È  ÷  Ç L - « 7 ¿ “ Ì ³  é 9 l  ò ¨ sÜ4,Í&›¸ºƒl©CJbU¢°'ŒqJ”ÑÔIîÇžh×8ÖDÙ±r|~H-LÓ©¯Ø›6®û¬ñ+ñ‰'>¨Œux¯>ÅÙý«bBÇÿ ûÎâY¼‹ÈUÕ‘û/=evöÇåë˜Ûµ&¡êi÷n·ŠÑÊUR^(’ i¹*–• „ ¤ ¡ â Í U J Š ' ì X p W G B Õ  Ð ” B ƒ ; ­ ã   ¾ °  « r o š DèhÄÒ=x™ 7 U ` Ÿ [ 4 V & 9 ä »ƒ… æ Ñ ^  » 2„×컢ȃ§‹ô±Gß4Æø¨‰"ª-³vSØO4Jhî³gyí¥-„ N D Œ ß ^ ‹ ô ( Õ @ ? ™  È '  F Ê g 2 P } … Ê  ‹  { y — ™ S “  v ‘ ã wpCØ ž Ð WŒ}Š ü É ’  û L Ä ã e B Í£¹Q$6]½vÐ’¹É‘³øP•ÜÕ;D•ÿÂÿúÿãÿ9Ug4õÿ“ÿeÿ‹ÿ™ÿ=½VØ®.ë)]·*5·_isI9o¼ÓKÔ³,r‡9ùQˆý‹w×mfq4íê_PÉÅY®ÿþÂý™ý°ýoý ý}üüüLüYü-ü üýûüVü¹üïüýóü¶üü´ü~ýÅþàÿ>Ùÿ‰þ|ýDýóülýóý‚þ£þPþõý©ýýü"ûû‡ûüôûÖû+ü(ü%ü²ûPûeûÆûüëûÖûü™üýsýþ þfÿ¥ÿwÿnÿsÿgÿÿÊC¢‘²öçÿ4ÿDÿêÿþ¥yHýµ\ÿðþçþ2ÿ,ÿÓþõýÕýhþ$ÿÿAþý‘ý»ýrýUýuýàýþþþiþÅþÅþŸþ“þ²þ=ÿôÿX².$ÕÑ»WÓ¥TÈÜ«YxЬg&^Q–l}éà¯á¦}¾S.ýƒi=GœŸ4×ç>ÑÉ˦ƞ¢¥X  .=Æ@êÐåÍÙôc/vÿÿÅþÝþiÿ8*你ȆBÛpS?)=5õz=ôÿfÿ÷þ“þ‰þ¼þ¾þþ~ýHýHýÕüÕûDúùvøeøBøå÷Ë÷’÷~÷e÷h÷;÷÷Ðö ö÷Ð÷_ø”øµøzøÿ÷i÷ööŒösö¸öÚö)÷±÷hø/ùKù8ù‰ùõù†ú•úYúOúû¢û1üêü<ý}ýBýÀüÄü3ý´ý‘ý¥ýäýïýþ0þþêý´ý]ýXý†ýœý¼ý þuþ­þ»þÿÿòþÊþ ÿŠÿôÿ8üÿžÿeÿ9ÿeÿ‹ÿ`ÿ/ÿäþÒþJþ°ý¶ý)þÀþ8ÿÁÿÚÿÿÿñÿtÿÿ\ÿFrq:¾lèÿ&ÿÄþ\þþãý¤ý ývý.ý ýÂü`üäû›û ûüWüüÁü‚üüªüKýlþlÿºÿªÿíÿ9vã’3ÊÜÍ|+M~ÀÌÔíÔá°T,›T9 xQÿ;þý üøúú,ùó÷i÷Éööpö ö‡õ¸ô ôPóÍòvòòóÜó}ôÈôÐôuôHô5ôVôôô›ôsôDôZôŸô)õ„õÈõ öAöTöÙõpõõàôçô÷ôüôÞôRô¹óvó6ó½òCòŸñ$ñÑð”ð`ððoð†ï'îí…ìÅìøìíŠíÍíçíÉí€í]íí¤ì ì8í;îïªï}ïMï&ïïïî^î4îyî+ïôïÒðHñIñDñ ñ ñ‰ñcò3ó³óôô¦ó*óó^ó•óôjô™ô}ôEôÇóÍòÞññ—ð¬ðôð ñððÃïï ï…îî îSî ï6ð[ñVò„òò½ñòÜòqóñó ô!ôaô»ôØôpôDô ô×óÇó¼óMóƒòæñiññ¿ð¤ð7ð‚ïªîÆí3íVí3í^ìuëÎê–ê¡êê¸ê×êñêë¹ê»ê ëxëËë¿ëÏë8ìqì[ì:ì]ìõì”í î}î ï…ï&ð ñ’ñò_òoò›ò óYóNótó†óÕófôôSôôéó¢ó‹óÙóBôÐô®ôoôô¥óó]òŸñ ñ'ðfï±î`î4îØíÇí·í0íqì¦ëLëKëëæëëXëëœê‰êëìKì=ìÜëµë¾ëñëÊë©ëìÅìí`íŽííì%ìãëÑëáë6ì†ìøìæíŽî¯îFî×ííàìUíRî#ïMïyï¾ïöï±ïÒîíísíÇínîïÍïð ðÎï‡ïï¾ï ð@ððÎï¡ï½ï~ï[ïïÏîqïð¬ðÿð/ñ0ñ&ñ^ññµñ òÆòzóòóöó¤óPó¸ò(ò»ñ‰ñ¤ñïñAò‘ònòòŒñXñNñHñAñ ñÕðüðjñÛñò.òkòò…ò`òåñmñ,ñóðàðñrñsññ‹ðÒï=ïáî·îÔîøîSïÑïaðªð¤ðuð ðYï€îhî­îåî˜îÓííRìðë{ëËêê ê•é]é¼è÷ç/ç˜æ æ æŽæ;ç­çLçšæíåªå¬åsåPåkåÍåDæææ†çøçêçòç/è8è±èléêäê„ë0ìŒì§ìòìüìíWíŽí¨ííÅíî¢îïsïóï}ðñXñ~ñbñXñsñ¦ñÃñlñÎð#ðËï•ï(ïÅîÚíšìTë2êgéíè€èè¡ç_ç3ç;ç™ç‰çpçìçRè€è èÑè éœéNêøêIë@ëmë¯ë¼ë¡ë2ëõêÿê=ëkëÊëCìœììì÷ì¬ìì®ëGëéêçêëSëÁë³ëoëÃê1êÊé}é:é~éDêëHëòê.ëDëPìVíaí7íòì!íií íîjîÎî.ïoïºï ð,ðéïDï>ïªï.ðãð•ñuòPóÏóÛó²ó”óˆóó”óô¢ô#õcõõô;ójò‚ñðððNðCð7ð0ðbð\ð=ððð@ðnðFðæïåïôïHð“ðèðøðñ”ñò{òó_óÈóùóíóQôáô õ”õûõ=ööböÊö¬ö·öÐöÍöföóõÄõöRö’önö`ö’öÞöL÷½÷ø÷KøÎøeùÔùÊùú€úû¨û³ûkûwûqû^ûXûiû&ûóúùúûüúûûûûûqû½ûü8üüVü¼ü$ýäü¬ü{üdü üøûhûÌúúnú1úúúøù,úyúBúÛùfùùÆøpø-øøä÷™÷ ÷Žö9ööìõžõLõ1õöô‚ô~ô…ôNô.ô³óWóDókóÀóô*ô3ô†ô:õªõòõ5öWölöiö‡öwöÄöV÷ü÷‹øÒøù$ùIùpùuù\ùYù‡ùšù‘ùsù]ùùMøZ÷ƒöàõHõ®ôôdôVôôÚóGóÀò;ò°ñõððôï`ïØî{î1î¾í7í®ììªëEëë ëVë¡ë&ìãìŽíAîàî÷îï0ï€ïÞïðUð‡ð«ð’ððÛï–ïŒïÝïâïäïƒïþî€îîÁíyíEí=í,íííàìbìëëÇê¥êŠê{êdêùé¹é¢é¢é•é\éêè7èºç‹ç¤çÏçè:èèèùçè‚èQé{éQéþèxèòçsçÆç½èUé#éêè±èèèTè´çxçç±çíçèèôçþçèèÐçUçœææ{æ2çÚçeèìèBékéžéêMêqê–êÉê.ë†ëçë8ìŒìÚìXíní?íÇìì˜ëGë^ëõë¨ì³ì_ìì¤ë{ë`ë[ëYëNë&ë±ê1êðêië~ëë‚ë‚ë€ëtëÉë"ìaìJì"ìqìæìQí²íî9îNî:îäí¡í“í°í î/î,îîøíáívíí[íðíYîDî@îùíÔí¶íGíÖìmì·ìIí±íÓí@íüì­ìrìlìbììÊì=í¯íÜíRî¾îïïï7ï—ï­ïïÛï~ðñEñcñ{ñ´ñòIòYò@òùñŠñ+ñsðPð“ðñžñÏñJñ¤ðêïeï6ïZï‘ïÓï+ð‡ðªðŠð;ðÈïBï¥î_îQîyîÍîñî0ï1ïïï ïï+ï½ïOð½ðéðTñŸñ½ñªñ¯ñòòçñ òòïñ¶ñVññRñ½ñò<òLò%òòGò°òÜòòò×òÅò²òÐòãòÅòÇò|ò7òòòåñÃñWò¡òÛòêò…ò<òìñÅñ°ñañâð¡ðkðíï”ï’ïqïUï:ïÆîNîÀí„í°íBî»îòîÒîiîôí¢í²íî¤îIï‘ï†ïTïQï]ï_ïtïËïððÊïšïï‡î+îÕífíðì‚ìKìbì¸ì(í–íÄí©í!íìTì@ìcìªìäì³ì)ì‘ë;ë)ëOë>ëMëwëÊëHì˜ìyìgìHììÝëoëôê„ê)ê£ééè•èè£çç_æ.ææóåˆåå¤äPääcãìâ†âMâ[â+â â­á.á¨àKà0ààà à¦ßt߯ßDàÊàNá©á?âãäËä]åœå$æùæ¾ç§èqéÝéhêIëKì7í„í¢íÃíöíUîµîïRï/ïïî¦î îÒíåíåí®í”íÄì ìèë¦ëëlëñêmê êvé8éŒélê ëûê¹ê}êêŒêÒê9ë3ëNëºëáëùëõëì(ì`ì¯ìôìKíí®íºí¨íãííåìùìSíî[î·îµîQïžï†ïˆï™ïùïWð¨ð½ðÃð¡ðuðiððð¯ïZïï0ïRï¿ï–ïèï¸ðÆð×ðÆðÆð²ðàðYñÁñ2òEòò¡ñvñhñ—ñâñññ¼ñµñÃñšñdñ)ññÉðºðËð¨ð‘ðdððuïæîîXî3îöí«íQí3íaíží³íµí¦íoííïì÷ìûì÷ìÒìÏìÄìæì3í@ííÖìáìÚìíjí•íÈíÓíî<î€îwîbî„îvîuî’îXîîqíAí†íáíáí›ííŸì•ìì\ì+ìÉë•ë‹ë‘ëfë8ë”êÐéÿèKè·çççsçQç>ççÏææMåËä‘äŒä¶äÕäFå¼åíåîå²å§åŠåfå$å:åiå’åÚåæøåÉåìå`æ¦æræ(æáåææ4æ.æóå¾å©å åšååsåå—äZävä£ä¦ä´ä¢äuä\äZäIä1äFä†äèä)ååå3å¹å]æçŠçÝçûç-èèôçèJè³èéséNêë±ë4ì9ì$ìììïë#ìxìäì+ííàì¦ìVì!ìŠëÐêUê+ê(êêÙéqééèGèuç¤ææÌå‰åxåkåkåSå7ååõä&å9å©åæ¢æAç†ç”ççáç:è èéÒéêžëtì%íÓíVîÑînï\ð‰ñ¨ò®óªôaõäõlö§öpöHöö+öSö›öÀöÅö±öšö>ö‡õÜôZô ô÷óÅó²ó©óKóôò¬òLòòÕñ~ñ9ñ3ñ]ñ“ñ¨ñ¬ñ™ñ½ñ/òóéóõöæöŒ÷"ø¥øù‡ùÊùú<ú“úÑúûûEû[ûaû¾ûÝûüü‘üýŠýÍýàýëý-þkþÈþúþ ÿÿ5ÿ|ÿ¸ÿ¹c£V¾$‡å:|³ú+ƒÅîÔt“Õæó¸^U[¥òàs*4VdpŽ™’‘½ÂÂÂÛ&¸.ׇG#.I p¼ú?k¦ècÎ+–ÙùåÆíý Á >  ¸ ê  Y K ˆ U q ) # F V 5  Õ ª u h : 6 0 ;  ÉmØsÌ€/ÔU¢—@"Ihxw§#”(üŇI ü « 5 ß   ˜ <ËAÐhè ï*13¿[ù‰¹R½Xâ ¡ A Ý ‚ K   Ø ³ X ô  K H N ` ’ Ç  F k Ô ) N Œ È E ë ª-pÊH­,Ììü,%+9P4÷ÕǸkÊ>¤ÃÂÃ;(&"ò š / Ú s H  i ¤ ö Þ Ë Ï Ö : Ä /…ª~޹òýîm¶¢¼øM¶cžy;.(Cl„‚9ìZôðíÅ­„FZYeh{…d^`l³Ö4O¼øIw–û7‹QNð®{á\ÒC‚Ÿš¡™^;ç’0Ú}“,QÑ)``A'ò+[´ï#'0=n®ž¦)†“fõEšAFФµƒZÄ…‹´ëQâ”I‚èE¸8Óh Án¯0QnuXvlM4Èž¤qE4ç¤^»ocO2܈K6"ü­H:H¯Ÿy§âP1 ._¾w×é¿éìê6X?êøãÇÀgËÙ³„Hú (G”ŽsF ˜¹/¸³Ž* ìÔµ®kì–/Úó%0zÒ)3?t†šÆúÿ,>å¯a5étü}?Ówè g ú  _ ö ¿ µ Í ß Û œ º + š Ï  .  !   ï Ý ¡ y ^ -    6 J G . ^ ±  ] ¦ à 2 ‰ å Fj£tŸÉ÷,T@Ϩ‘Œ—›‰”slM7ý  V£ÑÆÒN­ä0­"i¶^rœÍ_o[ ´œ¨Ÿ¢…cÕš‹T ´2ÔDÞ] ¾ ¥ m V ó ÿ " \ ˜ [Ýqø_Ý;ÌyF‹ëYˆ„ˆËŸ"}©È–~bZ%ÀtÜ“Xœ<Í€4è‹€aiL4òÀœ¥Þ(\ª0fB2"ùË«Q/ ¡]ó캮¶¾Âäù1ôû༛€u“^ouPЄPÇsï ‘ 9 û ´ | E / ! 5 t ” ¶ ý  0 R u ´ ò <nql@í  ¤ K 4 X É  | Î ó '.é ó õ Ô © ¾ Ð ó Æ   † C     ë Ý ¨ ‡ ~ „ · ü   Ö Ð Ã È Õ é ó ÿ Õ ° k e þ ß ¢ « Œ ” Ë ç " ‚ Ø - c ¡ IHK6*å Ì … > ï « Y  ¯ ] Õ ¢ ` ü  & 4 † Ó @ q u Z Y ] A e ­ È  + Y f K N Y i K  à « k  ä ‰ ?  á<ûÙõöJo—R2 êÔ÷ýá¼4Èz œË[؃ œ=½G§jCNjTlÑÿ…ÿDÿÿ§þNþáý‹ýAýëü®üaüüÃûxû*ûÆúúNúòù¨ùcù(ùLù*ùAù…ù™ùÒùú<údúŠú¯ú’úŠúÚú&ûsûœûÄûßûãûÛû±ûŸûhû1ûûéúêúûüúÝú›úFúú¿ù†ù\ùRùLù|ùÎù úúúú%úõùµù—ùŠù—ùùùùòù úúÕù©ùsùBù0ù ùöøÇøÙø¡ø,ø¼÷"÷§ö$ö—õ õˆôéóYóºò0ò£ñWñâðGðØïï&ïïëî”îŠî î°íRí í›ìUìCìsì·ìöìïìúìáì¿ì«ì í{íàíbîÓîeïµïðXð„ð½ðÉðñ¯ñIò óÛó=ôŒô×ô@õ—õëõXö•öãö ÷F÷*÷Çö…ö/öàõrõõ•ôôdócò‹ñrðfïeî¤í!íííQíÎíîDîKî4îîûí î–îïXïVïBïbï;ïï¦îXîîîíîTîœî°îÕîìîï÷îÄî©î™î’îÖîóîøîØî¶î³îŽîlîsî€î†î¬î¿îïîòîîîèîöîÝîÖîûîï?ïRïkïXïTïIïKïNïHï?ï2ï\ï•ï¬ï®ï‚ï]ï4ï ïï ï;ïiï›ïµïáïCðEðVð[ðJð^ðcðbðnðZðKð ðìïèï¦ïï“ïÆïÿïjðÖð<ñ—ñõñìñçñžñBñîðûðÕðŸðŠðNðïï±ïuïïúîöî+ïKï¢ïÛïÝïØï†ï/ïþî¯înîî±í^í(íòìÙìÔìÎì§ìŠì”ìØìí€íëíZîŒî«î¸îÀîëîóî!ï@ïiïkï{ï¹ï×ïÌïÌï˜ïŽïrï'ïñîîzî{î{îbîTîHî“îïïìï5ðuðÍð-ñqñ›ñ“ñyñ@ññÑð¬ðcðð—ïï¥îî“íí ì\ì ìýëçëëë÷ëìðëëë½ë~ëzëPëkëxëë²ëèëì9ìuìÓì4í íîŽîïmïýï‹ðáðÿðìððð1ñnñ¦ñÿñòiòÑòóhó¯ó1ô_ôÀôùô!õõøô·ôOô$ôºóLó¿òòfñëðEð×ïfï×î‹î%îëíÿíŸí‡í6í,ílíŸíÜíîeî´îèî6ïï¥ïÀïðHðŠðÕð ññ[ñ›ñµñÉñ òDòªòöòoóÍóJôoô‹ô–ô>ô+ôüóßóÌó¤ó7ó²ò ò^ñ±ððtïï»îîˆî„î³îÆîøîEï ïãïð[ðð°ðÊðãðÍðÓðèðîðññAñ²ñ.òŠò óaó¶óôHô‰ôÊôÿôEõ~õ—õÏõØõüõùõùõöö,ö4ö=ö<ö+öö öãõ¤õ†õAõõ¾ôÚô¸óÊòÕòÐòó=ó”óèóJô„ôÊôÌôôÌôÍôÐôåôõôüôBõuõ­õÕõñõ#ö"ö/ö/ö5öEö(ö%öö«õvõfõõñô¯ôÎôæõ6ö$öö öö6öEöRöGöOöDö8ö;ö%ööö&öNöSö]ö9öEöbö{öŠö¹öæöùö4÷M÷<÷3÷%÷÷èöÅö•ögö(ö-öùõ´õsõõÚô¦ôsôAôIô=ô!ôôÕó¬ó“ópóyóeó ó¾ò~ònòCòÿñ›ñXññàð‘ðbðuðjðXðzð…ð—ð°ðïðñMññÄñØñ ò7òRòOòhòQò`ò‡ò‘òàòûò*óóóÞò°ò‹òfò\òLò*òäñ»ñˆñ5ñ ñ–ðHð1ð ðÆïKïãî•î'îãííhíí»ìPì÷ë”ëgë+ë³ê5êûéªéLéáèmèÝç?ç´æNæÙåLåçä‡ääÅãfãUããã0ãYããˆã±ãÞã%ä†äÕä8å•åçåGæ½æçDçHç{ç ç¤ç”çŽçwçuçUçXçHçúææUææºåˆåNåWåƒå~å’å¦åéå%æcæÃæÕæç+çBçyç§çðç-èè1è@ègèŽè‹è™èÀè·è¶èèèïè éCéréµéêVê›êÒêðêë%ëSëGë~ë±ë ìGì€ì•ìµìÁì­ìtì/ìÕë€ëjë@ë9ëEë1ëë×êšê`êêäéééê5ê€ê–êƒêOê6êêê ê#êõéêïéäéöéèéÒéêGêIêqêñê{ëûëaìŸìÎìðì%íSíšíîšîáîUï~ïžïàï÷ï ð-ðYðwð¥ð®ð½ð»ð¶ð˜ð‡ð“ð…ðkðNðEð8ððþïèïÏï–ï=ïùîÁî¡î€îdî!îñí¾í`ííËì°ìbììÔëŸëBëôê´êaê*êêêêLêZêtêŠêœêÕêëëëMëžë¦ëìžìí…íî>îŒîßîïDïYïœï¦ï·ï½ï·ï ïŽï|ïbïyïˆïšïÜïðIðyð¼ððð,ñuñòeòúòóëó8ôŒôèôõUõRõõtõUõRõõõéô•ôhôøóØóíóôDôƒôµôýô,õNõ[õ”õ·õ¸õÓõëõ+öªö3÷’÷Ö÷é÷ø&øøøø:øYø¢øÙø@ù—ùÙù8úÃúBûïûsüþüGý·ýÀýüý/þ:þEþþþþ÷ýÙý‘ý)ýÇüXüçû‰û@ûØú•úKú.ú%ú%úú$ú:ú8ú$ú<úOúXú]ú‡úÎúùúÜúÖú ú~úzúQúGú^ú™úÒú_ûùû€üý—ýøýWþœþÝþÿfÿÂÿ/²Pè†vï;¤ä/Y<1è­z[IFxn[T>ìÆÉõ ðËǪÃê .?WgiJÔ«dŽ‘¸å>Ro‹£Ú jÐzÌ1ˆ«?n‘LÂcà†ÅgË‰Ž—Ä;‹þcì}Р罈M#õÙæý+*9ý¡5Ú$š8¯¥‘“ŠdÑ RrbDK ¬8Ñ“sBDmµúF}¨®º{l Æ€´7ÕWÜÿUÿöþ†þ?þ/þþ'þ;þfþxþˆþ´þÁþÀþéþåþ ÿÿÌþ˜þIþÎý]ýæücüü¹ûŠû†ûnûMû_ûXû\ûvû½ûü“ü:ýõý¾þ ÿm&·ô$©ä%e½ñ0^†št/Ì‚E'çãü7UD"óÚµ Ž‡wœœšk ªHÁt?üÿF{Œu\=ýÿ¿ÿÿSÿ<ÿÿÜþ²þžþrþŠþ¦þšþ·þÄþ»þÀþÌþ÷þÿ>ÿWÿŸÿÀÿûÿ/\‘Î0šóO Öùöü«‰W-üìùû'Ie‡Áç3k©¾¶‘M#óÒÖÀ½´º¥|i4ç¼’hbSfhpˆÔ— †ñH5+Ó‚ý3É^œ[áÿ©ÿ†ÿ‹ÿkÿoÿgÿ‡ÿ±ÿÖÿ g« …÷†Òð)S“¿œª=Z††˜È.n×+t—¤²\à‚f/õæ±ßöÚ$SwkDRC üÍ5ÀlÌ–f$%$#8wÇ~¿`xƒ}TAíºv/÷ĸ{1! Z’Õþ;?:æ»tO µG¯ÿ=ÿçþnþêý”ý/ýŸü7üèûÊûû…ûDûöúkúÔù>ù‚øø‚÷÷¯öö¢õGõÝônôLôBô\ôzôtôômômô6ô0ôgôzô…ô½ôÀôÊôÏô§ôaôôÒó¼óëóôyôºôîôCõiõiõ^õkõ•õØõö3öcöµöøö7÷/÷,÷÷æööö½õQõêôxôôšó=óûò¨òdò5òòò4òxò¢ò°òÌòÊòÈòÏòÃòåò-ó]óó™óªóÏóÓóôôHô•ôßô5õõÊõö ö:ö‰öÑö3÷ˆ÷Û÷øRø‰ø¿øÑøÒø¤ørø'øÛ÷‡÷<÷%÷ØöµöjöâõfõÜôzôô“óUóóêò«òròMòdòqòƒò¦òÑòþò0ó3óXóWóóóótóŽóÏóô:ôJôUôJôCôTôyôrô­ôåôõ6õqõ±õßõÆõôõÏõ¨õŸõÞõö\ö®öøöC÷¢÷øcøÁøSùÜùFú½úûqûºûçûéûöûÐûûSû(ûôúÌú„ú&úÑùfùíø€ø÷÷¨÷Y÷%÷÷ÖöŸö©öxö-öåõÉõõõöö8öHöPöEö#öþõ¹õdõøôËôxô4ôÜónó óŠòò¬ñNññ÷ðñkñÑñ òqòÆòõòDó£óùóRôÅô<õ¤õöuöÞö;÷¦÷&øÒøFù²ùJúŽúÃú÷úû,û!û,ûûãú¡úŒúPú'úõù¨ù“ùtù ù¡ø,øÖ÷{÷ ÷âö³öQöößõ—õKõôô¶ôeô<ôô¯óVóÙòoò ò¼ñiññÉðvð6ðððûïÛïÿïTðð ñŠñòvòóyóÝó5ôTôˆô[ô7ôþóÕó—ó>óôòò*òÐñeñ ñÂðGð§ïï§îî‰íí·ì_ì2ììýëâëÒëÀë‚ëjë?ë+ë ë2ëPëdë=ë ëÅêkêê©éXé.é é&é3é?é:é(éé!é:éFé…éºéÓéê>ê†êÆêóêFë‡ëðë&ì’ìãìí0íí9íEíPíí¬íÚíúíîþíîúíÚíÊíyí*íêìëìÊì™ìYìçëxëÅê[êêlééœèè£ç6çÙæ™æCæ)æ×å¨åyåUåQå*ååëäÔä­ävä-ä äŸãEãÑâzâ÷á~áèàkàÏßhßbß ßßÒÞ¦Þ|Þ5Þ'ÞÞÞ*Þ+ÞÞ'ÞaÞºÞÜÞ÷ÞÿÞ6ß6ß4ßß0ß"ßßãÞ¦ÞqÞ>Þ:Þ5ÞcÞŸÞ߉ßôßOà¬àÙàá)ááHáTává®áÒáúáâââââ\â°âãnãåãªä)åÅåpæàæcç©çõçèèJè`èÃè…è*è¿çç‹ç•ç¯çÃçÅç½çµçwçeççìæºævæJæ æÈånåå¥ä;äöã”ã…ã²ãÎãäTärä¡äíäBåˆåÔåFælæÌæþæ#çGçcç“çªçâç,è`è£èºèÒèäèùèé é,é ééôèûè(éLé[éRéeéAéééÖèÂèˆèè”çç±æxæeæ æÎåˆå åÈäŒä]ä)äää/ääøãûãä3ärääÊäþäåNåiåwåbålåÁå&æyæãæ(çgçÂçèGèVèè…èžè“èèyè4èè¼ç/çææ‘å5åØärä-äàã’ãŠãnã|ã¢ã½ãøãäNäƒä•äšäÈäàäØäÙäÀä¯ä†äiäeää½ãlã:ãZãKãSã>ãmã¨ãíãUä åÎ哿YçDèóèuéúé‹êÌêënëmëVëOëúêgêÛéMéØèdè-è@èGèqè®è;é…éÀéêeêÄêëaë·ë ì/ìHìfìSìLì@ììíëåëµë¶ë°ëëvëëÑêCêêµé®éXé éòèÙè¾è±è·è«èèkèjè\èƒè¦è™èŠèaè3èççÂçsç(çáæŒæ0æÆåLåªä"äªãCãÉârââÌá¦á‡á`á`áoáá¦áßáWâ*ãöãéä®åYæçMç¡çúçJè®èéfé¼éäéüéëé³é é†éhéoéUé#éóèÔèè9è»ç çNæ åGåôä¶ä´äÕäå?ååçå.æˆæ ç¯çFèÓèPéØéNêêÜê7ë©ë+ì‘ìíœí8î­î@ïÄï'ðSð“ð§ð¿ðÖðÖðÔð«ð£ðaðRðAð%ðCðBðQðzð¥ðïð2ñZñqñ½ñ#òròÆòÿò"ó'ó'óýòÊò¼òvò0òÕñ€ñañJñ5ññÜð“ðˆð¦ð­ð¼ð°ð¸ðªð˜ð„ðzðIð7ðOðKð@ð;ðð»ïjïóî}îî‹íóìwìóëzëéêiêâééé£è/èŸç%ç±æ"æ¨å&å®äcäõã³ãšãgãNãMã8ã#ã*ãããWãƒã–ãŸã¿ã´ã¨ãŸã¿ãëã'äväàäAå‘åìåõå"æ-æææûåöåßåËå©åˆå]åXå2ååå å"åLålå™å åÆåãåæ(æGææ€æ„æ«æÐæ×æÁæ‘æ>æ;æ3ægæpæŒæ_ægæQæ-æ2æ"ææ7æbæræ¯æ£æŠæhæ8æææìåTæ]æ³æçkç¸ç è\è­è¹èòèé8éeédédé4é-éGéTé\éOémé†éÅéê8ê–êõê\ë°ëìgìËìfíîºî`ïðqðÇðûðûðãðÒðsð5ðìïšïqï?ïï»î;î·íífìõëÆë¼ëÍëÎë¿ë“ëMëîêê`êFêZêgêtêŸêêŽê‚êSêFê&ê(êXê²ê'ë«ëGìÞì„íîÄîmï5ð ñ ò!óôòô¤õ1öšöÔö÷+÷}÷Í÷(øø¾øïøùxùÑùúúãú ûOû]ûeûCû÷úïúæúÏú£ú–úú†úIúýùxùùø'øâ÷e÷÷ñöÃööGöúõ´õõEõ3õ#õöôÒôµôÆôþôPõœõèõNö„öÄö÷<÷š÷Â÷ç÷ÿ÷ó÷-ø@øRødøaøcø5øñ÷í÷Á÷•÷a÷4÷ ÷íöûöØöÂö¦öyöDö?ööÞõÜõÅõ”õ“õœõŸõ˜õ¾õ«õ¨õõõöRö¢ö÷—÷&øÀøfùïùˆúÜúOûÞûFü²üýý,ý[ý@ý;ýý%ýüüçüÈüpüüû8û®úBúùù¶ùpù ùýø¡ø}øCøøÉ÷±÷¼÷Ü÷(ø†øùAù„ùéù#úWú­ú ûvû÷û–üýœýþ”þ1ÿÂÿ`ìgÆ4dˆÙóñLJAöÇv.Ä,‹ÿãþ,þ_ý‘ü“û¯úÍùîøNøÃ÷]÷ãö^öãõ~õoõ^õ=õ3õôô·ô±ôô_ôKô]ô‘ôµôíô'õ"õ)õ$õõôô¸ôßôþôÝôòôöôòô¹ôœôjôLô>ô'ô ôãó›óYóêò«ò‘òNò-ò-ò òûñ òøñò;òmònò‘ò®ò³ò£òÅòòòùòóGóVóbóqó¡ó–óÇóéóøó/ôCôRô/ôåó‘ózóVóZóVó:ó(óÜòÛò‡ò"òíñdññ³ð”ð\ðvð_ð-ðUð2ð,ð4ð]ð£ðÒðñNñ|ñÛñòaòvò|òˆò¨òãò:ó¤óöó€ôÔôõõÞõ(öhö°öñöC÷c÷Ä÷ø1øgøˆø´øù\ùÎù?ú¹ú û]û§ûÊûúû)üAühü³üÐü ýIý:ýVý`ý”ýýhýˆýdýý›ýÊýÆý¿ýÊýýjý.ý ý­ü‚üJüüõûïû/ü{ü±üý|ý;þÑþšÿ’”­l$¬BÉsÿƒÿb´×Ù蜄ð¯L8ìéø5([¨ß÷ f°Ù) H t ‚ ¢ à  š ¤ ÷ a ° â   H v ¯ å )‰½âöM]­æøùãЗ‚}e?$ô±€qiBÒ ° i W + 8 W   ,ªZÛ`Ò§O ÇxÙ-r²Üô ûÊ®p*Øoî›môåѶ³µn,Ù%¤%zR¼¨Pð Å ‚ “ è )cœÒæ÷E±œ!µ0¡ê!,"OCCiŸýQ¶aoœÁÒÏ¿r Ô©½±“‘œ·ÌïùHX>'ó¿>ìп׾Ò»˜ˆmML@.IQxš²¸È²¢œ—¬»²Úü#PÝE¼rÕ,!$)h½ÙââÒ qH 蹈¤ŽŸ«˜kofwµí»²…¶4¿R* $;HK`Wb|ŽªÓiŒœ¬³ÂàK‰†c/ÓŒ5þ͈‹WØœVðÃ^ÿž,Õz"Äw{ ò ø ý â ¿ w # ² c % à – k g C 7 ' ó µ œ Š o Z 3  .  û Ü — { l F ; 4 I ~ { œ } ˜ È Î à   C † ¯ ö : t † o ™ — Z + › r d /  · ™ ¤ ° æ , k ²  ¾ n  ’ ‡û[œùO·0~Í&?PK(8E9ONO ß›mZKW\›ð 4—øQÓC–û.b¬ÑAL`¤¿Þû-z®öP”â6¦Õ a“ÔÀ­wb+˱3ÝQ¸X®C´7»‚ojW.$çéëØýV™Â÷\¦÷@Šê7›ÉVéUè1Po—·ÙäÚ¡& óS½2”­^ܶšrSUø(ôËáÖ¾ºÌÕýGyˆ¥¦½Îè R“éð DcogK]ƒÅAlxcçŠ;é Œ dÔöHŸÿWÄ /  « . Ú „ < Ï 8 ÛÊ“jXC8R4íâÁÊ»<õaçjå¡a0XcWt²€ °Ð×¾ÛìDÀŠ{FK×s§?ìZÞoþÒUI"#%NQmŸ¿ý<WC³]ýÿÄÿ„ÿHÿÿÑþ›þDþîý¤ýýýÐü…ü$üÅûlû9ûÖúpúïù}ù(ùùëøëøðøGù–ùÌùú<ú‹ú ú´úàúûTûzû‹ûœûû™ûªû–û®ûãûü<ü¯ü\ýýÙý!þkþ¶þÛþ*ÿzÿ¹ÿòÿJxŠi(åÿÂÿ­ÿ”ÿQÿ#ÿùþ‘þWþ4þ'þ3þþ=þGþXþvþzþŸþwþƒþwþ‹þ§þÔþøþ7ÿ„ÿÂÿC}Ôl‰ÂýûýöåôNkŸºåî)W¡n&¾Oçu  _ Ì  e ¿  ˜ Ú ð á ­ ž š † t X 0  · H  × £ ˜ t X  ñ Ü ž ª ˜ £ ¤ ¥ — ¤ Á Ë í ä Ï ˆ b ( + f Š u … ‰ v b i l x Ë ò 5 • ´ £ Å Ä › ˆ y ‰ {  ð ” } ' Û®‡TPbw®Ì3 p í > À N Æ n õ J W w ” ‘ x ] = ë « w ô 1 § 9 Ù £ Ž »  Y › £ ® È ë  / 6 R F F 5 0  õ î Å ¿ ³ ¬ Å ¸ ¢ ~ ] O R  º p évôˆû’?Â”Ž…Š£š“¢¢Ÿ®ËÔѶŽJ%Ú‚yvi_XÎöìç0`‰Œ^G&  ^È3¦³¯ UüŒ6ËEÃ}9Ô„4æ¡™‘ÌHn\…¼Ï÷yÀh—ÆÂa&öW.ä©”üÿŠÿÿÚþ‰þ1þöý¯ý”ýnýký×ý?þ½þÿ˜ÿ q E‰Æåʳ} ÓnÁÿªÿoÿaÿÿöÿ€œCÖ-oÛ4gu}vrZl‡ºþRCJS3y”ÒÖÄÎàÞëõ .j‚ŸÇë"L9!þ´z0®f}£\ú‚ È…A͇<Ùÿkÿ&ÿìþ”þ_þKþþþüýþþCþvþ…þ©þ¥þÿ9ÿSÿGÿ<ÿ1ÿÿÿ¶þ[þùýŽýýïü¼üZüüÌûlû ûÆú}úPúûù½ùùrùõø·ønøBø^øaødø@øWøQø`øø¯øÇøù_ù°ùóù(úYúqúŒú¬úšútú_ú&úFúOúOúDú/úXúeú¼úû–ûØûëûMü„üÀüÉü§üwüHüîûüüü3ü ü»ûcû4ûûîúéú¶úúúuúCúêù’ù+ù×øŠøbøDøTøPø+ø;øVøNøjøø„ømøiø‹ø¤øïø!ùRùfùNùRùIù/ùùÓø¢ø«øŒøPø(ø@ø&ø,øøømøÏøSù‘ùÒùú'ú"ú úúúõùôù$úOú×ú"ûmûvûVû5û-ûûûòúûNû¸ûüwüÈüý+ý1ý@ý[ýgýwý„ýfýUýSýwý¤ýÖýþkþ¸þ4ÿ–ÿ*ª#ŒÐâðîðçÜô¡”z9í´zìÿ²ÿŒÿtÿSÿUÿgÿÿ”ÿÜÿðÿ9zÜ-¢bÁn‘ã5ˆïsÔ[¾õ3+ægå>ÀWÿž;ÔVø“IÛm*öÿÆÿ¤ÿ_ÿÿæþ¶þ»þÆþñþ7ÿ¿ÿB€ÍÖù';n½6Ä4«3Ÿç+?]Ù³d&Ia…Ù l±û LN<êΰn/òbàq¬BâØÄ¹Žfä†#Ûÿ‹ÿGÿÿ þ^þèýˆýý¼ü‰üGüàû‰ûcûûœú/úÚù‰ùMùùÝøÊøÎøØøÉøˆøgø"øë÷Ä÷¹÷’÷S÷ ÷µö8ö©õâô?ôàóKóóò<òò òüñµñJñòð„ð!ðÄïwï ï¶îOîÖíaíìì‹ì?ìÀënë?ëëÝê»êNêêê×éÕéæé(êcê¦êëQë´ë!ìµì&í~íÐíîXîŽîïïÿïbð¯ðíðñ/ñ3ñ@ñ^ñ’ñÍñýñbò˜òåò)ókóuóƒó¹óØóéóôOô³ôÁôÞôùôþôíôÉôÛôÊô·ô¼ôŒôNô ôËóxó0óóòKòòÆññgñ@ññïðñÞð”ð]ð ðèï¯ïïšïïêïLð»ð4ñÇñ^òó”óôWô¢ôÂôçôõ!õfõ ö~öÛöL÷¶÷ øŽøýø,ù’ùæù-úuúÝúWû¢û!ümü{ümü[ü]üVüvüü¡üïü'ýdý¢ýèýþSþ]þeþYþMþzþ‡þ„þsþFþöý¬ý>ýÂü‹ü1üåû¨ûbû0ûûéúÙú³ú¥ú«ú½úëúHûËû>ü”üý€ýÝý<þ‡þ­þúþ8ÿoÿkÿÿÿ¸ÿÔÿùÿDp‘¹õ hÓj—«“|}yR__uŽ’™˜žÊø3p¦î*47N_m¨Ô2{•¿ÁÑßñý;hfn€{\;ÿ”l*Ô’(àv¾mK-0JvÅ“ŠÇßù,25ôÞÖÜÜõÿÿ;X‚¹÷68JtFº–_Z~”®t5Ò*·M«êS ³a"ÏÿšÿiÿJÿ+ÿÿïþ÷þÌþþ+þÃýqýý»üuüBüüëûöûîûüVü‘üúüiýýéýþ7þpþŠþ‘þˆþþþƒþ þ¸þÎþðþéþ³þƒþ€þ¬þ¯þÙþìþÿ$ÿPÿuÿ™ÿ {ÃVÄLœ8q‘’Œˆ~n?-59-EEÁ†P ®KÛX(ìžiÙÿÿHÿùþ|þ þ–ýZý ý¼üwüJü,üü8üNüvüŽü¼ü/ýzý­ýæýBþ¢þýþFÿ¶ÿ*ÿ”ú8sÉß 4=of]bs{¿Õ:_zˆ‡vS8ÚU]\X„wc' ùÌ´hm/"â©d2þêØýmÄGôgõa—ŸžŽsrq‡Ò(zÃ(g¨oÖ'R©Êì÷ߣ…kC Ƽ….Ã[è¡TJü·\Ür¬/µL¾ÿyÿLÿ4ÿ"ÿ ÿúþÖþ…þFþþîýÚý¶ýŸýtýCýýòüßüãüìüàüÐüÁüèüýýAý^ýEý(ýýýgý´ýòý]þ±þüþ ÿCÿ†ÿ’ÿ›ÿ¦ÿ¤ÿýÿ\ŸôéÕÝ¡…M úÿðÿøÿÕÿ—ÿTÿ-ÿ ÿ(ÿ;ÿaÿpÿ†ÿaÿ0ÿõþ•þ1þÂýXýPý3ý-ý=ýMý>ý-ýýâüØüõüýFý`ýbýYýJý=ý7ý ýòüáüÝü ý%ý[ýgýuývýýÀýþ?þ{þ¥þÊþÝþ;ÿˆÿÿÿvðqÛ:¨Q›ªÂÆÞã͹žc„Ž™–hq}O7s«ÇêóÙ‹IÉ “›r3ÏhÇB»ÿ>ÿêþ¢þ¤þ…þþ þþ£þ¶þÚþ)ÿvÿÎÿÜÿ6Htyˆ˜}R,61•í*So– ¾æ&—÷\ÙVŒ¸sØ%vÄøþÑ˽¹ÏÁ©ˆK"ΙšvZ?(Vw¨áæ ÿ;DϵŸ§¤Ðëþ"öîó\ólîõ& -  0 ) @ H E C X v ˜ µ ñ î  $ H n P 6  Ü ¢ u V  2 b ¶  X ‡ “ ’ r K C  –  Ÿ3§6Û“nSdlzÉ:|¦ÇÅ¬Æ¹ÏøF[w¢Àß' ³ U "  Ì P È \Ÿ¸þbšÇòâ~, úNM0¿o2ê ¼ ­ à ©   ~ - ë o  Å z W ? ÷ À • ^ ¸ W ×`õ°‡]/ÚÜ£ ¨³ {Û+‘Þ( U ‘ ± Ò Ò Ù Â › — [ I > A L t ¼  ^ ¬ Ó î Å ´ S Ô Æ ¡ © Î ç  ' q Ú E “ © ¸ ¿ † „ + ¼ L Ú x ,     Íɇ+î¾›ƒ1óÃoFB#ʉVKԼˠžÎiÞXÇAÎz Ç D µ † 5 ™ Ü  7 f „ — ² ™ g  Z ç n ¡ « \ & ) 3 N   õ 9 h ˆ › ² ü  I e x  \ < 0  Á  ~ Ò > ” Ý $ j š Ö % € Ý _©òƒöI}Ýtøv±ôŒ%£ ›%­2šë!_¤´¦šj<×oëºk¸òÀ …L!ÿ⻣¦¨¥‰}yip‹˜Ó'j¨âúë×± –ž©‡œŽ­¥á#W«í7~}¢ÁùY­î4j¦FšË <–ëLÔXÖ8¾räpâX ¯ Ó Í æ Ú ž ? ëXx—x{‚„ÔyîBÍ[ðÁ¥f9    Ë·—œ·â-m©ð]šg¿:‡ G¹eŽÌ'Rv ÀX ÇôñÙ¢a©? Ðâäô +ñéÖêÿ4Ulž®¶·ˆI ©xk:7DCƒ¹päQ S|¬ú7Šï\ØSÃô R ` ‡ ‚ f 2   ÝÒߟ~}v{YN2,-/-"þ¾‚<ù»z7ýº¨ÝòøùåË¥r]9áðϤ›¤^«f ÃjnO-ÑÑñæó}bâN«\´]aL.M¤è3RJ3ýê¦G0Â~Ž2Þ–®Jö࿉X3L€¥w#¿R«-³ zï–“Èð5Ä3e¶¹¾º T0ø½£€)Ò™{›È'ÃŒ™QŠÇã#ѯ|b`Uq´Þ7“½ÝÒƒ9ΊdF@Gd€sM ÔŽ¹H·J¿8Çcä°¨¾Ûø /[‡Ìbð‚eQS9'Ö·dòˆKã^îG£á 3 + 6 3 ö¼›ŸŠb(¸ƒ:ÞŠ\þ©5´q!øÁˆd Û Í¡±´ÁÙÓ¿°¯ÃÏý-<W„’u=ñšrh„ƒ§¼ß RÂP…¿ìGIˆ¿&^u8(è£u4é²²Cï¥Fò†1ñ›PôãëÓ§_û¶„Fµz)¹ -°HÒ‡WMgÞ5ƒÛ6q¯çA¡ Qm™šÁ„†sr[t‹°ò]Èw¹áþ5KapoQИ}<³WÞƒ+ç–aâ»u»3ËAê´©µ½Á¬¤ln]Pvyy¡M›Ó&ZS_MS8þÐÓYµiÜW¹#O”­®«šfpƒ”¿õ+iŽ´ëàðÏ‹,ëñÕ  #Û¸o;×»§¶ê$M‘aŸ>¶rËýAYz”°áð N½4à©1äeÒA„ºõü<J,=?–Ø" B q Á ¶ Ö é È º • | V F ! F D Q x Ñ !Q!h!‹!™!Í!ó!""""2"R"i"^"d"g"H"E"B"R"†"Œ""™"¼"Ë"Ñ"×"ö"'#*#C#}#£#Ö#$‹$õ$W%©%ä%&"&?&t&Â&ë&'S'm'f'7'õ&Õ&&£&g&V&n&r&Š&è&'C'£'À' (K((ã(C)¦)!*¤* +Š+ß+D,œ,Ö,<-{-µ-*.g.~.Œ.c.J.3.(.þ-Í-˜-B-ã,,@,ö+Ê+¯+^+ +Ú*´*’*k*Q*G*b*m*‚*d*T*1* *Ü)®)o)9))²(\(ô'S'$'è&¸&†&·&¾&Ú&ó&û&'8'p'…'£'¦'Ô'(@(x(¹(Á(Å(Ó(É(Ì(Ã(Ý(Ï(¦(™(6(Â'G'–&ì%¿$Ô#y#ï"¡"""¯!g!L!ý á ê Á v Ü Ø Ï ž!Ø!" ""1"E"N"4"*""ð!²!p!!¦ 9 ³*“ñ2™ëzÌ ‰¦µ®ü+Xy­»K´«’c('!î–Ä;½j#ùß×Ç´¤Z+Û/;D=ÝÑ}=é-ûÕ©¯ž‘˜ ®Û(}æ=º$…Êë"T’ªè!MOGJDÔ¡pg==!زŒƒ¢¦¦zW6äíéÝ 1w¨‹’Z>æÉd ÷Ÿ`H-2Or¹æYf²ÿJŸç_¼"oô}gÄþf» OÀJîœ :!Ô!L"Ž"â" #*#N#F#o#j#1#Ô"ƒ"û!y!Ý ]  ¯¥k*ÓlH4 ÷í'$%5/ëΊT L£Âº’šn¿cñ´c*öØÛå<ŠæSó•2Èp ¥ '!Ï!_"Û"T#¡#$C$k$¡$Ã$Æ$õ$%M%z%š%¼%Ê%ß%×%ª%c%ÿ$—$â#N#š""‘! !£ Q   ú) t ¡ Ã È ï W!!±!µ!Ô!")"T"Q"u"L"#"""ã!»!Õ!µ! !’!j!5!4!1!!A!#!!!=!?!L!2!!± + £×-užÅä%pÑ6ăô¤e0Ñ—bÄcý„ÊråwW@2@5»Rã)G •  e Å  š ê~ 7ÃB/uªÚK¤ò6- áÊîÏÚé V± } ä _ Í > ¯ + V  ° 0 ¤ ö 8 § zì À[È(i‘õQ“ÿòþkþëýýVýòüuü<ü üúûüûøûfüŽüÃü¤üÇü5ýƒýÛý=þÁþ7ÿ¹ÿq½sources_5316/test/fon/texio/0000755000176700017670000000000010650662615014623 5ustar paulpaulsources_5316/test/fon/texio/texio17.TextGrid0000644000176700017670000000025010650661273017573 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exisources_5316/test/fon/texio/texio10.TextGrid0000644000176700017670000000126610650657135017576 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = sources_5316/test/fon/texio/texio14.TextGrid0000644000176700017670000000165410650660677017610 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = <early> 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd" sources_5316/test/fon/texio/texio3.TextGrid0000644000176700017670000000166410650652763017524 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = "too early" 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd" sources_5316/test/fon/texio/texio18.TextGrid0000644000176700017670000000163210650661562017602 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exi sts> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd"sources_5316/test/fon/texio/texio15.TextGrid0000644000176700017670000000163010650660742017574 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad"x intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd"sources_5316/test/fon/texio/texio4.TextGrid0000644000176700017670000000165010650655631017515 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? 666.6 <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd" sources_5316/test/fon/texio/texio2.TextGrid0000644000176700017670000000164410650652730017513 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = 666 "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd" sources_5316/test/fon/texio/texio9.TextGrid0000644000176700017670000000065610650653325017525 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 sources_5316/test/fon/texio/texio11.TextGrid0000644000176700017670000000127610650657243017600 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad"sources_5316/test/fon/texio/texio13.TextGrid0000644000176700017670000000165410650660141017571 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = "early" 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd" sources_5316/test/fon/texio/texio12.TextGrid0000644000176700017670000000165410650657744017607 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? "early" <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd" sources_5316/test/fon/texio/texio6.TextGrid0000644000176700017670000000165410650653145017521 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = <early> 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd" sources_5316/test/fon/texio/texio16.TextGrid0000644000176700017670000000127410650661173017600 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "adsources_5316/test/fon/texio/texio19.TextGrid0000644000176700017670000000177610650662012017603 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exihgjkfdghkjdfhgjkdfghjkdfhgkdjfghdkfjghdfkjghdkgjdhfsts> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd"sources_5316/test/fon/texio/texio5.TextGrid0000644000176700017670000000165410650653107017516 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = <early> "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd" sources_5316/test/fon/texio/texio1.TextGrid0000644000176700017670000000072211105570562017504 0ustar paulpaulFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad""ta""" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd" sources_5316/test/fon/texio/texio7.TextGrid0000644000176700017670000000147610650653222017520 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exists> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 sources_5316/test/fon/texio/texio20.TextGrid0000644000176700017670000000162210650662632017571 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 tiers? <exi> size = 1 item []: item [1]: class = "IntervalTier" name = "test" xmin = 0 xmax = 1 intervals: size = 2 intervals [1]: xmin = 0 xmax = 0.5051115439848715 text = "ad" intervals [2]: xmin = 0.5051115439848715 xmax = 1 text = "sd"sources_5316/test/fon/texio/texio8.TextGrid0000644000176700017670000000022210650653271017511 0ustar paulpaulþÿFile type = "ooTextFile" Object class = "TextGrid" xmin = 0 xmax = 1 sources_5316/test/fon/endian.praat0000644000176700017670000000536011130227551015754 0ustar paulpaulecho Endian... procedure do Read from file... test.wav energyInAir = Get energy in air assert "'energyInAir:11'" = "0.00008397361" Read from file... test.Sound energyInAir2 = Get energy in air Remove select Sound test assert energyInAir2 = energyInAir Write to WAV file... test2.wav Remove Read from file... test2.wav energyInAir2 = Get energy in air deleteFile ("test2.wav") assert energyInAir2 = energyInAir Write to AIFF file... test2.aiff Remove Read from file... test2.aiff energyInAir2 = Get energy in air deleteFile ("test2.aiff") assert energyInAir2 = energyInAir Write to FLAC file... test2.flac Remove Read from file... test2.flac energyInAir2 = Get energy in air deleteFile ("test2.flac") assert energyInAir2 = energyInAir Write to binary file... test2.bin Remove Read from file... test2.bin energyInAir2 = Get energy in air deleteFile ("test2.bin") assert energyInAir2 = energyInAir Write to Sesam file... test2.sdf Remove Read from file... test2.sdf deleteFile ("test2.sdf") energyInAir2 = Get energy in air Write to Sesam file... test3.sdf Remove Read from file... test3.sdf deleteFile ("test3.sdf") energyInAir3 = Get energy in air assert energyInAir3 = energyInAir2 Remove Create Sound... test 0 100 22050 0.1 * randomGauss (0, 1) for i to 2 stopwatch Write to WAV file... kanweg.Sound t1 = stopwatch stopwatch Write to AIFF file... kanweg.Sound t2 = stopwatch stopwatch Write to binary file... kanweg.Sound t3 = stopwatch stopwatch Write to FLAC file... kanweg.Sound t4 = stopwatch printline 't1:2' 't2:2' 't3:2' 't4:2' endfor Create Sound... test 0 1 22050 exp(-x*1000) Write to binary file... kanweg.Sound Read from file... kanweg.Sound Formula... (self = Sound_test []) - 1 energyInAir = Get energy in air assert energyInAir = 0 plus Sound test Remove Create Sound... test 0 1 22050 exp(x*1000) Write to binary file... kanweg.Sound Read from file... kanweg.Sound Formula... (self = Sound_test []) - 1 energyInAir = Get energy in air assert energyInAir = 0 plus Sound test Remove deleteFile ("kanweg.Sound") Create TableOfReal... test 1 22050 Formula... exp(-col/22.05) Write to binary file... kanweg.TableOfReal Read from file... kanweg.TableOfReal Formula... (self = TableOfReal_test []) - 1 norm = Get table norm assert norm = 0 plus TableOfReal test Remove Create TableOfReal... test 1 22050 Formula... exp(col/22.05) Write to binary file... kanweg.TableOfReal Read from file... kanweg.TableOfReal Formula... (self = TableOfReal_test []) - 1 norm = Get table norm assert norm = 0 plus TableOfReal test Remove deleteFile ("kanweg.TableOfReal") endproc printline Optimized: Debug... 0 call do printline Portable: Debug... 18 call do Debug... 0 printline OK sources_5316/test/fon/textioSpeed.praat0000644000176700017670000000114111130226745017010 0ustar paulpaul# textioSpeed.praat # Paul Boersma, 9 November 2008 echo Text I/O speed: for i to 33 sound'i' = Create Sound from formula... sound'i' Mono 0 10 44100 i endfor select sound1 for i from 2 to 33 plus sound'i' endfor print writing: stopwatch Write to text file... kanweg.Collection t = stopwatch printline 't:3' seconds Remove print reading: stopwatch Read from file... kanweg.Collection t = stopwatch printline 't:3' seconds assert numberOfSelected () = 33 minus Sound sound30 Remove select Sound sound30 mean = Get mean... All 0 0 assert mean = 30 ; 'mean' deleteFile ("kanweg.Collection") printline OK sources_5316/contrib/0000755000176700017670000000000011513143135013360 5ustar paulpaulsources_5316/contrib/ola/0000755000176700017670000000000011724523411014136 5ustar paulpaulsources_5316/contrib/ola/KNN_prune.h0000644000176700017670000000531711614422044016152 0ustar paulpaul#ifndef _KNN_prune_h_ #define _KNN_prune_h_ /* KNN_prune.h * * Copyright (C) 2007-2008 Ola Söder * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 20080529 Initial release * pb 2011/03/08 C++ */ ///////////////////////////////////////////////////// // Prune auxs // ///////////////////////////////////////////////////// #include "KNN.h" #include "FeatureWeights.h" #include "OlaP.h" ///////////////////////////////////////////////////// // Prototypes // ///////////////////////////////////////////////////// // Prune long KNN_prune_prune ( KNN me, // the classifier to be pruned double n, // pruning degree: noise, 0 <= n <= 1 double r, // pruning redundancy: noise, 0 <= n <= 1 long k // k(!) ); // sort indices according to pruning order defined by rule 2 void KNN_prune_sort ( Pattern p, // source Categories c, // source long k, // k(!) long * indices, // indices of instances to be sorted long nindices // the number of instances to be sorted ); // k-coverage long KNN_prune_kCoverage ( Pattern p, // source Categories c, // source long y, // source instance index long k, // k(!) long * indices // Out: kCoverage set ); // testing for superfluousness int KNN_prune_superfluous ( Pattern p, // source Categories c, // source long y, // source instance index long k, // k(!) long skipper // Skipping instance skipper ); // testing for criticalness int KNN_prune_critical ( Pattern p, // source Categories c, // source long y, // source instance index long k // k(!) ); // testing for noisyness int KNN_prune_noisy ( Pattern p, // source Categories c, // source long y, // source instance index long k // k(!) ); /* End of file KNN_prune.h */ #endif sources_5316/contrib/ola/KNN_threads.cpp0000644000176700017670000001256311632724216017015 0ustar paulpaul/* KNN_threads.c * * Copyright (C) 2009 Ola Söder * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 20090123 First version */ ///////////////////////////////////////////////////// // // ///////////////////////////////////////////////////// #include #include "KNN.h" #include "KNN_threads.h" #include "OlaP.h" // Threading disabled /* // Linux... #if defined (__linux__) #define __USE_GNU #include // BSD-style OSes #elif defined (__APPLE__) #include #include #endif // Non-pthreaders, Windows #ifdef _WIN32 #include // The rest of the pack #else #include #endif */ ///////////////////////////////////////////////////// // KNN_getNumberOfCPUs // ///////////////////////////////////////////////////// int KNN_getNumberOfCPUs(void) { return(1); // Threading disabled /* int ncpus = 0; // Linux... #if defined (__linux__) cpu_set_t * cpuset = (cpu_set_t *) malloc(sizeof(cpu_set_t)); if(cpuset) { sched_getaffinity(0, sizeof(cpu_set_t), cpuset); for(int cpu = 0; cpu <= CPU_SETSIZE; ++cpu) if(CPU_ISSET(cpu, cpuset)) ++ncpus; free(cpuset); } Melder_assert(ncpus >= 1); // BSD-style OSes #elif defined (__APPLE__) int mib[2]; size_t len = sizeof(ncpus); mib[0] = CTL_HW; mib[1] = HW_NCPU; sysctl(mib, 2, &ncpus, &len, 0, 0); // Non-pthreaders, Windows #elif defined (_WIN32) typedef BOOL (WINAPI *LPFN_GLPI) (PSYSTEM_LOGICAL_PROCESSOR_INFORMATION, PDWORD); BOOL done, rc; DWORD returnLength, byteOffset; PSYSTEM_LOGICAL_PROCESSOR_INFORMATION buffer, ptr; LPFN_GLPI Glpi; Glpi = (LPFN_GLPI) GetProcAddress(GetModuleHandle(TEXT("kernel32")), "GetLogicalProcessorInformation"); if(!Glpi) return(1); done = FALSE; buffer = NULL; returnLength = 0; while(!done) { rc = Glpi(buffer, &returnLength); if(!rc) { if(GetLastError() == ERROR_INSUFFICIENT_BUFFER) { if(buffer) free(buffer); return (1); } else done = TRUE; } byteOffset = 0; ptr=buffer; while (byteOffset < returnLength) { switch (ptr->Relationship) { case RelationProcessorCore: ++ncpus; default: } byteOffset += sizeof(SYSTEM_LOGICAL_PROCESSOR_INFORMATION); ++ptr; } } free(buffer); ncpus = 1; // Unknown OS #else ncpus = 1; #endif Melder_assert(ncpus >= 1); return(ncpus); */ } ///////////////////////////////////////////////////// // KNN_threadDistribution // ///////////////////////////////////////////////////// void * KNN_threadDistribution ( void * (* function) (void *), void ** input, int nthreads ) { Melder_assert(function && input && nthreads > 0); if(!(function && input && nthreads > 0)) { KNN_thread_status * error = (KNN_thread_status *) malloc(sizeof(enum KNN_thread_status)); if(error) *error = KNN_THREAD_ERROR; return((void *) error); } if(nthreads > 1) { #ifdef _WIN32 // Threading disabled /* HANDLE hHandle[nthreads]; for(int i = 0; i < nthreds; ++) hHandle[i] = CreateThread(NULL, 0, function, input[i], 0, NULL); while(nthreads--) WaitForSingleObject(hHandle[nthreds], INFINITE); */ #else // Threading disabled /* pthread_t thread_ids[nthreads]; for(int i = 0; i < nthreads; ++i) pthread_create(&thread_ids[i], NULL, function, input[i]); while(nthreads--) pthread_join(thread_ids[nthreads], NULL); return(NULL); */ #endif } void *result = function (input [0]); return result; } ///////////////////////////////////////////////////// // KNN_threadTest // ///////////////////////////////////////////////////// void KNN_threadTest(void) { void * dummy[KNN_getNumberOfCPUs()]; KNN_threadDistribution(KNN_threadTestAux, (void **) &dummy, KNN_getNumberOfCPUs()); } ///////////////////////////////////////////////////// // KNN_threadTestAux // ///////////////////////////////////////////////////// void * KNN_threadTestAux(void * dummy) { dummy = NULL; // dummy assignment to avoid compiler warnings; for(int i = 0; i < 50000; ++i) for(int i = 0; i < 50000; ++i) ; return(NULL); } sources_5316/contrib/ola/Pattern_to_Categories_cluster.cpp0000644000176700017670000001144411646363623022705 0ustar paulpaul/* Pattern_to_Categories_cluster.cpp * * Copyright (C) 2007-2008 Ola So"der, 2010-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 20070529 initial release * pb 20100606 removed some array-creations-on-the-stack * pb 20100606 corrected some arrary-index-out-of-bounds errors * pb 20100606 corrected some memory leaks * pb 2011/03/08 tried to repair some of the header file chaos (several procedures here should be in KNN.c instead) * pb 2011/04/13 C++ */ #include "Pattern_to_Categories_cluster.h" #include "KNN.h" // BUG ///////////////////////////////////////////////////////////////////////////////////////////// // Pattern_to_Categories_cluster // ///////////////////////////////////////////////////////////////////////////////////////////// Categories Pattern_to_Categories_cluster ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern p, // source // FeatureWeights fws, // feature weights // long k, // k(!) // double s, // clustersize constraint 0 < s <= 1 // long m // reseed maximum // ) { autoCategories categories = Categories_sequentialNumbers (k); if (k == p->ny) return categories.transfer(); autoKNN knn = KNN_create(); if(p->ny % k) if (s > (double) (p->ny / k) / (double) (p->ny / k + 1)) s = (double) (p->ny / k) / (double) (p->ny / k + 1); double progress = m; autoNUMvector sizes (0L, k); autoNUMvector seeds (0L, k); autoPattern centroids = (Pattern) Pattern_create (k, p->nx); autoNUMvector beta (0L, centroids->nx); do { double delta; long nfriends = 0; Melder_progress (1 - (progress - m) / progress, L""); for (long y = 1; y <= centroids->ny; y++) { int ifriend = 1; long ys = (long) lround(NUMrandomUniform(1, p->ny)); if (nfriends) { while (ifriend) { ys = (long) lround(NUMrandomUniform(1, p->ny)); for (long fc = 0; fc < nfriends; fc++) { ifriend = 0; Melder_assert (fc < k); if (seeds [fc] == ys) { ifriend = 1; break; } } } } Melder_assert (nfriends <= k); seeds [nfriends++] = ys; for (long x = 1; x <= centroids->nx; x++) centroids->z[y][x] = p->z[ys][x]; } do { delta = 0; KNN_learn (knn.peek(), centroids.peek(), categories.peek(), kOla_REPLACE, kOla_SEQUENTIAL); autoCategories interim = KNN_classifyToCategories (knn.peek(), p, fws, 1, kOla_FLAT_VOTING); for (long x = 1; x <= k; x++) sizes [x] = 0; for (long yp = 1; yp <= categories->size; yp++) { double alfa = 1; Melder_assert (yp <= centroids->ny); for (long x = 1; x <= centroids->nx; x++) { beta[x] = centroids->z[yp][x]; } for (long ys = 1; ys <= interim->size; ys++) { if (FeatureWeights_areFriends ((SimpleString) categories->item[yp], (SimpleString) interim->item[ys])) { for (long x = 1; x <= p->nx; x++) { Melder_assert (ys <= p->ny); if (alfa == 1) { centroids->z[yp][x] = p->z[ys][x]; } else { centroids->z[yp][x] += (p->z[ys][x] - centroids->z[yp][x]) / alfa; } } Melder_assert (yp <= k); sizes [yp] ++; alfa++; } } for (long x = 1; x <= centroids->nx; x++) { delta += fabs (beta[x] - centroids->z[yp][x]); } } } while (delta); double smax = sizes [1]; double smin = sizes [1]; for (long x = 1; x <= k; x++) { if (smax < sizes [x]) smax = sizes [x]; if (smin > sizes [x]) smin = sizes [x]; } sizes [0] = smin / smax; --m; } while (sizes[0] < s && m > 0); autoCategories output = KNN_classifyToCategories (knn.peek(), p, fws, 1, kOla_FLAT_VOTING); return output.transfer(); } /* End of file Pattern_to_Categories_cluster.cpp */ sources_5316/contrib/ola/Makefile0000644000176700017670000000131011704274244015576 0ustar paulpaul# Makefile of the library "contrib/ola" # Ola So"der 19 January 2008 # Paul Boersma, 14 January 2012 include ../../makefile.defs CPPFLAGS = -I ../../dwtools -I ../../fon -I ../../sys -I ../../dwsys -I ../../stat -I ../../num -I ../../external/gsl -D_DEBUG -D_REENTRANT OBJECTS = KNN.o \ KNN_threads.o Pattern_to_Categories_cluster.o KNN_prune.o FeatureWeights.o praat_contrib_Ola_KNN.o manual_KNN.o .PHONY: all clean all: libOla.a clean: $(RM) $(OBJECTS) $(RM) libOla.a libOla.a: $(OBJECTS) touch libOla.a rm libOla.a ar cq libOla.a $(OBJECTS) $(RANLIB) libOla.a $(OBJECTS): *.h ../../sys/*.h ../../dwtools/*.h ../../fon/*.h ../../dwsys/*.h ../../stat/*.h ../../num/*.h ../../external/gsl/*.h sources_5316/contrib/ola/manual_KNN.cpp0000644000176700017670000012704711627222747016652 0ustar paulpaul/* manual_KNN.c * * Copyright (C) 2007-2008 Ola Söder * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 2008/05/29 Initial release * os 2009/01/23 Removed irrelevant information * pb 2010/12/28 lay-out, spelling */ #include "ManPagesM.h" #include "KNN.h" void manual_KNN_init (ManPages me); void manual_KNN_init (ManPages me) { MAN_BEGIN (L"kNN classifiers", L"Ola Söder", 20080529) INTRO (L"This tutorial describes the use of kNN classifiers in Praat.") NORMAL (L"@@kNN classifiers 1. What is a kNN classifier?|1. What is a kNN classifier?@") NORMAL (L"@@kNN classifiers 1.1. Improving classification accuracy|1.1. Improving classification accuracy@") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting|1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.1.1. Filter-based feature weighting|1.1.1.1. Filter-based feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.1.2. Wrapper-based feature weighting|1.1.1.2. Wrapper-based feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.2. Model selection|1.1.2. Model selection@") NORMAL (L"@@kNN classifiers 1.2. Improving resource efficiency|1.2. Improving resource efficiency@") LIST_ITEM (L"@@kNN classifiers 1.2.1. Pruning|1.2.1. Pruning@") NORMAL (L"@@kNN classifiers 2. Quick start|2. Quick start@") NORMAL (L"@@kNN classifiers 3. Command overview|3. Command overview@") MAN_END MAN_BEGIN (L"KNN", L"Ola Söder", 20080529) INTRO (L"One of the @@types of objects@ in Praat.") NORMAL (L"A #KNN classifier can %learn associations between its %input and its %output. " "The @@kNN classifiers@ tutorial gives you an introduction to the usage of %%k%NN learners in Praat.") MAN_END MAN_BEGIN (L"FeatureWeights", L"Ola Söder", 20080729) INTRO (L"One of the @@types of objects@ in Praat.") NORMAL (L"A @FeatureWeights object is a %d-dimensional vector containing weight values used to transform a %d-dimensional space. Feature weighting can be used to improve the classifcation accuracy of @KNN classifiers. It can also be used to generate a @Dissimilarity matrix from a @Pattern object. @Dissimilarity matrices in conjunction with @@Multidimensional scaling|MDS-analysis@ can aid the visualization of high-dimensional data.") MAN_END MAN_BEGIN (L"kNN classifiers 1. What is a kNN classifier?", L"Ola Söder", 20080529) NORMAL (L"%%Instance-based% classifiers such as the %%k%NN classifier operate on the premises that classification of unknown instances " "can be done by relating the unknown to the known according to some @@Euclidean distance|distance/similarity function@. " "The intuition is that two instances far apart in the %%instance space% defined by the appropriate %%distance function% are less likely " "than two closely situated instances to belong to the same class.") ENTRY (L"The learning process") NORMAL (L"Unlike many artificial learners, %%instance-based% learners do not abstract any information from the training data during the learning phase. " "Learning is merely a question of encapsulating the training data. The process of %generalization is postponed until it is absolutely unavoidable, " "that is, at the time of %classification. This property has lead to the referring to %%instance-based% learners as %lazy learners, " "whereas classifiers such as @@Feedforward neural networks 1. What is a feedforward neural network?|feedforward neural networks@, " "where proper %abstraction is done during the learning phase, often are entitled %eager learners.") ENTRY (L"Classification") NORMAL (L"Classification (%generalization) using an %%instance-based% classifier can be a simple matter of locating the nearest neighbour in %%instance space% " "and labelling the unknown instance with the same class label as that of the located (known) neighbour. " "This approach is often referred to as a %%nearest neighbour classifier%. " "The downside of this simple approach is the lack of robustness that characterize the resulting classifiers. " "The high degree of local sensitivity makes %%nearest neighbour classifiers% highly susceptible to noise in the training data.") NORMAL (L"More robust models can be achieved by locating %k, where %k > 1, neighbours and letting the majority vote decide the outcome of the class labelling. " "A higher value of %k results in a smoother, less locally sensitive, function. " "The %%nearest neighbour classifier% can be regarded as a special case of the more general %%k-nearest neighbours classifier%, " "hereafter referred to as a %%k%NN classifier. The drawback of increasing the value of %k is of course that as %k approaches %n, " "where %n is the size of the %%instance base%, the performance of the classifier will approach that of the most straightforward %%statistical baseline%, " "the assumption that all unknown instances belong to the class most most frequently represented in the training data.") NORMAL (L"This problem can be avoided by limiting the influence of distant instances. " "One way of doing so is to assign a weight to each vote, where the weight is a function of the distance between the unknown and the known instance. " "By letting each weight be defined by the inversed squared distance between the known and unknown instances votes cast by distant instances " "will have very little influence on the decision process compared to instances in the near neighbourhood. " "%%Distance weighted voting% usually serves as a good middle ground as far as local sensitivity is concerned.") MAN_END MAN_BEGIN (L"kNN classifiers 1.1. Improving classification accuracy", L"Ola Söder", 20080529) NORMAL (L"This tutorial describes possible ways of improving the classification accuracy of a %%k%NN classifier.") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting|1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.2. Model selection|1.1.2. Model selection@") MAN_END MAN_BEGIN (L"kNN classifiers 1.1.1. Feature weighting", L"Ola Söder", 20080529) NORMAL (L"A %%k%NN classifier in its most basic form operates under the implicit assumption that all features are of equal value as far as the classification problem at hand is concerned. When irrelevant and noisy features influence the neighbourhood search to the same degree as highly relevant features, the accuracy of the model is likely to deteriorate. %%Feature weighting% is a technique used to approximate the optimal degree of influence of individual features using a training set. When successfully applied relevant features are attributed a high weight value, whereas irrelevant features are given a weight value close to zero. %%Feature weighting% can be used not only to improve classification accuracy but also to discard features with weights below a certain threshold value and thereby increase the resource efficiency of the classifier.") NORMAL (L"Two fundamentally different approaches to this optimization problem can be identified, the %%filter-based% and the %%wrapper-based%. The class of %%filter-based% methods contains algorithms that use no input other than the training data itself to calculate the %%feature weights%, whereas %%wrapper-based% algorithms use feedback from a classifier to guide the search. %%Wrapper-based% algorithms are inherently more powerful than their filter-based counterpart as they implicitly take the %%inductive bias% of the classifier into account. This power comes at a price however; the usage of %%wrapper-based% algorithms increases the risk of %%overfitting% the training data.") NORMAL (L"In @@kNN classifiers 1.1.1.1. Filter-based feature weighting|section 1.1.1.1.@ the %%filter-based% feature weighting algorithm implemented in Praat is presented. @@kNN classifiers 1.1.1.2. Wrapper-based feature weighting|Section 1.1.1.2.@ contains an account of the implemented %%wrapper-based% feature weighting algorithm.") MAN_END MAN_BEGIN (L"kNN classifiers 1.1.1.1. Filter-based feature weighting", L"Ola Söder", 20080529) NORMAL (L"The %%filter-based% %%feature weighting% algorithm implemented in Praat is an extended version of the well known R\\s{ELIEF} algorithm, R\\s{ELIEF-F}, such as it is presented (with one minor exception, see below) in @@Igor Kononenko (1994)|Kononenko (1994)@. Unlike the original R\\s{ELIEF} algorithm, the R\\s{ELIEF-F} algorithm copes with multi class (as in more than 2 classes) data sets. The simple intuition behind the R\\s{ELIEF-F} algorithm is that a good feature is a feature with little within class variance and generous amounts of between-class variance. A bad feature is characterized by within-class and between-class variances of magnitudes roughly equal.") NORMAL (L"The computation of the weight vector is done in an iterative fashion, with all weights initially set to 0. All features in the training set are normalized (all values are set within the range [0 ... 1]) and thereafter used to update the weight vector as follows: On each iteration a random instance is chosen. The nearest hit is located, where hit is an instance of the same class as that of the randomly chosen instance. The nearest misses of all the classes but that of the randomly chosen instance are located, where a miss is an instance of a class different from that of the randomly chosen instance. Each weight is updated by subtracting the difference between the given attribute of the randomly chosen instance and that of the nearest hit and adding the corresponding difference between the chosen instance and all the nearest misses weighted by the prior probabilities of their classes. If the distance between the attribute of the randomly chosen instance and the nearest hit equals the corresponding value for the nearest miss(es) then the weight value will not change, it will thus remain 0 given that the current iteration is the first one. If the difference between the attribute of the chosen instance and the nearest hit is lower than the corresponding value for the miss(es) then the weight value will be increased. On average highly significant attributes will result in absolute values distinct from 0, leading to an absolute increase of the weight, and insignificant attributes will on average result in values near 0, retaining the pessimistic view that all features are of no value as predictors.") NORMAL (L"The implementation of R\\s{ELIEF-F} found in Praat differs slightly from the algorithm described. Instances are not randomly chosen, instead all instances are used to update the weight vector. This simplification is of no concern unless massive data sets are used, in which case the Praat approach would be no less precise, but needlessly slow.") MAN_END MAN_BEGIN (L"kNN classifiers 1.1.1.2. Wrapper-based feature weighting", L"Ola Söder", 20090123) NORMAL (L"The %%wrapper-based% %%feature weighting% algorithm implemented in Praat attempts to find the globally optimal feature weights by means of a greedy local search. The local neighbourhood is defined by a number of random seeds centered around a pivot seed. For each iteration of the algorithm the best performing seed is chosen to be the pivot of the next iteration. At the same time the maximum allowed distance between a seed and the pivot is decreased by a constant factor. Given a sufficient number of seeds and a small shrinkage factor the algorithm will on average home in on a good approximation of the global maximum.") NORMAL (L"Given reasonable parameter settings, the search algorithm on average gives good results without huge memory and CPU requirements. The strong point of the method, the ability to efficiently do a rather thorough search of the weight space, can, as mentioned in @@kNN classifiers 1.1.1. Feature weighting|section 1.1.1.@, lead to overfitting. One way of minimizing this problem is to constrain the algorithm by means of %%early stopping%. In Praat this is done in a very naive fashion, by simply not allowing the algorithm to explore weights achieving an accuracy higher than a specified threshold value.") MAN_END MAN_BEGIN (L"kNN classifiers 1.1.2. Model selection", L"Ola Söder", 20080529) NORMAL (L"%%Model selection% is the process of choosing classifier parameters suitable for the classification task at hand. In most cases this is done manually in an experimental fashion.") NORMAL (L"The search for the optimal model can also be automated. In Praat this is done by means of the same @@kNN classifiers 1.1.1.2. Wrapper-based feature weighting|greedy local search algorithm@ used to search the weight space for feature weights. The %%model selection% search implementation in Praat lets the user limit the search space with respect to the parameter %k. By setting a maximum allowed value of %k the search space can be shrunk considerably.") NORMAL (L"Due to its discrete (%k) and nominal (vote weighting) nature, the size of the search space is normally of no concern, making an experimental/manual search tractable. The %%model selection% feature of Praat becomes an essential tool only when applied to huge instance bases where the expected optimal value of %k is high. In most cases however, manual experimenting will suffice.") MAN_END MAN_BEGIN (L"kNN classifiers 1.2. Improving resource efficiency", L"Ola Söder", 20080529) NORMAL (L"%%Instance-based% learners such as the %%k%NN classifier implemented in Praat are fairly inefficient as far as CPU and memory usage is concerned. The performance can be improved upon by making sure that only those instances that are vital for the accuracy of the classifier are stored and that non-vital instances are disposed of. Praat does give the user the possibility to prune non-vital or harmful instances, making the resulting classifier less memory and CPU hungry and in some cases more accurate even though that is not the primary objective of the pruning algorithm.") MAN_END MAN_BEGIN (L"kNN classifiers 1.2.1. Pruning", L"Ola Söder", 20080529) NORMAL (L"Pruning is the process of discarding instances that do not improve upon the classification accuracy of the classifier. This group of instances includes noisy instances that, at best, make no difference as far as model accuracy is concerned, at worst, induces classification errors. It also includes instances that are redundant; instances that are implied by the defined neighbourhood.") ENTRY (L"The C-Pruner algorithm") NORMAL (L"The C-Pruner algorithm such as it is presented in @@Ke-Ping Zhao et al. (2003)|Zhao et al. (2003)@ identifies pruning candidates and computes the order in which these candidates shall be removed. The ordering is of vital importance since the removal of one candidate might disqualify other candidates, making them non-prunable. In order to understand how the C-Pruner algorithm operates a few definitions are necessary:") LIST_ITEM (L"\\bu The %k-reachability set of an instance %p consists of the %k nearest neighbours of %p") LIST_ITEM (L"\\bu The %k-coverage set of an instance %p consists of those instances of the same class as that of %p having %p as one of their %k nearest neighbours.") LIST_ITEM (L"\\bu An instance %p is superfluous if it is implied by %k-reachability, that is, if it can be correctly classified using %k-reachability as instance base.") LIST_ITEM (L"\\bu An instance %p is critical if at least one instance in the %k-coverage set of %p is not implied by the %k-reachability set of %p or, after %p is deleted, atleast one instance in the %k-coverage set of %p is not implied by the %k-reachability set of %p.") LIST_ITEM (L"\\bu An instance %p is noisy if %p isn't superfluous and the %k-reachability set of %p is bigger than the %k-coverage set of %p.") NORMAL (L"Given these definitions, an instance is tagged for pruning if one of the following conditions hold: It is noisy, or it is superfluous but not critical. This translates to the discarding of instances that are bad class predictors (noise) and of instances that are highly typical of their class and thus are located close to the center of the cluster defining the given class. Instances located close to the class center are very likely implied by the surrounding border instances and thus redundant. In order to avoid destructive domino effects it is important that the pruning starts close to the center of the cluster and works its way out and not the other way around. To impose this ordering the C-Pruner algorithm uses the following heuristics to determine the order of removal of two superfluous instances %p__i_ and %p__j_:") LIST_ITEM (L"\\bu If the %k-reachability set of %p__i_ contains more instances of the same class as that of %p__i_ than the corresponding value for %p__j_ then %p__i_ should be removed before %p__j_.") LIST_ITEM (L"\\bu If the %k-reachability set of %p__i_ contains the same number of instances of the same class as that of %p__i_ as the corresponding value for %p__j_ and the distance between %p__i_ and the closest instance of a class different from the class of %p__i_ is greater than the corresponding value for %p__j_ then %p__i_ should be removed before %p__j_.") LIST_ITEM (L"\\bu If the %k-reachability set of %p__i_ contains the same number of instances of the same class as that of %p__i_ as the corresponding value for %p__j_ and the distance between %p__i_ and the closest instance of a class different from the class of %p__i_ equals the corresponding value for %p__j_ then the order of removal is decided randomly.") NORMAL (L"In order to gain control of the degree of pruning the Praat implementation of the C-Pruner algorithm decides whether to prune or not prune a given instance tagged for pruning on a probabilistic basis. This makes it possible for the user to specify the hardness of the pruning process (e.g. 100 percent (exp.) noise, 50 percent (exp.) redundancy) to be able to find a good compromise between model accuracy and resource requirements.") MAN_END MAN_BEGIN (L"kNN classifiers 2. Quick start", L"Ola Söder", 20080809) ENTRY (L"An example: Learning the Iris data set") NORMAL (L"In the @@Feedforward neural networks|the feedforward neural networks tutorial@ a description of how the @FFNet classifier in Praat can be applied to @@iris data set|the Iris data set@ can be found.") NORMAL (L"The same data can be used to test the %%k%NN feature of Praat. To do so create an example data set using the @@Create iris example...@ command found in the ##Neural nets# submenu. The form prompting for network topology settings can be ignored by selecting OK. Select the newly created @Pattern and @Categories objects and click ##To KNN Classifier...#. A form prompting for a name of the classifier to be created will be shown. The ordering in which instances are to be inserted into the instance base can also be specified, make sure that #Random is selected and thereafter close the form by selecting OK. The newly created and trained classifier will be shown in the list of objects.") NORMAL (L"To estimate how well the classifier can be expected to classify new samples of Irises select ##Query -# \\=> ##Get accuracy estimate...#. A form prompting for %%k%NN parameter settings and evaluation method will be shown. Experiment with the parameter settings until satisfactory results are achieved. If everything worked out the estimate will likely end up somewhere in the range of 94-98 percent.") NORMAL (L"An alternative to manually experimenting with model parameters is to let the computer do the job. This is done be choosing the @KNN object and thereafter selecting ##Query -# \\=> ##Get optimized parameters...#. The form shown prompts for a selection of parameters controlling the search. The default values will in most cases, including this, be appropriate.") NORMAL (L"Another way of improving classification accuracy is to transform the instance space in which the individual instances, in this case Irises, are stored as to maximize the distance between instances of different classes and minimize the distance between instances of the same class. This can be done by means of feature weighting. To do so select the @KNN object and choose ##To FeatureWeights...#. Adjust the %%k%NN settings according to the ones found by the model search algorithm and let the remaining options retain the default values. Click OK. A @FeatureWeights object will be added to the objects list. The feature weights contained within the newly created object can be used by selecting named object in conjunction with the @KNN classifier and thereafter choosing the desired action.") MAN_END MAN_BEGIN (L"k-means clustering", L"Ola Söder", 20080529) INTRO (L"This tutorial describes the use of %%k%-means clustering in Praat. ") NORMAL (L"@@k-means clustering 1. How does k-means clustering work?|1. How does k-means clustering work?@") NORMAL (L"@@k-means clustering 2. Quick start|2. Quick start@") MAN_END MAN_BEGIN (L"k-means clustering 1. How does k-means clustering work?", L"Ola Söder", 20080529) NORMAL (L"The %%k%-means clustering algorithm attempts to split a given anonymous data set (a set containing no information as to class identity) into a fixed number (%k) of clusters.") NORMAL (L"Initially %k number of so called %centroids are chosen. A %centroid is a data point (imaginary or real) at the center of a cluster. In Praat each centroid is an existing data point in the given input data set, picked at random, such that all %centroids are unique (that is, for all %centroids %c__%i_ and %c__%j_, %c__%i_ \\=/ %c__%j_). These %centroids are used to train a @@kNN classifiers 1. What is a kNN classifier?|kNN classifier@. The resulting classifier is used to classify (using %k = 1) the data and thereby produce an initial randomized set of clusters. Each %centroid is thereafter set to the arithmetic mean of the cluster it defines. The process of classification and %centroid adjustment is repeated until the values of the %centroids stabilize. The final %centroids will be used to produce the final classification/clustering of the input data, effectively turning the set of initially anonymous data points into a set of data points, each with a class identity.") MAN_END MAN_BEGIN (L"k-means clustering 2. Quick start", L"Ola Söder", 20080529) NORMAL (L"Clustering using the %%k%-means clustering algorithm in Praat is done by selecting a @Pattern and choosing ##To Categories...#. In the appearing requester the number of sought after clusters (unique categories) can be specified. The cluster size ratio constraint (%z) imposes a constraint on the output such that %cluster size(%x) / %cluster size(%y) > %z for all clusters %x and %y in the resulting set of clusters. Valid values of %z are 0 < %z <= 1 where values near 0 imposes practically no constraints on the cluster sizes and a value of 1 tells the algorithm to attempt to create clusters of equal size. The size ratio constraint is enforced in a very naive fashion, by random reseeding. Since this can be a rather time consuming process it is possible to set an upper bound on the number of reseeds done by the algorithm. This upper bound is defined by the parameter ##Maximum number of reseeds#. It should be noted however that normally there's no need to use the size ratio constraint, selecting the desired number of clusters will, on average, result in clusters of roughly equal size, given well distributed data.") MAN_END MAN_BEGIN (L"Pattern to Dissimilarity", L"Ola Söder", 20080529) NORMAL (L"A @Dissimilarity matrix can be used in conjunction with @@Multidimensional scaling|Multidimensional scaling@ to aid visualization of high-dimensional data. A @Dissimilarity object is a matrix of the distances, according to the chosen @@Euclidean distance|distance function@, between all the data points in the @Pattern object.") NORMAL (L"A @Dissimilarity object can be created by selecting a @Pattern object and choosing ##To Dissimilarity#. The dissimilarity matrix can also be computed using feature weights. This is done by selecting a @Pattern object, an @FeatureWeights object and choosing ##To Dissimilarity#.") MAN_END MAN_BEGIN (L"Euclidean distance", L"Ola Söder", 20080529) NORMAL (L"The Euclidean distance between the %n-dimensional vectors %a and %b can be calculated as follows:") FORMULA (L"\\De__Euclidean_(%x,%y) = \\Vr(\\su__%i=1..%n_(%a__%i_ - %b__%I_)^2)") MAN_END MAN_BEGIN (L"kNN classifiers 3. Command overview", L"Ola Söder", 20080809 ) INTRO (L"KNN commands") ENTRY (L"Creation:") LIST_ITEM (L"\\bu @@Pattern & Categories: To KNN classifier...@") LIST_ITEM (L"\\bu @@Create KNN...@") ENTRY (L"Learning:") LIST_ITEM (L"\\bu @@KNN & Pattern & Categories: Learn...@") ENTRY (L"Classification:") LIST_ITEM (L"\\bu @@KNN & Pattern: To Categories...@") LIST_ITEM (L"\\bu @@KNN & Pattern: To TabelOfReal...@") LIST_ITEM (L"\\bu @@KNN & Pattern & FeatureWeights: To Categories...@") LIST_ITEM (L"\\bu @@KNN & Pattern & FeatureWeights: To TableOfReal...@") ENTRY (L"Evaluation:") LIST_ITEM (L"\\bu @@KNN & Pattern & Categories: Evaluate...@") LIST_ITEM (L"\\bu @@KNN & Pattern & Categories & FeatureWeights: Evaluate...@") ENTRY (L"Queries") LIST_ITEM (L"\\bu @@KNN: Get optimized parameters...@") LIST_ITEM (L"\\bu @@KNN: Get accuracy estimate...@") LIST_ITEM (L"\\bu @@KNN & FeatureWeights: Get accuracy estimate...@") LIST_ITEM (L"\\bu @@KNN: Get size of instance base@") ENTRY (L"Extractions") LIST_ITEM (L"\\bu @@KNN: Extract input Pattern@") LIST_ITEM (L"\\bu @@KNN: Extract output Categories@") ENTRY (L"Modification:") LIST_ITEM (L"\\bu @@KNN: Shuffle@") LIST_ITEM (L"\\bu @@KNN: Prune...@") LIST_ITEM (L"\\bu @@KNN: Reset...@") ENTRY (L"Miscellaneous:") LIST_ITEM (L"\\bu @@KNN: To FeatureWeights...@") LIST_ITEM (L"\\bu @@KNN & Pattern & Categories: To FeatureWeights...@") LIST_ITEM (L"\\bu @@Pattern & Categories: To FeatureWeights...@") ENTRY (L"Pre/post processing:") LIST_ITEM (L"\\bu @@Pattern: To Categories...@") LIST_ITEM (L"\\bu @@Pattern & FeatureWeights: To Categories...@") LIST_ITEM (L"\\bu @@Pattern: To Dissimilarity...@") LIST_ITEM (L"\\bu @@Pattern & FeatureWeights: To Dissimilarity...@") MAN_END MAN_BEGIN (L"Pattern & Categories: To KNN classifier...", L"Ola Söder", 20080726 ) INTRO (L"Create and train a @KNN classifier using the selected @Pattern and @Categories objects as training data.") ENTRY (L"Settings") TAG (L"##Name")\ DEFINITION (L"The name of the @KNN classifier.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") LIST_ITEM (L"@@kNN classifiers 1. What is a kNN classifier?@") MAN_END MAN_BEGIN (L"Create KNN...", L"Ola Söder", 20080718 ) INTRO (L"Create a new @KNN classifier.") ENTRY (L"Settings") TAG (L"##Name") DEFINITION (L"The name of the classifier.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN & Pattern & Categories: Learn...", L"Ola Söder", 20080726 ) INTRO (L"Train the selected @KNN classifier using the chosen @Pattern and @Categories objects as training data.") ENTRY (L"Settings") TAG (L"##Name") DEFINITION (L"The name of the classifier.") TAG (L"##Ordering") DEFINITION (L"The order in which the training instances are to be inserted into the instance base.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") LIST_ITEM (L"@@kNN classifiers 1. What is a kNN classifier?@") MAN_END MAN_BEGIN (L"KNN & Pattern: To Categories...", L"Ola Söder", 20080726 ) INTRO (L"Use the selected @KNN classifier to classify the chosen @Pattern. A @Categories object containing the result will be created.") ENTRY (L"Settings") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") LIST_ITEM (L"@@kNN classifiers 1. What is a kNN classifier?@") MAN_END MAN_BEGIN (L"KNN & Pattern: To TabelOfReal...", L"Ola Söder", 20080718 ) INTRO (L"Use the selected @KNN classifier to classify the chosen @Pattern. A @TableOfReal object containing verbose information on the decision process will be created.") ENTRY (L"Settings") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") TAG (L"##Output") DEFINITION (L"Specifies the degree of verbosity, where %%winners only% generates a @TableOfReal containing information on the instances of the winning category only whereas %%All candidates% results in a @TableOfReal with verbose information on all unique categories in the neighbourhood defined by the parameter %k.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") LIST_ITEM (L"@@kNN classifiers 1. What is a kNN classifier?@") MAN_END MAN_BEGIN (L"KNN & Pattern & FeatureWeights: To Categories...", L"Ola Söder", 20080726 ) INTRO (L"Use the selected @KNN classifier and @FeatureWeights object to classify the chosen @Pattern. A @Categories object containing the result will be created.") ENTRY (L"Settings") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.1.1. Filter-based feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.1.2. Wrapper-based feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1. Improving classification accuracy@") LIST_ITEM (L"@@kNN classifiers 1. What is a kNN classifier?@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN & Pattern & FeatureWeights: To TableOfReal...", L"Ola Söder", 20080718 ) INTRO (L"Use the selected @KNN classifier and the feature weights, @FeatureWeights, to classify the chosen @Pattern. A @TableOfReal object containing verbose information on the decision process will be created.") ENTRY (L"Settings") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") TAG (L"##Output") DEFINITION (L"Specifies the degree of verbosity, where %%winners only% generates a @TableOfReal containing information on the instances of the winning category only whereas %%All candidates% results in a @TableOfReal with verbose information on all unique categories in the neighbourhood defined by the parameter %k.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.1.1. Filter-based feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.1.2. Wrapper-based feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1. Improving classification accuracy@") LIST_ITEM (L"@@kNN classifiers 1. What is a kNN classifier?@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN: Get optimized parameters...", L"Ola Söder", 20080718 ) INTRO (L"Perform an automated search for the optimal @KNN parameter settings.") ENTRY (L"Settings") TAG (L"##Evaluation method") DEFINITION (L"The method to be used for estimating the classification accuracy, which in turn is used to guide the model search. " "Supported methods are 10-fold cross-validation and leave-one-out.") TAG (L"##k max") DEFINITION (L"The maximum value of the parameter %k.") TAG (L"##Number of seeds") DEFINITION (L"The size of the parameter neighbourhood to be searched.") TAG (L"##Learning rate") DEFINITION (L"The rate at which the parameter neighbourhood is shrunk (per iteration).") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers 1.1.2. Model selection@") LIST_ITEM (L"@@kNN classifiers 1.1. Improving classification accuracy@") LIST_ITEM (L"@@kNN classifiers 1. What is a kNN classifier?@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN: Get accuracy estimate...", L"Ola Söder", 20080718 ) INTRO (L"Estimate the classification accuracy of the selected @KNN classifier.") ENTRY (L"Settings") TAG (L"##Evaluation method") DEFINITION (L"The method to be used for estimating the classification accuracy. Supported methods are 10-fold cross-validation and leave-one-out.") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") ENTRY (L"See also:") LIST_ITEM (L"@@KNN & FeatureWeights: Get accuracy estimate...@") LIST_ITEM (L"@@KNN & Pattern & Categories: Evaluate...@") LIST_ITEM (L"@@KNN & Pattern & Categories & FeatureWeights: Evaluate...@") LIST_ITEM (L"@@kNN classifiers 1.1. Improving classification accuracy@") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.2. Model selection@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN & FeatureWeights: Get accuracy estimate...", L"Ola Söder", 20080809) INTRO (L"Estimate the classification accuracy of the @KNN classifier using the chosen @FeatureWeights.") ENTRY (L"Settings") TAG (L"##Evaluation method") DEFINITION (L"The method to be used for estimating the classification accuracy. " "Supported methods are 10-fold cross-validation and leave-one-out.") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") ENTRY (L"See also:") LIST_ITEM (L"@@KNN & Pattern & Categories: Evaluate...@") LIST_ITEM (L"@@KNN & Pattern & Categories & FeatureWeights: Evaluate...@") LIST_ITEM (L"@@kNN classifiers 1.1. Improving classification accuracy@") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.2. Model selection@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN & Pattern & Categories: Evaluate...", L"Ola Söder", 20080718) INTRO (L"Estimate the classification accuracy of the chosen @KNN classifier using the selected @Pattern and @Categories objects as test set.") ENTRY (L"Settings") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") ENTRY (L"See also:") LIST_ITEM (L"@@KNN & Pattern & Categories & FeatureWeights: Evaluate...@") LIST_ITEM (L"@@KNN: Get accuracy estimate...@") LIST_ITEM (L"@@kNN classifiers 1.1. Improving classification accuracy@") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.2. Model selection@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN & Pattern & Categories & FeatureWeights: Evaluate...", L"Ola Söder", 20080718) INTRO (L"Estimate the classification accuracy of the chosen @KNN classifier using the selected @Pattern and @Categories objects as test set. The selected @FeatureWeights object will be used in the classification process.") ENTRY (L"Settings") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") ENTRY (L"See also:") LIST_ITEM (L"@@KNN & Pattern & Categories: Evaluate...@") LIST_ITEM (L"@@KNN: Get accuracy estimate...@") LIST_ITEM (L"@@kNN classifiers 1.1. Improving classification accuracy@") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.2. Model selection@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN: Get size of instance base", L"Ola Söder", 20080718) INTRO (L"Queries the selected @KNN for the number of instances in the instance base. ") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN: Extract input Pattern", L"Ola Söder", 20080726) INTRO (L"Create a new @Pattern object identical to the one in the instance base of the selected @KNN classifier.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN: Extract output Categories", L"Ola Söder", 20080726) INTRO (L"Create a new @Categories object identical to the one in the instance base of the selected @KNN classifier.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN: Shuffle", L"Ola Söder", 20080718) INTRO (L"Shuffle the instance base of the selected classifier.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN: Prune...", L"Ola Söder", 20080718) INTRO (L"Prune the instance base of the selected classifier.") ENTRY (L"Settings") TAG (L"##Noise pruning degree") DEFINITION (L"A value in the range [0 ... 1] specifying the probability that instances tagged as noisy by @@kNN classifiers 1.2.1. Pruning|the C-Pruner algorithm@ will be pruned.") TAG (L"##Redundancy pruning degree") DEFINITION (L"The probability that instances tagged as redundant by @@kNN classifiers 1.2.1. Pruning|the C-Pruner algorithm@ will be pruned.") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers 1.2.1. Pruning@") LIST_ITEM (L"@@kNN classifiers 1.2. Improving resource efficiency@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN: Reset...", L"Ola Söder", 20080718) INTRO (L"Empty the instance base of the selected classifier.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN: To FeatureWeights...", L"Ola Söder", 20080728) INTRO (L"Wrap the selected @KNN and use its feedback to guide the search for the optimal feature weights. A @FeatureWeights object will be created.") ENTRY (L"Settings") TAG (L"##Learning rate") DEFINITION (L"The rate at which the maximum distance between the pivot and a random seed is decremented.") TAG (L"##Number of seeds") DEFINITION (L"The size of the feature weight neighbourhood.") TAG (L"##Stop at") DEFINITION (L"A value specifying a stopping criterion. When feature weights yielding accuracy estimates higher than the specified value the search will stop. A value of 1 imposes no constraints whereas a value of 0.5 will result in the termination of the search algorithm once feature weights resulting in an classification accuracy of 50 percent or better are found.") TAG (L"##Optimization") DEFINITION (L"Specifies whether to search for all features simultaneously or one at a time.") TAG (L"##Evaluation method") DEFINITION (L"The method to be used for estimating the classification accuracy. Supported methods are 10-fold cross-validation and leave-one-out.") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood used for feedback classification.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers 1.1.1.2. Wrapper-based feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1. Improving classification accuracy@") LIST_ITEM (L"@@KNN & Pattern & Categories & FeatureWeights: Evaluate...@") LIST_ITEM (L"@@kNN classifiers 1. What is a kNN classifier?@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"KNN & Pattern & Categories: To FeatureWeights...", L"Ola Söder", 20080809) INTRO (L"Wrap the selected @KNN and use its classification accuracy on the test set constituted by the @Pattern and @Categories objects as feedback to guide the search for the optimal feature weights. A @FeatureWeights object will be created.") ENTRY (L"Settings") TAG (L"##Learning rate") DEFINITION (L"The rate at which the maximum distance between the pivot and a random seed is decremented.") TAG (L"##Number of seeds") DEFINITION (L"The size of the feature weight neighbourhood.") TAG (L"##Stop at") DEFINITION (L"A value specifying a stopping criterion. When feature weights yielding accuracy estimates higher than the specified value the search will stop. A value of 1 imposes no constraints whereas a value of 0.5 will result in the termination of the search algorithm once feature weights resulting in an classification accuracy of 50 percent or better are found.") TAG (L"##Optimization") DEFINITION (L"Specifies whether to search for all features simultaneously or one at a time.") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood used for feedback classification.") TAG (L"##Vote weighting") DEFINITION (L"The type of vote weighting to be used.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers 1.1.1.2. Wrapper-based feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1. Improving classification accuracy@") LIST_ITEM (L"@@KNN & Pattern & Categories & FeatureWeights: Evaluate...@") LIST_ITEM (L"@@kNN classifiers 1. What is a kNN classifier?@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"Pattern & Categories: To FeatureWeights...", L"Ola Söder", 20080809) INTRO (L"Compute an estimate of the optimal feature weights using the @@kNN classifiers 1.1.1.1. Filter-based feature weighting|RELIEF-F algorithm@.") ENTRY (L"Setting") TAG (L"##k neighbours") DEFINITION (L"The size of the neighbourhood.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers 1.1.1.1. Filter-based feature weighting@") LIST_ITEM (L"@@kNN classifiers 1.1.1.2. Wrapper-based feature weighting@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"Pattern: To Categories...", L"Ola Söder", 20080728) INTRO (L"Split the given @Pattern into a fixed number of clusters using the @@k-means clustering|%%k%-means clustering algorithm@. A @Categories object containing numbered categories corresponding to the generated clusters will be created.") ENTRY (L"Settings") TAG (L"##k clusters") DEFINITION (L"The number of clusters to be generated.") TAG (L"##Cluster size ratio constraint") DEFINITION (L"The minimum allowed ratio between the smallest and the biggest cluster.") TAG (L"##Maximum number of reseeds") DEFINITION (L"The maximum allowed number of reseeds used to enforce the cluster size ratio constraint.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"Pattern & FeatureWeights: To Categories...", L"Ola Söder", 20080728) INTRO (L"Split the given @Pattern into a fixed number of clusters using the @@k-means clustering|%%k%-means clustering algorithm@ and the feature weights contained within the selected @FeatureWeights object. A @Categories object containing numbered categories corresponding to the generated clusters will be created.") ENTRY (L"Settings") TAG (L"##k clusters") DEFINITION (L"The number of clusters to be generated.") TAG (L"##Cluster size ratio constraint") DEFINITION (L"The minimum allowed ratio between the smallest and the biggest cluster.") TAG (L"##Maximum number of reseeds") DEFINITION (L"The maximum allowed number of reseeds used to enforce the cluster size ratio constraint.") ENTRY (L"See also:") LIST_ITEM (L"@@kNN classifiers@") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") MAN_END MAN_BEGIN (L"Pattern: To Dissimilarity...", L"Ola Söder", 20080718) INTRO (L"Generate a @Dissimilarity matrix from the selected @Pattern. Dissimilarities are computed using the @@Euclidean distance@") ENTRY (L"See also:") LIST_ITEM (L"@@Multidimensional scaling@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"Pattern & FeatureWeights: To Dissimilarity...", L"Ola Söder", 20080718) INTRO (L"Generate a @Dissimilarity matrix from the selected @Pattern using the feature weights contained within the selected @FeatureWeights object. Dissimilarities are computed using the @@Euclidean distance@.") ENTRY (L"See also:") LIST_ITEM (L"@@Multidimensional scaling@") LIST_ITEM (L"@@kNN classifiers 1.1.1. Feature weighting@") LIST_ITEM (L"@@kNN classifiers@") MAN_END MAN_BEGIN (L"Ke-Ping Zhao et al. (2003)", L"Ola Söder", 20080718) NORMAL (L"Ke-Ping Zhao et al. (2003): \"C-Pruner: An improved instance pruning algorithm.\" " "In %%Proceedings of the Second International Conference on Machine Learning and Cybernetics%, November 2003, 94\\--99.") MAN_END MAN_BEGIN (L"Igor Kononenko (1994)", L"Ola Söder", 20080718) NORMAL (L"Igor Kononenko (1994): \"Estimating attributes: Analysis and extensions of relief.\" " "In %%ECML-94: Proceedings of the European Conference on Machine Learning%, Secaucus, NJ, USA, 171\\--182. " "New York: Springer.") MAN_END } /* End of file manual_KNN.c */ sources_5316/contrib/ola/OlaP.h0000644000176700017670000000267511141127454015154 0ustar paulpaul#ifndef _OlaP_h_ #define _OlaP_h_ /* OlaP.h * * Copyright (C) 2007-2008 Ola Söder * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 20080529 Initial release */ ///////////////////////////////////////// // Macros // ///////////////////////////////////////// #define OlaSWAP(TYPE, X, Y) {TYPE temp = X; X = Y; Y = temp;} #define OlaMAX(x,y) ((x) > (y) ? (x) : (y)) #define OlaMIN(x,y) ((x) < (y) ? (x) : (y)) #define OlaSQUARE(x) ((x) * (x)) ///////////////////////////////////////// // DEBUG // ///////////////////////////////////////// ///////////////////////////////////////// // Misc defines // ///////////////////////////////////////// #define kOla_MINFLOAT 0.0000000000000000000001 #endif /* _Misc_h_ */ sources_5316/contrib/ola/KNN_threads.h0000644000176700017670000000277511614422044016460 0ustar paulpaul#ifndef _KNN_threads_h_ #define _KNN_threads_h_ /* KNN_threads.h * * Copyright (C) 2009 Ola Söder * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 20090123 First version * pb 2011/03/08 C++ */ ///////////////////////////////////////////////////// // // ///////////////////////////////////////////////////// // Error codes enum KNN_thread_status { KNN_THREAD_OK, KNN_THREAD_ERROR }; // Query the number of available CPUs int KNN_getNumberOfCPUs(void); // Distribute the work specified by // (*function) and input over nthreads // threads void * KNN_threadDistribution ( void * (* function) (void *), void ** input, int nthreads ); // Test threading void KNN_threadTest(void); // Test threading aux void * KNN_threadTestAux ( void * dummy ); /* End of file KNN_threads.h */ #endif sources_5316/contrib/ola/KNN_prune.cpp0000644000176700017670000001770011604346060016506 0ustar paulpaul/* KNN_prune.cpp * * Copyright (C) 2007-2008 Ola So"der, 2010-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 2007/05/29 Initial release * os 2009/01/23 Bugfix: Rejects classifiers containing 0 or 1 instances * pb 2010/06/06 removed some array-creations-on-the-stack * pb 2011/04/14 C++ * pb 2011/04/16 removed memory leaks */ #include "KNN_prune.h" ///////////////////////////////////////////////////////////////////////////////////////////// // Prune // ///////////////////////////////////////////////////////////////////////////////////////////// long KNN_prune_prune ( KNN me, // the classifier to be pruned double n, // pruning degree: noise, 0 <= n <= 1 double r, // pruning redundancy: noise, 0 <= n <= 1 long k // k(!) ) { autoCategories uniqueCategories = Categories_selectUniqueItems (my output, 1); if (Categories_getSize (uniqueCategories.peek()) == my nInstances) return 0; long removals = 0; long ncandidates = 0; autoNUMvector candidates (0L, my nInstances - 1); if (my nInstances <= 1) return 0; for (long y = 1; y <= my nInstances; y ++) { if (KNN_prune_noisy (my input, my output, y, k)) { if (n == 1 || NUMrandomUniform (0, 1) <= n) { KNN_removeInstance (me, y); ++ removals; } } } for (long y = 1; y <= my nInstances; ++ y) { if (KNN_prune_superfluous (my input, my output, y, k, 0) && ! KNN_prune_critical (my input, my output, y, k)) candidates [ncandidates ++] = y; } KNN_prune_sort (my input, my output, k, candidates.peek(), ncandidates); for (long y = 0; y < ncandidates; ++ y) { if (KNN_prune_superfluous (my input, my output, candidates [y], k, 0) && ! KNN_prune_critical (my input, my output, candidates [y], k)) { if (r == 1 || NUMrandomUniform (0, 1) <= r) { KNN_removeInstance (me, candidates[y]); for (long i = y + 1; i < ncandidates; ++ i) { if(candidates[i] > candidates[y]) -- candidates[i]; } ++ removals; } } } return removals; } ///////////////////////////////////////////////////////////////////////////////////////////// // sort indices according to pruning order defined by rule 2 // ///////////////////////////////////////////////////////////////////////////////////////////// void KNN_prune_sort ( Pattern p, // source Categories c, // source long k, // k(!) long * indices, // indices of instances to be sorted long nindices // the number of instances to be sorted ) { long n = nindices; autoNUMvector h (0L, nindices - 1); for (long cc = 0; cc < nindices; ++ cc) h [cc] = KNN_friendsAmongkNeighbours (p, p, c, indices [cc], k); while (-- n) { // insertion-sort, is heap-sort worth the effort? for (long m = n; m < nindices - 1; m ++) { if (h [m - 1] > h[m]) break; if (h [m - 1] < h[m]) { OlaSWAP (long, indices [m - 1], indices [m]); } else { if (KNN_nearestEnemy (p, p, c, indices [m - 1]) < KNN_nearestEnemy (p, p, c, indices [m])) { OlaSWAP (long, indices [m - 1], indices [m]); } else { if (NUMrandomUniform (0, 1) > 0.5) { OlaSWAP (long, indices [m - 1], indices [m]); } } } } } } ///////////////////////////////////////////////////////////////////////////////////////////// // k-coverage // ///////////////////////////////////////////////////////////////////////////////////////////// long KNN_prune_kCoverage ( Pattern p, // source Categories c, // source long y, // source instance index long k, // k(!) long * indices // Out: kCoverage set ) { Melder_assert (y <= p->ny); Melder_assert (k > 0 && k <= p->ny); long cc = 0; autoFeatureWeights fws = FeatureWeights_create (p -> nx); autoNUMvector tempindices (0L, p -> ny - 1); for (long yy = 1; yy <= p -> ny; yy++) { if (y != yy && FeatureWeights_areFriends ((SimpleString) c -> item [y], (SimpleString) c -> item [yy])) { long n = KNN_kNeighboursSkip (p, p, fws.peek(), yy, k, tempindices.peek(), y); while (n) { Melder_assert (n <= p -> ny); if (tempindices [-- n] == y) { indices [cc ++] = yy; break; } } } } return cc; } ///////////////////////////////////////////////////////////////////////////////////////////// // testing for superfluousness // ///////////////////////////////////////////////////////////////////////////////////////////// int KNN_prune_superfluous ( Pattern p, // source Categories c, // source long y, // source instance index long k, // k(!) long skipper // Skipping instance skipper ) { if (y > p -> ny) y = p -> ny; // safety belt if (k > p -> ny) k = p -> ny; autoFeatureWeights fws = FeatureWeights_create (p -> nx); autoNUMvector indices (0L, k - 1); autoNUMvector freqindices (0L, k - 1); autoNUMvector distances (0L, k - 1); autoNUMvector freqs (0L, k - 1); if (! KNN_kNeighboursSkip (p, p, fws.peek(), y, k, indices.peek(), skipper)) return 0; long ncategories = KNN_kIndicesToFrequenciesAndDistances (c, k, indices.peek(), distances.peek(), freqs.peek(), freqindices.peek()); int result = FeatureWeights_areFriends ((SimpleString) c -> item [y], (SimpleString) c -> item [freqindices [KNN_max (freqs.peek(), ncategories)]]); if (result) return 1; return 0; } ///////////////////////////////////////////////////////////////////////////////////////////// // testing for criticalness // ///////////////////////////////////////////////////////////////////////////////////////////// int KNN_prune_critical ( Pattern p, // source Categories c, // source long y, // source instance index long k // k(!) ) { if (y > p -> ny) y = p -> ny; // safety belt if (k > p -> ny) k = p -> ny; autoFeatureWeights fws = FeatureWeights_create (p -> nx); autoNUMvector indices (0L, k - 1); long ncollected = KNN_kNeighboursSkip (p, p, fws.peek(), y, k, indices.peek(), y); for (long ic = 0; ic < ncollected; ic ++) { if (! KNN_prune_superfluous (p, c, indices [ic], k, 0) || ! KNN_prune_superfluous (p, c, indices [ic], k, y)) { return 1; } } return 0; } ///////////////////////////////////////////////////////////////////////////////////////////// // testing for noisyness // ///////////////////////////////////////////////////////////////////////////////////////////// int KNN_prune_noisy ( Pattern p, // source Categories c, // source long y, // source instance index long k // k(!) ) { if (y > p -> ny) y = p -> ny; // safety belt if (k > p -> ny) k = p -> ny; autoFeatureWeights fws = FeatureWeights_create (p -> nx); autoNUMvector indices (0L, p->ny - 1); // the coverage is not bounded by k but by n long reachability = KNN_kNeighboursSkip (p, p, fws.peek(), y, k, indices.peek(), y); long coverage = KNN_prune_kCoverage (p, c, y, k, indices.peek()); if (! KNN_prune_superfluous (p, c, y, k, 0) && reachability > coverage) return 1; return 0; } /* End of file KNN_prune.cpp */ sources_5316/contrib/ola/ChangeLog.txt0000644000176700017670000000211311223204660016517 0ustar paulpaul-------------------- libOla.a - ChangeLog -------------------- 2008-05-29 * Initial release 2008-08-10 * Bugfixes * Merging with the upstream version of Praat 2008-10-01 * Bugfix: C-Pruner now rejects instance bases of sizes <= 1 * Multithreaded kNN-classification implemented (Linux only) 2009-01-23 * Bugfix: KNN_learn(...) MUX:ing removed; broke scripting * Bugfix: KNN serialization fixed (using the proper version ID) * Removed redundant information from the manual * The TableOfReal output of the KNN classifier now mimics the format of the corresponding output of the FFNet classifier. 2009-01-31 * kNN-classifier no longer executes in a thread of its own * on single-CPU machines 2009-07-02 * Threading disabled on all plattforms * Bugfix: The k-means clustering routine no longer attempts to create clusters when k > number of patterns by means of reseeding. * Bugfix: Inadequate checking of input data in the C-Pruner routine resulting in rare crashes fixed. sources_5316/contrib/ola/KNN.cpp0000644000176700017670000015757211724373741015322 0ustar paulpaul/* KNN.cpp * * Copyright (C) 2008 Ola So"der, 2010-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 2008/05/29 initial release * pb 2010/06/06 removed some array-creations-on-the-stack * pb 2011/04/12 C++ * pb 2011/04/13 removed several memory leaks * pb 2011/07/07 some exception safety */ #include "KNN.h" #include "KNN_threads.h" #include "OlaP.h" #include "oo_DESTROY.h" #include "KNN_def.h" #include "oo_COPY.h" #include "KNN_def.h" #include "oo_EQUAL.h" #include "KNN_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "KNN_def.h" #include "oo_WRITE_TEXT.h" #include "KNN_def.h" #include "oo_WRITE_BINARY.h" #include "KNN_def.h" #include "oo_READ_TEXT.h" #include "KNN_def.h" #include "oo_READ_BINARY.h" #include "KNN_def.h" #include "oo_DESCRIPTION.h" #include "KNN_def.h" Thing_implement (KNN, Data, 0); ///////////////////////////////////////////////////////////////////////////////////////////// // Praat specifics // ///////////////////////////////////////////////////////////////////////////////////////////// void structKNN :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Size of instancebase: ", Melder_integer (nInstances)); } ///////////////////////////////////////////////////////////////////////////////////////////// // Creation // ///////////////////////////////////////////////////////////////////////////////////////////// KNN KNN_create () { try { autoKNN me = Thing_new (KNN); my nInstances = 0; return me.transfer(); } catch (MelderError) { Melder_throw ("KNN classifier not created."); } } ///////////////////////////////////////////////////////////////////////////////////////////// // Learning // ///////////////////////////////////////////////////////////////////////////////////////////// int KNN_learn ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // the classifier to be trained // Pattern p, // source pattern // Categories c, // target categories // int method, // method <- REPLACE or APPEND // int ordering // ordering <- SHUFFLE? ) { if (c->size == p->ny) // the number of input vectors must { // equal the number of categories. switch (method) { case kOla_REPLACE: // in REPLACE mode simply // dispose of the current if (my nInstances > 0) // instance base and store { // the new one. forget (my input); forget (my output); } my input = (Pattern) Data_copy (p); // LEAK my output = (Categories) Data_copy (c); my nInstances = c->size; break; case kOla_APPEND: // in APPEND mode a new // instance base is formed // by merging the new and // the old. // if (p->nx == (my input)->nx) // the number of features // of the old and new // instance base must // match; otherwise merging // won't be possible. { /* * Create without change. */ autoPattern tinput = (Pattern) Matrix_appendRows (my input, p, classPattern); autoCategories toutput = (Categories) Collections_merge (my output, c); /* * Change without error. */ forget (my input); forget (my output); my input = tinput.transfer(); my output = toutput.transfer(); my nInstances += p->ny; } else // fail { return kOla_DIMENSIONALITY_MISMATCH; } break; } if (ordering == kOla_SHUFFLE) // shuffle the instance base { KNN_shuffleInstances(me); } } else // fail { return kOla_PATTERN_CATEGORIES_MISMATCH; } return kOla_SUCCESS; // success } ///////////////////////////////////////////////////////////////////////////////////////////// // Classification - To Categories // ///////////////////////////////////////////////////////////////////////////////////////////// typedef struct { KNN me; Pattern ps; long * output; FeatureWeights fws; long k; int dist; long istart; long istop; } KNN_input_ToCategories_t; Categories KNN_classifyToCategories ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // the classifier being used // Pattern ps, // the pattern to classify // FeatureWeights fws, // feature weights // long k, // the number of sought after neighbours // int dist // distance weighting ) { int nthreads = KNN_getNumberOfCPUs(); long *outputindices = NUMvector (0, ps->ny); long chunksize = ps->ny / nthreads; Melder_assert(nthreads > 0); Melder_assert(k > 0 && k <= my nInstances); if(chunksize < 1) { chunksize = 1; nthreads = ps->ny; } long istart = 1; long istop = chunksize; Categories output = Categories_create(); KNN_input_ToCategories_t ** input = (KNN_input_ToCategories_t **) malloc(nthreads * sizeof(KNN_input_ToCategories_t *)); if(!input) return(NULL); for(int i = 0; i < nthreads; ++i) { input[i] = (KNN_input_ToCategories_t *) malloc(sizeof(KNN_input_ToCategories_t)); if(!input[i]) { while(input[i--]) free(input[i]); free(input); return(NULL); } } for(int i = 0; i < nthreads; ++i) { input[i]->me = me; input[i]->ps = ps; input[i]->output = outputindices; input[i]->fws = fws; input[i]->k = k; input[i]->dist = dist; input[i]->istart = istart; if(istop + chunksize > ps->ny) { input[i]->istop = ps->ny; break; } else { input[i]->istop = istop; istart = istop + 1; istop += chunksize; } } enum KNN_thread_status * error = (enum KNN_thread_status *) KNN_threadDistribution(KNN_classifyToCategoriesAux, (void **) input, nthreads); //void *error = KNN_classifyToCategoriesAux (input [0]); for (int i = 0; i < nthreads; ++ i) free (input [i]); free (input); if (error) // Something went very wrong, you ought to inform the user! { free (error); return NULL; } if (output) { for (long i = 1; i <= ps->ny; ++i) Collection_addItem (output, Data_copy ((SimpleString) my output -> item [outputindices [i]])); } NUMvector_free (outputindices, 0); return output; } void * KNN_classifyToCategoriesAux ( /////////////////////////////// // Parameters // /////////////////////////////// void * input ) { Melder_assert(((KNN_input_ToCategories_t *) input)->istart > 0 && ((KNN_input_ToCategories_t *) input)->istop > 0 && ((KNN_input_ToCategories_t *) input)->istart <= ((KNN_input_ToCategories_t *) input)->ps->ny && ((KNN_input_ToCategories_t *) input)->istop <= ((KNN_input_ToCategories_t *) input)->ps->ny && ((KNN_input_ToCategories_t *) input)->istart <= ((KNN_input_ToCategories_t *) input)->istop); long ncollected; long ncategories; long *indices = NUMvector (0, ((KNN_input_ToCategories_t *) input)->k); long *freqindices = NUMvector (0, ((KNN_input_ToCategories_t *) input)->k); double *distances = NUMvector (0, ((KNN_input_ToCategories_t *) input)->k); double *freqs = NUMvector (0, ((KNN_input_ToCategories_t *) input)->k); for (long y = ((KNN_input_ToCategories_t *) input)->istart; y <= ((KNN_input_ToCategories_t *) input)->istop; ++y) { ///////////////////////////////////////// // Localizing the k nearest neighbours // ///////////////////////////////////////// ncollected = KNN_kNeighbours ( ((KNN_input_ToCategories_t *) input)->ps, ((KNN_input_ToCategories_t *) input)->me->input, ((KNN_input_ToCategories_t *) input)->fws, y, ((KNN_input_ToCategories_t *) input)->k, indices, distances ); ///////////////////////////////////////////////// // Computing frequencies and average distances // ///////////////////////////////////////////////// ncategories = KNN_kIndicesToFrequenciesAndDistances ( ((KNN_input_ToCategories_t *) input)->me->output, ((KNN_input_ToCategories_t *) input)->k, indices, distances, freqs, freqindices ); //////////////////////// // Distance weighting // //////////////////////// switch(((KNN_input_ToCategories_t *) input)->dist) { case kOla_DISTANCE_WEIGHTED_VOTING: for (long c = 0; c < ncategories; ++c) freqs[c] *= 1 / OlaMAX(distances[c], kOla_MINFLOAT); break; case kOla_SQUARED_DISTANCE_WEIGHTED_VOTING: for (long c = 0; c < ncategories; ++c) freqs[c] *= 1 / OlaMAX(OlaSQUARE(distances[c]), kOla_MINFLOAT); } KNN_normalizeFloatArray(freqs, ncategories); ((KNN_input_ToCategories_t *) input)->output[y] = freqindices[KNN_max(freqs, ncategories)]; } NUMvector_free (indices, 0); NUMvector_free (freqindices, 0); NUMvector_free (distances, 0); NUMvector_free (freqs, 0); return(NULL); } //////////////////////////////////////////////////////////////////////////////////////////// // Classification - To TableOfReal // ///////////////////////////////////////////////////////////////////////////////////////////// typedef struct { KNN me; Pattern ps; Categories uniqueCategories; TableOfReal output; FeatureWeights fws; long k; int dist; long istart; long istop; } KNN_input_ToTableOfReal_t; TableOfReal KNN_classifyToTableOfReal ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // the classifier being used // Pattern ps, // source Pattern // FeatureWeights fws, // feature weights // long k, // the number of sought after neighbours // int dist // distance weighting ) { int nthreads = KNN_getNumberOfCPUs(); long chunksize = ps->ny / nthreads; Categories uniqueCategories = Categories_selectUniqueItems(my output, 1); long ncategories = Categories_getSize(uniqueCategories); Melder_assert(nthreads > 0); Melder_assert(ncategories > 0); Melder_assert(k > 0 && k <= my nInstances); if(!ncategories) return(NULL); if(chunksize < 1) { chunksize = 1; nthreads = ps->ny; } long istart = 1; long istop = chunksize; KNN_input_ToTableOfReal_t ** input = (KNN_input_ToTableOfReal_t **) malloc(nthreads * sizeof(KNN_input_ToTableOfReal_t *)); if(!input) return(NULL); TableOfReal output = TableOfReal_create(ps->ny, ncategories); for (long i = 1; i <= ncategories; ++i) TableOfReal_setColumnLabel (output, i, SimpleString_c ((SimpleString) uniqueCategories->item[i])); for(int i = 0; i < nthreads; ++i) { input[i] = (KNN_input_ToTableOfReal_t *) malloc(sizeof(KNN_input_ToTableOfReal_t)); if(!input[i]) { while(input[i--]) free(input[i]); free(input); return(NULL); } } for(int i = 0; i < nthreads; ++i) { input[i]->me = me; input[i]->ps = ps; input[i]->output = output; input[i]->uniqueCategories = uniqueCategories; input[i]->fws = fws; input[i]->k = k; input[i]->dist = dist; input[i]->istart = istart; if(istop + chunksize > ps->ny) { input[i]->istop = ps->ny; break; } else { input[i]->istop = istop; istart = istop + 1; istop += chunksize; } } enum KNN_thread_status * error = (enum KNN_thread_status *) KNN_threadDistribution(KNN_classifyToTableOfRealAux, (void **) input, nthreads); for(int i = 0; i < nthreads; ++i) free(input[i]); free(input); if(error) // Something went very wrong, you ought to inform the user! { free(error); return(NULL); } return(output); } void * KNN_classifyToTableOfRealAux ( /////////////////////////////// // Parameters // /////////////////////////////// void * input ) { long ncategories = Categories_getSize (((KNN_input_ToTableOfReal_t *) input)->uniqueCategories); long *indices = NUMvector (0, ((KNN_input_ToTableOfReal_t *) input)->k); double *distances = NUMvector (0, ((KNN_input_ToTableOfReal_t *) input)->k); for (long y = ((KNN_input_ToTableOfReal_t *) input)->istart; y <= ((KNN_input_ToTableOfReal_t *) input)->istop; ++y) { KNN_kNeighbours(((KNN_input_ToTableOfReal_t *) input)->ps, ((KNN_input_ToTableOfReal_t *) input)->me->input, ((KNN_input_ToTableOfReal_t *) input)->fws, y, ((KNN_input_ToTableOfReal_t *) input)->k, indices, distances); for(long i = 0; i < ((KNN_input_ToTableOfReal_t *) input)->k; ++i) { for(long j = 1; j <= ncategories; ++j) if(FeatureWeights_areFriends ((SimpleString) ((KNN_input_ToTableOfReal_t *) input)->me->output->item[indices[i]], (SimpleString) ((KNN_input_ToTableOfReal_t *) input)->uniqueCategories->item[j])) ++((KNN_input_ToTableOfReal_t *) input)->output->data[y][j]; } } switch (((KNN_input_ToTableOfReal_t *) input)->dist) { case kOla_DISTANCE_WEIGHTED_VOTING: for (long y = ((KNN_input_ToTableOfReal_t *) input)->istart; y <= ((KNN_input_ToTableOfReal_t *) input)->istop; ++y) { double sum = 0; for(long c = 1; c <= ncategories; ++c) { ((KNN_input_ToTableOfReal_t *) input)->output->data[y][c] *= 1 / OlaMAX(distances[c], kOla_MINFLOAT); sum += ((KNN_input_ToTableOfReal_t *) input)->output->data[y][c]; } for(long c = 1; c <= ncategories; ++c) ((KNN_input_ToTableOfReal_t *) input)->output->data[y][c] /= sum; } break; case kOla_SQUARED_DISTANCE_WEIGHTED_VOTING: for (long y = ((KNN_input_ToTableOfReal_t *) input)->istart; y <= ((KNN_input_ToTableOfReal_t *) input)->istop; ++y) { double sum = 0; for(long c = 1; c <= ncategories; ++c) { ((KNN_input_ToTableOfReal_t *) input)->output->data[y][c] *= 1 / OlaMAX(OlaSQUARE(distances[c]), kOla_MINFLOAT); sum += ((KNN_input_ToTableOfReal_t *) input)->output->data[y][c]; } for(long c = 1; c <= ncategories; ++c) ((KNN_input_ToTableOfReal_t *) input)->output->data[y][c] /= sum; } break; case kOla_FLAT_VOTING: for (long y = ((KNN_input_ToTableOfReal_t *) input)->istart; y <= ((KNN_input_ToTableOfReal_t *) input)->istop; ++y) { double sum = 0; for(long c = 1; c <= ncategories; ++c) sum += ((KNN_input_ToTableOfReal_t *) input)->output->data[y][c]; for(long c = 1; c <= ncategories; ++c) ((KNN_input_ToTableOfReal_t *) input)->output->data[y][c] /= sum; } } NUMvector_free (indices, 0); NUMvector_free (distances, 0); return(NULL); } ////////////////////////////////////////////////////////////////////////////////////////////// // Classification - Folding // ///////////////////////////////////////////////////////////////////////////////////////////// Categories KNN_classifyFold ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // the classifier being used // Pattern ps, // source Pattern // FeatureWeights fws, // feature weights // long k, // the number of sought after neighbours // int dist, // distance weighting // long begin, // fold start, inclusive [... // long end // fold end, inclusive ...] // ) { Melder_assert(k > 0 && k <= ps->ny); Melder_assert(end > 0 && end <= ps->ny); Melder_assert(begin > 0 && begin <= ps->ny); if (begin > end) OlaSWAP(long, begin, end); if (k > my nInstances - (end - begin)) k = my nInstances - (end - begin); long ncollected; long ncategories; autoNUMvector indices (0L, k); autoNUMvector freqindices (0L, k); autoNUMvector distances (0L, k); autoNUMvector freqs (0L, k); autoNUMvector outputindices (0L, ps->ny); long noutputindices = 0; for (long y = begin; y <= end; ++y) { ///////////////////////////////////////// // Localizing the k nearest neighbours // ///////////////////////////////////////// ncollected = KNN_kNeighboursSkipRange (ps, my input, fws, y, k, indices.peek(), distances.peek(), begin, end); ///////////////////////////////////////////////// // Computing frequencies and average distances // ///////////////////////////////////////////////// ncategories = KNN_kIndicesToFrequenciesAndDistances (my output, k, indices.peek(), distances.peek(), freqs.peek(), freqindices.peek()); //////////////////////// // Distance weighting // //////////////////////// switch (dist) { case kOla_DISTANCE_WEIGHTED_VOTING: for (long c = 0; c < ncategories; c ++) freqs [c] *= 1 / OlaMAX (distances [c], kOla_MINFLOAT); break; case kOla_SQUARED_DISTANCE_WEIGHTED_VOTING: for (long c = 0; c < ncategories; c ++) freqs [c] *= 1 / OlaMAX (OlaSQUARE (distances [c]), kOla_MINFLOAT); } KNN_normalizeFloatArray (freqs.peek(), ncategories); outputindices [noutputindices++] = freqindices [KNN_max (freqs.peek(), ncategories)]; } Categories output = Categories_create (); for (long o = 0; o < noutputindices; o ++) { Collection_addItem (output, Data_copy ((SimpleString) my output -> item [outputindices [o]])); } return output; } ///////////////////////////////////////////////////////////////////////////////////////////// // Evaluation // ///////////////////////////////////////////////////////////////////////////////////////////// double KNN_evaluate ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // the classifier being used // FeatureWeights fws, // feature weights // long k, // the number of sought after neighbours // int dist, // distance weighting // int mode // kOla_TEN_FOLD_CROSS_VALIDATION / kOla_LEAVE_ONE_OUT // ) { double correct = 0; long adder; switch(mode) { case kOla_TEN_FOLD_CROSS_VALIDATION: adder = my nInstances / 10; break; case kOla_LEAVE_ONE_OUT: if (my nInstances > 1) adder = 1; else adder = 0; break; default: adder = 0; } if (adder == 0) return -1; for (long begin = 1; begin <= my nInstances; begin += adder) { autoCategories c = KNN_classifyFold (me, my input, fws, k, dist, begin, OlaMIN (begin + adder - 1, my nInstances)); for (long y = 1; y <= c -> size; y ++) if (FeatureWeights_areFriends ((SimpleString) c -> item [y], (SimpleString) my output -> item [begin + y - 1])) ++ correct; } correct /= (double) my nInstances; return correct; } ///////////////////////////////////////////////////////////////////////////////////////////// // Evaluation using a separate test set // ///////////////////////////////////////////////////////////////////////////////////////////// double KNN_evaluateWithTestSet ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // the classifier being used // Pattern p, // The vectors of the test set // Categories c, // The categories of the test set // FeatureWeights fws, // feature weights // long k, // the number of sought after neighbours // int dist // distance weighting // ) { double correct = 0; Categories t = KNN_classifyToCategories(me, p, fws, k, dist); if (t) { for (long y = 1; y <= t->size; y++) if (FeatureWeights_areFriends ((SimpleString) t->item[y], (SimpleString) c->item[y])) correct++; forget(t); return(correct / c->size); } else { return(0); } } ///////////////////////////////////////////////////////////////////////////////////////////// // Model search // ///////////////////////////////////////////////////////////////////////////////////////////// typedef struct structsoil { double performance; long dist; long k; } soil; double KNN_modelSearch ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // the classifier being used // FeatureWeights fws, // feature weights // long * k, // valid long *, to hold the output value of k // int * dist, // valid int *, to hold the output value dist_weight // int mode, // evaluation mode // double rate, // learning rate // long nseeds // the number of seeds to be used // ) { try { int dists[] = { kOla_SQUARED_DISTANCE_WEIGHTED_VOTING, kOla_DISTANCE_WEIGHTED_VOTING, kOla_FLAT_VOTING }; long max = *k; double range = (double) max / 2; double pivot = range; double dpivot = 1; double drange = 1; double drate = rate / range; soil best = {0, lround(dpivot), lround(dpivot)}; autoNUMvector field (0L, nseeds - 1); while (range > 0) { for (long n = 0; n < nseeds; n++) { field[n].k = lround(NUMrandomUniform(OlaMAX(pivot - range, 1), OlaMIN(pivot + range, max))); field[n].dist = lround(NUMrandomUniform(OlaMAX(dpivot - drange, 0), OlaMIN(dpivot + drange, 2))); field[n].performance = KNN_evaluate(me, fws, field[n].k, dists[field[n].dist], mode); } long maxindex = 0; for (long n = 1; n < nseeds; n++) if (field[n].performance > field[maxindex].performance) maxindex = n; if (field[maxindex].performance > best.performance) { pivot = field[maxindex].k; dpivot = field[maxindex].dist; best.performance = field[maxindex].performance; best.dist = field[maxindex].dist; best.k = field[maxindex].k; } range -= rate; drange -= drate; } *k = best.k; *dist = dists[best.dist]; return best.performance; } catch (MelderError) { Melder_throw (me, " & ", fws, ": model search not performed."); } } ///////////////////////////////////////////////////////////////////////////////////////////// // Euclidean distance // ///////////////////////////////////////////////////////////////////////////////////////////// double KNN_distanceEuclidean ( Pattern ps, // Pattern 1 // Pattern pt, // Pattern 2 // FeatureWeights fws, // Feature weights // long rows, // Vector index of pattern 1 // long rowt // Vector index of pattern 2 ) { double distance = 0; for (long x = 1; x <= ps->nx; ++x) distance += OlaSQUARE((ps->z[rows][x] - pt->z[rowt][x]) * fws->fweights->data[1][x]); return(sqrt(distance)); } ///////////////////////////////////////////////////////////////////////////////////////////// // Manhattan distance // ///////////////////////////////////////////////////////////////////////////////////////////// double KNN_distanceManhattan ( Pattern ps, // Pattern 1 // Pattern pt, // Pattern 2 // long rows, // Vector index of pattern 1 // long rowt // Vector index of pattern 2 // ) { double distance = 0; for (long x = 1; x <= ps->nx; ++x) distance += fabs(ps->z[rows][x] - pt->z[rowt][x]); return(distance); } ///////////////////////////////////////////////////////////////////////////////////////////// // Find longest distance // ///////////////////////////////////////////////////////////////////////////////////////////// long KNN_max ( double * distances, // an array of distances containing ... // long ndistances // ndistances distances // ) { long maxndx = 0; for(long maxc = 1; maxc < ndistances; ++maxc) if (distances[maxc] > distances[maxndx]) maxndx = maxc; return(maxndx); } //////////////////////////////////////////////////////////////////////////////////////////// // Locate k neighbours, skip one + disposal of distance // ///////////////////////////////////////////////////////////////////////////////////////////// long KNN_kNeighboursSkip ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern j, // source pattern // Pattern p, // target pattern (where neighbours are sought for) // FeatureWeights fws, // feature weights // long jy, // source instance index // long k, // the number of sought after neighbours // long * indices, // memory space to contain the indices of // the k neighbours // long skipper // the index of the instance to be skipped // ) { long maxi; long dc = 0; long py = 1; autoNUMvector distances (0L, k - 1); Melder_assert(jy > 0 && jy <= j->ny); Melder_assert(k > 0 && k <= p->ny); Melder_assert(skipper <= p->ny); while (dc < k && py <= p -> ny) { if (py != jy && py != skipper) { distances [dc] = KNN_distanceEuclidean (j, p, fws, jy, py); indices [dc] = py; ++ dc; } ++ py; } maxi = KNN_max (distances.peek(), k); while (py <= p->ny) { if (py != jy && py != skipper) { double d = KNN_distanceEuclidean (j, p, fws, jy, py); if (d < distances [maxi]) { distances [maxi] = d; indices [maxi] = py; maxi = KNN_max (distances.peek(), k); } } ++ py; } return OlaMIN (k, dc); } ////////////////////////////////////////////////////////////////////////////////// // Locate the k nearest neighbours, exclude instances within the range defined // // by [begin ... end] // ////////////////////////////////////////////////////////////////////////////////// long KNN_kNeighboursSkipRange ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern j, // source-pattern (where the unknown is located) // Pattern p, // target pattern (where neighbours are sought for) // FeatureWeights fws, // feature weights // long jy, // the index of the unknown instance in the source pattern // long k, // the number of sought after neighbours // long * indices, // a pointer to a memory-space big enough for k longs // representing indices to the k neighbours in the // target pattern // double * distances, // a pointer to a memory-space big enough for k // doubles representing the distances to the k // neighbours // long begin, // an index indicating the first instance in the // target pattern to be excluded from the search // long end // an index indicating the last instance in the // range of excluded instances in the target // pattern ) { /////////////////////////////// // Private variables // /////////////////////////////// long maxi; // index indicating the most distant neighbour // among the k nearest // long dc = 0; // fetch counter // long py = 0; // Melder_assert(jy > 0 && jy <= j->ny); Melder_assert(k > 0 && k <= p->ny); Melder_assert(end > 0 && end <= j->ny); Melder_assert(begin > 0 && begin <= j->ny); while (dc < k && (end + py) % p->ny + 1 != begin) // the first k neighbours are the nearest found { // sofar if ((end + py) % p->ny + 1 != jy) // no instance is its own neighbour { distances[dc] = KNN_distanceEuclidean(j, p, fws, jy, (end + py) % p->ny + 1); indices[dc] = (end + py) % p->ny + 1; ++dc; } ++py; } maxi = KNN_max(distances, k); // accept only those instances less distant while ((end + py) % p->ny + 1 != begin) // than the least near one found this far { if ((end + py) % p->ny + 1 != jy) { double d = KNN_distanceEuclidean(j, p, fws, jy, (end + py) % p->ny + 1); if (d < distances[maxi]) { distances[maxi] = d; indices[maxi] = (end + py) % p->ny + 1; maxi = KNN_max(distances, k); } } ++py; } return(OlaMIN(k, dc)); // return the number of found neighbours } ///////////////////////////////////////////////////////////////////////////////////////////// // Locate k neighbours // ///////////////////////////////////////////////////////////////////////////////////////////// long KNN_kNeighbours ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern j, // source-pattern (where the unknown is located) // Pattern p, // target pattern (where neighbours are sought for) // FeatureWeights fws, // feature weights // long jy, // the index of the unknown instance in the source pattern // long k, // the number of sought after neighbours // long * indices, // a pointer to a memory-space big enough for k longs // representing indices to the k neighbours in the // target pattern double * distances // a pointer to a memory-space big enough for k // doubles representing the distances to the k // neighbours // ) { long maxi; long dc = 0; long py = 1; Melder_assert(jy > 0 && jy <= j->ny); Melder_assert(k > 0 && k <= p->ny); Melder_assert(indices); Melder_assert(distances); while (dc < k && py <= p->ny) { if (py != jy) { distances[dc] = KNN_distanceEuclidean(j, p, fws, jy, py); indices[dc] = py; ++dc; } ++py; } maxi = KNN_max(distances, k); while (py <= p->ny) { if (py != jy) { double d = KNN_distanceEuclidean(j, p, fws, jy, py); if (d < distances[maxi]) { distances[maxi] = d; indices[maxi] = py; maxi = KNN_max(distances, k); } } ++py; } long ret = OlaMIN(k, dc); if (ret < 1) { indices[0] = jy; return(0); } else return(ret); } ///////////////////////////////////////////////////////////////////////////////////////////// // Locating k (nearest) friends // ///////////////////////////////////////////////////////////////////////////////////////////// long KNN_kFriends ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern j, // source-pattern // Pattern p, // target pattern (where friends are sought for) // Categories c, // categories // long jy, // the index of the source instance // long k, // the number of sought after friends // long * indices // a pointer to a memory-space big enough for k longs // representing indices to the k friends in the // target pattern ) { long maxi; long dc = 0; long py = 1; double *distances = NUMvector (0, k - 1); Melder_assert(jy <= j->ny && k <= p->ny && k > 0); Melder_assert(indices); while (dc < k && py < p->ny) { if (jy != py && FeatureWeights_areFriends ((SimpleString) c->item[jy], (SimpleString) c->item[py])) { distances[dc] = KNN_distanceManhattan(j, p, jy, py); indices[dc] = py; dc++; } ++py; } maxi = KNN_max(distances, k); while (py <= p->ny) { if (jy != py && FeatureWeights_areFriends ((SimpleString) c->item[jy],(SimpleString) c->item[py])) { double d = KNN_distanceManhattan(j, p, jy, py); if (d < distances[maxi]) { distances[maxi] = d; indices[maxi] = py; maxi = KNN_max(distances, k); } } ++py; } NUMvector_free (distances, 0); return(OlaMIN(k,dc)); } ///////////////////////////////////////////////////////////////////////////////////////////// // Computing the distance to the nearest enemy // ///////////////////////////////////////////////////////////////////////////////////////////// double KNN_nearestEnemy ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern j, // source-pattern // Pattern p, // target pattern (where friends are sought for) // Categories c, // categories // long jy // the index of the source instance // ) { double distance = KNN_distanceManhattan(j, p, jy, 1); Melder_assert(jy > 0 && jy <= j->ny ); for (long y = 2; y <= p->ny; y++) { if (FeatureWeights_areEnemies ((SimpleString) c->item[jy], (SimpleString) c->item[y])) { double newdist = KNN_distanceManhattan(j, p, jy, y); if (newdist > distance) distance = newdist; } } return(distance); } ///////////////////////////////////////////////////////////////////////////////////////////// // Computing the number of friends among k neighbours // ///////////////////////////////////////////////////////////////////////////////////////////// long KNN_friendsAmongkNeighbours ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern j, // source-pattern // Pattern p, // target pattern (where friends are sought for) // Categories c, // categories // long jy, // the index of the source instance // long k // k (!) // ) { autoNUMvector distances (0L, k - 1); autoNUMvector indices (0L, k - 1); long friends = 0; Melder_assert (jy > 0 && jy <= j->ny && k <= p->ny && k > 0); autoFeatureWeights fws = FeatureWeights_create (p -> nx); long ncollected = KNN_kNeighbours (j, p, fws.peek(), jy, k, indices.peek(), distances.peek()); while (ncollected--) if (FeatureWeights_areFriends ((SimpleString) c->item[jy], (SimpleString) c->item[indices[ncollected]])) friends++; return friends ; } ///////////////////////////////////////////////////////////////////////////////////////////// // Locating k unique (nearest) enemies // ///////////////////////////////////////////////////////////////////////////////////////////// long KNN_kUniqueEnemies ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern j, // source-pattern // Pattern p, // target pattern (where friends are sought for) // Categories c, // categories // long jy, // the index of the source instance // long k, // k (!) // long * indices // a memory space to hold the indices of the // located enemies // ) { long maxi; long dc = 0; long py = 1; double *distances = NUMvector (0, k - 1); Melder_assert (jy <= j->ny); Melder_assert (k <= p->ny); Melder_assert (k > 0); Melder_assert (indices != NULL); while (dc < k && py <= p->ny) { if (FeatureWeights_areEnemies ((SimpleString) c->item[jy], (SimpleString) c->item[py])) { int hasfriend = 0; for (long sc = 0; sc < dc; ++sc) if (FeatureWeights_areFriends ((SimpleString) c->item[py], (SimpleString) c->item[indices[sc]])) hasfriend = 1; if (!hasfriend) { distances[dc] = KNN_distanceManhattan(j, p, jy, py); indices[dc] = py; ++dc; } } ++py; } maxi = KNN_max(distances, k); while (py <= p->ny) { if (FeatureWeights_areEnemies ((SimpleString) c->item[jy], (SimpleString) c->item[py])) { int hasfriend = 0; for (long sc = 0; sc < dc; ++sc) if (FeatureWeights_areFriends ((SimpleString) c->item[py], (SimpleString) c->item[indices[sc]])) hasfriend = 1; if (!hasfriend) { double d = KNN_distanceManhattan(j, p, jy, py); if (d < distances[maxi] && FeatureWeights_areFriends ((SimpleString) c->item[jy], (SimpleString) c->item[py])) { distances[maxi] = d; indices[maxi] = py; maxi = KNN_max(distances, k); } } } ++py; } NUMvector_free (distances, 0); return(OlaMIN(k,dc)); } ///////////////////////////////////////////////////////////////////////////////////////////// // Compute dissimilarity matrix // ///////////////////////////////////////////////////////////////////////////////////////////// Dissimilarity KNN_patternToDissimilarity ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern p, // Pattern // FeatureWeights fws // Feature weights // ) { autoDissimilarity output = Dissimilarity_create (p -> ny); for (long y = 1; y <= p -> ny; ++ y) for (long x = 1; x <= p -> ny; ++ x) output -> data [y] [x] = KNN_distanceEuclidean (p, p, fws, y, x); return output.transfer(); } ///////////////////////////////////////////////////////////////////////////////////////////// // Compute frequencies // ///////////////////////////////////////////////////////////////////////////////////////////// long KNN_kIndicesToFrequenciesAndDistances ( /////////////////////////////// // Parameters // /////////////////////////////// Categories c, // Source categories // long k, // k (!) // long * indices, // In: indices // double * distances, // Out: distances // double * freqs, // Out: and frequencies (double, sic!) // long *freqindices // Out: and indices -> freqs. ) { long ncategories = 0; Melder_assert(k <= c->size && k > 0); Melder_assert(distances && indices && freqs && freqindices); for (long y = 0; y < k; ++y) { int hasfriend = 0; long ifriend = 0; while (ifriend < ncategories) { if (FeatureWeights_areFriends ((SimpleString) c->item[indices[y]], (SimpleString) c->item[freqindices[ifriend]])) { hasfriend = 1; break; } ++ifriend; } if (!hasfriend) { freqindices[ncategories] = indices[y]; freqs[ncategories] = 1; distances[ncategories] = distances[y]; ncategories++; } else { ++freqs[ifriend]; distances[ifriend] += (distances[y] - distances[ifriend]) / (ncategories + 1); } } return(ncategories); } ///////////////////////////////////////////////////////////////////////////////////////////// // Normalize array // ///////////////////////////////////////////////////////////////////////////////////////////// void KNN_normalizeFloatArray ( /////////////////////////////// // Parameters // /////////////////////////////// double * array, // Array to be normalized // long n // The number of elements // in the array ) { long c = 0; double sum = 0; while(c < n) sum += array[c++]; while(c--) array[c] /= sum; } ///////////////////////////////////////////////////////////////////////////////////////////// // Remove instance // ///////////////////////////////////////////////////////////////////////////////////////////// void KNN_removeInstance ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // Classifier // long y // Index of the instance to be purged // ) { if (y == 1 && my nInstances == 1) { my nInstances = 0; forget(my input); forget(my output); return; } Melder_assert(y > 0 && y <= my nInstances); if (y > my nInstances || y < 1) return; // safety belt Pattern newPattern = (Pattern) Pattern_create(my nInstances - 1, (my input)->nx); Melder_assert(newPattern); if (newPattern) { long yt = 1; for (long cy = 1; cy <= my nInstances; ++cy) if (cy != y) { for (long cx = 1; cx <= (my input)->nx; ++cx) newPattern->z[yt][cx] = (my input)->z[cy][cx]; ++yt; } forget(my input); my input = newPattern; Collection_removeItem(my output, y); my nInstances--; } } ///////////////////////////////////////////////////////////////////////////////////////////// // Shuffle instances // ///////////////////////////////////////////////////////////////////////////////////////////// void KNN_shuffleInstances ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me // Classifier whose instance // base is to be shuffled ) { if (my nInstances < 2) return; // It takes atleast two to tango autoPattern new_input = Pattern_create (my nInstances, my input -> nx); autoCategories new_output = Categories_create (); long y = 1; while (my nInstances) { long pick = (long) lround (NUMrandomUniform (1, my nInstances)); Collection_addItem (new_output.peek(), Data_copy ((SimpleString) my output -> item [pick])); for (long x = 1;x <= (my input)->nx; ++x) new_input -> z [y] [x] = my input-> z [pick] [x]; KNN_removeInstance (me, pick); ++y; } forget (my input); forget (my output); my nInstances = new_output -> size; my input = new_input.transfer(); my output = new_output.transfer(); } ///////////////////////////////////////////////////////////////////////////////////////////// // KNN to Permutation (experimental) // ///////////////////////////////////////////////////////////////////////////////////////////// Permutation KNN_SA_ToPermutation ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // the classifier being used // long tries, // // long iterations, // // double step_size, // // double boltzmann_c, // // double temp_start, // // double damping_f, // // double temp_stop // // ) { gsl_rng * r; const gsl_rng_type * T; KNN_SA_t * istruct = KNN_SA_t_create(my input); Permutation result = Permutation_create(my nInstances); gsl_siman_params_t params = {tries, iterations, step_size, boltzmann_c, temp_start, damping_f, temp_stop}; gsl_rng_env_setup(); T = gsl_rng_default; r = gsl_rng_alloc(T); gsl_siman_solve(r, istruct, KNN_SA_t_energy, KNN_SA_t_step, KNN_SA_t_metric, NULL, // KNN_SA_t_print, KNN_SA_t_copy, KNN_SA_t_copy_construct, KNN_SA_t_destroy, 0, params); for (long i = 1; i <= my nInstances; ++i) result->p[i] = istruct->indices[i]; KNN_SA_t_destroy(istruct); return(result); } double KNN_SA_t_energy ( /////////////////////////////// // Parameters // /////////////////////////////// void * istruct ) { if(((KNN_SA_t *) istruct)->p->ny < 2) return(0); double eCost = 0; for(long i = 1; i <= ((KNN_SA_t *) istruct)->p->ny; ++i) { /* fast and sloppy version */ double jDist = 0; double kDist = 0; long j = i - 1 > 0 ? i - 1 : ((KNN_SA_t *) istruct)->p->ny; long k = i + 1 <= ((KNN_SA_t *) istruct)->p->ny ? i + 1 : 1; for (long x = 1; x <= ((KNN_SA_t *) istruct)->p->nx; ++x) { jDist += OlaSQUARE(((KNN_SA_t *) istruct)->p->z[((KNN_SA_t *) istruct)->indices[i]][x] - ((KNN_SA_t *) istruct)->p->z[((KNN_SA_t *) istruct)->indices[j]][x]); kDist += OlaSQUARE(((KNN_SA_t *) istruct)->p->z[((KNN_SA_t *) istruct)->indices[i]][x] - ((KNN_SA_t *) istruct)->p->z[((KNN_SA_t *) istruct)->indices[k]][x]); } eCost += ((sqrt(jDist) + sqrt(kDist)) / 2 - eCost) / i; } return(eCost); } double KNN_SA_t_metric ( void * istruct1, void * istruct2 ) { double result = 0; for(long i = ((KNN_SA_t *) istruct1)->p->ny; i >= 1; --i) if(((KNN_SA_t *) istruct1)->indices[i] != ((KNN_SA_t *) istruct2)->indices[i]) ++result; return(result); } void KNN_SA_t_print (void * istruct) { Melder_casual ("\n"); for (long i = 1; i <= ((KNN_SA_t *) istruct) -> p -> ny; i ++) Melder_casual ("%ld,", ((KNN_SA_t *) istruct) -> indices [i]); Melder_casual ("\n"); } void KNN_SA_t_step ( const gsl_rng * r, void * istruct, double step_size ) { long i1 = lround ((((KNN_SA_t *) istruct) -> p -> ny - 1) * gsl_rng_uniform (r)) + 1; long i2 = (i1 + lround (step_size * gsl_rng_uniform (r))) % ((KNN_SA_t *) istruct) -> p -> ny + 1; if (i1 == i2) return; if (i1 > i2) OlaSWAP (long, i1, i2); long partitions[i2 - i1 + 1]; KNN_SA_partition(((KNN_SA_t *) istruct)->p, i1, i2, partitions); for (long r, l = 1, stop = i2 - i1 + 1; l < stop; l ++) { while (l < stop && partitions [l] == 1) l ++; r = l + 1; while (r <= stop && partitions [r] == 2) r ++; if (r == stop) break; OlaSWAP (long, ((KNN_SA_t *) istruct) -> indices [i1], ((KNN_SA_t *) istruct) -> indices [i2]); } } void KNN_SA_t_copy ( void * istruct_src, void * istruct_dest ) { ((KNN_SA_t *) istruct_dest)->p = ((KNN_SA_t *) istruct_src)->p; for(long i = 1; i <= ((KNN_SA_t *) istruct_dest)->p->ny; ++i) ((KNN_SA_t *) istruct_dest)->indices[i] = ((KNN_SA_t *) istruct_src)->indices[i]; } void * KNN_SA_t_copy_construct ( void * istruct ) { KNN_SA_t * result = (KNN_SA_t *) malloc(sizeof(KNN_SA_t)); result->p = ((KNN_SA_t *) istruct)->p; result->indices = (long *) malloc(sizeof(long) * (result->p->ny + 1)); for(long i = 1; i <= result->p->ny; ++i) result->indices[i] = ((KNN_SA_t *) istruct)->indices[i]; return((void *) result); } KNN_SA_t * KNN_SA_t_create ( Pattern p ) { KNN_SA_t * result = (KNN_SA_t *) malloc(sizeof(KNN_SA_t)); result->p = p; result->indices = (long *) malloc(sizeof(long) * (p->ny + 1)); for(long i = 1; i <= p->ny; ++i) result->indices[i] = i; return(result); } void KNN_SA_t_destroy ( void * istruct ) { free(((KNN_SA_t *) istruct)->indices); free((KNN_SA_t *) istruct); } void KNN_SA_partition ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern p, // // long i1, // i1 < i2 // long i2, // // long * result // [0] anv. ej // ) { long c1 = (long) lround(NUMrandomUniform(i1, i2)); long c2 = (long) lround(NUMrandomUniform(i1, i2)); double *p1 = NUMvector (1, p->nx); double *p2 = NUMvector (1, p->nx); for(long x = 1; x <= p->nx; ++x) { p1[x] = p->z[c1][x]; p2[x] = p->z[c2][x]; } for (bool converging = true; converging; ) { double d1, d2; converging = false; for(long i = i1, j = 1; i <= i2; ++i) { d1 = 0; d2 = 0; for (long x = 1; x <= p->nx; ++x) { d1 += OlaSQUARE(p->z[i][x] - p1[x]); d2 += OlaSQUARE(p->z[i][x] - p2[x]); } d1 = sqrt(d1); d2 = sqrt(d2); if(d1 < d2) { if(result[j] != 1) { converging = true; result[j] = 1; } } else { if(result[j] != 2) { converging = true; result[j] = 2; } } ++j; } for (long x = 1; x <= p -> nx; x ++) { p1[x] = 0; p2[x] = 0; } for (long i = i1, j = 1, j1 = 1, j2 = 1; i <= i2; i ++) { if (result [j] == 1) { for (long x = 1; x <= p->nx; x ++) p1[x] += (p->z[i][x] - p1[x]) / j1; ++j1; } else { for (long x = 1; x <= p -> nx; x ++) p2[x] += (p->z[i][x] - p2[x]) / j2; ++j2; } ++j; } } NUMvector_free (p1, 1); NUMvector_free (p2, 1); } /* End of file KNN.cpp */ sources_5316/contrib/ola/FeatureWeights.h0000644000176700017670000000545011625721237017247 0ustar paulpaul#ifndef _FeatureWeights_h_ #define _FeatureWeights_h_ /* FeatureWeights.h * * Copyright (C) 2007-2008 Ola Söder * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 20080529 Initial release * pb 2011/03/08 */ ///////////////////////////////////////////////////// // Praat datatypes // ///////////////////////////////////////////////////// #include "Data.h" #include "TableOfReal.h" #include "Pattern.h" #include "Categories.h" ///////////////////////////////////////////////////// // Miscs // ///////////////////////////////////////////////////// #include "OlaP.h" ///////////////////////////////////////////////////// // Praat specifics // ///////////////////////////////////////////////////// #include "FeatureWeights_def.h" oo_CLASS_CREATE (FeatureWeights, Data); ///////////////////////////////////////////////////// // Private definitions and macros // ///////////////////////////////////////////////////// #define FeatureWeights_areFriends(x,y) ! SimpleString_compare (x,y) #define FeatureWeights_areEnemies(x,y) SimpleString_compare (x,y) ///////////////////////////////////////////////////// // Prototypes // ///////////////////////////////////////////////////// // Create FeatureWeights FeatureWeights_create ( long nweights // number of weights ); // Compute prior probabilities long FeatureWeights_computePriors ( Categories c, // source categories long * indices, // Out: instances indices .. double * priors // Out: .. and their prior probabilities ); // Compute feature weights (obsolete) FeatureWeights FeatureWeights_compute ( Pattern pp, // Source pattern Categories c, // Source categories long k // k(!) ); // Compute feature weights according to the RELIEF-F algorithm FeatureWeights FeatureWeights_computeRELIEF ( Pattern pp, // source pattern Categories c, // source categories long k // k(!) ); /* End of file FeatureWeights.h */ #endif sources_5316/contrib/ola/TODO.txt0000644000176700017670000000006611143120700015433 0ustar paulpaulMultithreading on Windows. Approx n. search? kD-tree? sources_5316/contrib/ola/Pattern_to_Categories_cluster.h0000644000176700017670000000376211614421743022347 0ustar paulpaul/* Pattern_to_Categories_cluster.h * * Copyright (C) 2007-2008 Ola Söder * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 20070529 Initial release * pb 2011/03/08 C++ */ ///////////////////////////////////////////////////// // DEBUG // ///////////////////////////////////////////////////// //#define CLUSTERING_DEBUG ///////////////////////////////////////////////////// // Praat datatypes // ///////////////////////////////////////////////////// #include "Pattern.h" #include "Categories.h" ///////////////////////////////////////////////////// // Miscs // ///////////////////////////////////////////////////// #include "FeatureWeights.h" ///////////////////////////////////////////////////// // Prototypes // ///////////////////////////////////////////////////// // Pattern_to_Categories_cluster Categories Pattern_to_Categories_cluster ( Pattern p, // source FeatureWeights fws, // feature weights long k, // k(!) double s, // clustersize constraint 0 < s <= 1 long m // reseed maximum ); /* End of file Pattern_to_Categories_cluster.h */ sources_5316/contrib/ola/KNN.h0000644000176700017670000003334211625721240014742 0ustar paulpaul#ifndef _KNN_h_ #define _KNN_h_ /* KNN.h * * Copyright (C) 2007-2008 Ola Söder * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 20080529 Initial release * pb 2011/03/08 C++ */ ///////////////////////////////////////////////////// // Praat datatypes // ///////////////////////////////////////////////////// #include "Data.h" #include "Pattern.h" #include "Categories.h" #include "TableOfReal.h" #include "Permutation.h" #include "MDS.h" ///////////////////////////////////////////////////// // KNN miscs // ///////////////////////////////////////////////////// #include "OlaP.h" #include "FeatureWeights.h" #include "gsl_siman.h" ///////////////////////////////////////////////////// // Praat specifics // ///////////////////////////////////////////////////// #include "KNN_def.h" oo_CLASS_CREATE (KNN, Data); ///////////////////////////////////////////////////// // Private definitions and macros // ///////////////////////////////////////////////////// #define kOla_TEN_FOLD_CROSS_VALIDATION 1 #define kOla_LEAVE_ONE_OUT 2 #define kOla_TO_TABLEOFREAL 1 #define kOla_TO_TABLEOFREAL_ALL 2 #define kOla_TO_CATEGORIES 4 #define kOla_SQUARED_DISTANCE_WEIGHTED_VOTING 8 #define kOla_DISTANCE_WEIGHTED_VOTING 16 #define kOla_FLAT_VOTING 32 #define kOla_ERROR 0 #define kOla_SUCCESS 303 #define kOla_APPEND 1 #define kOla_REPLACE 2 #define kOla_SHUFFLE 1 #define kOla_SEQUENTIAL 2 #define kOla_PATTERN_CATEGORIES_MISMATCH 111 #define kOla_DIMENSIONALITY_MISMATCH 222 #define kOla_FWEIGHTS_MISMATCH 333 ///////////////////////////////////////////////////// // Prototypes // ///////////////////////////////////////////////////// // a near-dummy function KNN KNN_create(void); // Learning int KNN_learn ( KNN me, // the classifier to be trained Pattern p, // source pattern Categories c, // target categories int method, // method <- REPLACE or APPEND int ordering // ordering <- SHUFFLE? ); // Classification - To Categories Categories KNN_classifyToCategories ( KNN me, // the classifier being used Pattern ps, // target pattern (where neighbours are sought for) FeatureWeights fws, // feature weights long k, // the number of sought after neighbours int dist // distance weighting ); // Classification - To Categories, threading aux void * KNN_classifyToCategoriesAux ( void * input ); // Classification - To TableOfReal TableOfReal KNN_classifyToTableOfReal ( KNN me, // the classifier being used Pattern ps, // target pattern (where neighbours are sought for) FeatureWeights fws, // feature weights long k, // the number of sought after neighbours int dist // distance weighting ); // Classification - To TableOfReal, threading aux void * KNN_classifyToTableOfRealAux ( void * input ); // Classification - To TableOfReal, all candidates TableOfReal KNN_classifyToTableOfRealAll ( KNN me, // the classifier being used Pattern ps, // target pattern (where neighbours are sought for) FeatureWeights fws, // feature weights long k, // the number of sought after neighbours int dist // distance weighting ); // Classification - Folding Categories KNN_classifyFold ( KNN me, // the classifier being used Pattern ps, // target pattern (where neighbours are sought for) FeatureWeights fws, // feature weights long k, // the number of sought after neighbours int dist, // distance weighting long begin, // fold start, inclusive [... long end // fold end, inclusive ...] ); // Evaluation double KNN_evaluate ( KNN me, // the classifier being used FeatureWeights fws, // feature weights long k, // the number of sought after neighbours int dist, // distance weighting int mode // TEN_FOLD_CROSS_VALIDATION / LEAVE_ONE_OUT ); // Evaluation using a separate test set double KNN_evaluateWithTestSet ( KNN me, // the classifier being used Pattern p, // The vectors of the test set Categories c, // The categories of the test set FeatureWeights fws, // feature weights long k, // the number of sought after neighbours int dist // distance weighting ); // Model search double KNN_modelSearch ( KNN me, // the classifier being used FeatureWeights fws, // feature weights long * k, // valid long *, to hold the output value of k int * dist, // valid int *, to hold the output value dist_weight int mode, // evaluation mode double rate, // learning rate long nseeds // the number of seeds to be used ); // Euclidean distance double KNN_distanceEuclidean ( Pattern ps, // Pattern 1 Pattern pt, // Pattern 2 FeatureWeights fws, // Feature weights long rows, // Vector index of pattern 1 long rowt // Vector index of pattern 2 ); // Manhattan distance double KNN_distanceManhattan ( Pattern ps, // Pattern 1 Pattern pt, // Pattern 2 long rows, // Vector index of pattern 1 long rowt // Vector index of pattern 2 ); // Find longest distance long KNN_max ( double * distances, // an array of distances containing ... long ndistances // ndistances distances ); // Locate k neighbours, skip one + disposal of distance long KNN_kNeighboursSkip ( Pattern j, // source pattern Pattern p, // target pattern (where neighbours are sought for) FeatureWeights fws, // feature weights long jy, // source instance index long k, // the number of sought after neighbours long * indices, // memory space to contain the indices of long skipper // the index of the instance to be skipped ); // Locate the k nearest neighbours, exclude instances within the range defined // by [begin ... end] long KNN_kNeighboursSkipRange ( Pattern j, // source-pattern (where the unknown is located) Pattern p, // target pattern (where neighbours are sought for) FeatureWeights fws, // feature weights long jy, // the index of the unknown instance in the source pattern long k, // the number of sought after neighbours long * indices, // a pointer to a memory-space big enough for k longs // representing indices to the k neighbours in the // target pattern double * distances, // a pointer to a memory-space big enough for k // doubles representing the distances to the k // neighbours long begin, // an index indicating the first instance in the // target pattern to be excluded from the search long end // an index indicating the last instance in the // range of excluded instances in the target // pattern ); // Locate k neighbours long KNN_kNeighbours ( Pattern j, // source-pattern (where the unknown is located) Pattern p, // target pattern (where neighbours are sought for) FeatureWeights fws, // feature weights long jy, // the index of the unknown instance in the source pattern long k, // the number of sought after neighbours long * indices, // a pointer to a memory-space big enough for k longs // representing indices to the k neighbours in the // target pattern double * distances // a pointer to a memory-space big enough for k // doubles representing the distances to the k // neighbours ); // Locating k (nearest) friends long KNN_kFriends ( Pattern j, // source-pattern Pattern p, // target pattern (where friends are sought for) Categories c, // categories long jy, // the index of the source instance long k, // the number of sought after friends long * indices // a pointer to a memory-space big enough for k longs // representing indices to the k friends in the // target pattern ); // Computing the distance to the nearest enemy double KNN_nearestEnemy ( Pattern j, // source-pattern Pattern p, // target pattern (where friends are sought for) Categories c, // categories long jy // the index of the source instance ); // Computing the number of friends among k neighbours long KNN_friendsAmongkNeighbours ( Pattern j, // source-pattern Pattern p, // target pattern (where friends are sought for) Categories c, // categories long jy, // the index of the source instance long k // k (!) ); // Locating k unique (nearest) enemies long KNN_kUniqueEnemies ( Pattern j, // source-pattern Pattern p, // target pattern (where friends are sought for) Categories c, // categories long jy, // the index of the source instance long k, // k (!) long * indices // a memory space to hold the indices of the // located enemies ); // Compute dissimilarity matrix Dissimilarity KNN_patternToDissimilarity ( Pattern p, // Pattern FeatureWeights fws // Feature weights ); // Compute frequencies long KNN_kIndicesToFrequenciesAndDistances ( Categories c, // Source categories long k, // k (!) long * indices, // In: indices double * distances, // Out: distances double * freqs, // Out: and frequencies (double, sic!) long *freqindices // Out: and indices -> freqs. ); // Normalize array void KNN_normalizeFloatArray ( double * array, // Array to be normalized long n // The number of elements // in the array ); // Remove instance void KNN_removeInstance ( KNN me, // Classifier long y // Index of the instance to be purged // ); // Shuffle instances void KNN_shuffleInstances ( KNN me // Classifier whose instance // base is to be shuffled ); // Experimental code Permutation KNN_SA_ToPermutation ( KNN me, // the classifier being used long tries, // long iterations, // double step_size, // double boltzmann_c, // double temp_start, // double damping_f, // double temp_stop // // ); // Experimental code typedef struct { Pattern p; long * indices; } KNN_SA_t; // Experimental code double KNN_SA_t_energy ( void * istruct ); // Experimental code double KNN_SA_t_metric ( void * istruct1, void * istruct2 ); // Experimental code void KNN_SA_t_print ( void * istruct ); // Experimental code void KNN_SA_t_step ( const gsl_rng * r, void * istruct, double step_size ); // Experimental code void KNN_SA_t_copy ( void * istruct_src, void * istruct_dest ); // Experimental code void * KNN_SA_t_copy_construct ( void * istruct ); // Experimental code KNN_SA_t * KNN_SA_t_create ( Pattern p ); // Experimental code void KNN_SA_t_destroy ( void * istruct ); // Experimental code void KNN_SA_partition ( Pattern p, long i1, long i2, long * result ); // Compute feature weights (wrapper), evaluate using folding FeatureWeights FeatureWeights_computeWrapperInt ( KNN me, // Classifier long k, // k(!) int d, // distance weighting long nseeds, // the number of seeds double alfa, // shrinkage factor double stop, // stop at int mode, // mode (co/serial) int emode // evaluation mode (10-fold/L1O) ); // Compute feature weights (wrapper), evaluate using separate test set FeatureWeights FeatureWeights_computeWrapperExt ( KNN nn, // Classifier Pattern pp, // test pattern Categories c, // test categories long k, // k(!) int d, // distance weighting long nseeds, // the number of seeds double alfa, // shrinkage factor double stop, // stop at int mode // mode (co/serial) ); // Evaluate feature weights, wrapper aux. double FeatureWeights_evaluate ( FeatureWeights fws, // Weights to evaluate KNN nn, // Classifier Pattern pp, // test pattern Categories c, // test categories long k, // k(!) int d // distance weighting ); /* End of file KNN.h */ #endif sources_5316/contrib/ola/KNN_def.h0000644000176700017670000000207211621503322015547 0ustar paulpaul/* KNN_def.h * * Copyright (C) 2007-2009 Ola Söder, 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Pattern.h" #define ooSTRUCT KNN oo_DEFINE_CLASS (KNN, Data) oo_LONG (nInstances) oo_OBJECT (Pattern, 2, input) oo_OBJECT (Categories, 0, output) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (KNN) #undef ooSTRUCT /* End of file KNN_def.h */ sources_5316/contrib/ola/FeatureWeights.cpp0000644000176700017670000003575711724523411017611 0ustar paulpaul/* FeatureWeights.cpp * * Copyright (C) 2007-2008 Ola So"der, 2010-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 2007/05/29 Initial release * pb 2010/06/06 removed some array-creations-on-the-stack * pb 2011/03/08 tried to repair some of the header file chaos (several procedures here should be in KNN.c instead) * pb 2011/04/12 C++ */ #include "FeatureWeights.h" #include "KNN.h" // BUG #include "oo_DESTROY.h" #include "FeatureWeights_def.h" #include "oo_COPY.h" #include "FeatureWeights_def.h" #include "oo_EQUAL.h" #include "FeatureWeights_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "FeatureWeights_def.h" #include "oo_WRITE_TEXT.h" #include "FeatureWeights_def.h" #include "oo_WRITE_BINARY.h" #include "FeatureWeights_def.h" #include "oo_READ_TEXT.h" #include "FeatureWeights_def.h" #include "oo_READ_BINARY.h" #include "FeatureWeights_def.h" #include "oo_DESCRIPTION.h" #include "FeatureWeights_def.h" void structFeatureWeights :: v_info () { this -> structData :: v_info (); MelderInfo_writeLine2 (L"Number of weights: ", Melder_integer (fweights -> numberOfColumns)); } Thing_implement (FeatureWeights, Data, 0); ///////////////////////////////////////////////////////////////////////////////////////////// // Creation... // ///////////////////////////////////////////////////////////////////////////////////////////// FeatureWeights FeatureWeights_create ( /////////////////////////////// // Parameters // /////////////////////////////// long nweights // number of weights ) { try { autoFeatureWeights me = Thing_new (FeatureWeights); my fweights = TableOfReal_create (1, nweights); therror for (long i = 1; i <= nweights; i ++) { my fweights -> data [1] [i] = 1; } return me.transfer(); } catch (MelderError) { Melder_throw ("FeatureWeights not created."); } } ///////////////////////////////////////////////////////////////////////////////////////////// // Compute prior probabilities // ///////////////////////////////////////////////////////////////////////////////////////////// long FeatureWeights_computePriors ( /////////////////////////////// // Parameters // /////////////////////////////// Categories c, // source categories // long * indices, // Out: instances indices .. // double * priors // Out: .. and their prior probabilities // ) { long nc = 0; for (long y = 1; y <= c->size; y++) { long ifriend = -1; for (long sc = 0; sc < nc; sc++) if (FeatureWeights_areFriends ((SimpleString) c->item[y], (SimpleString) c->item[indices[sc]])) ifriend = sc; if (ifriend < 0) { indices[nc] = y; priors[nc] = 1; nc++; } else { priors[ifriend]++; } } for (long q = 0; q < nc; q++) priors[q] /= c->size; return(nc); } ///////////////////////////////////////////////////////////////////////////////////////////// // Compute feature weights // ///////////////////////////////////////////////////////////////////////////////////////////// FeatureWeights FeatureWeights_compute // Obsolete ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern pp, // Source pattern // Categories c, // Source categories // long k // k(!) ) { return(FeatureWeights_computeRELIEF(pp, c, k)); } ///////////////////////////////////////////////////////////////////////////////////////////// // Compute feature weights (wrapper), evaluate using folding // ///////////////////////////////////////////////////////////////////////////////////////////// FeatureWeights FeatureWeights_computeWrapperInt ( /////////////////////////////// // Parameters // /////////////////////////////// KNN me, // Classifier // long k, // k(!) // int d, // distance weighting // long nseeds, // the number of seeds // double alfa, // shrinkage factor // double stop, // stop at // int mode, // mode (co/serial) // int emode // evaluation mode (10-fold/L1O) // ) { if (! me) return NULL; try { double pivot = 0.5; double range = 0.5; autoNUMvector results (0L, nseeds); autoThingVector cs (0L, nseeds); for (long y = 0; y <= nseeds; y++) { cs [y] = FeatureWeights_create (my input -> nx); therror } for (long x = 1; x <= my input -> nx; x ++) cs [nseeds] -> fweights -> data [1] [x] = pivot; results [nseeds] = KNN_evaluate (me, cs [nseeds], k, d, emode); while (range > 0 && results [nseeds] < stop) { long best = nseeds; if (mode == 2) { for (long x = 1; x <= (my input)->nx; x++) { for (long y = 0; y < nseeds; y++) { cs[y]->fweights->data[1][x] = NUMrandomUniform(OlaMAX(0, cs[nseeds]->fweights->data[1][x] - range), OlaMIN(1, cs[nseeds]->fweights->data[1][x] + range)); results[y] = KNN_evaluate(me, cs[y], k, d, emode); } for (long q = 0; q < nseeds; q++) if (results[q] > results[best]) best = q; if (results[best] > results[nseeds]) { for (long x = 1; x <= (my input)->nx; x++) cs[nseeds]->fweights->data[1][x] = cs[best]->fweights->data[1][x]; results[nseeds] = results[best]; } } } else { for (long y = 0; y < nseeds; y++) { for (long x = 1; x <= (my input)->nx; x++) { cs[y]->fweights->data[1][x] = NUMrandomUniform(OlaMAX(0, cs[nseeds]->fweights->data[1][x] - range), OlaMIN(1, cs[nseeds]->fweights->data[1][x] + range)); } results[y] = KNN_evaluate (me, cs [y], k, d, emode); } for (long q = 0; q < nseeds; q++) if (results[q] > results[best]) best = q; if (results[best] > results[nseeds]) { for (long x = 1; x <= (my input)->nx; x++) cs[nseeds]->fweights->data[1][x] = cs[best]->fweights->data[1][x]; results[nseeds] = results[best]; } } range -= alfa; } FeatureWeights result = cs [nseeds]; cs [nseeds] = NULL; // prevent destruction return result; } catch (MelderError) { Melder_throw ("FeatureWeights: wrapper not computed."); } } ///////////////////////////////////////////////////////////////////////////////////////////// // Compute feature weights (wrapper), evaluate using separate test set // ///////////////////////////////////////////////////////////////////////////////////////////// FeatureWeights FeatureWeights_computeWrapperExt ( /////////////////////////////// // Parameters // /////////////////////////////// KNN nn, // Classifier // Pattern pp, // test pattern // Categories c, // test categories // long k, // k(!) // int d, // distance weighting // long nseeds, // the number of seeds // double alfa, // shrinkage factor // double stop, // stop at // int mode // mode (co/serial) // ) { if (nn == NULL) return NULL; try { double pivot = 0.5; double range = 0.5; autoNUMvector results (0L, nseeds); autoThingVector cs (0L, nseeds); for (long y = 0; y <= nseeds; y++) { cs [y] = FeatureWeights_create (pp -> nx); therror } for (long x = 1; x <= pp -> nx; x ++) cs [nseeds] -> fweights -> data [1] [x] = pivot; results [nseeds] = FeatureWeights_evaluate (cs [nseeds], nn, pp, c, k, d); while (range > 0 && results [nseeds] < stop) { long best = nseeds; if (mode == 2) { for (long x = 1; x <= pp->nx; x++) { for (long y = 0; y < nseeds; y++) { cs[y]->fweights->data[1][x] = NUMrandomUniform(OlaMAX(0, cs[nseeds]->fweights->data[1][x] - range), OlaMIN(1, cs[nseeds]->fweights->data[1][x] + range)); results[y] = FeatureWeights_evaluate(cs[y], nn, pp, c, k, d); } for (long q = 0; q < nseeds; q++) if (results[q] > results[best]) best = q; if (results[best] > results[nseeds]) { for (long x = 1; x <= pp->nx; x++) cs[nseeds]->fweights->data[1][x] = cs[best]->fweights->data[1][x]; results[nseeds] = results[best]; } } } else { for (long y = 0; y < nseeds; y++) { for (long x = 1; x <= pp->nx; x++) { cs[y]->fweights->data[1][x] = NUMrandomUniform(OlaMAX(0, cs[nseeds]->fweights->data[1][x] - range), OlaMIN(1, cs[nseeds]->fweights->data[1][x] + range)); } results[y] = FeatureWeights_evaluate (cs [y], nn, pp, c, k, d); } for (long q = 0; q < nseeds; q++) if (results[q] > results[best]) best = q; if (results[best] > results[nseeds]) { for (long x = 1; x <= pp->nx; x++) cs[nseeds]->fweights->data[1][x] = cs[best]->fweights->data[1][x]; results[nseeds] = results[best]; } } range -= alfa; } FeatureWeights result = cs [nseeds]; cs [nseeds] = NULL; // prevent destruction return result; } catch (MelderError) { Melder_throw ("FeatureWeights: wrapper not computed."); } } ///////////////////////////////////////////////////////////////////////////////////////////// // Evaluate feature weights, wrapper aux. // ///////////////////////////////////////////////////////////////////////////////////////////// double FeatureWeights_evaluate // Obsolete - use *_EvaluateWithTestSet // instead ( /////////////////////////////// // Parameters // /////////////////////////////// FeatureWeights fws, // Weights to evaluate // KNN nn, // Classifier // Pattern pp, // test pattern // Categories c, // test categories // long k, // k(!) // int d // distance weighting // ) { try { autoCategories o = KNN_classifyToCategories (nn, pp, fws, k, d); double hits = 0; for (long y = 1; y <= o->size; y++) if (FeatureWeights_areFriends ((SimpleString) o -> item [y], (SimpleString) c -> item [y])) hits ++; hits /= o -> size; return hits; } catch (MelderError) { throw; return 0; } } ///////////////////////////////////////////////////////////////////////////////////////////// // Compute feature weights according to the RELIEF-F algorithm // ///////////////////////////////////////////////////////////////////////////////////////////// FeatureWeights FeatureWeights_computeRELIEF ( /////////////////////////////// // Parameters // /////////////////////////////// Pattern pp, // source pattern // Categories c, // source categories // long k // k(!) // ) { autoPattern p = (Pattern) Data_copy (pp); autoFeatureWeights me = FeatureWeights_create (p -> nx); ///////////////////////////////// // Initial weights <- 0 // ///////////////////////////////// for (long i = 1; i <= p->nx; i++) { my fweights -> data [1] [i] = 0.0; } ///////////////////////////////// // Normalization // ///////////////////////////////// autoNUMvector min (0L, p->nx - 1); autoNUMvector max (0L, p->nx - 1); for (long x = 1; x <= p -> nx; x ++) { max [x] = p -> z [1] [x]; // BUG: this will just crash because of array index out of bounds min [x] = max [x]; } for (long y = 1; y <= p -> ny; y ++) { for (long x = 1; x <= p->nx; x++) { if (p->z[y][x] > max[x]) max[x] = p->z[y][x]; if (p->z[y][x] < min[x]) min[x] = p->z[y][x]; } } autoNUMvector alfa (0L, p -> nx - 1); for (long x = 1; x <= p -> nx; x ++) { alfa [x] = max [x] - min [x]; // BUG: this will just crash because of array index out of bounds } for (long y = 1; y <= p->ny; y++) { for (long x = 1; x <= p->nx; x++) { if (alfa [x]) { p->z[y][x] = (p->z[y][x] - min[x]) / alfa[x]; } else { p->z[y][x] = 0; } } } ///////////////////////////////// // Computing prior class probs // ///////////////////////////////// autoNUMvector priors (0L, c->size - 1); // worst-case allocations autoNUMvector classes (0L, c->size - 1);// autoNUMvector enemies (0L, c->size - 1);// autoNUMvector friends (0L, c->size - 1);// long nclasses = FeatureWeights_computePriors (c, classes.peek(), priors.peek()); Melder_assert (nclasses >= 2); ///////////////////////////////// // Updating the w.vector // ///////////////////////////////// for (long y = 1; y <= p -> ny; y ++) { long nfriends = KNN_kFriends (p.peek(), p.peek(), c, y, k, friends.peek()); long nenemies = KNN_kUniqueEnemies (p.peek(), p.peek(), c, y, nclasses - 1, enemies.peek()); if (nfriends && nenemies) { autoNUMvector classps (0L, nenemies - 1); for (long eq = 0; eq < nenemies; eq++) { for (long iq = 0; iq < nclasses; iq++) { if (FeatureWeights_areFriends ((SimpleString) c->item[enemies[eq]], (SimpleString) c->item[classes[iq]])) { classps[eq] = priors[iq]; break; } } } for (long x = 1; x <= p->nx; x++) { double p1 = 0.0; double p2 = 0.0; for (long ec = 0; ec < nfriends; ec++) { p1 += fabs(p->z[y][x] - p->z[friends[ec]][x]) / (p->ny * nfriends); } for (long ec = 0; ec < nenemies; ec++) { p2 += (fabs(p->z[y][x] - p->z[enemies[ec]][x]) * classps[ec]) / p->ny; } my fweights -> data [1] [x] = my fweights -> data [1] [x] - p1 + p2; } } } return me.transfer(); } /* End of file FeatureWeights.cpp */ sources_5316/contrib/ola/BUGS.txt0000644000176700017670000000006311055314703015435 0ustar paulpaulKnown bugs: CPrune: progress indicators are borken sources_5316/contrib/ola/FeatureWeights_def.h0000644000176700017670000000205211621503322020045 0ustar paulpaul/* FeatureWeights_def.h * * Copyright (C) 2007-2009 Ola Söder, 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT FeatureWeights oo_DEFINE_CLASS (FeatureWeights, Data) oo_OBJECT (TableOfReal, 0, fweights) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (FeatureWeights) #undef ooSTRUCT /* End of file FeatureWeights_def.h */ sources_5316/contrib/ola/praat_contrib_Ola_KNN.cpp0000644000176700017670000011371511635432706021011 0ustar paulpaul/* praat_contrib_Ola_KNN.cpp * * Copyright (C) 2007-2009 Ola Söder, 2010-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * os 2007/05/29 Initial release? * os 2009/01/23 Bugfix: Removed MUX:ing (KNN_learn) incompatible with the scripting engine. Thanks to Paul Boersma for spotting this problem. * pb 2010/12/28 in messages: typos, English, interpunction * pb 2011/07/12 C++ and removed several errors * pb 2011/09/18 made a start with handling dataChanged at all */ #include "KNN.h" #include "KNN_threads.h" #include "KNN_prune.h" #include "Pattern_to_Categories_cluster.h" #include "FeatureWeights.h" #include "praat.h" static const wchar *QUERY_BUTTON = L"Query -"; static const wchar *MODIFY_BUTTON = L"Modify -"; static const wchar *EXTRACT_BUTTON = L"Extract -"; ///////////////////////////////////////////////////////////////////////////////////////// // KNN creations // ///////////////////////////////////////////////////////////////////////////////////////// FORM (KNN_create, L"Create kNN Classifier", L"kNN classifiers 1. What is a kNN classifier?") WORD (L"Name", L"Classifier") OK DO autoKNN knn = KNN_create (); praat_new (knn.transfer(), GET_STRING (L"Name")); END FORM (KNN_Pattern_Categories_to_KNN, L"Create kNN classifier", L"kNN classifiers 1. What is a kNN classifier?" ) WORD (L"Name", L"Classifier") RADIO (L"Ordering", 1) RADIOBUTTON (L"Random") RADIOBUTTON (L"Sequential") OK DO iam_ONLY (Pattern); thouart_ONLY (Categories); int ordering = GET_INTEGER (L"Ordering"); autoKNN knn = KNN_create (); switch (ordering) { case 1: ordering = kOla_SHUFFLE; break; case 2: ordering = kOla_SEQUENTIAL; } int result = KNN_learn (knn.peek(), me, thee, kOla_REPLACE, ordering); switch (result) { case kOla_PATTERN_CATEGORIES_MISMATCH: Melder_throw ("The number of Categories should be equal to the number of rows in Pattern."); case kOla_DIMENSIONALITY_MISMATCH: Melder_throw ("The dimensionality of Pattern should be equal to that of the instance base."); default: praat_new (knn.transfer(), GET_STRING(L"Name")); } END ///////////////////////////////////////////////////////////////////////////////////////// // KNN extractions, queries and modifications // ///////////////////////////////////////////////////////////////////////////////////////// DIRECT (KNN_getNumberOfInstances) iam_ONLY (KNN); Melder_information (Melder_integer (my nInstances), L" units"); END FORM (KNN_getOptimumModel, L"kNN model selection", L"kNN classifiers 1.1.2. Model selection") RADIO (L"Evaluation method", 1) RADIOBUTTON (L"Leave one out") RADIOBUTTON (L"10-fold cross-validation") INTEGER (L"k max", L"50") INTEGER (L"Number of seeds", L"10") POSITIVE (L"Learning rate", L"0.2") OK DO iam_ONLY (KNN); long k = GET_INTEGER (L"k max"); double lrate = GET_REAL (L"Learning rate"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k max such that 0 < k max < ", my nInstances + 1, "."); long nseeds = GET_INTEGER (L"Number of seeds"); if (nseeds < 1) Melder_throw ("The number of seeds should exceed 1."); int mode = GET_INTEGER (L"Evaluation method"); switch (mode) { case 2: mode = kOla_TEN_FOLD_CROSS_VALIDATION; break; case 1: mode = kOla_LEAVE_ONE_OUT; break; } autoFeatureWeights fws = FeatureWeights_create ((my input) -> nx); int dist; KNN_modelSearch (me, fws.peek(), &k, &dist, mode, lrate, nseeds); switch (dist) { case kOla_SQUARED_DISTANCE_WEIGHTED_VOTING: Melder_information (L"Vote weighting: Inversed squared distance\n", L"k: ", Melder_integer(k)); break; case kOla_DISTANCE_WEIGHTED_VOTING: Melder_information (L"Vote weighting: Inversed distance\n", L"k: ", Melder_integer(k)); break; case kOla_FLAT_VOTING: Melder_information (L"Vote weighting: Flat\n", L"k: ", Melder_integer(k)); break; } END FORM (KNN_evaluate, L"Evaluation", L"KNN: Get accuracy estimate...") RADIO (L"Evaluation method", 1) RADIOBUTTON (L"Leave one out") RADIOBUTTON (L"10-fold cross-validation") INTEGER (L"k neighbours", L"1") RADIO (L"Vote weighting", 1) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty."); long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); int vt = GET_INTEGER (L"Vote weighting"); switch (vt) { case 1: vt = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: vt = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: vt = kOla_FLAT_VOTING; break; } int mode = GET_INTEGER (L"Evaluation method"); switch (mode) { case 2: mode = kOla_TEN_FOLD_CROSS_VALIDATION; break; case 1: mode = kOla_LEAVE_ONE_OUT; break; } autoFeatureWeights fws = FeatureWeights_create (my input -> nx); double result = KNN_evaluate (me, fws.peek(), k, vt, mode); if (lround (result) == kOla_FWEIGHTS_MISMATCH) Melder_throw ("The number of feature weights should be equal to the dimensionality of the Pattern."); Melder_information (Melder_double (100 * result), L" percent of the instances correctly classified."); // BUG: use Melder_percent END FORM (KNN_evaluateWithFeatureWeights, L"Evaluation", L"KNN & FeatureWeights: Get accuracy estimate...") RADIO (L"Evaluation method", 1) RADIOBUTTON (L"Leave one out") RADIOBUTTON (L"10-fold cross-validation") INTEGER (L"k neighbours", L"1") RADIO (L"Vote weighting", 1) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty"); thouart_ONLY (FeatureWeights); long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); int vt = GET_INTEGER (L"Vote weighting"); switch (vt) { case 1: vt = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: vt = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: vt = kOla_FLAT_VOTING; break; } int mode = GET_INTEGER (L"Evaluation method"); switch (mode) { case 2: mode = kOla_TEN_FOLD_CROSS_VALIDATION; break; case 1: mode = kOla_LEAVE_ONE_OUT; break; } double result = KNN_evaluate (me, thee, k, vt, mode); if (lround (result) == kOla_FWEIGHTS_MISMATCH) Melder_throw ("The number of feature weights should be equal to the dimensionality of the Pattern."); Melder_information (Melder_double (100 * result), L" percent of the instances correctly classified."); END DIRECT (KNN_extractInputPatterns) iam_ONLY (KNN); if (my nInstances > 0) { praat_new (Data_copy (my input), L"Input Patterns"); } else { Melder_throw ("Instance base is empty."); } END DIRECT (KNN_extractOutputCategories) iam_ONLY (KNN); if (my nInstances > 0) { praat_new (Data_copy (my output), L"Output Categories"); } else { Melder_throw ("Instance base is empty."); } END FORM (KNN_reset, L"Reset", L"KNN: Reset...") LABEL (L"", L"Warning: this command destroys all previous learning.") OK DO iam_ONLY (KNN); forget (my input); forget (my output); my nInstances = 0; praat_dataChanged (me); // BUG: this should be inserted much more often END DIRECT (KNN_shuffle) iam_ONLY (KNN); if (my nInstances > 0) KNN_shuffleInstances (me); else Melder_throw ("Instance base is empty."); END FORM (KNN_prune, L"Pruning", L"KNN: Prune...") POSITIVE (L"Noise pruning degree", L"1") POSITIVE (L"Redundancy pruning degree", L"1") INTEGER (L"k neighbours", L"1") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty."); long oldn = my nInstances; // save before it changes! long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); double n = GET_REAL (L"Noise pruning degree"); double r = GET_REAL (L"Redundancy pruning degree"); if (n <= 0 || n > 1 || r <= 0 || r > 1) Melder_throw ("Please select a pruning degree d such that 0 < d <= 1."); long npruned = KNN_prune_prune (me, n, r, k); Melder_information (Melder_integer (npruned), L" instances discarded. \n", L"Size of new instance base: ", Melder_integer (oldn - npruned)); END ///////////////////////////////////////////////////////////////////////////////////////// // Learning // ///////////////////////////////////////////////////////////////////////////////////////// FORM (KNN_learn, L"Learning", L"kNN classifiers 1. What is a kNN classifier?") RADIO (L"Learning method", 1) RADIOBUTTON (L"Append new information") RADIOBUTTON (L"Replace current intancebase") RADIO (L"Ordering", 1) RADIOBUTTON (L"Random") RADIOBUTTON (L"Sequential") OK DO iam_ONLY (KNN); thouart_ONLY (Pattern); heis_ONLY (Categories); int ordering = GET_INTEGER (L"Ordering"); switch (ordering) { case 1: ordering = kOla_SHUFFLE; break; case 2: ordering = kOla_SEQUENTIAL; } int method = GET_INTEGER (L"Learning method"); int result = kOla_ERROR; switch (method) { case 1: result = KNN_learn (me, thee, him, my nInstances == 0 ? kOla_REPLACE : kOla_APPEND, ordering); break; case 2: result = KNN_learn (me, thee, him, kOla_REPLACE, ordering); break; } switch (result) { case kOla_PATTERN_CATEGORIES_MISMATCH: Melder_throw ("The number of Categories should be equal to the number of rows in Pattern."); case kOla_DIMENSIONALITY_MISMATCH: Melder_throw ("The dimensionality of Pattern should be equal to that of the instance base."); } END ///////////////////////////////////////////////////////////////////////////////////////// // Evaluation // ///////////////////////////////////////////////////////////////////////////////////////// FORM (KNN_evaluateWithTestSet, L"Evaluation", L"KNN & Pattern & Categories: Evaluate...") INTEGER (L"k neighbours", L"1") RADIO (L"Vote weighting", 1) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty"); thouart_ONLY (Pattern); heis_ONLY (Categories); long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); int vt = GET_INTEGER (L"Vote weighting"); switch (vt) { case 1: vt = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: vt = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: vt = kOla_FLAT_VOTING; break; } if (thy ny != his size) Melder_throw ("The number of Categories should be equal to the number of rows in Pattern."); if (thy nx != (my input)->nx) Melder_throw ("The dimensionality of Pattern should be equal to that of the instance base."); autoFeatureWeights fws = FeatureWeights_create (thy nx); double result = KNN_evaluateWithTestSet (me, thee, him, fws.peek(), k, vt); Melder_information (Melder_double (100 * result), L" percent of the instances correctly classified."); END FORM (KNN_evaluateWithTestSetAndFeatureWeights, L"Evaluation", L"KNN & Pattern & Categories & FeatureWeights: Evaluate...") INTEGER (L"k neighbours", L"1") RADIO (L"Vote weighting", 1) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty"); Pattern p = (Pattern) ONLY (classPattern); Categories c = (Categories) ONLY (classCategories); FeatureWeights fws = (FeatureWeights) ONLY (classFeatureWeights); long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); int vt = GET_INTEGER (L"Vote weighting"); switch (vt) { case 1: vt = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: vt = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: vt = kOla_FLAT_VOTING; break; } if (p -> ny != c -> size) Melder_throw ("The number of Categories should be equal to the number of rows in Pattern."); if (p -> nx != my input -> nx) Melder_throw ("The dimensionality of Pattern should be equal to that of the instance base."); if (p->nx != fws -> fweights -> numberOfColumns) Melder_throw ("The number of feature weights should be equal to the dimensionality of the Pattern."); double result = KNN_evaluateWithTestSet (me, p, c, fws, k, vt); Melder_information (Melder_double (100 * result), L" percent of the instances correctly classified."); END ///////////////////////////////////////////////////////////////////////////////////////// // Classification // ///////////////////////////////////////////////////////////////////////////////////////// FORM (KNN_toCategories, L"Classification", L"KNN & Pattern: To Categories...") INTEGER (L"k neighbours", L"1") RADIO (L"Vote weighting", 1) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty."); thouart_ONLY (Pattern); long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); int vt = GET_INTEGER (L"Vote weighting"); switch (vt) { case 1: vt = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: vt = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: vt = kOla_FLAT_VOTING; break; } if (thy nx != my input -> nx) Melder_throw ("The dimensionality of Pattern should match that of the instance base."); autoFeatureWeights fws = FeatureWeights_create (thy nx); praat_new (KNN_classifyToCategories (me, thee, fws.peek(), k, vt), L"Output"); END FORM (KNN_toTableOfReal, L"Classification", L"KNN & Pattern: To TabelOfReal...") INTEGER (L"k neighbours", L"1") RADIO (L"Vote weighting", 1) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty."); thouart_ONLY (Pattern); long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); autoFeatureWeights fws = FeatureWeights_create(thy nx); int vt = GET_INTEGER (L"Vote weighting"); switch (vt) { case 1: vt = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: vt = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: vt = kOla_FLAT_VOTING; break; } if (thy nx != my input -> nx) Melder_throw ("The dimensionality of Pattern should match that of the instance base."); praat_new (KNN_classifyToTableOfReal (me, thee, fws.peek(), k, vt), L"Output"); END FORM (KNN_toCategoriesWithFeatureWeights, L"Classification", L"KNN & Pattern & FeatureWeights: To Categories...") INTEGER (L"k neighbours", L"KNN & Pattern & FeatureWeights: To Categories...") RADIO (L"Vote weighting", 1) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty."); thouart_ONLY (Pattern); heis_ONLY (FeatureWeights); int vt = GET_INTEGER (L"Vote weighting"); switch (vt) { case 1: vt = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: vt = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: vt = kOla_FLAT_VOTING; break; } long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); if (thy nx != (my input)->nx) Melder_throw ("The dimensionality of Pattern should be equal to that of the instance base."); if (thy nx != his fweights -> numberOfColumns) Melder_throw ("The number of feature weights should be equal to the dimensionality of the Pattern."); praat_new (KNN_classifyToCategories (me, thee, him, k, vt), L"Output"); END FORM (KNN_toTableOfRealWithFeatureWeights, L"Classification", L"KNN & Pattern & FeatureWeights: To TableOfReal...") INTEGER (L"k neighbours", L"1") RADIO (L"Vote weighting", 1) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty."); thouart_ONLY (Pattern); heis_ONLY (FeatureWeights); long k = GET_INTEGER (L"k neighbours"); int vt = GET_INTEGER (L"Vote weighting"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "\n"); if (thy nx != his fweights -> numberOfColumns) Melder_throw ("The number of features and the number of feature weights should be equal."); switch (vt) { case 1: vt = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: vt = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: vt = kOla_FLAT_VOTING; break; } praat_new (KNN_classifyToTableOfReal (me, thee, him, k, vt), L"Output"); END ///////////////////////////////////////////////////////////////////////////////////////// // Clustering // ///////////////////////////////////////////////////////////////////////////////////////// FORM (Pattern_to_Categories_cluster, L"k-means clustering", L"Pattern: To Categories...") INTEGER (L"k clusters", L"1") POSITIVE (L"Cluster size ratio constraint", L"0.0000001"); INTEGER (L"Maximum number of reseeds", L"1000") OK DO iam_ONLY (Pattern); if (my nx > 0 && my ny > 0) { long k = GET_INTEGER (L"k clusters"); if (k < 1 || k > my ny) Melder_throw ("Please select a value of k such that 0 < k <= ", my ny, "."); long rs = GET_INTEGER (L"Maximum number of reseeds"); if (rs < 0) Melder_throw ("The maximum number of reseeds should not be negative."); double rc = GET_REAL (L"Cluster size ratio constraint"); if (rc > 1 || rc <= 0) Melder_throw ("Please select a value of the cluster size ratio constraint c such that 0 < c <= 1."); autoFeatureWeights fws = FeatureWeights_create (my nx); praat_new (Pattern_to_Categories_cluster (me, fws.peek(), k, rc, rs), L"Output"); } else { Melder_throw ("Pattern is empty."); } END FORM (Pattern_to_Categories_clusterWithFeatureWeights, L"k-means clustering", L"Pattern & FeatureWeights: To Categories...") INTEGER (L"k clusters", L"1") POSITIVE (L"Cluster size ratio constraint", L"0.0000001"); INTEGER (L"Maximum number of reseeds", L"1000") OK DO iam_ONLY (Pattern); if (my nx > 0 && my ny > 0) { thouart_ONLY (FeatureWeights); if (my nx != thy fweights -> numberOfColumns) Melder_throw ("The number of features and the number of feature weights should be equal."); long k = GET_INTEGER(L"k clusters"); if (k < 1 || k > my ny) Melder_throw ("Please select a value of k such that 0 < k <= ", my ny, "."); long rs = GET_INTEGER(L"Maximum number of reseeds"); if (rs < 0) Melder_throw ("The maximum number of reseeds should not be negative."); double rc = GET_REAL(L"Cluster size ratio constraint"); if (rc > 1 || rc <= 0) Melder_throw ("Please select a value of the cluster size ratio constraint c such that 0 < c <= 1."); praat_new (Pattern_to_Categories_cluster (me, thee, k, rc, rs), L"Output"); } else { Melder_throw ("Pattern is empty."); } END ///////////////////////////////////////////////////////////////////////////////////////// // Dissimilarity computations // ///////////////////////////////////////////////////////////////////////////////////////// DIRECT (KNN_patternToDissimilarity) iam_ONLY (Pattern); autoFeatureWeights fws = FeatureWeights_create (my nx); praat_new (KNN_patternToDissimilarity (me, fws.peek()), L"Output"); END DIRECT (KNN_patternToDissimilarityWithFeatureWeights) iam_ONLY (Pattern); thouart_ONLY (FeatureWeights); if (my nx != thy fweights -> numberOfColumns) Melder_throw ("The number of features and the number of feature weights should be equal."); praat_new (KNN_patternToDissimilarity (me, thee), L"Output"); END ///////////////////////////////////////////////////////////////////////////////////////// // Computation of permutation // ///////////////////////////////////////////////////////////////////////////////////////// FORM (KNN_SA_computePermutation, L"To Permutation...", L"Pattern & Categories: To FeatureWeights...") NATURAL(L"Tries per step", L"200") NATURAL(L"Iterations", L"10") POSITIVE(L"Step size", L"10") POSITIVE(L"Boltzmann constant", L"1.0") POSITIVE(L"Initial temperature", L"0.002") POSITIVE(L"Damping factor", L"1.005") POSITIVE(L"Final temperature", L"0.000002") OK DO iam_ONLY (KNN); long tries = GET_INTEGER (L"Tries per step"); long iterations = GET_INTEGER (L"Iterations"); double step_size = GET_REAL (L"Step size"); double bolzmann_c = GET_REAL (L"Boltzmann constant"); double temp_start = GET_REAL (L"Initial temperature"); double temp_damp = GET_REAL (L"Damping factor"); double temp_stop = GET_REAL (L"Final temperature"); praat_new (KNN_SA_ToPermutation (me, tries, iterations, step_size, bolzmann_c, temp_start, temp_damp, temp_stop), L"Output"); END ///////////////////////////////////////////////////////////////////////////////////////// // Computation of feature weights // ///////////////////////////////////////////////////////////////////////////////////////// FORM (FeatureWeights_computeRELIEF, L"Feature weights", L"Pattern & Categories: To FeatureWeights...") INTEGER (L"Number of neighbours", L"1") OK DO iam_ONLY (Pattern); thouart_ONLY (Categories); if (my ny < 2) Melder_throw ("The Pattern object should contain at least 2 rows."); if (my ny != thy size) Melder_throw ("The number of rows in the Pattern object should equal the number of categories in the Categories object."); praat_new (FeatureWeights_compute (me, thee, GET_INTEGER (L"Number of neighbours")), L"Output"); END FORM (FeatureWeights_computeWrapperExt, L"Feature weights", L"KNN & Pattern & Categories: To FeatureWeights..") POSITIVE(L"Learning rate", L"0.02") NATURAL(L"Number of seeds", L"20") POSITIVE(L"Stop at", L"1") RADIO (L"Optimization", 1) RADIOBUTTON (L"Co-optimization") RADIOBUTTON (L"Single feature") NATURAL (L"k neighbours", L"1") RADIO (L"Vote weighting", 3) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty"); thouart_ONLY (Pattern); heis_ONLY (Categories); int mode = GET_INTEGER (L"Vote weighting"); switch (mode) { case 1: mode = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: mode = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: mode = kOla_FLAT_VOTING; break; } long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); if (thy nx != my input -> nx) Melder_throw ("The dimensionality of Pattern should be equal to that of the instance base."); praat_new (FeatureWeights_computeWrapperExt (me, thee, him, k, mode, GET_INTEGER (L"Number of seeds"), GET_REAL (L"Learning rate"), GET_REAL (L"Stop at"), (int) GET_INTEGER (L"Optimization")), L"Output"); END FORM (FeatureWeights_computeWrapperInt, L"Feature weights", L"KNN: To FeatureWeights...") POSITIVE(L"Learning rate", L"0.02") NATURAL(L"Number of seeds", L"10") POSITIVE(L"Stop at", L"1") RADIO (L"Optimization", 1) RADIOBUTTON (L"Co-optimization") RADIOBUTTON (L"Single feature") RADIO (L"Evaluation method", 1) RADIOBUTTON (L"Leave one out") RADIOBUTTON (L"10-fold cross-validation") NATURAL (L"k neighbours", L"1") RADIO (L"Vote weighting", 3) RADIOBUTTON (L"Inversed squared distance") RADIOBUTTON (L"Inversed distance") RADIOBUTTON (L"Flat") OK DO iam_ONLY (KNN); if (my nInstances < 1) Melder_throw ("Instance base is empty"); int emode = GET_INTEGER (L"Evaluation method"); switch (emode) { case 2: emode = kOla_TEN_FOLD_CROSS_VALIDATION; break; case 1: emode = kOla_LEAVE_ONE_OUT; break; } int mode = GET_INTEGER (L"Vote weighting"); switch (mode) { case 1: mode = kOla_SQUARED_DISTANCE_WEIGHTED_VOTING; break; case 2: mode = kOla_DISTANCE_WEIGHTED_VOTING; break; case 3: mode = kOla_FLAT_VOTING; break; } long k = GET_INTEGER (L"k neighbours"); if (k < 1 || k > my nInstances) Melder_throw ("Please select a value of k such that 0 < k < ", my nInstances + 1, "."); praat_new (FeatureWeights_computeWrapperInt (me, k, mode, GET_INTEGER (L"Number of seeds"), GET_REAL (L"Learning rate"), GET_REAL (L"Stop at"), (int) GET_INTEGER (L"Optimization"), emode), L"Output"); END ///////////////////////////////////////////////////////////////////////////////////////// // Creation and processing of auxiliary datatypes // ///////////////////////////////////////////////////////////////////////////////////////// FORM (Pattern_create, L"Create Pattern", 0) WORD (L"Name", L"1x1") NATURAL (L"Dimension of a pattern", L"1") NATURAL (L"Number of patterns", L"1") OK DO praat_new (Pattern_create (GET_INTEGER (L"Number of patterns"), GET_INTEGER (L"Dimension of a pattern")), GET_STRING (L"Name")); END FORM (Categories_create, L"Create Categories", 0) WORD (L"Name", L"empty") OK DO praat_new (Categories_create (), GET_STRING (L"Name")); END FORM (FeatureWeights_create, L"Create FeatureWeights", 0) WORD (L"Name", L"empty") NATURAL (L"Number of weights", L"1") OK DO praat_new (FeatureWeights_create (GET_INTEGER (L"Number of weights")), GET_STRING (L"Name")); END ///////////////////////////////////////////////////////////////////////////////////////// // DEBUG // ///////////////////////////////////////////////////////////////////////////////////////// // Disabled /* #ifdef _DEBUG DIRECT (KNN_debug_KNN_SA_partition) Pattern p = ONLY (classPattern); Pattern output = Pattern_create (p->ny, p->nx); autoNUMvector result (0, p->ny); KNN_SA_partition (p, 1, p->ny, result); for (long k = 1, c = 1; k <= output->ny; ++k, ++c) for (long i = 1; i <= p->ny && k <= output->ny; ++i) if(result [i] == c) { for(long j = 1; j <= output->nx; ++j) output->z[k][j] = p->z[i][j]; ++k; } praat_new (output, L"Output"); END DIRECT (KNN_debug_KNN_getNumberOfCPUs) Melder_information (Melder_integer(KNN_getNumberOfCPUs()), L" CPUs available"); END DIRECT (KNN_debug_KNN_threadTest) KNN_threadTest(); END #endif */ ///////////////////////////////////////////////////////////////////////////////////////// // Help // ///////////////////////////////////////////////////////////////////////////////////////// DIRECT (KNN_help) Melder_help (L"KNN classifiers"); END DIRECT (hint_KNN_and_FeatureWeights_evaluate) Melder_information (L"The accuracy of a KNN can be estimated by selecting a KNN and a FeatureWeights object and choosing \"Evaluate...\"."); END DIRECT (hint_KNN_and_Pattern_classify) Melder_information (L"You can use the KNN as a classifier by selecting a KNN and a Pattern and choosing \"To Categories...\" or \"To TableOfReal...\"."); END DIRECT (hint_KNN_and_Pattern_and_FeatureWeights_classify) Melder_information (L"You can use the KNN as a classifier by selecting a KNN, a Pattern and an FeatureWeights object and choosing \"To Categories...\" or \"To TableOfReal...\"."); END DIRECT (hint_KNN_and_Pattern_and_Categories_learn) Melder_information (L"You can train a KNN by selecting a KNN, a Pattern and a Categories object together and choosing \"Learn...\"."); END DIRECT (hint_KNN_and_Pattern_and_Categories_evaluate) Melder_information (L"The accuracy of a KNN can be estimated by selecting a KNN, a test Pattern and the corresponding Categories object and choosing \"Evaluate...\"."); END DIRECT (hint_KNN_and_Pattern_and_Categories_and_FeatureWeights_evaluate) Melder_information (L"The accuracy of a KNN can be estimated by selecting a KNN, a test Pattern, an FeatureWeights object, and the corresponding Categories object and choosing \"Evaluate...\"."); END DIRECT (hint_Pattern_and_FeatureWeights_to_Categories) Melder_information (L"A Pattern object and a FeatureWeights object can be used to compute a fixed number of clusters using the k-means clustering clustering algorithm."); END DIRECT (hint_Pattern_and_FeatureWeights_to_Dissimilarity) Melder_information (L"A Dissimilarity matrix can be generated from a Pattern and a FeatureWeights object."); END ///////////////////////////////////////////////////////////////////////////////////////// // Setting callbacks // ///////////////////////////////////////////////////////////////////////////////////////// void praat_contrib_Ola_KNN_init (void); void praat_contrib_Ola_KNN_init (void) { Thing_recognizeClassesByName (classKNN, NULL); Thing_recognizeClassesByName (classFeatureWeights, NULL); ////////// // Menu // ////////// praat_addMenuCommand (L"Objects", L"New", L"kNN classifiers", 0, 0, 0); praat_addMenuCommand (L"Objects", L"New", L"kNN classifiers", 0, 1, DO_KNN_help); praat_addMenuCommand (L"Objects", L"New", L"-- KNN --", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Create kNN classifier...", 0, 1, DO_KNN_create); praat_addMenuCommand (L"Objects", L"New", L"Advanced", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Create Pattern...", 0, 2, DO_Pattern_create); praat_addMenuCommand (L"Objects", L"New", L"Create Categories...", 0, 2, DO_Categories_create); praat_addMenuCommand (L"Objects", L"New", L"Create FeatureWeights...", 0, 2, DO_FeatureWeights_create); ///////////// // Actions // ///////////// praat_addAction1 (classKNN, 0, L"kNN help", 0, 0, DO_KNN_help); praat_addAction1 (classKNN, 0, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (classKNN, 1, L"Get optimized parameters...", 0, 2, DO_KNN_getOptimumModel); praat_addAction1 (classKNN, 1, L"Get accuracy estimate...", 0, 2, DO_KNN_evaluate); praat_addAction1 (classKNN, 1, L"Get size of instancebase", 0, 2, DO_KNN_getNumberOfInstances); praat_addAction1 (classKNN, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classKNN, 1, L"Shuffle", 0, 1, DO_KNN_shuffle); praat_addAction1 (classKNN, 1, L"Prune...", 0, 1, DO_KNN_prune); praat_addAction1 (classKNN, 1, L"Reset...", 0, 1, DO_KNN_reset); praat_addAction1 (classKNN, 0, EXTRACT_BUTTON, 0, 0, 0); praat_addAction1 (classKNN, 0, L"Extract input Patterns", 0, 1, DO_KNN_extractInputPatterns); praat_addAction1 (classKNN, 0, L"Extract output Categories", 0, 1, DO_KNN_extractOutputCategories); praat_addAction1 (classKNN, 0, L"To FeatureWeights...", 0, 0, DO_FeatureWeights_computeWrapperInt); // praat_addAction1 (classKNN, 0, L"To Permutation...", 0, 0, DO_KNN_SA_computePermutation); // praat_addAction2 (classKNN, 1, classFeatureWeights, 1, L"To Permutation...", 0, 0, DO_KNN_evaluateWithFeatureWeights); praat_addAction (classKNN, 1, classPattern, 1, classCategories, 1, L"Learn...", 0, 0, DO_KNN_learn); praat_addAction2 (classKNN, 1, classFeatureWeights, 1, L"Evaluate...", 0, 0, DO_KNN_evaluateWithFeatureWeights); praat_addAction (classKNN, 1, classPattern, 1, classCategories, 1, L"Evaluate...", 0, 0, DO_KNN_evaluateWithTestSet); praat_addAction4 (classKNN, 1, classPattern, 1, classCategories, 1, classFeatureWeights, 1, L"Evaluate...", 0, 0, DO_KNN_evaluateWithTestSetAndFeatureWeights); praat_addAction (classKNN, 1, classPattern, 1, classCategories, 1, L"To FeatureWeights...", 0, 0, DO_FeatureWeights_computeWrapperExt); praat_addAction2 (classKNN, 1, classPattern, 1, L"To Categories...", 0, 0, DO_KNN_toCategories); praat_addAction2 (classKNN, 1, classPattern, 1, L"To TableOfReal...", 0, 0, DO_KNN_toTableOfReal); praat_addAction (classKNN, 1, classPattern, 1, classFeatureWeights, 1, L"To Categories...", 0, 0, DO_KNN_toCategoriesWithFeatureWeights); praat_addAction (classKNN, 1, classPattern, 1, classFeatureWeights, 1, L"To TableOfReal...", 0, 0, DO_KNN_toTableOfRealWithFeatureWeights); praat_addAction1 (classPattern, 1, L"To Dissimilarity", 0, 1, DO_KNN_patternToDissimilarity); praat_addAction1 (classPattern, 1, L"To Categories...", 0, 1, DO_Pattern_to_Categories_cluster); praat_addAction2 (classPattern, 1, classFeatureWeights, 1, L"To Dissimilarity", 0, 0, DO_KNN_patternToDissimilarityWithFeatureWeights); praat_addAction2 (classPattern, 1, classFeatureWeights, 1, L"To Categories...", 0, 0, DO_Pattern_to_Categories_clusterWithFeatureWeights); praat_addAction2 (classPattern, 1, classCategories, 1, L"To FeatureWeights...", 0, 0, DO_FeatureWeights_computeRELIEF); praat_addAction2 (classPattern, 1, classCategories, 1, L"To KNN Classifier...", 0, 0, DO_KNN_Pattern_Categories_to_KNN); /////////// // DEBUG // /////////// /* #ifdef _DEBUG praat_addAction1 (classKNN, 0, L"_DEBUG: KNN_getNumberOfCPUs", 0, 0, DO_KNN_debug_KNN_getNumberOfCPUs); praat_addAction1 (classKNN, 0, L"_DEBUG: KNN_threadTest", 0, 0, DO_KNN_debug_KNN_threadTest); praat_addAction1 (classPattern, 1, L"_DEBUG: KNN_SA_partition", 0, 1, DO_KNN_debug_KNN_SA_partition); #endif */ /////////// // Hints // /////////// praat_addAction1 (classPattern, 0, L"& FeatureWeights: To Categories?", 0, 0, DO_hint_Pattern_and_FeatureWeights_to_Categories); praat_addAction1 (classPattern, 0, L"& FeatureWeights: To Dissimilarity?", 0, 0, DO_hint_Pattern_and_FeatureWeights_to_Dissimilarity); praat_addAction1 (classKNN, 0, L"& FeatureWeights: Evaluate?", 0, 0, DO_hint_KNN_and_FeatureWeights_evaluate); // praat_addAction1 (classKNN, 0, L"& FeatureWeights: To Permutation?", 0, 0, DO_hint_Pattern_and_FeatureWeights_to_Dissimilarity); praat_addAction1 (classKNN, 0, L"& Pattern: Classify?", 0, 0, DO_hint_KNN_and_Pattern_classify); praat_addAction1 (classKNN, 0, L"& Pattern & FeatureWeights: Classify?", 0, 0, DO_hint_KNN_and_Pattern_and_FeatureWeights_classify); praat_addAction1 (classKNN, 0, L"& Pattern & Categories: Learn?", 0, 0, DO_hint_KNN_and_Pattern_and_Categories_learn); praat_addAction1 (classKNN, 0, L"& Pattern & Categories: Evaluate?", 0, 0, DO_hint_KNN_and_Pattern_and_Categories_evaluate); praat_addAction1 (classKNN, 0, L"& Pattern & Categories & FeatureWeights: Evaluate?", 0, 0, DO_hint_KNN_and_Pattern_and_Categories_and_FeatureWeights_evaluate); INCLUDE_MANPAGES (manual_KNN_init) } sources_5316/main/0000755000176700017670000000000011746732140012654 5ustar paulpaulsources_5316/main/GNU_General_Public_License.txt0000644000176700017670000004262507575637520020467 0ustar paulpaulGNU GENERAL PUBLIC LICENSE Version 2, June 1991 Copyright (C) 1989, 1991 Free Software Foundation, Inc. 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. Preamble The licenses for most software are designed to take away your freedom to share and change it. By contrast, the GNU General Public License is intended to guarantee your freedom to share and change free software--to make sure the software is free for all its users. This General Public License applies to most of the Free Software Foundation's software and to any other program whose authors commit to using it. (Some other Free Software Foundation software is covered by the GNU Library General Public License instead.) You can apply it to your programs, too. When we speak of free software, we are referring to freedom, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for this service if you wish), that you receive source code or can get it if you want it, that you can change the software or use pieces of it in new free programs; and that you know you can do these things. To protect your rights, we need to make restrictions that forbid anyone to deny you these rights or to ask you to surrender the rights. These restrictions translate to certain responsibilities for you if you distribute copies of the software, or if you modify it. For example, if you distribute copies of such a program, whether gratis or for a fee, you must give the recipients all the rights that you have. You must make sure that they, too, receive or can get the source code. And you must show them these terms so they know their rights. We protect your rights with two steps: (1) copyright the software, and (2) offer you this license which gives you legal permission to copy, distribute and/or modify the software. Also, for each author's protection and ours, we want to make certain that everyone understands that there is no warranty for this free software. If the software is modified by someone else and passed on, we want its recipients to know that what they have is not the original, so that any problems introduced by others will not reflect on the original authors' reputations. Finally, any free program is threatened constantly by software patents. We wish to avoid the danger that redistributors of a free program will individually obtain patent licenses, in effect making the program proprietary. To prevent this, we have made it clear that any patent must be licensed for everyone's free use or not licensed at all. The precise terms and conditions for copying, distribution and modification follow. TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION 0. This License applies to any program or other work which contains a notice placed by the copyright holder saying it may be distributed under the terms of this General Public License. The "Program", below, refers to any such program or work, and a "work based on the Program" means either the Program or any derivative work under copyright law: that is to say, a work containing the Program or a portion of it, either verbatim or with modifications and/or translated into another language. (Hereinafter, translation is included without limitation in the term "modification".) Each licensee is addressed as "you". Activities other than copying, distribution and modification are not covered by this License; they are outside its scope. The act of running the Program is not restricted, and the output from the Program is covered only if its contents constitute a work based on the Program (independent of having been made by running the Program). Whether that is true depends on what the Program does. 1. You may copy and distribute verbatim copies of the Program's source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice and disclaimer of warranty; keep intact all the notices that refer to this License and to the absence of any warranty; and give any other recipients of the Program a copy of this License along with the Program. You may charge a fee for the physical act of transferring a copy, and you may at your option offer warranty protection in exchange for a fee. 2. You may modify your copy or copies of the Program or any portion of it, thus forming a work based on the Program, and copy and distribute such modifications or work under the terms of Section 1 above, provided that you also meet all of these conditions: a) You must cause the modified files to carry prominent notices stating that you changed the files and the date of any change. b) You must cause any work that you distribute or publish, that in whole or in part contains or is derived from the Program or any part thereof, to be licensed as a whole at no charge to all third parties under the terms of this License. c) If the modified program normally reads commands interactively when run, you must cause it, when started running for such interactive use in the most ordinary way, to print or display an announcement including an appropriate copyright notice and a notice that there is no warranty (or else, saying that you provide a warranty) and that users may redistribute the program under these conditions, and telling the user how to view a copy of this License. (Exception: if the Program itself is interactive but does not normally print such an announcement, your work based on the Program is not required to print an announcement.) These requirements apply to the modified work as a whole. If identifiable sections of that work are not derived from the Program, and can be reasonably considered independent and separate works in themselves, then this License, and its terms, do not apply to those sections when you distribute them as separate works. But when you distribute the same sections as part of a whole which is a work based on the Program, the distribution of the whole must be on the terms of this License, whose permissions for other licensees extend to the entire whole, and thus to each and every part regardless of who wrote it. Thus, it is not the intent of this section to claim rights or contest your rights to work written entirely by you; rather, the intent is to exercise the right to control the distribution of derivative or collective works based on the Program. In addition, mere aggregation of another work not based on the Program with the Program (or with a work based on the Program) on a volume of a storage or distribution medium does not bring the other work under the scope of this License. 3. You may copy and distribute the Program (or a work based on it, under Section 2) in object code or executable form under the terms of Sections 1 and 2 above provided that you also do one of the following: a) Accompany it with the complete corresponding machine-readable source code, which must be distributed under the terms of Sections 1 and 2 above on a medium customarily used for software interchange; or, b) Accompany it with a written offer, valid for at least three years, to give any third party, for a charge no more than your cost of physically performing source distribution, a complete machine-readable copy of the corresponding source code, to be distributed under the terms of Sections 1 and 2 above on a medium customarily used for software interchange; or, c) Accompany it with the information you received as to the offer to distribute corresponding source code. (This alternative is allowed only for noncommercial distribution and only if you received the program in object code or executable form with such an offer, in accord with Subsection b above.) The source code for a work means the preferred form of the work for making modifications to it. For an executable work, complete source code means all the source code for all modules it contains, plus any associated interface definition files, plus the scripts used to control compilation and installation of the executable. However, as a special exception, the source code distributed need not include anything that is normally distributed (in either source or binary form) with the major components (compiler, kernel, and so on) of the operating system on which the executable runs, unless that component itself accompanies the executable. If distribution of executable or object code is made by offering access to copy from a designated place, then offering equivalent access to copy the source code from the same place counts as distribution of the source code, even though third parties are not compelled to copy the source along with the object code. 4. You may not copy, modify, sublicense, or distribute the Program except as expressly provided under this License. Any attempt otherwise to copy, modify, sublicense or distribute the Program is void, and will automatically terminate your rights under this License. However, parties who have received copies, or rights, from you under this License will not have their licenses terminated so long as such parties remain in full compliance. 5. You are not required to accept this License, since you have not signed it. However, nothing else grants you permission to modify or distribute the Program or its derivative works. These actions are prohibited by law if you do not accept this License. Therefore, by modifying or distributing the Program (or any work based on the Program), you indicate your acceptance of this License to do so, and all its terms and conditions for copying, distributing or modifying the Program or works based on it. 6. Each time you redistribute the Program (or any work based on the Program), the recipient automatically receives a license from the original licensor to copy, distribute or modify the Program subject to these terms and conditions. You may not impose any further restrictions on the recipients' exercise of the rights granted herein. You are not responsible for enforcing compliance by third parties to this License. 7. If, as a consequence of a court judgment or allegation of patent infringement or for any other reason (not limited to patent issues), conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot distribute so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not distribute the Program at all. For example, if a patent license would not permit royalty-free redistribution of the Program by all those who receive copies directly or indirectly through you, then the only way you could satisfy both it and this License would be to refrain entirely from distribution of the Program. If any portion of this section is held invalid or unenforceable under any particular circumstance, the balance of the section is intended to apply and the section as a whole is intended to apply in other circumstances. It is not the purpose of this section to induce you to infringe any patents or other property right claims or to contest validity of any such claims; this section has the sole purpose of protecting the integrity of the free software distribution system, which is implemented by public license practices. Many people have made generous contributions to the wide range of software distributed through that system in reliance on consistent application of that system; it is up to the author/donor to decide if he or she is willing to distribute software through any other system and a licensee cannot impose that choice. This section is intended to make thoroughly clear what is believed to be a consequence of the rest of this License. 8. If the distribution and/or use of the Program is restricted in certain countries either by patents or by copyrighted interfaces, the original copyright holder who places the Program under this License may add an explicit geographical distribution limitation excluding those countries, so that distribution is permitted only in or among countries not thus excluded. In such case, this License incorporates the limitation as if written in the body of this License. 9. The Free Software Foundation may publish revised and/or new versions of the General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns. Each version is given a distinguishing version number. If the Program specifies a version number of this License which applies to it and "any later version", you have the option of following the terms and conditions either of that version or of any later version published by the Free Software Foundation. If the Program does not specify a version number of this License, you may choose any version ever published by the Free Software Foundation. 10. If you wish to incorporate parts of the Program into other free programs whose distribution conditions are different, write to the author to ask for permission. For software which is copyrighted by the Free Software Foundation, write to the Free Software Foundation; we sometimes make exceptions for this. Our decision will be guided by the two goals of preserving the free status of all derivatives of our free software and of promoting the sharing and reuse of software generally. NO WARRANTY 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. END OF TERMS AND CONDITIONS How to Apply These Terms to Your New Programs If you develop a new program, and you want it to be of the greatest possible use to the public, the best way to achieve this is to make it free software which everyone can redistribute and change under these terms. To do so, attach the following notices to the program. It is safest to attach them to the start of each source file to most effectively convey the exclusion of warranty; and each file should have at least the "copyright" line and a pointer to where the full notice is found. one line to give the program's name and an idea of what it does. Copyright (C) yyyy name of author This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. Also add information on how to contact you by electronic and paper mail. If the program is interactive, make it output a short notice like this when it starts in an interactive mode: Gnomovision version 69, Copyright (C) year name of author Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. This is free software, and you are welcome to redistribute it under certain conditions; type `show c' for details. The hypothetical commands `show w' and `show c' should show the appropriate parts of the General Public License. Of course, the commands you use may be called something other than `show w' and `show c'; they could even be mouse-clicks or menu items--whatever suits your program. You should also get your employer (if you work as a programmer) or your school, if any, to sign a "copyright disclaimer" for the program, if necessary. Here is a sample; alter the names: Yoyodyne, Inc., hereby disclaims all copyright interest in the program `Gnomovision' (which makes passes at compilers) written by James Hacker. signature of Ty Coon, 1 April 1989 Ty Coon, President of Vice This General Public License does not permit incorporating your program into proprietary programs. If your program is a subroutine library, you may consider it more useful to permit linking proprietary applications with the library. If this is what you want to do, use the GNU Library General Public License instead of this License. sources_5316/main/Makefile0000644000176700017670000000055711632715371014324 0ustar paulpaul# Makefile of the 'main' routines. # Paul Boersma, 10 September 2011 include ../makefile.defs CPPFLAGS = -I ../num -I ../sys -I ../fon .PHONY: clean main_*.o: ../sys/praat.h ../sys/praat_version.h ../sys/Graphics.h clean: $(RM) main_*.o $(RM) praat_win.o # The following is only for Windows. praat_win.o: praat_win.rc $(WINDRES) -o praat_win.o praat_win.rc sources_5316/main/praat_win.ico0000644000176700017670000000137607575636771015365 0ustar paulpaul è( @€œÎüÌfüdœÿÿÿ{ê r¤u¿ð›ér‚""""""""""""""""""""""""" """ 333333""""""333333"""""" 333333""""""33333""""" 3333"" ""30"" "" """"""""" """""""""" " """ ÿþÿÿüÿÿøÿÿðÿÿàÿÿÀÿÿ€?ÿÿÿÿÿÿ?ÿÿÿÿÿÿÿÿ€ÿÿÿÿÿüÿð?àÀ€€àøþÿÿÿ€ÿÿÀÿÿÀÿÿáÿÿóŸÿsources_5316/main/praat_mac.plist0000644000176700017670000002505511746732140015667 0ustar paulpaul CFBundleDevelopmentRegion English CFBundleDocumentTypes CFBundleTypeExtensions Collection CFBundleTypeName Collection of Praat objects CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions praat CFBundleTypeName Praat script CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions aifc CFBundleTypeName AIFC audio file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions aiff CFBundleTypeName AIFF audio file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions wav CFBundleTypeName WAV audio file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions aif CFBundleTypeName AIF audio file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions mp3 CFBundleTypeName MP3 audio file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions flac CFBundleTypeName FLAC audio file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions au CFBundleTypeName Sun audio file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions Sound CFBundleTypeName Praat sound file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions Pitch CFBundleTypeName Praat pitch curve CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions Formant CFBundleTypeName Praat formant curve CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions TextGrid CFBundleTypeName Praat annotation CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions ExperimentMFC CFBundleTypeName Praat listening experiment CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions Matrix CFBundleTypeName Praat matrix CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions PointProcess CFBundleTypeName Praat point process CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions Table CFBundleTypeName Praat table CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions TableOfReal CFBundleTypeName Praat numeric table CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions OTGrammar CFBundleTypeName Praat Optimality-Theoretic grammar CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions OTMulti CFBundleTypeName Praat multi-level OT grammar CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions Distributions CFBundleTypeName Praat distribution table CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions PairDistribution CFBundleTypeName Praat distribution of string pairs CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions EEG CFBundleTypeName Praat electro-encephalogram CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions bdf CFBundleTypeName BDF electro-encephalogram CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions Movie CFBundleTypeName Praat movie file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions Corpus CFBundleTypeName Praat corpus file CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions ERPTier CFBundleTypeName Praat event-related potentials CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleTypeExtensions ERP CFBundleTypeName Praat event-related potential CFBundleTypeRole Editor LSTypeIsPackage NSPersistentStoreTypeKey Binary CFBundleExecutable Praat CFBundleGetInfoString Praat PRAAT_VERSION_STR, © 1992-PRAAT_YEAR by Paul Boersma and David Weenink CFBundleIconFile Praat CFBundleIdentifier org.praat.Praat CFBundleInfoDictionaryVersion 6.0 CFBundleName Praat CFBundlePackageType APPL CFBundleShortVersionString PRAAT_VERSION_STR CFBundleSignature PpgB CFBundleVersion PRAAT_VERSION_STR LSRequiresCarbon NSHumanReadableCopyright Copyright © 1992-PRAAT_YEAR by Paul Boersma and David Weenink sources_5316/main/praat_win.rc0000644000176700017670000000010510600163756015161 0ustar paulpaulapplication_icon ICON praat_win.ico 1 Rt_manifest praat.exe.manifest sources_5316/main/praat.exe.manifest0000644000176700017670000000140510563721470016273 0ustar paulpaul sources_5316/main/main_Praat.cpp0000644000176700017670000000400611627217345015436 0ustar paulpaul/* main_Praat.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "praat.h" #include "praat_version.h" static void logo (Graphics g) { Graphics_setWindow (g, 0, 1, 0.00, 0.80); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_setFont (g, kGraphics_font_TIMES); Graphics_setFontSize (g, 45); Graphics_setColour (g, Graphics_MAROON); Graphics_text (g, 0.385, 0.66, L"P"); Graphics_text (g, 0.448, 0.66, L"\\s{R}"); Graphics_text (g, 0.510, 0.66, L"\\s{A}"); Graphics_text (g, 0.575, 0.66, L"\\s{A}"); Graphics_text (g, 0.628, 0.66, L"\\s{T}"); Graphics_setFontSize (g, 15); Graphics_text (g, 0.5, 0.55, L"%%doing phonetics by computer"); #define xstr(s) str(s) #define str(s) #s Graphics_text (g, 0.5, 0.45, L"version " xstr(PRAAT_VERSION_STR)); Graphics_setColour (g, Graphics_BLACK); Graphics_setFontSize (g, 14); Graphics_text (g, 0.5, 0.33, L"www.praat.org"); Graphics_setFont (g, kGraphics_font_HELVETICA); Graphics_setFontSize (g, 10); Graphics_text (g, 0.5, 0.16, L"Copyright \\co 1992-" xstr(PRAAT_YEAR) " by Paul Boersma and David Weenink"); } int main (int argc, char *argv []) { praat_setLogo (130, 80, logo); praat_init ("Praat", argc, argv); INCLUDE_LIBRARY (praat_uvafon_init) INCLUDE_LIBRARY (praat_contrib_Ola_KNN_init) praat_run (); return 0; } /* End of file main_Praat.cpp */ sources_5316/dwtools/0000755000176700017670000000000011757230116013421 5ustar paulpaulsources_5316/dwtools/Matrix_extensions.h0000644000176700017670000000445711744262636017337 0ustar paulpaul#ifndef _Matrix_extensions_h_ #define _Matrix_extensions_h_ /* Matrix_extensions.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110307 Latest modification */ #include "Matrix.h" #include "Graphics.h" void Matrix_scatterPlot (I, Graphics g, long icx, long icy, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish); /* Draw my columns ix and iy as a scatterplot (with squares) */ void Matrix_drawAsSquares (I, Graphics graphics, double xmin, double xmax, double ymin, double ymax, int garnished); /* Draw a Matrix as small squares whose area correspond to the matrix element */ /* The square is filled with black if the weights are negative */ void Matrix_drawRowsAsLineSegments (I, Graphics g, double xmin, double xmax, double ymin, double ymax, double minimum, double maximum, int connect); /* draw a row as segments */ void Matrix_scale (I, int choice); /* choice = 1 :divide each elmnt by the maximum (abs) */ /* choice = 2 :rows, divide each row elmnt by the maximum (abs) of that row */ /* choice = 3 :columns, divide each col elmnt by the maximum of that col */ Matrix Matrix_transpose (I); void Matrix_drawDistribution (I, Graphics g, double xmin, double xmax, double ymin, double ymax, double minimum, double maximum, long nBins, double freqMin, double freqmax, int cumulative, int garnish); void Matrix_drawSliceY (I, Graphics g, double x, double ymin, double ymax, double min, double max); int Matrix_fitPolynomial (I, long maxDegree); Matrix Matrix_solveEquation (I, double tolerance); #endif /* _Matrix_extensions_h_ */ sources_5316/dwtools/Polynomial.h0000644000176700017670000002104611631430741015715 0ustar paulpaul#ifndef _Polynomial_h_ #define _Polynomial_h_ /* Polynomial.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110306 Latest modification. */ #define FITTER_PARAMETER_FREE 0 #define FITTER_PARAMETER_FIXED 1 #include "SimpleVector.h" #include "Function.h" #include "TableOfReal.h" #include "Graphics.h" #include "Minimizers.h" #include "Spectrum.h" #include "RealTier.h" #include "SSCP.h" #define Spline_MAXIMUM_DEGREE 20 #include "Polynomial_def.h" oo_CLASS_CREATE (FunctionTerms, Function); void FunctionTerms_init (I, double xmin, double xmax, long numberOfCoefficients); void FunctionTerms_initFromString (I, double xmin, double xmax, const wchar_t *s, int allowTrailingZeros); FunctionTerms FunctionTerms_create (double xmin, double xmax, long numberOfCoefficients); void FunctionTerms_setDomain (I, double xmin, double xmax); void FunctionTerms_setCoefficient (I, long index, double value); double FunctionTerms_evaluate (I, double x); void FunctionTerms_evaluate_z (I, dcomplex *z, dcomplex *p); void FunctionTerms_evaluateTerms (I, double x, double terms[]); void FunctionTerms_getExtrema (I, double x1, double x2, double *xmin, double *ymin, double *xmax, double *ymax); long FunctionTerms_getDegree (I); double FunctionTerms_getMinimum (I, double x1, double x2); double FunctionTerms_getXOfMinimum (I, double x1, double x2); double FunctionTerms_getMaximum (I, double x1, double x2); double FunctionTerms_getXOfMaximum (I, double x1, double x2); /* Returns minimum and maximum function values (ymin, ymax) in interval [x1, x2] and their x-values (xmin, xmax). Precondition: [x1, x2] is a (sub)domain my xmin <= x1 < x2 <= my xmax */ void FunctionTerms_draw (I, Graphics g, double xmin, double xmax, double ymin, double ymax, int extrapolate, int garnish); /* Extrapolate only for functions whose domain is extendable and that can be extrapolated. Polynomials can be extrapolated. LegendreSeries and ChebyshevSeries cannot be extrapolated. */ void FunctionTerms_drawBasisFunction (I, Graphics g, long index, double xmin, double xmax, double ymin, double ymax, int extrapolate, int garnish); Thing_define (Polynomial, FunctionTerms) { // overridden methods: public: virtual double v_evaluate (double x); virtual void v_evaluate_z (dcomplex *z, dcomplex *p); virtual void v_evaluateTerms (double x, double terms[]); virtual void v_getExtrema (double x1, double x2, double *xmin, double *ymin, double *xmax, double *ymax); //virtual long v_getDegree (); David, is het OK dat deze niet overschreven wordt? Ja }; Polynomial Polynomial_create (double xmin, double xmax, long degree); Polynomial Polynomial_createFromString (double xmin, double xmax, const wchar_t *s); void Polynomial_scaleCoefficients_monic (Polynomial me); /* Make coefficent of leading term 1.0 */ Polynomial Polynomial_scaleX (Polynomial me, double xmin, double xmax); /* x' = (x-location) / scale */ void Polynomial_evaluate_z (Polynomial me, dcomplex *z, dcomplex *p); /* Evaluate at complex z = x + iy */ double Polynomial_getArea (Polynomial me, double xmin, double xmax); Polynomial Polynomial_getDerivative (Polynomial me); Polynomial Polynomial_getPrimitive (Polynomial me); void Polynomial_draw (I, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish); double Polynomial_evaluate (I, double x); void Polynomial_evaluateTerms (I, double x, double terms[]); Polynomial Polynomials_multiply (Polynomial me, Polynomial thee); void Polynomials_divide (Polynomial me, Polynomial thee, Polynomial *q, Polynomial *r); Thing_define (LegendreSeries, FunctionTerms) { // overridden methods: public: virtual double v_evaluate (double x); virtual void v_evaluateTerms (double x, double terms[]); virtual void v_getExtrema (double x1, double x2, double *xmin, double *ymin, double *xmax, double *ymax); }; LegendreSeries LegendreSeries_create (double xmin, double xmax, long numberOfPolynomials); LegendreSeries LegendreSeries_createFromString (double xmin, double xmax, const wchar_t *s); LegendreSeries LegendreSeries_getDerivative (LegendreSeries me); Polynomial LegendreSeries_to_Polynomial (LegendreSeries me); Thing_define (Roots, ComplexVector) { }; Roots Roots_create (long numberOfRoots); void Roots_fixIntoUnitCircle (Roots me); void Roots_sort (Roots me); /* Sort to size of real part a+bi, a-bi*/ dcomplex Roots_evaluate_z (Roots me, dcomplex z); Roots Polynomial_to_Roots_ev (Polynomial me); long Roots_getNumberOfRoots (Roots me); void Roots_draw (Roots me, Graphics g, double rmin, double rmax, double imin, double imax, const wchar_t *symbol, int fontSize, int garnish); dcomplex Roots_getRoot (Roots me, long index); void Roots_setRoot (Roots me, long index, double re, double im); Spectrum Roots_to_Spectrum (Roots me, double nyquistFrequency, long numberOfFrequencies, double radius); Roots Polynomial_to_Roots (Polynomial me); /* Find roots of polynomial and polish them */ void Roots_and_Polynomial_polish (Roots me, Polynomial thee); Polynomial Roots_to_Polynomial (Roots me); Polynomial TableOfReal_to_Polynomial (I, long degree, long xcol, long ycol, long scol); LegendreSeries TableOfReal_to_LegendreSeries (I, long numberOfPolynomials, long xcol, long ycol, long scol); Spectrum Polynomial_to_Spectrum (Polynomial me, double nyquistFrequency, long numberOfFrequencies, double radius); /* A ChebyshevSeries p(x) on a domain [xmin,xmax] is defined as the following linear combination of Chebyshev polynomials T[k](x') of degree k-1 and domain [-1, 1]: p(x) = sum (k=1..numberOfCoefficients, c[k]*T[k](x')) - c[1] / 2, where x' = (2 * x - xmin - xmax) / (xmax - xmin) This is equivalent to: p(x) = c[1] /2 + sum (k=2..numberOfCoefficients, c[k]*T[k](x')) */ Thing_define (ChebyshevSeries, FunctionTerms) { // overridden methods: public: virtual double v_evaluate (double x); virtual void v_evaluateTerms (double x, double terms[]); virtual void v_getExtrema (double x1, double x2, double *xmin, double *ymin, double *xmax, double *ymax); }; ChebyshevSeries ChebyshevSeries_create (double xmin, double xmax, long numberOfPolynomials); ChebyshevSeries ChebyshevSeries_createFromString (double xmin, double xmax, const wchar_t *s); Polynomial ChebyshevSeries_to_Polynomial (ChebyshevSeries me); oo_CLASS_CREATE (Spline, FunctionTerms); void Spline_init (I, double xmin, double xmax, long degree, long numberOfCoefficients, long numberOfKnots); long Spline_getOrder (I); void Spline_drawKnots (I, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish); Spline Spline_scaleX (I, double xmin, double xmax); /* scale domain and knots to new domain */ Thing_define (MSpline, Spline) { // overridden methods: public: virtual double v_evaluate (double x); virtual void v_evaluateTerms (double x, double terms[]); }; MSpline MSpline_create (double xmin, double xmax, long degree, long numberOfInteriorKnots); MSpline MSpline_createFromStrings (double xmin, double xmax, long degree, const wchar_t *coef, const wchar_t *interiorKnots); Thing_define (ISpline, Spline) { // overridden methods: public: virtual double v_evaluate (double x); virtual void v_evaluateTerms (double x, double terms[]); virtual long v_getOrder (); }; ISpline ISpline_create (double xmin, double xmax, long degree, long numberOfInteriorKnots); ISpline ISpline_createFromStrings (double xmin, double xmax, long degree, const wchar_t *coef, const wchar_t *interiorKnots); /****************** fit **********************************************/ void FunctionTerms_and_RealTier_fit (I, thou, int *freezeCoefficients, double tol, int ic, Covariance *c); Polynomial RealTier_to_Polynomial (I, long degree, double tol, int ic, Covariance *cvm); LegendreSeries RealTier_to_LegendreSeries (I, long degree, double tol, int ic, Covariance *cvm); ChebyshevSeries RealTier_to_ChebyshevSeries (I, long degree, double tol, int ic, Covariance *cvm); #endif /* _Polynomial_h_ */ sources_5316/dwtools/Sounds_to_DTW.h0000664000176700017670000000175511723710247016300 0ustar paulpaul#ifndef _Sound_to_DTW_h_ #define _Sounds_to_DTW_h_ /* Sounds_to_DTW.h * * Copyright (C) 2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20120221 */ #include "DTW.h" #include "Sound.h" DTW Sounds_to_DTW (Sound me, Sound thee, double analysisWidth, double dt, double band, int slope); #endif /* _Sounds_to_DTW_h_ */ sources_5316/dwtools/Activation.cpp0000644000176700017670000000450011725071311016220 0ustar paulpaul/* Activation.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020315 GPL header djmw 20041203 Added _Activation_checkElements. djmw 20080122 float -> double djmw 20110304 Thing_new */ #include "Activation.h" Thing_implement (Activation, Matrix, 2); int _Activation_checkElements (Activation me) { for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) { if (my z[i][j] < 0 || my z[i][j] > 1) { return 0; } } } return 1; } void Activation_init (I, long ny, long nx) { iam (Activation); double xmin = 1, xmax = nx, dx = 1, x1 = 1, ymin = 1, ymax = ny; double dy = 1, y1 = 1; my ny = ny; my nx = nx; Matrix_init (me, xmin, xmax, nx, dx, x1, ymin, ymax, ny, dy, y1); } Activation Activation_create (long ny, long nx) { try { autoActivation me = Thing_new (Activation); Activation_init (me.peek(), ny, nx); return me.transfer(); } catch (MelderError) { Melder_throw ("Activation not created."); } } Activation Matrix_to_Activation (I) { iam (Matrix); try { autoActivation thee = Activation_create (my ny, my nx); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Activation."); } } Matrix Activation_to_Matrix (I) { iam (Activation); try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Matrix."); } } /* End of file Activation.cpp */ sources_5316/dwtools/SSCP.h0000644000176700017670000002143411630434506014345 0ustar paulpaul#ifndef _SSCP_h_ #define _SSCP_h_ /* SSCP.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "TableOfReal_extensions.h" #include "PCA.h" #include "CCA.h" #include "SSCP_def.h" oo_CLASS_CREATE (SSCP, TableOfReal); Thing_define (Covariance, SSCP) { }; Thing_define (Correlation, SSCP) { }; /* Ordered collection of SSCP's All SSCP's must have the same dimensions and labels. */ Thing_define (SSCPs, Ordered) { }; void SSCP_init (I, long dimension, long storage); SSCP SSCP_create (long dimension); void SSCP_drawConcentrationEllipse (SSCP me, Graphics g, double scale, int confidence, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int garnish); void SSCP_setNumberOfObservations (I, double numberOfObservations); void SSCP_setCentroid (I, long component, double value); // only SSCP & Covariance void SSCP_setValue (I, long row, long col, double value); // only SSCP & Covariance double SSCP_getNumberOfObservations (I); double SSCP_getDegreesOfFreedom (I); double SSCP_getTotalVariance (I); double SSCP_getCumulativeContributionOfComponents (I, long from, long to); double SSCP_getLnDeterminant (I); double SSCP_getConcentrationEllipseArea(I, double scale, int confidence, long d1, long d2); double SSCP_getFractionVariation (I, long from, long to); SSCP TableOfReal_to_SSCP (I, long rowb, long rowe, long colb, long cole); TableOfReal SSCP_and_TableOfReal_extractDistanceQuantileRange (SSCP me, thou, double qlow, double qhigh); TableOfReal Covariance_and_TableOfReal_extractDistanceQuantileRange (Covariance me, thou, double qlow, double qhigh); /* Select from a TableOfReal the rows whose Mahalanobis distance to the centroid (from the SSCP) is in the quantile [qlow, qhigh]. */ TableOfReal Covariance_and_TableOfReal_mahalanobis (Covariance me, thou, bool useTableCentroid); /* Calculate the Mahalanobis distance: sqrt ((x-m)'S**-1 (x-m)) use the m-vector (centroid) from the covariance unless useTableColumnMeans is true. */ Covariance TableOfReal_to_Covariance (I); Correlation TableOfReal_to_Correlation (I); Correlation TableOfReal_to_Correlation_rank (I); TableOfReal SSCP_to_TableOfReal (SSCP me); TableOfReal SSCP_extractCentroid (I); TableOfReal Covariance_to_TableOfReal_randomSampling (Covariance me, long numberOfData); /* Generate a table with data based on the covariance matrix */ void Covariance_and_PCA_generateOneVector (Covariance me, PCA thee, double *vec, double *buf); /* A convenience function to avoid the calculation of the PCA each time we want to generate a random vector The PCA must be the result of a previous SSCP_to_PCA call ! The covariance matrix must not be singular or diagonal! Returns the random sampled vector in vec (which must be of size my numberOfColumns). Preconditions: 1. Covariance may not be in diagonal representation (1 row) 2. Dimensions of me and PCA agree 3. vec is of length my numberOfColumns 4. buf, a vector of length my numberOfColumns, is needed so the routine cannot fail */ SSCPs TableOfReal_to_SSCPs_byLabel (I); PCA SSCP_to_PCA (I); void SSCP_expandPCA (I); void SSCP_unExpandPCA (I); CCA SSCP_to_CCA (I, long ny); Covariance Covariance_create (long dimension); Covariance Covariance_createSimple (wchar_t *covars, wchar_t *centroid, long numberOfObservations); Covariance Covariance_create_reduceStorage (long dimension, long storage); /* storage 0 or >= dimension: complete matrix storage 1: only diagonal storage 2: diagonal + 1 off-diagonal [i,i+1] storage 3: diagonal + off-diagonal [i,i+1] + off-diagonal [i,i+2] .... storage dimension : complete matrix See also SSCP_expand () for usage. */ Correlation Correlation_create (long dimension); TableOfReal Correlation_confidenceIntervals (Correlation me, double confidenceLevel, long numberOfTests, int method); /* if (method == 1) Confidence intervals by Ruben's approximation if (method == 2) Obtain large-sample conservative multiple tests and intervals by the Bonferroni inequality and the Fisher z transformation. Put upper value of confidence intervals in upper matrix and lower values of confidence intervals in lower part of resulting table. Diagonal values are 1 (and represent both upper and lower c.i.). */ /* Precondition ||vector|| = 1 */ void Covariance_getMarginalDensityParameters (Covariance me, double *vector, double *mu, double *stdev); double Covariance_getMarginalProbabilityAtPosition (Covariance me, double *vector, double x); double Covariance_getProbabilityAtPosition_string (Covariance me, wchar_t *xpos); double Covariance_getProbabilityAtPosition (Covariance me, double *x); /* evaluate the pdf(x,mu,Sigma) at x */ Covariance SSCP_to_Covariance (SSCP me, long numberOfConstraints); SSCP Covariance_to_SSCP (Covariance me); void SSCP_testDiagonality_bartlett (SSCP me, long numberOfContraints, double *chisq, double *probability); void Correlation_testDiagonality_bartlett (Correlation me, long numberOfContraints, double *chisq, double *probability); /* Test whether matrices are diagonal matrices, Morrison, page 118 */ Correlation SSCP_to_Correlation (I); Configuration SSCP_to_Configuration (I, long numberOfDimensions); Configuration Covariance_to_Configuration (Covariance me, long numberOfDimensions); Configuration Correlation_to_Configuration (Correlation me, long numberOfDimensions); void Covariance_difference (Covariance me, Covariance thee, double *prob, double *chisq, long *ndf); void Covariance_getSignificanceOfOneMean (Covariance me, long index, double mu, double *probability, double *t, double *ndf); void Covariance_getSignificanceOfMeansDifference (Covariance me, long index1, long index2, double mu, int paired, int equalVariances, double *probability, double *t, double *ndf); void Covariance_getSignificanceOfOneVariance (Covariance me, long index, double sigmasq, double *probability, double *chisq, long *ndf); void Covariance_getSignificanceOfVariancesRatio (Covariance me, long index1, long index2, double ratio, double *probability, double *f, long *ndf); double Covariances_getMultivariateCentroidDifference (Covariance me, Covariance thee, int equalCovariances, double *prob, double *fisher, double *df1, double *df2); /* Are the centroids of me and thee different? Assumption: the two covariances are equal. (we pool me and thee, dimension p). Two sample test of Morrison (1990), page 141: T^2 = n1*n2/(n1+n2) (m1-m2)'S^-1(m1-m2) # weighted Mahalanobis distance f = T^2 * (n1+n2-p-1)/((n1+n2-2)*p) f has Fisher distribution with p and n1+n2-p-1 degrees of freedom. */ void Covariances_equality (Collection me, int method, double *prob, double *chisq, double *df); /* Equality of covariance. method = 1 : Bartlett (Morrison, 1990) method = 2 : Wald (Schott, 2001) */ SSCPs SSCPs_create (); SSCP SSCPs_to_SSCP_sum (SSCPs me); /* Sum the sscp's and weigh each means with it's numberOfObservations. */ SSCP SSCPs_to_SSCP_pool (SSCPs me); void SSCPs_getHomegeneityOfCovariances_box (SSCPs me, double *probability, double *chisq, long *ndf); SSCP SSCP_toTwoDimensions (I, double *v1, double *v2); SSCPs SSCPs_toTwoDimensions (SSCPs me, double *v1, double *v2); SSCPs SSCPs_extractTwoDimensions (SSCPs me, long d1, long d2); /* For inheritors */ void SSCPs_drawConcentrationEllipses (SSCPs me, Graphics g, double scale, int confidence, const wchar_t *label, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish); void SSCPs_getEllipsesBoundingBoxCoordinates (SSCPs me, double scale, int confidence, double *xmin, double *xmax, double *ymin, double *ymax); void SSCP_expand (I); /* Expand a reduced storage SSCP. For efficiency reasons, the expanded matrix is kept in memory. Successive calls to SSCP_expand don't change anything unless Before using one of the Covariance functions defined here on a reduced matrix we first have to expand it to normal size. Covariance me = Covariance_create_reduceStorage (dimension, 1); // diagonal only ... SSCP_expand (me); PCA thee = SSCP_to_PCA (me); */ void SSCP_unExpand (I); /* Use only if the memory is really needed! */ void SSCP_expandLowerCholesky (I); // create lower square root of covariance matrix void SSCP_unExpandLowerCholesky (I); #endif /* _SSCP_h_ */ sources_5316/dwtools/SPINET_to_Pitch.cpp0000644000176700017670000001060311634333436016763 0ustar paulpaul/* SPINET_to_Pitch.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19970408 djmw 20020813 GPL header djmw 20021106 Latest modification */ #include "SPINET_to_Pitch.h" #include "Pitch_extensions.h" #include "NUM2.h" /* from Erb-scale to log2-scale */ Pitch SPINET_to_Pitch (SPINET me, double harmonicFallOffSlope, double ceiling, int maxnCandidates) { try { long nPointsPerOctave = 48; double fmin = NUMerbToHertz (Sampled2_rowToY (me, 1)); double fmax = NUMerbToHertz (Sampled2_rowToY (me, my ny)); double fminl2 = NUMlog2 (fmin), fmaxl2 = NUMlog2 (fmax); double points = (fmaxl2 - fminl2) * nPointsPerOctave; double dfl2 = (fmaxl2 - fminl2) / (points - 1); long nFrequencyPoints = points; long maxHarmonic = fmax / fmin; double maxStrength = 0, unvoicedCriterium = 0.45, maxPower = 0; if (nFrequencyPoints < 2) { Melder_throw ("Frequency range too small."); } if (ceiling <= fmin) { Melder_throw ("Ceiling is smaller than centre frequency of lowest filter."); } autoPitch thee = Pitch_create (my xmin, my xmax, my nx, my dx, my x1, ceiling, maxnCandidates); autoNUMvector power (1, my nx); autoNUMvector pitch (1, nFrequencyPoints); autoNUMvector sumspec (1, nFrequencyPoints); autoNUMvector y (1, my ny); autoNUMvector yv2 (1, my ny); autoNUMvector fl2 (1, my ny); // From ERB's to log (f) for (long i = 1; i <= my ny; i++) { double f = NUMerbToHertz (my y1 + (i - 1) * my dy); fl2[i] = NUMlog2 (f); } // Determine global maximum power in frame for (long j = 1; j <= my nx; j++) { double p = 0; for (long i = 1; i <= my ny; i++) { p += my s[i][j]; } if (p > maxPower) { maxPower = p; } power[j] = p; } if (maxPower == 0) { Melder_throw ("No power"); } for (long j = 1; j <= my nx; j++) { Pitch_Frame pitchFrame = &thy frame[j]; pitchFrame -> intensity = power[j] / maxPower; for (long i = 1; i <= my ny; i++) { y[i] = my s[i][j]; } NUMspline (fl2.peek(), y.peek(), my ny, 1e30, 1e30, yv2.peek()); for (long k = 1; k <= nFrequencyPoints; k++) { double f = fminl2 + (k - 1) * dfl2; NUMsplint (fl2.peek(), y.peek(), yv2.peek(), my ny, f, & pitch[k]); sumspec[k] = 0; } // Formula (8): weighted harmonic summation. for (long m = 1; m <= maxHarmonic; m++) { double hm = 1 - harmonicFallOffSlope * NUMlog2 (m); long kb = 1 + floor (nPointsPerOctave * NUMlog2 (m)); for (long k = kb; k <= nFrequencyPoints; k++) { if (pitch[k] > 0) { sumspec[k - kb + 1] += pitch[k] * hm; } } } // into Pitch object Pitch_Frame_init (pitchFrame, maxnCandidates); pitchFrame -> nCandidates = 0; /* !!!!! */ Pitch_Frame_addPitch (pitchFrame, 0, 0, maxnCandidates); /* unvoiced */ for (long k = 2; k <= nFrequencyPoints - 1; k++) { double y1 = sumspec[k - 1], y2 = sumspec[k], y3 = sumspec[k + 1]; if (y2 > y1 && y2 >= y3) { double denum = y1 - 2 * y2 + y3, tmp = y3 - 4 * y2; double x = dfl2 * (y1 - y3) / (2 * denum); double f = pow (2, fminl2 + (k - 1) * dfl2 + x); double strength = (2 * y1 * (4 * y2 + y3) - y1 * y1 - tmp * tmp) / (8 * denum); if (strength > maxStrength) { maxStrength = strength; } Pitch_Frame_addPitch (pitchFrame, f, strength, maxnCandidates); } } } // Scale the pitch strengths for (long j = 1; j <= my nx; j++) { double f0, localStrength; Pitch_Frame_getPitch (&thy frame[j], &f0, &localStrength); Pitch_Frame_resizeStrengths (&thy frame[j], localStrength / maxStrength, unvoicedCriterium); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Pitch created."); } } /* End of file SPINET_to_Pitch.cpp */ sources_5316/dwtools/Pitch_extensions.h0000644000176700017670000000323311535130317017115 0ustar paulpaul#ifndef _Pitch_extensions_h_ #define _Pitch_extensions_h_ /* Pitch_extensions.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19970408 djmw 20020813 GPL header djmw 20110307 Latest modification */ #ifndef _Pitch_h_ #include "Pitch.h" #endif #ifndef _PitchTier_h_ #include "PitchTier.h" #endif #ifdef __cplusplus extern "C" { #endif void Pitch_Frame_addPitch (Pitch_Frame me, double f, double strength, int maxnCandidates); void Pitch_Frame_getPitch (Pitch_Frame me, double *f, double *strength); void Pitch_Frame_resizeStrengths (Pitch_Frame me, double maxStrength, double unvoicedCriterium); Pitch Pitch_scaleTime (Pitch me, double scaleFactor); /* Scale time domain and pitches: xmin' = xmin; dx' = dx * scaleFactor; x1' = xmin + 0.5 * dx'; xmax' = xmin + nx * dx'; pitch[i]' = pitch[i]/scaleFactor; */ Pitch PitchTier_to_Pitch (PitchTier me, double dt, double pitchFloor, double pitchCeiling); #ifdef __cplusplus } #endif #endif /* _Pitch_extensions_h_ */ sources_5316/dwtools/Eigen_and_SSCP.h0000644000176700017670000000247211553067232016301 0ustar paulpaul#ifndef _Eigen_and_SSCP_h_ #define _Eigen_and_SSCP_h_ /* Eigen_and_SSCP.h * * Copyright (C) 1993-2004 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020327 Initial version djmw 20040219 GPL header */ #ifndef _Eigen_h_ #include "Eigen.h" #endif #ifndef _SSCP_h_ #include "SSCP.h" #endif #ifdef __cplusplus extern "C" { #endif SSCP Eigen_and_SSCP_project (I, SSCP thee); Covariance Eigen_and_Covariance_project (I, Covariance thee); /* Purpose: project the SSCP (thee) on the eigenspace (me): S' = E' S E Returns SSCP-object with square matrix dimension 'my numberOfEigenvalues' */ #ifdef __cplusplus } #endif #endif /* _Eigen_and_SSCP_h_ */ sources_5316/dwtools/TableOfReal_and_Permutation.h0000644000176700017670000000242511607123037021123 0ustar paulpaul#ifndef _TableOfReal_and_Permutation_h_ #define _TableOfReal_and_Permutation_h_ /* TableOfReal_and_Permutation.h * * Copyright (C) 2005-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20050708 djmw 20110307 Latest modification */ #include "Permutation.h" #include "TableOfReal.h" #ifdef __cplusplus extern "C" { #endif TableOfReal TableOfReal_and_Permutation_permuteRows (I, Permutation thee); /* Permutation (n1,n2,..nn) new his z[1] = my z[n1], his z[2] = my z[n2], ..*/ Permutation TableOfReal_to_Permutation_sortRowLabels (I); #ifdef __cplusplus } #endif #endif /* _TableOfReal_and_Permutation_h_ */ sources_5316/dwtools/AffineTransform.h0000644000176700017670000000237711627171437016675 0ustar paulpaul#ifndef _AffineTransform_h_ #define _AffineTransform_h_ /* AffineTransform.h * * Copyright (C) 2001-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" #include "TableOfReal.h" #include "AffineTransform_def.h" oo_CLASS_CREATE (AffineTransform, Data); void AffineTransform_init (I, long n); AffineTransform AffineTransform_create (long n); Any AffineTransform_invert (I); /* Get inverse transform for y = A x + t: x = A^(-1)y - A^(-1) t */ TableOfReal AffineTransform_extractMatrix (I); TableOfReal AffineTransform_extractTranslationVector (I); #endif /* _AffineTransform_h_ */ sources_5316/dwtools/CategoriesEditor.h0000644000176700017670000000257011627172221017030 0ustar paulpaul#ifndef _CategoriesEditor_h_ #define _CategoriesEditor_h_ /* CategoriesEditor.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Command.h" #include "Editor.h" #include "Categories.h" Thing_define (CategoriesEditor, Editor) { // new data: public: CommandHistory history; int position; GuiObject list, text, outOfView, undo, redo; GuiObject remove, insert, insertAtEnd, replace, moveUp, moveDown; // overridden methods: void v_destroy (); void v_createChildren (); void v_createHelpMenuItems (EditorMenu menu); void v_dataChanged (); }; CategoriesEditor CategoriesEditor_create (GuiObject parent, const wchar *title, Categories data); #endif /* _CategoriesEditor_h_ */ sources_5316/dwtools/LFCC.h0000644000176700017670000000216011627241366014305 0ustar paulpaul#ifndef _LFCC_h_ #define _LFCC_h_ /* LFCC.h * * Linear Frequency Cepstral Coefficients class. * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20001213 djmw 20020813 GPL header djmw 20110306 Latest modification. */ #include "CC.h" Thing_define (LFCC, CC) { }; LFCC LFCC_create (double tmin, double tmax, long nt, double dt, double t1, long maximumNumberOfCoefficients, double fmin, double fmax); #endif /* _LFCC_h_ */ sources_5316/dwtools/Strings_extensions.cpp0000664000176700017670000002107111747467563020061 0ustar paulpaul/* Strings_extensions.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20011003 djmw 20020813 GPL header djmw 20030107 Added Strings_setString djmw 20031212 Added Strings_extractPart djmw 20040301 Added Strings_createFixedLength. djmw 20040308 Corrected bug in strings_to_Strings. djmw 20040427 Strings_append added. djmw 20040629 Strings_append now accepts an Ordered of Strings. djmw 20050714 New: Strings_to_Permutation, Strings_and_Permutation_permuteStrings. djmw 20050721 Extra argument in Strings_to_Permutation. djmw 20101007 StringsIndex Stringses_to_StringsIndex (Strings me, Strings classes) djmw 20120407 + Strings_createFromCharacters */ #include "Strings_extensions.h" #include "NUM2.h" Strings Strings_createFixedLength (long numberOfStrings) { try { if (numberOfStrings <= 0) { Melder_throw ("The number of strings must be positive."); } autoStrings me = Thing_new (Strings); my strings = NUMvector (1, numberOfStrings); my numberOfStrings = numberOfStrings; return me.transfer(); } catch (MelderError) { Melder_throw ("Strings not created."); } } Strings Strings_createAsCharacters (const wchar_t *string) { try { autoStrings me = Thing_new (Strings); my numberOfStrings = wcslen (string); my strings = NUMvector (1, my numberOfStrings); autoMelderString s; for (long i = 1; i <= my numberOfStrings; i++) { MelderString_appendCharacter (&s, *string++); my strings[i] = Melder_wcsdup (s.string); MelderString_empty (&s); } return me.transfer(); } catch (MelderError) { Melder_throw ("Strings from characters not created."); } } Strings Strings_createAsTokens (const wchar_t *string) { try { autoStrings me = Thing_new (Strings); my numberOfStrings = Melder_countTokens (string); my strings = NUMvector (1, my numberOfStrings); long i = 1; for (wchar_t *token = Melder_firstToken (string); token != 0; token = Melder_nextToken ()) { my strings[i++] = Melder_wcsdup (token); } return me.transfer(); } catch (MelderError) { Melder_throw ("Strings from characters not created."); } } long Strings_findString (Strings me, const wchar_t *string) { for (long i = 1; i <= my numberOfStrings; i++) { if (Melder_wcsequ (my strings[i], string)) { return i; } } return 0; } Strings Strings_append (Collection me) { try { long index = 1, numberOfStrings = 0; for (long i = 1; i <= my size; i++) { Strings s = (Strings) my item[i]; numberOfStrings += s -> numberOfStrings; } autoStrings thee = Strings_createFixedLength (numberOfStrings); for (long i = 1; i <= my size; i++) { Strings s = (Strings) my item[i]; for (long j = 1; j <= s -> numberOfStrings; j++, index++) { if (s -> strings[j] == 0) { continue; } thy strings [index] = Melder_wcsdup (s -> strings[j]); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not appended."); } } Strings Strings_change (Strings me, const wchar_t *search, const wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp) { try { autoStrings thee = Thing_new (Strings); wchar_t **strings = strs_replace (my strings, 1, my numberOfStrings, search, replace, maximumNumberOfReplaces, nmatches, nstringmatches, use_regexp); thy numberOfStrings = my numberOfStrings; thy strings = strings; return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not changed."); } } void Strings_setString (Strings me, const wchar_t *newstr, long index) { try { if (index < 1 || index > my numberOfStrings) { Melder_throw ("Index must be in range [1, ", my numberOfStrings, L"]."); } autostring s = Melder_wcsdup (newstr); Melder_free (my strings[index]); my strings[index] = s.transfer(); } catch (MelderError) { Melder_throw (me, ": no string set at index ", index); } } Strings strings_to_Strings (wchar_t **strings, long from, long to) { try { autoStrings thee = Strings_createFixedLength (to - from + 1); for (long i = from; i <= to; i++) { thy strings[i - from + 1] = Melder_wcsdup (strings[i]); } return thee.transfer(); } catch (MelderError) { Melder_throw ("Strings not created."); } } Strings Strings_extractPart (Strings me, long from, long to) { try { if (from < 1 || to > my numberOfStrings || from > to) Melder_throw ("Strings_extractPart: begin and end must be in interval [1, ", my numberOfStrings, L"]."); return strings_to_Strings (my strings, from, to); } catch (MelderError) { Melder_throw (me, ": no part extracted."); } } Strings strings_to_Strings_link (wchar_t **strings, long n) { try { autoStrings me = Strings_createFixedLength (n); for (long i = 1; i <= n; i++) { my strings[i] = strings[i]; } return me.transfer(); } catch (MelderError) { Melder_throw ("Strings not linked."); } } void _Strings_unlink (Strings me) { my numberOfStrings = 0; } Permutation Strings_to_Permutation (Strings me, int sort) { try { autoPermutation thee = Permutation_create (my numberOfStrings); if (sort != 0) { NUMindexx_s (my strings, my numberOfStrings, thy p); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Permutation created."); } } Strings Strings_and_Permutation_permuteStrings (Strings me, Permutation thee) { try { if (my numberOfStrings != thy numberOfElements) Melder_throw ("Strings_and_Permutation_permuteStrings: " "The number of strings and the number of elements in the Permutation must be equal."); autoStrings him = Strings_createFixedLength (my numberOfStrings); for (long i = 1; i <= thy numberOfElements; i++) { long index = thy p[i]; his strings[i] = Melder_wcsdup (my strings[index]); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no permuted Strings created."); } } StringsIndex Stringses_to_StringsIndex (Strings me, Strings classes) { try { autoStringsIndex tmp = Strings_to_StringsIndex (classes); long numberOfClasses = tmp -> classes -> size; autoStringsIndex him = StringsIndex_create (my numberOfStrings); for (long i = 1; i <= numberOfClasses; i++) { SimpleString t = (SimpleString) tmp -> classes -> item[i]; autoSimpleString t2 = Data_copy (t); Collection_addItem (his classes, t2.transfer()); } for (long j = 1; j <= my numberOfStrings; j++) { long index = 0; wchar_t *stringsj = my strings[j]; for (long i = 1; i <= numberOfClasses; i++) { SimpleString ss = (SimpleString) his classes -> item[i]; if (Melder_wcscmp (stringsj, ss -> string) == 0) { index = i; break; } } his classIndex[j] = index; } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no StringsIndex created."); } } StringsIndex Strings_to_StringsIndex (Strings me) { try { autoStringsIndex thee = StringsIndex_create (my numberOfStrings); autoPermutation sorted = Strings_to_Permutation (me, 1); long numberOfClasses = 0; wchar_t *strings = NULL; for (long i = 1; i <= sorted -> numberOfElements; i++) { long index = sorted -> p[i]; wchar_t *stringsi = my strings[index]; if (i == 1 || Melder_wcscmp (strings, stringsi) != 0) { numberOfClasses++; autoSimpleString him = SimpleString_create (stringsi); Collection_addItem (thy classes, him.transfer()); strings = stringsi; } thy classIndex[index] = numberOfClasses; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no StringsIndex created."); } } Strings StringsIndex_to_Strings (StringsIndex me) { try { autoStrings thee = Strings_createFixedLength (my numberOfElements); for (long i = 1; i <= thy numberOfStrings; i++) { SimpleString s = (SimpleString) my classes -> item[my classIndex[i]]; thy strings[i] = Melder_wcsdup (s -> string); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Strings created."); } } /* End of file Strings_extensions.cpp */ sources_5316/dwtools/Matrix_Categories.h0000644000176700017670000000217411607123040017176 0ustar paulpaul#ifndef _Matrix_Categories_h_ #define _Matrix_Categories_h_ /* Matrix_Categories.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110307 Latest modification */ #include "Matrix.h" #include "Categories.h" #include "TableOfReal.h" #ifdef __cplusplus extern "C" { #endif TableOfReal Matrix_and_Categories_to_TableOfReal (I, Categories thee); #ifdef __cplusplus } #endif #endif /* _Matrix_Categories_h_ */ sources_5316/dwtools/Spectrum_extensions.h0000644000176700017670000000335111607123041017645 0ustar paulpaul#ifndef _Spectrum_extensions_h_ #define _Spectrum_extensions_h_ /* Spectrum_extensions.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010114 djmw 20020813 GPL header djmw 20110307 Latest modification */ #include "Spectrum.h" #include "Sound.h" #include "Graphics.h" #ifdef __cplusplus extern "C" { #endif Matrix Spectrum_unwrap (Spectrum me); /* Unwrap the phases of the spectrum according to an algorithm by Tribolet as published in: Tribolet, J.M. & Quatieri, T.F. (1979), Computation of the Complex Spectrum, in: Programs for Digital Signal Processing, Digital Signal Processing Commitee (eds), IEEE Press, chapter 7.1. First row of returned matrix contains the amplitudes-squared, second row contains the unwrapped phases. */ void Spectrum_drawPhases (Spectrum me, Graphics g, double fmin, double fmax, double phase_min, double phase_max, int unwrap, int garnish); Spectrum Spectra_multiply (Spectrum me, Spectrum thee); void Spectrum_conjugate (Spectrum me); #ifdef __cplusplus } #endif #endif /* _Spectrum_extensions_h_ */ sources_5316/dwtools/EditDistanceTable_def.h0000664000176700017670000000370711743577006017740 0ustar paulpaul/* EditDistanceTable_def.h * * Copyright (C) 2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20120406 First version */ #define ooSTRUCT PairOfInteger oo_DEFINE_STRUCT (PairOfInteger) oo_LONG (x) oo_LONG (y) oo_END_STRUCT (PairOfInteger) #undef ooSTRUCT #define ooSTRUCT WarpingPath oo_DEFINE_CLASS (WarpingPath, Data) oo_LONG (_capacity) oo_LONG (d_pathLength) oo_STRUCT_VECTOR (PairOfInteger, d_path, d_pathLength) oo_END_CLASS (WarpingPath) #undef ooSTRUCT #define ooSTRUCT EditCostsTable oo_DEFINE_CLASS (EditCostsTable, TableOfReal) #if oo_DECLARING // overridden methods: virtual void v_info (); virtual bool v_matchTargetSymbol (const wchar_t *targetSymbol, const wchar_t *symbol); virtual bool v_matchSourceSymbol (const wchar_t *sourceSymbol, const wchar_t *symbol); virtual bool v_matchTargetWithSourceSymbol (const wchar_t *targetSymbol, const wchar_t *sourceSymbol); #endif oo_END_CLASS (EditCostsTable) #undef ooSTRUCT #define ooSTRUCT EditDistanceTable oo_DEFINE_CLASS (EditDistanceTable, TableOfReal) oo_OBJECT (WarpingPath, 0, d_warpingPath) #if oo_DECLARING oo_OBJECT (EditCostsTable, 0, d_editCostsTable) // overridden methods: virtual void v_info (); #endif oo_END_CLASS (EditDistanceTable) #undef ooSTRUCT /* End of file EditDistanceTable_def.h */ sources_5316/dwtools/TableOfReal_extensions.cpp0000664000176700017670000016503011725112233020525 0ustar paulpaul/* TableOfReal_extensions.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20000202 17 typos in F1-3,L1-3 table corrected djmw 20030707 Changed TableOfReal_drawVectors interface. djmw 20031030 Added TableOfReal_appendColumns djmw 20031216 Interface change in TableOfReal_choleskyDecomposition djmw 20040108 Corrected a memory leak in TableOfReal_drawBoxPlots djmw 20040211 Modified TableOfReal_copyLabels behaviour: copy NULL-labels too. djmw 20040511 Removed TableOfReal_extractRowsByRowLabel,TableOfReal_selectColumnsWhereRow djmw 20040617 Removed column selection bug in TableOfReal_drawRowsAsHistogram djmw 20041105 Added TableOfReal_createFromVanNieropData_25females djmw 20041115 TableOfReal_drawScatterPlot: plotting a NULL-label crashed Praat. djmw 20041213 Added TableOfReal_createFromWeeninkData. djmw 20050221 TableOfReal_meansByRowLabels, extra reduce parameter. djmw 20050222 TableOfReal_drawVectors didn't draw rowlabels. djmw 20050512 TableOfReal TableOfReal_meansByRowLabels crashed if first label in sorted was NULL. djmw 20051116 TableOfReal_drawScatterPlot draw reverse permited by choosing xmin > xmax and/or ymin>ymax djmw 20060301 TableOfReal_meansByRowLabels extra medianize djmw 20060626 Extra NULL argument for ExecRE. djmw 20061021 printf expects %ld for 'long int' djmw 20070822 wchar_t djmw 20070902 Better error messages (object type and name feedback) djmw 20070614 updated to version 1.30 of regular expressions. djmw 20071202 Melder_warning djmw 20080122 float -> double djmw 20081119 +TableOfReal_areAllCellsDefined djmw 20090506 +setInner for _drawScatterPlotMatrix djmw 20091009 +TableOfReal_drawColumnAsDistribution djmw 20100222 Corrected a bug in TableOfReal_copyOneRowWithLabel which caused label corruption if from and to table were equal and rows were equal too. djmw 20111110 Use autostringvector djmw 20111123 Always use Melder_wcscmp */ #include #include "SSCP.h" #include "Matrix_extensions.h" #include "NUMclapack.h" #include "NUM2.h" #include "SVD.h" #include "Table_extensions.h" #include "TableOfReal_extensions.h" #include "TableOfReal_and_Permutation.h" #include "regularExp.h" #include "Formula.h" #define EMPTY_STRING(s) ((s) == NULL || s[0] == '\0') #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) #define Graphics_ARROW 1 #define Graphics_TWOWAYARROW 2 #define Graphics_LINE 3 TableOfReal TableOfReal_and_TableOfReal_columnCorrelations (I, thou, int center, int normalize); TableOfReal TableOfReal_and_TableOfReal_rowCorrelations (I, thou, int center, int normalize); int TableOfReal_areAllCellsDefined (I, long rb, long re, long cb, long ce) { iam (TableOfReal); if (re <= rb || rb < 1 || re > my numberOfRows) { rb = 1; re = my numberOfRows; } if (ce <= cb || cb < 1 || ce > my numberOfColumns) { cb = 1; ce = my numberOfColumns; } autoNUMvector invalid_columns (1, my numberOfColumns); long numberOfInvalidRows = 0, numberOfInvalidColumns = 0; for (long i = rb; i <= re; i++) { for (long j = cb; j <= ce; j++) { long rowcount = 0; if (my data[i][j] == NUMundefined) { invalid_columns[j]++; rowcount++; } if (rowcount > 0) { numberOfInvalidRows++; } } } if (numberOfInvalidRows != 0) { for (long j = 1; j <= my numberOfColumns; j++) { if (invalid_columns[j] > 0) { numberOfInvalidColumns++; } } Melder_throw (numberOfInvalidRows == 1 ? "One row contains invalid data." : (numberOfInvalidColumns == 1 ? "One column contains invalid data." : "Several rows and columns contain invalid data.")); } return numberOfInvalidRows == 0 ? 1 : 0; } void TableOfReal_copyOneRowWithLabel (I, thou, long myrow, long thyrow) { iam (TableOfReal); thouart (TableOfReal); try { if (me == thee && myrow == thyrow) { return; } if (myrow < 1 || myrow > my numberOfRows || thyrow < 1 || thyrow > thy numberOfRows || my numberOfColumns != thy numberOfColumns) { Melder_throw ("The dimensions do not fit."); } Melder_free (thy rowLabels[thyrow]); thy rowLabels[thyrow] = Melder_wcsdup (my rowLabels[myrow]); if (my data[myrow] != thy data[thyrow]) { NUMvector_copyElements (my data[myrow], thy data[thyrow], 1, my numberOfColumns); } } catch (MelderError) { Melder_throw (me, ": row ", myrow, " not copied to ", thee); } } int TableOfReal_hasRowLabels (I) { iam (TableOfReal); if (my rowLabels == NULL) { return 0; } for (long i = 1; i <= my numberOfRows; i++) { if (EMPTY_STRING (my rowLabels[i])) { return 0; } } return 1; } int TableOfReal_hasColumnLabels (I) { iam (TableOfReal); if (my columnLabels == NULL) { return 0; } for (long i = 1; i <= my numberOfColumns; i++) { if (EMPTY_STRING (my columnLabels[i])) { return 0; } } return 1; } TableOfReal TableOfReal_createIrisDataset () { float iris[150][4] = { {5.1, 3.5, 1.4, 0.2}, {4.9, 3.0, 1.4, 0.2}, {4.7, 3.2, 1.3, 0.2}, {4.6, 3.1, 1.5, 0.2}, {5.0, 3.6, 1.4, 0.2}, {5.4, 3.9, 1.7, 0.4}, {4.6, 3.4, 1.4, 0.3}, {5.0, 3.4, 1.5, 0.2}, {4.4, 2.9, 1.4, 0.2}, {4.9, 3.1, 1.5, 0.1}, {5.4, 3.7, 1.5, 0.2}, {4.8, 3.4, 1.6, 0.2}, {4.8, 3.0, 1.4, 0.1}, {4.3, 3.0, 1.1, 0.1}, {5.8, 4.0, 1.2, 0.2}, {5.7, 4.4, 1.5, 0.4}, {5.4, 3.9, 1.3, 0.4}, {5.1, 3.5, 1.4, 0.3}, {5.7, 3.8, 1.7, 0.3}, {5.1, 3.8, 1.5, 0.3}, {5.4, 3.4, 1.7, 0.2}, {5.1, 3.7, 1.5, 0.4}, {4.6, 3.6, 1.0, 0.2}, {5.1, 3.3, 1.7, 0.5}, {4.8, 3.4, 1.9, 0.2}, {5.0, 3.0, 1.6, 0.2}, {5.0, 3.4, 1.6, 0.4}, {5.2, 3.5, 1.5, 0.2}, {5.2, 3.4, 1.4, 0.2}, {4.7, 3.2, 1.6, 0.2}, {4.8, 3.1, 1.6, 0.2}, {5.4, 3.4, 1.5, 0.4}, {5.2, 4.1, 1.5, 0.1}, {5.5, 4.2, 1.4, 0.2}, {4.9, 3.1, 1.5, 0.2}, {5.0, 3.2, 1.2, 0.2}, {5.5, 3.5, 1.3, 0.2}, {4.9, 3.6, 1.4, 0.1}, {4.4, 3.0, 1.3, 0.2}, {5.1, 3.4, 1.5, 0.2}, {5.0, 3.5, 1.3, 0.3}, {4.5, 2.3, 1.3, 0.3}, {4.4, 3.2, 1.3, 0.2}, {5.0, 3.5, 1.6, 0.6}, {5.1, 3.8, 1.9, 0.4}, {4.8, 3.0, 1.4, 0.3}, {5.1, 3.8, 1.6, 0.2}, {4.6, 3.2, 1.4, 0.2}, {5.3, 3.7, 1.5, 0.2}, {5.0, 3.3, 1.4, 0.2}, {7.0, 3.2, 4.7, 1.4}, {6.4, 3.2, 4.5, 1.5}, {6.9, 3.1, 4.9, 1.5}, {5.5, 2.3, 4.0, 1.3}, {6.5, 2.8, 4.6, 1.5}, {5.7, 2.8, 4.5, 1.3}, {6.3, 3.3, 4.7, 1.6}, {4.9, 2.4, 3.3, 1.0}, {6.6, 2.9, 4.6, 1.3}, {5.2, 2.7, 3.9, 1.4}, {5.0, 2.0, 3.5, 1.0}, {5.9, 3.0, 4.2, 1.5}, {6.0, 2.2, 4.0, 1.0}, {6.1, 2.9, 4.7, 1.4}, {5.6, 2.9, 3.6, 1.3}, {6.7, 3.1, 4.4, 1.4}, {5.6, 3.0, 4.5, 1.5}, {5.8, 2.7, 4.1, 1.0}, {6.2, 2.2, 4.5, 1.5}, {5.6, 2.5, 3.9, 1.1}, {5.9, 3.2, 4.8, 1.8}, {6.1, 2.8, 4.0, 1.3}, {6.3, 2.5, 4.9, 1.5}, {6.1, 2.8, 4.7, 1.2}, {6.4, 2.9, 4.3, 1.3}, {6.6, 3.0, 4.4, 1.4}, {6.8, 2.8, 4.8, 1.4}, {6.7, 3.0, 5.0, 1.7}, {6.0, 2.9, 4.5, 1.5}, {5.7, 2.6, 3.5, 1.0}, {5.5, 2.4, 3.8, 1.1}, {5.5, 2.4, 3.7, 1.0}, {5.8, 2.7, 3.9, 1.2}, {6.0, 2.7, 5.1, 1.6}, {5.4, 3.0, 4.5, 1.5}, {6.0, 3.4, 4.5, 1.6}, {6.7, 3.1, 4.7, 1.5}, {6.3, 2.3, 4.4, 1.3}, {5.6, 3.0, 4.1, 1.3}, {5.5, 2.5, 4.0, 1.3}, {5.5, 2.6, 4.4, 1.2}, {6.1, 3.0, 4.6, 1.4}, {5.8, 2.6, 4.0, 1.2}, {5.0, 2.3, 3.3, 1.0}, {5.6, 2.7, 4.2, 1.3}, {5.7, 3.0, 4.2, 1.2}, {5.7, 2.9, 4.2, 1.3}, {6.2, 2.9, 4.3, 1.3}, {5.1, 2.5, 3.0, 1.1}, {5.7, 2.8, 4.1, 1.3}, {6.3, 3.3, 6.0, 2.5}, {5.8, 2.7, 5.1, 1.9}, {7.1, 3.0, 5.9, 2.1}, {6.3, 2.9, 5.6, 1.8}, {6.5, 3.0, 5.8, 2.2}, {7.6, 3.0, 6.6, 2.1}, {4.9, 2.5, 4.5, 1.7}, {7.3, 2.9, 6.3, 1.8}, {6.7, 2.5, 5.8, 1.8}, {7.2, 3.6, 6.1, 2.5}, {6.5, 3.2, 5.1, 2.0}, {6.4, 2.7, 5.3, 1.9}, {6.8, 3.0, 5.5, 2.1}, {5.7, 2.5, 5.0, 2.0}, {5.8, 2.8, 5.1, 2.4}, {6.4, 3.2, 5.3, 2.3}, {6.5, 3.0, 5.5, 1.8}, {7.7, 3.8, 6.7, 2.2}, {7.7, 2.6, 6.9, 2.3}, {6.0, 2.2, 5.0, 1.5}, {6.9, 3.2, 5.7, 2.3}, {5.6, 2.8, 4.9, 2.0}, {7.7, 2.8, 6.7, 2.0}, {6.3, 2.7, 4.9, 1.8}, {6.7, 3.3, 5.7, 2.1}, {7.2, 3.2, 6.0, 1.8}, {6.2, 2.8, 4.8, 1.8}, {6.1, 3.0, 4.9, 1.8}, {6.4, 2.8, 5.6, 2.1}, {7.2, 3.0, 5.8, 1.6}, {7.4, 2.8, 6.1, 1.9}, {7.9, 3.8, 6.4, 2.0}, {6.4, 2.8, 5.6, 2.2}, {6.3, 2.8, 5.1, 1.5}, {6.1, 2.6, 5.6, 1.4}, {7.7, 3.0, 6.1, 2.3}, {6.3, 3.4, 5.6, 2.4}, {6.4, 3.1, 5.5, 1.8}, {6.0, 3.0, 4.8, 1.8}, {6.9, 3.1, 5.4, 2.1}, {6.7, 3.1, 5.6, 2.4}, {6.9, 3.1, 5.1, 2.3}, {5.8, 2.7, 5.1, 1.9}, {6.8, 3.2, 5.9, 2.3}, {6.7, 3.3, 5.7, 2.5}, {6.7, 3.0, 5.2, 2.3}, {6.3, 2.5, 5.0, 1.9}, {6.5, 3.0, 5.2, 2.0}, {6.2, 3.4, 5.4, 2.3}, {5.9, 3.0, 5.1, 1.8} }; try { autoTableOfReal me = TableOfReal_create (150, 4); TableOfReal_setColumnLabel (me.peek(), 1, L"sl"); TableOfReal_setColumnLabel (me.peek(), 2, L"sw"); TableOfReal_setColumnLabel (me.peek(), 3, L"pl"); TableOfReal_setColumnLabel (me.peek(), 4, L"pw"); for (long i = 1; i <= 150; i++) { int kind = (i - 1) / 50 + 1; wchar_t const *label = kind == 1 ? L"1" : kind == 2 ? L"2" : L"3"; for (long j = 1; j <= 4; j++) { my data[i][j] = iris[i - 1][j - 1]; } TableOfReal_setRowLabel (me.peek(), i, label); } Thing_setName (me.peek(), L"iris"); return me.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal from iris data not created."); } } Strings TableOfReal_extractRowLabels (I) { iam (TableOfReal); try { autoStrings thee = Thing_new (Strings); if (my numberOfRows > 0) { thy strings = NUMvector (1, my numberOfRows); thy numberOfStrings = my numberOfRows; for (long i = 1; i <= my numberOfRows; i++) { wchar_t const *label = my rowLabels[i] ? my rowLabels[i] : L"?"; thy strings[i] = Melder_wcsdup (label); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": row labels not extracted."); } } Strings TableOfReal_extractColumnLabels (I) { iam (TableOfReal); try { autoStrings thee = Thing_new (Strings); if (my numberOfColumns > 0) { thy strings = NUMvector (1, my numberOfColumns); thy numberOfStrings = my numberOfColumns; for (long i = 1; i <= my numberOfColumns; i++) { wchar_t const *label = my columnLabels[i] ? my columnLabels[i] : L"?"; thy strings[i] = Melder_wcsdup (label); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": column labels not extracted."); } } TableOfReal TableOfReal_transpose (I) { iam (TableOfReal); try { autoTableOfReal thee = TableOfReal_create (my numberOfColumns, my numberOfRows); for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { thy data[j][i] = my data[i][j]; } } NUMstrings_copyElements (my rowLabels, thy columnLabels, 1, my numberOfRows); NUMstrings_copyElements (my columnLabels, thy rowLabels, 1, my numberOfColumns); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not transposed."); } } int TableOfReal_to_Pattern_and_Categories (I, long fromrow, long torow, long fromcol, long tocol, Pattern *p, Categories *c) { *p = 0; *c = 0; try { iam (TableOfReal); long ncol = my numberOfColumns, nrow = my numberOfRows; if (fromrow == torow && fromrow == 0) { fromrow = 1; torow = nrow; } else if (fromrow > 0 && fromrow <= nrow && torow == 0) { torow = nrow; } else if (! (fromrow > 0 && torow <= nrow && fromrow <= torow)) { Melder_throw ("Invalid row selection."); } if (fromcol == tocol && fromcol == 0) { fromcol = 1; tocol = ncol; } else if (fromcol > 0 && fromcol <= ncol && tocol == 0) { tocol = ncol; } else if (! (fromcol > 0 && tocol <= ncol && fromcol <= tocol)) { Melder_throw ("Invalid column selection."); } nrow = torow - fromrow + 1; ncol = tocol - fromcol + 1; autoPattern ap = Pattern_create (nrow, ncol); autoCategories ac = Categories_create (); long row = 1; for (long i = fromrow; i <= torow; i++, row++) { wchar_t const *s = my rowLabels[i] ? my rowLabels[i] : L"?"; autoSimpleString item = SimpleString_create (s); Collection_addItem (ac.peek(), item.transfer()); long col = 1; for (long j = fromcol; j <= tocol; j++, col++) { ap -> z[row][col] = my data[i][j]; } } *p = ap.transfer(); *c = ac.transfer(); return 1; } catch (MelderError) { Melder_throw ("Pattern and Categories not created from TableOfReal."); } } void TableOfReal_getColumnExtrema (I, long col, double *min, double *max) { *min = NUMundefined; *max = NUMundefined; iam (TableOfReal); if (col < 1 || col > my numberOfColumns) { Melder_throw ("Invalid column number."); } *min = *max = my data[1][col]; for (long i = 2; i <= my numberOfRows; i++) { if (my data[i][col] > *max) { *max = my data[i][col]; } else if (my data[i][col] < *min) { *min = my data[i][col]; } } } void TableOfReal_drawRowsAsHistogram (I, Graphics g, const wchar_t *rows, long colb, long cole, double ymin, double ymax, double xoffsetFraction, double interbarFraction, double interbarsFraction, const wchar_t *greys, int garnish) { iam (TableOfReal); if (colb >= cole) { colb = 1; cole = my numberOfColumns; } if (colb <= cole && (colb < 1 || cole > my numberOfColumns)) { Melder_throw ("Invalid columns"); } long nrows; autoNUMvector irows (NUMstring_to_numbers (rows, &nrows), 1); for (long i = 1; i <= nrows; i++) { long irow = irows[i]; if (irow < 0 || irow > my numberOfRows) { Melder_throw ("Invalid row (", irow, ")."); } if (ymin >= ymax) { double min, max; NUMvector_extrema (my data[irow], colb, cole, &min, &max); if (i > 1) { if (min < ymin) { ymin = min; } if (max > ymax) { ymax = max; } } else { ymin = min; ymax = max; } } } long ngreys; autoNUMvector igreys (NUMstring_to_numbers (greys, &ngreys), 1); Graphics_setWindow (g, 0, 1, ymin, ymax); Graphics_setInner (g); long ncols = cole - colb + 1; double bar_width = 1 / (ncols * nrows + 2 * xoffsetFraction + (ncols - 1) * interbarsFraction + ncols * (nrows - 1) * interbarFraction); double dx = (interbarsFraction + nrows + (nrows - 1) * interbarFraction) * bar_width; for (long i = 1; i <= nrows; i++) { long irow = irows[i]; double xb = xoffsetFraction * bar_width + (i - 1) * (1 + interbarFraction) * bar_width; double x1 = xb; double grey = i <= ngreys ? igreys[i] : igreys[ngreys]; for (long j = colb; j <= cole; j++) { double x2 = x1 + bar_width; double y1 = ymin, y2 = my data[irow][j]; if (y2 > ymin) { if (y2 > ymax) { y2 = ymax; } Graphics_setGrey (g, grey); Graphics_fillRectangle (g, x1, x2, y1, y2); Graphics_setGrey (g, 0); /* Black */ Graphics_rectangle (g, x1, x2, y1, y2); } x1 += dx; } } Graphics_unsetInner (g); if (garnish) { double xb = (xoffsetFraction + 0.5 * (nrows + (nrows - 1) * interbarFraction)) * bar_width; for (long j = colb; j <= cole; j++) { if (my columnLabels[j]) { Graphics_markBottom (g, xb, 0, 0, 0, my columnLabels[j]); } xb += dx; } Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); } } void TableOfReal_drawBiplot (I, Graphics g, double xmin, double xmax, double ymin, double ymax, double sv_splitfactor, int labelsize, int garnish) { iam (TableOfReal); long nr = my numberOfRows, nc = my numberOfColumns, nPoints = nr + nc; int fontsize = Graphics_inqFontSize (g); autoSVD svd = SVD_create (nr, nc); NUMmatrix_copyElements (my data, svd -> u, 1, nr, 1, nc); NUMcentreColumns (svd -> u, 1, nr, 1, nc, 0); SVD_compute (svd.peek()); long numberOfZeroed = SVD_zeroSmallSingularValues (svd.peek(), 0); long nmin = MIN (nr, nc) - numberOfZeroed; if (nmin < 2) { Melder_throw ("There must be at least two (independent) columns in the table."); } autoNUMvector x (1, nPoints); autoNUMvector y (1, nPoints); double lambda1 = pow (svd -> d[1], sv_splitfactor); double lambda2 = pow (svd -> d[2], sv_splitfactor); for (long i = 1; i <= nr; i++) { x[i] = svd -> u[i][1] * lambda1; y[i] = svd -> u[i][2] * lambda2; } lambda1 = svd -> d[1] / lambda1; lambda2 = svd -> d[2] / lambda2; for (long i = 1; i <= nc; i++) { x[nr + i] = svd -> v[i][1] * lambda1; y[nr + i] = svd -> v[i][2] * lambda2; } if (xmax <= xmin) { NUMvector_extrema (x.peek(), 1, nPoints, &xmin, &xmax); } if (xmax <= xmin) { xmax += 1; xmin -= 1; } if (ymax <= ymin) { NUMvector_extrema (y.peek(), 1, nPoints, &ymin, &ymax); } if (ymax <= ymin) { ymax += 1; ymin -= 1; } Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setInner (g); if (labelsize > 0) { Graphics_setFontSize (g, labelsize); } Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (long i = 1; i <= nPoints; i++) { wchar_t const *label; if (i <= nr) { label = my rowLabels[i]; if (label == NULL) { label = L"?__r_"; } } else { label = my columnLabels[i - nr]; if (label == NULL) { label = L"?__c_"; } } Graphics_text (g, x[i], y[i], label); } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_marksBottom (g, 2, 1, 1, 0); } if (labelsize > 0) { Graphics_setFontSize (g, fontsize); } } /* Draw a box plot of data[1..ndata]. The vertical center line of the plot is at position 'x'. The rectangle box is 2*w wide, the whisker 2*r. All drawing outside [ymin, ymax] is clipped. */ static void Graphics_drawBoxPlot (Graphics g, double data[], long ndata, double x, double r, double w, double ymin, double ymax) { int lineType = Graphics_inqLineType (g); Melder_assert (r > 0 && w > 0); if (ndata < 3) { return; } /* Sort the data (increasing: data[1] <= ... <= data[ndata]). Get the median (q50) and the upper and lower quartile points (q25 and q75). Now q25 and q75 are the lower and upper hinges, respectively. The fances can be calcultaed from q25 and q75. The spread is defined as the interquartile range or midrange |q75 - q25|. The fences are defined as: (lower/upper) innerfence = (lower/upper) hinge +/- 1.5 hspread (lower/upper) outerfence = (lower/upper) hinge +/- 3.0 hspread */ NUMsort_d (ndata, data); if (ymax <= ymin) { ymin = data[1]; ymax = data[ndata]; } if (data[1] > ymax || data[ndata] < ymin) { return; } double mean = 0; for (long i = 1; i <= ndata; i++) { mean += data[i]; } mean /= ndata; double q25 = NUMquantile (ndata, data, 0.25); double q50 = NUMquantile (ndata, data, 0.5); double q75 = NUMquantile (ndata, data, 0.75); double hspread = fabs (q75 - q25); double lowerOuterFence = q25 - 3.0 * hspread; double lowerInnerFence = q25 - 1.5 * hspread; double upperInnerFence = q75 + 1.5 * hspread; double upperOuterFence = q75 + 3.0 * hspread; /* Decide whether there are outliers that have to be drawn. First process data from below (data are sorted). */ long i = 1, ie = ndata; while (i <= ie && data[i] < ymin) { i++; } Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); while (i <= ie && data[i] < lowerOuterFence) { Graphics_text (g, x, data[i], L"o"); i++; } while (i <= ie && data[i] < lowerInnerFence) { Graphics_text (g, x, data[i], L"*"); i++; } double lowerWhisker = data[i] < q25 ? data[i] : lowerInnerFence; if (lowerWhisker > ymax) { return; } // Next process data from above. i = ndata; ie = i; while (i >= ie && data[i] > ymax) { i--; } while (i >= ie && data[i] > upperOuterFence) { Graphics_text (g, x, data[i], L"o"); i--; } while (i >= ie && data[i] > upperInnerFence) { Graphics_text (g, x, data[i], L"*"); i--; } double upperWhisker = data[i] > q75 ? data[i] : upperInnerFence; if (upperWhisker < ymin) { return; } /* Determine what parts of the "box" have to be drawn within the range [ymin, ymax]. Horizontal lines first. */ double y1 = lowerWhisker; if (ymax > y1 && ymin < y1) { Graphics_line (g, x - r, y1, x + r, y1); } y1 = q25; if (ymax > y1 && ymin < y1) { Graphics_line (g, x - w, y1, x + w, y1); } y1 = q50; if (ymax > y1 && ymin < y1) { Graphics_line (g, x - w, y1, x + w, y1); } y1 = q75; if (ymax > y1 && ymin < y1) { Graphics_line (g, x - w, y1, x + w, y1); } y1 = upperWhisker; if (ymax > y1 && ymin < y1) { Graphics_line (g, x - r, y1, x + r, y1); } // Extension: draw the mean too. y1 = mean; if (ymax > y1 && ymin < y1) { Graphics_setLineType (g, Graphics_DOTTED); Graphics_line (g, x - w, y1, x + w, y1); Graphics_setLineType (g, lineType); } // Now process the vertical lines. y1 = lowerWhisker; double y2 = q25; if (ymax > y1 && ymin < y2) { y1 = MAX (y1, ymin); y2 = MIN (y2, ymax); Graphics_line (g, x, y1, x, y2); } y1 = q25; y2 = q75; if (ymax > y1 && ymin < y2) { y1 = MAX (y1, ymin); y2 = MIN (y2, ymax); Graphics_line (g, x - w, y1, x - w, y2); Graphics_line (g, x + w, y1, x + w, y2); } y1 = q75; y2 = upperWhisker; if (ymax > y1 && ymin < y2) { y1 = MAX (y1, ymin); y2 = MIN (y2, ymax); Graphics_line (g, x, y1, x, y2); } } void TableOfReal_drawBoxPlots (I, Graphics g, long rowmin, long rowmax, long colmin, long colmax, double ymin, double ymax, int garnish) { iam (TableOfReal); if (rowmax < rowmin || rowmax < 1) { rowmin = 1; rowmax = my numberOfRows; } if (rowmin < 1) { rowmin = 1; } if (rowmax > my numberOfRows) { rowmax = my numberOfRows; } long numberOfRows = rowmax - rowmin + 1; if (colmax < colmin || colmax < 1) { colmin = 1; colmax = my numberOfColumns; } if (colmin < 1) { colmin = 1; } if (colmax > my numberOfColumns) { colmax = my numberOfColumns; } if (ymax <= ymin) { NUMmatrix_extrema (my data, rowmin, rowmax, colmin, colmax, &ymin, &ymax); } autoNUMvector data (1, numberOfRows); Graphics_setWindow (g, colmin - 0.5, colmax + 0.5, ymin, ymax); Graphics_setInner (g); for (long j = colmin; j <= colmax; j++) { double x = j, r = 0.05, w = 0.2, t; long ndata = 0; for (long i = 1; i <= numberOfRows; i++) { if ( (t = my data[rowmin + i - 1][j]) != NUMundefined) { data[++ndata] = t; } } Graphics_drawBoxPlot (g, data.peek(), ndata, x, r, w, ymin, ymax); } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); for (long j = colmin; j <= colmax; j++) { if (my columnLabels && my columnLabels[j] && my columnLabels[j][0]) { Graphics_markBottom (g, j, 0, 1, 0, my columnLabels [j]); } } Graphics_marksLeft (g, 2, 1, 1, 0); } } int TableOfReal_equalLabels (I, thou, int rowLabels, int columnLabels) { iam (TableOfReal); thouart (TableOfReal); Melder_assert (rowLabels || columnLabels); if (rowLabels) { if (my numberOfRows != thy numberOfRows) { return 0; } if (my rowLabels == thy rowLabels) { return 1; } for (long i = 1; i <= my numberOfRows; i++) { if (Melder_wcscmp (my rowLabels[i], thy rowLabels[i])) { return 0; } } } if (columnLabels) { if (my numberOfColumns != thy numberOfColumns) { return 0; } if (my columnLabels == thy columnLabels) { return 1; } for (long i = 1; i <= my numberOfColumns; i++) { if (Melder_wcscmp (my columnLabels[i], thy columnLabels[i]) != 0) { return 0; } } } return 1; } void TableOfReal_copyLabels (I, thou, int rowOrigin, int columnOrigin) { iam (TableOfReal); thouart (TableOfReal); if (rowOrigin == 1) { if (my numberOfRows != thy numberOfRows) { Melder_throw ("#rows1 must equal #rows2"); } NUMstrings_copyElements (my rowLabels, thy rowLabels, 1, thy numberOfRows); } else if (rowOrigin == -1) { if (my numberOfColumns != thy numberOfRows) { Melder_throw ("#columns1 must equal #rows2."); } NUMstrings_copyElements (my columnLabels, thy rowLabels, 1, thy numberOfRows); } if (columnOrigin == 1) { if (my numberOfColumns != thy numberOfColumns) { Melder_throw ("#columns1 must equal #columns2."); } NUMstrings_copyElements (my columnLabels, thy columnLabels, 1, thy numberOfColumns); } else if (columnOrigin == -1) { if (my numberOfRows != thy numberOfColumns) { Melder_throw ("#rows1 must equal #columns2"); } NUMstrings_copyElements (my rowLabels, thy columnLabels, 1, thy numberOfColumns); } } void TableOfReal_labelsFromCollectionItemNames (I, thou, int row, int column) { iam (TableOfReal); try { thouart (Collection); if (row) { Melder_assert (my numberOfRows == thy size); for (long i = 1; i <= my numberOfRows; i++) { wchar_t const *name = Thing_getName ( (Thing) thy item[i]); TableOfReal_setRowLabel (me, i, name); } } if (column) { Melder_assert (my numberOfColumns == thy size); for (long i = 1; i <= my numberOfColumns; i++) { wchar_t const *name = Thing_getName ( (Thing) thy item[i]); TableOfReal_setColumnLabel (me, i, name); } } } catch (MelderError) { Melder_throw (me, ": labels not changed."); } } void TableOfReal_centreColumns (I) { iam (TableOfReal); NUMcentreColumns (my data, 1, my numberOfRows, 1, my numberOfColumns, NULL); } void TableOfReal_and_Categories_setRowLabels (I, Categories thee) { iam (TableOfReal); try { if (my numberOfRows != thy size) { Melder_throw ("The number of items in both objects must be equal."); } /* If anything goes wrong we must leave the Table intact. We first copy the Categories, swap the labels and then delete the newly created categories. */ autoCategories c = Data_copy (thee); for (long i = 1; i <= my numberOfRows; i++) { SimpleString s = (SimpleString) c -> item[i]; wchar_t *t = s -> string; s -> string = my rowLabels[i]; my rowLabels[i] = t; } } catch (MelderError) { Melder_throw (me, ": row labels not set from categories."); } } void TableOfReal_centreColumns_byRowLabel (I) { iam (TableOfReal); wchar_t *label = my rowLabels[1]; long index = 1; for (long i = 2; i <= my numberOfRows; i++) { wchar_t *li = my rowLabels[i]; if (Melder_wcscmp (li, label) != 0) { NUMcentreColumns (my data, index, i - 1, 1, my numberOfColumns, 0); label = li; index = i; } } NUMcentreColumns (my data, index, my numberOfRows, 1, my numberOfColumns, NULL); } double TableOfReal_getRowSum (I, long index) { iam (TableOfReal); if (index < 1 || index > my numberOfRows) { return NUMundefined; } double sum = 0; for (long j = 1; j <= my numberOfColumns; j++) { sum += my data[index][j]; } return sum; } double TableOfReal_getColumnSumByLabel (I, const wchar_t *label) { iam (TableOfReal); long index = TableOfReal_columnLabelToIndex (me, label); if (index < 1) { Melder_throw ("There is no \"", label, "\" column label."); } return TableOfReal_getColumnSum (me, index); } double TableOfReal_getRowSumByLabel (I, const wchar_t *label) { iam (TableOfReal); long index = TableOfReal_rowLabelToIndex (me, label); if (index < 1) { Melder_throw ("There is no \"", label, "\" row label."); } return TableOfReal_getRowSum (me, index); } double TableOfReal_getColumnSum (I, long index) { iam (TableOfReal); if (index < 1 || index > my numberOfColumns) { return NUMundefined; } double sum = 0; for (long i = 1; i <= my numberOfRows; i++) { sum += my data[i][index]; } return sum; } double TableOfReal_getGrandSum (I) { iam (TableOfReal); double sum = 0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { sum += my data[i][j]; } } return sum; } void TableOfReal_centreRows (I) { iam (TableOfReal); NUMcentreRows (my data, 1, my numberOfRows, 1, my numberOfColumns); } void TableOfReal_doubleCentre (I) { iam (TableOfReal); NUMdoubleCentre (my data, 1, my numberOfRows, 1, my numberOfColumns); } void TableOfReal_normalizeColumns (I, double norm) { iam (TableOfReal); NUMnormalizeColumns (my data, my numberOfRows, my numberOfColumns, norm); } void TableOfReal_normalizeRows (I, double norm) { iam (TableOfReal); NUMnormalizeRows (my data, my numberOfRows, my numberOfColumns, norm); } void TableOfReal_standardizeColumns (I) { iam (TableOfReal); NUMstandardizeColumns (my data, 1, my numberOfRows, 1, my numberOfColumns); } void TableOfReal_standardizeRows (I) { iam (TableOfReal); NUMstandardizeRows (my data, 1, my numberOfRows, 1, my numberOfColumns); } void TableOfReal_normalizeTable (I, double norm) { iam (TableOfReal); NUMnormalize (my data, my numberOfRows, my numberOfColumns, norm); } double TableOfReal_getTableNorm (I) { iam (TableOfReal); double sumsq = 0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { sumsq += my data[i][j] * my data[i][j]; } } return sqrt (sumsq); } int TableOfReal_checkPositive (I) { iam (TableOfReal); long negative = 0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { if (my data[i][j] < 0) { negative ++; break; } } } return negative == 0; } /* NUMundefined ??? */ void NUMdmatrix_getColumnExtrema (double **a, long rowb, long rowe, long icol, double *min, double *max); void NUMdmatrix_getColumnExtrema (double **a, long rowb, long rowe, long icol, double *min, double *max) { *min = *max = a[rowb][icol]; for (long i = rowb + 1; i <= rowe; i++) { double t = a[i][icol]; if (t > *max) { *max = t; } else if (t < *min) { *min = t; } } } void TableOfReal_drawScatterPlotMatrix (I, Graphics g, long colb, long cole, double fractionWhite) { iam (TableOfReal); long m = my numberOfRows; if (colb == 0 && cole == 0) { colb = 1; cole = my numberOfColumns; } else if (cole < colb || colb < 1 || cole > my numberOfColumns) { return; } long n = cole - colb + 1; if (n == 1) { return; } autoNUMvector xmin (colb, cole); autoNUMvector xmax (colb, cole); for (long j = colb; j <= cole; j++) { xmin[j] = xmax[j] = my data[1][j]; } for (long i = 2; i <= m; i++) { for (long j = colb; j <= cole; j++) { if (my data[i][j] > xmax[j]) { xmax[j] = my data[i][j]; } else if (my data[i][j] < xmin[j]) { xmin[j] = my data[i][j]; } } } for (long j = colb; j <= cole; j++) { double extra = fractionWhite * fabs (xmax[j] - xmin[j]); if (extra == 0) { extra = 0.5; } xmin[j] -= extra; xmax[j] += extra; } Graphics_setWindow (g, 0, n, 0, n); Graphics_setInner (g); Graphics_line (g, 0, n, n, n); Graphics_line (g, 0, 0, 0, n); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (long i = 1; i <= n; i++) { long xcol, ycol = colb + i - 1; wchar_t const *mark; wchar label[20]; Graphics_line (g, 0, n - i, n, n - i); Graphics_line (g, i, n, i, 0); for (long j = 1; j <= n; j++) { xcol = colb + j - 1; if (i == j) { mark = my columnLabels[xcol]; if (! mark) { swprintf (label, 20, L"Column %ld", xcol); mark = label; } Graphics_text (g, j - 0.5, n - i + 0.5, mark); } else { for (long k = 1; k <= m; k++) { double x = j - 1 + (my data[k][xcol] - xmin[xcol]) / (xmax[xcol] - xmin[xcol]); double y = n - i + (my data[k][ycol] - xmin[ycol]) / (xmax[ycol] - xmin[ycol]); mark = EMPTY_STRING (my rowLabels[k]) ? L"+" : my rowLabels[k]; Graphics_text (g, x, y, mark); } } } } Graphics_unsetInner (g); } void TableOfReal_drawScatterPlot (I, Graphics g, long icx, long icy, long rowb, long rowe, double xmin, double xmax, double ymin, double ymax, int labelSize, int useRowLabels, const wchar_t *label, int garnish) { iam (TableOfReal); double m = my numberOfRows, n = my numberOfColumns; int fontSize = Graphics_inqFontSize (g); if (icx < 1 || icx > n || icy < 1 || icy > n) { return; } if (rowb < 1) { rowb = 1; } if (rowe > m) { rowe = m; } if (rowe <= rowb) { rowb = 1; rowe = m; } if (xmax == xmin) { NUMdmatrix_getColumnExtrema (my data, rowb, rowe, icx, & xmin, & xmax); double tmp = xmax - xmin == 0 ? 0.5 : 0.0; xmin -= tmp; xmax += tmp; } if (ymax == ymin) { NUMdmatrix_getColumnExtrema (my data, rowb, rowe, icy, & ymin, & ymax); double tmp = ymax - ymin == 0 ? 0.5 : 0.0; ymin -= tmp; ymax += tmp; } Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setInner (g); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_setFontSize (g, labelSize); long noLabel = 0; for (long i = rowb; i <= rowe; i++) { double x = my data[i][icx], y = my data[i][icy]; if ( ( (xmin < xmax && x >= xmin && x <= xmax) || (xmin > xmax && x <= xmin && x >= xmax)) && ( (ymin < ymax && y >= ymin && y <= ymax) || (ymin > ymax && y <= ymin && y >= ymax))) { const wchar_t *plotLabel = useRowLabels ? my rowLabels[i] : label; if (! NUMstring_containsPrintableCharacter (plotLabel)) { noLabel++; continue; } Graphics_text (g, x, y, plotLabel); } } Graphics_setFontSize (g, fontSize); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); if (ymin < ymax) { if (my columnLabels[icx]) { Graphics_textBottom (g, 1, my columnLabels[icx]); } Graphics_marksBottom (g, 2, 1, 1, 0); } else { if (my columnLabels[icx]) { Graphics_textTop (g, 1, my columnLabels[icx]); } Graphics_marksTop (g, 2, 1, 1, 0); } if (xmin < xmax) { if (my columnLabels[icy]) { Graphics_textLeft (g, 1, my columnLabels[icy]); } Graphics_marksLeft (g, 2, 1, 1, 0); } else { if (my columnLabels[icy]) { Graphics_textRight (g, 1, my columnLabels[icy]); } Graphics_marksRight (g, 2, 1, 1, 0); } } if (noLabel > 0) { Melder_warning (Melder_integer (noLabel), L" from ", Melder_integer (my numberOfRows), L" labels are " "not visible because they are empty or they contain only spaces or non-printable characters"); } } /**************** TABLESOFREAL **************************************/ Thing_implement (TablesOfReal, Ordered, 0); void TablesOfReal_init (I, ClassInfo klas) { iam (TablesOfReal); Ordered_init (me, klas, 10); } TablesOfReal TablesOfReal_create () { try { autoTablesOfReal me = Thing_new (TablesOfReal); TablesOfReal_init (me.peek(), classTableOfReal); return me.transfer(); } catch (MelderError) { Melder_throw ("TablesOfReal not created."); } } TableOfReal TablesOfReal_sum (I) { iam (TablesOfReal); try { if (my size <= 0) { return 0; } autoTableOfReal thee = Data_copy ( (TableOfReal) my item[1]); for (long i = 2; i <= my size; i++) { TableOfReal him = (TableOfReal) my item[i]; if (thy numberOfRows != his numberOfRows || thy numberOfColumns != his numberOfColumns || ! TableOfReal_equalLabels (thee.peek(), him, 1, 1)) { Melder_throw ("Dimensions or labels differ for table 1 and ", i, "."); } for (long j = 1; j <= thy numberOfRows; j++) { for (long k = 1; k <= thy numberOfColumns; k++) { thy data[j][k] += his data[j][k]; } } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": sum not created."); } } int TablesOfReal_checkDimensions (I) { iam (TablesOfReal); if (my size < 2) { return 1; } TableOfReal t1 = (TableOfReal) my item[1]; for (long i = 2; i <= my size; i++) { TableOfReal t = (TableOfReal) my item[i]; if (t -> numberOfColumns != t1 -> numberOfColumns || t -> numberOfRows != t1 -> numberOfRows) { return 0; } } return 1; } double TableOfReal_getColumnQuantile (I, long col, double quantile) { try { iam (TableOfReal); if (col < 1 || col > my numberOfColumns) { return NUMundefined; } autoNUMvector values (1, my numberOfRows); for (long i = 1; i <= my numberOfRows; i++) { values[i] = my data[i][col]; } NUMsort_d (my numberOfRows, values.peek()); double r = NUMquantile (my numberOfRows, values.peek(), quantile); return r; } catch (MelderError) { return NUMundefined; } } static TableOfReal TableOfReal_createPolsVanNieropData (int choice, int include_levels) { try { autoTable table = Table_createFromPolsVanNieropData (); // Default: Pols 50 males, first part of the table. long nrows = 50 * 12; long ncols = include_levels ? 6 : 3; long ib = 1; if (choice == 2) { /* Van Nierop 25 females */ ib = nrows + 1; nrows = 25 * 12; } autoTableOfReal thee = TableOfReal_create (nrows, ncols); for (long i = 1; i <= nrows; i++) { TableRow row = (TableRow) table -> rows -> item[ib + i - 1]; TableOfReal_setRowLabel (thee.peek(), i, row -> cells[4].string); for (long j = 1; j <= 3; j++) { thy data[i][j] = Melder_atof (row -> cells[4 + j].string); if (include_levels) { thy data[i][3 + j] = Melder_atof (row -> cells[7 + j].string); } } } for (long j = 1; j <= 3; j++) { wchar_t const *label = table -> columnHeaders[4 + j].label; TableOfReal_setColumnLabel (thee.peek(), j, label); if (include_levels) { label = table -> columnHeaders[7 + j].label; TableOfReal_setColumnLabel (thee.peek(), 3 + j, label); } } return thee.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal from Pols & Van Nierop data not created."); } } TableOfReal TableOfReal_createFromPolsData_50males (int include_levels) { return TableOfReal_createPolsVanNieropData (1, include_levels); } TableOfReal TableOfReal_createFromVanNieropData_25females (int include_levels) { return TableOfReal_createPolsVanNieropData (2, include_levels); } TableOfReal TableOfReal_createFromWeeninkData (int option) { try { long nvowels = 12, ncols = 3, nrows = 10 * nvowels; autoTable table = Table_createFromWeeninkData (); long ib = option == 1 ? 1 : option == 2 ? 11 : 21; /* m f c*/ ib = (ib - 1) * nvowels + 1; autoTableOfReal thee = TableOfReal_create (nrows, ncols); for (long i = 1; i <= nrows; i++) { TableRow row = (TableRow) table -> rows -> item[ib + i - 1]; TableOfReal_setRowLabel (thee.peek(), i, row -> cells[5].string); for (long j = 1; j <= 3; j++) { thy data[i][j] = Melder_atof (row -> cells[6 + j].string); /* Skip F0 */ } } for (long j = 1; j <= 3; j++) { wchar_t const *label = table -> columnHeaders[6 + j].label; TableOfReal_setColumnLabel (thee.peek(), j, label); } return thee.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal from Weenink data not created."); } } TableOfReal TableOfReal_randomizeRows (TableOfReal me) { try { autoPermutation p = Permutation_create (my numberOfRows); Permutation_permuteRandomly_inline (p.peek(), 0, 0); autoTableOfReal thee = TableOfReal_and_Permutation_permuteRows (me, p.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": randomized rows not created"); } } TableOfReal TableOfReal_bootstrap (TableOfReal me) { try { autoTableOfReal thee = TableOfReal_create (my numberOfRows, my numberOfColumns); // Copy column labels. for (long i = 1; i <= my numberOfColumns; i++) { if (my columnLabels[i]) { TableOfReal_setColumnLabel (thee.peek(), i, my columnLabels[i]); } } /* Select randomly from table with replacement. Because of replacement you do not get back the original data set. A random fraction, typically 1/e (37%) are replaced by duplicates. */ for (long i = 1; i <= my numberOfRows; i++) { long p = NUMrandomInteger (1, my numberOfRows); NUMvector_copyElements (my data[p], thy data[i], 1, my numberOfColumns); if (my rowLabels[p]) { TableOfReal_setRowLabel (thee.peek(), i, my rowLabels[p]); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": bootstrapped data not created."); } } void TableOfReal_changeRowLabels (I, const wchar_t *search, const wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp) { iam (TableOfReal); try { autostringvector rowLabels (strs_replace (my rowLabels, 1, my numberOfRows, search, replace, maximumNumberOfReplaces, nmatches, nstringmatches, use_regexp), 1, my numberOfRows); NUMstrings_free (my rowLabels, 1, my numberOfRows); my rowLabels = rowLabels.transfer(); } catch (MelderError) { Melder_throw (me, ": row labels not changed."); } } void TableOfReal_changeColumnLabels (I, const wchar_t *search, const wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp) { iam (TableOfReal); try { autostringvector columnLabels (strs_replace (my columnLabels, 1, my numberOfColumns, search, replace, maximumNumberOfReplaces, nmatches, nstringmatches, use_regexp), 1, my numberOfColumns); NUMstrings_free (my columnLabels, 1, my numberOfColumns); my columnLabels = columnLabels.transfer(); } catch (MelderError) { Melder_throw (me, ": column labels not changed."); } } long TableOfReal_getNumberOfLabelMatches (I, const wchar_t *search, int columnLabels, int use_regexp) { iam (TableOfReal); long nmatches = 0, numberOfLabels = my numberOfRows; wchar_t **labels = my rowLabels; regexp *compiled_regexp = 0; if (search == 0 || wcslen (search) == 0) { return 0; } if (columnLabels) { numberOfLabels = my numberOfColumns; labels = my columnLabels; } if (use_regexp) { const wchar_t *compileMsg; compiled_regexp = CompileRE ( (regularExp_CHAR *) search, &compileMsg, 0); if (compiled_regexp == 0) { Melder_throw (compileMsg); } } for (long i = 1; i <= numberOfLabels; i++) { if (labels[i] == 0) { continue; } if (use_regexp) { if (ExecRE (compiled_regexp, 0, (regularExp_CHAR *) labels[i], NULL, 0, '\0', '\0', 0, 0, 0)) { nmatches++; } } else if (wcsequ (labels[i], search)) { nmatches++; } } if (use_regexp) { free (compiled_regexp); } return nmatches; } void TableOfReal_drawVectors (I, Graphics g, long colx1, long coly1, long colx2, long coly2, double xmin, double xmax, double ymin, double ymax, int vectype, int labelsize, int garnish) { iam (TableOfReal); long nx = my numberOfColumns, ny = my numberOfRows; int fontsize = Graphics_inqFontSize (g); if (colx1 < 1 || colx1 > nx || coly1 < 1 || coly1 > nx) { Melder_warning (L"The index in the \"From\" column(s) must be in range [1, ", Melder_integer (nx), L"]."); return; } if (colx2 < 1 || colx2 > nx || coly2 < 1 || coly2 > nx) { Melder_warning (L"The index in the \"To\" column(s) must be in range [1, ", Melder_integer (nx), L"]."); return; } double min, max; if (xmin >= xmax) { NUMmatrix_extrema (my data, 1, ny, colx1, colx1, &min, &max); NUMmatrix_extrema (my data, 1, ny, colx2, colx2, &xmin, &xmax); if (min < xmin) { xmin = min; } if (max > xmax) { xmax = max; } } if (ymin >= ymax) { NUMmatrix_extrema (my data, 1, ny, coly1, coly1, &min, &max); NUMmatrix_extrema (my data, 1, ny, coly2, coly2, &ymin, &ymax); if (min < ymin) { ymin = min; } if (max > ymax) { ymax = max; } } if (xmin == xmax) { if (ymin == ymax) { return; } xmin -= 0.5; xmax += 0.5; } if (ymin == ymax) { ymin -= 0.5; ymax += 0.5; } Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setInner (g); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); if (labelsize > 0) { Graphics_setFontSize (g, labelsize); } for (long i = 1; i <= ny; i++) { double x1 = my data[i][colx1]; double y1 = my data[i][coly1]; double x2 = my data[i][colx2]; double y2 = my data[i][coly2]; wchar_t const *mark = EMPTY_STRING (my rowLabels[i]) ? L"" : my rowLabels[i]; if (vectype == Graphics_LINE) { Graphics_line (g, x1, y1, x2, y2); } else if (vectype == Graphics_TWOWAYARROW) { Graphics_arrow (g, x1, y1, x2, y2); Graphics_arrow (g, x2, y2, x1, y1); } else { /*if (vectype == Graphics_ARROW) */ Graphics_arrow (g, x1, y1, x2, y2); } if (labelsize > 0) { Graphics_text (g, x1, y1, mark); } } if (labelsize > 0) { Graphics_setFontSize (g, fontsize); } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_marksBottom (g, 2, 1, 1, 0); } } void TableOfReal_drawColumnAsDistribution (I, Graphics g, int column, double minimum, double maximum, long nBins, double freqMin, double freqMax, int cumulative, int garnish) { iam (TableOfReal); if (column < 1 || column > my numberOfColumns) { return; } autoMatrix thee = TableOfReal_to_Matrix (me); Matrix_drawDistribution (thee.peek(), g, column - 0.5, column + 0.5, 0, 0, minimum, maximum, nBins, freqMin, freqMax, cumulative, garnish); if (garnish && my columnLabels[column] != 0) { Graphics_textBottom (g, 1, my columnLabels[column]); } } TableOfReal TableOfReal_sortRowsByIndex (I, long *index, int reverse) { iam (TableOfReal); try { if (my rowLabels == 0) { Melder_throw ("No labels to sort"); } double min, max; NUMvector_extrema (index, 1, my numberOfRows, &min, &max); if (min < 1 || max > my numberOfRows) { Melder_throw ("One or more indices out of range [1, ", my numberOfRows, "]."); } autoTableOfReal thee = TableOfReal_create (my numberOfRows, my numberOfColumns); for (long i = 1; i <= my numberOfRows; i++) { long myindex = reverse ? i : index[i]; long thyindex = reverse ? index[i] : i; wchar_t *mylabel = my rowLabels[myindex]; double *mydata = my data[myindex]; double *thydata = thy data[thyindex]; // Copy the row label thy rowLabels[i] = Melder_wcsdup (mylabel); // Copy the row values for (long j = 1; j <= my numberOfColumns; j++) { thydata[j] = mydata[j]; } } // Copy column labels. NUMstrings_copyElements (my columnLabels, thy columnLabels, 1, my numberOfColumns); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not sorted by row index."); } } long *TableOfReal_getSortedIndexFromRowLabels (I) { iam (TableOfReal); try { autoNUMvector index (1, my numberOfRows); NUMindexx_s (my rowLabels, my numberOfRows, index.peek()); return index.transfer(); } catch (MelderError) { Melder_throw (me, ": no sorted index created."); } } TableOfReal TableOfReal_sortOnlyByRowLabels (I) { iam (TableOfReal); try { autoPermutation index = TableOfReal_to_Permutation_sortRowLabels (me); autoTableOfReal thee = TableOfReal_and_Permutation_permuteRows (me, index.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not sorted by row labels."); } } static void NUMmedianizeColumns (double **a, long rb, long re, long cb, long ce) { long n = re - rb + 1; if (n < 2) { return; } autoNUMvector tmp (1, n); for (long j = cb; j <= ce; j++) { long k = 1; for (long i = rb; i <= re; i++, k++) { tmp[k] = a[i][j]; } NUMsort_d (n, tmp.peek()); double median = NUMquantile (n, tmp.peek(), 0.5); for (long i = rb; i <= re; i++) { a[i][j] = median; } } } static void NUMstatsColumns (double **a, long rb, long re, long cb, long ce, int stats) { if (stats == 0) { NUMaverageColumns (a, rb, re, cb, ce); } else { NUMmedianizeColumns (a, rb, re, cb, ce); } } TableOfReal TableOfReal_meansByRowLabels (I, int expand, int stats) { iam (TableOfReal); try { autoTableOfReal thee = 0; autoNUMvector index (TableOfReal_getSortedIndexFromRowLabels (me), 1); autoTableOfReal sorted = TableOfReal_sortRowsByIndex (me, index.peek(), 0); long indexi = 1, indexr = 0; wchar_t const *label = sorted -> rowLabels[1]; for (long i = 2; i <= my numberOfRows; i++) { wchar_t const *li = sorted -> rowLabels[i]; if (Melder_wcscmp (li, label) != 0) { NUMstatsColumns (sorted -> data, indexi, i - 1, 1, my numberOfColumns, stats); if (expand == 0) { indexr++; TableOfReal_copyOneRowWithLabel (sorted.peek(), sorted.peek(), indexi, indexr); } label = li; indexi = i; } } NUMstatsColumns (sorted -> data, indexi, my numberOfRows, 1, my numberOfColumns, stats); if (expand != 0) { // Now invert the table. wchar_t **tmp = sorted -> rowLabels; sorted -> rowLabels = my rowLabels; thee.reset (TableOfReal_sortRowsByIndex (sorted.peek(), index.peek(), 1)); sorted -> rowLabels = tmp; } else { indexr++; TableOfReal_copyOneRowWithLabel (sorted.peek(), sorted.peek(), indexi, indexr); thee.reset (TableOfReal_create (indexr, my numberOfColumns)); for (long i = 1; i <= indexr; i++) { TableOfReal_copyOneRowWithLabel (sorted.peek(), thee.peek(), i, i); } NUMstrings_copyElements (sorted -> columnLabels, thy columnLabels, 1, my numberOfColumns); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": means by row labels not created."); } } TableOfReal TableOfReal_rankColumns (I) { iam (TableOfReal); try { autoTableOfReal thee = Data_copy (me); NUMrankColumns (thy data, 1, thy numberOfRows, 1, thy numberOfColumns); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": column ranks not created."); } } void TableOfReal_setSequentialColumnLabels (I, long from, long to, const wchar_t *precursor, long number, long increment) { iam (TableOfReal); if (from == 0) { from = 1; } if (to == 0) { to = my numberOfColumns; } if (from < 1 || from > my numberOfColumns || to < from || to > my numberOfColumns) { Melder_throw ("Wrong column indices."); } NUMstrings_setSequentialNumbering (my columnLabels, from, to, precursor, number, increment); } void TableOfReal_setSequentialRowLabels (I, long from, long to, const wchar_t *precursor, long number, long increment) { iam (TableOfReal); if (from == 0) { from = 1; } if (to == 0) { to = my numberOfRows; } if (from < 1 || from > my numberOfRows || to < from || to > my numberOfRows) { Melder_throw ("Wrong row indices."); } NUMstrings_setSequentialNumbering (my rowLabels, from, to, precursor, number, increment); } /* For the inheritors */ TableOfReal TableOfReal_to_TableOfReal (I) { iam (TableOfReal); try { autoTableOfReal thee = TableOfReal_create (my numberOfRows, my numberOfColumns); NUMmatrix_copyElements (my data, thy data, 1, my numberOfRows, 1, my numberOfColumns); TableOfReal_copyLabels (me, thee.peek(), 1, 1); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not copied."); } } TableOfReal TableOfReal_choleskyDecomposition (I, int upper, int inverse) { iam (TableOfReal); try { char diag = 'N'; long n = my numberOfColumns, lda = my numberOfRows, info; if (n != lda) { Melder_throw ("The table must be a square symmetric table."); } autoTableOfReal thee = Data_copy (me); if (upper) { for (long i = 2; i <= n; i++) for (long j = 1; j < i; j++) { thy data[i][j] = 0; } } else { for (long i = 1; i < n; i++) for (long j = i + 1; j <= n; j++) { thy data[i][j] = 0; } } char uplo = upper ? 'L' : 'U'; NUMlapack_dpotf2 (&uplo, &n, &thy data[1][1], &lda, &info); if (info != 0) { Melder_throw ("dpotf2 fails"); } if (inverse) { NUMlapack_dtrtri (&uplo, &diag, &n, &thy data[1][1], &lda, &info); if (info != 0) { Melder_throw ("dtrtri fails"); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Cholesky decomposition not performed."); } } TableOfReal TableOfReal_appendColumns (I, thou) { try { iam (TableOfReal); thouart (TableOfReal); long ncols = my numberOfColumns + thy numberOfColumns; long labeldiffs = 0; if (my numberOfRows != thy numberOfRows) { Melder_throw ("Number of rows must be equal."); } /* Stricter label checking??? append only if (my rowLabels[i] == thy rowlabels[i], i=1..my numberOfRows) or (my rowLabels[i] == 'empty', i=1..my numberOfRows) or (thy rowLabels[i] == 'empty', i=1..my numberOfRows); 'empty': NULL or \w* */ autoTableOfReal him = TableOfReal_create (my numberOfRows, ncols); NUMstrings_copyElements (my rowLabels, his rowLabels, 1, my numberOfRows); NUMstrings_copyElements (my columnLabels, his columnLabels, 1, my numberOfColumns); NUMstrings_copyElements (thy columnLabels, &his columnLabels[my numberOfColumns], 1, thy numberOfColumns); for (long i = 1; i <= my numberOfRows; i++) { if (Melder_wcscmp (my rowLabels[i], thy rowLabels[i]) != 0) { labeldiffs++; } NUMvector_copyElements (my data[i], his data[i], 1, my numberOfColumns); NUMvector_copyElements (thy data[i], &his data[i][my numberOfColumns], 1, thy numberOfColumns); } if (labeldiffs > 0) { Melder_warning (Melder_integer (labeldiffs), L" row labels differed."); } return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal with appended columns not created."); } } TableOfReal TableOfReal_appendColumnsMany (Collection me) { try { if (my size == 0) { Melder_throw ("No tables selected."); } TableOfReal thee = (TableOfReal) my item [1]; long nrow = thy numberOfRows; long ncol = thy numberOfColumns; for (long itab = 2; itab <= my size; itab++) { thee = (TableOfReal) my item [itab]; ncol += thy numberOfColumns; if (thy numberOfRows != nrow) { Melder_throw ("Numbers of rows in item ", itab, " differs from previous."); } } autoTableOfReal him = Thing_new (TableOfReal); TableOfReal_init (him.peek(), nrow, ncol); /* Unsafe: new attributes not initialized. */ for (long irow = 1; irow <= nrow; irow++) { TableOfReal_setRowLabel (him.peek(), irow, thy rowLabels [irow]); } ncol = 0; for (long itab = 1; itab <= my size; itab++) { thee = (TableOfReal) my item [itab]; for (long icol = 1; icol <= thy numberOfColumns; icol++) { ncol++; TableOfReal_setColumnLabel (him.peek(), ncol, thy columnLabels [icol]); for (long irow = 1; irow <= nrow; irow++) { his data[irow][ncol] = thy data[irow][icol]; } } } Melder_assert (ncol == his numberOfColumns); return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal with appended columns not created."); } } double TableOfReal_normalityTest_BHEP (I, double *h, double *tnb, double *lnmu, double *lnvar) { iam (TableOfReal); try { long n = my numberOfRows, p = my numberOfColumns; double beta = *h > 0 ? NUMsqrt1_2 / *h : NUMsqrt1_2 * pow ( (1.0 + 2 * p) / 4, 1.0 / (p + 4)) * pow (n, 1.0 / (p + 4)); double p2 = p / 2.0; double beta2 = beta * beta, beta4 = beta2 * beta2, beta8 = beta4 * beta4; double gamma = 1 + 2 * beta2, gamma2 = gamma * gamma, gamma4 = gamma2 * gamma2; double delta = 1.0 + beta2 * (4 + 3 * beta2), delta2 = delta * delta; double prob = NUMundefined; if (*h <= 0) { *h = NUMsqrt1_2 / beta; } *tnb = *lnmu = *lnvar = NUMundefined; if (n < 2 || p < 1) { return NUMundefined; } autoCovariance thee = TableOfReal_to_Covariance (me); try { SSCP_expandLowerCholesky (thee.peek()); } catch (MelderError) { *tnb = 4 * n; } { double djk, djj, sumjk = 0, sumj = 0; double b1 = beta2 / 2, b2 = b1 / (1.0 + beta2); /* Heinze & Wagner (1997), page 3 We use d[j][k] = ||Y[j]-Y[k]||^2 = (Y[j]-Y[k])'S^(-1)(Y[j]-Y[k]) So d[j][k]= d[k][j] and d[j][j] = 0 */ for (long j = 1; j <= n; j++) { for (long k = 1; k < j; k++) { djk = NUMmahalanobisDistance_chi (thy lowerCholesky, my data[j], my data[k], p, p); sumjk += 2 * exp (-b1 * djk); // factor 2 because d[j][k] == d[k][j] } sumjk += 1; // for k == j djj = NUMmahalanobisDistance_chi (thy lowerCholesky, my data[j], thy centroid, p, p); sumj += exp (-b2 * djj); } *tnb = (1.0 / n) * sumjk - 2.0 * pow (1.0 + beta2, - p2) * sumj + n * pow (gamma, - p2); // n * } double mu = 1.0 - pow (gamma, -p2) * (1.0 + p * beta2 / gamma + p * (p + 2) * beta4 / (2 * gamma2)); double var = 2.0 * pow (1 + 4 * beta2, -p2) + 2.0 * pow (gamma, -p) * (1.0 + 2 * p * beta4 / gamma2 + 3 * p * (p + 2) * beta8 / (4 * gamma4)) - 4.0 * pow (delta, -p2) * (1.0 + 3 * p * beta4 / (2 * delta) + p * (p + 2) * beta8 / (2 * delta2)); double mu2 = mu * mu; *lnmu = 0.5 * log (mu2 * mu2 / (mu2 + var)); //log (sqrt (mu2 * mu2 /(mu2 + var))); *lnvar = sqrt (log ( (mu2 + var) / mu2)); prob = NUMlogNormalQ (*tnb, *lnmu, *lnvar); return prob; } catch (MelderError) { Melder_throw (me, ": cannot determine normality."); } } TableOfReal TableOfReal_and_TableOfReal_crossCorrelations (I, thou, int by_columns, int center, int normalize) { iam (TableOfReal); thouart (TableOfReal); return by_columns ? TableOfReal_and_TableOfReal_columnCorrelations (me, thee, center, normalize) : TableOfReal_and_TableOfReal_rowCorrelations (me, thee, center, normalize); } TableOfReal TableOfReal_and_TableOfReal_rowCorrelations (I, thou, int center, int normalize) { try { iam (TableOfReal); thouart (TableOfReal); if (my numberOfColumns != thy numberOfColumns) { Melder_throw (L"Both tables must have the same number of columns."); } autoTableOfReal him = TableOfReal_create (my numberOfRows, thy numberOfRows); autoNUMmatrix my_data (NUMmatrix_copy (my data, 1, my numberOfRows, 1, my numberOfColumns), 1, 1); autoNUMmatrix thy_data (NUMmatrix_copy (thy data, 1, thy numberOfRows, 1, thy numberOfColumns), 1, 1); if (center) { NUMcentreRows (my_data.peek(), 1, my numberOfRows, 1, my numberOfColumns); NUMcentreRows (thy_data.peek(), 1, thy numberOfRows, 1, thy numberOfColumns); } if (normalize) { NUMnormalizeRows (my_data.peek(), my numberOfRows, my numberOfColumns, 1); NUMnormalizeRows (thy_data.peek(), thy numberOfRows, thy numberOfColumns, 1); } NUMstrings_copyElements (my rowLabels, his rowLabels, 1, his numberOfRows); NUMstrings_copyElements (thy rowLabels, his columnLabels, 1, his numberOfColumns); for (long i = 1; i <= my numberOfRows; i++) { for (long k = 1; k <= thy numberOfRows; k++) { double ctmp = 0; for (long j = 1; j <= my numberOfColumns; j++) { ctmp += my_data[i][j] * thy_data[k][j]; } his data[i][k] = ctmp; } } return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal with row correlations not created."); } } TableOfReal TableOfReal_and_TableOfReal_columnCorrelations (I, thou, int center, int normalize) { try { iam (TableOfReal); thouart (TableOfReal); if (my numberOfRows != thy numberOfRows) { Melder_throw (L"Both tables must have the same number of rows."); } autoTableOfReal him = TableOfReal_create (my numberOfColumns, thy numberOfColumns); autoNUMmatrix my_data (NUMmatrix_copy (my data, 1, my numberOfRows, 1, my numberOfColumns), 1, 1); autoNUMmatrix thy_data (NUMmatrix_copy (thy data, 1, thy numberOfRows, 1, thy numberOfColumns), 1, 1); if (center) { NUMcentreColumns (my_data.peek(), 1, my numberOfRows, 1, my numberOfColumns, NULL); NUMcentreColumns (thy_data.peek(), 1, thy numberOfRows, 1, thy numberOfColumns, NULL); } if (normalize) { NUMnormalizeColumns (my_data.peek(), my numberOfRows, my numberOfColumns, 1); NUMnormalizeColumns (thy_data.peek(), thy numberOfRows, thy numberOfColumns, 1); } NUMstrings_copyElements (my columnLabels, his rowLabels, 1, his numberOfRows); NUMstrings_copyElements (thy columnLabels, his columnLabels, 1, his numberOfColumns); for (long j = 1; j <= my numberOfColumns; j++) { for (long k = 1; k <= thy numberOfColumns; k++) { double ctmp = 0; for (long i = 1; i <= my numberOfRows; i++) { ctmp += my_data[i][j] * thy_data[i][k]; } his data[j][k] = ctmp; } } return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal with column correlations not created."); } } #undef EMPTY_STRING #undef MAX #undef MIN /* End of file TableOfReal_extensions.c 1869*/ sources_5316/dwtools/MFCC.h0000644000176700017670000000350211752212656014306 0ustar paulpaul#ifndef _MFCC_h_ #define _MFCC_h_ /* MFCC.h * * Mel Frequency Cepstral Coefficients class. * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010501 djmw 20020813 GPL header djmw 20120504 Latest modification. */ #include "CC.h" #include "Sound.h" #include "TableOfReal.h" Thing_define (MFCC, CC) { }; /* Interpretation: Mel frequency cepstral coefficients as a function of time. c0 represents the average filter output (dB's). */ MFCC MFCC_create (double tmin, double tmax, long nt, double dt, double t1, long maximumNumberOfCoefficients, double fmin_mel, double fmax_mel); void MFCC_lifter (MFCC me, long lifter); /* Lifter the cepstral coefficients: c[i] *= (1 + lifter / 2 * sin (NUMpi * i / lifter)) */ TableOfReal MFCC_to_TableOfReal (MFCC me, bool includeC0); Sound MFCC_to_Sound (MFCC me); Sound MFCCs_crossCorrelate (MFCC me, MFCC thee, enum kSounds_convolve_scaling scaling, enum kSounds_convolve_signalOutsideTimeDomain signalOutsideTimeDomain); Sound MFCCs_convolve (MFCC me, MFCC thee, enum kSounds_convolve_scaling scaling, enum kSounds_convolve_signalOutsideTimeDomain signalOutsideTimeDomain); #endif /* _MFCC_h_ */ sources_5316/dwtools/Configuration_AffineTransform.h0000644000176700017670000000263211535126127021550 0ustar paulpaul#ifndef _Configuration_AffineTransform_h_ #define _Configuration_AffineTransform_h_ /* Configuration_AffineTransform.c * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020315 GPL header djmw 20110307 Latest modification */ #ifndef _Configuration_h_ #include "Configuration.h" #endif #ifndef _AffineTransform_h_ #include "AffineTransform.h" #endif #ifdef __cplusplus extern "C" { #endif AffineTransform Configurations_to_AffineTransform_congruence (Configuration me, Configuration thee, long maximumNumberOfIterations, double tolerance); Configuration Configuration_and_AffineTransform_to_Configuration (Configuration me, thou); #ifdef __cplusplus } #endif #endif /* _Configuration_AffineTransform_h_ */ sources_5316/dwtools/Sampled2_def.h0000644000176700017670000000206411627251337016065 0ustar paulpaul/* Sampled2_def.h * * Copyright (C) 1993-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19970408 djmw 20020813 GPL header */ #define ooSTRUCT Sampled2 oo_DEFINE_CLASS (Sampled2, Sampled) // David, dit was Data i.p.v. Sampled! oo_DOUBLE (ymin) oo_DOUBLE (ymax) oo_LONG (ny) oo_DOUBLE (dy) oo_DOUBLE (y1) oo_END_CLASS (Sampled2) #undef ooSTRUCT /* End of file Sampled2_def.h */ sources_5316/dwtools/TableOfReal_and_SVD.h0000644000176700017670000000245111607125752017255 0ustar paulpaul#ifndef _TableOfReal_and_SVD_h_ #define TableOfReal_and_SVD_h_ /* TableOfReal_and_SVD.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20021009 GPL header djmw 20110397 Latest modification */ #include "SVD.h" #include "TableOfReal.h" #ifdef __cplusplus extern "C" { #endif SVD TableOfReal_to_SVD (I); GSVD TablesOfReal_to_GSVD (I, thou); TableOfReal SVD_to_TableOfReal (SVD me, long from, long to); TableOfReal SVD_extractLeftSingularVectors (I); TableOfReal SVD_extractRightSingularVectors (I); TableOfReal SVD_extractSingularValues (I); #ifdef __cplusplus } #endif #endif // _TableOfReal_and_SVD_h_ sources_5316/dwtools/Polygon_extensions.cpp0000664000176700017670000011303611752177155020051 0ustar paulpaul/* Polygon_extensions.c * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20080122 float -> double djmw 20100407 Sound_to_Polygon, Sounds_to_Polygon_encloseds djmw 20100418 Polygon_rotate. bug: angle was in degrees now in radians */ #include "Matrix.h" #include "NUM2.h" #include "Polygon_extensions.h" #include "Vector.h" #include "DLL.h" // void Polygon_getExtrema (Polygon me, double *xmin, double *xmax, double *ymin, double *ymax) { *xmin = my x[1]; *xmax = my x[1]; *ymin = my y[1]; *ymax = my y[1]; for (long i = 2; i <= my numberOfPoints; i++) { if (my x[i] < *xmin) { *xmin = my x[i]; } else if (my x[i] > *xmax) { *xmax = my x[i]; } if (my y[i] < *ymin) { *ymin = my y[i]; } else if (my y[i] > *ymax) { *ymax = my y[i]; } } } Polygon Polygon_createSimple (wchar_t *xystring) { try { long numberOfPoints; autoNUMvector xys (NUMstring_to_numbers (xystring, &numberOfPoints), 1); if (numberOfPoints < 6) { Melder_throw ("There must be at least 3 points (= x,y pairs) in the Polygon"); } if (numberOfPoints % 2 != 0) { Melder_throw ("One value is missing."); } numberOfPoints /= 2; // x,y pairs autoPolygon me = Polygon_create (numberOfPoints); for (long i = 1; i <= numberOfPoints; i++) { my x[i] = xys[2 * i - 1]; my y[i] = xys[2 * i]; if (i > 1 && my x[i] == my x[i - 1] && my y[i] == my y[i - 1]) { Melder_warning ("Two successives vertices are equal."); } } return me.transfer(); } catch (MelderError) { Melder_throw ("Polygon not created."); } } Polygon Polygon_createFromRandomVertices (long numberOfVertices, double xmin, double xmax, double ymin, double ymax) { try { autoPolygon me = Polygon_create (numberOfVertices); for (long i = 1; i <= numberOfVertices; i++) { my x[i] = NUMrandomUniform (xmin, xmax); my y[i] = NUMrandomUniform (ymin, ymax); } return me.transfer(); } catch (MelderError) { Melder_throw ("Polygon not created."); } } void Polygon_translate (Polygon me, double xt, double yt) { for (long i = 1; i <= my numberOfPoints; i++) { my x[i] += xt; my y[i] += yt; } } /* rotate counterclockwise w.r.t. (xc,yc) */ void Polygon_rotate (Polygon me, double alpha, double xc, double yc) { double f = alpha * NUMpi / 180, cosa = cos (f), sina = sin (f); Polygon_translate (me, -xc, -yc); for (long i = 1; i <= my numberOfPoints; i++) { double x = my x[i]; my x[i] = cosa * my x[i] - sina * my y[i]; my y[i] = sina * x + cosa * my y[i]; } Polygon_translate (me, xc, yc); } void Polygon_scale (Polygon me, double xs, double ys) { for (long i = 1; i <= my numberOfPoints; i++) { my x[i] *= xs; my y[i] *= ys; } } void Polygon_reverseX (Polygon me) { for (long i = 1; i <= my numberOfPoints; i++) { my x[i] = -my x[i]; } } void Polygon_reverseY (Polygon me) { for (long i = 1; i <= my numberOfPoints; i++) { my y[i] = -my y[i]; } } void Polygon_Categories_draw (Polygon me, thou, Graphics graphics, double xmin, double xmax, double ymin, double ymax, int garnish) { thouart (Categories); double min, max, tmp; if (my numberOfPoints != thy size) { return; } if (xmax == xmin) { NUMvector_extrema (my x, 1, my numberOfPoints, & min, & max); tmp = max - min == 0 ? 0.5 : 0.0; xmin = min - tmp; xmax = max + tmp; } if (ymax == ymin) { NUMvector_extrema (my y, 1, my numberOfPoints, & min, & max); tmp = max - min == 0 ? 0.5 : 0.0; ymin = min - tmp; ymax = max + tmp; } Graphics_setInner (graphics); Graphics_setWindow (graphics, xmin, xmax, ymin, ymax); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_HALF); for (long i = 1; i <= my numberOfPoints; i++) { OrderedOfString_drawItem (thee, graphics, i, my x[i], my y[i]); } Graphics_unsetInner (graphics); if (garnish) { Graphics_drawInnerBox (graphics); Graphics_marksLeft (graphics, 2, 1, 1, 0); if (ymin * ymax < 0.0) { Graphics_markLeft (graphics, 0.0, 1, 1, 1, NULL); } Graphics_marksBottom (graphics, 2, 1, 1, 0); if (xmin * xmax < 0.0) { Graphics_markBottom (graphics, 0.0, 1, 1, 1, NULL); } } } static void setWindow (Polygon me, Graphics graphics, double xmin, double xmax, double ymin, double ymax) { Melder_assert (me); if (xmax <= xmin) { /* Autoscaling along x axis. */ xmax = xmin = my x [1]; for (long i = 2; i <= my numberOfPoints; i ++) { if (my x [i] < xmin) { xmin = my x [i]; } if (my x [i] > xmax) { xmax = my x [i]; } } if (xmin == xmax) { xmin -= 1.0; xmax += 1.0; } } if (ymax <= ymin) { /* Autoscaling along y axis. */ ymax = ymin = my y [1]; for (long i = 2; i <= my numberOfPoints; i ++) { if (my y [i] < ymin) { ymin = my y [i]; } if (my y [i] > ymax) { ymax = my y [i]; } } if (ymin == ymax) { ymin -= 1.0; ymax += 1.0; } } Graphics_setWindow (graphics, xmin, xmax, ymin, ymax); } void Polygon_drawMarks (Polygon me, Graphics g, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark) { Graphics_setInner (g); setWindow (me, g, xmin, xmax, ymin, ymax); for (long i = 1; i <= my numberOfPoints; i++) { Graphics_mark (g, my x[i], my y[i], size_mm, mark); } Graphics_unsetInner (g); } #define CLIP_Y(y,ymin,ymax) (clip ? ((y) > (ymax) ? (ymax) : (y) < (ymin) ? (ymin) : (y)) : y) Polygon Sound_to_Polygon (Sound me, int channel, double tmin, double tmax, double ymin, double ymax, double level) { try { bool clip = ymin < ymax; if (channel < 1 || channel > my ny) { Melder_throw ("Channel does not exist."); } if (tmin >= tmax) { tmin = my xmin; tmax = my xmax; } if (tmin < my xmin) { tmin = my xmin; } if (tmax > my xmax) { tmax = my xmax; } if (tmin >= my xmax || tmax < my xmin) { Melder_throw ("Invalid domain."); } long k = 1, i1 = Sampled_xToHighIndex (me, tmin); long i2 = Sampled_xToLowIndex (me, tmax); long numberOfPoints = i2 - i1 + 1 + 2 + 2; // begin + endpoint + level autoPolygon him = Polygon_create (numberOfPoints); /* In Vector_getValueAtX the interpolation only returns defined values between the left and right edges that are calculated as left = x1 - 0.5 * dx; right = left + my nx * dx. Given a sound, for example on the domain [0,...], the value of 'left' with the above formula might not return exactly xmin but instead a very small deviation (due to the imprecise representation of real numbers in a computer). Querying for the value at xmin which is outside the interpolation domain then produces an 'undefined'. We try to avoid this with the following workaround. */ double xmin = my x1 - 0.5 * my dx; double xmax = xmin + my nx * my dx; tmin = tmin < xmin ? xmin : tmin; tmax = tmax > xmax ? xmax : tmax; // End of workaround his x[k] = tmin; his y[k++] = CLIP_Y (level, ymin, ymax); his x[k] = tmin; double y = Vector_getValueAtX (me, tmin, channel, Vector_VALUE_INTERPOLATION_LINEAR); his y[k++] = CLIP_Y (y, ymin, ymax); for (long i = i1; i <= i2; i++) { y = my z[channel][i]; his x[k] = my x1 + (i - 1) * my dx; his y[k++] = CLIP_Y (y, ymin, ymax); } his x[k] = tmax; y = Vector_getValueAtX (me, tmax, channel, Vector_VALUE_INTERPOLATION_LINEAR); his y[k++] = CLIP_Y (y, ymin, ymax); his x[k] = tmax; his y[k++] = CLIP_Y (level, ymin, ymax); return him.transfer(); } catch (MelderError) { Melder_throw (me, ":no Polygon created."); } } /* Area inbetween */ Polygon Sounds_to_Polygon_enclosed (Sound me, Sound thee, int channel, double tmin, double tmax, double ymin, double ymax) { try { bool clip = ymin < ymax; if (my ny > 1 && thy ny > 1 && my ny != thy ny) { Melder_throw ("The numbers of channels of the two sounds have to be equal or 1."); } long numberOfChannels = my ny > thy ny ? my ny : thy ny; if (channel < 1 || channel > numberOfChannels) { Melder_throw ("Channel does not exist."); } // find overlap in the domains with xmin workaround as in Sound_to_Polygon double xmin1 = my x1 - 0.5 * my dx, xmin2 = thy x1 - 0.5 * thy dx ; double xmin = my xmin > thy xmin ? xmin1 : xmin2; double xmax = my xmax < thy xmax ? xmin1 + my nx * my dx : xmin2 + thy nx * thy dx; if (xmax <= xmin) { Melder_throw ("Domains must overlap."); } if (tmin >= tmax) { tmin = xmin; tmax = xmax; } if (tmin < xmin) { tmin = xmin; } if (tmax > xmax) { tmax = xmax; } if (tmin >= xmax || tmax < xmin) { Melder_throw ("Invalid domain."); } long k = 1; long ib1 = Sampled_xToHighIndex (me, tmin); long ie1 = Sampled_xToLowIndex (me, tmax); long n1 = ie1 - ib1 + 1; long ib2 = Sampled_xToHighIndex (thee, tmin); long ie2 = Sampled_xToLowIndex (thee, tmax); long n2 = ie2 - ib2 + 1; long numberOfPoints = n1 + n2 + 4; // me + thee + begin + endpoint + closing autoPolygon him = Polygon_create (numberOfPoints); // my starting point at tmin double y = Vector_getValueAtX (me, tmin, (my ny == 1 ? 1 : channel), Vector_VALUE_INTERPOLATION_LINEAR); his x[k] = tmin; his y[k++] = CLIP_Y (y, ymin, ymax); // my samples for (long i = ib1; i <= ie1; i++) { double t = my x1 + (i - 1) * my dx; y = my z[my ny == 1 ? 1 : channel][i]; his x[k] = t; his y[k++] = CLIP_Y (y, ymin, ymax); } // my end point at tmax y = Vector_getValueAtX (me, tmax, (my ny == 1 ? 1 : channel), Vector_VALUE_INTERPOLATION_LINEAR); his x[k] = tmax; his y[k++] = y; // thy starting point at tmax y = Vector_getValueAtX (thee, tmax, (thy ny == 1 ? 1 : channel), Vector_VALUE_INTERPOLATION_LINEAR); his x[k] = tmax; his y[k++] = y; // thy samples for (long i = ie2; i >= ib2; i--) { double t = thy x1 + (i - 1) * thy dx; y = thy z[thy ny == 1 ? 1 : channel][i]; his x[k] = t; his y[k++] = CLIP_Y (y, ymin, ymax); } // thy end point at tmin y = Vector_getValueAtX (thee, tmin, (thy ny == 1 ? 1 : channel), Vector_VALUE_INTERPOLATION_LINEAR); his x[k] = tmin; his y[k] = y; Melder_assert (k == numberOfPoints); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no enclosed Polygon created."); } } #define INTERSECTION_OUTSIDE 0 #define INTERSECTION_PROPER 1 #define INTERSECTION_AT_EDGE 2 #define INTERSECTION_AT_VERTEX 3 #define INTERSECTION_COPLANAR 4 #define INTERSECTION_COPLANAR_AT_EDGE 6 #define INTERSECTION_COPLANAR_AT_VERTEX 7 // 12 is from subject 34 from clipping static int get_collinearIntersectionPoint (double x1, double x2, double x3, double x4, double *xs) { bool p3inb12 = (x1 < x3 and x3 <= x2) or (x1 > x3 and x3 >= x2); bool p4inb12 = (x1 < x4 and x4 <= x2) or (x1 > x4 and x4 >= x2); int intersection = INTERSECTION_AT_VERTEX; if (x1 < x2) { if (x3 < x4) { if (x2 < x3 || x4 < x1) { intersection = INTERSECTION_OUTSIDE; } else if (p3inb12) { // 4 can be inside or outside *xs = p4inb12 ? x4 : x2; } else if (p4inb12) { // 3 is outside *xs = x4; } else { // 3 and 4 outside 12 segment *xs = x2; intersection = INTERSECTION_AT_EDGE; } } else { // x4 < x3 if (x2 < x4 || x3 < x1) { intersection = INTERSECTION_OUTSIDE; } else if (p3inb12) { // 4 can be inside or outside *xs = x4; } else if (p4inb12) { // 3 outside *xs = x4; } else { *xs = x2; intersection = INTERSECTION_AT_EDGE; } } } else { // x2 < x1 if (x3 < x4) { if (x1 < x3 || x4 < x2) { intersection = INTERSECTION_OUTSIDE; } else if (p3inb12) { *xs = p4inb12 ? x4 : x3; } else if (p4inb12) { // 3 outside *xs = x4; } else { *xs = x2; intersection = INTERSECTION_AT_EDGE; } } else { // x4 < x3 if (x1 < x4 || x3 < x2) { intersection = INTERSECTION_OUTSIDE; } else if (p3inb12) { *xs = x3; } else if (p4inb12) { *xs = x4; } else { *xs = x3; } } } return intersection; } // Line from a to b : // (1) ab = (1-s)*a+s*b = a + s*(b-a) = a + s * b' // (2) cd = c+t*(d-c) = c + t * d' // where b' = b - a and d' = d - c. // at intersection: // (3) a + s * b' = c + t * d' // Cross (3) with d'; // cross (a, d') + s * cross (b', d') = cross (c, d') // s = cross (c - a, d') / cross (b', d') // Cross (3) with b' // cross (a, b') = cross (c, b') + t * cross (d', b') // t = cross (c - a, b') / cross (b', d') // if cross (b', b') then b' and d' are parallel // After Paul Rourke // Area of triangle a,b,c = ((bx-ax)(cy-ay) - (cx-ax)(by-ay)) / 2 #define POS(ax,ay,bx,by,cx,cy) (bx - ax) * (cy - ay) - (cx - ax) * (by-ay); // if POS(a,b,c) (> 0 ; <0, 0) then c is on (the left of; the right of; collinear with) the line segment (a,b) // Register the crossing of line a(1)b(2) with c(3)d(4), if the crossing is degenerate only register the tip. static int LineSegments_getIntersection (double x1, double y1, double x2, double y2, double x3, double y3, double x4, double y4, double *mua, double *mub, double eps) { // bounding box pre-selection double min12 = x1 < x2 ? x1 : x2; double max12 = x1 > x2 ? x1 : x2; double min34 = x3 < x4 ? x3 : x4; double max34 = x3 > x4 ? x3 : x4; if (max12 - min34 < -eps or max34 - min12 < -eps) { return INTERSECTION_OUTSIDE; // eps? } min12 = y1 < y2 ? y1 : y2; max12 = y1 > y2 ? y1 : y2; min34 = y3 < y4 ? y3 : y4; max34 = y3 > y4 ? y3 : y4; if (max12 - min34 < -eps or max34 - min12 < -eps) { return INTERSECTION_OUTSIDE; } double cad = (x3 - x1) * (y4 - y3) - (y3 - y1) * (x4 - x3); // cross (c - a, d') double cab = (x3 - x1) * (y2 - y1) - (y3 - y1) * (x2 - x1); // cross (c - a, b') double bd = (x2 - x1) * (y4 - y3) - (y2 - y1) * (x4 - x3); // cross (b', d') if (fabs (bd) > eps) { *mua = cad / bd; *mub = cab / bd; if (*mua <= eps or * mua > 1 + eps or * mub < eps or * mub > 1 + eps) { return INTERSECTION_OUTSIDE; } if (*mua > eps and *mua <= 1 - eps and *mub >= eps and * mub < 1 - eps) { // This occurs most of the cases (hopefully) return INTERSECTION_PROPER; } // Now eps < mua,mub <= 1+eps // and at least one of the mu's is near 1, // the other is in [eps,1] if (fabs (*mua - 1) < eps) { *mua = 1; } if (fabs (*mub - 1) < eps) { *mub = 1; } // is the intersection at an edge or at vertex if (*mua == 1) { // end of ab touches cd return *mub == 1 ? INTERSECTION_AT_VERTEX : INTERSECTION_AT_EDGE; } else { // ab crosses a vertex return INTERSECTION_AT_VERTEX; } } else { // ab and cd are parallel or coplanar if (fabs (cad) > eps and fabs (cab) > eps) { return INTERSECTION_OUTSIDE; } if (x1 == x2) { x1 = y1; x2 = y2; x3 = y3; x4 = y4; } double xs; int intersection = get_collinearIntersectionPoint (x1, x2, x3, x4, &xs); if (intersection != INTERSECTION_OUTSIDE) { *mua = fabs ( (xs - x1) / (x2 - x1)); *mub = fabs ( (xs - x3) / (x4 - x3)); intersection += INTERSECTION_COPLANAR; } return intersection; } } // Vertices: // first node has prev = 0, last node has next = 0; // entry marks the entrance of the OTHER polygon Thing_define (Vertex, Data) { // new data: public: double x, y, alpha; DLLNode neighbour; long poly_npoints, id; int intersect, entry; bool processed; // overridden methods: virtual void v_copy (Any data_to); }; Thing_implement (Vertex, Data, 0); void structVertex :: v_copy (thou) { thouart (Vertex); thy x = x; thy y = y; thy alpha = alpha; thy neighbour = neighbour; thy poly_npoints = poly_npoints; thy id = id; thy intersect = intersect; thy entry = entry; thy processed = processed; } Vertex Vertex_create (); Vertex Vertex_create () { try { autoVertex me = Thing_new (Vertex); return me.transfer(); } catch (MelderError) { Melder_throw ("Vertex not created."); } } Thing_define (Vertices, DLL) { // overridden methods: protected: static int s_compare (Any data1, Any data2); virtual Data_CompareFunction v_getCompareFunction () { return s_compare; } }; Thing_implement (Vertices, DLL, 0); #define VERTEX(n) ((Vertex) (n -> data)) int structVertices :: s_compare (I, thou) { iam (DLLNode); thouart (DLLNode); return VERTEX (me) -> alpha < VERTEX (thee) -> alpha ? -1 : VERTEX (me) -> alpha > VERTEX (thee) -> alpha ? 1 : 0; } Vertices Vertices_create (); Vertices Vertices_create () { try { Vertices me = Thing_new (Vertices); return me; } catch (MelderError) { Melder_throw ("Vertices not created."); } } void Vertices_addCopyBack (Vertices me, DLLNode n); void Vertices_addCopyBack (Vertices me, DLLNode n) { try { autoDLLNode nc = (DLLNode) Data_copy (n); DLL_addBack ( (DLL) me, nc.transfer()); } catch (MelderError) { Melder_throw (me, ": no copy added."); } } static bool pointsInsideInterval (double *x, long n, long istart, long iend, long *jstart, long *jend) { double xmax = x[istart], xmin = x[istart]; long imax = istart, imin = istart; long iendmod = iend > istart ? iend : iend + n; // circular for (long i = istart + 1; i <= iendmod; i++) { long index = (i - 1) % n + 1; // make it circular if (x[index] > xmax) { xmax = x[index]; imax = index; } else if (x[index] < xmin) { xmin = x[index]; imin = index; } } *jstart = imin; *jend = imax; if (x[istart] > x[iend]) { *jstart = imax; *jend = imin; } if (x[istart] == x[*jstart] and x[iend] == x[*jend]) { // if there are duplicates of the extrema *jstart = istart; *jend = iend; } return *jstart == istart and * jend == iend; } Polygon Polygon_circularPermutation (Polygon me, long nshift); Polygon Polygon_circularPermutation (Polygon me, long nshift) { try { autoPolygon thee = Data_copy (me); if (nshift != 0) { for (long i = 1; i <= my numberOfPoints; i++) { long inew = (i + nshift - 1) % my numberOfPoints + 1; thy x[inew] = my x[i]; thy y[inew] = my y[i]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not circularly permuted."); } } void _Polygons_copyNonCollinearities (Polygon me, Polygon thee, long collstart, long collend); void _Polygons_copyNonCollinearities (Polygon me, Polygon thee, long collstart, long collend) { // Determine if all collinear point are within the interval [colstart,colend] long jstart, jend; bool allPointsInside = my x[collstart] != my x[collend] ? pointsInsideInterval (my x, my numberOfPoints, collstart, collend, &jstart, &jend) : pointsInsideInterval (my y, my numberOfPoints, collstart, collend, &jstart, &jend); if (not allPointsInside) { if (collstart != jstart) { // also include the extreme point at start thy numberOfPoints++; thy x[thy numberOfPoints] = my x[jstart]; thy y[thy numberOfPoints] = my y[jstart]; } if (collend != jend) { // also include the extreme point at end thy numberOfPoints++; thy x[thy numberOfPoints] = my x[jend]; thy y[thy numberOfPoints] = my y[jend]; } } thy numberOfPoints++; thy x[thy numberOfPoints] = my x[collend]; thy y[thy numberOfPoints] = my y[collend]; } #define AREA(x1,y1,x2,y2,x3,y3) (x1*(y2 - y3)+x2*(y3-y1)+x3*(y1-y2)) Polygon Polygon_simplify (Polygon me); Polygon Polygon_simplify (Polygon me) { try { autoPolygon p1 = Data_copy (me); // pass 1: remove doublets long np = 1; for (long i = 2; i <= my numberOfPoints; i++) { if (my x[i] != p1 -> x[np] || my y[i] != p1 -> y[np]) { p1 -> x[++np] = my x[i]; p1 -> y[np] = my y[i]; } } // last and first points! if (p1 -> x[np] == p1 -> x[1] && p1 -> y[np] == p1 -> y[1]) { np--; } if (np < 3) { Melder_throw ("Not enough points left after doublet removal."); } p1 -> numberOfPoints = np; // pass 2: remove collinearities autoPolygon p = Data_copy (p1.peek()); p -> numberOfPoints = 0; // is there collinearity between the first and the last points of p1? double eps = 1e-15; double area = AREA (p1 -> x[np], p1 -> y[np], p1 -> x[1], p1 -> y[1], p1 -> x[2], p1 -> y[2]); long collend = 2; while (fabs (area) < eps && collend < np) { collend++; area = AREA (p1 -> x[collend - 2], p1 -> y[collend - 2], p1 -> x[collend - 1], p1 -> y[collend - 1], p1 -> x[collend], p1 -> y[collend]); } collend--; area = AREA (p1 -> x[np - 1], p1 -> y[np - 1], p1 -> x[np], p1 -> y[np], p1 -> x[1], p1 -> y[1]); long collstart = np - 1; while (fabs (area) < eps && collstart > collend) { collstart--; area = AREA (p1 -> x[collstart], p1 -> y[collstart], p1 -> x[collstart + 1], p1 -> y[collstart + 1], p1 -> x[collstart + 2], p1 -> y[collstart + 2]); } collstart++; if (collend - collstart + p1 -> numberOfPoints > 1) { _Polygons_copyNonCollinearities (p1.peek(), p.peek(), collstart, collend); } else { p -> numberOfPoints = 1; p -> x[1] = p1 -> x[1]; p -> y[1] = p1 -> y[1]; } bool collinearity = false; long endpos = collstart - 1; for (long i = collend + 1; i <= endpos; i++) { // start was < numberOfPoints // if i-1, i, i+1 are coplanar, remove i // area = x1*(y2 - y3)+x2*(y3-y1)+x3*(y1-y2) area = AREA (p1 -> x[i - 1], p1 -> y[i - 1], p1 -> x[i], p1 -> y[i], p1 -> x[i + 1], p1 -> y[i + 1]); if (fabs (area) < eps) { if (collinearity) { collend = i + 1; } else { // start of possibly new series collinearity = true; collstart = i - 1; collend = i + 1; } if (i != endpos) { continue; } } if (not collinearity) { p -> numberOfPoints++; p -> x[p -> numberOfPoints] = p1 -> x[i]; p -> y[p -> numberOfPoints] = p1 -> y[i]; } else { // end of series of collinearities detected _Polygons_copyNonCollinearities (p1.peek(), p.peek(), collstart, collend); collinearity = false; } } if (not collinearity and collend != endpos + 1) { // only if previous series was not collinear p -> numberOfPoints++; p -> x[p -> numberOfPoints] = p1 -> x[endpos + 1]; p -> y[p -> numberOfPoints] = p1 -> y[endpos + 1]; } if (p -> numberOfPoints < 3) { Melder_throw ("Not enough points left after collinear points removal."); } autoPolygon thee = Data_copy (p.peek()); // return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not simplified."); } } #undef AREA Vertices Polygon_to_Vertices (Polygon me, bool close); Vertices Polygon_to_Vertices (Polygon me, bool close) { try { autoVertices thee = Vertices_create (); for (long i = 1 ; i <= my numberOfPoints; i++) { autoVertex v = Vertex_create (); v -> x = my x[i]; v -> y = my y[i]; autoDLLNode n = DLLNode_create ( (Data) v.transfer()); DLL_addBack ( (DLL) thee.peek(), n.transfer()); } Melder_assert (thy numberOfNodes == my numberOfPoints); if (close) { Vertices_addCopyBack (thee.peek(), thy front); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Vertices created."); } } #define SKIP_INTERSECTION_NODES(n) while(VERTEX(n) -> intersect != 0) n = n -> next; void Vertices_print (Vertices me, Vertices thee); void Vertices_print (Vertices me, Vertices thee) { long ns = 0, nc = 0, nt, nt2; // MelderInfo_open(); DLLNode n = my front; MelderInfo_writeLine1 (L""); while (n != 0) { double x = VERTEX (n) -> x, y = VERTEX (n) -> y, alpha = VERTEX (n) -> alpha; const wchar_t *type = 0, *itype; if (VERTEX (n) -> intersect == 0) { type = L"S"; ns++; nt = ns; itype = L"-"; nt2 = 0; } else { type = L"I"; nt = VERTEX (n) -> id; nt2 = VERTEX (VERTEX (n) -> neighbour) -> id; itype = Melder_integer (VERTEX (n) -> intersect); } MelderInfo_write9 (type, Melder_integer (nt), L" I", itype, L", (", Melder_double (x), L", ", Melder_double (y), L"), "); MelderInfo_write6 (Melder_double (alpha), L", E", Melder_integer (VERTEX (n) -> entry), L"(", Melder_integer (nt2), L")\n"); n = n -> next; } MelderInfo_writeLine1 (L""); n = thy front; while (n != 0) { double x = VERTEX (n) -> x, y = VERTEX (n) -> y, alpha = VERTEX (n) -> alpha; const wchar_t *type = 0, *itype; if (VERTEX (n) -> intersect == 0) { type = L"C"; nc++; nt = nc; itype = L"-"; nt2 = 0; } else { type = L"I"; nt = VERTEX (n) -> id; nt2 = VERTEX (VERTEX (n) -> neighbour) -> id; itype = Melder_integer (VERTEX (n) -> intersect); } MelderInfo_write9 (type, Melder_integer (nt), L" I", itype, L", (", Melder_double (x), L", ", Melder_double (y), L"), "); MelderInfo_write6 (Melder_double (alpha), L", E", Melder_integer (VERTEX (n) -> entry), L"(", Melder_integer (nt2), L")\n"); n = n -> next; } // MelderInfo_close(); } void Vertices_sortIntersections (Vertices me); void Vertices_sortIntersections (Vertices me) { DLLNode ni = my front, first; bool intersections = false; while (ni != my back) { if (VERTEX (ni) -> intersect == 0) { if (intersections) { // the previous was the last of a series of intersections DLL_sortPart ( (DLL) me, first, ni -> prev); // restore myNode pointers intersections = false; } } else { if (not intersections) { first = ni; intersections = true; } } ni = ni -> next; } // we might have missed the last series of intersections if (intersections) { DLL_sortPart ( (DLL) me, first, ni -> prev); } } void Vertices_addIntersections (Vertices me, Vertices thee); void Vertices_addIntersections (Vertices me, Vertices thee) { try { double eps = 1e-15; long id = 0; if (my numberOfNodes < 4 || thy numberOfNodes < 4) { Melder_throw ("We need at least three vertices."); } DLLNode ni = my front; // the node index in me (s) while (ni != my back) { // until penultimate double x1 = VERTEX (ni) -> x, y1 = VERTEX (ni) -> y; double x2 = VERTEX (ni -> next) -> x, y2 = VERTEX (ni -> next) -> y; DLLNode nj = thy front; // the current node index in thee (c) while (nj != thy back && VERTEX (nj) -> intersect == 0) { DLLNode njn = nj -> next; SKIP_INTERSECTION_NODES (njn) double x3 = VERTEX (nj) -> x, y3 = VERTEX (nj) -> y; double x4 = VERTEX (njn) -> x, y4 = VERTEX (njn) -> y, mua, mub; int intersection = LineSegments_getIntersection (x1, y1, x2, y2, x3, y3, x4, y4, &mua, &mub, eps); if (intersection != INTERSECTION_OUTSIDE) { id++; // 1. create the vertices autoVertex ins = Vertex_create (); ins -> x = x1 + mua * (x2 - x1); ins -> y = y1 + mua * (y2 - y1); ins -> alpha = mua; ins -> intersect = intersection; ins -> id = id; autoVertex inc = Data_copy (ins.peek()); inc -> alpha = mub; // 2. create the nodes autoDLLNode ns = DLLNode_create (0); autoDLLNode nc = DLLNode_create (0); // 3. link the neighbours + copy the links DLLNode njc = ins -> neighbour = nc.peek(); DLLNode nic = inc -> neighbour = ns.peek(); // 4. transfer the vertices to the nodes ns -> data = (Data) ins.transfer(); nc -> data = (Data) inc.transfer(); // 5. add the nodes to the list DLL_addAfter ( (DLL) me, ni, ns.transfer()); DLL_addAfter ( (DLL) thee, nj, nc.transfer()); // 6. set node pointer to inserted nodes ni = nic; nj = njc; } nj = nj -> next; SKIP_INTERSECTION_NODES (nj) } ni = ni -> next; } if (Melder_debug == -1) { MelderInfo_open(); Vertices_print (me, thee); } Vertices_sortIntersections (me); Vertices_sortIntersections (thee); if (Melder_debug == -1) { Vertices_print (me, thee); } } catch (MelderError) { Melder_throw ("Intersections not calculated."); } } #define Polygon_EN 1 #define Polygon_EX 2 #define Polygon_ENEX 3 #define Polygon_EXEN 4 void Vertices_markEntryPoints (Vertices me, int firstLocation); void Vertices_markEntryPoints (Vertices me, int firstLocation) { int entry = (firstLocation == Polygon_INSIDE) ? Polygon_EX : (firstLocation == Polygon_OUTSIDE) ? Polygon_EN : Polygon_ENEX; // problematic when on boundary // my back/front can never be an intersection node for (DLLNode ni = my front -> next; ni != my back; ni = ni -> next) { if (VERTEX (ni) -> intersect == 0) { continue; } VERTEX (ni) -> entry = entry; entry = (entry == Polygon_EN) ? Polygon_EX : (entry == Polygon_EX) ? Polygon_EN : Polygon_ENEX; } } Vertices Verticeses_connectClippingPathsUnion (Vertices me, Vertices thee); Vertices Verticeses_connectClippingPathsUnion (Vertices me, Vertices thee) { try { // find my first vertex outside thee, by searching the first intersection entry DLLNode firstOutside = my front; bool firstOutsideSet = true; for (DLLNode ni = my front; ni != 0; ni = ni -> next) { if (VERTEX (ni) -> intersect == 0) { // if (firstOutsideSet) { continue; } firstOutside = ni; break; } else if (VERTEX (ni) -> entry == Polygon_EN) { break; } // We were inside else { firstOutsideSet = false; } } autoVertices him = Vertices_create (); long poly_npoints = 0; DLLNode current = firstOutside; bool inside = false, forward = true; do { if (VERTEX (current) -> intersect == 0) { Vertices_addCopyBack (him.peek(), current); poly_npoints++; } else { // intersection point // store and jump to other polygon Vertices_addCopyBack (him.peek(), current); poly_npoints++; current = VERTEX (current) -> neighbour; inside = not inside; forward = VERTEX (current) -> entry == Polygon_EX; } if (forward) { current = current -> next; if (current == 0) { current = inside ? thy front : my front; } } else { current = current -> prev; if (current == 0) { current = inside ? thy back : my back; } } } while (current != firstOutside and current != 0 and poly_npoints < my numberOfNodes); VERTEX (his front) -> poly_npoints = poly_npoints; return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no clipping path."); } } Vertices Verticeses_connectClippingPaths (Vertices me, bool use_myinterior, Vertices thee, bool use_thyinterior); Vertices Verticeses_connectClippingPaths (Vertices me, bool use_myinterior, Vertices thee, bool use_thyinterior) { try { autoVertices him = Vertices_create (); DLLNode prevPoly; long poly_npoints = 0; for (DLLNode ni = my front; ni != 0; ni = ni -> next) { if ( (VERTEX (ni) -> intersect == 0) || VERTEX (ni) -> processed) { continue; } // Intersection found: start new polygon DLLNode currentPoly = his back; if (currentPoly == his front) { Vertices_addCopyBack (him.peek(), ni); poly_npoints++; prevPoly = his front; } else { Vertices_addCopyBack (him.peek(), ni); poly_npoints++; VERTEX (prevPoly) -> poly_npoints = poly_npoints; poly_npoints = 0; prevPoly = currentPoly; } DLLNode current = ni; VERTEX (current) -> processed = true; long jumps = 0; do { if (VERTEX (current) -> entry == Polygon_EN) { while ( (current = current -> next) != 0 and VERTEX (current) -> intersect == 0) { Vertices_addCopyBack (him.peek(), current); poly_npoints++; } if (current == 0) { // back of list? Goto front current = (jumps % 2 == 0) ? my front : thy front; while ( (current = current -> next) != 0 and VERTEX (current) -> intersect == 0) { Vertices_addCopyBack (him.peek(), current); poly_npoints++; } Vertices_addCopyBack (him.peek(), current); poly_npoints++; // intersection point } else if (current == ni) { break; // done } else { current = current -> prev; } } else if (VERTEX (current) -> entry == Polygon_EX) { while ( (current = current -> prev) != 0 and VERTEX (current) -> intersect == 0) { Vertices_addCopyBack (him.peek(), current); poly_npoints++; } if (current == 0) { // start of list? Goto end current = (jumps % 2 == 0) ? my back : thy back; while ( (current = current -> prev) != 0 and VERTEX (current) -> intersect == 0) { Vertices_addCopyBack (him.peek(), current); poly_npoints++; } Vertices_addCopyBack (him.peek(), current); poly_npoints++; // intersection point } else if (current == ni) { break; // done } else { current = current -> next; } } else { } VERTEX (current) -> processed = true; current = VERTEX (current) -> neighbour; jumps++; VERTEX (current) -> processed = true; } while (current != ni); // polygon closed } // last polygon: VERTEX (prevPoly) -> poly_npoints = poly_npoints; return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no clipping vertices created."); } } // Polygon Vertices_to_Polygon (Vertices me, DLLNode *ni); Polygon Vertices_to_Polygon (Vertices me, DLLNode *ni) { DLLNode n = *ni; try { long i = 1, nPoints = VERTEX (n) -> poly_npoints; if (nPoints == 0) { Melder_throw ("No number info."); } autoPolygon thee = Polygon_create (nPoints); thy x[i] = VERTEX (n) -> x; thy y[i] = VERTEX (n) -> y; while ( (n = n -> next) != 0 and VERTEX (n) -> poly_npoints == 0 and i <= nPoints) { i++; thy x[i] = VERTEX (n) -> x; thy y[i] = VERTEX (n) -> y; } *ni = n; return thee.transfer(); } catch (MelderError) { Melder_throw ("Polygon not created."); } } Collection Vertices_to_Polygons (Vertices me); Collection Vertices_to_Polygons (Vertices me) { try { autoCollection thee = Collection_create (classPolygon, 10); DLLNode ni = my front; do { autoPolygon p = Vertices_to_Polygon (me, & ni); Collection_addItem (thee.peek(), p.transfer()); } while (ni != 0); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no polygon collection created."); } } Collection Polygons_findClippings (Polygon me, bool use_myinterior, Polygon thee, bool use_thyinterior); Collection Polygons_findClippings (Polygon me, bool use_myinterior, Polygon thee, bool use_thyinterior) { try { autoVertices s = Polygon_to_Vertices (me, true); // subject long ns = s -> numberOfNodes; autoVertices c = Polygon_to_Vertices (thee, true); // clip long nc = c -> numberOfNodes; double eps = 1e-15; // phase 1: Get all intersections and add them to both lists Vertices_addIntersections (s.peek(), c.peek()); long nnewnodes = s -> numberOfNodes - ns; int firstLocation = Polygon_getLocationOfPoint (thee, my x[1], my y[1], eps); if (nnewnodes == 0) { // no crossings, either one completely inside the other or separate autoCollection apc; if (not use_myinterior and not use_thyinterior and firstLocation == Polygon_INSIDE) { autoPolygon ap = Data_copy (thee); Collection_addItem (apc.peek(), ap.transfer()); } else { autoPolygon ap = Data_copy (me); Collection_addItem (apc.peek(), ap.transfer()); } return apc.transfer(); } // phase 2: Determine intersections as entry / exit points Vertices_markEntryPoints (s.peek(), firstLocation); firstLocation = Polygon_getLocationOfPoint (me, thy x[1], thy y[1], eps); Vertices_markEntryPoints (c.peek(), firstLocation); if (Melder_debug == -1) { Vertices_print (s.peek(), c.peek()); MelderInfo_close(); Melder_throw ("Bail out of Polygons_findClippings."); } // phase 3: Determine the clipping paths // use_myinterior use_thyinterior result // true false diff me - thee // false false union // true true clip // false true diff thee - me autoVertices pgs = 0; if (not use_myinterior and not use_thyinterior) { pgs.reset (Verticeses_connectClippingPathsUnion (s.peek(), c.peek())); } else { pgs.reset (Verticeses_connectClippingPaths (s.peek(), use_myinterior, c.peek(), use_thyinterior)); } // phase 4: to Polygons autoCollection pols = Vertices_to_Polygons (pgs.peek()); return pols.transfer(); } catch (MelderError) { Melder_throw (me, ": no union Polygon created."); } } Collection Polygons_clip (Polygon subject, Polygon clipper) { try { autoCollection him = Polygons_findClippings (subject, true, clipper, true); return him.transfer(); } catch (MelderError) { Melder_throw (subject, ": no union created."); } } Polygon Polygons_union (Polygon me, Polygon thee); Polygon Polygons_union (Polygon me, Polygon thee) { try { autoCollection him = Polygons_findClippings (me, false, thee, false); //Melder_assert (his size == 1); autoPolygon p = (Polygon) Collection_subtractItem (him.peek(), 1); Collection_dontOwnItems (him.peek()); return p.transfer(); } catch (MelderError) { Melder_throw (me, ": no union created."); } } #define CROSSING (my y[i] < y0) != (my y[ip1] < y0) #define AREA { a = (my x[i]-x0)*(my y[ip1]-y0) - (my x[ip1]-x0)*(my y[i]-y0); if (fabs (a) <= eps) return Polygon_EDGE; } #define RIGHT_CROSSING (a > 0) == (my y[ip1] > my y[i]) #define MODIFY_CROSSING_NUMBER { if (my y[ip1] > my y[i]) nup++; else nup--; } int Polygon_getLocationOfPoint (Polygon me, double x0, double y0, double eps); int Polygon_getLocationOfPoint (Polygon me, double x0, double y0, double eps) { if (my y[1] == y0 and my x[1] == x0) { return Polygon_VERTEX; } long nup = 0; for (long i = 1; i <= my numberOfPoints; i++) { double a; long ip1 = i < my numberOfPoints ? i + 1 : 1; if (my y[ip1] == y0) { if (my x[ip1] == x0) { return Polygon_VERTEX; } else if (my y[i] == y0 and (my x[ip1] > x0) == (my x[i] < x0)) { return Polygon_EDGE; } } if (CROSSING) { if (my x[i] >= x0) { if (my x[ip1] > x0) MODIFY_CROSSING_NUMBER else { AREA if (RIGHT_CROSSING) MODIFY_CROSSING_NUMBER } } else { if (my x[ip1] > x0) { AREA if (RIGHT_CROSSING) MODIFY_CROSSING_NUMBER } } } } return nup % 2 == 0 ? Polygon_OUTSIDE : Polygon_INSIDE; } /* End of file Polygon_extensions.cpp */ sources_5316/dwtools/Makefile0000664000176700017670000000403311737613653015074 0ustar paulpaul# Makefile of the library "dwtools" # David Weenink, 22 February 2010 # djmw 20120221 Latest modification include ../makefile.defs CPPFLAGS = -I ../num -I ../LPC -I ../fon -I ../sys -I ../stat -I ../dwsys -I ../external/portaudio -I ../external/espeak OBJECTS = Activation.o AffineTransform.o \ Categories.o CategoriesEditor.o \ Categories_and_Strings.o CCA.o CCA_and_Correlation.o \ CC.o CCs_to_DTW.o \ ClassificationTable.o Confusion.o \ Configuration.o ContingencyTable.o \ Configuration_AffineTransform.o \ Configuration_and_Procrustes.o Distance.o \ DTW.o DTW_and_TextGrid.o \ Discriminant.o Discriminant_Pattern_Categories.o \ EditDistanceTable.o \ Eigen_and_Matrix.o Eigen_and_Procrustes.o \ Eigen_and_TableOfReal.o\ Eigen_and_SSCP.o Excitations.o \ FilterBank.o FormantGrid_extensions.o \ GaussianMixture.o \ HMM.o \ ICA.o Intensity_extensions.o \ LFCC.o LongSound_extensions.o \ KlattGrid.o KlattGridEditors.o KlattTable.o \ MelFilter_and_MFCC.o MFCC.o \ manual_dwtools.o manual_BSS.o manual_HMM.o manual_KlattGrid.o manual_MDS.o manual_Permutation.o \ Minimizers.o \ Matrix_extensions.o \ Matrix_Categories.o MDS.o \ Pattern.o PCA.o \ Pitch_extensions.o Polynomial.o \ Polygon_extensions.o Procrustes.o \ Proximity.o \ Resonator.o \ Sampled2.o \ Sound_and_FilterBank.o Sound_extensions.o \ Sound_to_MFCC.o Sounds_to_DTW.o \ Sound_to_Pitch2.o Sound_to_SPINET.o SPINET.o SPINET_to_Pitch.o \ Spectrum_extensions.o SSCP.o Strings_extensions.o \ SpeechSynthesizer.o SpeechSynthesizer_and_TextGrid.o\ Table_extensions.o TableOfReal_and_SVD.o\ TableOfReal_extensions.o \ TableOfReal_and_Permutation.o \ TextGrid_extensions.o \ VowelEditor.o \ praat_MDS_init.o praat_BSS_init.o praat_HMM_init.o praat_KlattGrid_init.o praat_David_init.o .PHONY: all clean all: libdwtools.a clean: $(RM) $(OBJECTS) $(RM) libdwtools.a libdwtools.a: $(OBJECTS) touch libdwtools.a rm libdwtools.a ar cq libdwtools.a $(OBJECTS) $(RANLIB) libdwtools.a $(OBJECTS): *.h ../num/NUM.h ../sys/*.h ../fon/*.h ../dwsys/*.h ../stat/*.h ../LPC/*.h sources_5316/dwtools/Categories.h0000644000176700017670000000314011630404722015651 0ustar paulpaul#ifndef _Categories_h_ #define _Categories_h_ /* Categories.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection_extensions.h" #include "Simple_extensions.h" #include "TableOfReal.h" #include "Graphics.h" Thing_define (Categories, OrderedOfString) { // overridden methods: public: virtual void v_readText (MelderReadText text); virtual void v_writeText (MelderFile file); }; void Categories_init (Categories me, long size); Categories Categories_create (); Categories Categories_sequentialNumbers (long n); Categories Categories_selectUniqueItems (Categories me, int sorted); void Categories_drawItem (Categories me, Graphics g, long position, double xWC, double yWC); Categories OrderedOfString_to_Categories (I); long Categories_getSize (Categories me); /* return my size */ Categories TableOfReal_to_CategoriesRow (I); Categories TableOfReal_to_CategoriesColumn (I); #endif /* _Categories_h_ */ sources_5316/dwtools/Intensity_extensions.h0000644000176700017670000000333011607123040020025 0ustar paulpaul#ifndef _Intensity_extensions_h_ #define _Intensity_extensions_h_ /* Intensity_extensions.h * * Copyright (C) 2006-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20061204 Initial version djmw 20110307 Latewst modification */ #include "Sound.h" #include "Intensity.h" #include "TextGrid.h" #ifdef __cplusplus extern "C" { #endif TextGrid Intensity_to_TextGrid_detectSilences (Intensity me, double silenceThreshold_dB, double minSilenceDuration, double minSoundingDuration, const wchar_t *silenceLabel, const wchar_t *soundingLabel); /* Marks "silence" intervals in a sound as intervals in a TextGrid. silenceThreshold_dB: silence-to-speech and speech-to-silence threshold as dB's below maximum intensity We have speech if: local_intensity >= max_intensity - silenceThreshold. Silence if: local_intensity < max_intensity - silenceThreshold. If minSilenceDuration > 0 then only intervals with a duration > minSilenceDuration will be labelled as silences in the IntervalTier. */ #ifdef __cplusplus } #endif #endif /* _Intensity_extensions_h_ */ sources_5316/dwtools/Categories_and_Strings.h0000644000176700017670000000222111607121356020206 0ustar paulpaul#ifndef _Categories_and_Strings_h_ #define _Categories_and_Strings_h_ /* Categories_and_Strings.h * * Copyright (C) 2001-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020315 GPL header djmw 20110305 Latest modification */ #include "Categories.h" #include "Strings.h" #ifdef __cplusplus extern "C" { #endif Strings Categories_to_Strings (Categories me); Categories Strings_to_Categories (Strings me); #ifdef __cplusplus } #endif #endif /* _Categories_and_Strings_h_ */ sources_5316/dwtools/CCA.h0000644000176700017670000000743611627172415014175 0ustar paulpaul#ifndef _CCA_h_ #define _CCA_h_ /* CCA.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020423 GPL header djmw 20110306 Latest modification. */ #include "Eigen.h" #include "TableOfReal.h" #include "Strings.h" #include "CCA_def.h" oo_CLASS_CREATE (CCA, Data); /* Class CCA represents the Canonical Correlation Analysis of two datasets (two tables with multivariate data, Table 1 was N rows x p columns, Table 2 was N rows x q columns, and p <= q). Interpretation: The eigenvectors v1[i] en v2[i] have the property that for the linear compounds c1[1] = v1[1]' . Table1 c2[1]= v2[1]' . Table2 .............................................. c1[p] = v1[p]' . Table1 c2[p]= v2[p]' . Table2 the sample correlation of c1[1] and c2[1] is greatest, the sample correlation of c1[2] and c2[2] is greatest amoung all linear compounds uncorrelated with c1[1] and c2[1], and so on, for all p possible pairs. */ CCA CCA_create (long numberOfCoefficients, long ny, long nx); void CCA_drawEigenvector (CCA me, Graphics g, int x_or_y, long ivec, long first, long last, double ymin, double ymax, int weigh, double size_mm, const wchar_t *mark, int connect, int garnish); double CCA_getEigenvectorElement (CCA me, int x_or_y, long ivec, long element); CCA TableOfReal_to_CCA (TableOfReal me, long ny); /* Solves the canonical correlation analysis equations: (S12*inv(S22)*S12' - lambda S11)X1 = 0 (1) (S12'*inv(S11)*S12 - lambda S22)X2 = 0 (2) Where S12 = T1' * T2, S11 = T1' * T1 and S22 = T2' * T2. Given the following svd's: svd (T1) = U1 D1 V1' svd (T2) = U2 D2 V2' We can write down: inv(S11) = V1 * D1^-2 * V1' and inv(S22) = V2 * D2^-2 * V2', and S12*inv(S22)*S12' simplifies to: V1*D1*U1'*U2 * U2'*U1*D1*V1' and (1) becomes: (V1*D1*U1'*U2 * U2'*U1*D1*V1' -lambda V1*D1 * D1*V1')X1 = 0 This can be written as: (V1*D1*U1'*U2 * U2'*U1 -lambda V1*D1) D1*V1'*X1 = 0 multiplying from the left with: D1^-1*V1' results in (U1'*U2 * U2'*U1 -lambda) D1*V1'*X1 = 0 Taking the svd(U2'*U1) = U D V' we get: (D^2 -lambda)V'*D1*V1'*X1 = 0 The eigenvectors X1 can be formally written as: X1 = V1*inv(D1)*V Equation (2) results in: X2 = V2*inv(D2)*U */ TableOfReal CCA_and_TableOfReal_scores (CCA me, TableOfReal thee, long numberOfFactors); /* Return the factors in a table with 2*numberOfFactors columns. The first 'numberOfFactors' columns are the scores for the dependent part of the table the following 'numberOfFactors' columns are for the independent part. */ TableOfReal CCA_and_TableOfReal_factorLoadings (CCA me, TableOfReal thee); /* Get the canonical factor loadings (also structure correlation coefficients), the correlation of a canonical variable with an original variable. */ double CCA_getCorrelationCoefficient (CCA me, long index); void CCA_getZeroCorrelationProbability (CCA me, long index, double *chisq, long *ndf, double *probability); TableOfReal CCA_and_TableOfReal_predict (CCA me, TableOfReal thee, long from); /* Given independent table, predict the dependent one, on the basis of the canonical correlations. */ #endif /* CCA.h */ sources_5316/dwtools/Polynomial_def.h0000644000176700017670000000335211627247753016551 0ustar paulpaul/* Polynomial_def.h * * Copyright (C) 1993-2002 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 1999 djmw 20020813 GPL header */ #define ooSTRUCT FunctionTerms oo_DEFINE_CLASS (FunctionTerms, Function) oo_LONG (numberOfCoefficients) oo_DOUBLE_VECTOR (coefficients, numberOfCoefficients) #if oo_DECLARING // new methods: virtual double v_evaluate (double x); virtual void v_evaluate_z (dcomplex *z, dcomplex *p); virtual void v_evaluateTerms (double x, double terms[]); virtual void v_getExtrema (double x1, double x2, double *xmin, double *ymin, double *xmax, double *ymax); virtual long v_getDegree (); #endif oo_END_CLASS (FunctionTerms) #undef ooSTRUCT #define ooSTRUCT Spline oo_DEFINE_CLASS (Spline, FunctionTerms) oo_LONG (degree) oo_LONG (numberOfKnots) oo_DOUBLE_VECTOR (knots, numberOfKnots) #if oo_DECLARING // overridden methods: virtual double v_evaluate (double x); virtual long v_getDegree (); // new methods: virtual long v_getOrder (); #endif oo_END_CLASS (Spline) #undef ooSTRUCT /* End of file Polynomial_def.h */ sources_5316/dwtools/Sound_to_Pitch2.h0000644000176700017670000000267211535130316016577 0ustar paulpaul#ifndef _Sound_to_Pitch2_h_ #define _Sound_to_Pitch2_h_ /* Sound_to_Pitch2.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19970410 djmw 20020813 GPL header djmw 20110307 Latest modification */ #include "Sound_extensions.h" #include "Pitch.h" #ifdef __cplusplus extern "C" { #endif Pitch Sound_to_Pitch_shs (Sound me, double timeStep, double minimumPitch, double maximumFrequency, double ceiling, long maxnSubharmonics, long maxnCandidates, double compressionFactor, long nDivisionsPerOctave); Pitch Sound_to_Pitch_SPINET (Sound me, double timeStep, double windowDuration, double minimumFrequencyHz, double maximumFrequencyHz, long nFilters, double ceiling, int maxnCandidates); #ifdef __cplusplus } #endif #endif /* _Sound_to_Pitch2_h_ */ sources_5316/dwtools/MDS.h0000644000176700017670000005146411630403764014230 0ustar paulpaul#ifndef _MDS_h_ #define _MDS_h_ /* MDS.h * * Multi Dimensional Scaling * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110306 Latest modification. */ #define KRUSKAL_MAXDIMENSION 10 /* process */ #define MDS_DISCRETE 0 #define MDS_CONTINUOUS 1 /* measurement conditionality */ #define MDS_UNCONDITIONAL 0 #define MDS_MATRIXCONDITIONAL 1 #define MDS_ROWCONDITIONAL 2 /* analysis level */ #define MDS_ABSOLUTE 0 #define MDS_RATIO 1 #define MDS_INTERVAL 2 #define MDS_SPLINE 3 #define MDS_ORDINAL 4 #define MDS_NOMINAL 5 /* normalization */ #define CONFIGURATION_COLUMNS 1 #define CONFIGURATION_MATRIX 2 /* ties processing */ #define MDS_PRIMARY_APPROACH 1 #define MDS_SECONDARY_APPROACH 2 /* stress */ #define MDS_NORMALIZED_STRESS 1 #define MDS_STRESS_1 2 #define MDS_STRESS_2 3 #define MDS_RAW_STRESS 4 #define MDS_MSPLINE 1 #define MDS_ISPLINE 2 #include "Graphics.h" #include "Minimizers.h" #include "Confusion.h" #include "ContingencyTable.h" #include "TableOfReal_extensions.h" #include "Proximity.h" #include "Distance.h" #include "Configuration.h" #include "SSCP.h" /************************** class Weight **************************************/ Thing_define (Weight, TableOfReal) { }; Weight Weight_create (long numberOfPoints); /************************** class Salience **************************************/ Thing_define (Salience, TableOfReal) { }; Salience Salience_create (long numberOfSources, long numberOfDimensions); void Salience_setDefaults (Salience me); long Salience_correctNegatives (Salience me); void Salience_draw (Salience me, Graphics g, int xdimension, int ydimension, int garnish); /************************** class MDSVec ******************************/ Thing_define (MDSVec, Data) { // new data: public: long nProximities, nPoints; double *proximity; long *iPoint, *jPoint; // overridden methods: protected: virtual void v_destroy (); }; MDSVec MDSVec_create (long nObjects); /************** class MDSVecs *********************************/ Thing_define (MDSVecs, Ordered) { }; MDSVecs MDSVecs_create (); Configuration ContingencyTable_to_Configuration_ca (ContingencyTable me, long numberOfDimensions, int scaling); /********************* class Proximities *******************************/ Thing_define (Proximities, TablesOfReal) { }; void Proximities_init (I, ClassInfo klas); Proximities Proximities_create (); /****************** class Confusions **********************************/ Thing_define (Confusions, Proximities) { }; Confusions Confusions_create (); Confusion Confusions_sum (Confusions me); /************* class Distances **************************************/ Thing_define (Distances, Proximities) { }; Distances Distances_create (); /**************** class ScalarProduct **************************************/ Thing_define (ScalarProduct, TableOfReal) { }; ScalarProduct ScalarProduct_create (long numberOfPoints); /************** class ScalarProducts ********************************/ Thing_define (ScalarProducts, TablesOfReal) { }; ScalarProducts ScalarProducts_create (); /************* class Dissimilarity *********************************/ Thing_define (Dissimilarity, Proximity) { }; Dissimilarity Dissimilarity_create (long numberOfPoints); int Dissimilarity_getAdditiveConstant (I, double *c); /* Get the best estimate for the additive constant: "distance = dissimilarity + constant" F. Cailliez (1983), The analytical solution of the additive constant problem, Psychometrika 48, 305-308. */ /****************** class Transformator *******************************/ Thing_define (Transformator, Thing) { // new data: public: long numberOfPoints; int normalization; // new methods: virtual Distance v_transform (MDSVec vec, Distance dist, Weight w); }; void Transformator_init (I, long numberOfPoints); Transformator Transformator_create (long numberOfPoints); void Transformator_setNormalization (I, int normalization); Distance Transformator_transform (I, MDSVec vec, Distance dist, Weight w); Thing_define (ISplineTransformator, Transformator) { // new data: public: long numberOfInteriorKnots, order, numberOfParameters; double **m, *b, *knot; // overridden methods: virtual void v_destroy (); virtual Distance v_transform (MDSVec vec, Distance dist, Weight w); }; ISplineTransformator ISplineTransformator_create (long numberOfPoints, long numberOfInteriorKnots, long order); Thing_define (RatioTransformator, Transformator) { // new data: public: double ratio; // overridden methods: virtual Distance v_transform (MDSVec vec, Distance dist, Weight w); }; RatioTransformator RatioTransformator_create (long numberOfPoints); Thing_define (MonotoneTransformator, Transformator) { // new data: public: int tiesProcessing; // overridden methods: virtual Distance v_transform (MDSVec vec, Distance dist, Weight w); }; MonotoneTransformator MonotoneTransformator_create (long numberPoints); void MonotoneTransformator_setTiesProcessing (MonotoneTransformator, int tiesProcessing); /*************** class Dissimilarities ****************************/ Thing_define (Dissimilarities, Proximities) { }; Dissimilarities Dissimilarities_create (); /**************** class Similarity *****************************/ Thing_define (Similarity, Proximity) { }; Similarity Similarity_create (long numberOfPoints); /************** KRUSKAL *********************************************/ Thing_define (Kruskal, Thing) { // new data: public: int process; int measurementLevel; int conditionality; Configuration configuration; Proximities proximities; int stress_formula; MDSVec vec; double **dx; Minimizer minimizer; // overridden methods: virtual void v_destroy (); }; Kruskal Kruskal_create (long numberOfpoints, long numberOfDimensions); double Dissimilarity_Configuration_Weight_Transformator_normalizedStress (Dissimilarity me, Configuration conf, Weight weight, Transformator t); double Distance_Weight_stress (Distance fit, Distance c, Weight w, int type); /* Calculates stress. type is one of (MDS_NORMALIZED_STRESS, MDS_STRESS_1, MDS_STRESS_2, MDS_RAW_STRESS) */ double Distance_Weight_congruenceCoefficient (Distance x, Distance y, Weight w); /* Congruence coefficient B&G page 350. */ void Distance_Weight_rawStressComponents (Distance fit, Distance conf, Weight weight, double *eta_fit, double *eta_conf, double *rho); /* Computes eta_fit = sum (iVector_scale djmw 20020516 GPL header djmw 20020523 Removed Sound_read/writeWAVAudioFile djmw 20030926 Sound_changeGender djmw 20040405 Renamed: Sound_overrideSamplingFrequency djmw 20041124 Changed call to Sound_to_Spectrum & Spectrum_to_Sound. djmw 20050620 Changed Pitch_HERTZ to Pitch_UNIT_HERTZ djmw 20050628 New and extended Sound_createShepardToneComplex that corrects incorrect amplitudes of tones in complex. (amplitudes were on linear instead of log scale) djmw 20060921 Added Sound_to_IntervalTier_detectSilence djmw 20061010 Removed crashing bug in Sound_to_IntervalTier_detectSilence. djmw 20061201 Interface change: removed minimumPitch parameter from Sound_and_Pitch_changeGender. djmw 20061214 Sound_and_Pitch_changeSpeaker removed warning. djmw 20070103 Sound interface changes djmw 20070129 Warning added in changeGender_old. djmw 20071022 Possible (bug?) correction in Sound_createShepardToneComplex djmw 20071030 Sound_preEmphasis: no pre-emphasis above the Nyquist frequency. djmw 20071202 Melder_warning djmw 20080122 float -> double djmw 20080320 +Sound_fade. djmw 20080530 +Sound_localAverage pb 20090926 Correction in Sound_and_Pitch_changeGender_old djmw 20091023 Added Sound_drawIntervals djmw 20091028 Sound_drawIntervals -> Sound_drawParts + Graphics_function djmw 20091126 Sound_drawParts -> Sound_drawWheres djmw 20091211 Sound_fade: removed erroneous warning djmw 20100318 Cross-correlation, convolution and autocorrelation djmw 20100325 -Cross-correlation, convolution and autocorrelation djmw 20111227 Sound_trimSilencesAtStartAndEnd and Sound_getStartAndEndTimesOfSounding */ #include "Formula.h" #include "Intensity_extensions.h" #include "Sound_extensions.h" #include "Sound_and_Spectrum.h" #include "Spectrum_extensions.h" #include "Sound_to_Intensity.h" #include "Sound_to_Pitch.h" #include "Vector.h" #include "Pitch_extensions.h" #include "Pitch_to_PitchTier.h" #include "Pitch_to_PointProcess.h" #include "Polygon_extensions.h" #include "TextGrid_extensions.h" #include "DurationTier.h" #include "Manipulation.h" #include "NUM2.h" #define MAX_T 0.02000000001 /* Maximum interval between two voice pulses (otherwise voiceless). */ static void PitchTier_modifyExcursionRange (PitchTier me, double tmin, double tmax, double multiplier, double fref_Hz) { if (fref_Hz <= 0) { return; } double fref_st = 12.0 * log (fref_Hz / 100.0) / NUMln2; for (long i = 1; i <= my points -> size; i++) { RealPoint point = (RealPoint) my points -> item [i]; double f = point -> value; if (point -> number < tmin || point -> number > tmax) { continue; } if (f > 0) { double f_st = fref_st + 12.0 * log2 (f / fref_Hz) * multiplier; point -> value = 100.0 * exp (f_st * (NUMln2 / 12.0)); } } } static void Pitch_scaleDuration (Pitch me, double multiplier) { if (multiplier != 1) { // keep xmin at the same value my dx *= multiplier; my x1 = my xmin + (my x1 - my xmin) * multiplier; my xmax = my xmin + (my xmax - my xmin) * multiplier; } } static void Pitch_scalePitch (Pitch me, double multiplier) { for (long i = 1; i <= my nx; i++) { double f = my frame[i].candidate[1].frequency; f *= multiplier; if (f < my ceiling) { my frame[i].candidate[1].frequency = f; } } } static void i1write (Sound me, FILE *f, long *nClip) { double *s = my z[1], min = -128, max = 127; *nClip = 0; for (long i = 1; i <= my nx; i++) { double sample = floor (s[i] * 128 + 0.5); if (sample > max) { sample = max; (*nClip) ++; } else if (sample < min) { sample = min; (*nClip) ++; } binputi1 (sample, f); } } static void i1read (Sound me, FILE *f) { double *s = my z[1]; for (long i = 1; i <= my nx; i++) { s[i] = bingeti1 (f) / 128.0; } } static void u1write (Sound me, FILE *f, long *nClip) { double *s = my z[1], min = 0, max = 255; *nClip = 0; for (long i = 1; i <= my nx; i++) { double sample = floor ( (s[i] + 1) * 255 / 2 + 0.5); if (sample > max) { sample = max; (*nClip) ++; } else if (sample < min) { sample = min; (*nClip) ++; } binputu1 (sample, f); } } static void u1read (Sound me, FILE *f) { double *s = my z[1]; for (long i = 1; i <= my nx; i++) { s[i] = bingetu1 (f) / 128.0 - 1.0; } } static void i2write (Sound me, FILE *f, int littleEndian, long *nClip) { double *s = my z[1], min = -32768, max = 32767; void (*put) (int, FILE *) = littleEndian ? binputi2LE : binputi2; *nClip = 0; for (long i = 1; i <= my nx; i++) { double sample = floor (s[i] * 32768 + 0.5); if (sample > max) { sample = max; (*nClip) ++; } else if (sample < min) { sample = min; (*nClip) ++; } put (sample, f); } } static void i2read (Sound me, FILE *f, int littleEndian) { double *s = my z[1]; int (*get) (FILE *) = littleEndian ? bingeti2LE : bingeti2; for (long i = 1; i <= my nx; i++) { s[i] = get (f) / 32768.; } } static void u2write (Sound me, FILE *f, int littleEndian, long *nClip) { double *s = my z[1], min = 0, max = 65535; void (*put) (unsigned int, FILE *) = littleEndian ? binputu2LE : binputu2; *nClip = 0; for (long i = 1; i <= my nx; i++) { double sample = floor ( (s[i] + 1) * 65535 / 2 + 0.5); if (sample > max) { sample = max; (*nClip) ++; } else if (sample < min) { sample = min; (*nClip) ++; } put (sample, f); } } static void u2read (Sound me, FILE *f, int littleEndian) { double *s = my z[1]; unsigned int (*get) (FILE *) = littleEndian ? bingetu2LE : bingetu2; for (long i = 1; i <= my nx; i++) { s[i] = get (f) / 32768.0 - 1.0; } } static void i4write (Sound me, FILE *f, int littleEndian, long *nClip) { double *s = my z[1]; double min = -2147483648.0, max = 2147483647.0; void (*put) (long, FILE *) = littleEndian ? binputi4LE : binputi4; *nClip = 0; for (long i = 1; i <= my nx; i++) { double sample = floor (s[i] * 2147483648.0 + 0.5); if (sample > max) { sample = max; (*nClip) ++; } else if (sample < min) { sample = min; (*nClip) ++; } put (sample, f); } } static void i4read (Sound me, FILE *f, int littleEndian) { double *s = my z[1]; long (*get) (FILE *) = littleEndian ? bingeti4LE : bingeti4; for (long i = 1; i <= my nx; i++) { s[i] = get (f) / 2147483648.; } } static void u4write (Sound me, FILE *f, int littleEndian, long *nClip) { double *s = my z[1]; double min = 0.0, max = 4294967295.0; void (*put) (unsigned long, FILE *) = littleEndian ? binputu4LE : binputu4; *nClip = 0; for (long i = 1; i <= my nx; i++) { double sample = floor (s[i] * 4294967295.0 + 0.5); if (sample > max) { sample = max; (*nClip) ++; } else if (sample < min) { sample = min; (*nClip) ++; } put (sample, f); } } static void u4read (Sound me, FILE *f, int littleEndian) { double *s = my z[1]; long (*get) (FILE *) = littleEndian ? bingeti4LE : bingeti4; for (long i = 1; i <= my nx; i++) { s[i] = get (f) / 2147483648.0 - 1.0; } } static void r4write (Sound me, FILE *f) { double *s = my z[1]; for (long i = 1; i <= my nx; i++) { binputr4 (s[i], f); } } static void r4read (Sound me, FILE *f) { double *s = my z[1]; for (long i = 1; i <= my nx; i++) { s[i] = bingetr4 (f); } } static long fileLengthBytes (FILE *f) { long begin, end, current; if ( (current = ftell (f)) < 0 || fseek (f, 0L, SEEK_SET) || (begin = ftell (f)) < 0 || fseek (f, 0L, SEEK_END) || (end = ftell (f)) < 0 || fseek (f, current, SEEK_SET)) { end = begin = 0; } return end - begin; } /* Old TIMIT sound-file format */ Sound Sound_readFromCmuAudioFile (MelderFile file) { try { int littleEndian = 1; autofile f = Melder_fopen (file, "rb"); if (bingeti2LE (f) != 6) { Melder_throw ("Incorrect header size."); } bingeti2LE (f); short nChannels = bingeti2LE (f); if (nChannels < 1) { Melder_throw ("Incorrect number of channels."); } if (nChannels > 1) { Melder_throw ("File has multiple channels: cannot read."); } if (bingeti2LE (f) < 1) { Melder_throw ("Incorrect sampling frequency."); } long nSamples = bingeti4LE (f); if (nSamples < 1) { Melder_throw ("Incorrect number of samples."); } autoSound me = Sound_createSimple (1, nSamples / 16000., 16000); i2read (me.peek(), f, littleEndian); f.close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not read from CMU audio file ", MelderFile_messageName (file), "."); } } Sound Sound_readFromRawFile (MelderFile file, const char *format, int nBitsCoding, int littleEndian, int unSigned, long skipNBytes, double samplingFrequency) { try { autofile f = Melder_fopen (file, "rb"); if (! format) { format = "integer"; } if (nBitsCoding <= 0) { nBitsCoding = 16; } long nBytesPerSample = (nBitsCoding + 7) / 8; if (strequ (format, "float")) { nBytesPerSample = 4; } if (nBytesPerSample == 3 || nBytesPerSample > 4) { Melder_throw ("Number of bytes per sample should be 1, 2 or 4."); } if (skipNBytes <= 0) { skipNBytes = 0; } long nSamples = (fileLengthBytes (f) - skipNBytes) / nBytesPerSample; if (nSamples < 1) { Melder_throw ("No samples left to read"); } autoSound me = Sound_createSimple (1, nSamples / samplingFrequency, samplingFrequency); fseek (f, skipNBytes, SEEK_SET); if (nBytesPerSample == 1 && unSigned) { u1read (me.peek(), f); } else if (nBytesPerSample == 1 && ! unSigned) { i1read (me.peek(), f); } else if (nBytesPerSample == 2 && unSigned) { u2read (me.peek(), f, littleEndian); } else if (nBytesPerSample == 2 && ! unSigned) { i2read (me.peek(), f, littleEndian); } else if (nBytesPerSample == 4 && unSigned) { u4read (me.peek(), f, littleEndian); } else if (nBytesPerSample == 4 && ! unSigned) { i4read (me.peek(), f, littleEndian); } else if (nBytesPerSample == 4 && strequ (format, "float")) { r4read (me.peek(), f); } f.close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not read from raw audio file ", MelderFile_messageName (file), "."); } } void Sound_writeToRawFile (Sound me, MelderFile file, const char *format, int littleEndian, int nBitsCoding, int unSigned) { try { long nClip = 0; autofile f = Melder_fopen (file, "wb"); if (! format) { format = "integer"; } if (nBitsCoding <= 0) { nBitsCoding = 16; } long nBytesPerSample = (nBitsCoding + 7) / 8; if (strequ (format, "float")) { nBytesPerSample = 4; } if (nBytesPerSample == 3 || nBytesPerSample > 4) { Melder_throw (L"number of bytes per sample should be 1, 2 or 4."); } if (nBytesPerSample == 1 && unSigned) { u1write (me, f, & nClip); } else if (nBytesPerSample == 1 && ! unSigned) { i1write (me, f, & nClip); } else if (nBytesPerSample == 2 && unSigned) { u2write (me, f, littleEndian, & nClip); } else if (nBytesPerSample == 2 && ! unSigned) { i2write (me, f, littleEndian, & nClip); } else if (nBytesPerSample == 4 && unSigned) { u4write (me, f, littleEndian, & nClip); } else if (nBytesPerSample == 4 && ! unSigned) { i4write (me, f, littleEndian, & nClip); } else if (nBytesPerSample == 4 && strequ (format, "float")) { r4write (me, f); } if (nClip > 0) Melder_warning (Melder_integer (nClip), L" from ", Melder_integer (my nx), L" samples have been clipped.\nAdvice: you could scale the amplitudes or save as a binary file."); if (feof (f) || ferror (f)) { Melder_throw ("Sound_writeToRawFile: not completed"); } f.close (file); } catch (MelderError) { Melder_throw (me, ": saving as raw file not performed."); } } struct dialogic_adpcm { char code; short last, index; short step_size[49]; short adjust[8]; }; static void dialogic_adpcm_init (struct dialogic_adpcm *adpcm) { short step_size[49] = { 16, 17, 19, 21, 23, 25, 28, 31, 34, 37, 41, 45, 50, 55, 60, 66, 73, 80, 88, 97, 107, 118, 130, 143, 157, 173, 190, 209, 230, 253, 279, 307, 337, 371, 408, 449, 494, 544, 598, 658, 724, 796, 876, 963, 1060, 1166, 1282, 1411, 1552 }; short adjust[8] = { -1, -1, -1, -1, 2, 4, 6, 8 }; adpcm -> last = 0; adpcm -> index = 0; for (long i = 0; i < 49; i++) { adpcm -> step_size[i] = step_size[i]; } for (long i = 0; i < 8; i++) { adpcm -> adjust[i] = adjust[i]; } } /* The code is adapted from: Bob Edgar (), "PC Telephony - The complete guide to designing, building and programming systems using Dialogic and Related Hardware", 272-276. */ static float dialogic_adpcm_decode (struct dialogic_adpcm *adpcm) { float scale = 32767.0 / 32768.0 / 2048.0; // nibble = B3 B2 B1 B0 (4 lower bits) // d(n) = ss(n)*B2 + ss(n)/2 *B1 + ss(n)/4*B0 + ss(n)/8 short ss = adpcm -> step_size[adpcm -> index]; short e = ss / 8; if (adpcm -> code & 0x01) { e += ss / 4; } if (adpcm -> code & 0x02) { e += ss / 2; } if (adpcm -> code & 0x04) { e += ss; } // If B3==1 then d(n) = -d(n); short diff = (adpcm -> code & 0x08) ? -e : e; // x(n) = x(n-1)+d(n) short s = adpcm -> last + diff; if (s > 2048) { s = 2048; } if (s < -2048) { s = -2048; } adpcm -> last = s; // ss(n+1) = ss(n) * 1.1*M(L(n)) via lookup table adpcm -> index += adpcm -> adjust[adpcm -> code & 0x07]; if (adpcm -> index < 0) { adpcm -> index = 0; } if (adpcm -> index > 48) { adpcm -> index = 48; } return scale * s; } Sound Sound_readFromDialogicADPCMFile (MelderFile file, double sampleRate) { try { autofile f = Melder_fopen (file, "rb"); long filelength = MelderFile_length (file); if (filelength <= 0) { Melder_throw ("File is empty."); } // Two samples in each byte long numberOfSamples = 2 * filelength; if (numberOfSamples <= 0) { Melder_throw ("File too long"); } autoSound me = Sound_createSimple (1, numberOfSamples / sampleRate, sampleRate); // Read all bytes and decode struct dialogic_adpcm adpcm; dialogic_adpcm_init (& adpcm); long n = 1; for (long i = 1; i <= filelength; i++) { unsigned char sc; fread (&sc, 1, 1, f); adpcm.code = (char) ( (sc >> 4) & 0x0f); my z[1][n++] = dialogic_adpcm_decode (& adpcm); adpcm.code = (char) (sc & 0x0f); my z[1][n++] = dialogic_adpcm_decode (& adpcm); } f.close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not read from Dialogic ADPCM file", MelderFile_messageName (file), "."); } } void Sound_preEmphasis (Sound me, double preEmphasisFrequency) { if (preEmphasisFrequency >= 0.5 / my dx) { return; // above Nyquist? } double preEmphasis = exp (- 2.0 * NUMpi * preEmphasisFrequency * my dx); for (long channel = 1; channel <= my ny; channel++) { double *s = my z[channel]; for (long i = my nx; i >= 2; i--) { s[i] -= preEmphasis * s[i - 1]; } } } void Sound_deEmphasis (Sound me, double deEmphasisFrequency) { double deEmphasis = exp (- 2.0 * NUMpi * deEmphasisFrequency * my dx); for (long channel = 1; channel <= my ny; channel++) { double *s = my z[channel]; for (long i = 2; i <= my nx; i++) { s[i] += deEmphasis * s[i - 1]; } } } Sound Sound_createGaussian (double windowDuration, double samplingFrequency) { try { autoSound me = Sound_createSimple (1, windowDuration, samplingFrequency); double *s = my z[1]; double imid = 0.5 * (my nx + 1), edge = exp (-12.0); for (long i = 1; i <= my nx; i++) { s[i] = (exp (-48.0 * (i - imid) * (i - imid) / (my nx + 1) / (my nx + 1)) - edge) / (1 - edge); } return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from Gaussian function."); } } Sound Sound_createHamming (double windowDuration, double samplingFrequency) { try { autoSound me = Sound_createSimple (1, windowDuration, samplingFrequency); double *s = my z[1]; double p = 2 * NUMpi / (my nx - 1); for (long i = 1; i <= my nx; i++) { s[i] = 0.54 - 0.46 * cos ( (i - 1) * p); } return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from Hamming function."); }; } static Sound Sound_create2 (double minimumTime, double maximumTime, double samplingFrequency) { return Sound_create (1, minimumTime, maximumTime, floor ( (maximumTime - minimumTime) * samplingFrequency + 0.5), 1.0 / samplingFrequency, minimumTime + 0.5 / samplingFrequency); } /* Trig functions whose arguments form a linear sequence x = x1 + n.dx, for n=0,1,2,... are efficiently calculated by the following recurrence: cos(a+dx) = cos(a) - (alpha . cos(a) + beta . sin(a)) sin(a+dx) = sin(a) - (alpha . sin(a) - beta . sin(a)) where alpha and beta are precomputed coefficients alpha = 2 sin^2(dx/2) and beta = sin(dx) In this way aplha and beta do not loose significance if the increment dx is small. */ static Sound Sound_createToneComplex (double minimumTime, double maximumTime, double samplingFrequency, double firstFrequency, long numberOfComponents, double frequencyDistance, long mistunedComponent, double mistuningFraction, int scaleAmplitudes) { try { autoSound me = Sound_create2 (minimumTime, maximumTime, samplingFrequency); for (long j = 1; j <= numberOfComponents; j++) { double fraction = j == mistunedComponent ? mistuningFraction : 0; double w = 2 * NUMpi * (firstFrequency + (j - 1 + fraction) * frequencyDistance); double delta = w * my dx; double alpha = 2 * sin (delta / 2) * sin (delta / 2); double beta = sin (delta); double sint = sin (w * my x1); double cost = cos (w * my x1); my z[1][1] += sint; for (long i = 2; i <= my nx; i++) { double costd = cost - (alpha * cost + beta * sint); double sintd = sint - (alpha * sint - beta * cost); my z[1][i] += sintd; cost = costd; sint = sintd; } } if (scaleAmplitudes) { Vector_scale (me.peek(), 0.99996948); } return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from tone complex."); } } Sound Sound_createSimpleToneComplex (double minimumTime, double maximumTime, double samplingFrequency, double firstFrequency, long numberOfComponents, double frequencyDistance, int scaleAmplitudes) { if (firstFrequency + (numberOfComponents - 1) * frequencyDistance > samplingFrequency / 2) { Melder_warning (L"Sound_createSimpleToneComplex: frequency of (some) components too high."); numberOfComponents = 1.0 + (samplingFrequency / 2 - firstFrequency) / frequencyDistance; } return Sound_createToneComplex (minimumTime, maximumTime, samplingFrequency, firstFrequency, numberOfComponents, frequencyDistance, 0, 0, scaleAmplitudes); } Sound Sound_createMistunedHarmonicComplex (double minimumTime, double maximumTime, double samplingFrequency, double firstFrequency, long numberOfComponents, long mistunedComponent, double mistuningFraction, int scaleAmplitudes) { if (firstFrequency + (numberOfComponents - 1) * firstFrequency > samplingFrequency / 2) { Melder_warning (L"Sound_createMistunedHarmonicComplex: frequency of (some) components too high."); numberOfComponents = 1.0 + (samplingFrequency / 2 - firstFrequency) / firstFrequency; } if (mistunedComponent > numberOfComponents) { Melder_warning (L"Sound_createMistunedHarmonicComplex: mistuned component too high."); } return Sound_createToneComplex (minimumTime, maximumTime, samplingFrequency, firstFrequency, numberOfComponents, firstFrequency, mistunedComponent, mistuningFraction, scaleAmplitudes); } /* The gammachirp is a "chirp tone" with a gamma-function envelope: f(t) = t^(n-1) exp (-2 pi b t) cos (2 pi f0 t + c ln (t) + p0) = t^(n-1) exp (-2 pi b t) cos (phi(t)) Instantaneous frequency f is defined as f = d phi(t) / dt / (2 pi) and so: f = f0 + c /(2 pi t) Irino: bandwidth = (frequency * (6.23e-6 * frequency + 93.39e-3) + 28.52) */ Sound Sound_createGammaTone (double minimumTime, double maximumTime, double samplingFrequency, long gamma, double frequency, double bandwidth, double initialPhase, double addition, int scaleAmplitudes) { try { autoSound me = Sound_create2 (minimumTime, maximumTime, samplingFrequency); for (long i = 1; i <= my nx; i++) { double t = (i - 0.5) * my dx; double f = frequency + addition / (NUM2pi * t); if (f > 0 && f < samplingFrequency / 2) my z[1][i] = pow (t, gamma - 1) * exp (- NUM2pi * bandwidth * t) * cos (NUM2pi * frequency * t + addition * log (t) + initialPhase); } if (scaleAmplitudes) { Vector_scale (me.peek(), 0.99996948); } return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from gammatone function."); } } static void NUMgammatoneFilter4 (double *x, double *y, long n, double centre_frequency, double bandwidth, double samplingFrequency) { double a[5], b[9], dt = 1.0 / samplingFrequency, wt = NUMpi * centre_frequency * dt; double bt = 2 * NUMpi * bandwidth * dt, dt2 = dt * dt, dt4 = dt2 * dt2; Melder_assert (n > 0 && centre_frequency > 0 && bandwidth >= 0 && samplingFrequency > 0); /* The filter function is: H(z) = sum (i=0..4, a[i] z^-i) / sum (j=0..4, b[j] z^-j) Coefficients a & b according to: Slaney (1993), An efficient implementation of the Patterson-Holdsworth auditory filterbank, Apple Computer Technical Report 35, 41 pages. For the a's we have left out an overal scale factor of dt^4. This makes a[0] = 1. */ a[0] = dt4; a[1] = -4 * dt4 * cos (2 * wt) * exp (- bt); a[2] = 6 * dt4 * cos (4 * wt) * exp (-2 * bt); a[3] = -4 * dt4 * cos (6 * wt) * exp (-3 * bt); a[4] = dt4 * cos (8 * wt) * exp (-4 * bt); b[0] = 1; b[1] = -8 * cos (2 * wt) * exp (- bt); b[2] = (16 + 12 * cos (4 * wt)) * exp (-2 * bt); b[3] = (-48 * cos (2 * wt) - 8 * cos (6 * wt)) * exp (-3 * bt); b[4] = (36 + 32 * cos (4 * wt) + 2 * cos (8 * wt)) * exp (-4 * bt); b[5] = (-48 * cos (2 * wt) - 8 * cos (6 * wt)) * exp (-5 * bt); b[6] = (16 + 12 * cos (4 * wt)) * exp (-6 * bt); b[7] = -8 * cos (2 * wt) * exp (-7 * bt); b[8] = exp (-8 * bt); /* Calculate gain (= Abs (H(z); f=fc) and scale a[0-4] with it. */ double zr = cos (2 * wt), zi = -sin (2 * wt); double dr = a[4], di = 0, tr, ti, nr, ni; for (long j = 1; j <= 4; j++) { tr = a[4 - j] + zr * dr - zi * di; ti = zi * dr + zr * di; dr = tr; di = ti; } dr = b[8]; di = 0; for (long j = 1; j <= 8; j++) { nr = b[8 - j] + zr * dr - zi * di; ni = zi * dr + zr * di; dr = nr; di = ni; } double n2 = nr * nr + ni * ni; double gr = tr * nr + ti * ni; double gi = ti * nr - tr * ni; double gain = sqrt (gr * gr + gi * gi) / n2; for (long j = 0; j <= 4; j++) { a[j] /= gain; } if (Melder_debug == -1) { Melder_casual ("--gammatonefilter4--\nF = %ls, B = %ls, T = %ls\nGain = %ls", Melder_double (centre_frequency), Melder_double (bandwidth), Melder_double (dt), Melder_double (gain)); for (long i = 0; i <= 4; i++) { Melder_casual ("a[%d] = %ls", i, Melder_double (a[i])); } for (long i = 0; i <= 8; i++) { Melder_casual ("b[%d] = %ls", i, Melder_double (b[i])); } } /* Perform the filtering. For the first 8 samples we must do some extra work. */ long n8 = n < 8 ? n : 8; for (long i = 1; i <= n8; i++) { y[i] = a[0] * x[i]; if (i > 1) { y[i] += a[1] * x[i - 1] - b[1] * y[i - 1]; } else { continue; } if (i > 2) { y[i] += a[2] * x[i - 2] - b[2] * y[i - 2]; } else { continue; } if (i > 3) { y[i] += a[3] * x[i - 3] - b[3] * y[i - 3]; } else { continue; } if (i > 4) { y[i] += a[4] * x[i - 4] - b[4] * y[i - 4]; } else { continue; } if (i > 5) { y[i] -= b[5] * y[i - 5]; } else { continue; } if (i > 6) { y[i] -= b[6] * y[i - 6]; } else { continue; } if (i > 7) { y[i] -= b[7] * y[i - 7]; } } for (long i = n8 + 1; i <= n; i++) { // y[i] = a[0] * x[i]; // y[i] += a[1] * x[i-1] + a[2] * x[i-2] + a[3] * x[i-3] + a[4] * x[i-4]; // y[i] -= b[1] * y[i-1] + b[2] * y[i-2] + b[3] * y[i-3] + b[4] * y[i-4]; // y[i] -= b[5] * y[i-5] + b[6] * y[i-6] + b[7] * y[i-7] + b[8] * y[i-8]; y[i] = a[0] * x[i] + a[1] * x[i - 1] + a[2] * x[i - 2] + a[3] * x[i - 3] + a[4] * x[i - 4] - b[1] * y[i - 1] - b[2] * y[i - 2] - b[3] * y[i - 3] - b[4] * y[i - 4] - b[5] * y[i - 5] - b[6] * y[i - 6] - b[7] * y[i - 7] - b[8] * y[i - 8]; } } Sound Sound_filterByGammaToneFilter4 (Sound me, double centre_frequency, double bandwidth) { try { if (centre_frequency <= 0) { Melder_throw ("Centre frequency must be positive."); } if (bandwidth < 0) { Melder_throw ("Bandwidth must be positive."); } autoSound thee = Sound_create (my ny, my xmin, my xmax, my nx, my dx, my x1); autoNUMvector y (1, my nx); autoNUMvector x (1, my nx); double fs = 1 / my dx; for (long channel = 1; channel <= my ny; channel++) { for (long i = 1; i <= my nx; i++) { x[i] = my z[channel][i]; } NUMgammatoneFilter4 (x.peek(), y.peek(), my nx, centre_frequency, bandwidth, fs); for (long i = 1; i <= my nx; i++) { thy z[channel][i] = y[i]; } } return thee.transfer(); } catch (MelderError) { Melder_throw ("Sound not filtered by gammatone filter4."); } } /* Sound Sound_createShepardTone (double minimumTime, double maximumTime, double samplingFrequency, double baseFrequency, double frequencyShiftFraction, double maximumFrequency, double amplitudeRange) { Sound me; long i, j, nComponents = 1 + log2 (maximumFrequency / 2 / baseFrequency); double lmin = pow (10, - amplitudeRange / 10); double twoPi = 2.0 * NUMpi, f = baseFrequency * (1 + frequencyShiftFraction); if (nComponents < 2) Melder_warning (L"Sound_createShepardTone: only 1 component."); Melder_casual ("Sound_createShepardTone: %ld components.", nComponents); if (! (me = Sound_create2 (minimumTime, maximumTime, samplingFrequency))) return NULL; for (j=1; j <= nComponents; j++) { double fj = f * pow (2, j-1), wj = twoPi * fj; double amplitude = lmin + (1 - lmin) * (1 - cos (twoPi * log (fj + 1) / log (maximumFrequency + 1))) / 2; for (i=1; i <= my nx; i++) { my z[1][i] += amplitude * sin (wj * (i - 0.5) * my dx); } } Vector_scale (me, 0.99996948); return me; } */ Sound Sound_createShepardToneComplex (double minimumTime, double maximumTime, double samplingFrequency, double lowestFrequency, long numberOfComponents, double frequencyChange_st, double amplitudeRange, double octaveShiftFraction) { try { double highestFrequency = lowestFrequency * pow (2, numberOfComponents); double lmax_db = 0, lmin_db = lmax_db - fabs (amplitudeRange); if (highestFrequency > samplingFrequency / 2) Melder_throw ("The highest frequency you want to generate is " "above the Nyquist frequency. Choose a larger value for \"Sampling frequency\", or lower values for " "\"Number of components\" or \"Lowest frequency\"."); if (octaveShiftFraction < 0 || octaveShiftFraction >= 1) Melder_throw ("Octave offset fraction " "must be greater or equal zero and smaller than one."); double octaveTime, sweeptime; if (frequencyChange_st != 0) { octaveTime = 12 / fabs (frequencyChange_st); sweeptime = numberOfComponents * octaveTime; } else { octaveTime = sweeptime = 1e38; } autoSound me = Sound_create2 (minimumTime, maximumTime, samplingFrequency); double a = frequencyChange_st / 12; for (long i = 1; i <= numberOfComponents; i++) { double tswitch; double freqi = lowestFrequency * pow (2, i - 1 + octaveShiftFraction); double b1, b2; double phase1 = 0, phasejm1 = 0; /* The frequency is f(t) = lowestFrequency * 2^tone(t) The tone is parametrized with a straight line: tone(t) = a * t + b where a = frequencyChange_st / 12 and b depends on the component If frequencyChange_st >=0 The tone rises until highest frequency at t=tswich, then falls to lowest and starts rising again. The slope is always the same. The offsets are b1 and b2 respectively. We count octaveShiftFraction as distance from tone base else if frequencyChange_st < 0 The tone falls until the lowest frequency at t=tswich, then jumps to highest and starts falling again All tones start one octave higher as in rising case. We also count octaveShiftFraction down from this tone base. else No changes in frequency of the components. endif */ if (frequencyChange_st >= 0) { b1 = i - 1 + octaveShiftFraction; b2 = 0; tswitch = (numberOfComponents - b1) * octaveTime; } else { freqi *= 2; b1 = i - octaveShiftFraction; b2 = numberOfComponents; tswitch = b1 * octaveTime; } for (long j = 1; j <= my nx; j++) { double t = Sampled_indexToX (me.peek(), j); double tmod = fmod (t, sweeptime); double tone = tmod <= tswitch ? b1 + a * tmod : b2 + a * (tmod - tswitch); double f = lowestFrequency * pow (2, tone); /* double theta = 2 * NUMpi * log2 (f / lowestFrequency) / numberOfComponents; */ double theta = 2 * NUMpi * tone / numberOfComponents; double level = pow (10, (lmin_db + (lmax_db - lmin_db) * (1 - cos (theta)) / 2) / 20); double phasej = phasejm1 + 2 * NUMpi * f * my dx; /* Integrate 2*pi*f(t) */ if (j == 1) { phase1 = phasej; // phase1 = j == 1 ? phasej : phase1; } my z[1][j] += level * sin (phasej - phase1); // si phasejm1 = phasej; } } Vector_scale (me.peek(), 0.99996948); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from Shepard tone complex."); } } /* can be implemented more efficiently with sin recurrence? */ /* amplitude(f) = min + (1-min)*(1-cos(2*pi*(ln(f/f1) / ln(fn/f1)))/2 */ Sound Sound_createShepardTone (double minimumTime, double maximumTime, double samplingFrequency, double lowestFrequency, long numberOfComponents, double frequencyChange_st, double amplitudeRange) { try { double scale = pow (2, numberOfComponents); double maximumFrequency = lowestFrequency * scale; double lmin = pow (10, - amplitudeRange / 10), twoPi = 2.0 * NUMpi; double ln2t0 = log (2) * frequencyChange_st / 12; double lnf1 = log (lowestFrequency + 1); double amplarg = twoPi / log ( (maximumFrequency + 1) / (lowestFrequency + 1)); if (lowestFrequency > samplingFrequency / 2) Melder_throw ("Sound_createShepardTone: lowest frequency too high."); if (maximumFrequency > samplingFrequency / 2) Melder_throw ("Sound_createShepardTone: frequency of highest component too high."); autoSound me = Sound_create2 (minimumTime, maximumTime, samplingFrequency); for (long i = 1; i <= my nx; i++) { double argt, t = (i - 0.5) * my dx, ft = lowestFrequency; if (frequencyChange_st != 0) { double expt = exp (ln2t0 * t); argt = twoPi * lowestFrequency * (expt - 1) / ln2t0; ft *= expt; } else { argt = twoPi * ft * t; } for (long j = 1; j <= numberOfComponents; j++) { while (ft >= maximumFrequency) { ft /= scale; argt /= scale; } //amplitude = lmin + (1 - lmin) * (1 - cos (twoPi * log (ft + 1) / log (maximumFrequency + 1))) / 2; double amplitude = lmin + (1 - lmin) * (1 - cos (amplarg * (log (ft + 1) - lnf1))) / 2; my z[1][i] += amplitude * sin (argt); ft *= 2; argt *= 2; } } Vector_scale (me.peek(), 0.99996948); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from Shepard tone."); } } Sound Sound_createPattersonWightmanTone (double minimumTime, double maximumTime, double samplingFrequency, double baseFrequency, double frequencyShiftRatio, long numberOfComponents) { try { if ( (numberOfComponents - 1 + frequencyShiftRatio) * baseFrequency > samplingFrequency / 2) Melder_throw ("Frequency of one or more components too large."); autoSound me = Sound_create2 (minimumTime, maximumTime, samplingFrequency); double w0 = NUM2pi * baseFrequency; for (long i = 1; i <= my nx; i++) { double a = 0, t = (i - 0.5) * my dx; for (long j = 1; j <= numberOfComponents; j++) { a += sin ( (j + frequencyShiftRatio) * w0 * t); } my z[1][i] = a; } Vector_scale (me.peek(), 0.99996948); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from Patterson Wightman tone."); } } Sound Sound_createPlompTone (double minimumTime, double maximumTime, double samplingFrequency, double baseFrequency, double frequencyFraction, long m) { try { double w1 = NUM2pi * (1 - frequencyFraction) * baseFrequency; double w2 = NUM2pi * (1 + frequencyFraction) * baseFrequency; if (12 * (1 + frequencyFraction) * baseFrequency > samplingFrequency / 2) Melder_throw ("Sound_createPlompTone: frequency of one or more components too large."); autoSound me = Sound_create2 (minimumTime, maximumTime, samplingFrequency); for (long i = 1; i <= my nx; i++) { double a = 0, t = (i - 0.5) * my dx; for (long j = 1; j <= m; j++) { a += sin (j * w1 * t); } for (long j = m + 1; j <= 12; j++) { a += sin (j * w2 * t); } my z[1][i] = a; } Vector_scale (me.peek(), 0.99996948); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from Plomp tone."); } } void Sounds_multiply (Sound me, Sound thee) { long n = my nx < thy nx ? my nx : thy nx; double *s1 = my z[1], *s2 = thy z[1]; for (long i = 1; i <= n; i++) { s1[i] *= s2[i]; } } double Sound_power (Sound me) { double e = 0, *amplitude = my z[1]; for (long i = 1; i <= my nx; i++) { e += amplitude[i] * amplitude[i]; } return sqrt (e) * my dx / (my xmax - my xmin); } double Sound_correlateParts (Sound me, double tx, double ty, double duration) { if (ty < tx) { double t = tx; tx = ty; ty = t; } long nbx = Sampled_xToNearestIndex (me, tx); long nby = Sampled_xToNearestIndex (me, ty); long ney = Sampled_xToNearestIndex (me, ty + duration); long increment = 0, decrement = 0; if (nbx < 1) { increment = 1 - nbx; } if (ney > my nx) { decrement = ney - my nx; } long ns = duration / my dx - increment - decrement; if (ns < 1) { return 0; } double *x = & my z[1][nbx + increment - 1]; double *y = & my z[1][nby + increment - 1]; double xm = 0, ym = 0, sxx = 0, syy = 0, sxy = 0; for (long i = 1; i <= ns; i++) { xm += x[i]; ym += y[i]; } xm /= ns; ym /= ns; for (long i = 1; i <= ns; i++) { double xt = x[i] - xm, yt = y[i] - ym; sxx += xt * xt; syy += yt * yt; sxy += xt * yt; } double denum = sxx * syy; double rxy = denum > 0 ? sxy / sqrt (denum) : 0; return rxy; } void Sound_localMean (Sound me, double fromTime, double toTime, double *mean) { long n1 = Sampled_xToNearestIndex (me, fromTime); long n2 = Sampled_xToNearestIndex (me, toTime); double *s = my z[1]; *mean = 0; if (fromTime > toTime) { return; } if (n1 < 1) { n1 = 1; } if (n2 > my nx) { n2 = my nx; } for (long i = n1; i <= n2; i++) { *mean += s[i]; } *mean /= n2 - n1 + 1; } void Sound_localPeak (Sound me, double fromTime, double toTime, double ref, double *peak) { long n1 = Sampled_xToNearestIndex (me, fromTime); long n2 = Sampled_xToNearestIndex (me, toTime); double *s = my z[1]; *peak = -1e38; if (fromTime > toTime) { return; } if (n1 < 1) { n1 = 1; } if (n2 > my nx) { n2 = my nx; } for (long i = n1; i <= n2; i++) { double ds = fabs (s[i] - ref); if (ds > *peak) { *peak = ds; } } } void Sound_into_Sound (Sound me, Sound to, double startTime) { long index = Sampled_xToNearestIndex (me, startTime); for (long i = 1; i <= to -> nx; i++) { long j = index - 1 + i; to -> z[1][i] = j < 1 || j > my nx ? 0 : my z[1][j]; } } /* IntervalTier Sound_PointProcess_to_IntervalTier (Sound me, PointProcess thee, double window); IntervalTier Sound_PointProcess_to_IntervalTier (Sound me, PointProcess thee, double window) { IntervalTier him; TextInterval interval; double t1, t2, t, window2 = window / 2; long i; him = IntervalTier_create (my xmin, my xmax); if (him == NULL) return NULL; t1 = thy t[1] - window2; if (t1 < my xmin) t1 = my xmin; t2 = t1 + window2; if (t2 > my xmax) t2 = my xmax; interval = TextInterval_create (t1, t2, "yes"); if (interval == NULL || ! Collection_addItem (his intervals, interval)) goto end; for (i = 2; i <= thy nt; i++) { t = thy t[i]; if (t <= t2) { long index = his points -> size; RealPoint point = his points -> item[index]; t2 = t + window2; if (t2 > my xmax) t2 = my xmax; point -> value = t2; } else { t2 = t + window2; if (t2 > my xmax) t2 = my xmax; if (! RealTier_addPoint (him, t, t2)) goto end; } } end: if (Melder_hasError()) forget (him); return him; } */ void Sound_overwritePart (Sound me, double t1, double t2, Sound thee, double t3) { if (my dx != thy dx) { Melder_throw ("Sample rates must be equal."); } if (t1 == 0) { t1 = my xmin; } if (t2 == 0) { t2 = my xmax; } long i1 = Sampled_xToHighIndex (me, t1); long i2 = Sampled_xToLowIndex (me, t2); if (i1 > i2 || i2 > my nx || i1 < 1) Melder_throw ("Times of part to be overwritten must be within the sound."); if (t3 == 0) { t3 = thy xmin; } long i3 = Sampled_xToHighIndex (thee, t3); long i4 = Sampled_xToLowIndex (thee, t3 + t2 - t1); if (i4 > thy nx || i3 < 1) { Melder_throw ("Not enough samples to be copied."); } if (i4 - i3 != i2 - i1) { Melder_throw ("Error i4 - i3 != i2 - i1."); } for (long i = i1; i <= i2; i++) { my z[1][i] = thy z[1][i - i1 + i3]; } } void Sound_filter_part_formula (Sound me, double t1, double t2, const wchar_t *formula, Interpreter interpreter) { try { autoSound part = Sound_extractPart (me, t1, t2, kSound_windowShape_RECTANGULAR, 1, 1); autoSpectrum spec = Sound_to_Spectrum (part.peek(), TRUE); Matrix_formula ( (Matrix) spec.peek(), formula, interpreter, 0); autoSound filtered = Spectrum_to_Sound (spec.peek()); // Overwrite part between t1 and t2 of original with the filtered signal */ Sound_overwritePart (me, t1, t2, filtered.peek(), 0); } catch (MelderError) { Melder_throw (me, ": part not filtered by formula."); } } /* First approximation on the basis of differences in the sampled signal. The underlying analog signal still could have jumps undetected by this algorithm. We could get a better approximation by first upsampling the signal. */ PointProcess Sound_to_PointProcess_getJumps (Sound me, double minimumJump, double dt) { try { autoPointProcess thee = PointProcess_create (my xmin, my xmax, 10); long i = 1, dtn = dt / my dx; if (dtn < 1) { dtn = 1; } double *s = my z[1]; while (i < my nx) { long j = i + 1, step = 1; while (j <= i + dtn && j <= my nx) { if (fabs (s[i] - s[j]) > minimumJump) { double t = Sampled_indexToX (me, i); PointProcess_addPoint (thee.peek(), t); step = j - i + 1; break; } j++; } i += step; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no PointProcess created."); } } /* Internal pitch representation in semitones */ Sound Sound_and_Pitch_changeSpeaker (Sound me, Pitch him, double formantMultiplier, // > 0 double pitchMultiplier, // > 0 double pitchRangeMultiplier, // any number double durationMultiplier) { // > 0 try { double samplingFrequency_old = 1 / my dx; if (my xmin != his xmin || my xmax != his xmax) Melder_throw ("The Pitch and the Sound object must have the same start and end times."); autoSound sound = Data_copy (me); Vector_subtractMean (sound.peek()); if (formantMultiplier != 1) { // Shift all frequencies (inclusive pitch!) */ Sound_overrideSamplingFrequency (sound.peek(), samplingFrequency_old * formantMultiplier); } autoPitch pitch = Data_copy (him); Pitch_scaleDuration (pitch.peek(), 1 / formantMultiplier); // Pitch_scalePitch (pitch.peek(), formantMultiplier); autoPointProcess pulses = Sound_Pitch_to_PointProcess_cc (sound.peek(), pitch.peek()); autoPitchTier pitchTier = Pitch_to_PitchTier (pitch.peek()); double median = Pitch_getQuantile (pitch.peek(), 0, 0, 0.5, kPitch_unit_HERTZ); if (median != 0 && median != NUMundefined) { /* Incorporate pitch shift from overriding the sampling frequency */ PitchTier_multiplyFrequencies (pitchTier.peek(), sound -> xmin, sound -> xmax, pitchMultiplier / formantMultiplier); PitchTier_modifyExcursionRange (pitchTier.peek(), sound -> xmin, sound -> xmax, pitchRangeMultiplier, median); } else if (pitchMultiplier != 1) { Melder_warning (L"Pitch has not been changed because the sound was entirely voiceless."); } autoDurationTier duration = DurationTier_create (my xmin, my xmax); RealTier_addPoint (duration.peek(), (my xmin + my xmax) / 2, formantMultiplier * durationMultiplier); autoSound thee = Sound_Point_Pitch_Duration_to_Sound (sound.peek(), pulses.peek(), pitchTier.peek(), duration.peek(), MAX_T); // Resample to the original sampling frequency if (formantMultiplier != 1) { thee.reset (Sound_resample (thee.peek(), samplingFrequency_old, 10)); } return thee.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from Pitch & Sound."); } } Sound Sound_changeSpeaker (Sound me, double pitchMin, double pitchMax, double formantMultiplier, // > 0 double pitchMultiplier, // > 0 double pitchRangeMultiplier, // any number double durationMultiplier) { // > 0 try { autoPitch pitch = Sound_to_Pitch (me, 0.8 / pitchMin, pitchMin, pitchMax); autoSound thee = Sound_and_Pitch_changeSpeaker (me, pitch.peek(), formantMultiplier, pitchMultiplier, pitchRangeMultiplier, durationMultiplier); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": speaker not changed."); } } TextGrid Sound_to_TextGrid_detectSilences (Sound me, double minPitch, double timeStep, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, const wchar_t *silentLabel, const wchar_t *soundingLabel) { try { int subtractMeanPressure = 1; autoIntensity thee = Sound_to_Intensity (me, minPitch, timeStep, subtractMeanPressure); autoTextGrid him = Intensity_to_TextGrid_detectSilences (thee.peek(), silenceThreshold, minSilenceDuration, minSoundingDuration, silentLabel, soundingLabel); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no TextGrid with silences created."); } } void Sound_getStartAndEndTimesOfSounding (Sound me, double minPitch, double timeStep, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double *t1, double *t2) { try { const wchar_t *silentLabel = L"-", *soundingLabel = L"+"; autoTextGrid dbs = Sound_to_TextGrid_detectSilences (me, minPitch, timeStep, silenceThreshold, minSilenceDuration, minSoundingDuration, silentLabel, soundingLabel); IntervalTier itier = (IntervalTier) dbs -> tiers -> item[1]; TextInterval ti = (TextInterval) itier -> intervals -> item[1]; *t1 = my xmin; if (Melder_wcsequ (ti -> text, silentLabel)) { *t1 = ti -> xmax; } *t2 = my xmax; ti = (TextInterval) itier -> intervals -> item[itier -> intervals -> size]; if (Melder_wcsequ (ti -> text, silentLabel)) { *t2 = ti -> xmin; } } catch (MelderError) { Melder_throw ("Sounding times not found."); } } Sound Sound_and_IntervalTier_cutPartsMatchingLabel (Sound me, IntervalTier thee, const wchar_t *match) { try { // count samples of the trimmed sound long ixmin, ixmax, numberOfSamples = 0, previous_ixmax = 0; double xmin = my xmin; // start time of output sound is start time of input sound for (long iint = 1; iint <= thy intervals -> size; iint++) { TextInterval ti = (TextInterval) thy intervals -> item[iint]; if (! Melder_wcsequ (ti -> text, match)) { numberOfSamples += Sampled_getWindowSamples (me, ti -> xmin, ti -> xmax, &ixmin, &ixmax); // if two contiguous intervals have to be copied then the last sample of previous interval // and first sample of current interval might sometimes be equal numberOfSamples = ixmin == previous_ixmax ? --numberOfSamples : numberOfSamples; previous_ixmax = ixmax; } else { // matches label if (iint == 1) { // Start time of output sound is end time of first interval xmin = ti -> xmax; } } } // Now copy the parts. The output sound starts at xmin autoSound him = Sound_create (my ny, xmin, xmin + numberOfSamples * my dx, numberOfSamples, my dx, xmin + 0.5 * my dx); numberOfSamples = 0; previous_ixmax = 0; for (long iint = 1; iint <= thy intervals -> size; iint++) { TextInterval ti = (TextInterval) thy intervals -> item[iint]; if (! Melder_wcsequ (ti -> text, match)) { long ipos; Sampled_getWindowSamples (me, ti -> xmin, ti -> xmax, &ixmin, &ixmax); if (ixmin == previous_ixmax) { ixmin++; } previous_ixmax = ixmax; for (long ichan = 1; ichan <= my ny; ichan++) { ipos = numberOfSamples + 1; for (long i = ixmin; i <= ixmax; i++, ipos++) { his z[ichan][ipos] = my z[ichan][i]; } } numberOfSamples = --ipos; } } Melder_assert (numberOfSamples == his nx); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": intervals not trimmed."); } } Sound Sound_trimSilences (Sound me, double trimDuration, bool onlyAtStartAndEnd, double minPitch, double timeStep, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, TextGrid *tg, const wchar_t *trimLabel) { try { if (my ny > 1) { Melder_throw ("The sound must be a mono sound."); } const wchar_t *silentLabel = L"silent", *soundingLabel = L"sounding"; const wchar_t *copyLabel = L""; autoTextGrid dbs = Sound_to_TextGrid_detectSilences (me, minPitch, timeStep, silenceThreshold, minSilenceDuration, minSoundingDuration, silentLabel, soundingLabel); autoIntervalTier itg = (IntervalTier) Data_copy ((IntervalTier) dbs -> tiers -> item[1]); IntervalTier itier = (IntervalTier) dbs -> tiers -> item[1]; for (long iint = 1; iint <= itier -> intervals -> size; iint++) { TextInterval ti = (TextInterval) itier -> intervals -> item[iint]; TextInterval ati = (TextInterval) itg -> intervals -> item[iint]; double duration = ti -> xmax - ti -> xmin; if (duration > trimDuration && Melder_wcsequ (ti -> text, silentLabel)) { // silent const wchar_t * label = trimLabel; if (iint == 1) { // first is special double trim_t = ti -> xmax - trimDuration; IntervalTier_moveBoundary (itg.peek(), iint, false, trim_t); } else if (iint == itier -> intervals -> size) { // last is special double trim_t = ti -> xmin + trimDuration; IntervalTier_moveBoundary (itg.peek(), iint, true, trim_t); } else { if (onlyAtStartAndEnd) { label = ati -> text; } else { double trim_t = ti -> xmin + 0.5 * trimDuration; IntervalTier_moveBoundary (itg.peek(), iint, true, trim_t); trim_t = ti -> xmax - 0.5 * trimDuration; IntervalTier_moveBoundary (itg.peek(), iint, false, trim_t); } } TextInterval_setText (ati, label); } else { // sounding TextInterval_setText (ati, copyLabel); } } autoSound thee = Sound_and_IntervalTier_cutPartsMatchingLabel (me, itg.peek(), trimLabel); if (tg != NULL) { TextGrid_addTier (dbs.peek(), itg.transfer()); *tg = dbs.transfer(); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": silences not trimmed."); } } Sound Sound_trimSilencesAtStartAndEnd (Sound me, double trimDuration, double minPitch, double timeStep, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double *t1, double *t2) { try { TextGrid tg; autoSound thee = Sound_trimSilences (me, trimDuration, true, minPitch, timeStep, silenceThreshold, minSilenceDuration, minSoundingDuration, &tg, L"trimmed"); autoTextGrid atg = tg; IntervalTier trim = (IntervalTier) tg -> tiers -> item[2]; TextInterval ti1 = (TextInterval) trim -> intervals -> item[1]; *t1 = my xmin; if (Melder_wcsequ (ti1 -> text, L"trimmed")) { *t1 = ti1 -> xmax; } TextInterval ti2 = (TextInterval) trim -> intervals -> item[trim -> intervals -> size]; *t2 = my xmax; if (Melder_wcsequ (ti2 -> text, L"trimmed")) { *t2 = ti2 -> xmin; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": silences not trimmed."); } } /* Compatibility with old Sound(&pitch)_changeGender ***********************************/ static void PitchTier_modifyRange_old (PitchTier me, double tmin, double tmax, double factor, double fmid) { for (long i = 1; i <= my points -> size; i ++) { RealPoint point = (RealPoint) my points -> item [i]; double f = point -> value; if (point -> number < tmin || point -> number > tmax) { continue; } f = fmid + (f - fmid) * factor; point -> value = f < 0 ? 0 : f; } } static Pitch Pitch_scaleTime_old (Pitch me, double scaleFactor) { try { double dx = my dx, x1 = my x1, xmax = my xmax; if (scaleFactor != 1) { dx = my dx * scaleFactor; x1 = my xmin + 0.5 * dx; xmax = my xmin + my nx * dx; } autoPitch thee = Pitch_create (my xmin, xmax, my nx, dx, x1, my ceiling, 2); for (long i = 1; i <= my nx; i++) { double f = my frame[i].candidate[1].frequency; thy frame[i].candidate[1].strength = my frame[i].candidate[1].strength; f /= scaleFactor; if (f < my ceiling) { thy frame[i].candidate[1].frequency = f; } } return thee.transfer(); } catch (MelderError) { Melder_throw ("Pitch not scaled."); } } Sound Sound_and_Pitch_changeGender_old (Sound me, Pitch him, double formantRatio, double new_pitch, double pitchRangeFactor, double durationFactor) { try { double samplingFrequency_old = 1 / my dx; if (my ny > 1) { Melder_throw ("Change Gender works only on mono sounds."); } if (my xmin != his xmin || my xmax != his xmax) Melder_throw ("The Pitch and the Sound object must have the same starting times and finishing times."); if (new_pitch < 0) { Melder_throw ("The new pitch median must not be negative."); } autoSound sound = Data_copy (me); Vector_subtractMean (sound.peek()); if (formantRatio != 1) { // Shift all frequencies (inclusive pitch!) Sound_overrideSamplingFrequency (sound.peek(), samplingFrequency_old * formantRatio); } autoPitch pitch = Pitch_scaleTime_old (him, 1 / formantRatio); autoPointProcess pulses = Sound_Pitch_to_PointProcess_cc (sound.peek(), pitch.peek()); autoPitchTier pitchTier = Pitch_to_PitchTier (pitch.peek()); double median = Pitch_getQuantile (pitch.peek(), 0, 0, 0.5, kPitch_unit_HERTZ); if (median != 0 && median != NUMundefined) { // Incorporate pitch shift from overriding the sampling frequency if (new_pitch == 0) { new_pitch = median / formantRatio; } double factor = new_pitch / median; PitchTier_multiplyFrequencies (pitchTier.peek(), sound -> xmin, sound -> xmax, factor); PitchTier_modifyRange_old (pitchTier.peek(), sound -> xmin, sound -> xmax, pitchRangeFactor, new_pitch); } else { Melder_warning (L"There were no voiced segments found."); } autoDurationTier duration = DurationTier_create (my xmin, my xmax); RealTier_addPoint (duration.peek(), (my xmin + my xmax) / 2, formantRatio * durationFactor); autoSound thee = Sound_Point_Pitch_Duration_to_Sound (sound.peek(), pulses.peek(), pitchTier.peek(), duration.peek(), 0.8 / Pitch_getMinimum (pitch.peek(), 0.0, 0.0, kPitch_unit_HERTZ, false)); // Resample to the original sampling frequency if (formantRatio != 1) { thee.reset (Sound_resample (thee.peek(), samplingFrequency_old, 10)); } return thee.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from Pitch & Sound."); } } Sound Sound_changeGender_old (Sound me, double fmin, double fmax, double formantRatio, double new_pitch, double pitchRangeFactor, double durationFactor) { try { autoPitch pitch = Sound_to_Pitch (me, 0.8 / fmin, fmin, fmax); autoSound thee = Sound_and_Pitch_changeGender_old (me, pitch.peek(), formantRatio, new_pitch, pitchRangeFactor, durationFactor); return thee.transfer(); } catch (MelderError) { Melder_throw ("Sound not created for gender change."); } } /* End of compatibility with Sound_changeGender and Sound_and_Pitch_changeGender ***********************************/ /* Draw a sound vertically, from bottom to top */ void Sound_draw_btlr (Sound me, Graphics g, double tmin, double tmax, double amin, double amax, int direction, int garnish) { double xmin, xmax, ymin, ymax; if (tmin == tmax) { tmin = my xmin; tmax = my xmax; } long itmin, itmax; Matrix_getWindowSamplesX (me, tmin, tmax, &itmin, &itmax); if (amin == amax) { Matrix_getWindowExtrema (me, itmin, itmax, 1, my ny, &amin, &amax); if (amin == amax) { amin -= 1.0; amax += 1.0; } } /* In bottom-to-top-drawing the maximum amplitude is on the left, minimum on the right */ if (direction == FROM_BOTTOM_TO_TOP) { xmin = amax; xmax = amin; ymin = tmin; ymax = tmax; } else if (direction == FROM_TOP_TO_BOTTOM) { xmin = amin; xmax = amax; ymin = tmax; ymax = tmin; } else if (direction == FROM_RIGHT_TO_LEFT) { xmin = tmax; xmax = tmin; ymin = amin; ymax = amax; } else { //if (direction == FROM_LEFT_TO_RIGHT) xmin = tmin; xmax = tmax; ymin = amin; ymax = amax; } Graphics_setWindow (g, xmin, xmax, ymin, ymax); double a1 = my z[1][itmin]; double t1 = Sampled_indexToX (me, itmin); for (long it = itmin + 1; it <= itmax; it++) { double t2 = Sampled_indexToX (me, it); double a2 = my z[1][it]; if (direction == FROM_BOTTOM_TO_TOP || direction == FROM_TOP_TO_BOTTOM) { Graphics_line (g, a1, t1, a2, t2); } else { Graphics_line (g, t1, a1, t2, a2); } a1 = a2; t1 = t2; } if (garnish) { if (direction == FROM_BOTTOM_TO_TOP) { if (amin * amax < 0) { Graphics_markBottom (g, 0, 0, 1, 1, NULL); } } else if (direction == FROM_TOP_TO_BOTTOM) { if (amin * amax < 0) { Graphics_markTop (g, 0, 0, 1, 1, NULL); } } else if (direction == FROM_RIGHT_TO_LEFT) { if (amin * amax < 0) { Graphics_markRight (g, 0, 0, 1, 1, NULL); } } else { //if (direction == FROM_LEFT_TO_RIGHT) if (amin * amax < 0) { Graphics_markLeft (g, 0, 0, 1, 1, NULL); } } Graphics_rectangle (g, xmin, xmax, ymin, ymax); } } void Sound_fade (Sound me, int channel, double t, double fadeTime, int inout, int fadeGlobal) { long numberOfSamples = fabs (fadeTime) / my dx; double t1 = t, t2 = t1 + fadeTime; const wchar_t *fade_inout = inout > 0 ? L"out" : L"in"; if (t > my xmax) { t = my xmax; if (inout <= 0) { // fade in Melder_warning (L"The start time of the fade-in is after the end time of the sound. The fade-in will not happen."); return; } } else if (t < my xmin) { t = my xmin; if (inout > 0) { // fade out Melder_warning (L"The start time of the fade-out is before the start time of the sound. The fade-out will not happen."); return; } } if (fadeTime < 0) { t1 = t + fadeTime; t2 = t; } else if (fadeTime > 0) { t1 = t; t2 = t + fadeTime; } else { Melder_warning (L"You have given a \"Fade time\" of zero seconds. The fade-", fade_inout, L"will not happen."); return; } long i0 = 0, iystart, iyend; if (channel == 0) { // all iystart = 1; iyend = my ny; } else if (channel == 2) { // right iystart = iyend = my ny < 2 ? 1 : 2; } else { // left and other cases iystart = iyend = 1; // default channel 1 } long istart = Sampled_xToNearestIndex (me, t1); if (istart < 1) { istart = 1; } if (istart >= my nx) { Melder_warning (L"The part to fade ", fade_inout, L" lies after the end time of the sound. The fade-", fade_inout, L" will not happen."); return; } long iend = Sampled_xToNearestIndex (me, t2); if (iend <= 1) { Melder_warning (L"The part to fade ", fade_inout, L" lies before the start time of the sound. Fade-", fade_inout, L" will be incomplete."); return; } if (iend > my nx) { iend = my nx; } if (iend - istart + 1 >= numberOfSamples) { numberOfSamples = iend - istart + 1; } else { // If the start of the fade is before xmin, arrange starting phase. // The end of the fade after xmax presents no problems (i0 = 0). if (fadeTime < 0) { i0 = numberOfSamples - (iend - istart + 1); } Melder_warning (L"The fade time is larger than the part of the sound to fade ", fade_inout, L". Fade-", fade_inout, L" will be incomplete."); } for (long ichannel = iystart; ichannel <= iyend; ichannel++) { for (long i = istart; i <= iend; i++) { double cosp = cos (NUMpi * (i0 + i - istart) / (numberOfSamples - 1)); if (inout <= 0) { cosp = -cosp; // fade-in } my z[ichannel][i] *= 0.5 * (1 + cosp); } if (fadeGlobal) { if (inout <= 0) { for (long i = 1; i < istart; i++) { my z[ichannel][i] = 0; } } else { for (long i = iend; i < my nx; i++) { my z[ichannel][i] = 0; } } } } } /* 1; rect 2:hamming 3: bartlet 4: welch 5: hanning 6:gaussian */ Sound Sound_createFromWindowFunction (double windowDuration, double samplingFrequency, int windowType) { try { autoSound me = Sound_createSimple (1, windowDuration, samplingFrequency); for (long i = 1; i <= my nx; i ++) { double phase = (my x1 + (i - 1) * my dx) / windowDuration; double value; switch (windowType) { case 1: value = 1.0; break; case 2: /* Hamming */ value = 0.54 - 0.46 * cos (2.0 * NUMpi * phase); break; case 3: /* Bartlett */ value = 1.0 - fabs ( (2.0 * phase - 1.0)); break; case 4: /* Welch */ value = 1.0 - (2.0 * phase - 1.0) * (2.0 * phase - 1.0); break; case 5: /* Hanning */ value = 0.5 * (1.0 - cos (2.0 * NUMpi * phase)); break; case 6: { /* Gaussian */ double edge = exp (-12.0); phase -= 0.5; /* -0.5 .. +0.5 */ value = (exp (-48.0 * phase * phase) - edge) / (1.0 - edge); break; } break; default: value = 1.0; } my z[1][i] = value; } return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from window function."); } } /* y[n] = sum(i=-n, i=n, x[n+mi])/(2*n+1) */ Sound Sound_localAverage (Sound me, double averagingInterval, int windowType) { try { double windowDuration = windowType == 6 ? 2 * averagingInterval : averagingInterval; autoSound thee = Data_copy (me); autoSound window = Sound_createFromWindowFunction (windowDuration, 1 / my dx, windowType); long nswindow2 = window -> nx / 2; long nswindow2p = (window -> nx - 1) / 2; // nx is odd: one sample less in the forward direction if (nswindow2 < 1) { return thee.transfer(); } double *w = window -> z[1]; for (long k = 1; k <= thy ny; k++) { for (long i = 1; i <= my nx; i++) { double sum = 0, wsum = 0; long m = (nswindow2 + 1 - i + 1) < 1 ? 1 : (nswindow2 + 1 - i + 1); long jfrom = (i - nswindow2) < 1 ? 1 : (i - nswindow2); long jto = (i + nswindow2p) > my nx ? my nx : (i + nswindow2p); for (long j = jfrom; j <= jto; j++, m++) { sum += my z[k][j] * w[m]; wsum += w[m]; } thy z[k][i] = sum / wsum; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Sound (local average) created."); } } static void _Sound_garnish (Sound me, Graphics g, double tmin, double tmax, double minimum, double maximum) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Time (s)"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_setWindow (g, tmin, tmax, minimum - (my ny - 1) * (maximum - minimum), maximum); Graphics_markLeft (g, minimum, 1, 1, 0, NULL); Graphics_markLeft (g, maximum, 1, 1, 0, NULL); if (minimum != 0.0 && maximum != 0.0 && (minimum > 0.0) != (maximum > 0.0)) { Graphics_markLeft (g, 0.0, 1, 1, 1, NULL); } if (my ny == 2) { Graphics_setWindow (g, tmin, tmax, minimum, maximum + (my ny - 1) * (maximum - minimum)); Graphics_markRight (g, minimum, 1, 1, 0, NULL); Graphics_markRight (g, maximum, 1, 1, 0, NULL); if (minimum != 0.0 && maximum != 0.0 && (minimum > 0.0) != (maximum > 0.0)) { Graphics_markRight (g, 0.0, 1, 1, 1, NULL); } } } static void _Sound_getWindowExtrema (Sound me, double *tmin, double *tmax, double *minimum, double *maximum, long *ixmin, long *ixmax) { if (*tmin == *tmax) { *tmin = my xmin; *tmax = my xmax; } Matrix_getWindowSamplesX (me, *tmin, *tmax, ixmin, ixmax); if (*minimum == *maximum) { Matrix_getWindowExtrema (me, *ixmin, *ixmax, 1, my ny, minimum, maximum); if (*minimum == *maximum) { *minimum -= 1.0; *maximum += 1.0; } } } /* Given sample numbers isample and isample+1, where the formula evaluates to the booleans left and right, respectively. We want to find the point in this interval where the formula switches from true to false. The x-value of the best point is approximated by a number of bisections. It is essential that the intermediate interpolated y-values are always between the values at points isample and isample+1. We cannot use a sinc-interpolation because at strong amplitude changes high-frequency oscilations may occur. (may be leave out the interpolation and just use Vector_VALUE_INTERPOLATION_LINEAR only?) */ static void Sound_findIntermediatePoint_bs (Sound me, long ichannel, long isample, bool left, bool right, const wchar_t *formula, Interpreter interpreter, int interpolation, long numberOfBisections, double *x, double *y) { if (left) { *x = Matrix_columnToX (me, isample); *y = my z[ichannel][isample]; } else { *x = Matrix_columnToX (me, isample + 1); *y = my z[ichannel][isample + 1]; } if ( (left && right) || (!left && !right)) { Melder_throw ("Invalid situation."); } if (numberOfBisections < 1) { return; } long nx = 3; double dx = my dx / 2; double xleft = Matrix_columnToX (me, isample); autoSound thee = Sound_create (my ny, my xmin, my xmax, nx, dx, xleft); // my domain ! for (long channel = 1; channel <= my ny; channel++) { thy z[channel][1] = my z[channel][isample]; thy z[channel][3] = my z[channel][isample + 1]; } Formula_compile (interpreter, thee.peek(), formula, kFormula_EXPRESSION_TYPE_NUMERIC, true); // bisection to find optimal x and y long istep = 1; double xright = xleft + my dx, xmid; // !! do { xmid = (xleft + xright) / 2; for (long channel = 1; channel <= my ny; channel++) { thy z[channel][2] = Vector_getValueAtX (me, xmid, channel, interpolation); } // Only thy x1 and thy dx have changed; It seems we don't have to recompile. struct Formula_Result result; Formula_run (ichannel, 2, & result); bool current = result.result.numericResult; dx /= 2; if ( (left && current) || (! left && ! current)) { xleft = xmid; left = current; for (long channel = 1; channel <= my ny; channel++) { thy z[channel][1] = thy z[channel][2]; } thy x1 = xleft; } else if ( (left && ! current) || (!left && current)) { xright = xmid; right = current; for (long channel = 1; channel <= my ny; channel++) { thy z[channel][3] = thy z[channel][2]; } } else { // we should not even be here. break; } thy xmin = xleft - dx / 2; thy xmax = xright + dx / 2; thy dx = dx; istep ++; } while (istep < numberOfBisections); *x = xmid; *y = thy z[ichannel][2]; } void Sound_drawWhere (Sound me, Graphics g, double tmin, double tmax, double minimum, double maximum, bool garnish, const wchar_t *method, long numberOfBisections, const wchar_t *formula, Interpreter interpreter) { Formula_compile (interpreter, me, formula, kFormula_EXPRESSION_TYPE_NUMERIC, true); long ixmin, ixmax; _Sound_getWindowExtrema (me, &tmin, &tmax, &minimum, &maximum, &ixmin, &ixmax); // Set coordinates for drawing. Graphics_setInner (g); struct Formula_Result result; for (long channel = 1; channel <= my ny; channel ++) { Graphics_setWindow (g, tmin, tmax, minimum - (my ny - channel) * (maximum - minimum), maximum + (channel - 1) * (maximum - minimum)); if (wcsstr (method, L"bars") || wcsstr (method, L"Bars")) { for (long ix = ixmin; ix <= ixmax; ix ++) { Formula_run (channel, ix, & result); if (result.result.numericResult) { double x = Sampled_indexToX (me, ix); double y = my z [channel] [ix]; double left = x - 0.5 * my dx, right = x + 0.5 * my dx; if (y > maximum) { y = maximum; } if (left < tmin) { left = tmin; } if (right > tmax) { right = tmax; } Graphics_line (g, left, y, right, y); Graphics_line (g, left, y, left, minimum); Graphics_line (g, right, y, right, minimum); } } } else if (wcsstr (method, L"poles") || wcsstr (method, L"Poles")) { for (long ix = ixmin; ix <= ixmax; ix ++) { Formula_run (channel, ix, & result); if (result.result.numericResult) { double x = Sampled_indexToX (me, ix); double y = my z[channel][ix]; if (y > maximum) { y = maximum; } if (y < minimum) { y = minimum; } Graphics_line (g, x, 0, x, y); } } } else if (wcsstr (method, L"speckles") || wcsstr (method, L"Speckles")) { for (long ix = ixmin; ix <= ixmax; ix ++) { Formula_run (channel, ix, & result); if (result.result.numericResult) { double x = Sampled_indexToX (me, ix); Graphics_fillCircle_mm (g, x, my z [channel] [ix], 1.0); } } } else { // The default: draw as a curve. bool current = true, previous = true; long istart = ixmin; double xb = Sampled_indexToX (me, ixmin), yb = my z[channel][ixmin], xe, ye; for (long ix = ixmin; ix <= ixmax; ix++) { Formula_run (channel, ix, & result); current = result.result.numericResult; // true means draw if (previous && not current) { // leaving drawing segment if (ix != ixmin) { if (ix - istart > 1) { xe = Matrix_columnToX (me, istart); ye = my z[channel][istart]; Graphics_line (g, xb, yb, xe, ye); xb = xe; xe = Matrix_columnToX (me, ix - 1); Graphics_function (g, my z[channel], istart, ix - 1, xb, xe); xb = xe; yb = my z[channel][ix - 1]; } Sound_findIntermediatePoint_bs (me, channel, ix - 1, previous, current, formula, interpreter, Vector_VALUE_INTERPOLATION_LINEAR, numberOfBisections, &xe, &ye); Graphics_line (g, xb, yb, xe, ye); Formula_compile (interpreter, me, formula, kFormula_EXPRESSION_TYPE_NUMERIC, true); } } else if (current && not previous) { // entry drawing segment istart = ix; Sound_findIntermediatePoint_bs (me, channel, ix - 1, previous, current, formula, interpreter, Vector_VALUE_INTERPOLATION_LINEAR, numberOfBisections, &xb, &yb); xe = Sampled_indexToX (me, ix), ye = my z[channel][ix]; Graphics_line (g, xb, yb, xe, ye); xb = xe; yb = ye; Formula_compile (interpreter, me, formula, kFormula_EXPRESSION_TYPE_NUMERIC, true); } else if (previous && current && ix == ixmax) { xe = Matrix_columnToX (me, istart); ye = my z[channel][istart]; Graphics_line (g, xb, yb, xe, ye); xb = xe; xe = Matrix_columnToX (me, ix); Graphics_function (g, my z[channel], istart, ix, xb, xe); xb = xe; yb = my z[channel][ix]; } previous = current; } } } Graphics_setWindow (g, tmin, tmax, minimum, maximum); if (garnish && my ny == 2) { Graphics_line (g, tmin, 0.5 * (minimum + maximum), tmax, 0.5 * (minimum + maximum)); } Graphics_unsetInner (g); if (garnish) { _Sound_garnish (me, g, tmin, tmax, minimum, maximum); } } void Sound_paintWhere (Sound me, Graphics g, Graphics_Colour colour, double tmin, double tmax, double minimum, double maximum, double level, bool garnish, long numberOfBisections, const wchar_t *formula, Interpreter interpreter) { try { long ixmin, ixmax; struct Formula_Result result; Formula_compile (interpreter, me, formula, kFormula_EXPRESSION_TYPE_NUMERIC, true); _Sound_getWindowExtrema (me, &tmin, &tmax, &minimum, &maximum, &ixmin, &ixmax); Graphics_setColour (g, colour); Graphics_setInner (g); for (long channel = 1; channel <= my ny; channel++) { Graphics_setWindow (g, tmin, tmax, minimum - (my ny - channel) * (maximum - minimum), maximum + (channel - 1) * (maximum - minimum)); bool current, previous = true, fill = false; // fill only when leaving area double tmini = tmin, tmaxi = tmax, xe, ye; long ix = ixmin; do { Formula_run (channel, ix, & result); current = result.result.numericResult; if (ix == ixmin) { previous = current; } if (previous != current) { Sound_findIntermediatePoint_bs (me, channel, ix - 1, previous, current, formula, interpreter, Vector_VALUE_INTERPOLATION_LINEAR, numberOfBisections, &xe, &ye); if (current) { // entering painting area tmini = xe; } else { //leaving painting area tmaxi = xe; fill = true; } Formula_compile (interpreter, me, formula, kFormula_EXPRESSION_TYPE_NUMERIC, true); } if (ix == ixmax && current) { tmaxi = tmax; fill = true; } if (fill) { autoPolygon him = Sound_to_Polygon (me, channel, tmini, tmaxi, minimum, maximum, level); Graphics_fillArea (g, his numberOfPoints, &his x[1], &his y[1]); fill = false; } previous = current; } while (++ix <= ixmax); } Graphics_setWindow (g, tmin, tmax, minimum, maximum); if (garnish && my ny == 2) { Graphics_line (g, tmin, 0.5 * (minimum + maximum), tmax, 0.5 * (minimum + maximum)); } Graphics_unsetInner (g); if (garnish) { _Sound_garnish (me, g, tmin, tmax, minimum, maximum); } } catch (MelderError) { Melder_clearError (); } } void Sounds_paintEnclosed (Sound me, Sound thee, Graphics g, Graphics_Colour colour, double tmin, double tmax, double minimum, double maximum, bool garnish) { try { long ixmin, ixmax, numberOfChannels = my ny > thy ny ? my ny : thy ny; double min1 = minimum, max1 = maximum, tmin1 = tmin, tmax1 = tmax; double min2 = min1, max2 = max1, tmin2 = tmin1, tmax2 = tmax1; double xmin = my xmin > thy xmin ? my xmin : thy xmin; double xmax = my xmax < thy xmax ? my xmax : thy xmax; if (xmax <= xmin) { return; } if (tmin >= tmax) { tmin = xmin; tmax = xmax; } _Sound_getWindowExtrema (thee, &tmin1, &tmax1, &min1, &max1, &ixmin, &ixmax); _Sound_getWindowExtrema (me, &tmin2, &tmax2, &min2, &max2, &ixmin, &ixmax); minimum = min1 < min2 ? min1 : min2; maximum = max1 > max2 ? max1 : max2; Graphics_setColour (g, colour); Graphics_setInner (g); for (long channel = 1; channel <= numberOfChannels; channel++) { autoPolygon him = Sounds_to_Polygon_enclosed (me, thee, channel, tmin, tmax, minimum, maximum); Graphics_setWindow (g, tmin, tmax, minimum - (numberOfChannels - channel) * (maximum - minimum), maximum + (channel - 1) * (maximum - minimum)); Graphics_fillArea (g, his numberOfPoints, &his x[1], &his y[1]); } Graphics_setWindow (g, tmin, tmax, minimum, maximum); if (garnish && (my ny == 2 || thy ny == 2)) { Graphics_line (g, tmin, 0.5 * (minimum + maximum), tmax, 0.5 * (minimum + maximum)); } Graphics_unsetInner (g); if (garnish) { _Sound_garnish (my ny == 2 ? me : thee, g, tmin, tmax, minimum, maximum); } } catch (MelderError) { Melder_clearError (); } } /* End of file Sound_extensions.cpp 2099*/ sources_5316/dwtools/Procrustes_def.h0000644000176700017670000000210611627250650016561 0ustar paulpaul/* Procrustes_def.h * * Copyright (C) 1993-2005 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Procrustes oo_DEFINE_CLASS (Procrustes, AffineTransform) oo_DOUBLE (s) #if oo_DECLARING // overridden methods: virtual void v_transform (double **in, long nrows, double **out); virtual Any v_invert (); #endif oo_END_CLASS (Procrustes) #undef ooSTRUCT /* End of file Procrustes_def.h */ sources_5316/dwtools/ClassificationTable.cpp0000644000176700017670000001022511627172672020040 0ustar paulpaul/* ClassificationTable.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 1998 djmw 20020315 GPL header djmw 20040422 Added ClassificationTable_to_Categories_maximumProbability djmw 20040623 Added ClassificationTable_to_Strings_maximumProbability djmw 20040824 Added Strings_extensions.h header djmw 20101122 ClassificationTable_to_Correlation_columns djmw 20110304 Thing_new */ #include "ClassificationTable.h" #include "Strings_extensions.h" #include "NUM2.h" Thing_implement (ClassificationTable, TableOfReal, 0); ClassificationTable ClassificationTable_create (long numberOfRows, long numberOfGroups) { try { autoClassificationTable me = Thing_new (ClassificationTable); TableOfReal_init (me.peek(), numberOfRows, numberOfGroups); return me.transfer(); } catch (MelderError) { Melder_throw ("ClassificationTable not created."); } } Confusion ClassificationTable_to_Confusion (ClassificationTable me) { try { autoCategories c1 = TableOfReal_to_CategoriesRow (me); autoCategories c2 = ClassificationTable_to_Categories_maximumProbability (me); autoConfusion thee = Categories_to_Confusion (c1.peek(), c2.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": confusions cannot be calculated."); } } Strings ClassificationTable_to_Strings_maximumProbability (ClassificationTable me) { try { autoStrings thee = Strings_createFixedLength (my numberOfRows); for (long i = 1; i <= my numberOfRows; i++) { double max = my data[i][1]; long col = 1; for (long j = 2; j <= my numberOfColumns; j++) { if (my data[i][j] > max) { max = my data[i][j]; col = j; } } if (my columnLabels[col] != 0) { Strings_setString (thee.peek(), my columnLabels[col], i); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": strings cannot be created."); } } Categories ClassificationTable_to_Categories_maximumProbability (ClassificationTable me) { try { autoCategories thee = Categories_create (); for (long i = 1; i <= my numberOfRows; i++) { double max = my data[i][1]; long col = 1; for (long j = 2; j <= my numberOfColumns; j++) { if (my data[i][j] > max) { max = my data[i][j]; col = j; } } OrderedOfString_append (thee.peek(), my columnLabels[col]); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Categories created."); } } Correlation ClassificationTable_to_Correlation_columns (ClassificationTable me) { try { autoCorrelation thee = Correlation_create (my numberOfColumns); for (long icol = 1; icol <= thy numberOfColumns; icol++) { wchar_t *label = my columnLabels[icol]; TableOfReal_setRowLabel (thee.peek(), icol, label); TableOfReal_setColumnLabel (thee.peek(), icol, label); } for (long irow = 1; irow <= thy numberOfColumns; irow++) { thy data[irow][irow] = 1; for (long icol = irow + 1; icol <= thy numberOfColumns; icol++) { double n11 = 0, n22 = 0, n12 = 0; for (long i = 1; i <= my numberOfRows; i++) { n12 += my data[i][irow] * my data[i][icol]; n11 += my data[i][irow] * my data[i][irow]; n22 += my data[i][icol] * my data[i][icol]; } // probabilities might be very low! if (n12 > 0 && n22 > 0) { thy data[irow][icol] = thy data[icol][irow] = n12 / sqrt (n11 * n22); } } } thy numberOfObservations = my numberOfRows; return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no correlation created."); } } /* End of file ClassificationTable.cpp */ sources_5316/dwtools/Discriminant.h0000644000176700017670000000744311627174633016235 0ustar paulpaul#ifndef _Discriminant_h_ #define _Discriminant_h_ /* Discriminant.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Graphics.h" #include "Configuration.h" #include "ClassificationTable.h" #include "Eigen.h" #include "SSCP.h" #include "Discriminant_def.h" oo_CLASS_CREATE (Discriminant, Eigen); Discriminant Discriminant_create (long numberOfGroups, long numberOfEigenvalues, long dimension); long Discriminant_groupLabelToIndex (Discriminant me, const wchar_t *label); void Discriminant_setAprioriProbability (Discriminant me, long group, double p); long Discriminant_getNumberOfGroups (Discriminant me); long Discriminant_getNumberOfObservations (Discriminant me, long group); long Discriminant_getNumberOfFunctions (Discriminant me); double Discriminant_getWilksLambda (Discriminant me, long numberOfDimensions); void Discriminant_getPartialDiscriminationProbability (Discriminant me, long numberOfDimensions, double *probability, double *chisq, long *ndf); double Discriminant_getConcentrationEllipseArea (Discriminant me, long group, double scale, int confidence, int discriminantDirections, long d1, long d2); double Discriminant_getLnDeterminant_group (Discriminant me, long group); double Discriminant_getLnDeterminant_total (Discriminant me); void Discriminant_drawTerritorialMap (Discriminant me, Graphics g, int discriminantDirections, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int poolCovarianceMatrices, int garnish); void Discriminant_drawConcentrationEllipses (Discriminant me, Graphics g, double scale, int confidence, wchar_t *label, int discriminantDirections, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish); TableOfReal Discriminant_extractCoefficients (Discriminant me, int choice); TableOfReal Discriminant_extractGroupCentroids (Discriminant me); TableOfReal Discriminant_extractGroupStandardDeviations (Discriminant me); SSCP Discriminant_extractPooledWithinGroupsSSCP (Discriminant me); SSCP Discriminant_extractWithinGroupSSCP (Discriminant me, long index); SSCP Discriminant_extractBetweenGroupsSSCP (Discriminant me); Strings Discriminant_extractGroupLabels (Discriminant me); void Discriminant_setGroupLabels (Discriminant me, Strings thee); Configuration Discriminant_and_TableOfReal_to_Configuration (Discriminant me, TableOfReal thee, long numberOfDimensions); ClassificationTable Discriminant_and_TableOfReal_to_ClassificationTable (Discriminant me, TableOfReal thee, int poolCovarianceMatrices, int useAprioriProbabilities); ClassificationTable Discriminant_and_TableOfReal_to_ClassificationTable_dw (Discriminant me, TableOfReal thee, int poolCovarianceMatrices, int useAprioriProbabilities, double alpha, double minProb, TableOfReal *displacements); TableOfReal Discriminant_and_TableOfReal_mahalanobis (Discriminant me, TableOfReal thee, long group, bool poolCovarianceMatrices); /* Mahalanobis distance with respect to group mean */ Discriminant TableOfReal_to_Discriminant (I); Configuration TableOfReal_to_Configuration_lda (TableOfReal me, long numberOfDimensions); #endif /* _Discriminant_h_ */ sources_5316/dwtools/Matrix_extensions.cpp0000644000176700017670000002326011744262636017663 0ustar paulpaul/* Matrix_extensions.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20040226 Matrix_drawAsSquares: respect the colour environment (fill with current colour). djmw 20041110 Matrix_drawDistribution did't draw lowest bin correctly. djmw 20050221 Matrix_drawDistribution would draw outside window. djmw 20050405 Matrix_drawDistribution crashed if minimum > data minimum5 djmw 20080122 float -> double */ #include "Matrix_extensions.h" #include "Eigen.h" #include "NUM2.h" void Matrix_scatterPlot (I, Graphics g, long icx, long icy, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { iam (Matrix); long ix = labs (icx), iy = labs (icy); if (ix < 1 || ix > my nx || iy < 1 || iy > my nx) { return; } if (xmax <= xmin) { (void) Matrix_getWindowExtrema (me, ix, ix, 1, my ny, & xmin, & xmax); if (xmax <= xmin) { xmin -= 0.5; xmax += 0.5; } } if (ymax <= ymin) { (void) Matrix_getWindowExtrema (me, iy, iy, 1, my ny, & ymin, & ymax); if (ymax <= ymin) { ymin -= 0.5; ymax += 0.5; } } Graphics_setInner (g); if (icx < 0) { double t = xmin; xmin = xmax; xmax = t; } if (icy < 0) { double t = ymin; ymin = ymax; ymax = t; } Graphics_setWindow (g, xmin, xmax, ymin, ymax); for (long i = 1; i <= my ny; i++) { if (my z[i][ix] >= xmin && my z[i][ix] <= xmax && my z[i][iy] >= ymin && my z[i][iy] <= ymax) { Graphics_mark (g, my z[i][ix], my z[i][iy], size_mm, mark); } } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); if (ymin * ymax < 0.0) { Graphics_markLeft (g, 0.0, 1, 1, 1, NULL); } Graphics_marksBottom (g, 2, 1, 1, 0); if (xmin * xmax < 0.0) { Graphics_markBottom (g, 0.0, 1, 1, 1, NULL); } } } void Matrix_drawAsSquares (I, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish) { iam (Matrix); Graphics_Colour colour = Graphics_inqColour (g); long ixmin, ixmax, iymin, iymax; if (xmax <= xmin) { xmin = my xmin; xmax = my xmax; } long nx = Matrix_getWindowSamplesX (me, xmin, xmax, &ixmin, &ixmax); if (ymax <= ymin) { ymin = my ymin; ymax = my ymax; } long ny = Matrix_getWindowSamplesY (me, ymin, ymax, &iymin, &iymax); double min, max = nx > ny ? nx : ny; double dx = (xmax - xmin) / max, dy = (ymax - ymin) / max; Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Matrix_getWindowExtrema (me, ixmin, ixmax, iymin, iymax, & min, & max); double wAbsMax = fabs (max) > fabs (min) ? fabs (max) : fabs (min); for (long i = iymin; i <= iymax; i++) { double y = Matrix_rowToY (me, i); for (long j = ixmin; j <= ixmax; j++) { double x = Matrix_columnToX (me, j); double d = 0.95 * sqrt (fabs (my z[i][j]) / wAbsMax); double x1WC = x - d * dx / 2, x2WC = x + d * dx / 2; double y1WC = y - d * dy / 2, y2WC = y + d * dy / 2; if (my z[i][j] > 0) { Graphics_setColour (g, Graphics_WHITE); } Graphics_fillRectangle (g, x1WC, x2WC, y1WC, y2WC); Graphics_setColour (g, colour); Graphics_rectangle (g, x1WC, x2WC , y1WC, y2WC); } } Graphics_setGrey (g, 0.0); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); if (ymin * ymax < 0.0) { Graphics_markLeft (g, 0.0, 1, 1, 1, NULL); } Graphics_marksBottom (g, 2, 1, 1, 0); if (xmin * xmax < 0.0) { Graphics_markBottom (g, 0.0, 1, 1, 1, NULL); } } } void Matrix_scale (I, int choice) { iam (Matrix); double min, max, extremum; long nZero = 0; if (choice == 2) { /* by row */ for (long i = 1; i <= my ny; i++) { Matrix_getWindowExtrema (me, 1, my nx, i, i, &min, &max); extremum = fabs (max) > fabs (min) ? fabs (max) : fabs (min); if (extremum == 0.0) { nZero++; } else for (long j = 1; j <= my nx; j++) { my z[i][j] /= extremum; } } } else if (choice == 3) { /* by col */ for (long j = 1; j <= my nx; j++) { Matrix_getWindowExtrema (me, j, j, 1, my ny, &min, &max); extremum = fabs (max) > fabs (min) ? fabs (max) : fabs (min); if (extremum == 0.0) { nZero++; } else for (long i = 1; i <= my ny; i++) { my z[i][j] /= extremum; } } } else if (choice == 1) { /* overall */ Matrix_getWindowExtrema (me, 1, my nx, 1, my ny, &min, &max); extremum = fabs (max) > fabs (min) ? fabs (max) : fabs (min); if (extremum == 0.0) { nZero++; } else { for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) { my z[i][j] /= extremum; } } } } else { Melder_flushError ("Matrix_scale: choice must be >= 0 && < 3."); return; } if (nZero) { Melder_warning (L"Matrix_scale: extremum == 0, (part of) matrix unscaled."); } } Matrix Matrix_transpose (I) { iam (Matrix); try { autoMatrix thee = Matrix_create (my ymin, my ymax, my ny, my dy, my y1, my xmin, my xmax, my nx, my dx, my x1); for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) { thy z[j][i] = my z[i][j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not transposed."); } } void Matrix_drawDistribution (I, Graphics g, double xmin, double xmax, double ymin, double ymax, double minimum, double maximum, long nBins, double freqMin, double freqMax, int cumulative, int garnish) { iam (Matrix); if (nBins <= 0) { return; } if (xmax <= xmin) { xmin = my xmin; xmax = my xmax; } if (ymax <= ymin) { ymin = my ymin; ymax = my ymax; } long ixmin, ixmax, iymin, iymax; if (Matrix_getWindowSamplesX (me, xmin, xmax, & ixmin, & ixmax) == 0 || Matrix_getWindowSamplesY (me, ymin, ymax, & iymin, & iymax) == 0) { return; } if (maximum <= minimum) Matrix_getWindowExtrema (me, ixmin, ixmax, iymin, iymax, & minimum, & maximum); if (maximum <= minimum) { minimum -= 1.0; maximum += 1.0; } /* Count the numbers per bin and the total */ if (nBins < 1) { nBins = 10; } autoNUMvector freq (1, nBins); double binWidth = (maximum - minimum) / nBins; long nxy = 0; for (long i = iymin; i <= iymax; i++) { for (long j = ixmin; j <= ixmax; j++) { long bin = 1 + floor ( (my z[i][j] - minimum) / binWidth); if (bin <= nBins && bin > 0) { freq[bin]++; nxy ++; } } } if (freqMax <= freqMin) { if (cumulative) { freqMin = 0; freqMax = 1.0; } else { NUMvector_extrema (freq.peek(), 1, nBins, & freqMin, & freqMax); if (freqMax <= freqMin) { freqMin = freqMin > 1 ? freqMin - 1 : 0; freqMax += 1.0; } } } Graphics_setInner (g); Graphics_setWindow (g, minimum, maximum, freqMin, freqMax); double fi = 0; for (long i = 1; i <= nBins; i++) { double ftmp = freq[i]; fi = cumulative ? fi + freq[i] / nxy : freq[i]; ftmp = fi; if (ftmp > freqMax) { ftmp = freqMax; } if (ftmp > freqMin) Graphics_rectangle (g, minimum + (i - 1) * binWidth, minimum + i * binWidth, freqMin, ftmp); } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); if (! cumulative) { Graphics_textLeft (g, 1, L"Number/bin"); } } } void Matrix_drawSliceY (I, Graphics g, double x, double ymin, double ymax, double min, double max) { iam (Matrix); if (x < my xmin || x > my xmax) { return; } long ix = Matrix_xToNearestColumn (me, x); if (ymax <= ymin) { ymin = my ymin; ymax = my ymax; } long iymin, iymax; long ny = Matrix_getWindowSamplesY (me, ymin, ymax, &iymin, &iymax); if (ny < 1) { return; } if (max <= min) { Matrix_getWindowExtrema (me, ix, ix, iymin, iymax, &min, &max); } if (max <= min) { min -= 0.5; max += 0.5; } autoNUMvector y (iymin, iymax); Graphics_setWindow (g, ymin, ymax, min, max); Graphics_setInner (g); for (long i = iymin; i <= iymax; i++) { y[i] = my z[i][ix]; } Graphics_function (g, y.peek(), iymin, iymax, Matrix_rowToY (me, iymin), Matrix_rowToY (me, iymax)); Graphics_unsetInner (g); } Matrix Matrix_solveEquation (I, double tolerance) { try { iam (Matrix); long nr = my ny, nc = my nx - 1; if (nc == 0) { Melder_throw ("Matrix_solveEquation: there must be at least 2 columns in the matrix."); } if (nr < nc) { Melder_warning (L"Matrix_solveEquation: solution is not unique (fewer equations than unknowns)."); } autoNUMmatrix u (1, nr, 1, nc); autoNUMvector b (1, nr); autoNUMvector x (1, nc); autoMatrix thee = Matrix_create (0.5, 0.5 + nc, nc, 1, 1, 0.5, 1.5, 1, 1, 1); for (long i = 1; i <= nr; i++) { for (long j = 1; j <= nc; j++) { u[i][j] = my z[i][j]; } b[i] = my z[i][my nx]; } NUMsolveEquation (u.peek(), nr, nc, b.peek(), 0, x.peek()); for (long j = 1; j <= nc; j++) { thy z[1][j] = x[j]; } return thee.transfer(); } catch (MelderError) { Melder_throw ("Matrix equation not solved."); } } /* End of file Matrix_extensions.cpp */ sources_5316/dwtools/KlattTable.cpp0000644000176700017670000101365311634072437016171 0ustar paulpaul/* KlattTable.cpp * * Copyright (C) 2008-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* The README file that accompanied the version 3.03 softare: Klatt Cascade-Parallel Formant Synthesizer v 3.03 (April 1994) -------------------------------------------------------------- Jon Iles j.p.iles@cs.bham.ac.uk Nick Ing-Simmons nicki@lobby.ti.com History ------- This file contains a version of the Klatt Cascade-Parallel Formant Speech Synthesizer. The software for this synthesizer was originally described in (1) and an updated version of the software was described in (2). The most recent version of the software synthesizer as described in (2) is commercially available from Sensimetrics Inc. (3) The code contained within this directory is a translation of the original Fortran, into C, by Dennis Klatt. In terms of the two articles referred to above, this version seems to be the mid point of the development between the two systems described. Modifications ------------- The main part of the code in this directory was posted to comp.speech in early 1993 as part of a crude text to speech conversion system. The code taken from comp.speech seemed to have been modified considerably from the original, and for use of the synthesizer in research it was necessary to "fix" the changes that had been made. The major changes that have been made are: 1. Re-introduced the parallel-only / cascade-parallel switch. This allows choice of synthesis method, either using both branches, or just using the parallel branch. 2. Correct use of bandwidth parameters. One of the cascade bandwidth parameters was being wrongly used in the parallel branch of the synthesizer. 3. Modified operation of natural voicing source. The amplitude of the natural voicing source was very much smaller than the amplitude of the impulse source, making it difficult to swap between them to evaluate the differences. 4. Removed the software synthesizer from the context of a text to speech system. The synthesizer is now a stand-alone program, accepting input as a set of parameters from a file, and allowing output to a file or to stdout. 5. Increased the number of parameters available for use in the input file. The original comp.speech software made assumptions about a number of the control parameters. To provide the greatest flexibility, these parameters have been made specific in the input file. It is important to note that the input file format is NOT compatible with that used by the software originally posted to the comp.speech news group. 6. Added command line options to control the parameters that remain constant during synthesis. 7. Added F0 flutter control, as described in (2). 8. Subsequently the code in parwave was re-written by Nick to improve efficiency, and add a more acceptable ANSI style, and generally make an elegant implementation. 9. Further re-writes have been carried out to remove all global references. All parameters are passed around in structures. 10. The facility to use a sampled natural excitation waveform has been implemented. Naturalness of the resulting synthetic speech can be greatly improved by using the glottal excitation waveform from a natural speaker, especially if it is the speaker on whose voice the synthesis is actually based. This may be obtained indirectly by inverse-filtering a vowel. 11. This synthesizer appears in modified form as part of Nick's rsynth text-to-speech system. This may be found at svr-ftp.eng.cam.ac.uk in comp.speech/sources. 12. Fixed bug to the antiresonator code that caused overflow problems when compiling on a PC 13. Various minor modifications to ensure correct compilation using Microsoft C 7.0 (tested) and Borland C (untested). 14. Modified random number generation for noise production as previously it was dependent on the size of the "long" type. Input File Format ----------------- The input file consists of a series of parameter frames. Each frame of parameters (usually) represents 10ms of audio output, although this figure can be adjusted down to 1ms per frame. The parameters in each frame are described below. To avoid confusion, note that the cascade and parallel branch of the synthesizer duplicate some of the control parameters. f0 This is the fundamental frequency (pitch) of the utterance in this case it is specified in steps of 0.1 Hz, hence 100Hz will be represented by a value of 1000. av Amplitude of voicing for the cascade branch of the synthesizer in dB0. Range 0-70, value usually 60 for a vowel sound. f1 First formant frequency in 200-1300 Hz. b1 Cascade branch bandwidth of first formant in the range 40-1000 Hz. f2 Second formant frequency in the range 550 - 3000 Hz. b2 Cascade branch bandwidth of second formant in the range 40-1000 Hz. f3 Third formant frequency in the range 1200-4999 Hz. b3 Cascade branch bandwidth of third formant in the range 40-1000 Hz. f4 Fourth formant frequency in 1200-4999 Hz. b4 Cascade branch bandwidth of fourth formant in the range 40-1000 Hz. f5 Fifth formant frequency in the range 1200-4999 Hz. b5 Cascade branch bandwidth of fifth formant in the range 40-1000 Hz. f6 Sixth formant frequency in the range 1200-4999 Hz. b6 Cascade branch bandwidth of sixth formant in the range 40-2000 Hz. fnz Frequency of the nasal zero in the range 248-528 Hz. (cascade branch only) An implementation of a Klatt cascade-parallel formant synthesizer. A re-implementation in C of Dennis Klatt's Fortran code, by: Jon Iles (j.p.iles@cs.bham.ac.uk) Nick Ing-Simmons (nicki@lobby.ti.com) This code is a slightly modified version of the code of bnz Bandwidth of the nasal zero in the range 40-1000 Hz (cascade branch only) fnp Frequency of the nasal pole in the range 248-528 Hz bnp Bandwidth of the nasal pole in the range 40-1000 Hz ah Amplitude of aspiration 0-70 dB. kopen Open quotient of voicing waveform, range 0-60, usually 30. Will influence the gravelly or smooth quality of the voice. Only works with impulse and antural simulations. For the sampled glottal excitation waveform the open quotient is fixed. aturb Amplitude of turbulence 0-80 dB. A value of 40 is useful. Can be used to simulate "breathy" voice quality. tilt Spectral tilt in dB, range 0-24. Tilts down the output spectrum. The value refers to dB down at 3Khz. Increasing the value emphasizes the low frequency content of the speech and attenuates the high frequency content. af Amplitude of frication in dB, range 0-80 (parallel branch) skew Spectral Skew - skewness of alternate periods, range 0-40 a1 Amplitude of first formant in the parallel branch, in 0-80 dB. b1p Bandwidth of the first formant in the parallel branch, in Hz. a2 Amplitude of parallel branch second formant. b2p Bandwidth of parallel branch second formant. a3 Amplitude of parallel branch third formant. b3p Bandwidth of parallel branch third formant. a4 Amplitude of parallel branch fourth formant. b4p Bandwidth of parallel branch fourth formant. a5 Amplitude of parallel branch fifth formant. b5p Bandwidth of parallel branch fifth formant. a6 Amplitude of parallel branch sixth formant. b6p Bandwidth of parallel branch sixth formant. anp Amplitude of the parallel branch nasal formant. ab Amplitude of bypass frication in dB. 0-80. avp Amplitude of voicing for the parallel branch, 0-70 dB. gain Overall gain in dB range 0-80. Command Line Options -------------------- -h Displays a help message. -i sets input filename. -o sets output filename. If output filename not specified, stdout is used. -q quiet - print no messages. -t select output waveform (RTFC !) -c select cascade-parallel configuration. Parallel only configuration is default. -n Number of formants in cascade branch. Default is 5. -s set sample rate Default is 10Khz. -f set number of milliseconds per frame. Default is 10ms per frame -v Specifies that the voicing source to be used. 1 = impulse train. 2 = natural simulation. 3 = natural samples. Default is natural voicing -V Specifies the filename for a sampled natural excitation waveform. See man page for format details. -r Output raw binary samples, rather than ASCII integer samples. 1 = high byte, low byte arrangement. 2 = low byte, high byte arrangement. -F percentage of f0 flutter Default is 0 Example Parameter File ---------------------- Some example parameter files for a short segments of speech are included in this distribution. e.g. file called example1.par. Use the following to produce the output waveforms: klatt -i example1.par -o example1.dat -f 5 -v 2 klatt -i example2.par -o example2.dat -f 5 -s 16000 -v 2 The '-r' option can be used to produce raw binary output, which can then be converted to many different formats using utilities such as 'sox' (sound exchange) which are available from major ftp sites. An example is given below of conversion to the ulaw encoded format used by Sun Sparc SLC's sox -r 16000 -s -w example.raw -r 8000 -b -U example.au Beware of the byte ordering of your machine - if the above procedure produces distored rubbish, try using -r 2 instead of -r 1. This just reverses the byte ordering in the raw binary output file. It is also worth noting that the above example reduces the quality of the output, as the sampling rate is being halved and the number of bits per sample is being halved. Ideally output should be at 16kHz with 16 bits per sample. Notes ----- This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 1, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. Bug reports, comments etc. to j.p.iles@cs.bham.ac.uk References ---------- (1) @article{klatt1980, AUTHOR = {Klatt,D.H.}, JOURNAL = {Journal of the Acoustic Society of America}, PAGES = {971--995}, TITLE = {Software for a cascade/parallel formant synthesizer}, VOLUME = {67}, NUMBER = {3}, MONTH = {March}, YEAR = 1980} (2) @Article{klatt1990, author = "Klatt,D.H. and Klatt, L.C.", title = "Analysis, synthesis and perception of voice quality variations among female and male talkers.", journal = "Journal of the Acoustical Society of America", year = "1990", volume = "87", number = "2", pages = "820--857", month = "February"} (3) Dr. David Williams at Sensimetrics Corporation, 64 Sidney Street, Cambridge, MA 02139. Fax: (617) 225-0470 Tel: (617) 225-2442 e-mail sensimetrics@sens.com */ /* djmw 20081019 first implementation. djmw 20081128 Parallel section: rnp filters dif(source)+frication instead of source only. djmw 20090708 +Table_to_KlattTable, KlattTable_to_Table djmw 20110308 Thing_new + struct KlattFrame -> struct structKlattFrame djmw 20110329 Table_get(Numeric|String)Value is now Table_get(Numeric|String)Value_Assert */ #include "KlattTable.h" #include "Resonator.h" Thing_implement (KlattTable, Table, 0); #define CASCADE_PARALLEL 1 /* Type of synthesis model */ #define ALL_PARALLEL 2 #define KlattTable_NPAR 40 /* Number of control parameters */ #define MAX_SAM 20000 /* Maximum sample rate */ #define TRUE 1 #define FALSE 0 #define IMPULSIVE 1 /* Type of voicing source */ #define NATURAL 2 #define SAMPLED 3 #define NUMBER_OF_SAMPLES 100 #define SAMPLE_FACTOR 0.00001 /* Structure for Klatt Parameters */ typedef struct structKlattFrame { long F0hz10; /* Voicing fund freq in units of 0.1 Hz */ long AVdb; /* Amp of voicing in dB, 0 to 70 */ long Fhz[9]; /* Formant freqs in Hz */ long Bhz[9]; /* bandwidths in Hz */ long Bphz[7]; /* Bandwidths, parallel branch */ long A[7]; /* Formant amplitudes parallel branch */ long FNZhz; /* Nasal zero freq in Hz, 248 to 528 */ long BNZhz; /* Nasal zero bw in Hz, 40 to 1000 */ long FNPhz; /* Nasal pole freq in Hz, 248 to 528 */ long BNPhz; /* Nasal pole bw in Hz, 40 to 1000 */ long ah; /* Amp of aspiration in dB, 0 to 70 */ long Kopen; /* # of samples in open period, 10 to 65 */ long Aturb; /* Breathiness in voicing, 0 to 80 */ long TLTdb; /* Voicing spectral tilt in dB, 0 to 24 */ long AF; /* Amp of frication in dB, 0 to 80 */ long Kskew; /* Skewness of alternate periods, 0 to 40 in sample#/2 */ long ANP; /* Amp of par nasal pole in dB, 0 to 80 */ long AB; /* Amp of bypass fric. in dB, 0 to 80 */ long AVpdb; /* Amp of voicing, par in dB, 0 to 70 */ long Gain0; /* Overall gain, 60 dB is unity, 0 to 60 */ } *KlattFrame; static const wchar_t *columnNames = L"f0 av f1 b1 f2 b2 f3 b3 f4 b4 f5 b5 f6 b6 fnz bnz fnp bnp ah kopen aturb tilt af skew a1 b1p a2 b2p a3 b3p a4 b4p a5 b5p a6 b6p anp ab avp gain"; static const wchar_t *columnNamesA[KlattTable_NPAR + 1] = {L"", L"f0", L"av", L"f1", L"b1", L"f2", L"b2", L"f3", L"b3", L"f4", L"b4", L"f5", L"b5", L"f6", L"b6", L"fnz", L"bnz", L"fnp", L"bnp", L"ah", L"kopen", L"aturb", L"tilt", L"af", L"skew", L"a1", L"b1p", L"a2", L"b2p", L"a3", L"b3p", L"a4", L"b4p", L"a5", L"b5p", L"a6", L"b6p", L"anp", L"ab", L"avp", L"gain"}; static double DBtoLIN (long dB) { static double amptable[88] = { 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 6.0, 7.0, 8.0, 9.0, 10.0, 11.0, 13.0, 14.0, 16.0, 18.0, 20.0, 22.0, 25.0, 28.0, 32.0, 35.0, 40.0, 45.0, 51.0, 57.0, 64.0, 71.0, 80.0, 90.0, 101.0, 114.0, 128.0, 142.0, 159.0, 179.0, 202.0, 227.0, 256.0, 284.0, 318.0, 359.0, 405.0, 455.0, 512.0, 568.0, 638.0, 719.0, 811.0, 911.0, 1024.0, 1137.0, 1276.0, 1438.0, 1622.0, 1823.0, 2048.0, 2273.0, 2552.0, 2875.0, 3244.0, 3645.0, 4096.0, 4547.0, 5104.0, 5751.0, 6488.0, 7291.0, 8192.0, 9093.0, 10207.0, 11502.0, 12976.0, 14582.0, 16384.0, 18350.0, 20644.0, 23429.0, 26214.0, 29491.0, 32767 }; return (dB < 0) || (dB > 87) ? 0 : amptable[dB] * .001; } /* Structure for Klatt Globals */ typedef struct structKlattGlobal { int synthesis_model; /* cascade-parallel or all-parallel */ int outsl; /* Output waveform selector */ long samrate; /* Number of output samples per second */ long FLPhz ; /* Frequeny of glottal downsample low-pass filter */ long BLPhz ; /* Bandwidth of glottal downsample low-pass filter */ long nfcascade; /* Number of formants in cascade vocal tract */ int glsource; /* Type of glottal source */ int f0_flutter; /* Percentage of f0 flutter 0-100 */ long nspfr; /* number of samples per frame */ long nper; /* Counter for number of samples in a pitch period */ long ns; long T0; /* Fundamental period in output samples times 4 */ long nopen; /* Number of samples in open phase of period */ long nmod; /* Position in period to begin noise amp. modul */ long Kopen; /* # of samples in open period, 10 to 65 */ long Kskew; /* Skewness of alternate periods, 0 to 40 in sample#/2 */ double TLTdb; /* Voicing spectral tilt in dB, 0 to 24 */ long nrand; /* Varible used by random number generator */ double pulse_shape_a; /* Makes waveshape of glottal pulse when open */ double pulse_shape_b; /* Makes waveshape of glottal pulse when open */ double onemd; double decay; double amp_bypas; /* AB converted to linear gain */ double AVdb; /* Amp of voicing in dB, 0 to 70 */ double amp_voice; /* AVdb converted to linear gain */ double par_amp_voice; /* AVpdb converted to linear gain */ double amp_aspir; /* AP converted to linear gain */ double amp_frica; /* AF converted to linear gain */ double Aturb; /* Breathiness in voicing, 0 to 80 */ double amp_breth; /* ATURB converted to linear gain */ double amp_gain0; /* G0 converted to linear gain */ long num_samples; /* number of glottal samples */ double sample_factor; /* multiplication factor for glottal samples */ short *natural_samples; /* pointer to an array of glottal samples */ long F0hz10; /* Voicing fund freq in units of 0.1 Hz */ long original_f0; /* original value of f0 not modified by flutter (kanweg) */ Resonator rp[7], rc[9], rnpp, rnpc, rgl, rlp, rout; AntiResonator rnz; } *KlattGlobal; KlattTable KlattTable_readFromRawTextFile (MelderFile fs) { try { autoMatrix thee = Matrix_readFromRawTextFile (fs); if (thy nx != KlattTable_NPAR) { Melder_throw ("A KlattTable needs ", KlattTable_NPAR, " columns."); } autoKlattTable me = Thing_new (KlattTable); Table_initWithColumnNames (me.peek(), thy ny, columnNames); for (long irow = 1; irow <= thy ny; irow++) { for (long jcol = 1; jcol <= KlattTable_NPAR; jcol++) { double val = thy z[irow][jcol]; if (jcol > 3 && jcol < 13 && (jcol % 2 == 0) && val <= 0) { // bw == 0? val = thy z[irow][jcol - 1] / 10; } Table_setNumericValue ( (Table) me.peek(), irow, jcol, val); } } return me.transfer(); } catch (MelderError) { Melder_throw ("KlattTable not read from file."); } } static void KlattGlobal_free (KlattGlobal me) { for (long i = 1; i <= 8; i++) { Melder_free (my rc[i]); if (i <= 6) { Melder_free (my rp[i]); } } Melder_free (my rnpp); Melder_free (my rnpc); Melder_free (my rnz); Melder_free (my rgl); Melder_free (my rlp); Melder_free (my rout); Melder_free (me); } static KlattGlobal KlattGlobal_create (double samplingFrequency) { KlattGlobal me = 0; try { me = (KlattGlobal) _Melder_calloc_f (1, sizeof (struct structKlattGlobal)); my samrate = samplingFrequency; double dT = 1.0 / my samrate; for (long i = 1; i <= 8; i++) { my rc[i] = Resonator_create (dT, Resonator_NORMALISATION_H0); if (i <= 6) { my rp[i] = Resonator_create (dT, Resonator_NORMALISATION_H0); } } my rnpp = Resonator_create (dT, Resonator_NORMALISATION_H0); my rnpc = Resonator_create (dT, Resonator_NORMALISATION_H0); my rgl = Resonator_create (dT, Resonator_NORMALISATION_H0); my rlp = Resonator_create (dT, Resonator_NORMALISATION_H0); my rout = Resonator_create (dT, Resonator_NORMALISATION_H0); my rnz = AntiResonator_create (dT); return me; } catch (MelderError) { KlattGlobal_free (me); Melder_throw ("KlattGlobal not created."); } } static void KlattGlobal_init (KlattGlobal me, int synthesisModel, int numberOfFormants, int glottalSource, double frameDuration, long flutter, int outputType) { static short natural_samples[NUMBER_OF_SAMPLES] = { -310, -400, 530, 356, 224, 89, 23, -10, -58, -16, 461, 599, 536, 701, 770, 605, 497, 461, 560, 404, 110, 224, 131, 104, -97, 155, 278, -154, -1165, -598, 737, 125, -592, 41, 11, -247, -10, 65, 92, 80, -304, 71, 167, -1, 122, 233, 161, -43, 278, 479, 485, 407, 266, 650, 134, 80, 236, 68, 260, 269, 179, 53, 140, 275, 293, 296, 104, 257, 152, 311, 182, 263, 245, 125, 314, 140, 44, 203, 230, -235, -286, 23, 107, 92, -91, 38, 464, 443, 176, 98, -784, -2449, -1891, -1045, -1600, -1462, -1384, -1261, -949, -730 }; my nspfr = my samrate * frameDuration; /* average number of samples per frame */ my synthesis_model = synthesisModel; my nfcascade = numberOfFormants; my glsource = glottalSource; my natural_samples = natural_samples; my num_samples = NUMBER_OF_SAMPLES; my sample_factor = (float) SAMPLE_FACTOR; my outsl = outputType; my f0_flutter = flutter; my FLPhz = 0.0950 * my samrate; // depends on samplingFrequency ???? my BLPhz = 0.0630 * my samrate; Filter_setFB (my rlp, my FLPhz, my BLPhz); } static KlattFrame KlattFrame_create () { return Melder_malloc (structKlattFrame, 1); } static void KlattFrame_free (KlattFrame me) { Melder_free (me); } KlattTable KlattTable_create (double frameDuration, double totalDuration) { try { autoKlattTable me = (KlattTable) Thing_new (KlattTable); long nrows = floor (totalDuration / frameDuration) + 1; Table_initWithColumnNames (me.peek(), nrows, columnNames); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattTable not created."); } } //static void frame_init(KlattGlobal_ptr globals, KlattFrame_ptr frame) static void KlattGlobal_getFrame (KlattGlobal me, KlattFrame thee) { double amp_parF[7] = {0, 0.4, 0.15, 0.06, 0.04, 0.022, 0.03}; my F0hz10 = thy F0hz10; my original_f0 = my F0hz10 / 10; my Kopen = thy Kopen; my Kskew = thy Kskew; my TLTdb = thy TLTdb; my Aturb = thy Aturb; my AVdb = thy AVdb; my AVdb -= 7; if (my AVdb < 0) { my AVdb = 0; } my amp_aspir = DBtoLIN (thy ah) * 0.05; my amp_frica = DBtoLIN (thy AF) * 0.25; my par_amp_voice = DBtoLIN (thy AVpdb); double amp_parFNP = DBtoLIN (thy ANP) * 0.6; my amp_bypas = DBtoLIN (thy AB) * 0.05; thy Gain0 -= 3; if (thy Gain0 <= 0) { thy Gain0 = 57; } my amp_gain0 = DBtoLIN (thy Gain0); /* Set coefficients of variable cascade resonators */ for (long i = 8; i > 0; i--) { if (my nfcascade >= i) { Filter_setFB (my rc[i], thy Fhz[i], thy Bhz[i]); } } /* Set coefficients of nasal resonator and zero antiresonator */ Filter_setFB (my rnpc, thy FNPhz, thy BNPhz); Filter_setFB (my rnz, thy FNZhz, thy BNZhz); /* Set coefficients of parallel resonators, and amplitude of outputs */ for (long i = 1; i <= 6; i++) { Filter_setFB (my rp[i], thy Fhz[i], thy Bphz[i]); my rp[i] -> a *= amp_parF[i] * DBtoLIN (thy A[i]); } Filter_setFB (my rnpp, thy FNPhz, thy BNPhz); my rnpp -> a *= amp_parFNP; /* output low-pass filter */ Filter_setFB (my rout, 0, (long) (my samrate / 2)); } /* This function adds F0 flutter, as specified in: "Analysis, synthesis and perception of voice quality variations among female and male talkers" D.H. Klatt and L.C. Klatt JASA 87(2) February 1990. Flutter is added by applying a quasi-random element constructed from three slowly varying sine waves. */ static void KlattFrame_flutter (KlattGlobal me) { static long time_count = 0; double fla = (double) my f0_flutter / 50; double flb = (double) my original_f0 / 100; double flc = sin (2 * NUMpi * 12.7 * time_count); double fld = sin (2 * NUMpi * 7.1 * time_count); double fle = sin (2 * NUMpi * 4.7 * time_count); double delta_f0 = fla * flb * (flc + fld + fle) * 10; my F0hz10 += (long) delta_f0; time_count++; } /* Random number generator (return a number between -8191 and +8191) Noise spectrum is tilted down by soft low-pass filter having a pole near the origin in the z-plane, i.e. output = input + (0.75 * lastoutput) */ static float KlattGlobal_gen_noise (KlattGlobal me) { static double nlast = 0; double noise; my nrand = ( (rand() % (int) ( ( (8191) + 1) - (-8191))) + (-8191)); noise = my nrand + (0.75 * nlast); nlast = noise; return noise; } /* Generate a low pass filtered train of impulses as an approximation of a natural excitation waveform. Low-pass filter the differentiated impulse with a critically-damped second-order filter, time constant proportional to Kopen. */ static float KlattGlobal_impulsive_source (KlattGlobal me) { static double doublet[] = {0.0, 13000000.0, -13000000.0}; static double vwave; vwave = my nper < 3 ? doublet[my nper] : 0; return Filter_getOutput (my rgl, vwave); } /* Vwave is the differentiated glottal flow waveform, there is a weak spectral zero around 800 Hz, magic constants a,b reset pitch synchronously. */ static float KlattGlobal_natural_source (KlattGlobal me) { static double vwave = 0; double lgtemp = 0; if (my nper < my nopen) { my pulse_shape_a -= my pulse_shape_b; vwave += my pulse_shape_a; lgtemp = vwave * 0.028; } else { vwave = 0.0; } return lgtemp; } /* Allows the use of a glottal excitation waveform sampled from a real voice. */ static float KlattGlobal_sampled_source (KlattGlobal me) { double result = 0; if (my T0 != 0) { double ftemp = my nper; ftemp *= my num_samples / my T0; long itemp = ftemp; double temp_diff = ftemp - itemp; long current_value = my natural_samples[itemp]; long next_value = my natural_samples[itemp + 1]; double diff_value = next_value - current_value; diff_value = diff_value * temp_diff; result = my natural_samples[itemp] + diff_value; result = result * my sample_factor; } return result; } /* Reset selected parameters pitch-synchronously. Constant B0 controls shape of glottal pulse as a function of desired duration of open phase N0 (Note that N0 is specified in terms of 40,000 samples/sec of speech) Assume voicing waveform V(t) has form: k1 t**2 - k2 t**3 If the radiation characterivative, a temporal derivative is folded in, and we go from continuous time to discrete integers n: dV/dt = vwave[n] = sum over i=1,2,...,n of { a - (i * b) } = a n - b/2 n**2 where the constants a and b control the detailed shape and amplitude of the voicing waveform over the open portion of the voicing cycle "nopen". Let integral of dV/dt have no net dc flow --> a = (b * nopen) / 3 Let maximum of dUg(n)/dn be constant --> b = gain / (nopen * nopen) meaning as nopen gets bigger, V has bigger peak proportional to n Thus, to generate the table below for 40 <= nopen <= 263: B0[nopen - 40] = 1920000 / (nopen * nopen) Modified calculation by djmw 20081127 Given a and b as above (which are wrong, see below) V'[n]= b*N/3*n - b/2*n^2. V'[N]=b/3*N^2-b/2*N^2=b/6*N^2 Given the table B0 for N=40, b=1200 and V'[N]=1200/6*(40)^2=320000 Also b=G/N^2 then V'[n]=-G/6 (=1920000/6=320000)! (We have not implemented the following correct calculations in the code) N=nopen dV/dt = vwave[n]=sum(i=1, n, a-i*b) = a*n-b*1/2*n*(n+1)=(a-b/2)*n-b/2 * n^2 (Here they forgot that sum(i=1,N,i)=1/2*n*(n+1) ! ) We want the sum(i=1,N, dV/dt[n])==0, therefore (a-b/2)*1/2*N*(N+1)-b*1/2*1/6*N*(N+1)*(2*N+1)==0. It follows that (a-b/2) - b*1/6*(2*N+1)==0 => a = b*(N+2)/3 we can rewrite with only b: V'[n] = b/2 {(2N+1)/3*n - n^2} The maximum of V'[n] is where (2N+1)/3-2n==0 => for n=(2N+1)/6 This maximum is b/2{(2N+1)/3*(2N+1)/(2*3)-((2N+1)/(2*3))^2} = 1/72*b*(2N+1)^2 The minimum is at n=N and equals V'[N]=b/6 {N-N^2}. This minimum has larger amplitude than the maximum. b = 6*gain/(N^2-N), b approx 6*gain/N^2. With a maximum gain of 32767 we arrive at b= 196602 / (N^2-N) Their value is 20*log10(1920000/196602) = 19.79 dB too high! The noise is in the range [-8192,8192], */ static void KlattGlobal_pitch_synch_par_reset (KlattGlobal me) { static long skew; static short B0[224] = { 1200, 1142, 1088, 1038, 991, 948, 907, 869, 833, 799, 768, 738, 710, 683, 658, 634, 612, 590, 570, 551, 533, 515, 499, 483, 468, 454, 440, 427, 415, 403, 391, 380, 370, 360, 350, 341, 332, 323, 315, 307, 300, 292, 285, 278, 272, 265, 259, 253, 247, 242, 237, 231, 226, 221, 217, 212, 208, 204, 199, 195, 192, 188, 184, 180, 177, 174, 170, 167, 164, 161, 158, 155, 153, 150, 147, 145, 142, 140, 137, 135, 133, 131, 128, 126, 124, 122, 120, 119, 117, 115, 113, 111, 110, 108, 106, 105, 103, 102, 100, 99, 97, 96, 95, 93, 92, 91, 90, 88, 87, 86, 85, 84, 83, 82, 80, 79, 78, 77, 76, 75, 75, 74, 73, 72, 71, 70, 69, 68, 68, 67, 66, 65, 64, 64, 63, 62, 61, 61, 60, 59, 59, 58, 57, 57, 56, 56, 55, 55, 54, 54, 53, 53, 52, 52, 51, 51, 50, 50, 49, 49, 48, 48, 47, 47, 46, 46, 45, 45, 44, 44, 43, 43, 42, 42, 41, 41, 41, 41, 40, 40, 39, 39, 38, 38, 38, 38, 37, 37, 36, 36, 36, 36, 35, 35, 35, 35, 34, 34, 33, 33, 33, 33, 32, 32, 32, 32, 31, 31, 31, 31, 30, 30, 30, 30, 29, 29, 29, 29, 28, 28, 28, 28, 27, 27 }; if (my F0hz10 > 0) { /* T0 is 4* the number of samples in one pitch period */ my T0 = (40 * my samrate) / my F0hz10; my amp_voice = DBtoLIN (my AVdb); /* Duration of period before amplitude modulation */ my nmod = my T0; if (my AVdb > 0) { my nmod >>= 1; } /* Breathiness of voicing waveform */ my amp_breth = DBtoLIN (my Aturb) * 0.1; /* Set open phase of glottal period where 40 <= open phase <= 263 */ my nopen = 4 * my Kopen; if ( (my glsource == IMPULSIVE) && (my nopen > 263)) { my nopen = 263; } if (my nopen >= (my T0 - 1)) { my nopen = my T0 - 2; Melder_warning (L"Glottal open period cannot exceed T0, truncated"); } if (my nopen < 40) { /* F0 max = 1000 Hz */ my nopen = 40; Melder_warning (L"Warning: minimum glottal open period is 10 samples.\n" "truncated, nopen = ", Melder_integer (my nopen)); } /* Reset a & b, which determine shape of "natural" glottal waveform */ my pulse_shape_b = B0[my nopen - 40]; my pulse_shape_a = (my pulse_shape_b * my nopen) * 0.333; /* Reset width of "impulsive" glottal pulse */ long temp = my samrate / my nopen; Filter_setFB (my rgl, 0, temp); // Only used for impulsive source. /* Make gain at F1 about constant */ double temp1 = my nopen * 0.00833; my rgl -> a *= temp1 * temp1; /* Truncate skewness so as not to exceed duration of closed phase of glottal period. */ temp = my T0 - my nopen; if (my Kskew > temp) { Melder_information (L"Kskew duration=", Melder_integer (my Kskew), L" > glottal closed period=", Melder_integer (my T0 - my nopen), L" truncate"); my Kskew = temp; } if (skew >= 0) { skew = my Kskew; } else { skew = - my Kskew; } /* Add skewness to closed portion of voicing period */ my T0 = my T0 + skew; skew = - skew; } else { my T0 = 4; /* Default for f0 undefined */ my amp_voice = 0.0; my nmod = my T0; my amp_breth = 0.0; my pulse_shape_a = 0.0; my pulse_shape_b = 0.0; } /* Reset these pars pitch synchronously or at update rate if f0=0 */ if ( (my T0 != 4) || (my ns == 0)) { /* Set one-pole low-pass filter that tilts glottal source */ my decay = (0.033 * my TLTdb); my onemd = my decay > 0.0 ? 1.0 - my decay : 1; } } // This is Klatt80 with improved source model. static void KlattGlobal_synthesizeFrame (KlattGlobal me, short *output) { double out, frics, glotout, aspiration, par_glotout, noise, sourc, voice = 0; static double vlast = 0, glotlast = 0; KlattFrame_flutter (me); /* MAIN LOOP, for each output sample of current frame: */ for (my ns = 0; my ns < my nspfr; my ns++) { /* Get low-passed random number for aspiration and frication noise */ noise = KlattGlobal_gen_noise (me); /* Amplitude modulate noise (reduce noise amplitude during second half of glottal period) if voicing simultaneously present. */ if (my nper > my nmod) { noise *= 0.5; } /* Compute frication noise */ frics = my amp_frica * noise; /* Compute voicing waveform. Run glottal source simulation at 4 times normal sample rate to minimize quantization noise in period of female voice. */ for (long n4 = 0; n4 < 4; n4++) { switch (my glsource) { case IMPULSIVE: voice = KlattGlobal_impulsive_source (me); break; case NATURAL: voice = KlattGlobal_natural_source (me); break; case SAMPLED: voice = KlattGlobal_sampled_source (me); break; } /* Reset period when counter 'nper' reaches T0 */ if (my nper >= my T0) { my nper = 0; KlattGlobal_pitch_synch_par_reset (me); } /* Low-pass filter voicing waveform before downsampling from 4*samrate to samrate samples/sec. Resonator f=.09*samrate, bw=.06*samrate */ voice = Filter_getOutput (my rlp, voice); /* Increment counter that keeps track of 4*samrate samples per sec */ my nper++; } /* Tilt spectrum of voicing source down by soft low-pass filtering, amount of tilt determined by TLTdb */ voice = (voice * my onemd) + (vlast * my decay); vlast = voice; /* Add breathiness during glottal open phase. Amount of breathiness determined by parameter Aturb Use nrand rather than noise because noise is low-passed. */ if (my nper < my nopen) { voice += my amp_breth * my nrand; } /* Set voicing amplitude */ glotout = my amp_voice * voice; par_glotout = my par_amp_voice * voice; /* Compute aspiration amplitude and add to voicing source */ aspiration = my amp_aspir * noise; glotout += aspiration; par_glotout += aspiration; /* Cascade vocal tract, excited by laryngeal sources. Nasal antiresonator, then formants FNP, F5, F4, F3, F2, F1 */ if (my synthesis_model != ALL_PARALLEL) { out = Filter_getOutput (my rnz, glotout); /* anti resonator */ out = Filter_getOutput (my rnpc, out); for (long i = 8; i > 0; i--) { if (my nfcascade >= i) { out = Filter_getOutput (my rc[i], out); } } } else { /* we are not using the cascade tract, set out to zero */ out = 0; } /* Excite parallel F1 and FNP by voicing waveform */ sourc = par_glotout; /* Source is voicing plus aspiration */ /* Standard parallel vocal tract Formants F6,F5,F4,F3,F2, outputs added with alternating sign. Sound sourc for other parallel resonators is frication plus first difference of voicing waveform. In Klatt80: source: through r1, diff(source)+frication: through filters rnp, r2, r3, r4 frication: through r5, r6 and ab. In the original code of Iles and Ing it was source: through r1 and rnp diff(source)+frication: r2, r3, r4 , r5, r6, ab Problem: The source signal is already v'[n], and we are differentiating here again ??? */ out += Filter_getOutput (my rp[1], sourc); sourc = frics + par_glotout - glotlast; // diff glotlast = par_glotout; out += Filter_getOutput (my rnpp, sourc); for (long i = 6; i >= 2; i--) { if (my nfcascade >= i) { out = Filter_getOutput (my rp[i], sourc) - out; } } double outbypas = my amp_bypas * sourc; out = outbypas - out; if (my outsl != 0) { switch (my outsl) { case 1: out = voice; break; case 2: out = aspiration; break; case 3: out = frics; break; case 4: out = glotout; break; case 5: out = par_glotout; break; case 6: out = outbypas; break; case 7: out = sourc; break; } } out = Filter_getOutput (my rout, out); double temp = out * my amp_gain0; /* Convert back to integer */ if (temp < -32768.0) { temp = -32768.0; } if (temp > 32767.0) { temp = 32767.0; } *output++ = temp; } } static int KlattTable_checkLimits (KlattTable me) { long nviolations_upper[KlattTable_NPAR + 1] = { 0 }, nviolations_lower[KlattTable_NPAR + 1] = { 0 }; long lower[KlattTable_NPAR + 1] = { 0, // dummy 10, 0, // f0, av 200, 40, 550, 40, 1200, 40, 1200, 40, 1200, 40, 1200, 40, // f1,b1 -- f6,b6 248, 40, 248, 40, // fnz, bnz, fnp, bnp 0, 0, 0, 0, 0, 0, // ah, kopen, aturb, tilt, af, skew 0, 40, 0, 40, 0, 40, 0, 40, 0, 40, 0, 40, // a1,b1p -- a6,b6p 0, 0, 0, 0 // anp, ab, avp, gain }; long upper[KlattTable_NPAR + 1] = { 0, // dummy 10000, 70, // f0, av 1300, 1000, 3000, 1000, 4999, 1000, 4999, 1000, 6999, 1000, 7000, 1000, // f1,b1 -- f6,b6 528, 1000, 528, 1000, // fnz, bnz, fnp, bnp 70, 60, 80, 24, 80, 40, // ah, kopen, aturb, tilt, af, skew 80, 1000, 80, 1000, 80, 1000, 80, 1000, 80, 1000, 80, 1000, // a1,b1p -- a6,b6p 80, 80, 70, 80 // anp, ab, avp, gain }; long nv = 0; for (long irow = 1; irow <= my rows -> size; irow++) { for (long j = 1; j <= KlattTable_NPAR; j++) { long val = Table_getNumericValue_Assert ( (Table) me, irow, j); if (val < lower[j]) { nviolations_lower[j]++; nv++; } else if (val > upper[j]) { nviolations_upper[j]++; nv++; } } } if (nv > 0) { MelderInfo_open (); MelderInfo_writeLine3 (L"Diagnostics for KlattTable \"", Thing_getName (me), L"\":"); MelderInfo_writeLine2 (L"Number of frames: ", Melder_integer (my rows -> size)); for (long j = 1; j <= KlattTable_NPAR; j++) { if (nviolations_lower[j] > 0) { if (nviolations_upper[j] > 0) { MelderInfo_writeLine9 (columnNamesA[j], L": ", Melder_integer (nviolations_lower[j]), L" frame(s) < min = ", Melder_integer (nviolations_lower[j]), L"; ", Melder_integer (nviolations_upper[j]), L" frame(s) > max = ", Melder_integer (upper[j])); } else { MelderInfo_writeLine5 (columnNamesA[j], L": ", Melder_integer (nviolations_lower[j]), L" frame(s) < min = ", Melder_integer (lower[j])); } } else if (nviolations_upper[j] > 0) { MelderInfo_writeLine5 (columnNamesA[j], L": ", Melder_integer (nviolations_upper[j]), L" frame(s) > max = ", Melder_integer (upper[j])); } } MelderInfo_close (); return 0; } return 1; } Sound KlattTable_to_Sound (KlattTable me, double samplingFrequency, int synthesisModel, int numberOfFormants, double frameDuration, int glottalSource, double flutter, int outputType) { KlattGlobal thee = 0; KlattFrame frame = 0; try { long numberOfSamples = 1, par[KlattTable_NPAR + 1]; if (! KlattTable_checkLimits (me)) { Melder_warning (L"Some values in the KlattTable are outside the limits, the resulting sound may sound weird."); } thee = KlattGlobal_create (samplingFrequency); frame = KlattFrame_create (); autoNUMvector iwave (0L, MAX_SAM); thy samrate = samplingFrequency; KlattGlobal_init (thee, synthesisModel, numberOfFormants, glottalSource, frameDuration, flutter, outputType); autoSound him = Sound_createSimple (1, frameDuration * my rows -> size, samplingFrequency); for (long irow = 1 ; irow <= my rows -> size; irow++) { for (long col = 1; col <= KlattTable_NPAR; col++) { par[col] = Table_getNumericValue_Assert ( (Table) me, irow, col); } long jcol = 1; frame -> F0hz10 = par[jcol++]; frame -> AVdb = par[jcol++]; frame -> Fhz[1] = par[jcol++]; frame -> Bhz[1] = par[jcol++]; frame -> Fhz[2] = par[jcol++]; frame -> Bhz[2] = par[jcol++]; frame -> Fhz[3] = par[jcol++]; frame -> Bhz[3] = par[jcol++]; frame -> Fhz[4] = par[jcol++]; frame -> Bhz[4] = par[jcol++]; frame -> Fhz[5] = par[jcol++]; frame -> Bhz[5] = par[jcol++]; frame -> Fhz[6] = par[jcol++]; frame -> Bhz[6] = par[jcol++]; frame -> FNZhz = par[jcol++]; frame -> BNZhz = par[jcol++]; frame -> FNPhz = par[jcol++]; frame -> BNPhz = par[jcol++]; frame -> ah = par[jcol++]; frame -> Kopen = par[jcol++]; frame -> Aturb = par[jcol++]; frame -> TLTdb = par[jcol++]; frame -> AF = par[jcol++]; frame -> Kskew = par[jcol++]; frame -> A[1] = par[jcol++]; frame -> Bphz[1] = par[jcol++]; frame -> A[2] = par[jcol++]; frame -> Bphz[2] = par[jcol++]; frame -> A[3] = par[jcol++]; frame -> Bphz[3] = par[jcol++]; frame -> A[4] = par[jcol++]; frame -> Bphz[4] = par[jcol++]; frame -> A[5] = par[jcol++]; frame -> Bphz[5] = par[jcol++]; frame -> A[6] = par[jcol++]; frame -> Bphz[6] = par[jcol++]; frame -> ANP = par[jcol++]; frame -> AB = par[jcol++]; frame -> AVpdb = par[jcol++]; frame -> Gain0 = par[jcol++];; frame -> Fhz[7] = 6500; frame -> Bhz[7] = 600; frame -> Fhz[8] = 7500; frame -> Bhz[8] = 600; KlattGlobal_getFrame (thee, frame); KlattGlobal_synthesizeFrame (thee, iwave.peek()); for (long isam = 0; isam < thy nspfr; isam++) { his z[1][numberOfSamples++] = iwave[isam] / 32768.0; } } KlattGlobal_free (thee); KlattFrame_free (frame); return him.transfer (); } catch (MelderError) { KlattGlobal_free (thee); KlattFrame_free (frame); Melder_throw (me, ": no Sound created."); } } KlattTable KlattTable_createExample () { long nrows = 1376; struct klatt_params { short p[40]; } klatt_data [1376] = { {{ 1000, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1000, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1010, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1020, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1030, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1040, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1050, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1060, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1070, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1080, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1090, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1100, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1110, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1120, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1130, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1140, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1150, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1160, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1170, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1180, 0, 542, 0, 1372, 0, 2634, 0, 3737, 0, 5740, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 52, 0, 56, 0, 71, 0, 66, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1190, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 28, 60 }}, {{ 1200, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 31, 60 }}, {{ 1207, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 34, 60 }}, {{ 1214, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 36, 60 }}, {{ 1221, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 39, 60 }}, {{ 1228, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 42, 60 }}, {{ 1234, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 42, 60 }}, {{ 1241, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 42, 60 }}, {{ 1248, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 42, 60 }}, {{ 1255, 0, 506, 0, 752, 0, 3029, 0, 3545, 0, 6301, 0, 7523, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 41, 73, 79, 56, 108, 53, 65, 43, 80, 37, 80, 0, 0, 42, 60 }}, {{ 1262, 0, 510, 0, 765, 0, 3006, 0, 3547, 0, 6283, 0, 7484, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 42, 72, 78, 56, 106, 53, 65, 43, 80, 37, 80, 0, 0, 42, 60 }}, {{ 1269, 0, 518, 0, 792, 0, 2961, 0, 3552, 0, 6248, 0, 7407, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 38, 43, 71, 75, 56, 102, 53, 64, 43, 80, 37, 80, 0, 0, 44, 60 }}, {{ 1276, 0, 530, 0, 833, 0, 2899, 0, 3560, 0, 6197, 0, 7302, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 45, 70, 71, 56, 98, 52, 63, 43, 80, 38, 80, 0, 0, 45, 60 }}, {{ 1282, 0, 543, 0, 892, 0, 2825, 0, 3572, 0, 6132, 0, 7176, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 41, 47, 67, 66, 55, 92, 51, 62, 43, 80, 38, 80, 0, 0, 46, 60 }}, {{ 1289, 0, 556, 0, 969, 0, 2749, 0, 3592, 0, 6055, 0, 7046, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 42, 50, 65, 62, 55, 86, 50, 61, 43, 80, 39, 80, 0, 0, 48, 60 }}, {{ 1296, 0, 567, 0, 1068, 0, 2680, 0, 3622, 0, 5969, 0, 6926, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 43, 52, 62, 58, 55, 81, 50, 61, 44, 80, 39, 80, 0, 0, 50, 60 }}, {{ 1303, 0, 573, 0, 1156, 0, 2642, 0, 3651, 0, 5903, 0, 6858, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 54, 61, 57, 56, 78, 50, 63, 44, 80, 39, 80, 0, 0, 51, 60 }}, {{ 1310, 0, 576, 0, 1230, 0, 2624, 0, 3677, 0, 5854, 0, 6823, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 55, 59, 56, 56, 76, 50, 64, 44, 80, 39, 80, 0, 0, 52, 60 }}, {{ 1322, 0, 576, 0, 1287, 0, 2617, 0, 3699, 0, 5819, 0, 6809, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 55, 59, 57, 56, 76, 50, 66, 44, 80, 39, 80, 0, 0, 54, 60 }}, {{ 1335, 0, 576, 0, 1326, 0, 2616, 0, 3714, 0, 5797, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 55, 58, 57, 57, 75, 50, 67, 44, 80, 39, 80, 0, 0, 56, 60 }}, {{ 1348, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 57, 60 }}, {{ 1360, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 58, 60 }}, {{ 1372, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1385, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 1, 0, 60, 60 }}, {{ 1398, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 3, 0, 59, 60 }}, {{ 1410, 0, 585, 0, 1342, 0, 2619, 0, 3715, 0, 5810, 0, 6804, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 59, 58, 57, 79, 50, 68, 44, 80, 39, 80, 4, 0, 58, 60 }}, {{ 1422, 0, 603, 0, 1337, 0, 2628, 0, 3706, 0, 5849, 0, 6803, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 55, 60, 61, 58, 85, 51, 67, 44, 80, 40, 80, 6, 0, 56, 60 }}, {{ 1435, 0, 624, 0, 1341, 0, 2649, 0, 3705, 0, 5883, 0, 6805, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 61, 65, 60, 95, 52, 65, 45, 80, 40, 80, 9, 0, 54, 60 }}, {{ 1448, 0, 643, 0, 1367, 0, 2692, 0, 3727, 0, 5885, 0, 6814, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 62, 72, 62, 110, 54, 61, 47, 80, 39, 80, 12, 0, 51, 60 }}, {{ 1460, 0, 650, 0, 1417, 0, 2754, 0, 3776, 0, 5837, 0, 6833, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 80, 65, 125, 56, 56, 49, 80, 39, 80, 16, 0, 49, 60 }}, {{ 1460, 0, 649, 0, 1470, 0, 2811, 0, 3830, 0, 5769, 0, 6852, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 87, 68, 137, 58, 51, 52, 80, 38, 80, 19, 0, 47, 60 }}, {{ 1460, 0, 644, 0, 1513, 0, 2855, 0, 3874, 0, 5707, 0, 6867, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 92, 70, 145, 60, 47, 54, 80, 37, 80, 23, 0, 46, 60 }}, {{ 1460, 0, 641, 0, 1537, 0, 2879, 0, 3899, 0, 5672, 0, 6876, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 94, 71, 149, 60, 45, 55, 80, 37, 80, 26, 0, 45, 60 }}, {{ 1460, 0, 641, 0, 1537, 0, 2879, 0, 3899, 0, 5672, 0, 6876, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 94, 71, 149, 60, 45, 55, 80, 37, 80, 29, 0, 45, 60 }}, {{ 1460, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 31, 0, 45, 60 }}, {{ 1460, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 32, 0, 45, 60 }}, {{ 1460, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 34, 0, 45, 60 }}, {{ 1460, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 640, 0, 1540, 0, 2882, 0, 3903, 0, 5668, 0, 6876, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 94, 71, 149, 61, 45, 55, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 641, 0, 1532, 0, 2876, 0, 3899, 0, 5677, 0, 6872, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 94, 70, 148, 60, 45, 55, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 642, 0, 1522, 0, 2868, 0, 3894, 0, 5691, 0, 6867, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 92, 70, 146, 60, 46, 55, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 643, 0, 1509, 0, 2856, 0, 3886, 0, 5709, 0, 6861, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 91, 69, 143, 60, 47, 54, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 644, 0, 1493, 0, 2843, 0, 3877, 0, 5730, 0, 6855, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 89, 69, 140, 59, 48, 53, 80, 38, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 644, 0, 1477, 0, 2827, 0, 3866, 0, 5753, 0, 6849, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 87, 68, 136, 59, 50, 52, 80, 38, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 643, 0, 1461, 0, 2809, 0, 3853, 0, 5779, 0, 6846, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 84, 67, 132, 58, 51, 51, 80, 38, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 641, 0, 1447, 0, 2789, 0, 3839, 0, 5804, 0, 6846, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 62, 81, 66, 127, 57, 53, 50, 80, 39, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 636, 0, 1435, 0, 2769, 0, 3824, 0, 5829, 0, 6850, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 62, 79, 65, 121, 57, 55, 49, 80, 39, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 629, 0, 1428, 0, 2747, 0, 3808, 0, 5852, 0, 6860, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 61, 76, 64, 116, 56, 57, 48, 80, 39, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 618, 0, 1428, 0, 2725, 0, 3791, 0, 5870, 0, 6879, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 61, 73, 63, 110, 55, 58, 47, 80, 39, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 603, 0, 1436, 0, 2703, 0, 3773, 0, 5884, 0, 6908, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 60, 70, 62, 103, 55, 60, 47, 80, 39, 80, 35, 0, 45, 60 }}, {{ 1460, 0, 583, 0, 1454, 0, 2682, 0, 3755, 0, 5890, 0, 6950, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 561, 0, 1481, 0, 2665, 0, 3740, 0, 5888, 0, 6997, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 538, 0, 1513, 0, 2651, 0, 3726, 0, 5879, 0, 7049, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 514, 0, 1548, 0, 2640, 0, 3715, 0, 5866, 0, 7102, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 491, 0, 1586, 0, 2632, 0, 3705, 0, 5849, 0, 7155, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 468, 0, 1623, 0, 2625, 0, 3697, 0, 5831, 0, 7206, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 448, 0, 1659, 0, 2620, 0, 3690, 0, 5813, 0, 7254, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 429, 0, 1692, 0, 2617, 0, 3684, 0, 5795, 0, 7298, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 413, 0, 1722, 0, 2614, 0, 3680, 0, 5778, 0, 7336, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 399, 0, 1746, 0, 2612, 0, 3676, 0, 5764, 0, 7368, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 389, 0, 1765, 0, 2611, 0, 3674, 0, 5753, 0, 7392, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 382, 0, 1779, 0, 2610, 0, 3672, 0, 5746, 0, 7409, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 46, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 35, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 43, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 56, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 58, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1460, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 72, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 0, 60 }}, {{ 1460, 0, 304, 0, 1265, 0, 2343, 0, 3343, 0, 6085, 0, 7150, 0, 0, 0, 200, 30, 72, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 0, 60 }}, {{ 1460, 0, 384, 0, 1107, 0, 2418, 0, 3392, 0, 6038, 0, 7106, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 0, 60 }}, {{ 1460, 0, 491, 0, 864, 0, 2707, 0, 3511, 0, 6110, 0, 7147, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 0, 60 }}, {{ 1475, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 0, 60 }}, {{ 1490, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 0, 60 }}, {{ 1505, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 0, 0, 58, 60 }}, {{ 1520, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 0, 0, 58, 60 }}, {{ 1519, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 0, 0, 59, 60 }}, {{ 1517, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1516, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1514, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1513, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1511, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 1, 0, 60, 60 }}, {{ 1510, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 2, 0, 60, 60 }}, {{ 1509, 0, 518, 0, 779, 0, 2921, 0, 3582, 0, 6230, 0, 7231, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 48, 68, 63, 53, 87, 50, 61, 42, 80, 38, 80, 5, 0, 59, 60 }}, {{ 1507, 0, 540, 0, 841, 0, 2890, 0, 3588, 0, 6186, 0, 7205, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 47, 68, 66, 55, 93, 51, 62, 43, 80, 38, 80, 8, 0, 56, 60 }}, {{ 1506, 0, 578, 0, 984, 0, 2848, 0, 3623, 0, 6083, 0, 7144, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 42, 68, 73, 58, 105, 53, 62, 45, 80, 39, 80, 12, 0, 53, 60 }}, {{ 1504, 0, 619, 0, 1239, 0, 2836, 0, 3731, 0, 5894, 0, 7026, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 28, 66, 84, 64, 126, 57, 57, 49, 80, 38, 80, 17, 0, 49, 60 }}, {{ 1503, 0, 635, 0, 1436, 0, 2862, 0, 3840, 0, 5745, 0, 6931, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 13, 64, 91, 68, 142, 59, 49, 53, 80, 37, 80, 22, 0, 47, 60 }}, {{ 1501, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 27, 0, 45, 60 }}, {{ 1500, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 30, 0, 45, 60 }}, {{ 1497, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 32, 0, 45, 60 }}, {{ 1493, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 34, 0, 45, 60 }}, {{ 1490, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1487, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1483, 0, 642, 0, 1530, 0, 2871, 0, 3891, 0, 5683, 0, 6873, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 93, 70, 148, 60, 46, 55, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1480, 0, 645, 0, 1504, 0, 2845, 0, 3864, 0, 5722, 0, 6864, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 91, 69, 143, 59, 48, 54, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1477, 0, 649, 0, 1468, 0, 2809, 0, 3827, 0, 5772, 0, 6851, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 86, 68, 136, 58, 51, 52, 80, 38, 80, 35, 0, 46, 60 }}, {{ 1473, 0, 650, 0, 1427, 0, 2765, 0, 3786, 0, 5825, 0, 6836, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 81, 66, 127, 57, 55, 50, 80, 39, 80, 35, 0, 49, 60 }}, {{ 1470, 0, 647, 0, 1387, 0, 2718, 0, 3746, 0, 5870, 0, 6822, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 75, 63, 117, 55, 59, 48, 80, 39, 80, 35, 0, 52, 60 }}, {{ 1467, 0, 637, 0, 1354, 0, 2673, 0, 3715, 0, 5890, 0, 6810, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 62, 69, 61, 104, 53, 63, 46, 80, 40, 80, 35, 0, 56, 60 }}, {{ 1463, 0, 622, 0, 1339, 0, 2646, 0, 3704, 0, 5880, 0, 6804, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 52, 61, 65, 59, 94, 52, 66, 45, 80, 40, 80, 0, 0, 58, 60 }}, {{ 1460, 0, 606, 0, 1337, 0, 2630, 0, 3705, 0, 5854, 0, 6803, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 54, 60, 61, 58, 86, 51, 67, 44, 80, 40, 80, 0, 0, 60, 60 }}, {{ 1455, 0, 592, 0, 1339, 0, 2622, 0, 3711, 0, 5825, 0, 6804, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 55, 59, 59, 57, 81, 51, 67, 44, 80, 40, 80, 0, 0, 60, 60 }}, {{ 1450, 0, 581, 0, 1344, 0, 2618, 0, 3718, 0, 5800, 0, 6805, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 58, 57, 77, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1445, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1440, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1435, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1430, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1425, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1420, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1415, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 54, 60 }}, {{ 1410, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 54, 60 }}, {{ 1405, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1400, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1383, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1367, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1350, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1333, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1317, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1283, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1267, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1250, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1233, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 56, 0, 57, 0, 75, 0, 68, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1217, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 64, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 65, 100, 75, 100, 65, 100, 0, 0, 0, 60 }}, {{ 1200, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 64, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 65, 100, 75, 100, 65, 100, 0, 0, 0, 60 }}, {{ 1150, 0, 517, 0, 2038, 0, 2845, 0, 3850, 0, 5703, 0, 7608, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1100, 0, 528, 0, 1991, 0, 2822, 0, 3840, 0, 5691, 0, 7551, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1090, 0, 543, 0, 1921, 0, 2791, 0, 3827, 0, 5674, 0, 7470, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1080, 0, 562, 0, 1831, 0, 2757, 0, 3812, 0, 5655, 0, 7370, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1070, 0, 583, 0, 1720, 0, 2724, 0, 3796, 0, 5637, 0, 7260, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1060, 0, 605, 0, 1592, 0, 2701, 0, 3782, 0, 5621, 0, 7149, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1050, 0, 624, 0, 1450, 0, 2696, 0, 3773, 0, 5612, 0, 7048, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1040, 0, 637, 0, 1332, 0, 2711, 0, 3772, 0, 5613, 0, 6986, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1030, 0, 644, 0, 1239, 0, 2736, 0, 3774, 0, 5619, 0, 6952, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1020, 0, 648, 0, 1166, 0, 2765, 0, 3779, 0, 5628, 0, 6936, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1010, 0, 650, 0, 1113, 0, 2791, 0, 3785, 0, 5637, 0, 6931, 0, 0, 0, 200, 30, 0, 60, 0, 0, 35, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 1000, 0, 651, 0, 1078, 0, 2811, 0, 3789, 0, 5644, 0, 6931, 0, 0, 0, 200, 30, 0, 60, 0, 0, 32, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 990, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 32, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 980, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 100, 50, 100, 60, 100, 65, 100, 70, 100, 55, 100, 0, 0, 0, 60 }}, {{ 970, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 57, 60 }}, {{ 960, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 58, 60 }}, {{ 958, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 58, 60 }}, {{ 957, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 59, 60 }}, {{ 955, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 59, 60 }}, {{ 953, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 952, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 950, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 948, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 947, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 945, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 943, 0, 651, 0, 1061, 0, 2822, 0, 3791, 0, 5648, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 942, 0, 650, 0, 1068, 0, 2817, 0, 3790, 0, 5651, 0, 6931, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 52, 55, 68, 52, 64, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 940, 0, 647, 0, 1082, 0, 2808, 0, 3788, 0, 5658, 0, 6930, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 44, 59, 53, 55, 69, 52, 64, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 938, 0, 644, 0, 1102, 0, 2794, 0, 3785, 0, 5667, 0, 6929, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 45, 58, 53, 56, 69, 52, 65, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 937, 0, 639, 0, 1130, 0, 2777, 0, 3782, 0, 5678, 0, 6928, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 46, 58, 53, 56, 70, 52, 65, 45, 80, 41, 80, 0, 0, 60, 60 }}, {{ 935, 0, 632, 0, 1166, 0, 2757, 0, 3778, 0, 5692, 0, 6928, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 46, 58, 54, 56, 72, 52, 65, 44, 80, 41, 80, 0, 0, 60, 60 }}, {{ 933, 0, 623, 0, 1209, 0, 2735, 0, 3773, 0, 5708, 0, 6929, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 46, 47, 58, 55, 56, 73, 52, 66, 44, 80, 40, 80, 0, 0, 60, 60 }}, {{ 932, 0, 612, 0, 1260, 0, 2713, 0, 3769, 0, 5725, 0, 6933, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 45, 48, 58, 56, 57, 74, 52, 67, 44, 80, 40, 80, 0, 0, 60, 60 }}, {{ 930, 0, 597, 0, 1321, 0, 2691, 0, 3764, 0, 5743, 0, 6941, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 45, 49, 58, 58, 57, 76, 52, 67, 44, 80, 40, 80, 0, 0, 60, 60 }}, {{ 928, 0, 580, 0, 1390, 0, 2672, 0, 3761, 0, 5761, 0, 6953, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 57, 59, 58, 78, 52, 68, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 927, 0, 559, 0, 1470, 0, 2656, 0, 3758, 0, 5778, 0, 6972, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 51, 57, 61, 58, 80, 53, 69, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 925, 0, 533, 0, 1560, 0, 2647, 0, 3757, 0, 5792, 0, 6998, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 57, 64, 59, 81, 53, 70, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 923, 0, 502, 0, 1662, 0, 2646, 0, 3757, 0, 5805, 0, 7033, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 52, 56, 67, 60, 83, 53, 70, 45, 80, 37, 80, 0, 0, 60, 60 }}, {{ 922, 0, 471, 0, 1758, 0, 2654, 0, 3760, 0, 5812, 0, 7071, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 52, 56, 70, 61, 85, 54, 71, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 920, 0, 440, 0, 1848, 0, 2668, 0, 3764, 0, 5816, 0, 7112, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 52, 55, 73, 62, 86, 54, 72, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 919, 0, 411, 0, 1930, 0, 2686, 0, 3768, 0, 5816, 0, 7152, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 52, 55, 76, 63, 87, 55, 72, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 918, 0, 384, 0, 2006, 0, 2706, 0, 3773, 0, 5815, 0, 7192, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 52, 55, 79, 64, 87, 55, 73, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 916, 0, 359, 0, 2073, 0, 2728, 0, 3778, 0, 5812, 0, 7229, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 51, 54, 81, 64, 88, 56, 73, 48, 80, 34, 80, 0, 0, 60, 60 }}, {{ 915, 0, 337, 0, 2131, 0, 2749, 0, 3784, 0, 5808, 0, 7262, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 51, 54, 83, 65, 88, 56, 73, 48, 80, 33, 80, 0, 0, 60, 60 }}, {{ 914, 0, 318, 0, 2181, 0, 2768, 0, 3788, 0, 5804, 0, 7292, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 50, 54, 85, 66, 88, 57, 73, 49, 80, 33, 80, 0, 0, 60, 60 }}, {{ 912, 0, 302, 0, 2220, 0, 2785, 0, 3792, 0, 5801, 0, 7316, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 33, 50, 54, 87, 66, 89, 57, 74, 49, 80, 32, 80, 0, 0, 60, 60 }}, {{ 911, 0, 290, 0, 2251, 0, 2798, 0, 3795, 0, 5798, 0, 7335, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 33, 49, 54, 88, 66, 89, 57, 74, 49, 80, 32, 80, 0, 0, 60, 60 }}, {{ 910, 0, 282, 0, 2271, 0, 2807, 0, 3797, 0, 5796, 0, 7348, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 54, 89, 67, 89, 57, 74, 49, 80, 32, 80, 0, 0, 60, 60 }}, {{ 909, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 0, 0, 60, 60 }}, {{ 908, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 0, 0, 60, 60 }}, {{ 906, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 0, 0, 60, 60 }}, {{ 905, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 1, 0, 60, 60 }}, {{ 904, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 2, 0, 60, 60 }}, {{ 902, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 3, 0, 60, 60 }}, {{ 901, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 5, 0, 60, 60 }}, {{ 900, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 7, 0, 59, 60 }}, {{ 899, 0, 284, 0, 2238, 0, 2783, 0, 3772, 0, 5820, 0, 7318, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 33, 49, 53, 87, 66, 90, 57, 72, 49, 80, 32, 80, 9, 0, 57, 60 }}, {{ 898, 0, 294, 0, 2148, 0, 2732, 0, 3724, 0, 5864, 0, 7253, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 50, 53, 82, 65, 93, 57, 69, 48, 80, 33, 80, 12, 0, 55, 60 }}, {{ 896, 0, 308, 0, 2006, 0, 2673, 0, 3661, 0, 5910, 0, 7171, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 52, 52, 75, 63, 95, 56, 65, 46, 80, 34, 80, 15, 0, 53, 60 }}, {{ 895, 0, 325, 0, 1801, 0, 2629, 0, 3595, 0, 5935, 0, 7095, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 55, 53, 67, 61, 96, 56, 60, 44, 80, 35, 80, 18, 0, 50, 60 }}, {{ 894, 0, 337, 0, 1579, 0, 2623, 0, 3549, 0, 5918, 0, 7055, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 60, 54, 62, 60, 93, 55, 57, 43, 80, 37, 80, 21, 0, 48, 60 }}, {{ 892, 0, 345, 0, 1402, 0, 2644, 0, 3529, 0, 5877, 0, 7049, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 64, 55, 58, 59, 90, 55, 56, 42, 80, 38, 80, 23, 0, 47, 60 }}, {{ 891, 0, 348, 0, 1279, 0, 2670, 0, 3522, 0, 5837, 0, 7056, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 56, 57, 58, 86, 55, 56, 41, 80, 39, 80, 25, 0, 46, 60 }}, {{ 890, 0, 350, 0, 1216, 0, 2687, 0, 3520, 0, 5813, 0, 7063, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 56, 56, 58, 84, 55, 56, 41, 80, 39, 80, 27, 0, 45, 60 }}, {{ 894, 0, 350, 0, 1216, 0, 2687, 0, 3520, 0, 5813, 0, 7063, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 56, 56, 58, 84, 55, 56, 41, 80, 39, 80, 28, 0, 45, 60 }}, {{ 897, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 29, 0, 45, 60 }}, {{ 901, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 904, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 908, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 911, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 915, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 919, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 922, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 926, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 929, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 933, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 936, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 30, 0, 45, 60 }}, {{ 940, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 941, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 942, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 943, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 944, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 945, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 946, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 947, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 948, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 949, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 950, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 951, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 952, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 953, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 954, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 955, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 956, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 957, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 958, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 959, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 960, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 961, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 962, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 963, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 964, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 965, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 966, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 967, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 968, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 969, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 970, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 971, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 972, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 973, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 974, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 975, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 976, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 977, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 978, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 0, 60 }}, {{ 979, 0, 350, 0, 1200, 0, 2691, 0, 3520, 0, 5807, 0, 7065, 0, 0, 0, 200, 30, 0, 60, 0, 0, 38, 0, 0, 50, 57, 56, 58, 83, 55, 56, 41, 80, 39, 80, 0, 0, 43, 60 }}, {{ 980, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 51, 60 }}, {{ 989, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 51, 60 }}, {{ 998, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 51, 60 }}, {{ 1006, 0, 481, 0, 1539, 0, 2809, 0, 3806, 0, 5770, 0, 6975, 0, 0, 0, 200, 30, 0, 60, 0, 0, 34, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 51, 60 }}, {{ 1015, 0, 500, 0, 1570, 0, 2785, 0, 3803, 0, 5839, 0, 6997, 0, 0, 0, 200, 30, 0, 60, 0, 0, 11, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 52, 60 }}, {{ 1024, 0, 528, 0, 1617, 0, 2761, 0, 3805, 0, 5917, 0, 7031, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 54, 60 }}, {{ 1032, 0, 566, 0, 1680, 0, 2752, 0, 3819, 0, 5978, 0, 7080, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 55, 60 }}, {{ 1041, 0, 602, 0, 1744, 0, 2770, 0, 3846, 0, 5988, 0, 7130, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 47, 59, 78, 64, 111, 57, 71, 46, 80, 38, 80, 0, 0, 57, 60 }}, {{ 1050, 0, 630, 0, 1793, 0, 2800, 0, 3875, 0, 5962, 0, 7170, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 48, 59, 80, 64, 112, 58, 80, 45, 80, 38, 80, 0, 0, 59, 60 }}, {{ 1048, 0, 648, 0, 1825, 0, 2828, 0, 3898, 0, 5928, 0, 7198, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 49, 59, 82, 65, 114, 58, 88, 44, 80, 39, 80, 0, 0, 59, 60 }}, {{ 1046, 0, 657, 0, 1842, 0, 2844, 0, 3911, 0, 5907, 0, 7212, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 49, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1044, 0, 657, 0, 1842, 0, 2844, 0, 3911, 0, 5907, 0, 7212, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 49, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1042, 0, 647, 0, 1829, 0, 2837, 0, 3911, 0, 5885, 0, 7175, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 82, 65, 113, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1040, 0, 624, 0, 1796, 0, 2809, 0, 3897, 0, 5855, 0, 7101, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 52, 59, 79, 64, 108, 57, 87, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1038, 0, 591, 0, 1751, 0, 2751, 0, 3857, 0, 5818, 0, 7004, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 54, 58, 75, 63, 100, 55, 82, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1036, 0, 552, 0, 1698, 0, 2646, 0, 3769, 0, 5783, 0, 6904, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 57, 70, 61, 90, 53, 75, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1034, 0, 511, 0, 1643, 0, 2469, 0, 3603, 0, 5762, 0, 6825, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 64, 59, 77, 51, 67, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 1032, 0, 483, 0, 1607, 0, 2292, 0, 3425, 0, 5763, 0, 6798, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 54, 57, 59, 56, 67, 49, 60, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1030, 0, 466, 0, 1586, 0, 2138, 0, 3266, 0, 5775, 0, 6799, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 56, 54, 60, 47, 55, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1026, 0, 456, 0, 1574, 0, 2025, 0, 3147, 0, 5788, 0, 6810, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 51, 58, 54, 52, 55, 46, 52, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1022, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1018, 0, 457, 0, 1544, 0, 1983, 0, 3092, 0, 5812, 0, 6824, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 54, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1014, 0, 466, 0, 1494, 0, 2019, 0, 3109, 0, 5845, 0, 6838, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 59, 53, 51, 58, 46, 52, 46, 80, 35, 80, 0, 0, 58, 60 }}, {{ 1010, 0, 479, 0, 1421, 0, 2078, 0, 3137, 0, 5892, 0, 6864, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 60, 54, 51, 64, 46, 54, 45, 80, 35, 80, 0, 0, 57, 60 }}, {{ 1006, 0, 494, 0, 1325, 0, 2168, 0, 3178, 0, 5954, 0, 6910, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 61, 56, 52, 71, 47, 56, 44, 80, 35, 80, 0, 0, 56, 60 }}, {{ 1002, 0, 507, 0, 1208, 0, 2296, 0, 3235, 0, 6028, 0, 6986, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 49, 63, 58, 52, 79, 48, 58, 44, 80, 36, 80, 0, 0, 54, 60 }}, {{ 998, 0, 516, 0, 1072, 0, 2473, 0, 3312, 0, 6112, 0, 7103, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 66, 63, 53, 88, 49, 60, 43, 80, 36, 80, 0, 0, 52, 60 }}, {{ 994, 0, 518, 0, 962, 0, 2641, 0, 3383, 0, 6178, 0, 7223, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 41, 46, 68, 67, 54, 95, 50, 62, 43, 80, 37, 80, 0, 0, 51, 60 }}, {{ 990, 0, 516, 0, 876, 0, 2787, 0, 3445, 0, 6229, 0, 7334, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 44, 70, 72, 55, 101, 52, 63, 43, 80, 37, 80, 0, 0, 50, 60 }}, {{ 995, 0, 512, 0, 820, 0, 2892, 0, 3488, 0, 6261, 0, 7414, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 38, 43, 71, 75, 56, 104, 52, 64, 43, 80, 37, 80, 0, 0, 48, 60 }}, {{ 1000, 0, 513, 0, 834, 0, 2865, 0, 3477, 0, 6253, 0, 7394, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 38, 43, 71, 74, 55, 103, 52, 64, 43, 80, 37, 80, 0, 0, 47, 60 }}, {{ 1005, 0, 515, 0, 855, 0, 2827, 0, 3461, 0, 6241, 0, 7364, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 43, 71, 73, 55, 102, 52, 64, 43, 80, 37, 80, 0, 0, 48, 60 }}, {{ 1010, 0, 516, 0, 883, 0, 2776, 0, 3440, 0, 6225, 0, 7325, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 44, 70, 71, 55, 100, 51, 63, 43, 80, 37, 80, 0, 0, 49, 60 }}, {{ 1015, 0, 517, 0, 918, 0, 2714, 0, 3414, 0, 6204, 0, 7278, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 40, 45, 69, 70, 54, 98, 51, 63, 43, 80, 37, 80, 0, 0, 49, 60 }}, {{ 1020, 0, 518, 0, 960, 0, 2643, 0, 3384, 0, 6179, 0, 7225, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 41, 46, 68, 67, 54, 95, 50, 62, 43, 80, 37, 80, 0, 0, 50, 60 }}, {{ 1025, 0, 518, 0, 1011, 0, 2563, 0, 3350, 0, 6149, 0, 7167, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 41, 47, 67, 65, 54, 92, 50, 61, 43, 80, 37, 80, 0, 0, 51, 60 }}, {{ 1030, 0, 516, 0, 1069, 0, 2477, 0, 3313, 0, 6113, 0, 7106, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 42, 47, 66, 63, 53, 88, 49, 60, 43, 80, 36, 80, 0, 0, 51, 60 }}, {{ 1035, 0, 513, 0, 1136, 0, 2386, 0, 3274, 0, 6072, 0, 7044, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 43, 48, 65, 61, 53, 84, 48, 59, 43, 80, 36, 80, 0, 0, 52, 60 }}, {{ 1040, 0, 507, 0, 1211, 0, 2292, 0, 3233, 0, 6026, 0, 6983, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 43, 49, 63, 58, 52, 79, 48, 58, 44, 80, 36, 80, 0, 0, 53, 60 }}, {{ 1045, 0, 499, 0, 1280, 0, 2214, 0, 3198, 0, 5982, 0, 6936, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 50, 62, 57, 52, 74, 47, 56, 44, 80, 36, 80, 0, 0, 53, 60 }}, {{ 1050, 0, 491, 0, 1343, 0, 2150, 0, 3170, 0, 5942, 0, 6900, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 61, 55, 52, 69, 47, 55, 45, 80, 35, 80, 0, 0, 54, 60 }}, {{ 1052, 0, 483, 0, 1398, 0, 2098, 0, 3146, 0, 5907, 0, 6874, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 60, 54, 51, 65, 46, 54, 45, 80, 35, 80, 0, 0, 55, 60 }}, {{ 1055, 0, 475, 0, 1446, 0, 2057, 0, 3127, 0, 5876, 0, 6854, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 59, 54, 51, 62, 46, 53, 46, 80, 35, 80, 0, 0, 55, 60 }}, {{ 1058, 0, 468, 0, 1487, 0, 2025, 0, 3112, 0, 5850, 0, 6840, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 59, 53, 51, 59, 46, 52, 46, 80, 35, 80, 0, 0, 56, 60 }}, {{ 1060, 0, 462, 0, 1519, 0, 2000, 0, 3100, 0, 5828, 0, 6831, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 56, 46, 52, 46, 80, 34, 80, 0, 0, 57, 60 }}, {{ 1062, 0, 457, 0, 1544, 0, 1983, 0, 3092, 0, 5812, 0, 6824, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 54, 46, 51, 47, 80, 34, 80, 0, 0, 57, 60 }}, {{ 1065, 0, 453, 0, 1560, 0, 1971, 0, 3087, 0, 5801, 0, 6821, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 53, 45, 51, 47, 80, 34, 80, 0, 0, 58, 60 }}, {{ 1068, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 59, 60 }}, {{ 1070, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 59, 60 }}, {{ 1072, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1075, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 56, 60 }}, {{ 1078, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 53, 60 }}, {{ 1080, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 49, 60 }}, {{ 1082, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 46, 60 }}, {{ 1085, 0, 451, 0, 1570, 0, 2013, 0, 3118, 0, 5791, 0, 6824, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 43, 50, 58, 54, 52, 57, 46, 52, 46, 80, 34, 80, 0, 0, 42, 60 }}, {{ 1088, 0, 450, 0, 1573, 0, 2105, 0, 3185, 0, 5782, 0, 6835, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 43, 50, 58, 56, 53, 66, 48, 55, 46, 80, 35, 80, 0, 0, 38, 60 }}, {{ 1090, 0, 450, 0, 1574, 0, 2234, 0, 3282, 0, 5769, 0, 6851, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 42, 50, 57, 60, 56, 79, 50, 59, 45, 80, 36, 80, 0, 0, 35, 60 }}, {{ 1092, 0, 451, 0, 1572, 0, 2391, 0, 3406, 0, 5755, 0, 6873, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 41, 50, 57, 64, 58, 93, 52, 62, 45, 80, 36, 80, 0, 0, 31, 60 }}, {{ 1095, 0, 455, 0, 1563, 0, 2562, 0, 3551, 0, 5742, 0, 6902, 0, 0, 0, 200, 30, 52, 60, 0, 0, 0, 0, 40, 48, 57, 68, 61, 106, 55, 63, 45, 80, 37, 80, 0, 0, 28, 60 }}, {{ 1098, 0, 460, 0, 1551, 0, 2680, 0, 3659, 0, 5736, 0, 6926, 0, 0, 0, 200, 30, 52, 60, 0, 0, 40, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 24, 60 }}, {{ 1100, 0, 465, 0, 1539, 0, 2756, 0, 3736, 0, 5733, 0, 6945, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 469, 0, 1529, 0, 2802, 0, 3785, 0, 5731, 0, 6958, 0, 0, 0, 200, 30, 0, 60, 0, 0, 43, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 45, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 46, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 471, 0, 1524, 0, 2823, 0, 3809, 0, 5731, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 469, 0, 1519, 0, 2817, 0, 3799, 0, 5719, 0, 6958, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 464, 0, 1511, 0, 2805, 0, 3778, 0, 5695, 0, 6947, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 457, 0, 1500, 0, 2783, 0, 3742, 0, 5661, 0, 6934, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 448, 0, 1487, 0, 2748, 0, 3687, 0, 5622, 0, 6923, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 439, 0, 1474, 0, 2694, 0, 3607, 0, 5580, 0, 6920, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 429, 0, 1461, 0, 2617, 0, 3495, 0, 5541, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 420, 0, 1453, 0, 2508, 0, 3340, 0, 5512, 0, 6967, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 413, 0, 1451, 0, 2358, 0, 3133, 0, 5499, 0, 7036, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 410, 0, 1455, 0, 2205, 0, 2925, 0, 5505, 0, 7121, 0, 0, 0, 200, 30, 0, 60, 0, 0, 48, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 408, 0, 1464, 0, 2057, 0, 2727, 0, 5525, 0, 7213, 0, 0, 0, 200, 30, 0, 60, 0, 0, 47, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 409, 0, 1475, 0, 1923, 0, 2548, 0, 5551, 0, 7302, 0, 0, 0, 200, 30, 0, 60, 0, 0, 46, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 410, 0, 1486, 0, 1808, 0, 2396, 0, 5577, 0, 7382, 0, 0, 0, 200, 30, 0, 60, 0, 0, 43, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 411, 0, 1495, 0, 1718, 0, 2276, 0, 5601, 0, 7447, 0, 0, 0, 200, 30, 0, 60, 0, 0, 41, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 413, 0, 1502, 0, 1656, 0, 2194, 0, 5619, 0, 7492, 0, 0, 0, 200, 30, 0, 60, 0, 0, 39, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 413, 0, 1506, 0, 1624, 0, 2152, 0, 5628, 0, 7516, 0, 0, 0, 200, 30, 0, 60, 0, 0, 39, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 413, 0, 1506, 0, 1624, 0, 2152, 0, 5628, 0, 7516, 0, 0, 0, 200, 30, 0, 60, 0, 0, 39, 0, 0, 10, 0, 10, 55, 100, 0, 10, 60, 200, 0, 10, 0, 0, 0, 60 }}, {{ 1100, 0, 413, 0, 1506, 0, 1624, 0, 2152, 0, 5628, 0, 7516, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 12, 69, 75, 48, 127, 52, 85, 39, 80, 31, 80, 0, 0, 36, 60 }}, {{ 1100, 0, 413, 0, 1506, 0, 1624, 0, 2152, 0, 5628, 0, 7516, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 12, 69, 75, 48, 127, 52, 85, 39, 80, 31, 80, 0, 0, 39, 60 }}, {{ 1101, 0, 413, 0, 1506, 0, 1624, 0, 2152, 0, 5628, 0, 7516, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 12, 69, 75, 48, 127, 52, 85, 39, 80, 31, 80, 0, 0, 42, 60 }}, {{ 1103, 0, 413, 0, 1506, 0, 1624, 0, 2152, 0, 5628, 0, 7516, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 12, 69, 75, 48, 127, 52, 85, 39, 80, 31, 80, 0, 0, 45, 60 }}, {{ 1104, 0, 413, 0, 1510, 0, 1634, 0, 2170, 0, 5615, 0, 7497, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 13, 68, 75, 48, 127, 52, 85, 39, 80, 31, 80, 0, 0, 48, 60 }}, {{ 1106, 0, 411, 0, 1518, 0, 1655, 0, 2206, 0, 5589, 0, 7460, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 14, 68, 74, 48, 126, 53, 85, 39, 80, 31, 80, 0, 0, 49, 60 }}, {{ 1107, 0, 408, 0, 1530, 0, 1687, 0, 2259, 0, 5552, 0, 7406, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 15, 67, 73, 49, 126, 53, 84, 39, 80, 31, 80, 0, 0, 49, 60 }}, {{ 1109, 0, 405, 0, 1547, 0, 1729, 0, 2329, 0, 5505, 0, 7337, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 39, 17, 66, 72, 50, 125, 53, 84, 39, 80, 32, 80, 0, 0, 50, 60 }}, {{ 1110, 0, 400, 0, 1570, 0, 1784, 0, 2416, 0, 5451, 0, 7256, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 38, 19, 64, 71, 51, 125, 53, 83, 40, 80, 32, 80, 0, 0, 50, 60 }}, {{ 1111, 0, 394, 0, 1599, 0, 1850, 0, 2517, 0, 5393, 0, 7166, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 38, 22, 62, 70, 52, 125, 53, 82, 40, 80, 33, 80, 0, 0, 51, 60 }}, {{ 1113, 0, 386, 0, 1635, 0, 1929, 0, 2633, 0, 5334, 0, 7071, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 38, 24, 61, 69, 54, 125, 54, 82, 40, 80, 34, 80, 0, 0, 52, 60 }}, {{ 1114, 0, 377, 0, 1680, 0, 2021, 0, 2762, 0, 5279, 0, 6975, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 27, 59, 69, 55, 125, 55, 81, 41, 80, 34, 80, 0, 0, 52, 60 }}, {{ 1116, 0, 366, 0, 1735, 0, 2128, 0, 2902, 0, 5233, 0, 6885, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 29, 57, 68, 57, 127, 55, 80, 42, 80, 35, 80, 0, 0, 53, 60 }}, {{ 1117, 0, 353, 0, 1802, 0, 2251, 0, 3053, 0, 5201, 0, 6805, 0, 0, 0, 200, 30, 16, 60, 0, 0, 0, 0, 37, 32, 54, 69, 60, 130, 56, 79, 42, 80, 35, 80, 0, 0, 53, 60 }}, {{ 1119, 0, 340, 0, 1866, 0, 2364, 0, 3182, 0, 5189, 0, 6753, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 33, 53, 70, 62, 134, 57, 78, 43, 80, 36, 80, 0, 0, 54, 60 }}, {{ 1120, 0, 327, 0, 1927, 0, 2467, 0, 3294, 0, 5192, 0, 6721, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 34, 51, 71, 63, 137, 58, 77, 43, 80, 36, 80, 0, 0, 55, 60 }}, {{ 1122, 0, 316, 0, 1984, 0, 2559, 0, 3388, 0, 5206, 0, 6704, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 34, 50, 73, 65, 141, 59, 77, 44, 80, 36, 80, 0, 0, 55, 60 }}, {{ 1123, 0, 306, 0, 2034, 0, 2640, 0, 3467, 0, 5225, 0, 6699, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 35, 49, 74, 66, 145, 60, 76, 44, 80, 36, 80, 0, 0, 56, 60 }}, {{ 1125, 0, 297, 0, 2078, 0, 2708, 0, 3530, 0, 5247, 0, 6701, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 35, 49, 76, 68, 148, 61, 76, 44, 80, 36, 80, 0, 0, 56, 60 }}, {{ 1127, 0, 290, 0, 2114, 0, 2763, 0, 3580, 0, 5268, 0, 6706, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 48, 77, 69, 151, 61, 75, 45, 80, 36, 80, 0, 0, 57, 60 }}, {{ 1128, 0, 284, 0, 2142, 0, 2805, 0, 3617, 0, 5285, 0, 6712, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 48, 78, 69, 154, 62, 75, 45, 80, 35, 80, 0, 0, 58, 60 }}, {{ 1130, 0, 281, 0, 2160, 0, 2833, 0, 3641, 0, 5298, 0, 6717, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 48, 79, 70, 155, 62, 75, 45, 80, 35, 80, 0, 0, 58, 60 }}, {{ 1132, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 59, 60 }}, {{ 1133, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 59, 60 }}, {{ 1135, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1137, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1138, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1140, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1142, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 59, 60 }}, {{ 1143, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 58, 60 }}, {{ 1145, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 58, 60 }}, {{ 1147, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 57, 60 }}, {{ 1148, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 56, 60 }}, {{ 1150, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 54, 60 }}, {{ 1152, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 53, 60 }}, {{ 1153, 0, 282, 0, 2160, 0, 2843, 0, 3653, 0, 5313, 0, 6724, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 48, 79, 70, 155, 62, 75, 45, 80, 35, 80, 0, 0, 51, 60 }}, {{ 1155, 0, 289, 0, 2142, 0, 2835, 0, 3654, 0, 5329, 0, 6730, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 35, 48, 79, 70, 154, 62, 74, 45, 80, 35, 80, 0, 0, 49, 60 }}, {{ 1157, 0, 299, 0, 2114, 0, 2824, 0, 3654, 0, 5353, 0, 6740, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 35, 48, 79, 69, 152, 62, 73, 45, 80, 35, 80, 0, 0, 48, 60 }}, {{ 1158, 0, 312, 0, 2077, 0, 2809, 0, 3655, 0, 5383, 0, 6753, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 36, 49, 78, 69, 150, 61, 72, 45, 80, 36, 80, 0, 0, 45, 60 }}, {{ 1160, 0, 328, 0, 2032, 0, 2792, 0, 3657, 0, 5420, 0, 6769, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 37, 50, 78, 68, 146, 61, 71, 45, 80, 36, 80, 0, 0, 43, 60 }}, {{ 1162, 0, 347, 0, 1979, 0, 2774, 0, 3659, 0, 5463, 0, 6787, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 38, 51, 77, 68, 143, 60, 70, 45, 80, 36, 80, 0, 0, 41, 60 }}, {{ 1163, 0, 369, 0, 1918, 0, 2754, 0, 3662, 0, 5511, 0, 6808, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 39, 52, 77, 67, 139, 60, 68, 46, 80, 36, 80, 0, 0, 39, 60 }}, {{ 1165, 0, 393, 0, 1850, 0, 2735, 0, 3666, 0, 5561, 0, 6830, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 40, 53, 76, 66, 134, 59, 66, 46, 80, 36, 80, 0, 0, 36, 60 }}, {{ 1167, 0, 419, 0, 1776, 0, 2717, 0, 3671, 0, 5615, 0, 6853, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 41, 54, 75, 66, 129, 58, 64, 46, 80, 37, 80, 0, 0, 35, 60 }}, {{ 1168, 0, 447, 0, 1696, 0, 2703, 0, 3679, 0, 5668, 0, 6876, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 43, 56, 74, 65, 124, 58, 63, 46, 80, 37, 80, 0, 0, 33, 60 }}, {{ 1170, 0, 473, 0, 1619, 0, 2693, 0, 3687, 0, 5717, 0, 6898, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 44, 57, 73, 64, 119, 57, 61, 46, 80, 37, 80, 0, 0, 31, 60 }}, {{ 1172, 0, 496, 0, 1552, 0, 2689, 0, 3696, 0, 5756, 0, 6915, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 44, 58, 72, 63, 114, 56, 60, 46, 80, 38, 80, 0, 0, 30, 60 }}, {{ 1173, 0, 515, 0, 1494, 0, 2689, 0, 3705, 0, 5787, 0, 6929, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 45, 59, 71, 63, 111, 56, 59, 46, 80, 38, 80, 0, 0, 28, 60 }}, {{ 1175, 0, 531, 0, 1445, 0, 2692, 0, 3713, 0, 5811, 0, 6940, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 46, 59, 71, 62, 108, 56, 58, 47, 80, 38, 80, 0, 0, 27, 60 }}, {{ 1177, 0, 545, 0, 1405, 0, 2696, 0, 3720, 0, 5830, 0, 6949, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 46, 60, 70, 62, 105, 55, 57, 47, 80, 38, 80, 0, 0, 26, 60 }}, {{ 1178, 0, 555, 0, 1371, 0, 2701, 0, 3727, 0, 5844, 0, 6956, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 46, 60, 70, 62, 103, 55, 57, 47, 80, 38, 80, 0, 0, 26, 60 }}, {{ 1180, 0, 564, 0, 1345, 0, 2706, 0, 3732, 0, 5854, 0, 6961, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 46, 61, 69, 61, 101, 55, 57, 47, 80, 39, 80, 0, 0, 25, 60 }}, {{ 1182, 0, 570, 0, 1326, 0, 2710, 0, 3737, 0, 5861, 0, 6964, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 46, 61, 69, 61, 100, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 1183, 0, 574, 0, 1313, 0, 2713, 0, 3739, 0, 5866, 0, 6967, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 1185, 0, 576, 0, 1307, 0, 2715, 0, 3741, 0, 5868, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 1187, 0, 576, 0, 1307, 0, 2715, 0, 3741, 0, 5868, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 1188, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1190, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1184, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1177, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1171, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1164, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1158, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1151, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1145, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1139, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1132, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1126, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1119, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1113, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1106, 0, 462, 0, 1513, 0, 2553, 0, 3535, 0, 5746, 0, 6910, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 1100, 0, 466, 0, 1520, 0, 2560, 0, 3550, 0, 5757, 0, 6909, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 1075, 0, 474, 0, 1530, 0, 2570, 0, 3573, 0, 5773, 0, 6909, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 49, 58, 68, 61, 104, 54, 62, 45, 80, 37, 80, 0, 0, 50, 60 }}, {{ 1050, 0, 484, 0, 1544, 0, 2585, 0, 3603, 0, 5793, 0, 6911, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 49, 58, 68, 61, 103, 54, 62, 45, 80, 37, 80, 0, 0, 51, 60 }}, {{ 1048, 0, 496, 0, 1563, 0, 2603, 0, 3638, 0, 5816, 0, 6916, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 49, 58, 68, 61, 102, 54, 62, 45, 80, 37, 80, 0, 0, 53, 60 }}, {{ 1045, 0, 512, 0, 1587, 0, 2626, 0, 3679, 0, 5840, 0, 6927, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 50, 58, 69, 62, 101, 55, 63, 46, 80, 37, 80, 0, 0, 55, 60 }}, {{ 1043, 0, 530, 0, 1616, 0, 2654, 0, 3722, 0, 5864, 0, 6945, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 70, 62, 101, 55, 65, 46, 80, 38, 80, 0, 0, 57, 60 }}, {{ 1041, 0, 552, 0, 1652, 0, 2686, 0, 3767, 0, 5885, 0, 6975, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 72, 62, 102, 55, 67, 46, 80, 38, 80, 0, 0, 58, 60 }}, {{ 1038, 0, 575, 0, 1691, 0, 2720, 0, 3808, 0, 5900, 0, 7012, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 74, 63, 103, 56, 71, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1036, 0, 595, 0, 1726, 0, 2750, 0, 3840, 0, 5907, 0, 7053, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 76, 63, 105, 56, 75, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1034, 0, 612, 0, 1758, 0, 2777, 0, 3864, 0, 5910, 0, 7092, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 50, 59, 78, 64, 108, 57, 79, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1031, 0, 627, 0, 1786, 0, 2800, 0, 3882, 0, 5910, 0, 7129, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 79, 64, 110, 57, 83, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1029, 0, 640, 0, 1809, 0, 2819, 0, 3896, 0, 5908, 0, 7161, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 81, 64, 112, 58, 87, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1027, 0, 649, 0, 1826, 0, 2833, 0, 3905, 0, 5905, 0, 7186, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 82, 65, 113, 58, 90, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1024, 0, 655, 0, 1838, 0, 2843, 0, 3911, 0, 5903, 0, 7204, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1022, 0, 658, 0, 1844, 0, 2848, 0, 3914, 0, 5901, 0, 7213, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1020, 0, 658, 0, 1844, 0, 2848, 0, 3914, 0, 5901, 0, 7213, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1017, 0, 658, 0, 1844, 0, 2848, 0, 3914, 0, 5899, 0, 7211, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1015, 0, 655, 0, 1840, 0, 2845, 0, 3913, 0, 5895, 0, 7202, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 114, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1013, 0, 651, 0, 1834, 0, 2841, 0, 3912, 0, 5890, 0, 7188, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 83, 65, 114, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1010, 0, 646, 0, 1827, 0, 2836, 0, 3910, 0, 5883, 0, 7171, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 51, 59, 82, 65, 112, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1008, 0, 639, 0, 1818, 0, 2829, 0, 3907, 0, 5874, 0, 7149, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 51, 59, 81, 64, 111, 58, 90, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1006, 0, 631, 0, 1807, 0, 2819, 0, 3903, 0, 5864, 0, 7124, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 52, 59, 80, 64, 109, 57, 88, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1003, 0, 622, 0, 1795, 0, 2807, 0, 3896, 0, 5853, 0, 7097, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 52, 59, 79, 64, 107, 57, 87, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1001, 0, 612, 0, 1781, 0, 2791, 0, 3886, 0, 5841, 0, 7066, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 53, 58, 78, 64, 105, 56, 86, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 999, 0, 602, 0, 1766, 0, 2772, 0, 3873, 0, 5829, 0, 7034, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 53, 58, 76, 63, 102, 56, 84, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 996, 0, 590, 0, 1750, 0, 2748, 0, 3855, 0, 5816, 0, 7001, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 54, 58, 75, 63, 100, 55, 82, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 994, 0, 578, 0, 1733, 0, 2719, 0, 3832, 0, 5804, 0, 6967, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 58, 73, 62, 97, 55, 80, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 992, 0, 565, 0, 1715, 0, 2684, 0, 3802, 0, 5792, 0, 6934, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 57, 71, 62, 93, 54, 77, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 989, 0, 551, 0, 1697, 0, 2642, 0, 3766, 0, 5782, 0, 6902, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 57, 70, 61, 89, 53, 75, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 987, 0, 538, 0, 1678, 0, 2592, 0, 3720, 0, 5773, 0, 6872, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 68, 60, 86, 52, 72, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 985, 0, 524, 0, 1660, 0, 2533, 0, 3665, 0, 5766, 0, 6846, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 66, 60, 81, 52, 69, 46, 80, 38, 80, 0, 0, 60, 60 }}, {{ 982, 0, 512, 0, 1644, 0, 2473, 0, 3607, 0, 5762, 0, 6826, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 64, 59, 77, 51, 67, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 980, 0, 501, 0, 1630, 0, 2413, 0, 3548, 0, 5760, 0, 6813, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 62, 58, 74, 50, 64, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 977, 0, 492, 0, 1618, 0, 2354, 0, 3489, 0, 5761, 0, 6804, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 60, 57, 70, 49, 62, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 974, 0, 484, 0, 1608, 0, 2297, 0, 3430, 0, 5763, 0, 6799, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 54, 57, 59, 56, 67, 49, 60, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 971, 0, 477, 0, 1599, 0, 2242, 0, 3374, 0, 5766, 0, 6797, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 54, 57, 58, 55, 65, 48, 58, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 968, 0, 471, 0, 1592, 0, 2191, 0, 3321, 0, 5770, 0, 6797, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 57, 54, 62, 48, 57, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 965, 0, 467, 0, 1586, 0, 2144, 0, 3272, 0, 5774, 0, 6799, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 56, 54, 60, 47, 55, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 962, 0, 463, 0, 1581, 0, 2101, 0, 3227, 0, 5779, 0, 6802, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 57, 55, 53, 58, 47, 54, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 959, 0, 459, 0, 1578, 0, 2063, 0, 3188, 0, 5783, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 57, 54, 53, 56, 46, 53, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 956, 0, 457, 0, 1574, 0, 2031, 0, 3154, 0, 5787, 0, 6810, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 51, 58, 54, 52, 55, 46, 52, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 953, 0, 455, 0, 1572, 0, 2005, 0, 3126, 0, 5790, 0, 6813, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 52, 54, 46, 52, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 950, 0, 453, 0, 1570, 0, 1986, 0, 3105, 0, 5793, 0, 6816, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 52, 53, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 947, 0, 452, 0, 1569, 0, 1972, 0, 3091, 0, 5795, 0, 6818, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 944, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 941, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 938, 0, 451, 0, 1568, 0, 1971, 0, 3090, 0, 5797, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 935, 0, 450, 0, 1566, 0, 1983, 0, 3103, 0, 5799, 0, 6820, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 51, 52, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 932, 0, 449, 0, 1564, 0, 2000, 0, 3122, 0, 5802, 0, 6822, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 52, 53, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 929, 0, 447, 0, 1561, 0, 2022, 0, 3146, 0, 5805, 0, 6824, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 58, 53, 52, 53, 46, 51, 47, 80, 34, 80, 0, 0, 59, 60 }}, {{ 926, 0, 445, 0, 1558, 0, 2050, 0, 3176, 0, 5810, 0, 6828, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 53, 52, 53, 46, 51, 47, 80, 34, 80, 0, 0, 59, 60 }}, {{ 923, 0, 442, 0, 1554, 0, 2082, 0, 3211, 0, 5815, 0, 6832, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 53, 52, 54, 46, 52, 47, 80, 35, 80, 0, 0, 58, 60 }}, {{ 920, 0, 439, 0, 1551, 0, 2118, 0, 3250, 0, 5820, 0, 6839, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 54, 57, 54, 53, 54, 46, 52, 47, 80, 35, 80, 0, 0, 58, 60 }}, {{ 917, 0, 436, 0, 1549, 0, 2157, 0, 3293, 0, 5825, 0, 6847, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 55, 57, 54, 53, 55, 47, 53, 47, 80, 35, 80, 0, 0, 57, 60 }}, {{ 914, 0, 432, 0, 1547, 0, 2200, 0, 3338, 0, 5830, 0, 6858, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 56, 57, 54, 54, 55, 47, 53, 46, 80, 35, 80, 0, 0, 56, 60 }}, {{ 911, 0, 428, 0, 1546, 0, 2245, 0, 3385, 0, 5834, 0, 6873, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 56, 56, 55, 54, 56, 47, 54, 46, 80, 35, 80, 0, 0, 56, 60 }}, {{ 908, 0, 424, 0, 1548, 0, 2291, 0, 3433, 0, 5838, 0, 6891, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 57, 56, 55, 55, 57, 48, 54, 46, 80, 35, 80, 0, 0, 55, 60 }}, {{ 905, 0, 419, 0, 1552, 0, 2338, 0, 3481, 0, 5841, 0, 6913, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 57, 56, 56, 55, 58, 48, 55, 46, 80, 35, 80, 0, 0, 54, 60 }}, {{ 902, 0, 415, 0, 1558, 0, 2385, 0, 3527, 0, 5842, 0, 6940, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 57, 56, 57, 55, 59, 49, 56, 46, 80, 35, 80, 0, 0, 53, 60 }}, {{ 899, 0, 410, 0, 1569, 0, 2431, 0, 3571, 0, 5840, 0, 6973, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 55, 57, 56, 60, 49, 57, 46, 80, 35, 80, 0, 0, 52, 60 }}, {{ 896, 0, 405, 0, 1583, 0, 2474, 0, 3610, 0, 5837, 0, 7013, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 55, 58, 56, 61, 50, 58, 46, 80, 35, 80, 0, 0, 50, 60 }}, {{ 893, 0, 401, 0, 1600, 0, 2508, 0, 3639, 0, 5831, 0, 7054, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 49, 60 }}, {{ 890, 0, 397, 0, 1618, 0, 2536, 0, 3661, 0, 5824, 0, 7096, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 48, 60 }}, {{ 890, 0, 394, 0, 1637, 0, 2558, 0, 3676, 0, 5816, 0, 7138, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 47, 60 }}, {{ 891, 0, 391, 0, 1657, 0, 2574, 0, 3686, 0, 5807, 0, 7178, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 46, 60 }}, {{ 891, 0, 388, 0, 1677, 0, 2587, 0, 3691, 0, 5797, 0, 7217, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 46, 60 }}, {{ 891, 0, 386, 0, 1696, 0, 2596, 0, 3692, 0, 5788, 0, 7254, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 45, 60 }}, {{ 892, 0, 384, 0, 1714, 0, 2602, 0, 3691, 0, 5779, 0, 7288, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 44, 60 }}, {{ 892, 0, 383, 0, 1731, 0, 2606, 0, 3689, 0, 5771, 0, 7319, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 44, 60 }}, {{ 892, 0, 382, 0, 1745, 0, 2608, 0, 3685, 0, 5763, 0, 7346, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 43, 60 }}, {{ 893, 0, 380, 0, 1758, 0, 2609, 0, 3682, 0, 5756, 0, 7369, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 43, 60 }}, {{ 893, 0, 380, 0, 1769, 0, 2610, 0, 3678, 0, 5751, 0, 7388, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 42, 60 }}, {{ 893, 0, 379, 0, 1777, 0, 2610, 0, 3675, 0, 5746, 0, 7402, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 42, 60 }}, {{ 894, 0, 379, 0, 1782, 0, 2610, 0, 3673, 0, 5743, 0, 7412, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 42, 60 }}, {{ 894, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 42, 60 }}, {{ 894, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 42, 60 }}, {{ 895, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 42, 60 }}, {{ 895, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 42, 60 }}, {{ 895, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 42, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 42, 60 }}, {{ 896, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 41, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 41, 60 }}, {{ 896, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 39, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 39, 60 }}, {{ 896, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 35, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 35, 60 }}, {{ 897, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 30, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 30, 60 }}, {{ 897, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 25, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 25, 60 }}, {{ 897, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 18, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 18, 60 }}, {{ 898, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 1, 60, 0, 0, 12, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 12, 60 }}, {{ 898, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 1, 60, 0, 0, 7, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 7, 60 }}, {{ 898, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 1, 60, 0, 0, 4, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 4, 60 }}, {{ 899, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 1, 60, 0, 0, 2, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 2, 60 }}, {{ 899, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 1, 60, 0, 0, 1, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 1, 60 }}, {{ 899, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 1, 60, 0, 0, 1, 0, 0, 40, 35, 40, 50, 50, 65, 100, 75, 200, 65, 100, 0, 0, 1, 60 }}, {{ 900, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 901, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 901, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 902, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 902, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 902, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 903, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 903, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 904, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 904, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 904, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 905, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 905, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 906, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 906, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 906, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 907, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 907, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 908, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 908, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 908, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 909, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 909, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 910, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 910, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 910, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 911, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 911, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 912, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 912, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 912, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 913, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 913, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 914, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 914, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 914, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 915, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 915, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 916, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 916, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 916, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 917, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 917, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 918, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 918, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 918, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 919, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 919, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 920, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 920, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 920, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 921, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 921, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 922, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 922, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 922, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 923, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 923, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 924, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 924, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 924, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 925, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 925, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 926, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 926, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 926, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 927, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 927, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 928, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 928, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 928, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 929, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 929, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 930, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 930, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 930, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 931, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 931, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 932, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 932, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 932, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 933, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 933, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 934, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 934, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 934, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 935, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 935, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 936, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 936, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 936, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 937, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 937, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 938, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 938, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 938, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 939, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 939, 0, 379, 0, 1785, 0, 2610, 0, 3672, 0, 5742, 0, 7417, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 64, 0, 67, 0, 63, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 940, 0, 591, 0, 1313, 0, 2691, 0, 3779, 0, 5717, 0, 6857, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 57, 75, 51, 70, 44, 80, 40, 80, 30, 0, 39, 60 }}, {{ 940, 0, 591, 0, 1313, 0, 2691, 0, 3779, 0, 5717, 0, 6857, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 57, 75, 51, 70, 44, 80, 40, 80, 30, 0, 42, 60 }}, {{ 945, 0, 591, 0, 1313, 0, 2691, 0, 3779, 0, 5717, 0, 6857, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 57, 75, 51, 70, 44, 80, 40, 80, 30, 0, 45, 60 }}, {{ 950, 0, 591, 0, 1313, 0, 2691, 0, 3779, 0, 5717, 0, 6857, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 57, 75, 51, 70, 44, 80, 40, 80, 30, 0, 45, 60 }}, {{ 955, 0, 591, 0, 1313, 0, 2691, 0, 3779, 0, 5717, 0, 6857, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 57, 75, 51, 70, 44, 80, 40, 80, 30, 0, 45, 60 }}, {{ 960, 0, 590, 0, 1314, 0, 2690, 0, 3779, 0, 5720, 0, 6856, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 57, 75, 51, 70, 44, 80, 40, 80, 30, 0, 45, 60 }}, {{ 965, 0, 589, 0, 1315, 0, 2688, 0, 3777, 0, 5724, 0, 6853, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 57, 75, 51, 70, 44, 80, 40, 80, 30, 0, 45, 60 }}, {{ 970, 0, 588, 0, 1317, 0, 2683, 0, 3774, 0, 5730, 0, 6850, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 57, 75, 51, 69, 44, 80, 40, 80, 30, 0, 46, 60 }}, {{ 975, 0, 587, 0, 1319, 0, 2678, 0, 3770, 0, 5737, 0, 6844, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 57, 75, 51, 69, 44, 80, 40, 80, 30, 0, 49, 60 }}, {{ 980, 0, 585, 0, 1323, 0, 2670, 0, 3764, 0, 5746, 0, 6838, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 58, 57, 57, 75, 51, 69, 44, 80, 40, 80, 30, 0, 52, 60 }}, {{ 985, 0, 583, 0, 1327, 0, 2660, 0, 3757, 0, 5756, 0, 6831, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 54, 58, 57, 57, 75, 51, 69, 44, 80, 40, 80, 0, 0, 56, 60 }}, {{ 990, 0, 580, 0, 1332, 0, 2649, 0, 3748, 0, 5766, 0, 6824, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 55, 58, 57, 57, 75, 50, 69, 44, 80, 40, 80, 0, 0, 58, 60 }}, {{ 994, 0, 579, 0, 1337, 0, 2639, 0, 3740, 0, 5773, 0, 6818, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 55, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 998, 0, 577, 0, 1340, 0, 2631, 0, 3733, 0, 5778, 0, 6813, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 55, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1001, 0, 576, 0, 1343, 0, 2624, 0, 3728, 0, 5782, 0, 6810, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 55, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1005, 0, 576, 0, 1345, 0, 2620, 0, 3724, 0, 5785, 0, 6807, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1009, 0, 575, 0, 1346, 0, 2618, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1012, 0, 575, 0, 1346, 0, 2618, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1016, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 1, 0, 60, 60 }}, {{ 1020, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 2, 0, 60, 60 }}, {{ 1024, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 3, 0, 60, 60 }}, {{ 1028, 0, 575, 0, 1346, 0, 2617, 0, 3722, 0, 5786, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 56, 58, 57, 57, 75, 50, 68, 44, 80, 39, 80, 5, 0, 59, 60 }}, {{ 1031, 0, 557, 0, 1344, 0, 2602, 0, 3692, 0, 5820, 0, 6861, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 55, 58, 58, 57, 76, 51, 65, 44, 80, 39, 80, 8, 0, 58, 60 }}, {{ 1035, 0, 519, 0, 1335, 0, 2584, 0, 3639, 0, 5871, 0, 6953, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 54, 58, 59, 57, 78, 51, 60, 45, 80, 38, 80, 11, 0, 56, 60 }}, {{ 1039, 0, 464, 0, 1308, 0, 2584, 0, 3578, 0, 5904, 0, 7046, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 56, 58, 59, 57, 80, 53, 56, 44, 80, 38, 80, 15, 0, 53, 60 }}, {{ 1042, 0, 409, 0, 1265, 0, 2617, 0, 3538, 0, 5885, 0, 7085, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 61, 58, 58, 58, 82, 54, 54, 43, 80, 38, 80, 19, 0, 50, 60 }}, {{ 1046, 0, 373, 0, 1227, 0, 2658, 0, 3524, 0, 5844, 0, 7080, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 57, 58, 83, 55, 55, 42, 80, 39, 80, 22, 0, 47, 60 }}, {{ 1050, 0, 355, 0, 1205, 0, 2684, 0, 3520, 0, 5815, 0, 7069, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 55, 41, 80, 39, 80, 25, 0, 46, 60 }}, {{ 1055, 0, 355, 0, 1205, 0, 2684, 0, 3520, 0, 5815, 0, 7069, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 57, 56, 58, 83, 55, 55, 41, 80, 39, 80, 27, 0, 45, 60 }}, {{ 1060, 0, 267, 0, 1676, 0, 2414, 0, 3530, 0, 5966, 0, 7193, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 55, 55, 46, 50, 47, 47, 80, 33, 80, 28, 0, 45, 60 }}, {{ 1065, 0, 267, 0, 1676, 0, 2414, 0, 3530, 0, 5966, 0, 7193, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 55, 55, 46, 50, 47, 47, 80, 33, 80, 29, 0, 45, 60 }}, {{ 1070, 0, 267, 0, 1676, 0, 2414, 0, 3530, 0, 5966, 0, 7193, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 55, 55, 46, 50, 47, 47, 80, 33, 80, 30, 0, 45, 60 }}, {{ 1075, 0, 267, 0, 1676, 0, 2414, 0, 3530, 0, 5966, 0, 7193, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 55, 55, 46, 50, 47, 47, 80, 33, 80, 30, 0, 45, 60 }}, {{ 1080, 0, 268, 0, 1679, 0, 2416, 0, 3528, 0, 5969, 0, 7190, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 55, 55, 47, 50, 47, 47, 80, 33, 80, 30, 0, 45, 60 }}, {{ 1085, 0, 271, 0, 1685, 0, 2420, 0, 3523, 0, 5974, 0, 7184, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 56, 55, 50, 50, 48, 47, 80, 33, 80, 30, 0, 45, 60 }}, {{ 1090, 0, 275, 0, 1695, 0, 2427, 0, 3517, 0, 5978, 0, 7174, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 57, 56, 53, 50, 49, 46, 80, 33, 80, 30, 0, 46, 60 }}, {{ 1095, 0, 279, 0, 1709, 0, 2438, 0, 3510, 0, 5980, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 58, 56, 58, 51, 51, 46, 80, 33, 80, 30, 0, 47, 60 }}, {{ 1100, 0, 284, 0, 1730, 0, 2454, 0, 3504, 0, 5974, 0, 7139, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 59, 57, 64, 52, 53, 45, 80, 34, 80, 30, 0, 49, 60 }}, {{ 1105, 0, 289, 0, 1759, 0, 2477, 0, 3501, 0, 5956, 0, 7110, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 61, 58, 72, 52, 55, 45, 80, 34, 80, 30, 0, 51, 60 }}, {{ 1110, 0, 293, 0, 1797, 0, 2509, 0, 3503, 0, 5919, 0, 7073, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 52, 63, 59, 82, 54, 58, 45, 80, 34, 80, 30, 0, 54, 60 }}, {{ 1115, 0, 295, 0, 1848, 0, 2553, 0, 3513, 0, 5857, 0, 7024, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 56, 52, 66, 61, 94, 55, 61, 44, 80, 35, 80, 0, 0, 56, 60 }}, {{ 1120, 0, 295, 0, 1906, 0, 2605, 0, 3530, 0, 5773, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 53, 51, 69, 63, 106, 56, 64, 44, 80, 35, 80, 0, 0, 58, 60 }}, {{ 1122, 0, 294, 0, 1963, 0, 2656, 0, 3552, 0, 5682, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 49, 51, 71, 64, 118, 58, 67, 44, 80, 35, 80, 0, 0, 59, 60 }}, {{ 1123, 0, 291, 0, 2016, 0, 2705, 0, 3575, 0, 5591, 0, 6864, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 46, 50, 74, 66, 128, 59, 69, 44, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1124, 0, 288, 0, 2064, 0, 2748, 0, 3598, 0, 5506, 0, 6820, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 42, 49, 75, 67, 137, 60, 71, 44, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1126, 0, 285, 0, 2104, 0, 2786, 0, 3618, 0, 5432, 0, 6782, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 39, 49, 77, 68, 144, 61, 73, 44, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1128, 0, 282, 0, 2135, 0, 2815, 0, 3634, 0, 5373, 0, 6753, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 37, 48, 78, 69, 150, 61, 74, 45, 80, 35, 80, 0, 0, 59, 60 }}, {{ 1129, 0, 280, 0, 2156, 0, 2834, 0, 3646, 0, 5332, 0, 6733, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 35, 48, 79, 70, 154, 62, 74, 45, 80, 35, 80, 0, 0, 58, 60 }}, {{ 1131, 0, 279, 0, 2167, 0, 2845, 0, 3652, 0, 5310, 0, 6723, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 48, 79, 70, 155, 62, 75, 45, 80, 35, 80, 0, 0, 56, 60 }}, {{ 1132, 0, 279, 0, 2167, 0, 2845, 0, 3652, 0, 5310, 0, 6723, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 48, 79, 70, 155, 62, 75, 45, 80, 35, 80, 0, 0, 53, 60 }}, {{ 1134, 0, 294, 0, 2129, 0, 2830, 0, 3654, 0, 5340, 0, 6735, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 35, 48, 79, 69, 153, 62, 74, 45, 80, 35, 80, 0, 0, 49, 60 }}, {{ 1135, 0, 323, 0, 2048, 0, 2798, 0, 3656, 0, 5407, 0, 6764, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 37, 50, 78, 69, 147, 61, 71, 45, 80, 36, 80, 0, 0, 45, 60 }}, {{ 1137, 0, 364, 0, 1931, 0, 2758, 0, 3661, 0, 5500, 0, 6803, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 39, 52, 77, 67, 139, 60, 68, 46, 80, 36, 80, 0, 0, 39, 60 }}, {{ 1138, 0, 417, 0, 1783, 0, 2719, 0, 3671, 0, 5609, 0, 6850, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 41, 54, 75, 66, 129, 58, 65, 46, 80, 37, 80, 0, 0, 35, 60 }}, {{ 1140, 0, 476, 0, 1610, 0, 2693, 0, 3688, 0, 5722, 0, 6900, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 44, 57, 73, 64, 118, 57, 61, 46, 80, 37, 80, 0, 0, 31, 60 }}, {{ 1141, 0, 519, 0, 1482, 0, 2690, 0, 3707, 0, 5793, 0, 6932, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 45, 59, 71, 63, 110, 56, 59, 46, 80, 38, 80, 0, 0, 28, 60 }}, {{ 1143, 0, 549, 0, 1391, 0, 2698, 0, 3723, 0, 5836, 0, 6952, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 46, 60, 70, 62, 104, 55, 57, 47, 80, 38, 80, 0, 0, 26, 60 }}, {{ 1144, 0, 568, 0, 1333, 0, 2708, 0, 3735, 0, 5859, 0, 6963, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 46, 61, 69, 61, 101, 55, 57, 47, 80, 39, 80, 0, 0, 25, 60 }}, {{ 1146, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 1147, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 1149, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1150, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1154, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1157, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1161, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1164, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1168, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1171, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1175, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1179, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1182, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1186, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1189, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1193, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1196, 0, 462, 0, 1513, 0, 2553, 0, 3535, 0, 5746, 0, 6910, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 1200, 0, 466, 0, 1520, 0, 2560, 0, 3550, 0, 5757, 0, 6909, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 1235, 0, 474, 0, 1530, 0, 2570, 0, 3573, 0, 5773, 0, 6909, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 49, 58, 68, 61, 104, 54, 62, 45, 80, 37, 80, 0, 0, 50, 60 }}, {{ 1270, 0, 484, 0, 1544, 0, 2585, 0, 3603, 0, 5793, 0, 6911, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 49, 58, 68, 61, 103, 54, 62, 45, 80, 37, 80, 0, 0, 51, 60 }}, {{ 1276, 0, 496, 0, 1563, 0, 2603, 0, 3638, 0, 5816, 0, 6916, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 49, 58, 68, 61, 102, 54, 62, 45, 80, 37, 80, 0, 0, 53, 60 }}, {{ 1282, 0, 512, 0, 1587, 0, 2626, 0, 3679, 0, 5840, 0, 6927, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 50, 58, 69, 62, 101, 55, 63, 46, 80, 37, 80, 0, 0, 55, 60 }}, {{ 1288, 0, 530, 0, 1616, 0, 2654, 0, 3722, 0, 5864, 0, 6945, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 70, 62, 101, 55, 65, 46, 80, 38, 80, 0, 0, 57, 60 }}, {{ 1294, 0, 552, 0, 1652, 0, 2686, 0, 3767, 0, 5885, 0, 6975, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 72, 62, 102, 55, 67, 46, 80, 38, 80, 0, 0, 58, 60 }}, {{ 1300, 0, 575, 0, 1691, 0, 2720, 0, 3808, 0, 5900, 0, 7012, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 74, 63, 103, 56, 71, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1306, 0, 595, 0, 1726, 0, 2750, 0, 3840, 0, 5907, 0, 7053, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 76, 63, 105, 56, 75, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1312, 0, 612, 0, 1758, 0, 2777, 0, 3864, 0, 5910, 0, 7092, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 50, 59, 78, 64, 108, 57, 79, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1318, 0, 627, 0, 1786, 0, 2800, 0, 3882, 0, 5910, 0, 7129, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 79, 64, 110, 57, 83, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1324, 0, 640, 0, 1809, 0, 2819, 0, 3896, 0, 5908, 0, 7161, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 81, 64, 112, 58, 87, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1330, 0, 649, 0, 1826, 0, 2833, 0, 3905, 0, 5905, 0, 7186, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 82, 65, 113, 58, 90, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1336, 0, 655, 0, 1838, 0, 2843, 0, 3911, 0, 5903, 0, 7204, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1342, 0, 658, 0, 1844, 0, 2848, 0, 3914, 0, 5901, 0, 7213, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1348, 0, 658, 0, 1844, 0, 2848, 0, 3914, 0, 5901, 0, 7213, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1354, 0, 658, 0, 1844, 0, 2848, 0, 3914, 0, 5899, 0, 7211, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1360, 0, 655, 0, 1840, 0, 2845, 0, 3913, 0, 5895, 0, 7202, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 114, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1366, 0, 651, 0, 1834, 0, 2841, 0, 3912, 0, 5890, 0, 7188, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 83, 65, 114, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1372, 0, 646, 0, 1827, 0, 2836, 0, 3910, 0, 5883, 0, 7171, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 51, 59, 82, 65, 112, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1378, 0, 639, 0, 1818, 0, 2829, 0, 3907, 0, 5874, 0, 7149, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 51, 59, 81, 64, 111, 58, 90, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1384, 0, 631, 0, 1807, 0, 2819, 0, 3903, 0, 5864, 0, 7124, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 52, 59, 80, 64, 109, 57, 88, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1390, 0, 622, 0, 1795, 0, 2807, 0, 3896, 0, 5853, 0, 7097, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 52, 59, 79, 64, 107, 57, 87, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1396, 0, 612, 0, 1781, 0, 2791, 0, 3886, 0, 5841, 0, 7066, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 53, 58, 78, 64, 105, 56, 86, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1402, 0, 602, 0, 1766, 0, 2772, 0, 3873, 0, 5829, 0, 7034, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 53, 58, 76, 63, 102, 56, 84, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1408, 0, 590, 0, 1750, 0, 2748, 0, 3855, 0, 5816, 0, 7001, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 54, 58, 75, 63, 100, 55, 82, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1414, 0, 578, 0, 1733, 0, 2719, 0, 3832, 0, 5804, 0, 6967, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 58, 73, 62, 97, 55, 80, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1420, 0, 565, 0, 1715, 0, 2684, 0, 3802, 0, 5792, 0, 6934, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 57, 71, 62, 93, 54, 77, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1426, 0, 551, 0, 1697, 0, 2642, 0, 3766, 0, 5782, 0, 6902, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 57, 70, 61, 89, 53, 75, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1432, 0, 538, 0, 1678, 0, 2592, 0, 3720, 0, 5773, 0, 6872, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 68, 60, 86, 52, 72, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1438, 0, 524, 0, 1660, 0, 2533, 0, 3665, 0, 5766, 0, 6846, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 66, 60, 81, 52, 69, 46, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1444, 0, 512, 0, 1644, 0, 2473, 0, 3607, 0, 5762, 0, 6826, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 64, 59, 77, 51, 67, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 1450, 0, 501, 0, 1630, 0, 2413, 0, 3548, 0, 5760, 0, 6813, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 62, 58, 74, 50, 64, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 1456, 0, 492, 0, 1618, 0, 2354, 0, 3489, 0, 5761, 0, 6804, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 60, 57, 70, 49, 62, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1462, 0, 484, 0, 1608, 0, 2297, 0, 3430, 0, 5763, 0, 6799, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 54, 57, 59, 56, 67, 49, 60, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1468, 0, 477, 0, 1599, 0, 2242, 0, 3374, 0, 5766, 0, 6797, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 54, 57, 58, 55, 65, 48, 58, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1474, 0, 471, 0, 1592, 0, 2191, 0, 3321, 0, 5770, 0, 6797, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 57, 54, 62, 48, 57, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1480, 0, 467, 0, 1586, 0, 2144, 0, 3272, 0, 5774, 0, 6799, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 56, 54, 60, 47, 55, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1486, 0, 463, 0, 1581, 0, 2101, 0, 3227, 0, 5779, 0, 6802, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 57, 55, 53, 58, 47, 54, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1492, 0, 459, 0, 1578, 0, 2063, 0, 3188, 0, 5783, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 57, 54, 53, 56, 46, 53, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1498, 0, 457, 0, 1574, 0, 2031, 0, 3154, 0, 5787, 0, 6810, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 51, 58, 54, 52, 55, 46, 52, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1504, 0, 455, 0, 1572, 0, 2005, 0, 3126, 0, 5790, 0, 6813, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 52, 54, 46, 52, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1510, 0, 453, 0, 1570, 0, 1986, 0, 3105, 0, 5793, 0, 6816, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 52, 53, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1516, 0, 452, 0, 1569, 0, 1972, 0, 3091, 0, 5795, 0, 6818, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1522, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1528, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1534, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1540, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1546, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1552, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1558, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1564, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1570, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1576, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 53, 60 }}, {{ 1582, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 47, 60 }}, {{ 1588, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 40, 60 }}, {{ 1594, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 33, 60 }}, {{ 1600, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 27, 60 }}, {{ 1606, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 20, 60 }}, {{ 1612, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 14, 60 }}, {{ 1618, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 7, 60 }}, {{ 1624, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1630, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1626, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1622, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1618, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1613, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1609, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1605, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1601, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1597, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1593, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1589, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1585, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1580, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1576, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1572, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1568, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1564, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1560, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1556, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1552, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1547, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1543, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1539, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1535, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1531, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1527, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1523, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1519, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1514, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1510, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1506, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1502, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1498, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1494, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1490, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1486, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1481, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1477, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1473, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1469, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1465, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1461, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1457, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1453, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1448, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1444, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1440, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1436, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1432, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1428, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1424, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1420, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1415, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1411, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1407, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1403, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1399, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1395, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1391, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1387, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1382, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1378, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1374, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1370, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1366, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1362, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1358, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1354, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1349, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1345, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1341, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1337, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1333, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1329, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1325, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1321, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1316, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1312, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1308, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1304, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1285, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1270, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1255, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1240, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1225, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1210, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1195, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1180, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1165, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1150, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1135, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1120, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1105, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1090, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1075, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1060, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1045, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1030, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1015, 0, 523, 0, 2043, 0, 2848, 0, 3848, 0, 5725, 0, 7619, 0, 0, 0, 200, 30, 0, 60, 0, 0, 36, 0, 0, 100, 55, 100, 70, 100, 70, 100, 55, 100, 35, 100, 0, 0, 48, 60 }}, {{ 1000, 0, 545, 0, 2007, 0, 2830, 0, 3836, 0, 5758, 0, 7582, 0, 0, 0, 200, 30, 0, 60, 0, 0, 36, 0, 0, 100, 55, 100, 70, 100, 70, 100, 55, 100, 35, 100, 0, 0, 48, 60 }}, {{ 975, 0, 576, 0, 1954, 0, 2806, 0, 3820, 0, 5807, 0, 7529, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 34, 57, 84, 63, 109, 60, 92, 44, 80, 36, 80, 0, 0, 50, 60 }}, {{ 950, 0, 616, 0, 1885, 0, 2776, 0, 3804, 0, 5869, 0, 7464, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 36, 58, 82, 63, 109, 59, 88, 44, 80, 37, 80, 0, 0, 52, 60 }}, {{ 950, 0, 662, 0, 1802, 0, 2744, 0, 3793, 0, 5943, 0, 7392, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 45, 38, 59, 80, 62, 109, 59, 82, 45, 80, 38, 80, 0, 0, 54, 60 }}, {{ 951, 0, 712, 0, 1705, 0, 2713, 0, 3792, 0, 6027, 0, 7318, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 47, 39, 60, 78, 62, 107, 58, 74, 45, 80, 39, 80, 0, 0, 56, 60 }}, {{ 951, 0, 763, 0, 1598, 0, 2689, 0, 3809, 0, 6118, 0, 7249, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 49, 39, 62, 76, 62, 104, 58, 63, 47, 80, 39, 80, 0, 0, 58, 60 }}, {{ 952, 0, 800, 0, 1511, 0, 2677, 0, 3839, 0, 6190, 0, 7206, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 50, 37, 63, 76, 63, 100, 57, 52, 49, 80, 39, 80, 0, 0, 60, 60 }}, {{ 952, 0, 827, 0, 1442, 0, 2674, 0, 3874, 0, 6246, 0, 7180, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 51, 35, 64, 76, 63, 96, 57, 42, 51, 80, 39, 80, 0, 0, 60, 60 }}, {{ 952, 0, 845, 0, 1389, 0, 2676, 0, 3909, 0, 6288, 0, 7167, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 33, 65, 77, 63, 93, 57, 33, 53, 80, 39, 80, 0, 0, 60, 60 }}, {{ 953, 0, 858, 0, 1350, 0, 2680, 0, 3940, 0, 6318, 0, 7161, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 31, 65, 77, 64, 90, 57, 26, 55, 80, 39, 80, 0, 0, 59, 60 }}, {{ 953, 0, 865, 0, 1325, 0, 2683, 0, 3962, 0, 6337, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 30, 66, 78, 64, 88, 57, 21, 56, 80, 39, 80, 0, 0, 57, 60 }}, {{ 954, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 55, 60 }}, {{ 954, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 53, 60 }}, {{ 955, 0, 864, 0, 1330, 0, 2683, 0, 3958, 0, 6334, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 30, 65, 77, 64, 88, 57, 22, 56, 80, 39, 80, 0, 0, 50, 60 }}, {{ 955, 0, 853, 0, 1364, 0, 2678, 0, 3928, 0, 6307, 0, 7163, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 32, 65, 77, 64, 91, 57, 28, 54, 80, 39, 80, 0, 0, 46, 60 }}, {{ 955, 0, 836, 0, 1418, 0, 2674, 0, 3889, 0, 6266, 0, 7173, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 51, 34, 64, 76, 63, 95, 57, 38, 52, 80, 39, 80, 0, 0, 42, 60 }}, {{ 956, 0, 808, 0, 1492, 0, 2676, 0, 3848, 0, 6206, 0, 7198, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 51, 37, 63, 76, 63, 99, 57, 49, 50, 80, 39, 80, 0, 0, 38, 60 }}, {{ 956, 0, 767, 0, 1590, 0, 2687, 0, 3811, 0, 6125, 0, 7245, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 49, 39, 62, 76, 62, 104, 58, 62, 47, 80, 39, 80, 0, 0, 35, 60 }}, {{ 957, 0, 707, 0, 1715, 0, 2716, 0, 3792, 0, 6019, 0, 7324, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 47, 39, 60, 78, 62, 107, 58, 75, 45, 80, 38, 80, 0, 0, 32, 60 }}, {{ 957, 0, 649, 0, 1825, 0, 2752, 0, 3795, 0, 5923, 0, 7411, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 45, 38, 59, 80, 63, 109, 59, 84, 45, 80, 38, 80, 0, 0, 29, 60 }}, {{ 957, 0, 598, 0, 1917, 0, 2789, 0, 3810, 0, 5840, 0, 7493, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 35, 58, 83, 63, 109, 60, 90, 44, 80, 37, 80, 0, 0, 27, 60 }}, {{ 958, 0, 556, 0, 1988, 0, 2821, 0, 3829, 0, 5776, 0, 7562, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 33, 57, 85, 63, 109, 60, 93, 45, 80, 36, 80, 0, 0, 26, 60 }}, {{ 958, 0, 527, 0, 2037, 0, 2845, 0, 3846, 0, 5731, 0, 7612, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 31, 56, 87, 64, 109, 61, 95, 45, 80, 35, 80, 0, 0, 25, 60 }}, {{ 959, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 30, 56, 88, 64, 109, 61, 96, 45, 80, 35, 80, 0, 0, 24, 60 }}, {{ 959, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 30, 56, 88, 64, 109, 61, 96, 45, 80, 35, 80, 0, 0, 24, 60 }}, {{ 960, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 29, 0, 78, 0, 86, 0, 18, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 960, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 29, 0, 78, 0, 86, 0, 18, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 961, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 29, 0, 78, 0, 86, 0, 18, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 962, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 29, 0, 78, 0, 86, 0, 18, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 964, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 29, 0, 78, 0, 86, 0, 18, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 965, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 29, 0, 78, 0, 86, 0, 18, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 966, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 29, 0, 78, 0, 86, 0, 18, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 968, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 29, 0, 78, 0, 86, 0, 18, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 969, 0, 857, 0, 1328, 0, 2698, 0, 3979, 0, 6330, 0, 7151, 0, 0, 0, 200, 30, 0, 60, 0, 0, 36, 0, 0, 100, 55, 100, 70, 100, 70, 100, 55, 100, 35, 100, 0, 0, 48, 60 }}, {{ 970, 0, 833, 0, 1358, 0, 2723, 0, 3989, 0, 6297, 0, 7136, 0, 0, 0, 200, 30, 0, 60, 0, 0, 36, 0, 0, 100, 55, 100, 70, 100, 70, 100, 55, 100, 35, 100, 0, 0, 48, 60 }}, {{ 980, 0, 797, 0, 1404, 0, 2756, 0, 4000, 0, 6245, 0, 7113, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 49, 30, 64, 80, 66, 100, 58, 26, 55, 80, 38, 80, 0, 0, 50, 60 }}, {{ 990, 0, 749, 0, 1467, 0, 2795, 0, 4008, 0, 6174, 0, 7081, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 47, 31, 63, 81, 67, 109, 58, 31, 55, 80, 38, 80, 0, 0, 52, 60 }}, {{ 990, 0, 689, 0, 1548, 0, 2835, 0, 4006, 0, 6080, 0, 7041, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 45, 31, 61, 83, 68, 118, 59, 37, 53, 80, 38, 80, 0, 0, 54, 60 }}, {{ 990, 0, 617, 0, 1648, 0, 2870, 0, 3986, 0, 5960, 0, 6989, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 32, 59, 83, 69, 128, 60, 44, 52, 80, 37, 80, 0, 0, 56, 60 }}, {{ 990, 0, 533, 0, 1771, 0, 2893, 0, 3941, 0, 5811, 0, 6927, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 33, 57, 84, 69, 138, 60, 53, 50, 80, 37, 80, 0, 0, 58, 60 }}, {{ 990, 0, 460, 0, 1880, 0, 2898, 0, 3882, 0, 5676, 0, 6871, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 33, 54, 83, 70, 145, 61, 59, 49, 80, 36, 80, 0, 0, 60, 60 }}, {{ 990, 0, 400, 0, 1974, 0, 2891, 0, 3818, 0, 5557, 0, 6822, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 34, 52, 82, 70, 150, 61, 65, 47, 80, 36, 80, 0, 0, 60, 60 }}, {{ 990, 0, 351, 0, 2051, 0, 2878, 0, 3758, 0, 5459, 0, 6782, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 34, 50, 81, 70, 153, 62, 69, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 990, 0, 315, 0, 2110, 0, 2864, 0, 3708, 0, 5383, 0, 6752, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 34, 49, 80, 70, 154, 62, 72, 46, 80, 35, 80, 0, 0, 59, 60 }}, {{ 990, 0, 291, 0, 2150, 0, 2853, 0, 3672, 0, 5331, 0, 6731, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 48, 80, 70, 156, 62, 74, 45, 80, 35, 80, 0, 0, 57, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 55, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 53, 60 }}, {{ 990, 0, 289, 0, 2141, 0, 2835, 0, 3654, 0, 5330, 0, 6731, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 35, 48, 79, 70, 154, 62, 74, 45, 80, 35, 80, 0, 0, 50, 60 }}, {{ 990, 0, 309, 0, 2085, 0, 2812, 0, 3655, 0, 5377, 0, 6751, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 36, 49, 79, 69, 150, 61, 72, 45, 80, 36, 80, 0, 0, 46, 60 }}, {{ 990, 0, 339, 0, 2002, 0, 2782, 0, 3658, 0, 5445, 0, 6780, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 37, 51, 78, 68, 144, 60, 70, 45, 80, 36, 80, 0, 0, 42, 60 }}, {{ 990, 0, 377, 0, 1896, 0, 2748, 0, 3663, 0, 5528, 0, 6815, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 39, 52, 76, 67, 137, 59, 67, 46, 80, 36, 80, 0, 0, 38, 60 }}, {{ 990, 0, 422, 0, 1768, 0, 2716, 0, 3672, 0, 5620, 0, 6855, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 41, 54, 75, 66, 128, 58, 64, 46, 80, 37, 80, 0, 0, 35, 60 }}, {{ 990, 0, 471, 0, 1624, 0, 2694, 0, 3687, 0, 5714, 0, 6896, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 44, 57, 73, 64, 119, 57, 61, 46, 80, 37, 80, 0, 0, 32, 60 }}, {{ 990, 0, 509, 0, 1511, 0, 2689, 0, 3702, 0, 5778, 0, 6925, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 45, 58, 72, 63, 112, 56, 59, 46, 80, 38, 80, 0, 0, 29, 60 }}, {{ 990, 0, 538, 0, 1426, 0, 2694, 0, 3716, 0, 5820, 0, 6945, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 46, 60, 71, 62, 106, 55, 58, 47, 80, 38, 80, 0, 0, 27, 60 }}, {{ 990, 0, 558, 0, 1364, 0, 2702, 0, 3728, 0, 5847, 0, 6957, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 46, 60, 70, 62, 103, 55, 57, 47, 80, 39, 80, 0, 0, 26, 60 }}, {{ 990, 0, 570, 0, 1325, 0, 2710, 0, 3737, 0, 5862, 0, 6965, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 46, 61, 69, 61, 100, 55, 56, 47, 80, 39, 80, 0, 0, 25, 60 }}, {{ 990, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 990, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 990, 0, 461, 0, 1512, 0, 2551, 0, 3531, 0, 5744, 0, 6910, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 990, 0, 463, 0, 1516, 0, 2555, 0, 3541, 0, 5750, 0, 6909, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 995, 0, 468, 0, 1522, 0, 2562, 0, 3555, 0, 5760, 0, 6909, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 48, 58, 67, 61, 104, 54, 62, 45, 80, 37, 80, 0, 0, 49, 60 }}, {{ 1000, 0, 474, 0, 1530, 0, 2570, 0, 3573, 0, 5773, 0, 6909, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 49, 58, 68, 61, 104, 54, 62, 45, 80, 37, 80, 0, 0, 50, 60 }}, {{ 1002, 0, 481, 0, 1540, 0, 2581, 0, 3595, 0, 5788, 0, 6910, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 49, 58, 68, 61, 103, 54, 62, 45, 80, 37, 80, 0, 0, 52, 60 }}, {{ 1005, 0, 490, 0, 1554, 0, 2594, 0, 3621, 0, 5805, 0, 6913, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 49, 58, 68, 61, 102, 54, 62, 45, 80, 37, 80, 0, 0, 53, 60 }}, {{ 1008, 0, 501, 0, 1570, 0, 2610, 0, 3650, 0, 5823, 0, 6919, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 49, 58, 68, 61, 102, 54, 62, 46, 80, 37, 80, 0, 0, 54, 60 }}, {{ 1010, 0, 513, 0, 1589, 0, 2628, 0, 3682, 0, 5842, 0, 6928, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 69, 62, 101, 55, 63, 46, 80, 38, 80, 0, 0, 55, 60 }}, {{ 1012, 0, 527, 0, 1611, 0, 2649, 0, 3715, 0, 5860, 0, 6942, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 70, 62, 101, 55, 64, 46, 80, 38, 80, 0, 0, 56, 60 }}, {{ 1015, 0, 543, 0, 1638, 0, 2673, 0, 3750, 0, 5877, 0, 6962, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 71, 62, 102, 55, 66, 46, 80, 38, 80, 0, 0, 58, 60 }}, {{ 1018, 0, 562, 0, 1668, 0, 2700, 0, 3785, 0, 5892, 0, 6990, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 72, 63, 102, 55, 69, 46, 80, 38, 80, 0, 0, 59, 60 }}, {{ 1020, 0, 578, 0, 1698, 0, 2726, 0, 3815, 0, 5902, 0, 7020, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 74, 63, 104, 56, 72, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1022, 0, 594, 0, 1725, 0, 2749, 0, 3839, 0, 5907, 0, 7051, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 76, 63, 105, 56, 75, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1025, 0, 608, 0, 1750, 0, 2771, 0, 3858, 0, 5910, 0, 7082, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 50, 58, 77, 64, 107, 57, 78, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1028, 0, 621, 0, 1773, 0, 2790, 0, 3874, 0, 5910, 0, 7112, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 79, 64, 109, 57, 82, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1030, 0, 631, 0, 1793, 0, 2806, 0, 3887, 0, 5909, 0, 7139, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 80, 64, 110, 57, 84, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1032, 0, 640, 0, 1810, 0, 2820, 0, 3897, 0, 5907, 0, 7163, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 81, 64, 112, 58, 87, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1035, 0, 648, 0, 1824, 0, 2832, 0, 3904, 0, 5905, 0, 7183, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 82, 65, 113, 58, 89, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1038, 0, 653, 0, 1835, 0, 2840, 0, 3909, 0, 5903, 0, 7199, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 83, 65, 114, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1040, 0, 657, 0, 1842, 0, 2846, 0, 3913, 0, 5902, 0, 7210, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1042, 0, 659, 0, 1846, 0, 2849, 0, 3914, 0, 5901, 0, 7215, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 49, 60, 83, 65, 115, 58, 93, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1045, 0, 659, 0, 1846, 0, 2849, 0, 3914, 0, 5901, 0, 7215, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 49, 60, 83, 65, 115, 58, 93, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1048, 0, 658, 0, 1845, 0, 2848, 0, 3914, 0, 5900, 0, 7213, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 93, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1050, 0, 657, 0, 1843, 0, 2847, 0, 3914, 0, 5898, 0, 7207, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1052, 0, 654, 0, 1839, 0, 2845, 0, 3913, 0, 5895, 0, 7200, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 114, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1055, 0, 651, 0, 1835, 0, 2842, 0, 3912, 0, 5891, 0, 7190, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 83, 65, 114, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1058, 0, 648, 0, 1830, 0, 2838, 0, 3911, 0, 5886, 0, 7177, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 82, 65, 113, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1060, 0, 643, 0, 1824, 0, 2833, 0, 3909, 0, 5880, 0, 7163, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 51, 59, 82, 65, 112, 58, 90, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1062, 0, 638, 0, 1816, 0, 2828, 0, 3907, 0, 5873, 0, 7146, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 51, 59, 81, 64, 111, 58, 90, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1065, 0, 632, 0, 1808, 0, 2820, 0, 3903, 0, 5865, 0, 7128, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 51, 59, 80, 64, 110, 57, 89, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1068, 0, 626, 0, 1799, 0, 2812, 0, 3898, 0, 5857, 0, 7107, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 52, 59, 79, 64, 108, 57, 88, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1070, 0, 619, 0, 1789, 0, 2801, 0, 3892, 0, 5849, 0, 7085, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 52, 59, 79, 64, 106, 57, 87, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1072, 0, 611, 0, 1779, 0, 2789, 0, 3884, 0, 5840, 0, 7062, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 53, 58, 78, 64, 105, 56, 85, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1075, 0, 603, 0, 1768, 0, 2775, 0, 3874, 0, 5831, 0, 7038, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 53, 58, 77, 63, 103, 56, 84, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1078, 0, 594, 0, 1756, 0, 2758, 0, 3862, 0, 5821, 0, 7014, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 54, 58, 75, 63, 101, 56, 83, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1080, 0, 585, 0, 1743, 0, 2738, 0, 3847, 0, 5812, 0, 6988, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 54, 58, 74, 63, 99, 55, 81, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1082, 0, 576, 0, 1730, 0, 2715, 0, 3828, 0, 5803, 0, 6963, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 58, 73, 62, 96, 55, 79, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1085, 0, 566, 0, 1717, 0, 2689, 0, 3806, 0, 5794, 0, 6938, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 57, 72, 62, 94, 54, 78, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1088, 0, 556, 0, 1703, 0, 2659, 0, 3780, 0, 5786, 0, 6914, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 57, 70, 61, 91, 54, 76, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1090, 0, 546, 0, 1690, 0, 2624, 0, 3749, 0, 5778, 0, 6890, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 69, 61, 88, 53, 74, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1092, 0, 536, 0, 1676, 0, 2585, 0, 3714, 0, 5772, 0, 6869, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 67, 60, 85, 52, 72, 46, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1095, 0, 525, 0, 1662, 0, 2541, 0, 3672, 0, 5766, 0, 6849, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 66, 60, 82, 52, 70, 46, 80, 38, 80, 0, 0, 60, 60 }}, {{ 1098, 0, 516, 0, 1649, 0, 2496, 0, 3629, 0, 5763, 0, 6833, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 64, 59, 79, 51, 68, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 1100, 0, 507, 0, 1638, 0, 2451, 0, 3585, 0, 5761, 0, 6821, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 63, 58, 76, 50, 66, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 1104, 0, 500, 0, 1628, 0, 2406, 0, 3541, 0, 5760, 0, 6811, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 62, 58, 73, 50, 64, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 1107, 0, 493, 0, 1619, 0, 2362, 0, 3496, 0, 5761, 0, 6805, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 61, 57, 71, 49, 62, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 1110, 0, 487, 0, 1612, 0, 2318, 0, 3452, 0, 5762, 0, 6800, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 60, 56, 68, 49, 61, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1114, 0, 481, 0, 1605, 0, 2276, 0, 3409, 0, 5764, 0, 6798, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 54, 57, 59, 56, 66, 48, 60, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1117, 0, 476, 0, 1599, 0, 2236, 0, 3368, 0, 5766, 0, 6797, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 54, 57, 58, 55, 64, 48, 58, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1121, 0, 472, 0, 1593, 0, 2198, 0, 3328, 0, 5769, 0, 6797, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 57, 55, 62, 48, 57, 47, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1124, 0, 468, 0, 1588, 0, 2161, 0, 3290, 0, 5773, 0, 6798, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 56, 54, 61, 47, 56, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1128, 0, 465, 0, 1584, 0, 2127, 0, 3255, 0, 5776, 0, 6800, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 55, 54, 59, 47, 55, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1131, 0, 462, 0, 1581, 0, 2096, 0, 3222, 0, 5779, 0, 6803, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 57, 55, 53, 58, 47, 54, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1135, 0, 460, 0, 1578, 0, 2068, 0, 3193, 0, 5783, 0, 6805, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 57, 54, 53, 56, 46, 53, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1138, 0, 458, 0, 1576, 0, 2043, 0, 3166, 0, 5786, 0, 6808, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 51, 58, 54, 52, 55, 46, 53, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1142, 0, 456, 0, 1573, 0, 2021, 0, 3143, 0, 5788, 0, 6811, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 51, 58, 54, 52, 54, 46, 52, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1145, 0, 454, 0, 1572, 0, 2003, 0, 3124, 0, 5791, 0, 6813, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 52, 54, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1149, 0, 453, 0, 1571, 0, 1988, 0, 3108, 0, 5793, 0, 6815, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 52, 53, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1152, 0, 452, 0, 1570, 0, 1977, 0, 3096, 0, 5794, 0, 6817, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 53, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1156, 0, 452, 0, 1569, 0, 1969, 0, 3088, 0, 5795, 0, 6818, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1159, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1163, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1166, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1170, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1173, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1177, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1180, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1184, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1187, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1191, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1194, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1198, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 55, 60 }}, {{ 1201, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 50, 60 }}, {{ 1205, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 45, 60 }}, {{ 1208, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 40, 60 }}, {{ 1212, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 35, 60 }}, {{ 1215, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 30, 60 }}, {{ 1219, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 25, 60 }}, {{ 1222, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 20, 60 }}, {{ 1226, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 15, 60 }}, {{ 1229, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 10, 60 }}, {{ 1233, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 5, 60 }}, {{ 1236, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1240, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1244, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1249, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1253, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1257, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1262, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1266, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1270, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1275, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1279, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1283, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1288, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1292, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1296, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1301, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1305, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1309, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1314, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1318, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1322, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1327, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1331, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1335, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1340, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1344, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1348, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1353, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1357, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1361, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1366, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1370, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1374, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1379, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1383, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1387, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1392, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1396, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1400, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1405, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1409, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1413, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1418, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1422, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1426, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1431, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1435, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1439, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1444, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1448, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1452, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1457, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1461, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1465, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1470, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1474, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1478, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1483, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1487, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1491, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1496, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 39, 60 }}, {{ 1500, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 42, 60 }}, {{ 1498, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 45, 60 }}, {{ 1495, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 48, 60 }}, {{ 1492, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 51, 60 }}, {{ 1490, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 54, 60 }}, {{ 1488, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 57, 60 }}, {{ 1485, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1482, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1480, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1478, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 0, 0, 60, 60 }}, {{ 1475, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 1, 0, 60, 60 }}, {{ 1472, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 2, 0, 60, 60 }}, {{ 1470, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 4, 0, 60, 60 }}, {{ 1468, 0, 868, 0, 1313, 0, 2686, 0, 3974, 0, 6346, 0, 7159, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 52, 29, 66, 78, 64, 86, 56, 18, 57, 80, 39, 80, 5, 0, 60, 60 }}, {{ 1465, 0, 858, 0, 1312, 0, 2712, 0, 3995, 0, 6326, 0, 7131, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 51, 29, 66, 78, 65, 89, 57, 19, 57, 80, 39, 80, 7, 0, 59, 60 }}, {{ 1462, 0, 837, 0, 1312, 0, 2761, 0, 4033, 0, 6282, 0, 7081, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 50, 30, 65, 79, 66, 94, 57, 21, 57, 80, 39, 80, 10, 0, 58, 60 }}, {{ 1460, 0, 806, 0, 1319, 0, 2823, 0, 4073, 0, 6213, 0, 7015, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 48, 30, 65, 81, 67, 101, 57, 24, 56, 80, 39, 80, 13, 0, 56, 60 }}, {{ 1458, 0, 767, 0, 1340, 0, 2883, 0, 4099, 0, 6114, 0, 6946, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 45, 28, 65, 84, 68, 111, 58, 28, 56, 80, 39, 80, 16, 0, 54, 60 }}, {{ 1455, 0, 721, 0, 1386, 0, 2922, 0, 4085, 0, 5977, 0, 6890, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 23, 64, 87, 70, 124, 59, 33, 56, 80, 38, 80, 19, 0, 51, 60 }}, {{ 1452, 0, 687, 0, 1439, 0, 2926, 0, 4038, 0, 5858, 0, 6869, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 64, 90, 70, 134, 59, 37, 56, 80, 38, 80, 22, 0, 49, 60 }}, {{ 1450, 0, 663, 0, 1487, 0, 2913, 0, 3981, 0, 5763, 0, 6868, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 64, 92, 71, 142, 60, 41, 56, 80, 37, 80, 25, 0, 48, 60 }}, {{ 1448, 0, 647, 0, 1524, 0, 2896, 0, 3932, 0, 5697, 0, 6873, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 94, 71, 147, 60, 43, 56, 80, 37, 80, 28, 0, 46, 60 }}, {{ 1445, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 30, 0, 45, 60 }}, {{ 1442, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 31, 0, 45, 60 }}, {{ 1440, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 33, 0, 45, 60 }}, {{ 1438, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 34, 0, 45, 60 }}, {{ 1435, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1432, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1430, 0, 640, 0, 1543, 0, 2885, 0, 3905, 0, 5663, 0, 6878, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 56, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1428, 0, 640, 0, 1542, 0, 2883, 0, 3905, 0, 5666, 0, 6876, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 95, 71, 150, 61, 44, 55, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1425, 0, 642, 0, 1539, 0, 2879, 0, 3903, 0, 5674, 0, 6872, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 94, 71, 149, 60, 45, 55, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1422, 0, 644, 0, 1535, 0, 2874, 0, 3902, 0, 5685, 0, 6865, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 93, 70, 148, 60, 45, 55, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1420, 0, 646, 0, 1529, 0, 2867, 0, 3899, 0, 5699, 0, 6857, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 92, 70, 146, 60, 46, 55, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1418, 0, 649, 0, 1523, 0, 2858, 0, 3897, 0, 5716, 0, 6848, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 91, 70, 144, 60, 46, 54, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1415, 0, 653, 0, 1516, 0, 2848, 0, 3894, 0, 5736, 0, 6838, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 90, 69, 142, 59, 47, 54, 80, 37, 80, 35, 0, 45, 60 }}, {{ 1412, 0, 656, 0, 1509, 0, 2837, 0, 3890, 0, 5757, 0, 6827, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 88, 69, 139, 59, 48, 53, 80, 38, 80, 35, 0, 45, 60 }}, {{ 1410, 0, 660, 0, 1503, 0, 2825, 0, 3886, 0, 5781, 0, 6818, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 63, 86, 68, 136, 59, 49, 53, 80, 38, 80, 35, 0, 45, 60 }}, {{ 1408, 0, 663, 0, 1498, 0, 2813, 0, 3882, 0, 5805, 0, 6810, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 62, 85, 68, 133, 58, 50, 52, 80, 38, 80, 35, 0, 45, 60 }}, {{ 1405, 0, 667, 0, 1494, 0, 2800, 0, 3878, 0, 5830, 0, 6804, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 62, 83, 67, 130, 58, 51, 51, 80, 39, 80, 35, 0, 45, 60 }}, {{ 1402, 0, 669, 0, 1492, 0, 2788, 0, 3873, 0, 5855, 0, 6801, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 32, 0, 81, 0, 126, 0, 53, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1400, 0, 671, 0, 1494, 0, 2776, 0, 3869, 0, 5878, 0, 6803, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 36, 0, 79, 0, 123, 0, 55, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1398, 0, 671, 0, 1499, 0, 2765, 0, 3864, 0, 5899, 0, 6811, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 39, 0, 78, 0, 120, 0, 57, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1396, 0, 670, 0, 1509, 0, 2755, 0, 3860, 0, 5918, 0, 6826, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 42, 0, 76, 0, 116, 0, 59, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1394, 0, 667, 0, 1525, 0, 2748, 0, 3856, 0, 5932, 0, 6849, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 45, 0, 75, 0, 113, 0, 61, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1392, 0, 662, 0, 1547, 0, 2743, 0, 3852, 0, 5941, 0, 6882, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 74, 0, 111, 0, 64, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1390, 0, 655, 0, 1578, 0, 2741, 0, 3849, 0, 5944, 0, 6926, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 74, 0, 108, 0, 67, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1388, 0, 646, 0, 1613, 0, 2743, 0, 3847, 0, 5940, 0, 6977, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 74, 0, 106, 0, 70, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1385, 0, 635, 0, 1651, 0, 2748, 0, 3846, 0, 5930, 0, 7033, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 74, 0, 105, 0, 73, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1383, 0, 624, 0, 1691, 0, 2754, 0, 3846, 0, 5917, 0, 7092, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 75, 0, 104, 0, 76, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1381, 0, 612, 0, 1732, 0, 2763, 0, 3845, 0, 5899, 0, 7153, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 48, 0, 76, 0, 104, 0, 79, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1379, 0, 599, 0, 1773, 0, 2773, 0, 3846, 0, 5880, 0, 7214, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 46, 0, 77, 0, 104, 0, 81, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1377, 0, 587, 0, 1815, 0, 2783, 0, 3846, 0, 5859, 0, 7274, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 44, 0, 78, 0, 104, 0, 84, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1375, 0, 575, 0, 1854, 0, 2794, 0, 3847, 0, 5837, 0, 7333, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 42, 0, 80, 0, 105, 0, 86, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1373, 0, 564, 0, 1892, 0, 2804, 0, 3848, 0, 5815, 0, 7388, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 40, 0, 81, 0, 105, 0, 88, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1371, 0, 553, 0, 1927, 0, 2815, 0, 3850, 0, 5795, 0, 7440, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 38, 0, 82, 0, 106, 0, 90, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1369, 0, 543, 0, 1959, 0, 2825, 0, 3851, 0, 5775, 0, 7487, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 37, 0, 84, 0, 106, 0, 91, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1367, 0, 535, 0, 1987, 0, 2833, 0, 3852, 0, 5757, 0, 7528, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 35, 0, 85, 0, 107, 0, 93, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1365, 0, 527, 0, 2011, 0, 2841, 0, 3853, 0, 5742, 0, 7564, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 33, 0, 86, 0, 108, 0, 94, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1363, 0, 521, 0, 2031, 0, 2847, 0, 3854, 0, 5729, 0, 7593, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 32, 0, 86, 0, 108, 0, 95, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1360, 0, 516, 0, 2046, 0, 2852, 0, 3854, 0, 5719, 0, 7615, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 31, 0, 87, 0, 108, 0, 95, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1358, 0, 513, 0, 2056, 0, 2856, 0, 3855, 0, 5712, 0, 7630, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 31, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1356, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1354, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 30, 0, 88, 0, 109, 0, 96, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1352, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 36, 0, 0, 100, 55, 100, 70, 100, 70, 100, 55, 100, 35, 100, 0, 0, 48, 60 }}, {{ 1350, 0, 512, 0, 2061, 0, 2857, 0, 3855, 0, 5709, 0, 7638, 0, 0, 0, 200, 30, 0, 60, 0, 0, 36, 0, 0, 100, 55, 100, 70, 100, 70, 100, 55, 100, 35, 100, 0, 0, 48, 60 }}, {{ 1325, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 47, 0, 69, 0, 99, 0, 56, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1300, 0, 463, 0, 1825, 0, 2082, 0, 2944, 0, 5259, 0, 6818, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 1300, 0, 465, 0, 1830, 0, 2122, 0, 2989, 0, 5250, 0, 6805, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 1285, 0, 468, 0, 1839, 0, 2181, 0, 3055, 0, 5240, 0, 6787, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 16, 57, 74, 60, 131, 56, 72, 46, 80, 35, 80, 0, 0, 50, 60 }}, {{ 1270, 0, 472, 0, 1850, 0, 2257, 0, 3141, 0, 5229, 0, 6765, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 16, 57, 75, 61, 135, 56, 72, 47, 80, 35, 80, 0, 0, 53, 60 }}, {{ 1266, 0, 478, 0, 1863, 0, 2348, 0, 3246, 0, 5221, 0, 6741, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 16, 56, 77, 63, 140, 57, 71, 47, 80, 35, 80, 0, 0, 55, 60 }}, {{ 1263, 0, 485, 0, 1879, 0, 2451, 0, 3367, 0, 5219, 0, 6716, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 15, 56, 80, 65, 145, 58, 70, 48, 80, 36, 80, 0, 0, 58, 60 }}, {{ 1260, 0, 492, 0, 1893, 0, 2533, 0, 3464, 0, 5224, 0, 6699, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 15, 56, 82, 66, 149, 59, 69, 49, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1256, 0, 498, 0, 1903, 0, 2595, 0, 3540, 0, 5232, 0, 6688, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 14, 55, 83, 68, 152, 60, 68, 49, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1253, 0, 503, 0, 1911, 0, 2639, 0, 3595, 0, 5241, 0, 6681, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 13, 55, 84, 68, 155, 60, 66, 50, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1249, 0, 506, 0, 1916, 0, 2668, 0, 3631, 0, 5248, 0, 6677, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 13, 55, 85, 69, 156, 60, 66, 50, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1246, 0, 508, 0, 1919, 0, 2683, 0, 3649, 0, 5252, 0, 6675, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 13, 55, 86, 69, 157, 61, 65, 50, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1242, 0, 508, 0, 1919, 0, 2683, 0, 3649, 0, 5252, 0, 6675, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 13, 55, 86, 69, 157, 61, 65, 50, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1239, 0, 508, 0, 1920, 0, 2679, 0, 3647, 0, 5261, 0, 6676, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 14, 55, 85, 69, 156, 60, 65, 50, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1235, 0, 507, 0, 1922, 0, 2673, 0, 3642, 0, 5281, 0, 6676, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 15, 55, 85, 69, 154, 60, 66, 50, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1232, 0, 505, 0, 1924, 0, 2664, 0, 3637, 0, 5309, 0, 6679, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 18, 55, 84, 69, 152, 60, 66, 50, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1228, 0, 502, 0, 1929, 0, 2653, 0, 3630, 0, 5346, 0, 6684, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 21, 55, 83, 68, 149, 60, 66, 49, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1225, 0, 497, 0, 1937, 0, 2642, 0, 3623, 0, 5389, 0, 6693, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 24, 55, 81, 68, 144, 59, 67, 49, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1221, 0, 491, 0, 1947, 0, 2631, 0, 3617, 0, 5439, 0, 6708, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 28, 54, 80, 67, 140, 59, 67, 48, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1218, 0, 481, 0, 1962, 0, 2623, 0, 3614, 0, 5493, 0, 6731, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 32, 54, 79, 67, 134, 58, 68, 48, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1214, 0, 468, 0, 1983, 0, 2620, 0, 3615, 0, 5549, 0, 6767, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 36, 54, 78, 66, 128, 58, 69, 47, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1211, 0, 451, 0, 2010, 0, 2623, 0, 3622, 0, 5605, 0, 6816, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 40, 54, 78, 66, 122, 57, 70, 47, 80, 36, 80, 0, 0, 60, 60 }}, {{ 1207, 0, 428, 0, 2047, 0, 2636, 0, 3637, 0, 5660, 0, 6884, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 44, 54, 78, 65, 115, 57, 71, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1204, 0, 404, 0, 2084, 0, 2656, 0, 3657, 0, 5701, 0, 6957, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 46, 54, 79, 65, 109, 57, 71, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 1200, 0, 380, 0, 2121, 0, 2680, 0, 3680, 0, 5732, 0, 7030, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 48, 54, 81, 65, 104, 57, 72, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1198, 0, 357, 0, 2157, 0, 2706, 0, 3704, 0, 5754, 0, 7101, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 49, 54, 82, 66, 100, 57, 72, 48, 80, 34, 80, 0, 0, 60, 60 }}, {{ 1196, 0, 337, 0, 2190, 0, 2732, 0, 3727, 0, 5769, 0, 7168, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 49, 53, 84, 66, 97, 57, 73, 48, 80, 33, 80, 0, 0, 60, 60 }}, {{ 1194, 0, 318, 0, 2219, 0, 2756, 0, 3749, 0, 5780, 0, 7227, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 49, 53, 86, 66, 94, 57, 73, 49, 80, 33, 80, 0, 0, 60, 60 }}, {{ 1192, 0, 303, 0, 2243, 0, 2777, 0, 3768, 0, 5787, 0, 7276, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 33, 49, 53, 87, 66, 92, 57, 73, 49, 80, 32, 80, 0, 0, 60, 60 }}, {{ 1190, 0, 291, 0, 2262, 0, 2794, 0, 3783, 0, 5791, 0, 7315, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 33, 49, 53, 88, 66, 90, 57, 74, 49, 80, 32, 80, 0, 0, 59, 60 }}, {{ 1188, 0, 282, 0, 2274, 0, 2806, 0, 3793, 0, 5793, 0, 7341, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 33, 49, 53, 89, 67, 89, 57, 74, 49, 80, 32, 80, 0, 0, 58, 60 }}, {{ 1186, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 0, 0, 56, 60 }}, {{ 1184, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 32, 49, 53, 89, 67, 89, 57, 74, 50, 80, 32, 80, 0, 0, 53, 60 }}, {{ 1182, 0, 296, 0, 2239, 0, 2788, 0, 3785, 0, 5799, 0, 7313, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 33, 49, 54, 87, 66, 90, 57, 73, 49, 80, 32, 80, 0, 0, 49, 60 }}, {{ 1180, 0, 331, 0, 2156, 0, 2745, 0, 3761, 0, 5809, 0, 7235, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 50, 54, 84, 65, 92, 57, 73, 48, 80, 33, 80, 0, 0, 45, 60 }}, {{ 1178, 0, 379, 0, 2033, 0, 2693, 0, 3731, 0, 5821, 0, 7136, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 51, 54, 79, 64, 94, 56, 71, 47, 80, 34, 80, 0, 0, 39, 60 }}, {{ 1176, 0, 436, 0, 1873, 0, 2648, 0, 3705, 0, 5836, 0, 7035, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 39, 51, 55, 74, 63, 97, 55, 69, 46, 80, 36, 80, 0, 0, 35, 60 }}, {{ 1174, 0, 496, 0, 1678, 0, 2629, 0, 3693, 0, 5851, 0, 6958, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 51, 57, 70, 62, 99, 55, 65, 46, 80, 37, 80, 0, 0, 31, 60 }}, {{ 1172, 0, 534, 0, 1526, 0, 2643, 0, 3701, 0, 5860, 0, 6935, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 68, 61, 99, 54, 62, 46, 80, 38, 80, 0, 0, 28, 60 }}, {{ 1170, 0, 558, 0, 1414, 0, 2672, 0, 3717, 0, 5865, 0, 6942, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 48, 60, 68, 61, 99, 54, 59, 46, 80, 38, 80, 0, 0, 26, 60 }}, {{ 1168, 0, 571, 0, 1341, 0, 2699, 0, 3732, 0, 5868, 0, 6957, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 60, 68, 61, 99, 55, 57, 46, 80, 39, 80, 0, 0, 25, 60 }}, {{ 1166, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 1164, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 1162, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1160, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1149, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1138, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1127, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1116, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1105, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1094, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1083, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1072, 0, 278, 0, 2281, 0, 2812, 0, 3799, 0, 5795, 0, 7354, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 49, 0, 89, 0, 89, 0, 74, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 1061, 0, 235, 0, 1987, 0, 2058, 0, 2877, 0, 5298, 0, 6768, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 1050, 0, 238, 0, 2002, 0, 2134, 0, 2950, 0, 5285, 0, 6756, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 985, 0, 241, 0, 2025, 0, 2244, 0, 3056, 0, 5269, 0, 6741, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 37, 43, 49, 63, 60, 113, 55, 74, 42, 80, 34, 80, 0, 0, 51, 60 }}, {{ 920, 0, 247, 0, 2056, 0, 2385, 0, 3193, 0, 5258, 0, 6725, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 41, 48, 66, 62, 123, 57, 76, 42, 80, 35, 80, 0, 0, 54, 60 }}, {{ 919, 0, 256, 0, 2094, 0, 2551, 0, 3356, 0, 5257, 0, 6714, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 39, 48, 71, 65, 135, 59, 76, 43, 80, 35, 80, 0, 0, 57, 60 }}, {{ 918, 0, 264, 0, 2125, 0, 2675, 0, 3479, 0, 5269, 0, 6712, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 37, 48, 74, 67, 144, 60, 76, 44, 80, 35, 80, 0, 0, 60, 60 }}, {{ 916, 0, 271, 0, 2147, 0, 2763, 0, 3568, 0, 5284, 0, 6715, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 36, 48, 77, 68, 150, 61, 76, 44, 80, 35, 80, 0, 0, 59, 60 }}, {{ 915, 0, 276, 0, 2162, 0, 2820, 0, 3625, 0, 5297, 0, 6718, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 35, 47, 79, 69, 154, 62, 75, 45, 80, 35, 80, 0, 0, 57, 60 }}, {{ 914, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 54, 60 }}, {{ 912, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 34, 34, 47, 79, 70, 156, 62, 75, 45, 80, 35, 80, 0, 0, 50, 60 }}, {{ 911, 0, 302, 0, 2106, 0, 2821, 0, 3654, 0, 5360, 0, 6743, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 35, 35, 49, 79, 69, 151, 61, 73, 45, 80, 35, 80, 0, 0, 45, 60 }}, {{ 910, 0, 346, 0, 1982, 0, 2775, 0, 3659, 0, 5461, 0, 6786, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 36, 38, 51, 77, 68, 143, 60, 70, 45, 80, 36, 80, 0, 0, 39, 60 }}, {{ 909, 0, 409, 0, 1806, 0, 2724, 0, 3669, 0, 5594, 0, 6843, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 38, 41, 54, 75, 66, 131, 59, 65, 46, 80, 36, 80, 0, 0, 34, 60 }}, {{ 908, 0, 483, 0, 1590, 0, 2691, 0, 3691, 0, 5734, 0, 6905, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 44, 57, 73, 64, 117, 57, 60, 46, 80, 37, 80, 0, 0, 30, 60 }}, {{ 906, 0, 533, 0, 1441, 0, 2692, 0, 3713, 0, 5813, 0, 6941, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 46, 59, 71, 62, 107, 56, 58, 47, 80, 38, 80, 0, 0, 27, 60 }}, {{ 905, 0, 562, 0, 1349, 0, 2705, 0, 3731, 0, 5853, 0, 6960, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 46, 60, 69, 61, 102, 55, 57, 47, 80, 39, 80, 0, 0, 25, 60 }}, {{ 904, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 902, 0, 576, 0, 1305, 0, 2715, 0, 3741, 0, 5869, 0, 6968, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 47, 61, 69, 61, 99, 55, 56, 47, 80, 39, 80, 0, 0, 24, 60 }}, {{ 901, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 279, 0, 2170, 0, 2847, 0, 3653, 0, 5305, 0, 6720, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 34, 0, 79, 0, 156, 0, 75, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 900, 0, 462, 0, 1513, 0, 2553, 0, 3535, 0, 5746, 0, 6910, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 900, 0, 466, 0, 1520, 0, 2560, 0, 3550, 0, 5757, 0, 6909, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 100, 50, 100, 50, 100, 50, 100, 35, 100, 0, 100, 0, 0, 60, 60 }}, {{ 870, 0, 474, 0, 1530, 0, 2570, 0, 3573, 0, 5773, 0, 6909, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 40, 49, 58, 68, 61, 104, 54, 62, 45, 80, 37, 80, 0, 0, 50, 60 }}, {{ 840, 0, 484, 0, 1544, 0, 2585, 0, 3603, 0, 5793, 0, 6911, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 49, 58, 68, 61, 103, 54, 62, 45, 80, 37, 80, 0, 0, 51, 60 }}, {{ 840, 0, 496, 0, 1563, 0, 2603, 0, 3638, 0, 5816, 0, 6916, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 49, 58, 68, 61, 102, 54, 62, 45, 80, 37, 80, 0, 0, 53, 60 }}, {{ 839, 0, 512, 0, 1587, 0, 2626, 0, 3679, 0, 5840, 0, 6927, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 50, 58, 69, 62, 101, 55, 63, 46, 80, 37, 80, 0, 0, 55, 60 }}, {{ 839, 0, 530, 0, 1616, 0, 2654, 0, 3722, 0, 5864, 0, 6945, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 70, 62, 101, 55, 65, 46, 80, 38, 80, 0, 0, 57, 60 }}, {{ 839, 0, 552, 0, 1652, 0, 2686, 0, 3767, 0, 5885, 0, 6975, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 72, 62, 102, 55, 67, 46, 80, 38, 80, 0, 0, 58, 60 }}, {{ 838, 0, 575, 0, 1691, 0, 2720, 0, 3808, 0, 5900, 0, 7012, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 74, 63, 103, 56, 71, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 838, 0, 595, 0, 1726, 0, 2750, 0, 3840, 0, 5907, 0, 7053, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 58, 76, 63, 105, 56, 75, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 838, 0, 612, 0, 1758, 0, 2777, 0, 3864, 0, 5910, 0, 7092, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 50, 59, 78, 64, 108, 57, 79, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 837, 0, 627, 0, 1786, 0, 2800, 0, 3882, 0, 5910, 0, 7129, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 79, 64, 110, 57, 83, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 837, 0, 640, 0, 1809, 0, 2819, 0, 3896, 0, 5908, 0, 7161, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 81, 64, 112, 58, 87, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 837, 0, 649, 0, 1826, 0, 2833, 0, 3905, 0, 5905, 0, 7186, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 82, 65, 113, 58, 90, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 836, 0, 655, 0, 1838, 0, 2843, 0, 3911, 0, 5903, 0, 7204, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 836, 0, 658, 0, 1844, 0, 2848, 0, 3914, 0, 5901, 0, 7213, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 836, 0, 658, 0, 1844, 0, 2848, 0, 3914, 0, 5901, 0, 7213, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 835, 0, 658, 0, 1844, 0, 2848, 0, 3914, 0, 5899, 0, 7211, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 115, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 835, 0, 655, 0, 1840, 0, 2845, 0, 3913, 0, 5895, 0, 7202, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 60, 83, 65, 114, 58, 92, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 835, 0, 651, 0, 1834, 0, 2841, 0, 3912, 0, 5890, 0, 7188, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 50, 59, 83, 65, 114, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 834, 0, 646, 0, 1827, 0, 2836, 0, 3910, 0, 5883, 0, 7171, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 51, 59, 82, 65, 112, 58, 91, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 834, 0, 639, 0, 1818, 0, 2829, 0, 3907, 0, 5874, 0, 7149, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 51, 59, 81, 64, 111, 58, 90, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 834, 0, 631, 0, 1807, 0, 2819, 0, 3903, 0, 5864, 0, 7124, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 52, 59, 80, 64, 109, 57, 88, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 833, 0, 622, 0, 1795, 0, 2807, 0, 3896, 0, 5853, 0, 7097, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 52, 59, 79, 64, 107, 57, 87, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 833, 0, 612, 0, 1781, 0, 2791, 0, 3886, 0, 5841, 0, 7066, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 53, 58, 78, 64, 105, 56, 86, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 833, 0, 602, 0, 1766, 0, 2772, 0, 3873, 0, 5829, 0, 7034, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 53, 58, 76, 63, 102, 56, 84, 44, 80, 39, 80, 0, 0, 60, 60 }}, {{ 832, 0, 590, 0, 1750, 0, 2748, 0, 3855, 0, 5816, 0, 7001, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 54, 58, 75, 63, 100, 55, 82, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 832, 0, 578, 0, 1733, 0, 2719, 0, 3832, 0, 5804, 0, 6967, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 58, 73, 62, 97, 55, 80, 45, 80, 39, 80, 0, 0, 60, 60 }}, {{ 832, 0, 565, 0, 1715, 0, 2684, 0, 3802, 0, 5792, 0, 6934, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 57, 71, 62, 93, 54, 77, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 831, 0, 551, 0, 1697, 0, 2642, 0, 3766, 0, 5782, 0, 6902, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 55, 57, 70, 61, 89, 53, 75, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 831, 0, 538, 0, 1678, 0, 2592, 0, 3720, 0, 5773, 0, 6872, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 68, 60, 86, 52, 72, 45, 80, 38, 80, 0, 0, 60, 60 }}, {{ 831, 0, 524, 0, 1660, 0, 2533, 0, 3665, 0, 5766, 0, 6846, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 66, 60, 81, 52, 69, 46, 80, 38, 80, 0, 0, 60, 60 }}, {{ 830, 0, 512, 0, 1644, 0, 2473, 0, 3607, 0, 5762, 0, 6826, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 41, 56, 57, 64, 59, 77, 51, 67, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 830, 0, 501, 0, 1630, 0, 2413, 0, 3548, 0, 5760, 0, 6813, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 62, 58, 74, 50, 64, 46, 80, 37, 80, 0, 0, 60, 60 }}, {{ 830, 0, 492, 0, 1618, 0, 2354, 0, 3489, 0, 5761, 0, 6804, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 55, 57, 60, 57, 70, 49, 62, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 830, 0, 484, 0, 1608, 0, 2297, 0, 3430, 0, 5763, 0, 6799, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 54, 57, 59, 56, 67, 49, 60, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 830, 0, 477, 0, 1599, 0, 2242, 0, 3374, 0, 5766, 0, 6797, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 42, 54, 57, 58, 55, 65, 48, 58, 46, 80, 36, 80, 0, 0, 60, 60 }}, {{ 830, 0, 471, 0, 1592, 0, 2191, 0, 3321, 0, 5770, 0, 6797, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 57, 54, 62, 48, 57, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 830, 0, 467, 0, 1586, 0, 2144, 0, 3272, 0, 5774, 0, 6799, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 53, 57, 56, 54, 60, 47, 55, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 830, 0, 463, 0, 1581, 0, 2101, 0, 3227, 0, 5779, 0, 6802, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 57, 55, 53, 58, 47, 54, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 830, 0, 459, 0, 1578, 0, 2063, 0, 3188, 0, 5783, 0, 6806, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 52, 57, 54, 53, 56, 46, 53, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 830, 0, 457, 0, 1574, 0, 2031, 0, 3154, 0, 5787, 0, 6810, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 43, 51, 58, 54, 52, 55, 46, 52, 47, 80, 35, 80, 0, 0, 60, 60 }}, {{ 830, 0, 455, 0, 1572, 0, 2005, 0, 3126, 0, 5790, 0, 6813, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 52, 54, 46, 52, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 453, 0, 1570, 0, 1986, 0, 3105, 0, 5793, 0, 6816, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 51, 58, 53, 52, 53, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1972, 0, 3091, 0, 5795, 0, 6818, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 46, 51, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 60, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 53, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 47, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 40, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 33, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 27, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 20, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 14, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 44, 50, 58, 53, 51, 52, 45, 50, 47, 80, 34, 80, 0, 0, 7, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 452, 0, 1569, 0, 1966, 0, 3084, 0, 5796, 0, 6819, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 50, 0, 53, 0, 52, 0, 50, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }}, {{ 830, 0, 920, 0, 1445, 0, 2804, 0, 3915, 0, 5969, 0, 6256, 0, 0, 0, 200, 30, 0, 60, 0, 0, 0, 0, 0, 87, 0, 62, 0, 103, 0, 105, 0, 80, 0, 80, 0, 0, 0, 60 }} }; try { autoKlattTable me = (KlattTable) Thing_new (KlattTable); Table_initWithColumnNames (me.peek(), nrows, columnNames); for (long irow = 1; irow <= nrows; irow++) { for (long jcol = 1; jcol <= KlattTable_NPAR; jcol++) { double val = klatt_data[irow - 1].p[jcol - 1]; if (jcol > 3 && jcol < 13 && (jcol % 2 == 0) && val <= 0) { // bw == 0? val = klatt_data[irow - 1].p[jcol] / 10; } Table_setNumericValue ( (Table) me.peek(), irow, jcol, val); } } return me.transfer(); } catch (MelderError) { Melder_throw (" KlattTable example not created."); } } KlattTable Table_to_KlattTable (Table me) { try { if (my numberOfColumns != KlattTable_NPAR) { Melder_throw ("A KlattTable needs ", KlattTable_NPAR, L" columns."); } autoKlattTable thee = Thing_new (KlattTable); my structTable :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw ("KlattTable not created from Table."); } } Table KlattTable_to_Table (KlattTable me) { try { autoTable thee = Thing_new (Table); my structTable :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw ("Table not created from KlattTable."); } } /* End of file KlattTable.cpp */ sources_5316/dwtools/MDS.cpp0000644000176700017670000032401211725074655014563 0ustar paulpaul/* MDS.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020408 GPL djmw 20020513 Applied TableOfReal_setSequential{Column/Row}Labels djmw 20030623 Modified calls to NUMeigensystem_d djmw 20040309 Extra tests for empty objects. djmw 20061218 Changed to Melder_information format. djmw 20071022 Removed unused code. djmw 20071106 drawSplines: to wchar_t djmw 20071201 Melder_warning djmw 20071213 Removed Preference. djmw 20080724 Thing_classNameW ->Thing_className djmw 20110304 Thing_new */ #include "SVD.h" #include "Matrix_extensions.h" #include "TableOfReal_extensions.h" #include "MDS.h" #include "SSCP.h" #include "PCA.h" #define TINY 1e-30 /********************** NUMERICAL STUFF **************************************/ static void NUMdmatrix_into_vector (double **m, double *v, long r1, long r2, long c1, long c2) { long k = 1; for (long i = r1; i <= r2; i++) { for (long j = c1; j <= c2; j++) { v[k++] = m[i][j]; } } } static void NUMdvector_into_matrix (const double *v, double **m, long r1, long r2, long c1, long c2) { long k = 1; for (long i = r1; i <= r2; i++) { for (long j = c1; j <= c2; j++) { m[i][j] = v[k++]; } } } static void NUMdmatrix_normalizeRows (double **m, long nr, long nc) { for (long i = 1; i <= nr; i++) { double rowSum = 0; for (long j = 1; j <= nc; j++) { rowSum += m[i][j]; } if (rowSum != 0) { for (long j = 1; j <= nc; j++) { m[i][j] /= rowSum; } } } } static long NUMdmatrix_countZeros (double **m, long nr, long nc) { long nZeros = 0; for (long i = 1; i <= nr; i++) { for (long j = 1; j <= nc; j++) { if (m[i][j] == 0) { nZeros++; } } } return nZeros; } static void NUMsort3 (double *data, long *iPoint, long *jPoint, long ifrom, long ito, int ascending) { if (ifrom > ito || ifrom < 1) { Melder_throw ("invalid range."); } long n = ito - ifrom + 1; if (n == 1) { return; } autoNUMvector indx (ifrom, ito); autoNUMvector atmp (ifrom, ito); autoNUMvector itmp (ifrom, ito); //NUMindexx (data + ifrom - 1, n, indx + ifrom - 1); NUMindexx (&data [ifrom - 1], n, &indx [ifrom - 1]); if (! ascending) { for (long j = ifrom; j <= ifrom + n / 2; j++) { long tmp = indx[j]; indx[j] = indx[ito - j + ifrom]; indx[ito - j + ifrom] = tmp; } } for (long j = ifrom; j <= ito; j++) { indx[j] += ifrom - 1; } for (long j = ifrom; j <= ito; j++) { atmp[j] = data[j]; } for (long j = ifrom; j <= ito; j++) { data[j] = atmp[indx[j]]; } for (long j = ifrom; j <= ito; j++) { itmp[j] = iPoint[j]; } for (long j = ifrom; j <= ito; j++) { iPoint[j] = itmp[indx[j]]; } for (long j = ifrom; j <= ito; j++) { itmp[j] = jPoint[j]; } for (long j = ifrom; j <= ito; j++) { jPoint[j] = itmp[indx[j]]; } } /************ Configurations & Similarity **************************/ Distances Configurations_to_Distances (Configurations me) { try { autoDistances thee = Distances_create (); for (long i = 1; i <= my size; i++) { Configuration conf = (Configuration) (my item[i]); autoDistance d = Configuration_to_Distance (conf); Thing_setName (d.peek(), Thing_getName (conf)); Collection_addItem (thee.peek(), d.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw ("Distances not created form Configurations."); } } Similarity Configurations_to_Similarity_cc (Configurations me, Weight weight) { try { autoDistances d = Configurations_to_Distances (me); autoSimilarity thee = Distances_to_Similarity_cc (d.peek(), weight); return thee.transfer(); } catch (MelderError) { Melder_throw ("Similarity not created form Configurations."); } } Similarity Distances_to_Similarity_cc (Distances me, Weight w) { try { if (my size == 0) { Melder_throw ("Distances is empty."); } if (! TablesOfReal_checkDimensions (me)) { Melder_throw ("All matrices must have the same dimensions."); } autoWeight aw = 0; if (w == 0) { aw.reset (Weight_create ( ( (Distance) (my item[1])) -> numberOfRows)); w = aw.peek(); } autoSimilarity thee = Similarity_create (my size); for (long i = 1; i <= my size; i++) { Distance di = (Distance) (my item[i]); wchar_t *name = Thing_getName (di); TableOfReal_setRowLabel (thee.peek(), i, name); TableOfReal_setColumnLabel (thee.peek(), i, name); thy data[i][i] = 1; for (long j = i + 1; j <= my size; j++) { Distance dj = (Distance) (my item[j]); thy data[i][j] = thy data[j][i] = Distance_Weight_congruenceCoefficient (di, dj, w); } } return thee.transfer(); } catch (MelderError) { Melder_throw ("Similarity not created form Distancess."); } } /***************** Transformator **********************************************/ Thing_implement (Transformator, Thing, 0); Distance structTransformator :: v_transform (MDSVec vec, Distance dist, Weight w) { try { (void) w; autoDistance thee = Distance_create (numberOfPoints); TableOfReal_copyLabels (dist, thee.peek(), 1, 1); /* Absolute scaling */ for (long i = 1; i <= vec -> nProximities; i++) { long ii = vec -> iPoint[i]; long jj = vec -> jPoint[i]; thy data[ii][jj] = thy data[jj][ii] = vec -> proximity[i]; } return thee.transfer(); } catch (MelderError) { Melder_throw ("Distance not created."); } } void Transformator_init (I, long numberOfPoints) { iam (Transformator); my numberOfPoints = numberOfPoints; my normalization = 1; } Transformator Transformator_create (long numberOfPoints) { try { autoTransformator me = Thing_new (Transformator); Transformator_init (me.peek(), numberOfPoints); my normalization = 0; return me.transfer(); } catch (MelderError) { Melder_throw ("No Transformator created."); } } Distance Transformator_transform (I, MDSVec vec, Distance d, Weight w) { iam (Transformator); try { if (my numberOfPoints != vec -> nPoints || my numberOfPoints != d -> numberOfRows || d -> numberOfRows != w -> numberOfRows) { Melder_throw (L"Dimensions do not agree."); } return my v_transform (vec, d, w); } catch (MelderError) { Melder_throw (me, "Distance not created."); } } Thing_implement (RatioTransformator, Transformator, 0); Distance structRatioTransformator :: v_transform (MDSVec vec, Distance d, Weight w) { autoDistance thee = Distance_create (numberOfPoints); TableOfReal_copyLabels (d, thee.peek(), 1, 1); // Determine ratio (eq. 9.4) double etaSq = 0, rho = 0; for (long i = 1; i <= vec -> nProximities; i++) { long ii = vec -> iPoint[i]; long jj = vec -> jPoint[i]; double delta_ij = vec -> proximity[i], d_ij = d -> data[ii][jj]; double tmp = w -> data[ii][jj] * delta_ij * delta_ij; etaSq += tmp; rho += tmp * d_ij * d_ij; } // transform if (etaSq == 0) { Melder_throw ("Eta squared is zero."); } this -> ratio = rho / etaSq; for (long i = 1; i <= vec -> nProximities; i++) { long ii = vec -> iPoint[i]; long jj = vec -> jPoint[i]; thy data[ii][jj] = thy data[jj][ii] = this -> ratio * vec -> proximity[i]; } if (normalization) { Distance_Weight_smacofNormalize (thee.peek(), w); } return thee.transfer(); } RatioTransformator RatioTransformator_create (long numberOfPoints) { try { autoRatioTransformator me = Thing_new (RatioTransformator); Transformator_init (me.peek(), numberOfPoints); return me.transfer(); } catch (MelderError) { Melder_throw ("RatioTransformator not created."); } } Thing_implement (MonotoneTransformator, Transformator, 0); Distance structMonotoneTransformator :: v_transform (MDSVec vec, Distance d, Weight w) { try { autoDistance thee = MDSVec_Distance_monotoneRegression (vec, d, tiesProcessing); if (normalization) { Distance_Weight_smacofNormalize (thee.peek(), w); } return thee.transfer(); } catch (MelderError) { Melder_throw ("Distance not created."); } } MonotoneTransformator MonotoneTransformator_create (long numberOfPoints) { try { autoMonotoneTransformator me = Thing_new (MonotoneTransformator); Transformator_init (me.peek(), numberOfPoints); my tiesProcessing = MDS_PRIMARY_APPROACH; return me.transfer(); } catch (MelderError) { Melder_throw ("MonotoneTransformator not created."); } } void MonotoneTransformator_setTiesProcessing (MonotoneTransformator me, int tiesProcessing) { my tiesProcessing = tiesProcessing; } Thing_implement (ISplineTransformator, Transformator, 0); void structISplineTransformator :: v_destroy () { NUMvector_free (b, 1); NUMvector_free (knot, 1); NUMmatrix_free (m, 1, 1); ISplineTransformator_Parent :: v_destroy (); } Distance structISplineTransformator :: v_transform (MDSVec vec, Distance dist, Weight w) { double tol = 1e-6; long itermax = 20, nx = vec -> nProximities; long nKnots = numberOfInteriorKnots + order + order + 2; autoDistance thee = Distance_create (dist -> numberOfRows); TableOfReal_copyLabels (dist, thee.peek(), 1, -1); autoNUMvector d (1, nx); for (long i = 1; i <= nx; i++) { d[i] = dist -> data[vec -> iPoint[i]][vec -> jPoint[i]]; } /* Process knots. Put interior knots at quantiles. Guarantee that for each proximity x[i]: knot[j] <= x[i] < knot[j+1] */ for (long i = 1; i <= order + 1; i++) { knot [i] = vec -> proximity [1]; knot [nKnots - i + 1] = vec -> proximity [nx] * 1.000001; } for (long i = 1; i <= numberOfInteriorKnots; i++) { double fraction = (double) i / (numberOfInteriorKnots + 1); knot [order + 1 + i] = NUMquantile (nx, vec -> proximity, fraction); } /* Calculate data matrix m. */ for (long i = 1; i <= nx; i++) { double y, x = vec -> proximity [i]; m [i] [1] = 1; for (long j = 2; j <= numberOfParameters; j++) { try { NUMispline (knot, nKnots, order, j - 1, x, & y); } catch (MelderError) { Melder_throw ("I-spline[", j - 1, "], data[", i, "d] = ", x); } m [i] [j] = y; } } NUMsolveNonNegativeLeastSquaresRegression (m, nx, numberOfParameters, d.peek(), tol, itermax, b); for (long i = 1; i <= nx; i++) { long ii = vec->iPoint[i]; long jj = vec->jPoint[i]; double r = 0; for (long j = 1; j <= numberOfParameters; j++) { r += m[i][j] * b[j]; } thy data[ii][jj] = thy data[jj][ii] = r; } if (normalization) { Distance_Weight_smacofNormalize (thee.peek(), w); } return thee.transfer(); } ISplineTransformator ISplineTransformator_create (long numberOfPoints, long numberOfInteriorKnots, long order) { try { autoISplineTransformator me = Thing_new (ISplineTransformator); long nData = (numberOfPoints - 1) * numberOfPoints / 2; Transformator_init (me.peek(), numberOfPoints); /* 1 extra parameter for the intercept. 2 extra knots for the I-spline. */ my numberOfParameters = numberOfInteriorKnots + order + 1; long numberOfKnots = numberOfInteriorKnots + order + order + 2; my b = NUMvector (1, my numberOfParameters); my knot = NUMvector (1, numberOfKnots); my m = NUMmatrix (1, nData, 1, my numberOfParameters); for (long i = 1; i <= my numberOfParameters; i++) { my b[i] = NUMrandomUniform (0, 1); } my numberOfInteriorKnots = numberOfInteriorKnots; my order = order; return me.transfer(); } catch (MelderError) { Melder_throw ("ISplineTransformator not created."); } } /***************** CONTINGENCYTABLE **************************************/ Configuration ContingencyTable_to_Configuration_ca (ContingencyTable me, long numberOfDimensions, int scaling) { try { long nr = my numberOfRows, nc = my numberOfColumns; long dimmin = nr < nc ? nr : nc; autoNUMmatrix h (NUMmatrix_copy (my data, 1, nr, 1, nc), 1, 1); autoNUMvector rowsum (1, nr); autoNUMvector colsum (1, nc); autoConfiguration thee = Configuration_create (nr + nc, numberOfDimensions); if (numberOfDimensions == 0) { numberOfDimensions = dimmin - 1; } if (numberOfDimensions >= dimmin) { Melder_throw ("Dimension too high."); } /* Ref: A. Gifi (1990), Nonlinear Multivariate Analysis, Wiley & Sons, reprinted 1996, Chapter 8, Multidimensional scaling and Correspondence Analysis. Get row and column marginals */ double sum = 0; for (long i = 1; i <= nr; i++) { for (long j = 1; j <= nc; j++) { rowsum[i] += my data[i][j]; colsum[j] += my data[i][j]; } if (rowsum[i] <= 0) { Melder_throw ("Empty row: ", i, "."); } sum += rowsum[i]; } for (long j = 1; j <= nc; j++) { if (colsum[j] <= 0) { Melder_throw ("Empty column: ", j, "."); } } /* Remove trivial singular vectors (Eq. 8.24), construct Dr^(-1/2) H Dc^(-1/2) - Dr^(1/2) uu' Dc^(1/2) / N */ for (long i = 1; i <= nr; i++) { for (long j = 1; j <= nc; j++) { double rc = sqrt (rowsum[i] * colsum[j]); h[i][j] = h[i][j] / rc - rc / sum; } } /* Singular value decomposition of h */ autoSVD svd = SVD_create_d (h.peek(), nr, nc); SVD_zeroSmallSingularValues (svd.peek(), 0); /* Scale row vectors and column vectors to configuration. */ for (long j = 1; j <= numberOfDimensions; j++) { double rootsum = sqrt (sum), xfactor, yfactor, lambda = svd -> d[j]; if (scaling == 1) { /* Scale row points in the centre of gravity of column points (eq 8.5.a) */ xfactor = rootsum * lambda; yfactor = rootsum; } else if (scaling == 2) { /* Scale column points in the centre of gravity of row points (8.5.b) */ xfactor = rootsum; yfactor = rootsum * lambda; } else if (scaling == 3) { /* Treat row and columns symmetrically (8.5.c). */ xfactor = yfactor = rootsum * sqrt (lambda); } else { break; } for (long i = 1; i <= nr; i++) { thy data[i][j] = svd -> u[i][j] * xfactor / sqrt (rowsum[i]); } for (long i = 1; i <= nc; i++) { thy data[nr + i][j] = svd -> v[i][j] * yfactor / sqrt (colsum[i]); } } TableOfReal_setSequentialColumnLabels (thee.peek(), 0, 0, NULL, 1, 1); NUMstrings_copyElements (my rowLabels, thy rowLabels, 1, nr); for (long i = 1; i <= nc; i++) { if (my columnLabels[i]) { TableOfReal_setRowLabel (thee.peek(), nr + i, my columnLabels[i]); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created."); } } Dissimilarity TableOfReal_to_Dissimilarity (I) { iam (TableOfReal); try { if (my numberOfRows != my numberOfColumns) { Melder_throw ("TableOfReal must be a square tabel."); } TableOfReal_checkPositive (me); autoDissimilarity thee = Thing_new (Dissimilarity); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Dissimilarity."); } } Similarity TableOfReal_to_Similarity (I) { iam (TableOfReal); try { if (my numberOfRows != my numberOfColumns) { Melder_throw ("TableOfReal must be a square table."); } TableOfReal_checkPositive (me); autoSimilarity thee = Thing_new (Similarity); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Similarity."); } } Distance TableOfReal_to_Distance (I) { iam (TableOfReal); try { if (my numberOfRows != my numberOfColumns) { Melder_throw ("TableOfReal must be a square table."); } TableOfReal_checkPositive (me); autoDistance thee = Thing_new (Distance); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Distance."); } } Salience TableOfReal_to_Salience (I) { iam (TableOfReal); try { TableOfReal_checkPositive (me); autoSalience thee = Thing_new (Salience); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Salience."); } } Weight TableOfReal_to_Weight (I) { iam (TableOfReal); try { TableOfReal_checkPositive (me); autoWeight thee = Thing_new (Weight); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Weight."); } } ScalarProduct TableOfReal_to_ScalarProduct (I) { iam (TableOfReal); try { if (my numberOfRows != my numberOfColumns) { Melder_throw ("TableOfReal must be a square table."); } autoScalarProduct thee = Thing_new (ScalarProduct); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to ScalarProduct."); } } /**************** Covariance & Correlation to Configuration *****************/ Configuration SSCP_to_Configuration (I, long numberOfDimensions) { iam (SSCP); try { autoConfiguration thee = Configuration_create (my numberOfRows, numberOfDimensions); autoPCA a = SSCP_to_PCA (me); TableOfReal_setSequentialColumnLabels (thee.peek(), 0, 0, NULL, 1, 1); for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= numberOfDimensions; j++) { double s = 0; for (long k = 1; k <= my numberOfRows; k++) { s += my data[k][i] * a -> eigenvectors[k][j]; } thy data[i][j] = s; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created."); } } Configuration Covariance_to_Configuration (Covariance me, long numberOfDimensions) { return SSCP_to_Configuration (me, numberOfDimensions); } Configuration Correlation_to_Configuration (Correlation me, long numberOfDimensions) { return SSCP_to_Configuration (me, numberOfDimensions); } /**************************** Weight *****************************************/ Thing_implement (Weight, TableOfReal, 0); Weight Weight_create (long numberOfPoints) { try { autoWeight me = Thing_new (Weight); TableOfReal_init (me.peek(), numberOfPoints, numberOfPoints); for (long i = 1; i <= numberOfPoints; i++) { for (long j = 1; j <= numberOfPoints; j++) { my data[i][j] = 1; } } return me.transfer(); } catch (MelderError) { Melder_throw ("Weight not created."); } } /**************** Salience *****************************************/ Thing_implement (Salience, TableOfReal, 0); Salience Salience_create (long numberOfSources, long numberOfDimensions) { try { autoSalience me = Thing_new (Salience); TableOfReal_init (me.peek(), numberOfSources, numberOfDimensions); Salience_setDefaults (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("Salience not created."); } } long Salience_correctNegatives (Salience me) { /* The weights might be negative. We correct this by simply making them positive. */ long nNegatives = 0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { if (my data[i][j] < 0) { nNegatives++; my data[i][j] = - my data[i][j]; } } } return nNegatives; } void Salience_setDefaults (Salience me) { for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { my data[i][j] = 1 / sqrt (my numberOfColumns); } } for (long j = 1; j <= my numberOfColumns; j++) { wchar_t s[40]; swprintf (s, 40, L"dimension %ld", j); TableOfReal_setColumnLabel (me, j, s); } } void Salience_draw (Salience me, Graphics g, int ix, int iy, int garnish) { long nc2, nc1 = ix < iy ? (nc2 = iy, ix) : (nc2 = ix, iy); double xmin = 0, xmax = 1, ymin = 0, ymax = 1, wmax = 1; if (ix < 1 || ix > my numberOfColumns || iy < 1 || iy > my numberOfColumns) { return; } for (long i = 1; i <= my numberOfRows; i++) { for (long j = nc1; j <= nc2; j++) { if (my data[i][j] > wmax) { wmax = my data[i][j]; } } } xmax = ymax = wmax; Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (long i = 1; i <= my numberOfRows; i++) { if (my rowLabels[i]) { Graphics_text (g, my data[i][ix], my data[i][iy], my rowLabels[i]); } } Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_BOTTOM); Graphics_line (g, xmin, ymax, xmin, ymin); Graphics_line (g, xmin, ymin, xmax, ymin); /* Graphics_arc (g, xmin, ymin, xmax - xmin, 0, 90); */ Graphics_unsetInner (g); if (garnish) { if (my columnLabels[ix]) { Graphics_textBottom (g, 0, my columnLabels[ix]); } if (my columnLabels[iy]) { Graphics_textLeft (g, 0, my columnLabels[iy]); } } } /******** MDSVEC *******************************************/ Thing_implement (MDSVec, Data, 0); void structMDSVec :: v_destroy () { NUMvector_free (proximity, 1); NUMvector_free (iPoint, 1); NUMvector_free (jPoint, 1); MDSVec_Parent :: v_destroy (); } MDSVec MDSVec_create (long nPoints) { try { autoMDSVec me = Thing_new (MDSVec); my nPoints = nPoints; my nProximities = nPoints * (nPoints - 1) / 2; my proximity = NUMvector (1, my nProximities); my iPoint = NUMvector (1, my nProximities); my jPoint = NUMvector (1, my nProximities); return me.transfer(); } catch (MelderError) { Melder_throw ("MDSVec not created."); } } MDSVec Dissimilarity_to_MDSVec (Dissimilarity me) { try { autoMDSVec thee = MDSVec_create (my numberOfRows); long k = 0; for (long i = 1; i <= my numberOfRows - 1; i++) { for (long j = i + 1; j <= my numberOfColumns; j++) { double f = (my data[i][j] + my data[j][i]) / 2; if (f > 0) { k++; thy proximity[k] = f; thy iPoint[k] = i; thy jPoint[k] = j; } } } thy nProximities = k; NUMsort3 (thy proximity, thy iPoint, thy jPoint, 1, k, 1); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no MDSVec created."); } } /*********************** MDSVECS *******************************************/ Thing_implement (MDSVecs, Ordered, 0); MDSVecs MDSVecs_create () { try { autoMDSVecs me = Thing_new (MDSVecs); Ordered_init (me.peek(), classMDSVec, 10); return me.transfer(); } catch (MelderError) { Melder_throw ("MDSVecs not created."); } } MDSVecs Dissimilarities_to_MDSVecs (Dissimilarities me) { try { autoMDSVecs thee = MDSVecs_create (); for (long i = 1; i <= my size; i++) { autoMDSVec him = Dissimilarity_to_MDSVec ( (Dissimilarity) (my item[i])); Thing_setName (him.peek(), Thing_getName ( (Thing) my item[i])); Collection_addItem (thee.peek(), him.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no MDSVecs created."); } } /************************** CONFUSIONS **************************************/ Thing_implement (Confusions, Proximities, 0); Confusions Confusions_create () { try { autoConfusions me = Thing_new (Confusions); Proximities_init (me.peek(), classConfusion); return me.transfer(); } catch (MelderError) { Melder_throw ("Confusions not created."); } } Confusion Confusions_sum (Confusions me) { try { autoTableOfReal sum = TablesOfReal_sum (me); autoConfusion thee = TableOfReal_to_Confusion (sum.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not created."); } } /************************** DISTANCES **************************************/ Thing_implement (Distances, Proximities, 0); Distances Distances_create () { try { autoDistances me = Thing_new (Distances); Proximities_init (me.peek(), classDistance); return me.transfer(); } catch (MelderError) { Melder_throw ("Distances not created."); } } /***************** SCALARPRODUCT ***************************************/ Thing_implement (ScalarProduct, TableOfReal, 0); ScalarProduct ScalarProduct_create (long numberOfPoints) { try { autoScalarProduct me = Thing_new (ScalarProduct); TableOfReal_init (me.peek(), numberOfPoints, numberOfPoints); return me.transfer(); } catch (MelderError) { Melder_throw ("ScalarProduct not created."); } } /************* SCALARPRODUCTS **************************************/ Thing_implement (ScalarProducts, TablesOfReal, 0); ScalarProducts ScalarProducts_create () { try { autoScalarProducts me = Thing_new (ScalarProducts); TablesOfReal_init (me.peek(), classScalarProduct); return me.transfer(); } catch (MelderError) { Melder_throw ("ScalarProducts not created."); } } /****************** DISSIMILARITY **********************************/ Thing_implement (Dissimilarity, Proximity, 0); Dissimilarity Dissimilarity_create (long numberOfPoints) { try { autoDissimilarity me = Thing_new (Dissimilarity); Proximity_init (me.peek(), numberOfPoints); return me.transfer(); } catch (MelderError) { Melder_throw ("Dissimilarity not created."); } } int Dissimilarity_getAdditiveConstant (I, double *c) { // Why not: double Diss..(I) ??? *c = 0; try { iam (Dissimilarity); long nProximities = 0, nPoints = my numberOfRows, nPoints2 = 2 * nPoints; double proximity; /* Return c = average dissimilarity in case of failure */ if (nPoints < 1) { Melder_throw ("Matrix part is empty."); } *c = 0; for (long i = 1; i <= nPoints - 1; i++) { for (long j = i + 1; j <= nPoints; j++) { proximity = (my data[i][j] + my data[j][i]) / 2; if (proximity > 0) { nProximities++; *c += proximity; } } } if (nProximities < 1) { Melder_throw ("No proximities larger than zero."); } *c /= nProximities; autoNUMmatrix wd (1, nPoints, 1, nPoints); autoNUMmatrix wdsqrt (1, nPoints, 1, nPoints); autoNUMmatrix b (1, nPoints2, 1, nPoints2); autoNUMvector eigenvalue (1, nPoints2); /* The matrices D & D1/2 with distances (squared and linear) */ for (long i = 1; i <= nPoints - 1; i++) { for (long j = i + 1; j <= nPoints; j++) { proximity = (my data[i][j] + my data[j][i]) / 2; wdsqrt[i][j] = - proximity / 2; wd[i][j] = - proximity * proximity / 2; } } NUMdoubleCentre (wdsqrt.peek(), 1, nPoints, 1, nPoints); NUMdoubleCentre (wd.peek(), 1, nPoints, 1, nPoints); /* Calculate the B matrix according to eq. 6 */ for (long i = 1; i <= nPoints; i++) { for (long j = 1; j <= nPoints; j++) { b[i][nPoints + j] = 2 * wd[i][j]; b[nPoints + i][nPoints + j] = -4 * wdsqrt[i][j]; b[nPoints + i][i] = -1; } } /* Get eigenvalues and sort them descending */ NUMeigensystem (b.peek(), nPoints2, NULL, eigenvalue.peek()); if (eigenvalue[1] <= 0) { Melder_throw ("Negative eigenvalue."); } *c = eigenvalue[1]; return 1; } catch (MelderError) { Melder_throw ("Additive constant not calculated."); } } /*************** DISSIMILARITIES **************************************/ Thing_implement (Dissimilarities, Proximities, 0); Dissimilarities Dissimilarities_create () { try { autoDissimilarities me = Thing_new (Dissimilarities); Proximities_init (me.peek(), classDissimilarity); return me.transfer(); } catch (MelderError) { Melder_throw ("Dissimilarities not created."); } } /************* SIMILARITY *****************************************/ Thing_implement (Similarity, Proximity, 0); Similarity Similarity_create (long numberOfPoints) { try { autoSimilarity me = Thing_new (Similarity); Proximity_init (me.peek(), numberOfPoints); return me.transfer(); } catch (MelderError) { Melder_throw ("Similarity not created."); } } Similarity Confusion_to_Similarity (Confusion me, int normalize, int symmetrizeMethod) { try { if (my numberOfColumns != my numberOfRows) { Melder_throw ("Confusion must be a square table."); } long nxy = my numberOfColumns; autoSimilarity thee = Similarity_create (nxy); TableOfReal_copyLabels (me, thee.peek(), 1, 1); NUMmatrix_copyElements (my data, thy data, 1, my numberOfRows, 1, my numberOfColumns); if (normalize) { NUMdmatrix_normalizeRows (thy data, nxy, nxy); } if (symmetrizeMethod == 1) { return thee.transfer(); } if (symmetrizeMethod == 2) { // Average data for (long i = 1; i <= nxy - 1; i++) { for (long j = i + 1; j <= nxy; j++) { thy data[i][j] = thy data[j][i] = (thy data[i][j] + thy data[j][i]) / 2; } } } else if (symmetrizeMethod == 3) { // Method Houtgast. autoNUMmatrix p (NUMmatrix_copy (thy data, 1, nxy, 1, nxy), 1, 1); for (long i = 1; i <= nxy; i++) { for (long j = i; j <= nxy; j++) { double tmp = 0; for (long k = 1; k <= nxy; k++) { tmp += p[i][k] < p[j][k] ? p[i][k] : p[j][k]; } thy data[j][i] = thy data[i][j] = tmp; } } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Similarity created."); } } Dissimilarity Similarity_to_Dissimilarity (Similarity me, double maximumDissimilarity) { try { long nxy = my numberOfColumns; double max = 0; autoDissimilarity thee = Dissimilarity_create (nxy); TableOfReal_copyLabels (me, thee.peek(), 1, 1); NUMmatrix_copyElements (my data, thy data, 1, my numberOfRows, 1, my numberOfColumns); for (long i = 1; i <= nxy; i++) { for (long j = 1; j <= nxy; j++) { if (thy data[i][j] > max) { max = thy data[i][j]; } } } if (maximumDissimilarity <= 0) { maximumDissimilarity = max; } if (maximumDissimilarity < max) Melder_warning (L"Your maximumDissimilarity is smaller than the maximum similarity. Some data may be lost."); for (long i = 1; i <= nxy; i++) { for (long j = 1; j <= nxy; j++) { double d = maximumDissimilarity - thy data[i][j]; thy data[i][j] = d > 0 ? d : 0; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Dissimilarity created."); } } Distance Dissimilarity_to_Distance (Dissimilarity me, int scale) { try { double additiveConstant = 0; autoDistance thee = Distance_create (my numberOfRows); TableOfReal_copyLabels (me, thee.peek(), 1, 1); if (scale == MDS_ORDINAL && ! Dissimilarity_getAdditiveConstant (me, &additiveConstant)) { Melder_warning (L"Dissimilarity_to_Distance: could not determine " "\"additive constant\", the average dissimilarity was used as " "its value."); } for (long i = 1; i <= my numberOfRows - 1; i++) { for (long j = i + 1; j <= my numberOfColumns; j++) { double d = 0.5 * (my data[i][j] + my data[j][i]) + additiveConstant; thy data[i][j] = thy data[j][i] = d; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Distance created."); } } Weight Dissimilarity_to_Weight (Dissimilarity me) { try { autoWeight thee = Weight_create (my numberOfRows); TableOfReal_copyLabels (me, thee.peek(), 1, 1); for (long i = 1; i <= my numberOfRows; i++) { for (long j = i; j <= my numberOfRows; j++) { if (my data[i][j] > 0) { thy data[i][j] = 1; } } thy data[i][i] = 0; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Weight created."); } } Dissimilarity Confusion_to_Dissimilarity_pdf (Confusion me, double minimumConfusionLevel) { try { if (my numberOfColumns != my numberOfRows) { Melder_throw ("Confusion must be a square table."); } Melder_assert (minimumConfusionLevel > 0); autoDissimilarity thee = Dissimilarity_create (my numberOfColumns); TableOfReal_copyLabels (me, thee.peek(), 1, 1); NUMmatrix_copyElements (my data, thy data, 1, my numberOfRows, 1, my numberOfColumns); /* Correct "zero" responses. */ for (long i = 1; i <= my numberOfColumns; i++) { for (long j = 1; j <= my numberOfColumns; j++) { if (thy data[i][j] == 0) { thy data[i][j] = minimumConfusionLevel; } } } NUMdmatrix_normalizeRows (thy data, my numberOfColumns, my numberOfColumns); /* Consider the fraction as the fraction overlap between two gaussians with unequal sigmas (1 & s). We have two matrix elements p[i][j] && p[j][i] N (x, m, s) = 1 / (s * sqrt(2 pi)) exp(-((x - m) / s)^2 / 2) N1 (x) = N (x, 0, 1) N2 (x) = N (x, m, s) These two gaussians cross each other at a point X that can be found by solving N1 (x) == N2 (x). The solution that is important to us is: X = (- m + s sqrt (m^2 - 2 (s^2 - 1) ln(s))) / (s^2 - 1) (1) This point X must be the solution of F (X, 0, 1) == p[i][j], where F (x, m, s) = P (x>X, m, s) = Integral (x, infinity, N (x, m, s) dx) We can solve for m and obtain: m = X + s sqrt (X^2 + 2 ln (s)) (2) We also have Integral (-Infinity, X, N2 (x) dx) == p[j][i]; By changing integration variables, (x - m) / s = y, we get Integral ((x-m)/s, Infinity, N (y, 0, 1) dy) == p[j][i] Let this equation result in a value Y, i.e., (X - m) / s = Y (3) (2) and (3) together and solve for m: m = X + Y * exp ((Y * y - X * X) / 2); Make maximum dissimilarity equal to 4sigma. */ for (long i = 1; i <= my numberOfColumns; i++) { for (long j = i + 1; j <= my numberOfColumns; j++) { double x = thy data[i][j] <= thy data[j][i] ? thy data[i][j] : thy data[j][i]; double y = thy data[i][j] > thy data[j][i] ? thy data[i][j] : thy data[j][i]; x = NUMinvGaussQ (x); y = NUMinvGaussQ (y); double d = x + y * exp ( (y * y - x * x) / 2); /* Melder_info ("i, j, x, y, d: %d %d %.17g %.17g %.17g", i, j, x, y, d); */ thy data[i][j] = thy data [j][i] = d; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Dissimilarity created from pdf."); } } void Distance_and_Configuration_drawScatterDiagram (Distance me, Configuration him, Graphics g, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { autoDistance dist = Configuration_to_Distance (him); Proximity_Distance_drawScatterDiagram (me, dist.peek(), g, xmin, xmax, ymin, ymax, size_mm, mark, garnish); } Dissimilarity Distance_to_Dissimilarity (Distance me) { try { autoDissimilarity thee = Dissimilarity_create (my numberOfRows); TableOfReal_copyLabels (me, thee.peek(), 1, 1); NUMmatrix_copyElements (my data, thy data, 1, my numberOfRows, 1, my numberOfColumns); return thee.transfer(); } catch (MelderError) { Melder_throw ("Dissimilarity not created from Distance."); } } Configuration Distance_to_Configuration_torsca (Distance me, int numberOfDimensions) { try { if (numberOfDimensions > my numberOfRows) { Melder_throw ("Number of dimensions too high."); } autoScalarProduct sp = Distance_to_ScalarProduct (me, 0); autoConfiguration thee = Configuration_create (my numberOfRows, numberOfDimensions); TableOfReal_copyLabels (me, thee.peek(), 1, 0); NUMprincipalComponents (sp -> data, my numberOfRows, numberOfDimensions, thy data); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created (torsca method)."); } } ScalarProduct Distance_to_ScalarProduct (Distance me, int normalize) { try { autoScalarProduct thee = ScalarProduct_create (my numberOfRows); TableOfReal_copyLabels (me, thee.peek(), 1, 1); for (long i = 1; i <= my numberOfRows - 1; i++) { for (long j = i + 1; j <= my numberOfColumns; j++) { /* force symmetry by averaging! */ double d = 0.5 * (my data[i][j] + my data[j][i]); thy data[i][j] = thy data[j][i] = - 0.5 * d * d; } } TableOfReal_doubleCentre (thee.peek()); if (my name) { Thing_setName (thee.peek(), my name); } if (normalize) { TableOfReal_normalizeTable (thee.peek(), 1); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no ScalarProduct created."); } } /********** Configuration & ..... ***********************************/ Distance Configuration_to_Distance (Configuration me) { try { autoDistance thee = Distance_create (my numberOfRows); TableOfReal_copyLabels (me, thee.peek(), 1, -1); for (long i = 1; i <= thy numberOfRows - 1; i++) { for (long j = i + 1; j <= thy numberOfColumns; j++) { double dmax = 0, d = 0; /* first divide distance by maximum to prevent overflow when metric is a large number. d = (x^n)^(1/n) may overflow if x>1 & n >>1 even if d would not overflow! metric changed 24/11/97 my w[k] * pow (|i-j|) instead of pow (my w[k] * |i-j|) */ for (long k = 1; k <= my numberOfColumns; k++) { double dtmp = fabs (my data[i][k] - my data[j][k]); if (dtmp > dmax) { dmax = dtmp; } } if (dmax > 0) { for (long k = 1; k <= my numberOfColumns; k++) { double arg = fabs (my data[i][k] - my data[j][k]) / dmax; d += my w[k] * pow (arg, my metric); } } thy data[i][j] = thy data[j][i] = dmax * pow (d, 1.0 / my metric); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Distance created."); } } void Proximity_Distance_drawScatterDiagram (I, Distance thee, Graphics g, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { iam (Proximity); long n = my numberOfRows * (my numberOfRows - 1) / 2; double **x = my data, **y = thy data; if (n == 0) { return; } if (! TableOfReal_equalLabels (me, thee, 1, 1)) { Melder_throw ("Proximity_Distance_drawScatterDiagram: Dimensions and labels must be the same."); } if (xmax <= xmin) { xmin = xmax = x[1][2]; for (long i = 1; i <= thy numberOfRows - 1; i++) { for (long j = i + 1; j <= thy numberOfColumns; j++) { if (x[i][j] > xmax) { xmax = x[i][j]; } else if (x[i][j] < xmin) { xmin = x[i][j]; } } } } if (ymax <= ymin) { ymin = ymax = y[1][2]; for (long i = 1; i <= my numberOfRows - 1; i++) { for (long j = i + 1; j <= my numberOfColumns; j++) { if (y[i][j] > ymax) { ymax = y[i][j]; } else if (y[i][j] < ymin) { ymin = y[i][j]; } } } } Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setInner (g); for (long i = 1; i <= thy numberOfRows - 1; i++) { for (long j = i + 1; j <= thy numberOfColumns; j++) { if (x[i][j] >= xmin && x[i][j] <= xmax && y[i][j] >= ymin && y[i][j] <= ymax) { Graphics_mark (g, x[i][j], y[i][j], size_mm, mark); } } } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textLeft (g, 1, L"Distance"); Graphics_textBottom (g, 1, L"Dissimilarity"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } Distances MDSVecs_Distance_monotoneRegression (MDSVecs me, Distance thee, int tiesProcessing) { try { autoDistances him = Distances_create (); for (long i = 1; i <= my size; i++) { autoMDSVec vec = (MDSVec) my item[i]; if (vec -> nPoints != thy numberOfRows) { Melder_throw ("Dimension of MDSVec and Distance must be equal."); } autoDistance fit = MDSVec_Distance_monotoneRegression (vec.peek(), thee, tiesProcessing); Collection_addItem (him.peek(), fit.transfer()); } return him.transfer(); } catch (MelderError) { Melder_throw ("No Distances created from MDSVecs & Distance."); } } Distance MDSVec_Distance_monotoneRegression (MDSVec me, Distance thee, int tiesProcessing) { try { long nProximities = my nProximities; if (thy numberOfRows != my nPoints) { Melder_throw ("Distance and MDSVVec dimension do not agreee."); } autoNUMvector distance (1, nProximities); autoNUMvector fit (1, nProximities); autoDistance him = Distance_create (thy numberOfRows); TableOfReal_copyLabels (thee, him.peek(), 1, 1); long *iPoint = my iPoint, *jPoint = my jPoint; for (long i = 1; i <= nProximities; i++) { distance[i] = thy data[iPoint[i]][jPoint[i]]; } if (tiesProcessing == MDS_PRIMARY_APPROACH || MDS_SECONDARY_APPROACH) { /* Kruskal's primary approach to tie-blocks: Sort corresponding distances, with iPoint, and jPoint. Kruskal's secondary approach: Substitute average distance in each tie block */ long ib = 1; for (long i = 2; i <= nProximities; i++) { if (my proximity[i] == my proximity[i - 1]) { continue; } if (i - ib > 1) { if (tiesProcessing == MDS_PRIMARY_APPROACH) { NUMsort3 (distance.peek(), iPoint, jPoint, ib, i - 1, 1); // sort ascending } else if (tiesProcessing == MDS_SECONDARY_APPROACH) { double mean = 0; for (long j = ib; j <= i - 1; j++) { mean += distance[j]; } mean /= (i - ib); for (long j = ib; j <= i - 1; j++) { distance[j] = mean; } } } ib = i; } } NUMmonotoneRegression (distance.peek(), nProximities, fit.peek()); /* Fill Distance with monotone regressed distances */ for (long i = 1; i <= nProximities; i++) { long ip = iPoint[i], jp = jPoint[i]; his data[ip][jp] = his data[jp][ip] = fit[i]; } /* Make rest of distances equal to the maximum fit. */ for (long i = 1; i <= his numberOfRows - 1; i++) { for (long j = i + 1; j <= his numberOfColumns; j++) { if (! his data[i][j]) { his data[i][j] = his data[j][i] = fit[nProximities]; } } } return him.transfer(); } catch (MelderError) { Melder_throw ("Distance not created."); } } Distance Dissimilarity_Distance_monotoneRegression (Dissimilarity me, Distance thee, int tiesProcessing) { try { if (thy numberOfRows != my numberOfRows) { Melder_throw ("Dimensions do not agree."); } autoMDSVec vec = Dissimilarity_to_MDSVec (me); autoDistance him = MDSVec_Distance_monotoneRegression (vec.peek(), thee, tiesProcessing); return him.transfer(); } catch (MelderError) { Melder_throw ("Distance not created."); } } /*************** class Proximities **************************************/ Thing_implement (Proximities, TablesOfReal, 0); void Proximities_init (I, ClassInfo klas) { iam (Proximities); TablesOfReal_init (me, klas); } Proximities Proximities_create () { try { autoProximities me = Thing_new (Proximities); Proximities_init (me.peek(), classProximity); return me.transfer(); } catch (MelderError) { Melder_throw ("Proximities not created."); } } ScalarProducts Distances_to_ScalarProducts (Distances me, int normalize) { try { autoScalarProducts thee = ScalarProducts_create (); for (long i = 1; i <= my size; i++) { autoScalarProduct sp = Distance_to_ScalarProduct ( (Distance) (my item[i]), normalize); Collection_addItem (thee.peek(), sp.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no ScalarProducts created."); } } int Distances_to_Configuration_ytl (Distances me, int numberOfDimensions, int normalizeScalarProducts, Configuration *out1, Salience *out2) { try { *out1 = NULL; *out2 = NULL; autoScalarProducts sp = Distances_to_ScalarProducts (me, normalizeScalarProducts); ScalarProducts_to_Configuration_ytl (sp.peek(), numberOfDimensions, out1, out2); return 1; } catch (MelderError) { Melder_throw (me, ": no Configuration created (ytl method)."); } } void ScalarProducts_to_Configuration_ytl (ScalarProducts me, int numberOfDimensions, Configuration *out1, Salience *out2) { long numberOfSources = my size; autoNUMvector ci (1, numberOfSources); try { long nPoints = ( (ScalarProduct) my item[1]) -> numberOfRows; double **w; autoConfiguration thee = Configuration_create (nPoints, numberOfDimensions); autoSalience mdsw = Salience_create (numberOfSources, numberOfDimensions); TableOfReal_copyLabels (my item[1], thee.peek(), 1, 0); autoNUMvector eval (1, numberOfSources); autoNUMmatrix cl (1, numberOfDimensions, 1, numberOfDimensions); autoNUMmatrix pmean (1, nPoints, 1, nPoints); autoNUMmatrix y (1, nPoints, 1, numberOfDimensions); autoNUMmatrix yinv (1, numberOfDimensions, 1, nPoints); autoNUMmatrix a (1, numberOfSources, 1, numberOfSources); autoNUMmatrix evec (1, numberOfSources, 1, numberOfSources); autoNUMmatrix K (1, numberOfDimensions, 1, numberOfDimensions); *out1 = NULL; *out2 = NULL; Thing_setName (mdsw.peek(), L"ytl"); Thing_setName (thee.peek(), L"ytl"); TableOfReal_labelsFromCollectionItemNames (mdsw.peek(), me, 1, 0); // Determine the average scalar product matrix (Pmean) of // dimension [1..nPoints][1..nPoints]. for (long i = 1; i <= numberOfSources; i++) { ScalarProduct sp = (ScalarProduct) my item[i]; for (long j = 1; j <= nPoints; j++) { for (long k = 1; k <= nPoints; k++) { pmean[j][k] += sp->data[j][k]; } } } if (numberOfSources > 1) { for (long j = 1; j <= nPoints; j++) { for (long k = 1; k <= nPoints; k++) { pmean[j][k] /= numberOfSources; } } } // Up to a rotation K, the initial configuration can be found by // extracting the first 'numberOfDimensions' principal components of Pmean. NUMdmatrix_into_principalComponents (pmean.peek(), nPoints, nPoints, numberOfDimensions, y.peek()); NUMmatrix_copyElements (y.peek(), thy data, 1, nPoints, 1, numberOfDimensions); // We cannot determine weights from only one sp-matrix. if (numberOfSources == 1) { Melder_throw ("Only one source."); } // Calculate the C[i] matrices [1..numberOfDimensions][1..numberOfDimensions] // from the P[i] by: C[i] = (y'.y)^-1 . y' . P[i] . y . (y'.y)^-1 == // yinv P[i] yinv' NUMpseudoInverse (y.peek(), nPoints, numberOfDimensions, yinv.peek(), 1e-14); for (long i = 1; i <= numberOfSources; i++) { ScalarProduct sp = (ScalarProduct) my item[i]; ci[i] = NUMmatrix (1, numberOfDimensions, 1, numberOfDimensions); for (long j = 1; j <= numberOfDimensions; j++) { for (long k = 1; k <= numberOfDimensions; k++) { for (long l = 1; l <= nPoints; l++) { if (yinv[j][l] != 0) { for (long m = 1; m <= nPoints; m++) { ci[i][j][k] += yinv[j][l] * sp -> data[l][m] * yinv[k][m]; } } } } } } // Calculate the A[1..numberOfSources][1..numberOfSources] matrix by (eq.12): // a[i][j] = trace (C[i]*C[j]) - trace (C[i]) * trace (C[j]) / numberOfDimensions; // Get the first eigenvector and form matrix cl from a linear combination of the C[i]'s for (long i = 1; i <= numberOfSources; i++) { for (long j = i; j <= numberOfSources; j++) { a[j][i] = a[i][j] = NUMtrace2 (ci[i], ci[j], numberOfDimensions) - NUMtrace (ci[i], numberOfDimensions) * NUMtrace (ci[j], numberOfDimensions) / numberOfDimensions; } } NUMeigensystem (a.peek(), numberOfSources, evec.peek(), eval.peek()); for (long i = 1; i <= numberOfSources; i++) { for (long j = 1; j <= numberOfDimensions; j++) { for (long k = 1; k <= numberOfDimensions; k++) { cl[j][k] += ci[i][j][k] * evec[i][1]; /* eq. (7) */ } } } // The rotation K is obtained from the eigenvectors of cl // Is the following still correct??? eigensystem was not sorted?? NUMeigensystem (cl.peek(), numberOfDimensions, K.peek(), NULL); // Now get the configuration: X = Y.K for (long i = 1; i <= nPoints; i++) { for (long j = 1; j <= numberOfDimensions; j++) { double x = 0; for (long k = 1; k <= numberOfDimensions; k++) { x += y[i][k] * K[k][j]; } thy data [i][j] = x; } } Configuration_normalize (thee.peek(), 0, 1); // And finally the weights: W[i] = K' C[i] K (eq. (5)). // We are only interested in the diagonal of the resulting matrix W[i]. w = mdsw -> data; for (long i = 1; i <= numberOfSources; i++) { for (long j = 1; j <= numberOfDimensions; j++) { double wt = 0; for (long k = 1; k <= numberOfDimensions; k++) { if (K[k][j] != 0) { for (long l = 1; l <= numberOfDimensions; l++) { wt += K[k][j] * ci[i][k][l] * K[l][j]; } } } w[i][j] = wt; } } *out1 = thee.transfer(); *out2 = mdsw.transfer(); for (long i = 1; i <= numberOfSources; i++) { NUMmatrix_free (ci[i], 1, 1); } } catch (MelderError) { for (long i = 1; i <= numberOfSources; i++) { NUMmatrix_free (ci[i], 1, 1); }; Melder_throw (me, ": no Configuration (ytl) crerated."); } } Dissimilarities Distances_to_Dissimilarities (Distances me) { try { autoDissimilarities thee = Dissimilarities_create (); for (long i = 1; i <= my size; i++) { wchar_t *name = Thing_getName ( (Thing) my item[i]); autoDissimilarity him = Distance_to_Dissimilarity ( (Distance) (my item[i])); Thing_setName (him.peek(), name ? name : L"untitled"); Collection_addItem (thee.peek(), him.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Dissimilarities created."); } } Distances Dissimilarities_to_Distances (Dissimilarities me, int measurementLevel) { try { autoDistances thee = Distances_create (); for (long i = 1; i <= my size; i++) { autoDistance him = Dissimilarity_to_Distance ( (Dissimilarity) my item[i], measurementLevel == MDS_ORDINAL); wchar_t *name = Thing_getName ( (Thing) my item[i]); Thing_setName (him.peek(), name ? name : L"untitled"); Collection_addItem (thee.peek(), him.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Distances created."); } } /***************** Kruskal *****************************************/ static void smacof_guttmanTransform (Configuration cx, Configuration cz, Distance disp, Weight weight, double **vplus) { long nPoints = cx -> numberOfRows, nDimensions = cx -> numberOfColumns; double **z = cz -> data; autoNUMmatrix b (1, nPoints, 1, nPoints); autoDistance distZ = Configuration_to_Distance (cz); // compute B(Z) (eq. 8.25) for (long i = 1; i <= nPoints; i++) { double sum = 0; for (long j = 1; j <= nPoints; j++) { double dzij = distZ -> data[i][j]; if (i == j || dzij == 0) { continue; } b[i][j] = - weight -> data[i][j] * disp -> data[i][j] / dzij; sum += b[i][j]; } b[i][i] = - sum; } // Guttman transform: Xu = (V+)B(Z)Z (eq. 8.29) for (long i = 1; i <= nPoints; i++) { for (long j = 1; j <= nDimensions; j++) { double xij = 0; for (long k = 1; k <= nPoints; k++) { for (long l = 1; l <= nPoints; l++) { xij += vplus[i][k] * b[k][l] * z[l][j]; } } cx -> data[i][j] = xij; } } } double Distance_Weight_stress (Distance fit, Distance conf, Weight weight, int type) { double eta_fit, eta_conf, rho, stress = NUMundefined, denum, tmp; Distance_Weight_rawStressComponents (fit, conf, weight, &eta_fit, &eta_conf, &rho); // All formula's for stress, except for raw stress, are independent of the // scale of the configuration, i.e., the distances conf[i][j]. if (type == MDS_NORMALIZED_STRESS) { denum = eta_fit * eta_conf; if (denum > 0) { stress = 1.0 - rho * rho / denum; } } else if (type == MDS_STRESS_1) { denum = eta_fit * eta_conf; if (denum > 0) { tmp = 1.0 - rho * rho / denum; if (tmp > 0) { stress = sqrt (tmp); } } } else if (type == MDS_STRESS_2) { double m = 0, wsum = 0, var = 0, **w = weight -> data; double **c = conf -> data; long nPoints = conf -> numberOfRows; // Get average distance for (long i = 1; i <= nPoints - 1; i++) { for (long j = i + 1; j <= nPoints; j++) { m += w[i][j] * c[i][j]; wsum += w[i][j]; } } m /= wsum; if (m > 0) { // Get variance for (long i = 1; i <= nPoints - 1; i++) { for (long j = i + 1; j <= nPoints; j++) { tmp = c[i][j] - m; var += w[i][j] * tmp * tmp; } } denum = var * eta_fit; if (denum > 0) { stress = sqrt ( (eta_fit * eta_conf - rho * rho) / denum); } } } else if (type == MDS_RAW_STRESS) { stress = eta_fit + eta_conf - 2 * rho ; } return stress; } void Distance_Weight_rawStressComponents (Distance fit, Distance conf, Weight weight, double *eta_fit, double *eta_conf, double *rho) { long nPoints = conf -> numberOfRows; *eta_fit = *eta_conf = *rho = 0; double wsum = 0; for (long i = 1; i <= nPoints - 1; i++) { double *wi = weight -> data[i]; double *fiti = fit -> data[i]; double *confi = conf -> data[i]; for (long j = i + 1; j <= nPoints; j++) { *eta_fit += wi[j] * fiti[j] * fiti[j]; *eta_conf += wi[j] * confi[j] * confi[j]; *rho += wi[j] * fiti[j] * confi[j]; wsum += wi[j]; } } } double Dissimilarity_Configuration_Transformator_Weight_stress (Dissimilarity d, Configuration c, Any transformator, Weight w, int type) { Transformator t = (Transformator) transformator; long nPoints = d -> numberOfRows; double stress = NUMundefined; if (nPoints < 1 || nPoints != c -> numberOfRows || nPoints != t -> numberOfPoints || (w && nPoints != w -> numberOfRows)) { Melder_throw ("Incorrect number of points."); } autoWeight aw = 0; if (w == 0) { aw.reset (Weight_create (nPoints)); w = aw.peek(); } autoDistance cdist = Configuration_to_Distance (c); autoMDSVec vec = Dissimilarity_to_MDSVec (d); autoDistance fit = Transformator_transform (t, vec.peek(), cdist.peek(), w); stress = Distance_Weight_stress (fit.peek(), cdist.peek(), w, type); return stress; } double Dissimilarity_Configuration_Weight_absolute_stress (Dissimilarity d, Configuration c, Weight w, int type) { autoTransformator t = Transformator_create (d -> numberOfRows); double stress = Dissimilarity_Configuration_Transformator_Weight_stress (d, c, t.peek(), w, type); return stress; } double Dissimilarity_Configuration_Weight_ratio_stress (Dissimilarity d, Configuration c, Weight w, int type) { autoRatioTransformator t = RatioTransformator_create (d -> numberOfRows); double stress = Dissimilarity_Configuration_Transformator_Weight_stress (d, c, t.peek(), w, type); return stress; } double Dissimilarity_Configuration_Weight_interval_stress (Dissimilarity d, Configuration c, Weight w, int type) { autoISplineTransformator t = ISplineTransformator_create (d -> numberOfRows, 0, 1); double stress = Dissimilarity_Configuration_Transformator_Weight_stress (d, c, t.peek(), w, type); return stress; } double Dissimilarity_Configuration_Weight_monotone_stress (Dissimilarity d, Configuration c, Weight w, int tiesProcessing, int type) { autoMonotoneTransformator t = MonotoneTransformator_create (d -> numberOfRows); MonotoneTransformator_setTiesProcessing (t.peek(), tiesProcessing); double stress = Dissimilarity_Configuration_Transformator_Weight_stress (d, c, t.peek(), w, type); return stress; } double Dissimilarity_Configuration_Weight_ispline_stress (Dissimilarity d, Configuration c, Weight w, long numberOfInteriorKnots, long order, int type) { autoISplineTransformator t = ISplineTransformator_create (d -> numberOfRows, numberOfInteriorKnots, order); double stress = Dissimilarity_Configuration_Transformator_Weight_stress (d, c, t.peek(), w, type); return stress; } void Distance_Weight_smacofNormalize (Distance me, Weight w) { double sumsq = 0; for (long i = 1; i <= my numberOfRows - 1; i++) { double *wi = w -> data[i]; double *di = my data[i]; for (long j = i + 1; j <= my numberOfRows; j++) { sumsq += wi[j] * di[j] * di[j]; } } double scale = sqrt (my numberOfRows * (my numberOfRows - 1) / (2 * sumsq)); for (long i = 1; i <= my numberOfRows - 1; i++) { for (long j = i + 1; j <= my numberOfRows; j++) { my data[j][i] = (my data[i][j] *= scale); } } } double Distance_Weight_congruenceCoefficient (Distance x, Distance y, Weight w) { long nPoints = x -> numberOfRows; if (y -> numberOfRows != nPoints || w -> numberOfRows != nPoints) { return 0; } double xy = 0, x2 = 0, y2 = 0; for (long i = 1; i <= nPoints - 1; i++) { double *xi = x -> data[i]; double *yi = y -> data[i]; double *wi = w -> data[i]; for (long j = i + 1; j <= nPoints - 1; j++) { xy += wi[j] * xi[j] * yi[j]; x2 += wi[j] * xi[j] * xi[j]; y2 += wi[j] * yi[j] * yi[j]; } } return xy / (sqrt (x2) * sqrt (y2)); } Configuration Dissimilarity_Configuration_Weight_Transformator_smacof (Dissimilarity me, Configuration conf, Weight weight, Any transformator, double tolerance, long numberOfIterations, int showProgress, double *stress) { try { Transformator t = (Transformator) transformator; long nPoints = conf -> numberOfRows; long nDimensions = conf -> numberOfColumns; double tol = 1e-6, stressp = 1e38; bool no_weight = weight == 0; if (my numberOfRows != nPoints || (!no_weight && weight -> numberOfRows != nPoints) || t -> numberOfPoints != nPoints) { Melder_throw ("Dimensions not in concordance."); } autoWeight aw = 0; if (no_weight) { aw.reset (Weight_create (nPoints)); weight = aw.peek(); } autoNUMmatrix v (1, nPoints, 1, nPoints); autoNUMmatrix vplus (1, nPoints, 1, nPoints); autoConfiguration z = Data_copy (conf); autoMDSVec vec = Dissimilarity_to_MDSVec (me); double **w = weight -> data; if (showProgress) { Melder_progress (0.0, L"MDS analysis"); } // Get V (eq. 8.19). for (long i = 1; i <= nPoints; i++) { double wsum = 0; for (long j = 1; j <= nPoints; j++) { if (i == j) { continue; } v[i][j] = - w[i][j]; wsum += w[i][j]; } v[i][i] = wsum; } // V is row and column centered and therefore: rank(V) <= nPoints-1. // V^-1 does not exist -> get Moore-Penrose inverse. NUMpseudoInverse (v.peek(), nPoints, nPoints, vplus.peek(), tol); for (long iter = 1; iter <= numberOfIterations; iter++) { autoDistance dist = Configuration_to_Distance (conf); // transform & normalization autoDistance fit = Transformator_transform (t, vec.peek(), dist.peek(), weight); // Make conf the Guttman transform of z smacof_guttmanTransform (conf, z.peek(), fit.peek(), weight, vplus.peek()); // Compute stress autoDistance cdist = Configuration_to_Distance (conf); *stress = Distance_Weight_stress (fit.peek(), cdist.peek(), weight, MDS_NORMALIZED_STRESS); // Check stop criterium if (fabs (*stress - stressp) / stressp < tolerance) { break; } // Make Z = X NUMmatrix_copyElements (conf -> data, z -> data, 1, nPoints, 1, nDimensions); stressp = *stress; if (showProgress) { Melder_progress ( (double) iter / (numberOfIterations + 1), L"kruskal: stress ", Melder_double (*stress)); therror } } if (showProgress) { Melder_progress (1.0, 0); } return z.transfer(); } catch (MelderError) { if (showProgress) { Melder_progress (1.0, 0); } Melder_throw (me, ": no improved Configuration created (smacof method)."); } } Configuration Dissimilarity_Configuration_Weight_Transformator_multiSmacof (Dissimilarity me, Configuration conf, Weight w, Any transformator, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { int showMulti = showProgress && numberOfRepetitions > 1; try { int showSingle = showProgress && numberOfRepetitions == 1; double stress, stressmax = 1e38; autoConfiguration cstart = Data_copy (conf); autoConfiguration cbest = Data_copy (conf); if (showMulti) { Melder_progress (0.0, L"MDS many times"); } for (long i = 1; i <= numberOfRepetitions; i++) { autoConfiguration cresult = Dissimilarity_Configuration_Weight_Transformator_smacof (me, cstart.peek(), w, transformator, tolerance, numberOfIterations, showSingle, &stress); if (stress < stressmax) { stressmax = stress; cbest.reset (cresult.transfer()); } Configuration_randomize (cstart.peek()); TableOfReal_centreColumns (cstart.peek()); if (showMulti) { Melder_progress ( (double) i / (numberOfRepetitions + 1), Melder_integer (i), L" from ", Melder_integer (numberOfRepetitions)); therror } } if (showMulti) { Melder_progress (1.0, NULL); } return cbest.transfer(); } catch (MelderError) { if (showMulti) { Melder_progress (1.0, NULL); } Melder_throw (me, ": no improved Configuration created (smacodf method)."); } } Configuration Dissimilarity_Configuration_Weight_absolute_mds (Dissimilarity me, Configuration cstart, Weight w, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoTransformator t = Transformator_create (my numberOfRows); autoConfiguration c = Dissimilarity_Configuration_Weight_Transformator_multiSmacof (me, cstart, w, t.peek(), tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no improved Configuration created (absolute mds method)."); } } Configuration Dissimilarity_Configuration_Weight_ratio_mds (Dissimilarity me, Configuration cstart, Weight w, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoRatioTransformator t = RatioTransformator_create (my numberOfRows); autoConfiguration c = Dissimilarity_Configuration_Weight_Transformator_multiSmacof (me, cstart, w, t.peek(), tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no improved Configuration created (ratio mds method)."); } } Configuration Dissimilarity_Configuration_Weight_interval_mds (Dissimilarity me, Configuration cstart, Weight w, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoISplineTransformator t = ISplineTransformator_create (my numberOfRows, 0, 1); autoConfiguration c = Dissimilarity_Configuration_Weight_Transformator_multiSmacof (me, cstart, w, t.peek(), tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no improved Configuration created (interval mds method)."); } } Configuration Dissimilarity_Configuration_Weight_monotone_mds (Dissimilarity me, Configuration cstart, Weight w, int tiesProcessing, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoMonotoneTransformator t = MonotoneTransformator_create (my numberOfRows); MonotoneTransformator_setTiesProcessing (t.peek(), tiesProcessing); autoConfiguration c = Dissimilarity_Configuration_Weight_Transformator_multiSmacof (me, cstart, w, t.peek(), tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no improved Configuration created (monotone mds method)."); } } Configuration Dissimilarity_Configuration_Weight_ispline_mds (Dissimilarity me, Configuration cstart, Weight w, long numberOfInteriorKnots, long order, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoISplineTransformator t = ISplineTransformator_create (my numberOfRows, numberOfInteriorKnots, order); autoConfiguration c = Dissimilarity_Configuration_Weight_Transformator_multiSmacof (me, cstart, w, t.peek(), tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no improved Configuration created (ispline mds method)."); } } Configuration Dissimilarity_Weight_absolute_mds (Dissimilarity me, Weight w, long numberOfDimensions, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoDistance d = Dissimilarity_to_Distance (me, MDS_ABSOLUTE); autoConfiguration cstart = Distance_to_Configuration_torsca (d.peek(), numberOfDimensions); autoConfiguration c = Dissimilarity_Configuration_Weight_absolute_mds (me, cstart.peek(), w, tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created (absolute mds method)."); } } Configuration Dissimilarity_Weight_interval_mds (Dissimilarity me, Weight w, long numberOfDimensions, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoDistance d = Dissimilarity_to_Distance (me, MDS_RATIO); autoConfiguration cstart = Distance_to_Configuration_torsca (d.peek(), numberOfDimensions); autoConfiguration c = Dissimilarity_Configuration_Weight_interval_mds (me, cstart.peek(), w, tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created (interval mds method)."); } } Configuration Dissimilarity_Weight_monotone_mds (Dissimilarity me, Weight w, long numberOfDimensions, int tiesProcessing, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoDistance d = Dissimilarity_to_Distance (me, MDS_ORDINAL); autoConfiguration cstart = Distance_to_Configuration_torsca (d.peek(), numberOfDimensions); autoConfiguration c = Dissimilarity_Configuration_Weight_monotone_mds (me, cstart.peek(), w, tiesProcessing, tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created (monotone mds method)."); } } Configuration Dissimilarity_Weight_ratio_mds (Dissimilarity me, Weight w, long numberOfDimensions, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoDistance d = Dissimilarity_to_Distance (me, MDS_RATIO); autoConfiguration cstart = Distance_to_Configuration_torsca (d.peek(), numberOfDimensions); autoConfiguration c = Dissimilarity_Configuration_Weight_ratio_mds (me, cstart.peek(), w, tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created (ratio mds method)."); } } Configuration Dissimilarity_Weight_ispline_mds (Dissimilarity me, Weight w, long numberOfDimensions, long numberOfInteriorKnots, long order, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress) { try { autoDistance d = Dissimilarity_to_Distance (me, MDS_ORDINAL); autoConfiguration cstart = Distance_to_Configuration_torsca (d.peek(), numberOfDimensions); autoConfiguration c = Dissimilarity_Configuration_Weight_ispline_mds (me, cstart.peek(), w, numberOfInteriorKnots, order, tolerance, numberOfIterations, numberOfRepetitions, showProgress); return c.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created (ispline mds method)."); } } /***** classical **/ static void MDSVec_Distances_getStressValues (MDSVec me, Distance ddist, Distance dfit, int stress_formula, double *stress, double *s, double *t, double *dbar) { long nProximities = my nProximities; long *iPoint = my iPoint, *jPoint = my jPoint; double **dist = ddist -> data, **fit = dfit -> data; *s = *t = *dbar = 0; if (stress_formula == 2) { for (long i = 1; i <= nProximities; i++) { *dbar += dist[iPoint[i]][jPoint[i]]; } *dbar /= nProximities; } for (long i = 1; i <= nProximities; i++) { long ii = iPoint[i], jj = jPoint[i]; double st = dist[ii][jj] - fit[ii][jj]; double tt = dist[ii][jj] - *dbar; *s += st * st; *t += tt * tt; } *stress = *t > 0 ? sqrt (*s / *t) : 0; } static double func (Data object, const double p[]) { Kruskal me = (Kruskal) object; MDSVec him = my vec; double **x = my configuration -> data, s, t, dbar, stress; double metric = my configuration -> metric; long numberOfDimensions = my configuration -> numberOfColumns; long numberOfPoints = my configuration -> numberOfRows; int tiesProcessing = my process == MDS_CONTINUOUS ? 1 : 0; // Substitute results of minimizer into configuration and // normalize the configuration NUMdvector_into_matrix (p, x, 1, numberOfPoints, 1, numberOfDimensions); // Normalize NUMcentreColumns (x, 1, numberOfPoints, 1, numberOfDimensions, NULL); NUMnormalize (x, numberOfPoints, numberOfDimensions, sqrt (numberOfPoints)); // Calculate interpoint distances from the configuration autoDistance dist = Configuration_to_Distance (my configuration); // Monotone regression autoDistance fit = MDSVec_Distance_monotoneRegression (my vec, dist.peek(), tiesProcessing); // Get numerator and denominator of stress MDSVec_Distances_getStressValues (my vec, dist.peek(), fit.peek(), my stress_formula, &stress, &s, &t, &dbar); // Gradient calculation. for (long i = 1; i <= numberOfPoints; i++) { for (long j = 1; j <= numberOfDimensions; j++) { my dx[i][j] = 0; } } // Prevent overflow when stress is small if (stress < 1e-6) { return stress; } for (long i = 1; i <= his nProximities; i++) { long ii = my vec -> iPoint[i], jj = my vec -> jPoint[i]; double g1 = stress * ( (dist->data[ii][jj] - fit->data[ii][jj]) / s - (dist->data[ii][jj] - dbar) / t); for (long j = 1; j <= numberOfDimensions; j++) { double dj = x[ii][j] - x[jj][j]; double g2 = g1 * pow (fabs (dj) / dist->data[ii][jj], metric - 1); if (dj < 0) { g2 = -g2; } my dx[ii][j] += g2; my dx[jj][j] -= g2; } } // Increment the number of times this function has been called (my minimizer -> funcCalls) ++; return stress; } /* Precondition: configuration was not changed since previous call to func */ static void dfunc (Data object, const double p[], double dp[]) { Kruskal me = (Kruskal) object; Configuration thee = my configuration; (void) p; long k = 1; for (long i = 1; i <= thy numberOfRows; i++) { for (long j = 1; j <= thy numberOfColumns; j++) { dp[k++] = my dx[i][j]; } } } Thing_implement (Kruskal, Thing, 0); void structKruskal :: v_destroy () { NUMmatrix_free (dx, 1, 1); forget (configuration); forget (proximities); forget (vec); forget (minimizer); Kruskal_Parent :: v_destroy (); } Kruskal Kruskal_create (long numberOfPoints, long numberOfDimensions) { try { autoKruskal me = Thing_new (Kruskal); my proximities = Proximities_create (); my configuration = Configuration_create (numberOfPoints, numberOfDimensions); my dx = NUMmatrix (1, numberOfPoints, 1, numberOfDimensions); return me.transfer(); } catch (MelderError) { Melder_throw ("Kruskal not created."); } } Configuration Dissimilarity_kruskal (Dissimilarity me, long numberOfDimensions, long metric, int tiesProcessing, int stress_formula, double tolerance, long numberOfIterations, long numberOfRepetitions) { try { int scale = 1; (void) metric; autoDistance d = Dissimilarity_to_Distance (me, scale); autoConfiguration c = Distance_to_Configuration_torsca (d.peek(), numberOfDimensions); Configuration_normalize (c.peek(), 1.0, 0); autoConfiguration thee = Dissimilarity_Configuration_kruskal (me, c.peek(), tiesProcessing, stress_formula, tolerance, numberOfIterations, numberOfRepetitions); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created (kruskal method)."); } } void Dissimilarity_Configuration_drawShepardDiagram (Dissimilarity me, Configuration him, Graphics g, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { autoDistance dist = Configuration_to_Distance (him); Proximity_Distance_drawScatterDiagram (me, dist.peek(), g, xmin, xmax, ymin, ymax, size_mm, mark, garnish); } Distance Dissimilarity_Configuration_monotoneRegression (Dissimilarity dissimilarity, Configuration configuration, int tiesProcessing) { try { autoDistance dist = Configuration_to_Distance (configuration); autoDistance result = Dissimilarity_Distance_monotoneRegression (dissimilarity, dist.peek(), tiesProcessing); return result.transfer(); } catch (MelderError) { Melder_throw ("No Distance created (monotone regression)."); } } Distances Dissimilarities_Configuration_monotoneRegression (Dissimilarities me, Configuration configuration, int tiesProcessing) { try { autoDistances result = Distances_create (); autoDistance dist = Configuration_to_Distance (configuration); for (long i = 1; i <= my size; i++) { autoDistance d = Dissimilarity_Distance_monotoneRegression ( (Dissimilarity) my item[i], dist.peek(), tiesProcessing); Collection_addItem (result.peek(), d.transfer()); } return result.transfer(); } catch (MelderError) { Melder_throw ("No Distances created (monotone regression)."); } } void Dissimilarity_Configuration_drawMonotoneRegression (Dissimilarity me, Configuration him, Graphics g, int tiesProcessing, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { /* obsolete replace by transformator */ autoDistance fit = Dissimilarity_Configuration_monotoneRegression (me, him, tiesProcessing); Proximity_Distance_drawScatterDiagram (me, fit.peek(), g, xmin, xmax, ymin, ymax, size_mm, mark, garnish); } void Dissimilarity_Configuration_Weight_drawAbsoluteRegression (Dissimilarity d, Configuration c, Weight w, Graphics g, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { autoTransformator t = Transformator_create (d->numberOfRows); autoDistance fit = Dissimilarity_Configuration_Transformator_Weight_transform (d, c, t.peek(), w); Proximity_Distance_drawScatterDiagram (d, fit.peek(), g, xmin, xmax, ymin, ymax, size_mm, mark, garnish); } void Dissimilarity_Configuration_Weight_drawRatioRegression (Dissimilarity d, Configuration c, Weight w, Graphics g, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { autoRatioTransformator t = RatioTransformator_create (d -> numberOfRows); autoDistance fit = Dissimilarity_Configuration_Transformator_Weight_transform (d, c, t.peek(), w); Proximity_Distance_drawScatterDiagram (d, fit.peek(), g, xmin, xmax, ymin, ymax, size_mm, mark, garnish); } void Dissimilarity_Configuration_Weight_drawIntervalRegression (Dissimilarity d, Configuration c, Weight w, Graphics g, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { Dissimilarity_Configuration_Weight_drawISplineRegression (d, c, w, g, 0, 1, xmin, xmax, ymin, ymax, size_mm, mark, garnish); } void Dissimilarity_Configuration_Weight_drawMonotoneRegression (Dissimilarity d, Configuration c, Weight w, Graphics g, int tiesProcessing, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { autoMonotoneTransformator t = MonotoneTransformator_create (d->numberOfRows); MonotoneTransformator_setTiesProcessing (t.peek(), tiesProcessing); autoDistance fit = Dissimilarity_Configuration_Transformator_Weight_transform (d, c, t.peek(), w); Proximity_Distance_drawScatterDiagram (d, fit.peek(), g, xmin, xmax, ymin, ymax, size_mm, mark, garnish); } void Dissimilarity_Configuration_Weight_drawISplineRegression (Dissimilarity d, Configuration c, Weight w, Graphics g, long numberOfInternalKnots, long order, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark, int garnish) { autoISplineTransformator t = ISplineTransformator_create (d->numberOfRows, numberOfInternalKnots, order); autoDistance fit = Dissimilarity_Configuration_Transformator_Weight_transform (d, c, t.peek(), w); Proximity_Distance_drawScatterDiagram (d, fit.peek(), g, xmin, xmax, ymin, ymax, size_mm, mark, garnish); } Distance Dissimilarity_Configuration_Transformator_Weight_transform (Dissimilarity d, Configuration c, Any t, Weight w) { try { autoWeight aw = 0; if (w == 0) { aw.reset (Weight_create (d -> numberOfRows)); w = aw.peek(); } autoDistance cdist = Configuration_to_Distance (c); autoMDSVec v = Dissimilarity_to_MDSVec (d); autoDistance thee = Transformator_transform (t, v.peek(), cdist.peek(), w); return thee.transfer(); } catch (MelderError) { Melder_throw ("Distance not created."); } } double Dissimilarity_Configuration_Weight_Transformator_normalizedStress (Dissimilarity me, Configuration conf, Weight weight, Transformator t) { autoDistance cdist = Configuration_to_Distance (conf); autoMDSVec vec = Dissimilarity_to_MDSVec (me); autoDistance fdist = Transformator_transform (t, vec.peek(), cdist.peek(), weight); double stress = Distance_Weight_stress (fdist.peek(), cdist.peek(), weight, MDS_NORMALIZED_STRESS); return stress; } double Dissimilarity_Configuration_getStress (Dissimilarity me, Configuration him, int tiesProcessing, int stress_formula) { autoDistance dist = Configuration_to_Distance (him); autoMDSVec vec = Dissimilarity_to_MDSVec (me); autoDistance fit = MDSVec_Distance_monotoneRegression (vec.peek(), dist.peek(), tiesProcessing); double s, t, dbar; double stress; MDSVec_Distances_getStressValues (vec.peek(), dist.peek(), fit.peek(), stress_formula, &stress, &s, &t, &dbar); return stress; } Configuration Dissimilarity_Configuration_kruskal (Dissimilarity me, Configuration him, int tiesProcessing, int stress_formula, double tolerance, long numberOfIterations, long numberOfRepetitions) { try { // The Configuration is normalized: each dimension centred + // total variance set long numberOfCoordinates = my numberOfRows * his numberOfColumns; long numberOfParameters = numberOfCoordinates - his numberOfColumns - 1; long numberOfData = my numberOfRows * (my numberOfRows - 1) / 2; if (numberOfData < numberOfParameters) { Melder_throw ("The number of data must be larger than number of parameters in the model."); } autoKruskal thee = Kruskal_create (my numberOfRows, his numberOfColumns); TableOfReal_copyLabels (me, thy configuration, 1, 0); autoDissimilarity dissimilarity = Data_copy (me); Collection_addItem (thy proximities, dissimilarity.transfer()); thy vec = Dissimilarity_to_MDSVec (me); thy minimizer = (Minimizer) VDSmagtMinimizer_create (numberOfCoordinates, (Data) thee.peek(), func, dfunc); NUMdmatrix_into_vector (his data, thy minimizer -> p, 1, his numberOfRows, 1, his numberOfColumns); thy stress_formula = stress_formula; thy process = tiesProcessing; Configuration_setMetric (thy configuration, his metric); Minimizer_minimizeManyTimes (thy minimizer, numberOfRepetitions, numberOfIterations, tolerance); /* call the function to get the best configuration */ (void) func ( (Data) thee.peek(), ( (Minimizer) (thy minimizer)) -> p); autoConfiguration result = Data_copy (thy configuration); return result.transfer(); } catch (MelderError) { Melder_throw (me, ": no Configuration created."); } } /************************** INDSCAL **************************************/ /* Ten Berge, Kiers & Krijnen (1993), Computational Solutions for the Problem of Negative Saliences and Nonsymmetry in INDSCAL, Journal of Classification 10, 115-124. */ static void indscal_iteration_tenBerge (ScalarProducts zc, Configuration xc, Salience weights) { long nPoints = xc -> numberOfRows, nDimensions = xc -> numberOfColumns; long nSources = zc -> size; double **x = xc -> data, **w = weights -> data, lambda; // tolerance = 1e-4 is nearly optimal for dominant eigenvector estimation. double tolerance = 1e-4; autoNUMmatrix wsih (1, nPoints, 1, nPoints); autoNUMvector solution (1, nPoints); for (long h = 1; h <= nDimensions; h++) { autoCollection sprc = Data_copy ( (Collection) zc); for (long k = 1; k <= nPoints; k++) { for (long l = 1; l <= nPoints; l++) { wsih[k][l] = 0; } } for (long i = 1; i <= nSources; i++) { ScalarProduct spr = (ScalarProduct) sprc -> item[i]; double **sih = spr -> data; // Construct the S[i][h] matrices (eq. 6) for (long j = 1; j <= nDimensions; j++) { if (j == h) { continue; } for (long k = 1; k <= nPoints; k++) { for (long l = 1; l <= nPoints; l++) { sih[k][l] -= x[k][j] * x[l][j] * w[i][j]; } } } // the weighted S matrix (eq. 8) for (long k = 1; k <= nPoints; k++) { for (long l = 1; l <= nPoints; l++) { wsih[k][l] += w[i][h] * sih[k][l]; } } } // largest eigenvalue of m (nonsymmetric matrix!!) is optimal solution for this dimension for (long k = 1; k <= nPoints; k++) { solution[k] = x[k][h]; } NUMdominantEigenvector (wsih.peek(), nPoints, solution.peek(), &lambda, tolerance); // normalize the solution: centre and x'x = 1 double mean = 0; for (long k = 1; k <= nPoints; k++) { mean += solution[k]; } mean /= nPoints; if (mean == 0) { continue; } double scale = 0; for (long k = 1; k <= nPoints; k++) { solution[k] -= mean; scale += solution[k] * solution[k]; } for (long k = 1; k <= nPoints; k++) { x[k][h] = solution[k] / sqrt (scale); } // update weights. Make negative weights zero. for (long i = 1; i <= nSources; i++) { ScalarProduct spr = (ScalarProduct) sprc -> item[i]; double **sih = spr -> data, wih = 0; for (long k = 1; k <= nPoints; k++) { for (long l = 1; l <= nPoints; l++) { wih += x[k][h] * sih[k][l] * x[l][h]; } } if (wih < 0) { wih = 0; } w[i][h] = wih; } } } void ScalarProducts_Configuration_Salience_indscal (ScalarProducts sp, Configuration configuration, Salience weights, double tolerance, long numberOfIterations, int showProgress, Configuration *out1, Salience *out2, double *vaf) { try { double tol = 1e-6, vafp = 0; long nZeros = 0, nSources = sp -> size, iter; autoConfiguration x = Data_copy (configuration); autoSalience w = Data_copy (weights); *out1 = 0; *out2 = 0; if (showProgress) { Melder_progress (0.0, L"INDSCAL analysis"); } // Solve for X, and W matrix via Alternating Least Squares. for (iter = 1; iter <= numberOfIterations; iter++) { indscal_iteration_tenBerge (sp, x.peek(), w.peek()); // Goodness of fit and test criterion. ScalarProducts_Configuration_Salience_vaf (sp, x.peek(), w.peek(), vaf); if (*vaf > 1 - tol || fabs (*vaf - vafp) / vafp < tolerance) { break; } vafp = *vaf; if (showProgress) { Melder_progress ( (double) iter / (numberOfIterations + 1), L"indscal: vaf ", Melder_double (*vaf)); therror } } // Count number of zero weights nZeros = NUMdmatrix_countZeros (w->data, w->numberOfRows, w->numberOfColumns); // Set labels & names. Thing_setName (x.peek(), L"indscal"); Thing_setName (w.peek(), L"indscal"); TableOfReal_labelsFromCollectionItemNames (w.peek(), sp, 1, 0); *out1 = x.transfer(); *out2 = w.transfer(); if (showProgress) { MelderInfo_open (); MelderInfo_writeLine4 (L"**************** INDSCAL results on Distances " "*******************\n\n", Thing_className (sp), L"number of objects: ", Melder_integer (nSources)); for (long i = 1; i <= nSources; i++) { MelderInfo_writeLine2 (L" ", Thing_getName ( (Thing) sp -> item[i])); } if (nZeros > 0) { MelderInfo_writeLine5 (L"WARNING: ", Melder_integer (nZeros), L" zero weight", (nZeros > 1 ? L"s" : L""), L"!"); } MelderInfo_writeLine5 (L"\n\nVariance Accounted For = ", Melder_double (*vaf), L"\nThe optimal configuration was reached in ", Melder_integer ( (iter > numberOfIterations ? numberOfIterations : iter)), L" iterations."); MelderInfo_close (); } if (showProgress) { Melder_progress (1.0, NULL); } } catch (MelderError) { if (showProgress) { Melder_progress (1.0, NULL); } Melder_throw ("No indscal configuration calculated."); } } void Distances_Configuration_Salience_indscal (Distances distances, Configuration configuration, Salience weights, int normalizeScalarProducts, double tolerance, long numberOfIterations, int showProgress, Configuration *out1, Salience *out2, double *vaf) { try { *out1 = 0; *out2 = 0; autoScalarProducts sp = Distances_to_ScalarProducts (distances, normalizeScalarProducts); ScalarProducts_Configuration_Salience_indscal (sp.peek(), configuration, weights, tolerance, numberOfIterations, showProgress, out1, out2, vaf); } catch (MelderError) { Melder_throw ("No indscal configuration calculated."); } } void Dissimilarities_Configuration_Salience_indscal (Dissimilarities dissims, Configuration configuration, Salience weights, int tiesProcessing, int normalizeScalarProducts, double tolerance, long numberOfIterations, int showProgress, Configuration *out1, Salience *out2, double *vaf) { try { double tol = 1e-6, vafp = 0; long iter, nSources = dissims -> size;; autoConfiguration x = Data_copy (configuration); autoSalience w = Data_copy (weights); autoMDSVecs vecs = Dissimilarities_to_MDSVecs (dissims); *out1 = 0; *out2 = 0; if (showProgress) { Melder_progress (0.0, L"INDSCAL analysis"); } for (iter = 1; iter <= numberOfIterations; iter++) { autoDistances distances = MDSVecs_Configuration_Salience_monotoneRegression (vecs.peek(), x.peek(), w.peek(), tiesProcessing); autoScalarProducts sp = Distances_to_ScalarProducts (distances.peek(), normalizeScalarProducts); indscal_iteration_tenBerge (sp.peek(), x.peek(), w.peek()); // Goodness of fit and test criterion. Distances_Configuration_Salience_vaf (distances.peek(), x.peek(), w.peek(), normalizeScalarProducts, vaf); if (*vaf > 1 - tol || fabs (*vaf - vafp) / vafp < tolerance) { break; } vafp = *vaf; if (showProgress) { Melder_progress ( (double) iter / (numberOfIterations + 1), L"indscal: vaf ", Melder_double (*vaf)); therror } } // Count number of zero weights long nZeros = NUMdmatrix_countZeros (w -> data, w -> numberOfRows, w -> numberOfColumns); // Set labels & names. Thing_setName (x.peek(), L"indscal_mr"); Thing_setName (w.peek(), L"indscal_mr"); TableOfReal_labelsFromCollectionItemNames (w.peek(), dissims, 1, 0); *out1 = x.transfer(); *out2 = w.transfer(); if (showProgress) { MelderInfo_open (); MelderInfo_writeLine1 (L"**************** INDSCAL with monotone regression *******************"); MelderInfo_writeLine1 (Thing_className (dissims)); MelderInfo_writeLine2 (L"Number of objects: ", Melder_integer (nSources)); for (long i = 1; i <= nSources; i++) { MelderInfo_writeLine2 (L" ", Thing_getName ( (Thing) dissims -> item[i])); } if (nZeros > 0) { MelderInfo_writeLine4 (L"WARNING: ", Melder_integer (nZeros), L" zero weight", (nZeros > 1 ? L"s" : L"")); } MelderInfo_writeLine2 (L"Variance Accounted For: ", Melder_double (*vaf)); MelderInfo_writeLine1 (L"Based on MONOTONE REGRESSION"); MelderInfo_writeLine2 (L"number of iterations: ", Melder_integer ( (iter > numberOfIterations ? numberOfIterations : iter))); MelderInfo_close (); } if (showProgress) { Melder_progress (1.0, NULL); } } catch (MelderError) { if (showProgress) { Melder_progress (1.0, NULL); } Melder_throw ("no inscal configuration calculated."); } } void Distances_Configuration_indscal (Distances dists, Configuration conf, int normalizeScalarProducts, double tolerance, long numberOfIterations, int showProgress, Configuration *out1, Salience *out2) { try { autoSalience w = Salience_create (dists -> size, conf -> numberOfColumns); double vaf; Distances_Configuration_Salience_indscal (dists, conf, w.peek(), normalizeScalarProducts, tolerance, numberOfIterations, showProgress, out1, out2, &vaf); } catch (MelderError) { Melder_throw ("No indscal performed."); } } Distances MDSVecs_Configuration_Salience_monotoneRegression (MDSVecs vecs, Configuration conf, Salience weights, int tiesProcessing) { try { long nDimensions = conf -> numberOfColumns; autoNUMvector w (NUMvector_copy (conf -> w, 1, nDimensions), 1); autoDistances distances = Distances_create (); for (long i = 1; i <= vecs -> size; i++) { NUMvector_copyElements (weights -> data[i], conf -> w, 1, nDimensions); autoDistance dc = Configuration_to_Distance (conf); autoDistance dist = MDSVec_Distance_monotoneRegression ( (MDSVec) vecs -> item[i], dc.peek(), tiesProcessing); Collection_addItem (distances.peek(), dist.transfer()); } Configuration_setDefaultWeights (conf); return distances.transfer(); } catch (MelderError) { Melder_throw ("No Distances created."); } } Salience Distances_Configuration_to_Salience (Distances d, Configuration c, int normalize) { try { autoScalarProducts sp = Distances_to_ScalarProducts (d, normalize); autoSalience w = ScalarProducts_Configuration_to_Salience (sp.peek(), c); return w.transfer(); } catch (MelderError) { Melder_throw ("No Salience created."); } } Salience ScalarProducts_Configuration_to_Salience (ScalarProducts me, Configuration him) { try { autoSalience salience = Salience_create (my size, his numberOfColumns); autoConfiguration cx = Data_copy (him); indscal_iteration_tenBerge (me, cx.peek(), salience.peek()); return salience.transfer(); } catch (MelderError) { Melder_throw ("No Salience created."); } } Salience Dissimilarities_Configuration_to_Salience (Dissimilarities me, Configuration him, int tiesProcessing, int normalizeScalarProducts) { try { autoDistances distances = Dissimilarities_Configuration_monotoneRegression (me, him, tiesProcessing); autoSalience w = Distances_Configuration_to_Salience (distances.peek(), him, normalizeScalarProducts); return w.transfer(); } catch (MelderError) { Melder_throw ("No Salience created."); } } void Dissimilarities_Configuration_indscal (Dissimilarities dissims, Configuration conf, int tiesProcessing, int normalizeScalarProducts, double tolerance, long numberOfIterations, int showProgress, Configuration *out1, Salience *out2) { try { *out1 = 0; *out2 = 0; autoDistances distances = Dissimilarities_Configuration_monotoneRegression (dissims, conf, tiesProcessing); auto Salience weights = Distances_Configuration_to_Salience (distances.peek(), conf, normalizeScalarProducts); double vaf; Dissimilarities_Configuration_Salience_indscal (dissims, conf, weights, tiesProcessing, normalizeScalarProducts, tolerance, numberOfIterations, showProgress, out1, out2, &vaf); } catch (MelderError) { Melder_throw ("No indscal performed."); } } void Dissimilarities_indscal (Dissimilarities me, long numberOfDimensions, int tiesProcessing, int normalizeScalarProducts, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress, Configuration *out1, Salience *out2) { int showMulti = showProgress && numberOfRepetitions > 1; try { int showSingle = showProgress && numberOfRepetitions == 1; double vaf, vafmin = 0; *out1 = 0; *out2 = 0; autoDistances distances = Dissimilarities_to_Distances (me, MDS_ORDINAL); Configuration cstart1 = 0; Salience wstart1 = 0; Distances_to_Configuration_ytl (distances.peek(), numberOfDimensions, normalizeScalarProducts, &cstart1, &wstart1); autoConfiguration cstart = cstart1; autoSalience wstart = wstart1; autoConfiguration cbest = Data_copy ( (Configuration) cstart.peek()); autoSalience wbest = Data_copy ( (Salience) wstart.peek()); if (showMulti) { Melder_progress (0.0, L"Indscal many times"); } for (long iter = 1; iter <= numberOfRepetitions; iter++) { Configuration cresult1 = 0; Salience wresult1 = 0; Dissimilarities_Configuration_Salience_indscal (me, cstart.peek(), wstart.peek(), tiesProcessing, normalizeScalarProducts, tolerance, numberOfIterations, showSingle, &cresult1, &wresult1, &vaf); autoConfiguration cresult = cresult1; autoSalience wresult = wresult1; if (vaf > vafmin) { vafmin = vaf; cbest.reset (cresult.transfer()); wbest.reset (wresult.transfer()); } Configuration_randomize (cstart.peek()); Configuration_normalize (cstart.peek(), 1.0, 1); Salience_setDefaults (wstart.peek()); if (showMulti) { Melder_progress ( (double) iter / (numberOfRepetitions + 1), Melder_integer (iter), L" from ", Melder_integer (numberOfRepetitions)); therror } } *out1 = cbest.transfer(); *out2 = wbest.transfer(); if (showMulti) { Melder_progress (1.0, 0); } } catch (MelderError) { if (showMulti) { Melder_progress (1.0, 0); } Melder_throw (me, ": no indscal performed."); } } void Distances_indscal (Distances distances, long numberOfDimensions, int normalizeScalarProducts, double tolerance, long numberOfIterations, long numberOfRepetitions, int showProgress, Configuration *out1, Salience *out2) { int showMulti = showProgress && numberOfRepetitions > 1; try { int showSingle = showProgress && numberOfRepetitions == 1; double vaf, vafmin = 0; *out1 = 0; *out2 = 0; Configuration cstart1 = 0; Salience wstart1 = 0; Distances_to_Configuration_ytl (distances, numberOfDimensions, normalizeScalarProducts, &cstart1, &wstart1); autoConfiguration cstart = cstart1; autoSalience wstart = wstart1; autoConfiguration cbest = Data_copy (cstart.peek()); autoSalience wbest = Data_copy (wstart.peek()); if (showMulti) { Melder_progress (0.0, L"Indscal many times"); } for (long i = 1; i <= numberOfRepetitions; i++) { Configuration cresult1 = 0; Salience wresult1 = 0; Distances_Configuration_Salience_indscal (distances, cstart.peek(), wstart.peek(), normalizeScalarProducts, tolerance, numberOfIterations, showSingle, &cresult1, &wresult1, &vaf); autoConfiguration cresult = cresult1; autoSalience wresult = wresult1; if (vaf > vafmin) { vafmin = vaf; cbest.reset (cresult.transfer()); wbest.reset (wresult.transfer()); } Configuration_randomize (cstart.peek()); Configuration_normalize (cstart.peek(), 1.0, 1); Salience_setDefaults (wstart.peek()); if (showMulti) { Melder_progress ( (double) i / (numberOfRepetitions + 1), Melder_integer (i), L" from ", Melder_integer (numberOfRepetitions)); therror } } *out1 = cbest.transfer(); *out2 = wbest.transfer(); if (showMulti) { Melder_progress (1.0, NULL); } } catch (MelderError) { if (showMulti) { Melder_progress (1.0, NULL); } Melder_throw (distances, ": no indscal performed."); } } void Dissimilarities_Configuration_Salience_vaf (Dissimilarities me, Configuration thee, Salience him, int tiesProcessing, int normalizeScalarProducts, double *vaf) { autoDistances distances = Dissimilarities_Configuration_monotoneRegression (me, thee, tiesProcessing); Distances_Configuration_Salience_vaf (distances.peek(), thee, him, normalizeScalarProducts, vaf); } void Distances_Configuration_vaf (Distances me, Configuration thee, int normalizeScalarProducts, double *vaf) { autoSalience w = Distances_Configuration_to_Salience (me, thee, normalizeScalarProducts); Distances_Configuration_Salience_vaf (me, thee, w.peek(), normalizeScalarProducts, vaf); } void Dissimilarities_Configuration_vaf (Dissimilarities me, Configuration thee, int tiesProcessing, int normalizeScalarProducts, double *vaf) { autoSalience w = Dissimilarities_Configuration_to_Salience (me, thee, tiesProcessing, normalizeScalarProducts); Dissimilarities_Configuration_Salience_vaf (me, thee, w.peek(), tiesProcessing, normalizeScalarProducts, vaf); } void Distances_Configuration_Salience_vaf (Distances me, Configuration thee, Salience him, int normalizeScalarProducts, double *vaf) { if (my size != his numberOfRows || thy numberOfColumns != his numberOfColumns) Melder_throw ("Dimensions must conform."); autoScalarProducts sp = Distances_to_ScalarProducts (me, normalizeScalarProducts); ScalarProducts_Configuration_Salience_vaf (sp.peek(), thee, him, vaf); } void ScalarProduct_Configuration_getVariances (ScalarProduct me, Configuration thee, double *varianceExplained, double *varianceTotal) { *varianceExplained = *varianceTotal = 0; autoDistance distance = Configuration_to_Distance (thee); autoScalarProduct fit = Distance_to_ScalarProduct (distance.peek(), 0); /* ScalarProduct is double centred, i.e., mean == 0. */ for (long j = 1; j <= my numberOfRows; j++) { for (long k = 1; k <= my numberOfColumns; k++) { double d2 = my data[j][k] - fit -> data[j][k]; *varianceExplained += d2 * d2; *varianceTotal += my data[j][k] * my data[j][k]; } } } void ScalarProducts_Configuration_Salience_vaf (ScalarProducts me, Configuration thee, Salience him, double *vaf) { autoNUMvector w (NUMvector_copy (thy w, 1, thy numberOfColumns), 1); // save weights try { if (my size != his numberOfRows || thy numberOfColumns != his numberOfColumns) Melder_throw ("Dimensions of input objects must conform."); double t = 0, n = 0; for (long i = 1; i <= my size; i++) { ScalarProduct sp = (ScalarProduct) my item[i]; if (sp -> numberOfRows != thy numberOfRows) { Melder_throw ("ScalarProduct ", i, " does not match Configuration."); } // weigh configuration before calculating variances for (long j = 1; j <= thy numberOfColumns; j++) { thy w[j] = sqrt (his data[i][j]); } double vare, vart; ScalarProduct_Configuration_getVariances (sp, thee, &vare, &vart); t += vare; n += vart; } *vaf = n > 0 ? 1.0 - t / n : 0; NUMvector_copyElements (w.peek(), thy w, 1, thy numberOfColumns); // restore weights } catch (MelderError) { NUMvector_copyElements (w.peek(), thy w, 1, thy numberOfColumns); Melder_throw ("No vaf calculasted."); } } /********************** Examples *********************************************/ Dissimilarity Dissimilarity_createLetterRExample (double noiseStd) { try { autoConfiguration r = Configuration_createLetterRExample (1); autoDistance d = Configuration_to_Distance (r.peek()); autoDissimilarity me = Distance_to_Dissimilarity (d.peek()); Thing_setName (me.peek(), L"R"); for (long i = 1; i <= my numberOfRows - 1; i++) { for (long j = i + 1; j <= my numberOfRows; j++) { double dis = my data[i][j]; my data[j][i] = my data[i][j] = dis * dis + 5 + NUMrandomUniform (0, noiseStd); } } return me.transfer(); } catch (MelderError) { Melder_throw ("Dissimilarity for letter R example not created."); } } Salience Salience_createCarrollWishExample () { try { long nSources = 8; double wx[9] = {0, 1, 0.866, 0.707, 0.5, 0.1, 0.5, 0.354, 0.1}; double wy[9] = {0, 0.1, 0.5, 0.707, 0.866, 1, 0.1, 0.354, 0.5}; wchar_t const *name[] = { L"", L"1", L"2", L"3", L"4", L"5", L"6", L"7", L"8"}; autoSalience me = Salience_create (nSources, 2); for (long i = 1; i <= nSources; i++) { my data[i][1] = wx[i]; my data[i][2] = wy[i]; TableOfReal_setRowLabel (me.peek(), i, name[i]); } return me.transfer(); } catch (MelderError) { Melder_throw ("Salience for Carroll Wish example not created."); } } Collection INDSCAL_createCarrollWishExample (double noiseRange) { try { autoConfiguration c = Configuration_createCarrollWishExample (); long nObjects = c -> numberOfRows, nSources = 8; autoSalience s = Salience_createCarrollWishExample (); autoCollection me = Collection_create (classData, nSources); for (long l = 1; l <= nSources; l++) { c -> w[1] = s -> data[l][1]; c -> w[2] = s -> data[l][2]; autoDistance d = Configuration_to_Distance (c.peek()); autoDissimilarity dissim = Distance_to_Dissimilarity (d.peek()); for (long i = 1; i <= nObjects - 1; i++) { for (long j = i + 1; j <= nObjects; j++) { dissim -> data[i][j] = (dissim -> data[j][i] += NUMrandomUniform (0, noiseRange)); } } Thing_setName (dissim.peek(), s -> rowLabels[l]); Collection_addItem (me.peek(), dissim.transfer()); } Thing_setName (me.peek(), L"CarrollWish"); return me.transfer(); } catch (MelderError) { Melder_throw ("Collection not created."); } } void drawSplines (Graphics g, double low, double high, double ymin, double ymax, int type, long order, wchar_t const *interiorKnots, int garnish) { long k = order, numberOfKnots, numberOfInteriorKnots = 0; long nSplines, n = 1000; double knot[101], y[1001]; wchar_t *start, *end; if (type == MDS_ISPLINE) { k++; } for (long i = 1; i <= k; i++) { knot[i] = low; } numberOfKnots = k; start = (wchar_t *) interiorKnots; while (*start) { double value = wcstod (start, &end); start = end; if (value < low || value > high) { Melder_warning (L"drawSplines: knots must be in interval (", Melder_double (low), L", ", Melder_double (high), L")"); return; } if (numberOfKnots == 100) { Melder_warning (L"drawSplines: too many knots (101)"); return; } knot[++numberOfKnots] = value; } numberOfInteriorKnots = numberOfKnots - k; for (long i = 1; i <= k; i++) { knot[++numberOfKnots] = high; } nSplines = order + numberOfInteriorKnots; if (nSplines == 0) { return; } Graphics_setWindow (g, low, high, ymin, ymax); Graphics_setInner (g); for (long i = 1; i <= nSplines; i++) { double x, yx, dx = (high - low) / (n - 1); for (long j = 1; j <= n; j++) { x = low + dx * (j - 1); if (type == MDS_MSPLINE) { (void) NUMmspline (knot, numberOfKnots, order, i, x, &yx); } else { (void) NUMispline (knot, numberOfKnots, order, i, x, &yx); } y[j] = yx < ymin ? ymin : yx > ymax ? ymax : yx; } Graphics_function (g, y, 1, n, low, high); } Graphics_unsetInner (g); if (garnish) { static MelderString ts = { 0 }; long lastKnot = type == MDS_ISPLINE ? numberOfKnots - 2 : numberOfKnots; MelderString_empty (&ts); Graphics_drawInnerBox (g); Graphics_textLeft (g, 0, type == MDS_MSPLINE ? L"\\s{M}\\--spline" : L"\\s{I}\\--spline"); Graphics_marksTop (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); if (low <= knot[order]) { if (order == 1) { MelderString_append (&ts, L"t__1_"); } else if (order == 2) { MelderString_append (&ts, L"{t__1_, t__2_}"); } else { MelderString_append (&ts, L"{t__1_..t__", Melder_integer (order), L"_}"); } Graphics_markBottom (g, low, 0, 0, 0, ts.string); } for (long i = 1; i <= numberOfInteriorKnots; i++) { if (low <= knot[k + i] && knot[k + i] < high) { MelderString_empty (&ts); MelderString_append (&ts, L"t__", Melder_integer (order + i), L"_"); Graphics_markBottom (g, knot[k + i], 0, 1, 1, ts.string); Graphics_markTop (g, knot[k + i], 1, 0, 0, 0); } } if (knot[lastKnot - order + 1] <= high) { MelderString_empty (&ts); if (order == 1) { MelderString_append (&ts, L"t__", Melder_integer (lastKnot), L"_"); } else { MelderString_append (&ts, L"{t__", Melder_integer (order == 2 ? lastKnot - 1 : lastKnot - order + 1), L"_, t__", Melder_integer (lastKnot), L"_}"); } Graphics_markBottom (g, high, 0, 0, 0, ts.string); } } } void drawMDSClassRelations (Graphics g) { long nBoxes = 6; double boxWidth = 0.3, boxWidth2 = boxWidth / 2, boxWidth3 = boxWidth / 3; double boxHeight = 0.1, boxHeight2 = boxHeight / 2; double boxHeight3 = boxHeight / 3; double r_mm = 3, dxt = 0.025, dyt = 0.03; double dboxx = 1 - 0.2 - 2 * boxWidth, dboxy = (1 - 4 * boxHeight) / 3; double x1, x2, xm, x23, x13, y1, y2, ym, y23, y13; double x[7] = {0.0, 0.2, 0.2, 0.7, 0.2, 0.7, 0.2}; /* left */ double y[7] = {0.0, 0.9, 0.6, 0.6, 0.3, 0.3, 0.0}; /* bottom */ wchar_t const *text[7] = {L"", L"Confusion", L"Dissimilarity %\\de__%%ij%_", L"Similarity", L"Distance %d__%%ij%_, %d\\'p__%%ij%_", L"ScalarProduct", L"Configuration" }; Graphics_setWindow (g, -0.05, 1.05, -0.05, 1.05); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (long i = 1; i <= nBoxes; i++) { x2 = x[i] + boxWidth; y2 = y[i] + boxHeight; xm = x[i] + boxWidth2; ym = y[i] + boxHeight2; Graphics_roundedRectangle (g, x[i], x2, y[i], y2, r_mm); Graphics_text (g, xm, ym, text[i]); } Graphics_setLineWidth (g, 2); Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_BOTTOM); // Confusion to Dissimilarity xm = x[1] + boxWidth2; y2 = y[2] + boxHeight; Graphics_arrow (g, xm, y[1], xm, y2); Graphics_text (g, xm + dxt, y2 + dboxy / 2, L"pdf"); // Confusion to Similarity x1 = x[1] + boxWidth; xm = x[3] + boxWidth2; ym = y[1] + boxHeight2; y2 = y[3] + boxHeight; Graphics_line (g, x1, ym, xm, ym); Graphics_arrow (g, xm, ym, xm, y2); y2 += + dboxy / 2 + dyt / 2; Graphics_text (g, xm + dxt, y2, L"average"); y2 -= dyt; Graphics_text (g, xm + dxt, y2, L"houtgast"); // Dissimilarity to Similarity x1 = x[2] + boxWidth; y23 = y[2] + 2 * boxHeight3; Graphics_arrow (g, x1, y23, x[3], y23); y13 = y[2] + boxHeight3; Graphics_arrow (g, x[3], y13, x1, y13); // Dissimilarity to Distance x13 = x[4] + boxWidth3; y1 = y[4] + boxHeight; Graphics_arrow (g, x13, y1, x13, y[2]); x23 = x[4] + 2 * boxWidth3; Graphics_arrow (g, x23, y[2], x23, y1); x1 = x23 + dxt; y1 = y[2] - dyt; x2 = 0 + dxt; y1 -= dyt; Graphics_text (g, x1, y1, L"%d\\'p__%%ij%_ = %\\de__%%ij%_"); Graphics_text (g, x2, y1, L"absolute"); y1 -= dyt; Graphics_text (g, x1, y1, L"%d\\'p__%%ij%_ = %b\\.c%\\de__%%ij%_"); Graphics_text (g, x2, y1, L"ratio"); y1 -= dyt; Graphics_text (g, x1, y1, L"%d\\'p__%%ij%_ = %b\\.c%\\de__%%ij%_+%a"); Graphics_text (g, x2, y1, L"interval"); y1 -= dyt; Graphics_text (g, x1, y1, L"%d\\'p__%%ij%_ = \\s{I}-spline (%\\de__%%ij%_)"); Graphics_text (g, x2, y1, L"\\s{I}\\--spline"); y1 -= dyt; Graphics_text (g, x1, y1, L"%d\\'p__%%ij%_ = monotone (%\\de__%%ij%_)"); Graphics_text (g, x2, y1, L"monotone"); // Distance to ScalarProduct x1 = x[4] + boxWidth; ym = y[4] + boxHeight2; Graphics_arrow (g, x1, ym, x[5], ym); // Distance to Configuration y1 = y[6] + boxHeight; Graphics_arrow (g, x13, y1, x13, y[4]); // ScalarProduct to Configuration x13 = x[5] + boxWidth3; x23 = x[6] + 2 * boxWidth3; y1 = y[5] - dboxy / 2; Graphics_line (g, x13, y[5], x13, y1); Graphics_line (g, x13, y1, x23, y1); Graphics_arrow (g, x23, y1, x23, y[6] + boxHeight); x1 = x[6] + boxWidth + dboxx / 2; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (g, x1, y1, L"\\s{TORSCA}"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_TOP); Graphics_text (g, x1, y1, L"\\s{YTL}"); Graphics_setLineType (g, Graphics_DOTTED); x23 = x[5] + 2 * boxWidth3; ym = y[6] + boxHeight2; Graphics_line (g, x23, y[5], x23, ym); Graphics_arrow (g, x23, ym, x[6] + boxWidth, ym); x1 = x[6] + boxWidth + dboxx / 2 + boxWidth3; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (g, x1, ym, L"\\s{INDSCAL}"); // Dissimilarity to Configuration ym = y[2] + boxHeight2; y2 = y[6] + boxHeight2; Graphics_line (g, x[2], ym, 0, ym); Graphics_line (g, 0, ym, 0, y2); Graphics_arrow (g, 0, y2, x[6], y2); // Restore settings Graphics_setLineType (g, Graphics_DRAWN); Graphics_setLineWidth (g, 1); Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_BOTTOM); } /* End of file MDS.cpp */ sources_5316/dwtools/Proximity.cpp0000644000176700017670000000234311627250702016132 0ustar paulpaul/* Proximity.c * * Copyright (C) 1993-2004 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20040309 Removed assertion 'numberOfPoints> 0' in Proximity_init */ #include "Proximity.h" #include "TableOfReal_extensions.h" Thing_implement (Proximity, TableOfReal, 0); void Proximity_init (I, long numberOfPoints) { iam (Proximity); TableOfReal_init (me, numberOfPoints, numberOfPoints); TableOfReal_setSequentialRowLabels (me, 0, 0, NULL, 1, 1); TableOfReal_setSequentialColumnLabels (me, 0, 0, NULL, 1, 1); } /* End of file Proximity.c */ sources_5316/dwtools/Discriminant_def.h0000644000176700017670000000226511627174665017055 0ustar paulpaul/* Discriminant_def.h * * Copyright (C) 1993-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Discriminant oo_DEFINE_CLASS (Discriminant, Eigen) oo_LONG (numberOfGroups) oo_OBJECT (SSCPs, 0, groups) oo_OBJECT (SSCP, 0, total) oo_DOUBLE_VECTOR (aprioriProbabilities, numberOfGroups) oo_DOUBLE_MATRIX (costs, numberOfGroups, numberOfGroups) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (Discriminant) #undef ooSTRUCT /* End of file Discriminant_def.h */ sources_5316/dwtools/Vowel_def.h0000644000176700017670000000170711627360652015516 0ustar paulpaul/* Vowel_def.h * * Copyright (C) 2011 David Weenink & Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Vowel oo_DEFINE_CLASS (Vowel, Function) oo_OBJECT (PitchTier, 0, pt) oo_OBJECT (FormantTier, 0, ft) oo_END_CLASS (Vowel) #undef ooSTRUCT /* End of file Vowel_def.h */ sources_5316/dwtools/SpeechSynthesizer_and_TextGrid.h0000664000176700017670000000517211746237055021723 0ustar paulpaul#ifndef _SpeechSynthesizer_and_TextGrid_h_ #define _SpeechSynthesizer_and_TextGrid_h_ /* SpeechSynthesizer_and_TextGrid.h * * Copyright (C) 2011-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20111214 */ #include "SpeechSynthesizer.h" #include "TextGrid_extensions.h" #include "EditDistanceTable.h" Sound SpeechSynthesizer_and_TextInterval_to_Sound (SpeechSynthesizer me, TextInterval thee, TextGrid *tg); Sound SpeechSynthesizer_and_TextGrid_to_Sound (SpeechSynthesizer me, TextGrid thee, long itier, long iiint, TextGrid *tg); TextGrid SpeechSynthesizer_and_Sound_and_TextInterval_align (SpeechSynthesizer me, Sound thee, TextInterval him, double silenceThreshold, double minSilenceDuration, double minSoundingDuration); TextGrid SpeechSynthesizer_and_Sound_and_IntervalTier_align (SpeechSynthesizer me, Sound thee, IntervalTier him, long istart, long iend, double silenceThreshold, double minSilenceDuration, double minSoundingDuration); TextGrid SpeechSynthesizer_and_Sound_and_TextGrid_align (SpeechSynthesizer me, Sound thee, TextGrid him, long tierNumber, long istart, long iend, double silenceThreshold, double minSilenceDuration, double minSoundingDuration); TextGrid SpeechSynthesizer_and_Sound_and_TextGrid_align2 (SpeechSynthesizer me, Sound thee, TextGrid him, long tierNumber, long istart, long iend, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double trimDuration); Table IntervalTiers__to_Table_textAlignmentment (IntervalTier target, IntervalTier source, EditCostsTable costs); Table TextGrids_to_Table_textAlignmentment (TextGrid target, long ttier, TextGrid source, long stier, EditCostsTable costs); /* For testing purposes only */ TextGrid TextGrid_and_IntervalTier_patch (TextGrid me, IntervalTier thee, const wchar_t *patchLabel, double precision); TextGrid TextGrid_and_IntervalTier_cutPartsMatchingLabel (TextGrid me, IntervalTier thee, const wchar_t *label, double precision); #endif // _SpeechSynthesizer_and_TextGrid_h_ sources_5316/dwtools/CategoriesEditor.cpp0000664000176700017670000006630711662404447017404 0ustar paulpaul/* CategoriesEditor.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 1995 djmw 19980225 repaired a memory leak, caused by wrong inheritance for CategoriesEditorInsert command. djmw 20020408 GPL djmw 20020408 Modified 'createMenus' djmw 20060111 Replaced Resources.h with Preferences.h djmw 20060328 Changed last argument to 0 in XtVaSetValues, XtVaGetValues and XtVaCreateManagedWidget for 64-bit compatibility. djmw 20070620 Latest modification. pb 20080320 split off Help menu pb 20080321 new Editor API djmw 20090107 Removed a bug in update that caused editor to crash on replace djmw 20090203 Removed potential crashes in CategoriesEditor_create. djmw 20110304 Thing_new djmw 20111110 Use autostringvector */ #define CategoriesEditor_TEXTMAXLENGTH 100 #include "CategoriesEditor.h" //#include "Preferences.h" #include "EditorM.h" Thing_implement (CategoriesEditor, Editor, 0); /* forward declarations */ static void update (I, long from, long to, const long *select, long nSelect); static void update_dos (I); const wchar *CategoriesEditor_EMPTYLABEL = L"(empty)"; static void menu_cb_help (EDITOR_ARGS) { EDITOR_IAM (CategoriesEditor); Melder_help (L"CategoriesEditor"); } /**************** Some methods for Collection ****************/ /* Preconditions: */ /* 1 <= (position[i], newpos) <= size; */ /* newpos <= position[1] || newpos >= position[npos] */ static void Ordered_moveItems (I, long position[], long npos, long newpos) { iam (Ordered); long pos, min = position[1], max = position[1]; for (long i = 2; i <= npos; i++) { if (position[i] > max) { max = position[i]; } else if (position[i] < min) { min = position[i]; } } Melder_assert (min >= 1 && max <= my size && (newpos <= min || newpos >= max)); autoNUMvector tmp (1, npos); // 'remove' for (long i = 1; i <= npos; i++) { tmp[i] = (Data) my item[position[i]]; my item[position[i]] = 0; } // create a contiguous 'hole' if (newpos <= min) { pos = max; for (long i = max; i >= newpos; i--) { if (my item[i]) { my item[pos--] = my item[i]; } } pos = newpos; } else { pos = min; for (long i = min; i <= newpos; i++) { if (my item[i]) { my item[pos++] = my item[i]; } } pos = newpos - npos + 1; } // fill the 'hole' for (long i = 1; i <= npos; i++) { my item[pos++] = tmp[i]; } } static void Collection_replaceItemPos (I, Any item, long pos) { iam (Collection); if (pos < 1 || pos > my size) { return; } forget ( ( (SimpleString *) my item) [pos]); my item[pos] = item; } /* Remove the item at position 'from' and insert it at position 'to'. */ static void Ordered_moveItem (I, long from, long to) { iam (Ordered); if (from < 1 || from > my size) { from = my size; } if (to < 1 || to > my size) { to = my size; } if (from == to) { return; } Data tmp = (Data) my item[from]; if (from > to) { for (long i = from; i > to; i--) { my item[i] = my item[i - 1]; } } else { for (long i = from; i < to; i++) { my item[i] = my item[i + 1]; } } my item[to] = tmp; } /********************** General Command **********************/ Thing_define (CategoriesEditorCommand, Command) { // new data: public: Categories categories; long *selection; long nSelected, newPos; // overridden methods: virtual void v_destroy (); }; Thing_implement (CategoriesEditorCommand, Command, 0); void structCategoriesEditorCommand :: v_destroy () { NUMvector_free (selection, 1); forget (categories); CategoriesEditorCommand_Parent :: v_destroy (); } static void CategoriesEditorCommand_init (I, const wchar_t *name, Any data, int (*execute) (Any), int (*undo) (Any), int nCategories, int nSelected) { iam (CategoriesEditorCommand); (void) nCategories; my nSelected = nSelected; Command_init (me, name, data, execute, undo); my categories = Categories_create(); my selection = NUMvector (1, nSelected); } /*********************** Insert Command ***********************/ Thing_define (CategoriesEditorInsert, CategoriesEditorCommand) { }; Thing_implement (CategoriesEditorInsert, CategoriesEditorCommand, 0); static int CategoriesEditorInsert_execute (I) { iam (CategoriesEditorInsert); CategoriesEditor editor = (CategoriesEditor) my data; Categories categories = (Categories) editor -> data; autoSimpleString str = Data_copy ( (SimpleString) ( (Categories) my categories)->item[1]); Ordered_addItemPos (categories, str.transfer(), my selection[1]); update (editor, my selection[1], 0, my selection, 1); return 1; } static int CategoriesEditorInsert_undo (I) { iam (CategoriesEditorInsert); CategoriesEditor editor = (CategoriesEditor) my data; Categories categories = (Categories) editor -> data; Collection_removeItem (categories, my selection[1]); update (editor, my selection[1], 0, my selection, 1); return 1; } static CategoriesEditorInsert CategoriesEditorInsert_create (Any data, Any str, int position) { try { autoCategoriesEditorInsert me = Thing_new (CategoriesEditorInsert); CategoriesEditorCommand_init (me.peek(), L"Insert", data, CategoriesEditorInsert_execute, CategoriesEditorInsert_undo, 1, 1); my selection[1] = position; Collection_addItem (my categories, (SimpleString) str); return me.transfer(); } catch (MelderError) { Melder_throw ("CategoriesEditorInsert not created."); } } /*********************** Remove Command ***********************/ Thing_define (CategoriesEditorRemove, CategoriesEditorCommand) { }; Thing_implement (CategoriesEditorRemove, CategoriesEditorCommand, 0); static int CategoriesEditorRemove_execute (I) { iam (CategoriesEditorRemove); CategoriesEditor editor = (CategoriesEditor) my data; Categories l_categories = (Categories) editor -> data; // David, weer link: tweemaal dezelfde naam (categories): is ok, geen conflict. Naam toch maar aangepast for (long i = my nSelected; i >= 1; i--) { Ordered_addItemPos (my categories, (SimpleString) l_categories -> item[my selection[i]], 1); l_categories -> item[my selection[i]] = 0; Collection_removeItem (l_categories, my selection[i]); } update (editor, my selection[1], 0, 0, 0); return 1; } static int CategoriesEditorRemove_undo (I) { iam (CategoriesEditorRemove); CategoriesEditor editor = (CategoriesEditor) my data; Categories categories = (Categories) editor -> data; for (long i = 1; i <= my nSelected; i++) { autoSimpleString item = Data_copy ( (SimpleString) my categories -> item[i]); Ordered_addItemPos (categories, item.transfer(), my selection[i]); } update (editor, my selection[1], 0, my selection, my nSelected); return 1; } static CategoriesEditorRemove CategoriesEditorRemove_create (Any data, long *posList, long posCount) { try { autoCategoriesEditorRemove me = Thing_new (CategoriesEditorRemove); CategoriesEditorCommand_init (me.peek(), L"Remove", data, CategoriesEditorRemove_execute, CategoriesEditorRemove_undo, posCount, posCount); for (long i = 1; i <= posCount; i++) { my selection[i] = posList[i]; } return me.transfer(); } catch (MelderError) { Melder_throw ("CategoriesEditorRemove not created."); } } //update (me); /*********************** Replace Command ***********************/ Thing_define (CategoriesEditorReplace, CategoriesEditorCommand) { }; Thing_implement (CategoriesEditorReplace, CategoriesEditorCommand, 0); static int CategoriesEditorReplace_execute (I) { iam (CategoriesEditorReplace); CategoriesEditor editor = (CategoriesEditor) my data; Categories categories = (Categories) editor -> data; for (long i = my nSelected; i >= 1; i--) { autoSimpleString str = Data_copy ( (SimpleString) my categories -> item[1]); Ordered_addItemPos (my categories, (SimpleString) categories -> item[my selection[i]], 2); categories -> item[my selection[i]] = str.transfer(); } update (editor, my selection[1], my selection[my nSelected], my selection, my nSelected); return 1; } static int CategoriesEditorReplace_undo (I) { iam (CategoriesEditorReplace); CategoriesEditor editor = (CategoriesEditor) my data; Categories categories = (Categories) editor -> data; for (long i = 1; i <= my nSelected; i++) { autoSimpleString str = Data_copy ( (SimpleString) my categories -> item[i + 1]); Collection_replaceItemPos (categories, str.transfer(), my selection[i]); } update (editor, my selection[1], my selection[my nSelected], my selection, my nSelected); return 1; } static CategoriesEditorReplace CategoriesEditorReplace_create (Any data, Any str, long *posList, long posCount) { try { autoCategoriesEditorReplace me = Thing_new (CategoriesEditorReplace); CategoriesEditorCommand_init (me.peek(), L"Replace", data, CategoriesEditorReplace_execute, CategoriesEditorReplace_undo, posCount + 1, posCount); for (long i = 1; i <= posCount; i++) { my selection[i] = posList[i]; } Collection_addItem (my categories, (SimpleString) str); return me.transfer(); } catch (MelderError) { Melder_throw ("CategoriesEditorReplace not created."); } } /*********************** MoveUp Command ***********************/ Thing_define (CategoriesEditorMoveUp, CategoriesEditorCommand) { }; Thing_implement (CategoriesEditorMoveUp, CategoriesEditorCommand, 0); static int CategoriesEditorMoveUp_execute (I) { iam (CategoriesEditorMoveUp); CategoriesEditor editor = (CategoriesEditor) my data; Ordered_moveItems (editor->data, my selection, my nSelected, my newPos); autoNUMvector selection (1, my nSelected); for (long i = 1; i <= my nSelected; i++) { selection[i] = my newPos + i - 1; } update (editor, my newPos, my selection[my nSelected], selection.peek(), my nSelected); return 1; } static int CategoriesEditorMoveUp_undo (I) { iam (CategoriesEditorMoveUp); CategoriesEditor editor = (CategoriesEditor) my data; for (long i = 1; i <= my nSelected; i++) { Ordered_moveItem (editor->data, my newPos, my selection[my nSelected]); } update (editor, my newPos, my selection[my nSelected], my selection, my nSelected); return 1; } static CategoriesEditorMoveUp CategoriesEditorMoveUp_create (Any data, long *posList, long posCount, long newPos) { try { autoCategoriesEditorMoveUp me = Thing_new (CategoriesEditorMoveUp); CategoriesEditorCommand_init (me.peek(), L"Move up", data, CategoriesEditorMoveUp_execute, CategoriesEditorMoveUp_undo, 0, posCount); for (long i = 1; i <= posCount; i++) { my selection[i] = posList[i]; } my newPos = newPos; return me.transfer(); } catch (MelderError) { Melder_throw ("CategoriesEditorMoveUp not created."); } } /*********************** MoveDown Command ***********************/ Thing_define (CategoriesEditorMoveDown, CategoriesEditorCommand) { }; Thing_implement (CategoriesEditorMoveDown, CategoriesEditorCommand, 0); static int CategoriesEditorMoveDown_execute (I) { iam (CategoriesEditorMoveDown); CategoriesEditor editor = (CategoriesEditor) my data; Ordered_moveItems ( (Ordered) editor -> data, my selection, my nSelected, my newPos); autoNUMvector selection (1, my nSelected); for (long i = 1; i <= my nSelected; i++) { selection[i] = my newPos - my nSelected + i; } update (editor, my selection[1], my newPos, selection.peek(), my nSelected); return 1; } static int CategoriesEditorMoveDown_undo (I) { iam (CategoriesEditorMoveDown); CategoriesEditor editor = (CategoriesEditor) my data; for (long i = 1; i <= my nSelected; i++) { Ordered_moveItem (editor -> data, my newPos, my selection[1]); // TODO 1 or i ?? } long from = my selection[1]; update (editor, (from > 1 ? from-- : from), my newPos, my selection, my nSelected); return 1; } static CategoriesEditorMoveDown CategoriesEditorMoveDown_create (Any data, long *posList, long posCount, long newPos) { try { autoCategoriesEditorMoveDown me = Thing_new (CategoriesEditorMoveDown); CategoriesEditorCommand_init (me.peek(), L"Move down", data, CategoriesEditorMoveDown_execute, CategoriesEditorMoveDown_undo, 0, posCount); for (long i = 1; i <= posCount; i++) { my selection[i] = posList[i]; } my newPos = newPos; return me.transfer(); } catch (MelderError) { Melder_throw ("CategoriesEditorMoveDown not created."); } } /********************* Commands (End) *************************************/ static void notifyOutOfView (I) { iam (CategoriesEditor); autoMelderString tmp; long posCount; MelderString_append (&tmp, L""); autoNUMvector posList (GuiList_getSelectedPositions (my list, & posCount), 1); if (posList.peek() != 0) { long outOfView = 0, top = GuiList_getTopPosition (my list), bottom = GuiList_getBottomPosition (my list); for (long i = posCount; i > 0; i--) { if (posList[i] < top || posList[i] > bottom) { outOfView++; } } if (outOfView > 0) { MelderString_append (&tmp, Melder_integer (outOfView), L" selection(s) out of view"); } } GuiLabel_setString (my outOfView, tmp.string); } static void update_dos (I) { iam (CategoriesEditor); autoMelderString tmp; Boolean undoSense = true, redoSense = true; // undo const wchar_t *name; if (! (name = CommandHistory_commandName (my history, 0))) { name = L"nothing"; undoSense = false; } MelderString_append (&tmp, L"Undo ", L"\"", name, L"\""); GuiButton_setString (my undo, tmp.string); GuiObject_setSensitive (my undo, undoSense); // redo if (! (name = CommandHistory_commandName (my history, 1))) { name = L"nothing"; redoSense = False; } MelderString_empty (&tmp); MelderString_append (&tmp, L"Redo ", L"\"", name, L"\""); GuiButton_setString (my redo, tmp.string); GuiObject_setSensitive (my redo, redoSense); } static void updateWidgets (I) { /*all buttons except undo & redo */ iam (CategoriesEditor); long size = ( (Categories) my data)->size; bool insert = false, insertAtEnd = true, replace = false, remove = false; bool moveUp = false, moveDown = false; long posCount; autoNUMvector posList (GuiList_getSelectedPositions (my list, & posCount), 1); if (posList.peek() != 0) { long firstPos = posList[1], lastPos = posList[posCount]; bool contiguous = lastPos - firstPos + 1 == posCount; moveUp = contiguous && firstPos > 1; moveDown = contiguous && lastPos < size; my position = firstPos; remove = true; replace = true; //insertAtEnd = False; if (posCount == 1) { insert = true; //if (posList[1] == size) insertAtEnd = True; if (size == 1 && ! wcscmp (CategoriesEditor_EMPTYLABEL, OrderedOfString_itemAtIndex_c (my data, 1))) { remove = false; } } } GuiObject_setSensitive (my insert, insert); GuiObject_setSensitive (my insertAtEnd, insertAtEnd); GuiObject_setSensitive (my replace, replace); GuiObject_setSensitive (my remove, remove); GuiObject_setSensitive (my moveUp, moveUp); GuiObject_setSensitive (my moveDown, moveDown); if (my history) { update_dos (me); } notifyOutOfView (me); } static void update (I, long from, long to, const long *select, long nSelect) { iam (CategoriesEditor); long size = ((Categories) my data) -> size; if (size == 0) { autoSimpleString str = SimpleString_create (CategoriesEditor_EMPTYLABEL); Collection_addItem ( (Categories) my data, str.transfer()); update (me, 0, 0, 0, 0); return; } if (from == 0 && from == to) { from = 1; to = size; } if (from < 1 || from > size) { from = size; } if (to < 1 || to > size) { to = size; } if (from > to) { long ti = from; from = to; to = ti; } // Begin optimization: add the items from a table instead of separately. try { autostringvector table (from, to); autoMelderString itemText; long itemCount = GuiList_getNumberOfItems (my list); for (long i = from; i <= to; i++) { wchar_t wcindex[20]; MelderString_empty (&itemText); swprintf (wcindex, 19, L"%5ld ", i); MelderString_append (&itemText, wcindex, OrderedOfString_itemAtIndex_c (my data, i)); table[i] = Melder_wcsdup_f (itemText.string); } if (itemCount > size) { /* some items have been removed from Categories? */ for (long j = itemCount; j > size; j --) { GuiList_deleteItem (my list, j); } itemCount = size; } if (to > itemCount) { for (long j = 1; j <= to - itemCount; j ++) { GuiList_insertItem (my list, table [itemCount + j], 0); } } if (from <= itemCount) { long n = (to < itemCount ? to : itemCount); for (long j = from; j <= n; j++) { GuiList_replaceItem (my list, table[j], j); } } } catch (MelderError) { throw; } // End of optimization // HIGHLIGHT GuiList_deselectAllItems (my list); if (size == 1) { /* the only item is always selected */ const wchar_t *catg = OrderedOfString_itemAtIndex_c (my data, 1); GuiList_selectItem (my list, 1); updateWidgets (me); // instead of "notify". BUG? GuiText_setString (my text, catg); } else if (nSelect > 0) { // Select but postpone highlighting for (long i = 1; i <= nSelect; i++) { GuiList_selectItem (my list, select[i] > size ? size : select[i]); } } // VIEWPORT { long top = GuiList_getTopPosition (my list), bottom = GuiList_getBottomPosition (my list); long visible = bottom - top + 1; if (nSelect == 0) { top = my position - visible / 2; } else if (select[nSelect] < top) { // selection above visible area top = select[1]; } else if (select[1] > bottom) { // selection below visible area top = select[nSelect] - visible + 1; } else { long deltaTopPos = -1, nUpdate = to - from + 1; if ( (from == select[1] && to == select[nSelect]) || // Replace (nUpdate > 2 && nSelect == 1) /* Inserts */) { deltaTopPos = 0; } else if (nUpdate == nSelect + 1 && select[1] == from + 1) { // down deltaTopPos = 1; } top += deltaTopPos; } if (top + visible > size) { top = size - visible + 1; } if (top < 1) { top = 1; } GuiList_setTopPosition (my list, top); } } static void gui_button_cb_remove (I, GuiButtonEvent event) { (void) event; iam (CategoriesEditor); long posCount; autoNUMvector posList (GuiList_getSelectedPositions (my list, & posCount), 1); if (posList.peek() != 0) { autoCategoriesEditorRemove command = CategoriesEditorRemove_create (me, posList.peek(), posCount); if (! Command_do (command.peek())) { return; } if (my history) { CommandHistory_insertItem (my history, command.transfer()); } updateWidgets (me); } } static void insert (I, int position) { iam (CategoriesEditor); autostring text = GuiText_getString (my text); if (wcslen (text.peek()) != 0) { autoSimpleString str = SimpleString_create (text.peek()); autoCategoriesEditorInsert command = CategoriesEditorInsert_create (me, str.transfer(), position); Command_do (command.peek()); if (my history) { CommandHistory_insertItem (my history, command.transfer()); } updateWidgets (me); } } static void gui_button_cb_insert (I, GuiButtonEvent event) { (void) event; iam (CategoriesEditor); insert (me, my position); } static void gui_button_cb_insertAtEnd (I, GuiButtonEvent event) { (void) event; iam (CategoriesEditor); Categories categories = (Categories) my data; insert (me, categories -> size + 1); my position = categories -> size; } static void gui_button_cb_replace (I, GuiButtonEvent event) { (void) event; iam (CategoriesEditor); long posCount; autoNUMvector posList (GuiList_getSelectedPositions (my list, & posCount), 1); if (posCount > 0) { autostring text = GuiText_getString (my text); if (wcslen (text.peek()) != 0) { autoSimpleString str = SimpleString_create (text.peek()); autoCategoriesEditorReplace command = CategoriesEditorReplace_create (me, str.transfer(), posList.peek(), posCount); Command_do (command.peek()); if (my history) { CommandHistory_insertItem (my history, command.transfer()); } updateWidgets (me); } } } /* Precondition: contiguous selection */ static void gui_button_cb_moveUp (I, GuiButtonEvent event) { (void) event; iam (CategoriesEditor); long posCount; autoNUMvector posList (GuiList_getSelectedPositions (my list, & posCount), 1); if (posCount > 0) { autoCategoriesEditorMoveUp command = CategoriesEditorMoveUp_create (me, posList.peek(), posCount, posList[1] - 1); Command_do (command.peek()); therror if (my history) { CommandHistory_insertItem (my history, command.transfer()); } updateWidgets (me); } } /* Precondition: contiguous selection */ static void gui_button_cb_moveDown (I, GuiButtonEvent event) { (void) event; iam (CategoriesEditor); long posCount; autoNUMvector posList (GuiList_getSelectedPositions (my list, & posCount), 1); if (posCount > 0) { autoCategoriesEditorMoveDown command = CategoriesEditorMoveDown_create (me, posList.peek(), posCount, posList[posCount] + 1); Command_do (command.peek()); therror if (my history) { CommandHistory_insertItem (my history, command.transfer()); } updateWidgets (me); } } static void gui_cb_scroll (GUI_ARGS) { GUI_IAM (CategoriesEditor); notifyOutOfView (me); } static void gui_list_cb_double_click (void *void_me, GuiListEvent event) { (void) event; iam (CategoriesEditor); const wchar_t *catg = OrderedOfString_itemAtIndex_c (my data, my position); GuiText_setString (my text, catg); } static void gui_list_cb_extended (void *void_me, GuiListEvent event) { (void) event; iam (CategoriesEditor); updateWidgets (me); } static void gui_button_cb_undo (I, GuiButtonEvent event) { (void) event; iam (CategoriesEditor); if (CommandHistory_offleft (my history)) { return; } Command_undo (CommandHistory_getItem (my history)); CommandHistory_back (my history); updateWidgets (me); } static void gui_button_cb_redo (I, GuiButtonEvent event) { (void) event; iam (CategoriesEditor); CommandHistory_forth (my history); if (CommandHistory_offright (my history)) { return; } Command_do (CommandHistory_getItem (my history)); updateWidgets (me); } void structCategoriesEditor :: v_destroy () { forget (history); /* !! Editor */ CategoriesEditor_Parent :: v_destroy (); } void structCategoriesEditor :: v_createHelpMenuItems (EditorMenu menu) { CategoriesEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"CategoriesEditor help", '?', menu_cb_help); } // origin is at top left. void structCategoriesEditor :: v_createChildren () { double menuBarOffset = 40; double button_width = 90, button_height = menuBarOffset, list_width = 260, list_height = 200, list_bottom; double delta_x = 15, delta_y = menuBarOffset / 2, text_button_height = button_height / 2; double left, right, top, bottom, buttons_left, buttons_top; left = 5; right = left + button_width; top = 3 + menuBarOffset; bottom = top + text_button_height; GuiLabel_createShown (d_windowForm, left, right, top, bottom, L"Positions:", 0); left = right + delta_x ; right = left + button_width; GuiLabel_createShown (d_windowForm, left, right, top, bottom, L"Values:", 0); left = 0; right = left + list_width; buttons_top = (top = bottom + delta_y); list_bottom = bottom = top + list_height; list = GuiList_create (d_windowForm, left, right, top, bottom, true, 0); GuiList_setSelectionChangedCallback (list, gui_list_cb_extended, this); GuiList_setDoubleClickCallback (list, gui_list_cb_double_click, this); GuiObject_show (list); /* The valueChangedCallback does not get any notification in case of: drag, decrement, increment, pageIncrement & pageDecrement */ #ifndef _WIN32 #if motif GuiObject vertScrollBar; XtVaGetValues (GuiObject_parent (list), XmNverticalScrollBar, & vertScrollBar, 0); XtAddCallback (vertScrollBar, XmNvalueChangedCallback, gui_cb_scroll, (XtPointer) this); XtAddCallback (vertScrollBar, XmNdragCallback, gui_cb_scroll, (XtPointer) this); XtAddCallback (vertScrollBar, XmNdecrementCallback, gui_cb_scroll, (XtPointer) this); XtAddCallback (vertScrollBar, XmNincrementCallback, gui_cb_scroll, (XtPointer) this); XtAddCallback (vertScrollBar, XmNpageIncrementCallback, gui_cb_scroll, (XtPointer) this); XtAddCallback (vertScrollBar, XmNpageDecrementCallback, gui_cb_scroll, (XtPointer) this); #endif #endif buttons_left = left = right + 2 * delta_x; right = left + button_width; bottom = top + button_height; GuiLabel_createShown (d_windowForm, left, right, top, bottom, L"Value:", 0); left = right + delta_x; right = left + button_width; text = GuiText_createShown (d_windowForm, left, right, top, bottom, 0); GuiText_setString (text, CategoriesEditor_EMPTYLABEL); left = buttons_left; right = left + button_width; top = bottom + delta_y; bottom = top + button_height; insert = GuiButton_createShown (d_windowForm, left, right, top, bottom, L"Insert", gui_button_cb_insert, this, GuiButton_DEFAULT); left = right + delta_x; right = left + button_width; replace = GuiButton_createShown (d_windowForm, left, right, top, bottom, L"Replace", gui_button_cb_replace, this, 0); left = buttons_left; right = left + 1.5 * button_width; top = bottom + delta_y; bottom = top + button_height; insertAtEnd = GuiButton_createShown (d_windowForm, left, right, top, bottom, L"Insert at end", gui_button_cb_insertAtEnd, this, 0); top = bottom + delta_y; bottom = top + button_height; undo = GuiButton_createShown (d_windowForm, left, right, top, bottom, L"Undo", gui_button_cb_undo, this, 0); top = bottom + delta_y; bottom = top + button_height; redo = GuiButton_createShown (d_windowForm, left, right, top, bottom, L"Redo", gui_button_cb_redo, this, 0); top = bottom + delta_y; bottom = top + button_height; remove = GuiButton_createShown (d_windowForm, left, right, top, bottom, L"Remove", gui_button_cb_remove, this, 0); top = bottom + delta_y; bottom = top + button_height; moveUp = GuiButton_createShown (d_windowForm, left, right, top, bottom, L"Move selection up", gui_button_cb_moveUp, this, 0); top = bottom + delta_y; bottom = top + button_height; moveDown = GuiButton_createShown (d_windowForm, left, right, top, bottom, L"Move selection down", gui_button_cb_moveDown, this, 0); top = list_bottom + delta_y; bottom = top + button_height; left = 5; right = left + 200; outOfView = GuiLabel_createShown (d_windowForm, left, right, top, bottom, L"", 0); } void structCategoriesEditor :: v_dataChanged () { update (this, 0, 0, 0, 0); updateWidgets (this); } CategoriesEditor CategoriesEditor_create (GuiObject parent, const wchar *title, Categories data) { try { autoCategoriesEditor me = Thing_new (CategoriesEditor); Editor_init (me.peek(), parent, 20, 40, 600, 600, title, data); my history = CommandHistory_create (100); update (me.peek(), 0, 0, 0, 0); updateWidgets (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("Categories window not created."); } } /* End of file CategoriesEditor.c 950*/ sources_5316/dwtools/Activation.h0000644000176700017670000000276511627171126015706 0ustar paulpaul#ifndef _Activation_h_ #define _Activation_h_ /* Activation.h * * Copyright (C) 1993-2011 David Weenink * * This program is free oftware; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020315 GPL header. djmw 20110505 Latest modification. */ #include "Matrix.h" #ifdef __cplusplus extern "C" { #endif Thing_define (Activation, Matrix) { }; /* Attributes: xmin :1 xmax :#units nx :#units dx :1 x1 :1 ymin :1 ymax :#patterns ny :#patterns dy :1 y1 :1 z[iy][ix] :the activities */ void Activation_init (I, long ny, long nx); Activation Activation_create (long ny, long nx); Activation Matrix_to_Activation (I); Matrix Activation_to_Matrix (I); int _Activation_checkElements (Activation me); /* Return 1 if all elements are in interval [0,1] else 0. */ #ifdef __cplusplus } #endif #endif /* _Activation_h_ */ sources_5316/dwtools/DTW.h0000664000176700017670000001020711723710247014233 0ustar paulpaul#ifndef _DTW_h_ #define _DTW_h_ /* DTW.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110306 Latest modification. */ #include "Spectrogram.h" #include "Polygon_extensions.h" #include "Pitch.h" #include "DurationTier.h" #include "Sound.h" #include "DTW_def.h" oo_CLASS_CREATE (DTW, Matrix); #define DTW_SAKOECHIBA 1 #define DTW_SLOPES 2 #define DTW_UNREACHABLE -1 #define DTW_FORBIDDEN -2 #define DTW_START 3 #define DTW_XANDY 2 #define DTW_X 4 #define DTW_Y 6 void DTW_Path_Query_init (DTW_Path_Query me, long ny, long nx); /* Prototype on y-axis and test on x-axis */ DTW DTW_create (double tminp, double tmaxp, long ntp, double dtp, double t1p, double tminc, double tmaxc, long ntc, double dtc, double t1c); void DTW_setWeights (DTW me, double wx, double wy, double wd); DTW DTW_swapAxes (DTW me); void DTW_findPath_bandAndSlope (DTW me, double sakoeChibaBand, int localSlope, Matrix *cummulativeDists); void DTW_findPath (DTW me, int matchStart, int matchEnd, int slope); // deprecated /* Obsolete Function: Calculate the minimum path (through a distance matrix). Possible constraints: matchStart: path starts at position (1,1) (bottom-left) matchEnd: path ends at (I,J) (top-right) slope: 1 no constraints 2 1/3 < slope < 3 3 1/2 < slope < 2 4 2/3 < slope < 3/2 For algorithm and DP-equations see the article (& especially table I) in: Sakoe, H. & Chiba, S. (1978), Dynamic Programming Algorithm Optimization for Spoken Word recognition, IEEE Trans. on ASSP, vol 26, 43-49. */ void DTW_Path_recode (DTW me); double DTW_getPathY (DTW me, double tx); /* Get the time Y-time that corresponds to time t (along X). */ double DTW_getYTimeFromXTime (DTW me, double tx); double DTW_getXTimeFromYTime (DTW me, double ty); long DTW_getMaximumConsecutiveSteps (DTW me, int direction); void DTW_paintDistances (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, double minimum, double maximum, int garnish); void DTW_drawPath (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish); void DTW_drawWarpX (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, double tx, int garnish); void DTW_pathRemoveRedundantNodes (DTW me); void DTW_pathQueryRecode (DTW me); void DTW_drawDistancesAlongPath (DTW me, Graphics g, double xmin, double xmax, double dmin, double dmax, int garnish); void DTW_and_Sounds_draw (DTW me, Sound yy, Sound xx, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish); void DTW_and_Sounds_drawWarpX (DTW me, Sound yy, Sound xx, Graphics g, double xmin, double xmax, double ymin, double ymax, double tx, int garnish); Polygon DTW_to_Polygon (DTW me, double band, int slope); void DTW_and_Polygon_findPathInside (DTW me, Polygon thee, int localSlope, Matrix *cummulativeDists); Matrix DTW_to_Matrix_distances(DTW me); Matrix DTW_to_Matrix_cummulativeDistances (DTW me, double sakoeChibaBand, int slope); Matrix DTW_and_Polygon_to_Matrix_cummulativeDistances (DTW me, Polygon thee, int localSlope); DTW Matrices_to_DTW (I, thou, int matchStart, int matchEnd, int slope, int metric); DTW Spectrograms_to_DTW (Spectrogram me, Spectrogram thee, int matchStart, int matchEnd, int slope, int metric); DTW Pitches_to_DTW (Pitch me, Pitch thee, double vuv_costs, double time_weight, int matchStart, int matchEnd, int slope); DurationTier DTW_to_DurationTier (DTW me); void DTW_and_Matrix_replace (DTW me, Matrix thee); #endif /* _DTW_h_ */ sources_5316/dwtools/HMM_def.h0000644000176700017670000000420111665132077015033 0ustar paulpaul/* HMM_def.h * * Copyright (C) 2010-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20100929 Initial definition. djmw 20110329 oo_STRINGW -> oo_STRING */ #define ooSTRUCT HMM_State oo_DEFINE_CLASS (HMM_State, Data) oo_STRING(label) oo_END_CLASS(HMM_State) #undef ooSTRUCT #define ooSTRUCT HMM_Observation oo_DEFINE_CLASS (HMM_Observation, Data) oo_STRING(label) oo_OBJECT (GaussianMixture, 1, gm) oo_END_CLASS(HMM_Observation) #undef ooSTRUCT #define ooSTRUCT HMM oo_DEFINE_CLASS (HMM, Data) oo_INT (notHidden) // to model a Markov model instead of HMM oo_INT (leftToRight) oo_LONG (numberOfStates) oo_LONG (numberOfObservationSymbols) oo_LONG (numberOfMixtureComponents) oo_LONG (componentDimension) oo_INT (componentStorage) oo_DOUBLE_MATRIX_FROM (transitionProbs, 0, numberOfStates, 1, numberOfStates + 1) // row 0: initial probabilities oo_DOUBLE_MATRIX (emissionProbs, numberOfStates, numberOfObservationSymbols) oo_OBJECT (Ordered, 1, states) oo_OBJECT (Ordered, 1, observationSymbols) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS(HMM) #undef ooSTRUCT #define ooSTRUCT HMM_Viterbi oo_DEFINE_CLASS (HMM_Viterbi, Data) oo_LONG (numberOfTimes) oo_LONG (numberOfStates) oo_DOUBLE (prob) oo_DOUBLE_MATRIX (viterbi, numberOfStates, numberOfTimes) oo_LONG_MATRIX (bp, numberOfStates, numberOfTimes) oo_LONG_VECTOR (path, numberOfTimes) oo_END_CLASS(HMM_Viterbi) #undef ooSTRUCT /* End of file HMM_def.h */ sources_5316/dwtools/Procrustes.cpp0000644000176700017670000000556411627250612016307 0ustar paulpaul/* Procrustes.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020813 GPL header djmw 20040117 Corrected bug in classProcrustes_transform: scale (s) was not used. djmw 20050406 Renamed Procrustus Procrustes djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20110304 Thing_new */ #include "Procrustes.h" #include "oo_DESTROY.h" #include "Procrustes_def.h" #include "oo_COPY.h" #include "Procrustes_def.h" #include "oo_EQUAL.h" #include "Procrustes_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Procrustes_def.h" #include "oo_WRITE_TEXT.h" #include "Procrustes_def.h" #include "oo_WRITE_BINARY.h" #include "Procrustes_def.h" #include "oo_READ_TEXT.h" #include "Procrustes_def.h" #include "oo_READ_BINARY.h" #include "Procrustes_def.h" #include "oo_DESCRIPTION.h" #include "Procrustes_def.h" Thing_implement (Procrustes, AffineTransform, 0); void structProcrustes :: v_transform (double **in, long nrows, double **out) { for (long i = 1; i <= nrows; i++) { for (long j = 1; j <= n; j++) { double tmp = 0; for (long k = 1; k <= n; k++) { tmp += in[i][k] * r[k][j]; } out[i][j] = s * tmp + t[j]; } } } Any structProcrustes :: v_invert () { autoProcrustes thee = Data_copy (this); /* R is symmetric rotation matrix --> inverse is transpose! */ thy s = s == 0 ? 1 : 1 / s; for (long i = 1; i <= n; i++) { for (long j = i + 1; j <= n; j++) { thy r[i][j] = r[j][i]; thy r[j][i] = r[i][j]; } thy t[i] = 0; /* for (j = 1; j <= thy n; j++) { thy t[i] -= thy r[i][j] * t[j]; } */ for (long j = 1; j <= thy n; j++) { thy t[i] -= thy r[j][i] * t[j]; } thy t[i] *= thy s; } return thee.transfer(); } static void Procrustes_setDefaults (Procrustes me) { my s = 1; for (long i = 1; i <= my n; i++) { my t[i] = 0; my r[i][i] = 1; for (long j = i + 1; j <= my n; j++) { my r[i][j] = my r[j][i] = 0; } } } Procrustes Procrustes_create (long n) { try { autoProcrustes me = (Procrustes) Thing_new (Procrustes); AffineTransform_init (me.peek(), n); Procrustes_setDefaults (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("Procrustes not created."); } } /* End of file Procrustes.c */ sources_5316/dwtools/SSCP_def.h0000644000176700017670000000271011627252422015160 0ustar paulpaul/* SSCP_def.h * * Copyright (C) 1993-2010 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT SSCP oo_DEFINE_CLASS (SSCP, TableOfReal) oo_DOUBLE (numberOfObservations) oo_DOUBLE_VECTOR (centroid, numberOfColumns) /* The following definitions are only needed when we want to use many big diagonal or almost diagonal matrices like for example in a GaussianMixture, or for efficiently calculating many times a distance like a'S^(-1)a */ #if !oo_READING && !oo_WRITING oo_LONG (expansionNumberOfRows) oo_INT (dataChanged) oo_DOUBLE_MATRIX (expansion, expansionNumberOfRows, numberOfColumns) oo_DOUBLE (lnd) oo_DOUBLE_MATRIX (lowerCholesky, numberOfColumns, numberOfColumns) oo_OBJECT (PCA, 0, pca) #endif oo_END_CLASS (SSCP) #undef ooSTRUCT /* End of file SSCP_def.h */ sources_5316/dwtools/praat_David_init.cpp0000664000176700017670000103056011756770370017407 0ustar paulpaul/* praat_David_init.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030701 Added Strings_setString. djmw 20031020 Changed Matrix_solveEquation. djmw 20031023 Added Spectra_multiply, Spectrum_conjugate and modified interface for CCA_and_TableOfReal_scores. djmw 20031030 Added TableOfReal_appendColumns. djmw 20031107 Added TablesOfReal_to_GSVD. djmw 20040303 Latest modification djmw 20040305 Added hints for PCA. djmw 20040323 Added hint for Discriminant. djmw 20040324 Added PCA_and_TableOfReal_getFractionVariance. djmw 20040331 Modified Eigen_drawEigenvalues interface. djmw 20040406 Extensive checks for creation of Sounds. djmw 20040414 Forms texts. djmw 20040523 Discriminant_and_TableOfReal_to_ClassificationTable: give new object a name. djmw 20040623 Added ClassificationTable_to_Strings_maximumProbability. djmw 20040704 BarkFilter... in Thing_recognizeClassesByName. djmw 20041020 MelderFile -> structMelderFile. djmw 20041105 TableOfReal_createFromVanNieropData_25females. djmw 20041108 FormantFilter_drawSpectrum bug correted (wrong field name). djmw 20050308 Find path (slopes), Find path (band)... and others. djmw 20050404 TableOfReal_appendColumns -> TableOfReal_appendColumnsMany djmw 20050406 Procrustus -> Prorustes djmw 20050407 MelFilter_drawFilterFunctions error in field names crashed praat djmw 20050706 Eigen_getSumOfEigenvalues djmw 20051012 Robust LPC analysis test djmw 20051116 TableOfReal_drawScatterPlot horizontal and vertical axes indices must be positive numbers djmw SVD extract lef/right singular vectors djmw 20060111 TextGrid: Extend time moved from depth 1 to depth 2. djmw 20060308 Thing_recognizeClassesByName: StringsIndex, CCA djmw 20070206 Sound_changeGender: pitch range factor must be >= 0 djmw 20070304 Latest modification. djmw 20070903 Melder_new<1...> djmw 20071011 REQUIRE requires L"". djmw 20071202 Melder_warning djmw 20080521 Confusion_drawAsnumbers djmw 20090109 KlattGrid formulas for formant djmw 20090708 KlattTable <-> Table djmw 20090822 Thing_recognizeClassesByName: added classCepstrum, classIndex, classKlattTable djmw 20090914 Excitation to Excitations crashed because of NULL reference djmw 20090927 TableOfReal_drawRow(s)asHistogram djmw 20091023 Sound_draw_selectedIntervals djmw 20091230 Covariance_and_TableOfReal_mahalanobis djmw 20100212 Standardize on Window length djmw 20100511 Categories_getNumberOfCategories djmw 20111224 Latest modification. */ #include "praat.h" #include "NUM2.h" #include "NUMlapack.h" #include "NUMmachar.h" #include "Activation.h" #include "Categories.h" #include "CategoriesEditor.h" #include "ClassificationTable.h" #include "Collection_extensions.h" #include "Confusion.h" #include "Discriminant.h" #include "EditDistanceTable.h" #include "Editor.h" #include "EditDistanceTable.h" #include "Eigen_and_Matrix.h" #include "Eigen_and_Procrustes.h" #include "Eigen_and_SSCP.h" #include "Eigen_and_TableOfReal.h" #include "Excitations.h" #include "espeakdata_FileInMemory.h" #include "FileInMemory.h" #include "Formula.h" #include "FormantGridEditor.h" #include "FormantGrid_extensions.h" #include "Intensity_extensions.h" #include "IntensityTierEditor.h" #include "Matrix_Categories.h" #include "Matrix_extensions.h" #include "LongSound_extensions.h" #include "KlattGridEditors.h" #include "KlattTable.h" #include "Minimizers.h" #include "Pattern.h" #include "PCA.h" #include "PitchTierEditor.h" #include "Polygon_extensions.h" #include "Polynomial.h" #include "Sound_extensions.h" #include "Sounds_to_DTW.h" #include "Spectrum_extensions.h" #include "Spectrogram.h" #include "SpeechSynthesizer.h" #include "SpeechSynthesizer_and_TextGrid.h" #include "SSCP.h" #include "Strings_extensions.h" #include "SVD.h" #include "Table_extensions.h" #include "TableOfReal_and_Permutation.h" #include "TextGrid_extensions.h" #include "Categories_and_Strings.h" #include "CCA_and_Correlation.h" #include "Cepstrum_and_Spectrum.h" #include "CCs_to_DTW.h" #include "Discriminant_Pattern_Categories.h" #include "DTW_and_TextGrid.h" #include "MelFilter_and_MFCC.h" #include "Permutation_and_Index.h" #include "Pitch_extensions.h" #include "Sound_and_FilterBank.h" #include "Sound_to_Pitch2.h" #include "Sound_to_SPINET.h" #include "TableOfReal_and_SVD.h" #include "VowelEditor.h" #undef iam #define iam iam_LOOP static const wchar_t *QUERY_BUTTON = L"Query -"; static const wchar_t *DRAW_BUTTON = L"Draw -"; static const wchar_t *MODIFY_BUTTON = L"Modify -"; static const wchar_t *EXTRACT_BUTTON = L"Extract -"; void praat_TimeFunction_query_init (ClassInfo klas); void praat_TimeFrameSampled_query_init (ClassInfo klas); void praat_TableOfReal_init (ClassInfo klas); void praat_TableOfReal_init2 (ClassInfo klas); void praat_SSCP_as_TableOfReal_init (ClassInfo klas); void praat_CC_init (ClassInfo klas); void DTW_constraints_addCommonFields (void *dia); void DTW_constraints_getCommonFields (void *dia, int *begin, int *end, int *slope); void praat_Matrixft_query_init (ClassInfo klas); int praat_Fon_formula (UiForm dia, Interpreter interpreter); void praat_EditDistanceTable_as_TableOfReal_init (ClassInfo klas); #undef INCLUDE_DTW_SLOPES /********************** Activation *******************************************/ FORM (Activation_formula, L"Activation: Formula", 0) LABEL (L"label", L"for col := 1 to ncol do { self [row, col] := `formula' ; x := x + dx } y := y + dy }}") TEXTFIELD (L"formula", L"self") OK DO praat_Fon_formula (dia, interpreter); END DIRECT (Activation_to_Matrix) LOOP { iam (Activation); praat_new (Activation_to_Matrix (me), my name); } END /********************** BarkFilter *******************************************/ DIRECT (BarkFilter_help) Melder_help (L"BarkFilter"); END FORM (BarkFilter_drawSpectrum, L"BarkFilter: Draw spectrum (slice)", L"FilterBank: Draw spectrum (slice)...") POSITIVE (L"Time (s)", L"0.1") REAL (L"left Frequency range (Bark)", L"0.0") REAL (L"right Frequency range (Bark)", L"0.0") REAL (L"left Amplitude range (dB)", L"0.0") REAL (L"right Amplitude range (dB)", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (BarkFilter); FilterBank_drawTimeSlice (me, GRAPHICS, GET_REAL (L"Time"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), L"Barks", GET_INTEGER (L"Garnish")); } END FORM (BarkFilter_drawSekeyHansonFilterFunctions, L"BarkFilter: Draw filter functions", L"FilterBank: Draw filter functions...") INTEGER (L"left Filter range", L"0") INTEGER (L"right Filter range", L"0") RADIO (L"Frequency scale", 1) RADIOBUTTON (L"Hertz") RADIOBUTTON (L"Bark") RADIOBUTTON (L"mel") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") BOOLEAN (L"Amplitude scale in dB", 1) REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (BarkFilter); BarkFilter_drawSekeyHansonFilterFunctions (me, GRAPHICS, GET_INTEGER (L"Frequency scale"), GET_INTEGER (L"left Filter range"), GET_INTEGER (L"right Filter range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_INTEGER (L"Amplitude scale in dB"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), GET_INTEGER (L"Garnish")); } END /********************** Categories ****************************************/ FORM (Categories_append, L"Categories: Append 1 category", L"Categories: Append 1 category...") SENTENCE (L"Category", L"") OK DO LOOP { iam (Categories); OrderedOfString_append (me, GET_STRING (L"Category")); } END DIRECT (Categories_edit) if (theCurrentPraatApplication -> batch) { Melder_throw ("Cannot edit a Categories from batch."); } else { LOOP { iam (Categories); praat_installEditor (CategoriesEditor_create (theCurrentPraatApplication -> topShell, my name, me), IOBJECT); } } END DIRECT (Categories_getNumberOfCategories) LOOP { iam (Categories); Melder_information (Melder_integer (my size), L" categories"); } END DIRECT (Categories_getNumberOfDifferences) Categories c1 = 0, c2 = 0; LOOP { iam (Categories); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); long NumberOfDifferences = OrderedOfString_getNumberOfDifferences (c1, c2); if (NumberOfDifferences < 0) { Melder_information (L"-1 (undefined: number of elements differ!)"); } else { Melder_information (Melder_integer (NumberOfDifferences), L" differences"); } END DIRECT (Categories_getFractionDifferent) Categories c1 = 0, c2 = 0; LOOP { iam (Categories); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); Melder_information (Melder_double (OrderedOfString_getFractionDifferent (c1, c2))); END DIRECT (Categories_difference) Categories c1 = 0, c2 = 0; LOOP { iam (Categories); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); double fraction; long n; OrderedOfString_difference (c1, c2, &n, &fraction); Melder_information (Melder_integer (n), L" differences"); END DIRECT (Categories_selectUniqueItems) LOOP { iam (Categories); praat_new (Categories_selectUniqueItems (me, 1), my name, L"_uniq"); } END DIRECT (Categories_to_Confusion) Categories c1 = 0, c2 = 0; LOOP { iam (Categories); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); praat_new (Categories_to_Confusion (c1, c2), Thing_getName (c1), L"_", Thing_getName (c2)); END DIRECT (Categories_to_Strings) LOOP { iam (Categories); praat_new (Categories_to_Strings (me), my name); } END DIRECT (Categories_join) Categories c1 = 0, c2 = 0; LOOP { iam (Categories); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); praat_new (OrderedOfString_joinItems (c1, c2), 0); END DIRECT (Categories_permuteItems) LOOP { iam (Collection); praat_new (Collection_permuteItems (me), my name, L"_perm"); } END /***************** CC ****************************************/ FORM (CC_getValue, L"CC: Get value", L"CC: Get value...") REAL (L"Time (s)", L"0.1") NATURAL (L"Index", L"1") OK DO LOOP { iam (CC); // ?? generic Melder_informationReal (CC_getValue (me, GET_REAL (L"Time"), GET_INTEGER (L"Index")), 0); } END FORM (CC_paint, L"CC: Paint", L"CC: Paint...") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") INTEGER (L"From coefficient", L"0") INTEGER (L"To coefficient", L"0") REAL (L"Minimum", L"0.0") REAL (L"Maximum", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (CC); CC_paint (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_INTEGER (L"From coefficient"), GET_INTEGER (L"To coefficient"), GET_REAL (L"Minimum"), GET_REAL (L"Maximum"), GET_INTEGER (L"Garnish")); } END FORM (CC_drawC0, L"CC: Draw c0", L"CC: Draw c0...") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (CC); CC_drawC0 (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), GET_INTEGER (L"Garnish")); } END FORM (CCs_to_DTW, L"CC: To DTW", L"CC: To DTW...") LABEL (L"", L"Distance between cepstral coefficients") REAL (L"Cepstral weight", L"1.0") REAL (L"Log energy weight", L"0.0") REAL (L"Regression weight", L"0.0") REAL (L"Regression weight log energy", L"0.0") REAL (L"Regression coefficients window (s)", L"0.056") DTW_constraints_addCommonFields (dia); OK DO CC c1 = 0, c2 = 0; LOOP { iam (CC); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); int begin, end, slope; DTW_constraints_getCommonFields (dia, &begin, &end, &slope); autoDTW thee = CCs_to_DTW (c1, c2, GET_REAL (L"Cepstral weight"), GET_REAL (L"Log energy weight"), GET_REAL (L"Regression weight"), GET_REAL (L"Regression weight log energy"), GET_REAL (L"Regression coefficients window")); DTW_findPath (thee.peek(), begin, end, slope); praat_new (thee.transfer(), 0); END DIRECT (CC_to_Matrix) LOOP { iam (CC); praat_new (CC_to_Matrix (me), my name); } END /******************* class CCA ********************************/ FORM (CCA_drawEigenvector, L"CCA: Draw eigenvector", L"Eigen: Draw eigenvector...") OPTIONMENU (L"X or Y", 1) OPTION (L"y") OPTION (L"x") INTEGER (L"Eigenvector number", L"1") LABEL (L"", L"Multiply by eigenvalue?") BOOLEAN (L"Component loadings", 0) LABEL (L"", L"Select part of the eigenvector:") INTEGER (L"left Element range", L"0") INTEGER (L"right Element range", L"0") REAL (L"left Amplitude range", L"-1.0") REAL (L"right Amplitude range", L"1.0") POSITIVE (L"Mark size (mm)", L"1.0") SENTENCE (L"Mark string (+xo.)", L"+") BOOLEAN (L"Connect points", 1) BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (CCA); CCA_drawEigenvector (me, GRAPHICS, GET_INTEGER (L"X or Y"), GET_INTEGER (L"Eigenvector number"), GET_INTEGER (L"left Element range"), GET_INTEGER (L"right Element range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), GET_INTEGER (L"Component loadings"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Connect points"), GET_INTEGER (L"Garnish")); } END DIRECT (CCA_getNumberOfCorrelations) LOOP { iam (CCA); Melder_information (Melder_double (my numberOfCoefficients)); } END FORM (CCA_getCorrelationCoefficient, L"CCA: Get canonical correlation coefficient", L"CCA: Get canonical correlation coefficient") NATURAL (L"Coefficient number", L"1") OK DO LOOP { iam (CCA); Melder_information (Melder_double (CCA_getCorrelationCoefficient (me, GET_INTEGER (L"Coefficient number")))); } END FORM (CCA_getEigenvectorElement, L"CCA: Get eigenvector element", L"Eigen: Get eigenvector element...") OPTIONMENU (L"X or Y", 1) OPTION (L"y") OPTION (L"x") NATURAL (L"Eigenvector number", L"1") NATURAL (L"Element number", L"1") OK DO LOOP { iam (CCA); Melder_information (Melder_double (CCA_getEigenvectorElement (me, GET_INTEGER (L"X or Y"), GET_INTEGER (L"Eigenvector number"), GET_INTEGER (L"Element number")))); } END FORM (CCA_getZeroCorrelationProbability, L"CCA: Get zero correlation probability", L"CCA: Get zero correlation probability...") NATURAL (L"Coefficient number", L"1") OK DO LOOP { iam (CCA); double p, chisq; long ndf; CCA_getZeroCorrelationProbability (me, GET_INTEGER (L"Coefficient number"), &chisq, &ndf, &p); Melder_information (Melder_double (p), L" (=probability for chisq = ", Melder_double (chisq), L" and ndf = ", Melder_integer (ndf), L")"); } END DIRECT (CCA_and_Correlation_factorLoadings) CCA cca = FIRST (CCA); Correlation c = FIRST (Correlation); praat_new (CCA_and_Correlation_factorLoadings (cca, c), Thing_getName (cca), L"_loadings"); END FORM (CCA_and_Correlation_getVarianceFraction, L"CCA & Correlation: Get variance fraction", L"CCA & Correlation: Get variance fraction...") LABEL (L"", L"Get the fraction of variance from the data in set...") OPTIONMENU (L"X or Y", 1) OPTION (L"y") OPTION (L"x") LABEL (L"", L"extracted by...") NATURAL (L"left Canonical variate range", L"1") NATURAL (L"right Canonical variate range", L"1") OK DO CCA cca = FIRST (CCA); Correlation c = FIRST (Correlation); int x_or_y = GET_INTEGER (L"X or Y"); int cv_from = GET_INTEGER (L"left Canonical variate range"); int cv_to = GET_INTEGER (L"right Canonical variate range"); Melder_information (Melder_double (CCA_and_Correlation_getVarianceFraction (cca, c, x_or_y, cv_from, cv_to)), L" (fraction variance from ", (x_or_y == 1 ? L"y" : L"x"), L", extracted by canonical variates ", Melder_integer (cv_from), L" to ", Melder_integer (cv_to), L")"); END FORM (CCA_and_Correlation_getRedundancy_sl, L"CCA & Correlation: Get Stewart-Love redundancy", L"CCA & Correlation: Get redundancy (sl)...") LABEL (L"", L"Get the redundancy of the data in set...") OPTIONMENU (L"X or Y", 1) OPTION (L"y") OPTION (L"x") LABEL (L"", L"extracted by...") NATURAL (L"left Canonical variate range", L"1") NATURAL (L"right Canonical variate range", L"1") LABEL (L"", L"...given the availability of the data in the other set.") OK DO CCA cca = FIRST (CCA); Correlation c = FIRST (Correlation); int x_or_y = GET_INTEGER (L"X or Y"); int cv_from = GET_INTEGER (L"left Canonical variate range"); int cv_to = GET_INTEGER (L"right Canonical variate range"); Melder_information (Melder_double (CCA_and_Correlation_getRedundancy_sl (cca, c, x_or_y, cv_from, cv_to)), L" (redundancy from ", (x_or_y == 1 ? L"y" : L"x"), L" extracted by canonical variates ", Melder_integer (cv_from), L" to ", Melder_integer (cv_to), L")"); END DIRECT (CCA_and_TableOfReal_factorLoadings) CCA cca = FIRST (CCA); TableOfReal tr = FIRST (TableOfReal); praat_new (CCA_and_TableOfReal_factorLoadings (cca, tr), Thing_getName (cca), L"_loadings"); END FORM (CCA_and_TableOfReal_scores, L"CCA & TableOfReal: To TableOfReal (scores)", L"CCA & TableOfReal: To TableOfReal (scores)...") INTEGER (L"Number of canonical correlations", L"0 (=all)") OK DO CCA cca = FIRST (CCA); TableOfReal tr = FIRST (TableOfReal); praat_new2 (CCA_and_TableOfReal_scores (cca, tr, GET_INTEGER (L"Number of canonical correlations")), Thing_getName (cca), L"_scores"); END FORM (CCA_and_TableOfReal_predict, L"CCA & TableOfReal: Predict", L"CCA & TableOfReal: Predict...") LABEL (L"", L"The data set from which to predict starts at...") INTEGER (L"Column number", L"1") OK DO CCA cca = FIRST (CCA); TableOfReal tr = FIRST (TableOfReal); praat_new (CCA_and_TableOfReal_predict (cca, tr, GET_INTEGER (L"Column number")), tr->name, L"_", cca->name); END /***************** ChebyshevSeries ****************************************/ DIRECT (ChebyshevSeries_help) Melder_help (L"ChebyshevSeries"); END FORM (ChebyshevSeries_create, L"Create ChebyshevSeries", L"Create ChebyshevSeries...") WORD (L"Name", L"cs") LABEL (L"", L"Domain") REAL (L"Xmin", L"-1") REAL (L"Xmax", L"1") LABEL (L"", L"ChebyshevSeries(x) = c[1] T[0](x) + c[2] T[1](x) + ... c[n+1] T[n](x)") LABEL (L"", L"T[k] is a Chebyshev polynomial of degree k") SENTENCE (L"Coefficients (c[k])", L"0 0 1.0") OK DO double xmin = GET_REAL (L"Xmin"), xmax = GET_REAL (L"Xmax"); REQUIRE (xmin < xmax, L"Xmin must be smaller than Xmax.") praat_new (ChebyshevSeries_createFromString (xmin, xmax, GET_STRING (L"Coefficients")), GET_STRING (L"Name")); END DIRECT (ChebyshevSeries_to_Polynomial) LOOP { iam (ChebyshevSeries); praat_new (ChebyshevSeries_to_Polynomial (me), my name); } END /***************** ClassificationTable ****************************************/ DIRECT (ClassificationTable_help) Melder_help (L"ClassificationTable"); END DIRECT (ClassificationTable_to_Confusion) LOOP { iam (ClassificationTable); praat_new (ClassificationTable_to_Confusion (me), 0); } END DIRECT (ClassificationTable_to_Correlation_columns) LOOP { iam (ClassificationTable); praat_new (ClassificationTable_to_Correlation_columns (me), my name, L"_col"); } END DIRECT (ClassificationTable_to_Strings_maximumProbability) LOOP { iam (ClassificationTable); praat_new (ClassificationTable_to_Strings_maximumProbability (me), my name); } END /********************** Confusion *******************************************/ DIRECT (Confusion_help) Melder_help (L"Confusion"); END FORM (Confusion_createSimple, L"Create simple Confusion", L"Create simple Confusion...") WORD (L"Name", L"simple") SENTENCE (L"Labels", L"u i a") OK DO praat_new (Confusion_createSimple (GET_STRING (L"Labels")), GET_STRING (L"Name")); END FORM (Confusion_increase, L"Confusion: Increase", L"Confusion: Increase...") WORD (L"Stimulus", L"u") WORD (L"Response", L"i") OK DO LOOP { iam (Confusion); Confusion_increase (me, GET_STRING (L"Stimulus"), GET_STRING (L"Response")); praat_dataChanged (me); } END FORM (Confusion_getValue, L"Confusion: Get value", 0) WORD (L"Stimulus", L"u") WORD (L"Response", L"i") OK DO wchar_t *stim = GET_STRING (L"Stimulus"); wchar_t *resp = GET_STRING (L"Response"); LOOP { iam (Confusion); Melder_information (Melder_double (Confusion_getValue (me, stim, resp)), L" ( [\"", stim, L"\", \"", resp, L"\"] )"); } END FORM (Confusion_getResponseSum, L"Confusion: Get response sum", L"Confusion: Get response sum...") WORD (L"Response", L"u") OK DO LOOP { iam (TableOfReal); Melder_information (Melder_double (TableOfReal_getColumnSumByLabel (me, GET_STRING (L"Response")))); } END FORM (Confusion_getStimulusSum, L"Confusion: Get stimulus sum", L"Confusion: Get stimulus sum...") WORD (L"Stimulus", L"u") OK DO LOOP { iam (TableOfReal); Melder_information (Melder_double (TableOfReal_getRowSumByLabel (me, GET_STRING (L"Stimulus")))); } END DIRECT (Confusion_to_TableOfReal_marginals) LOOP { iam (TableOfReal); praat_new (Confusion_to_TableOfReal_marginals (me), my name); } END DIRECT (Confusion_difference) Confusion c1 = 0, c2 = 0; LOOP { iam (Confusion); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); praat_new (Confusion_difference (c1, c2), L"diffs"); END FORM (Confusion_condense, L"Confusion: Condense", L"Confusion: Condense...") SENTENCE (L"Search", L"^(u|i)$") SENTENCE (L"Replace", L"high") INTEGER (L"Replace limit", L"0 (=unlimited)") RADIO (L"Search and replace are", 2) RADIOBUTTON (L"Literals") RADIOBUTTON (L"Regular Expressions") OK DO LOOP { iam (Confusion); praat_new (Confusion_condense (me, GET_STRING (L"Search"), GET_STRING (L"Replace"), GET_INTEGER (L"Replace limit"), GET_INTEGER (L"Search and replace are") - 1), my name, L"_cnd"); } END FORM (Confusion_group, L"Confusion: Group stimuli & responses", L"Confusion: Group...") SENTENCE (L"Stimuli & Responses", L"u i") SENTENCE (L"New label", L"high") INTEGER (L"New label position", L"0 (=at start)") OK DO const wchar_t *newlabel = GET_STRING (L"New label"); LOOP { iam (Confusion); praat_new (Confusion_group (me, GET_STRING (L"Stimuli & Responses"), newlabel, GET_INTEGER (L"New label position")), Thing_getName (me), L"_sr", newlabel); } END FORM (Confusion_groupStimuli, L"Confusion: Group stimuli", L"Confusion: Group stimuli...") SENTENCE (L"Stimuli", L"u i") SENTENCE (L"New label", L"high") INTEGER (L"New label position", L"0") OK DO const wchar_t *newlabel = GET_STRING (L"New label"); LOOP { iam (Confusion); praat_new (Confusion_groupStimuli (me, GET_STRING (L"Stimuli"), newlabel, GET_INTEGER (L"New label position")), Thing_getName (me), L"_s", newlabel); } END FORM (Confusion_groupResponses, L"Confusion: Group responses", L"Confusion: Group responses...") SENTENCE (L"Responses", L"a i") SENTENCE (L"New label", L"front") INTEGER (L"New label position", L"0") OK DO const wchar_t *newlabel = GET_STRING (L"New label"); LOOP { iam (Confusion); praat_new (Confusion_groupResponses (me, GET_STRING (L"Responses"), newlabel, GET_INTEGER (L"New label position")), Thing_getName (me), L"_s", newlabel); } END FORM (Confusion_drawAsNumbers, L"", L"") BOOLEAN (L"Draw marginals", 1) RADIO (L"Format", 3) RADIOBUTTON (L"decimal") RADIOBUTTON (L"exponential") RADIOBUTTON (L"free") RADIOBUTTON (L"rational") NATURAL (L"Precision", L"5") OK DO autoPraatPicture picture; LOOP { iam (Confusion); Confusion_drawAsNumbers (me, GRAPHICS, GET_INTEGER (L"Draw marginals"), GET_INTEGER (L"Format"), GET_INTEGER (L"Precision")); } END DIRECT (Confusion_getFractionCorrect) LOOP { iam (Confusion); double f; long n; Confusion_getFractionCorrect (me, &f, &n); Melder_information (Melder_double (f), L" (fraction correct)"); } END /******************* Confusion & Matrix *************************************/ FORM (Confusion_Matrix_draw, L"Confusion & Matrix: Draw confusions with arrows", 0) INTEGER (L"Category position", L"0 (=all)") REAL (L"Lower level (%)", L"0") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO long categoryPosition = GET_INTEGER (L"Category position"); REQUIRE (categoryPosition >= 0, L"Category position must be >= 0") Confusion conf = FIRST (Confusion); Matrix mat = FIRST (Matrix); Confusion_Matrix_draw (conf, mat, GRAPHICS, categoryPosition, GET_REAL (L"Lower level"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); END /**********************Correlation *******************************************/ DIRECT (Correlation_help) Melder_help (L"Correlation"); END FORM (Correlation_confidenceIntervals, L"Correlation: Confidence intervals...", L"Correlation: Confidence intervals...") POSITIVE (L"Confidence level (0-1)", L"0.95") INTEGER (L"Number of tests (Bonferroni correction)", L"0") RADIO (L"Approximation", 1) RADIOBUTTON (L"Ruben") RADIOBUTTON (L"Fisher") OK DO double cl = GET_REAL (L"Confidence level"); double numberOfTests = GET_INTEGER (L"Number of tests"); LOOP { iam (Correlation); praat_new (Correlation_confidenceIntervals (me, cl, numberOfTests, GET_INTEGER (L"Approximation")), L"conf_intervals"); } END FORM (Correlation_testDiagonality_bartlett, L"Correlation: Get diagonality (bartlett)", L"SSCP: Get diagonality (bartlett)...") NATURAL (L"Number of contraints", L"1") OK DO double chisq, p; long nc = GET_INTEGER (L"Number of contraints"); LOOP { iam (Correlation); Correlation_testDiagonality_bartlett (me, nc, &chisq, &p); Melder_information (Melder_double (p), L" (=probability, based on chisq = ", Melder_double (chisq), L"and ndf = ", Melder_integer (my numberOfRows * (my numberOfRows - 1) / 2)); } END DIRECT (Correlation_to_PCA) LOOP { iam (Correlation); praat_new (SSCP_to_PCA (me), my name); } END /**********************Covariance *******************************************/ DIRECT (Covariance_help) Melder_help (L"Covariance"); END FORM (Covariance_createSimple, L"Create simple Covariance", L"Create simple Covariance...") WORD (L"Name", L"c") SENTENCE (L"Covariances", L"1.0 0.0 1.0") SENTENCE (L"Centroid", L"0.0 0.0") POSITIVE (L"Number of observations", L"100.0") OK DO praat_new (Covariance_createSimple (GET_STRING (L"Covariances"), GET_STRING (L"Centroid"), GET_REAL (L"Number of observations")), GET_STRING (L"Name")); END FORM (Covariance_getProbabilityAtPosition, L"Covariance: Get probability at position", 0) SENTENCE (L"Position", L"10.0 20.0") OK DO wchar_t *position = GET_STRING (L"Position"); LOOP { iam (Covariance); double p = Covariance_getProbabilityAtPosition_string (me, position); Melder_information (Melder_double (p), L" (= probability at position ", position, L")"); } END FORM (Covariance_getSignificanceOfOneMean, L"Covariance: Get significance of one mean", L"Covariance: Get significance of one mean...") LABEL (L"", L"Get probability that the mean with") NATURAL (L"Index", L"1") LABEL (L"", L"differs from") REAL (L"Value", L"0.0") LABEL (L"", L"(Null hypothesis: the observed difference is due to chance.)") OK DO LOOP { iam (Covariance); double t, p; double ndf; Covariance_getSignificanceOfOneMean (me, GET_INTEGER (L"Index"), GET_REAL (L"Value"), &p, &t , &ndf); Melder_information (Melder_double (p), L" (=probability, based on t = ", Melder_double (t), L" and ndf = ", Melder_integer (ndf)); } END FORM (Covariance_getSignificanceOfMeansDifference, L"Covariance: Get significance of means difference", L"Covariance: Get significance of means difference...") LABEL (L"", L"Get probability that the difference between means") NATURAL (L"Index1", L"1") NATURAL (L"Index2", L"2") LABEL (L"", L"differs from") REAL (L"Value", L"0.0") LABEL (L"", L"when the means are") BOOLEAN (L"Paired", 1) LABEL (L"", L"and have") BOOLEAN (L"Equal variances", 1) OK DO LOOP { iam (Covariance); double t, p; double ndf; Covariance_getSignificanceOfMeansDifference (me, GET_INTEGER (L"Index1"), GET_INTEGER (L"Index2"), GET_REAL (L"Value"), GET_INTEGER (L"Paired"), GET_INTEGER (L"Equal variances"), &p, &t , &ndf); Melder_information (Melder_double (p), L" (=probability, based on t = ", Melder_double (t), L"and ndf = ", Melder_integer (ndf), L")"); } END FORM (Covariance_getSignificanceOfOneVariance, L"Covariance: Get significance of one variance", L"Covariance: Get significance of one variance...") LABEL (L"", L"Get probability that the variance with") NATURAL (L"Index", L"1") LABEL (L"", L"differs from") REAL (L"Value", L"0.0") LABEL (L"", L"(Null hypothesis: the observed difference is due to chance.)") OK DO LOOP { iam (Covariance); double chisq, p; long ndf; Covariance_getSignificanceOfOneVariance (me, GET_INTEGER (L"Index"), GET_REAL (L"Value"), &p, &chisq , &ndf); Melder_information (Melder_double (p), L" (=probability, based on chisq = ", Melder_double (chisq), L"and ndf = ", Melder_integer (ndf)); } END FORM (Covariance_getSignificanceOfVariancesRatio, L"Covariance: Get significance of variances ratio", L"Covariance: Get significance of variances ratio...") NATURAL (L"Index1", L"1") NATURAL (L"Index2", L"2") REAL (L"Hypothesized ratio", L"1.0") OK DO LOOP { iam (Covariance); double f, p; long ndf; Covariance_getSignificanceOfVariancesRatio (me, GET_INTEGER (L"Index1"), GET_INTEGER (L"Index2"), GET_REAL (L"Hypothesized ratio"), &p, &f , &ndf); Melder_information (Melder_double (p), L" (=probability, based on F = ", Melder_double (f), L"and ndf1 = ", Melder_integer (ndf), L" and ndf2 = ", Melder_integer (ndf)); } END FORM (Covariance_getFractionVariance, L"Covariance: Get fraction variance", L"Covariance: Get fraction variance...") NATURAL (L"From dimension", L"1") NATURAL (L"To dimension", L"1") OK DO LOOP { iam (Covariance); Melder_information (Melder_double (SSCP_getFractionVariation (me, GET_INTEGER (L"From dimension"), GET_INTEGER (L"To dimension")))); } END FORM (Covariances_reportMultivariateMeanDifference, L"Covariances: Report multivariate mean difference", L"Covariances: Report multivariate mean difference...") BOOLEAN (L"Covariances are equal", 1) OK DO Covariance c1 = 0, c2 = 0; LOOP { iam (Covariance); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); double prob, fisher, df1, df2, difference; int equalCovariances = GET_INTEGER (L"Covariances are equal"); MelderInfo_open (); difference = Covariances_getMultivariateCentroidDifference (c1, c2, equalCovariances, &prob, &fisher, &df1, &df2); MelderInfo_writeLine3 (L"Under the assumption that the two covariances are", (equalCovariances ? L" " : L" not "), L"equal:"); MelderInfo_writeLine2 (L"Difference between multivariate means = ", Melder_double (difference)); MelderInfo_writeLine2 (L"Fisher's F = ", Melder_double (fisher)); MelderInfo_writeLine2 (L"Significance from zero = ", Melder_double (prob)); MelderInfo_writeLine4 (L"Degrees of freedom = ", Melder_double (df1), L", ", Melder_double (df2)); MelderInfo_writeLine4 (L"(Number of observations = ", Melder_integer (c1->numberOfObservations), L", ", Melder_integer (c2->numberOfObservations)); MelderInfo_writeLine3 (L"Dimension of covariance matrices = ", Melder_integer (c1-> numberOfRows), L")"); MelderInfo_close (); END FORM (Covariance_to_TableOfReal_randomSampling, L"Covariance: To TableOfReal (random sampling)", L"Covariance: To TableOfReal (random sampling)...") INTEGER (L"Number of data points", L"0") OK DO LOOP { iam (Covariance); praat_new (Covariance_to_TableOfReal_randomSampling (me, GET_INTEGER (L"Number of data points")), my name); } END DIRECT (Covariances_reportEquality) autoCollection set = praat_getSelectedObjects (); MelderInfo_open (); { double chisq, p, df; Covariances_equality (set.peek(), 1, &p, &chisq, &df); MelderInfo_writeLine1 (L"Difference between covariance matrices:"); MelderInfo_writeLine2 (L"Significance of difference (bartlett) = ", Melder_double (p)); MelderInfo_writeLine2 (L"Chi-squared = ", Melder_double (chisq)); MelderInfo_writeLine2 (L"Degrees of freedom = ", Melder_double (df)); Covariances_equality (set.peek(), 2, &p, &chisq, &df); MelderInfo_writeLine2 (L"Significance of difference (wald) = ", Melder_double (p)); MelderInfo_writeLine2 (L"Chi-squared = ", Melder_double (chisq)); MelderInfo_writeLine2 (L"Degrees of freedom = ", Melder_double (df)); } MelderInfo_close (); END DIRECT (Covariance_to_Correlation) LOOP { iam (Covariance); praat_new (SSCP_to_Correlation (me), my name); } END DIRECT (Covariance_to_PCA) LOOP { iam (Covariance); praat_new (SSCP_to_PCA (me), my name); } END FORM (Covariance_and_TableOfReal_mahalanobis, L"Covariance & TableOfReal: To TableOfReal (mahalanobis)", L"Covariance & TableOfReal: To TableOfReal (mahalanobis)...") BOOLEAN (L"Centroid from table", 0) OK DO Covariance cov = FIRST (Covariance); TableOfReal tr = FIRST (TableOfReal); praat_new (Covariance_and_TableOfReal_mahalanobis (cov, tr, GET_INTEGER (L"Centroid from table")), L"mahalanobis"); END /********************** Discriminant **********************************/ DIRECT (Discriminant_help) Melder_help (L"Discriminant"); END DIRECT (Discriminant_setGroupLabels) Discriminant me = FIRST (Discriminant); Strings ss = FIRST (Strings); Discriminant_setGroupLabels (me, ss); praat_dataChanged (me); END FORM (Discriminant_and_Pattern_to_Categories, L"Discriminant & Pattern: To Categories", L"Discriminant & Pattern: To Categories...") BOOLEAN (L"Pool covariance matrices", 1) BOOLEAN (L"Use apriori probabilities", 1) OK DO Discriminant me = FIRST (Discriminant); Pattern pat = FIRST (Pattern); praat_new (Discriminant_and_Pattern_to_Categories (me, pat, GET_INTEGER (L"Pool covariance matrices"), GET_INTEGER (L"Use apriori probabilities")), my name, L"_", pat->name); END FORM (Discriminant_and_TableOfReal_to_Configuration, L"Discriminant & TableOfReal: To Configuration", L"Discriminant & TableOfReal: To Configuration...") INTEGER (L"Number of dimensions", L"0") OK DO long dimension = GET_INTEGER (L"Number of dimensions"); REQUIRE (dimension >= 0, L"Number of dimensions must be greater equal zero.") Discriminant me = FIRST (Discriminant); TableOfReal tr = FIRST_GENERIC (TableOfReal); praat_new (Discriminant_and_TableOfReal_to_Configuration (me, tr, dimension), my name, L"_", tr->name); END DIRECT (hint_Discriminant_and_TableOfReal_to_ClassificationTable) Melder_information (L"You can use the Discriminant as a classifier by \nselecting a Discriminant and a TableOfReal object together."); END FORM (Discriminant_and_TableOfReal_to_ClassificationTable, L"Discriminant & TableOfReal: To ClassificationTable", L"Discriminant & TableOfReal: To ClassificationTable...") BOOLEAN (L"Pool covariance matrices", 1) BOOLEAN (L"Use apriori probabilities", 1) OK DO Discriminant me = FIRST (Discriminant); TableOfReal tr = FIRST_GENERIC (TableOfReal); praat_new (Discriminant_and_TableOfReal_to_ClassificationTable (me, tr, GET_INTEGER (L"Pool covariance matrices"), GET_INTEGER (L"Use apriori probabilities")), my name, L"_", tr->name); END FORM (Discriminant_and_TableOfReal_mahalanobis, L"Discriminant & TableOfReal: To TableOfReal (mahalanobis)", L"Discriminant & TableOfReal: To TableOfReal (mahalanobis)...") SENTENCE (L"Group label", L"") BOOLEAN (L"Pool covariance matrices", 0) OK DO Discriminant me = FIRST (Discriminant); TableOfReal tr = FIRST (TableOfReal); long group = Discriminant_groupLabelToIndex (me, GET_STRING (L"Group label")); REQUIRE (group > 0, L"Group label does not exist.") praat_new (Discriminant_and_TableOfReal_mahalanobis (me, tr, group, GET_INTEGER (L"Pool covariance matrices")), L"mahalanobis"); END FORM (Discriminant_getWilksLambda, L"Discriminant: Get Wilks' lambda", L"Discriminant: Get Wilks' lambda...") LABEL (L"", L"Product (i=from..numberOfEigenvalues, 1 / (1 + eigenvalue[i]))") INTEGER (L"From", L"1") OK DO long from = GET_INTEGER (L"From"); REQUIRE (from >= 1, L"Number must be greater than or equal to one.") LOOP { iam (Discriminant); Melder_information (Melder_double (Discriminant_getWilksLambda (me, from))); } END FORM (Discriminant_getCumulativeContributionOfComponents, L"Discriminant: Get cumulative contribution of components", L"Eigen: Get cumulative contribution of components...") NATURAL (L"From component", L"1") NATURAL (L"To component", L"1") OK DO LOOP { iam (Discriminant); Melder_information (Melder_double (Eigen_getCumulativeContributionOfComponents (me, GET_INTEGER (L"From component"), GET_INTEGER (L"To component")))); } END FORM (Discriminant_getPartialDiscriminationProbability, L"Discriminant: Get partial discrimination probability", L"Discriminant: Get partial discrimination probability...") INTEGER (L"Number of dimensions", L"1") OK DO long ndf, n = GET_INTEGER (L"Number of dimensions"); double chisq, p; REQUIRE (n >= 0, L"Number of dimensions must be greater than or equal to zero.") LOOP { iam (Discriminant); Discriminant_getPartialDiscriminationProbability (me, n, &p, &chisq, &ndf); Melder_information (Melder_double (p), L" (=probability, based on chisq = ", Melder_double (chisq), L"and ndf = ", Melder_integer (ndf)); } END DIRECT (Discriminant_getHomegeneityOfCovariances_box) LOOP { iam (Discriminant); double chisq, p; long ndf; SSCPs_getHomegeneityOfCovariances_box ( (SSCPs) my groups, &p, &chisq, &ndf); Melder_information (Melder_double (p), L" (=probability, based on chisq = ", Melder_double (chisq), L"and ndf = ", Melder_integer (ndf)); } END DIRECT (Discriminant_reportEqualityOfCovariances_wald) MelderInfo_open (); LOOP { iam (Discriminant); double chisq, prob, df; Covariances_equality ( (Collection) my groups, 2, &prob, &chisq, &df); MelderInfo_writeLine1 (L"Wald test for equality of covariance matrices:"); MelderInfo_writeLine2 (L"Chi squared: ", Melder_double (chisq)); MelderInfo_writeLine2 (L"Significance: ", Melder_double (prob)); MelderInfo_writeLine2 (L"Degrees of freedom: ", Melder_double (df)); MelderInfo_writeLine2 (L"Number of matrices: ", Melder_integer (my groups -> size)); } MelderInfo_close (); END FORM (Discriminant_getConcentrationEllipseArea, L"Discriminant: Get concentration ellipse area", L"Discriminant: Get concentration ellipse area...") SENTENCE (L"Group label", L"") POSITIVE (L"Number of sigmas", L"1.0") BOOLEAN (L"Discriminant plane", 1) INTEGER (L"X-dimension", L"1") INTEGER (L"Y-dimension", L"2") OK DO LOOP { iam (Discriminant); long group = Discriminant_groupLabelToIndex (me, GET_STRING (L"Group label")); REQUIRE (group > 0, L"Group label does not exist.") Melder_information (Melder_double (Discriminant_getConcentrationEllipseArea (me, group, GET_REAL (L"Number of sigmas"), 0, GET_INTEGER (L"Discriminant plane"), GET_INTEGER (L"X-dimension"), GET_INTEGER (L"Y-dimension")))); } END FORM (Discriminant_getConfidenceEllipseArea, L"Discriminant: Get confidence ellipse area", L"Discriminant: Get confidence ellipse area...") SENTENCE (L"Group label", L"") POSITIVE (L"Confidence level (0-1)", L"0.95") BOOLEAN (L"Discriminant plane", 1) INTEGER (L"X-dimension", L"1") INTEGER (L"Y-dimension", L"2") OK DO LOOP { iam (Discriminant); long group = Discriminant_groupLabelToIndex (me, GET_STRING (L"Group label")); REQUIRE (group > 0, L"Group label does not exist.") Melder_information (Melder_double (Discriminant_getConcentrationEllipseArea (me, group, GET_REAL (L"Confidence level"), 1, GET_INTEGER (L"Discriminant plane"), GET_INTEGER (L"X-dimension"), GET_INTEGER (L"Y-dimension")))); } END FORM (Discriminant_getLnDeterminant_group, L"Discriminant: Get determinant (group)", L"Discriminant: Get determinant (group)...") SENTENCE (L"Group label", L"") OK DO LOOP { iam (Discriminant); long group = Discriminant_groupLabelToIndex (me, GET_STRING (L"Group label")); REQUIRE (group > 0, L"Group label does not exist.") Melder_information (Melder_double (Discriminant_getLnDeterminant_group (me, group))); } END DIRECT (Discriminant_getLnDeterminant_total) LOOP { iam (Discriminant); Melder_information (Melder_double (Discriminant_getLnDeterminant_total (me))); } END FORM (Discriminant_invertEigenvector, L"Discriminant: Invert eigenvector", 0) NATURAL (L"Index of eigenvector", L"1") OK DO LOOP { iam (Discriminant); Eigen_invertEigenvector (me, GET_INTEGER (L"Index of eigenvector")); praat_dataChanged (me); } END FORM (Discriminant_drawSigmaEllipses, L"Discriminant: Draw sigma ellipses", L"Discriminant: Draw sigma ellipses...") POSITIVE (L"Number of sigmas", L"1.0") BOOLEAN (L"Discriminant plane", 1) INTEGER (L"X-dimension", L"1") INTEGER (L"Y-dimension", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Discriminant); Discriminant_drawConcentrationEllipses (me, GRAPHICS, GET_REAL (L"Number of sigmas"), 0, 0, GET_INTEGER (L"Discriminant plane"), GET_INTEGER (L"X-dimension"), GET_INTEGER (L"Y-dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END FORM (Discriminant_drawOneSigmaEllipse, L"Discriminant: Draw one sigma ellipse", L"Discriminant: Draw one sigma ellipse...") SENTENCE (L"Label", L"") POSITIVE (L"Number of sigmas", L"1.0") BOOLEAN (L"Discriminant plane", 1) INTEGER (L"X-dimension", L"1") INTEGER (L"Y-dimension", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Discriminant); Discriminant_drawConcentrationEllipses (me, GRAPHICS, GET_REAL (L"Number of sigmas"), 0, GET_STRING (L"Label"), GET_INTEGER (L"Discriminant plane"), GET_INTEGER (L"X-dimension"), GET_INTEGER (L"Y-dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END FORM (Discriminant_drawConfidenceEllipses, L"Discriminant: Draw confidence ellipses", 0) POSITIVE (L"Confidence level (0-1)", L"0.95") BOOLEAN (L"Discriminant plane", 1) INTEGER (L"X-dimension", L"1") INTEGER (L"Y-dimension", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Discriminant); Discriminant_drawConcentrationEllipses (me, GRAPHICS, GET_REAL (L"Confidence level"), 1, NULL, GET_INTEGER (L"Discriminant plane"), GET_INTEGER (L"X-dimension"), GET_INTEGER (L"Y-dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END FORM (Discriminant_drawOneConfidenceEllipse, L"Discriminant: Draw one confidence ellipse", 0) SENTENCE (L"Label", L"") POSITIVE (L"Confidence level (0-1)", L"0.95") BOOLEAN (L"Discriminant plane", 1) INTEGER (L"X-dimension", L"1") INTEGER (L"Y-dimension", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Discriminant); Discriminant_drawConcentrationEllipses (me, GRAPHICS, GET_REAL (L"Confidence level"), 1, GET_STRING (L"Label"), GET_INTEGER (L"Discriminant plane"), GET_INTEGER (L"X-dimension"), GET_INTEGER (L"Y-dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END DIRECT (Discriminant_extractBetweenGroupsSSCP) LOOP { iam (Discriminant); praat_new (Discriminant_extractBetweenGroupsSSCP (me), 0); } END DIRECT (Discriminant_extractGroupCentroids) LOOP { iam (Discriminant); praat_new (Discriminant_extractGroupCentroids (me), L"centroids"); } END DIRECT (Discriminant_extractGroupStandardDeviations) LOOP { iam (Discriminant); praat_new (Discriminant_extractGroupStandardDeviations (me), L"group_stddevs"); } END DIRECT (Discriminant_extractGroupLabels) LOOP { iam (Discriminant); praat_new (Discriminant_extractGroupLabels (me), L"group_labels"); } END DIRECT (Discriminant_extractPooledWithinGroupsSSCP) LOOP { iam (Discriminant); praat_new (Discriminant_extractPooledWithinGroupsSSCP (me), L"pooled_within"); } END FORM (Discriminant_extractWithinGroupSSCP, L"Discriminant: Extract within-group SSCP", L"Discriminant: Extract within-group SSCP...") NATURAL (L"Group index", L"1") OK DO long index = GET_INTEGER (L"Group index"); LOOP { iam (Discriminant); praat_new (Discriminant_extractWithinGroupSSCP (me, index), my name, L"_g", Melder_integer (index)); } END DIRECT (Discriminant_getNumberOfFunctions) LOOP { iam (Discriminant); Melder_information (Melder_integer (Discriminant_getNumberOfFunctions (me))); } END DIRECT (Discriminant_getDimensionOfFunctions) LOOP { iam (Discriminant); Melder_information (Melder_integer (Eigen_getDimensionOfComponents (me))); } END DIRECT (Discriminant_getNumberOfGroups) LOOP { iam (Discriminant); Melder_information (Melder_integer (Discriminant_getNumberOfGroups (me))); } END FORM (Discriminant_getNumberOfObservations, L"Discriminant: Get number of observations", L"Discriminant: Get number of observations...") INTEGER (L"Group", L"0 (=total)") OK DO LOOP { iam (Discriminant); Melder_information (Melder_integer (Discriminant_getNumberOfObservations (me, GET_INTEGER (L"Group")))); } END /********************** DTW *******************************************/ FORM (DTW_and_Polygon_findPathInside, L"DTW & Polygon: Find path inside", 0) RADIO (L"Slope constraint", 1) RADIOBUTTON (L"no restriction") RADIOBUTTON (L"1/3 < slope < 3") RADIOBUTTON (L"1/2 < slope < 2") RADIOBUTTON (L"2/3 < slope < 3/2") OK DO int localSlope = GET_INTEGER (L"Slope constraint"); DTW me = FIRST (DTW); Polygon thee = FIRST (Polygon); DTW_and_Polygon_findPathInside (me, thee, localSlope, 0); END FORM (DTW_and_Polygon_to_Matrix_cummulativeDistances, L"DTW & Polygon: To Matrix (cumm. distances)", 0) RADIO (L"Slope constraint", 1) RADIOBUTTON (L"no restriction") RADIOBUTTON (L"1/3 < slope < 3") RADIOBUTTON (L"1/2 < slope < 2") RADIOBUTTON (L"2/3 < slope < 3/2") OK DO int localSlope = GET_INTEGER (L"Slope constraint"); DTW me = FIRST (DTW); Polygon thee = FIRST (Polygon); autoMatrix him = DTW_and_Polygon_to_Matrix_cummulativeDistances (me, thee, localSlope); praat_new (him.transfer(), my name, L"_", Melder_integer (localSlope)); END FORM (DTW_and_Sounds_draw, L"DTW & Sounds: Draw", L"DTW & Sounds: Draw...") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO Sound s1 = 0, s2 = 0; DTW dtw = 0; LOOP { iam (Data); if (CLASS == classSound) { (s1 ? s2 : s1) = (Sound) me; } else if (CLASS == classDTW) { dtw = (DTW) me; } } Melder_assert (s1 && s2 && dtw); autoPraatPicture picture; DTW_and_Sounds_draw (dtw, s2, s1, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); END FORM (DTW_and_Sounds_drawWarpX, L"DTW & Sounds: Draw warp (x)", L"DTW & Sounds: Draw warp (x)...") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") REAL (L"Time (s)", L"0.1") BOOLEAN (L"Garnish", 1) OK DO Sound s1 = 0, s2 = 0; LOOP { iam (Sound); (s1 ? s2 : s1) = me; } Melder_assert (s1 && s2); DTW dtw = FIRST (DTW); autoPraatPicture picture; DTW_and_Sounds_drawWarpX (dtw, s2, s1, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Time"), GET_INTEGER (L"Garnish")); END void DTW_constraints_addCommonFields (void *dia) { Any radio; LABEL (L"", L"Boundary conditions") BOOLEAN (L"Match begin positions", 0) BOOLEAN (L"Match end positions", 0) RADIO (L"Slope constraint", 1) RADIOBUTTON (L"no restriction") RADIOBUTTON (L"1/3 < slope < 3") RADIOBUTTON (L"1/2 < slope < 2") RADIOBUTTON (L"2/3 < slope < 3/2") } void DTW_constraints_getCommonFields (void *dia, int *begin, int *end, int *slope) { *begin = GET_INTEGER (L"Match begin positions"); *end = GET_INTEGER (L"Match end positions"); *slope = GET_INTEGER (L"Slope constraint"); } DIRECT (DTW_help) Melder_help (L"DTW"); END FORM (DTW_drawPath, L"DTW: Draw path", 0) REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 0); OK DO autoPraatPicture picture; LOOP { iam (DTW); DTW_drawPath (me, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); } END FORM (DTW_drawDistancesAlongPath, L"DTW: Draw distances along path", 0) REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 0); OK DO autoPraatPicture picture; LOOP { iam (DTW); DTW_drawDistancesAlongPath (me, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); } END FORM (DTW_paintDistances, L"DTW: Paint distances", 0) REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") REAL (L"Minimum", L"0.0") REAL (L"Maximum", L"0.0") BOOLEAN (L"Garnish", 0); OK DO autoPraatPicture picture; LOOP { iam (DTW); DTW_paintDistances (me, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Minimum"), GET_REAL (L"Maximum"), GET_INTEGER (L"Garnish")); } END FORM (DTW_drawWarpX, L"DTW: Draw warp (x)", L"DTW: Draw warp (x)...") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") REAL (L"Time (s)", L"0.1") BOOLEAN (L"Garnish", 0); OK DO autoPraatPicture picture; LOOP { iam (DTW); DTW_drawWarpX (me, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Time"), GET_INTEGER (L"Garnish")); } END DIRECT (DTW_getStartTimeX) LOOP { iam (DTW); Melder_information (Melder_double (my xmin), L" s (= start time along x)"); } END DIRECT (DTW_getEndTimeX) LOOP { iam (DTW); Melder_information (Melder_double (my xmax), L" s (= end time along x)"); } END DIRECT (DTW_getTotalDurationX) LOOP { iam (DTW); Melder_information (Melder_double (my xmax - my xmin), L" s (= total duration along x)"); } END DIRECT (DTW_getStartTimeY) LOOP { iam (DTW); Melder_information (Melder_double (my ymin), L" s (= start time along y)"); } END DIRECT (DTW_getEndTimeY) LOOP { iam (DTW); Melder_information (Melder_double (my ymax), L" s (= end time along y)"); } END DIRECT (DTW_getTotalDurationY) LOOP { iam (DTW); Melder_information (Melder_double (my ymax - my ymin), L" s (= total duration along y)"); } END DIRECT (DTW_getNumberOfFramesX) LOOP { iam (DTW); Melder_information (Melder_integer (my nx), L" (= number of frames along x)"); } END DIRECT (DTW_getTimeStepX) LOOP { iam (DTW); Melder_information (Melder_double (my dx), L" s (= time step along x)"); } END FORM (DTW_getTimeFromFrameNumberX, L"DTW: Get time from frame number (x)", 0) NATURAL (L"Frame number (x)", L"1") OK DO double column = GET_INTEGER (L"Frame number"); LOOP { iam (DTW); Melder_information (Melder_double (Matrix_columnToX (me, column)), L" s (= y time at x frame ", Melder_integer (column), L")"); } END FORM (DTW_getFrameNumberFromTimeX, L"DTW: Get frame number from time (x)", 0) REAL (L"Time along x (s)", L"0.1") OK DO double time = GET_REAL (L"Time along x"); LOOP { iam (DTW); if (time < my xmin || time > my xmax) { Melder_throw (me, "Time outside x domain."); } long iframe = floor (Matrix_xToColumn (me, time) + 0.5); Melder_information (Melder_integer (iframe), L" (= x frame at y time ", Melder_double (time), L")"); } END DIRECT (DTW_getNumberOfFramesY) LOOP { iam (DTW); Melder_information (Melder_integer (my ny), L" (= number of frames along y)"); } END DIRECT (DTW_getTimeStepY) LOOP { iam (DTW); Melder_information (Melder_double (my dy), L" s (= time step along y)"); } END FORM (DTW_getTimeFromFrameNumberY, L"DTW: Get time from frame number (y)", 0) NATURAL (L"Frame number (y)", L"1") OK DO double row = GET_INTEGER (L"Frame number"); LOOP { iam (DTW); Melder_information (Melder_double (Matrix_rowToY (me, row)), L" s (= x time at y frame ", Melder_integer (row), L")"); } END FORM (DTW_getFrameNumberFromTimeY, L"DTW: Get frame number from time (y)", 0) REAL (L"Time along y (s)", L"0.1") OK DO double time = GET_REAL (L"Time along y"); LOOP { iam (DTW); if (time < my ymin || time > my ymax) { Melder_throw (me, "Time outside y domain."); } long iframe = floor (Matrix_yToRow (me, time) + 0.5); Melder_information (Melder_integer (iframe), L" (= y frame at x time ", Melder_double (time), L")"); } END FORM (DTW_getPathY, L"DTW: Get time along path", L"DTW: Get time along path...") REAL (L"Time (s)", L"0.0") OK DO LOOP { iam (DTW); Melder_information (Melder_double (DTW_getPathY (me, GET_REAL (L"Time")))); } END FORM (DTW_getYTimeFromXTime, L"DTW: Get y time from x time", L"DTW: Get y time from x time...") REAL (L"Time at x (s)", L"0.0") OK DO double time = GET_REAL (L"Time at x"); LOOP { iam (DTW); Melder_information (Melder_double (DTW_getYTimeFromXTime (me, time)), L" s (= y time at z time ", Melder_double (time), L")"); } END FORM (DTW_getXTimeFromYTime, L"DTW: Get x time from y time", L"DTW: Get x time from y time...") REAL (L"Time at y (s)", L"0.0") OK DO double time = GET_REAL (L"Time at y"); LOOP { iam (DTW); Melder_information (Melder_double (DTW_getXTimeFromYTime (me, time)), L" s (= x time at y time ", Melder_double (time), L")"); } END FORM (DTW_getMaximumConsecutiveSteps, L"DTW: Get maximum consecutive steps", L"DTW: Get maximum consecutive steps...") OPTIONMENU (L"Direction", 1) OPTION (L"X") OPTION (L"Y") OPTION (L"Diagonaal") OK DO int direction[] = {DTW_START, DTW_X, DTW_Y, DTW_XANDY}; const wchar_t *string[] = {L"", L"x", L"y", L"diagonal"}; int d = GET_INTEGER (L"Direction"); LOOP { iam (DTW); Melder_information (Melder_integer (DTW_getMaximumConsecutiveSteps (me, direction[d])), L" (= maximum number of consecutive steps in ", string[d], L" direction)"); } END DIRECT (DTW_getWeightedDistance) LOOP { iam (DTW); Melder_information (Melder_double (my weightedDistance)); } END FORM (DTW_getDistanceValue, L"DTW: Get distance value", 0) REAL (L"Time at x (s)", L"0.1") REAL (L"Time at y (s)", L"0.1") OK DO double xtime = GET_REAL (L"Time at x"); double ytime = GET_REAL (L"Time at y"); double dist; LOOP { iam (DTW); if (xtime < my xmin || xtime > my xmax || ytime < my ymin || ytime > my ymax) { dist = NUMundefined; } else { long irow = Matrix_yToNearestRow (me, ytime); long icol = Matrix_xToNearestColumn (me, xtime); dist = my z[irow][icol]; } Melder_information (Melder_double (dist), L" (= distance at (", Melder_double (xtime), L", ", Melder_double (ytime), L"))"); } END DIRECT (DTW_getMinimumDistance) LOOP { iam (DTW); double minimum = NUMundefined, maximum = NUMundefined; Matrix_getWindowExtrema (me, 0, 0, 0, 0, & minimum, & maximum); Melder_informationReal (minimum, 0); } END DIRECT (DTW_getMaximumDistance) LOOP { iam (DTW); double minimum = NUMundefined, maximum = NUMundefined; Matrix_getWindowExtrema (me, 0, 0, 0, 0, & minimum, & maximum); Melder_informationReal (maximum, 0); } END FORM (DTW_formulaDistances, L"DTW: Formula (distances)", 0) LABEL (L"label", L"y := y1; for row := 1 to nrow do { x := x1; " "for col := 1 to ncol do { self [row, col] := `formula' ; x := x + dx } y := y + dy }") TEXTFIELD (L"formula", L"self") OK DO LOOP { iam (DTW); autoMatrix cp = DTW_to_Matrix_distances (me); try { Matrix_formula (reinterpret_cast (me), GET_STRING (L"formula"), interpreter, 0); double minimum, maximum; Matrix_getWindowExtrema (me, 0, 0, 0, 0, & minimum, & maximum); if (minimum < 0) { DTW_and_Matrix_replace (me, cp.peek()); // restore original Melder_throw ("Execution of the formula has made some distance(s) negative which is not allowed."); } praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); throw; } } END FORM (DTW_setDistanceValue, L"DTW: Set distance value", 0) REAL (L"Time at x (s)", L"0.1") REAL (L"Time at y (s)", L"0.1") REAL (L"New value", L"0.0") OK DO double xtime = GET_REAL (L"Time at x"); double ytime = GET_REAL (L"Time at y"); double val = GET_REAL (L"New value"); if (val < 0) { Melder_throw ("Distances cannot be negative."); } LOOP { iam (DTW); if (xtime < my xmin || xtime > my xmax) { Melder_throw ("Time at x outside domain."); } if (ytime < my ymin || ytime > my ymax) { Melder_throw ("Time at y outside domain."); } long irow = Matrix_yToNearestRow (me, ytime); long icol = Matrix_xToNearestColumn (me, xtime); my z[irow][icol] = GET_REAL (L"New value"); praat_dataChanged (me); } END FORM (DTW_findPath, L"DTW: Find path", 0) DTW_constraints_addCommonFields (dia); OK DO int begin, end, slope; DTW_constraints_getCommonFields (dia, &begin, &end, &slope); LOOP { iam (DTW); DTW_findPath (me, begin, end, slope); } END FORM (DTW_findPath_bandAndSlope, L"DTW: find path (band & slope)", 0) REAL (L"Sakoe-Chiba band (s)", L"0.05") RADIO (L"Slope constraint", 1) RADIOBUTTON (L"no restriction") RADIOBUTTON (L"1/3 < slope < 3") RADIOBUTTON (L"1/2 < slope < 2") RADIOBUTTON (L"2/3 < slope < 3/2") OK DO double band = GET_REAL (L"Sakoe-Chiba band"); int slope = GET_INTEGER (L"Slope constraint"); LOOP { iam (DTW); DTW_findPath_bandAndSlope (me, band, slope, 0); } END FORM (DTW_to_Matrix_cummulativeDistances, L"DTW: To Matrix", 0) REAL (L"Sakoe-Chiba band (s)", L"0.05") RADIO (L"Slope constraint", 1) RADIOBUTTON (L"no restriction") RADIOBUTTON (L"1/3 < slope < 3") RADIOBUTTON (L"1/2 < slope < 2") RADIOBUTTON (L"2/3 < slope < 3/2") OK DO double band = GET_REAL (L"Sakoe-Chiba band"); int slope = GET_INTEGER (L"Slope constraint"); LOOP { iam (DTW); autoMatrix thee = DTW_to_Matrix_cummulativeDistances (me, band, slope); praat_new (thee.transfer(), my name, L"_cd"); } END FORM (DTW_to_Polygon, L"DTW: To Polygon...", 0) REAL (L"Sakoe-Chiba band (s)", L"0.1") RADIO (L"Slope constraint", 1) RADIOBUTTON (L"no restriction") RADIOBUTTON (L"1/3 < slope < 3") RADIOBUTTON (L"1/2 < slope < 2") RADIOBUTTON (L"2/3 < slope < 3/2") OK DO double band = GET_REAL (L"Sakoe-Chiba band"); int slope = GET_INTEGER (L"Slope constraint"); LOOP { iam (DTW); autoPolygon thee = DTW_to_Polygon (me, band, slope); praat_new (thee.transfer(), my name); } END DIRECT (DTW_to_Matrix_distances) LOOP { iam (DTW); praat_new (DTW_to_Matrix_distances (me), my name); } END DIRECT (DTW_swapAxes) LOOP { iam (DTW); praat_new (DTW_swapAxes (me), my name, L"_axesSwapped"); } END DIRECT (DTW_and_Matrix_replace) DTW me = FIRST (DTW); Matrix m = FIRST (Matrix); DTW_and_Matrix_replace (me, m); praat_dataChanged (me); END DIRECT (DTW_and_TextGrid_to_TextGrid) DTW me = FIRST (DTW); TextGrid tg = FIRST (TextGrid); praat_new (DTW_and_TextGrid_to_TextGrid (me, tg, 0), 0); END DIRECT (DTW_and_IntervalTier_to_Table) DTW me = FIRST (DTW); IntervalTier ti = FIRST (IntervalTier); praat_new (DTW_and_IntervalTier_to_Table (me, ti, 1.0/44100), my name); END /******************** EditDistanceTable & EditCostsTable ********************************************/ DIRECT (EditDistanceTable_help) Melder_help (L"EditDistanceTable"); END DIRECT (EditDistanceTable_to_TableOfReal_directions) LOOP { iam (EditDistanceTable); praat_new (EditDistanceTable_to_TableOfReal_directions (me), my name); } END DIRECT (EditDistanceTable_setEditCosts) EditDistanceTable me = FIRST (EditDistanceTable); EditCostsTable thee = FIRST(EditCostsTable); EditDistanceTable_setEditCosts (me, thee); END FORM (EditDistanceTable_setDefaultCosts, L"", 0) REAL (L"Insertion costs", L"1.0") REAL (L"Deletion costs", L"1.0") REAL (L"Substitution costs", L"2.0") OK DO double insertionCosts = GET_REAL (L"Insertion costs"); if (insertionCosts < 0) { Melder_throw ("Insertion costs cannot be negative."); } double deletionCosts = GET_REAL (L"Deletion costs"); if (deletionCosts < 0) { Melder_throw ("Deletion costs cannot be negative."); } double substitutionCosts = GET_REAL (L"Substitution costs"); if (substitutionCosts < 0) { Melder_throw ("Substitution costs cannot be negative."); } LOOP { iam (EditDistanceTable); EditDistanceTable_setDefaultCosts (me, insertionCosts, deletionCosts, substitutionCosts); } END FORM (EditDistanceTable_draw, L"EditDistanceTable_draw", 0) RADIO (L"Format", 3) RADIOBUTTON (L"decimal") RADIOBUTTON (L"exponential") RADIOBUTTON (L"free") RADIOBUTTON (L"rational") NATURAL (L"Precision", L"1") REAL (L"Rotate source labels by (degrees)", L"0.0") OK DO autoPraatPicture picture; LOOP { iam (EditDistanceTable); EditDistanceTable_draw (me, GRAPHICS, GET_INTEGER (L"Format"), GET_INTEGER (L"Precision"), GET_REAL (L"Rotate source labels by")); } END DIRECT (EditDistanceTable_drawEditOperations) autoPraatPicture picture; LOOP { iam(EditDistanceTable); EditDistanceTable_drawEditOperations (me, GRAPHICS); } END DIRECT (EditCostsTable_help) Melder_help (L"EditCostsTable"); END FORM (EditCostsTable_getTargetIndex, L"EditCostsTable: Get target index", 0) SENTENCE (L"Target", L"") OK DO LOOP { iam (EditCostsTable); Melder_informationReal (EditCostsTable_getTargetIndex (me, GET_STRING (L"Target")), NULL); } END FORM (EditCostsTable_getSourceIndex, L"EditCostsTable: Get source index", 0) SENTENCE (L"Source", L"") OK DO LOOP { iam (EditCostsTable); Melder_informationReal (EditCostsTable_getSourceIndex (me, GET_STRING (L"Source")), NULL); } END FORM (EditCostsTable_getInsertionCost, L"EditCostsTable: Get insertion cost", 0) SENTENCE (L"Target", L"") OK DO LOOP { iam (EditCostsTable); Melder_informationReal (EditCostsTable_getInsertionCost (me, GET_STRING (L"Target")), NULL); } END FORM (EditCostsTable_getDeletionCost, L"EditCostsTable: Get deletion cost", 0) SENTENCE (L"Source", L"") OK DO LOOP { iam (EditCostsTable); Melder_informationReal (EditCostsTable_getDeletionCost (me, GET_STRING (L"Source")), NULL); } END FORM (EditCostsTable_getSubstitutionCost, L"EditCostsTable: Get substitution cost", 0) SENTENCE (L"Target", L"") SENTENCE (L"Source", L"") OK DO LOOP { iam (EditCostsTable); Melder_informationReal (EditCostsTable_getSubstitutionCost (me, GET_STRING (L"Target"), GET_STRING (L"Source")), NULL); } END FORM (EditCostsTable_getOthersCost, L"EditCostsTable: Get cost (others)", 0) RADIO (L"Others cost type", 1) RADIOBUTTON (L"Insertion") RADIOBUTTON (L"Deletion") RADIOBUTTON (L"Equality") RADIOBUTTON (L"Inequality") OK DO LOOP { iam (EditCostsTable); Melder_informationReal (EditCostsTable_getOthersCost (me, GET_INTEGER (L"Others cost type")), NULL); } END FORM (EditCostsTable_setTargetSymbol_index, L"EditCostsTable: Set target symbol (index)", 0) NATURAL (L"Index", L"1") SENTENCE (L"Target", L"a") OK DO LOOP { iam (TableOfReal); TableOfReal_setRowLabel (me, GET_INTEGER (L"Index"), GET_STRING (L"Target")); } END FORM (EditCostsTable_setSourceSymbol_index, L"EditCostsTable: Set source symbol (index)", 0) NATURAL (L"Index", L"1") SENTENCE (L"Source", L"a") OK DO LOOP { iam (TableOfReal); TableOfReal_setColumnLabel (me, GET_INTEGER (L"Index"), GET_STRING (L"Source")); } END FORM (EditCostsTable_setInsertionCosts, L"EditCostsTable: Set insertion costs", 0) SENTENCE (L"Targets", L"") REAL (L"Cost", L"2.0") OK DO LOOP { iam (EditCostsTable); EditCostsTable_setInsertionCosts (me, GET_STRING (L"Targets"), GET_REAL (L"Cost")); } END FORM (EditCostsTable_setDeletionCosts, L"EditCostsTable: Set deletion costs", 0) SENTENCE (L"Sources", L"") REAL (L"Cost", L"2.0") OK DO LOOP { iam (EditCostsTable); EditCostsTable_setDeletionCosts (me, GET_STRING (L"Sources"), GET_REAL (L"Cost")); } END FORM (EditCostsTable_setSubstitutionCosts, L"EditCostsTable: Set substitution costs", 0) SENTENCE (L"Targets", L"a i u") SENTENCE (L"Sources", L"a i u") REAL (L"Cost", L"2.0") OK DO LOOP { iam (EditCostsTable); EditCostsTable_setSubstitutionCosts (me, GET_STRING (L"Targets"), GET_STRING (L"Sources"), GET_REAL (L"Cost")); } END FORM (EditCostsTable_setOthersCosts, L"EditCostsTable: Set costs (others)", 0) LABEL (L"", L"Others costs") REAL (L"Insertion", L"1.0") REAL (L"Deletion", L"1.0") LABEL (L"", L"Substitution costs") REAL (L"Equality", L"0.0") REAL (L"Inequality", L"2.0") OK DO LOOP { iam (EditCostsTable); EditCostsTable_setOthersCosts (me, GET_REAL (L"Insertion"), GET_REAL (L"Deletion"), GET_REAL (L"Equality"), GET_REAL (L"Inequality")); } END DIRECT (EditCostsTable_to_TableOfReal) LOOP { iam (EditCostsTable); praat_new (EditCostsTable_to_TableOfReal (me), my name); } END FORM (EditCostsTable_createEmpty, L"Create empty EditCostsTable", 0) SENTENCE (L"Name", L"editCosts") INTEGER (L"Target alphabet size", L"0") INTEGER (L"Source alphabet size", L"0") OK DO long targetAlphabetSize = GET_INTEGER (L"Target alphabet size"); targetAlphabetSize = targetAlphabetSize < 0 ? 0 : targetAlphabetSize; long sourceAlphabetSize = GET_INTEGER (L"Source alphabet size"); sourceAlphabetSize = sourceAlphabetSize < 0 ? 0 : sourceAlphabetSize; praat_new (EditCostsTable_create (targetAlphabetSize, sourceAlphabetSize), GET_STRING (L"Name")); END /******************** Eigen ********************************************/ DIRECT (Eigen_drawEigenvalues_scree) Melder_warning (L"The command \"Draw eigenvalues (scree)...\" has been " "removed.\n To get a scree plot use \"Draw eigenvalues...\" with the " "arguments\n 'Fraction of eigenvalues summed' and 'Cumulative' unchecked."); END FORM (Eigen_drawEigenvalues, L"Eigen: Draw eigenvalues", L"Eigen: Draw eigenvalues...") INTEGER (L"left Eigenvalue range", L"0") INTEGER (L"right Eigenvalue range", L"0") REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") BOOLEAN (L"Fraction of eigenvalues summed", 0) BOOLEAN (L"Cumulative", 0) POSITIVE (L"Mark size (mm)", L"1.0") SENTENCE (L"Mark string (+xo.)", L"+") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Eigen); Eigen_drawEigenvalues (me, GRAPHICS, GET_INTEGER (L"left Eigenvalue range"), GET_INTEGER (L"right Eigenvalue range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), GET_INTEGER (L"Fraction of eigenvalues summed"), GET_INTEGER (L"Cumulative"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); } END FORM (Eigen_drawEigenvector, L"Eigen: Draw eigenvector", L"Eigen: Draw eigenvector...") INTEGER (L"Eigenvector number", L"1") BOOLEAN (L"Component loadings", 0) INTEGER (L"left Element range", L"0") INTEGER (L"right Element range", L"0") REAL (L"left Amplitude range", L"-1.0") REAL (L"right Amplitude range", L"1.0") POSITIVE (L"Mark size (mm)", L"1.0") SENTENCE (L"Mark string (+xo.)", L"+") BOOLEAN (L"Connect points", 1) BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Eigen); Eigen_drawEigenvector (me, GRAPHICS, GET_INTEGER (L"Eigenvector number"), GET_INTEGER (L"left Element range"), GET_INTEGER (L"right Element range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), GET_INTEGER (L"Component loadings"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Connect points"), 0, GET_INTEGER (L"Garnish")); } END DIRECT (Eigen_getNumberOfEigenvalues) LOOP { iam (Eigen); Melder_information (Melder_integer (my numberOfEigenvalues)); } END DIRECT (Eigen_getDimension) LOOP { iam (Eigen); Melder_information (Melder_integer (my dimension)); } END FORM (Eigen_getEigenvalue, L"Eigen: Get eigenvalue", L"Eigen: Get eigenvalue...") NATURAL (L"Eigenvalue number", L"1") OK DO LOOP { iam (Eigen); long number = GET_INTEGER (L"Eigenvalue number"); if (number > my numberOfEigenvalues) { Melder_throw ("Eigenvalue number must be smaller than ", my numberOfEigenvalues + 1); } Melder_information (Melder_double (my eigenvalues[number])); } END FORM (Eigen_getSumOfEigenvalues, L"Eigen:Get sum of eigenvalues", L"Eigen: Get sum of eigenvalues...") INTEGER (L"left Eigenvalue range", L"0") INTEGER (L"right Eigenvalue range", L"0") OK DO LOOP { iam (Eigen); Melder_information (Melder_double (Eigen_getSumOfEigenvalues (me, GET_INTEGER (L"left Eigenvalue range"), GET_INTEGER (L"right Eigenvalue range")))); } END FORM (Eigen_getEigenvectorElement, L"Eigen: Get eigenvector element", L"Eigen: Get eigenvector element...") NATURAL (L"Eigenvector number", L"1") NATURAL (L"Element number", L"1") OK DO LOOP { iam (Eigen); Melder_information (Melder_double (Eigen_getEigenvectorElement (me, GET_INTEGER (L"Eigenvector number"), GET_INTEGER (L"Element number")))); } END DIRECT (Eigens_alignEigenvectors) autoCollection set = praat_getSelectedObjects (); Eigens_alignEigenvectors (set.peek()); END FORM (Eigen_and_Matrix_project, L"Eigen & Matrix: Project", L"Eigen & Matrix: Project...") INTEGER (L"Number of dimensions", L"0") OK DO Eigen me = FIRST_GENERIC (Eigen); Matrix mat = FIRST_GENERIC (Matrix); praat_new (Eigen_and_Matrix_project (me, mat, GET_INTEGER (L"Number of dimensions")), my name, L"_", mat->name); END DIRECT (Eigen_and_SSCP_project) Eigen me = FIRST_GENERIC (Eigen); SSCP cp = FIRST (SSCP); praat_new (Eigen_and_SSCP_project (me, cp), my name, L"_", cp->name); END DIRECT (Eigen_and_Covariance_project) Eigen me = FIRST_GENERIC (Eigen); Covariance cv = FIRST (Covariance); praat_new (Eigen_and_Covariance_project (me, cv), my name, L"_", cv->name); END /******************** Index ********************************************/ DIRECT (Index_help) Melder_help (L"Index"); END DIRECT (Index_getNumberOfClasses) LOOP { iam (Index); Melder_information (Melder_integer (my classes -> size)); } END FORM (StringsIndex_getClassLabel, L"StringsIndex: Get class label", L"StringsIndex: Get class label...") NATURAL (L"Class index", L"1") OK DO long klas = GET_INTEGER (L"Class index"); LOOP { iam (StringsIndex); long numberOfClasses = my classes -> size; if (klas > numberOfClasses) { Melder_throw ("Index must be less than or equal ", numberOfClasses, L"."); } SimpleString ss = (SimpleString) my classes -> item[klas]; Melder_information (ss -> string); } END FORM (StringsIndex_getLabel, L"StringsIndex: Get label", L"StringsIndex: Get label...") NATURAL (L"Element index", L"1") OK DO long index = GET_INTEGER (L"Element index"); LOOP { iam (StringsIndex); if (index > my numberOfElements) { Melder_throw ("Index must be less than or equal ", my numberOfElements, L"."); } long klas = my classIndex[index]; SimpleString ss = (SimpleString) my classes -> item [klas]; Melder_information (ss -> string); } END FORM (Index_getIndex, L"Index: Get index", L"Index: Get index...") NATURAL (L"Element index", L"1") OK DO long index = GET_INTEGER (L"Element index"); LOOP { iam (Index); if (index > my numberOfElements) { Melder_throw ("Index must be less than or equal ", my numberOfElements, L"."); } Melder_information (Melder_integer (my classIndex[index])); } END FORM (StringsIndex_getClassIndex, L"StringsIndex: Get class index", L"StringsIndex: Get class index...") WORD (L"Class label", L"label") OK DO wchar_t *klasLabel = GET_STRING (L"Class label"); LOOP { iam (StringsIndex); long index = StringsIndex_getClass (me, klasLabel); Melder_information (Melder_integer (index)); } END FORM (Index_extractPart, L"Index: Extract part", L"Index: Extract part...") INTEGER (L"left Range", L"0") INTEGER (L"right Range", L"0") OK DO LOOP { iam (Index); praat_new (Index_extractPart (me, GET_INTEGER (L"left Range"), GET_INTEGER (L"right Range")), Thing_getName (me), L"_part"); } END FORM (Index_to_Permutation, L"Index: To Permutation", L"Index: To Permutation...") BOOLEAN (L"Permute within classes", 1) OK DO LOOP { iam (Index); praat_new (Index_to_Permutation_permuteRandomly (me, GET_INTEGER (L"Permute within classes")), my name); } END DIRECT (StringsIndex_to_Strings) LOOP { iam (StringsIndex); praat_new (StringsIndex_to_Strings (me), my name); } END /******************** Excitation ********************************************/ DIRECT (Excitation_to_Excitations) autoExcitations e = Excitations_create (100); LOOP { iam (Excitation); autoExcitation thee = Data_copy (me); Collection_addItem (e.peek(), thee.transfer()); } praat_new (e.transfer(), L"appended"); END /******************** Excitations ********************************************/ FORM (Excitations_formula, L"Excitations: Formula", 0) LABEL (L"label", L"for all objects in Excitations do { for col := 1 to ncol do { self [col] := `formula' ; x := x + dx } }") TEXTFIELD (L"formula", L"self") OK DO LOOP { iam (Excitations); for (long j = 1; j <= my size; j++) { Matrix_formula ( (Matrix) my item[j], GET_STRING (L"formula"), interpreter, 0); } praat_dataChanged (me); } END DIRECT (Excitations_addItem) Excitations e = FIRST (Excitations); WHERE_DOWN (SELECTED && CLASS == classExcitation) { iam (Excitation); autoExcitation thee = Data_copy (me); Collection_addItem (e, thee.transfer()); } END FORM (Excitations_getItem, L"Excitations: Get item", 0) NATURAL (L"Item number", L"1") OK DO LOOP { iam (Excitations); praat_new (Excitations_getItem (me, GET_INTEGER (L"Item number")), my name, L"_item"); } END DIRECT (Excitations_append) Excitations e1 = 0, e2 = 0; LOOP { iam (Excitations); (e1 ? e2 : e1) = me; } Melder_assert (e1 && e2); praat_new ( (Excitations) Collections_merge (e1, e2), L"appended"); END FORM (Excitations_to_Pattern, L"Excitations: To Pattern", 0) NATURAL (L"Join", L"1") OK DO LOOP { iam (Excitations); praat_new (Excitations_to_Pattern (me, GET_INTEGER (L"Join")), my name); } END DIRECT (Excitations_to_TableOfReal) LOOP { iam (Excitations); praat_new (Excitations_to_TableOfReal (me), my name); } END /************************* FileInMemory ***********************************/ FORM_READ (FileInMemory_create, L"Create file in memory", 0, true) autoFileInMemory me = FileInMemory_create (file); praat_new (me.transfer(), MelderFile_name (file)); END FORM (FileInMemory_setId, L"FileInMemory: Set id", 0) SENTENCE (L"New id", L"New id") OK DO LOOP { iam (FileInMemory); FileInMemory_setId (me, GET_STRING (L"New id")); praat_dataChanged (me); } END FORM (FileInMemory_showAsCode, L"FileInMemory: Show as code", 0) WORD (L"Name", L"example") INTEGER (L"Number of bytes per line", L"20") OK DO const wchar_t *name = GET_STRING (L"Name"); LOOP { iam (FileInMemory); MelderInfo_open (); FileInMemory_showAsCode (me, name, GET_INTEGER (L"Number of bytes per line")); MelderInfo_close (); } END /************************* FilesInMemory ***********************************/ FORM (FilesInMemory_createFromDirectoryContents, L"Create files in memory from directory contents", 0) SENTENCE (L"Name", L"list") LABEL (L"", L"Directory:") TEXTFIELD (L"Directory", L"/home/david/praat/src/espeak-work/espeak-1.46.13/espeak-data") WORD (L"Only files that match pattern", L"*.txt") OK DO autoFilesInMemory me = FilesInMemory_createFromDirectoryContents (GET_STRING (L"Directory"), GET_STRING (L"Only files that match pattern")); praat_new (me.transfer(), GET_STRING (L"Name")); END FORM (FilesInMemory_createCopyFromFilesInMemory, L"", 0) OPTIONMENU (L"Espeakdata", 5) OPTION (L"phons") OPTION (L"dicts") OPTION (L"voices") OPTION (L"variants") OPTION (L"voices_names") OPTION (L"variants_names") OK DO long choice = GET_INTEGER (L"Espeakdata"); if (choice == 1) { autoFilesInMemory f = (FilesInMemory) Data_copy (espeakdata_phons); praat_new (f.transfer(), L"espeakdata_phons"); } else if (choice == 2) { autoFilesInMemory f = (FilesInMemory) Data_copy (espeakdata_dicts); praat_new (f.transfer(), L"espeakdata_dicts"); } else if (choice == 3) { autoFilesInMemory f = (FilesInMemory) Data_copy (espeakdata_voices); praat_new (f.transfer(), L"espeakdata_voices"); } else if (choice == 4) { autoFilesInMemory f = (FilesInMemory) Data_copy (espeakdata_variants); praat_new (f.transfer(), L"espeakdata_variants"); } else if (choice == 5) { autoStrings s = (Strings) Data_copy (espeakdata_voices_names); praat_new (s.transfer(), L"espeakdata_voices_names"); } else if (choice == 6) { autoStrings s = (Strings) Data_copy (espeakdata_variants_names); praat_new (s.transfer(), L"espeakdata_variants_names"); } END FORM (FilesInMemory_showAsCode, L"FilesInMemory: Show as code", 0) WORD (L"Name", L"example") INTEGER (L"Number of bytes per line", L"20") OK DO LOOP { iam (FilesInMemory); MelderInfo_open (); FilesInMemory_showAsCode (me, GET_STRING (L"Name"), GET_INTEGER (L"Number of bytes per line")); MelderInfo_close (); } END FORM (FilesInMemory_showOneFileAsCode, L"FilesInMemory: Show one file as code", 0) NATURAL (L"Index", L"1") WORD (L"Name", L"example") INTEGER (L"Number of bytes per line", L"20") OK DO LOOP { iam (FilesInMemory); MelderInfo_open (); FilesInMemory_showOneFileAsCode (me, GET_INTEGER (L"Index"), GET_STRING (L"Name"), GET_INTEGER (L"Number of bytes per line")); MelderInfo_close (); } END DIRECT (FileInMemory_to_FilesInMemory) autoFilesInMemory thee = FilesInMemory_create (); LOOP { iam (FileInMemory); FileInMemory him = Data_copy (me); Collection_addItem (thee.peek(), him); } praat_new (thee.transfer(), L"files"); END DIRECT (FilesInMemory_addItems) FilesInMemory thee = FIRST (FilesInMemory); LOOP { iam (Data); if (CLASS == classFileInMemory) { FileInMemory t1 = (FileInMemory) Data_copy (me); Collection_addItem (thee, t1); } } END DIRECT (FilesInMemory_merge) FilesInMemory f1 = 0, f2 = 0; LOOP { iam (FilesInMemory); (f1 ? f2 : f1) = me; } Melder_assert (f1 != 0 && f2 != 0); autoFilesInMemory fim = (FilesInMemory) Collections_merge (f1, f2); praat_new (fim.transfer(), f1 -> name, L"_", f2 -> name); END DIRECT (FilesInMemory_to_Strings_id) LOOP { iam (FilesInMemory); praat_new (FilesInMemory_to_Strings_id (me), my name); } END /************************* FilterBank ***********************************/ FORM (FilterBank_drawFilters, L"FilterBank: Draw filters", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_drawRows (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range")); } END FORM (FilterBank_drawOneContour, L"FilterBank: Draw one contour", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") REAL (L"Height (dB)", L"40.0") OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_drawOneContour (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"Height")); } END FORM (FilterBank_drawContours, L"FilterBank: Draw contours", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_drawContours (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range")); } END FORM (FilterBank_drawFrequencyScales, L"FilterBank: Draw frequency scales", L"FilterBank: Draw frequency scales...") RADIO (L"Horizontal frequency scale", 1) RADIOBUTTON (L"Hertz") RADIOBUTTON (L"Bark") RADIOBUTTON (L"mel") REAL (L"left Horizontal frequency range", L"0.0") REAL (L"right Horizontal frequency range", L"0.0") RADIO (L"Vertical frequency scale", 1) RADIOBUTTON (L"Hertz") RADIOBUTTON (L"Bark") RADIOBUTTON (L"mel") REAL (L"left Vertical frequency range", L"0.0") REAL (L"right Vertical frequency range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (FilterBank); FilterBank_drawFrequencyScales (me, GRAPHICS, GET_INTEGER (L"Horizontal frequency scale"), GET_REAL (L"left Horizontal frequency range"), GET_REAL (L"right Horizontal frequency range"), GET_INTEGER (L"Vertical frequency scale"), GET_REAL (L"left Vertical frequency range"), GET_REAL (L"right Vertical frequency range"), GET_INTEGER (L"Garnish")); } END FORM (FilterBank_paintImage, L"FilterBank: Paint image", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_paintImage (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range")); } END FORM (FilterBank_paintContours, L"FilterBank: Paint contours", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_paintContours (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range")); } END FORM (FilterBank_paintCells, L"FilterBank: Paint cells", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_paintCells (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range")); } END FORM (FilterBank_paintSurface, L"FilterBank: Paint surface", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_paintSurface (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), 30, 45); } END FORM (FilterBank_getFrequencyInHertz, L"FilterBank: Get frequency in Hertz", L"FilterBank: Get frequency in Hertz...") REAL (L"Frequency", L"10.0") RADIO (L"Unit", 2) RADIOBUTTON (L"Hertz") RADIOBUTTON (L"Bark") RADIOBUTTON (L"mel") OK DO LOOP { iam (FilterBank); double f = FilterBank_getFrequencyInHertz (me, GET_REAL (L"Frequency"), GET_INTEGER (L"Unit")); Melder_informationReal (f, L"Hertz"); } END FORM (FilterBank_getFrequencyInBark, L"FilterBank: Get frequency in Bark", L"FilterBank: Get frequency in Bark...") REAL (L"Frequency", L"93.17") RADIO (L"Unit", 1) RADIOBUTTON (L"Hertz") RADIOBUTTON (L"Bark") RADIOBUTTON (L"mel") OK DO LOOP { iam (FilterBank); double f = FilterBank_getFrequencyInBark (me, GET_REAL (L"Frequency"), GET_INTEGER (L"Unit")); Melder_informationReal (f, L"Bark"); } END FORM (FilterBank_getFrequencyInMel, L"FilterBank: Get frequency in mel", L"FilterBank: Get frequency in mel...") REAL (L"Frequency", L"1000.0") RADIO (L"Unit", 1) RADIOBUTTON (L"Hertz") RADIOBUTTON (L"Bark") RADIOBUTTON (L"mel") OK DO LOOP { iam (FilterBank); double f = FilterBank_getFrequencyInMel (me, GET_REAL (L"Frequency"), GET_INTEGER (L"Unit")); Melder_informationReal (f, L"mel"); } END FORM (FilterBank_equalizeIntensities, L"FilterBank: Equalize intensities", L"") REAL (L"Intensity (dB)", L"80.0") OK DO LOOP { iam (FilterBank); FilterBank_equalizeIntensities (me, GET_REAL (L"Intensity")); praat_dataChanged (me); } END DIRECT (FilterBank_to_Matrix) LOOP { iam (FilterBank); praat_new (FilterBank_to_Matrix (me), my name); } END FORM (FilterBanks_crossCorrelate, L"FilterBanks: Cross-correlate", 0) RADIO_ENUM (L"Amplitude scaling", kSounds_convolve_scaling, DEFAULT) RADIO_ENUM (L"Signal outside time domain is...", kSounds_convolve_signalOutsideTimeDomain, DEFAULT) OK DO FilterBank f1 = 0, f2 = 0; LOOP { iam (FilterBank); (f1 ? f2 : f1) = me; } Melder_assert (f1 != 0 && f2 != 0); praat_new (FilterBanks_crossCorrelate (f1, f2, GET_ENUM (kSounds_convolve_scaling, L"Amplitude scaling"), GET_ENUM (kSounds_convolve_signalOutsideTimeDomain, L"Signal outside time domain is...")), f1 -> name, L"_", f2 -> name); END FORM (FilterBanks_convolve, L"FilterBanks: Convolve", 0) RADIO_ENUM (L"Amplitude scaling", kSounds_convolve_scaling, DEFAULT) RADIO_ENUM (L"Signal outside time domain is...", kSounds_convolve_signalOutsideTimeDomain, DEFAULT) OK DO FilterBank f1 = 0, f2 = 0; LOOP { iam (FilterBank); (f1 ? f2 : f1) = me; } Melder_assert (f1 != 0 && f2 != 0); praat_new (FilterBanks_convolve (f1, f2, GET_ENUM (kSounds_convolve_scaling, L"Amplitude scaling"), GET_ENUM (kSounds_convolve_signalOutsideTimeDomain, L"Signal outside time domain is...")), f1 -> name, L"_", f2 -> name); END DIRECT (FilterBank_to_Intensity) LOOP { iam (FilterBank); praat_new (FilterBank_to_Intensity (me), my name); } END /*********** FormantFilter *******************************************/ DIRECT (FormantFilter_help) Melder_help (L"FormantFilter"); END FORM (FormantFilter_drawFilterFunctions, L"FormantFilter: Draw filter functions", L"FilterBank: Draw filter functions...") INTEGER (L"left Filter range", L"0") INTEGER (L"right Filter range", L"0") POSITIVE (L"Bandwidth (Hz)", L"100.0") RADIO (L"Frequency scale", 1) RADIOBUTTON (L"Hertz") RADIOBUTTON (L"Bark") RADIOBUTTON (L"mel") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") BOOLEAN (L"Amplitude scale in dB", 1) REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (FormantFilter); FormantFilter_drawFilterFunctions (me, GRAPHICS, GET_REAL (L"Bandwidth"), GET_INTEGER (L"Frequency scale"), GET_INTEGER (L"left Filter range"), GET_INTEGER (L"right Filter range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_INTEGER (L"Amplitude scale in dB"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), GET_INTEGER (L"Garnish")); } END FORM (FormantFilter_drawSpectrum, L"FormantFilter: Draw spectrum (slice)", L"FilterBank: Draw spectrum (slice)...") POSITIVE (L"Time (s)", L"0.1") REAL (L"left Frequency range (Hz)", L"0.0") REAL (L"right Frequency range (Hz)", L"0.0") REAL (L"left Amplitude range (dB)", L"0.0") REAL (L"right Amplitude range (dB)", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (FilterBank); FilterBank_drawTimeSlice (me, GRAPHICS, GET_REAL (L"Time"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), L"Hz", GET_INTEGER (L"Garnish")); } END /****************** FormantGrid *********************************/ FORM (old_FormantGrid_draw, L"FormantGrid: Draw", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0 (=all)") REAL (L"left Frequency range (Hz)", L"0.0") REAL (L"right Frequency range (Hz)", L"0.0 (=auto)") BOOLEAN (L"Bandwidths", false) BOOLEAN (L"Garnish", true) OK DO autoPraatPicture picture; LOOP { iam (FormantGrid); FormantGrid_draw (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_INTEGER (L"Bandwidths"), GET_INTEGER (L"Garnish"), L"lines and speckles"); } END FORM (FormantGrid_draw, L"FormantGrid: Draw", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0 (=all)") REAL (L"left Frequency range (Hz)", L"0.0") REAL (L"right Frequency range (Hz)", L"0.0 (=auto)") BOOLEAN (L"Bandwidths", false) BOOLEAN (L"Garnish", true) LABEL (L"", L"") OPTIONMENU (L"Drawing method", 1) OPTION (L"lines") OPTION (L"speckles") OPTION (L"lines and speckles") OK DO_ALTERNATIVE (old_FormantGrid_draw) autoPraatPicture picture; LOOP { iam (FormantGrid); FormantGrid_draw (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_INTEGER (L"Bandwidths"), GET_INTEGER (L"Garnish"), GET_STRING (L"Drawing method")); } END /****************** FunctionTerms *********************************/ FORM (FunctionTerms_draw, L"FunctionTerms: Draw", 0) REAL (L"Xmin", L"0.0") REAL (L"Xmax", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Extrapolate", 0) BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (FunctionTerms); FunctionTerms_draw (me, GRAPHICS, GET_REAL (L"Xmin"), GET_REAL (L"Xmax"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Extrapolate"), GET_INTEGER (L"Garnish")); } END FORM (FunctionTerms_drawBasisFunction, L"FunctionTerms: Draw basis function", 0) NATURAL (L"Index", L"1") REAL (L"Xmin", L"0.0") REAL (L"Xmax", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Extrapolate", 0) BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (FunctionTerms); FunctionTerms_drawBasisFunction (me, GRAPHICS, GET_INTEGER (L"Index"), GET_REAL (L"Xmin"), GET_REAL (L"Xmax"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Extrapolate"), GET_INTEGER (L"Garnish")); } END FORM (FunctionTerms_evaluate, L"FunctionTerms: Evaluate", 0) REAL (L"X", L"0.0") OK DO LOOP { iam (FunctionTerms); Melder_information (Melder_double (FunctionTerms_evaluate (me, GET_REAL (L"X")))); } END DIRECT (FunctionTerms_getNumberOfCoefficients) LOOP { iam (FunctionTerms); Melder_information (Melder_integer (my numberOfCoefficients)); } END FORM (FunctionTerms_getCoefficient, L"FunctionTerms: Get coefficient", 0) LABEL (L"", L"p(x) = c[1] + c[2] x + ... c[n+1] x^n") NATURAL (L"Index", L"1") OK DO long index = GET_INTEGER (L"Index"); LOOP { iam (FunctionTerms); if (index > my numberOfCoefficients) { Melder_throw ("Index too large."); } Melder_information (Melder_double (my coefficients[index])); } END DIRECT (FunctionTerms_getDegree) LOOP { iam (FunctionTerms); Melder_information (Melder_integer (FunctionTerms_getDegree (me))); } END FORM (FunctionTerms_getMaximum, L"FunctionTerms: Get maximum", L"Polynomial: Get maximum...") LABEL (L"", L"Interval") REAL (L"Xmin", L"0.0") REAL (L"Xmax", L"0.0") OK DO LOOP { iam (FunctionTerms); double x = FunctionTerms_getMaximum (me, GET_REAL (L"Xmin"), GET_REAL (L"Xmax")); Melder_information (Melder_double (x)); } END FORM (FunctionTerms_getMinimum, L"FunctionTerms: Get minimum", L"Polynomial: Get minimum...") LABEL (L"", L"Interval") REAL (L"Xmin", L"0.0") REAL (L"Xmax", L"0.0") OK DO LOOP { iam (FunctionTerms); double x = FunctionTerms_getMinimum (me, GET_REAL (L"Xmin"), GET_REAL (L"Xmax")); Melder_information (Melder_double (x)); } END FORM (FunctionTerms_getXOfMaximum, L"FunctionTerms: Get x of maximum", L"Polynomial: Get x of maximum...") LABEL (L"", L"Interval") REAL (L"Xmin", L"0.0") REAL (L"Xmax", L"0.0") OK DO LOOP { iam (FunctionTerms); double x = FunctionTerms_getXOfMaximum (me, GET_REAL (L"Xmin"), GET_REAL (L"Xmax")); Melder_information (Melder_double (x)); } END FORM (FunctionTerms_getXOfMinimum, L"FunctionTerms: Get x of minimum", L"Polynomial: Get x of minimum...") LABEL (L"", L"Interval") REAL (L"Xmin", L"0.0") REAL (L"Xmax", L"0.0") OK DO LOOP { iam (FunctionTerms); double x = FunctionTerms_getXOfMinimum (me, GET_REAL (L"Xmin"), GET_REAL (L"Xmax")); Melder_information (Melder_double (x)); } END FORM (FunctionTerms_setCoefficient, L"FunctionTerms: Set coefficient", 0) LABEL (L"", L"p(x) = c[1]F[0] + c[2]F[1] + ... c[n+1]F[n]") LABEL (L"", L"F[k] is of degree k") NATURAL (L"Index", L"1") REAL (L"Value", L"0.0") OK DO LOOP { iam (FunctionTerms); FunctionTerms_setCoefficient (me, GET_INTEGER (L"Index"), GET_REAL (L"Value")); } END FORM (FunctionTerms_setDomain, L"FunctionTerms: Set domain", 0) REAL (L"Xmin", L"0.0") REAL (L"Xmax", L"2.0") OK DO double xmin = GET_REAL (L"Xmin"), xmax = GET_REAL (L"Xmax"); LOOP { iam (FunctionTerms); if (xmax <= xmin) { Melder_throw ("Xmax must be larger than Xmin."); } FunctionTerms_setDomain (me, xmin, xmax); } END /***************** Intensity ***************************************************/ FORM (Intensity_to_TextGrid_detectSilences, L"Intensity: To TextGrid (silences)", L"Intensity: To TextGrid (silences)...") REAL (L"Silence threshold (dB)", L"-25.0") POSITIVE (L"Minimum silent interval duration (s)", L"0.1") POSITIVE (L"Minimum sounding interval duration (s)", L"0.05") WORD (L"Silent interval label", L"silent") WORD (L"Sounding interval label", L"sounding") OK DO LOOP { iam (Intensity); praat_new (Intensity_to_TextGrid_detectSilences (me, GET_REAL (L"Silence threshold"), GET_REAL (L"Minimum silent interval duration"), GET_REAL (L"Minimum sounding interval duration"), GET_STRING (L"Silent interval label"), GET_STRING (L"Sounding interval label")), my name); } END /***************** ISpline ***************************************************/ DIRECT (ISpline_help) Melder_help (L"ISpline"); END FORM (ISpline_create, L"Create ISpline", L"Create ISpline...") WORD (L"Name", L"ispline") LABEL (L"", L"Domain") REAL (L"Xmin", L"0") REAL (L"Xmax", L"1") LABEL (L"", L"ISpline(x) = c[1] I[1](x) + c[2] I[1](x) + ... c[n] I[n](x)") LABEL (L"", L"all I[k] are polynomials of degree \"Degree\"") LABEL (L"", L"Relation: numberOfCoefficients == numberOfInteriorKnots + degree") INTEGER (L"Degree", L"3") SENTENCE (L"Coefficients (c[k])", L"1.2 2.0 1.2 1.2 3.0 0.0") SENTENCE (L"Interior knots" , L"0.3 0.5 0.6") OK DO double xmin = GET_REAL (L"Xmin"), xmax = GET_REAL (L"Xmax"); long degree = GET_INTEGER (L"Degree"); if (xmax <= xmin) { Melder_throw ("Xmin must be smaller than Xmax."); } praat_new (ISpline_createFromStrings (xmin, xmax, degree, GET_STRING (L"Coefficients"), GET_STRING (L"Interior knots")), GET_STRING (L"Name")); END /******************* KlattTable *********************************/ DIRECT (KlattTable_help) Melder_help (L"KlattTable"); END DIRECT (KlattTable_createExample) praat_new (KlattTable_createExample (), L"example"); END FORM (KlattTable_to_Sound, L"KlattTable: To Sound", L"KlattTable: To Sound...") POSITIVE (L"Sampling frequency", L"16000") RADIO (L"Synthesis model", 1) RADIOBUTTON (L"Cascade") RADIOBUTTON (L"Parallel") NATURAL (L"Number of formants", L"5") POSITIVE (L"Frame duration (s)", L"0.005") REAL (L"Flutter percentage (%)", L"0.0") OPTIONMENU (L"Voicing source", 1) OPTION (L"Impulsive") OPTION (L"Natural") OPTIONMENU (L"Output type", 1) OPTION (L"Sound") OPTION (L"Voicing") OPTION (L"Aspiration") OPTION (L"Frication") OPTION (L"Cascade-glottal-output") OPTION (L"Parallel-glottal-output") OPTION (L"Bypass-output") OPTION (L"All-excitations") OK DO double flutter = GET_REAL (L"Flutter percentage"); int outputType = GET_INTEGER (L"Output type") - 1; if (flutter < 0 || flutter > 100) { Melder_throw ("Flutter must be between 0 and 100%."); } LOOP { iam (KlattTable); praat_new (KlattTable_to_Sound (me, GET_REAL (L"Sampling frequency"), GET_INTEGER (L"Synthesis model"), GET_INTEGER (L"Number of formants"), GET_REAL (L"Frame duration"), GET_INTEGER (L"Voicing source"), GET_REAL (L"Flutter percentage"), outputType), my name); } END FORM (KlattTable_to_KlattGrid, L"KlattTable: To KlattGrid", 0) POSITIVE (L"Frame duration (s)", L"0.002") OK DO LOOP { iam (KlattTable); praat_new (KlattTable_to_KlattGrid (me, GET_REAL (L"Frame duration")), my name); } END DIRECT (KlattTable_to_Table) LOOP { iam (KlattTable); praat_new (KlattTable_to_Table (me), my name); } END DIRECT (Table_to_KlattTable) LOOP { iam (Table); praat_new (Table_to_KlattTable (me), my name); } END FORM (Table_getMedianAbsoluteDeviation, L"Table: Get median absolute deviation", L"Table: Get median absolute deviation...") SENTENCE (L"Column label", L"") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); double mad = Table_getMedianAbsoluteDeviation (me, icol); Melder_information (Melder_double (mad)); } END /******************* LegendreSeries *********************************/ FORM (LegendreSeries_create, L"Create LegendreSeries", L"Create LegendreSeries...") WORD (L"Name", L"ls") LABEL (L"", L"Domain") REAL (L"Xmin", L"-1") REAL (L"Xmax", L"1") LABEL (L"", L"LegendreSeries(x) = c[1] P[0](x) + c[2] P[1](x) + ... c[n+1] P[n](x)") LABEL (L"", L"P[k] is a Legendre polynomial of degree k") SENTENCE (L"Coefficients", L"0 0 1.0") OK DO double xmin = GET_REAL (L"Xmin"), xmax = GET_REAL (L"Xmax"); if (xmin >= xmax) { Melder_throw ("Xmin must be smaller than Xmax."); } praat_new (LegendreSeries_createFromString (xmin, xmax, GET_STRING (L"Coefficients")), GET_STRING (L"Name")); END DIRECT (LegendreSeries_help) Melder_help (L"LegendreSeries"); END DIRECT (LegendreSeries_to_Polynomial) LOOP { iam (LegendreSeries); praat_new (LegendreSeries_to_Polynomial (me), my name); } END /********************* LongSound **************************************/ FORM_READ (LongSounds_appendToExistingSoundFile, L"LongSound: Append to existing sound file", 0, false) autoCollection set = praat_getSelectedObjects (); LongSounds_appendToExistingSoundFile (set.peek(), file); END FORM_WRITE (LongSounds_writeToStereoAiffFile, L"LongSound: Save as AIFF file", 0, L"aiff") LongSound s1 = 0, s2 = 0; LOOP { iam (LongSound); (s1 ? s2 : s1) = me; } Melder_assert (s1 != 0 && s2 != 0); LongSounds_writeToStereoAudioFile16 (s1, s2, Melder_AIFF, file); END FORM_WRITE (LongSounds_writeToStereoAifcFile, L"LongSound: Save as AIFC file", 0, L"aifc") LongSound s1 = 0, s2 = 0; LOOP { iam (LongSound); (s1 ? s2 : s1) = me; } Melder_assert (s1 != 0 && s2 != 0); LongSounds_writeToStereoAudioFile16 (s1, s2, Melder_AIFC, file); END FORM_WRITE (LongSounds_writeToStereoWavFile, L"LongSound: Save as WAV file", 0, L"wav") LongSound s1 = 0, s2 = 0; LOOP { iam (LongSound); (s1 ? s2 : s1) = me; } Melder_assert (s1 != 0 && s2 != 0); LongSounds_writeToStereoAudioFile16 (s1, s2, Melder_WAV, file); END FORM_WRITE (LongSounds_writeToStereoNextSunFile, L"LongSound: Save as NeXT/Sun file", 0, L"au") LongSound s1 = 0, s2 = 0; LOOP { iam (LongSound); (s1 ? s2 : s1) = me; } Melder_assert (s1 != 0 && s2 != 0); LongSounds_writeToStereoAudioFile16 (s1, s2, Melder_NEXT_SUN, file); END FORM_WRITE (LongSounds_writeToStereoNistFile, L"LongSound: Save as NIST file", 0, L"nist") LongSound s1 = 0, s2 = 0; LOOP { iam (LongSound); (s1 ? s2 : s1) = me; } Melder_assert (s1 != 0 && s2 != 0); LongSounds_writeToStereoAudioFile16 (s1, s2, Melder_NIST, file); END /******************* Matrix **************************************************/ FORM (Matrix_drawAsSquares, L"Matrix: Draw as squares", L"Matrix: Draw as squares...") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_drawAsSquares (me, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); } END FORM (Matrix_drawDistribution, L"Matrix: Draw distribution", L"Matrix: Draw distribution...") LABEL (L"", L"Selection of (part of) Matrix") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") LABEL (L"", L"Selection of Matrix values") REAL (L"Minimum value", L"0.0") REAL (L"Maximum value", L"0.0") LABEL (L"", L"Display of the distribution") NATURAL (L"Number of bins", L"10") REAL (L"Minimum frequency", L"0.0") REAL (L"Maximum frequency", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_drawDistribution (me, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Minimum value"), GET_REAL (L"Maximum value"), GET_INTEGER (L"Number of bins"), GET_REAL (L"Minimum frequency"), GET_REAL (L"Maximum frequency"), 0, GET_INTEGER (L"Garnish")); } END FORM (Matrix_drawCumulativeDistribution, L"Matrix: Draw cumulative distribution", L"") LABEL (L"", L"Selection of (part of) Matrix") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") LABEL (L"", L"Selection of Matrix values") REAL (L"Minimum value", L"0.0") REAL (L"Maximum value", L"0.0") LABEL (L"", L"Display of the distribution") NATURAL (L"Number of bins", L"10") REAL (L"Minimum", L"0.0") REAL (L"Maximum", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Matrix); Matrix_drawDistribution (me, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Minimum value"), GET_REAL (L"Maximum value"), GET_INTEGER (L"Number of bins"), GET_REAL (L"Minimum"), GET_REAL (L"Maximum"), 1, GET_INTEGER (L"Garnish")); } END FORM (Matrix_scale, L"Matrix: Scale", 0) LABEL (L"", L"self[row, col] := self[row, col] / `Scale factor'") RADIO (L"Scale factor", 1) RADIOBUTTON (L"Extremum in matrix") RADIOBUTTON (L"Extremum in each row") RADIOBUTTON (L"Extremum in each column") OK DO int scale = GET_INTEGER (L"Scale factor"); if (scale < 1 || scale > 4) { Melder_throw ("Scale must be in (0,4) interval."); } autoPraatPicture picture; LOOP { iam (Matrix); Matrix_scale (me, scale); praat_dataChanged (me); } END DIRECT (Matrix_transpose) LOOP { iam (Matrix); praat_new (Matrix_transpose (me), my name, L"_transposed"); } END FORM (Matrix_solveEquation, L"Matrix: Solve equation", L"Matrix: Solve equation...") REAL (L"Tolerance", L"1.19e-7") OK DO LOOP { iam (Matrix); praat_new (Matrix_solveEquation (me, GET_REAL (L"Tolerance")), Thing_getName (me), L"_solution"); } END DIRECT (Matrix_Categories_to_TableOfReal) Matrix me = FIRST (Matrix); Categories cat = FIRST (Categories); praat_new (Matrix_and_Categories_to_TableOfReal (me, cat), my name, L"_", cat->name); END FORM (Matrix_scatterPlot, L"Matrix: Scatter plot", 0) NATURAL (L"Column for X-axis", L"1") NATURAL (L"Column for Y-axis", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") POSITIVE (L"Mark size (mm)", L"1.0") SENTENCE (L"Mark string (+xo.)", L"+") BOOLEAN (L"Garnish", 1) OK DO long x = GET_INTEGER (L"Column for X-axis"); long y = GET_INTEGER (L"Column for Y-axis"); if (x == 0 || y == 0) { Melder_throw ("X and Y component must differ from 0."); } LOOP { iam (Matrix); Matrix_scatterPlot (me, GRAPHICS, x, y, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); } END DIRECT (Matrix_to_Activation) LOOP { iam (Matrix); praat_new (Matrix_to_Activation (me), my name); } END FORM (Matrices_to_DTW, L"Matrices: To DTW", L"Matrix: To DTW...") LABEL (L"", L"Distance between cepstral coefficients") REAL (L"Distance metric", L"2.0") DTW_constraints_addCommonFields (dia); OK DO int begin, end, slope; DTW_constraints_getCommonFields (dia, &begin, &end, &slope); Matrix m1 = 0, m2 = 0; LOOP { iam (Matrix); (m1 ? m2 : m1) = me; } Melder_assert (m1 && m2); praat_new (Matrices_to_DTW (m1, m2, begin, end, slope, GET_REAL (L"Distance metric")), m1->name, L"_", m2->name); END FORM (Matrix_to_Pattern, L"Matrix: To Pattern", 0) NATURAL (L"Join", L"1") OK DO LOOP { iam (Matrix); praat_new (Matrix_to_Pattern (me, GET_INTEGER (L"Join")), my name); } END /***** MATRIXFT *************/ DIRECT (Matrixft_getHighestFrequency) LOOP { iam (Matrix); Melder_information (Melder_double (my ymax)); } END DIRECT (Matrixft_getLowestFrequency) LOOP { iam (Matrix); Melder_information (Melder_double (my ymin)); } END DIRECT (Matrixft_getNumberOfFrequencies) LOOP { iam (Matrix); Melder_information (Melder_double (my ny)); } END DIRECT (Matrixft_getFrequencyDistance) LOOP { iam (Matrix); Melder_information (Melder_double (my dy)); } END FORM (Matrixft_getFrequencyOfRow, L"Get frequency of row", 0) NATURAL (L"Row number", L"1") OK DO LOOP { iam (Matrix); Melder_information (Melder_double (Matrix_rowToY (me, GET_INTEGER (L"Row number")))); } END FORM (Matrixft_getXofColumn, L"Get time of column", 0) NATURAL (L"Column number", L"1") OK DO LOOP { iam (Matrix); Melder_information (Melder_double (Matrix_columnToX (me, GET_INTEGER (L"Column number")))); } END FORM (Matrixft_getValueInCell, L"Get value in cell", 0) POSITIVE (L"Time (s)", L"0.5") POSITIVE (L"Frequency", L"1") OK DO double t = GET_REAL (L"Time"); double f = GET_REAL (L"Frequency"); LOOP { iam (Matrix); if (f < my ymin || f > my ymax) { Melder_throw ("Frequency out of range."); } if (t < my xmin || t > my xmax) { Melder_throw ("Time out of range."); } long col = Matrix_xToNearestColumn (me, t); if (col < 1) { col = 1; } if (col > my nx) { col = my nx; } long row = Matrix_yToNearestRow (me, f); if (row < 1) { row = 1; } if (row > my ny) { row = my ny; } double ta = Matrix_columnToX (me, col); double fa = Matrix_rowToY (me, row); Melder_information (Melder_single (my z[row][col]), L" (delta t: ", Melder_double (ta - t), L" f: ", Melder_double (fa - f), L")"); } END /**************** MelFilter *******************************************/ DIRECT (MelFilter_help) Melder_help (L"MelFilter"); END FORM (MelFilter_drawFilterFunctions, L"MelFilter: Draw filter functions", L"FilterBank: Draw filter functions...") INTEGER (L"left Filter range", L"0") INTEGER (L"right Filter range", L"0") RADIO (L"Frequency scale", 1) RADIOBUTTON (L"Hertz") RADIOBUTTON (L"Bark") RADIOBUTTON (L"Mel") REAL (L"left Frequency range", L"0.0") REAL (L"right Frequency range", L"0.0") BOOLEAN (L"Amplitude scale in dB", 0) REAL (L"left Amplitude range", L"0.0") REAL (L"right Amplitude range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (MelFilter); MelFilter_drawFilterFunctions (me, GRAPHICS, GET_INTEGER (L"Frequency scale"), GET_INTEGER (L"left Filter range"), GET_INTEGER (L"right Filter range"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_INTEGER (L"Amplitude scale in dB"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), GET_INTEGER (L"Garnish")); } END FORM (MelFilter_drawSpectrum, L"MelFilter: Draw spectrum (slice)", L"FilterBank: Draw spectrum (slice)...") POSITIVE (L"Time (s)", L"0.1") REAL (L"left Frequency range (mel)", L"0.0") REAL (L"right Frequency range (mel)", L"0.0") REAL (L"left Amplitude range (dB)", L"0.0") REAL (L"right Amplitude range (dB)", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (FilterBank); FilterBank_drawTimeSlice (me, GRAPHICS, GET_REAL (L"Time"), GET_REAL (L"left Frequency range"), GET_REAL (L"right Frequency range"), GET_REAL (L"left Amplitude range"), GET_REAL (L"right Amplitude range"), L"Mels", GET_INTEGER (L"Garnish")); } END FORM (MelFilter_to_MFCC, L"MelFilter: To MFCC", L"MelFilter: To MFCC...") NATURAL (L"Number of coefficients", L"12") OK DO LOOP { iam (MelFilter); praat_new (MelFilter_to_MFCC (me, GET_INTEGER (L"Number of coefficients")), my name); } END /**************** MFCC *******************************************/ DIRECT (MFCC_help) Melder_help (L"MFCC"); END FORM (MFCC_to_MelFilter, L"MFCC: To MelFilter", L"MFCC: To MelFilter...") INTEGER (L"From coefficient", L"0") INTEGER (L"To coefficient", L"0") POSITIVE (L"Position of first filter (mel)", L"100.0") POSITIVE (L"Distance between filters (mel)", L"100.0") OK DO LOOP { iam (MFCC); praat_new (MFCC_to_MelFilter (me, GET_INTEGER (L"From coefficient"), GET_INTEGER (L"To coefficient"), GET_REAL (L"Position of first filter"), GET_REAL (L"Distance between filters")), my name); } END FORM (MFCC_to_TableOfReal, L"MFCC: To TableOfReal", L"MFCC: To TableOfReal...") BOOLEAN (L"Include energy", 0) OK DO LOOP { iam (MFCC); praat_new (MFCC_to_TableOfReal (me, GET_INTEGER (L"Include energy")), my name); } END FORM (MFCCs_crossCorrelate, L"MFCC & MFCC: Cross-correlate", 0) RADIO_ENUM (L"Amplitude scaling", kSounds_convolve_scaling, DEFAULT) RADIO_ENUM (L"Signal outside time domain is...", kSounds_convolve_signalOutsideTimeDomain, DEFAULT) OK DO MFCC m1 = 0, m2 = 0; LOOP { iam (MFCC); (m1 ? m2 : m1) = me; } Melder_assert (m1 && m2); praat_new (MFCCs_crossCorrelate (m1, m2, GET_ENUM (kSounds_convolve_scaling, L"Amplitude scaling"), GET_ENUM (kSounds_convolve_signalOutsideTimeDomain, L"Signal outside time domain is...")), m1 -> name, L"_", m2 -> name); END FORM (MFCCs_convolve, L"MFCC & MFCC: Convolve", 0) RADIO_ENUM (L"Amplitude scaling", kSounds_convolve_scaling, DEFAULT) RADIO_ENUM (L"Signal outside time domain is...", kSounds_convolve_signalOutsideTimeDomain, DEFAULT) OK DO MFCC m1 = 0, m2 = 0; LOOP { iam (MFCC); (m1 ? m2 : m1) = me; } Melder_assert (m1 && m2); praat_new (MFCCs_convolve (m1, m2, GET_ENUM (kSounds_convolve_scaling, L"Amplitude scaling"), GET_ENUM (kSounds_convolve_signalOutsideTimeDomain, L"Signal outside time domain is...")), m1 -> name, L"_", m2 -> name); END DIRECT (MFCC_to_Sound) LOOP { iam (MFCC); praat_new (MFCC_to_Sound (me), my name); } END /**************** MSpline *******************************************/ FORM (MSpline_create, L"Create MSpline", L"Create MSpline...") WORD (L"Name", L"mspline") LABEL (L"", L"Domain") REAL (L"Xmin", L"0") REAL (L"Xmax", L"1") LABEL (L"", L"MSpline(x) = c[1] M[1](x) + c[2] M[1](x) + ... c[n] M[n](x)") LABEL (L"", L"all M[k] are polynomials of degree \"Degree\"") LABEL (L"", L"Relation: numberOfCoefficients == numberOfInteriorKnots + degree + 1") INTEGER (L"Degree", L"2") SENTENCE (L"Coefficients (c[k])", L"1.2 2.0 1.2 1.2 3.0 0.0") SENTENCE (L"Interior knots" , L"0.3 0.5 0.6") OK DO double xmin = GET_REAL (L"Xmin"), xmax = GET_REAL (L"Xmax"); long degree = GET_INTEGER (L"Degree"); if (xmin >= xmax) { Melder_throw ("Xmin must be smaller than Xmax."); } praat_new (MSpline_createFromStrings (xmin, xmax, degree, GET_STRING (L"Coefficients"), GET_STRING (L"Interior knots")), GET_STRING (L"Name")); END DIRECT (MSpline_help) Melder_help (L"MSpline"); END /********************** Pattern *******************************************/ DIRECT (Pattern_and_Categories_to_Discriminant) Pattern me = FIRST (Pattern); Categories cat = FIRST (Categories); praat_new (Pattern_and_Categories_to_Discriminant (me, cat), Thing_getName (me), L"_", Thing_getName (cat)); END FORM (Pattern_draw, L"Pattern: Draw", 0) NATURAL (L"Pattern number", L"1") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Pattern); Pattern_draw (me, GRAPHICS, GET_INTEGER (L"Pattern number"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); } END FORM (Pattern_formula, L"Pattern: Formula", 0) LABEL (L"label", L" y := 1; for row := 1 to nrow do { x := 1; " "for col := 1 to ncol do { self [row, col] := `formula' ; x := x + 1 } " "y := y + 1 }}") TEXTFIELD (L"formula", L"self") OK DO praat_Fon_formula (dia, interpreter); END FORM (Pattern_setValue, L"Pattern: Set value", L"Pattern: Set value...") NATURAL (L"Row number", L"1") NATURAL (L"Column number", L"1") REAL (L"New value", L"0.0") OK DO LOOP { iam (Pattern); long row = GET_INTEGER (L"Row number"), column = GET_INTEGER (L"Column number"); if (row > my ny) { Melder_throw ("Row number must not be greater than number of rows."); } if (column > my nx) { Melder_throw ("Column number must not be greater than number of columns."); } my z [row] [column] = GET_REAL (L"New value"); praat_dataChanged (me); } END DIRECT (Pattern_to_Matrix) LOOP { iam (Pattern); praat_new (Pattern_to_Matrix (me), my name); } END /******************* PCA ******************************/ DIRECT (PCA_help) Melder_help (L"PCA"); END DIRECT (hint_PCA_and_TableOfReal_to_Configuration) Melder_information (L"You can get principal components by selecting a PCA and a TableOfReal\n" "together and choosing \"To Configuration...\"."); END DIRECT (hint_PCA_and_Covariance_Project) Melder_information (L"You can get a new Covariance object rotated to the directions of the direction vectors\n" " in the PCA object by selecting a PCA and a Covariance object together."); END DIRECT (hint_PCA_and_Configuration_to_TableOfReal_reconstruct) Melder_information (L"You can reconstruct the original TableOfReal as well as possible from\n" " the principal components in the Configuration and the direction vectors in the PCA object."); END FORM (PCA_and_TableOfReal_getFractionVariance, L"PCA & TableOfReal: Get fraction variance", L"PCA & TableOfReal: Get fraction variance...") NATURAL (L"left Principal component range", L"1") NATURAL (L"right Principal component range", L"1") OK DO PCA me = FIRST (PCA); TableOfReal tab = FIRST (TableOfReal); Melder_information (Melder_double (PCA_and_TableOfReal_getFractionVariance (me, tab, GET_INTEGER (L"left Principal component range"), GET_INTEGER (L"right Principal component range")))); END DIRECT (PCA_and_Configuration_to_TableOfReal_reconstruct) PCA me = FIRST (PCA); Configuration conf = FIRST (Configuration); praat_new (PCA_and_Configuration_to_TableOfReal_reconstruct (me, conf), my name, L"_", conf->name); END FORM (PCA_and_TableOfReal_to_Configuration, L"PCA & TableOfReal: To Configuration", L"PCA & TableOfReal: To Configuration...") INTEGER (L"Number of dimensions", L"0 (=all)") OK DO long dimension = GET_INTEGER (L"Number of dimensions"); if (dimension < 0) { Melder_throw ("Number of dimensions must be greater equal zero."); } PCA me = FIRST (PCA); TableOfReal tab = FIRST_GENERIC (TableOfReal); praat_new (PCA_and_TableOfReal_to_Configuration (me, tab, dimension), my name, L"_", tab->name); END FORM (PCA_and_TableOfReal_to_TableOfReal_zscores, L"PCA & TableOfReal: To TableOfReal (z-scores)", L"PCA & TableOfReal: To TableOfReal (z-scores)...") INTEGER (L"Number of dimensions", L"0 (=all)") OK DO long dimension = GET_INTEGER (L"Number of dimensions"); if (dimension < 0) { Melder_throw ("Number of dimensions must be greater than or equal to zero."); } PCA me = FIRST (PCA); TableOfReal thee = FIRST_GENERIC (TableOfReal); praat_new (PCA_and_TableOfReal_to_TableOfReal_zscores (me, thee, dimension), my name, L"_", thy name, L"_zscores"); END FORM (PCA_getCentroidElement, L"PCA: Get centroid element...", 0) NATURAL (L"Number", L"1") OK DO long number = GET_INTEGER (L"Number"); LOOP { iam (PCA); if (number > my dimension) { Melder_throw ("Number may not be larger than ", my dimension, "."); } Melder_information (Melder_double (my centroid[number]), L" (element ", Melder_integer (number), L")"); } END FORM (PCA_getEqualityOfEigenvalues, L"PCA: Get equality of eigenvalues", L"PCA: Get equality of eigenvalues...") INTEGER (L"left Eigenvalue range", L"0") INTEGER (L"right Eigenvalue range", L"0") BOOLEAN (L"Conservative test", 0) OK DO LOOP { iam (PCA); long ndf; double p, chisq; PCA_getEqualityOfEigenvalues (me, GET_INTEGER (L"left Eigenvalue range"), GET_INTEGER (L"right Eigenvalue range"), GET_INTEGER (L"Conservative test"), &p, &chisq, &ndf); Melder_information (Melder_double (p), L" (=probability, based on chisq = ", Melder_double (chisq), L"and ndf = ", Melder_integer (ndf)); } END FORM (PCA_getNumberOfComponentsVAF, L"PCA: Get number of components (VAF)", L"PCA: Get number of components (VAF)...") POSITIVE (L"Variance fraction (0-1)", L"0.95") OK DO double f = GET_REAL (L"Variance fraction"); LOOP { iam (Eigen); if (f <= 0 || f > 1) { Melder_throw ("The variance fraction must be in interval (0-1)."); } Melder_information (Melder_integer (Eigen_getDimensionOfFraction (me, f))); } END FORM (PCA_getFractionVAF, L"PCA: Get fraction variance accounted for", L"PCA: Get fraction variance accounted for...") NATURAL (L"left Principal component range", L"1") NATURAL (L"right Principal component range", L"1") OK DO long from = GET_INTEGER (L"left Principal component range"); long to = GET_INTEGER (L"right Principal component range"); if (from > to) { Melder_throw ("The second component must be greater than or equal to the first component."); } LOOP { iam (Eigen); if (from > to) { Melder_throw ("The second component must be greater than or equal to the first component."); } Melder_information (Melder_double (Eigen_getCumulativeContributionOfComponents (me, from, to))); } END FORM (PCA_invertEigenvector, L"PCA: Invert eigenvector", 0) NATURAL (L"Eigenvector number", L"1") OK DO LOOP { iam (Eigen); Eigen_invertEigenvector (me, GET_INTEGER (L"Eigenvector number")); praat_dataChanged (me); } END FORM (PCA_to_TableOfReal_reconstruct1, L"PCA: To TableOfReal (reconstruct)", L"PCA: To TableOfReal (reconstruct 1)...") SENTENCE (L"Coefficients", L"1.0 1.0") OK DO LOOP { iam (PCA); praat_new (PCA_to_TableOfReal_reconstruct1 (me, GET_STRING (L"Coefficients")), my name, L"_reconstructed"); } END FORM (PCAs_to_Procrustes, L"PCA & PCA: To Procrustes", L"PCA & PCA: To Procrustes...") NATURAL (L"left Eigenvector range", L"1") NATURAL (L"right Eigenvector range", L"2") OK DO long from = GET_INTEGER (L"left Eigenvector range"); long to = GET_INTEGER (L"right Eigenvector range"); PCA p1 = 0, p2 = 0; LOOP { iam (PCA); (p1 ? p2 : p1) = me; } Melder_assert (p1 && p2); praat_new (Eigens_to_Procrustes (p1, p2, from, to), Thing_getName (p1), L"_", Thing_getName (p2)); END DIRECT (PCAs_getAngleBetweenPc1Pc2Plane_degrees) PCA p1 = 0, p2 = 0; LOOP { iam (PCA); (p1 ? p2 : p1) = me; } Melder_assert (p1 && p2); Melder_information (Melder_double (Eigens_getAngleBetweenEigenplanes_degrees (p1, p2)), L" degrees (=angle of intersection between the two pc1-pc2 eigenplanes)"); END /******************* Permutation **************************************/ DIRECT (Permutation_help) Melder_help (L"Permutation"); END FORM (Permutation_create, L"Create Permutation", L"Create Permutation...") WORD (L"Name", L"p") NATURAL (L"Number of elements", L"10") BOOLEAN (L"Identity Permutation", 1) OK DO Permutation p = Permutation_create (GET_INTEGER (L"Number of elements")); int identity = GET_INTEGER (L"Identity Permutation"); if (! identity) { Permutation_permuteRandomly_inline (p, 0, 0); } praat_new (p, GET_STRING (L"Name")); END DIRECT (Permutation_getNumberOfElements) LOOP { iam (Permutation); Melder_information (Melder_integer (my numberOfElements)); } END FORM (Permutation_getValueAtIndex, L"Permutation: Get value", L"Permutation: Get value...") NATURAL (L"Index", L"1") OK DO long index = GET_INTEGER (L"Index"); LOOP { iam (Permutation); Melder_information (Melder_integer (Permutation_getValueAtIndex (me, index)), L" (value, at index = ", Melder_integer (index), L")"); } END FORM (Permutation_getIndexAtValue, L"Permutation: Get index", L"Permutation: Get index...") NATURAL (L"Value", L"1") OK DO long value = GET_INTEGER (L"Value"); LOOP { iam (Permutation); Melder_information (Melder_integer (Permutation_getIndexAtValue (me, value)), L" (index, at value = ", Melder_integer (value), L")"); } END DIRECT (Permutation_sort) LOOP { iam (Permutation); Permutation_sort (me); praat_dataChanged (me); } END FORM (Permutation_swapBlocks, L"Permutation: Swap blocks", L"Permutation: Swap blocks...") NATURAL (L"From index", L"1") NATURAL (L"To index", L"2") NATURAL (L"Block size", L"1") OK DO LOOP { iam (Permutation); Permutation_swapBlocks (me, GET_INTEGER (L"From index"), GET_INTEGER (L"To index"), GET_INTEGER (L"Block size")); praat_dataChanged (me); } END FORM (Permutation_swapPositions, L"Permutation: Swap positions", L"Permutation: Swap positions...") NATURAL (L"First index", L"1") NATURAL (L"Second index", L"2") OK DO LOOP { iam (Permutation); Permutation_swapPositions (me, GET_INTEGER (L"First index"), GET_INTEGER (L"Second index")); praat_dataChanged (me); } END FORM (Permutation_swapNumbers, L"Permutation: Swap numbers", L"Permutation: Swap numbers...") NATURAL (L"First number", L"1") NATURAL (L"Second number", L"2") OK DO LOOP { iam (Permutation); Permutation_swapNumbers (me, GET_INTEGER (L"First number"), GET_INTEGER (L"Second number")); praat_dataChanged (me); } END FORM (Permutation_swapOneFromRange, L"Permutation: Swap one from range", L"Permutation: Swap one from range...") LABEL (L"", L"A randomly chosen element from ") INTEGER (L"left Index range", L"0") INTEGER (L"right Index range", L"0") LABEL (L"", L"is swapped with the element at") NATURAL (L"Index", L"1") BOOLEAN (L"Forbid same", 1) OK DO LOOP { iam (Permutation); Permutation_swapOneFromRange (me, GET_INTEGER (L"left Index range"), GET_INTEGER (L"right Index range"), GET_INTEGER (L"Index"), GET_INTEGER (L"Forbid same")); praat_dataChanged (me); } END FORM (Permutation_permuteRandomly, L"Permutation: Permute randomly", L"Permutation: Permute randomly...") INTEGER (L"left Index range", L"0") INTEGER (L"right Index range", L"0") OK DO LOOP { iam (Permutation); praat_new (Permutation_permuteRandomly (me, GET_INTEGER (L"left Index range"), GET_INTEGER (L"right Index range")), Thing_getName (me), L"_rdm"); } END FORM (Permutation_rotate, L"Permutation: Rotate", L"Permutation: Rotate...") INTEGER (L"left Index range", L"0") INTEGER (L"right Index range", L"0") INTEGER (L"Step size", L"1") OK DO long step = GET_INTEGER (L"Step size"); LOOP { iam (Permutation); praat_new (Permutation_rotate (me, GET_INTEGER (L"left Index range"), GET_INTEGER (L"right Index range"), step), Thing_getName (me), L"_rot", Melder_integer (step)); } END FORM (Permutation_reverse, L"Permutation: Reverse", L"Permutation: Reverse...") INTEGER (L"left Index range", L"0") INTEGER (L"right Index range", L"0") OK DO LOOP { iam (Permutation); praat_new (Permutation_reverse (me, GET_INTEGER (L"left Index range"), GET_INTEGER (L"right Index range")), Thing_getName (me), L"_rev"); } END FORM (Permutation_permuteBlocksRandomly, L"Permutation: Permute blocks randomly", L"Permutation: Permute randomly (blocks)...") INTEGER (L"left Index range", L"0") INTEGER (L"right Index range", L"0") NATURAL (L"Block size", L"12") BOOLEAN (L"Permute within blocks", 1) BOOLEAN (L"No doublets", 0) OK DO long blocksize = GET_INTEGER (L"Block size"); LOOP { iam (Permutation); praat_new (Permutation_permuteBlocksRandomly (me, GET_INTEGER (L"left Index range"), GET_INTEGER (L"right Index range"), blocksize, GET_INTEGER (L"Permute within blocks"), GET_INTEGER (L"No doublets")), Thing_getName (me), L"_pbr", Melder_integer (blocksize)); } END FORM (Permutation_interleave, L"Permutation: Interleave", L"Permutation: Interleave...") INTEGER (L"left Index range", L"0") INTEGER (L"right Index range", L"0") NATURAL (L"Block size", L"12") INTEGER (L"Offset", L"0") OK DO LOOP { iam (Permutation); praat_new (Permutation_interleave (me, GET_INTEGER (L"left Index range"), GET_INTEGER (L"right Index range"), GET_INTEGER (L"Block size"), GET_INTEGER (L"Offset")), Thing_getName (me), L"_itl"); } END DIRECT (Permutation_invert) LOOP { iam (Permutation); praat_new (Permutation_invert (me), Thing_getName (me), L"_inv"); } END DIRECT (Permutations_multiply) autoCollection set = praat_getSelectedObjects (); praat_new (Permutations_multiply (set.peek()), L"mul_", Melder_integer (set -> size)); END DIRECT (Permutations_next) LOOP { iam (Permutation); Permutation_next_inline (me); praat_dataChanged (me); } END DIRECT (Permutations_previous) LOOP { iam (Permutation); Permutation_previous_inline (me); praat_dataChanged (me); } END FORM (Pitches_to_DTW, L"Pitches: To DTW", L"Pitches: To DTW...") REAL (L"Voiced-unvoiced costs", L"24.0") REAL (L"Time costs weight", L"10.0") DTW_constraints_addCommonFields (dia); OK DO int begin, end, slope; DTW_constraints_getCommonFields (dia, &begin, &end, &slope); Pitch p1 = 0, p2 = 0; LOOP { iam (Pitch); (p1 ? p2 : p1) = me; } Melder_assert (p1 && p2); praat_new (Pitches_to_DTW (p1, p2, GET_REAL (L"Voiced-unvoiced costs"), GET_REAL (L"Time costs weight"), begin, end, slope), L"dtw_", Thing_getName (p1), L"_", Thing_getName (p2)); END FORM (PitchTier_to_Pitch, L"PitchTier: To Pitch", L"PitchTier: To Pitch...") POSITIVE (L"Step size", L"0.02") POSITIVE (L"Pitch floor", L"60.0") POSITIVE (L"Pitch ceiling", L"400.0") OK DO LOOP { iam (PitchTier); praat_new (PitchTier_to_Pitch (me, GET_REAL (L"Step size"), GET_REAL (L"Pitch floor"), GET_REAL (L"Pitch ceiling")), my name); } END /******************* Polygon & Categories *************************************/ FORM (Polygon_createSimple, L"Create simple Polygon", L"Create simple Polygon...") WORD (L"Name", L"p") SENTENCE (L"Vertices as X-Y pairs", L"0.0 0.0 0.0 1.0 1.0 0.0") OK DO praat_new (Polygon_createSimple (GET_STRING (L"Vertices as X-Y pairs")), GET_STRING (L"Name")); END FORM (Polygon_createFromRandomVertices, L"", 0) WORD (L"Name", L"p") NATURAL (L"Number of vertices", L"10") REAL (L"left X range", L"0.0") REAL (L"right X range", L"1.0") REAL (L"left Y range", L"0.0") REAL (L"right Y range", L"1.0") OK DO praat_new (Polygon_createFromRandomVertices (GET_INTEGER (L"Number of vertices"), GET_REAL (L"left X range"), GET_REAL (L"right X range"), GET_REAL (L"left Y range"), GET_REAL (L"right Y range")), GET_STRING (L"Name")); END DIRECT (Polygon_getNumberOfPoints) LOOP { iam (Polygon); Melder_information (Melder_integer (my numberOfPoints)); } END FORM (Polygon_getPointX, L"Polygon: Get point (x)", 0) NATURAL (L"Point number", L"1") OK DO long point = GET_INTEGER (L"Point number"); LOOP { iam (Polygon); if (point > my numberOfPoints) { Melder_throw ("Point cannot be larger than ", my numberOfPoints, "."); } Melder_information (Melder_double (my x[point])); } END FORM (Polygon_getPointY, L"Polygon: Get point (y)", 0) NATURAL (L"Point number", L"1") OK DO long point = GET_INTEGER (L"Point number"); LOOP { iam (Polygon); if (point > my numberOfPoints) { Melder_throw ("Vertex cannot be larger than ", my numberOfPoints, "."); } Melder_information (Melder_double (my y[point])); } END FORM (Polygon_getLocationOfPoint, L"Get location of point", L"Polygon: Get location of point...") LABEL (L"", L"Point is (I)n, (O)ut, (E)dge or (V)ertex?") REAL (L"X", L"0.0") REAL (L"Y", L"0.0") REAL (L"Precision", L"1.64e-15") OK DO double eps = GET_REAL (L"Precision"); REQUIRE (eps >= 0, L"The precision cannot be negative.") LOOP { iam (Polygon); int loc = Polygon_getLocationOfPoint (me, GET_REAL (L"X"), GET_REAL (L"Y"), eps); Melder_information (loc == Polygon_INSIDE ? L"I" : loc == Polygon_OUTSIDE ? L"O" : loc == Polygon_EDGE ? L"E" : L"V"); } END FORM (Polygon_circularPermutation, L"Polygon: Circular permutation", 0) INTEGER (L"Shift", L"1") OK DO long shift = GET_INTEGER (L"Shift"); LOOP { iam (Polygon); praat_new (Polygon_circularPermutation (me, shift), my name, L"_", Melder_integer (shift)); } END DIRECT (Polygon_simplify) LOOP { iam (Polygon); praat_new (Polygon_simplify (me), my name, L"_s"); } END FORM (Polygon_translate, L"Polygon: Translate", L"Polygon: Translate...") REAL (L"X", L"0.0") REAL (L"Y", L"0.0") OK DO LOOP { iam (Polygon); Polygon_translate (me, GET_REAL (L"X"), GET_REAL (L"Y")); } END FORM (Polygon_rotate, L"Polygon: Rotate", L"Polygon: Rotate...") LABEL (L"", L"Rotate counterclockwise over the") REAL (L"Angle (degrees)", L"0.0") LABEL (L"", L"With respect to the point") REAL (L"X", L"0.0") REAL (L"Y", L"0.0") OK DO LOOP { iam (Polygon); Polygon_rotate (me, GET_REAL (L"Angle"), GET_REAL (L"X"), GET_REAL (L"Y")); praat_dataChanged (me); } END FORM (Polygon_scale, L"Polygon: Scale polygon", 0) REAL (L"X", L"0.0") REAL (L"Y", L"0.0") OK DO LOOP { iam (Polygon); Polygon_scale (me, GET_REAL (L"X"), GET_REAL (L"Y")); praat_dataChanged (me); } END FORM (Polygon_Categories_draw, L"Polygon & Categories: Draw", 0) REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO Polygon me = FIRST (Polygon); Categories cat = FIRST (Categories); Polygon_Categories_draw (me, cat, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); END DIRECT (Polygon_reverseX) LOOP { iam (Polygon); Polygon_reverseX (me); praat_dataChanged (me); } END DIRECT (Polygon_reverseY) LOOP { iam (Polygon); Polygon_reverseY (me); praat_dataChanged (me); } END /***************** Polynomial *******************/ DIRECT (Polynomial_help) Melder_help (L"Polynomial"); END FORM (Polynomial_create, L"Create Polynomial", L"Create Polynomial...") WORD (L"Name", L"p") LABEL (L"", L"Domain of polynomial") REAL (L"Xmin", L"-3") REAL (L"Xmax", L"4") LABEL (L"", L"p(x) = c[1] + c[2] x + ... c[n+1] x^n") SENTENCE (L"Coefficients", L"2.0 -1.0 -2.0 1.0") OK DO double xmin = GET_REAL (L"Xmin"), xmax = GET_REAL (L"Xmax"); if (xmin >= xmax) { Melder_throw ("Xmin must be smaller than Xmax."); } praat_new (Polynomial_createFromString (xmin, xmax, GET_STRING (L"Coefficients")), GET_STRING (L"Name")); END FORM (Polynomial_getArea, L"Polynomial: Get area", L"Polynomial: Get area...") LABEL (L"", L"Interval") REAL (L"Xmin", L"0.0") REAL (L"Xmax", L"0.0") OK DO LOOP { iam (Polynomial); double area = Polynomial_getArea (me, GET_REAL (L"Xmin"), GET_REAL (L"Xmax")); Melder_information (Melder_double (area)); } END DIRECT (Polynomial_getDerivative) LOOP { iam (Polynomial); praat_new (Polynomial_getDerivative (me), my name, L"_derivative"); } END DIRECT (Polynomial_getPrimitive) LOOP { iam (Polynomial); praat_new (Polynomial_getPrimitive (me), my name, L"_primitive"); } END FORM (Polynomial_scaleX, L"Polynomial: Scale x", L"Polynomial: Scale x...") LABEL (L"", L"New domain") REAL (L"Xmin", L"-1.0") REAL (L"Xmax", L"1.0") OK DO double xmin = GET_REAL (L"Xmin"), xmax = GET_REAL (L"Xmax"); if (xmin >= xmax) { Melder_throw ("Xmin must be smaller than Xmax."); } LOOP { iam (Polynomial); praat_new (Polynomial_scaleX (me, xmin, xmax), my name, L"_scaleX"); } END DIRECT (Polynomial_scaleCoefficients_monic) LOOP { iam (Polynomial); Polynomial_scaleCoefficients_monic (me); praat_dataChanged (me); } END DIRECT (Polynomial_to_Roots) LOOP { iam (Polynomial); praat_new (Polynomial_to_Roots (me), my name); } END FORM (Polynomial_evaluate_z, L"Polynomial: Get value (complex)", L"Polynomial: Get value (complex)...") REAL (L"Real part", L"0.0") REAL (L"Imaginary part", L"0.0") OK DO dcomplex p, z = dcomplex_create (GET_REAL (L"Real part"), GET_REAL (L"Imaginary part")); LOOP { iam (Polynomial); Polynomial_evaluate_z (me, &z, &p); Melder_information (Melder_double (p.re), L" + ", Melder_double (p.im), L" i"); } END FORM (Polynomial_to_Spectrum, L"Polynomial: To Spectrum", L"Polynomial: To Spectrum...") POSITIVE (L"Nyquist frequency (Hz)", L"5000.0") NATURAL (L"Number of frequencies (>1)", L"1025") OK DO long n = GET_INTEGER (L"Number of frequencies"); LOOP { iam (Polynomial); praat_new (Polynomial_to_Spectrum (me, GET_REAL (L"Nyquist frequency"), n, 1.0), my name); } END DIRECT (Polynomials_multiply) Polynomial p1 = 0, p2 = 0; LOOP { iam (Polynomial); (p1 ? p2 : p1) = me; } Melder_assert (p1 && p2); praat_new (Polynomials_multiply (p1, p2), Thing_getName (p1), L"_x_", Thing_getName (p2)); END FORM (Polynomials_divide, L"Polynomials: Divide", L"Polynomials: Divide...") BOOLEAN (L"Want quotient", 1) BOOLEAN (L"Want remainder", 1) OK DO /* With gcc (GCC) 3.2.2 20030217 (Red Hat Linux 8.0 3.2.2-2) The following line initiates pq = NULL and I don't know why Polynomial p1 = NULL, p2 = NULL, pq, pr; */ bool wantq = GET_INTEGER (L"Want quotient"); bool wantr = GET_INTEGER (L"Want remainder"); if (! wantq && ! wantr) { Melder_throw ("Either \'Want quotient\' or \'Want remainder\' must be chosen"); } Polynomial p1 = 0, p2 = 0; LOOP { iam (Polynomial); (p1 ? p2 : p1) = me; } Melder_assert (p1 && p2); Polynomial q, r; if (! wantq) { q = 0; } if (! wantr) { r = 0; } Polynomials_divide (p1, p2, &q, &r); autoPolynomial aq = q, ar = r; if (wantq) { praat_new (aq.transfer(), Thing_getName (p1), L"_q"); } if (wantr) { praat_new (ar.transfer(), Thing_getName (p1), L"_r"); } END /********************* Roots ******************************/ DIRECT (Roots_help) Melder_help (L"Roots"); END FORM (Roots_draw, L"Roots: Draw", 0) REAL (L"Minimum of real axis", L"0.0") REAL (L"Maximum of real axis", L"0.0") REAL (L"Minimum of imaginary axis", L"0.0") REAL (L"Maximum of imaginary axis", L"0.0") SENTENCE (L"Mark string (+x0...)", L"o") NATURAL (L"Mark size", L"12") BOOLEAN (L"Garnish", 0) OK DO autoPraatPicture picture; LOOP { iam (Roots); Roots_draw (me, GRAPHICS, GET_REAL (L"Minimum of real axis"), GET_REAL (L"Maximum of real axis"), GET_REAL (L"Minimum of imaginary axis"), GET_REAL (L"Maximum of imaginary axis"), GET_STRING (L"Mark string"), GET_INTEGER (L"Mark size"), GET_INTEGER (L"Garnish")); } END DIRECT (Roots_getNumberOfRoots) LOOP { iam (Roots); Melder_information (Melder_integer (Roots_getNumberOfRoots (me))); } END FORM (Roots_getRoot, L"Roots: Get root", 0) NATURAL (L"Root number", L"1") OK DO LOOP { iam (Roots); dcomplex z = Roots_getRoot (me, GET_INTEGER (L"Root number")); Melder_information (Melder_double (z.re), (z.im < 0 ? L" - " : L" + "), Melder_double (fabs (z.im)), L" i"); } END FORM (Roots_getRealPartOfRoot, L"Roots: Get real part", 0) NATURAL (L"Root number", L"1") OK DO LOOP { iam (Roots); dcomplex z = Roots_getRoot (me, GET_INTEGER (L"Root number")); Melder_information (Melder_double (z.re)); } END FORM (Roots_getImaginaryPartOfRoot, L"Roots: Get imaginary part", 0) NATURAL (L"Root number", L"1") OK DO LOOP { iam (Roots); dcomplex z = Roots_getRoot (me, GET_INTEGER (L"Root number")); Melder_information (Melder_double (z.im)); } END FORM (Roots_setRoot, L"Roots: Set root", 0) NATURAL (L"Root number", L"1") REAL (L"Real part", L"1.0/sqrt(2)") REAL (L"Imaginary part", L"1.0/sqrt(2)") OK DO LOOP { iam (Roots); Roots_setRoot (me, GET_INTEGER (L"Root number"), GET_REAL (L"Real part"), GET_REAL (L"Imaginary part")); praat_dataChanged (me); } END FORM (Roots_to_Spectrum, L"Roots: To Spectrum", L"Roots: To Spectrum...") POSITIVE (L"Nyquist frequency (Hz)", L"5000.0") NATURAL (L"Number of frequencies (>1)", L"1025") OK DO long n = GET_INTEGER (L"Number of frequencies"); LOOP { iam (Roots); praat_new (Roots_to_Spectrum (me, GET_REAL (L"Nyquist frequency"), n, 1.0), my name); } END DIRECT (Roots_and_Polynomial_polish) Roots me = FIRST (Roots); Polynomial pol = FIRST (Polynomial); Roots_and_Polynomial_polish (me, pol); praat_dataChanged (me); END /*****************************************************************************/ DIRECT (Praat_ReportFloatingPointProperties) if (! NUMfpp) { NUMmachar (); } MelderInfo_open (); MelderInfo_writeLine1 (L"Double precision floating point properties of this machine,"); MelderInfo_writeLine1 (L"as calculated by algorithms from the Binary Linear Algebra System (BLAS)"); MelderInfo_writeLine2 (L"Radix: ", Melder_double (NUMfpp -> base)); MelderInfo_writeLine2 (L"Number of digits in mantissa: ", Melder_double (NUMfpp -> t)); MelderInfo_writeLine2 (L"Smallest exponent before (gradual) underflow (expmin): ", Melder_integer (NUMfpp -> emin)); MelderInfo_writeLine2 (L"Largest exponent before overflow (expmax): ", Melder_integer (NUMfpp -> emax)); MelderInfo_writeLine2 (L"Does rounding occur in addition: ", (NUMfpp -> rnd == 1 ? L"yes" : L"no")); MelderInfo_writeLine2 (L"Quantization step (d): ", Melder_double (NUMfpp -> prec)); MelderInfo_writeLine2 (L"Quantization error (eps = d/2): ", Melder_double (NUMfpp -> eps)); MelderInfo_writeLine2 (L"Underflow threshold (= radix ^ (expmin - 1)): ", Melder_double (NUMfpp -> rmin)); MelderInfo_writeLine2 (L"Safe minimum (such that its inverse does not overflow): ", Melder_double (NUMfpp -> sfmin)); MelderInfo_writeLine2 (L"Overflow threshold (= (1 - eps) * radix ^ expmax): ", Melder_double (NUMfpp -> rmax)); MelderInfo_close (); END /******************** Sound ****************************************/ static void Sound_create_addCommonFields (void *dia) { REAL (L"Starting time (s)", L"0.0") REAL (L"Finishing time (s)", L"0.1") POSITIVE (L"Sampling frequency (Hz)", L"44100.0") } static void Sound_create_checkCommonFields (void *dia, double *startingTime, double *finishingTime, double *samplingFrequency) { double numberOfSamples_real; *startingTime = GET_REAL (L"Starting time"); *finishingTime = GET_REAL (L"Finishing time"); *samplingFrequency = GET_REAL (L"Sampling frequency"); numberOfSamples_real = floor ( (*finishingTime - *startingTime) * *samplingFrequency + 0.5); if (*finishingTime <= *startingTime) { if (*finishingTime == *startingTime) { Melder_throw ("A Sound cannot have a duration of zero."); } else { Melder_throw ("A Sound cannot have a duration less than zero."); } if (*startingTime == 0.0) { Melder_throw ("Please set the finishing time to something greater than 0 seconds."); } else { Melder_throw ("Please lower the starting time or raise the finishing time."); } } if (*samplingFrequency <= 0.0) Melder_throw ("A Sound cannot have a negative sampling frequency.\n" "Please set the sampling frequency to something greater than zero, e.g. 44100 Hz."); if (numberOfSamples_real < 1.0) { Melder_error_ ("A Sound cannot have zero samples.\n"); if (*startingTime == 0.0) { Melder_throw ("Please raise the finishing time."); } else { Melder_throw ("Please lower the starting time or raise the finishing time."); } } if (numberOfSamples_real > LONG_MAX) { Melder_throw ("A Sound cannot have ", Melder_bigInteger (numberOfSamples_real), " samples; the maximum is ", Melder_bigInteger (LONG_MAX), " samples.\n"); #if 0 if (*startingTime == 0.0) { Melder_throw (L"Please lower the finishing time or the sampling frequency."); } else { Melder_throw (L"Please raise the starting time, lower the finishing time, or lower the sampling frequency."); } #endif } } FORM (Sound_and_Pitch_to_FormantFilter, L"Sound & Pitch: To FormantFilter", L"Sound & Pitch: To FormantFilter...") POSITIVE (L"Analysis window duration (s)", L"0.015") POSITIVE (L"Time step (s)", L"0.005") LABEL (L"", L"Filter bank parameters") POSITIVE (L"Position of first filter (Hz)", L"100.0") POSITIVE (L"Distance between filters (Hz)", L"50.0") REAL (L"Maximum frequency", L"0"); POSITIVE (L"Relative bandwidth", L"1.1") OK DO Sound me = FIRST (Sound); Pitch p = FIRST (Pitch); praat_new (Sound_and_Pitch_to_FormantFilter (me, p, GET_REAL (L"Analysis window duration"), GET_REAL (L"Time step"), GET_REAL (L"Position of first filter"), GET_REAL (L"Maximum frequency"), GET_REAL (L"Distance between filters"), GET_REAL (L"Relative bandwidth")), my name, L"_", p->name); END FORM (Sound_and_Pitch_changeGender, L"Sound & Pitch: Change gender", L"Sound & Pitch: Change gender...") POSITIVE (L"Formant shift ratio", L"1.2") REAL (L"New pitch median (Hz)", L"0.0 (=no change)") POSITIVE (L"Pitch range factor", L"1.0 (=no change)") POSITIVE (L"Duration factor", L"1.0") OK DO Sound me = FIRST (Sound); Pitch p = FIRST (Pitch); praat_new (Sound_and_Pitch_changeGender_old (me, p, GET_REAL (L"Formant shift ratio"), GET_REAL (L"New pitch median"), GET_REAL (L"Pitch range factor"), GET_REAL (L"Duration factor")), my name, L"_", p->name); END FORM (Sound_and_Pitch_changeSpeaker, L"Sound & Pitch: Change speaker", L"Sound & Pitch: Change speaker...") POSITIVE (L"Multiply formants by", L"1.1 (male->female)") POSITIVE (L"Multiply pitch by", L"1.8 (male->female") REAL (L"Multiply pitch range by", L"1.0 (=no change)") POSITIVE (L"Multiply duration", L"1.0") OK DO Sound me = FIRST (Sound); Pitch p = FIRST (Pitch); praat_new (Sound_and_Pitch_changeSpeaker (me, p, GET_REAL (L"Multiply formants by"), GET_REAL (L"Multiply pitch by"), GET_REAL (L"Multiply pitch range by"), GET_REAL (L"Multiply duration")), my name, L"_", p->name); END FORM (Sound_and_IntervalTier_cutPartsMatchingLabel, L"Sound & IntervalTier: Cut parts matching label", 0) SENTENCE (L"Label", L"cut") OK DO const wchar_t *label = GET_STRING (L"Label"); Sound me = FIRST (Sound); IntervalTier thee = FIRST (IntervalTier); praat_new (Sound_and_IntervalTier_cutPartsMatchingLabel (me, thee, label), my name, L"_cut"); END FORM (Sound_createFromGammaTone, L"Create a gammatone", L"Create Sound from gammatone...") WORD (L"Name", L"gammatone") Sound_create_addCommonFields (dia); INTEGER (L"Gamma", L"4") POSITIVE (L"Frequency (Hz)", L"1000.0") REAL (L"Bandwidth (Hz)", L"150.0") REAL (L"Initial phase (radians)", L"0.0") REAL (L"Addition factor", L"0.0") BOOLEAN (L"Scale amplitudes", 1) OK DO double startingTime, finishingTime, samplingFrequency; long gamma = GET_INTEGER (L"Gamma"); double bandwidth = GET_REAL (L"Bandwidth"); double f = GET_REAL (L"Frequency"); Sound_create_checkCommonFields (dia, &startingTime, &finishingTime, &samplingFrequency); if (f >= samplingFrequency / 2) Melder_throw ("Frequency cannot be larger than half the sampling frequency.\n" "Please use a frequency smaller than ", samplingFrequency / 2); if (gamma < 0) { Melder_throw ("Gamma cannot be negative.\nPlease use a positive or zero gamma."); } if (bandwidth < 0) { Melder_throw ("Bandwidth cannot be negative.\nPlease use a positive or zero bandwidth."); } autoSound sound = Sound_createGammaTone (startingTime, finishingTime, samplingFrequency, gamma, f, bandwidth, GET_REAL (L"Initial phase"), GET_REAL (L"Addition factor"), GET_INTEGER (L"Scale amplitudes")); //Sound_create_check (sound.peek(), startingTime, finishingTime, samplingFrequency);//TODO praat_new (sound.transfer(), GET_STRING (L"Name")); END FORM (Sound_createFromShepardTone, L"Create a Shepard tone", L"Create Sound from Shepard tone...") WORD (L"Name", L"shepardTone") Sound_create_addCommonFields (dia); POSITIVE (L"Lowest frequency (Hz)", L"4.863") NATURAL (L"Number of components", L"10") REAL (L"Frequency change (semitones/s)", L"4.0") REAL (L"Amplitude range (dB)", L"30.0") REAL (L"Octave shift fraction ([0,1))", L"0.0") OK DO double startingTime, finishingTime, samplingFrequency; double amplitudeRange = GET_REAL (L"Amplitude range"); double octaveShiftFraction = GET_REAL (L"Octave shift fraction"); Sound_create_checkCommonFields (dia, &startingTime, &finishingTime, &samplingFrequency); if (amplitudeRange < 0) { Melder_throw ("Amplitude range cannot be negative.\nPlease use a positive or zero amplitude range."); } autoSound sound = Sound_createShepardToneComplex (startingTime, finishingTime, samplingFrequency, GET_REAL (L"Lowest frequency"), GET_INTEGER (L"Number of components"), GET_REAL (L"Frequency change"), GET_REAL (L"Amplitude range"), octaveShiftFraction); // Sound_create_check (sound, startingTime, finishingTime, samplingFrequency); //TODO praat_new (sound.transfer(), GET_STRING (L"Name")); END FORM (Sound_drawWhere, L"Sound: Draw where", L"Sound: Draw where...") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range", L"0.0 (= all)") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0 (= auto)") BOOLEAN (L"Garnish", 1) LABEL (L"", L"") OPTIONMENU (L"Drawing method", 1) OPTION (L"Curve") OPTION (L"Bars") OPTION (L"Poles") OPTION (L"Speckles") LABEL (L"", L"Draw only those parts where the following condition holds:") TEXTFIELD (L"Formula", L"x < xmin + (xmax - xmin) / 2; first half") OK DO long numberOfBisections = 10; autoPraatPicture picture; LOOP { iam (Sound); Sound_drawWhere (me, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish"), GET_STRING (L"Drawing method"), numberOfBisections, GET_STRING (L"Formula"), interpreter); } END FORM (Sound_playOneChannel, L"Sound: Play one channel", 0) NATURAL (L"Channel", L"1") OK DO long ichannel = GET_INTEGER (L"Channel"); LOOP { iam (Sound); if (ichannel > my ny) { Melder_throw (me, " there is no channel 6. Sound in channel not played."); } autoSound thee = Sound_extractChannel (me, ichannel); Sound_play (thee.peek(), 0, 0); } END FORM (Sounds_to_DTW, L"Sounds: To DTW", 0) POSITIVE (L"Window length (s)", L"0.015") POSITIVE (L"Time step (s)", L"0.005") LABEL (L"", L"") REAL (L"Sakoe-Chiba band (s)", L"0.1") RADIO (L"Slope constraint", 1) RADIOBUTTON (L"no restriction") RADIOBUTTON (L"1/3 < slope < 3") RADIOBUTTON (L"1/2 < slope < 2") RADIOBUTTON (L"2/3 < slope < 3/2") OK DO double analysisWidth = GET_REAL (L"Window length"); double dt = GET_REAL (L"Time step"); double band = GET_REAL (L"Sakoe-Chiba band"); int slope = GET_INTEGER (L"Slope constraint"); Sound s1 = 0, s2 = 0; LOOP { iam (Sound); (s1 ? s2 : s1) = me; } Melder_assert (s1 && s2); praat_new (Sounds_to_DTW (s1, s2, analysisWidth, dt, band, slope), s1 -> name, L"_", s2 -> name); END FORM (Sound_to_TextGrid_detectSilences, L"Sound: To TextGrid (silences)", L"Sound: To TextGrid (silences)...") LABEL (L"", L"Parameters for the intensity analysis") POSITIVE (L"Minimum pitch (Hz)", L"100") REAL (L"Time step (s)", L"0.0 (= auto)") LABEL (L"", L"Silent intervals detection") REAL (L"Silence threshold (dB)", L"-25.0") POSITIVE (L"Minimum silent interval duration (s)", L"0.1") POSITIVE (L"Minimum sounding interval duration (s)", L"0.1") WORD (L"Silent interval label", L"silent") WORD (L"Sounding interval label", L"sounding") OK DO LOOP { iam (Sound); praat_new (Sound_to_TextGrid_detectSilences (me, GET_REAL (L"Minimum pitch"), GET_REAL (L"Time step"), GET_REAL (L"Silence threshold"), GET_REAL (L"Minimum silent interval duration"), GET_REAL (L"Minimum sounding interval duration"), GET_STRING (L"Silent interval label"), GET_STRING (L"Sounding interval label")), my name); } END FORM (Sound_trimSilences, L"Sound: Trim silences", L"Sound: Trim silences...") REAL (L"Trim duration (s)", L"0.08") BOOLEAN (L"Only at start and end", 1); LABEL (L"", L"Parameters for the intensity analysis") POSITIVE (L"Minimum pitch (Hz)", L"100") REAL (L"Time step (s)", L"0.0 (= auto)") LABEL (L"", L"Silent intervals detection") REAL (L"Silence threshold (dB)", L"-35.0") POSITIVE (L"Minimum silent interval duration (s)", L"0.1") POSITIVE (L"Minimum sounding interval duration (s)", L"0.05") BOOLEAN (L"Save trimming info as TextGrid", 0) WORD (L"Trim label", L"trimmed") OK DO double trimDuration = GET_REAL (L"Trim duration"); if (trimDuration < 0) { trimDuration = 0; } bool onlyAtStartAndEnd = GET_INTEGER (L"Only at start and end"); double minPitch = GET_REAL (L"Minimum pitch"); double timeStep = GET_REAL (L"Time step"); double silenceThreshold = GET_REAL (L"Silence threshold"); double minSilenceDuration = GET_REAL (L"Minimum silent interval duration"); double minSoundingDuration = GET_REAL (L"Minimum sounding interval duration"); bool saveTextGrid = GET_INTEGER (L"Save trimming info as TextGrid"); const wchar_t *trimlabel = GET_STRING (L"Trim label"); LOOP { iam (Sound); TextGrid tg = NULL; autoSound thee = Sound_trimSilences (me, trimDuration, onlyAtStartAndEnd, minPitch, timeStep, silenceThreshold, minSilenceDuration, minSoundingDuration, (saveTextGrid ? &tg : 0), trimlabel); autoTextGrid atg = tg; if (saveTextGrid) { praat_new (atg.transfer(), my name, L"_trimmed"); } praat_new (thee.transfer(), my name, L"_trimmed"); } END FORM (Sound_to_BarkFilter, L"Sound: To BarkFilter", L"Sound: To BarkFilter...") POSITIVE (L"Window length (s)", L"0.015") POSITIVE (L"Time step (s)", L"0.005") LABEL (L"", L"Filter bank parameters") POSITIVE (L"Position of first filter (bark)", L"1.0") POSITIVE (L"Distance between filters (bark)", L"1.0") REAL (L"Maximum frequency (bark)", L"0"); OK DO LOOP { iam (Sound); praat_new (Sound_to_BarkFilter (me, GET_REAL (L"Window length"), GET_REAL (L"Time step"), GET_REAL (L"Position of first filter"), GET_REAL (L"Maximum frequency"), GET_REAL (L"Distance between filters")), my name); } END FORM (Sound_to_FormantFilter, L"Sound: To FormantFilter", L"Sound: To FormantFilter...") POSITIVE (L"Window length (s)", L"0.015") POSITIVE (L"Time step (s)", L"0.005") LABEL (L"", L"Filter bank parameters") POSITIVE (L"Position of first filter (Hz)", L"100.0") POSITIVE (L"Distance between filters (Hz)", L"50.0") REAL (L"Maximum frequency", L"0"); POSITIVE (L"Relative bandwidth", L"1.1") LABEL (L"", L"Pitch analysis") REAL (L"Minimum pitch (Hz)", L"75.0") REAL (L"Maximum pitch (Hz)", L"600.0") OK DO LOOP { iam (Sound); praat_new (Sound_to_FormantFilter (me, GET_REAL (L"Window length"), GET_REAL (L"Time step"), GET_REAL (L"Position of first filter"), GET_REAL (L"Maximum frequency"), GET_REAL (L"Distance between filters"), GET_REAL (L"Relative bandwidth"), GET_REAL (L"Minimum pitch"), GET_REAL (L"Maximum pitch")), my name); } END FORM (Sound_to_MelFilter, L"Sound: To MelFilter", L"Sound: To MelFilter...") POSITIVE (L"Window length (s)", L"0.015") POSITIVE (L"Time step (s)", L"0.005") LABEL (L"", L"Filter bank parameters") POSITIVE (L"Position of first filter (mel)", L"100.0") POSITIVE (L"Distance between filters (mel)", L"100.0") REAL (L"Maximum frequency (mel)", L"0.0"); OK DO LOOP { iam (Sound); praat_new (Sound_to_MelFilter (me, GET_REAL (L"Window length"), GET_REAL (L"Time step"), GET_REAL (L"Position of first filter"), GET_REAL (L"Maximum frequency"), GET_REAL (L"Distance between filters")), my name); } END FORM (Sound_to_Pitch_shs, L"Sound: To Pitch (shs)", L"Sound: To Pitch (shs)...") POSITIVE (L"Time step (s)", L"0.01") POSITIVE (L"Minimum pitch (Hz)", L"50.0") NATURAL (L"Max. number of candidates (Hz)", L"15") LABEL (L"", L"Algorithm parameters") POSITIVE (L"Maximum frequency component (Hz)", L"1250.0") NATURAL (L"Max. number of subharmonics", L"15") POSITIVE (L"Compression factor (<=1)", L"0.84") POSITIVE (L"Ceiling (Hz)", L"600.0") NATURAL (L"Number of points per octave", L"48"); OK DO double minimumPitch = GET_REAL (L"Minimum pitch"); double fmax = GET_REAL (L"Maximum frequency component"); double ceiling = GET_REAL (L"Ceiling"); if (minimumPitch >= ceiling) { Melder_throw ("Minimum pitch should be smaller than ceiling."); } if (ceiling >= fmax) { Melder_throw ("Maximum frequency must be greater than or equal to ceiling."); } LOOP { iam (Sound); praat_new (Sound_to_Pitch_shs (me, GET_REAL (L"Time step"), minimumPitch, fmax, ceiling, GET_INTEGER (L"Max. number of subharmonics"), GET_INTEGER (L"Max. number of candidates"), GET_REAL (L"Compression factor"), GET_INTEGER (L"Number of points per octave")), my name); } END FORM (Sound_fadeIn, L"Sound: Fade in", L"Sound: Fade in...") CHANNEL (L"Channel (number, Left, or Right)", L"1") OPTION (L"All") OPTION (L"Left") OPTION (L"Right") REAL (L"Time (s)", L"-10000.0") REAL (L"Fade time (s)", L"0.005") BOOLEAN (L"Silent from start", 0) OK DO long channel = GET_INTEGER (L"Channel") - 1; LOOP { iam (Sound); Sound_fade (me, channel, GET_REAL (L"Time"), GET_REAL (L"Fade time"), -1, GET_INTEGER (L"Silent from start")); praat_dataChanged (me); } END FORM (Sound_fadeOut, L"Sound: Fade out", L"Sound: Fade out...") CHANNEL (L"Channel (number, Left, or Right)", L"1") OPTION (L"All") OPTION (L"Left") OPTION (L"Right") REAL (L"Time (s)", L"10000.0") REAL (L"Fade time (s)", L"-0.005") BOOLEAN (L"Silent to end", 0) OK DO long channel = GET_INTEGER (L"Channel") - 1; LOOP { iam (Sound); Sound_fade (me, channel, GET_REAL (L"Time"), GET_REAL (L"Fade time"), 1, GET_INTEGER (L"Silent to end")); praat_dataChanged (me); } END FORM (Sound_to_KlattGrid_simple, L"Sound: To KlattGrid (simple)", L"Sound: To KlattGrid (simple)...") POSITIVE (L"Time step (s)", L"0.005") LABEL (L"", L"Formant determination") NATURAL (L"Max. number of formants", L"5") POSITIVE (L"Maximum formant (Hz)", L"5500 (=adult female)") POSITIVE (L"Window length (s)", L"0.025") POSITIVE (L"Pre-emphasis from (Hz)", L"50.0") LABEL (L"", L"Pitch determination") POSITIVE (L"Pitch floor (Hz)", L"60.0") POSITIVE (L"Pitch ceiling (Hz)", L"600.0") LABEL (L"", L"Intensity determination") POSITIVE (L"Minimum pitch (Hz)", L"100.0") BOOLEAN (L"Subtract mean", 1) OK DO LOOP { iam (Sound); praat_new (Sound_to_KlattGrid_simple (me, GET_REAL (L"Time step"), GET_INTEGER (L"Max. number of formants"), GET_REAL (L"Maximum formant"), GET_REAL (L"Window length"), GET_REAL (L"Pre-emphasis from"), GET_REAL (L"Pitch floor"), GET_REAL (L"Pitch ceiling"), GET_REAL (L"Minimum pitch"), GET_INTEGER (L"Subtract mean")), my name); } END FORM (Sound_to_Pitch_SPINET, L"Sound: To SPINET", L"Sound: To SPINET...") POSITIVE (L"Time step (s)", L"0.005") POSITIVE (L"Window length (s)", L"0.040") LABEL (L"", L"Gammatone filter bank") POSITIVE (L"Minimum filter frequency (Hz)", L"70.0") POSITIVE (L"Maximum filter frequency (Hz)", L"5000.0") NATURAL (L"Number of filters", L"250"); POSITIVE (L"Ceiling (Hz)", L"500.0") NATURAL (L"Max. number of candidates", L"15") OK DO double fmin = GET_REAL (L"Minimum filter frequency"); double fmax = GET_REAL (L"Maximum filter frequency"); if (fmax <= fmin) { Melder_throw ("Maximum frequency must be larger than minimum frequency."); } LOOP { iam (Sound); praat_new (Sound_to_Pitch_SPINET (me, GET_REAL (L"Time step"), GET_REAL (L"Window length"), fmin, fmax, GET_INTEGER (L"Number of filters"), GET_REAL (L"Ceiling"), GET_INTEGER (L"Max. number of candidates")), my name); } END FORM (Sound_to_Polygon, L"Sound: To Polygon", L"Sound: To Polygon...") CHANNEL (L"Channel (number, Left, or Right)", L"1") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") REAL (L"Connection y-value", L"0.0") OK DO long channel = GET_INTEGER (L"Channel"); LOOP { iam (Sound); if (channel > my ny) { channel = 1; } praat_new (Sound_to_Polygon (me, channel, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Connection y-value")), my name); } END FORM (Sounds_to_Polygon_enclosed, L"Sounds: To Polygon (enclosed)", L"Sounds: To Polygon (enclosed)...") CHANNEL (L"Channel (number, Left, or Right)", L"1") OPTION (L"Left") OPTION (L"Right") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") OK DO long channel = GET_INTEGER (L"Channel"); Sound s1 = 0, s2 = 0; LOOP { iam (Sound); (s1 ? s2 : s1) = me; } Melder_assert (s1 && s2); praat_new (Sounds_to_Polygon_enclosed (s1, s2, channel, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range")), s1->name, L"_", s2->name); END FORM (Sound_filterByGammaToneFilter4, L"Sound: Filter (gammatone)", L"Sound: Filter (gammatone)...") POSITIVE (L"Centre frequency (Hz)", L"1000.0") POSITIVE (L"Bandwidth (Hz)", L"150.0") OK DO LOOP { iam (Sound); praat_new (Sound_filterByGammaToneFilter4 (me, GET_REAL (L"Centre frequency"), GET_REAL (L"Bandwidth")), my name, L"_filtered"); } END FORM (Sound_changeSpeaker, L"Sound: Change speaker", L"Sound: Change speaker...") LABEL (L"", L"Pitch measurement parameters") POSITIVE (L"Pitch floor (Hz)", L"75.0") POSITIVE (L"Pitch ceiling (Hz)", L"600.0") LABEL (L"", L"Modification parameters") POSITIVE (L"Multiply formants by", L"1.2") POSITIVE (L"Multiply pitch by", L"1.0") REAL (L"Multiply pitch range by", L"1.0 (=no change)") POSITIVE (L"Multiply duration by", L"1.0") OK DO double minimumPitch = GET_REAL (L"Pitch floor"); double maximumPitch = GET_REAL (L"Pitch ceiling"); if (minimumPitch >= maximumPitch) { Melder_throw ("Maximum pitch should be greater than minimum pitch."); } LOOP { iam (Sound); praat_new (Sound_changeSpeaker (me, minimumPitch, maximumPitch, GET_REAL (L"Multiply formants by"), GET_REAL (L"Multiply pitch by"), GET_REAL (L"Multiply pitch range by"), GET_REAL (L"Multiply duration by")), my name, L"_changeSpeaker"); } END FORM (Sound_changeGender, L"Sound: Change gender", L"Sound: Change gender...") LABEL (L"", L"Pitch measurement parameters") POSITIVE (L"Pitch floor (Hz)", L"75.0") POSITIVE (L"Pitch ceiling (Hz)", L"600.0") LABEL (L"", L"Modification parameters") POSITIVE (L"Formant shift ratio", L"1.2") REAL (L"New pitch median (Hz)", L"0.0 (=no change)") REAL (L"Pitch range factor", L"1.0 (=no change)") POSITIVE (L"Duration factor", L"1.0") OK DO double minimumPitch = GET_REAL (L"Pitch floor"); double maximumPitch = GET_REAL (L"Pitch ceiling"); double pitchrf = GET_REAL (L"Pitch range factor"); if (minimumPitch >= maximumPitch) { Melder_throw ("Maximum pitch should be greater than minimum pitch."); } if (pitchrf < 0) { Melder_throw ("Pitch range factor may not be negative"); } LOOP { iam (Sound); praat_new (Sound_changeGender_old (me, minimumPitch, maximumPitch, GET_REAL (L"Formant shift ratio"), GET_REAL (L"New pitch median"), pitchrf, GET_REAL (L"Duration factor")), my name, L"_changeGender"); } END FORM (Sound_paintWhere, L"Sound paint where", L"Sound: Paint where...") COLOUR (L"Colour (0-1, name, or {r,g,b})", L"0.5") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") REAL (L"Fill from level", L"0.0") BOOLEAN (L"Garnish", 1) LABEL (L"", L"Paint only those parts where the following condition holds:") TEXTFIELD (L"Formula", L"1; always") OK DO long numberOfBisections = 10; autoPraatPicture picture; LOOP { iam (Sound); Sound_paintWhere (me, GRAPHICS, GET_COLOUR (L"Colour"), GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Fill from level"), GET_INTEGER (L"Garnish"), numberOfBisections, GET_STRING (L"Formula"), interpreter); } END FORM (Sounds_paintEnclosed, L"Sounds paint enclosed", L"Sounds: Paint enclosed...") COLOUR (L"Colour (0-1, name, or {r,g,b})", L"0.5") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO Sound s1 = 0, s2 = 0; LOOP { iam (Sound); (s1 ? s2 : s1) = me; } Melder_assert (s1 && s2); autoPraatPicture picture; Sounds_paintEnclosed (s1, s2, GRAPHICS, GET_COLOUR (L"Colour"), GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); END FORM_READ (Sound_readFromRawFileLE, L"Read Sound from raw Little Endian file", 0, true) praat_new (Sound_readFromRawFile (file, NULL, 16, 1, 0, 0, 16000), MelderFile_name (file)); END FORM_READ (Sound_readFromRawFileBE, L"Read Sound from raw 16-bit Little Endian file", 0, true) praat_new (Sound_readFromRawFile (file, NULL, 16, 0, 0, 0, 16000), MelderFile_name (file)); END FORM_READ (KlattTable_readFromRawTextFile, L"KlattTable_readFromRawTextFile", 0, true) praat_new (KlattTable_readFromRawTextFile (file), MelderFile_name (file)); END FORM_WRITE (Sound_writeToRawFileBE, L"Sound: Save as raw 16-bit Big Endian file", 0, L"raw") LOOP { iam (Sound); Sound_writeToRawFile (me, file, 0, 0, 16, 0); } END FORM_WRITE (Sound_writeToRawFileLE, L"Sound: Save as raw 16-bit Little Endian file", 0, L"raw") LOOP { iam (Sound); Sound_writeToRawFile (me, file, 0, 1, 16, 0); } END /************ Spectrograms *********************************************/ FORM (Spectrograms_to_DTW, L"Spectrograms: To DTW", 0) DTW_constraints_addCommonFields (dia); OK DO int begin, end, slope; DTW_constraints_getCommonFields (dia, &begin, &end, &slope); Spectrogram s1 = 0, s2 = 0; LOOP { iam (Spectrogram); (s1 ? s2 : s1) = me; } Melder_assert (s1 && s2); praat_new (Spectrograms_to_DTW (s1, s2, begin, end, slope, 1), s1->name, L"_", s2->name); END /**************** Spectrum *******************************************/ FORM (Spectrum_drawPhases, L"Spectrum: Draw phases", L"Spectrum: Draw phases...") REAL (L"From frequency (Hz)", L"0.0") REAL (L"To frequency (Hz)", L"0.0") REAL (L"Minimum phase (dB/Hz)", L"0.0 (= auto)") REAL (L"Maximum phase (dB/Hz)", L"0.0 (= auto)") BOOLEAN (L"Unwrap", 1) BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Spectrum); Spectrum_drawPhases (me, GRAPHICS, GET_REAL (L"From frequency"), GET_REAL (L"To frequency"), GET_REAL (L"Minimum phase"), GET_REAL (L"Maximum phase"), GET_INTEGER (L"Unwrap"), GET_INTEGER (L"Garnish")); } END DIRECT (Spectrum_conjugate) LOOP { iam (Spectrum); Spectrum_conjugate (me); praat_dataChanged (me); } END DIRECT (Spectra_multiply) Spectrum s1 = 0, s2 = 0; LOOP { iam (Spectrum); (s1 ? s2 : s1) = me; } Melder_assert (s1 && s2); praat_new (Spectra_multiply (s1, s2), Thing_getName (s1), L"_x_", Thing_getName (s2)); END DIRECT (Spectrum_unwrap) LOOP { iam (Spectrum); praat_new (Spectrum_unwrap (me), 0); } END DIRECT (Spectrum_to_Cepstrum) LOOP { iam (Spectrum); praat_new (Spectrum_to_Cepstrum (me), 0); } END /************* SpeechSynthesizer *************************************************/ DIRECT (SpeechSynthesizer_help) Melder_help (L"SpeechSynthesizer"); END FORM (SpeechSynthesizer_create, L"Create SpeechSynthesizer", L"Create SpeechSynthesizer...") long prefVoice = Strings_findString (espeakdata_voices_names, L"English"); if (prefVoice == 0) { prefVoice = 1; } LIST (L"Language", espeakdata_voices_names -> numberOfStrings, (const wchar_t **) espeakdata_voices_names -> strings, prefVoice) long prefVariant = Strings_findString (espeakdata_variants_names, L"default"); LABEL (L"", L"The voice variants will only work in a future version o Praat") LIST (L"Voice variant", espeakdata_variants_names -> numberOfStrings, (const wchar_t **) espeakdata_variants_names -> strings, prefVariant) OK DO long voiceIndex = GET_INTEGER (L"Language"); long variantIndex = GET_INTEGER (L"Voice variant"); // default is not in the list! autoSpeechSynthesizer me = SpeechSynthesizer_create (voiceIndex, variantIndex); praat_new (me.transfer(), espeakdata_voices_names -> strings[voiceIndex], L"_", espeakdata_variants_names -> strings[variantIndex]); END FORM (SpeechSynthesizer_playText, L"SpeechSynthesizer: Play text", L"SpeechSynthesizer: Play text...") SENTENCE (L"Text", L"This is some text.") OK DO const wchar_t *text = GET_STRING (L"Text"); LOOP { iam (SpeechSynthesizer); SpeechSynthesizer_playText (me, text); } END FORM (SpeechSynthesizer_to_Sound, L"SpeechSynthesizer: To Sound", L"SpeechSynthesizer: To Sound...") SENTENCE (L"Text", L"This is some text.") BOOLEAN (L"Create TextGrid with annotations", 0); OK DO const wchar_t *text = GET_STRING (L"Text"); bool createTextGrid = GET_INTEGER (L"Create TextGrid with annotations"); LOOP { iam (SpeechSynthesizer); TextGrid tg = 0; Table t = 0; autoSound thee = SpeechSynthesizer_to_Sound (me, text, (createTextGrid ? &tg : NULL), (Melder_debug == -2 ? &t : NULL)); autoTextGrid atg = tg; autoTable atr = t; praat_new (thee.transfer(), my name); if (createTextGrid) { praat_new (atg.transfer(), my name); } if (Melder_debug == -2) { praat_new (atr.transfer(), my name); } } END DIRECT (SpeechSynthesizer_getVoiceName) LOOP { iam (SpeechSynthesizer); Melder_information (espeakdata_voices_names -> strings [my d_voice]); } END DIRECT (SpeechSynthesizer_getVoiceVariant) LOOP { iam (SpeechSynthesizer); Melder_information (espeakdata_variants_names -> strings[my d_voiceVariant]); } END FORM (SpeechSynthesizer_setTextInputSettings, L"SpeechSynthesizer: Set text input settings", L"SpeechSynthesizer: Set text input settings...") OPTIONMENU (L"Input text format is", 1) OPTION (L"Text only") OPTION (L"Phoneme codes only") OPTION (L"Mixed with tags") OPTIONMENU (L"Input phoneme codes are", 1) OPTION (L"Kirshenbaum_espeak") OK DO int inputTextFormat = GET_INTEGER (L"Input text format is"); int inputPhonemeCoding = SpeechSynthesizer_PHONEMECODINGS_KIRSHENBAUM; // LOOP { iam (SpeechSynthesizer); SpeechSynthesizer_setTextInputSettings (me, inputTextFormat, inputPhonemeCoding); } END FORM (SpeechSynthesizer_setSpeechOutputSettings, L"SpeechSynthesizer: Set speech output settings", L"SpeechSynthesizer: Set speech output settings...") POSITIVE (L"Sampling frequency (Hz)", L"44100") REAL (L"Gap between words (s)", L"0.01") INTEGER (L"Pitch adjustment (0-99)", L"50") INTEGER (L"Pitch range (0-99)", L"50"); NATURAL (L"Words per minute (80-450)", L"175"); BOOLEAN (L"Estimate words per minute from data", 1); OPTIONMENU (L"Output phoneme codes are", 2) OPTION (L"Kirshenbaum_espeak") OPTION (L"IPA") OK DO double samplingFrequency = GET_REAL (L"Sampling frequency"); double wordgap = GET_REAL (L"Gap between words"); if (wordgap < 0) wordgap = 0; double pitchAdjustment = GET_INTEGER (L"Pitch adjustment"); if (pitchAdjustment < 0) pitchAdjustment = 0; if (pitchAdjustment > 99) pitchAdjustment = 99; double pitchRange = GET_INTEGER (L"Pitch range"); if (pitchRange < 0) pitchRange = 0; if (pitchRange > 99) pitchRange = 99; double wordsPerMinute = GET_INTEGER (L"Words per minute"); bool estimateWordsPerMinute = GET_INTEGER (L"Estimate words per minute from data"); int outputPhonemeCodes = GET_INTEGER (L"Output phoneme codes are"); LOOP { iam (SpeechSynthesizer); SpeechSynthesizer_setSpeechOutputSettings (me, samplingFrequency, wordgap, pitchAdjustment, pitchRange, wordsPerMinute, estimateWordsPerMinute, outputPhonemeCodes); } END /************* SpeechSynthesizer and TextGrid ************************/ FORM (SpeechSynthesizer_and_TextGrid_to_Sound, L"SpeechSynthesizer & TextGrid: To Sound", 0) NATURAL (L"Tier number", L"1") NATURAL (L"Interval number", L"1") BOOLEAN (L"Create TextGrid with annotations", 0); OK DO bool createTextGrid = GET_INTEGER (L"Create TextGrid with annotations"); SpeechSynthesizer me = FIRST (SpeechSynthesizer); TextGrid thee = FIRST (TextGrid), tg = 0; autoSound him = SpeechSynthesizer_and_TextGrid_to_Sound (me, thee, GET_INTEGER (L"Tier number"), GET_INTEGER (L"Interval number"), (createTextGrid ? &tg : NULL)); autoTextGrid atg = tg; praat_new (him.transfer(), my name); if (createTextGrid) { praat_new (atg.transfer(), my name); } END FORM (SpeechSynthesizer_and_Sound_and_TextGrid_align, L"SpeechSynthesizer & Sound & TextGrid: To TextGrid (align)", 0) NATURAL (L"Tier number", L"1") NATURAL (L"From interval number", L"1") NATURAL (L"To interval number", L"1") REAL (L"Silence threshold (dB)", L"-35.0") POSITIVE (L"Minimum silent interval duration (s)", L"0.1") POSITIVE (L"Minimum sounding interval duration (s)", L"0.1") OK DO double silenceThreshold = GET_REAL (L"Silence threshold"); double minSilenceDuration = GET_REAL (L"Minimum silent interval duration"); double minSoundingDuration = GET_REAL (L"Minimum sounding interval duration"); SpeechSynthesizer synth = FIRST (SpeechSynthesizer); Sound s = FIRST (Sound); TextGrid tg = FIRST (TextGrid); autoTextGrid thee = SpeechSynthesizer_and_Sound_and_TextGrid_align (synth, s, tg, GET_INTEGER (L"Tier number"), GET_INTEGER (L"From interval number"), GET_INTEGER (L"To interval number"), silenceThreshold, minSilenceDuration, minSoundingDuration); praat_new (thee.transfer(), thy name, L"_aligned"); END FORM (SpeechSynthesizer_and_Sound_and_TextGrid_align2, L"SpeechSynthesizer & Sound & TextGrid: To TextGrid (align, trim)", 0) NATURAL (L"Tier number", L"1") NATURAL (L"From interval number", L"1") NATURAL (L"To interval number", L"1") REAL (L"Silence threshold (dB)", L"-35.0") POSITIVE (L"Minimum silent interval duration (s)", L"0.1") POSITIVE (L"Minimum sounding interval duration (s)", L"0.1") REAL (L"Silence trim duration (s)", L"0.08") OK DO double silenceThreshold = GET_REAL (L"Silence threshold"); double minSilenceDuration = GET_REAL (L"Minimum silent interval duration"); double minSoundingDuration = GET_REAL (L"Minimum sounding interval duration"); double trimDuration = GET_REAL (L"Silence trim duration"); if (trimDuration < 0) { trimDuration = 0; } SpeechSynthesizer synth = FIRST (SpeechSynthesizer); Sound s = FIRST (Sound); TextGrid tg = FIRST (TextGrid); autoTextGrid thee = SpeechSynthesizer_and_Sound_and_TextGrid_align2 (synth, s, tg, GET_INTEGER (L"Tier number"), GET_INTEGER (L"From interval number"), GET_INTEGER (L"To interval number"), silenceThreshold, minSilenceDuration, minSoundingDuration, trimDuration); praat_new (thee.transfer(), thy name, L"_aligned"); END /************* Spline *************************************************/ FORM (Spline_drawKnots, L"Spline: Draw knots", 0) REAL (L"Xmin", L"0.0") REAL (L"Xmax", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO LOOP { iam (Spline); Spline_drawKnots (me, GRAPHICS, GET_REAL (L"Xmin"), GET_REAL (L"Xmax"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); } END DIRECT (Spline_getOrder) LOOP { iam (Spline); Melder_information (Melder_integer (Spline_getOrder (me))); } END FORM (Spline_scaleX, L"Spline: Scale x", L"Spline: Scale x...") LABEL (L"", L"New domain") REAL (L"Xmin", L"-1.0") REAL (L"Xmax", L"1.0") OK DO double xmin = GET_REAL (L"Xmin"), xmax = GET_REAL (L"Xmax"); if (xmin >= xmax) { Melder_throw ("Xmin must be smaller than Xmax."); } LOOP { iam (Spline); praat_new (Spline_scaleX (me, xmin, xmax), my name, L"_scaleX"); } END /************ SSCP ***************************************************/ DIRECT (SSCP_help) Melder_help (L"SSCP"); END FORM (SSCP_drawConfidenceEllipse, L"SSCP: Draw confidence ellipse", 0) POSITIVE (L"Confidence level", L"0.95") NATURAL (L"Index for X-axis", L"1") NATURAL (L"Index for Y-axis", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (SSCP); SSCP_drawConcentrationEllipse (me, GRAPHICS, GET_REAL (L"Confidence level"), 1, GET_INTEGER (L"Index for X-axis"), GET_INTEGER (L"Index for Y-axis"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); } END FORM (SSCP_drawSigmaEllipse, L"SSCP: Draw sigma ellipse", L"SSCP: Draw sigma ellipse...") POSITIVE (L"Number of sigmas", L"1.0") NATURAL (L"Index for X-axis", L"1") NATURAL (L"Index for Y-axis", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (SSCP); SSCP_drawConcentrationEllipse (me, GRAPHICS, GET_REAL (L"Number of sigmas"), 0, GET_INTEGER (L"Index for X-axis"), GET_INTEGER (L"Index for Y-axis"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); } END DIRECT (SSCP_extractCentroid) LOOP { iam (SSCP); praat_new (SSCP_extractCentroid (me), my name, L"_centroid"); } END FORM (SSCP_getConfidenceEllipseArea, L"SSCP: Get confidence ellipse area", L"SSCP: Get confidence ellipse area...") POSITIVE (L"Confidence level", L"0.95") NATURAL (L"Index for X-axis", L"1") NATURAL (L"Index for Y-axis", L"2") OK DO double conf = GET_REAL (L"Confidence level"); long d1 = GET_INTEGER (L"Index for X-axis"); long d2 = GET_INTEGER (L"Index for Y-axis"); LOOP { iam (SSCP); Melder_information (Melder_double (SSCP_getConcentrationEllipseArea (me, conf, 1, d1, d2))); } END FORM (SSCP_getFractionVariation, L"SSCP: Get fraction variation", L"SSCP: Get fraction variation...") NATURAL (L"From dimension", L"1") NATURAL (L"To dimension", L"1") OK DO LOOP { iam (SSCP); Melder_information (Melder_double (SSCP_getFractionVariation (me, GET_INTEGER (L"From dimension"), GET_INTEGER (L"To dimension")))); } END FORM (SSCP_getConcentrationEllipseArea, L"SSCP: Get sigma ellipse area", L"SSCP: Get sigma ellipse area...") POSITIVE (L"Number of sigmas", L"1.0") NATURAL (L"Index for X-axis", L"1") NATURAL (L"Index for Y-axis", L"2") OK DO double nsigmas = GET_REAL (L"Number of sigmas"); long d1 = GET_INTEGER (L"Index for X-axis"); long d2 = GET_INTEGER (L"Index for Y-axis"); LOOP { iam (SSCP); Melder_information (Melder_double (SSCP_getConcentrationEllipseArea (me, nsigmas, 0, d1, d2))); } END DIRECT (SSCP_getDegreesOfFreedom) LOOP { iam (SSCP); Melder_information (Melder_double (SSCP_getDegreesOfFreedom (me))); } END DIRECT (SSCP_getNumberOfObservations) LOOP { iam (SSCP); Melder_information (Melder_integer (my numberOfObservations)); } END DIRECT (SSCP_getTotalVariance) LOOP { iam (SSCP); Melder_information (Melder_double (SSCP_getTotalVariance (me))); } END FORM (SSCP_getCentroidElement, L"SSCP: Get centroid element", L"SSCP: Get centroid element") NATURAL (L"Number", L"1") OK DO long number = GET_INTEGER (L"Number"); LOOP { iam (SSCP); if (number < 1 || number > my numberOfColumns) { Melder_throw ("\"Number\" must be smaller than ", my numberOfColumns + 1, "."); } Melder_information (Melder_double (my centroid[number])); } END DIRECT (SSCP_getLnDeterminant) LOOP { iam (SSCP); Melder_information (Melder_double (SSCP_getLnDeterminant (me))); } END FORM (SSCP_testDiagonality_bartlett, L"SSCP: Get diagonality (bartlett)", L"SSCP: Get diagonality (bartlett)...") NATURAL (L"Number of contraints", L"1") OK DO double chisq, p; long nc = GET_INTEGER (L"Number of contraints"); LOOP { iam (SSCP); SSCP_testDiagonality_bartlett (me, nc, &chisq, &p); Melder_information (Melder_double (p), L" (=probability for chisq = ", Melder_double (chisq), L" and ndf = ", Melder_integer (my numberOfRows * (my numberOfRows - 1) / 2), L")"); } END DIRECT (SSCP_to_Correlation) LOOP { iam (SSCP); praat_new (SSCP_to_Correlation (me), 0); } END FORM (SSCP_to_Covariance, L"SSCP: To Covariance", L"SSCP: To Covariance...") NATURAL (L"Number of constraints", L"1") OK DO long noc = GET_INTEGER (L"Number of constraints"); LOOP { iam (SSCP); praat_new (SSCP_to_Covariance (me, noc), 0); } END DIRECT (SSCP_to_PCA) LOOP { iam (SSCP); praat_new (SSCP_to_PCA (me), 0); } END /******************* Strings ****************************/ DIRECT (Strings_createFromEspeakVoices) praat_new (NULL, L"voices"); END FORM (Strings_createAsCharacters, L"Strings: Create as characters", 0) SENTENCE (L"Text", L"intention") OK DO praat_new (Strings_createAsCharacters (GET_STRING (L"Text")), 0); END FORM (Strings_createAsTokens, L"Strings: Create as tokens", 0) SENTENCE (L"Text", L"There are seven tokens in this text") OK DO praat_new (Strings_createAsTokens (GET_STRING (L"Text")), 0); END DIRECT (Strings_append) autoCollection set = praat_getSelectedObjects (); praat_new (Strings_append (set.transfer()), L"appended"); END DIRECT (Strings_to_Categories) LOOP { iam (Strings); praat_new (Strings_to_Categories (me), 0); } END FORM (Strings_setString, L"Strings: Set string", L"Strings: Set string...") NATURAL (L"Index", L"1") SENTENCE (L"String", L"") OK DO LOOP { iam (Strings); Strings_setString (me, GET_STRING (L"String"), GET_INTEGER (L"Index")); praat_dataChanged (me); } END FORM (Strings_change, L"Strings: Change", L"Strings: Change") SENTENCE (L"Search", L"a") SENTENCE (L"Replace", L"a") INTEGER (L"Replace limit", L"0 (=unlimited)") RADIO (L"Search and replace are:", 1) RADIOBUTTON (L"Literals") RADIOBUTTON (L"Regular Expressions") OK DO long nmatches, nstringmatches; LOOP { iam (Strings); praat_new (Strings_change (me, GET_STRING (L"Search"), GET_STRING (L"Replace"), GET_INTEGER (L"Replace limit"), &nmatches, &nstringmatches, GET_INTEGER (L"Search and replace are") - 1), 0); } END FORM (Strings_extractPart, L"Strings: Extract part", L"") NATURAL (L"From index", L"1") NATURAL (L"To index", L"1") OK DO LOOP { iam (Strings); praat_new (Strings_extractPart (me, GET_INTEGER (L"From index"), GET_INTEGER (L"To index")), my name, L"_part"); } END DIRECT (Strings_to_EditDistanceTable) Strings s1 = NULL, s2 = NULL; LOOP { iam(Strings); (s1 ? s2 : s1) = me; } Melder_assert (s1 != NULL && s2 != NULL); autoEditDistanceTable table = EditDistanceTable_create (s1, s2); praat_new (table.transfer(), s1 -> name, L"_", s2 -> name); END FORM (Strings_to_Permutation, L"Strings: To Permutation", L"Strings: To Permutation...") BOOLEAN (L"Sort", 1) OK DO LOOP { iam (Strings); praat_new (Strings_to_Permutation (me, GET_INTEGER (L"Sort")), my name); } END DIRECT (Strings_and_Permutation_permuteStrings) Strings me = FIRST (Strings); Permutation p = FIRST (Permutation); praat_new (Strings_and_Permutation_permuteStrings (me, p), my name, L"_", p->name); END FORM (SVD_to_TableOfReal, L"SVD: To TableOfReal", L"SVD: To TableOfReal...") NATURAL (L"First component", L"1") INTEGER (L"Last component", L"0 (=all)") OK DO LOOP { iam (SVD); praat_new (SVD_to_TableOfReal (me, GET_INTEGER (L"First component"), GET_INTEGER (L"Last component")), my name); } END DIRECT (SVD_extractLeftSingularVectors) LOOP { iam (SVD); praat_new (SVD_extractLeftSingularVectors (me), Thing_getName (me), L"_lsv"); } END DIRECT (SVD_extractRightSingularVectors) LOOP { iam (SVD); praat_new (SVD_extractRightSingularVectors (me), Thing_getName (me), L"_rsv"); } END DIRECT (SVD_extractSingularValues) LOOP { iam (SVD); praat_new (SVD_extractSingularValues (me), Thing_getName (me), L"_sv"); } END /******************* Table ****************************/ DIRECT (Table_createFromPetersonBarneyData) praat_new (Table_createFromPetersonBarneyData (), L"pb"); END DIRECT (Table_createFromPolsVanNieropData) praat_new (Table_createFromPolsVanNieropData (), L"pvn"); END DIRECT (Table_createFromWeeninkData) praat_new (Table_createFromWeeninkData (), L"m10w10c10"); END FORM (Table_drawScatterPlotWithConfidenceIntervals, L"Table: Scatter plot (confidence intervals)", L"") NATURAL (L"Horizontal axis column", L"1") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") INTEGER (L"left Horizontal confidence interval column", L"3") INTEGER (L"right Horizontal confidence interval column", L"4") NATURAL (L"Vertical axis column", L"2") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") INTEGER (L"left Vertical confidence interval column", L"5") INTEGER (L"right Vertical confidence interval column", L"6") REAL (L"Bar size (mm)", L"1.0") BOOLEAN (L"Garnish", 1); OK DO autoPraatPicture picture; LOOP { iam (Table); Table_drawScatterPlotWithConfidenceIntervals (me, GRAPHICS, GET_INTEGER (L"Horizontal axis column"), GET_INTEGER (L"Vertical axis column"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"left Horizontal confidence interval column"), GET_INTEGER (L"right Horizontal confidence interval column"), GET_INTEGER (L"left Vertical confidence interval column"), GET_INTEGER (L"right Vertical confidence interval column"), GET_REAL (L"Bar size"), GET_INTEGER (L"Garnish")); } END /******************* TableOfReal ****************************/ DIRECT (New_CreateIrisDataset) praat_new (TableOfReal_createIrisDataset (), 0); END FORM (TableOfReal_reportMultivariateNormality, L"TableOfReal: Report multivariate normality (BHEP)", L"TableOfReal: Report multivariate normality (BHEP)...") REAL (L"Smoothing parameter", L"0.0") OK DO double h = GET_REAL (L"Smoothing parameter"); MelderInfo_open (); LOOP { iam (TableOfReal); double tnb, lnmu, lnvar; double prob = TableOfReal_normalityTest_BHEP (me, &h, &tnb, &lnmu, &lnvar); MelderInfo_open (); MelderInfo_writeLine1 (L"Baringhaus–Henze–Epps–Pulley normality test:"); MelderInfo_writeLine2 (L"Significance of normality: ", Melder_double (prob)); MelderInfo_writeLine2 (L"BHEP statistic: ", Melder_double (tnb)); MelderInfo_writeLine2 (L"Lognormal mean: ", Melder_double (lnmu)); MelderInfo_writeLine2 (L"Lognormal variance: ", Melder_double (lnvar)); MelderInfo_writeLine2 (L"Smoothing: ", Melder_double (h)); MelderInfo_writeLine2 (L"Sample size: ", Melder_integer (my numberOfRows)); MelderInfo_writeLine2 (L"Number of variables: ", Melder_integer (my numberOfColumns)); } MelderInfo_close (); END DIRECT (TableOfReal_and_Permutation_permuteRows) TableOfReal me = FIRST (TableOfReal); Permutation p = FIRST (Permutation); praat_new (TableOfReal_and_Permutation_permuteRows (me, p), my name, L"_", p->name); END DIRECT (TableOfReal_to_Permutation_sortRowlabels) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Permutation_sortRowLabels (me), my name); } END DIRECT (TableOfReal_appendColumns) autoCollection set = praat_getSelectedObjects (); praat_new (TableOfReal_appendColumnsMany (set.peek()), L"columns_appended"); END FORM (TableOfReal_createFromPolsData_50males, L"Create TableOfReal (Pols 1973)", L"Create TableOfReal (Pols 1973)...") BOOLEAN (L"Include formant levels", 0) OK DO praat_new (TableOfReal_createFromPolsData_50males (GET_INTEGER (L"Include formant levels")), L"pols_50males"); END FORM (TableOfReal_createFromVanNieropData_25females, L"Create TableOfReal (Van Nierop 1973)...", L"Create TableOfReal (Van Nierop 1973)...") BOOLEAN (L"Include formant levels", 0) OK DO praat_new1 (TableOfReal_createFromVanNieropData_25females (GET_INTEGER (L"Include formant levels")), L"vannierop_25females"); END FORM (TableOfReal_createFromWeeninkData, L"Create TableOfReal (Weenink 1985)...", L"Create TableOfReal (Weenink 1985)...") RADIO (L"Speakers group", 1) RADIOBUTTON (L"Men") RADIOBUTTON (L"Women") RADIOBUTTON (L"Children") OK DO int type = GET_INTEGER (L"Speakers group"); praat_new (TableOfReal_createFromWeeninkData (type), (type == 1 ? L"m10" : type == 2 ? L"w10" : L"c10")); END FORM (TableOfReal_drawScatterPlot, L"TableOfReal: Draw scatter plot", L"TableOfReal: Draw scatter plot...") LABEL (L"", L"Select the part of the table") NATURAL (L"Horizontal axis column number", L"1") NATURAL (L"Vertical axis column number", L"2") INTEGER (L"left Row number range", L"0") INTEGER (L"right Row number range", L"0") LABEL (L"", L"Select the drawing area limits") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") NATURAL (L"Label size", L"12") BOOLEAN (L"Use row labels", 0) WORD (L"Label", L"+") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Sound); TableOfReal_drawScatterPlot (me, GRAPHICS, GET_INTEGER (L"Horizontal axis column number"), GET_INTEGER (L"Vertical axis column number"), GET_INTEGER (L"left Row number range"), GET_INTEGER (L"right Row number range"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Use row labels"), GET_STRING (L"Label"), GET_INTEGER (L"Garnish")); } END FORM (TableOfReal_drawScatterPlotMatrix, L"TableOfReal: Draw scatter plots matrix", 0) INTEGER (L"From column", L"0") INTEGER (L"To column", L"0") POSITIVE (L"Fraction white", L"0.1") OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawScatterPlotMatrix (me, GRAPHICS, GET_INTEGER (L"From column"), GET_INTEGER (L"To column"), GET_REAL (L"Fraction white")); } END FORM (TableOfReal_drawBiplot, L"TableOfReal: Draw biplot", L"TableOfReal: Draw biplot...") LABEL (L"", L"") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") REAL (L"Split factor", L"0.5") INTEGER (L"Label size", L"10") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawBiplot (me, GRAPHICS, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Split factor"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END FORM (TableOfReal_drawVectors, L"Draw vectors", L"TableOfReal: Draw vectors...") LABEL (L"", L"From (x1, y1) to (x2, y2)") NATURAL (L"left From columns (x1, y1)", L"1") NATURAL (L"right From columns (x1, y1)", L"2") NATURAL (L"left To columns (x2, y2)", L"3") NATURAL (L"right To columns (x2, y2)", L"4") LABEL (L"", L"Select the drawing area") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") RADIO (L"Vector type", 1) RADIOBUTTON (L"Arrow") RADIOBUTTON (L"Double arrow") RADIOBUTTON (L"Line") INTEGER (L"Label size", L"10") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawVectors (me, GRAPHICS, GET_INTEGER (L"left From columns"), GET_INTEGER (L"right From columns"), GET_INTEGER (L"left To columns"), GET_INTEGER (L"right To columns"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Vector type"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END FORM (TableOfReal_drawRowAsHistogram, L"Draw row as histogram", L"TableOfReal: Draw rows as histogram...") LABEL (L"", L"Select from the table") WORD (L"Row number", L"1") INTEGER (L"left Column range", L"0") INTEGER (L"right Column range", L"0") LABEL (L"", L"Vertical drawing range") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") LABEL (L"", L"Offset and distance in units of 'bar width'") REAL (L"Horizontal offset", L"0.5") REAL (L"Distance between bars", L"1.0") WORD (L"Grey value (1=white)", L"0.7") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawRowsAsHistogram (me, GRAPHICS, GET_STRING (L"Row number"), GET_INTEGER (L"left Column range"), GET_INTEGER (L"right Column range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Horizontal offset"), 0, GET_REAL (L"Distance between bars"), GET_STRING (L"Grey value"), GET_INTEGER (L"Garnish")); } END FORM (TableOfReal_drawRowsAsHistogram, L"Draw rows as histogram", L"TableOfReal: Draw rows as histogram...") LABEL (L"", L"Select from the table") SENTENCE (L"Row numbers", L"1 2") INTEGER (L"left Column range", L"0") INTEGER (L"right Column range", L"0") LABEL (L"", L"Vertical drawing range") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") LABEL (L"", L"Offset and distance in units of 'bar width'") REAL (L"Horizontal offset", L"1.0") REAL (L"Distance between bar groups", L"1.0") REAL (L"Distance between bars", L"0.0") SENTENCE (L"Grey values (1=white)", L"1 1") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawRowsAsHistogram (me, GRAPHICS, GET_STRING (L"Row numbers"), GET_INTEGER (L"left Column range"), GET_INTEGER (L"right Column range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Horizontal offset"), GET_REAL (L"Distance between bars"), GET_REAL (L"Distance between bar groups"), GET_STRING (L"Grey values"), GET_INTEGER (L"Garnish")); } END FORM (TableOfReal_drawBoxPlots, L"TableOfReal: Draw box plots", L"TableOfReal: Draw box plots...") INTEGER (L"From row", L"0") INTEGER (L"To row", L"0") INTEGER (L"From column", L"0") INTEGER (L"To column", L"0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawBoxPlots (me, GRAPHICS, GET_INTEGER (L"From row"), GET_INTEGER (L"To row"), GET_INTEGER (L"From column"), GET_INTEGER (L"To column"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); } END FORM (TableOfReal_drawColumnAsDistribution, L"TableOfReal: Draw column as distribution", L"TableOfReal: Draw column as distribution...") NATURAL (L"Column number", L"1") REAL (L"left Value range", L"0.0") REAL (L"right Value range", L"0.0") REAL (L"left Frequency range", L"0.0") REAL (L"right frequency range", L"0.0") NATURAL (L"Number of bins", L"10") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawColumnAsDistribution (me, GRAPHICS, GET_INTEGER (L"Column number"), GET_REAL (L"left Value range"), GET_REAL (L"right Value range"), GET_INTEGER (L"Number of bins"), GET_REAL (L"left Frequency range"), GET_REAL (L"right frequency range"), 0, GET_INTEGER (L"Garnish")); } END FORM (TableOfReal_to_Configuration_lda, L"TableOfReal: To Configuration (lda)", L"TableOfReal: To Configuration (lda)...") INTEGER (L"Number of dimensions", L"0 (= all)") OK DO long dimension = GET_INTEGER (L"Number of dimensions"); if (dimension < 0) { Melder_throw ("Number of dimensions must be greater equal zero."); } LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Configuration_lda (me, dimension), my name, L"_lda"); } END FORM (TableOfReal_to_CCA, L"TableOfReal: To CCA", L"TableOfReal: To CCA...") NATURAL (L"Dimension of dependent variate", L"2") OK DO LOOP { iam (TableOfReal); praat_new (TableOfReal_to_CCA (me, GET_INTEGER (L"Dimension of dependent variate")), my name); } END FORM (TableOfReal_to_Configuration_pca, L"TableOfReal: To Configuration (pca)", L"TableOfReal: To Configuration (pca)...") NATURAL (L"Number of dimensions", L"2") OK DO LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Configuration_pca (me, GET_INTEGER (L"Number of dimensions")), my name, L"_pca"); } END DIRECT (TableOfReal_to_Discriminant) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Discriminant (me), my name); } END DIRECT (TableOfReal_to_PCA) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_PCA (me), my name); } END FORM (TableOfReal_to_SSCP, L"TableOfReal: To SSCP", L"TableOfReal: To SSCP...") INTEGER (L"Begin row", L"0") INTEGER (L"End row", L"0") INTEGER (L"Begin column", L"0") INTEGER (L"End column", L"0") OK DO LOOP { iam (TableOfReal); praat_new (TableOfReal_to_SSCP (me, GET_INTEGER (L"Begin row"), GET_INTEGER (L"End row"), GET_INTEGER (L"Begin column"), GET_INTEGER (L"End column")), my name); } END /* For the inheritors */ DIRECT (TableOfReal_to_TableOfReal) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_TableOfReal (me), my name); } END DIRECT (TableOfReal_to_Correlation) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Correlation (me), my name); } END DIRECT (TableOfReal_to_Correlation_rank) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Correlation_rank (me), my name); } END DIRECT (TableOfReal_to_Covariance) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Covariance (me), my name); } END DIRECT (TableOfReal_to_SVD) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_SVD (me), my name); } END DIRECT (TablesOfReal_to_Eigen_gsvd) TableOfReal t1 = 0, t2 = 0; LOOP { iam (TableOfReal); (t1 ? t2 : t1) = me; } Melder_assert (t1 && t2); praat_new (TablesOfReal_to_Eigen_gsvd (t1, t2), 0); END FORM (TableOfReal_and_TableOfReal_crossCorrelations, L"TableOfReal & TableOfReal: Cross-correlations", 0) OPTIONMENU (L"Correlations between", 1) OPTION (L"Rows") OPTION (L"Columns") BOOLEAN (L"Center", 0) BOOLEAN (L"Normalize", 0) OK DO int by_columns = GET_INTEGER (L"Correlations between") - 1; TableOfReal t1 = 0, t2 = 0; LOOP { iam (TableOfReal); (t1 ? t2 : t1) = me; } Melder_assert (t1 && t2); praat_new (TableOfReal_and_TableOfReal_crossCorrelations (t1, t2, by_columns, GET_INTEGER (L"Center"), GET_INTEGER (L"Normalize")), (by_columns ? L"by_columns" : L"by_rows"), L"cc"); END DIRECT (TablesOfReal_to_GSVD) TableOfReal t1 = 0, t2 = 0; LOOP { iam (TableOfReal); (t1 ? t2 : t1) = me; } Melder_assert (t1 && t2); praat_new (TablesOfReal_to_GSVD (t1, t2), 0); END FORM (TableOfReal_choleskyDecomposition, L"TableOfReal: Cholesky decomposition", 0) BOOLEAN (L"Upper (else L)", 0) BOOLEAN (L"Inverse", 0) OK DO LOOP { iam (TableOfReal); praat_new (TableOfReal_choleskyDecomposition (me, GET_INTEGER (L"Upper"), GET_INTEGER (L"Inverse")), my name); } END FORM (TableOfReal_to_Pattern_and_Categories, L"TableOfReal: To Pattern and Categories", L"TableOfReal: To Pattern and Categories...") INTEGER (L"left Row range", L"0") INTEGER (L"right Row range", L"0 (=all)") INTEGER (L"left Column range", L"0") INTEGER (L"right Column range", L"0 (=all)") OK DO LOOP { iam (TableOfReal); Pattern p = 0; Categories c = 0; TableOfReal_to_Pattern_and_Categories (me, GET_INTEGER (L"left Row range"), GET_INTEGER (L"right Row range"), GET_INTEGER (L"left Column range"), GET_INTEGER (L"right Column range"), &p, &c); autoPattern ap = p; autoCategories ac = c; praat_new (ap.transfer(), Thing_getName (me)); praat_new (ac.transfer(), Thing_getName (me)); } END FORM (TableOfReal_getColumnSum, L"TableOfReal: Get column sum", L"") INTEGER (L"Column", L"1") OK DO LOOP { iam (TableOfReal); Melder_information (Melder_double (TableOfReal_getColumnSum (me, GET_INTEGER (L"Column")))); } END FORM (TableOfReal_getRowSum, L"TableOfReal: Get row sum", L"") INTEGER (L"Row", L"1") OK DO LOOP { iam (TableOfReal); Melder_information (Melder_double (TableOfReal_getRowSum (me, GET_INTEGER (L"Row")))); } END DIRECT (TableOfReal_getGrandSum) LOOP { iam (TableOfReal); Melder_information (Melder_double (TableOfReal_getGrandSum (me))); } END FORM (TableOfReal_meansByRowLabels, L"TableOfReal: Means by row labels", L"TableOfReal: To TableOfReal (means by row labels)...") BOOLEAN (L"Expand", 0) OK DO LOOP { iam (TableOfReal); praat_new (TableOfReal_meansByRowLabels (me, GET_INTEGER (L"Expand"), 0), NAME, L"_byrowlabels"); } END FORM (TableOfReal_mediansByRowLabels, L"TableOfReal: Medians by row labels", L"TableOfReal: To TableOfReal (medians by row labels)...") BOOLEAN (L"Expand", 0) OK DO LOOP { iam (TableOfReal); praat_new (TableOfReal_meansByRowLabels (me, GET_INTEGER (L"Expand"), 1), Thing_getName (me), L"_byrowlabels"); } END /***** TableOfReal and FilterBank *****/ FORM (TextGrid_extendTime, L"TextGrid: Extend time", L"TextGrid: Extend time...") LABEL (L"", L"") POSITIVE (L"Extend domain by (s)", L"1.0") RADIO (L"At", 1) RADIOBUTTON (L"End") RADIOBUTTON (L"Start") OK DO LOOP { iam (TextGrid); TextGrid_extendTime (me, GET_REAL (L"Extend domain by"), GET_INTEGER (L"At") - 1); praat_dataChanged (me); } END FORM (TextGrid_replaceIntervalTexts, L"TextGrid: Replace interval text", L"TextGrid: Replace interval text...") LABEL (L"", L"") NATURAL (L"Tier number", L"1") INTEGER (L"left Interval range", L"0") INTEGER (L"right Interval range", L"0") SENTENCE (L"Search", L"a") SENTENCE (L"Replace", L"a") RADIO (L"Search and replace strings are:", 1) RADIOBUTTON (L"Literals") RADIOBUTTON (L"Regular Expressions") OK DO long from = GET_INTEGER (L"left Interval range"); long to = GET_INTEGER (L"right Interval range"); int isregexp = GET_INTEGER (L"Search and replace strings are") - 1; wchar_t *search = GET_STRING (L"Search"); LOOP { iam (TextGrid); long nmatches, nstringmatches; TextGrid_changeLabels (me, GET_INTEGER (L"Tier number"), from, to, search, GET_STRING (L"Replace"), isregexp, &nmatches, &nstringmatches); praat_dataChanged (me); } END FORM (TextGrid_replacePointTexts, L"TextGrid: Replace point text", L"TextGrid: Replace point text...") LABEL (L"", L"") NATURAL (L"Tier number", L"1") INTEGER (L"left Interval range", L"0") INTEGER (L"right Interval range", L"0") SENTENCE (L"Search", L"a") SENTENCE (L"Replace", L"a") RADIO (L"Search and replace strings are:", 1) RADIOBUTTON (L"Literals") RADIOBUTTON (L"Regular Expressions") OK DO long from = GET_INTEGER (L"left Interval range"); long to = GET_INTEGER (L"right Interval range"); LOOP { iam (TextGrid); long nmatches, nstringmatches; TextGrid_changeLabels (me, GET_INTEGER (L"Tier number"), from, to, GET_STRING (L"Search"), GET_STRING (L"Replace"), GET_INTEGER (L"Search and replace strings are") - 1, &nmatches, &nstringmatches); praat_dataChanged (me); } END FORM (TextGrids_to_Table_textAlignmentment, L"TextGrids: To Table (text alignment)", 0) NATURAL (L"Target tier", L"1") NATURAL (L"Source tier", L"1") OK DO TextGrid tg1 = 0, tg2 = 0; LOOP { iam (TextGrid); (tg1 ? tg2 : tg1) = me; } Melder_assert (tg1 && tg2); praat_new (TextGrids_to_Table_textAlignmentment (tg1, GET_INTEGER (L"Target tier"), tg2, GET_INTEGER (L"Source tier"), 0), tg1 -> name, L"_", tg2 -> name); END FORM (TextGrids_and_EditCostsTable_to_Table_textAlignmentment, L"TextGrids & EditCostsTable: To Table(text alignmentment)", 0) NATURAL (L"Target tier", L"1") NATURAL (L"Source tier", L"1") OK DO TextGrid tg1 = 0, tg2 = 0; EditCostsTable ect = 0; LOOP { if (CLASS == classTextGrid) { (tg1 ? tg2 : tg1) = (TextGrid) OBJECT; } else { ect = (EditCostsTable) OBJECT; } } Melder_assert (tg1 && tg2 && ect); praat_new (TextGrids_to_Table_textAlignmentment (tg1, GET_INTEGER (L"Target tier"), tg2, GET_INTEGER (L"Source tier"), ect), tg1 -> name, L"_", tg2 -> name); END FORM (TextGrid_setTierName, L"TextGrid: Set tier name", L"TextGrid: Set tier name...") NATURAL (L"Tier number:", L"1") SENTENCE (L"Name", L""); OK DO LOOP { iam (TextGrid); TextGrid_setTierName (me, GET_INTEGER (L"Tier number"), GET_STRING (L"Name")); praat_dataChanged (me); } END DIRECT (VowelEditor_create) if (theCurrentPraatApplication -> batch) { Melder_throw ("Cannot edit from batch."); } autoVowelEditor vowelEditor = VowelEditor_create (theCurrentPraatApplication -> topShell, L"VowelEditor", NULL); vowelEditor.transfer(); // user becomes the owner END static Any cmuAudioFileRecognizer (int nread, const char *header, MelderFile fs) { return nread < 12 || header [0] != 6 || header [1] != 0 ? NULL : Sound_readFromCmuAudioFile (fs); } void praat_CC_init (ClassInfo klas) { praat_addAction1 (klas, 1, L"Paint...", 0, 1, DO_CC_paint); praat_addAction1 (klas, 1, L"Draw...", 0, 1, DO_CC_drawC0); praat_addAction1 (klas, 1, QUERY_BUTTON, 0, 0, 0); praat_TimeFrameSampled_query_init (klas); praat_addAction1 (klas, 1, L"Get value...", 0, 1, DO_CC_getValue); praat_addAction1 (klas, 0, L"To Matrix", 0, 0, DO_CC_to_Matrix); praat_addAction1 (klas, 2, L"To DTW...", 0, 0, DO_CCs_to_DTW); } static void praat_Eigen_Matrix_project (ClassInfo klase, ClassInfo klasm); static void praat_Eigen_Matrix_project (ClassInfo klase, ClassInfo klasm) { praat_addAction2 (klase, 1, klasm, 1, L"Project...", 0, 0, DO_Eigen_and_Matrix_project); } static void praat_Eigen_query_init (ClassInfo klas) { praat_addAction1 (klas, 1, L"Get eigenvalue...", 0, 1, DO_Eigen_getEigenvalue); praat_addAction1 (klas, 1, L"Get sum of eigenvalues...", 0, 1, DO_Eigen_getSumOfEigenvalues); praat_addAction1 (klas, 1, L"Get number of eigenvectors", 0, 1, DO_Eigen_getNumberOfEigenvalues); praat_addAction1 (klas, 1, L"Get eigenvector dimension", 0, 1, DO_Eigen_getDimension); praat_addAction1 (klas, 1, L"Get eigenvector element...", 0, 1, DO_Eigen_getEigenvectorElement); } static void praat_Eigen_draw_init (ClassInfo klas) { praat_addAction1 (klas, 0, L"Draw eigenvalues...", 0, 1, DO_Eigen_drawEigenvalues); praat_addAction1 (klas, 0, L"Draw eigenvalues (scree)...", 0, praat_DEPTH_1 | praat_HIDDEN, DO_Eigen_drawEigenvalues_scree); praat_addAction1 (klas, 0, L"Draw eigenvector...", 0, 1, DO_Eigen_drawEigenvector); } static void praat_Index_init (ClassInfo klas) { praat_addAction1 (klas, 1, L"Get number of classes", 0, 0, DO_Index_getNumberOfClasses); praat_addAction1 (klas, 1, L"To Permutation...", 0, 0, DO_Index_to_Permutation); praat_addAction1 (klas, 1, L"Extract part...", 0, 0, DO_Index_extractPart); } static void praat_FilterBank_query_init (ClassInfo klas); static void praat_FilterBank_query_init (ClassInfo klas) { praat_addAction1 (klas, 0, QUERY_BUTTON, 0, 0, 0); praat_Matrixft_query_init (klas); praat_addAction1 (klas, 0, L"-- frequency scales --", 0, 1, 0); praat_addAction1 (klas, 1, L"Get frequency in Hertz...", 0, 1, DO_FilterBank_getFrequencyInHertz); praat_addAction1 (klas, 1, L"Get frequency in Bark...", 0, 1, DO_FilterBank_getFrequencyInBark); praat_addAction1 (klas, 1, L"Get frequency in mel...", 0, 1, DO_FilterBank_getFrequencyInMel); } static void praat_FilterBank_modify_init (ClassInfo klas); static void praat_FilterBank_modify_init (ClassInfo klas) { praat_addAction1 (klas, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (klas, 0, L"Equalize intensities...", 0, 1, DO_FilterBank_equalizeIntensities); } static void praat_FilterBank_draw_init (ClassInfo klas); static void praat_FilterBank_draw_init (ClassInfo klas) { praat_addAction1 (klas, 0, DRAW_BUTTON, 0, 0, 0); praat_addAction1 (klas, 0, L"Draw filters...", 0, 1, DO_FilterBank_drawFilters); praat_addAction1 (klas, 0, L"Draw one contour...", 0, 1, DO_FilterBank_drawOneContour); praat_addAction1 (klas, 0, L"Draw contours...", 0, 1, DO_FilterBank_drawContours); praat_addAction1 (klas, 0, L"Paint image...", 0, 1, DO_FilterBank_paintImage); praat_addAction1 (klas, 0, L"Paint contours...", 0, 1, DO_FilterBank_paintContours); praat_addAction1 (klas, 0, L"Paint cells...", 0, 1, DO_FilterBank_paintCells); praat_addAction1 (klas, 0, L"Paint surface...", 0, 1, DO_FilterBank_paintSurface); praat_addAction1 (klas, 0, L"-- frequency scales --", 0, 1, 0); praat_addAction1 (klas, 0, L"Draw frequency scales...", 0, 1, DO_FilterBank_drawFrequencyScales); } static void praat_FilterBank_all_init (ClassInfo klas); static void praat_FilterBank_all_init (ClassInfo klas) { praat_FilterBank_draw_init (klas); praat_FilterBank_query_init (klas); praat_FilterBank_modify_init (klas); praat_addAction1 (klas, 0, L"To Intensity", 0, 0, DO_FilterBank_to_Intensity); praat_addAction1 (klas, 0, L"To Matrix", 0, 0, DO_FilterBank_to_Matrix); praat_addAction1 (klas, 2, L"Cross-correlate...", 0, 0, DO_FilterBanks_crossCorrelate); praat_addAction1 (klas, 2, L"Convolve...", 0, 0, DO_FilterBanks_convolve); } static void praat_FunctionTerms_init (ClassInfo klas) { praat_addAction1 (klas, 0, DRAW_BUTTON, 0, 0, 0); praat_addAction1 (klas, 0, L"Draw...", 0, 1, DO_FunctionTerms_draw); praat_addAction1 (klas, 0, L"Draw basis function...", 0, 1, DO_FunctionTerms_drawBasisFunction); praat_addAction1 (klas, 0, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (klas, 1, L"Get number of coefficients", 0, 1, DO_FunctionTerms_getNumberOfCoefficients); praat_addAction1 (klas, 1, L"Get coefficient...", 0, 1, DO_FunctionTerms_getCoefficient); praat_addAction1 (klas, 1, L"Get degree", 0, 1, DO_FunctionTerms_getDegree); praat_addAction1 (klas, 0, L"-- function specifics --", 0, 1, 0); praat_addAction1 (klas, 1, L"Get value...", 0, 1, DO_FunctionTerms_evaluate); praat_addAction1 (klas, 1, L"Get minimum...", 0, 1, DO_FunctionTerms_getMinimum); praat_addAction1 (klas, 1, L"Get x of minimum...", 0, 1, DO_FunctionTerms_getXOfMinimum); praat_addAction1 (klas, 1, L"Get maximum...", 0, 1, DO_FunctionTerms_getMaximum); praat_addAction1 (klas, 1, L"Get x of maximum...", 0, 1, DO_FunctionTerms_getXOfMaximum); praat_addAction1 (klas, 0, L"Modify -", 0, 0, 0); praat_addAction1 (klas, 1, L"Set domain...", 0, 1, DO_FunctionTerms_setDomain); praat_addAction1 (klas, 1, L"Set coefficient...", 0, 1, DO_FunctionTerms_setCoefficient); praat_addAction1 (klas, 0, L"Analyse", 0, 0, 0); } /* Query buttons for frame-based frequency x time subclasses of matrix. */ void praat_Matrixft_query_init (ClassInfo klas) { praat_TimeFrameSampled_query_init (klas); praat_addAction1 (klas, 1, L"Get time from column...", 0, 1, DO_Matrixft_getXofColumn); praat_addAction1 (klas, 1, L"-- frequencies --", 0, 1, 0); praat_addAction1 (klas, 1, L"Get lowest frequency", 0, 1, DO_Matrixft_getLowestFrequency); praat_addAction1 (klas, 1, L"Get highest frequency", 0, 1, DO_Matrixft_getHighestFrequency); praat_addAction1 (klas, 1, L"Get number of frequencies", 0, 1, DO_Matrixft_getNumberOfFrequencies); praat_addAction1 (klas, 1, L"Get frequency distance", 0, 1, DO_Matrixft_getFrequencyDistance); praat_addAction1 (klas, 1, L"Get frequency from row...", 0, 1, DO_Matrixft_getFrequencyOfRow); praat_addAction1 (klas, 1, L"-- get value --", 0, 1, 0); praat_addAction1 (klas, 1, L"Get value in cell...", 0, 1, DO_Matrixft_getValueInCell); } static void praat_Spline_init (ClassInfo klas) { praat_FunctionTerms_init (klas); praat_addAction1 (klas, 0, L"Draw knots...", L"Draw basis function...", 1, DO_Spline_drawKnots); praat_addAction1 (klas, 1, L"Get order", L"Get degree", 1, DO_Spline_getOrder); praat_addAction1 (klas, 1, L"Scale x...", L"Analyse", 0, DO_Spline_scaleX); } static void praat_SSCP_query_init (ClassInfo klas) { praat_addAction1 (klas, 1, L"-- statistics --", L"Get value...", 1, 0); praat_addAction1 (klas, 1, L"Get number of observations", L"-- statistics --", 1, DO_SSCP_getNumberOfObservations); praat_addAction1 (klas, 1, L"Get degrees of freedom", L"Get number of observations", 1, DO_SSCP_getDegreesOfFreedom); praat_addAction1 (klas, 1, L"Get centroid element...", L"Get degrees of freedom", 1, DO_SSCP_getCentroidElement); praat_addAction1 (klas, 1, L"Get ln(determinant)", L"Get centroid element...", 1, DO_SSCP_getLnDeterminant); } static void praat_SSCP_extract_init (ClassInfo klas) { praat_addAction1 (klas, 1, L"Extract centroid", EXTRACT_BUTTON, 1, DO_SSCP_extractCentroid); } FORM (SSCP_setValue, L"Covariance: Set value", L"Covariance: Set value...") NATURAL (L"Row number", L"1") NATURAL (L"Column number", L"1") REAL (L"New value", L"1.0") OK DO LOOP { iam (SSCP); SSCP_setValue (me, GET_INTEGER (L"Row number"), GET_INTEGER (L"Column number"), GET_REAL (L"New value")); } END FORM (SSCP_setCentroid, L"", 0) NATURAL (L"Element number", L"1") REAL (L"New value", L"1.0") OK DO LOOP { iam (SSCP); SSCP_setCentroid (me, GET_INTEGER (L"Element number"), GET_REAL (L"New value")); } END void praat_SSCP_as_TableOfReal_init (ClassInfo klas) { praat_TableOfReal_init (klas); praat_removeAction (klas, NULL, NULL, L"Set value..."); praat_addAction1 (klas, 1, L"Set centroid...", L"Formula...", 1, DO_SSCP_setCentroid); praat_addAction1 (klas, 1, L"Set value...", L"Formula...", 1, DO_SSCP_setValue); praat_addAction1 (klas, 0, L"To TableOfReal", L"To Matrix", 1, DO_TableOfReal_to_TableOfReal); } void praat_TableOfReal_init2 (ClassInfo klas) { praat_TableOfReal_init (klas); praat_addAction1 (klas, 0, L"To TableOfReal", L"To Matrix", 1, DO_TableOfReal_to_TableOfReal); } void praat_EditDistanceTable_as_TableOfReal_init (ClassInfo klas) { praat_TableOfReal_init (klas); praat_addAction1 (klas, 0, L"Set default costs...", L"Formula...", 1, DO_EditDistanceTable_setDefaultCosts); praat_removeAction (klas, NULL, NULL, L"Draw as numbers..."); praat_addAction1 (klas, 0, L"Draw...", L"Draw -", 1, DO_EditDistanceTable_draw); praat_addAction1 (klas, 0, L"Draw edit operations", L"Draw...", 1, DO_EditDistanceTable_drawEditOperations); praat_removeAction (klas, NULL, NULL, L"Draw as numbers if..."); praat_removeAction (klas, NULL, NULL, L"Draw as squares..."); praat_removeAction (klas, NULL, NULL, L"Draw vertical lines..."); praat_removeAction (klas, NULL, NULL, L"Draw horizontal lines..."); praat_removeAction (klas, NULL, NULL, L"Draw left and right lines..."); praat_removeAction (klas, NULL, NULL, L"Draw top and bottom lines..."); praat_removeAction (klas, NULL, NULL, L"-- draw lines --"); } void praat_uvafon_David_init (); void praat_uvafon_David_init () { Data_recognizeFileType (TextGrid_TIMITLabelFileRecognizer); Data_recognizeFileType (cmuAudioFileRecognizer); Thing_recognizeClassesByName (classActivation, classBarkFilter, classCategories, classCepstrum, classCCA, classChebyshevSeries, classClassificationTable, classConfusion, classCorrelation, classCovariance, classDiscriminant, classDTW, classEigen, classExcitations, classEditCostsTable, classEditDistanceTable, classFileInMemory, classFilesInMemory, classFormantFilter, classIndex, classKlattTable, classPermutation, classISpline, classLegendreSeries, classMelFilter, classMSpline, classPattern, classPCA, classPolynomial, classRoots, classSimpleString, classStringsIndex, classSpeechSynthesizer, classSPINET, classSSCP, classSVD, NULL); VowelEditor_prefs (); espeakdata_praat_init (); praat_addMenuCommand (L"Objects", L"Goodies", L"Report floating point properties", 0, 0, DO_Praat_ReportFloatingPointProperties); praat_addMenuCommand (L"Objects", L"New", L"Create Strings from espeak voices", L"Create Strings as directory list...", 1 + praat_HIDDEN, DO_Strings_createFromEspeakVoices); praat_addMenuCommand (L"Objects", L"New", L"Create iris data set", L"Create TableOfReal...", 1, DO_New_CreateIrisDataset); praat_addMenuCommand (L"Objects", L"New", L"Create Permutation...", 0, 0, DO_Permutation_create); praat_addMenuCommand (L"Objects", L"New", L"Polynomial", 0, 0, 0); praat_addMenuCommand (L"Objects", L"New", L"Create Polynomial...", 0, 1, DO_Polynomial_create); praat_addMenuCommand (L"Objects", L"New", L"Create LegendreSeries...", 0, 1, DO_LegendreSeries_create); praat_addMenuCommand (L"Objects", L"New", L"Create ChebyshevSeries...", 0, 1, DO_ChebyshevSeries_create); praat_addMenuCommand (L"Objects", L"New", L"Create MSpline...", 0, 1, DO_MSpline_create); praat_addMenuCommand (L"Objects", L"New", L"Create ISpline...", 0, 1, DO_ISpline_create); praat_addMenuCommand (L"Objects", L"New", L"Create Sound from gammatone...", L"Create Sound from tone complex...", 1, DO_Sound_createFromGammaTone); praat_addMenuCommand (L"Objects", L"New", L"Create Sound from gamma-tone...", L"Create Sound from tone complex...", praat_DEPTH_1 | praat_HIDDEN, DO_Sound_createFromGammaTone); praat_addMenuCommand (L"Objects", L"New", L"Create Sound from Shepard tone...", L"Create Sound from gammatone...", 1, DO_Sound_createFromShepardTone); praat_addMenuCommand (L"Objects", L"New", L"Create Sound from VowelEditor...", L"Create Sound from Shepard tone...", praat_DEPTH_1, DO_VowelEditor_create); praat_addMenuCommand (L"Objects", L"New", L"Create SpeechSynthesizer...", L"Create Sound from VowelEditor...", praat_DEPTH_1, DO_SpeechSynthesizer_create); praat_addMenuCommand (L"Objects", L"New", L"Create formant table (Pols & Van Nierop 1973)", L"Create Table...", 1, DO_Table_createFromPolsVanNieropData); praat_addMenuCommand (L"Objects", L"New", L"Create formant table (Peterson & Barney 1952)", L"Create Table...", 1, DO_Table_createFromPetersonBarneyData); praat_addMenuCommand (L"Objects", L"New", L"Create formant table (Weenink 1985)", L"Create formant table (Peterson & Barney 1952)", 1, DO_Table_createFromWeeninkData); praat_addMenuCommand (L"Objects", L"New", L"Create TableOfReal (Pols 1973)...", L"Create TableOfReal...", 1, DO_TableOfReal_createFromPolsData_50males); praat_addMenuCommand (L"Objects", L"New", L"Create TableOfReal (Van Nierop 1973)...", L"Create TableOfReal (Pols 1973)...", 1, DO_TableOfReal_createFromVanNieropData_25females); praat_addMenuCommand (L"Objects", L"New", L"Create TableOfReal (Weenink 1985)...", L"Create TableOfReal (Van Nierop 1973)...", 1, DO_TableOfReal_createFromWeeninkData); praat_addMenuCommand (L"Objects", L"New", L"Create simple Confusion...", L"Create TableOfReal (Weenink 1985)...", 1, DO_Confusion_createSimple); praat_addMenuCommand (L"Objects", L"New", L"Create simple Covariance...", L"Create simple Confusion...", 1, DO_Covariance_createSimple); praat_addMenuCommand (L"Objects", L"New", L"Create empty EditCostsTable...", L"Create simple Covariance...", 1, DO_EditCostsTable_createEmpty); praat_addMenuCommand (L"Objects", L"New", L"Create KlattTable example", L"Create TableOfReal (Weenink 1985)...", praat_DEPTH_1 + praat_HIDDEN, DO_KlattTable_createExample); praat_addMenuCommand (L"Objects", L"New", L"Create Strings as characters...", L"Create TextGrid...", praat_HIDDEN, DO_Strings_createAsCharacters); praat_addMenuCommand (L"Objects", L"New", L"Create Strings as tokens...", L"Create TextGrid...", praat_HIDDEN, DO_Strings_createAsTokens); praat_addMenuCommand (L"Objects", L"New", L"Create simple Polygon...", 0, praat_HIDDEN, DO_Polygon_createSimple); praat_addMenuCommand (L"Objects", L"New", L"Create Polygon (random vertices)...", 0, praat_HIDDEN, DO_Polygon_createFromRandomVertices); praat_addMenuCommand (L"Objects", L"New", L"FilesInMemory", 0, praat_HIDDEN, 0); praat_addMenuCommand (L"Objects", L"New", L"Create FileInMemory...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_FileInMemory_create); praat_addMenuCommand (L"Objects", L"New", L"Create copy from FilesInMemory...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_FilesInMemory_createCopyFromFilesInMemory); praat_addMenuCommand (L"Objects", L"New", L"Create FilesInMemory from directory contents...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_FilesInMemory_createFromDirectoryContents); praat_addMenuCommand (L"Objects", L"Open", L"Read Sound from raw 16-bit Little Endian file...", L"Read from special sound file", 1, DO_Sound_readFromRawFileLE); praat_addMenuCommand (L"Objects", L"Open", L"Read Sound from raw 16-bit Big Endian file...", L"Read Sound from raw 16-bit Little Endian file...", 1, DO_Sound_readFromRawFileBE); praat_addMenuCommand (L"Objects", L"Open", L"Read KlattTable from raw text file...", L"Read Matrix from raw text file...", praat_HIDDEN, DO_KlattTable_readFromRawTextFile); praat_addAction1 (classActivation, 0, L"Modify", 0, 0, 0); praat_addAction1 (classActivation, 0, L"Formula...", 0, 0, DO_Activation_formula); praat_addAction1 (classActivation, 0, L"Hack", 0, 0, 0); praat_addAction1 (classActivation, 0, L"To Matrix", 0, 0, DO_Activation_to_Matrix); praat_addAction2 (classActivation, 1, classCategories, 1, L"To TableOfReal", 0, 0, DO_Matrix_Categories_to_TableOfReal); praat_addAction1 (classBarkFilter, 0, L"BarkFilter help", 0, 0, DO_BarkFilter_help); praat_FilterBank_all_init (classBarkFilter); praat_addAction1 (classBarkFilter, 0, L"Draw spectrum (slice)...", L"Draw filters...", 1, DO_BarkFilter_drawSpectrum); praat_addAction1 (classBarkFilter, 1, L"Draw filter functions...", L"Draw filters...", 1, DO_BarkFilter_drawSekeyHansonFilterFunctions); praat_addAction1 (classCategories, 0, L"Edit", 0, 0, DO_Categories_edit); praat_addAction1 (classCategories, 0, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (classCategories, 1, L"Get number of categories", QUERY_BUTTON, 1, DO_Categories_getNumberOfCategories); praat_addAction1 (classCategories, 2, L"Get difference", QUERY_BUTTON, praat_HIDDEN | praat_DEPTH_1, DO_Categories_difference); praat_addAction1 (classCategories, 2, L"Get number of differences", QUERY_BUTTON, 1, DO_Categories_getNumberOfDifferences); praat_addAction1 (classCategories, 2, L"Get fraction different", QUERY_BUTTON, 1, DO_Categories_getFractionDifferent); praat_addAction1 (classCategories, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classCategories, 1, L"Append 1 category...", MODIFY_BUTTON, 1, DO_Categories_append); praat_addAction1 (classCategories, 0, L"Extract", 0, 0, 0); praat_addAction1 (classCategories, 0, L"To unique Categories", 0, 0, DO_Categories_selectUniqueItems); praat_addAction1 (classCategories, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classCategories, 2, L"To Confusion", 0, 0, DO_Categories_to_Confusion); praat_addAction1 (classCategories, 0, L"Synthesize", 0, 0, 0); praat_addAction1 (classCategories, 2, L"Join", 0, 0, DO_Categories_join); praat_addAction1 (classCategories, 0, L"Permute items", 0, 0, DO_Categories_permuteItems); praat_addAction1 (classCategories, 0, L"To Strings", 0, 0, DO_Categories_to_Strings); praat_addAction1 (classChebyshevSeries, 0, L"ChebyshevSeries help", 0, 0, DO_ChebyshevSeries_help); praat_FunctionTerms_init (classChebyshevSeries); praat_addAction1 (classChebyshevSeries, 0, L"To Polynomial", L"Analyse", 0, DO_ChebyshevSeries_to_Polynomial); praat_addAction1 (classCCA, 1, L"Draw eigenvector...", 0, 0, DO_CCA_drawEigenvector); praat_addAction1 (classCCA, 1, L"Get number of correlations", 0, 0, DO_CCA_getNumberOfCorrelations); praat_addAction1 (classCCA, 1, L"Get correlation...", 0, 0, DO_CCA_getCorrelationCoefficient); praat_addAction1 (classCCA, 1, L"Get eigenvector element...", 0, 0, DO_CCA_getEigenvectorElement); praat_addAction1 (classCCA, 1, L"Get zero correlation probability...", 0, 0, DO_CCA_getZeroCorrelationProbability); praat_addAction2 (classCCA, 1, classTableOfReal, 1, L"To TableOfReal (scores)...", 0, 0, DO_CCA_and_TableOfReal_scores); praat_addAction2 (classCCA, 1, classTableOfReal, 1, L"To TableOfReal (loadings)", 0, 0, DO_CCA_and_TableOfReal_factorLoadings); praat_addAction2 (classCCA, 1, classTableOfReal, 1, L"Predict...", 0, 0, DO_CCA_and_TableOfReal_predict); praat_addAction2 (classCCA, 1, classCorrelation, 1, L"To TableOfReal (loadings)", 0, 0, DO_CCA_and_Correlation_factorLoadings); praat_addAction2 (classCCA, 1, classCorrelation, 1, L"Get variance fraction...", 0, 0, DO_CCA_and_Correlation_getVarianceFraction); praat_addAction2 (classCCA, 1, classCorrelation, 1, L"Get redundancy (sl)...", 0, 0, DO_CCA_and_Correlation_getRedundancy_sl); praat_addAction1 (classConfusion, 0, L"Confusion help", 0, 0, DO_Confusion_help); praat_TableOfReal_init2 (classConfusion); praat_removeAction (classConfusion, NULL, NULL, L"Draw as numbers..."); praat_removeAction (classConfusion, NULL, NULL, L"Sort by label..."); praat_removeAction (classConfusion, NULL, NULL, L"Sort by column..."); praat_addAction1 (classConfusion, 0, L"Draw as numbers...", L"Draw -", 1, DO_Confusion_drawAsNumbers); praat_addAction1 (classConfusion, 1, L"Get value (labels)...", L"Get value...", 1, DO_Confusion_getValue); praat_addAction1 (classConfusion, 0, L"-- confusion statistics --", L"Get value (labels)...", 1, 0); praat_addAction1 (classConfusion, 1, L"Get fraction correct", L"-- confusion statistics --", 1, DO_Confusion_getFractionCorrect); praat_addAction1 (classConfusion, 1, L"Get stimulus sum...", L"Get fraction correct", 1, DO_Confusion_getStimulusSum); praat_addAction1 (classConfusion, 1, L"Get row sum...", L"Get fraction correct", praat_DEPTH_1 | praat_HIDDEN, DO_TableOfReal_getRowSum); praat_addAction1 (classConfusion, 1, L"Get response sum...", L"Get stimulus sum...", 1, DO_Confusion_getResponseSum); praat_addAction1 (classConfusion, 1, L"Get column sum...", L"Get row sum...", praat_DEPTH_1 | praat_HIDDEN, DO_TableOfReal_getColumnSum); praat_addAction1 (classConfusion, 1, L"Get grand sum", L"Get response sum...", 1, DO_TableOfReal_getGrandSum); praat_addAction1 (classConfusion, 0, L"Increase...", L"Formula...", 1, DO_Confusion_increase); praat_addAction1 (classConfusion, 0, L"To TableOfReal (marginals)", L"To TableOfReal", 0, DO_Confusion_to_TableOfReal_marginals); praat_addAction1 (classConfusion, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classConfusion, 0, L"Condense...", 0, praat_HIDDEN, DO_Confusion_condense); praat_addAction1 (classConfusion, 0, L"Group...", 0, 0, DO_Confusion_group); praat_addAction1 (classConfusion, 0, L"Group stimuli...", 0, 0, DO_Confusion_groupStimuli); praat_addAction1 (classConfusion, 0, L"Group responses...", 0, 0, DO_Confusion_groupResponses); praat_addAction1 (classConfusion, 2, L"To difference matrix", 0, 0, DO_Confusion_difference); praat_addAction2 (classConfusion, 1, classMatrix, 1, L"Draw", 0, 0, 0); praat_addAction2 (classConfusion, 1, classMatrix, 1, L"Draw confusion...", 0, 0, DO_Confusion_Matrix_draw); praat_addAction1 (classCovariance, 0, L"Covariance help", 0, 0, DO_Covariance_help); praat_SSCP_as_TableOfReal_init (classCovariance); praat_SSCP_query_init (classCovariance); praat_SSCP_extract_init (classCovariance); praat_addAction1 (classCovariance, 1, L"Get probability at position...", L"Get value...", 1, DO_Covariance_getProbabilityAtPosition); praat_addAction1 (classCovariance, 1, L"Get diagonality (bartlett)...", L"Get ln(determinant)", 1, DO_SSCP_testDiagonality_bartlett); praat_addAction1 (classCovariance, 1, L"Get significance of one mean...", L"Get diagonality (bartlett)...", 1, DO_Covariance_getSignificanceOfOneMean); praat_addAction1 (classCovariance, 1, L"Get significance of means difference...", L"Get significance of one mean...", 1, DO_Covariance_getSignificanceOfMeansDifference); praat_addAction1 (classCovariance, 1, L"Get significance of one variance...", L"Get significance of means difference...", 1, DO_Covariance_getSignificanceOfOneVariance); praat_addAction1 (classCovariance, 1, L"Get significance of variances ratio...", L"Get significance of one variance...", 1, DO_Covariance_getSignificanceOfVariancesRatio); praat_addAction1 (classCovariance, 1, L"Get fraction variance...", L"Get significance of variances ratio...", 1, DO_Covariance_getFractionVariance); praat_addAction1 (classCovariance, 2, L"Report multivariate mean difference...", L"Get fraction variance...", 1, DO_Covariances_reportMultivariateMeanDifference); praat_addAction1 (classCovariance, 2, L"Difference", L"Report multivariate mean difference...", praat_DEPTH_1 | praat_HIDDEN, DO_Covariances_reportEquality); praat_addAction1 (classCovariance, 0, L"Report equality of covariances", L"Report multivariate mean difference...", praat_DEPTH_1 | praat_HIDDEN, DO_Covariances_reportEquality); praat_addAction1 (classCovariance, 0, L"To TableOfReal (random sampling)...", 0, 0, DO_Covariance_to_TableOfReal_randomSampling); praat_addAction1 (classCovariance, 0, L"To Correlation", 0, 0, DO_Covariance_to_Correlation); praat_addAction1 (classCovariance, 0, L"To PCA", 0, 0, DO_Covariance_to_PCA); praat_addAction2 (classCovariance, 1, classTableOfReal, 1, L"To TableOfReal (mahalanobis)...", 0, 0, DO_Covariance_and_TableOfReal_mahalanobis); praat_addAction1 (classClassificationTable, 0, L"ClassificationTable help", 0, 0, DO_ClassificationTable_help); praat_TableOfReal_init (classClassificationTable); praat_addAction1 (classClassificationTable, 0, L"To Confusion", 0, 0, DO_ClassificationTable_to_Confusion); praat_addAction1 (classClassificationTable, 0, L"To Correlation (columns)", 0, 0, DO_ClassificationTable_to_Correlation_columns); praat_addAction1 (classClassificationTable, 0, L"To Strings (max. prob.)", 0, 0, DO_ClassificationTable_to_Strings_maximumProbability); praat_addAction1 (classCorrelation, 0, L"Correlation help", 0, 0, DO_Correlation_help); praat_TableOfReal_init2 (classCorrelation); praat_SSCP_query_init (classCorrelation); praat_SSCP_extract_init (classCorrelation); praat_addAction1 (classCorrelation, 1, L"Get diagonality (bartlett)...", L"Get ln(determinant)", 1, DO_Correlation_testDiagonality_bartlett); praat_addAction1 (classCorrelation, 0, L"Confidence intervals...", 0, 0, DO_Correlation_confidenceIntervals); praat_addAction1 (classCorrelation, 0, L"To PCA", 0, 0, DO_Correlation_to_PCA); praat_addAction1 (classDiscriminant, 0, L"Discriminant help", 0, 0, DO_Discriminant_help); praat_addAction1 (classDiscriminant, 0, DRAW_BUTTON, 0, 0, 0); praat_Eigen_draw_init (classDiscriminant); praat_addAction1 (classDiscriminant, 0, L"-- sscps --", 0, 1, 0); praat_addAction1 (classDiscriminant, 0, L"Draw sigma ellipses...", 0, 1, DO_Discriminant_drawSigmaEllipses); praat_addAction1 (classDiscriminant, 0, L"Draw one sigma ellipse...", 0, 1, DO_Discriminant_drawOneSigmaEllipse); praat_addAction1 (classDiscriminant, 0, L"Draw confidence ellipses...", 0, 1, DO_Discriminant_drawConfidenceEllipses); praat_addAction1 (classDiscriminant, 1, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (classDiscriminant, 1, L"-- eigen structure --", 0, 1, 0); praat_Eigen_query_init (classDiscriminant); praat_addAction1 (classDiscriminant, 1, L"-- discriminant --", 0, 1, 0); praat_addAction1 (classDiscriminant, 1, L"Get number of functions", 0, 1, DO_Discriminant_getNumberOfFunctions); praat_addAction1 (classDiscriminant, 1, L"Get dimension of functions", 0, 1, DO_Discriminant_getDimensionOfFunctions); praat_addAction1 (classDiscriminant, 1, L"Get number of groups", 0, 1, DO_Discriminant_getNumberOfGroups); praat_addAction1 (classDiscriminant, 1, L"Get number of observations...", 0, 1, DO_Discriminant_getNumberOfObservations); praat_addAction1 (classDiscriminant, 1, L"-- tests --", 0, 1, 0); praat_addAction1 (classDiscriminant, 1, L"Get Wilks lambda...", 0, 1, DO_Discriminant_getWilksLambda); praat_addAction1 (classDiscriminant, 1, L"Get cumulative contribution of components...", 0, 1, DO_Discriminant_getCumulativeContributionOfComponents); praat_addAction1 (classDiscriminant, 1, L"Get partial discrimination probability...", 0, 1, DO_Discriminant_getPartialDiscriminationProbability); praat_addAction1 (classDiscriminant, 1, L"Get homogeneity of covariances (box)", 0, praat_DEPTH_1 | praat_HIDDEN, DO_Discriminant_getHomegeneityOfCovariances_box); praat_addAction1 (classDiscriminant, 1, L"Report equality of covariance matrices", 0, 1, DO_Discriminant_reportEqualityOfCovariances_wald); praat_addAction1 (classDiscriminant, 1, L"-- ellipses --", 0, 1, 0); praat_addAction1 (classDiscriminant, 1, L"Get sigma ellipse area...", 0, 1, DO_Discriminant_getConcentrationEllipseArea); praat_addAction1 (classDiscriminant, 1, L"Get confidence ellipse area...", 0, 1, DO_Discriminant_getConfidenceEllipseArea); praat_addAction1 (classDiscriminant, 1, L"Get ln(determinant_group)...", 0, 1, DO_Discriminant_getLnDeterminant_group); praat_addAction1 (classDiscriminant, 1, L"Get ln(determinant_total)", 0, 1, DO_Discriminant_getLnDeterminant_total); praat_addAction1 (classDiscriminant, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classDiscriminant, 1, L"Invert eigenvector...", 0, 1, DO_Discriminant_invertEigenvector); praat_addAction1 (classDiscriminant, 0, L"Align eigenvectors", 0, 1, DO_Eigens_alignEigenvectors); praat_addAction1 (classDiscriminant, 0, EXTRACT_BUTTON, 0, 0, 0); praat_addAction1 (classDiscriminant, 1, L"Extract pooled within-groups SSCP", 0, 1, DO_Discriminant_extractPooledWithinGroupsSSCP); praat_addAction1 (classDiscriminant, 1, L"Extract within-group SSCP...", 0, 1, DO_Discriminant_extractWithinGroupSSCP); praat_addAction1 (classDiscriminant, 1, L"Extract between-groups SSCP", 0, 1, DO_Discriminant_extractBetweenGroupsSSCP); praat_addAction1 (classDiscriminant, 1, L"Extract group centroids", 0, 1, DO_Discriminant_extractGroupCentroids); praat_addAction1 (classDiscriminant, 1, L"Extract group standard deviations", 0, 1, DO_Discriminant_extractGroupStandardDeviations); praat_addAction1 (classDiscriminant, 1, L"Extract group labels", 0, 1, DO_Discriminant_extractGroupLabels); praat_addAction1 (classDiscriminant , 0, L"& TableOfReal: To ClassificationTable?", 0, 0, DO_hint_Discriminant_and_TableOfReal_to_ClassificationTable); /* praat_addAction1 (classDiscriminant, 1, L"Extract coefficients...", 0, 1, DO_Discriminant_extractCoefficients);*/ praat_Eigen_Matrix_project (classDiscriminant, classFormantFilter); praat_Eigen_Matrix_project (classDiscriminant, classBarkFilter); praat_Eigen_Matrix_project (classDiscriminant, classMelFilter); praat_addAction2 (classDiscriminant, 1, classPattern, 1, L"To Categories...", 0, 0, DO_Discriminant_and_Pattern_to_Categories); praat_addAction2 (classDiscriminant, 1, classSSCP, 1, L"Project", 0, 0, DO_Eigen_and_SSCP_project); praat_addAction2 (classDiscriminant, 1, classStrings, 1, L"Modify Discriminant", 0, 0, 0); praat_addAction2 (classDiscriminant, 1, classStrings, 1, L"Set group labels", 0, 0, DO_Discriminant_setGroupLabels); praat_addAction2 (classDiscriminant, 1, classTableOfReal, 1, L"To Configuration...", 0, 0, DO_Discriminant_and_TableOfReal_to_Configuration); praat_addAction2 (classDiscriminant, 1, classTableOfReal, 1, L"To ClassificationTable...", 0, 0, DO_Discriminant_and_TableOfReal_to_ClassificationTable); praat_addAction2 (classDiscriminant, 1, classTableOfReal, 1, L"To TableOfReal (mahalanobis)...", 0, 0, DO_Discriminant_and_TableOfReal_mahalanobis); praat_addAction1 (classDTW, 0, L"DTW help", 0, 0, DO_DTW_help); praat_addAction1 (classDTW, 0, DRAW_BUTTON, 0, 0, 0); praat_addAction1 (classDTW, 0, L"Draw path...", 0, 1, DO_DTW_drawPath); praat_addAction1 (classDTW, 0, L"Paint distances...", 0, 1, DO_DTW_paintDistances); praat_addAction1 (classDTW, 0, L"Draw warp (x)...", 0, 1, DO_DTW_drawWarpX); praat_addAction1 (classDTW, 0, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (classDTW, 1, L"Query time domains", 0, 1, 0); praat_addAction1 (classDTW, 1, L"Get start time (x)", 0, 2, DO_DTW_getStartTimeX); praat_addAction1 (classDTW, 1, L"Get end time (x)", 0, 2, DO_DTW_getEndTimeX); praat_addAction1 (classDTW, 1, L"Get total duration (x)", 0, 2, DO_DTW_getTotalDurationX); praat_addAction1 (classDTW, 1, L"-- time domain x from y separator --", 0, 2, 0); praat_addAction1 (classDTW, 1, L"Get start time (y)", 0, 2, DO_DTW_getStartTimeY); praat_addAction1 (classDTW, 1, L"Get end time (y)", 0, 2, DO_DTW_getEndTimeY); praat_addAction1 (classDTW, 1, L"Get total duration (y)", 0, 2, DO_DTW_getTotalDurationY); praat_addAction1 (classDTW, 1, L"Query time samplings", 0, 1, 0); praat_addAction1 (classDTW, 1, L"Get number of frames (x)", 0, 2, DO_DTW_getNumberOfFramesX); praat_addAction1 (classDTW, 1, L"Get time step (x)", 0, 2, DO_DTW_getTimeStepX); praat_addAction1 (classDTW, 1, L"Get time from frame number (x)...", 0, 2, DO_DTW_getTimeFromFrameNumberX); praat_addAction1 (classDTW, 1, L"Get frame number from time (x)...", 0, 2, DO_DTW_getFrameNumberFromTimeX); praat_addAction1 (classDTW, 1, L"-- time sampling x from y separator --", 0, 2, 0); praat_addAction1 (classDTW, 1, L"Get number of frames (y)", 0, 2, DO_DTW_getNumberOfFramesY); praat_addAction1 (classDTW, 1, L"Get time step (y)", 0, 2, DO_DTW_getTimeStepY); praat_addAction1 (classDTW, 1, L"Get time from frame number (y)...", 0, 2, DO_DTW_getTimeFromFrameNumberY); praat_addAction1 (classDTW, 1, L"Get frame number from time (y)...", 0, 2, DO_DTW_getFrameNumberFromTimeY); praat_addAction1 (classDTW, 1, L"Get y time from x time...", 0, 1, DO_DTW_getYTimeFromXTime); praat_addAction1 (classDTW, 1, L"Get x time from y time...", 0, 1, DO_DTW_getXTimeFromYTime); praat_addAction1 (classDTW, 1, L"Get y time...", 0, praat_HIDDEN + praat_DEPTH_1, DO_DTW_getYTimeFromXTime); praat_addAction1 (classDTW, 1, L"Get x time...", 0, praat_HIDDEN + praat_DEPTH_1, DO_DTW_getXTimeFromYTime); praat_addAction1 (classDTW, 1, L"Get maximum consecutive steps...", 0, 1, DO_DTW_getMaximumConsecutiveSteps); praat_addAction1 (classDTW, 1, L"Get time along path...", 0, praat_DEPTH_1 | praat_HIDDEN, DO_DTW_getPathY); praat_addAction1 (classDTW, 1, L"-- distance queries --", 0, 1, 0); praat_addAction1 (classDTW, 1, L"Get distance value...", 0, 1, DO_DTW_getDistanceValue); praat_addAction1 (classDTW, 1, L"Get minimum distance", 0, 1, DO_DTW_getMinimumDistance); praat_addAction1 (classDTW, 1, L"Get maximum distance", 0, 1, DO_DTW_getMaximumDistance); praat_addAction1 (classDTW, 1, L"Get distance (weighted)", 0, 1, DO_DTW_getWeightedDistance); praat_addAction1 (classDTW, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classDTW, 0, L"Formula (distances)...", 0, 1, DO_DTW_formulaDistances); praat_addAction1 (classDTW, 0, L"Set distance value...", 0, 1, DO_DTW_setDistanceValue); praat_addAction1 (classDTW, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classDTW, 0, L"Find path...", 0, praat_HIDDEN, DO_DTW_findPath); praat_addAction1 (classDTW, 0, L"Find path (band & slope)...", 0, 0, DO_DTW_findPath_bandAndSlope); praat_addAction1 (classDTW, 0, L"To Polygon...", 0, 1, DO_DTW_to_Polygon); praat_addAction1 (classDTW, 0, L"To Matrix (distances)", 0, 0, DO_DTW_to_Matrix_distances); praat_addAction1 (classDTW, 0, L"To Matrix (cumm. distances)...", 0, 0, DO_DTW_to_Matrix_cummulativeDistances); praat_addAction1 (classDTW, 0, L"Swap axes", 0, 0, DO_DTW_swapAxes); praat_addAction2 (classDTW, 1, classMatrix, 1, L"Replace matrix", 0, 0, DO_DTW_and_Matrix_replace); praat_addAction2 (classDTW, 1, classTextGrid, 1, L"To TextGrid (warp times)", 0, 0, DO_DTW_and_TextGrid_to_TextGrid); praat_addAction2 (classDTW, 1, classIntervalTier, 1, L"To Table (distances)", 0, 0, DO_DTW_and_IntervalTier_to_Table); praat_addAction2 (classDTW, 1, classPolygon, 1, L"Find path inside...", 0, 0, DO_DTW_and_Polygon_findPathInside); praat_addAction2 (classDTW, 1, classPolygon, 1, L"To Matrix (cumm. distances)...", 0, 0, DO_DTW_and_Polygon_to_Matrix_cummulativeDistances); praat_addAction2 (classDTW, 1, classSound, 2, L"Draw...", 0, 0, DO_DTW_and_Sounds_draw); praat_addAction2 (classDTW, 1, classSound, 2, L"Draw warp (x)...", 0, 0, DO_DTW_and_Sounds_drawWarpX); praat_addAction1 (classEditDistanceTable, 1, L"EditDistanceTable help", 0, 0, DO_EditDistanceTable_help); praat_EditDistanceTable_as_TableOfReal_init (classEditDistanceTable); praat_addAction1 (classEditDistanceTable, 1, L"To TableOfReal (directions)...", 0, praat_HIDDEN, DO_EditDistanceTable_to_TableOfReal_directions); praat_addAction2 (classEditDistanceTable, 1, classEditCostsTable, 1, L"Set new edit costs", 0, 0, DO_EditDistanceTable_setEditCosts); praat_addAction1 (classEditCostsTable, 1, L"EditCostsTable help", 0, 0, DO_EditCostsTable_help); praat_addAction1 (classEditCostsTable, 0, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (classEditCostsTable, 1, L"Get target index...", 0, 1, DO_EditCostsTable_getTargetIndex); praat_addAction1 (classEditCostsTable, 1, L"Get source index...", 0, 1, DO_EditCostsTable_getSourceIndex); praat_addAction1 (classEditCostsTable, 1, L"Get insertion cost...", 0, 1, DO_EditCostsTable_getInsertionCost); praat_addAction1 (classEditCostsTable, 1, L"Get deletion cost...", 0, 1, DO_EditCostsTable_getDeletionCost); praat_addAction1 (classEditCostsTable, 1, L"Get substitution cost...", 0, 1, DO_EditCostsTable_getSubstitutionCost); praat_addAction1 (classEditCostsTable, 1, L"Get cost (others)...", 0, 1, DO_EditCostsTable_getOthersCost); praat_addAction1 (classEditCostsTable, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classEditCostsTable, 1, L"Set target symbol (index)...", 0, 1, DO_EditCostsTable_setTargetSymbol_index); praat_addAction1 (classEditCostsTable, 1, L"Set source symbol (index)...", 0, 1, DO_EditCostsTable_setSourceSymbol_index); praat_addAction1 (classEditCostsTable, 1, L"Set insertion costs...", 0, 1, DO_EditCostsTable_setInsertionCosts); praat_addAction1 (classEditCostsTable, 1, L"Set deletion costs...", 0, 1, DO_EditCostsTable_setDeletionCosts); praat_addAction1 (classEditCostsTable, 1, L"Set substitution costs...", 0, 1, DO_EditCostsTable_setSubstitutionCosts); praat_addAction1 (classEditCostsTable, 1, L"Set costs (others)...", 0, 1, DO_EditCostsTable_setOthersCosts); praat_addAction1 (classEditCostsTable, 1, L"To TableOfReal", 0, 0, DO_EditCostsTable_to_TableOfReal); praat_Index_init (classStringsIndex); praat_addAction1 (classIndex, 0, L"Index help", 0, 0, DO_Index_help); praat_addAction1 (classStringsIndex, 1, L"Get class label...", 0, 0, DO_StringsIndex_getClassLabel); praat_addAction1 (classStringsIndex, 1, L"Get class index...", 0, 0, DO_StringsIndex_getClassIndex); praat_addAction1 (classStringsIndex, 1, L"Get label...", 0, 0, DO_StringsIndex_getLabel); praat_addAction1 (classIndex, 1, L"Get index...", 0, 0, DO_Index_getIndex); praat_addAction1 (classStringsIndex, 1, L"To Strings", 0, 0, DO_StringsIndex_to_Strings); praat_addAction1 (classExcitation, 0, L"Synthesize", L"To Formant...", 0, 0); praat_addAction1 (classExcitation, 0, L"To Excitations", L"Synthesize", 0, DO_Excitation_to_Excitations); praat_addAction1 (classExcitations, 0, L"Modify", 0, 0, 0); praat_addAction1 (classExcitations, 0, L"Formula...", 0, 0, DO_Excitations_formula); praat_addAction1 (classExcitations, 0, L"Extract", 0, 0, 0); praat_addAction1 (classExcitations, 0, L"Extract Excitation...", 0, 0, DO_Excitations_getItem); praat_addAction1 (classExcitations, 0, L"Synthesize", 0, 0, 0); praat_addAction1 (classExcitations, 0, L"Append", 0, 0, DO_Excitations_append); praat_addAction1 (classExcitations, 0, L"Convert", 0, 0, 0); praat_addAction1 (classExcitations, 0, L"To Pattern...", 0, 0, DO_Excitations_to_Pattern); praat_addAction1 (classExcitations, 0, L"To TableOfReal", 0, 0, DO_Excitations_to_TableOfReal); praat_addAction2 (classExcitations, 1, classExcitation, 0, L"Add to Excitations", 0, 0, DO_Excitations_addItem); praat_addAction1 (classFileInMemory, 1, L"Show as code...", 0, 0, DO_FileInMemory_showAsCode); praat_addAction1 (classFileInMemory, 1, L"Set id...", 0, 0, DO_FileInMemory_setId); praat_addAction1 (classFileInMemory, 0, L"To FilesInMemory", 0, 0, DO_FileInMemory_to_FilesInMemory); praat_addAction1 (classFilesInMemory, 1, L"Show as code...", 0, 0, DO_FilesInMemory_showAsCode); praat_addAction1 (classFilesInMemory, 1, L"Show one file as code...", 0, 0, DO_FilesInMemory_showOneFileAsCode); praat_addAction1 (classFilesInMemory, 0, L"Merge", 0, 0, DO_FilesInMemory_merge); praat_addAction1 (classFilesInMemory, 0, L"To Strings (id)", 0, 0, DO_FilesInMemory_to_Strings_id); praat_addAction2 (classFilesInMemory, 1, classFileInMemory, 0, L"Add items to Collection", 0, 0, DO_FilesInMemory_addItems); praat_addAction1 (classFormantFilter, 0, L"FormantFilter help", 0, 0, DO_FormantFilter_help); praat_FilterBank_all_init (classFormantFilter); praat_addAction1 (classFormantFilter, 0, L"Draw spectrum (slice)...", L"Draw filters...", 1, DO_FormantFilter_drawSpectrum); praat_addAction1 (classFormantFilter, 0, L"Draw filter functions...", L"Draw filters...", 1, DO_FormantFilter_drawFilterFunctions); praat_addAction1 (classFormantGrid, 0, L"Draw...", L"Edit", 1, DO_FormantGrid_draw); praat_addAction1 (classIntensity, 0, L"To TextGrid (silences)...", L"To IntensityTier (valleys)", 0, DO_Intensity_to_TextGrid_detectSilences); praat_addAction1 (classISpline, 0, L"ISpline help", 0, 0, DO_ISpline_help); praat_Spline_init (classISpline); praat_addAction1 (classKlattTable, 0, L"KlattTable help", 0, 0, DO_KlattTable_help); praat_addAction1 (classKlattTable, 0, L"To Sound...", 0, 0, DO_KlattTable_to_Sound); praat_addAction1 (classKlattTable, 0, L"To KlattGrid...", 0, 0, DO_KlattTable_to_KlattGrid); praat_addAction1 (classKlattTable, 0, L"To Table", 0, 0, DO_KlattTable_to_Table); praat_addAction1 (classLegendreSeries, 0, L"LegendreSeries help", 0, 0, DO_LegendreSeries_help); praat_FunctionTerms_init (classLegendreSeries); praat_addAction1 (classLegendreSeries, 0, L"To Polynomial", L"Analyse", 0, DO_LegendreSeries_to_Polynomial); praat_addAction1 (classLongSound, 0, L"Append to existing sound file...", 0, 0, DO_LongSounds_appendToExistingSoundFile); praat_addAction1 (classSound, 0, L"Append to existing sound file...", 0, 0, DO_LongSounds_appendToExistingSoundFile); praat_addAction2 (classLongSound, 0, classSound, 0, L"Append to existing sound file...", 0, 0, DO_LongSounds_appendToExistingSoundFile); praat_addAction1 (classLongSound, 2, L"Save as stereo AIFF file...", L"Save as NIST file...", 1, DO_LongSounds_writeToStereoAiffFile); praat_addAction1 (classLongSound, 2, L"Write to stereo AIFF file...", L"Write to NIST file...", praat_HIDDEN + praat_DEPTH_1, DO_LongSounds_writeToStereoAiffFile); praat_addAction1 (classLongSound, 2, L"Save as stereo AIFC file...", L"Save as stereo AIFF file...", 1, DO_LongSounds_writeToStereoAifcFile); praat_addAction1 (classLongSound, 2, L"Write to stereo AIFC file...", L"Write to stereo AIFF file...", praat_HIDDEN + praat_DEPTH_1, DO_LongSounds_writeToStereoAifcFile); praat_addAction1 (classLongSound, 2, L"Save as stereo WAV file...", L"Save as stereo AIFC file...", 1, DO_LongSounds_writeToStereoWavFile); praat_addAction1 (classLongSound, 2, L"Write to stereo WAV file...", L"Write to stereo AIFC file...", praat_HIDDEN + praat_DEPTH_1, DO_LongSounds_writeToStereoWavFile); praat_addAction1 (classLongSound, 2, L"Save as stereo NeXt/Sun file...", L"Save as stereo WAV file...", 1, DO_LongSounds_writeToStereoNextSunFile); praat_addAction1 (classLongSound, 2, L"Write to stereo NeXt/Sun file...", L"Write to stereo WAV file...", praat_HIDDEN + praat_DEPTH_1, DO_LongSounds_writeToStereoNextSunFile); praat_addAction1 (classLongSound, 2, L"Save as stereo NIST file...", L"Save as stereo NeXt/Sun file...", 1, DO_LongSounds_writeToStereoNistFile); praat_addAction1 (classLongSound, 2, L"Write to stereo NIST file...", L"Write to stereo NeXt/Sun file...", praat_HIDDEN + praat_DEPTH_1, DO_LongSounds_writeToStereoNistFile); praat_addAction1 (classMatrix, 0, L"Scatter plot...", L"Paint cells...", 1, DO_Matrix_scatterPlot); praat_addAction1 (classMatrix, 0, L"Draw as squares...", L"Scatter plot...", 1, DO_Matrix_drawAsSquares); praat_addAction1 (classMatrix, 0, L"Draw distribution...", L"Draw as squares...", 1, DO_Matrix_drawDistribution); praat_addAction1 (classMatrix, 0, L"Draw cumulative distribution...", L"Draw distribution...", 1, DO_Matrix_drawCumulativeDistribution); praat_addAction1 (classMatrix, 0, L"Transpose", L"Synthesize", 0, DO_Matrix_transpose); praat_addAction1 (classMatrix, 0, L"Solve equation...", L"Analyse", 0, DO_Matrix_solveEquation); praat_addAction1 (classMatrix, 0, L"To Pattern...", L"To VocalTract", 1, DO_Matrix_to_Pattern); praat_addAction1 (classMatrix, 0, L"To Activation", L"To Pattern...", 1, DO_Matrix_to_Activation); praat_addAction1 (classMatrix, 2, L"To DTW...", L"To ParamCurve", 1, DO_Matrices_to_DTW); praat_addAction2 (classMatrix, 1, classCategories, 1, L"To TableOfReal", 0, 0, DO_Matrix_Categories_to_TableOfReal); praat_addAction1 (classMelFilter, 0, L"MelFilter help", 0, 0, DO_MelFilter_help); praat_FilterBank_all_init (classMelFilter); praat_addAction1 (classMelFilter, 0, L"Draw spectrum (slice)...", L"Draw filters...", 1, DO_MelFilter_drawSpectrum); praat_addAction1 (classMelFilter, 0, L"Draw filter functions...", L"Draw filters...", 1, DO_MelFilter_drawFilterFunctions); praat_addAction1 (classMelFilter, 0, L"To MFCC...", 0, 0, DO_MelFilter_to_MFCC); praat_addAction1 (classMFCC, 0, L"MFCC help", 0, 0, DO_MFCC_help); praat_CC_init (classMFCC); praat_addAction1 (classMFCC, 0, L"To MelFilter...", 0, 0, DO_MFCC_to_MelFilter); praat_addAction1 (classMFCC, 0, L"To TableOfReal...", 0, 0, DO_MFCC_to_TableOfReal); praat_addAction1 (classMFCC, 0, L"To Sound", 0, praat_HIDDEN, DO_MFCC_to_Sound); praat_addAction1 (classMFCC, 2, L"Cross-correlate...", 0, 0, DO_MFCCs_crossCorrelate); praat_addAction1 (classMFCC, 2, L"Convolve...", 0, 0, DO_MFCCs_convolve); praat_addAction1 (classMSpline, 0, L"MSpline help", 0, 0, DO_MSpline_help); praat_Spline_init (classMSpline); praat_addAction1 (classPattern, 0, L"Draw", 0, 0, 0); praat_addAction1 (classPattern, 0, L"Draw...", 0, 0, DO_Pattern_draw); praat_addAction1 (classPattern, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classPattern, 0, L"Formula...", 0, 1, DO_Pattern_formula); praat_addAction1 (classPattern, 0, L"Set value...", 0, 1, DO_Pattern_setValue); praat_addAction1 (classPattern, 0, L"To Matrix", 0, 0, DO_Pattern_to_Matrix); praat_addAction2 (classPattern, 1, classCategories, 1, L"To TableOfReal", 0, 0, DO_Matrix_Categories_to_TableOfReal); praat_addAction2 (classPattern, 1, classCategories, 1, L"To Discriminant", 0, 0, DO_Pattern_and_Categories_to_Discriminant); praat_addAction1 (classPCA, 0, L"PCA help", 0, 0, DO_PCA_help); praat_addAction1 (classPCA, 0, DRAW_BUTTON, 0, 0, 0); praat_Eigen_draw_init (classPCA); praat_addAction1 (classPCA, 0, QUERY_BUTTON, 0, 0, 0); praat_Eigen_query_init (classPCA); praat_addAction1 (classPCA, 1, L"-- pca --", 0, 1, 0); praat_addAction1 (classPCA, 1, L"Get centroid element...", 0, 1, DO_PCA_getCentroidElement); praat_addAction1 (classPCA, 1, L"Get equality of eigenvalues...", 0, 1, DO_PCA_getEqualityOfEigenvalues); praat_addAction1 (classPCA, 1, L"Get fraction variance accounted for...", 0, 1, DO_PCA_getFractionVAF); praat_addAction1 (classPCA, 1, L"Get number of components (VAF)...", 0, 1, DO_PCA_getNumberOfComponentsVAF); praat_addAction1 (classPCA, 2, L"Get angle between pc1-pc2 planes", 0, 1, DO_PCAs_getAngleBetweenPc1Pc2Plane_degrees); praat_addAction1 (classPCA, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classPCA, 1, L"Invert eigenvector...", 0, 1, DO_PCA_invertEigenvector); praat_addAction1 (classPCA, 0, L"Align eigenvectors", 0, 1, DO_Eigens_alignEigenvectors); praat_addAction1 (classPCA, 2, L"To Procrustes...", 0, 0, DO_PCAs_to_Procrustes); praat_addAction1 (classPCA, 0, L"To TableOfReal (reconstruct 1)...", 0, 0, DO_PCA_to_TableOfReal_reconstruct1); praat_addAction1 (classPCA, 0, L"& TableOfReal: To Configuration?", 0, 0, DO_hint_PCA_and_TableOfReal_to_Configuration); praat_addAction1 (classPCA, 0, L"& Configuration (reconstruct)?", 0, 0, DO_hint_PCA_and_Configuration_to_TableOfReal_reconstruct); praat_addAction1 (classPCA, 0, L"& Covariance: Project?", 0, 0, DO_hint_PCA_and_Covariance_Project); praat_addAction2 (classPCA, 1, classConfiguration, 1, L"To TableOfReal (reconstruct)", 0, 0, DO_PCA_and_Configuration_to_TableOfReal_reconstruct); praat_addAction2 (classPCA, 1, classSSCP, 1, L"Project", 0, 0, DO_Eigen_and_SSCP_project); praat_addAction2 (classPCA, 1, classTableOfReal, 1, L"To Configuration...", 0, 0, DO_PCA_and_TableOfReal_to_Configuration); praat_addAction2 (classPCA, 1, classTableOfReal, 1, L"To TableOfReal (z-scores)...", 0, 0, DO_PCA_and_TableOfReal_to_TableOfReal_zscores); praat_addAction2 (classPCA, 1, classTableOfReal, 1, L"Get fraction variance...", 0, 0, DO_PCA_and_TableOfReal_getFractionVariance); praat_addAction2 (classPCA, 1, classCovariance, 1, L"Project", 0, 0, DO_Eigen_and_Covariance_project); praat_Eigen_Matrix_project (classPCA, classFormantFilter); praat_Eigen_Matrix_project (classPCA, classBarkFilter); praat_Eigen_Matrix_project (classPCA, classMelFilter); praat_addAction1 (classPermutation, 0, L"Permutation help", 0, 0, DO_Permutation_help); praat_addAction1 (classPermutation, 0, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (classPermutation, 1, L"Get number of elements", 0, 1, DO_Permutation_getNumberOfElements); praat_addAction1 (classPermutation, 1, L"Get value...", 0, 1, DO_Permutation_getValueAtIndex); praat_addAction1 (classPermutation, 1, L"Get index...", 0, 1, DO_Permutation_getIndexAtValue); praat_addAction1 (classPermutation, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classPermutation, 1, L"Sort", 0, 1, DO_Permutation_sort); praat_addAction1 (classPermutation, 1, L"Swap blocks...", 0, 1, DO_Permutation_swapBlocks); praat_addAction1 (classPermutation, 1, L"Swap numbers...", 0, 1, DO_Permutation_swapNumbers); praat_addAction1 (classPermutation, 1, L"Swap positions...", 0, 1, DO_Permutation_swapPositions); praat_addAction1 (classPermutation, 1, L"Swap one from range...", 0, 1, DO_Permutation_swapOneFromRange); praat_addAction1 (classPermutation, 0, L"-- sequential permutations --", 0, 1, 0); praat_addAction1 (classPermutation, 0, L"Next", 0, 1, DO_Permutations_next); praat_addAction1 (classPermutation, 0, L"Previous", 0, 1, DO_Permutations_previous); praat_addAction1 (classPermutation, 1, L"Permute randomly...", 0, 0, DO_Permutation_permuteRandomly); praat_addAction1 (classPermutation, 1, L"Permute randomly (blocks)...", 0, 0, DO_Permutation_permuteBlocksRandomly); praat_addAction1 (classPermutation, 1, L"Interleave...", 0, 0, DO_Permutation_interleave); praat_addAction1 (classPermutation, 1, L"Rotate...", 0, 0, DO_Permutation_rotate); praat_addAction1 (classPermutation, 1, L"Reverse...", 0, 0, DO_Permutation_reverse); praat_addAction1 (classPermutation, 1, L"Invert", 0, 0, DO_Permutation_invert); praat_addAction1 (classPermutation, 0, L"Multiply", 0, 0, DO_Permutations_multiply); praat_addAction1 (classPitch, 2, L"To DTW...", L"To PointProcess", praat_HIDDEN, DO_Pitches_to_DTW); praat_addAction1 (classPitchTier, 0, L"To Pitch...", L"To Sound (sine)...", 1, DO_PitchTier_to_Pitch); praat_addAction1 (classPolygon, 0, QUERY_BUTTON, L"Paint circles...", 0, 0); praat_addAction1 (classPolygon, 0, L"Get number of points", QUERY_BUTTON, 1, DO_Polygon_getNumberOfPoints); praat_addAction1 (classPolygon, 0, L"Get point (x)...", L"Get number of points", 1, DO_Polygon_getPointX); praat_addAction1 (classPolygon, 0, L"Get point (y)...", L"Get point (x)...", 1, DO_Polygon_getPointY); praat_addAction1 (classPolygon, 0, L"-- other queries --", L"Get point (y)...", 1, 0); praat_addAction1 (classPolygon, 0, L"Get location of point...", L"-- other queries --", 1, DO_Polygon_getLocationOfPoint); praat_addAction1 (classPolygon, 0, L"Translate...", MODIFY_BUTTON, 1, DO_Polygon_translate); praat_addAction1 (classPolygon, 0, L"Rotate...", L"Translate...", 1, DO_Polygon_rotate); praat_addAction1 (classPolygon, 0, L"Scale...", L"Rotate...", 1, DO_Polygon_scale); praat_addAction1 (classPolygon, 0, L"Reverse X", L"Scale...", 1, DO_Polygon_reverseX); praat_addAction1 (classPolygon, 0, L"Reverse Y", L"Reverse X", 1, DO_Polygon_reverseY); praat_addAction1 (classPolygon, 0, L"Simplify", 0, praat_HIDDEN, DO_Polygon_simplify); praat_addAction1 (classPolygon, 0, L"Circular permutation...", 0, praat_HIDDEN, DO_Polygon_circularPermutation); praat_addAction2 (classPolygon, 1, classCategories, 1, L"Draw...", 0, 0, DO_Polygon_Categories_draw); praat_addAction1 (classPolynomial, 0, L"Polynomial help", 0, 0, DO_Polynomial_help); praat_FunctionTerms_init (classPolynomial); praat_addAction1 (classPolynomial, 0, L"-- area --", L"Get x of maximum...", 1, 0); praat_addAction1 (classPolynomial, 1, L"Get area...", L"-- area --", 1, DO_Polynomial_getArea); praat_addAction1 (classPolynomial, 0, L"-- monic --", L"Set coefficient...", 1, 0); praat_addAction1 (classPolynomial, 0, L"Scale coefficients (monic)", L"-- monic --", 1, DO_Polynomial_scaleCoefficients_monic); praat_addAction1 (classPolynomial, 1, L"Get value (complex)...", L"Get value...", 1, DO_Polynomial_evaluate_z); praat_addAction1 (classPolynomial, 0, L"To Spectrum...", L"Analyse", 0, DO_Polynomial_to_Spectrum); praat_addAction1 (classPolynomial, 0, L"To Roots", 0, 0, DO_Polynomial_to_Roots); praat_addAction1 (classPolynomial, 0, L"To Polynomial (derivative)", 0, 0, DO_Polynomial_getDerivative); praat_addAction1 (classPolynomial, 0, L"To Polynomial (primitive)", 0, 0, DO_Polynomial_getPrimitive); praat_addAction1 (classPolynomial, 0, L"Scale x...", 0, 0, DO_Polynomial_scaleX); praat_addAction1 (classPolynomial, 2, L"Multiply", 0, 0, DO_Polynomials_multiply); praat_addAction1 (classPolynomial, 2, L"Divide...", 0, 0, DO_Polynomials_divide); praat_addAction1 (classRoots, 1, L"Roots help", 0, 0, DO_Roots_help); praat_addAction1 (classRoots, 1, L"Draw...", 0, 0, DO_Roots_draw); praat_addAction1 (classRoots, 1, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (classRoots, 1, L"Get number of roots", 0, 1, DO_Roots_getNumberOfRoots); praat_addAction1 (classRoots, 1, L"-- roots --", 0, 1, 0); praat_addAction1 (classRoots, 1, L"Get root...", 0, 1, DO_Roots_getRoot); praat_addAction1 (classRoots, 1, L"Get real part of root...", 0, 1, DO_Roots_getRealPartOfRoot); praat_addAction1 (classRoots, 1, L"Get imaginary part of root...", 0, 1, DO_Roots_getImaginaryPartOfRoot); praat_addAction1 (classRoots, 1, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classRoots, 1, L"Set root...", 0, 1, DO_Roots_setRoot); praat_addAction1 (classRoots, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classRoots, 0, L"To Spectrum...", 0, 0, DO_Roots_to_Spectrum); praat_addAction2 (classRoots, 1, classPolynomial, 1, L"Polish roots", 0, 0, DO_Roots_and_Polynomial_polish); praat_addAction1 (classSound, 1, L"Save as raw 16-bit Big Endian file...", 0, 0, DO_Sound_writeToRawFileBE); praat_addAction1 (classSound, 1, L"Write to raw 16-bit Big Endian file...", 0, praat_HIDDEN, DO_Sound_writeToRawFileBE); praat_addAction1 (classSound, 1, L"Save as raw 16-bit Little Endian file...", 0, 0, DO_Sound_writeToRawFileLE); praat_addAction1 (classSound, 1, L"Write to raw 16-bit Little Endian file...", 0, praat_HIDDEN, DO_Sound_writeToRawFileLE); praat_addAction1 (classSound, 0, L"To TextGrid (silences)...", L"To IntervalTier", 1, DO_Sound_to_TextGrid_detectSilences); praat_addAction1 (classSound, 0, L"Play one channel...", L"Play", praat_HIDDEN, DO_Sound_playOneChannel); praat_addAction1 (classSound, 0, L"Draw where...", L"Draw...", 1, DO_Sound_drawWhere); // praat_addAction1 (classSound, 0, L"Paint where...", L"Draw where...", praat_DEPTH_1 | praat_HIDDEN, DO_Sound_paintWhere); praat_addAction1 (classSound, 0, L"Paint where...", L"Draw where...", 1, DO_Sound_paintWhere); // praat_addAction1 (classSound, 2, L"Paint enclosed...", L"Paint where...", praat_DEPTH_1 | praat_HIDDEN, DO_Sounds_paintEnclosed); praat_addAction1 (classSound, 2, L"Paint enclosed...", L"Paint where...", 1, DO_Sounds_paintEnclosed); praat_addAction1 (classSound, 0, L"To Pitch (shs)...", L"To Pitch (cc)...", 1, DO_Sound_to_Pitch_shs); praat_addAction1 (classSound, 0, L"Fade in...", L"Multiply by window...", praat_HIDDEN + praat_DEPTH_1, DO_Sound_fadeIn); praat_addAction1 (classSound, 0, L"Fade out...", L"Fade in...", praat_HIDDEN + praat_DEPTH_1, DO_Sound_fadeOut); praat_addAction1 (classSound, 0, L"To Pitch (SPINET)...", L"To Pitch (cc)...", 1, DO_Sound_to_Pitch_SPINET); praat_addAction1 (classSound, 0, L"To FormantFilter...", L"To Cochleagram (edb)...", 1, DO_Sound_to_FormantFilter); praat_addAction1 (classSound, 0, L"To BarkFilter...", L"To FormantFilter...", 1, DO_Sound_to_BarkFilter); praat_addAction1 (classSound, 0, L"To MelFilter...", L"To BarkFilter...", 1, DO_Sound_to_MelFilter); praat_addAction1 (classSound, 0, L"To Polygon...", L"Down to Matrix", praat_DEPTH_1 | praat_HIDDEN, DO_Sound_to_Polygon); praat_addAction1 (classSound, 2, L"To Polygon (enclosed)...", L"Cross-correlate...", praat_DEPTH_1 | praat_HIDDEN, DO_Sounds_to_Polygon_enclosed); praat_addAction1 (classSound, 2, L"To DTW...", L"Cross-correlate...", praat_DEPTH_1, DO_Sounds_to_DTW); praat_addAction1 (classSound, 0, L"Filter (gammatone)...", L"Filter (formula)...", 1, DO_Sound_filterByGammaToneFilter4); praat_addAction1 (classSound, 0, L"Change gender...", L"Deepen band modulation...", 1, DO_Sound_changeGender); praat_addAction1 (classSound, 0, L"Change speaker...", L"Deepen band modulation...", praat_DEPTH_1 | praat_HIDDEN, DO_Sound_changeSpeaker); praat_addAction1 (classSound, 0, L"Trim silences...", L"Resample...", praat_DEPTH_1 | praat_HIDDEN, DO_Sound_trimSilences); praat_addAction1 (classSound, 0, L"To KlattGrid (simple)...", L"To Manipulation...", 1, DO_Sound_to_KlattGrid_simple); praat_addAction2 (classSound, 1, classPitch, 1, L"To FormantFilter...", 0, 0, DO_Sound_and_Pitch_to_FormantFilter); praat_addAction2 (classSound, 1, classPitch, 1, L"Change gender...", 0, 0, DO_Sound_and_Pitch_changeGender); praat_addAction2 (classSound, 1, classPitch, 1, L"Change speaker...", 0, praat_HIDDEN, DO_Sound_and_Pitch_changeSpeaker); praat_addAction2 (classSound, 1, classIntervalTier, 1, L"Cut parts matching label...", 0, 0, DO_Sound_and_IntervalTier_cutPartsMatchingLabel); praat_addAction1 (classSpectrogram, 2, L"To DTW...", L"To Spectrum (slice)...", 0, DO_Spectrograms_to_DTW); praat_addAction1 (classSpectrum, 0, L"Draw phases...", L"Draw (log freq)...", 1, DO_Spectrum_drawPhases); praat_addAction1 (classSpectrum, 0, L"Conjugate", L"Formula...", praat_HIDDEN | praat_DEPTH_1, DO_Spectrum_conjugate); praat_addAction1 (classSpectrum, 2, L"Multiply", L"To Sound (fft)", praat_HIDDEN, DO_Spectra_multiply); praat_addAction1 (classSpectrum, 0, L"To Matrix (unwrap)", L"To Matrix", 0, DO_Spectrum_unwrap); praat_addAction1 (classSpectrum, 0, L"To Cepstrum", L"To Spectrogram", 0, DO_Spectrum_to_Cepstrum); praat_addAction1 (classSpeechSynthesizer, 0, L"SpeechSynthesizer help", 0, 0, DO_SpeechSynthesizer_help); praat_addAction1 (classSpeechSynthesizer, 0, L"Play text...", 0, 0, DO_SpeechSynthesizer_playText); praat_addAction1 (classSpeechSynthesizer, 0, L"To Sound...", 0, 0, DO_SpeechSynthesizer_to_Sound); praat_addAction1 (classSpeechSynthesizer, 0, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (classSpeechSynthesizer, 1, L"Get voice name", 0, 1, DO_SpeechSynthesizer_getVoiceName); praat_addAction1 (classSpeechSynthesizer, 1, L"Get voice variant", 0, 1, DO_SpeechSynthesizer_getVoiceVariant); praat_addAction1 (classSpeechSynthesizer, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classSpeechSynthesizer, 0, L"Set text input settings...", 0, 1, DO_SpeechSynthesizer_setTextInputSettings); praat_addAction1 (classSpeechSynthesizer, 0, L"Set speech output settings...", 0, 1, DO_SpeechSynthesizer_setSpeechOutputSettings); praat_addAction2 (classSpeechSynthesizer, 1, classTextGrid, 1, L"To Sound...", 0, 0, DO_SpeechSynthesizer_and_TextGrid_to_Sound); praat_addAction3 (classSpeechSynthesizer, 1, classSound, 1, classTextGrid, 1, L"To TextGrid (align)...", 0, 0, DO_SpeechSynthesizer_and_Sound_and_TextGrid_align); praat_addAction3 (classSpeechSynthesizer, 1, classSound, 1, classTextGrid, 1, L"To TextGrid (align,trim)...", 0, 0, DO_SpeechSynthesizer_and_Sound_and_TextGrid_align2); praat_addAction1 (classSSCP, 0, L"SSCP help", 0, 0, DO_SSCP_help); praat_TableOfReal_init2 (classSSCP); praat_removeAction (classSSCP, NULL, NULL, L"Append"); praat_addAction1 (classSSCP, 0, L"Draw sigma ellipse...", DRAW_BUTTON, 1, DO_SSCP_drawSigmaEllipse); praat_addAction1 (classSSCP, 0, L"Draw confidence ellipse...", DRAW_BUTTON, 1, DO_SSCP_drawConfidenceEllipse); praat_SSCP_query_init (classSSCP); praat_addAction1 (classSSCP, 1, L"Get diagonality (bartlett)...", L"Get ln(determinant)", 1, DO_SSCP_testDiagonality_bartlett); praat_addAction1 (classSSCP, 1, L"Get total variance", L"Get diagonality (bartlett)...", 1, DO_SSCP_getTotalVariance); praat_addAction1 (classSSCP, 1, L"Get sigma ellipse area...", L"Get total variance", 1, DO_SSCP_getConcentrationEllipseArea); praat_addAction1 (classSSCP, 1, L"Get confidence ellipse area...", L"Get sigma ellipse area...", 1, DO_SSCP_getConfidenceEllipseArea); praat_addAction1 (classSSCP, 1, L"Get fraction variation...", L"Get confidence ellipse area...", 1, DO_SSCP_getFractionVariation); praat_SSCP_extract_init (classSSCP); praat_addAction1 (classSSCP, 0, L"To PCA", 0, 0, DO_SSCP_to_PCA); praat_addAction1 (classSSCP, 0, L"To Correlation", 0, 0, DO_SSCP_to_Correlation); praat_addAction1 (classSSCP, 0, L"To Covariance...", 0, 0, DO_SSCP_to_Covariance); praat_addAction1 (classStrings, 0, L"To Categories", 0, 0, DO_Strings_to_Categories); praat_addAction1 (classStrings, 0, L"Append", 0, 0, DO_Strings_append); praat_addAction1 (classStrings, 1, L"Set string...", L"Genericize", 0, DO_Strings_setString); praat_addAction1 (classStrings, 0, L"Change...", L"Set string...", 0, DO_Strings_change); praat_addAction1 (classStrings, 0, L"Extract part...", L"Change...", 0, DO_Strings_extractPart); praat_addAction1 (classStrings, 0, L"To Permutation...", L"To Distributions", 0, DO_Strings_to_Permutation); praat_addAction1 (classStrings, 2, L"To EditDistanceTable", L"To Distributions", 0, DO_Strings_to_EditDistanceTable); praat_addAction1 (classSVD, 0, L"To TableOfReal...", 0, 0, DO_SVD_to_TableOfReal); praat_addAction1 (classSVD, 0, L"Extract left singular vectors", 0, 0, DO_SVD_extractLeftSingularVectors); praat_addAction1 (classSVD, 0, L"Extract right singular vectors", 0, 0, DO_SVD_extractRightSingularVectors); praat_addAction1 (classSVD, 0, L"Extract singular values", 0, 0, DO_SVD_extractSingularValues); praat_addAction1 (classTable, 0, L"Scatter plot (ci)...", 0, praat_DEPTH_1 | praat_HIDDEN, DO_Table_drawScatterPlotWithConfidenceIntervals); praat_addAction1 (classTable, 0, L"To KlattTable", 0, praat_HIDDEN, DO_Table_to_KlattTable); praat_addAction1 (classTable, 1, L"Get median absolute deviation...", L"Get standard deviation...", 1, DO_Table_getMedianAbsoluteDeviation); praat_addAction1 (classTableOfReal, 1, L"Report multivariate normality...", L"Get column stdev (label)...", praat_DEPTH_1 | praat_HIDDEN, DO_TableOfReal_reportMultivariateNormality); praat_addAction1 (classTableOfReal, 0, L"Append columns", L"Append", 1, DO_TableOfReal_appendColumns); praat_addAction1 (classTableOfReal, 0, L"Multivariate statistics -", 0, 0, 0); praat_addAction1 (classTableOfReal, 0, L"To Discriminant", 0, 1, DO_TableOfReal_to_Discriminant); praat_addAction1 (classTableOfReal, 0, L"To PCA", 0, 1, DO_TableOfReal_to_PCA); praat_addAction1 (classTableOfReal, 0, L"To SSCP...", 0, 1, DO_TableOfReal_to_SSCP); praat_addAction1 (classTableOfReal, 0, L"To Covariance", 0, 1, DO_TableOfReal_to_Covariance); praat_addAction1 (classTableOfReal, 0, L"To Correlation", 0, 1, DO_TableOfReal_to_Correlation); praat_addAction1 (classTableOfReal, 0, L"To Correlation (rank)", 0, 1, DO_TableOfReal_to_Correlation_rank); praat_addAction1 (classTableOfReal, 0, L"To CCA...", 0, 1, DO_TableOfReal_to_CCA); praat_addAction1 (classTableOfReal, 0, L"To TableOfReal (means by row labels)...", 0, 1, DO_TableOfReal_meansByRowLabels); praat_addAction1 (classTableOfReal, 0, L"To TableOfReal (medians by row labels)...", 0, 1, DO_TableOfReal_mediansByRowLabels); praat_addAction1 (classTableOfReal, 0, L"-- configurations --", 0, 1, 0); praat_addAction1 (classTableOfReal, 0, L"To Configuration (pca)...", 0, 1, DO_TableOfReal_to_Configuration_pca); praat_addAction1 (classTableOfReal, 0, L"To Configuration (lda)...", 0, 1, DO_TableOfReal_to_Configuration_lda); praat_addAction1 (classTableOfReal, 2, L"-- between tables --", L"To Configuration (lda)...", 1, 0); praat_addAction1 (classTableOfReal, 2, L"To TableOfReal (cross-correlations)...", 0, praat_HIDDEN + praat_DEPTH_1, DO_TableOfReal_and_TableOfReal_crossCorrelations); praat_addAction1 (classTableOfReal, 1, L"To Pattern and Categories...", L"To Matrix", 1, DO_TableOfReal_to_Pattern_and_Categories); praat_addAction1 (classTableOfReal, 1, L"Split into Pattern and Categories...", L"To Pattern and Categories...", praat_DEPTH_1 | praat_HIDDEN, DO_TableOfReal_to_Pattern_and_Categories); praat_addAction1 (classTableOfReal, 0, L"To Permutation (sort row labels)", L"To Matrix", 1, DO_TableOfReal_to_Permutation_sortRowlabels); praat_addAction1 (classTableOfReal, 1, L"To SVD", 0, praat_HIDDEN, DO_TableOfReal_to_SVD); praat_addAction1 (classTableOfReal, 2, L"To GSVD", 0, praat_HIDDEN, DO_TablesOfReal_to_GSVD); praat_addAction1 (classTableOfReal, 2, L"To Eigen (gsvd)", 0, praat_HIDDEN, DO_TablesOfReal_to_Eigen_gsvd); praat_addAction1 (classTableOfReal, 0, L"To TableOfReal (cholesky)...", 0, praat_HIDDEN, DO_TableOfReal_choleskyDecomposition); praat_addAction1 (classTableOfReal, 0, L"-- scatter plots --", L"Draw top and bottom lines...", 1, 0); praat_addAction1 (classTableOfReal, 0, L"Draw scatter plot...", L"-- scatter plots --", 1, DO_TableOfReal_drawScatterPlot); praat_addAction1 (classTableOfReal, 0, L"Draw scatter plot matrix...", L"Draw scatter plot...", 1, DO_TableOfReal_drawScatterPlotMatrix); praat_addAction1 (classTableOfReal, 0, L"Draw box plots...", L"Draw scatter plot matrix...", 1, DO_TableOfReal_drawBoxPlots); praat_addAction1 (classTableOfReal, 0, L"Draw biplot...", L"Draw box plots...", 1, DO_TableOfReal_drawBiplot); praat_addAction1 (classTableOfReal, 0, L"Draw vectors...", L"Draw box plots...", praat_DEPTH_1 | praat_HIDDEN, DO_TableOfReal_drawVectors); praat_addAction1 (classTableOfReal, 1, L"Draw row as histogram...", L"Draw biplot...", praat_DEPTH_1 | praat_HIDDEN, DO_TableOfReal_drawRowAsHistogram); praat_addAction1 (classTableOfReal, 1, L"Draw rows as histogram...", L"Draw row as histogram...", praat_DEPTH_1 | praat_HIDDEN, DO_TableOfReal_drawRowsAsHistogram); praat_addAction1 (classTableOfReal, 1, L"Draw column as distribution...", L"Draw rows as histogram...", praat_DEPTH_1, DO_TableOfReal_drawColumnAsDistribution); praat_addAction2 (classStrings, 1, classPermutation, 1, L"Permute strings", 0, 0, DO_Strings_and_Permutation_permuteStrings); praat_addAction2 (classTableOfReal, 1, classPermutation, 1, L"Permute rows", 0, 0, DO_TableOfReal_and_Permutation_permuteRows); praat_addAction1 (classTextGrid, 0, L"Extend time...", L"Scale times...", 2, DO_TextGrid_extendTime); praat_addAction1 (classTextGrid, 1, L"Set tier name...", L"Remove tier...", 1, DO_TextGrid_setTierName); praat_addAction1 (classTextGrid, 0, L"Replace interval text...", L"Set interval text...", 2, DO_TextGrid_replaceIntervalTexts); praat_addAction1 (classTextGrid, 0, L"Replace point text...", L"Set point text...", 2, DO_TextGrid_replacePointTexts); praat_addAction1 (classTextGrid, 2, L"To Table (text alignment)...", L"Extract part...", 0, DO_TextGrids_to_Table_textAlignmentment); praat_addAction2 (classTextGrid, 2, classEditCostsTable, 1, L"To Table (text alignment)...", 0, 0, DO_TextGrids_and_EditCostsTable_to_Table_textAlignmentment); INCLUDE_MANPAGES (manual_dwtools_init) INCLUDE_MANPAGES (manual_Permutation_init) INCLUDE_LIBRARY (praat_uvafon_MDS_init) INCLUDE_LIBRARY (praat_KlattGrid_init) INCLUDE_LIBRARY (praat_HMM_init) INCLUDE_LIBRARY (praat_BSS_init) } /* End of file praat_David.cpp */ sources_5316/dwtools/Configuration.h0000644000176700017670000000764211630404722016406 0ustar paulpaul#ifndef _Configuration_h_ #define _Configuration_h_ /* Configuration.h * * Copyright (C) 1992-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Graphics.h" #include "TableOfReal.h" #include "Collection.h" #include "Configuration_def.h" oo_CLASS_CREATE (Configuration, TableOfReal); Configuration Configuration_create (long numberOfPoints, long numberOfDimensions); void Configuration_setMetric (Configuration me, long metric); void Configuration_setDefaultWeights (Configuration me); /* All w[i] = 1 */ void Configuration_setSqWeights (Configuration me, const double weight[]); /* All w[i] = sqrt (weight[i]) */ void Configuration_randomize (Configuration me); /* new x[i][j] = randomUniform (-1,1) */ void Configuration_normalize (Configuration me, double variance, int choice); /* 1. centre columns 2. choice == !0 : each column == 0 : normalize matrix */ void Configuration_rotate (Configuration me, long dimension1, long dimension2, double angle_degrees); /* Precondition: dimension1 != dimension2 1 <= dimension1, dimension2 <= my numberOfColumns */ void Configuration_invertDimension (Configuration me, int dimension); /* Function: Invert one dimension. for (i=1; i <= my numberOfRows; i++) my data[i][dimension] = - my data[i][dimension]; */ Configuration Configuration_congruenceRotation (Configuration me, Configuration thee, long maximumNumberOfIterations, double tolerance); /* Rotate thee for maximum congruence. Algorithm: Henk Kiers & Patrick Groenen (1996), "A monotonically convergent algorithm for orthogonal congruence rotation", Psychometrika 61, 375-389. */ Configuration Configuration_varimax (Configuration me, int normalizeRows, int quartimax, long maximumNumberOfIterations, double tolerance); /* Perform varimax rotation. Algorithm with extra security from: Jos Ten Berge (1995), "Suppressing permutations or rigid planar rotations: a remedy against nonoptimal varimax rotations", Psychometrika 60, 437-446. */ void Configuration_rotateToPrincipalDirections (Configuration me); void Configuration_draw (Configuration me, Graphics g, int xCoordinate, int yCoordinate, double xmin, double xmax, double ymin, double ymax, int labelSize, int useRowLabels, const wchar_t *label, int garnish); void Configuration_drawConcentrationEllipses (Configuration me, Graphics g, double scale, int confidence, const wchar_t *label, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish); Configuration TableOfReal_to_Configuration (I); Configuration TableOfReal_to_Configuration_pca (TableOfReal me, long numberOfDimensions); /* Precondition: numberOfDimensions > 0 Function: principal component analysis Postcondition: (Configuration) numberOfColumns = MIN (my numberOfColumns, numberOfDimensions) */ Configuration Configuration_createLetterRExample (int choice); /* Create a two-dimensional configuartion from the letter R. choice = 1 : undistorted; choice = 2 : result of monotone fit on distorted (d^2 + 5 +32.5*z) */ Configuration Configuration_createCarrollWishExample (); /************************** class Configurations **************************************/ Thing_define (Configurations, Ordered) { }; Configurations Configurations_create (); #endif /* _Configuration_h_ */ sources_5316/dwtools/Procrustes.h0000644000176700017670000000205511627250625015750 0ustar paulpaul#ifndef _Procrustes_h_ #define _Procrustes_h_ /* Procrustes.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010926 djmw 20020813 GPL header djmw 20110306 Latest modification. */ #include "AffineTransform.h" #include "Procrustes_def.h" oo_CLASS_CREATE (Procrustes, AffineTransform); Procrustes Procrustes_create (long n); #endif /* _Procrustes_h_ */ sources_5316/dwtools/Pitch_extensions.cpp0000644000176700017670000001705711627245261017470 0ustar paulpaul/* Pitch_extensions.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 1997 djmw 20030217 Latest modification djmw 20061201 Interface change: removed minimumPitch parameter from PitchTier_modifyRange. djmw 20061207 Removed PitchTier_modifyRange. */ #include "Pitch_extensions.h" void Pitch_Frame_addPitch (Pitch_Frame me, double f, double strength, int maxnCandidates) { long pos = 0; double weakest = 1e38; if (my nCandidates < maxnCandidates) { pos = ++ my nCandidates; } else { /* Find weakest candidate so far (skip the unvoiced one) */ for (long i = 1; i <= maxnCandidates; i++) if (my candidate[i].strength < weakest && my candidate[i].frequency > 0) { weakest = my candidate[i].strength; pos = i; } if (strength < weakest) { pos = 0; } } if (pos) { my candidate[pos].frequency = f; my candidate[pos].strength = strength; } } void Pitch_Frame_getPitch (Pitch_Frame me, double *f, double *strength) { long pos = 1; *strength = -1; for (long i = 1; i <= my nCandidates; i++) if (my candidate[i].strength > *strength && my candidate[i].frequency > 0) { *strength = my candidate[i].strength; pos = i; } *f = my candidate[pos].frequency; } void Pitch_Frame_resizeStrengths (Pitch_Frame me, double maxStrength, double unvoicedCriterium) { int pos = 1; double strongest = my candidate[1].strength; for (long i = 2; i <= my nCandidates; i++) { if (my candidate[i].strength > strongest) { strongest = my candidate[i].strength; pos = i; } } if (strongest != 0) { for (long i = 1; i <= my nCandidates; i++) { my candidate[i].strength *= maxStrength / strongest; } } if (maxStrength < unvoicedCriterium) { for (long i = 1; i <= my nCandidates; i++) if (my candidate[i].frequency == 0) { pos = i; break; } } if (pos != 1) { double tmp = my candidate[1].frequency; my candidate[1].frequency = my candidate[pos].frequency; my candidate[pos].frequency = tmp; tmp = my candidate[1].strength; my candidate[1].strength = my candidate[pos].strength; my candidate[pos].strength = tmp; } } Pitch Pitch_scaleTime (Pitch me, double scaleFactor) { try { double dx = my dx, x1 = my x1, xmax = my xmax; if (scaleFactor != 1) { dx = my dx * scaleFactor; x1 = my xmin + 0.5 * dx; xmax = my xmin + my nx * dx; } autoPitch thee = Pitch_create (my xmin, xmax, my nx, dx, x1, my ceiling, 2); for (long i = 1; i <= my nx; i++) { double f = my frame[i].candidate[1].frequency; thy frame[i].candidate[1].strength = my frame[i].candidate[1].strength; f /= scaleFactor; if (f < my ceiling) { thy frame[i].candidate[1].frequency = f; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not scaled."); } } static double HertzToSpecial (double value, int pitchUnit) { return pitchUnit == kPitch_unit_HERTZ ? value : pitchUnit == kPitch_unit_HERTZ_LOGARITHMIC ? value <= 0.0 ? NUMundefined : log10 (value) : pitchUnit == kPitch_unit_MEL ? NUMhertzToMel (value) : pitchUnit == kPitch_unit_LOG_HERTZ ? value <= 0.0 ? NUMundefined : log10 (value) : pitchUnit == kPitch_unit_SEMITONES_1 ? value <= 0.0 ? NUMundefined : 12.0 * log (value / 1.0) / NUMln2 : pitchUnit == kPitch_unit_SEMITONES_100 ? value <= 0.0 ? NUMundefined : 12.0 * log (value / 100.0) / NUMln2 : pitchUnit == kPitch_unit_SEMITONES_200 ? value <= 0.0 ? NUMundefined : 12.0 * log (value / 200.0) / NUMln2 : pitchUnit == kPitch_unit_SEMITONES_440 ? value <= 0.0 ? NUMundefined : 12.0 * log (value / 440.0) / NUMln2 : pitchUnit == kPitch_unit_ERB ? NUMhertzToErb (value) : NUMundefined; } static double SpecialToHertz (double value, int pitchUnit) { return pitchUnit == kPitch_unit_HERTZ ? value : pitchUnit == kPitch_unit_HERTZ_LOGARITHMIC ? pow (10.0, value) : pitchUnit == kPitch_unit_MEL ? NUMmelToHertz (value) : pitchUnit == kPitch_unit_LOG_HERTZ ? pow (10.0, value) : pitchUnit == kPitch_unit_SEMITONES_1 ? 1.0 * exp (value * (NUMln2 / 12.0)) : pitchUnit == kPitch_unit_SEMITONES_100 ? 100.0 * exp (value * (NUMln2 / 12.0)) : pitchUnit == kPitch_unit_SEMITONES_200 ? 200.0 * exp (value * (NUMln2 / 12.0)) : pitchUnit == kPitch_unit_SEMITONES_440 ? 440.0 * exp (value * (NUMln2 / 12.0)) : pitchUnit == kPitch_unit_ERB ? NUMerbToHertz (value) : NUMundefined; } PitchTier PitchTier_normalizePitchRange (PitchTier me, double pitchMin_ref_Hz, double pitchMax_ref_Hz, double pitchMin_Hz, double pitchMax_Hz, int pitchUnit); PitchTier PitchTier_normalizePitchRange (PitchTier me, double pitchMin_ref_Hz, double pitchMax_ref_Hz, double pitchMin_Hz, double pitchMax_Hz, int pitchUnit) { try { double fminr = HertzToSpecial (pitchMin_ref_Hz, pitchUnit); double fmaxr = HertzToSpecial (pitchMax_ref_Hz, pitchUnit); double fmin = HertzToSpecial (pitchMin_Hz, pitchUnit); double fmax = HertzToSpecial (pitchMax_Hz, pitchUnit); if (fminr == NUMundefined || fmaxr == NUMundefined || fmin == NUMundefined || fmax == NUMundefined) { Melder_throw ("The conversion of a pitch value is not defined. "); } double ranger = fmaxr - fminr, range = fmax - fmin; if (ranger < 0.01 || range < 0.01) { Melder_throw ("Pitch range too small."); } double fmidr = fminr + ranger / 2; double factor = ranger / range; autoPitchTier thee = Data_copy (me); for (long i = 1; i <= my points -> size; i ++) { RealPoint point = (RealPoint) thy points -> item [i]; double f = HertzToSpecial (point -> value, pitchUnit); f = factor * (f - fmidr); f = SpecialToHertz (f, pitchUnit); point -> value = f; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no PitchTier created."); } } Pitch PitchTier_to_Pitch (PitchTier me, double dt, double pitchFloor, double pitchCeiling) { try { if (my points -> size < 1) { Melder_throw ("The PitchTier is empty."); } if (dt <= 0) { Melder_throw ("The time step should be a positive number."); } if (pitchFloor >= pitchCeiling) { Melder_throw ("The pitch ceiling must be a higher number than the pitch floor."); } double tmin = my xmin, tmax = my xmax, t1 = my xmin + dt / 2; long nt = (tmax - tmin - t1) / dt; if (t1 + nt * dt < tmax) { nt++; } if (nt < 1) { Melder_throw ("Duration is too short."); } autoPitch thee = Pitch_create (tmin, tmax, nt, dt, t1, pitchCeiling, 1); for (long i = 1; i <= nt; i++) { Pitch_Frame frame = (Pitch_Frame) & thy frame [i]; Pitch_Candidate candidate = (Pitch_Candidate) & frame -> candidate [1]; double t = t1 + (i - 1) * dt; double f = RealTier_getValueAtTime (me, t); if (f < pitchFloor || f > pitchCeiling) { f = 0; } candidate -> frequency = f; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Pitch created."); } } /* End of file Pitch_extensions.cpp */ sources_5316/dwtools/Minimizers.h0000644000176700017670000001447611631445477015745 0ustar paulpaul#ifndef _Minimizers_h_ #define _Minimizers_h_ /* Minimizers.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20030701 Removed non-GPL minimizations djmw 20110414 Latest modification. */ #include "Data.h" #include "Graphics.h" /*********** deferred class Minimizer **********************************/ Thing_define (Minimizer, Thing) { // new data: public: long nParameters; /* the number of parameters */ double *p; /* the parameters */ double minimum; /* current minimum */ double *history; /* previous minima */ double tolerance; /* stop criterium */ Data object; /* reference to the object that uses this Minimizer */ long funcCalls; /* the number of times 'func' has been called */ long success; /* indicates whether I'm done */ long start; /* start iteration series */ long maxNumOfIterations; /* the current maximum number of iterations */ long iteration; /* the total number of iterations */ void (*after) (I, Any aclosure); /* to be called after each iteration */ Any aclosure; Graphics gmonitor; /* graphics to monitor the minimization process */ // overridden methods: virtual void v_destroy (); virtual void v_info () { } // new methods: virtual void v_minimize () { } /* does the work */ virtual void v_reset () { } /* reset the minimizer */ virtual void v_setParameters (Any parameters) { (void) parameters; } }; void Minimizer_init (I, long nParameters, Data object); /* Preconditions: nParameters > 0; Postconditions: if (gmonitor) gmonitor != NULL */ void Minimizer_reset (Minimizer me, const double guess[]); /* reset the start values for the minimizer * Preconditions: * guess != NULL; * Post conditions: * p[] = guess[]; * my minimum = 1.0e30; * success = maxNumOfIterations = iteration = funcCalls = 0; * reset (me); */ void Minimizer_setAfterEachIteration (Minimizer me, int (*after) (I, Any aclosure), Any aclosure); /* set the procedure that is executed after each iteration. */ void Minimizer_setParameters (Minimizer me, Any parameters); /* for inheritors */ void Minimizer_minimize (Minimizer me, long maxNumOfIterations, double tolerance, int monitor); /* Minimizes during maximally maxNumOfIterations. The gmonitor is initialized * before minimization and cleared afterwards. * Preconditions: * maxNumOfIterations >= 0; * tolerance > 0; * Postconditions: * if (reset) Minimizer_reset called with xopt as initial guess. * after each function call: funcCalls++ * after each iteration: iteration++ */ void Minimizer_minimizeManyTimes (Minimizer me, long numberOfTimes, long maxIterationsPerTime, double tolerance); void Minimizer_drawHistory (Minimizer me, Graphics g, long itmin, long itmax, double minimum, double maximum, int garnish); double Minimizer_getMinimum (Minimizer me); /********** deferred class LineMinimizer ************************************/ Thing_define (LineMinimizer, Minimizer) { // new data: public: /* the function to be minimized */ double (*func) (Data object, const double p[]); double maxLineStep; /*maximum step in line search direction */ double *direction; /* search direction vector */ double *ptry; /* point in search direction */ // overridden methods: virtual void v_destroy (); // new methods: //virtual void v_linmin (double p[], double fp, double direction[], double *fret); // David, is dit correct? ja }; void LineMinimizer_init (I, long nParameters, Data object, double (*func) (Data object, const double p[])); /****************** class SteepestDescentMinimizer**************************/ typedef struct structSteepestDescentMinimizer_parameters { double eta, momentum; } *SteepestDescentMinimizer_parameters; Thing_define (SteepestDescentMinimizer, Minimizer) { // new data: public: double eta, momentum; double (*func) (Data object, const double p[]); void (*dfunc) (Data object, const double p[], double dp[]); /* calculates gradient at position p */ // overridden methods: virtual void v_minimize (); virtual void v_setParameters (Any parameters); }; SteepestDescentMinimizer SteepestDescentMinimizer_create (long nParameters, Data object, double (*func) (Data object, const double p[]), void (*dfunc) (Data object, const double p[], double dp[])); /********** class VDSmagtMinimizer ********************************/ typedef struct structVDSmagtMinimizer_parameters { double lineSearchGradient; long lineSearchMaxNumOfIterations; } *VDSmagtMinimizer_parameters; Thing_define (VDSmagtMinimizer, Minimizer) { // new data: public: double (*func) (Data object, const double p[]); void (*dfunc) (Data object, const double p[], double dp[]); double *dp; double lineSearchGradient; long lineSearchMaxNumOfIterations; double gr0, gropt, df, alplim, alpha, dalpha, alphamin; double *pc; /* position of current point */ double *gc; /* gradient of current point */ double *g0; /* gradient at beginning of line search */ double *s; /* search direction for line search */ double *srst;/* search direction for first iteration after restart */ double *grst; /* gradient for first iteration after restart */ double fc, grc, fch, gr2s, temp, grs, beta, gcg0; double gamma, gamma_in, f0, gsq, gopt_sq; long lineSearch_iteration, flag, again, one_up, restart; long restart_flag; // overridden methods: virtual void v_destroy (); virtual void v_minimize (); virtual void v_reset (); virtual void v_setParameters (Any parameters); }; VDSmagtMinimizer VDSmagtMinimizer_create (long dimension, Data object, double (*func) (Data object, const double p[]), void (*dfunc) (Data object, const double p[], double dp[])); #endif /* _Minimizer_h_ */ sources_5316/dwtools/FormantGrid_extensions.h0000644000176700017670000000254411607123040020261 0ustar paulpaul#ifndef _FormantGrid_extensions_h_ #define _FormantGrid_extensions_h_ /* FormantGrid_extensions.h * * Copyright (C) 2009-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20090310 djmw 20110307 Latest modification */ #include "FormantGrid.h" #include "Graphics.h" #ifdef __cplusplus extern "C" { #endif void FormantGrid_draw (FormantGrid me, Graphics g, double xmin, double xmax, double ymin, double ymax, bool bandwidths, bool garnish, const wchar_t *method); void FormantGrid_removeFormantAndBandwidthTiers (FormantGrid me, int position); void FormantGrid_addFormantAndBandwidthTiers (FormantGrid me, int position); #ifdef __cplusplus } #endif #endif /* _FormantGrid_extensions_h_ */ sources_5316/dwtools/Configuration.cpp0000644000176700017670000004237711725110366016750 0ustar paulpaul/* Configuration.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010920 +Configuration_getDilationFactor djmw 20020315 GPL header djmw 20030513 applied change in numeric label generation djmw 20030801 Configuration_drawConcentrationEllipses extra argument djmw 20040303 Moved containsPrintableCharacter to NUM2.c djmw 20041026 Removed non-used code. djmw 20050314 Configuration_draw crashed when rowlabel==NULL djmw 20061021 printf expects %ld for 'long int' djmw 20061212 Changed info to Melder_writeLine format. djmw 20071009 wchar_t djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20100302 Extra test in Configuration_rotate djmw 20110304 Thing_new */ #include #include "SVD.h" #include "PCA.h" #include "Configuration.h" #include "Configuration_AffineTransform.h" #include "TableOfReal_extensions.h" #include "SSCP.h" #include "oo_DESTROY.h" #include "Configuration_def.h" #include "oo_COPY.h" #include "Configuration_def.h" #include "oo_EQUAL.h" #include "Configuration_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Configuration_def.h" #include "oo_WRITE_TEXT.h" #include "Configuration_def.h" #include "oo_WRITE_BINARY.h" #include "Configuration_def.h" #include "oo_READ_TEXT.h" #include "Configuration_def.h" #include "oo_READ_BINARY.h" #include "Configuration_def.h" #include "oo_DESCRIPTION.h" #include "Configuration_def.h" Thing_implement (Configuration, TableOfReal, 0); void structConfiguration :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of points: ", Melder_integer (numberOfRows)); MelderInfo_writeLine2 (L"Number of dimensions: ", Melder_integer (numberOfColumns)); MelderInfo_writeLine2 (L"Metric: ", Melder_integer (metric)); } Configuration Configuration_create (long numberOfPoints, long numberOfDimensions) { try { autoConfiguration me = Thing_new (Configuration); TableOfReal_init (me.peek(), numberOfPoints, numberOfDimensions); my w = NUMvector (1, numberOfDimensions); TableOfReal_setSequentialRowLabels (me.peek(), 0, 0, NULL, 1, 1); TableOfReal_setSequentialColumnLabels (me.peek(), 0, 0, L"dimension ", 1, 1); my metric = 2; Configuration_setDefaultWeights (me.peek()); Configuration_randomize (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("Configuration not created."); } } void Configuration_setMetric (Configuration me, long metric) { my metric = metric; } void Configuration_setDefaultWeights (Configuration me) { for (long i = 1; i <= my numberOfColumns; i++) { my w[i] = 1; } } void Configuration_setSqWeights (Configuration me, const double weight[]) { for (long i = 1; i <= my numberOfColumns; i++) { my w[i] = sqrt (weight[i]); } } void Configuration_normalize (Configuration me, double sumsq, int columns) { TableOfReal_centreColumns (me); if (columns) { sumsq = sumsq <= 0 ? 1.0 : sqrt (sumsq); NUMnormalizeColumns (my data, my numberOfRows, my numberOfColumns, sumsq); } else { if (sumsq <= 0) { sumsq = my numberOfRows; } NUMnormalize (my data, my numberOfRows, my numberOfColumns, sqrt (sumsq)); } } void Configuration_randomize (Configuration me) { for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { my data[i][j] = NUMrandomUniform (-1, 1); } } } void Configuration_rotate (Configuration me, long dimension1, long dimension2, double angle_degrees) { double f = NUMpi * (2 - angle_degrees / 180); double cosa = cos (f), sina = sin (f); if (dimension1 == dimension2 || angle_degrees == 0) { return; } if (dimension1 > dimension2) { long dt = dimension1; dimension1 = dimension2; dimension2 = dt; } if (dimension1 < 1 || dimension2 > my numberOfColumns) { return; } for (long i = 1; i <= my numberOfRows; i++) { double x1 = my data[i][dimension1], x2 = my data[i][dimension2]; my data[i][dimension1] = cosa * x1 + sina * x2; my data[i][dimension2] = - sina * x1 + cosa * x2; } } void Configuration_invertDimension (Configuration me, int dimension) { if (dimension < 1 || dimension > my numberOfColumns) { return; } for (long i = 1; i <= my numberOfRows; i++) { my data[i][dimension] = - my data[i][dimension]; } } static double NUMsquaredVariance (double **a, long nr, long nc, int rawPowers) { double v4 = 0; for (long j = 1; j <= nc; j++) { double sum4 = 0, mean = 0; for (long i = 1; i <= nr; i++) { double sq = a[i][j] * a[i][j]; sum4 += sq * sq; mean += sq; } v4 += sum4; if (! rawPowers) { v4 -= mean * mean / nr; } } return v4; } /* Varimax rotation, implementation according to: Jos Ten Berge (1995), "Suppressing permutations or rigid planar rotations: a remedy against nonoptimal varimax rotations", Psychometrika 60, 437-446. */ static void NUMvarimax (double **xm, double **ym, long nr, long nc, int normalizeRows, int quartimax, long maximumNumberOfIterations, double tolerance) { Melder_assert (nr > 0 && nc > 0); NUMmatrix_copyElements (xm, ym, 1, nr, 1, nc); if (nc == 1) { return; } if (nc == 2) { maximumNumberOfIterations = 1; } autoNUMvector u (1, nr); autoNUMvector v (1, nr); autoNUMvector norm; // Normalize sum of squares of each row to one. // After rotation we have to rescale. if (normalizeRows) { norm.reset (1, nr); for (long i = 1; i <= nr; i++) { for (long j = 1; j <= nc; j++) { norm[i] += ym[i][j] * ym[i][j]; } if (norm[i] <= 0) { continue; } norm[i] = sqrt (norm[i]); for (long j = 1; j <= nc; j++) { ym[i][j] /= norm[i]; } } } // Initial squared "variance". double varianceSq = NUMsquaredVariance (ym, nr, nc, quartimax); if (varianceSq == 0) { return; } // Treat columns pairwise. double varianceSq_old; long numberOfIterations = 0; do { for (long c1 = 1; c1 <= nc; c1++) { for (long c2 = c1 + 1; c2 <= nc; c2++) { double um = 0, vm = 0; for (long i = 1; i <= nr; i++) { double x = ym[i][c1], y = ym[i][c2]; u[i] = x * x - y * y; um += u[i]; v[i] = 2 * x * y; vm += v[i]; } um /= nr; vm /= nr; if (quartimax || nr == 1) { um = vm = 0; } /* In the paper just before equation (1): a = 2n u'v, b = n(u'u-v'v), c = sqrt(a^2+b^2) w = -sign(a) sqrt((b+c) / 2c) Tricks: multiplication with n drops out! a's multiplication by 2 outside the loop. */ double a = 0, b = 0; for (long i = 1; i <= nr; i++) { double ui = u[i] - um, vi = v[i] - vm; a += ui * vi; b += ui * ui - vi * vi; } double c = sqrt (4 * a * a + b * b); double w = sqrt ( (c + b) / (2 * c)); if (a > 0) { w = -w; } double cost = sqrt (0.5 + 0.5 * w); double sint = sqrt (0.5 - 0.5 * w); double t22 = cost; double t11 = cost; double t12 = sint; double t21 = -sint; // Prevent permutations: when w < 0, i.e., a > 0, swap columns of T:/ if (w < 0) { t11 = sint; t12 = t21 = cost; t22 = -sint; } // Rotate in the plane spanned by c1 and c2. for (long i = 1; i <= nr; i++) { double *xt = ym[i], xtc1 = xt[c1]; xt[c1] = xtc1 * t11 + xt[c2] * t21; xt[c2] = xtc1 * t12 + xt[c2] * t22; } } } numberOfIterations++; varianceSq_old = varianceSq; varianceSq = NUMsquaredVariance (ym, nr, nc, quartimax); } while (fabs (varianceSq_old - varianceSq) / varianceSq_old > tolerance && numberOfIterations < maximumNumberOfIterations); if (normalizeRows) { for (long i = 1; i <= nr; i++) { for (long j = 1; j <= nc; j++) { ym[i][j] *= norm[i]; } } } } Configuration Configuration_varimax (Configuration me, int normalizeRows, int quartimax, long maximumNumberOfIterations, double tolerance) { try { autoConfiguration thee = Data_copy (me); NUMvarimax (my data, thy data, my numberOfRows, my numberOfColumns, normalizeRows, quartimax, maximumNumberOfIterations, tolerance); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": varimax rotation not performed."); } } Configuration Configuration_congruenceRotation (Configuration me, Configuration thee, long maximumNumberOfIterations, double tolerance) { try { autoAffineTransform at = Configurations_to_AffineTransform_congruence (me, thee, maximumNumberOfIterations, tolerance); autoConfiguration him = Configuration_and_AffineTransform_to_Configuration (me, at.peek()); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": congruence rotation not performed."); } } /* Replace by TableOfReal_to_Configuration_pca ??? */ void Configuration_rotateToPrincipalDirections (Configuration me) { try { autoNUMmatrix m (NUMmatrix_copy (my data, 1, my numberOfRows, 1, my numberOfColumns), 1, 1); NUMdmatrix_into_principalComponents (my data, my numberOfRows, my numberOfColumns, my numberOfColumns, m.peek()); NUMvector_free (my data, 1); my data = m.transfer(); } catch (MelderError) { Melder_throw (me, ": not rotated to principal directions."); } } void Configuration_draw (Configuration me, Graphics g, int xCoordinate, int yCoordinate, double xmin, double xmax, double ymin, double ymax, int labelSize, int useRowLabels, const wchar_t *label, int garnish) { long nPoints = my numberOfRows, numberOfDimensions = my numberOfColumns; if (numberOfDimensions > 1 && (xCoordinate > numberOfDimensions || yCoordinate > numberOfDimensions)) { return; } if (numberOfDimensions == 1) { xCoordinate = 1; } int fontSize = Graphics_inqFontSize (g), noLabel = 0; if (labelSize == 0) { labelSize = fontSize; } autoNUMvector x (1, nPoints); autoNUMvector y (1, nPoints); for (long i = 1; i <= nPoints; i++) { x[i] = my data[i][xCoordinate] * my w[xCoordinate]; y[i] = numberOfDimensions > 1 ? my data[i][yCoordinate] * my w[yCoordinate] : 0; } if (xmax <= xmin) { NUMvector_extrema (x.peek(), 1, nPoints, &xmin, &xmax); } if (xmax <= xmin) { xmax += 1; xmin -= 1; } if (ymax <= ymin) { NUMvector_extrema (y.peek(), 1, nPoints, &ymin, &ymax); } if (ymax <= ymin) { ymax += 1; ymin -= 1; } Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setInner (g); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_setFontSize (g, labelSize); for (long i = 1; i <= my numberOfRows; i++) { if (x[i] >= xmin && x[i] <= xmax && y[i] >= ymin && y[i] <= ymax) { wchar_t const *plotLabel = useRowLabels ? my rowLabels[i] : label; if (NUMstring_containsPrintableCharacter (plotLabel)) { Graphics_text (g, x[i], y[i], plotLabel); } else { noLabel++; } } } Graphics_setFontSize (g, fontSize); Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_BOTTOM); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); if (numberOfDimensions > 1) { Graphics_marksLeft (g, 2, 1, 1, 0); if (my columnLabels[xCoordinate]) { Graphics_textBottom (g, 1, my columnLabels[xCoordinate]); } if (my columnLabels[yCoordinate]) { Graphics_textLeft (g, 1, my columnLabels[yCoordinate]); } } } if (noLabel > 0) Melder_warning (L"Configuration_draw: ", Melder_integer (noLabel), L" from ", Melder_integer (my numberOfRows), L" labels are not visible because they are empty or they contain only spaces or they contain only non-printable characters"); } void Configuration_drawConcentrationEllipses (Configuration me, Graphics g, double scale, int confidence, const wchar_t *label, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish) { autoSSCPs sscps = TableOfReal_to_SSCPs_byLabel (me); SSCPs_drawConcentrationEllipses (sscps.peek(), g, scale, confidence, label, d1, d2, xmin, xmax, ymin, ymax, fontSize, garnish); } Configuration TableOfReal_to_Configuration (I) { iam (TableOfReal); try { autoConfiguration thee = Configuration_create (my numberOfRows, my numberOfColumns); NUMmatrix_copyElements (my data, thy data, 1, my numberOfRows, 1, my numberOfColumns); TableOfReal_copyLabels (me, thee.peek(), 1, 1); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted."); } } Configuration TableOfReal_to_Configuration_pca (TableOfReal me, long numberOfDimensions) { try { if (numberOfDimensions < 1 || numberOfDimensions > my numberOfColumns) { numberOfDimensions = my numberOfColumns; } autoPCA pca = TableOfReal_to_PCA (me); autoConfiguration thee = PCA_and_TableOfReal_to_Configuration (pca.peek(), me, numberOfDimensions); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": pca not performed."); } } /********************** Examples *********************************************/ Configuration Configuration_createLetterRExample (int choice) { double x1[33] = { 0, -5, -5, -5, -5, -5, -5, -5, -5, -5, -5, -5, -4, -3, -2, -1, 0, 1, 2.25, 3, 3, 2.25, 1, 0, -1, -2, -3, -4, -1, 0, 1, 2, 3 }; double y1[33] = { 0, -6, -5, -4, -3, -2, -1, 0, 1, 2, 3, 4, 4, 4, 4, 4, 4, 4, 3.5, 2, 1, -0.5, -1, -1, -1, -1, -1, -1, -2, -3, -4, -5, -6 }; double x2[33] = {0, 0.94756043346272423, 0.73504466902509913, 0.4528453515175927, 0.46311499024105723, 0.30345454816993439, 0.075184942115601547, -0.090010071904764719, -0.19630977381424003, -0.36341509807865086, -0.54216996409132612, -0.68704678013309872, -0.67370169194623086, -0.69336494336440502, -0.67809065144478664, -0.61382610572366281, -0.68656530656078996, -0.57704879646736551, -0.63417502349009069, -0.37153350651419026, -0.091809666009009777, 0.054833807442559397, 0.1445593164362155, 0.055587230806920782, 0.18201798315035453, 0.048445620192953162, 0.081595930742961439, 0.20063623749033621, 0.28546520751183313, 0.39384438699721991, 0.62832258520372286, 0.78548335015622228, 1.0610707888793069 }; double y2[33] = {0, 0.49630791172076621, 0.53320347382055022, 0.62384637225470441, 0.47592708487655661, 0.50364353255684202, 0.55311720162084443, 0.55118713773007066, 0.50007736370068601, 0.40432332354648709, 0.49817059660482677, 0.49803436631629411, 0.33213829258059019, 0.14585700576425648, -0.022110500334692869, -0.1752555003289698, -0.29448744336706828, -0.45639468287493545, -0.59177815505008013, -0.74980550818568981, -0.78095916436791279, -0.64447562732895125, -0.49526830813007033, -0.22443396573313243, -0.066378148077667398, -0.03498490725857361, 0.16196028200653381, 0.30633527000982519, -0.14894460651161745, -0.30808798640907431, -0.35920781945385832, -0.62766325578928184, -0.60389363590825562 }; try { double *x, *y; autoConfiguration me = Configuration_create (32, 2); if (choice == 2) { x = x2; y = y2; Thing_setName (me.peek(), L"R_fit"); } else { x = x1; y = y1; Thing_setName (me.peek(), L"R"); } for (long i = 1; i <= 32; i++) { wchar_t s[20]; swprintf (s, 20, L"%ld", i); TableOfReal_setRowLabel (me.peek(), i, s); my data [i][1] = x[i]; my data [i][2] = y[i]; } return me.transfer(); } catch (MelderError) { Melder_throw ("Letter R Configuration not created."); } } Configuration Configuration_createCarrollWishExample () { double x[10] = {0, -1, 0, 1, -1, 0, 1, -1, 0, 1}; double y[10] = {0, 1, 1, 1, 0, 0, 0, -1, -1, -1}; wchar_t const *label[] = { L"", L"A", L"B", L"C", L"D", L"E", L"F", L"G", L"H", L"I"}; try { long nObjects = 9; autoConfiguration me = Configuration_create (nObjects, 2); for (long i = 1; i <= nObjects; i++) { my data[i][1] = x[i]; my data[i][2] = y[i]; TableOfReal_setRowLabel (me.peek(), i, label[i]); } return me.transfer(); } catch (MelderError) { Melder_throw ("Carroll Wish Configuration not created."); } } /************ CONFIGURATIONS **************************************/ Thing_implement (Configurations, Ordered, 0); Configurations Configurations_create () { try { autoConfigurations me = Thing_new (Configurations); Ordered_init (me.peek(), classConfiguration, 10); return me.transfer(); } catch (MelderError) { Melder_throw ("Configurations not created."); } } /* End of file Configuration.cpp */ sources_5316/dwtools/Polygon_extensions.h0000664000176700017670000000705511723710247017512 0ustar paulpaul#ifndef _Polygon_extensions_h_ #define _Polygon_extensions_h_ /* Polygon_extensions.h * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 1996 djmw 20020813 GPL header djmw 20120220 Latest modification */ #include "Polygon.h" #include "Categories.h" #include "Graphics.h" #include "Sound.h" #define Polygon_INSIDE -1 #define Polygon_OUTSIDE 0 #define Polygon_BOUNDARY 1 #define Polygon_EDGE 3 #define Polygon_VERTEX 5 void Polygon_getExtrema (Polygon me, double *xmin, double *xmax, double *ymin, double *ymax); Polygon Polygon_createSimple (wchar_t *xystring); Polygon Polygon_createFromRandomVertices (long numberOfVertices, double xmin, double xmax, double ymin, double ymax); Polygon Polygon_simplify (Polygon me); void Polygon_translate (Polygon me, double xt, double yt); void Polygon_rotate (Polygon me, double alpha, double xc, double yc); void Polygon_scale (Polygon me, double xs, double ys); void Polygon_reverseX (Polygon me); void Polygon_reverseY (Polygon me); Polygon Polygon_circularPermutation (Polygon me, long nshift); // Is point (x,y) Inside, Outside, Boundary (Edge or Vertex) ? int Polygon_getLocationOfPoint (Polygon me, double x0, double y0, double eps); void Polygon_Categories_draw (Polygon me, Any categories, Graphics graphics, double xmin, double xmax, double ymin, double ymax, int garnish); /* reverse axis when min > max */ void Polygon_drawMarks (Polygon me, Graphics g, double xmin, double xmax, double ymin, double ymax, double size_mm, const wchar_t *mark); Polygon Sound_to_Polygon (Sound me, int channel, double tmin, double tmax, double ymin, double ymax, double level); /* Post-conditions: If there are ns = i2 - i1 + 1 samples of the sound in the interval (tmin, tmax), the first at index i1 and the last at index i2, the Polygon will have np = 2 + ns + 2 + 1 points. i1 = Sampled_xToHighIndex (me, tmin) i2 = Sampled_xToLowIndex (me, tmax) thy x[1] = tmin thy y[1] = clip(level) thy x[2] = tmin thy y[2] = interpolated amplitude in 'channel' at tmin (or, averaged over all channels if channel = 0) thy x[3] = my x1 + (i1 - 1) * my dx thy y[3] = clip(my z[channel][i1]) (or, averaged over all channels if channel == 0) ... thy x[ns+2] = my x1 +(i2 - 1) * my dx thy y[ns+2] = clip(my z[channel][i2]) (or, averaged over all channels if channel == 0) thy x[ns+3] = tmax thy y[ns+3] = clip(interpolated amplitude in 'channel' at tmax (or, averaged over all channels if channel == 0)) thy x[ns+4] = tmax thy y[ns+4] = clip(level) thy x[ns+5] = thy x[1] (close the path) thy y[ns+5] = thy y[1] where clip(y) = y < ymin ? ymin : y > ymax ? ymax ; y; */ Polygon Sounds_to_Polygon_enclosed (Sound me, Sound thee, int channel, double tmin, double tmax, double ymin, double ymax); /* Area enclosed by the sounds */ Polygon Polygons_union (Polygon me, Polygon thee); Collection Polygons_clip (Polygon me, Polygon thee); #endif /* _Polygon_extensions_h_ */ sources_5316/dwtools/Discriminant.cpp0000644000176700017670000006571411725122771016570 0ustar paulpaul/* Discriminant.c * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20011016 removed some causes for compiler warnings djmw 20020313 removed obsolete TableOfReal_sortByLabels method djmw 20020314 +Discriminant_extractWithinGroupSSCP, +Discriminant_extractGroupLabels, +Discriminant_setGroupLabels. djmw 20020327 modified Discriminant_and_TableOfReal_to_Configuration djmw 20020418 Removed some causes for compiler warnings djmw 20020502 modified call Eigen_and_TableOfReal_project_into djmw 20030801 Discriminant_drawConcentrationEllipses extra argument djmw 20050405 Modified column label: eigenvector->Eigenvector djmw 20061021 printf expects %ld for 'long int' djmw 20061212 Changed info to Melder_writeLine format. djmw 20071009 wchar_t djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20071201 Melder_warning djmw 20081119 Check in TableOfReal_to_Discriminant if TableOfReal_areAllCellsDefined djmw 20100107 +Discriminant_and_TableOfReal_mahalanobis djmw 20110304 Thing_new */ #include "Discriminant.h" #include "SSCP.h" #include "Eigen_and_SSCP.h" #include "Eigen_and_TableOfReal.h" #include "NUMlapack.h" #include "SVD.h" #include "NUM2.h" #include "TableOfReal_extensions.h" #include "oo_DESTROY.h" #include "Discriminant_def.h" #include "oo_COPY.h" #include "Discriminant_def.h" #include "oo_EQUAL.h" #include "Discriminant_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Discriminant_def.h" #include "oo_WRITE_TEXT.h" #include "Discriminant_def.h" #include "oo_READ_TEXT.h" #include "Discriminant_def.h" #include "oo_WRITE_BINARY.h" #include "Discriminant_def.h" #include "oo_READ_BINARY.h" #include "Discriminant_def.h" #include "oo_DESCRIPTION.h" #include "Discriminant_def.h" #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) Thing_implement (Discriminant, Eigen, 0); void structDiscriminant :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of groups: ", Melder_integer (numberOfGroups)); MelderInfo_writeLine2 (L"Number of variables: ", Melder_integer (dimension)); MelderInfo_writeLine2 (L"Number of discriminant functions: ", Melder_integer (Discriminant_getNumberOfFunctions (this))); MelderInfo_writeLine2 (L"Number of observations (total): ", Melder_integer (Discriminant_getNumberOfObservations (this, 0))); } Discriminant Discriminant_create (long numberOfGroups, long numberOfEigenvalues, long dimension) { try { autoDiscriminant me = Thing_new (Discriminant); my numberOfGroups = numberOfGroups; Eigen_init (me.peek(), numberOfEigenvalues, dimension); my groups = SSCPs_create (); my total = SSCP_create (dimension); my aprioriProbabilities = NUMvector (1, numberOfGroups); my costs = NUMmatrix (1, numberOfGroups, 1, numberOfGroups); return me.transfer(); } catch (MelderError) { Melder_throw ("Discriminant not created."); } } long Discriminant_groupLabelToIndex (Discriminant me, const wchar_t *label) { wchar_t *name; for (long i = 1; i <= my numberOfGroups; i++) { if ( (name = Thing_getName ( (Thing) my groups -> item[i])) && wcsequ (name, label)) { return i; } } return 0; } long Discriminant_getNumberOfGroups (Discriminant me) { return my numberOfGroups; } long Discriminant_getNumberOfObservations (Discriminant me, long group) { if (group == 0) { SSCP sscp = (SSCP) my total; return sscp -> numberOfObservations; } else if (group >= 1 && group <= my numberOfGroups) { SSCP sscp = (SSCP) my groups -> item[group]; return sscp -> numberOfObservations; } else { return -1; } } void Discriminant_setAprioriProbability (Discriminant me, long group, double p) { if (group < 1 || group > my numberOfGroups) { Melder_throw ("The group number (", group, ") must be in the interval [1, ", my numberOfGroups, "]; the supplied value (", group, ") falls outside it."); } if (p < 0 || p > 1) { Melder_throw ("The probability must be in the interval [0, 1]; the supplied value (", p, ") falls outside it."); } my aprioriProbabilities[group] = p; } long Discriminant_getNumberOfFunctions (Discriminant me) { long nf = MIN (my numberOfGroups - 1, my dimension); nf = MIN (nf, my numberOfEigenvalues); return nf; } void Discriminant_setGroupLabels (Discriminant me, Strings thee) { if (my numberOfGroups != thy numberOfStrings) Melder_throw ("The number of strings must equal the number of groups."); for (long i = 1; i <= my numberOfGroups; i++) { const wchar_t *noname = L"", *name; name = thy strings[i]; if (name == 0) { name = noname; } Thing_setName ( (Thing) my groups -> item[i], name); } } Strings Discriminant_extractGroupLabels (Discriminant me) { try { autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, my numberOfGroups); thy numberOfStrings = my numberOfGroups; for (long i = 1; i <= my numberOfGroups; i++) { wchar_t *name = Thing_getName ( (Thing) my groups -> item[i]); thy strings[i] = Melder_wcsdup (name); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": group labels not extracted."); } } TableOfReal Discriminant_extractGroupCentroids (Discriminant me) { try { long m = my groups -> size, n = my dimension; autoTableOfReal thee = TableOfReal_create (m, n); for (long i = 1; i <= m; i++) { SSCP sscp = (SSCP) my groups -> item[i]; TableOfReal_setRowLabel (thee.peek(), i, Thing_getName (sscp)); NUMvector_copyElements (sscp -> centroid, thy data[i], 1, n); } NUMstrings_copyElements ( ( (SSCP) my groups -> item[m]) -> columnLabels, thy columnLabels, 1, n); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": group centroids not extracted."); } } TableOfReal Discriminant_extractGroupStandardDeviations (Discriminant me) { try { long m = my groups -> size, n = my dimension; autoTableOfReal thee = TableOfReal_create (m, n); for (long i = 1; i <= m; i++) { SSCP sscp = (SSCP) my groups -> item[i]; TableOfReal_setRowLabel (thee.peek(), i, Thing_getName (sscp)); long numberOfObservationsm1 = sscp -> numberOfObservations - 1; for (long j = 1; j <= n; j++) { thy data[i][j] = numberOfObservationsm1 > 0 ? sqrt (sscp -> data[j][j] / numberOfObservationsm1) : NUMundefined; } } NUMstrings_copyElements ( ( (SSCP) my groups -> item[m]) -> columnLabels, thy columnLabels, 1, n); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": group standard deviations not extracted."); } } double Discriminant_getWilksLambda (Discriminant me, long from) { long numberOfFunctions = Discriminant_getNumberOfFunctions (me); if (from >= numberOfFunctions) { return 1; } if (from < 1) { from = 1; } return NUMwilksLambda (my eigenvalues, 1 + from, numberOfFunctions); } /* raw r[j]: eigenvec[i][j] unstandardized u[j]: sqrt(N-g) * r[j] standardized s[j]: u[j] sqrt (w[i][i] / (N-g)) */ TableOfReal Discriminant_extractCoefficients (Discriminant me, int choice) { try { int raw = choice == 0, standardized = choice == 2; long nx = my dimension, ny = my numberOfEigenvalues; SSCP total = my total; autoTableOfReal thee = TableOfReal_create (ny, nx + 1); NUMstrings_copyElements (my total -> columnLabels, thy columnLabels, 1, nx); autoSSCP within = 0; if (standardized) { within.reset (Discriminant_extractPooledWithinGroupsSSCP (me)); } TableOfReal_setColumnLabel (thee.peek(), nx + 1, L"constant"); TableOfReal_setSequentialRowLabels (thee.peek(), 1, ny, L"function_", 1, 1); double scale = sqrt (total -> numberOfObservations - my numberOfGroups); double *centroid = my total -> centroid; for (long i = 1; i <= ny; i++) { double u0 = 0, ui; for (long j = 1; j <= nx; j++) { if (standardized) { scale = sqrt (within -> data[j][j]); } thy data[i][j] = ui = scale * my eigenvectors[i][j];; u0 += ui * centroid[j]; } thy data[i][nx + 1] = raw ? 0 : -u0; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": coefficients not extracted."); } } static long Discriminant_getDegreesOfFreedom (Discriminant me) { long ndf = 0; for (long i = 1; i <= my groups -> size; i++) { ndf += SSCP_getDegreesOfFreedom (my groups -> item[i]); } return ndf; } void Discriminant_getPartialDiscriminationProbability (Discriminant me, long numberOfDimensions, double *probability, double *chisq, long *ndf) { long g = my numberOfGroups; long p = my dimension, k = numberOfDimensions; long numberOfFunctions = Discriminant_getNumberOfFunctions (me); double degreesOfFreedom = Discriminant_getDegreesOfFreedom (me); double lambda; *probability = 1; *chisq = 0; *ndf = 0; if (k >= numberOfFunctions) { return; } lambda = NUMwilksLambda (my eigenvalues, k + 1, numberOfFunctions); if (lambda == 1) { return; } *chisq = - (degreesOfFreedom + (g - p) / 2 - 1) * log (lambda); *ndf = (p - k) * (g - k - 1); *probability = NUMchiSquareQ (*chisq, *ndf); } double Discriminant_getConcentrationEllipseArea (Discriminant me, long group, double scale, int confidence, int discriminantDirections, long d1, long d2) { SSCPs groups = my groups; double area = NUMundefined; if (group < 1 || group > my numberOfGroups) { return area; } if (discriminantDirections) { autoSSCP thee = Eigen_and_SSCP_project (me, (SSCP) groups -> item[group]); area = SSCP_getConcentrationEllipseArea (thee.peek(), scale, confidence, d1, d2); } else { area = SSCP_getConcentrationEllipseArea (groups -> item[group], scale, confidence, d1, d2); } return area; } double Discriminant_getLnDeterminant_group (Discriminant me, long group) { if (group < 1 || group > my numberOfGroups) { return NUMundefined; } autoCovariance c = SSCP_to_Covariance ( (SSCP) my groups -> item[group], 1); double ln_d = SSCP_getLnDeterminant (c.peek()); return ln_d; } double Discriminant_getLnDeterminant_total (Discriminant me) { autoCovariance c = SSCP_to_Covariance (my total, 1); double ln_d = SSCP_getLnDeterminant (c.peek()); return ln_d; } SSCP Discriminant_extractPooledWithinGroupsSSCP (Discriminant me) { return SSCPs_to_SSCP_pool (my groups); } SSCP Discriminant_extractWithinGroupSSCP (Discriminant me, long index) { try { if (index < 1 || index > my numberOfGroups) Melder_throw ("Index must be in interval [1,", my numberOfGroups, "]."); autoSSCP thee = Data_copy ( (SSCP) my groups -> item[index]); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": within group SSCP not created."); } } SSCP Discriminant_extractBetweenGroupsSSCP (Discriminant me) { try { long n = my total -> numberOfRows; autoSSCP b = Data_copy (my total); autoSSCP w = SSCPs_to_SSCP_pool (my groups); for (long i = 1; i <= n; i++) { for (long j = i; j <= n; j++) { b -> data[j][i] = (b -> data[i][j] -= w -> data[i][j]); } } return b.transfer(); } catch (MelderError) { Melder_throw (me, ": between group SSCP not created."); } } void Discriminant_drawTerritorialMap (Discriminant me, Graphics g, int discriminantDirections, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int poolCovarianceMatrices, int garnish) { (void) me; (void) g; (void) discriminantDirections; (void) d1; (void) d2; (void) xmin; (void) xmax; (void) ymin; (void) ymax; (void) fontSize; (void) poolCovarianceMatrices; (void) garnish; } void Discriminant_drawConcentrationEllipses (Discriminant me, Graphics g, double scale, int confidence, wchar_t *label, int discriminantDirections, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish) { long numberOfFunctions = Discriminant_getNumberOfFunctions (me); if (! discriminantDirections) { SSCPs_drawConcentrationEllipses (my groups, g, scale, confidence, label, d1, d2, xmin, xmax, ymin, ymax, fontSize, garnish); return; } if (numberOfFunctions <= 1) { Melder_warning (L"Discriminant_drawConcentrationEllipses: Nothing drawn " "because there is only one dimension in the discriminant space."); return; } // Project SSCPs on eigenvectors. if (d1 == 0 && d2 == 0) { d1 = 1; d2 = MIN (numberOfFunctions, d1 + 1); } else if (d1 < 0 || d2 > numberOfFunctions) { return; } double *v1 = my eigenvectors[d1]; double *v2 = my eigenvectors[d2]; autoSSCPs thee = SSCPs_toTwoDimensions (my groups, v1, v2); SSCPs_drawConcentrationEllipses (thee.peek(), g, scale, confidence, label, 1, 2, xmin, xmax, ymin, ymax, fontSize, 0); if (garnish) { wchar_t llabel[40]; Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); swprintf (llabel, 40, L"function %ld", d2); Graphics_textLeft (g, 1, llabel); Graphics_marksBottom (g, 2, 1, 1, 0); swprintf (llabel, 40, L"function %ld", d1); Graphics_textBottom (g, 1, llabel); } } Discriminant TableOfReal_to_Discriminant (I) { iam (TableOfReal); try { autoDiscriminant thee = Thing_new (Discriminant); long dimension = my numberOfColumns; TableOfReal_areAllCellsDefined (me, 0, 0, 0, 0); if (NUMdmatrix_hasInfinities (my data, 1, my numberOfRows, 1, dimension)) { Melder_throw ("Table contains infinities."); } if (! TableOfReal_hasRowLabels (me)) { Melder_throw ("At least one of the rows has no label."); } autoTableOfReal mew = TableOfReal_sortOnlyByRowLabels (me); if (! TableOfReal_hasColumnLabels (mew.peek())) { TableOfReal_setSequentialColumnLabels (mew.peek(), 0, 0, L"c", 1, 1); } thy groups = TableOfReal_to_SSCPs_byLabel (mew.peek()); thy total = TableOfReal_to_SSCP (mew.peek(), 0, 0, 0, 0); if ( (thy numberOfGroups = thy groups -> size) < 2) { Melder_throw ("Number of groups must be greater than one."); } TableOfReal_centreColumns_byRowLabel (mew.peek()); // Overall centroid and apriori probabilities and costs. autoNUMvector centroid (1, dimension); autoNUMmatrix between (1, thy numberOfGroups, 1, dimension); thy aprioriProbabilities = NUMvector (1, thy numberOfGroups); thy costs = NUMmatrix (1, thy numberOfGroups, 1, thy numberOfGroups); double sum = 0, scale; for (long k = 1; k <= thy numberOfGroups; k++) { SSCP m = (SSCP) thy groups -> item[k]; sum += scale = SSCP_getNumberOfObservations (m); for (long j = 1; j <= dimension; j++) { centroid[j] += scale * m -> centroid[j]; } } for (long j = 1; j <= dimension; j++) { centroid[j] /= sum; } for (long k = 1; k <= thy numberOfGroups; k++) { SSCP m = (SSCP) thy groups -> item[k]; scale = SSCP_getNumberOfObservations (m); thy aprioriProbabilities[k] = scale / my numberOfRows; for (long j = 1; j <= dimension; j++) { between[k][j] = sqrt (scale) * (m -> centroid[j] - centroid[j]); } } // We need to solve B'B.x = lambda W'W.x, where B'B and W'W are the between and within covariance matrices. // We do not calculate these covariance matrices directly from the data but instead use the GSVD to solve for // the eigenvalues and eigenvectors of the equation. Eigen_initFromSquareRootPair (thee.peek(), between.peek(), thy numberOfGroups, dimension, mew -> data, my numberOfRows); // Default priors and costs for (long k = 1; k <= thy numberOfGroups; k++) { for (long j = k + 1; j <= thy numberOfGroups; j++) { thy costs[k][j] = thy costs[j][k] = 1; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Discriminant not created."); } } Configuration Discriminant_and_TableOfReal_to_Configuration (Discriminant me, TableOfReal thee, long numberOfDimensions) { try { if (numberOfDimensions == 0) { numberOfDimensions = Discriminant_getNumberOfFunctions (me); } autoConfiguration him = Configuration_create (thy numberOfRows, numberOfDimensions); Configuration thim = him.peek(); Eigen_and_TableOfReal_project_into (me, thee, 1, thy numberOfColumns, & thim, 1, numberOfDimensions); TableOfReal_copyLabels (thee, thim, 1, 0); TableOfReal_setSequentialColumnLabels (him.peek(), 0, 0, L"Eigenvector ", 1, 1); return him.transfer(); } catch (MelderError) { Melder_throw ("Configuration not created."); } } /* Calculate squared Mahalanobis distance: (v-m)'S^-1(v-m). Input matrix (li) is the inverse L^-1 of the Cholesky decomposition S = L.L'. */ static double mahalanobisDistanceSq (double **li, long n, double *v, double *m, double *buf) { for (long i = 1; i <= n; i++) { buf[i] = v[i] - m[i]; } double chisq = 0; for (long i = n; i > 0; i--) { double t = 0; for (long j = 1; j <= i; j++) { t += li[i][j] * buf[j]; } chisq += t * t; } return chisq; } TableOfReal Discriminant_and_TableOfReal_mahalanobis (Discriminant me, TableOfReal thee, long group, bool poolCovarianceMatrices) { try { if (group < 1 || group > my numberOfGroups) { Melder_throw ("Group does not exist."); } autoSSCP pool = SSCPs_to_SSCP_pool (my groups); autoCovariance covg = SSCP_to_Covariance (pool.peek(), my numberOfGroups); autoCovariance cov = SSCP_to_Covariance ( (SSCP) my groups -> item[group], 1); autoTableOfReal him = 0; if (poolCovarianceMatrices) { // use group mean instead of overall mean! NUMvector_copyElements (cov -> centroid, covg -> centroid, 1, cov -> numberOfColumns); him.reset (Covariance_and_TableOfReal_mahalanobis (covg.peek(), thee, false)); } else { him.reset (Covariance_and_TableOfReal_mahalanobis (cov.peek(), thee, false)); } return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal not created."); } } ClassificationTable Discriminant_and_TableOfReal_to_ClassificationTable (Discriminant me, TableOfReal thee, int poolCovarianceMatrices, int useAprioriProbabilities) { try { long g = Discriminant_getNumberOfGroups (me); long p = Eigen_getDimensionOfComponents (me); long m = thy numberOfRows; if (p != thy numberOfColumns) Melder_throw ("The number of columns does not agree with the dimension of the discriminant."); autoNUMvector log_p (1, g); autoNUMvector log_apriori (1, g); autoNUMvector ln_determinant (1, g); autoNUMvector buf (1, p); autoNUMvector sscpvec (1, g); autoSSCP pool = SSCPs_to_SSCP_pool (my groups); autoClassificationTable him = ClassificationTable_create (m, g); NUMstrings_copyElements (thy rowLabels, his rowLabels, 1, m); // Scale the sscp to become a covariance matrix. for (long i = 1; i <= p; i++) { for (long k = i; k <= p; k++) { pool -> data[k][i] = (pool -> data[i][k] /= (pool -> numberOfObservations - g)); } } double lnd; autoSSCPs agroups = 0; SSCPs groups; if (poolCovarianceMatrices) { /* Covariance matrix S can be decomposed as S = L.L'. Calculate L^-1. L^-1 will be used later in the Mahalanobis distance calculation: v'.S^-1.v == v'.L^-1'.L^-1.v == (L^-1.v)'.(L^-1.v). */ NUMlowerCholeskyInverse (pool -> data, p, &lnd); for (long j = 1; j <= g; j++) { ln_determinant[j] = lnd; sscpvec[j] = pool.peek(); } groups = (SSCPs) my groups; } else { // Calculate the inverses of all group covariance matrices. // In case of a singular matrix, substitute inverse of pooled. agroups.reset (Data_copy ( (SSCPs) my groups)); groups = agroups.peek(); long npool = 0; for (long j = 1; j <= g; j++) { SSCP t = (SSCP) groups -> item[j]; long no = SSCP_getNumberOfObservations (t); for (long i = 1; i <= p; i++) { for (long k = i; k <= p; k++) { t -> data[k][i] = (t -> data[i][k] /= (no - 1)); } } sscpvec[j] = (SSCP) groups -> item[j]; try { NUMlowerCholeskyInverse (t -> data, p, &ln_determinant[j]); } catch (MelderError) { // Try the alternative: the pooled covariance matrix. // Clear the error. Melder_clearError (); if (npool == 0) { NUMlowerCholeskyInverse (pool -> data, p, &lnd); } npool++; sscpvec[j] = pool.peek(); ln_determinant[j] = lnd; } } if (npool > 0) { Melder_warning (Melder_integer (npool), L" groups use pooled covariance matrix."); } } // Labels for columns in ClassificationTable for (long j = 1; j <= g; j++) { const wchar_t *name = Thing_getName ( (Thing) my groups -> item[j]); if (! name) { name = L"?"; } TableOfReal_setColumnLabel (him.peek(), j, name); } // Normalize the sum of the apriori probabilities to 1. // Next take ln (p) because otherwise probabilities might be too small to represent. NUMvector_normalize1 (my aprioriProbabilities, g); double logg = log (g); for (long j = 1; j <= g; j++) { log_apriori[j] = useAprioriProbabilities ? log (my aprioriProbabilities[j]) : - logg; } // Generalized squared distance function: // D^2(x) = (x - mu)' S^-1 (x - mu) + ln (determinant(S)) - 2 ln (apriori) for (long i = 1; i <= m; i++) { double norm = 0, pt_max = -1e38; for (long j = 1; j <= g; j++) { SSCP t = (SSCP) groups -> item[j]; double md = mahalanobisDistanceSq (sscpvec[j] -> data, p, thy data[i], t -> centroid, buf.peek()); double pt = log_apriori[j] - 0.5 * (ln_determinant[j] + md); if (pt > pt_max) { pt_max = pt; } log_p[j] = pt; } for (long j = 1; j <= g; j++) { norm += (log_p[j] = exp (log_p[j] - pt_max)); } for (long j = 1; j <= g; j++) { his data[i][j] = log_p[j] / norm; } } return him.transfer(); } catch (MelderError) { Melder_throw ("ClassificationTable from Discriminant & TableOfReal not created."); } } ClassificationTable Discriminant_and_TableOfReal_to_ClassificationTable_dw (Discriminant me, TableOfReal thee, int poolCovarianceMatrices, int useAprioriProbabilities, double alpha, double minProb, TableOfReal *displacements) { try { long g = Discriminant_getNumberOfGroups (me); long p = Eigen_getDimensionOfComponents (me); long m = thy numberOfRows; if (p != thy numberOfColumns) Melder_throw ("The number of columns does not agree with the dimension of the discriminant."); autoNUMvector log_p (1, g); autoNUMvector log_apriori (1, g); autoNUMvector ln_determinant (1, g); autoNUMvector buf (1, p); autoNUMvector displacement (1, p); autoNUMvector x (1, p); autoNUMvector sscpvec (1, g); autoSSCP pool = SSCPs_to_SSCP_pool (my groups); autoClassificationTable him = ClassificationTable_create (m, g); NUMstrings_copyElements (thy rowLabels, his rowLabels, 1, m); autoTableOfReal adisplacements = Data_copy (thee); // Scale the sscp to become a covariance matrix. for (long i = 1; i <= p; i++) { for (long k = i; k <= p; k++) { pool -> data[k][i] = (pool -> data[i][k] /= (pool -> numberOfObservations - g)); } } double lnd; autoSSCPs agroups = 0; SSCPs groups; if (poolCovarianceMatrices) { // Covariance matrix S can be decomposed as S = L.L'. Calculate L^-1. // L^-1 will be used later in the Mahalanobis distance calculation: // v'.S^-1.v == v'.L^-1'.L^-1.v == (L^-1.v)'.(L^-1.v). NUMlowerCholeskyInverse (pool -> data, p, &lnd); for (long j = 1; j <= g; j++) { ln_determinant[j] = lnd; sscpvec[j] = pool.peek(); } groups = my groups; } else { //Calculate the inverses of all group covariance matrices. // In case of a singular matrix, substitute inverse of pooled. agroups.reset (Data_copy ( (SSCPs) my groups)); groups = agroups.peek(); long npool = 0; for (long j = 1; j <= g; j++) { SSCP t = (SSCP) groups -> item[j]; long no = SSCP_getNumberOfObservations (t); for (long i = 1; i <= p; i++) { for (long k = i; k <= p; k++) { t -> data[k][i] = (t -> data[i][k] /= (no - 1)); } } sscpvec[j] = (SSCP) groups -> item[j]; try { NUMlowerCholeskyInverse (t -> data, p, &ln_determinant[j]); } catch (MelderError) { // Try the alternative: the pooled covariance matrix. // Clear the error. Melder_clearError (); if (npool == 0) { NUMlowerCholeskyInverse (pool -> data, p, &lnd); } npool++; sscpvec[j] = pool.peek(); ln_determinant[j] = lnd; } } if (npool > 0) { Melder_warning (Melder_integer (npool), L" groups use pooled covariance matrix."); } } // Labels for columns in ClassificationTable for (long j = 1; j <= g; j++) { const wchar_t *name = Thing_getName ( (Thing) my groups -> item[j]); if (! name) { name = L"?"; } TableOfReal_setColumnLabel (him.peek(), j, name); } // Normalize the sum of the apriori probabilities to 1. // Next take ln (p) because otherwise probabilities might be too small to represent. double logg = log (g); NUMvector_normalize1 (my aprioriProbabilities, g); for (long j = 1; j <= g; j++) { log_apriori[j] = useAprioriProbabilities ? log (my aprioriProbabilities[j]) : - logg; } // Generalized squared distance function: // D^2(x) = (x - mu)' S^-1 (x - mu) + ln (determinant(S)) - 2 ln (apriori) for (long i = 1; i <= m; i++) { SSCP winner; double norm = 0, pt_max = -1e38; long iwinner = 1; for (long k = 1; k <= p; k++) { x[k] = thy data[i][k] + displacement[k]; } for (long j = 1; j <= g; j++) { SSCP t = (SSCP) groups -> item[j]; double md = mahalanobisDistanceSq (sscpvec[j] -> data, p, x.peek(), t -> centroid, buf.peek()); double pt = log_apriori[j] - 0.5 * (ln_determinant[j] + md); if (pt > pt_max) { pt_max = pt; iwinner = j; } log_p[j] = pt; } for (long j = 1; j <= g; j++) { norm += (log_p[j] = exp (log_p[j] - pt_max)); } for (long j = 1; j <= g; j++) { his data[i][j] = log_p[j] / norm; } // Save old displacement, calculate new displacement winner = (SSCP) groups -> item[iwinner]; for (long k = 1; k <= p; k++) { adisplacements -> data[i][k] = displacement[k]; if (his data[i][iwinner] > minProb) { double delta_k = winner -> centroid[k] - x[k]; displacement[k] += alpha * delta_k; } } } *displacements = adisplacements.transfer(); return him.transfer(); } catch (MelderError) { Melder_throw ("ClassificationTable for Weenink procedure not created."); } } Configuration TableOfReal_to_Configuration_lda (TableOfReal me, long numberOfDimensions) { try { autoDiscriminant thee = TableOfReal_to_Discriminant (me); autoConfiguration him = Discriminant_and_TableOfReal_to_Configuration (thee.peek(), me, numberOfDimensions); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": Configuration with lda data not created."); } } #undef MAX #undef MIN /* End of file Discriminant.c 1043*/ sources_5316/dwtools/Sound_to_SPINET.h0000644000176700017670000000237311607123041016443 0ustar paulpaul#ifndef _Sound_to_SPINET_h_ #define _Sound_to_SPINET_h_ /* Sound_to_SPINET.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19970408 djmw 20020813 GPL header djmw 20110307 Latest modification */ #include "SPINET.h" #include "Sound_extensions.h" #ifdef __cplusplus extern "C" { #endif SPINET Sound_to_SPINET (Sound me, double timeStep, double windowDuration, double minimumFrequencyHz, double maximumFrequencyHz, long nFilters, double excitationErbProportion, double inhibitionErbProportion); #ifdef __cplusplus } #endif #endif /* _Sound_to_SPINET_h_ */ sources_5316/dwtools/SPINET_def.h0000644000176700017670000000120311627252111015401 0ustar paulpaul/* SPINET_def.h */ /* David Weenink, 6 apr 1997 */ #define ooSTRUCT SPINET oo_DEFINE_CLASS (SPINET, Sampled2) oo_LONG (gamma) /* filter order */ oo_DOUBLE (excitationErbProportion) /* excitatory bandwidth proportionality factor*/ oo_DOUBLE (inhibitionErbProportion) /* inhibitatory bandwidth proportionality factor*/ oo_DOUBLE_MATRIX (y, ny, nx) /* short term average energy spectrum */ /* spectrum after on-center/off-surround and rectification */ oo_DOUBLE_MATRIX (s, ny, nx) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (SPINET) #undef ooSTRUCT /* End of file SPINET_def.h */ sources_5316/dwtools/Sound_to_DTW.h0000664000176700017670000000223711720735750016114 0ustar paulpaul#ifndef _Sound_to_MFCC_h_ #define _Sound_to_MFCC_h_ /* Sound_to_MFCC.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010410 djmw 20020813 GPL header djmw 20110307 Latest modification */ #include "MFCC.h" #include "Sound.h" #ifdef __cplusplus extern "C" { #endif MFCC Sound_to_MFCC (Sound me, long numberOfCoefficients, double analysisWidth, double dt, double f1_mel, double fmax_mel, double df_mel); #ifdef __cplusplus } #endif #endif /* _Sound_to_MFCC_h_ */ sources_5316/dwtools/.Table_extensions.cpp.kate-swp0000644000176700017670000000024011631634470021241 0ustar paulpaulKate Swap File - Version 1.0SIP}ESIP{ESIP{ESIP$}ESI B{ESI B}ESI B{ESI B!}Esources_5316/dwtools/Categories_and_Strings.cpp0000644000176700017670000000356011606610672020553 0ustar paulpaul/* Categories_and_Strings.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020315 GPL header djmw 20110304 Thing_new */ #include "Categories_and_Strings.h" Strings Categories_to_Strings (Categories me) { try { if (my size < 1) { Melder_throw ("No elements."); } autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, my size); thy numberOfStrings = my size; for (long i = 1; i <= my size; i++) { SimpleString s = (SimpleString) my item[i]; thy strings[i] = Melder_wcsdup (s -> string); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Strings."); } } Categories Strings_to_Categories (Strings me) { try { if (my numberOfStrings < 1) { Melder_throw ("Empty strings."); } autoCategories thee = Thing_new (Categories); Categories_init (thee.peek(), my numberOfStrings); for (long i = 1; i <= my numberOfStrings; i++) { autoSimpleString s = SimpleString_create (my strings[i]); Collection_addItem (thee.peek(), s.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted."); } } /* End of file Categories_and_Strings.cpp */ sources_5316/dwtools/ClassificationTable.h0000644000176700017670000000271511627172705017507 0ustar paulpaul#ifndef _ClassificationTable_h_ #define _ClassificationTable_h_ /* ClassificationTable.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "TableOfReal.h" #include "SSCP.h" #include "Confusion.h" #include "Strings.h" Thing_define (ClassificationTable, TableOfReal) { }; ClassificationTable ClassificationTable_create (long numberOfRows, long numberOfColumns); Categories ClassificationTable_to_Categories_maximumProbability (ClassificationTable me); Strings ClassificationTable_to_Strings_maximumProbability (ClassificationTable me); Confusion ClassificationTable_to_Confusion (ClassificationTable me); /* Correlations between the classes (columns) */ Correlation ClassificationTable_to_Correlation_columns (ClassificationTable me); #endif /* _ClassificationTable_h_ */ sources_5316/dwtools/Eigen_and_SSCP.cpp0000644000176700017670000000457311606610672016641 0ustar paulpaul/* Eigen_and_SSCP.c * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020327 djmw 20020813 GPL header djmw 20040219 Eigen_and_Covariance_project added. */ #include "Eigen_and_SSCP.h" static void Eigen_and_SSCP_project_ (I, thou, Any sscp) { iam (Eigen); thouart (SSCP); SSCP him = (SSCP) sscp; for (long i = 1; i <= my numberOfEigenvalues; i++) { for (long j = i; j <= my numberOfEigenvalues; j++) { double tmp = 0; for (long k = 1; k <= my dimension; k++) { for (long m = 1; m <= my dimension; m++) { tmp += my eigenvectors[i][k] * thy data[k][m] * my eigenvectors[j][m]; } } his data[i][j] = his data[j][i] = tmp; } double tmp = 0; for (long m = 1; m <= my dimension; m++) { tmp += thy centroid[m] * my eigenvectors[i][m]; } his centroid[i] = tmp; } his numberOfObservations = SSCP_getNumberOfObservations (thee); } SSCP Eigen_and_SSCP_project (I, SSCP thee) { try { iam (Eigen); if (thy numberOfRows != my dimension) { Melder_throw ("SSCP_and_Eigen_project: dimensions don't agree."); } autoSSCP him = SSCP_create (my numberOfEigenvalues); Eigen_and_SSCP_project_ (me, thee, him.peek()); return him.transfer(); } catch (MelderError) { Melder_throw ("SSCP not projected."); } } Covariance Eigen_and_Covariance_project (I, Covariance thee) { try { iam (Eigen); if (thy numberOfRows != my dimension) { Melder_throw ("Covariance_and_Eigen_project: dimensions don't agree."); } autoCovariance him = Covariance_create (my numberOfEigenvalues); Eigen_and_SSCP_project_ (me, thee, him.peek()); return him.transfer(); } catch (MelderError) { Melder_throw ("Covariance not projected."); } } /* End of file Eigen_and_SSCP.cpp */ sources_5316/dwtools/GaussianMixture.h0000644000176700017670000001410711627237640016732 0ustar paulpaul#ifndef _GaussianMixture_h_ #define _GaussianMixture_h_ /* GaussianMixture.h * * Copyright (C) 2010-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20101021 initial version djmw 20110306 Latest modification. */ #include "ClassificationTable.h" #include "Matrix.h" #include "SSCP.h" #include "TableOfReal_extensions.h" #include "GaussianMixture_def.h" oo_CLASS_CREATE (GaussianMixture, Data); /* Constraints for a Gaussian mixture: all covariances have the same 'dimension' parameter */ GaussianMixture GaussianMixture_create (long numberOfComponents, long dimension, long storage); /* Start each function with expand and end with unExpand */ void GaussianMixture_expandPCA (GaussianMixture me); void GaussianMixture_unExpandPCA (GaussianMixture me); void GaussianMixture_drawConcentrationEllipses (GaussianMixture me, Graphics g, double scale, int confidence, wchar_t *label, int pcaDirections, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish); void GaussianMixture_and_PCA_drawConcentrationEllipses (GaussianMixture me, PCA him, Graphics g, double scale, int confidence, wchar_t *label, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish); void GaussianMixture_drawMarginalPdf (GaussianMixture me, Graphics g, long d, double xmin, double xmax, double ymin, double ymax, long npoints, long nbins, int garnish); void GaussianMixture_and_PCA_drawMarginalPdf (GaussianMixture me, PCA him, Graphics g, long d, double xmin, double xmax, double ymin, double ymax, long npoints, long nbins, int garnish); GaussianMixture TableOfReal_to_GaussianMixture_fromRowLabels (I, long storage); void GaussianMixture_initialGuess (GaussianMixture me, TableOfReal thee, double nSigmas, double ru_range); /* Give an initial guess for the centroids and covariances of the GaussianMixture based on the data in the table. Position centroids on the nSigma-ellips in the pc1-pc2 plane with some random variation and the covariances as a scaled down version of the total covariance. The randomly varied position of a centroid on the ellipse is parametrized as: x = a * (1 + randomUniform (-ru_range, ru_range)) * cos (alpha) y = b * (1 + randomUniform (-ru_range, ru_range)) * sin (alpha). where a and b are the axes of the ellipse and 0<= alpha <= 2pi. */ #define GaussianMixture_LIKELIHOOD 0 #define GaussianMixture_MML 1 #define GaussianMixture_BIC 2 #define GaussianMixture_AIC 3 #define GaussianMixture_AICC 4 #define GaussianMixture_CD_LIKELIHOOD 5 const wchar_t *GaussianMixture_criterionText (int criterion); GaussianMixture TableOfReal_to_GaussianMixture (I, long numberOfComponents, double delta_lnp, long maxNumberOfIterations, double lambda, int storage, int criterion); void GaussianMixture_and_TableOfReal_improveLikelihood (GaussianMixture me, thou, double delta_lnp, long maxNumberOfIterations, double lambda, int criterion); GaussianMixture GaussianMixture_and_TableOfReal_to_GaussianMixture_CEMM (GaussianMixture me, thou, long minNumberOfComponents, double delta_l, long maxNumberOfIterations, double lambda, int criterion); void GaussianMixture_splitComponent (GaussianMixture me, long component); ClassificationTable GaussianMixture_and_TableOfReal_to_ClassificationTable (GaussianMixture me, TableOfReal thee); TableOfReal GaussianMixture_and_TableOfReal_to_TableOfReal_BHEPNormalityTests (GaussianMixture me, thou, double h); double GaussianMixture_and_TableOfReal_getLikelihoodValue (GaussianMixture me, thou, int criterion); double GaussianMixture_getProbabilityAtPosition (GaussianMixture me, double *vector); double GaussianMixture_getProbabilityAtPosition_string (GaussianMixture me, const wchar_t *vector); double GaussianMixture_getMarginalProbabilityAtPosition (GaussianMixture me, double *vector, double x); Correlation GaussianMixture_and_TableOfReal_to_Correlation (GaussianMixture me, thou); /* Correlation between components based on the data in the table */ Covariance GaussianMixture_to_Covariance_total (GaussianMixture me); Covariance GaussianMixture_to_Covariance_between (GaussianMixture me); Covariance GaussianMixture_to_Covariance_within (GaussianMixture me); Covariance GaussianMixture_extractComponent(GaussianMixture me, long component); TableOfReal GaussianMixture_extractCentroids (GaussianMixture me); TableOfReal GaussianMixture_extractMixingProbabilities (GaussianMixture me); PCA GaussianMixture_to_PCA (GaussianMixture me); Matrix GaussianMixture_and_PCA_to_Matrix_density (GaussianMixture me, PCA pca, long d1, long d2, double xmin, double xmax, long nx, double ymin, double ymax, long ny); void GaussianMixture_and_PCA_getIntervalsAlongDirections (GaussianMixture me, PCA thee, long d1, long d2, double nsigmas, double *xmin, double *xmax, double *ymin, double *ymax); void GaussianMixture_and_PCA_getIntervalAlongDirection (GaussianMixture me, PCA thee, long d, double nsigmas, double *xmin, double *xmax); void GaussianMixture_getIntervalAlongDirection (GaussianMixture me, long d, double nsigmas, double *xmin, double *xmax); void GaussianMixture_getIntervalsAlongDirections (GaussianMixture me, long d1, long d2, double nsigmas, double *xmin, double *xmax, double *ymin, double *ymax); /* with on demand expand of pca ! */ int GaussianMixture_generateOneVector (GaussianMixture me, double *c, wchar_t **covname, double *buf); TableOfReal GaussianMixture_to_TableOfReal_randomSampling (GaussianMixture me, long numberOfPoints); #endif /* _GaussianMixture_h_ */ sources_5316/dwtools/MelFilter_and_MFCC.cpp0000644000176700017670000000721011606610672017424 0ustar paulpaul/* MelFilter_and_MFCC.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020813 GPL header djmw 20110207 Latest modification */ #include "MelFilter_and_MFCC.h" #include "NUM2.h" #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) MFCC MelFilter_to_MFCC (MelFilter me, long numberOfCoefficients) { try { long nf = my ny; double fmax_mel = my y1 + (nf - 1) * my dy; Melder_assert (numberOfCoefficients > 0); autoNUMmatrix dct (NUMcosinesTable (1, numberOfCoefficients, nf), 1, 1); autoMFCC thee = MFCC_create (my xmin, my xmax, my nx, my dx, my x1, numberOfCoefficients, my y1, fmax_mel); for (long frame = 1; frame <= my nx; frame++) { CC_Frame cf = (CC_Frame) & thy frame[frame]; CC_Frame_init (cf, numberOfCoefficients); for (long i = 1; i <= numberOfCoefficients; i++) { double p = 0; for (long j = 1; j <= nf; j++) { p += my z[j][frame] * dct[i][j]; } cf -> c[i] = p; } // c0 equals the average of the filterbank outputs. double p = 0; for (long j = 1; j <= nf; j++) { p += my z[j][frame]; } cf -> c0 = p / nf; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no MFCC created."); } } MelFilter MFCC_to_MelFilter (MFCC me, long first_cc, long last_cc, double f1_mel, double df_mel) { try { int use_c0 = 0; long nf = ( (my fmax - MAX (my fmin, f1_mel)) / df_mel + 0.5); double fmin = MAX (f1_mel - df_mel, 0), fmax = f1_mel + (nf + 1) * df_mel; if (nf < 1) Melder_throw ("MFCC_to_MelFilter: the position of the " "first filter, the distance between the filters, and, the maximum " "do not result in a positive number of filters."); // Default values if (first_cc == 0) { first_cc = 1; use_c0 = 1; } if (last_cc == 0) { last_cc = my maximumNumberOfCoefficients; } // Be strict if (last_cc < first_cc || first_cc < 1 || last_cc > my maximumNumberOfCoefficients) Melder_throw ("MFCC_to_MelFilter: coefficients must be in interval [1,", my maximumNumberOfCoefficients, "]."); autoNUMmatrix dct (NUMcosinesTable (first_cc, last_cc, nf), first_cc, 1); // TODO ?? //if ((dct = NUMcosinesTable (first_cc, last_cc, nf)) == NULL) return NULL; autoMelFilter thee = MelFilter_create (my xmin, my xmax, my nx, my dx, my x1, fmin, fmax, nf, df_mel, f1_mel); for (long frame = 1; frame <= my nx; frame++) { CC_Frame cf = (CC_Frame) & my frame[frame]; long ie = MIN (last_cc, cf -> numberOfCoefficients); for (long j = 1; j <= nf; j++) { double t = 0; for (long i = first_cc; i <= ie; i++) { t += cf -> c[i] * dct[i][j]; } // The inverse CT has a factor 1/N t /= nf; if (use_c0) { t += cf -> c0; } thy z[j][frame] = t; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no MelFilter created."); } } #undef MAX #undef MIN /* End of file MelFilter_and_MFCC.cpp */ sources_5316/dwtools/CC_def.h0000644000176700017670000000271011627172334014700 0ustar paulpaul/* CC_def.h * * Copyright (C) 1993-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT CC_Frame oo_DEFINE_STRUCT (CC_Frame) oo_LONG (numberOfCoefficients) #if oo_READING_BINARY if (localVersion == 0) { oo_FLOAT (c0) oo_FLOAT_VECTOR (c, numberOfCoefficients) } else { oo_DOUBLE (c0) oo_DOUBLE_VECTOR (c, numberOfCoefficients) } #else oo_DOUBLE (c0) oo_DOUBLE_VECTOR (c, numberOfCoefficients) #endif oo_END_STRUCT (CC_Frame) #undef ooSTRUCT #define ooSTRUCT CC oo_DEFINE_CLASS (CC, Sampled) oo_DOUBLE (fmin) oo_DOUBLE (fmax) oo_LONG (maximumNumberOfCoefficients) oo_STRUCT_VECTOR (CC_Frame, frame, nx) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (CC) #undef ooSTRUCT /* End of file CC_def.h */ sources_5316/dwtools/TextGrid_extensions.h0000644000176700017670000001256711743614533017622 0ustar paulpaul#ifndef _TextGrid_extensions_h_ #define _TextGrid_extensions_h_ /* TextGrid_extensions.h * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020516 GPL header djmw 20120418 Latest modification */ #include "TextGrid.h" TextGrid TextGrid_readFromTIMITLabelFile (MelderFile file, int phnFile); /* Read TIMIT label file with the following structure: samplenumber1 samplenumber2 label1 samplenumber3 samplenumber4 label2 ... samplenumber2n-1 samplenumber2n labeln The first tier of TextGrid will contain the TIMIT labels. If phnFile != 0, the second tier will contain the translation of the TIMIT labels into IPA labels. For the translation from sample number to time a default sampling frequency of 16000 Hz is assumed. */ Any TextGrid_TIMITLabelFileRecognizer (int nread, const char *header, MelderFile file); /* There are two types of TIMIT label files. One with phonetic labels, these files have '.phn' as file extension. The other contains word labels and has '.wrd' as extension. Since these extensions are only valid on the CDROM we can not use them for filetype recognition. Both TIMIT label files do not have a self-describing format. For filetype recognition we make use of the fact that both files are text files and always have three items on each line: two numbers followed by a string. The numbers increase in a monotone way. The recognizer only checks the first two lines and it tests whether 0 <= number[1] < number[2] <= number[3] < number[4] (A number of .wrd files do not obey the monotonocity constraint for number[4] and number[5] !) The decision whether it is a .phn or .wrd file is: .phn if string[1] == 'h#' AND string[2] is a TIMIT phonetic label .wrd if (string[1] == 'h#' AND string[2] is a valid word) OR string[1] and string[2] are both valid words. A valid word is a string with contains the lowercase characters [a-z] and [']. */ TextGrid TextGrids_merge (TextGrid grid1, TextGrid grid2); /* Merge two textGrids. The new domain will be: [min(grid1->xmin, grid2->xmin), max(grid1->xmax, grid2->xmax)]. This implies that for the resulting TextGrid each interval tier will have one or two extra intervals if the domains of the two TextGrids are not equal, */ void TextGrid_extendTime (TextGrid me, double delta_time, int position); /* Extend the begin-time (delta_time<0) or end-time (delta_time>0). For Point-tiers only the domain will be extended. Interval tiers will have a new (empty) interval at the start or the end. */ void TextGrid_setTierName (TextGrid me, long itier, const wchar_t *newName); void TextTier_changeLabels (I, long from, long to, const wchar_t *search, const wchar_t *replace, int use_regexp, long *nmatches, long *nstringmatches); void IntervalTier_changeLabels (I, long from, long to, const wchar_t *search, const wchar_t *replace, int use_regexp, long *nmatches, long *nstringmatches); void IntervalTier_removeBoundariesBetweenIdenticallyLabeledIntervals (IntervalTier me, const wchar_t *label); void IntervalTier_cutIntervalsOnLabelMatch (IntervalTier me, const wchar_t *label); void IntervalTier_cutIntervals_minimumDuration (IntervalTier me, const wchar_t *label, double minimumDuration); void TextGrid_changeLabels (TextGrid me, int tier, long from, long to, const wchar_t *search, const wchar_t *replace, int use_regexp, long *nmatches, long *nstringmatches); /* Set the start/end time to a smaller/larger value. * If mark is NULL, only times are changed * If mark != NULL mark the previous start/end time * For a TextTier this involves adding a point with the marker * For an IntervalTier this involves adding a new interval */ void IntervalTier_setLaterEndTime (IntervalTier me, double xmax, const wchar_t *mark); void IntervalTier_setEarlierStartTime (IntervalTier me, double xmin, const wchar_t *mark); void IntervalTier_moveBoundary (IntervalTier me, long interval, bool atStart, double newTime); void TextTier_setLaterEndTime (TextTier me, double xmax, const wchar_t *mark); void TextTier_setEarlierStartTime (TextTier me, double xmin, const wchar_t *mark); void TextGrid_setEarlierStartTime (TextGrid me, double xmin, const wchar_t *imark, const wchar_t *pmark); void TextGrid_setLaterEndTime (TextGrid me, double xmax, const wchar_t *imark, const wchar_t *pmark); // Precondition: if (preserveTimes) { my xmax <= thy xmin } // Postcondition: my xmin preserved void IntervalTiers_append_inline (IntervalTier me, IntervalTier thee, bool preserveTimes); void TextTiers_append_inline (TextTier me, TextTier thee, bool preserveTimes); void TextGrids_append_inline (TextGrid me, TextGrid thee, bool preserveTimes); // Postcondition: TextGrid TextGrids_to_TextGrid_appendContinuous (Collection me, bool preserveTimes); #endif /* _TextGrid_extensions_h_ */ sources_5316/dwtools/manual_HMM.cpp0000644000176700017670000006417511667466511016132 0ustar paulpaul/* manual_HMM.cpp * * Copyright (C) 2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20101009 Initial version */ #include "ManPagesM.h" void manual_HMM (ManPages me); void manual_HMM (ManPages me) { MAN_BEGIN (L"expectation-maximization", L"djmw", 20111130) NORMAL (L"Expectation-maximization (EM) is an iterative method used to find maximum " "likelihood estimates of parameters in probabilistic models, where the model depends on " "unobserved, also called %%latent%, variables. EM alternates between performing an expectation (E) step, " "which computes an expectation of the likelihood by including the latent variables as if they " "were observed, and a maximization (M) step, which computes the maximum likelihood " "estimates of the parameters by maximizing the expected likelihood found in the E step. The " "parameters found on the M step are then used to start another E step, and the process is " "repeated until some criterion is satisfied. EM is frequently used for data clustering like for example in " "@@TableOfReal: To GaussianMixture...|Gaussian mixtures@ or in the @@HMM & HMM_ObservationSequences: Learn...|Baum-Welch training@ of a Hidden Markov Model.") MAN_END MAN_BEGIN (L"GaussianMixture", L"djmw", 20101026) INTRO (L"A Gaussian mixture is a probability density function (p.d.f.). It is a combination of several Gaussian densities.") NORMAL (L"The GaussianMixture's p.d.f. is defined as the weighted sum of %K multivariate Gaussian p.d.f's:") FORMULA (L"pdf(x) = \\Si__%%i%=1_^^%K^ p__%i_ %N(%x;\\mu__%i_,\\Si__%i_),") NORMAL (L"where each %N(%x;\\mu__%i_,\\Si__%i_) is a multivariate p.d.f. with mean \\mu__%i_ and covariance matrix \\Si__%i_. The coefficients %p__%i_ sum to 1. ") NORMAL (L"For an introduction to Gaussian mixtures see for example @@Bishop (2006)@.") MAN_END MAN_BEGIN (L"GaussianMixture: Draw concentration ellipses...", L"djmw", 20101101) INTRO (L"Draws the concentration ellipse for each component in the @@GaussianMixture@. ") NORMAL (L"The principal component plane will be determined from @@GaussianMixture: To PCA@.") NORMAL (L"You might also use another @PCA and to combine it with a GaussianMixture for drawing (@@GaussianMixture & PCA: Draw concentration ellipses...@).") ENTRY (L"Settings") TAG (L"##Number of sigmas") DEFINITION (L"determines the @@concentration ellipse|data coverage@.") TAG (L"##Principal component plane") DEFINITION (L"determines whether the principal component plane is used or not for drawing.") MAN_END MAN_BEGIN (L"GaussianMixture: Get probability at position", L"djmw",20101103) INTRO (L"Evaluate the pdf of the @@GaussianMixture@ at the given position.") MAN_END MAN_BEGIN (L"GaussianMixture & PCA: Draw concentration ellipses...", L"djmw", 20101101) INTRO (L"Draws the concentration ellipse for each component in the @@GaussianMixture@ in the plane spanned by the selected @PCA.") ENTRY (L"Settings") TAG (L"##Number of sigmas") DEFINITION (L"determines the @@concentration ellipse|data coverage@.") MAN_END MAN_BEGIN (L"GaussianMixture: Draw marginal pdf...", L"djmw", 20101122) INTRO (L"A command to draw the marginal p.d.f. (probability density function) of the selected @GaussianMixture.") NORMAL (L"A marginal distribution is the projection of the (multivariate) p.d.f. on one dimension or direction. " "This direction may also be externally defined by selecting a @PCA and a GaussianMixture together.") MAN_END MAN_BEGIN (L"GaussianMixture: Split component...", L"djmw", 20101122) INTRO (L"Splits one component of the selected @GaussianMixture into two components.") NORMAL (L"The selected component is split based on a @PCA analysis of its covariance matrix. The new means are situated " "around the old components mean, 1\\si apart in the first principal components direction, and the new covariances are " "constructed with information from the old covariance matrix. ") NORMAL (L"The details of the algorith are described in @@Zhang et al. (2003)@.") MAN_END MAN_BEGIN (L"GaussianMixture: To PCA", L"djmw", 20101030) INTRO (L"Creates a @PCA from the selected @GaussianMixture.") NORMAL (L"The PCA is calculated from the @@GaussianMixture: To Covariance (total)|total covariance matrix@ of the GaussianMixture.") MAN_END MAN_BEGIN (L"GaussianMixture & PCA: To Matrix (density)...", L"djmw", 20101101) INTRO (L"Represent the @@GaussianMixture@ p.d.f. on the plane spanned by @@PCA@. This makes it possible to draw " "the p.d.f. as grey values with one of the special @@Matrix@ image drawing methods.") NORMAL (L"For each cell in the matrix of dimension %%numberOfRows% \\xx %%numberOfColumns%, the p.d.f. will be evaluated.") MAN_END MAN_BEGIN (L"GaussianMixture: To Covariance (between)", L"djmw", 20101030) INTRO (L"The covariance between the centers of the components of the @@GaussianMixture@ is calculated; " "each center is weighted according to its mixing probability.") MAN_END MAN_BEGIN (L"GaussianMixture: To Covariance (within)", L"djmw", 20101120) INTRO (L"The covariances of the components of the @@GaussianMixture@ are pooled.") MAN_END MAN_BEGIN (L"GaussianMixture: To Covariance (total)", L"djmw", 20101030) INTRO (L"The sum of the @@GaussianMixture: To Covariance (within)|within@ and @@GaussianMixture: To Covariance (between)|between@ covariances of the @@GaussianMixture@ is calculated.") MAN_END MAN_BEGIN (L"GaussianMixture: To TableOfReal (random sampling)...", L"djmw", 20101030) INTRO (L"The selected @@GaussianMixture@ is used as a generator of data.") ENTRY (L"Setting") TAG (L"##Number of data points") DEFINITION (L"determines how many random data point have to be generated.") ENTRY (L"Algorithm") NORMAL (L"For each data point to be generated:") NORMAL (L"1. A random number decides to which component in the mixture the data point will belong.") NORMAL (L"2. According to the procedure described in @@Covariance: To TableOfReal (random sampling)...@, one " "data point will be generated.") MAN_END MAN_BEGIN (L"TableOfReal: To GaussianMixture...", L"djmw", 20111130) INTRO (L"Creates a @@GaussianMixture@ from the selected @@TableOfReal@ by an @@expectation-maximization|" "expectation-maximization@ procedure.") ENTRY (L"Settings") TAG (L"##Number of components") DEFINITION (L"defines the number of Gaussians in the mixture.") TAG (L"##Tolerance of minimizer") DEFINITION (L"defines when to stop optimizing. If the relative difference between the likelihoods at two successive " "iteration steps differs by less then the tolerance we stop, i.e. when |(%L(%i-1)-%L(%i))/%L(%i)| < %%tolerance%. ") TAG (L"##Maximum number of iterations") DEFINITION (L"defines another stopping criterion. The EM iteration will stop when either the tolerance " "is reached or the maximum number of iterations. If zero is chosen, no iteration will be performed and the " "GaussianMixture will be initialized with the initial guess.") TAG (L"##Stability coefficient lambda") DEFINITION (L"defines the fraction of the total covariance that will be added to the each of the mixture " "covariance matrices during the EM iteration. This may prevent one or more of these matrices to become singular.") TAG (L"##Covariance matrices are") DEFINITION (L"defines whether the complete covariance matrices in the mixture have to be calculated or only the diagonal.") ENTRY (L"Expectation\\--Maximization Algorithm") NORMAL (L"The Expectation\\--Maximization (EM) algorithm is an iterative procedure to maximize the likelihood of the data given a model. For a " "GaussianMixture, the parameters in the model are the centers and the covariances of all components in the mixture " "and their mixing probabilities.") NORMAL (L"The number of parameters depends on the number of components in the mixture and the dimension of the data. " "For a full covariance matrix we have to find %dimension%(%dimension%+1)/2 matrix elements and another " " %dimension vector elements for its center. This makes the total number of parameters that have to be estimated " "for a mixture with ##Number of components# components equal to " "%numberOfComponents \\.c %dimension%(%dimension%+3)/2 + %numberOfComponents.") NORMAL (L"For diagonal covariance matrices the number of parameters reduces considerably.") NORMAL (L"The EM iteration has to start with a sensible initial guess for all the parameters. For the initial guess, " "we derive our centers from positions on the 1-\\si ellipse in the plane spanned by the first two principal " "components. We then make all covariance matrices equal to a scaled down version of the total covariance matrix " "where the scaling factor depends on the number of components and the quotient of the between and within variance. " "Initialy all mixing probabilities will be chosen equal.") NORMAL (L"How to proceed from the initial guess with the EM to find the optimal values for all the parameters " "in the Gaussian mixture is explained in great detail by @@Bishop (2006)@.") MAN_END #define GaussianMixture_OPTION_MENU_CRITERIA \ OPTIONMENU (L"Criterion based on", 1) \ OPTION (L"Maximum likelihood") \ OPTION (L"Minimum message length") \ OPTION (L"Bayes information") \ OPTION (L"Akaike information") \ OPTION (L"Akaike corrected") \ OPTION (L"Complete-data ML") MAN_BEGIN (L"GaussianMixture & TableOfReal: Get likelihood value...", L"djmw", 20101125) INTRO (L"Calculates how well the @GaussianMixture model fits the data according to a criterion.") ENTRY (L"Settings") TAG (L"##Maximum likelihood") FORMULA (L"ML = \\Si__%i=1..%n_ log (\\Si__%m=1..%k_ \\al__%k_ %p__%%ik%_)") TAG (L"##Minimum message length") FORMULA (L"DL = ML - 0.5(N\\.c\\Si__%m=1..%k_ log(%n\\al__%m_/12) -%k\\.clog(%n/12) -%k(%N+1))") TAG (L"##Bayes information") FORMULA (L"BIC = 2\\.cML - k\\.cN\\.clog(n)") TAG (L"##Akaike information") FORMULA (L"AIC = 2(ML - k\\.cN) ") TAG (L"##Akaike corrected") FORMULA (L"AICc = 2(ML - k\\.cN\\.cn/(n-k\\.cN-1))") TAG (L"##Complete-data ML") FORMULA (L"\\Si__%i=1..%n_\\Si__%m=1..%k_ \\ga__%%im%_ log (\\ga__%%im%_)") NORMAL (L"In the formulas above %n is the number of data points, %k is the number of mixture components, %N is the " "number of parameters in one component, i.e. %d + %d(%d+1)/2 for a full covariance matrix of " "dimension %d with means. The \\al__%k_ are the mixing probabilities, the %p__%%ik%_ are the probabilities for the %i-th data vector in the %k-th component. The \\ga__%%ik%_ are defined as ") FORMULA (L"\\ga__%%im%_= \\al__%m_\\.c%p__%%im%_ /(\\Si__%j=1..%k_ \\al__%j_\\.c%p__%%ij%_).") MAN_END MAN_BEGIN (L"GaussianMixture & TableOfReal: Improve likelihood...", L"djmw", 20111130) INTRO (L"Try to improve the likelihood of the parameters in the @@GaussianMixture@ by an @@expectation-maximization@ algorithm.") ENTRY (L"Settings & EM Algorithm") NORMAL (L"As decribed in @@TableOfReal: To GaussianMixture...@.") MAN_END MAN_BEGIN (L"GaussianMixture & TableOfReal: To Correlation (columns)", L"djmw", 20101111) INTRO (L"Create a @Correlation matrix from the selected @TableOfReal and the @GaussianMixture.") NORMAL (L"We start by calculating the ClassificationTable @@GaussianMixture & TableOfReal: To ClassificationTable|from " "the data and the GaussianMixture@.") NORMAL (L"Nex we calculate correlations between the %%columns% of the ClassificationTable: cell [%i,%j] of the " "correlation matrix will then contain the value:") FORMULA (L"%p[%i] \\.c %p[%j] / (||%p[%i]||\\.c ||%p[%j]||), ") NORMAL (L"where %p[%i] is the data in the %i-th column of the classification table and ||%p[%i]|| is its Euclidean norm. " "The index %i runs from 1 to the number of components in the mixture.") NORMAL (L"Because all the elements in a column are positive numbers, i.e. probabilities, all correlations will be positive numbers too.") MAN_END MAN_BEGIN (L"GaussianMixture & TableOfReal: To ClassificationTable", L"djmw", 20101122) INTRO (L"Create a @ClassificationTable from the selected @TableOfReal and the @GaussianMixture.") NORMAL (L"The classification table is a matrix with the same number of rows as the selected #TableOfReal " "object. The number of columns equals the number of components in the mixture. " "Cell [%i,%j] of the classification table contains the probability " "that the data in row %i of the TableOfReal belongs to component %j of the mixture.") MAN_END MAN_BEGIN (L"GaussianMixture & TableOfReal: To GaussianMixture (CEMM)...", L"djmw", 20101120) INTRO (L"Find the best @@GaussianMixture@ from the data according to a iterative component-wise optimization algorithm by which components may be deleted.") ENTRY (L"Settings") TAG (L"##Minimum number of components") DEFINITION (L"defines the minimum number of components that have to survive the minimization process. If a value of zero is chosen all components will survive and no deletions will take place.") TAG (L"##Tolerance of minimizer") DEFINITION (L"defines when to stop optimizing. If the relative difference between the likelihoods at two successive " "iteration steps differs by less then the tolerance we stop, i.e. when |(%L(%i-1)-%L(%i))/%L(%i)| < %%tolerance%. ") TAG (L"##Maximum number of iterations") DEFINITION (L"defines another stop criterion. Iteration stops whenever the number of iterations reaches this value.") TAG (L"##Stability coefficient lambda") DEFINITION (L"defines the fraction of the totat covariance that is added to the covariance of each component to " "prevent these matrices from becoming singular.") TAG (L"##Criterion based on") DEFINITION (L"defines whether the function to be optimized is the log likelihood or the related miminum description length.") ENTRY (L"Algorithm") NORMAL (L"The component-wise optimization algorithm is described in @@Figueiredo & Jain (2002)@ where the function to be optimized " "is the minimum description length defined as:") FORMULA (L"%L(\\te,%Y) = %N/2 \\Si__%m=1_^^%k^ ln(%n\\al__%k_/12) + %k/2 ln(%n/12) + %k(%N+1)/2 - ln %p(%Y|\\te),") NORMAL (L"where %k is the number of components, %N is the number of parameters of one component, " "i.e. %d+%d(%d+1)/2 for a full covariance matrix of dimension %d with means and %d+%d for a diagonal " "matrix with means; %n is the number of data vectors. The term ln %p(%Y|\\te) is the log likelihood of the data " "given the model.") NORMAL (L"For the optimization we either optimize the complete function %L(\\te,%Y) or only the likelihood ln %p(%Y|\\te) term.") MAN_END MAN_BEGIN (L"GaussianMixture & TableOfReal: To TableOfReal (BHEP normality tests)...", L"djmw", 20101113) INTRO (L"Tests the data in the @TableOfReal that belong to the components of the @GaussianMixture for normality " "according to an adapted version of the @@BHEP multivariate normality test@.") ENTRY (L"Setting") TAG (L"##Beta") DEFINITION (L"determines the smoothing parameter of the data. If %beta equals zero the smoothing is determined " "automatically for each component of the mixture separately as: ") FORMULA (L"%beta = 1/(\\Vr2) (2%p+1)^^1/(%p+4)^ n^^1/(%p+4)^,") NORMAL (L"where %n is the effective number of elements in the component and %p the dimension of the data.") MAN_END MAN_BEGIN (L"TableOfReal: To GaussianMixture (row labels)...", L"djmw", 20101101) INTRO (L"Creates a @@GaussianMixture@ from the selected @TableOfReal. The number of mixture components is determined by the number of different row labels.") ENTRY (L"Setting") TAG (L"##Covariance matrices are") DEFINITION (L"defines whether the complete covariance matrices in the mixture have to be calculated or only the diagonal.") MAN_END MAN_BEGIN (L"HMM_ObservationSequence", L"djmw", 20101010) INTRO (L"An HMM_ObservationSequence models a sequence of observations. The observation sequence can be generated " "by the @HMM or it can be used to train a model.") MAN_END MAN_BEGIN (L"HMM_StateSequence", L"djmw", 20101010) INTRO (L"An HMM_StateSequence models the sequence of states that an @HMM has traversed.") MAN_END MAN_BEGIN (L"HMM", L"djmw", 20101225) INTRO (L"A HMM is a Hidden Markov Model. Markov models are often used to model observation sequences. " "The fundamental assumption in a markov model is that the probability of an observation (event) can only " "depend on the previous observation. " "A HMM can be visualised as a graph with a number of %%states%. If states are connected they have line connecting them. The following picture shows a HMM with two states, labeled \"Rainy\" and \"Sunny\". Each state can emit three symbols (these are not visible in the graph). ") SCRIPT (5, 5, L"Create simple HMM... wheather n \"Rainy Sunny\" Walk Shop Clean\n" "Draw... no\n" "Remove\n") INTRO (L"For an introduction into HMM's see @@Rabiner (1989)@.") MAN_END MAN_BEGIN (L"HMM: Create simple HMM...", L"djmw", 20101009) INTRO (L"Creates a @@HMM|Hidden Markov Model@ from given states and observation symbols.") ENTRY (L"Settings") TAG (L"##Name") DEFINITION (L"determines the name (for the list of objects).") TAG (L"##States") DEFINITION (L"determines the number of and the names of the states.") TAG (L"##Symbols") DEFINITION (L"determines the number and the names of the observation symbols.") NORMAL (L"You can define a (not hidden) Markov model by leaving either the States or the Symbols field empty.") NORMAL (L"The model is initialised with equal probabilities for all the transitions and emissions.") MAN_END MAN_BEGIN (L"HMM: Extract transition probabilities", L"djmw", 20101020) INTRO (L"Extract the transition probabilities of the selected @@HMM@ as a @@TableOfReal@.") NORMAL (L"The row label shows the %%from% state and the column label the %%to% state, therefore the cell element " "in row %i and column %j shows the probability of making a transition from state %i to state %j.") MAN_END MAN_BEGIN (L"HMM: Extract emission probabilities", L"djmw", 20101020) INTRO (L"Extract the emission probabilities of the selected @@HMM@ as a @@TableOfReal@.") NORMAL (L"The row label shows the %%from% state and the column label the %%to% symbol, therefore the cell element " "in row %i and column %j shows the probability of emitting symbol %j from state %i.") MAN_END MAN_BEGIN (L"HMM & HMM: Get cross-entropy...", L"djmw", 20101017) INTRO (L"Calculates the cross-entropy between the two selected @@HMM@ models based on observation sequences.") ENTRY (L"Settings") TAG (L"##Observation length") DEFINITION (L"defines the number of observations that have to generated.") TAG (L"##Symmetric") DEFINITION (L"defines whether the symmetric formula is used in the calculation.") ENTRY (L"Algorithm") NORMAL (L"The cross-entropy is a measure of the distance between two models \\la__1_ and \\la__2_. It is defined as") FORMULA (L"%D(\\la__1_,\\la__2_) = 1/%N (log %p(%O__2_|\\la__1_) - log %p(%O__2_|\\la__2_)),") NORMAL (L"where %O__2_ is an observation sequence of length %N generated by model \\la__2_.") NORMAL (L"The symmetrized version is:") FORMULA (L"%D__%s_(\\la__1_,\\la__2_) = (%D(\\la__1_,\\la__2_) + %D(\\la__2_,\\la__1_))/2.") MAN_END MAN_BEGIN (L"HMM & HMM_ObservationSequence: Get cross-entropy", L"djmw", 20101017) INTRO (L"Calculates the cross-entropy between the selected @@HMM@ model and the @@HMM_ObservationSequence@.") NORMAL (L"The cross-entropy is a useful upper bound for the entropy of a model. An approximation to the cross-entropy for a model on a observation sequence %O of length %N is: ") FORMULA (L"%H(%O) = -1/%N log %p(%O),") NORMAL (L"where %p(%O) is the probability of the observation sequence given the model.") MAN_END MAN_BEGIN (L"HMM & HMM & HMM_ObservationSequence: Get cross-entropy", L"djmw", 20101017) INTRO (L"Get the (symmetric) cross-entropy for the two selected @HMM models and an observation sequence.") NORMAL (L"See @@HMM & HMM: Get cross-entropy...@.") MAN_END MAN_BEGIN (L"HMM: To HMM_ObservationSequence...", L"djmw", 20101010) INTRO (L"Use the selected @HMM as a generator for an observation sequence.") ENTRY (L"Settings") TAG (L"##Start state") DEFINITION (L"defines the state in which the HMM starts. If a zero is given the start state is randomly chosen according to the start probabilities.") TAG (L"##Number of observations") DEFINITION (L"defines the number of observations to generate. For models of %%finite% duration such as left-to-right models, the HMM generator may stop before this number is reached.") MAN_END MAN_BEGIN (L"HMM: Get transition probability...", L"djmw", 20101010) INTRO (L"For the selected @HMM get the probability to make a transition from one state to the other.") MAN_END MAN_BEGIN (L"HMM: Get emission probability...", L"djmw", 20101010) INTRO (L"For the selected @HMM get the probability that in a given state a particular symbol will be emitted.") MAN_END MAN_BEGIN (L"HMM: Get start probability...", L"djmw", 20101010) INTRO (L"For the selected @HMM get the probabilities that the model will start in a particular state.") MAN_END MAN_BEGIN (L"HMM: Get p (time, state)...", L"djmw", 20101010) INTRO (L"For the selected @HMM get the probability that after a given number of time steps the HMM will be in " "a particular state.") MAN_END MAN_BEGIN (L"HMM: Get p (time, state, symbol)...", L"djmw", 20101010) INTRO (L"For the selected @HMM get the probability that after a given number of time steps the HMM will be in " "a particular state and emits a certain symbol.") NORMAL (L"This probability is the product of the %%probability being in particular state at that time (index)% and the %%probability of emitting a certain symbol in that state%.") MAN_END MAN_BEGIN (L"HMM: Get probability staying in state...", L"djmw", 20101010) INTRO (L"For the selected @HMM get the probability that it stays exactly the given number of times in that state.") NORMAL (L"This probability is %\\al__%%ii%_^^numberOfTimes-1^(1 - %\\al__%%ii%_),\n" "where \\al__%%ii%_ is the probability of staying in state %i.") MAN_END MAN_BEGIN (L"HMM: Get expected duration in state...", L"djmw", 20101010) INTRO (L"For the selected @HMM get the number of time units that the system is expected to stay in that state.") MAN_END MAN_BEGIN (L"HMM & HMM_StateSequence: Get probability", L"djmw", 20101010) INTRO (L"Get the natural logarithm of the probability that the selected @@HMM_StateSequence|state sequence@ was generated by the selected @HMM.") MAN_END MAN_BEGIN (L"HMM & HMM_ObservationSequence: Get probability", L"djmw", 20101010) INTRO (L"Get the natural logarithm of the probability that the selected @@HMM_ObservationSequence|state sequence@ was generated by the selected @HMM.") ENTRY (L"Algorithm") NORMAL (L"Viterbi") MAN_END MAN_BEGIN (L"HMM: Set transition probabilities...", L"djmw", 20101010) INTRO (L"Sets the probabilities for making a transition from one state to all other states.") ENTRY (L"Settings") TAG (L"##Probabilities") DEFINITION (L"the list of transition probabilities from the given state. " "The values given will be scaled as probabilities. A zero is used to mark a transition that will never occur. ") ENTRY (L"Examples") NORMAL (L"For a three state model the input \"1 3 7\" will result in the same probabilities as the input \"0.1 0.3 0.7\".") MAN_END MAN_BEGIN (L"HMM: Set emission probabilities...", L"djmw", 20101010) INTRO (L"Sets the probabilities for emitting the symbols from the state.") NORMAL (L"The values given will be scaled as probabilities. ") ENTRY (L"Examples") NORMAL (L"For an HMM with four symbols the input \"1 3 3 3\" will result in the same probabilities as the input \"0.1 0.3 0.3 0.3\".") MAN_END MAN_BEGIN (L"HMM: Set start probabilities...", L"djmw", 20101010) INTRO (L"Sets the probabilities that the model starts in the particular states.") NORMAL (L"The values given will be scaled as probabilities. ") MAN_END MAN_BEGIN (L"HMM & HMM_ObservationSequence: To TableOfReal (bigrams)...", L"djmw", 20101019) INTRO (L"Get a table with bigrams and marginals form the selected @HMM_ObservationSequence and the @HMM.") NORMAL (L"The entry at row %i and column %j shows how often the %j-th symbol follows the %i-th symbol in the observation sequence.") ENTRY (L"Remark") NORMAL (L"The row and colum marginals for the first and the last element in the obsevation sequence will not be equal because there is no transition to the first and no transition from the last one.") MAN_END MAN_BEGIN (L"HMM_ObservationSequence: To TableOfReal (bigrams)...", L"djmw", 20101019) INTRO (L"Get a table with bigrams form the selected @HMM_ObservationSequence.") NORMAL (L"See also @@HMM & HMM_ObservationSequence: To TableOfReal (bigrams)...@.") MAN_END MAN_BEGIN (L"HMM & HMM_ObservationSequences: Learn...", L"djmw", 20111130) INTRO (L"Train the transition and emission probabilities of the @HMM from the observations.") ENTRY (L"Algorithm") NORMAL (L"The Baum-Welch @@expectation-maximization@ procedure. It uses the forward and backward procedures to (re)estimate the parameters until convergence is reached.") MAN_END MAN_BEGIN (L"Bishop (2006)", L"djmw", 20101026) NORMAL (L"C.M. Bishop (2006): %%Pattern recognition and machine learning%. Springer.") MAN_END MAN_BEGIN (L"Figueiredo & Jain (2002)",L"djmw", 20101229) NORMAL (L"Mario A.T. Figueiredo & Anil K. Jain (2002): \"Unsupervised learning of finite mixture models.\" " "%%IEEE Transactions on Pattern Analysis and Machine Intelligence% ##24(3)#: 381\\--396.") MAN_END MAN_BEGIN (L"Rabiner (1989)", L"djmw", 20101017) NORMAL (L"L.R. Rabiner (1989): \"A tutorial on Hidden Markov Models and selected applications in speech recognition.\" %%Proceedings of the IEEE% #77: 257\\--286.") MAN_END MAN_BEGIN (L"Tenreiro (2009)", L"djmw", 20101113) NORMAL (L"C. Tenreiro (2009): \"On the choice of the smoothing parameter for the BHEP goodness-of-fit test.\" " "%%Computational Statistics and Data Analysis% #53: 1038\\--1053.") MAN_END MAN_BEGIN (L"Zhang et al. (2003)", L"djmw", 20101122) NORMAL (L"Zhihua Zhang & Chibiao Chen & Jian Sun & Kap Luk Chan (2003): \"EM algorithms for Gaussian mixtures with " "split-and-merge operation.\" %%Pattern Recognition% #36: 1973\\--1983.") MAN_END } /* End of file manual_HMM.cpp */ sources_5316/dwtools/CCA_def.h0000644000176700017670000000241211627172621014777 0ustar paulpaul/* CCA_def.h * * Copyright (C) 1993-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020423 GPL header djmw 20031214 Added x/yLabels djmw 20060529 Added object version numbers. djmw 20080122 float -> double */ #define ooSTRUCT CCA oo_DEFINE_CLASS (CCA, Data) oo_LONG (numberOfCoefficients) oo_LONG (numberOfObservations) oo_OBJECT (Strings, 0, yLabels) oo_OBJECT (Strings, 0, xLabels) oo_OBJECT(Eigen, 0, y) oo_OBJECT(Eigen, 0, x) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (CCA) #undef ooSTRUCT /* End of file CCA_def.h */ sources_5316/dwtools/Confusion.cpp0000664000176700017670000004502411663507106016101 0ustar paulpaul/* Confusion.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010628 djmw 20020813 GPL header djmw 20061214 Changed info to Melder_writeLine format. djmw 20070620 Latest modification. djmw 20080521 +Confusion_drawAsNumbers djmw 20110304 Thing_new djmw 20111110 Use autostringvector */ #include "Confusion.h" #include "Polygon_extensions.h" #include "Matrix_extensions.h" #include "TableOfReal_extensions.h" #include "Collection_extensions.h" #include "Distributions_and_Strings.h" #include "NUM2.h" Thing_implement (Confusion, TableOfReal, 0); void structConfusion :: v_info () { double h, hx, hy, hygx, hxgy, uygx, uxgy, uxy, frac; long nCorrect; Confusion_getEntropies (this, & h, & hx, & hy, & hygx, & hxgy, & uygx, & uxgy, & uxy); Confusion_getFractionCorrect (this, & frac, & nCorrect); MelderInfo_writeLine2 (L"Number of rows: ", Melder_integer (numberOfRows)); MelderInfo_writeLine2 (L"Number of colums: ", Melder_integer (numberOfColumns)); MelderInfo_writeLine1 (L"Entropies (y is row variable):"); MelderInfo_writeLine2 (L" Total: ", Melder_double (h)); MelderInfo_writeLine2 (L" Y: ", Melder_double (hy)); MelderInfo_writeLine2 (L" X: ", Melder_double (hx)); MelderInfo_writeLine2 (L" Y given x: ", Melder_double (hygx)); MelderInfo_writeLine2 (L" X given y: ", Melder_double (hxgy)); MelderInfo_writeLine2 (L" Dependency of y on x; ", Melder_double (uygx)); MelderInfo_writeLine2 (L" Dependency of x on y: ", Melder_double (uxgy)); MelderInfo_writeLine2 (L" Symmetrical dependency: ", Melder_double (uxy)); MelderInfo_writeLine2 (L" Total number of entries: ", Melder_integer (Confusion_getNumberOfEntries (this))); MelderInfo_writeLine2 (L" Fraction correct: ", Melder_double (frac)); } Confusion Confusion_create (long numberOfStimuli, long numberOfResponses) { try { autoConfusion me = Thing_new (Confusion); TableOfReal_init (me.peek(), numberOfStimuli, numberOfResponses); return me.transfer(); } catch (MelderError) { Melder_throw ("Confusion not created."); } } Confusion Confusion_createSimple (const wchar_t *labels) { try { long numberOfLabels = Melder_countTokens (labels); if (numberOfLabels < 1) { Melder_throw ("Not enough labels."); } autoConfusion me = Confusion_create (numberOfLabels, numberOfLabels); long ilabel = 1; for (wchar_t *token = Melder_firstToken (labels); token != 0; token = Melder_nextToken ()) { for (long i = 1; i <= ilabel - 1; i++) { if (Melder_wcscmp (token, my rowLabels[i]) == 0) { Melder_throw ("Label ", i, "and ", ilabel, "may not be equal."); } } TableOfReal_setRowLabel (me.peek(), ilabel, token); TableOfReal_setColumnLabel (me.peek(), ilabel, token); ilabel++; } return me.transfer(); } catch (MelderError) { Melder_throw ("Simple Confusion not created."); } } Confusion Categories_to_Confusion (Categories me, Categories thee) { try { if (my size != thy size) { Melder_throw ("Categories_to_Confusion: dimensions do not agree."); } autoCategories ul1 = Categories_selectUniqueItems (me, 1); autoCategories ul2 = Categories_selectUniqueItems (thee, 1); autoConfusion him = Confusion_create (ul1 -> size, ul2 -> size); for (long i = 1; i <= ul1 -> size; i++) { SimpleString s = (SimpleString) ul1 -> item[i]; TableOfReal_setRowLabel (him.peek(), i, s -> string); } for (long i = 1; i <= ul2 -> size; i++) { SimpleString s = (SimpleString) ul2 -> item[i]; TableOfReal_setColumnLabel (him.peek(), i, s -> string); } for (long i = 1; i <= my size; i++) { SimpleString myi = (SimpleString) my item[i], thyi = (SimpleString) thy item[i]; Confusion_increase (him.peek(), SimpleString_c (myi), SimpleString_c (thyi)); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no Confusion created."); } } #define TINY 1.0e-30 void Confusion_getEntropies (Confusion me, double *h, double *hx, double *hy, double *hygx, double *hxgy, double *uygx, double *uxgy, double *uxy) { *h = *hx = *hy = *hxgy = *hygx = *uygx = *uxgy = *uxy = 0; autoNUMvector rowSum (1, my numberOfRows); autoNUMvector colSum (1, my numberOfColumns); double sum = 0.0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { rowSum[i] += my data[i][j]; colSum[j] += my data[i][j]; sum += my data[i][j]; } } for (long i = 1; i <= my numberOfRows; i++) { if (rowSum[i] > 0) { *hy -= rowSum[i] / sum * NUMlog2 (rowSum[i] / sum); } } for (long j = 1; j <= my numberOfColumns; j++) { if (colSum[j] > 0) { *hx -= colSum[j] / sum * NUMlog2 (colSum[j] / sum); } } for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { if (my data[i][j] > 0) { *h -= my data[i][j] / sum * NUMlog2 (my data[i][j] / sum); } } } *hygx = *h - *hx; *hxgy = *h - *hy; *uygx = (*hy - *hygx) / (*hy + TINY); *uxgy = (*hx - *hxgy) / (*hx + TINY); *uxy = 2.0 * (*hx + *hy - *h) / (*hx + *hy + TINY); } void Confusion_increase (Confusion me, const wchar_t *stim, const wchar_t *resp) { try { long stimIndex = TableOfReal_rowLabelToIndex (me, stim); if (stimIndex < 1) { Melder_throw ("Stimulus not valid."); } long respIndex = TableOfReal_columnLabelToIndex (me, resp); if (respIndex < 1) { Melder_throw ("Response not valid."); } my data[stimIndex][respIndex] += 1; } catch (MelderError) { Melder_throw (me, ": not increased."); } } double Confusion_getValue (Confusion me, const wchar_t *stim, const wchar_t *resp) { long stimIndex = TableOfReal_rowLabelToIndex (me, stim); if (stimIndex < 1) { Melder_throw ("Stimulus not valid."); } long respIndex = TableOfReal_columnLabelToIndex (me, resp); if (respIndex < 1) { Melder_throw ("Response not valid."); } return my data[stimIndex][respIndex]; } void Confusion_getFractionCorrect (Confusion me, double *fraction, long *numberOfCorrect) { *fraction = NUMundefined; *numberOfCorrect = -1; double c = 0, ct = 0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { if (my rowLabels[i] == 0 || my columnLabels[j] == 0) { return; } ct += my data[i][j]; if (wcscmp (my rowLabels[i], my columnLabels[j]) == 0) { c += my data[i][j]; } } } if (ct != 0) { *fraction = c / ct; } *numberOfCorrect = c; } /*************** Confusion_Matrix_draw ****************************************/ #define NPOINTS 6 static Polygon Polygon_createPointer () { try { double x[NPOINTS + 1] = { 0, 0, 0.9, 1, 0.9, 0, 0 }; double y[NPOINTS + 1] = { 0, 0, 0, 0.5, 1, 1, 0 }; autoPolygon me = Polygon_create (NPOINTS); for (long i = 1; i <= NPOINTS; i++) { my x[i] = x[i]; my y[i] = y[i]; } return me.transfer(); } catch (MelderError) { Melder_throw ("Polygon not created."); } } static void Polygon_drawInside (I, Graphics g) { iam (Polygon); Graphics_polyline (g, my numberOfPoints, & my x[1], & my y[1]); } void Confusion_Matrix_draw (Confusion me, Matrix thee, Graphics g, long index, double lowerPercentage, double xmin, double xmax, double ymin, double ymax, int garnish) { long ib = 1, ie = my numberOfRows; if (index > 0 && index <= my numberOfColumns) { ib = ie = index; } if (thy ny != my numberOfRows) { Melder_throw ("Wrong number of positions."); } if (xmax <= xmin) { (void) Matrix_getWindowExtrema (thee, 1, 1, 1, thy ny, &xmin, &xmax); } if (xmax <= xmin) { return; } if (ymax <= ymin) { (void) Matrix_getWindowExtrema (thee, 2, 2, 1, thy ny, &ymin, &ymax); } if (ymax <= ymin) { return; } double rmax = fabs (xmax - xmin) / 10; double rmin = rmax / 10; Graphics_setInner (g); Graphics_setWindow (g, xmin - rmax, xmax + rmax, ymin - rmax, ymax + rmax); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (long i = 1; i <= my numberOfRows; i++) { Graphics_text (g, thy z[i][1], thy z[i][2], my rowLabels[i]); } for (long i = ib; i <= ie; i++) { double xSum = 0; for (long j = 1; j <= my numberOfColumns; j++) { xSum += my data[i][j]; } if (xSum <= 0) { continue; /* no confusions */ } double x1 = thy z[i][1]; double y1 = thy z[i][2]; double r = rmax * my data[i][i] / xSum; Graphics_circle (g, x1, y1, r > rmin ? r : rmin); for (long j = 1; j <= my numberOfColumns; j++) { double x2 = thy z[j][1], y2 = thy z[j][2]; double perc = 100 * my data[i][j] / xSum; double dx = x2 - x1, dy = y2 - y1; double alpha = atan2 (dy, dx); if (perc == 0 || perc < lowerPercentage || j == i) { continue; } xmin = x1; xmax = x2; if (x2 < x1) { xmin = x2; xmax = x1; } ymin = y1; xmax = y2; if (y2 < y1) { ymin = y2; ymax = y1; } autoPolygon p = Polygon_createPointer(); double xs = sqrt (dx * dx + dy * dy) - 2.2 * r; if (xs < 0) { xs = 0; } double ys = perc * rmax / 100; Polygon_scale (p.peek(), xs, ys); Polygon_translate (p.peek(), x1, y1 - ys / 2); Polygon_rotate (p.peek(), alpha, x1, y1); Polygon_translate (p.peek(), 1.1 * r * cos (alpha), 1.1 * r * sin (alpha)); Polygon_drawInside (p.peek(), g); } } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); if (ymin * ymax < 0.0) { Graphics_markLeft (g, 0.0, 1, 1, 1, NULL); } Graphics_marksLeft (g, 2, 1, 1, 0); if (xmin * xmax < 0.0) { Graphics_markBottom (g, 0.0, 1, 1, 1, NULL); } } } Matrix Confusion_difference (Confusion me, Confusion thee) { try { /* categories must be the same too*/ if (my numberOfColumns != thy numberOfColumns || my numberOfRows != thy numberOfRows) Melder_throw ("Dimensions not equal."); autoMatrix him = Matrix_create (0.5, my numberOfColumns + 0.5, my numberOfColumns, 1, 1, 0.5, my numberOfRows + 0.5, my numberOfRows, 1, 1); for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { his z[i][j] = my data[i][j] - thy data[i][j]; } } return him.transfer(); } catch (MelderError) { Melder_throw ("Matrix not created from two Confusions."); } } long Confusion_getNumberOfEntries (Confusion me) { double total = 0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { total += my data[i][j]; } } return total; } static void create_index (wchar_t **s, long sb, long se, wchar_t **ref, long rb, long re, long *index) { for (long i = sb; i <= se; i++) { long indxj = 0; for (long j = rb; j <= re; j++) { if (wcsequ (s[i], ref[j])) { indxj = j; break; } } index[i] = indxj; } } Confusion Confusion_condense (Confusion me, const wchar_t *search, const wchar_t *replace, long maximumNumberOfReplaces, int use_regexp) { try { long nmatches, nstringmatches; if (my rowLabels == 0 || my columnLabels == 0) { Melder_throw ("No row or column labels."); } autostringvector rowLabels (strs_replace (my rowLabels, 1, my numberOfRows, search, replace, maximumNumberOfReplaces, &nmatches, &nstringmatches, use_regexp), 1, my numberOfRows); autostringvector columnLabels (strs_replace (my columnLabels, 1, my numberOfColumns, search, replace, maximumNumberOfReplaces, &nmatches, &nstringmatches, use_regexp), 1, my numberOfColumns); autoStrings srow = Thing_new (Strings); srow -> numberOfStrings = my numberOfRows; srow -> strings = rowLabels.transfer(); autoStrings scol = Thing_new (Strings); scol -> numberOfStrings = my numberOfColumns; scol -> strings = columnLabels.transfer(); /* Find dimension of new Confusion */ autoDistributions dcol = Strings_to_Distributions (scol.peek()); long nresp = dcol -> numberOfRows; autoDistributions drow = Strings_to_Distributions (srow.peek()); long nstim = drow -> numberOfRows; autoConfusion thee = Confusion_create (nstim, nresp); NUMstrings_copyElements (drow -> rowLabels, thy rowLabels, 1, nstim); NUMstrings_copyElements (dcol -> rowLabels, thy columnLabels, 1, nresp); autoNUMvector rowIndex (1, my numberOfRows); create_index (srow -> strings, 1, my numberOfRows, drow -> rowLabels, 1, nstim, rowIndex.peek()); autoNUMvector columnIndex (1, my numberOfColumns); create_index (scol -> strings, 1, my numberOfColumns, dcol -> rowLabels, 1, nresp, columnIndex.peek()); for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { thy data [rowIndex [i]][columnIndex[j]] += my data[i][j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not condensed."); } } Confusion TableOfReal_to_Confusion (I) { iam (TableOfReal); try { if (! TableOfReal_checkPositive (me)) { Melder_throw ("Elements may not be less than zero."); } autoConfusion thee = Thing_new (Confusion); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Confusion."); } } Confusion Confusion_group (Confusion me, const wchar_t *labels, const wchar_t *newLabel, long newpos) { try { autoConfusion stim = Confusion_groupStimuli (me, labels, newLabel, newpos); autoConfusion thee = Confusion_groupResponses (stim.peek(), labels, newLabel, newpos); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not grouped."); } } Confusion Confusion_groupStimuli (Confusion me, const wchar_t *labels, const wchar_t *newLabel, long newpos) { try { long ncondense = Melder_countTokens (labels); autoNUMvector irow (1, my numberOfRows); for (long i = 1; i <= my numberOfRows; i++) { irow[i] = i; } for (wchar_t *token = Melder_firstToken (labels); token != 0; token = Melder_nextToken ()) { for (long i = 1; i <= my numberOfRows; i++) { if (Melder_wcsequ (token, my rowLabels[i])) { irow[i] = 0; break; } } } long nfound = 0; for (long i = 1; i <= my numberOfRows; i++) { if (irow[i] == 0) { nfound ++; } } if (nfound == 0) { Melder_throw ("Invalid stimulus labels."); } if (nfound != ncondense) { Melder_warning (L"One or more of the given stimulus labels are suspect."); } long newnstim = my numberOfRows - nfound + 1; if (newpos < 1) { newpos = 1; } if (newpos > newnstim) { newpos = newnstim; } autoConfusion thee = Confusion_create (newnstim, my numberOfColumns); NUMstrings_copyElements (my columnLabels, thy columnLabels, 1, my numberOfColumns); TableOfReal_setRowLabel (thee.peek(), newpos, newLabel); long inewrow = 1; for (long i = 1; i <= my numberOfRows; i++) { long rowpos = newpos; if (irow[i] > 0) { if (inewrow == newpos) { inewrow++; } rowpos = inewrow; inewrow++; TableOfReal_setRowLabel (thee.peek(), rowpos, my rowLabels[i]); } for (long j = 1; j <= my numberOfColumns; j++) { thy data[rowpos][j] += my data[i][j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": stimuli not grouped."); } } Confusion Confusion_groupResponses (Confusion me, const wchar_t *labels, const wchar_t *newLabel, long newpos) { try { long ncondense = Melder_countTokens (labels); autoNUMvector icol (1, my numberOfColumns); for (long i = 1; i <= my numberOfColumns; i++) { icol[i] = i; } for (wchar_t *token = Melder_firstToken (labels); token != 0; token = Melder_nextToken ()) { for (long i = 1; i <= my numberOfColumns; i++) { if (Melder_wcsequ (token, my columnLabels[i])) { icol[i] = 0; break; } } } long nfound = 0; for (long i = 1; i <= my numberOfColumns; i++) { if (icol[i] == 0) { nfound ++; } } if (nfound == 0) { Melder_throw ("Invalid response labels."); } if (nfound != ncondense) { Melder_warning (L"One or more of the given response labels are suspect."); } long newnresp = my numberOfColumns - nfound + 1; if (newpos < 1) { newpos = 1; } if (newpos > newnresp) { newpos = newnresp; } autoConfusion thee = Confusion_create (my numberOfRows, newnresp); NUMstrings_copyElements (my rowLabels, thy rowLabels, 1, my numberOfRows); TableOfReal_setColumnLabel (thee.peek(), newpos, newLabel); long inewcol = 1; for (long i = 1; i <= my numberOfColumns; i++) { long colpos = newpos; if (icol[i] > 0) { if (inewcol == newpos) { inewcol++; } colpos = inewcol; inewcol++; TableOfReal_setColumnLabel (thee.peek(), colpos, my columnLabels[i]); } for (long j = 1; j <= my numberOfRows; j++) { thy data[j][colpos] += my data[j][i]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": responses not grouped."); } } TableOfReal Confusion_to_TableOfReal_marginals (I) { iam (Confusion); try { autoTableOfReal thee = TableOfReal_create (my numberOfRows + 1, my numberOfColumns + 1); double total = 0; for (long i = 1; i <= my numberOfRows; i++) { double rowsum = 0; for (long j = 1; j <= my numberOfColumns; j++) { thy data[i][j] = my data[i][j]; rowsum += my data[i][j]; } thy data[i][my numberOfColumns + 1] = rowsum; total += rowsum; } thy data[my numberOfRows + 1][my numberOfColumns + 1] = total; for (long j = 1; j <= my numberOfColumns; j++) { double colsum = 0; for (long i = 1; i <= my numberOfRows; i++) { colsum += my data[i][j]; } thy data[my numberOfRows + 1][j] = colsum; } NUMstrings_copyElements (my rowLabels, thy rowLabels, 1, my numberOfRows); NUMstrings_copyElements (my columnLabels, thy columnLabels, 1, my numberOfColumns); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": table with marginals not created."); } } void Confusion_drawAsNumbers (I, Graphics g, int marginals, int iformat, int precision) { iam (Confusion); TableOfReal thee = (TableOfReal) me; autoTableOfReal athee = 0; if (marginals) { athee.reset (Confusion_to_TableOfReal_marginals (me)); thee = athee.peek(); } TableOfReal_drawAsNumbers (thee, g, 1, thy numberOfRows, iformat, precision); } /* End of file Confusion.cpp */ sources_5316/dwtools/SPINET_to_Pitch.h0000644000176700017670000000220411607123040016412 0ustar paulpaul#ifndef _SPINET_to_Pitch_h_ #define _SPINET_to_Pitch_h_ /* SPINET_to_Pitch.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19970408 djmw 20020813 GPL header djmw 20110307 Latest modification */ #include "SPINET.h" #include "Pitch.h" #ifdef __cplusplus extern "C" { #endif Pitch SPINET_to_Pitch (SPINET me, double harmonicFallOffSlope, double ceiling, int maxnCandidates); #ifdef __cplusplus } #endif #endif /* _SPINET_to_Pitch_h_ */ sources_5316/dwtools/KlattTable.h0000644000176700017670000001100111630424601015604 0ustar paulpaul#ifndef _KlattTable_h_ #define _KlattTable_h_ /* KlattTable.h * * Copyright (C) 2008-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20081018 Initial version djmw 20110306 Latest modification */ #include "TableOfReal.h" #include "Sound.h" #include "Table.h" Thing_define (KlattTable, Table) { }; KlattTable KlattTable_create (double frameDuration, double totalDuration); /* f0 (08) This is the fundamental frequency (pitch) of the utterance. In this case it is specified in steps of 0.1 Hz, hence 100Hz will be represented by a value of 1000. av (08) Amplitude of voicing for the cascade branch of the synthesizer in dB0. Range 0-70, value usually 60 for a vowel sound. f1 (08) First formant frequency in 200-1300 Hz. b1 (08) Cascade branch bandwidth of first formant in the range 40-1000 Hz. f2 (08) Second formant frequency in the range 550 - 3000 Hz. b2 (08) Cascade branch bandwidth of second formant in the range 40-1000 Hz. f3 (08) Third formant frequency in the range 1200-4999 Hz. b3 (08) Cascade branch bandwidth of third formant in the range 40-1000 Hz. f4 (08) Fourth formant frequency in 1200-4999 Hz. b4 (08) Cascade branch bandwidth of fourth formant in the range 40-1000 Hz. f5 (08) Fifth formant frequency in the range 1200-4999 Hz. b5 (08) Cascade branch bandwidth of fifth formant in the range 40-1000 Hz. f6 (08) Sixth formant frequency in the range 1200-4999 Hz. b6 (08) Cascade branch bandwidth of sixth formant in the range 40-2000 Hz. fnz (08) Frequency of the nasal zero in the range 248-528 Hz. (cascade branch only) bnz (08) Bandwidth of the nasal zero in the range 40-1000 Hz (cascade branch only) fnp (08) Frequency of the nasal pole in the range 248-528 Hz bnp (08) Bandwidth of the nasal pole in the range 40-1000 Hz ah (08) Amplitude of aspiration 0-70 dB. kopen (-8) Open quotient of voicing waveform, range 0-60, usually 30. Will influence the gravelly or smooth quality of the voice. Only works with impulse and antural simulations. For the sampled glottal excitation waveform the open quotient is fixed. aturb Amplitude of turbulence 0-80 dB. A value of 40 is useful. Can be used to simulate "breathy" voice quality. tltdb (-8) Spectral tilt in dB, range 0-24. Tilts down the output spectrum. The value refers to dB down at 3Khz. Increasing the value emphasizes the low frequency content of the speech and attenuates the high frequency content. af (08) Amplitude of frication in dB, range 0-80 (parallel branch) skew Spectral Skew - skewness of alternate periods, range 0-40 a1 (08) Amplitude of first formant in the parallel branch, in 0-80 dB. b1p (-8) Bandwidth of the first formant in the parallel branch, in Hz. a2 (08) Amplitude of parallel branch second formant. b2p (-8) Bandwidth of parallel branch second formant. a3 (08) Amplitude of parallel branch third formant. b3p (-8) Bandwidth of parallel branch third formant. a4 (08) Amplitude of parallel branch fourth formant. b4p (-8) Bandwidth of parallel branch fourth formant. a5 (08) Amplitude of parallel branch fifth formant. b5p (-8) Bandwidth of parallel branch fifth formant. a6 (08) Amplitude of parallel branch sixth formant. b6p (-8) Bandwidth of parallel branch sixth formant. anp Amplitude of the parallel branch nasal formant. ab (08) Amplitude of bypass frication in dB. 0-80. avp Amplitude of voicing for the parallel branch, 0-70 dB. gain Overall gain in dB range 0-80. */ Sound KlattTable_to_Sound (KlattTable me, double samplingFrequency, int synthesisModel, int numberOfFormants, double frameDuration, int voicing, double flutter, int outputType); Sound KlattTable_and_Sound_to_Sound (KlattTable me, Sound thee); KlattTable KlattTable_createExample (); KlattTable Table_to_KlattTable (Table me); Table KlattTable_to_Table (KlattTable me); KlattTable KlattTable_readFromRawTextFile (MelderFile fs); #endif /* _KlattTable_h_ */ sources_5316/dwtools/VowelEditor.h0000664000176700017670000000506511663507106016047 0ustar paulpaul#ifndef _VowelEditor_h_ #define _VowelEditor_h_ /* VowelEditor.h * * Copyright (C) 2008-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20070130 First djmw 20110306 Latest modification. */ #include "FormantTier.h" #include "PitchTier.h" #include "TableOfReal.h" #include "Editor.h" #include "Vowel_def.h" oo_CLASS_CREATE (Vowel, Function); struct structVowelEditor_F0 { double start; double slopeOctPerSec; double minimum, maximum; double samplingFrequency, adaptFactor, adaptTime; long interpolationDepth; }; struct structVowelEditor_F1F2Grid { double df1, df2; int text_left, text_right, text_bottom, text_top; double grey; }; Thing_define (VowelEditor, Editor) { // new data: public: int soundFollowsMouse, shiftKeyPressed; double f1min, f1max, f2min, f2max; // domain of graphics F1-F2 area Matrix f3, b3, f4, b4; int frequencyScale; // 0: lin, 1: log, 2: bark, 3: mel int axisOrientation; // 0: origin topright + f1 down + f2 to left, 0: origin lb + f1 right +f2 up int marksDataset, speakerType; // 1 = male, 2 = female, 3 = child int marksFontSize; Graphics g; // the drawing short width, height; // size of drawing area in pixels Table marks; // Vowel, F1, F2, Colour... Vowel vowel; double markTraceEvery; structVowelEditor_F0 f0; double maximumDuration, extendDuration; Sound source, target; GuiObject drawingArea, playButton, reverseButton, publishButton; GuiObject f0Label, f0TextField, f0SlopeLabel, f0SlopeTextField; GuiObject durationLabel, durationTextField, extendLabel, extendTextField; GuiObject startInfo, endInfo; structVowelEditor_F1F2Grid grid; // overridden methods: void v_destroy (); void v_createChildren (); void v_createMenus (); void v_createHelpMenuItems (EditorMenu menu); }; VowelEditor VowelEditor_create (GuiObject parent, const wchar *title, Data data); void VowelEditor_prefs (); #endif /* _VowelEditor_h_ */ sources_5316/dwtools/Sound_and_FilterBank.h0000644000176700017670000000440211752213326017604 0ustar paulpaul#ifndef _Sound_and_FilterBank_h_ #define _Sound_and_FilterBank_h_ /* Sound_and_FilterBank.h * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010404 djmw 20020813 GPL header djmw 20120508 Latest modification */ #include "FilterBank.h" #include "Pitch.h" #include "Sound.h" BarkFilter Sound_to_BarkFilter (Sound me, double analysisWidth, double dt, double f1_bark, double fmax_bark, double df_bark); /* Filtering with filters on a Bark scale as defined by Andrew Sekey & Brian Hanson (1984), "Improved 1-Bark bandwidth "auditory filter", Jasa 75, 1902-1904. Although not explicitely stated the filter function is defined in the power domain. 10 log F(z) = 15.8 + 7.5(z + 0.5) - 17.5 * sqrt(1 + (z + 0.5)^2) */ MelFilter Sound_to_MelFilter (Sound me, double analysisWidth, double dt, double f1_mel, double fmax_mel, double df_mel); FormantFilter Sound_to_FormantFilter (Sound me, double analysisWidth, double dt, double f1_hz, double fmax_hz, double df_hz, double relative_bw, double minimumPitch, double maximumPitch); FormantFilter Sound_and_Pitch_to_FormantFilter (Sound me, Pitch thee, double analysisWidth, double dt, double f1_hz, double fmax_hz, double df_hz, double relative_bw); Sound FilterBanks_crossCorrelate (FilterBank me, FilterBank thee, enum kSounds_convolve_scaling scaling, enum kSounds_convolve_signalOutsideTimeDomain signalOutsideTimeDomain); Sound FilterBanks_convolve (FilterBank me, FilterBank thee, enum kSounds_convolve_scaling scaling, enum kSounds_convolve_signalOutsideTimeDomain signalOutsideTimeDomain); #endif /* _Sound_and_FilterBank_h_ */ sources_5316/dwtools/Excitations.h0000644000176700017670000000271711627237131016073 0ustar paulpaul#ifndef _Excitations_h_ #define _Excitations_h_ /* Excitations.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110306 Latest modification. */ #include "Collection.h" #include "Excitation.h" #include "Pattern.h" #include "TableOfReal.h" Thing_define (Excitations, Ordered) { }; /* Excitations is a collection of objects of the same class Excitation */ Excitations Excitations_create (long initialCapacity); Pattern Excitations_to_Pattern (Excitations me, long join); /* Precondition: my size >= 1, all items have same dimension */ TableOfReal Excitations_to_TableOfReal (Excitations me); /* Precondition: my size >= 1, all items have same dimension */ Excitation Excitations_getItem (Excitations m, long item); #endif /* _Excitations_h_ */ sources_5316/dwtools/Discriminant_Pattern_Categories.cpp0000644000176700017670000000362611606610672022424 0ustar paulpaul/* Discriminant_Pattern_Categories.cpp * * Copyright (C) 2004-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20040422 Initial version */ #include "Discriminant_Pattern_Categories.h" #include "TableOfReal.h" #include "Matrix_Categories.h" Discriminant Pattern_and_Categories_to_Discriminant (Pattern me, Categories thee) { try { autoTableOfReal t = Matrix_and_Categories_to_TableOfReal (me, thee); autoDiscriminant him = TableOfReal_to_Discriminant (t.peek()); return him.transfer(); } catch (MelderError) { Melder_throw ("Discriminant not created from Pattern & Categories."); } } Categories Discriminant_and_Pattern_to_Categories (Discriminant me, Pattern thee, int poolCovarianceMatrices, int useAprioriProbabilities) { try { autoTableOfReal t = Matrix_to_TableOfReal (thee); autoClassificationTable ct = Discriminant_and_TableOfReal_to_ClassificationTable (me, t.peek(), poolCovarianceMatrices, useAprioriProbabilities); autoCategories him = ClassificationTable_to_Categories_maximumProbability (ct.peek()); return him.transfer(); } catch (MelderError) { Melder_throw ("Categories not created from Pattern & Discriminant."); } } /* End of file Discriminant_Pattern_Categories.cpp */ sources_5316/dwtools/Sound_and_FilterBank.cpp0000644000176700017670000003335111752214063020143 0ustar paulpaul/* Sound_and_FilterBank.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010718 djmw 20020813 GPL header. djmw 20041124 Changed call to Sound_to_Spectrum. djmw 20070103 Sound interface changes djmw 20071107 Errors/warnings text changes djmw 20071202 Melder_warning */ #include "Sound_and_FilterBank.h" #include "Sound_extensions.h" #include "Sound_and_Spectrum.h" #include "Sound_to_Pitch.h" #include "Vector.h" #include "NUM2.h" #define MIN(m,n) ((m) < (n) ? (m) : (n)) // prototypes Sound FilterBank_as_Sound (FilterBank me); /* The gaussian(x) = (exp(-48*((i-(n+1)/2)/(n+1))^2)-exp(-12))/(1-exp(-12)); For power we need thearea under the square of this window: Integrate (gaussian(i)^2,i=1..n) = (sqrt(Pi)*sqrt(3)*sqrt(2)*erf(2*(n-1)*sqrt(3)*sqrt(2)/(n+1))*(n+1)+ 24*exp(-24)*(n-1)+ -4*sqrt(Pi)*sqrt(3)*exp(-12)*erf(2*(n-1)*sqrt(3)/(n+1))*(n+1))/ (24 * (-1+exp(-12))^2) To compare with the rectangular window we need to divide this by the window width (n-1) x 1^2. */ static double gaussian_window_squared_correction (long n) { double e12 = exp (-12), denum = (e12 - 1) * (e12 - 1) * 24 * (n - 1); double sqrt3 = sqrt (3), sqrt2 = sqrt (2), sqrtpi = sqrt (NUMpi); double arg1 = 2 * sqrt3 * (n - 1) / (n + 1), arg2 = arg1 * sqrt2; double p2 = sqrtpi * sqrt3 * sqrt2 * (1 - NUMerfcc (arg2)) * (n + 1); double p1 = 4 * sqrtpi * sqrt3 * e12 * (1 - NUMerfcc (arg1)) * (n + 1); return (p2 - p1 + 24 * (n - 1) * e12 * e12) / denum; } static Matrix Sound_to_spectralpower (Sound me) { try { autoSpectrum s = Sound_to_Spectrum (me, TRUE); autoMatrix thee = Matrix_create (s -> xmin, s -> xmax, s -> nx, s -> dx, s -> x1, 1, 1, 1, 1, 1); double scale = 2.0 * s -> dx / (my xmax - my xmin); // factor '2' because of positive and negative frequencies // s -> dx : width of frequncy bin // my xmax - my xmin : duration of sound double *z = thy z[1], *re = s -> z[1], *im = s -> z[2]; for (long i = 1; i <= s -> nx; i++) { z[i] = scale * (re[i] * re[i] + im[i] * im [i]); } // Frequency bins at 0 Hz and nyquist don't count for two. z[1] *= 0.5; z[s -> nx] *= 0.5; return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Matrix with spectral power created."); } } static int Sound_into_BarkFilter_frame (Sound me, BarkFilter thee, long frame) { autoMatrix pv = Sound_to_spectralpower (me); long nf = pv -> nx; autoNUMvector z (1, nf); for (long j = 1; j <= nf; j++) { z[j] = HZTOBARK (pv -> x1 + (j - 1) * pv -> dx); } for (long i = 1; i <= thy ny; i++) { double p = 0; double z0 = thy y1 + (i - 1) * thy dy; double *pow = pv -> z[1]; // TODO ?? for (long j = 1; j <= nf; j++) { // Sekey & Hanson filter is defined in the power domain. // We therefore multiply the power with a (and not a^2). // integral (F(z),z=0..25) = 1.58/9 double a = NUMsekeyhansonfilter_amplitude (z0, z[j]); p += a * pow[j] ; } thy z[i][frame] = p; } return 1; } BarkFilter Sound_to_BarkFilter (Sound me, double analysisWidth, double dt, double f1_bark, double fmax_bark, double df_bark) { try { double t1, nyquist = 0.5 / my dx, samplingFrequency = 2 * nyquist; double windowDuration = 2 * analysisWidth; /* gaussian window */ double zmax = NUMhertzToBark2 (nyquist); double fmin_bark = 0; long nt, frameErrorCount = 0; // Check defaults. if (f1_bark <= 0) { f1_bark = 1; } if (fmax_bark <= 0) { fmax_bark = zmax; } if (df_bark <= 0) { df_bark = 1; } fmax_bark = MIN (fmax_bark, zmax); long nf = floor ( (fmax_bark - f1_bark) / df_bark + 0.5); if (nf <= 0) { Melder_throw ("The combination of filter parameters is not valid."); } Sampled_shortTermAnalysis (me, windowDuration, dt, & nt, & t1); autoSound sframe = Sound_createSimple (1, windowDuration, samplingFrequency); autoSound window = Sound_createGaussian (windowDuration, samplingFrequency); autoBarkFilter thee = BarkFilter_create (my xmin, my xmax, nt, dt, t1, fmin_bark, fmax_bark, nf, df_bark, f1_bark); autoMelderProgress progess (L"BarkFilter analysis"); for (long i = 1; i <= nt; i++) { double t = Sampled_indexToX (thee.peek(), i); Sound_into_Sound (me, sframe.peek(), t - windowDuration / 2); Sounds_multiply (sframe.peek(), window.peek()); if (! Sound_into_BarkFilter_frame (sframe.peek(), thee.peek(), i)) { frameErrorCount++; } if ( (i % 10) == 1) { Melder_progress ( (double) i / nt, L"BarkFilter analysis: frame ", Melder_integer (i), L" from ", Melder_integer (nt), L"."); therror } } if (frameErrorCount > 0) { Melder_warning (L"Analysis results of ", Melder_integer (frameErrorCount), L" frame(s) out of ", Melder_integer (nt), L" will be suspect."); } double ref = FilterBank_DBREF * gaussian_window_squared_correction (window -> nx); NUMdmatrix_to_dBs (thy z, 1, thy ny, 1, thy nx, ref, FilterBank_DBFAC, FilterBank_DBFLOOR); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no BarkFilter created."); } } static int Sound_into_MelFilter_frame (Sound me, MelFilter thee, long frame) { autoMatrix pv = Sound_to_spectralpower (me); double z1 = pv -> x1; double dz = pv -> dx; long nf = pv -> nx; double df = thy dy; for (long i = 1; i <= thy ny; i++) { double p = 0; double fc_mel = thy y1 + (i - 1) * df; double fc_hz = MELTOHZ (fc_mel); double fl_hz = MELTOHZ (fc_mel - df); double fh_hz = MELTOHZ (fc_mel + df); double *pow = pv -> z[1]; for (long j = 1; j <= nf; j++) { // Filter with a triangular filter the power (=amplitude-squared) double f = z1 + (j - 1) * dz; double a = NUMtriangularfilter_amplitude (fl_hz, fc_hz, fh_hz, f); p += a * pow[j] ; } thy z[i][frame] = p; } return 1; } MelFilter Sound_to_MelFilter (Sound me, double analysisWidth, double dt, double f1_mel, double fmax_mel, double df_mel) { try { double t1, samplingFrequency = 1 / my dx, nyquist = 0.5 * samplingFrequency; double windowDuration = 2 * analysisWidth; /* gaussian window */ double fmin_mel = 0; double fbottom = HZTOMEL (100.0), fceiling = HZTOMEL (nyquist); long nt, frameErrorCount = 0; // Check defaults. if (fmax_mel <= 0 || fmax_mel > fceiling) { fmax_mel = fceiling; } if (fmax_mel <= f1_mel) { f1_mel = fbottom; fmax_mel = fceiling; } if (f1_mel <= 0) { f1_mel = fbottom; } if (df_mel <= 0) { df_mel = 100.0; } // Determine the number of filters. long nf = floor ( (fmax_mel - f1_mel) / df_mel + 0.5); fmax_mel = f1_mel + nf * df_mel; Sampled_shortTermAnalysis (me, windowDuration, dt, &nt, &t1); autoSound sframe = Sound_createSimple (1, windowDuration, samplingFrequency); autoSound window = Sound_createGaussian (windowDuration, samplingFrequency); autoMelFilter thee = MelFilter_create (my xmin, my xmax, nt, dt, t1, fmin_mel, fmax_mel, nf, df_mel, f1_mel); autoMelderProgress progress (L"MelFilters analysis"); for (long i = 1; i <= nt; i++) { double t = Sampled_indexToX (thee.peek(), i); Sound_into_Sound (me, sframe.peek(), t - windowDuration / 2); Sounds_multiply (sframe.peek(), window.peek()); if (! Sound_into_MelFilter_frame (sframe.peek(), thee.peek(), i)) { frameErrorCount++; } if ( (i % 10) == 1) { Melder_progress ( (double) i / nt, L"Frame ", Melder_integer (i), L" out of ", Melder_integer (nt), L"."); therror } } if (frameErrorCount) Melder_warning (L"Analysis results of ", Melder_integer (frameErrorCount), L" frame(s) out of ", Melder_integer (nt), L" will be suspect."); // Window correction. double ref = FilterBank_DBREF * gaussian_window_squared_correction (window -> nx); NUMdmatrix_to_dBs (thy z, 1, thy ny, 1, thy nx, ref, FilterBank_DBFAC, FilterBank_DBFLOOR); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no MelFilter created."); } } /* Analog formant filter response : H(f) = i f B / (f1^2 - f^2 + i f B) */ static int Sound_into_FormantFilter_frame (Sound me, FormantFilter thee, long frame, double bw) { Melder_assert (bw > 0); autoMatrix pv = Sound_to_spectralpower (me); double z1 = pv -> x1; double dz = pv -> dx; long nf = pv -> nx; for (long i = 1; i <= thy ny; i++) { double p = 0; double fc = thy y1 + (i - 1) * thy dy; double *pow = pv -> z[1]; for (long j = 1; j <= nf; j++) { // H(f) = ifB / (fc^2 - f^2 + ifB) // H(f)| = fB / sqrt ((fc^2 - f^2)^2 + f^2B^2) //|H(f)|^2 = f^2B^2 / ((fc^2 - f^2)^2 + f^2B^2) // = 1 / (((fc^2 - f^2) /fB)^2 + 1) double f = z1 + (j - 1) * dz; double a = NUMformantfilter_amplitude (fc, bw, f); p += a * pow[j]; } thy z[i][frame] = p; } return 1; } FormantFilter Sound_to_FormantFilter (Sound me, double analysisWidth, double dt, double f1_hz, double fmax_hz, double df_hz, double relative_bw, double minimumPitch, double maximumPitch) { try { double floor = 80, ceiling = 600; if (minimumPitch >= maximumPitch) { minimumPitch = floor; maximumPitch = ceiling; } if (minimumPitch <= 0) { minimumPitch = floor; } if (maximumPitch <= 0) { maximumPitch = ceiling; } autoPitch thee = Sound_to_Pitch (me, dt, minimumPitch, maximumPitch); autoFormantFilter ff = Sound_and_Pitch_to_FormantFilter (me, thee.peek(), analysisWidth, dt, f1_hz, fmax_hz, df_hz, relative_bw); return ff.transfer(); } catch (MelderError) { Melder_throw (me, ": no FormantFilter created."); } } FormantFilter Sound_and_Pitch_to_FormantFilter (Sound me, Pitch thee, double analysisWidth, double dt, double f1_hz, double fmax_hz, double df_hz, double relative_bw) { try { double t1, windowDuration = 2 * analysisWidth; /* gaussian window */ double nyquist = 0.5 / my dx, samplingFrequency = 2 * nyquist, fmin_hz = 0; long nt, f0_undefined = 0; if (my xmin > thy xmin || my xmax > thy xmax) Melder_throw ("The domain of the Sound is not included in the domain of the Pitch."); double f0_median = Pitch_getQuantile (thee, thy xmin, thy xmax, 0.5, kPitch_unit_HERTZ); if (f0_median == NUMundefined || f0_median == 0) { f0_median = 100; Melder_warning (L"Pitch values undefined. Bandwith fixed to 100 Hz. "); } if (f1_hz <= 0) { f1_hz = 100; } if (fmax_hz <= 0) { fmax_hz = nyquist; } if (df_hz <= 0) { df_hz = f0_median / 2; } if (relative_bw <= 0) { relative_bw = 1.1; } fmax_hz = MIN (fmax_hz, nyquist); long nf = floor ( (fmax_hz - f1_hz) / df_hz + 0.5); Sampled_shortTermAnalysis (me, windowDuration, dt, &nt, &t1); autoFormantFilter him = FormantFilter_create (my xmin, my xmax, nt, dt, t1, fmin_hz, fmax_hz, nf, df_hz, f1_hz); // Temporary objects autoSound sframe = Sound_createSimple (1, windowDuration, samplingFrequency); autoSound window = Sound_createGaussian (windowDuration, samplingFrequency); autoMelderProgress progress (L"Sound & Pitch: To FormantFilter"); for (long i = 1; i <= nt; i++) { double t = Sampled_indexToX (him.peek(), i); double b, f0 = Pitch_getValueAtTime (thee, t, kPitch_unit_HERTZ, 0); if (f0 == NUMundefined || f0 == 0) { f0_undefined++; f0 = f0_median; } b = relative_bw * f0; Sound_into_Sound (me, sframe.peek(), t - windowDuration / 2); Sounds_multiply (sframe.peek(), window.peek()); Sound_into_FormantFilter_frame (sframe.peek(), him.peek(), i, b); if ( (i % 10) == 1) { Melder_progress ( (double) i / nt, L"Frame ", Melder_integer (i), L" out of ", Melder_integer (nt), L"."); therror } } double ref = FilterBank_DBREF * gaussian_window_squared_correction (window -> nx); NUMdmatrix_to_dBs (his z, 1, his ny, 1, his nx, ref, FilterBank_DBFAC, FilterBank_DBFLOOR); return him.transfer(); } catch (MelderError) { Melder_throw ("FormantFilter not created from Pitch & FormantFilter."); } } Sound FilterBank_as_Sound (FilterBank me) { try { autoSound thee = Sound_create (my ny, my xmin, my xmax, my nx, my dx, my x1); for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) thy z[i][j] = my z[i][j]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Sound created."); } } Sound FilterBanks_crossCorrelate (FilterBank me, FilterBank thee, enum kSounds_convolve_scaling scaling, enum kSounds_convolve_signalOutsideTimeDomain signalOutsideTimeDomain) { try { autoSound cc = Sounds_crossCorrelate ((Sound) me, (Sound) thee, scaling, signalOutsideTimeDomain); return cc.transfer(); } catch (MelderError) { Melder_throw (me, " and ", thee, " not cross-correlated."); } } Sound FilterBanks_convolve (FilterBank me, FilterBank thee, enum kSounds_convolve_scaling scaling, enum kSounds_convolve_signalOutsideTimeDomain signalOutsideTimeDomain) { try { autoSound cc = Sounds_convolve ((Sound) me, (Sound) thee, scaling, signalOutsideTimeDomain); return cc.transfer(); } catch (MelderError) { Melder_throw (me, " and ", thee, " not convolved."); } } /* End of file Sound_and_FilterBank.cpp */ sources_5316/dwtools/KlattGrid_def.h0000644000176700017670000001513711627241204016300 0ustar paulpaul/* KlattGrid_def.h * * Copyright (C) 2008-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT PhonationPoint oo_DEFINE_CLASS (PhonationPoint, Data) oo_DOUBLE (time) /* AnyPoint : glottis closing time */ oo_DOUBLE (period) /* 1/F0 */ oo_DOUBLE (openPhase) oo_DOUBLE (collisionPhase) oo_DOUBLE (te) // time from glottis open to exponential decay or closing oo_DOUBLE (power1) /* flow function */ oo_DOUBLE (power2) oo_DOUBLE (pulseScale) /* multiplier for diplophonia, shimmer */ oo_END_CLASS (PhonationPoint) #undef ooSTRUCT #define ooSTRUCT PhonationTier oo_DEFINE_CLASS (PhonationTier, Function) oo_COLLECTION (SortedSetOfDouble, points, PhonationPoint, 0) oo_END_CLASS (PhonationTier) #undef ooSTRUCT #define ooSTRUCT PhonationGridPlayOptions oo_DEFINE_CLASS (PhonationGridPlayOptions, Data) oo_INT (voicing) oo_INT (aspiration) oo_INT (breathiness) oo_INT (flutter) oo_INT (doublePulsing) oo_INT (collisionPhase) oo_INT (spectralTilt) oo_INT (flowFunction) // 1: User defined with tiers (power1, power2); 2: (2,3); 3: (3,4) oo_INT (flowDerivative) oo_DOUBLE (maximumPeriod) oo_END_CLASS (PhonationGridPlayOptions) #undef ooSTRUCT #define ooSTRUCT PhonationGrid oo_DEFINE_CLASS (PhonationGrid, Function) oo_OBJECT (PitchTier, 0, pitch) oo_OBJECT (RealTier, 0, flutter) // [0,1] oo_OBJECT (IntensityTier, 0, voicingAmplitude) // dB oo_OBJECT (RealTier, 0, doublePulsing) // [0,1] oo_OBJECT (RealTier, 0, openPhase) // (0,1) oo_OBJECT (RealTier, 0, collisionPhase) // oo_OBJECT (RealTier, 0, power1) // 2,3.. oo_OBJECT (RealTier, 0, power2) // 3,4.. power2>power1 oo_OBJECT (IntensityTier, 0, spectralTilt) // dB oo_OBJECT (IntensityTier, 0, aspirationAmplitude) // dB oo_OBJECT (IntensityTier, 0, breathinessAmplitude) // dB #if !oo_READING && !oo_WRITING oo_OBJECT (PhonationGridPlayOptions, 0, options) #endif #if oo_READING options = PhonationGridPlayOptions_create (); PhonationGrid_setNames (this); #endif #if oo_DECLARING // overridden methods: public: virtual void v_info (); #endif oo_END_CLASS (PhonationGrid) #undef ooSTRUCT #define ooSTRUCT VocalTractGridPlayOptions oo_DEFINE_CLASS (VocalTractGridPlayOptions, Data) oo_INT (filterModel) oo_LONG (startOralFormant) oo_LONG (endOralFormant) oo_LONG (startNasalFormant) oo_LONG (endNasalFormant) oo_LONG (startNasalAntiFormant) oo_LONG (endNasalAntiFormant) oo_END_CLASS (VocalTractGridPlayOptions) #undef ooSTRUCT #define ooSTRUCT VocalTractGrid oo_DEFINE_CLASS (VocalTractGrid, Function) oo_OBJECT (FormantGrid, 0, oral_formants) oo_OBJECT (FormantGrid, 0, nasal_formants) oo_OBJECT (FormantGrid, 0, nasal_antiformants) // for parallel synthesis oo_COLLECTION (Ordered, oral_formants_amplitudes, IntensityTier, 0) oo_COLLECTION (Ordered, nasal_formants_amplitudes, IntensityTier, 0) #if !oo_READING && !oo_WRITING oo_OBJECT (VocalTractGridPlayOptions, 0, options) #endif #if oo_READING options = VocalTractGridPlayOptions_create (); VocalTractGrid_setNames (this); #endif #if oo_DECLARING // overridden methods: public: virtual void v_info (); #endif oo_END_CLASS (VocalTractGrid) #undef ooSTRUCT #define ooSTRUCT CouplingGridPlayOptions oo_DEFINE_CLASS (CouplingGridPlayOptions, Data) oo_LONG (startTrachealFormant) oo_LONG (endTrachealFormant) oo_LONG (startTrachealAntiFormant) oo_LONG (endTrachealAntiFormant) oo_LONG (startDeltaFormant) oo_LONG (endDeltaFormant) oo_LONG (startDeltaBandwidth) oo_LONG (endDeltaBandwidth) oo_INT (openglottis) oo_DOUBLE (fadeFraction) oo_END_CLASS (CouplingGridPlayOptions) #undef ooSTRUCT #define ooSTRUCT CouplingGrid oo_DEFINE_CLASS (CouplingGrid, Function) oo_OBJECT (FormantGrid, 0, tracheal_formants) oo_OBJECT (FormantGrid, 0, tracheal_antiformants) oo_COLLECTION (Ordered, tracheal_formants_amplitudes, IntensityTier, 0) oo_OBJECT (FormantGrid, 0, delta_formants) #if !oo_READING && !oo_WRITING oo_OBJECT (PhonationTier, 0, glottis) oo_OBJECT (CouplingGridPlayOptions, 0, options) #endif #if oo_READING options = CouplingGridPlayOptions_create (); glottis = PhonationTier_create (xmin, xmax); CouplingGrid_setNames (this); #endif #if oo_DECLARING // overridden methods: public: virtual void v_info (); #endif oo_END_CLASS (CouplingGrid) #undef ooSTRUCT #define ooSTRUCT FricationGridPlayOptions oo_DEFINE_CLASS (FricationGridPlayOptions, Data) oo_LONG (startFricationFormant) oo_LONG (endFricationFormant) oo_INT (bypass) oo_END_CLASS (FricationGridPlayOptions) #undef ooSTRUCT #define ooSTRUCT FricationGrid oo_DEFINE_CLASS (FricationGrid, Function) oo_OBJECT (IntensityTier, 0, fricationAmplitude) // dB oo_OBJECT (FormantGrid, 0, frication_formants) oo_COLLECTION (Ordered, frication_formants_amplitudes, RealTier, 0) oo_OBJECT (IntensityTier, 0, bypass) // dB #if !oo_READING && !oo_WRITING oo_OBJECT (FricationGridPlayOptions, 0, options) #endif #if oo_READING options = FricationGridPlayOptions_create (); FricationGrid_setNames (this); #endif #if oo_DECLARING // overridden methods: public: virtual void v_info (); #endif oo_END_CLASS (FricationGrid) #undef ooSTRUCT #define ooSTRUCT KlattGridPlayOptions oo_DEFINE_CLASS (KlattGridPlayOptions, Data) oo_DOUBLE (samplingFrequency) oo_INT (scalePeak) oo_DOUBLE (xmin) oo_DOUBLE (xmax) oo_END_CLASS (KlattGridPlayOptions) #undef ooSTRUCT #define ooSTRUCT KlattGrid oo_DEFINE_CLASS (KlattGrid, Function) oo_OBJECT (PhonationGrid, 0, phonation) // Glottal source oo_OBJECT (VocalTractGrid, 0, vocalTract) // Filter oo_OBJECT (CouplingGrid, 0, coupling) // Coupling between source and filter oo_OBJECT (FricationGrid, 0, frication) // Frication source oo_OBJECT (IntensityTier, 0, gain) // final scaling #if !oo_READING && !oo_WRITING oo_OBJECT (KlattGridPlayOptions, 0, options) #endif #if oo_READING options = KlattGridPlayOptions_create (); KlattGrid_setNames (this); #endif #if oo_DECLARING // overridden methods: protected: virtual void v_info (); #endif oo_END_CLASS (KlattGrid) #undef ooSTRUCT sources_5316/dwtools/Sound_to_SPINET.cpp0000644000176700017670000001101711634154427017005 0ustar paulpaul/* Sound_to_SPINET.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20070103 Sound interface changes */ #include "Sound_to_SPINET.h" #include "NUM2.h" static double fgamma (double x, long n) { double x2p1 = 1 + x * x, d = x2p1; for (long i = 2; i <= n; i++) { d *= x2p1; } return 1 / d; } /* precondition: 0 < minimumFrequencyHz < maximumFrequencyHz */ SPINET Sound_to_SPINET (Sound me, double timeStep, double windowDuration, double minimumFrequencyHz, double maximumFrequencyHz, long nFilters, double excitationErbProportion, double inhibitionErbProportion) { try { double firstTime, b = 1.02, samplingFrequency = 1 / my dx; if (timeStep < my dx) { timeStep = my dx; } if (maximumFrequencyHz > samplingFrequency / 2) { maximumFrequencyHz = samplingFrequency / 2; } long numberOfFrames; Sampled_shortTermAnalysis (me, windowDuration, timeStep, &numberOfFrames, &firstTime); autoSPINET thee = SPINET_create (my xmin, my xmax, numberOfFrames, timeStep, firstTime, minimumFrequencyHz, maximumFrequencyHz, nFilters, excitationErbProportion, inhibitionErbProportion); autoSound window = Sound_createGaussian (windowDuration, samplingFrequency); autoSound frame = Sound_createSimple (1, windowDuration, samplingFrequency); autoNUMvector f (1, nFilters); autoNUMvector bw (1, nFilters); autoNUMvector aex (1, nFilters); autoNUMvector ain (1, nFilters); // Cochlear filterbank: gammatone for (long i = 1; i <= nFilters; i++) { f[i] = NUMerbToHertz (thy y1 + (i - 1) * thy dy); bw[i] = 2 * NUMpi * b * (f[i] * (6.23e-6 * f[i] + 93.39e-3) + 28.52); } autoMelderProgress progress (L"SPINET analysis"); for (long i = 1; i <= nFilters; i++) { double bb = (f[i] / 1000) * exp (- f[i] / 1000); // outer & middle ear and phase locking double tgammaMax = (thy gamma - 1) / bw[i]; // Time where gammafunction envelope has maximum double gammaMaxAmplitude = pow ( (thy gamma - 1) / (NUMe * bw[i]), (thy gamma - 1)); // tgammaMax double timeCorrection = tgammaMax - windowDuration / 2; autoSound gammaTone = Sound_createGammaTone (0, 0.1, samplingFrequency, thy gamma, b, f[i], 0, 0, 0); autoSound filtered = Sounds_convolve (me, gammaTone.peek(), kSounds_convolve_scaling_SUM, kSounds_convolve_signalOutsideTimeDomain_ZERO); // To energy measure: weigh with broad-band transfer function for (long j = 1; j <= numberOfFrames; j++) { Sound_into_Sound (filtered.peek(), frame.peek(), Sampled_indexToX (thee.peek(), j) + timeCorrection); Sounds_multiply (frame.peek(), window.peek()); thy y[i][j] = Sound_power (frame.peek()) * bb / gammaMaxAmplitude; } Melder_progress ( (double) i / nFilters, L"SPINET: filter ", Melder_integer (i), L" from ", Melder_integer (nFilters), L"."); therror } // Excitatory and inhibitory area functions for (long i = 1; i <= nFilters; i++) { for (long k = 1; k <= nFilters; k++) { double fr = (f[k] - f[i]) / bw[i]; aex[i] += fgamma (fr / thy excitationErbProportion, thy gamma); ain[i] += fgamma (fr / thy inhibitionErbProportion, thy gamma); } } // On-center off-surround interactions for (long j = 1; j <= numberOfFrames; j++) for (long i = 1; i <= nFilters; i++) { double a = 0; for (long k = 1; k <= nFilters; k++) { double fr = (f[k] - f[i]) / bw[i]; double hexsq = fgamma (fr / thy excitationErbProportion, thy gamma); double hinsq = fgamma (fr / thy inhibitionErbProportion, thy gamma); a += thy y[k][j] * (hexsq / aex[i] - hinsq / ain[i]); } thy s[i][j] = a > 0 ? a : 0; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no SPINET created."); } } /* End of file Sound_to_SPINET.cpp */ sources_5316/dwtools/SpeechSynthesizer.cpp0000664000176700017670000004302611747467563017634 0ustar paulpaul/* SpeechSynthesizer.cpp * * Copyright (C) 2011-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20111214 */ #include "SpeechSynthesizer.h" #include "speech.h" #include "speak_lib.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" #define espeak_SAMPLINGFREQUENCY 22050 extern structMelderDir praatDir; extern int option_phoneme_events; Thing_implement (SpeechSynthesizer, Data, 0); void structSpeechSynthesizer :: v_destroy () { Melder_free (d_voiceName); Melder_free (d_voiceVariantName); NUMvector_free (d_wav, 1); Melder_free (d_punctuations); SpeechSynthesizer_Parent :: v_destroy (); } void structSpeechSynthesizer :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Voice name: ", d_voiceName); MelderInfo_writeLine2 (L"Voice variant: ", d_voiceVariantName); MelderInfo_writeLine2 (L"Input text format: ", (d_inputTextFormat == SpeechSynthesizer_INPUT_TEXTONLY ? L"text only" : d_inputTextFormat == SpeechSynthesizer_INPUT_PHONEMESONLY ? L"phonemes only" : L"tagged text")); MelderInfo_writeLine2 (L"Input phoneme coding: ", (d_inputPhonemeCoding == SpeechSynthesizer_PHONEMECODINGS_KIRSHENBAUM ? L"Kirshenbaum" : L"???")); MelderInfo_writeLine3 (L"Sampling frequency: ", Melder_double (d_samplingFrequency), L" Hz"); MelderInfo_writeLine3 (L"Word gap: ", Melder_double (d_wordgap), L" s"); MelderInfo_writeLine3 (L"Pitch adjustment value: ", Melder_integer (d_pitchAdjustment), L" (0-100)"); MelderInfo_writeLine4 (L"Speeking rate: ", Melder_integer (d_wordsPerMinute), L" words per minute", (d_estimateWordsPerMinute ? L" (but estimated from data if possible)" : L" (fixed)")); MelderInfo_writeLine2 (L"Output phoneme coding: ", (d_inputPhonemeCoding == SpeechSynthesizer_PHONEMECODINGS_KIRSHENBAUM ? L"Kirshenbaum" : d_inputPhonemeCoding == SpeechSynthesizer_PHONEMECODINGS_IPA ? L"IPA" : L"???")); } static void NUMvector_extendNumberOfElements (long elementSize, void **v, long lo, long *hi, long extraDemand) { try { char *result; if (*v == NULL) { long newhi = lo + extraDemand - 1; result = reinterpret_cast (NUMvector (elementSize, lo, newhi)); *hi = newhi; } else { long offset = lo * elementSize; for (;;) { // not very infinite: 99.999 % of the time once, 0.001 % twice result = reinterpret_cast (Melder_realloc ((char *) *v + offset, (*hi - lo + 1 + extraDemand) * elementSize)); if ((result -= offset) != NULL) break; // this will normally succeed at the first try (void) Melder_realloc_f (result + offset, 1); // ??make "sure" that the second try will succeed } (*hi) += extraDemand; memset (result + *hi * elementSize, 0, elementSize); // initialize the new elements to zeroes } *v = result; } catch (MelderError) { Melder_throw ("Vector: size not extended."); } } static void NUMvector_supplyStorage (long elementSize, void **v, long lo, long *hi, long nfilled, long extraDemand) { long old_capacity = *hi - lo + 1, new_capacity = nfilled + extraDemand; if (new_capacity < old_capacity) return; new_capacity = new_capacity > 2 * old_capacity ? new_capacity : 2 * old_capacity; NUMvector_extendNumberOfElements (elementSize, v, lo, hi, new_capacity); } template void NUMvector_supplyStorage (T** v, long lo, long *hi, long nfilled, long extraDemand) { NUMvector_supplyStorage (sizeof (T), (void**) v, lo, hi, nfilled, extraDemand); } static int synthCallback (short *wav, int numsamples, espeak_EVENT *events) { char phoneme_name[9]; if (wav == 0) return 1; // It is essential that the SpeechSynthesizer is identified here by the user_data, // because the espeakEVENT_LIST_TERMINATED event may still be accompanied by // a piece of audio data!! SpeechSynthesizer me = (SpeechSynthesizer) (events -> user_data); while(events -> type != espeakEVENT_LIST_TERMINATED) { if (events -> type == espeakEVENT_SAMPLERATE) { my d_internalSamplingFrequency = events -> id.number; } else { //my events = Table "time type type-t t-pos length a-pos sample id uniq"; // 1 2 3 4 5 6 7 8 9 Table_appendRow (my d_events); long irow = my d_events -> rows -> size; double time = events -> audio_position * 0.001; Table_setNumericValue (my d_events, irow, 1, time); Table_setNumericValue (my d_events, irow, 2, events -> type); // Column 3 will be filled afterwards Table_setNumericValue (my d_events, irow, 4, events -> text_position); Table_setNumericValue (my d_events, irow, 5, events -> length); Table_setNumericValue (my d_events, irow, 6, events -> audio_position); Table_setNumericValue (my d_events, irow, 7, events -> sample); if (events -> type == espeakEVENT_MARK || events -> type == espeakEVENT_PLAY) { Table_setStringValue (my d_events, irow, 8, Melder_peekUtf8ToWcs (events -> id.name)); } else { // Ugly hack because id.string in not 0-terminated if 8 chars long! memcpy (phoneme_name, events -> id.string, 8); phoneme_name[8] = 0; Table_setStringValue (my d_events, irow, 8, Melder_peekUtf8ToWcs (phoneme_name)); } Table_setNumericValue (my d_events, irow, 9, events -> unique_identifier); } events++; } if (me != 0) { NUMvector_supplyStorage (&my d_wav, 1, &my d_wavCapacity, my d_numberOfSamples, numsamples); for (long i = 1; i <= numsamples; i++) { my d_wav[my d_numberOfSamples + i] = wav[i - 1]; } my d_numberOfSamples += numsamples; } return 0; } static void SpeechSynthesizer_setDefaults (SpeechSynthesizer me) { SpeechSynthesizer_setTextInputSettings (me, SpeechSynthesizer_INPUT_TEXTONLY, SpeechSynthesizer_PHONEMECODINGS_KIRSHENBAUM); SpeechSynthesizer_setSpeechOutputSettings (me, 44100, 0.01, 50, 50, 175, true, SpeechSynthesizer_PHONEMECODINGS_IPA); } SpeechSynthesizer SpeechSynthesizer_create (long voiceIndex, long voiceVariantIndex) { try { autoSpeechSynthesizer me = Thing_new (SpeechSynthesizer); my d_voice = voiceIndex; my d_voiceVariant = voiceVariantIndex; FileInMemory fim = (FileInMemory) espeakdata_voices -> item[voiceIndex]; my d_voiceName = Melder_wcsdup (fim -> d_id); if (voiceVariantIndex != 1) { // 1 is default, i.e. no variant voiceVariantIndex--; // !!! FileInMemory vfim = (FileInMemory) espeakdata_variants -> item[voiceVariantIndex]; my d_voiceVariantName = Melder_wcsdup (vfim -> d_id); } else { my d_voiceVariantName = Melder_wcsdup (L"default"); // TODO what is the default? } my d_wavCapacity = 2 * 22050; // 2 seconds my d_wav = NUMvector (1, my d_wavCapacity); SpeechSynthesizer_setDefaults (me.peek()); int fsamp = espeak_Initialize (AUDIO_OUTPUT_SYNCHRONOUS, 0, NULL, espeakINITIALIZE_PHONEME_EVENTS); // 4000 ms if (fsamp == -1) Melder_throw ("Internal espeak error."); return me.transfer(); } catch (MelderError) { Melder_throw ("SpeechSynthesizer not created."); } } void SpeechSynthesizer_setTextInputSettings (SpeechSynthesizer me, int inputTextFormat, int inputPhonemeCoding) { my d_inputTextFormat = inputTextFormat; my d_inputPhonemeCoding = inputPhonemeCoding; } void SpeechSynthesizer_setSpeechOutputSettings (SpeechSynthesizer me, double samplingFrequency, double wordgap, long pitchAdjustment, long pitchRange, long wordsPerMinute, bool estimateWordsPerMinute, int outputPhonemeCoding) { my d_samplingFrequency = samplingFrequency; my d_wordgap = wordgap; my d_pitchAdjustment = pitchAdjustment; my d_pitchRange = pitchRange; if (wordsPerMinute <= 0) wordsPerMinute = 175; if (wordsPerMinute > 450) wordsPerMinute = 450; if (wordsPerMinute < 80) wordsPerMinute = 80; my d_wordsPerMinute = wordsPerMinute; my d_estimateWordsPerMinute = estimateWordsPerMinute; my d_outputPhonemeCoding = outputPhonemeCoding; } void SpeechSynthesizer_playText (SpeechSynthesizer me, const wchar_t *text) { autoSound thee= SpeechSynthesizer_to_Sound (me, text, 0, 0); Sound_playPart (thee.peek(), thy xmin, thy xmax, 0, 0); } static Sound buffer_to_Sound (short *wav, long numberOfSamples, double samplingFrequency) { try { double dx = 1.0 / samplingFrequency; double xmax = numberOfSamples * dx; autoSound thee = Sound_create (1, 0, xmax, numberOfSamples, dx, dx / 2); for (long i = 1; i <= numberOfSamples; i++) { thy z[1][i] = wav[i] / 32768.0; } return thee.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from synthesizer data."); } } static void IntervalTier_addBoundaryUnsorted (IntervalTier me, long iinterval, double time, const wchar_t *newLabel, bool isNewleftLabel) { if (time <= my xmin || time >= my xmax) { Melder_throw ("Time is outside interval."); } // Find interval to split if (iinterval <= 0) { iinterval = IntervalTier_timeToLowIndex (me, time); } // Modify end time of left label TextInterval ti = (TextInterval) my intervals -> item[iinterval]; ti -> xmax = time; if (isNewleftLabel) TextInterval_setText (ti, newLabel); autoTextInterval ti_new = TextInterval_create (time, my xmax, (! isNewleftLabel ? newLabel : L"")); Sorted_addItem_unsorted (my intervals, ti_new.transfer()); } static void Table_setEventTypeString (Table me) { try { for (long i = 1; i <= my rows -> size; i++) { int type = Table_getNumericValue_Assert (me, i, 2); const wchar_t *label = L"0"; if (type == espeakEVENT_WORD) { label = L"word"; } else if (type == espeakEVENT_SENTENCE) { label = L"sent"; } else if (type == espeakEVENT_MARK) { label = L"mark"; } else if (type == espeakEVENT_PLAY) { label = L"play"; } else if (type == espeakEVENT_END) { label = L"s-end"; } else if (type == espeakEVENT_MSG_TERMINATED) { label = L"msg_term"; } else if (type == espeakEVENT_PHONEME) { label = L"phoneme"; } Table_setStringValue (me, i, 3, label); } } catch (MelderError) { Melder_throw ("Event types not set."); } } static TextGrid Table_to_TextGrid (Table me, const wchar_t *text, double xmin, double xmax) { //Table_createWithColumnNames (0, L"time type type-t t-pos length a-pos sample id uniq"); try { long length, textLength = wcslen (text); long numberOfRows = my rows -> size; long timeColumnIndex = Table_getColumnIndexFromColumnLabel (me, L"time"); long typeColumnIndex = Table_getColumnIndexFromColumnLabel (me, L"type"); long tposColumnIndex = Table_getColumnIndexFromColumnLabel (me, L"t-pos"); long idColumnIndex = Table_getColumnIndexFromColumnLabel (me, L"id"); autoTextGrid thee = TextGrid_create (xmin, xmax, L"sentence clause word phoneme", L""); TextGrid_setIntervalText (thee.peek(), 1, 1, text); long p1c = 1, p1w = 1; double t1p = xmin; bool wordEnd = false; autoMelderString mark; IntervalTier itc = (IntervalTier) thy tiers -> item[2]; IntervalTier itw = (IntervalTier) thy tiers -> item[3]; IntervalTier itp = (IntervalTier) thy tiers -> item[4]; for (long i = 1; i <= numberOfRows; i++) { double time = Table_getNumericValue_Assert (me, i, timeColumnIndex); int type = Table_getNumericValue_Assert (me, i, typeColumnIndex); long pos = Table_getNumericValue_Assert (me, i, tposColumnIndex); if (type == espeakEVENT_SENTENCE) { // Only insert a new boundary, no text // text will be inserted at end sentence event if (time > xmin and time < xmax) { IntervalTier_addBoundaryUnsorted (itc, itc -> intervals -> size, time, L"", true); } p1c = pos; } else if (type == espeakEVENT_END) { // End of clause: insert new boundary, and fill left interval with text length = pos - p1c + 1; MelderString_ncopy (&mark, text + p1c - 1, length); if (time > xmin and time < xmax) { IntervalTier_addBoundaryUnsorted (itc, itc -> intervals -> size, time, mark.string, true); } else { TextGrid_setIntervalText (thee.peek(), 2, itc -> intervals -> size, mark.string); } MelderString_empty (&mark); p1c = pos; // End of clause always signals "end of a word" if (pos <= textLength) { length = pos - p1w + 1; MelderString_ncopy (&mark, text + p1w - 1, length); if (time > xmin and time < xmax) { IntervalTier_addBoundaryUnsorted (itw, itw -> intervals -> size, time, mark.string, true); } else { TextGrid_setIntervalText (thee.peek(), 3, itw -> intervals -> size, mark.string); } MelderString_empty (&mark); // now the next word event should not trigger setting the left interval text wordEnd = false; } } else if (type == espeakEVENT_WORD) { if (pos < p1w) continue; if (time > xmin and time < xmax) { length = pos - p1w; if (pos == textLength) length++; MelderString_ncopy (&mark, text + p1w - 1, length); IntervalTier_addBoundaryUnsorted (itw, itw -> intervals -> size, time, (wordEnd ? mark.string : L""), true); MelderString_empty (&mark); } wordEnd = true; p1w = pos; } else if (type == espeakEVENT_PHONEME) { const wchar_t *id = Table_getStringValue_Assert (me, i, idColumnIndex); if (time > t1p) { // Insert new boudary and label interval with the id // TODO: Translate the id to the correct notation TextInterval ti = (TextInterval) itp -> intervals -> item[itp -> intervals -> size]; if (time > ti -> xmin and time < ti -> xmax) { IntervalTier_addBoundaryUnsorted (itp, itp -> intervals -> size, time, id, false); } } else { // Just in case the phoneme starts at xmin we only need to set interval text TextGrid_setIntervalText (thee.peek(), 4, itp -> intervals -> size, id); } t1p = time; } } Sorted_sort (itc -> intervals); Sorted_sort (itw -> intervals); Sorted_sort (itp -> intervals); return thee.transfer(); } catch (MelderError) { Melder_throw ("TextGrid not created from Table with events."); } } static void espeakdata_SetVoiceByName (const char *name, const char *variantName) { espeak_VOICE voice_selector; // autoMelderString voice; // MelderString_append (&voice, Melder_peekUtf8ToWcs (name), L"+", Melder_peekUtf8ToWcs (variantName)); memset(&voice_selector, 0, sizeof(voice_selector)); MelderString npv = { 0 }; MelderString_append (&npv, Melder_peekUtf8ToWcs (name), L"+", Melder_peekUtf8ToWcs (variantName)); voice_selector.name = (char *) Melder_peekWcsToUtf8 (npv.string); // include variant name in voice stack ?? // voice_selector.name = (char *) name; // include variant name in voice stack ?? if (LoadVoice (name,1) != NULL) { LoadVoice(variantName, 2); DoVoiceChange(voice); SetVoiceStack (&voice_selector, variantName); } } Sound SpeechSynthesizer_to_Sound (SpeechSynthesizer me, const wchar_t *text, TextGrid *tg, Table *events) { try { int fsamp = espeak_Initialize (AUDIO_OUTPUT_SYNCHRONOUS, 0, NULL, // 5000ms espeakINITIALIZE_PHONEME_EVENTS|espeakINITIALIZE_PHONEME_IPA); if (fsamp == -1) Melder_throw ("Internal espeak error."); int synth_flags = espeakCHARS_WCHAR; if (my d_inputTextFormat == SpeechSynthesizer_INPUT_TAGGEDTEXT) synth_flags |= espeakSSML; if (my d_inputTextFormat != SpeechSynthesizer_INPUT_TEXTONLY) synth_flags |= espeakPHONEMES; option_phoneme_events = espeakINITIALIZE_PHONEME_EVENTS; // extern int option_phoneme_events; if (my d_outputPhonemeCoding == SpeechSynthesizer_PHONEMECODINGS_IPA) { option_phoneme_events |= espeakINITIALIZE_PHONEME_IPA; } espeak_SetSynthCallback (synthCallback); espeak_SetParameter (espeakRATE, my d_wordsPerMinute, 0); espeak_SetParameter (espeakPITCH, my d_pitchAdjustment, 0); espeak_SetParameter (espeakRANGE, my d_pitchRange, 0); espeakdata_SetVoiceByName ((const char *) Melder_peekWcsToUtf8 (my d_voiceName), (const char *) Melder_peekWcsToUtf8 (my d_voiceVariantName)); espeak_SetParameter (espeakWORDGAP, my d_wordgap * 100, 0); // espeak wordgap is in units of 10 ms espeak_SetParameter (espeakCAPITALS, 0, 0); espeak_SetParameter (espeakPUNCTUATION, espeakPUNCT_NONE, 0); my d_events = Table_createWithColumnNames (0, L"time type type-t t-pos length a-pos sample id uniq"); long textLength = wcslen (text); espeak_Synth (text, textLength + 1, 0, POS_CHARACTER, 0, synth_flags, NULL, me); espeak_Terminate (); autoSound thee = buffer_to_Sound (my d_wav, my d_numberOfSamples, my d_internalSamplingFrequency); if (my d_samplingFrequency != my d_internalSamplingFrequency) { thee.reset (Sound_resample (thee.peek(), my d_samplingFrequency, 50)); } my d_numberOfSamples = 0; // re-use the wav-buffer if (tg != NULL) { double xmin = Table_getNumericValue_Assert (my d_events, 1, 1); if (xmin > thy xmin) xmin = thy xmin; double xmax = Table_getNumericValue_Assert (my d_events, my d_events -> rows -> size, 1); if (xmax < thy xmax) xmax = thy xmax; autoTextGrid atg1 = Table_to_TextGrid (my d_events, text, xmin, xmax); autoTextGrid atg2 = TextGrid_extractPart (atg1.peek(), thy xmin, thy xmax, 0); *tg = atg2.transfer(); } if (events != NULL) { Table_setEventTypeString (my d_events); *events = my d_events; my d_events = 0; } forget (my d_events); return thee.transfer(); } catch (MelderError) { espeak_Terminate (); Melder_throw ("Text not played."); } } /* End of file SpeechSynthesizer.cpp */sources_5316/dwtools/Matrix_Categories.cpp0000644000176700017670000000312011606610672017534 0ustar paulpaul/* Matrix_Categories.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header */ #include "Matrix_Categories.h" #include "TableOfReal_extensions.h" TableOfReal Matrix_and_Categories_to_TableOfReal (I, Categories thee) { try { iam (Matrix); if (thy size != my ny) { Melder_throw ("Number of rows and number of categories must be equal."); } autoTableOfReal him = TableOfReal_create (my ny, my nx); TableOfReal_setSequentialColumnLabels (him.peek(), 0, 0, NULL, 1, 1); for (long i = 1; i <= my ny; i++) { his rowLabels[i] = Melder_wcsdup (OrderedOfString_itemAtIndex_c (thee, i)); } for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) { his data[i][j] = my z[i][j]; } } return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal not created from Matrix & Categories."); } } /* End of file Matrix_Categories.cpp */ sources_5316/dwtools/.SpeechSynthesizer.cpp.kate-swp0000664000176700017670000000046011712450541021413 0ustar paulpaulKate Swap File - Version 1.0SI“/,ESI“0 ESI“1iESI“2.ESI“3eESI“4.ESI“5 ESI“6nESI“7oESI“8 ESI“9vESI“:aESI“;rESI“<iESI“=aESI“>nESI“?tEsources_5316/dwtools/praat_MDS_init.cpp0000644000176700017670000023011411725114062016757 0ustar paulpaul/* praat_MDS_init.cpp * * Copyright (C) 1992-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020408 GPL djmw 20020408 Added MDS-tutorial djmw 20020603 Changes due to TableOfReal dynamic menu changes. djmw 20040415 Forms texts. djmw 20040513 More forms text changes djmw 20041027 Orhogonal transform parameter for Configurations_to_Procrustes djmw 20050406 classProcrustus -> classProcrustes. djmw 20050426 Removed "Procrustus.h" djmw 20050630 Better name of Procrustes object after Configurations_to_Procrustes. djmw 20061218 Introduction of Melder_information<12...9> djmw 20070902 Melder_new<1...> djmw 20071011 REQUIRE requires L"". djmw 20090818 Thing_recognizeClassesByName: added classAffineTransform, classScalarProduct, classWeight */ #include #include "NUM2.h" #include "praat.h" #include "MDS.h" #include "ContingencyTable.h" #include "TableOfReal_extensions.h" #include "Configuration_and_Procrustes.h" #include "Configuration_AffineTransform.h" #include "Confusion.h" #include "Formula.h" void praat_TableOfReal_init (ClassInfo klas); void praat_TableOfReal_init2 (ClassInfo klas); static const wchar_t *QUERY_BUTTON = L"Query -"; static const wchar_t *DRAW_BUTTON = L"Draw -"; static const wchar_t *ANALYSE_BUTTON = L"Analyse -"; static const wchar_t *CONFIGURATION_BUTTON = L"To Configuration -"; /* Tests */ /* Sort row 1 ascending and store in row 3 Sort row 1 and move row 2 along and store in rows 4 and 5 respectively Make an index for row 1 and store in row 6 */ static void TabelOfReal_testSorting (I, long rowtoindex) { iam (TableOfReal); try { long nc = my numberOfColumns; autoNUMvector index (1, nc); if (my numberOfRows < 6) { Melder_throw ("TabelOfReal_sort2: we want at least 6 rows!!"); } if (rowtoindex < 1 || rowtoindex > 2) { Melder_throw ("TabelOfReal_sort2: rowtoindex <= 2"); } // Copy 1->3 and sort 3 inplace NUMvector_copyElements (my data[1], my data[3], 1, nc); NUMsort_d (nc, my data[3]); // Copy 1->4 and 2->5, sort 4+5 in parallel NUMvector_copyElements (my data[1], my data[4], 1, nc); NUMvector_copyElements (my data[2], my data[5], 1, nc); NUMsort2 (nc, my data[4], my data[5]); NUMindexx (my data[rowtoindex], nc, index.peek()); for (long i = 1; i <= nc; i++) { my data[6][i] = index[i]; } } catch (MelderError) { Melder_throw (me, ": sorting test not ok."); } } #undef iam #define iam iam_LOOP FORM (TabelOfReal_testSorting, L"TabelOfReal: Sort and index", L"") NATURAL (L"Row to index", L"1") OK DO LOOP { iam (TableOfReal); TabelOfReal_testSorting (me, GET_INTEGER (L"Row to index")); } END /************************* examples ***************************************/ FORM (Dissimilarity_createLetterRExample, L"Create letter R example", L"Create letter R example...") LABEL (L"", L"For the monotone transformation on the distances") REAL (L"Noise range", L"32.5") OK DO praat_new (Dissimilarity_createLetterRExample (GET_REAL (L"Noise range")), 0); END FORM (INDSCAL_createCarrollWishExample, L"Create INDSCAL Carroll & Wish example...", L"Create INDSCAL Carroll & Wish example...") REAL (L"Noise standard deviation", L"0.0") OK DO praat_new (INDSCAL_createCarrollWishExample (GET_REAL (L"Noise standard deviation")), 0); END FORM (Configuration_create, L"Create Configuration", L"Create Configuration...") WORD (L"Name", L"uniform") NATURAL (L"Number of points", L"10") NATURAL (L"Number of dimensions", L"2") LABEL (L"", L"Formula:") TEXTFIELD (L"formula", L"randomUniform(-1.5, 1.5)") OK DO autoConfiguration me = Configuration_create (GET_INTEGER (L"Number of points"), GET_INTEGER (L"Number of dimensions")); TableOfReal_formula (me.peek(), GET_STRING (L"formula"), interpreter, 0); praat_new (me.transfer(), GET_STRING (L"Name")); END FORM (drawSplines, L"Draw splines", L"spline") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"1.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"20.0") RADIO (L"Spline type", 1) RADIOBUTTON (L"M-spline") RADIOBUTTON (L"I-spline") INTEGER (L"Order", L"3") SENTENCE (L"Interior knots", L"0.3 0.5 0.6") BOOLEAN (L"Garnish", 1) OK DO double xmin = GET_REAL (L"left Horizontal range"), xmax = GET_REAL (L"right Horizontal range"); double ymin = GET_REAL (L"left Vertical range"), ymax = GET_REAL (L"right Vertical range"); if (xmax <= xmin or ymax <= ymin) { Melder_throw ("Required: xmin < xmax and ymin < ymax."); } autoPraatPicture picture; drawSplines (GRAPHICS, xmin, xmax, ymin, ymax, GET_INTEGER (L"Spline type"), GET_INTEGER (L"Order"), GET_STRING (L"Interior knots"), GET_INTEGER (L"Garnish")); END DIRECT (drawMDSClassRelations) autoPraatPicture picture; drawMDSClassRelations (GRAPHICS); END /***************** AffineTransform ***************************************/ DIRECT (AffineTransform_help) Melder_help (L"AffineTransform"); END DIRECT (AffineTransform_invert) LOOP { iam (AffineTransform); praat_new ( (AffineTransform) AffineTransform_invert (me), NAME, L"_inv"); } END FORM (AffineTransform_getTransformationElement, L"AffineTransform: Get transformation element", L"Procrustes") NATURAL (L"Row number", L"1") NATURAL (L"Column number", L"1") OK DO long row = GET_INTEGER (L"Row number"); long column = GET_INTEGER (L"Column number"); LOOP { iam (AffineTransform); if (row > my n) { Melder_throw ("Row number must not exceed number of rows."); } if (column > my n) { Melder_throw ("Column number must not exceed number of columns."); } Melder_information (Melder_double (my r [row] [column])); } END FORM (AffineTransform_getTranslationElement, L"AffineTransform: Get translation element", L"Procrustes") NATURAL (L"Index", L"1") OK DO long number = GET_INTEGER (L"Index"); LOOP { iam (AffineTransform); if (number > my n) { Melder_throw ("Index must not exceed number of elements."); } Melder_information (Melder_double (my t [number])); } END DIRECT (AffineTransform_extractMatrix) LOOP { iam (AffineTransform); praat_new (AffineTransform_extractMatrix (me), my name); } END DIRECT (AffineTransform_extractTranslationVector) LOOP { iam (AffineTransform); praat_new (AffineTransform_extractTranslationVector (me), my name); } END /***************** Configuration ***************************************/ DIRECT (Configuration_help) Melder_help (L"Configuration"); END static void Configuration_draw_addCommonFields (void *dia) { NATURAL (L"Horizontal dimension", L"1") NATURAL (L"Vertical dimension", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") } FORM (Configuration_draw, L"Configuration: Draw", L"Configuration: Draw...") Configuration_draw_addCommonFields (dia); NATURAL (L"Label size", L"12") BOOLEAN (L"Use row labels", 0) WORD (L"Label", L"+") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Configuration); Configuration_draw (me, GRAPHICS, GET_INTEGER (L"Horizontal dimension"), GET_INTEGER (L"Vertical dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Use row labels"), GET_STRING (L"Label"), GET_INTEGER (L"Garnish")); } END FORM (Configuration_drawSigmaEllipses, L"Configuration: Draw sigma ellipses", L"Configuration: Draw sigma ellipses...") POSITIVE (L"Number of sigmas", L"1.0") Configuration_draw_addCommonFields (dia); INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Configuration); Configuration_drawConcentrationEllipses (me, GRAPHICS, GET_REAL (L"Number of sigmas"), 0, 0, GET_INTEGER (L"Horizontal dimension"), GET_INTEGER (L"Vertical dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END FORM (Configuration_drawOneSigmaEllipse, L"Configuration: Draw one sigma ellipse", L"Configuration: Draw sigma ellipses...") SENTENCE (L"Label", L"") POSITIVE (L"Number of sigmas", L"1.0") Configuration_draw_addCommonFields (dia); INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Configuration); Configuration_drawConcentrationEllipses (me, GRAPHICS, GET_REAL (L"Number of sigmas"), 0, GET_STRING (L"Label"), GET_INTEGER (L"Horizontal dimension"), GET_INTEGER (L"Vertical dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END FORM (Configuration_drawConfidenceEllipses, L"Configuration: Draw confidence ellipses", 0) POSITIVE (L"Confidence level (0-1)", L"0.95") Configuration_draw_addCommonFields (dia); INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Configuration); Configuration_drawConcentrationEllipses (me, GRAPHICS, GET_REAL (L"Confidence level"), 1, 0, GET_INTEGER (L"Horizontal dimension"), GET_INTEGER (L"Vertical dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END FORM (Configuration_drawOneConfidenceEllipse, L"Configuration: Draw one confidence ellipse", 0) SENTENCE (L"Label", L"") POSITIVE (L"Confidence level (0-1)", L"0.95") Configuration_draw_addCommonFields (dia); INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Configuration); Configuration_drawConcentrationEllipses (me, GRAPHICS, GET_REAL (L"Confidence level"), 1, GET_STRING (L"Label"), GET_INTEGER (L"Horizontal dimension"), GET_INTEGER (L"Vertical dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END DIRECT (Configuration_randomize) LOOP { iam (Configuration); Configuration_randomize (me); } END FORM (Configuration_normalize, L"Configuration: Normalize", L"Configuration: Normalize...") REAL (L"Sum of squares", L"0.0") LABEL (L"", L"On (INDSCAL), Off (Kruskal)") BOOLEAN (L"Each dimension separately", 1) OK DO LOOP { iam (Configuration); Configuration_normalize (me, GET_REAL (L"Sum of squares"), GET_INTEGER (L"Each dimension separately")); } END DIRECT (Configuration_centralize) LOOP { iam (Configuration); TableOfReal_centreColumns (me); } END FORM (Configuration_rotate, L"Configuration: Rotate", L"Configuration: Rotate...") NATURAL (L"Dimension 1", L"1") NATURAL (L"Dimension 2", L"2") REAL (L"Angle (degrees)", L"60.0") OK DO LOOP { iam (Configuration); Configuration_rotate (me, GET_INTEGER (L"Dimension 1"), GET_INTEGER (L"Dimension 2"), GET_REAL (L"Angle")); } END DIRECT (Configuration_rotateToPrincipalDirections) LOOP { iam (Configuration); Configuration_rotateToPrincipalDirections (me); } END FORM (Configuration_invertDimension, L"Configuration: Invert dimension", L"Configuration: Invert dimension...") NATURAL (L"Dimension", L"1") OK DO LOOP { iam (Configuration); Configuration_invertDimension (me, GET_INTEGER (L"Dimension")); } END DIRECT (Configuration_to_Distance) LOOP { iam (Configuration); praat_new (Configuration_to_Distance (me), my name); } END FORM (Configuration_varimax, L"Configuration: To Configuration (varimax)", L"Configuration: To Configuration (varimax)...") BOOLEAN (L"Normalize rows", 1) BOOLEAN (L"Quartimax", 0) NATURAL (L"Maximum number of iterations", L"50") POSITIVE (L"Tolerance", L"1e-6") OK DO LOOP { iam (Configuration); praat_new (Configuration_varimax (me, GET_INTEGER (L"Normalize rows"), GET_INTEGER (L"Quartimax"), GET_INTEGER (L"Maximum number of iterations"), GET_REAL (L"Tolerance")), my name, L"_varimax"); } END DIRECT (Configurations_to_Similarity_cc) autoConfigurations set = (Configurations) praat_getSelectedObjects (); praat_new (Configurations_to_Similarity_cc (set.peek(), 0), L"congruence"); END FORM (Configurations_to_Procrustes, L"Configuration & Configuration: To Procrustes", L"Configuration & Configuration: To Procrustes...") BOOLEAN (L"Orthogonal transform", 0) OK DO Configuration c1 = 0, c2 = 0; LOOP { iam (Configuration); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); praat_new (Configurations_to_Procrustes (c1, c2, GET_INTEGER (L"Orthogonal transform")), Thing_getName (c2), L"_to_", Thing_getName (c1)); END FORM (Configurations_to_AffineTransform_congruence, L"Configurations: To AffineTransform (congruence)", L"Configurations: To AffineTransform (congruence)...") NATURAL (L"Maximum number of iterations", L"50") POSITIVE (L"Tolerance", L"1e-6") OK DO Configuration c1 = 0, c2 = 0; LOOP { iam (Configuration); (c1 ? c2 : c1) = me; } Melder_assert (c1 && c2); praat_new (Configurations_to_AffineTransform_congruence (c1, c2, GET_INTEGER (L"Maximum number of iterations"), GET_REAL (L"Tolerance")), c1 -> name, L"_", c2 -> name); END DIRECT (Configuration_Weight_to_Similarity_cc) autoConfigurations thee = Configurations_create (); Collection_dontOwnItems (thee.peek()); Weight w = 0; LOOP { iam (Data); if (CLASS == classConfiguration) { Collection_addItem (thee.peek(), me); } else if (CLASS == classWeight) { w = (Weight) me; } } Melder_assert (thy size > 0 && w); praat_new (Configurations_to_Similarity_cc (thee.peek(), w), L"congruence"); END DIRECT (Configuration_and_AffineTransform_to_Configuration) Configuration me = FIRST (Configuration); AffineTransform at = FIRST_GENERIC (AffineTransform); praat_new (Configuration_and_AffineTransform_to_Configuration (me, at), my name, L"_", at -> name); END /*************** Confusion *********************************/ FORM (Confusion_to_Dissimilarity_pdf, L"Confusion: To Dissimilarity (pdf)", L"Confusion: To Dissimilarity (pdf)...") POSITIVE (L"Minimum confusion level", L"0.5") OK DO LOOP { iam (Confusion); praat_new (Confusion_to_Dissimilarity_pdf (me, GET_REAL (L"Minimum confusion level")), my name, L"_pdf"); } END FORM (Confusion_to_Similarity, L"Confusion: To Similarity", L"Confusion: To Similarity...") BOOLEAN (L"Normalize", 1) RADIO (L"Symmetrization", 1) RADIOBUTTON (L"No symmetrization") RADIOBUTTON (L"Average (s[i][j] = (c[i][j]+c[j][i])/2)") RADIOBUTTON (L"Houtgast (s[i][j]= sum (min(c[i][k],c[j][k])))") OK DO LOOP { iam (Confusion); praat_new (Confusion_to_Similarity (me, GET_INTEGER (L"Normalize"), GET_INTEGER (L"Symmetrization")), my name); } END DIRECT (Confusions_sum) autoConfusions me = (Confusions) praat_getSelectedObjects (); praat_new (Confusions_sum (me.peek()), L"sum"); END DIRECT (Confusion_to_ContingencyTable) LOOP { iam (Confusion); praat_new (Confusion_to_ContingencyTable (me), my name); } END /*************** ContingencyTable *********************************/ FORM (ContingencyTable_to_Configuration_ca, L"ContingencyTable: To Configuration (ca)", L"ContingencyTable: To Configuration (ca)...") NATURAL (L"Number of dimensions", L"2") RADIO (L"Scaling of final configuration", 3) RADIOBUTTON (L"Row points in centre of gravity of column points") RADIOBUTTON (L"Column points in centre of gravity of row points") RADIOBUTTON (L"Row points and column points symmetric") OK DO LOOP { iam (ContingencyTable); praat_new (ContingencyTable_to_Configuration_ca (me, GET_INTEGER (L"Number of dimensions"), GET_INTEGER (L"Scaling of final configuration")), my name); } END DIRECT (ContingencyTable_chisqProbability) LOOP { iam (ContingencyTable); Melder_information (Melder_double (ContingencyTable_chisqProbability (me))); } END DIRECT (ContingencyTable_cramersStatistic) LOOP { iam (ContingencyTable); Melder_information (Melder_double (ContingencyTable_cramersStatistic (me))); } END DIRECT (ContingencyTable_contingencyCoefficient) LOOP { iam (ContingencyTable); Melder_information (Melder_double (ContingencyTable_contingencyCoefficient (me))); } END /************************* Correlation ***********************************/ FORM (Correlation_to_Configuration, L"Correlation: To Configuration", 0) NATURAL (L"Number of dimensions", L"2") OK DO LOOP { iam (Correlation); praat_new (Correlation_to_Configuration (me, GET_INTEGER (L"Number of dimensions")), my name); } END /************************* Similarity ***************************************/ DIRECT (Similarity_help) Melder_help (L"Similarity"); END FORM (Similarity_to_Dissimilarity, L"Similarity: To Dissimilarity", L"Similarity: To Dissimilarity...") REAL (L"Maximum dissimilarity", L"0.0 (=from data)") OK DO LOOP { iam (Similarity); praat_new (Similarity_to_Dissimilarity (me, GET_REAL (L"Maximum dissimilarity")), my name); } END /**************** Dissimilarity ***************************************/ static void Dissimilarity_to_Configuration_addCommonFields (void *dia) { LABEL (L"", L"Minimization parameters") REAL (L"Tolerance", L"1e-5") NATURAL (L"Maximum number of iterations", L"50 (= each repetition)") NATURAL (L"Number of repetitions", L"1") } static void Dissimilarity_and_Configuration_getStress_addCommonFields (void *dia, void *radio) { RADIO (L"Stress measure", 1) RADIOBUTTON (L"Normalized") RADIOBUTTON (L"Kruskal's stress-1") RADIOBUTTON (L"Kruskal's stress-2") RADIOBUTTON (L"Raw") } static void Dissimilarity_Configuration_drawDiagram_addCommonFields (void *dia) { REAL (L"left Proximity range", L"0.0") REAL (L"right Proximity range", L"0.0") REAL (L"left Distance range", L"0.0") REAL (L"right Distance range", L"0.0") POSITIVE (L"Mark size (mm)", L"1.0") SENTENCE (L"Mark string (+xo.)", L"+") BOOLEAN (L"Garnish", 1) } DIRECT (Dissimilarity_help) Melder_help (L"Dissimilarity"); END DIRECT (Dissimilarity_getAdditiveConstant) LOOP { iam (Dissimilarity); double c; Dissimilarity_getAdditiveConstant (me, &c); Melder_information (Melder_double (c)); } END FORM (Dissimilarity_Configuration_kruskal, L"Dissimilarity & Configuration: To Configuration (kruskal)", L"Dissimilarity & Configuration: To Configuration (kruskal)...") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") RADIO (L"Stress calculation", 1) RADIOBUTTON (L"Formula1") RADIOBUTTON (L"Formula2") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); praat_new (Dissimilarity_Configuration_kruskal (me, c, GET_INTEGER (L"Handling of ties"), GET_INTEGER (L"Stress calculation"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions")), my name, L"_kruskal"); END FORM (Dissimilarity_Configuration_absolute_mds, L"Dissimilarity & Configuration: To Configuration (absolute mds)", L"Dissimilarity & Configuration: To Configuration (absolute mds)...") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_absolute_mds (me, c, 0, GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_absolute"); END FORM (Dissimilarity_Configuration_ratio_mds, L"Dissimilarity & Configuration: To Configuration (ratio mds)", L"Dissimilarity & Configuration: To Configuration (ratio mds)...") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_ratio_mds (me, c, 0, GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_ratio"); END FORM (Dissimilarity_Configuration_interval_mds, L"Dissimilarity & Configuration: To Configuration (interval mds)", L"Dissimilarity & Configuration: To Configuration (interval mds)...") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_interval_mds (me, c, 0, GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_interval"); END FORM (Dissimilarity_Configuration_monotone_mds, L"Dissimilarity & Configuration: To Configuration (monotone mds)", L"Dissimilarity & Configuration: To Configuration (monotone mds)...") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_monotone_mds (me, c, 0, GET_INTEGER (L"Handling of ties"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_monotone"); END FORM (Dissimilarity_Configuration_ispline_mds, L"Dissimilarity & Configuration: To Configuration (i-spline mds)", L"Dissimilarity & Configuration: To Configuration (i-spline mds)...") LABEL (L"", L"Spline smoothing") INTEGER (L"Number of interior knots", L"1") INTEGER (L"Order of I-spline", L"1") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_ispline_mds (me, c, 0, GET_INTEGER (L"Number of interior knots"), GET_INTEGER (L"Order of I-spline"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_ispline"); END FORM (Dissimilarity_Configuration_Weight_absolute_mds, L"Dissimilarity & Configuration & Weight: To Configuration (absolute mds)", L"Dissimilarity & Configuration & Weight: To Configuration...") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_absolute_mds (me, c, w, GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_w_absolute"); END FORM (Dissimilarity_Configuration_Weight_ratio_mds, L"Dissimilarity & Configuration & Weight: To Configuration (ratio mds)", L"Dissimilarity & Configuration & Weight: To Configuration...") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_ratio_mds (me, c, w, GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_w_ratio"); END FORM (Dissimilarity_Configuration_Weight_interval_mds, L"Dissimilarity & Configuration & Weight: To Configuration (interval mds)", L"Dissimilarity & Configuration & Weight: To Configuration...") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_interval_mds (me, c, w, GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_w_interval"); END FORM (Dissimilarity_Configuration_Weight_monotone_mds, L"Dissimilarity & Configuration & Weight: To Configuration (monotone mds)", L"Dissimilarity & Configuration & Weight: To Configuration...") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_monotone_mds (me, c, w, GET_INTEGER (L"Handling of ties"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_sw_monotone"); END FORM (Dissimilarity_Configuration_Weight_ispline_mds, L"Dissimilarity & Configuration & Weight: To Configuration (i-spline mds)", L"Dissimilarity & Configuration & Weight: To Configuration...") LABEL (L"", L"Spline smoothing") INTEGER (L"Number of interior knots", L"1") INTEGER (L"Order of I-spline", L"1") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); int showProgress = 1; praat_new (Dissimilarity_Configuration_Weight_ispline_mds (me, c, w, GET_INTEGER (L"Number of interior knots"), GET_INTEGER (L"Order of I-spline"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_sw_ispline"); END FORM (Dissimilarity_Configuration_getStress, L"Dissimilarity & Configuration: Get stress", L"Dissimilarity & Configuration: get stress") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") RADIO (L"Stress calculation", 1) RADIOBUTTON (L"Formula1") RADIOBUTTON (L"Formula2") OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Melder_information (Melder_double (Dissimilarity_Configuration_getStress (me, c, GET_INTEGER (L"Handling of ties"), GET_INTEGER (L"Stress calculation")))); END FORM (Dissimilarity_Configuration_absolute_stress, L"Dissimilarity & Configuration: Get stress (absolute mds)", L"Dissimilarity & Configuration: Get stress (absolute mds)...") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_absolute_stress (me, c, 0, GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_ratio_stress, L"Dissimilarity & Configuration: Get stress (ratio mds)", L"Dissimilarity & Configuration: Get stress (ratio mds)...") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_ratio_stress (me, c, 0, GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_interval_stress, L"Dissimilarity & Configuration: Get stress (interval mds)", L"Dissimilarity & Configuration: Get stress (interval mds)...") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_interval_stress (me, c, 0, GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_monotone_stress, L"Dissimilarity & Configuration: Get stress (monotone mds)", L"Dissimilarity & Configuration: Get stress (monotone mds)...") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_monotone_stress (me, c, 0, GET_INTEGER (L"Handling of ties"), GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_ispline_stress, L"Dissimilarity & Configuration: Get stress (i-spline mds)", L"Dissimilarity & Configuration: Get stress (i-spline mds)...") INTEGER (L"Number of interior knots", L"1") INTEGER (L"Order of I-spline", L"3") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_ispline_stress (me, c, 0, GET_INTEGER (L"Number of interior knots"), GET_INTEGER (L"Order of I-spline"), GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_Weight_absolute_stress, L"Dissimilarity & Configuration & Weight: Get stress (absolute mds)", L"Dissimilarity & Configuration & Weight: Get stress (absolute mds)...") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_absolute_stress (me, c, w, GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_Weight_ratio_stress, L"Dissimilarity & Configuration & Weight: Get stress (ratio mds)", L"Dissimilarity & Configuration & Weight: Get stress (ratio mds)...") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_ratio_stress (me, c, w, GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_Weight_interval_stress, L"Dissimilarity & Configuration & Weight: Get stress (interval mds)", L"Dissimilarity & Configuration & Weight: Get stress (interval mds)...") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_interval_stress (me, c, w, GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_Weight_monotone_stress, L"Dissimilarity & Configuration & Weight: Get stress (monotone mds)", L"Dissimilarity & Configuration & Weight: Get stress (monotone mds)...") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach)") RADIOBUTTON (L"Secondary approach") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_monotone_stress (me, c, w, GET_INTEGER (L"Handling of ties"), GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_Weight_ispline_stress, L"Dissimilarity & Configuration & Weight: Get stress (i-spline mds)", L"Dissimilarity & Configuration & Weight: Get stress (i-spline mds)...") INTEGER (L"Number of interior knots", L"1") INTEGER (L"Order of I-spline", L"3") Dissimilarity_and_Configuration_getStress_addCommonFields (dia, radio); OK DO Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Weight w = FIRST (Weight); Melder_information (Melder_double (Dissimilarity_Configuration_Weight_ispline_stress (me, c, w, GET_INTEGER (L"Number of interior knots"), GET_INTEGER (L"Order of I-spline"), GET_INTEGER (L"Stress measure")))); END FORM (Dissimilarity_Configuration_drawShepardDiagram, L"Dissimilarity & Configuration: Draw Shepard diagram", L"Dissimilarity & Configuration: Draw Shepard diagram...") Dissimilarity_Configuration_drawDiagram_addCommonFields (dia); OK DO autoPraatPicture picture; Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Dissimilarity_Configuration_drawShepardDiagram (me, c, GRAPHICS, GET_REAL (L"left Proximity range"), GET_REAL (L"right Proximity range"), GET_REAL (L"left Distance range"), GET_REAL (L"right Distance range"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); END FORM (Dissimilarity_Configuration_drawAbsoluteRegression, L"Dissimilarity & Configuration: Draw regression (absolute mds)", L"Dissimilarity & Configuration: Draw regression (absolute mds)...") Dissimilarity_Configuration_drawDiagram_addCommonFields (dia); OK DO autoPraatPicture picture; Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Dissimilarity_Configuration_Weight_drawAbsoluteRegression (me, c, 0, GRAPHICS, GET_REAL (L"left Proximity range"), GET_REAL (L"right Proximity range"), GET_REAL (L"left Distance range"), GET_REAL (L"right Distance range"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); END FORM (Dissimilarity_Configuration_drawRatioRegression, L"Dissimilarity & Configuration: Draw regression (ratio mds)", L"Dissimilarity & Configuration: Draw regression (ratio mds)...") Dissimilarity_Configuration_drawDiagram_addCommonFields (dia); OK DO autoPraatPicture picture; Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Dissimilarity_Configuration_Weight_drawRatioRegression (me, c, 0, GRAPHICS, GET_REAL (L"left Proximity range"), GET_REAL (L"right Proximity range"), GET_REAL (L"left Distance range"), GET_REAL (L"right Distance range"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); END FORM (Dissimilarity_Configuration_drawIntervalRegression, L"Dissimilarity & Configuration: Draw regression (interval mds)", L"Dissimilarity & Configuration: Draw regression (interval mds)...") Dissimilarity_Configuration_drawDiagram_addCommonFields (dia); OK DO autoPraatPicture picture; Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Dissimilarity_Configuration_Weight_drawIntervalRegression (me, c, 0, GRAPHICS, GET_REAL (L"left Proximity range"), GET_REAL (L"right Proximity range"), GET_REAL (L"left Distance range"), GET_REAL (L"right Distance range"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); END FORM (Dissimilarity_Configuration_drawMonotoneRegression, L"Dissimilarity & Configuration: Draw regression (monotone mds)", L"Dissimilarity & Configuration: Draw regression (monotone mds)...") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach)") RADIOBUTTON (L"Secondary approach") Dissimilarity_Configuration_drawDiagram_addCommonFields (dia); OK DO autoPraatPicture picture; Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Dissimilarity_Configuration_Weight_drawMonotoneRegression (me, c, 0, GRAPHICS, GET_INTEGER (L"Handling of ties"), GET_REAL (L"left Proximity range"), GET_REAL (L"right Proximity range"), GET_REAL (L"left Distance range"), GET_REAL (L"right Distance range"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); END FORM (Dissimilarity_Configuration_drawISplineRegression, L"Dissimilarity & Configuration: Draw regression (i-spline mds)", L"Dissimilarity & Configuration: Draw regression (i-spline mds)...") INTEGER (L"Number of interior knots", L"1") INTEGER (L"Order of I-spline", L"3") Dissimilarity_Configuration_drawDiagram_addCommonFields (dia); OK DO autoPraatPicture picture; Dissimilarity me = FIRST (Dissimilarity); Configuration c = FIRST (Configuration); Dissimilarity_Configuration_Weight_drawISplineRegression (me, c, 0, GRAPHICS, GET_INTEGER (L"Number of interior knots"), GET_INTEGER (L"Order of I-spline"), GET_REAL (L"left Proximity range"), GET_REAL (L"right Proximity range"), GET_REAL (L"left Distance range"), GET_REAL (L"right Distance range"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); END FORM (Dissimilarity_kruskal, L"Dissimilarity: To Configuration (kruskal)", L"Dissimilarity: To Configuration (kruskal)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") NATURAL (L"Distance metric", L"2 (=Euclidean)") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") RADIO (L"Stress calculation", 1) RADIOBUTTON (L"Formula1") RADIOBUTTON (L"Formula2") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO LOOP { iam (Dissimilarity); praat_new (Dissimilarity_kruskal (me, GET_INTEGER (L"Number of dimensions"), GET_INTEGER (L"Distance metric"), GET_INTEGER (L"Handling of ties"), GET_INTEGER (L"Stress calculation"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions")), my name); } END FORM (Dissimilarity_absolute_mds, L"Dissimilarity: To Configuration (absolute mds)", L"Dissimilarity: To Configuration (absolute mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO LOOP { iam (Dissimilarity); int showProgress = 1; praat_new (Dissimilarity_Weight_absolute_mds (me, NULL, GET_INTEGER (L"Number of dimensions"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_absolute"); } END FORM (Dissimilarity_ratio_mds, L"Dissimilarity: To Configuration (ratio mds)", L"Dissimilarity: To Configuration (ratio mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO LOOP { iam (Dissimilarity); int showProgress = 1; praat_new (Dissimilarity_Weight_ratio_mds (me, 0, GET_INTEGER (L"Number of dimensions"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_ratio"); } END FORM (Dissimilarity_interval_mds, L"Dissimilarity: To Configuration (interval mds)", L"Dissimilarity: To Configuration (interval mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO LOOP { iam (Dissimilarity); int showProgress = 1; praat_new (Dissimilarity_Weight_interval_mds (me, 0, GET_INTEGER (L"Number of dimensions"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_interval"); } END FORM (Dissimilarity_monotone_mds, L"Dissimilarity: To Configuration (monotone mds)", L"Dissimilarity: To Configuration (monotone mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO LOOP { iam (Dissimilarity); int showProgress = 1; praat_new (Dissimilarity_Weight_monotone_mds (me, 0, GET_INTEGER (L"Number of dimensions"), GET_INTEGER (L"Handling of ties"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_monotone"); } END FORM (Dissimilarity_ispline_mds, L"Dissimilarity: To Configuration (i-spline mds)", L"Dissimilarity: To Configuration (i-spline mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") LABEL (L"", L"Spline smoothing") INTEGER (L"Number of interior knots", L"1") INTEGER (L"Order of I-spline", L"1") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO long niknots = GET_INTEGER (L"Number of interior knots"); long order = GET_INTEGER (L"Order of I-spline"); if (not (order > 0 || niknots > 0)) { Melder_throw ("Order-zero spline must at least have 1 interior knot."); } LOOP { iam (Dissimilarity); int showProgress = 1; praat_new (Dissimilarity_Weight_ispline_mds (me, 0, GET_INTEGER (L"Number of dimensions"), niknots, order, GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_ispline"); } END FORM (Dissimilarity_Weight_ispline_mds, L"Dissimilarity & Weight: To Configuration (i-spline mds)", L"Dissimilarity & Weight: To Configuration (i-spline mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") LABEL (L"", L"Spline smoothing") INTEGER (L"Number of interior knots", L"1") INTEGER (L"Order of I-spline", L"1") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Weight w = FIRST (Weight); int showProgress = 1; long niknots = GET_INTEGER (L"Number of interior knots"); long order = GET_INTEGER (L"Order of I-spline"); if (not (order > 0 || niknots > 0)) { Melder_throw ("Order-zero spline must at least have 1 interior knot."); } praat_new (Dissimilarity_Weight_ispline_mds (me, w, GET_INTEGER (L"Number of dimensions"), niknots, order, GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_ispline"); END FORM (Dissimilarity_Weight_absolute_mds, L"Dissimilarity & Weight: To Configuration (absolute mds)", L"Dissimilarity & Weight: To Configuration (absolute mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Weight w = FIRST (Weight); int showProgress = 1; praat_new (Dissimilarity_Weight_absolute_mds (me, w, GET_INTEGER (L"Number of dimensions"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_absolute"); END FORM (Dissimilarity_Weight_ratio_mds, L"Dissimilarity & Weight: To Configuration (ratio mds)", L"Dissimilarity & Weight: To Configuration (ratio mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Weight w = FIRST (Weight); int showProgress = 1; praat_new (Dissimilarity_Weight_ratio_mds (me, w, GET_INTEGER (L"Number of dimensions"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_absolute"); END FORM (Dissimilarity_Weight_interval_mds, L"Dissimilarity & Weight: To Configuration (interval mds)", L"Dissimilarity & Weight: To Configuration (interval mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Weight w = FIRST (Weight); int showProgress = 1; praat_new (Dissimilarity_Weight_interval_mds (me, w, GET_INTEGER (L"Number of dimensions"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_absolute"); END FORM (Dissimilarity_Weight_monotone_mds, L"Dissimilarity & Weight: To Configuration (monotone mds)", L"Dissimilarity & Weight: To Configuration (monotone mds)...") LABEL (L"", L"Configuration") NATURAL (L"Number of dimensions", L"2") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") Dissimilarity_to_Configuration_addCommonFields (dia); OK DO Dissimilarity me = FIRST (Dissimilarity); Weight w = FIRST (Weight); int showProgress = 1; praat_new (Dissimilarity_Weight_monotone_mds (me, w, GET_INTEGER (L"Number of dimensions"), GET_INTEGER (L"Handling of ties"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), showProgress), my name, L"_monotone"); END FORM (Dissimilarity_to_Distance, L"Dissimilarity: To Distance", L"Dissimilarity: To Distance...") BOOLEAN (L"Scale (additive constant)", 1) OK DO LOOP { iam (Dissimilarity); praat_new (Dissimilarity_to_Distance (me, GET_INTEGER (L"Scale")), my name); } END DIRECT (Dissimilarity_to_Weight) LOOP { iam (Dissimilarity); praat_new (Dissimilarity_to_Weight (me), my name); } END /************************* Distance(s) ***************************************/ FORM (Distance_to_ScalarProduct, L"Distance: To ScalarProduct", L"Distance: To ScalarProduct...") BOOLEAN (L"Make sum of squares equal 1.0", 1) OK DO LOOP { iam (Distance); praat_new (Distance_to_ScalarProduct (me, GET_INTEGER (L"Make sum of squares equal 1.0")), my name); } END DIRECT (Distance_to_Dissimilarity) LOOP { iam (Distance); praat_new (Distance_to_Dissimilarity (me), my name); } END FORM (Distances_indscal, L"Distance: To Configuration (indscal)", L"Distance: To Configuration (indscal)...") NATURAL (L"Number of dimensions", L"2") BOOLEAN (L"Normalize scalar products", 1) LABEL (L"", L"Minimization parameters") REAL (L"Tolerance", L"1e-5") NATURAL (L"Maximum number of iterations", L"100 (= each repetition)") NATURAL (L"Number of repetitions", L"1") OK DO autoDistances me = (Distances) praat_getSelectedObjects (); Configuration c; Salience s; Distances_indscal (me.peek(), GET_INTEGER (L"Number of dimensions"), GET_INTEGER (L"Normalize scalar products"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), GET_INTEGER (L"Number of repetitions"), 1, &c, &s); autoConfiguration ac = c; autoSalience as = s; praat_new (ac.transfer(), L"indscal"); praat_new (as.transfer(), L"indscal"); END FORM (Distance_and_Configuration_drawScatterDiagram, L"Distance & Configuration: Draw scatter diagram", L"Distance & Configuration: Draw scatter diagram...") REAL (L"Minimum x-distance", L"0.0") REAL (L"Maximum x-distance", L"0.0") REAL (L"Minimum y-distance", L"0.0") REAL (L"Maximum y-distance", L"0.0") POSITIVE (L"Mark size (mm)", L"1.0") SENTENCE (L"Mark string (+xo.)", L"+") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; Distance me = FIRST (Distance); Configuration c = FIRST (Configuration); Distance_and_Configuration_drawScatterDiagram (me, c, GRAPHICS, GET_REAL (L"Minimum x-distance"), GET_REAL (L"Maximum x-distance"), GET_REAL (L"Minimum y-distance"), GET_REAL (L"Maximum y-distance"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); END FORM (Distance_Configuration_indscal, L"Distance & Configuration: To Configuration (indscal)", L"Distance & Configuration: To Configuration (indscal)...") BOOLEAN (L"Normalize scalar products", 1) LABEL (L"", L"Minimization parameters") REAL (L"Tolerance", L"1e-5") NATURAL (L"Maximum number of iterations", L"100 (= each repetition)") OK DO autoDistances thee = Distances_create (); Collection_dontOwnItems (thee.peek()); Configuration c = 0; LOOP { iam (Data); if (CLASS == classDistance) { Collection_addItem (thee.peek(), me); } else if (CLASS == classConfiguration) { c = (Configuration) me; } } Melder_assert (thy size > 0 && c); Configuration cr; Salience sr; Distances_Configuration_indscal (thee.peek(), c, GET_INTEGER (L"Normalize scalar products"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), 1, &cr, &sr); autoConfiguration ac = cr; autoSalience as = sr; praat_new (ac.transfer(), L"indscal"); praat_new (as.transfer(), L"indscal"); END FORM (Distance_Configuration_vaf, L"Distance & Configuration: Get VAF", L"Distance & Configuration: Get VAF...") BOOLEAN (L"Normalize scalar products", 1) OK DO autoDistances thee = Distances_create (); Collection_dontOwnItems (thee.peek()); Configuration c = 0; LOOP { iam (Data); if (CLASS == classDistance) { Collection_addItem (thee.peek(), me); } else if (CLASS == classConfiguration) { c = (Configuration) me; } } Melder_assert (thy size > 0 && c); double vaf; Distances_Configuration_vaf (thee.peek(), c, GET_INTEGER (L"Normalize scalar products"), &vaf); Melder_information (Melder_double (vaf)); END FORM (Distance_Configuration_Salience_vaf, L"Distance & Configuration & Salience: Get VAF", L"Distance & Configuration & Salience: Get VAF...") BOOLEAN (L"Normalize scalar products", 1) OK DO autoDistances thee = Distances_create (); Collection_dontOwnItems (thee.peek()); Configuration c = 0; Salience s = 0; LOOP { iam (Data); if (CLASS == classDistance) { Collection_addItem (thee.peek(), me); } else if (CLASS == classConfiguration) { c = (Configuration) me; } else if (CLASS == classSalience) { s = (Salience) me; } } Melder_assert (thy size > 0 && c && s); double vaf; Distances_Configuration_Salience_vaf (thee.peek(), c, s, GET_INTEGER (L"Normalize scalar products"), &vaf); Melder_information (Melder_double (vaf)); END FORM (Dissimilarity_Configuration_Salience_vaf, L"Dissimilarity & Configuration & Salience: Get VAF", L"Dissimilarity & Configuration & Salience: Get VAF...") RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") BOOLEAN (L"Normalize scalar products", 1) OK DO autoDissimilarities thee = Dissimilarities_create (); Collection_dontOwnItems (thee.peek()); Configuration c = 0; Salience s = 0; LOOP { iam (Data); if (CLASS == classDissimilarity) { Collection_addItem (thee.peek(), me); } else if (CLASS == classConfiguration) { c = (Configuration) me; } else if (CLASS == classSalience) { s = (Salience) me; } } Melder_assert (thy size > 0 && c && s); double vaf; Dissimilarities_Configuration_Salience_vaf (thee.peek(), c, s, GET_INTEGER (L"Handling of ties"), GET_INTEGER (L"Normalize scalar products"), &vaf); Melder_information (Melder_double (vaf)); END FORM (Distance_Configuration_Salience_indscal, L"Distance & Configuration & Salience: To Configuration (indscal)", L"Distance & Configuration & Salience: To Configuration (indscal)...") BOOLEAN (L"Normalize scalar products", 1) LABEL (L"", L"Minimization parameters") REAL (L"Tolerance", L"1e-5") NATURAL (L"Maximum number of iterations", L"100") OK DO autoDistances thee = Distances_create (); Collection_dontOwnItems (thee.peek()); Configuration c = 0; Salience s = 0; LOOP { iam (Data); if (CLASS == classDistance) { Collection_addItem (thee.peek(), me); } else if (CLASS == classConfiguration) { c = (Configuration) me; } else if (CLASS == classSalience) { s = (Salience) me; } } Melder_assert (thy size > 0 && c && s); double vaf; Configuration cr; Salience sr; Distances_Configuration_Salience_indscal (thee.peek(), c, s, GET_INTEGER (L"Normalize scalar products"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Maximum number of iterations"), 1, &cr, &sr, &vaf); autoConfiguration ac = cr; autoSalience as = sr; praat_new (ac.transfer(), L"indscal"); praat_new (as.transfer(), L"indscal"); END FORM (Distances_to_Configuration_ytl, L"Distance: To Configuration (ytl)", L"Distance: To Configuration (ytl)...") NATURAL (L"Number of dimensions", L"2") BOOLEAN (L"Normalize scalar products", 1) BOOLEAN (L"Salience object", 0) OK DO autoDistances me = (Distances) praat_getSelectedObjects (); Configuration cr; Salience sr; Distances_to_Configuration_ytl (me.peek(), GET_INTEGER (L"Number of dimensions"), GET_INTEGER (L"Normalize scalar products"), &cr, &sr); autoConfiguration ac = cr; autoSalience as = sr; praat_new (ac.transfer(), L"ytl"); if (GET_INTEGER (L"Salience object")) { praat_new (as.transfer(), L"ytl"); } END FORM (Dissimilarity_Distance_monotoneRegression, L"Dissimilarity & Distance: Monotone regression", 0) RADIO (L"Handling of ties", 1) RADIOBUTTON (L"Primary approach") RADIOBUTTON (L"Secondary approach") OK DO Dissimilarity me = FIRST (Dissimilarity); Distance d = FIRST (Distance); praat_new (Dissimilarity_Distance_monotoneRegression (me, d, GET_INTEGER (L"Handling of ties")), my name); END FORM (Distance_Dissimilarity_drawShepardDiagram, L"Distance & Dissimilarity: Draw Shepard diagram", L"") REAL (L"Minimum dissimilarity", L"0.0") REAL (L"Maximum dissimilarity", L"0.0") REAL (L"left Distance range", L"0.0") REAL (L"right Distance range", L"0.0") POSITIVE (L"Mark size (mm)", L"1.0") SENTENCE (L"Mark string (+xo.)", L"+") BOOLEAN (L"Garnish", 1) OK DO Dissimilarity me = FIRST (Dissimilarity); Distance d = FIRST (Distance); Proximity_Distance_drawScatterDiagram (me, d, GRAPHICS, GET_REAL (L"Minimum dissimilarity"), GET_REAL (L"Maximum dissimilarity"), GET_REAL (L"left Distance range"), GET_REAL (L"right Distance range"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); END DIRECT (MDS_help) Melder_help (L"Multidimensional scaling"); END /************************* Salience ***************************************/ FORM (Salience_draw, L"Salience: Draw", 0) NATURAL (L"Horizontal dimension", L"1") NATURAL (L"Vertical dimension", L"2") BOOLEAN (L"Garnish", 1) OK DO LOOP { iam (Salience); Salience_draw (me, GRAPHICS, GET_INTEGER (L"Horizontal dimension"), GET_INTEGER (L"Vertical dimension"), GET_INTEGER (L"Garnish")); } END /************************* COVARIANCE & CONFIGURATION ********************/ FORM (Covariance_to_Configuration, L"Covariance: To Configuration", 0) NATURAL (L"Number of dimensions", L"2") OK DO LOOP { iam (Covariance); praat_new (Covariance_to_Configuration (me, GET_INTEGER (L"Number of dimensions")), my name); } END /********* Procrustes ***************************/ DIRECT (Procrustes_help) Melder_help (L"Procrustes"); END DIRECT (Procrustes_getScale) LOOP { iam (Procrustes); Melder_information (Melder_double (my s)); } END /********* Casts from & to TableOfReal ***************************/ DIRECT (TableOfReal_to_Dissimilarity) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Dissimilarity (me), my name); } END DIRECT (TableOfReal_to_Similarity) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Similarity (me), my name); } END DIRECT (TableOfReal_to_Distance) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Distance (me), my name); } END DIRECT (TableOfReal_to_Salience) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Salience (me), my name); } END DIRECT (TableOfReal_to_Weight) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Weight (me), my name); } END DIRECT (TableOfReal_to_ScalarProduct) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_ScalarProduct (me), my name); } END DIRECT (TableOfReal_to_Configuration) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Configuration (me), my name); } END DIRECT (TableOfReal_to_ContingencyTable) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_ContingencyTable (me), my name); } END /********************** TableOfReal ***************************************/ DIRECT (TableOfReal_getTableNorm) LOOP { iam (TableOfReal); Melder_information (Melder_double (TableOfReal_getTableNorm (me))); } END FORM (TableOfReal_normalizeTable, L"TableOfReal: Normalize table", L"TableOfReal: Normalize table...") POSITIVE (L"Norm", L"1.0") OK DO LOOP { iam (TableOfReal); TableOfReal_normalizeTable (me, GET_REAL (L"Norm")); } END FORM (TableOfReal_normalizeRows, L"TableOfReal: Normalize rows", L"TableOfReal: Normalize rows...") POSITIVE (L"Norm", L"1.0") OK DO LOOP { iam (TableOfReal); TableOfReal_normalizeRows (me, GET_REAL (L"Norm")); } END FORM (TableOfReal_normalizeColumns, L"TableOfReal: Normalize columns", L"TableOfReal: Normalize columns...") POSITIVE (L"Norm", L"1.0") OK DO LOOP { iam (TableOfReal); TableOfReal_normalizeColumns (me, GET_REAL (L"Norm")); } END DIRECT (TableOfReal_centreRows) LOOP { iam (TableOfReal); TableOfReal_centreRows (me); } END DIRECT (TableOfReal_centreColumns) LOOP { iam (TableOfReal); TableOfReal_centreColumns (me); } END DIRECT (TableOfReal_doubleCentre) LOOP { iam (TableOfReal); TableOfReal_doubleCentre (me); } END DIRECT (TableOfReal_standardizeRows) LOOP { iam (TableOfReal); TableOfReal_standardizeRows (me); } END DIRECT (TableOfReal_standardizeColumns) LOOP { iam (TableOfReal); TableOfReal_standardizeColumns (me); } END DIRECT (TableOfReal_to_Confusion) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_Confusion (me), my name); } END static void praat_AffineTransform_init (ClassInfo klas) { praat_addAction1 (klas, 0, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (klas, 1, L"Get transformation element...", QUERY_BUTTON, 1, DO_AffineTransform_getTransformationElement); praat_addAction1 (klas, 1, L"Get translation element...", QUERY_BUTTON, 1, DO_AffineTransform_getTranslationElement); praat_addAction1 (klas, 0, L"Invert", 0, 0, DO_AffineTransform_invert); } static void praat_Configuration_and_AffineTransform_init (ClassInfo transform) { praat_addAction2 (classConfiguration, 1, transform, 1, L"To Configuration", 0, 0, DO_Configuration_and_AffineTransform_to_Configuration); } void praat_TableOfReal_extras (ClassInfo klas); void praat_TableOfReal_extras (ClassInfo klas) { praat_addAction1 (klas, 1, L"-- get additional --", L"Get value...", 1, 0); praat_addAction1 (klas, 1, L"Get table norm", L"-- get additional --", 1, DO_TableOfReal_getTableNorm); praat_addAction1 (klas, 1, L"-- set additional --", L"Set column label (label)...", 1, 0); praat_addAction1 (klas, 1, L"Normalize rows...", L"-- set additional --", 1, DO_TableOfReal_normalizeRows); praat_addAction1 (klas, 1, L"Normalize columns...", L"Normalize rows...", 1, DO_TableOfReal_normalizeColumns); praat_addAction1 (klas, 1, L"Normalize table...", L"Normalize columns...", 1, DO_TableOfReal_normalizeTable); praat_addAction1 (klas, 1, L"Standardize rows", L"Normalize table...", 1, DO_TableOfReal_standardizeRows); praat_addAction1 (klas, 1, L"Standardize columns", L"Standardize rows", 1, DO_TableOfReal_standardizeColumns); praat_addAction1 (klas, 1, L"Test sorting...", L"Standardize columns", praat_DEPTH_1 + praat_HIDDEN, DO_TabelOfReal_testSorting); } void praat_uvafon_MDS_init (); void praat_uvafon_MDS_init () { Thing_recognizeClassesByName (classAffineTransform, classProcrustes, classContingencyTable, classDissimilarity, classSimilarity, classConfiguration, classDistance, classSalience, classScalarProduct, classWeight, NULL); Thing_recognizeClassByOtherName (classProcrustes, L"Procrustus"); praat_addMenuCommand (L"Objects", L"New", L"Multidimensional scaling", 0, 0, 0); praat_addMenuCommand (L"Objects", L"New", L"MDS tutorial", 0, 1, DO_MDS_help); praat_addMenuCommand (L"Objects", L"New", L"-- MDS --", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Create letter R example...", 0, 1, DO_Dissimilarity_createLetterRExample); praat_addMenuCommand (L"Objects", L"New", L"Create INDSCAL Carroll Wish example...", 0, 1, DO_INDSCAL_createCarrollWishExample); praat_addMenuCommand (L"Objects", L"New", L"Create Configuration...", 0, 1, DO_Configuration_create); praat_addMenuCommand (L"Objects", L"New", L"Draw splines...", 0, 1, DO_drawSplines); praat_addMenuCommand (L"Objects", L"New", L"Draw MDS class relations", 0, 1, DO_drawMDSClassRelations); /****** 1 class ********************************************************/ praat_addAction1 (classAffineTransform, 0, L"AffineTransform help", 0, 0, DO_AffineTransform_help); praat_AffineTransform_init (classAffineTransform); praat_addAction1 (classConfiguration, 0, L"Configuration help", 0, 0, DO_Configuration_help); praat_TableOfReal_init2 (classConfiguration); praat_TableOfReal_extras (classConfiguration); (void) praat_removeAction (classConfiguration, NULL, NULL, L"Insert column (index)..."); (void) praat_removeAction (classConfiguration, NULL, NULL, L"Remove column (index)..."); (void) praat_removeAction (classConfiguration, NULL, NULL, L"Append"); praat_addAction1 (classConfiguration, 0, L"Draw...", DRAW_BUTTON, 1, DO_Configuration_draw); praat_addAction1 (classConfiguration, 0, L"Draw sigma ellipses...", L"Draw...", 1, DO_Configuration_drawSigmaEllipses); praat_addAction1 (classConfiguration, 0, L"Draw one sigma ellipse...", L"Draw...", 1, DO_Configuration_drawOneSigmaEllipse); praat_addAction1 (classConfiguration, 0, L"Draw confidence ellipses...", L"Draw sigma ellipses...", 1, DO_Configuration_drawConfidenceEllipses); praat_addAction1 (classConfiguration, 0, L"Draw one confidence ellipse...", L"Draw sigma ellipses...", 1, DO_Configuration_drawOneConfidenceEllipse); praat_addAction1 (classConfiguration, 0, L"Randomize", L"Normalize table...", 1, DO_Configuration_randomize); praat_addAction1 (classConfiguration, 0, L"Normalize...", L"Randomize", 1, DO_Configuration_normalize); praat_addAction1 (classConfiguration, 0, L"Centralize", L"Randomize", 1, DO_Configuration_centralize); praat_addAction1 (classConfiguration, 1, L"-- set rotations & reflections --", L"Centralize", 1, 0); praat_addAction1 (classConfiguration, 0, L"Rotate...", L"-- set rotations & reflections --", 1, DO_Configuration_rotate); praat_addAction1 (classConfiguration, 0, L"Rotate (pc)", L"Rotate...", 1, DO_Configuration_rotateToPrincipalDirections); praat_addAction1 (classConfiguration, 0, L"Invert dimension...", L"Rotate (pc)", 1, DO_Configuration_invertDimension); praat_addAction1 (classConfiguration, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classConfiguration, 0, L"To Distance", 0, 0, DO_Configuration_to_Distance); praat_addAction1 (classConfiguration, 0, L"To Configuration (varimax)...", 0, 0, DO_Configuration_varimax); praat_addAction1 (classConfiguration, 0, L"To Similarity (cc)", 0, 0, DO_Configurations_to_Similarity_cc); praat_addAction1 (classConfiguration, 0, L"Match configurations -", 0, 0, 0); praat_addAction1 (classConfiguration, 2, L"To Procrustes...", 0, 1, DO_Configurations_to_Procrustes); praat_addAction1 (classConfiguration, 2, L"To AffineTransform (congruence)...", 0, 1, DO_Configurations_to_AffineTransform_congruence); praat_addAction1 (classConfusion, 0, L"To ContingencyTable", L"To Matrix", 0, DO_Confusion_to_ContingencyTable); praat_addAction1 (classConfusion, 0, L"To Proximity -", L"Analyse", 0, 0); praat_addAction1 (classConfusion, 0, L"To Dissimilarity (pdf)...", L"To Proximity -", 1, DO_Confusion_to_Dissimilarity_pdf); praat_addAction1 (classConfusion, 0, L"To Similarity...", L"To Proximity -", 1, DO_Confusion_to_Similarity); praat_addAction1 (classConfusion, 0, L"Sum", L"Synthesize -", 1, DO_Confusions_sum); praat_TableOfReal_init2 (classContingencyTable); praat_addAction1 (classContingencyTable, 1, L"-- statistics --", L"Get value...", 1, 0); praat_addAction1 (classContingencyTable, 1, L"Get chi squared probability", L"-- statistics --", 1, DO_ContingencyTable_chisqProbability); praat_addAction1 (classContingencyTable, 1, L"Get Cramer's statistic", L"Get chi squared probability", 1, DO_ContingencyTable_cramersStatistic); praat_addAction1 (classContingencyTable, 1, L"Get contingency coefficient", L"Get Cramer's statistic", 1, DO_ContingencyTable_contingencyCoefficient); praat_addAction1 (classContingencyTable, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classContingencyTable, 1, L"To Configuration (ca)...", 0, 0, DO_ContingencyTable_to_Configuration_ca); praat_addAction1 (classCorrelation, 0, L"To Configuration...", 0, 0, DO_Correlation_to_Configuration); praat_addAction1 (classDissimilarity, 0, L"Dissimilarity help", 0, 0, DO_Dissimilarity_help); praat_TableOfReal_init2 (classDissimilarity); praat_TableOfReal_extras (classDissimilarity); praat_addAction1 (classDissimilarity, 0, L"Get additive constant", L"Get table norm", 1, DO_Dissimilarity_getAdditiveConstant); praat_addAction1 (classDissimilarity, 0, CONFIGURATION_BUTTON, 0, 0, 0); praat_addAction1 (classDissimilarity, 1, L"To Configuration (monotone mds)...", 0, 1, DO_Dissimilarity_monotone_mds); praat_addAction1 (classDissimilarity, 1, L"To Configuration (i-spline mds)...", 0, 1, DO_Dissimilarity_ispline_mds); praat_addAction1 (classDissimilarity, 1, L"To Configuration (interval mds)...", 0, 1, DO_Dissimilarity_interval_mds); praat_addAction1 (classDissimilarity, 1, L"To Configuration (ratio mds)...", 0, 1, DO_Dissimilarity_ratio_mds); praat_addAction1 (classDissimilarity, 1, L"To Configuration (absolute mds)...", 0, 1, DO_Dissimilarity_absolute_mds); praat_addAction1 (classDissimilarity, 1, L"To Configuration (kruskal)...", 0, 1, DO_Dissimilarity_kruskal); praat_addAction1 (classDissimilarity, 0, L"To Distance...", 0, 0, DO_Dissimilarity_to_Distance); praat_addAction1 (classDissimilarity, 0, L"To Weight", 0, 0, DO_Dissimilarity_to_Weight); praat_addAction1 (classCovariance, 0, L"To Configuration...", 0, 0, DO_Covariance_to_Configuration); praat_TableOfReal_init2 (classDistance); praat_TableOfReal_extras (classDistance); praat_addAction1 (classDistance, 0, L"Analyse -", 0, 0, 0); praat_addAction1 (classDistance, 0, CONFIGURATION_BUTTON, 0, 0, 0); praat_addAction1 (classDistance, 0, L"To Configuration (indscal)...", 0, 1, DO_Distances_indscal); praat_addAction1 (classDistance, 0, L"-- linear scaling --", 0, 1, 0); praat_addAction1 (classDistance, 0, L"To Configuration (ytl)...", 0, 1, DO_Distances_to_Configuration_ytl); praat_addAction1 (classDistance, 0, L"To Dissimilarity", 0, 0, DO_Distance_to_Dissimilarity); praat_addAction1 (classDistance, 0, L"To ScalarProduct...", 0, 0, DO_Distance_to_ScalarProduct); praat_addAction1 (classProcrustes, 0, L"Procrustes help", 0, 0, DO_Procrustes_help); praat_AffineTransform_init (classProcrustes); praat_addAction1 (classProcrustes, 1, L"Get scale", QUERY_BUTTON, 1, DO_Procrustes_getScale); praat_addAction1 (classProcrustes, 0, L"Extract transformation matrix", 0, 0, DO_AffineTransform_extractMatrix); praat_addAction1 (classProcrustes, 0, L"Extract translation vector", 0, 0, DO_AffineTransform_extractTranslationVector); praat_TableOfReal_init2 (classSalience); praat_TableOfReal_extras (classSalience); praat_addAction1 (classSalience, 0, L"Draw...", DRAW_BUTTON, 1, DO_Salience_draw); praat_addAction1 (classSimilarity, 0, L"Similarity help", 0, 0, DO_Similarity_help); praat_TableOfReal_init2 (classSimilarity); praat_TableOfReal_extras (classSimilarity); praat_addAction1 (classSimilarity, 0, L"Analyse -", 0, 0, 0); praat_addAction1 (classSimilarity, 0, L"To Dissimilarity...", 0, 0, DO_Similarity_to_Dissimilarity); praat_TableOfReal_init2 (classScalarProduct); praat_TableOfReal_extras (classScalarProduct); praat_TableOfReal_extras (classTableOfReal); praat_addAction1 (classTableOfReal, 1, L"Centre rows", L"Normalize table...", 1, DO_TableOfReal_centreRows); praat_addAction1 (classTableOfReal, 1, L"Centre columns", L"Centre rows", 1, DO_TableOfReal_centreColumns); praat_addAction1 (classTableOfReal, 1, L"Double centre", L"Centre columns", 1, DO_TableOfReal_doubleCentre); praat_addAction1 (classTableOfReal, 0, L"Cast -", 0, 0, 0); praat_addAction1 (classTableOfReal, 0, L"To Confusion", 0, 1, DO_TableOfReal_to_Confusion); praat_addAction1 (classTableOfReal, 0, L"To Dissimilarity", 0, 1, DO_TableOfReal_to_Dissimilarity); praat_addAction1 (classTableOfReal, 0, L"To Similarity", 0, 1, DO_TableOfReal_to_Similarity); praat_addAction1 (classTableOfReal, 0, L"To Distance", 0, 1, DO_TableOfReal_to_Distance); praat_addAction1 (classTableOfReal, 0, L"To Salience", 0, 1, DO_TableOfReal_to_Salience); praat_addAction1 (classTableOfReal, 0, L"To Weight", 0, 1, DO_TableOfReal_to_Weight); praat_addAction1 (classTableOfReal, 0, L"To ScalarProduct", 0, 1, DO_TableOfReal_to_ScalarProduct); praat_addAction1 (classTableOfReal, 0, L"To Configuration", 0, 1, DO_TableOfReal_to_Configuration); praat_addAction1 (classTableOfReal, 0, L"To ContingencyTable", 0, 1, DO_TableOfReal_to_ContingencyTable); praat_TableOfReal_init2 (classWeight); /****** 2 classes ********************************************************/ praat_Configuration_and_AffineTransform_init (classAffineTransform); praat_Configuration_and_AffineTransform_init (classProcrustes); praat_addAction2 (classConfiguration, 0, classWeight, 1, L"Analyse", 0, 0, 0); praat_addAction2 (classConfiguration, 0, classWeight, 1, L"To Similarity (cc)", 0, 0, DO_Configuration_Weight_to_Similarity_cc); praat_addAction2 (classDissimilarity, 1, classWeight, 1, ANALYSE_BUTTON, 0, 0, 0); praat_addAction2 (classDissimilarity, 1, classWeight, 1, L"To Configuration (monotone mds)...", 0, 1, DO_Dissimilarity_Weight_monotone_mds); praat_addAction2 (classDissimilarity, 1, classWeight, 1, L"To Configuration (i-spline mds)...", 0, 1, DO_Dissimilarity_Weight_ispline_mds); praat_addAction2 (classDissimilarity, 1, classWeight, 1, L"To Configuration (interval mds)...", 0, 1, DO_Dissimilarity_Weight_interval_mds); praat_addAction2 (classDissimilarity, 1, classWeight, 1, L"To Configuration (ratio mds)...", 0, 1, DO_Dissimilarity_Weight_ratio_mds); praat_addAction2 (classDissimilarity, 1, classWeight, 1, L"To Configuration (absolute mds)...", 0, 1, DO_Dissimilarity_Weight_absolute_mds); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, DRAW_BUTTON, 0, 0, 0); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Draw Shepard diagram...", 0, 1, DO_Dissimilarity_Configuration_drawShepardDiagram); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"-- draw regressions --", 0, 1, 0); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Draw monotone regression...", 0, 1, DO_Dissimilarity_Configuration_drawMonotoneRegression); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Draw i-spline regression...", 0, 1, DO_Dissimilarity_Configuration_drawISplineRegression); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Draw interval regression...", 0, 1, DO_Dissimilarity_Configuration_drawIntervalRegression); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Draw ratio regression...", 0, 1, DO_Dissimilarity_Configuration_drawRatioRegression); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Draw absolute regression...", 0, 1, DO_Dissimilarity_Configuration_drawAbsoluteRegression); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, QUERY_BUTTON, 0, 0, 0); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Get stress...", 0, 1, DO_Dissimilarity_Configuration_getStress); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Get stress (monotone mds)...", 0, 1, DO_Dissimilarity_Configuration_monotone_stress); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Get stress (i-spline mds)...", 0, 1, DO_Dissimilarity_Configuration_ispline_stress); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Get stress (interval mds)...", 0, 1, DO_Dissimilarity_Configuration_interval_stress); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Get stress (ratio mds)...", 0, 1, DO_Dissimilarity_Configuration_ratio_stress); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"Get stress (absolute mds)...", 0, 1, DO_Dissimilarity_Configuration_absolute_stress); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, ANALYSE_BUTTON, 0, 0, 0); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"To Configuration (monotone mds)...", 0, 1, DO_Dissimilarity_Configuration_monotone_mds); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"To Configuration (i-spline mds)...", 0, 1, DO_Dissimilarity_Configuration_ispline_mds); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"To Configuration (interval mds)...", 0, 1, DO_Dissimilarity_Configuration_interval_mds); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"To Configuration (ratio mds)...", 0, 1, DO_Dissimilarity_Configuration_ratio_mds); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"To Configuration (absolute mds)...", 0, 1, DO_Dissimilarity_Configuration_absolute_mds); praat_addAction2 (classDissimilarity, 1, classConfiguration, 1, L"To Configuration (kruskal)...", 0, 1, DO_Dissimilarity_Configuration_kruskal); praat_addAction2 (classDistance, 1, classConfiguration, 1, DRAW_BUTTON, 0, 0, 0); praat_addAction2 (classDistance, 1, classConfiguration, 1, L"Draw scatter diagram...", 0, 0, DO_Distance_and_Configuration_drawScatterDiagram); praat_addAction2 (classDistance, 1, classConfiguration, 1, QUERY_BUTTON, 0, 0, 0); praat_addAction2 (classDistance, 0, classConfiguration, 1, L"Get VAF...", 0, 0, DO_Distance_Configuration_vaf); praat_addAction2 (classDistance, 1, classConfiguration, 1, ANALYSE_BUTTON, 0, 0, 0); praat_addAction2 (classDistance, 0, classConfiguration, 1, L"To Configuration (indscal)...", 0, 1, DO_Distance_Configuration_indscal); praat_addAction2 (classDistance, 1, classDissimilarity, 1, L"Draw Shepard diagram...", 0, 0, DO_Distance_Dissimilarity_drawShepardDiagram); praat_addAction2 (classDissimilarity, 1, classDistance, 1, L"Monotone regression...", 0, 0, DO_Dissimilarity_Distance_monotoneRegression); /****** 3 classes ********************************************************/ praat_addAction3 (classDissimilarity, 0, classConfiguration, 1, classSalience, 1, QUERY_BUTTON, 0, 0, 0); praat_addAction3 (classDissimilarity, 0, classConfiguration, 1, classSalience, 1, L"Get VAF...", 0, 1, DO_Dissimilarity_Configuration_Salience_vaf); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, QUERY_BUTTON, 0, 0, 0); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"Get stress (monotone mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_monotone_stress); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"Get stress (i-spline mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_ispline_stress); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"Get stress (interval mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_interval_stress); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"Get stress (ratio mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_ratio_stress); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"Get stress (absolute mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_absolute_stress); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, ANALYSE_BUTTON, 0, 0, 0); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"To Configuration (monotone mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_monotone_mds); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"To Configuration (i-spline mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_ispline_mds); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"To Configuration (interval mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_interval_mds); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"To Configuration (ratio mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_ratio_mds); praat_addAction3 (classDissimilarity, 1, classConfiguration, 1, classWeight, 1, L"To Configuration (absolute mds)...", 0, 1, DO_Dissimilarity_Configuration_Weight_absolute_mds); praat_addAction3 (classDistance, 0, classConfiguration, 1, classSalience, 1, QUERY_BUTTON, 0, 0, 0); praat_addAction3 (classDistance, 0, classConfiguration, 1, classSalience, 1, L"Get VAF...", 0, 1, DO_Distance_Configuration_Salience_vaf); praat_addAction3 (classDistance, 0, classConfiguration, 1, classSalience, 1, L"Analyse", 0, 0, 0); praat_addAction3 (classDistance, 0, classConfiguration, 1, classSalience, 1, L"To Configuration (indscal)...", 0, 0, DO_Distance_Configuration_Salience_indscal); INCLUDE_MANPAGES (manual_MDS_init) } /* End of file praat_MDS_init.c 1775*/ sources_5316/dwtools/Table_extensions.cpp0000644000176700017670000032356711737406057017462 0ustar paulpaul/* Table_extensions.cpp * * Copyright (C) 1997-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020619 GPL header djmw 20040113 Added comment header for Peterson&Barney data. djmw 20040512 Corrected Peterson&Barney ARPABET-labeling. djmw 20041213 Added Table_createFromWeeninkData. djmw 20080125 Corrected mislabeling of vowels in the Peterson&Barney dataset according to Watrous djmw 20080508 Labeling back to original PB article. djmw 20110329 Table_get(Numeric|String)Value is now Table_get(Numeric|String)Value_Assert */ /* speaker type (m|w|c), sex(m|f), id, vowel_number, vowel_label F0, F1, F2, F3 */ #include "Table_extensions.h" #include "GraphicsP.h" #include "NUM2.h" /* The Peterson & Barney data were once (1991) obtained by me (djmw) as a compressed tar-file by anonymous ftp from ftp://linc.cis.upenn.edu/pub, However, this site appears no longer to be an anonymous ftp site. The compressed tar file contained two files: a header file 'pb.header' and a data file 'verified_pb.data'. The header file reads: "This file contains the vowel formant data reported by Gordon E. Peterson and Harold L. Barney in their classic paper, "Control methods used in a study of the vowels", JASA 24(2) 175-184, 1952. This data was supplied in printed form by Ignatius Mattingly, April, 1990. The data consists of the formant values F0, F1, F2, and F3 for each of two repetitions of ten vowels by 76 speakers (1520 utterances). The vowels were pronounced in isolated words consisting of hVd. Of the speakers, 33 were men, 28 were women and 15 were children. Dr. Mattingly reported that he obtained from G. Peterson the information that children speakers 62, 63, 65, 66, 67, 68, 73 and 76 were female. The data are organized by speaker type, speaker, and vowel into 1520 lines of 8 fields. The fields are: Speaker Type, Speaker Number, Phoneme Number, Phoneme Label, F0, F1, F2 and F3. The speaker types are type 1 (men), type 2 (women) and type 3 (children)." */ Table Table_createFromPetersonBarneyData () { long nrows = 1520, ncols = 9; const wchar_t *columnLabels[9] = {L"Type", L"Sex", L"Speaker", L"Vowel", L"IPA", L"F0", L"F1", L"F2", L"F3"}; const wchar_t *type[3] = {L"m", L"w", L"c"}; // Wrong order before 20080125 // wchar_t *vowel[10] = {L"iy", L"ih", L"eh", L"ae", L"aa", L"ao", L"uh", L"uw", L"ah", L"er"}; // wchar_t *ipa[10] = {L"i", L"\\ic", L"\\ep", L"\\ae", L"\\as", L"\\ct", L"\\hs", L"u", // L"\\vt", L"\\er\\hr"}; const wchar_t *vowel[10] = {L"iy", L"ih", L"eh", L"ae", L"ah", L"aa", L"ao", L"uh", L"uw", L"er"}; // Watrous IPA symbols // wchar_t *ipa[10] = {L"i", L"\\ic", L"e", L"\\ae", L"\\vt", L"\\as", L"o", L"\\hs", L"u", L"\\er"}; // P&B IPA symbols const wchar_t *ipa[10] = {L"i", L"\\ic", L"\\ef", L"\\ae", L"\\vt", L"\\as", L"\\ct", L"\\hs", L"u", L"\\er\\hr"}; const wchar_t *sex[2] = {L"m", L"f"}; struct pbdatum { short star; /* was there a * in front of the vowel-type? */ short f[4]; /* f0, f1, f2, f3 */ } pbdata [] = { {0, {160, 240, 2280, 2850}}, {0, {186, 280, 2400, 2790}}, {0, {203, 390, 2030, 2640}}, {0, {192, 310, 1980, 2550}}, {0, {161, 490, 1870, 2420}}, {1, {155, 570, 1700, 2600}}, {1, {140, 560, 1820, 2660}}, {0, {180, 630, 1700, 2550}}, {0, {144, 590, 1250, 2620}}, {0, {148, 620, 1300, 2530}}, {0, {148, 740, 1070, 2490}}, {0, {170, 800, 1060, 2640}}, {1, {161, 600, 970, 2280}}, {1, {158, 660, 980, 2220}}, {0, {163, 440, 1120, 2210}}, {0, {190, 400, 1070, 2280}}, {0, {160, 240, 1040, 2150}}, {0, {157, 270, 930, 2280}}, {0, {177, 370, 1520, 1670}}, {0, {164, 460, 1330, 1590}}, {0, {147, 220, 2220, 2910}}, {0, {148, 210, 2360, 3250}}, {0, {141, 410, 1890, 2680}}, {0, {139, 420, 1850, 2500}}, {0, {136, 500, 1760, 2590}}, {1, {135, 510, 1710, 2380}}, {0, {128, 690, 1610, 2560}}, {0, {131, 700, 1690, 2580}}, {1, {140, 650, 1080, 2420}}, {1, {125, 625, 1060, 2490}}, {0, {140, 650, 1040, 2450}}, {0, {136, 670, 1100, 2430}}, {0, {149, 580, 580, 2470}}, {0, {140, 560, 560, 2410}}, {0, {145, 450, 940, 1910}}, {0, {141, 410, 830, 2240}}, {0, {140, 280, 650, 3300}}, {0, {137, 260, 660, 3300}}, {0, {145, 510, 1210, 1570}}, {0, {145, 510, 1130, 1510}}, {0, {105, 250, 2180, 2680}}, {0, {111, 244, 2300, 2780}}, {0, {100, 400, 1930, 2610}}, {0, {104, 400, 1990, 2700}}, {0, {100, 550, 1810, 2500}}, {0, {95, 540, 1810, 2480}}, {0, {93, 630, 1710, 2400}}, {0, {94, 658, 1755, 2305}}, {1, {100, 600, 1200, 2320}}, {0, {105, 612, 1160, 2350}}, {0, {91, 640, 1080, 2140}}, {0, {94, 720, 1090, 2230}}, {0, {92, 550, 870, 2300}}, {0, {120, 540, 840, 2280}}, {0, {114, 460, 1150, 2290}}, {0, {114, 456, 1030, 2300}}, {0, {112, 340, 950, 2240}}, {1, {112, 326, 900, 2190}}, {0, {100, 500, 1370, 1780}}, {0, {106, 530, 1330, 1800}}, {0, {150, 300, 2240, 3400}}, {0, {156, 280, 2450, 3200}}, {1, {156, 450, 1960, 2400}}, {0, {146, 440, 2050, 2360}}, {0, {130, 570, 1780, 2410}}, {0, {150, 555, 1890, 2440}}, {0, {125, 750, 1610, 2340}}, {0, {136, 770, 1580, 2350}}, {0, {132, 660, 1200, 2330}}, {1, {150, 675, 1140, 2380}}, {0, {125, 750, 1100, 2550}}, {0, {138, 800, 1120, 2500}}, {0, {143, 540, 850, 2320}}, {0, {150, 555, 890, 2370}}, {0, {136, 460, 960, 2210}}, {0, {156, 460, 1000, 2350}}, {0, {140, 380, 950, 2050}}, {0, {148, 385, 850, 2330}}, {0, {150, 590, 1400, 1840}}, {0, {145, 555, 1430, 1730}}, {0, {140, 310, 2310, 2820}}, {0, {131, 260, 2250, 2850}}, {0, {137, 440, 2060, 2640}}, {0, {134, 430, 1880, 2450}}, {0, {140, 580, 1910, 2500}}, {0, {137, 550, 1770, 2400}}, {0, {143, 830, 1720, 2180}}, {0, {135, 750, 1690, 2320}}, {0, {136, 630, 1300, 1950}}, {0, {130, 650, 1170, 2000}}, {0, {131, 760, 1220, 2140}}, {1, {126, 720, 1260, 2020}}, {0, {136, 540, 970, 1980}}, {0, {124, 550, 880, 1950}}, {0, {133, 470, 1040, 1990}}, {0, {132, 490, 990, 1920}}, {0, {141, 380, 950, 2140}}, {0, {133, 330, 800, 2130}}, {0, {143, 560, 1510, 1800}}, {0, {136, 510, 1460, 1700}}, {0, {125, 312, 2350, 2800}}, {0, {119, 330, 2430, 2870}}, {0, {133, 420, 2000, 2660}}, {0, {125, 313, 2000, 2750}}, {0, {120, 600, 1860, 2500}}, {0, {114, 570, 1830, 2570}}, {0, {119, 676, 1670, 2540}}, {0, {125, 725, 1687, 2500}}, {1, {118, 680, 1150, 2560}}, {0, {125, 726, 1270, 2560}}, {0, {125, 740, 1100, 2680}}, {1, {113, 670, 960, 2650}}, {1, {120, 660, 1030, 2690}}, {1, {125, 720, 960, 2700}}, {0, {120, 456, 1080, 2520}}, {0, {120, 450, 1140, 2600}}, {0, {125, 313, 838, 2340}}, {0, {125, 288, 938, 2450}}, {0, {120, 503, 1305, 1775}}, {0, {120, 505, 1320, 1750}}, {0, {186, 320, 2320, 3120}}, {0, {172, 310, 2280, 3020}}, {1, {167, 470, 2000, 2660}}, {0, {170, 410, 2040, 2715}}, {1, {167, 630, 1900, 2860}}, {0, {146, 614, 1840, 2770}}, {0, {143, 740, 1800, 2450}}, {0, {162, 775, 1810, 2200}}, {1, {167, 620, 1240, 2410}}, {0, {160, 640, 1250, 2400}}, {1, {162, 650, 970, 2580}}, {0, {163, 650, 980, 2350}}, {0, {145, 430, 720, 2450}}, {0, {171, 510, 800, 2500}}, {1, {170, 460, 1120, 2150}}, {1, {170, 493, 1120, 2300}}, {0, {175, 380, 1040, 2260}}, {1, {200, 400, 1000, 2350}}, {0, {167, 570, 1300, 1750}}, {0, {157, 565, 1370, 1710}}, {1, {105, 230, 2480, 3200}}, {0, {109, 218, 2380, 3100}}, {1, {110, 320, 2200, 2680}}, {0, {103, 206, 2130, 2570}}, {1, {107, 430, 2100, 2630}}, {1, {105, 515, 1760, 2470}}, {1, {107, 514, 2060, 2600}}, {1, {106, 552, 1820, 2500}}, {0, {108, 640, 1300, 2300}}, {0, {104, 624, 1350, 2410}}, {1, {111, 714, 1170, 2420}}, {1, {97, 650, 1150, 2350}}, {1, {107, 590, 965, 2500}}, {0, {109, 578, 970, 2460}}, {0, {111, 467, 1110, 2400}}, {0, {105, 475, 1220, 2310}}, {0, {107, 270, 910, 2200}}, {0, {108, 260, 975, 2320}}, {0, {107, 460, 1400, 1790}}, {0, {103, 425, 1410, 1760}}, {0, {175, 316, 2200, 2800}}, {0, {175, 280, 2275, 2775}}, {0, {167, 450, 1820, 2475}}, {0, {167, 434, 1850, 2425}}, {0, {157, 582, 1725, 2375}}, {0, {158, 586, 1800, 2425}}, {0, {150, 600, 1750, 2375}}, {1, {145, 582, 1775, 2375}}, {1, {145, 626, 1125, 2200}}, {0, {160, 641, 1120, 2225}}, {0, {144, 708, 1054, 2420}}, {1, {150, 705, 1050, 2375}}, {0, {146, 614, 848, 2200}}, {0, {143, 600, 860, 2175}}, {0, {167, 500, 1000, 2325}}, {0, {167, 500, 1000, 2325}}, {0, {167, 334, 1150, 2200}}, {0, {183, 312, 1020, 2300}}, {0, {157, 518, 1305, 1570}}, {0, {157, 504, 1210, 1510}}, {0, {129, 260, 2260, 2820}}, {0, {125, 250, 2200, 2825}}, {0, {146, 400, 2040, 2500}}, {0, {144, 389, 2000, 2425}}, {0, {126, 500, 1870, 2500}}, {0, {125, 500, 1775, 2450}}, {0, {110, 660, 1650, 2500}}, {0, {120, 624, 1700, 2475}}, {0, {122, 650, 1220, 2550}}, {0, {120, 672, 1260, 2500}}, {0, {114, 750, 1080, 2680}}, {0, {114, 777, 1026, 2625}}, {0, {115, 580, 800, 2650}}, {0, {117, 585, 819, 2625}}, {1, {140, 480, 950, 2500}}, {0, {127, 461, 993, 2350}}, {0, {140, 280, 950, 2300}}, {0, {133, 266, 920, 2300}}, {0, {128, 500, 1340, 1700}}, {0, {133, 532, 1275, 1600}}, {0, {146, 248, 2225, 3100}}, {0, {140, 238, 2175, 3075}}, {0, {150, 405, 1925, 2550}}, {0, {138, 416, 1940, 2600}}, {1, {147, 588, 1790, 2500}}, {1, {133, 586, 1725, 2650}}, {0, {145, 725, 1700, 2425}}, {0, {127, 710, 1650, 2220}}, {1, {136, 586, 1078, 2300}}, {0, {136, 627, 1038, 2360}}, {1, {145, 725, 1046, 2325}}, {1, {131, 746, 1018, 2300}}, {0, {140, 560, 840, 2500}}, {1, {140, 560, 924, 2350}}, {0, {150, 495, 1080, 2275}}, {0, {143, 430, 1030, 2275}}, {0, {162, 290, 760, 2300}}, {0, {157, 315, 850, 2025}}, {0, {150, 511, 1561, 1876}}, {0, {138, 530, 1450, 1887}}, {0, {110, 220, 2410, 3000}}, {0, {125, 240, 2440, 3280}}, {0, {120, 450, 1880, 2450}}, {0, {118, 380, 1930, 2420}}, {0, {115, 560, 1650, 2300}}, {0, {123, 560, 1720, 2300}}, {0, {110, 680, 1720, 2330}}, {0, {133, 630, 1680, 2280}}, {1, {110, 560, 1430, 2250}}, {1, {120, 560, 1390, 2240}}, {1, {108, 800, 1330, 2260}}, {0, {110, 740, 1240, 2280}}, {1, {120, 600, 920, 2080}}, {1, {133, 580, 910, 2000}}, {0, {130, 400, 1200, 2210}}, {0, {110, 420, 1230, 2230}}, {0, {122, 300, 900, 2130}}, {0, {123, 260, 1010, 2240}}, {0, {125, 400, 1450, 1650}}, {0, {128, 360, 1410, 1640}}, {0, {142, 290, 2290, 2600}}, {0, {135, 260, 2290, 2700}}, {0, {132, 390, 1950, 2550}}, {1, {135, 400, 1900, 2450}}, {1, {124, 490, 1740, 2500}}, {1, {125, 500, 1780, 2430}}, {0, {125, 660, 1630, 2500}}, {0, {132, 670, 1630, 2380}}, {0, {140, 600, 1220, 2530}}, {0, {125, 600, 1210, 2430}}, {1, {125, 680, 1120, 2630}}, {0, {128, 670, 1100, 2700}}, {0, {127, 510, 720, 2450}}, {0, {120, 480, 710, 2540}}, {1, {133, 380, 910, 2350}}, {0, {140, 440, 1030, 2400}}, {0, {127, 350, 720, 2750}}, {0, {140, 380, 740, 2880}}, {0, {128, 430, 1370, 1610}}, {0, {135, 440, 1360, 1600}}, {0, {114, 228, 2350, 2860}}, {0, {118, 220, 2350, 2920}}, {1, {110, 407, 2070, 2500}}, {1, {112, 420, 1900, 2450}}, {0, {106, 445, 2020, 2420}}, {0, {115, 470, 2020, 2500}}, {0, {103, 721, 1680, 2400}}, {0, {109, 750, 1710, 2440}}, {1, {104, 552, 1122, 2500}}, {1, {115, 580, 1150, 2600}}, {0, {98, 686, 1078, 2570}}, {1, {103, 700, 1050, 2680}}, {0, {102, 560, 665, 2620}}, {0, {106, 550, 650, 2700}}, {0, {112, 448, 980, 2370}}, {0, {104, 410, 940, 2370}}, {0, {116, 232, 696, 2200}}, {0, {117, 222, 665, 2080}}, {0, {120, 432, 1300, 1400}}, {0, {111, 420, 1300, 1570}}, {0, {121, 230, 2100, 2850}}, {0, {118, 240, 2000, 2980}}, {0, {130, 365, 1900, 2340}}, {0, {119, 300, 2040, 2560}}, {1, {112, 440, 1980, 2310}}, {1, {120, 410, 2050, 2500}}, {1, {133, 620, 1710, 2110}}, {0, {124, 660, 1800, 2150}}, {0, {120, 660, 1000, 2380}}, {0, {110, 660, 960, 2450}}, {1, {122, 600, 830, 2250}}, {1, {119, 620, 820, 2400}}, {0, {117, 500, 620, 2250}}, {0, {106, 550, 700, 2550}}, {0, {140, 390, 730, 2180}}, {0, {130, 360, 740, 2200}}, {0, {131, 260, 720, 2100}}, {0, {132, 260, 740, 2040}}, {0, {125, 450, 1230, 1600}}, {0, {127, 460, 1300, 1650}}, {0, {150, 300, 2355, 3250}}, {0, {150, 300, 2460, 3280}}, {0, {160, 385, 2242, 2805}}, {0, {150, 407, 2250, 2780}}, {0, {140, 504, 2090, 2720}}, {0, {146, 543, 1980, 2640}}, {0, {133, 680, 1958, 2542}}, {0, {141, 708, 1840, 2535}}, {0, {150, 675, 1320, 2550}}, {0, {150, 704, 1393, 2550}}, {0, {137, 825, 1168, 2750}}, {0, {135, 840, 1210, 2680}}, {1, {143, 671, 1000, 2670}}, {1, {147, 690, 968, 2660}}, {0, {143, 443, 1273, 2430}}, {0, {153, 459, 1286, 2410}}, {0, {146, 395, 1300, 2160}}, {0, {153, 400, 1320, 2150}}, {0, {140, 532, 1500, 1890}}, {0, {146, 538, 1460, 1818}}, {0, {120, 264, 2290, 2700}}, {0, {128, 256, 2305, 2635}}, {0, {112, 380, 1880, 2440}}, {0, {115, 346, 1930, 2390}}, {0, {100, 510, 1780, 2300}}, {0, {108, 520, 1730, 2275}}, {0, {100, 630, 1770, 2350}}, {0, {105, 630, 1642, 2170}}, {0, {103, 601, 1273, 2130}}, {1, {105, 590, 1283, 2150}}, {1, {100, 750, 1150, 2440}}, {0, {95, 703, 1092, 2320}}, {0, {97, 565, 780, 2350}}, {0, {106, 584, 849, 2460}}, {0, {105, 420, 1100, 2140}}, {0, {111, 422, 1200, 2175}}, {0, {117, 315, 1080, 2260}}, {0, {125, 326, 1125, 2210}}, {0, {111, 444, 1300, 1625}}, {0, {109, 469, 1288, 1600}}, {0, {124, 210, 2100, 3090}}, {0, {130, 220, 2080, 3180}}, {0, {128, 280, 2000, 2710}}, {0, {130, 310, 1950, 2670}}, {0, {121, 470, 1910, 2580}}, {1, {129, 490, 1930, 2650}}, {0, {116, 640, 1620, 2200}}, {0, {118, 650, 1580, 2360}}, {0, {121, 610, 1100, 2230}}, {0, {126, 620, 1120, 2330}}, {1, {118, 700, 1100, 2240}}, {1, {120, 670, 1100, 2220}}, {0, {122, 460, 720, 2180}}, {0, {118, 470, 690, 2200}}, {0, {129, 320, 770, 1860}}, {1, {130, 310, 790, 1920}}, {0, {140, 210, 670, 1900}}, {0, {148, 240, 730, 1850}}, {0, {128, 390, 1320, 1550}}, {0, {124, 420, 1240, 1510}}, {0, {129, 190, 2650, 3280}}, {0, {135, 190, 2700, 3170}}, {0, {132, 370, 1750, 2700}}, {0, {130, 370, 1800, 2750}}, {1, {122, 370, 1680, 2560}}, {1, {125, 375, 1700, 2500}}, {1, {121, 550, 1570, 2600}}, {1, {120, 530, 1610, 2650}}, {1, {118, 570, 1050, 2500}}, {1, {125, 590, 1100, 2480}}, {1, {112, 640, 970, 2870}}, {1, {122, 670, 980, 2900}}, {1, {113, 560, 860, 2900}}, {0, {121, 570, 820, 2820}}, {1, {125, 350, 1000, 2500}}, {1, {130, 380, 920, 2370}}, {0, {130, 250, 1000, 2100}}, {0, {140, 210, 960, 1940}}, {0, {130, 360, 1300, 1920}}, {0, {133, 370, 1300, 1760}}, {0, {127, 250, 2180, 2660}}, {0, {131, 260, 2210, 2780}}, {0, {121, 400, 1900, 2440}}, {0, {122, 350, 1980, 2480}}, {1, {116, 560, 1670, 2310}}, {1, {124, 530, 1700, 2380}}, {0, {120, 680, 1470, 2280}}, {0, {119, 620, 1580, 2320}}, {0, {120, 620, 1100, 2390}}, {1, {125, 640, 1110, 2370}}, {1, {115, 630, 980, 2330}}, {1, {121, 670, 940, 2380}}, {0, {112, 560, 790, 2480}}, {0, {120, 610, 840, 2420}}, {0, {121, 360, 860, 2200}}, {0, {120, 400, 840, 2200}}, {0, {140, 280, 670, 2140}}, {0, {126, 250, 720, 2190}}, {0, {120, 480, 1410, 1760}}, {0, {121, 470, 1330, 1700}}, {0, {155, 280, 2400, 2910}}, {0, {150, 300, 2320, 2960}}, {1, {142, 410, 2060, 2680}}, {0, {150, 450, 2050, 2670}}, {0, {135, 540, 1900, 2530}}, {0, {135, 540, 1920, 2520}}, {0, {138, 620, 1800, 2440}}, {0, {140, 690, 1820, 2480}}, {1, {150, 630, 1200, 2600}}, {0, {140, 680, 1290, 2600}}, {0, {145, 740, 1110, 2500}}, {1, {143, 700, 1060, 2720}}, {1, {146, 600, 970, 2570}}, {0, {138, 650, 880, 2660}}, {0, {142, 430, 1130, 2440}}, {0, {143, 430, 1150, 2420}}, {0, {142, 280, 990, 2330}}, {0, {145, 290, 1000, 2300}}, {0, {150, 420, 1350, 1600}}, {0, {150, 450, 1350, 1600}}, {0, {135, 300, 2300, 2800}}, {0, {135, 350, 2240, 2760}}, {1, {136, 410, 2200, 2680}}, {1, {138, 440, 2080, 2520}}, {1, {133, 580, 1870, 2320}}, {1, {127, 520, 1900, 2400}}, {0, {130, 760, 1920, 2480}}, {0, {132, 670, 1850, 2560}}, {1, {139, 810, 1110, 2100}}, {1, {131, 770, 1150, 2100}}, {1, {141, 700, 1040, 2120}}, {0, {125, 750, 1160, 2080}}, {1, {133, 670, 920, 2240}}, {1, {142, 570, 850, 2250}}, {0, {140, 550, 970, 2200}}, {1, {141, 490, 870, 2240}}, {0, {150, 300, 600, 2300}}, {0, {148, 230, 570, 2100}}, {0, {140, 560, 1520, 2100}}, {0, {140, 540, 1570, 2050}}, {0, {125, 240, 2100, 2900}}, {0, {119, 240, 2150, 2860}}, {0, {130, 380, 1870, 2450}}, {0, {120, 430, 1710, 2350}}, {1, {119, 580, 1770, 2500}}, {1, {117, 570, 1750, 2400}}, {1, {115, 760, 1580, 2440}}, {0, {110, 715, 1500, 2300}}, {1, {124, 620, 880, 2500}}, {1, {124, 650, 1000, 2520}}, {0, {119, 710, 950, 2520}}, {1, {120, 690, 960, 2520}}, {0, {125, 460, 610, 2500}}, {0, {120, 470, 710, 2500}}, {0, {125, 390, 900, 2100}}, {0, {125, 460, 920, 2140}}, {0, {125, 250, 690, 2080}}, {0, {130, 270, 650, 2050}}, {0, {122, 540, 1280, 1720}}, {0, {118, 510, 1280, 1650}}, {0, {148, 280, 2450, 2700}}, {0, {160, 288, 2500, 2880}}, {0, {160, 400, 2080, 2530}}, {0, {153, 384, 2110, 2500}}, {1, {138, 590, 1900, 2200}}, {1, {153, 583, 1840, 2250}}, {0, {145, 680, 1850, 2400}}, {0, {140, 685, 1780, 2160}}, {0, {143, 660, 1370, 2110}}, {1, {145, 680, 1300, 2100}}, {1, {140, 760, 1260, 2120}}, {0, {135, 770, 1140, 2020}}, {0, {145, 500, 800, 1850}}, {0, {132, 600, 1000, 2000}}, {0, {157, 380, 1060, 1950}}, {0, {150, 470, 1220, 2150}}, {0, {162, 324, 800, 2220}}, {0, {139, 290, 800, 2150}}, {0, {150, 560, 1350, 1780}}, {0, {150, 600, 1470, 1820}}, {0, {110, 250, 2190, 3000}}, {0, {106, 254, 2085, 2890}}, {0, {111, 330, 1967, 2670}}, {0, {108, 430, 1940, 2590}}, {0, {116, 464, 2100, 2700}}, {0, {105, 504, 1995, 2780}}, {0, {94, 595, 1900, 2700}}, {0, {100, 670, 1860, 2500}}, {0, {96, 620, 1200, 2420}}, {0, {105, 630, 1127, 2420}}, {0, {100, 750, 1160, 2360}}, {0, {96, 740, 1155, 2330}}, {0, {101, 460, 740, 2300}}, {1, {105, 494, 789, 2420}}, {0, {113, 400, 1020, 2200}}, {0, {128, 450, 1028, 2160}}, {0, {140, 392, 1000, 2120}}, {0, {116, 350, 898, 2140}}, {0, {117, 547, 1340, 1688}}, {0, {128, 512, 1280, 1570}}, {0, {123, 246, 2185, 2730}}, {0, {133, 267, 2280, 2800}}, {0, {140, 420, 2300, 2800}}, {0, {120, 384, 2110, 2620}}, {0, {120, 480, 1920, 2540}}, {1, {112, 551, 1788, 2450}}, {0, {114, 628, 1837, 2570}}, {1, {111, 622, 1890, 2560}}, {0, {114, 628, 1254, 2470}}, {0, {114, 617, 1255, 2480}}, {1, {117, 690, 1072, 2660}}, {1, {103, 630, 1000, 2530}}, {0, {117, 510, 700, 2650}}, {0, {120, 504, 756, 2540}}, {0, {122, 465, 990, 2440}}, {0, {125, 462, 976, 2450}}, {0, {120, 324, 708, 2440}}, {0, {157, 387, 786, 2518}}, {0, {122, 488, 1468, 1712}}, {0, {118, 472, 1465, 1725}}, {0, {138, 275, 2060, 2800}}, {0, {136, 270, 2020, 2790}}, {0, {133, 349, 2030, 2760}}, {0, {136, 340, 1940, 2560}}, {1, {120, 444, 1800, 2500}}, {1, {127, 380, 1800, 2440}}, {0, {125, 688, 1600, 2300}}, {0, {122, 660, 1570, 2380}}, {1, {128, 565, 1157, 2310}}, {0, {130, 550, 1150, 2250}}, {0, {125, 712, 1024, 2250}}, {0, {125, 670, 1080, 2300}}, {0, {125, 550, 913, 2360}}, {0, {126, 550, 890, 2280}}, {0, {128, 360, 1028, 2160}}, {1, {140, 390, 1060, 2150}}, {0, {133, 294, 930, 2050}}, {0, {140, 280, 1000, 2160}}, {0, {125, 440, 1250, 1625}}, {0, {130, 480, 1160, 1520}}, {0, {125, 320, 2160, 2900}}, {0, {133, 267, 2230, 3000}}, {0, {115, 440, 1750, 2400}}, {0, {116, 390, 1780, 2450}}, {0, {117, 525, 1800, 2480}}, {0, {110, 520, 1750, 2390}}, {0, {111, 660, 1600, 2400}}, {0, {120, 720, 1680, 2430}}, {0, {117, 600, 1250, 2300}}, {1, {125, 575, 1170, 2240}}, {1, {111, 730, 1160, 2340}}, {0, {117, 860, 1280, 2470}}, {0, {114, 560, 810, 2290}}, {0, {116, 584, 840, 2280}}, {0, {130, 455, 970, 2140}}, {0, {120, 456, 1040, 2038}}, {0, {125, 350, 820, 2130}}, {0, {128, 366, 772, 2058}}, {1, {111, 450, 1420, 1870}}, {0, {118, 472, 1430, 1840}}, {0, {133, 333, 2305, 3200}}, {0, {131, 326, 2260, 3030}}, {1, {125, 375, 2188, 2750}}, {1, {133, 400, 2150, 2680}}, {1, {125, 500, 1980, 2480}}, {1, {150, 480, 1950, 2340}}, {0, {116, 640, 1710, 2450}}, {0, {123, 615, 1720, 2220}}, {0, {116, 583, 1110, 2360}}, {1, {117, 608, 1120, 2700}}, {0, {111, 777, 1170, 2600}}, {0, {114, 750, 1175, 2820}}, {1, {105, 630, 891, 2519}}, {1, {114, 572, 924, 2660}}, {0, {125, 438, 975, 2300}}, {0, {140, 420, 938, 2300}}, {0, {133, 333, 800, 2130}}, {0, {140, 320, 840, 2150}}, {0, {120, 480, 1320, 1870}}, {0, {127, 483, 1335, 1844}}, {0, {166, 267, 2300, 2940}}, {0, {156, 220, 2300, 2900}}, {0, {154, 431, 2040, 2460}}, {0, {155, 360, 2010, 2400}}, {1, {150, 565, 1950, 2500}}, {0, {180, 540, 2000, 2450}}, {1, {143, 600, 2000, 2570}}, {0, {138, 590, 1950, 2460}}, {1, {157, 630, 1140, 2200}}, {1, {186, 630, 1170, 2280}}, {1, {146, 730, 1048, 2450}}, {0, {155, 730, 1130, 2320}}, {1, {150, 600, 900, 2400}}, {1, {178, 640, 890, 2280}}, {1, {160, 448, 960, 2200}}, {0, {196, 450, 1000, 2180}}, {0, {167, 333, 835, 2170}}, {0, {198, 280, 750, 2170}}, {0, {163, 488, 1300, 1600}}, {0, {163, 490, 1380, 1620}}, {0, {120, 312, 2380, 2900}}, {0, {120, 300, 2350, 3000}}, {0, {140, 490, 2000, 2620}}, {1, {140, 490, 1960, 2600}}, {0, {125, 640, 2000, 2620}}, {0, {111, 555, 1870, 2540}}, {0, {112, 697, 1610, 2540}}, {0, {114, 684, 1634, 2510}}, {0, {115, 633, 1260, 2530}}, {1, {120, 660, 1213, 2460}}, {0, {112, 730, 1203, 2700}}, {0, {107, 752, 1125, 2620}}, {0, {108, 507, 755, 2420}}, {0, {116, 538, 816, 2450}}, {0, {114, 456, 1040, 2300}}, {0, {120, 480, 1120, 2160}}, {1, {123, 344, 960, 2150}}, {0, {125, 350, 1000, 2250}}, {0, {112, 539, 1370, 1800}}, {0, {117, 549, 1353, 1728}}, {0, {146, 292, 2500, 3150}}, {0, {133, 266, 2370, 3100}}, {0, {143, 372, 2220, 2640}}, {0, {131, 350, 2130, 2610}}, {1, {133, 574, 1840, 2260}}, {1, {133, 563, 1960, 2450}}, {0, {125, 650, 1738, 2400}}, {0, {130, 663, 1820, 2400}}, {0, {137, 600, 1370, 2180}}, {1, {125, 625, 1312, 2250}}, {0, {133, 735, 1070, 2100}}, {0, {117, 713, 1180, 2200}}, {0, {125, 625, 875, 2180}}, {1, {115, 700, 1000, 2250}}, {0, {150, 420, 1100, 2000}}, {0, {140, 420, 1120, 2100}}, {0, {125, 350, 980, 2200}}, {0, {133, 320, 918, 2100}}, {0, {143, 554, 1480, 1800}}, {0, {128, 484, 1505, 1890}}, {0, {143, 286, 2415, 2860}}, {0, {150, 300, 2415, 2860}}, {1, {140, 400, 1980, 2500}}, {1, {145, 407, 2095, 2620}}, {1, {125, 525, 1988, 2610}}, {0, {144, 553, 1935, 2530}}, {0, {133, 640, 1773, 2490}}, {0, {133, 640, 1840, 2560}}, {0, {143, 672, 1272, 2640}}, {0, {146, 658, 1241, 2560}}, {0, {130, 780, 1170, 2640}}, {0, {131, 788, 1115, 2645}}, {1, {138, 633, 891, 2500}}, {1, {150, 600, 935, 2550}}, {0, {175, 490, 1102, 2420}}, {0, {154, 492, 1077, 2306}}, {1, {160, 320, 960, 2240}}, {0, {160, 320, 960, 2290}}, {0, {143, 543, 1310, 1643}}, {0, {145, 508, 1309, 1600}}, {1, {230, 370, 2670, 3100}}, {0, {234, 390, 2760, 3060}}, {0, {234, 468, 2330, 2930}}, {0, {205, 410, 2380, 2950}}, {0, {190, 550, 2200, 2880}}, {0, {191, 570, 2100, 3040}}, {0, {200, 800, 1980, 2810}}, {0, {192, 860, 1920, 2850}}, {0, {227, 635, 1200, 3250}}, {0, {200, 700, 1200, 3100}}, {1, {210, 880, 1240, 2870}}, {0, {188, 830, 1200, 2880}}, {0, {207, 570, 830, 3300}}, {1, {200, 700, 1000, 3130}}, {0, {240, 410, 940, 3040}}, {0, {225, 450, 970, 3190}}, {0, {238, 480, 955, 2960}}, {1, {208, 395, 810, 2900}}, {0, {200, 500, 1850, 2100}}, {0, {200, 560, 1750, 2100}}, {0, {225, 270, 2760, 3550}}, {0, {240, 290, 2700, 3350}}, {0, {245, 460, 2500, 3220}}, {0, {220, 410, 2400, 3240}}, {0, {220, 620, 2300, 3200}}, {0, {210, 630, 2300, 3170}}, {0, {220, 820, 2180, 2850}}, {0, {195, 740, 2120, 3070}}, {0, {240, 800, 1300, 2900}}, {0, {225, 760, 1400, 2830}}, {0, {214, 850, 1120, 2620}}, {0, {190, 880, 1220, 2850}}, {0, {228, 460, 900, 2830}}, {1, {222, 440, 880, 2850}}, {0, {250, 500, 1040, 2750}}, {0, {245, 490, 1000, 2720}}, {0, {250, 400, 940, 2720}}, {0, {245, 410, 860, 2700}}, {0, {225, 440, 1560, 1750}}, {0, {210, 420, 1600, 1750}}, {0, {210, 290, 2700, 3020}}, {0, {215, 280, 2630, 3240}}, {1, {211, 420, 2300, 2950}}, {0, {211, 420, 2220, 2980}}, {1, {207, 640, 2120, 2900}}, {1, {221, 700, 2000, 2900}}, {0, {212, 1000, 1830, 2820}}, {0, {204, 980, 1800, 2820}}, {1, {205, 780, 1410, 2720}}, {0, {208, 710, 1450, 2750}}, {0, {205, 950, 1280, 2600}}, {0, {210, 870, 1260, 2740}}, {0, {203, 610, 900, 2710}}, {0, {210, 630, 840, 2700}}, {0, {211, 440, 1050, 2780}}, {0, {210, 420, 1050, 2740}}, {0, {222, 380, 860, 2500}}, {0, {208, 330, 750, 2740}}, {0, {208, 580, 1450, 1720}}, {0, {212, 540, 1560, 1900}}, {0, {210, 294, 2800, 3100}}, {0, {222, 270, 2880, 3160}}, {0, {202, 420, 2430, 3030}}, {0, {212, 420, 2370, 2930}}, {1, {200, 580, 2180, 2770}}, {1, {217, 540, 2160, 2770}}, {0, {200, 820, 1970, 2620}}, {0, {210, 840, 2000, 2700}}, {1, {208, 690, 1200, 2900}}, {0, {201, 666, 1206, 2900}}, {1, {200, 800, 1200, 2920}}, {1, {190, 760, 1140, 2850}}, {0, {200, 560, 760, 2800}}, {0, {207, 560, 770, 3000}}, {1, {215, 430, 1075, 2580}}, {0, {213, 430, 1000, 2700}}, {0, {220, 330, 840, 2550}}, {0, {213, 280, 850, 2500}}, {0, {205, 430, 1800, 1930}}, {0, {200, 420, 1740, 1960}}, {0, {175, 350, 2800, 3160}}, {0, {187, 338, 2870, 3300}}, {0, {200, 400, 2540, 3200}}, {0, {210, 420, 2680, 3000}}, {0, {180, 518, 2470, 3200}}, {0, {200, 600, 2400, 3150}}, {0, {171, 773, 2000, 2870}}, {0, {175, 875, 2100, 2970}}, {1, {183, 733, 1468, 2700}}, {0, {200, 740, 1280, 2900}}, {1, {178, 730, 1210, 2740}}, {1, {175, 735, 1220, 2850}}, {0, {160, 560, 960, 2850}}, {0, {192, 536, 850, 2850}}, {0, {212, 424, 1040, 2780}}, {0, {200, 520, 1060, 2670}}, {0, {190, 380, 770, 2900}}, {0, {187, 340, 750, 2780}}, {1, {177, 490, 2120, 2480}}, {0, {197, 493, 1930, 2300}}, {0, {250, 325, 2700, 3100}}, {0, {225, 310, 2750, 3225}}, {0, {214, 350, 2580, 3000}}, {0, {267, 390, 2700, 3200}}, {0, {233, 560, 2330, 2800}}, {0, {200, 520, 2500, 3000}}, {0, {171, 806, 1970, 2600}}, {0, {150, 825, 1860, 2550}}, {0, {186, 708, 1485, 2760}}, {0, {188, 676, 1500, 2590}}, {0, {200, 800, 1200, 2800}}, {1, {205, 714, 1154, 2850}}, {0, {267, 530, 800, 2780}}, {1, {180, 485, 810, 2750}}, {0, {214, 450, 1460, 2550}}, {0, {233, 467, 1400, 2450}}, {0, {225, 450, 1080, 2350}}, {0, {200, 400, 1000, 2400}}, {0, {193, 524, 1700, 2130}}, {0, {180, 507, 1800, 2380}}, {0, {200, 300, 3100, 3400}}, {1, {216, 300, 3100, 3500}}, {0, {214, 428, 2570, 3000}}, {0, {220, 440, 2640, 3080}}, {0, {210, 528, 2540, 3170}}, {1, {210, 504, 2520, 3200}}, {0, {187, 940, 2250, 2760}}, {0, {200, 820, 2200, 2920}}, {0, {204, 816, 1450, 2700}}, {1, {214, 858, 1500, 2700}}, {0, {200, 960, 1280, 3000}}, {1, {180, 1040, 1300, 3000}}, {0, {220, 520, 880, 2500}}, {0, {217, 574, 890, 2510}}, {1, {233, 466, 1330, 2750}}, {1, {233, 466, 1165, 2800}}, {0, {180, 300, 850, 2800}}, {1, {175, 350, 840, 2750}}, {0, {216, 432, 1790, 2060}}, {0, {219, 360, 1900, 2320}}, {0, {225, 337, 2700, 3300}}, {0, {233, 340, 2720, 3200}}, {0, {237, 474, 2370, 3095}}, {0, {237, 475, 2400, 3090}}, {0, {229, 526, 2360, 3090}}, {0, {233, 580, 2360, 3150}}, {1, {230, 690, 2185, 2990}}, {1, {220, 660, 2200, 3020}}, {1, {225, 675, 1551, 2923}}, {0, {233, 690, 1630, 2900}}, {0, {222, 845, 1334, 2890}}, {0, {233, 888, 1290, 2800}}, {0, {225, 631, 923, 2250}}, {0, {233, 543, 980, 2300}}, {0, {233, 537, 1360, 2920}}, {0, {240, 480, 1345, 2680}}, {0, {235, 400, 1180, 2760}}, {0, {233, 396, 1120, 2560}}, {0, {225, 450, 1640, 2250}}, {0, {233, 489, 1630, 2090}}, {0, {225, 225, 2760, 3900}}, {0, {230, 230, 2850, 3800}}, {0, {238, 429, 2560, 3200}}, {1, {230, 430, 2575, 3100}}, {0, {214, 579, 2570, 3300}}, {0, {214, 536, 2570, 3100}}, {0, {205, 823, 2220, 2870}}, {0, {200, 800, 2100, 2900}}, {0, {250, 750, 1500, 2750}}, {0, {217, 738, 1300, 2820}}, {0, {200, 840, 1300, 3100}}, {1, {206, 990, 1340, 3100}}, {0, {214, 579, 856, 2790}}, {0, {205, 545, 905, 2750}}, {1, {233, 490, 1220, 2610}}, {1, {250, 513, 1500, 2650}}, {0, {250, 400, 1250, 2500}}, {0, {225, 405, 1080, 2500}}, {0, {233, 466, 1860, 2260}}, {0, {225, 540, 1780, 2220}}, {0, {240, 290, 3000, 3840}}, {0, {250, 325, 2900, 3500}}, {0, {250, 500, 2370, 3120}}, {1, {238, 476, 2380, 3090}}, {0, {238, 760, 2380, 3205}}, {0, {233, 746, 2290, 3030}}, {0, {206, 1008, 1990, 2870}}, {0, {200, 1040, 2000, 2800}}, {0, {220, 830, 1540, 2860}}, {0, {237, 900, 1510, 2840}}, {0, {206, 970, 1343, 3018}}, {1, {236, 592, 1230, 2600}}, {0, {233, 650, 900, 2920}}, {0, {229, 687, 1060, 2780}}, {1, {233, 512, 1211, 2630}}, {0, {233, 467, 1167, 2595}}, {0, {250, 450, 875, 2750}}, {0, {233, 420, 935, 2710}}, {0, {230, 622, 1750, 2070}}, {0, {225, 652, 1710, 2043}}, {0, {255, 275, 2800, 3310}}, {0, {245, 245, 2800, 3300}}, {0, {267, 534, 2500, 3250}}, {0, {264, 528, 2640, 3370}}, {0, {238, 700, 2380, 3250}}, {0, {250, 750, 2480, 3000}}, {0, {237, 1020, 1900, 2960}}, {0, {233, 1005, 2050, 2870}}, {0, {263, 750, 1500, 2850}}, {0, {250, 850, 1400, 2750}}, {0, {258, 978, 1290, 2840}}, {0, {246, 935, 1230, 2730}}, {0, {250, 500, 750, 2750}}, {0, {243, 632, 850, 2850}}, {0, {250, 350, 1170, 2750}}, {0, {266, 450, 1000, 2800}}, {0, {256, 358, 640, 2560}}, {0, {250, 300, 750, 2500}}, {0, {260, 520, 1560, 1820}}, {0, {250, 500, 1500, 1750}}, {0, {236, 236, 2790, 3760}}, {0, {242, 242, 2770, 3800}}, {0, {222, 444, 2555, 3110}}, {0, {242, 420, 2700, 3120}}, {0, {226, 634, 2325, 2940}}, {0, {225, 608, 2475, 3100}}, {0, {210, 1010, 2060, 2900}}, {0, {200, 980, 2160, 2920}}, {0, {217, 818, 1450, 2500}}, {0, {200, 750, 1280, 2650}}, {0, {220, 820, 1200, 2640}}, {0, {210, 900, 1120, 2900}}, {0, {220, 440, 749, 2640}}, {0, {210, 567, 752, 2600}}, {1, {204, 460, 1045, 2504}}, {0, {240, 480, 1105, 2400}}, {0, {250, 420, 1000, 2500}}, {0, {275, 350, 1100, 2400}}, {0, {217, 487, 1500, 1780}}, {0, {206, 467, 1420, 1640}}, {0, {225, 360, 2920, 3400}}, {0, {233, 340, 2840, 3300}}, {0, {257, 514, 2570, 3070}}, {0, {238, 500, 2680, 3260}}, {0, {238, 650, 2495, 3090}}, {1, {216, 650, 2380, 3030}}, {0, {225, 1020, 2030, 2700}}, {0, {225, 1000, 2200, 2770}}, {0, {225, 788, 1462, 2920}}, {0, {217, 736, 1500, 2900}}, {1, {214, 987, 1330, 2830}}, {0, {214, 1009, 1415, 3080}}, {1, {226, 672, 1084, 2495}}, {0, {209, 627, 1045, 2504}}, {0, {250, 500, 1200, 2450}}, {0, {230, 460, 1150, 2880}}, {0, {267, 420, 990, 2860}}, {0, {190, 380, 893, 2920}}, {0, {246, 610, 1630, 2020}}, {0, {225, 585, 1700, 1850}}, {0, {285, 285, 2900, 3500}}, {0, {286, 310, 2900, 3400}}, {0, {297, 480, 2670, 3260}}, {1, {220, 440, 2620, 3380}}, {0, {173, 550, 2370, 3140}}, {0, {260, 520, 2340, 3040}}, {0, {167, 790, 2180, 3020}}, {0, {280, 840, 2160, 3020}}, {0, {280, 840, 1400, 2750}}, {0, {270, 760, 1330, 2950}}, {0, {252, 900, 1290, 2750}}, {1, {260, 900, 1240, 3110}}, {0, {175, 700, 1050, 2750}}, {0, {190, 720, 1080, 3030}}, {0, {286, 540, 1200, 2860}}, {0, {205, 570, 1200, 2970}}, {0, {328, 400, 980, 2630}}, {0, {290, 440, 990, 2900}}, {0, {286, 570, 2000, 2480}}, {0, {260, 510, 1850, 2350}}, {0, {170, 340, 2750, 3120}}, {0, {238, 360, 2760, 3120}}, {0, {167, 480, 2390, 2950}}, {1, {194, 520, 2450, 3000}}, {0, {220, 620, 2520, 2920}}, {0, {222, 620, 2440, 2880}}, {0, {222, 1110, 2160, 2700}}, {0, {214, 1070, 1960, 2750}}, {1, {217, 820, 1240, 2600}}, {1, {216, 860, 1300, 2670}}, {0, {150, 840, 1110, 2930}}, {0, {170, 850, 1120, 2850}}, {0, {200, 500, 700, 2930}}, {0, {212, 380, 720, 2700}}, {0, {235, 400, 940, 2820}}, {0, {214, 380, 860, 2680}}, {0, {196, 330, 760, 2870}}, {0, {188, 350, 710, 2760}}, {0, {182, 550, 1780, 2080}}, {0, {201, 600, 1750, 2000}}, {0, {200, 320, 2360, 2980}}, {0, {203, 304, 2380, 3050}}, {1, {211, 444, 2220, 2740}}, {1, {210, 420, 2090, 2780}}, {0, {200, 500, 2350, 2830}}, {0, {200, 600, 2200, 2700}}, {1, {192, 845, 1700, 2300}}, {0, {187, 860, 1724, 2530}}, {0, {200, 720, 1440, 2380}}, {0, {191, 707, 1470, 2440}}, {0, {200, 700, 1080, 2420}}, {1, {192, 767, 1150, 2590}}, {0, {200, 600, 860, 2410}}, {0, {200, 600, 900, 2400}}, {0, {210, 546, 1090, 2400}}, {0, {210, 462, 1240, 2310}}, {0, {257, 360, 930, 2260}}, {0, {220, 440, 1100, 2300}}, {0, {200, 540, 1400, 1800}}, {0, {204, 460, 1350, 1560}}, {0, {203, 406, 2600, 2945}}, {1, {200, 400, 2600, 3100}}, {0, {200, 460, 2300, 2800}}, {0, {210, 420, 2305, 2835}}, {0, {190, 570, 2100, 2720}}, {0, {207, 538, 2175, 2880}}, {0, {189, 850, 1853, 2685}}, {0, {193, 830, 1800, 2620}}, {0, {200, 720, 1500, 2560}}, {0, {200, 800, 1400, 2420}}, {0, {194, 915, 1280, 2530}}, {0, {206, 723, 1196, 2600}}, {0, {192, 575, 1073, 2490}}, {0, {200, 600, 1100, 2600}}, {0, {202, 520, 1210, 2420}}, {0, {212, 468, 1275, 2550}}, {0, {207, 370, 1000, 2470}}, {0, {205, 330, 970, 2460}}, {0, {200, 560, 1600, 1900}}, {0, {206, 514, 1540, 1955}}, {0, {240, 380, 2880, 3360}}, {0, {250, 380, 2820, 3300}}, {1, {233, 514, 2600, 2930}}, {0, {237, 473, 2660, 2970}}, {0, {223, 567, 2460, 3122}}, {0, {224, 521, 2460, 2920}}, {0, {218, 808, 2070, 2880}}, {1, {203, 678, 2420, 3080}}, {0, {200, 800, 1340, 2700}}, {1, {214, 772, 1280, 2660}}, {0, {183, 843, 1190, 2860}}, {0, {205, 740, 1160, 2780}}, {1, {222, 623, 1022, 2700}}, {0, {220, 594, 990, 2640}}, {1, {240, 480, 960, 2820}}, {0, {242, 484, 900, 2640}}, {0, {233, 370, 933, 2520}}, {0, {250, 325, 750, 2500}}, {0, {225, 450, 1680, 2050}}, {1, {233, 466, 1630, 1865}}, {0, {200, 320, 2750, 3100}}, {0, {178, 356, 2755, 3200}}, {0, {194, 388, 2622, 3050}}, {0, {194, 426, 2460, 3040}}, {0, {187, 592, 2242, 2765}}, {1, {191, 535, 2290, 2870}}, {1, {188, 750, 2060, 2770}}, {1, {162, 650, 2110, 2618}}, {0, {187, 618, 1518, 2700}}, {0, {183, 624, 1430, 2660}}, {0, {163, 766, 1180, 2340}}, {0, {167, 750, 1065, 2640}}, {1, {170, 595, 918, 2600}}, {1, {176, 630, 985, 2630}}, {0, {200, 420, 1200, 2600}}, {0, {200, 460, 1260, 2640}}, {0, {187, 375, 1124, 2685}}, {1, {188, 375, 1143, 2700}}, {0, {180, 504, 1565, 1835}}, {0, {183, 513, 1578, 1830}}, {0, {280, 357, 2800, 3360}}, {0, {275, 340, 2860, 3350}}, {0, {290, 480, 2600, 3060}}, {0, {292, 465, 2598, 3060}}, {1, {250, 700, 2350, 2980}}, {0, {240, 737, 2325, 3100}}, {0, {200, 960, 2100, 3000}}, {0, {217, 1030, 2200, 3260}}, {0, {275, 920, 1512, 2950}}, {0, {260, 910, 1688, 3050}}, {0, {275, 990, 1237, 2360}}, {0, {267, 987, 1172, 3180}}, {0, {267, 587, 1068, 3270}}, {0, {293, 560, 990, 3150}}, {1, {275, 520, 1350, 3190}}, {1, {280, 510, 1415, 3130}}, {0, {300, 420, 1045, 3060}}, {0, {300, 390, 960, 3030}}, {0, {230, 460, 1860, 2250}}, {0, {214, 504, 1820, 2290}}, {0, {200, 240, 2760, 3700}}, {0, {220, 220, 2850, 3800}}, {0, {228, 319, 2500, 3020}}, {0, {216, 324, 2500, 3010}}, {0, {220, 616, 2380, 2900}}, {0, {212, 615, 2300, 2800}}, {1, {212, 710, 2120, 2600}}, {1, {210, 690, 2250, 2680}}, {0, {221, 800, 1520, 2380}}, {0, {210, 780, 1470, 2400}}, {0, {199, 995, 1392, 2290}}, {0, {200, 1000, 1400, 2440}}, {0, {205, 656, 944, 2250}}, {0, {200, 720, 960, 2380}}, {0, {223, 335, 1049, 2470}}, {0, {210, 420, 1009, 2300}}, {0, {219, 329, 877, 2550}}, {0, {230, 340, 900, 2530}}, {0, {206, 400, 1380, 1560}}, {0, {201, 400, 1240, 1480}}, {0, {220, 286, 2800, 3550}}, {0, {241, 289, 2800, 3400}}, {0, {225, 383, 2420, 3080}}, {0, {240, 384, 2400, 3050}}, {1, {209, 418, 2430, 3110}}, {0, {230, 460, 2300, 3050}}, {0, {187, 861, 2100, 2800}}, {0, {224, 896, 2040, 3000}}, {0, {218, 654, 1160, 2800}}, {0, {230, 690, 1195, 2770}}, {0, {208, 860, 1103, 2700}}, {0, {212, 806, 1060, 2850}}, {0, {202, 606, 910, 2900}}, {0, {201, 583, 860, 2840}}, {0, {225, 340, 900, 2650}}, {0, {235, 470, 1100, 2560}}, {0, {205, 308, 1025, 2650}}, {0, {235, 329, 1151, 2560}}, {0, {213, 533, 1425, 1830}}, {0, {214, 535, 1412, 1800}}, {0, {236, 307, 2670, 3150}}, {0, {245, 340, 2700, 3250}}, {0, {231, 417, 2300, 3000}}, {1, {239, 410, 2200, 2910}}, {1, {222, 644, 2250, 3000}}, {0, {224, 670, 2300, 2880}}, {1, {224, 784, 1800, 2750}}, {1, {234, 820, 1750, 2890}}, {0, {225, 765, 1300, 2700}}, {0, {221, 730, 1390, 2790}}, {1, {225, 834, 1282, 2800}}, {0, {212, 850, 1270, 2760}}, {1, {229, 688, 1029, 2750}}, {0, {222, 670, 1040, 2640}}, {0, {251, 427, 1506, 2640}}, {0, {240, 460, 1370, 2610}}, {0, {236, 378, 1416, 2580}}, {0, {239, 380, 1430, 2610}}, {0, {230, 460, 1200, 1909}}, {0, {225, 410, 1580, 1800}}, {0, {256, 384, 2860, 3210}}, {0, {250, 375, 3000, 3400}}, {0, {230, 460, 2665, 3140}}, {0, {233, 467, 2680, 3150}}, {0, {229, 640, 2400, 2860}}, {0, {233, 630, 2530, 3030}}, {1, {233, 700, 2560, 3150}}, {1, {225, 675, 2510, 3145}}, {1, {240, 768, 1440, 2855}}, {0, {234, 794, 1447, 2920}}, {0, {227, 978, 1362, 2724}}, {0, {233, 933, 1350, 2610}}, {0, {240, 700, 1080, 2810}}, {0, {240, 720, 1090, 2840}}, {0, {243, 500, 1215, 2870}}, {0, {239, 500, 1240, 2860}}, {0, {263, 470, 1000, 2820}}, {0, {272, 378, 950, 2990}}, {0, {243, 480, 1410, 1700}}, {0, {243, 493, 1580, 1775}}, {0, {268, 320, 2900, 3200}}, {0, {263, 290, 2750, 3050}}, {1, {258, 460, 2380, 2940}}, {1, {251, 480, 2260, 2980}}, {1, {246, 640, 2220, 2900}}, {1, {250, 670, 2250, 2960}}, {0, {243, 950, 1970, 2890}}, {0, {244, 980, 1950, 2920}}, {1, {251, 750, 1280, 2760}}, {0, {258, 770, 1340, 2800}}, {1, {250, 950, 1130, 3160}}, {1, {256, 850, 1150, 2940}}, {0, {242, 530, 870, 2680}}, {0, {250, 600, 900, 2770}}, {1, {250, 600, 1225, 2500}}, {1, {264, 630, 1320, 2560}}, {0, {258, 440, 1290, 2530}}, {0, {269, 460, 1080, 2640}}, {0, {250, 600, 1500, 2000}}, {0, {254, 610, 1520, 1950}}, {0, {234, 280, 2690, 3040}}, {0, {261, 280, 2740, 2980}}, {0, {260, 470, 2500, 3400}}, {0, {262, 440, 2480, 3240}}, {0, {242, 730, 2300, 3100}}, {0, {260, 750, 2340, 3120}}, {0, {233, 860, 2070, 2880}}, {0, {240, 890, 1920, 2710}}, {0, {257, 770, 1540, 2840}}, {0, {257, 800, 1410, 2860}}, {0, {240, 790, 1250, 3080}}, {1, {241, 820, 1210, 2960}}, {0, {234, 408, 695, 3040}}, {0, {246, 420, 590, 3100}}, {0, {251, 500, 1230, 2520}}, {0, {256, 480, 1230, 2750}}, {0, {263, 419, 1050, 2850}}, {0, {278, 390, 1060, 2800}}, {0, {220, 420, 1720, 1900}}, {0, {255, 510, 1680, 1890}}, {0, {208, 270, 2820, 3450}}, {0, {225, 250, 2880, 3350}}, {0, {220, 370, 2530, 3060}}, {0, {250, 400, 2600, 3120}}, {0, {214, 640, 2360, 3020}}, {0, {219, 650, 2430, 3040}}, {0, {205, 900, 2090, 3000}}, {0, {200, 860, 2160, 2870}}, {0, {214, 750, 1540, 2800}}, {0, {214, 770, 1530, 2780}}, {0, {195, 920, 1350, 2550}}, {1, {210, 920, 1470, 2690}}, {0, {194, 720, 1110, 2420}}, {0, {200, 700, 1100, 2780}}, {0, {222, 470, 1200, 2900}}, {0, {237, 470, 1190, 2800}}, {0, {240, 380, 980, 3100}}, {0, {188, 340, 920, 3050}}, {0, {222, 530, 1670, 2050}}, {0, {200, 500, 1720, 1900}}, {0, {258, 310, 2740, 3200}}, {0, {262, 262, 2680, 3170}}, {0, {262, 450, 2310, 3020}}, {0, {263, 472, 2270, 2950}}, {1, {245, 640, 1980, 2920}}, {1, {235, 700, 2110, 2940}}, {0, {194, 810, 1860, 2620}}, {0, {234, 890, 1800, 2700}}, {1, {230, 710, 1340, 2780}}, {1, {245, 740, 1470, 2940}}, {1, {225, 830, 1020, 2650}}, {1, {219, 830, 1095, 2610}}, {0, {240, 600, 850, 2760}}, {0, {253, 455, 810, 2750}}, {0, {282, 400, 1070, 2530}}, {0, {250, 450, 1050, 2450}}, {0, {260, 290, 670, 2380}}, {0, {275, 330, 630, 2460}}, {0, {240, 500, 1630, 2040}}, {0, {243, 490, 1580, 2190}}, {0, {228, 460, 3300, 3950}}, {0, {200, 400, 3400, 3850}}, {1, {205, 600, 2550, 4000}}, {1, {205, 610, 2500, 4100}}, {1, {225, 600, 2750, 3600}}, {1, {210, 760, 2500, 3850}}, {0, {200, 1000, 2300, 3900}}, {1, {200, 800, 2500, 4050}}, {1, {200, 1000, 1750, 3550}}, {0, {223, 1110, 1690, 4040}}, {1, {205, 1220, 1560, 3650}}, {1, {200, 1300, 1800, 3450}}, {0, {219, 660, 1100, 3850}}, {1, {217, 690, 1090, 3900}}, {1, {206, 620, 1420, 3700}}, {0, {220, 620, 1410, 3520}}, {0, {233, 440, 900, 3900}}, {0, {200, 400, 650, 3800}}, {0, {210, 610, 2300, 2900}}, {0, {200, 450, 2150, 2550}}, {0, {290, 320, 3500, 4260}}, {0, {305, 350, 3400, 4100}}, {0, {322, 640, 3200, 3660}}, {0, {325, 650, 3000, 3800}}, {0, {270, 850, 2900, 3680}}, {1, {285, 700, 3120, 3750}}, {0, {256, 1130, 2560, 3500}}, {0, {285, 1140, 2000, 3560}}, {0, {310, 1130, 1740, 3670}}, {0, {300, 1000, 1800, 3450}}, {1, {265, 1170, 1500, 3440}}, {1, {283, 980, 1300, 3100}}, {1, {265, 530, 1060, 3450}}, {1, {272, 540, 1080, 3000}}, {0, {285, 560, 1440, 3500}}, {0, {294, 570, 1450, 3500}}, {0, {333, 350, 1280, 3650}}, {0, {290, 340, 1160, 2950}}, {1, {275, 560, 1740, 2460}}, {0, {302, 600, 1800, 2200}}, {0, {240, 380, 3140, 3700}}, {0, {258, 310, 3350, 3650}}, {1, {290, 580, 2760, 3400}}, {0, {250, 500, 2660, 3500}}, {1, {250, 780, 2450, 3400}}, {1, {240, 672, 2550, 3400}}, {1, {240, 660, 2900, 3370}}, {1, {215, 760, 2850, 3300}}, {0, {250, 880, 1500, 3200}}, {0, {243, 850, 1700, 3250}}, {0, {250, 940, 1380, 2400}}, {0, {276, 1200, 1500, 3160}}, {0, {250, 750, 1250, 3450}}, {0, {225, 675, 950, 3240}}, {0, {300, 610, 1500, 3300}}, {0, {275, 500, 1370, 3500}}, {0, {256, 300, 1280, 3150}}, {0, {250, 400, 1300, 3700}}, {0, {250, 500, 1540, 1700}}, {0, {242, 580, 1620, 1790}}, {0, {291, 410, 3200, 3800}}, {0, {264, 420, 3400, 3900}}, {1, {291, 580, 2900, 3820}}, {1, {280, 560, 2840, 3900}}, {1, {292, 810, 2640, 4200}}, {1, {270, 780, 2720, 4100}}, {0, {270, 1080, 2480, 3950}}, {0, {245, 1050, 2420, 4000}}, {1, {286, 970, 1600, 3950}}, {1, {250, 800, 1680, 3800}}, {1, {275, 1040, 1350, 3850}}, {0, {250, 1100, 1460, 4250}}, {1, {286, 770, 1150, 3950}}, {1, {273, 710, 1200, 3900}}, {1, {285, 680, 1420, 3800}}, {0, {278, 640, 1350, 3950}}, {0, {300, 420, 1110, 3640}}, {0, {280, 505, 1050, 3400}}, {0, {320, 640, 1940, 2820}}, {0, {265, 610, 2100, 2600}}, {0, {330, 460, 2800, 3550}}, {0, {333, 490, 2730, 3550}}, {1, {310, 560, 2500, 3450}}, {1, {310, 580, 2500, 3450}}, {1, {286, 800, 2300, 3750}}, {1, {310, 835, 2420, 3740}}, {0, {282, 950, 2150, 3650}}, {0, {310, 1000, 2150, 3700}}, {0, {293, 880, 1700, 3750}}, {0, {340, 900, 1600, 3650}}, {1, {299, 990, 1410, 3750}}, {0, {280, 1050, 1320, 3730}}, {1, {285, 770, 940, 3750}}, {1, {333, 680, 1020, 3700}}, {0, {322, 550, 1195, 3750}}, {0, {350, 550, 1340, 3500}}, {1, {316, 600, 1200, 3600}}, {0, {345, 550, 1100, 3470}}, {0, {310, 805, 1705, 2420}}, {0, {310, 710, 1700, 2400}}, {0, {210, 340, 3400, 4320}}, {0, {227, 590, 3610, 4220}}, {0, {235, 680, 3250, 4380}}, {1, {220, 440, 3000, 3790}}, {0, {212, 660, 2900, 3610}}, {1, {216, 610, 2760, 3650}}, {0, {214, 1240, 2700, 3640}}, {0, {215, 1050, 2550, 3550}}, {0, {216, 820, 1470, 3500}}, {1, {211, 970, 1410, 3200}}, {0, {218, 1090, 1380, 3050}}, {1, {212, 860, 1250, 2800}}, {0, {211, 800, 1220, 3700}}, {0, {214, 640, 1070, 3000}}, {0, {219, 660, 1360, 3700}}, {0, {214, 730, 1500, 3600}}, {0, {220, 620, 1100, 3250}}, {0, {216, 600, 1280, 3650}}, {0, {222, 670, 2130, 2360}}, {0, {205, 760, 2240, 2460}}, {0, {253, 330, 3250, 3720}}, {0, {262, 340, 3100, 3400}}, {1, {250, 500, 2500, 3640}}, {1, {278, 530, 2630, 3640}}, {1, {255, 710, 2550, 3560}}, {1, {250, 750, 2480, 3470}}, {0, {233, 1140, 2260, 3640}}, {0, {245, 1110, 2230, 3380}}, {0, {256, 770, 1540, 3500}}, {0, {257, 800, 1490, 3300}}, {0, {240, 940, 1400, 3400}}, {1, {245, 930, 1370, 3120}}, {0, {240, 530, 860, 3400}}, {0, {240, 520, 910, 3420}}, {0, {255, 510, 1250, 3320}}, {0, {260, 520, 1140, 3320}}, {0, {274, 360, 660, 3050}}, {0, {260, 310, 730, 3500}}, {0, {250, 550, 1500, 1800}}, {0, {239, 480, 1650, 1960}}, {0, {250, 300, 2950, 3600}}, {0, {270, 320, 3210, 3600}}, {0, {290, 550, 2610, 3560}}, {1, {286, 540, 2570, 3600}}, {0, {280, 700, 2500, 3580}}, {0, {263, 600, 2360, 3400}}, {0, {260, 970, 2400, 3200}}, {0, {250, 950, 2270, 3200}}, {0, {270, 780, 1650, 3350}}, {1, {250, 720, 1500, 3240}}, {1, {278, 950, 1200, 2950}}, {1, {250, 920, 1080, 2770}}, {1, {262, 790, 1050, 2900}}, {0, {250, 750, 1000, 2500}}, {0, {275, 540, 1430, 3320}}, {0, {263, 530, 1580, 3200}}, {0, {295, 420, 1500, 3010}}, {0, {260, 450, 1330, 2840}}, {0, {272, 570, 1880, 2400}}, {0, {255, 510, 1610, 1910}}, {0, {235, 280, 2820, 3400}}, {0, {244, 317, 3125, 3500}}, {0, {230, 460, 2520, 3300}}, {0, {212, 420, 2480, 3140}}, {0, {235, 657, 2300, 3300}}, {0, {232, 672, 2275, 3300}}, {0, {231, 808, 1950, 3300}}, {0, {225, 870, 2000, 3200}}, {0, {236, 706, 1410, 3200}}, {0, {211, 720, 1480, 2880}}, {1, {250, 950, 1350, 3100}}, {1, {227, 910, 1360, 2950}}, {0, {203, 700, 1120, 3070}}, {0, {230, 690, 920, 2760}}, {0, {250, 475, 1250, 3150}}, {0, {212, 460, 1210, 2750}}, {0, {244, 403, 1100, 2950}}, {0, {242, 363, 920, 2900}}, {0, {226, 452, 1580, 1810}}, {0, {232, 510, 1550, 1740}}, {0, {230, 280, 3140, 3830}}, {0, {250, 300, 3400, 3950}}, {1, {225, 450, 2700, 3650}}, {1, {250, 400, 2840, 3700}}, {0, {215, 580, 2650, 3550}}, {1, {220, 620, 2660, 3770}}, {0, {240, 910, 2370, 3160}}, {0, {233, 930, 2350, 3450}}, {0, {250, 770, 1650, 3420}}, {0, {230, 690, 1600, 3350}}, {1, {242, 970, 1450, 3260}}, {1, {225, 1010, 1650, 3150}}, {0, {232, 670, 1160, 3550}}, {0, {225, 720, 1260, 3400}}, {0, {216, 500, 1640, 3580}}, {0, {250, 450, 1440, 3500}}, {0, {290, 350, 1160, 3260}}, {0, {273, 330, 1090, 3350}}, {0, {240, 430, 1800, 2400}}, {0, {233, 470, 1840, 2400}}, {0, {275, 330, 3050, 3800}}, {0, {286, 340, 2860, 3610}}, {0, {280, 500, 2720, 3360}}, {0, {230, 600, 2750, 3550}}, {0, {245, 735, 2450, 3300}}, {0, {258, 780, 2560, 3300}}, {0, {235, 940, 2020, 2580}}, {0, {232, 1070, 2320, 2900}}, {0, {268, 860, 1530, 3100}}, {0, {256, 970, 1500, 3050}}, {1, {245, 780, 1250, 3180}}, {1, {236, 970, 970, 3120}}, {1, {258, 825, 1210, 3100}}, {1, {300, 930, 930, 2900}}, {0, {260, 490, 1460, 2860}}, {0, {286, 570, 1320, 2840}}, {0, {275, 470, 1400, 2800}}, {0, {286, 370, 1160, 2800}}, {0, {268, 510, 1660, 2100}}, {0, {250, 480, 1700, 1830}}, {0, {295, 380, 3200, 4000}}, {0, {267, 350, 3250, 3700}}, {0, {294, 380, 2960, 3800}}, {0, {300, 520, 2900, 3600}}, {0, {280, 670, 2790, 3600}}, {1, {275, 620, 2750, 3500}}, {0, {262, 1070, 2380, 3100}}, {0, {275, 1130, 2320, 3110}}, {1, {290, 700, 1730, 2960}}, {0, {270, 725, 1570, 2900}}, {0, {278, 1110, 1630, 2780}}, {0, {280, 1130, 1400, 3000}}, {1, {292, 580, 930, 2950}}, {0, {270, 540, 1070, 3000}}, {0, {300, 450, 1350, 3000}}, {0, {320, 520, 1600, 3150}}, {0, {307, 460, 1460, 3070}}, {0, {300, 400, 1700, 3000}}, {0, {300, 540, 1770, 2040}}, {0, {286, 540, 2050, 2300}}, {0, {300, 300, 3250, 3850}}, {0, {275, 275, 3280, 3800}}, {0, {286, 570, 2850, 3400}}, {0, {267, 485, 2630, 3450}}, {0, {264, 650, 2880, 3500}}, {0, {284, 570, 2900, 3600}}, {0, {260, 1300, 2280, 3130}}, {0, {260, 1300, 2160, 3300}}, {0, {275, 850, 1540, 3020}}, {0, {262, 840, 1580, 2880}}, {0, {250, 1230, 1300, 3200}}, {0, {286, 1090, 1230, 2980}}, {0, {265, 850, 850, 2920}}, {1, {285, 685, 1030, 2900}}, {0, {283, 540, 1420, 3050}}, {0, {300, 600, 1440, 2900}}, {0, {280, 390, 1340, 2830}}, {0, {284, 340, 1110, 3080}}, {0, {280, 530, 1650, 1740}}, {0, {286, 550, 1660, 1770}}, {0, {265, 370, 2950, 3400}}, {0, {290, 370, 2910, 3480}}, {0, {271, 515, 2740, 3280}}, {0, {290, 485, 2600, 3200}}, {0, {262, 630, 2520, 3150}}, {0, {272, 565, 2440, 3120}}, {0, {262, 970, 2030, 2880}}, {0, {275, 915, 2130, 2900}}, {0, {270, 810, 1600, 3230}}, {1, {280, 760, 1530, 3180}}, {1, {270, 810, 1350, 2940}}, {0, {275, 1000, 1360, 3000}}, {1, {270, 535, 970, 2960}}, {1, {275, 550, 1080, 2850}}, {1, {275, 550, 1420, 3040}}, {0, {295, 570, 1500, 3000}}, {0, {283, 510, 1700, 3020}}, {1, {278, 500, 1640, 3050}}, {0, {261, 522, 1830, 2350}}, {0, {282, 530, 1800, 2250}}, {0, {320, 350, 3240, 3760}}, {0, {344, 344, 3120, 3640}}, {0, {308, 590, 2760, 3500}}, {0, {320, 540, 2900, 3500}}, {0, {307, 830, 2750, 3650}}, {0, {308, 800, 2640, 3540}}, {0, {294, 1140, 2450, 3230}}, {0, {239, 1130, 2550, 3150}}, {0, {310, 930, 1540, 3120}}, {0, {315, 950, 1670, 3150}}, {0, {350, 1190, 1470, 3150}}, {1, {314, 1070, 1460, 2950}}, {0, {300, 910, 1200, 3180}}, {0, {330, 830, 1250, 3250}}, {0, {327, 630, 1310, 3270}}, {0, {322, 610, 1550, 3400}}, {0, {345, 520, 1250, 3460}}, {0, {334, 500, 1140, 3380}}, {0, {308, 740, 1850, 2160}}, {0, {328, 660, 1830, 2200}} }; try { autoTable me = Table_create (nrows, ncols); for (long i = 1; i <= nrows; i++) { TableRow row = (TableRow) my rows -> item[i]; int vowel_id = ( (i - 1) % 20) / 2 + 1; /* 1 - 10 */ int speaker_id = (i - 1) / 20 + 1; /* 1 - 76 */ int speaker_type, speaker_sex; if (speaker_id <= 33) { /* 33 men */ speaker_type = 0; speaker_sex = 0; } else if (speaker_id <= (33 + 28)) { /* 28 women */ speaker_type = 1; speaker_sex = 1; } else { /*15 children */ speaker_type = 2; speaker_sex = 0; if (speaker_id == 62 || speaker_id == 63 || (speaker_id >= 65 && speaker_id <= 68) || speaker_id == 73 || speaker_id == 76) { speaker_sex = 1; } } row -> cells [1]. string = Melder_wcsdup_f (type [speaker_type]); row -> cells [2]. string = Melder_wcsdup_f (sex [speaker_sex]); row -> cells [3]. string = Melder_wcsdup_f (Melder_integer (speaker_id)); row -> cells [4]. string = Melder_wcsdup_f (vowel [vowel_id - 1]); row -> cells [5]. string = Melder_wcsdup_f (ipa [vowel_id - 1]); for (long j = 0; j <= 3; j++) { row -> cells [j + 6].string = Melder_wcsdup_f (Melder_integer (pbdata[i - 1].f[j])); } } for (long j = 1; j <= ncols; j++) { Table_setColumnLabel (me.peek(), j, columnLabels[j - 1]); my columnHeaders [j]. numericized = FALSE; } return me.transfer(); } catch (MelderError) { Melder_throw ("Table not created from Peterson & Barney data."); } } Table Table_createFromPolsVanNieropData () { long nrows = 900, ncols = 10; const wchar_t *columnLabels[10] = {L"Sex", L"Speaker", L"Vowel", L"IPA", L"F1", L"F2", L"F3", L"L1", L"L2", L"L3"}; const wchar_t *vowel[12] = {L"oe", L"aa", L"oo", L"a", L"eu", L"ie", L"uu", L"ee", L"u", L"e", L"o", L"i" }; const wchar_t *ipa[12] = {L"u", L"a", L"o", L"\\as", L"\\o/", L"i", L"y", L"e", L"\\yc", L"\\ep", L"\\ct", L"\\ic"}; const wchar_t *sex[2] = {L"m", L"f"}; struct polsdatum { short f[3]; /* frequency F1, F2, F3 */ short l[3]; /* level f1, f2, f3 */ } polsdata [] = { /* 50*12 males */ /* male 1 */ {{320, 630, 2560}, {6, 13, 48}}, /* poet */ {{780, 1300, 2460}, {6, 8, 30}}, /* paat */ {{500, 940, 2420}, {3, 12, 35}}, /* poot */ {{720, 1060, 2420}, {3, 8, 27}}, /* pat */ {{430, 1580, 2260}, {2, 24, 36}}, /* peut */ {{280, 2300, 2780}, {14, 22, 27}}, /* piet */ {{320, 1680, 2140}, {6, 23, 30}}, /* puut */ {{420, 2000, 2620}, {5, 20, 23}}, /* peet */ {{420, 1540, 2380}, {4, 19, 24}}, /* put */ {{600, 1720, 2700}, {3, 17, 29}}, /* pet */ {{520, 1000, 2520}, {4, 13, 31}}, /* pot */ {{350, 2000, 2520}, {7, 19, 18}}, /* pit */ /* male 2 */ {{440, 780, 2600}, {7, 20, 35}}, {{940, 1300, 2780}, {5, 13, 26}}, {{500, 740, 2700}, {7, 11, 32}}, {{800, 1000, 2480}, {11, 11, 31}}, {{460, 1500, 2300}, {10, 20, 20}}, {{320, 2400, 3040}, {9, 28, 27}}, {{340, 1600, 2050}, {7, 30, 32}}, {{420, 2200, 2650}, {4, 10, 12}}, {{540, 1370, 2320}, {6, 23, 31}}, {{760, 1660, 2600}, {8, 13, 18}}, {{560, 800, 2800}, {5, 17, 37}}, {{430, 2030, 2660}, {7, 18, 17}}, /* male 3 */ {{280, 740, 2160}, {8, 32, 46}}, {{860, 1500, 2580}, {7, 13, 19}}, {{480, 820, 2280}, {4, 11, 33}}, {{680, 1020, 2460}, {9, 14, 25}}, {{360, 1520, 2080}, {5, 16, 21}}, {{270, 2040, 2860}, {5, 18, 18}}, {{280, 1600, 1900}, {5, 16, 21}}, {{380, 1940, 2580}, {5, 15, 17}}, {{400, 1520, 2120}, {4, 21, 24}}, {{560, 1840, 2520}, {7, 18, 22}}, {{500, 820, 2520}, {3, 11, 30}}, {{350, 2000, 2660}, {4, 15, 19}}, /* male 4 */ {{360, 820, 2220}, {6, 11, 30}}, {{840, 1300, 2280}, {9, 7, 22}}, {{500, 900, 2320}, {7, 13, 35}}, {{680, 1000, 2480}, {12, 12, 27}}, {{440, 1320, 2060}, {5, 12, 27}}, {{240, 2060, 2580}, {5, 20, 23}}, {{300, 1540, 2020}, {4, 18, 24}}, {{460, 1920, 2460}, {7, 18, 17}}, {{480, 1320, 2200}, {6, 15, 22}}, {{660, 1660, 2340}, {7, 16, 21}}, {{500, 800, 2520}, {7, 14, 34}}, {{440, 1920, 2380}, {3, 19, 18}}, /* male 5 */ {{440, 880, 2300}, {6, 22, 41}}, {{820, 1420, 2180}, {6, 7, 28}}, {{540, 960, 2460}, {4, 10, 28}}, {{780, 1040, 2620}, {8, 10, 32}}, {{540, 1540, 2160}, {2, 17, 19}}, {{300, 2300, 2900}, {5, 23, 30}}, {{360, 1860, 2200}, {2, 15, 15}}, {{520, 1960, 2400}, {4, 21, 21}}, {{560, 1440, 2280}, {2, 17, 27}}, {{700, 1720, 2300}, {7, 13, 22}}, {{600, 880, 3000}, {5, 5, 25}}, {{560, 1920, 2400}, {5, 22, 25}}, /* male 6 */ {{260, 700, 2550}, {3, 24, 45}}, {{820, 1460, 2760}, {10, 15, 27}}, {{450, 900, 2460}, {19, 20, 45}}, {{700, 1080, 2660}, {13, 22, 32}}, {{460, 1750, 2300}, {7, 32, 40}}, {{240, 2500, 3000}, {3, 33, 37}}, {{260, 2100, 2500}, {10, 37, 43}}, {{300, 2320, 2860}, {8, 26, 26}}, {{440, 1700, 2660}, {7, 27, 32}}, {{560, 2080, 2840}, {12, 15, 16}}, {{550, 900, 2740}, {7, 25, 30}}, {{340, 2340, 3000}, {8, 31, 31}}, /* male 7 */ {{280, 860, 2340}, {5, 15, 33}}, {{800, 1320, 2540}, {7, 14, 26}}, {{520, 920, 2600}, {8, 15, 33}}, {{600, 1000, 2760}, {7, 7, 25}}, {{450, 1660, 2260}, {7, 20, 24}}, {{260, 2340, 2640}, {3, 17, 20}}, {{280, 1780, 2160}, {3, 25, 29}}, {{400, 2040, 2400}, {9, 19, 21}}, {{460, 1560, 2400}, {4, 19, 22}}, {{620, 1760, 2560}, {6, 18, 25}}, {{560, 960, 2760}, {9, 16, 33}}, {{340, 2000, 2600}, {6, 14, 18}}, /* male 8 */ {{320, 880, 2200}, {6, 16, 40}}, {{800, 1160, 2600}, {6, 13, 26}}, {{560, 980, 2360}, {5, 8, 35}}, {{700, 1080, 2540}, {10, 14, 34}}, {{500, 1480, 2300}, {8, 17, 29}}, {{280, 2080, 2620}, {3, 27, 27}}, {{320, 1760, 2060}, {4, 25, 32}}, {{400, 1940, 2540}, {9, 17, 22}}, {{400, 1560, 2280}, {6, 18, 28}}, {{540, 1860, 2540}, {4, 14, 19}}, {{560, 920, 2320}, {8, 13, 32}}, {{340, 1960, 2480}, {6, 13, 17}}, /* male 9 */ {{300, 680, 2400}, {3, 19, 32}}, {{860, 1300, 2660}, {12, 18, 26}}, {{500, 940, 2500}, {3, 13, 33}}, {{700, 1120, 2620}, {9, 17, 24}}, {{500, 1500, 2280}, {3, 17, 22}}, {{300, 2380, 2960}, {2, 20, 22}}, {{300, 1760, 2160}, {1, 19, 23}}, {{480, 2100, 2580}, {4, 15, 15}}, {{500, 1580, 2400}, {5, 12, 22}}, {{640, 1700, 2620}, {3, 15, 19}}, {{560, 900, 2940}, {4, 8, 31}}, {{400, 2040, 2600}, {7, 17, 19}}, /* male 10 */ {{360, 900, 2220}, {11, 21, 46}}, {{880, 1400, 2660}, {9, 17, 29}}, {{460, 940, 2400}, {3, 13, 37}}, {{660, 1040, 2660}, {5, 5, 31}}, {{460, 1580, 2360}, {4, 22, 26}}, {{340, 2200, 2920}, {14, 30, 26}}, {{400, 1880, 2800}, {12, 19, 33}}, {{460, 2080, 2800}, {4, 18, 17}}, {{460, 1480, 2260}, {5, 27, 31}}, {{600, 1860, 2640}, {7, 18, 23}}, {{520, 860, 2880}, {2, 24, 32}}, {{460, 2100, 2800}, {6, 19, 22}}, /* male 11 */ {{320, 830, 2060}, {5, 16, 45}}, {{820, 1340, 2200}, {7, 9, 26}}, {{520, 840, 2040}, {7, 13, 31}}, {{660, 1060, 2300}, {8, 9, 28}}, {{440, 1520, 2040}, {7, 16, 22}}, {{300, 2100, 2600}, {5, 23, 30}}, {{300, 1740, 2040}, {2, 17, 19}}, {{340, 2040, 2460}, {5, 20, 24}}, {{500, 1440, 2200}, {8, 17, 21}}, {{600, 1760, 2380}, {10, 15, 19}}, {{560, 900, 2300}, {9, 10, 28}}, {{300, 1960, 2400}, {7, 22, 24}}, /* male 12 */ {{400, 860, 2700}, {7, 15, 46}}, {{940, 1520, 3040}, {10, 19, 33}}, {{580, 1040, 2960}, {5, 17, 42}}, {{860, 1280, 3000}, {8, 19, 34}}, {{480, 1600, 2620}, {7, 15, 32}}, {{300, 2500, 2880}, {3, 29, 29}}, {{300, 1670, 2350}, {3, 31, 39}}, {{480, 2220, 2640}, {7, 30, 31}}, {{380, 1600, 2540}, {4, 22, 33}}, {{630, 2140, 2880}, {7, 27, 27}}, {{640, 900, 3000}, {8, 13, 39}}, {{360, 2220, 2780}, {5, 23, 31}}, /* male 13 */ {{260, 780, 2460}, {5, 20, 44}}, {{900, 1560, 2860}, {9, 13, 26}}, {{440, 850, 2600}, {3, 17, 42}}, {{860, 1140, 2820}, {10, 12, 30}}, {{460, 1580, 2400}, {3, 19, 27}}, {{260, 2560, 3240}, {3, 28, 34}}, {{300, 1960, 2500}, {2, 31, 29}}, {{460, 2320, 2960}, {6, 25, 27}}, {{460, 1600, 2460}, {6, 22, 30}}, {{680, 2100, 2940}, {14, 19, 25}}, {{540, 800, 2740}, {7, 13, 36}}, {{380, 2500, 2980}, {7, 20, 23}}, /* male 14 */ {{340, 720, 2500}, {6, 16, 47}}, {{900, 1500, 3020}, {10, 13, 33}}, {{450, 900, 2700}, {4, 16, 42}}, {{600, 1000, 2720}, {12, 10, 31}}, {{420, 1740, 2560}, {8, 21, 25}}, {{360, 2500, 3000}, {8, 10, 13}}, {{360, 1900, 2420}, {6, 16, 12}}, {{380, 1780, 2420}, {4, 36, 18}}, {{500, 1640, 2620}, {4, 23, 29}}, {{600, 1940, 2700}, {3, 16, 19}}, {{500, 800, 2800}, {3, 10, 38}}, {{400, 2360, 2740}, {7, 13, 27}}, /* male 15 */ {{360, 780, 2320}, {5, 23, 50}}, {{860, 1420, 2420}, {8, 15, 35}}, {{440, 840, 2480}, {9, 20, 38}}, {{660, 980, 2500}, {6, 13, 33}}, {{460, 1660, 2200}, {2, 21, 31}}, {{300, 2360, 2960}, {7, 29, 27}}, {{320, 1740, 2220}, {2, 28, 30}}, {{400, 2240, 2560}, {5, 23, 24}}, {{480, 1420, 2220}, {6, 23, 37}}, {{680, 1640, 2340}, {9, 21, 28}}, {{560, 860, 2780}, {4, 15, 44}}, {{440, 2120, 2500}, {2, 22, 23}}, /* male 16 */ {{360, 760, 2300}, {7, 23, 52}}, {{660, 1000, 2500}, {9, 15, 35}}, {{500, 920, 2520}, {7, 15, 37}}, {{780, 1060, 2380}, {5, 9, 38}}, {{440, 1560, 2260}, {7, 25, 31}}, {{280, 2200, 2880}, {7, 43, 38}}, {{380, 1720, 2200}, {7, 29, 39}}, {{360, 2140, 2620}, {3, 26, 28}}, {{360, 1600, 2400}, {4, 26, 33}}, {{520, 1800, 2480}, {8, 32, 35}}, {{540, 920, 2640}, {6, 20, 44}}, {{340, 2080, 2680}, {3, 28, 27}}, /* male 17 */ {{400, 820, 2200}, {5, 15, 48}}, {{1100, 1480, 2260}, {10, 14, 30}}, {{520, 940, 2560}, {5, 15, 43}}, {{660, 940, 2820}, {11, 11, 35}}, {{500, 1720, 2400}, {5, 19, 23}}, {{360, 2300, 3260}, {11, 25, 17}}, {{360, 2100, 2420}, {10, 19, 20}}, {{440, 2360, 2860}, {6, 20, 25}}, {{500, 1760, 2600}, {6, 15, 25}}, {{660, 1840, 2620}, {7, 17, 24}}, {{540, 860, 2860}, {3, 9, 41}}, {{400, 2440, 3000}, {5, 28, 30}}, /* male 18 */ {{360, 860, 2520}, {6, 15, 35}}, {{740, 1300, 2660}, {7, 9, 22}}, {{460, 800, 2620}, {3, 20, 35}}, {{740, 1040, 2800}, {15, 13, 30}}, {{440, 1400, 2200}, {4, 21, 25}}, {{340, 2040, 2500}, {6, 18, 20}}, {{340, 1340, 2040}, {3, 15, 25}}, {{420, 1760, 2420}, {6, 18, 21}}, {{460, 1380, 2200}, {6, 20, 22}}, {{560, 1640, 2400}, {9, 13, 19}}, {{540, 920, 2520}, {9, 10, 23}}, {{400, 1800, 2400}, {8, 19, 21}}, /* male 19 */ {{320, 840, 2360}, {5, 20, 45}}, {{780, 1140, 2740}, {8, 15, 36}}, {{460, 1020, 2700}, {6, 11, 43}}, {{800, 1100, 2720}, {15, 17, 42}}, {{440, 1500, 2500}, {5, 23, 37}}, {{260, 2000, 2680}, {4, 39, 40}}, {{300, 1540, 2100}, {5, 33, 42}}, {{400, 1900, 2680}, {6, 25, 34}}, {{440, 1500, 2400}, {4, 26, 42}}, {{600, 1700, 2640}, {18, 33, 40}}, {{500, 800, 3000}, {5, 20, 47}}, {{400, 2000, 2500}, {5, 27, 37}}, /* male 20 */ {{400, 960, 2400}, {10, 16, 37}}, {{800, 1220, 2380}, {7, 13, 25}}, {{500, 1080, 2500}, {10, 14, 31}}, {{780, 1100, 2600}, {10, 11, 30}}, {{400, 1480, 2380}, {8, 20, 25}}, {{280, 2380, 2720}, {6, 23, 24}}, {{300, 1760, 2220}, {5, 14, 22}}, {{400, 2000, 2600}, {4, 20, 24}}, {{440, 1500, 2440}, {4, 15, 20}}, {{440, 1800, 2620}, {12, 18, 22}}, {{460, 860, 2600}, {12, 13, 33}}, {{400, 2040, 2640}, {3, 18, 23}}, /* male 21 */ {{300, 700, 2100}, {3, 15, 37}}, {{800, 1100, 2300}, {11, 15, 30}}, {{420, 700, 2440}, {5, 12, 33}}, {{660, 920, 2520}, {6, 9, 32}}, {{400, 1300, 2000}, {2, 22, 30}}, {{300, 1940, 2620}, {5, 25, 24}}, {{260, 1920, 2900}, {4, 21, 31}}, {{300, 1900, 2340}, {4, 20, 24}}, {{400, 1200, 2000}, {4, 20, 29}}, {{540, 1500, 2280}, {4, 15, 22}}, {{400, 740, 2580}, {3, 11, 34}}, {{300, 1900, 2380}, {2, 20, 20}}, /* male 22 */ {{400, 780, 2500}, {6, 14, 40}}, {{760, 1260, 2620}, {6, 14, 30}}, {{540, 860, 2600}, {4, 7, 34}}, {{660, 1100, 2460}, {9, 12, 30}}, {{540, 1460, 2260}, {5, 12, 20}}, {{300, 2300, 2800}, {7, 20, 17}}, {{300, 1980, 2900}, {6, 14, 32}}, {{420, 2100, 2600}, {4, 17, 21}}, {{500, 1440, 2300}, {4, 18, 26}}, {{540, 1900, 2600}, {10, 20, 22}}, {{550, 900, 3000}, {5, 11, 34}}, {{300, 2200, 2700}, {6, 14, 20}}, /* male 23 */ {{360, 900, 2140}, {3, 14, 37}}, {{800, 1250, 2650}, {12, 13, 26}}, {{520, 960, 2200}, {5, 7, 28}}, {{760, 1120, 2700}, {12, 10, 29}}, {{400, 1500, 2160}, {7, 20, 30}}, {{300, 2260, 3000}, {4, 18, 17}}, {{320, 1800, 2500}, {6, 17, 32}}, {{460, 2020, 2800}, {3, 10, 16}}, {{500, 1500, 2300}, {7, 15, 23}}, {{640, 1600, 2500}, {8, 22, 32}}, {{550, 940, 2420}, {7, 12, 40}}, {{460, 2100, 2880}, {2, 21, 24}}, /* male 24 */ {{360, 860, 2460}, {4, 15, 33}}, {{840, 1400, 2500}, {5, 8, 20}}, {{460, 900, 2520}, {1, 8, 31}}, {{620, 1020, 2770}, {7, 6, 26}}, {{410, 1460, 2360}, {2, 11, 18}}, {{270, 2140, 2580}, {2, 15, 21}}, {{300, 1870, 2300}, {1, 11, 16}}, {{360, 2000, 2520}, {2, 17, 19}}, {{400, 1520, 2400}, {2, 12, 17}}, {{600, 1600, 2580}, {3, 12, 20}}, {{500, 900, 2700}, {2, 11, 33}}, {{360, 1940, 2550}, {1, 19, 21}}, /* male 25 */ {{360, 860, 2200}, {8, 22, 46}}, {{880, 1240, 2400}, {7, 14, 25}}, {{460, 920, 3300}, {2, 11, 40}}, {{600, 1000, 2600}, {4, 7, 32}}, {{400, 1440, 2160}, {2, 31, 37}}, {{360, 2240, 2760}, {6, 23, 21}}, {{380, 1660, 2000}, {13, 16, 26}}, {{460, 2000, 2520}, {5, 23, 32}}, {{460, 1500, 2300}, {7, 17, 25}}, {{540, 1700, 2460}, {10, 22, 35}}, {{540, 1000, 2600}, {8, 13, 40}}, {{340, 2040, 2580}, {9, 27, 30}}, /* male 26 */ {{400, 800, 2500}, {6, 23, 42}}, {{960, 1300, 2640}, {9, 8, 29}}, {{460, 860, 2460}, {7, 16, 39}}, {{740, 1140, 2400}, {9, 10, 30}}, {{400, 1600, 2400}, {6, 21, 25}}, {{360, 2500, 2840}, {10, 19, 20}}, {{360, 1800, 2400}, {8, 21, 27}}, {{360, 2080, 2680}, {5, 14, 16}}, {{400, 1620, 2440}, {5, 15, 21}}, {{600, 1940, 2600}, {5, 13, 23}}, {{560, 980, 2900}, {5, 13, 32}}, {{400, 2060, 2540}, {5, 21, 21}}, /* male 27 */ {{300, 900, 2300}, {3, 15, 38}}, {{780, 1300, 2400}, {9, 18, 32}}, {{550, 1000, 2480}, {5, 10, 35}}, {{680, 1050, 2550}, {5, 10, 35}}, {{520, 1480, 2400}, {5, 16, 27}}, {{260, 2180, 2560}, {1, 30, 30}}, {{250, 1720, 2220}, {1, 26, 32}}, {{360, 2100, 2650}, {4, 31, 25}}, {{440, 1440, 2440}, {4, 21, 26}}, {{600, 1600, 2500}, {5, 15, 27}}, {{560, 950, 2700}, {3, 10, 40}}, {{360, 1900, 2600}, {3, 26, 31}}, /* male 28 */ {{280, 740, 2500}, {3, 20, 45}}, {{780, 1300, 2840}, {4, 12, 25}}, {{440, 860, 2860}, {5, 13, 41}}, {{440, 700, 3040}, {9, 10, 37}}, {{450, 1520, 2320}, {2, 25, 30}}, {{220, 2340, 2960}, {1, 35, 36}}, {{240, 1800, 2140}, {3, 36, 37}}, {{300, 2200, 2600}, {4, 28, 33}}, {{440, 1500, 2480}, {3, 26, 37}}, {{500, 1660, 2620}, {10, 30, 38}}, {{420, 700, 3000}, {4, 12, 35}}, {{300, 2140, 2760}, {6, 32, 31}}, /* male 29 */ {{340, 660, 2320}, {4, 13, 37}}, {{640, 1250, 2480}, {10, 16, 29}}, {{560, 1000, 2480}, {10, 14, 31}}, {{720, 1150, 2600}, {10, 13, 26}}, {{480, 1400, 2160}, {9, 22, 28}}, {{300, 2040, 2640}, {5, 20, 22}}, {{280, 1540, 1960}, {3, 21, 23}}, {{460, 1760, 2320}, {7, 19, 20}}, {{440, 1550, 2200}, {8, 16, 23}}, {{480, 1660, 1960}, {10, 16, 23}}, {{480, 840, 2840}, {9, 12, 28}}, {{400, 1780, 2360}, {7, 20, 23}}, /* male 30 */ {{360, 800, 2540}, {1, 11, 40}}, {{600, 1300, 2600}, {6, 8, 27}}, {{500, 860, 2440}, {2, 7, 36}}, {{750, 1140, 2640}, {4, 9, 30}}, {{460, 1400, 2340}, {1, 23, 28}}, {{340, 2300, 2620}, {2, 26, 25}}, {{300, 1540, 2300}, {5, 25, 35}}, {{440, 2000, 2540}, {1, 14, 19}}, {{440, 1360, 2360}, {1, 19, 26}}, {{620, 1840, 2560}, {3, 18, 23}}, {{520, 820, 2680}, {2, 7, 34}}, {{420, 2000, 2640}, {1, 20, 25}}, /*L2 (10) corrected 20021211 */ /* male 31 */ {{340, 740, 2240}, {5, 15, 44}}, {{820, 1200, 2250}, {5, 17, 40}}, {{440, 820, 2540}, {3, 13, 37}}, {{760, 1060, 2340}, {8, 15, 42}}, {{460, 1540, 2380}, {3, 21, 25}}, {{280, 2260, 2620}, {8, 31, 32}}, {{300, 1800, 2220}, {6, 36, 37}}, {{460, 1900, 2260}, {3, 34, 31}}, {{380, 1540, 2400}, {15, 36, 40}}, {{500, 1740, 2400}, {4, 26, 39}}, {{460, 840, 2580}, {7, 28, 35}}, {{320, 2100, 2460}, {7, 30, 27}}, /* male 32 */ {{360, 900, 2200}, {5, 18, 39}}, {{640, 1280, 2340}, {7, 15, 26}}, {{460, 920, 2360}, {7, 14, 33}}, {{720, 1200, 2580}, {11, 14, 26}}, {{420, 1520, 2260}, {6, 17, 23}}, {{400, 2000, 2560}, {5, 15, 20}}, {{380, 1700, 2100}, {6, 18, 21}}, {{440, 1740, 2420}, {4, 14, 17}}, {{500, 1520, 2440}, {5, 14, 21}}, {{580, 1540, 2460}, {5, 12, 24}}, {{580, 1020, 2700}, {9, 13, 30}}, {{460, 1720, 2400}, {7, 22, 20}}, /* male 33 */ {{400, 700, 2600}, {4, 17, 45}}, {{900, 1440, 2600}, {10, 17, 36}}, {{460, 860, 2600}, {7, 18, 45}}, {{680, 1000, 2200}, {7, 13, 39}}, {{460, 1600, 2540}, {5, 28, 37}}, {{300, 2260, 2880}, {7, 28, 26}}, {{320, 1860, 2200}, {7, 22, 28}}, {{440, 2180, 2660}, {3, 24, 28}}, {{380, 1560, 2360}, {8, 26, 33}}, {{620, 1720, 2060}, {6, 21, 28}}, {{600, 860, 2900}, {12, 18, 37}}, {{440, 2040, 2600}, {4, 26, 30}}, /* male 34 */ {{370, 900, 2230}, {3, 17, 35}}, {{700, 1200, 2580}, {12, 17, 30}}, {{500, 840, 2460}, {4, 13, 37}}, {{720, 1080, 2640}, {7, 13, 37}}, {{440, 1300, 2220}, {4, 20, 31}}, {{300, 2040, 2580}, {7, 25, 25}}, {{320, 1540, 2080}, {8, 21, 23}}, {{380, 1860, 2450}, {7, 24, 33}}, {{460, 1200, 2360}, {3, 20, 30}}, {{580, 1500, 2380}, {9, 22, 25}}, {{480, 820, 2580}, {8, 15, 32}}, {{400, 1800, 2360}, {6, 23, 26}}, /* male 35 */ {{280, 1040, 2340}, {7, 26, 41}}, {{820, 1300, 2760}, {10, 15, 32}}, {{440, 1220, 2580}, {6, 18, 29}}, {{600, 1040, 2540}, {8, 13, 27}}, {{420, 1560, 2480}, {6, 22, 26}}, {{300, 2160, 2700}, {5, 29, 30}}, {{250, 1760, 2320}, {9, 30, 38}}, {{440, 1940, 2550}, {5, 25, 28}}, {{400, 1600, 2460}, {8, 26, 29}}, {{580, 1820, 2460}, {5, 23, 30}}, {{460, 860, 2660}, {5, 21, 37}}, {{400, 2100, 2640}, {8, 27, 27}}, /* male 36 */ {{360, 740, 2160}, {2, 21, 40}}, {{660, 1260, 2540}, {10, 18, 21}}, {{500, 900, 2600}, {9, 20, 30}}, {{640, 1000, 2880}, {11, 17, 29}}, {{460, 1300, 2140}, {8, 19, 25}}, {{300, 1900, 2580}, {11, 18, 22}}, {{320, 1660, 2060}, {9, 17, 20}}, {{400, 1780, 2320}, {8, 20, 21}}, {{380, 1360, 2200}, {6, 20, 25}}, {{540, 1600, 2260}, {8, 21, 22}}, {{540, 860, 2720}, {7, 20, 32}}, {{400, 1740, 2340}, {5, 22, 23}}, /* male 37 */ {{300, 900, 2140}, {5, 21, 39}}, {{700, 1240, 2460}, {10, 18, 28}}, {{480, 960, 2140}, {4, 12, 32}}, {{640, 1120, 2480}, {9, 14, 32}}, {{460, 1520, 2160}, {4, 18, 25}}, {{320, 2120, 2600}, {10, 20, 26}}, {{320, 1800, 2200}, {8, 25, 27}}, {{320, 1920, 2460}, {8, 21, 27}}, {{480, 1460, 2260}, {5, 22, 27}}, {{600, 1600, 2480}, {7, 17, 24}}, {{500, 950, 2450}, {4, 14, 38}}, {{460, 1820, 2480}, {6, 18, 26}}, /* male 38 */ {{320, 760, 2080}, {11, 23, 41}}, {{840, 1180, 2700}, {13, 20, 37}}, {{500, 920, 2400}, {13, 17, 37}}, {{660, 1060, 2700}, {13, 17, 36}}, {{440, 1400, 2220}, {5, 32, 37}}, {{280, 2240, 2700}, {14, 29, 35}}, {{300, 1640, 2080}, {12, 31, 31}}, {{440, 2040, 2600}, {11, 19, 24}}, {{400, 1460, 2160}, {8, 32, 38}}, {{580, 1700, 1900}, {13, 26, 26}}, {{500, 840, 2920}, {10, 18, 40}}, {{360, 2060, 2440}, {7, 21, 27}}, /* male 39 */ {{320, 760, 2480}, {9, 21, 46}}, {{700, 1420, 2680}, {9, 16, 31}}, {{500, 940, 2500}, {4, 16, 41}}, {{700, 1060, 2720}, {8, 10, 38}}, {{440, 1580, 2260}, {11, 34, 39}}, {{260, 2200, 2700}, {5, 29, 32}}, {{200, 1600, 2060}, {7, 33, 34}}, {{400, 2200, 2600}, {13, 29, 31}}, {{380, 1500, 2220}, {8, 25, 37}}, {{540, 1750, 2420}, {8, 23, 32}}, {{520, 820, 2560}, {10, 19, 43}}, {{400, 1700, 2320}, {3, 38, 23}}, /* male 40 */ {{300, 680, 1920}, {7, 28, 48}}, {{740, 1200, 2550}, {8, 10, 24}}, {{420, 860, 2420}, {7, 17, 37}}, {{640, 1120, 2500}, {12, 17, 37}}, {{360, 1500, 2180}, {3, 27, 35}}, {{280, 2160, 2920}, {4, 27, 31}}, {{260, 1560, 2050}, {2, 26, 27}}, {{360, 2020, 2500}, {4, 26, 28}}, {{440, 1400, 2320}, {4, 21, 32}}, {{460, 1660, 2460}, {5, 19, 27}}, {{500, 840, 2580}, {6, 14, 35}}, {{360, 1920, 2560}, {3, 31, 31}}, /* male 41 */ {{360, 880, 2320}, {2, 12, 43}}, {{840, 1200, 2500}, {12, 17, 37}}, {{580, 1060, 2300}, {11, 10, 32}}, {{580, 1100, 2680}, {8, 12, 33}}, {{560, 1600, 2200}, {9, 22, 27}}, {{300, 2260, 2800}, {5, 25, 26}}, {{320, 1760, 2100}, {5, 23, 25}}, {{500, 2020, 2660}, {5, 17, 21}}, {{420, 1520, 2320}, {1, 20, 28}}, {{700, 1800, 2620}, {8, 17, 22}}, {{540, 860, 2720}, {7, 13, 35}}, {{420, 2080, 2600}, {4, 21, 25}}, /* male 42 */ {{420, 800, 2400}, {5, 15, 40}}, {{800, 1400, 2900}, {9, 16, 41}}, {{420, 820, 2480}, {5, 8, 40}}, {{600, 1200, 2760}, {6, 12, 34}}, {{400, 1560, 2120}, {2, 20, 31}}, {{320, 2360, 2820}, {8, 25, 27}}, {{340, 1680, 2240}, {9, 19, 35}}, {{400, 2180, 2760}, {2, 19, 20}}, {{400, 1440, 2360}, {3, 15, 26}}, {{700, 1700, 2340}, {11, 18, 29}}, {{500, 780, 2840}, {7, 14, 38}}, {{380, 2120, 2720}, {2, 21, 25}}, /* male 43 */ {{300, 760, 2020}, {3, 16, 38}}, {{740, 1200, 2360}, {8, 15, 29}}, {{460, 860, 2200}, {8, 12, 39}}, {{620, 900, 2500}, {8, 12, 27}}, {{400, 1340, 2100}, {7, 20, 31}}, {{240, 2000, 2340}, {2, 22, 28}}, {{240, 1580, 1860}, {3, 16, 24}}, {{360, 1640, 2080}, {5, 19, 26}}, {{400, 1340, 2060}, {3, 16, 28}}, {{580, 1400, 2120}, {6, 13, 24}}, {{500, 800, 2460}, {6, 6, 31}}, {{440, 1720, 2100}, {7, 19, 24}}, /* male 44 */ {{260, 800, 2400}, {3, 16, 48}}, {{780, 1300, 2700}, {6, 14, 28}}, {{480, 900, 2500}, {5, 8, 35}}, {{620, 1000, 2820}, {5, 9, 28}}, {{420, 1400, 2300}, {3, 18, 29}}, {{240, 2040, 2680}, {1, 31, 28}}, {{260, 1580, 2260}, {3, 31, 28}}, {{380, 2000, 2600}, {5, 29, 26}}, {{420, 1420, 2400}, {2, 21, 26}}, {{540, 1640, 2440}, {5, 19, 26}}, {{480, 840, 2800}, {6, 13, 32}}, {{280, 1960, 2560}, {5, 27, 28}}, /* male 45 */ {{300, 840, 3060}, {3, 10, 38}}, {{800, 1220, 2280}, {6, 10, 26}}, {{500, 920, 2120}, {6, 8, 31}}, {{700, 1020, 2600}, {3, 11, 28}}, {{400, 1260, 2020}, {6, 17, 24}}, {{260, 1960, 2440}, {1, 22, 22}}, {{300, 1480, 1940}, {2, 18, 22}}, {{440, 1880, 2380}, {6, 17, 17}}, {{320, 1400, 2140}, {5, 18, 27}}, {{500, 1560, 2300}, {7, 18, 22}}, {{540, 780, 2400}, {8, 13, 34}}, {{360, 1860, 2300}, {4, 20, 21}}, /* male 46 */ {{320, 860, 2380}, {3, 19, 41}}, {{660, 1400, 2540}, {11, 20, 27}}, {{520, 940, 2580}, {7, 11, 34}}, {{700, 1040, 2720}, {4, 8, 23}}, {{400, 1600, 2280}, {2, 27, 29}}, {{320, 2340, 3140}, {3, 33, 29}}, {{300, 1860, 2160}, {2, 25, 25}}, {{420, 2200, 2760}, {1, 17, 23}}, {{460, 2320, 3360}, {2, 33, 37}}, {{500, 2100, 2760}, {6, 23, 38}}, {{600, 920, 2700}, {8, 17, 29}}, {{420, 2200, 2740}, {3, 30, 32}}, /* male 47 */ {{360, 800, 2120}, {3, 18, 33}}, {{700, 1220, 2760}, {6, 13, 27}}, {{540, 940, 2640}, {2, 8, 33}}, {{620, 1080, 2800}, {4, 10, 33}}, {{500, 1400, 2200}, {6, 18, 25}}, {{320, 2240, 2940}, {2, 22, 27}}, {{320, 1800, 2100}, {1, 26, 27}}, {{420, 2040, 2400}, {3, 19, 24}}, {{460, 1440, 2140}, {1, 13, 25}}, {{600, 1600, 2520}, {6, 13, 27}}, {{560, 700, 2780}, {5, 11, 31}}, {{440, 1920, 2560}, {3, 22, 24}}, /* male 48 */ {{300, 760, 1900}, {3, 17, 42}}, {{800, 1260, 2740}, {7, 10, 28}}, {{460, 840, 1840}, {4, 13, 38}}, {{540, 900, 2400}, {10, 14, 28}}, {{420, 1380, 2100}, {2, 16, 29}}, {{220, 2080, 2900}, {2, 28, 21}}, {{220, 1760, 2120}, {1, 22, 25}}, {{440, 2060, 2780}, {1, 19, 21}}, {{440, 1440, 2560}, {3, 19, 31}}, {{580, 1400, 2100}, {5, 15, 22}}, {{520, 900, 2300}, {3, 10, 32}}, {{420, 1720, 2720}, {6, 22, 21}}, /* male 49 */ {{320, 1000, 2220}, {3, 24, 43}}, {{700, 1280, 2500}, {3, 13, 30}}, {{460, 1060, 2380}, {4, 13, 31}}, {{620, 1100, 2840}, {10, 18, 33}}, {{340, 1440, 2260}, {4, 21, 30}}, {{280, 2140, 2580}, {3, 31, 32}}, {{280, 1820, 2220}, {2, 36, 35}}, {{340, 2100, 2500}, {2, 29, 31}}, {{380, 1460, 2400}, {2, 26, 38}}, {{500, 1640, 2500}, {7, 27, 31}}, {{500, 960, 2720}, {4, 17, 31}}, {{420, 1960, 2700}, {1, 32, 32}}, /* male 50 */ {{340, 780, 2020}, {11, 22, 36}}, {{660, 1220, 2500}, {9, 14, 22}}, {{420, 760, 2440}, {2, 17, 33}}, {{560, 1000, 2600}, {6, 13, 25}}, {{400, 1320, 2120}, {8, 18, 21}}, {{300, 1860, 2440}, {6, 22, 22}}, {{280, 1600, 1900}, {6, 16, 19}}, {{340, 1740, 2260}, {3, 12, 17}}, {{400, 1360, 2160}, {4, 16, 22}}, {{520, 1580, 2240}, {2, 12, 16}}, {{380, 800, 2560}, {7, 11, 25}}, {{360, 1740, 2260}, {5, 14, 17}}, /* 25*12 females */ {{250, 800, 2450}, {0, 8, 45}}, /* poet */ {{950, 1500, 2650}, {5, 14, 30}}, /* paat */ {{500, 1050, 2600}, {3, 5, 38}}, /* poot */ {{720, 1100, 2950}, {8, 2, 24}}, /* pat */ {{500, 1800, 2500}, {6, 14, 30}}, /* peut */ {{280, 2500, 3100}, {0, 32, 26}}, /* piet */ {{250, 1700, 2200}, {0, 18, 21}}, /* puut */ {{500, 2350, 2750}, {2, 12, 12}}, /* peet */ {{520, 1550, 2400}, {4, 15, 27}}, /* put */ {{750, 2000, 2600}, {4, 20, 20}}, /* pet */ {{550, 900, 2800}, {6, 3, 34}}, /* pot */ {{480, 2150, 2650}, {5, 20, 22}}, /* pit */ /* female 2 */ {{300, 750, 2700}, {0, 10, 50}}, {{1100, 1500, 3000}, {6, 9, 28}}, /* djmw 20021212 L3 (was 20) */ {{520, 900, 2800}, {2, 8, 30}}, {{800, 1150, 3000}, {2, 12, 34}}, /* djmw 20021212 F3 (was 300 in Van Nierop data!)*/ {{450, 1600, 2950}, {2, 22, 31}}, {{250, 2700, 3300}, {0, 27, 31}}, {{300, 1900, 2650}, {0, 23, 33}}, {{550, 2300, 3000}, {0, 17, 22}}, {{450, 1900, 2800}, {0, 20, 32}}, {{700, 2150, 3100}, {0, 22, 30}}, {{600, 950, 2800}, {0, 10, 40}}, {{350, 2450, 2900}, {0, 27, 28}}, /* female 3 */ {{350, 800, 2700}, {0, 19, 50}}, {{1000, 1450, 2800}, {7, 7, 34}}, {{500, 1000, 2600}, {4, 11, 45}}, {{650, 1000, 2700}, {7, 1, 29}}, {{460, 1650, 2400}, {2, 21, 35}}, {{250, 2450, 2900}, {0, 30, 26}}, {{250, 1750, 2500}, {0, 22, 31}}, {{480, 2600, 3600}, {4, 22, 33}}, {{450, 1650, 2600}, {2, 16, 32}}, {{650, 2450, 2800}, {6, 19, 20}}, {{650, 1050, 2800}, {1, 10, 42}}, {{350, 2600, 3200}, {0, 24, 35}}, /* female 4 */ {{350, 750, 2500}, {1, 10, 36}}, {{1000, 1550, 2900}, {6, 14, 18}}, {{450, 950, 2450}, {2, 6, 30}}, {{800, 1100, 3200}, {6, 6, 26}}, {{450, 1900, 2400}, {3, 14, 14}}, {{250, 2450, 3050}, {0, 15, 22}}, {{300, 1900, 2350}, {0, 12, 15}}, {{450, 2250, 2850}, {3, 16, 12}}, {{430, 1700, 2650}, {2, 12, 17}}, {{600, 2250, 2950}, {4, 12, 15}}, {{600, 850, 3200}, {4, 3, 30}}, {{430, 2500, 3000}, {2, 16, 24}}, /* female 5 */ {{300, 900, 2700}, {0, 12, 42}}, {{750, 1600, 2800}, {2, 15, 24}}, {{480, 950, 2600}, {2, 13, 32}}, {{800, 1200, 2900}, {3, 13, 30}}, {{430, 1500, 2600}, {1, 20, 25}}, {{250, 2800, 3150}, { -1, 22, 32}}, {{300, 1400, 2500}, {0, 24, 28}}, {{420, 2400, 2900}, {2, 27, 27}}, {{500, 1650, 2850}, {1, 16, 25}}, {{750, 1900, 3000}, {4, 25, 30}}, {{600, 1200, 2850}, {3, 17, 23}}, {{490, 1950, 2900}, {2, 29, 28}}, /* female 6 */ {{300, 750, 2350}, {2, 8, 37}}, /* djmw 20021212 L2 (was 0) */ {{950, 1400, 2400}, {2, 12, 23}}, {{650, 1100, 2200}, {4, 8, 34}}, /* djmw 20021212 L2 (was 0) */ {{900, 1100, 2600}, {2, 6, 26}}, /* djmw 20021212 L3 (was 20) */ {{490, 1700, 2400}, {1, 18, 24}}, /* djmw 20021212 L2 (was 14) */ {{300, 2500, 2800}, {0, 16, 21}}, {{300, 1800, 2400}, {0, 10, 14}}, {{470, 2400, 2750}, {2, 17, 19}}, {{570, 1750, 2550}, {0, 17, 18}}, /* djmw 20021212 L3 (was 19) */ {{700, 1750, 2400}, {0, 10, 16}}, {{600, 1200, 2500}, {0, 18, 28}}, /* djmw 20021212 L2,3 (was 10,20) */ {{440, 2250, 2700}, {0, 17, 18}}, /* female 7 */ {{350, 850, 2600}, { -1, 16, 38}}, {{950, 1200, 2900}, {7, 9, 40}}, {{550, 1050, 2500}, {2, 6, 38}}, {{850, 1200, 2800}, { -1, 12, 39}}, {{440, 1800, 2500}, {0, 24, 30}}, {{300, 2300, 3000}, { -1, 22, 30}}, {{350, 1850, 2400}, { -1, 23, 27}}, {{460, 2400, 2900}, {1, 28, 30}}, /* djmw 20021212 L2 (was 20) */ {{490, 1650, 2700}, {1, 22, 28}}, {{650, 1700, 2750}, {2, 28, 28}}, /* djmw 20021212 L2 (was 20) */ {{450, 700, 3000}, {6, 2, 33}}, /* djmw 20021212 L2 (was 8) */ {{440, 2550, 3000}, {1, 40, 41}}, /* female 8 */ {{350, 1000, 2500}, {2, 19, 40}}, {{950, 1400, 2700}, {8, 14, 29}}, {{500, 950, 2450}, {6, 10, 34}}, {{850, 1230, 2950}, {8, 19, 42}}, {{520, 1650, 2600}, {6, 22, 28}}, {{250, 2500, 3000}, {0, 25, 30}}, {{250, 1750, 2300}, {0, 23, 29}}, {{510, 2250, 2850}, {4, 30, 24}}, {{650, 1600, 2600}, {6, 18, 26}}, {{720, 1750, 2650}, {4, 19, 27}}, {{750, 1150, 2650}, {2, 15, 37}}, {{510, 2050, 2950}, {2, 22, 23}}, /* female 9 */ {{300, 850, 2650}, {0, 14, 43}}, {{950, 1350, 2700}, {4, 6, 25}}, {{550, 900, 2700}, {5, 4, 37}}, {{930, 1300, 2800}, {0, 15, 35}}, {{550, 1500, 2400}, {0, 10, 22}}, {{280, 2450, 3000}, {0, 13, 21}}, {{300, 1650, 2400}, {0, 26, 32}}, {{530, 2400, 3000}, {0, 4, 14}}, {{600, 1600, 2000}, {0, 14, 16}}, {{850, 1950, 2800}, {1, 12, 19}}, {{750, 1050, 2900}, {2, 4, 32}}, {{550, 2300, 2800}, {1, 14, 22}}, /* female 10 */ {{350, 800, 2500}, {0, 21, 44}}, {{1100, 1450, 2900}, {5, 9, 31}}, {{400, 850, 2600}, {0, 5, 46}}, {{750, 1050, 2950}, {4, 9, 25}}, {{420, 1650, 2550}, {0, 17, 38}}, {{300, 2450, 3050}, { -1, 28, 35}}, {{280, 1850, 2500}, { -1, 20, 30}}, {{420, 2400, 2800}, {1, 25, 29}}, {{420, 1500, 2350}, {0, 22, 34}}, {{650, 1850, 2800}, {2, 28, 31}}, {{550, 800, 2800}, {4, 7, 44}}, {{420, 2350, 2750}, {2, 27, 28}}, /* female 11 */ {{300, 800, 2850}, { -1, 22, 54}}, {{1150, 1550, 2850}, {6, 9, 26}}, {{600, 1000, 2700}, {3, 9, 30}}, {{750, 1100, 2700}, {2, 10, 34}}, {{500, 1800, 2550}, {3, 17, 24}}, {{250, 2400, 3100}, {0, 27, 35}}, {{250, 2000, 3650}, {0, 30, 36}}, {{420, 2400, 2900}, {5, 28, 31}}, /* djmw 20021212 L2,3 (was 20,34) */ {{470, 1700, 2500}, {4, 26, 37}}, /* djmw 20021212 L2 (was 20) */ {{700, 1880, 2650}, {2, 21, 26}}, {{650, 900, 2650}, {5, 4, 33}}, {{490, 2250, 2650}, {3, 22, 26}}, /* female 12 */ {{300, 900, 2500}, { -1, 20, 39}}, {{950, 1500, 2700}, {3, 16, 20}}, {{450, 1000, 2650}, {2, 8, 35}}, {{600, 1050, 2800}, {4, 4, 33}}, {{420, 1650, 2500}, {1, 14, 22}}, {{250, 2300, 2850}, {0, 30, 24}}, {{300, 1800, 2300}, { -1, 21, 28}}, {{400, 2100, 2700}, {0, 29, 20}}, {{420, 1650, 2450}, {0, 17, 28}}, {{550, 1800, 2650}, {2, 19, 20}}, {{450, 1050, 2800}, {2, 10, 26}}, {{420, 1850, 2700}, {0, 27, 26}}, /* female 13 */ {{300, 850, 2800}, {0, 19, 47}}, {{1100, 1400, 2800}, {6, 10, 25}}, {{550, 900, 2900}, {2, 16, 44}}, {{700, 1050, 2750}, {4, 6, 33}}, {{490, 1700, 2500}, {0, 33, 35}}, {{300, 2500, 2950}, {0, 40, 35}}, {{300, 1900, 2450}, {0, 24, 36}}, {{500, 2500, 3000}, {4, 31, 32}}, {{460, 1450, 2500}, {6, 33, 38}}, {{700, 1700, 2700}, {1, 18, 30}}, {{500, 800, 2700}, {2, 6, 38}}, {{550, 2250, 2750}, {3, 28, 26}}, /* female 14 */ {{350, 900, 3600}, {0, 16, 44}}, {{950, 1420, 2950}, {5, 7, 26}}, {{400, 1000, 2400}, {0, 12, 36}}, {{600, 950, 2650}, {4, 7, 31}}, {{420, 1400, 2500}, {1, 21, 24}}, {{300, 2500, 2850}, {0, 26, 27}}, {{250, 1450, 2200}, {0, 29, 36}}, {{420, 1950, 2700}, {0, 20, 20}}, {{410, 1550, 2400}, {0, 20, 28}}, {{600, 1650, 2600}, {3, 9, 21}}, {{430, 880, 2950}, {2, 6, 32}}, {{410, 1950, 2250}, {0, 31, 30}}, /* female 15 */ {{350, 1000, 2350}, {0, 29, 41}}, {{850, 1100, 2800}, {2, 5, 25}}, {{600, 1000, 2800}, {2, 6, 30}}, {{850, 1400, 2600}, {1, 20, 31}}, {{470, 2000, 2550}, {2, 16, 18}}, {{250, 2650, 3250}, {0, 31, 40}}, {{300, 2000, 2400}, {0, 23, 24}}, {{430, 2400, 2900}, {1, 22, 27}}, {{460, 1900, 2500}, {2, 25, 28}}, {{650, 1900, 2900}, {2, 19, 23}}, {{600, 900, 2400}, {3, 7, 35}}, {{460, 2400, 2900}, {1, 26, 27}}, /* female 16 */ {{300, 850, 3300}, {0, 20, 52}}, {{1050, 1400, 2450}, {6, 8, 31}}, {{500, 950, 2400}, {4, 10, 44}}, {{850, 1050, 2850}, {6, 7, 37}}, {{480, 1650, 2300}, {2, 14, 32}}, {{300, 3000, 4200}, {0, 32, 36}}, {{300, 1900, 2450}, {0, 27, 37}}, {{460, 2450, 3000}, {1, 32, 30}}, {{500, 1550, 3100}, {2, 18, 40}}, {{650, 1800, 2700}, {2, 22, 32}}, {{450, 750, 2850}, {4, 2, 38}}, {{440, 2200, 2900}, {0, 30, 29}}, /* female 17 */ {{320, 850, 2500}, {0, 18, 50}}, /* djmw 20021212 L2 (was 10) */ {{1100, 1350, 2900}, {7, 9, 25}}, {{450, 900, 2600}, {2, 8, 39}}, /* djmw 20021212 L3 (was 30) */ {{800, 1200, 2800}, {2, 14, 32}}, {{480, 1800, 2500}, {2, 24, 29}}, {{300, 2600, 3000}, {0, 32, 32}}, {{300, 1900, 2400}, {0, 25, 28}}, {{460, 2300, 2900}, {2, 26, 29}}, {{480, 1800, 2650}, {2, 27, 28}}, /* djmw 20021212 L3 (was 20) */ {{650, 1850, 3000}, {4, 22, 34}}, {{550, 800, 2850}, {4, 4, 30}}, {{470, 2200, 3000}, {2, 28, 33}}, /* djmw 20021212 L2 (was 20) */ /* female 18 */ {{350, 750, 2550}, {0, 14, 48}}, /* djmw 20021212 L3 (was 40) */ {{1050, 1700, 2850}, {0, 14, 22}}, {{550, 1000, 2600}, {3, 4, 32}}, {{750, 1150, 2950}, {5, 3, 30}}, {{550, 1750, 2600}, {2, 12, 19}}, {{300, 2400, 3000}, {0, 21, 22}}, {{300, 1950, 2500}, {0, 18, 22}}, {{510, 2200, 3000}, {1, 24, 27}}, {{490, 1750, 2450}, {2, 23, 29}}, {{600, 2200, 3000}, {3, 14, 23}}, {{700, 850, 2900}, {6, 6, 38}}, {{540, 2200, 3000}, {9, 22, 22}}, /* female 19 */ {{350, 950, 2800}, {0, 24, 51}}, {{1000, 1500, 2900}, {6, 10, 26}}, {{450, 950, 2800}, {2, 16, 48}}, {{700, 1050, 3000}, {5, 5, 35}}, {{450, 1700, 2450}, {4, 23, 28}}, {{250, 2600, 3000}, {0, 28, 34}}, {{330, 1900, 2700}, {0, 30, 42}}, {{520, 2500, 2900}, {2, 28, 30}}, {{450, 1700, 2800}, {1, 24, 30}}, {{700, 1850, 3000}, {2, 23, 24}}, {{600, 900, 3150}, {2, 12, 38}}, {{490, 2400, 3100}, {2, 35, 31}}, /* female 20 */ {{300, 950, 2650}, {1, 21, 29}}, {{680, 1250, 2600}, {3, 23, 50}}, {{400, 850, 2700}, {3, 16, 44}}, {{500, 1050, 3000}, {4, 13, 42}}, {{390, 1550, 2500}, {2, 28, 35}}, {{250, 2300, 2900}, {0, 36, 38}}, {{250, 1950, 3600}, {0, 34, 45}}, {{420, 2100, 2600}, {2, 25, 34}}, {{420, 2100, 2600}, {2, 26, 34}}, {{600, 1500, 2800}, {5, 25, 36}}, {{450, 750, 2800}, {2, 11, 48}}, {{440, 2050, 2700}, {1, 27, 38}}, /* female 21 */ {{330, 750, 2900}, {1, 8, 44}}, {{1150, 1500, 2750}, {3, 8, 35}}, {{530, 950, 2850}, {0, 8, 40}}, {{850, 1050, 3000}, {5, 5, 36}}, {{500, 1700, 2700}, {0, 20, 31}}, {{300, 2600, 3100}, { -1, 23, 28}}, {{300, 1800, 2400}, {0, 22, 27}}, {{520, 2550, 3050}, {0, 22, 26}}, {{520, 1650, 2550}, {0, 20, 28}}, {{700, 1850, 2900}, {0, 16, 24}}, {{650, 1100, 2900}, { -1, 11, 36}}, {{450, 2300, 2800}, {0, 16, 17}}, /* female 22 */ {{300, 850, 2800}, {0, 15, 42}}, {{1080, 1400, 2750}, {2, 3, 21}}, {{480, 950, 2300}, {0, 6, 30}}, {{800, 1100, 2800}, {3, 3, 28}}, {{470, 1800, 2500}, {0, 12, 23}}, {{300, 2350, 2850}, { -1, 31, 31}}, {{300, 2100, 2600}, { -1, 25, 31}}, {{460, 2600, 2900}, {0, 20, 23}}, {{470, 1800, 2500}, {0, 16, 29}}, {{600, 2000, 2700}, {2, 13, 11}}, {{500, 750, 2650}, {4, 2, 24}}, {{500, 2300, 2750}, {0, 20, 22}}, /* female 23 */ {{350, 700, 2800}, {0, 10, 46}}, {{950, 1500, 2900}, {0, 19, 23}}, {{530, 980, 2850}, {0, 14, 34}}, {{750, 1100, 3000}, {4, 1, 27}}, {{520, 1800, 2450}, {2, 20, 25}}, {{300, 2550, 2950}, {0, 22, 24}}, {{300, 1950, 2450}, {0, 30, 31}}, {{500, 2300, 2800}, {0, 21, 29}}, {{550, 1700, 2750}, {0, 21, 24}}, {{650, 1850, 2700}, { -1, 16, 20}}, {{650, 980, 2650}, {1, 4, 34}}, {{500, 2400, 2800}, {4, 16, 18}}, /* female 24 */ {{300, 900, 2900}, {0, 12, 45}}, {{900, 1650, 2850}, {1, 6, 23}}, {{500, 900, 2300}, {0, 4, 39}}, {{750, 1150, 2750}, {2, 6, 27}}, {{550, 1650, 2500}, {0, 16, 24}}, {{300, 2500, 2850}, {0, 27, 34}}, {{250, 1850, 2300}, {0, 30, 26}}, {{490, 2400, 2850}, {2, 16, 18}}, {{520, 1800, 2450}, {3, 22, 23}}, {{650, 2100, 2800}, {2, 14, 13}}, {{550, 1100, 3900}, {2, 11, 32}}, {{510, 2350, 2950}, {1, 24, 23}}, /* djmw 20021212 L3 (was 33) */ /* female 25 */ {{300, 800, 3700}, {0, 13, 50}}, /* djmw 20021212 L2 (was 17) */ {{1000, 1450, 2650}, {4, 7, 24}}, {{550, 1000, 2850}, {8, 10, 43}}, {{750, 1050, 3000}, {2, 6, 33}}, {{500, 1550, 2400}, {4, 16, 25}}, {{250, 2400, 2950}, {0, 26, 24}}, {{300, 1800, 2400}, {0, 26, 26}}, {{490, 2300, 2800}, {8, 15, 20}}, {{550, 1550, 2500}, {1, 14, 25}}, {{700, 1950, 2750}, {0, 4, 13}}, {{630, 980, 2850}, {5, 7, 39}}, {{490, 2300, 2900}, {4, 17, 22}} }; try { autoTable me = Table_create (nrows, ncols); for (long i = 1; i <= nrows; i++) { TableRow row = (TableRow) my rows -> item[i]; int vowel_id = ( (i - 1) % 12) + 1; /* 1 - 12 */ int speaker_id = (i - 1) / 12 + 1; /* 1 - 75 */ int speaker_sex = speaker_id <= 50 ? 0 : 1; row -> cells [1]. string = Melder_wcsdup_f (sex [speaker_sex]); row -> cells [2]. string = Melder_wcsdup_f (Melder_integer (speaker_id)); row -> cells [3]. string = Melder_wcsdup_f (vowel [vowel_id - 1]); row -> cells [4]. string = Melder_wcsdup_f (ipa [vowel_id - 1]); for (long j = 0; j <= 2; j++) { row -> cells [j + 5]. string = Melder_wcsdup_f (Melder_integer (polsdata[i - 1].f[j])); row -> cells [j + 8]. string = Melder_wcsdup_f (Melder_integer (polsdata[i - 1].l[j])); } } for (long j = 1; j <= ncols; j++) { Table_setColumnLabel (me.peek(), j, columnLabels[j - 1]); my columnHeaders [j]. numericized = false; } return me.transfer(); } catch (MelderError) { Melder_throw ("Table not created from Pols & van Nierop data."); } } Table Table_createFromWeeninkData () { long nrows = 360, ncols = 9; const wchar_t *columnLabels[9] = {L"Type", L"Sex", L"Speaker", L"Vowel", L"IPA", L"F0", L"F1", L"F2", L"F3"}; const wchar_t *type[3] = {L"m", L"w", L"c"}; /* Our order: "oe", "o", "oo", "a", "aa", "u", "eu", "uu", "ie", "i", "ee", "e" to Pols & van Nierop order */ int order[13] = { 0, 1, 5, 3, 4, 7, 9, 8, 11, 6, 12, 2, 10}; const wchar_t *vowel[13] = {L"", L"oe", L"aa", L"oo", L"a", L"eu", L"ie", L"uu", L"ee", L"u", L"e", L"o", L"i"}; const wchar_t *ipa[13] = {L"", L"u", L"a", L"o", L"\\as", L"\\o/", L"i", L"y", L"e", L"\\yc", L"\\ep", L"\\ct", L"\\ic"}; const wchar_t *sex[2] = {L"m", L"f"}; struct weeninkdatum { short f[4]; /* f0, f1, f2, f3 */ } weeninkdata [] = { {{182, 335, 748, 2332}}, {{170, 435, 669, 2886}}, {{164, 488, 911, 2362}}, {{170, 671, 1005, 2822}}, {{160, 787, 1372, 3313}}, {{165, 396, 1624, 2374}}, {{165, 472, 1585, 2344}}, {{180, 293, 1791, 2177}}, {{176, 314, 2149, 3215}}, {{164, 393, 2120, 2694}}, {{161, 454, 1982, 2673}}, {{165, 502, 1902, 2632}}, /* Speaker 2 */ {{161, 308, 709, 2222}}, {{155, 461, 760, 2632}}, {{148, 510, 907, 2532}}, {{153, 645, 1004, 2604}}, {{145, 758, 1244, 2658}}, {{155, 449, 1489, 2279}}, {{145, 454, 1388, 2308}}, {{162, 314, 1620, 2111}}, {{158, 303, 1984, 2835}}, {{150, 429, 1888, 2502}}, {{156, 460, 1748, 2442}}, {{150, 580, 1679, 2383}}, /* Speaker 3 */ {{124, 343, 719, 2107}}, {{124, 519, 818, 1975}}, {{125, 532, 937, 2044}}, {{126, 721, 1135, 2077}}, {{125, 850, 1328, 2299}}, {{131, 390, 1307, 2177}}, {{129, 481, 1438, 2203}}, {{127, 270, 1705, 2068}}, {{121, 275, 2081, 2882}}, {{129, 377, 2044, 2638}}, {{131, 464, 1949, 2536}}, {{124, 645, 1854, 2488}}, /* Speaker 4 */ {{119, 322, 590, 2146}}, {{110, 438, 703, 2392}}, {{106, 489, 845, 2157}}, {{120, 708, 1126, 2302}}, {{107, 818, 1333, 2312}}, {{109, 406, 1505, 2133}}, {{109, 422, 1518, 2116}}, {{115, 298, 1581, 2162}}, {{119, 268, 2189, 2950}}, {{109, 400, 2151, 2870}}, {{108, 420, 2075, 2495}}, {{108, 550, 1905, 2383}}, /* Speaker 5 */ {{132, 282, 656, 2355}}, {{118, 462, 662, 2852}}, {{117, 482, 797, 2531}}, {{115, 723, 1036, 2456}}, {{117, 732, 1356, 2562}}, {{118, 454, 1516, 2178}}, {{119, 466, 1484, 2139}}, {{129, 271, 1642, 2154}}, {{122, 255, 2390, 2787}}, {{120, 353, 2114, 2507}}, {{114, 441, 2020, 2392}}, {{122, 601, 1858, 2315}}, /* Speaker 6 */ {{155, 275, 560, 2397}}, {{141, 395, 705, 2802}}, {{149, 419, 831, 1824}}, {{142, 674, 1113, 2455}}, {{137, 696, 1262, 2778}}, {{148, 419, 1493, 2242}}, {{148, 422, 1599, 2319}}, {{157, 291, 1585, 2160}}, {{152, 281, 2324, 3124}}, {{144, 358, 2269, 2936}}, {{146, 426, 2174, 2786}}, {{140, 560, 1941, 2722}}, /* Speaker 7 */ {{165, 315, 703, 2304}}, {{138, 531, 837, 2338}}, {{130, 471, 838, 2391}}, {{135, 713, 1218, 2466}}, {{140, 807, 1478, 2390}}, {{126, 467, 1639, 2227}}, {{135, 504, 1520, 2268}}, {{151, 341, 1738, 2246}}, {{145, 302, 2255, 2887}}, {{140, 379, 2183, 2614}}, {{133, 400, 2198, 2551}}, {{137, 587, 2024, 2516}}, /* Speaker 8 */ {{179, 361, 730, 2256}}, {{168, 500, 714, 2782}}, {{165, 495, 961, 2405}}, {{162, 642, 988, 2308}}, {{156, 921, 1409, 2909}}, {{166, 451, 1482, 2657}}, {{175, 505, 1546, 2443}}, {{177, 341, 1705, 2291}}, {{176, 285, 2288, 2817}}, {{173, 364, 2126, 2907}}, {{153, 492, 2102, 2778}}, {{158, 628, 1777, 2903}}, /* Speaker 9 */ {{180, 358, 700, 2672}}, {{177, 524, 759, 2784}}, {{169, 557, 856, 2727}}, {{178, 685, 1075, 2677}}, {{168, 855, 1311, 2701}}, {{170, 499, 1496, 2725}}, {{170, 502, 1385, 2112}}, {{178, 348, 1504, 2129}}, {{176, 318, 2252, 2846}}, {{169, 422, 2186, 2816}}, {{159, 509, 1941, 2732}}, {{165, 582, 1920, 2773}}, /* Speaker 10 */ {{161, 277, 592, 2493}}, {{141, 490, 718, 2757}}, {{137, 392, 692, 2512}}, {{142, 642, 991, 2707}}, {{144, 753, 1306, 2617}}, {{140, 388, 1570, 2175}}, {{139, 357, 1675, 2105}}, {{156, 248, 1846, 2117}}, {{148, 258, 2280, 3350}}, {{149, 367, 2129, 2731}}, {{142, 357, 2163, 2624}}, {{143, 581, 1865, 2572}}, /* Speaker 11 */ {{282, 305, 842, 2366}}, {{273, 557, 986, 2677}}, {{277, 606, 1090, 2422}}, {{274, 819, 1327, 2819}}, {{277, 938, 1580, 2953}}, {{278, 503, 1826, 2518}}, {{274, 579, 1630, 2501}}, {{286, 312, 2065, 3737}}, {{282, 291, 2540, 3225}}, {{278, 506, 2270, 3040}}, {{277, 559, 2245, 2846}}, {{277, 770, 2137, 2919}}, /* Speaker 12 */ {{255, 307, 738, 2529}}, {{265, 505, 938, 2641}}, {{228, 524, 1067, 2510}}, {{233, 902, 1183, 2603}}, {{215, 841, 1504, 2712}}, {{239, 464, 1655, 2556}}, {{234, 443, 1754, 2607}}, {{245, 303, 1762, 2460}}, {{241, 277, 2439, 3407}}, {{262, 490, 2371, 3198}}, {{228, 484, 2044, 2593}}, {{234, 495, 2296, 3204}}, /* Speaker 13 */ {{298, 309, 627, 3029}}, {{267, 785, 918, 2956}}, {{259, 600, 948, 2684}}, {{257, 893, 1136, 2844}}, {{245, 1028, 1498, 2715}}, {{258, 501, 1746, 2529}}, {{265, 536, 1799, 2601}}, {{280, 282, 1391, 2520}}, {{270, 275, 2664, 3174}}, {{260, 511, 2320, 2882}}, {{255, 506, 2482, 2846}}, {{258, 783, 2027, 2606}}, /* Speaker 14 */ {{187, 327, 586, 2463}}, {{177, 520, 690, 2828}}, {{175, 540, 956, 2599}}, {{178, 596, 1023, 2750}}, {{184, 692, 1382, 2432}}, {{186, 397, 1658, 2422}}, {{175, 512, 1674, 2458}}, {{186, 291, 1737, 2236}}, {{203, 271, 2299, 3260}}, {{187, 369, 2263, 2903}}, {{182, 471, 2057, 2729}}, {{196, 593, 2122, 2779}}, /* Speaker 15 */ {{263, 448, 830, 2687}}, {{230, 570, 1010, 2614}}, {{244, 595, 1109, 2686}}, {{240, 806, 1386, 2591}}, {{239, 890, 1574, 2965}}, {{244, 482, 1900, 2710}}, {{251, 502, 1529, 2716}}, {{238, 436, 2134, 2626}}, {{254, 374, 2580, 3181}}, {{252, 494, 2323, 2989}}, {{242, 484, 2323, 3025}}, {{246, 595, 1897, 2865}}, /* Speaker 16 */ {{238, 325, 737, 2290}}, {{224, 462, 764, 2600}}, {{202, 577, 944, 2651}}, {{216, 674, 1084, 2851}}, {{210, 833, 1333, 2256}}, {{214, 427, 1708, 2346}}, {{202, 502, 1546, 2326}}, {{242, 289, 1669, 2169}}, {{232, 337, 2060, 2841}}, {{224, 416, 2217, 2769}}, {{214, 491, 1950, 2674}}, {{188, 548, 2071, 2727}}, /* Speaker 17 */ {{277, 313, 578, 2457}}, {{254, 549, 855, 2793}}, {{250, 608, 904, 2724}}, {{267, 890, 1294, 2732}}, {{263, 1047, 1578, 2848}}, {{289, 549, 1728, 2844}}, {{258, 508, 1747, 2799}}, {{284, 287, 1982, 2793}}, {{268, 268, 2873, 4075}}, {{258, 440, 2590, 3090}}, {{248, 489, 2529, 3111}}, {{261, 606, 2078, 2980}}, /* Speaker 18 */ {{330, 334, 729, 3332}}, {{247, 629, 864, 3024}}, {{234, 521, 935, 2760}}, {{264, 964, 1246, 3112}}, {{261, 1008, 1573, 2932}}, {{278, 509, 1887, 2596}}, {{243, 487, 1799, 2393}}, {{303, 306, 1781, 2415}}, {{282, 296, 2597, 3571}}, {{217, 425, 2636, 3314}}, {{250, 490, 2642, 3494}}, {{275, 787, 2326, 2992}}, /* Speaker 19 */ {{228, 322, 661, 2721}}, {{214, 589, 821, 2729}}, {{219, 457, 857, 2582}}, {{229, 801, 1260, 2911}}, {{220, 898, 1628, 2770}}, {{233, 463, 1630, 2306}}, {{225, 456, 1671, 2381}}, {{225, 283, 1779, 2211}}, {{224, 276, 2495, 3372}}, {{224, 440, 2385, 3007}}, {{216, 435, 2363, 2866}}, {{212, 637, 2130, 3029}}, /* Speaker 20 */ {{246, 324, 730, 2644}}, {{230, 636, 923, 2757}}, {{233, 534, 954, 2542}}, {{234, 820, 1256, 3064}}, {{248, 966, 1695, 2890}}, {{237, 484, 1753, 2718}}, {{240, 480, 1917, 2670}}, {{247, 291, 1981, 2701}}, {{243, 290, 2648, 3176}}, {{256, 501, 2358, 3058}}, {{238, 469, 2406, 3008}}, {{236, 693, 2128, 2991}}, /* Speaker 21 */ {{342, 353, 758, 3269}}, {{309, 627, 976, 3256}}, {{334, 663, 1017, 3075}}, {{321, 964, 1576, 3186}}, {{316, 1129, 2249, 3404}}, {{330, 650, 2336, 3284}}, {{311, 636, 2083, 3328}}, {{331, 357, 2389, 3185}}, {{332, 337, 2960, 3595}}, {{351, 586, 2833, 3595}}, {{312, 621, 2839, 3614}}, {{309, 765, 2755, 3636}}, /* Speaker 22 */ {{326, 359, 682, 2948}}, {{318, 631, 795, 3537}}, {{296, 688, 1135, 2930}}, {{285, 746, 1135, 1926}}, {{290, 1006, 2166, 3263}}, {{326, 632, 1990, 3042}}, {{285, 570, 2015, 3155}}, {{321, 324, 2025, 3104}}, {{338, 346, 3069, 3573}}, {{320, 636, 3025, 3709}}, {{306, 611, 2770, 3648}}, {{331, 893, 2639, 3566}}, /* Speaker 23 */ {{312, 414, 828, 2908}}, {{314, 609, 936, 3139}}, {{305, 659, 1201, 3015}}, {{298, 890, 1303, 3003}}, {{300, 1150, 2116, 3205}}, {{275, 537, 1968, 3032}}, {{277, 534, 1997, 3009}}, {{304, 398, 2298, 2940}}, {{302, 330, 3010, 3746}}, {{312, 547, 2965, 3673}}, {{275, 551, 2786, 3442}}, {{299, 641, 2662, 3410}}, /* Speaker 24 */ {{301, 315, 812, 3357}}, {{316, 621, 960, 3701}}, {{305, 604, 1179, 3659}}, {{331, 981, 1701, 3374}}, {{322, 954, 2010, 3291}}, {{297, 581, 2085, 3288}}, {{307, 613, 1991, 3392}}, {{322, 331, 2099, 3096}}, {{326, 326, 3235, 3935}}, {{307, 547, 2747, 3618}}, {{308, 613, 2763, 3710}}, {{315, 622, 2459, 3616}}, /* Speaker 25 */ {{360, 417, 981, 3610}}, {{354, 697, 1017, 3077}}, {{363, 741, 1302, 3381}}, {{340, 1028, 1611, 2973}}, {{337, 1122, 1930, 3068}}, {{310, 608, 2105, 3177}}, {{323, 628, 1929, 3197}}, {{378, 384, 2255, 2992}}, {{363, 363, 3235, 4069}}, {{338, 527, 2698, 3458}}, {{308, 643, 2603, 3382}}, {{326, 712, 2351, 3498}}, /* Speaker 26 */ {{375, 380, 798, 3316}}, {{371, 456, 759, 3321}}, {{324, 656, 1118, 3296}}, {{340, 1031, 1690, 3163}}, {{376, 1154, 1920, 3519}}, {{362, 604, 2162, 3603}}, {{342, 679, 2035, 3683}}, {{371, 374, 2042, 3206}}, {{349, 361, 3082, 3782}}, {{357, 499, 2899, 3934}}, {{324, 646, 2820, 3970}}, {{353, 706, 2785, 3942}}, /* Speaker 27 */ {{312, 339, 850, 4356}}, {{319, 619, 919, 3570}}, {{288, 576, 1156, 3681}}, {{301, 865, 1567, 3326}}, {{296, 914, 2090, 3113}}, {{297, 589, 2150, 3208}}, {{287, 580, 2146, 3340}}, {{303, 330, 2431, 3032}}, {{291, 313, 3090, 4039}}, {{305, 539, 3015, 3905}}, {{291, 577, 2589, 2778}}, {{307, 616, 2448, 3856}}, /* Speaker 28 */ {{353, 354, 1085, 3082}}, {{343, 617, 990, 3027}}, {{281, 822, 1180, 2931}}, {{324, 993, 1424, 2941}}, {{297, 1192, 1792, 2922}}, {{314, 444, 2170, 3044}}, {{275, 608, 1817, 2909}}, {{355, 358, 2138, 3160}}, {{321, 323, 3169, 3625}}, {{315, 499, 2831, 3465}}, {{303, 608, 2707, 3369}}, {{313, 718, 2479, 3627}}, /* Speaker 29 */ {{361, 363, 1050, 3239}}, {{365, 666, 1094, 3269}}, {{327, 830, 1289, 3145}}, {{325, 963, 1293, 3046}}, {{356, 1163, 1707, 3188}}, {{377, 580, 2191, 3234}}, {{336, 673, 2339, 3167}}, {{342, 345, 2344, 3103}}, {{341, 346, 2729, 3370}}, {{326, 541, 2568, 3297}}, {{331, 677, 2561, 3320}}, {{354, 897, 2463, 3338}}, /* Speaker 30 */ {{332, 352, 979, 2988}}, {{286, 596, 973, 2690}}, {{304, 753, 1174, 3005}}, {{290, 884, 1432, 2806}}, {{347, 1060, 2079, 2706}}, {{303, 592, 2069, 2889}}, {{299, 644, 1775, 3005}}, {{296, 329, 2082, 2791}}, {{315, 326, 2807, 3612}}, {{298, 561, 2612, 3330}}, {{281, 569, 2415, 3239}}, {{280, 709, 2460, 3314}} }; try { autoTable me = Table_create (nrows, ncols); for (long i = 1; i <= nrows; i++) { TableRow row = (TableRow) my rows -> item[i]; int speaker_id = (i - 1) / 12 + 1; /* 1 - 30 */ int vowel_id = (i - 1) % 12 + 1; /* 1 - 12 */ int index_in_data = (speaker_id - 1) * 12 + order[vowel_id] - 1; int speaker_type, speaker_sex; if (speaker_id <= 10) { /* 10 men */ speaker_type = 0; speaker_sex = 0; } else if (speaker_id <= 20) { /* 10 women */ speaker_type = 1; speaker_sex = 1; } else { /* 10 children */ speaker_type = 2; speaker_sex = 0; // Which children were m/f ? } row -> cells [1]. string = Melder_wcsdup_f (type [speaker_type]); row -> cells [2]. string = Melder_wcsdup_f (sex [speaker_sex]); row -> cells [3]. string = Melder_wcsdup_f (Melder_integer (speaker_id)); row -> cells [4]. string = Melder_wcsdup_f (vowel [vowel_id]); row -> cells [5]. string = Melder_wcsdup_f (ipa [vowel_id]); for (long j = 0; j <= 3; j++) { row -> cells [j + 6]. string = Melder_wcsdup_f (Melder_integer (weeninkdata[index_in_data].f[j])); } } for (long j = 1; j <= ncols; j++) { Table_setColumnLabel (me.peek(), j, columnLabels[j - 1]); my columnHeaders [j]. numericized = false; } return me.transfer(); } catch (MelderError) { Melder_throw ("Table not created from Weenink data."); } } void Table_drawScatterPlotWithConfidenceIntervals (Table me, Graphics g, long xcolumn, long ycolumn, double xmin, double xmax, double ymin, double ymax, long xci_min, long xci_max, long yci_min, long yci_max, double bar_mm, int garnish) { long nrows = my rows -> size; double x2min, x1max, y1max, y2min; double bar = ceil (bar_mm * g -> resolution / 25.4); // check validity of columns if (xcolumn < 1 || xcolumn > nrows || ycolumn < 1 || ycolumn > nrows) { return; } if (labs (xci_min) > nrows || labs (xci_max) > nrows || labs (yci_min) > nrows || labs (yci_max) > nrows) { return; } if (xmin >= xmax && Table_getExtrema (me, xci_min, &xmin, &x1max) && Table_getExtrema (me, xci_max, &x2min, &xmax) && xmin >= xmax) { return; } if (ymin >= ymax && Table_getExtrema (me, yci_min, &ymin, &y1max) && Table_getExtrema (me, yci_max, &y2min, &ymax) && ymin >= ymax) { return; } Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setInner (g); for (long row = 1; row <= nrows; row++) { double x = Table_getNumericValue_Assert (me, row, xcolumn); double y = Table_getNumericValue_Assert (me, row, ycolumn); double x1 = Table_getNumericValue_Assert (me, row, xci_min); double x2 = Table_getNumericValue_Assert (me, row, xci_max); double y1 = Table_getNumericValue_Assert (me, row, yci_min); double y2 = Table_getNumericValue_Assert (me, row, yci_max); double xo1, yo1, xo2, yo2; if (xci_min > 0) { if (NUMclipLineWithinRectangle (x1, y, x, y, xmin, ymin, xmax, ymax, &xo1, &yo1, &xo2, &yo2)) { Graphics_line (g, xo1, yo1, xo2, yo2); } if (bar > 0 && NUMclipLineWithinRectangle (x1, y - bar / 2, x1, y + bar / 2, xmin, ymin, xmax, ymax, &xo1, &yo1, &xo2, &yo2)) { Graphics_line (g, xo1, yo1, xo2, yo2); } } if (xci_max > 0) { if (NUMclipLineWithinRectangle (x, y, x2, y, xmin, ymin, xmax, ymax, &xo1, &yo1, &xo2, &yo2)) { Graphics_line (g, xo1, yo1, xo2, yo2); } if (bar > 0 && NUMclipLineWithinRectangle (x2, y - bar / 2, x2, y + bar / 2, xmin, ymin, xmax, ymax, &xo1, &yo1, &xo2, &yo2)) { Graphics_line (g, xo1, yo1, xo2, yo2); } } if (yci_min > 0) { if (NUMclipLineWithinRectangle (x, y1, x, y, xmin, ymin, xmax, ymax, &xo1, &yo1, &xo2, &yo2)) { Graphics_line (g, xo1, yo1, xo2, yo2); } if (bar > 0 && NUMclipLineWithinRectangle (x - bar / 2, y1, x + bar / 2, y1, xmin, ymin, xmax, ymax, &xo1, &yo1, &xo2, &yo2)) { Graphics_line (g, xo1, yo1, xo2, yo2); } } if (yci_max > 0) { if (NUMclipLineWithinRectangle (x, y, x, y2, xmin, ymin, xmax, ymax, &xo1, &yo1, &xo2, &yo2)) { Graphics_line (g, xo1, yo1, xo2, yo2); } if (bar > 0 && NUMclipLineWithinRectangle (x - bar / 2, y2, x + bar / 2, y2, xmin, ymin, xmax, ymax, &xo1, &yo1, &xo2, &yo2)) { Graphics_line (g, xo1, yo1, xo2, yo2); } } } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_marksBottom (g, 2, 1, 1, 0); } } double Table_getMedianAbsoluteDeviation (Table me, long columnNumber) try { Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); Table_numericize_Assert (me, columnNumber); if (my rows -> size < 1) { return NUMundefined; } autoNUMvector data (1, my rows -> size); for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); data[irow] = row -> cells[columnNumber].number; if (data[irow] == NUMundefined) { Melder_throw (me, ": the cell in row ", irow, " of column \"", my columnHeaders[columnNumber].label ? my columnHeaders[columnNumber].label : Melder_integer (columnNumber), " is undefined."); } } double mad, location; NUMmad (data.peek(), my rows -> size, &location, 1, &mad, 0); return mad; } catch (MelderError) { Melder_throw (me, ": cannot compute median absolute deviation of column ", columnNumber, "."); } /* End of file Table_extensions.cpp */ sources_5316/dwtools/.Sound_extensions.cpp.kate-swp0000664000176700017670000001123411721653675021321 0ustar paulpaulKate Swap File - Version 1.0SW÷ESIøvESIøoESIøiESIødESIø ESIøSESIøoESIøuESIønESIø dESIø _ESIø pESIø lESIø aESIøyESIøCESIøhESIøaESIønESIønESIøeESIølESIø ESIø9ESIøSESIøoESIøuESIønESIødESIø ESIømESIøeESIø ,ESIø! ESIø"lESIø#oESIø$nESIø%gESIø& ESIø'cESIø(hESIø)aESIø*nESIø+nESIø,eESIø-lESIø.)ESIø/ ESIø0{ESWø1Iù ESWùIú ESRúESIú}ESWúESRùESIù ESIùtESIùrESIùyESIù ESIù{ESWù Iú ESWúIû ESRûIû ESIû}RûIû ESIû ESIûcESIûaESIûtESIû cESIû hESIû  ESIû (ESIû MESIûeESIûlESIûdESIûeESIûrESIûEESIûrESIûrESIûoESIûrESIû)ESIû ESIû{ESWûIü ESIüMESIü eESIü lESIü dESIü eESIü rESIü_ESIütESIühESIürESIüoESIüwESIü ESIü(ESRøIø(ESIü"ESIücESIühESIüaESIünESIünESIüeESIülESRüESIüCESIümESIüeESIü,ESIü ESRüIü:ESIü ESIücESIü$ ESIü%"ESIü&,ESIü' ESIü(MESIü)eESIü*lESIü+dESIü,eESIü-rESIü._ESIü/iESIü0nESIü1tESIü2eESIü3gESIü4eESIü5rESIü6 ESIü7(ESIü8cESIü9hESIü:aESIü;nESIü<nESIü=eESIü>lESIü?)ESIü@,ESIüA ESIüB"ESIüC ESIüDnESIüEoESIüFtESIüG ESIüHpESIüIlESIüJaESIüKyESIüLeESIüMdESIüN.ESIüO"ESIüP)ESIüQ;ESWüRIý ESRýIý ESIý}RýIý ESWù Iú ESIúaESIú uESIú tESIú oESIú SESIú oESIúuESIúnESIúdESIú ESIútESIúhESIúeESIúeESIú ESIú=ESIú ESIú.Sound_extractChannel (Sound me, long ichannel)ESRú/5ESIø'iESRú37ESRú23ESIú<;ESIûSESIû oESIû uESIû nESIû dESIû _ESIûpESIûlESIûaESIûyESIû ESIû(ESIûtESIûhESIûeESIûeESIû.ESIûpESIûeESIûeESIûkESIû(ESIû)ESIû,ESIû  ESIû!0ESIû",ESIû# ESIû$0ESIû%)ESIû&;ESRû'Rú=UüUûESWù Iú= autoSound thee = Sound_extractChannel (me, ichannel);Wú=Iû' Sound_play (thee.peek(), 0, 0);ESRû'ESRú<=ESIú2 longESRø'(ESIú/Sound ESRúGESRúESRúUúESRýIý RýESRýIý ESRýUýESRü$RESRüESRüIüCESRüESRüESIücESRüESRøIø9ESRüESRüUüESRûESRûIû RûESRûIû ESRûUûESRúUúESRù ESIù ESUûESRúESIú ESRúUúESRùUùESRø1ESUøEsources_5316/dwtools/KlattGridEditors.cpp0000644000176700017670000003332511634333436017355 0ustar paulpaul/* KlattGridEditors.c * * Copyright (C) 2009-2011 david Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * djmw 20090123 * djmw 20090128 Remove source menu from formant grid editor. * djmw 20090420 dbEditor * djmw 20090527 Protect FormantGridEditor against empty FormantGrids. * djmw 20110304 Thing_new */ #include "Preferences.h" #include "KlattGridEditors.h" #include "EditorM.h" static void KlattGrid_Editor_defaultPlay (KlattGrid me, double tmin, double tmax) { my options -> xmin = tmin; my options-> xmax = tmax; KlattGrid_playSpecial (me); } /************************** KlattGrid_realTierEditor *********************************/ Thing_implement (KlattGrid_realTierEditor, RealTierEditor, 0); static void menu_cb_KlattGridHelp (EDITOR_ARGS) { EDITOR_IAM (KlattGrid_realTierEditor); Melder_help (L"KlattGrid"); } void structKlattGrid_realTierEditor :: v_createHelpMenuItems (EditorMenu menu) { KlattGrid_realTierEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"KlattGrid help", 0, menu_cb_KlattGridHelp); } void structKlattGrid_realTierEditor :: v_play (double ltmin, double ltmax) { KlattGrid_Editor_defaultPlay (klattgrid, ltmin, ltmax); } void KlattGrid_realTierEditor_init (KlattGrid_realTierEditor me, GuiObject parent, const wchar_t *title, KlattGrid klattgrid, RealTier data) { my klattgrid = klattgrid; RealTierEditor_init (me, parent, title, data, 0, 0); } /************************** KlattGrid_pitchTierEditor *********************************/ Thing_implement (KlattGrid_pitchTierEditor, KlattGrid_realTierEditor, 0); static void menu_cb_KlattGrid_pitchTierEditorHelp (EDITOR_ARGS) { EDITOR_IAM (KlattGrid_pitchTierEditor); Melder_help (L"PitchTierEditor"); } static void menu_cb_PitchTierHelp (EDITOR_ARGS) { EDITOR_IAM (KlattGrid_pitchTierEditor); Melder_help (L"PitchTier"); } void structKlattGrid_pitchTierEditor :: v_createHelpMenuItems (EditorMenu menu) { EditorMenu_addCommand (menu, L"PitchTierEditor help", 0, menu_cb_KlattGrid_pitchTierEditorHelp); EditorMenu_addCommand (menu, L"PitchTier help", 0, menu_cb_PitchTierHelp); } KlattGrid_pitchTierEditor KlattGrid_pitchTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_pitchTierEditor me = Thing_new (KlattGrid_pitchTierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> pitch; KlattGrid_realTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid pitch window not created."); } } /************************** KlattGrid_intensityTierEditor *********************************/ Thing_implement (KlattGrid_intensityTierEditor, KlattGrid_realTierEditor, 0); static void menu_cb_IntensityTierHelp (EDITOR_ARGS) { EDITOR_IAM (KlattGrid_intensityTierEditor); Melder_help (L"IntensityTier"); } void structKlattGrid_intensityTierEditor :: v_createHelpMenuItems (EditorMenu menu) { KlattGrid_intensityTierEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"IntensityTier help", 0, menu_cb_IntensityTierHelp); } void KlattGrid_intensityTierEditor_init (KlattGrid_intensityTierEditor me, GuiObject parent, const wchar_t *title, KlattGrid klattgrid, RealTier tier) { KlattGrid_realTierEditor_init (me, parent, title, klattgrid, tier); } /************************** KlattGrid_DecibelTierEditor *********************************/ Thing_implement (KlattGrid_decibelTierEditor, KlattGrid_intensityTierEditor, 0); KlattGrid_decibelTierEditor KlattGrid_decibelTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid, RealTier tier) { try { autoKlattGrid_decibelTierEditor me = Thing_new (KlattGrid_decibelTierEditor); KlattGrid_intensityTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid decibel window not created."); } } /************************** KlattGrid_voicingAmplitudeTierEditor *********************************/ Thing_implement (KlattGrid_voicingAmplitudeTierEditor, KlattGrid_intensityTierEditor, 0); KlattGrid_voicingAmplitudeTierEditor KlattGrid_voicingAmplitudeTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_voicingAmplitudeTierEditor me = Thing_new (KlattGrid_voicingAmplitudeTierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> voicingAmplitude; KlattGrid_intensityTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid voicing amplitude window not created."); } } /************************** KlattGrid_aspirationAmplitudeTierEditor *********************************/ Thing_implement (KlattGrid_aspirationAmplitudeTierEditor, KlattGrid_intensityTierEditor, 0); KlattGrid_aspirationAmplitudeTierEditor KlattGrid_aspirationAmplitudeTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_aspirationAmplitudeTierEditor me = Thing_new (KlattGrid_aspirationAmplitudeTierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> aspirationAmplitude; KlattGrid_intensityTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid aspiration amplitude window not created."); } } /************************** KlattGrid_breathinessAmplitudeTierEditor *********************************/ Thing_implement (KlattGrid_breathinessAmplitudeTierEditor, KlattGrid_intensityTierEditor, 0); KlattGrid_breathinessAmplitudeTierEditor KlattGrid_breathinessAmplitudeTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_breathinessAmplitudeTierEditor me = Thing_new (KlattGrid_breathinessAmplitudeTierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> breathinessAmplitude; KlattGrid_intensityTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid breathiness amplitude window not created."); } } /************************** KlattGrid_spectralTiltTierEditor *********************************/ Thing_implement (KlattGrid_spectralTiltTierEditor, KlattGrid_intensityTierEditor, 0); KlattGrid_spectralTiltTierEditor KlattGrid_spectralTiltTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_spectralTiltTierEditor me = Thing_new (KlattGrid_spectralTiltTierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> spectralTilt; KlattGrid_intensityTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid spectral tilt window not created."); } } /************************** KlattGrid_fricationBypassTierEditor *********************************/ Thing_implement (KlattGrid_fricationBypassTierEditor, KlattGrid_intensityTierEditor, 0); KlattGrid_fricationBypassTierEditor KlattGrid_fricationBypassTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_fricationBypassTierEditor me = Thing_new (KlattGrid_fricationBypassTierEditor); RealTier tier = (RealTier) klattgrid -> frication -> bypass; KlattGrid_intensityTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid frication bypass window not created."); } } /************************** KlattGrid_fricationAmplitudeTierEditor *********************************/ Thing_implement (KlattGrid_fricationAmplitudeTierEditor, KlattGrid_intensityTierEditor, 0); KlattGrid_fricationAmplitudeTierEditor KlattGrid_fricationAmplitudeTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_fricationAmplitudeTierEditor me = Thing_new (KlattGrid_fricationAmplitudeTierEditor); RealTier tier = (RealTier) klattgrid -> frication -> fricationAmplitude; KlattGrid_intensityTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid frication amplitude window not created."); } } /************************** KlattGrid_openPhaseTierEditor *********************************/ Thing_implement (KlattGrid_openPhaseTierEditor, KlattGrid_realTierEditor, 0); KlattGrid_openPhaseTierEditor KlattGrid_openPhaseTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_openPhaseTierEditor me = Thing_new (KlattGrid_openPhaseTierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> openPhase; KlattGrid_realTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid_openPhaseTierEditor not created."); } } /************************** KlattGrid_collisionPhaseTierEditor *********************************/ Thing_implement (KlattGrid_collisionPhaseTierEditor, KlattGrid_realTierEditor, 0); KlattGrid_collisionPhaseTierEditor KlattGrid_collisionPhaseTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_collisionPhaseTierEditor me = Thing_new (KlattGrid_collisionPhaseTierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> collisionPhase; KlattGrid_realTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid collision phase window not created."); } } /************************** KlattGrid_power1TierEditor *********************************/ Thing_implement (KlattGrid_power1TierEditor, KlattGrid_realTierEditor, 0); KlattGrid_power1TierEditor KlattGrid_power1TierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_power1TierEditor me = Thing_new (KlattGrid_power1TierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> power1; KlattGrid_realTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid power1 window not created."); } } /************************** KlattGrid_power2TierEditor *********************************/ Thing_implement (KlattGrid_power2TierEditor, KlattGrid_realTierEditor, 0); KlattGrid_power2TierEditor KlattGrid_power2TierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_power2TierEditor me = Thing_new (KlattGrid_power2TierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> power2; KlattGrid_realTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid power2 window not created."); } } /************************** KlattGrid_flutterTierEditor *********************************/ Thing_implement (KlattGrid_flutterTierEditor, KlattGrid_realTierEditor, 0); KlattGrid_flutterTierEditor KlattGrid_flutterTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_flutterTierEditor me = Thing_new (KlattGrid_flutterTierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> flutter; KlattGrid_realTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid flutter window not created."); } } /************************** KlattGrid_doublePulsingTierEditor *********************************/ Thing_implement (KlattGrid_doublePulsingTierEditor, KlattGrid_realTierEditor, 0); KlattGrid_doublePulsingTierEditor KlattGrid_doublePulsingTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid) { try { autoKlattGrid_doublePulsingTierEditor me = Thing_new (KlattGrid_doublePulsingTierEditor); RealTier tier = (RealTier) klattgrid -> phonation -> doublePulsing; KlattGrid_realTierEditor_init (me.peek(), parent, title, klattgrid, tier); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid double pulsing window not created."); } } /************************** KlattGrid_formantGridEditor *********************************/ Thing_implement (KlattGrid_formantGridEditor, FormantGridEditor, 0); static bool FormantGrid_isEmpty (FormantGrid me) { return my formants -> size == 0 || my bandwidths -> size == 0; } void structKlattGrid_formantGridEditor :: v_play (double ltmin, double ltmax) { KlattGrid_Editor_defaultPlay (klattgrid, ltmin, ltmax); } KlattGrid_formantGridEditor KlattGrid_formantGridEditor_create (GuiObject parent, const wchar_t *title, KlattGrid data, int formantType) { try { Melder_assert (data != NULL); FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (data, formantType); if (fg == NULL) { Melder_throw ("Formant type unknown."); } if (FormantGrid_isEmpty (*fg)) { Melder_throw ("Cannot edit an empty formant grid."); } autoKlattGrid_formantGridEditor me = Thing_new (KlattGrid_formantGridEditor); my klattgrid = data; FormantGridEditor_init (me.peek(), parent, title, *fg); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid formant window not created."); } } /* End of file KlattGridEditors.cpp */ sources_5316/dwtools/VowelEditor.cpp0000664000176700017670000017715511747467621016426 0ustar paulpaul/* VowelEditor.c * * Copyright (C) 2008-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20080202, 20080330 djmw 20090114 FormantTier_to_FormantGrid. djmw 20090613 Extract KlattGrid djmw 20110329 Table_get(Numeric|String)Value is now Table_get(Numeric|String)Value_Assert djmw 20110331 Corrected a typo */ /* trajectory --> path ???? The main part of the VowelEditor is a drawing area. In this drawing area a cursor can be moved around by a mouse. The position of the cursor is related to the F1 and F2 frequencies. On_mouse_down the position of the cursor is sampled (Not a fixed intervals!). This results in a series of (x,y) values that will be transformed to (F1,F2) values in Hertz The corresponding sound wil be made audible until the mouse is released. Graphics area is F1-F2 plane. Origin top-right with log(F2) horizontal and log(F1) vertical). Axis orientation from topright: F1 down, F2 to the left. F1, F2 are always evaluated to Hz; In the Graphics part, the Graphics_window (0, 1, 0, 1), i.e. origin is bottom-left. log(fmin) -> 1; log(fmax)-> 0 Transformations XY <=> F1F2: VowelEditor_getXYFromF1F2(...) and VowelEditor_getF1F2FromXY(...) For x direction F2 from right to left 1 = a * log(f2min) +b 0 = a * log(f2max) +b x' = a (log(f2)-log(f2max)) 1 = a * log(f1min) +b 0 = a * log(f1max) +b y' = a (log(f1)-log(f1max)) TO DO: The third and higher formant frequencies can also be set indirectly by defining them as functions on the f1,f2 plane (for example, by an object of type Matrix). Make sound-follows-mouse real time! */ #include "FormantGrid.h" #include "KlattGrid.h" #include "../external/portaudio/portaudio.h" #include "praat.h" #include "PitchTier_to_PointProcess.h" #include "PitchTier_to_Sound.h" #include "PointProcess_and_Sound.h" #include "Polygon.h" #include "TableOfReal_extensions.h" #include "Table_extensions.h" #include "VowelEditor.h" #include "machine.h" #include "Preferences.h" #include "EditorM.h" #include #if defined (macintosh) #include #elif defined (linux) #include #include #endif Thing_implement (VowelEditor, Editor, 0); // Male, Female, Child speaker #define VG_SPEAKER_M 0 #define VG_SPEAKER_F 1 #define VG_SPEAKER_C 2 // STATUS_INFO >=Gui_LABEL_HEIGHT !! #define STATUS_INFO (1.5*Gui_LABEL_HEIGHT) #define MARGIN_RIGHT 10 #define MARGIN_LEFT 50 #define MARGIN_TOP 50 #define MARGIN_BOTTOM (60+STATUS_INFO) #define BUFFER_SIZE_SEC 4 #define SAMPLING_FREQUENCY 44100 #define STATUSINFO_STARTINTR0 L"Start (F1,F2,F0) = (" #define STATUSINFO_ENDINTR0 L"End (F1,F2,F0) = (" #define STATUSINFO_ENDING L")" #define MICROSECPRECISION(x) (round((x)*1000000)/1000000) // To prevent the generation of inaudible short Sounds we set a minimum duration #define MINIMUM_SOUND_DURATION 0.01 // maximum number of marks #define VowelEditor_MAXIMUM_MARKERS 30 // prototypes: button callbacks static void gui_button_cb_publish (I, GuiButtonEvent event); static void gui_button_cb_play (I, GuiButtonEvent event); static void gui_drawingarea_cb_resize (I, GuiDrawingAreaResizeEvent event); static void gui_drawingarea_cb_click (I, GuiDrawingAreaClickEvent event); static void gui_button_cb_reverse (I, GuiButtonEvent event); static void gui_drawingarea_cb_expose (I, GuiDrawingAreaExposeEvent event); // prototypes: helpers static double getRealFromTextWidget (GuiObject me); static double getCoordinate (double fmin, double fmax, double f); static double getF0 (structVowelEditor_F0 *f0p, double time); static void checkF1F2 (VowelEditor me, double *f1, double *f2); static void checkF0 (structVowelEditor_F0 *f0p, double *f0); static void checkXY (double *x, double *y); static void Sound_fadeIn (Sound me, double duration, int fromFirstNonZeroSample); static void Sound_fadeOut (Sound me, double duration); static void PitchTier_newDuration (PitchTier me, structVowelEditor_F0 *f0p, double newDuration); static void FormantTier_newDuration (FormantTier me, double newDuration); static void FormantTier_drawF1F2Trajectory (FormantTier me, Graphics g, double f1min, double f1max, double f2min, double f2max, double markTraceEvery, double width); static FormantGrid FormantTier_to_FormantGrid (FormantTier me); static PitchTier VowelEditor_to_PitchTier (VowelEditor me, double duration); static void VowelEditor_updateF0Info (VowelEditor me); static void VowelEditor_updateExtendDuration (VowelEditor me); static double VowelEditor_updateDurationInfo (VowelEditor me); static void VowelEditor_Vowel_updateTiers (VowelEditor me, Vowel thee, double time, double x, double y); static void VowelEditor_Vowel_addData (VowelEditor me, Vowel thee, double time, double f1, double f2, double f0); static void VowelEditor_getXYFromF1F2 (VowelEditor me, double f1, double f2, double *x, double *y); static void VowelEditor_getF1F2FromXY (VowelEditor me, double x, double y, double *f1, double *f2); static void VowelEditor_updateVowel (VowelEditor me); static Sound VowelEditor_createTarget (VowelEditor me); static void VowelEditor_Vowel_reverseFormantTier (VowelEditor me); static void VowelEditor_shiftF1F2 (VowelEditor me, double f1_st, double f2_st); static void VowelEditor_setSource (VowelEditor me); static void VowelEditor_setMarks (VowelEditor me, int marksDataset, int speakerType, int fontSize); static void VowelEditor_setF3F4 (VowelEditor me, double f3, double b3, double f4, double b4); static void VowelEditor_getF3F4 (VowelEditor me, double f1, double f2, double *f3, double *b3, double *f4, double *b4); static void VowelEditor_getVowelMarksFromTableFile (VowelEditor me, MelderFile file); static void VowelEditor_createTableFromVowelMarksInPreferences (VowelEditor me); static void Table_addColumn_size (Table me, int size); static double Matrix_getValue (Matrix me, double x, double y); static void VowelEditor_drawBackground (VowelEditor me, Graphics g); static void createPersistentVowelMarks (); static void copyVowelMarksInPreferences_volatile (Table me); static Vowel Vowel_create (double duration); static Vowel Vowel_create_twoFormantSchwa (double duration); static void Vowel_newDuration (Vowel me, structVowelEditor_F0 *f0p, double newDuration); static Sound Vowel_to_Sound_pulses (Vowel me, double samplingFrequency, double adaptFactor, double adaptTime, long interpolationDepth); // forward declarations end static struct structVowelEditor_F0 f0default = { 140.0, 0.0, 40.0, 2000.0, SAMPLING_FREQUENCY, 1, 0.0, 2000 }; static struct structVowelEditor_F1F2Grid griddefault = { 200, 500, 0, 1, 0, 1, 0.5 }; #include "oo_DESTROY.h" #include "Vowel_def.h" #include "oo_COPY.h" #include "Vowel_def.h" #include "oo_EQUAL.h" #include "Vowel_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Vowel_def.h" #include "oo_WRITE_TEXT.h" #include "Vowel_def.h" #include "oo_READ_TEXT.h" #include "Vowel_def.h" #include "oo_WRITE_BINARY.h" #include "Vowel_def.h" #include "oo_READ_BINARY.h" #include "Vowel_def.h" #include "oo_DESCRIPTION.h" #include "Vowel_def.h" // Preferences structs struct markInfo { double f1, f2; int size; wchar vowel [Preferences_STRING_BUFFER_SIZE]; }; static struct { int shellWidth, shellHeight; int soundFollowsMouse; double f1min, f1max, f2min, f2max; double f3, b3, f4, b4; double markTraceEvery, extendDuration; int frequencyScale; int axisOrientation; int speakerType, marksDataset, numberOfMarks, marksFontSize; wchar mark[VowelEditor_MAXIMUM_MARKERS][Preferences_STRING_BUFFER_SIZE]; } prefs; Thing_implement (Vowel, Function, 0); static Vowel Vowel_create (double duration) { try { autoVowel me = Thing_new (Vowel); Function_init (me.peek(), 0, duration); my ft = FormantTier_create (0, duration); my pt = PitchTier_create (0, duration); return me.transfer(); } catch (MelderError) { Melder_throw ("Vowel not created."); } } static Vowel Vowel_create_twoFormantSchwa (double duration) { try { autoVowel me = Vowel_create (duration); autoFormantPoint fp = FormantPoint_create (0); fp -> formant [0] = 500; fp -> bandwidth[0] = 50; fp -> formant [1] = 1500; fp -> bandwidth[1] = 150; fp -> numberOfFormants = 2; Collection_addItem (my ft -> points, fp.transfer()); RealTier_addPoint (my pt, 0, 140); fp.reset (FormantPoint_create (duration)); fp -> formant [0] = 500; fp -> bandwidth[0] = 50; fp -> formant [1] = 1500; fp -> bandwidth[1] = 150; fp -> numberOfFormants = 2; Collection_addItem (my ft -> points, fp.transfer()); RealTier_addPoint (my pt, duration, 140); return me.transfer(); } catch (MelderError) { Melder_throw ("Schwa Vowel not created"); } } static Sound Vowel_to_Sound_pulses (Vowel me, double samplingFrequency, double adaptFactor, double adaptTime, long interpolationDepth) { try { autoPointProcess pp = PitchTier_to_PointProcess (my pt); autoSound thee = PointProcess_to_Sound_pulseTrain (pp.peek(), samplingFrequency, adaptFactor, adaptTime, interpolationDepth); Sound_FormantTier_filter_inline (thee.peek(), my ft); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Sound with pulses not created."); } } static FormantGrid FormantTier_to_FormantGrid (FormantTier me) { try { long numberOfFormants = FormantTier_getMaxNumFormants (me); autoFormantGrid thee = FormantGrid_createEmpty (my xmin, my xmax, numberOfFormants); for (long ipoint = 1; ipoint <= my points -> size; ipoint++) { FormantPoint fp = (FormantPoint) my points -> item[ipoint]; double t = fp -> time; for (long iformant = 1; iformant <= fp -> numberOfFormants; iformant++) { FormantGrid_addFormantPoint (thee.peek(), iformant, t, fp -> formant[iformant - 1]); FormantGrid_addBandwidthPoint (thee.peek(), iformant, t, fp -> bandwidth[iformant - 1]); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no FormantGrod created."); } } static void VowelEditor_getXYFromF1F2 (VowelEditor me, double f1, double f2, double *x, double *y) { *x = log (f2 / my f2max) / log (my f2min / my f2max); *y = log (f1 / my f1max) / log (my f1min / my f1max); } //Graphics_DCtoWC ???? static void VowelEditor_getF1F2FromXY (VowelEditor me, double x, double y, double *f1, double *f2) { *f2 = my f2min * pow (my f2max / my f2min, 1 - x); *f1 = my f1min * pow (my f1max / my f1min, 1 - y); } #define REPRESENTNUMBER(x,i) (((x) == NUMundefined) ? L" undef" : ((swprintf(buffer[i], 7, L"%6.1f",x)), buffer[i])) static void appendF1F2F0 (MelderString *statusInfo, const wchar_t *intro, double f1, double f2, double f0, const wchar_t *ending) { const wchar_t *komma = L", "; wchar_t buffer[4][10]; MelderString_append (statusInfo, intro, REPRESENTNUMBER (f1, 1), komma, REPRESENTNUMBER (f2, 2), komma, REPRESENTNUMBER (f0, 3), ending); } static double getRealFromTextWidget (GuiObject me) { double value = NUMundefined; wchar_t *dirty = GuiText_getString (me); try { Interpreter_numericExpression (NULL, dirty, & value); } catch (MelderError) { Melder_clearError (); value = NUMundefined; } Melder_free (dirty); return value; } static void VowelEditor_updateF0Info (VowelEditor me) { double f0 = getRealFromTextWidget (my f0TextField); checkF0 (&my f0, &f0); GuiText_setString (my f0TextField, Melder_double (f0)); my f0.start = f0; double slopeOctPerSec = getRealFromTextWidget (my f0SlopeTextField); if (slopeOctPerSec == NUMundefined) { slopeOctPerSec = f0default.slopeOctPerSec; } my f0.slopeOctPerSec = slopeOctPerSec; GuiText_setString (my f0SlopeTextField, Melder_double (my f0.slopeOctPerSec)); } static void VowelEditor_updateExtendDuration (VowelEditor me) { double extend = getRealFromTextWidget (my extendTextField); if (extend == NUMundefined || extend <= MINIMUM_SOUND_DURATION || extend > my maximumDuration) { extend = MINIMUM_SOUND_DURATION; } GuiText_setString (my extendTextField, Melder_double (extend)); my extendDuration = prefs.extendDuration = extend; } static double VowelEditor_updateDurationInfo (VowelEditor me) { double duration = getRealFromTextWidget (my durationTextField); if (duration == NUMundefined || duration < MINIMUM_SOUND_DURATION) { duration = MINIMUM_SOUND_DURATION; } GuiText_setString (my durationTextField, Melder_double (MICROSECPRECISION (duration))); return duration; } static void Sound_fadeIn (Sound me, double duration, int fromFirstNonZeroSample) { long istart = 1, numberOfSamples = duration / my dx; if (numberOfSamples < 2) { return; } if (fromFirstNonZeroSample != 0) { // If the first part of the sound is very low level we put sample values to zero and // start windowing from the position where the amplitude is above the minimum level. // WARNING: this part is special for the artificial vowels because // 1. They have no offset // 2. They are already scaled to a maximum amplitude of 0.99 // 3. For 16 bit precision double zmin = 0.5 / pow (2, 16); while (fabs (my z[1][istart]) < zmin && istart < my nx) { my z[1][istart] = 0; // To make sure istart++; } } if (numberOfSamples > my nx - istart + 1) { numberOfSamples = my nx - istart + 1; } for (long i = 1; i <= numberOfSamples; i++) { double phase = NUMpi * (i - 1) / (numberOfSamples - 1); my z[1][istart + i - 1] *= 0.5 * (1 - cos (phase)); } } static void Sound_fadeOut (Sound me, double duration) { long istart, numberOfSamples = duration / my dx; if (numberOfSamples < 2) { return; } if (numberOfSamples > my nx) { numberOfSamples = my nx; } istart = my nx - numberOfSamples; // only one channel for (long i = 1; i <= numberOfSamples; i++) { double phase = NUMpi * (i - 1) / (numberOfSamples - 1); my z[1][istart + i] *= 0.5 * (1 + cos (phase)); } } static double getF0 (structVowelEditor_F0 *f0p, double time) { double f0 = f0p -> start * pow (2, f0p -> slopeOctPerSec * time); if (f0 < f0p -> minimum) { f0 = f0p -> minimum; } else if (f0 > f0p -> maximum) { f0 = f0p -> maximum; } return f0; } static void VowelEditor_Vowel_reverseFormantTier (VowelEditor me) { FormantTier ft = (FormantTier) my vowel -> ft; double duration = ft -> xmax; long np = ft -> points -> size, np_2 = np / 2; for (long i = 1; i <= np_2; i++) { FormantPoint fpt = (FormantPoint) ft -> points -> item[i]; ft -> points -> item[i] = ft -> points -> item[np - i + 1]; ft -> points -> item[np - i + 1] = fpt; fpt = (FormantPoint) ft -> points -> item[i]; fpt -> time = duration - fpt -> time; fpt = (FormantPoint) ft -> points -> item[np - i + 1]; fpt -> time = duration - fpt -> time; } if (np % 2 == 1) { FormantPoint fpt = (FormantPoint) ft -> points -> item[np_2 + 1]; fpt -> time = duration - fpt -> time; } } static void VowelEditor_shiftF1F2 (VowelEditor me, double f1_st, double f2_st) { FormantTier ft = my vowel -> ft; for (long i = 1; i <= ft -> points -> size; i++) { FormantPoint fp = (FormantPoint) ft -> points -> item[i]; double f1 = fp -> formant[0], f2 = fp -> formant[1]; f1 *= pow (2, f1_st / 12); if (f1 < my f1min) { f1 = my f1min; } if (f1 > my f1max) { f1 = my f1max; } fp -> formant[0] = f1; fp -> bandwidth[0] = f1 / 10; f2 *= pow (2, f2_st / 12); if (f2 < my f2min) { f2 = my f2min; } if (f2 > my f2max) { f2 = my f2max; } fp -> formant[1] = f2; fp -> bandwidth[1] = f2 / 10; double f3, b3, f4, b4; VowelEditor_getF3F4 (me, f1, f2, &f3, &b3, &f4, &b4); fp -> formant[2] = f3; fp -> bandwidth[2] = b3; fp -> formant[3] = f4; fp -> bandwidth[3] = b4; } } static void Vowel_newDuration (Vowel me, structVowelEditor_F0 *f0p, double newDuration) { if (newDuration != my xmax) { double multiplier = newDuration / my xmax; FormantTier_newDuration (my ft, newDuration); my xmax *= multiplier; } PitchTier_newDuration (my pt, f0p, newDuration); // always update } static void FormantTier_newDuration (FormantTier me, double newDuration) { if (newDuration != my xmax) { double multiplier = newDuration / my xmax; for (long i = 1; i <= my points -> size; i++) { FormantPoint fp = (FormantPoint) my points -> item[i]; fp -> time *= multiplier; } my xmax *= multiplier; } } static void PitchTier_newDuration (PitchTier me, structVowelEditor_F0 *f0p, double newDuration) { // Always update; GuiObject text might have changed double multiplier = newDuration / my xmax; for (long i = 1; i <= my points -> size; i++) { RealPoint pp = (RealPoint) my points -> item[i]; pp -> number *= multiplier; pp -> value = getF0 (f0p, pp -> number); } my xmax *= multiplier; } static void VowelEditor_updateVowel (VowelEditor me) { double newDuration = VowelEditor_updateDurationInfo (me); // Get new duration from TextWidget VowelEditor_updateF0Info (me); // Get new pitch and slope values from TextWidgets Vowel_newDuration (my vowel, & my f0, newDuration); } static double getCoordinate (double fmin, double fmax, double f) { return log (f / fmax) / log (fmin / fmax); } #define GETX(x) (getCoordinate (f2min, f2max, x)) #define GETY(y) (getCoordinate (f1min, f1max, y)) // Our FormantTiers always have a FormantPoint at t=xmin and t=xmax; static void FormantTier_drawF1F2Trajectory (FormantTier me, Graphics g, double f1min, double f1max, double f2min, double f2max, double markTraceEvery, double width) { int it, imark = 1, glt = Graphics_inqLineType (g); double glw = Graphics_inqLineWidth (g), x1, x1p, y1, y1p, t1; Graphics_Colour colour = Graphics_inqColour (g); long nfp = my points -> size; FormantPoint fp = (FormantPoint) my points -> item[1]; FormantPoint fpn = (FormantPoint) my points -> item[nfp]; double tm, markLength = 0.01; Graphics_setInner (g); Graphics_setWindow (g, 0, 1, 0, 1); Graphics_setLineType (g, Graphics_DRAWN); // Too short too hear ? if ( (my xmax - my xmin) < 0.005) { Graphics_setColour (g, Graphics_RED); } x1p = x1 = GETX (fp->formant[1]); y1p = y1 = GETY (fp->formant[0]); t1 = fp->time; for (it = 2; it <= nfp; it++) { fp = (FormantPoint) my points -> item[it]; double x2 = GETX (fp->formant[1]), y2 = GETY (fp->formant[0]), t2 = fp->time; Graphics_setLineWidth (g, 3); if (x1 == x2 && y1 == y2) { x1 = x1p; y1 = y1p; } else { Graphics_line (g, x1, y1, x2, y2); } while (markTraceEvery > 0 && (tm = markTraceEvery * imark) < t2) { // line orthogonal to y = (y1/x1)*x is y = -(x1/y1)*x double fraction = (tm - t1) / (t2 - t1); double dx = x2 - x1, dy = y2 - y1; double xm = x1 + fraction * dx, ym = y1 + fraction * dy; double xl1 = dy * markLength / sqrt (dx * dx + dy * dy), xl2 = - xl1; double yl1 = dx * markLength / sqrt (dx * dx + dy * dy), yl2 = - yl1; if (dx * dy > 0) { xl1 = -fabs (xl1); yl1 = fabs (yl1); xl2 = fabs (xl1); yl2 = -fabs (yl1); } else if (dx * dy < 0) { xl1 = -fabs (xl1); yl1 = -fabs (yl1); xl2 = fabs (xl1); yl2 = fabs (yl1); } Graphics_setLineWidth (g, 1); Graphics_line (g, xm + xl1, ym + yl1, xm + xl2, ym + yl2); imark++; } x1p = x1; y1p = y1; x1 = x2; y1 = y2; t1 = t2; } // Arrow at end { double gas = Graphics_inqArrowSize (g), arrowSize = 1; double size = 10.0 * arrowSize * Graphics_getResolution (g) / 75.0 / width, size2 = size * size; Graphics_setArrowSize (g, arrowSize); it = 1; while (it <= (nfp - 1)) { fp = (FormantPoint) my points -> item[nfp - it]; double dx = GETX (fpn->formant[1]) - GETX (fp->formant[1]); double dy = GETY (fpn->formant[0]) - GETY (fp->formant[0]); double d2 = dx * dx + dy * dy; if (d2 > size2) { break; } it++; } Graphics_arrow (g, GETX (fp->formant[1]), GETY (fp->formant[0]), GETX (fpn->formant[1]), GETY (fpn->formant[0])); Graphics_setArrowSize (g, gas); } Graphics_unsetInner (g); Graphics_setColour (g, colour); Graphics_setLineType (g, glt); Graphics_setLineWidth (g, glw); } #undef GETX #undef GETY static PitchTier VowelEditor_to_PitchTier (VowelEditor me, double duration) { try { double t_end = duration; double f0_end = my f0.start * pow (2, my f0.slopeOctPerSec * t_end); autoPitchTier thee = PitchTier_create (0, t_end); RealTier_addPoint (thee.peek(), 0, my f0.start); if (my f0.slopeOctPerSec < 0) { if (f0_end < my f0.minimum) { t_end = log2 (my f0.minimum / my f0.start) / my f0.slopeOctPerSec; f0_end = my f0.minimum; } } else if (my f0.slopeOctPerSec > 0) { if (f0_end > my f0.maximum) { t_end = log2 (my f0.maximum / my f0.start) / my f0.slopeOctPerSec; f0_end = my f0.maximum; } } RealTier_addPoint (thee.peek(), t_end, f0_end); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no PitchTier created."); } } void VowelEditor_prefs () { Preferences_addInt (L"VowelEditor.shellWidth", &prefs.shellWidth, 500); Preferences_addInt (L"VowelEditor.shellHeight", &prefs.shellHeight, 500); Preferences_addInt (L"VowelEditor.soundFollowsMouse", &prefs.soundFollowsMouse, 1); Preferences_addDouble (L"VowelEditor.f1min", &prefs.f1min, 200); Preferences_addDouble (L"VowelEditor.f1max", &prefs.f1max, 1200); Preferences_addDouble (L"VowelEditor.f2min", &prefs.f2min, 500); Preferences_addDouble (L"VowelEditor.f2max", &prefs.f2max, 3500); Preferences_addDouble (L"VowelEditor.f3", &prefs.f3, 2500); Preferences_addDouble (L"VowelEditor.b3", &prefs.b3, 250); Preferences_addDouble (L"VowelEditor.f4", &prefs.f4, 3500); Preferences_addDouble (L"VowelEditor.b4", &prefs.b4, 350); Preferences_addDouble (L"VowelEditor.markTraceEvery", &prefs.markTraceEvery, 0.05); Preferences_addDouble (L"VowelEditor.extendDuration", &prefs.extendDuration, 0.05); Preferences_addInt (L"VowelEditor.frequencyScale", &prefs.frequencyScale, 0); Preferences_addInt (L"VowelEditor.axisOrientation", &prefs.axisOrientation, 0); Preferences_addInt (L"VowelEditor.speakerType", &prefs.speakerType, 1); Preferences_addInt (L"VowelEditor.marksDataset", &prefs.marksDataset, 2); Preferences_addInt (L"VowelEditor.marksFontsize", &prefs.marksFontSize, 14); createPersistentVowelMarks (); } static void copyVowelMarksInPreferences_volatile (Table me) { long numberOfRows = prefs.numberOfMarks = my rows -> size; if (numberOfRows > 0) { long col_vowel = Table_getColumnIndexFromColumnLabel (me, L"Vowel"); long col_f1 = Table_getColumnIndexFromColumnLabel (me, L"F1"); long col_f2 = Table_getColumnIndexFromColumnLabel (me, L"F2"); long col_size = Table_getColumnIndexFromColumnLabel (me, L"Size"); autoMelderString mark, markID; for (long i = 1; i <= VowelEditor_MAXIMUM_MARKERS; i++) { if (i <= numberOfRows) { MelderString_append (&mark, Table_getStringValue_Assert (me, i, col_vowel), L"\t", Table_getStringValue_Assert (me, i, col_f1), L"\t", Table_getStringValue_Assert (me, i, col_f2), L"\t", Table_getStringValue_Assert (me, i, col_size)); long length = wcslen (mark.string); if (length > Preferences_STRING_BUFFER_SIZE) Melder_throw ("Preference mark", i, "too many characters"); wcscpy (prefs.mark[i-1], mark.string); MelderString_empty (&mark); } else { wcscpy (prefs.mark[i-1], L"x"); } } // The following code removes the superfluous mark preferences, // *if* we had access to the thePreferences set (but we don't) // autoMelderString markID; // for (long i = VowelEditor_MAXIMUM_MARKERS; i > numberOfRows; i--) { // MelderString_append (&markID, L"VowelEditor.mark", (i < 10 ? L"0" : L""), Melder_integer (i)); // long index = SortedSetOfString_lookUp (thePreferences, markID.string); // Collection_removeItem (thePreferences, index); // MelderString_empty (&markID); // } } } static void createPersistentVowelMarks () { autoMelderString markID; // Deadlock: // This function is executed before the preferences are read from file and before we know how // many vowel marks the user wants. // However, to succesfully read the preferences from file we need the names of the preferences otherwise // they will not be assigned a value. // We therefore create fake names first and later fill them with data. long numberOfMarks = VowelEditor_MAXIMUM_MARKERS; Preferences_addInt (L"VowelEditor.numberOfMarks", &prefs.numberOfMarks, numberOfMarks); for (long i = 1; i <= numberOfMarks; i++) { MelderString_append (&markID, L"VowelEditor.mark", (i < 10 ? L"0" : L""), Melder_integer (i)); Preferences_addString (markID.string, & prefs.mark[i-1][0], L"x"); MelderString_empty (&markID); } } void VowelEditor_createTableFromVowelMarksInPreferences (VowelEditor me) { long numberOfRows = VowelEditor_MAXIMUM_MARKERS; try { autoTable marks = Table_createWithColumnNames (0, L"Vowel F1 F2 Size"); long nmarksFound = 0; for (long i = 1; i <= numberOfRows; i++) { long numberOfTokens; autoMelderTokens rowi (prefs.mark[i-1], &numberOfTokens); if (numberOfTokens < 4) { // we are done break; } Table_appendRow (marks.peek()); for (long j = 1; j <= 4; j++) { Table_setStringValue (marks.peek(), i, j, rowi[j]); } nmarksFound++; } if (nmarksFound == 0) { my speakerType = prefs.speakerType = 1; my marksDataset = prefs.marksDataset = 1; VowelEditor_setMarks (me, my marksDataset, my speakerType, prefs.marksFontSize); } else { my marks = marks.transfer(); // my marks == NULL; } } catch (MelderError) { Melder_throw (L"Cannot create Table from preferences. Default marks set."); my speakerType = prefs.speakerType = 1; my marksDataset = prefs.marksDataset = 1; VowelEditor_setMarks (me, my marksDataset, my speakerType, prefs.marksFontSize); } } static void Table_addColumn_size (Table me, int size) { long col_size = Table_findColumnIndexFromColumnLabel (me, L"Size"); if (col_size == 0) { Table_appendColumn (me, L"Size"); for (long i = 1; i <= my rows -> size; i++) { Table_setNumericValue (me, i, my numberOfColumns, size); } } } static void VowelEditor_setMarks (VowelEditor me, int marksDataset, int speakerType, int fontSize) { autoTable te = 0; const wchar_t *Type[4] = { L"", L"m", L"w", L"c" }; const wchar_t *Sex[3] = { L"", L"m", L"f"}; if (marksDataset == 1) { // American-English autoTable thee = Table_createFromPetersonBarneyData (); te.reset (Table_extractRowsWhereColumn_string (thee.peek(), 1, kMelder_string_EQUAL_TO, Type[speakerType])); } else if (marksDataset == 2) { // Dutch if (speakerType == 1 || speakerType == 2) { // male + female from Pols van Nierop autoTable thee = Table_createFromPolsVanNieropData (); te.reset (Table_extractRowsWhereColumn_string (thee.peek(), 1, kMelder_string_EQUAL_TO, Sex[speakerType])); } else { autoTable thee = Table_createFromWeeninkData (); te.reset (Table_extractRowsWhereColumn_string (thee.peek(), 1, kMelder_string_EQUAL_TO, Type[speakerType])); } } else if (marksDataset == 3) { // None forget (my marks); return; } else { // Leave as is return; } autoTable thee = Table_collapseRows (te.peek(), L"IPA", L"", L"F1 F2", L"", L"", L""); long col_ipa = Table_findColumnIndexFromColumnLabel (thee.peek(), L"IPA"); Table_setColumnLabel (thee.peek(), col_ipa, L"Vowel"); Table_addColumn_size (thee.peek(), fontSize); forget (my marks); my marks = thee.transfer(); copyVowelMarksInPreferences_volatile (my marks); } static void VowelEditor_getVowelMarksFromTableFile (VowelEditor me, MelderFile file) { try { autoData data = (Data) Data_readFromFile (file); if (! Thing_member ((Thing) data.peek(), classTable)) Melder_throw (L"\"", MelderFile_name (file), L"\" is not a Table file"); autoTable marks = (Table) data.transfer(); // check if columns Vowel F1 & F2 are present Table_getColumnIndexFromColumnLabel (marks.peek(), L"Vowel"); Table_getColumnIndexFromColumnLabel (marks.peek(), L"F1"); Table_getColumnIndexFromColumnLabel (marks.peek(), L"F2"); Table_addColumn_size (marks.peek(), prefs.marksFontSize); forget (my marks); my marks = marks.transfer(); my marksDataset = prefs.marksDataset = 9999; copyVowelMarksInPreferences_volatile (my marks); // our marks preferences are dynamic, save each time } catch (MelderError) { Melder_throw ("Vowel marks from Table not shown."); } } static void VowelEditor_setF3F4 (VowelEditor me, double f3, double b3, double f4, double b4) { double xmin = my f2min, xmax = my f2max, dx = my f2max - my f2min, x1 = dx / 2; double dy = my f1max - my f1min, y1 = dy / 2; if (my f3 == 0) { my f3 = Matrix_create (xmin, xmax, 1, dx, x1, my f1min, my f1max, 1, dy, y1); } if (my b3 == 0) { my b3 = Matrix_create (xmin, xmax, 1, dx, x1, my f1min, my f1max, 1, dy, y1); } if (my f4 == 0) { my f4 = Matrix_create (xmin, xmax, 1, dx, x1, my f1min, my f1max, 1, dy, y1); } if (my b4 == 0) { my b4 = Matrix_create (xmin, xmax, 1, dx, x1, my f1min, my f1max, 1, dy, y1); } my f3 -> z[1][1] = f3; my b3 -> z[1][1] = b3; my f4 -> z[1][1] = f4; my b4 -> z[1][1] = b4; } static double Matrix_getValue (Matrix me, double x, double y) { (void) x; (void) y; return my z[1][1]; } static void VowelEditor_getF3F4 (VowelEditor me, double f1, double f2, double *f3, double *b3, double *f4, double *b4) { *f3 = Matrix_getValue (my f3, f2, f1); *b3 = Matrix_getValue (my b3, f2, f1); *f4 = Matrix_getValue (my f4, f2, f1); *b4 = Matrix_getValue (my b4, f2, f1); } static void VowelEditor_drawBackground (VowelEditor me, Graphics g) { double x1, y1, x2, y2, f1, f2; Graphics_setInner (g); Graphics_setWindow (g, 0, 1, 0, 1); Graphics_setGrey (g, 0); Graphics_setLineType (g, Graphics_DRAWN); Graphics_setLineWidth (g, 2); Graphics_rectangle (g, 0, 1, 0, 1); Graphics_setLineWidth (g, 1); Graphics_setGrey (g, 0.5); int fontSize = Graphics_inqFontSize (g); // draw the marks if (my marks != 0) { long col_vowel = Table_getColumnIndexFromColumnLabel (my marks, L"Vowel"); long col_f1 = Table_getColumnIndexFromColumnLabel (my marks, L"F1"); long col_f2 = Table_getColumnIndexFromColumnLabel (my marks, L"F2"); long col_fs = Table_findColumnIndexFromColumnLabel (my marks, L"Size"); for (long i = 1; i <= my marks -> rows -> size; i++) { const wchar_t *label = Table_getStringValue_Assert (my marks, i, col_vowel); f1 = Table_getNumericValue_Assert (my marks, i, col_f1); f2 = Table_getNumericValue_Assert (my marks, i, col_f2); if (f1 >= my f1min && f1 <= my f1max && f2 >= my f2min && f2 <= my f2max) { VowelEditor_getXYFromF1F2 (me, f1, f2, &x1, &y1); int size = prefs.marksFontSize; if (col_fs != 0) { size = Table_getNumericValue_Assert (my marks, i, col_fs); } Graphics_setFontSize (g, size); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x1, y1, label); } } } Graphics_setFontSize (g, fontSize); // Draw the line F1=F2 // VowelEditor_getXYFromF1F2 (me, my f2min, my f2min, &x1, &y1); if (y1 >= 0 && y1 <= 1) { VowelEditor_getXYFromF1F2 (me, my f1max, my f1max, &x2, &y2); if (x2 >= 0 && x2 <= 1) { Polygon p = Polygon_create (3); p -> x[1] = x1; p -> y[1] = y1; p -> x[2] = x2; p -> y[2] = y2; p -> x[3] = 1; p -> y[3] = 0; Graphics_fillArea (g, p -> numberOfPoints, & p -> x[1], & p -> y[1]); // Polygon_paint does not work because of use of Graphics_setInner. forget (p); Graphics_line (g, x1, y1, x2, y2); } } // Draw the grid if (my grid.df1 < (my f1max - my f1min)) { // Horizontal lines long iline = (my f1min + my grid.df1) / my grid.df1; Graphics_setGrey (g, 0.5); Graphics_setLineType (g, Graphics_DOTTED); while ( (f1 = iline * my grid.df1) < my f1max) { if (f1 > my f1min) { VowelEditor_getXYFromF1F2 (me, f1, my f2min, &x1, &y1); VowelEditor_getXYFromF1F2 (me, f1, my f2max, &x2, &y2); Graphics_line (g, x1, y1, x2, y2); } iline++; } Graphics_setLineType (g, Graphics_DRAWN); Graphics_setGrey (g, 0); // black } if (my grid.df2 < (my f2max - my f2min)) { long iline = (my f2min + my grid.df2) / my grid.df2; Graphics_setGrey (g, 0.5); Graphics_setLineType (g, Graphics_DOTTED); while ( (f2 = iline * my grid.df2) < my f2max) { // vert line if (f2 > my f2min) { VowelEditor_getXYFromF1F2 (me, my f1min, f2, &x1, &y1); VowelEditor_getXYFromF1F2 (me, my f1max, f2, &x2, &y2); Graphics_line (g, x1, y1, x2, y2); } iline++; } Graphics_setLineType (g, Graphics_DRAWN); Graphics_setGrey (g, 0); // black } Graphics_unsetInner (g); Graphics_setGrey (g, 0); // black Graphics_markLeft (g, 0, 0, 1, 0, Melder_double (my f1max)); Graphics_markLeft (g, 1, 0, 1, 0, Melder_double (my f1min)); Graphics_markTop (g, 0, 0, 1, 0, Melder_double (my f2max)); Graphics_markTop (g, 1, 0, 1, 0, Melder_double (my f2min)); } typedef struct { long some_check_value; long istart; float *z; } *paVowelData; /* This routine will be called by the PortAudio engine when audio is needed. ** It may called at interrupt level on some machines so don't do anything ** that could mess up the system like calling malloc() or free(). */ static int paCallback (const void *inputBuffer, void *outputBuffer, unsigned long framesPerBuffer, const PaStreamCallbackTimeInfo *timeInfo, PaStreamCallbackFlags statusFlags, I) { iam (paVowelData); float *out = (float *) outputBuffer; unsigned int i; (void) inputBuffer; /* Prevent unused variable warning. */ (void) timeInfo; (void) statusFlags; for (i = 0; i < framesPerBuffer; i++) { *out++ = my z[my istart + i]; /* left */ *out++ = my z[my istart + i]; /* right */ } my istart += framesPerBuffer; return 0; } /********** MENU METHODS **********/ static void menu_cb_help (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); (void) me; Melder_help (L"VowelEditor"); } static void menu_cb_prefs (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Preferences", 0); BOOLEAN (L"Sound-follows-mouse", 1) EDITOR_OK SET_INTEGER (L"Sound-follows-mouse", prefs.soundFollowsMouse) EDITOR_DO my frequencyScale = prefs.frequencyScale; my axisOrientation = prefs.axisOrientation; my soundFollowsMouse = prefs.soundFollowsMouse = GET_INTEGER (L"Sound-follows-mouse"); Graphics_updateWs (my g); EDITOR_END } static void menu_cb_ranges_f1f2 (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"F1 (vert) and F2 (hor) view ranges", 0); POSITIVE (L"left F1 range (Hz)", L"200.0") POSITIVE (L"right F1 range (Hz)", L"1000.0") POSITIVE (L"left F2 range (Hz)", L"500.0") POSITIVE (L"right F2 range (Hz)", L"2500.0") EDITOR_OK SET_REAL (L"left F1 range", prefs.f1min) SET_REAL (L"right F1 range", prefs.f1max) SET_REAL (L"left F2 range", prefs.f2min) SET_REAL (L"right F2 range", prefs.f2max) EDITOR_DO my frequencyScale = prefs.frequencyScale; my axisOrientation = prefs.axisOrientation; my f1min = prefs.f1min = GET_REAL (L"left F1 range"); my f1max = prefs.f1max = GET_REAL (L"right F1 range"); my f2min = prefs.f2min = GET_REAL (L"left F2 range"); my f2max = prefs.f2max = GET_REAL (L"right F2 range"); Graphics_updateWs (my g); EDITOR_END } static void menu_cb_publishSound (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); autoSound publish = VowelEditor_createTarget (me); my broadcastPublication (publish.transfer()); } static void menu_cb_extract_FormantGrid (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); VowelEditor_updateVowel (me); autoFormantGrid publish = FormantTier_to_FormantGrid (my vowel -> ft); my broadcastPublication (publish.transfer()); } static void menu_cb_extract_KlattGrid (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); VowelEditor_updateVowel (me); autoFormantGrid fg = FormantTier_to_FormantGrid (my vowel -> ft); autoKlattGrid publish = KlattGrid_create (fg -> xmin, fg -> xmax, fg -> formants -> size, 0, 0, 0, 0, 0, 0); KlattGrid_addVoicingAmplitudePoint (publish.peek(), fg -> xmin, 90); therror KlattGrid_replacePitchTier (publish.peek(), my vowel -> pt); therror KlattGrid_replaceFormantGrid (publish.peek(), KlattGrid_ORAL_FORMANTS, fg.peek()); therror my broadcastPublication (publish.transfer()); } static void menu_cb_extract_PitchTier (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); VowelEditor_updateVowel (me); autoPitchTier publish = Data_copy (my vowel -> pt); my broadcastPublication (publish.transfer()); } static void menu_cb_drawTrajectory (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Draw trajectory", 0) my v_form_pictureWindow (cmd); BOOLEAN (L"Garnish", 1) EDITOR_OK my v_ok_pictureWindow (cmd); EDITOR_DO int garnish = GET_INTEGER (L"Garnish"); my v_do_pictureWindow (cmd); Editor_openPraatPicture (me); if (garnish) { VowelEditor_drawBackground (me, my pictureGraphics); } FormantTier_drawF1F2Trajectory (my vowel -> ft, my pictureGraphics, my f1min, my f1max, my f2min, my f2max, my markTraceEvery, my width); Editor_closePraatPicture (me); EDITOR_END } static void menu_cb_showOneVowelMark (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Show one vowel mark", 0); POSITIVE (L"F1 (Hz)", L"300.0") POSITIVE (L"F2 (Hz)", L"600.0") WORD (L"Mark", L"u") EDITOR_OK EDITOR_DO double f1 = GET_REAL (L"F1"); double f2 = GET_REAL (L"F2"); wchar_t *label = GET_STRING (L"Mark"); if (f1 >= my f1min && f1 <= my f1max && f2 >= my f2min && f2 <= my f2max) { long irow = 1; if (my marks == NULL) { my marks = Table_createWithColumnNames (1, L"IPA F1 F2 Colour"); } else { Table_appendRow (my marks); } irow = my marks -> rows -> size; Table_setStringValue (my marks, irow, 1, label); Table_setNumericValue (my marks, irow, 2, f1); Table_setNumericValue (my marks, irow, 3, f2); Graphics_updateWs (my g); } EDITOR_END } static void menu_cb_showVowelMarks (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Show vowel marks", 0); LABEL (L"note", L"") OPTIONMENU (L"Data set", 1) OPTION (L"American English") OPTION (L"Dutch") OPTION (L"None") OPTIONMENU (L"Speaker", 1) OPTION (L"Man") OPTION (L"Woman") OPTION (L"Child") NATURAL (L"Font size (points)", L"14") EDITOR_OK if (my marksDataset == 9999) SET_STRING (L"note", L"(Warning: current vowel marks are not from one of these data sets.)") SET_INTEGER (L"Data set", my marksDataset); SET_INTEGER (L"Speaker", my speakerType); SET_INTEGER (L"Font size", my marksFontSize); EDITOR_DO my marksDataset = prefs.marksDataset = GET_INTEGER (L"Data set"); my speakerType = prefs.speakerType = GET_INTEGER (L"Speaker"); my marksFontSize = prefs.marksFontSize = GET_INTEGER (L"Font size"); VowelEditor_setMarks (me, my marksDataset, my speakerType, my marksFontSize); Graphics_updateWs (my g); EDITOR_END } static void menu_cb_showVowelMarksFromTableFile (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM_READ (L"VowelEditor: Show vowel marks from Table file", L"VowelEditor: Show vowel marks from Table file..."); EDITOR_DO_READ VowelEditor_getVowelMarksFromTableFile (me, file); Graphics_updateWs (my g); EDITOR_END } static void menu_cb_setF0 (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Set F0", 0); POSITIVE (L"Start F0 (Hz)", L"150.0") REAL (L"Slope (oct/s)", L"0.0") EDITOR_OK EDITOR_DO double f0 = GET_REAL (L"Start F0"); checkF0 (&my f0, &f0); my f0.start = f0; my f0.slopeOctPerSec = GET_REAL (L"Slope"); VowelEditor_setSource (me); therror GuiText_setString (my f0TextField, Melder_double (my f0.start)); GuiText_setString (my f0SlopeTextField, Melder_double (my f0.slopeOctPerSec)); EDITOR_END } static void menu_cb_setF3F4 (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Set F3 & F4", 0); POSITIVE (L"F3 (Hz)", L"2500.0") POSITIVE (L"B3 (Hz)", L"250.0") POSITIVE (L"F4 (Hz)", L"3500.0") POSITIVE (L"B4 (Hz)", L"350.0") EDITOR_OK EDITOR_DO double f3 = GET_REAL (L"F3"), b3 = GET_REAL (L"B3"); double f4 = GET_REAL (L"F4"), b4 = GET_REAL (L"B4"); if (f3 >= f4) { Melder_throw ("F4 must be larger than F3."); } VowelEditor_setF3F4 (me, f3, b3, f4, b4); therror EDITOR_END } static void menu_cb_reverseTrajectory (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); VowelEditor_Vowel_reverseFormantTier (me); Graphics_updateWs (my g); } static void VowelEditor_Vowel_addData (VowelEditor me, Vowel thee, double time, double f1, double f2, double f0) { autoFormantPoint fp = FormantPoint_create (time); double f3, b3, f4, b4; fp -> formant[0] = f1; fp -> bandwidth[0] = f1 / 10; fp -> formant[1] = f2; fp -> bandwidth[1] = f2 / 10; VowelEditor_getF3F4 (me, f1, f2, &f3, &b3, &f4, &b4); fp -> formant[2] = f3; fp -> bandwidth[2] = b3; fp -> formant[3] = f4; fp -> bandwidth[3] = b4; fp -> numberOfFormants = 4; Collection_addItem (thy ft -> points, fp.transfer()); RealTier_addPoint (thy pt, time, f0); } static void checkF1F2 (VowelEditor me, double *f1, double *f2) { if (*f1 < my f1min) { *f1 = my f1min; } if (*f1 > my f1max) { *f1 = my f1max; } if (*f2 < my f2min) { *f2 = my f2min; } if (*f2 > my f2max) { *f1 = my f2max; } } static void checkF0 (structVowelEditor_F0 *f0p, double *f0) { if (*f0 == NUMundefined) { *f0 = f0p -> start; } if (*f0 > f0p -> maximum) { *f0 = f0p -> maximum; } if (*f0 < f0p -> minimum) { *f0 = f0p -> minimum; } } static void checkXY (double *x, double *y) { if (*x < 0) { *x = 0; } else if (*x > 1) { *x = 1; } if (*y < 0) { *y = 0; } else if (*y > 1) { *y = 1; } } static void menu_cb_newTrajectory (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"New Trajectory", 0); POSITIVE (L"Start F1 (Hz)", L"700.0") POSITIVE (L"Start F2 (Hz)", L"1200.0") POSITIVE (L"End F1 (Hz)", L"350.0") POSITIVE (L"End F2 (Hz)", L"800.0") POSITIVE (L"Duration (s)", L"0.25") EDITOR_OK EDITOR_DO double f0, f1, f2, time, duration = GET_REAL (L"Duration"); autoVowel vowel = Vowel_create (duration); time = 0; f0 = getF0 (&my f0, time); f1 = GET_REAL (L"Start F1"); f2 = GET_REAL (L"Start F2"); checkF1F2 (me, &f1, &f2); VowelEditor_Vowel_addData (me, vowel.peek(), time, f1, f2, f0); time = duration; f0 = getF0 (&my f0, time); f1 = GET_REAL (L"End F1"); f2 = GET_REAL (L"End F2"); checkF1F2 (me, &f1, &f2); VowelEditor_Vowel_addData (me, vowel.peek(), time, f1, f2, f0); GuiText_setString (my durationTextField, Melder_double (MICROSECPRECISION (duration))); forget (my vowel); my vowel = vowel.transfer(); Graphics_updateWs (my g); EDITOR_END } static void menu_cb_extendTrajectory (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Extend Trajectory", 0); POSITIVE (L"To F1 (Hz)", L"500.0") POSITIVE (L"To F2 (Hz)", L"1500.0") POSITIVE (L"Extra duration (s)", L"0.1") EDITOR_OK EDITOR_DO Vowel thee = my vowel; double newDuration = thy xmax + GET_REAL (L"Extra duration"); double f0 = getF0 (&my f0, newDuration); double f1 = GET_REAL (L"To F1"); double f2 = GET_REAL (L"To F2"); thy xmax = thy pt -> xmax = thy ft -> xmax = newDuration; checkF1F2 (me, &f1, &f2); VowelEditor_Vowel_addData (me, thee, newDuration, f1, f2, f0); GuiText_setString (my durationTextField, Melder_double (MICROSECPRECISION (newDuration))); Graphics_updateWs (my g); EDITOR_END } static void menu_cb_modifyTrajectoryDuration (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Modify duration", 0); POSITIVE (L"New duration (s)", L"0.5") EDITOR_OK EDITOR_DO GuiText_setString (my durationTextField, Melder_double (MICROSECPRECISION (GET_REAL (L"New duration")))); EDITOR_END } static void menu_cb_shiftTrajectory (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Shift trajectory", 0); REAL (L"F1 (semitones)", L"0.5") REAL (L"F2 (semitones)", L"0.5") EDITOR_OK EDITOR_DO VowelEditor_shiftF1F2 (me, GET_REAL (L"F1"), GET_REAL (L"F2")); Graphics_updateWs (my g); EDITOR_END } static void menu_cb_showTrajectoryTimeMarksEvery (EDITOR_ARGS) { EDITOR_IAM (VowelEditor); EDITOR_FORM (L"Show trajectory time marks every", 0); REAL (L"Distance (s)", L"0.05") EDITOR_OK SET_REAL (L"Distance", my markTraceEvery) EDITOR_DO my markTraceEvery = GET_REAL (L"Distance"); if (my markTraceEvery < 0) { my markTraceEvery = 0; } Graphics_updateWs (my g); EDITOR_END } /********** BUTTON METHODS **********/ static void gui_button_cb_play (I, GuiButtonEvent event) { (void) event; iam (VowelEditor); autoSound thee = VowelEditor_createTarget (me); Sound_play (thee.peek(), 0, 0); Graphics_updateWs (my g); } static void gui_button_cb_publish (I, GuiButtonEvent event) { (void) event; iam (VowelEditor); autoSound publish = VowelEditor_createTarget (me); my broadcastPublication (publish.transfer()); } static void gui_button_cb_reverse (I, GuiButtonEvent event) { (void) event; iam (VowelEditor); VowelEditor_Vowel_reverseFormantTier (me); struct structGuiButtonEvent play_event = { 0 }; play_event.button = my playButton; gui_button_cb_play (me, &play_event); } /* Main drawing routine: it's been called after every call to Graphics_updateWs (g) */ static void gui_drawingarea_cb_expose (I, GuiDrawingAreaExposeEvent event) { iam (VowelEditor); (void) event; double ts = my vowel -> xmin, te = my vowel -> xmax; FormantTier ft = (FormantTier) my vowel -> ft; static MelderString statusInfo = { 0 }; if (my g == 0) { return; // Could be the case in the very beginning. } Graphics_clearWs (my g); appendF1F2F0 (&statusInfo, STATUSINFO_STARTINTR0, FormantTier_getValueAtTime (ft, 1, ts), FormantTier_getValueAtTime (ft, 2, ts), getF0 (&my f0, ts), STATUSINFO_ENDING); GuiLabel_setString (my startInfo, statusInfo.string); MelderString_empty (&statusInfo); appendF1F2F0 (&statusInfo, STATUSINFO_ENDINTR0, FormantTier_getValueAtTime (ft, 1, te), FormantTier_getValueAtTime (ft, 2, te), getF0 (&my f0, te), STATUSINFO_ENDING); GuiLabel_setString (my endInfo, statusInfo.string); MelderString_empty (&statusInfo); Graphics_setGrey (my g, 0.9); Graphics_fillRectangle (my g, 0, 1, 0, 1); Graphics_setInner (my g); Graphics_setWindow (my g, 0, 1, 0, 1); Graphics_setGrey (my g, 1); Graphics_fillRectangle (my g, 0, 1, 0, 1); Graphics_unsetInner (my g); Graphics_setGrey (my g, 0); VowelEditor_drawBackground (me, my g); FormantTier_drawF1F2Trajectory (my vowel -> ft, my g, my f1min, my f1max, my f2min, my f2max, my markTraceEvery, my width); } static void gui_drawingarea_cb_resize__ (I, GuiDrawingAreaResizeEvent event) { iam (VowelEditor); (void) me; (void) event; if (me == NULL || my g == NULL) { return; } my height = GuiObject_getHeight (my drawingArea); my width = GuiObject_getWidth (my drawingArea); Graphics_setWsViewport (my g, 0, my width , 0, my height); Graphics_setWsWindow (my g, 0, my width, 0, my height); Graphics_setViewport (my g, 0, my width, 0, my height); Graphics_updateWs (my g); } static void gui_drawingarea_cb_resize (I, GuiDrawingAreaResizeEvent event) { iam (VowelEditor); if (my g == NULL) { return; // Could be the case in the very beginning. } Graphics_setWsViewport (my g, 0, event -> width, 0, event -> height); my width = event -> width; my height = event -> height; Graphics_setWsWindow (my g, 0, my width, 0, my height); Graphics_setViewport (my g, 0, my width, 0, my height); #if gtk // updateWs() also resizes the cairo clipping context to the new window size #endif Graphics_updateWs (my g); /* Save the current shell size as the user's preference for a new FunctionEditor. */ prefs.shellWidth = GuiObject_getWidth (my d_windowShell); prefs.shellHeight = GuiObject_getHeight (my d_windowShell); } static void VowelEditor_Vowel_updateTiers (VowelEditor me, Vowel thee, double time, double x, double y) { double f3, b3, f4, b4; if (time > thy xmax) { thy xmax = time; thy ft -> xmax = time; thy pt -> xmax = time; } double f0 = getF0 (& my f0, time), f1, f2; autoFormantPoint point = FormantPoint_create (time); VowelEditor_getF1F2FromXY (me, x, y, &f1, &f2); VowelEditor_getF3F4 (me, f1, f2, &f3, &b3, &f4, &b4); point -> formant[0] = f1; point -> bandwidth[0] = f1 / 10; point -> formant[1] = f2; point -> bandwidth[1] = f2 / 10; point -> formant[2] = f3; point -> bandwidth[2] = b3; point -> formant[3] = f4; point -> bandwidth[3] = b4; point -> numberOfFormants = 4; Collection_addItem (thy ft -> points, point.transfer()); RealTier_addPoint (thy pt, time, f0); } // shift key always extends what already is. // Special case : !soundFollowsMouse. The first click just defines the vowel's first f1f2-position, static void gui_drawingarea_cb_click (I, GuiDrawingAreaClickEvent event) { iam (VowelEditor); (void) event; Vowel thee = 0; autoVowel athee = 0; double x, y, xb, yb, tb, t, dt = 0; double t0 = Melder_clock (); long iskipped = 0; struct structGuiButtonEvent gb_event = { 0 }; Graphics_setInner (my g); Graphics_getMouseLocation (my g, & x, & y); checkXY (&x, &y); if (event -> shiftKeyPressed) { VowelEditor_updateExtendDuration (me); (my shiftKeyPressed) ++; thee = my vowel; dt = thy xmax + my extendDuration; t = 0 + dt; VowelEditor_Vowel_updateTiers (me, thee, t, x, y); GuiText_setString (my durationTextField, Melder_double (t)); if (! my soundFollowsMouse) { goto end; } } else { t = 0; my shiftKeyPressed = 0; athee.reset (Vowel_create (MINIMUM_SOUND_DURATION)); thee = athee.peek(); VowelEditor_Vowel_updateTiers (me, thee, t, x, y); GuiText_setString (my durationTextField, Melder_double (t)); if (! my soundFollowsMouse) { VowelEditor_Vowel_updateTiers (me, thee, MINIMUM_SOUND_DURATION, x, y); goto end; } } Graphics_xorOn (my g, Graphics_BLUE); while (Graphics_mouseStillDown (my g)) { xb = x, yb = y, tb = t; t = Melder_clock () - t0 + dt; // Get relative time in seconds from the clock Graphics_getMouseLocation (my g, & x, & y); checkXY (&x, &y); // If the new point equals the previous one: no tier update if (xb == x && yb == y) { iskipped++; continue; } // Add previous point only if at least one previous event was skipped... if (iskipped > 0) { VowelEditor_Vowel_updateTiers (me, thee, tb, xb, yb); } iskipped = 0; Graphics_line (my g, xb, yb, x, y); VowelEditor_Vowel_updateTiers (me, thee, t, x, y); GuiText_setString (my durationTextField, Melder_double (MICROSECPRECISION (t))); } t = Melder_clock () - t0; // To prevent ultra short clicks we set a minimum of 0.01 s duration if (t < MINIMUM_SOUND_DURATION) { t = MINIMUM_SOUND_DURATION; } t += dt; GuiText_setString (my durationTextField, Melder_double (MICROSECPRECISION (t))); VowelEditor_Vowel_updateTiers (me, thee, t, x, y); Graphics_xorOff (my g); end: Graphics_unsetInner (my g); if (my shiftKeyPressed == 0) { forget (my vowel); my vowel = athee.transfer(); } gb_event.button = my drawingArea; gui_button_cb_play (me, & gb_event); } static void gui_drawingarea_cb_key (I, GuiDrawingAreaKeyEvent event) { iam (VowelEditor); (void) me; (void) event; } static void cb_publish (Editor editor, void *closure, Data publish) { (void) editor; (void) closure; try { praat_new (publish, 0); praat_updateSelection (); } catch (MelderError) { Melder_flushError (0); } } static void updateWidgets (I) { iam (VowelEditor); (void) me; } void structVowelEditor :: v_destroy () { forget (g); forget (marks); forget (source); forget (target); forget (vowel); forget (f3); forget (b3); forget (f4); forget (b4); VowelEditor_Parent :: v_destroy (); } void structVowelEditor :: v_createMenus () { VowelEditor_Parent :: v_createMenus (); Editor_addMenu (this, L"View", 0); Editor_addCommand (this, L"File", L"Preferences...", 0, menu_cb_prefs); Editor_addCommand (this, L"File", L"-- publish data --", 0, NULL); Editor_addCommand (this, L"File", L"Publish Sound", 0, menu_cb_publishSound); Editor_addCommand (this, L"File", L"Extract KlattGrid", 0, menu_cb_extract_KlattGrid); Editor_addCommand (this, L"File", L"Extract FormantGrid", 0, menu_cb_extract_FormantGrid); Editor_addCommand (this, L"File", L"Extract PitchTier", 0, menu_cb_extract_PitchTier); Editor_addCommand (this, L"File", L"-- drawing --", 0, NULL); Editor_addCommand (this, L"File", L"Draw trajectory...", 0, menu_cb_drawTrajectory); Editor_addCommand (this, L"File", L"-- scripting --", 0, NULL); Editor_addCommand (this, L"Edit", L"-- f0 --", 0, NULL); Editor_addCommand (this, L"Edit", L"Set F0...", 0, menu_cb_setF0); Editor_addCommand (this, L"Edit", L"Set F3 & F4...", 0, menu_cb_setF3F4); Editor_addCommand (this, L"Edit", L"-- trajectory commands --", 0, NULL); Editor_addCommand (this, L"Edit", L"Reverse trajectory", 0, menu_cb_reverseTrajectory); Editor_addCommand (this, L"Edit", L"Modify trajectory duration...", 0, menu_cb_modifyTrajectoryDuration); Editor_addCommand (this, L"Edit", L"New trajectory...", 0, menu_cb_newTrajectory); Editor_addCommand (this, L"Edit", L"Extend trajectory...", 0, menu_cb_extendTrajectory); Editor_addCommand (this, L"Edit", L"Shift trajectory...", 0, menu_cb_shiftTrajectory); Editor_addCommand (this, L"View", L"F1 & F2 range...", 0, menu_cb_ranges_f1f2); Editor_addCommand (this, L"View", L"--show vowel marks--", 0, NULL); Editor_addCommand (this, L"View", L"Show one vowel mark...", Editor_HIDDEN, menu_cb_showOneVowelMark); Editor_addCommand (this, L"View", L"Show vowel marks...", Editor_HIDDEN, menu_cb_showVowelMarks); Editor_addCommand (this, L"View", L"Show vowel marks from fixed set...", 0, menu_cb_showVowelMarks); Editor_addCommand (this, L"View", L"Show vowel marks from Table file...", 0, menu_cb_showVowelMarksFromTableFile); Editor_addCommand (this, L"View", L"--show trajectory time marks--", 0, NULL); Editor_addCommand (this, L"View", L"Show trajectory time marks every...", 0, menu_cb_showTrajectoryTimeMarksEvery); } void structVowelEditor :: v_createHelpMenuItems (EditorMenu menu) { VowelEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"VowelEditor help", '?', menu_cb_help); } void structVowelEditor :: v_createChildren () { GuiObject form; // Origin is top left! #if gtk guint nrows = 25, ncols = 7, ileft, iright = 0, itop, ibottom; form = d_windowForm; GuiObject table = gtk_table_new (nrows, ncols, false); gtk_table_set_row_spacings (GTK_TABLE (table), 4); gtk_table_set_col_spacings (GTK_TABLE (table), 4); gtk_container_set_border_width (GTK_CONTAINER (table), 4); gtk_container_add (GTK_CONTAINER (form), GTK_WIDGET (table)); itop = nrows - 3; ibottom = itop + 2; ileft = iright; iright = ileft + 1; playButton = GuiButton_create (NULL, 0, 0, 0, 0, L"Play", gui_button_cb_play, this, 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (playButton), ileft, iright, itop, ibottom); ileft = iright; iright = ileft + 1; reverseButton = GuiButton_create (NULL, 0, 0, 0, 0, L"Reverse", gui_button_cb_reverse, this, 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (reverseButton), ileft, iright, itop, ibottom); ileft = iright; iright = ileft + 1; publishButton = GuiButton_create (NULL, 0, 0, 0, 0, L"Publish", gui_button_cb_publish, this, 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (publishButton), ileft, iright, itop, ibottom); ileft = iright; iright = ileft + 1; durationLabel = GuiLabel_create (NULL, 0, 0, 0, 0, L"Duration (s):", 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (durationLabel), ileft, iright, itop, itop + 1); durationTextField = GuiText_create (NULL, 0, 0, 0, 0, 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (durationTextField), ileft, iright, itop + 1, ibottom); ileft = iright; iright = ileft + 1; extendLabel = GuiLabel_create (NULL, 0, 0, 0, 0, L"Extend (s):", 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (extendLabel), ileft, iright, itop, itop + 1); extendTextField = GuiText_create (NULL, 0, 0, 0, 0, 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (extendTextField), ileft, iright, itop + 1, ibottom); ileft = iright; iright = ileft + 1; f0Label = GuiLabel_create (NULL, 0, 0, 0, 0, L"Start F0 (Hz):", 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (f0Label), ileft, iright, itop, itop + 1); f0TextField = GuiText_create (NULL, 0, 0, 0, 0, 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (f0TextField), ileft, iright, itop + 1, ibottom); ileft = iright; iright = ileft + 1; f0SlopeLabel = GuiLabel_create (NULL, 0, 0, 0, 0, L"F0 slope (oct/s):", 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (f0SlopeLabel), ileft, iright, itop, itop + 1); f0SlopeTextField = GuiText_create (NULL, 0, 0, 0, 0, 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (f0SlopeTextField), ileft, iright, itop + 1, ibottom); itop = nrows - 1; ibottom = itop + 1; ileft = 0; iright = ileft + 3; startInfo = GuiLabel_create (NULL, 0, 0, 0, 0, L"", 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (startInfo), ileft, iright, itop, ibottom); ileft = iright + 1; iright = ileft + 3; endInfo = GuiLabel_create (NULL, 0, 0, 0, 0, L"", 0); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (endInfo), ileft, iright, itop, ibottom); drawingArea = GuiDrawingArea_create (NULL, 0, 0, 0, 0, gui_drawingarea_cb_expose, gui_drawingarea_cb_click, gui_drawingarea_cb_key, gui_drawingarea_cb_resize, this, 0); gtk_widget_set_double_buffered (GTK_WIDGET (drawingArea), FALSE); gtk_table_attach_defaults (GTK_TABLE (table), GTK_WIDGET (drawingArea), 0, ncols, 0, nrows - 3); gtk_widget_show_all (GTK_WIDGET (form)); #elif motif double button_width = 60, text_width = 95, status_info_width = 290; double left, right, top, bottom, bottom_widgets_top, bottom_widgets_bottom, bottom_widgets_halfway; form = XmCreateForm (d_windowForm, "buttons", NULL, 0); XtVaSetValues (form, XmNleftAttachment, XmATTACH_FORM, XmNrightAttachment, XmATTACH_FORM, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, Machine_getMenuBarHeight (), XmNbottomAttachment, XmATTACH_FORM, XmNtraversalOn, False, /* Needed in order to redirect all keyboard input to the text widget?? */ NULL); // Three buttons on a row: Play, Reverse, Publish left = 10; right = left + button_width; bottom_widgets_top = top = -MARGIN_BOTTOM + 10; bottom_widgets_bottom = bottom = -STATUS_INFO; playButton = GuiButton_createShown (form, left, right, top, bottom, L"Play", gui_button_cb_play, this, 0); left = right + 10; right = left + button_width; reverseButton = GuiButton_createShown (form, left, right, top, bottom, L"Reverse", gui_button_cb_reverse, this, 0); left = right + 10; right = left + button_width; publishButton = GuiButton_createShown (form, left, right, top, bottom, L"Publish", gui_button_cb_publish, this, 0); // Four Text widgets with the label on top: Duration, Extend, F0, Slope // Make the F0 slope button 10 wider to accomodate the text // We wil not use a callback from a Text widget. It will get called multiple times during the editing // of the text. Better to have all editing done and then query the widget for its value! left = right + 10; right = left + text_width; bottom_widgets_halfway = bottom = (top + bottom) / 2; top = bottom_widgets_top; durationLabel = GuiLabel_createShown (form, left, right, top , bottom, L"Duration (s):", 0); top = bottom; bottom = bottom_widgets_bottom; durationTextField = GuiText_createShown (form, left, right, top, bottom, 0); left = right + 10; right = left + text_width; top = bottom_widgets_top; bottom = bottom_widgets_halfway; extendLabel = GuiLabel_createShown (form, left, right, top, bottom, L"Extend (s):", 0); top = bottom; bottom = bottom_widgets_bottom; extendTextField = GuiText_createShown (form, left, right, top, bottom, 0); left = right + 10; right = left + text_width; top = bottom_widgets_top; bottom = bottom_widgets_halfway; f0Label = GuiLabel_createShown (form, left, right, top, bottom, L"Start F0 (Hz):", 0); top = bottom; bottom = bottom_widgets_bottom; f0TextField = GuiText_createShown (form, left, right, top, bottom, 0); left = right + 10; right = left + text_width + 10; top = bottom_widgets_top; bottom = bottom_widgets_halfway; f0SlopeLabel = GuiLabel_createShown (form, left, right, top, bottom, L"F0 slope (oct/s):", 0); top = bottom; bottom = bottom_widgets_bottom; f0SlopeTextField = GuiText_createShown (form, left, right, top, bottom, 0); // The status startInfo and endInfo widget at the bottom: bottom = - (STATUS_INFO - Gui_LABEL_HEIGHT) / 2; top = bottom - Gui_LABEL_HEIGHT; left = MARGIN_LEFT; right = left + status_info_width; startInfo = GuiLabel_createShown (form, left, right, top, bottom, L"", 0); left = right; right = left + status_info_width; endInfo = GuiLabel_createShown (form, left, right, top, bottom, L"", 0); /***** Create drawing area. *****/ // Approximately square because for our defaults: f1min=200, f1max=1000 and f2min = 500, f2mx = 2500, // log distances are equal (log (1000/200) == log (2500/500) ). drawingArea = GuiDrawingArea_createShown (form, 0, 0, 0, -MARGIN_BOTTOM, gui_drawingarea_cb_expose, gui_drawingarea_cb_click, gui_drawingarea_cb_key, gui_drawingarea_cb_resize, this, 0); height = GuiObject_getHeight (drawingArea); width = GuiObject_getWidth (drawingArea); GuiObject_show (form); #endif } static void VowelEditor_setSource (VowelEditor me) { autoPitchTier pt = VowelEditor_to_PitchTier (me, my maximumDuration); autoSound thee = PitchTier_to_Sound_pulseTrain (pt.peek(), my f0.samplingFrequency, my f0.adaptFactor, my f0.adaptTime, my f0.interpolationDepth, 0); if (my source != 0) { forget (my source); } my source = thee.transfer(); } // static Sound VowelEditor_createTarget (VowelEditor me) { try { VowelEditor_updateVowel (me); // update pitch and duration autoSound thee = Vowel_to_Sound_pulses (my vowel, 44100, 0.7, 0.05, 30); Vector_scale (thee.peek(), 0.99); Sound_fadeIn (thee.peek(), 0.005, 1); Sound_fadeOut (thee.peek(), 0.005); return thee.transfer(); } catch (MelderError) { Melder_throw ("Target Sound not created."); } } VowelEditor VowelEditor_create (GuiObject parent, const wchar *title, Data data) { try { autoVowelEditor me = Thing_new (VowelEditor); Editor_init (me.peek(), parent, 0, 0, prefs.shellWidth, prefs.shellHeight, title, data); #if motif Melder_assert (XtWindow (my drawingArea)); #endif my g = Graphics_create_xmdrawingarea (my drawingArea); Graphics_setFontSize (my g, 12); my setPublicationCallback (cb_publish, NULL); my f1min = prefs.f1min; my f1max = prefs.f1max; my f2min = prefs.f2min; my f2max = prefs.f2max; my frequencyScale = prefs.frequencyScale; my axisOrientation = prefs.axisOrientation; my speakerType = prefs.speakerType; my marksDataset = prefs.marksDataset; my marksFontSize = prefs.marksFontSize; my soundFollowsMouse = prefs.soundFollowsMouse; if (my marksDataset > 3) { // TODO variable?? VowelEditor_createTableFromVowelMarksInPreferences (me.peek()); } else { VowelEditor_setMarks (me.peek(), my marksDataset, my speakerType, 14); } VowelEditor_setF3F4 (me.peek(), prefs.f3, prefs.b3, prefs.f4, prefs.b4); my maximumDuration = BUFFER_SIZE_SEC; my extendDuration = prefs.extendDuration; if (my data != 0) { my vowel = Data_copy ( (Vowel) data); } else { my vowel = Vowel_create_twoFormantSchwa (0.2); } my markTraceEvery = prefs.markTraceEvery; my f0 = f0default; VowelEditor_setSource (me.peek()); my target = Sound_createSimple (1, my maximumDuration, my f0.samplingFrequency); GuiText_setString (my f0TextField, Melder_double (my f0.start)); GuiText_setString (my f0SlopeTextField, Melder_double (my f0.slopeOctPerSec)); GuiText_setString (my durationTextField, L"0.2"); // Source has been created GuiText_setString (my extendTextField, Melder_double (my extendDuration)); my grid = griddefault; { // This exdents because it's a hack: struct structGuiDrawingAreaResizeEvent event = { my drawingArea, 0 }; event. width = GuiObject_getWidth (my drawingArea); event. height = GuiObject_getHeight (my drawingArea); gui_drawingarea_cb_resize (me.peek(), & event); } //struct structGuiDrawingAreaResizeEvent event = { 0 }; //event.widget = my drawingArea; //gui_drawingarea_cb_resize (me, & event); updateWidgets (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("VowelEditor not created."); } } /* End of file VowelEditor.cpp */ sources_5316/dwtools/CCA_and_Correlation.cpp0000644000176700017670000001214111627172607017703 0ustar paulpaul/* CCA_and_Correlation.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020525 GPL header. djmw 20060323 Stewart-Love redundancy added. djmw 20071022 Melder_error */ #include "CCA_and_Correlation.h" #include "NUM2.h" TableOfReal CCA_and_Correlation_factorLoadings (CCA me, Correlation thee) { try { long ny = my y -> dimension, nx = my x -> dimension; if (ny + nx != thy numberOfColumns) Melder_throw ("The number of columns in the Correlation " "must equal the sum of the dimensions in the CCA object"); autoTableOfReal him = TableOfReal_create (2 * my numberOfCoefficients, thy numberOfColumns); NUMstrings_copyElements (thy columnLabels, his columnLabels, 1, thy numberOfColumns); TableOfReal_setSequentialRowLabels (him.peek(), 1, my numberOfCoefficients, L"dv", 1, 1); TableOfReal_setSequentialRowLabels (him.peek(), my numberOfCoefficients + 1, 2 * my numberOfCoefficients, L"iv", 1, 1); double **evecy = my y -> eigenvectors, **evecx = my x -> eigenvectors; for (long i = 1; i <= thy numberOfRows; i++) { for (long j = 1; j <= my numberOfCoefficients; j++) { double t = 0; for (long k = 1; k <= ny; k++) { t += thy data[i][k] * evecy[j][k]; } his data[j][i] = t; } for (long j = 1; j <= my numberOfCoefficients; j++) { double t = 0; for (long k = 1; k <= nx; k++) { t += thy data[i][ny + k] * evecx[j][k]; } his data[my numberOfCoefficients + j][i] = t; } } return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal not created from CCA & Correlation."); } } static void _CCA_and_Correlation_check (CCA me, Correlation thee, int canonicalVariate_from, int canonicalVariate_to) { if (my y -> dimension + my x -> dimension != thy numberOfColumns) { Melder_throw ("The number of columns in the Correlation object must equal the sum of the dimensions in the CCA object"); } if (canonicalVariate_to < canonicalVariate_from) { Melder_throw ("The second value in the \"Canonical variate range\" must be equal or larger than the first."); } if (canonicalVariate_from < 1 || canonicalVariate_to > my numberOfCoefficients) { Melder_throw ("The \"Canonical variate range\" must be within the interval [1, ", my numberOfCoefficients, "]."); } } double CCA_and_Correlation_getVarianceFraction (CCA me, Correlation thee, int x_or_y, int canonicalVariate_from, int canonicalVariate_to) { _CCA_and_Correlation_check (me, thee, canonicalVariate_from, canonicalVariate_to); /* For the formulas see: William W. Cooley & Paul R. Lohnes (1971), Multivariate data Analysis, John Wiley & Sons, pag 170-... varianceFraction = s'.s / n, where e.g. for the independent set x: s = Rxx . c, and Rxx is the correlation matrix of x, c is the factor coefficient for x, nx is the dimension of x, The factor coefficient c is the eigenvector e for x scaled by the st.dev of the component, i.e. c = e / sqrt (e'.R.e) (pag 32-33). Therefore: varianceFraction = s'.s / n = c'Rxx' Rxx c/n = (e'.Rxx' Rxx.e) /(e'.Rxx.e) * 1/n (for one can. variate) */ long n = my x -> dimension; double **evec = my x -> eigenvectors; long ioffset = my y -> dimension; if (x_or_y == 1) { /* y: dependent set */ n = my y -> dimension; evec = my y -> eigenvectors; ioffset = 0; } double varianceFraction = 0; for (long icv = canonicalVariate_from; icv <= canonicalVariate_to; icv++) { double variance = 0, varianceScaling = 0; for (long i = 1; i <= n; i++) { double si = 0; for (long j = 1; j <= n; j++) { si += thy data[ioffset + i][ioffset + j] * evec[icv][j]; /* Rxx.e */ } variance += si * si; /* (Rxx.e)'(Rxx.e) = e'.Rxx'.Rxx.e */ varianceScaling += evec[icv][i] * si; /* e'.Rxx.e*/ } varianceFraction += (variance / varianceScaling) / n; } return varianceFraction; } double CCA_and_Correlation_getRedundancy_sl (CCA me, Correlation thee, int x_or_y, int canonicalVariate_from, int canonicalVariate_to) { _CCA_and_Correlation_check (me, thee, canonicalVariate_from, canonicalVariate_to); double redundancy = 0; for (long icv = canonicalVariate_from; icv <= canonicalVariate_to; icv++) { double varianceFraction = CCA_and_Correlation_getVarianceFraction (me, thee, x_or_y, icv, icv); if (varianceFraction == NUMundefined) { return NUMundefined; } redundancy += varianceFraction * my y -> eigenvalues[icv]; } return redundancy; } /* End of file CCA_and_Correlation.cpp */ sources_5316/dwtools/CCA.cpp0000644000176700017670000002465711725071435014533 0ustar paulpaul/* CCA.c * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020402 GPL header djme 20021008 removed SVD_sort djmw 20031023 Removed one argument from CCA_and_TableOfReal_scores djmw 20031106 Removed bug from CCA_and_TableOfReal_scores djmw 20031221 Removed bug: CCA_and_TableOfReal_scores (wrong dimensions to Eigen_project_into). djmw 20061212 Changed info to Melder_writeLine format. djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20081119 Check in TableOfReal_to_CCA if TableOfReal_areAllCellsDefined */ #include "CCA_and_Correlation.h" #include "NUM2.h" #include "NUMlapack.h" #include "SVD.h" #include "Strings_extensions.h" #include "TableOfReal_extensions.h" #include "Eigen_and_TableOfReal.h" #include "oo_DESTROY.h" #include "CCA_def.h" #include "oo_COPY.h" #include "CCA_def.h" #include "oo_EQUAL.h" #include "CCA_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "CCA_def.h" #include "oo_WRITE_TEXT.h" #include "CCA_def.h" #include "oo_WRITE_BINARY.h" #include "CCA_def.h" #include "oo_READ_TEXT.h" #include "CCA_def.h" #include "oo_READ_BINARY.h" #include "CCA_def.h" #include "oo_DESCRIPTION.h" #include "CCA_def.h" void structCCA :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of coefficients: ", Melder_integer (numberOfCoefficients)); MelderInfo_writeLine2 (L"ny: ", Melder_integer (y -> dimension)); MelderInfo_writeLine2 (L"nx: ", Melder_integer (x -> dimension)); } Thing_implement (CCA, Data, 0); CCA CCA_create (long numberOfCoefficients, long ny, long nx) { try { autoCCA me = Thing_new (CCA); my numberOfCoefficients = numberOfCoefficients; my yLabels = Thing_new (Strings); my xLabels = Thing_new (Strings); my y = Eigen_create (numberOfCoefficients, ny); my x = Eigen_create (numberOfCoefficients, nx); return me.transfer(); } catch (MelderError) { Melder_throw ("CCA not created."); } } void CCA_drawEigenvector (CCA me, Graphics g, int x_or_y, long ivec, long first, long last, double ymin, double ymax, int weigh, double size_mm, const wchar_t *mark, int connect, int garnish) { Eigen e = my x; Strings labels = my xLabels; if (x_or_y == 1) { e = my y; labels = my yLabels; } Eigen_drawEigenvector (e, g, ivec, first, last, ymin, ymax, weigh, size_mm, mark, connect, labels -> strings, garnish); } double CCA_getEigenvectorElement (CCA me, int x_or_y, long ivec, long element) { Eigen e = x_or_y == 1 ? my y : my x; return Eigen_getEigenvectorElement (e, ivec, element); } CCA TableOfReal_to_CCA (TableOfReal me, long ny) { try { long n = my numberOfRows, nx = my numberOfColumns - ny; if (ny < 1 || ny > my numberOfColumns - 1) { Melder_throw ("Dimension of first part not correct."); } if (ny > nx) Melder_throw (L"The dimension of the dependent part (", ny, L") must be less than or equal to " "the dimension of the independent part (", nx, L")."); if (n < ny) { Melder_throw (L"The number of observations must be larger then ", ny, "."); } TableOfReal_areAllCellsDefined (me, 0, 0, 0, 0); // Use svd as (temporary) storage, and copy data autoSVD svdy = SVD_create (n, ny); autoSVD svdx = SVD_create (n, nx); for (long i = 1; i <= n; i++) { for (long j = 1; j <= ny; j++) { svdy -> u[i][j] = my data[i][j]; } for (long j = 1; j <= nx; j++) { svdx -> u[i][j] = my data[i][ny + j]; } } double **uy = svdy -> u; double **vy = svdy -> v; double **ux = svdx -> u; double **vx = svdx -> v; double fnormy = NUMfrobeniusnorm (n, ny, uy); double fnormx = NUMfrobeniusnorm (n, nx, ux); if (fnormy == 0 || fnormx == 0) { Melder_throw ("One of the parts of the table contains only zeros."); } /* Centre the data and svd it. */ NUMcentreColumns (uy, 1, n, 1, ny, NULL); NUMcentreColumns (ux, 1, n, 1, nx, NULL); SVD_compute (svdy.peek()); SVD_compute (svdx.peek()); long numberOfZeroedy = SVD_zeroSmallSingularValues (svdy.peek(), 0); long numberOfZeroedx = SVD_zeroSmallSingularValues (svdx.peek(), 0); /* Form the matrix C = ux' uy (use svd-object storage) */ autoSVD svdc = SVD_create (nx, ny); double **uc = svdc -> u; double **vc = svdc -> v; for (long i = 1; i <= nx; i++) { for (long j = 1; j <= ny; j++) { double t = 0; for (long q = 1; q <= n; q++) { t += ux[q][i] * uy[q][j]; } uc[i][j] = t; } } SVD_compute (svdc.peek()); long numberOfZeroedc = SVD_zeroSmallSingularValues (svdc.peek(), 0); long numberOfCoefficients = ny - numberOfZeroedc; autoCCA thee = CCA_create (numberOfCoefficients, ny, nx); thy yLabels = strings_to_Strings (my columnLabels, 1, ny); thy xLabels = strings_to_Strings (my columnLabels, ny + 1, my numberOfColumns); double **evecy = thy y -> eigenvectors; double **evecx = thy x -> eigenvectors; thy numberOfObservations = n; /* Y = Vy * inv(Dy) * Vc X = Vx * inv(Dx) * Uc For the eigenvectors we want a row representation: colums(Y) = rows(Y') = rows(Vc' * inv(Dy) * Vy') colums(X) = rows(X') = rows(Uc' * inv(Dx) * Vx') rows(Y') = evecy[i][j] = Vc[k][i] * Vy[j][k] / Dy[k] rows(X') = evecx[i][j] = Uc[k][i] * Vx[j][k] / Dx[k] */ for (long i = 1; i <= numberOfCoefficients; i++) { double ccc = svdc -> d[i]; thy y -> eigenvalues[i] = thy x -> eigenvalues[i] = ccc * ccc; for (long j = 1; j <= ny; j++) { double t = 0; for (long q = 1; q <= ny - numberOfZeroedy; q++) { t += vc[q][i] * vy[j][q] / svdy -> d[q]; } evecy[i][j] = t; } for (long j = 1; j <= nx; j++) { double t = 0; for (long q = 1; q <= nx - numberOfZeroedx; q++) { t += uc[q][i] * vx[j][q] / svdx -> d[q]; } evecx[i][j] = t; } } /* Normalize eigenvectors. */ NUMnormalizeRows (thy y -> eigenvectors, numberOfCoefficients, ny, 1); NUMnormalizeRows (thy x -> eigenvectors, numberOfCoefficients, nx, 1); Melder_assert (thy x -> dimension == thy xLabels -> numberOfStrings && thy y -> dimension == thy yLabels -> numberOfStrings); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": CCA not created."); } } TableOfReal CCA_and_TableOfReal_scores (CCA me, TableOfReal thee, long numberOfFactors) { try { long n = thy numberOfRows; long nx = my x -> dimension, ny = my y -> dimension; if (ny + nx != thy numberOfColumns) Melder_throw ("The number of columns in the table (", thy numberOfColumns, ") does not agree with the dimensions of the CCA object (ny + nx = ", ny, " + ", nx, ")."); if (numberOfFactors == 0) { numberOfFactors = my numberOfCoefficients; } if (numberOfFactors < 1 || numberOfFactors > my numberOfCoefficients) Melder_throw ("The number of factors must be in interval [1, ", my numberOfCoefficients, L"]."); autoTableOfReal him = TableOfReal_create (n, 2 * numberOfFactors); TableOfReal phim = him.peek(); NUMstrings_copyElements (thy rowLabels, his rowLabels, 1, thy numberOfRows); Eigen_and_TableOfReal_project_into (my y, thee, 1, ny, &phim, 1, numberOfFactors); Eigen_and_TableOfReal_project_into (my x, thee, ny + 1, thy numberOfColumns, &phim, numberOfFactors + 1, his numberOfColumns); TableOfReal_setSequentialColumnLabels (him.peek(), 1, numberOfFactors, L"y_", 1, 1); TableOfReal_setSequentialColumnLabels (him.peek(), numberOfFactors + 1, his numberOfColumns, L"x_", 1, 1); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no TableOfReal with scores created."); } } TableOfReal CCA_and_TableOfReal_predict (CCA me, TableOfReal thee, long from) { try { long ny = my y -> dimension, nx = my x -> dimension; long nev = my y -> numberOfEigenvalues; /* We can only predict when we have the largest dimension as input and the number of coefficients equals the dimension of the smallest. */ if (ny != nev) { Melder_throw ("There are not enough correlations present for prediction."); } if (from == 0) { from = 1; } long ncols = thy numberOfColumns - from + 1; if (from < 1 || ncols != nx) { Melder_throw ("The number of columns to analyze must be equal to ", nx, "."); } // ???? dimensions if nx .. ny ?? autoTableOfReal him = Eigen_and_TableOfReal_project (my x, thee, from, ny); autoNUMvector buf (1, ny); // u = V a -> a = V'u double **v = my y -> eigenvectors; double *d = my y -> eigenvalues; for (long i = 1; i <= thy numberOfRows; i++) { NUMvector_copyElements (his data[i], buf.peek(), 1, ny); for (long j = 1; j <= ny; j++) { double t = 0; for (long k = 1; k <= ny; k++) { t += sqrt (d[k]) * v[k][j] * buf[k]; } his data [i][j] = t; } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no predictions created."); } } TableOfReal CCA_and_TableOfReal_factorLoadings (CCA me, TableOfReal thee) { try { autoCorrelation c = TableOfReal_to_Correlation (thee); autoTableOfReal him = CCA_and_Correlation_factorLoadings (me, c.peek()); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no factor loadings created."); } } double CCA_getCorrelationCoefficient (CCA me, long index) { if (index < 1 || index > my numberOfCoefficients) { return NUMundefined; } return sqrt (my y -> eigenvalues[index]); } void CCA_getZeroCorrelationProbability (CCA me, long index, double *chisq, long *ndf, double *probability) { double lambda = 1, *ev = my y -> eigenvalues; long nev = my y -> numberOfEigenvalues; long ny = my y -> dimension, nx = my x -> dimension; *chisq = *probability = NUMundefined; *ndf = 0; if (index < 1 || index > nev) { return; } for (long i = index; i <= nev; i++) { lambda *= (1 - ev[i]); } *ndf = (ny - index + 1) * (nx - index + 1); *chisq = - (my numberOfObservations - (ny + nx + 3) / 2) * log (lambda); *probability = NUMchiSquareQ (*chisq, *ndf); } /* End of file CCA.c */ sources_5316/dwtools/Table_extensions.h0000644000176700017670000000276411737311704017112 0ustar paulpaul#ifndef _Table_extensions_h_ #define _Table_extensions_h_ /* Table_extensions.h * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020411 initial GPL djmw 20110105 Latest modification. */ #include "TableOfReal.h" #include "Collection.h" #include "Pattern.h" #include "Categories.h" #include "Strings.h" #include "SSCP.h" #include "Table.h" Table Table_createFromPetersonBarneyData (); Table Table_createFromPolsVanNieropData (); Table Table_createFromWeeninkData (); double Table_getMedianAbsoluteDeviation (Table me, long columnNumber); void Table_drawScatterPlotWithConfidenceIntervals (Table me, Graphics g, long xcolumn, long ycolumn, double xmin, double xmax, double ymin, double ymax, long xci_min, long xci_max, long yci_min, long yci_max, double bar_mm, int garnish); #endif // _Table_extensions_h_ sources_5316/dwtools/.DTW_def.h.kate-swp0000664000176700017670000000011511735131664016661 0ustar paulpaulKate Swap File - Version 1.0SR6ESR+ ESREsources_5316/dwtools/DTW_def.h0000644000176700017670000000404611627236702015055 0ustar paulpaul/* DTW_def.h * * Copyright (C) 1993-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19981207 djmw 20020813 GPL header djmw 20070216 Latest modification */ #define ooSTRUCT DTW_Path oo_DEFINE_STRUCT (DTW_Path) oo_LONG (x) oo_LONG (y) oo_END_STRUCT (DTW_Path) #undef ooSTRUCT #define ooSTRUCT DTW_Path_Index oo_DEFINE_STRUCT (DTW_Path_Index) oo_LONG (ibegin) oo_LONG (iend) oo_END_STRUCT (DTW_Path_Index) #undef ooSTRUCT #define ooSTRUCT DTW_Path_xytime oo_DEFINE_STRUCT (DTW_Path_xytime) oo_DOUBLE (x) oo_DOUBLE (y) oo_END_STRUCT (DTW_Path_xytime) #undef ooSTRUCT #define ooSTRUCT DTW_Path_Query oo_DEFINE_STRUCT (DTW_Path_Query) oo_LONG (nx) oo_LONG (ny) oo_LONG (nxy) oo_STRUCT_VECTOR (DTW_Path_xytime, xytimes, nxy) oo_STRUCT_VECTOR (DTW_Path_Index, xindex, nx) oo_STRUCT_VECTOR (DTW_Path_Index, yindex, ny) oo_END_STRUCT (DTW_Path_Query) #undef ooSTRUCT #define ooSTRUCT DTW oo_DEFINE_CLASS (DTW, Matrix) oo_DOUBLE (weightedDistance) oo_LONG (pathLength) oo_STRUCT_VECTOR (DTW_Path, path, pathLength) #if ! oo_READING && ! oo_WRITING oo_DOUBLE (wx) oo_DOUBLE (wy) oo_DOUBLE (wd) oo_STRUCT (DTW_Path_Query, pathQuery) #endif #if oo_READING DTW_Path_Query_init (& pathQuery, ny, nx); DTW_Path_recode (this); #endif #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (DTW) #undef ooSTRUCT /* End of file DTW_def.h */ sources_5316/dwtools/Sound_extensions.h0000644000176700017670000002204211735057427017151 0ustar paulpaul#ifndef _Sound_extensions_h_ #define _Sound_extensions_h_ /* Sound_extensions.h * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20120323 Latest modification */ #include "Sound.h" #include "Pitch.h" #include "Collection.h" #include "PointProcess.h" #include "TextGrid.h" #include "Interpreter_decl.h" int Sound_writeToNistAudioFile (Sound me, MelderFile file); Sound Sound_readFromCmuAudioFile (MelderFile file); /* only 16 bit signed has been tested !! */ Sound Sound_readFromRawFile (MelderFile file, const char *format, int nBitsCoding, int littleEndian, int unSigned, long skipNBytes, double samplingFrequency); /* Reads a Sound from a raw file: * fileName : name of the file * format : "integer" (default) * "float" (this implies nBitsCoding=nBitsStorage=32, see below) * nBitsCoding : number of bits used in the coding (1..16) (default = 16 ) * (the storage is assumed to be a multiple of 8 bits ) * littleEndian: if littleEndian != 0 then little-endian else big-endian * unSigned : if unSigned != 0 then unsigned else signed * skipNBytes : start reading after this number of bytes (skipNBytes >= 0 ) */ Sound Sound_readFromDialogicADPCMFile (MelderFile file, double sampleRate); /* */ void Sound_writeToRawFile (Sound me, MelderFile file, const char *format, int littleEndian, int nBitsCoding, int unSigned); void Sound_into_Sound (Sound me, Sound to, double startTime); /* precondition: my dx == to->dx (equal sampling times */ void Sound_overwritePart (Sound me, double t1, double t2, Sound thee, double t3); /* Overwrite the part between (t1,t2) in me with samples from Sound thee, starting at t3 in thee. */ void Sound_preEmphasis (Sound me, double preEmphasisFrequency); /* deEmphasis = exp(- 2 * NUMpi * deEmphasisFrequency * my dx); */ /* for (i=my nx; i >=2; i-- ) my z[1][i] -= preEmphasis * my z[1][i-1]; */ void Sound_deEmphasis (Sound me, double preEmphasisFrequency); /* for (i=2; i <= my nx; i++ ) my z[1][i] += deEmphasis * my z[1][i-1]; */ Sound Sound_createGaussian (double windowDuration, double samplingFrequency); Sound Sound_createHamming (double windowDuration, double samplingFrequency); Sound Sound_createSimpleToneComplex (double minimumTime, double maximumTime, double samplingFrequency, double firstFrequency, long numberOfComponents, double frequencyDistance, int scaleAmplitudes); Sound Sound_createMistunedHarmonicComplex (double minimumTime, double maximumTime, double samplingFrequency, double firstFrequency, long numberOfComponents, long mistunedComponent, double mistuningFraction, int scaleAmplitudes); Sound Sound_createGammaTone (double minimumTime, double maximumTime, double samplingFrequency, long gamma, double frequency, double bandwidth, double initialPhase, double addition, int scaleAmplitudes); Sound Sound_createShepardTone (double minimumTime, double maximumTime, double samplingFrequency, double lowestFrequency, long numberOfComponents, double frequencyChange, double amplitudeRange); Sound Sound_createShepardToneComplex (double minimumTime, double maximumTime, double samplingFrequency, double lowestFrequency, long numberOfComponents, double frequencyChange_st, double amplitudeRange, double octaveShiftFraction); Sound Sound_createPattersonWightmanTone (double minimumTime, double maximumTime, double samplingFrequency, double baseFrequency, double frequencyShiftRatio, long numberOfComponents); Sound Sound_createPlompTone (double minimumTime, double maximumTime, double samplingFrequency, double baseFrequency, double frequencyFraction, long m); Sound Sound_createFromWindowFunction (double effectiveTime, double samplingFrequency, int windowType); /* 1; rect 2:hamming 3: bartlet 4: welch 5: hanning 6:gaussian */ Sound Sound_filterByGammaToneFilter4 (Sound me, double centre_frequency, double bandwidth); void Sounds_multiply (Sound me, Sound thee); /* precondition: my nx = thy nx */ double Sound_correlateParts (Sound me, double t1, double t2, double duration); /* Correlate part (t1, t1+duration) with (t2, t2+duration) */ void Sound_localMean (Sound me, double fromTime, double toTime, double *mean); void Sound_localPeak (Sound me, double fromTime, double toTime, double ref, double *peak); Sound Sound_localAverage (Sound me, double averaginginterval, int windowType); /* y[n] = sum(i=-n, i=n, x[n+i])/(2*n+1) */ double Sound_power (Sound me); void Sound_scale_dB (Sound me, double level_dB); /* Scales the amplitude of a Sound to a certain dB level. The reference value is an amplitude of 1. All amplitudes are multiplied by a scale factor which is 10^(level_dB/10) / extremum, where extremum is the maximum of the absolute values the signal values. */ void Sound_fade (Sound me, int channel, double t, double fadeTime, int inout, int fadeGlobal); /* if inout <= 0 fade in with (1-cos)/2 else fade out with (1+cos)/2 channel = 0 (all), 1 (left), 2 (right). */ #define FROM_LEFT_TO_RIGHT 0 #define FROM_RIGHT_TO_LEFT 1 #define FROM_BOTTOM_TO_TOP 2 #define FROM_TOP_TO_BOTTOM 3 void Sound_draw_btlr (Sound me, Graphics g, double tmin, double tmax, double amin, double amax, int direction, int garnish); /* direction is one of the macros's FROM_LEFT_TO_RIGHT... */ void Sound_drawWhere (Sound me, Graphics g, double tmin, double tmax, double minimum, double maximum, bool garnish, const wchar_t *method, long numberOfBisections, const wchar_t *formula, Interpreter interpreter); void Sound_paintWhere (Sound me, Graphics g, Graphics_Colour colour, double tmin, double tmax, double minimum, double maximum, double level, bool garnish, long numberOfBisections, const wchar_t *formula, Interpreter interpreter); void Sounds_paintEnclosed (Sound me, Sound thee, Graphics g, Graphics_Colour colour, double tmin, double tmax, double minimum, double maximum, bool garnish); Sound Sound_changeGender (Sound me, double pitchMin, double pitchMax, double pitchRatio, double formantFrequenciesRatio, double durationRatio); Sound Sound_and_Pitch_changeGender (Sound me, Pitch him, double pitchRatio, double formantFrequenciesRatio, double durationRatio); Sound Sound_changeGender_old (Sound me, double fmin, double fmax, double formantRatio, double new_pitch, double pitchRangeFactor, double durationFactor); Sound Sound_and_Pitch_changeGender_old (Sound me, Pitch him, double formantRatio, double new_pitch, double pitchRangeFactor, double durationFactor); PointProcess Sound_to_PointProcess_getJumps (Sound me, double minimumJump, double dt); /* Marks jumps in the signal where the amplitude changes more than 'minimumJump' within time dt */ void Sound_filter_part_formula (Sound me, double t1, double t2, const wchar_t *formula, Interpreter interpreter); Sound Sound_changeSpeaker (Sound me, double pitchMin, double pitchMax, double formantMultiplier, // > 0 double pitchMultiplier, // > 0 double pitchRangeMultiplier, // any number double durationMultiplier); // > 0 Sound Sound_and_Pitch_changeSpeaker (Sound me, Pitch him, double formantMultiplier, // > 0 double pitchMultiplier, // > 0 double pitchRangeMultiplier, // any number double durationMultiplier); // > 0 /* Outphased */ Sound Sound_changeGender_old (Sound me, double fmin, double fmax, double formantRatio, double new_pitch, double pitchRangeFactor, double durationFactor); TextGrid Sound_to_TextGrid_detectSilences (Sound me, double minPitch, double timeStep, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, const wchar_t *silentLabel, const wchar_t *soundingLabel); void Sound_getStartAndEndTimesOfSounding (Sound me, double minPitch, double timeStep, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double *t1, double *t2); Sound Sound_and_IntervalTier_cutPartsMatchingLabel (Sound me, IntervalTier thee, const wchar_t *match); /* Cut intervals that match the label from the sound. The starting time of the new sound is * (1) my xmin if the first interval is not matching * (2) the end time of the first interval if matching */ Sound Sound_trimSilencesAtStartAndEnd (Sound me, double trimDuration, double minPitch, double timeStep, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double *t1, double *t2); Sound Sound_trimSilences (Sound me, double trimDuration, bool onlyAtStartAndEnd, double minPitch, double timeStep, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, TextGrid *tg, const wchar_t *trimLabel); #endif /* _Sound_extensions_h_ */ sources_5316/dwtools/manual_Permutation.cpp0000664000176700017670000005343311663507106020005 0ustar paulpaul/* manual_Permutation.cpp * * Copyright (C) 2005-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* 20050709 djmw */ #include "ManPagesM.h" void manual_Permutation_init (ManPages me); void manual_Permutation_init (ManPages me) { MAN_BEGIN (L"Permutation", L"djmw", 20050721) INTRO (L"One of the @@types of objects@ in Praat. A Permutation object with %n elements consists of some ordering of " "the numbers 1,2...%n.") ENTRY (L"Interpretation") NORMAL (L"A permutation like for example (2,3,5,4,1) is an %arrangement of the five objects 1, 2, 3, 4, and 5. " "It tells us that the second object is in the first position, the third object is in the second position, " "the fifth object in the third position and so on.") NORMAL (L"If we combine a Permutation together with an other object, like a Strings for example, we may force a " "new arrangement of the strings, according to the specification in the Permutation (see @@Strings & Permutation: Permute strings@)." ) ENTRY (L"Commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@Create Permutation...@") NORMAL (L"Query:") LIST_ITEM (L"\\bu ##Get number of elements#") LIST_ITEM (L"\\bu @@Permutation: Get value...|Get value...@") LIST_ITEM (L"\\bu @@Permutation: Get index...|Get index...@") NORMAL (L"Modification:") LIST_ITEM (L"\\bu @@Permutation: Sort|Sort@") LIST_ITEM (L"\\bu @@Permutation: Swap blocks...|Swap blocks...@") LIST_ITEM (L"\\bu @@Permutation: Swap positions...|Swap positions...@") LIST_ITEM (L"\\bu @@Permutation: Swap numbers...|Swap numbers...@") LIST_ITEM (L"\\bu @@Permutation: Swap one from range...|Swap one from range...@") NORMAL (L"Permutations:") LIST_ITEM (L"\\bu @@Permutation: Permute randomly...|Permute randomly...@") LIST_ITEM (L"\\bu @@Permutation: Permute randomly (blocks)...|Permute randomly (blocks)...@") LIST_ITEM (L"\\bu @@Permutation: Interleave...|Interleave...@") LIST_ITEM (L"\\bu @@Permutation: Rotate...|Rotate...@") LIST_ITEM (L"\\bu @@Permutation: Reverse...|Reverse...@") LIST_ITEM (L"\\bu @@Permutation: Invert|Invert@") NORMAL (L"Successive permutations:") LIST_ITEM (L"\\bu @@Permutations: Multiply|Multiply@") ENTRY (L"Usage") LIST_ITEM (L"@@Strings & Permutation: Permute strings@ to rearrange the strings in a Strings object.") LIST_ITEM (L"@@TableOfReal & Permutation: Permute rows@ to rearrange the rows in a TableOfReal object.") MAN_END MAN_BEGIN (L"Create Permutation...", L"djmw", 20050709) INTRO (L"A command to create a @Permutation of the numbers 1,2, ..., %numberOfElements.") ENTRY (L"Settings") TAG (L"##Name") DEFINITION (L"the name of the new permutation.") TAG (L"##Number of elements%") DEFINITION (L"the number of elements in the permutation.") TAG (L"##Identity permutation") DEFINITION (L"determines whether the permution will be a randomly chosen one, or the @@identity permutation@.") MAN_END MAN_BEGIN (L"identity permutation", L"djmw", 20050713) INTRO (L"The identity permutation is (1,2,3,...,%numberOfElements), i.e. the numbers 1 to " "%numberOfElements in their natural order. ") MAN_END MAN_BEGIN (L"Permutation: Get value...", L"djmw", 20050709) INTRO (L"Get the value at the index position.") ENTRY (L"Example") NORMAL (L"The query for the value at index 3 for the permutation (3,2,4,5,1) gives 4.") MAN_END MAN_BEGIN (L"Permutation: Get index...", L"djmw", 20050714) INTRO (L"Get the index position of the value. ") ENTRY (L"Example") NORMAL (L"The query for the index of value 3 for the permutation (3,2,4,5,1) gives 1.") MAN_END MAN_BEGIN (L"Permutation: Reverse...", L"djmw", 20110105) INTRO (L"Reverse the elements in the given range.") ENTRY (L"Setting") TAG (L"##Index range#") DEFINITION (L"defines the range of indices that will be reversed.") ENTRY (L"Examples") NORMAL (L"1. With ##Index range# = [0,0], the permutation (1,2,3,4,5) is turned into (5,4,3,2,1). ") NORMAL (L"2. With ##Index range# = [3,0], the permutation (1,2,3,4,5) is turned into (1,2,5,4,3). ") MAN_END MAN_BEGIN (L"Permutation: Swap one from range...", L"djmw", 20110105) INTRO (L"An element at an index, randomly chosen from a range, will be permuted with an element at a prescribed index position.") ENTRY (L"Settings") TAG (L"##Index range#") DEFINITION (L"defines the range of indices from which one will be randomly chosen.") TAG (L"##Index#") DEFINITION (L"defines the special index position whose element will be interchanged with the one chosen from the range.") TAG (L"##Forbid same") DEFINITION (L"when %on, forbids the randomly chosen position and the index position to be the same. " "This switch is only of relevance when the chosen range happens to overlap the index position.") ENTRY (L"Examples") NORMAL (L"With ##Index range# = [0,0], ##Index# = 3, ##Forbid same# is %off and (1,2,3,4,5) as the starting permutation, the outcome might be one of " "the five permutations (3,2,1,4,5), (1,3,2,4,5), (1,2,3,4,5), (1,2,4,3,5), (1,2,5,4,3). If ##Forbid same# were chosen as %on, the " "(1,2,3,4,5) permutation is forbidden and the outcome could only be one of the four remaining permutations.") MAN_END MAN_BEGIN (L"Permutation: Permute randomly...", L"djmw", 20111123) INTRO (L"Generates a new @@Permutation@ by randomly permuting a range of elements in the selected Permutation object.") ENTRY (L"Setting") TAG (L"##Index range#") DEFINITION (L"defines the range of elements that will be permuted. The elements outside this range will be kept intact.") ENTRY (L"Example") NORMAL (L"If we start with the permutation (4,6,3,1,5,2,7) and a chosen ##Index range# that runs from 3 to 6, a new permutation will be generated as follows:") LIST_ITEM (L"1. A new permutation of the same dimension as the selected one will be created. ") LIST_ITEM (L"2. Because the index range starts at 3, the first two elements of the selected permutation will be copied " "to the first two locations in the newly created permutation. The new permutation is now (4,6,.,.,.,.,.), where a " "dot (.) means that the element is unspecified.") LIST_ITEM (L"3. The elements 3 to 6 of the selected permutation, i.e. the numbers (3,1,5,2) will be randomly permuted. " "There are 24 possible permutations of these 4 numbers. Say the outcome happens to be (5,1,3,2). The new permutation is now (4,6,5,1,3,2,.).") LIST_ITEM (L"4. The remaining element (7) is copied to the new permutation. Finally, this results " "in the new permutation being (4,6,5,1,3,2,7).") MAN_END MAN_BEGIN (L"Permutation: Permute randomly (blocks)...", L"djmw", 20110105) INTRO (L"Generates a new @Permutation by randomly permuting blocks of size %blocksize.") ENTRY (L"Settings") TAG (L"##Index range#") DEFINITION (L"the range of elements whose blocks will be permuted.") TAG (L"##Block size#") DEFINITION (L"the size of the blocks that will be permuted. There must fit an integer number of blocks " "in the chosen range.") TAG (L"##Permute within blocks#") DEFINITION (L"when %on, the elements in each block are also randomly permuted.") TAG (L"##No doublets#") DEFINITION (L"guarantees that the first element in each block does not equal the last element of the previous block modulo " "the block size. E.g. the numbers 3, 6, 9 are all equal modulo 3. " "This parameter only has effect when ##Permute within blocks# is %on.") ENTRY (L"Examples") NORMAL (L"1. With ##Index range# = [0,0], ##Block size# = 3 and ##Permute within blocks# is %off, the permutation ((1,2,3),(4,5,6),(7,8,9)) " "is turned into one of six possible permutations, for example into ((4,5,6),(7,8,9),(1,2,3)). (The option ##No doublets# will be ignored and the parentheses are only there to indicate the blocks.)") NORMAL (L"2. With ##Index range# = [0,0], ##Block size# = 3, ##Permute within blocks# is %on and ##No doublets# is %off, " "the permutation ((1,2,3),(4,5,6),(7,8,9)) might turn into ((5,4,6),(9,8,7),(3,1,2)).") NORMAL (L"3. With the same options as 2 but ##No doublets# is %on, the previously given outcome is forbidden because " "the last element of the first block (6) and the first element of the next block (9) are equal modulo 3 (the " "blocksize). A valid outcome might then be ((5,4,6),(8,9,7),(3,1,2)).") MAN_END MAN_BEGIN (L"Permutation: Swap blocks...", L"djmw", 20110105) INTRO (L"A command to swap the contents of two index ranges in the selected @Permutation.") ENTRY (L"Settings") TAG (L"##From index#, ##To index#") DEFINITION (L"the two starting positions from where elements are to be swapped. The blocks may overlap.") TAG (L"##Block size#") DEFINITION (L"determines the number of pairs to swap. ") ENTRY (L"Behaviour") NORMAL (L"If the ##Block size# equals one, only the elements at the ##From index# and ##To index# position are swapped. If blocksize is greater than one, the two elements at ##From index#+1 and ##To index#+1 will be swapped too. This goes on until the last two elements in each block have been swapped.") ENTRY (L"Examples") NORMAL (L"1. Swap two blocks: with ##From index# = 1, ##To index# = 4, and ##Block size# = 2, the permutation (1,2,3,4,5) is turned into (4,5,3,1,2).") NORMAL (L"2. Swap two elements: with ##From index# = 1, ##To index# = 4, and ##Block size# = 1, the permutation (1,2,3,4,5) is turned into (4,2,3,1,5).") NORMAL (L"3. Swap two overlapping blocks: with ##From index# = 1, ##To index# = 3, and ##Block size# = 3, the permutation (1,2,3,4,5) is turned into " "(3,4,5,2,1).") MAN_END MAN_BEGIN (L"Permutation: Swap positions...", L"djmw", 20110105) INTRO (L"Swaps the contents at two indices in the selected @@Permutation@.") ENTRY (L"Settings") TAG (L"##First index#, ##Second index#") DEFINITION (L"the two indices from where elements have to be swapped. The order of these indices is not important.") ENTRY (L"Example") NORMAL (L"With ##First index# = 1 and ##Second index# = 3, the permutation (1,3,4,2,5) is turned into (4,3,1,2,5).") MAN_END MAN_BEGIN (L"Permutation: Swap numbers...", L"djmw", 20110105) INTRO (L"Swaps two numbers in the selected @@Permutation@.") ENTRY (L"Settings") TAG (L"##First number#, ##Second number#") DEFINITION (L"the two numbers that have to be swapped. The order of these numbers is not important.") ENTRY (L"Example") NORMAL (L"With ##First number# = 1 and ##Second number# = 3, the permutation (1,3,4,2,5) is turned into (3,1,4,2,5).") MAN_END MAN_BEGIN (L"Permutation: Interleave...", L"djmw", 20110105) INTRO (L"Generates a new @Permutation by interleaving elements from successive blocks. ") NORMAL (L"We always start with the first element in the first block. When the offset is zero, the next element will be the first " "element of the second block, then the first element of the third block. After the first element of the last block, we start again " "with the second elements in each block. And so on. (In card playing, with two blocks of 26 cards each, this is called a faro " "shuffle and eight successive faro shuffles will return the deck to precisely the order in which you began.)") NORMAL (L"If the offset differs from zero and equals 1 for example, we start with the first element in the first block, then the " "second element in the second block, the third element in the third block and so on. When the last element of a block is reached " "and the number of blocks is not exhausted the next element will be the first from the next block. When the last block is reached, " "we start the same cycle again with the next lower element in the first block (which by the way need not be the second element, " "see also example 4).") ENTRY (L"Settings") TAG (L"##Index range#") DEFINITION (L"the range of elements that will be permuted.") TAG (L"##Block size#") DEFINITION (L"the size of a block. An integer number of blocks must fit " "in the chosen ##Index range#.") TAG (L"##Offset#") DEFINITION (L"determines the relative positions of selected elements in successive blocks.") ENTRY (L"Examples") NORMAL (L"1. With ##Index range# = [0,0], ##Block size# = 3, and ##Offset# = 0, the permutation ((1,2,3),(4,5,6),(7,8,9)) is turned into (1,4,7,2,5,8,3,6,9).") NORMAL (L"2. With ##Index range# = [0,0], ##Block size# = 3, and ##Offset# = 1, the permutation ((1,2,3),(4,5,6),(7,8,9)) is turned into (1,5,9,2,6,7,3,4,8).") NORMAL (L"3. With ##Index range# = [0,0], ##Block size# = 3, and ##Offset# = 2, the permutation ((1,2,3),(4,5,6),(7,8,9)) is turned into (1,6,8,2,4,9,3,5,7).") NORMAL (L"4. With ##Index range# = [0,0], ##Block size# = 4, and ##Offset# = 1, the permutation ((1,2,3,4),(5,6,7,8)) is turned into (1,6,3,8,2,7,4,5).") MAN_END MAN_BEGIN (L"Permutation: Next", L"djmw", 20100521) NORMAL (L"Get the next @@Permutation|permutation@ in lexicographic order. Starting with the identity permutation and " "repeatedly applying this function will iterate through all possible permutations. If no further permutation " "is available the current permutation will not change. ") ENTRY (L"Examples") NORMAL (L"If we start with (1,2,3,4) successively applying Next will generate the following sequence (1,2,4,3), (1,3,2,4), (1,3,4,2), (1,4,2,3), (1,4,3,2), etc.") MAN_END MAN_BEGIN (L"Permutation: Previous", L"djmw", 20100521) NORMAL (L"Get the previous @@Permutation|permutation@ in lexicographic order. If no further permutation " "is available the current permutation will not change. ") NORMAL (L"This Previous operation follows the opposite order of @@Permutation: Next@.") MAN_END MAN_BEGIN (L"Permutation: Rotate...", L"djmw", 20110105) INTRO (L"A circular shift of all elements within the given range.") ENTRY (L"Settings") TAG (L"##Index range#") DEFINITION (L"the range of elements that will be circularly permuted.") // ambiguous; are these the positions or the numbers? TAG (L"##Step size#") DEFINITION (L"define how many positions each element will be shifted.") ENTRY (L"Examples") NORMAL (L"1. With ##Step size# = 2 and ##Index range# = [1,5], the permutation (1,2,3,4,5) is turned into (4,5,1,2,3). ") NORMAL (L"2. With ##Step size# = 2 and ##Index range# = [2,5], the permutation ((1),(2,3,4,5)) is turned into ((1),(4,5,2,3))") NORMAL (L"3. With ##Step size# = -1 and ##Index range# = [0,0], the permutation (1,2,3,4,5) is turned into (2,3,4,5,1).") MAN_END MAN_BEGIN (L"Permutation: Invert", L"djmw", 20050709) INTRO (L"Generates the inverse of the selected @Permutation.") ENTRY (L"Example") NORMAL (L"If the permutation is (1,5,3,2,4) the inverse will be (1,4,3,5,2). If we @@Permutations: Multiply|multiply@ these two permutations the result will be the identity permutation (1,2,3,4,5).") MAN_END MAN_BEGIN (L"Permutations: Multiply", L"djmw", 20050717) INTRO (L"Apply the selected @@Permutation@s one after the other. ") NORMAL (L"Permutations are %not commutative, i.e. applying permutation %p__1_ after %p__2_ might not give the same outcome as applying " "%p__2_ after %p__1_.") MAN_END MAN_BEGIN (L"Permutation: Sort", L"djmw", 20050709) INTRO (L"Sorts the elements ascending, i.e. set the selected @@Permutation@ to the @@identity permutation@.") MAN_END MAN_BEGIN (L"TableOfReal & Permutation: Permute rows", L"djmw", 20050709) INTRO (L"Generate a new @TableOfReal with a row ordering determined by the @Permutation.") ENTRY (L"Example") NORMAL (L"If the selected TableOfReal has 5 rows and the permutation is (5,4,3,2,1) the first row of the new TableOfReal equals the fifth row of the selected, the second row of new equals the fourth row of the selected and so on.") MAN_END MAN_BEGIN (L"Strings & Permutation: Permute strings", L"djmw", 20050721) INTRO (L"Generate a new @Strings with a strings ordering determined by the @Permutation.") NORMAL (L"The number of strings in the #Strings and the number of elements in the #Permutation have to be equal.") ENTRY (L"Examples") NORMAL (L"1. If the selected Strings has the 4 strings ordered as \"heed\", \"hid\", \"hood\", \"hud\", and the permutation is " "(4,3,2,1), the new Strings has the ordering \"hud\", \"hood\", \"hid\", \"heed\".") NORMAL (L"2. In the example that is discussed in the @@ExperimentMFC|listening experiment@ section, we have four stimuli \"heed.wav\", " "\"hid.wav\", \"hood.wav\", \"hud.wav\" that we want to present three times to each subject with a " "randomization strategy, i.e. stimuli presented in blocks of four, randomized, and no two successive stimuli equal. " "This type of randomization can easily be accomplished with a Permutation object and a Strings." ) LIST_ITEM (L"1. Fill the Strings object with 12 strings, i.e. three repetitions of the four stimuli. ") LIST_ITEM (L"2. Create a Permutation object with 12 elements and perform ##@@Permutation: Permute randomly (blocks)...|Permute randomly (blocks)...@ 0 0 4 yes yes#. We randomly permute blocks of size 4 and permute randomly within these blocks and make sure that on the transition from on block to the other no two stimuli are equal. (Of course, the random permutation of the blocks makes no difference here since all the blocks have the same content.)") LIST_ITEM (L"3. Select the Strings and the Permutation together and choose ##Permute strings#. " "Now the new Strings will contain the new ordering of the stimuli.") MAN_END MAN_BEGIN (L"Strings: To Permutation...", L"djmw", 20050721) INTRO (L"Generates a @Permutation with the same number of elements as the @Strings.") ENTRY (L"Setting") TAG (L"##Sort") DEFINITION (L"determines whether the Permutation will have an element ordering that can be used to sort the Strings alphabetically.") ENTRY (L"Example") NORMAL (L"If \"Sort\" is %on, and the selected Strings contains 4 strings ordered as \"hud\", \"hid\", \"hood\", " "\"heed\", the generated Permutation will be (4,2,3,1). If you now select the String and the Permutation " "together and choose @@Strings & Permutation: Permute strings|Permute strings@, the new Strings will have " "the strings ordered alphabetically as \"heed\", \"hid\", \"hood\", \"hud\". " "You can also sort the Strings alphabetically descending, by first @@Permutation: Reverse...|reversing@ " "the elements in the Permutation before you select the Permutation and the Strings together. ") MAN_END MAN_BEGIN (L"Index", L"djmw", 20050725) INTRO (L"One of the @@Types of objects|types of objects@ in the P\\s{RAAT} program.") MAN_END MAN_BEGIN (L"Strings: To Index", L"djmw", 20050721) INTRO (L"Generates an @Index from the selected @Strings.") ENTRY (L"Example") NORMAL (L"We start from the following #Strings:") CODE (L"6 (number of strings)") CODE (L"\"hallo\"") CODE (L"\"dag allemaal\"") CODE (L"\"hallo\"") CODE (L"\"tot morgen\"") CODE (L"\"hallo\"") CODE (L"\"tot morgen\"") NORMAL (L"This will give us the following #Index:") CODE (L"1 (number of columns) \"\" (no column name)") CODE (L"\"dag allemaal\"") CODE (L"\"hallo\"") CODE (L"\"tot morgen\"") CODE (L"6 (number of elements)") CODE (L"2") CODE (L"1") CODE (L"2") CODE (L"3") CODE (L"2") CODE (L"3") MAN_END MAN_BEGIN (L"Index: To Permutation...", L"djmw", 20050725) INTRO (L"Generates a @Permutation from the selected @Index by randomly permuting blocks of equivalent elements.") NORMAL (L"Suppose your data consists of groups of equivalent elements and the number of elements in the groups are not equal. You want to make random ordering of your data such that the elements in a group stay together. The following example shows you how.") ENTRY (L"Setting") TAG (L"##Permute within classes") DEFINITION (L"determines whether the elements within a class will be randomly permuted.") ENTRY (L"Example") NORMAL (L"Suppose your data, for example a @Strings, consists of groups of equivalent elements and the number of elements in the groups are not equal. You want to make a random ordering of your data such that the elements in a group stay together. The following example shows you how.") NORMAL (L"We start from the following Strings:") CODE (L"6 (number of strings)") CODE (L"\"hallo\"") CODE (L"\"dag allemaal\"") CODE (L"\"hallo\"") CODE (L"\"tot morgen\"") CODE (L"\"hallo\"") CODE (L"\"tot morgen\"") NORMAL (L"We choose @@Strings: To Index|To Index@ which will give us the following #Index:") CODE (L"1 (number of columns) \"\" (no column name)") CODE (L"\"dag allemaal\"") CODE (L"\"hallo\"") CODE (L"\"tot morgen\"") CODE (L"6 (number of elements)") CODE (L"2") CODE (L"1") CODE (L"2") CODE (L"3") CODE (L"2") CODE (L"3") NORMAL (L"We choose ##To Permutation# and with ##Permute within classes# %off, this might generate the permutation (2,4,6,1,3,5).") NORMAL (L"Selecting the Permutation and the Strings together and choosing @@Strings & Permutation: " "Permute strings|Permute strings@ will generate the following Strings:") CODE (L"\"dag allemaal\"") CODE (L"\"tot morgen\"") CODE (L"\"tot morgen\"") CODE (L"\"hallo\"") CODE (L"\"hallo\"") CODE (L"\"hallo\"") NORMAL (L"We see that the permutation always keeps identical strings together.") MAN_END MAN_BEGIN (L"Index: Extract part...", L"djmw", 20050725) INTRO (L"Creates a new @Index by copying a part of selected Index.") ENTRY (L"Example") NORMAL (L"Given the following Index:") CODE (L"1 (number of columns) \"\" (no column name)") CODE (L"\"dag allemaal\"") CODE (L"\"hallo\"") CODE (L"\"tot morgen\"") CODE (L"6 (number of elements)") CODE (L"2") CODE (L"1") CODE (L"2") CODE (L"3") CODE (L"2") CODE (L"3") NORMAL (L"The command ##Extract part... 1 2# gives you the new Index:") CODE (L"1 (number of columns) \"\" (no column name)") CODE (L"\"dag allemaal\"") CODE (L"\"hallo\"") CODE (L"\"tot morgen\"") CODE (L"6 (number of elements)") CODE (L"2") CODE (L"1") NORMAL (L"Note that all classes stay intact and may have zero references like for example the \"tot morgen\" class. ") MAN_END } /* End of file manual_Permutation.cpp */ sources_5316/dwtools/manual_BSS.cpp0000664000176700017670000005365111747043037016130 0ustar paulpaul/* manual_BSS.cpp * * Copyright (C) 2010-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20101227 Initial version */ #include "ManPagesM.h" void manual_BSS (ManPages me); void manual_BSS (ManPages me) { MAN_BEGIN (L"CrossCorrelationTable", L"djmw", 20110105) INTRO (L"One of the types of objects in Praat. A CrossCorrelationTable represents the cross-correlations between " "a number of signals. Cell [%i,%j] of a CrossCorrelationTable contains the cross-correlation between the %i-th " "and the %j-th signal. For example, the CrossCorrelationTable of an %n-channel sound is a %n\\xx%n table where " "the number in cell [%i,%j] is the cross-correlation of channel %i with channel %j (for a particular lag time %\\ta).") NORMAL (L"A CrossCorrelationTable has a square matrix whose cells contain the cross-correlations between " "the signals and a centroid vector with the average value of each signal.") ENTRY (L"Remarks") NORMAL (L"Sometimes in the statistical literature, the cross-correlation between signals is also called " "\"covariance\". However, the only thing a @@Covariance@ has in common with a CrossCorrelationTable is that " "both are symmetric matrices. The differences between a CrossCorrelationTable and a Covariance are:") TAG (L"1. a Covariance matrix is always positive-definite; for a cross-correlation table this is only guaranteed if " "the lag time %\\ta = 0.") TAG (L"2. The elements %%c__ij_% in a Covariance always satisfy |%%c__ij_%/\\Vr(%%c__ii_%\\.c%%c__jj_%)| \\<_ 1; this is " "generally not the case for cross-correlations.") MAN_END MAN_BEGIN (L"CrossCorrelationTables", L"djmw", 20101227) INTRO (L"One of the types of objects in Praat. A CrossCorrelationTables represents a collection of @@CrossCorrelationTable@ objects.") MAN_END MAN_BEGIN (L"CrossCorrelationTables: Create test set...", L"djmw", 20110212) INTRO (L"Create a collection of @@CrossCorrelationTable@s that are all derived from different diagonal matrices by the same transformation matrix.") ENTRY (L"Settings") SCRIPT (5.4, Manual_SETTINGS_WINDOW_HEIGHT (4), L"" Manual_DRAW_SETTINGS_WINDOW ("CrossCorrelationTables: Create test set", 4) Manual_DRAW_SETTINGS_WINDOW_FIELD ("Matrix dimension", "5") Manual_DRAW_SETTINGS_WINDOW_FIELD ("Number of matrices", "20") Manual_DRAW_SETTINGS_WINDOW_BOOLEAN("First is positive-definite",1) Manual_DRAW_SETTINGS_WINDOW_FIELD ("Sigma", "0.02") ) TAG (L"##Matrix dimension") DEFINITION (L"determines the size of the square matrix with cross-correlations.") TAG (L"##Number of matrices") DEFINITION (L"determines the number of matrices that have to be generated.") TAG (L"##First is positive-definite") DEFINITION (L"guarantees that the first matrix of the series is positive definite.") TAG (L"##Sigma") DEFINITION (L"the standard deviation of the noise that is added to each transformation matrix element. A value " "of zero makes all the cross-correlation matrices jointly diagonalizable. A value greater than zero " "makes each transformation matrix a little different and the collection not jointly " "diagonalizable anymore.") ENTRY (L"Algorithm") NORMAL (L"All the CrossCorrelationTable matrices are generated as #V\\'p\\.c#D__%k_\\.c #V, where #D__%k_ is a diagonal matrix " "with entries randomly choosen from the [-1,1] interval. The matrix #V is a \"random\" orthogonal matrix " "obtained from the singular value decomposition of a matrix #M = #U\\.c#D\\.c#V\\'p, where the cells of the " "matrix #M are random Gaussian numbers with mean 0 and standard deviation 1.") NORMAL (L"If the first matrix has to be positive definite, the numbers on the diagonal of #D__1_ are randomly " "chosen from the [0.1,1] interval.") MAN_END MAN_BEGIN (L"Sound: To CrossCorrelationTable...", L"djmw", 20110212) INTRO (L"A command that creates a @@CrossCorrelationTable@ form every selected @@Sound@ object.") ENTRY (L"Settings") SCRIPT (5.4, Manual_SETTINGS_WINDOW_HEIGHT (2), L"" Manual_DRAW_SETTINGS_WINDOW ("Sound: To CrossCorrelationTable", 2) Manual_DRAW_SETTINGS_WINDOW_RANGE("Time range", "0.0", "10.0") Manual_DRAW_SETTINGS_WINDOW_FIELD ("Lag time", "0.0") ) TAG (L"##Time range (s)#,") DEFINITION (L"determines the time range over which the table is calculated.") TAG (L"##Lag time (s)#,") DEFINITION (L"determines the lag time.") ENTRY (L"Algorithm") NORMAL (L"The cross-correlation between channel %i and channel %j for lag time \\ta is defined as the " "discretized #integral") FORMULA (L"cross-corr (%c__%i_, %c__%j_) [%\\ta] \\=3 \\su__%t_ %c__%i_[%t] %c__%j_[%t+%\\ta] %%\\Det%,") NORMAL (L"where %t and %t+%\\ta are discrete times and %%\\Det% is the @@sampling period@. ") MAN_END MAN_BEGIN (L"Sound: To Covariance (channels)...", L"djmw", 20120303) INTRO (L"Detemines the @@Covariance|covariances@ between the channels of a selected @Sound.") NORMAL (L"The covariance of a sound is determined by calculating the @@CrossCorrelationTable@ of a multichannel sound for a lag time equal to zero.") MAN_END MAN_BEGIN (L"Sound: To Sound (blind source separation)...", L"djmw", 20120428) INTRO (L"Analyze the selected multi-channel sound into its independent components by an iterative method.") NORMAL (L"The @@blind source separation@ method to find the independent components tries to simultaneously diagonalize a number of " "@@CrossCorrelationTable@s that are calculated from the multi-channel sound at different lag times.") ENTRY (L"Settings") SCRIPT (5.4, Manual_SETTINGS_WINDOW_HEIGHT (6), L"" Manual_DRAW_SETTINGS_WINDOW ("Sound: To Sound (blind source separation)", 6) Manual_DRAW_SETTINGS_WINDOW_RANGE("Time range (s)", "0.0", "10.0") Manual_DRAW_SETTINGS_WINDOW_FIELD ("Number of cross-correlations", "20") Manual_DRAW_SETTINGS_WINDOW_FIELD ("Lag times", "0.002") Manual_DRAW_SETTINGS_WINDOW_FIELD ("Maximum number of iterations", "100") Manual_DRAW_SETTINGS_WINDOW_FIELD ("Tolerance", "0.001") Manual_DRAW_SETTINGS_WINDOW_OPTIONMENU("Diagonalization method", "ffdiag") ) TAG (L"##Time range (s)") DEFINITION (L"defines the time range over which the ##CrossCorrelationTable#s of the sound will be calculated.") TAG (L"##Number of cross-correlations") DEFINITION (L"defines the number of ##CrossCorrelationTable#s to be calculated.") TAG (L"##Lag times") DEFINITION (L"defines the lag time %\\ta__0_ for the ##CrossCorrelationTable#s. These tables " "are calculated at lag times %\\ta__k_=(%k - 1)%\\ta__0_, where %k runs from 1 to %%numberOfCrosscorrelations%.") TAG (L"##Maximum number of iterations") DEFINITION (L"defines a stopping criterion for the iteration. The iteration will stops when this number is reached.") TAG (L"##Tolerance") DEFINITION (L"defines another stopping criterion that depends on the method used.") TAG (L"##Diagonalization method") DEFINITION (L"defines the method to determine the independent components.") ENTRY (L"Algorithm") NORMAL (L"This method tries to decompose the sound according to the %%instantaneous% mixing model") FORMULA (L"#Y=#A\\.c#X.") NORMAL (L"In this model #Y is a matrix with the selected multi-channel sound, #A is a so-called " "%%mixing matrix% and #X is a matrix with the independent components. " "Essentially the model says that each channel in the multi-channel sound is a linear combination of the " "independent sound components in #X. " "If we would know the mixing matrix #A we could easily solve the model above for #X by standard means. " "However, if we don't know #A and we don't know #X, the decomposition of #Y is underdetermined as there " "are an infinite number of possibilities. ") NORMAL (L"One approach to solve the equation above is to make assumptions about the statistical properties " "of the components in the matrix #X: it turns out that a sufficient assumption is to assume that the " "components in #X at each time instant are %%statistically independent%. This is not an unrealistic " "assumption in many cases, although in practice it need not be exactly the case. Another assumption is " "that the mixing matrix is constant." ) NORMAL (L"The theory says that statistically independent signals are not correlated (although the reverse " "is not always true: signals that are not correlated don't have to be statistically independent). " "The methods implemented here all follow this lead as follows. If we calculate the @@CrossCorrelationTable@ " "for the left and the right side signals of the equation above, then, " "for the multi-channel sound #Y this will result in a cross-correlation matrix #C. For the right side we " "obtain #A\\.c#D\\.c#A\\'p, where #D is a diagonal matrix because all the cross-correlations between " "different independent components are zero by definition. This results in the following identity: ") FORMULA (L"#C(\\ta)=#A\\.c#D(\\ta)\\.c#A\\'p, for all values of the lag time \\ta.") NORMAL (L"This equation says that, given the model, the cross-correlation matrix can be diagonalized for " "all values of the lag time %%by the same transformation matrix% #A.") NORMAL (L"If we calculate the cross-correlation matrices for a number of different lag times, say 20, we " "then have to obtain the matrix #A that diagonalizes them all. Unfortunately there is no closed form solution " "that diagonalizes more than two matrices at the same time and we have to resort to iterative " "algorithms for joint diagonalization. ") NORMAL (L"Two of these algorithms are the ##qdiag# method as described in @@Vollgraf & Obermayer (2006)@ " "and the ##ffdiag# method as described in @@Ziehe et al. (2004)@. ") NORMAL (L"Unfortunately the convergence criteria of these two algorithms cannot easily be compared as " "the criterion for the ##ffdiag# algorithm is the relative change of the square root of the sum of the " "squared off-diagonal " "elements of the transformed cross-correlation matrices and the criterion for ##qdiag# is the largest " "change in the eigenvectors norm during an iteration.") ENTRY (L"Example") NORMAL (L"We start by creating a speech synthesizer that need to create two sounds. We will mix the two sounds and finally our blind source separation software will try to undo our mixing by extracting the two original sounds as well as possible from the two mixtures.") CODE(L"synth = Create SpeechSynthesizer... English default") CODE(L"s1 = To Sound... \"This is some text\" no") NORMAL (L"The first speech sound was created from the text \"This is some text\" at a speed of 175 words per minute.") CODE(L"select synth") CODE(L"Set speech output settings... 44100 0.01 80 50 145 n IPA") CODE(L"s2 = To Sound... \"Abracadabra, abra\" 0.01 80 50 145 yes no no yes") NORMAL (L"The second sound \"Abracadabra, abra\" was synthesized at 145 words per minute with a somewhat larger pitch excursion (80) than the previous sound (50).") CODE(L"plus s1") CODE(L"stereo = Combine to stereo") NORMAL (L"We combine the two separate sounds into one stereo sound because our blind source separation works on multichannel sounds only.") CODE(L"mm = Create simple MixingMatrix... mm 2 2 1.0 2.0 2.0 1.0") NORMAL (L"A two by two MixingMatrix is created.") CODE(L"plus stereo") CODE(L"Mix") NORMAL (L"The last command, Mix, creates a new two-channel sound where each channel is a linear mixture of the two " "channels in the stereo sound, i.e. channel 1 is the sum of s1 and s2 with mixture strengths of 1 and 2, respectively. " "The second channel is also the sum of s1 and s2 but now with mixture strengths 2 and 1, respectively.") CODE (L"To Sound (blind source separation)... 0.1 1 20 0.0002 100 0.001 ffdiag") NORMAL (L"The two channels in the new sound that results from this command contain a reasonable approximation of " "the two originating sounds.") NORMAL (L"In the top panel the two speech sounds \"This is some text\" and \"abracadabra, abra\". " "The middle panel shows the two mixed sounds while the lower panel shows the two sounds after unmixing.") SCRIPT (6, 6, L" " "syn = Create SpeechSynthesizer... English default\n" "s1 = To Sound... \"This is some text\" no\n" "select syn\n" "Set speech output settings... 44100 0.01 80 50 145 n IPA\n" "s2 =To Sound... \"abracadabra, abra\" no\n" "plus s1\n" "stereo = Combine to stereo\n" "Select inner viewport... 1 6 0.1 1.9\n" "Draw... 0 0 0 0 n Curve\n" "Draw inner box\n" "mm = Create simple MixingMatrix... mm 2 2 1.0 2.0 2.0 1.0\n" "plus stereo\n" "mixed = Mix\n" "Select inner viewport... 1 6 2.1 3.9\n" "Draw... 0 0 0 0 n Curve\n" "Draw inner box\n" "unmixed = To Sound (blind source separation)... 0.1 1 20 0.00021 100 0.001 ffdiag\n" "Select inner viewport... 1 6 4.1 5.9\n" "Draw... 0 0 0 0 n Curve\n" "Draw inner box\n" "plus syn\n" "plus stereo\n" "plus s1\n" "plus s2\n" "plus mixed\n" "plus mm\n" "Remove\n" ) NORMAL (L"The first two panels will not change between different sessions of praat. The last panel, which shows " "the result of the blind source separation, i.e. unmixing, will not always be the same because of two things. In the first place the unmixing always starts with an initialisation with random values of the parameters that " "we have to determine for the blind source separation. Therefore the iteration sequence will never be the same and the final outcomes might differ. In the second place, as was explained in the @@blind source separation@ manual, the unmixing is only " "unique up to a scale factor and a permutation. Therefore the channels in the unmixed sound do not necessarily correspond to the corresponding channel in our \"original\" stereo sound.") MAN_END MAN_BEGIN (L"Sound: To Sound (whiten channels)...", L"djmw", 20120303) INTRO (L"Transforms the channels of the selected @Sound linearly to make them white, i.e. the new channels will be uncorrelated and their variances equal unity.") ENTRY (L"Settings") TAG (L"##Variance fraction to keep#,") DEFINITION (L"determines, indirectly, how many channels the final sound will have.") ENTRY (L"Algorithm") NORMAL (L"We start by determining the @@Sound: To Covariance (channels)...|covariance@ of the selected sound. " "Next a @@Principal component analysis|principal component analysis@ determines the eigenvalues and eigenvectors of the covariance matrix. The settings of the variance fraction to keep determines how many eigenvalues and eigenvectors we use for the whitening. This number, %p, will also be equal to the number of channels of the resulting whitened sound.") NORMAL (L"In mathematical terms. For an %n-channel sound, if #E is the matrix with the eigenvectors and #D=diag (%d__1_, %d__2_,..., %d__n_) is the diagonal matrix with the " "eigenvalues of the covariance matrix, then the whitening matrix is #W = #E#D^^-1/2^#E\\'p, where #D^^-1/2^=diag (%d__1_^^-1/2^, ..., %d__p_^^-1/2^, 0, ..., 0). Only the %p most important eigenvalues have been retained, where %p was determined as the smallest integer for which (%d__1_+%d__2_+...%d__%p_)/(%d__1_+%d__2_+ ... + %d__%n_) >= %%varianceFractionToKeep%.") NORMAL (L"The resulting sound samples of the whitened sound, %w__%ij_, are then calculated from the samples of the " "original sound, %s__%kj_, as %w__%ij_ = \\Si__%k_ W__%ik_ %s__%kj_, where 1 \\<_ %i \\<_%p, 1 \\<_ %j \\<_ numberOfSamples and 1 \\<_ %k \\<_ %n.") MAN_END MAN_BEGIN (L"blind source separation", L"djmw", 20120223) INTRO (L"Blind source separation (BSS) is a technique for estimating individual source components from their mixtures " "at multiple sensors. It is called %blind because we don't use any other information besides the mixtures. ") NORMAL (L"For example, imagine a room with a number of persons present and a number of microphones for recording. " "When one or more persons are speaking at the same time, each microphone registers a different %mixture of individual speaker's audio signals. It is the task of BSS to untangle these mixtures into their sources, i.e. the individual speaker's audio signals. " "In general, this is a difficult problem because of several complicating factors. ") LIST_ITEM (L"\\bu Different locations of speakers and microphones in the room: the individual speaker's audio signals do not reach all microphones at the same time. ") LIST_ITEM (L"\\bu Room acoustics: the signal that reaches a microphone is composed of the signal that %directly travels to the microphone and parts that come from room reverberations and echos. ") LIST_ITEM (L"\\bu Varying distances to microphones: one ore more speakers might be moving. This makes the mixing time dependent.") NORMAL (L"If the number of sources is %larger than the number of sensors we speak of an %overdetermined problem. If the number of sensors and the number of sources are %equal we speak of a %determined problem. The more difficult problem is the %underdetermined one where the number of sensors is %less than the number of sources. ") ENTRY (L"Typology of mixtures") NORMAL (L"In general two different types of mixtures are considered in the literature: %%instantaneous " "mixtures% and %%convolutive mixtures%. ") TAG (L"%%Instantaneous mixtures%") DEFINITION (L"where the mixing is instantaneous, corresponds to the model #Y=#A\\.c#X. In this model #Y is a matrix with the recorded microphone sounds, #A is a so-called " "%%mixing matrix% and #X is a matrix with the independent source signals. " "Essentially the model says that the signal that each microphone records is a (possibly different) linear combination of the %same source signals. " "If we would know the mixing matrix #A we could easily solve the model above for #X by standard means. " "However, in general we don't know #A and #X and there are an infinite number of possible decompositions for #Y. The problem is however solvable by making some (mild) assumptions about #A and #X. ") TAG (L"%%Convolutive mixtures%") DEFINITION (L"are mixtures where the mixing is of convolutive nature, i.e. the model is ") FORMULA (L"%%y__i_ (n)% = \\Si__%j_^^%d^\\Si__%\\ta_^^M__%ij_-1^ %%h__ij_(\\ta)x__j_(n-\\ta) + N__i_(n)%, for %i=1..m.") DEFINITION (L"Here %%y__i_ (n) is the %n-th sample of the %i-th microphone signal, %m is the number of microphones, %%h__ij_(\\ta)% is the multi-input multi-output linear filter with the source-microphone impulse responses that characterize the propagation of the sound in the room and %%N__i_% is a noise source. This model is typically much harder to solve than the previous one because of the %%h__ij_(\\ta)% filter term that can have thousands of coefficients. For example, the typical @@reverberation time@ of a room is approximately 0.3 s which corresponds to 2400 samples, i.e. filter coefficients, for an 8 kHz sampled sound.") ENTRY (L"Solving the blind source separation for instantaneous mixtures") NORMAL (L"Various techniques exist for solving the blind source separation problem for %instantaneous mixtures. Very popular ones make make use of second order statistics (SOS) by trying to " "simultaneously diagonalize a large number of cross-correlation matrices. Other techniques like independent component analysis use higher order statistics (HOS) to find the independent components, i.e. the sources.") NORMAL (L"Given the decomposition problem #Y=#A\\.c#X, we can see that the solution is determined " "only upto a permutation and a scaling of the components. This is called the %%indeterminancy " "problem% of BSS. This can be seen as follows: given a permutation matrix #P, i.e. a matrix which " "contains only zeros except for one 1 in every row and column, and a diagonal scaling matrix #D, any " "scaling and permutation of the independent components #X__%n_=(#D\\.c#P)\\.c#X can be compensated " "by the reversed scaling of the mixing matrix #A__%n_=#A\\.c(#D\\.c#P)^^-1^ because #A\\.c(#D\\.c#P)^^-1^\\.c(#D\\.c#P)\\.c#X = #A\\.c#X = #Y. ") ENTRY (L"Solving the blind source separation for convolutive mixtures") NORMAL (L"Solutions for %convolutive mixture problems are much harder to achieve. " "One normally starts by transforming the problem to the frequency domain where the " "convolution is turned into a multiplication. The problem then translates into a separate " "%%instantaneous% mixing problem for %%each% frequency in the frequency domain. It is here that " "the indeterminacy problem hits us because it is not clear beforehand how to combine the " "independent components of each frequency bin.") MAN_END MAN_BEGIN (L"reverberation time", L"djmw", 20110107) NORMAL (L"Reverberation is the persistence of sound in a room after the sound source has silenced. ") NORMAL (L"The %%reverberation time% is normally defined as the time required for the persistence of a direct sound " "to decay by 60 dB after the direct sound has silenced. Sometimes this dB level is indicated with a subscript " "and the reverberation time is given by the symbol %T__60_. " "The reverberation time depends mainly on a room's volume and area and on the absorption at the walls. Generally absorption is frequency dependent and therefore the reverberation time of a room varies with frequency. ") MAN_END MAN_BEGIN (L"Vollgraf & Obermayer (2006)", L"djmw", 20110105) NORMAL (L"Roland Vollgraf & Klaus Obermayer (2006): \"Quadratic optimization for simultaneous matrix " "diagonalization.\" %%IEEE Transactions On Signal Processing% #54: 3270\\--3278.") MAN_END MAN_BEGIN (L"Ziehe et al. (2004)", L"djmw", 20110105) NORMAL (L"Andreas Ziehe, Pavel Laskov, Guido Nolte & Klaus-Robert M\\u\"ller (2004): \"A fast algorithm for joint " "diagonalization with non-orthogonal transformations and its application to blind source separation\", " "%%Journal of Machine Learning Research% #5: 777\\--800.") MAN_END } /* End of file manual_BSS.cpp */ sources_5316/dwtools/Polynomial.cpp0000644000176700017670000015162311725102305016251 0ustar paulpaul/* Polynomial.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20030619 Added SVD_compute before SVD_solve djmw 20060510 Polynomial_to_Roots: changed behaviour. All roots found are now saved. In previous version a NULL pointer was returned. New error messages. djmw 20061021 printf expects %ld for 'long int' djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20071201 Melder_warning djmw 20080122 float -> double djmw 20110304 Thing_new */ #include "Polynomial.h" #include "SVD.h" #include "NUMclapack.h" #include "TableOfReal_extensions.h" #include "NUMmachar.h" #include "oo_DESTROY.h" #include "Polynomial_def.h" #include "oo_COPY.h" #include "Polynomial_def.h" #include "oo_EQUAL.h" #include "Polynomial_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Polynomial_def.h" #include "oo_WRITE_TEXT.h" #include "Polynomial_def.h" #include "oo_WRITE_BINARY.h" #include "Polynomial_def.h" #include "oo_READ_TEXT.h" #include "Polynomial_def.h" #include "oo_READ_BINARY.h" #include "Polynomial_def.h" #include "oo_DESCRIPTION.h" #include "Polynomial_def.h" #undef our #define our ((Polynomial_Table) my methods) -> #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) /* Evaluate polynomial and derivative jointly c[1..n] -> degree n-1 !! */ static void Polynomial_evaluate2 (I, double x, double *f, double *df) { iam (Polynomial); long double p = my coefficients[my numberOfCoefficients], dp = 0, xc = x; for (long i = my numberOfCoefficients - 1; i > 0; i--) { dp = dp * xc + p; p = p * xc + my coefficients[i]; } *f = p; *df = dp; } /* Get value and derivative */ static void Polynomial_evaluate2_z (I, dcomplex *z, dcomplex *p, dcomplex *dp) { iam (Polynomial); long double pr = my coefficients[my numberOfCoefficients], pi = 0; long double dpr = 0, dpi = 0, x = z -> re, y = z -> im; for (long i = my numberOfCoefficients - 1; i > 0; i--) { long double tr = dpr; dpr = dpr * x - dpi * y + pr; dpi = tr * y + dpi * x + pi; tr = pr; pr = pr * x - pi * y + my coefficients[i]; pi = tr * y + pi * x; } p -> re = pr; p -> im = pi; dp -> re = dpr; dp -> im = dpi; } /* void polynomial_divide (double *u, long m, double *v, long n, double *q, double *r); Purpose: Find the quotient q(x) and the remainder r(x) polynomials that result from the division of the polynomial u(x) = u[1] + u[2]*x^1 + u[3]*x^2 + ... + u[m]*x^(m-1) by the polynomial v(x) = v[1] + v[2]*x^1 + v[3]*x^2 + ... + v[n]*x^(n-1), such that u(x) = v(x)*q(x) + r(x). The arrays u, v, q and r have to be dimensioned as u[1...m], v[1..n], q[1...m] and r[1...m], respectively. On return, the q[1..m-n] and r[1..n-1] contain the quotient and the remainder polynomial coefficients, repectively. See Knuth, The Art of Computer Programming, Volume 2: Seminumerical algorithms, Third edition, Section 4.6.1 Algorithm D (the algorithm as described has been modified to prevent overwriting of the u-polynomial). */ static void polynomial_divide (double *u, long m, double *v, long n, double *q, double *r) { // Copy u[1..m] into r[1..n] to prevent overwriting of u. // Put the q coefficients to zero for cases n > m. for (long k = 1; k <= m; k++) { r[k] = u[k]; q[k] = 0; } for (long k = m - n + 1; k > 0; k--) { /* D1 */ q[k] = r[n + k - 1] / v[n]; /* D2 with u -> r*/ for (long j = n + k - 1; j >= k; j--) { r[j] -= q[k] * v[j - k + 1]; } } } static void Polynomial_polish_realroot (I, double *x, long maxit) { iam (Polynomial); double xbest = *x, pmin = 1e38; if (! NUMfpp) { NUMmachar (); } for (long i = 1; i <= maxit; i++) { double p, dp; Polynomial_evaluate2 (me, *x, &p, &dp); double fabsp = fabs (p); if (fabsp > pmin || fabs (fabsp - pmin) < NUMfpp -> eps) { // We stop because the approximation gets worse or we cannot get closer anymore // Return previous (best) value for x. *x = xbest; return; } pmin = fabsp; xbest = *x; if (fabs (dp) == 0) { return; } double dx = p / dp; /* Newton -Raphson */ *x -= dx; } // Melder_throw ("Maximum number of iterations exceeded."); } static void Polynomial_polish_complexroot_nr (I, dcomplex *z, long maxit) { iam (Polynomial); dcomplex zbest = *z; double pmin = 1e38; if (! NUMfpp) { NUMmachar (); } for (long i = 1; i <= maxit; i++) { dcomplex p, dp; Polynomial_evaluate2_z (me, z, &p, &dp); double fabsp = dcomplex_abs (p); if (fabsp > pmin || fabs (fabsp - pmin) < NUMfpp -> eps) { // We stop because the approximation gets worse. // Return previous (best) value for z. *z = zbest; return; } pmin = fabsp; zbest = *z; if (dcomplex_abs (dp) == 0) { return; } dcomplex dz = dcomplex_div (p , dp); /* Newton -Raphson */ *z = dcomplex_sub (*z, dz); } // Melder_throw ("Maximum number of iterations exceeded."); } /* Symbolic evaluation of polynomial coefficients. Recurrence: P[n] = (a[n] * x + b[n]) P[n-1] + c[n] P[n-2], where P[n] is any orthogonal polynomial of degree n. P[n] is an array of coefficients p[k] representing: p[1] + p[2] x + ... p[n+1] x^n. Preconditions: degree > 1; pnm1 : polynomial of degree n - 1 pnm2 : polynomial of degree n - 2 */ static void NUMpolynomial_recurrence (double *pn, long degree, double a, double b, double c, double *pnm1, double *pnm2) { Melder_assert (degree > 1); pn[1] = b * pnm1[1] + c * pnm2[1]; for (long i = 2; i <= degree - 1; i++) { pn[i] = a * pnm1[i - 1] + b * pnm1[i] + c * pnm2[i]; } pn[degree] = a * pnm1[degree - 1] + b * pnm1[degree]; pn[degree + 1] = a * pnm1[degree]; } /* frozen[1..ma] */ static void svdcvm (double **v, long mfit, long ma, int *frozen, double *w, double **cvm) { autoNUMvector wti (1, mfit); for (long i = 1; i <= mfit; i++) { if (w[i]) { wti[i] = 1.0 / (w[i] * w[i]); } } for (long i = 1; i <= mfit; i++) { for (long j = 1; j <= i; j++) { double sum = 0; for (long k = 1; k <= mfit; k++) { sum += v[i][k] * v[j][k] * wti[k]; } cvm[j][i] = cvm[i][j] = sum; } } for (long i = mfit + 1; i <= ma; i++) { for (long j = 1; j <= i; j++) { cvm[j][i] = cvm[i][j] = 0; } } long k = mfit; for (long j = ma; j > 0; j--) { // if (! frozen || ! frozen[i]) why i?? TODO if (! frozen || ! frozen[j]) { for (long i = 1; i <= ma; i++) { double t = cvm[i][k]; cvm[i][k] = cvm[i][j]; cvm[i][j] = t; } for (long i = 1; i <= ma; i++) { double t = cvm[k][i]; cvm[k][i] = cvm[j][i]; cvm[j][i] = t; } k--; } } } /********* FunctionTerms *********************************************/ Thing_implement (FunctionTerms, Function, 0); double structFunctionTerms :: v_evaluate (double x) { (void) x; return NUMundefined; } void structFunctionTerms :: v_evaluate_z (dcomplex *z, dcomplex *p) { (void) z; p -> re = p -> im = NUMundefined; } void structFunctionTerms :: v_evaluateTerms (double x, double terms[]) { (void) x; for (long i = 1; i <= numberOfCoefficients; i++) { terms[i] = NUMundefined; } } long structFunctionTerms :: v_getDegree () { return numberOfCoefficients - 1; } void structFunctionTerms :: v_getExtrema (double x1, double x2, double *lxmin, double *ymin, double *lxmax, double *ymax) { // David, geen aparte naam hier nodig: ??? long numberOfPoints = 1000; // Melder_warning (L"defaultGetExtrema: extrema calculated by sampling the interval"); double x = x1, dx = (x2 - x1) / (numberOfPoints - 1); *lxmin = *lxmax = x; *ymin = *ymax = v_evaluate (x); for (long i = 2; i <= numberOfPoints; i++) { x += dx; double y = v_evaluate (x); if (y > *ymax) { *ymax = y; *lxmax = x; } else if (y < *ymin) { *ymin = y; *lxmin = x; } } } void FunctionTerms_init (I, double xmin, double xmax, long numberOfCoefficients) { iam (FunctionTerms); my coefficients = NUMvector (1, numberOfCoefficients); my numberOfCoefficients = numberOfCoefficients; my xmin = xmin; my xmax = xmax; } FunctionTerms FunctionTerms_create (double xmin, double xmax, long numberOfCoefficients) { try { autoFunctionTerms me = Thing_new (FunctionTerms); FunctionTerms_init (me.peek(), xmin, xmax, numberOfCoefficients); return me.transfer(); } catch (MelderError) { Melder_throw ("FunctionTerms not created."); } } void FunctionTerms_initFromString (I, double xmin, double xmax, const wchar_t *s, int allowTrailingZeros) { iam (FunctionTerms); long numberOfCoefficients; autoNUMvector numbers (NUMstring_to_numbers (s, &numberOfCoefficients), 1); if (! allowTrailingZeros) { while (numbers[numberOfCoefficients] == 0 && numberOfCoefficients > 1) { numberOfCoefficients--; } } FunctionTerms_init (me, xmin, xmax, numberOfCoefficients); NUMvector_copyElements (numbers.peek(), my coefficients, 1, numberOfCoefficients); } long FunctionTerms_getDegree (I) { iam (FunctionTerms); return my v_getDegree (); } void FunctionTerms_setDomain (I, double xmin, double xmax) { iam (FunctionTerms); my xmin = xmin; my xmax = xmax; } double FunctionTerms_evaluate (I, double x) { iam (FunctionTerms); return my v_evaluate (x); } void FunctionTerms_evaluate_z (I, dcomplex *z, dcomplex *p) { iam (FunctionTerms); my v_evaluate_z (z, p); } void FunctionTerms_evaluateTerms (I, double x, double terms[]) { iam (FunctionTerms); my v_evaluateTerms (x, terms); } void FunctionTerms_getExtrema (I, double x1, double x2, double *xmin, double *ymin, double *xmax, double *ymax) { iam (FunctionTerms); if (x2 <= x1) { x1 = my xmin; x2 = my xmax; } my v_getExtrema (x1, x2, xmin, ymin, xmax, ymax); } double FunctionTerms_getMinimum (I, double x1, double x2) { iam (FunctionTerms); double xmin, xmax, ymin, ymax; FunctionTerms_getExtrema (me, x1, x2, &xmin, &ymin, &xmax, &ymax); return ymin; } double FunctionTerms_getXOfMinimum (I, double x1, double x2) { iam (FunctionTerms); double xmin, xmax, ymin, ymax; FunctionTerms_getExtrema (me, x1, x2, &xmin, &ymin, &xmax, &ymax); return xmin; } double FunctionTerms_getMaximum (I, double x1, double x2) { iam (FunctionTerms); double xmin, xmax, ymin, ymax; FunctionTerms_getExtrema (me, x1, x2, &xmin, &ymin, &xmax, &ymax); return ymax; } double FunctionTerms_getXOfMaximum (I, double x1, double x2) { iam (FunctionTerms); double xmin, xmax, ymin, ymax; FunctionTerms_getExtrema (me, x1, x2, &xmin, &ymin, &xmax, &ymax); return xmax; } static void Graphics_polyline_clipTopBottom (Graphics g, double *x, double *y, long numberOfPoints, double ymin, double ymax) { long index = 0; if (numberOfPoints < 2) { return; } double x1 = x[0], y1 = y[0]; double xb = x1, yb = y1; for (long i = 1; i < numberOfPoints; i++) { double x2 = x[i], y2 = y[i]; if (! ( (y1 > ymax && y2 > ymax) || (y1 < ymin && y2 < ymin))) { double dxy = (x2 - x1) / (y1 - y2); double xcros_max = x1 - (ymax - y1) * dxy; double xcros_min = x1 - (ymin - y1) * dxy; if (y1 > ymax && y2 < ymax) { // Line enters from above: start new segment. Save start values. xb = x[i - 1]; yb = y[i - 1]; index = i - 1; y[i - 1] = ymax; x[i - 1] = xcros_max; } if (y1 > ymin && y2 < ymin) { // Line leaves at bottom: draw segment. Save end values and restore them // Origin of arrays for Graphics_polyline are at element 0 !!! double xe = x[i], ye = y[i]; y[i] = ymin; x[i] = xcros_min; Graphics_polyline (g, i - index + 1, x + index, y + index); x[index] = xb; y[index] = yb; x[i] = xe; y[i] = ye; } if (y1 < ymin && y2 > ymin) { // Line enters from below: start new segment. Save start values xb = x[i - 1]; yb = y[i - 1]; index = i - 1; // David, dit klopt toch niet? xb is tweemaal gedefinieerd, en hier verdwijnt een toekenning; Klopt, nu niet meer (was overigens geen probleem vanwege nieuwe toekenning!) y[i - 1] = ymin; x[i - 1] = xcros_min; } if (y1 < ymax && y2 > ymax) { // Line leaves at top: draw segment. Save and restore double xe = x[i], ye = y[i]; y[i] = ymax; x[i] = xcros_max; Graphics_polyline (g, i - index + 1, x + index, y + index); x[index] = xb; y[index] = yb; x[i] = xe; y[i] = ye; } } else { index = i; } y1 = y2; x1 = x2; } if (index < numberOfPoints - 1) { Graphics_polyline (g, numberOfPoints - index, x + index, y + index); x[index] = xb; y[index] = yb; } } void FunctionTerms_draw (I, Graphics g, double xmin, double xmax, double ymin, double ymax, int extrapolate, int garnish) { iam (FunctionTerms); long numberOfPoints = 1000; autoNUMvector y (1, numberOfPoints + 1); autoNUMvector x (1, numberOfPoints + 1); if (xmax <= xmin) { xmin = my xmin; xmax = my xmax; } double fxmin = xmin, fxmax = xmax; if (! extrapolate) { if (xmax < my xmin || xmin > my xmax) { return; } if (xmin < my xmin) { fxmin = my xmin; } if (xmax > my xmax) { fxmax = my xmax; } } if (ymax <= ymin) { double x1, x2; FunctionTerms_getExtrema (me, fxmin, fxmax, &x1, &ymin, &x2, &ymax); } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); // Draw only the parts within [fxmin, fxmax] X [ymin, ymax]. double dx = (fxmax - fxmin) / (numberOfPoints - 1); for (long i = 1; i <= numberOfPoints; i++) { x[i] = fxmin + (i - 1.0) * dx; y[i] = FunctionTerms_evaluate (me, x[i]); } //Graphics_polyline_clipTopBottom (g, x+1, y+1, numberOfPoints, ymin, ymax); Graphics_polyline_clipTopBottom (g, &x[1], &y[1], numberOfPoints, ymin, ymax); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } void FunctionTerms_drawBasisFunction (I, Graphics g, long index, double xmin, double xmax, double ymin, double ymax, int extrapolate, int garnish) { iam (FunctionTerms); if (index < 1 || index > my numberOfCoefficients) { return; } autoFunctionTerms thee = (FunctionTerms) Data_copy (me); for (long i = 1; i <= my numberOfCoefficients; i++) { thy coefficients[i] = 0; } thy coefficients[index] = 1; thy numberOfCoefficients = index; FunctionTerms_draw (thee.peek(), g, xmin, xmax, ymin, ymax, extrapolate, garnish); } void FunctionTerms_setCoefficient (I, long index, double value) { iam (FunctionTerms); if (index < 1 || index > my numberOfCoefficients) { Melder_throw (L"Idex out of range [1, ", my numberOfCoefficients, L"]."); } if (index == my numberOfCoefficients && value == 0) { Melder_throw (L"You cannot remove the highest degree term."); } my coefficients[index] = value; } /********** Polynomial ***********************************************/ Thing_implement (Polynomial, FunctionTerms, 0); double structPolynomial :: v_evaluate (double x) { long double p = coefficients [numberOfCoefficients]; for (long i = numberOfCoefficients - 1; i > 0; i--) { p = p * x + coefficients [i]; } return p; } void structPolynomial :: v_evaluate_z (dcomplex *z, dcomplex *p) { long double x = z -> re, y = z -> im; long double pr = coefficients [numberOfCoefficients]; long double pi = 0; for (long i = numberOfCoefficients - 1; i > 0; i--) { long double p_r = pr; pr = pr * x - pi * y + coefficients[i]; pi = p_r * y + pi * x; } p -> re = pr; p -> im = pi; } void structPolynomial :: v_evaluateTerms (double x, double terms[]) { terms[1] = 1; for (long i = 2; i <= numberOfCoefficients; i++) { terms[i] = terms[i - 1] * x; } } void structPolynomial :: v_getExtrema (double x1, double x2, double *lxmin, double *ymin, double *lxmax, double *ymax) { try { long degree = numberOfCoefficients - 1; *lxmin = x1; *ymin = v_evaluate (x1); *lxmax = x2; *ymax = v_evaluate (x2); if (*ymin > *ymax) { /* Swap */ double t = *ymin; *ymin = *ymax; *ymax = t; t = *lxmin; *lxmin = *lxmax; *lxmax = t; } if (degree < 2) { return; } autoPolynomial d = Polynomial_getDerivative (this); autoRoots r = Polynomial_to_Roots (d.peek()); for (long i = 1; i <= degree - 1; i++) { double x = (r -> v[i]).re; if (x > x1 && x < x2) { double y = v_evaluate (x); if (y > *ymax) { *ymax = y; *lxmax = x; } else if (y < *ymin) { *ymin = y; *lxmin = x; } } } } catch (MelderError) { structFunctionTerms :: v_getExtrema (x1, x2, lxmin, ymin, lxmax, ymax); Melder_clearError (); } } Polynomial Polynomial_create (double lxmin, double lxmax, long degree) { try { autoPolynomial me = Thing_new (Polynomial); FunctionTerms_init (me.peek(), lxmin, lxmax, degree + 1); return me.transfer(); } catch (MelderError) { Melder_throw ("Polynomial not created."); } } Polynomial Polynomial_createFromString (double lxmin, double lxmax, const wchar_t *s) { try { autoPolynomial me = Thing_new (Polynomial); FunctionTerms_initFromString (me.peek(), lxmin, lxmax, s, 0); return me.transfer(); } catch (MelderError) { Melder_throw ("Polynomial not created from string."); } } void Polynomial_scaleCoefficients_monic (Polynomial me) { double cn = my coefficients[my numberOfCoefficients]; if (cn == 1 || my numberOfCoefficients <= 1) { return; } for (long i = 1; i < my numberOfCoefficients; i++) { my coefficients[i] /= cn; } my coefficients[my numberOfCoefficients] = 1; } /* Transform the polynomial as if the domain were [xmin, xmax]. Some polynomials (Legendre) are defined on the domain [-1,1]. The domain for x may be extended to [xmin, xmax] by a transformation such as x' = (2 * x - (xmin + xmax)) / (xmax - xmin) -1 < x' < x. This procedure transforms x' back to x. */ Polynomial Polynomial_scaleX (Polynomial me, double xmin, double xmax) { try { Melder_assert (xmin < xmax); autoPolynomial thee = Polynomial_create (xmin, xmax, my numberOfCoefficients - 1); thy coefficients[1] = my coefficients[1]; if (my numberOfCoefficients == 1) { return thee.transfer(); } // x = a x + b // Constraints: // my xmin = a xmin + b; a = (my xmin - my xmax) / (xmin - xmax); // my xmax = a xmax + b; b = my xmin - a * xmin double a = (my xmin - my xmax) / (xmin - xmax); double b = my xmin - a * xmin; thy coefficients[2] = my coefficients[2] * a; thy coefficients[1] += my coefficients[2] * b; if (my numberOfCoefficients == 2) { return thee.transfer(); } autoNUMvector buf (1, 3 * my numberOfCoefficients); double *pn = buf.peek(); double *pnm1 = pn + my numberOfCoefficients; double *pnm2 = pnm1 + my numberOfCoefficients; // Start the recursion: P[1] = a x + b; P[0] = 1; pnm1[2] = a; pnm1[1] = b; pnm2[1] = 1; for (long n = 2; n <= my numberOfCoefficients - 1; n++) { double *t1 = pnm1, *t2 = pnm2; NUMpolynomial_recurrence (pn, n, a, b, 0, pnm1, pnm2); if (my coefficients[n + 1] != 0) { for (long j = 1; j <= n + 1; j++) { thy coefficients[j] += my coefficients[n + 1] * pn[j]; } } pnm1 = pn; pnm2 = t1; pn = t2; } return thee.transfer(); } catch (MelderError) { Melder_throw (""); } } double Polynomial_evaluate (I, double x) { iam (Polynomial); return my v_evaluate (x); } void Polynomial_evaluate_z (Polynomial me, dcomplex *z, dcomplex *p) { my v_evaluate_z (z, p); } static void Polynomial_evaluate_z_cart (Polynomial me, double r, double phi, double *re, double *im) { double rn = 1; *re = my coefficients[1]; *im = 0; if (r == 0) { return; } for (long i = 2; i <= my numberOfCoefficients; i++) { rn *= r; double arg = (i - 1) * phi; *re += my coefficients[i] * rn * cos (arg); *im += my coefficients[i] * rn * sin (arg); } } Polynomial Polynomial_getDerivative (Polynomial me) { try { if (my numberOfCoefficients == 1) { return Polynomial_create (my xmin, my xmax, 0); } autoPolynomial thee = Polynomial_create (my xmin, my xmax, my numberOfCoefficients - 2); for (long i = 1; i <= thy numberOfCoefficients; i++) { thy coefficients[i] = i * my coefficients[i + 1]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no derivative created."); } } Polynomial Polynomial_getPrimitive (Polynomial me) { try { autoPolynomial thee = Polynomial_create (my xmin, my xmax, my numberOfCoefficients); for (long i = 1; i <= my numberOfCoefficients; i++) { thy coefficients[i + 1] = my coefficients[i] / i; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no primitive created."); } } double Polynomial_getArea (Polynomial me, double xmin, double xmax) { if (xmax >= xmin) { xmin = my xmin; xmax = my xmax; } autoPolynomial p = Polynomial_getPrimitive (me); double area = FunctionTerms_evaluate (p.peek(), xmax) - FunctionTerms_evaluate (p.peek(), xmin); return area; } Polynomial Polynomials_multiply (Polynomial me, Polynomial thee) { try { long n1 = my numberOfCoefficients, n2 = thy numberOfCoefficients; if (my xmax <= thy xmin || my xmin >= thy xmax) { Melder_throw ("Domains do not overlap."); } double xmin = my xmin > thy xmin ? my xmin : thy xmin; double xmax = my xmax < thy xmax ? my xmax : thy xmax; autoPolynomial him = Polynomial_create (xmin, xmax, n1 + n2 - 2); for (long i = 1; i <= n1; i++) { for (long j = 1; j <= n2; j++) { long k = i + j - 1; his coefficients [k] += my coefficients[i] * thy coefficients[j]; } } return him.transfer(); } catch (MelderError) { Melder_throw ("Polynomials not multiplied."); } } void Polynomials_divide (Polynomial me, Polynomial thee, Polynomial *q, Polynomial *r) { long degree, m = my numberOfCoefficients, n = thy numberOfCoefficients; if (*q == 0 && *r == 0) { return; } autoNUMvector qc (1, m); autoNUMvector rc (1, m); autoPolynomial aq = 0, ar = 0; polynomial_divide (my coefficients, m, thy coefficients, n, qc.peek(), rc.peek()); if (*q) { degree = MAX (m - n, 0); aq.reset (Polynomial_create (my xmin, my xmax, degree)); if (degree >= 0) { NUMvector_copyElements (qc.peek(), aq -> coefficients, 1, degree + 1); } } if (*r) { degree = n - 2; if (m >= n) { degree --; } if (degree < 0) { degree = 0; } while (degree > 1 && rc[degree] == 0) { degree--; } ar.reset (Polynomial_create (my xmin, my xmax, degree)); NUMvector_copyElements (rc.peek(), ar -> coefficients, 1, degree + 1); } *q = aq.transfer(); *r = ar.transfer(); } /******** LegendreSeries ********************************************/ Thing_implement (LegendreSeries, FunctionTerms, 0); double structLegendreSeries :: v_evaluate (double x) { double p = coefficients[1]; // Transform x from domain [xmin, xmax] to domain [-1, 1] if (x < xmin || x > xmax) { return NUMundefined; } double pim1 = x = (2 * x - xmin - xmax) / (xmax - xmin); if (numberOfCoefficients > 1) { double pim2 = 1, twox = 2 * x, f2 = x, d = 1.0; p += coefficients[2] * pim1; for (long i = 3; i <= numberOfCoefficients; i++) { double f1 = d++; f2 += twox; double pi = (f2 * pim1 - f1 * pim2) / d; p += coefficients[i] * pi; pim2 = pim1; pim1 = pi; } } return p; } void structLegendreSeries :: v_evaluateTerms (double x, double terms[]) { if (x < xmin || x > xmax) { for (long i = 1; i <= numberOfCoefficients; i++) { terms[i] = NUMundefined; } return; } // Transform x from domain [xmin, xmax] to domain [-1, 1] x = (2 * x - xmin - xmax) / (xmax - xmin); terms[1] = 1; if (numberOfCoefficients > 1) { double twox = 2 * x, f2 = x, d = 1.0; terms[2] = x; for (long i = 3; i <= numberOfCoefficients; i++) { double f1 = d++; f2 += twox; terms[i] = (f2 * terms[i - 1] - f1 * terms[i - 2]) / d; } } } void structLegendreSeries :: v_getExtrema (double x1, double x2, double *lxmin, double *ymin, double *lxmax, double *ymax) { try { autoPolynomial p = LegendreSeries_to_Polynomial (this); FunctionTerms_getExtrema (p.peek(), x1, x2, lxmin, ymin, lxmax, ymax); } catch (MelderError) { structFunctionTerms :: v_getExtrema (x1, x2, lxmin, ymin, lxmax, ymax); Melder_clearError (); } } LegendreSeries LegendreSeries_create (double xmin, double xmax, long numberOfPolynomials) { try { autoLegendreSeries me = Thing_new (LegendreSeries); FunctionTerms_init (me.peek(), xmin, xmax, numberOfPolynomials); return me.transfer(); } catch (MelderError) { Melder_throw ("LegendreSeries not created."); } } LegendreSeries LegendreSeries_createFromString (double xmin, double xmax, const wchar_t *s) { try { autoLegendreSeries me = Thing_new (LegendreSeries); FunctionTerms_initFromString (me.peek(), xmin, xmax, s, 0); return me.transfer(); } catch (MelderError) { Melder_throw ("LegendreSeries not created from string."); } } LegendreSeries LegendreSeries_getDerivative (LegendreSeries me) { try { autoLegendreSeries thee = LegendreSeries_create (my xmin, my xmax, my numberOfCoefficients - 1); for (long n = 1; n <= my numberOfCoefficients - 1; n++) { // P[n]'(x) = Sum (k=0..nonNegative, (2n - 4k - 1) P[n-2k-1](x)) long n2 = n - 1; for (long k = 0; n2 >= 0; k++, n2 -= 2) { thy coefficients [n2 + 1] += (2 * n - 4 * k - 1) * my coefficients[n + 1]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no derivative created."); } } Polynomial LegendreSeries_to_Polynomial (LegendreSeries me) { try { double xmin = -1, xmax = 1; autoPolynomial thee = Polynomial_create (xmin, xmax, my numberOfCoefficients - 1); thy coefficients[1] = my coefficients[1]; /* * p[1] */ if (my numberOfCoefficients == 1) { return thee.transfer(); } thy coefficients[2] = my coefficients[2]; /* * p[2] */ if (my numberOfCoefficients > 2) { autoNUMvector buf (1, 3 * my numberOfCoefficients); double *pn = buf.peek(); double *pnm1 = pn + my numberOfCoefficients; double *pnm2 = pnm1 + my numberOfCoefficients; // Start the recursion: P[1] = x; P[0] = 1; pnm1[2] = 1; pnm2[1] = 1; for (long n = 2; n <= my numberOfCoefficients - 1; n++) { double a = (2 * n - 1.0) / n; double c = - (n - 1.0) / n; double *t1 = pnm1, *t2 = pnm2; NUMpolynomial_recurrence (pn, n, a, 0, c, pnm1, pnm2); if (my coefficients[n + 1] != 0) { for (long j = 1; j <= n + 1; j++) { thy coefficients[j] += my coefficients[n + 1] * pn[j]; } } pnm1 = pn; pnm2 = t1; pn = t2; } } if (my xmin != xmin || my xmax != xmax) { thee.reset (Polynomial_scaleX (thee.peek(), my xmin, my xmax)); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Polynomial."); } } /********* Roots ****************************************************/ Thing_implement (Roots, ComplexVector, 0); Roots Roots_create (long numberOfRoots) { try { autoRoots me = Thing_new (Roots); ComplexVector_init (me.peek(), 1, numberOfRoots); return me.transfer(); } catch (MelderError) { Melder_throw ("Roots not created."); } } void Roots_fixIntoUnitCircle (Roots me) { dcomplex z10 = dcomplex_create (1, 0); for (long i = my min; i <= my max; i++) { if (dcomplex_abs (my v[i]) > 1.0) { my v[i] = dcomplex_div (z10, dcomplex_conjugate (my v[i])); } } } static void NUMdcvector_extrema_re (dcomplex v[], long lo, long hi, double *min, double *max) { *min = *max = v[lo].re; for (long i = lo + 1; i <= hi; i++) { if (v[i].re < *min) { *min = v[i].re; } else if (v[i].re > *max) { *max = v[i].re; } } } static void NUMdcvector_extrema_im (dcomplex v[], long lo, long hi, double *min, double *max) { *min = *max = v[lo].im; for (long i = lo + 1; i <= hi; i++) { if (v[i].im < *min) { *min = v[i].im; } else if (v[i].im > *max) { *max = v[i].im; } } } void Roots_draw (Roots me, Graphics g, double rmin, double rmax, double imin, double imax, const wchar_t *symbol, int fontSize, int garnish) { int oldFontSize = Graphics_inqFontSize (g); double eps = 1e-6; if (rmax <= rmin) { NUMdcvector_extrema_re (my v, 1, my max, &rmin, &rmax); } double denum = fabs (rmax) > fabs (rmin) ? fabs (rmax) : fabs (rmin); if (denum == 0) { denum = 1; } if (fabs ( (rmax - rmin) / denum) < eps) { rmin -= 1; rmax += 1; } if (imax <= imin) { NUMdcvector_extrema_im (my v, 1, my max, &imin, &imax); } denum = fabs (imax) > fabs (imin) ? fabs (imax) : fabs (imin); if (denum == 0) { denum = 1; } if (fabs ( (imax - imin) / denum) < eps) { imin -= 1; imax += 1; } Graphics_setInner (g); Graphics_setWindow (g, rmin, rmax, imin, imax); Graphics_setFontSize (g, fontSize); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (long i = 1; i <= my max; i++) { double re = my v[i].re, im = my v[i].im; if (re >= rmin && re <= rmax && im >= imin && im <= imax) { Graphics_text (g, re, im, symbol); } } Graphics_setFontSize (g, oldFontSize); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); if (rmin * rmax < 0) { Graphics_markLeft (g, 0, 1, 1, 1, L"0"); } if (imin * imax < 0) { Graphics_markBottom (g, 0, 1, 1, 1, L"0"); } Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_textLeft (g, 1, L"Imaginary part"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_textBottom (g, 1, L"Real part"); } } Roots Polynomial_to_Roots (Polynomial me) { try { long np1 = my numberOfCoefficients, n = np1 - 1, n2 = n * n; if (n < 1) { Melder_throw ("Cannot find roots of a constant function."); } // Allocate storage for Hessenberg matrix (n * n) plus real and imaginary // parts of eigenvalues wr[1..n] and wi[1..n]. autoNUMvector hes (1, n2 + n + n); double *wr = &hes[n2]; double *wi = &hes[n2 + n]; // Fill the upper Hessenberg matrix (storage is Fortran) // C: [i][j] -> Fortran: (j-1)*n + i for (long i = 1; i <= n; i++) { hes[ (i - 1) *n + 1] = - (my coefficients[np1 - i] / my coefficients[np1]); if (i < n) { hes[ (i - 1) *n + 1 + i] = 1; } } // Find out the working storage needed char job = 'E', compz = 'N'; long ilo = 1, ihi = n, ldh = n, ldz = n, lwork = -1, info; double *z = 0, wt[1]; NUMlapack_dhseqr (&job, &compz, &n, &ilo, &ihi, &hes[1], &ldh, &wr[1], &wi[1], z, &ldz, wt, &lwork, &info); if (info != 0) { if (info < 0) { Melder_throw (L"Programming error. Argument ", info, " in NUMlapack_dhseqr has illegal value."); } } lwork = wt[0]; autoNUMvector work (1, lwork); // Find eigenvalues. NUMlapack_dhseqr (&job, &compz, &n, &ilo, &ihi, &hes[1], &ldh, &wr[1], &wi[1], z, &ldz, &work[1], &lwork, &info); long nrootsfound = n; long ioffset = 0; if (info > 0) { // if INFO = i, NUMlapack_dhseqr failed to compute all of the eigenvalues. Elements i+1:n of // WR and WI contain those eigenvalues which have been successfully computed nrootsfound -= info; if (nrootsfound < 1) { Melder_throw ("No roots found."); } Melder_warning (L"Calculated only ", Melder_integer (nrootsfound), L" roots."); ioffset = info; } else if (info < 0) { Melder_throw (L"Programming error. Argument ", info, L" in NUMlapack_dhseqr has illegal value."); } autoRoots thee = Roots_create (nrootsfound); for (long i = 1; i <= nrootsfound; i++) { (thy v[i]).re = wr[ioffset + i]; (thy v[i]).im = wi[ioffset + i]; } Roots_and_Polynomial_polish (thee.peek(), me); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no roots can be calculated."); } } void Roots_sort (Roots me) { (void) me; } /* Precondition: complex roots occur in pairs (a,bi), (a,-bi) with b>0 */ void Roots_and_Polynomial_polish (Roots me, Polynomial thee) { long i = my min, maxit = 80; while (i <= my max) { double im = my v[i].im, re = my v[i].re; if (im != 0) { Polynomial_polish_complexroot_nr (thee, & my v[i], maxit); if (i < my max && im == -my v[i + 1].im && re == my v[i + 1].re) { my v[i + 1].re = my v[i].re; my v[i + 1].im = -my v[i].im; i++; } } else { Polynomial_polish_realroot (thee, & (my v[i].re), maxit); } i++; } } Polynomial Roots_to_Polynomial (Roots me) { try { (void) me; throw MelderError(); } catch (MelderError) { Melder_throw ("Not implemented yet"); } } void Roots_setRoot (Roots me, long index, double re, double im) { if (index < my min || index > my max) { Melder_throw ("Index must be in interval [1, ", my max, "]."); } my v[index].re = re; my v[index].im = im; } dcomplex Roots_evaluate_z (Roots me, dcomplex z) { dcomplex result = {1, 0}; for (long i = my min; i <= my max; i++) { dcomplex t = dcomplex_sub (z, my v[i]); result = dcomplex_mul (result, t); } return result; } Spectrum Roots_to_Spectrum (Roots me, double nyquistFrequency, long numberOfFrequencies, double radius) { try { if (numberOfFrequencies < 2) { Melder_throw ("NumberOfFrequencies must be greater or equal 2."); } autoSpectrum thee = Spectrum_create (nyquistFrequency, numberOfFrequencies); double phi = NUMpi / (numberOfFrequencies - 1); dcomplex z; for (long i = 1; i <= numberOfFrequencies; i++) { z.re = radius * cos ( (i - 1) * phi); z.im = radius * sin ( (i - 1) * phi); dcomplex s = Roots_evaluate_z (me, z); thy z[1][i] = s.re; thy z[2][i] = s.im; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Spectrum calculated."); } } long Roots_getNumberOfRoots (Roots me) { return my max; } dcomplex Roots_getRoot (Roots me, long index) { if (index < 1 || index > my max) { Melder_throw ("Root index out of range."); } return my v [index]; } /* Can be speeded up by doing a FFT */ Spectrum Polynomial_to_Spectrum (Polynomial me, double nyquistFrequency, long numberOfFrequencies, double radius) { try { if (numberOfFrequencies < 2) { Melder_throw (L"NumberOfFrequencies must be greater or equal 2."); } autoSpectrum thee = Spectrum_create (nyquistFrequency, numberOfFrequencies); double phi = NUMpi / (numberOfFrequencies - 1); for (long i = 1; i <= numberOfFrequencies; i++) { double re, im; Polynomial_evaluate_z_cart (me, radius, (i - 1) * phi, &re, &im); thy z[1][i] = re; thy z[2][i] = im; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Spectrum calculated."); } } /****** ChebyshevSeries ******************************************/ Thing_implement (ChebyshevSeries, FunctionTerms, 0); /* p(x) = sum (k=1..numberOfCoefficients, c[k]*T[k](x')) - c[1] / 2; Numerical evaluation via Clenshaw's recurrence equation (NRC: 5.8.11) d[m+1] = d[m] = 0; d[j] = 2 x' d[j+1] - d[j+2] + c[j]; p(x) = d[0] = x' d[1] - d[2] + c[0] / 2; x' = (2 * x - xmin - xmax) / (xmax - xmin) */ double structChebyshevSeries :: v_evaluate (double x) { if (x < xmin || x > xmax) { return NUMundefined; } double d1 = 0, d2 = 0; if (numberOfCoefficients > 1) { // Transform x from domain [xmin, xmax] to domain [-1, 1] x = (2 * x - xmin - xmax) / (xmax - xmin); double x2 = 2 * x; for (long i = numberOfCoefficients; i > 1; i--) { double tmp = d1; d1 = x2 * d1 - d2 + coefficients[i]; d2 = tmp; } } return x * d1 - d2 + coefficients[1]; } /* T[n](x) = 2*x*T[n-1] - T[n-2](x) n >= 2 */ void structChebyshevSeries :: v_evaluateTerms (double x, double *terms) { if (x < xmin || x > xmax) { for (long i = 1; i <= numberOfCoefficients; i++) { terms[i] = NUMundefined; } return; } terms[1] = 1; if (numberOfCoefficients > 1) { // Transform x from domain [xmin, xmax] to domain [-1, 1] terms[2] = x = (2 * x - xmin - xmax) / (xmax - xmin); for (long i = 3; i <= numberOfCoefficients; i++) { terms[i] = 2 * x * terms[i - 1] - terms[i - 2]; } } } void structChebyshevSeries :: v_getExtrema (double x1, double x2, double *lxmin, double *ymin, double *lxmax, double *ymax) { try { autoPolynomial p = ChebyshevSeries_to_Polynomial (this); FunctionTerms_getExtrema (p.peek(), x1, x2, lxmin, ymin, lxmax, ymax); } catch (MelderError) { Melder_throw (this, "Extrema cannot be calculated"); // David, dat is fout: er moet een Melder_throw of een Melder_clearError volgen: Klopt } } ChebyshevSeries ChebyshevSeries_create (double lxmin, double lxmax, long numberOfPolynomials) { try { autoChebyshevSeries me = Thing_new (ChebyshevSeries); FunctionTerms_init (me.peek(), lxmin, lxmax, numberOfPolynomials); return me.transfer(); } catch (MelderError) { Melder_throw ("ChebyshevSeries not created."); } } ChebyshevSeries ChebyshevSeries_createFromString (double lxmin, double lxmax, const wchar_t *s) { try { autoChebyshevSeries me = Thing_new (ChebyshevSeries); FunctionTerms_initFromString (me.peek(), lxmin, lxmax, s, 0); return me.transfer(); } catch (MelderError) { Melder_throw ("ChebyshevSeries not created from string."); }; } Polynomial ChebyshevSeries_to_Polynomial (ChebyshevSeries me) { try { double xmin = -1, xmax = 1; autoPolynomial thee = Polynomial_create (xmin, xmax, my numberOfCoefficients - 1); thy coefficients[1] = my coefficients[1] /* * p[1] */; if (my numberOfCoefficients == 1) { return thee.transfer(); } thy coefficients[2] = my coefficients[2]; if (my numberOfCoefficients > 2) { autoNUMvector buf (1, 3 * my numberOfCoefficients); double *pn = buf.peek(); double *pnm1 = pn + my numberOfCoefficients; double *pnm2 = pnm1 + my numberOfCoefficients; // Start the recursion: T[1] = x; T[0] = 1; pnm1[2] = 1; pnm2[1] = 1; double a = 2, b = 0, c = -1; for (long n = 2; n <= my numberOfCoefficients - 1; n++) { double *t1 = pnm1, *t2 = pnm2; NUMpolynomial_recurrence (pn, n, a, b, c, pnm1, pnm2); if (my coefficients[n + 1] != 0) { for (long j = 1; j <= n + 1; j++) { thy coefficients[j] += my coefficients[n + 1] * pn[j]; } } pnm1 = pn; pnm2 = t1; pn = t2; } } if (my xmin != xmin || my xmax != xmax) { thee.reset (Polynomial_scaleX (thee.peek(), my xmin, my xmax)); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, "; not converted to Polynomial."); }; } void FunctionTerms_and_RealTier_fit (I, thou, int *freeze, double tol, int ic, Covariance *c) { iam (FunctionTerms); thouart (RealTier); try { long numberOfData = thy points -> size; long numberOfParameters = my numberOfCoefficients; long numberOfFreeParameters = numberOfParameters; if (numberOfData < 2) { Melder_throw ("Not enough data points."); } autoFunctionTerms frozen = Data_copy (me); autoNUMvector terms (1, my numberOfCoefficients); autoNUMvector p (1, numberOfParameters); autoNUMvector y_residual (1, numberOfData); autoCovariance ac = 0; if (ic) { ac.reset (Covariance_create (numberOfParameters)); } long k = 1; for (long j = 1; j <= my numberOfCoefficients; j++) { if (freeze && freeze[j]) { numberOfFreeParameters--; } else { p[k] = my coefficients[j]; k++; frozen -> coefficients[j] = 0; } } if (numberOfFreeParameters == 0) { Melder_throw ("No free parameters left."); } autoSVD svd = SVD_create (numberOfData, numberOfFreeParameters); double sigma = RealTier_getStandardDeviation_points (thee, my xmin, my xmax); if (sigma == NUMundefined) { Melder_throw ("Not enough data points in fit interval."); } for (long i = 1; i <= numberOfData; i++) { // Only 'residual variance' must be explained by the model // Evaluate only with the frozen parameters RealPoint point = (RealPoint) thy points -> item [i]; double x = point -> number, y = point -> value, **u = svd -> u; double y_frozen = numberOfFreeParameters == numberOfParameters ? 0 : FunctionTerms_evaluate (frozen.peek(), x); y_residual[i] = (y - y_frozen) / sigma; // Data matrix FunctionTerms_evaluateTerms (me, x, terms.peek()); k = 0; for (long j = 1; j <= my numberOfCoefficients; j++) { if (! freeze || ! freeze[j]) { k++; u[i][k] = terms[j] / sigma; } } } // SVD and evaluation of the singular values if (tol > 0) { SVD_setTolerance (svd.peek(), tol); } SVD_compute (svd.peek()); SVD_solve (svd.peek(), y_residual.peek(), p.peek()); // Put fitted values at correct position k = 1; for (long j = 1; j <= my numberOfCoefficients; j++) { if (! freeze || ! freeze[j]) { my coefficients[j] = p[k++]; } } if (ic) { svdcvm (svd -> v, numberOfFreeParameters, numberOfParameters, freeze, svd -> d, ac -> data); } *c = ac.transfer(); } catch (MelderError) { Melder_throw (me, " & ", thee, ": no fit."); } } Polynomial RealTier_to_Polynomial (I, long degree, double tol, int ic, Covariance *cvm) { iam (RealTier); try { autoPolynomial thee = Polynomial_create (my xmin, my xmax, degree); FunctionTerms_and_RealTier_fit (thee.peek(), me, 0, tol, ic, cvm); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Polynomial fitted."); } } LegendreSeries RealTier_to_LegendreSeries (I, long degree, double tol, int ic, Covariance *cvm) { iam (RealTier); try { autoLegendreSeries thee = LegendreSeries_create (degree, my xmin, my xmax); FunctionTerms_and_RealTier_fit (thee.peek(), me, 0, tol, ic, cvm); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no LegendreSeries fitted."); } } ChebyshevSeries RealTier_to_ChebyshevSeries (I, long degree, double tol, int ic, Covariance *cvm) { iam (RealTier); try { autoChebyshevSeries thee = ChebyshevSeries_create (degree, my xmin, my xmax); FunctionTerms_and_RealTier_fit (thee.peek(), me, 0, tol, ic, cvm); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ":no ChebyshevSeries fitted."); }; } /******* Splines *************************************************/ /* Functions for calculating an mspline and an ispline. These functions should replace the functions in NUM2.c. Before we can do that we first have to adapt the spline- dependencies in MDS.c. Formally nKnots == order + numberOfInteriorKnots + order. We forget about the multiple knots at start and end. Our point-sequece xmin < interiorKont[1] < ... < interiorKnot[n] < xmax. nKnots is now numberOfinteriorKnots + 2. */ static double NUMmspline2 (double points[], long numberOfPoints, long order, long index, double x) { long numberOfSplines = numberOfPoints + order - 2; double m[Spline_MAXIMUM_DEGREE + 2]; Melder_assert (numberOfPoints > 2 && order > 0 && index > 0); if (index > numberOfSplines) { return NUMundefined; } /* Find the range/interval where x is located. M-splines of order k have degree k-1. M-splines are zero outside interval [ knot[i], knot[i+order] ). First and last 'order' knots are equal, i.e., knot[1] = ... = knot[order] && knot[nKnots-order+1] = ... knot[nKnots]. */ long index_b = index - order + 1; index_b = MAX (index_b, 1); if (x < points[index_b]) { return 0; } long index_e = index_b + MIN (index, order); index_e = MIN (numberOfPoints, index_e); if (x > points[index_e]) { return 0; } // Calculate M[i](x|1,t) according to eq.2. for (long k = 1; k <= order; k++) { long k1 = index - order + k, k2 = k1 + 1; m[k] = 0; if (k1 > 0 && k2 <= numberOfPoints && x >= points[k1] && x < points[k2]) { m[k] = 1 / (points[k2] - points[k1]); } } // Iterate to get M[i](x|k,t) for (long k = 2; k <= order; k++) { for (long j = 1; j <= order - k + 1; j++) { long k1 = index - order + j, k2 = k1 + k; if (k2 > 1 && k1 < 1) { k1 = 1; } else if (k2 > numberOfPoints && k1 < numberOfPoints) { k2 = numberOfPoints; } if (k1 > 0 && k2 <= numberOfPoints) { double p1 = points[k1], p2 = points[k2]; m[j] = k * ( (x - p1) * m[j] + (p2 - x) * m[j + 1]) / ( (k - 1) * (p2 - p1)); } } } return m[1]; } static double NUMispline2 (double points[], long numberOfPoints, long order, long index, double x) { Melder_assert (numberOfPoints > 2 && order > 0 && index > 0); long index_b = index - order + 1; index_b = MAX (index_b, 1); if (x < points[index_b]) { return 0; } long index_e = index_b + MIN (index, order); index_e = MIN (numberOfPoints, index_e); if (x > points[index_e]) { return 1; } long j; for (j = index_e - 1; j >= index_b; j--) { if (x > points[j]) { break; } } // Equation 5 in Ramsay's article contains some errors!!! // 1. the interval selection must be 'j-k <= i <= j' instead of // 'j-k+1 <= i <= j' // 2. the summation index m starts at 'i+1' instead of 'i' double y = 0; for (long m = index + 1; m <= j + order; m++) { long km = m - order, kmp = km + order + 1; km = MAX (km, 1); kmp = MIN (kmp, numberOfPoints); y += (points[kmp] - points[km]) * NUMmspline2 (points, numberOfPoints, order + 1, m, x); } return y /= (order + 1); } Thing_implement (Spline, FunctionTerms, 0); double structSpline :: v_evaluate (double x) { (void) x; return 0; } long structSpline :: v_getDegree () { return degree; } long structSpline :: v_getOrder () { return degree + 1; } /* Precondition: FunctionTerms part inited + degree */ static void Spline_initKnotsFromString (I, long degree, const wchar_t *interiorKnots) { iam (Spline); if (degree > Spline_MAXIMUM_DEGREE) { Melder_throw ("Degree must be <= 20."); } long numberOfInteriorKnots; autoNUMvector numbers (NUMstring_to_numbers (interiorKnots, &numberOfInteriorKnots), 1); if (numberOfInteriorKnots > 0) { NUMsort_d (numberOfInteriorKnots, numbers.peek()); if (numbers[1] <= my xmin || numbers[numberOfInteriorKnots] > my xmax) { Melder_throw ("Knots must be inside domain."); } } my degree = degree; long order = Spline_getOrder (me); /* depends on spline type !! */ long n = numberOfInteriorKnots + order; if (my numberOfCoefficients != n) { Melder_throw ("NumberOfCoefficients must equal ", n, "."); } my numberOfKnots = numberOfInteriorKnots + 2; my knots = NUMvector (1, my numberOfKnots); for (long i = 1; i <= numberOfInteriorKnots; i++) { my knots[i + 1] = numbers[i]; } my knots[1] = my xmin; my knots[my numberOfKnots] = my xmax; } void Spline_init (I, double xmin, double xmax, long degree, long numberOfCoefficients, long numberOfKnots) { iam (Spline); if (degree > Spline_MAXIMUM_DEGREE) { Melder_throw ("Spline_init: degree must be <= 20."); } FunctionTerms_init (me, xmin, xmax, numberOfCoefficients); my knots = NUMvector (1, numberOfKnots); my degree = degree; my numberOfKnots = numberOfKnots; my knots[1] = xmin; my knots[numberOfKnots] = xmax; } void Spline_drawKnots (I, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish) { iam (Spline); long order = Spline_getOrder (me); wchar_t ts[20] = L""; if (xmax <= xmin) { xmin = my xmin; xmax = my xmax; } if (xmax < my xmin || xmin > my xmax) { return; } if (ymax <= ymin) { double x1, x2; FunctionTerms_getExtrema (me, xmin, xmax, &x1, &ymin, &x2, &ymax); } Graphics_setWindow (g, xmin, xmax, ymin, ymax); if (my knots[1] >= xmin && my knots[1] <= xmax) { if (garnish) { if (order == 1) { swprintf (ts, 20, L"t__1_"); } else if (order == 2) { swprintf (ts, 20, L"{t__1_, t__2_}"); } else { swprintf (ts, 20, L"{t__1_..t__%ld_}", order); } } Graphics_markTop (g, my knots[1], 0, 1, 1, ts); } for (long i = 2; i <= my numberOfKnots - 1; i++) { if (my knots[i] >= xmin && my knots[i] <= xmax) { if (garnish) { swprintf (ts, 20, L"t__%ld_", i + order - 1); } Graphics_markTop (g, my knots[i], 0, 1, 1, ts); } } if (my knots[my numberOfKnots] >= xmin && my knots[my numberOfKnots] <= xmax) { if (garnish) { long numberOfKnots = my numberOfKnots + 2 * (order - 1); if (order == 1) { swprintf (ts, 20, L"t__%ld_", numberOfKnots); } else if (order == 2) { swprintf (ts, 20, L"{t__%d_, t__%ld_}", numberOfKnots - 1, numberOfKnots); } else { swprintf (ts, 20, L"{t__%d_..t__%ld_}", numberOfKnots - order + 1, numberOfKnots); } } Graphics_markTop (g, my knots[my numberOfKnots], 0, 1, 1, ts); } } #undef our #define our ((Spline_Table) my methods) -> long Spline_getOrder (I) { iam (Spline); return my v_getOrder (); } Spline Spline_scaleX (I, double xmin, double xmax) { try { iam (Spline); Melder_assert (xmin < xmax); autoSpline thee = Data_copy (me); thy xmin = xmin; thy xmax = xmax; // x = a x + b // Constraints: // my xmin = a xmin + b; a = (my xmin - my xmax) / (xmin - xmax); // my xmax = a xmax + b; b = my xmin - a * xmin double a = (xmin - xmax) / (my xmin - my xmax); double b = xmin - a * my xmin; for (long i = 1; i <= my numberOfKnots; i++) { thy knots[i] = a * my knots[i] + b; } return thee.transfer(); } catch (MelderError) { Melder_throw ("Scaled Spline not created."); } } /********* MSplines ************************************************/ double structMSpline :: v_evaluate (double x) { if (x < xmin || x > xmax) { return 0; } double result = 0; for (long i = 1; i <= numberOfCoefficients; i++) { if (coefficients[i] != 0) result += coefficients[i] * NUMmspline2 (knots, numberOfKnots, degree + 1, i, x); } return result; } void structMSpline :: v_evaluateTerms (double x, double *terms) { if (x < xmin || x > xmax) { return; } for (long i = 1; i <= numberOfCoefficients; i++) { terms[i] = NUMmspline2 (knots, numberOfKnots, degree + 1, i, x); } } Thing_implement (MSpline, Spline, 0); MSpline MSpline_create (double xmin, double xmax, long degree, long numberOfInteriorKnots) { try { autoMSpline me = Thing_new (MSpline); long numberOfCoefficients = numberOfInteriorKnots + degree + 1; long numberOfKnots = numberOfCoefficients + degree + 1; Spline_init (me.peek(), xmin, xmax, degree, numberOfCoefficients, numberOfKnots); return me.transfer(); } catch (MelderError) { Melder_throw ("MSpline not created."); } } MSpline MSpline_createFromStrings (double xmin, double xmax, long degree, const wchar_t *coef, const wchar_t *interiorKnots) { try { if (degree > Spline_MAXIMUM_DEGREE) { Melder_throw ("Degree must be <= 20."); } autoMSpline me = Thing_new (MSpline); FunctionTerms_initFromString (me.peek(), xmin, xmax, coef, 1); Spline_initKnotsFromString (me.peek(), degree, interiorKnots); return me.transfer(); } catch (MelderError) { Melder_throw ("MSpline not created from strings."); } } /******** ISplines ************************************************/ double structISpline :: v_evaluate (double x) { if (x < xmin || x > xmax) { return 0; } double result = 0; for (long i = 1; i <= numberOfCoefficients; i++) { if (coefficients[i] != 0) result += coefficients[i] * NUMispline2 (knots, numberOfKnots, degree, i, x); } return result; } void structISpline :: v_evaluateTerms (double x, double *terms) { for (long i = 1; i <= numberOfCoefficients; i++) { terms[i] = NUMispline2 (knots, numberOfKnots, degree, i, x); } } long structISpline :: v_getOrder () { return degree; } Thing_implement (ISpline, Spline, 0); ISpline ISpline_create (double xmin, double xmax, long degree, long numberOfInteriorKnots) { try { autoISpline me = Thing_new (ISpline); long numberOfCoefficients = numberOfInteriorKnots + degree; long numberOfKnots = numberOfCoefficients + degree; Spline_init (me.peek(), xmin, xmax, degree, numberOfCoefficients, numberOfKnots); return me.transfer(); } catch (MelderError) { Melder_throw ("ISpline not created."); } } ISpline ISpline_createFromStrings (double xmin, double xmax, long degree, const wchar_t *coef, const wchar_t *interiorKnots) { try { if (degree > Spline_MAXIMUM_DEGREE) { Melder_throw ("Degree must be <= 20."); } autoISpline me = Thing_new (ISpline); FunctionTerms_initFromString (me.peek(), xmin, xmax, coef, 1); Spline_initKnotsFromString (me.peek(), degree, interiorKnots); return me.transfer(); } catch (MelderError) { Melder_throw ("ISpline not created from strings."); }; } /* #define RationalFunction_members Function_members \ Polynomial num, denum; #define RationalFunction_methods Function_methods class_create (RationalFunction, Function) RationalFunction RationalFunction_create (double xmin, double xmax, long degree_num, long degree_denum) { RationalFunction me = new (RationalFunction); if (! me || ! (my num = Polynomial_create (xmin, xmax, degree_num)) || ! (my denum = Polynomial_create (xmin, xmax, degree_denum))) forget (me); return me; } RationalFunction RationalFunction_createFromString (I, double xmin, double xmax, char *num, char *denum) { RationalFunction me = new (RationalFunction); long i; if (! (my num = Polynomial_createFromString (xmin, xmax, num)) || ! (my denum = Polynomial_createFromString (xmin, xmax, denum))) forget (me); if (my denum -> v[1] != 1 && my denum -> v[1] != 0) { double q0 = my denum -> v[1]; for (i=1; 1 <= my num ->numberOfCoefficients; i++) my num -> v[i] /= q0; for (i=1; 1 <= my denum ->numberOfCoefficients; i++) my denum -> v[i] /= q0; } return me; } // divide out common roots RationalFunction RationalFunction_simplify (RationalFunction me) { Roots num = NULL, denum = NULL; RationalFunction thee = NULL; if (! (num = Polynomial_to_Roots (my num)) || ! (denum = Polynomial_to_Roots (my denum))) goto end; } */ #undef MAX #undef MIN /* end of file Polynomial.cpp */ sources_5316/dwtools/SSCP.cpp0000664000176700017670000016162411725413201014702 0ustar paulpaul/* SSCP.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010614 Covariance_difference: corrected bug in calculation of trace (A B^-1) that caused chisq values to be completely unreliable. djmw 20010628 TableOfReal_to_SSCP: skip error-return when nrows < 2, just issue warning. djmw 20010906 TableOfReal_to_SSCP. djmw 20020212 +getEllipse(s)BoundingBoxCoordinates. djmw 20020313 corrected SSCP_Eigen_project. djmw 20020327 Moved SSCP_and_Eigen_project to Eigen_and_SSCP.c. djmw 20020418 Removed some causes for compiler warnings. djmw 20020430 Changed explicit calculation of SSCP to svd in TableOfReal_to_SSCP. djmw 20030703 Replaced NUMincompletebeta with gsl_sf_beta_inc. djmw 20030801 SSCPs_drawConcentrationEllipses extra label argument. djmw 20030825 Replaced gsl_sf_beta_inc with NUMincompletebeta. djmw 20031104 Added SSCP_to_CCA. djmw 20031117 Added SSCP_extractCentroid. djmw 20031127 Added Covariance_and_TableOfReal_extractDistanceQuantileRange. djmw 20040211 Better warnings in TableOfReal_to_SSCPs_byLabel for single cases. djmw 20040214 Fixed some compiler warnings. djmw 20040219 SSCP_getTraceFraction added. djmw 20040617 SSCP(s)_drawConcentrationEllipse(s) draw with reverse axes possible. (not yet supported by commands in Picture window like 'One mark bottom...' because of reversed axes)! djmw 20060202 Removed a bug in TableOfReal_to_SSCP that could crash Praat (if nrows < ncols). djmw 20060503 Covariance_getSignificanceOfMeansDifference: set probability = 0 if var_pooled = 0 and paired. djmw 20060811 Removed bug in SSCP_and_TableOfReal_to_MahalanobisDistances that caused column labels always to be copied. djmw 20061021 printf expects %ld for 'long int' djmw 20061214 Corrected possible integer overflow in ellipseScalefactor. djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20071016 To Melder_error djmw 20071202 Melder_warning djmw 20080122 float -> double djmw 20081119 TableOfReal_to_SSCP check if numbers are defined djmw 20090617 TableOfReal_to_SSCPs_byLabel better warnings for singular cases. djmw 20090629 +Covariances_getMultivariateCentroidDifference, Covariances_equality. djmw 20100106 +Covariance_and_TableOfReal_mahalanobis. djmw 20101019 Reduced storage Covariance. djmw 20110304 Thing_new */ #include "SSCP.h" #include "Eigen.h" #include "NUMclapack.h" #include "NUMlapack.h" #include "NUM2.h" #include "SVD.h" #include "oo_DESTROY.h" #include "SSCP_def.h" #include "oo_COPY.h" #include "SSCP_def.h" #include "oo_EQUAL.h" #include "SSCP_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "SSCP_def.h" #include "oo_WRITE_TEXT.h" #include "SSCP_def.h" #include "oo_READ_TEXT.h" #include "SSCP_def.h" #include "oo_WRITE_BINARY.h" #include "SSCP_def.h" #include "oo_READ_BINARY.h" #include "SSCP_def.h" #include "oo_DESCRIPTION.h" #include "SSCP_def.h" #undef MAX #undef MIN #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) #define TOVEC(x) (&(x) - 1) Thing_implement (SSCP, TableOfReal, 0); /* Calculate scale factor by which sqrt(eigenvalue) has to be multiplied to obtain the length of an ellipse axis. */ static double ellipseScalefactor (I, double scale, int confidence) { iam (SSCP); long n = SSCP_getNumberOfObservations (me); if (confidence) { long p = my numberOfColumns; double f; if (n - p < 1) { return -1; } /* D.E. Johnson (1998), Applied Multivariate methods, page 410 */ f = NUMinvFisherQ (1 - scale, p, n - p); scale = 2 * sqrt (f * p * (n - 1) / ( ( (double) n) * (n - p))); } else { // very ugly, temporary hack scale *= 2 / (scale < 0 ? -1 : sqrt (n - 1)); } return scale; } static void getEllipseBoundingBoxCoordinates (SSCP me, double scale, int confidence, double *xmin, double *xmax, double *ymin, double *ymax) { double a, b, cs, sn, width, height; double lscale = ellipseScalefactor (me, scale, confidence); NUMeigencmp22 (my data[1][1], my data[1][2], my data[2][2], &a, &b, &cs, &sn); NUMgetEllipseBoundingBox (sqrt (a), sqrt (b), cs, & width, & height); *xmin = my centroid[1] - lscale * width / 2; *xmax = *xmin + lscale * width; *ymin = my centroid[2] - lscale * height / 2; *ymax = *ymin + lscale * height; } void SSCPs_getEllipsesBoundingBoxCoordinates (SSCPs me, double scale, int confidence, double *xmin, double *xmax, double *ymin, double *ymax) { *xmin = *ymin = 1e38; *xmax = *ymax = - *xmin; for (long i = 1; i <= my size; i++) { SSCP s = (SSCP) my item[i]; double xmn, xmx, ymn, ymx; getEllipseBoundingBoxCoordinates (s, scale, confidence, &xmn, &xmx, &ymn, &ymx); if (xmn < *xmin) { *xmin = xmn; } if (xmx > *xmax) { *xmax = xmx; } if (ymn < *ymin) { *ymin = ymn; } if (ymx > *ymax) { *ymax = ymx; } } } static SSCP _SSCP_extractTwoDimensions (SSCP me, long d1, long d2) { autoSSCP thee = SSCP_create (2); if (my numberOfRows == 1) { // diagonal thy data [1][1] = my data [1][d1]; thy data [2][2] = my data [1][d2]; } else { thy data [1][1] = my data [d1][d1]; thy data [2][2] = my data [d2][d2]; thy data [2][1] = thy data [1][2] = my data [d1][d2]; } thy centroid[1] = my centroid[d1]; thy centroid[2] = my centroid[d2]; thy numberOfObservations = my numberOfObservations; TableOfReal_setColumnLabel (thee.peek(), 1, my columnLabels[d1]); TableOfReal_setColumnLabel (thee.peek(), 2, my columnLabels[d2]); TableOfReal_setRowLabel (thee.peek(), 1, my columnLabels[d1]); TableOfReal_setRowLabel (thee.peek(), 2, my columnLabels[d2]); return thee.transfer(); } SSCPs SSCPs_extractTwoDimensions (SSCPs me, long d1, long d2) { try { autoSSCPs thee = SSCPs_create (); for (long i = 1; i <= my size; i++) { autoSSCP t = _SSCP_extractTwoDimensions ( (SSCP) my item[i], d1, d2); Thing_setName (t.peek(), Thing_getName ( (Thing) my item[i])); Collection_addItem (thee.peek(), t.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": cannot extract two dimensions."); } } static void _SSCP_drawTwoDimensionalEllipse (SSCP me, Graphics g, double scale, int fontSize) { long nsteps = 100; wchar_t *name; autoNUMvector x (0L, nsteps); autoNUMvector y (0L, nsteps); // Get principal axes and orientation for the ellipse by performing the // eigen decomposition of a symmetric 2-by-2 matrix. // Principal axes are a and b with eigenvector/orientation (cs, sn). double a, b, cs, sn; NUMeigencmp22 (my data[1][1], my data[1][2], my data[2][2], &a, &b, &cs, &sn); // 1. Take sqrt to get units of 'std_dev' a = scale * sqrt (a) / 2; b = scale * sqrt (b) / 2; x[nsteps] = x[0] = my centroid[1] + cs * a; y[nsteps] = y[0] = my centroid[2] + sn * a; double angle = 0; double angle_inc = NUM2pi / nsteps; for (long i = 1; i < nsteps; i++, angle += angle_inc) { double xc = a * cos (angle); double yc = b * sin (angle); double xt = xc * cs - yc * sn; y[i] = my centroid[2] + xc * sn + yc * cs; x[i] = my centroid[1] + xt; } Graphics_polyline (g, nsteps + 1, x.peek(), y.peek()); if (fontSize > 0 && (name = Thing_getName (me))) { int oldFontSize = Graphics_inqFontSize (g); Graphics_setFontSize (g, fontSize); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, my centroid[1], my centroid[2], name); Graphics_setFontSize (g, oldFontSize); } } SSCP SSCP_toTwoDimensions (I, double *v1, double *v2) { iam (SSCP); try { double *vec[3]; autoSSCP thee = SSCP_create (2); // Projection P of S on v1 and v2 (given matrix V' with 2 rows) is P = V'SV // P[i][j] = sum(k) sum(m) V'[i][k]*S[k][m]*V[m][j] = V'[i][k]*S[k][m]*V'[j][m] // For the new centroids cnew[i] = sum(m) V'[i][m]*c[m] vec[1] = v1; vec[2] = v2; if (my numberOfRows == 1) { // 1xn diagonal matrix for (long k = 1; k <= my numberOfColumns; k++) { thy data[1][1] += v1[k] * my data[1][k] * v1[k]; } for (long k = 1; k <= my numberOfColumns; k++) { thy data[1][2] += v1[k] * my data[1][k] * v2[k]; } for (long k = 1; k <= my numberOfColumns; k++) { thy data[2][2] += v2[k] * my data[1][k] * v2[k]; } thy data[2][1] = thy data[1][2]; } else { for (long i = 1; i <= 2; i++) { for (long j = i; j <= 2; j++) { double sum = 0; for (long k = 1; k <= my numberOfRows; k++) { for (long m = 1; m <= my numberOfRows; m++) { sum += vec[i][k] * my data[k][m] * vec[j][m]; } } thy data[j][i] = thy data[i][j] = sum; } } } // centroids for (long m = 1; m <= my numberOfColumns; m++) { thy centroid[1] += v1[m] * my centroid[m]; } for (long m = 1; m <= my numberOfColumns; m++) { thy centroid[2] += v2[m] * my centroid[m]; } thy numberOfObservations = SSCP_getNumberOfObservations (me); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": cannot extract two dimensions."); } } void SSCP_init (I, long dimension, long storage) { iam (SSCP); TableOfReal_init (me, storage, dimension); my centroid = NUMvector (1, dimension); } SSCP SSCP_create (long dimension) { try { autoSSCP me = Thing_new (SSCP); SSCP_init (me.peek(), dimension, dimension); return me.transfer(); } catch (MelderError) { Melder_throw ("SSCP not created."); } } double SSCP_getConcentrationEllipseArea (I, double scale, int confidence, long d1, long d2) { iam (SSCP); long p = my numberOfRows; if (d1 < 1 || d1 > p || d2 < 1 || d2 > p || d1 == d2) { Melder_throw ("Incorrect axes."); } autoSSCP thee = _SSCP_extractTwoDimensions (me, d1, d2); scale = ellipseScalefactor (thee.peek(), scale, confidence); if (scale < 0) { Melder_throw ("Invalid scale factor."); } double a, b, cs, sn; NUMeigencmp22 (thy data[1][1], thy data[1][2], thy data[2][2], &a, &b, &cs, &sn); // 1. Take sqrt to get units of 'std_dev' a = scale * sqrt (a) / 2; b = scale * sqrt (b) / 2; return NUMpi * a * b; } double SSCP_getFractionVariation (I, long from, long to) { iam (SSCP); long n = my numberOfRows; if (from < 1 || from > to || to > n) { return NUMundefined; } double sum = 0, trace = 0; for (long i = 1; i <= n; i++) { trace += my numberOfRows == 1 ? my data[1][i] : my data[i][i]; if (i >= from && i <= to) { sum += my numberOfRows == 1 ? my data[1][i] : my data[i][i]; } } return trace > 0 ? sum / trace : NUMundefined; } void SSCP_drawConcentrationEllipse (SSCP me, Graphics g, double scale, int confidence, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int garnish) { long p = my numberOfColumns; if (d1 < 1 || d1 > p || d2 < 1 || d2 > p || d1 == d2) { Melder_throw ("Incorrect axes."); } autoSSCP thee = _SSCP_extractTwoDimensions (me, d1, d2); double xmn, xmx, ymn, ymx; getEllipseBoundingBoxCoordinates (thee.peek(), scale, confidence, &xmn, &xmx, &ymn, &ymx); if (xmax == xmin) { xmin = xmn; xmax = xmx; } if (ymax == ymin) { ymin = ymn; ymax = ymx; } Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setInner (g); scale = ellipseScalefactor (thee.peek(), scale, confidence); if (scale < 0) { Melder_throw ("Invalid scale factor."); } _SSCP_drawTwoDimensionalEllipse (thee.peek(), g, scale, 0); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_marksBottom (g, 2, 1, 1, 0); } } void SSCP_setNumberOfObservations (I, double numberOfObservations) { iam (SSCP); my numberOfObservations = numberOfObservations; } double SSCP_getNumberOfObservations (I) { iam (SSCP); return my numberOfObservations; } double SSCP_getDegreesOfFreedom (I) { iam (SSCP); return my numberOfObservations - 1; } double SSCP_getTotalVariance (I) { iam (SSCP); double trace = 0; for (long i = 1; i <= my numberOfColumns; i++) { trace += my numberOfRows == 1 ? my data[1][i] : my data[i][i]; } return trace; } double SSCP_getCumulativeContributionOfComponents (I, long from, long to) { iam (SSCP); double sum = NUMundefined; if (to == 0) { to = my numberOfRows; } if (from > 0 && to <= my numberOfRows && from <= to) { sum = SSCP_getTotalVariance (me); double partial = 0; for (long i = from; i <= to; i++) { partial += my numberOfRows == 1 ? my data[1][i] : my data[i][i]; } if (sum > 0) { sum = partial / sum; } } return sum; } /* For nxn matrix only ! */ void Covariance_and_PCA_generateOneVector (Covariance me, PCA thee, double *vec, double *buf) { // Generate the multi-normal vector elements N(0,sigma) for (long j = 1; j <= my numberOfColumns; j++) { buf[j] = NUMrandomGauss (0, sqrt (thy eigenvalues[j])); } // Rotate back for (long j = 1; j <= my numberOfColumns; j++) { vec[j] = 0; for (long k = 1; k <= my numberOfColumns; k++) { vec[j] += buf[k] * thy eigenvectors[k][j]; } } // Restore the centroid for (long j = 1; j <= my numberOfColumns; j++) { vec[j] += my centroid[j]; } } TableOfReal Covariance_to_TableOfReal_randomSampling (Covariance me, long numberOfData) { try { if (numberOfData <= 0) { numberOfData = my numberOfObservations; } autoPCA pca = SSCP_to_PCA (me); autoTableOfReal thee = TableOfReal_create (numberOfData, my numberOfColumns); autoNUMvector buf (1, my numberOfColumns); for (long i = 1; i <= numberOfData; i++) { Covariance_and_PCA_generateOneVector (me, pca.peek(), thy data[i], buf.peek()); } NUMstrings_copyElements (my columnLabels, thy columnLabels, 1, my numberOfColumns); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not random sampled."); } } SSCP TableOfReal_to_SSCP (I, long rowb, long rowe, long colb, long cole) { iam (TableOfReal); try { TableOfReal_areAllCellsDefined (me, rowb, rowe, colb, cole); if (rowb == 0 && rowe == 0) { rowb = 1; rowe = my numberOfRows; } else if (rowe < rowb || rowb < 1 || rowe > my numberOfRows) { Melder_throw ("Invalid row number."); } if (colb == 0 && cole == 0) { colb = 1; cole = my numberOfColumns; } else if (cole < colb || colb < 1 || cole > my numberOfColumns) { Melder_throw ("Invalid column number."); } long m = rowe - rowb + 1; /* # rows */ long n = cole - colb + 1; /* # columns */ if (m < n) Melder_warning (L"The SSCP will not have \n" "full dimensionality. This may be a problem in following analysis steps. \n" "(The number of data points was less than the number of variables.)"); autoSSCP thee = SSCP_create (n); autoNUMmatrix v (1, m, 1, n); long nvalidrows = 0; for (long i = 1; i <= m; i++) { nvalidrows++; for (long j = 1; j <= n; j++) { v[i][j] = my data[rowb + i - 1][colb + j - 1]; } } NUMcentreColumns (v.peek(), 1, m, 1, n, thy centroid); SSCP_setNumberOfObservations (thee.peek(), m); // sum of squares and cross products = T'T for (long i = 1; i <= n; i++) { for (long j = i; j <= n; j++) { double t = 0; for (long k = 1; k <= m; k++) { t += v[k][i] * v[k][j]; } thy data[i][j] = thy data[j][i] = t; } } NUMstrings_copyElements (TOVEC (my columnLabels[colb]), thy columnLabels, 1, n); NUMstrings_copyElements (thy columnLabels, thy rowLabels, 1, n); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": SSCP not created."); } } TableOfReal SSCP_and_TableOfReal_extractDistanceQuantileRange (SSCP me, thou, double qlow, double qhigh) { try { thouart (TableOfReal); autoCovariance cov = SSCP_to_Covariance (me, 1); autoTableOfReal him = Covariance_and_TableOfReal_extractDistanceQuantileRange (cov.peek(), thee, qlow, qhigh); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no distance quantile ranges created."); } } TableOfReal Covariance_and_TableOfReal_mahalanobis (Covariance me, thou, bool useTableCentroid) { try { thouart (TableOfReal); autoTableOfReal him = TableOfReal_create (thy numberOfRows, 1); autoNUMvector centroid (NUMvector_copy (my centroid, 1, thy numberOfColumns), 1); autoNUMmatrix covari (NUMmatrix_copy (my data, 1, my numberOfRows, 1, my numberOfRows), 1, 1); // Mahalanobis distance calculation. S = L.L' -> S**-1 = L**-1' . L**-1 // (x-m)'S**-1 (x-m) = (x-m)'L**-1' . L**-1. (x-m) = // (L**-1.(x-m))' . (L**-1.(x-m)) // Get inverse of covari in lower triangular part. double lndet; NUMlowerCholeskyInverse (covari.peek(), my numberOfRows, &lndet); if (useTableCentroid) { for (long icol = 1; icol <= thy numberOfColumns; icol++) { double mean = 0; for (long irow = 1; irow <= thy numberOfRows; irow++) { mean += thy data[irow][icol]; } centroid[icol] = mean / thy numberOfRows; } } for (long k = 1; k <= thy numberOfRows; k++) { his data[k][1] = sqrt (NUMmahalanobisDistance_chi (covari.peek(), thy data[k], centroid.peek(), my numberOfRows, my numberOfRows)); if (thy rowLabels[k] != 0) { TableOfReal_setRowLabel (him.peek(), k, thy rowLabels[k]); } } TableOfReal_setColumnLabel (him.peek(), 1, L"d"); return him.transfer(); } catch (MelderError) { Melder_throw (me, "no Mahalanobis distances created."); } } TableOfReal Covariance_and_TableOfReal_extractDistanceQuantileRange (Covariance me, thou, double qlow, double qhigh) { try { thouart (TableOfReal); autoTableOfReal him = Covariance_and_TableOfReal_mahalanobis (me, thee, false); double low = TableOfReal_getColumnQuantile (him.peek(), 1, qlow); double high = TableOfReal_getColumnQuantile (him.peek(), 1, qhigh); // Count the number filtered. // nsel = (qhigh - qlow) * nrows is sometimes one off long nsel = 0; for (long i = 1; i <= thy numberOfRows; i++) { if (low <= his data[i][1] && his data[i][1] < high) { nsel++; } } if (nsel < 1) { Melder_throw ("Not enough data in quantile interval."); } autoTableOfReal r = TableOfReal_create (nsel, thy numberOfColumns); NUMstrings_copyElements (thy columnLabels, r -> columnLabels, 1, thy numberOfColumns); //((r -> columnLabels = NUMstrings_copy (thy columnLabels, 1, thy numberOfColumns)) == NULL)) goto end; long k = 0; for (long i = 1; i <= thy numberOfRows; i++) { if (low <= his data[i][1] && his data[i][1] < high) { k++; TableOfReal_copyOneRowWithLabel (thee, r.peek(), i, k); } } return r.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal with distancequantile range not created."); } } Covariance TableOfReal_to_Covariance (I) { iam (TableOfReal); try { autoSSCP sscp = TableOfReal_to_SSCP (me, 0, 0, 0, 0); autoCovariance thee = SSCP_to_Covariance (sscp.peek(), 1); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": covariances not created."); } } Correlation TableOfReal_to_Correlation (I) { iam (TableOfReal); try { autoSSCP sscp = TableOfReal_to_SSCP (me, 0, 0, 0, 0); autoCorrelation thee = SSCP_to_Correlation (sscp.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": correlations not created."); } } Correlation TableOfReal_to_Correlation_rank (I) { iam (TableOfReal); try { autoTableOfReal t = TableOfReal_rankColumns (me); autoCorrelation thee = TableOfReal_to_Correlation (t.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": rank correlations not created."); } } SSCPs TableOfReal_to_SSCPs_byLabel (I) { iam (TableOfReal); try { autoSSCPs thee = SSCPs_create (); autoTableOfReal mew = TableOfReal_sortOnlyByRowLabels (me); const wchar_t *label = mew -> rowLabels[1]; Melder_warningOff (); long numberOfCases = my numberOfRows, ncols = my numberOfColumns; long lastrow = 0, ngroups = 0, nsingular = 0, index = 1; for (long i = 2; i <= numberOfCases; i++) { long nrows = 0; const wchar_t *li = mew -> rowLabels[i]; if (Melder_wcscmp (li, label) != 0) { // current label different from previous one(s) nrows = i - index; lastrow = i - 1; } else if (i == numberOfCases) { // current (last) label is same as previous nrows = i - index + 1; lastrow = i; } else { // next one continue; } // We found a new group ngroups++; if (nrows > 1) { // We need at least two rows for an SSCP if (nrows < ncols) { nsingular++; } autoSSCP t = TableOfReal_to_SSCP (mew.peek(), index, lastrow, 0, 0); if (! (label = mew -> rowLabels[index])) { label = L"?"; } Thing_setName (t.peek(), label); Collection_addItem (thee.peek(), t.transfer()); } label = li; index = i; } if (lastrow != numberOfCases) { ngroups++; } Melder_warningOn (); if (nsingular > 0 || thy size != ngroups) { long notIncluded = ngroups - thy size; Melder_warning (Melder_integer (ngroups), L" different groups detected: ", Melder_integer (nsingular + notIncluded), L" group(s) with less rows than columns (of which ", Melder_integer (notIncluded), L" with only one row)."); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": SSCP not created from labels."); } } PCA SSCP_to_PCA (I) { iam (SSCP); try { double **data = my data; autoNUMmatrix adata; autoPCA thee = PCA_create (my numberOfColumns, my numberOfColumns); if (my numberOfRows == 1) { // 1xn matrix -> nxn // ugly hack adata.reset (1, my numberOfColumns, 1, my numberOfColumns); for (long i = 1; i <= my numberOfColumns; i++) { data[i][i] = my data[1][i]; } data = adata.peek(); } NUMstrings_copyElements (my columnLabels, thy labels, 1, my numberOfColumns); Eigen_initFromSymmetricMatrix (thee.peek(), data, my numberOfColumns); NUMvector_copyElements (my centroid, thy centroid, 1, my numberOfColumns); PCA_setNumberOfObservations (thee.peek(), my numberOfObservations); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": PCA not created."); } } void SSCP_setValue (I, long row, long col, double value) { iam (SSCP); if (col < 0 || col > my numberOfColumns) { Melder_throw ("Illegal column number."); } if (row < 0 || row > my numberOfColumns) { Melder_throw ("Illegal row number."); // ! yes numberOfColumns } if (row == col && value <= 0) { Melder_throw ("Diagonal element must always be a positive number."); } if (my numberOfRows == 1) { // diagonal if (row != col) { Melder_throw ("Row and column number must be equal for a diagonal matrix."); } my data[1][row] = value; } else { if (row != col && (fabs (value) > my data[row][row] || fabs (value) > my data[row][row])) Melder_throw ("The off-diagonal cannot be larger than the diagonal values. Input diagonal elements first, or change this value."); my data[row][col] = my data[col][row] = value; } } void SSCP_setCentroid (I, long component, double value) { iam (SSCP); if (component < 1 || component > my numberOfColumns) { Melder_throw ("Illegal component number."); } my centroid[component] = value; } CCA SSCP_to_CCA (I, long ny) { iam (SSCP); try { char upper = 'L', diag = 'N'; long info; if (ny < 1 || ny >= my numberOfRows) { Melder_throw ("ny < 1 || ny >= my numberOfRows"); } if (my numberOfRows == 1) { Melder_throw ("Matrix is diagonal."); } long m = my numberOfRows, nx = m - ny, xy_interchanged = nx < ny, yof = 0, xof = ny; if (xy_interchanged) { yof = ny; xof = 0; nx = ny; ny = m - nx; } autoCCA thee = Thing_new (CCA); autoNUMmatrix sxx (1, nx, 1, nx); autoNUMmatrix syy (1, ny, 1, ny); autoNUMmatrix syx (1, ny, 1, nx); // Copy Syy and Sxx into upper part of syy and sxx matrices. for (long i = 1; i <= ny; i++) { for (long j = i; j <= ny; j++) { syy[i][j] = my data[yof + i][yof + j]; } } for (long i = 1; i <= nx; i++) { for (long j = i; j <= nx; j++) { sxx[i][j] = my data[xof + i][xof + j]; } } for (long i = 1; i <= nx; i++) { for (long j = 1; j <= ny; j++) { syx[i][j] = my data[yof + i][xof + j]; } } // Cholesky decomposition: Syy = Uy'*Uy and Sxx = Ux'*Ux. // (Pretend as if colum-major storage) (void) NUMlapack_dpotf2 (&upper, &ny, &syy[1][1], &ny, &info); if (info != 0) Melder_throw ("The leading minor of order ", info, " is not positive definite, and the " "factorization of Syy could not be completed."); (void) NUMlapack_dpotf2 (&upper, &nx, &sxx[1][1], &nx, &info); if (info != 0) Melder_throw ("The leading minor of order ", info, " is not positive definite, and the " "factorization of Sxx could not be completed."); /* With Cholesky decomps Sxx = Ux'* Ux, Syy = Uy * Uy' Sxx**-1 = Uxi * Uxi' and Syy**-1 = Uyi * Uyi', where Uxi = Ux**-1 and Uyi = Uy**-1, the equations (1) (Syx * Sxx**-1 * Syx' - lambda Syy) y = 0 (1') (Syx' * Syy**-1 * Syx - lambda Sxx) x = 0 can be written as: (2) (Syx * Uxi * Uxi' * Syx' - lambda Uy' * Uy) y = 0 (2') (Syx' * Uyi * Uyi' * Syx - lambda Ux' * Ux) x = 0 More explicitly as: (3) (Uxi' * Syx')' * (Uxi' * Syx') - lambda Uy' * Uy) y = 0 (3') (Uyi' * Syx )' * (Uyi' * Syx ) - lambda Ux' * Ux) x = 0 They are now in the form (A'A - lambda B'B) x = 0 and both can be solved with the GSVD. However, these equations are not independent. Both have the same eigenvalues and given the eigenvectors for one, the eigenvectors for the other can be calculated. If nx >= ny use eq. (3) GSVD (Uxi' * Syx', Uy) gives lambda's and y. To get x multiply (1) from the left by Syx'*Syy**-1 (4) (Syx'*Syy**-1*Syx * Sxx**-1 - lambda ) Syx' * y = 0 Split off Sxx**-1 (5) (Syx'*Syy**-1*Syx -lambda Sxx) * Sxx**-1 * Syx' * y = 0 It follows that x = Sxx**-1 * Syx' * y = Uxi * Uxi' * Sxy * y If ny > nx use eq. (3') We switch the role of x and y. */ autoNUMmatrix a (1, nx, 1, ny); // Uxi = inverse(Ux) (void) NUMlapack_dtrti2 (&upper, &diag, &nx, &sxx[1][1], &nx, &info); if (info != 0) { Melder_throw ("Error in inverse for Sxx."); } // Prepare Uxi' * Syx' = (Syx * Uxi)' for (long i = 1; i <= ny; i++) { for (long j = 1; j <= nx; j++) { double t = 0; for (long k = 1; k <= j; k++) { t += syx[i][k] * sxx[k][j]; } a[j][i] = t; } } autoGSVD gsvd = GSVD_create_d (a.peek(), nx, ny, syy.peek(), ny); autoNUMmatrix ri (NUMmatrix_copy (gsvd -> r, 1, gsvd -> numberOfColumns, 1, gsvd -> numberOfColumns), 1, 1); thy y = Eigen_create (gsvd -> numberOfColumns, gsvd -> numberOfColumns); thy x = Eigen_create (thy y -> numberOfEigenvalues, nx); // Get X=Q*R**-1 (void) NUMlapack_dtrti2 (&upper, &diag, &gsvd -> numberOfColumns, &ri[1][1], &gsvd -> numberOfColumns, &info); if (info != 0) { Melder_throw ("Error in inverse for R."); } for (long i = 1; i <= gsvd -> numberOfColumns; i++) { double t = gsvd -> d1[i] / gsvd -> d2[i]; thy y -> eigenvalues[i] = t * t; for (long j = 1; j <= gsvd -> numberOfColumns; j++) { t = 0; for (long k = 1; k <= j; k++) { t += gsvd -> q[i][k] * ri[k][j]; } thy y ->eigenvectors[j][i] = t; } } NUMnormalizeRows (thy y -> eigenvectors, thy y -> numberOfEigenvalues, thy y -> numberOfEigenvalues, 1); thy numberOfCoefficients = thy y -> numberOfEigenvalues; thy numberOfObservations = my numberOfObservations; // x = Sxx**-1 * Syx' * y for (long i = 1; i <= thy numberOfCoefficients; i++) { double *evecy = thy y -> eigenvectors[i]; double *evecx = thy x -> eigenvectors[i]; for (long j = 1; j <= nx; j++) { double t = 0; for (long k = j; k <= nx; k++) { for (long l = 1; l <= nx; l++) { for (long n = 1; n <= ny; n++) { t += sxx[j][k] * sxx[l][k] * syx[n][l] * evecy[n]; } } } evecx[j] = t; } } NUMnormalizeRows (thy x -> eigenvectors, thy x -> numberOfEigenvalues, nx, 1); if (ny < nx) { Eigen t = thy x; thy x = thy y; thy y = t; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": CCA not created."); } } /************ SSCPs ***********************************************/ Thing_implement (SSCPs, Ordered, 0); SSCPs SSCPs_create () { try { autoSSCPs me = Thing_new (SSCPs); Ordered_init (me.peek(), classSSCP, 10); return me.transfer(); } catch (MelderError) { Melder_throw ("SSCPs not created."); } } SSCP SSCPs_to_SSCP_pool (SSCPs me) { try { autoSSCP thee = Data_copy ( (SSCP) my item[1]); for (long k = 2; k <= my size; k++) { SSCP t = (SSCP) my item[k]; long no = t -> numberOfObservations; if (t -> numberOfRows != thy numberOfRows) { Melder_throw ("Unequal dimensions (", k, ")."); } thy numberOfObservations += no; // Sum the sscp's and weigh the centroid. for (long i = 1; i <= thy numberOfRows; i++) { // if 1xn for (long j = 1; j <= thy numberOfColumns; j++) { thy data[i][j] += t -> data[i][j]; } } for (long j = 1; j <= thy numberOfRows; j++) { thy centroid[j] += no * t -> centroid[j]; } } for (long i = 1; i <= thy numberOfRows; i++) { thy centroid[i] /= thy numberOfObservations; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not pooled."); } } void SSCPs_getHomegeneityOfCovariances_box (SSCPs me, double *probability, double *chisq, long *ndf) { *probability = 0; *chisq = 0; *ndf = 0; autoSSCP pooled = SSCPs_to_SSCP_pool (me); long p = pooled -> numberOfColumns; double ln_determinant, inv = 0, sum = 0, g = my size; for (long i = 1; i <= g; i++) { SSCP t = (SSCP) my item[i]; double ni = t -> numberOfObservations - 1; NUMdeterminant_cholesky (t -> data, p, &ln_determinant); // Box-test is for covariance matrices -> scale determinant. ln_determinant -= p * log (ni); sum += ni; inv += 1 / ni; *chisq -= ni * ln_determinant; } NUMdeterminant_cholesky (pooled -> data, p, &ln_determinant); ln_determinant -= p * log (pooled -> numberOfObservations - g); *chisq += sum * ln_determinant; *chisq *= 1.0 - (inv - 1 / sum) * (2 * p * p + 3 * p - 1) / (6 * (p + 1) * (g - 1)); *ndf = (g - 1) * p * (p + 1) / 2; *probability = NUMchiSquareQ (*chisq, *ndf); } SSCPs SSCPs_toTwoDimensions (SSCPs me, double *v1, double *v2) { try { autoSSCPs thee = SSCPs_create (); for (long i = 1; i <= my size; i++) { autoSSCP t = (SSCP) SSCP_toTwoDimensions (my item[i], v1, v2); Thing_setName (t.peek(), Thing_getName ( (Thing) my item[i])); Collection_addItem (thee.peek(), t.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not reduced to two dimensions."); } } void SSCPs_drawConcentrationEllipses (SSCPs me, Graphics g, double scale, int confidence, const wchar_t *label, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish) { SSCP t = (SSCP) my item[1]; long p = t -> numberOfColumns; if (d1 < 1 || d1 > p || d2 < 1 || d2 > p || d1 == d2) { Melder_throw ("Incorrect axes."); } autoSSCPs thee = SSCPs_extractTwoDimensions (me, d1, d2); double xmn, xmx, ymn, ymx; SSCPs_getEllipsesBoundingBoxCoordinates (thee.peek(), scale, confidence, &xmn, &xmx, &ymn, &ymx); if (xmin == xmax) { xmin = xmn; xmax = xmx; } if (ymin == ymax) { ymin = ymn; ymax = ymx; } Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setInner (g); for (long i = 1; i <= thy size; i++) { double lscale; t = (SSCP) thy item[i]; lscale = ellipseScalefactor (t, scale, confidence); if (lscale < 0) { continue; } if (label == 0 || Melder_wcscmp (label, Thing_getName (t)) == 0) { _SSCP_drawTwoDimensionalEllipse (t, g, lscale, fontSize); } } Graphics_unsetInner (g); if (garnish) { wchar_t text[20]; t = (SSCP) my item[1]; Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); swprintf (text, 20, L"Dimension %ld", d2); Graphics_textLeft (g, 1, t -> columnLabels[d2] ? t -> columnLabels[d2] : text); Graphics_marksBottom (g, 2, 1, 1, 0); swprintf (text, 20, L"Dimension %ld", d1); Graphics_textBottom (g, 1, t -> columnLabels[d1] ? t -> columnLabels[d1] : text); } } TableOfReal SSCP_to_TableOfReal (SSCP me) { try { autoTableOfReal thee = Thing_new (TableOfReal); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not copied."); } } TableOfReal SSCP_extractCentroid (I) { iam (SSCP); try { long n = my numberOfColumns; autoTableOfReal thee = TableOfReal_create (1, n); NUMvector_copyElements (my centroid, thy data[1], 1, n); thy columnLabels = NUMstrings_copy (my columnLabels, 1, n); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": centroid not extracted."); } } Thing_implement (Covariance, SSCP, 0); Thing_implement (Correlation, SSCP, 0); Covariance Covariance_create (long dimension) { try { autoCovariance me = Thing_new (Covariance); SSCP_init (me.peek(), dimension, dimension); return me.transfer(); } catch (MelderError) { Melder_throw ("Covariance not created."); } } Covariance Covariance_create_reduceStorage (long dimension, long storage) { try { autoCovariance me = Thing_new (Covariance); if (storage <= 0 || storage >= dimension) { storage = dimension; } SSCP_init (me.peek(), dimension, storage); return me.transfer(); } catch (MelderError) { Melder_throw ("Reduced storage covariance not created."); } } Covariance Covariance_createSimple (wchar_t *covariances, wchar_t *centroid, long numberOfObservations) { try { long dimension, ncovars; autoNUMvector centroids (NUMstring_to_numbers (centroid, &dimension), 1); autoNUMvector covars (NUMstring_to_numbers (covariances, &ncovars), 1); long ncovars_wanted = dimension * (dimension + 1) / 2; if (ncovars != ncovars_wanted) Melder_throw ("The number of covariance matrix elements and the number of " "centroid elements are not in concordance. There should be d(d+1)/2 covariance values and d centroid values."); autoCovariance me = Covariance_create (dimension); // Construct the full covariance matrix from the upper-diagonal elements long rowNumber = 1; for (long inum = 1; inum <= ncovars_wanted; inum++) { long nmissing = (rowNumber - 1) * rowNumber / 2; long inumc = inum + nmissing; rowNumber = (inumc - 1) / dimension + 1; long icol = ( (inumc - 1) % dimension) + 1; my data[rowNumber][icol] = my data[icol][rowNumber] = covars[inum]; if (icol == dimension) { rowNumber++; } } // Check if a valid covariance, first check variances then covariances for (long irow = 1; irow <= dimension; irow++) { if (my data[irow][irow] <= 0) { Melder_throw ("The variances, i.e. the diagonal matrix elements, must all be positive numbers."); } } for (long irow = 1; irow <= dimension; irow++) { for (long icol = irow + 1; icol <= dimension; icol++) { if (fabs (my data[irow][icol] / sqrt (my data[irow][irow] * my data[icol][icol])) > 1) { long nmissing = (irow - 1) * irow / 2; long inum = (irow - 1) * dimension + icol - nmissing; Melder_throw (L"The covariance in cell [", irow, L",", icol, L"], i.e. input item ", inum, L" is too large."); } } } for (long inum = 1; inum <= dimension; inum++) { my centroid[inum] = centroids[inum]; } my numberOfObservations = numberOfObservations; return me.transfer(); } catch (MelderError) { Melder_throw ("Simple Covariance not created."); } } Correlation Correlation_create (long dimension) { try { autoCorrelation me = Thing_new (Correlation); SSCP_init (me.peek(), dimension, dimension); return me.transfer(); } catch (MelderError) { Melder_throw ("Correlation not created."); } } Covariance SSCP_to_Covariance (SSCP me, long numberOfConstraints) { try { Melder_assert (numberOfConstraints >= 0); autoCovariance thee = Thing_new (Covariance); my structSSCP :: v_copy (thee.peek()); for (long i = 1; i <= my numberOfRows; i++) { for (long j = i; j <= my numberOfColumns; j++) { thy data[j][i] = thy data[i][j] /= (my numberOfObservations - numberOfConstraints); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, "; Covariance not created."); } } SSCP Covariance_to_SSCP (Covariance me) { try { autoSSCP thee = Thing_new (SSCP); my structSSCP :: v_copy (thee.peek()); for (long i = 1; i <= my numberOfRows; i++) { for (long j = i; j <= my numberOfColumns; j++) { thy data[j][i] = thy data[i][j] *= (my numberOfObservations - 1); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": SSCP not created."); } } Correlation SSCP_to_Correlation (I) { iam (SSCP); try { autoCorrelation thee = Thing_new (Correlation); my structSSCP :: v_copy (thee.peek()); for (long i = 1; i <= my numberOfRows; i++) { for (long j = i; j <= my numberOfColumns; j++) { thy data[j][i] = thy data[i][j] /= sqrt (my data[i][i] * my data[j][j]); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Correlation not created."); } } double SSCP_getLnDeterminant (I) { try { iam (SSCP); double ln_d; NUMdeterminant_cholesky (my data, my numberOfRows, &ln_d); return ln_d; } catch (MelderError) { return NUMundefined; } } static Covariance Covariances_pool (Covariance me, Covariance thee) { try { if (my numberOfRows != thy numberOfRows || my numberOfColumns != thy numberOfColumns) Melder_throw ("Matrices must have equal dimensions."); autoSSCPs sscps = SSCPs_create (); autoSSCP sscp1 = Covariance_to_SSCP (me); Collection_addItem (sscps.peek(), sscp1.transfer()); autoSSCP sscp2 = Covariance_to_SSCP (thee); Collection_addItem (sscps.peek(), sscp2.transfer()); autoSSCP pool = SSCPs_to_SSCP_pool (sscps.peek()); autoCovariance him = SSCP_to_Covariance (pool.peek(), 2); return him.transfer(); } catch (MelderError) { Melder_throw (me, "not pooled."); } } static double **productOfSquareMatrices (double **s1, double **s2, long n) { autoNUMmatrix r (1, n, 1, n); for (long i = 1; i <= n; i++) { for (long j = 1; j <= n; j++) { double sum = 0; for (long k = 1; k <= n; k++) { sum += s1[i][k] * s2[k][j]; } r[i][j] = sum; } } return r.transfer(); } static double traceOfSquaredMatrixProduct (double **s1, double **s2, long n) { // tr ((s1*s2)^2), s1, s2 are symmetric autoNUMmatrix m (productOfSquareMatrices (s1, s2, n), 1, 1); double trace2 = NUMtrace2 (m.peek(), m.peek(), n); return trace2; } double Covariance_getProbabilityAtPosition_string (Covariance me, wchar_t *vector) { autoNUMvector v (1, my numberOfColumns); long i = 0; for (wchar_t *token = Melder_firstToken (vector); token != NULL; token = Melder_nextToken ()) { v[++i] = Melder_atof (token); if (i == my numberOfColumns) { break; } } double p = Covariance_getProbabilityAtPosition (me, v.peek()); return p; } double Covariance_getProbabilityAtPosition (Covariance me, double *x) { if (my lowerCholesky == 0) { SSCP_expandLowerCholesky (me); } double ln2pid = my numberOfColumns * log (NUM2pi); double dsq = NUMmahalanobisDistance_chi (my lowerCholesky, x, my centroid, my numberOfRows, my numberOfColumns); double lnN = - 0.5 * (ln2pid + my lnd + dsq); double p = exp (lnN); return p; } double Covariance_getMarginalProbabilityAtPosition (Covariance me, double *vector, double x) { double mu, stdev; Covariance_getMarginalDensityParameters (me, vector, &mu, &stdev); double dx = (x - mu) / stdev; double p = (NUM1_sqrt2pi / stdev) * exp (- 0.5 * dx * dx); return p; } /* Precondition ||v|| = 1 */ void Covariance_getMarginalDensityParameters (Covariance me, double *v, double *mu, double *stdev) { *stdev = *mu = 0; if (my numberOfRows == 1) { // 1xn diagonal matrix for (long m = 1; m <= my numberOfColumns; m++) { *stdev += v[m] * my data[1][m] * v[m]; } } else { for (long k = 1; k <= my numberOfRows; k++) { for (long m = 1; m <= my numberOfColumns; m++) { *stdev += v[k] * my data[k][m] * v[m]; } } } *stdev = sqrt (*stdev); for (long m = 1; m <= my numberOfColumns; m++) { *mu += v[m] * my centroid[m]; } } double Covariances_getMultivariateCentroidDifference (Covariance me, Covariance thee, int equalCovariances, double *prob, double *fisher, double *df1, double *df2) { long p = my numberOfRows, N = my numberOfObservations + thy numberOfObservations; long N1 = my numberOfObservations, n1 = N1 - 1; long N2 = thy numberOfObservations, n2 = N2 - 1; double dif = *prob = *fisher = NUMundefined; *df1 = p; *df2 = N - p - 1; if (*df2 < 1) { Melder_throw ("Not enough observations (", N, ") for this test."); } if (N1 < p || N2 < p) { Melder_throw ("At least one of the covariances has less observations than variables."); } dif = 0; for (long i = 1; i <= p; i++) { double dist = my centroid[i] - thy centroid[i]; dif += dist * dist; } dif = sqrt (dif); if (equalCovariances) { // Morrison, page 141 autoCovariance pool = Covariances_pool (me, thee); autoNUMmatrix s (NUMmatrix_copy (my data, 1, p, 1, p), 1, 1); double lndet; NUMlowerCholeskyInverse (s.peek(), p, &lndet); double mahalanobis = NUMmahalanobisDistance_chi (s.peek(), my centroid, thy centroid, p, p); double hotelling_tsq = mahalanobis * N1 * N2 / N; *fisher = hotelling_tsq * *df2 / ( (N - 2) * *df1); } else { /* Krishnamoorthy-Yu (2004): Modified Nel and Van der Merwe test Hotelling t^2 = (x1-x2)'*S^-1*(x1 -x2) follows nu*p*Fisher(p,nu-p+1)/(nu-p+1) Approximate number of degrees of freedom (their formula 7, page 164) nu = (p+p^2)/((1/n1)(tr (S1*S^-1)^2 + (tr(S1*S^-1))^2)) +(1/n2)(tr (S2*S^-1)^2 + (tr(S2*S^-1))^2))) the matrices S1 and S2 are the covariance matrices 'my data' and 'thy data' divided by N1 and N2 respectively. S is the pooled covar divided by N. */ autoNUMmatrix s1 (1, p, 1, p); autoNUMmatrix s2 (1, p, 1, p); autoNUMmatrix s (1, p, 1, p); for (long i = 1; i <= p; i++) { for (long j = 1; j <= p; j++) { s1[i][j] = my data[i][j] / my numberOfObservations; s2[i][j] = thy data[i][j] / thy numberOfObservations; s[i][j] = s1[i][j] + s2[i][j]; } } double lndet; NUMlowerCholeskyInverse (s.peek(), p, &lndet); // Krishan... formula 2, page 162 double hotelling_tsq = NUMmahalanobisDistance_chi (s.peek(), my centroid, thy centroid, p, p); autoNUMmatrix si (NUMinverseFromLowerCholesky (s.peek(), p), 1, 1); double tr_s1sisqr = traceOfSquaredMatrixProduct (s1.peek(), si.peek(), p); double tr_s1si = NUMtrace2 (s1.peek(), si.peek(), p); double tr_s2sisqr = traceOfSquaredMatrixProduct (s2.peek(), si.peek(), p); double tr_s2si = NUMtrace2 (s2.peek(), si.peek(), p); double nu = (p + p * p) / ( (tr_s1sisqr + tr_s1si * tr_s1si) / n1 + (tr_s2sisqr + tr_s2si * tr_s2si) / n2); *df2 = nu - p + 1; *fisher = hotelling_tsq * (nu - p + 1) / (nu * p); } *prob = NUMfisherQ (*fisher, *df1, *df2); return dif; } /* Schott 2001 */ void Covariances_equality (Collection me, int method, double *prob, double *chisq, double *df) { try { long nc = my size; double nsi = 0; *prob = *chisq = *df = NUMundefined; if (nc < 2) { Melder_throw ("We need at least two matrices"); } long p = 1, ns = 0; for (long i = 1; i <= nc; i++) { Covariance ci = (Covariance) my item[i]; double ni = ci -> numberOfObservations - 1; if (i == 1) { p = ci -> numberOfRows; } if (ci -> numberOfRows != p) { Melder_throw ("The dimensions of matrix ", i, " differ from the previous one(s)."); } if (ni < p) { Melder_throw ("The number of observations in matrix ", i, " is less than the number of variables. "); } ns += ni; nsi += 1.0 / ni; } autoNUMmatrix s (1, p, 1, p); for (long i = 1; i <= nc; i++) { // pool Covariance ci = (Covariance) my item[i]; double sf = (ci -> numberOfObservations - 1.0) / ns; for (long j = 1; j <= p; j++) { for (long k = 1; k <= p; k++) { s[j][k] += sf * ci -> data[j][k]; } } } if (method == 1) { // bartlett double lnd; try { NUMdeterminant_cholesky (s.peek(), p, &lnd); } catch (MelderError) { Melder_throw ("Pooled covariance matrix is singular."); } double m = ns * lnd; for (long i = 1; i <= nc; i++) { Covariance ci = (Covariance) my item[i]; try { NUMdeterminant_cholesky (ci -> data, p, &lnd); } catch (MelderError) { Melder_throw ("Covariance matrix ", i, " is singular."); } m -= (ci -> numberOfObservations - 1) * lnd; } double c1 = 1.0 - (2.0 * p * p - 3 * p - 1) / (6.0 * (p + 1) * (nc - 1)) * (nsi - 1 / ns); *df = (nc - 1) * p * (p + 1) / 2; *chisq = m * c1; } else if (method == 2) { // Schott (2001) Wald 1 // sum(i, ni/n *tr((si*s^-1)^2)- sum(i,sum(j, (ni/n)*(nj/n) *tr(si*s^-1*sj*s^-1))) = // sum(i=1..k, (ni/n -(ni/n)^2) tr((si*s^-1)^2) // - 2 * sum (i=1..k, sum(j=1..i-1, (ni/n)*(nj/n) *tr(si*s^-1*sj*s^-1))) double trace = 0; NUMlowerCholeskyInverse (s.peek(), p, NULL); autoNUMmatrix si (NUMinverseFromLowerCholesky (s.peek(), p), 1, 1); for (long i = 1; i <= nc; i++) { Covariance ci = (Covariance) my item[i]; double ni = ci -> numberOfObservations - 1; autoNUMmatrix s1 (productOfSquareMatrices (ci -> data, si.peek(), p), 1, 1); double trace_ii = NUMtrace2 (s1.peek(), s1.peek(), p); trace += (ni / ns) * (1 - (ni / ns)) * trace_ii; for (long j = i + 1; j <= nc; j++) { Covariance cj = (Covariance) my item[j]; double nj = cj -> numberOfObservations - 1; autoNUMmatrix s2 (productOfSquareMatrices (cj -> data, si.peek(), p), 1, 1); double trace_ij = NUMtrace2 (s1.peek(), s2.peek(), p); trace -= 2 * (ni / ns) * (nj / ns) * trace_ij; } } *df = (nc - 1) * p * (p + 1) / 2; *chisq = (ns / 2) * trace; } else { return; } *prob = NUMchiSquareQ (*chisq, *df); } catch (MelderError) { Melder_throw ("Equality coud not be tested."); } } void Covariance_difference (Covariance me, Covariance thee, double *prob, double *chisq, long *ndf) { long p = my numberOfRows; long numberOfObservations = my numberOfObservations; double ln_me, ln_thee; if (my numberOfRows != thy numberOfRows) { Melder_throw ("Matrices must have equal dimensions."); } if (my numberOfObservations != thy numberOfObservations) { numberOfObservations = (my numberOfObservations > thy numberOfObservations ? thy numberOfObservations : my numberOfObservations) - 1; Melder_warning (L"Covariance_difference: number of observations of matrices do not agree.\n" " The minimum size (", Melder_integer (numberOfObservations), L") of the two is used."); } if (numberOfObservations < 2) { Melder_throw ("Number of observations too small."); } autoNUMmatrix linv (NUMmatrix_copy (thy data, 1, p, 1, p), 1, 1); NUMlowerCholeskyInverse (linv.peek(), p, & ln_thee); NUMdeterminant_cholesky (my data, p, &ln_me); /* We need trace (A B^-1). We have A and the inverse L^(-1) of the cholesky decomposition L^T L of B in the lower triangle + diagonal. Always: tr (A B) = tr (B A) tr (A B^-1) = tr (A (L L^T)^-1) = tr (A L^-1 (L^T)^-1) trace = sum(i=1..p, j=1..p, l=max(i,j)..p, A[i][j]Lm[l][j]Lm[l][i], where Lm = L^(-1) */ double trace = 0; for (long i = 1; i <= p; i++) { for (long j = 1; j <= p; j++) { long lp = MAX (j, i); for (long l = lp; l <= p; l++) { trace += my data[i][j] * linv[l][j] * linv[l][i]; } } } double l = (numberOfObservations - 1) * fabs (ln_thee - ln_me + trace - p); *chisq = l * fabs (1 - (2 * p + 1 - 2 / (p + 1)) / (numberOfObservations - 1) / 6); *ndf = p * (p + 1) / 2; *prob = NUMchiSquareQ (*chisq, *ndf); } static void checkOneIndex (TableOfReal me, long index) { if (index < 1 || index > my numberOfColumns) { Melder_throw ("Index must be in interval [1, ", my numberOfColumns, "]."); } } static void checkTwoIndices (TableOfReal me, long index1, long index2) { if (index1 < 1 || index1 > my numberOfColumns || index2 < 1 || index2 > my numberOfColumns) { Melder_throw ("Index must be in interval [1, ", my numberOfColumns, "]."); } if (index1 == index2) { Melder_throw ("Indices must be different."); } } void Covariance_getSignificanceOfOneMean (Covariance me, long index, double mu, double *probability, double *t, double *ndf) { double var; *probability = *t = NUMundefined; *ndf = my numberOfObservations - 1; checkOneIndex (me, index); if ( (var = my data[index][index]) == 0) { return; } *t = (my centroid[index] - mu) / sqrt (var / my numberOfObservations); *probability = 2 * NUMstudentQ (fabs (*t), *ndf); } void Covariance_getSignificanceOfMeansDifference (Covariance me, long index1, long index2, double mu, int paired, int equalVariances, double *probability, double *t, double *ndf) { long n = my numberOfObservations; double df, var1, var2, var_pooled; *probability = *t = NUMundefined; *ndf = 2 * (n - 1); checkTwoIndices (me, index1, index2); var1 = my data[index1][index1]; var2 = my data[index2][index2]; var_pooled = var1 + var2; if (var_pooled == 0) { Melder_warning (L"The pooled variance turned out to be zero. Check your data. "); return; } if (paired) { var_pooled -= 2 * my data[index1][index2]; *ndf /= 2; } if (var_pooled == 0) { Melder_warning (L"The pooled variance with the paired correction turned out to be zero. "); *probability = 0; return; } *t = (my centroid[index1] - my centroid[index2] - mu) / sqrt (var_pooled / n); /* Return two sided probabilty. */ if (equalVariances) { *probability = 2 * NUMstudentQ (fabs (*t), *ndf); } else { df = (1 + 2 * var1 * var2 / (var1 * var1 + var2 * var2)) * (n - 1); *probability = NUMincompleteBeta (df / 2, 0.5, df / (df + (*t) * (*t))); *ndf = df; } } void Covariance_getSignificanceOfOneVariance (Covariance me, long index, double sigmasq, double *probability, double *chisq, long *ndf) { double var; *probability = *chisq = NUMundefined; *ndf = my numberOfObservations - 1; checkOneIndex (me, index); if ( (var = my data[index][index]) == 0) { return; } *chisq = *ndf; if (sigmasq != 0) { *chisq = *ndf * var / sigmasq; } *probability = NUMchiSquareQ (*chisq, *ndf); } void Covariance_getSignificanceOfVariancesRatio (Covariance me, long index1, long index2, double ratio, double *probability, double *f, long *ndf) { long n = my numberOfObservations; double var1, var2, ratio2; *ndf = n - 1; *probability = *f = NUMundefined; checkTwoIndices (me, index1, index2); var1 = my data[index1][index1]; var2 = my data[index2][index2]; if (var1 == 0 || var2 == 0) { return; } *f = ratio2 = (var1 / var2) / ratio; if (var2 > var1) { ratio2 = (var2 / var1) * ratio; } *probability = 2 * NUMfisherQ (ratio2, *ndf, *ndf); if (*probability > 1) { *probability = 2 - *probability; } } TableOfReal Correlation_confidenceIntervals (Correlation me, double confidenceLevel, long numberOfTests, int method) { try { long m_bonferroni = my numberOfRows * (my numberOfRows - 1) / 2; if (confidenceLevel <= 0 || confidenceLevel > 1) { Melder_throw ("Confidence level must be in interval (0-1)."); } if (my numberOfObservations < 5) { Melder_throw ("The number of observations must be greater than 4."); } if (numberOfTests < 0) { Melder_throw ("The \"number of tests\" cannot be less than zero."); } else if (numberOfTests == 0) { numberOfTests = m_bonferroni; } if (numberOfTests > m_bonferroni) { Melder_warning (L"The \"number of tests\" exceeds the number of elements in the Correlation object."); } autoTableOfReal thee = TableOfReal_create (my numberOfRows, my numberOfRows); TableOfReal_copyLabels (me, thee.peek(), 1, 1); // Obtain large-sample conservative multiple tests and intervals by the // Bonferroni inequality and the Fisher z transformation. // Put upper value of confidence intervals in upper part and lower // values of confidence intervals in lower part of resulting table. double z = NUMinvGaussQ ( (1 - confidenceLevel) / (2 * numberOfTests)); double zf = z / sqrt (my numberOfObservations - 3); double two_n = 2 * my numberOfObservations; for (long i = 1; i <= my numberOfRows; i++) { for (long j = i + 1; j <= my numberOfRows; j++) { double rij = my data[i][j], rmin, rmax; if (method == 2) { // Fisher's approximation double zij = 0.5 * log ( (1 + rij) / (1 - rij)); rmax = tanh (zij + zf); rmin = tanh (zij - zf); } else if (method == 1) { // Ruben's approximation double rs = rij / sqrt (1 - rij * rij); double a = two_n - 3 - z * z; double b = rs * sqrt ( (two_n - 3) * (two_n - 5)); double c = (a - 2) * rs * rs - 2 * z * z; // Solve: a y^2 - 2b y + c = 0 // q = -0.5((-2b) + sgn(-2b) sqrt((-2b)^2 - 4ac)) // y1 = q/a; y2 = c/q; double q, d = sqrt (b * b - a * c); if (b > 0) { d = - d; } q = b - d; rmin = q / a; rmin /= sqrt (1 + rmin * rmin); rmax = c / q; rmax /= sqrt (1 + rmax * rmax); if (rmin > rmax) { double t = rmin; rmin = rmax; rmax = t; } } else { rmax = rmin = 0; } thy data[i][j] = rmax; thy data[j][i] = rmin; } thy data[i][i] = 1; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": confidence intervals not created."); } } void SSCP_testDiagonality_bartlett (SSCP me, long numberOfContraints, double *chisq, double *probability) { *chisq = *probability = NUMundefined; autoCorrelation c = SSCP_to_Correlation (me); Correlation_testDiagonality_bartlett (c.peek(), numberOfContraints, chisq, probability); } /* Morrison, page 118 */ void Correlation_testDiagonality_bartlett (Correlation me, long numberOfContraints, double *chisq, double *probability) { *chisq = *probability = NUMundefined; if (numberOfContraints <= 0) { numberOfContraints = 1; } if (numberOfContraints > my numberOfObservations) { Melder_warning (L"Correlation_testDiagonality_bartlett: number of constraints cannot exceed the number of observations."); return; } long p = my numberOfRows; double ln_determinant; NUMdeterminant_cholesky (my data, p, &ln_determinant); *chisq = - ln_determinant * (my numberOfObservations - numberOfContraints - (2 * p + 5) / 6); *probability = NUMchiSquareQ (*chisq, p * (p - 1) / 2); } void SSCP_expand (I) { iam (SSCP); // A reduced matrix has my numberOfRows < my numberOfColumns. // After expansion: // my numberOfRows == my numberOfColumns // my storageNumberOfRows = my numberOfRows (before) // my data (after) = my expansion; // my expansion = my data (before) // No expansion for a standard matrix or if already expanded and data has not changed! if ( (my expansionNumberOfRows == 0 && my numberOfRows == my numberOfColumns) || (my expansionNumberOfRows > 0 && ! my dataChanged)) { return; } if (my expansion == 0) { my expansion = NUMmatrix (1, my numberOfColumns, 1, my numberOfColumns); } for (long ir = 1; ir <= my numberOfColumns; ir++) { for (long ic = ir; ic <= my numberOfColumns; ic++) { long dij = abs (ir - ic); my expansion[ir][ic] = my expansion[ic][ir] = dij < my numberOfRows ? my data[dij + 1][ic] : 0; } } // Now make 'my data' point to 'my expansion' double **tmp = my data; my data = my expansion; my expansion = tmp; my expansionNumberOfRows = my numberOfRows; my numberOfRows = my numberOfColumns; // Now forget(me) is save my dataChanged = 0; } void SSCP_unExpand (I) { iam (SSCP); if (my expansionNumberOfRows == 0) { return; } NUMmatrix_free (my data, 1, 1); my data = my expansion; my expansion = 0; my numberOfRows = my expansionNumberOfRows; my expansionNumberOfRows = 0; my dataChanged = 0; } void SSCP_expandLowerCholesky (I) { iam (SSCP); if (my lowerCholesky == 0) { my lowerCholesky = NUMmatrix (1, my numberOfRows, 1, my numberOfColumns); } if (my numberOfRows == 1) { // diagonal my lnd = 0; for (long j = 1; j <= my numberOfColumns; j++) { my lowerCholesky[1][j] = 1 / sqrt (my data[1][j]); // inverse is 1/stddev my lnd += log (my data[1][j]); // diagonal elmnt is variance } } else { for (long i = 1; i <= my numberOfRows; i++) { for (long j = i; j <= my numberOfColumns; j++) { my lowerCholesky[j][i] = my lowerCholesky[i][j] = my data[i][j]; } } try { NUMlowerCholeskyInverse (my lowerCholesky, my numberOfColumns, & (my lnd)); } catch (MelderError) { // singular matrix: arrange a diagonal only inverse. my lnd = 0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = i; j <= my numberOfColumns; j++) { my lowerCholesky[i][j] = my lowerCholesky[j][i] = i == j ? 1. / sqrt (my data[i][i]) : 0; } my lnd += log (my data[i][i]); } my lnd *= 2; } } } void SSCP_unExpandLowerCholesky (I) { iam (SSCP); NUMmatrix_free (my lowerCholesky, 1, 1); my lnd = 0; } void SSCP_expandPCA (I) { iam (SSCP); if (my pca != 0) { forget (my pca); } my pca = SSCP_to_PCA (me); } void SSCP_unExpandPCA (I) { iam (SSCP); forget (my pca); } #undef MAX #undef MIN /* End of file SSCP.c 2148*/ sources_5316/dwtools/CCs_to_DTW.h0000664000176700017670000000322611723710247015470 0ustar paulpaul#ifndef _CCs_to_DTW_h_ #define _CCs_to_DTW_h_ /* CCs_to_DTW.h * * Dynamic Time Warp of two CCs. * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020315 GPL header */ #include "CC.h" #include "DTW.h" DTW CCs_to_DTW (I, thou, double wc, double wle, double wr, double wer, double dtr); /* 1. Calculate distances between CCs: Distance between frame i (from me) and j (from thee) is wc * d1 + wle * d2 + wr * d3 + wer * d4, where wc, wle, wr & wer are weights and d1 = Sum (k=1; k=nCoefficients; (c[i,k]-c[j,k])^2) d2 = (c[0,k]-c[0,k])^2 d3 = Sum (k=1; k=nCoefficients; (r[i,k]-r[j,k])^2), with r[i,k] the regression coefficient of the cepstral coefficients from the frames within a time span of 'dtr' seconds. c[i,j] is jth cepstral coefficient in frame i. d4 = regression on energy (c[0]) 2. Find optimum path through the distance matrix (see DTW). PRECONDITIONS: at least one of wc, wle, wr, wer != 0 */ #endif /* _CCs_to_DTW_h_ */ sources_5316/dwtools/Discriminant_Pattern_Categories.h0000644000176700017670000000266211535130316022061 0ustar paulpaul#ifndef _Discriminant_Pattern_Categories_h_ #define _Discriminant_Pattern_Categories_h_ /* Discriminant_Pattern_Categories.h * * Copyright (C) 2004-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20040422 Initial version djmw 20110307 Latest modification */ #ifndef _Discriminant_h_ #include "Discriminant.h" #endif #ifndef _Pattern_h_ #include "Pattern.h" #endif #ifndef _Categories_h_ #include "Categories.h" #endif #ifdef __cplusplus extern "C" { #endif Discriminant Pattern_and_Categories_to_Discriminant (Pattern me, Categories thee); Categories Discriminant_and_Pattern_to_Categories (Discriminant me, Pattern thee, int poolCovarianceMatrices,int useAprioriProbabilities); #ifdef __cplusplus } #endif #endif /* _Discriminant_Pattern_Categories_h_ */ sources_5316/dwtools/Spectrum_extensions.cpp0000644000176700017670000002065011634154426020214 0ustar paulpaul/* Spectrum_extensions.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010718 djmw 20020813 GPL header djmw 20030929 Added a warning in Spectrum_drawPhases. djmw 20031023 New: Spectra_multiply, Spectrum_conjugate djmw 20040506 Changed warning message in Spectrum_drawPhases. djmw 20041124 Changed call to Sound_to_Spectrum. djmw 20061218 Introduction of Melder_information<12...9> djmw 20071022 phase_unwrap initialize phase = 0. djmw 20080122 float -> double djmw 20080202 Warning in Spectrum_drawPhases to wchar_t djmw 20080411 Removed define NUM2pi */ #include "Spectrum_extensions.h" #include "Sound_and_Spectrum.h" #include "NUM2.h" #define SIGN(x,s) ((s) < 0 ? -fabs (x) : fabs(x)) #define THLCON 0.5 #define THLINC 1.5 #define EXP2 12 #define PPVPHA(x,y,test) ((test) ? atan2 (-(y),-(x)) : atan2 ((y),(x))) #define PHADVT(xr,xi,yr,yi,xa) ((xa) > 0 ? ((xr)*(yr)+(xi)*(yi))/ (xa) : 0) struct tribolet_struct { double thlinc, thlcon; double ddf, dvtmn2; double *x; long nx, l, count; int reverse_sign; }; /* Perform modified Goertzel algorithm to calculate, at frequency 'freq_rad', the real and imaginary part of the spectrum and the d/df of the spectrum of x. Reference: Bonzanigo (1978), IEEE Trans. ASSP, Vol. 26. */ static void getSpectralValues (struct tribolet_struct *tbs, double freq_rad, double *xr, double *xi, double *nxr, double *nxi) { double cosf = cos (freq_rad), sinf = sin (freq_rad); double a = 2 * cosf, b, u1 = 0, u2 = u1, w1 = u1, w2 = u1; double *x = tbs -> x; long nx = tbs -> nx; for (long j = 1; j <= nx; j++) { double xj = x[j]; double u0 = xj + a * u1 - u2; double w0 = (j - 1) * xj + a * w1 - w2; u2 = u1; u1 = u0; w2 = w1; w1 = w0; } /* Bonzanigo's phase correction */ a = freq_rad * (nx - 1); u1 = cos (a); u2 = - sin (a); a = u1 - u2 * cosf; b = u2 * sinf; *xr = u1 * a - u2 * b; *xi = u2 * a + u1 * b; a = w1 - w2 * cosf; b = w2 * sinf; *nxr = u1 * a - u2 * b; *nxi = u2 * a + u1 * b; tbs -> count ++; } /* Find the closest unwrapped phase estimate from the two admissible phase values (a1 & a2). */ static int phase_check (double pv, double *phase, double thlcon) { double a0 = (*phase - pv) / NUM2pi; long k = a0; double a1 = pv + k * NUM2pi; double a2 = a1 + SIGN (NUM2pi, a0); double a3 = fabs (a1 - *phase); double a4 = fabs (a2 - *phase); if (a3 > thlcon && a4 > thlcon) { return 0; } *phase = a3 > a4 ? a2 : a1; return 1; } /* Phase unwrapping based on Tribolet's adaptive integration method. the unwrapped phase estimate is returned. */ static double phase_unwrap (struct tribolet_struct *tbs, double pfreq, double ppv, double pdvt, double *pphase, double *ppdvt) { double sdvt[25], sppv[25]; double freq, phase = 0, phase_inc; double delta, xr, xi, xmsq, nxr, nxi; long k, sindex[25], pindex = 1, sp = 1; sppv[sp] = ppv; sdvt[sp] = pdvt; sindex[sp] = tbs -> l + 1; goto p40; p20: /* When the routine runs out of stack space, there probably is a zero very near the unit circle that results in a jump of pi in the phase. */ if ( (sindex[sp] - pindex) <= 1) { return phase; } /* p30: Get the intermediate frequency value and compute its phase derivative and principal value. */ k = (sindex[sp] + pindex) / 2; freq = pfreq + (k - 1) * tbs -> ddf; getSpectralValues (tbs, freq, &xr, &xi, &nxr, &nxi); sindex[++sp] = k; sppv[sp] = PPVPHA (xr, xi, tbs -> reverse_sign); xmsq = xr * xr + xi * xi; sdvt[sp] = PHADVT (xr, xi, nxr, nxi, xmsq); p40: /* Evaluate the phase increment. If the phase increment, reduced by the expected linear phase increment, is greater than the specified threshold, adapt step size. */ delta = 0.5 * tbs -> ddf * (sindex[sp] - pindex); phase_inc = delta * (*ppdvt + sdvt[sp]); if (fabs (phase_inc - delta * tbs -> dvtmn2) > tbs -> thlinc) { goto p20; } phase = *pphase + phase_inc; if (! phase_check (sppv[sp], &phase, tbs -> thlcon)) { goto p20; } if (fabs (phase - *pphase) > NUMpi) { goto p20; } if (sp == 1) { return phase; } /* p10: Update previous estimate. */ pindex = sindex[sp]; *pphase = phase; *ppdvt = sdvt[sp--]; goto p40; } Matrix Spectrum_unwrap (Spectrum me) { try { struct tribolet_struct tbs; int remove_linear_part = 1; long nfft = 2; while (nfft < my nx - 1) { nfft *= 2; } nfft *= 2; if (nfft / 2 != my nx - 1) { Melder_throw ("Dimension of Spectrum is not (power of 2 - 1)."); } autoSound x = Spectrum_to_Sound (me); autoSound nx = Data_copy (x.peek()); for (long i = 1; i <= x -> nx; i++) { nx -> z[1][i] *= (i - 1); } autoSpectrum snx = Sound_to_Spectrum (nx.peek(), 1); autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 1, 2, 2, 1, 1); // Common variables. tbs.thlinc = THLINC; tbs.thlcon = THLCON; tbs.x = x -> z[1]; tbs.nx = x -> nx; tbs.l = (pow (2, EXP2) + 0.1); tbs.ddf = NUM2pi / ( (tbs.l) * nfft); tbs.reverse_sign = my z[1][1] < 0; tbs.count = 0; // Reuse snx : put phase derivative (d/df) in imaginary part. tbs.dvtmn2 = 0; for (long i = 1; i <= my nx; i ++) { double xr = my z[1][i], xi = my z[2][i]; double nxr = snx -> z[1][i], nxi = snx -> z[2][i]; double xmsq = xr * xr + xi * xi; double pdvt = PHADVT (xr, xi, nxr, nxi, xmsq); thy z[1][i] = xmsq; snx -> z[2][i] = pdvt; tbs.dvtmn2 += pdvt; } tbs.dvtmn2 = (2 * tbs.dvtmn2 - snx -> z[2][1] - snx -> z[2][my nx]) / (my nx - 1); autoMelderProgress progress (L"Phase unwrapping"); double pphase = 0, phase = 0; double ppdvt = snx -> z[2][1]; thy z[2][1] = PPVPHA (my z[1][1], my z[2][1], tbs.reverse_sign); for (long i = 2; i <= my nx; i ++) { double pfreq = NUM2pi * (i - 1) / nfft; double pdvt = snx -> z[2][i]; double ppv = PPVPHA (my z[1][i], my z[2][i], tbs.reverse_sign); phase = phase_unwrap (&tbs, pfreq, ppv, pdvt, &pphase, &ppdvt); ppdvt = pdvt; thy z[2][i] = pphase = phase; Melder_progress ( (double) i / my nx, Melder_integer (i), L" unwrapped phases from ", Melder_integer (my nx), L"."); therror } long iphase = (phase / NUMpi + 0.1); if (remove_linear_part) { phase /= my nx - 1; for (long i = 2; i <= my nx; i ++) { thy z[2][i] -= phase * (i - 1); } } Melder_information (L"Number of spectral values: ", Melder_integer (tbs.count)); Melder_information (L" iphase = ", Melder_integer (iphase)); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not unwrapped."); } } void Spectrum_drawPhases (Spectrum me, Graphics g, double fmin, double fmax, double phase_min, double phase_max, int unwrap, int garnish) { autoMatrix thee = 0; int reverse_sign = my z[1][1] < 0; if (unwrap) { thee.reset (Spectrum_unwrap (me)); } else { thee.reset (Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 1, 2, 2, 1, 1)); for (long i = 1; i <= my nx; i ++) { thy z[2][i] = PPVPHA (my z[1][i], my z[2][i], reverse_sign); } } Matrix_drawRows (thee.peek(), g, fmin, fmax, 1.9, 2.1, phase_min, phase_max); if (garnish) { } } Spectrum Spectra_multiply (Spectrum me, Spectrum thee) { try { if (my nx != thy nx || my x1 != thy x1 || my xmax != thy xmax || my dx != thy dx) { Melder_throw ("Dimensions of both spectra do not conform."); } autoSpectrum him = Data_copy (me); for (long i = 1; i <= his nx; i++) { his z[1][i] = my z[1][i] * thy z[1][i] - my z[2][i] * thy z[2][i]; his z[2][i] = my z[1][i] * thy z[2][i] + my z[2][i] * thy z[1][i]; } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not multiplied."); } } void Spectrum_conjugate (Spectrum me) { for (long i = 1; i <= my nx; i++) { my z[2][i] = - my z[2][i]; } } /* End of file Spectrum_extensions.cpp */ sources_5316/dwtools/Sound_to_MFCC.h0000644000176700017670000000223711607123040016147 0ustar paulpaul#ifndef _Sound_to_MFCC_h_ #define _Sound_to_MFCC_h_ /* Sound_to_MFCC.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010410 djmw 20020813 GPL header djmw 20110307 Latest modification */ #include "MFCC.h" #include "Sound.h" #ifdef __cplusplus extern "C" { #endif MFCC Sound_to_MFCC (Sound me, long numberOfCoefficients, double analysisWidth, double dt, double f1_mel, double fmax_mel, double df_mel); #ifdef __cplusplus } #endif #endif /* _Sound_to_MFCC_h_ */ sources_5316/dwtools/AffineTransform.cpp0000644000176700017670000000734511725071311017215 0ustar paulpaul/* AffineTransform.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020315 GPL header djmw 20041027 Added AffineTransform_extractMatrix djmw 20050726 Added AffineTransform_extractTranslationVector djmw 20061021 printf expects %ld for 'long int' djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20110304 Thing_new */ #include "AffineTransform.h" #include "NUM2.h" #include "oo_DESTROY.h" #include "AffineTransform_def.h" #include "oo_COPY.h" #include "AffineTransform_def.h" #include "oo_EQUAL.h" #include "AffineTransform_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "AffineTransform_def.h" #include "oo_WRITE_TEXT.h" #include "AffineTransform_def.h" #include "oo_WRITE_BINARY.h" #include "AffineTransform_def.h" #include "oo_READ_TEXT.h" #include "AffineTransform_def.h" #include "oo_READ_BINARY.h" #include "AffineTransform_def.h" #include "oo_DESCRIPTION.h" #include "AffineTransform_def.h" void structAffineTransform :: v_transform (double **in, long nrows, double **out) { for (long i = 1; i <= nrows; i++) { for (long j = 1; j <= n; j++) { double tmp = 0; for (long k = 1; k <= n; k++) { tmp += in[i][k] * r[k][j]; } out[i][j] = tmp + t[j]; } } } Any structAffineTransform :: v_invert () { autoAffineTransform thee = Data_copy (this); double tolerance = 0.000001; NUMpseudoInverse (r, n, n, thy r, tolerance); therror for (long i = 1; i <= n; i++) { thy t[i] = 0; for (long j = 1; j <= thy n; j++) { thy t[i] -= thy r[i][j] * t[j]; } } return thee.transfer(); } Thing_implement (AffineTransform, Data, 0); void AffineTransform_init (I, long n) { iam (AffineTransform); if (n < 1) { Melder_throw ("Dimensionality must be at least 1."); } my n = n; my r = NUMmatrix (1, n, 1, n); my t = NUMvector (1, n); } AffineTransform AffineTransform_create (long n) { try { autoAffineTransform me = Thing_new (AffineTransform); AffineTransform_init (me.peek(), n); return me.transfer(); } catch (MelderError) { Melder_throw ("AffineTransform not created."); } } Any AffineTransform_invert (I) { iam (AffineTransform); AffineTransform thee = (AffineTransform) my v_invert (); return thee; } TableOfReal AffineTransform_extractMatrix (I) { iam (AffineTransform); try { autoTableOfReal thee = TableOfReal_create (my n, my n); NUMmatrix_copyElements (my r, thy data, 1, my n, 1, my n); for (long i = 1; i <= my n; i++) { wchar_t label[20]; (void) swprintf (label, 20, L"%ld", i); TableOfReal_setRowLabel (thee.peek(), i, label); TableOfReal_setColumnLabel (thee.peek(), i, label); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": transformation matrix not extracted."); } } TableOfReal AffineTransform_extractTranslationVector (I) { iam (AffineTransform); try { autoTableOfReal thee = TableOfReal_create (1, my n); for (long i = 1; i <= my n; i++) { thy data[1][i] = my t[i]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": translation vector not extracted."); } } /* End of file AffineTransform.cpp */ sources_5316/dwtools/Sounds_to_DTW.cpp0000664000176700017670000000327111723710247016626 0ustar paulpaul/* Sounds_to_DTW.cpp * * Copyright (C) 2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20120221 */ #include "Sound_to_MFCC.h" #include "Sounds_to_DTW.h" #include "CCs_to_DTW.h" DTW Sounds_to_DTW (Sound me, Sound thee, double analysisWidth, double dt, double band, int slope) { try { long numberOfCoefficients = 12; double fmin_mel = 100, df_mel = 100, fmax_mel = 0.0; autoMFCC mfcc_me = Sound_to_MFCC (me, numberOfCoefficients, analysisWidth, dt, fmin_mel, fmax_mel, df_mel); autoMFCC mfcc_thee = Sound_to_MFCC (thee, numberOfCoefficients, analysisWidth, dt, fmin_mel, fmax_mel, df_mel); double wc = 1, wle = 0, wr = 0, wer = 0, dtr = 0; autoDTW him = CCs_to_DTW (mfcc_me.peek(), mfcc_thee.peek(), wc, wle, wr, wer, dtr); autoPolygon p = DTW_to_Polygon (him.peek(), band, slope); DTW_and_Polygon_findPathInside (him.peek(), p.peek(), slope, 0); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no DTW created."); } } /* End of file Sounds_to_DTW.cpp */ sources_5316/dwtools/SpeechSynthesizer_and_TextGrid.cpp0000664000176700017670000011141411755507106022250 0ustar paulpaul/* SpeechSynthesizer_and_TextGrid.cpp * * Copyright (C) 2011-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20111214 */ #include "DTW.h" #include "Sounds_to_DTW.h" #include "Sound_extensions.h" #include "SpeechSynthesizer_and_TextGrid.h" #include "CCs_to_DTW.h" #include "DTW_and_TextGrid.h" #include "NUMmachar.h" // prototypes void IntervalTier_splitInterval (IntervalTier me, double time, const wchar_t *leftLabel, long interval, double precision); IntervalTier IntervalTier_and_IntervalTier_cutPartsMatchingLabel (IntervalTier me, IntervalTier thee, const wchar_t *label, double precision); IntervalTier IntervalTiers_patch_noBoundaries (IntervalTier me, IntervalTier thee, const wchar_t *patchLabel, double precision); TextGrid SpeechSynthesizer_and_Sound_and_IntervalTier_align2 (SpeechSynthesizer me, Sound thee, IntervalTier him, long istart, long iend, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double trimDuration); Table IntervalTiers_to_Table_textAlignmentment (IntervalTier target, IntervalTier source, EditCostsTable costs); Sound SpeechSynthesizer_and_TextInterval_to_Sound (SpeechSynthesizer me, TextInterval thee, TextGrid *tg) { try { if (thy text == NULL || thy text[0] == '\0') { Melder_throw ("No text in TextInterval."); } autoSound him = SpeechSynthesizer_to_Sound (me, thy text, tg, NULL); return him.transfer(); } catch (MelderError) { Melder_throw ("Sound not created from TextInterval."); } } Sound SpeechSynthesizer_and_TextGrid_to_Sound (SpeechSynthesizer me, TextGrid thee, long tierNumber, long iinterval, TextGrid *tg) { try { TextGrid_checkSpecifiedTierNumberWithinRange (thee, tierNumber); IntervalTier intervalTier = (IntervalTier) thy tiers -> item [tierNumber]; if (intervalTier -> classInfo != classIntervalTier) { Melder_throw ("Tier ", tierNumber, " is not an interval tier."); } if (iinterval < 1 || iinterval > intervalTier -> intervals -> size) { Melder_throw ("Interval ", iinterval, " does not exist on tier ", tierNumber, "."); } return SpeechSynthesizer_and_TextInterval_to_Sound (me, (TextInterval) intervalTier -> intervals -> item[iinterval], tg); } catch (MelderError) { Melder_throw ("Sound not created from textGrid."); } } static double TextGrid_getStartTimeOfFirstOccurence (TextGrid thee, long tierNumber, const wchar_t *label) { TextGrid_checkSpecifiedTierNumberWithinRange (thee, tierNumber); IntervalTier intervalTier = (IntervalTier) thy tiers -> item [tierNumber]; if (intervalTier -> classInfo != classIntervalTier) { Melder_throw ("Tier ", tierNumber, " is not an interval tier."); } double start = NUMundefined; for (long iint = 1; iint <= intervalTier -> intervals -> size; iint++) { TextInterval ti = (TextInterval) intervalTier -> intervals -> item[iint]; if (Melder_wcscmp (ti -> text, label) == 0) { start = ti -> xmin; break; } } return start; } static double TextGrid_getEndTimeOfLastOccurence (TextGrid thee, long tierNumber, const wchar_t *label) { TextGrid_checkSpecifiedTierNumberWithinRange (thee, tierNumber); IntervalTier intervalTier = (IntervalTier) thy tiers -> item [tierNumber]; if (intervalTier -> classInfo != classIntervalTier) { Melder_throw ("Tier ", tierNumber, " is not an interval tier."); } double end = NUMundefined; for (long iint = intervalTier -> intervals -> size; iint > 0; iint--) { TextInterval ti = (TextInterval) intervalTier -> intervals -> item[iint]; if (Melder_wcscmp (ti -> text, label) == 0) { end = ti -> xmax; break; } } return end; } static void IntervalTier_getLabelInfo (IntervalTier me, const wchar_t *label, double *labelDurations, long *numberOfOccurences) { *labelDurations = 0; *numberOfOccurences = 0; for (long i = 1; i <= my intervals -> size; i++) { TextInterval ti = (TextInterval) my intervals -> item[i]; if (Melder_wcsequ (ti -> text, label)) { *labelDurations += ti -> xmax - ti -> xmin; (*numberOfOccurences)++; } } } #define TIMES_ARE_CLOSE(x,y) (fabs((x)-(y)) < precision) void IntervalTier_splitInterval (IntervalTier me, double time, const wchar_t *leftLabel, long interval, double precision) { try { long index = 0; TextInterval ti = NULL; for (long i = interval; i <= my intervals -> size; i++) { // interval > 0 ti = (TextInterval) my intervals -> item[i]; if (time < ti -> xmax + precision && time > ti -> xmin - precision) { index = i; break; } } // if index == 0 then search left intervals?? if (index == 0 || TIMES_ARE_CLOSE(time, ti -> xmin) || TIMES_ARE_CLOSE(time, ti -> xmax)) { return; } autoTextInterval newInterval = TextInterval_create (ti -> xmin, time, leftLabel); // Make start of current and begin of new interval equal ti -> xmin = time; Collection_addItem (my intervals, newInterval.transfer()); } catch (MelderError) { Melder_throw ("Boundary not inserted."); } } TextTier TextTier_and_IntervalTier_cutPartsMatchingLabel (TextTier me, IntervalTier thee, const wchar_t *label, double precision) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Domains must be equal."); } long myIndex = 1; double timeCut = 0; autoTextTier him = TextTier_create (0, my xmax - my xmin); for (long j = 1; j <= thy intervals -> size; j++) { TextInterval cut = (TextInterval) thy intervals -> item[j]; if (Melder_wcsequ (cut -> text, label)) { timeCut += cut -> xmax - cut -> xmin; } else { while (myIndex <= my points -> size) { TextPoint tp = (TextPoint) my points -> item[myIndex]; if (tp -> number < cut -> xmin - precision) { // point is left of cut myIndex++; } else if (tp -> number < cut -> xmax + precision) { // point is in (no)cut double time = tp -> number - my xmin - timeCut; TextTier_addPoint (him.peek(), time, tp -> mark); myIndex++; } else { break; } } } } his xmax -= timeCut; return him.transfer(); } catch (MelderError) { Melder_throw (me, ": parts not cut."); } } // Cut parts from me marked by labels in thee IntervalTier IntervalTier_and_IntervalTier_cutPartsMatchingLabel (IntervalTier me, IntervalTier thee, const wchar_t *label, double precision) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Domains must be equal."); } autoNUMvector durations (1, my intervals -> size); for (long i = 1; i <= my intervals -> size; i++) { TextInterval ti = (TextInterval) my intervals -> item[i]; durations[i] = ti -> xmax - ti -> xmin; } long myInterval = 1; for (long j = 1; j <= thy intervals -> size; j++) { TextInterval cut = (TextInterval) thy intervals -> item[j]; if (Melder_wcsequ (cut -> text, label)) { // trim while (myInterval <= my intervals -> size) { TextInterval ti = (TextInterval) my intervals -> item[myInterval]; if (ti -> xmin > cut -> xmin - precision && ti -> xmax < cut -> xmax + precision) { // 1. interval completely within cut durations[myInterval] = 0; myInterval++; } else if (ti -> xmin < cut -> xmin + precision && cut -> xmin < ti -> xmax + precision) { // 2. cut start is within interval if (cut -> xmax > ti -> xmax - precision) { // interval end is in cut, interval start before durations[myInterval] -= ti -> xmax - cut -> xmin; myInterval++; } else { // 3. cut completely within interval durations[myInterval] -= cut -> xmax - cut -> xmin; break; } } else if (cut -> xmax > ti -> xmin - precision && cut -> xmin < ti -> xmax + precision) { // +1+2 : cut end is within interval, cut start before durations[myInterval] -= cut -> xmax - ti -> xmin; break; } else if (ti -> xmax < cut -> xmin + precision) { myInterval++; } } } } double totalDuration = 0; for (long i = 1; i <= my intervals -> size; i++) { if (durations[i] < precision) { durations[i] = 0; } totalDuration += durations[i]; } autoIntervalTier him = IntervalTier_create (0, totalDuration); double time = 0; long hisInterval = 1; for (long i = 1; i <= my intervals -> size; i++) { if (durations[i] <= 0) continue; TextInterval ti = (TextInterval) my intervals -> item[i]; time += durations[i]; if (fabs (time - totalDuration) > precision) { IntervalTier_splitInterval (him.peek(), time, ti -> text, hisInterval, precision); hisInterval++; } else { // last interval TextInterval histi = (TextInterval) his intervals -> item[hisInterval]; TextInterval_setText (histi, ti -> text); } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": parts not cut."); } } TextGrid TextGrid_and_IntervalTier_cutPartsMatchingLabel (TextGrid me, IntervalTier thee, const wchar_t *label, double precision) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Domains must be equal."); } double cutDurations = 0; for (long i = 1; i <= thy intervals -> size; i++) { TextInterval cut = (TextInterval) thy intervals -> item[i]; if (Melder_wcsequ (cut -> text, label)) { cutDurations += cut -> xmax - cut -> xmin; } } if (cutDurations <= precision) { // Nothing to patch return (TextGrid) Data_copy (me); } autoTextGrid him = TextGrid_createWithoutTiers (0, thy xmax - thy xmin - cutDurations); for (long itier = 1; itier <= my tiers -> size; itier++) { Function anyTier = (Function) my tiers -> item[itier]; if (anyTier -> classInfo == classIntervalTier) { autoIntervalTier ait = IntervalTier_and_IntervalTier_cutPartsMatchingLabel ((IntervalTier) anyTier, thee, label, precision); Collection_addItem (his tiers, ait.transfer()); } else { autoTextTier att = TextTier_and_IntervalTier_cutPartsMatchingLabel ((TextTier) anyTier, thee, label, precision); Collection_addItem (his tiers, att.transfer()); } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no parts cut."); } } // Patch thy intervals that match patchLabel into my intervals // The resulting IntervalTier has thy xmin as starting time and thy xmax as end time IntervalTier IntervalTiers_patch_noBoundaries (IntervalTier me, IntervalTier thee, const wchar_t *patchLabel, double precision) { try { autoNUMvector durations (0L, my intervals -> size + 1); for (long i = 1; i <= my intervals -> size; i++) { TextInterval myti = (TextInterval) my intervals -> item[i]; durations[i] = myti -> xmax - myti -> xmin; } long myInterval = 1; double xShift = thy xmin - my xmin; for (long j = 1; j <= thy intervals -> size; j++) { TextInterval patch = (TextInterval) thy intervals -> item[j]; if (Melder_wcsequ (patch -> text, patchLabel)) { if (j == 1) { xShift += durations[0] = patch -> xmax - patch -> xmin; } else if (j == thy intervals -> size) { durations[my intervals -> size + 1] = patch -> xmax - patch -> xmin; } else { while (myInterval <= my intervals -> size) { TextInterval ti = (TextInterval) my intervals -> item[myInterval]; double tixmin = ti -> xmin + xShift; double tixmax = ti -> xmax + xShift; if ((patch -> xmin > tixmin - precision) && (patch -> xmin < tixmax + precision)) { durations[myInterval] += patch -> xmax - patch -> xmin; break; } myInterval++; } } } else { while (myInterval <= my intervals -> size) { TextInterval ti = (TextInterval) my intervals -> item[myInterval]; double tixmax = ti -> xmax + xShift; if (tixmax < patch -> xmin + precision) { myInterval++; } else { break; } } } } autoIntervalTier him = IntervalTier_create (thy xmin, thy xmax); // first interval double time = thy xmin + durations[0]; long hisInterval = 1; if (durations[0] > 0) { IntervalTier_splitInterval (him.peek(), time , L"", hisInterval, precision); hisInterval++; } for (long i = 1; i <= my intervals -> size; i++) { TextInterval ti = (TextInterval) my intervals -> item[i]; time += durations[i]; IntervalTier_splitInterval (him.peek(), time, ti -> text, hisInterval, precision); hisInterval++; } if (durations[my intervals -> size + 1] > 0) { time += durations[my intervals -> size + 1]; IntervalTier_splitInterval (him.peek(), time , L"", hisInterval, precision); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not patched."); } } IntervalTier IntervalTiers_patch (IntervalTier me, IntervalTier thee, const wchar_t *patchLabel, double precision) { try { autoIntervalTier him = IntervalTier_create (thy xmin, thy xmax); long myInterval = 1, hisInterval = 1; double xmax = thy xmin; for (long i = 1; i <= thy intervals -> size; i++) { TextInterval myti, ti = (TextInterval) thy intervals -> item[i]; if (Melder_wcsequ (ti -> text, patchLabel)) { bool splitInterval = false; double endtime, split = 0; if (i > 0) { while (myInterval <= my intervals -> size) { myti = (TextInterval) my intervals -> item[myInterval]; endtime = xmax + myti -> xmax - myti -> xmin; if (endtime <= ti -> xmin + precision) { xmax = endtime; IntervalTier_splitInterval (him.peek(), xmax, myti -> text, hisInterval, precision); hisInterval++; } else { if (xmax < ti -> xmin - precision) { // split interval ??? splitInterval = true; xmax = ti -> xmin; split = endtime - xmax; IntervalTier_splitInterval (him.peek(), xmax, myti -> text, hisInterval, precision); hisInterval ++; myInterval++; } break; } myInterval++; } } xmax += ti -> xmax - ti -> xmin; IntervalTier_splitInterval (him.peek(), xmax, L"", hisInterval, precision); hisInterval++; if (splitInterval) { xmax += split; IntervalTier_splitInterval (him.peek(), xmax, myti -> text, hisInterval, precision); hisInterval ++; } } else if (i == thy intervals -> size) { // copy remaining if last interval doesn't match while (myInterval <= my intervals -> size) { myti = (TextInterval) my intervals -> item[myInterval]; xmax += myti -> xmax - myti -> xmin; IntervalTier_splitInterval (him.peek(), xmax, myti -> text, hisInterval, precision); hisInterval++; myInterval++; } } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not patched."); } } TextTier TextTier_and_IntervalTier_patch (TextTier me, IntervalTier thee, const wchar_t *patchLabel, double precision) { try { long myIndex = 1; autoTextTier him = TextTier_create (thy xmin, thy xmax); double xShift = thy xmin - my xmin; for (long i = 1; i <= thy intervals -> size; i++) { TextInterval ti = (TextInterval) thy intervals -> item[i]; if (Melder_wcsequ (ti -> text, patchLabel)) { if (i > 1) { while (myIndex <= my points -> size) { TextPoint tp = (TextPoint) my points -> item[myIndex]; double time = tp -> number + xShift; if (time < ti -> xmin + precision) { autoTextPoint atp = TextPoint_create (time, tp -> mark); Collection_addItem (his points, atp.transfer()); } else { break; } myIndex++; } } xShift += ti -> xmax - ti -> xmin; } else if (i == thy intervals -> size) { while (myIndex <= my points -> size) { TextPoint tp = (TextPoint) my points -> item[myIndex]; double time = tp -> number + xShift; if (time < ti -> xmin + precision) { autoTextPoint atp = TextPoint_create (time, tp -> mark); Collection_addItem (his points, atp.transfer()); } myIndex++; } } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": cannot patch TextTier."); } } TextGrid TextGrid_and_IntervalTier_patch (TextGrid me, IntervalTier thee, const wchar_t *patchLabel, double precision) { try { double patchDurations; long numberOfPatches; IntervalTier_getLabelInfo (thee, patchLabel, &patchDurations, &numberOfPatches); if (patchDurations <= 0 || my xmax - my xmin >= thy xmax - thy xmin ) { // Nothing to patch return (TextGrid) Data_copy (me); } autoTextGrid him = TextGrid_createWithoutTiers (thy xmin, thy xmax); for (long itier = 1; itier <= my tiers -> size; itier++) { Function anyTier = (Function) my tiers -> item[itier]; if (anyTier -> classInfo == classIntervalTier) { // autoIntervalTier ait = IntervalTiers_patch ((IntervalTier) anyTier, thee, patchLabel, precision); autoIntervalTier ait = IntervalTiers_patch_noBoundaries ((IntervalTier) anyTier, thee, patchLabel, precision); Collection_addItem (his tiers, ait.transfer()); } else { autoTextTier att = TextTier_and_IntervalTier_patch ((TextTier) anyTier, thee, patchLabel, precision); Collection_addItem (his tiers, att.transfer()); } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not patched."); } } // We assume that the Sound and the SpeechSynthesizer have the same samplingFrequency // schakel waarschuwingen over stiltedetectie uit TextGrid SpeechSynthesizer_and_Sound_and_TextInterval_align (SpeechSynthesizer me, Sound thee, TextInterval him, double silenceThreshold, double minSilenceDuration, double minSoundingDuration) { try { if (thy xmin != his xmin || thy xmax != his xmax) { Melder_throw ("Domains of Sound and TextGrid must be equal."); } if (fabs (1.0 / thy dx - my d_samplingFrequency) > NUMfpp -> eps) { Melder_throw ("The sampling frequencies of the SpeechSynthesizer and the Sound must be equal."); } long numberOfTokens = Melder_countTokens (his text); if (numberOfTokens == 0) { Melder_throw ("The interval has no text."); } // Remove silent intervals from start and end of sounds double minPitch = 200, timeStep = 0.005, precision = thy dx; double t1_thee, t2_thee; autoSound s_thee = Sound_trimSilencesAtStartAndEnd (thee, 0.0, minPitch, timeStep, silenceThreshold, minSilenceDuration, minSoundingDuration, &t1_thee, &t2_thee); double s_thee_duration = s_thee -> xmax - s_thee -> xmin; bool hasSilence_thee = fabs (t1_thee - thy xmin) > precision || fabs (t2_thee - thy xmax) > precision; if (my d_estimateWordsPerMinute) { double wordsPerMinute_raw = 60.0 * numberOfTokens / (his xmax - his xmin); double wordsPerMinute = 60.0 * numberOfTokens / s_thee_duration; my d_wordsPerMinute = 0.5 * (wordsPerMinute_raw + wordsPerMinute); } TextGrid tg2 = 0; autoSound s2 = SpeechSynthesizer_and_TextInterval_to_Sound (me, him, &tg2); autoTextGrid atg2 = tg2, s_atg2; /* * For the synthesizer the silence threshold has to be < -30 dB, otherwise fricatives will not * be found as sounding! This is ok since silences are almost at zero amplitudes * We also have to decrease the minimum silence and minimum sounding duration to catch, for example, * the final plosive "t" from the word "text" * */ double s2_silenceThreshold = -40, s2_minSilenceDuration = 0.05, s2_minSoundingDuration = 0.05; double t1_s2, t2_s2; autoSound s_s2 = Sound_trimSilencesAtStartAndEnd (s2.peek(), 0.0, minPitch, timeStep, s2_silenceThreshold, s2_minSilenceDuration, s2_minSoundingDuration, &t1_s2, &t2_s2); double s_s2_duration = s_s2 -> xmax - s_s2 -> xmin; bool hasSilence_s2 = fabs (t1_s2 - s2 -> xmin) > precision || fabs (t2_s2 - s2 -> xmax) > precision; if (hasSilence_s2) { s_atg2.reset (TextGrid_extractPart (atg2.peek(), t1_s2, t2_s2, true)); } double analysisWidth = 0.02, dt = 0.005, band = 0.0; // compare the durations of the two sounds to get an indication of the slope constraint of the DTW double slope = s_thee_duration / s_s2_duration; slope = slope > 1 ? slope : 1 / slope; int constraint = slope < 1.5 ? 4 : (slope < 2 ? 3 : (slope < 3 ? 2 : 1)); //autoMFCC m1 = Sound_to_MFCC ((hasSilence_thee ? s_thee.peek() : thee), // numberOfCoefficients, analysisWidth, dt, f1_mel, fmax_mel, df_mel); //autoMFCC m2 = Sound_to_MFCC ((hasSilence_s2 ? s_s2.peek() : s2.peek()), // numberOfCoefficients, analysisWidth, dt, f1_mel, fmax_mel, df_mel); //double wc = 1, wle = 0, wr = 0, wer = 0, dtr = 0; //int matchStart = 1, matchEnd = 1, constraint = 4; // no 1/3 1/2 2/3 //autoDTW dtw = CCs_to_DTW (m1.peek(), m2.peek(), wc, wle, wr, wer, dtr, matchStart, matchEnd, constraint); autoDTW dtw = Sounds_to_DTW ((hasSilence_thee ? s_thee.peek() : thee), (hasSilence_s2 ? s_s2.peek() : s2.peek()), analysisWidth, dt, band, constraint); autoTextGrid result = DTW_and_TextGrid_to_TextGrid (dtw.peek(), (hasSilence_s2 ? s_atg2.peek() : atg2.peek()), precision); if (hasSilence_thee) { if (t1_thee > thy xmin) { TextGrid_setEarlierStartTime (result.peek(), thy xmin, L"", L""); } if (t2_thee < thy xmax) { TextGrid_setLaterEndTime (result.peek(), thy xmax, L"", L""); } } return result.transfer(); } catch (MelderError) { Melder_throw ("Sound and TextInterval not aligned."); } } /* typedef struct structAlignmentOfSoundAndTextStruct { double windowLength, timeStep; // analysis double f1_mel, fmax_mel, df_mel; // MelFilter long numberOfMFCCCoefficients; // MFCC double dtw_cepstralWeight, dtw_logEnergyWeight; // MFCC -> DTW double dtw_regressionWeight, dtw_regressionlogEnergyWeight; double dtw_regressionWindowLength; double dtw_sakoeChibaBand, dtw_constraint; double silenceThreshold, minSilenceDuration, minSoundingDuration, trimDuration; // silence detection long language, voicevariant, pitchAdjustment, pitchRange, wordsPerMinute; // synthesizer bool interpretPhonemeCodes, ipa, set_wordsPerMinute; double wordgap; // synthesizer } *SpeechSynthesizer_alignmentStruct;*/ TextGrid SpeechSynthesizer_and_Sound_and_TextInterval_align2 (SpeechSynthesizer me, Sound thee, TextInterval him, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double trimDuration); TextGrid SpeechSynthesizer_and_Sound_and_TextInterval_align2 (SpeechSynthesizer me, Sound thee, TextInterval him, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double trimDuration) { try { if (thy xmin != his xmin || thy xmax != his xmax) { Melder_throw ("Domains of Sound and TextGrid must be equal."); } if (fabs (1.0 / thy dx - my d_samplingFrequency) > NUMfpp -> eps) { Melder_throw ("The sampling frequencies of the SpeechSynthesizer and the Sound must be equal."); } const wchar_t *trimLabel = L"trim"; // 1. trim the silences of the sound /* * For the synthesizer the silence threshold has to be < -30 dB, otherwise fricatives will not * be found as sounding! This is ok since silences are almost at zero amplitudes * We also have to decrease the minimum silence and minimum sounding duration to catch, for example, * the final plosive "t" from the word "text" * */ TextGrid tg_tmp = 0; double minPitch = 200, timeStep = 0.005, precision = thy dx; autoSound thee_trimmed = Sound_trimSilences (thee, trimDuration, false, minPitch, timeStep, silenceThreshold, minSilenceDuration, minSoundingDuration, &tg_tmp, trimLabel); autoTextGrid thee_trimmer = tg_tmp; // 2. synthesize the sound from the TextInterval autoSound synth = SpeechSynthesizer_and_TextInterval_to_Sound (me, him, &tg_tmp); autoTextGrid tg_syn = tg_tmp; // 3. There should be no silences in the synthesized sound except at the start and finish. // Set the wordwap parameter to a small value like 0.001 s. // 4. Get DTW from the two sounds double analysisWidth = 0.02, dt = 0.005, band = 0.0; int constraint = 4; autoDTW dtw = Sounds_to_DTW (thee_trimmed.peek(), synth.peek(), analysisWidth, dt, band, constraint); // 6. Warp the synthesis TextGrid // first make domain equal, otherwsise the warper protests autoTextGrid warp = DTW_and_TextGrid_to_TextGrid (dtw.peek(), tg_syn.peek(), precision); // 7. Patch the trimmed intervals back into the warped TextGrid autoTextGrid result = TextGrid_and_IntervalTier_patch (warp.peek(), (IntervalTier) thee_trimmer -> tiers ->item[1], L"trim", 2 * thy dx); return result.transfer(); } catch (MelderError) { Melder_throw (thee, ": sound and TextInterval not aligned."); } } TextGrid SpeechSynthesizer_and_Sound_and_IntervalTier_align (SpeechSynthesizer me, Sound thee, IntervalTier him, long istart, long iend, double silenceThreshold, double minSilenceDuration, double minSoundingDuration) { try { if (istart < 1 || iend < istart || iend > his intervals -> size) { Melder_throw ("Not avalid interval range."); } autoCollection textgrids = Ordered_create (); TextInterval tb = (TextInterval) his intervals -> item[istart]; TextInterval te = (TextInterval) his intervals -> item[iend]; autoTextGrid result = TextGrid_create (tb -> xmin, te -> xmax, L"sentence clause word phoneme", L""); for (long iint = istart; iint <= iend; iint ++) { TextInterval ti = (TextInterval) his intervals -> item[iint]; if (ti -> text != NULL && wcslen (ti -> text) > 0) { autoSound sound = Sound_extractPart (thee, ti -> xmin, ti -> xmax, kSound_windowShape_RECTANGULAR, 1, true); autoTextGrid atg = SpeechSynthesizer_and_Sound_and_TextInterval_align (me, sound.peek(), ti, silenceThreshold, minSilenceDuration, minSoundingDuration); Collection_addItem (textgrids.peek(), atg.transfer()); } } if (textgrids -> size == 0) { Melder_throw ("Nothing could be aligned. Was your IntervalTier empty?"); } autoTextGrid aligned = TextGrids_to_TextGrid_appendContinuous (textgrids.peek(), true); return aligned.transfer(); } catch (MelderError) { Melder_throw ("No aligned TextGrid created."); } } TextGrid SpeechSynthesizer_and_Sound_and_IntervalTier_align2 (SpeechSynthesizer me, Sound thee, IntervalTier him, long istart, long iend, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double trimDuration) { try { if (istart < 1 || iend < istart || iend > his intervals -> size) { Melder_throw ("Not avalid interval range."); } autoCollection textgrids = Ordered_create (); TextInterval tb = (TextInterval) his intervals -> item[istart]; TextInterval te = (TextInterval) his intervals -> item[iend]; autoTextGrid result = TextGrid_create (tb -> xmin, te -> xmax, L"sentence clause word phoneme", L""); for (long iint = istart; iint <= iend; iint ++) { TextInterval ti = (TextInterval) his intervals -> item[iint]; if (ti -> text != NULL && wcslen (ti -> text) > 0) { autoSound sound = Sound_extractPart (thee, ti -> xmin, ti -> xmax, kSound_windowShape_RECTANGULAR, 1, true); autoTextGrid atg = SpeechSynthesizer_and_Sound_and_TextInterval_align2 (me, sound.peek(), ti, silenceThreshold, minSilenceDuration, minSoundingDuration, trimDuration); Collection_addItem (textgrids.peek(), atg.transfer()); } } if (textgrids -> size == 0) { Melder_throw ("Nothing could be aligned. Was your IntervalTier empty?"); } autoTextGrid aligned = TextGrids_to_TextGrid_appendContinuous (textgrids.peek(), true); return aligned.transfer(); } catch (MelderError) { Melder_throw ("No aligned TextGrid created."); } } TextGrid SpeechSynthesizer_and_Sound_and_TextGrid_align (SpeechSynthesizer me, Sound thee, TextGrid him, long tierNumber, long istart, long iend, double silenceThreshold, double minSilenceDuration, double minSoundingDuration) { try {//TODO: check not empty tier IntervalTier iTier = TextGrid_checkSpecifiedTierIsIntervalTier (him, tierNumber); autoTextGrid tg = SpeechSynthesizer_and_Sound_and_IntervalTier_align (me, thee, iTier, istart, iend, silenceThreshold, minSilenceDuration, minSoundingDuration); return tg.transfer(); } catch (MelderError) { Melder_throw (""); } } TextGrid SpeechSynthesizer_and_Sound_and_TextGrid_align2 (SpeechSynthesizer me, Sound thee, TextGrid him, long tierNumber, long istart, long iend, double silenceThreshold, double minSilenceDuration, double minSoundingDuration, double trimDuration) { try {//TODO: check not empty tier IntervalTier iTier = TextGrid_checkSpecifiedTierIsIntervalTier (him, tierNumber); autoTextGrid tg = SpeechSynthesizer_and_Sound_and_IntervalTier_align2 (me, thee, iTier, istart, iend, silenceThreshold, minSilenceDuration, minSoundingDuration, trimDuration); return tg.transfer(); } catch (MelderError) { Melder_throw (""); } } static Strings IntervalTier_to_Strings_withOriginData (IntervalTier me, long *from) { try { autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, my intervals -> size); for (long i = 1; i <= my intervals -> size; i++) { TextInterval ti = (TextInterval) my intervals -> item[i]; if (ti -> text != 0 && ti -> text[0] != '\0') { thy strings [++(thy numberOfStrings)] = Melder_wcsdup (ti -> text); from[thy numberOfStrings] = i; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Strings created."); } } Table IntervalTiers_to_Table_textAlignmentment (IntervalTier target, IntervalTier source, EditCostsTable costs) { try { long numberOfTargetIntervals = target -> intervals -> size; long numberOfSourceIntervals = source -> intervals -> size; autoNUMvector targetOrigin (1, numberOfTargetIntervals); autoNUMvector sourceOrigin (1, numberOfSourceIntervals); autoStrings targets = IntervalTier_to_Strings_withOriginData (target, targetOrigin.peek()); autoStrings sources = IntervalTier_to_Strings_withOriginData (source, sourceOrigin.peek()); autoEditDistanceTable edit = EditDistanceTable_create (targets.peek(), sources.peek()); if (costs != 0) { EditDistanceTable_setEditCosts (edit.peek(), costs); EditDistanceTable_findPath (edit.peek(), NULL); } long pathLength = edit -> d_warpingPath -> d_pathLength; autoTable thee = Table_createWithColumnNames (pathLength - 1, L"targetInterval targetText targetStart targetEnd sourceInterval sourceText sourceStart sourceEnd operation"); for (long i = 2; i <= pathLength; i++) { structPairOfInteger p = edit -> d_warpingPath -> d_path[i]; structPairOfInteger p1 = edit -> d_warpingPath -> d_path[i - 1]; double targetStart = NUMundefined, targetEnd = NUMundefined; double sourceStart = NUMundefined, sourceEnd = NUMundefined; const wchar_t * targetText = L"", *sourceText = L""; long targetInterval = p.y > 1 ? targetOrigin[p.y - 1] : 0; long sourceInterval = p.x > 1 ? sourceOrigin[p.x - 1] : 0; if (targetInterval > 0) { TextInterval ti = (TextInterval) target -> intervals -> item[targetInterval]; targetStart = ti -> xmin; targetEnd = ti -> xmax; targetText = ti -> text; } if (sourceInterval > 0) { TextInterval ti = (TextInterval) source -> intervals -> item[sourceInterval]; sourceStart = ti -> xmin; sourceEnd = ti -> xmax; sourceText = ti -> text; } long irow = i - 1; if (p.y == p1.y) { // deletion Table_setNumericValue (thee.peek(), irow, 1, 0); Table_setStringValue (thee.peek(), irow, 2, L""); Table_setNumericValue (thee.peek(), irow, 3, NUMundefined); Table_setNumericValue (thee.peek(), irow, 4, NUMundefined); Table_setNumericValue (thee.peek(), irow, 5, sourceInterval); Table_setStringValue (thee.peek(), irow, 6, sourceText); Table_setNumericValue (thee.peek(), irow, 7, sourceStart); Table_setNumericValue (thee.peek(), irow, 8, sourceEnd); Table_setStringValue (thee.peek(), irow, 9, L"d"); } else if (p.x == p1.x) { // insertion Table_setNumericValue (thee.peek(), irow, 1, targetInterval); Table_setStringValue (thee.peek(), irow, 2, targetText); Table_setNumericValue (thee.peek(), irow, 3, targetStart); Table_setNumericValue (thee.peek(), irow, 4, targetEnd); Table_setNumericValue (thee.peek(), irow, 5, 0); Table_setStringValue (thee.peek(), irow, 6, L""); Table_setNumericValue (thee.peek(), irow, 7, NUMundefined); Table_setNumericValue (thee.peek(), irow, 8, NUMundefined); Table_setStringValue (thee.peek(), irow, 9, L"i"); } else { // substitution ? Table_setNumericValue (thee.peek(), irow, 1, targetInterval); Table_setStringValue (thee.peek(), irow, 2, targetText); Table_setNumericValue (thee.peek(), irow, 3, targetStart); Table_setNumericValue (thee.peek(), irow, 4, targetEnd); Table_setNumericValue (thee.peek(), irow, 5, sourceInterval); Table_setStringValue (thee.peek(), irow, 6, sourceText); Table_setNumericValue (thee.peek(), irow, 7, sourceStart); Table_setNumericValue (thee.peek(), irow, 8, sourceEnd); Table_setStringValue (thee.peek(), irow, 9, Melder_wcsequ (targetText, sourceText) ? L" " : L"s"); } } return thee.transfer(); } catch (MelderError) { Melder_throw (target, " and ", source, " not aligned."); } } Table TextGrids_to_Table_textAlignmentment (TextGrid target, long ttier, TextGrid source, long stier, EditCostsTable costs) { try { IntervalTier targetTier = TextGrid_checkSpecifiedTierIsIntervalTier (target, ttier); IntervalTier sourceTier = TextGrid_checkSpecifiedTierIsIntervalTier (source, stier); return IntervalTiers_to_Table_textAlignmentment (targetTier, sourceTier, costs); } catch (MelderError) { Melder_throw (L"No text alignment table created from TextGrids ", target, " and ", source, L"."); } } // End of file TextGrid_and_SpeechSynthesizer.cppsources_5316/dwtools/Eigen_and_Procrustes.cpp0000644000176700017670000000374211606610672020237 0ustar paulpaul/* Eigen_and_Procrustes.cpp * Copyright (C) 2005-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2004 Initial version */ #include "Eigen_and_Procrustes.h" #include "Configuration_and_Procrustes.h" #include "NUM2.h" Procrustes Eigens_to_Procrustes (I, thou, long evec_from, long evec_to) { try { iam (Eigen); thouart (Eigen); long nvectors = evec_to - evec_from + 1; long nmin = my numberOfEigenvalues < thy numberOfEigenvalues ? my numberOfEigenvalues : thy numberOfEigenvalues; if (my dimension != thy dimension) { Melder_throw ("The eigenvectors must have the same dimension."); } if (evec_from > evec_to || evec_from < 1 || evec_to > nmin) { Melder_throw ("Eigenvector range too large."); } autoNUMmatrix x (1, my dimension, 1, nvectors); autoNUMmatrix y (1, my dimension, 1, nvectors); for (long j = 1; j <= nvectors; j++) { for (long i = 1; i <= my dimension; i++) { x[i][j] = my eigenvectors[evec_from + j - 1][i]; y[i][j] = thy eigenvectors[evec_from + j - 1][i]; } } autoProcrustes him = Procrustes_create (nvectors); NUMProcrustes (x.peek(), y.peek(), my dimension, nvectors, his r, NULL, NULL); return him.transfer(); } catch (MelderError) { Melder_throw ("Procrustes not created from Eigens."); } } /* End of file Eigen_and_Procrustes.cpp */ sources_5316/dwtools/MFCC.cpp0000644000176700017670000001120411752212656014637 0ustar paulpaul/* MFCC.cpp * * Mel Frequency Cepstral Coefficients class. * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * djmw 20020813 GPL header * djmw 20110304 Thing_new */ #include "MFCC.h" #include "NUM2.h" Thing_implement (MFCC, CC, 1); MFCC MFCC_create (double tmin, double tmax, long nt, double dt, double t1, long maximumNumberOfCoefficients, double fmin_mel, double fmax_mel) { try { autoMFCC me = Thing_new (MFCC); CC_init (me.peek(), tmin, tmax, nt, dt, t1, maximumNumberOfCoefficients, fmin_mel, fmax_mel); return me.transfer(); } catch (MelderError) { Melder_throw ("MFCC not created."); } } void MFCC_lifter (MFCC me, long lifter) { try { Melder_assert (lifter > 0); autoNUMvector c (1, my maximumNumberOfCoefficients); for (long i = 1; i <= my maximumNumberOfCoefficients; i++) { c[i] = (1 + lifter / 2 * sin (NUMpi * i / lifter)); } for (long frame = 1; frame <= my nx; frame++) { CC_Frame cf = (CC_Frame) & my frame[frame]; for (long i = 1; i <= cf -> numberOfCoefficients; i++) { cf -> c[i] *= c[i]; } } } catch (MelderError) { Melder_throw (me, ": not lifted."); } } TableOfReal MFCC_to_TableOfReal (MFCC me, bool includeC0) { try { long numberOfColumns = my maximumNumberOfCoefficients + (includeC0 ? 1 : 0); autoTableOfReal thee = TableOfReal_create (my nx, numberOfColumns); autoMelderString columnLabel; for (long i = 1; i <= numberOfColumns; i++) { MelderString_append (&columnLabel, L"c", Melder_integer (includeC0 ? i - 1 : i)); TableOfReal_setColumnLabel (thee.peek(), i, columnLabel.string); MelderString_empty (&columnLabel); } long offset = includeC0 ? 1 : 0; for (long iframe = 1; iframe <= my nx; iframe++) { CC_Frame cf = (CC_Frame) & my frame[iframe]; for (long j = 1; j <= cf -> numberOfCoefficients; j++) { thy data[iframe][j + offset] = cf -> c[j]; } if (includeC0) { thy data[iframe][1] = cf -> c0; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to TabelOfReal."); } } Sound MFCC_to_Sound (MFCC me) { try { autoSound thee = Sound_create (my maximumNumberOfCoefficients, my xmin, my xmax, my nx, my dx, my x1); for (long iframe = 1; iframe <= my nx; iframe++) { CC_Frame cf = (CC_Frame) & my frame[iframe]; for (long j = 1; j <= my maximumNumberOfCoefficients; j++) { thy z[j][iframe] = cf -> c[j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not represented as Sound."); } } Sound MFCCs_crossCorrelate (MFCC me, MFCC thee, enum kSounds_convolve_scaling scaling, enum kSounds_convolve_signalOutsideTimeDomain signalOutsideTimeDomain) { try { if (my dx != thy dx) { Melder_throw ("The samplings of the two MFCC's have to be equal."); } if (my maximumNumberOfCoefficients != thy maximumNumberOfCoefficients) { Melder_throw ("The number of coefficients in the two MFCC's have to be equal."); } autoSound target = MFCC_to_Sound (me); autoSound source = MFCC_to_Sound (thee); autoSound cc = Sounds_crossCorrelate (target.peek(), source.peek(), scaling, signalOutsideTimeDomain); return cc.transfer(); } catch (MelderError) { Melder_throw ("No cross-correlation between ", me, " and ", thee, " calculated."); } } Sound MFCCs_convolve (MFCC me, MFCC thee, enum kSounds_convolve_scaling scaling, enum kSounds_convolve_signalOutsideTimeDomain signalOutsideTimeDomain) { try { if (my dx != thy dx) { Melder_throw ("The samplings of the two MFCC's have to be equal."); } if (my maximumNumberOfCoefficients != thy maximumNumberOfCoefficients) { Melder_throw ("The number of coefficients in the two MFCC's have to be equal."); } autoSound target = MFCC_to_Sound (me); autoSound source = MFCC_to_Sound (thee); autoSound cc = Sounds_convolve (target.peek(), source.peek(), scaling, signalOutsideTimeDomain); return cc.transfer(); } catch (MelderError) { Melder_throw (me, " and ", thee, " not convolved."); } } /* End of file MFCC.cpp */ sources_5316/dwtools/FormantGrid_extensions.cpp0000644000176700017670000000646111606610672020631 0ustar paulpaul/* FormantGrid_extensions.c * * Copyright (C) 2009-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20090310 */ #include "FormantGrid_extensions.h" #include "NUM2.h" void FormantGrid_draw (FormantGrid me, Graphics g, double xmin, double xmax, double ymin, double ymax, bool bandwidths, bool garnish, const wchar_t *method) { Ordered tiers = bandwidths ? my bandwidths : my formants; if (xmax <= xmin) { xmin = my xmin; xmax = my xmax; } if (ymax <= ymin) { ymin = 0; ymax = bandwidths ? 1000 : 8000; } for (long iformant = 1; iformant <= my formants -> size; iformant++) { const wchar_t *quantity = 0; bool garnish2 = false; RealTier tier = (RealTier) tiers -> item[iformant]; if (iformant == my formants -> size) { quantity = L"Frequency (Hz)"; if (garnish) { garnish2 = true; } } RealTier_draw (tier, g, xmin, xmax, ymin, ymax, garnish2, method, quantity); } } static void FormantGrid_removeFormantTier (FormantGrid me, int position) { if (position < 1 || position > my formants -> size) { return; } Collection_removeItem (my formants, position); } static void FormantGrid_removeBandwidthTier (FormantGrid me, int position) { if (position < 1 || position > my bandwidths -> size) { return; } Collection_removeItem (my bandwidths, position); } void FormantGrid_removeFormantAndBandwidthTiers (FormantGrid me, int position) { FormantGrid_removeFormantTier (me, position); FormantGrid_removeBandwidthTier (me, position); } static void FormantGrid_addFormantTier (FormantGrid me, int position) { if (position > my formants -> size || position < 1) { position = my formants -> size + 1; } autoRealTier rt = RealTier_create (my xmin, my xmax); Ordered_addItemPos (my formants, rt.transfer(), position); } static void FormantGrid_addBandwidthTier (FormantGrid me, int position) { if (position > my bandwidths -> size || position < 1) { position = my bandwidths -> size + 1; } autoRealTier rt = RealTier_create (my xmin, my xmax); Ordered_addItemPos (my bandwidths, rt.transfer(), position); } void FormantGrid_addFormantAndBandwidthTiers (FormantGrid me, int position) { try { if (my formants -> size != my bandwidths -> size) { Melder_throw ("Number of formants and bandwidths must be equal."); } if (position > my formants -> size || position < 1) { position = my formants -> size + 1; } FormantGrid_addFormantTier (me, position); try { FormantGrid_addBandwidthTier (me, position); } catch (MelderError) { FormantGrid_removeFormantTier (me, position); throw MelderError (); } } catch (MelderError) { Melder_throw (me, ": no ties added."); } } /* End of file FormantGrid_extensions.cpp */ sources_5316/dwtools/CCA_and_Correlation.h0000644000176700017670000000374411535126101017343 0ustar paulpaul#ifndef _CCA_and_Correlation_h_ #define _CCA_and_Correlation_h_ /* CCA_and_Correlation.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020516 GPL header djmw 20110307 Latest modification. */ #ifndef _CCA_h_ #include "CCA.h" #endif #ifndef _SSCP_h_ #include "SSCP.h" #endif #ifdef __cplusplus extern "C" { #endif TableOfReal CCA_and_Correlation_factorLoadings (CCA me, Correlation thee); /* Get the canonical factor loadings (also structure correlation coefficients), the correlation of a canonical variable with an original variable. */ double CCA_and_Correlation_getVarianceFraction (CCA me, Correlation thee, int x_or_y, int canonicalVariate_from, int canonicalVariate_to); /* Get the fraction of variance extracted from the dependent/independent set by the canonical variate range. */ double CCA_and_Correlation_getRedundancy_sl (CCA me, Correlation thee, int x_or_y, int canonicalVariate_from, int canonicalVariate_to); /* The Stewart-Love redundancy is the fraction of variance extracted by the canonical variate times the fraction of shared variance between the canonical variate and the corresponding canonical variate of the other set. redundancy = VarianceFraction * (canonical correlation)^2 */ #ifdef __cplusplus } #endif #endif /* _CCA_and_Correlation_h_ */ sources_5316/dwtools/LFCC.cpp0000644000176700017670000000247611627241351014644 0ustar paulpaul/* LFCC.cpp * * Linear Frequency Cepstral Coefficients class. * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20001228 djmw 20020813 GPL header djmw 20110304 Thing_new */ #include "LFCC.h" Thing_implement (LFCC, CC, 1); LFCC LFCC_create (double tmin, double tmax, long nt, double dt, double t1, long maximumNumberOfCoefficients, double fmin, double fmax) { try { autoLFCC me = Thing_new (LFCC); CC_init (me.peek(), tmin, tmax, nt, dt, t1, maximumNumberOfCoefficients, fmin, fmax); return me.transfer(); } catch (MelderError) { Melder_throw ("LFCC not created."); } } /* End of file LFCC.cpp */ sources_5316/dwtools/EditDistanceTable.h0000664000176700017670000000776511756717717017143 0ustar paulpaul#ifndef _EditDistanceTable_h_ #define _EditDistanceTable_h_ /* EditDistanceTable.h * * Copyright (C) 2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Strings_extensions.h" #include "TableOfReal.h" #define WARPING_fromLeft 1 #define WARPING_fromBelow 2 #define WARPING_fromDiag 4 #include "EditDistanceTable_def.h" oo_CLASS_CREATE (WarpingPath, Data); oo_CLASS_CREATE (EditCostsTable, TableOfReal); oo_CLASS_CREATE (EditDistanceTable, TableOfReal); WarpingPath WarpingPath_create (long length); // Search the path for the corresponding axis value. If path is horizontal/vertical // ivar1 and ivar2 will not ge eqal. The return value is the length of the path segment (ivar2-ivar1 +1) long WarpingPath_getColumnsFromRowIndex (WarpingPath me, long irow, long *icol1, long *icol2); long WarpingPath_getRowsFromColumnIndex (WarpingPath me, long icol, long *irow1, long *irow2); EditCostsTable EditCostsTable_create (long targetAlphabetSize, long sourceAlphabetSize); /* The insertion, deletion and substitution costs are specified in this table * 1..n-2 target symbols (target alphabet) * 1..m-2 source symbols (source alphabet) * row n-1 and col m-1 specify no-match symbols * cells [n][1..m-1] specify insertion costs * cells [1..n-1][m] specify deletion costs * cell [n-1][m-1] no-match target == no-match source * cell [n][m] no-match target != no-match source */ void EditCostsTable_setDefaultCosts (EditCostsTable me, double insertionCosts, double deletionCosts, double substitutionCosts); long EditCostsTable_getTargetIndex (EditCostsTable me, const wchar_t *symbol); long EditCostsTable_getSourceIndex (EditCostsTable me, const wchar_t *symbol); double EditCostsTable_getInsertionCost (EditCostsTable me, const wchar_t *symbol); void EditCostsTable_setInsertionCosts (EditCostsTable me, wchar_t *targets, double cost); void EditCostsTable_setOthersCosts (EditCostsTable me, double insertionCosts, double deletionCost, double substitutionCost_equal, double substitutionCost_unequal); double EditCostsTable_getOthersCost (EditCostsTable me, int type); double EditCostsTable_getDeletionCost (EditCostsTable me, const wchar_t *symbol); void EditCostsTable_setDeletionCosts (EditCostsTable me, wchar_t *sources, double cost); double EditCostsTable_getSubstitutionCost (EditCostsTable me, const wchar_t *symbol, const wchar *replacement); void EditCostsTable_setSubstitutionCosts (EditCostsTable me, wchar_t *targets, wchar_t *sources, double cost); TableOfReal EditCostsTable_to_TableOfReal (EditCostsTable me); EditDistanceTable EditDistanceTable_create (Strings target, Strings source); EditDistanceTable EditDistanceTable_createFromCharacterStrings (const wchar_t *chars1, const wchar_t *chars2); void EditDistanceTable_draw (EditDistanceTable me, Graphics graphics, int iformat, int precision, double angle); void EditDistanceTable_drawEditOperations (EditDistanceTable me, Graphics graphics); void EditDistanceTable_setDefaultCosts (EditDistanceTable me, double insertionCosts, double deletionCosts, double substitutionCosts); void EditDistanceTable_findPath (EditDistanceTable me, TableOfReal *directions); void EditDistanceTable_setEditCosts (EditDistanceTable me, EditCostsTable thee); TableOfReal EditDistanceTable_to_TableOfReal_directions (EditDistanceTable me); TableOfReal EditDistanceTable_to_TableOfReal (EditDistanceTable me); #endif /* _EditDistanceTable_h_ */ sources_5316/dwtools/PCA.cpp0000644000176700017670000002153211752707005014534 0ustar paulpaul/* PCA.cpp * * Principal Component Analysis * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20000511 PCA_and_TableOfReal_to_Configuration: added centralize option. (later removed) djmw 20020327 PCA_and_TableOfReal_to_Configuration modified internals. djmw 20020418 Removed some causes for compiler warnings. djmw 20020502 modified call Eigen_and_TableOfReal_project_into. djmw 20030324 Added PCA_and_TableOfReal_getFractionVariance. djmw 20061212 Changed info to Melder_writeLine format. djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20071201 Melder_warning djmw 20081119 Check in TableOfReal_to_PCA if TableOfReal_areAllCellsDefined djmw 20110304 Thing_new */ #include "PCA.h" #include "NUMlapack.h" #include "NUM2.h" #include "TableOfReal_extensions.h" #include "Eigen_and_SSCP.h" #include "Eigen_and_TableOfReal.h" #include "Configuration.h" #include "oo_DESTROY.h" #include "PCA_def.h" #include "oo_COPY.h" #include "PCA_def.h" #include "oo_EQUAL.h" #include "PCA_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "PCA_def.h" #include "oo_WRITE_TEXT.h" #include "PCA_def.h" #include "oo_READ_TEXT.h" #include "PCA_def.h" #include "oo_WRITE_BINARY.h" #include "PCA_def.h" #include "oo_READ_BINARY.h" #include "PCA_def.h" #include "oo_DESCRIPTION.h" #include "PCA_def.h" Thing_implement (PCA, Eigen, 0); void structPCA :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of components: ", Melder_integer (numberOfEigenvalues)); MelderInfo_writeLine2 (L"Number of dimensions: ", Melder_integer (dimension)); MelderInfo_writeLine2 (L"Number of observations: ", Melder_integer (numberOfObservations)); } PCA PCA_create (long numberOfComponents, long dimension) { try { autoPCA me = Thing_new (PCA); Eigen_init (me.peek(), numberOfComponents, dimension); my labels = NUMvector (1, dimension); my centroid = NUMvector (1, dimension); return me.transfer(); } catch (MelderError) { Melder_throw ("PCA not created"); } } void PCA_setNumberOfObservations (PCA me, long numberOfObservations) { my numberOfObservations = numberOfObservations; } long PCA_getNumberOfObservations (PCA me) { return my numberOfObservations; } void PCA_getEqualityOfEigenvalues (PCA me, long from, long to, int conservative, double *probability, double *chisq, long *ndf) { double sum = 0, sumln = 0; *probability = 1; *ndf = 0; *chisq = 0; if ( (from > 0 && to == from) || to > my numberOfEigenvalues) { return; } if (to <= from) { from = 1; to = my numberOfEigenvalues; } long i; for (i = from; i <= to; i++) { if (my eigenvalues[i] <= 0) { break; } sum += my eigenvalues[i]; sumln += log (my eigenvalues[i]); } if (sum == 0) { return; } long r = i - from; long n = my numberOfObservations - 1; if (conservative) { n -= from + (r * (2 * r + 1) + 2) / (6 * r); } *ndf = r * (r + 1) / 2 - 1; *chisq = n * (r * log (sum / r) - sumln); *probability = NUMchiSquareQ (*chisq, *ndf); } PCA TableOfReal_to_PCA (I) { iam (TableOfReal); try { long m = my numberOfRows, n = my numberOfColumns; if (! TableOfReal_areAllCellsDefined (me, 0, 0, 0, 0)) { Melder_throw ("Undefined cells."); } if (m < 2) Melder_throw ("There is not enough data to perform a PCA.\n" "Your table has less than 2 rows."); if (m < n) Melder_warning (L"The number of rows in your table is less than the\n" "number of columns. "); if (NUMfrobeniusnorm (m, n, my data) == 0) { Melder_throw ("All values in your table are zero."); } autoPCA thee = Thing_new (PCA); autoNUMmatrix a (NUMmatrix_copy (my data, 1, m, 1, n), 1, 1); thy centroid = NUMvector (1, n); for (long j = 1; j <= n; j++) { double colmean = a[1][j]; for (long i = 2; i <= m; i++) { colmean += a[i][j]; } colmean /= m; for (long i = 1; i <= m; i++) { a[i][j] -= colmean; } thy centroid[j] = colmean; } Eigen_initFromSquareRoot (thee.peek(), a.peek(), m, n); thy labels = NUMvector (1, n); NUMstrings_copyElements (my columnLabels, thy labels, 1, n); PCA_setNumberOfObservations (thee.peek(), m); /* The covariance matrix C = A'A / (N-1). However, we have calculated the eigenstructure for A'A. This has no consequences for the eigenvectors, but the eigenvalues have to be divided by (N-1). */ for (long i = 1; i <= thy numberOfEigenvalues; i++) { thy eigenvalues[i] /= (m - 1); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": PCA not created."); } } TableOfReal PCA_and_TableOfReal_to_TableOfReal_zscores (PCA me, TableOfReal thee, long numberOfDimensions) { try { if (numberOfDimensions == 0 || numberOfDimensions > my numberOfEigenvalues) { numberOfDimensions = my numberOfEigenvalues; } autoTableOfReal him = TableOfReal_create (thy numberOfRows, numberOfDimensions); for (long i = 1; i <= thy numberOfRows; i++) { /* row */ for (long j = 1; j <= numberOfDimensions; j++) { double r = 0, sigma = sqrt (my eigenvalues[j]); for (long k = 1; k <= my dimension; k++) { // eigenvector in row, data in row r += my eigenvectors[j][k] * (thy data[i][k] - my centroid[k]) / sigma; } his data[i][j] = r; } } NUMstrings_copyElements (thy rowLabels, his rowLabels, 1, thy numberOfRows); TableOfReal_setSequentialColumnLabels (him.peek(), 0, 0, L"pc", 1, 1); return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal (zscores) not created from PCA & TableOfReal."); } } Configuration PCA_and_TableOfReal_to_Configuration (PCA me, thou, long numberOfDimensions) { try { thouart (TableOfReal); if (numberOfDimensions == 0 || numberOfDimensions > my numberOfEigenvalues) { numberOfDimensions = my numberOfEigenvalues; } autoConfiguration him = Configuration_create (thy numberOfRows, numberOfDimensions); Configuration thim = him.peek(); Eigen_and_TableOfReal_project_into (me, thee, 1, thy numberOfColumns, & thim, 1, numberOfDimensions); NUMstrings_copyElements (thy rowLabels, his rowLabels, 1, thy numberOfRows); TableOfReal_setSequentialColumnLabels (him.peek(), 0, 0, L"pc", 1, 1); return him.transfer(); } catch (MelderError) { Melder_throw ("Configuration not created from PCA & TableOfReal."); } } TableOfReal PCA_and_Configuration_to_TableOfReal_reconstruct (PCA me, thou) { try { thouart (Configuration); long npc = thy numberOfColumns; if (thy numberOfColumns > my dimension) { Melder_throw ("The dimension of the Configuration must be less than or equal to the dimension of the PCA."); } if (npc > my numberOfEigenvalues) { npc = my numberOfEigenvalues; } autoTableOfReal him = TableOfReal_create (thy numberOfRows, my dimension); NUMstrings_copyElements (my labels, his columnLabels, 1, my dimension); NUMstrings_copyElements (thy rowLabels, his rowLabels, 1, thy numberOfRows); for (long i = 1; i <= thy numberOfRows; i++) { double *hisdata = his data[i]; for (long k = 1; k <= npc; k++) { double *evec = my eigenvectors[k], pc = thy data[i][k]; for (long j = 1; j <= my dimension; j++) { hisdata[j] += pc * evec[j]; } } } return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal not reconstructed."); } } double PCA_and_TableOfReal_getFractionVariance (PCA me, thou, long from, long to) { try { thouart (TableOfReal); double fraction = NUMundefined; if (from < 1 || from > to || to > thy numberOfColumns) { return NUMundefined; } autoSSCP s = TableOfReal_to_SSCP (thee, 0, 0, 0, 0); autoSSCP sp = Eigen_and_SSCP_project (me, s.peek()); fraction = SSCP_getFractionVariation (sp.peek(), from, to); return fraction; } catch (MelderError) { return NUMundefined; } } TableOfReal PCA_to_TableOfReal_reconstruct1 (PCA me, wchar_t *numstring) { try { long npc; autoNUMvector pc (NUMstring_to_numbers (numstring, & npc), 1); autoConfiguration c = Configuration_create (1, npc); for (long j = 1; j <= npc; j++) { c -> data [1][j] = pc[j]; } autoTableOfReal him = PCA_and_Configuration_to_TableOfReal_reconstruct (me, c.peek()); return him.transfer(); } catch (MelderError) { Melder_throw (me, " not reconstructed."); } } /* End of file PCA.cpp */ sources_5316/dwtools/praat_KlattGrid_init.cpp0000644000176700017670000017443011652056017020235 0ustar paulpaul/* praat_KlattGrid_init.c * * Copyright (C) 2009-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20090420 */ #include "praat.h" #include "IntensityTierEditor.h" #include "KlattGridEditors.h" #include "KlattTable.h" #undef iam #define iam iam_LOOP /******************* KlattGrid *********************************/ static const wchar_t *formant_names[] = { L"", L"oral ", L"nasal ", L"frication ", L"tracheal ", L"nasal anti", L"tracheal anti", L"delta "}; static void KlattGrid_4formants_addCommonField (void *dia) { Any radio; OPTIONMENU (L"Formant type", 1) OPTION (L"Normal formant") OPTION (L"Nasal formant") OPTION (L"Frication formant") OPTION (L"Tracheal formant") } static void KlattGrid_6formants_addCommonField (void *dia) { Any radio; OPTIONMENU (L"Formant type", 1) OPTION (L"Normal formant") OPTION (L"Nasal formant") OPTION (L"Frication formant") OPTION (L"Tracheal formant") OPTION (L"Nasal antiformant") OPTION (L"Tracheal antiformant") // OPTION (L"Delta formant") } static void KlattGrid_7formants_addCommonField (void *dia) { Any radio; OPTIONMENU (L"Formant type", 1) OPTION (L"Normal formant") OPTION (L"Nasal formant") OPTION (L"Frication formant") OPTION (L"Tracheal formant") OPTION (L"Nasal antiformant") OPTION (L"Tracheal antiformant") OPTION (L"Delta formant") } static void KlattGrid_PhonationGridPlayOptions_addCommonFields (void *dia) { Any radio; //LABEL (L"", L"Phonation options") BOOLEAN (L"Voicing", 1) BOOLEAN (L"Flutter", 1) BOOLEAN (L"Double pulsing", 1) BOOLEAN (L"Collision phase", 1) BOOLEAN (L"Spectral tilt", 1) OPTIONMENU (L"Flow function", 1) OPTION (L"Powers in tiers") OPTION (L"t^2-t^3") OPTION (L"t^3-t^4") BOOLEAN (L"Flow derivative", 1) BOOLEAN (L"Aspiration", 1) BOOLEAN (L"Breathiness", 1) } static void KlattGrid_PhonationGridPlayOptions_getCommonFields (void *dia, KlattGrid thee) { PhonationGridPlayOptions pp = thy phonation -> options; pp -> voicing = GET_INTEGER (L"Voicing"); pp -> flutter = GET_INTEGER (L"Flutter"); pp -> doublePulsing = GET_INTEGER (L"Double pulsing"); pp -> collisionPhase = GET_INTEGER (L"Collision phase"); pp -> spectralTilt = GET_INTEGER (L"Spectral tilt"); pp -> flowFunction = GET_INTEGER (L"Flow function"); pp -> flowDerivative = GET_INTEGER (L"Flow derivative"); pp -> aspiration = GET_INTEGER (L"Aspiration"); pp -> breathiness = GET_INTEGER (L"Breathiness"); } static void KlattGrid_PlayOptions_addCommonFields (void *dia, int sound) { Any radio; //LABEL (L"", L"Time domain") REAL (L"left Time range (s)", L"0") REAL (L"right Time range (s)", L"0") if (sound) POSITIVE (L"Sampling frequency (Hz)", L"44100") BOOLEAN (L"Scale peak", 1) KlattGrid_PhonationGridPlayOptions_addCommonFields (dia); OPTIONMENU (L"Filter options", 1) OPTION (L"Cascade") OPTION (L"Parallel") REAL (L"left Oral formant range", L"1") REAL (L"right Oral formant range", L"5") REAL (L"left Nasal formant range", L"1") REAL (L"right Nasal formant range", L"1") REAL (L"left Nasal antiformant range", L"1") REAL (L"right Nasal antiformant range", L"1") //LABEL (L"", L"Coupling options") REAL (L"left Tracheal formant range", L"1") REAL (L"right Tracheal formant range", L"1") REAL (L"left Tracheal antiformant range", L"1") REAL (L"right Tracheal antiformant range", L"1") REAL (L"left Delta formant range", L"1") REAL (L"right Delta formant range", L"1") REAL (L"left Delta bandwidth range", L"1") REAL (L"right Delta bandwidth range", L"1") //LABEL (L"", L"Frication options") REAL (L"left Frication formant range", L"1") REAL (L"right Frication formant range", L"6") BOOLEAN (L"Frication bypass", 1) } static void KlattGrid_PlayOptions_getCommonFields (void *dia, int sound, KlattGrid thee) { KlattGrid_setDefaultPlayOptions (thee); KlattGridPlayOptions pk = thy options; pk -> scalePeak = GET_INTEGER (L"Scale peak"); pk -> xmin = GET_REAL (L"left Time range"); pk -> xmax = GET_REAL (L"right Time range"); if (sound) { pk -> samplingFrequency = GET_REAL (L"Sampling frequency"); } pk -> scalePeak = GET_INTEGER (L"Scale peak"); KlattGrid_PhonationGridPlayOptions_getCommonFields (dia, thee); VocalTractGridPlayOptions pv = thy vocalTract -> options; pv -> filterModel = GET_INTEGER (L"Filter options") == 1 ? KlattGrid_FILTER_CASCADE : KlattGrid_FILTER_PARALLEL; pv -> startOralFormant = GET_REAL (L"left Oral formant range"); pv -> endOralFormant = GET_REAL (L"right Oral formant range"); pv -> startNasalFormant = GET_REAL (L"left Nasal formant range"); pv -> endNasalFormant = GET_REAL (L"right Nasal formant range"); pv -> startNasalAntiFormant = GET_REAL (L"left Nasal antiformant range"); pv -> endNasalAntiFormant = GET_REAL (L"right Nasal antiformant range"); CouplingGridPlayOptions pc = thy coupling -> options; pc -> startTrachealFormant = GET_REAL (L"left Tracheal formant range"); pc -> endTrachealFormant = GET_REAL (L"right Tracheal formant range"); pc -> startTrachealAntiFormant = GET_REAL (L"left Tracheal antiformant range"); pc -> endTrachealAntiFormant = GET_REAL (L"right Tracheal antiformant range"); pc -> startDeltaFormant = GET_REAL (L"left Delta formant range"); pc -> endDeltaFormant = GET_REAL (L"right Delta formant range"); pc -> startDeltaBandwidth = GET_REAL (L"left Delta bandwidth range"); pc -> endDeltaFormant = GET_REAL (L"right Delta bandwidth range"); FricationGridPlayOptions pf = thy frication -> options; pf -> startFricationFormant = GET_REAL (L"left Frication formant range"); pf -> endFricationFormant = GET_REAL (L"right Frication formant range"); pf -> bypass = GET_INTEGER (L"Frication bypass"); } DIRECT (KlattGrid_createExample) praat_new (KlattGrid_createExample(), L"example"); END FORM (KlattGrid_create, L"Create KlattGrid", L"Create KlattGrid...") WORD (L"Name", L"kg") REAL (L"Start time (s)", L"0.0") REAL (L"End time (s)", L"1.0") INTEGER (L"Number of oral formants", L"6") INTEGER (L"Number of nasal formants", L"1") INTEGER (L"Number of nasal antiformants", L"1") INTEGER (L"Number of frication formants", L"6") LABEL (L"", L"Coupling between source and filter") INTEGER (L"Number of tracheal formants", L"1") INTEGER (L"Number of tracheal antiformants", L"1") INTEGER (L"Number of delta formants", L"1") OK DO double tmin = GET_REAL (L"Start time"); double tmax = GET_REAL (L"End time"); REQUIRE (tmin < tmax, L"The start time must lie before the end time.") long numberOfOralFormants = GET_INTEGER (L"Number of oral formants"); long numberOfNasalFormants = GET_INTEGER (L"Number of nasal formants"); long numberOfNasalAntiFormants = GET_INTEGER (L"Number of nasal antiformants"); long numberOfTrachealFormants = GET_INTEGER (L"Number of tracheal formants"); long numberOfTrachealAntiFormants = GET_INTEGER (L"Number of tracheal antiformants"); long numberOfFricationFormants = GET_INTEGER (L"Number of frication formants"); long numberOfDeltaFormants = GET_INTEGER (L"Number of delta formants"); REQUIRE (numberOfOralFormants >= 0 && numberOfNasalFormants >= 0 && numberOfNasalAntiFormants >= 0 && numberOfTrachealFormants >= 0 && numberOfTrachealAntiFormants >= 0 && numberOfFricationFormants >= 0 && numberOfDeltaFormants >= 0, L"The number of (..) formants cannot be negative!") praat_new (KlattGrid_create (tmin, tmax, numberOfOralFormants, numberOfNasalFormants, numberOfNasalAntiFormants, numberOfTrachealFormants, numberOfTrachealAntiFormants, numberOfFricationFormants, numberOfDeltaFormants), GET_STRING (L"Name")); END #define KlattGrid_INSTALL_TIER_EDITOR(Name,name) \ DIRECT (KlattGrid_edit##Name##Tier) \ if (theCurrentPraatApplication -> batch) { Melder_throw ("Cannot edit a KlattGrid from batch."); } \ LOOP {\ iam (KlattGrid); \ auto##KlattGrid_##name##TierEditor editor = KlattGrid_##name##TierEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); \ praat_installEditor (editor.transfer(), IOBJECT); \ }\ END KlattGrid_INSTALL_TIER_EDITOR (Pitch, pitch) KlattGrid_INSTALL_TIER_EDITOR (VoicingAmplitude, voicingAmplitude) KlattGrid_INSTALL_TIER_EDITOR (Flutter, flutter) KlattGrid_INSTALL_TIER_EDITOR (Power1, power1) KlattGrid_INSTALL_TIER_EDITOR (Power2, power2) KlattGrid_INSTALL_TIER_EDITOR (OpenPhase, openPhase) KlattGrid_INSTALL_TIER_EDITOR (CollisionPhase, collisionPhase) KlattGrid_INSTALL_TIER_EDITOR (DoublePulsing, doublePulsing) KlattGrid_INSTALL_TIER_EDITOR (AspirationAmplitude, aspirationAmplitude) KlattGrid_INSTALL_TIER_EDITOR (BreathinessAmplitude, breathinessAmplitude) KlattGrid_INSTALL_TIER_EDITOR (SpectralTilt, spectralTilt) KlattGrid_INSTALL_TIER_EDITOR (FricationBypass, fricationBypass) KlattGrid_INSTALL_TIER_EDITOR (FricationAmplitude, fricationAmplitude) #undef KlattGrid_INSTALL_TIER_EDITOR #define KlattGRID_EDIT_FORMANTGRID(Name,formantType) \ DIRECT (KlattGrid_edit##Name##FormantGrid) \ if (theCurrentPraatApplication -> batch) { Melder_throw ("Cannot edit a KlattGrid from batch."); } \ LOOP {\ iam (KlattGrid); \ const wchar_t *id_and_name = Melder_wcscat (Melder_integer (ID), L". ", formant_names[formantType], L"formant grid"); \ autoKlattGrid_formantGridEditor editor = KlattGrid_formantGridEditor_create (theCurrentPraatApplication -> topShell, id_and_name, me, formantType); \ praat_installEditor (editor.transfer(), IOBJECT); \ Melder_free (id_and_name); \ } \ END KlattGRID_EDIT_FORMANTGRID (Oral, KlattGrid_ORAL_FORMANTS) KlattGRID_EDIT_FORMANTGRID (Nasal, KlattGrid_NASAL_FORMANTS) KlattGRID_EDIT_FORMANTGRID (Tracheal, KlattGrid_TRACHEAL_FORMANTS) KlattGRID_EDIT_FORMANTGRID (NasalAnti, KlattGrid_NASAL_ANTIFORMANTS) KlattGRID_EDIT_FORMANTGRID (TrachealAnti, KlattGrid_TRACHEAL_ANTIFORMANTS) KlattGRID_EDIT_FORMANTGRID (Delta, KlattGrid_DELTA_FORMANTS) KlattGRID_EDIT_FORMANTGRID (Frication, KlattGrid_FRICATION_FORMANTS) #undef KlattGRID_EDIT_FORMANTGRID #define KlattGrid_EDIT_FORMANT_AMPLITUDE_TIER(Name,name,formantType) \ FORM (KlattGrid_edit##Name##FormantAmplitudeTier, L"KlattGrid: View & Edit " #name "formant amplitude tier", 0) \ NATURAL (L"Formant number", L"1") \ OK \ DO \ long formantNumber = GET_INTEGER (L"Formant number"); \ if (theCurrentPraatApplication -> batch) { Melder_throw ("Cannot edit a KlattGrid from batch."); } \ LOOP { \ iam (KlattGrid); \ Ordered *amp = KlattGrid_getAddressOfAmplitudes (me, formantType); \ if (amp == NULL) Melder_throw ("Unknown formant type"); \ if (formantNumber > (*amp) -> size) Melder_throw ("Formant number does not exist."); \ const wchar_t *id_and_name = Melder_wcscat (Melder_integer (ID), L". ", formant_names[formantType], L"formant amplitude tier"); \ autoKlattGrid_decibelTierEditor editor = KlattGrid_decibelTierEditor_create (theCurrentPraatApplication -> topShell, id_and_name, me, (RealTier) (*amp)->item[formantNumber]); \ praat_installEditor (editor.transfer(), IOBJECT); \ Melder_free (id_and_name); \ } \ END KlattGrid_EDIT_FORMANT_AMPLITUDE_TIER (Oral, oral, KlattGrid_ORAL_FORMANTS) KlattGrid_EDIT_FORMANT_AMPLITUDE_TIER (Nasal, nasal, KlattGrid_NASAL_FORMANTS) KlattGrid_EDIT_FORMANT_AMPLITUDE_TIER (Tracheal, tracheal, KlattGrid_TRACHEAL_FORMANTS) KlattGrid_EDIT_FORMANT_AMPLITUDE_TIER (Frication, frication, KlattGrid_FRICATION_FORMANTS) #undef KlattGrid_EDIT_FORMANT_AMPLITUDE_TIER #define KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE(Name,name,unit,default,require, requiremessage,newname,tiertype) \ FORM(KlattGrid_get##Name##AtTime, L"KlattGrid: Get " #name " at time", 0) \ REAL (L"Time", L"0.5") \ OK \ DO \ LOOP { iam (KlattGrid); \ Melder_informationReal (KlattGrid_get##Name##AtTime (me, GET_REAL (L"Time")), unit); \ }\ END \ FORM (KlattGrid_add##Name##Point, L"KlattGrid: Add " #name " point", 0) \ REAL (L"Time (s)", L"0.5") \ REAL (L"Value" unit, default) \ OK \ DO \ double value = GET_REAL (L"Value"); \ REQUIRE (require, requiremessage) \ LOOP { iam (KlattGrid); \ KlattGrid_add##Name##Point (me, GET_REAL (L"Time"), value); \ praat_dataChanged (me); \ } \ END \ FORM (KlattGrid_remove##Name##Points, L"Remove " #name " points", 0) \ REAL (L"From time (s)", L"0.3")\ REAL (L"To time (s)", L"0.7") \ OK \ DO \ LOOP { iam (KlattGrid); \ KlattGrid_remove##Name##Points (me, GET_REAL (L"From time"), GET_REAL (L"To time")); \ praat_dataChanged (me);\ } \ END \ DIRECT (KlattGrid_extract##Name##Tier) \ LOOP { iam (KlattGrid); \ praat_new (KlattGrid_extract##Name##Tier (me), newname); \ } \ END \ DIRECT (KlattGrid_replace##Name##Tier) \ KlattGrid me = FIRST(KlattGrid); \ tiertype thee = FIRST(tiertype); \ KlattGrid_replace##Name##Tier (me, thee); \ praat_dataChanged (me);\ END // 55 DO_KlattGrid... functions KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (Pitch, pitch, L" (Hz)", (L"100.0"), (value >= 0), (L"Pitch must be greater equal zero."), L"f0", PitchTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (VoicingAmplitude, voicing amplitude, L" (dB SPL)", L"90.0", (1), L"", L"voicing", IntensityTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (Flutter, flutter, L" (0..1)", (L"0.0"), (value >= 0 && value <= 1), (L"Flutter must be in [0,1]."), L"flutter", RealTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (Power1, power1, L"", L"3", (value > 0), L"Power1 needs to be positive.", L"power1", RealTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (Power2, power2, L"", L"4", (value > 0), L"Power2 needs to be positive.", L"power2", RealTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (OpenPhase, open phase, L"", L"0.7", (value >= 0 && value <= 1), L"Open phase must be greater than zero and smaller equal one.", L"openPhase", RealTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (CollisionPhase, collision phase, L"", L"0.03", (value >= 0 && value < 1), L"Collision phase must be greater equal zero and smaller than one.", L"collisionPhase", RealTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (DoublePulsing, double pulsing, L" (0..1)", L"0.0", (value >= 0 && value <= 1), L"Double pulsing must be greater equal zero and smaller equal one.", L"doublePulsing", RealTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (SpectralTilt, spectral tilt, L" (dB)", L"0.0", (value >= 0), L"Spectral tilt must be greater equal zero.", L"spectralTilt", IntensityTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (AspirationAmplitude, aspiration amplitude, L" (dB SPL)", L"0.0", (1), L"", L"aspiration", IntensityTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (BreathinessAmplitude, breathiness amplitude, L" (dB SPL)", L"30.0", (1), L"", L"breathiness", IntensityTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (FricationAmplitude, frication amplitude, L" (dB SPL)", L"30.0", (1), L"", L"frication", IntensityTier) KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE (FricationBypass, frication bypass, L" (dB)", L"30.0", (1), L"", L"bypass", IntensityTier) #undef KlattGrid_PHONATION_GET_ADD_REMOVE_EXTRACT_REPLACE #define KlattGrid_FORMULA_FORMANT_FBA_VALUE(Name,namef,ForBs,forbs,textfield,formantType,label) \ FORM (KlattGrid_formula##Name##Formant##ForBs, L"KlattGrid: Formula (" #namef "ormant " #forbs ")", L"Formant: Formula (" #forbs ")...") \ LABEL (L"", L"row is formant number, col is point number:\nfor row from 1 to nrow do for col from 1 to ncol do " #ForBs " (row, col) :=") \ LABEL (L"", label) \ TEXTFIELD (L"formula", textfield) \ OK \ DO \ LOOP { iam (KlattGrid); \ KlattGrid_formula_##forbs (me, formantType, GET_STRING (L"formula"), interpreter); \ praat_dataChanged (me); \ } \ END #define KlattGrid_ADD_FBA_VALUE(Name,namef,Form,FBA,fba,formantType,default,unit,require,requiremessage) \ FORM (KlattGrid_add##Name##Formant##FBA##Point, L"KlattGrid: Add " #namef "ormant " #fba " point", 0) \ NATURAL (L"Formant number", L"1") \ REAL (L"Time (s)", L"0.5") \ REAL (L"Value " #unit, default) \ OK \ DO \ double value = GET_REAL (L"Value"); \ REQUIRE (require, requiremessage) \ LOOP { iam (KlattGrid); \ KlattGrid_add##Form##Point (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"Time"), value); \ praat_dataChanged (me); \ } \ END #define KlattGrid_REMOVE_FBA_VALUE(Name,namef,Form,FBA,fba,formantType) \ FORM (KlattGrid_remove##Name##Formant##FBA##Points, L"KlattGrid: Remove " #namef "ormant " #fba " points", 0) \ NATURAL (L"Formant number", L"1") \ REAL (L"From time (s)", L"0.3")\ REAL (L"To time (s)", L"0.7") \ OK \ DO \ LOOP { iam (KlattGrid); \ KlattGrid_remove##Form##Points (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"From time"), GET_REAL (L"To time")); \ praat_dataChanged (me);\ } \ END #define KlattGrid_ADD_FORMANT(Name,namef,formantType) \ FORM (KlattGrid_add##Name##Formant, L"KlattGrid: Add " #namef "ormant", 0) \ INTEGER (L"Position", L"0 (=at end)") \ OK \ DO \ LOOP { iam (KlattGrid); \ KlattGrid_addFormant (me, formantType, GET_INTEGER (L"Position")); \ praat_dataChanged (me); \ } \ END #define KlattGrid_REMOVE_FORMANT(Name,namef,formantType) \ FORM (KlattGrid_remove##Name##Formant, L"KlattGrid: Remove " #namef "ormant", 0) \ INTEGER (L"Position", L"0 (=do nothing)") \ OK \ DO \ LOOP { iam (KlattGrid); \ KlattGrid_removeFormant (me, formantType, GET_INTEGER (L"Position")); \ praat_dataChanged (me); \ } \ END #define KlattGrid_FORMULA_ADD_REMOVE_FBA(Name,namef,formantType) \ KlattGrid_FORMULA_FORMANT_FBA_VALUE (Name, namef, Frequencies, frequencies, L"if row = 2 then self + 200 else self fi", formantType, L" ") \ KlattGrid_FORMULA_FORMANT_FBA_VALUE (Name, namef, Bandwidths, bandwidths, L"self / 10 ; 10% of frequency", formantType, L"Warning: self is formant frequency.") \ KlattGrid_ADD_FBA_VALUE (Name, namef, Formant, Frequency, frequency, formantType, L"500.0", (Hz), (value>0), L"Frequency must be greater than zero.") \ KlattGrid_ADD_FBA_VALUE (Name, namef, Bandwidth, Bandwidth, bandwidth, formantType, L"50.0", (Hz), (value>0), L"Bandwidth must be greater than zero.") \ KlattGrid_ADD_FBA_VALUE (Name, namef, Amplitude, Amplitude, amplitude, formantType, L"0.0", (dB), (NUMdefined(value)), L"Amplitude must be defined.") \ KlattGrid_REMOVE_FBA_VALUE (Name, namef, Formant, Frequency, frequency, formantType) \ KlattGrid_REMOVE_FBA_VALUE (Name, namef, Bandwidth, Bandwidth, bandwidth, formantType) \ KlattGrid_REMOVE_FBA_VALUE (Name, namef, Amplitude, Amplitude, amplitude, formantType) \ KlattGrid_ADD_FORMANT(Name,namef,formantType) \ KlattGrid_REMOVE_FORMANT(Name,namef,formantType) #define KlattGrid_FORMULA_ADD_REMOVE_FB(Name,namef,formantType) \ KlattGrid_FORMULA_FORMANT_FBA_VALUE (Name, namef, Frequencies, frequencies, L"if row = 2 then self + 200 else self fi",formantType, L" ") \ KlattGrid_FORMULA_FORMANT_FBA_VALUE (Name, namef, Bandwidths, bandwidths, L"self / 10 ; 10% of frequency",formantType,L"Warning: self is formant frequency.") \ KlattGrid_ADD_FBA_VALUE (Name, namef, Formant,Frequency, frequency, formantType, L"500.0", (Hz), (value>0), L"Frequency must be greater than zero.") \ KlattGrid_ADD_FBA_VALUE (Name, namef, Bandwidth, Bandwidth, bandwidth, formantType, L"50.0", (Hz), (value>0), L"Bandwidth must be greater than zero.") \ KlattGrid_REMOVE_FBA_VALUE (Name, namef, Formant, Frequency, frequency, formantType) \ KlattGrid_REMOVE_FBA_VALUE (Name, namef, Bandwidth, Bandwidth, bandwidth, formantType) \ KlattGrid_ADD_FORMANT(Name,namef,formantType) \ KlattGrid_REMOVE_FORMANT(Name,namef,formantType) #define KlattGrid_FORMULA_ADD_REMOVE_FB_DELTA(Name,namef,formantType) \ KlattGrid_FORMULA_FORMANT_FBA_VALUE (Name, namef, Frequencies, frequencies, L"if row = 2 then self + 200 else self fi",formantType, L" ") \ KlattGrid_FORMULA_FORMANT_FBA_VALUE (Name, namef, Bandwidths, bandwidths, L"self / 10 ; 10% of frequency",formantType,L"Warning: self is formant frequency.") \ KlattGrid_ADD_FBA_VALUE (Name, namef, Formant,Frequency, frequency, formantType, L"-100.0", (Hz), (value!=NUMundefined), L"Frequency must be defined.") \ KlattGrid_ADD_FBA_VALUE (Name, namef, Bandwidth, Bandwidth, bandwidth, formantType, L"-50.0", (Hz), (value!=NUMundefined), L"Bandwidth must be defined.") \ KlattGrid_REMOVE_FBA_VALUE (Name, namef, Formant, Frequency, frequency, formantType) \ KlattGrid_REMOVE_FBA_VALUE (Name, namef, Bandwidth, Bandwidth, bandwidth, formantType) \ KlattGrid_ADD_FORMANT(Name,namef,formantType) \ KlattGrid_REMOVE_FORMANT(Name,namef,formantType) KlattGrid_FORMULA_ADD_REMOVE_FBA (Oral, oral f, KlattGrid_ORAL_FORMANTS) KlattGrid_FORMULA_ADD_REMOVE_FBA (Nasal, nasal f, KlattGrid_NASAL_FORMANTS) KlattGrid_FORMULA_ADD_REMOVE_FB (NasalAnti, nasal antif, KlattGrid_NASAL_ANTIFORMANTS) KlattGrid_FORMULA_ADD_REMOVE_FB_DELTA (Delta, delta f, KlattGrid_DELTA_FORMANTS) KlattGrid_FORMULA_ADD_REMOVE_FBA (Tracheal, tracheal f, KlattGrid_TRACHEAL_FORMANTS) KlattGrid_FORMULA_ADD_REMOVE_FB (TrachealAnti, tracheal antif, KlattGrid_TRACHEAL_ANTIFORMANTS) KlattGrid_FORMULA_ADD_REMOVE_FBA (Frication, frication f, KlattGrid_FRICATION_FORMANTS) #undef KlattGrid_FORMULA_ADD_REMOVE_FB #undef KlattGrid_FORMULA_ADD_REMOVE #undef KlattGrid_ADD_FORMANT_AND_BANDWDTH_TIER #undef KlattGrid_REMOVE_FBA_VALUE #undef KlattGrid_ADD_FBA_VALUE #undef KlattGrid_FORMULA_FORMANT_FB_VALUE DIRECT (KlattGrid_extractPointProcess_glottalClosures) LOOP { iam (KlattGrid); praat_new (KlattGrid_extractPointProcess_glottalClosures (me), my name); } END FORM (KlattGrid_formula_frequencies, L"KlattGrid: Formula (frequencies)", L"Formant: Formula (frequencies)...") KlattGrid_6formants_addCommonField (dia); LABEL (L"", L"row is formant number, col is point number: for row from 1 to nrow do for col from 1 to ncol do F (row, col) :=") TEXTFIELD (L"formula", L"if row = 2 then self + 200 else self fi") OK DO int formantType = GET_INTEGER (L"Formant type"); LOOP { iam (KlattGrid); KlattGrid_formula_frequencies (me, formantType, GET_STRING (L"formula"), interpreter); praat_dataChanged (me); } END FORM (KlattGrid_formula_bandwidths, L"KlattGrid: Formula (bandwidths)", L"Formant: Formula (bandwidths)...") KlattGrid_6formants_addCommonField (dia); LABEL (L"", L"row is formant number, col is point number: for row from 1 to nrow do for col from 1 to ncol do F (row, col) :=") TEXTFIELD (L"formula", L"if row = 2 then self + 200 else self fi") OK DO int formantType = GET_INTEGER (L"Formant type"); LOOP { iam (KlattGrid); KlattGrid_formula_bandwidths (me, formantType, GET_STRING (L"formula"), interpreter); praat_dataChanged (me); } END #define KlattGrid_FORMANT_GET_FB_VALUE(Name,name,ForB,forb,FormB,formantType) \ FORM (KlattGrid_get##Name##Formant##ForB##AtTime, L"KlattGrid: Get " #name " " #forb " at time", 0) \ NATURAL (L"Formant number", L"1") \ REAL (L"Time (s)", L"0.5") \ OK \ DO \ LOOP { iam (KlattGrid); \ Melder_informationReal (KlattGrid_get##FormB##AtTime (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"Time")), L" (Hz)"); \ } \ END #define KlattGrid_FORMANT_GET_A_VALUE(Name,name,formantType) \ FORM (KlattGrid_get##Name##FormantAmplitudeAtTime, L"KlattGrid: Get " #name " formant amplitude at time", 0) \ NATURAL (L"Formant number", L"1") \ REAL (L"Time (s)", L"0.5") \ OK \ DO \ LOOP { iam (KlattGrid); \ Melder_informationReal (KlattGrid_getAmplitudeAtTime (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"Time")), L" (dB)"); \ } \ END #define KlattGrid_FORMANT_GET_FB_VALUES(Name,name,formantType) \ KlattGrid_FORMANT_GET_FB_VALUE(Name,name,Frequency,frequency,Formant,formantType) \ KlattGrid_FORMANT_GET_FB_VALUE(Name,name,Bandwidth,bandwidth,Bandwidth,formantType) KlattGrid_FORMANT_GET_FB_VALUES (Oral, oral, KlattGrid_ORAL_FORMANTS) KlattGrid_FORMANT_GET_A_VALUE (Oral, oral, KlattGrid_ORAL_FORMANTS) KlattGrid_FORMANT_GET_FB_VALUES (Nasal, nasal, KlattGrid_NASAL_FORMANTS) KlattGrid_FORMANT_GET_A_VALUE (Nasal, nasal, KlattGrid_NASAL_FORMANTS) KlattGrid_FORMANT_GET_FB_VALUES (NasalAnti, nasal anti, KlattGrid_NASAL_ANTIFORMANTS) KlattGrid_FORMANT_GET_FB_VALUES (Tracheal, tracheal f, KlattGrid_TRACHEAL_FORMANTS) KlattGrid_FORMANT_GET_A_VALUE (Tracheal, tracheal f, KlattGrid_TRACHEAL_FORMANTS) KlattGrid_FORMANT_GET_FB_VALUES (Delta, delta f, KlattGrid_DELTA_FORMANTS) KlattGrid_FORMANT_GET_FB_VALUES (TrachealAnti, tracheal antif, KlattGrid_TRACHEAL_ANTIFORMANTS) KlattGrid_FORMANT_GET_FB_VALUES (Frication, frication, KlattGrid_FRICATION_FORMANTS) KlattGrid_FORMANT_GET_A_VALUE (Frication, frication, KlattGrid_FRICATION_FORMANTS) #undef KlattGrid_FORMANT_GET_FB_VALUES #undef KlattGrid_FORMANT_GET_A_VALUE #define KlattGrid_EXTRACT_FORMANT_GRID(Name,gridType) \ DIRECT (KlattGrid_extract##Name##FormantGrid) \ LOOP { iam (KlattGrid); \ praat_new (KlattGrid_extractFormantGrid (me, gridType), formant_names[gridType]); \ } \ END #define KlattGrid_EXTRACT_FORMANT_AMPLITUDE(Name,name,formantType) \ FORM (KlattGrid_extract##Name##FormantAmplitudeTier, L"KlattGrid: Extract " #name " formant amplitude tier", 0) \ NATURAL (L"Formant number", L"1") \ OK \ DO \ LOOP { iam (KlattGrid); \ praat_new (KlattGrid_extractAmplitudeTier (me, formantType, GET_INTEGER (L"Formant number")), formant_names[formantType]); \ } \ END KlattGrid_EXTRACT_FORMANT_GRID (Oral, KlattGrid_ORAL_FORMANTS) KlattGrid_EXTRACT_FORMANT_AMPLITUDE (Oral, oral, KlattGrid_ORAL_FORMANTS) KlattGrid_EXTRACT_FORMANT_GRID (Nasal, KlattGrid_NASAL_FORMANTS) KlattGrid_EXTRACT_FORMANT_AMPLITUDE (Nasal, nasal, KlattGrid_NASAL_FORMANTS) KlattGrid_EXTRACT_FORMANT_GRID (Frication, KlattGrid_FRICATION_FORMANTS) KlattGrid_EXTRACT_FORMANT_AMPLITUDE (Frication, frication, KlattGrid_FRICATION_FORMANTS) KlattGrid_EXTRACT_FORMANT_GRID (Tracheal, KlattGrid_TRACHEAL_FORMANTS) KlattGrid_EXTRACT_FORMANT_AMPLITUDE (Tracheal, tracheal, KlattGrid_TRACHEAL_FORMANTS) KlattGrid_EXTRACT_FORMANT_GRID (NasalAnti, KlattGrid_NASAL_ANTIFORMANTS) KlattGrid_EXTRACT_FORMANT_GRID (TrachealAnti, KlattGrid_TRACHEAL_ANTIFORMANTS) KlattGrid_EXTRACT_FORMANT_GRID (Delta, KlattGrid_DELTA_FORMANTS) #undef KlattGrid_EXTRACT_FORMANTGRID #define KlattGrid_REPLACE_FORMANT_GRID(Name,formantType) \ DIRECT (KlattGrid_replace##Name##FormantGrid) \ KlattGrid me = FIRST (KlattGrid); \ FormantGrid thee = FIRST (FormantGrid); \ KlattGrid_replaceFormantGrid (me, formantType, thee); \ praat_dataChanged (me); \ END #define KlattGrid_REPLACE_FORMANT_AMPLITUDE(Name,name,formantType) \ FORM (KlattGrid_replace##Name##FormantAmplitudeTier, L"KlattGrid: Replace " #name " formant amplitude tier", 0) \ NATURAL (L"Formant number", L"1") \ OK \ DO \ KlattGrid me = FIRST (KlattGrid); \ IntensityTier thee = FIRST (IntensityTier); \ KlattGrid_replaceAmplitudeTier (me, formantType, GET_INTEGER (L"Formant number"), thee); \ praat_dataChanged (me); \ END KlattGrid_REPLACE_FORMANT_GRID (Oral, KlattGrid_ORAL_FORMANTS) KlattGrid_REPLACE_FORMANT_AMPLITUDE (Oral, oral, KlattGrid_ORAL_FORMANTS) KlattGrid_REPLACE_FORMANT_GRID (Nasal, KlattGrid_NASAL_FORMANTS) KlattGrid_REPLACE_FORMANT_AMPLITUDE (Nasal, nasal, KlattGrid_NASAL_FORMANTS) KlattGrid_REPLACE_FORMANT_GRID (NasalAnti, KlattGrid_NASAL_ANTIFORMANTS) KlattGrid_REPLACE_FORMANT_GRID (Tracheal, KlattGrid_TRACHEAL_FORMANTS) KlattGrid_REPLACE_FORMANT_AMPLITUDE (Tracheal, tracheal, KlattGrid_TRACHEAL_FORMANTS) KlattGrid_REPLACE_FORMANT_GRID (TrachealAnti, KlattGrid_TRACHEAL_ANTIFORMANTS) KlattGrid_REPLACE_FORMANT_GRID (Delta, KlattGrid_DELTA_FORMANTS) KlattGrid_REPLACE_FORMANT_GRID (Frication, KlattGrid_FRICATION_FORMANTS) KlattGrid_REPLACE_FORMANT_AMPLITUDE (Frication, frication, KlattGrid_FRICATION_FORMANTS) #undef KlattGrid_REPLACE_FORMANT_AMPLITUDE #undef KlattGrid_REPLACE_FORMANTGRID #define KlattGrid_FORMANT_GET_ADD_REMOVE(Name,name,unit,default,require,requiremessage) \ FORM (KlattGrid_get##Name##AtTime, L"KlattGrid: Get " #name " at time", 0) \ KlattGrid_6formants_addCommonField (dia); \ NATURAL (L"Formant number", L"1") \ REAL (L"Time (s)", L"0.5") \ OK \ DO \ int formantType = GET_INTEGER (L"Formant type"); \ LOOP { iam (KlattGrid); \ Melder_informationReal (KlattGrid_get##Name##AtTime (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"Time")), L" (Hz)"); \ } \ END \ FORM (KlattGrid_getDelta##Name##AtTime, L"KlattGrid: Get delta " #name " at time", 0) \ NATURAL (L"Formant number", L"1") \ REAL (L"Time (s)", L"0.5") \ OK \ DO \ LOOP { iam (KlattGrid); \ Melder_informationReal (KlattGrid_getDelta##Name##AtTime (me, GET_INTEGER (L"Formant number"), GET_REAL (L"Time")), L" (Hz)"); \ } \ END \ FORM (KlattGrid_add##Name##Point, L"KlattGrid: Add " #name " point", 0) \ KlattGrid_6formants_addCommonField (dia); \ NATURAL (L"Formant number", L"1") \ REAL (L"Time (s)", L"0.5") \ REAL (L"Value" unit, default) \ OK \ DO \ int formantType = GET_INTEGER (L"Formant type"); \ double value = GET_REAL (L"Value"); \ REQUIRE (require, requiremessage) \ LOOP { iam (KlattGrid); \ KlattGrid_add##Name##Point (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"Time"), value); \ praat_dataChanged (me); \ } \ END \ FORM (KlattGrid_addDelta##Name##Point, L"KlattGrid: Add delta " #name " point", 0) \ NATURAL (L"Formant number", L"1") \ REAL (L"Time (s)", L"0.5") \ REAL (L"Value" unit, default) \ OK \ DO \ double value = GET_REAL (L"Value"); \ REQUIRE (require, requiremessage) \ LOOP { iam (KlattGrid); \ KlattGrid_addDelta##Name##Point (me, GET_INTEGER (L"Formant number"), GET_REAL (L"Time"), value); \ praat_dataChanged (me); \ } \ END \ FORM (KlattGrid_remove##Name##Points, L"Remove " #name " points", 0) \ KlattGrid_6formants_addCommonField (dia); \ NATURAL (L"Formant number", L"1") \ REAL (L"From time (s)", L"0.3")\ REAL (L"To time (s)", L"0.7") \ OK \ DO \ int formantType = GET_INTEGER (L"Formant type"); \ LOOP { iam (KlattGrid); \ KlattGrid_remove##Name##Points (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"From time"), GET_REAL (L"To time")); \ praat_dataChanged (me);\ } \ END \ FORM (KlattGrid_removeDelta##Name##Points, L"Remove delta " #name " points", 0) \ NATURAL (L"Formant number", L"1") \ REAL (L"From time (s)", L"0.3")\ REAL (L"To time (s)", L"0.7") \ OK \ DO \ LOOP { iam (KlattGrid); \ KlattGrid_removeDelta##Name##Points (me, GET_INTEGER (L"Formant number"), GET_REAL (L"From time"), GET_REAL (L"To time")); \ praat_dataChanged (me);\ } \ END KlattGrid_FORMANT_GET_ADD_REMOVE (Formant, formant, L" (Hz)", L"500.0", (value > 0), L"Frequency must be greater than zero.") KlattGrid_FORMANT_GET_ADD_REMOVE (Bandwidth, bandwidth, L" (Hz)", L"50.0", (value > 0), L"Bandwidth must be greater than zero.") #undef KlattGrid_FORMANT_GET_ADD_REMOVE FORM (KlattGrid_addFormantAndBandwidthTier, L"", 0) KlattGrid_7formants_addCommonField (dia); INTEGER (L"Position", L"0 (=at end)") OK DO long gridType = GET_INTEGER (L"Formant type"); LOOP { iam (KlattGrid); KlattGrid_addFormantAndBandwidthTier (me, gridType, GET_INTEGER (L"Position")); praat_dataChanged (me); } END FORM (KlattGrid_extractFormantGrid, L"KlattGrid: Extract formant grid", 0) KlattGrid_6formants_addCommonField (dia); OK DO long gridType = GET_INTEGER (L"Formant type"); LOOP { iam (KlattGrid); praat_new (KlattGrid_extractFormantGrid (me, gridType), formant_names[gridType]); } END FORM (KlattGrid_replaceFormantGrid, L"KlattGrid: Replace formant grid", 0) KlattGrid_6formants_addCommonField (dia); OK DO KlattGrid me = FIRST (KlattGrid); FormantGrid thee = FIRST (FormantGrid); KlattGrid_replaceFormantGrid (me, GET_INTEGER (L"Formant type"), thee); praat_dataChanged (OBJECT); END FORM (KlattGrid_getAmplitudeAtTime, L"KlattGrid: Get amplitude at time", 0) \ KlattGrid_4formants_addCommonField (dia); NATURAL (L"Formant number", L"1") REAL (L"Time (s)", L"0.5") OK DO int formantType = GET_INTEGER (L"Formant type"); LOOP { iam (KlattGrid); Melder_informationReal (KlattGrid_getAmplitudeAtTime (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"Time")), L" (dB)"); } END FORM (KlattGrid_addAmplitudePoint, L"KlattGrid: Add amplitude point", 0) KlattGrid_4formants_addCommonField (dia); NATURAL (L"Formant number", L"1") REAL (L"Time (s)", L"0.5") REAL (L"Value (Hz)", L"80.0") OK DO int formantType = GET_INTEGER (L"Formant type"); double value = GET_REAL (L"Value"); LOOP { iam (KlattGrid); KlattGrid_addAmplitudePoint (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"Time"), value); praat_dataChanged (me); } END FORM (KlattGrid_removeAmplitudePoints, L"Remove amplitude points", 0) \ KlattGrid_4formants_addCommonField (dia); NATURAL (L"Formant number", L"1") REAL (L"From time (s)", L"0.3") REAL (L"To time (s)", L"0.7") OK DO int formantType = GET_INTEGER (L"Formant type"); LOOP { iam (KlattGrid); KlattGrid_removeAmplitudePoints (me, formantType, GET_INTEGER (L"Formant number"), GET_REAL (L"From time"), GET_REAL (L"To time")); praat_dataChanged (me); } END FORM (KlattGrid_extractAmplitudeTier, L"", 0) KlattGrid_4formants_addCommonField (dia); NATURAL (L"Formant number", L"1") OK DO int formantType = GET_INTEGER (L"Formant type"); LOOP { iam (KlattGrid); praat_new (KlattGrid_extractAmplitudeTier (me, formantType, GET_INTEGER (L"Formant number")), formant_names[formantType]); } END FORM (KlattGrid_replaceAmplitudeTier, L"KlattGrid: Replace amplitude tier", 0) KlattGrid_4formants_addCommonField (dia); NATURAL (L"Formant number", L"1") OK DO int formantType = GET_INTEGER (L"Formant type"); KlattGrid me = FIRST (KlattGrid); IntensityTier thee = FIRST (IntensityTier); KlattGrid_replaceAmplitudeTier (me, formantType, GET_INTEGER (L"Formant number"), thee); praat_dataChanged (me); END FORM (KlattGrid_to_Sound_special, L"KlattGrid: To Sound (special)", L"KlattGrid: To Sound (special)...") KlattGrid_PlayOptions_addCommonFields (dia, 1); OK DO LOOP { iam (KlattGrid); KlattGrid_setDefaultPlayOptions (me); KlattGrid_PlayOptions_getCommonFields (dia, 1, me); praat_new (KlattGrid_to_Sound (me), my name); } END DIRECT (KlattGrid_to_Sound) LOOP { iam (KlattGrid); KlattGrid_setDefaultPlayOptions (me); praat_new (KlattGrid_to_Sound (me), my name); } END FORM (KlattGrid_playSpecial, L"KlattGrid: Play special", L"KlattGrid: Play special...") KlattGrid_PlayOptions_addCommonFields (dia, 0); OK DO LOOP { iam (KlattGrid); KlattGrid_setDefaultPlayOptions (me); KlattGrid_PlayOptions_getCommonFields (dia, 0, me); KlattGrid_playSpecial (me); } END FORM (KlattGrid_to_Sound_phonation, L"KlattGrid: To Sound (phonation)", L"KlattGrid: To Sound (phonation)...") POSITIVE (L"Sampling frequency (Hz)", L"44100") KlattGrid_PhonationGridPlayOptions_addCommonFields (dia); OK DO LOOP { iam (KlattGrid); KlattGrid_PhonationGridPlayOptions_getCommonFields (dia, me); my options -> samplingFrequency = GET_REAL (L"Sampling frequency"); praat_new (KlattGrid_to_Sound_phonation (me), my name, L"_phonation"); } END DIRECT (KlattGrid_help) Melder_help (L"KlattGrid"); END DIRECT (KlattGrid_play) LOOP { iam (KlattGrid); KlattGrid_play (me); } END FORM (KlattGrid_draw, L"KlattGrid: Draw", 0) RADIO (L"Synthesis model", 1) RADIOBUTTON (L"Cascade") RADIOBUTTON (L"Parallel") OK DO autoPraatPicture picture; LOOP { iam (KlattGrid); KlattGrid_draw (me, GRAPHICS, GET_INTEGER (L"Synthesis model") - 1); } END FORM (KlattGrid_drawVocalTract, L"KlattGrid: Draw vocal tract", 0) RADIO (L"Synthesis model", 1) RADIOBUTTON (L"Cascade") RADIOBUTTON (L"Parallel") BOOLEAN (L"Include tracheal formants", 1); OK DO autoPraatPicture picture; LOOP { iam (KlattGrid); KlattGrid_drawVocalTract (me, GRAPHICS, GET_INTEGER (L"Synthesis model") - 1, GET_INTEGER (L"Include tracheal formants")); } END DIRECT (KlattGrid_drawPhonation) autoPraatPicture picture; LOOP { iam (KlattGrid); PhonationGrid_draw (my phonation, GRAPHICS); } END DIRECT (KlattGrid_drawFrication) autoPraatPicture picture; LOOP { iam (KlattGrid); FricationGrid_draw (my frication, GRAPHICS); } END FORM (KlattGrid_to_oralFormantGrid_openPhases, L"KlattGrid: Extract oral formant grid (open phases)", L"KlattGrid: Extract oral formant grid (open phases)...") REAL (L"Fade fraction (0..0.5)", L"0.1") OK DO double fadeFraction = GET_REAL (L"Fade fraction"); REQUIRE (fadeFraction < 0.5, L"Fade fraction has to be smaller than 0.5.") LOOP { iam (KlattGrid); praat_new (KlattGrid_to_oralFormantGrid_openPhases (me, fadeFraction), L"corrected"); } END FORM (Sound_KlattGrid_filterByVocalTract, L"Sound & KlattGrid: Filter by vocal tract", L"Sound & KlattGrid: Filter by vocal tract...") RADIO (L"Vocal tract filter model", 1) RADIOBUTTON (L"Cascade") RADIOBUTTON (L"Parallel") OK DO Sound me = FIRST (Sound); KlattGrid thee = FIRST (KlattGrid); int filterModel = GET_INTEGER (L"Vocal tract filter model") - 1; praat_new (Sound_KlattGrid_filterByVocalTract (me, thee, filterModel), my name, L"_", thy name); END void praat_KlattGrid_init (); void praat_KlattGrid_init () { Thing_recognizeClassesByName (classKlattGrid, NULL); praat_addMenuCommand (L"Objects", L"New", L"Acoustic synthesis (Klatt)", 0, 0, 0); praat_addMenuCommand (L"Objects", L"New", L"KlattGrid help", 0, 1, DO_KlattGrid_help); praat_addMenuCommand (L"Objects", L"New", L"-- the synthesizer grid --", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Create KlattGrid...", 0, 1, DO_KlattGrid_create); praat_addMenuCommand (L"Objects", L"New", L"Create KlattGrid example", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_createExample); /* Edit oral/nasal/tracheal/frication/delta formant grid Edit nasal/tracheal antiformant grid Get oral/nasal/tracheal/frication/delta formant at time... Get nasal/tracheal antiformant at time... Get oral/nasal/tracheal/frication/delta formant bandwidth at time... Get nasal/tracheal antiformant bandwidth at time... Get oral/nasal/tracheal/frication formant amplitude at time... Formula (oral/nasal/tracheal/frication/delta formant frequencies)... Formula (nasal/tracheal antiformant frequencies)... Formula (oral/nasal/tracheal/frication/delta formant bandwidths)... Formula (nasal/tracheal antiformant bandwidths)... Add oral/nasal/tracheal/frication/delta formant point... Add nasal/tracheal antiformant point... Add oral/nasal/tracheal/frication/delta formant bandwidth point... Add nasal/tracheal antiformant bandwidth point... Add oral/nasal/tracheal/frication formant amplitude point... Remove oral/nasal/tracheal/frication/delta formant points... Remove nasal/tracheal antiformant points... Remove oral/nasal/tracheal/frication/delta bandwidth points... Remove nasal/tracheal antiformant bandwidth points... Remove oral/nasal/tracheal/frication formant amplitude points... Extract oral/nasal/tracheal/frication/delta formant grid Extract nasal/tracheal antiformant grid Replace oral/nasal/tracheal/frication/delta formant grid Replace nasal/tracheal antiformant grid Add oral/nasal/tracheal/frication/delta formant and bandwidth tier Add nasal/tracheal antiformant and bandwidth tier #define KlattGrid_ORAL_FORMANTS 1 #define KlattGrid_NASAL_FORMANTS 2 #define KlattGrid_FRICATION_FORMANTS 3 #define KlattGrid_TRACHEAL_FORMANTS 4 #define KlattGrid_NASAL_ANTIFORMANTS 5 #define KlattGrid_TRACHEAL_ANTIFORMANTS 6 #define KlattGrid_DELTA_FORMANTS 7 */ praat_addAction1 (classKlattGrid, 0, L"KlattGrid help", 0, 0, DO_KlattGrid_help); praat_addAction1 (classKlattGrid, 0, L"Edit phonation -", 0, 0, 0); praat_addAction1 (classKlattGrid, 0, L"Edit pitch tier", 0, 1, DO_KlattGrid_editPitchTier); praat_addAction1 (classKlattGrid, 0, L"Edit voicing amplitude tier", 0, 1, DO_KlattGrid_editVoicingAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Edit flutter tier", 0, 1, DO_KlattGrid_editFlutterTier); praat_addAction1 (classKlattGrid, 0, L"Edit power1 tier", 0, 1, DO_KlattGrid_editPower1Tier); praat_addAction1 (classKlattGrid, 0, L"Edit power2 tier", 0, 1, DO_KlattGrid_editPower2Tier); praat_addAction1 (classKlattGrid, 0, L"Edit open phase tier", 0, 1, DO_KlattGrid_editOpenPhaseTier); praat_addAction1 (classKlattGrid, 0, L"Edit collision phase tier", 0, 1, DO_KlattGrid_editCollisionPhaseTier); praat_addAction1 (classKlattGrid, 0, L"Edit double pulsing tier", 0, 1, DO_KlattGrid_editDoublePulsingTier); praat_addAction1 (classKlattGrid, 0, L"Edit spectral tilt tier", 0, 1, DO_KlattGrid_editSpectralTiltTier); praat_addAction1 (classKlattGrid, 0, L"Edit aspiration amplitude tier", 0, 1, DO_KlattGrid_editAspirationAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Edit breathiness amplitude tier", 0, 1, DO_KlattGrid_editBreathinessAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Edit filters -", 0, 0, 0); praat_addAction1 (classKlattGrid, 0, L"Edit oral formant grid", 0, 1, DO_KlattGrid_editOralFormantGrid); praat_addAction1 (classKlattGrid, 0, L"Edit nasal formant grid", 0, 1, DO_KlattGrid_editNasalFormantGrid); praat_addAction1 (classKlattGrid, 0, L"Edit nasal antiformant grid", 0, 1, DO_KlattGrid_editNasalAntiFormantGrid); praat_addAction1 (classKlattGrid, 0, L"Edit oral formant amplitude tier...", 0, 1, DO_KlattGrid_editOralFormantAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Edit nasal formant amplitude tier...", 0, 1, DO_KlattGrid_editNasalFormantAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"-- edit delta formant grid --", 0, 1, 0); praat_addAction1 (classKlattGrid, 0, L"Edit delta formant grid", 0, 1, DO_KlattGrid_editDeltaFormantGrid); praat_addAction1 (classKlattGrid, 0, L"Edit tracheal formant grid", 0, 1, DO_KlattGrid_editTrachealFormantGrid); praat_addAction1 (classKlattGrid, 0, L"Edit tracheal antiformant grid", 0, 1, DO_KlattGrid_editTrachealAntiFormantGrid); praat_addAction1 (classKlattGrid, 0, L"Edit tracheal formant amplitude tier...", 0, 1, DO_KlattGrid_editTrachealFormantAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"-- edit frication tiers --", 0, 1, 0); praat_addAction1 (classKlattGrid, 1, L"Edit frication amplitude tier", 0, 1, DO_KlattGrid_editFricationAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Edit frication formant grid", 0, 1, DO_KlattGrid_editFricationFormantGrid); praat_addAction1 (classKlattGrid, 0, L"Edit frication formant amplitude tier...", 0, 1, DO_KlattGrid_editFricationFormantAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Edit frication bypass tier", 0, 1, DO_KlattGrid_editFricationBypassTier); praat_addAction1 (classKlattGrid, 1, L"Edit frication amplitude tier", 0, 1, DO_KlattGrid_editFricationAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Play", 0, 0, DO_KlattGrid_play); praat_addAction1 (classKlattGrid, 0, L"Play special...", 0, 0, DO_KlattGrid_playSpecial); praat_addAction1 (classKlattGrid, 0, L"To Sound", 0, 0, DO_KlattGrid_to_Sound); praat_addAction1 (classKlattGrid, 0, L"To Sound (special)...", 0, 0, DO_KlattGrid_to_Sound_special); praat_addAction1 (classKlattGrid, 0, L"To Sound (phonation)...", 0, 0, DO_KlattGrid_to_Sound_phonation); praat_addAction1 (classKlattGrid, 0, L"Draw -", 0, 0, 0); praat_addAction1 (classKlattGrid, 0, L"Draw synthesizer...", 0, 1, DO_KlattGrid_draw); praat_addAction1 (classKlattGrid, 0, L"Draw vocal tract...", 0, 1, DO_KlattGrid_drawVocalTract); praat_addAction1 (classKlattGrid, 0, L"Draw phonation", 0, 1, DO_KlattGrid_drawPhonation); praat_addAction1 (classKlattGrid, 0, L"Draw frication", 0, 1, DO_KlattGrid_drawFrication); praat_addAction1 (classKlattGrid, 0, L"Query phonation -", 0, 0, 0); praat_addAction1 (classKlattGrid, 1, L"Get pitch at time...", 0, 1, DO_KlattGrid_getPitchAtTime); praat_addAction1 (classKlattGrid, 1, L"Get voicing amplitude at time...", 0, 1, DO_KlattGrid_getVoicingAmplitudeAtTime); praat_addAction1 (classKlattGrid, 1, L"Get flutter at time...", 0, 1, DO_KlattGrid_getFlutterAtTime); praat_addAction1 (classKlattGrid, 1, L"Get power1 at time...", 0, 1, DO_KlattGrid_getPower1AtTime); praat_addAction1 (classKlattGrid, 1, L"Get power2 at time...", 0, 1, DO_KlattGrid_getPower2AtTime); praat_addAction1 (classKlattGrid, 1, L"Get open phase at time...", 0, 1, DO_KlattGrid_getOpenPhaseAtTime); praat_addAction1 (classKlattGrid, 1, L"Get collision phase at time...", 0, 1, DO_KlattGrid_getCollisionPhaseAtTime); praat_addAction1 (classKlattGrid, 1, L"Get double pulsing at time...", 0, 1, DO_KlattGrid_getDoublePulsingAtTime); praat_addAction1 (classKlattGrid, 1, L"Get spectral tilt at time...", 0, 1, DO_KlattGrid_getSpectralTiltAtTime); praat_addAction1 (classKlattGrid, 1, L"Get aspiration amplitude at time...", 0, 1, DO_KlattGrid_getAspirationAmplitudeAtTime); praat_addAction1 (classKlattGrid, 1, L"Get breathiness amplitude at time...", 0, 1, DO_KlattGrid_getBreathinessAmplitudeAtTime); praat_addAction1 (classKlattGrid, 0, L"Query filters -", 0, 0, 0); praat_addAction1 (classKlattGrid, 1, L"Get formant at time...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_getFormantAtTime); praat_addAction1 (classKlattGrid, 1, L"Get bandwidth at time...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_getBandwidthAtTime); praat_addAction1 (classKlattGrid, 1, L"Get amplitude at time...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_getAmplitudeAtTime); praat_addAction1 (classKlattGrid, 1, L"Get delta formant at time...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_getDeltaFormantAtTime); praat_addAction1 (classKlattGrid, 1, L"Get delta bandwidth at time...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_getDeltaBandwidthAtTime); #define KlattGRID_GET_FORMANT_FB_VALUES_ACTION(Name,namef) \ praat_addAction1 (classKlattGrid, 1, L"Get " #namef "ormant frequency at time...", 0, 1, DO_KlattGrid_get##Name##FormantFrequencyAtTime); \ praat_addAction1 (classKlattGrid, 1, L"Get " #namef "ormant bandwidth at time...", 0, 1, DO_KlattGrid_get##Name##FormantBandwidthAtTime); #define KlattGRID_GET_FORMANT_A_VALUES_ACTION(Name,name) \ praat_addAction1 (classKlattGrid, 1, L"Get " #name " formant amplitude at time...", 0, 1, DO_KlattGrid_get##Name##FormantAmplitudeAtTime); \ KlattGRID_GET_FORMANT_FB_VALUES_ACTION (Oral, oral f) KlattGRID_GET_FORMANT_A_VALUES_ACTION (Oral, oral) KlattGRID_GET_FORMANT_FB_VALUES_ACTION (Nasal, nasal f) KlattGRID_GET_FORMANT_A_VALUES_ACTION (Nasal, nasal) KlattGRID_GET_FORMANT_FB_VALUES_ACTION (NasalAnti, nasal antif) praat_addAction1 (classKlattGrid, 1, L"-- query delta characteristics", 0, 1, 0); KlattGRID_GET_FORMANT_FB_VALUES_ACTION (Delta, delta f) KlattGRID_GET_FORMANT_FB_VALUES_ACTION (Tracheal, tracheal f) KlattGRID_GET_FORMANT_A_VALUES_ACTION (Tracheal, tracheal) KlattGRID_GET_FORMANT_FB_VALUES_ACTION (TrachealAnti, tracheal antif) praat_addAction1 (classKlattGrid, 1, L"-- query frication characteristics", 0, 1, 0); KlattGRID_GET_FORMANT_FB_VALUES_ACTION (Frication, frication f) KlattGRID_GET_FORMANT_A_VALUES_ACTION (Frication, frication) #undef KlattGRID_GET_FORMANT_A_VALUES_ACTION #undef KlattGRID_GET_FORMANT_A_VALUES_ACTION praat_addAction1 (classKlattGrid, 1, L"Get frication bypass at time...", 0, 1, DO_KlattGrid_getFricationBypassAtTime); praat_addAction1 (classKlattGrid, 1, L"Get frication amplitude at time...", 0, 1, DO_KlattGrid_getFricationAmplitudeAtTime); praat_addAction1 (classKlattGrid, 0, L"Modify phonation -", 0, 0, 0); praat_addAction1 (classKlattGrid, 0, L"Add pitch point...", 0, 1, DO_KlattGrid_addPitchPoint); praat_addAction1 (classKlattGrid, 0, L"Add voicing amplitude point...", 0, 1, DO_KlattGrid_addVoicingAmplitudePoint); praat_addAction1 (classKlattGrid, 0, L"Add flutter point...", 0, 1, DO_KlattGrid_addFlutterPoint); praat_addAction1 (classKlattGrid, 0, L"Add power1 point...", 0, 1, DO_KlattGrid_addPower1Point); praat_addAction1 (classKlattGrid, 0, L"Add power2 point...", 0, 1, DO_KlattGrid_addPower2Point); praat_addAction1 (classKlattGrid, 0, L"Add open phase point...", 0, 1, DO_KlattGrid_addOpenPhasePoint); praat_addAction1 (classKlattGrid, 0, L"Add collision phase point...", 0, 1, DO_KlattGrid_addCollisionPhasePoint); praat_addAction1 (classKlattGrid, 0, L"Add double pulsing point...", 0, 1, DO_KlattGrid_addDoublePulsingPoint); praat_addAction1 (classKlattGrid, 0, L"Add spectral tilt point...", 0, 1, DO_KlattGrid_addSpectralTiltPoint); praat_addAction1 (classKlattGrid, 0, L"Add aspiration amplitude point...", 0, 1, DO_KlattGrid_addAspirationAmplitudePoint); praat_addAction1 (classKlattGrid, 0, L"Add breathiness amplitude point...", 0, 1, DO_KlattGrid_addBreathinessAmplitudePoint); #define KlattGrid_REMOVE_POINTS_ACTION(Name,name) \ praat_addAction1 (classKlattGrid, 0, L"Remove " #name " points between...", 0, praat_DEPTH_1+praat_HIDDEN, DO_KlattGrid_remove##Name##Points); \ praat_addAction1 (classKlattGrid, 0, L"Remove " #name " points...", 0, 1, DO_KlattGrid_remove##Name##Points); KlattGrid_REMOVE_POINTS_ACTION (Pitch, pitch) KlattGrid_REMOVE_POINTS_ACTION (VoicingAmplitude, voicing amplitude) KlattGrid_REMOVE_POINTS_ACTION (Flutter, flutter) KlattGrid_REMOVE_POINTS_ACTION (Power1, power1) KlattGrid_REMOVE_POINTS_ACTION (Power2, power2) KlattGrid_REMOVE_POINTS_ACTION (OpenPhase, open phase) KlattGrid_REMOVE_POINTS_ACTION (CollisionPhase, collision phase) KlattGrid_REMOVE_POINTS_ACTION (DoublePulsing, double pulsing) KlattGrid_REMOVE_POINTS_ACTION (SpectralTilt, spectral tilt) KlattGrid_REMOVE_POINTS_ACTION (AspirationAmplitude, aspiration amplitude) KlattGrid_REMOVE_POINTS_ACTION (BreathinessAmplitude, breathiness amplitude) praat_addAction1 (classKlattGrid, 0, L"Modify vocal tract -", 0, 0, 0); #define KlattGrid_MODIFY_ACTION_FBA(Name,namef) \ praat_addAction1 (classKlattGrid, 0, L"Formula (" #namef "ormant frequencies)...", 0, 1, DO_KlattGrid_formula##Name##FormantFrequencies); \ praat_addAction1 (classKlattGrid, 0, L"Formula (" #namef "ormant bandwidths)...", 0, 1, DO_KlattGrid_formula##Name##FormantBandwidths); \ praat_addAction1 (classKlattGrid, 0, L"Add " #namef "ormant frequency point...", 0, 1, DO_KlattGrid_add##Name##FormantFrequencyPoint); \ praat_addAction1 (classKlattGrid, 0, L"Add " #namef "ormant bandwidth point...", 0, 1, DO_KlattGrid_add##Name##FormantBandwidthPoint); \ praat_addAction1 (classKlattGrid, 0, L"Add " #namef "ormant amplitude point...", 0, 1, DO_KlattGrid_add##Name##FormantAmplitudePoint); \ praat_addAction1 (classKlattGrid, 0, L"Remove " #namef "ormant frequency points...", 0, 1, DO_KlattGrid_remove##Name##FormantFrequencyPoints); \ praat_addAction1 (classKlattGrid, 0, L"Remove " #namef "ormant bandwidth points...", 0, 1, DO_KlattGrid_remove##Name##FormantBandwidthPoints); \ praat_addAction1 (classKlattGrid, 0, L"Remove " #namef "ormant amplitude points...", 0, 1, DO_KlattGrid_remove##Name##FormantAmplitudePoints); \ praat_addAction1 (classKlattGrid, 0, L"Add " #namef "ormant...", 0, 1, DO_KlattGrid_add##Name##Formant); \ praat_addAction1 (classKlattGrid, 0, L"Remove " #namef "ormant...", 0, 1, DO_KlattGrid_remove##Name##Formant); #define KlattGrid_MODIFY_ACTION_FB(Name,namef) \ praat_addAction1 (classKlattGrid, 0, L"Formula (" #namef "ormant frequencies)...", 0, 1, DO_KlattGrid_formula##Name##FormantFrequencies); \ praat_addAction1 (classKlattGrid, 0, L"Formula (" #namef "ormant bandwidths)...", 0, 1, DO_KlattGrid_formula##Name##FormantBandwidths); \ praat_addAction1 (classKlattGrid, 0, L"Add " #namef "ormant frequency point...", 0, 1, DO_KlattGrid_add##Name##FormantFrequencyPoint); \ praat_addAction1 (classKlattGrid, 0, L"Add " #namef "ormant bandwidth point...", 0, 1, DO_KlattGrid_add##Name##FormantBandwidthPoint); \ praat_addAction1 (classKlattGrid, 0, L"Remove " #namef "ormant frequency points...", 0, 1, DO_KlattGrid_remove##Name##FormantFrequencyPoints); \ praat_addAction1 (classKlattGrid, 0, L"Remove " #namef "ormant bandwidth points...", 0, 1, DO_KlattGrid_remove##Name##FormantBandwidthPoints); \ praat_addAction1 (classKlattGrid, 0, L"Add " #namef "ormant...", 0, 1, DO_KlattGrid_add##Name##Formant); \ praat_addAction1 (classKlattGrid, 0, L"Remove " #namef "ormant...", 0, 1, DO_KlattGrid_remove##Name##Formant); KlattGrid_MODIFY_ACTION_FBA (Oral, oral f) praat_addAction1 (classKlattGrid, 0, L"-- oral modify separator --", 0, 1, 0); KlattGrid_MODIFY_ACTION_FBA (Nasal, nasal f) praat_addAction1 (classKlattGrid, 0, L"-- nasal modify separator --", 0, 1, 0); KlattGrid_MODIFY_ACTION_FB (NasalAnti, nasal antif) praat_addAction1 (classKlattGrid, 0, L"Formula (frequencies)...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_formula_frequencies); praat_addAction1 (classKlattGrid, 0, L"Formula (bandwidths)...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_formula_bandwidths); praat_addAction1 (classKlattGrid, 0, L"Add formant point...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_addFormantPoint); praat_addAction1 (classKlattGrid, 0, L"Add bandwidth point...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_addBandwidthPoint); praat_addAction1 (classKlattGrid, 0, L"Add amplitude point...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_addAmplitudePoint); praat_addAction1 (classKlattGrid, 0, L"Remove formant points between...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_removeFormantPoints); praat_addAction1 (classKlattGrid, 0, L"Remove bandwidth points between...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_removeBandwidthPoints); praat_addAction1 (classKlattGrid, 0, L"Remove amplitude points between...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_removeAmplitudePoints); praat_addAction1 (classKlattGrid, 0, L"Modify coupling - ", 0, 0, 0); KlattGrid_MODIFY_ACTION_FB (Delta, delta f) praat_addAction1 (classKlattGrid, 0, L"-- delta modify separator --", 0, 1, 0); KlattGrid_MODIFY_ACTION_FBA (Tracheal, tracheal f) praat_addAction1 (classKlattGrid, 0, L"-- nasal modify separator --", 0, 1, 0); KlattGrid_MODIFY_ACTION_FB (TrachealAnti, tracheal antif) praat_addAction1 (classKlattGrid, 0, L"Add delta formant point...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_addDeltaFormantPoint); praat_addAction1 (classKlattGrid, 0, L"Add delta bandwidth point...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_addDeltaBandwidthPoint); praat_addAction1 (classKlattGrid, 0, L"Remove delta formant points between...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_removeDeltaFormantPoints); praat_addAction1 (classKlattGrid, 0, L"Remove delta bandwidth points between...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_removeDeltaBandwidthPoints); praat_addAction1 (classKlattGrid, 0, L"Modify frication -", 0, 0, 0); KlattGrid_MODIFY_ACTION_FBA (Frication, frication f) praat_addAction1 (classKlattGrid, 0, L"-- frication modify separator --", 0, 1, 0); praat_addAction1 (classKlattGrid, 0, L"Add frication bypass point...", 0, 1, DO_KlattGrid_addFricationBypassPoint); praat_addAction1 (classKlattGrid, 0, L"Add frication amplitude point...", 0, 1, DO_KlattGrid_addFricationAmplitudePoint); KlattGrid_REMOVE_POINTS_ACTION (FricationBypass, frication bypass) KlattGrid_REMOVE_POINTS_ACTION (FricationAmplitude, frication amplitude) praat_addAction1 (classKlattGrid, 0, L"Add formant and bandwidth tier...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_addFormantAndBandwidthTier); #undef KlattGrid_REMOVE_POINTS_ACTION #undef KlattGrid_MODIFY_ACTION_FB #undef KlattGrid_MODIFY_ACTION_FBA praat_addAction1 (classKlattGrid, 0, L"Extract phonation -", 0, 0, 0); praat_addAction1 (classKlattGrid, 0, L"Extract pitch tier", 0, 1, DO_KlattGrid_extractPitchTier); praat_addAction1 (classKlattGrid, 0, L"Extract voicing amplitude tier", 0, 1, DO_KlattGrid_extractVoicingAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Extract flutter tier", 0, 1, DO_KlattGrid_extractFlutterTier); praat_addAction1 (classKlattGrid, 0, L"Extract power1 tier", 0, 1, DO_KlattGrid_extractPower1Tier); praat_addAction1 (classKlattGrid, 0, L"Extract power2 tier", 0, 1, DO_KlattGrid_extractPower2Tier); praat_addAction1 (classKlattGrid, 0, L"Extract open phase tier", 0, 1, DO_KlattGrid_extractOpenPhaseTier); praat_addAction1 (classKlattGrid, 0, L"Extract collision phase tier", 0, 1, DO_KlattGrid_extractCollisionPhaseTier); praat_addAction1 (classKlattGrid, 0, L"Extract double pulsing tier", 0, 1, DO_KlattGrid_extractDoublePulsingTier); praat_addAction1 (classKlattGrid, 0, L"Extract spectral tilt tier", 0, 1, DO_KlattGrid_extractSpectralTiltTier); praat_addAction1 (classKlattGrid, 0, L"Extract aspiration amplitude tier", 0, 1, DO_KlattGrid_extractAspirationAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Extract breathiness amplitude tier", 0, 1, DO_KlattGrid_extractBreathinessAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"-- extract glottal events--", 0, 1, 0); praat_addAction1 (classKlattGrid, 0, L"Extract PointProcess (glottal closures)", 0, 1, DO_KlattGrid_extractPointProcess_glottalClosures); #define KlattGRID_EXTRACT_FORMANT_GRID_ACTION(Name,namef) \ praat_addAction1 (classKlattGrid, 0, L"Extract " #namef "ormant grid", 0, 1, DO_KlattGrid_extract##Name##FormantGrid); #define KlattGRID_EXTRACT_FORMANT_AMPLITUDE_ACTION(Name,name) \ praat_addAction1 (classKlattGrid, 0, L"Extract " #name " formant amplitude tier...", 0, 1, DO_KlattGrid_extract##Name##FormantAmplitudeTier); praat_addAction1 (classKlattGrid, 0, L"Extract filters -", 0, 0, 0); praat_addAction1 (classKlattGrid, 0, L"Extract formant grid...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_extractFormantGrid); // deprecated KlattGRID_EXTRACT_FORMANT_GRID_ACTION (Oral, oral f) praat_addAction1 (classKlattGrid, 0, L"Extract amplitude tier...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_KlattGrid_extractAmplitudeTier); // deprecated praat_addAction1 (classKlattGrid, 0, L"Extract formant grid (open phases)...", 0, praat_HIDDEN + praat_DEPTH_1, DO_KlattGrid_to_oralFormantGrid_openPhases); praat_addAction1 (classKlattGrid, 0, L"Extract oral formant grid (open phases)...", 0, 1, DO_KlattGrid_to_oralFormantGrid_openPhases); KlattGRID_EXTRACT_FORMANT_AMPLITUDE_ACTION (Oral, oral) KlattGRID_EXTRACT_FORMANT_GRID_ACTION (Nasal, nasal f) KlattGRID_EXTRACT_FORMANT_AMPLITUDE_ACTION (Nasal, nasal) KlattGRID_EXTRACT_FORMANT_GRID_ACTION (NasalAnti, nasal antif) praat_addAction1 (classKlattGrid, 0, L"-- extract delta characteristics", 0, 1, 0); praat_addAction1 (classKlattGrid, 0, L"Extract delta formant grid", 0, 1, DO_KlattGrid_extractDeltaFormantGrid); KlattGRID_EXTRACT_FORMANT_GRID_ACTION (Tracheal, tracheal f) KlattGRID_EXTRACT_FORMANT_AMPLITUDE_ACTION (Tracheal, tracheal) KlattGRID_EXTRACT_FORMANT_GRID_ACTION (TrachealAnti, tracheal antif) praat_addAction1 (classKlattGrid, 0, L"-- extract frication characteristics", 0, 1, 0); KlattGRID_EXTRACT_FORMANT_GRID_ACTION (Frication, frication f) KlattGRID_EXTRACT_FORMANT_AMPLITUDE_ACTION (Frication, frication) praat_addAction1 (classKlattGrid, 0, L"Extract frication bypass tier", 0, 1, DO_KlattGrid_extractFricationBypassTier); praat_addAction1 (classKlattGrid, 0, L"Extract frication amplitude tier", 0, 1, DO_KlattGrid_extractFricationAmplitudeTier); #undef KlattGRID_EXTRACT_FORMANT_AMPLITUDE_ACTION #undef KlattGRID_EXTRACT_FORMANT_GRID_ACTION praat_addAction2 (classKlattGrid, 1, classPitchTier, 1, L"Replace pitch tier", 0, 1, DO_KlattGrid_replacePitchTier); praat_addAction2 (classKlattGrid, 1, classRealTier, 1, L"Replace flutter tier", 0, 1, DO_KlattGrid_replaceFlutterTier); praat_addAction2 (classKlattGrid, 1, classRealTier, 1, L"Replace power1 tier", 0, 1, DO_KlattGrid_replacePower1Tier); praat_addAction2 (classKlattGrid, 1, classRealTier, 1, L"Replace power2 tier", 0, 1, DO_KlattGrid_replacePower2Tier); praat_addAction2 (classKlattGrid, 1, classRealTier, 1, L"Replace open phase tier", 0, 1, DO_KlattGrid_replaceOpenPhaseTier); praat_addAction2 (classKlattGrid, 1, classRealTier, 1, L"Replace collision phase tier", 0, 1, DO_KlattGrid_replaceCollisionPhaseTier); praat_addAction2 (classKlattGrid, 1, classRealTier, 1, L"Replace double pulsing tier", 0, 1, DO_KlattGrid_replaceDoublePulsingTier); praat_addAction2 (classKlattGrid, 1, classIntensityTier, 1, L"-- replace formant amplitudes --", 0, 1, 0); #define KlattGrid_REPLACE_FORMANTGRID_ACTION(Name,namef) \ praat_addAction2 (classKlattGrid, 1, classFormantGrid, 1, L"Replace " #namef "ormant grid", 0, 1, DO_KlattGrid_replace##Name##FormantGrid); #define KlattGrid_REPLACE_FORMANT_AMPLITUDE_ACTION(Name,namef) \ praat_addAction2 (classKlattGrid, 1, classIntensityTier, 1, L"Replace " #namef "ormant amplitude tier...", 0, 1, DO_KlattGrid_replace##Name##FormantAmplitudeTier); KlattGrid_REPLACE_FORMANTGRID_ACTION (Oral, oral f) KlattGrid_REPLACE_FORMANTGRID_ACTION (Nasal, nasal f) KlattGrid_REPLACE_FORMANTGRID_ACTION (NasalAnti, nasal antif) praat_addAction2 (classKlattGrid, 1, classFormantGrid, 1, L"-- replace coupling --", 0, 1, 0); KlattGrid_REPLACE_FORMANTGRID_ACTION (Tracheal, tracheal f) KlattGrid_REPLACE_FORMANTGRID_ACTION (TrachealAnti, tracheal antif) KlattGrid_REPLACE_FORMANTGRID_ACTION (Delta, delta f) praat_addAction2 (classKlattGrid, 1, classFormantGrid, 1, L"-- replace frication --", 0, 1, 0); KlattGrid_REPLACE_FORMANTGRID_ACTION (Frication, frication f) praat_addAction2 (classKlattGrid, 1, classFormantGrid, 1, L"Replace formant grid...", 0, praat_HIDDEN + praat_DEPTH_1, DO_KlattGrid_replaceFormantGrid); praat_addAction2 (classKlattGrid, 1, classIntensityTier, 1, L"Replace voicing amplitude tier", 0, 1, DO_KlattGrid_replaceVoicingAmplitudeTier); praat_addAction2 (classKlattGrid, 1, classIntensityTier, 1, L"Replace spectral tilt tier", 0, 1, DO_KlattGrid_replaceSpectralTiltTier); praat_addAction2 (classKlattGrid, 1, classIntensityTier, 1, L"Replace aspiration amplitude tier", 0, 1, DO_KlattGrid_replaceAspirationAmplitudeTier); praat_addAction2 (classKlattGrid, 1, classIntensityTier, 1, L"Replace breathiness amplitude tier", 0, 1, DO_KlattGrid_replaceBreathinessAmplitudeTier); praat_addAction2 (classKlattGrid, 1, classIntensityTier, 1, L"Replace amplitude tier...", 0, praat_HIDDEN + praat_DEPTH_1, DO_KlattGrid_replaceAmplitudeTier); KlattGrid_REPLACE_FORMANT_AMPLITUDE_ACTION (Oral, oral f) KlattGrid_REPLACE_FORMANT_AMPLITUDE_ACTION (Nasal, nasal f) KlattGrid_REPLACE_FORMANT_AMPLITUDE_ACTION (Tracheal, tracheal f) KlattGrid_REPLACE_FORMANT_AMPLITUDE_ACTION (Frication, frication f) praat_addAction2 (classKlattGrid, 1, classIntensityTier, 1, L"Replace frication amplitude tier", 0, 1, DO_KlattGrid_replaceFricationAmplitudeTier); praat_addAction2 (classKlattGrid, 1, classIntensityTier, 1, L"Replace frication bypass tier", 0, 1, DO_KlattGrid_replaceFricationBypassTier); #undef KlattGrid_REPLACE_FORMANT_AMPLITUDE_ACTION #undef KlattGrid_REPLACE_FORMANTGRID_ACTION praat_addAction2 (classKlattGrid, 1, classSound, 1, L"Filter by vocal tract...", 0, 1, DO_Sound_KlattGrid_filterByVocalTract); INCLUDE_MANPAGES (manual_KlattGrid) } /* End of file praat_KlattGrid_init.c */ sources_5316/dwtools/SpeechSynthesizer.h0000664000176700017670000000506511742103044017252 0ustar paulpaul#ifndef _SpeechSynthesizer_h_ #define _SpeechSynthesizer_h_ /* SpeechSynthesizer.h * * Copyright (C) 2011-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20111214 */ #include "Sound.h" #include "TextGrid.h" #define SpeechSynthesizer_PHONEMECODINGS_IPA 2 #define SpeechSynthesizer_PHONEMECODINGS_KIRSHENBAUM 1 #define SpeechSynthesizer_INPUT_TEXTONLY 1 #define SpeechSynthesizer_INPUT_PHONEMESONLY 2 #define SpeechSynthesizer_INPUT_TAGGEDTEXT 3 Thing_define (SpeechSynthesizer, Data) { public: // sythesizers language /voice long d_voice, d_voiceVariant; wchar_t *d_voiceName, *d_voiceVariantName; wchar_t *d_punctuations; // text input int d_inputTextFormat; // text-only, phonemes-only, mixed int d_inputPhonemeCoding; // 1/: output phonemes in espeak/ notation // speech output long d_numberOfSamples, d_wavCapacity; short *d_wav; double d_samplingFrequency; double d_internalSamplingFrequency; double d_wordgap; long d_pitchAdjustment, d_pitchRange; long d_wordsPerMinute; bool d_estimateWordsPerMinute; // TextGrid bool d_createEventPerPhoneme; int d_outputPhonemeCoding; // 1/2: output phonemes in espeak/IPA notation Table d_events; // Filled by the call back // overridden methods: void v_destroy (); void v_info (); }; SpeechSynthesizer SpeechSynthesizer_create (long voice, long voiceVariant); void SpeechSynthesizer_setTextInputSettings (SpeechSynthesizer me, int inputTextFormat, int inputPhonemeCoding); void SpeechSynthesizer_setSpeechOutputSettings (SpeechSynthesizer me, double samplingFrequency, double wordgap, long pitchAdjustment, long pitchRange, long wordsPerMinute, bool estimateWordsPerMinute, int outputPhonemeCodes); Sound SpeechSynthesizer_to_Sound (SpeechSynthesizer me, const wchar_t *text, TextGrid *tg, Table *events); void SpeechSynthesizer_playText (SpeechSynthesizer me, const wchar_t *text); /* End of file SpeechSynthesizer.h */ #endif sources_5316/dwtools/praat_BSS_init.cpp0000644000176700017670000004241111740334221016762 0ustar paulpaul/* praat_BSS_init.c * * Copyright (C) 2010-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20101003 djmw 20110101 Latest modification */ #include "praat.h" #include "ICA.h" #include "PCA.h" #include "Sound.h" #undef iam #define iam iam_LOOP void praat_SSCP_as_TableOfReal_init (ClassInfo klas); void praat_TableOfReal_init (ClassInfo klas); void praat_TableOfReal_init3 (ClassInfo klas); /********************** CrossCorrelationTable(s) ******************/ FORM (CrossCorrelationTables_createTestSet, L"CrossCorrelationTables: Create test set", L"CrossCorrelationTables: Create test set...") WORD (L"Name", L"5x5") NATURAL (L"Matrix dimension", L"5") NATURAL (L"Number of matrices", L"20") BOOLEAN (L"First is positive definite", 1) REAL (L"Sigma", L"0.02") OK DO praat_new (CrossCorrelationTables_createTestSet (GET_INTEGER (L"Matrix dimension"), GET_INTEGER (L"Number of matrices"), GET_INTEGER (L"First is positive definite"), GET_REAL (L"Sigma")), GET_STRING (L"Name")); END FORM (CrossCorrelationTable_createSimple, L"Create simple CrossCorrelationTable", 0) WORD (L"Name", L"ct") SENTENCE (L"Cross correlations", L"1.0 0.0 1.0") SENTENCE (L"Centroid", L"0.0 0.0") POSITIVE (L"Number of samples", L"100.0") OK DO praat_new (CrossCorrelationTable_createSimple (GET_STRING (L"Cross correlations"), GET_STRING (L"Centroid"), GET_REAL (L"Number of samples")), GET_STRING (L"Name")); END FORM (MixingMatrix_createSimple, L"Create simple MixingMatrix", 0) WORD (L"Name", L"mm") NATURAL (L"Number of channels", L"2") NATURAL (L"Number of components", L"2") SENTENCE (L"Mixing coefficients", L"1.0 1.0 1.0 1.0") OK DO praat_new (MixingMatrix_createSimple (GET_INTEGER (L"Number of channels"), GET_INTEGER (L"Number of components"), GET_STRING (L"Mixing coefficients")), GET_STRING (L"Name")); END DIRECT (CrossCorrelationTable_help) Melder_help (L"CrossCorrelationTable"); END DIRECT (CrossCorrelationTable_to_PCA) LOOP { iam (CrossCorrelationTable); praat_new (SSCP_to_PCA (me), my name); } END FORM (Sound_and_PCA_projectChannels, L"Sound & PCA: To Sound (project channels)", 0) NATURAL (L"Number of components", L"10") OK DO Sound me = FIRST (Sound); PCA thee = FIRST (PCA); praat_new (Sound_and_PCA_projectChannels (me, thee, GET_INTEGER (L"Number of components")), Thing_getName (me), L"_projected"); END FORM (Sound_and_PCA_whitenChannels, L"Sound & PCA: To Sound (whiten channels)", 0) NATURAL (L"Number of components", L"10") OK DO Sound me = FIRST (Sound); PCA thee = FIRST (PCA); praat_new (Sound_and_PCA_whitenChannels (me, thee, GET_INTEGER (L"Number of components")), Thing_getName (me), L"_white"); END DIRECT (CrossCorrelationTable_to_CrossCorrelationTables) autoCrossCorrelationTables thee = CrossCorrelationTables_create (); long nrows = 0, ncols = 0, nselected = 0; LOOP { iam (CrossCorrelationTable); nselected++; if (nselected == 1) { nrows = my numberOfRows; ncols = my numberOfColumns; } if (my numberOfRows != nrows || my numberOfColumns != ncols) Melder_throw ("Dimensions of table ", IOBJECT, " differs from the rest."); autoCrossCorrelationTable myc = Data_copy (me); Collection_addItem (thee.peek(), myc.transfer()); } praat_new (thee.transfer(), L"ct_", Melder_integer (nselected)); END FORM (Sound_to_Covariance_channels, L"Sound: To Covariance (channels)", L"Sound: To Covariance (channels)...") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"10.0") OK DO LOOP { iam (Sound); praat_new (Sound_to_Covariance_channels (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range")), my name); } END FORM (Sound_to_CrossCorrelationTable, L"Sound: To CrossCorrelationTable", L"Sound: To CrossCorrelationTable...") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"10.0") REAL (L"Lag time (s)", L"0.0") OK DO double lagTime = fabs (GET_REAL (L"Lag time")); LOOP { iam (Sound); praat_new (Sound_to_CrossCorrelationTable (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), lagTime), my name); } END FORM (Sounds_to_CrossCorrelationTable_combined, L"Sound: To CrossCorrelationTable (combined)", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"10.0") REAL (L"Lag time (s)", L"0.0") OK DO Sound s1 = NULL, s2 = NULL; LOOP { iam (Sound); (s1 ? s2 : s1) = me; } Melder_assert (s1 != NULL && s2 != NULL); autoCrossCorrelationTable thee = Sounds_to_CrossCorrelationTable_combined (s1, s2, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"Lag time")); praat_new (thee.transfer(), s1 -> name, L"_", s2 -> name, L"_cc"); END DIRECT (CrossCorrelationTables_help) Melder_help (L"CrossCorrelationTables"); END FORM (CrossCorrelationTables_getDiagonalityMeasure, L"CrossCorrelationTables: Get diagonality measure", L"CrossCorrelationTables: Get diagonality measure...") NATURAL (L"First table", L"1") NATURAL (L"Last table", L"100") OK DO LOOP { iam (CrossCorrelationTables); double dm = CrossCorrelationTables_getDiagonalityMeasure (me, 0, GET_INTEGER (L"First table"), GET_INTEGER (L"Last table")); Melder_information (Melder_double (dm), L" (= average sum of squared off-diagonal elements)"); } END FORM (CrossCorrelationTables_extractCrossCorrelationTable, L"CrossCorrelationTables: Extract one CrossCorrelationTable", 0) NATURAL (L"Index", L"1") OK DO long index = GET_INTEGER (L"Index"); LOOP { iam (CrossCorrelationTables); if (index > my size) { Melder_throw (L"Index too large."); } autoCrossCorrelationTable thee = Data_copy ( (CrossCorrelationTable) my item[index]); praat_new (thee.transfer(), Thing_getName (me), L"_", Melder_integer (index)); } END FORM (CrossCorrelationTables_to_Diagonalizer, L"CrossCorrelationTables: To Diagonalizer", 0) NATURAL (L"Maximum number of iterations", L"100") POSITIVE (L"Tolerance", L"0.001") OPTIONMENU (L"Diagonalization method", 2) OPTION (L"qdiag") OPTION (L"ffdiag") OK DO LOOP { iam (CrossCorrelationTables); praat_new (CrossCorrelationTables_to_Diagonalizer (me, GET_INTEGER (L"Maximum number of iterations"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Diagonalization method")), my name); } END FORM (Diagonalizer_and_CrossCorrelationTables_improveDiagonality, L"Diagonalizer & CrossCorrelationTables: Improve diagonality", 0) NATURAL (L"Maximum number of iterations", L"100") POSITIVE (L"Tolerance", L"0.001") OPTIONMENU (L"Diagonalization method", 2) OPTION (L"qdiag") OPTION (L"ffdiag") OK DO Diagonalizer d = FIRST (Diagonalizer); CrossCorrelationTables ccts = FIRST (CrossCorrelationTables); Diagonalizer_and_CrossCorrelationTables_improveDiagonality (d, ccts, GET_INTEGER (L"Maximum number of iterations"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Diagonalization method")); END FORM (CrossCorrelationTables_and_Diagonalizer_getDiagonalityMeasure, L"CrossCorrelationTables & Diagonalizer: Get diagonality measure", 0) NATURAL (L"First table", L"1") NATURAL (L"Last table", L"100") OK DO CrossCorrelationTables ccts = FIRST (CrossCorrelationTables); Diagonalizer d = FIRST (Diagonalizer); double dm = CrossCorrelationTables_and_Diagonalizer_getDiagonalityMeasure (ccts, d, 0, GET_INTEGER (L"First table"), GET_INTEGER (L"Last table")); Melder_information (Melder_double (dm), L" (= average sum of squared off-diagonal elements)"); END DIRECT (CrossCorrelationTable_and_Diagonalizer_diagonalize) CrossCorrelationTable cct = FIRST (CrossCorrelationTable); Diagonalizer d = FIRST (Diagonalizer); praat_new (CrossCorrelationTable_and_Diagonalizer_diagonalize (cct, d), cct->name, L"_", d->name); END DIRECT (CrossCorrelationTables_and_Diagonalizer_diagonalize) CrossCorrelationTables ccts = FIRST (CrossCorrelationTables); Diagonalizer d = FIRST (Diagonalizer); praat_new (CrossCorrelationTables_and_Diagonalizer_diagonalize (ccts, d), ccts->name, L"_", d->name); END FORM (CrossCorrelationTables_and_MixingMatrix_improveUnmixing, L"", 0) LABEL (L"", L"Iteration parameters") NATURAL (L"Maximum number of iterations", L"100") POSITIVE (L"Tolerance", L"0.001") OPTIONMENU (L"Diagonalization method", 2) OPTION (L"qdiag") OPTION (L"ffdiag") OK DO MixingMatrix mm = FIRST (MixingMatrix); CrossCorrelationTables ccts = FIRST (CrossCorrelationTables); MixingMatrix_and_CrossCorrelationTables_improveUnmixing (mm, ccts, GET_INTEGER (L"Maximum number of iterations"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Diagonalization method")); END DIRECT (Diagonalizer_to_MixingMatrix) LOOP { iam (Diagonalizer); praat_new (Diagonalizer_to_MixingMatrix (me), my name); } END FORM (Sound_to_MixingMatrix, L"Sound: To MixingMatrix", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"10.0") NATURAL (L"Number of cross-correlations", L"20") POSITIVE (L"Lag times (s)", L"0.002") LABEL (L"", L"Iteration parameters") NATURAL (L"Maximum number of iterations", L"100") POSITIVE (L"Tolerance", L"0.001") OPTIONMENU (L"Diagonalization method", 2) OPTION (L"qdiag") OPTION (L"ffdiag") OK DO LOOP { iam (Sound); praat_new (Sound_to_MixingMatrix (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_INTEGER (L"Number of cross-correlations"), GET_REAL (L"Lag times"), GET_INTEGER (L"Maximum number of iterations"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Diagonalization method")), my name); } END FORM (Sound_to_CrossCorrelationTables, L"Sound: To CrossCorrelationTables", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"10.0") NATURAL (L"Number of cross-correlations", L"20") POSITIVE (L"Lag times (s)", L"0.002") OK DO LOOP { iam (Sound); praat_new (Sound_to_CrossCorrelationTables (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_REAL (L"Lag times"), GET_INTEGER (L"Number of cross-correlations")), my name); } END FORM (Sound_to_Sound_bss, L"Sound: To Sound (blind source separation)", L"Sound: To Sound (blind source separation)...") REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"10.0") NATURAL (L"Number of cross-correlations", L"20") POSITIVE (L"Lag times (s)", L"0.002") LABEL (L"", L"Iteration parameters") NATURAL (L"Maximum number of iterations", L"100") POSITIVE (L"Tolerance", L"0.001") OPTIONMENU (L"Diagonalization method", 2) OPTION (L"qdiag") OPTION (L"ffdiag") OK DO LOOP { iam (Sound); praat_new (Sound_to_Sound_BSS (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_INTEGER (L"Number of cross-correlations"), GET_REAL (L"Lag times"), GET_INTEGER (L"Maximum number of iterations"), GET_REAL (L"Tolerance"), GET_INTEGER (L"Diagonalization method")), my name, L"_bss"); } END FORM (Sound_to_Sound_whitenChannels, L"Sound: To Sound (whiten channels)", L"Sound: To Sound (whiten channels)...") POSITIVE (L"Variance fraction to keep", L"0.99") OK DO double varianceFraction = GET_REAL (L"Variance fraction to keep"); if (varianceFraction > 1) varianceFraction = 1; long permille = varianceFraction * 1000.0; LOOP { iam (Sound); praat_new (Sound_whitenChannels (me, varianceFraction), my name, L"_", Melder_integer (permille)); } END DIRECT (Sound_and_MixingMatrix_mix) Sound s = FIRST (Sound); MixingMatrix mm = FIRST (MixingMatrix); praat_new (Sound_and_MixingMatrix_mix (s, mm), Thing_getName (s), L"_mixed"); END DIRECT (Sound_and_MixingMatrix_unmix) Sound s = FIRST (Sound); MixingMatrix mm = FIRST (MixingMatrix); praat_new (Sound_and_MixingMatrix_unmix (s, mm), Thing_getName (s), L"_unmixed"); END DIRECT (TableOfReal_to_MixingMatrix) LOOP { iam (TableOfReal); praat_new (TableOfReal_to_MixingMatrix (me), my name); } END FORM (TableOfReal_and_TableOfReal_crossCorrelations, L"TableOfReal & TableOfReal: Cross-correlations", 0) OPTIONMENU (L"Correlations between", 1) OPTION (L"Rows") OPTION (L"Columns") BOOLEAN (L"Center", 0) BOOLEAN (L"Normalize", 0) OK DO TableOfReal t1 = 0, t2 = 0; LOOP { iam (TableOfReal); (t1 ? t2 : t1) = me; } Melder_assert (t1 != NULL && t2 != NULL); int by_columns = GET_INTEGER (L"Correlations between") - 1; praat_new (TableOfReal_and_TableOfReal_crossCorrelations (t1, t2, by_columns, GET_INTEGER (L"Center"), GET_INTEGER (L"Normalize")), (by_columns ? L"by_columns" : L"by_rows")); END void praat_TableOfReal_init3 (ClassInfo klas) { praat_TableOfReal_init (klas); praat_addAction1 (klas, 2, L"To TableOfReal (cross-correlations)...", 0, 0, DO_TableOfReal_and_TableOfReal_crossCorrelations); } void praat_BSS_init (void); void praat_BSS_init (void) { Thing_recognizeClassesByName (classDiagonalizer, classMixingMatrix, classCrossCorrelationTable, classCrossCorrelationTables, NULL); praat_addMenuCommand (L"Objects", L"New", L"Create simple CrossCorrelationTable...", L"Create simple Covariance...", praat_HIDDEN + praat_DEPTH_1, DO_CrossCorrelationTable_createSimple); praat_addMenuCommand (L"Objects", L"New", L"Create test CrossCorrelationTables...", L"Create simple CrossCorrelationTable...", praat_HIDDEN + praat_DEPTH_1, DO_CrossCorrelationTables_createTestSet); praat_addMenuCommand (L"Objects", L"New", L"Create simple MixingMatrix...", L"Create test CrossCorrelationTables...", praat_HIDDEN + praat_DEPTH_1, DO_MixingMatrix_createSimple); praat_addAction1 (classCrossCorrelationTable, 0, L"CrossCorrelationTable help", 0, 0, DO_CrossCorrelationTable_help); praat_SSCP_as_TableOfReal_init (classCrossCorrelationTable); praat_addAction1 (classCrossCorrelationTable, 0, L"To PCA", 0, 0, DO_CrossCorrelationTable_to_PCA); praat_addAction1 (classCrossCorrelationTable, 0, L"To CrossCorrelationTables", 0, 0, DO_CrossCorrelationTable_to_CrossCorrelationTables); praat_addAction1 (classCrossCorrelationTables, 0, L"CrossCorrelationTables help", 0, 0, DO_CrossCorrelationTables_help); praat_addAction1 (classCrossCorrelationTables, 1, L"Extract CrossCorrelationTable...", 0, 0, DO_CrossCorrelationTables_extractCrossCorrelationTable); praat_addAction1 (classCrossCorrelationTables, 1, L"Get diagonality measure...", 0, 0, DO_CrossCorrelationTables_getDiagonalityMeasure); praat_addAction1 (classCrossCorrelationTables, 0, L"To Diagonalizer...", 0, 0, DO_CrossCorrelationTables_to_Diagonalizer); praat_TableOfReal_init3 (classDiagonalizer); praat_addAction1 (classDiagonalizer, 0, L"To MixingMatrix", 0, 0, DO_Diagonalizer_to_MixingMatrix); praat_TableOfReal_init3 (classMixingMatrix); praat_addAction1 (classSound, 0, L"To MixingMatrix...", L"Resample...", praat_HIDDEN + praat_DEPTH_1, DO_Sound_to_MixingMatrix); praat_addAction1 (classSound, 0, L"To CrossCorrelationTable...", L"Resample...", 1, DO_Sound_to_CrossCorrelationTable); praat_addAction1 (classSound, 0, L"To Covariance (channels)...", L"Resample...", praat_HIDDEN + praat_DEPTH_1, DO_Sound_to_Covariance_channels); praat_addAction1 (classSound, 0, L"To CrossCorrelationTables...", L"Resample...", praat_HIDDEN + praat_DEPTH_1, DO_Sound_to_CrossCorrelationTables); praat_addAction1 (classSound, 0, L"To Sound (blind source separation)...", L"Resample...", 1, DO_Sound_to_Sound_bss); praat_addAction1 (classSound, 0, L"To Sound (whiten channels)...", L"Resample...", 1, DO_Sound_to_Sound_whitenChannels); praat_addAction1 (classSound, 0, L"To CrossCorrelationTable (combined)...", L"Cross-correlate...", 1, DO_Sounds_to_CrossCorrelationTable_combined); praat_addAction1 (classTableOfReal, 0, L"To MixingMatrix", L"To Configuration", praat_HIDDEN, DO_TableOfReal_to_MixingMatrix); praat_addAction2 (classSound, 1, classMixingMatrix, 1, L"Mix", 0, 0, DO_Sound_and_MixingMatrix_mix); praat_addAction2 (classSound, 1, classMixingMatrix, 1, L"Unmix", 0, 0, DO_Sound_and_MixingMatrix_unmix); praat_addAction2 (classSound, 1, classPCA, 1, L"To Sound (whiten channels)...", 0 , 0, DO_Sound_and_PCA_whitenChannels); praat_addAction2 (classSound, 1, classPCA, 1, L"To Sound (project channels)...", 0 , 0, DO_Sound_and_PCA_projectChannels); praat_addAction2 (classCrossCorrelationTable, 1, classDiagonalizer, 1, L"Diagonalize", 0 , 0, DO_CrossCorrelationTable_and_Diagonalizer_diagonalize); praat_addAction2 (classCrossCorrelationTables, 1, classDiagonalizer, 1, L"Get diagonality measure...", 0 , 0, DO_CrossCorrelationTables_and_Diagonalizer_getDiagonalityMeasure); praat_addAction2 (classCrossCorrelationTables, 1, classDiagonalizer, 1, L"Diagonalize", 0 , 0, DO_CrossCorrelationTables_and_Diagonalizer_diagonalize); praat_addAction2 (classCrossCorrelationTables, 1, classDiagonalizer, 1, L"Improve diagonality...", 0 , 0, DO_Diagonalizer_and_CrossCorrelationTables_improveDiagonality); praat_addAction2 (classCrossCorrelationTables, 1, classMixingMatrix, 1, L"Improve unmixing...", 0 , 0, DO_CrossCorrelationTables_and_MixingMatrix_improveUnmixing); INCLUDE_MANPAGES (manual_BSS) } /* End of file praat_BSS_init.c */ sources_5316/dwtools/Strings_extensions.h0000664000176700017670000000462611740103124017502 0ustar paulpaul#ifndef _Strings_extensions_h_ #define _Strings_extensions_h_ /* Strings_extensions.h * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010114 djmw 20020813 GPL header djmw 20040629 Strings_append now accepts an Ordered of Strings. djmw 20050714 Permutations djmw 20050724 Index djmw 20120407 Latest modification */ #include "Collection.h" #include "Strings.h" #include "Permutation.h" #include "Index.h" Strings Strings_createFixedLength (long numberOfStrings); Strings Strings_createAsCharacters (const wchar_t *string); Strings Strings_createAsTokens (const wchar_t *string); long Strings_findString (Strings me, const wchar_t *string); Strings Strings_append (Collection me); Strings Strings_change (Strings me, const wchar_t *search, const wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp); void Strings_setString (Strings me, const wchar_t *newstr, long index); Strings strings_to_Strings (wchar_t **strings, long from, long to); Strings Strings_extractPart (Strings me, long start, long end); Strings strings_to_Strings_link (wchar_t** strings, long n); /* for (i=1; i<= n; i++) my strings[i] = strings[i]; */ void _Strings_unlink (Strings me); /* for (i=1; i<= my numberOfStrings; i++) my strings[i] = NULL; */ StringsIndex Strings_to_StringsIndex (Strings me); StringsIndex Stringses_to_StringsIndex (Strings me, Strings classes); /* Construct the index with strings in classes, index[i]=0 when my strings[i] doesn't occur in classes */ Strings StringsIndex_to_Strings (StringsIndex me); Permutation Strings_to_Permutation (Strings me, int sort); Strings Strings_and_Permutation_permuteStrings (Strings me, Permutation thee); #endif /* _Strings_extensions_h_ */ sources_5316/dwtools/PCA_def.h0000644000176700017670000000216711627245124015022 0ustar paulpaul/* PCA_def.h * * Copyright (C) 1993-2002 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19981225, 20020813 GPL header, 20110329 latest modification */ #define ooSTRUCT PCA oo_DEFINE_CLASS (PCA, Eigen) oo_LONG (numberOfObservations) oo_STRING_VECTOR (labels, dimension) oo_DOUBLE_VECTOR (centroid, dimension) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (PCA) #undef ooSTRUCT /* End of file PCA_def.h */ sources_5316/dwtools/CCs_to_DTW.cpp0000664000176700017670000000730011725101411016005 0ustar paulpaul/* CCs_to_DTW.c * * Dynamic Time Warp of two CCs. * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020315 GPL header djmw 20080122 float -> double */ #include "CCs_to_DTW.h" static void regression (I, long frame, double r[], long nr) { iam (CC); // sum(i^2;i=-n..n) = 2n^3/3 + n^2 +n/3 = n (n (2n/3 + 1) + 1/3); long nrd2 = nr / 2; double sumsq = nrd2 * (nrd2 * (nr / 3 + 1) + 1 / 3); if (frame <= nrd2 || frame >= my nx - nrd2) { return; } for (long i = 0; i <= my maximumNumberOfCoefficients; i++) { r[i] = 0; } long nmin = CC_getMinimumNumberOfCoefficients (me, frame - nrd2, frame + nrd2); for (long i = 0; i <= nmin; i++) { double ri = 0; for (long j = -nrd2; j <= nrd2; j++) { CC_Frame cf = & my frame[frame + j]; double c = i == 0 ? cf -> c0 : cf -> c[i]; ri += c * j; } r[i] = ri / sumsq / my dx; } } DTW CCs_to_DTW (I, thou, double wc, double wle, double wr, double wer, double dtr) { try { iam (CC); thouart (CC); if (my maximumNumberOfCoefficients != thy maximumNumberOfCoefficients) { Melder_throw ("CC orders must be equal."); } long nr = dtr / my dx; if (wr != 0 && nr < 2) { Melder_throw ("Time window for regression is too small."); } if (nr % 2 == 0) { nr++; } if (wr != 0) { Melder_casual ("%ld frames used for regression coefficients.", nr); } autoDTW him = DTW_create (my xmin, my xmax, my nx, my dx, my x1, thy xmin, thy xmax, thy nx, thy dx, thy x1); autoNUMvector ri (0L, my maximumNumberOfCoefficients); autoNUMvector rj (0L, my maximumNumberOfCoefficients); // Calculate distance matrix autoMelderProgress progess (L"CCs_to_DTW"); for (long i = 1; i <= my nx; i++) { CC_Frame fi = & my frame[i]; regression (me, i, ri.peek(), nr); for (long j = 1; j <= thy nx; j++) { CC_Frame fj = & thy frame[j]; double dist = 0, distr = 0; // Cepstral distance if (wc != 0) { for (long k = 1; k <= fj -> numberOfCoefficients; k++) { double d = fi -> c[k] - fj -> c[k]; dist += d * d; } dist *= wc; } // Log energy distance if (wle != 0) { double d = fi -> c0 - fj -> c0; dist += wle * d * d; } // Regression distance if (wr != 0) { regression (thee, j, rj.peek(), nr); for (long k = 1; k <= fj -> numberOfCoefficients; k++) { double d = ri[k] - rj[k]; distr += d * d; } dist += wr * distr; } // Regression on c[0]: log(energy) if (wer != 0) { if (wr == 0) { regression (thee, j, rj.peek(), nr); } double d = ri[0] - rj[0]; dist += wer * d * d; } dist /= wc + wle + wr + wer; his z[i][j] = sqrt (dist); /* prototype along y-direction */ } if ( (i % 10) == 1) { Melder_progress (0.999 * i / my nx, L"Calculate distances: frame ", Melder_integer (i), L" from ", Melder_integer (my nx), L"."); therror } } return him.transfer(); } catch (MelderError) { Melder_throw ("DTW not created from CCs."); } } /* End of file CCs_to_DTW.cpp */ sources_5316/dwtools/ContingencyTable.cpp0000644000176700017670000001467511634065143017372 0ustar paulpaul/* ContingencyTable.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ContingencyTable.h" #include "TableOfReal_extensions.h" #include "NUM2.h" Thing_implement (ContingencyTable, TableOfReal, 0); #define TINY 1e-30 void structContingencyTable :: v_info () { structData :: v_info (); long ndf; double h, hx, hy, hygx, hxgy, uygx, uxgy, uxy, chisq; ContingencyTable_entropies (this, &h, &hx, &hy, &hygx, &hxgy, &uygx, &uxgy, &uxy); ContingencyTable_chisq (this, &chisq, &ndf); Melder_information (L"Number of rows: ", Melder_integer (numberOfRows)); Melder_information (L"Number of columns: ", Melder_integer (numberOfColumns)); Melder_information (L"Entropies (y is row variable):"); Melder_information (L" Total: ", Melder_double (h)); Melder_information (L" Y: ", Melder_double (hy)); Melder_information (L" X: ", Melder_double (hx)); Melder_information (L" Y given x: ", Melder_double (hygx)); Melder_information (L" X given y: ", Melder_double (hxgy)); Melder_information (L" Dependency of y on x: ", Melder_double (uygx)); Melder_information (L" Dependency of x on y: ", Melder_double (uxgy)); Melder_information (L" Symmetrical dependency: ", Melder_double (uxy)); Melder_information (L" Chi squared: ", Melder_double (chisq)); Melder_information (L" Degrees of freedom: ", Melder_integer (ndf)); Melder_information (L" Probability: ", Melder_double (ContingencyTable_chisqProbability (this))); } ContingencyTable ContingencyTable_create (long numberOfRows, long numberOfColumns) { try { autoContingencyTable me = Thing_new (ContingencyTable); TableOfReal_init (me.peek(), numberOfRows, numberOfColumns); return me.transfer(); } catch (MelderError) { Melder_throw ("ContingencyTable not created."); } } double ContingencyTable_chisqProbability (ContingencyTable me) { double chisq; long df; ContingencyTable_chisq (me, &chisq, &df); if (chisq == 0 && df == 0) { return 0; } return NUMchiSquareQ (chisq, df); } double ContingencyTable_cramersStatistic (ContingencyTable me) { double chisq, sum = 0; long df, nr = my numberOfRows, nc = my numberOfColumns, nmin = nr; if (nr == 1 || nc == 1) { return 0; } for (long i = 1; i <= nr; i++) { for (long j = 1; j <= nc; j++) { sum += my data[i][j]; } } if (nc < nr) { nmin = nc; } nmin--; ContingencyTable_chisq (me, &chisq, &df); if (chisq == 0 && df == 0) { return 0; } return sqrt (chisq / (sum * nmin)); } double ContingencyTable_contingencyCoefficient (ContingencyTable me) { double chisq, sum = 0; long df, nr = my numberOfRows, nc = my numberOfColumns; for (long i = 1; i <= nr; i++) { for (long j = 1; j <= nc; j++) { sum += my data[i][j]; } } ContingencyTable_chisq (me, &chisq, &df); if (chisq == 0 && df == 0) { return 0; } return sqrt (chisq / (chisq + sum)); } void ContingencyTable_chisq (ContingencyTable me, double *chisq, long *df) { long nr = my numberOfRows, nc = my numberOfColumns; *chisq = 0; *df = 0; autoNUMvector rowsum (1, nr); autoNUMvector colsum (1, nc); /* row and column marginals */ double sum = 0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { rowsum[i] += my data[i][j]; colsum[j] += my data[i][j]; } sum += rowsum[i]; } for (long i = 1; i <= my numberOfRows; i++) { if (rowsum[i] == 0) { --nr; } } for (long j = 1; j <= my numberOfColumns; j++) { if (colsum[j] == 0) { --nc; } } *df = (nr - 1) * (nc - 1); for (long i = 1; i <= my numberOfRows; i++) { if (rowsum[i] == 0) { continue; } for (long j = 1; j <= my numberOfColumns; j++) { if (colsum[j] == 0) { continue; } double expt = rowsum[i] * colsum[j] / sum; double tmp = my data[i][j] - expt; *chisq += tmp * tmp / expt; } } } void ContingencyTable_entropies (ContingencyTable me, double *h, double *hx, double *hy, double *hygx, double *hxgy, double *uygx, double *uxgy, double *uxy) { *h = *hx = *hy = *hxgy = *hygx = *uygx = *uxgy = *uxy = 0; autoNUMvector rowsum (1, my numberOfRows); autoNUMvector colsum (1, my numberOfColumns); /* row and column totals */ double sum = 0.0; for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { rowsum[i] += my data[i][j]; colsum[j] += my data[i][j]; } sum += rowsum[i]; } /* Entropy of x distribution */ for (long j = 1; j <= my numberOfColumns; j++) { if (colsum[j] > 0) { double p = colsum[j] / sum; *hx -= p * NUMlog2 (p); } } /* Entropy of y distribution */ for (long i = 1; i <= my numberOfRows; i++) { if (rowsum[i] > 0) { double p = rowsum[i] / sum; *hy -= p * NUMlog2 (p); } } /* Total entropy */ for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { if (my data[i][j] > 0) { double p = my data[i][j] / sum; *h -= p * NUMlog2 (p); } } } /* Conditional entropies */ *hygx = *h - *hx; *hxgy = *h - *hy; *uygx = (*hy - *hygx) / (*hy + TINY); *uxgy = (*hx - *hxgy) / (*hx + TINY); *uxy = 2.0 * (*hx + *hy - *h) / (*hx + *hy + TINY); } ContingencyTable Confusion_to_ContingencyTable (Confusion me) { try { autoContingencyTable thee = Thing_new (ContingencyTable); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to ContingencyTable."); } } ContingencyTable TableOfReal_to_ContingencyTable (I) { iam (TableOfReal); try { TableOfReal_checkPositive (me); autoContingencyTable thee = Thing_new (ContingencyTable); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to ContingencyTable."); } } // End of file ContingencyTable.cpp sources_5316/dwtools/.KlattGridEditors.cpp.kate-swp0000644000176700017670000000014711631633500021151 0ustar paulpaulKate Swap File - Version 1.0SI#include "EditorM.h"WESRUESUEsources_5316/dwtools/.praat_David_init.cpp.kate-swp0000664000176700017670000000023011652055411021170 0ustar paulpaulKate Swap File - Version 1.0SR'I' ESR'I' ESRsIs ESRsIs Esources_5316/dwtools/DTW_and_TextGrid.cpp0000644000176700017670000002345111735023201017213 0ustar paulpaul/* DTW_and_TextGrid.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20060906 djmw 20070306: Reverse x and y. Reference should always be vertical! djmw 20110304 Thing_new */ #include "DTW_and_TextGrid.h" // begin old prototypes for compatibility reasons with the past TextGrid DTW_and_TextGrid_to_TextGrid_old (DTW me, TextGrid thee); IntervalTier DTW_and_IntervalTier_to_IntervalTier_old (DTW me, IntervalTier thee); TextTier DTW_and_TextTier_to_TextTier_old (DTW me, TextTier thee); // end old /* Get times from TextGrid and substitute new time form the y-times of the DTW. */ TextTier DTW_and_TextTier_to_TextTier (DTW me, TextTier thee, double precision) { try { if (fabs (my ymin - thy xmin) <= precision && fabs (my ymax - thy xmax) <= precision) { // map from Y to X autoTextTier him = Data_copy (thee); his xmin = my xmin; his xmax = my xmax; for (long i = 1; i <= his points -> size; i++) { TextPoint textpoint = (TextPoint) his points -> item[i]; double time = DTW_getXTimeFromYTime (me, textpoint -> number); textpoint -> number = time; } return him.transfer(); } else if (fabs (my xmin - thy xmin) <= precision && fabs (my xmax - thy xmax) <= precision) { // map from X to Y autoTextTier him = Data_copy (thee); his xmin = my ymin; his xmax = my ymax; for (long i = 1; i <= his points -> size; i++) { TextPoint textpoint = (TextPoint) his points -> item[i]; double time = DTW_getYTimeFromXTime (me, textpoint -> number); textpoint -> number = time; } return him.transfer(); } else { Melder_throw ("The domain of the TextTier and one of the domains of the DTW must be equal."); } } catch (MelderError) { Melder_throw ("TextTier not created from DTW & TextTier."); } } IntervalTier DTW_and_IntervalTier_to_IntervalTier (DTW me, IntervalTier thee, double precision) { try { if (fabs (my ymin - thy xmin) <= precision && fabs (my ymax - thy xmax) <= precision) { // map from Y to X autoIntervalTier him = Data_copy (thee); his xmin = my xmin; his xmax = my xmax; for (long i = 1; i <= his intervals -> size; i++) { TextInterval textinterval = (TextInterval) his intervals -> item[i]; double xmin = DTW_getXTimeFromYTime (me, textinterval -> xmin); textinterval -> xmin = xmin; double xmax = DTW_getXTimeFromYTime (me, textinterval -> xmax); textinterval -> xmax = xmax; } return him.transfer(); } else if (fabs (my xmin - thy xmin) <= precision && fabs (my xmax - thy xmax) <= precision) { // map from X to Y autoIntervalTier him = Data_copy (thee); his xmin = my ymin; his xmax = my ymax; for (long i = 1; i <= his intervals -> size; i++) { TextInterval textinterval = (TextInterval) his intervals -> item[i]; double xmin = DTW_getYTimeFromXTime (me, textinterval -> xmin); textinterval -> xmin = xmin; double xmax = DTW_getYTimeFromXTime (me, textinterval -> xmax); textinterval -> xmax = xmax; } return him.transfer(); } else { Melder_throw ("The domain of the IntervalTier and one of the domains of the DTW must be equal."); } } catch (MelderError) { Melder_throw ("IntervalTier not created from DTW & IntervalTier."); } } TextGrid DTW_and_TextGrid_to_TextGrid (DTW me, TextGrid thee, double precision) { try { double tmin, tmax; if (fabs (my ymin - thy xmin) <= precision && fabs (my ymax - thy xmax) <= precision) { tmin = my xmin; tmax = my xmax; } else if (fabs (my xmin - thy xmin) <= precision && fabs (my xmax - thy xmax) <= precision) { tmin = my ymin; tmax = my ymax; } else { Melder_throw ("The domain of the TextGrid must be equal to one of the domains of the DTW."); } autoTextGrid him = TextGrid_createWithoutTiers (tmin, tmax); for (long i = 1; i <= thy tiers -> size; i++) { Function anyTier = (Function) thy tiers -> item[i]; if (anyTier -> classInfo == classIntervalTier) { autoIntervalTier tier = DTW_and_IntervalTier_to_IntervalTier (me, (IntervalTier) anyTier, precision); TextGrid_addTier (him.peek(), tier.peek()); } else if (anyTier -> classInfo == classTextTier) { autoTextTier tier = DTW_and_TextTier_to_TextTier (me, (TextTier) anyTier, precision); TextGrid_addTier (him.peek(), tier.peek()); } else { Melder_throw ("Unknown tier."); } } return him.transfer(); } catch (MelderError) { Melder_throw ("TextGrid not created from DTW & TextGrid."); } } Table DTW_and_IntervalTier_to_Table (DTW me, IntervalTier thee, double precision) { try { long numberOfIntervals = thy intervals -> size; autoTable him = Table_createWithColumnNames (numberOfIntervals, L"tmin tmax label dist"); if (fabs (my ymin - thy xmin) <= precision && fabs (my ymax - thy xmax) <= precision) { // map from Y to X long pathIndex = 1; for (long i = 1; i <= numberOfIntervals; i++) { TextInterval textinterval = (TextInterval) thy intervals -> item[i]; double xmin = DTW_getXTimeFromYTime (me, textinterval -> xmin); double xmax = DTW_getXTimeFromYTime (me, textinterval -> xmax); long ixmin, ixmax; long numberOfFrames = Matrix_getWindowSamplesX (me, xmin, xmax, &ixmin, &ixmax); double sumOfDistances = 0; while (pathIndex < my pathLength && my path[pathIndex].x < ixmax) { sumOfDistances += my z[my path[pathIndex].y][my path[pathIndex].x]; pathIndex++; } Table_setNumericValue (him.peek(), i, 1, textinterval -> xmin); Table_setNumericValue (him.peek(), i, 2, textinterval -> xmax); Table_setStringValue (him.peek(), i, 3, textinterval -> text); Table_setNumericValue (him.peek(), i, 4, sumOfDistances / numberOfFrames); } } else if (fabs (my xmin - thy xmin) <= precision && fabs (my xmax - thy xmax) <= precision) { // map from X to Y long pathIndex = 1; for (long i = 1; i <= numberOfIntervals; i++) { TextInterval textinterval = (TextInterval) thy intervals -> item[i]; double ymin = DTW_getYTimeFromXTime (me, textinterval -> xmin); double ymax = DTW_getYTimeFromXTime (me, textinterval -> xmax); long iymin, iymax; long numberOfFrames = Matrix_getWindowSamplesY (me, ymin, ymax, &iymin, &iymax); double sumOfDistances = 0; while (pathIndex < my pathLength && my path[pathIndex].y < iymax) { sumOfDistances += my z[my path[pathIndex].y][my path[pathIndex].x]; pathIndex++; } Table_setNumericValue (him.peek(), i, 1, textinterval -> xmin); Table_setNumericValue (him.peek(), i, 2, textinterval -> xmax); Table_setStringValue (him.peek(), i, 3, textinterval -> text); Table_setNumericValue (him.peek(), i, 4, sumOfDistances / numberOfFrames); } } else { Melder_throw ("The domain of the IntervalTier and one of the domains of the DTW must be equal."); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no Table with distances created."); } } /* Get times from TextGrid and substitute new time form the y-times of the DTW. */ TextTier DTW_and_TextTier_to_TextTier_old (DTW me, TextTier thee) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("The domain of the TextTier and the DTW must be equal."); } autoTextTier him = Data_copy (thee); his xmin = my ymin; his xmax = my ymax; for (long i = 1; i <= his points -> size; i++) { TextPoint textpoint = (TextPoint) his points -> item[i]; double time = DTW_getPathY (me, textpoint -> number); textpoint -> number = time; } return him.transfer(); } catch (MelderError) { Melder_throw ("TextTier not created."); } } IntervalTier DTW_and_IntervalTier_to_IntervalTier_old (DTW me, IntervalTier thee) { try { if ( (my xmin != thy xmin) || my xmax != thy xmax) Melder_throw ("The domain of the IntervalTier and the DTW must be equal."); autoIntervalTier him = Data_copy (thee); his xmin = my ymin; his xmax = my ymax; for (long i = 1; i <= his intervals -> size; i++) { TextInterval textinterval = (TextInterval) his intervals -> item[i]; double xmin = DTW_getPathY (me, textinterval -> xmin); textinterval -> xmin = xmin; double xmax = DTW_getPathY (me, textinterval -> xmax); textinterval -> xmax = xmax; } return him.transfer(); } catch (MelderError) { Melder_throw ("IntervalTier not created."); } } TextGrid DTW_and_TextGrid_to_TextGrid_old (DTW me, TextGrid thee) { try { autoTextGrid him = Thing_new (TextGrid); if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("The domain of the TextGrid and the y-domain of the DTW must be equal."); } his xmin = my ymin; his xmax = my ymax; his tiers = Ordered_create (); for (long i = 1; i <= thy tiers -> size; i++) { Data anyTier = (Data) thy tiers -> item[i]; if (anyTier -> classInfo == classIntervalTier) { autoIntervalTier tier = DTW_and_IntervalTier_to_IntervalTier_old (me, (IntervalTier) anyTier); TextGrid_addTier (him.peek(), tier.peek()); } else if (anyTier -> classInfo == classTextTier) { autoTextTier tier = DTW_and_TextTier_to_TextTier_old (me, (TextTier) anyTier); TextGrid_addTier (him.peek(), tier.peek()); } else { Melder_throw (L"Unknown tier."); } } return him.transfer(); } catch (MelderError) { Melder_throw ("TextGrid not created."); } } /* End of file DTW_and_TextGrid.cpp */ sources_5316/dwtools/TableOfReal_extensions.h0000644000176700017670000001637711752704002020202 0ustar paulpaul#ifndef _TableOfReal_extensions_h_ #define _TableOfReal_extensions_h_ /* TableOfReal_extensions.h * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020411 initial GPL djmw 20110105 Latest modification. */ #include "TableOfReal.h" #include "Collection.h" #include "Pattern.h" #include "Categories.h" #include "Strings.h" #include "SSCP.h" int TableOfReal_to_Pattern_and_Categories(I, long fromrow, long torow, long fromcol, long tocol, Pattern *p, Categories *c); TableOfReal TableOfReal_transpose (I); Strings TableOfReal_extractRowLabels (I); Strings TableOfReal_extractColumnLabels (I); void TableOfReal_and_Categories_setRowLabels (I, Categories thee); /* !!! Set rowlabels from categories Because we need a Table-object with string-columns. */ TableOfReal TableOfReal_sortOnlyByRowLabels (I); long *TableOfReal_getSortedIndexFromRowLabels (I); TableOfReal TableOfReal_sortRowsByIndex (I, long *index, int reverse); /* thy data[reverse ? i : index[i]][j] = my data[reverse ? index[i] : i] */ TableOfReal TableOfReal_createIrisDataset (); int TableOfReal_areAllCellsDefined (I, long rb, long re, long cb, long ce); TableOfReal TableOfReal_createFromPolsData_50males (int include_levels); TableOfReal TableOfReal_createFromVanNieropData_25females (int include_levels); TableOfReal TableOfReal_createFromWeeninkData (int option); /* M W C */ void TableOfReal_getColumnExtrema (I, long col, double *min, double *max); void TableOfReal_drawRowsAsHistogram (I, Graphics g, const wchar_t *rows, long colb, long cole, double ymin, double ymax, double xoffsetFraction, double interbarFraction, double interbarsFraction, const wchar_t *greys, int garnish); void TableOfReal_drawScatterPlot (I, Graphics g, long icx, long icy, long rowb, long rowe, double xmin, double xmax, double ymin, double ymax, int labelSize, int useRowLabels, const wchar_t *label, int garnish); void TableOfReal_drawScatterPlotMatrix (I, Graphics g, long colb, long cole, double fractionWhite); void TableOfReal_drawBoxPlots (I, Graphics g, long rowmin, long rowmax, long colmin, long colmax, double ymin, double ymax, int garnish); void TableOfReal_drawVectors (I, Graphics g, long colx1, long coly1, long colx2, long coly2, double xmin, double xmax, double ymin, double ymax, int vectype, int labelsize, int garnish); void TableOfReal_drawBiplot (I, Graphics g, double xmin, double xmax, double ymin, double ymax, double sv_splitfactor, int labelsize, int garnish); void TableOfReal_drawColumnAsDistribution (I, Graphics g, int column, double minimum, double maximum, long nBins, double freqMin, double freqMax, int cumulative, int garnish); long TableOfReal_getNumberOfLabelMatches (I, const wchar_t *search, int columnLabels, int use_regexp); /* Find number of labels that match search description. */ int TableOfReal_equalLabels (I, thou, int rowLabels, int columnLabels); /* return 1 when labels are equal else 0 */ void TableOfReal_copyLabels (I, thou, int rowOrigin, int columnOrigin); /* rowOrigin == 1 copy from row rowOrigin == 0 do nothing rowOrigin == -1 copy from column columnOrigin == 1 copy from column columnOrigin == 0 do nothing columnOrigin == -1 copy from row */ void TableOfReal_labelsFromCollectionItemNames (I, thou, int row, int column); void TableOfReal_setSequentialColumnLabels (I, long from, long to, const wchar_t *precursor, long number, long increment); void TableOfReal_setSequentialRowLabels (I, long from, long to, const wchar_t *precursor, long number, long increment); int TableOfReal_hasRowLabels (I); int TableOfReal_hasColumnLabels (I); void TableOfReal_changeRowLabels (I, const wchar_t *search, const wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp); void TableOfReal_changeColumnLabels (I, const wchar_t *search, const wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp); /* Change all row/column labels. The 'search' and 'replace' string are interpreted as regular expressions when 'use_regexp' != 0. 'maximumNumberOfReplaces' is the maximum number of replaces in EACH string in the array of strings (you can replace ALL occurrences by making this number <= 0) The totalnumber of matches found is returned in 'nmatches'. The number of strings with at least one match is returned in 'nstringmatches'. */ void TableOfReal_centreColumns (I); void TableOfReal_centreColumns_byRowLabel (I); /* PRECONDITION: Table must be sorted by row labels !! */ double TableOfReal_getColumnQuantile (I, long col, double quantile); double TableOfReal_getRowSumByLabel (I, const wchar_t *label); double TableOfReal_getRowSum (I, long index); double TableOfReal_getColumnSumByLabel (I, const wchar_t *label); double TableOfReal_getColumnSum (I, long index); double TableOfReal_getGrandSum (I); void TableOfReal_centreRows (I); void TableOfReal_doubleCentre (I); int TableOfReal_checkPositive (I); double TableOfReal_getTableNorm (I); void TableOfReal_normalizeTable (I, double norm); void TableOfReal_normalizeColumns (I, double norm); void TableOfReal_normalizeRows (I, double norm); void TableOfReal_standardizeColumns (I); void TableOfReal_standardizeRows (I); TableOfReal TableOfReal_rankColumns (I); TableOfReal TableOfReal_meansByRowLabels (I, int expand, int stats); /* stats == 0? averages : medians For a table with n rows and m different labels (m <= n): if (expand=1) { output has n rows, substitute each array by the average value for that row label} else output a table with m rows, the averages for the m labels. */ TableOfReal TableOfReal_bootstrap (TableOfReal me); /* Produce new table with the same number of entries, but randomly selected with replacement. */ TableOfReal TableOfReal_randomizeRows (TableOfReal me); /* Produce new table with randomized rows */ /* For the inheritors */ TableOfReal TableOfReal_to_TableOfReal (I); TableOfReal TableOfReal_choleskyDecomposition (I, int upper, int inverse); TableOfReal TableOfReal_appendColumns (I, thou); TableOfReal TableOfReal_appendColumnsMany (Collection me); void TableOfReal_copyOneRowWithLabel (I, thou, long myrow, long thyrow); double TableOfReal_normalityTest_BHEP (I, double *beta, double *tnb, double *lnmu, double *lnvar); TableOfReal TableOfReal_and_TableOfReal_crossCorrelations (I, thou, int by_columns, int center, int normalize); /********************* class TablesOfReal ******************************/ Thing_define (TablesOfReal, Ordered) { }; void TablesOfReal_init (I, ClassInfo klas); TablesOfReal TablesOfReal_create (); TableOfReal TablesOfReal_sum (I); int TablesOfReal_checkDimensions (I); #endif /* _TableOfReal_extensions_h_ */ sources_5316/dwtools/ICA.h0000664000176700017670000001352311737553641014205 0ustar paulpaul#ifndef _ICA_h_ #define _ICA_h_ /* ICA.h * * Copyright (C) 2010-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20101202 Initial version djmw 20120406 Latest modification. */ #include "SSCP.h" #include "Sound.h" Thing_define (MixingMatrix, TableOfReal) { }; Thing_define (Diagonalizer, TableOfReal) { }; Thing_define (CrossCorrelationTable, SSCP) { // overridden methods: public: virtual void v_info (); }; Thing_define (CrossCorrelationTables, Ordered) { // overridden methods: public: virtual void v_info (); }; /* Cell [i,j] of a CrossCorrelationTable contains the cross-correlation between signal i and signal j. For example, the CrossCorrelation of an n-channel sound is a nxn table where cell [i,j] contains the cross-correlation of channel i with channel j for a particlular lag time tau. In the statistical literature sometimes the cross-correlation between signals is also called "covariance". However, the only thing a Covariance has in common with a CrossCorrelationTable is that both are symmetric matrices. Differences between a CrossCorrelationTable and a Covariance: 1. a Covariance matrix is always positive definite, for a cross-correlation table this is only guaranteed for lag time tau = 0. 2. The elements c[i][j] in a Covariance always satisfy |c[i][j]/sqrt(c[i][i]*c[j][j])| <= 1, this is in general not the case for cross-correlations. */ CrossCorrelationTable CrossCorrelationTable_create (long dimension); CrossCorrelationTable CrossCorrelationTable_createSimple (wchar_t *covars, wchar_t *centroid, long numberOfSamples); /* (sum(i,j=1..dimension, i!=j; C[i][j]^2))/(dimension*(dimension-1)) */ double CrossCorrelationTable_getDiagonalityMeasure (CrossCorrelationTable me); CrossCorrelationTable CrossCorrelationTable_and_Diagonalizer_diagonalize (CrossCorrelationTable me, Diagonalizer thee); CrossCorrelationTables CrossCorrelationTables_create (); double CrossCorrelationTables_getDiagonalityMeasure (CrossCorrelationTables me, double *w, long start, long end); double CrossCorrelationTables_and_Diagonalizer_getDiagonalityMeasure (CrossCorrelationTables me, Diagonalizer thee, double *w, long start, long end); CrossCorrelationTables CrossCorrelationTables_createTestSet (long dimension, long n, int firstPositiveDefinite, double sigma); MixingMatrix MixingMatrix_create (long numberOfChannels, long numberOfComponents); MixingMatrix MixingMatrix_createSimple (long numberOfChannels, long numberOfComponents, wchar_t *elements); void MixingMatrix_initializeRandom (MixingMatrix me); Diagonalizer Diagonalizer_create (long dimension); Sound Sound_and_MixingMatrix_mix (Sound me, MixingMatrix thee); Sound Sound_and_MixingMatrix_unmix (Sound me, MixingMatrix thee); MixingMatrix Sound_to_MixingMatrix (Sound me, double startTime, double endTime, long ncovars, double lagTime, long maxNumberOfIterations, double delta_w, int method); Sound Sound_to_Sound_BSS (Sound me, double startTime, double endTime, long ncovars, double lagTime, long maxNumberOfIterations, double delta_w, int method); Sound Sound_and_PCA_whitenChannels (Sound me, PCA thee, long numberOfComponents); Sound Sound_and_PCA_projectChannels (Sound me, PCA thee, long numberOfComponents); PCA Sound_to_PCA_channels (Sound me, double startTime, double endTime); Sound Sound_whitenChannels (Sound me, double varianceFraction); Sound Sound_and_Covariance_whitenChannels (Sound me, Covariance thee, double varianceFraction); void MixingMatrix_and_CrossCorrelationTables_improveUnmixing (MixingMatrix me, CrossCorrelationTables thee, long maxNumberOfIterations, double tol, int method); /* Determine the matrix that diagonalizes a series of CrossCorrelationTables as well as possible. */ Diagonalizer CrossCorrelationTables_to_Diagonalizer (CrossCorrelationTables me, long maxNumberOfIterations, double tol, int method); void Diagonalizer_and_CrossCorrelationTables_improveDiagonality (Diagonalizer me, CrossCorrelationTables thee, long maxNumberOfIterations, double tol, int method); /* Determine V*C[k]*V' for k=1..n, where V is the diagonalizer matrix and C[k} the k-th CrossCorrelationTable. */ CrossCorrelationTables CrossCorrelationTables_and_Diagonalizer_diagonalize (CrossCorrelationTables me, Diagonalizer thee); Diagonalizer MixingMatrix_to_Diagonalizer (MixingMatrix me); MixingMatrix Diagonalizer_to_MixingMatrix (Diagonalizer me); /* For multi-channel "sounds" like EEG signals. The cross-correlation between channel i and channel j is defined as sum(k=1..nsamples; (z[i][k] - mean[i])(z[j][k + lag] - mean[j])) / (nsamples - 1). */ CrossCorrelationTable Sound_to_CrossCorrelationTable (Sound me, double startTime, double endTime, double lagTime); CrossCorrelationTable Sounds_to_CrossCorrelationTable_combined (Sound me, Sound thee, double relativeStartTime, double relativeEndTime, double lagTime); // The covariance is the cross-correlation with lag 0. Covariance Sound_to_Covariance_channels (Sound me, double startTime, double endTime); /* Determine a CrossCorrelationTable for lags (k-1)*lagTime, where k = 1...n. */ CrossCorrelationTables Sound_to_CrossCorrelationTables (Sound me, double startTime, double endTime, double lagTime, long n); MixingMatrix TableOfReal_to_MixingMatrix (TableOfReal me); #endif /*_ICA_h_ */ sources_5316/dwtools/Distance.cpp0000644000176700017670000000236711627236214015670 0ustar paulpaul/* Distance.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110304 Thing_new */ #include "Distance.h" Thing_implement (Distance, Proximity, 0); Distance Distance_create (long numberOfPoints) { try { autoDistance me = Thing_new (Distance); Proximity_init (me.peek(), numberOfPoints); return me.transfer(); } catch (MelderError) { Melder_throw ("Distance not created."); } } void Distance_drawDendogram (Distance me, Graphics g, int method) { (void) me; (void) g; (void) method; } /* End of file Distance.cpp */ sources_5316/dwtools/TextGrid_extensions.cpp0000664000176700017670000006353311753532347020161 0ustar paulpaul/* TextGrid_extensions.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020702 GPL header djmw 20020702 +TextGrid_extendTime djmw 20051215 Corrected a bug in TextGrid_readFromTIMITLabelFile that caused a crash when the first number in a file was not 0 (in that case an empty interval was added as the first element in the tier). djmw 20060517 Added (TextTier|IntervalTier|TextGrid)_changeLabels. djmw 20060712 TextGrid_readFromTIMITLabelFile: don't set first boundary to zero for .wrd files. djmw 20060921 Added IntervalTier_cutIntervalOnLabelMatch, IntervalTier_cutIntervals_minimumDuration djmw 20061113 Reassign item in list after a deletion. djmw 20061116 Added IntervalTier_cutInterval to correct a bug in IntervalTier_removeBoundary... djmw 20071008 Removed two unused variables. djmw 20071202 Melder_warning */ #include #include "TextGrid_extensions.h" #include "NUM2.h" struct TIMIT_key { const char *timitLabel, *ipaLabel; } TIMIT_toIpaTable[] = { {"", ""}, /* Vowels */ {"iy", "i"}, /* beet: bcl b IY tcl t */ {"ih", "\\ic"}, /* bit: bcl b IH tcl t */ {"eh", "\\ep"}, /* bet: bcl b EH tcl t */ {"ey", "e"}, /* bait: bcl b EY tcl t */ {"ae", "\\ae"}, /* bat: bcl b AE tcl t */ {"aa", "\\as"}, /* bott: bcl b AA tcl t */ {"aw", "a\\hs"}, /* bout: bcl b AW tcl t */ {"ay", "a\\ic"}, /* bite: bcl b AY tcl t */ {"ah", "\\vt"}, /* but: bcl b AH tcl t */ {"ao", "\\ct"}, /* bought: bcl b AO tcl t */ {"oy", "\\ct\\ic"}, /* boy: bcl b OY */ {"ow", "o"}, /* boat: bcl b OW tcl t */ {"uh", "\\hs"}, /* book: bcl b UH tcl t */ {"uw", "u"}, /* boot: bcl b UW tcl t */ /* fronted allophone of uw (alveolair contexts) */ {"ux", "\\u\""}, /* toot: tcl t UX tcl t */ {"er", "\\er\\hr"}, /* bird: bcl b ER dcl d */ {"ax", "\\sw"}, /* about: AX bcl b aw tcl t */ {"ix", "\\i-"}, /* debit: dcl d eh bcl b IX tcl t */ {"axr", "\\sr"}, /* butter: bcl ah dx AXR */ /* devoiced schwa, very short */ {"ax-h", "\\sw\\ov"}, /* suspect: s AX-H s pcl p eh kcl k tcl t */ /* Semivowels and glides */ {"l", "l"}, /* lay: L ey */ {"r", "r"}, /* ray: R ey */ {"w", "w"}, /* way: w ey */ {"y", "j"}, /* yacht: Y aa tcl t */ {"hh", "h" }, /* hay: HH ey*/ /* voiced allophone of h */ {"hv", "\\hh"}, /* ahead: ax HV eh dcl d */ {"el", "l\\|v"}, /* bottle: bcl b aa tcl t EL */ /* Nasals */ {"m", "m"}, /* mom: M aa M */ {"n", "n"}, /* noon: N uw N*/ {"ng", "\\ng"}, /* sing: s ih NG */ {"em", "m\\|v"}, /* bottom: b aa tcl t EM */ {"en", "n\\|v"}, /* button: b ah q EN */ {"eng", "\\ng\\|v"}, /* washington: w aa sh ENG tcl t ax n */ /* nasal flap */ {"nx", "n^\\fh"}, /* winner: wih NX axr */ /* Fricatives */ {"s", "s"}, /* sea: S iy */ {"sh", "\\sh"}, /* she: SH iy */ {"z", "z"}, /* zone: Z ow n */ {"zh", "\\zh"}, /* azure: ae ZH er */ {"f", "f"}, /* fin: F ih n */ {"th", "\\te"}, /* thin: TH ih n */ {"v", "v"}, /* van: v ae n */ {"dh", "\\dh"}, /* then: DH en */ /* Affricates */ {"jh", "d\\zh"}, /* joke: DCL JH ow kcl k */ {"ch", "t\\sh"}, /* choke TCL CH ow kcl k */ /* Stops */ {"b", "b"}, /* bee: BCL B iy */ {"d", "d"}, /* day: DCL D ey */ {"g", "g"}, /* gay: GCL G ey */ {"p", "p"}, /* pea: PCL P iy */ {"t", "t"}, /* tea: TCL T iy */ {"k", "k"}, /* key: KCL K iy */ /* flap */ {"dx", "\\fh"}, /* muddy: m ah DX iy & dirty: dcl d er DX iy */ /* glottal stop */ {"q", "?"}, /* Others */ {"pau", ""}, /* pause */ {"epi", ""}, /* epenthetic silence */ {"h#", ""}, /* marks start and end piece of sentence */ /* the following markers only occur in the dictionary */ {"1", "1"}, /* primary stress marker */ {"2", "2"} /* secondary stress marker */ }; #define TIMIT_NLABELS (sizeof TIMIT_toIpaTable / sizeof TIMIT_toIpaTable[1] - 1) static const char *TIMIT_DELIMITER = "h#"; static const char *timitLabelToIpaLabel (const char timitLabel[]) { for (unsigned int i = 1; i <= TIMIT_NLABELS; i++) if (!strcmp (TIMIT_toIpaTable[i].timitLabel, timitLabel)) { return TIMIT_toIpaTable[i].ipaLabel; } return timitLabel; } static int isTimitPhoneticLabel (const char label[]) { for (unsigned int i = 1; i <= TIMIT_NLABELS; i++) if (! strcmp (TIMIT_toIpaTable[i].timitLabel, label)) { return 1; } return 0; } static int isTimitWord (const char label[]) { const char *p = label; for (; *p; p++) if (isupper (*p) && *p != '\'') { return 0; } return 1; } Any TextGrid_TIMITLabelFileRecognizer (int nread, const char *header, MelderFile file) { long it[5]; int length, phnFile = 0; char hkruis[3] = "h#", label1[512], label2[512]; if (nread < 12 || sscanf (header, "%ld%ld%s%n\n", &it[1], &it[2], label1, &length) != 3 || it[1] < 0 || it[2] <= it[1] || sscanf (&header[length], "%ld%ld%s\n", &it[3], &it[4], label2) != 3 || // 20120512 djmw removed the extra "it[3] < it[2]" check, because otherwise train/dr7/mdlm0/si1864.wrd cannot be read it[4] <= it[3]) { return 0; } if (! strcmp (label1, hkruis)) { if (isTimitPhoneticLabel (label2)) { phnFile = 1; } else if (! isTimitWord (label2)) { return 0; } } else if (! isTimitWord (label1) || ! isTimitWord (label2)) { return 0; } return TextGrid_readFromTIMITLabelFile (file, phnFile); } static void IntervalTier_add (IntervalTier me, double xmin, double xmax, const wchar_t *label) { long i = IntervalTier_timeToIndex (me, xmin); // xmin is in interval i if (i < 1) { Melder_throw ("Index too low."); } autoTextInterval newti = TextInterval_create (xmin, xmax, label); TextInterval interval = (TextInterval) my intervals -> item[i]; double xmaxi = interval -> xmax; if (xmax > xmaxi) { Melder_throw ("Don't know what to do"); // Don't know what to do } if (xmin == interval -> xmin) { if (xmax == interval -> xmax) { // interval already present TextInterval_setText (interval, label); return; } // split interval interval -> xmin = xmax; Collection_addItem (my intervals, newti.transfer()); return; } interval -> xmax = xmin; Collection_addItem (my intervals, newti.transfer()); // extra interval when xmax's are not the same if (xmax < xmaxi) { autoTextInterval newti2 = TextInterval_create (xmax, xmaxi, interval -> text); Collection_addItem (my intervals, newti2.transfer()); } } TextGrid TextGrid_readFromTIMITLabelFile (MelderFile file, int phnFile) { try { double dt = 1.0 / 16000; /* 1 / (TIMIT samplingFrequency) */ double xmax = dt; autofile f = Melder_fopen (file, "r"); // Ending time will only be known after all labels have been read. // We start with a sufficiently long duration (one hour) and correct this later. autoTextGrid me = TextGrid_create (0, 3600, L"wrd", 0); IntervalTier timit = (IntervalTier) my tiers -> item[1]; long linesRead = 0; char line[200], label[200]; while (fgets (line, 199, f)) { long it1, it2; linesRead++; if (sscanf (line, "%ld%ld%s", &it1, &it2, label) != 3) { Melder_throw ("Incorrect number of items."); } if (it1 < 0 || it2 <= it1) { Melder_throw (L"Incorrect time at line ", linesRead); } xmax = it2 * dt; double xmin = it1 * dt; long ni = timit -> intervals -> size - 1; if (ni < 1) { ni = 1; // Some files do not start with a first line "0 h#". // Instead they start with " h#", where number1 > 0. // We override number1 with 0. */ if (xmin > 0 && phnFile) { xmin = 0; } } TextInterval interval = (TextInterval) timit -> intervals -> item[ni]; if (xmin < interval -> xmax && linesRead > 1) { xmin = interval -> xmax; Melder_warning (L"File \"", MelderFile_messageName (file), L"\": Start time set to previous end " "time for label at line ", Melder_integer (linesRead), L"."); } // standard: new TextInterval const char *labelstring = (strncmp (label, "h#", 2) ? label : TIMIT_DELIMITER); IntervalTier_add (timit, xmin, xmax, Melder_peekUtf8ToWcs (labelstring)); } // Now correct the end times, based on last read interval. // (end time was set to large value!) if (timit -> intervals -> size < 2) { Melder_throw ("Empty TextGrid"); } Collection_removeItem (timit -> intervals, timit -> intervals -> size); TextInterval interval = (TextInterval) timit -> intervals -> item[timit -> intervals -> size]; timit -> xmax = interval -> xmax; my xmax = xmax; if (phnFile) { // Create tier 2 with IPA symbols autoIntervalTier ipa = Data_copy (timit); Thing_setName (ipa.peek(), L"ipa"); // First change the data in ipa for (long i = 1; i <= ipa -> intervals -> size; i++) { interval = (TextInterval) timit -> intervals -> item[i]; TextInterval_setText ( (TextInterval) ipa -> intervals -> item[i], Melder_peekUtf8ToWcs (timitLabelToIpaLabel (Melder_peekWcsToUtf8 (interval -> text)))); } Collection_addItem (my tiers, ipa.transfer()); // Then: add to collection Thing_setName (timit, L"phn"); // rename wrd } f.close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("TextGrid not read from file ", file, "."); } } TextGrid TextGrids_merge (TextGrid me, TextGrid thee) { try { int at_end = 0, at_start = 1; autoTextGrid g1 = Data_copy (me); autoTextGrid g2 = Data_copy (thee); // The new TextGrid will have the domain // [min(g1->xmin, g2->xmin), max(g1->xmax, g2->xmax)] double extra_time_end = fabs (g2 -> xmax - g1 -> xmax); double extra_time_start = fabs (g2 -> xmin - g1 -> xmin); if (g1 -> xmin > g2 -> xmin) { TextGrid_extendTime (g1.peek(), extra_time_start, at_start); } if (g1 -> xmax < g2 -> xmax) { TextGrid_extendTime (g1.peek(), extra_time_end, at_end); } if (g2 -> xmin > g1 -> xmin) { TextGrid_extendTime (g2.peek(), extra_time_start, at_start); } if (g2 -> xmax < g1 -> xmax) { TextGrid_extendTime (g2.peek(), extra_time_end, at_end); } for (long i = 1; i <= g2 -> tiers -> size; i++) { autoFunction tier = Data_copy ( (Function) g2 -> tiers -> item [i]); Collection_addItem (g1 -> tiers, tier.transfer()); } return g1.transfer(); } catch (MelderError) { Melder_throw (me, " & ", thee, ": not merged."); } } void IntervalTier_setLaterEndTime (IntervalTier me, double xmax, const wchar_t *mark) { try { if (xmax <= my xmax) return; // nothing to be done TextInterval ti = (TextInterval) my intervals -> item[my intervals -> size]; Melder_assert (xmax > ti -> xmax); if (mark != NULL) { autoTextInterval interval = TextInterval_create (ti -> xmax, xmax, mark); Collection_addItem (my intervals, interval.transfer()); } else { // extend last interval ti -> xmax = xmax; } my xmax = xmax; } catch (MelderError) { Melder_throw (L"Larger end time of IntervalTier not set."); } } void IntervalTier_setEarlierStartTime (IntervalTier me, double xmin, const wchar_t *mark) { try { if (xmin >= my xmin) return; // nothing to be done TextInterval ti = (TextInterval) my intervals -> item[1]; Melder_assert (xmin < ti -> xmin); if (mark != NULL) { autoTextInterval interval = TextInterval_create (xmin, ti -> xmin, mark); Collection_addItem (my intervals, interval.transfer()); } else { // extend first interval ti -> xmin = xmin; } my xmin = xmin; } catch (MelderError) { Melder_throw (L"Earlier start time of IntervalTier not set."); } } void IntervalTier_moveBoundary (IntervalTier me, long iint, bool atStart, double newTime) { try { if (iint < 1 or iint > my intervals -> size) { Melder_throw ("Interval out of range."); } if ((iint == 1 && atStart) or ((iint == my intervals -> size && not atStart))) { Melder_throw ("Cannot change the domain."); } TextInterval interval = (TextInterval) my intervals -> item[iint]; if (atStart) { TextInterval pinterval = (TextInterval) my intervals -> item[iint-1]; if (newTime <= pinterval -> xmin) { Melder_throw ("Cannot move past the start of previous interval."); } pinterval -> xmax = interval -> xmin = newTime; } else { TextInterval ninterval = (TextInterval) my intervals -> item[iint+1]; if (newTime >= ninterval -> xmax) { Melder_throw ("Cannot move past the end of next interval."); } ninterval -> xmin = interval -> xmax = newTime; } } catch (MelderError) { Melder_throw (me, ": boundary not moved."); } } void TextTier_setLaterEndTime (TextTier me, double xmax, const wchar_t *mark) { try { if (xmax <= my xmax) return; // nothing to be done if (mark != NULL) { autoTextPoint textpoint = TextPoint_create (my xmax, mark); Collection_addItem (my points, textpoint.transfer()); } my xmax = xmax; } catch (MelderError) { Melder_throw (L"Larger end time of TextTier not set."); } } void TextTier_setEarlierStartTime (TextTier me, double xmin, const wchar_t *mark) { try { if (xmin >= my xmin) return; // nothing to be done if (mark != NULL) { autoTextPoint textpoint = TextPoint_create (my xmin, mark); Collection_addItem (my points, textpoint.transfer()); } my xmin = xmin; } catch (MelderError) { Melder_throw (L"Earlier start time of TextTier not set."); } } void TextGrid_setEarlierStartTime (TextGrid me, double xmin, const wchar_t *imark, const wchar_t *pmark) { try { if (xmin >= my xmin) return; for (long tierNumber = 1 ; tierNumber <= my tiers -> size; tierNumber++) { Function tier = (Function) my tiers -> item [tierNumber]; if (tier -> classInfo == classIntervalTier) { IntervalTier_setEarlierStartTime ((IntervalTier) tier, xmin, imark); } else { TextTier_setEarlierStartTime ((TextTier) tier, xmin, pmark); } } my xmin = xmin; } catch (MelderError) { Melder_throw (L"Earlier start time of TextGrid not set."); } } void TextGrid_setLaterEndTime (TextGrid me, double xmax, const wchar_t *imark, const wchar_t *pmark) { try { if (xmax <= my xmax) return; for (long tierNumber =1 ; tierNumber <= my tiers -> size; tierNumber++) { Function tier = (Function) my tiers -> item [tierNumber]; if (tier -> classInfo == classIntervalTier) { IntervalTier_setLaterEndTime ((IntervalTier) tier, xmax, imark); } else { TextTier_setLaterEndTime ((TextTier) tier, xmax, pmark); } } my xmax = xmax; } catch (MelderError) { Melder_throw (L"Larger end time of TextGrid not set."); } } void TextGrid_extendTime (TextGrid me, double extra_time, int position) { autoTextGrid thee = 0; try { double xmax = my xmax, xmin = my xmin; int at_end = position == 0; if (extra_time == 0) { return; } extra_time = fabs (extra_time); // Just in case... thee.reset (Data_copy (me)); if (at_end) { xmax += extra_time; } else { xmin -= extra_time; } for (long i = 1; i <= my tiers -> size; i++) { Function anyTier = (Function) my tiers -> item [i]; double tmin = anyTier -> xmin, tmax = anyTier -> xmax; if (at_end) { anyTier -> xmax = xmax; tmin = tmax; tmax = xmax; } else { anyTier -> xmin = xmin; tmax = tmin; tmin = xmin; } if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; autoTextInterval interval = TextInterval_create (tmin, tmax, L""); Collection_addItem (tier -> intervals, interval.transfer()); } } my xmin = xmin; my xmax = xmax; } catch (MelderError) { Melder_throw (me, ": time not extended."); } } void TextGrid_setTierName (TextGrid me, long itier, const wchar_t *newName) { try { long ntiers = my tiers -> size; if (itier < 1 || itier > ntiers) Melder_throw ("Tier number (", itier, ") should not be " "larger than the number of tiers (", ntiers, L")."); Thing_setName ( (Thing) my tiers -> item [itier], newName); } catch (MelderError) { Melder_throw (me, ": tier name not set."); } } static void IntervalTier_cutInterval (IntervalTier me, long index, int extend_option) { long size_pre = my intervals -> size; /* There always must be at least one interval */ if (size_pre == 1 || index > size_pre || index < 1) { return; } TextInterval ti = (TextInterval) my intervals -> item[index]; double xmin = ti -> xmin; double xmax = ti -> xmax; Collection_removeItem (my intervals, index); if (index == 1) { // Change xmin of the new first interval. ti = (TextInterval) my intervals -> item[index]; ti -> xmin = xmin; } else if (index == size_pre) { // Change xmax of the new last interval. ti = (TextInterval) my intervals -> item[my intervals -> size]; ti -> xmax = xmax; } else { if (extend_option == 0) { // extend earlier interval to the right ti = (TextInterval) my intervals -> item[index - 1]; ti -> xmax = xmax; } else { // extend next interval to the left ti = (TextInterval) my intervals -> item[index]; ti -> xmin = xmin; } } } void IntervalTier_removeBoundariesBetweenIdenticallyLabeledIntervals (IntervalTier me, const wchar_t *label) { try { for (long iint = my intervals -> size; iint > 1; iint--) { TextInterval ti = (TextInterval) my intervals -> item[iint]; if (Melder_wcsequ (ti -> text, label)) { TextInterval tim1 = (TextInterval) my intervals -> item[iint - 1]; if (Melder_wcsequ (tim1 -> text, label)) { Melder_free (tim1 -> text); IntervalTier_removeLeftBoundary (me, iint); } } } } catch (MelderError) { Melder_throw (me, ": boundaries not removed."); } } void IntervalTier_cutIntervals_minimumDuration (IntervalTier me, const wchar_t *label, double minimumDuration) { long i = 1; while (i <= my intervals -> size) { TextInterval ti = (TextInterval) my intervals -> item[i]; if ( (label == 0 || (ti -> text != 0 && wcsequ (ti -> text, label))) && ti -> xmax - ti -> xmin < minimumDuration) { IntervalTier_cutInterval (me, i, 0); } else { i++; } } } void IntervalTier_cutIntervalsOnLabelMatch (IntervalTier me, const wchar_t *label) { long i = 1; while (i < my intervals -> size) { TextInterval ti = (TextInterval) my intervals -> item[i]; TextInterval tip1 = (TextInterval) my intervals -> item[i + 1]; if ( (label == 0 || (ti -> text != 0 && wcsequ (ti -> text, label))) && (Melder_wcscmp (ti -> text, tip1 -> text) == 0)) { IntervalTier_cutInterval (me, i, 1); } else { i++; } } } void IntervalTier_changeLabels (I, long from, long to, const wchar_t *search, const wchar_t *replace, int use_regexp, long *nmatches, long *nstringmatches) { iam (IntervalTier); try { if (from == 0) { from = 1; } if (to == 0) { to = my intervals -> size; } if (from > to || from < 1 || to > my intervals -> size) { Melder_throw ("Incorrect specification of where to act."); } if (use_regexp && wcslen (search) == 0) Melder_throw ("The regex search string cannot be empty.\n" "You may search for an empty string with the expression \"^$\""); long nlabels = to - from + 1; autoNUMvector labels (1, nlabels); for (long i = from; i <= to; i++) { TextInterval interval = (TextInterval) my intervals -> item[i]; labels[i - from + 1] = interval -> text; // Shallow copy. } autostringvector newlabels (strs_replace (labels.peek(), 1, nlabels, search, replace, 0, nmatches, nstringmatches, use_regexp), 1, nlabels); for (long i = from; i <= to; i++) { TextInterval interval = (TextInterval) my intervals -> item[i]; Melder_free (interval -> text); interval -> text = newlabels[i - from + 1]; // Transfer of ownership. newlabels[i - from + 1] = 0; } } catch (MelderError) { Melder_throw (me, ": labels not changed."); } } void TextTier_changeLabels (I, long from, long to, const wchar_t *search, const wchar_t *replace, int use_regexp, long *nmatches, long *nstringmatches) { iam (TextTier); try { if (from == 0) { from = 1; } if (to == 0) { to = my points -> size; } if (from > to || from < 1 || to > my points -> size) { Melder_throw ("Incorrect specification of where to act."); } if (use_regexp && wcslen (search) == 0) Melder_throw ("The regex search string cannot be empty.\n" "You may search for an empty string with the expression \"^$\""); long nmarks = to - from + 1; autoNUMvector marks (1, nmarks); for (long i = from; i <= to; i++) { TextPoint point = (TextPoint) my points -> item[i]; marks[i - from + 1] = point -> mark; // Shallow copy. } autostringvector newmarks (strs_replace (marks.peek(), 1, nmarks, search, replace, 0, nmatches, nstringmatches, use_regexp), 1, nmarks); for (long i = from; i <= to; i++) { TextPoint point = (TextPoint) my points -> item[i]; Melder_free (point -> mark); point -> mark = newmarks[i - from + 1]; // Transfer of ownership. newmarks[i - from + 1] = 0; } } catch (MelderError) { Melder_throw (me, ": no labels changed."); } } void TextGrid_changeLabels (TextGrid me, int tier, long from, long to, const wchar_t *search, const wchar_t *replace, int use_regexp, long *nmatches, long *nstringmatches) { try { long ntiers = my tiers -> size; if (tier < 1 || tier > ntiers) Melder_throw ("The tier number (", tier, ") should not be " "larger than the number of tiers (", ntiers, ")."); if (use_regexp && wcslen (search) == 0) Melder_throw ("The regex search string cannot be empty.\n" "You may search for an empty string with the expression \"^$\""); Data anyTier = (Data) my tiers -> item [tier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier_changeLabels (anyTier, from, to, search, replace, use_regexp, nmatches, nstringmatches); } else { TextTier_changeLabels (anyTier, from, to, search, replace, use_regexp, nmatches, nstringmatches); } } catch (MelderError) { Melder_throw (me, ": labels not changed"); } } // Precondition: if (preserveTimes) { my xmax <= thy xmin } // Postcondition: my xmin preserved void IntervalTiers_append_inline (IntervalTier me, IntervalTier thee, bool preserveTimes) { try { double xmax_previous = my xmax, time_shift = my xmax - thy xmin; if (preserveTimes && my xmax < thy xmin) { autoTextInterval connection = TextInterval_create (my xmax, thy xmin, L""); xmax_previous = thy xmin; Collection_addItem (my intervals, connection.transfer()); } for (long iint = 1; iint <= thy intervals -> size; iint++) { autoTextInterval ti = (TextInterval) Data_copy ((Data) thy intervals -> item[iint]); if (not preserveTimes) { ti -> xmin = xmax_previous; xmax_previous = ti -> xmax += time_shift; } Collection_addItem (my intervals, ti.transfer()); } my xmax = preserveTimes ? thy xmax : xmax_previous; } catch (MelderError) { Melder_throw ("IntervalTiers not appended."); } } // Precondition: if (preserveTimes) { my xmax <= thy xmin } void TextTiers_append_inline (TextTier me, TextTier thee, bool preserveTimes) { try { for (long iint = 1; iint <= thy points -> size; iint++) { autoTextPoint tp = (TextPoint) Data_copy ((Data) thy points -> item[iint]); if (not preserveTimes) { tp -> number += my xmax - thy xmin; } Collection_addItem (my points, tp.transfer()); } my xmax = preserveTimes ? thy xmax : my xmax + (thy xmax - thy xmin); } catch (MelderError) { Melder_throw ("TextTiers not appended."); } } void TextGrids_append_inline (TextGrid me, TextGrid thee, bool preserveTimes) { try { if (my tiers -> size != thy tiers -> size) { Melder_throw ("The number of tiers must be equal."); } if (preserveTimes && thy xmin < my xmax) { Melder_throw ("The start time of the second TextGrid can't be earlier than the end time of the first one if you want to preserve times."); } // all tiers must have the same end time // last intervals must have the same end time double xmax = preserveTimes ? thy xmax : my xmax + (thy xmax - thy xmin); for (long itier = 1; itier <= my tiers -> size; itier++) { Function anyTier = (Function) my tiers -> item[itier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier ti = (IntervalTier) anyTier; IntervalTiers_append_inline (ti, (IntervalTier) thy tiers -> item[itier], preserveTimes); // make sure last interval has correct end tTime TextInterval last = (TextInterval) ti -> intervals -> item [ti -> intervals -> size]; last -> xmax = xmax; Melder_assert (last -> xmax > last -> xmin); } else { // TextTier TextTier ti = (TextTier) anyTier; TextTiers_append_inline (ti, (TextTier) thy tiers -> item [itier], preserveTimes); ti -> xmax = xmax; } } my xmax = xmax; } catch (MelderError) { Melder_throw ("TextGrids not appended."); } } TextGrid TextGrids_to_TextGrid_appendContinuous (Collection me, bool preserveTimes) { try { if (my size == 1) { return (TextGrid) Data_copy ((Data) my item[1]); } autoTextGrid thee = (TextGrid) Data_copy ((Data) my item[1]); for (long igrid = 2; igrid <= my size; igrid++) { TextGrids_append_inline (thee.peek(), (TextGrid) my item[igrid], preserveTimes); } if (not preserveTimes) Function_shiftXBy ((Function) thee.peek(), -thy xmin); return thee.transfer(); } catch (MelderError) { Melder_throw ("No aligned TextGrid created from Collection."); } } /* End of file TextGrid_extensions.cpp */ sources_5316/dwtools/LongSound_extensions.h0000644000176700017670000000242111652014401017747 0ustar paulpaul#ifndef _LongSound_extensions_h_ #define _LongSound_extensions_h_ /* LongSound_extensions.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020627 djmw 20020813 GPL header djmw 20110702 Latest modification */ #include "LongSound.h" #if defined (_WIN32) #include "winport_on.h" #include #include "winport_off.h" #endif void LongSounds_writeToStereoAudioFile16 (LongSound me, LongSound thee, int audioFileType, MelderFile file); void LongSounds_appendToExistingSoundFile (Collection me, MelderFile file); #endif /* _LongSound_extensions_h_ */ sources_5316/dwtools/Configuration_and_Procrustes.h0000644000176700017670000000236111535126147021460 0ustar paulpaul#ifndef _Configuration_and_Procrustes_h_ #define _Configuration_and_Procrustes_h_ /* Configuration_and_Procrustes.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110307 Latest modification. */ #ifndef _Configuration_h_ #include "Configuration.h" #endif #ifndef _Procrustes_h_ #include "Procrustes.h" #endif #ifdef __cplusplus extern "C" { #endif Procrustes Configurations_to_Procrustes (Configuration me, Configuration thee, int orthogonal); #ifdef __cplusplus } #endif #endif /* _Configuration_and_Procrustes_h_ */ sources_5316/dwtools/Pattern.h0000644000176700017670000000327311627244357015224 0ustar paulpaul#ifndef _Pattern_h_ #define _Pattern_h_ /* Pattern.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Matrix.h" Thing_define (Pattern, Matrix) { }; /* Attributes: xmin :index of first input node. xmax :last node index. nx :Number of inputs. dx :1. x1 :1. ymin :1. ymax :#patterns. dy :1. y1 :1. z[iy][ix] :the inputs. All elements in interval [0,1]. */ void Pattern_init (I, long ny, long nx); Pattern Pattern_create (long ny, long nx); void Pattern_normalize (I, int choice, double pmin, double pmax); /* choice == 1: z[i][j] = (z[i][j]-pmin) / (pmax-pmin); * choice == 2: z[i][j] *= 1.0 / sum(j=1,j=nx, z[i][j]-pmin) */ void Pattern_draw (I, Graphics g, long pattern, double xmin, double xmax, double ymin, double ymax, int garnish); Pattern Matrix_to_Pattern (I, int join); Matrix Pattern_to_Matrix (Pattern me); int _Pattern_checkElements (Pattern me); /* Return 1 if all elements are in interval [0,1] else 0. */ #endif /* _Pattern_h_ */ sources_5316/dwtools/Distance.h0000644000176700017670000000201311627236243015323 0ustar paulpaul#ifndef _Distance_h_ #define _Distance_h_ /* Distance.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Proximity.h" #include "Graphics.h" Thing_define (Distance, Proximity) { }; Distance Distance_create (long numberOfPoints); void Distance_drawDendogram (Distance me, Graphics g, int method); #endif /* _Distance_h_ */ sources_5316/dwtools/FilterBank.cpp0000644000176700017670000004326311725072645016164 0ustar paulpaul/* FilterBank.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010718 djmw 20020813 GPL header djmw 20030901 Added fiter function drawing and frequency scale drawing. djmw 20050731 +FilterBank_and_PCA_drawComponent djmw 20071017 Melder_error djmw 20071201 Melder_warning djmw 20080122 float -> double djmw 20110304 Thing_new */ #include "Eigen_and_Matrix.h" #include "FilterBank.h" #include "Matrix_extensions.h" #include "NUM2.h" static double scaleFrequency (double f, int scale_from, int scale_to) { double fhz = NUMundefined; if (scale_from == scale_to) { return f; } if (scale_from == FilterBank_HERTZ) { fhz = f; } else if (scale_from == FilterBank_BARK) { fhz = BARKTOHZ (f); } else if (scale_from == FilterBank_MEL) { fhz = MELTOHZ (f); } if (scale_to == FilterBank_HERTZ || fhz == NUMundefined) { return fhz; } if (scale_to == FilterBank_BARK) { f = HZTOBARK (fhz); } else if (scale_to == FilterBank_MEL) { f = HZTOMEL (fhz); } else { return NUMundefined; } return f; } static wchar_t const *GetFreqScaleText (int scale) { wchar_t const *hertz = L"Frequency (Hz)"; wchar_t const *bark = L"Frequency (Bark)"; wchar_t const *mel = L"Frequency (mel)"; wchar_t const *error = L"Frequency (undefined)"; if (scale == FilterBank_HERTZ) { return hertz; } else if (scale == FilterBank_BARK) { return bark; } else if (scale == FilterBank_MEL) { return mel; } return error; } static int checkLimits (I, int fromFreqScale, int toFreqScale, int *fromFilter, int *toFilter, double *zmin, double *zmax, int dbScale, double *ymin, double *ymax) { iam (Matrix); if (*fromFilter == 0) { *fromFilter = 1; } if (*toFilter == 0) { *toFilter = my ny; } if (*toFilter < *fromFilter) { *fromFilter = 1; *toFilter = my ny; } if (*fromFilter < 1) { *fromFilter = 1; } if (*toFilter > my ny) { *toFilter = my ny; } if (*fromFilter > *toFilter) { Melder_warning (L"Filter numbers must be in range [1, ", Melder_integer (my ny), L"]"); return 0; } if (*zmin < 0 || *zmax < 0) { Melder_warning (L"Frequencies must be positive."); return 0; } if (*zmax <= *zmin) { *zmin = scaleFrequency (my ymin, fromFreqScale, toFreqScale); *zmax = scaleFrequency (my ymax, fromFreqScale, toFreqScale); } if (*ymax <= *ymin) { *ymax = 1; *ymin = 0; if (dbScale) { *ymax = 0; *ymin = -60; } } return 1; } static double to_dB (double a, double factor, double ref_dB) { if (a <= 0) { return ref_dB; } a = factor * log10 (a); if (a < ref_dB) { a = ref_dB; } return a; } static void setDrawingLimits (double *a, long n, double amin, double amax, long *ibegin, long *iend) { *ibegin = 0; *iend = n + 1; long lower = 1; for (long i = 1; i <= n; i++) { if (a[i] == NUMundefined) { if (lower == 0) { /* high frequency part */ *iend = i; break; } *ibegin = i; continue; } lower = 0; if (a[i] < amin) { a[i] = amin; } else if (a[i] > amax) { a[i] = amax; } } (*ibegin) ++; (*iend)--; } Thing_implement (FilterBank, Matrix, 2); Thing_implement (BarkFilter, FilterBank, 2); BarkFilter BarkFilter_create (double tmin, double tmax, long nt, double dt, double t1, double fmin, double fmax, long nf, double df, long f1) { try { autoBarkFilter me = Thing_new (BarkFilter); Matrix_init (me.peek(), tmin, tmax, nt, dt, t1, fmin, fmax, nf, df, f1); return me.transfer(); } catch (MelderError) { Melder_throw ("BarkFilter not created."); } } double FilterBank_getFrequencyInHertz (I, double f, int scale_from) { (void) void_me; return scaleFrequency (f, scale_from, FilterBank_HERTZ); } double FilterBank_getFrequencyInBark (I, double f, int scale_from) { (void) void_me; return scaleFrequency (f, scale_from, FilterBank_BARK); } double FilterBank_getFrequencyInMel (I, double f, int scale_from) { (void) void_me; return scaleFrequency (f, scale_from, FilterBank_MEL); } int FilterBank_getFrequencyScale (I) { iam (FilterBank); return my v_getFrequencyScale (); } void FilterBank_drawFrequencyScales (I, Graphics g, int horizontalScale, double xmin, double xmax, int verticalScale, double ymin, double ymax, int garnish) { iam (FilterBank); int myFreqScale = FilterBank_getFrequencyScale (me); if (xmin < 0 || xmax < 0 || ymin < 0 || ymax < 0) { Melder_warning (L"Frequencies must be >= 0."); return; } if (xmin >= xmax) { double xmint = my ymin; double xmaxt = my ymax; if (ymin < ymax) { xmint = scaleFrequency (ymin, verticalScale, myFreqScale); xmaxt = scaleFrequency (ymax, verticalScale, myFreqScale); } xmin = scaleFrequency (xmint, myFreqScale, horizontalScale); xmax = scaleFrequency (xmaxt, myFreqScale, horizontalScale); } if (ymin >= ymax) { ymin = scaleFrequency (xmin, horizontalScale, verticalScale); ymax = scaleFrequency (xmax, horizontalScale, verticalScale); } long n = 2000; autoNUMvector a (1, n); Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); double df = (xmax - xmin) / (n - 1); for (long i = 1; i <= n; i++) { double f = xmin + (i - 1) * df; a[i] = scaleFrequency (f, horizontalScale, verticalScale); } long ibegin, iend; setDrawingLimits (a.peek(), n, ymin, ymax, & ibegin, & iend); if (ibegin <= iend) { double fmin = xmin + (ibegin - 1) * df; double fmax = xmax - (n - iend) * df; Graphics_function (g, a.peek(), ibegin, iend, fmin, fmax); } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_textLeft (g, 1, GetFreqScaleText (verticalScale)); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_textBottom (g, 1, GetFreqScaleText (horizontalScale)); } } void BarkFilter_drawSekeyHansonFilterFunctions (BarkFilter me, Graphics g, int toFreqScale, int fromFilter, int toFilter, double zmin, double zmax, int dbScale, double ymin, double ymax, int garnish) { if (! checkLimits (me, FilterBank_BARK, toFreqScale, & fromFilter, & toFilter, & zmin, & zmax, dbScale, & ymin, & ymax)) { return; } long n = 1000; autoNUMvector a (1, n); Graphics_setInner (g); Graphics_setWindow (g, zmin, zmax, ymin, ymax); for (long j = fromFilter; j <= toFilter; j++) { double df = (zmax - zmin) / (n - 1); double zMid = Matrix_rowToY (me, j); long ibegin, iend; for (long i = 1; i <= n; i++) { double f = zmin + (i - 1) * df; double z = scaleFrequency (f, toFreqScale, FilterBank_BARK); if (z == NUMundefined) { a[i] = NUMundefined; } else { z -= zMid + 0.215; a[i] = 7 - 7.5 * z - 17.5 * sqrt (0.196 + z * z); if (! dbScale) { a[i] = pow (10, a[i]); } } } setDrawingLimits (a.peek(), n, ymin, ymax, &ibegin, &iend); if (ibegin <= iend) { double fmin = zmin + (ibegin - 1) * df; double fmax = zmax - (n - iend) * df; Graphics_function (g, a.peek(), ibegin, iend, fmin, fmax); } } Graphics_unsetInner (g); if (garnish) { double distance = dbScale ? 10 : 1; wchar_t const *ytext = dbScale ? L"Amplitude (dB)" : L"Amplitude"; Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeftEvery (g, 1, distance, 1, 1, 0); Graphics_textLeft (g, 1, ytext); Graphics_textBottom (g, 1, GetFreqScaleText (toFreqScale)); } } Thing_implement (MelFilter, FilterBank, 2); MelFilter MelFilter_create (double tmin, double tmax, long nt, double dt, double t1, double fmin, double fmax, long nf, double df, double f1) { try { autoMelFilter me = Thing_new (MelFilter); Matrix_init (me.peek(), tmin, tmax, nt, dt, t1, fmin, fmax, nf, df, f1); return me.transfer(); } catch (MelderError) { Melder_throw ("MelFilter not created."); } } /* void FilterBank_drawFilters (I, Graphics g, long fromf, long tof, double xmin, double xmax, int xlinear, double ymin, double ymax, int ydb, double (*tolinf)(double f), double (*tononlin) (double f), double (*filteramp)(double f0, double b, double f)) { iam (Matrix); }*/ void FilterBank_drawTimeSlice (I, Graphics g, double t, double fmin, double fmax, double min, double max, const wchar_t *xlabel, int garnish) { iam (Matrix); Matrix_drawSliceY (me, g, t, fmin, fmax, min, max); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); if (xlabel) { Graphics_textBottom (g, 0, xlabel); } } } void MelFilter_drawFilterFunctions (MelFilter me, Graphics g, int toFreqScale, int fromFilter, int toFilter, double zmin, double zmax, int dbScale, double ymin, double ymax, int garnish) { if (! checkLimits (me, FilterBank_MEL, toFreqScale, & fromFilter, & toFilter, & zmin, & zmax, dbScale, & ymin, & ymax)) { return; } long n = 1000; autoNUMvector a (1, n); Graphics_setInner (g); Graphics_setWindow (g, zmin, zmax, ymin, ymax); for (long j = fromFilter; j <= toFilter; j++) { double df = (zmax - zmin) / (n - 1); double fc_mel = my y1 + (j - 1) * my dy; double fc_hz = MELTOHZ (fc_mel); double fl_hz = MELTOHZ (fc_mel - my dy); double fh_hz = MELTOHZ (fc_mel + my dy); long ibegin, iend; for (long i = 1; i <= n; i++) { // Filterfunction: triangular on a linear frequency scale AND a linear amplitude scale. double f = zmin + (i - 1) * df; double z = scaleFrequency (f, toFreqScale, FilterBank_HERTZ); if (z == NUMundefined) { a[i] = NUMundefined; } else { a[i] = NUMtriangularfilter_amplitude (fl_hz, fc_hz, fh_hz, z); if (dbScale) { a[i] = to_dB (a[i], 10, ymin); } } } setDrawingLimits (a.peek(), n, ymin, ymax, &ibegin, &iend); if (ibegin <= iend) { double fmin = zmin + (ibegin - 1) * df; double fmax = zmax - (n - iend) * df; Graphics_function (g, a.peek(), ibegin, iend, fmin, fmax); } } Graphics_unsetInner (g); if (garnish) { double distance = dbScale ? 10 : 1; wchar_t const *ytext = dbScale ? L"Amplitude (dB)" : L"Amplitude"; Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeftEvery (g, 1, distance, 1, 1, 0); Graphics_textLeft (g, 1, ytext); Graphics_textBottom (g, 1, GetFreqScaleText (toFreqScale)); } } /* void MelFilter_drawFilters (MelFilter me, Graphics g, long from, long to, double fmin, double fmax, double ymin, double ymax, int dbscale, int garnish) { long i; double df = my dy; if (fmin >= fmax) { fmin = my ymin; fmax = my ymax; } if (from >= to) { from = 1; to = my ny; } Graphics_setWindow (g, my ymin, my ymax, 0, 1); Graphics_setInner (g); for (i = from; i <= to; i++) { double fc = my y1 + (i - 1) * df; double fc_hz = MELTOHZ (fc); double fl_hz = MELTOHZ (fc - df); double fh_hz = MELTOHZ (fc + df); *//* Draw triangle *//* Graphics_line (g, fl_hz, 0, fc_hz, 1); Graphics_line (g, fc_hz, 1, fh_hz, 0); } Graphics_unsetInner (g); } */ Matrix FilterBank_to_Matrix (I) { iam (Matrix); try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Matrix."); } } BarkFilter Matrix_to_BarkFilter (I) { iam (Matrix); try { autoBarkFilter thee = BarkFilter_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to BarkFilter."); } } MelFilter Matrix_to_MelFilter (I) { iam (Matrix); try { autoMelFilter thee = MelFilter_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to MelFilter."); } } Thing_implement (FormantFilter, FilterBank, 2); FormantFilter FormantFilter_create (double tmin, double tmax, long nt, double dt, double t1, double fmin, double fmax, long nf, double df, double f1) { try { autoFormantFilter me = Thing_new (FormantFilter); Matrix_init (me.peek(), tmin, tmax, nt, dt, t1, fmin, fmax, nf, df, f1); return me.transfer(); } catch (MelderError) { Melder_throw ("FormantFilter not created."); } } void FormantFilter_drawFilterFunctions (FormantFilter me, Graphics g, double bandwidth, int toFreqScale, int fromFilter, int toFilter, double zmin, double zmax, int dbScale, double ymin, double ymax, int garnish) { if (! checkLimits (me, FilterBank_HERTZ, toFreqScale, & fromFilter, & toFilter, & zmin, & zmax, dbScale, & ymin, & ymax)) { return; } if (bandwidth <= 0) { Melder_warning (L"Bandwidth must be greater than zero."); } long n = 1000; autoNUMvectora (1, n); Graphics_setInner (g); Graphics_setWindow (g, zmin, zmax, ymin, ymax); for (long j = fromFilter; j <= toFilter; j++) { double df = (zmax - zmin) / (n - 1); double fc = my y1 + (j - 1) * my dy; long ibegin, iend; for (long i = 1; i <= n; i++) { double f = zmin + (i - 1) * df; double z = scaleFrequency (f, toFreqScale, FilterBank_HERTZ); if (z == NUMundefined) { a[i] = NUMundefined; } else { a[i] = NUMformantfilter_amplitude (fc, bandwidth, z); if (dbScale) { a[i] = to_dB (a[i], 10, ymin); } } } setDrawingLimits (a.peek(), n, ymin, ymax, &ibegin, &iend); if (ibegin <= iend) { double fmin = zmin + (ibegin - 1) * df; double fmax = zmax - (n - iend) * df; Graphics_function (g, a.peek(), ibegin, iend, fmin, fmax); } } Graphics_unsetInner (g); if (garnish) { double distance = dbScale ? 10 : 1; wchar_t const *ytext = dbScale ? L"Amplitude (dB)" : L"Amplitude"; Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeftEvery (g, 1, distance, 1, 1, 0); Graphics_textLeft (g, 1, ytext); Graphics_textBottom (g, 1, GetFreqScaleText (toFreqScale)); } } FormantFilter Matrix_to_FormantFilter (I) { iam (Matrix); try { autoFormantFilter thee = FormantFilter_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to FormantFilter."); } } Spectrum FormantFilter_to_Spectrum_slice (FormantFilter me, double t) { try { double sqrtref = sqrt (FilterBank_DBREF); double factor2 = 2 * 10 * FilterBank_DBFAC; autoSpectrum thee = Spectrum_create (my ymax, my ny); thy xmin = my ymin; thy xmax = my ymax; thy x1 = my y1; thy dx = my dy; /* Frequency step. */ long frame = Sampled_xToIndex (me, t); if (frame < 1) { frame = 1; } if (frame > my nx) { frame = my nx; } for (long i = 1; i <= my ny; i++) { /* power = ref * 10 ^ (value / 10) sqrt(power) = sqrt(ref) * 10 ^ (value / (2*10)) */ thy z[1][i] = sqrtref * pow (10, my z[i][frame] / factor2); thy z[2][i] = 0.0; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Spectral slice not created."); } } Intensity FilterBank_to_Intensity (I) { iam (Matrix); try { autoIntensity thee = Intensity_create (my xmin, my xmax, my nx, my dx, my x1); double db_ref = 10 * log10 (FilterBank_DBREF); for (long j = 1; j <= my nx; j++) { double p = 0; for (long i = 1; i <= my ny; i++) { p += FilterBank_DBREF * exp (NUMln10 * my z[i][j] / 10); } thy z[1][j] = 10 * log10 (p) - db_ref; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Intensity not created."); } } void FilterBank_equalizeIntensities (I, double intensity_db) { iam (Matrix); for (long j = 1; j <= my nx; j++) { double p = 0; for (long i = 1; i <= my ny; i++) { p += FilterBank_DBREF * exp (NUMln10 * my z[i][j] / 10); } double delta_db = intensity_db - 10 * log10 (p / FilterBank_DBREF); for (long i = 1; i <= my ny; i++) { my z[i][j] += delta_db; } } } void FilterBank_and_PCA_drawComponent (I, PCA thee, Graphics g, long component, double dblevel, double frequencyOffset, double scale, double tmin, double tmax, double fmin, double fmax) { iam (FilterBank); if (component < 1 || component > thy numberOfEigenvalues) { Melder_throw ("Component too large."); } // Scale Intensity autoFilterBank fcopy = (FilterBank) Data_copy (me); FilterBank_equalizeIntensities (fcopy.peek(), dblevel); autoMatrix him = Eigen_and_Matrix_project (thee, fcopy.peek(), component); for (long j = 1; j <= my nx; j++) { fcopy -> z[component][j] = frequencyOffset + scale * fcopy -> z[component][j]; } Matrix_drawRows (fcopy.peek(), g, tmin, tmax, component - 0.5, component + 0.5, fmin, fmax); } /* End of file Filterbank.cpp */ sources_5316/dwtools/Configuration_def.h0000644000176700017670000000206211627173226017223 0ustar paulpaul/* Configuration_def.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Configuration oo_DEFINE_CLASS (Configuration, TableOfReal) oo_LONG (metric) oo_DOUBLE_VECTOR (w, numberOfColumns) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (Configuration) #undef ooSTRUCT /* End of file Configuration_def.h */ sources_5316/dwtools/Intensity_extensions.cpp0000644000176700017670000001100711731606002020362 0ustar paulpaul/* Intensity_extensions.cpp * * Copyright (C) 2007-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20061204 Initial version djmw 20070129 Extra argument for Vector_getAndX djmw 20071201 Melder_warning djmw 20090818 Intensity_to_TextGrid_detectSilences: mark last interval also if sounding */ #include "Intensity_extensions.h" #include "TextGrid_extensions.h" static void IntervalTier_addBoundaryUnsorted (IntervalTier me, long iinterval, double time, const wchar_t *leftLabel) { if (time <= my xmin || time >= my xmax) { Melder_throw ("Time is outside interval."); } // Find interval to split if (iinterval <= 0) { iinterval = IntervalTier_timeToLowIndex (me, time); } // Modify end time of left label TextInterval ti = (TextInterval) my intervals -> item[iinterval]; ti -> xmax = time; TextInterval_setText (ti, leftLabel); autoTextInterval ti_new = TextInterval_create (time, my xmax, L""); Sorted_addItem_unsorted (my intervals, ti_new.transfer()); } TextGrid Intensity_to_TextGrid_detectSilences (Intensity me, double silenceThreshold_dB, double minSilenceDuration, double minSoundingDuration, const wchar_t *silenceLabel, const wchar_t *soundingLabel) { try { double duration = my xmax - my xmin, time; if (silenceThreshold_dB >= 0) { Melder_throw ("The silence threshold w.r.t. the maximum intensity should be a negative number."); } autoTextGrid thee = TextGrid_create (my xmin, my xmax, L"silences", L""); IntervalTier it = (IntervalTier) thy tiers -> item[1]; TextInterval_setText ( (TextInterval) it -> intervals -> item[1], soundingLabel); if (minSilenceDuration > duration) { return thee.transfer(); } double intensity_max_db, intensity_min_db, xOfMaximum, xOfMinimum; Vector_getMaximumAndX (me, 0, 0, 1, NUM_PEAK_INTERPOLATE_PARABOLIC, &intensity_max_db, &xOfMaximum); Vector_getMinimumAndX (me, 0, 0, 1, NUM_PEAK_INTERPOLATE_PARABOLIC, &intensity_min_db, &xOfMinimum); double intensity_dbRange = intensity_max_db - intensity_min_db; if (intensity_dbRange < 10) Melder_warning (L"The loudest and softest part in your sound only differ by ", Melder_double (intensity_dbRange), L" dB."); double intensityThreshold = intensity_max_db - fabs (silenceThreshold_dB); if (minSilenceDuration > duration || intensityThreshold < intensity_min_db) { return thee.transfer(); } int inSilenceInterval = my z[1][1] < intensityThreshold; long iinterval = 1; const wchar_t *label; for (long i = 2; i <= my nx; i++) { int addBoundary = 0; if (my z[1][i] < intensityThreshold) { if (!inSilenceInterval) { // Start of silence addBoundary = 1; inSilenceInterval = 1; label = soundingLabel; } } else { if (inSilenceInterval) { // End of silence addBoundary = 1; inSilenceInterval = 0; label = silenceLabel; } } if (addBoundary) { time = my x1 + (i - 1) * my dx; IntervalTier_addBoundaryUnsorted (it, iinterval, time, label); iinterval++; } } // (re)label last interval */ label = inSilenceInterval ? silenceLabel : soundingLabel; TextInterval_setText ( (TextInterval) it -> intervals -> item[iinterval], label); Sorted_sort (it -> intervals); // First remove short non-silence intervals in-between silence intervals and // then remove the remaining short silence intervals. // This works much better than first removing short silence intervals and // then short non-silence intervals. IntervalTier_cutIntervals_minimumDuration (it, soundingLabel, minSoundingDuration); IntervalTier_cutIntervalsOnLabelMatch (it, silenceLabel); IntervalTier_cutIntervals_minimumDuration (it, silenceLabel, minSilenceDuration); IntervalTier_cutIntervalsOnLabelMatch (it, soundingLabel); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": TextGrid not created."); } } /* End of file Intensity_extensions.cpp */sources_5316/dwtools/Configuration_AffineTransform.cpp0000644000176700017670000001265311725071311022102 0ustar paulpaul/* Configuration_AffineTransform.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020315 GPL header */ #include "Configuration_AffineTransform.h" #include "Configuration_and_Procrustes.h" #include "Procrustes.h" #include "SVD.h" #undef your #define your ((AffineTransform_Table) thy methods) -> static void do_steps45 (double **w, double **t, double **c, long n, double *f) { // Step 4 || 10: If W'T has negative diagonal elements, multiply corresponding columns in T by -1. for (long i = 1; i <= n; i++) { double d = 0; for (long k = 1; k <= n; k++) { d += w[k][i] * t[k][i]; } if (d < 0) { for (long k = 1; k <= n; k++) { t[k][i] = -t[k][i]; } } } // Step 5 & 11: f = tr W'T (Diag (T'CT))^-1/2 *f = 0; for (long i = 1; i <= n; i++) { double d = 0, tct = 0; for (long k = 1; k <= n; k++) { d += w[k][i] * t[k][i]; for (long j = 1; j <= n; j++) { tct += t[k][i] * c[k][j] * t[j][i]; } } if (tct > 0) { *f += d / sqrt (tct); } } } static void NUMmaximizeCongruence (double **b, double **a, long nr, long nc, double **t, long maximumNumberOfIterations, double tolerance) { long numberOfIterations = 0; Melder_assert (nr > 0 && nc > 0); Melder_assert (t); if (nc == 1) { t[1][1] = 1; return; } autoNUMmatrix c (1, nc, 1, nc); autoNUMmatrix w (1, nc, 1, nc); autoNUMmatrix u (1, nc, 1, nc); autoNUMvector evec (1, nc); autoSVD svd = SVD_create (nc, nc); // Steps 1 & 2: C = A'A and W = A'B double checkc = 0, checkw = 0; for (long i = 1; i <= nc; i++) { for (long j = 1; j <= nc; j++) { for (long k = 1; k <= nr; k++) { c[i][j] += a[k][i] * a[k][j]; w[i][j] += a[k][i] * b[k][j]; } checkc += c[i][j]; checkw += w[i][j]; } } if (checkc == 0 || checkw == 0) { Melder_throw ("NUMmaximizeCongruence: we cannot rotate a zero matrix."); } // Scale W by (diag(B'B))^-1/2 for (long j = 1; j <= nc; j++) { double scale = 0; for (long k = 1; k <= nr; k++) { scale += b[k][j] * b[k][j]; } if (scale > 0) { scale = 1 / sqrt (scale); } for (long i = 1; i <= nc; i++) { w[i][j] *= scale; } } // Step 3: largest eigenvalue of C evec[1] = 1; double rho, f, f_old; NUMdominantEigenvector (c.peek(), nc, evec.peek(), &rho, 1.0e-6); do_steps45 (w.peek(), t, c.peek(), nc, &f); do { for (long j = 1; j <= nc; j++) { // Step 7.a double p = 0; for (long k = 1; k <= nc; k++) { for (long i = 1; i <= nc; i++) { p += t[k][j] * c[k][i] * t[i][j]; } } // Step 7.b double q = 0; for (long k = 1; k <= nc; k++) { q += w[k][j] * t[k][j]; } // Step 7.c if (q == 0) { for (long i = 1; i <= nc; i++) { u[i][j] = 0; } } else { double ww = 0; for (long k = 1; k <= nc; k++) { ww += w[k][j] * w[k][j]; } for (long i = 1; i <= nc; i++) { double ct = 0; for (long k = 1; k <= nc; k++) { ct += c[i][k] * t[k][j]; } u[i][j] = (q * (ct - rho * t[i][j]) / p - 2 * ww * t[i][j] / q - w[i][j]) / sqrt (p); } } } // Step 8 SVD_svd_d (svd.peek(), u.peek()); // Step 9 for (long i = 1; i <= nc; i++) { for (long j = 1; j <= nc; j++) { t[i][j] = 0; for (long k = 1; k <= nc; k++) { t[i][j] -= svd -> u[i][k] * svd -> v[j][k]; } } } numberOfIterations++; f_old = f; // Steps 10 & 11 equal steps 4 & 5 do_steps45 (w.peek(), t, c.peek(), nc, &f); } while (fabs (f_old - f) / f_old > tolerance && numberOfIterations < maximumNumberOfIterations); } AffineTransform Configurations_to_AffineTransform_congruence (Configuration me, Configuration thee, long maximumNumberOfIterations, double tolerance) { try { // Use Procrustes transform to obtain starting configuration. // (We only need the transformation matrix T.) autoProcrustes p = Configurations_to_Procrustes (me, thee, 0); NUMmaximizeCongruence (my data, thy data, my numberOfRows, p -> n, p -> r, maximumNumberOfIterations, tolerance); autoAffineTransform at = AffineTransform_create (p -> n); NUMmatrix_copyElements (p -> r, at -> r, 1, p -> n, 1, p -> n); return at.transfer(); } catch (MelderError) { Melder_throw (me, ": no congruence transformation created."); } } Configuration Configuration_and_AffineTransform_to_Configuration (Configuration me, thou) { try { thouart (AffineTransform); if (my numberOfColumns != thy n) { Melder_throw ("Dimensions do not agree."); } autoConfiguration him = (Configuration) Data_copy (me); // Apply transformation YT thy v_transform (my data, my numberOfRows, his data); return him.transfer(); } catch (MelderError) { Melder_throw ("Configuration not created."); } } /* End of file Configuration_AffineTransform.cpp */ sources_5316/dwtools/Proximity.h0000644000176700017670000000177511627250712015610 0ustar paulpaul#ifndef _Proximity_h_ #define _Proximity_h_ /* Proximity.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110306 Latest modification. */ #include "TableOfReal.h" Thing_define (Proximity, TableOfReal) { }; void Proximity_init (I, long numberOfPoints); #endif /* _Proximity_h_ */ sources_5316/dwtools/praat_HMM_init.cpp0000664000176700017670000011114311674622653016774 0ustar paulpaul/* praat_HMM_init.cpp * * Copyright (C) 2010-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20101003 */ #include "praat.h" #include "GaussianMixture.h" #include "HMM.h" #include "Strings_extensions.h" #include "TableOfReal.h" #undef iam #define iam iam_LOOP //#undef praat_HIDDEN //#define praat_HIDDEN 0 #define GaussianMixture_OPTION_MENU_CRITERIA \ OPTIONMENU (L"Criterion based on", 1) \ OPTION (L"Likelihood") \ OPTION (L"Message length") \ OPTION (L"Bayes information") \ OPTION (L"Akaike information") \ OPTION (L"Akaike corrected") \ OPTION (L"Complete-data ML") Correlation GaussianMixture_and_TableOfReal_to_Correlation2 (GaussianMixture me, thou); DIRECT (GaussianMixture_help) Melder_help (L"GaussianMixture"); END FORM (GaussianMixture_drawConcentrationEllipses, L"GaussianMixture: Draw concentration ellipses", L"GaussianMixture: Draw concentration ellipses...") POSITIVE (L"Number of sigmas", L"1.0") BOOLEAN (L"Principal component plane", 1) INTEGER (L"X-dimension", L"1") INTEGER (L"Y-dimension", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (GaussianMixture); GaussianMixture_drawConcentrationEllipses (me, GRAPHICS, GET_REAL (L"Number of sigmas"), 0, 0, GET_INTEGER (L"Principal component plane"), GET_INTEGER (L"X-dimension"), GET_INTEGER (L"Y-dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); } END FORM (GaussianMixture_and_PCA_drawConcentrationEllipses, L"GaussianMixture & PCA: Draw concentration ellipses", L"GaussianMixture & PCA: Draw concentration ellipses...") POSITIVE (L"Number of sigmas", L"1.0") INTEGER (L"X-dimension", L"1") INTEGER (L"Y-dimension", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") INTEGER (L"Label size", L"12") BOOLEAN (L"Garnish", 1) OK DO GaussianMixture me = FIRST (GaussianMixture); PCA pca = FIRST (PCA); GaussianMixture_and_PCA_drawConcentrationEllipses (me, pca, GRAPHICS, GET_REAL (L"Number of sigmas"), 0, NULL, GET_INTEGER (L"X-dimension"), GET_INTEGER (L"Y-dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Label size"), GET_INTEGER (L"Garnish")); END FORM (GaussianMixture_drawMarginalPdf, L"GaussianMixture: Draw marginal pdf", L"GaussianMixture: Draw marginal pdf...") INTEGER (L"X-dimension", L"1") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") NATURAL (L"Number of points", L"500") INTEGER (L"Number of bins", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (GaussianMixture); GaussianMixture_drawMarginalPdf (me, GRAPHICS, GET_INTEGER (L"X-dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Number of points"), GET_INTEGER (L"Number of bins"), GET_INTEGER (L"Garnish")); } END DIRECT (GaussianMixture_getNumberOfComponents) LOOP { iam (GaussianMixture); Melder_information (Melder_integer (my numberOfComponents), L" (= number of components)"); } END DIRECT (GaussianMixture_getDimensionOfComponent) LOOP { iam (GaussianMixture); Melder_information (Melder_integer (my dimension), L" (= dimension of component)"); } END FORM (GaussianMixture_getProbabilityAtPosition, L"GaussianMixture: Get probability at position", 0) SENTENCE (L"Position", L"100.0 300.0") OK DO const wchar_t *position = GET_STRING (L"Position"); LOOP { iam (GaussianMixture); double p = GaussianMixture_getProbabilityAtPosition_string (me, position); Melder_information (Melder_double (p), L" (= probability at position ", position); } END FORM (GaussianMixture_splitComponent, L"GaussianMixture: Split component", L"GaussianMixture: Split component...") NATURAL (L"Component", L"1") OK DO LOOP { iam (GaussianMixture); GaussianMixture_splitComponent (me, GET_INTEGER (L"Component")); } END FORM (GaussianMixture_and_PCA_drawMarginalPdf, L"GaussianMixture & PCA: Draw pdf function", L"GaussianMixture: Draw marginal pdf...") INTEGER (L"X-dimension", L"1") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") NATURAL (L"Number of points", L"500") INTEGER (L"Number of bins", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; GaussianMixture me = FIRST (GaussianMixture); PCA pca = FIRST (PCA); GaussianMixture_and_PCA_drawMarginalPdf (me, pca, GRAPHICS, GET_INTEGER (L"X-dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Number of points"), GET_INTEGER (L"Number of bins"), GET_INTEGER (L"Garnish")); END FORM (GaussianMixture_and_PCA_to_Matrix_density, L"GaussianMixture & PCA: To Matrix density", L"GaussianMixture & PCA: To Matrix (density)...") INTEGER (L"X-dimension", L"1") INTEGER (L"Y-dimension", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") NATURAL (L"Number of columns", L"100") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") NATURAL (L"Number of rows", L"100") OK DO GaussianMixture me = FIRST (GaussianMixture); PCA pca = FIRST (PCA); praat_new (GaussianMixture_and_PCA_to_Matrix_density (me, pca, GET_INTEGER (L"X-dimension"), GET_INTEGER (L"Y-dimension"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_INTEGER (L"Number of columns"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Number of rows")), my name, L"_", pca->name); END FORM (GaussianMixture_extractComponent, L"GaussianMixture: Extract component", 0) NATURAL (L"Component", L"1") OK DO long component = GET_INTEGER (L"Component"); LOOP { iam (GaussianMixture); Covariance cov = GaussianMixture_extractComponent (me, component); praat_new (cov, my name, L"_", cov->name); } END DIRECT (GaussianMixture_extractCentroids) LOOP { iam (GaussianMixture); praat_new (GaussianMixture_extractCentroids (me), my name); } END DIRECT (GaussianMixture_extractMixingProbabilities) LOOP { iam (GaussianMixture); praat_new (GaussianMixture_extractMixingProbabilities (me), my name); } END DIRECT (GaussianMixture_to_PCA) LOOP { iam (GaussianMixture); praat_new (GaussianMixture_to_PCA (me), my name); } END FORM (GaussianMixture_to_TableOfReal_randomSampling, L"GaussianMixture: To TableOfReal (random sampling)", L"GaussianMixture: To TableOfReal (random sampling)...") NATURAL (L"Number of data points", L"100") OK DO long numberOfpoints = GET_INTEGER (L"Number of data points"); LOOP { iam (GaussianMixture); praat_new (GaussianMixture_to_TableOfReal_randomSampling (me, numberOfpoints), my name); } END DIRECT (GaussianMixture_to_Covariance_between) LOOP { iam (GaussianMixture); praat_new (GaussianMixture_to_Covariance_between (me), my name, L"_b"); } END DIRECT (GaussianMixture_to_Covariance_within) LOOP { iam (GaussianMixture); praat_new (GaussianMixture_to_Covariance_within (me), my name, L"_w"); } END DIRECT (GaussianMixture_to_Covariance_total) LOOP { iam (GaussianMixture); praat_new (GaussianMixture_to_Covariance_total (me), my name, L"_t"); } END FORM (GaussianMixture_and_TableOfReal_getLikelihoodValue, L"GaussianMixture & TableOfReal: Get likelihood value", L"GaussianMixture & TableOfReal: Get likelihood value...") GaussianMixture_OPTION_MENU_CRITERIA OK DO GaussianMixture me = FIRST (GaussianMixture); TableOfReal thee = FIRST (TableOfReal); int criterion = GET_INTEGER (L"Criterion based on") - 1; const wchar_t *criterionText = GaussianMixture_criterionText (criterion); double lnpdn = GaussianMixture_and_TableOfReal_getLikelihoodValue (me, thee, criterion); Melder_information (Melder_double (lnpdn / thy numberOfRows), L" (= ", criterionText, L", n = ", Melder_integer (thy numberOfRows), L")"); END DIRECT (HMM_help) Melder_help (L"HMM"); END FORM (HMM_create, L"Create HMM", L"") WORD (L"Name", L"hmm") BOOLEAN (L"Left to right model", 0) NATURAL (L"Number of states", L"3") NATURAL (L"Number of observations", L"3") OK DO praat_new (HMM_create (GET_INTEGER (L"Left to right model"), GET_INTEGER (L"Number of states"), GET_INTEGER (L"Number of observations")), GET_STRING (L"Name")); END FORM (HMM_createSimple, L"HMM: Create simple", L"HMM: Create simple HMM...") WORD (L"Name", L"weather") BOOLEAN (L"Left to right model", 0) SENTENCE (L"States", L"Rainy Sunny") SENTENCE (L"Observations", L"Walk Shop Clean") OK DO praat_new (HMM_createSimple (GET_INTEGER (L"Left to right model"), GET_STRING (L"States"), GET_STRING (L"Observations")), GET_STRING (L"Name")); END FORM (HMM_createContinuousModel, L"HMM: Create continuous model", 0) WORD (L"Name", L"cm") BOOLEAN (L"Left to right model", 0) NATURAL (L"Number of states", L"3") NATURAL (L"Number of symbols", L"10") LABEL (L"", L"For the Gaussian mixtures:") NATURAL (L"Number of components", L"3") NATURAL (L"Dimension of component", L"39") OPTIONMENU (L"Covariance matrices are", 1) OPTION (L"Complete") OPTION (L"Diagonal") OK DO long componentStorage = GET_INTEGER (L"Covariance matrices are") - 1; long dimension = GET_INTEGER (L"Dimension of component"); REQUIRE (componentStorage >= 0 && componentStorage <= dimension, L"Not a valid covariance matrix type") praat_new (HMM_createContinuousModel (GET_INTEGER (L"Left to right model"), GET_INTEGER (L"Number of states"), GET_INTEGER (L"Number of symbols"), GET_INTEGER (L"Number of components"), dimension, componentStorage), GET_STRING (L"Name")); END FORM (HMM_ObservationSequence_to_HMM, L"HMM_ObservationSequence: To HMM", 0) LABEL (L"", L"(0 states gives a non-hidden model) ") INTEGER (L"Number of states", L"2") BOOLEAN (L"Left to right model", 0) OK DO long numberOfStates = GET_INTEGER (L"Number of states"); LOOP { iam (HMM_ObservationSequence); praat_new (HMM_createFromHMM_ObservationSequence (me, numberOfStates, GET_INTEGER (L"Left to right model")), my name, L"_", Melder_integer (numberOfStates)); } END FORM (HMM_draw, L"HMM: Draw", 0) BOOLEAN (L"Garnish", 0) OK DO autoPraatPicture picture; LOOP { iam (HMM); HMM_draw (me, GRAPHICS, GET_INTEGER (L"Garnish")); } END FORM (HMM_and_HMM_StateSequence_drawTrellis, L"HMM & Strings: Draw trellis", 0) BOOLEAN (L"Connect", 1); BOOLEAN (L"Garnish", 1); OK DO autoPraatPicture picture; HMM me = FIRST (HMM); HMM_StateSequence hmm_ss = FIRST (HMM_StateSequence); HMM_and_HMM_StateSequence_drawTrellis (me, hmm_ss, GRAPHICS, GET_INTEGER (L"Connect"), GET_INTEGER (L"Garnish")); END DIRECT (HMM_drawForwardProbabilitiesIllustration) autoPraatPicture picture; HMM_drawForwardProbabilitiesIllustration (GRAPHICS, true); END DIRECT (HMM_drawBackwardProbabilitiesIllustration) autoPraatPicture picture; HMM_drawBackwardProbabilitiesIllustration (GRAPHICS, true); END DIRECT (HMM_drawForwardAndBackwardProbabilitiesIllustration) autoPraatPicture picture; HMM_drawForwardAndBackwardProbabilitiesIllustration (GRAPHICS, true); END FORM (HMM_getTransitionProbability, L"HMM: Get transition probability", L"HMM: Get transition probability...") NATURAL (L"From state number", L"1") NATURAL (L"To state number", L"1") OK DO LOOP { iam (HMM); long s1 = GET_INTEGER (L"From state number"), s2 = GET_INTEGER (L"To state number"); REQUIRE (s1 <= my numberOfStates && s2 <= my numberOfStates, L"State number(s) too high.") Melder_information (Melder_double (my transitionProbs[s1][s2]), L" : [ ", Melder_integer (s1), L", ", Melder_integer (s2), L" ]"); } END FORM (HMM_getEmissionProbability, L"HMM: Get emission probability", L"HMM: Get emission probability...") NATURAL (L"From state number", L"1") NATURAL (L"To symbol number", L"1") OK DO LOOP { iam (HMM); long s1 = GET_INTEGER (L"From state number"), s2 = GET_INTEGER (L"To symbol number"); REQUIRE (s1 <= my numberOfStates, L"State number too high.") REQUIRE (s2 <= my numberOfObservationSymbols, L"Symbol number too high.") Melder_information (Melder_double (my emissionProbs[s1][s2]), L" : [ ", Melder_integer (s1), L", ", Melder_integer (s2), L" ]"); } END FORM (HMM_getStartProbability, L"HMM: Get start probability", L"HMM: Get start probability...") NATURAL (L"State number", L"1") OK DO LOOP { iam (HMM); long s1 = GET_INTEGER (L"State number"); REQUIRE (s1 <= my numberOfStates, L"State number too high.") Melder_information (Melder_double (my transitionProbs[0][s1]), L" : [ ", Melder_integer (s1), L" ]"); } END FORM (HMM_getProbabilityAtTimeBeingInState, L"HMM: Get probability of being in state at time", L"HMM: Get p (time, state)...") NATURAL (L"Time index", L"10") NATURAL (L"State number", L"1") OK DO long istate = GET_INTEGER (L"State number"); long itime = GET_INTEGER (L"Time index"); LOOP { iam (HMM); double lnp = HMM_getProbabilityAtTimeBeingInState (me, itime, istate); Melder_information (Melder_double (lnp), L" (=ln(p), p = ", Melder_naturalLogarithm (lnp), L") Being in state ", Melder_integer (istate), L" at time ", Melder_integer (itime)); } END FORM (HMM_getProbabilityAtTimeBeingInStateEmittingSymbol, L"HMM: get probability being at time in state emitting symbol", L"HMM: Get p (time, state, symbol)...") NATURAL (L"Time index", L"10") NATURAL (L"State number", L"1") NATURAL (L"Symbol number", L"1") OK DO long istate = GET_INTEGER (L"State number"); long itime = GET_INTEGER (L"Time index"); long isymbol = GET_INTEGER (L"Symbol number"); LOOP { iam (HMM); double lnp = HMM_getProbabilityAtTimeBeingInStateEmittingSymbol (me, itime, istate, isymbol); Melder_information (Melder_double (lnp), L" (=ln(p), p = ", Melder_naturalLogarithm (lnp), L") Being in state ", Melder_integer (istate), L" emitting symbol ", Melder_integer (isymbol), L" at time ", Melder_integer (itime)); } END FORM (HMM_getProbabilityOfStayingInState, L"HMM: Get probability of staying in state", L"HMM: Get probability staying in state...") NATURAL (L"State number", L"1") NATURAL (L"Number of times", L"2") OK DO LOOP { iam (HMM); Melder_informationReal (HMM_getProbabilityOfStayingInState (me, GET_INTEGER (L"State number"), GET_INTEGER (L"Number of times")), 0); } END FORM (HMM_getExpectedValueOfDurationInState, L"HMM: Get expected value of duration in state", L"HMM: Get expected duration in state...") NATURAL (L"State number", L"1") OK DO LOOP { iam (HMM); Melder_informationReal (HMM_getExpectedValueOfDurationInState (me, GET_INTEGER (L"State number")), L" time units"); } END FORM (HMM_getSymbolLabel, L"HMM: Get symbol label", 0) NATURAL (L"Symbol number", L"1") OK DO long is = GET_INTEGER (L"Symbol number"); LOOP { iam (HMM); REQUIRE (is <= my numberOfObservationSymbols, L"Symbol number too high.") HMM_Observation s = (HMM_Observation) my observationSymbols -> item[is]; Melder_information (s -> label); } END FORM (HMM_getStateLabel, L"HMM: Get state label", 0) NATURAL (L"State number", L"1") OK DO long is = GET_INTEGER (L"State number"); LOOP { iam (HMM); REQUIRE (is <= my numberOfStates, L"State number too high.") HMM_State s = (HMM_State) my states -> item[is]; Melder_information (s -> label); } END FORM (HMM_and_HMM_getCrossEntropy, L"HMM & HMM: Get cross-entropy...", L"HMM & HMM: Get cross-entropy...") NATURAL (L"Observation length", L"2000") BOOLEAN (L"Symmetric", 1) OK DO long n = GET_INTEGER (L"Observation length"); int sym = GET_INTEGER (L"Symmetric"); HMM m1 = 0, m2 = 0; LOOP { iam (HMM); (m1 ? m2 : m1) = me; } Melder_assert (m1 && m2); double ce = HMM_and_HMM_getCrossEntropy (m1, m2, n, sym); Melder_information (Melder_double (ce), L" (=", (sym ? L"symmetric " : L""), L" cross-entropy between models for observation length = ", Melder_integer (n), L")"); END DIRECT (HMM_and_HMM_and_HMM_ObservationSequence_getCrossEntropy) HMM m1 = 0, m2 = 0; HMM_ObservationSequence hmm_os = 0; LOOP { if (CLASS == classHMM_ObservationSequence) { hmm_os = (HMM_ObservationSequence) OBJECT; } else { (m1 ? m2 : m1) = (HMM) OBJECT; } } Melder_assert (m1 && m2 && hmm_os); double ce = HMM_and_HMM_and_HMM_ObservationSequence_getCrossEntropy (m1, m2, hmm_os); Melder_information (Melder_double (ce), L" (=symmetric cross-entropy between models)"); END FORM (HMM_to_HMM_ObservationSequence, L"HMM: To HMM_ObservationSequence (generate observations)", L"HMM: To HMM_ObservationSequence...") INTEGER (L"Start state", L"0") NATURAL (L"Number of observations", L"20") OK DO LOOP { iam (HMM); praat_new (HMM_to_HMM_ObservationSequence (me, GET_INTEGER (L"Start state"), GET_INTEGER (L"Number of observations")), my name); } END DIRECT (HMM_and_HMM_StateSequence_getProbability) HMM me = FIRST (HMM); HMM_StateSequence hmm_ss = FIRST (HMM_StateSequence); double lnp = HMM_and_HMM_StateSequence_getProbability (me, hmm_ss); Melder_information (Melder_double (lnp), L" (=ln(p), p = ", Melder_naturalLogarithm (lnp), L")"); END DIRECT (HMM_and_HMM_ObservationSequence_getProbability) HMM me = FIRST (HMM); HMM_ObservationSequence hmm_os = FIRST (HMM_ObservationSequence); double lnp = HMM_and_HMM_ObservationSequence_getProbability (me, hmm_os); Melder_information (Melder_double (lnp), L" (=ln(p), p = ", Melder_naturalLogarithm (lnp), L")"); END DIRECT (HMM_and_HMM_ObservationSequence_getCrossEntropy) HMM me = FIRST (HMM); HMM_ObservationSequence hmm_os = FIRST (HMM_ObservationSequence); double ce = HMM_and_HMM_ObservationSequence_getCrossEntropy (me, hmm_os); Melder_information (Melder_double (ce), L" (= cross-entropy)"); END DIRECT (HMM_and_HMM_ObservationSequence_getPerplexity) HMM me = FIRST (HMM); HMM_ObservationSequence hmm_os = FIRST (HMM_ObservationSequence); double py = HMM_and_HMM_ObservationSequence_getPerplexity (me, hmm_os); Melder_information (Melder_double (py), L" (= perplexity)"); END DIRECT (HMM_and_HMM_ObservationSequence_to_HMM_StateSequence) HMM me = FIRST (HMM); HMM_ObservationSequence thee = FIRST (HMM_ObservationSequence); praat_new (HMM_and_HMM_ObservationSequence_to_HMM_StateSequence (me, thee), my name, L"_", thy name, L"_states"); END FORM (HMM_and_HMM_ObservationSequence_learn, L"HMM & HMM_ObservationSequence: Learn", L"HMM & HMM_ObservationSequences: Learn...") POSITIVE (L"Relative precision in log(p)", L"0.001") REAL (L"Minimum probability", L"0.00000000001") OK DO double minProb = GET_REAL (L"Minimum probability"); REQUIRE (minProb >= 0 && minProb < 1, L"A probabilty must be >= 0 and < 1!") autoHMM_ObservationSequences hmm_oss = HMM_ObservationSequences_create (); HMM hmm = 0; Collection_dontOwnItems (hmm_oss.peek()); LOOP { iam (Data); if (CLASS == classHMM_ObservationSequence) { Collection_addItem (hmm_oss.peek(), me); } else { hmm = (HMM) me; } } HMM_and_HMM_ObservationSequences_learn (hmm, hmm_oss.peek(), GET_REAL (L"Relative precision in log"), minProb); END FORM (HMM_setTransitionProbabilities, L"HMM: Set transition probabilities", L"HMM: Set transition probabilities...") NATURAL (L"State number", L"1") SENTENCE (L"Probabilities", L"0.1 0.9") OK DO LOOP { iam (HMM); HMM_setTransitionProbabilities (me, GET_INTEGER (L"State number"), GET_STRING (L"Probabilities")); } END FORM (HMM_setEmissionProbabilities, L"HMM: Set emission probabilities", L"HMM: Set emission probabilities...") NATURAL (L"State number", L"1") SENTENCE (L"Probabilities", L"0.1 0.7 0.2") OK DO LOOP { iam (HMM); HMM_setEmissionProbabilities (me, GET_INTEGER (L"State number"), GET_STRING (L"Probabilities")); } END FORM (HMM_setStartProbabilities, L"HMM: Set start probabilities", L"HMM: Set start probabilities...") SENTENCE (L"Probabilities", L"0.1 0.9") OK DO LOOP { iam (HMM); HMM_setStartProbabilities (me, GET_STRING (L"Probabilities")); } END DIRECT (HMM_extractTransitionProbabilities) LOOP { iam (HMM); praat_new (HMM_extractTransitionProbabilities (me), my name, L"_t"); } END DIRECT (HMM_extractEmissionProbabilities) LOOP { iam (HMM); praat_new (HMM_extractEmissionProbabilities (me), my name, L"_e"); } END FORM (HMM_ObservationSequence_to_TableOfReal, L"HMM_ObservationSequence: To TableOfReal ", L"HMM_ObservationSequence: To TableOfReal (bigrams)...") BOOLEAN (L"As probabilities", 1) OK DO LOOP { iam (HMM_ObservationSequence); praat_new (HMM_ObservationSequence_to_TableOfReal_transitions (me, GET_INTEGER (L"As probabilities")), my name); } END FORM (HMM_and_HMM_ObservationSequence_to_TableOfReal, L"HMM & HMM_ObservationSequence: To TableOfReal", L"HMM & HMM_ObservationSequence: To TableOfReal (bigrams)...") BOOLEAN (L"As probabilities", 1) OK DO HMM me = FIRST (HMM); HMM_ObservationSequence hmm_os = FIRST (HMM_ObservationSequence); praat_new (HMM_and_HMM_ObservationSequence_to_TableOfReal_transitions (me, hmm_os, GET_INTEGER (L"As probabilities")), hmm_os -> name, L"_m"); END FORM (HMM_and_HMM_StateSequence_to_TableOfReal, L"HMM & HMM_StateSequence: To TableOfReal", 0) BOOLEAN (L"As probabilities", 1) OK DO HMM me = FIRST (HMM); HMM_StateSequence hmm_ss = FIRST (HMM_StateSequence); praat_new (HMM_and_HMM_StateSequence_to_TableOfReal_transitions (me, hmm_ss, GET_INTEGER (L"As probabilities")), Thing_getName (hmm_ss), L"_m"); END FORM (HMM_StateSequence_to_TableOfReal, L"HMM_StateSequence: To TableOfReal", 0) BOOLEAN (L"As probabilities", 1) OK DO LOOP { iam (HMM_StateSequence); praat_new (Strings_to_TableOfReal_transitions ( (Strings) me, GET_INTEGER (L"As probabilities")), my name); } END DIRECT (HMM_ObservationSequence_to_Strings) LOOP { iam (HMM_ObservationSequence); praat_new (HMM_ObservationSequence_to_Strings (me), my name); } END DIRECT (Strings_to_HMM_ObservationSequence) LOOP { iam (Strings); praat_new (Strings_to_HMM_ObservationSequence (me), my name); } END DIRECT (HMM_StateSequence_to_Strings) LOOP { iam (HMM_StateSequence); praat_new (HMM_StateSequence_to_Strings (me), my name); } END FORM (TableOfReal_to_GaussianMixture_fromRowlabels, L"TableOfReal: To GaussianMixture from row labels", L"TableOfReal: To GaussianMixture (row labels)...") OPTIONMENU (L"Covariance matrices are", 1) OPTION (L"Complete") OPTION (L"Diagonal") OK DO long storage = GET_INTEGER (L"Covariance matrices are") - 1; LOOP { iam (TableOfReal); praat_new (TableOfReal_to_GaussianMixture_fromRowLabels (me, storage), my name); } END FORM (TableOfReal_to_GaussianMixture, L"TableOfReal: To GaussianMixture (no labels)", L"TableOfReal: To GaussianMixture...") NATURAL (L"Number of components", L"2") POSITIVE (L"Tolerance of minimizer", L"0.001") INTEGER (L"Maximum number of iterations", L"200") REAL (L"Stability coefficient lambda", L"0.001") OPTIONMENU (L"Covariance matrices are", 1) OPTION (L"Complete") OPTION (L"Diagonal") GaussianMixture_OPTION_MENU_CRITERIA OK DO int criterion = GET_INTEGER (L"Criterion based on") - 1; double lambda = GET_REAL (L"Stability coefficient lambda"); REQUIRE (lambda >= 0 && lambda < 1, L"Lambda must be in interval [0,1).") long storage = GET_INTEGER (L"Covariance matrices are") - 1; LOOP { iam (TableOfReal); praat_new (TableOfReal_to_GaussianMixture (me, GET_INTEGER (L"Number of components"), GET_REAL (L"Tolerance of minimizer"), GET_INTEGER (L"Maximum number of iterations"), lambda, storage, criterion), my name); } END FORM (GaussianMixture_and_TableOfReal_improveLikelihood, L"GaussianMixture & TableOfReal: Improve likelihood", L"GaussianMixture & TableOfReal: Improve likelihood...") POSITIVE (L"Tolerance of minimizer", L"0.001") NATURAL (L"Maximum number of iterations", L"200") REAL (L"Stability coefficient lambda", L"0.001") GaussianMixture_OPTION_MENU_CRITERIA OK DO long criterion = GET_INTEGER (L"Criterion based on") - 1; double lambda = GET_REAL (L"Stability coefficient lambda"); GaussianMixture me = FIRST (GaussianMixture); TableOfReal thee = FIRST (TableOfReal); REQUIRE (lambda >= 0 && lambda < 1, L"Lambda must be in interval [0,1).") REQUIRE (thy numberOfColumns == my dimension, L"The number of columns and the dimension of the model do not agree."); REQUIRE (my numberOfComponents < thy numberOfRows / 2, L"Not enough data points.") GaussianMixture_and_TableOfReal_improveLikelihood (me, thee, GET_REAL (L"Tolerance of minimizer"), GET_INTEGER (L"Maximum number of iterations"), lambda, criterion); END FORM (GaussianMixture_and_TableOfReal_to_GaussianMixture_CEMM, L"GaussianMixture & TableOfReal: To GaussianMixture (CEMM)", L"GaussianMixture & TableOfReal: To GaussianMixture (CEMM)...") INTEGER (L"Minimum number of components", L"1") POSITIVE (L"Tolerance of minimizer", L"0.001") NATURAL (L"Maximum number of iterations", L"200") REAL (L"Stability coefficient lambda", L"0.001") GaussianMixture_OPTION_MENU_CRITERIA OK DO double lambda = GET_REAL (L"Stability coefficient lambda"); int criterion = GET_INTEGER (L"Criterion based on") - 1; GaussianMixture me = FIRST (GaussianMixture); TableOfReal thee = FIRST (TableOfReal); REQUIRE (lambda >= 0 && lambda < 1, L"Lambda must be in interval [0,1).") REQUIRE (thy numberOfColumns == my dimension, L"The number of columns and the dimension of the model do not agree."); REQUIRE (my numberOfComponents < thy numberOfRows / 2, L"Not enough data points.") praat_new (GaussianMixture_and_TableOfReal_to_GaussianMixture_CEMM (me, thee, GET_INTEGER (L"Minimum number of components"), GET_REAL (L"Tolerance of minimizer"), GET_INTEGER (L"Maximum number of iterations"), lambda, criterion), my name); END DIRECT (GaussianMixture_and_TableOfReal_to_ClassificationTable) GaussianMixture me = FIRST (GaussianMixture); TableOfReal thee = FIRST (TableOfReal); praat_new (GaussianMixture_and_TableOfReal_to_ClassificationTable (me, thee), my name, L"_", thy name); END DIRECT (GaussianMixture_and_TableOfReal_to_Correlation) GaussianMixture me = FIRST (GaussianMixture); TableOfReal thee = FIRST (TableOfReal); praat_new (GaussianMixture_and_TableOfReal_to_Correlation (me, thee), my name, L"_", thy name); END FORM (GaussianMixture_and_TableOfReal_to_TableOfReal_BHEPNormalityTests, L"GaussianMixture & TableOfReal: To TableOfReal BHEP normality tests", L"GaussianMixture & TableOfReal: To TableOfReal (BHEP normality tests)...") REAL (L"Smoothing parameter", L"1.41") OK DO GaussianMixture me = FIRST (GaussianMixture); TableOfReal thee = FIRST (TableOfReal); double h = GET_REAL (L"Smoothing parameter"); praat_new (GaussianMixture_and_TableOfReal_to_TableOfReal_BHEPNormalityTests (me, thee, h), my name, L"_", thy name); END void praat_HMM_init (); void praat_HMM_init () { Thing_recognizeClassesByName (classHMM, classHMM_State, classHMM_Observation, classHMM_ObservationSequence, classHMM_StateSequence, classGaussianMixture, NULL); praat_addMenuCommand (L"Objects", L"New", L"Markov models", 0, praat_HIDDEN, 0); praat_addMenuCommand (L"Objects", L"New", L"Create HMM...", 0, praat_HIDDEN + praat_DEPTH_1, DO_HMM_create); praat_addMenuCommand (L"Objects", L"New", L"Create simple HMM...", 0, praat_HIDDEN + praat_DEPTH_1, DO_HMM_createSimple); praat_addMenuCommand (L"Objects", L"New", L"Create continuous HMM...", 0, praat_HIDDEN + praat_DEPTH_1, DO_HMM_createContinuousModel); praat_addMenuCommand (L"Objects", L"New", L"--drawings--", 0, praat_HIDDEN + praat_DEPTH_1, 0); praat_addMenuCommand (L"Objects", L"New", L"Draw forward probabilities illustration", 0, praat_HIDDEN + praat_DEPTH_1, DO_HMM_drawForwardProbabilitiesIllustration); praat_addMenuCommand (L"Objects", L"New", L"Draw backward probabilities illustration", 0, praat_HIDDEN + praat_DEPTH_1, DO_HMM_drawBackwardProbabilitiesIllustration); praat_addMenuCommand (L"Objects", L"New", L"Draw forward and backward probabilities illustration", 0, praat_HIDDEN + praat_DEPTH_1, DO_HMM_drawForwardAndBackwardProbabilitiesIllustration); praat_addAction1 (classGaussianMixture, 0, L"GaussianMixture help", 0, 0, DO_GaussianMixture_help); praat_addAction1 (classGaussianMixture, 0, L"Draw concentration ellipses...", 0, 0, DO_GaussianMixture_drawConcentrationEllipses); praat_addAction1 (classGaussianMixture, 0, L"Draw marginal pdf...", 0, 0, DO_GaussianMixture_drawMarginalPdf); praat_addAction1 (classGaussianMixture, 0, L"Query -", 0, 0, 0); praat_addAction1 (classGaussianMixture, 1, L"Get number of components", 0, 1, DO_GaussianMixture_getNumberOfComponents); praat_addAction1 (classGaussianMixture, 1, L"Get dimension of component", 0, 1, DO_GaussianMixture_getDimensionOfComponent); praat_addAction1 (classGaussianMixture, 1, L"Get probability at position...", 0, 1, DO_GaussianMixture_getProbabilityAtPosition); praat_addAction1 (classGaussianMixture, 0, L"Modify -", 0, 0, 0); praat_addAction1 (classGaussianMixture, 1, L"Split component...", 0, 1, DO_GaussianMixture_splitComponent); praat_addAction1 (classGaussianMixture, 0, L"Extract -", 0, 0, 0); praat_addAction1 (classGaussianMixture, 0, L"Extract mixing probabilities", 0, 1, DO_GaussianMixture_extractMixingProbabilities); praat_addAction1 (classGaussianMixture, 0, L"Extract component...", 0, 1, DO_GaussianMixture_extractComponent); praat_addAction1 (classGaussianMixture, 0, L"Extract centroids", 0, 1, DO_GaussianMixture_extractCentroids); praat_addAction1 (classGaussianMixture, 0, L"To Covariance (between)", 0, 0, DO_GaussianMixture_to_Covariance_between); praat_addAction1 (classGaussianMixture, 0, L"To Covariance (within)", 0, 0, DO_GaussianMixture_to_Covariance_within); praat_addAction1 (classGaussianMixture, 0, L"To Covariance (total)", 0, 0, DO_GaussianMixture_to_Covariance_total); praat_addAction1 (classGaussianMixture, 0, L"To PCA", 0, 0, DO_GaussianMixture_to_PCA); praat_addAction1 (classGaussianMixture, 0, L"To TableOfReal (random sampling)...", 0, 0, DO_GaussianMixture_to_TableOfReal_randomSampling); praat_addAction2 (classGaussianMixture, 1, classTableOfReal, 1, L"Get likelihood value...", 0, 0, DO_GaussianMixture_and_TableOfReal_getLikelihoodValue); praat_addAction2 (classGaussianMixture, 1, classTableOfReal, 1, L"Improve likelihood...", 0, 0, DO_GaussianMixture_and_TableOfReal_improveLikelihood); praat_addAction2 (classGaussianMixture, 1, classTableOfReal, 1, L"To GaussianMixture (CEMM)...", 0, 0, DO_GaussianMixture_and_TableOfReal_to_GaussianMixture_CEMM); praat_addAction2 (classGaussianMixture, 1, classTableOfReal, 1, L"To ClassificationTable", 0, 0, DO_GaussianMixture_and_TableOfReal_to_ClassificationTable); praat_addAction2 (classGaussianMixture, 1, classTableOfReal, 1, L"To Correlation", 0, 0, DO_GaussianMixture_and_TableOfReal_to_Correlation); praat_addAction2 (classGaussianMixture, 1, classTableOfReal, 1, L"To TableOfReal (BHEP normality tests)...", 0, 0, DO_GaussianMixture_and_TableOfReal_to_TableOfReal_BHEPNormalityTests); praat_addAction2 (classGaussianMixture, 1, classPCA, 1, L"Draw concentration ellipses...", 0, 0, DO_GaussianMixture_and_PCA_drawConcentrationEllipses); praat_addAction2 (classGaussianMixture, 1, classPCA, 1, L"Draw marginal pdf...", 0, 0, DO_GaussianMixture_and_PCA_drawMarginalPdf); praat_addAction2 (classGaussianMixture, 1, classPCA, 1, L"To Matrix (density)...", 0, 0, DO_GaussianMixture_and_PCA_to_Matrix_density); praat_addAction1 (classHMM, 0, L"HMM help ", 0, 0, DO_HMM_help); praat_addAction1 (classHMM, 0, L"Draw...", 0, 0, DO_HMM_draw); praat_addAction1 (classHMM, 0, L"Query -", 0, 0, 0); praat_addAction1 (classHMM, 1, L"Get transition probability...", 0, 1, DO_HMM_getTransitionProbability); praat_addAction1 (classHMM, 1, L"Get emission probability...", 0, 1, DO_HMM_getEmissionProbability); praat_addAction1 (classHMM, 1, L"Get start probability...", 0, 1, DO_HMM_getStartProbability); praat_addAction1 (classHMM, 1, L"Get p (time, state)...", 0, 1, DO_HMM_getProbabilityAtTimeBeingInState); praat_addAction1 (classHMM, 1, L"Get p (time, state, symbol)...", 0, 1, DO_HMM_getProbabilityAtTimeBeingInStateEmittingSymbol); praat_addAction1 (classHMM, 1, L"Get probability staying in state...", 0, 1, DO_HMM_getProbabilityOfStayingInState); praat_addAction1 (classHMM, 1, L"Get expected duration in state...", 0, 1, DO_HMM_getExpectedValueOfDurationInState); praat_addAction1 (classHMM, 1, L"---- states / symbols -----", 0, 1, 0); praat_addAction1 (classHMM, 1, L"Get state label...", 0, 1, DO_HMM_getStateLabel); praat_addAction1 (classHMM, 1, L"Get symbol label...", 0, 1, DO_HMM_getSymbolLabel); praat_addAction1 (classHMM, 0, L"--- multiple HMMs ----", 0, 1, 0); praat_addAction1 (classHMM, 2, L"Get cross-entropy...", 0, 1, DO_HMM_and_HMM_getCrossEntropy); praat_addAction1 (classHMM, 0, L"Modify -", 0, 0, 0); praat_addAction1 (classHMM, 1, L"Set transition probabilities...", 0, 1, DO_HMM_setTransitionProbabilities); praat_addAction1 (classHMM, 1, L"Set emission probabilities...", 0, 1, DO_HMM_setEmissionProbabilities); praat_addAction1 (classHMM, 1, L"Set start probabilities...", 0, 1, DO_HMM_setStartProbabilities); praat_addAction1 (classHMM, 0, L"Extract -", 0, 0, 0); praat_addAction1 (classHMM, 0, L"Extract transition probabilities", 0, 1, DO_HMM_extractTransitionProbabilities); praat_addAction1 (classHMM, 0, L"Extract emission probabilities", 0, 1, DO_HMM_extractEmissionProbabilities); praat_addAction1 (classHMM, 0, L"To HMM_ObservationSequence...", 0, 0, DO_HMM_to_HMM_ObservationSequence); praat_addAction2 (classHMM, 1, classHMM_StateSequence, 1, L"Draw trellis...", 0, 0, DO_HMM_and_HMM_StateSequence_drawTrellis); praat_addAction2 (classHMM, 1, classHMM_StateSequence, 1, L"Get probability", 0, 0, DO_HMM_and_HMM_StateSequence_getProbability); praat_addAction2 (classHMM, 1, classHMM_StateSequence, 1, L"To TableOfReal (bigrams)...", 0, 0, DO_HMM_and_HMM_StateSequence_to_TableOfReal); praat_addAction2 (classHMM, 1, classHMM_ObservationSequence, 1, L"Get probability", 0, 0, DO_HMM_and_HMM_ObservationSequence_getProbability); praat_addAction2 (classHMM, 1, classHMM_ObservationSequence, 1, L"Get cross-entropy", 0, 0, DO_HMM_and_HMM_ObservationSequence_getCrossEntropy); praat_addAction2 (classHMM, 1, classHMM_ObservationSequence, 1, L"Get perplexity", 0, 0, DO_HMM_and_HMM_ObservationSequence_getPerplexity); praat_addAction2 (classHMM, 1, classHMM_ObservationSequence, 1, L"To HMM_StateSequence", 0, 0, DO_HMM_and_HMM_ObservationSequence_to_HMM_StateSequence); praat_addAction2 (classHMM, 2, classHMM_ObservationSequence, 1, L"Get cross-entropy", 0, 0, DO_HMM_and_HMM_and_HMM_ObservationSequence_getCrossEntropy); praat_addAction2 (classHMM, 1, classHMM_ObservationSequence, 1, L"To TableOfReal (bigrams)...", 0, 0, DO_HMM_and_HMM_ObservationSequence_to_TableOfReal); praat_addAction2 (classHMM, 1, classHMM_ObservationSequence, 0, L"Learn...", 0, 0, DO_HMM_and_HMM_ObservationSequence_learn); praat_addAction1 (classHMM_ObservationSequence, 0, L"To TableOfReal (bigrams)...", 0, 0, DO_HMM_ObservationSequence_to_TableOfReal); praat_addAction1 (classHMM_ObservationSequence, 0, L"To Strings", 0, 0, DO_HMM_ObservationSequence_to_Strings); praat_addAction1 (classHMM_StateSequence, 0, L"To TableOfReal (bigrams)...", 0, 0, DO_HMM_StateSequence_to_TableOfReal); praat_addAction1 (classHMM_StateSequence, 0, L"To Strings", 0, 0, DO_HMM_StateSequence_to_Strings); praat_addAction1 (classHMM_ObservationSequence, 0, L"To HMM...", 0, 1, DO_HMM_ObservationSequence_to_HMM); praat_addAction1 (classStrings, 0, L"To HMM_ObservationSequence", 0, praat_HIDDEN, DO_Strings_to_HMM_ObservationSequence); praat_addAction1 (classTableOfReal, 0, L"To GaussianMixture (row labels)...", L"To Covariance", praat_HIDDEN + praat_DEPTH_1, DO_TableOfReal_to_GaussianMixture_fromRowlabels); praat_addAction1 (classTableOfReal, 0, L"To GaussianMixture...", L"To Covariance", praat_HIDDEN + praat_DEPTH_1, DO_TableOfReal_to_GaussianMixture); INCLUDE_MANPAGES (manual_HMM) } /* End of file praat_HMM_init.cpp */ sources_5316/dwtools/Categories.cpp0000644000176700017670000001055711675363356016236 0ustar paulpaul/* Categories.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020315 GPL header djmw 20110304 Thing_new */ #include "Categories.h" void structCategories :: v_readText (MelderReadText a_text) { long l_size = texgeti4 (a_text); if (l_size == 0) { OrderedOfString_init (this, 1); } else if (l_size < 0) { Melder_throw ("Size cannot be negative."); } else { OrderedOfString_init (this, l_size); // David, in je vorige versie kon dit tweemaal aangeroepen worden (en in dat geval crashend): Ja dat was een bug, Ok nu } for (long i = 1; i <= l_size; i ++) { autoSimpleString itemi = Thing_new (SimpleString); itemi -> v_readText (a_text); therror Ordered_addItemPos (this, itemi.transfer(), i); } } void structCategories :: v_writeText (MelderFile file) { texputi4 (file, size, L"size", 0, 0, 0, 0, 0); for (long i = 1; i <= size; i++) { SimpleString data = (SimpleString) item [i]; texputintro (file, L"item" " [", Melder_integer (i), L"]:", 0, 0, 0); data -> structSimpleString :: v_writeText (file); texexdent (file); } } Thing_implement (Categories, OrderedOfString, 0); void Categories_init (Categories me, long size) { OrderedOfString_init (me, size); } Categories Categories_create () { try { autoCategories me = Thing_new (Categories); Categories_init (me.peek(), 10); return me.transfer(); } catch (MelderError) { Melder_throw ("Categories not created."); } } Categories Categories_sequentialNumbers (long n) { try { autoCategories me = Thing_new (Categories); OrderedOfString_init (me.peek(), 5); OrderedOfString_sequentialNumbers (me.peek(), n); return me.transfer(); } catch (MelderError) { Melder_throw ("Sequential number Categories not created."); } } Categories Categories_selectUniqueItems (Categories me, int sorted) { try { autoOrderedOfString s = OrderedOfString_selectUniqueItems (me, sorted); autoCategories thee = OrderedOfString_to_Categories (s.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no unique categories created."); } } void Categories_drawItem (Categories me, Graphics g, long position, double xWC, double yWC) { if (position < 1 || position > my size) { return; } SimpleString_draw ( (SimpleString) my item[position], g, xWC, yWC); } Categories OrderedOfString_to_Categories (I) { iam (OrderedOfString); try { autoCategories thee = Categories_create(); for (long i = 1; i <= my size; i++) { autoSimpleString item = Data_copy ( (SimpleString) my item [i]); Collection_addItem (thee.peek(), item.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Categories."); } } long Categories_getSize (Categories me) { return my size; } /* TableOfReal_Rowlabels_to_Categories ??? */ Categories TableOfReal_to_CategoriesRow (I) { iam (TableOfReal); try { autoCategories thee = Categories_create (); for (long i = 1; i <= my numberOfRows; i++) { if (my rowLabels[i]) { autoSimpleString s = SimpleString_create (my rowLabels[i]); Collection_addItem (thee.peek(), s.transfer()); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": row labels not converted to Categories."); } } Categories TableOfReal_to_CategoriesColumn (I) { iam (TableOfReal); try { autoCategories thee = Categories_create (); for (long i = 1; i <= my numberOfColumns; i++) { if (my columnLabels[i]) { autoSimpleString s = SimpleString_create (my columnLabels[i]); Collection_addItem (thee.peek(), s.transfer()); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": columnlabels not converted to Categories."); } } /* End of file Categories.cpp */ sources_5316/dwtools/manual_dwtools.cpp0000664000176700017670000073501511757127674017210 0ustar paulpaul/* manual_dwtools.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020313 GPL djmw 20101101 Latest modification */ #include "ManPagesM.h" #include "Sound_extensions.h" #include "TableOfReal_extensions.h" #ifndef _Configuration_h_ #include "Configuration.h" #endif #ifndef _Discriminant_h_ #include "Discriminant.h" #endif static TableOfReal getStandardizedLogFrequencyPolsData (int includeLevels) { autoTableOfReal me = TableOfReal_createFromPolsData_50males (includeLevels); for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= 3; j++) { my data[i][j] = log10 (my data[i][j]); } } TableOfReal_standardizeColumns (me.peek()); TableOfReal_setColumnLabel (me.peek(), 1, L"standardized log (%F__1_)"); TableOfReal_setColumnLabel (me.peek(), 2, L"standardized log (%F__2_)"); TableOfReal_setColumnLabel (me.peek(), 3, L"standardized log (%F__3_)"); if (includeLevels) { TableOfReal_setColumnLabel (me.peek(), 4, L"standardized %L__1_"); TableOfReal_setColumnLabel (me.peek(), 5, L"standardized %L__1_"); TableOfReal_setColumnLabel (me.peek(), 6, L"standardized %L__3_"); } return me.transfer(); } static void drawPolsF1F2_log (Graphics g) { autoTableOfReal me = getStandardizedLogFrequencyPolsData (0); Graphics_setWindow (g, -2.9, 2.9, -2.9, 2.9); TableOfReal_drawScatterPlot (me.peek(), g, 1, 2, 0, 0, -2.9, 2.9, -2.9, 2.9, 10, 1, L"+", 1); } static void drawPolsF1F2ConcentrationEllipses (Graphics g) { autoTableOfReal me = getStandardizedLogFrequencyPolsData (0); autoDiscriminant d = TableOfReal_to_Discriminant (me.peek()); Discriminant_drawConcentrationEllipses (d.peek(), g, 1, 0, NULL, 0, 1, 2, -2.9, 2.9, -2.9, 2.9, 12, 1); } static void drawPolsDiscriminantConfiguration (Graphics g) { autoTableOfReal me = getStandardizedLogFrequencyPolsData (0); autoDiscriminant d = TableOfReal_to_Discriminant (me.peek()); autoConfiguration c = Discriminant_and_TableOfReal_to_Configuration (d.peek(), me.peek(), 2); Configuration_draw (c.peek(), g, 1, 2, -2.9, 2.9, -2.9, 2.9, 0, 1, L"", 1); } static void drawBoxPlot (Graphics g) { double q25 = 25, q50 = 50, q75 = 60, mean = 45; double hspread = q75 - q25, r = 0.05, w = 0.2; double lowerInnerFence = q25 - 1.5 * hspread; double upperInnerFence = q75 + 1.5 * hspread; double upperOuterFence = q75 + 3.0 * hspread; double lowerWhisker = lowerInnerFence + 0.1 * hspread; double upperWhisker = upperInnerFence - 0.5 * hspread; double ymin = lowerWhisker - 0.1 * hspread, ymax = q75 + 4 * hspread; double x = 0, dx = 0.01, xar = x + 0.7, xtl = xar + dx; double xal1 = x + r + dx, xal2 = x + w + r, y; Graphics_setWindow (g, -1, 2, ymin, ymax); Graphics_setInner (g); Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_line (g, x - r, lowerWhisker, x + r, lowerWhisker); Graphics_line (g, x, lowerWhisker, x, q25); Graphics_line (g, x - w, q25, x + w, q25); Graphics_line (g, x - w, q50, x + w, q50); Graphics_line (g, x - w, q75, x + w, q75); Graphics_line (g, x - w, q25, x - w, q75); Graphics_line (g, x + w, q25, x + w, q75); Graphics_line (g, x, q75, x, upperWhisker); Graphics_line (g, x - r, upperWhisker, x + r, upperWhisker); y = q75 + 2.5 * hspread; Graphics_text (g, x, y, L"*"); Graphics_arrow (g, xar, y, xal1, y); Graphics_text (g, xtl, y, L"outlier > %%upperInnerFence%"); y = q75 + 3.5 * hspread; Graphics_text (g, x, y, L"o"); Graphics_arrow (g, xar, y, xal1, y); Graphics_text (g, xtl, y, L"outlier > %%upperOuterFence%"); y = upperOuterFence; Graphics_setLineType (g, Graphics_DOTTED); Graphics_line (g, -xtl, y, xtl, y); Graphics_text (g, xtl, y, L"%%upperOuterFence%"); y = upperInnerFence; Graphics_line (g, -xtl, y, xtl, y); Graphics_text (g, xtl, y, L"%%upperInnerFence%"); Graphics_line (g, x - w, mean, x + w, mean); Graphics_setLineType (g, Graphics_DRAWN); y = upperWhisker; Graphics_arrow (g, xar, y, xal2, y); Graphics_text (g, xtl, y, L"%%upperWhisker%"); y = lowerWhisker; Graphics_arrow (g, xar, y, xal2, y); Graphics_text (g, xtl, y, L"%%lowerWhisker%"); y = q75; Graphics_arrow (g, xar, y, xal2, y); Graphics_text (g, xtl, y, L"%%q75%"); y = q25; Graphics_arrow (g, xar, y, xal2, y); Graphics_text (g, xtl, y, L"%%q25%"); y = q50; Graphics_arrow (g, xar, y, xal2, y); Graphics_text (g, xtl, y, L"%%q50%"); y = mean; Graphics_arrow (g, xar, y, xal2, y); Graphics_text (g, xtl, y, L"%%mean%"); Graphics_unsetInner (g); } static void drawPartionedMatrix (Graphics g) { double min = 0, max = 10, x1, x2, y1, y2; Graphics_setWindow (g, min, max, min, max); x1 = 0; x2 = max; y1 = y2 = 7; Graphics_setLineType (g, Graphics_DOTTED); Graphics_line (g, x1, y1, x2, y2); x1 = x2 = 3; y1 = 0; y2 = max; Graphics_line (g, x1, y1, x2, y2); Graphics_setLineType (g, Graphics_DRAWN); x1 = 1.5; y1 = 7+3/2; Graphics_setFontSize (g, 14); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x1, y1, L"##S__yy_#"); x1 = 3 + 7/2; Graphics_text (g, x1, y1, L"##S__yx_#"); y1 = 7/2; Graphics_text (g, x1, y1, L"##S__xx_#"); x1 = 1.5; Graphics_text (g, x1, y1, L"##S__xy_#"); } void manual_dwtools_init (ManPages me); void manual_dwtools_init (ManPages me) { MAN_BEGIN (L"AffineTransform", L"djmw", 20010927) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An affine transform is a combination of a linear transformation #%A " "and a translation #%t that transforms a vector #%x to a new vector #%y " "in the following way:") FORMULA (L"#%y = #%A x + #%t") MAN_END MAN_BEGIN (L"AffineTransform: Invert", L"djmw", 20011008) INTRO (L"Get the inverse of the selected @AffineTransform object.") NORMAL (L"The inverse from") FORMULA (L"#%y = #%A x + #%t") NORMAL (L"is:") FORMULA (L"#%x = #%A^^-1^ - #%A^^-1^#%t.") MAN_END MAN_BEGIN (L"Band filtering in the frequency domain", L"djmw", 20010404) INTRO (L"We describe how band filtering in the frequency domain is performed.") NORMAL (L"We start with a @Sound and end with a filter bank representation of " "this sound. We assume a standard analysis context: a sound divided into " "frames according to a certain %%window length% and %%time step%. We will " "simulate a filterbank with %N filters.") NORMAL (L"The algorithm for each sound frame proceeds in the following way:") LIST_ITEM (L"1. Apply a Gaussian window to the sound frame.") LIST_ITEM (L"2. Convert the windowed frame into a @Spectrum object.") LIST_ITEM (L"3. Convert the spectral amplitudes to %energy values by squaring " "the real and imaginary parts and multiplying by %df, the frequency " "distance between two successive frequency points in the spectrum. " "Since the Spectrum object only contains positive frequencies, " "we have to multiply all energy values, except the first and the last " "frequency, by another factor of 2 to compensate for negative frequencies.") LIST_ITEM (L"4. For each of the %N filters in the filter bank: determine the " "inner product of its filter function with the energies as determined in " "the previous step. The result of each inner product is the energy in the " "corresponding filter.") LIST_ITEM (L"5. Convert the energies in each filter to power by dividing by " "the %%window length%.") LIST_ITEM (L"6. Correct the power, due to the windowing of the frame, by dividing " "by the integral of the %squared windowing function.") LIST_ITEM (L"7. Convert all power values to %dB's according to 10 * log10 " "(%power / 4 10^^-10^).") MAN_END MAN_BEGIN (L"Bonferroni correction", L"djmw", 20011107) NORMAL (L"In general, if we have %k independent significance tests " "at the %\\al level, the probability %p that we will get no significant " "differences in all these tests is simply the product of the individual " "probabilities: (1 - %\\al)^^%k^. " "For example, with %\\al = 0.05 and %k = 10 we get %p = 0.95^^10^ = 0.60. " "This means, however, we now have a 40\\% chance that one of these 10 " "tests will turn out significant, despite each individual test only being " "at the 5\\% level. " "In order to guarantee that the overall significance test is still at the " "%\\al level, we have to adapt the significance level %\\al\\'p of the " "individual test. ") NORMAL (L"This results in the following relation between the overall and the " "individual significance level:") FORMULA (L"(1 - %\\al\\'p)^^%k%^ = 1 - %\\al.") NORMAL (L"This equation can easily be solved for %\\al\\'p:") FORMULA (L"%\\al\\'p = 1 - (1-%\\al)^^1/%k^,") NORMAL (L"which for small %\\al reduces to:") FORMULA (L"%\\al\\'p = %\\al / %k") NORMAL (L"This is a very simple recipe: If you want an overall significance " "level %\\al and you perform %k individual tests, simply divide %\\al " "by %k to obtain the significance level for the individual tests.") MAN_END MAN_BEGIN (L"box plot", L"djmw", 20111010) INTRO (L"A box plot provides a simple graphical summary of data. These plots " "originate from the work of @@Tukey (1977)@.") ENTRY (L"Definitions") NORMAL (L"The following figure shows an annotated box plot.") PICTURE (5.0, 5.0, drawBoxPlot) NORMAL (L"To understand the box plot we need the following definitions:") LIST_ITEM (L"%%q25% = lower quartile, 25\\% of the data lie below this value") LIST_ITEM (L"%%q50% = median, 50\\% of the data lie below this value") LIST_ITEM (L"%%q75% = upper quartile, 25\\% of the data lie above this value") NORMAL (L"The following definitions all depend on these quantiles:") LIST_ITEM (L"%%hspread% = |%%q75% \\-- %%q25%| (50\\% interval)") LIST_ITEM (L"%%lowerOuterFence% = %%q25% \\-- 3.0 * %%hspread% (not in figure)") LIST_ITEM (L"%%lowerInnerFence% = %%q25% \\-- 1.5 * %%hspread% (not in figure)") LIST_ITEM (L"%%upperInnerFence% = %%q75% + 1.5 * %%hspread%") LIST_ITEM (L"%%upperOuterFence% = %%q75% + 3.0 * %%hspread%") LIST_ITEM (L"%%lowerWhisker% = smallest data value larger then %%lowerInnerFence%") LIST_ITEM (L"%%upperWhisker% = largest data value smaller then %%upperInnerFence%") NORMAL (L"The box plot is a summary of the data in which:") LIST_ITEM (L"\\bu the horizontal lines of the rectangle correspond to " " %%q25%, %%q50% and %%q75%, respectively.") LIST_ITEM (L"\\bu the dotted line corresponds to the mean.") LIST_ITEM (L"\\bu the outliers outside the %%outerFences% are drawn with an 'o'.") LIST_ITEM (L"\\bu the outliers in the intervals (%%lowerOuterFence%, %%lowerInnerFence%) " "and (%%upperInnerFence%, %%upperOuterFence%) are drawn with an '*'.") LIST_ITEM (L"\\bu the whisker lines outside the rectangle connect %%q25% with %%lowerWhisker%, and, " "%%q75% with %%upperWhisker%, respectively. With no outliers present, the " "whiskers mark minimum and/or maximum of the data.") MAN_END MAN_BEGIN (L"BarkFilter", L"djmw", 20010404) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type BarkFilter represents an acoustic time-frequency " "representation of a sound: the power spectral density %P(%z, %t), expressed " "in dB's. " "It is sampled into a number of points around equally spaced times %t__%i_ " "and frequencies %z__%j_ (on a Bark scale).") ENTRY (L"Inside a BarkFilter") NORMAL (L"With @Inspect you will see that this type contains the same " "attributes a @Matrix.") MAN_END MAN_BEGIN (L"Bootstrap", L"djmw", 20031103) INTRO (L"The bootstrap data points are a random sample of size %n " "drawn %%with% replacement from the sample (%x__1_,...%x__n_). This " "means that the bootstrap data set consists of members of the original " "data set, some appearing zero times, some appearing once, some appearing " "twice, etc.") NORMAL (L"More information can be found in @@Efron & Tibshirani (1993)@.") MAN_END MAN_BEGIN (L"canonical variate", L"djmw", 20060328) NORMAL (L"A ##canonical variate# is a new variable (variate) formed by making a linear combination of two " "or more variates (variables) from a data set. " "A linear combination of variables is the same as a weighted sum of variables. " "Because we can in infinitely many ways choose combinations of weights between variables in a data set, " "there are also infinitely many canonical variates possible. ") NORMAL (L"In general additional constraints must be satisfied by the weights to get a meaningful canonical variate. " "For example, in @@Canonical correlation analysis|canonical correlation analyis@ a data set is split up into two parts, a %%dependent% and an %%independent% part. " "In both parts we can form a canonical variate and we choose weights that maximize the correlation between these canonical variates " "(there is an @@TableOfReal: To CCA...|algorithm@ that calculates these weights).") MAN_END MAN_BEGIN (L"Categories", L"djmw", 19960918) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Categories represents an ordered collection of categories. Each " "category is a simple text string.") ENTRY (L"Categories commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu ##Create an empty Categories#") LIST_ITEM (L"\\bu @@FFNet & Pattern: To Categories...@") NORMAL (L"Viewing and editing:") LIST_ITEM (L"\\bu @CategoriesEditor") NORMAL (L"Analysis:") LIST_ITEM (L"\\bu @@Categories: To Confusion@") LIST_ITEM (L"\\bu @@Categories: Difference@") NORMAL (L"Synthesis") LIST_ITEM (L"\\bu @@Categories: Append@") LIST_ITEM (L"\\bu ##Categories: Permute...#") LIST_ITEM (L"\\bu ##Categories: To unique Categories#") ENTRY (L"Inside a Categories") NORMAL (L"With @Inspect you will see the following attributes:") TAG (L"%size") DEFINITION (L"the number of simple categories.") TAG (L"%item[]") DEFINITION (L"the categories. Each category is an object of type #SimpleString.") MAN_END MAN_BEGIN (L"Categories: Difference", L"djmw", 19960918) INTRO (L"A command to compute the difference between two selected @Categories objects.") ENTRY (L"Behaviour") NORMAL (L"Each element in the first object is compared with the corresponding " "object in the second object according to its compare method. " "The number of different %categories will be shown in the @@Info window@.") MAN_END MAN_BEGIN (L"Categories: To Confusion", L"djmw", 19960918) INTRO (L"A command to compute the @Confusion matrix from two selected " "@Categories objects.") ENTRY (L"Algorithm") NORMAL (L"A confusion matrix is constructed from both #Categories objects in " "the following way: The first Categories object is considered the stimulus " "Categories and its unique (sorted) categories " "form the row indices of the confusion matrix, the unique (sorted) " "categories of the second object form the column indices of this matrix.") NORMAL (L"Next, each element in the first #Categories object is compared with " "the corresponding object in the second object and the element in the " "confusion matrix addressed by this pair is incremented by 1.") MAN_END MAN_BEGIN (L"Categories: Append", L"djmw", 19960918) INTRO (L"You can choose this command after selecting 2 objects of type @Categories. " "A new object is created that contains the second object appended after the first.") MAN_END MAN_BEGIN (L"Categories: Edit", L"djmw", 19960918) INTRO (L"You can choose this command after selecting one #Categories. " "A @CategoriesEditor will appear on the screen, with the selected #Categories in it.") MAN_END MAN_BEGIN (L"CategoriesEditor", L"djmw", 19960918) ENTRY (L"An editor for manipulating @Categories.") NORMAL (L"To make a selection, use the left mouse button.") NORMAL (L"The Ctrl key extends a selection (discontinuously).") NORMAL (L"The Shift key extends a selection contiguously.") MAN_END MAN_BEGIN (L"CC", L"djmw", 20010219) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"Any object that represents cepstral coefficients as a function of " "time.") MAN_END MAN_BEGIN (L"CCA", L"djmw", 20020323) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}. ") NORMAL (L"An object of type CCA represents the @@Canonical correlation " "analysis@ of two multivariate datasets.") ENTRY (L"Commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@TableOfReal: To CCA...@") MAN_END MAN_BEGIN (L"CCA: Get zero correlation probability...", L"djmw", 20040407) INTRO (L"Get the probability that for the selected @CCA object the chosen " "canonical correlation coefficient is different from zero.") ENTRY (L"Setting") TAG (L"##Index") DEFINITION (L"is the index of the canonical correlation coefficient that " "you want to test.") ENTRY (L"Algorithm") NORMAL (L"Wilks' statistic: the probability that coefficient \\ro__%index_ " "differs from zero is ") FORMULA (L" %probability = chiSquareQ (\\ci^2, %ndf),") NORMAL (L"where the %%number of degrees of freedom% parameter equals") FORMULA (L"%ndf = (%n__y_ - %index +1)(%n__x_ - %index +1)") NORMAL (L"and the chi-squared parameter is") FORMULA (L"\\ci^2 = \\--(%numberOfObservations - (%n__y_ + %n__x_ +3)/2) " "log (\\La__%index_),") NORMAL (L"In the formulas above the variables %n__y_ and %n__x_ are the " "dimensions of the dependent and the independent data sets whose " "canonical correlations have been " "obtained, and Wilks' lambda is:") FORMULA (L"\\La__index_ = \\Pi__%i=%index..min(%ny,%nx)_ (1 \\-- \\ro__%i_^^2^)") MAN_END MAN_BEGIN (L"CCA & Correlation: To TableOfReal (loadings)", L"djmw", 20020525) INTRO (L"Determine from the selected @CCA and @Correlation objects the correlations " "of the canonical variables with the original variables. These correlations are " "called %%canonical factor loadings%, or also %%structure correlation " "coefficients%.") MAN_END MAN_BEGIN (L"CCA & Correlation: Get variance fraction...", L"djmw", 20060323) INTRO (L"Determine from the selected @CCA and @Correlation objects the fraction of the variance " "explained by the selected @@canonical variate@ range.") ENTRY (L"Settings") TAG (L"##%X or Y") DEFINITION (L"determines whether you select the dependent (y) or the independent (x) set.") TAG (L"##Canonical variate range") DEFINITION (L"determines the canonical variates (or canonical variables).") ENTRY (L"Remarks") NORMAL (L"1. In general the variance fractions for a particular canonical variate in the " "dependent and in the independent set are not the same.") NORMAL (L"2. In general, the variance fractions for all canonical variates do not sum to 1.") ENTRY (L"Algorithm") NORMAL (L"The formula's can be found on page 170 of @@Cooley & Lohnes (1971)@.") NORMAL (L"For example, the fraction of the variance explained by the %i^^th^ canonical " "variable in the dependent set is:") FORMULA (L"%%fractionVariance% = ((#y__i_\\'p #R__yy_\\'p #R__yy_ #y__i_) / (#y__i_\\'p #R__yy_ #y__i_)) / %n__%y_,") NORMAL (L"where #y__%i_ is the eigenvector for dependent canonical variable %i and #R__%%yy%_ is the correlation matrix for the %n__%y_ variables in the dependent set.") MAN_END MAN_BEGIN (L"CCA & Correlation: Get redundancy (sl)...", L"djmw", 20060323) INTRO (L"Determine from the selected @CCA and @Correlation objects the Stewart-Love redundancy for the " "selected canonical variates.") NORMAL (L"The Stewart-Love redundancy for a single @@canonical variate@ is the fraction of variance explained by the selected " "canonical variate in a set times the fraction of shared variance between the corresponding canonical variates in the two sets.") NORMAL (L"The Stewart-Love redundancy for a canonical variate range is the sum of the individual redundancies.") ENTRY (L"Settings") TAG (L"##X or Y") DEFINITION (L"determines whether you select the dependent (y) or the independent (x) set.") TAG (L"##Canonical variate range") DEFINITION (L"determines the canonical variates (or canonical variables).") ENTRY (L"Algorithm") NORMAL (L"The formula's can be found on page 170 of @@Cooley & Lohnes (1971)@.") NORMAL (L"For example, the redundancy of the dependent set (y) given the independent set (x) for the %i^^%%th%^ canonical " "variate can be expressed as:") FORMULA (L"%R__%i_(y) = %%varianceFraction%__%i_(y) * \\ro__%i_^2, ") NORMAL (L"where %%varianceFraction%__%i_(y) is the @@CCA & Correlation: Get variance fraction...|variance fraction@ explained " "by the %i^^%%th%^ canonical variate of the dependent set, and \\ro__%i_ is the %i^^%%th%^ canonical correlation coefficient.") NORMAL (L"The redundancy for the selected canonical variate in the dependent set shows what " "fraction of the variance in the %%dependent% set is already \"explained\" by " "the variance in the %%independent% set, i.e. this fraction could be considered as redundant.") NORMAL (L"In the same way we can measure the redundancy of the independent (x) set giving the dependent set (y).") ENTRY (L"Remark") NORMAL (L"In general %R__%i_(y) \\=/ %R__%i_(x).") MAN_END MAN_BEGIN (L"CCA & TableOfReal: To TableOfReal (loadings)", L"djmw", 20020525) INTRO (L"Determine from the selected @CCA and @TableOfReal objects the correlations " "of the canonical variables with the original variables. These correlations are " "called %%canonical factor loadings%, or also %%structure correlation " "coefficients%.") MAN_END MAN_BEGIN (L"CCA & TableOfReal: To TableOfReal (scores)...", L"djmw", 20040407) INTRO (L"Determines the scores on the dependent and the independent canonical " "variates from the selected @CCA and @TableOfReal objects.") ENTRY (L"Settings") TAG (L"##Number of canonical correlations") DEFINITION (L"determines the dimension, i.e., the number of elements of the resulting " "canonical score vectors. The newly created table will have twice this number of " "columns because we have calculated score vectors for the dependent and the " "independent variates.") ENTRY (L"Behaviour") NORMAL (L"The scores on the dependent set are determined as #T__%y_ #Y, where " "#T__%y_ is the dependent part in the table and #Y is a matrix with " "%numberOfCanonicalCorrelations eigenvectors for the dependent variate.") NORMAL (L"The scores for the independent variates are then determined in an analogous " "way as #T__%x_ #X.") NORMAL (L"The scores for the dependent data will be in the lower numbered columns, " "the scores for the independent part will be in the higher numbered columns of " "the newly created object.") MAN_END MAN_BEGIN (L"Canonical correlation analysis", L"djmw", 20020509) INTRO (L"This tutorial will show you how to perform canonical correlation " "analysis with P\\s{RAAT}.") ENTRY (L"1. Objective of canonical correlation analysis") NORMAL (L"In canonical correlation analysis we try to find the correlations between " "two data sets. One data set is called the %dependent set, the other the " "%independent set. In P\\s{RAAT} these two sets must reside into one " "@TableOfReal object. The lower numbered columns of this table will then be " "interpreted as the dependent part, the rest of the columns as the " "independent part. " "The dimension of, i.e., the number of columns in, the dependent part may not " "exceed the dimension of the independent part.") NORMAL (L"As an example, we will use the dataset from @@Pols et al. (1973)@ " "with the frequencies and levels of the first three formants from the 12 " "Dutch monophthongal vowels as spoken in /h_t/ context by 50 male speakers. " "We will try to find the canonical correlation between formant frequencies " "(the %dependent part) and levels (the %independent part). " "The dimension of both groups of variates is 3. " "In the introduction of the " "@@discriminant analysis@ tutorial you can find how to get these data, " "how to take the logarithm of the formant frequency values and how to " "standardize them. The following script summarizes:") CODE (L"Create TableOfReal (Pols 1973)... yes") CODE (L"Formula... if col < 4 then log10 (self) else self endif") CODE (L"Standardize columns") NORMAL (L"Before we start with the %canonical correlation analysis we will first have " "a look at the %Pearson correlations of this table and " "calculate the @Correlation matrix. It is given by:") CODE (L" F1 F2 F3 L1 L2 L3") CODE (L"F1 1 -0.338 0.191 0.384 -0.505 -0.014") CODE (L"F2 -0.338 1 0.190 -0.106 0.526 -0.568") CODE (L"F3 0.191 0.190 1 0.113 -0.038 0.019") CODE (L"L1 0.384 -0.106 0.113 1 -0.038 0.085") CODE (L"L2 -0.505 0.526 -0.038 -0.038 1 0.128") CODE (L"L3 -0.014 -0.568 0.019 0.085 0.128 1") NORMAL (L"The following script summarizes:") CODE (L"select TableOfReal pols_50males") CODE (L"To Correlation") CODE (L"Draw as numbers... 1 0 decimal 3") NORMAL (L"The correlation matrix shows that high correlations exist between some " "formant frequencies and some levels. For example, the correlation " "coefficient between F2 and L2 equals 0.526.") NORMAL (L"In a canonical correlation analysis of the dataset above, we try " "to find the linear " "combination %u__1_ of %F__1_, %F__2_ and %F__3_ that correlates maximally " "with the linear combination %v__1_ of %L__1_, %L__2_ and %L__3_. " "When we have found these %u__1_ and %v__1_ we next try to find a new " "combination %u__2_ of the formant frequencies and a new combination " "%v__2_ of the levels that have maximum correlation. These %u__2_ and " "%v__2_ must be uncorrelated with %u__1_ and %v__1_. " "When we express the above with formulas we have:") FORMULA (L"%u__1_ = %y__11_%F__1_+%y__12_%F__2_ + %y__13_%F__3_") FORMULA (L"%v__1_ = %x__11_%L__1_+%x__12_%L__2_ + %x__13_%L__3_") FORMULA (L"\\ro(%u__1_, %v__1_) = maximum, \\ro(%u__2_, %v__2_) = submaximum, ") FORMULA (L"\\ro(%u__2_, %u__1_) = \\ro (%u__2_, %v__1_) = \\ro (%v__2_, %v__1_) " "= \\ro (%v__2_, %u__1_) = 0,") NORMAL (L"where the \\ro(%u__i_, %v__i_) are the correlations between the " "@@canonical variate@s %u__i_ and %v__i_ and the %y__%ij_'s and %x__%ij_'s are" " the ##canonical coefficients# for the dependent and the independent " "variates, respectively.") ENTRY (L"2. How to perform a canonical correlation analysis") NORMAL (L"Select the TableOfReal and choose from the dynamic menu the option " "@@TableOfReal: To CCA...|To CCA...@. This command is available in the " "\"Multivariate statistics\" action button. We fill out the form and supply " "3 for %%Dimension of dependent variate%. The resulting CCA object will bear " "the same name as the TableOfReal object. The following script summarizes:") CODE (L"select TableOfReal pols_50males") CODE (L"To CCA... 3") ENTRY (L"3. How to get the canonical correlation coefficients") NORMAL (L"You can get the canonical correlation coefficients by queries of the CCA " "object. You will find that the three canonical correlation coefficients, " "\\ro(%u__1_, %v__1_), \\ro(%u__2_, %v__2_) and \\ro(%u__3_, %v__3_) are " " approximately 0.86, 0.53 and 0.07, respectively. " "The following script summarizes:") CODE (L"cc1 = Get correlation... 1") CODE (L"cc2 = Get correlation... 2") CODE (L"cc3 = Get correlation... 3") CODE (L"printline cc1 = 'cc1', cc2 = 'cc2', cc3 = 'cc3'") ENTRY (L"4. How to obtain canonical scores") NORMAL (L"Canonical #scores, also named @@canonical variate@s, are the linear combinations:") FORMULA (L"%u__%i_ = %y__%i1_%F__1_+%y__%i2_%F__2_ + %y__%i3_%F__3_, and,") FORMULA (L"%v__%i_ = %x__%i1_%L__1_+%x__%i2_%L__2_ + %x__%i3_%L__3_,") NORMAL (L"where the index %i runs from 1 to the number of correlation coefficients.") NORMAL (L"You can get the canonical scores by selecting a CCA object together with " "the TableOfReal object and choose " "@@CCA & TableOfReal: To TableOfReal (scores)...|To TableOfReal (scores)...@") NORMAL (L"When we now calculate the ##Correlation# matrix of these canonical variates we " "get the following table:") CODE (L" u1 u2 u3 v1 v2 v3") CODE (L"u1 1 . . 0.860 . .") CODE (L"u2 . 1 . . 0.531 .") CODE (L"u3 . . 1 . . 0.070") CODE (L"v1 0.860 . . 1 . .") CODE (L"v2 . 0.1 . . 1 .") CODE (L"v3 . . 0.070 . . 1") NORMAL (L"The scores with a dot are zero to numerical precision. In this table the " "only correlations that differ from zero are the canonical correlations. " "The following script summarizes:") CODE (L"select CCA pols_50males") CODE (L"plus TableOfReal pols_50males") CODE (L"To TableOfReal (scores)... 3") CODE (L"To Correlation") CODE (L"Draw as numbers if... 1 0 decimal 2 abs(self) > 1e-14") ENTRY (L"5. How to predict one dataset from the other") NORMAL (L"@@CCA & TableOfReal: Predict...@") NORMAL (L"Additional information can be found in @@Weenink (2003)@.") MAN_END MAN_BEGIN (L"CCA & TableOfReal: Predict...", L"djmw", 20020503) INTRO (L"") MAN_END MAN_BEGIN (L"Chebyshev polynomials", L"djmw", 19990620) INTRO (L"The Chebyshev polynomials %T__%n_(%x) of degree %n are special orthogonal polynomial functions " "defined on the domain [-1, 1].") NORMAL (L"Orthogonality:") FORMULA (L"__-1_\\in^^1^ %W(%x) %T__%i_(%x) %T__%j_(%x) %dx = \\de__%ij_") FORMULA (L"%W(%x) = (1 \\-- %x^^2^)^^\\--1/2^ (-1 < x < 1)") NORMAL (L"They obey certain recurrence relations:") FORMULA (L"%T__%n_(%x) = 2 %x %T__%n-1_(%x) \\-- %T__%n-2_(%x)") FORMULA (L"%T__0_(%x) = 1") FORMULA (L"%T__1_(%x) = %x") MAN_END MAN_BEGIN (L"ChebyshevSeries", L"djmw", 19990620) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type ChebyshevSeries represents a linear combination of @@Chebyshev polynomials@ " "%T__%k_(%x).") FORMULA (L"ChebyshevSeries (%x) = \\Si__%k=1..%numberOfCoefficients_ %c__%k_ %T__%k_(%x)") MAN_END MAN_BEGIN (L"ChebyshevSeries: To Polynomial", L"djmw", 19990620) INTRO (L"A command to transform the selected @ChebyshevSeries object into a @@Polynomial@ object.") NORMAL (L"We find polynomial coefficients %c__%k_ such that") FORMULA (L"\\Si__%k=1..%numberOfCoefficients_ %c__%k_ %x^^%k^ = \\Si__%k=1.." "%numberOfCoefficients_ %l__%k_ %T__%k_(%x)") NORMAL (L"We use the recurrence relation for @@Chebyshev polynomials@ to calculate these coefficients.") MAN_END MAN_BEGIN (L"ClassificationTable", L"djmw", 19990525) INTRO (L"One of the @@types of objects@ in Praat.") NORMAL (L"An object of type ClassificationTable represents the result of a classification experiment. " "The numbers in a row show how well a particular input matches the classes represented by the " "column labels. The higher the number the better the match.") MAN_END MAN_BEGIN (L"concentration ellipse", L"djmw", 20071113) INTRO (L"The percentage of bivariate normally distributed data covered by an ellipse " "whose axes have a length of %numberOfSigmas\\.c\\si can be obtained by integration of the p.d.f. " "over an elliptical area. This results in the following equation as can be " "verified from equation 26.3.21 in @@Abramowitz & Stegun (1970)@:") FORMULA (L"%percentage = (1 - exp (-%numberOfSigmas^^2^/2))\\.c 100\\% ,") NORMAL (L"where the %numberOfSigmas is the radius of the \"ellipse\":") FORMULA (L"(%x/%\\si__x_)^2 + (%y/%\\si__y_)^2 = %numberOfSigmas^2.") NORMAL (L"The %numberOfSigmas = 1 ellipse covers 39.3\\% , " "the %numberOfSigmas = 2 ellipse covers 86.5\\% and " "the %numberOfSigmas = 3 ellipse covers 98.9\\% of the data.") NORMAL (L"From the formula above we can show that if we want to cover %p percent of the data, we have to " "chose %numberOfSigmas as:") FORMULA (L"%numberOfSigmas = \\Vr(-2 ln(1-%p/100)).") NORMAL (L"For covering 95\\% of the data we calculate %numberOfSigmas = 2.45.") MAN_END MAN_BEGIN (L"confidence interval", L"djmw", 20011105) INTRO (L"The confidence interval gives an estimated range of values which " "is likely to include an unknown population parameter. " "The estimated range is calculated from a given set of observations.") ENTRY (L"Examples") NORMAL (L"At the \\al level of significance a two sided confidence interval " "for the true mean \\mu for normally distributed data with mean %%mean% and " "known standard deviation %\\si can be constructed as:") FORMULA (L"%%mean% - %z__\\al/2_ \\si / \\Vr%N \\<_ \\mu \\<_ " "%%mean% + %z__\\al/2_ \\si / \\Vr%N,") NORMAL (L"where %z__\\al/2_ = invGaussQ (\\al/2) and %N is the number of observations.") NORMAL (L"If the standard deviation is %not known, we have to estimate its value (%s) " "from the data and the formula above becomes:") FORMULA (L"%%mean% - %t__%%\\al/2;N%_ %s / \\Vr%N \\<_ \\mu \\<_ " "%%mean% + %t__%%\\al/2;N%_ %s / \\Vr%N,") NORMAL (L"where %t__%%\\al/2;N%_ = invStudentQ (%\\al/2, %N-1).") NORMAL (L"For %\\al=0.05 and %N=20 we get %z__0.025_=1.96 and %t__0.025;20_=2.039. " "This shows that when we have to estimate the standard deviation from the data, " "the confidence interval is wider than when the standard deviation is known " "beforehand.") MAN_END MAN_BEGIN (L"confidence level", L"djmw", 20011105) NORMAL (L"The confidence level is the probability value 1-\\al associated " "with a @@confidence interval@, where \\al is the level of significance. " "It can also be expressed as a percentage 100(1-\\al)\\% and is than " "sometimes called the %%confidence coefficient%.") MAN_END MAN_BEGIN (L"Confusion", L"djmw", 20110517) INTRO (L"One of the @@types of objects@ in Praat.") NORMAL (L"An object of type Confusions represents a confusion matrix, with " "stimuli as row labels and responses as column labels. The entry at " "position [%i][%j] represents the number of times response %j " "was given to the stimulus %i.") ENTRY (L"Creating a Confusion from data in a text file") NORMAL (L"Suppose you have two objects A and B. " "In one way or another, you have acquired the following " "confusions: %\\de__%AA_ = 6, %\\de__%AB_ = 2 , %\\de__%BA_ = 1, " "and %\\de__%BB_ = 7.") NORMAL (L"You can create a simple text file like the following:") CODE (L"\"ooTextFile\" ! to make Praat recognize your file") CODE (L"\"Confusion\" ! The line that tells Praat about the contents") CODE (L"2 \"A\" \"B\" ! Number of columns, and column labels") CODE (L"2 ! Number of rows") CODE (L"\"A\" 6 2 ! Row label A, A-A value, A-B value") CODE (L"\"B\" 1 7 ! Row label B, B-A value, B-B value") NORMAL (L"This text file can be read with the @@Read from file...@ command. ") ENTRY (L"Commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@Categories: To Confusion") LIST_ITEM (L"\\bu @@Create simple Confusion...") NORMAL (L"Drawing") LIST_ITEM (L"\\bu ##Draw as numbers...") LIST_ITEM (L"\\bu ##Draw as squares...") NORMAL (L"Query") LIST_ITEM (L"\\bu @@Confusion: Get fraction correct|Get fraction correct") LIST_ITEM (L"\\bu @@Confusion: Get stimulus sum...") LIST_ITEM (L"\\bu @@Confusion: Get response sum...") LIST_ITEM (L"\\bu ##Get grand sum") NORMAL (L"Modification") LIST_ITEM (L"\\bu ##Formula...") LIST_ITEM (L"\\bu @@Confusion: Increase...") NORMAL (L"Grouping") LIST_ITEM (L"\\bu @@Confusion: Group stimuli...@") LIST_ITEM (L"\\bu @@Confusion: Group responses...@") NORMAL (L"Analysis:") LIST_ITEM (L"\\bu @@Confusion: To Similarity...@") LIST_ITEM (L"\\bu @@Confusion: To Dissimilarity (pdf)...@") ENTRY (L"Inside a Confusion") NORMAL (L"With @Inspect you will see the following attributes:") TAG (L"%numberOfRows") DEFINITION (L"the number of stimuli.") TAG (L"%numberOfColumns") DEFINITION (L"the number of responses.") TAG (L"%rowLabels") DEFINITION (L"the names of the stimuli.") TAG (L"columnLabels") DEFINITION (L"the names of the responses.") MAN_END MAN_BEGIN (L"Create simple Confusion...", L"djmw", 20110517) INTRO (L"Creates a square @@Confusion|confusion matrix@ with equal stimulus labels and response labels.") ENTRY (L"Example") NORMAL (L"The command ##Create simple Confusion... simple u i a# results in the following Confusion:") CODE (L" u i a ! The response labels") CODE (L"u 0 0 0 ! Responses on stimulus u,") CODE (L"i 0 0 0 ! Responses on stimulus i") CODE (L"a 0 0 0 ! Responses on stimulus a") MAN_END MAN_BEGIN (L"Confusion: Increase...", L"djmw", 20110517) INTRO (L"Increases the contents of the corresponding cell in the selected @@Confusion@ by one.") ENTRY (L"Settings") TAG (L"##Stimulus# and ##Response#") DEFINITION (L"define the cell whose value will be increased by one.") ENTRY (L"Example") NORMAL (L"Given the following Confusion:") CODE (L" u i a ! The response labels") CODE (L" u 6 2 1 ! Responses on stimulus u,") CODE (L" i 3 4 2 ! Responses on stimulus i") CODE (L" a 1 4 4 ! Responses on stimulus a") NORMAL (L"The command ##Increase... u i# results in:") CODE (L" u i a ! The responses") CODE (L" u 6 3 1 ! Responses on stimulus u,") CODE (L" i 3 4 2 ! Responses on stimulus i") CODE (L" a 1 4 4 ! Responses on stimulus a") MAN_END MAN_BEGIN (L"Confusion: Group...", L"djmw", 20110517) INTRO (L"Groups a number of stimuli and responses into one new category.") ENTRY (L"Settings") TAG (L"##Stimuli & Responses") DEFINITION (L"defines the labels that will be grouped.") TAG (L"##New label") DEFINITION (L"defines the new label for the grouped labels.") TAG (L"##New label position") DEFINITION (L"the row/column number for the new group label.") ENTRY (L"Example") NORMAL (L"Given the following selected Confusion:") CODE (L" u i a ! The response labels") CODE (L" u 6 2 1 ! Responses on stimulus u,") CODE (L" i 3 4 2 ! Responses on stimulus i") CODE (L" a 1 4 4 ! Responses on stimulus a") NORMAL (L"After the command ##Group stimuli... \"u i\" high 0#, the new Confusion will be:") CODE (L" high a ! The new response labels") CODE (L" high 15 3 ! Responses on group %%high%") CODE (L" a 5 4 ! Responses on stimulus a") NORMAL (L"Instead after the command ##Group stimuli... \"u i\" high 2#, the new Confusion will be:") CODE (L" a high ! The new response labels") CODE (L" a 4 5 ! Responses on stimulus a") CODE (L" high 3 15 ! Responses on group %%high%") MAN_END MAN_BEGIN (L"Confusion: Group stimuli...", L"djmw", 20110512) INTRO (L"Groups a number of stimuli into one new category.") ENTRY (L"Settings") TAG (L"##Stimuli") DEFINITION (L"defines the stimuli that will be grouped.") TAG (L"##New label") DEFINITION (L"defines the new label for the grouped stimuli.") TAG (L"##New label position") DEFINITION (L"the row number for the new group label.") ENTRY (L"Example") NORMAL (L"Given the following selected Confusion:") CODE (L" u i a ! The response labels") CODE (L" u 6 2 1 ! Responses on stimulus u,") CODE (L" i 3 4 2 ! Responses on stimulus i") CODE (L" a 1 4 4 ! Responses on stimulus a") NORMAL (L"After the command ##Group stimuli... \"u i\" high 1#, the new Confusion will be:") CODE (L" u i a ! The response labels") CODE (L" high 9 6 3 ! Responses on stimulus group %%high%,") CODE (L" a 1 4 4 ! Responses on stimulus a") MAN_END MAN_BEGIN (L"Confusion: Group responses...", L"djmw", 20110512) INTRO (L"Groups a number of responses into one new category.") ENTRY (L"Settings") TAG (L"##Responses") DEFINITION (L"defines the responses that will be grouped.") TAG (L"##New label") DEFINITION (L"defines the new label for the grouped responses.") TAG (L"##New label position") DEFINITION (L"the column number for the new group label.") ENTRY (L"Example") NORMAL (L"Given the following selected Confusion:") CODE (L" u i a ! The response labels") CODE (L" u 6 2 1 ! Responses on stimulus u,") CODE (L" i 3 4 2 ! Responses on stimulus i") CODE (L" a 1 4 4 ! Responses on stimulus a") NORMAL (L"After the command ##Group responses... \"a i\" front 1#, the new Confusion will be:") CODE (L" front i ! The new response labels") CODE (L" u 7 2 ! Responses on stimulus u,") CODE (L" i 5 4 ! Responses on stimulus i") CODE (L" a 5 4 ! Responses on stimulus a") MAN_END MAN_BEGIN (L"Confusion: Get stimulus sum...", L"djmw", 20110517) INTRO (L"Returns the number of responses for the chosen stimulus (the sum of all the numbers in the row with this stimulus label). ") ENTRY (L"Example") NORMAL (L"Given the following selected Confusion:") CODE (L" u i a ! The response labels") CODE (L" u 6 2 1 ! Responses on stimulus u,") CODE (L" i 3 4 2 ! Responses on stimulus i") CODE (L" a 1 4 4 ! Responses on stimulus a") NORMAL (L"The command ##Get stimulus sum... a# will return the number 9.") MAN_END MAN_BEGIN (L"Confusion: Get response sum...", L"djmw", 20110517) INTRO (L"Returns the number of times the chosen response was given (the sum of all the numbers in the column with this response label).") ENTRY (L"Example") NORMAL (L"Given the following selected Confusion:") CODE (L" u i a ! The response labelss") CODE (L" u 6 2 1 ! Responses on stimulus u,") CODE (L" i 3 4 2 ! Responses on stimulus i") CODE (L" a 1 4 4 ! Responses on stimulus a") NORMAL (L"The command ##Get response sum... a# will return the number 7.") MAN_END MAN_BEGIN (L"Confusion: Condense...", L"djmw", 20110512) INTRO (L"Groups row and column labels of the selected @Confusion object in " "order to reduce its dimension. ") ENTRY (L"Settings") TAG (L"##Search") DEFINITION (L"the pattern to match.") TAG (L"##Replace") DEFINITION (L"the pattern that replaces the match(es).") TAG (L"##Replace limit") DEFINITION (L"limits the maximum number of times that a match/replace cycle " "may occur within each label.") TAG (L"##Search and replace are") DEFINITION (L"defines whether the search and replace strings are taken " "literally or as a @@Regular expressions|regular expression@.") ENTRY (L"Behaviour") NORMAL (L"First all row and column labels are changed according to the search " "and replace specification. Next all rows or columns that have the same " "labels are summed. ") MAN_END MAN_BEGIN (L"Confusion: Get fraction correct", L"djmw", 20000225) INTRO (L"A @@query@ to ask the selected @Confusion matrix for the fraction of " "correct classifications.") NORMAL (L"The \"fraction correct\" is defined as the quotient of the number " "of correct classifications and the sum of the entries in the matrix.") NORMAL (L"Correct classifications have identical row and column labels.") MAN_END MAN_BEGIN (L"Confusion: To TableOfReal (marginals)", L"djmw", 20011031) INTRO (L"A new @TableOfReal object is created from the selected @Confusion " "object with one extra row and column. ") NORMAL (L"The first element of the extra row will contain the sum of the " "confusions in the the first %column, the first element of the extra " "column will contain the sum of the confusions in the the first %row, " "etc... The bottom-right element will contain the sum of all confusions.") MAN_END MAN_BEGIN (L"Correlation", L"djmw", 19990105) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Correlation represents the correlation coefficients " "of a multivariate data set.") MAN_END MAN_BEGIN (L"Correlation: Confidence intervals...", L"djmw", 20040407) INTRO (L"Calculates @@confidence interval@s for the correlation coefficients " "from the selected @Correlation object(s) and saves these intervals in a " "new @TableOfReal object.") ENTRY (L"Settings") TAG (L"##Confidence level") DEFINITION (L"the @@confidence level@ you want for the confidence intervals.") TAG (L"##Number of tests") DEFINITION (L"determines the @@Bonferroni correction@ for the significance " "level. If the default value (zero) is chosen, it will be set equal " "to the number of correlations involved (a matrix of dimension %n " "has %n\\.c(%n-1)/2 correlations).") TAG (L"##Approximation") DEFINITION (L"defines the approximation that will be used to calculate the " "confidence intervals. It is either Fisher's z transformation or Ruben's " "transformation. According to @@Boomsma (1977)@, Ruben's approximation is " "more accurate than Fisher's.") ENTRY (L"Algorithm") NORMAL (L"We obtain intervals by the large-sample conservative multiple tests " "with Bonferroni inequality and the Fisher or Ruben transformation. " "We put the upper values of the confidence intervals in the upper " "triangular part of the matrix and the lower values of the confidence " "intervals in lower triangular part of the resulting TableOfReal object.") NORMAL (L"In %%Fisher's approximation%, for each element %r__%ij_ of the " "correlation matrix the confidence interval is:") FORMULA (L"#[ tanh (%z__%ij_ - %z__%\\al\\'p_ / \\Vr(%N - 3)) , " "tanh (%z__%ij_ + %z__%\\al\\'p_ / \\Vr(%N - 3)) #],") NORMAL (L"where %z__%ij_ is the Fisher z-transform of the correlation %r__%ij_:") FORMULA (L"%z__%ij_ = 1/2 ln ((1 + %r__%ij_) / (1 - %r__%ij_)), ") NORMAL (L"%z__%\\al\\'p_ the Bonferroni corrected %z-value " "%z__%\\al/(2\\.c%numberOfTests)_, ") FORMULA (L"%\\al = 1 - %confidenceLevel,") NORMAL (L"and %N the number of observations that the correlation matrix is " "based on.") NORMAL (L"In %%Ruben's approximation% the confidence interval for element %r__%ij_ " "is:") FORMULA (L"#[ %x__1_ / \\Vr(1 - %x__1_^2), %x__2_ / \\Vr(1 - %x__2_^2) #]") NORMAL (L"in which %x__1_ and %x__2_ are the smallest and the largest root from") FORMULA (L"%a %x^^2^ + %b %x + %c = 0, with") FORMULA (L"%a = 2%N - 3 - %z__%\\al\\'p_^^2^") FORMULA (L"%b = - 2 %r\\'p \\Vr((2%N - 3)(2%N - 5))") FORMULA (L"%c = (2%N - 5 - %z__%\\al\\'p_^^2^) %r\\'p^^2^ - 2%z__%\\al\\'p_^^2^, and") FORMULA (L"%r\\'p = %r__%ij_ / \\Vr(1 - %r__%ij_^2),") MAN_END MAN_BEGIN (L"Covariance", L"djmw", 19990105) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Covariance represents the sums of squares and cross " "products of a multivariate data set divided by the number of observations.") NORMAL (L"An object of type Covariance contains the same attributes as an object of " "type @SSCP.") NORMAL (L"Since an object of type Covariance contains the mean values (the " "centroids), the covariances as well as the number of observations it has " "all the information necessary to be the subject of all kinds of statistical " "tests on means and variances.") MAN_END MAN_BEGIN (L"Create simple Covariance...", L"djmw", 20101125) INTRO (L"Create a @@Covariance@ matrix with its centroid.") ENTRY (L"Settings") TAG (L"##Covariances") DEFINITION (L"define the covariances. Because a covariance matrix is a symmetric matrix, only the upper triangular " "part of the matrix has to be input (row-wise). If your covariance matrix is " "of dimension %d, your input needs %d(%d+1)/2 elements. The first %d input elements are the elements of the first " "row of the covariance matrix, the next %d-1 input elements are for the second row, then %d-2 for the third row, etc.") TAG (L"##Centroid") DEFINITION (L"defines the centroid. ") TAG (L"##Number of observations") DEFINITION (L"defines the number of observations. ") MAN_END MAN_BEGIN (L"Covariance: Set value...", L"djmw", 20101124) INTRO (L"Input @@Covariance@ matrix cell values.") ENTRY (L"Constraints on input values") TAG (L"A covariance matrix is a %%symmetric% matrix: values input at cell [%i,%j] will be automatically input at " "cell [%j,%i] too.") TAG (L"All values on the diagonal must be positive numbers.") TAG (L"The absolute value of an off-diagonal element at cell [%i,%j] must be smaller than the corresponding diagonal " "elements at cells [%i,%i] and [%j,%j].") MAN_END MAN_BEGIN (L"Covariance: Difference", L"djmw", 20090624) INTRO (L"You can choose this command after selecting two objects of type @Covariance. ") NORMAL (L"We test the hypothesis that the samples that gave rise to the two " "covariance matrices #%M__1_ and #%M__2_, have equal covariances. " "The test statistic is %L\\'p which is distributed as " "a \\ci^2 variate with %p(%p+1)/2 degrees of freedom.") FORMULA (L"%L\\'p = %L \\.c (1 \\-- (2%p + 1 \\-- 2 / (%p + 1)) / (6 \\.c ( %N \\-- 1))),") NORMAL (L"where, ") FORMULA (L"%L = (%N \\-- 1) \\.c (ln determinant (#%M__1_) \\-- ln determinant " "(#%M__2_)) + trace (#%M__2_ \\.c #%M__1_^^\\--1^) \\-- %p), ") NORMAL (L"%p is dimension of covariance matrix and " "%N is the number of observations underlying the covariance matrix. ") NORMAL (L"For more details on this test, see e.g. page 292 of @@Morrison (1990)@.") MAN_END MAN_BEGIN (L"Covariance: Get significance of one mean...", L"djmw", 20040407) INTRO (L"Gets the level of significance for one mean from the selected " "@Covariance object being different from a hypothesized mean.") ENTRY (L"Settings") TAG (L"##Index") DEFINITION (L"the position of the element in the means vector (centroid) that " "you want to test. ") TAG (L"##Value") DEFINITION (L"the hypothesized mean %\\mu (see below).") ENTRY (L"Behaviour") NORMAL (L"This is the standard test on means when the variance is unknown. " "The test statistic is") FORMULA (L"%t = (%mean - %\\mu) \\Vr%(N / %s^2),") NORMAL (L"which has the Student %t distribution with %ndf = %N-1 degrees of freedom.") NORMAL (L"In the formulas above, %mean is the element of the mean vector at " "position %index, %\\mu is the hypothesized mean, " "%N is the number of observations, %s^2 " "is the variance at position [%index][%index] in the covariance matrix.") NORMAL (L"The returned probability %p is the %%two-sided% probability") FORMULA (L"%p = 2 * studentQ (%t, %ndf)") NORMAL (L"A low probability %p means that the difference is significant.") MAN_END MAN_BEGIN (L"Covariance: Get fraction variance...", L"djmw", 20040407) INTRO (L"A command to ask the selected @Covariance object for the fraction " "of the total variance that is accounted for by the selected dimension(s).") ENTRY (L"Settings") TAG (L"##From dimension#, ##To dimension#") DEFINITION (L"define the range of components. By choosing both numbers equal, " "you get the fraction of the variance \"explained\" by that dimension.") ENTRY (L"Details") NORMAL (L"The total variance is the sum of the diagonal elements of the covariance " "matrix #C, i.e., its trace. " "The fraction is defined as:") FORMULA (L"\\Si__%i=%from..%to_ %%C__ii_% / \\Si__%i=1..%numberOfRows_ %%C__ii_%") MAN_END MAN_BEGIN (L"Covariance: Get significance of means difference...", L"djmw", 20040407) INTRO (L"Gets the level of significance for the %difference of two means " "from the selected @Covariance object being different from a hypothesized " "value.") ENTRY (L"Settings") TAG (L"##Index1#, ##Index2#") DEFINITION (L"the positions of the two elements of the means vector whose " "difference is compared to the hypothesized difference.") TAG (L"##Value") DEFINITION (L"the hypothesized difference (%\\mu).") TAG (L"##Paired samples") DEFINITION (L"determines whether we treat the two means as being dependent. ") TAG (L"##Equal variances") DEFINITION (L"determines whether the distribution of the difference of the means " "is a Student t-distribution (see below).") ENTRY (L"Behaviour") NORMAL (L"This is Student's t-test for the significance of a difference of means. " "The test statistic is:") FORMULA (L"%t = (%mean__1_ - %mean__2_ - %\\mu) \\Vr (%N / %s^2) with %ndf " "degrees of freedom.") NORMAL (L"In the formula above %mean__1_ and %mean__2_ are the elements of the " "means vector, %\\mu is the hypothesized difference and %N is the number of " "observations. The value that we use for the (combined) variance %s^2 is:") FORMULA (L"%s^2 = %var__1_ + %var__2_ - 2 * %covar__12_,") NORMAL (L"when the samples are %paired, and ") FORMULA (L"%s^2 = %var__1_ + %var__2_ ") NORMAL (L"when they are not.") NORMAL (L"The %var__1_ and %var__2_ are the variance components for " "%mean__1_ and %mean__2_, respectively, and %covar__12_ is their covariance." " When we have %%paired samples% we assume that the two variances are " "not independent and their covariance is subtracted, otherwise their " "covariance is not taken into account. Degrees of freedom parameter %ndf " "usually equals 2(%N-1). ") NORMAL (L"If the two variances are significantly different, the statistic %t " "above is only %approximately distributed as Student's %t with " "degrees of freedom equal to:") FORMULA (L"%ndf = (%N-1) \\.c (%var__1_ + %var__2_)^2 / (%var__1_^2 + " "%var__2_^2).") NORMAL (L"The returned probability %p will be the %%two-sided% probability") FORMULA (L"%p = 2 * studentQ (%t, %ndf)") NORMAL (L"A low probability %p means that the difference is significant.") MAN_END MAN_BEGIN (L"Covariance: Get significance of one variance...", L"djmw", 20040407) INTRO (L"Gets the probability for one variance from the selected " "@Covariance object being different from a hypothesized variance.") ENTRY (L"Settings") TAG (L"##Index") DEFINITION (L"the position of the variance element.") TAG (L"##Hypothesized variance") DEFINITION (L"the hypothesized variance %\\si^2") ENTRY (L"Behaviour") NORMAL (L"The test statistic") FORMULA (L"%\\ci^2 = (%N-1)%s^2 / %\\si^2,") NORMAL (L"is distributed as a chi-squared variate with %ndf = %N-1 degrees of freedom.") NORMAL (L"The returned probability %p will be ") FORMULA (L"%p = chiSquareQ (%\\ci^2, %ndf)") MAN_END MAN_BEGIN (L"Covariance: Get significance of variance ratio...", L"djmw", 20040407) INTRO (L"Gets the probability for the ratio of two variances " "from the selected @Covariance object being different from a hypothesized " "ratio.") ENTRY (L"Settings") TAG (L"##Index1#, ##Index2#") DEFINITION (L"determine the variances.") TAG (L"##Hypothesized ratio") DEFINITION (L"the hypothesized ratio %F.") ENTRY (L"Behaviour") NORMAL (L"The test statistic") FORMULA (L"%f = %s__1_^2 / %s__2_^2 / %ratio") NORMAL (L"is distributed as Fisher's F distribution with %ndf__1_ = %N-1 and " "%ndf__2_ = %N-1 degrees of freedom for the numerator and denominator terms, " "respectively.") NORMAL (L"The returned probability %p will be the %%two-sided% probability") FORMULA (L"%p = 2 * fisherQ (%f, %ndf__1_, %ndf__2_)") NORMAL (L"If %s__2_^2 > %s__1_^2 we use 1/%f to determine the probability.") MAN_END MAN_BEGIN (L"Covariances: Report multivariate mean difference...", L"djmw", 20090627) INTRO (L"Reports the probability that the two multivariate means of the selected @@Covariance@s are equal.") ENTRY (L"Settings") TAG (L"##Covariances are equal") DEFINITION (L"determines whether the test is performed as if the two covariance matrices are equal or not.") ENTRY (L"Algorithm") NORMAL (L"For equal covariance matrices the test is via Hotelling's T^^2^ as described in @@Morrison (1990)|Morrison (1990,@ page 141). " "The test statistic is %F = (%N__1_+%N__2_-%p-1)/((%N__1_+%N__2_-2)%p)\\.c T^^2^, with %p and %N__1_+%N__2_-%p-1 degrees of freedom.") NORMAL (L"If the covariance matrices are not equal, we apply a correction on the number of degrees of freedom as " "proposed by @@Krishnamoorthy & Yu (2004)@. The test statistic in this case is %F = (\\nu-%p+1)/(%p\\nu)\\.c T^^2^, " "with %p and \\nu degrees of freedom. Here \\nu is a corrected number of degrees of freedom. ") NORMAL (L"(The test for unequal covariances simplifies to Welch's approximate solution for the univariate t-test with unequal variances.) ") MAN_END MAN_BEGIN (L"Covariances: Report equality", L"djmw", 20090701) INTRO (L"Reports the probability that the selected @@Covariance@ matrices are equal.") NORMAL (L"We use the Bartlett test and the Wald test. According to @@Schott (2001)@, " "both tests are overly sensitive to violations of normality.") MAN_END MAN_BEGIN (L"Covariance: To TableOfReal (random sampling)...", L"djmw", 20101101) INTRO (L"Generate a @TableOfReal object by random sampling from a multi-variate " "normal distribution whose @Covariance matrix is the selected object.") ENTRY (L"Setting") TAG (L"##Number of data points") DEFINITION (L"determines the number of data points that will be generated. Each " "data point occupies one row in the generated table.") ENTRY (L"Algorithm") NORMAL (L"The algorithm proceeds as follows:") LIST_ITEM (L"1. Diagonalize the covariance matrix: calculate the eigenvalues $v__%i_ and " "eigenvectors %#e__%i_ of the %m \\xx %m Covariance matrix. " "In general there will also be %m of these. Let #%E be the %m \\xx %m matrix " "with eigenvector %#e__%j_ in column %j (%j=1..%m).") LIST_ITEM (L"2. Generate a vector #x whose elements %x__%k_ equal %x__%k_ = " "randomGauss (0, \\Vr (%v__%k_)). " "Each %x__%k_ is a random deviate drawn from a Gaussian distribution with " "mean zero and standard deviation equal to the square root of the corresponding " "eigenvalue %v__%k_.") LIST_ITEM (L"3. Rotate back: calculate the vector #y = #%E #x, obtained by multiplying the vector " "#x with the matrix #%E.") LIST_ITEM (L"4. Add the centroid to #y and copy the elements of #y to the corresponding row of " "the TableOfReal object.") LIST_ITEM (L"5. Repeat steps 2, 3 and 4 until the desired number of data points " "has been reached.") LIST_ITEM (L"6. Copy the column labels from the Covariance object to the " "TableOfReal object.") NORMAL (L"In case the covariance matrix is diagonal, the algorithm is much simpler: we can skip " "the first and third step.") MAN_END MAN_BEGIN (L"Covariance & TableOfReal: Extract quantile range...", L"djmw", 20040225) INTRO (L"Extract those rows from the selected @TableOfReal object whose Mahalanobis " "distance, with respect to the selected @Covariance object, are within the " "quantile range.") MAN_END MAN_BEGIN (L"Covariance & TableOfReal: To TableOfReal (mahalanobis)...", L"djmw", 20100106) INTRO (L"Calculate Mahalanobis distance for the selected @TableOfReal with respect to the " "selected @Covariance object.") ENTRY (L"Setting") TAG (L"##Use table centroid") DEFINITION (L"Use the mean vector calculated from the columns in the selected TableOfReal instead of the means in the selected Covariance.") ENTRY (L"Explanation") NORMAL (L"The Mahalanobis distance is defined as") FORMULA (L"%d = \\Vr((#%x - #mean)\\'p #S^^-1^ (#%x - #mean)),") NORMAL (L"where #%x is a vector, #mean is the average and #S is the covariance matrix. ") NORMAL (L"It is the multivariate form of the distance measured in units of standard deviation.") ENTRY (L"Example") NORMAL (L"Count the number of items that are within 1, 2, 3, 4 and 5 standard deviations from the mean.") NORMAL (L"We first create a table with only one column and 10000 rows and fill it with numbers drawn from " "a normal distribution with mean zero and standard deviation one. Its covariance matrix, of course, is " "one dimensional. We next create a table with Mahalanobis distances.") CODE (L"n = 100000") CODE (L"t0 = Create TableOfReal... table n 1") CODE (L"Formula... randomGauss(0,1)") CODE (L"c = To Covariance") CODE (L"plus t0") CODE (L"ts = To TableOfReal (mahalanobis, 0)") CODE (L"") CODE (L"for nsigma to 5") CODE1 (L"select ts") CODE1 (L"Extract rows where... self < nsigma") CODE1 (L"nr = Get number of rows") CODE1 (L"nrp = nr / n * 100") CODE1 (L"expect = (1 - 2 * gaussQ (nsigma)) * 100") CODE1 (L"printline 'nsigma'-sigma: 'nrp:4'%, 'expect:4'%") CODE1 (L"Remove") CODE (L"endfor") MAN_END MAN_BEGIN (L"Create ChebyshevSeries...", L"djmw", 20040407) INTRO (L"A command to create a @ChebyshevSeries from a list of coefficients.") ENTRY (L"Settings") TAG (L"##Xmin# and ##Xmax#") DEFINITION (L"define the domain of the polynomials.") TAG (L"%Coefficients") DEFINITION (L"define the coefficients of each @@Chebyshev polynomials|Chebyshev polynomial@. " "The coefficient of the polynomial with the highest degree comes last.") MAN_END MAN_BEGIN (L"Create ISpline...", L"djmw", 20040407) INTRO (L"A command to create an @ISpline from a list of coefficients.") ENTRY (L"Settings") TAG (L"##Xmin# and ##Xmax#") DEFINITION (L"define the domain of the polynomial @spline.") TAG (L"%Degree") DEFINITION (L"defines the degree of the polynomial @spline.") TAG (L"%Coefficients") DEFINITION (L"define the coefficients of the basis polynomials.") TAG (L"%%Interior knots") DEFINITION (L"define the positions in the domain where continuity conditions are defined.") ENTRY (L"Behaviour") NORMAL (L"The number of coefficients and the number of interior knots must satisfy " "the following relation:") FORMULA (L"%numberOfCoefficients = %numberOfInteriorKnots + %degree") NORMAL (L"") MAN_END MAN_BEGIN (L"Create MSpline...", L"djmw", 20040407) INTRO (L"A command to create an @MSpline from a list of coefficients.") ENTRY (L"Settings") TAG (L"##Xmin# and ##Xmax#") DEFINITION (L"define the domain of the polynomial @spline.") TAG (L"##Degree") DEFINITION (L"defines the degree of the polynomial @spline.") TAG (L"##Coefficients") DEFINITION (L"define the coefficients of the basis polynomials.") TAG (L"##Interior knots") DEFINITION (L"define the positions in the domain where continuity conditions are defined.") ENTRY (L"Behaviour") NORMAL (L"The number of coefficients and the number of interior knots must satisfy " "the following relation:") FORMULA (L"%numberOfCoefficients = %numberOfInteriorKnots + %degree + 1") NORMAL (L"") MAN_END MAN_BEGIN (L"Create Polynomial...", L"djmw", 20040407) INTRO (L"A command to create an @Polynomial from a list of coefficients.") ENTRY (L"Settings") TAG (L"##Xmin# and ##Xmax#") DEFINITION (L"define the domain of the polynomial.") TAG (L"##Degree") DEFINITION (L"defines the degree of the basis polynomials.") TAG (L"##Coefficients") DEFINITION (L"define the coefficients of the polynomial. The coefficient of the " "highest power of %x comes last.") MAN_END MAN_BEGIN (L"Create LegendreSeries...", L"djmw", 20040407) INTRO (L"A command to create a @LegendreSeries from a list of coefficients.") ENTRY (L"Settings") TAG (L"##Xmin# and ##Xmax#") DEFINITION (L"define the domain of the polynomials.") TAG (L"##Coefficients") DEFINITION (L"define the coefficients of each @@Legendre polynomials|Legendre polynomial@. " "The coefficient of the polynomial with the highest degree comes last.") MAN_END MAN_BEGIN (L"Create Sound from gammatone...", L"djmw", 20100517) INTRO (L"A command to create a @Sound as a @@gammatone@.") ENTRY (L"Settings") TAG (L"##Name") DEFINITION (L"the name of the resulting Sound object.") TAG (L"##Minimum time (s)# and ##Maximum time (s)#") DEFINITION (L"the start and end time of the resulting Sound.") TAG (L"##Sampling frequency (Hz)") DEFINITION (L"the @@sampling frequency@ of the resulting Sound.") TAG (L"##Gamma") DEFINITION (L"determines the exponent of the polynomial.") TAG (L"##Frequency (Hz)# and ##Bandwidth (Hz)#") DEFINITION (L"determine the frequency and damping of the cosine wave in the gammatone.") TAG (L"##Initial phase (radians)") DEFINITION (L"the initial phase of the cosine wave.") TAG (L"##Addition factor# (standard value: 0)") DEFINITION (L"determines the degree of asymmetry in the spectrum of the gammatone. " "The zero default value gives a gammatone. A value unequal to zero results in a " "so called %gammachirp. A negative value is used in auditory filter modeling to " "guarantee the usual direction of filter asymmetry, which corresponds to an upward " "glide in instantaneous frequency.") TAG (L"##Scale amplitudes") DEFINITION (L"determines whether the amplitudes will be scaled to fit in the range (-1, 1).") ENTRY (L"Purpose") NORMAL (L"to create a Sound according to the following formula:") FORMULA (L"%t^^%\\ga\\--1^ e^^\\--2%\\pi\\.c%bandwidth\\.c%t^ " "cos (2%%\\pi\\.cfrequency\\.ct% + %additionFactor\\.cln(%t) + %initialPhase),") NORMAL (L"The %gammachirp function has a monotonically frequency-modulated carrier (the chirp) with " "instantaneous frequency ") FORMULA (L"%instantaneousFrequency(%t) = %frequency + %additionFactor / (2\\.c\\pi\\.c%t)") NORMAL (L"and an envelope that is a gamma distribution function. It is a theoretically optimum " "auditory filter, in the sense that it leads to minimal uncertainty in the joint time and " "scale representation of auditory signal analysis.") NORMAL (L"For faithful modelling of the inner ear, " "@@Irino & Patterson (1997)@ conclude that a value of approximately 1.5 * ERB (%frequency) " "is appropriate for %bandwidth. " "ERB stands for @@equivalent rectangular bandwidth@. Their formula for ERB is:") FORMULA (L"ERB(%f) = 6.23 10^^\\--6^ %f^2 + 93.39 10^^\\--3^ %f + 28.52.") NORMAL (L"To avoid @aliasing in the chirp sound, a sound is only generated during times where the " "instantaneous frequency is greater than zero and smaller than the @@Nyquist frequency@.") MAN_END MAN_BEGIN (L"Create Sound from Shepard tone...", L"djmw", 20050629) INTRO (L"One of the commands that create a @Sound.") ENTRY (L"Settings") TAG (L"##Name") DEFINITION (L"the name of the resulting Sound object.") TAG (L"##Minimum time (s)# and ##Maximum time (s)") DEFINITION (L"the start and end time of the resulting Sound.") TAG (L"##Sampling frequency (Hz)") DEFINITION (L"the @@sampling frequency@ of the resulting Sound.") TAG (L"##Lowest frequency (Hz)") DEFINITION (L"the frequency of the lowest component in the tone complex.") TAG (L"##Number of components") DEFINITION (L"the number of frequency components in the tone complex.") TAG (L"##Frequency change (semitones/s)") DEFINITION (L"determines how many semitones the frequency of each component will change in one second. " "The number of seconds needed to change one octave will then be 12 divided by ##Frequency change#. " "You can make rising, falling and monotonous tone complexes by chosing a positive, negative or zero value.") TAG (L"##Amplitude range% (dB)") DEFINITION (L"determines the relative size in decibels of the maximum and the minimum amplitude of the components in a tone complex. These relative amplitudes will then be 10^^\\--%amplitudeRange/20^. ") TAG (L"##Octave shift fraction (0-1)") DEFINITION (L"shifts all frequency components by this fraction at the start. You will probably only need this " "if you want to generate static tone complexes as the example script below shows.") ENTRY (L"Purpose") NORMAL (L"To create a Sound that is a continuous variant of the sound sequences " "used by @@Shepard (1964)@ in his " "experiment about the circularity in judgments of relative pitch.") NORMAL (L"The tone consists of many sinusoidal components whose frequencies " "might increase exponentially in time. " "All frequencies are always at successive intervals of an octave and sounded simultaneously. " "Thus the frequency of each component above the lowest is at each moment in time exactly twice " "the frequency of the one just below. The amplitudes are large for the components of intermediate " "frequency only, and tapered off gradually to subthreshold levels for the components at the " "highest and lowest extremes of frequency.") NORMAL (L"For a rising tone complex, the Sound is generated according to the following specification:") FORMULA (L"%s(%t) = \\su__%i=1..%numberOfComponents_ %A__%i_(%t) sin (arg__%i_(%t)), where") FORMULA (L"arg__%i_(%t) = \\in 2%\\pi f__%i_(%\\ta) %d\\ta , and") FORMULA (L"f__%i_(%t) = %lowestFrequency \\.c 2^^(%i \\-- 1 + octaveShiftFraction + %t/(12/%frequencyChange_st)^, with") FORMULA (L"%A__%i_(%t) = 10^^((%L__min_ + (%L__max_ \\-- %L__min_) (1 \\-- cos 2%\\pi%\\te__%i_(%t)) / 2) / 20)^, where,") FORMULA (L"%L__max_ = 0, %L__min_ = 10^^\\--%amplitudeRange/20^, and,") FORMULA (L"%\\te__%i_(%t) = 2\\pi log2 (%f(%t) / %lowestFrequency) / %numberOfComponents.") NORMAL (L"The maximum frequency that can be reached during a sweep by any single tone is:") FORMULA (L"%maximumFrequency = %lowestFrequency\\.c2^^%numberOfComponents^.") NORMAL (L"A component that reaches the maximum frequency falls instantaneously to the lowest frequency and then starts rising again.") NORMAL (L"The absolute @@sound pressure level@ of the resulting sound will not be set, it is only guaranteed that the peak value " "is just below 1. You can always scale the intensity with the ##Scale Intensity...# command.") ENTRY (L"Example") NORMAL (L"The following script generates 12 static Shepard tone complexes, 1 semitone 'apart', " "with a cosine window to temper the abrupt start and finish.") CODE (L"twin = 0.010") CODE (L"fwin = 1 / (2 * twin)") CODE (L"for i to 12") CODE1 (L"fraction = (i-1)/12") CODE1 (L"Create Sound from Shepard tone... s'i' 0 0.1 22050 4.863 10 0 34 'fraction'") CODE1 (L"Formula... if xxmax-twin then self*(1+cos(2*pi*fwin*(x-xmax+twin)))/2 else self fi") CODE (L"endfor") MAN_END MAN_BEGIN (L"Create formant table (Peterson & Barney 1952)", L"djmw", 20080509) INTRO (L"A command to create a @Table object filled with the " "fundamental frequency and the first three formant frequency values from 10 " "American-English monophthongal vowels as spoken in a /h_d/ context by 76 speakers " "(33 men, 28 women and 15 children). Every vowel was pronounced twice, so that there are " "1520 recorded vowels in total.") ENTRY (L"Table layout") NORMAL (L"The created table will contain 9 columns:") TAG (L"Column 1, labelled as %Type") DEFINITION (L"speaker type: \"m\", \"w\" or \"c\" (for %man, %women or %child).") TAG (L"Column 2, labelled as %Sex") DEFINITION (L"speaker sex: either \"m\" or \"f\" (for %male or %female).") TAG (L"Column 3, labelled as %Speaker") DEFINITION (L"speaker id: a number from 1 to 76.") TAG (L"Column 4, labelled as %Vowel") DEFINITION (L"the vowel name. The following list gives the vowel in a %h_d context word " "together with its representation in this column: (%heed, iy), (%hid, ih), " "(%head, eh), (%had, ae), (%hod, aa), (%hawed, ao), (%hood, uh), (%%who'd%, uw), " "(%hud, ah), (%heard, er).") TAG (L"Column 5, labelled as %IPA") DEFINITION (L"the IPA notation for the vowels as defined in @@Peterson & Barney (1952)@. ") TAG (L"Column 6, labelled as %F0") DEFINITION (L"the fundamental frequency in Hertz.") TAG (L"Column 7, 8 and 9, labelled as %F1, %F2 and %F3") DEFINITION (L"the frequencies in Hertz of the first three formants.") ENTRY (L"Remarks") NORMAL (L"We originally downloaded the data from the University of Pennsylvania FTP site, " "where they were reportedly based on a printed version supplied by Ignatius Mattingly. ") NORMAL (L"About the IPA notation. We used the original notation from the Peterson & Barney article. " "The notation in @@Watrous (1991)@ differs for three vowels: Watrous uses /e, o, \\er/ where Peterson & Barney use /\\ef, \\ct, \\er\\hr/.") NORMAL (L"More details about these data and how they were measured can be found in the articles" "@@Watrous (1991)@ and in @@Peterson & Barney (1952)@.") MAN_END MAN_BEGIN (L"Create formant table (Pols & Van Nierop 1973)", L"djmw", 20020620) INTRO (L"A command to create a @Table object filled with the frequencies and the levels " "of the first three formants from the 12 Dutch monophthong " "vowels as spoken in /h_t/ context by 50 male and 25 female speakers.") ENTRY (L"Table layout") NORMAL (L"The created table will contain 10 columns") TAG (L"Column 1, labeled as %Sex") DEFINITION (L"speaker sex: Either \"m\" or \"f\" (for %male or %female).") TAG (L"Column 2, labeled as %Speaker") DEFINITION (L"speaker id: a number from 1 to 75.") TAG (L"Column 3, labeled as %Vowel") DEFINITION (L"the vowel name. The following list gives the vowel in p_t context word " "together with its representation in this column: (%poet, oe), (%paat, aa), " "(%poot, oo), (%pat, a), (%peut, eu), (%piet, ie), (%puut, uu), (%peet, ee), " "(%put, u), (%pet, e), (%pot, o), (%pit, i).") TAG (L"Column 4, labeled as %IPA") DEFINITION (L"the IPA-notation for the vowels") TAG (L"Column 5, 6 and 7, labeled as %F1, %F2 and %F3") DEFINITION (L"the frequencies in Hertz of the first three formants.") TAG (L"Column 8, 9 and 10, labeled as %L1, %L2 and %L3") DEFINITION (L"the levels in decibel below overall SPL of the first three formants.") NORMAL (L"More details about these data and how they were measured can be found " "in @@Pols et al. (1973)@ and @@Van Nierop et al. (1973)@.") MAN_END MAN_BEGIN (L"Create formant table (Weenink 1985)", L"djmw", 20041217) INTRO (L"A command to create a @Table object filled with the " "fundamental frequency and the first three formant frequency values from 12 " "Dutch monophthongal vowels as spoken in isolation by 30 speakers " "(10 men, 10 women and 10 children). Every vowel was pronounced only once, so that there are " "360 recorded vowels in total. A reduced form, with only the formant frequecy values, is also available " "as a @@Create TableOfReal (Weenink 1985)...|TableOfReal@.") ENTRY (L"Table layout") NORMAL (L"The created table will contain 9 columns:") TAG (L"Column 1, labelled as %Type") DEFINITION (L"speaker type: \"m\", \"w\" or \"c\" (for %man, %women or %child).") TAG (L"Column 2, labelled as %Sex") DEFINITION (L"speaker sex: either \"m\" or \"f\" (for %male or %female).") TAG (L"Column 3, labelled as %Speaker") DEFINITION (L"speaker id: a number from 1 to 76.") TAG (L"Column 4, labelled as %Vowel") DEFINITION (L"the vowel name. The following list gives the vowel in Dutch p_t context words " "together with its representation in this column: (%poet, oe), (%paat, aa), " "(%poot, oo), (%pat, a), (%peut, eu), (%piet, ie), (%puut, uu), (%peet, ee), " "(%put, u), (%pet, e), (%pot, o), (%pit, i).") TAG (L"Column 5, labelled as %IPA") DEFINITION (L"the IPA notation for the vowels.") TAG (L"Column 6, labelled as %F0") DEFINITION (L"the fundamental frequency in Hertz.") TAG (L"Column 7, 8 and 9, labelled as %F1, %F2 and %F3") DEFINITION (L"the frequencies in Hertz of the first three formants. ") NORMAL (L"The formant frequency values have been determined by means of LPC analysis with a " "varying prediction order. See @@Weenink (1985)@.") MAN_END MAN_BEGIN (L"Create TableOfReal (Pols 1973)...", L"djmw", 19990426) INTRO (L"A command to create a @TableOfReal filled with the first three formant " "frequency values and (optionally) the levels from the 12 Dutch monophthongal " "vowels as spoken in /h_t/ context by 50 male speakers.") NORMAL (L"The first three columns will contain the frequencies in Hz, the next three columns " "the levels in decibels below the overall SPL of the measured vowel segment. Each row will " "be labelled with its corresponding vowel symbol.") NORMAL (L"More details about these data and how they were measured can be found in the paper of " "@@Pols et al. (1973)@.") MAN_END MAN_BEGIN (L"Create TableOfReal (Van Nierop 1973)...", L"djmw", 20041217) INTRO (L"A command to create a @TableOfReal filled with the first three formant " "frequency values and (optionally) the levels from the 12 Dutch monophthongal " "vowels as spoken in /h_t/ context by 25 female speakers.") NORMAL (L"The first three columns will contain the frequencies in Hz, the next three columns " "the levels in decibels below the overall SPL of the measured vowel segment. Each row will " "be labelled with its corresponding vowel symbol.") NORMAL (L"More details about these data and how they were measured can be found in the paper of " "@@Van Nierop et al. (1973)@.") MAN_END MAN_BEGIN (L"Create TableOfReal (Weenink 1985)...", L"djmw", 19990426) INTRO (L"A command to create a @TableOfReal filled with the first three formant " "frequency values from the 12 Dutch monophthongal " "vowels as spoken in isolation by either 10 men or 10 women or 10 children.") NORMAL (L"The three columns will contain the formant frequencies in Hz. Each row will " "be labelled with its corresponding vowel symbol.") NORMAL (L"More details about these data and how they were measured can be found in the paper of " "@@Weenink (1985)@.") MAN_END MAN_BEGIN (L"Discriminant", L"djmw", 19981103) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Discriminant represents the discriminant structure of a multivariate " "data set with several groups. This discriminant structure consists of a number of orthogonal " "directions in space, along which maximum separability of the groups can occur.") ENTRY (L"Commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@Discriminant analysis@ tutorial") LIST_ITEM (L"\\bu @@TableOfReal: To Discriminant@") NORMAL (L"Drawing") LIST_ITEM (L"\\bu Draw eigenvalues...") LIST_ITEM (L"\\bu Draw eigenvector...") LIST_ITEM (L"\\bu @@Discriminant: Draw sigma ellipses...|Draw sigma ellipses...@") MAN_END MAN_BEGIN (L"Discriminant analysis", L"djmw", 19990227) INTRO (L"This tutorial will show you how to perform discriminant analysis with P\\s{RAAT}") NORMAL (L"As an example, we will use the dataset from @@Pols et al. (1973)@ " "with the frequencies and levels of the first three formants from the 12 " "Dutch monophthongal vowels as spoken in /h_t/ context by 50 male speakers. " "This data set has been incorporated into " "Praat and can be called into play with the @@Create TableOfReal " "(Pols 1973)...@ command that can be found in the \"New / " "TableOfReal\" menu.") NORMAL (L"In the list of objects a new TableOfReal object will appear with 6 " "columns and 600 rows " "(50 speakers \\xx 12 vowels). The first three columns contain " "the formant frequencies in Hz, the last three columns contain the levels " "of the first three formants " "given in decibels below the overall sound pressure level of the measured " "vowel segment. Each row is labelled with a vowel label.") NORMAL (L"Pols et al. use logarithms of frequency values, we will too. Because " "the measurement units in the first three columns are in Hz and in the last " "three columns in dB, it is probably better to standardize the columns. " "The following script summarizes our achievements up till now:") CODE (L"Create TableOfReal (Pols 1973)... yes") CODE (L"Formula... if col < 4 then log10 (self) else self fi") CODE (L"Standardize columns") CODE (L"\\# change the column labels too, for nice plot labels.") CODE (L"Set column label (index)... 1 standardized log (\\% F\\_ \\_ 1\\_ )") CODE (L"Set column label (index)... 2 standardized log (\\% F\\_ \\_ 2\\_ )") CODE (L"Set column label (index)... 3 standardized log (\\% F\\_ \\_ 3\\_ )") CODE (L"Set column label (index)... 4 standardized \\% L\\_ \\_ 1\\_ ") CODE (L"Set column label (index)... 5 standardized \\% L\\_ \\_ 2\\_ ") CODE (L"Set column label (index)... 6 standardized \\% L\\_ \\_ 3\\_ ") NORMAL (L"To get an indication of what these data look like, we make a scatter " "plot of the " "first standardized log-formant-frequency against the second standardized " "log-formant-frequency. With the next script fragment you can reproduce the " "following picture.") CODE (L"Viewport... 0 5 0 5") CODE (L"select TableOfReal pols_50males") CODE (L"Draw scatter plot... 1 2 0 0 -2.9 2.9 -2.9 2.9 10 y + y") PICTURE (5, 5, drawPolsF1F2_log) NORMAL (L"Apart from a difference in scale this plot is the same as fig. 3 in the " "Pols et al. article.") ENTRY (L"1. How to perform a discriminant analysis") NORMAL (L"Select the TableOfReal and choose from the dynamic menu the option " "@@TableOfReal: To Discriminant|To Discriminant@. This command is available " "in the \"Multivariate statistics\" action button. The resulting Discriminant " "object will bear the same name as the TableOfReal object. The following " "script summarizes:") CODE (L"select TableOfReal pols_50males") CODE (L"To Discriminant") ENTRY (L"2. How to project data on the discriminant space") NORMAL (L"You select a TableOfReal and a Discriminant object together and choose: " "@@Discriminant & TableOfReal: To Configuration...|To Configuration...@. " "One of the options of the newly created Configuration object is to draw it. " "The following picture shows how the data look in the plane spanned by the " "first two dimensions of this Configuration. The directions in this " "configuration are the eigenvectors from the Discriminant.") PICTURE (5, 5, drawPolsDiscriminantConfiguration) NORMAL (L"The following script summarizes:") CODE (L"select TableOfReal pols_50males") CODE (L"plus Discriminant pols_50males") CODE (L"To Configuration... 0") CODE (L"Viewport... 0 5 0 5") CODE (L"Draw... 1 2 -2.9 2.9 -2.9 2.9 12 y + y") NORMAL (L"If you are only interested in this projection, there also is a short cut " "without an intermediate Discriminant object: " "select the TableOfReal object and choose @@TableOfReal: To Configuration " "(lda)...|To Configuration (lda)...@.") ENTRY (L"3. How to draw concentration ellipses") NORMAL (L"Select the Discriminant object and choose @@Discriminant: Draw sigma " "ellipses...|Draw sigma ellipses...@. In the form you can fill out the " "coverage of the ellipse by way of the %%Number of sigmas% parameter. " "You can also select the projection " "plane. The next figure shows the 1-%\\si concentration ellipses in the " "standardized log %F__1_ vs log %F__2_ plane. When the data are multinormally distributed, " "a 1-%\\si ellipse will cover approximately 39.3\\% of the data. " "The following code summarizes:") CODE (L"select Discriminant pols_50males") CODE (L"Draw sigma ellipses... 1.0 no 1 2 -2.9 2.9 -2.9 2.9 12 yes") PICTURE (5, 5, drawPolsF1F2ConcentrationEllipses) ENTRY (L"4. How to classify") NORMAL (L"Select together the Discriminant object (the classifier), and " "a TableOfReal object (the data to be classified). Next you choose " "@@Discriminant & TableOfReal: To ClassificationTable...|To " "ClassificationTable@. " "Normally you will enable the option %%Pool covariance matrices% and " "the pooled covariance matrix will be used for classification.") NORMAL (L"The ClassificationTable can be converted to a @Confusion object " "and its fraction correct can be queried with: " "@@Confusion: Get fraction correct@.") NORMAL (L"In general you would separate your data into two independent sets, " "\\s{TRAIN} and \\s{TEST}. You would use \\s{TRAIN} to train the " "discriminant classifier and \\s{TEST} to test how well it classifies. " "Several possibilities for splitting a dataset into two sets exist. " "We mention the @@Jackknife|jackknife@ (\"leave-one-out\") and the " "@@Bootstrap|bootstrap@ methods (\"resampling\").") MAN_END MAN_BEGIN (L"Discriminant: Draw sigma ellipses...", L"djmw", 20040407) INTRO (L"A command to draw for each group from the selected @Discriminant an ellipse " "that covers part of the multivariate data.") ENTRY (L"Settings") TAG (L"##Number of sigmas") DEFINITION (L"determines the @@concentration ellipse|data coverage@.") TAG (L"##Discriminant plane") DEFINITION (L"When on, the selected %X and %Y-dimension will refer to the eigenvectors " "of the discriminant space, and, consequently, the projection of the hyper ellipsoid " "onto the space spanned by these eigenvectors will be drawn. When off, the selected " "%X and Y-dimension will refer to the original dimensions.") TAG (L"##Xmin#, ##Xmax#, ##Ymin#, ##Ymax#") DEFINITION (L"determine the limits of the drawing area.") TAG (L"##Label size") DEFINITION (L"determines the size of the labels at the centre of the ellipse. No " "labels will be drawn when a value less than or equal to zero is chosen.") MAN_END MAN_BEGIN (L"Discriminant: Extract within-group SSCP...", L"djmw", 20020314) INTRO (L"Extract the @SSCP for group %%index% from the selected @Discriminant " "object.") MAN_END MAN_BEGIN (L"Discriminant: Extract pooled within-groups SSCP", L"djmw", 20020314) INTRO (L"Extract the pooled within-group @SSCP from the selected @Discriminant " "object.") MAN_END MAN_BEGIN (L"Discriminant: Get partial discrimination probability...", L"djmw", 19981102) INTRO (L"A command to test the selected @Discriminant for the significance of " "discrimination afforded by the remaining %n\\--%k eigenvectors after the acceptance of " "the first %k eigenvectors.") ENTRY (L"Details") NORMAL (L"The test statistic is:") FORMULA (L"%\\ci^2 = \\--(%degreesOfFreedom\\--(%numberOfGroups+%dimension)/2) ln \\La\\'p, where") FORMULA (L"%degreesOfFreedom = (%dimension\\--%k)(%numberOfGroups\\--%k\\--1), and, ") FORMULA (L"\\La\\'p = \\Pi__%j=%k+1..%numberOfEigenvalues_ 1 / (1 + %%eigenvalue[j]%)") MAN_END MAN_BEGIN (L"Discriminant: Get contribution of component...", L"djmw", 19981106) INTRO (L"A command to ask the selected @Discriminant for the contribution of the %j^^th^ " "discriminant function (component) to the total variance.") ENTRY (L"Details") NORMAL (L"The contribution is defined as:") FORMULA (L"%%eigenvalue[j]% / \\Si__%i=1..%numberOfEigenvalues_ %%eigenvalue[i]%") MAN_END MAN_BEGIN (L"Discriminant: Get Wilks' lambda...", L"djmw", 20040407) INTRO (L"A command to ask the selected @Discriminant for the value of Wilks' lamda (a " "multivariate measure of group differences over several variables).") ENTRY (L"Settings") TAG (L"##From") DEFINITION (L"the first eigenvalue number from which the value for lambda has to be calculated.") ENTRY (L"Details") NORMAL (L"Wilks' lambda is defined as:") FORMULA (L"%\\La = \\Pi__%i=%from..%numberOfEigenvalues_ 1 / (1 + %eigenvalue[%i])") NORMAL (L"Because lambda is a kind of %inverse measure, values of lambda which are near zero " "denote high discrimination between groups.") MAN_END MAN_BEGIN (L"Discriminant: Get concentration ellipse area...", L"djmw", 20040407) INTRO (L"A command to query the @Discriminant object for the area of the concentration " "ellipse of one of its groups.") ENTRY (L"Settings") TAG (L"##Number of sigmas") DEFINITION (L"determines the @@concentration ellipse|data coverage@.") TAG (L"##Discriminant plane") DEFINITION (L"When on, the selected %X and %Y-dimension will refer to the eigenvectors " "of the discriminant space, and, consequently, the area of the projection of the hyper ellipsoid " "onto the space spanned by these eigenvectors will be calculated. When off, the selected " "%X and Y-dimension will refer to the original dimensions.") ENTRY (L"Algorithm") NORMAL (L"See @@SSCP: Get sigma ellipse area...") MAN_END MAN_BEGIN (L"Discriminant: Get confidence ellipse area...", L"djmw", 20040407) INTRO (L"A command to query the @Discriminant object for the area of the confidence " "ellipse of one of its groups.") ENTRY (L"Settings") TAG (L"##Discriminant plane") DEFINITION (L"When on, the selected %X and %Y-dimension will refer to the eigenvectors " "of the discriminant space, and, consequently, the area of the projection of the hyper ellipsoid " "onto the space spanned by these eigenvectors will be calculated. When off, the selected " "%X and Y-dimension will refer to the original dimensions.") ENTRY (L"Algorithm") NORMAL (L"See @@SSCP: Get confidence ellipse area...") MAN_END MAN_BEGIN (L"Discriminant & Pattern: To Categories...", L"djmw", 20040422) INTRO (L"A command to use the selected @Discriminant to classify each pattern from the " "selected @Pattern into a category.") NORMAL (L"Arguments as in @@Discriminant & TableOfReal: To ClassificationTable...@.") MAN_END MAN_BEGIN (L"Discriminant & SSCP: Project", L"djmw", 20020313) INTRO (L"A command to project the selected @SSCP object on the eigenspace " "defined by the selected @Discriminant object.") NORMAL (L"Further details can be found in @@Eigen & SSCP: Project@") MAN_END MAN_BEGIN (L"Discriminant & TableOfReal: To ClassificationTable...", L"djmw", 20040407) INTRO (L"A command to use the selected @Discriminant to classify each row from the " "selected @TableOfReal. The newly created @ClassificationTable will then contain the posterior " "probabilities of group membership.") ENTRY (L"Settings") TAG (L"##Pool covariance matrices") DEFINITION (L"when on, all group covariance matrices are pooled and distances will be determined " "on the basis of only this pooled covariance matrix (see below).") ENTRY (L"Details") NORMAL (L"The posterior probabilities of group membership %p__%j_ for a vector #x are defined as:") FORMULA (L"%p__%j_ = %p(%j\\| #%x) = exp (\\--%d__%j_^^2^(#%x) / 2) / " "\\su__%k=1..%numberOfGroups_ exp (\\--%d__%k_^^2^(#%x) / 2),") NORMAL (L"where %d__%i_^^2^ is the generalized squared distance function:") FORMULA (L"%d__%i_^^2^(#%x) = ((#%x\\--#%\\mu__%i_)\\'p #\\Si__%i_^^-1^ (#%x\\--#%\\mu__%i_) + " "ln determinant (#\\Si__%i_)) / 2 \\-- ln %aprioriProbability__%i_") NORMAL (L"that depends on the individual covariance matrix #\\Si__%i_ and the mean " "#%\\mu__%i_ for group %i.") NORMAL (L"When the covariances matrices are %pooled, the squared distance function can be reduced to:") FORMULA (L"%d__%i_^^2^(#%x) = ((#%x\\--#%\\mu__%i_)\\'p #\\Si^^-1^ (#%x\\--#%\\mu__%i_) " "\\-- ln %aprioriProbability__%i_,") NORMAL (L"and #\\Si is now the pooled covariance matrix.") NORMAL (L"The a priori probabilities normally will have values that are related to the number of " "%training vectors %n__%i_ in each group:") FORMULA (L"%aprioriProbability__%i_ = %n__%i_ / \\Si__%k=1..%numberOfGroups_ %n__%k_") MAN_END MAN_BEGIN (L"Discriminant & TableOfReal: To Configuration...", L"djmw", 20040407) INTRO (L"A command to project each row in the selected @TableOfReal onto " "a space spanned by the eigenvectors of the selected @Discriminant. ") ENTRY (L"Settings") TAG (L"##Number of dimensions") DEFINITION (L"specifies the number of eigenvectors taken into account, i.e., determines " "the dimension of the resulting @Configuration. When the default value (0) is " "given the resulting Configuration will have the maximum dimension as allowed by " "the number of eigenvectors in the selected Discriminant.") ENTRY (L"Precondition") NORMAL (L"The number of columns in the TableOfReal must equal the dimension of the " "eigenvectors in the Discriminant.") NORMAL (L"See also @@Eigen & TableOfReal: Project...@.") MAN_END MAN_BEGIN (L"Discriminant & TableOfReal: To TableOfReal (mahalanobis)...", L"djmw", 20100107) INTRO (L"Calculate Mahalanobis distances for the selected @TableOfReal with respect to one group in the " "selected @Discriminant object.") ENTRY (L"Settings") TAG (L"##Group label") DEFINITION (L"defines which group mean to use for the distance calculation.") TAG (L"##Pool covariance matrices") DEFINITION (L"when on use a pooled covariance matrix instead of the group covariance matrix.") ENTRY (L"Algorithm") NORMAL (L"See @@Covariance & TableOfReal: To TableOfReal (mahalanobis)...@.") ENTRY (L"Example") NORMAL (L"Calculate the number of datapoints that are within the one-sigma elipses of two different groups, i.e. " "the number of data points that are in the overlapping area. ") NORMAL (L"Suppose the group labels are \\o/ and \\yc.") CODE (L"t = Create TableOfReal (Pols 1973)... no") CODE (L"Formula... log10(self)") CODE (L"d = To Discriminant") CODE (L"select t") CODE (L"plus d") CODE (L"t1 = To TableOfReal (mahalanobis)... \\bso/ no") CODE (L"select t") CODE (L"plus d") CODE (L"t2 = To TableOfReal (mahalanobis)... \\bsyc no") NORMAL (L"Now we count when both the t1 and t2 values are smaller than 1 (sigma):") CODE (L"Copy... tr") CODE (L"Formula... Object_'t1'[] < 1 and Object_'t2'[] < 1") CODE (L"Extract rows where column... 1 \"equal to\" 1") CODE (L"no = Get number of rows") MAN_END MAN_BEGIN (L"DTW", L"djmw", 20110603) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type DTW represents the dynamic time warp structure of " "two objects.") ENTRY (L"Commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@CC: To DTW...@ (from 2 objects with cepstral coefficients)") LIST_ITEM (L"\\bu ##Spectrogram: To DTW...# (from 2 Spectrogram objects)") NORMAL (L"Query:") LIST_ITEM (L"\\bu @@DTW: Get y time from x time...@") LIST_ITEM (L"\\bu @@DTW: Get x time from y time...@") MAN_END MAN_BEGIN (L"DTW: Draw warp (x)...", L"djmw", 20071204) INTRO (L"Draws the warp given a time on the \"x-direction\"") MAN_END MAN_BEGIN (L"DTW: Find path (band & slope)...", L"djmw", 20120223) INTRO (L"Finds the optimal path for the selected @DTW that lies within the union of the sakoe-chiba band and local slope limits.") ENTRY (L"Settings") TAG (L"##Sakoe-Chiba band (s)#,") DEFINITION (L"The maximum distance from the start/end of the sound where a path may start/finish.") TAG (L"##Slope constraint#,") DEFINITION (L"determines the maximum and minimum local slopes in the optimal path. For example, the constraint " "1/3 < slope < 3 forces the path locally after having taken three steps in the same direction direction to take the next step in the other direction, or after having taken two steps in the same direction to take the next step in the diagonal direction. At the same time the global consequences of the \"1/3 < slope < 3\" constraint mandates that the durations of the two domains do not differ by more than a factor of three. ") NORMAL (L"For more information see the article of @@Sakoe & Chiba (1978)@.") MAN_END MAN_BEGIN (L"DTW: Get maximum consecutive steps...", L"djmw", 20050307) INTRO (L"Get the maximum number of consecutive steps in the chosen direction along the optimal path from the selected @DTW.") MAN_END MAN_BEGIN (L"DTW: Get distance (weighted)", L"djmw", 20100628) INTRO (L"Queries the selected @DTW object for the weighted distance along the minimum path.") ENTRY (L"Algorithm") NORMAL (L"If the distance matrix has %%nx% cells along the %%x%-direction, %%ny% cells along the %%y%-direction and the " "sum of the distances along the minimum path is %%S%, the weighted distance is given by %%S%/(%nx+%ny). ") MAN_END MAN_BEGIN (L"DTW: Get time along path...", L"djmw", 20110603) INTRO (L"Queries the selected @DTW object for the time along the minimal path " "given the time along the \"%x-direction\". This command is deprecated, the new commands for querying are " "@@DTW: Get y time from x time...@ and @@DTW: Get x time from y time...@.") ENTRY (L"Setting") TAG (L"##Time (s)") DEFINITION (L"the time along the %x-direction.") ENTRY (L"Behaviour") NORMAL (L"When the %input time is in the interval [%xmin, %xmax], the %returned " "time will be in the interval [%ymin, %ymax], where [%xmin, %xmax] and " "[%ymin, %ymax] are the domains of the two \"objects\" from which the " "DTW-object was constructed." "For all other input times we assume that the two object are aligned.") NORMAL (L"We like to have a \"continuous\" interpretation of time for the quantized times in the %x and " "%y direction; we make the path piecewise linear. There are two special cases:") NORMAL (L"1. The local path is horizontal. We calculate the %y-time from the line that connects the " "lower-left position of the leftmost horizontal time block to the upper-right position of the " "rightmost horizontal time block.") NORMAL (L"2. The local path is vertical. We calculate the %y-time from the line that connects the " "lower-left position of the bottommost vertical time block to the upper-right position of the " "topmost horizontal time block.") MAN_END MAN_BEGIN (L"DTW: Get y time from x time...", L"djmw", 20110603) INTRO (L"Queries the selected @DTW object for the time along the %y-direction " "given the time along the \"%x-direction\". ") ENTRY (L"Setting") TAG (L"##Time (s)") DEFINITION (L"the time along the %x-direction.") ENTRY (L"Behaviour") NORMAL (L"When the %input time is in the interval [%xmin, %xmax], the %returned " "time will be in the interval [%ymin, %ymax], where [%xmin, %xmax] and " "[%ymin, %ymax] are the domains of the two \"objects\" from which the " "DTW-object was constructed." "For input times outside the domain we assume that the two object were aligned.") NORMAL (L"We like to have a \"continuous\" interpretation of time for the quantized times in the %x and " "%y direction; we make the path a piecewise linear monotonically increasing function. " "There are special cases:") NORMAL (L"1. The local path is in the %x-direction only. We calculate the %y-time from the line " "that connects the lower-left position of the begin cell of this path to the " "upper-right position of the last cell.") NORMAL (L"2. The local path is in the x-direction only. We calculate the %y-time from the line " "that connects the lower-left position of lowest cell to the upper-right position of the " "highest cell.") NORMAL (L"3. A cell is both part of a path in the %x- and the %y-direction. " "We then calculate the intersection point of the paths in the %x- and the %y-directions. " "The %y-times in this cell are now calculated from the two line segments that originate " "from this intersection point.") MAN_END MAN_BEGIN (L"DTW: Get x time from y time...", L"djmw", 20110603) INTRO (L"Queries the selected @DTW object for the time along the %x-direction " "given the time along the \"%y-direction\". ") ENTRY (L"Setting") TAG (L"##Time (s)") DEFINITION (L"the time along the %y-direction.") ENTRY (L"Behaviour") NORMAL (L"The behaviour is like @@DTW: Get y time from x time...@") MAN_END MAN_BEGIN (L"DTW: Swap axes", L"djmw", 20050306) INTRO (L"Swap the x and y-axes of the selected @DTW.") MAN_END MAN_BEGIN (L"DTW: To Polygon...", L"djmw", 20120223) INTRO (L"A command to convert for a selected @DTW the Sakoe-Chiba band and the local slope constraint " "to a @Polygon object. The polygon will show the boundaries of the search domain for the optimal path.") MAN_END MAN_BEGIN (L"DTW & TextGrid: To TextGrid (warp times)", L"djmw", 20110603) INTRO (L"Create a new TextGrid from the selected @DTW and @TextGrid by warping the " "times from the selected TextGrid to the newly created TextGrid.") ENTRY (L"Algorithm") NORMAL (L"First we check whether the y-domain of the DTW and the domain of the TextGrid are " "equal. If they are, a new TextGrid is created by copying the selected one. " "We then change its domain and make it equal to the x-domain of the DTW. " "Then for each tier we change the domain and @@DTW: Get x time from y time...|calculate new times@ by using the path.") MAN_END MAN_BEGIN (L"DTW & Sounds: Draw...", L"djmw", 20071204) INTRO (L"Draws the distances, the path and the sounds for the selected @DTW and the two selected @@Sound|Sounds@.") MAN_END MAN_BEGIN (L"DTW & Sounds: Draw warp (x)...", L"djmw", 20071204) INTRO (L"Draws the warp given a time on the \"x-direction\" for the selected @DTW and the two selected @@Sound|Sounds@.") MAN_END MAN_BEGIN (L"EditCostsTable", L"djmw", 20120522) INTRO (L"One of the @@types of objects@ in Praat.") NORMAL (L"The EditCostsTable shows the costs involved in changing one string of symbols into another one, the so called %%string edit costs%. These costs are generally divided into %%insertion%, %%deletion% and %%substitution% costs. An EditCostsTable is used to calculated the @@EditDistanceTable@. ") NORMAL (L"The most simple EditCostsTable has two rows and two columns only, and the cells in this table have the following interpretation:\n") TAG (L"Cell [1][1]:") DEFINITION (L"defines the cost of the substitution of a source symbol with a target symbol that doesn't match it. A good default value for the substitution cost is 2.0.") TAG (L"Cell [1][2]:") DEFINITION (L"defines the cost of the insertion of a target symbol in the source string. A good default value is 1.0.") TAG (L"Cell [2][1]:") DEFINITION (L"defines the cost of the deletion of a source symbol. A good default value is 1.0.") TAG (L"Cell [2][2]:") DEFINITION (L"defines the cost of substitution a source symbol with a target symbol that matches it. A good default is 0.0.") NORMAL (L"In general we can define a table for %%numberOfTargets% target symbols and %%numberOfSources% source symbols. The EditCostTable will need one extra dimensions to accommodate target symbol insertion costs and source symbol deletion costs and another extra dimension to represent other target and source symbols that don't have separate entries and can therefore be treated as one group. The dimension of the table will then be (%%numberOfTargets% + 2) \\xx (%%numberOfSources% + 2). The %%numberOfTargets% \\xx %%numberOfSources% part will show at cell [%i][%j] the costs of substitution of the %j-th source symbol by the %i-th target symbol. The values in row (%%numberOfTargets% + 1) represent the costs of substitution of the %j-th source symbol with one of the target from the rest category (this is the group of targets that do not belong to the %%numberOfTargets% targets represented in the upper part of the matrix). The first %%numberOfSources% cells in the last row represent the deletion cost of these symbols. The first %%numberOfTargets% cells in the last column represent the insertion costs of the corresponding target symbols. ") NORMAL (L"We can extend this minimal table with more rows and columns. Let us assume that we extend it by one target and one source symbol, \"t1\" and \"s1\", respectively. The EditCostTable will then be a 3 by 3 table:") CODE (L" s1 ") CODE (L"t1 1.1 1.2 1.3") CODE (L" 1.4 1.5 1.6") CODE (L" 1.7 1.8 0.0") NORMAL (L"The table has one labeled column: the first column is labeled with source symbol \"s1\". The first row is also labeled with the target symbol \"t1\". The numbers in the table have been to be distinctive and do probably not correspond to any practical situation. The table says that substitution of source symbol \"s1\" with target symbol \"t1\" costs 1.1, while the substitution of \"s1\" with any other target symbol costs 1.4. The substitution of any other source symbol by target \"t1\" costs 1.2 while the substitution with any othe target symbol costs 1.5 if they don't match and 0.0 if they match. The deletion costs of \"s1\" are 1.7 while the deletion cost of all other source symbols is 1.8. The insertion cost of \"t1\" is 1.3 while the other target symbols can be inserted with a cost of 1.6.") MAN_END MAN_BEGIN (L"EditDistanceTable", L"djmw", 20120523) INTRO (L"One of the @@types of objects@ in Praat.") NORMAL (L"An EditDistanceTable shows the accumulated distances between a target string and a sources string. " "For example, the accumulated distances between the target string \"intention\" and the source string " "\"execution\" can be expressed by the following EditDistanceTable:") SCRIPT (4, 4, L"target = Create Strings as characters... intention\n" "source = Create Strings as characters... execution\n" "plus target\n" "edt = To EditDistanceTable\n" "Draw... rational 1 0\n" "plus target\n" "plus source\n" "Remove\n") NORMAL (L"The target string is always displayed vertically while the source string is displayed horizontally and the origin is at the bottom-left corner of the table. Each cell of this table, dist[%i, %j], contains the accumulated distance between the first %i characters " "of the target and the first %j characters of the source. The cells on the path through this table which have the " "minimum accumulated cost are shown with boxes around them. Below we will explain how this path is calculated.") NORMAL (L"The local directional steps in this path show which %%edit operations% we have to perform on the source string symbols to obtain the target string symbols. Three edit operations exist: (1) %%insertion% of a target symbol in the source string. This happens each time we take a step in the vertical direction along the path. (2) %%deletion% of a symbol in the source string. This happens each time we take a step in horizontal direction along the path. (3) %%substitution% of a source symbol by a target symbol happens at each diagonal step along the path.") NORMAL (L"If we trace the path from its start at the origin to its end, we see that it first moves up, indicating the insertion of an \"i\" symbol in the source string. In the next step which is in the diagonal direction, the \"n\" target is substituted for the \"e\" source symbol. Next follows another substitution, \"t\" for \"x\". The next diagonal step substitutes \"e\" for an identical \"e\". This step is followed by a horizontal step in which the source symbol \"c\" is deleted. The next diagonal step substitutes an \"n\" for a \"u\". The path now continues in the diagonal direction until the end point and only identical substitutions occur in the last part. The following figure shows these operations more explicitly.") SCRIPT (4, 1.5, L"target = Create Strings as characters... intention\n" "source = Create Strings as characters... execution\n" "plus target\n" "edt = To EditDistanceTable\n" "Draw edit operations\n" "plus target\n" "plus source\n" "Remove\n") NORMAL (L"The value of the accumulated costs in a cell of the table is computed by taking the minimum of the accumulated distances from three possible paths that end in the current cell, i.e. the paths that come from the %%left%, from the %%diagonal% and from %%below%.") CODE (L"dist[i,j] = min (d__left_, d__diag_, d__below_), ") NORMAL (L"where ") CODE (L" d__left _ = dist[i-1,j] + insertionCost(target[i])") CODE (L" d__diag _ = dist[i-1,j-1] + substitutionCost(source[j],target[i])") CODE (L" d__below_ = dist[i,j-1] + deletionCost(source[j])") NORMAL (L"Since the calculation is recursive we start at the origin. After calculating the accumulative distances for each cell in the table as based on the algorithm above, the cell at the top-right position will contain the accumulated edit distance. This distance happens to be 8 for the given example. The value 8 results from using the target-indepent value of 1.0 for the insertion cost, the source-independent value of 1.0 for the deletion costs and a constant value of 2.0 for the substitution costs. If target and source symbol happen to be equal no costs are assigned, or, equivalently the substitution costs are zero if target and source symbol match. If you want more control over these costs you can create an @@EditCostsTable@ and specify your special costs and then @@EditDistanceTable & EditCostsTable: Set new edit costs|set the new edit costs@.") NORMAL (L"If during the calculations we also keep track of which of the three cells resulted in the local minimum accumulated distance, we can use this directional " "information to backtrack from the cell at the top-right position to the cell at the bottom-right position and obtain the minimum path.") MAN_END MAN_BEGIN (L"EditDistanceTable & EditCostsTable: Set new edit costs", L"djmw", 20120522) INTRO (L"A command available in the dynamic menu if an @@EditDistanceTable@ and an @@EditCostsTable@ are chosen together.") NORMAL (L"New accumulated cost values will be calculated and a new path based on these values will be calculated.") MAN_END MAN_BEGIN (L"Eigen", L"djmw", 19981102) INTRO (L"One of the @@types of objects@ in Praat.") NORMAL (L"An object of type Eigen represents the eigen structure of " "a matrix whose eigenvalues and eigenvectors are real.") ENTRY (L"Inside an Eigen") NORMAL (L"With @Inspect you will see the following attributes:") TAG (L"%numberOfEigenvalues") DEFINITION (L"the number of eigenvalues and eigenvectors") TAG (L"%dimension") DEFINITION (L"the dimension of an eigenvector.") TAG (L"%eigenvalues[1..%numberOfEigenvalues]") DEFINITION (L"the real eigenvalues.") TAG (L"%eigenvectors[1..%numberOfEigenvalues][1..%dimension]") DEFINITION (L"the real eigenvectors, stored by row.") MAN_END MAN_BEGIN (L"Eigen: Draw eigenvalues...", L"djmw", 20040407) INTRO (L"A command to draw the eigenvalues of the selected @Eigen object(s).") ENTRY (L"Settings") TAG (L"##Fraction of eigenvalues summed") DEFINITION (L"defines whether or not fractions are plotted. Fractions %f__%i_ " "will be calculated for each number %e__%i_ by dividing this number by the sum of all " "numbers %e__%j_: %f__%i_ = %e__%i_ / \\su__%j=1..%numberOfEigenvalues_ %e__%j_.") TAG (L"##Cumulative") DEFINITION (L"defines whether or not cumulative values are plotted. Cumulative " "values %c__%i_ will be calculated for each number %e__%i_ by summing the first %i " "numbers %e__%j_: %c__%i_ = \\su__%j=1..%i_ %e__%j_).") NORMAL (L"A @@Scree plot|scree@ plot can be obtained if both %%Fraction of eigenvalues summed% " "and %%Cumulative% are unchecked.") MAN_END MAN_BEGIN (L"Eigen: Draw eigenvector...", L"djmw", 20040407) INTRO (L"A command to draw an eigenvector from the selected @Eigen.") ENTRY (L"Settings") TAG (L"##Eigenvector number") DEFINITION (L"determines the eigenvector to be drawn.") TAG (L"%Component %loadings") DEFINITION (L"when on, the eigenvector is multiplied with the square root of the corresponding " "eigenvalue. (For @@PCA@-analysis this means that you will draw the so called " "%%component loading vector%. You will be able to compare " "quantitatively the elements in different component loading vectors because " "the %i-th element in the %j-th component loading vector gives the covariance between the %i-th " "original variable and the %j-th principal component.)") TAG (L"##Element rang%") DEFINITION (L"determine the first and last element of the vector that must be drawn.") TAG (L"##Minimum# and ##Maximum#") DEFINITION (L"determine the lower and upper bounds of the plot (choosing #Maximum smaller than #Minimum " "will draw the %%inverted% eigenvector). ") TAG (L"##Mark size#, ##Mark string#") DEFINITION (L"determine size and type of the marks that will be drawn.") TAG (L"##Garnish") DEFINITION (L"determines whether a bounding box and margins will be drawn.") MAN_END MAN_BEGIN (L"Eigen: Get contribution of component...", L"djmw", 19981109) INTRO (L"A command to ask the selected @Eigen for the contribution of the %j^^th^ " "eigenvalue to the total sum of eigenvalues.") ENTRY (L"Details") NORMAL (L"The contribution is defined as:") FORMULA (L"%%eigenvalue[j]% / \\Si__%i=1..%numberOfEigenvalues_ %%eigenvalue[i]%") MAN_END MAN_BEGIN (L"Eigen: Get cumulative contribution of components...", L"djmw", 19981109) INTRO (L"A command to ask the selected @Eigen for the contribution of the sum of the " "eigenvalues[%from..%to] to the total sum of eigenvalues.") ENTRY (L"Details") NORMAL (L"The contribution is defined as:") FORMULA (L"\\Si__%i=%from..%to_ %%eigenvalue[i]% / \\Si__%i=1..%numberOfEigenvalues_ %%eigenvalue[i]%") MAN_END MAN_BEGIN (L"Eigen: Get eigenvalue...", L"djmw", 20040225) INTRO (L"A command to query the selected @Eigen for the %i^^th^ " "eigenvalue.") MAN_END MAN_BEGIN (L"Eigen: Get eigenvector element...", L"djmw", 20040225) INTRO (L"A command to query the selected @Eigen for the %j^^th^ element of the " "%i^^th^ eigenvector.") MAN_END MAN_BEGIN (L"Eigen & Matrix: Project...", L"djmw", 20040407) INTRO (L"A command to project the columns of the @Matrix object onto the " "eigenspace of the @Eigen object.") ENTRY (L"Setting") TAG (L"##Number of dimensions") DEFINITION (L"defines the dimension, i.e., the number of rows, of the " "resulting object.") ENTRY (L"Algorithm") NORMAL (L"Project each column of the Matrix on the coordinate " "system given by the eigenvectors of the Eigen object. This can be done " "as follows:") FORMULA (L"%y__%ji_ = \\Si__%k=1..%numberOfColums_ %e__jk_ %x__%ki_, where") NORMAL (L"%y__%ji_ is the %j-th element of the %i-th column of the resulting " "(matrix) object, %e__%jk_ is the %k-th element of the %j-th eigenvector " "and, %x__%ki_ is the %k-th element of the %i-th column of the selected " "matrix object.") MAN_END MAN_BEGIN (L"Eigen & SSCP: Project", L"djmw", 20020328) INTRO (L"A command to project the @SSCP object onto the eigenspace of " "the @Eigen object.") ENTRY (L"Behaviour") NORMAL (L"Transform the SSCP object as if it was calculated in a coordinate " "system given by the eigenvectors of the Eigen object. This can be done " "as follows:") FORMULA (L"#%S__%t_ = #%E\\'p #%S #%E, where") NORMAL (L"where #%E\\'p is the transpose of the matrix with eigenvectors #%E, " "#%S is the square matrix with sums of squares and crossproducts, and " "#%S__%t_ the newly created square matrix. The dimension of #%S__%t_ may " "be smaller than the dimension of #%S.") MAN_END MAN_BEGIN (L"Eigen & TableOfReal: Project...", L"djmw", 20040407) INTRO (L"A command to project the rows of the @TableOfReal object onto the " "eigenspace of the @Eigen object.") ENTRY (L"Setting") TAG (L"##Number of dimensions") DEFINITION (L"defines the number of dimensions, i.e., the number of columns, of the " "resulting object.") ENTRY (L"Algorithm") NORMAL (L"Project each row of the TableOfReal on the coordinate " "system given by the eigenvectors of the Eigen object. This can be done " "as follows:") FORMULA (L"%y__%ij_ = \\Si__%k=1..%numberOfColums_ %e__jk_ %x__%ik_, where") NORMAL (L"%e__%jk_ is the %k-th element of the %j-th eigenvector, %x__%ik_ is " "the %k-th element of the %i-th row and %y__%ij_ is the %j-th element at " "the %i-th row of the matrix part of the resulting object.") MAN_END MAN_BEGIN (L"equivalent rectangular bandwidth", L"djmw", 19980713) INTRO (L"The %%equivalent rectangular bandwidth% (ERB) of a filter is defined " "as the width of a rectangular filter whose height equals the peak gain of " "the filter and which passes the same total power as the filter (given a flat " "spectrum input such as white noise or an impulse).") MAN_END MAN_BEGIN (L"Excitations", L"djmw", 19960918) INTRO (L"A collection of objects of type @Excitation. " "You can create an #Excitations by selecting one or more #Excitation's and " "selecting ##To Excitations#. You can add one or more #Excitation's to an " "#Excitations by selecting one #Excitations and one or more " "#Excitation's and selecting ##Add to Excitations# (the #Excitation's will " "be removed from the list of objects).") MAN_END MAN_BEGIN (L"Excitations: Append", L"djmw", 19960918) INTRO (L"You can choose this command after selecting two objects of type @Excitations. ") NORMAL (L"A new object is created that contains the second object appended after the first.") MAN_END MAN_BEGIN (L"Excitations: To Pattern...", L"djmw", 19960918) INTRO (L"A command to convert every selected @Excitations to a @Pattern object.") ENTRY (L"Setting") TAG (L"##Join") DEFINITION (L"the number of subsequent @Excitation objects to combine into one row of @Pattern. " "E.g. if an #Excitation has length 26 and %join = 2 then each row of #Pattern " "contains 52 elements. The number of rows in #Pattern will be %%my size% / 2. " "In the conversion process the elements of an #Excitation will be divided by 100.0 in order " "to guarantee that all patterns have values between 0 and 1.") MAN_END MAN_BEGIN (L"FilterBank: Draw filter functions...", L"djmw", 20030901) INTRO (L"") MAN_END MAN_BEGIN (L"FilterBank: Draw frequency scales...", L"djmw", 20030901) MAN_END MAN_BEGIN (L"FilterBank: Get frequency in Hertz...", L"djmw", 20030901) INTRO (L"A @query to the selected FilterBank object.") ENTRY (L"Return value") NORMAL (L"a frequency value in Hertz.") MAN_END MAN_BEGIN (L"FilterBank: Get frequency in Bark...", L"djmw", 20030901) MAN_END MAN_BEGIN (L"FilterBank: Get frequency in mel...", L"djmw", 20030901) MAN_END MAN_BEGIN (L"FormantFilter", L"djmw", 20010404) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type FormantFilter represents an acoustic time-frequency " "representation of a sound: the power spectral density %P(%f, %t), expressed " "in dB's. " "It is sampled into a number of points around equally spaced times %t__%i_ " "and frequencies %f__%j_ (on a linear frequency scale).") ENTRY (L"Inside a FormantFilter") NORMAL (L"With @Inspect you will see that this type contains the same " "attributes a @Matrix.") MAN_END MAN_BEGIN (L"gammatone", L"djmw", 20100517) INTRO (L"A gammatone is the product of a rising polynomial, a decaying exponential function, and a " "cosine wave.") NORMAL (L"It can be described with the following formula:") FORMULA (L"gammaTone (%t) = %a %t^^%\\ga\\--1^ e^^\\--2%\\pi\\.c%bandwidth\\.c%t^ " "cos (2%%\\pi\\.cfrequency\\.ct% + %initialPhase),") NORMAL (L"where %\\ga determines the order of the gammatone.") NORMAL (L"The gammatone function has a monotone carrier (the tone) with an " "envelope that is a gamma distribution function. The amplitude spectrum is essentially " "symmetric on a linear frequency scale. This function is used in some time-domain " "auditory models to simulate the spectral analysis performed by the basilar membrane. " "It was popularized in auditory modeling by @@Johannesma (1972)@. @@Flanagan (1960)@ " "already used it to model basilar membrane motion.") MAN_END MAN_BEGIN (L"generalized singular value decomposition", L"djmw", 19981007) INTRO (L"For %m > %n, the %%generalized singular value decomposition% (gsvd) of an %m \\xx %n matrix #%A and " "a %p \\xx %n matrix #%B is given by the pair of factorizations") FORMULA (L"#%A = #%U #%\\Si__1_ [#%0, #%R] #%Q\\'p and #%B = #%V #%\\Si__2_ [#%0, #%R] #%Q\\'p") NORMAL (L"The matrices in these factorizations have the following properties:") TAG (L"\\bu #%U [%m \\xx %m], #%V [%p \\xx %p] and #%Q [%n \\xx %n]") DEFINITION (L" are orthogonal matrices. In the reconstruction formula's above we maximally need " "only the first %n columns of matrices #%U and #%V (when %m and/or %p are greater than %n).") TAG (L"\\bu #%R [%r \\xx %r],") DEFINITION (L"is an upper triangular nonsingular matrix. %r is the rank of [#%A\\'p, #%B\\'p]\\'p " "and %r \\<_ %n. The matrix [#%0, #%R] is %r \\xx %n and its first %n \\xx (%n \\-- %r) part " "is a zero matrix.") TAG (L"\\bu #%\\Si__1_ [%m \\xx %r] and #%\\Si__2_ [%p \\xx %r]") DEFINITION (L"are real, nonnegative and \"diagonal\".") NORMAL (L"In practice, the matrices #%\\Si__1_ and #%\\Si__2_ are never used. Instead a shorter " "representation with numbers %\\al__%i_ and %\\be__%i_ is used. These numbers obey " "0 \\<_ \\al__%i_ \\<_ 1 and \\al__%i_^^2^ + \\be__%i_^^2^ = 1. The following relations exist:") FORMULA (L"#%\\Si__1_\\'p #%\\Si__1_ + #%\\Si__2_\\'p #%\\Si__2_ = #%I, ") FORMULA (L"#%\\Si__1_\\'p #%\\Si__1_ = #diag (%\\al__1_^^2^, ..., %\\al__%r_^^2^), and, ") FORMULA (L"#%\\Si__2_\\'p #%\\Si__2_ = #diag (%\\be__1_^^2^, ..., %\\be__%r_^^2^).") NORMAL (L"The ratios \\al__%i_ / \\be__%i_ are called the %%generalized singular values% of the " "pair #%A, #%B. Let %l be the rank of #%B and %k + %l (= %r) the rank of [#%A\\'p, #%B\\'p]\\'p. " "Then the first %k generalized singular values are infinite and the remaining %l are finite. " "(When %#B is of full rank then, of course, %k = 0).") ENTRY (L"Special cases") NORMAL (L"\\bu If #%B is a square nonsingular matrix, the gsvd of #%A and #%B is equivalent to the " "singular value decomposition of #%A #%B^^\\--1^.") NORMAL (L"\\bu The generalized eigenvalues and eigenvectors of #%A\\'p #%A - %\\la #%B\\'p #%B " "can be expressed in terms of the gsvd. The columns of the matrix #%X, constructed as") CODE (L"X = Q*( I 0 )") CODE (L" ( 0 inv(R) ),") NORMAL (L"form the eigenvectors. The important eigenvectors, of course, correspond " "to the positions where the %l eigenvalues are not infinite.") MAN_END MAN_BEGIN (L"invFisherQ", L"djmw", 20000525) INTRO (L"$$invFisherQ$ (%q, %df1, %df2) returns the value %f for which " "$$@fisherQ (%f, %df1, %df2) = %q.") MAN_END MAN_BEGIN (L"fisherQ", L"djmw", 20000525) INTRO (L"$$fisherQ$ (%f, %df1, %df2) returns the area under Fisher's F-distribution " "from %f to +\\oo.") MAN_END MAN_BEGIN (L"ISpline", L"djmw", 19990627) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}. ") NORMAL (L"An object of type ISpline represents a linear combination of basis " "i@spline functions. Each basis %ispline is a monotonically increasing " "polynomial function of degree %p.") FORMULA (L"ISpline (%x) = \\Si__%k=1..%numberOfCoefficients_ %c__%k_ %ispline__%k_(%x)") MAN_END MAN_BEGIN (L"Jackknife", L"djmw", 20031103) INTRO (L"A technique for estimating the bias and standard deviation of an " "estimate.") NORMAL (L"Suppose we have a sample #%x = (%x__1_, %x__2_,...%x__n_) and wish to estimate " "the bias and standard error of an estimator \\Te. The jackknife " "focuses on the samples that leave out one observation at a time: " "the %i-th jackknife sample consists of the data with the %i-th observation " "removed.") MAN_END MAN_BEGIN (L"Kirshenbaum phonetic encoding", L"djmw", 20120413) INTRO (L"The Kirshenbaum phonetic encoding represents International Phonetic Alphabet symbols using ascii characters. See: http://www.kirshenbaum.net/IPA/ascii-ipa.pdf. The @@espeak@ speech synthesizer on which our synthesizer is based accepts this encoding as text input. ") MAN_END MAN_BEGIN (L"Legendre polynomials", L"djmw", 19990620) INTRO (L"The Legendre polynomials %P__%n_(%x) of degree %n are special " "orthogonal polynomial functions defined on the domain [-1, 1].") NORMAL (L"Orthogonality:") FORMULA (L"__-1_\\in^^1^ %W(%x) %P__%i_(%x) %P__%j_(%x) %dx = \\de__%ij_") FORMULA (L"%W(%x) = 1 (-1 < x < 1)") NORMAL (L"They obey certain recurrence relations:") FORMULA (L"%n %P__%n_(%x) = (2%n \\-- 1) %x %P__%n-1_(%x) \\-- (%n \\-- 1) %P__%n-2_(%x)") FORMULA (L"%P__0_(%x) = 1") FORMULA (L"%P__1_(%x) = %x") NORMAL (L"We may %change the domain of these polynomials to [%xmin, %xmax] by " "using the following transformation:") FORMULA (L"%x\\'p = (2%x \\-- (%xmax + %xmin)) / (%xmax - %xmin).") NORMAL (L"We subsequently use %P__%k_(%x\\'p) instead of %P__%k_(%x).") MAN_END MAN_BEGIN (L"LegendreSeries", L"djmw", 19990620) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type LegendreSeries represents a linear combination of @@Legendre polynomials@ " "%P__%k_(%x).") FORMULA (L"LegendreSeries (%x) = \\Si__%k=1..%numberOfCoefficients_ %c__%k_ %P__%k_(%x)") MAN_END MAN_BEGIN (L"LegendreSeries: To Polynomial", L"djmw", 19990620) INTRO (L"A command to transform the selected @LegendreSeries object into a @@Polynomial@ object.") NORMAL (L"We find polynomial coefficients %c__%k_ such that") FORMULA (L"\\Si__%k=1..%numberOfCoefficients_ %c__%k_ %x^^%k^ = " "\\Si__%k=1..%numberOfCoefficients_ %l__%k_ %P__%k_(%x)") NORMAL (L"We use the recurrence relation for @@Legendre polynomials@ to calculate these coefficients.") MAN_END MAN_BEGIN (L"Matrix: Draw distribution...", L"djmw", 20041110) INTRO (L"A command to draw the distribution histogram of the values in the selected part of a @Matrix.") ENTRY (L"Settings") TAG (L"##Horizontal range#, ##Vertical range#") DEFINITION (L"determine the part of the matrix whose distribution will be drawn.") TAG (L"##Minimum value#, ##Maximum value#") DEFINITION (L"determine the range of values that will be considered in the distribution. " "To treat all bin widths equally, the range will include the %%Minimum value% and exclude the " "%%Maximum value% (see below).") TAG (L"##Number of bins") DEFINITION (L"determines the number of bars in the distribution histogram.") TAG (L"##Minimum frequency#, ##Maximum frequency#") DEFINITION (L"determine the limits of the vertical axis.") ENTRY (L"Algorithm") NORMAL (L"For a particular matrix element %z, the histogram bin number %%i% that will be incremented obeys the following relation:") FORMULA (L"%%lowerBinBorder%__%i_ \\<_ %z < %%lowerBinBorder%__%i_+ %%binWidth%,") NORMAL (L"where") FORMULA (L"%%binWidth% = (%%maximumValue% - %%minimumValue%)/%%numberOfBins%,") NORMAL (L"and") FORMULA (L"%%lowerBinBorder%__%i_ = %%minimumValue% + (%i - 1)\\.c%%binWidth%.") NORMAL (L"In this way all bins will be based on exactly the same width, as each binning interval includes its lower border " "and excludes its upper border " "(i.e., each interval is closed to the left and open to the right). ") MAN_END MAN_BEGIN (L"Matrix: Solve equation...", L"djmw", 19961006) INTRO (L"Solve the general matrix equation #A #x = #b for #x.") NORMAL (L"The matrix #A can be any general %m \\xx %n matrix, #b is a %m-dimensional " "and #x a %n-dimensional vector. The @Matrix contains #A as its first %n columns " "and #b as its last column. The %n-dimensional solution is returned as a #Matrix " "with %n columns.") NORMAL (L"When the number of equations (%m) is %greater than the number of unknowns (%n) the " "algorithm gives the best least-squares solution. If on the contrary you " "have %fewer equations than unknowns the solution will not be unique.") ENTRY (L"Method") NORMAL (L"Singular value decomposition with backsubstitution. " "Zero will be substituted for eigenvalues smaller than %tolerance \\.c " "%%maximum_eigenvalue% (when the user-supplied %tolerance equals 0.0 a " "value of 2.2 \\.c 10^^-16^ \\.c %%number_of_unknowns% " "will be used as %tolerance).") NORMAL (L"See for more details: @@Golub & van Loan (1996)@ chapters 2 and 3.") MAN_END MAN_BEGIN (L"MelFilter", L"djmw", 20010404) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type MelFilter represents an acoustic time-frequency " "representation of a sound: the power spectral density %P(%f, %t), " "expressed in dB's. " "It is sampled into a number of points around equally spaced times %t__%i_ " "and frequencies %f__%j_ (on a Mel frequency scale).") ENTRY (L"Inside a MelFilter") NORMAL (L"With @Inspect you will see that this type contains the same " "attributes a @Matrix.") MAN_END MAN_BEGIN (L"MelFilter: To MFCC...", L"djmw", 20010404) INTRO (L"A command to create a @MFCC object from each selected @MelFilter " "object.") NORMAL (L"Mel frequency cepstral coefficients result from the Discrete Cosine " "Transform of the filterbank spectrum (in dB). The following formula " "shows the relation:") FORMULA (L"%c__%i_ = \\Si__%j=1_^^%N^ %P__%j_ cos (%i\\pi/%N (%j-0.5))),") NORMAL (L"where %N represents the number of filters and %P__%j_ the power in dB " "in the %j^^%th^ filter.") NORMAL (L"This transformation was first used by @@Davis & Mermelstein (1980)@.") MAN_END MAN_BEGIN (L"MFCC: To TableOfReal...", L"djmw", 20120504) INTRO (L"Convert the selected @@MFCC@ object to a @@TableOfReal@ object. Each MFCC frame results " "in one row in the TableOfReal. If the \"Include energy\" option is chosen, the zeroth MFCC " "coefficient will be saved in the first column.") MAN_END MAN_BEGIN (L"MSpline", L"djmw", 19990627) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}. ") NORMAL (L"An object of type MSpline represents a linear combination of basis " "m@spline functions. Each basis %mspline is a positive polynomial function " "of degree %p.") FORMULA (L"MSpline (%x) = \\Si__%k=1..%numberOfCoefficients_ %c__%k_ %mspline__%k_(%x)") MAN_END MAN_BEGIN (L"Pattern", L"djmw", 20041201) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") INTRO (L"An object of type Pattern represents a sequence of patterns that can serve as " "inputs for a neural net. All elements in a Pattern have to be in the interval [0,1].") ENTRY (L"Pattern commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu ##Create Pattern with zeroes...#") LIST_ITEM (L"\\bu @@TableOfReal: To Pattern and Categories...@") NORMAL (L"Synthesis:") LIST_ITEM (L"\\bu @@FFNet & Pattern: To Categories...@") LIST_ITEM (L"\\bu @@Pattern & Categories: To FFNet...@") ENTRY (L"Inside a Pattern") NORMAL (L"With @Inspect you will see that this type contains the same " "attributes as a @Matrix.") MAN_END MAN_BEGIN (L"PCA", L"djmw", 19990323) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}. " "See the @@Principal component analysis@ tutorial.") NORMAL (L"An object of type PCA represents the principal components analysis " "of a multivariate dataset.") ENTRY (L"Commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@Principal component analysis@ tutorial") LIST_ITEM (L"\\bu @@TableOfReal: To PCA@") ENTRY (L"Inside a PCA") NORMAL (L"With @Inspect you will see that this type contains the same " "attributes as an @Eigen with the following extras:") TAG (L"%numberOfObservations") DEFINITION (L"the number of observations in the multivariate dataset that originated the PCA, " "usually equal to the dataset's number of rows.") TAG (L"%labels[1..%dimension]") DEFINITION (L"the label that corresponds to each dimension.") TAG (L"%centroid") DEFINITION (L"the centroids of the originating multivariate data set.") MAN_END MAN_BEGIN (L"PCA: Get fraction variance accounted for...", L"djmw", 19990106) INTRO (L"A command to query the selected @PCA for the fraction %%variance " "accounted for% by the selected components.") ENTRY (L"Setting") TAG (L"##Principal component range") DEFINITION (L"defines the range of the principal components. If you choose both numbers equal, " "you get the fraction of the \"variance\" explained by that one component.") ENTRY (L"Details") NORMAL (L"The contribution is defined as:") FORMULA (L"\\Si__%i=%from..%to_ %%eigenvalue[i]% / \\Si__%i=1..%numberOfEigenvalues_ %%eigenvalue[i]%") MAN_END MAN_BEGIN (L"PCA: Get eigenvalue...", L"djmw", 20040225) INTRO (L"A command to query the selected @PCA for the %i^^th^ " "eigenvalue.") MAN_END MAN_BEGIN (L"PCA: Get eigenvector element...", L"djmw", 20040225) INTRO (L"A command to query the selected @PCA for the %j^^th^ element of the " "%i^^th^ eigenvector.") MAN_END MAN_BEGIN (L"PCA: Get equality of eigenvalues...",L"djmw", 19981102) INTRO (L"A command to get the probability that some of the eigenvalues of the " "selected @PCA object are equal. A low probability means that it is not " "very likely that that these numbers are equal.") NORMAL (L"We test the hypothesis %H__0_: %\\la__%from_ = ... = %\\la__%to_ " "that %r (= %to\\--%from+1) of the eigenvalues \\la of the covariance " "matrix are equal. The remaining eigenvalues are unrestricted as to their " "values and multiplicities. The alternative hypothesis to %H__0_ is that " "some of the eigenvalues in the set are distinct.") ENTRY (L"Settings") TAG (L"##Eigenvalue range") DEFINITION (L"define the range of eigenvalues to be tested for equality.") TAG (L"##Conservative test") DEFINITION (L"when on, a more conservative estimate for %n is chosen (see below).") ENTRY (L"Details") NORMAL (L"The test statistic is:") FORMULA (L"\\ci^2 = \\--%n \\Si__%j=%from..%to_ ln %eigenvalue[%j] + %n %r " "ln (\\Si__%j=%from..%to_ %eigenvalue[%j] / %r),") NORMAL (L"with %r(%r+1)/2 \\--1 degrees of freedom. Here %n = %totalNumberOfCases \\-- 1.") NORMAL (L"A special case occurs when the variation in the last %r dimensions is spherical. In a " "slightly more conservative test we may replace %n by %n\\--%from\\--(2%r^2+%r+2)/6%r.") NORMAL (L"Also see @@Morrison (1990)@, page 336.") MAN_END MAN_BEGIN (L"PCA: Get number of components (VAF)...", L"djmw", 19990111) INTRO (L"A command to ask the selected @PCA for the minimum number of " "components that are necessary " "to explain the given fraction %%variance accounted for%.") ENTRY (L"Setting") TAG (L"##Variance accounted for (fraction)") DEFINITION (L"the fraction variance accounted for that must be explained.") MAN_END MAN_BEGIN (L"PCA: To TableOfReal (reconstruct 1)...", L"djmw", 20030108) INTRO (L"A command to reconstruct a single data item. The result is stored as " "a @TableOfReal with only one row.") ENTRY (L"Settings") TAG (L"##Coefficients") DEFINITION (L"the weight for the eigenvectors.") NORMAL (L"The algorithm is explained in @@PCA & Configuration: To TableOfReal " "(reconstruct)@.") MAN_END MAN_BEGIN (L"PCA & Configuration: To TableOfReal (reconstruct)", L"djmw", 20030108) INTRO (L"A command to reconstruct a @TableOfReal from the selected @Configuration" " and @PCA.") NORMAL (L"The TableOfReal is reconstructed from the eigenvectors of the PCA and " "elements of the Configuration are the weight factors: ") FORMULA (L"%#t__%i_ = \\Si__%k_ %c__%ik_ #%e__%k_,") NORMAL (L"where %#t__%i_ is the %i-th row in the resulting TableOfReal object, %c__%ik_ is " "the element at row %i and column %k in the Configuration object and #%e__%k_ " "the %k-th eigenvector from the PCA object.") MAN_END MAN_BEGIN (L"PCA & PCA: Get angle between pc1-pc2 planes", L"djmw", 20041028) INTRO (L"A command to calculate the angle between two planes. Each plane is spanned by the first " "two eigenvectors from the corresponding @@PCA@.") ENTRY (L"Algorithm") NORMAL (L"The algorithm is described in section 12.4.3 of @@Golub & van Loan (1996)@:") NORMAL (L"First we form the projection of one set of eigenvectors on the other set. " "This results in a 2\\xx2 matrix #C:") FORMULA (L"#C = #E__1_\\'p #E__2_,") NORMAL (L"where #E__1_ and #E__2_ are 2\\xx%%dimension% and %%dimension%\\xx2 matrices " "that contain the first two eigenvectors of the PCA's, respectively.") NORMAL (L"Next, we compute the @@singular value decomposition@ of #C:") FORMULA (L"#C = #U #\\Si #V\\'p") NORMAL (L"Now the cosine of the angle between the two planes is given by \\si__2_ and " "the angle in degrees is therefore:") FORMULA (L"arccos (\\si__2_)\\.c180/\\pi") MAN_END MAN_BEGIN (L"PCA & PCA: To Procrustes...", L"djmw", 20041028) INTRO (L"A command to calculate a @Procrustes from the two selected @@PCA@'s.") NORMAL (L"Determines the orthogonal @@Procrustes transform@.") NORMAL (L"Algorithm 12.4.1 in @@Golub & van Loan (1996)@.") MAN_END MAN_BEGIN (L"PCA & TableOfReal: To Configuration...", L"djmw", 19990111) INTRO (L"A command to construct a @Configuration from the selected @TableOfReal" " and @PCA.") ENTRY (L"Setting") TAG (L"##Number of dimensions") DEFINITION (L"determines the number of dimensions of the resulting Configuration.") ENTRY (L"Algorithm") NORMAL (L"The TableOfReal is projected on the eigenspace of the PCA, i.e., " "each row of the TableOfReal is treated as a vector, and the inner product " "with the eigenvectors of the PCA determine its coordinates in the Configuration.") NORMAL (L"Because the algorithm performs a projection, the resulting Configuration will " "##only be centered#, i.e., its centroid will be at ##0#, if the data in the " "TableOfReal object are centered too. ") NORMAL (L"See also @@Eigen & TableOfReal: Project...@.") MAN_END MAN_BEGIN (L"PCA & TableOfReal: To TableOfReal (z-scores)...", L"djmw", 20120510) INTRO (L"A command to construct a @TableOfReal with z-scores from the selected @TableOfReal" " and @PCA.") ENTRY (L"Setting") TAG (L"##Number of dimensions") DEFINITION (L"determines the number of dimensions of the resulting Configuration.") ENTRY (L"Algorithm") NORMAL (L"The values %d__%ij_ in the new TableOfReal are calculated as") FORMULA (L"%d__%ij_ = ##eigenvector#__j_\\.c ##z#__%i_,") NORMAL (L"which is the inproduct of the %j-th eigenvector and the z-score vector ##z#__%i_ of the %i-th row whose elements %z__%ij_ are defined as") FORMULA (L"%z__%ij_ = (data__%ij_ - mean__%j_) / sqrt (eigenvalue__%j_),") NORMAL (L"in which data__%ij_ is the data value at row %i and column %j of the selected TableOfReal and mean__%j_ is the " "%j-th centroid value of the PCA. The square root of the %j-th eigenvalue is the standard deviation in " " the %j-th principal direction.") MAN_END MAN_BEGIN (L"PCA & TableOfReal: Get fraction variance...", L"djmw", 20040324) INTRO (L"A command to query the selected @PCA and @TableOfReal object for the explained " "fraction of the variance if the TableOfReal object were projected onto the PCA space.") ENTRY (L"Algorithm") LIST_ITEM (L"1. The TableOfReal is @@TableOfReal: To Covariance|converted@ to a " "Covariance object.") LIST_ITEM (L"2. The Covariance object is @@PCA & Covariance: Project|projected@ on " "the PCA eigenspace and the newly obtained projected Covariance object is " "@@Covariance: Get fraction variance...|queried@ for the fraction variance.") MAN_END MAN_BEGIN (L"PitchTier: To Pitch...", L"djmw", 20061128) INTRO (L"Synthesizes a new @Pitch from the selected @PitchTier.") MAN_END MAN_BEGIN (L"Polygon: Rotate...", L"djmw", 20100418) INTRO (L"Rotates the selected @@Polygon@ counterclockwise with respect to the given coordinates.") MAN_END MAN_BEGIN (L"Create simple Polygon...", L"djmw", 20110622) INTRO (L"Creates a @@Polygon@ from user supplied x/y pairs.") ENTRY (L"Settings") TAG (L"##Name") DEFINITION (L"defines the name of the resulting Polygon.") TAG (L"##Vertices as X-Y pairs#,") DEFINITION (L"defines the x-y values of the vertices of the Polygon. The Polygon will be automatically closed, i.e., the first and the last point will be connected.") ENTRY (L"Example") NORMAL (L"The command ##Create simple Polygon... p 0.0 0.0 0.0 1.0 1.0 0.0# defines a Polygon with three points. In the figure the three points are indicated with open circles while the Polygon is drawn as a closed figure.") SCRIPT (4,4, L"Create simple Polygon... p 0.0 0.0 0.0 1.0 1.0 0.0\n" "Draw circles... 0 1 0 1 3\n" "Draw closed... 0 1 0 1\n" "Remove\n") MAN_END MAN_BEGIN (L"Polygon: Get location of point...", L"djmw", 20120220) INTRO (L"Determines whether a given point is on the ##I#nside, the ##O#utside, on an ##E#dge or on a ##V#ertex of the selected Polygon.") ENTRY (L"Algorithm") NORMAL (L"We determine how often a horizontal line extending from the point crosses the polygon. If the number of crossings is even, the point is on the outside, else on the inside. Special care is taken to be able to detect if a point is on the boundary of the polygon. The used algorithm is from @@Hormann & Agathos (2001)@") MAN_END MAN_BEGIN (L"Polygon: Simplify", L"djmw", 20110615) INTRO (L"Removes collinear vertices from a @@Polygon@.") ENTRY (L"Example") SCRIPT (4, 4, L"p1 = Create simple Polygon... p 0.0 0.0 0.0 1.0 0.5 0.5 1.0 0.0 0.5 0 0 -0.5 0 -0.25\n" "Draw closed... 0 0 0 0\n" "Red\n" "Draw circles... 0 0 0 0 3\n" "p2 = Simplify\n" "Black\n" "Paint circles... 0 0 0 0 1.5\n" "plus p1\n" "Remove\n" ) NORMAL (L"Given the Polygon with the seven vertices indicated by the red open circles, the Simplify action results in the Polygon with four vertices indicated by the filled black circles.") MAN_END MAN_BEGIN (L"Polygon: Translate...", L"djmw", 20100418) INTRO (L"Translates the selected @@Polygon@ over the given vector.") NORMAL (L"Given the old coordinates (x__i_, y__i_) and the translation (x__t_,y__t_), the new coordinates are:") FORMULA (L"x__i_\\'p = x__i_ + x__t_") FORMULA (L"y__i_\\'p = y__i_ + y__t_") MAN_END MAN_BEGIN (L"Polynomial", L"djmw", 19990608) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type " "Polynomial represents a polynomial function on a domain.") NORMAL (L"A polynomial of degree %n is defined as:") FORMULA (L"%p(%x) = %c__1_ + %c__2_ %x + %c__3_ %x^^2^ + ... c__%n+1_ %x^^%n^.") NORMAL (L"The real numbers %c__%k_ are called the polynomial %coefficients.") ENTRY (L"Commands") NORMAL (L"Creation") LIST_ITEM (L"\\bu @@Create Polynomial...@ (in the ##New menu#)") LIST_ITEM (L"\\bu @@LPC: To Polynomial (slice)...@ (from prediction coefficients)") LIST_ITEM (L"\\bu @@LegendreSeries: To Polynomial@") LIST_ITEM (L"\\bu @@ChebyshevSeries: To Polynomial@") NORMAL (L"Drawing") LIST_ITEM (L"\\bu ##Draw...#") NORMAL (L"Queries") LIST_ITEM (L"\\bu @@Polynomial: Get function value...|Get function value...@: get %p(%x)") LIST_ITEM (L"\\bu ##Get coefficient value...#: get %c__%i_") LIST_ITEM (L"\\bu @@Polynomial: Get minimum...|Get minimum...@: minimum of %p(%x) on an interval") LIST_ITEM (L"\\bu @@Polynomial: Get x of minimum...|Get x of minimum...@") LIST_ITEM (L"\\bu @@Polynomial: Get maximum...|Get maximum...@: maximum of %p(%x) on an interval") LIST_ITEM (L"\\bu @@Polynomial: Get x of maximum...|Get x of maximum...@") LIST_ITEM (L"\\bu @@Polynomial: Get area...|Get area...@") NORMAL (L"Modification") LIST_ITEM (L"\\bu ##Set domain...#: new domain") LIST_ITEM (L"\\bu ##Set coefficient value...#: change one coefficient") NORMAL (L"Conversion") LIST_ITEM (L"\\bu @@Polynomial: To Spectrum...|To Spectrum...@ (evaluation over unit-circle)") LIST_ITEM (L"\\bu @@Polynomial: To Polynomial (derivative)|To Polynomial (derivative)@") LIST_ITEM (L"\\bu @@Polynomial: To Polynomial (primitive)|To Polynomial (primitive)@") LIST_ITEM (L"\\bu @@Polynomial: To Roots|To Roots@: roots of polynomial") MAN_END MAN_BEGIN (L"Polynomial: Get area...", L"djmw", 19990610) INTRO (L"A command to compute the area below the selected @Polynomial object.") ENTRY (L"Settings") TAG (L"##Xmin#, ##Xmax#") DEFINITION (L"define the interval.") NORMAL (L"The area is defined as __%xmin_\\in^^xmax^ %p(%x) %dx.") MAN_END MAN_BEGIN (L"Polynomial: Get function value...", L"djmw", 19990610) INTRO (L"A command to compute %p(%x) for the selected @Polynomial object.") MAN_END MAN_BEGIN (L"Polynomial: Get maximum...", L"djmw", 19990610) INTRO (L"A command to compute, on a specified interval, the maximum value of the selected " "@Polynomial object.") MAN_END MAN_BEGIN (L"Polynomial: Get x of maximum...", L"djmw", 19990610) INTRO (L"A command to compute, on a specified interval, the location of the maximum of the " "selected @Polynomial object.") MAN_END MAN_BEGIN (L"Polynomial: Get minimum...", L"djmw", 19990610) INTRO (L"A command to compute, on a specified interval, the minimum value of the selected " "@Polynomial object.") MAN_END MAN_BEGIN (L"Polynomial: Get x of minimum...", L"djmw", 19990610) INTRO (L"A command to compute, on a specified interval, the location of the minimum of the " "selected @Polynomial object.") MAN_END MAN_BEGIN (L"Polynomials: Multiply", L"djmw", 19990616) INTRO (L"A command to multiply two @@Polynomial|polynomials@ with each other.") NORMAL (L"The result of multiplying 1 + 2 %x and 2 \\-- %x^2 will be the polynomial:") FORMULA (L"2 + 4 %x \\-- %x^2 \\-- 2 %x^3.") MAN_END MAN_BEGIN (L"Polynomial: To Polynomial (derivative)", L"djmw", 19990610) INTRO (L"A command to compute the derivative of the selected @Polynomial object.") MAN_END MAN_BEGIN (L"Polynomial: To Polynomial (primitive)", L"djmw", 19990610) INTRO (L"A command to compute the primitive of the selected @Polynomial object.") MAN_END MAN_BEGIN (L"Polynomial: Scale x...", L"djmw", 19990610) INTRO (L"A command to transform the selected @Polynomial object to a new domain.") TAG (L"##Xmin# and ##Xmax#") DEFINITION (L"define the new domain.") ENTRY (L"Behaviour") NORMAL (L"The polynomial is transformed from domain [%x__min_, %x__max_] to " "domain [%Xmin, %Xmax] in such a way that its form stays the same. " "This is accomplished by first calculating:") FORMULA (L"%f(%x\\'p) = \\Si__%k=1..%numberOfCoefficients_ %c__%k_ %x\\'p^^%k^, where") FORMULA (L"%x\\'p = %a %x + %b,") NORMAL (L"and then collecting terms of equal degree. The %a and %b are defined as") FORMULA (L"%a = (%x__min_ \\-- %x__max_) / (%Xmin \\-- %Xmax)") FORMULA (L"%b = %x__min_ \\-- %a %Xmin") MAN_END MAN_BEGIN (L"Polynomial: To Roots", L"djmw", 19990608) INTRO (L"A command to compute the @@Roots|roots@ of the selected @Polynomial objects.") ENTRY (L"Algorithm") NORMAL (L"The roots are found from the polished eigenvalues of a special companion matrix. " "For further explanation on these methods see @@Press et al. (1992)@.") MAN_END MAN_BEGIN (L"Polynomial: To Spectrum...", L"djmw", 19990616) INTRO (L"A command to compute the @@Spectrum|spectrum@ of the selected @Polynomial objects.") ENTRY (L"Settings") TAG (L"##Nyquist frequency (Hz)") DEFINITION (L"defines the highest frequency in the spectrum. The lowest frequency of the spectrum " "will be 0 Hz.") TAG (L"##Number of frequencies") DEFINITION (L"defines the number of frequencies in the spectrum.") ENTRY (L"Algorithm") NORMAL (L"We calculate the spectrum by evaluating the polynomial at regularly spaced points %z__%k_ " "on the upper half of a circle with radius %r = 1 in the complex plane. The upperhalf of the " "unit circle, where %k\\.c%\\fi is in the interval [0, %\\pi], will be mapped to frequencies " "[0, @@Nyquist frequency@] in the spectrum. ") NORMAL (L"The complex values %z__%k_ (%k=1..%numberOfFrequencies) are defined as:") FORMULA (L"%z__%k_ = %r e^^%i %k %\\fi^, where,") FORMULA (L"%\\fi = \\pi / (%numberOfFrequencies \\-- 1) and %r = 1.") MAN_END MAN_BEGIN (L"Principal component analysis", L"djmw", 20120510) INTRO (L"This tutorial describes how you can perform principal component " "analysis with P\\s{RAAT}.") NORMAL (L"Principal component analysis (PCA) involves a mathematical procedure " "that transforms a number of (possibly) correlated variables into a " "(smaller) number of uncorrelated variables called %%principal " "components%. The first principal component accounts for as much of the " "variability in the data as possible, and each succeeding component " "accounts for as much of the remaining variability as possible.") ENTRY (L"1. Objectives of principal component analysis") LIST_ITEM (L"\\bu To discover or to reduce the dimensionality of the data set.") LIST_ITEM (L"\\bu To identify new meaningful underlying variables.") ENTRY (L"2. How to start") NORMAL (L"We assume that the multi-dimensional data have been collected in a @TableOfReal data matrix, " "in which the rows are associated with the cases and the columns with the variables.") NORMAL (L"Traditionally, principal component analysis is performed on the " "symmetric @@Covariance|Covariance@ matrix or on the symmetric @@correlation|Correlation@ matrix. " "These matrices can be calculated from the data matrix. " "The covariance matrix contains scaled @@SSCP|sums of squares and cross products@. " "A correlation matrix is like a covariance matrix but first the variables, i.e. the columns, have been standardized. " "We will have to standardize the data first if the variances of " "variables differ much, or if the units of measurement of the " "variables differ. You can standardize the data in the TableOfReal by choosing @@TableOfReal: Standardize columns|Standardize columns@.") NORMAL (L"To perform the analysis, we select the TabelOfReal data matrix in the list of objects and choose " "@@TableOfReal: To PCA|To PCA@. This results in a new PCA object in the " "list of objects.") NORMAL (L"We can now make a @@Scree plot|scree@ plot of the eigenvalues, @@Eigen: Draw " "eigenvalues...|Draw eigenvalues...@ " "to get an indication of the importance of each eigenvalue. The exact " "contribution of each eigenvalue (or a range of eigenvalues) to the " "\"explained variance\" can also be queried: " "@@PCA: Get fraction variance accounted for...|Get fraction variance " "accounted for...@. You might also check for the equality of a " "number of eigenvalues: @@PCA: Get equality of eigenvalues...|Get equality " "of eigenvalues...@.") ENTRY (L"3. Determining the number of components") NORMAL (L"There are two methods to help you to choose the number of components. " "Both methods are based on relations between the eigenvalues.") LIST_ITEM (L"\\bu Plot the eigenvalues, @@Eigen: Draw eigenvalues...|" "Draw eigenvalues...@. If the points on the graph tend to level out (show an \"elbow\"), " "these eigenvalues are usually close enough to zero that they can be " "ignored.") LIST_ITEM (L"\\bu Limit the number of components to that number that accounts for a certain fraction of the total variance. For example, if you are satisfied with 95% of the total variance explained then use the number you get by the query ##Get number of components (VAF)... 0.95#.") ENTRY (L"4. Getting the principal components") NORMAL (L"Principal components are obtained by projecting the multivariate " "datavectors on the space spanned by the eigenvectors. This can be done " "in two ways:") LIST_ITEM (L"1. Directly from the TableOfReal without first forming a " "@PCA object: " "@@TableOfReal: To Configuration (pca)...|To Configuration (pca)...@. " "You can then draw the Configuration or display its numbers. ") LIST_ITEM (L"2. Select a PCA and a TableOfReal object together and choose " "@@PCA & TableOfReal: To Configuration...|To Configuration...@. " "In this way you project the TableOfReal onto the PCA's eigenspace.") ENTRY (L"5. Mathematical background on principal component analysis") NORMAL (L"The mathematical technique used in PCA is called eigen analysis: " "we solve for the eigenvalues and eigenvectors of a square symmetric " "matrix with sums of squares and cross products. " "The eigenvector associated with the largest eigenvalue has the same " "direction as the first principal component. The eigenvector associated " "with the second largest eigenvalue determines the direction of the second " "principal component. " "The sum of the eigenvalues equals the trace of the square matrix and the " "maximum number of eigenvectors equals the number of rows (or columns) of " "this matrix.") ENTRY (L"6. Algorithms") NORMAL (L"If our starting point happens to be a symmetric matrix like the covariance matrix, " "we solve for the eigenvalue and eigenvectors " "by first performing a Householder reduction to tridiagonal form, followed" " by the QL algorithm with implicit shifts.") NORMAL (L"If, conversely, our starting point is the data matrix #%A , " "we do not have to form explicitly the matrix with sums of squares and " "cross products, #%A\\'p#%A. Instead, we proceed by a numerically more " "stable method, and form the @@singular value decomposition@ of #%A, " "#%U #%\\Si #%V\\'p. The matrix #%V then contains the eigenvectors, " "and the squared diagonal elements of #%\\Si contain the eigenvalues.") MAN_END MAN_BEGIN (L"PCA & Covariance: Project", L"djmw", 20040225) INTRO (L"A command to project the @Covariance object onto the eigenspace of " "the @PCA object. ") NORMAL (L"Further details can be found in @@Eigen & SSCP: Project@.") MAN_END MAN_BEGIN (L"PCA & SSCP: Project", L"djmw", 20040225) INTRO (L"A command to project the @SSCP object onto the eigenspace of " "the @PCA object. ") NORMAL (L"Further details can be found in @@Eigen & SSCP: Project@.") MAN_END MAN_BEGIN (L"Regular expressions", L"djmw", 20010706) INTRO (L"This tutorial describes the %syntax of regular expressions in P\\s{RAAT} ") ENTRY (L"Introduction") NORMAL (L"A %%regular expression% is a text string that describes a %set " "of strings. Regular expressions (regex) are useful as a way to search " "for patterns in text strings and, optionally, replace them by another " "pattern.") NORMAL (L"Some regex match only one string, i.e., the set they describe has " "only one member. For example, the regex \"ab\" matches the string \"ab\" " "and no others. Other regex match more than one string, i.e., the set " "they describe has more than one member. For example, the regex \"a*\" " "matches the string made up of any number (including zero) of \"a\"s. " "As you can see, some characters match themselves (such as \"a\" and " "\"b\") and these characters are called %ordinary characters. The " "characters that don't match themselves, such as \"*\", are called " "%special characters or %meta characters. Many special characters are only " "special characters in the %search regex and are ordinary characters in " "the substitution regex. ") NORMAL (L"You can read the rest of this tutorial sequentially with the help of " "the \"<1\" and \">1\" buttons.") LIST_ITEM (L"1. @@Regular expressions 1. Special characters|Special characters@ " "(\\bs \\^ \\$ { } [ ] ( ) . + ? \\| - &)") LIST_ITEM (L"2. @@Regular expressions 2. Quantifiers|Quantifiers@ " "(how often do we match).") LIST_ITEM (L"3. @@Regular expressions 3. Anchors|Anchors@ (where do we match)") LIST_ITEM (L"4. @@Regular expressions 4. Special constructs with parenthesis|" "Special constructs with parenthesis@ (grouping constructs)") LIST_ITEM (L"5. @@Regular expressions 5. Special control characters|" "Special control characters@ (difficult-to-type characters like \\bsn)") LIST_ITEM (L"6. @@Regular expressions 6. Convenience escape sequences|" "Convenience escape sequences@ " "(\\bsd \\bsD \\bsl \\bsL \\bss \\bsS \\bsw \\bsW \\bsB)") LIST_ITEM (L"7. @@Regular expressions 7. Octal and hexadecimal escapes|" "Octal and hexadecimal escapes@ (things like \\bs053 or \\bsX2B)") LIST_ITEM (L"8. @@Regular expressions 8. Substitution special characters|" "Substitution special characters@ (\\bs1..\\bs9 \\bsU \\bsu \\bsL \\bsl &)") NORMAL (L"More in depth coverage of regular expressions can be found in " "@@Friedl (1997)@.") MAN_END MAN_BEGIN (L"Regular expressions 1. Special characters", L"djmw", 20010718) INTRO (L"The following characters are the %meta characters that give special " "meaning to the regular expression search syntax:") TAG (L"#\\bs# the backslash %escape character.") DEFINITION (L"The backslash gives special meaning to the character " "following it. For example, the combination \"\\bsn\" stands for the " "%newline, one of the @@Regular expressions 5. Special control characters" "|control characters@. The combination \"\\bsw\" stands for a \"word\" " "character, one of the @@Regular expressions 6. Convenience escape " "sequences|" "convenience escape sequences@ while \"\\bs1\" is one of the @@Regular " "expressions 8. Substitution special characters|substitution special " "characters@.") LIST_ITEM1 (L"Example: The regex \"aa\\bsn\" tries to match two consecutive " "\"a\"s at the end of a line, inclusive the newline character itself.") LIST_ITEM1 (L"Example: \"a\\bs+\" matches \"a+\" and not a series of one or " "\"a\"s.") TAG (L"##\\^ # the caret is the start of line @@Regular expressions 3. " "Anchors|anchor@ or the negate symbol.") LIST_ITEM1 (L"Example: \"\\^ a\" matches \"a\" at the start of a line.") LIST_ITEM1 (L"Example: \"[\\^ 0-9]\" matches any non digit.") TAG (L"##\\$ # the dollar is the end of line @@Regular expressions 3. " "Anchors|anchor@.") LIST_ITEM1 (L"Example: \"b\\$ \" matches a \"b\" at the end of a line.") LIST_ITEM1 (L"Example: \"\\^ b\\$ \" matches the empty line.") TAG (L"##{ }# the open and close curly bracket are used as range @@Regular " "expressions 2. Quantifiers|quantifiers@.") LIST_ITEM1 (L"Example: \"a{2,3}\" matches \"aa\" or \"aaa\".") TAG (L"##[ ]# the open and close square bracket define a character class to " "match a %single character.") DEFINITION (L"The \"\\^ \" as the first character following the \"[\" negates " "and the match is for the characters %not listed. " "The \"-\" denotes a range of characters. Inside a \"[ ]\" character " "class construction most special characters are interpreted as ordinary " "characters. ") LIST_ITEM1 (L"Example: \"[d-f]\" is the same as \"[def]\" and matches \"d\", " "\"e\" or \"f\".") LIST_ITEM1 (L"Example: \"[a-z]\" matches any lowercase characters in the " "alfabet.") LIST_ITEM1 (L"Example: \"[\\^ 0-9]\" matches any character that is not a digit.") LIST_ITEM1 (L"Example: A search for \"[][()?<>$^.*?^]\" in the string " "\"[]()?<>$^.*?^\" followed by a replace string \"r\" has the result " "\"rrrrrrrrrrrrr\". Here the search string is %one character class and " "all the meta characters are interpreted as ordinary characters without " "the need to escape them.") TAG (L"##( )# the open and close parenthesis are used for grouping " "characters (or other regex).") DEFINITION (L"The groups can be referenced in " "both the search and the @@Regular expressions 8. Substitution special " "characters|substitution@ phase. There also exist some @@Regular " "expressions 4. Special constructs with parenthesis|special constructs " "with parenthesis@.") LIST_ITEM1 (L"Example: \"(ab)\\bs1\" matches \"abab\".") TAG (L"##.# the dot matches any character except the newline.") LIST_ITEM1 (L"Example: \".a\" matches two consecutive characters where " "the last one is \"a\".") LIST_ITEM1 (L"Example: \".*\\bs.txt\\$ \" matches all strings that end in " "\".txt\".") TAG (L"##*# the star is the match-zero-or-more @@Regular expressions 2. " "Quantifiers|quantifier@.") LIST_ITEM1 (L"Example: \"\\^ .*\\$ \" matches an entire line. ") TAG (L"##+# the plus is the match-one-or-more quantifier.") TAG (L"##?# the question mark is the match-zero-or-one " "quantifier. The question mark is also used in " "@@Regular expressions 4. Special constructs with parenthesis|special " "constructs with parenthesis@ and in @@Regular expressions 2. " "Quantifiers|changing match behaviour@.") TAG (L"##\\| # the vertical pipe separates a series of alternatives.") LIST_ITEM1 (L"Example: \"(a|b|c)a\" matches \"aa\" or \"ba\" or \"ca\".") TAG (L"##< ># the smaller and greater signs are @@Regular expressions 3. " "Anchors|anchors@ that specify a left or right word boundary.") TAG (L"##-# the minus indicates a range in a character class (when it is " "not at the first position after the \"[\" opening bracket or the last " "position before the \"]\" closing bracket.") LIST_ITEM1 (L"Example: \"[A-Z]\" matches any uppercase character.") LIST_ITEM1 (L"Example: \"[A-Z-]\" or \"[-A-Z]\" match any uppercase character " "or \"-\".") TAG (L"##&# the and is the \"substitute complete match\" symbol.") MAN_END MAN_BEGIN (L"Regular expressions 2. Quantifiers", L"djmw", 20010708) INTRO (L"Quantifiers specify how often the preceding @@Regular expressions|" "regular expression@ should match.") TAG (L"##*# Try to match the preceding regular expression zero or more times.") LIST_ITEM1 (L"Example: \"(ab)c*\" matches \"ab\" followed by zero or more " "\"c\"s, i.e., \"ab\", \"abc\", \"abcc\", \"abccc\" ...") TAG (L"##+# Try to match the preceding regular expression one or more times.") LIST_ITEM1 (L"Example: \"(ab)c+\" matches \"ab\" followed by one or more " "\"c\"s, i.e., \"abc\", \"abcc\", \"abccc\" ...") TAG (L"##{%m, %n}# Try to match the preceding regular expression between %m " "and %n times.") DEFINITION (L"If you leave %m out, it is assumed to be zero. If you leave " "%n out it is assumed to be infinity. I.e., \"{,%n}\" matches from %zero " "to %n times, \"{%m,}\" matches a minimum of %m times, \"{,}\" matches " "the same as \"*\" and \"{n}\" is shorthand for \"{n, n\"} and matches " "exactly %n times.") LIST_ITEM1 (L"Example: \"(ab){1,2}\" matches \"ab\" and \"abab\".") TAG (L"##?# Try to match zero or one time.") ENTRY (L"Changing match behaviour") NORMAL (L"Default the quantifiers above try to match as much as possible, they " "are %greedy. " "You can change greedy behaviour to %lazy behaviour by adding an " "extra \"?\" after the quantifier.") LIST_ITEM1 (L"Example: In the string \"cabddde\", the search \"abd{1,2}\" " "matches \"abdd\", while the search for \"abd{1,2}?\" matches \"abd\".") LIST_ITEM1 (L"Example: In the string \"cabddde\", the search \"abd+\" " "matches \"abddd\", while the search for \"abd+?\" matches \"abd\".") MAN_END MAN_BEGIN (L"Regular expressions 3. Anchors", L"djmw", 20010708) INTRO (L"Anchors let you specify a very specific position within the search " "text.") TAG (L"##\\^ # Try to match the (following) regex at the beginning of a line.") LIST_ITEM1 (L"Example: \"\\^ ab\" matches \"ab\" only at the beginning of a " "line and not, for example, in the line \"cab\".") TAG (L"##\\$ # Try to match the (following) regex at the end of a line.") TAG (L"##<# Try to match the regex at the %start of a word.") DEFINITION (L"The character class that defines a %word can be found at the " "@@Regular expressions 6. Convenience escape sequences|convenience escape " "sequences@ page.") TAG (L"##># Try to match the regex at the %end of a word.") TAG (L"##\\bsB# Not a word boundary") DEFINITION (L"") MAN_END MAN_BEGIN (L"Regular expressions 4. Special constructs with parenthesis", L"djmw", 20010710) INTRO (L"Some special constructs exist with parenthesis. ") TAG (L"##(?:#%regex#)# is a grouping-only construct.") DEFINITION (L"They exist merely for efficiency reasons and facilitate grouping.") TAG (L"##(?=#%regex#)# is a positive look-ahead.") DEFINITION (L"A match of the regular expression contained in the positive " "look-ahead construct is attempted. If the match succeeds, control is " "passed to the regex following this construct and the text consumed by " "this look-ahead construct is first unmatched. ") TAG (L"##(?!#%regex#)# is a negative look-ahead.") DEFINITION (L"Functions like a positive look-ahead, only the " "%regex must %not match.") LIST_ITEM (L"Example: \"abc(?!.*abc.*)\" searches for the %last " "occurrence of \"abc\" in a string.") TAG (L"##(?i#%regex#)# is a case insensitive regex.") TAG (L"##(?I#%regex#)# is a case sensitive regex.") DEFINITION (L"Default a regex is case sensitive. ") LIST_ITEM1 (L"Example: \"(?iaa)\" matches \"aa\", \"aA\", \"Aa\" and \"AA\".") TAG (L"##(?n#%regex#)# matches newlines.") TAG (L"##(?N#%regex#)# doesn't match newlines.") NORMAL (L"All the constructs above do not capture text and cannot be " "referenced, i.e., the parenthesis are not counted. However, you " "can make them capture text by surrounding them with %ordinary " "parenthesis.") MAN_END MAN_BEGIN (L"Regular expressions 5. Special control characters", L"djmw", 20010708) INTRO (L"Special control characters in a @@Regular expressions|regular " "expression@ specify characters that are difficult to type.") TAG (L"#\\bsa alert (bell).") TAG (L"#\\bsb backspace.") TAG (L"#\\bse ASCII escape character.") TAG (L"#\\bsf form feed (new page).") TAG (L"#\\bsn newline.") TAG (L"#\\bsr carriage return.") LIST_ITEM1 (L"Example : a search for \"\\bsr\\bsn\" followed by a replace " "\"\\bsr\" changes Windows text files to Macintosh text files.") LIST_ITEM1 (L"Example : a search for \"\\bsr\" followed by a replace " "\"\\bsn\" changes Macintosh text files to Unix text files.") LIST_ITEM1 (L"Example : a search for \"\\bsr\\bsn\" followed by a replace " "\"\\bsn\" changes Windows text files to Unix text files.") TAG (L"#\\bst horizontal tab.") TAG (L"#\\bsv vertical tab.") MAN_END MAN_BEGIN (L"Regular expressions 6. Convenience escape sequences", L"djmw", 20010708) INTRO (L"Convenience escape sequences in a @@Regular expressions|regular " "expression@ present a shorthand for some character classes.") TAG (L"#\\bsd matches a digit: [0-9].") LIST_ITEM1 (L"Example: \"-?\\bsd+\" matches any integer.") TAG (L"#\\bsD %not a digit: [\\^ 0-9].") TAG (L"#\\bsl a letter: [a-zA-Z].") TAG (L"#\\bsL %not a letter: [\\^ a-zA-Z].") TAG (L"#\\bss whitespace: [ \\bst\\bsn\\bsr\\bsf\\bsv].") TAG (L"#\\bsS %not whitespace: [\\^ \\bst\\bsn\\bsr\\bsf\\bsv].") TAG (L"#\\bsw \"word\" character: [a-zA-Z0-9\\_ ].") LIST_ITEM1 (L"Example: \"\\bsw+\" matches a \"word\", i.e., a string of one " "or more characters that may consist of letters, digits and underscores.") TAG (L"#\\bsW %not a \"word\" character: [\\^ a-zA-Z0-9\\_ ].") TAG (L"#\\bsB any character that is %not a word-delimiter.") MAN_END MAN_BEGIN (L"Regular expressions 7. Octal and hexadecimal escapes", L"djmw", 20010709) INTRO (L"An octal number can be represented by the octal escape \"\\bs0\" " "and maximally three digits from the digit class [0-7]. " "The octal number should not exceed \\bs0377. ") NORMAL (L"A hexadecimal number can be represented by the octal escape " "\"\\bsx\" or \"\\bsX\"and maximally two characters from the class " "[0-9A-F]. The maximum hexadecimal number should not exceed \\bsxFF. ") LIST_ITEM1 (L"Example: \\bs053 and \\bsX2B both specify the \"+\" character.") MAN_END MAN_BEGIN (L"Regular expressions 8. Substitution special characters", L"djmw", 20010708) INTRO (L"The substitution string is mostly interpreted as ordinary text except " "for the @@Regular expressions 5. Special control characters|" "special control characters@, the @@Regular expressions 7. Octal and " "hexadecimal escapes|octal and hexadecimal escapes@ and the following " "character combinations:") TAG (L"#\\bs1 ... #\\bs9 are backreferences at sub-expressions 1 ... 9 in the match.") DEFINITION (L"Any of the first nine sub-expressions of the match string can " "be inserted into the replacement string by inserting a `\\bs' followed " "by a digit from 1 to 9 that represents the string matched by a " "parenthesized expression within the regular expression. The numbering " "is left to right.") LIST_ITEM1 (L"Example: A search for \"(a)(b)\" in the string \"abc\", " "followed by a replace \"\\bs2\\bs1\" results in \"bac\".") TAG (L"#& reference at entire match.") DEFINITION (L"The entire string that was matched by the search operation will " "be substituted.") LIST_ITEM1 (L"Example: a search for \".\" in the string \"abcd\" followed by " "the replace \"&&\" doubles every character in the result " "\"aabbccdd\".") TAG (L"#\\bsU #\\bsu to uppercase.") DEFINITION (L"The text inserted by \"&\" or \"\\bs1\" ... \"\\bs9\" is " "converted to %uppercase (\"\\bsu\" only changes the %first character to " "uppercase).") LIST_ITEM1 (L"Example: A search for \"(aa)\" in the string \"aabb\", " "followed by a replace \"\\bsU\\bs1bc\" results in the string \"AAbcbb\".") TAG (L"#\\bsL #\\bsl to lowercase.") DEFINITION (L"The text inserted by \"&\" or \"\\bs1\" ... \"\\bs9\" is " "converted to %lowercase (\"\\bsl\" only changes the %first character to " "lowercase).") LIST_ITEM1 (L"Example: A search for \"(AA)\" with a replace \"\\bsl\\bs1bc\" " "in the string \"AAbb\" results in the string \"aAbcbb\".") MAN_END MAN_BEGIN (L"Roots", L"djmw", 19990608) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Roots " "represents the (complex) roots of a @@Polynomial|polynomial@ function.") ENTRY (L"Commands") NORMAL (L"Creation") LIST_ITEM (L"\\bu @@Polynomial: To Roots@") NORMAL (L"Drawing") LIST_ITEM (L"\\bu ##Draw...# (in the complex plane)") NORMAL (L"Queries") LIST_ITEM (L"\\bu ##Get root...#: get complex root") LIST_ITEM (L"\\bu ##Get real part of root...#") LIST_ITEM (L"\\bu ##Get imaginary part of root...#") MAN_END MAN_BEGIN (L"Scree plot", L"djmw", 20040331) NORMAL (L"A scree plot shows the sorted eigenvalues, from large to " "small, as a function of the eigenvalue index.") MAN_END MAN_BEGIN (L"singular value decomposition", L"djmw", 20120510) INTRO (L"The %%singular value decomposition% (SVD) is a matrix factorization algorithm.") NORMAL (L"For %m > %n, the singular value decomposition of a real %m \\xx %n matrix #A is the " "factorization") FORMULA (L"#A = #U #\\Si #V\\'p,") NORMAL (L"The matrices in this factorization have the following properties:") TAG (L"#U [%m \\xx %n] and #V [%n \\xx %n]") DEFINITION (L"are orthogonal matrices. The columns #u__%i_ of #U =[#u__1_, ..., #u__%n_] " "are the %%left singular vectors%, and the columns #v__%i_ of #V [#v__1_, ..., #v__%n_] " "are the %%right singular vectors%.") TAG (L"#\\Si [%n \\xx %n] = diag (%\\si__1_, ..., %\\si__%n_)") DEFINITION (L"is a real, nonnegative, and diagonal matrix. Its diagonal contains the so called " "%%singular values% %\\si__%i_, where %\\si__1_ \\>_ ... \\>_ %\\si__%n_ \\>_ 0.") NORMAL (L"If %m < %n, the decomposition results in #U [%m \\xx %m] and #V [%n \\xx %m].") MAN_END MAN_BEGIN (L"Sound & Pitch: Change speaker...", L"djmw", 20070722) INTRO (L"A command to create a new Sound object with manipulated characteristics " "from the selected @Sound and @Pitch.") NORMAL (L"With this command you can have finer grained control over the " "pitch than with the @@Sound: Change speaker...@ command. " "Accurate pitch measurement determines the quality of the " "@@overlap-add@ synthesis." ) ENTRY (L"Settings") NORMAL (L"The settings are described in @@Sound: Change speaker...@. ") MAN_END MAN_BEGIN (L"Sound & Pitch: Change gender...", L"djmw", 20070722) /* INTRO (L"Deprecated: use @@Sound & Pitch: Change speaker...@") */ NORMAL (L"A command to create a new Sound object with manipulated characteristics " "from the selected @Sound and @Pitch.") NORMAL (L"With this command you can have finer grained control over the " "pitch than with the @@Sound: Change gender...@ command. " "Accurate pitch measurement determines the quality of the " "@@overlap-add@ synthesis." ) ENTRY (L"Settings") NORMAL (L"The settings are described in @@Sound: Change gender...@. ") MAN_END MAN_BEGIN (L"Sound: Change gender...", L"djmw", 20030205) /* INTRO (L"Deprecated: use @@Sound: Change speaker...@") */ NORMAL (L"A command to create a new @Sound with manipulated characteristics.") ENTRY (L"Settings") NORMAL (L"The quality of the @@overlap-add|manipulation@ depends on the pitch measurement.") NORMAL (L"The arguments that control the pitch measurement are:") TAG (L"##Minimum pitch (Hz)# (standard value: 75 Hz)") DEFINITION (L"pitch candidates below this frequency will not be considered.") TAG (L"##%Maximum pitch (Hz)# (standard value: 600 Hz)") DEFINITION (L"pitch candidates above this frequency will be ignored.") NORMAL (L"The arguments that control the manipulation are:") TAG (L"##Formant shift ratio") DEFINITION (L"determines the frequencies of the formants in the newly created " "Sound. If this ratio equals 1 no frequency shift will occur and " "the formant frequencies will not change. A ratio of 1.1 will change " "a male voice to a voice with approximate female formant characteristics. " "A ratio of 1/1.1 will change a female voice to a voice with approximate male formant " "characteristics.") TAG (L"##New pitch median (Hz)# (standard value: 0.0 Hz, i.e. same as original)") DEFINITION (L"determines what the median pitch of the new Sound will be. " "The pitch values in the newly created Sound will be calculated from the pitch " "values in the selected Sound by multiplying them by a factor " "%%newPitchMedian / oldPitchMedian%. This factor equals 1.0 if the default " "value for the new pitch median (0.0) is chosen. ") TAG (L"##Pitch range factor# (standard value: 1.0)") DEFINITION (L"determines an %extra% scaling of the new pitch values around the %new% " "pitch median. A factor of 1.0 means that no additional pitch modification will occur " "(except the obvious one described above). A factor of 0.0 monotonizes the new " "sound to the new pitch median.") TAG (L"##Duration factor# (standard value: 1.0)") DEFINITION (L"The factor with which the sound will be lengthened. The default is 1.0. " "If you take a value less than 1.0, the resulting sound will be shorter than " "the original. A value larger than 3.0 will not work.") NORMAL (L"If you want more control over the synthesis you can supply your own " "Pitch object and use the @@Sound & Pitch: Change gender...@ command. ") ENTRY (L"Algorithm") NORMAL (L"The shifting of frequencies is done via manipulation of the sampling frequency. " "Pitch and duration changes are generated with @@overlap-add@ synthesis.") NORMAL (L"The new pitch values are calculated in a two step process. We first multiply all " "the pitches with the factor %%newPitchMedian / oldPitchMedian% according to:") FORMULA (L"%newPitch = %pitch * %newPitchMedian / %oldPitchMedian.") NORMAL (L"It follows that if the %newPitchMedian equals the %oldPitchMedian no " "change in pitch values will occur in the first step.") NORMAL (L"Subsequently, the pitch range scale factor determines the final pitch values " "in the following linear manner:") FORMULA (L"%finalPitch = %newPitchMedian + (%newPitch \\-- %newPitchMedian) * %pitchRangeScaleFactor") NORMAL (L"Hence, it follows that no further scaling occurs if %pitchRangeScaleFactor " "equals 1.0.") MAN_END MAN_BEGIN (L"Sound: Change speaker...", L"djmw", 20080515) INTRO (L"A command to create a new @Sound with manipulated characteristics.") ENTRY (L"Settings") NORMAL (L"The quality of the @@overlap-add|manipulation@ depends on the pitch measurement.") NORMAL (L"The arguments that control the pitch measurement are:") TAG (L"##Pitch floor (Hz)# (standard value: 75 Hz)") DEFINITION (L"pitch candidates below this frequency will not be considered.") TAG (L"##Pitch ceiling (Hz)# (standard value: 600 Hz)") DEFINITION (L"pitch candidates above this frequency will be ignored.") NORMAL (L"The arguments that control the manipulation are:") TAG (L"##Multiply formants by") DEFINITION (L"determines the formant frequencies of the newly created sound. " "The formant frequency of the new sound will equal the formant frequencies of the selected sound multiplied by this number. " "If this number equals 1, formant frequencies will not change. A number of 1.1 will change " "a male voice to a voice with approximate female formant characteristics. " "A ratio of 1/1.1 will change a female voice to a voice with approximate male formant " "characteristics.") TAG (L"##Multiply pitch by") DEFINITION (L"determines what the pitch of the new Sound will be. " "The pitch values of the new sound will equal the pitch values of the selected sound multiplied by this number. A value of 1.8 will approximately change a male's pitch to a female's pitch.") TAG (L"##Multiply pitch range by# (standard value: 1.0)") DEFINITION (L"determines the pitch range of the newly created sound. " "A factor of 1.0 means that no additional pitch modification will occur " "(except the obvious one described above). A factor of 0.0 monotonizes the new " "sound to the new pitch median. A negative number inverses the pitch range with respect to the median.") TAG (L"##Multiply duration by# (standard value: 1.0)") DEFINITION (L"determines how to modify the duration of the newly created sound. " "A value of 1.0 means that the new sound will have the same duration as the selected sound. " "A value less than 1.0 will result in a shortened new sound. A value larger than 2.5 will not work.") NORMAL (L"If you want more control over the synthesis you can supply your own " "Pitch object and use the @@Sound & Pitch: Change speaker...@ command. ") ENTRY (L"Algorithm") NORMAL (L"The shifting of formant frequencies is done via manipulation of the sampling frequency. " "To multiply all formants by a factor of 1.10 (i.e. raising them by 10 percent), a sampling " "frequency of 44100 Hz is first raised to 48510 Hz (without changing " "the samples). After this, the sound is lengthened by a factor of 1.10 " "and the pitch is lowered by a factor of 1.10, so that the original " "duration and pitch are restored. After this, the sound is resampled " "to 44100 Hz (by sinc interpolation)." "Pitch and duration changes are generated with @@overlap-add@ synthesis.") MAN_END MAN_BEGIN (L"Sound: Draw where...", L"djmw", 20110213) INTRO (L"A command to draw only those parts of a @Sound where a condition holds.") ENTRY (L"Settings") SCRIPT (5.4, Manual_SETTINGS_WINDOW_HEIGHT (5), L"" Manual_DRAW_SETTINGS_WINDOW ("Sound: Draw where...", 5) Manual_DRAW_SETTINGS_WINDOW_RANGE("Time range (s)", "0.0", "0.0 (=all)") Manual_DRAW_SETTINGS_WINDOW_RANGE ("Vertical range", "0.0", "0.0 (=all)") Manual_DRAW_SETTINGS_WINDOW_BOOLEAN("Garnish", 1) Manual_DRAW_SETTINGS_WINDOW_OPTIONMENU("Drawing method", "Curve") Manual_DRAW_SETTINGS_WINDOW_TEXT ("Draw only those parts where the following condition holds", "x < xmin + (xmax - xmin) / 2; first half") ) TAG (L"##Time range (s)") DEFINITION (L"selects the time domain for the drawing.") TAG (L"##Vertical range") DEFINITION (L"defines the vertical limits; larger amplitudes will be clipped.") TAG (L"##Draw only those parts where the following condition holds#") DEFINITION (L"determines the part of the sound that will be drawn. All parts where the formula evaluates to true will be drawn. " "This formula may ##not# contain references to the sampling of the sound, i.e. don't use 'col', 'x1', 'dx' and 'ncol' in it.") ENTRY (L"Example 1") NORMAL (L"The following script draws all amplitudes larger than one in red.") CODE (L"Create Sound from formula... s Mono 0 1 2000 1.8*sin(2*pi*5*x)+randomGauss(0,0.1)") CODE (L"Red") CODE (L"Draw where... 0 0 -2 2 n Curve abs(self)>1") CODE (L"Black") CODE (L"Draw where... 0 0 -2 2 y Curve not (abs(self)>1)") SCRIPT (8, 3, L"Create Sound from formula... s Mono 0 1 2000 1.8*sin(2*pi*5*x)+randomGauss(0,0.1)\n" "Red\n" "Draw where... 0 0 -2 2 n Curve abs(self)>1\n" "Black\n" "Draw where... 0 0 -2 2 y Curve not (abs(self)>1)\n" "Remove\n" ) ENTRY (L"Example 2") NORMAL (L"Draw the second half of a sound:") CODE (L"Draw where... 0 0 -1 1 n Curve x > xmin + (xmax - xmin) / 2") ENTRY (L"Example 3") NORMAL (L"Draw only positive amplitudes:") CODE (L"Draw where... 0 0 -1 1 n Curve self>0") ENTRY (L"Example 4") NORMAL (L"Draw parts where pitch is larger than 300 Hz in red:") CODE (L"s = selected (\"Sound\")") CODE (L"p = To Pitch... 0 75 600") CODE (L"pt = Down to PitchTier") CODE (L"select s") CODE (L"Red") CODE (L"Draw where... 0 0 -1 1 yes Curve Object_'pt'(x) > 300") CODE (L"Black") CODE (L"Draw where... 0 0 -1 1 yes Curve not (Object_'pt'(x) > 300)") MAN_END MAN_BEGIN (L"Sound: Fade in...", L"djmw", 20080314) INTRO (L"A command to gradually increase the amplitude of a selected @Sound.") ENTRY (L"Settings") TAG (L"##Channel") DEFINITION (L"determines whether you want to fade all channels or only the left of the right channel.") TAG (L"##Time (s)") DEFINITION (L"determines where the fade-in will take place. If %time is earlier than the start time of the sound, the start time of the sound wil be used.") TAG (L"##Fade time (s)") DEFINITION (L"determines the start point and the endpoint of the fade-in with respect to the %time argument. Depending on the sign of %%fadeTime%, %time is either the start or the end position of the fade-in. If %%fadeTime% is positive, fade-in will take place between %%time% and %%time+fadeTime%. If %%fadeTime% is negative, fade-in wil take place between %%time+fadeTime% and %time.") TAG (L"##Silent from start") DEFINITION (L"when on, makes the sound silent before the fade-in starts. " "When off, the sound before the fade-in starts will not be changed. ") ENTRY (L"Algorithm") NORMAL (L"Multiplication with the first half period of a (1-cos(x))/2 function. ") ENTRY (L"Cross-fading two sounds") NORMAL (L"The following script cross-fades two sounds s1 and s2 at time 1 second and leaves the result in s2.") CODE1 (L"crossFTime = 0.5") CODE1 (L"t = 1") CODE1 (L"Create Sound from formula... s1 Mono 0 2 44100 sin(2*pi*500*x)") CODE1 (L"Fade out... All t-crossFTime/2 crossFTime y") CODE1 (L"Create Sound from formula... s2 Mono 0 2 44100 sin(2*pi*1000*x)") CODE1 (L"Fade in... All t-crossFTime/2 crossFTime y") CODE1 (L"Formula... self+Sound_s1[]") MAN_END MAN_BEGIN (L"Sound: Fade out...", L"djmw", 20080314) INTRO (L"A command to gradually decrease the amplitude of a selected @Sound.") ENTRY (L"Settings") TAG (L"##Channel") DEFINITION (L"determines whether you want to fade all channels or only the left of the right channel.") TAG (L"##Time (s)") DEFINITION (L"determines where the fade-out will take place. If %time is later than the end time of the sound, the end time of the sound wil be used.") TAG (L"##Fade time (s)") DEFINITION (L"determines the start point and the endpoint of the fade-out with respect to the %time argument. Depending on the sign of %%fadeTime%, %time is either the start or the end position of the fade-out. If %%fadeTime% is positive, fade-out will take place between %%time% and %%time+fadeTime%. If %%fadeTime% is negative, fade-out wil take place between %%time+fadeTime% and %time.") TAG (L"##Silent to end") DEFINITION (L"Make the sound silent after the fade-out finishes. ") ENTRY (L"Algorithm") NORMAL (L"Multiplication with the first half period of a (1+cos(%%x%))/2 function.") MAN_END MAN_BEGIN (L"Sound: Filter (gammatone)...", L"djmw", 19980712) INTRO (L"A command to filter a Sound by a fourth order gammatone bandpass filter.") ENTRY (L"Settings") TAG (L"##Centre frequency (Hz)#, ##Bandwidth (Hz)#") DEFINITION (L"determine the passband of the filter.") ENTRY (L"Algorithm") NORMAL (L"The impulse response of the filter is a 4-th order @@gammatone@. This " "filter is implemented as a simple 8-th order recursive digital filter with " "4 zeros and 8 poles (these 8 poles consist of one conjugate pole pair to the " "4-th power). In the Z-domain its formula is: ") FORMULA (L"%#H (%z) = (1 + \\su__%i=1..4_ %a__%i_%z^^%\\--i^) / " "(1 + \\su__%j=1..8_ %b__%j_%z^^%\\--j^)") NORMAL (L"The derivation of the filter coefficients %a__%i_ and %b__%j_ is " "according to @@Slaney (1993)@. " "The gain of the filter is scaled to unity at the centre frequency.") MAN_END MAN_BEGIN (L"Sound: To BarkFilter...", L"djmw", 20010404) INTRO (L"A command that creates a @BarkFilter object from every selected " "@Sound object by @@band filtering in the frequency domain@ with a " "bank of filters.") NORMAL (L"The filter functions used are:") FORMULA (L"10 log %#H(%z) = 7 - 7.5 * (%z__%c_ - %z - 0.215) - 17.5 * \\Vr " "(0.196 + (%z__%c_ - %z - 0.215)^2)") NORMAL (L"where %z__%c_ is the central (resonance) frequency of the filter in Bark. " "The bandwidths of these filters are constant and equal 1 Bark.") MAN_END MAN_BEGIN (L"Sound: To FormantFilter...", L"djmw", 20010404) INTRO (L"A command that creates a @FormantFilter object from every selected " "@Sound object by @@band filtering in the frequency domain@ with a " "bank of filters whose bandwidths depend on the pitch of the signal.") NORMAL (L"The analysis proceeds in two steps:") LIST_ITEM (L"1. We perform a pitch analysis (see @@Sound: To Pitch...@ for " "details).") LIST_ITEM (L"2. We perform a filter bank analysis on a linear frequency scale. " "The bandwidth of the filters depends on the measured pitch (see @@Sound & " "Pitch: To FormantFilter...@ for details).") MAN_END MAN_BEGIN (L"Sound: Paint where...", L"djmw", 20110213) INTRO (L"A command to paint only those parts of a @Sound where a condition holds. The painted area is the area " "between the Sound and a horizontal line at a certain level.") ENTRY (L"Settings") SCRIPT (5.4, Manual_SETTINGS_WINDOW_HEIGHT (6), L"" Manual_DRAW_SETTINGS_WINDOW ("Sound: Paint where...", 6) Manual_DRAW_SETTINGS_WINDOW_FIELD ("Colour (0-1, name, {r,g,b})", "0.5") Manual_DRAW_SETTINGS_WINDOW_RANGE("Time range (s)", "0.0", "0.0 (=all)") Manual_DRAW_SETTINGS_WINDOW_RANGE ("Vertical range", "0.0", "0.0 (=all)") Manual_DRAW_SETTINGS_WINDOW_FIELD ("Fill from level", "0") Manual_DRAW_SETTINGS_WINDOW_BOOLEAN("Garnish", 1) Manual_DRAW_SETTINGS_WINDOW_TEXT ("Paint only those parts where the following condition holds", "1; always") ) TAG (L"##Colour") DEFINITION (L"defines the @@Colour|colour@ of the paint.") TAG (L"##Time range (s)") DEFINITION (L"selects the time domain for the drawing.") TAG (L"##Vertical range") DEFINITION (L"defines the vertical limits; larger amplitudes will be clipped.") TAG (L"##Fill from level") DEFINITION (L"defines the level of the horizontal line. ") TAG (L"##Formula") DEFINITION (L"determines the part of the sound that will be painted. All parts where the formula evaluates to true will be painted. " "This formula may ##not# contain references to the sampling of the sound, i.e. don't use 'col', 'x1', 'dx' and 'ncol' in it.") ENTRY (L"Example 1") NORMAL (L"The following script paints the area under a sine curve in red and the area above in green." "For the first paint the horizontal line is at y=-1, for the second paint the line is at y=+1. " "The formula always evaluates to true.") CODE (L"s = Create Sound from formula... s Mono 0 1 10000 0.5*sin(2*pi*5*x)") CODE (L"Paint where... Red 0 0 -1 1 -1 y 1") CODE (L"Paint where... Green 0 0 -1 1 1 n 1") SCRIPT (8, 5, L"s = Create Sound from formula... s Mono 0 1 10000 0.5*sin(2*pi*5*x)\n" "Paint where... Red 0 0 -1 1 -1 n 1\n" "Paint where... Green 0 0 -1 1 1 y 1\n" "Remove\n") ENTRY (L"Example 2") NORMAL (L"The following script paints the area below zero in red and the area above in green." "The horizontal line is now always at y=0 and we use the formula to differentiate the areas.") CODE (L"s = Create Sound from formula... s Mono 0 1 10000 0.5*sin(2*pi*5*x)") CODE (L"Paint where... Red 0 0 -1 1 0 n self>0") CODE (L"Paint where... Green 0 0 -1 1 0 y self<0") SCRIPT (8, 5, L"s = Create Sound from formula... s Mono 0 1 10000 0.5*sin(2*pi*5*x)\n" "Paint where... Red 0 0 -1 1 0 n self<0\n" "Paint where... Green 0 0 -1 1 0 y self>0\n" "Remove\n") ENTRY (L"Example 3") NORMAL (L"To give an indication that the area under a 1/x curve between the points %a and %b and the area " "between %c and %d are equal if %b/%a = %d/%c. For example, for %a=1, %b=2, %c=4 and %d=8: ") CODE (L"Create Sound from formula... 1dx Mono 0 20 100 1/x") CODE (L"Draw... 0 20 0 1.5 yes Curve") CODE (L"Paint where... Grey 0 20 0 1.5 0 yes (x >= 1 and x <2) or (x>=4 and x<8)") CODE (L"One mark bottom... 1 y y n") CODE (L"One mark bottom... 2 y y n") CODE (L"One mark bottom... 4 y y n") CODE (L"One mark bottom... 8 y y n") SCRIPT (8, 5, L"Create Sound from formula... 1dx Mono 0 20 100 1/x\n" "Draw... 0 20 0 1.5 yes Curve\n" "Paint where... Grey 0 20 0 1.5 0 yes (x >= 1 and x <2) or (x>=4 and x<8)\n" "One mark bottom... 1 y y n\n" "One mark bottom... 2 y y n\n" "One mark bottom... 4 y y n\n" "One mark bottom... 8 y y n\n" "Remove\n") MAN_END MAN_BEGIN (L"Sounds: Paint enclosed...", L"djmw", 20110524) INTRO (L"Paints the area between the two selected @@Sound@s. ") ENTRY (L"Settings") SCRIPT (5.4, Manual_SETTINGS_WINDOW_HEIGHT (4), L"" Manual_DRAW_SETTINGS_WINDOW ("Sounds: Paint enclosed", 4) Manual_DRAW_SETTINGS_WINDOW_FIELD ("Colour (0-1, name, {r,g,b})", "0.5") Manual_DRAW_SETTINGS_WINDOW_RANGE("Time range (s)", "0.0", "0.0 (=all)") Manual_DRAW_SETTINGS_WINDOW_RANGE ("Vertical range", "0.0", "0.0 (=all)") Manual_DRAW_SETTINGS_WINDOW_BOOLEAN("Garnish", 1) ) TAG (L"##Colour") DEFINITION (L"defines the @@Colour|colour@ of the paint.") TAG (L"##Time range (s)") DEFINITION (L"selects the time domain for the drawing.") TAG (L"##Vertical range") DEFINITION (L"defines the vertical limits, larger amplitudes will be clipped.") ENTRY (L"Example") NORMAL (L"The following script paints the area enclosed between a sine tone of 5 Hz and the straight line %y = %x/2.") CODE (L"s1 = Create Sound from formula... sine Mono 0 1 10000 1/2 * sin(2*pi*5*x)") CODE (L"s2 = Create Sound from formula... line Mono 0 1 10000 x / 2") CODE (L"plus s1") CODE (L"Paint enclosed... Grey 0 0 -1 1 yes") SCRIPT ( 4, 2, L"s1 = Create Sound from formula... sine Mono 0 1 10000 1/2 * sin(2*pi*5*x)\n" "s2 = Create Sound from formula... line Mono 0 1 10000 x / 2\n" "plus s1\n" "Paint enclosed... Grey 0 0 -1 1 yes\n" "Remove\n") MAN_END MAN_BEGIN (L"Sound: To Polygon...", L"djmw", 20110620) INTRO (L"A command that creates a @@Polygon@ from a selected @@Sound@, where the Polygon's " " points are defined by the (%time, %amplitude) pairs of the sound. ") ENTRY (L"Settings") TAG (L"##Channel") DEFINITION (L"defines which channel of the sound is used.") TAG (L"##Time range (s)") DEFINITION (L"defines the part of the sound whose (%time, %amplitude) pairs have to be included.") TAG (L"##Vertical range") DEFINITION (L"defines the vertical limits, larger amplitudes will be clipped.") TAG (L"##Connection y-value") DEFINITION (L"defines the y-value of the first and last point of the Polygon. This gives the opportunity to " " draw a closed Polygon with the horizontal connection line at any position you like. ") ENTRY (L"Example") NORMAL (L"The following script paints the area under a sound curve in red and the area above in green.") CODE (L"s = Create Sound from formula... s Mono 0 1 10000 0.5*sin(2*pi*5*x)") CODE (L"\\# Connection y-value is at amplitude -1: area under the curve.") CODE (L"p1 = To Polygon... 1 0 0 -1 1 -1") CODE (L"Paint... {1,0,0} 0 0 -1 1") CODE (L"select s") CODE (L"\\# Connection y-value is now at amplitude 1: area above the curve.") CODE (L"p2 = To Polygon... 1 0 0 -1 1 1") CODE (L"Paint... {0,1,0} 0 0 -1 1") SCRIPT (4.5, 2, L"s = Create Sound from formula... s Mono 0 1 10000 0.5*sin(2*pi*5*x)\n" "p1 = To Polygon... 1 0 0 -1 1 -1\n" "Paint... {1,0,0} 0 0 -1 1\n" "Remove\n" "select s\n" "p2 = To Polygon... 1 0 0 -1 1 1\n" "Paint... {0,1,0} 0 0 -1 1\n" "plus s\n" "Remove\n" ) MAN_END #define xxx_to_TextGrid_detectSilences_COMMON_PARAMETERS_HELP \ TAG (L"##Silence threshold (dB)") \ DEFINITION (L"determines the maximum silence intensity value in dB with respect to the maximum " \ "intensity. For example, if %imax is the maximum intensity in dB then the maximum silence " \ "intensity is calculated as %%imax - silenceThreshold%; intervals with an intensity smaller " \ "than this value are considered as silent intervals.") \ TAG (L"##Minimum silent interval duration (s)") \ DEFINITION (L"determines the minimum duration for an interval to be considered as silent. " \ "If you don't want the closure for a plosive to count as silent then use a large enough value.") \ TAG (L"##Minimum sounding interval duration (s)") \ DEFINITION (L"determines the minimum duration for an interval to be ##not# considered as silent. " \ "This offers the possibility to filter out small intense bursts of relatively short duration.") \ TAG (L"##Silent interval label") \ DEFINITION (L"determines the label for a silent interval in the TextGrid.") \ TAG (L"##Sounding interval label") \ DEFINITION (L"determines the label for a sounding interval in the TextGrid.") MAN_BEGIN (L"Sound: To TextGrid (silences)...", L"djmw", 20061205) INTRO (L"A command that creates a @TextGrid in which the silent and sounding intervals of the selected @Sound are marked.") ENTRY (L"Settings") xxx_to_TextGrid_detectSilences_COMMON_PARAMETERS_HELP ENTRY (L"Algorithm") NORMAL (L"First the intensity is determined according to the @@Sound: To Intensity...@ command. " "Next the silent and sounding intervas are determined as in the @@Intensity: To TextGrid (silences)...@ command.") MAN_END MAN_BEGIN (L"Intensity: To TextGrid (silences)...", L"djmw", 20061201) INTRO (L"A command that creates a @TextGrid in which the silent and sounding intervals of the selected @Intensity are marked.") ENTRY (L"Settings") xxx_to_TextGrid_detectSilences_COMMON_PARAMETERS_HELP ENTRY (L"Algorithm") NORMAL (L"First the intensity contour is evaluated and the intervals above and below the silence threshold are marked as " "%sounding and %silent. " "We then remove sounding intervals with a duration smaller than the %%Minimum sounding interval duration%. " "This step is followed by joining the neighbouring silent intervals that resulted because of this removal. " "Finally we remove silent intervals with a duration smaller than the %%Minimum silent interval duration%. " "This is followed by joining the neighbouring sounding intervals that resulted because of this removal.") NORMAL (L"Experience showed that first removing short intensity bursts instead of short silences gave better results than doing it the other way around.") ENTRY (L"Important") NORMAL (L"The effectiveness of the %%Minimum silent interval duration% and %%Minimum sounding interval duration% " "depends on the effective analysis window duration that was used to determine the intensity contour. " "For example, if you have chosen 100 Hz for the \"Minimum pitch\" parameter in the @@Sound: To Intensity...@ analysis, " "the effective analysis window duration was 32 ms. Don't expect to find sounding " "or silent intervals with a duration smaller than this effective analysis window duration.") MAN_END MAN_BEGIN (L"Sound: Trim silences...", L"djmw", 20120323) INTRO (L"A command that creates from the selected @Sound a new sound in which all silence durations are not longer than a specified value.") ENTRY (L"Settings") TAG (L"%%Trim duration (s)%,") DEFINITION (L"specifies the maximum allowed silence duration.") TAG (L"%%Minimum pitch (Hz)%, and, %Time step (s)%,") DEFINITION (L"determine how we measure the intensities on which the determination of silent intervals is based. See @@Sound: To Intensity...@ for more info.") TAG (L"%%Silence threshold (dB)%, %%Minimum silent interval duration (s)%, and %%Minimum sounding interval duration%,") DEFINITION (L"determine how the silent intervals will be determined. See @@Intensity: To TextGrid (silences)...@ for more info.") TAG (L"%%Save trimming info as TextGrid%,") DEFINITION (L"determines if a TextGrid with trimming information will also be created. The TextGrid will have one tier where interval of the %%originating% sound that were trimmed have been labeled. ") TAG (L"%%Trim label%,") DEFINITION (L"determines the label that the trimmed intervals in the TextGrid will get.") MAN_END MAN_BEGIN (L"Sound & Pitch: To FormantFilter...", L"djmw", 20010404) INTRO (L"A command that creates a @FormantFilter object from the selected " "@Sound and @Pitch objects by @@band filtering in the frequency domain@ with a " "bank of filters whose bandwidths depend on the Pitch.") NORMAL (L"The filter functions used are:") FORMULA (L"%#H(%f, %F__0_) = 1 / (((%f__%c_^^2^ - %f^2) /%f\\.c%B(%F__0_)))^2 + 1),") NORMAL (L"where %f__%c_ is the central (resonance) frequency of the filter. " "%B(%F__0_) is the bandwidth in Hz and determined as") FORMULA (L"%B(%F__0_) = %relativeBandwidth\\.c%F__0_, ") NORMAL (L"where %F__0_ is the fundamental frequency as determined from the Pitch " "object. Whenever the value of %F__0_ is undefined, a value of 100 Hz is taken.") MAN_END MAN_BEGIN (L"Sound: To MelFilter...", L"djmw", 20010404) INTRO (L"A command that creates a @MelFilter object from every selected " "@Sound object by @@band filtering in the frequency domain@ with a " "bank of filters.") NORMAL (L"The filter functions used are triangular in shape on a %linear " "frequency scale. The filter function depends on three parameters, the " "lower frequency %f__%l_, the central frequency %f__%c_ and the higher " "frequency %f__%h_. " "On a %mel scale, the distances %f__%c_-%f__%l_ and %f__%h_-%f__%c_ " "are the same for each filter and are equal to the distance between the " "%f__%c_'s of successive filters. The filter function is:" ) FORMULA (L"%#H(%f) = 0 for %f \\<_ %f__%l_ and %f \\>_ %f__%h_") FORMULA (L"%#H(%f) = (%f - %f__%l_) / (%f__%c_ - %f__%l_) for %f__%l_ \\<_ %f \\<_ %f__%c_") FORMULA (L"%#H(%f) = (%f__%h_ - %f) / (%f__%h_ - %f__%c_) for %f__%c_ \\<_ %f \\<_ %f__%h_") MAN_END MAN_BEGIN (L"Sound: To Pitch (shs)...", L"djmw", 19970402) INTRO (L"A command that creates a @Pitch object from every selected @Sound object.") ENTRY (L"Purpose") NORMAL (L"to perform a pitch analysis based on a spectral compression model. " "The concept of this model is that each spectral component not only activates " "those elements of the central pitch processor that are most sensitive to the " "component's frequency, but also elements that have a lower harmonic " "relation with this component. Therefore, when a specific element of the " "central pitch processor is most sensitive at a frequency %f__0_, it receives " "contributions from spectral components in the " "signal at integral multiples of %f__0_.") ENTRY (L"Algorithm") NORMAL (L"The spectral compression consists of the summation of a sequence of " "harmonically compressed spectra. " "The abscissa of these spectra is compressed by an integral factor, the rank " "of the compression. The maximum of the resulting sum spectrum is the " "estimate of the pitch. Details of the algorithm can be " "found in @@Hermes (1988)@") ENTRY (L"Settings") TAG (L"##Time step (s)# (standard value: 0.01 s)") DEFINITION (L"the measurement interval (frame duration), in seconds.") TAG (L"##Minimum pitch (Hz)# (standard value: 50 Hz)") DEFINITION (L"candidates below this frequency will not be recruited. This parameter " "determines the length of the analysis window.") TAG (L"##Max. number of candidates# (standard value: 15)") DEFINITION (L"The maximum number of candidates that will be recruited.") TAG (L"##Maximum frequency (Hz)# (standard value: 1250 Hz)") DEFINITION (L"higher frequencies will not be considered.") TAG (L"##Max. number of subharmonics# (standard value: 15)") DEFINITION (L"the maximum number of harmonics that add up to the pitch.") TAG (L"##Compression factor# (standard value: 0.84)") DEFINITION (L"the factor by which successive compressed spectra are multiplied before the summation.") TAG (L"##Number of points per octave# (standard value: 48)") DEFINITION (L"determines the sampling of the logarithmic frequency scale.") TAG (L"##Ceiling (Hz)# (standard value: 500 Hz)") DEFINITION (L"candidates above this frequency will be ignored.") MAN_END MAN_BEGIN (L"Spectra: Multiply", L"djmw", 20100318) INTRO (L"Returns a new Spectrum object that is the product of the two selected " "@Spectrum objects.") MAN_END MAN_BEGIN (L"Spectrum: Conjugate", L"djmw", 20031023) INTRO (L"Reverses the sign of the complex part of the selected @Spectrum object(s).") NORMAL (L"For real signals, conjugation in the spectral domain amounts to time-inversion in the time domain.") MAN_END MAN_BEGIN (L"SpeechSynthesizer", L"djmw", 20120413) INTRO (L"The SpeechSynthesizer is one of the @@types of objects@ in Praat. It creates a speech sound from text. The actual text-to-speech synthesis is performed by the @@Espeak@ speech synthsizer and therefore our SpeechSynthsizer is merely an interface to Espeak.") ENTRY (L"Commands") NORMAL (L"Creation:") LIST_ITEM (L"\\bu @@Create SpeechSynthesizer...@") NORMAL (L"Playing:") LIST_ITEM (L"\\bu @@SpeechSynthesizer: Play text...|Play text...@") LIST_ITEM (L"\\bu @@SpeechSynthesizer: To Sound...|To Sound...@") NORMAL (L"Modification:") LIST_ITEM (L"\\bu @@SpeechSynthesizer: Set text input settings...|Set text input settings...@") LIST_ITEM (L"\\bu @@SpeechSynthesizer: Set speech output settings...|Set speech output settings...@") MAN_END MAN_BEGIN (L"Create SpeechSynthesizer...", L"djmw", 20120221) INTRO (L"Creates the @@Espeak@ speech synthesizer.") ENTRY (L"Settings") TAG (L"##Language#") DEFINITION (L"determines the language of the synthesizer.") TAG (L"##Voice variant#") DEFINITION (L"determines which voice type the synthesizer uses (male, female or whispered voices).") MAN_END MAN_BEGIN (L"SpeechSynthesizer: Play text...", L"djmw", 20120413) INTRO (L"The selected @@SpeechSynthesizer@ plays a text") ENTRY (L"Settings") TAG (L"##Text#") DEFINITION (L"is the text to be played. Text within [[ ]] is treated as phonemes codes in @@Kirshenbaum phonetic encoding@. For example, besides a text like \"This is text\", you might also input \"This [[Iz]] text\".") MAN_END MAN_BEGIN (L"SpeechSynthesizer: To Sound...", L"djmw", 20120414) INTRO (L"The selected @@SpeechSynthesizer@ converts a text to the corresponding speech sound.") ENTRY (L"Settings") TAG (L"##Text#") DEFINITION (L"is the text to be played. Text within [[ ]] is treated as phonemes codes in @@Kirshenbaum phonetic encoding@. For example, besides a text like \"This is text\", you might also input \"This [[Iz]] text\".") TAG (L"##Create TextGrid with annotations#") DEFINITION (L"determines whether, besides the sound, a TextGrid with multiple-tier annotations will appear.") MAN_END MAN_BEGIN (L"SpeechSynthesizer: Set text input settings...", L"djmw", 20120414) INTRO (L"A command available in the ##Modify# menu when you select a @@SpeechSynthesizer@.") ENTRY (L"Settings") TAG (L"##Input text format is#") DEFINITION (L"determines how the input text will be synthesized.") TAG (L"##Input phoneme codes are#") DEFINITION (L"") MAN_END MAN_BEGIN (L"SpeechSynthesizer: Set speech output settings...", L"djmw", 20120414) INTRO (L"A command available in the ##Modify# menu when you select a @@SpeechSynthesizer@.") ENTRY (L"Settings") TAG (L"##Sampling frequency#") DEFINITION (L"determines how the sampling frequency of the sound.") TAG (L"##Gap between words#") DEFINITION (L"determines the amount of silence between words.") TAG (L"##Pitch adjustment#") DEFINITION (L"") TAG (L"##Pitch range#") DEFINITION (L"") TAG (L"##Words per minute#") DEFINITION (L"determines the speaking rate in words per minute.") TAG (L"##estimate words per minute from data#") DEFINITION (L"") TAG (L"##Output phoneme codes are#") MAN_END MAN_BEGIN (L"SSCP", L"djmw", 19981103) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type SSCP represents the sums of squares and cross products of " "a multivariate data set.") NORMAL (L"Besides the matrix part, an object of type SSCP also contains a " "vector with centroids.") ENTRY (L"Inside a SSCP") NORMAL (L"With @Inspect you will see that this type contains the same " "attributes as a @TableOfReal with the following extras:") TAG (L"%numberOfObservations") TAG (L"%centroid") MAN_END MAN_BEGIN (L"SSCP: Draw sigma ellipse...", L"djmw", 19990222) INTRO (L"A command to draw for the selected @SSCP an ellipse that " "covers a part of the multivariate data.") ENTRY (L"Setting") TAG (L"##Number of sigmas") DEFINITION (L"determines the @@concentration ellipse|data coverage@.") MAN_END MAN_BEGIN (L"SSCP: Get sigma ellipse area...", L"djmw", 20000525) INTRO (L"A command to query the selected @SSCP object for the area of a " "sigma ellipse.") ENTRY (L"Algorithm") NORMAL (L"The algorithm proceeds as follows:") LIST_ITEM (L"1. The four array elements in the SSCP-matrix that correspond to the chosen dimensions " "are copied into a two-dimensional matrix #%S (symmetric of course).") LIST_ITEM (L"2. The eigenvalues of #%S are determined, call them %s__1_ and %s__2_.") LIST_ITEM (L"3. The lengths %l__%i_ of the axes of the ellipse can be obtained as the " "square root of the %s__i_ multiplied by a scale factor: %l__%i_ = %scaleFactor \\.c " "\\Vr (%s__%i_ ), " "where %scaleFactor = %numberOfSigmas / \\Vr(%numberOfObservations \\-- 1).") LIST_ITEM (L"4. The area of the ellipse will be %\\pi\\.c%l__1_\\.c%l__2_.") MAN_END MAN_BEGIN (L"SSCP: Get confidence ellipse area...", L"djmw", 20000525) INTRO (L"A command to query the selected @SSCP object for the area of a " "confidence ellipse.") ENTRY (L"Algorithm") NORMAL (L"The algorithm proceeds as follows:") LIST_ITEM (L"1. The four array elements in the SSCP-matrix that correspond to the chosen dimensions " "are copied into a two-dimensional matrix #%S (symmetric of course).") LIST_ITEM (L"2. The eigenvalues of #%S are determined, call them %s__1_ and %s__2_.") LIST_ITEM (L"3. The lengths %l__1_ and %l__2_ of the two axes of the ellipse can be obtained as " "(see for example @@Johnson (1998)@, page 410): ") FORMULA (L" %l__%i_ = %scaleFactor \\.c \\Vr (%s__%i_ ),") LIST_ITEM (L" where") FORMULA (L"%scaleFactor = \\Vr (%f \\.c %p \\.c (%n \\-- 1) / (%n \\.c (%n \\-- %p))),") LIST_ITEM (L" in which %f = $$@@invFisherQ@$ (1 \\-- %confidenceLevel, %p, %n \\-- %p), " "where %p is the numberOfRows from the SSCP object and %n the %numberOfObservations.") LIST_ITEM (L"4. The area of the ellipse will be %\\pi\\.c%l__1_\\.c%l__2_.") MAN_END MAN_BEGIN (L"SSCP: Get diagonality (bartlett)...", L"djmw", 20011111) INTRO (L"Tests the hypothesis that the selected @SSCP matrix object is " "diagonal.") ENTRY (L"Setting") TAG (L"##Number of constraints") DEFINITION (L"modifies the number of independent observations. " "The default value is 1.") ENTRY (L"Algorithm") NORMAL (L"The test statistic is |#R|^^N/2^, the N/2-th power of the determinant" " of the correlation matrix. @@Bartlett (1954)@ developed the following " "approximation to the limiting distribution:") FORMULA (L"\\ci^2 = -(%N - %numberOfConstraints - (2%p + 5) /6) ln |#R|") NORMAL (L"In the formula's above, %p is the dimension of the correlation " "matrix, %N-%numberOfConstraints is the number of independent " "observations. Normally %numberOfConstraints would " "equal 1, however, if the matrix has been computed in some other way, " "e.g., from within-group sums of squares and cross-products of %k " "independent groups, %numberOfConstraints would equal %k.") NORMAL (L"We return the probability %\\al as ") FORMULA (L"%\\al = chiSquareQ (\\ci^2 , %p(%p-1)/2).") NORMAL (L"A very low %\\al indicates that it is very improbable that the " "matrix is diagonal.") MAN_END MAN_BEGIN (L"SSCP: Get fraction variation...", L"djmw", 20040210) INTRO (L"A command to ask the selected @SSCP object for the fraction " "of the total variation that is accounted for by the selected dimension(s).") NORMAL (L"Further details can be found in @@Covariance: Get fraction variance...@.") MAN_END MAN_BEGIN (L"SSCP: To CCA...", L"djmw", 20031103) INTRO (L"A command that creates a @@CCA|canonical correlation@ object from the " "selected @SSCP object.") ENTRY (L"Setting") TAG (L"##Dimension of dependent variate (ny)") DEFINITION (L"defines a partition of the square %n x %n SSCP matrix S into the parts S__yy_ of " "dimension %ny x %ny, S__xx_ of dimension %nx x %nx, and the parts " "S__xy_ and S__yx_ of dimensions %nx x %ny and %ny x %nx, respectively.") ENTRY (L"Algorithm") NORMAL (L"The partition for the square SSCP-matrix is as follows:") PICTURE (2.0, 2.0, drawPartionedMatrix) NORMAL (L"The canonical correlation equations we have to solve are:") FORMULA (L"(1) (#S__%yx_ #S__%xx_^^-1^ #S__%yx_\\'p -\\la #S__%yy_)#y = #0") FORMULA (L"(2) (#S__%yx_\\'p #S__%yy_^^-1^ #S__%yx_ -\\la #S__%xx_)#x = #0") NORMAL (L"where #S__%yy_ [%ny \\xx %ny] and #S__%xx_ [%nx \\xx %nx] are " "symmetric, positive definite matrices belonging to the dependent and the " "independent variables, respectively. ") NORMAL (L"These two equations are not independent and we will show that both " "equations have the same eigenvalues and that the eigenvectors #x for " "equation (2) can be obtained from the eigenvectors #y of equation (1).") NORMAL (L"We can solve equation (1) in several ways, however, the numerically " "stablest algorithm is probably by performing first a Cholesky decomposition " "of #S__xx_ and #S__yy_, followed by a @@generalized singular value " "decomposition@. The algorithm goes as follows:") NORMAL (L"The Cholesky decompositions (\"square roots\") of #S__yy_ and #S__xx_ are:") FORMULA (L"#S__yy_ = #U\\'p #U and #S__xx_ = #H\\'p #H,") NORMAL (L"where #U and H are upper triangular matrices. From these decompositions, " "the inverse for #S__xx_^^-1^ is easily computed. Let #K be the inverse of #H, " "then we can write: ") FORMULA (L"#S__xx_^^-1^ = #K #K\\'p.") NORMAL (L"We next substitute in equation (1) and rewrite as:") FORMULA (L"((#K\\'p#S__yx_\\'p)\\'p (#K\\'p#S__yx_\\'p) - \\la #U\\'p #U)#x = 0") NORMAL (L"This equation can be solved for eigenvalues and eigenvectors by the " "generalized singular value decomposition because it is of the form " "#A\\'p#A -\\la #B\\'p#B.") NORMAL (L"Now, given the solution for equation (1) we can find the solution " "for equation (2) by first multiplying (1) from the left with " "#S__yx_\\'p#S__yy_^^-1^, resulting in:") FORMULA (L"(#S__yx_\\'p#S__yy_^^-1^#S__yx_#S__xx_^^-1^#S__yx_\\'p -\\la #S__yx_\\'p) #y = 0") NORMAL (L"Now we split of the term #S__xx_^^-1^#S__yx_\\'p and obtain:") FORMULA (L"(#S__yx_\\'p#S__yy_^^-1^#S__yx_ - \\la #S__xx_) #S__xx_^^-1^#S__yx_\\'p #y = 0") NORMAL (L"This equation is like equation (2) and it has therefore the same eigenvalues " "and eigenvectors. (We also proved this fact in the algorithmic section of " "@@TableOfReal: To CCA...@.)") NORMAL (L"The eigenvectors #x is now") FORMULA (L"#x = #S__xx_^^-1^#S__yx_\\'p #y.") MAN_END MAN_BEGIN (L"SSCP: To Covariance...", L"djmw", 20090624) INTRO (L"A command that creates a @Covariance object from each selected @SSCP object.") ENTRY (L"Setting") TAG (L"##Number of constraints") DEFINITION (L"determines the factor by which each entry in the " "SSCP-matrix is scaled to obtain the Covariance matrix.") ENTRY (L"Details") NORMAL (L"The relation between the numbers %c__%ij_ in the covariance matrix and the numbers %s__%ij_ in " "the originating SSCP matrix is:") FORMULA (L"%c__%ij_ = %s__%ij_ / (%numberOfObservations - %numberOfConstraints)") NORMAL (L"Normally %numberOfConstraints will equal 1. However, when the SSCP was the " "result of summing %g SSCP objects, as is, for example, the case when you obtained the total " "within-groups SSCP from pooling the individual group SSCP's, %numberOfConstraints will equal the number of pooled SSCP's, %g.") MAN_END MAN_BEGIN (L"SSCP & TableOfReal: Extract quantile range...", L"djmw", 20040225) INTRO (L"Extract those rows from the selected @TableOfReal object whose Mahalanobis " "distance, with respect to the selected @SSCP object, are within the " "quantile range.") MAN_END MAN_BEGIN (L"T-test", L"djmw", 20020117) INTRO (L"A test on the mean of a normal variate when the variance is unknown.") NORMAL (L"In Praat, the t-test is used to query a @Covariance object and:") LIST_ITEM (L"1. get the significance of one mean. See @@Covariance: Get " "significance of one mean...@.") LIST_ITEM (L"2. get the significance of the %difference between two means. " "See @@Covariance: Get significance of means difference...@.") NORMAL (L"You should use a t-test when you want to test a hypothesis about " "the mean of one column in a @TableOfReal object, or, if you want to test " "a hypothesis about the difference between the means of two columns in " "this object.") NORMAL (L"You can perform these t-tests in Praat by first transforming the " "TableOfReal object into a Covariance object (see @@TableOfReal: To " "Covariance@) and then choosing the appropriate query method on the " "latter object.") MAN_END MAN_BEGIN (L"BHEP multivariate normality test", L"djmw", 20101124) INTRO (L"The Baringhaus–Henze–Epps–Pulley multivariate normality test.") NORMAL (L"According to @@Henze & Wagner (1997)@ the test has:") LIST_ITEM (L"\\bu affine invariance,") LIST_ITEM (L"\\bu consistency against each fixed nonnormal alternative distribution,") LIST_ITEM (L"\\bu asymptotic power against contiguous alternatives of order \\Vr (%n),") LIST_ITEM (L"\\bu feasibility for any dimension and any sample size.") NORMAL (L"The test depends on a smoothing parameter %%h% that can be chosen in various ways:") NORMAL (L"@@Henze & Wagner (1997)@ recommend %h = 1.41, while") NORMAL (L"@@Tenreiro (2009)@ recommends %h__%%s% _= 0.448 + 0.026\\.c%d for short tailed alternatives and " " %h__%%l%_ = 0.928 + 0.049\\.c%d for long tailed alternatives.") MAN_END MAN_BEGIN (L"Table: Get median absolute deviation...", L"djmw", 20120405) INTRO (L"Get the median absolute deviation (MAD) of the column in the selected @@Table@ (adjusted by a scale factor).") ENTRY (L"Algorithm") NORMAL (L"From the %n numbers %x__1_, %x__2_, ..., %x__%n_ in the selected column we first calculate the @@quantile algorithm|median@ " "value %x__median_. Next we calculate the %n absolute deviations from this median: %d__1_, %d__2_, ..., %d__%n_, " "where %d__%j_=|%x__%j_ - %x__median_|. " "Then we calculate the MAD value, which is the median of the %n values %d__1_, %d__2_, ..., %d__%n_. Finally we multiply the MAD " "value by the scale factor 1.4826. This last multiplication makes the result comparable with the value of the standard deviation if " "the %x values are normally distributed.") MAN_END MAN_BEGIN (L"TableOfReal: Report multivariate normality (BHEP)...", L"djmw", 20090701) INTRO (L"Report about multivariate normality according to the @@BHEP multivariate normality test@.") ENTRY (L"Settings") TAG (L"##Smoothing parameter") DEFINITION (L"determines the smoothing parameter %h.") MAN_END MAN_BEGIN (L"TableOfReal: Change row labels...", L"djmw", 20010822) INTRO (L"Changes the row labels of the selected @TableOfReal object according " "to the specification in the search and replace fields.") NORMAL (L"Both search and replace fields may contain @@regular expressions|" "Regular expressions@. The ##Replace limit# parameter limits the number of " "replaces that may occur within each label.") MAN_END MAN_BEGIN (L"TableOfReal: Change column labels...", L"djmw", 20010822) INTRO (L"Changes the column labels of the selected @TableOfReal object according " "to the specification in the search and replace fields.") NORMAL (L"Both search and replace fields may contain @@regular expressions|" "Regular expressions@. The %%Replace limit% parameter limits the number of " "replaces that may occur within each label.") MAN_END MAN_BEGIN (L"TableOfReal: Draw biplot...", L"djmw", 20020603) INTRO (L"A command to draw a biplot for each column in the selected " "@TableOfReal object.") ENTRY (L"Settings") TAG (L"##Xmin#, ##Xmax#, ##Ymin#, ##Ymax#") DEFINITION (L"determine the drawing boundaries.") TAG (L"##Split factor") DEFINITION (L"determines the weighing of the row and column structure " "(see below).") ENTRY (L"Behaviour") LIST_ITEM (L"1. Get the @@singular value decomposition@ #U #\\Si #V\\'p of the " "table.") LIST_ITEM (L"2. Calculate weighing factors %\\la for row and columns") FORMULA (L"%\\la__r,1_ = %\\si__1_^^%splitFactor^") FORMULA (L"%\\la__c,1_ = %\\si__1_^^1-%splitFactor^") FORMULA (L"%\\la__r,2_ = %\\si__2_^^%splitFactor^") FORMULA (L"%\\la__c,2_ = %\\si__2_^^1-%splitFactor^") DEFINITION (L"where %\\si__1_ and %\\si__2_ are the first and the second singular values") LIST_ITEM (L"3. For the rows (%i from 1..%numberOfRows) form:") FORMULA (L"%xr__%i_ = %U__%i1_ %\\la__%r,1_") FORMULA (L"%yr__%i_ = %U__%i2_ %\\la__%r,2_") LIST_ITEM (L"4. For the columns (%i from 1..%numberOfColumns) form:") FORMULA (L"%xc__%i_ = %V__%i1_ %\\la__%c,1_") FORMULA (L"%yc__%i_ = %V__%i2_ %\\la__%c,2_") LIST_ITEM (L"5. Plot the points (%xr__%i_, yr__%i_) and (%xc__%i_, yc__%i_) in the " "same figure with the corresponding row and column labels.") MAN_END MAN_BEGIN (L"TableOfReal: Draw box plots...", L"djmw", 20000523) INTRO (L"A command to draw a @@box plot@ for each column in the selected " "@TableOfReal object.") ENTRY (L"Settings") TAG (L"##From row#, ##To row#, ##From column#, ##To column#") DEFINITION (L"determine the part of the table that you want to analyse.") TAG (L"%Ymin and %Ymax") DEFINITION (L"determine the drawing boundaries.") MAN_END MAN_BEGIN (L"TableOfReal: Draw rows as histogram...", L"djmw", 20030619) INTRO (L"A command to draw a histogram from the rows in the selected " "@TableOfReal object.") NORMAL (L"The histogram will consist of %groups of bars. The number of groups will " "be determined by the number of selected columns from the table, while the " "number of bars within each group will be determined from the number of " "selected rows.") ENTRY (L"Settings") TAG (L"##Row numbers# and ##Column range#") DEFINITION (L"determine the part of the table that you want to draw. " "The column range determines the number of bars that you want to draw for " "each row selected by the %%Row numbers% argument.") TAG (L"##Ymin# and ##Ymax#") DEFINITION (L"the drawing boundaries.") NORMAL (L"The following arguments are all relative to the width of a bar " "in the histogram. ") TAG (L"##Horizontal offset") DEFINITION (L"the offset from the left and right margin.") TAG (L"##Distance between bar groups") DEFINITION (L"the distance between each group, i.e., the distance " "between the right side of the last bar in a group to the left side of " "the first bar in the next group.") TAG (L"##Distance between bars") DEFINITION (L"the distance between the bars in a group.") TAG (L"##Grey values") DEFINITION (L"the grey values of the bars in a group.") ENTRY (L"Bar positioning") NORMAL (L"If you want to put the labels yourself you will need the following information.") NORMAL (L"The width of a bar is determined as follows:") FORMULA (L"%width = 1 / (%nc \\.c %nr + 2 \\.c %hoffset + (%nc - 1)\\.c %intergroup +" "%nc\\.c(%nr -1)\\.c %interbar),") NORMAL (L"where %nc is the number of columns (groups) to draw, %nr is the number of " "rows to draw (the number of bars within a group), %hoffset is the horizontal " "offset, %intergroup the distance between each group and %interbar " "the distance between the bars within a group.") NORMAL (L"The spacing between the bars drawn from a row:") FORMULA (L"%dx = (%intergroup + %nr + (%nr -1) \\.c %interbar) *% width") NORMAL (L"The first bar for the %k-th row starts at:") FORMULA (L"%x1 = %hoffset \\.c %width + (%k - 1) \\.c (1 + %interbar) \\.c %width") MAN_END MAN_BEGIN (L"TableOfReal: Select columns where row...", L"djmw", 20020502) INTRO (L"Copy columns from the selected @TableOfReal object to a new " "TableOfReal object.") ENTRY (L"Settings") TAG (L"##Columns") DEFINITION (L"defines the indices of the columns to be selected. Ranges can be " "defined with a colon \":\". Columns will be selected in the specified " "order.") TAG (L"##Row condition") DEFINITION (L"specifies a condition for the selection of rows. If the " "condition evaluates as %true for a particular row, the selected elements " "in this row will be copied. See @@Matrix: Formula...@ for the kind of " "expressions that can be used here.") ENTRY (L"Examples") CODE (L"Select columns where row... \"1 2 3\" 1") CODE (L"Select columns where row... \"1 : 3\" 1") NORMAL (L"Two alternative expressions to copy the first three columns to a new table " "with the same number of rows.") CODE (L"Select columns where row... \"3 : 1\" 1") NORMAL (L"Copy the first three columns to a new table with the same number of " "rows. The new table will have the 3 columns reversed.") CODE (L"Select columns where row... \"1:6 9:11\" self[row,8]>0") NORMAL (L"Copy the first six columns and columns 9, 10, and 11 to a new table. " "Copy only elements from rows where the element in column 8 is greater " "than zero.") MAN_END MAN_BEGIN (L"TableOfReal: Standardize columns", L"djmw", 19990428) INTRO (L"Standardizes each column of the selected @TableOfReal.") NORMAL (L"The entries %x__%ij_ in the TableOfReal will change to:") FORMULA (L"(%x__%ij_ \\-- %\\mu__%j_) / %\\si__%j_, ") NORMAL (L"where %\\mu__%j_ and %\\si__%j_ are the mean and the standard deviation as calculated " "from the %j^^th^ column, respectively. After standardization all column means will equal zero " "and all column standard deviations will equal one.") MAN_END MAN_BEGIN (L"TableOfReal: To Configuration (lda)...", L"djmw", 19981103) INTRO (L"Calculates a @Configuration based on the @Discriminant scores obtained " "from the selected @TableOfReal. Row labels in the table indicate group membership.") ENTRY (L"Setting") TAG (L"##Number of dimensions") DEFINITION (L"determines the number of dimensions of the resulting Configuration.") ENTRY (L"Algorithm") NORMAL (L"First we calculate the Discriminant from the data in the TableOfReal. " "See @@TableOfReal: To Discriminant@ for details.") NORMAL (L"The eigenvectors of the Discriminant determine the directions that " "the data in the TableOfReal will be projected unto.") MAN_END MAN_BEGIN (L"TableOfReal: To Configuration (pca)...", L"djmw", 19980909) INTRO (L"Calculates a @Configuration based on the principal components from the " "selected @TableOfReal.") ENTRY (L"Setting") TAG (L"##Number of dimensions") DEFINITION (L"determines the number of dimensions of the resulting Configuration.") ENTRY (L"Algorithm") NORMAL (L"We form principal components without explicitly calculating the covariance matrix " "#C = #M\\'p\\.c#M, where #M is the matrix part of the TableOfReal. ") LIST_ITEM (L"1. Make the singular value decomposition of #M. This results in " "#M = #U\\.c#d\\.c#V\\'p.") LIST_ITEM (L"2. Sort singular values #d and corresponding row vectors in #V (descending).") LIST_ITEM (L"3. The principalComponent__%ij_ = \\su__%k=1..%numberOfColumns_ %M__%ik_ \\.c %V__%jk_.") ENTRY (L"Remark") NORMAL (L"The resulting configuration is unique up to reflections along the new principal directions.") MAN_END MAN_BEGIN (L"TableOfReal: To Correlation", L"djmw", 20020105) INTRO (L"A command that creates a (%Pearson) @Correlation object from every " "selected @TableOfReal object. The correlations are calculated between " "columns.") ENTRY (L"Algorithm") NORMAL (L"The linear correlation coefficient %r__%ij_ (also called the %%product" " moment correlation coefficient% or %%Pearson's correlation coefficient%) " " between the elements of columns %i and %j is calculated as:") FORMULA (L"%r__%ij_ = \\Si__%k_ (%x__%ki_ - %mean__%i_)(%x__%kj_ - %mean__%j_)/" "(\\Vr (\\Si__%k_(%x__%ki_ - %mean__%i_)^2) \\Vr (\\Si__%k_(%x__%kj_ -" " %mean__%j_)^2)),") NORMAL (L"where %x__%mn_ is the element %m in column %n, and %mean__%n_ " "is the mean of column %n.") MAN_END MAN_BEGIN (L"TableOfReal: To Correlation (rank)", L"djmw", 20020105) INTRO (L"A command that creates a (%%Spearman rank-order%) @Correlation object " "from every selected @TableOfReal object. The correlations are calculated " "between columns.") ENTRY (L"Algorithm") NORMAL (L"The Spearman rank-order correlation coefficient %r__%ij_ between " "the elements of columns %i and %j is calculated as the linear correlation" " of the ranks:") FORMULA (L"%r__%ij_ = \\Si__%k_ (%R__%ki_ - %Rmean__%i_) " "(%R__%kj_ - %Rmean__%j_) / (\\Vr (\\Si__%k_(%R__%ki_ - %Rmean__%i_)^2) " "\\Vr (\\Si__%k_(%R__%kj_ - %Rmean__%j_)^2)),") NORMAL (L"where %R__%mn_ is the rank of element %m in column %n, " "and %Rmean__%n_ is the mean of the ranks in column %n.") MAN_END MAN_BEGIN (L"TableOfReal: To Covariance", L"djmw", 20020117) INTRO (L"A command that creates a @Covariance object from every " "selected @TableOfReal object. The covariances are calculated between " "columns.") ENTRY (L"Algorithm") NORMAL (L"The covariance coefficients %s__%ij_ " " between the elements of columns %i and %j are defined as:") FORMULA (L"%s__%ij_ = \\Si__%k_ (%x__%ki_ - %mean__%i_)(%x__%kj_ - %mean__%j_)/" "(%numberOfObservations - %numberOfConstraints),") NORMAL (L"where %x__%ki_ is the element %k in column %i, %mean__%i_ " "is the mean of column %i, %numberOfObservations equals the number of rows in " "the table, and %numberOfConstraints equals 1.") NORMAL (L"The actual calculation goes as follows") LIST_ITEM (L"1. Centralize each column (subtract the mean).") LIST_ITEM (L"2. Get its @@singular value decomposition@ #U #\\Si #V\\'p.") LIST_ITEM (L"3. Form #S = #V #\\Si #V\\'p.") LIST_ITEM (L"4. Divide all elements in #S by (%numberOfObservations - 1).") MAN_END MAN_BEGIN (L"TableOfReal: To Discriminant", L"djmw", 19990104) INTRO (L"A command that creates a @Discriminant object from every selected " "@TableOfReal object. Row labels in the table indicate group membership.") ENTRY (L"Algorithm") NORMAL (L"We solve for directions #x that are eigenvectors of the generalized " "eigenvalue equation:") FORMULA (L"#%B #x - %\\la #%W #x = 0,") NORMAL (L"where #%B and #%W are the between-groups and the within-groups sums of " "squares and cross-products matrices, respectively. Both #%B and #%W are symmetric " "matrices. Standard formula show that both matrices can also " "be written as a matrix product. The formula above then transforms to:") FORMULA (L"#%B__1_\\'p#%B__1_ #x - %\\la #%W__1_\\'p#%W__1_ #x = 0") NORMAL (L"The equation can be solved with the @@generalized singular value decomposition@. " "This procedure is numerically very stable and can even cope with cases when both " "matrices are singular.") NORMAL (L"The a priori probabilities in the Discriminant will be calculated from the number of " "%training vectors %n__%i_ in each group:") FORMULA (L"%aprioriProbability__%i_ = %n__%i_ / \\Si__%k=1..%numberOfGroups_ %n__%k_") MAN_END MAN_BEGIN (L"TableOfReal: To PCA", L"djmw", 19980106) INTRO (L"A command that creates a @PCA object from every selected " "@TableOfReal object.") MAN_END MAN_BEGIN (L"TableOfReal: To SSCP...", L"djmw", 19990218) INTRO (L"Calculates Sums of Squares and Cross Products (@SSCP) from the selected @TableOfReal.") ENTRY (L"Algorithm") NORMAL (L"The sums of squares and cross products %s__%ij_ " " between the elements of columns %i and %j are calculated as:") FORMULA (L"%s__%ij_ = \\Si__%k_ (%x__%ki_ - %mean__%i_)(%x__%kj_ - %mean__%j_),") NORMAL (L"where %x__%mn_ is the element %m in column %n and %mean__%n_ " "is the mean of column %n.") MAN_END MAN_BEGIN (L"TableOfReal: To Pattern and Categories...", L"djmw", 20040429) INTRO (L"Extracts a @Pattern and a @Categories from the selected @TableOfReal.") NORMAL (L"The selected rows and columns are copied into the Pattern and " "the corresponding row labels are copied into a Categories. ") MAN_END MAN_BEGIN (L"TableOfReal: To CCA...", L"djmw", 20020424) INTRO (L"A command that creates a @CCA object from the selected " "@TableOfReal object.") ENTRY (L"Settings") TAG (L"%%Dimension of dependent variate (ny)") DEFINITION (L"defines the partition of the table into the two parts whose " "correlations will be determined. The first %ny columns must be the " "dependent part, the rest of the columns will be interpreted as the " "independent part (%nx columns). In general %nx must be larger than or " "equal to %ny.") ENTRY (L"Behaviour") NORMAL (L"Calculates canonical correlations between the %dependent and the " "%independent parts of the table. The corresponding " "canonical coefficients are also determined.") ENTRY (L"Algorithm") NORMAL (L"The canonical correlation equations for two data sets #T__%y_ " "[%n \\xx %p] and #T__%x_ [n \\xx %q] are:") FORMULA (L"(1) (#S__%yx_ #S__%xx_^^-1^ #S__%yx_\\'p -\\la #S__%yy_)#y = #0") FORMULA (L"(2) (#S__%yx_\\'p #S__%yy_^^-1^ #S__%yx_ -\\la #S__%xx_)#x = #0") NORMAL (L"where #S__%yy_ [%p \\xx %p] and #S__%xx_ [%q \\xx %q] are the " "covariance matrices of data sets #T__%y_ and #T__%x_, respectively, " "#S__%yx_ [%p \\xx %q] is the matrix of covariances between data sets " "#T__%y_ and #T__%x_, and the vectors #y and #x are the %%canonical " "weights% or the %%canonical function coefficients% for the dependent and " "the independent data, respectively. " "In terms of the (dependent) data set #T__%y_ and the (independent) data set " "#T__%x_, these covariances can be written as:") FORMULA (L"#S__%yy_ = #T__%y_\\'p #T__%y_, #S__%yx_ = #T__%y_\\'p #T__%x_ and " "#S__%xx_ = #T__%x_\\'p #T__%x_.") NORMAL (L"The following @@singular value decomposition@s ") FORMULA (L"#T__%y_ = #U__%y_ #D__%y_ #V__%y_\\'p and #T__%x_ = #U__%x_ #D__%x_ " "#V__%x_\\'p ") NORMAL (L"transform equation (1) above into:") FORMULA (L"(3) (#V__%y_ #D__%y_ #U__%y_\\'p#U__%x_ #U__%x_\\'p #U__%y_ #D__%y_ " "#V__%y_\\'p - \\la #V__%y_ #D__%y_ #D__%y_ #V__%y_\\'p)#y = 0 ") NORMAL (L"where we used the fact that:") FORMULA (L"#S__%xx_^^-1^ = #V__%x_ #D__%x_^^-2^ #V__%x_\\'p.") NORMAL (L"Equation (3) can be simplified by multiplication from the left by " "#D__%y_^^-1^ #V__%y_' to:") FORMULA (L" (4) ((#U__%x_\\'p #U__%y_)\\'p (#U__%x_\\'p #U__%y_) - \\la #I)#D__%y_ " "#V__%y_\\'p #y = #0") NORMAL (L"This equation can, finally, be solved by a substitution of the s.v.d " "of #U__%x_\\'p #U__%y_ = #U #D #V\\'p into (4). This results in") FORMULA (L"(5) (#D^^2^ - \\la #I) #V\\'p #D__%y_ #V__%y_\\'p #y = #0") NORMAL (L"In an analogous way we can reduce eigenequation (2) to:") FORMULA (L"(6) (#D^^2^ - \\la #I) #U\\'p #D__%x_ #V__%x_\\'p #x = #0") NORMAL (L"From (5) and (6) we deduce that the eigenvalues in both equations " "are equal to the squared singular values of the product matrix " "#U__%x_\\'p#U__%y_. " "These singular values are also called %%canonical " "correlation coefficients%. The eigenvectors #y and #x can be obtained " "from the columns of the following matrices #Y and #X:") FORMULA (L"#Y = #V__%y_ #D__%y_^^-1^ #V") FORMULA (L"#X = #V__%x_ #D__%x_^^-1^ #U") NORMAL (L"For example, when the vector #y equals the first column of #Y and " "the vector #x equals " "the first column of #X, then the vectors #u = #T__%y_#y and #v = #T__%x_#x " "are the linear combinations from #T__%y_ and #T__%x_ that have maximum " "correlation. Their correlation coefficient equals the first canonical " "correlation coefficient.") MAN_END MAN_BEGIN (L"TableOfReal: To TableOfReal (means by row labels)...", L"djmw", 20050221) INTRO (L"A command that appears in the ##Multivariate statistics# menu if you select a @@TableOfReal@. " "It calculates the multivariate means for the different row labels from the selected TableOfReal.") ENTRY (L"Setting") TAG (L"##Expand") DEFINITION (L"when %off, then for a table with %n rows and %m different labels (%m\\<_%n), the resulting table will have %m rows. " "When %on, the dimensions of the resulting table will be the same as the originating, and corresponding means substituded " "in each row.") ENTRY (L"Example") NORMAL (L"The following commands") CODE (L"@@Create TableOfReal (Pols 1973)...@ 0") CODE (L"To TableOfReal (means by row labels)... 0") NORMAL (L"will result in a new TableOfReal that has 12 rows. Each row will contain the mean F1, F2 and F3 values for a particular vowel. These means " " were obtained from 50 representations of that vowel.") NORMAL (L"If we had chosen the %expansion:") CODE (L"To TableOfReal (means by row labels)... 1") NORMAL (L"the resulting TableOfReal would have had 600 rows. This representation comes in handy when, for example, you have to calculate deviations from the mean.") MAN_END MAN_BEGIN (L"TextGrid: Extend time...", L"djmw", 20020702) INTRO (L"Extends the domain of the selected @TextGrid object.") ENTRY (L"Settings") TAG (L"##Extend domain by") DEFINITION (L"defines the amount of time by which the domain will be extended.") TAG (L"##At") DEFINITION (L"defines whether starting times or finishing times will be " "modified.") ENTRY (L"Behaviour") NORMAL (L"We add an extra (empty) interval into each %%interval tier%. " "This is necessary to keep original intervals intact. According to the " "value of the second argument, the new interval will be added at the " "beginning or at the end of the tier.") NORMAL (L"For %%point tiers% only the domain will be changed.") MAN_END MAN_BEGIN (L"TIMIT acoustic-phonetic speech corpus", L"djmw", 19970320) INTRO (L"A large American-English speech corpus that resulted from the joint efforts " "of several American research sites.") NORMAL (L"The TIMIT corpus contains a total of 6300 sentences, 10 sentences spoken by " "630 speakers selected from 8 major dialect regions of the USA. 70\\% of " "the speakers are male, 30\\% are female.") NORMAL (L"The text corpus design was done by the Massachusetts Institute of " "Technology (MIT), Stanford Research Institute and Texas Instruments (TI). " "The speech was recorded at TI, transcribed at MIT, and has been maintained, " "verified and prepared for CDROM production by the American National Institute " "of Standards and Technology (NIST) (@@Lamel et al. (1986)@).") MAN_END MAN_BEGIN (L"VowelEditor", L"djmw", 20111124) INTRO (L"An Editor for generating vowel-like @@sound|Sound@s from mouse movements.") ENTRY (L"How to get a sound") NORMAL (L"With the mouse button down, you can move the mouse cursor around in the plane " "spanned by the first two formants. While you move the cursor around, the positions you trace will be " "indicated by blue dots. After you release the mouse button, the color of the trajectory will change " "to black and you will hear the vowel-like sound whose " "first two formants follow this trajectory. The small bars on the trajectory are time markers. With " "default settings time markers are at 50 milliseconds apart and they may give you an indication of the speed you traversed the trajectory.") ENTRY (L"The interface") NORMAL (L"In the lower part of the editor a number of buttons and fields are displayed.") TAG (L"##Play") DEFINITION (L"will play the trajectory.") TAG (L"##Reverse") DEFINITION (L"will reverse the trajectory and play it.") TAG (L"##Publish") DEFINITION (L"will publish the sound in the list of objects.") TAG (L"##Duration (s)") DEFINITION (L"allows to modify the duration of the current trajectory. ") TAG (L"##Extend (s)") DEFINITION (L"determines the duration of the straight line trajectory that connects the endpoint of the current trajectory with the startpoint of a new trajectory. You may extend the current trajectory by starting a new trajectory with the shift button pressed. After you finished the new trajectory, three trajectories will be appended: the current one, the straight line one and the new one.") TAG (L"##Start F0 (Hz)") DEFINITION (L"determines the fundamental frequency at the start of the trajectory.") TAG (L"##F0 slope (oct/s)") DEFINITION (L"determines how many octaves the pitch will changes during the course of the trajectory.") NORMAL (L"The bottom line in the Editor displays the first and second formant frequency and the fundamental frequency at the start point and the endpoint of the trajectory.") ENTRY (L"Edit menu") TAG (L"##Set F0...") DEFINITION (L"Set pitch and slope.") TAG (L"##Set F3 & F4...") DEFINITION (L"Set the frequencies and bandwidths for the third and fourth formant.") TAG (L"##Reverse trajectory") DEFINITION (L"Reverses the trajectory (like editor button).") // ?? TAG (L"##Modify trajectory duration...") DEFINITION (L"Modifies trajectory duration (like editor field).") // ?? TAG (L"##New trajectory...") DEFINITION (L"Set startpoint, endpoint and duration of a new trajectory.") TAG (L"##Extend trajectory...") DEFINITION (L"Extend current trajectory to...") TAG (L"##Shift trajectory...") DEFINITION (L"Shift current trajectory.") ENTRY (L"View menu") TAG (L"##F1 & F2 range...#") DEFINITION (L"Modify the horizontal and vertical scales.") TAG (L"##Show vowel marks from fixed set...#") DEFINITION (L"Show the vowel marks in the editor from a fixed set of vowel inventories.") TAG (L"##Show vowel marks from Table file...#") DEFINITION (L"Put your own marks in the editor. The Table needs to have at least three mandatory columns " "labeled \"Vowel\", \"F1\" and \"F2\" and " "one optional column labeled \"Size\". The Vowel column contains the vowel marker labels, the F1 and " "F2 columns have the first and second formant frequencies in Hertz. The optional Size column contains " "the font size of the vowel markers.") TAG (L"##Show trajectory time markers every...") DEFINITION (L"Shows time markers as small bars orthogonal to the trajectory. ") ENTRY (L"Publishing") TAG (L"##Publish Sound") TAG (L"##Extract FormantTier") TAG (L"##Extract PitchTier") DEFINITION (L"Publish the Sound, the PitchTier and the FormantTier from the trajectory.") TAG (L"##Draw trajectory...") DEFINITION (L"Draws the trajectory in the picture window") MAN_END MAN_BEGIN (L"VowelEditor: Show vowel marks from Table file...", L"djmw", 20111124) INTRO (L"A command in the @@VowelEditor@ that lets you set your own vowel marks. ") ENTRY (L"Layout of the Table") NORMAL (L"The Table needs at least three mandatory columns labeled \"Vowel\", \"F1\" and \"F2\" and " "one optional column labeled \"Size\". The Vowel column contains the vowel marker labels, the F1 and " "F2 columns have the first and second formant frequencies in Hertz. The optional Size column contains " "the font size of the vowel markers.") MAN_END /********************** GSL ********************************************/ MAN_BEGIN (L"incompleteBeta", L"djmw", 20071024) TAG (L"##incompleteBeta (%a, %b, %x)") DEFINITION (L"I__x_(%a,%b) = 1/beta(%a,%b)\\in__0_^%x %t^^%a-1^(1-%t)^^%b-1^ dt,") NORMAL (L"for 0 \\<_ %x \\<_ 1 and %a and %b and %a+%b not equal to a negative integer.") //double incompleteBeta (double a, double b, double x); //Pre: 0<= x <= 1; a> 0, b>0 //Def: $I_x(a,b)=B_x(a,b)/B(a,b)=1/B(a,b) \int_0^x t^{a-1}(1-t)^{b-1)dt$ //Limiting values: $I_0(a,b)=0 I_1(a,b)=1$ //Symmetry: $I_x(a,b) = 1 - I_{1-x}(b,a)$ MAN_END MAN_BEGIN (L"incompleteGammaP", L"djmw", 20071024) TAG (L"##incompleteGammaP (%a, %x)") DEFINITION (L"incompleteGammaP = 1/\\Ga(%a)\\in__0_^%x e^^-%t^%t^^%a-1^ dt,") NORMAL (L"For %x\\>_ 0 and %a not a negative integer.") MAN_END MAN_BEGIN (L"lnBeta", L"djmw", 20071024) TAG (L"##lnBeta (%a, %b)") DEFINITION (L"Computes the logarithm of the #beta function, subject to %a and %b and %a+%b not being negative integers.") MAN_END /********************* References **************************************/ MAN_BEGIN (L"Bai & Demmel (1993)", L"djmw", 19981007) NORMAL (L"Z. Bai & J. Demmel (1993): \"Computing the generalized singular value " "decomposition.\" %%SIAM J. Sci. Comput.% #14: 1464\\--1486.") MAN_END MAN_BEGIN (L"Bartlett (1954)", L"djmw", 20011111) NORMAL (L"M.S. Bartlett (1954): \"A note on multiplying factors for various " "chi-squared approximations.\", %%Joural of the Royal Statistical Society, " "Series B% #16: 296\\--298") MAN_END MAN_BEGIN (L"Boomsma (1977)", L"djmw", 20020524) NORMAL (L"A. Boomsma (1977): \"Comparing approximations of confidence intervals " "for the product-moment correlation coefficient.\" %%Statistica Neerlandica% " "#31: 179-186.") MAN_END MAN_BEGIN (L"Cooley & Lohnes (1971)", L"djmw", 20060322) NORMAL (L"W.W. Colley & P.R. Lohnes (1971): %%Multivariate data analysis%. " "John Wiley & Sons.") MAN_END MAN_BEGIN (L"Davis & Mermelstein (1980)", L"djmw", 20010419) NORMAL (L"S.B. Davis & P. Mermelstein (1980), \"Comparison of parametric " "representations for monosyllabic word recognition in continuously " "spoken sentences.\" " "%%IEEE Transactions on ASSP% #28: 357\\--366.") MAN_END MAN_BEGIN (L"Efron & Tibshirani (1993)", L"djmw", 20031103) NORMAL (L"B. Efron & R.J. Tibshirani (1993): %%An introduction " "to the bootstrap%. Chapman & Hall.") MAN_END MAN_BEGIN (L"Espeak", L"djmw", 20111217) NORMAL (L"Jonathan Duddington's Espeak speech synthesizer, available via http://espeak.sourceforge.net/") MAN_END MAN_BEGIN (L"Flanagan (1960)", L"djmw", 19980713) NORMAL (L"J.L. Flanagan (1960): \"Models for approximating basilar membrane " "displacement.\" %%Bell System Technical Journal% #39: 1163\\--1191.") MAN_END MAN_BEGIN (L"Friedl (1997)", L"djmw", 20010710) NORMAL (L"J.E.F. Friedl (1997): %%Mastering Regular Expressions%. " "O'Reilly & Associates.") MAN_END MAN_BEGIN (L"Greiner & Hormann (1998)", L"djmw", 20110617) NORMAL (L"G. Greiner & K. Hormann (1998): \"Efficient clipping of arbitrary polygons.\" %%ACM Transactions on Graphics% #17: 71\\--83.") MAN_END MAN_BEGIN (L"Heath et al. (1986)", L"djmw", 19981007) NORMAL (L"M.T. Heath, J.A. Laub, C.C. Paige & R.C. Ward (1986): \"Computing the " "singular value decomposition of a product of two matrices.\" " "%%SIAM J. Sci. Statist. Comput.% #7: 1147\\--1159.") MAN_END MAN_BEGIN (L"Hermes (1988)", L"djmw", 19980123) NORMAL (L"D.J. Hermes (1988): \"Measurement of pitch by subharmonic " "summation.\" %%Journal of the Acoustical Society of America% #83: 257\\--264.") MAN_END MAN_BEGIN (L"Henze & Wagner (1997)", L"djmw", 20090630) NORMAL (L"N. Henze & T. Wagner (1997): \"A new npproach to the BHEP Tests for Multivariate Normality.\" " "%%Journal of Multivariate Analysis% #62: 1\\--23.") MAN_END MAN_BEGIN (L"Hormann & Agathos (2001)", L"djmw", 20110617) NORMAL (L"K. Hormann & A. Agathos (2001): \"The point in polygon problem for arbitrary polygons.\" " "%%Computational Geometry% #20: 131\\--144.") MAN_END MAN_BEGIN (L"Irino & Patterson (1997)", L"djmw", 20100517) NORMAL (L"T. Irino & R.D. Patterson (1997): \"A time-domain, level-dependent " "auditory filter: The gammachirp.\" %%Journal of the Acoustical Society of America% #101: 412\\--419.") MAN_END MAN_BEGIN (L"Johannesma (1972)", L"djmw", 19980123) NORMAL (L"P.I.M. Johannesma (1972): \"The pre-response stimulus ensemble of " "neurons in the cochlear nucleus.\" In %%Symposium on Hearing Theory% " "(IPO, Eindhoven, Holland), 58\\--69.") MAN_END MAN_BEGIN (L"Johnson (1998)", L"djmw", 20000525) NORMAL (L"D.E. Johnson (1998): %%Applied Multivariate methods%.") MAN_END MAN_BEGIN (L"Kim & Kim (2006)", L"djmw", 20110617) NORMAL (L"D.H. Kim & M.-J. Kim (2006): \"An extension of polygon clipping to resolve degenerate cases.\" %%Computer-Aided Design & Applications% #3: 447\\--456.") MAN_END MAN_BEGIN (L"Krishnamoorthy & Yu (2004)", L"djmw", 20090813) NORMAL (L"K. Krishnamoortht & J. Yu (2004): \"Modified Nel and Van der Merwe test for multivariate " "Behrens-Fisher problem.\" %%Statistics & Probability Letters% #66: 161\\--169.") MAN_END MAN_BEGIN (L"Lamel et al. (1986)", L"djmw", 19980123) NORMAL (L"L.F. Lamel, R.H. Kassel & S. Sennef (1986): \"Speech Database " "Development: Design and Analysis of the Acoustic-Phonetic Corpus.\" " "%%Proc. DARPA Speech Recognition Workshop%, Report No. SAIC-86/1546, " "100\\--119.") MAN_END MAN_BEGIN (L"Morrison (1990)", L"djmw", 19980123) NORMAL (L"D.F. Morrison (1990): %%Multivariate Statistical Methods%. " "New York: McGraw-Hill.") MAN_END MAN_BEGIN (L"Peterson & Barney (1952)", L"djmw", 20020620) NORMAL (L"G.E. Peterson & H.L. Barney (1952): \"Control methods used in a study " "of the vowels.\" %%Journal of the Acoustical Society of America% #24: 175\\--184") MAN_END MAN_BEGIN (L"Pols et al. (1973)", L"djmw", 19990426) NORMAL (L"L.C.W. Pols, H.R.C. Tromp & R. Plomp (1973): " "\"Frequency analysis of Dutch vowels from 50 male speakers.\" " "%%Journal of the Acoustical Society of America% #53: 1093\\--1101.") MAN_END MAN_BEGIN (L"Press et al. (1992)", L"djmw", 19980114) NORMAL (L"W.H. Press, S.A. Teukolsky, W.T. Vetterling & B.P. Flannery (1992): " "%%Numerical recipes in C: The art of scientific computing%. " "Second Edition. Cambridge University Press.") MAN_END MAN_BEGIN (L"Sakoe & Chiba (1978)", L"djmw", 20050302) NORMAL (L"H. Sakoe & S. Chiba (1978): \"Dynamic programming algorithm optimization for spoken word recognition.\" " "%%Transactions on ASSP% #26: 43\\--49.") MAN_END MAN_BEGIN (L"Schott (2001)", L"djmw", 20090629) NORMAL (L"J. R. Schott (2001): \"Some tests for the equality of covariance matrices.\" " "%%Journal of Statistical Planning and Inference% #94: 25\\-–36.") MAN_END MAN_BEGIN (L"Shepard (1964)", L"djmw", 19980114) NORMAL (L"R.N. Shepard (1964): \"Circularity in judgments of relative pitch.\" " "%%Journal of the Acoustical Society of America% #36: 2346\\--2353.") MAN_END MAN_BEGIN (L"Slaney (1993)", L"djmw", 19980712) NORMAL (L"M. Slaney (1993): \"An efficient implementation of the " "Patterson-Holdsworth auditory filterbank.\" " "%%Apple Computer Technical Report% #35, 41 pages.") MAN_END MAN_BEGIN (L"Tribolet et al. (1979)", L"djmw", 20010114) NORMAL (L"J.M. Tribolet & T.F. Quatieri (1979): \"Computation of the Complex " "Cepstrum.\" In %%Programs for Digital Signal Processing%, " "Digital Signal Processing Committee (eds.), IEEE Press.") MAN_END MAN_BEGIN (L"Tukey (1977)", L"djmw", 20000524) NORMAL (L"J.W. Tukey (1977): %%Exploratory data analysis%. Reading, MA: Addison-Wesley.") MAN_END MAN_BEGIN (L"Van Nierop et al. (1973)", L"djmw", 20020620) NORMAL (L"D.J.P.J. Van Nierop, L.C.W. Pols & R. Plomp (1973): \"Frequency " "analysis of Dutch vowels from 25 female speakers.\" %%Acustica% #29: 110\\--118") MAN_END MAN_BEGIN (L"Weenink (1985)", L"djmw", 20111010) NORMAL (L"D.J.M. Weenink (1985), \"Formant analysis of Dutch vowels from 10 children\", " "%%Proceedings of the Institute of Phonetic Sciences of the " "University of Amsterdam% #9, 45\\--52.") MAN_END MAN_BEGIN (L"Watrous (1991)", L"djmw", 20080125) NORMAL (L"R.L. Watrous (1991): \"Current status of Peterson-Barney vowel formant data.\" " "%%Journal of the Acoustical Society of America% #89: 2459\\--2460.") MAN_END MAN_BEGIN (L"Weenink (1999)", L"djmw", 20041217) NORMAL (L"D.J.M. Weenink (1999): \"Accurate algorithms for performing " "principal component analysis and discriminant analysis.\" " "%%Proceedings of the Institute of Phonetic Sciences of the " "University of Amsterdam% #23: 77\\--89.") MAN_END MAN_BEGIN (L"Weenink (2003)", L"djmw", 20040225) NORMAL (L"D.J.M. Weenink (2003): \"Canonical correlation analysis.\" " "%%Proceedings of the Institute of Phonetic Sciences of the " "University of Amsterdam% #25: 81\\--99.") MAN_END } /* End of file manual_dwtools.cpp */ sources_5316/dwtools/Sound_to_MFCC.cpp0000644000176700017670000000250011606610672016506 0ustar paulpaul/* Sound_to_MFCC.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010410 djmw 20020813 GPL header */ #include "Sound_to_MFCC.h" #include "Sound_and_FilterBank.h" MFCC Sound_to_MFCC (Sound me, long numberOfCoefficients, double analysisWidth, double dt, double f1_mel, double fmax_mel, double df_mel) { try { autoMelFilter mf = Sound_to_MelFilter (me, analysisWidth, dt, f1_mel, fmax_mel, df_mel); autoMFCC mfcc = MelFilter_to_MFCC (mf.peek(), numberOfCoefficients); return mfcc.transfer(); } catch (MelderError) { Melder_throw (me, ": no MFCC created."); } } /* End of file Sound_to_MFCC.cpp */ sources_5316/dwtools/DTW.cpp0000664000176700017670000014440211741614156014575 0ustar paulpaul/* DTW.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20050302 Path finder modified with sakoe-chiba band djmw 20050305 DTW_to_Polygon djmw 20050306 DTW_swapAxes djmw 20050530 Added Matrices_to_DTW djmw 20060909 DTW_getPathY linear behaviour outside domains. djmw 20061205 Pitches_to_DTW djmw 20061214 Changed info to Melder_writeLine format. djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20071016 To Melder_error djmw 20071022 Extra comments + possible bug correction in DTW_Path_recode. djmw 20071201 Melder_warning. djmw 20071204 DTW_and_Sounds_draw. djmw 20080122 float -> double djmw 20081123 DTW_and_Sounds_checkDomains did not swap sounds correctly. djmw 20091009 Removed a bug in DTW_Path_recode that could cause two identical x and y times in succesion at the end. djmw 20100504 extra check in DTW_Path_makeIndex djmw 20110304 Thing_new */ #include "DTW.h" #include "Sound_extensions.h" #include "NUM2.h" #include "NUMmachar.h" #include "oo_DESTROY.h" #include "DTW_def.h" #include "oo_COPY.h" #include "DTW_def.h" #include "oo_EQUAL.h" #include "DTW_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "DTW_def.h" #include "oo_WRITE_TEXT.h" #include "DTW_def.h" #include "oo_WRITE_BINARY.h" #include "DTW_def.h" #include "oo_READ_TEXT.h" #include "DTW_def.h" #include "oo_READ_BINARY.h" #include "DTW_def.h" #include "oo_DESCRIPTION.h" #include "DTW_def.h" Thing_implement (DTW, Matrix, 2); #define DTW_BIG 1e38 void structDTW :: v_info () { structData :: v_info (); MelderInfo_writeLine5 (L"Domain prototype:", Melder_double (ymin), L" to ", Melder_double (ymax), L" (s)."); MelderInfo_writeLine5 (L"Domain candidate:", Melder_double (xmin), L" to ", Melder_double (xmax), L" (s)."); MelderInfo_writeLine2 (L"Number of frames prototype: ", Melder_integer (ny)); MelderInfo_writeLine2 (L"Number of frames candidate: ", Melder_integer (nx)); MelderInfo_writeLine2 (L"Path length (frames): ", Melder_integer (pathLength)); MelderInfo_writeLine2 (L"Global warped distance: ", Melder_double (weightedDistance)); if (nx == ny) { double dd = 0; for (long i = 1; i <= nx; i++) { dd += z[i][i]; } MelderInfo_writeLine2 (L"Distance along diagonal: ", Melder_double (dd / nx)); } } static void DTW_drawWarpX_raw (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, double tx, int garnish, int inset); static void DTW_paintDistances_raw (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, double minimum, double maximum, int garnish, int inset); static void DTW_drawPath_raw (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish, int inset); static double _DTW_and_Sounds_getPartY (Graphics g, double dtw_part_x); static void DTW_findPath_special (DTW me, int matchStart, int matchEnd, int slope, Matrix *cummulativeDists); /* Two 'slope lines, lh and ll, start in the lower left corner, the upper/lower has the maximum/minimum allowed slope. Two other lines, ru and rl, end in the upper-right corner. The upper/lower line have minimum/maximum slope. 1. the four lines with the two intersections determine a diamond For vertical line at x we return the upper and lower y of the two intersections 1. When we don't have a diamond, we return an error and the vertical distance between the slopelines in ylow. */ /* The actual path will be interpolated as follows: The distance matrix has cells of dimensions dx by dy. The optimal path connects these cells with one another in the following ways: In a diagonal ''path'' segment, i.e. when cells have no side in common, the interplated path runs from the lowerleft corner to the upperright corner. If a path segment is horizontal or vertical the path also runs from lowerleft to upperright. It is only when a horizontal and a vertical segment have a cell in common that we have to make some adjustments to the path in the common cell. This will be done as follows: Let nx and ny be the number of horizontal and vertical cells in this path segment. The path will always start at the lowerleft of the leftmost block and end at the upperright of the rightmost block. In the common cell we have to introduce an extra point in the path at (x1,y1) where the line from the horizontal segment and the line from the vertical segment intersect. Let the lowerleft and upperright point of the common cell be (0,0) and (dx,dy), then the coordinates (x,y) of the intersection can be calculated as follows: If we have two lines y = a1*x+b1 and y = a2*x+b2 they intersect at (x,y) = (b2-b1, a1*b2-a2*b1)/(a1-a2) For horizontal-vertical (hv) cells: a1 = dy/(nx*dx), a2 = ny*dy/dx b1 = dy*(nx-1)/nx, b2 = 0 Then: (x,y) = (dx, dy*ny ) * (nx-1)/(nx*ny-1) For vertical-horizontal (vh) cells: a1 = ny*dy/dx, a2 = dy/(nx*dx) b1 = -(ny-1)*dy b2 = 0 Then: (x,y) = (nx*dx, dy) * (ny-1)/(nx*ny-1) */ /* DTW_getXTime (DTW me, (DTW_getYTime (DTW me, double tx)) == tx */ double DTW_getYTimeFromXTime (DTW me, double tx) { DTW_Path_Query thee = & my pathQuery; if (tx < my xmin) { return my ymin - (my xmin - tx); } if (tx > my xmax) { return my ymax + (tx - my xmax); } if (! NUMfpp) { NUMmachar (); } double eps = 3 * NUMfpp -> eps; /* Find in which column is tx */ long ib, ie; long ix = (long) floor ( (tx - my x1) / my dx + 1.5); if (ix < 1) { ib = 1; ie = 2; } else if (ix > my nx) { ib = thy nxy - 1; ie = thy nxy; } else { ib = thy xindex[ix].ibegin; ie = thy xindex[ix].iend; } if (ie - ib > 1) { long it = ib + 1; while (tx - thy xytimes[it].x > eps) { it++; } ie = it; ib = it - 1; } double a = (thy xytimes[ib].y - thy xytimes[ie].y) / (thy xytimes[ib].x - thy xytimes[ie].x); double b = thy xytimes[ib].y - a * thy xytimes[ib].x; return a * tx + b; } double DTW_getXTimeFromYTime (DTW me, double ty) { DTW_Path_Query thee = & my pathQuery; if (ty < my ymin) { return my ymin - (my ymin - ty); } if (ty > my ymax) { return my ymax + (ty - my ymax); } if (! NUMfpp) { NUMmachar (); } double eps = 3 * NUMfpp -> eps; /* Find in which row is ty */ long ib, ie; long iy = (long) floor ( (ty - my y1) / my dy + 1.5); if (iy < 1) { ib = 1; ie = 2; } else if (iy > my ny) { ib = thy nxy - 1; ie = thy nxy; } else { ib = thy yindex[iy].ibegin; ie = thy yindex[iy].iend; } if (ie - ib > 1) { long it = ib + 1; while (ty - thy xytimes[it].y > eps) { it++; } ie = it; ib = it - 1; } double a = (thy xytimes[ib].y - thy xytimes[ie].y) / (thy xytimes[ib].x - thy xytimes[ie].x); double b = thy xytimes[ib].y - a * thy xytimes[ib].x; return (ty - b) / a; } void DTW_Path_Query_init (DTW_Path_Query me, long ny, long nx) { Melder_assert (ny > 0 && nx > 0); my ny = ny; my nx = nx; my nxy = 2 * (ny > nx ? ny : nx) + 2; // maximum number of points my xytimes = NUMvector (1, my nxy); my yindex = NUMvector (1, my ny); my xindex = NUMvector (1, my nx); } static void DTW_Path_makeIndex (DTW me, int xory) { DTW_Path_Query thee = & my pathQuery; DTW_Path_Index index; double x1, dx; long nx; if (! NUMfpp) { NUMmachar (); } double eps = 3 * NUMfpp -> eps; if (xory == DTW_X) { index = thy xindex; nx = my nx; x1 = my x1; dx = my dx; } else { index = thy yindex; nx = my ny; x1 = my y1; dx = my dy; } double xy_x2 = xory == DTW_X ? thy xytimes[3].x : thy xytimes[3].y; long i = 3; for (long j = 1; j <= nx; j++) { double xlow = x1 + (j - 1 - 0.5) * dx; double xhigh = xlow + dx; if (xlow - xy_x2 > -eps && i < thy nxy) { // i.e. xlow >= xy_x2 i++; xy_x2 = xory == DTW_X ? thy xytimes[i].x : thy xytimes[i].y; } index[j].ibegin = i - 1; while (xhigh - xy_x2 > eps && i < thy nxy) { // i.e. xhigh > xy_x2 i++; xy_x2 = xory == DTW_X ? thy xytimes[i].x : thy xytimes[i].y; } index[j].iend = i; } } /* Recode the path from a chain of cells to a piecewise linear path. */ void DTW_Path_recode (DTW me) { DTW_Path_Query thee = & my pathQuery; long nxy; // current number of elements in recoded path long nx = 1; // current number of successive horizontal cells in the cells chain long ny = 1; // current number of successive vertical cells in the cells chain long nd = 0; // current number of successive diagonal cells in the cells chain int isv = 0; // previous segment in the original path was vertical int ish = 0; // previous segment in the original path was horizontal long ixp = 0, iyp = 0; // previous cell /* Algorithm 1: get all the points in the path 2. get the x and y indices */ /* 1. Starting point always at origin */ thy xytimes[1].x = my xmin; thy xytimes[1].y = my ymin; nx = my path[1].x; ixp = nx - 1; thy xytimes[2].x = my x1 + (nx - 1 - 0.5) * my dx; ny = my path[1].y; iyp = ny - 1; thy xytimes[2].y = my y1 + (ny - 1 - 0.5) * my dy; // implicit: my x1 - 0.5 * my dx > my xmin && my y1 - 0.5 * my dy > my ymin nxy = 2; for (long j = 1; j <= my pathLength; j++) { long index; // where are we in the new path? long ix = my path[j].x, iy = my path[j].y; double xright = my x1 + (ix - 1 + 0.5) * my dx; double x, y, f, ytop = my y1 + (iy - 1 + 0.5) * my dy; if (iy == iyp) { // horizontal path? ish = 1; if (isv) { // we came from vertical direction? // We came from a vertical direction so this is the second horizontal cell in a row. // The statement after this "if" updates nx to 2. nx = 1; isv = 0; } nx++; if (ny > 1 || nd > 1) { // Previous segment was diagonal or vertical: modify intersection // The vh intersection (x,y) = (nx*dx, dy) * (ny-1)/(nx*ny-1) // A diagonal segment has ny = 1. f = (ny - 1.0) / (nx * ny - 1); x = xright - nx * my dx + nx * my dx * f; y = ytop - my dy + my dy * f; index = nxy - 1; if (nx == 2) { index = nxy; nxy++; } thy xytimes[index].x = x; thy xytimes[index].y = y; } nd = 0; } else if (ix == ixp) { // vertical isv = 1; if (ish) { ny = 1; ish = 0; } ny++; if (nx > 1 || nd > 1) { // The hv intersection (x,y) = (dx, dy*ny ) * (nx-1)/(nx*ny-1) f = (nx - 1.0) / (nx * ny - 1); x = xright - my dx + my dx * f; y = ytop - ny * my dy + ny * my dy * f; index = nxy - 1; if (ny == 2) { index = nxy; nxy++; } thy xytimes[index].x = x; thy xytimes[index].y = y; } nd = 0; } else if (ix == (ixp + 1) && iy == (iyp + 1)) { // diagonal nd++; if (nd == 1) { nxy++; } nx = ny = 1; } else { Melder_throw ("The path goes back in time."); } // update thy xytimes[nxy].x = xright; thy xytimes[nxy].y = ytop; ixp = ix; iyp = iy; } if (my xmax > thy xytimes[nxy].x || my ymax > thy xytimes[nxy].y) { nxy++; thy xytimes[nxy].x = my xmax; thy xytimes[nxy].y = my ymax; } Melder_assert (nxy <= 2 * (my ny > my nx ? my ny : my nx) + 2); thy nxy = nxy; DTW_Path_makeIndex (me, DTW_X); DTW_Path_makeIndex (me, DTW_Y); } void DTW_pathRemoveRedundantNodes (DTW me) { long i = 1, skip = 0; for (long j = 2; j <= my pathLength; j++) { if ( (my path[j].y == my path[i].y) || my path[j].x == my path[i].x) { skip++; } else { /* if (j-1)^th was the last of a series: store it */ if (skip > 0) { my path[++i] = my path[j - 1]; } /* same check again */ skip = 0; if ( (my path[j].y == my path[i].y) || my path[j].x == my path[i].x) { skip++; } else { my path[++i] = my path[j]; } } } if (skip > 0) { my path[++i] = my path[my pathLength]; } my pathLength = i; } /* Prototype must be on y-axis and test on x-axis */ DTW DTW_create (double tminp, double tmaxp, long ntp, double dtp, double t1p, double tminc, double tmaxc, long ntc, double dtc, double t1c) { try { autoDTW me = Thing_new (DTW); Matrix_init (me.peek(), tminc, tmaxc, ntc, dtc, t1c, tminp, tmaxp, ntp, dtp, t1p); my path = NUMvector (1, ntc + ntp - 1); DTW_Path_Query_init (& my pathQuery, ntp, ntc); my wx = 1; my wy = 1; my wd = 2; return me.transfer(); } catch (MelderError) { Melder_throw ("DTW not created."); } } void DTW_setWeights (DTW me, double wx, double wy, double wd) { my wx = wx; my wy = wy; my wd = wd; } DTW DTW_swapAxes (DTW me) { try { autoDTW thee = DTW_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); for (long x = 1; x <= my nx; x++) { for (long y = 1; y <= my ny; y++) { thy z[x][y] = my z[y][x]; } } thy pathLength = my pathLength; for (long i = 1; i <= my pathLength; i++) { thy path[i].x = my path[i].y; thy path[i].y = my path[i].x; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": axes not swapped."); } } double DTW_getPathY (DTW me, double tx) { // Assume linear behaviour outside domains // Other option: scale with x_domain/y_domain if (tx < my xmin) { return my ymin - (my xmin - tx); } if (tx > my xmax) { return my ymax + (tx - my xmax); } // Find column in DTW matrix long ix = (tx - my x1) / my dx + 1; if (ix < 1) { ix = 1; } if (ix > my nx) { ix = my nx; } // Find index in the path and the row number (iy) long i = ix + my path[1].x - 1; while (i <= my pathLength && my path[i].x != ix) { i++; } if (i > my pathLength) { return NUMundefined; } long iy = my path[i].y; /* row */ /* We like to have a "continuous" interpretation of time for the quantized x and y times. A time block is specified by lower left (x,y) and upper right (x+dx,y+dy). The path is interpreted as piecewise linear. Two special cases: 1. the local path is horizontal, i.e. two or more path elements with the same path.y value. We calculate the y-time from the line that connects the lower-left position of the leftmost horizontal time block to the upper-right position of the rightmost time horizontal block. (lowest column number to highest column number) For the first column and the last column we need to do something special if 2. the local path is vertical, i.e. two or path elements with the same path.x value. We calculate the y-time from the line that connects the lower-left position of the bottommost vertical time block to the upper-right position of the topmost time horizontal block. (lowest row number to highest row number) */ // Horizontal path? Find left and right positions. long ileft = i - 1; while (ileft >= 1 && my path[ileft].y == iy) { ileft--; } ileft++; if (ileft == 1 && ix > 1 && my path[ileft].y > 1) { ileft++; } long iright = i + 1; while (iright <= my pathLength && my path[iright].y == iy) { iright++; } iright--; if (iright == my pathLength && ix < my nx && my path[iright].y < my ny) { iright--; } long nxx = iright - ileft + 1; // Vertical path? Only if not already horizontal. long ibottom = i; long itop = i; if (nxx == 1) { ibottom--; while (ibottom >= 1 && my path[ibottom].x == ix) { ibottom--; } ibottom++; itop++; while (itop <= 1 && my path[itop].x == ix) { itop--; } itop++; } long nyy = itop - ibottom + 1; double boxx = nxx * my dx; double boxy = nyy * my dy; double ty; // Corrections at extreme left and right if path[1].x=1 && path[1].y>1 if (ix == my nx) { boxx = my xmax - (my x1 + (ix - 1) * my dx - my dx / 2); boxy = my ymax - (my y1 + (iy - 1) * my dy - my dy / 2); ty = my ymax - (boxy - (boxx - (my xmax - tx)) * boxy / boxx); } else if (ix == 1) { boxx = my x1 + my dx / 2 - my xmin; boxy = my y1 + (itop - 1) * my dy + my dy / 2 - my ymin; ty = (tx - my xmin) * boxy / boxx + my ymin; } else { // Diagonal interpolation in a box with lower left (0,0) and upper right (nxx*dx, nyy*dy). double ty0 = (tx - (my x1 + (my path[ileft].x - 1) * my dx - my dx / 2)) * boxy / boxx; ty = my y1 + (my path[ibottom].y - 1) * my dy - my dy / 2 + ty0; } return ty; } long DTW_getMaximumConsecutiveSteps (DTW me, int direction) { long nglobal = 1, nlocal = 1; for (long i = 2; i <= my pathLength; i++) { int localdirection; if (my path[i].y == my path[i - 1].y) { localdirection = DTW_X; } else if (my path[i].x == my path[i - 1].x) { localdirection = DTW_Y; } else { localdirection = DTW_XANDY; } if (localdirection == direction) { nlocal += 1; } if (direction != localdirection || i == my pathLength) { if (nlocal > nglobal) { nglobal = nlocal; } nlocal = 1; } } return nglobal; } static void DTW_paintDistances_raw (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, double minimum, double maximum, int garnish, int inset) { long ixmin, ixmax, iymin, iymax; if (xmax <= xmin) { xmin = my xmin; xmax = my xmax; } if (ymax <= ymin) { ymin = my ymin; ymax = my ymax; } (void) Matrix_getWindowSamplesX (me, xmin - 0.49999 * my dx, xmax + 0.49999 * my dx, & ixmin, & ixmax); (void) Matrix_getWindowSamplesY (me, ymin - 0.49999 * my dy, ymax + 0.49999 * my dy, & iymin, & iymax); if (maximum <= minimum) { (void) Matrix_getWindowExtrema (me, ixmin, ixmax, iymin, iymax, & minimum, & maximum); } if (maximum <= minimum) { minimum -= 1.0; maximum += 1.0; } if (xmin >= xmax || ymin >= ymax) { return; } if (inset) { Graphics_setInner (g); } Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_cellArray (g, my z, ixmin, ixmax, Matrix_columnToX (me, ixmin - 0.5), Matrix_columnToX (me, ixmax + 0.5), iymin, iymax, Matrix_rowToY (me, iymin - 0.5), Matrix_rowToY (me, iymax + 0.5), minimum, maximum); Graphics_rectangle (g, xmin, xmax, ymin, ymax); if (inset) { Graphics_unsetInner (g); } if (garnish) { Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } void DTW_paintDistances (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, double minimum, double maximum, int garnish) { DTW_paintDistances_raw (me, g, xmin, xmax, ymin, ymax, minimum, maximum, garnish, 1); } static void DTW_drawPath_raw (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish, int inset) { DTW_Path_Query thee = & my pathQuery; if (xmin >= xmax) { xmin = my xmin; xmax = my xmax; } if (ymin >= ymax) { ymin = my ymin; ymax = my ymax; } if (inset) { Graphics_setInner (g); } Graphics_setWindow (g, xmin, xmax, ymin, ymax); for (long i = 1; i < thy nxy; i++) { double x1, y1, x2, y2; if (NUMclipLineWithinRectangle (thy xytimes[i].x, thy xytimes[i].y, thy xytimes[i + 1].x, thy xytimes[i + 1].y, xmin, ymin, xmax, ymax, &x1, &y1, &x2, &y2)) { Graphics_line (g, x1, y1, x2, y2); } } if (inset) { Graphics_unsetInner (g); } if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } void DTW_drawPath (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish) { DTW_drawPath_raw (me, g, xmin, xmax, ymin, ymax, garnish, 1); } static void DTW_drawWarpX_raw (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, double tx, int garnish, int inset) { double ty = DTW_getYTimeFromXTime (me, tx); int lineType = Graphics_inqLineType (g); if (xmin >= xmax) { xmin = my xmin; xmax = my xmax; } if (ymin >= ymax) { ymin = my ymin; ymax = my ymax; } if (inset) { Graphics_setInner (g); } Graphics_setWindow (g, xmin, xmax, ymin, ymax); ty = DTW_getYTimeFromXTime (me, tx); Graphics_setLineType (g, Graphics_DOTTED); if (ty <= ymax) { Graphics_line (g, tx, ymin, tx, ty); Graphics_line (g, tx, ty, xmin, ty); } else { Graphics_line (g, tx, ymin, tx, ymax); } Graphics_setLineType (g, lineType); if (inset) { Graphics_unsetInner (g); } if (garnish) { Graphics_markBottom (g, tx, 1, 1, 0, NULL); if (ty <= ymax) { Graphics_markLeft (g, ty, 1, 1, 0, 0); } } } void DTW_drawWarpX (DTW me, Graphics g, double xmin, double xmax, double ymin, double ymax, double tx, int garnish) { DTW_drawWarpX_raw (me, g, xmin, xmax, ymin, ymax, tx, garnish, 1); } static void DTW_and_Sounds_checkDomains (DTW me, Sound *y, Sound *x, double *xmin, double *xmax, double *ymin, double *ymax) { if (my ymin == (*y) -> xmin && my ymax == (*y) -> xmax) { if (my xmin != (*x) -> xmin || my xmax != (*x) -> xmax) { Melder_throw ("The domains of the DTW and the sound('s) don't match"); } } else if (my ymin == (*x) -> xmin && my ymax == (*x) -> xmax) { if (my xmin != (*y) -> xmin || my xmax != (*y) -> xmax) { Melder_throw ("The domains of the DTW and the sound('s) don't match"); } Sound tmp = *y; *y = *x; *x = tmp; // swap x and y } else { Melder_throw ("The domains of the DTW and the sound('s) don't match"); } if (*xmin >= *xmax) { *xmin = my xmin; *xmax = my xmax; } if (*ymin >= *ymax) { *ymin = my ymin; *ymax = my ymax; } } static void drawBox (Graphics g) { double x1WC, x2WC, y1WC, y2WC; double lineWidth = Graphics_inqLineWidth (g); Graphics_inqWindow (g, &x1WC, &x2WC, &y1WC, &y2WC); Graphics_setLineWidth (g, 2.0 * lineWidth); Graphics_rectangle (g, x1WC, x2WC, y1WC, y2WC); Graphics_setLineWidth (g, lineWidth); } /* In a picture with a DTW and a left and bottom Sound, we want "width" of the vertical sound and the "height" of the horizontal Sound t be equal. Given the horizontal fraction of the DTW-part, this routine returns the vertical part. */ static double _DTW_and_Sounds_getPartY (Graphics g, double dtw_part_x) { double x1NDC, x2NDC, y1NDC, y2NDC; Graphics_inqViewport (g, &x1NDC, &x2NDC, &y1NDC, &y2NDC); return 1 - ( (1 - dtw_part_x) * (x2NDC - x1NDC)) / (y2NDC - y1NDC); } void DTW_and_Sounds_draw (DTW me, Sound y, Sound x, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish) { DTW_and_Sounds_checkDomains (me, &y, &x, &xmin, &xmax, &ymin, &ymax); Graphics_setInner (g); Graphics_Viewport ovp = g -> outerViewport; // save for unsetInner double dtw_part_x = 0.85; double dtw_part_y = _DTW_and_Sounds_getPartY (g, dtw_part_x); /* DTW */ Graphics_Viewport vp = Graphics_insetViewport (g, 1 - dtw_part_x, 1, 1 - dtw_part_y, 1); DTW_paintDistances_raw (me, g, xmin, xmax, ymin, ymax, 0, 0, 0, 0); DTW_drawPath_raw (me, g, xmin, xmax, ymin, ymax, 0, 0); drawBox (g); Graphics_resetViewport (g, vp); /* Sound y */ vp = Graphics_insetViewport (g, 0, 1 - dtw_part_x, 1 - dtw_part_y, 1); Sound_draw_btlr (y, g, ymin, ymax, -1, 1, FROM_BOTTOM_TO_TOP, 0); if (garnish) { drawBox (g); } Graphics_resetViewport (g, vp); /* Sound x */ vp = Graphics_insetViewport (g, 1 - dtw_part_x, 1, 0, 1 - dtw_part_y); Sound_draw_btlr (x, g, xmin, xmax, -1, 1, FROM_LEFT_TO_RIGHT, 0); if (garnish) { drawBox (g); } Graphics_resetViewport (g, vp); /* Set window coordinates so that margins will work, i.e. extend time domains */ double xmin3 = xmax - (xmax - xmin) / dtw_part_x; double ymin3 = ymax - (ymax - ymin) / dtw_part_y; Graphics_setWindow (g, xmin3, xmax, ymin3, ymax); g -> outerViewport = ovp; // restore from _setInner Graphics_unsetInner (g); if (garnish) { Graphics_markLeft (g, ymin, 1, 1, 0, NULL); Graphics_markLeft (g, ymax, 1, 1, 0, NULL); Graphics_markBottom (g, xmin, 1, 1, 0, NULL); Graphics_markBottom (g, xmax, 1, 1, 0, NULL); } } void DTW_and_Sounds_drawWarpX (DTW me, Sound yy, Sound xx, Graphics g, double xmin, double xmax, double ymin, double ymax, double tx, int garnish) { Sound y = yy, x = xx; int lineType = Graphics_inqLineType (g); DTW_and_Sounds_checkDomains (me, &y, &x, &xmin, &xmax, &ymin, &ymax); Graphics_setInner (g); double dtw_part_x = 0.85; double dtw_part_y = _DTW_and_Sounds_getPartY (g, dtw_part_x); xmin = xmax - (xmax - xmin) / dtw_part_x; ymin = ymax - (ymax - ymin) / dtw_part_y; Graphics_setWindow (g, xmin, xmax, ymin, ymax); double ty = DTW_getYTimeFromXTime (me, tx); Graphics_setLineType (g, Graphics_DOTTED); Graphics_line (g, tx, ymin, tx, ty); Graphics_line (g, tx, ty, xmin, ty); Graphics_setLineType (g, lineType); Graphics_unsetInner (g); if (garnish) { Graphics_markBottom (g, tx, 1, 1, 0, NULL); Graphics_markLeft (g, ty, 1, 1, 0, NULL); } } Matrix DTW_to_Matrix_distances (DTW me) { try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": distances not converted to Matrix."); } } /* nog aanpassen, dl = sqrt (dx^2 + dy^2) */ void DTW_drawDistancesAlongPath (DTW me, Graphics g, double xmin, double xmax, double dmin, double dmax, int garnish) { if (xmin >= xmax) { xmin = my xmin; xmax = my xmax; } long ixmax, ixmin; if (! Matrix_getWindowSamplesX (me, xmin, xmax, &ixmin, &ixmax)) { return; } long ii = 1; while (ii < my pathLength && my path[ii].x < ixmin) { ii++; } ixmin = ii; while (ii <= my pathLength && my path[ii].x < ixmax) { ii++; } ixmax = ii; autoNUMvector d (ixmin, ixmax); for (long i = ixmin; i <= ixmax; i++) { d[i] = my z[my path[i].y][i]; } if (dmin >= dmax) { NUMvector_extrema (d.peek(), ixmin, ixmax, &dmin, &dmax); } else { for (long i = ixmin; i <= ixmax; i++) { if (d[i] > dmax) { d[i] = dmax; } else if (d[i] < dmin) { d[i] = dmin; } } } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, dmin, dmax); Graphics_function (g, d.peek(), ixmin, ixmax, xmin, xmax); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textLeft (g, 1, L"distance"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } /* metric = 1...n (sum (a_i^n))^(1/n) */ DTW Matrices_to_DTW (I, thou, int matchStart, int matchEnd, int slope, int metric) { try { iam (Matrix); thouart (Matrix); if (thy ny != my ny) { Melder_throw (L"Columns must have the same dimensions."); } autoDTW him = DTW_create (my xmin, my xmax, my nx, my dx, my x1, thy xmin, thy xmax, thy nx, thy dx, thy x1); autoMelderProgress progess (L"Calculate distances"); for (long i = 1; i <= my nx; i++) { for (long j = 1; j <= thy nx; j++) { /* First divide distance by maximum to prevent overflow when metric is a large number. d = (x^n)^(1/n) may overflow if x>1 & n >>1 even if d would not overflow! */ double dmax = 0, d = 0, dtmp; for (long k = 1; k <= my ny; k++) { dtmp = fabs (my z[k][i] - thy z[k][j]); if (dtmp > dmax) { dmax = dtmp; } } if (dmax > 0) { for (long k = 1; k <= my ny; k++) { dtmp = fabs (my z[k][i] - thy z[k][j]) / dmax; d += pow (dtmp, metric); } } d = dmax * pow (d, 1.0 / metric); his z[i][j] = d / my ny; /* == d * dy / ymax */ } if ( (i % 10) == 1) { Melder_progress (0.999 * i / my nx, L"Calculate distances: column ", Melder_integer (i), L" from ", Melder_integer (my nx), L"."); therror } } DTW_findPath (him.peek(), matchStart, matchEnd, slope); return him.transfer(); } catch (MelderError) { Melder_throw ("DTW not created from matrices."); } } DTW Spectrograms_to_DTW (Spectrogram me, Spectrogram thee, int matchStart, int matchEnd, int slope, int metric) { try { if (my xmin != thy xmin || my ymax != thy ymax || my ny != thy ny) { Melder_throw (L"The number of frequencies and/or frequency ranges do not match."); } autoMatrix m1 = Spectrogram_to_Matrix (me); autoMatrix m2 = Spectrogram_to_Matrix (thee); // Take log10 for dB's (4e-10 scaling not necessary) for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) { m1 -> z[i][j] = 10 * log10 (m1 -> z[i][j]); } } for (long i = 1; i <= thy ny; i++) { for (long j = 1; j <= thy nx; j++) { m2 -> z[i][j] = 10 * log10 (m2 -> z[i][j]); } } autoDTW him = Matrices_to_DTW (m1.peek(), m2.peek(), matchStart, matchEnd, slope, metric); return him.transfer(); } catch (MelderError) { Melder_throw ("DTW not created from Spectrograms."); } } #define FREQUENCY(frame) ((frame) -> candidate [1]. frequency) #define NOT_VOICED(f) ((f) <= 0.0 || (f) >= my ceiling) /* This includes NUMundefined! */ static int Pitch_findFirstAndLastVoicedFrame (Pitch me, long *first, long *last) { *first = 1; while (*first <= my nx && ! Pitch_isVoiced_i (me, *first)) { (*first) ++; } *last = my nx; while (*last >= *first && ! Pitch_isVoiced_i (me, *last)) { (*last)--; } return *first <= my nx && *last >= 1; } DTW Pitches_to_DTW_sgc (Pitch me, Pitch thee, double vuv_costs, double time_weight, int matchStart, int matchEnd, int slope); DTW Pitches_to_DTW_sgc (Pitch me, Pitch thee, double vuv_costs, double time_weight, int matchStart, int matchEnd, int slope) { // vuv_costs=24, time_weight=10 ? try { if (vuv_costs < 0) { Melder_throw ("Voiced-unvoiced costs may not be negative."); } if (time_weight < 0) { Melder_throw ("Time costs weight may not be negative."); } long myfirst, mylast, thyfirst, thylast; if (! Pitch_findFirstAndLastVoicedFrame (me, &myfirst, &mylast) || ! Pitch_findFirstAndLastVoicedFrame (thee, &thyfirst, &thylast)) { Melder_throw ("No voiced frames."); } /* We do not want the silences before the first voiced frame and after the last voiced frame to determine the distances. We create paths from (1,1)...(thyfirst,myfirst) and (thylast,mylast)...(thy nx,my nx) by making the other cell's distances very large. */ autoDTW him = DTW_create (my xmin, my xmax, my nx, my dx, my x1, thy xmin, thy xmax, thy nx, thy dx, thy x1); autoNUMvector pitchx (1, thy nx); int unit = kPitch_unit_SEMITONES_100; for (long j = 1; j <= thy nx; j++) { pitchx[j] = Sampled_getValueAtSample (thee, j, Pitch_LEVEL_FREQUENCY, unit); } for (long i = 1; i <= my nx; i++) { double pitchy = Sampled_getValueAtSample (me, i, Pitch_LEVEL_FREQUENCY, unit); double t1 = my x1 + (i - 1) * my dx; for (long j = 1; j <= thy nx; j++) { double t2 = thy x1 + (j - 1) * thy dx; double dist_f = 0; // based on pitch difference double dist_t = fabs (t1 - t2); if (pitchy == NUMundefined) { if (pitchx[j] != NUMundefined) { dist_f = vuv_costs; } } else if (pitchx[j] == NUMundefined) { dist_f = vuv_costs; } else { dist_f = fabs (pitchy - pitchx[j]); } his z[i][j] = sqrt (dist_f * dist_f + time_weight * dist_t * dist_t); } } DTW_findPath (him.peek(), matchStart, matchEnd, slope); return him.transfer(); } catch (MelderError) { Melder_throw ("DTW not created from Pitches."); } } DTW Pitches_to_DTW (Pitch me, Pitch thee, double vuv_costs, double time_weight, int matchStart, int matchEnd, int slope) { // vuv_costs=24, time_weight=10 ? try { if (vuv_costs < 0) { Melder_throw ("Voiced-unvoiced costs may not be negative."); } if (time_weight < 0) { Melder_throw ("Time costs weight may not be negative."); } autoDTW him = DTW_create (my xmin, my xmax, my nx, my dx, my x1, thy xmin, thy xmax, thy nx, thy dx, thy x1); autoNUMvector pitchx (1, thy nx); int unit = kPitch_unit_SEMITONES_100; for (long j = 1; j <= thy nx; j++) { pitchx[j] = Sampled_getValueAtSample (thee, j, Pitch_LEVEL_FREQUENCY, unit); } for (long i = 1; i <= my nx; i++) { double pitchy = Sampled_getValueAtSample (me, i, Pitch_LEVEL_FREQUENCY, unit); double t1 = my x1 + (i - 1) * my dx; for (long j = 1; j <= thy nx; j++) { double t2 = thy x1 + (j - 1) * thy dx; double dist_f = 0; // based on pitch difference double dist_t = fabs (t1 - t2); if (pitchy == NUMundefined) { if (pitchx[j] != NUMundefined) { dist_f = vuv_costs; } } else if (pitchx[j] == NUMundefined) { dist_f = vuv_costs; } else { dist_f = fabs (pitchy - pitchx[j]); } his z[i][j] = sqrt (dist_f * dist_f + time_weight * dist_t * dist_t); } } DTW_findPath (him.peek(), matchStart, matchEnd, slope); return him.transfer(); } catch (MelderError) { Melder_throw ("DTW not created from Pitches."); } } DurationTier DTW_to_DurationTier (DTW me) { (void) me; DurationTier thee = NULL; return thee; } void DTW_and_Matrix_replace (DTW me, Matrix thee) { try { if (my xmin != thy xmin || my xmax != thy xmax || my ymin != thy ymin || my ymax != thy ymax) { Melder_throw ("The X and Y domains of the matrix and the DTW must be equal."); } if (my nx != thy nx || my dx != thy dx || my ny != thy ny || my dy != thy dy) { Melder_throw ("The sampling of the matrix and the DTW must be equal."); } double minimum, maximum; Matrix_getWindowExtrema (me, 0, 0, 0, 0, & minimum, & maximum); if (minimum < 0) { Melder_throw ("Distances cannot be negative."); } NUMmatrix_copyElements (thy z, my z, 1, my ny, 1, my nx); } catch (MelderError) { Melder_throw (me, ": distances not replaced."); } } /****************** new implementation ********/ void DTW_findPath (DTW me, int matchStart, int matchEnd, int slope) { DTW_findPath_special (me, matchStart, matchEnd, slope, 0); } Matrix DTW_to_Matrix_cummulativeDistances (DTW me, double sakoeChibaBand, int slope) { try { Matrix cummulativeDistances; DTW_findPath_bandAndSlope (me, sakoeChibaBand, slope, &cummulativeDistances); return cummulativeDistances; } catch (MelderError) { Melder_throw (me, ": cummulative costs matrix not created."); } } static void DTW_checkSlopeConstraints (DTW me, double band, int slope) { try { double slopes[5] = { DTW_BIG, DTW_BIG, 3, 2, 1.5 } ; double dtw_slope = (my ymax - my ymin - band) / (my xmax - my xmin - band); if (slope < 1 || slope > 4) { Melder_throw ("Invalid slope constraint."); } if (dtw_slope <= 0 && slope != 1) { Melder_throw ("Band too wide."); } if (dtw_slope < 1) { dtw_slope = 1 / dtw_slope; } if (dtw_slope > slopes[slope]) { Melder_warning (L"There is a conflict between the chosen slope constraint and the relative duration. " "The duration ratio of the longest and the shortest object is ", Melder_double (dtw_slope), L". This implies that the largest slope in the constraint must have a value greater or equal to this ratio."); } } catch (MelderError) { Melder_throw ("Slope constraints can't be met."); } } static void DTW_and_Polygon_setUnreachableParts (DTW me, Polygon thee, long **psi) { try { double eps = my dx / 100; // safely enough double dtw_slope = (my ymax - my ymin) / (my xmax - my xmin); double xmin, xmax, ymin, ymax; Polygon_getExtrema (thee, &xmin, &xmax, &ymin, &ymax); // if the Polygon and the DTW don't overlap everything is unreachable! if (xmax <= my xmin || xmin >= my xmax || ymax <= my ymin || ymin >= my ymax) { Melder_throw ("DTW and Polygon don't overlap."); } // find border "above" polygon for (long ix = 1; ix <= my nx; ix++) { double x = my x1 + (ix - 1) * my dx; long iystart = (dtw_slope * ix * (my dx / my dy) + 1.0); for (long iy = iystart + 1; iy <= my ny; iy++) { double y = my y1 + (iy - 1) * my dy; if (Polygon_getLocationOfPoint (thee, x, y, eps) == Polygon_OUTSIDE) { for (long k = iy; k <= my ny; k++) { psi[k][ix] = DTW_UNREACHABLE; } break; } } } // find border "below" polygon for (long ix = 2; ix <= my nx; ix++) { double x = my x1 + (ix - 1) * my dx; long iystart = (dtw_slope * ix * (my dx / my dy)); // start 1 lower if (iystart > my ny) iystart = my ny; for (long iy = iystart - 1; iy >= 1; iy--) { double y = my y1 + (iy - 1) * my dy; if (Polygon_getLocationOfPoint (thee, x, y, eps) == Polygon_OUTSIDE) { for (long k = iy; k >= 1; k--) { psi[k][ix] = DTW_UNREACHABLE; } break; } } } } catch (MelderError) { Melder_throw (me, " can't set unreachable parts."); } } #define DTW_ISREACHABLE(y,x) ((psi[y][x] != DTW_UNREACHABLE) && (psi[y][x] != DTW_FORBIDDEN)) static void DTW_findPath_special (DTW me, int matchStart, int matchEnd, int slope, Matrix *cummulativeDists) { (void) matchStart; (void) matchEnd; try { autoPolygon thee = DTW_to_Polygon (me, 0.0, slope); DTW_and_Polygon_findPathInside (me, thee.peek(), slope, cummulativeDists); } catch (MelderError) { Melder_throw (me, ": cannot find path."); } } // Intersection of two straight lines y = a[i]*x+b[i], where a[2] = 1 / a[1]. Point (x1,y1) is on first line, // point (x2,y2) is on second line. static void getIntersectionPoint (double x1, double y1, double x2, double y2, double a, double *x3, double *y3) { *x3 = (y2 - y1 + a * x1 - x2 / a) / (a - 1 / a); *y3 = a * *x3 + y1 - a * x1; } Polygon DTW_to_Polygon (DTW me, double band, int slope) { try { DTW_checkSlopeConstraints (me, band, slope); double slopes[5] = { DTW_BIG, DTW_BIG, 3, 2, 1.5 } ; if (band <= 0) { if (slope == 1) { autoPolygon thee = Polygon_create (4); thy x[1] = my xmin; thy y[1] = my ymin; thy x[2] = my xmin; thy y[2] = my ymax; thy x[3] = my xmax; thy y[3] = my ymax; thy x[4] = my xmax; thy y[4] = my ymin; return thee.transfer(); } else { autoPolygon thee = Polygon_create (4); thy x[1] = my xmin; thy y[1] = my ymin; thy x[3] = my xmax; thy y[3] = my ymax; double x, y; getIntersectionPoint (my xmin, my ymin, my xmax, my ymax, slopes[slope], &x, &y); if (x < my xmin) x = my xmin; if (x > my xmax) x = my xmax; if (y < my ymin) y = my ymin; if (y > my ymax) y = my ymax; thy x[2] = x; thy y[2] = y; getIntersectionPoint (my xmin, my ymin, my xmax, my ymax, 1 / slopes[slope], &x, &y); if (x < my xmin) x = my xmin; if (x > my xmax) x = my xmax; if (y < my ymin) y = my ymin; if (y > my ymax) y = my ymax; thy x[4] = x; thy y[4] = y; return thee.transfer(); } } else { if (slope == 1) { autoPolygon thee = Polygon_create (6); thy x[1] = my xmin; thy y[1] = my ymin; thy x[2] = my xmin; thy y[2] = my ymin + band; thy x[3] = my xmax - band; thy y[3] = my ymax; thy x[4] = my xmax; thy y[4] = my ymax; thy x[5] = my xmax; thy y[5] = my ymax - band; thy x[6] = my xmin + band; thy y[6] = my ymin; return thee.transfer(); } else { autoPolygon thee = Polygon_create (8); double x, y; thy x[1] = my xmin; thy y[1] = my ymin; thy x[2] = my xmin; thy y[2] = my ymin + band; getIntersectionPoint (my xmin, my ymin + band, my xmax - band, my ymax, slopes[slope], &x, &y); if (x < my xmin) x = my xmin; if (x > my xmax) x = my xmax; if (y < my ymin) y = my ymin; if (y > my ymax) y = my ymax; thy x[3] = x; thy y[3] = y; thy x[4] = my xmax - band; thy y[4] = my ymax; thy x[5] = my xmax; thy y[5]= my ymax; thy x[6] = my xmax; thy y[6] = my ymax - band; getIntersectionPoint (my xmin + band, my ymin, my xmax, my ymax - band, 1 / slopes[slope], &x, &y); if (x < my xmin) x = my xmin; if (x > my xmax) x = my xmax; if (y < my ymin) y = my ymin; if (y > my ymax) y = my ymax; thy x[7] = x; thy y[7] = y; thy x[8] = my xmin + band; thy y[8] = my ymin; return thee.transfer(); } } } catch (MelderError) { Melder_throw (me, " no Polygon created."); } } Matrix DTW_and_Polygon_to_Matrix_cummulativeDistances (DTW me, Polygon thee, int localSlope) { try { Matrix cummulativeDistances; DTW_and_Polygon_findPathInside (me, thee, localSlope, &cummulativeDistances); return cummulativeDistances; } catch (MelderError) { Melder_throw (me, ": cummulative costs matrix not created from DTW and Polygon."); } } void DTW_findPath_bandAndSlope (DTW me, double sakoeChibaBand, int localSlope, Matrix *cummulativeDists) { try { autoPolygon thee = DTW_to_Polygon (me, sakoeChibaBand, localSlope); DTW_and_Polygon_findPathInside (me, thee.peek(), localSlope, cummulativeDists); } catch (MelderError) { Melder_throw (me, L" can't determine the path."); } } void DTW_and_Polygon_findPathInside (DTW me, Polygon thee, int localSlope, Matrix *cummulativeDists) { try { double slopes[5] = { DTW_BIG, DTW_BIG, 3, 2, 1.5 }; long pathIndex = my nx + my ny - 1; /* Maximum path length */ // if localSlope == 1 start of path is within 10% of minimum duration. Starts farther away long delta_xy = (my nx < my ny ? my nx : my ny) / 10; // if localSlope == 1 start within 10% of if (localSlope < 1 || localSlope > 4) { Melder_throw ("Local slope parameter is illegal."); } autoNUMmatrix delta (-2, my ny, -2, my nx); autoNUMmatrix psi (-2, my ny, -2, my nx); for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) { delta[i][j] = my z[i][j]; } } // start by making the outside unreachable for (long k = -2; k <= 1; k++) { for (long j = -2; j <= my nx; j++) { // delta[k][j] = DTW_BIG; psi[k][j] = DTW_UNREACHABLE; } for (long i = 1; i <= my ny; i++) { // delta[i][k] = DTW_BIG; psi[i][k] = DTW_UNREACHABLE; } } // Make begin part of first column reachable long rowto = delta_xy; if (localSlope != 1) rowto = slopes[localSlope] + 1.0; for (long iy = 2; iy <= rowto; iy++) { if (localSlope != 1) { delta[iy][1] = delta[iy - 1][1] + my z[iy][1]; psi[iy][1] = DTW_Y; } else { psi[iy][1] = DTW_START; // will be adapted by DTW_and_Polygon_setUnreachableParts } } // Make begin part of first row reachable long colto = delta_xy; if (localSlope != 1) colto = slopes[localSlope] + 1.0; for (long ix = 2; ix <= colto; ix++) { if (localSlope != 1) { delta[1][ix] = delta[1][ix -1] + my z[1][ix]; psi[1][ix] = DTW_X; } else { psi[1][ix] = DTW_START; // will be adapted by DTW_and_Polygon_setUnreachableParts } } // Now we can set the unreachable parts from the Polygon DTW_and_Polygon_setUnreachableParts (me, thee, psi.peek()); // Forward pass. long numberOfIsolatedPoints = 0; autoMelderProgress progress (L"Find path"); for (long j = 2; j <= my nx; j++) { for (long i = 2; i <= my ny; i++) { if (! DTW_ISREACHABLE (i, j)) continue; double g, gmin = DTW_BIG; long direction = 0; if (DTW_ISREACHABLE (i - 1, j - 1)) { gmin = delta[i - 1][j - 1] + 2 * my z[i][j]; direction = DTW_XANDY; } else if (DTW_ISREACHABLE (i, j - 1)) { gmin = delta[i][j - 1] + my z[i][j]; direction = DTW_X; } else if (DTW_ISREACHABLE (i - 1, j)) { gmin = delta[i - 1][j] + my z[i][j]; direction = DTW_Y; } else { numberOfIsolatedPoints++; continue; } switch (localSlope) { case 1: { // no restriction if (DTW_ISREACHABLE (i, j - 1) && ((g = delta[i][j - 1] + my z[i][j]) < gmin)) { gmin = g; direction = DTW_X; } if (DTW_ISREACHABLE (i - 1, j) && ((g = delta[i - 1][j] + my z[i][j]) < gmin)) { gmin = g; direction = DTW_Y; } } break; // P = 1/2 case 2: { // P = 1/2 if (DTW_ISREACHABLE (i - 1, j - 3) && psi[i][j - 1] == DTW_X && psi[i][j - 2] == DTW_XANDY && (g = delta[i-1][j-3] + 2 * my z[i][j-2] + my z[i][j-1] + my z[i][j]) < gmin) { gmin = g; direction = DTW_X; } if (DTW_ISREACHABLE (i - 1, j - 2) && psi[i][j - 1] == DTW_XANDY && (g = delta[i - 1][j - 2] + 2 * my z[i][j - 1] + my z[i][j]) < gmin) { gmin = g; direction = DTW_X; } if (DTW_ISREACHABLE (i - 2, j - 1) && psi[i - 1][j] == DTW_XANDY && (g = delta[i - 2][j - 1] + 2 * my z[i - 1][j] + my z[i][j]) < gmin) { gmin = g; direction = DTW_Y; } if (DTW_ISREACHABLE (i - 3, j - 1) && psi[i - 1][j] == DTW_Y && psi[i - 2][j] == DTW_XANDY && (g = delta[i-3][j-1] + 2 * my z[i-2][j] + my z[i-1][j] + my z[i][j]) < gmin) { gmin = g; direction = DTW_Y; } } break; // P = 1 case 3: { if (DTW_ISREACHABLE (i - 1, j - 2) && psi[i][j - 1] == DTW_XANDY && (g = delta[i - 1][j - 2] + 2 * my z[i][j - 1] + my z[i][j]) < gmin) { gmin = g; direction = DTW_X; } if (DTW_ISREACHABLE (i - 2, j - 1) && psi[i - 1][j] == DTW_XANDY && (g = delta[i - 2][j - 1] + 2 * my z[i - 1][j] + my z[i][j]) < gmin) { gmin = g; direction = DTW_Y; } } break; // P = 2 case 4: { if (DTW_ISREACHABLE (i - 2, j - 3) && psi[i][j - 1] == DTW_XANDY && psi[i - 1][j - 2] == DTW_XANDY && (g = delta[i-2][j-3] + 2 * my z[i-1][j-2] + 2 * my z[i][j-1] + my z[i][j]) < gmin) { gmin = g; direction = DTW_X; } if (DTW_ISREACHABLE (i - 3, j - 2) && psi[i - 1][j] == DTW_XANDY && psi[i - 2][j - 1] == DTW_XANDY && (g = delta[i-3][j-2] + 2 * my z[i-2][j-1] + 2 * my z[i-1][j] + my z[i][j]) < gmin) { gmin = g; direction = DTW_Y; } } break; default: break; } Melder_assert (direction != 0); psi[i][j] = direction; delta[i][j] = gmin; } if ((j % 10) == 2) { Melder_progress (0.999 * j / my nx, L"Calculate time warp: frame ", Melder_integer (j), L" from ", Melder_integer (my nx), L"."); therror } } // Find minimum at end of path and trace back. long iy = my ny; double minimum = delta[iy][my nx]; for (long i = my ny - 1; i > 0; i--) { if (! DTW_ISREACHABLE (i, my nx)) { break; // we're in unreachable places } else if (delta[i][my nx] < minimum) { minimum = delta[iy = i][my nx]; } } my weightedDistance = minimum / (my nx + my ny); my path[pathIndex].y = iy; long ix = my path[pathIndex].x = my nx; // Fill path backwards. while (ix > 1) { if (psi[iy][ix] == DTW_XANDY) { ix--; iy--; } else if (psi[iy][ix] == DTW_X) { ix--; } else if (psi[iy][ix] == DTW_Y) { iy--; } else if (psi[iy][ix] == DTW_START) { break; } if (pathIndex < 1 || iy < 1) break; //Melder_assert (pathIndex > 1 && iy > 0); my path[--pathIndex].x = ix; my path[pathIndex].y = iy; } my pathLength = my nx + my ny - pathIndex; if (pathIndex > 1) { for (long j = 1; j <= my pathLength; j++) { my path[j] = my path[pathIndex++]; } } DTW_Path_recode (me); if (cummulativeDists != 0) { autoMatrix him = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) { his z[i][j] = delta[i][j]; } } *cummulativeDists = him.transfer(); } } catch (MelderError) { Melder_throw (me, ": cannot find path."); } } /* End of file DTW.cpp */ sources_5316/dwtools/Categories_def.h0000644000176700017670000000170310745333605016501 0ustar paulpaul/* Categories_def.c * * Copyright (C) 1993-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020315 GPL header */ #define ooSTRUCT Categories oo_DEFINE_CLASS (Categories, OrderedOfString) oo_END_CLASS (Categories) #undef ooSTRUCT /* End of file Categories_def.h */ sources_5316/dwtools/GaussianMixture.cpp0000644000176700017670000015017511725072731017270 0ustar paulpaul/* GaussianMixture.cpp * * Copyright (C) 2011-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20101021 Initial version */ #include "Distributions_and_Strings.h" #include "GaussianMixture.h" #include "NUMlapack.h" #include "NUMmachar.h" #include "NUM2.h" #include "Strings_extensions.h" #include "oo_DESTROY.h" #include "GaussianMixture_def.h" #include "oo_COPY.h" #include "GaussianMixture_def.h" #include "oo_EQUAL.h" #include "GaussianMixture_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "GaussianMixture_def.h" #include "oo_WRITE_TEXT.h" #include "GaussianMixture_def.h" #include "oo_READ_TEXT.h" #include "GaussianMixture_def.h" #include "oo_WRITE_BINARY.h" #include "GaussianMixture_def.h" #include "oo_READ_BINARY.h" #include "GaussianMixture_def.h" #include "oo_DESCRIPTION.h" #include "GaussianMixture_def.h" Thing_implement (GaussianMixture, Data, 0); const wchar_t *GaussianMixture_criterionText (int criterion) { const wchar_t *criterionText[6] = { L"(1/n)*LLH", L"(1/n)*MML", L"(1/n)*BIC", L"(1/n)*AIC", L"(1/n)*AICc", L"(1/n)*CD_LLH" }; return criterion >= 0 && criterion < 7 ? criterionText[criterion] : L"(1/n)*ln(p)"; } void GaussianMixture_removeComponent (GaussianMixture me, long component); void GaussianMixture_removeComponent_bookkeeping (GaussianMixture me, long component, double **p, long numberOfRows); int GaussianMixture_and_TableOfReal_getProbabilities (GaussianMixture me, TableOfReal thee, long component, double **p); void GaussianMixture_and_TableOfReal_getGammas (GaussianMixture me, TableOfReal thee, double **gamma, double *lnp); double GaussianMixture_getLikelihoodValue (GaussianMixture me, double **p, long numberOfRows, int onlyLikelyhood); void GaussianMixture_updateProbabilityMarginals (GaussianMixture me, double **p, long numberOfRows); long GaussianMixture_getNumberOfParametersInComponent (GaussianMixture me); static void NUMdvector_scaleAsProbabilities (double *v, long n) { double sum = 0; for (long i = 1; i <= n; i++) { sum += v[i]; } if (sum > 0) for (long i = 1; i <= n; i++) { v[i] /= sum; } } static void GaussianMixture_updateCovariance (GaussianMixture me, long component, double **data, long numberOfRows, double **p) { if (component < 1 || component > my numberOfComponents) { return; } Covariance thee = (Covariance) my covariances -> item[component]; double mixprob = my mixingProbabilities[component]; double gsum = p[numberOfRows + 1][component]; // update the means for (long j = 1; j <= thy numberOfColumns; j++) { thy centroid[j] = 0; for (long i = 1; i <= numberOfRows; i++) { double gamma = mixprob * p[i][component] / p[i][my numberOfComponents + 1]; thy centroid[j] += gamma * data[i][j] ; // eq. Bishop 9.17 } thy centroid[j] /= gsum; } // update covariance with the new mean if (thy numberOfRows == 1) { // 1xn covariance for (long j = 1; j <= thy numberOfColumns; j++) { thy data[1][j] = 0; } for (long i = 1; i <= numberOfRows; i++) { double gamma = mixprob * p[i][component] / p[i][my numberOfComponents + 1]; double gdn = gamma / gsum; for (long j = 1; j <= thy numberOfColumns; j++) { double xj = thy centroid[j] - data[i][j]; thy data[1][j] += gdn * xj * xj; } } } else { // nxn covariance for (long j = 1; j <= thy numberOfRows; j++) for (long k = j; k <= thy numberOfColumns; k++) { thy data[k][j] = thy data[j][k] = 0; } for (long i = 1; i <= numberOfRows; i++) { double gamma = mixprob * p[i][component] / p[i][my numberOfComponents + 1]; double gdn = gamma / gsum; // we cannot divide by nk - 1, this could cause instability for (long j = 1; j <= thy numberOfColumns; j++) { double xj = thy centroid[j] - data[i][j]; for (long k = j; k <= thy numberOfColumns; k++) { thy data[j][k] = thy data[k][j] += gdn * xj * (thy centroid[k] - data[i][k]); } } } } thy numberOfObservations = my mixingProbabilities[component] * numberOfRows; } static void GaussianMixture_addCovarianceFraction (GaussianMixture me, long im, Covariance him, double fraction) { if (im < 1 || im > my numberOfComponents || fraction == 0) { return; } Covariance thee = (Covariance) my covariances -> item[im]; // prevent instability: add lambda fraction of global covariances if (thy numberOfRows == 1) { for (long j = 1; j <= thy numberOfColumns; j++) { thy data[1][j] += fraction * his data[j][j]; } } else { for (long j = 1; j <= thy numberOfColumns; j++) { for (long k = j; k <= thy numberOfColumns; k++) { thy data[k][j] = thy data[j][k] += fraction * his data[j][k]; } } } } void structGaussianMixture :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of components: ", Melder_integer (numberOfComponents)); MelderInfo_writeLine2 (L"Dimension of component: ", Melder_integer (dimension)); MelderInfo_writeLine1 (L"Mixing probabilities:"); for (long im = 1; im <= numberOfComponents; im++) { MelderInfo_writeLine7 (L" ", Melder_integer (im), L": p = ", Melder_double (mixingProbabilities[im]), L" Name = \"", Thing_getName ( (Thing) covariances -> item[im]), L"\""); } } static void GaussianMixture_setLabelsFromTableOfReal (GaussianMixture me, thou) { thouart (TableOfReal); for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; for (long j = 1; j <= my dimension; j++) { TableOfReal_setColumnLabel (cov, j, thy columnLabels[j]); } } } // only from big to reduced or same static void Covariance_into_Covariance (Covariance me, Covariance thee) { if (my numberOfColumns != thy numberOfColumns) { Melder_throw ("Dimensions must be equal."); } SSCP_unExpand (thee); // to its original state thy numberOfObservations = my numberOfObservations; // copy centroid & column labels for (long ic = 1; ic <= my numberOfColumns; ic++) { thy centroid[ic] = my centroid[ic]; } NUMstrings_copyElements (my columnLabels, thy columnLabels, 1, thy numberOfColumns); // Are the matrix sizes equal if (my numberOfRows == thy numberOfRows) { NUMstrings_copyElements (my rowLabels, thy rowLabels, 1, thy numberOfRows); NUMmatrix_copyElements (my data, thy data, 1, my numberOfRows, 1, my numberOfColumns); return; } else { for (long ir = 1; ir <= my numberOfRows; ir++) { for (long ic = ir; ic <= my numberOfColumns; ic++) { long dij = ic - ir; if (dij < thy numberOfRows) { thy data[dij + 1][ic] = my data[ir][ic]; } } } } } static void GaussianMixture_setDefaultMixtureNames (GaussianMixture me) { autoMelderString s; for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; MelderString_append (&s, L"m", Melder_integer (im)); Thing_setName (cov, s.string); MelderString_empty (&s); } } GaussianMixture GaussianMixture_create (long numberOfComponents, long dimension, long storage) { try { autoGaussianMixture me = Thing_new (GaussianMixture); my numberOfComponents = numberOfComponents; my dimension = dimension; my mixingProbabilities = NUMvector (1, numberOfComponents); my covariances = Ordered_create (); for (long im = 1; im <= numberOfComponents; im++) { autoCovariance cov = Covariance_create_reduceStorage (dimension, storage); Ordered_addItemPos (my covariances, cov.transfer(), im); } for (long im = 1; im <= numberOfComponents; im++) { my mixingProbabilities[im] = 1.0 / numberOfComponents; } GaussianMixture_setDefaultMixtureNames (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("GaussianMixture not created."); } } /* c is double vector 1..dimension !!!!!! */ int GaussianMixture_generateOneVector (GaussianMixture me, double *c, wchar_t **covname, double *buf) { try { double p = NUMrandomUniform (0, 1); long im = NUMgetIndexFromProbability (my mixingProbabilities, my numberOfComponents, p); Covariance thee = (Covariance) my covariances -> item[im]; *covname = thy name; if (thy numberOfRows == 1) { // 1xn reduced form for (long i = 1; i <= my dimension; i++) { c[i] = NUMrandomGauss (thy centroid[i], sqrt (thy data[1][i])); } } else { // nxn if (thy pca == 0) { SSCP_expandPCA (thee); // on demand expanding } Covariance_and_PCA_generateOneVector (thee, thy pca, c, buf); } return 1; } catch (MelderError) { Melder_throw (me, ": vector not generated."); } } GaussianMixture TableOfReal_to_GaussianMixture_fromRowLabels (I, long storage) { iam (TableOfReal); try { autoStrings rowLabels = TableOfReal_extractRowLabels (me); autoDistributions dist = Strings_to_Distributions (rowLabels.peek()); long numberOfComponents = dist -> numberOfRows; autoGaussianMixture thee = GaussianMixture_create (numberOfComponents, my numberOfColumns, storage); GaussianMixture_setLabelsFromTableOfReal (thee.peek(), me); for (long i = 1; i <= numberOfComponents; i++) { autoTableOfReal tab = TableOfReal_extractRowsWhereLabel (me, kMelder_string_EQUAL_TO, dist->rowLabels[i]); autoCovariance cov = TableOfReal_to_Covariance (tab.peek()); Covariance_into_Covariance (cov.peek(), (Covariance) thy covariances -> item[i]); Thing_setName ( (Thing) thy covariances -> item[i], dist -> rowLabels[i]); } for (long im = 1; im <= numberOfComponents; im++) { thy mixingProbabilities[im] = dist -> data[im][1] / my numberOfRows; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no GaussianMixture created."); } } Covariance GaussianMixture_to_Covariance_between (GaussianMixture me) { try { autoCovariance thee = Covariance_create (my dimension); // First the new centroid, based on the mixture centroids double nobs_total = 0; for (long i = 1; i <= my numberOfComponents; i++) { Covariance him = (Covariance) my covariances -> item[i]; double nobs = his numberOfObservations; // the weighting factor for (long ic = 1; ic <= my dimension; ic++) { thy centroid[ic] += nobs * his centroid[ic]; } nobs_total += nobs; } for (long ic = 1; ic <= my dimension; ic++) { thy centroid[ic] /= nobs_total; } Covariance cov = (Covariance) my covariances -> item[1]; for (long i = 1; i <= thy numberOfColumns; i++) { if (cov -> columnLabels[i]) { TableOfReal_setColumnLabel (thee.peek(), i, cov -> columnLabels[i]); TableOfReal_setRowLabel (thee.peek(), i, cov -> columnLabels[i]); // if diagonal ! } } // Between covariance, scale by the number of observations for (long i = 1; i <= my numberOfComponents; i++) { Covariance him = (Covariance) my covariances -> item[i]; double nobs = his numberOfObservations - 1; // we loose 1 degree of freedom for (long ir = 1; ir <= my dimension; ir++) { double dir = his centroid[ir] - thy centroid[ir]; for (long ic = ir; ic <= my dimension; ic++) { double dic = his centroid[ic] - thy centroid[ic]; thy data[ir][ic] = thy data[ic][ir] += nobs * dir * dic; } } } // Scale back for (long ir = 1; ir <= my dimension; ir++) { for (long ic = ir; ic <= my dimension; ic++) { thy data[ir][ic] = thy data[ic][ir] /= nobs_total; } } thy numberOfObservations = nobs_total; return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Covariance (between) created."); } } Covariance GaussianMixture_to_Covariance_within (GaussianMixture me) { try { autoCovariance thee = Covariance_create (my dimension); for (long i = 1; i <= my numberOfComponents; i++) { double p = my mixingProbabilities[i]; Covariance him = (Covariance) my covariances -> item[i]; if (his numberOfRows == 1) { for (long ic = 1; ic <= my dimension; ic++) { thy data[ic][ic] += p * his data[1][ic]; } } else { for (long ir = 1; ir <= my dimension; ir++) { for (long ic = ir; ic <= my dimension; ic++) { thy data[ir][ic] = thy data[ic][ir] += p * his data[ir][ic]; } } } thy numberOfObservations += his numberOfObservations - 1; // we loose a degree of freedom? } // Leave centroid at 0 so we can add the within and between covariance nicely TableOfReal_copyLabels (my covariances -> item[1], thee.peek(), 1, 1); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Covariance (within) created."); } } Covariance GaussianMixture_to_Covariance_total (GaussianMixture me) { try { autoCovariance thee = GaussianMixture_to_Covariance_between (me); autoCovariance within = GaussianMixture_to_Covariance_within (me); for (long ir = 1; ir <= my dimension; ir++) { for (long ic = ir; ic <= my dimension; ic++) { thy data[ir][ic] = thy data[ic][ir] += within -> data[ir][ic]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Covariance (total) created."); } } Covariance GaussianMixture_extractComponent (GaussianMixture me, long component) { try { if (component < 1 || component > my numberOfComponents) { Melder_throw ("Illegal component."); } return Data_copy ( (Covariance) my covariances -> item[component]); } catch (MelderError) { Melder_throw (me, ": no component extracted."); } } TableOfReal GaussianMixture_extractMixingProbabilities (GaussianMixture me) { try { autoTableOfReal thee = TableOfReal_create (my numberOfComponents, 2); TableOfReal_setColumnLabel (thee.peek(), 1, L"p"); TableOfReal_setColumnLabel (thee.peek(), 2, L"n"); for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; thy data[im][1] = my mixingProbabilities[im]; thy data[im][2] = cov -> numberOfObservations; TableOfReal_setRowLabel (thee.peek(), im, Thing_getName (cov)); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no mixing probabilities extracted."); } } TableOfReal GaussianMixture_extractCentroids (GaussianMixture me) { try { autoTableOfReal thee = TableOfReal_create (my numberOfComponents, my dimension); for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; if (im == 1) { for (long j = 1; j <= my dimension; j++) { TableOfReal_setColumnLabel (thee.peek(), j, cov -> columnLabels[j]); } } TableOfReal_setRowLabel (thee.peek(), im, Thing_getName (cov)); for (long j = 1; j <= my dimension; j++) { thy data[im][j] = cov -> centroid[j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no centroid extracted."); } } PCA GaussianMixture_to_PCA (GaussianMixture me) { try { autoCovariance him = GaussianMixture_to_Covariance_total (me); autoPCA thee = SSCP_to_PCA (him.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no PCA calculated."); } } void GaussianMixture_getIntervalsAlongDirections (GaussianMixture me, long d1, long d2, double nsigmas, double *xmin, double *xmax, double *ymin, double *ymax) { *xmin = *xmax = *ymin = *ymax = NUMundefined; if (d1 < 1 || d1 > my dimension || d2 < 1 || d2 > my dimension) { Melder_throw ("Incorrect directions."); } autoSSCPs sscps = SSCPs_extractTwoDimensions ( (SSCPs) my covariances, d1, d2); SSCPs_getEllipsesBoundingBoxCoordinates (sscps.peek(), -nsigmas, 0, xmin, xmax, ymin, ymax); } void GaussianMixture_getIntervalAlongDirection (GaussianMixture me, long d, double nsigmas, double *xmin, double *xmax) { double ymin, ymax; GaussianMixture_getIntervalsAlongDirections (me, d, d, nsigmas, xmin, xmax, &ymin, &ymax); } void GaussianMixture_and_PCA_getIntervalsAlongDirections (GaussianMixture me, PCA thee, long d1, long d2, double nsigmas, double *xmin, double *xmax, double *ymin, double *ymax) { *xmin = *xmax = *ymin = *ymax = NUMundefined; if (my dimension != thy dimension || d1 < 1 || d1 > my dimension || d2 < 1 || d2 > my dimension) { Melder_throw ("Incorrect directions."); } autoSSCPs sscps = SSCPs_toTwoDimensions ( (SSCPs) my covariances, thy eigenvectors[d1], thy eigenvectors[d2]); SSCPs_getEllipsesBoundingBoxCoordinates (sscps.peek(), -nsigmas, 0, xmin, xmax, ymin, ymax); } void GaussianMixture_and_PCA_getIntervalAlongDirection (GaussianMixture me, PCA thee, long d, double nsigmas, double *xmin, double *xmax) { double ymin, ymax; GaussianMixture_and_PCA_getIntervalsAlongDirections (me, thee, d, d, nsigmas, xmin, xmax, &ymin, &ymax); } void GaussianMixture_and_PCA_drawMarginalPdf (GaussianMixture me, PCA thee, Graphics g, long d, double xmin, double xmax, double ymin, double ymax, long npoints, long nbins, int garnish) { if (my dimension != thy dimension || d < 1 || d > my dimension) { Melder_warning (L"Dimensions don't agree."); return; } if (npoints <= 1) { npoints = 1000; } autoNUMvector p (1, npoints); double nsigmas = 2; if (xmax <= xmin) { GaussianMixture_and_PCA_getIntervalAlongDirection (me, thee, d, nsigmas, &xmin, &xmax); } double pmax = 0, dx = (xmax - xmin) / npoints, x1 = xmin + 0.5 * dx; double scalef = nbins <= 0 ? 1 : 1; // TODO for (long i = 1; i <= npoints; i++) { double x = x1 + (i - 1) * dx; p[i] = scalef * GaussianMixture_getMarginalProbabilityAtPosition (me, thy eigenvectors[d], x); if (p[i] > pmax) { pmax = p[i]; } } if (ymin >= ymax) { ymin = 0; ymax = pmax; } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_function (g, p.peek(), 1, npoints, x1, xmax - 0.5 * dx); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_markBottom (g, xmin, 1, 1, 0, NULL); Graphics_markBottom (g, xmax, 1, 1, 0, NULL); Graphics_markLeft (g, ymin, 1, 1, 0, NULL); Graphics_markLeft (g, ymax, 1, 1, 0, NULL); } } void GaussianMixture_drawMarginalPdf (GaussianMixture me, Graphics g, long d, double xmin, double xmax, double ymin, double ymax, long npoints, long nbins, int garnish) { if (d < 1 || d > my dimension) { Melder_warning (L"Dimension doesn't agree."); return; } if (npoints <= 1) { npoints = 1000; } autoNUMvector p (1, npoints); autoNUMvector v (1, my dimension); double nsigmas = 2; if (xmax <= xmin) { GaussianMixture_getIntervalAlongDirection (me, d, nsigmas, &xmin, &xmax); } double pmax = 0, dx = (xmax - xmin) / (npoints - 1); double scalef = nbins <= 0 ? 1 : 1; // TODO for (long i = 1; i <= npoints; i++) { double x = xmin + (i - 1) * dx; for (long k = 1; k <= my dimension; k++) { v[k] = k == d ? 1 : 0; } p[i] = scalef * GaussianMixture_getMarginalProbabilityAtPosition (me, v.peek(), x); if (p[i] > pmax) { pmax = p[i]; } } if (ymin >= ymax) { ymin = 0; ymax = pmax; } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_function (g, p.peek(), 1, npoints, xmin, xmax); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_markBottom (g, xmin, 1, 1, 0, NULL); Graphics_markBottom (g, xmax, 1, 1, 0, NULL); Graphics_markLeft (g, ymin, 1, 1, 0, NULL); Graphics_markLeft (g, ymax, 1, 1, 0, NULL); } } void GaussianMixture_and_PCA_drawConcentrationEllipses (GaussianMixture me, PCA him, Graphics g, double scale, int confidence, wchar_t *label, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish) { if (my dimension != his dimension) { Melder_warning (L"Dimensions don't agree."); return; } int d1_inverted = 0, d2_inverted = 0; if (d1 < 0) { d1 = abs (d1); Eigen_invertEigenvector (him, d1); d1_inverted = 1; } if (d2 < 0) { d2 = abs (d2); Eigen_invertEigenvector (him, d2); d2_inverted = 1; } autoSSCPs thee = SSCPs_toTwoDimensions ( (SSCPs) my covariances, his eigenvectors[d1], his eigenvectors[d2]); if (d1_inverted) { Eigen_invertEigenvector (him, d1); } if (d2_inverted) { Eigen_invertEigenvector (him, d2); } SSCPs_drawConcentrationEllipses (thee.peek(), g, -scale, confidence, label, 1, 2, xmin, xmax, ymin, ymax, fontSize, 0); if (garnish) { wchar_t llabel[40]; Graphics_drawInnerBox (g); Graphics_marksLeft (g, 2, 1, 1, 0); swprintf (llabel, 40, L"pc %ld", d2); Graphics_textLeft (g, 1, llabel); Graphics_marksBottom (g, 2, 1, 1, 0); swprintf (llabel, 40, L"pc %ld", d1); Graphics_textBottom (g, 1, llabel); } } void GaussianMixture_drawConcentrationEllipses (GaussianMixture me, Graphics g, double scale, int confidence, wchar_t *label, int pcaDirections, long d1, long d2, double xmin, double xmax, double ymin, double ymax, int fontSize, int garnish) { if (d1 == 0 && d2 == 0) { d1 = 1; d2 = 2; } if (abs (d1) > my dimension || abs (d2) > my dimension) { return; } if (! pcaDirections) { SSCPs_drawConcentrationEllipses ( (SSCPs) my covariances, g, -scale, confidence, label, abs (d1), abs (d2), xmin, xmax, ymin, ymax, fontSize, garnish); return; } autoPCA him = GaussianMixture_to_PCA (me); GaussianMixture_and_PCA_drawConcentrationEllipses (me, him.peek(), g, scale, confidence, label, d1, d2, xmin, xmax, ymin, ymax, fontSize, garnish); } void GaussianMixture_initialGuess (GaussianMixture me, TableOfReal thee, double nSigmas, double ru_range) { try { autoCovariance cov_t = TableOfReal_to_Covariance (thee); // assume equal probabilities for mixture // assume equal covariance matrices // spread centroids on an ellips in pc1-pc2 plane? if (my dimension == 1) { double dm = 2 * sqrt (cov_t -> data[1][1]) / my numberOfComponents; double m1 = cov_t -> centroid[1] - dm; for (long im = 1; im <= my numberOfComponents; im++) { Covariance covi = (Covariance) my covariances -> item[im]; covi -> centroid[1] = m1; covi -> data[1][1] = dm * dm; m1 += dm; covi -> numberOfObservations = thy numberOfRows / my numberOfComponents; } } else { autoPCA pca = SSCP_to_PCA (cov_t.peek()); autoSSCP s2d = SSCP_toTwoDimensions (cov_t.peek(), pca -> eigenvectors[1], pca -> eigenvectors[2]); autoConfiguration means2d = Configuration_create (my numberOfComponents, 2); double a, b, cs, sn; NUMeigencmp22 (s2d -> data[1][1], s2d -> data[1][2], s2d -> data[2][2], &a, &b, &cs, &sn); a = nSigmas * sqrt (a); b = nSigmas * sqrt (b); double angle = 0, angle_inc = NUM2pi / my numberOfComponents; for (long im = 1; im <= my numberOfComponents; im++, angle += angle_inc) { double xc = a * (1 + NUMrandomUniform (-ru_range, ru_range)) * cos (angle); double yc = b * (1 + NUMrandomUniform (-ru_range, ru_range)) * sin (angle); means2d -> data[im][1] = s2d -> centroid[1] + xc * cs - yc * sn; means2d -> data[im][2] = s2d -> centroid[2] + xc * sn + yc * cs; } // reconstruct the n-dimensional means from the 2-d from the eigenvectors autoTableOfReal means = PCA_and_Configuration_to_TableOfReal_reconstruct (pca.peek(), means2d.peek()); for (long im = 1; im <= my numberOfComponents; im++) { Covariance covi = (Covariance) my covariances -> item[im]; for (long ic = 1; ic <= my dimension; ic++) { covi -> centroid[ic] = means -> data[im][ic]; } covi -> numberOfObservations = thy numberOfRows / my numberOfComponents; } // Trick: use the new means to get the between SSCP, // if there is only one component the cov_b will be zero! autoCovariance cov_b = GaussianMixture_to_Covariance_between (me); double var_t = SSCP_getTotalVariance (cov_t.peek()); double var_b = SSCP_getTotalVariance (cov_b.peek()); if (var_b >= var_t) { // we have chosen our initial values too far out double scale = 0.9 * sqrt (var_t / var_b); for (long im = 1; im <= my numberOfComponents; im++) { Covariance covi = (Covariance) my covariances -> item[im]; for (long ic = 1; ic <= my dimension; ic++) { covi -> centroid[ic] -= (1 - scale) * (covi -> centroid[ic] - cov_b -> centroid[ic]); } } cov_b.reset (GaussianMixture_to_Covariance_between (me)); } // Within variances are now (total - between) / numberOfComponents; for (long ir = 1; ir <= my dimension; ir++) { for (long ic = ir; ic <= my dimension; ic++) { double scalef = my numberOfComponents == 1 ? 1 : (var_b / var_t) / my numberOfComponents; cov_t -> data[ic][ir] = cov_t -> data[ir][ic] *= scalef; } } // Copy them for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; if (cov -> numberOfRows == 1) { for (long ic = 1; ic <= my dimension; ic++) { cov -> data[1][ic] = cov_t -> data[ic][ic]; } } else { for (long ir = 1; ir <= my dimension; ir++) { for (long ic = ir; ic <= my dimension; ic++) { cov -> data[ir][ic] = cov -> data[ic][ir] = cov_t -> data[ir][ic]; } } } } } } catch (MelderError) { Melder_throw (me, " & ", thee, ": no initial guess possible."); } } ClassificationTable GaussianMixture_and_TableOfReal_to_ClassificationTable (GaussianMixture me, TableOfReal thee) { try { autoClassificationTable him = ClassificationTable_create (thy numberOfRows, my numberOfComponents); for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; SSCP_expandLowerCholesky (cov); TableOfReal_setColumnLabel (him.peek(), im, Thing_getName (cov)); } double ln2pid = - 0.5 * my dimension * log (NUM2pi); autoNUMvector lnN (1, my numberOfComponents); for (long i = 1; i <= thy numberOfRows; i++) { double psum = 0; for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; double dsq = NUMmahalanobisDistance_chi (cov -> lowerCholesky, thy data[i], cov -> centroid, cov -> numberOfRows, my dimension); lnN[im] = ln2pid - 0.5 * (cov -> lnd + dsq); psum += his data[i][im] = my mixingProbabilities[im] * exp (lnN[im]); } if (psum == 0) { // p's might be too small (underflow), make the largest equal to sfmin double lnmax = -INFINITY; long imm = 1; for (long im = 1; im <= my numberOfComponents; im++) { if (lnN[im] > lnmax) { lnmax = lnN[im]; } imm = im; } his data[i][imm] = NUMfpp -> sfmin; } // for (long im = 1; im <= my numberOfComponents; im++) { his data[i][im] /= psum; } TableOfReal_setRowLabel (him.peek(), i, thy rowLabels[i]); } return him.transfer(); } catch (MelderError) { Melder_throw ("No ClassificationTable created from GaussianMixture & TableOfReal."); } } void GaussianMixture_and_TableOfReal_getGammas (GaussianMixture me, TableOfReal thee, double **gamma, double *lnp) { try { for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; SSCP_expandLowerCholesky (cov); } double *nk = gamma[thy numberOfRows + 1]; for (long im = 1; im <= my numberOfComponents; im++) { nk[im] = 0; } *lnp = 0; double ln2pid = - 0.5 * my dimension * log (NUM2pi); autoNUMvector lnN (1, my numberOfComponents); for (long i = 1; i <= thy numberOfRows; i++) { double rowsum = 0; for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; double dsq = NUMmahalanobisDistance_chi (cov -> lowerCholesky, thy data[i], cov -> centroid, cov -> numberOfRows, my dimension); lnN[im] = ln2pid - 0.5 * (cov -> lnd + dsq); gamma[i][im] = my mixingProbabilities[im] * exp (lnN[im]); // eq. Bishop 9.16 rowsum += gamma[i][im]; } // If the gamma[i]'s are too small, their sum will be zero and the scaling will overflow if (rowsum == 0) { continue; // This is ok because gamma[i]'s will all be zero } // scale gamma and get log(likehood) (Bishop eq. 9.40) for (long im = 1; im <= my numberOfComponents; im++) { gamma[i][im] /= rowsum; // eq. Bishop 9.16 nk[im] += gamma[i][im]; // eq. Bishop 9.18 *lnp += gamma[i][im] * (log (my mixingProbabilities[im]) + lnN[im]); // eq. Bishop 9.40 } } } catch (MelderError) { Melder_throw (me, " & ", thee, ": no gammas."); } } void GaussianMixture_splitComponent (GaussianMixture me, long component) { try { if (component < 1 || component > my numberOfComponents) { Melder_throw ("Illegal component."); } Covariance thee = (Covariance) my covariances -> item[component]; // Always new PCA because we cannot be sure of data unchanged. SSCP_expandPCA (thee); autoCovariance cov1 = Data_copy ( (Covariance) thee); autoCovariance cov2 = Data_copy ( (Covariance) thee); SSCP_unExpandPCA (cov1.peek()); SSCP_unExpandPCA (cov2.peek()); // Eventually cov1 replaces component, cov2 at end autoNUMvector mixingProbabilities (1, my numberOfComponents + 1); for (long i = 1; i <= my numberOfComponents; i++) { mixingProbabilities[i] = my mixingProbabilities[i]; } double gamma = 0.5, lambda = 0.5, eta = 0.5, mu = 0.5; mixingProbabilities[component] = gamma * my mixingProbabilities[component]; mixingProbabilities[my numberOfComponents + 1] = (1 - gamma) * my mixingProbabilities[component]; double mp12 = mixingProbabilities[component] / mixingProbabilities[my numberOfComponents + 1]; double factor1 = (eta - eta * lambda * lambda - 1) / gamma + 1; double factor2 = (eta * lambda * lambda - eta - lambda * lambda) / (1 - gamma) + 1; double *ev = thy pca -> eigenvectors[1]; double d2 = thy pca -> eigenvalues[1]; for (long i = 1; i <= my dimension; i++) { cov1 -> centroid[i] -= (1 / sqrt (mp12)) * sqrt (d2) * mu * ev[i]; cov2 -> centroid[i] += sqrt (mp12) * sqrt (d2) * mu * ev[i]; if (thy numberOfRows == 1) { // diagonal cov1 -> data[1][i] = cov1 -> data [1][i] / mp12 + factor1 * d2; cov1 -> data[1][i] = cov2 -> data [i][i] * mp12 + factor2 * d2; } else { for (long j = i; j <= my dimension; j++) { cov1 -> data[j][i] = cov1 -> data[i][j] = cov1 -> data [i][j] / mp12 + factor1 * d2 * ev[i] * ev[j]; cov2 -> data[j][i] = cov2 -> data[i][j] = cov2 -> data [i][j] * mp12 + factor2 * d2 * ev[i] * ev[j]; } } } cov1 -> numberOfObservations *= gamma; cov2 -> numberOfObservations *= 1 - gamma; // Replace cov1 at component + add cov2. If something goes wrong we must be able to restore original! try { Thing_setName (cov2.peek(), Melder_wcscat (Thing_getName (cov2.peek()), L"-", Melder_integer (my numberOfComponents + 1))); Collection_addItem (my covariances, cov2.transfer()); } catch (MelderError) { Melder_throw (me, " cannot add new component."); } my covariances -> item[component] = cov1.transfer(); my numberOfComponents++; NUMvector_free (my mixingProbabilities, 1); my mixingProbabilities = mixingProbabilities.transfer(); } catch (MelderError) { Melder_throw (me, ": component ", component, " cannot be split."); } } int GaussianMixture_and_TableOfReal_getProbabilities (GaussianMixture me, TableOfReal thee, long component, double **p) { try { double ln2pid = my dimension * log (NUM2pi); // Update only one component or all? long icb = 1, ice = my numberOfComponents; if (component > 0 && component <= my numberOfComponents) { icb = ice = component; } for (long ic = icb; ic <= ice; ic++) { Covariance him = (Covariance) my covariances -> item[ic]; SSCP_expandLowerCholesky (him); for (long i = 1; i <= thy numberOfRows; i++) { double dsq = NUMmahalanobisDistance_chi (his lowerCholesky, thy data[i], his centroid, his numberOfRows, my dimension); p[i][ic] = exp (- 0.5 * (ln2pid + his lnd + dsq)); } } GaussianMixture_updateProbabilityMarginals (me, p, thy numberOfRows); return 1; } catch (MelderError) { Melder_throw (me, " & ", thee, ": no probabilies could be calculated."); } } void GaussianMixture_expandPCA (GaussianMixture me) { for (long im = 1; im <= my numberOfComponents; im++) { Covariance him = (Covariance) my covariances -> item[im]; if (his numberOfRows == 1) { Melder_throw ("Nothing to expand."); } his pca = SSCP_to_PCA (him); } } void GaussianMixture_unExpandPCA (GaussianMixture me) { for (long im = 1; im <= my numberOfComponents; im++) { SSCP_unExpandPCA (my covariances -> item[im]); } } void GaussianMixture_and_TableOfReal_improveLikelihood (GaussianMixture me, thou, double delta_lnp, long maxNumberOfIterations, double lambda, int criterion) { thouart (TableOfReal); try { const wchar_t *criterionText = GaussianMixture_criterionText (criterion); // The global covariance matrix is added with scaling coefficient lambda during updating the // mixture covariances to prevent numerical instabilities. autoCovariance covg = TableOfReal_to_Covariance (thee); autoNUMmatrix pp (1, thy numberOfRows + 1, 1, my numberOfComponents + 1); double *nk = pp[thy numberOfRows + 1]; // last row has the column marginals n(k) if (! GaussianMixture_and_TableOfReal_getProbabilities (me, thee, 0, pp.peek())) { MelderInfo_writeLine1 (L"Iteration not started, may be too much components?"); Melder_throw ("Iteration not started."); } double lnp = GaussianMixture_getLikelihoodValue (me, pp.peek(), thy numberOfRows, criterion); long iter = 0; MelderInfo_writeLine6 (L"\nIteration ", Melder_integer (iter), L": ", Melder_double (lnp / thy numberOfRows), L" (= ", criterionText); MelderInfo_open (); double lnp_prev; do { // E-step: get responsabilities (gamma) with current parameters // See C. Bishop (2006), Pattern reconition and machine learning, Springer, page 439... lnp_prev = lnp; iter++; // M-step: 1. new means & covariances for (long im = 1; im <= my numberOfComponents; im++) { GaussianMixture_updateCovariance (me, im, thy data, thy numberOfRows, pp.peek()); GaussianMixture_addCovarianceFraction (me, im, covg.peek(), lambda); } // M-step: 2. new mixingProbabilities for (long im = 1; im <= my numberOfComponents; im++) { my mixingProbabilities[im] = nk[im] / thy numberOfRows; } if (! GaussianMixture_and_TableOfReal_getProbabilities (me, thee, 0, pp.peek())) { break; } lnp = GaussianMixture_getLikelihoodValue (me, pp.peek(), thy numberOfRows, criterion); MelderInfo_writeLine6 (L"\nIteration ", Melder_integer (iter), L": ", Melder_double (lnp / thy numberOfRows), L" (= ", criterionText); } while (fabs ( (lnp - lnp_prev) / lnp_prev) > delta_lnp && iter < maxNumberOfIterations); // During EM, covariances were underestimated by a factor of (n-1)/n. Correction now. for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; if (cov -> numberOfObservations > 1.5) { if (cov -> numberOfRows == 1) { for (long j = 1; j <= thy numberOfColumns; j++) { cov -> data[1][j] *= cov -> numberOfObservations / (cov -> numberOfObservations - 1); } } else { for (long j = 1; j <= thy numberOfColumns; j++) for (long k = j; k <= thy numberOfColumns; k++) { cov -> data[j][k] = cov -> data[k][j] *= cov -> numberOfObservations / (cov -> numberOfObservations - 1); } } } } } catch (MelderError) { Melder_throw (me, " & ", thee, ": likelihood cannot be improved."); } } long GaussianMixture_getNumberOfParametersInComponent (GaussianMixture me) { Covariance thee = (Covariance) my covariances -> item[1]; // if diagonal) d (means) + d (stdev) // else n + n(n+1)/2 return thy numberOfRows == 1 ? 2 * thy numberOfColumns : thy numberOfColumns * (thy numberOfColumns + 3) / 2; } void GaussianMixture_updateProbabilityMarginals (GaussianMixture me, double **p, long numberOfRows) { long nocp1 = my numberOfComponents + 1, norp1 = numberOfRows + 1; for (long ic = 1; ic <= my numberOfComponents; ic++) { p[norp1][ic] = 0; } for (long i = 1; i <= numberOfRows; i++) { double rowsum = 0; for (long ic = 1; ic <= my numberOfComponents; ic++) { rowsum += my mixingProbabilities[ic] * p[i][ic]; } p[i][nocp1] = rowsum; for (long ic = 1; ic <= my numberOfComponents; ic++) { p[norp1][ic] += my mixingProbabilities[ic] * p[i][ic] / p[i][nocp1]; } } } void GaussianMixture_removeComponent_bookkeeping (GaussianMixture me, long component, double **p, long numberOfRows) { // p is (NumberOfRows+1) by (numberOfComponents+1) ! for (long i = 1; i <= numberOfRows + 1; i++) { for (long ic = component; ic <= my numberOfComponents; ic++) { p[i][ic] = p[i][ic + 1]; } } GaussianMixture_updateProbabilityMarginals (me, p, numberOfRows); GaussianMixture_removeComponent (me, component); } double GaussianMixture_and_TableOfReal_getLikelihoodValue (GaussianMixture me, thou, int criterion) { thouart (TableOfReal); double value = NUMundefined; autoNUMmatrix pp (1, thy numberOfRows + 1, 1, my numberOfComponents + 1); if (GaussianMixture_and_TableOfReal_getProbabilities (me, thee, 0, pp.peek())) { value = GaussianMixture_getLikelihoodValue (me, pp.peek(), thy numberOfRows, criterion); } return value; } double GaussianMixture_getLikelihoodValue (GaussianMixture me, double **p, long numberOfRows, int criterion) { // Because we try to _maximize_ a criterion, all criteria are negative numbers. if (criterion == GaussianMixture_CD_LIKELIHOOD) { double lnpcd = 0; for (long i = 1; i <= numberOfRows; i++) { double psum = 0, lnsum = 0; for (long ic = 1; ic <= my numberOfComponents; ic++) { double pp = my mixingProbabilities[ic] * p[i][ic]; psum += pp; lnsum += pp * log (pp); } if (psum > 0) { lnpcd += lnsum / psum; } } return lnpcd; } // The common factor for all other criteria is the log(likelihood) double lnp = 0; for (long i = 1; i <= numberOfRows; i++) { double psum = 0; for (long ic = 1; ic <= my numberOfComponents; ic++) { psum += my mixingProbabilities[ic] * p[i][ic]; } if (psum > 0) { lnp += log (psum); } } if (criterion == GaussianMixture_LIKELIHOOD) { return lnp; } double npars = GaussianMixture_getNumberOfParametersInComponent (me), np = npars * my numberOfComponents; if (criterion == GaussianMixture_MML) { /* Equation (15) in Mario A.T. Figueiredo, and Anil K. Jain, Unsupervised Learning of Finite Mixture Models : IEEE TRANSACTIONS ON PATTERN ANALYSIS AND MACHINE INTELLIGENCE, VOL. 24, NO. 3, MARCH 2002 L(theta,Y)= N/2*sum(m=1..k, log(n*alpha[k]/12)) +k/2*ln(n/12) +k(N+1)/2 - log (sum(i=1..n, sum(m=1..k, alpha[k]*p(k)))) */ double logmpn = 0; for (long ic = 1; ic <= my numberOfComponents; ic++) { logmpn += log (my mixingProbabilities[ic]); } // a rewritten L(theta,Y) is return lnp - 0.5 * my numberOfComponents * (npars + 1) * (log (numberOfRows / 12.0) + 1) + 0.5 * npars * logmpn; } else if (criterion == GaussianMixture_BIC) { return 2 * lnp - np * log (numberOfRows); } else if (criterion == GaussianMixture_AIC) { return 2 * (lnp - np); } else if (criterion == GaussianMixture_AICC) { np = npars * my numberOfComponents; return 2 * (lnp - np * (numberOfRows / (numberOfRows - np - 1))); } return lnp; } GaussianMixture GaussianMixture_and_TableOfReal_to_GaussianMixture_CEMM (GaussianMixture gm, thou, long minNumberOfComponents, double delta_l, long maxNumberOfIterations, double lambda, int criterion) { try { thouart (TableOfReal); const wchar_t *criterionText = GaussianMixture_criterionText (criterion); int deleteWeakComponents = minNumberOfComponents > 0; autoGaussianMixture me = Data_copy (gm); autoNUMmatrix p (1, thy numberOfRows + 2, 1, my numberOfComponents + 1); double *gsum = p[thy numberOfRows + 1]; // convenience array with sums autoCovariance covg = TableOfReal_to_Covariance (thee); double npars = GaussianMixture_getNumberOfParametersInComponent (me.peek()); double nparsd2 = deleteWeakComponents ? npars / 2 : 0; // Initial E-step: Update all p's. GaussianMixture_and_TableOfReal_getProbabilities (me.peek(), thee, 0, p.peek()); double lnew = GaussianMixture_getLikelihoodValue (me.peek(), p.peek(), thy numberOfRows, criterion); MelderInfo_open (); long iter = 0, component; MelderInfo_writeLine6 (L"iter: ", Melder_integer (iter), criterionText, Melder_double (lnew / thy numberOfRows), L", Components: ", Melder_integer (my numberOfComponents)); autoGaussianMixture best = 0; double lmax = -INFINITY, lprev; while (my numberOfComponents >= minNumberOfComponents) { do { iter++; component = 1; lprev = lnew; while (component <= my numberOfComponents) { // M-step for means and covariances GaussianMixture_updateProbabilityMarginals (me.peek(), p.peek(), thy numberOfRows); GaussianMixture_updateCovariance (me.peek(), component, thy data, thy numberOfRows, p.peek()); if (lambda > 0) { GaussianMixture_addCovarianceFraction (me.peek(), component, covg.peek(), lambda); } // Now check if enough support for a component exists double support_im = gsum[component] - nparsd2, support = 0; for (long ic = 1; ic <= my numberOfComponents; ic++) { double support_ic = gsum[ic] - nparsd2; if (support_ic > 0) { support += support_ic; } } my mixingProbabilities[component] = support_im > 0 ? support_im : 0; if (support > 0) { my mixingProbabilities[component] /= support; } NUMdvector_scaleAsProbabilities (my mixingProbabilities, my numberOfComponents); if (my mixingProbabilities[component] > 0) { // update p for component GaussianMixture_and_TableOfReal_getProbabilities (me.peek(), thee, component, p.peek()); component++; } else { // "Remove" the component column from p by shifting row values GaussianMixture_removeComponent_bookkeeping (me.peek(), component, p.peek(), thy numberOfRows); // Now numberOfComponents is one less! MelderInfo_writeLine2 (L"Removed component ", Melder_integer (component)); } } // L(theta,Y)=N/2 sum(m=1..k, log(n*mixingP[m]/12))+k/2log(n/12)+k/2(N+1)-loglikelihood reduces to: // k/2 (N+1){log(n/12)+1}+N/2sum(m=1..k,mixingP[m]) - loglikelihood lnew = GaussianMixture_getLikelihoodValue (me.peek(), p.peek(), thy numberOfRows, criterion); MelderInfo_writeLine8 (L"iter: ", Melder_integer (iter), L", ", criterionText, L"= ", Melder_double (lnew / thy numberOfRows), L", Components: ", Melder_integer (my numberOfComponents)); } while (lnew > lprev && fabs ( (lprev - lnew) / lnew) > delta_l && iter < maxNumberOfIterations); if (lnew > lmax) { best.reset (Data_copy (me.peek())); lmax = lnew; if (! deleteWeakComponents) { break; // TODO was got end; is dat hetzelfde? } } if (my numberOfComponents > 1) { // remove smallest component component = 1; double mpmin = my mixingProbabilities[component]; for (long ic = 2; ic <= my numberOfComponents; ic++) { if (my mixingProbabilities[ic] < mpmin) { mpmin = my mixingProbabilities[ic]; component = ic; } } GaussianMixture_removeComponent_bookkeeping (me.peek(), component, p.peek(), thy numberOfRows); } else { break; } } MelderInfo_close (); return best.transfer(); } catch (MelderError) { MelderInfo_close (); Melder_throw ("GaussianMixture not improved."); } } // The numberOfElemnts per covariance needs to be updated later void GaussianMixture_removeComponent (GaussianMixture me, long component) { if (component < 1 || component > my numberOfComponents || my numberOfComponents == 1) { return; } Collection_removeItem (my covariances, component); my numberOfComponents --; for (long ic = component; ic <= my numberOfComponents; ic++) { my mixingProbabilities[ic] = my mixingProbabilities[ic + 1]; } NUMdvector_scaleAsProbabilities (my mixingProbabilities, my numberOfComponents); } GaussianMixture TableOfReal_to_GaussianMixture (I, long numberOfComponents, double delta_lnp, long maxNumberOfIterations, double lambda, int storage, int criterion) { iam (TableOfReal); try { if (my numberOfRows < 2 * numberOfComponents) { Melder_throw ("The number of data points must at least be twice the number of components."); } autoGaussianMixture thee = GaussianMixture_create (numberOfComponents, my numberOfColumns, storage); GaussianMixture_setLabelsFromTableOfReal (thee.peek(), me); GaussianMixture_initialGuess (thee.peek(), me, 1, 0.05); if (maxNumberOfIterations <= 0) { return thee.transfer(); } GaussianMixture_and_TableOfReal_improveLikelihood (thee.peek(), me, delta_lnp, maxNumberOfIterations, lambda, criterion); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no GaussianMixture created."); } } Correlation GaussianMixture_and_TableOfReal_to_Correlation (GaussianMixture me, thou) { try { thouart (TableOfReal); if (my dimension != thy numberOfColumns) { Melder_throw ("Dimensions must be equal."); } autoClassificationTable ct = GaussianMixture_and_TableOfReal_to_ClassificationTable (me, thee); autoCorrelation him = ClassificationTable_to_Correlation_columns (ct.peek()); return him.transfer(); } catch (MelderError) { Melder_throw ("Correlation not created from GaussianMixture & TableOfReal."); } } double GaussianMixture_getProbabilityAtPosition_string (GaussianMixture me, const wchar_t *vector) { autoNUMvector v (1, my dimension); long i = 0; for (wchar_t *token = Melder_firstToken (vector); token != NULL; token = Melder_nextToken ()) { v[++i] = Melder_atof (token); if (i == my dimension) { break; } } double p = GaussianMixture_getProbabilityAtPosition (me, v.peek()); return p; } double GaussianMixture_getMarginalProbabilityAtPosition (GaussianMixture me, double *vector, double x) { double p = 0; for (long im = 1; im <= my numberOfComponents; im++) { double pim = Covariance_getMarginalProbabilityAtPosition ( (Covariance) my covariances -> item[im], vector, x); p += my mixingProbabilities[im] * pim; } return p; } double GaussianMixture_getProbabilityAtPosition (GaussianMixture me, double *xpos) { double p = 0; for (long im = 1; im <= my numberOfComponents; im++) { double pim = Covariance_getProbabilityAtPosition ( (Covariance) my covariances -> item[im], xpos); p += my mixingProbabilities[im] * pim; } return p; } Matrix GaussianMixture_and_PCA_to_Matrix_density (GaussianMixture me, PCA thee, long d1, long d2, double xmin, double xmax, long nx, double ymin, double ymax, long ny) { try { if (my dimension != thy dimension) { Melder_throw ("Dimensions must be equal."); } if (d1 > thy numberOfEigenvalues || d2 > thy numberOfEigenvalues) { Melder_throw ("Direction index too high."); } autoNUMvector v (1, my dimension); if (xmax == xmin || ymax == ymin) { double xmind, xmaxd, ymind, ymaxd, nsigmas = 2; GaussianMixture_and_PCA_getIntervalsAlongDirections (me, thee, d1, d2, nsigmas, &xmind, &xmaxd, &ymind, &ymaxd); if (xmax == xmin) { xmin = xmind; xmax = xmaxd; } if (ymax == ymin) { ymin = ymind; ymax = ymaxd; } } // xmin,xmax and ymin,ymax are coordinates in the pc1 vs pc2 plane double dx = fabs (xmax - xmin) / nx, dy = fabs (ymax - ymin) / ny; double x1 = xmin + 0.5 * dx, y1 = ymin + 0.5 * dy; autoMatrix him = Matrix_create (xmin, xmax, nx, dx, x1, ymin, ymax, ny, dy, y1); for (long i = 1; i <= ny; i++) { double y = y1 + (i - 1) * dy; for (long j = 1; j <= nx; j++) { double x = x1 + (j - 1) * dx; for (long k = 1; k <= my dimension; k++) { v[k] = x * thy eigenvectors[d1][k] + y * thy eigenvectors[d2][k]; } his z[i][j] = GaussianMixture_getProbabilityAtPosition (me, v.peek()); } } return him.transfer(); } catch (MelderError) { Melder_throw (me, " & ", thee, ": no Matrix density created."); } } TableOfReal GaussianMixture_to_TableOfReal_randomSampling (GaussianMixture me, long numberOfPoints) { try { Covariance cov = (Covariance) my covariances -> item[1]; autoTableOfReal thee = TableOfReal_create (numberOfPoints, my dimension); autoNUMvector buf (1, my dimension); NUMstrings_copyElements (cov -> columnLabels, thy columnLabels, 1, my dimension); for (long i = 1; i <= numberOfPoints; i++) { wchar_t *covname; GaussianMixture_generateOneVector (me, thy data[i], &covname, buf.peek()); TableOfReal_setRowLabel (thee.peek(), i, covname); } GaussianMixture_unExpandPCA (me); return thee.transfer(); } catch (MelderError) { GaussianMixture_unExpandPCA (me); Melder_throw ("TableOfReal with random ssampling not created."); } } TableOfReal GaussianMixture_and_TableOfReal_to_TableOfReal_BHEPNormalityTests (GaussianMixture me, thou, double h) { try { thouart (TableOfReal); long n = thy numberOfRows, d = thy numberOfColumns, nocp1 = my numberOfComponents + 1; if (d != my dimension) { Melder_throw ("Dimensions do not agree."); } // We cannot use a classification table because this could weigh a far-off data point with high probability autoNUMmatrix p (1, thy numberOfRows + 1, 1, my numberOfComponents + 1); GaussianMixture_and_TableOfReal_getProbabilities (me, thee, 0, p.peek()); // prob, beta, tnbo, lnmu, lnvar, ndata, ncol autoTableOfReal him = TableOfReal_create (my numberOfComponents, 7); // labels long iprob = 1, ih = 2, itnb = 3, ilnmu = 4, ilnvar = 5, indata = 6, id = 7; const wchar_t *label[8] = { L"", L"p", L"h", L"tnb", L"lnmu", L"lnvar", L"ndata", L"d" }; for (long icol = 1; icol <= 7; icol++) { TableOfReal_setColumnLabel (him.peek(), icol, label[icol]); } for (long irow = 1; irow <= my numberOfComponents; irow++) { Covariance cov = (Covariance) my covariances -> item[irow]; TableOfReal_setRowLabel (him.peek(), irow, Thing_getName (cov)); } for (long icol = 1 ; icol <= my numberOfComponents; icol++) { his data[icol][indata] = p[n + 1][icol]; } for (long im = 1; im <= my numberOfComponents; im++) { Covariance cov = (Covariance) my covariances -> item[im]; double mixingP = my mixingProbabilities[im]; double nd = his data[im][indata], d2 = d / 2.0; double beta = h > 0 ? NUMsqrt1_2 / h : NUMsqrt1_2 * pow ( (1.0 + 2 * d) / 4, 1.0 / (d + 4)) * pow (nd, 1.0 / (d + 4)); double beta2 = beta * beta, beta4 = beta2 * beta2, beta8 = beta4 * beta4; double gamma = 1 + 2 * beta2, gamma2 = gamma * gamma, gamma4 = gamma2 * gamma2; double delta = 1.0 + beta2 * (4 + 3 * beta2), delta2 = delta * delta; double mu = 1.0 - pow (gamma, -d2) * (1.0 + d * beta2 / gamma + d * (d + 2) * beta4 / (2 * gamma2)); double var = 2.0 * pow (1 + 4 * beta2, -d2) + 2.0 * pow (gamma, -d) * (1.0 + 2 * d * beta4 / gamma2 + 3 * d * (d + 2) * beta8 / (4 * gamma4)) - 4.0 * pow (delta, -d2) * (1.0 + 3 * d * beta4 / (2 * delta) + d * (d + 2) * beta8 / (2 * delta2)); double mu2 = mu * mu; double prob = NUMundefined, tnb = NUMundefined, lnmu = NUMundefined, lnvar = NUMundefined; try { SSCP_expandLowerCholesky (cov); } catch (MelderError) { tnb = 4 * nd; } double djk, djj, sumjk = 0, sumj = 0; double b1 = beta2 / 2, b2 = b1 / (1.0 + beta2); /* Heinze & Wagner (1997), page 3 We use d[j][k] = ||Y[j]-Y[k]||^2 = (Y[j]-Y[k])'S^(-1)(Y[j]-Y[k]) So d[j][k]= d[k][j] and d[j][j] = 0 */ for (long j = 1; j <= n; j++) { double wj = p[j][nocp1] > 0 ? mixingP * p[j][im] / p[j][nocp1] : 0; for (long k = 1; k < j; k++) { djk = NUMmahalanobisDistance_chi (cov -> lowerCholesky, thy data[j], thy data[k], d, d); double w = p[k][nocp1] > 0 ? wj * mixingP * p[k][im] / p[k][nocp1] : 0; sumjk += 2 * w * exp (-b1 * djk); // factor 2 because d[j][k] == d[k][j] } sumjk += wj * wj; // for k == j. Is this ok now for probability weighing ???? djj = NUMmahalanobisDistance_chi (cov -> lowerCholesky, thy data[j], cov -> centroid, d, d); sumj += wj * exp (-b2 * djj); } tnb = (1.0 / nd) * sumjk - 2.0 * pow (1.0 + beta2, - d2) * sumj + nd * pow (gamma, - d2); // n * his data[im][ilnmu] = lnmu = 0.5 * log (mu2 * mu2 / (mu2 + var)); //log (sqrt (mu2 * mu2 /(mu2 + var))); his data[im][ilnvar] = lnvar = sqrt (log ( (mu2 + var) / mu2)); his data[im][iprob] = prob = NUMlogNormalQ (tnb, lnmu, lnvar); his data[im][ih] = NUMsqrt1_2 / beta; his data[im][id] = d; his data[im][itnb] = tnb; } return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal for BHEP not created."); } } /* End of file GaussianMixture.cpp 1555*/ sources_5316/dwtools/Eigen_and_Matrix.h0000644000176700017670000000265711603620563017000 0ustar paulpaul#ifndef _Eigen_and_Matrix_h_ #define _Eigen_and_Matrix_h_ /* Eigen_and_Matrix.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020327 djmw 20020813 GPL header djmw 20110307 Latest modification */ #ifndef _Eigen_h_ #include "Eigen.h" #endif #ifndef _Matrix_h_ #include "Matrix.h" #endif #ifdef __cplusplus extern "C" { #endif Matrix Eigen_and_Matrix_project (I, thou, long numberOfComponents); /* Purpose: project the columns of the matrix (thou) on the eigenspace (me). */ void Eigen_and_Matrix_project_into (I, thou, Any void_pointer_to_him); /* Purpose: project the columns of the Matrix (thou) on the eigenspace (me). Result in existing Matrix (him). */ #ifdef __cplusplus } #endif #endif /* _Eigen_and_Matrix_h_ */ sources_5316/dwtools/HMM.h0000644000176700017670000001460611665133143014222 0ustar paulpaul#ifndef _HMM_h_ #define _HMM_h_ /* HMM.h * * Copyright (C) 2010-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Strings_extensions.h" #include "TableOfReal.h" #include "Collection.h" #include "GaussianMixture.h" #include "SSCP.h" #include "Index.h" #include "HMM_def.h" oo_CLASS_CREATE (HMM_State, Data); oo_CLASS_CREATE (HMM_Observation, Data); oo_CLASS_CREATE (HMM_Viterbi, Data); oo_CLASS_CREATE (HMM, Data); Thing_define (HMM_BaumWelch, Data) { // new data: public: long capacity; long numberOfTimes; long totalNumberOfSequences; long numberOfStates; long numberOfSymbols; double lnProb; double minProb; double **alpha; double **beta; double *scale; double **gamma; double ***xi; double **aij_num, **aij_denom; double **bik_num, **bik_denom; // overridden methods: virtual void v_destroy (); }; Thing_define (HMM_StateSequence, Strings) { }; Thing_define (HMM_ObservationSequence, Table) { }; // First column is always a symbol, if only 1 column then symbols only Thing_define (HMM_ObservationSequences, Collection) { }; HMM_ObservationSequence HMM_ObservationSequence_create (long numberOfItems, long dataLength); void HMM_ObservationSequence_removeObservation (HMM_ObservationSequence me, long index); Strings HMM_ObservationSequence_to_Strings (HMM_ObservationSequence me); HMM_ObservationSequence Strings_to_HMM_ObservationSequence (Strings me); StringsIndex HMM_ObservationSequence_to_StringsIndex (HMM_ObservationSequence me); StringsIndex HMM_and_HMM_ObservationSequence_to_StringsIndex (HMM me, HMM_ObservationSequence thee); TableOfReal HMM_ObservationSequence_to_TableOfReal_transitions (HMM_ObservationSequence me, int probabilities); TableOfReal HMM_and_HMM_ObservationSequence_to_TableOfReal_transitions (HMM me, HMM_ObservationSequence thee, int probabilities); HMM_ObservationSequences HMM_ObservationSequences_create (); long HMM_ObservationSequence_getNumberOfObservations (HMM_ObservationSequence me); long HMM_ObservationSequences_getLongestSequence (HMM_ObservationSequences me); TableOfReal HMM_StateSequence_to_TableOfReal_transitions (HMM_StateSequence me); TableOfReal HMM_and_HMM_StateSequence_to_TableOfReal_transitions (HMM me, HMM_StateSequence thee, int probabilities); HMM_StateSequence HMM_StateSequence_create (long numberOfItems); Strings HMM_StateSequence_to_Strings (HMM_StateSequence me); void HMM_State_setLabel (HMM_State me, wchar_t *label); HMM HMM_create (int leftToRight, long numberOfStates, long numberOfObservationSymbols); HMM HMM_createSimple (int leftToRight, const wchar_t *states_string, const wchar_t *symbols_string); HMM HMM_createContinuousModel (int leftToRight, long numberOfStates, long numberOfObservationSymbols, long numberOfMixtureComponentsPerSymbol, long componentDimension, long componentStorage); HMM HMM_createFullContinuousModel (int leftToRight, long numberOfStates, long numberOfObservationSymbols, long numberOfFeatureStreams, long *dimensionOfStream, long *numberOfGaussiansforStream); HMM HMM_createFromHMM_ObservationSequence (HMM_ObservationSequence me, long numberOfStates, int leftToRight); void HMM_draw (HMM me, Graphics g, int garnish); void HMM_drawBackwardProbabilitiesIllustration (Graphics g, bool garnish); void HMM_drawForwardProbabilitiesIllustration (Graphics g, bool garnish); void HMM_drawForwardAndBackwardProbabilitiesIllustration (Graphics g, bool garnish); void HMM_addObservation (HMM me, thou); void HMM_addState (HMM me, thou); void HMM_setDefaultStates (HMM me); void HMM_setDefaultObservations (HMM me); void HMM_setDefaultTransitionProbs (HMM me); void HMM_setDefaultStartProbs (HMM me); void HMM_setDefaultEmissionProbs (HMM me); void HMM_setDefaultMixingProbabilities (HMM me); void HMM_unExpandPCA (HMM me); /* Unexpand all the PCA's in the gaussian mixtures */ /* Set the probabilities. A probability zero value indicates that this p cannot be changed during training/learning. */ void HMM_setTransitionProbabilities (HMM me, long state_number, wchar_t *state_probs); void HMM_setEmissionProbabilities (HMM me, long state_number, wchar_t *emission_probs); void HMM_setStartProbabilities (HMM me, wchar_t *probs); double HMM_getProbabilityAtTimeBeingInState (HMM me, long itime, long istate); double HMM_getProbabilityAtTimeBeingInStateEmittingSymbol (HMM me, long itime, long istate, long isymbol); double HMM_getExpectedValueOfDurationInState (HMM me, long istate); double HMM_getProbabilityOfStayingInState (HMM me, long istate, long numberOfTimeUnits); double HMM_and_HMM_getCrossEntropy (HMM me, HMM thee, long observationLength, int symmetric); double HMM_and_HMM_and_HMM_ObservationSequence_getCrossEntropy (HMM me, HMM thee, HMM_ObservationSequence him); TableOfReal HMM_extractTransitionProbabilities (HMM me); TableOfReal HMM_extractEmissionProbabilities (HMM me); /* HMM & HMM_ObservationSequence ****/ HMM_ObservationSequence HMM_to_HMM_ObservationSequence (HMM me, long initialState, long numberOfItems); HMM_StateSequence HMM_and_HMM_ObservationSequence_to_HMM_StateSequence (HMM me, HMM_ObservationSequence thee); double HMM_and_HMM_StateSequence_getProbability (HMM me, HMM_StateSequence thee); void HMM_and_HMM_ObservationSequences_learn (HMM me, HMM_ObservationSequences thee, double delta_lnp, double minProb); void HMM_and_HMM_StateSequence_drawTrellis (HMM me, HMM_StateSequence thee, Graphics g, int connect, int garnish); double HMM_and_HMM_ObservationSequence_getProbability (HMM me, HMM_ObservationSequence thee); double HMM_and_HMM_ObservationSequence_getCrossEntropy (HMM me, HMM_ObservationSequence thee); double HMM_and_HMM_ObservationSequence_getPerplexity (HMM me, HMM_ObservationSequence thee); // somewhere else void MelderInfo_lnp (double logp); TableOfReal Strings_to_TableOfReal_transitions (Strings me, int probabilities); #endif /* _HMM_h_ */ sources_5316/dwtools/Sampled2.cpp0000644000176700017670000001241511627251253015600 0ustar paulpaul/* Sampled2.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sampled2.h" #include "NUM2.h" #include "oo_DESTROY.h" #include "Sampled2_def.h" #include "oo_COPY.h" #include "Sampled2_def.h" #include "oo_EQUAL.h" #include "Sampled2_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Sampled2_def.h" #include "oo_WRITE_TEXT.h" #include "Sampled2_def.h" #include "oo_WRITE_BINARY.h" #include "Sampled2_def.h" #include "oo_READ_BINARY.h" #include "Sampled2_def.h" #include "oo_DESCRIPTION.h" #include "Sampled2_def.h" Thing_implement (Sampled2, Sampled, 0); void structSampled2 :: v_readText (MelderReadText text) { xmin = texgetr8 (text); xmax = texgetr8 (text); nx = texgeti4 (text); dx = texgetr8 (text); x1 = texgetr8 (text); ymin = texgetr8 (text); ymax = texgetr8 (text); ny = texgeti4 (text); dy = texgetr8 (text); y1 = texgetr8 (text); if (xmin > xmax || ymin > ymax) { Melder_throw ("xmax should be greater than xmax and ymax should be greater than ymin."); } if (nx < 1 || ny < 1) { Melder_throw ("nx and ny should be at least 1."); } if (dx <= 0 || dy <= 0) { Melder_throw ("dx and dy should be positive."); } } void Sampled2_init (I, double xmin, double xmax, long nx, double dx, double x1, double ymin, double ymax, long ny, double dy, double y1) { iam (Sampled2); my xmin = xmin; my xmax = xmax; my nx = nx; my dx = dx; my x1 = x1; my ymin = ymin; my ymax = ymax; my ny = ny; my dy = dy; my y1 = y1; } double Sampled2_columnToX (I, double column) { iam (Sampled2); return my x1 + (column - 1) * my dx; } double Sampled2_rowToY (I, double row) { iam (Sampled2); return my y1 + (row - 1) * my dy; } double Sampled2_xToColumn (I, double x) { iam (Sampled2); return (x - my x1) / my dx + 1; } long Sampled2_xToLowColumn (I, double x) { iam (Sampled2); return (long) floor (Sampled2_xToColumn (me, x)); } long Sampled2_xToHighColumn (I, double x) { iam (Sampled2); return (long) ceil (Sampled2_xToColumn (me, x)); } long Sampled2_xToNearestColumn (I, double x) { iam (Sampled2); return (long) floor (Sampled2_xToColumn (me, x) + 0.5); } double Sampled2_yToRow (I, double y) { iam (Sampled2); return (y - my y1) / my dy + 1; } long Sampled2_yToLowRow (I, double y) { iam (Sampled2); return (long) floor (Sampled2_yToRow (me, y)); } long Sampled2_yToHighRow (I, double y) { iam (Sampled2); return (long) ceil (Sampled2_yToRow (me, y)); } long Sampled2_yToNearestRow (I, double y) { iam (Sampled2); return (long) floor (Sampled2_yToRow (me, y) + 0.5); } long Sampled2_getWindowSamplesX (I, double xmin, double xmax, long *ixmin, long *ixmax) { iam (Sampled2); *ixmin = 1 + (long) ceil ( (xmin - my x1) / my dx); *ixmax = 1 + (long) floor ( (xmax - my x1) / my dx); if (*ixmin < 1) { *ixmin = 1; } if (*ixmax > my nx) { *ixmax = my nx; } if (*ixmin > *ixmax) { return 0; } return *ixmax - *ixmin + 1; } long Sampled2_getWindowSamplesY (I, double ymin, double ymax, long *iymin, long *iymax) { iam (Sampled2); *iymin = 1 + (long) ceil ( (ymin - my y1) / my dy); *iymax = 1 + (long) floor ( (ymax - my y1) / my dy); if (*iymin < 1) { *iymin = 1; } if (*iymax > my ny) { *iymax = my ny; } if (*iymin > *iymax) { return 0; } return *iymax - *iymin + 1; } long Sampled2_getWindowExtrema_d (I, double **z, long ixmin, long ixmax, long iymin, long iymax, double *minimum, double *maximum) { iam (Sampled2); if (ixmin == 0) { ixmin = 1; } if (ixmax == 0) { ixmax = my nx; } if (iymin == 0) { iymin = 1; } if (iymax == 0) { iymax = my ny; } if (ixmin > ixmax || iymin > iymax) { return 0; } *minimum = *maximum = z[iymin][ixmin]; for (long iy = iymin; iy <= iymax; iy ++) for (long ix = ixmin; ix <= ixmax; ix ++) { if (z[iy][ix] < *minimum) { *minimum = z[iy][ix]; } if (z[iy][ix] > *maximum) { *maximum = z[iy][ix]; } } return (ixmax - ixmin + 1) * (iymax - iymin + 1); } long Sampled2_getWindowExtrema_f (I, float **z, long ixmin, long ixmax, long iymin, long iymax, double *minimum, double *maximum) { iam (Sampled2); if (ixmin == 0) { ixmin = 1; } if (ixmax == 0) { ixmax = my nx; } if (iymin == 0) { iymin = 1; } if (iymax == 0) { iymax = my ny; } if (ixmin > ixmax || iymin > iymax) { return 0; } *minimum = *maximum = z[iymin] [ixmin]; for (long iy = iymin; iy <= iymax; iy ++) for (long ix = ixmin; ix <= ixmax; ix ++) { if (z[iy][ix] < *minimum) { *minimum = z[iy][ix]; } if (z[iy][ix] > *maximum) { *maximum = z[iy][ix]; } } return (ixmax - ixmin + 1) * (iymax - iymin + 1); } /* End of file Sampled2.cpp */ sources_5316/dwtools/Eigen_and_TableOfReal.h0000644000176700017670000000327311603621037017644 0ustar paulpaul#ifndef _Eigen_and_TableOfReal_h_ #define _Eigen_and_TableOfReal_h_ /* Eigen_and_TableOfReal.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020327 Initial version djmw 20020813 GPL header djmw 20110307 Latest modification */ #ifndef _Eigen_h_ #include "Eigen.h" #endif #ifndef _TableOfReal_h_ #include "TableOfReal.h" #endif #ifdef __cplusplus extern "C" { #endif TableOfReal Eigen_and_TableOfReal_project (I, thou, long from, long numberOfComponents); /* Purpose: project the rows of the TableOfReal (thee) starting at index 'from' on the eigenspace (me). */ void Eigen_and_TableOfReal_project_into (I, thou, long thee_from, long thee_to, Any void_pointer_to_him, long his_from, long his_to); /* Purpose: project the rows of the TableOfReal (thee) on the eigenspace (me). Result in existing TableOfReal (him). */ Eigen TablesOfReal_to_Eigen_gsvd (TableOfReal me, TableOfReal thee); /* Solve A'A x -lambda B'B x = 0 */ #ifdef __cplusplus } #endif #endif /* _Eigen_and_TableOfReal_h_ */ sources_5316/dwtools/PCA.h0000644000176700017670000000421211752706064014201 0ustar paulpaul#ifndef _PCA_h_ #define _PCA_h_ /* PCA.h * * Principal Component Analysis * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110306 Latest modification. */ #include "TableOfReal.h" #include "Configuration.h" #include "Eigen.h" #include "PCA_def.h" oo_CLASS_CREATE (PCA, Eigen); PCA PCA_create (long numberOfComponents, long dimension); void PCA_setNumberOfObservations (PCA me, long numberOfObservations); long PCA_getNumberOfObservations (PCA me); PCA TableOfReal_to_PCA (I); /* Calculate PCA of M'M */ void PCA_getEqualityOfEigenvalues (PCA me, long from, long to, int conservative, double *probability, double *chisq, long *ndf); /* Morrison, Multivariate statistical methods, page 336 */ Configuration PCA_and_TableOfReal_to_Configuration (PCA me, thou, long numberOfDimensions); TableOfReal PCA_and_TableOfReal_to_TableOfReal_zscores (PCA me, TableOfReal thee, long numberOfDimensions); double PCA_and_TableOfReal_getFractionVariance (PCA me, thou, long from, long to); /* Get fraction variance of the table projected in the pca-space. Shorthand for projecting the Covariance of the TableOfReal on the PCA-space and quering the projected Covariance for 'fraction variance'. */ TableOfReal PCA_and_Configuration_to_TableOfReal_reconstruct (PCA me, thou); /* Reconstruct the original TableOfReal from the PCA and the Configuration */ TableOfReal PCA_to_TableOfReal_reconstruct1 (PCA me, wchar_t *numstring); #endif /* _PCA_h_ */ sources_5316/dwtools/CC.cpp0000644000176700017670000001314411747444504014424 0ustar paulpaul/* CC.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20011016 removed some causes for compiler warnings djmw 20020315 GPL header djmw 20061212 Changed info to Melder_writeLine format. djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20080122 float -> double djmw 20080513 CC_getValue */ #include "CC.h" #include "NUM2.h" #include "oo_DESTROY.h" #include "CC_def.h" #include "oo_COPY.h" #include "CC_def.h" #include "oo_EQUAL.h" #include "CC_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "CC_def.h" #include "oo_WRITE_TEXT.h" #include "CC_def.h" #include "oo_WRITE_BINARY.h" #include "CC_def.h" #include "oo_READ_TEXT.h" #include "CC_def.h" #include "oo_READ_BINARY.h" #include "CC_def.h" #include "oo_DESCRIPTION.h" #include "CC_def.h" Thing_implement (CC, Sampled, 1); void structCC :: v_info () { structData :: v_info (); MelderInfo_writeLine5 (L"Time domain:", Melder_double (xmin), L" to ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine2 (L"Number of frames: ", Melder_integer (nx)); MelderInfo_writeLine3 (L"Time step: ", Melder_double (dx), L" seconds"); MelderInfo_writeLine3 (L"First frame at: ", Melder_double (x1), L" seconds"); MelderInfo_writeLine2 (L"Number of coefficients: ", Melder_integer (maximumNumberOfCoefficients)); MelderInfo_writeLine3 (L"Minimum frequency: ", Melder_double (fmin), L" Hz"); MelderInfo_writeLine3 (L"Maximum frequency: ", Melder_double (fmax), L" Hz"); } void CC_Frame_init (CC_Frame me, long numberOfCoefficients) { my c = NUMvector (1, numberOfCoefficients); my numberOfCoefficients = numberOfCoefficients; } void CC_init (I, double tmin, double tmax, long nt, double dt, double t1, long maximumNumberOfCoefficients, double fmin, double fmax) { iam (CC); my fmin = fmin; my fmax = fmax; my maximumNumberOfCoefficients = maximumNumberOfCoefficients; Sampled_init (me, tmin, tmax, nt, dt, t1); my frame = NUMvector (1, nt); } Matrix CC_to_Matrix (I) { iam (CC); try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 1, my maximumNumberOfCoefficients, my maximumNumberOfCoefficients, 1, 1); for (long i = 1; i <= my nx; i++) { CC_Frame cf = & my frame[i]; for (long j = 1; j <= cf -> numberOfCoefficients; j++) { thy z[j][i] = cf -> c[j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Matrix."); } } void CC_paint (I, Graphics g, double xmin, double xmax, long cmin, long cmax, double minimum, double maximum, int garnish) { iam (CC); autoMatrix thee = CC_to_Matrix (me); Matrix_paintCells (thee.peek(), g, xmin, xmax, cmin, cmax, minimum, maximum); if (garnish) { Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_textBottom (g, 1, L"Time (s)"); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_textLeft (g, 1, L"Coefficients"); } } void CC_drawC0 (I, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish) { iam (CC); (void) garnish; if (xmin >= xmax) { xmin = my xmin; xmax = my xmax; } long bframe, eframe; (void) Sampled_getWindowSamples (me, xmin, xmax, &bframe, &eframe); autoNUMvector c (bframe, eframe); for (long i = bframe; i <= eframe; i++) { CC_Frame cf = & my frame[i]; c[i] = cf -> c0; } if (ymin >= ymax) { NUMvector_extrema (c.peek(), bframe, eframe, &ymin, &ymax); if (ymax <= ymin) { ymin -= 1.0; ymax += 1.0; } } else { NUMvector_clip (c.peek(), bframe, eframe, ymin, ymax); } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_function (g, c.peek(), bframe, eframe, xmin, xmax); Graphics_unsetInner (g); } void CC_getNumberOfCoefficients_extrema (I, long startframe, long endframe, long *min, long *max) { iam (CC); Melder_assert (startframe <= endframe); if (startframe == 0 && endframe == 0) { startframe = 1; endframe = my nx; } if (startframe < 1) { startframe = 1; } if (endframe > my nx) { endframe = my nx; } *min = my maximumNumberOfCoefficients; *max = 0; for (long i = startframe; i <= endframe; i++) { CC_Frame f = & my frame[i]; long nc = f -> numberOfCoefficients; if (nc < *min) { *min = nc; } else if (nc > *max) { *max = nc; } } } long CC_getMinimumNumberOfCoefficients (I, long startframe, long endframe) { iam (CC); long min, max; CC_getNumberOfCoefficients_extrema (me, startframe, endframe, &min, &max); return min; } long CC_getMaximumNumberOfCoefficients (I, long startframe, long endframe) { iam (CC); long min, max; CC_getNumberOfCoefficients_extrema (me, startframe, endframe, &min, &max); return max; } double CC_getValue (I, double t, long index) { iam (CC); long iframe = Sampled_xToNearestIndex (me, t); if (iframe < 1 || iframe > my nx) { return NUMundefined; } CC_Frame cf = & me -> frame[iframe]; return index > cf -> numberOfCoefficients ? NUMundefined : cf -> c[index]; } /* End of file CC.cpp */ sources_5316/dwtools/manual_MDS.cpp0000644000176700017670000030646011725413201016107 0ustar paulpaul/* manual_MDS.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020422 GPL + removed "C syntax" part of manpage djmw 20030317 Latest modification. djmw 20030825 Spelling corrections. djmw 20040118 Procrustes modifications. djmw 20040214 Removed last link to @praat program@. djmw 20040407 Change Arguments -> Settings. djmw 20040513 Spelling. djmw 20070108 Latest modification. */ #include "ManPagesM.h" #include "MDS.h" static void drawLetterRConfigurationExample (Graphics g) { autoConfiguration me = Configuration_createLetterRExample (1); Graphics_setWindow (g, -6, 4, -7, 5); Configuration_draw (me.peek(), g, 1, 2, -6, 4, -7, 5, 0, 1, L"", 1); } static void drawLetterRConfigurationExample2 (Graphics g) { autoConfiguration me = Configuration_createLetterRExample (2); Configuration_draw (me.peek(), g, 1, 2, -0.8, 1.2, -0.8, 0.7, 0, 1, L"", 1); } static void drawLetterRShepard (Graphics g) { autoDissimilarity d = Dissimilarity_createLetterRExample (32.5); autoConfiguration c = Configuration_createLetterRExample (2); Dissimilarity_Configuration_drawShepardDiagram (d.peek(), c.peek(), g, 0, 200, 0, 2.2, 1, L"+", 1); } static void drawLetterRRegression (Graphics g) { autoDissimilarity d = Dissimilarity_createLetterRExample (32.5); autoConfiguration c = Configuration_createLetterRExample (2); Dissimilarity_Configuration_drawMonotoneRegression (d.peek(), c.peek(), g, MDS_PRIMARY_APPROACH, 0, 200, 0, 2.2, 1, L"+", 1); } static void drawCarrollWishConfigurationExample (Graphics g) { autoConfiguration me = Configuration_createCarrollWishExample (); Graphics_setWindow (g, -2, 2, -2, 2); Configuration_draw (me.peek(), g, 1, 2, -2, 2, -2, 2, 0, 1, L"", 1); } static void drawCarrollWishSalienceExample (Graphics g) { autoSalience me = Salience_createCarrollWishExample (); Salience_draw (me.peek(), g, 1, 2, 1); } static void drawMsplineExample (Graphics g) { drawSplines (g, 0, 1, 0, 10, 1, 3, L"0.3 0.5 0.6", 1); } static void drawIsplineExample (Graphics g) { drawSplines (g, 0, 1, 0, 1.5, 2, 3, L"0.3 0.5 0.6", 1); } void manual_MDS_init (ManPages me); void manual_MDS_init (ManPages me) { MAN_BEGIN (L"CANDECOMP", L"djmw", 19971201) ENTRY (L"An algorithm to solve the INDSCAL problem.") NORMAL (L"In the analysis of the INDSCAL three-way data matrix (%numberOfPoints " "\\xx %numberOfDimensions \\xx %numberOfSources) we seek to minimize the " "function: ") FORMULA (L"%f(%X, %W__1_,..., %W__%numberOfSources_) = " "\\su__%i=1..%numberOfSources_ | %S__%i_ \\-- %X%W__%i_%X\\'p |^2") NORMAL (L"where %S__%i_ is a known symmetric %numberOfPoints \\xx %numberOfPoints " "matrix with scalar products of distances for source %i, %X is the unknown configuration " "%numberOfPoints \\xx %numberOfDimensions matrix, %X\\'p its transpose, and, %W__%i_ is " "the diagonal %numberOfDimensions \\xx %numberOfDimensions weight matrix for source %i. The function " "above has no analytical solution for %X and the %W__%i_. It can be solved, however, " "by an iterative procedure which Carroll & Chang have christened CANDECOMP " "(CANonical DECOMPosition). This method minimizes, instead of the function " "given above, the following function:") LIST_ITEM (L"%g(%X, %Y, %W__1_,..., %W__%numberOfSources_) = \\su__%i=1..%numberOfSources_ " "| %S__%i_ \\-- %X%W__%i_%Y\\'p |^2") NORMAL (L"where %X and %Y are both %numberOfPoints \\xx %numberOfDimensions configuration matrices.") NORMAL (L"The algorithm proceeds as follows:") NORMAL (L"1. Initialize the $W matrices and the configuration matrix %X. This can for example be " "done according to a procedure given in @@Young, Takane & Lewyckyj (1978)@.") NORMAL (L"2. An alternating least squares minimization process is started as described that " "sequentially updates %Y, %X an %W (@@Carroll & Chang (1970)@):") LIST_ITEM (L"2.1. Solve for a new %Y given %X and the %W__%i_") LIST_ITEM (L"2.2. Solve for a new %X given the %W__%i_ and the new %Y.") LIST_ITEM (L"2.3. Solve for the %W__%i_ given the new %X and %Y.") NORMAL (L"Evaluate the goodness-of-fit criterion and either repeat the minimization sequence " "(2.1\\--2.3) or continue.") NORMAL (L"3. Done: make %Y equal to %X and solve a last time for the %W__%i_.") NORMAL (L"Note: during the minimization the following constraints are effective:") LIST_ITEM (L"The configuration must be centered.") LIST_ITEM (L"The sum of squared coordinates in the configuration space is one for " "each dimension, i.e., the configuration always has unit variance in each dimension.") MAN_END MAN_BEGIN (L"Configuration", L"djmw", 20101102) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Configuration represents the positions of a number " "of labelled points in a multidimensional space.") ENTRY (L"How to create a Configuration") NORMAL (L"From the New menu:") LIST_ITEM (L" \\bu @@Create Configuration...") NORMAL (L"By multidimensional scaling:") LIST_ITEM (L" \\bu @@Dissimilarity: To Configuration (monotone mds)...") LIST_ITEM (L" \\bu @@Dissimilarity: To Configuration (i-spline mds)...") LIST_ITEM (L" \\bu @@Dissimilarity: To Configuration (interval mds)...") LIST_ITEM (L" \\bu @@Dissimilarity: To Configuration (ratio mds)...") LIST_ITEM (L" \\bu @@Dissimilarity: To Configuration (absolute mds)...") NORMAL (L"By multidimensional scaling with weights (@@Dissimilarity & Weight: To Configuration...@):") LIST_ITEM (L" \\bu ##Dissimilarity & Weight: To Configuration (monotone mds)...") LIST_ITEM (L" \\bu ##Dissimilarity & Weight: To Configuration (i-spline mds)...") LIST_ITEM (L" \\bu ##Dissimilarity & Weight: To Configuration (interval mds)...") LIST_ITEM (L" \\bu ##Dissimilarity & Weight: To Configuration (ratio mds)...") LIST_ITEM (L" \\bu ##Dissimilarity & Weight: To Configuration (absolute mds)...") NORMAL (L"By multidimensional scaling with a start Configuration:") LIST_ITEM (L" \\bu @@Dissimilarity & Configuration: To Configuration (monotone mds)...") LIST_ITEM (L" \\bu @@Dissimilarity & Configuration: To Configuration (i-spline mds)...") LIST_ITEM (L" \\bu @@Dissimilarity & Configuration: To Configuration (interval mds)...") LIST_ITEM (L" \\bu @@Dissimilarity & Configuration: To Configuration (ratio mds)...") LIST_ITEM (L" \\bu @@Dissimilarity & Configuration: To Configuration (absolute mds)...") NORMAL (L"By transforming an existing Configuration:") LIST_ITEM (L" \\bu @@Configuration: To Configuration (varimax)...") LIST_ITEM (L" \\bu @@Configuration & AffineTransform: To Configuration") LIST_ITEM (L" \\bu @@Configuration & Procrustes: To Configuration") NORMAL (L"From @@Principal component analysis@:") LIST_ITEM (L" \\bu @@TableOfReal: To Configuration (pca)...") LIST_ITEM (L" \\bu @@PCA & TableOfReal: To Configuration...") NORMAL (L"From @@Discriminant analysis@:") LIST_ITEM (L"@@TableOfReal: To Configuration (lda)...") LIST_ITEM (L" \\bu @@Discriminant & TableOfReal: To Configuration...") ENTRY (L"How to draw a Configuration") LIST_ITEM (L"\\bu @@Configuration: Draw...") LIST_ITEM (L"\\bu ##Configuration: Draw as numbers...") LIST_ITEM (L"\\bu ##Configuration: Draw as squares...") ENTRY (L"How to modify a Configuration") LIST_ITEM (L"\\bu @@Configuration: Randomize") LIST_ITEM (L"\\bu @@Configuration: Rotate (pc)@ (to principal directions)") LIST_ITEM (L"\\bu @@Configuration: Rotate...@ (in a plane around the origin)") LIST_ITEM (L"\\bu @@Configuration: Invert dimension...") LIST_ITEM (L"\\bu @@Configuration: Normalize...") ENTRY (L"Inside a Configuration") NORMAL (L"With @Inspect you will see the following attributes:") TAG (L"%numberOfRows") DEFINITION (L"the number of points (%numberOfPoints\\>_1).") TAG (L"%numberOfColumns") DEFINITION (L"the dimension of the space (%numberOfDimensions\\>_1).") TAG (L"%rowLabels") DEFINITION (L"the names associated with the points.") TAG (L"%columnLabels") DEFINITION (L"the names for the dimensions.") TAG (L"%data [1..%numberOfPoints][1..%numberOfDimensions]") DEFINITION (L"the coordinates of the points.") TAG (L"%metric") DEFINITION (L"determines the way distances between points are measured. In general " "the distance between points #x__%i_ and #x__%j_ is:") FORMULA (L"%d__%ij_ = " "(\\su__%k=1..%numberOfDimensions_ %w__%k_ |%x__%ik_ \\-- " "%x__%jk_|^^%metric^)^^1/%metric^") DEFINITION (L"For Euclidean distances %metric is 2.") TAG (L"%w [1..%numberOfDimensions]") DEFINITION (L"weight given to each dimension in the distance calculation.") MAN_END MAN_BEGIN (L"Configuration: Centralize", L"djmw", 19980413) INTRO (L"Makes the centre of the selected @Configuration equal to the origin.") NORMAL (L"") MAN_END MAN_BEGIN (L"Configuration: Draw...", L"djmw", 20040407) INTRO (L"Draws a projection of the selected @Configuration on a coordinate plane.") ENTRY (L"Settings") TAG (L"##X-coordinate#, ##Y-coordinate#") DEFINITION (L"control the dimensions that will show in the plot.") TAG (L"##xmin#, ##xmax#; ##ymin#, ##ymax#") DEFINITION (L"range for horizontal and vertical axes, respectively.") TAG (L"##Garnish") DEFINITION (L"when on, draws a bounding box with decoration.") MAN_END MAN_BEGIN (L"Configuration: Invert dimension...", L"djmw", 20040407) INTRO (L"Inverts one dimension of a @Configuration.") NORMAL (L"Setting") TAG (L"##Dimension") DEFINITION (L"the dimensions that has to be inverted.") ENTRY (L"Behaviour") NORMAL (L"For all points %i=1..%numberOfPoints: if %j == %dimension then %x__%ij_ " "= \\--%x__%ij_.") MAN_END MAN_BEGIN (L"Configuration: Normalize...", L"djmw", 20040407) INTRO (L"Normalizes the selected @Configuration.") ENTRY (L"Settings") TAG (L"##Sum of squares# (standard value: 0.0)") DEFINITION (L"The desired value for the variance.") TAG (L"##Each dimension separately") DEFINITION (L"When on, the sum of squares in each dimension (column) will be scaled to %sumOfSquares " "When off, the sum of squares of all the matrix elements will equal %sumOfSquares.") NORMAL (L"With the default value (0.0) for %sumOfSquares, and %eachDimensionSeparately chosen, " "an INDSCAL-like normalization is applied: the sum of squares for each column is scaled to " "equal 1.0. When %eachDimensionSeparately is off, a Kruskal-like normalization is applied: " "the sum of squares of the whole matrix is scaled equal to %numberOfRows.") ENTRY (L"Behaviour") NORMAL (L"Before the normalization will be applied, however, we first translate the centre of the " "configuration to the origin by subtracting the mean for each dimension. " "The sum of squares than equals variance.") MAN_END MAN_BEGIN (L"Configuration: Randomize", L"djmw", 19971201) INTRO (L"Changes all coordinates of the points #%x__%i_ in the @Configuration according to:") LIST_ITEM (L"%x__%ij_ = randomUniform (-1, 1)") MAN_END MAN_BEGIN (L"Configuration: Rotate...", L"djmw", 20100303) INTRO (L"Rotates the @Configuration in a plane around the origin.") NORMAL (L"Settings") TAG (L"##Dimension 1#, ##Dimension 2#") DEFINITION (L"the dimensions that span the plane. The order of dimension 1 and dimension 2 is not important: " "the lowest number always determines the first dimension.") TAG (L"##Angle") DEFINITION (L"the counter-clockwise rotation angle in degrees.") MAN_END MAN_BEGIN (L"Configuration: Rotate (pc)", L"djmw", 19971201) INTRO (L"Rotates the @Configuration to principal directions. The principal directions " "correspond to the principal components.") MAN_END MAN_BEGIN (L"Configuration: To Configuration (procrustes)", L"djmw", 19971219) INTRO (L"A command that transforms the second selected @Configuration object " "to match the first selected Configuration object as closely as possible." "This problem of fitting one configuration (testee) to another (target) " "as closely as possible is called the Procrustes problem. We use a " "special @@Procrustes transform@ algorithm that does not " "mutilate or distort the testee configuration.") NORMAL (L"Both Configuration objects must have the same dimensions.") MAN_END MAN_BEGIN (L"Configuration: To Configuration (varimax)...", L"djmw", 20040407) INTRO (L"A command that rotates the selected @Configuration object to a new " "Configuration object whose coordinates have maximum %squared variance. ") ENTRY (L"Settings") TAG (L"##Normalize rows") DEFINITION (L"when selected, the distances of all points to the origin will " "be made equal before iteration starts. We remember these scale factors " "and restore the original distances after the iteration process has " "stopped.") TAG (L"##Quartimax") DEFINITION (L"when selected, the sum of fourth powers, normalized or raw, " "will be maximized. ") TAG (L"##Maximum number of iterations") DEFINITION (L"sets a limit to the number of iterations. One iteration consists " "of %numberOfDimensions\\.c (%numberOfDimensions\\--1)/2 planar rotations " "of all pairs of dimensions.") TAG (L"##Tolerance") DEFINITION (L"also determines when the iteration stops. This happens if " "|%v__%i_\\--%v__%i+1_| < %tolerance \\.c %v__%i_, where %v__%i_ is the " "squared variance for the %i^^th^ iteration.") NORMAL (L"The iteration process stops when either the %%maximum number of " "iterations% is reached or the %tolerance criterion is met, which ever " "one is first.") ENTRY (L"Algorithm") NORMAL (L"The Varimax rotation procedure was first proposed by @@Kaiser " "(1958)@. Given a %numberOfPoints \\xx %numberOfDimensions configuration " "#A, the procedure tries to find an orthonormal rotation matrix #T such " "that the sum of variances of the columns of #B*#B is a maximum, where #B " "= #A#T and * is the element wise (Hadamard) product of matrices. A direct " "solution for the optimal #T is not available, except for the case when " "%numberOfDimensions equals two. Kaiser suggested an iterative " "algorithm based on planar rotations, i.e., alternate rotations of all " "pairs of columns of #A.") NORMAL (L"However, this procedure is not without problems: the varimax function " "may have stationary points that are not even local maxima. We have " "incorporated an algorithm of @@Ten Berge (1995)@ " "that prevents this unpleasant situation from happening.") MAN_END MAN_BEGIN (L"Configuration: To Distance", L"djmw", 19971207) INTRO (L"A command that computes a @Distance object for each selected " "@Configuration.") ENTRY (L"Algorithm") NORMAL (L"The distance %d__%ij_ between objects %i and %j is calculated as:") FORMULA (L"%d__%ij_ = %d__%ji_ = (\\su__%k=1..%numberOfDimensions_ |%x__%ik_ " "\\-- %x__%jk_|^2)^^1/2^") MAN_END MAN_BEGIN (L"Configuration: To Similarity (cc)", L"djmw", 19980130) INTRO (L"A command that create one @Similarity object from the selected " "@Configuration objects.") NORMAL (L"In the Similarity object entry %s__%ij_ equals the @@congruence " "coefficient@ for the %i-th and %j-th selected Configuration object.") NORMAL (L"All Configuration objects must have the same number of points and " "the same dimensions.") MAN_END MAN_BEGIN (L"Configuration & AffineTransform: To Configuration", L"djmw", 20011008) INTRO (L"A command that transforms the selected @Configuration to a new " "Configuration object according to the specifications in the selected " "@AffineTransform object.") MAN_END MAN_BEGIN (L"Configuration & Procrustes: To Configuration", L"djmw", 20011008) INTRO (L"A command that transforms the selected @Configuration to a new " "Configuration object according to the specifications in the selected " "@Procrustes object.") MAN_END MAN_BEGIN (L"Configurations: To AffineTransform (congruence)...", L"djmw", 20040407) INTRO (L"A command that creates an @AffineTransform object from two selected " "@Configuration objects.") NORMAL (L"We calculate the affine transform that transforms the second " "selected Configuration object to match the first selected Configuration " "object as closely as possible. " "The degree of proportionality is the congruence between corresponding " "dimensions.") ENTRY (L"Settings") TAG (L"##Maximum number of iterations") DEFINITION (L"sets a limit to the number of iterations.") TAG (L"##Tolerance") DEFINITION (L"also determines when the iteration stops. This happens if " "|%f(#T__%i_)\\--%f(#T__%i+1_)| < %tolerance \\.c %f(#T__%i_), where " "%f(#T__%i_) is the sum of the congruences for the %i^^th^ " "iteration (see below).") NORMAL (L"The iteration process stops when either the %%maximum number of " "iterations% is reached or the %tolerance criterion is met, which ever " "one is first.") ENTRY (L"Algorithm") NORMAL (L"Sometimes the criterion used in a @@Procrustes transform@ is too " "restrictive for comparing two configurations. This criterion is only " "zero when the positions in the rotated configuration (#A#T) equal the " "positions in the other configuration (#B). @@Brokken (1983)@ proposed an " "algorithm to maximize instead the sum of congruences between " "corresponding dimensions of #AT and #B. " "Specifically he proposed to maximize") FORMULA (L"%f(#T) = \\su__%i=1..%numberOfDimensions_ #t\\'p__%i_#A\\'p#b__%i_ /" " ((#t\\'p__%i_#A\\'p#A#t__%i_)^^1/2^(#b\\'p__%i_#b__%i_)^^1/2^),") NORMAL (L"where #t\\'p__%i_ and #b\\'p__%i_ are the %i^^th^ column of #T and " "#B, respectively. A direct solution for #T is not available, it can only " "be obtained by an iterative procedure. The implemented algorithm is from " "@@Kiers & Groenen (1996)@ and shows excellent convergence properties.") MAN_END MAN_BEGIN (L"Configuration & Configuration: To Procrustes...", L"djmw", 20011008) INTRO (L"A command that creates a @Procrustes object from two selected " "@Configuration objects.") ENTRY (L"Setting") TAG (L"##Orthogonal transform") DEFINITION (L"determines whether or not a translation and a scaling are allowed in the transform.") NORMAL (L"We calculate the @@Procrustes transform@ that transforms the second " "selected Configuration object to match the first selected Configuration " "object as closely as possible.") MAN_END MAN_BEGIN (L"Confusion: To Dissimilarity...", L"djmw", 20040407) INTRO (L"A command that creates a @Dissimilarity from every selected " "@Confusion.") ENTRY (L"Settings") TAG (L"##Normalize") DEFINITION (L"when on, normalize rows by dividing each row element by the row " "sum. In this way you correct for unequal stimulus numbers.") TAG (L"##No symmetrization#, #Average, #Houtgast") DEFINITION (L"determine the symmetrization procedure. See " "@@Confusion: To Similarity...") TAG (L"##Maximum dissimilarity") DEFINITION (L"determines the maximum dissimilarity possible. When the default " "value, 0.0, is chosen, %maximumDissimilarity " "is calculated as the maximum element in the Similarity object.") ENTRY (L"Algorithm") NORMAL (L"We first transform the Confusion to a Similarity. See " "@@Confusion: To Similarity...") NORMAL (L"To obtain dissimilarities from similarities we \"reverse\" the " "latter:") FORMULA (L"%%dissimilarity__%ij_ = %maximumDissimilarity \\-- %similarity__%ij_") MAN_END MAN_BEGIN (L"Confusion: To Dissimilarity (pdf)...", L"djmw", 20040407) INTRO (L"A command that creates a @Dissimilarity from every selected " "@Confusion.") ENTRY (L"Settings") TAG (L"##Symmetrize first") DEFINITION (L"when on, the confusion matrix is symmetrized before we calculate " "dissimilarities.") TAG (L"##Maximum dissimilarity (units of sigma)") DEFINITION (L"specifies the dissimilarity from confusion matrix elements that " "are zero.") ENTRY (L"Algorithm") TAG (L"1. Normalize rows by dividing each row element by the row sum (optional).") TAG (L"2. Symmetrize the matrix by averaging %f__%ij_ and %f__%ji_.") TAG (L"3. Transformation of the confusion measure which is a sort of " "%similarity measure to the %dissimilarity measure.") NORMAL (L"Similarity and dissimilarity have an inverse relationship: the " "greater the similarity, the smaller the dissimilarity and vice versa. " "Both have a monotonic relationship with distance. " "The most simple way to transform the similarities %f__%ij_ into " "dissimilarities is:") FORMULA (L"%dissimilarity__%ij_ = %maximumSimilarity \\-- %similarity__%ij_") NORMAL (L"For ordinal analyses like Kruskal this transformation is fine because " "only order relations are important in this analysis. However, for " "metrical analyses like INDSCAL this is not optimal. " "In INDSCAL, distance is a linear function of dissimilarity. This means " "that, with the transformation " "above, you ultimately fit an INDSCAL model in which the distance " "between object %i and %j will be linearly related to the confusion " "between %i and %j.") NORMAL (L"For the relation between confusion and dissimilarity, the model " "implemented here, makes the assumption that the amount of confusion " "between objects %i and %j is related to the amount that their " "probability density functions, pdf's, overlap. Because we do not know " "these pdf's we make the assumption that both are normal, have equal " "%sigma and are one-dimensional. The parameter to be determined is the " "distance between the centres of both pdf's. " "According to formula 26.2.23 in @@Abramowitz & Stegun (1970)@, for each " "fraction %f__%ij_, we have to find an %x that solves:") FORMULA (L"%f__%ij_ = 1 / \\Vr(2%\\pi) \\in__%x_^^\\oo^ e^^-%t\\.c%t/2^ %dt") NORMAL (L"This %x will be used as the dissimilarity between %i and %j. The " "relation between %x and %f__%ij_ is monotonic. This means that the " "results for a Kruskal analysis will not change much. For INDSCAL, in " "general, you will note a significantly better fit.") MAN_END MAN_BEGIN (L"Confusion: To Similarity...", L"djmw", 20040407) INTRO (L"A command that creates a @Similarity from every selected @Confusion.") ENTRY (L"Settings") TAG (L"##Normalize") DEFINITION (L"when on, normalize rows by dividing each row element by the row " "sum. In this way you correct for unequal stimulus numbers.") TAG (L"##No symmetrization#, #Average, #Houtgast") DEFINITION (L"determine the symmetrization procedure.") ENTRY (L"Algorithm") NORMAL (L"The %Average procedure averages:") FORMULA (L"%similarity__%ij_= %similarity__%ji_ = (%confusion__%ij_ + " "%confusion__%ji_) / 2") NORMAL (L"The %Houtgast procedure as described in the paper by @@Klein, Plomp " "& Pols (1970)@, expresses similarity between stimuli %i and %j by the " "number of times that stimulus %i and %j have " "resulted in the same response, summated over all response categories.") NORMAL (L"We use the following formula to calculate the %Houtgast " "dissimilarities:") FORMULA (L"%similarity__%ij_ = \\su__%k=1..%numberOfColumns_ min " "(%confusion__%ik_, %confusion__%jk_)") NORMAL (L"which is equivalent to the formula in the Klein et al. paper:") FORMULA (L"%similarity__%ij_ = \\su__%k=1..%numberOfColumns_ (%confusion__%ik_ " "+ %confusion__%jk_ \\-- |%confusion__%ik_ \\-- %confusion__%jk_|)") MAN_END MAN_BEGIN (L"congruence coefficient", L"djmw", 20040407) INTRO (L"The %%congruence coefficient% is a measure of similarity between two " "@@Configuration@s.") NORMAL (L"The congruence coefficient %c(#X, #Y) for the configurations #X and " "#Y is defined as:") FORMULA (L"%c(%X, %Y) = \\su__%i<%j_ %w__%ij_ %d__%ij_(#X) %d__%ij_(#Y) / " "([\\su__%i<%j_ %w__%ij_ %d^2__%ij_(#X)]^^1/2^ [\\su__%i<%j_ %w__%ij_ " "%d^2__%ij_(#Y)]^^1/2^),") NORMAL (L"where %d__%ij_(#X) is the distance between the points %i and %j in " "configuration #X and %w__%ij_ are nonnegative weights (default: %w__%ij_" " = 1).") NORMAL (L"Since distances are nonnegative, the congruence coefficient has a " "value between 0 and 1.") NORMAL (L"The %%congruence coefficient% is a better measure of the similarity " "between configurations than the %%correlation coefficient% of the " "distances. @@Borg & Groenen (1997)@ give a simple example where things " "go wrong with correlation coefficients: two configurations #X and #Y with three points each, have " "distances %d__12_(#X) = 1, %d__13_(#X) = 2, %d__23_(#X) = 3 and " "%d__12_(#Y) = 2, %d__13_(#Y) = 3, %d__23_(#Y) = 4. " "These distances have a correlation coefficient of 1. " "However, in #X the three points lie on a straight line and in #Y the " "points form a triangle. This unwanted situation occurs because " "in the calculation of the correlation coefficient the mean is subtracted " "from the distances and the resulting values are no longer distances " "(they may become negative). In calculating the correlation " "between the distances we should not subtract the mean. " "In fact, the congruence coefficient is exactly this correlation " "coefficient calculated with respect to the origin and " "not with respect to the centroid position (the \"mean\").") NORMAL (L"For further information on how well one number can assess the " "similarity between two configurations see @@Borg & Groenen (1997)@ " "section 19.7.") MAN_END MAN_BEGIN (L"ContingencyTable", L"djmw", 19971216) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"In a two-way contingency table, cell %f__%ij_ contains the frequency " "with which row category %i co-occurs with column category %j. " "Necessarily, all %f__%ij_ \\>_ 0.") ENTRY (L"Commands") NORMAL (L"Creation") LIST_ITEM (L"\\bu ##TableOfReal: To ##ContingencyTable") NORMAL (L"Query") LIST_ITEM (L"\\bu ##ContingencyTable: Get chi squared probability") LIST_ITEM (L"\\bu ##ContingencyTable: Get Cramer's statistic") LIST_ITEM (L"\\bu ##ContingencyTable: Get contingency coefficient") NORMAL (L"Analysis") LIST_ITEM (L"\\bu @@ContingencyTable: To Configuration (ca)...") MAN_END MAN_BEGIN (L"ContingencyTable: To Configuration (ca)...", L"djmw", 20040407) INTRO (L"A command that creates a @Configuration object from the selected " "@ContingencyTable object by means of @@Correspondence analysis@.") ENTRY (L"Settings") TAG (L"##Number of dimensions") DEFINITION (L"The dimensionality of the Configuration.") TAG (L"##Scaling of the final configuration") DEFINITION (L"determines whether row points are in the centre of gravity of " "column points, or, column points are in the centre of gravity of row " "points, or, whether roes and columns are treated symmetrically.") ENTRY (L"Algorithm") NORMAL (L"1. We start with the following transformation of the entries " "%f__%ij_:") FORMULA (L"%h__%ij_ = %f__%ij_ / \\Vr (%f__%i+_%f__+%j_) - \\Vr " "(%f__%i+_%f__+%j_) / %N,") NORMAL (L"where %h__%ij_ is the entry for a cell in the matrix #H with " "transformed data, %f__%i+_ " "is the total count for row %i, %f__+%j_ is the total count for column %j " "and %N is the grand total. " "This can be written in matrix form as:") FORMULA (L"#H = #R^^\\--1/2^#F#C^^\\--1/2^ \\-- #R^^1/2^#uu\\'p#C^^1/2^ / %N,") NORMAL (L"where #R and #C are diagonal matrices with the row and column totals, " "respectively and #u a column vector with all elements equal to 1. ") NORMAL (L"2. Next the singular value decomposition of matrix #H is performed:") FORMULA (L"#H = #K #\\La #L\\'p,") NORMAL (L"where #K\\'p#K = #I, #L\\'p#L = #I, and #\\La is a diagonal matrix " "with singular values.") NORMAL (L"3. Now the row (#X) and column points (#Y) can be determined. " "Three normalizations are possible:") TAG (L"\\bu Scale row points in the centre of gravity of column points") DEFINITION (L"#X = \\Vr%N #R^^\\--1/2^#K#\\La") DEFINITION (L"#Y = \\Vr%N #C^^\\--1/2^#L") TAG (L"\\bu Scale column points in the centre of gravity of row points") DEFINITION (L"#X = \\Vr%N #R^^\\--1/2^#K") DEFINITION (L"#Y = \\Vr%N #C^^\\--1/2^#L#\\La") TAG (L"\\bu Treat row points and column points symmetrically") DEFINITION (L"#X = \\Vr%N #R^^\\--1/2^#K#\\La^^\\--1/2^") DEFINITION (L"#Y = \\Vr%N #C^^\\--1/2^#L\\La^^\\--1/2^") NORMAL (L"For more details see @@Gifi (1990)@, chapter 8.") MAN_END MAN_BEGIN (L"Correspondence analysis", L"djmw", 19971216) INTRO (L"Correspondence analysis provides a method for representing data in " "an Euclidean space so that the results can be visually examined for " "structure. For data in a typical two-way @ContingencyTable both the row " "variables and the column variables are represented in the same space. " "This means that one can examine relations not only among row " "or column variables but also between row and column variables.") NORMAL (L"In correspondence analysis the data matrix is first transformed by " "dividing each cell by the square root of the corresponding row and column " "totals. " "The transformed matrix is then decomposed with singular value " "decomposition resulting in the singular values (which in this case are " "canonical correlations) and a set of row vectors and column vectors. " "Next the row and column vectors are rescaled with the original total " "frequencies to obtain optimal scores. " "These optimal scores are weighted by the square root of the singular " "values and become the coordinates of the points in the @Configuration.") NORMAL (L"Examples can be found in the books by @@Weller & Romney (1990)@ and " "@@Gifi (1990)@.") MAN_END MAN_BEGIN (L"Create Configuration...", L"djmw", 19980413) INTRO (L"A command to create a @Configuration with the specified number of " "points and number of dimensions. The location of the points will be " "determined by the formula (see @@Formulas@ for more " "information about possible formulas).") MAN_END MAN_BEGIN (L"Create INDSCAL Carroll & Wish example...", L"djmw", 19971201) INTRO (L"Creates eight @Dissimilarity objects that bear names \"1\" ... \"8\".") NORMAL (L"These objects contain the interpoint distances for a twodimensional " "3\\xx3 @Configuration of points, labelled A, B, C, ... I. " "All Dissimilarity objects are based on the following underlying configuration.") PICTURE (4.0, 4.0, drawCarrollWishConfigurationExample) NORMAL (L"The eight sources weigh this configuration in the following manner:") PICTURE (4.0, 4.0, drawCarrollWishSalienceExample) NORMAL (L"For each source, the distances were subjected to the transformation: ") FORMULA (L"%dissimilarity__%ij_ = %distance__%ij_ + %noiseRange \\.c #u, ") NORMAL (L"where #u is a uniform random variable between 0 and 1.") NORMAL (L"Now you can do the following for example:") TAG (L"Select all the Dissimilarity objects and choose @@Dissimilarity: To Distance...|" "To Distance...@.") DEFINITION (L"Uncheck scale (add \"additive constant\").") TAG (L"Select all the Distance objects and choose @@Distance: To Configuration (indscal)...|" "To Configuration (indscal)...@.") DEFINITION (L"and an @@INDSCAL analysis@ will be performed. In order to reproduce the saliences, " "you have to uncheck the \"Normalize scalar products\" option.") NORMAL (L"This example was adapted from @@Carroll & Wish (1974)@.") MAN_END MAN_BEGIN (L"Create letter R example...", L"djmw", 19971201) INTRO (L"Creates a @Dissimilarity object that bears the name %R. The " "dissimilarities in this object were chosen to be a monotone " "transformation of the distances between the 32 two-dimensional points " "that make up the capital letter #R.") PICTURE (4.0, 4.0, drawLetterRConfigurationExample) NORMAL (L"All 32 \\.c (32-1)/2 interpoint distances were subjected to the " "transformation: ") FORMULA (L"%dissimilarity__%ij_^ = %distance__%ij_^2 + 5 + %noiseRange \\.c #u, ") NORMAL (L"where #u is a uniform random variable between 0 and 1.") NORMAL (L"This example was chosen from @@Green, Carmone & Smith (1989)@.") MAN_END MAN_BEGIN (L"disparities", L"djmw", 19980111) INTRO (L"The numbers %d\\'p__%ij_ that result from applying an admissible " "transformation %f on the dissimilarities %\\de__%ij_, i.e., %d\\'p__%ij_ " "= %f (%\\de__%ij_). Disparities have the same dimension as distances. " "Other names for disparities are %%pseudo distances% and %%target " "distances%.") MAN_END MAN_BEGIN (L"Dissimilarity", L"djmw", 20010327) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"It represents a one-way table with " "dissimilarities between \"objects\".") ENTRY (L"Creating a Dissimilarity from data in a text file") NORMAL (L"Suppose you have three objects A, B and C. " "In one way or another, you have acquired the following (symmetric) " "dissimilarities: %\\de__%AB_ = 2 (= %\\de__%BA_) , %\\de__%AC_ = 1 " "(= %\\de__%CA_), and %\\de__%BC_ = 1.4 (= %\\de__CB_), where %\\de__%AB_" " represents the dissimilarity between object A and object B.") NORMAL (L"You can create a simple text file like the following:") CODE (L"\"ooTextFile\" ! The line by which Praat can recognize your file") CODE (L"\"Dissimilarity\" ! The line that tells Praat about the contents") CODE (L"3 \"A\" \"B\" \"C\" ! Number of columns, and column labels") CODE (L"3 ! Number of rows") CODE (L"\"A\" 0 2 1 ! Row label (A), A-B value, A-C value") CODE (L"\"B\" 2 0 1.4 ! Row label (B), B-A value, B-C value") CODE (L"\"C\" 1 1.4 0 ! Row label (C), C-A value, C-B value") NORMAL (L"Notice that:") LIST_ITEM (L"\\bu the row and column labels are identical.") LIST_ITEM (L"\\bu the matrix elements on the diagonal are zero.") LIST_ITEM (L"\\bu the matrix is symmetrical.") NORMAL (L"This text file can be read with the @@Read from file...@ command. " "Since a Dissimilarity object has the data structure of a square " "symmetrical TableOfReal, you could also start from an appropriate " "@TableOfReal object and cast it to a Dissimilarity object.") ENTRY (L"Commands") NORMAL (L"Creation") LIST_ITEM (L"\\bu @@Confusion: To Dissimilarity...") NORMAL (L"Drawing") LIST_ITEM (L"\\bu ##Draw as numbers...") LIST_ITEM (L"\\bu ##Draw as squares...") NORMAL (L"Query") LIST_ITEM (L"\\bu ##Get column mean (index)...") LIST_ITEM (L"\\bu ##Get column mean (label)...") LIST_ITEM (L"\\bu ##Get column stdev (index)...") LIST_ITEM (L"\\bu ##Get column stdev (label)...") LIST_ITEM (L"\\bu @@Dissimilarity: Get additive constant") NORMAL (L"Modification") LIST_ITEM (L"\\bu @@Formula...") LIST_ITEM (L"\\bu ##Set value...") LIST_ITEM (L"\\bu ##Remove column (index)...") LIST_ITEM (L"\\bu ##Insert column (index)...") LIST_ITEM (L"\\bu ##Set row label (index)...") LIST_ITEM (L"\\bu ##Set row label (label)...") LIST_ITEM (L"\\bu ##Set column label (index)...") LIST_ITEM (L"\\bu ##Set column label (label)...") NORMAL (L"Multidimensional scaling analysis") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (monotone mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (i-spline mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (interval mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (ratio mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (absolute mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (kruskal)...") LIST_ITEM (L"Transformations") LIST_ITEM (L"\\bu @@Dissimilarity: To Distance...") LIST_ITEM (L"\\bu @@Dissimilarity: To Weight") MAN_END MAN_BEGIN (L"Dissimilarity: Get additive constant", L"djmw", 19971201) INTRO (L"A command that calculates the \"additive constant\" from the selected @Dissimilarity.") NORMAL (L"Distances %d__%ij_ will be obtained from dissimilarities %\\de__%ij_ according to:") FORMULA (L" %distance__%ij_ = %dissimilarity__%ij_ + %additiveConstant") NORMAL (L"We use a procedure by @@Cailliez (1983)@ to solve the \"additive constant problem\", i.e. " "find the smallest %additiveConstant such that all %distance__%ij_ in the above equation " " have a Euclidean representation.") MAN_END MAN_BEGIN (L"Dissimilarity: To Configuration (absolute mds)...", L"djmw", 19980105) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity object.") NORMAL (L"The @disparities %d\\'p__%ij_ will be obtained from dissimilarities %\\de__%ij_ according to:") FORMULA (L"%d\\'p__%ij_ = %\\de__%ij_") MAN_END MAN_BEGIN (L"Dissimilarity: To Configuration (interval mds)...", L"djmw", 19980105) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity object.") NORMAL (L"The @disparities %d\\'p__%ij_ will be obtained from dissimilarities %\\de__%ij_ according to:") FORMULA (L"%d\\'p__%ij_ = %a + %b \\.c %\\de__%ij_") MAN_END MAN_BEGIN (L"Dissimilarity: To Configuration (i-spline mds)...", L"djmw", 20040407) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity object.") NORMAL (L"Dissimilarities %\\de__%ij_ and @disparities %d\\'p__%ij_ will be related by a @spline function:") FORMULA (L"%d\\'p__%ij_ = \\su__%k=1..(%%numberOfInteriorKnots%+%order)_ spline__%k_ (%knots, %order, %\\de__%ij_),") NORMAL (L"where spline__%k_ (\\.c) is the value of the %k^^th^ I-spline of order %order and knot sequence " "%knot evaluated at %\\de__%ij_.") ENTRY (L"Settings") TAG (L"##Number of dimensions") DEFINITION (L"determines the dimensionality of the configuration.") TAG (L"##Number of interior knots") DEFINITION (L"determines the number of segment boundaries. Each interior knot " "is the boundary between two segments. The splines in each segment will " "be joined as continuously as possible.") TAG (L"##Order of I-spline") DEFINITION (L"The order of the polynomial basis of the I-spline.") NORMAL (L"Finding the optimal Configuration involves a minimization process:") TAG (L"##Tolerance") DEFINITION (L"When successive values for the stress differ by less than " "#Tolerance, the minimization process stops.") TAG (L"##Maximum number of iterations") DEFINITION (L"Minimization stops after this number of iterations has been " "reached.") TAG (L"##Number of repetitions") DEFINITION (L"If chosen larger than 1, the minimization process will be " "repeated, each time with another random start configuration. " "The configuration that results in minimum stress, will be saved.") ENTRY (L"Hints") NORMAL (L"If %numberOfInteriorKnots is zero, polynomial regression will be " "performed. Therefore , the combination %numberOfInteriorKnots = 0 and " "%order = 1 also gives interval " "scaling (in fact, it is the implementation in this program).") NORMAL (L"In the limit when %order = 0 and %numberOfInteriorKnots = " "%numberOfDissimilarities, monotone regression is performed.") MAN_END MAN_BEGIN (L"Dissimilarity: To Configuration (kruskal)...", L"djmw", 20040407) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object.") ENTRY (L"Settings") TAG (L"##Number of dimensions# (standard value: 2)") DEFINITION (L"The dimensionality of the Configuration.") TAG (L"##Distance metric% (standard value: 2, i.e. Euclidean)") DEFINITION (L"the general distance between points #x__%i_ and #x__%j_ (%i,%j " "= 1..%numberOfPoints) is:") DEFINITION (L"(\\su__%k=1..%numberOfDimensions_ |%x__%ik_ \\--%x__%jk_|" "^^%metric^)^^1/%metric^") TAG (L"##Sort distances") DEFINITION (L"determines the handling of ties in the data. When off, whenever " "two or more dissimilarities are equal we do not care whether the fitted " "distances are equal or not. " "Consequently, no constraints are imposed on the fitted distances. " "When on, however, we impose the constaint that the fitted distances be " "equal whenever the dissimilarities are equal.") NORMAL (L"For the calculation of stress:") TAG (L"##Formula1 (default)") // ?? FORMULA (L"%stress = \\Vr(\\su(%distance__%k_ \\-- %fittedDistance__%k_)^2 / " "\\su %distance__%k_^2)") TAG (L"##Formula2") FORMULA (L"%stress = \\Vr(\\su(%distance__%k_ \\-- %fittedDistance__%k_)^2 / " "\\su (%distance__%k_ \\-- %averageDistance)^2)") DEFINITION (L"Note that values of stress 2 are generally more than double those " "of stress 1 for the same degree of fit.") NORMAL (L"Finding the optimal Configuration involves a minimization process:") TAG (L"##Tolerance") DEFINITION (L"When successive values for the stress differ less than %Tolerance " "the minimization process stops.") TAG (L"##Maximum number of iterations") DEFINITION (L"Minimization stops after this number of iterations has been " "reached.") TAG (L"##Number of repetitions") DEFINITION (L"When chosen larger than 1, the minimalization process will be " "repeated, each time with another random start configuration. " "The configuration that results in minimum stress will be saved.") ENTRY (L"Precautions") NORMAL (L"When there are few objects it is impossible to recover many " "dimensions. A rough rule of thumb is that there should be at least twice " "as many number of observations, i.e. the %numberOfPoints \\.c " "(%numberOfPoints - 1) / 2 (dis)similarities, than parameters " "to be estimated, i.e. the %numberOfPoints \\.c %numberOfDimensions " "position coordinates. A practical guide is:") LIST_ITEM (L"for %numberOfDimensions = 1 you need \\>_ 5 objects") LIST_ITEM (L"for %numberOfDimensions = 2 you need \\>_ 9 objects") LIST_ITEM (L"for %numberOfDimensions = 3 you need \\>_ 13 objects") NORMAL (L"There is no feasible way to be certain that you have found the " "true global minimum. However, by using a great number of different " "random starting configurations to scale the same data it is often " "possible to obtain practical certainty. " "Although the procedure for obtaining an initial configuration is based " "on a %linear relation between distance and (dis)similarity, it gives a " "very good approximation of the optimal #Configuration and " "the #Minimizer practically always finds the global minimum from it " "(I guess...). A way to find out is to try the %numberOfRepetitions " "parameter which gives you the possibility to fit many times and each " "time start with another random initial configuration.") ENTRY (L"Algorithm") LIST_ITEM (L"1. The Dissimilarity object is converted to a Distance object in " "the same way as in @@Dissimilarity: To Distance...@.)") LIST_ITEM (L"2. From the Distance object an initial Configuration is found by " "first transforming the Distance object to a matrix with scalar products " "of distances and subsequently solving for the first %numberOfDimensions " "eigenvectors of this matrix.") LIST_ITEM (L"3. A minimalization algorithm is started that tries to minimize a " "function. In this function:") LIST_ITEM (L"\\bu 3.1 We normalize the current Configuration from the minimizer") LIST_ITEM (L"\\bu 3.2 Calculate a new Distance object from the configuration") LIST_ITEM (L"\\bu 3.3 Do a monotone regression of this Distance on the " "Dissimilarity. This results in a new Distance object.") LIST_ITEM (L"\\bu 3.4 Calculate stress from this Distance and the Distance " "obtained from Dissimilarity.") NORMAL (L"The optimization process is ccontrolledby a conjugate gradient " "minimization algorithm that tries to minimize the %stress function. " "In @@Kruskal (1964)@, a steepest descent " "algorithm is used wwhichis less efficient. ") MAN_END MAN_BEGIN (L"Dissimilarity: To Configuration (monotone mds)...", L"djmw", 20040407) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object.") NORMAL (L"Dissimilarities %\\de__%ij_ and @disparities %d\\'p__%ij_ are " "related by:") FORMULA (L"%d\\'p__%ij_ \\<_ %d\\'p__%kl_ if %\\de__%ij_ \\<_ %\\de__%kl_") ENTRY (L"Settings") TAG (L"##Number of dimensions") DEFINITION (L"determines the number of dimensions of the configuration.") TAG (L"##Primary or secondary approach to ties") DEFINITION (L"When dissimilarities are equal, i.e., %\\de__%ij_ = %\\de__%kl_, " "the primary approach imposes no conditions on the corresponding " "@disparities %d\\'p__%ij_ and %d\\'p__%kl_, while the %secondary " "approach demands that also %d\\'p__%ij_ = %d\\'p__%kl_.") NORMAL (L"Finding the optimal Configuration involves a minimization process:") TAG (L"##Tolerance") DEFINITION (L"When successive values for the stress differ less than %Tolerance " "the minimization process stops.") TAG (L"##Maximum number of iterations") DEFINITION (L"Minimization stops after this number of iterations has been reached.") TAG (L"##Number of repetitions") DEFINITION (L"When chosen larger than 1, the minimalization process will be " "repeated, each time with another random start configuration. " "The configuration that results in minimum stress will be saved.") MAN_END MAN_BEGIN (L"Dissimilarity: To Configuration (ratio mds)...", L"djmw", 19980105) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object.") NORMAL (L"The @disparities %d\\'p__%ij_ will be obtained from dissimilarities " "%\\de__%ij_ according to:") FORMULA (L"%d\\'p__%ij_ = %b \\.c %\\de__%ij_") MAN_END MAN_BEGIN (L"Dissimilarity: To Distance...", L"djmw", 20040407) INTRO (L"A command that creates a @Distance object from a selected " "@Dissimilarity object.") ENTRY (L"Settings") TAG (L"##Scale") DEFINITION (L"when on, the @@Dissimilarity: Get additive constant|" "additiveConstant@ is determined, when off the %additiveConstant = 0.") NORMAL (L"dissimilarities are transformed to distances according to:") FORMULA (L" %distance__%ij_ = %dissimilarity__%ij_ + %additiveConstant.") MAN_END MAN_BEGIN (L"Dissimilarity: To Weight", L"djmw", 19980108) INTRO (L"Creates an object of type @Weight for each selected @Dissimilarity " "object.") NORMAL (L"The values in the weight matrix will be:") LIST_ITEM (L"%w__%ii_ = 0") LIST_ITEM (L"%w__%ij_ = 1 if %\\de__%ij_ > 0") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Draw regression (absolute mds)...", L"djmw", 20040407) INTRO (L"Draws a scatterplot of the dissimilarities %\\de__%ij_ from the " "selected @Dissimilarity object versus @disparities %d\\'p__%ij_ obtained " "from the \"regression\" of distances %d__%ij_ " "from @Configuration on the dissimilarities %\\de__%ij_.") FORMULA (L"%d\\'p__%ij_ = %\\de__%ij_") ENTRY (L"Settings") TAG (L"##Minimum proximity#, ##Maximum proximity#") DEFINITION (L"minimum and maximum values for the proximities (horizontal axis).") TAG (L"##Minimum distance#, ##Maximum distance#") DEFINITION (L"minimum and maximum values for the distances (vertical axis).") TAG (L"##Mark size (mm)#, ##Mark string#") DEFINITION (L"size and kind of the marks in the plot.") TAG (L"##Garnish") DEFINITION (L"when on, draws a bounding box with decoration.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Draw regression (interval mds)...", L"djmw", 20040407) INTRO (L"Draws a scatterplot of the dissimilarities %\\de__%ij_ from the " "selected @Dissimilarity versus @disparities %d\\'p__%ij_ obtained " "from the regression of distances %d__%ij_ " "from @Configuration on the dissimilarities %\\de__%ij_.") FORMULA (L"%d\\'p__%ij_ = %a + %b \\.c %\\de__%ij_,") NORMAL (L"where the values of %a and %b are determined by regression.") ENTRY (L"Settings") TAG (L"##Minimum proximity#, ##Maximum proximity#") DEFINITION (L"minimum and maximum values for the proximities (horizontal axis).") TAG (L"##Minimum distance#, ##Maximum distance#") DEFINITION (L"minimum and maximum values for the distances (vertical axis).") TAG (L"##Mark size (mm)#, ##Mark string#") DEFINITION (L"size and kind of the marks in the plot.") TAG (L"##Garnish") DEFINITION (L"when on, draws a bounding box with decoration.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Draw regression (i-spline mds)...", L"djmw", 20040407) INTRO (L"Draws a scatterplot of the dissimilarities %\\de__%ij_ from the " "selected @Dissimilarity versus @disparities %d\\'p__%ij_ obtained " "from the regression of distances %d__%ij_ from @Configuration on the " "@spline transformed dissimilarities %\\de__%ij_.") ENTRY (L"Settings") TAG (L"##Number of interior knots") DEFINITION (L"determines the number of segments.") TAG (L"##Order of I-spline") DEFINITION (L"The order of the polynomial basis of the I-spline.") TAG (L"##Minimum proximity#, ##Maximum proximity#") DEFINITION (L"minimum and maximum values for the proximities (horizontal axis).") TAG (L"##Minimum distance#, ##Maximum distance#") DEFINITION (L"minimum and maximum values for the distances (vertical axis).") TAG (L"##Mark size (mm)#, ##Mark string#") DEFINITION (L"size and kind of the marks in the plot.") TAG (L"##Garnish") DEFINITION (L"when on, draws a bounding box with decoration.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Draw regression (monotone mds)...", L"djmw", 20040407) INTRO (L"Draws a scatterplot of the dissimilarities %\\de__%ij_ from the " "selected @Dissimilarity versus @disparities %d\\'p__%ij_ obtained " "from the monotone regression of distances %d__%ij_ " "from @Configuration on the dissimilarities %\\de__%ij_.") ENTRY (L"Settings") TAG (L"##Primary or secondary approach to ties") DEFINITION (L"When dissimilarities are equal, i.e., %\\de__%ij_ = %\\de__%kl_ " "the primary approach imposes no conditions on the corresponding distances " "%d__%ij_ and %d__%kl_, while the %secondary approach demands that also " "%d__%ij_ = %d__%kl_.") TAG (L"##Minimum proximity#, ##Maximum proximity#") DEFINITION (L"minimum and maximum values for the proximities (horizontal axis).") TAG (L"##Minimum distance#, ##Maximum distance#") DEFINITION (L"minimum and maximum values for the distances (vertical axis).") TAG (L"##Mark size (mm)#, ##Mark string#") DEFINITION (L"size and kind of the marks in the plot.") TAG (L"##Garnish") DEFINITION (L"when on, draws a bounding box with decoration.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Draw regression (ratio mds)...", L"djmw", 20040407) INTRO (L"Draws a scatterplot of the dissimilarities %\\de__%ij_ from the " "selected @Dissimilarity versus @disparities %d\\'p__%ij_ obtained " "from the \"regression\" of distances %d__%ij_ " "from @Configuration on the dissimilarities %\\de__%ij_.") FORMULA (L"%d\\'p__%ij_ = %b \\.c %\\de__%ij_,") NORMAL (L"where the value of %b is determined by regression.") ENTRY (L"Settings") TAG (L"##Minimum proximity#, ##Maximum proximity#") DEFINITION (L"minimum and maximum values for the proximities (horizontal axis).") TAG (L"##Minimum distance#, ##Maximum distance#") DEFINITION (L"minimum and maximum values for the distances (vertical axis).") TAG (L"##Mark size (mm)#, ##Mark string#") DEFINITION (L"size and kind of the marks in the plot.") TAG (L"##Garnish") DEFINITION (L"when on, draws a bounding box with decoration.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Draw Shepard diagram...", L"djmw", 20040407) INTRO (L"Draws the Shepard diagram. This is a scatterplot of the " "dissimilarities from the @Dissimilarity object versus distances (as " "calculated from the @Configuration).") ENTRY (L"Settings") TAG (L"##Minimum proximity#, ##Maximum proximity#") DEFINITION (L"minimum and maximum values for the proximities (horizontal axis).") TAG (L"##Minimum distance#, ##Maximum distance#") DEFINITION (L"minimum and maximum values for the distances (vertical axis).") TAG (L"##Mark size (mm)#, ##Mark string#") DEFINITION (L"size and kind of the marks in the plot.") TAG (L"##Garnish") DEFINITION (L"when on, draws a bounding box with decoration.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Get stress (absolute mds)...", L"djmw", 19980119) INTRO (L"A command to obtain the @stress value for the selected @Dissimilarity " "and @Configuration object.") ENTRY (L"Behaviour") NORMAL (L"Stress formula's are #dependent of the scale of the Configuration: " "you will get #another stress value if you had pre-multiplied the " "selected Configuration with any number greater than zero.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Get stress (interval mds)...", L"djmw", 19980119) INTRO (L"A command to obtain the @stress value for the selected @Dissimilarity " "and @Configuration object.") ENTRY (L"Behaviour") NORMAL (L"We use stress formula's that are independent of the scale of the " "Configuration: you would have got the same stress value if you had " "pre-multiplied the selected Configuration with any number greater " "than zero.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Get stress (i-spline mds)...", L"djmw", 19980119) INTRO (L"A command to obtain the @stress value for the selected @Dissimilarity " "and @Configuration object.") ENTRY (L"Behaviour") NORMAL (L"We use stress formula's that are independent of the scale " "of the Configuration: you would have got the same stress value if " "you had pre-multiplied the selected Configuration with any number " "greater than zero.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Get stress (monotone mds)...", L"djmw", 19980119) INTRO (L"A command to obtain the @stress value for the selected @Dissimilarity " "and @Configuration object.") ENTRY (L"Behaviour") NORMAL (L"We use stress formula's that are independent of the scale " "of the Configuration: you would have got the same stress value if " "you had pre-multiplied the selected Configuration with any number " "greater than zero.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: Get stress (ratio mds)...", L"djmw", 19980119) INTRO (L"A command to obtain the @stress value for the selected @Dissimilarity " "and @Configuration object.") ENTRY (L"Behaviour") NORMAL (L"We use stress formula's that are independent of the scale " "of the Configuration: you would have got the same stress value if " "you had pre-multiplied the selected Configuration with any number " "greater than zero.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: To Configuration (absolute mds)...", L"djmw", 19980119) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object. The selected Configuration object serves as a starting " "configuration for the minimization process.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: To Configuration (interval mds)...", L"djmw", 19980119) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object. The selected Configuration object serves as a starting " "configuration for the minimization process.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: To Configuration (i-spline mds)...", L"djmw", 19980119) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object. The selected Configuration object serves as a starting " "configuration for the minimization process.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: To Configuration (kruskal)...", L"djmw", 19971201) INTRO (L"A command to fit an optimal @Configuration for the selected " "@Dissimilarity object. The selected @Configuration will be used as the " "starting configuration in the kruskal analysis.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: To Configuration (monotone mds)...", L"djmw", 19980119) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object. The selected Configuration object serves as a starting " "configuration for the minimization process.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration: To Configuration (ratio mds)...", L"djmw", 19980119) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object. The selected Configuration object serves as a starting " "configuration for the minimization process.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration & Weight: Get stress...", L"djmw", 20040407) INTRO (L"A command that calculates the @stress between distances %d__%ij_ " "derived from the selected @Configuration object and @disparities " "%d\\'p__%ij_ derived from the selected @Dissimilarity object. " "With the selected @Weight object the evaluation of the influence " "of each dissimilarity on stress can be influenced.") ENTRY (L"Settings") LIST_ITEM (L"%%Normalized stress%, %%Kruskal's stress-1%, %%Kruskal's " "stress-2% or %Raw stress%") ENTRY (L"Behaviour") NORMAL (L"Except for %absolute %mds, we us stress formula's that are " "independent of the scale of the Configuration (see @stress): you would " "have got the same stress value if you had pre-multiplied the selected " "Configuration with any number greater than zero.") MAN_END MAN_BEGIN (L"Dissimilarity & Configuration & Weight: To Configuration...", L"djmw", 20040407) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object. With the selected @Weight object the influence of each " "dissimilarity on @stress can be influenced. The selected Configuration " "object serves as a starting configuration for the minimization process.") ENTRY (L"Settings") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (monotone mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (i-spline mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (interval mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (ratio mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (absolute mds)...") MAN_END MAN_BEGIN (L"Dissimilarity & Weight: To Configuration...", L"djmw", 20040407) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object. With the selected @Weight object the influence of each " "dissimilarity on @stress can be influenced.") ENTRY (L"Settings") NORMAL (L"May be different and depend on the representation function, i.e. " "the scale of measurement.") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (monotone mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (i-spline mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (interval mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (ratio mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (absolute mds)...") MAN_END MAN_BEGIN (L"Dissimilarity & Weight: To Configuration...", L"djmw", 20040407) INTRO (L"A command that creates a @Configuration object from a @Dissimilarity " "object. With the selected @Weight object the influence of each " "dissimilarity on @stress can be influenced.") ENTRY (L"Settings") NORMAL (L"May be different and depend on the representation function, i.e. the scale of measurement.") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (monotone mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (i-spline mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (interval mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (ratio mds)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (absolute mds)...") MAN_END MAN_BEGIN (L"Distance", L"djmw", 19971124) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Distance represents distances between objects in a metrical space.") NORMAL (L"Creation") LIST_ITEM (L"\\bu @@Confusion: To Dissimilarity (pdf)...") LIST_ITEM (L"\\bu @@Dissimilarity: To Distance...") MAN_END MAN_BEGIN (L"Distance: To Configuration (indscal)...", L"djmw", 19971124) INTRO (L"Perform an @@INDSCAL analysis@ on the selected object(s) of type @Distance that " "results in a @Configuration and a @Salience object.") MAN_END MAN_BEGIN (L"Distance: To Configuration (ytl)...", L"djmw", 19971124) INTRO (L"A command that creates one @Configuration and one @Salience object " "from a collection of one or more @Distance objects.") NORMAL (L"This Configuration and Salience object normally serve as starting points " "for an @@individual difference scaling@ such as an @@INDSCAL analysis@.") NORMAL (L"The algorithm is ddescribedin @@Young, Takane & Lewyckyj (1978)@.") MAN_END MAN_BEGIN (L"Distance: To ScalarProduct...", L"djmw", 20040407) INTRO (L"A command that creates a @ScalarProduct for each selected @Distance.") ENTRY (L"Setting") TAG (L"##Make sum of squares equal 1.0") DEFINITION (L"when selected, the elements in the resulting matrix part will be scaled such that " "the sum of all the squared elements in the matrix equals 1.0.") ENTRY (L"Algorithm") NORMAL (L"ScalarProduct entries %b__%ij_ are created from distances %d__%ij_ bij double centering " "the matrix with elements \\--1/2 %d__%ij_^2, i.e.,") FORMULA (L"%b__%ij_= \\--1/2(%d__%ij_^2 \\-- %d__%\\.cj_^2 \\-- %d__%i\\.c_^2 + %d__%\\.c\\.c_^2),") NORMAL (L"where the dot (\\.c) means averaging over that dimension.") MAN_END MAN_BEGIN (L"Distance & Configuration: Draw scatter diagram...", L"djmw", 19971201) MAN_END MAN_BEGIN (L"Distance & Configuration: Get VAF...", L"djmw", 19971201) INTRO (L"Calculates the \"%%variance accounted for%\" from the selected collection of @Distance objects and the " "selected @Configuration. The optimal @Salience necessary for the calculation " "will be inferred from the selected Distance and Configuration objects.") MAN_END MAN_BEGIN (L"Distance & Configuration: To Configuration (indscal)...", L"djmw", 19971201) INTRO (L"Performs an @@INDSCAL analysis@ on the selected objects of type @Distance and calculates " "a @Configuration from them. Uses the selected Configuration object as the initial Configuration in " "the iteration process.") MAN_END MAN_BEGIN (L"Distance & Configuration & Salience: Get VAF...", L"djmw", 19971201) INTRO (L"Calculates the \"variance accounted for\" from the selected collection " "of @Distance objects, the " "selected @Configuration and the selected #Salience.") MAN_END MAN_BEGIN (L"Distance & Configuration & Salience: To Configuration " "(indscal)...", L"djmw", 19971201) INTRO (L"A command that creates a new @Configuration from the selected " "collection of @Distance objects, the selected @Configuration and the " "selected #Salience. The selected Configuration and Salience " "serve as start values for the @@INDSCAL analysis@.") MAN_END MAN_BEGIN (L"individual difference scaling", L"djmw", 19970502) INTRO (L"The purpose of individual difference scaling is to represent objects, " "whose dissimilarities are given, as points in a metrical space. " "The distances in the space should be in accordance with the " "dissimilarities as well as is possible. Besides the configuration a " "@Salience matrix is calculated.") NORMAL (L"The basic Euclidean model is:") LIST_ITEM (L"%\\de__%ijk_ \\~~ (\\su__%s=1..%r_ %w__%ks_(%x__%is_ \\-- " "%x__%js_)^2)^^1/2^") NORMAL (L"Here \\de__%ijk_ is the (known) dissimilarity between %objects %i and " "%j, as measured on %data %source %k. The %x's are the %coordinates of " "the objects in an %r-dimensional space and the %w's are weights or " "saliences. Because straight minimization of the expression above " "is difficult, one applies transformations on this expression. " "Squaring both sides gives the model:") LIST_ITEM (L"%\\de^2__%ijk_ \\~~ \\su__%s=1..%r_ %w__%ks_(%x__%is_ \\-- " "%x__%js_)^2") NORMAL (L"and the corresponding least squares loss function:") LIST_ITEM (L"\\su__%k=1..%numberOfSources_ \\su__%i=1..%numberOfPoints_ " "\\su__%j=1..%numberOfPoints_ (%\\de^2__%ijk_ \\-- %d^2__%ijk_)^2") NORMAL (L"This loss function is minimized in the (ratio scale option of the) " "#ALSCAL program of @@Takane, Young & de Leeuw (1976)@.") NORMAL (L"The transformation used by @@Carroll & Chang (1970)@ in the INDSCAL " "model, transforms the data from each source into scalar products " "of vectors. For the dissimilarities:") LIST_ITEM (L"%\\be__%ijk_ = \\--{ %\\de^2__%ijk_ \\-- %\\de^2__%i.%k_ \\-- " "%\\de^2__.%jk_ + %\\de^2__..%k_ } / 2,") NORMAL (L"where dots replacing indices indicate averaging over the range of " "that index. In the same way for the distances:") LIST_ITEM (L"%z__%ijk_ = \\--{ %d^2__%ijk_ \\-- %d^2__%i.%k_ \\-- %d" "^2__%.%jk_ + %d^2__%..%k_ } / 2.") LIST_ITEM (L"%\\be__%ijk_ \\~~ %z__%ijk_ = \\su__%s=1..%numberOfDimensions_ " "%w__%ks_ %x__%is_ %x__%js_") NORMAL (L"Translated into matrix algebra, the equation above translates to:") LIST_ITEM (L"%B__%k_ \\~~ %Z__%k_ = %X %W__%k_ %X\\'p,") NORMAL (L"where %X is a %numberOfPoints \\xx %numberOfDimensions configuration " "matrix, %W__%k_, a non-negative %numberOfDimensions \\xx " "%numberOfDimensions matrix with weights, and %B__%k_ " "the %k^^th^ slab of %\\be__%ijk_.") NORMAL (L"This translates to the following INDSCAL loss function:") FORMULA (L"%f(%X, %W__1_,..., %W__%numberOfSources_) = " "\\su__%k=1..%numberOfSources_ | %B__%k_ \\-- %X%W__%k_%X\\'p |^2") NORMAL (L"") MAN_END MAN_BEGIN (L"INDSCAL analysis", L"djmw", 20120306) INTRO (L"A method for @@individual difference scaling@ analysis in P\\s{RAAT}.") NORMAL (L"An INDSCAL analysis can be performed on objects of type Distance.") NORMAL (L"If you start with @Dissimilarity objects you first have to transform " "them to Distance objects.") LIST_ITEM (L"\\bu @@Dissimilarity: To Distance...@") NORMAL (L"If you start with a @Confusion you can use:") LIST_ITEM (L"\\bu @@Confusion: To Dissimilarity (pdf)...@") ENTRY (L"Examples") LIST_ITEM (L"\\bu @@Distance: To Configuration (indscal)...@") DEFINITION (L"Perform an INDSCAL analysis on one or more objects of type " "@Distance to calculate a @Configuration.") LIST_ITEM (L"\\bu @@Distance & Configuration: To Configuration (indscal)...@") DEFINITION (L"Perform an INDSCAL analysis on one or more objects of type " "@Distance to calculate a @Configuration. Use the selected Configuration " "object as the initial Configuration in the iteration process.") ENTRY (L"Algorithm") NORMAL (L"The function to be minimized in INDSCAL is the following:") FORMULA (L"%f(%X, %W__1_,..., %W__%numberOfSources_) = " "\\su__%i=1..%numberOfSources_ |%S__%i_ \\-- %XW__%i_%X\\'p|^2") NORMAL (L"where %X an unknown %numberOfPoints x %numberOfDimensions " "configuration matrix, the %W__%i_ are %numberOfSources unknown " "diagonal %numberOfDimensions x %numberOfDimensions matrices with weights, " "often called saliences, and the %S__%i_ are known symmetric " "matrices with scalar products of dimension %numberOfPoints x " "%numberOfPoints.") NORMAL (L"In the absence of an algorithm that minimizes %f, @@Carroll & " "Chang (1970)@ resorted to the @CANDECOMP algorithm, which instead of the " "function given above minimizes the following function:") FORMULA (L"%g(%X, %Y, %W__1_,..., %W__%numberOfSources_) = " "\\su__%i=1..%numberOfSources_ |%S__%i_ \\-- %XW__%i_%Y\\'p|^2.") NORMAL (L"Carroll & Chang claimed that for most practical circumstances %X " "and %Y converge to matrices that will be columnwise proportional. " "However, INDSCAL does not only require symmetry of the solution, " "but also non-negativity of the weights. Both these aspects cannot be " "guaranteed with the CANDECOMP algorithm.") NORMAL (L"@@Ten Berge, Kiers & Krijnen (1993)@ describe an algorithm that " "automatically satisfies symmetry because it solves %f directly, and, " "also, can guarantee non-negativity of the weights. " "This algorithm proceeds as follows:") NORMAL (L"Let #%x__%h_ be the %h-th column of %X. We then write the function %f above as:") FORMULA (L"%f(#%x__%h_, %w__1%h_, ..., %w__%numberOfSources %h_) = \\su__%i=1.." "%numberOfSources_ |%S__%ih_ \\-- #%x__%h_%w__%ih_#%x\\'p__%h_|^2,") NORMAL (L"with %S__%ih_ defined as:") FORMULA (L"%S__%ih_ = (%S__%i_ - \\su__%j\\=/%h, %j=1..%numberOfDimensions_ " "#%x__%j_%w__%ij_#%x\\'p__%j_).") NORMAL (L"Without loss of generality we may require that") FORMULA (L"#%x\\'p__%h_#%x__%h_ = 1") NORMAL (L"Minimizing %f over #%x__%h_ is equivalent to minimizing") FORMULA (L"\\su__%i=1..%numberOfSources_ |%S__%ih_|^2 \\-- 2tr \\su " "%S__%ih_#%x__%h_%w__%ih_#%x\\'p__%h_ + \\su %w^2__%ih_") NORMAL (L"This amounts to maximizing") FORMULA (L"%g(#%x__%h_) = #%x\\'p__%h_(\\su %w__%ih_%S__%ih_)#%x__%h_") NORMAL (L"subject to #%x\\'p__%h_#%x__%h_ = 1. The solution for #%x__%h_ is " "the dominant eigenvector of (\\su %w__%ih_%S__%ih_), " "which can be determined with the power method (see @@Golub & van Loan " "(1996)@). The optimal value " "for the %w__%ih_, given that all other parameters are fixed:") FORMULA (L"%w__%ih_ = #%x\\'p__%h_%S__%ih_#%x__%h_") NORMAL (L"In an alternating least squares procedure we may update columns of " "%X and the diagonals of the %W matrices in any sensible order.") MAN_END MAN_BEGIN (L"Kruskal analysis", L"djmw", 19971201) INTRO (L"One of the @@MDS models@ in P\\s{RAAT}.") NORMAL (L"You can perform a Kruskal-type multidimensional scaling only on " "objects of type @Dissimilarity. Objects of other types first have to " "be converted to objects of Dissimilarity type.") ENTRY (L"Example") NORMAL (L"Convert a @Dissimilarity object into a @Configuration object.") LIST_ITEM (L"\\bu @@Dissimilarity: To Configuration (monotone mds)...@") DEFINITION (L"choose appropriate parameters") LIST_ITEM (L"\\bu @@Dissimilarity & Configuration: Get stress (monotone mds)...@") DEFINITION (L"choose stress-1 to obtain the value for the @stress according " "to Kruskal.") ENTRY (L"How to get started") NORMAL (L"You can create an example @Dissimilarity object with the @@Create " "letter R example...@ button which you can find under the " "##Multidimensional scaling# option in the #New menu.") MAN_END MAN_BEGIN (L"MDS models", L"djmw", 20101109) INTRO (L"Multidimensional scaling (MDS) models are defined by specifying " "how given @Dissimilarity data, %\\de__%ij_, are " "mapped into distances of an %m-dimensional MDS @Configuration %#X. " "The mapping is specified by a %%representation function%, %f : " "%\\de__%ij_ \\-> %d__%ij_(#X), which specifies how " "dissimilarities should be related to the distances. The MDS analysis " "tries to find the configuration (in a given dimensionality) whose " "distances satisfy %f as closely as possible. " "This closeness is quantified by a badness-of-fit measure which is often " "called @stress.") ENTRY (L"Representation functions") NORMAL (L"In the application of MDS we try to find a configuration #X such that " "the following relations are satisfied as well as possible:") FORMULA (L"%f(%\\de__%ij_) \\~~ %d__%ij_(#X)") NORMAL (L"The numbers that result from applying %f on %\\de__%ij_ are sometimes " "called @disparities %d\\'p__%ij_. In most applications of MDS, besides " "the configuration #X, also the function %f is not " "completely specified, i.e., the exact parameters of %f are unknown and " "must also be estimated during the analysis. If no particular %f can be " "derived from a theoretical model, one often restricts %f to a particular " "class of functions on the basis of the scale level of the dissimilarity " "data. If the disparities are related to the proximities by a specific " "parametric function we speak of %metric MDS otherwise we speak of " "%ordinal or %%non-metric% MDS.") LIST_ITEM (L"\\bu %absolute mds: %d\\'p__%ij_ = \\de__%ij_") DEFINITION (L"No parameters need to be estimated.") LIST_ITEM (L"\\bu %ratio mds: %d\\'p__%ij_ = %b \\.c \\de__%ij_,") DEFINITION (L"where the value of %b can be estimated by a linear regression of " "%d__%ij_ on %\\de__%ij_.") LIST_ITEM (L"\\bu %interval mds: %d\\'p__%ij_ = %a + %b \\.c %\\de__%ij_,") DEFINITION (L"where the values of %a and %b can be estimated by a linear " "regression of %d__%ij_ on %\\de__%ij_.") LIST_ITEM (L"\\bu %i-spline mds: %d\\'p__%ij_ = %i-spline(%\\de__%ij_),") DEFINITION (L"where %i-spline(\\.c) is a smooth monotonically increasing " "@spline curve. The conceptual idea is that it is not possible to map " "all dissimilarities into disparities by one simple function.") LIST_ITEM (L"\\bu %monotone mds: %d\\'p__%ij_ = %monotone(\\de__%ij_),") DEFINITION (L"where %monotone(\\.c) is restricted to be a monotonic function " "that preserves the order of the dissimilarities:") FORMULA (L"if %\\de__%ij_ < %\\de__%kl_, then %d__%ij_(#X) < %d__%kl_(#X)") DEFINITION (L"If %\\de__%ij_ = %\\de__%kl_ and no particular constraint is involved for %d__%ij_(#X) " "and %d__%kl_(#X) this is referred to as the %%primary approach% to ties. The %%secondary " "approach% to ties requires that if %\\de__%ij_ = %\\de__%kl_, then also %d__%ij_(#X) = %d__%kl_(#X).") NORMAL (L"More information on all aspects of multidimensional scaling can be found in: " "@@Borg & Groenen (1997)@ and @@Ramsay (1988)@.") NORMAL (L"The most important object types used in Praat for MDS and the conversions between these types are " "shown in the following figure.") PICTURE (6, 6, drawMDSClassRelations) MAN_END MAN_BEGIN (L"Measurement levels", L"djmw", 19970502) INTRO (L"According to the measurement theory of @@Stevens (1951)@, there are four measurement levels, namely " "#Nominal, #Ordinal, #Interval and #Ratio. In the light of multidimensional scaling, the first " "two levels, Nominal and Ordinal, are often called %non-%metric. The last two are %metric.") MAN_END MAN_BEGIN (L"Multidimensional scaling", L"djmw", 20120306) INTRO (L"This tutorial describes how you can use P\\s{RAAT} to " "perform ##M#ulti##D#imensional ##S#caling (MDS) analysis.") NORMAL (L"MDS helps us to represent %dissimilarities between objects as " "%distances in a %%Euclidean space%. In effect, the more dissimilar two " "objects are, the larger the distance between the objects in the Euclidean " "space should be. The data types in P\\s{RAAT} that " "incorporate these notions are @Dissimilarity, @Distance and " "@Configuration.") NORMAL (L"In essence, an MDS-analysis is performed when you select a " "Dissimilarity object and choose one of the ##To Configuration (xxx)...# " "commands to obtain a Configuration object. In the above, method (xxx) " "represents on of the possible @@MDS models|multidimensional scaling " "models@.") ENTRY (L"MDS-analysis") NORMAL (L"Let us first create a Dissimilarity object. You can for example " "@@Dissimilarity|create a Dissimilarity object from a file@. Here we " "will the use the Dissimilarity object from @@Create letter R example...|" "the letter R example@. We have chosen the default value (32.5) for the " "(uniform) noise range. Note that this may result in substantial " "distortions between the dissimilarities and the distances.") NORMAL (L"Now you can do the following, for example:") NORMAL (L"Select the Dissimilarity and choose @@Dissimilarity: To Configuration " "(monotone mds)...|To Configuration (monotone mds)...@, and you perform " "a @@Kruskal analysis|kruskal@-like multidimensional scaling which " "results in a new " "Configuration object. (This Configuration could subsequently be used as " "the starting Configuration for a new MDS-analysis!).") NORMAL (L"Select the Configuration and choose @@Configuration: Draw...|Draw...@ " "and the following picture will result") PICTURE (4.0, 4.0, drawLetterRConfigurationExample2) NORMAL (L"The following script summarizes:") CODE (L"Create letter R example... 32.5") CODE (L"select Dissimilarity R") CODE (L"To Configuration (monotone mds)... 2 \"Primary approach\" 0.00001 50 1") CODE (L"Draw... 1 2 -0.8 1.2 -0.8 0.7 yes") ENTRY (L"Obtaining the stress value") NORMAL (L"Select the Dissimilarity and the Configuration together and query for " "the @stress value with: " "@@Dissimilarity & Configuration: Get stress (monotone mds)...|" "Get stress (monotone mds)...@. ") NORMAL (L"The following script summarizes:") CODE (L"select Dissimilarity R") CODE (L"plus Configuration R_monotone") CODE (L"Get stress (monotone mds)... \"Primary approach\" \"Kruskals's " "stress-1\")") ENTRY (L"The Shepard diagram") NORMAL (L"Select the Dissimilarity and the Configuration together to " "@@Dissimilarity & Configuration: Draw Shepard diagram...|" "draw the Shepard diagram@.") PICTURE (4.0, 4.0, drawLetterRShepard) NORMAL (L"The following script summarizes:") CODE (L"select Dissimilarity R") CODE (L"plus Configuration R_monotone") CODE (L"Draw Shepard diagram...0 200 0 2.2 1 + yes") ENTRY (L"The (monotone) regression") NORMAL (L"Select the Dissimilarity and the Configuration together to " "@@Dissimilarity & Configuration: Draw regression (monotone mds)...|" "draw the monotone regression@ of distances on dissimilarities.") PICTURE (4.0, 4.0, drawLetterRRegression) NORMAL (L"The following script summarizes:") CODE (L"select Dissimilarity R") CODE (L"plus Configuration R_monotone") CODE (L"Draw monotone regresion... \"Primary approach\" 0 200 0 2.2 1 + yes") NORMAL (L"When you enter %noiseRange = 0 in the form for the letter #R, perfect " "reconstruction is possible. The Shepard diagram then will show " "a perfectly smooth monotonically increasing function.") ENTRY (L"Weighing the dissimilarities") NORMAL (L"When you can't have equal confidence in all the number in the " "Dissimilarity object, you can give different weights to these numbers by " "associating a @Weight object with the Dissimilarity object. " "An easy way to do this is to select the Dissimilarity object and first " "choose @@Dissimilarity: To Weight|To Weight@. Then you might change the " "individual weights in the Weight object with the @@TableOfReal: Set " "value...| Set value...@ command (remember: make %w__%ij_ = %w__%ji_).") NORMAL (L"The following script summarizes:") CODE (L"select Dissimilarity R") CODE (L"To Weight") CODE (L"! Change [i][j] and [j][i] cells in the Weight object") CODE (L"Set value... i j val") CODE (L"Set value... j i val") CODE (L"...") CODE (L"! now we can do a weighed analysis.") CODE (L"select Dissimilarity R") CODE (L"plus Weight R") CODE (L"To Configuration (monotone mds)... 2 \"Primary approach\" 0.00001 50 1") NORMAL (L"You can also query the @stress values with three objects selected. " "The following script summarizes:") CODE (L"select Dissimilarity R") CODE (L"plus Weight R") CODE (L"plus Configuration R_s_monotone") CODE (L"Get stress (monotone mds)... \"Primary approach\" \"Kruskals's " "stress-1\")") ENTRY (L"Using a start Configuration") NORMAL (L"You could also use a Configuration object as a starting " "configuration in the minimization process. " "Lets assume that you are not satisfied with the stress value from the " "Configuration object that you obtained in the previous analysis. " "You can than use this Configuration object as a " "starting point for further analysis:") NORMAL (L"The following script summarizes:") CODE (L"select Dissimilarity R") CODE (L"plus Configuration R_monotone") CODE (L"plus Weight R") CODE (L"To Configuration (monotone mds)... 2 \"Primary approach\" 0.00001 50 1") ENTRY (L"Multiple Dissimilarity's (INDSCAL)") NORMAL (L"When you have multiple Dissimilarity objects you can also perform " "@@individual difference scaling@ (often called @@INDSCAL analysis@). ") NORMAL (L"As an example we can use an @@Create INDSCAL Carroll & Wish " "example...| example taken from Carrol & Wish@. " "Because INDSCAL only works on metrical data, we cannot use Dissimilarity " "objects directly. We have to transform them first @@Dissimilarity: To " "Distance...|to Distance@ objects.") NORMAL (L"This type of analysis on multiple objects results in two new objects: " "a Configuration and a @Salience.") MAN_END MAN_BEGIN (L"Procrustes", L"djmw", 20010927) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Procrustes represents the special @@AffineTransform|" "affine transform@ that consists of a " "combination of a translation, a shape preserving transformation and a scaling (this scaling is often called %dilation). " "Because the transformation has to be shape preserving, only a combination of a rotation and a reflection is allowed. " "A configuration matrix #%X is transformed in the following way to a new configuration matrix #%Y: ") FORMULA (L"#%Y = %s #%X #%T+ #1#%t',") NORMAL (L"where %s is the scaling factor, #%T is the shape preserving transformation matrix, #%t is the translation vector, " "and #1 is the vector with only ones as its elements.") NORMAL (L"For more information about the Procrustes transform and its algorithm " "see chapter 19 in @@Borg & Groenen (1997)@.") MAN_END MAN_BEGIN (L"Procrustes transform", L"djmw", 19980119) INTRO (L"A transformation that only uses a combination of a translation, " "a scaling and a rigid transformation to transform one Configuration such that it " "matches as closely as possible another Configuration. ") NORMAL (L"We speak of %%orthogonal Procrustes transform% when only the rigid " "transformation is allowed but no scaling or translation.") NORMAL (L"For more information about the Procrustes transform and its algorithm " "see chapter 19 in @@Borg & Groenen (1997)@.") MAN_END MAN_BEGIN (L"Proximity", L"djmw", 19961008) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type #Proximity represents proximities between objects.") ENTRY (L"Inside a Proximity") NORMAL (L"With @Inspect you will see the following attributes:") TAG (L"%numberOfRows, %numberOfColumns") DEFINITION (L"the number of objects (%numberOfRows and %numberOfColumns are " "equal and \\>_1).") TAG (L"%rowLabels, %columnLabels") DEFINITION (L"the names associated with the objects (%rowLabels and " "%columnLabels are equal.") TAG (L"%data [1..%numberOfRows][1..%numberOfColumns]") DEFINITION (L"the proximities between the objects.") MAN_END MAN_BEGIN (L"Salience", L"djmw", 19980112) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"Elements %s__%ij_ in the " "Salience matrix represent the importance of dimension %j (in the " "@Configuration) for data source %i.") ENTRY (L"Commands") NORMAL (L"Creation, as a by-product of:") LIST_ITEM (L"\\bu @@Distance: To Configuration (indscal)...") LIST_ITEM (L"\\bu @@Distance: To Configuration (ytl)...") MAN_END MAN_BEGIN (L"ScalarProduct", L"djmw", 19980125) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type ScalarProduct represents scalar products %b__%ij_ " "between objects %i and %j in a metrical space.") FORMULA (L"%b__%ij_ = \\su__%k=1..%numberOfDimensions_ %x__%ik_%x__%jk_,") NORMAL (L"where %x__%ik_ and %x__%jk_ are the coordinates of the %k-th " "dimension of points %i and %j, respectively. From this definition one " "can see that scalar products, in contrast to distances, " "do change when the origin is shifted.") NORMAL (L"Creation") LIST_ITEM (L"\\bu @@Distance: To ScalarProduct...@") MAN_END MAN_BEGIN (L"Similarity", L"djmw", 19961008) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Similarity represent a one-way " "table of similarities between \"objects\".") ENTRY (L"Commands") NORMAL (L"Creation") LIST_ITEM (L"\\bu @@Confusion: To Similarity...") NORMAL (L"Drawing") LIST_ITEM (L"\\bu ##Draw as numbers...") LIST_ITEM (L"\\bu ##Draw as squares...") NORMAL (L"Query") LIST_ITEM (L"\\bu ##Get column mean (index)...") LIST_ITEM (L"\\bu ##Get column mean (label)...") LIST_ITEM (L"\\bu ##Get column stdev (index)...") LIST_ITEM (L"\\bu ##Get column stdev (label)...") NORMAL (L"Modification") LIST_ITEM (L"\\bu ##Formula...") LIST_ITEM (L"\\bu ##Remove column (index)...") LIST_ITEM (L"\\bu ##Insert column (index)...") LIST_ITEM (L"\\bu ##Set row label (index)...") LIST_ITEM (L"\\bu ##Set row label (label)...") LIST_ITEM (L"\\bu ##Set column label (index)...") LIST_ITEM (L"\\bu ##Set column label (label)...") NORMAL (L"Analysis") LIST_ITEM (L"\\bu @@Similarity: To Dissimilarity...") MAN_END MAN_BEGIN (L"Similarity: To Dissimilarity...", L"djmw", 20040407) INTRO (L"A command that creates a @Dissimilarity from every selected " "@Similarity.") ENTRY (L"Setting") TAG (L"##Maximum dissimilarity") DEFINITION (L"determines the maximum dissimilarity possible. When the default " "value, 0.0, is chchosen%maximumDissimilarity " "is calculated as the maximum element in the Similarity object.") ENTRY (L"Algorithm") NORMAL (L"To obtain dissimilarities we 'reverse' similarities:") FORMULA (L"%%dissimilarity__%ij_ = %maximumDissimilarity \\-- %similarity__%ij_") NORMAL (L"In this way the order of dissimilarities is the reverse of the order " "of the similarities.") MAN_END MAN_BEGIN (L"smacof", L"djmw", 19980119) INTRO (L"Scaling by Majorizing a Complicated Function, the iterative algorithm " "to find an optimal Configuration.") LIST_ITEM (L"1. Initialize") LIST_ITEM (L" 1.a. Get initial Configuration #Z") LIST_ITEM (L" 1.b. Set stress %\\si__%n_^^[0]^ to a very large value.") LIST_ITEM (L" 1.c. Set iteration counter %k = 0") LIST_ITEM (L"2. Increase iteration counter by one: %k = %k + 1") LIST_ITEM (L"3. Calculate distances %d__%ij_(#Z).") LIST_ITEM (L"4. Transform dissimilarities %\\de__%ij_ into disparities " "%d\\'p__%ij_.") LIST_ITEM (L"5. Standardize the disparities so that %\\et__%d\\'p_^2 = " "%n(%n\\--1)/2.") LIST_ITEM (L"6. Compute the Guttman transform #X^^[%k]^ of #Z.") LIST_ITEM (L"7. Compute new distances %d__%ij_(#X^^[%k]^).") LIST_ITEM (L"8. Compute normalized stress %\\si__%n_ (#d\\'p, #X^^[%k]^)") LIST_ITEM (L"9. If |%\\si__%n_^^[%k]^ \\-- %\\si__%n_^^[%k\\--1]^| / %\\si__%n_" "^^[%k\\--1]^ < %\\ep or %k > %maximumNumberOfIterations, then stop") LIST_ITEM (L"10. Set #Z = #X^^[%k]^, and go to 2.") NORMAL (L"This algorithm goes back to @@De Leeuw (1977)@.") MAN_END MAN_BEGIN (L"spline", L"djmw", 20070108) INTRO (L"A spline function %f is a piecewise polynomial function defined on " "an interval [%x__%min_, %x__%max_] " "with specified continuity constraints, i.e., when the interval [%x__%min_," " %x__%max_] is subdivided by points %\\xi__%i_ such that %x__%min_ = " "%\\xi__%1_ < ... < %\\xi__%q_ = %%x__%max_, then within each subinterval " "[%\\xi__%j_, %\\xi__%j+1_) the function is a polynomial %P__%j_ of " "specified order %k.") NORMAL (L"A %%knot sequence% %t = {%t__1_, ..., %t__%n+%k_}, where %n is the " "number of free parameters that specify the spline function, is derived " "from the %\\xi__%i_ by placing knots at the boundary values %\\xi__%i_ " "according to the order of continuity at that boundary. The most common " "continuity characteristics imposed on %f request that for adjacent " "polynomials the derivatives up to order %k\\--2 match. For example, " "the knot sequence of a spline of order %k for a partition of [%x__%min_," " %%x__%max_] into three intervals (%q = 4) will be %t__1_ = ... = " "%t__%k_ = %x__%min_ (=%\\xi__1_), %t__%k+1_ = %\\xi__2_, %t__%k+2_ = " "%\\xi__3_ , %t__%k+3_ = ... = %t__%k+%k+2_ = %x__%max_ (= %\\xi__4_). " "This is called a %simple knot sequence, because all interior knots are " "simple. The number of free parameters %n for this case obeys a simple " "formula:") FORMULA (L"%n = %numberOfInteriorKnots + %order.") NORMAL (L"With suitable basis functions, for example, the M-spline family " "%M__%i_(%x|%k, %t), %i=1..%n, we can write any spline %f in the form:") FORMULA (L"%f = \\su__%i=1..%n_ %a__%i_%M__%i_,") NORMAL (L"where the %M__%i_ are defined by the following recursive formula's:") FORMULA (L"%M__%i_(%x|1,%t) = 1 / (%t__%i+1_ \\-- %t__%i_), %t__%i_ " "\\<_ %x < %t__%i+1_, 0 otherwise") FORMULA (L"%M__%i_(%x|%k,%t) = %k [(%x\\--%t__%i_)%M__%i_(%x|%k\\--1,%t) + " "(%t__%i+%k_\\--%x)%M__%i+1_(%x|%k\\--1,%t)] / " "((%k\\--1)(%t__%i+%k_\\--%t__%i_))") NORMAL (L"These %M__%i_ are localized because %M__%i_(%x|%k,%t) > 0 only when " "%t__%i_ \\<_ %x < %t__%i+%k_ and zero otherwise. Also, we have \\in" " M__%i_(%x)%dx = 1. Because of this localization a change in coefficient " "%a__%i_ will only effect %f within this interval.") NORMAL (L"The following picture shows an M-spline of order 3 on the interval " "[0, 1], with three interior knots at 0.3, 0.5 and 0.6.") PICTURE (5.0, 5.0, drawMsplineExample) NORMAL (L"Because the M-splines are nonnegative, %monotone splines% can be " "derived from them by %integration:") FORMULA (L"%I__%i_(%x|%k,%t) = \\in__%xmin_^%x %M__%i_(%u|%k,%t) %du") NORMAL (L"Because each %M__%i_(%x|%k, %t) is a piecewise polynomial of degree" " %k\\--1, each %I__%i_ will be of degree %k. Now we can write:") FORMULA (L"%f = \\su__%i=1..%n_ %b__%i_%I__%i_(%x|%k,%t)") NORMAL (L"We can use an M-spline of order %k+1 with a simple knot sequence %t, " "for which %t__%j_ \\<_ x < %t__%j+1_, to put " "the I-spline of order %k into a more convenient form:") FORMULA (L"%I__%i_(%x|%k,%t) = 0, %i > %j") FORMULA (L"%I__%i_(%x|%k,%t) = \\su__%m=%i+1..%j_ (%t__%m+%k+1_\\--" "%t__%m_)%M__%m_(%x|%k+1,%t)/(%k+1), %j\\--%k \\<_ %i \\<_ %j") FORMULA (L"%I__%i_(%x|%k,%t) = 1, %i < %j\\--%k") NORMAL (L"The following figure shows the I-splines that were derived from " "the M-splines above.") PICTURE (5.0, 5.0, drawIsplineExample) NORMAL (L"These spline formula's were taken from @@Ramsay (1988)@ and the " "errors in his I-spline formulas were corrected.") MAN_END MAN_BEGIN (L"stress", L"djmw", 19980108) INTRO (L"A badness-of-fit measure for the entire MDS representation.") NORMAL (L"Several measures exist.") ENTRY (L"Raw stress") FORMULA (L"%\\si__%r_ (#d\\'p, #X) = \\su__%i<%j_ %w__%ij_(%d\\'p__%ij_ \\-- " "%d__%ij_(#X))^2") FORMULA (L"= \\su__%i<%j_ %w__%ij_%d\\'p__%ij_^2 + \\su__%i<%j_ " "%w__%ij_%d__%ij_^2(#X) \\-- " "2 \\su__%i<%j_ %w__%ij_%d\\'p__%ij_%d__%ij_(#X)") FORMULA (L"= %\\et__%d\\'p_^2 + %\\et^2(#X) \\-- 2%\\ro(#d\\'p, #X)") NORMAL (L"where the %d\\'p__%ij_ are the @disparities that are the result " "from the transformation of the dissimilarities, i.e., %f(%\\de__%ij_). " "Raw stress can be misleading because it is dependent on the normalization " "of the disparities. The following measure tries to circumvent this " "inconvenience.") ENTRY (L"Normalized stress") FORMULA (L"%\\si__%n_ = \\si__%r_ / %\\et__%d\\'p_^2") NORMAL (L"This is the stress function that we minimize by iterative " "majorization. It goes back to @@De Leeuw (1977)@.") ENTRY (L"Kruskal's stress-1") FORMULA (L"%\\si__1_ = \\Vr (\\su__%i<%j_ %w__%ij_(%d\\'p__%ij_ \\-- " "%d__%ij_(#X))^2 / \\su__%i<%j_ %w__%ij_%d__%ij_^2(#X))^^1/2^") NORMAL (L"In this measure, which is due to @@Kruskal (1964)@, stress is " "expressed in relation to the size of #X.") ENTRY (L"Kruskal's stress-2") FORMULA (L"%\\si__2_ = \\Vr (\\su__%i<%j_ %w__%ij_(%d\\'p__%ij_ \\-- " "%d__%ij_(#X))^2 / \\su__%i<%j_ %w__%ij_(%d__%ij_(#X) - " "%averageDistance)^2)^^1/2^.") NORMAL (L"In general, this measure results in a stress value that is " "approximately twice the value for stress-1.") ENTRY (L"Relation between %\\si__1_ and %\\si__n_") NORMAL (L"When we have calculated %\\si__%n_ for Configuration #X, " "disparities #d\\'p and Weight #W we cannot " "directly use #X, #d\\'p and #W to calculate %\\si__1_ because the " "scale of #X is not necessarily optimal " "for %\\si__1_. We allow therefore a scale factor %b > 0 and " "try to calculate %\\si__1_ (#d\\'p, %b #X). We minimize the resulting " "expression for %b and substitute " "the result back into the formula for stress, i.e.,") FORMULA (L"%\\si__1_^2 (#d\\'p, %b #X) = (%\\et__%d\\'p_^2 + %b^2 %\\et^2(#X) " "\\-- 2 %b %\\ro(#d\\'p, #X)) / %b^2 %\\et^2(#X)") FORMULA (L"d%\\si__1_^2 (%b) / d%b == 0, gives") FORMULA (L"%b = %\\et__%d\\'p_^2 / %\\ro") FORMULA (L"%\\si__1_^2 = (1 - %\\ro^2 / (%\\et__%d\\'p_^2\\.c%\\et^2(#X)))") NORMAL (L"This means that %\\si__1_ = \\Vr %\\si__%n_.") ENTRY (L"Relation between %\\si__2_ and %\\si__n_") NORMAL (L"We can do the same trick as before for %\\si__2_:") FORMULA (L"%\\si__2_^2 (#d\\'p, %b #X) = (%\\et__%d\\'p_^2 + %b^2 %\\et^2(#X) " "\\-- 2 %b %\\ro(#d\\'p, #X)) / " "(%b^2 \\su__%i<%j_ %w__%ij_(%d__%ij_(#X) - %averageDistance)^2)") NORMAL (L"From which we derive:") FORMULA (L"%\\si__2_ = \\Vr ((%\\et__%d\\'p_^2 \\.c %\\et^2(#X) - " "%\\ro^2(#d\\'p, #X)) / (%\\et__%d\\'p_^2 \\.c \\su__%i<%j_ " "%w__%ij_(%d__%ij_(#X) - %averageDistance)^2))") MAN_END MAN_BEGIN (L"TableOfReal: Centre columns", L"djmw", 19980422) INTRO (L"A command that centres the columns in the selected @TableOfReal " "objects.") ENTRY (L"Algorithm") NORMAL (L"The new values in the table, %x\\'p__%ij_, will be:") FORMULA (L"%x\\'p__%ij_ = %x__%ij_ \\-- %x__\\.c%j_,") NORMAL (L"where") FORMULA (L"%x__\\.c%j_ = \\su__%i=1..%numberOfRows_ %x__%ij_ / %numberOfRows,") NORMAL (L"the average of column %j.") MAN_END MAN_BEGIN (L"TableOfReal: Centre rows", L"djmw", 19980422) INTRO (L"A command that centres the rows in the selected @TableOfReal objects.") ENTRY (L"Algorithm") NORMAL (L"The new values in the table, %x\\'p__%ij_, will be:") FORMULA (L"%x\\'p__%ij_ = %x__%ij_ \\-- %x__%i\\.c_,") NORMAL (L"where") FORMULA (L"%x__%i\\.c_ = \\su__%j=1..%numberOfColumns_ %x__%ij_ / " "%numberOfColumns,") NORMAL (L"the average of row %i.") MAN_END MAN_BEGIN (L"TableOfReal: Get table norm", L"djmw", 19980422) INTRO (L"A command that returns the norm of the selected @TableOfReal object.") ENTRY (L"Algorithm") NORMAL (L"Returns: sqrt (\\su__%i=1..%numberOfRows_ \\su__%j=1..%numberOfColumns" "_ %x__%ij_^2).") MAN_END MAN_BEGIN (L"TableOfReal: Normalize columns...", L"djmw", 19980422) INTRO (L"A command that normalizes the columns in the selected @TableOfReal " "objects.") ENTRY (L"Setting") TAG (L"##Norm") DEFINITION (L"determines the sum of the squared elements in each column after " "normalization.") ENTRY (L"Algorithm") NORMAL (L"All elements %x__%ij_ in each column %j=1..%numberOfColumns will be " "multiplied by sqrt (%norm / \\su__%i=1..%numberOfRows_ %x__%ij_^2).") MAN_END MAN_BEGIN (L"TableOfReal: Normalize rows...", L"djmw", 19980422) INTRO (L"A command that normalizes the rows in the selected @TableOfReal " "objects.") ENTRY (L"Setting") TAG (L"##Norm") DEFINITION (L"determines the sum of the squared elements in each row after " "normalization.") ENTRY (L"Algorithm") NORMAL (L"All elements %x__%ij_ in each row %i=1..%numberOfRows will be " "multiplied by sqrt (%norm / \\su__%j=1..%numberOfColumns_ %x__%ij_^2).") MAN_END MAN_BEGIN (L"TableOfReal: Normalize table...", L"djmw", 19980422) INTRO (L"A command that normalizes the elements in the selected @TableOfReal " "objects.") ENTRY (L"Setting") TAG (L"##Norm") DEFINITION (L"determines the sum of the squared elements after normalization.") ENTRY (L"Algorithm") NORMAL (L"All elements %x__%ij_ will be multiplied by " "sqrt (%norm / \\su__%i=1..%numberOfRows_ \\su__%j=1..%numberOfColumns_" " %x__%ij_^2.") MAN_END MAN_BEGIN (L"Weight", L"djmw", 19980108) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"An object of type Weight represents a matrix " "with weights %w__%ij_.") NORMAL (L"An object of type Weight selected together with an onject of type" " @Dissimilarity can be used to make distinctions in the importance of the" " contribution of each individual dissimilarity %\\de__%ij_ to " "@stress and therefore to the final configuration. Weights can be " "used for instance to code for missing values, i.e., take %w__%ij_ = 0 if " "dissimilarity %\\de__%ij_ is missing and %w__%ij_ = 1 if %\\de__%ij_ is" " known.") ENTRY (L"Commands") NORMAL (L"Creation") LIST_ITEM (L"\\bu @@Dissimilarity: To Weight") NORMAL (L"Analysis") NORMAL (L"See @@Dissimilarity & Weight: To Configuration...@ for help on the " "following analysis items: ") LIST_ITEM (L"\\bu ##Dissimilarity & Weight: To Configuration (monotone mds)...") LIST_ITEM (L"\\bu ##Dissimilarity & Weight: To Configuration (i-spline mds)...") LIST_ITEM (L"\\bu ##Dissimilarity & Weight: To Configuration (interval mds)...") LIST_ITEM (L"\\bu ##Dissimilarity & Weight: To Configuration (ratio mds)...") LIST_ITEM (L"\\bu ##Dissimilarity & Weight: To Configuration (absolute mds)...") NORMAL (L"Query") NORMAL (L"See @@Dissimilarity & Configuration & Weight: Get stress...@ for help " "on the following query items: ") LIST_ITEM (L"\\bu ##Dissimilarity & Configuration & Weight: Get stress " "(monotone mds)...") LIST_ITEM (L"\\bu ##Dissimilarity & Configuration & Weight: Get stress " "(i-spline mds)...") LIST_ITEM (L"\\bu ##Dissimilarity & Configuration & Weight: Get stress " "(interval mds)...") LIST_ITEM (L"\\bu ##Dissimilarity & Configuration & Weight: Get stress " "(ratio mds)...") LIST_ITEM (L"\\bu ##Dissimilarity & Configuration & Weight: Get stress " "(absolute mds)...") MAN_END /************ references ***********************************************/ MAN_BEGIN (L"Abramowitz & Stegun (1970)", L"djmw", 19971201) NORMAL (L"M. Abramowitz & I. Stegun (1970): %%Handbook of mathematical " "functions%. New York: Dover Publications.") MAN_END MAN_BEGIN (L"Borg & Groenen (1997)", L"djmw", 19971219) NORMAL (L"I. Borg & P. Groenen (1997): %%Modern multidimensional scaling: " "theory and applications%. Springer.") MAN_END MAN_BEGIN (L"Brokken (1983)", L"djmw", 19980406) NORMAL (L" F.B. Brokken (1983): \"Orthogonal Procrustes rotation maximizing " "congruence.\" %Psychometrika #48: 343\\--352.") MAN_END MAN_BEGIN (L"Cailliez (1983)", L"djmw", 19971201) NORMAL (L" F. Cailliez (1983): \"The analytical solution of the additive " "constant problem.\" %Psychometrika #48, 305-308.") MAN_END MAN_BEGIN (L"Carroll & Chang (1970)", L"djmw", 19971201) NORMAL (L"J.D. Carroll & J.-J. Chang, (1970): \"Analysis of Individual " "Differences in Multidimensional scaling via an N-way generalization of " "\"Eckart-Young\" Decomposition.\" %Psychometrika #35: 283\\--319.") MAN_END MAN_BEGIN (L"Carroll & Wish (1974)", L"djmw", 19971201) NORMAL (L"J.D. Carroll & M. Wish, (1974): \"Models and methods for three-way " "multidimensional scaling.\" In D.H. Krantz, R.C. Atkinson, R.D. Luce & " "P. Suppes (eds.): %%Contemporary developments in mathematical psychology: " "Vol. 2 Measurement, psychophysics, and neural " "information processing%, 283\\--319. New York: Academic Press.") MAN_END MAN_BEGIN (L"De Leeuw (1977)", L"djmw", 19971201) NORMAL (L"J. de Leeuw (1977): \"Applications of convex analysis to " "multidimensional scaling.\" In J.R. Barra, F. Brodeau, G. Romier & " "B. van Cutsem (eds.): %%Recent developments in statistics%. Amsterdam: " "North-Holland. 133\\--145.") MAN_END MAN_BEGIN (L"De Leeuw & Pruzansky (1978)", L"djmw", 19971201) NORMAL (L"J. de Leeuw & S. Pruzansky (1978): \"A new computational method to " "fit the weighted Euclidean distance model.\" %Psychometrika #43: 479\\--490.") MAN_END MAN_BEGIN (L"Gifi (1990)", L"djmw", 19971207) NORMAL (L"A. Gifi (1990): %%Nonlinear multivariate analysis%. John Wiley & " "Sons Ltd., reprint 1996.") MAN_END MAN_BEGIN (L"Golub & van Loan (1996)", L"djmw", 19971207) NORMAL (L"G. Golub & C. van Loan (1996): %%Matrix computations%. Third edition. " "London: The Johns Hopkins University Press.") // ?? MAN_END MAN_BEGIN (L"Green, Carmone & Smith (1989)", L"djmw", 19971201) NORMAL (L"P. Green, F. Carmone, S. Smith (1989): " "%%Multidimensional scaling: concepts and applications%. Section 3. Allyn and Bacon.") MAN_END MAN_BEGIN (L"Kaiser (1958)", L"djmw", 19980404) NORMAL (L" H.F. Kaiser (1958): \"The varimax criterion for analytic rotation " "in factor analysis.\" %Psychometrika #23: 187\\--200.") MAN_END MAN_BEGIN (L"Kiers & Groenen (1996)", L"djmw", 19971219) NORMAL (L"H.A.L. Kiers & P. Groenen (1996): \"A monotonically convergent " "algorithm for orthogonal congruence rotation.\" %Psychometrika #61: " "375\\--389.") MAN_END MAN_BEGIN (L"Klein, Plomp & Pols (1970)", L"djmw", 19971201) NORMAL (L" W. Klein, R. Plomp, & L.C.W. Pols (1970): \"Vowel Spectra, " "Vowel Spaces, and Vowel Identification.\" %%Journal of the Acoustical Society of America% #48: 999\\--1009.") MAN_END MAN_BEGIN (L"Kruskal (1964)", L"djmw", 19971201) NORMAL (L"J.B. Kruskal (1964): \"Nonmetric multidimensional scaling: a " "numerical method.\" %Psychometrika #29: 115\\--129.") MAN_END MAN_BEGIN (L"Ramsay (1988)", L"djmw", 19980106) NORMAL (L"J.O. Ramsay (1988): \"Monotone regression splines in action.\" " "%%Statistical Science% #3: 425\\--461.") MAN_END MAN_BEGIN (L"Stevens (1951)", L"djmw", 19971201) NORMAL (L"S.S. Stevens (1951): \"Mathematics, measurement, and psychophysics.\" " "In S.S. Stevens (ed.): %%Handbook of experimental psychology%. New York: " "Wiley.") MAN_END MAN_BEGIN (L"Takane, Young & de Leeuw (1976)", L"djmw", 19971201) NORMAL (L"Y. Takane, F. Young, J. de Leeuw (1976): \"Non-metric individual " "differences multidimensional scaling: an alternating least squares method " "with optimal scaling features.\" %Psychometrika #42: 7\\--67.") MAN_END MAN_BEGIN (L"Ten Berge (1995)", L"djmw", 19980404) NORMAL (L"J.M.F. ten Berge (1995): \"Suppressing permutations or rigid planar " "rotations: a remedy against nonoptimal varimax rotations.\" " "%Psychometrika #60, 437\\--446.") MAN_END MAN_BEGIN (L"Ten Berge, Kiers & Krijnen (1993)", L"djmw", 19971207) NORMAL (L"J.M.F. ten Berge, H.A.L. Kiers & W.P. Krijnen (1993): \"Computational " "solutions for the problem of negative saliences and nonsymmetry in " "INDSCAL.\" %%Journal of Classification% #10: 115\\--124.") MAN_END MAN_BEGIN (L"Torgerson (1958)", L"djmw", 19971201) NORMAL (L"W.S. Torgerson (1958): %%Theory and methods of scaling%. New York: Wiley.") MAN_END MAN_BEGIN (L"Young, Takane & Lewyckyj (1978)", L"djmw", 19971201) NORMAL (L"F.W. Young, Y. Takane & R. Lewyckyj (1978): " "\"Three notes on ALSCAL.\" %Psychometrika #43: 433\\--435.") MAN_END MAN_BEGIN (L"Weller & Romney (1990)", L"djmw", 19971216) NORMAL (L"S.C. Weller & A.K. Romney (1990): %%Metric Scaling: " "correspondence analysis%. Sage University Paper Series on Quantitative " "Applications in the Social Sciences 07-075. Newbury Park, CA: Sage.") MAN_END } /* End of file manual_MDS.cpp */ sources_5316/dwtools/TableOfReal_and_Permutation.cpp0000644000176700017670000000345311606610672021465 0ustar paulpaul/* TableOfReal_and_Permutation.cpp * * Copyright (C) 2005-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20050708 */ #include "TableOfReal_and_Permutation.h" #include "TableOfReal_extensions.h" #include "NUM2.h" TableOfReal TableOfReal_and_Permutation_permuteRows (I, Permutation thee) { iam (TableOfReal); try { if (my numberOfRows != thy numberOfElements) { Melder_throw (L"The number of rows in the table and the number of elements in the Permutation must be equal."); } autoTableOfReal him = TableOfReal_create (my numberOfRows, my numberOfColumns); for (long i = 1; i <= thy numberOfElements; i++) { TableOfReal_copyOneRowWithLabel (me, him.peek(), thy p[i], i); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not permuted."); } } Permutation TableOfReal_to_Permutation_sortRowLabels (I) { iam (TableOfReal); try { autoPermutation thee = Permutation_create (my numberOfRows); NUMindexx_s (my rowLabels, my numberOfRows, thy p); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Permutation created."); } } /* End of file TableOfReal_and_Permutation.cpp */ sources_5316/dwtools/MelFilter_and_MFCC.h0000644000176700017670000000445311627242567017106 0ustar paulpaul#ifndef _MelFilter_and_MFCC_h_ #define _MelFilter_and_MFCC_h_ /* MelFilter_and_MFCC.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2001 djmw 20020813 GPL header djmw 20110307 Latest modification */ #include "FilterBank.h" #include "MFCC.h" /* Three slightly "different" definitions of MFCC 1. Davis & Mermelstein MFCC[i] = SUM (j=1..N, f[j] * cos (i(j-1/2)pi/N)), i=1..N-1 2. Vergin & O'Shaughnessy MFCC[i] = SUM (j=0..N-1, f[j] * cos (i(j+1/2)pi/N)), i = 0..N-1 3. HTK-book MFCC[i] = sqrt(2/n) SUM (j=1..N, f[j] * cos (i(j-1/2)pi/N)) i = 0..N-1 The f[j]'s are the filterbank outputs in dB. We follow the definition of Davis and Mermelstein: MFCC[i] = SUM (j=1..N, f[j] * cos (i(j-1/2)pi/N)), i=1..N-1, however, we also calculate the zero coefficient as MFCC[0] = SUM (j=1..N, f[j]) / N. The pure cosine transform MFCC[0] would be the sum instead of the average. This average is more convenient in the inverse transform (from MFCC to MelFilter). */ MFCC MelFilter_to_MFCC (MelFilter me, long numberOfCoefficients); /* Calculates the Cosine Transform of the filterbank values (See Numerical Recipes in C, Chapter 12.3): F[k] = SUM (j=1..N, f[j] * cos (pi * k * (j - 1/2) / N)). The zeroth cepstral coefficient (F[0]) has been modified to represent the average filterbank output instead of the sum of these outputs. */ MelFilter MFCC_to_MelFilter (MFCC me, long firstCoefficient, long lastCoefficient, double f1_mel, double df_mel); /* Calculates the Inverse CT of cepstral coefficients: f[j] = c0+1/N * SUM (k=1..N, F[k] * cos (pi * k * (j - 1/2) / N)), */ #endif /* MelFilter_and_MFCC.h */ sources_5316/dwtools/KlattGrid.h0000644000176700017670000002727111630404722015464 0ustar paulpaul#ifndef _KlattGrid_h_ #define _KlattGrid_h_ /* KlattGrid.h * * Copyright (C) 2008-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * djmw 20080917 Initial version * djmw 20110306 Latest modification */ #include "Collection.h" #include "PointProcess.h" #include "Sound.h" #include "IntensityTier.h" #include "PitchTier.h" #include "FormantGrid.h" #include "KlattTable.h" #include "Interpreter_decl.h" #include "KlattGrid_def.h" oo_CLASS_CREATE (PhonationPoint, Data); oo_CLASS_CREATE (PhonationTier, Function); oo_CLASS_CREATE (PhonationGridPlayOptions, Data); oo_CLASS_CREATE (PhonationGrid, Function); oo_CLASS_CREATE (VocalTractGridPlayOptions, Data); oo_CLASS_CREATE (VocalTractGrid, Function); oo_CLASS_CREATE (CouplingGridPlayOptions, Data); oo_CLASS_CREATE (CouplingGrid, Function); oo_CLASS_CREATE (FricationGridPlayOptions, Data); oo_CLASS_CREATE (FricationGrid, Function); oo_CLASS_CREATE (KlattGridPlayOptions, Data); oo_CLASS_CREATE (KlattGrid, Function); /******************** PhonationPoint & Tier ************************************/ PhonationPoint PhonationPoint_create (double time, double period, double openPhase, double collisionPhase, double te, double power1, double power2, double pulseScale); PhonationTier PhonationTier_create (double tmin, double tmax); PointProcess PhonationTier_to_PointProcess_closures (PhonationTier me); /************************ PhonationGrid *********************************************/ PhonationGrid PhonationGrid_create (double tmin, double tmax); PhonationGridPlayOptions PhonationGridPlayOptions_create (); void PhonationGrid_setNames (PhonationGrid me); Sound PhonationGrid_to_Sound_aspiration (PhonationGrid me, double samplingFrequency); void PhonationGrid_draw (PhonationGrid me, Graphics g); double PhonationGrid_getMaximumPeriod (PhonationGrid me); PhonationTier PhonationGrid_to_PhonationTier (PhonationGrid me); /************************ VocalTractGrid *********************************************/ VocalTractGrid VocalTractGrid_create (double tmin, double tmax, long numberOfFormants, long numberOfNasalFormants, long numberOfNasalAntiFormants); VocalTractGridPlayOptions VocalTractGridPlayOptions_create (); void VocalTractGrid_setNames (VocalTractGrid me); void VocalTractGrid_draw (VocalTractGrid me, Graphics g, int filterModel); /************************ CouplingGrid *********************************************/ CouplingGrid CouplingGrid_create (double tmin, double tmax, long numberOfTrachealFormants, long numberOfTrachealAntiFormants, long numberOfDeltaFormants); CouplingGridPlayOptions CouplingGridPlayOptions_create (); void CouplingGrid_setNames (CouplingGrid me); double CouplingGrid_getDeltaFormantAtTime (CouplingGrid me, long iformant, double t); double CouplingGrid_getDeltaBandwidthAtTime (CouplingGrid me, long iformant, double t); /********************** FormantGrid & CouplingGrid *************************************/ void FormantGrid_CouplingGrid_updateOpenPhases (FormantGrid me, CouplingGrid thee); /********************** Sound & FormantGrid (& IntensityTier) *************************************/ void Sound_FormantGrid_filterWithOneFormant_inline (Sound me, FormantGrid thee, long iformant); void Sound_FormantGrid_filterWithOneAntiFormant_inline (Sound me, FormantGrid thee, long iformant); void Sound_FormantGrid_Intensities_filterWithOneFormant_inline (Sound me, FormantGrid thee, Ordered amplitudes, long iformant); Sound Sound_FormantGrid_Intensities_filter (Sound me, FormantGrid thee, Ordered amplitudes, long iformantb, long iformante, int alternatingSign); /************************ FricationGrid *********************************************/ FricationGrid FricationGrid_create (double tmin, double tmax, long numberOfFormants); FricationGridPlayOptions FricationGridPlayOptions_create (); void FricationGrid_setNames (FricationGrid me); void FricationGrid_draw (FricationGrid me, Graphics g); Sound FricationGrid_to_Sound (FricationGrid me, double samplingFrequency); Sound Sound_FricationGrid_filter (Sound me, FricationGrid thee); /************************ Sound & VocalTractGrid & CouplingGrid *********************************************/ Sound Sound_VocalTractGrid_CouplingGrid_filter (Sound me, VocalTractGrid thee, CouplingGrid coupling); /************************ KlattGrid *********************************************/ KlattGrid KlattGrid_create (double tmin, double tmax, long numberOfFormants, long numberOfNasalFormants, long numberOfNasalAntiFormants, long numberOfTrachealFormants, long numberOfTrachealAntiFormants, long numberOfFricationFormants, long numberOfDeltaFormants); KlattGrid KlattGrid_createExample (); KlattGridPlayOptions KlattGridPlayOptions_create (); void KlattGrid_setNames (KlattGrid me); KlattGrid KlattTable_to_KlattGrid (KlattTable me, double frameDuration); void KlattGrid_draw (KlattGrid me, Graphics g, int filterModel); void klattGrid_drawPhonation (KlattGrid me, Graphics g); void KlattGrid_drawVocalTract (KlattGrid me, Graphics g, int filterModel, int withTrachea); #define KlattGrid_FILTER_CASCADE 0 #define KlattGrid_FILTER_PARALLEL 1 #define KlattGrid_ORAL_FORMANTS 1 #define KlattGrid_NASAL_FORMANTS 2 #define KlattGrid_FRICATION_FORMANTS 3 #define KlattGrid_TRACHEAL_FORMANTS 4 #define KlattGrid_NASAL_ANTIFORMANTS 5 #define KlattGrid_TRACHEAL_ANTIFORMANTS 6 #define KlattGrid_DELTA_FORMANTS 7 // Add, Remove, Extract, Replace from PhonationGrid #define PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO(Name,tierType) \ double KlattGrid_get##Name##AtTime (KlattGrid me, double t); \ void KlattGrid_add##Name##Point (KlattGrid me, double t, double value); \ void KlattGrid_remove##Name##Points (KlattGrid me, double t1, double t2); \ tierType KlattGrid_extract##Name##Tier (KlattGrid me); \ void KlattGrid_replace##Name##Tier (KlattGrid me, tierType thee); // Generate 55 prototypes PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (Pitch, PitchTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (Flutter, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (DoublePulsing, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (OpenPhase, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (CollisionPhase, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (SpectralTilt, IntensityTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (Power1, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (Power2, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (VoicingAmplitude, IntensityTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (AspirationAmplitude, IntensityTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE_PROTO (BreathinessAmplitude, IntensityTier) #define KlattGrid_QUERY_ADD_REMOVE_PROTO(Name) \ double KlattGrid_get##Name##AtTime (KlattGrid me, int formantType, long iformant, double t); \ void KlattGrid_add##Name##Point (KlattGrid me, int formantType, long iformant, double t, double value); \ void KlattGrid_remove##Name##Points (KlattGrid me, int formantType, long iformant, double t1, double t2); \ double KlattGrid_getDelta##Name##AtTime (KlattGrid me, long iformant, double t); \ void KlattGrid_addDelta##Name##Point (KlattGrid me, long iformant, double t, double value); \ void KlattGrid_removeDelta##Name##Points (KlattGrid me, long iformant, double t1, double t2); // 12 prototypes KlattGrid_QUERY_ADD_REMOVE_PROTO(Formant) KlattGrid_QUERY_ADD_REMOVE_PROTO(Bandwidth) void KlattGrid_formula_frequencies (KlattGrid me, int formantType, const wchar_t *expression, Interpreter interpreter); void KlattGrid_formula_bandwidths (KlattGrid me, int formantType, const wchar_t *expression, Interpreter interpreter); void KlattGrid_formula_amplitudes (KlattGrid me, int formantType, const wchar_t *expression, Interpreter interpreter); FormantGrid KlattGrid_extractFormantGrid (KlattGrid me, int formantType); void KlattGrid_replaceFormantGrid (KlattGrid me, int formantType, FormantGrid thee); FormantGrid KlattGrid_extractDeltaFormantGrid (KlattGrid me); void KlattGrid_replaceDeltaFormantGrid (KlattGrid me, FormantGrid thee); FormantGrid KlattGrid_to_oralFormantGrid_openPhases (KlattGrid me, double fadeFraction); PointProcess KlattGrid_extractPointProcess_glottalClosures (KlattGrid me); double KlattGrid_getAmplitudeAtTime (KlattGrid me, int formantType, long iformant, double t); void KlattGrid_addAmplitudePoint (KlattGrid me, int formantType, long iformant, double t, double value); void KlattGrid_removeAmplitudePoints (KlattGrid me, int formantType, long iformant, double t1, double t2); IntensityTier KlattGrid_extractAmplitudeTier (KlattGrid me, int formantType, long iformant); void KlattGrid_replaceAmplitudeTier (KlattGrid me, int formantType, long iformant, IntensityTier thee); double KlattGrid_getFricationAmplitudeAtTime (KlattGrid me, double t); void KlattGrid_addFricationAmplitudePoint (KlattGrid me, double t, double value); void KlattGrid_removeFricationAmplitudePoints (KlattGrid me, double t1, double t2); IntensityTier KlattGrid_extractFricationAmplitudeTier (KlattGrid me); void KlattGrid_replaceFricationAmplitudeTier (KlattGrid me, IntensityTier thee); double KlattGrid_getFricationBypassAtTime (KlattGrid me, double t); void KlattGrid_addFricationBypassPoint (KlattGrid me, double t, double value); void KlattGrid_removeFricationBypassPoints (KlattGrid me, double t1, double t2); IntensityTier KlattGrid_extractFricationBypassTier (KlattGrid me); void KlattGrid_replaceFricationBypassTier (KlattGrid me, IntensityTier thee); void KlattGrid_setGlottisCoupling (KlattGrid me); FormantGrid * KlattGrid_getAddressOfFormantGrid (KlattGrid me, int formantType); Ordered * KlattGrid_getAddressOfAmplitudes (KlattGrid me, int formantType); // add/remove frequency + bandwidth (+amplitude) tiers void KlattGrid_addFormant (KlattGrid me,int formantType, long position); void KlattGrid_removeFormant (KlattGrid me,int formantType, long position); // add/remove frequency + bandwidth tiers void KlattGrid_addFormantAndBandwidthTier (KlattGrid me, int formantType, long position); void KlattGrid_removeFormantAndBandwidthTier (KlattGrid me, int formantType, long position); /***************** KlattGrid & Sound *************************************/ // reset PlayOptions to defaults void KlattGrid_play (KlattGrid me); // use playOptions void KlattGrid_playSpecial (KlattGrid me); void KlattGrid_setDefaultPlayOptions (KlattGrid me); Sound KlattGrid_to_Sound (KlattGrid me); Sound KlattGrid_to_Sound_phonation (KlattGrid me); int KlattGrid_synthesize (KlattGrid me, double t1, double t2, double samplingFrequency, double maximumPeriod); /* glottal: phonation+aspiration, before entering the filter frication: noise before entering the parallel frication filter section. */ Sound Sound_KlattGrid_filterByVocalTract (Sound me, KlattGrid thee, int filterModel); Sound Sound_KlattGrid_filter_frication (Sound me, KlattGrid thee); KlattGrid Sound_to_KlattGrid_simple (Sound me, double timeStep, long maximumNumberOfFormants, double maximumFormantFrequency, double windowLength, double preEmphasisFrequency, double minimumPitch, double maximumPitch, double minimumPitchIntensity, int subtractMean); #endif /* _KlattGrid_h_ */ sources_5316/dwtools/GaussianMixture_def.h0000644000176700017670000000222611627237663017554 0ustar paulpaul/* GaussianMixture_def.h * * Copyright (C) 2010 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT GaussianMixture oo_DEFINE_CLASS (GaussianMixture, Data) oo_LONG (numberOfComponents) oo_LONG (dimension) oo_DOUBLE_VECTOR (mixingProbabilities, numberOfComponents) oo_COLLECTION (Ordered, covariances, Covariance, 0) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS(GaussianMixture) #undef ooSTRUCT /* End of file GaussianMixture_def.h */ sources_5316/dwtools/TableOfReal_and_SVD.cpp0000644000176700017670000000610311725103641017600 0ustar paulpaul/* TableOfReal_and_SVD.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20021009 GPL header djmw 20031107 Added TablesOfReal_to_GSVD. djmw 20051202 Extract left/right singular vectors. */ #include "TableOfReal_and_SVD.h" #define MIN(m,n) ((m) < (n) ? (m) : (n)) TableOfReal SVD_to_TableOfReal (SVD me, long from, long to) { try { autoTableOfReal thee = TableOfReal_create (my numberOfRows, my numberOfColumns); SVD_synthesize (me, from, to, thy data); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no TableOfReal synthesized."); } } SVD TableOfReal_to_SVD (I) { iam (TableOfReal); try { autoSVD thee = SVD_create_d (my data, my numberOfRows, my numberOfColumns); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no SVD created."); } } TableOfReal SVD_extractLeftSingularVectors (I) { iam (SVD); try { long mn_min = MIN (my numberOfRows, my numberOfColumns); autoTableOfReal thee = TableOfReal_create (my numberOfRows, mn_min); NUMmatrix_copyElements (my u, thy data, 1, my numberOfRows, 1, mn_min); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": left singular vector not extracted."); } } TableOfReal SVD_extractRightSingularVectors (I) { iam (SVD); try { long mn_min = MIN (my numberOfRows, my numberOfColumns); autoTableOfReal thee = TableOfReal_create (my numberOfColumns, mn_min); NUMmatrix_copyElements (my v, thy data, 1, my numberOfColumns, 1, mn_min); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": right singular vector not extracted."); } } TableOfReal SVD_extractSingularValues (I) { iam (SVD); try { long mn_min = MIN (my numberOfRows, my numberOfColumns); autoTableOfReal thee = TableOfReal_create (1, mn_min); NUMvector_copyElements (my d, thy data[1], 1, mn_min); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": singular values not extracted."); } } GSVD TablesOfReal_to_GSVD (I, thou) { iam (TableOfReal); thouart (TableOfReal); try { if (my numberOfColumns != thy numberOfColumns) { Melder_throw ("Both tables must have the same number of columns."); } autoGSVD him = GSVD_create_d (my data, my numberOfRows, my numberOfColumns, thy data, thy numberOfRows); return him.transfer(); } catch (MelderError) { Melder_throw ("GSVD not constructed from TablesOfReal."); } } /* End of file SVD_and_TableOfReal.cpp */ sources_5316/dwtools/Eigen_and_Matrix.cpp0000644000176700017670000000427211606610672017331 0ustar paulpaul/* Eigen_and_Matrix.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 2002 djmw 20020813 GPL header */ #include "Eigen_and_Matrix.h" Matrix Eigen_and_Matrix_project (I, thou, long numberOfComponents) { try { iam (Eigen); thouart (Matrix); if (numberOfComponents == 0) { numberOfComponents = my numberOfEigenvalues; } autoMatrix him = Matrix_create (thy xmin, thy xmax, thy nx, thy dx, thy x1, 0.5, 0.5 + numberOfComponents, numberOfComponents, 1, 1); Matrix thim = him.peek(); Eigen_and_Matrix_project_into (me, thee, &thim); return him.transfer(); } catch (MelderError) { Melder_throw ("Projection Matrix not created."); } } void Eigen_and_Matrix_project_into (I, thou, Any void_pointer_to_him) { iam (Eigen); thouart (Matrix); Matrix him = * ( (Matrix *) void_pointer_to_him); if (my dimension != thy ny) Melder_throw ("The number of rows in the 'from' Matrix must equal the dimension of the eigenvector."); if (his nx != thy nx) { Melder_throw ("The number of columns in the Matrixes must be equal."); } if (his ny > my numberOfEigenvalues) Melder_throw ("The number of rows in the 'to' Matrix cannot exceed the number of eigenvectors."); for (long i = 1; i <= thy nx; i++) { for (long j = 1; j <= his ny; j++) { double r = 0; for (long k = 1; k <= my dimension; k++) { // eigenvector in row, data in column r += my eigenvectors[j][k] * thy z[k][i]; } his z[j][i] = r; } } } /* End of file Eigen_and_Matrix.cpp */ sources_5316/dwtools/manual_KlattGrid.cpp0000644000176700017670000003125011630135436017347 0ustar paulpaul/* manual_KlattGrid.cpp * * Copyright (C) 2009-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" void manual_KlattGrid (ManPages me); void manual_KlattGrid (ManPages me) { MAN_BEGIN (L"KlattGrid", L"djmw", 20091119) INTRO (L"A KlattGrid represents the source-filter model as a function of time. It consists of a number of tiers that model aspects of the source and the filter, and the interaction between source and filter. The KlattGrid implements a superset of the speech synthesizer described in figure 14 in the @@Klatt & Klatt (1990)@ article.") NORMAL (L"The following drawing represents a cascade synthesizer with six oral formants, one nasal formant, " "one nasal antiformant, one tracheal formant, one tracheal antiformant and six frication formants. ") SCRIPT (7.0, 6.5, L"Create KlattGrid... kg 0 1 6 1 1 6 1 1 1\n" "Draw synthesizer... Cascade\n" "Remove\n") NORMAL (L"In the next picture a parallel synthesizer branch is used instead of the cascade one.") SCRIPT (7.0, 6.5, L"Create KlattGrid... kg 0 1 6 1 1 6 1 1 1\n" "Draw synthesizer... Parallel\n" "Remove\n") NORMAL (L"All parameters in the synthesizer are represented by separate tiers.") ENTRY (L"The source") NORMAL (L"The source is modelled by the following tiers:") TAG (L"##Pitch") DEFINITION (L"models fundamental frequency (in Hertz).") TAG (L"##Flutter") DEFINITION (L"models a kind of \"random\" variation of the pitch (with a number between zero and one). ") TAG (L"##Voicing amplitude") DEFINITION (L"models the maximum amplitude of the glottal flow (in dB SPL).") TAG (L"##Open phase") DEFINITION (L"models the open phase of the glottis (with a number between zero and one). If the tier is empty a default of 0.7 " "will be used.") TAG (L"##Power1#, ##Power2#") DEFINITION (L"model the form of the glottal flow function flow(%t)=%t^^%%power1%^-%t^^%%power2%^ for 0\\<_ t \\<_ 1. " "To make glottal closure possible, %power2 has to be larger than %power1. If the power1 tier is empty, a default " "value of 3 will be used. If the power2 tier is empty, a default of 4 will be used.") TAG (L"##Collision phase") DEFINITION (L"models the last part of the flow function with an exponential decay function instead of a polynomial one. " "More information about #Power1, #Power2, ##Open phase# and ##Collision phase# can be found in the @@PointProcess: To Sound (phonation)...@ manual.") TAG (L"##Spectral tilt") DEFINITION (L"models the extra number of dB the voicing spectrum should be down at 3000 Hertz.") TAG (L"##Aspiration amplitude") DEFINITION (L"models the (maximum) amplitude of the noise generated at the glottis (in dB SPL). ") TAG (L"##Breathiness amplitude") DEFINITION (L"models the maximum breathiness noise amplitude during the open phase of the glottis (in dB SPL). " "The amplitude of the breathiness noise is modulated by the glottal flow.") TAG (L"##Double pulsing") DEFINITION (L"models diplophonia (by a fraction between zero and one). Whenever this parameter is greater than zero, " "alternate pulses are modified. A pulse is modified with this %%single% parameter in %%two% ways: it is %%delayed " "in time% and its amplitude is %%attenuated%. If the double pulsing value is a maximum and equals one, the time of " "closure of the first peak coincides with the opening time of the second one. ") ENTRY (L"The vocal tract filter") NORMAL (L"The filter is modelled by a number of @@FormantGrid@'s. For parallel synthesis the formant grids that normally " "only contain formant frequency and formant bandwidth tiers, have been extended with amplitude tiers. Amplitudes values are in dB. The following formant grids can be used:") TAG (L"##Oral formants") DEFINITION (L"represent the \"standard\" oral resonances of the vocal tract. ") TAG (L"##Nasal formants") DEFINITION (L"model resonances in the nasal tract. Because the form of the nasal tract does not vary much during the course of an utterance, nasal formants tend to be constant. ") TAG (L"##Nasal antiformants") DEFINITION (L"model dips in the spectrum caused by leakage to the nasal tract.") ENTRY (L"Interaction between source and filter") NORMAL (L"The interaction between source and filter is modeled by two formant grids.") TAG (L"##Tracheal formants") DEFINITION (L"model one aspect of the coupling of the trachea with the vocal tract transfer function, namely, by the " "introduction of extra formants (and antiformants) that sometimes distort vowel spectra to a varying degrees. " "According to @@Klatt & Klatt (1990)@, the other effect being increased losses at glottal termination which primarily affect first-formant bandwidths.") TAG (L"##Tracheal antiformants") DEFINITION (L"model dips in the spectrum caused by the trachea.") TAG (L"##Delta formants") DEFINITION (L"The values in this grid model the number of hertz that the oral formants and/or bandwidths change during the open phase " "of the glottis. @@Klatt & Klatt (1990)@ distinguish four types of source-filter interactions: an F1 ripple in the " "source waveform, a non-linear interaction between the first formant and the fundamental frequency, a truncation of " "the first formant and tracheal formants and antiformants. ") ENTRY (L"The frication section") NORMAL (L"The frication section is modeled with a frication formant grid, with formant frequencies, bandwidths and (separate) " "amplitudes (dB), a frication by-pass tier (dB) and an amplitude tier (dB SPL) that governs the frication noise source.") ENTRY (L"A minimal synthesizer") NORMAL (L"The following script produces a minimal voiced sound. The first line creates the standard KlattGrid." "The next two lines define a pitch point, in Hz, and the voicing amplitude, in dB. The last line " "creates the sound.") CODE (L"Create KlattGrid... kg 0 1 6 1 1 6 1 1 1") CODE (L"Add pitch point... 0.5 100") CODE (L"Add voicing amplitude point... 0.5 90 ") CODE (L"KlattGrid: To Sound") NORMAL (L"The following script will produce raw frication noise. Because we do not specify formant amplitudes, " "we turn off the formants in the parallel section.") CODE (L"Create KlattGrid... kg 0 1 6 1 1 6 1 1 1") CODE (L"Add frication amplitude point... 0.5 80") CODE (L"Add frication bypass point... 0.5 0") CODE (L"To Sound (special)... 0 0 44100 y n y y y y \"Powers in tiers\" y y y") CODE (L"... Cascade 1 5 1 1 1 1 1 1 1 1 1 1 1 1 1 0 y") ENTRY (L"Changes") NORMAL (L"In praat versions before 5.1.05 the values for the %%oral / nasal / tracheal formant amplitudes% and" " %%frication bypass amplitude% had to be given in dB SPL; " " now they are in real dB's, i.e." " 0 dB means no change in amplitude. You can calculate new values from old values as:\n" "new_value = old_value + 20*log10(2e-5). This means that you have to subtract approximately 94 dB from the old values.") MAN_END MAN_BEGIN (L"Create KlattGrid...", L"djmw", 20081224) INTRO (L"A command to create a multitier @@KlattGrid@ speech synthesizer.") MAN_END #define PhonationGrid_to_Sound_COMMON_PARAMETERS_HELP \ TAG (L"##Sampling frequency (Hz)") \ DEFINITION (L"the @@sampling frequency@ of the resulting sound.") \ TAG (L"##Voicing") \ DEFINITION (L"switches voicing on or off.") \ TAG (L"##Flutter") \ DEFINITION (L"switches the flutter tier on or off. This will, of course, only have effect if at least one flutter point has been defined in the flutter tier.") \ TAG (L"##Double pulsing") \ DEFINITION (L"switches the double pulsing tier on or off.") \ TAG (L"##Collision phase") \ DEFINITION (L"switches the collision phase tier on or off.") \ TAG (L"##Spectral tilt") \ DEFINITION (L"switches the spectral tilt tier on or off.") \ TAG (L"##Flow function") \ DEFINITION (L"determines which flow function will be used. The flow function is determined by two parameters, %%power1% and %%power2% as %%flow(t)=x^^power1^-x^^power2^%. " \ "If the option \"Powers in tier\" is chosen the power1 and power2 tiers will be used for the values of %%power1% and %%power2%. The other choices switch the two tiers off and instead fixed values will be used for %%power1% and %%power2%.") \ TAG (L"##Flow derivative") \ DEFINITION (L"determines whether the flow or the flow derivative is used for phonation. ") \ TAG (L"##Aspiration") \ DEFINITION (L"determines whether aspiration is included in the synthesis.") \ TAG (L"##Breathiness") \ DEFINITION (L"determines whether breathiness is included in the synthesis.") MAN_BEGIN (L"KlattGrid: To Sound (phonation)...", L"djmw", 20090122) INTRO (L"A command to synthesize a Sound from the selected @@KlattGrid@.") ENTRY (L"Settings") PhonationGrid_to_Sound_COMMON_PARAMETERS_HELP MAN_END MAN_BEGIN (L"KlattGrid: Play special...", L"djmw", 20090421) INTRO (L"A command to play part of a @@KlattGrid@.") ENTRY (L"Settings") TAG (L"##Time range (s)") DEFINITION (L"determines the part of the sound's domain that you want to hear. If both argument equal zero the complete sound is played. ") TAG (L"##Sampling frequency (Hz)") DEFINITION (L"determines the @@sampling frequency@ of the resulting sound.") TAG (L"##Scale peak") DEFINITION (L"determines whether the peak value of the sound will be set to 0.99. In this way the sound will always play well.") PhonationGrid_to_Sound_COMMON_PARAMETERS_HELP TAG (L"##Model") DEFINITION (L"switches on either the cascade or the parallel section of the synthesizer.") TAG (L"##Oral formant range#, ##Nasal formant range# ...") DEFINITION (L"selects the formants to use in the synthesis. Choosing the end of a range smaller than the start of the range switches off the formants. ") TAG (L"##Frication bypass") DEFINITION (L"switches the frication bypass of the frication section on or off. " "The complete frication section can be turned off by also switching off the frication formants.") MAN_END MAN_BEGIN (L"KlattGrid: To Sound (special)...", L"djmw", 20090415) INTRO (L"A command to synthesize a Sound from the selected @@KlattGrid@.") ENTRY (L"Settings") TAG (L"##Time range (s)") DEFINITION (L"determines the part of the domain that you want to save as a sound. If both argument equal zero the complete sound is created. ") TAG (L"##Sampling frequency (Hz)") DEFINITION (L"determines the @@sampling frequency@ of the resulting sound.") TAG (L"##Scale peak") DEFINITION (L"determines whether the peak value of the sound will be set to 0.99. In this way the sound will always play well and can be saved to a file with minimal loss of resolution.") PhonationGrid_to_Sound_COMMON_PARAMETERS_HELP TAG (L"##Model") DEFINITION (L"switches on either the cascade or the parallel section of the synthesizer.") TAG (L"##Oral formant range#, ##Nasal formant range# ...") DEFINITION (L"selects the formants to use in the synthesis. Choosing the end of a range smaller than the start of the range switches off the formants. ") TAG (L"##Frication bypass") DEFINITION (L"switches the frication bypass of the frication section on or off. " "The complete frication section can be turned off by also switching off the frication formants.") MAN_END MAN_BEGIN (L"KlattGrid: Extract oral formant grid (open phases)...", L"djmw", 20090421) INTRO (L"Extracts the oral formant grid as used in the synthesis, i.e. the resulting grid contains the informantion from the oral formant grid and the delta formant grid combined during the open phase of the glottis. ") MAN_END MAN_BEGIN (L"Sound: To KlattGrid (simple)...", L"djmw", 20090415) INTRO (L"Create a @@KlattGrid@ from a @@Sound@.") ENTRY (L"Algorithm") NORMAL (L"Oral formants are determined by the @@Sound: To Formant (burg)...@ method and transformed to a @@FormantGrid@. " "Pitch is determined by the @@Sound: To Pitch...@ method and transformed to a @@PitchTier@. " "With @@Sound: To Intensity...@ we determine intensity and convert it to an @@IntensityTier@.") NORMAL (L"Next a KlattGrid is created whose time domain conforms to the sound. Its pitch tier, normal formant grid " "and its voicing amplitude are replaced by the results from the analyses.") MAN_END MAN_BEGIN (L"Sound & KlattGrid: Filter by vocal tract...", L"djmw", 20090108) INTRO (L"Filters the selected sound with the vocal tract part of the selected @@KlattGrid@. During this filtering the delta formants and bandwidths are %%not% used. ") MAN_END } /* End of file manual_KlattGrid.cpp */ sources_5316/dwtools/CC.h0000644000176700017670000000354111627172270014064 0ustar paulpaul#ifndef _CC_h_ #define _CC_h_ /* CC.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010219 Cepstral Coefficients (abstract) class. djmw 20020402 GPL header djmw 20030612 Include CC_def.h djmw 20110306 Latest modification. */ #include "Graphics.h" #include "Matrix.h" #include "CC_def.h" oo_CLASS_CREATE (CC, Sampled); void CC_init (I, double tmin, double tmax, long nt, double dt, double t1, long maximumNumberOfCoefficients, double fmin, double fmax); void CC_getNumberOfCoefficients_extrema (I, long startframe, long endframe, long *min, long *max); long CC_getMinimumNumberOfCoefficients (I, long startframe, long endframe); long CC_getMaximumNumberOfCoefficients (I, long startframe, long endframe); void CC_paint (I, Graphics g, double xmin, double xmax, long cmin, long cmax, double minimum, double maximum, int garnish); void CC_drawC0 (I, Graphics g, double xmin, double xmax, double ymin, double ymax, int garnish); Matrix CC_to_Matrix (I); double CC_getValue (I, double t, long index); /******************* Frames ************************************************/ void CC_Frame_init (CC_Frame me, long numberOfCoefficients); #endif /* _CC_h_ */ sources_5316/dwtools/Sampled2.h0000644000176700017670000000607711627251275015260 0ustar paulpaul#ifndef _Sampled2_h_ #define _Sampled2_h_ /* Sampled2.h * * Copyright (C) 1993-2011 David Weenink & Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sampled.h" #include "Sampled2_def.h" oo_CLASS_CREATE (Sampled2, Sampled); void Sampled2_init (I, double xmin, double xmax, long nx, double dx, double x1, double ymin, double ymax, long ny, double dy, double y1); long Sampled2_getWindowSamplesX (I, double xmin, double xmax, long *ixmin, long *ixmax); /* Function: return the number of samples with x values in [xmin, xmax]. Put the first of these samples in ixmin. Put the last of these samples in ixmax. Postconditions: *ixmin >= 1; *ixmax <= my nx; if (result != 0) *ixmin <= *ixmax; else *ixmin > *ixmax; if (result != 0) result == *ixmax - *ixmin + 1; */ double Sampled2_columnToX (I, double column); /* Return my x1 + (column - 1) * my dx. */ double Sampled2_rowToY (I, double row); /* Return my y1 + (row - 1) * my dy. */ double Sampled2_xToColumn (I, double x); /* Return (x - xmin) / my dx + 1. */ long Sampled2_xToLowColumn (I, double x); /* Return floor (Matrix_xToColumn (me, x)). */ long Sampled2_xToHighColumn (I, double x); /* Return ceil (Matrix_xToColumn (me, x)). */ long Sampled2_xToNearestColumn (I, double x); /* Return floor (Matrix_xToColumn (me, x) + 0.5). */ double Sampled2_yToRow (I, double y); /* Return (y - ymin) / my dy + 1. */ long Sampled2_yToLowRow (I, double y); /* Return floor (Matrix_yToRow (me, y)). */ long Sampled2_yToHighRow (I, double x); /* Return ceil (Matrix_yToRow (me, y)). */ long Sampled2_yToNearestRow (I, double y); /* Return floor (Matrix_yToRow (me, y) + 0.5). */ long Sampled2_getWindowSamplesY (I, double ymin, double ymax, long *iymin, long *iymax); /**** a little bit dangerous ******/ long Sampled2_getWindowExtrema_d (I, double **z, long ixmin, long ixmax, long iymin, long iymax, double *minimum, double *maximum); long Sampled2_getWindowExtrema_f (I, float **z, long ixmin, long ixmax, long iymin, long iymax, double *minimum, double *maximum); /* Function: compute the minimum and maximum values of z over all samples inside [ixmin, ixmax] * [iymin, iymax]. Arguments: if ixmin = 0, start at first column; if ixmax = 0, end at last column (same for iymin and iymax). Return value: the number of samples inside the window. Postconditions: if result == 0, *minimum and *maximum are not changed; */ #endif /* _Sampled2_h_ */ sources_5316/dwtools/Resonator.cpp0000644000176700017670000000711511627251130016100 0ustar paulpaul/* Resonator.cpp * * Copyright (C) 2008-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * djmw 20081029 * djmw 20081124 +ConstantGainResonator * djmw 20110304 Thing_new */ #include "Resonator.h" Thing_implement (Filter, Data, 0); #define SETBC(f,bw) \ double r = exp (-NUMpi * dT * bw); \ c = -(r * r); \ b = 2.0 * r * cos (2.0 * NUMpi * f * dT); void structFilter :: v_resetMemory () { p1 = p2 = 0; } void structFilter :: v_setFB (double f, double bw) { SETBC (f, bw) a = 1.0 - b - c; } double structFilter :: v_getOutput (double input) { double output = a * input + b * p1 + c * p2; p2 = p1; p1 = output; return output; } Thing_implement (Resonator, Filter, 0); void structResonator :: v_setFB (double f, double bw) { SETBC (f, bw) a = normalisation == Resonator_NORMALISATION_H0 ? (1.0 - b - c) : (1 + c) * sin (2.0 * NUMpi * f * dT); } Resonator Resonator_create (double dT, int normalisation) { try { autoResonator me = Thing_new (Resonator); my a = 1; // all-pass my dT = dT; my normalisation = normalisation; return me.transfer(); } catch (MelderError) { Melder_throw ("Resonator not created."); } } Thing_implement (AntiResonator, Filter, 0); void structAntiResonator :: v_setFB (double f, double bw) { if (f <= 0 && bw <= 0) { a = 1; b = -2; c = 1; // all-pass except dc } else { SETBC (f, bw) a = 1 / (1.0 - b - c); // The next equations are incorporated in the getOutput function //c *= - a; b *= - a; } } /* y[n] = a * (x[n] - b * x[n-1] - c * x[n-2]) */ double structAntiResonator :: v_getOutput (double input) { double output = a * (input - b * p1 - c * p2); p2 = p1; p1 = input; return output; } Thing_implement (ConstantGainResonator, Filter, 0); void structConstantGainResonator :: v_resetMemory () { p1 = p2 = p3 = p4 = 0; } void structConstantGainResonator :: v_setFB (double f, double bw) { SETBC (f, bw) a = 1 - r; d = -r; } /* y[n] = a * (x[n] + d * x[n-2]) + b * y[n-1] + c * y[n-2] */ double structConstantGainResonator :: v_getOutput (double input) { double output = a * (input + d * p4) + b * p1 + c * p2; p2 = p1; p1 = output; p4 = p3; p3 = input; return output; } ConstantGainResonator ConstantGainResonator_create (double dT) { try { autoConstantGainResonator me = Thing_new (ConstantGainResonator); my a = 1; // all-pass my dT = dT; return me.transfer(); } catch (MelderError) { Melder_throw ("ConstantGainResonator not created."); } } AntiResonator AntiResonator_create (double dT) { try { autoAntiResonator me = Thing_new (AntiResonator); my a = 1; // all-pass my dT = dT; return me.transfer(); } catch (MelderError) { Melder_throw ("AntiResonator not created."); } } void Filter_setFB (I, double f, double b) { iam (Filter); my v_setFB (f, b); } double Filter_getOutput (I, double input) { iam (Filter); return my v_getOutput (input); } void Filter_resetMemory (I) { iam (Filter); my v_resetMemory (); } /* End of file Resonator.cpp */ sources_5316/dwtools/Resonator.h0000644000176700017670000000425311627251167015557 0ustar paulpaul#ifndef _Resonator_h_ #define _Resonator_h_ /* Resonator.h * * Copyright (C) 2008-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * djmw 20081029 * djmw 20110306 Latest modification */ #include "Sound.h" Thing_define (Filter, Data) { // new data: public: double dT; double a, b, c; double p1, p2; // new methods: virtual double v_getOutput (double input); virtual void v_setFB (double f, double b); virtual void v_resetMemory (); }; Thing_define (Resonator, Filter) { // new data: public: int normalisation; // overridden methods: virtual void v_setFB (double f, double b); }; Thing_define (AntiResonator, Resonator) { // overridden methods: virtual double v_getOutput (double input); virtual void v_setFB (double f, double b); }; Thing_define (ConstantGainResonator, Filter) { // new data: public: double d; double p3, p4; // overridden methods: virtual double v_getOutput (double input); virtual void v_setFB (double f, double b); virtual void v_resetMemory (); }; #define Resonator_NORMALISATION_H0 0 #define Resonator_NORMALISATION_HMAX 1 Resonator Resonator_create (double dT, int normalisation); ConstantGainResonator ConstantGainResonator_create (double dT); AntiResonator AntiResonator_create (double dT); /* Set a,b,c normalisation == 0: H(0) = 1 -> a = 1 -b - c normalisation == 1: H(Fmax) = 1 -> a = (1 + c)sin(2*pi*F*T) */ void Filter_setFB (I, double f, double b); double Filter_getOutput (I, double input); void Filter_resetMemory (I); #endif /* _Resonator_h_ */ sources_5316/dwtools/ICA.cpp0000664000176700017670000011030411737553641014533 0ustar paulpaul/* ICA.c * * Copyright (C) 2010-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20101202 Initial version djmw 20110304 Thing_new */ #include "ICA.h" #include "Interpreter.h" #include "NUM2.h" #include "PCA.h" #include "SVD.h" // matrix multiply R = V*C*V', V is nrv x ncv, C is ncv x ncv, R is nrv x nrv static void NUMdmatrices_multiply_VCVp (double **r, double **v, long nrv, long ncv, double **c, int csym) { for (long i = 1; i <= nrv; i++) { long jstart = csym ? i : 1; for (long j = jstart; j <= nrv; j++) { // V_ik C_kl V'_lj = V_ik C_kl V_jl double vcv = 0; for (long k = 1; k <= ncv; k++) { for (long l = 1; l <= ncv; l++) { vcv += v[i][k] * c[k][l] * v[j][l]; } } r[i][j] = vcv; if (csym) { r[j][i] = vcv; } } } } // matrix multiply R = V'*C*V, V is nrv x ncv, C is ncv x ncv, R is nrv x nrv static void NUMdmatrices_multiply_VpCV (double **r, double **v, long nrv, long ncv, double **c, int csym) { for (long i = 1; i <= ncv; i++) { long jstart = csym ? i : 1; for (long j = jstart; j <= ncv; j++) { // V'_ik C_kl V_lj = V_ki C_kl V_lj double vcv = 0; for (long k = 1; k <= nrv; k++) { for (long l = 1; l <= ncv; l++) { vcv += v[k][i] * c[k][l] * v[l][j]; } } r[i][j] = vcv; if (csym) { r[j][i] = vcv; } } } } // matrix multiply V*C, V is nrv x ncv, C is ncv x ncc, R is nrv x ncc; static void NUMdmatrices_multiply_VC (double **r, double **v, long nrv, long ncv, double **c, long ncc) { for (long i = 1; i <= nrv; i++) { for (long j = 1; j <= ncc; j++) { // V_ik C_kj double vc = 0; for (long k = 1; k <= ncv; k++) { vc += v[i][k] * c[k][j]; } r[i][j] = vc; } } } // matrix multiply V'*C, V is nrv x ncv, C is nrv x ncc, R is ncv x ncc; static void NUMdmatrices_multiply_VpC (double **r, double **v, long nrv, long ncv, double **c, long ncc) { for (long i = 1; i <= ncv; i++) { for (long j = 1; j <= ncc; j++) { // V'_ik C_kj double vc = 0; for (long k = 1; k <= nrv; k++) { vc += v[k][i] * c[k][j]; } r[i][j] = vc; } } } // D += scalef * M * M', M = nrm x ncm, D is nrm x nrm static void NUMdmatrices_multiplyScaleAdd (double **r, double **m, long nrm, long ncm, double scalef) { for (long i = 1; i <= nrm; i++) { for (long j = 1; j <= nrm; j++) { // M_ik M'_kj = M_ik M_jk double mm = 0; for (long k = 1; k <= ncm; k++) { mm += m[i][k] * m[j][k]; } r[i][j] += scalef * mm; } } } /* d = diag(diag(W'*C0*W)); W = W*d^(-1/2); D_ij = W'_ik C_kl W_lj => D_ii = W_ki C_kl W_li */ static void NUMdmatrix_normalizeColumnVectors (double **w, long nrw, long ncw, double **c) { for (long i = 1; i <= ncw; i++) { double di = 0; for (long k = 1; k <= ncw; k++) for (long l = 1; l <= nrw; l++) { di += w[k][i] * c[k][l] * w[l][i]; } di = 1 / sqrt (di); for (long j = 1; j <= nrw; j++) { w[j][i] *= di; } } } static double NUMdmatrix_diagonalityMeasure (double **v, long dimension) { double dmsq = 0; if (dimension < 2) { return 0; } for (long i = 1; i <= dimension; i++) { for (long j = 1; j <= dimension; j++) { if (i != j) { dmsq += v[i][j] * v[i][j]; } } } return dmsq / (dimension * (dimension - 1)); } static double NUMdmatrix_diagonalityIndex (double **v, long dimension) { double dindex = 0; for (long irow = 1; irow <= dimension; irow++) { double rowmax = fabs (v[irow][1]), rowsum = 0; for (long icol = 2; icol <= dimension; icol++) { if (fabs (v[irow][icol]) > rowmax) { rowmax = fabs (v[irow][icol]); } } for (long icol = 1; icol <= dimension; icol++) { rowsum += fabs (v[irow][icol]) / rowmax; } dindex += rowsum - 1; } for (long icol = 1; icol <= dimension; icol++) { double colmax = fabs (v[icol][1]), colsum = 0; for (long irow = 2; irow <= dimension; irow++) { if (fabs (v[irow][icol]) > colmax) { colmax = fabs (v[irow][icol]); } } for (long irow = 1; irow <= dimension; irow++) { colsum += fabs (v[irow][icol]) / colmax; } dindex += colsum - 1; } return dindex; } /* This routine is modeled after qdiag.m from Andreas Ziehe, Pavel Laskov, Guido Nolte, Klaus-Robert Müller, A Fast Algorithm for Joint Diagonalization with Non-orthogonal Transformations and its Application to Blind Source Separation, Journal of Machine Learning Research 5 (2004), 777–800. */ static void Diagonalizer_and_CrossCorrelationTables_ffdiag (Diagonalizer me, CrossCorrelationTables thee, long maxNumberOfIterations, double delta) { try { long iter = 0, dimension = my numberOfRows; double **v = my data; autoCrossCorrelationTables ccts = CrossCorrelationTables_and_Diagonalizer_diagonalize (thee, me); autoNUMmatrix w (1, dimension, 1, dimension); autoNUMmatrix vnew (1, dimension, 1, dimension); autoNUMmatrix cc (1, dimension, 1, dimension); for (long i = 1; i <= dimension; i++) { w[i][i] = 1; } MelderInfo_open (); double dm_new = CrossCorrelationTables_getDiagonalityMeasure (ccts.peek(), NULL, 0, 0); MelderInfo_writeLine5 (L"\nIteration ", Melder_integer (iter), L": ", Melder_double (dm_new), L" (= diagonality measurement)"); double dm_old, theta = 1 ; do { dm_old = dm_new; for (long i = 1; i <= dimension; i++) { for (long j = i + 1; j <= dimension; j++) { double zii = 0, zij = 0, zjj = 0, yij = 0, yji = 0; // zij = zji for (long k = 1; k <= ccts -> size; k++) { CrossCorrelationTable ct = (CrossCorrelationTable) ccts -> item [k]; zii += ct -> data[i][i] * ct -> data[i][i]; zij += ct -> data[i][i] * ct -> data[j][j]; zjj += ct -> data[j][j] * ct -> data[j][j]; yij += ct -> data[j][j] * ct -> data[i][j]; yji += ct -> data[i][i] * ct -> data[i][j]; } double denom = zjj * zii - zij * zij; if (denom != 0) { w[i][j] = (zij * yji - zii * yij) / denom; w[j][i] = (zij * yij - zjj * yji) / denom; } } } double norma = 0; for (long i = 1; i <= dimension; i++) { double normai = 0; for (long j = 1; j <= dimension; j++) { if (i != j) { normai += fabs (w[i][j]); } } if (normai > norma) { norma = normai; } } // evaluate the norm if (norma > theta) { double normf = 0; for (long i = 1; i <= dimension; i++) for (long j = 1; j <= dimension; j++) if (i != j) { normf += w[i][j] * w[i][j]; } double scalef = theta / sqrt (normf); for (long i = 1; i <= dimension; i++) { for (long j = 1; j <= dimension; j++) { if (i != j) { w[i][j] *= scalef; } } } } // update V NUMmatrix_copyElements (v, vnew.peek(), 1, dimension, 1, dimension); NUMdmatrices_multiply_VC (v, w.peek(), dimension, dimension, vnew.peek(), dimension); for (long k = 1; k <= ccts -> size; k++) { CrossCorrelationTable ct = (CrossCorrelationTable) ccts -> item[k]; NUMmatrix_copyElements (ct -> data, cc.peek(), 1, dimension, 1, dimension); NUMdmatrices_multiply_VCVp (ct -> data, w.peek(), dimension, dimension, cc.peek(), 1); } dm_new = CrossCorrelationTables_getDiagonalityMeasure (ccts.peek(), 0, 0, 0); iter++; MelderInfo_writeLine5 (L"\nIteration ", Melder_integer (iter), L": ", Melder_double (dm_new), L" (= diagonality measurement)"); } while (fabs ( (dm_old - dm_new) / dm_new) > delta && iter < maxNumberOfIterations); MelderInfo_close (); } catch (MelderError) { MelderInfo_close (); Melder_throw (me, " & ", thee, ": no joint diagonalization (ffdiag)."); } } /* The folowing two routines are modeled after qdiag.m from R. Vollgraf and K. Obermayer, Quadratic Optimization for Simultaneous Matrix Diagonalization, IEEE Transaction on Signal Processing, 2006, */ static void update_one_column (CrossCorrelationTables me, double **d, double *wp, double *wvec, double scalef, double *work) { long dimension = ( (CrossCorrelationTable) (my item[1])) -> numberOfColumns; for (long ic = 2; ic <= my size; ic++) { // exclude C0 SSCP cov = (SSCP) my item[ic]; double **c = cov -> data; // m1 = C * wvec for (long i = 1; i <= dimension; i++) { double r = 0; for (long j = 1; j <= dimension; j++) { r += c[i][j] * wvec[j]; } work[i] = r; } // D = D +/- 2*p(t)*(m1*m1'); for (long i = 1; i <= dimension; i++) { for (long j = 1; j <= dimension; j++) { d[i][j] += 2 * scalef * wp[ic] * work[i] * work[j]; } } } } static void Diagonalizer_and_CrossCorrelationTable_qdiag (Diagonalizer me, CrossCorrelationTables thee, double *cweights, long maxNumberOfIterations, double delta) { try { CrossCorrelationTable c0 = (CrossCorrelationTable) thy item[1]; double **w = my data; long dimension = c0 -> numberOfColumns; autoEigen eigen = Thing_new (Eigen); autoCrossCorrelationTables ccts = Data_copy (thee); autoNUMmatrix pinv (1, dimension, 1, dimension); autoNUMmatrix d (1, dimension, 1, dimension); autoNUMmatrix p (1, dimension, 1, dimension); autoNUMmatrix m1 (1, dimension, 1, dimension); autoNUMmatrix wc (1, dimension, 1, dimension); autoNUMvector wvec (1, dimension); autoNUMvector wnew (1, dimension); autoNUMvector mvec (1, dimension); for (long i = 1; i <= dimension; i++) // Transpose W for (long j = 1; j <= dimension; j++) { wc[i][j] = w[j][i]; } // d = diag(diag(W'*C0*W)); // W = W*d^(-1/2); NUMdmatrix_normalizeColumnVectors (wc.peek(), dimension, dimension, c0 -> data); // scale eigenvectors for sphering // [vb,db] = eig(C0); // P = db^(-1/2)*vb'; Eigen_initFromSymmetricMatrix (eigen.peek(), c0 -> data, dimension); for (long i = 1; i <= dimension; i++) { if (eigen -> eigenvalues[i] < 0) { Melder_throw ("Covariance matrix not positive definite."); } double scalef = 1 / sqrt (eigen -> eigenvalues[i]); for (long j = 1; j <= dimension; j++) { p[dimension - i + 1][j] = scalef * eigen -> eigenvectors[i][j]; } } // P*C[i]*P' for (long ic = 1; ic <= thy size; ic++) { CrossCorrelationTable cov1 = (CrossCorrelationTable) thy item[ic]; CrossCorrelationTable cov2 = (CrossCorrelationTable) ccts -> item[ic]; NUMdmatrices_multiply_VCVp (cov2 -> data, p.peek(), dimension, dimension, cov1 -> data, 1); } // W = P'\W == inv(P') * W NUMpseudoInverse (p.peek(), dimension, dimension, pinv.peek(), 0); NUMdmatrices_multiply_VpC (w, pinv.peek(), dimension, dimension, wc.peek(), dimension); // initialisation for order KN^3 for (long ic = 2; ic <= thy size; ic++) { CrossCorrelationTable cov = (CrossCorrelationTable) ccts -> item[ic]; // C * W NUMdmatrices_multiply_VC (m1.peek(), cov -> data, dimension, dimension, w, dimension); // D += scalef * M1*M1' NUMdmatrices_multiplyScaleAdd (d.peek(), m1.peek(), dimension, dimension, 2 * cweights[ic]); } long iter = 0; double delta_w; MelderInfo_open (); do { // the standard diagonality measure is rather expensive to calculate so we compare the norms of // differences of eigenvectors. delta_w = 0; for (long kol = 1; kol <= dimension; kol++) { for (long i = 1; i <= dimension; i++) { wvec[i] = w[i][kol]; } update_one_column (ccts.peek(), d.peek(), cweights, wvec.peek(), -1, mvec.peek()); Eigen_initFromSymmetricMatrix (eigen.peek(), d.peek(), dimension); // Eigenvalues already sorted; get eigenvector of smallest ! for (long i = 1; i <= dimension; i++) { wnew[i] = eigen -> eigenvectors[dimension][i]; } update_one_column (ccts.peek(), d.peek(), cweights, wnew.peek(), 1, mvec.peek()); for (long i = 1; i <= dimension; i++) { w[i][kol] = wnew[i]; } // compare norms of eigenvectors. We have to compare ||wvec +/- w_new|| because eigenvectors // may change sign. double normp = 0, normm = 0; for (long j = 1; j <= dimension; j++) { double dm = wvec[j] - wnew[j], dp = wvec[j] + wnew[j]; normp += dm * dm; normm += dp * dp; } normp = normp < normm ? normp : normm; normp = sqrt (normp); delta_w = normp > delta_w ? normp : delta_w; } iter++; MelderInfo_writeLine5 (L"\nIteration ", Melder_integer (iter), L": ", Melder_double (delta_w), L" (= vector norm difference)"); } while (delta_w > delta && iter < maxNumberOfIterations); // Revert the sphering W = P'*W; // Take transpose to make W*C[i]W' diagonal instead of W'*C[i]*W => (P'*W)'=W'*P // Calculate the "real" diagonality measure NUMmatrix_copyElements (w, wc.peek(), 1, dimension, 1, dimension); NUMdmatrices_multiply_VpC (w, wc.peek(), dimension, dimension, p.peek(), dimension); // W = W'*P: final result double dm = CrossCorrelationTables_and_Diagonalizer_getDiagonalityMeasure (thee, me, cweights, 1, thy size); MelderInfo_writeLine5 (L"\nDiagonality measure: ", Melder_double (dm), L" after ", Melder_integer (iter), L" iterations."); MelderInfo_close (); } catch (MelderError) { MelderInfo_close (); Melder_throw (me, " & ", thee, ": no joint diagonalization (qdiag)."); } } void MixingMatrix_and_CrossCorrelationTables_improveUnmixing (MixingMatrix me, CrossCorrelationTables thee, long maxNumberOfIterations, double tol, int method) { autoDiagonalizer him = MixingMatrix_to_Diagonalizer (me); Diagonalizer_and_CrossCorrelationTables_improveDiagonality (him.peek(), thee, maxNumberOfIterations, tol, method); NUMpseudoInverse (his data, his numberOfRows, his numberOfColumns, my data, 0); } /* Preconditions: * x[1..nrows][1..ncols], cc[1..nrows][1..nrows], centroid[1..nrows] * if (lag>0) {i2 + lag <= ncols} else {i1-lag >= 1} * no array boundary checks! * lag >= 0 */ static void NUMcrossCorrelate_rows (double **x, long nrows, long i1, long i2, long lag, double **cc, double *centroid, double scale) { lag = abs (lag); long nsamples = i2 - i1 + 1 + lag; for (long i = 1; i <= nrows; i++) { double sum = 0; for (long k = i1; k <= i2 + lag; k++) { sum += x[i][k]; } centroid[i] = sum / nsamples; } for (long i = 1; i <= nrows; i++) { for (long j = i; j <= nrows; j++) { double ccor = 0; for (long k = i1; k <= i2; k++) { ccor += (x[i][k] - centroid[i]) * (x[j][k + lag] - centroid[j]); } cc[j][i] = cc[i][j] = ccor * scale; } } } /* This is for multi-channel "sounds" like EEG signals. The cross-correlation between channel i and channel j is defined as sum(k=1..nsamples, (z[i][k] - mean[i])(z[j][k + tau] - mean[j]))*samplingTime */ CrossCorrelationTable Sound_to_CrossCorrelationTable (Sound me, double startTime, double endTime, double lagTime) { try { if (endTime <= startTime) { startTime = my xmin; endTime = my xmax; } long lag = lagTime / my dx; long i1 = Sampled_xToNearestIndex (me, startTime); if (i1 < 1) { i1 = 1; } long i2 = Sampled_xToNearestIndex (me, endTime); if (i2 > my nx) { i2 = my nx; } i2 -= lag; long nsamples = i2 - i1 + 1; if (nsamples <= my ny) { Melder_throw ("Not enough samples"); } autoCrossCorrelationTable thee = CrossCorrelationTable_create (my ny); NUMcrossCorrelate_rows (my z, my ny, i1, i2, lag, thy data, thy centroid, my dx); thy numberOfObservations = nsamples; return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": CrossCorrelationTable not created."); } } /* Calculate the CrossCorrelationTable between the channels of two multichannel sounds irrespective of the domains. * Both sounds are treated as if their domain runs from 0 to duration. * Outside the chose interval the sounds are assumed yo be zero * * */ CrossCorrelationTable Sounds_to_CrossCorrelationTable_combined (Sound me, Sound thee, double relativeStartTime, double relativeEndTime, double lagTime) { try { if (my dx != thy dx) { Melder_throw ("Sampling frequencies must be equal."); } if (relativeEndTime <= relativeStartTime) { relativeStartTime = my xmin; relativeEndTime = my xmax; } long ndelta = lagTime / my dx, nchannels = my ny + thy ny; long i1 = Sampled_xToNearestIndex (me, relativeStartTime); if (i1 < 1) { i1 = 1; } long i2 = Sampled_xToNearestIndex (me, relativeEndTime); if (i2 > my nx) { i2 = my nx; } i2 -= ndelta; long nsamples = i2 - i1 + 1; if (nsamples <= nchannels) { Melder_throw ("Not enough samples"); } autoCrossCorrelationTable him = CrossCorrelationTable_create (nchannels); autoNUMvector data (1, nchannels); for (long i = 1; i <= my ny; i++) { data[i] = my z[i]; } for (long i = 1; i <= thy ny; i++) { data[i + my ny] = thy z[i]; } NUMcrossCorrelate_rows (data.peek(), nchannels, i1, i2, ndelta, his data, his centroid, my dx); his numberOfObservations = nsamples; return him.transfer(); } catch (MelderError) { Melder_throw (me, ": CrossCorrelationTable not created."); } } Covariance Sound_to_Covariance_channels (Sound me, double startTime, double endTime) { try { double lagTime = 0.0; autoCrossCorrelationTable thee = Sound_to_CrossCorrelationTable (me, startTime, endTime, lagTime); autoCovariance him = Thing_new (Covariance); thy structCrossCorrelationTable :: v_copy (him.peek()); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no Covariance created."); } } CrossCorrelationTables Sound_to_CrossCorrelationTables (Sound me, double startTime, double endTime, double lagTime, long ncovars) { try { if (lagTime < my dx) { lagTime = my dx; } if (startTime + ncovars * lagTime > endTime) { Melder_throw ("Lag time too large."); } if (endTime <= startTime) { startTime = my xmin; endTime = my xmax; } autoCrossCorrelationTables thee = CrossCorrelationTables_create (); for (long i = 1; i <= ncovars; i++) { double lag = (i - 1) * lagTime; autoCrossCorrelationTable ct = Sound_to_CrossCorrelationTable (me, startTime, endTime, lag); Collection_addItem (thee.peek(), ct.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no CrossCorrelationTables created."); } } Sound Sound_to_Sound_BSS (Sound me, double startTime, double endTime, long ncovars, double lagTime, long maxNumberOfIterations, double tol, int method) { try { autoMixingMatrix him = Sound_to_MixingMatrix (me, startTime, endTime, ncovars, lagTime, maxNumberOfIterations, tol, method); autoSound thee = Sound_and_MixingMatrix_unmix (me, him.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not separated."); } } PCA Sound_to_PCA_channels (Sound me, double startTime, double endTime) { try { autoCrossCorrelationTable thee = Sound_to_CrossCorrelationTable (me, startTime, endTime, 0); autoPCA him = SSCP_to_PCA (thee.peek()); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no PCA created."); } } /************************ Diagonalizer **********************************/ Thing_implement (Diagonalizer, TableOfReal, 0); Diagonalizer Diagonalizer_create (long dimension) { try { autoDiagonalizer me = Thing_new (Diagonalizer); TableOfReal_init (me.peek(), dimension, dimension); for (long i = 1; i <= dimension; i++) { my data[i][i] = 1; } return me.transfer(); } catch (MelderError) { Melder_throw ("Diagonalizer not created."); } } /************************ MixingMatrix **********************************/ Thing_implement (MixingMatrix, TableOfReal, 0); MixingMatrix MixingMatrix_create (long numberOfChannels, long numberOfComponents) { try { autoMixingMatrix me = Thing_new (MixingMatrix); TableOfReal_init (me.peek(), numberOfChannels, numberOfComponents); MixingMatrix_initializeRandom (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("MixingMatrix not created."); } } MixingMatrix MixingMatrix_createSimple (long numberOfChannels, long numberOfComponents, wchar_t *elements) { try { long inum = 1, ntokens = Melder_countTokens (elements); if (ntokens == 0) { Melder_throw ("No matrix elements."); } long nwanted = numberOfChannels * numberOfComponents; autoMixingMatrix me = MixingMatrix_create (numberOfChannels, numberOfComponents); // Construct the full matrix from the elements double number; for (wchar_t *token = Melder_firstToken (elements); token != NULL && inum <= ntokens; token = Melder_nextToken (), inum++) { long irow = (inum - 1) / numberOfComponents + 1; long icol = (inum - 1) % numberOfComponents + 1; Interpreter_numericExpression (0, token, &number); my data[irow][icol] = number; } if (ntokens < nwanted) { for (long i = inum; i <= nwanted; i++) { long irow = (inum - 1) / numberOfComponents + 1; long icol = (inum - 1) % numberOfComponents + 1; my data[irow][icol] = number; // repeat the last number given! } } return me.transfer(); } catch (MelderError) { Melder_throw ("MixingMatrix not created."); } } void MixingMatrix_initializeRandom (MixingMatrix me) { for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { my data[i][j] = NUMrandomGauss (0, 1); } } } /***************** Diagonalizer & MixingMatrix *************************/ Diagonalizer MixingMatrix_to_Diagonalizer (MixingMatrix me) { try { if (my numberOfRows != my numberOfColumns) { Melder_throw ("The number of channels and the number of components must be equal."); } autoDiagonalizer thee = Diagonalizer_create (my numberOfRows); NUMpseudoInverse (my data, my numberOfRows, my numberOfColumns, thy data, 0); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Diagonalizer created."); } } MixingMatrix Diagonalizer_to_MixingMatrix (Diagonalizer me) { try { autoMixingMatrix thee = MixingMatrix_create (my numberOfRows, my numberOfColumns); NUMpseudoInverse (my data, my numberOfRows, my numberOfColumns, thy data, 0); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no MixingMatrix created."); } } /********************* Sound & MixingMatrix ************************************/ Sound Sound_and_MixingMatrix_mix (Sound me, MixingMatrix thee) { try { if (my ny != thy numberOfColumns) { Melder_throw ("The number of components in the MixingMatrix and the number of channels in the Sound must be equal."); } autoSound him = Sound_create (thy numberOfRows, my xmin, my xmax, my nx, my dx, my x1); for (long i = 1; i <= thy numberOfRows; i++) { for (long j = 1; j <= my nx; j++) { double mix = 0; for (long k = 1; k <= my ny; k++) { mix += thy data[i][k] * my z[k][j]; } his z[i][j] = mix; } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not mixed."); } } Sound Sound_and_MixingMatrix_unmix (Sound me, MixingMatrix thee) { try { if (my ny != thy numberOfRows) { Melder_throw ("The MixingMatrix and the Sound must have the same number of channels."); } autoNUMmatrix minv (1, thy numberOfColumns, 1, thy numberOfRows); NUMpseudoInverse (thy data, thy numberOfRows, thy numberOfColumns, minv.peek(), 0); autoSound him = Sound_create (thy numberOfColumns, my xmin, my xmax, my nx, my dx, my x1); for (long i = 1; i <= thy numberOfColumns; i++) { for (long j = 1; j <= my nx; j++) { double s = 0; for (long k = 1; k <= my ny; k++) { s += minv[i][k] * my z[k][j]; } his z[i][j] = s; } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not unmixed."); } } MixingMatrix Sound_to_MixingMatrix (Sound me, double startTime, double endTime, long ncovars, double lagTime, long maxNumberOfIterations, double tol, int method) { try { autoCrossCorrelationTables ccs = Sound_to_CrossCorrelationTables (me, startTime, endTime, lagTime, ncovars); autoMixingMatrix thee = MixingMatrix_create (my ny, my ny); MixingMatrix_and_CrossCorrelationTables_improveUnmixing (thee.peek(), ccs.peek(), maxNumberOfIterations, tol, method); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no MixingMatrix created."); } } #undef your #define your ((MixingMatrix_Table) thy methods) -> MixingMatrix TableOfReal_to_MixingMatrix (TableOfReal me) { try { if (my numberOfColumns != my numberOfRows) { Melder_throw ("Number of rows and columns must be equal."); } autoMixingMatrix thee = Thing_new (MixingMatrix); my structTableOfReal :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to MixingMatrix."); } } /************* CrossCorrelationTable *****************************/ Thing_implement (CrossCorrelationTable, SSCP, 0); void structCrossCorrelationTable :: v_info () { structSSCP :: v_info (); double dm = CrossCorrelationTable_getDiagonalityMeasure (this); MelderInfo_writeLine2 (L"Diagonality measure: ", Melder_double (dm)); } CrossCorrelationTable CrossCorrelationTable_create (long dimension) { try { autoCrossCorrelationTable me = Thing_new (CrossCorrelationTable); SSCP_init (me.peek(), dimension, dimension); return me.transfer(); } catch (MelderError) { Melder_throw ("CrossCorrelationTable not created."); } } CrossCorrelationTable CrossCorrelationTable_createSimple (wchar_t *covars, wchar_t *centroid, long numberOfSamples) { try { long dimension = Melder_countTokens (centroid); long ncovars = Melder_countTokens (covars); long ncovars_wanted = dimension * (dimension + 1) / 2; if (ncovars != ncovars_wanted) Melder_throw ("The number of matrix elements and the number of " "centroid elements are not in concordance. There should be \"d(d+1)/2\" matrix values and \"d\" centroid values."); autoCrossCorrelationTable me = CrossCorrelationTable_create (dimension); // Construct the full matrix from the upper-diagonal elements long inum = 1, irow = 1; for (wchar_t *token = Melder_firstToken (covars); token != NULL && inum <= ncovars_wanted; token = Melder_nextToken (), inum++) { double number; long nmissing = (irow - 1) * irow / 2; long inumc = inum + nmissing; irow = (inumc - 1) / dimension + 1; long icol = ( (inumc - 1) % dimension) + 1; Interpreter_numericExpression (NULL, token, &number); my data[irow][icol] = my data[icol][irow] = number; if (icol == dimension) { irow++; } } inum = 1; for (wchar_t *token = Melder_firstToken (centroid); token != NULL && inum <= dimension; token = Melder_nextToken (), inum++) { double number; Interpreter_numericExpression (NULL, token, &number); my centroid[inum] = number; } my numberOfObservations = numberOfSamples; return me.transfer(); } catch (MelderError) { Melder_throw ("CrossCorrelationTable not created."); } } double CrossCorrelationTable_getDiagonalityMeasure (CrossCorrelationTable me) { return NUMdmatrix_diagonalityMeasure (my data, my numberOfColumns); } /************* CrossCorrelationTables *****************************/ void structCrossCorrelationTables :: v_info () { structOrdered :: v_info (); CrossCorrelationTable thee = (CrossCorrelationTable) item[1]; MelderInfo_writeLine2 (L" Number of rows and columns: ", Melder_integer (thy numberOfRows)); for (long i = 1; i <= size; i++) { double dm = CrossCorrelationTable_getDiagonalityMeasure ( (CrossCorrelationTable) item[i]); MelderInfo_writeLine4 (L"Diagonality measure for item ", Melder_integer (i), L": ", Melder_double (dm)); } } Thing_implement (CrossCorrelationTables, Ordered, 0); CrossCorrelationTables CrossCorrelationTables_create () { try { autoCrossCorrelationTables me = Thing_new (CrossCorrelationTables); Ordered_init (me.peek(), classCrossCorrelationTable, 30); return me.transfer(); } catch (MelderError) { Melder_throw ("CrossCorrelationTables not created."); } } double CrossCorrelationTables_getDiagonalityMeasure (CrossCorrelationTables me, double *w, long start, long end) { if (start >= end) { start = 1; end = my size; } if (start < 1) { start = 1; } if (end > my size) { end = my size; } long ntables = end - start + 1; long dimension = ( (Covariance) (my item[1]))-> numberOfColumns; double dmsq = 0; for (long k = start; k <= end; k++) { CrossCorrelationTable thee = (CrossCorrelationTable) my item[k]; double dmksq = NUMdmatrix_diagonalityMeasure (thy data, dimension); dmsq += w == NULL ? dmksq / ntables : dmksq * w[k]; } return dmsq; } /************************** CrossCorrelationTables & Diagonalizer *******************************/ double CrossCorrelationTables_and_Diagonalizer_getDiagonalityMeasure (CrossCorrelationTables me, Diagonalizer thee, double *w, long start, long end) { autoCrossCorrelationTables him = CrossCorrelationTables_and_Diagonalizer_diagonalize (me, thee); double dm = CrossCorrelationTables_getDiagonalityMeasure (him.peek(), w, start, end); return dm; } CrossCorrelationTable CrossCorrelationTable_and_Diagonalizer_diagonalize (CrossCorrelationTable me, Diagonalizer thee) { try { if (my numberOfRows != thy numberOfRows) { Melder_throw ("The CrossCorrelationTable and the Diagonalizer matrix dimensions must be equal."); } autoCrossCorrelationTable him = CrossCorrelationTable_create (my numberOfColumns); NUMdmatrices_multiply_VCVp (his data, thy data, my numberOfColumns, my numberOfColumns, my data, 1); return him.transfer(); } catch (MelderError) { Melder_throw ("CrossCorrelationTable not diagonalized."); } } CrossCorrelationTables CrossCorrelationTables_and_Diagonalizer_diagonalize (CrossCorrelationTables me, Diagonalizer thee) { try { autoCrossCorrelationTables him = CrossCorrelationTables_create (); for (long i = 1; i <= my size; i++) { CrossCorrelationTable item = (CrossCorrelationTable) my item[i]; autoCrossCorrelationTable ct = CrossCorrelationTable_and_Diagonalizer_diagonalize (item, thee); Collection_addItem (him.peek(), ct.transfer()); } return him.transfer(); } catch (MelderError) { Melder_throw ("CrossCorrelationTables not diagonalized."); } } Diagonalizer CrossCorrelationTables_to_Diagonalizer (CrossCorrelationTables me, long maxNumberOfIterations, double tol, int method) { try { CrossCorrelationTable him = (CrossCorrelationTable) my item[1]; autoDiagonalizer thee = Diagonalizer_create (his numberOfColumns); Diagonalizer_and_CrossCorrelationTables_improveDiagonality (thee.peek(), me, maxNumberOfIterations, tol, method); return thee.transfer(); } catch (MelderError) { Melder_throw ("Diagonalizer not created from CrossCorrelationTables."); }; } void Diagonalizer_and_CrossCorrelationTables_improveDiagonality (Diagonalizer me, CrossCorrelationTables thee, long maxNumberOfIterations, double tol, int method) { if (method == 1) { autoNUMvector cweights (1, thy size); for (long i = 1; i <= thy size; i++) { cweights[i] = 1.0 / thy size; } Diagonalizer_and_CrossCorrelationTable_qdiag (me, thee, cweights.peek(), maxNumberOfIterations, tol); } else { Diagonalizer_and_CrossCorrelationTables_ffdiag (me, thee, maxNumberOfIterations, tol); } } Sound Sound_whitenChannels (Sound me, double varianceFraction) { try { autoCovariance cov = Sound_to_Covariance_channels (me, 0.0, 0.0); autoSound thee = Sound_and_Covariance_whitenChannels (me, cov.peek(), varianceFraction); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not whitened."); } } Sound Sound_and_Covariance_whitenChannels (Sound me, Covariance thee, double varianceFraction) { try { autoPCA pca = SSCP_to_PCA (thee); long numberOfComponents = Eigen_getDimensionOfFraction (pca.peek(), varianceFraction); autoSound him = Sound_and_PCA_whitenChannels (me, pca.peek(), numberOfComponents); return him.transfer (); } catch (MelderError) { Melder_throw (me, ": not whitened from ", thee); } } Sound Sound_and_PCA_projectChannels (Sound me, PCA thee, long numberOfComponents) { try { if (my ny != thy dimension) { Melder_throw ("The number of channels of the sound and the dimension of the PCA must be equal."); } if (numberOfComponents <= 0 || numberOfComponents > thy numberOfEigenvalues) { numberOfComponents = thy numberOfEigenvalues; } autoSound him = Sound_create (numberOfComponents, my xmin, my xmax, my nx, my dx, my x1); for (long ichan = 1; ichan <= numberOfComponents; ichan++) { for (long is = 1; is <= my nx; is++) { for (long evi = 1; evi <= thy dimension; evi++) { his z[ichan][is] += thy eigenvectors[ichan][evi] * my z[evi][is]; } } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not projected."); } } Sound Sound_and_PCA_whitenChannels (Sound me, PCA thee, long numberOfComponents) { try { if (my ny != thy dimension) { Melder_throw ("The number of channels of the sound and the dimension of the PCA must be equal."); } if (numberOfComponents <= 0 || numberOfComponents > thy numberOfEigenvalues) { numberOfComponents = thy numberOfEigenvalues; } autoNUMmatrix whiten (1, my ny, 1, my ny); for (long i = 1; i <= my ny; i++) { for (long j = i; j <= my ny; j++) { double wij = 0; for (long k = 1; k <= numberOfComponents; k++) { wij += thy eigenvectors[k][i] * thy eigenvectors[k][j] / sqrt (thy eigenvalues[k]); } whiten[i][j] = whiten[j][i] = wij; } } autoSound him = Sound_create (numberOfComponents, my xmin, my xmax, my nx, my dx, my x1); for (long i = 1; i <= his ny; i++) { for (long j = 1; j <= his nx; j++) { double hisij = 0; for (long k = 1; k <= my ny; k++) { hisij += whiten[i][k] * my z[k][j]; } his z[i][j] = hisij; } } return him.transfer(); } catch (MelderError) { Melder_throw ("Sound not created."); } } /* * Generate n different cct's that have a common diagonalizer. */ CrossCorrelationTables CrossCorrelationTables_createTestSet (long dimension, long n, int firstPositiveDefinite, double sigma) { try { // Start with a square matrix with random gaussian elements and make its singular value decomposition UDV' // The V matrix will be the common diagonalizer matrix that we use. autoNUMmatrix d (1, dimension, 1, dimension); for (long i = 1; i <= dimension; i++) { // Generate the rotation matrix for (long j = 1; j <= dimension; j++) { d[i][j] = NUMrandomGauss (0, 1); } } autoNUMmatrix v (1, dimension, 1, dimension); autoSVD svd = SVD_create_d (d.peek(), dimension, dimension); autoCrossCorrelationTables me = CrossCorrelationTables_create (); for (long i = 1; i <= dimension; i++) { for (long j = 1; j <= dimension; j++) { d[i][j] = 0; } } // Start with a diagonal matrix D and calculate V'DV for (long k = 1; k <= n; k++) { autoCrossCorrelationTable ct = CrossCorrelationTable_create (dimension); double low = k == 1 && firstPositiveDefinite ? 0.1 : -1; for (long i = 1; i <= dimension; i++) { d[i][i] = NUMrandomUniform (low, 1); } for (long i = 1; i <= dimension; i++) { for (long j = 1; j <= dimension; j++) { v[i][j] = NUMrandomGauss (svd -> v[i][j], sigma); } } // we need V'DV, however our V has eigenvectors row-wise -> VDV' NUMdmatrices_multiply_VCVp (ct -> data, v.peek(), dimension, dimension, d.peek(), 1); Collection_addItem (me.peek(), ct.transfer()); } return me.transfer(); } catch (MelderError) { Melder_throw ("CrossCorrelationTables test set not created."); } } static void Sound_and_MixingMatrix_improveUnmixing_fica (Sound me, MixingMatrix thee, long maxNumberOfIterations, double tol, int method) { (void) tol; (void) method; try { long iter = 0; if (my ny != thy numberOfColumns) { Melder_throw ("Dimensions do not agree."); } autoNUMmatrix x (NUMmatrix_copy (my z, 1, my ny, 1, my nx), 1, 1); do { iter++; } while (/*fabs((dm_old - dm_new) / dm_new) > tol &&*/ iter < maxNumberOfIterations); } catch (MelderError) { Melder_throw (me, " & ", thee, " ."); } } /* End of file ICA.cpp 987*/ sources_5316/dwtools/ContingencyTable.h0000644000176700017670000000162511627173520017027 0ustar paulpaul#ifndef _ContingencyTable_h_ #define _ContingencyTable_h_ #include "TableOfReal.h" #include "Confusion.h" Thing_define (ContingencyTable, TableOfReal) { // overridden methods: virtual void v_info (); }; // entries must be nonnegative numbers ContingencyTable ContingencyTable_create (long numberOfRows, long numberOfColumns); double ContingencyTable_chisqProbability (ContingencyTable me); double ContingencyTable_cramersStatistic (ContingencyTable me); double ContingencyTable_contingencyCoefficient (ContingencyTable me); void ContingencyTable_chisq (ContingencyTable me, double *chisq, long *df); void ContingencyTable_entropies (ContingencyTable me, double *h, double *hx, double *hy, double *hygx, double *hxgy, double *uygx, double *uxgy, double *uxy); ContingencyTable Confusion_to_ContingencyTable (Confusion me); ContingencyTable TableOfReal_to_ContingencyTable (I); #endif // _ContingencyTable_h_ sources_5316/dwtools/Eigen_and_TableOfReal.cpp0000644000176700017670000000646511752704002020204 0ustar paulpaul/* Eigen_and_TableOfReal.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020327 Initial version. djmw 20020429 _project: copy rowLabels too. djmw 20020502 Added from index to projections. djmw 20020813 GPL header djmw 20110304 Thing_new */ #include "Eigen_and_TableOfReal.h" #include "NUM2.h" TableOfReal Eigen_and_TableOfReal_project (I, thou, long from, long numberOfComponents) { try { iam (Eigen); thouart (TableOfReal); if (numberOfComponents == 0) { numberOfComponents = my numberOfEigenvalues; } autoTableOfReal him = TableOfReal_create (thy numberOfRows, numberOfComponents); TableOfReal thim = him.peek(); Eigen_and_TableOfReal_project_into (me, thee, from, thy numberOfColumns, &thim, 1, numberOfComponents); NUMstrings_copyElements (thy rowLabels, his rowLabels, 1, thy numberOfRows); return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal not created from projection."); } } void Eigen_and_TableOfReal_project_into (I, thou, long thee_from, long thee_to, Any void_pointer_to_him, long his_from, long his_to) { TableOfReal him = * ( (TableOfReal *) void_pointer_to_him); thouart (TableOfReal); iam (Eigen); long thee_ncols = thee_to - thee_from + 1; long his_ncols = his_to - his_from + 1; if (thee_from < 1 || thee_to > thy numberOfColumns || his_from < 1 || his_to > his numberOfColumns) { Melder_throw (L"Column selection not correct."); } if (thee_ncols != my dimension) { Melder_throw ("The number of selected columns to project (", thee_ncols, ") must equal the dimension of the eigenvectors (", my dimension, ")."); } if (his_ncols > my numberOfEigenvalues) { Melder_throw ("The number of selected columns in the result (", his_ncols, ") cannot exceed the number of eigenvectors (", my numberOfEigenvalues, ")."); } for (long i = 1; i <= thy numberOfRows; i++) { /* row */ for (long j = 1; j <= his_ncols; j++) { double r = 0; for (long k = 1; k <= my dimension; k++) { /* eigenvector in row, data in row */ r += my eigenvectors[j][k] * thy data[i][thee_from + k - 1]; } his data[i][his_from + j - 1] = r; } } } Eigen TablesOfReal_to_Eigen_gsvd (TableOfReal me, TableOfReal thee) { try { if (my numberOfColumns != thy numberOfColumns) { Melder_throw ("TablesOfReal_to_Eigen: Number of columns must be equal."); } autoEigen him = Thing_new (Eigen); Eigen_initFromSquareRootPair (him.peek(), my data, my numberOfRows, my numberOfColumns, thy data, thy numberOfRows); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": Eigen not created."); } } /* End of file Eigen_and_TableOfReal.cpp */ sources_5316/dwtools/.manual_dwtools.cpp.kate-swp0000664000176700017670000000244511757230014020771 0ustar paulpaulKate Swap File - Version 1.0SRdüýESIdx"ESWdyESIe ESIe"ESIer"ESWesIf ESIf"ESIfs"ESWftIg ESIg"ESIg”"ESWg•RhIh ESIh"ESIh¢"ESWh£Ii ESIi"ESIi"ESWiIj ESIj"ESUkESIjY ESIjc"ESWjdIk ESIk"ESIqc"ESWqdESIr ESIr"ESIr­ ESIr®aESIr¯tESIr° ESIr±aESIr²lESIr³lESIr¶"ESWr·Is ESIs"ESIs©"ESWsªIt ESIt"ESIt°"ESWt±RuIu ESIu"ESIt° ESIˆ¦"ESWˆ§ESI‰ ESI‰"ESI‰Û"ESW‰ÜIŠ ESIŠ"ESI‹©"ESW‹ªESIŒ ESIŒ"ESIŒ¨"ESWŒ©I ESI"ESI›"ESWœIŽ ESIŽ"ESIý"ESWþESIž ESIž"ESIž"ESWžIŸ ESIŸ"ESIŸœ"ESWŸI  ESI "Esources_5316/dwtools/KlattGrid.cpp0000664000176700017670000033530011756574041016027 0ustar paulpaul/* KlattGrid.cpp * * Copyright (C) 2008-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20080917 Initial version djmw 20090109 Add formulas for formant frequencies and bandwidths. djmw 20090123 Add PlayOptions. djmw 20090129 KlattGrid_draw text in boxes displays better djmw 20090311 Add RealTier_valuesInRange djmw 20090312 Add klattGrid_addFormantAndBandwidthTier djmw 20090326 Changed DBSPL_to_A into DB_to_A for bypass and formant amplitudes. djmw 20100223 Removed gsl dependency djmw 20110304 Thing_new djmw 20110308 struc connections -> struct structconnections djmw 20110329 Table_get(Numeric|String)Value is now Table_get(Numeric|String)Value_Assert djmw 20111011 Sound_VocalTractGrid_CouplingGrid_filter_cascade: group warnings */ #include "FormantGrid_extensions.h" #include "Formula.h" #include "KlattGrid.h" #include "KlattTable.h" #include "Resonator.h" #include "Pitch_to_PitchTier.h" #include "PitchTier_to_Sound.h" #include "PitchTier_to_PointProcess.h" #include "NUM2.h" #include "Sound_to_Formant.h" #include "Sound_to_Intensity.h" #include "Sound_to_Pitch.h" #include "oo_DESTROY.h" #include "KlattGrid_def.h" #include "oo_COPY.h" #include "KlattGrid_def.h" #include "oo_EQUAL.h" #include "KlattGrid_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "KlattGrid_def.h" #include "oo_WRITE_TEXT.h" #include "KlattGrid_def.h" #include "oo_WRITE_BINARY.h" #include "KlattGrid_def.h" #include "oo_READ_TEXT.h" #include "KlattGrid_def.h" #include "oo_READ_BINARY.h" #include "KlattGrid_def.h" #include "oo_DESCRIPTION.h" #include "KlattGrid_def.h" // Prototypes PointProcess PitchTier_to_PointProcess_flutter (PitchTier pitch, RealTier flutter, double maximumPeriod); void _Sound_FormantGrid_filterWithOneFormant_inline (Sound me, thou, long iformant, int antiformant); Sound Sound_VocalTractGrid_CouplingGrid_filter_parallel (Sound me, VocalTractGrid thee, CouplingGrid coupling); Sound PhonationGrid_PhonationTier_to_Sound_voiced (PhonationGrid me, PhonationTier thee, double samplingFrequency); Sound KlattGrid_to_Sound_aspiration (KlattGrid me, double samplingFrequency); #undef MIN #undef MAX #define MIN(x,y) ((x) < (y) ? (x) : (y)) #define MAX(x,y) ((x) > (y) ? (x) : (y)) #define KlattGrid_OPENPHASE_DEFAULT 0.7 #define KlattGrid_POWER1_DEFAULT 3 #define KlattGrid_POWER2_DEFAULT (KlattGrid_POWER1_DEFAULT+1) /* Amplitude scaling: maximum amplitude (-1,+1) corresponds to 91 dB */ /*static double NUMinterpolateLinear (double x1, double y1, double x2, double y2, double x) { if (y1 == y2) return y1; if (x1 == x2) return NUMundefined; return (y2 - y1) * (x - x1) / (x2 - x1) + y1; }*/ static void rel_to_abs (double *w, double *ws, long n, double d) { double sum = 0; for (long i = 1; i <= n; i++) { // relative sum += w[i]; } if (sum != 0) { double dw = d / sum; sum = 0; for (long i = 1; i <= n; i++) { // to absolute w[i] *= dw; sum += w[i]; ws[i] = sum; } } } static bool RealTier_valuesInRange (I, double min, double max) { iam (RealTier); for (long i = 1; i <= my points -> size; i++) { RealPoint p = (RealPoint) my points -> item[i]; if (NUMdefined (min) && p -> value < min) { return false; } if (NUMdefined (max) && p -> value < max) { return false; } } return true; } static double PointProcess_getPeriodAtIndex (PointProcess me, long it, double maximumPeriod) { double period = NUMundefined; if (it >= 2) { period = my t[it] - my t[it - 1]; if (period > maximumPeriod) { period = NUMundefined; } } if (period == NUMundefined) { if (it < my nt) { period = my t[it + 1] - my t[it]; if (period > maximumPeriod) { period = NUMundefined; } } } // NUMundefined can only occur for a single isolated pulse. return period; } #define UPDATE_TIER RealTier_addPoint (thee.peek(), mytime, myvalue); \ lasttime=mytime; myindex++; \ if (myindex <= numberOfValues)\ {\ mypoint = (RealPoint) my points -> item [myindex];\ mytime = mypoint -> number; myvalue = mypoint -> value;\ }\ else mytime = my xmax;\ static RealTier RealTier_updateWithDelta (RealTier me, RealTier delta, PhonationTier glottis, double openglottis_fadeFraction) { try { long myindex = 1; RealPoint mypoint = (RealPoint) my points -> item [myindex]; long numberOfValues = my points -> size; double mytime = mypoint -> number; double myvalue = mypoint -> value; double lasttime = my xmin - 0.001; // sometime before xmin autoRealTier thee = RealTier_create (my xmin, my xmax); if (openglottis_fadeFraction <= 0) { openglottis_fadeFraction = 0.0001; } if (openglottis_fadeFraction >= 0.5) { openglottis_fadeFraction = 0.4999; } for (long ipoint = 1; ipoint <= glottis -> points -> size; ipoint++) { PhonationPoint point = (PhonationPoint) glottis -> points -> item [ipoint]; double t4 = point -> time; // glottis closing double openDuration = point -> te ; double t1 = t4 - openDuration; double t2 = t1 + openglottis_fadeFraction * openDuration; double t3 = t4 - openglottis_fadeFraction * openDuration; // Add my points that lie before t1 and after previous t4 while (mytime > lasttime && mytime < t1) { UPDATE_TIER } if (t2 > t1) { // Set new value at t1 double myvalue1 = RealTier_getValueAtTime (me, t1); RealTier_addPoint (thee.peek(), t1, myvalue1); // Add my points between t1 and t2 while (mytime > lasttime && mytime < t2) { double dvalue = RealTier_getValueAtTime (delta, mytime); if (NUMdefined (dvalue)) { double fraction = (mytime - t1) / (openglottis_fadeFraction * openDuration); myvalue += dvalue * fraction; } UPDATE_TIER } } double myvalue2 = RealTier_getValueAtTime (me, t2); double dvalue = RealTier_getValueAtTime (delta, t2); if (NUMdefined (dvalue)) { myvalue2 += dvalue; } RealTier_addPoint (thee.peek(), t2, myvalue2); // Add points between t2 and t3 while (mytime > lasttime && mytime < t3) { dvalue = RealTier_getValueAtTime (delta, mytime); if (NUMdefined (dvalue)) { myvalue += dvalue; } UPDATE_TIER } // set new value at t3 double myvalue3 = RealTier_getValueAtTime (me, t3); dvalue = RealTier_getValueAtTime (delta, t3); if (NUMdefined (dvalue)) { myvalue3 += dvalue; } RealTier_addPoint (thee.peek(), t3, myvalue3); if (t4 > t3) { // Add my points between t3 and t4 while (mytime > lasttime && mytime < t4) { dvalue = RealTier_getValueAtTime (delta, mytime); if (NUMdefined (dvalue)) { double fraction = 1 - (mytime - t3) / (openglottis_fadeFraction * openDuration); myvalue += dvalue * fraction; } UPDATE_TIER } // Set new value at t4 double myvalue4 = RealTier_getValueAtTime (me, t4); RealTier_addPoint (thee.peek(), t4, myvalue4); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not updated with delta."); } } static bool FormantGrid_isFormantDefined (FormantGrid me, long iformant) { RealTier ftier = (RealTier) my formants -> item[iformant]; RealTier btier = (RealTier) my bandwidths -> item[iformant]; return ftier -> points -> size != 0 and btier -> points -> size != 0; } static bool FormantGrid_Intensities_isFormantDefined (FormantGrid me, Ordered thee, long iformant) { RealTier ftier = (RealTier) my formants -> item[iformant]; RealTier btier = (RealTier) my bandwidths -> item[iformant]; RealTier atier = (RealTier) thy item[iformant]; return ftier -> points -> size != 0 and btier -> points -> size != 0 and atier -> points -> size != 0; } static void check_formants (long numberOfFormants, long *ifb, long *ife) { if (numberOfFormants <= 0 || *ifb > numberOfFormants || *ife < *ifb || *ife < 1) { *ife = 0; // overrules everything *ifb value is a don't care now return; } if (*ifb <= 1) { *ifb = 1; } if (*ife > numberOfFormants) { *ife = numberOfFormants; } } static Sound Sound_createEmptyMono (double xmin, double xmax, double samplingFrequency) { long nt = ceil ( (xmax - xmin) * samplingFrequency); double dt = 1.0 / samplingFrequency; double tmid = (xmin + xmax) / 2; double t1 = tmid - 0.5 * (nt - 1) * dt; return Sound_create (1, xmin, xmax, nt, dt, t1); } static void _Sounds_add_inline (Sound me, Sound thee) { for (long i = 1; i <= my nx; i++) { my z[1][i] += thy z[1][i]; } } static Sound _Sound_diff (Sound me, int scale) { try { autoSound thee = Data_copy (me); // extremum double amax1 = -1.0e34, amax2 = amax1, val, pval = 0; if (scale) { for (long i = 1; i <= thy nx; i++) { val = fabs (thy z[1][i]); if (val > amax1) { amax1 = val; } } } // x[n]-x[n-1] for (long i = 1; i <= thy nx; i++) { val = thy z[1][i]; thy z[1][i] -= pval; pval = val; } if (scale) { for (long i = 1; i <= thy nx; i++) { val = fabs (thy z[1][i]); if (val > amax2) { amax2 = val; } } // scale for (long i = 1; i <= thy nx; i++) { thy z[1][i] *= amax1 / amax2; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not differenced."); } } /*static void _Sounds_addDifferentiated_inline (Sound me, Sound thee) { double pval = 0, dx = my dx; for (long i = 1; i <= my nx; i++) { double val = thy z[1][i]; my z[1][i] += (val - pval) / dx; // dx makes amplitude of dz/dt independent of sampling. pval = val; } }*/ typedef struct structconnections { long numberOfConnections; double *x, *y; } *connections; static void connections_free (connections me) { if (me == NULL) { return; } NUMvector_free (my x, 1); NUMvector_free (my y, 1); Melder_free (me); } static connections connections_create (long numberOfConnections) { connections me = 0; try { me = (connections) Melder_malloc (structconnections, 1); my numberOfConnections = numberOfConnections; my x = NUMvector (1, numberOfConnections); my y = NUMvector (1, numberOfConnections); return me; } catch (MelderError) { connections_free (me); Melder_throw ("Connections not created."); } } // Calculates the intersection point (xi,yi) of a line with a circle. // The line starts at the origin and P (xp, yp) is on that line. static void NUMcircle_radial_intersection_sq (double x, double y, double r, double xp, double yp, double *xi, double *yi) { double dx = xp - x, dy = yp - y; double d = sqrt (dx * dx + dy * dy); if (d > 0) { *xi = x + dx * r / d; *yi = y + dy * r / d; } else { *xi = *yi = NUMundefined; } } static void summer_draw (Graphics g, double x, double y, double r, int alternating) { Graphics_setLineWidth (g, 2); Graphics_circle (g, x, y, r); double dy = 3 * r / 4; // + symbol if (alternating) { y += r / 4; } Graphics_line (g, x, y + r / 2, x, y - r / 2); Graphics_line (g, x - r / 2, y, x + r / 2, y); if (alternating) { Graphics_line (g, x - r / 2, y - dy , x + r / 2, y - dy); } } static void _summer_drawConnections (Graphics g, double x, double y, double r, connections thee, int arrow, int alternating, double horizontalFraction) { summer_draw (g, x, y, r, alternating); for (long i = 1; i <= thy numberOfConnections; i++) { double xto, yto, xp = thy x[i], yp = thy y[i]; if (horizontalFraction > 0) { double dx = x - xp; if (dx > 0) { xp += horizontalFraction * dx; Graphics_line (g, thy x[i], yp, xp, yp); } } NUMcircle_radial_intersection_sq (x, y, r, xp, yp, &xto, &yto); if (xto == NUMundefined || yto == NUMundefined) { continue; } if (arrow) { Graphics_arrow (g, xp, yp, xto, yto); } else { Graphics_line (g, xp, yp, xto, yto); } } } static void summer_drawConnections (Graphics g, double x, double y, double r, connections thee, int arrow, double horizontalFraction) { _summer_drawConnections (g, x, y, r, thee, arrow, 0, horizontalFraction); } static void alternatingSummer_drawConnections (Graphics g, double x, double y, double r, connections thee, int arrow, double horizontalFraction) { _summer_drawConnections (g, x, y, r, thee, arrow, 1, horizontalFraction); } static void draw_oneSection (Graphics g, double xmin, double xmax, double ymin, double ymax, const wchar_t *line1, const wchar_t *line2, const wchar_t *line3) { long numberOfTextLines = 0, iline = 0; Graphics_rectangle (g, xmin, xmax, ymin, ymax); if (line1 != 0) { numberOfTextLines++; } if (line2 != 0) { numberOfTextLines++; } if (line3 != 0) { numberOfTextLines++; } double y = ymax, dy = (ymax - ymin) / (numberOfTextLines + 1), ddy = dy / 10; double x = (xmax + xmin) / 2; if (line1 != 0) { iline++; y -= dy - (numberOfTextLines == 2 ? ddy : 0); // extra spacing for two lines Graphics_text1 (g, x, y, line1); } if (line2 != 0) { iline++; y -= dy - (numberOfTextLines == 2 ? (iline == 1 ? ddy : -iline * ddy) : 0); Graphics_text1 (g, x, y, line2); } if (line3 != 0) { iline++; y -= dy - (numberOfTextLines == 2 ? -iline * ddy : 0); Graphics_text1 (g, x, y, line3); } } // Maximum amplitue (-1,1) at 93.97940008672037 dB #define DBSPL_to_A(x) (pow (10.0, x / 20.0) * 2.0e-5) // Normal dB's #define DB_to_A(x) (pow (10.0, x / 20.0)) /********************* PhonationTier ************************/ Thing_implement (PhonationPoint, Data, 0); PhonationPoint PhonationPoint_create (double time, double period, double openPhase, double collisionPhase, double te, double power1, double power2, double pulseScale) { try { autoPhonationPoint me = Thing_new (PhonationPoint); my time = time; my period = period; my openPhase = openPhase; my collisionPhase = collisionPhase; my te = te; my power1 = power1; my power2 = power2; my pulseScale = pulseScale; return me.transfer(); } catch (MelderError) { Melder_throw ("PhonationPoint not created."); } } Thing_implement (PhonationTier, Function, 0); PhonationTier PhonationTier_create (double tmin, double tmax) { try { autoPhonationTier me = Thing_new (PhonationTier); Function_init (me.peek(), tmin, tmax); my points = SortedSetOfDouble_create (); return me.transfer(); } catch (MelderError) { Melder_throw ("PhonationTier not created."); } } PointProcess PhonationTier_to_PointProcess_closures (PhonationTier me) { try { long nt = my points -> size; autoPointProcess thee = PointProcess_create (my xmin, my xmax, nt); for (long ip = 1; ip <= nt; ip++) { PhonationPoint fp = (PhonationPoint) my points -> item[ip]; PointProcess_addPoint (thee.peek(), fp -> time); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no PointProcess with closure times created."); } } /********************** PhonationGridPlayOptions **********************/ Thing_implement (PhonationGridPlayOptions, Data, 0); static void PhonationGridPlayOptions_setDefaults (PhonationGridPlayOptions me) { my flowDerivative = my voicing = 1; my aspiration = my breathiness = 1; my flutter = my doublePulsing = 1; my collisionPhase = my spectralTilt = 1; my flowFunction = 1; // User defined flow tiers (power1 & power2) my maximumPeriod = 0; } PhonationGridPlayOptions PhonationGridPlayOptions_create () { try { autoPhonationGridPlayOptions me = Thing_new (PhonationGridPlayOptions); return me.transfer(); } catch (MelderError) { Melder_throw ("PhonationGridPlayOptions not created."); } } /********************** PhonationGrid **********************/ Thing_implement (PhonationGrid, Function, 0); void structPhonationGrid :: v_info () { structData :: v_info (); const wchar_t *in1 = L" ", *in2 = L" "; MelderInfo_writeLine2 (in1, L"Time domain:"); MelderInfo_writeLine4 (in2, L"Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine4 (in2, L"End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine4 (in2, L"Total duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine2 (in1, L"\nNumber of points in the PHONATION tiers:"); MelderInfo_writeLine3 (in2, L"pitch: ", Melder_integer (pitch -> points -> size)); MelderInfo_writeLine3 (in2, L"voicingAmplitude: ", Melder_integer (voicingAmplitude -> points -> size)); MelderInfo_writeLine3 (in2, L"openPhase: ", Melder_integer (openPhase -> points -> size)); MelderInfo_writeLine3 (in2, L"collisionPhase: ", Melder_integer (collisionPhase -> points -> size)); MelderInfo_writeLine3 (in2, L"power1: ", Melder_integer (power1 -> points -> size)); MelderInfo_writeLine3 (in2, L"power2: ", Melder_integer (power2 -> points -> size)); MelderInfo_writeLine3 (in2, L"flutter: ", Melder_integer (flutter -> points -> size)); MelderInfo_writeLine3 (in2, L"doublePulsing: ", Melder_integer (doublePulsing -> points -> size)); MelderInfo_writeLine3 (in2, L"spectralTilt: ", Melder_integer (spectralTilt -> points -> size)); MelderInfo_writeLine3 (in2, L"aspirationAmplitude: ", Melder_integer (aspirationAmplitude -> points -> size)); MelderInfo_writeLine3 (in2, L"breathinessAmplitude:", Melder_integer (breathinessAmplitude -> points -> size)); } void PhonationGrid_setNames (PhonationGrid me) { Thing_setName (my pitch, L"pitch"); Thing_setName (my voicingAmplitude, L"voicingAmplitude"); Thing_setName (my openPhase, L"openPhase"); Thing_setName (my collisionPhase, L"collisionPhase"); Thing_setName (my power1, L"power1"); Thing_setName (my power2, L"power2"); Thing_setName (my flutter, L"flutter"); Thing_setName (my doublePulsing, L"doublePulsing"); Thing_setName (my spectralTilt, L"spectralTilt"); Thing_setName (my aspirationAmplitude, L"aspirationAmplitude"); Thing_setName (my breathinessAmplitude, L"breathinessAmplitude"); } PhonationGrid PhonationGrid_create (double tmin, double tmax) { try { autoPhonationGrid me = Thing_new (PhonationGrid); Function_init (me.peek(), tmin, tmax); my pitch = PitchTier_create (tmin, tmax); my voicingAmplitude = IntensityTier_create (tmin, tmax); my openPhase = RealTier_create (tmin, tmax); my collisionPhase = RealTier_create (tmin, tmax); my power1 = RealTier_create (tmin, tmax); my power2 = RealTier_create (tmin, tmax); my flutter = RealTier_create (tmin, tmax); my doublePulsing = RealTier_create (tmin, tmax); my spectralTilt = IntensityTier_create (tmin, tmax); my aspirationAmplitude = IntensityTier_create (tmin, tmax); my breathinessAmplitude = IntensityTier_create (tmin, tmax); my options = PhonationGridPlayOptions_create (); PhonationGrid_setNames (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("PhonationGrid not created."); } } static void PhonationGrid_checkFlowFunction (PhonationGrid me) { int hasPower1Points = my power1 -> points -> size > 0; int hasPower2Points = my power2 -> points -> size > 0; long ipoint = 1; do { double time = hasPower1Points ? ( (RealPoint) (my power1 -> points -> item[ipoint])) -> number : 0.5 * (my xmin + my xmax); double power1 = RealTier_getValueAtIndex (my power1, ipoint); if (power1 == NUMundefined) { power1 = KlattGrid_POWER1_DEFAULT; } if (power1 <= 0) { Melder_throw ("All power1 values must greater than zero."); } double power2 = RealTier_getValueAtTime (my power2, time); if (power2 == NUMundefined) { power2 = KlattGrid_POWER2_DEFAULT; } if (power2 <= power1) { Melder_throw ("At all times a power1 value must be smaller than the corresponding power2 value."); } } while (++ipoint < my power1 -> points -> size); // Now check power2 values. This is necessary to catch situations where power2 has a valley: // power1(0) = 3; power2(1)= 4; power2(1)= 4; power2(0.5) = 3; ipoint = 1; do { double time = hasPower2Points ? ( (RealPoint) (my power2 -> points -> item[ipoint])) -> number : 0.5 * (my xmin + my xmax); double power2 = RealTier_getValueAtIndex (my power2, ipoint); if (power2 == NUMundefined) { power2 = KlattGrid_POWER2_DEFAULT; } double power1 = RealTier_getValueAtTime (my power1, time); if (power1 == NUMundefined) { power1 = KlattGrid_POWER1_DEFAULT; } if (power2 <= power1) { Melder_throw ("At all times the power2 value must be greater than the corresponding power1 value."); } } while (++ipoint < my power2 -> points -> size); } static void PhonationGrid_draw_inside (PhonationGrid me, Graphics g, double xmin, double xmax, double ymin, double ymax, double dy, double *yout) { // dum voicing conn tilt conn summer (void) me; double xw[6] = { 0, 1, 0.5, 1, 0.5, 0.5 }, xws[6]; connections thee = connections_create (2); rel_to_abs (xw, xws, 5, xmax - xmin); dy = (ymax - ymin) / (1 + (dy < 0 ? 0 : dy) + 1); double x1 = xmin, x2 = x1 + xw[1]; double y2 = ymax, y1 = y2 - dy; draw_oneSection (g, x1, x2, y1, y2, NULL, L"Voicing", 0); x1 = x2; x2 = x1 + xw[2]; double ymid = (y1 + y2) / 2; Graphics_line (g, x1, ymid, x2, ymid); x1 = x2; x2 = x1 + xw[3]; draw_oneSection (g, x1, x2, y1, y2, NULL, L"Tilt", 0); thy x[1] = x2; thy y[1] = ymid; y2 = y1 - 0.5 * dy; y1 = y2 - dy; ymid = (y1 + y2) / 2; x2 = xmin + xws[3]; x1 = x2 - 1.5 * xw[3]; // some extra space draw_oneSection (g, x1, x2, y1, y2, NULL, L"Aspiration", 0); thy x[2] = x2; thy y[2] = ymid; double r = xw[5] / 2; double xs = xmax - r, ys = (ymax + ymin) / 2; int arrow = 1; summer_drawConnections (g, xs, ys, r, thee, arrow, 0.4); connections_free (thee); if (yout != 0) { *yout = ys; } } void PhonationGrid_draw (PhonationGrid me, Graphics g) { double xmin = 0, xmax2 = 0.9, xmax = 1, ymin = 0, ymax = 1, dy = 0.5, yout; Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); PhonationGrid_draw_inside (me, g, xmin, xmax2, ymin, ymax, dy, &yout); Graphics_arrow (g, xmax2, yout, xmax, yout); Graphics_unsetInner (g); } double PhonationGrid_getMaximumPeriod (PhonationGrid me) { double minimumPitch = RealTier_getMinimumValue (my pitch); return 2 / ( (minimumPitch == NUMundefined || minimumPitch == 0) ? (my xmax - my xmin) : minimumPitch); } PointProcess PitchTier_to_PointProcess_flutter (PitchTier pitch, RealTier flutter, double maximumPeriod) { try { autoPointProcess thee = PitchTier_to_PointProcess (pitch); if (flutter == 0) { return thee.transfer(); } double tsum = 0; for (long it = 2; it <= thy nt; it++) { double t = thy t[it - 1]; double period = thy t[it] - thy t[it - 1]; if (period < maximumPeriod && flutter -> points -> size > 0) { double fltr = RealTier_getValueAtTime (flutter, t); if (NUMdefined (fltr)) { // newF0 = f0 * (1 + (val / 50) * (sin ... + ...)); double newPeriod = period / (1 + (fltr / 50) * (sin (2 * NUMpi * 12.7 * t) + sin (2 * NUMpi * 7.1 * t) + sin (2 * NUMpi * 4.7 * t))); tsum += newPeriod - period; } } thy t[it] += tsum; } return thee.transfer(); } catch (MelderError) { Melder_throw (pitch, ": no flutter PointProcess created."); } } Sound PhonationGrid_to_Sound_aspiration (PhonationGrid me, double samplingFrequency) { try { autoSound thee = Sound_createEmptyMono (my xmin, my xmax, samplingFrequency); // Noise spectrum is tilted down by soft low-pass filter having a pole near // the origin in the z-plane, i.e. y[n] = x[n] + (0.75 * y[n-1]) double lastval = 0; if (my aspirationAmplitude -> points -> size > 0) { for (long i = 1; i <= thy nx; i++) { double t = thy x1 + (i - 1) * thy dx; double val = NUMrandomUniform (-1, 1); double a = DBSPL_to_A (RealTier_getValueAtTime (my aspirationAmplitude, t)); if (NUMdefined (a)) { thy z[1][i] = lastval = val + 0.75 * lastval; lastval = (val += 0.75 * lastval); // soft low-pass thy z[1][i] = val * a; } } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no aspiration Sound created."); } } static void Sound_PhonationGrid_spectralTilt_inline (Sound thee, PhonationGrid me) { if (my spectralTilt -> points -> size > 0) { /* Spectral tilt Filter y[n] = a * x[n] + b * y[n-1] => H(z) = a / (1 - bz^(-1)). We need attenuation, i.e. low-pass. Therefore 0 <= b <= 1. |H(f)| = a / sqrt (1 - 2*b*cos(2*pi*f*T) + b^2), |H(0)|= a /(1 - b) => if |H(0)| == 1, then a = 1 - b. Now solve 20 log|H(F)|= -c (at F=3 kHz and c > 0) Solution: if q = (1 - D * cos(2*pi*F*T)) / (1 - D), with D = 10^(-c/10) then b = q -sqrt(q^2 - 1) */ double cosf = cos (2 * NUMpi * 3000 * thy dx), ynm1 = 0; // samplingFrequency > 6000 ! for (long i = 1; i <= thy nx; i++) { double t = thy x1 + (i - 1) * thy dx; double tilt_db = RealTier_getValueAtTime (my spectralTilt, t); if (tilt_db > 0) { double d = pow (10, -tilt_db / 10); double q = (1 - d * cosf) / (1 - d); double b = q - sqrt (q * q - 1); double a = 1 - b; thy z[1][i] = a * thy z[1][i] + b * ynm1; ynm1 = thy z[1][i]; } } } } struct nrfunction_struct { double n; double m; double a; }; static void nrfunction (double x, double *fx, double *dfx, void *closure) { struct nrfunction_struct *nrfs = (struct nrfunction_struct *) closure; double mplusax = nrfs -> m + nrfs -> a * x; double mminn = nrfs -> m - nrfs -> n; *fx = pow (x, mminn) - (nrfs -> n + nrfs -> a * x) / mplusax; *dfx = mminn * pow (x, mminn - 1) - nrfs -> a * mminn / (mplusax * mplusax); } static double get_collisionPoint_x (double n, double m, double collisionPhase) { double y = NUMundefined; /* Domain [0,1]: The glottal flow is given by: U(y) = y^n - y^m 0<= y <= x, and m > n (x^n - x^m)exp(-a(y-x)) y >= x, where a = 1 / collisionPhase The x where this occurs is the point where the amplitudes as well as the derivatives are equal. I.e. the x where n x^(n-1) - m x^(m-1) = (x^n-x^m)(-a). This can be simplified: find x in (0,1) where f(x) = x^(m-n) - (n+ax)/(m+ax) == 0. For m - n == 1, f(x) is a second order equation f(x)= a x^2 + (m-a) x - n == 0. In all other cases we solve with Newton-Raphson. For these cases we also need the derivative: f'(x)= (m - n)x^(m - n - 1)- a(m - n) / (m + a x)^2 */ if (collisionPhase <= 0) { return 1; } double a = 1 / collisionPhase; if (m - n == 1) { double b = m - a; double c = - n, y1, y2; long nroots = NUMsolveQuadraticEquation (a, b, c, &y1, &y2); if (nroots == 2) { y = y2; } else if (nroots == 1) { y = y1; } } else { // Newton-Raphson // search in the interval from where the flow is a maximum to 1 struct nrfunction_struct nrfs = {n, m, a}; double root, xmaxFlow = pow (n / m, 1.0 / (m - n)); NUMnrbis (&nrfunction, xmaxFlow, 1, &nrfs, &root); y = root; } return y; } PhonationTier PhonationGrid_to_PhonationTier (PhonationGrid me) { try { long diplophonicPulseIndex = 0; PhonationGridPlayOptions pp = my options; PhonationGrid_checkFlowFunction (me); if (my pitch -> points -> size == 0) { Melder_throw ("Pitch tier is empty."); } if (pp -> maximumPeriod == 0) { pp -> maximumPeriod = PhonationGrid_getMaximumPeriod (me); } autoPointProcess point = PitchTier_to_PointProcess_flutter (my pitch, (pp -> flutter ? my flutter : 0), pp -> maximumPeriod); autoPhonationTier thee = PhonationTier_create (my xmin, my xmax); /* Cycle through the points of the point PointProcess. Each will become a period. We assume that the planning for the pitch period occurs approximately at a time T before the glottal closure. For each point t[i]: Determine the f0 -> period T[i] Determine time t[i]-T[i] the open quotient, power1, power2, collisionphase etc. Generate the period. */ for (long it = 1; it <= point -> nt; it++) { double re, t = point -> t[it]; // the glottis "closing" point double pulseDelay = 0; // For alternate pulses in case of diplophonia double pulseScale = 1; // For alternate pulses in case of diplophonia double period = PointProcess_getPeriodAtIndex (point.peek(), it, pp -> maximumPeriod); if (period == NUMundefined) { period = 0.5 * pp -> maximumPeriod; // Some default value } // Calculate the point where the exponential decay starts: // Query tiers where period starts . double periodStart = t - period; // point where period starts: double collisionPhase = pp -> collisionPhase ? RealTier_getValueAtTime (my collisionPhase, periodStart) : 0; if (collisionPhase == NUMundefined) { collisionPhase = 0; } double power1 = pp -> flowFunction == 1 ? RealTier_getValueAtTime (my power1, periodStart) : pp -> flowFunction; if (power1 == NUMundefined) { power1 = KlattGrid_POWER1_DEFAULT; } double power2 = pp -> flowFunction == 1 ? RealTier_getValueAtTime (my power2, periodStart) : pp -> flowFunction + 1; if (power2 == NUMundefined) { power2 = KlattGrid_POWER2_DEFAULT; } try { re = get_collisionPoint_x (power1, power2, collisionPhase); } catch (MelderError) { Melder_warning (L"Illegal collision point at t = ", Melder_double (t), L" (power1=", Melder_double (power1), L", power2=", Melder_double (power2), L"colPhase=", Melder_double (collisionPhase), L")"); } double openPhase = RealTier_getValueAtTime (my openPhase, periodStart); if (openPhase == NUMundefined) { openPhase = KlattGrid_OPENPHASE_DEFAULT; } double te = re * period * openPhase; // In case of diplophonia alternate pulses get modified. // A modified puls is delayed in time and its amplitude attenuated. // This delay scales to maximally equal the closed phase of the next period. // The doublePulsing scales the amplitudes as well as the delay linearly. double doublePulsing = pp -> doublePulsing ? RealTier_getValueAtTime (my doublePulsing, periodStart) : 0; if (doublePulsing == NUMundefined) { doublePulsing = 0; } if (doublePulsing > 0) { diplophonicPulseIndex++; if (diplophonicPulseIndex % 2 == 1) { // the odd one double nextPeriod = PointProcess_getPeriodAtIndex (point.peek(), it + 1, pp -> maximumPeriod); if (nextPeriod == NUMundefined) { nextPeriod = period; } double openPhase2 = KlattGrid_OPENPHASE_DEFAULT; if (my openPhase -> points -> size > 0) { openPhase2 = RealTier_getValueAtTime (my openPhase, t); } double maxDelay = period * (1 - openPhase2); pulseDelay = maxDelay * doublePulsing; pulseScale *= (1 - doublePulsing); } } else { diplophonicPulseIndex = 0; } t += pulseDelay; autoPhonationPoint phonationPoint = PhonationPoint_create (t, period, openPhase, collisionPhase, te, power1, power2, pulseScale); AnyTier_addPoint (thee.peek(), phonationPoint.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no PhonationTier created."); } } Sound PhonationGrid_PhonationTier_to_Sound_voiced (PhonationGrid me, PhonationTier thee, double samplingFrequency) { try { PhonationGridPlayOptions p = my options; double lastVal = NUMundefined; if (my voicingAmplitude -> points -> size == 0) { Melder_throw ("Voicing amplitude tier is empty."); } autoSound him = Sound_createEmptyMono (my xmin, my xmax, samplingFrequency); autoSound breathy = 0; if (p -> breathiness && my breathinessAmplitude -> points -> size > 0) { breathy.reset (Sound_createEmptyMono (my xmin, my xmax, samplingFrequency)); } /* Cycle through the points of the PhonationTier. Each will become a period. We assume that the planning for the pitch period occurs approximately at a time T before the glottal closure. For each point t[i]: Determine the f0 -> period T[i] Determine time t[i]-T[i] the open quotient, power1, power2, collisionphase etc. Generate the period. */ double *sound = his z[1]; for (long it = 1; it <= thy points -> size; it++) { PhonationPoint point = (PhonationPoint) thy points -> item[it]; double t = point -> time; // the glottis "closing" point double te = point -> te; double period = point -> period; // duration of the current period double openPhase = point -> openPhase; double collisionPhase = point -> collisionPhase; double pulseScale = point -> pulseScale; // For alternate pulses in case of diplophonia double power1 = point -> power1, power2 = point -> power2; double phase; // 0..1 double flow; //- double amplitude = pulseScale * (power1 + power2 + 1.0) / (power2 - power1); //- amplitude /= period * openPhase; // Maximum of U(x) = x^n - x^m is where the derivative U'(x) = n x^(n-1) - m x^(m-1) == 0, // i.e. (n/m) = x^(m-n), so xmax = (n/m)^(1/(m-n)) // U(xmax) = x^n (1-x^(m-n)) = (n/m)^(n/(m-n))(1-n/m) double amplitude = pulseScale / (pow (power1 / power2, 1 / (power2 / power1 - 1)) * (1 - power1 / power2)); // Fill in the samples to the left of the current point. long midSample = Sampled_xToLowIndex (him.peek(), t), beginSample; beginSample = midSample - floor (te / his dx); if (beginSample < 1) { beginSample = 0; } if (midSample > his nx) { midSample = his nx; } for (long i = beginSample; i <= midSample; i++) { double tsamp = his x1 + (i - 1) * his dx; phase = (tsamp - (t - te)) / (period * openPhase); if (phase > 0.0) { flow = amplitude * (pow (phase, power1) - pow (phase, power2)); if (i == 0) { lastVal = flow; // For the derivative continue; } sound[i] += flow; // Breathiness only during open part modulated by the flow if (breathy.peek() != 0) { double val = flow * NUMrandomUniform (-1, 1); double a = RealTier_getValueAtTime (my breathinessAmplitude, t); breathy -> z[1][i] += val * DBSPL_to_A (a); } } } // Determine the signal parameters at the current point. phase = te / (period * openPhase); //- double flow = amplitude * (period * openPhase) * (pow (phase, power1) - pow (phase, power2)); flow = amplitude * (pow (phase, power1) - pow (phase, power2)); // Fill in the samples to the right of the current point. if (flow > 0.0) { double ta = collisionPhase * (period * openPhase); double factorPerSample = exp (- his dx / ta); double value = flow * exp (- (his x1 + midSample * his dx - t) / ta); long endSample = midSample + floor (20 * ta / his dx); if (endSample > his nx) { endSample = his nx; } for (long i = midSample + 1; i <= endSample; i++) { sound[i] += value; value *= factorPerSample; } } } // Scale voiced part and add breathiness during open phase if (p -> flowDerivative) { double extremum = Vector_getAbsoluteExtremum (him.peek(), 0, 0, Vector_VALUE_INTERPOLATION_CUBIC); if (! NUMdefined (lastVal)) { lastVal = 0; } for (long i = 1; i <= his nx; i++) { double val = his z[1][i]; his z[1][i] -= lastVal; lastVal = val; } Vector_scale (him.peek(), extremum); } for (long i = 1; i <= his nx; i++) { double t = his x1 + (i - 1) * his dx; his z[1][i] *= DBSPL_to_A (RealTier_getValueAtTime (my voicingAmplitude, t)); if (breathy.peek() != 0) { his z[1][i] += breathy -> z[1][i]; } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no Sound created."); } } static Sound PhonationGrid_to_Sound_voiced (PhonationGrid me, double samplingFrequency) { try { autoPhonationTier thee = PhonationGrid_to_PhonationTier (me); autoSound him = PhonationGrid_PhonationTier_to_Sound_voiced (me, thee.peek(), samplingFrequency); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no voiced Sound created."); } } static Sound PhonationGrid_to_Sound (PhonationGrid me, CouplingGrid him, double samplingFrequency) { try { PhonationGridPlayOptions pp = my options; autoSound thee = 0; if (pp -> voicing) { if (him != 0 && his glottis -> points -> size > 0) { thee.reset (PhonationGrid_PhonationTier_to_Sound_voiced (me, his glottis, samplingFrequency)); } else { thee.reset (PhonationGrid_to_Sound_voiced (me, samplingFrequency)); } if (pp -> spectralTilt) { Sound_PhonationGrid_spectralTilt_inline (thee.peek(), me); } } if (pp -> aspiration) { autoSound aspiration = PhonationGrid_to_Sound_aspiration (me, samplingFrequency); if (thee.peek() == 0) { thee.reset (aspiration.transfer()); } else { _Sounds_add_inline (thee.peek(), aspiration.peek()); } } if (thee.peek() == 0) { thee.reset (Sound_createEmptyMono (my xmin, my xmax, samplingFrequency)); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Sound created."); } } static Ordered formantsAmplitudes_create (double tmin, double tmax, long numberOfFormants) { try { autoOrdered me = Ordered_create (); for (long i = 1; i <= numberOfFormants; i++) { autoIntensityTier a = IntensityTier_create (tmin, tmax); Collection_addItem (me.peek(), a.transfer()); } return me.transfer(); } catch (MelderError) { Melder_throw ("No formants amplitudes created."); }; } /********************** VocalTractGridPlayOptions **********************/ Thing_implement (VocalTractGridPlayOptions, Data, 0); static void VocalTractGridPlayOptions_setDefaults (VocalTractGridPlayOptions me, VocalTractGrid thee) { my filterModel = KlattGrid_FILTER_CASCADE; my endOralFormant = MIN (thy oral_formants -> formants -> size, thy oral_formants -> bandwidths -> size); my startOralFormant = 1; my endNasalFormant = MIN (thy nasal_formants -> formants -> size, thy nasal_formants -> bandwidths -> size); my startNasalFormant = 1; my endNasalAntiFormant = MIN (thy nasal_antiformants -> formants -> size, thy nasal_antiformants -> bandwidths -> size); my startNasalAntiFormant = 1; } VocalTractGridPlayOptions VocalTractGridPlayOptions_create () { try { VocalTractGridPlayOptions me = Thing_new (VocalTractGridPlayOptions); return me; } catch (MelderError) { Melder_throw ("VocalTractGridPlayOptions not created."); } } /********************** VocalTractGrid ***************************************/ static long FormantGrid_getNumberOfFormantPoints (FormantGrid me, long iformant) { if (iformant < 1 || iformant > my formants -> size) { return -1; } RealTier f = (RealTier) my formants -> item[iformant]; return f -> points -> size; } static long FormantGrid_getNumberOfBandwidthPoints (FormantGrid me, long iformant) { if (iformant < 1 || iformant > my bandwidths -> size) { return -1; } RealTier b = (RealTier) my bandwidths -> item[iformant]; return b -> points -> size; } static long Ordered_getNumberOfAmplitudePoints (Ordered me, long iformant) { if (me == 0 || iformant < 1 || iformant > my size) { return -1; } RealTier t = (RealTier) my item[iformant]; return t -> points -> size; } static void FormantGrid_info (FormantGrid me, Ordered amplitudes, const wchar_t *in1, const wchar_t *in2) { long nformants = my formants -> size; long namplitudes = amplitudes != NULL ? amplitudes -> size : 0; long nmax = MAX (nformants, namplitudes); for (long iformant = 1; iformant <= nmax; iformant++) { MelderInfo_writeLine4 (in1, L"Formant ", Melder_integer (iformant), L":"); if (iformant <= my formants -> size) { long nfp = FormantGrid_getNumberOfFormantPoints (me, iformant); long nbp = FormantGrid_getNumberOfBandwidthPoints (me, iformant); MelderInfo_writeLine3 (in2, L"formants: ", (nfp >= 0 ? Melder_integer (nfp) : L"-- undefined --")); MelderInfo_writeLine3 (in2, L"bandwidths: ", (nbp >= 0 ? Melder_integer (nbp) : L"-- undefined --")); } if (amplitudes != NULL) { long nap = Ordered_getNumberOfAmplitudePoints (amplitudes, iformant); MelderInfo_writeLine3 (in2, L"amplitudes: ", (nap >= 0 ? Melder_integer (nap) : L"-- undefined --")); } } } void structVocalTractGrid :: v_info () { structData :: v_info (); const wchar_t *in1 = L" ", *in2 = L" ", *in3 = L" "; MelderInfo_writeLine2 (in1, L"Time domain:"); MelderInfo_writeLine4 (in2, L"Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine4 (in2, L"End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine4 (in2, L"Total duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine2 (in1, L"\nNumber of points in the ORAL FORMANT tiers:"); FormantGrid_info (oral_formants, oral_formants_amplitudes, in2, in3); MelderInfo_writeLine2 (in1, L"\nNumber of points in the NASAL FORMANT tiers:"); FormantGrid_info (nasal_formants, nasal_formants_amplitudes, in2, in3); MelderInfo_writeLine2 (in1, L"\nNumber of points in the NASAL ANTIFORMANT tiers:"); FormantGrid_info (nasal_antiformants, NULL, in2, in3); } Thing_implement (VocalTractGrid, Function, 0); void VocalTractGrid_setNames (VocalTractGrid me) { Thing_setName (my oral_formants, L"oral_formants"); Thing_setName (my nasal_formants, L"nasal_formants"); Thing_setName (my nasal_antiformants, L"nasal_antiformants"); Thing_setName (my oral_formants_amplitudes, L"oral_formants_amplitudes"); Thing_setName (my nasal_formants_amplitudes, L"nasal_formants_amplitudes"); } VocalTractGrid VocalTractGrid_create (double tmin, double tmax, long numberOfFormants, long numberOfNasalFormants, long numberOfNasalAntiFormants) { try { autoVocalTractGrid me = Thing_new (VocalTractGrid); Function_init (me.peek(), tmin, tmax); my oral_formants = FormantGrid_createEmpty (tmin, tmax, numberOfFormants); my nasal_formants = FormantGrid_createEmpty (tmin, tmax, numberOfNasalFormants); my nasal_antiformants = FormantGrid_createEmpty (tmin, tmax, numberOfNasalAntiFormants); my oral_formants_amplitudes = formantsAmplitudes_create (tmin, tmax, numberOfFormants); my nasal_formants_amplitudes = formantsAmplitudes_create (tmin, tmax, numberOfNasalFormants); my options = VocalTractGridPlayOptions_create (); VocalTractGrid_setNames (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("VocalTractGrid not created."); } } static void VocalTractGrid_CouplingGrid_drawCascade_inline (VocalTractGrid me, CouplingGrid thee, Graphics g, double xmin, double xmax, double ymin, double ymax, double *yin, double *yout) { long numberOfOralFormants = my oral_formants -> formants -> size; long numberOfNasalFormants = my nasal_formants -> formants -> size; long numberOfNasalAntiFormants = my nasal_antiformants -> formants -> size; long numberOfTrachealFormants = thee != NULL ? thy tracheal_formants -> formants -> size : 0; long numberOfTrachealAntiFormants = thee != NULL ? thy tracheal_antiformants -> formants -> size : 0; double x1, y1 = ymin, x2, y2 = ymax, dx, ddx = 0.2, ymid = (y1 + y2) / 2; const wchar_t *text[6] = { 0, L"TF", L"TAF", L"NF", L"NAF", L""}; long nf[6] = {0, numberOfTrachealFormants, numberOfTrachealAntiFormants, numberOfNasalFormants, numberOfNasalAntiFormants, numberOfOralFormants}; long numberOfXSections = 5, nsx = 0; MelderString ff = { 0 }, fb = { 0 }; long numberOfFilters = numberOfNasalFormants + numberOfNasalAntiFormants + numberOfTrachealFormants + numberOfTrachealAntiFormants + numberOfOralFormants; if (numberOfFilters == 0) { x2 = xmax; Graphics_line (g, xmin, ymid, x2, ymid); goto end; } for (long isection = 1; isection <= numberOfXSections; isection++) if (nf[isection] > 0) { nsx++; } dx = (xmax - xmin) / (numberOfFilters + (nsx - 1) * ddx); x1 = xmin; for (long isection = 1; isection <= numberOfXSections; isection++) { long numberOfFormants = nf[isection]; if (numberOfFormants == 0) { continue; } x2 = x1 + dx; for (long i = 1; i <= numberOfFormants; i++) { MelderString_append (&ff, L"F", Melder_integer (i)); MelderString_append (&fb, L"B", Melder_integer (i)); draw_oneSection (g, x1, x2, y1, y2, text[isection], ff.string, fb.string); if (i < numberOfFormants) { x1 = x2; x2 = x1 + dx; } MelderString_empty (&ff); MelderString_empty (&fb); } if (isection < numberOfXSections) { x1 = x2; x2 = x1 + ddx * dx; Graphics_line (g, x1, ymid, x2, ymid); x1 = x2; } } end: if (yin != 0) { *yin = ymid; } if (yout != 0) { *yout = ymid; } MelderString_free (&ff); MelderString_free (&fb); } static void VocalTractGrid_CouplingGrid_drawParallel_inline (VocalTractGrid me, CouplingGrid thee, Graphics g, double xmin, double xmax, double ymin, double ymax, double dy, double *yin, double *yout) { // (0: filler) (1: hor. line to split) (2: split to diff) (3: diff) (4: diff to split) // (5: split to filter) (6: filters) (7: conn to summer) (8: summer) double xw[9] = { 0, 0.3, 0.2, 1.5, 0.5, 0.5, 1, 0.5, 0.5 }, xws[9]; long numberOfXSections = 8, ic = 0, numberOfYSections = 4; long numberOfNasalFormants = my nasal_formants -> formants -> size; long numberOfOralFormants = my oral_formants -> formants -> size; long numberOfTrachealFormants = thee != NULL ? thy tracheal_formants -> formants -> size : 0; long numberOfFormants = numberOfNasalFormants + numberOfOralFormants + numberOfTrachealFormants; long numberOfUpperPartFormants = numberOfNasalFormants + (numberOfOralFormants > 0 ? 1 : 0); long numberOfLowerPartFormants = numberOfFormants - numberOfUpperPartFormants; double ddy = dy < 0 ? 0 : dy, x1, y1, x2, y2, x3, r, ymid; const wchar_t *text[5] = { 0, L"Nasal", L"", L"", L"Tracheal"}; long nffrom[5] = {0, 1, 1, 2, 1}; long nfto[5] = {0, numberOfNasalFormants, (numberOfOralFormants > 0 ? 1 : 0), numberOfOralFormants, numberOfTrachealFormants}; autoMelderString fba; rel_to_abs (xw, xws, numberOfXSections, xmax - xmin); if (numberOfFormants == 0) { y1 = y2 = (ymin + ymax) / 2; Graphics_line (g, xmin, y1, xmax, y1); if (yin != NULL) { *yin = y1; } if (yout != NULL) { *yout = y2; } return; } dy = (ymax - ymin) / (numberOfFormants * (1 + ddy) - ddy); connections local_in = connections_create (numberOfFormants); connections local_out = connections_create (numberOfFormants); // parallel section x1 = xmin + xws[5]; x2 = x1 + xw[6]; y2 = ymax; x3 = xmin + xws[4]; for (long isection = 1; isection <= numberOfYSections; isection++) { long ifrom = nffrom[isection], ito = nfto[isection]; if (ito < ifrom) { continue; } for (long i = ifrom; i <= ito; i++) { y1 = y2 - dy; ymid = (y1 + y2) / 2; const wchar_t *fi = Melder_integer (i); MelderString_append (&fba, L"A", fi, L" F", fi, L" B", fi); draw_oneSection (g, x1, x2, y1, y2, text[isection], fba.string, NULL); Graphics_line (g, x3, ymid, x1, ymid); // to the left ic++; local_in -> x[ic] = x3; local_out -> x[ic] = x2; local_in -> y[ic] = local_out -> y[ic] = ymid; y2 = y1 - 0.5 * dy; MelderString_empty (&fba); } } ic = 0; x1 = local_in -> y[1]; if (numberOfUpperPartFormants > 0) { x1 = local_in -> x[numberOfUpperPartFormants]; y1 = local_in -> y[numberOfUpperPartFormants]; if (numberOfUpperPartFormants > 1) { Graphics_line (g, x1, y1, local_in -> x[1], local_in -> y[1]); // vertical } x2 = xmin; if (numberOfLowerPartFormants > 0) { x2 += xw[1]; } Graphics_line (g, x1, y1, x2, y1); // done } if (numberOfLowerPartFormants > 0) { long ifrom = numberOfUpperPartFormants + 1; x1 = local_in -> x[ifrom]; y1 = local_in -> y[ifrom]; // at the split if (numberOfLowerPartFormants > 1) { Graphics_line (g, x1, y1, local_in -> x[numberOfFormants], local_in -> y[numberOfFormants]); // vertical } x2 = xmin + xws[3]; // right of diff Graphics_line (g, x1, y1, x2, y1); // from vertical to diff x1 = xmin + xws[2]; // left of diff draw_oneSection (g, x1, x2, y1 + 0.5 * dy, y1 - 0.5 * dy, L"Pre-emphasis", NULL, NULL); x2 = x1; if (numberOfUpperPartFormants > 0) { x2 = xmin + xw[1]; y2 = y1; // at split Graphics_line (g, x1, y1, x2, y1); // to split y1 += (1 + ddy) * dy; Graphics_line (g, x2, y2, x2, y1); // vertical y1 -= 0.5 * (1 + ddy) * dy; } Graphics_line (g, xmin, y1, x2, y1); } r = xw[8] / 2; x2 = xmax - r; y2 = (ymin + ymax) / 2; alternatingSummer_drawConnections (g, x2, y2, r, local_out, 1, 0.4); connections_free (local_out); connections_free (local_in); if (yin != NULL) { *yin = y1; } if (yout != NULL) { *yout = y2; } } static void VocalTractGrid_CouplingGrid_draw_inside (VocalTractGrid me, CouplingGrid thee, Graphics g, int filterModel, double xmin, double xmax, double ymin, double ymax, double dy, double *yin, double *yout) { filterModel == KlattGrid_FILTER_CASCADE ? VocalTractGrid_CouplingGrid_drawCascade_inline (me, thee, g, xmin, xmax, ymin, ymax, yin, yout) : VocalTractGrid_CouplingGrid_drawParallel_inline (me, thee, g, xmin, xmax, ymin, ymax, dy, yin, yout); } static void VocalTractGrid_CouplingGrid_draw (VocalTractGrid me, CouplingGrid thee, Graphics g, int filterModel) { double xmin = 0, xmin1 = 0.05, xmax1 = 0.95, xmax = 1, ymin = 0, ymax = 1, dy = 0.5, yin, yout; Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_setLineWidth (g, 2); VocalTractGrid_CouplingGrid_draw_inside (me, thee, g, filterModel, xmin1, xmax1, ymin, ymax, dy, &yin, &yout); Graphics_line (g, xmin, yin, xmin1, yin); Graphics_arrow (g, xmax1, yout, xmax, yout); Graphics_unsetInner (g); } static Sound Sound_VocalTractGrid_CouplingGrid_filter_cascade (Sound me, VocalTractGrid thee, CouplingGrid coupling) { try { VocalTractGridPlayOptions pv = thy options; CouplingGridPlayOptions pc = coupling -> options; int useOpenGlottisInfo = pc -> openglottis && coupling && coupling -> glottis && coupling -> glottis -> points -> size > 0; FormantGrid oral_formants = thy oral_formants; FormantGrid nasal_formants = thy nasal_formants; FormantGrid nasal_antiformants = thy nasal_antiformants; FormantGrid tracheal_formants = coupling -> tracheal_formants; FormantGrid tracheal_antiformants = coupling -> tracheal_antiformants; int antiformants = 0; long numberOfFormants = oral_formants -> formants -> size; long numberOfTrachealFormants = tracheal_formants -> formants -> size; long numberOfTrachealAntiFormants = tracheal_antiformants -> formants -> size; long numberOfNasalFormants = nasal_formants -> formants -> size; long numberOfNasalAntiFormants = nasal_antiformants -> formants -> size; check_formants (numberOfFormants, & (pv -> startOralFormant), & (pv -> endOralFormant)); check_formants (numberOfNasalFormants, & (pv -> startNasalFormant), & (pv -> endNasalFormant)); check_formants (numberOfTrachealFormants, & (pc -> startTrachealFormant), & (pc -> endTrachealFormant)); check_formants (numberOfNasalAntiFormants, & (pv -> startNasalAntiFormant), & (pv -> endNasalAntiFormant)); check_formants (numberOfTrachealAntiFormants, & (pc -> startTrachealAntiFormant), & (pc -> endTrachealAntiFormant)); autoSound him = Data_copy (me); autoFormantGrid formants = 0; if (useOpenGlottisInfo) { formants.reset (Data_copy (thy oral_formants)); FormantGrid_CouplingGrid_updateOpenPhases (formants.peek(), coupling); } long nasal_formant_warning = 0, any_warning = 0; if (pv -> endNasalFormant > 0) { // Nasal formants antiformants = 0; for (long iformant = pv -> startNasalFormant; iformant <= pv -> endNasalFormant; iformant++) { if (FormantGrid_isFormantDefined (thy nasal_formants, iformant)) { _Sound_FormantGrid_filterWithOneFormant_inline (him.peek(), thy nasal_formants, iformant, antiformants); } else { // Melder_warning ("Nasal formant", iformant, ": frequency and/or bandwidth missing."); nasal_formant_warning++; any_warning++; } } } long nasal_antiformant_warning = 0; if (pv -> endNasalAntiFormant > 0) { // Nasal anti formants antiformants = 1; for (long iformant = pv -> startNasalAntiFormant; iformant <= pv -> endNasalAntiFormant; iformant++) { if (FormantGrid_isFormantDefined (thy nasal_antiformants, iformant)) { _Sound_FormantGrid_filterWithOneFormant_inline (him.peek(), thy nasal_antiformants, iformant, antiformants); } else { // Melder_warning ("Nasal antiformant", iformant, ": frequency and/or bandwidth missing."); nasal_antiformant_warning++; any_warning++; } } } long tracheal_formant_warning = 0; if (pc -> endTrachealFormant > 0) { // Tracheal formants antiformants = 0; for (long iformant = pc -> startTrachealFormant; iformant <= pc -> endTrachealFormant; iformant++) { if (FormantGrid_isFormantDefined (tracheal_formants, iformant)) { _Sound_FormantGrid_filterWithOneFormant_inline (him.peek(), tracheal_formants, iformant, antiformants); } else { // Melder_warning ("Tracheal formant", iformant, ": frequency and/or bandwidth missing."); tracheal_formant_warning++; any_warning++; } } } long tracheal_antiformant_warning = 0; if (pc -> endTrachealAntiFormant > 0) { // Tracheal anti formants antiformants = 1; for (long iformant = pc -> startTrachealAntiFormant; iformant <= pc -> endTrachealAntiFormant; iformant++) { if (FormantGrid_isFormantDefined (tracheal_antiformants, iformant)) { _Sound_FormantGrid_filterWithOneFormant_inline (him.peek(), tracheal_antiformants, iformant, antiformants); } else { // Melder_warning ("Tracheal antiformant", iformant, ": frequency and/or bandwidth missing."); tracheal_antiformant_warning++; any_warning++; } } } long oral_formant_warning = 0; if (pv -> endOralFormant > 0) { // Oral formants antiformants = 0; if (formants.peek() == 0) { formants.reset (thy oral_formants); } for (long iformant = pv -> startOralFormant; iformant <= pv -> endOralFormant; iformant++) { if (FormantGrid_isFormantDefined (formants.peek(), iformant)) { _Sound_FormantGrid_filterWithOneFormant_inline (him.peek(), formants.peek(), iformant, antiformants); } else { // Melder_warning ("Oral formant", iformant, ": frequency and/or bandwidth missing."); oral_formant_warning++; any_warning++; } } } if (any_warning > 0) { autoMelderString warning; if (nasal_formant_warning > 0) { MelderString_append (&warning, L"\tNasal formants: one or more are missing.\n"); } if (nasal_antiformant_warning) { MelderString_append (&warning, L"\tNasal antiformants: one or more are missing.\n"); } if (tracheal_formant_warning) { MelderString_append (&warning, L"\tTracheal formants: one or more are missing.\n"); } if (tracheal_antiformant_warning) { MelderString_append (&warning, L"\tTracheal antiformants: one or more are missing.\n"); } if (oral_formant_warning) { MelderString_append (&warning, L"\tOral formants: one or more are missing.\n"); } MelderInfo_open(); MelderInfo_writeLine1 (L"Warning:"); MelderInfo_writeLine1 (warning.string); MelderInfo_close(); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not filtered by vocaltract and coupling grid."); } } Sound Sound_VocalTractGrid_CouplingGrid_filter_parallel (Sound me, VocalTractGrid thee, CouplingGrid coupling) { try { VocalTractGridPlayOptions pv = thy options; CouplingGridPlayOptions pc = coupling -> options; autoSound him = 0; FormantGrid oral_formants = thy oral_formants; autoFormantGrid aof = 0; int alternatingSign = 0; // 0: no alternating signs in parallel adding of filter outputs, 1/-1 start sign int useOpenGlottisInfo = pc -> openglottis && coupling -> glottis && coupling -> glottis -> points -> size > 0; int scale = 1; long numberOfFormants = thy oral_formants -> formants -> size; long numberOfNasalFormants = thy nasal_formants -> formants -> size; long numberOfTrachealFormants = coupling -> tracheal_formants -> formants -> size; check_formants (numberOfFormants, & (pv -> startOralFormant), & (pv -> endOralFormant)); check_formants (numberOfNasalFormants, & (pv -> startNasalFormant), & (pv -> endNasalFormant)); check_formants (numberOfTrachealFormants, & (pc -> startTrachealFormant), & (pc -> endTrachealFormant)); if (useOpenGlottisInfo) { aof.reset (Data_copy (thy oral_formants)); oral_formants = aof.peek(); FormantGrid_CouplingGrid_updateOpenPhases (oral_formants, coupling); } if (pv -> endOralFormant > 0) { if (pv -> startOralFormant == 1) { him.reset (Data_copy (me)); if (oral_formants -> formants -> size > 0) { Sound_FormantGrid_Intensities_filterWithOneFormant_inline (him.peek(), oral_formants, thy oral_formants_amplitudes, 1); } } } if (pv -> endNasalFormant > 0) { alternatingSign = 0; autoSound nasal = Sound_FormantGrid_Intensities_filter (me, thy nasal_formants, thy nasal_formants_amplitudes, pv -> startNasalFormant, pv -> endNasalFormant, alternatingSign); if (him.peek() == 0) { him.reset (Data_copy (nasal.peek())); } else { _Sounds_add_inline (him.peek(), nasal.peek()); } } // Formants 2 and up, with alternating signs. // We perform pre-emphasis by differentiating. // Klatt (1980) states that a first difference for the higher formants is necessary to remove low-frequency // energy from them. This energy would otherwise distort the spectrum in the region of F1 during the synthesis // of some vowels. autoSound me_diff = _Sound_diff (me, scale); if (pv -> endOralFormant >= 2) { long startOralFormant2 = pv -> startOralFormant > 2 ? pv -> startOralFormant : 2; alternatingSign = startOralFormant2 % 2 == 0 ? -1 : 1; // 2 starts with negative sign if (startOralFormant2 <= oral_formants -> formants -> size) { autoSound vocalTract = Sound_FormantGrid_Intensities_filter (me_diff.peek(), oral_formants, thy oral_formants_amplitudes, startOralFormant2, pv -> endOralFormant, alternatingSign); if (him.peek() == 0) { him.reset (Data_copy (vocalTract.peek())); } else { _Sounds_add_inline (him.peek(), vocalTract.peek()); } } } if (pc -> endTrachealFormant > 0) { // Tracheal formants alternatingSign = 0; autoSound trachea = Sound_FormantGrid_Intensities_filter (me_diff.peek(), coupling -> tracheal_formants, coupling -> tracheal_formants_amplitudes, pc -> startTrachealFormant, pc -> endTrachealFormant, alternatingSign); if (him.peek() == 0) { him.reset (Data_copy (trachea.peek())); } else { _Sounds_add_inline (him.peek(), trachea.peek()); } } if (him.peek() == 0) { him.reset (Data_copy (me)); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not filtered in parallel."); } } Sound Sound_VocalTractGrid_CouplingGrid_filter (Sound me, VocalTractGrid thee, CouplingGrid coupling) { return thy options -> filterModel == KlattGrid_FILTER_CASCADE ? Sound_VocalTractGrid_CouplingGrid_filter_cascade (me, thee, coupling) : Sound_VocalTractGrid_CouplingGrid_filter_parallel (me, thee, coupling); } /********************** CouplingGridPlayOptions **********************/ Thing_implement (CouplingGridPlayOptions, Data, 0); static void CouplingGridPlayOptions_setDefaults (CouplingGridPlayOptions me, CouplingGrid thee) { my fadeFraction = 0.1; my openglottis = 1; my endTrachealFormant = MIN (thy tracheal_formants -> formants -> size, thy tracheal_formants -> bandwidths -> size); my startTrachealFormant = 1; my endTrachealAntiFormant = MIN (thy tracheal_antiformants -> formants -> size, thy tracheal_antiformants -> bandwidths -> size); my startTrachealAntiFormant = 1; my startDeltaFormant = 1; my endDeltaFormant = thy delta_formants -> formants -> size; my startDeltaBandwidth = 1; my endDeltaBandwidth = thy delta_formants -> bandwidths -> size; } CouplingGridPlayOptions CouplingGridPlayOptions_create () { try { CouplingGridPlayOptions me = Thing_new (CouplingGridPlayOptions); return me; } catch (MelderError) { Melder_throw ("CouplingGridPlayOptions not created."); } } /********************** CouplingGrid *************************************/ Thing_implement (CouplingGrid, Function, 0); void structCouplingGrid :: v_info () { structData :: v_info (); const wchar_t *in1 = L" ", *in2 = L" ", *in3 = L" "; MelderInfo_writeLine2 (in1, L"Time domain:"); MelderInfo_writeLine4 (in2, L"Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine4 (in2, L"End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine4 (in2, L"Total duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine2 (in1, L"\nNumber of points in the TRACHEAL FORMANT tiers:"); FormantGrid_info (tracheal_formants, tracheal_formants_amplitudes, in2, in3); MelderInfo_writeLine2 (in1, L"\nNumber of points in the TRACHEAL ANTIFORMANT tiers:"); FormantGrid_info (tracheal_antiformants, NULL, in2, in3); MelderInfo_writeLine2 (in1, L"\nNumber of points in the DELTA FORMANT tiers:"); FormantGrid_info (delta_formants, NULL, in2, in3); } void CouplingGrid_setNames (CouplingGrid me) { Thing_setName (my tracheal_formants, L"tracheal_formants"); Thing_setName (my tracheal_antiformants, L"tracheal_antiformants"); Thing_setName (my tracheal_formants_amplitudes, L"tracheal_formants_amplitudes"); Thing_setName (my delta_formants, L"delta_formants"); Thing_setName (my glottis, L"glottis"); } CouplingGrid CouplingGrid_create (double tmin, double tmax, long numberOfTrachealFormants, long numberOfTrachealAntiFormants, long numberOfDeltaFormants) { try { autoCouplingGrid me = Thing_new (CouplingGrid); Function_init (me.peek(), tmin, tmax); my tracheal_formants = FormantGrid_createEmpty (tmin, tmax, numberOfTrachealFormants); my tracheal_antiformants = FormantGrid_createEmpty (tmin, tmax, numberOfTrachealAntiFormants); my tracheal_formants_amplitudes = formantsAmplitudes_create (tmin, tmax, numberOfTrachealFormants); my delta_formants = FormantGrid_createEmpty (tmin, tmax, numberOfDeltaFormants); my glottis = PhonationTier_create (tmin, tmax); my options = CouplingGridPlayOptions_create (); CouplingGrid_setNames (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("CouplingGrid not created."); } } /********************** FormantGrid & CouplingGrid *************************************/ void FormantGrid_CouplingGrid_updateOpenPhases (FormantGrid me, CouplingGrid thee) { try { CouplingGridPlayOptions pc = thy options; for (long itier = 1; itier <= thy delta_formants -> formants -> size; itier++) { RealTier delta = (RealTier) thy delta_formants -> formants -> item[itier]; if (itier <= my formants -> size) { if (delta -> points -> size > 0) { autoRealTier rt = RealTier_updateWithDelta ( (RealTier) my formants -> item[itier], delta, thy glottis, pc -> fadeFraction); if (! RealTier_valuesInRange (rt.peek(), 0, NUMundefined)) { Melder_throw ("Formant ", itier, " coupling gives negative values."); } forget ( ( (Thing *) my formants -> item) [itier]); my formants -> item[itier] = rt.transfer(); } } delta = (RealTier) thy delta_formants -> bandwidths -> item[itier]; if (itier <= my bandwidths -> size) { if (delta -> points -> size > 0) { autoRealTier rt = RealTier_updateWithDelta ( (RealTier) my bandwidths -> item[itier], delta, thy glottis, pc -> fadeFraction); if (! RealTier_valuesInRange (rt.peek(), 0, NUMundefined)) { Melder_throw ("Bandwidth ", itier, " coupling gives negative values."); } forget ( ( (Thing *) my bandwidths -> item) [itier]); my bandwidths -> item[itier] = rt.transfer(); } } } } catch (MelderError) { Melder_throw (me, ": not updated with open hase information."); } } /************************ Sound & FormantGrid *********************************************/ void _Sound_FormantGrid_filterWithOneFormant_inline (Sound me, thou, long iformant, int antiformant) { thouart (FormantGrid); if (iformant < 1 || iformant > thy formants -> size) { Melder_warning (L"Formant ", Melder_integer (iformant), L" does not exist."); return; } RealTier ftier = (RealTier) thy formants -> item[iformant]; RealTier btier = (RealTier) thy bandwidths -> item[iformant]; if (ftier -> points -> size == 0 && btier -> points -> size == 0) { return; } else if (ftier -> points -> size == 0 || btier -> points -> size == 0) { Melder_throw ("Empty tier"); } double nyquist = 0.5 / my dx; autoFilter r = antiformant != 0 ? (Filter) AntiResonator_create (my dx) : (Filter) Resonator_create (my dx, Resonator_NORMALISATION_H0); for (long is = 1; is <= my nx; is++) { double t = my x1 + (is - 1) * my dx; double f = RealTier_getValueAtTime (ftier, t); double b = RealTier_getValueAtTime (btier, t); if (f <= nyquist && NUMdefined (b)) { Filter_setFB (r.peek(), f, b); } my z[1][is] = Filter_getOutput (r.peek(), my z[1][is]); } } void Sound_FormantGrid_filterWithOneAntiFormant_inline (Sound me, FormantGrid thee, long iformant) { _Sound_FormantGrid_filterWithOneFormant_inline (me, thee, iformant, 1); } void Sound_FormantGrid_filterWithOneFormant_inline (Sound me, FormantGrid thee, long iformant) { _Sound_FormantGrid_filterWithOneFormant_inline (me, thee, iformant, 0); } void Sound_FormantGrid_Intensities_filterWithOneFormant_inline (Sound me, FormantGrid thee, Ordered amplitudes, long iformant) { try { if (iformant < 1 || iformant > thy formants -> size) { Melder_throw ("Formant ", iformant, " not defined. \nThis formant will not be used."); } double nyquist = 0.5 / my dx; RealTier ftier = (RealTier) thy formants -> item[iformant]; RealTier btier = (RealTier) thy bandwidths -> item[iformant]; RealTier atier = (RealTier) amplitudes -> item[iformant]; if (ftier -> points -> size == 0 || btier -> points -> size == 0 || atier -> points -> size == 0) { return; // nothing to do } autoResonator r = Resonator_create (my dx, Resonator_NORMALISATION_HMAX); for (long is = 1; is <= my nx; is++) { double t = my x1 + (is - 1) * my dx; double f = RealTier_getValueAtTime (ftier, t); double b = RealTier_getValueAtTime (btier, t); double a; if (f <= nyquist && NUMdefined (b)) { Filter_setFB (r.peek(), f, b); a = RealTier_getValueAtTime (atier, t); if (NUMdefined (a)) { r -> a *= DB_to_A (a); } } my z[1][is] = Filter_getOutput (r.peek(), my z[1][is]); } } catch (MelderError) { Melder_throw (me, ": not filtered with one formant filter."); } } Sound Sound_FormantGrid_Intensities_filter (Sound me, FormantGrid thee, Ordered amplitudes, long iformantb, long iformante, int alternatingSign) { try { if (iformantb > iformante) { iformantb = 1; iformante = thy formants -> size; } if (iformantb < 1 || iformantb > thy formants -> size || iformante < 1 || iformante > thy formants -> size) { Melder_throw ("No such formant number."); } autoSound him = Sound_create (my ny, my xmin, my xmax, my nx, my dx, my x1); for (long iformant = iformantb; iformant <= iformante; iformant++) { if (FormantGrid_Intensities_isFormantDefined (thee, amplitudes, iformant)) { autoSound tmp = Data_copy (me); Sound_FormantGrid_Intensities_filterWithOneFormant_inline (tmp.peek(), thee, amplitudes, iformant); for (long is = 1; is <= my nx; is++) { his z[1][is] += alternatingSign >= 0 ? tmp -> z[1][is] : - tmp -> z[1][is]; } if (alternatingSign != 0) { alternatingSign = -alternatingSign; } } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not filtered."); } } /********************** FricationGridPlayOptions **********************/ Thing_implement (FricationGridPlayOptions, Data, 0); static void FricationGridPlayOptions_setDefaults (FricationGridPlayOptions me, FricationGrid thee) { my endFricationFormant = MIN (thy frication_formants -> formants -> size, thy frication_formants -> bandwidths -> size); my startFricationFormant = 2; my bypass = 1; } FricationGridPlayOptions FricationGridPlayOptions_create () { try { FricationGridPlayOptions me = Thing_new (FricationGridPlayOptions); return me; } catch (MelderError) { Melder_throw ("FricationGridPlayOptions not created."); } } /************************ FricationGrid (& Sound) *********************************************/ void structFricationGrid :: v_info () { structData :: v_info (); const static wchar_t *in1 = L" ", *in2 = L" ", *in3 = L" "; MelderInfo_writeLine2 (in1, L"Time domain:"); MelderInfo_writeLine4 (in2, L"Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine4 (in2, L"End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine4 (in2, L"Total duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine2 (in1, L"\nNumber of points in the FRICATION tiers:"); MelderInfo_writeLine3 (in2, L"fricationAmplitude: ", Melder_integer (fricationAmplitude -> points -> size)); MelderInfo_writeLine3 (in2, L"bypass: ", Melder_integer (bypass -> points -> size)); MelderInfo_writeLine2 (in1, L"\nNumber of points in the FRICATION FORMANT tiers:"); FormantGrid_info (frication_formants, frication_formants_amplitudes, in2, in3); } Thing_implement (FricationGrid, Function, 0); void FricationGrid_setNames (FricationGrid me) { Thing_setName (my fricationAmplitude, L"fricationAmplitude"); Thing_setName (my frication_formants, L"frication_formants"); Thing_setName (my bypass, L"bypass"); Thing_setName (my frication_formants_amplitudes, L"frication_formants_amplitudes"); } FricationGrid FricationGrid_create (double tmin, double tmax, long numberOfFormants) { try { autoFricationGrid me = Thing_new (FricationGrid); Function_init (me.peek(), tmin, tmax); my fricationAmplitude = IntensityTier_create (tmin, tmax); my frication_formants = FormantGrid_createEmpty (tmin, tmax, numberOfFormants); my bypass = IntensityTier_create (tmin, tmax); my frication_formants_amplitudes = formantsAmplitudes_create (tmin, tmax, numberOfFormants); my options = FricationGridPlayOptions_create (); FricationGrid_setNames (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("FricationGrid not created."); } } static void FricationGrid_draw_inside (FricationGrid me, Graphics g, double xmin, double xmax, double ymin, double ymax, double dy, double *yout) { long numberOfXSections = 5; long numberOfFormants = my frication_formants -> formants -> size; long numberOfParts = numberOfFormants + (numberOfFormants > 1 ? 0 : 1) ; // 2..number + bypass // dum noise, connections, filter, connections, adder double xw[6] = { 0, 2, 0.6, 1.5, 0.6, 0.5 }, xws[6]; double r, x1, y1, x2, y2, x3, xs, ys, ymid = (ymin + ymax) / 2; rel_to_abs (xw, xws, numberOfXSections, xmax - xmin); dy = dy < 0 ? 0 : dy; dy = (ymax - ymin) / (numberOfParts * (1 + dy) - dy); connections cp = connections_create (numberOfParts); if (cp == 0) { return; } // section 1 x1 = xmin; x2 = x1 + xw[1]; y1 = ymid - 0.5 * dy; y2 = y1 + dy; draw_oneSection (g, x1, x2, y1, y2, L"Frication", L"noise", NULL); // section 2, horizontal line halfway, vertical line x1 = x2; x2 = x1 + xw[2] / 2; Graphics_line (g, x1, ymid, x2, ymid); Graphics_line (g, x2, ymax - dy / 2, x2, ymin + dy / 2); x3 = x2; // final connection to section 2 , filters , connections to adder x1 = xmin + xws[2]; x2 = x1 + xw[3]; y2 = ymax; MelderString fba = { 0 }; for (long i = 1; i <= numberOfParts; i++) { const wchar_t *fi = Melder_integer (i + 1); y1 = y2 - dy; if (i < numberOfParts) { MelderString_append (&fba, L"A", fi, L" F", fi, L" B", fi); } else { MelderString_append (&fba, L"Bypass"); } draw_oneSection (g, x1, x2, y1, y2, NULL, fba.string, NULL); double ymidi = (y1 + y2) / 2; Graphics_line (g, x3, ymidi, x1, ymidi); // from noise to filter cp -> x[i] = x2; cp -> y[i] = ymidi; y2 = y1 - 0.5 * dy; MelderString_empty (&fba); } r = xw[5] / 2; xs = xmax - r; ys = ymid; if (numberOfParts > 1) { alternatingSummer_drawConnections (g, xs, ys, r, cp, 1, 0.4); } else { Graphics_line (g, cp -> x[1], cp -> y[1], xs + r, ys); } connections_free (cp); if (yout != NULL) { *yout = ys; } MelderString_free (&fba); } void FricationGrid_draw (FricationGrid me, Graphics g) { double xmin = 0, xmax = 1, xmax2 = 0.9, ymin = 0, ymax = 1, dy = 0.5, yout; Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_setLineWidth (g, 2); FricationGrid_draw_inside (me, g, xmin, xmax2, ymin, ymax, dy, &yout); Graphics_arrow (g, xmax2, yout, xmax, yout); Graphics_unsetInner (g); } Sound FricationGrid_to_Sound (FricationGrid me, double samplingFrequency) { try { autoSound thee = Sound_createEmptyMono (my xmin, my xmax, samplingFrequency); double lastval = 0; for (long i = 1; i <= thy nx; i++) { double t = thy x1 + (i - 1) * thy dx; double val = NUMrandomUniform (-1, 1); double a = 0; if (my fricationAmplitude -> points -> size > 0) { double dba = RealTier_getValueAtTime (my fricationAmplitude, t); a = dba == NUMundefined ? 0 : DBSPL_to_A (dba); } lastval = (val += 0.75 * lastval); // TODO: soft low-pass coefficient must be Fs dependent! thy z[1][i] = val * a; } autoSound him = Sound_FricationGrid_filter (thee.peek(), me); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no frication Sound created."); } } /************************ Sound & FricationGrid *********************************************/ Sound Sound_FricationGrid_filter (Sound me, FricationGrid thee) { try { FricationGridPlayOptions pf = thy options; autoSound him = 0; long numberOfFricationFormants = thy frication_formants -> formants -> size; check_formants (numberOfFricationFormants, & (pf -> startFricationFormant), & (pf -> endFricationFormant)); if (pf -> endFricationFormant > 1) { long startFricationFormant2 = pf -> startFricationFormant > 2 ? pf -> startFricationFormant : 2; int alternatingSign = startFricationFormant2 % 2 == 0 ? 1 : -1; // 2 starts with positive sign him.reset (Sound_FormantGrid_Intensities_filter (me, thy frication_formants, thy frication_formants_amplitudes, startFricationFormant2, pf -> endFricationFormant, alternatingSign)); } if (him.peek() == 0) { him.reset (Data_copy (me)); } if (pf -> bypass) { for (long is = 1; is <= his nx; is++) { // Bypass double t = his x1 + (is - 1) * his dx; double ab = 0; if (thy bypass -> points -> size > 0) { double val = RealTier_getValueAtTime (thy bypass, t); ab = val == NUMundefined ? 0 : DB_to_A (val); } his z[1][is] += my z[1][is] * ab; } } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not filtered by frication filter."); } } /********************** KlattGridPlayOptions **********************/ Thing_implement (KlattGridPlayOptions, Data, 0); static void KlattGridPlayOptions_setDefaults (KlattGridPlayOptions me, KlattGrid thee) { my samplingFrequency = 44100; my scalePeak = 1; my xmin = thy xmin; my xmax = thy xmax; } KlattGridPlayOptions KlattGridPlayOptions_create () { try { KlattGridPlayOptions me = Thing_new (KlattGridPlayOptions); return me; } catch (MelderError) { Melder_throw ("KlattGridPlayOptions not created."); } } void KlattGrid_setDefaultPlayOptions (KlattGrid me) { KlattGridPlayOptions_setDefaults (my options, me); PhonationGridPlayOptions_setDefaults (my phonation -> options); VocalTractGridPlayOptions_setDefaults (my vocalTract -> options, my vocalTract); CouplingGridPlayOptions_setDefaults (my coupling -> options, my coupling); FricationGridPlayOptions_setDefaults (my frication -> options, my frication); } /************************ KlattGrid *********************************************/ Thing_implement (KlattGrid, Function, 0); void structKlattGrid :: v_info () { structData :: v_info (); MelderInfo_writeLine1 (L"Time domain:"); MelderInfo_writeLine3 (L" Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine3 (L" End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine3 (L" Total duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine1 (L"\n--- PhonationGrid ---\n"); phonation -> v_info (); MelderInfo_writeLine1 (L"\n--- VocalTractGrid ---\n"); vocalTract -> v_info (); MelderInfo_writeLine1 (L"\n--- CouplingGrid ---\n"); coupling -> v_info (); MelderInfo_writeLine1 (L"\n--- FricationgGrid ---\n"); frication -> v_info (); } void KlattGrid_setNames (KlattGrid me) { Thing_setName (my phonation, L"phonation"); Thing_setName (my vocalTract, L"vocalTract"); Thing_setName (my coupling, L"coupling"); Thing_setName (my frication, L"frication"); Thing_setName (my gain, L"gain"); } KlattGrid KlattGrid_create (double tmin, double tmax, long numberOfFormants, long numberOfNasalFormants, long numberOfNasalAntiFormants, long numberOfTrachealFormants, long numberOfTrachealAntiFormants, long numberOfFricationFormants, long numberOfDeltaFormants) { try { autoKlattGrid me = Thing_new (KlattGrid); Function_init (me.peek(), tmin, tmax); my phonation = PhonationGrid_create (tmin, tmax); my vocalTract = VocalTractGrid_create (tmin, tmax, numberOfFormants, numberOfNasalFormants, numberOfNasalAntiFormants); my coupling = CouplingGrid_create (tmin, tmax, numberOfTrachealFormants, numberOfTrachealAntiFormants, numberOfDeltaFormants); my frication = FricationGrid_create (tmin, tmax, numberOfFricationFormants); my gain = IntensityTier_create (tmin, tmax); my options = KlattGridPlayOptions_create (); KlattGrid_setDefaultPlayOptions (me.peek()); KlattGrid_setNames (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid not created."); } } KlattGrid KlattGrid_createExample () { try { autoKlattTable thee = KlattTable_createExample (); autoKlattGrid me = KlattTable_to_KlattGrid (thee.peek(), 0.005); return me.transfer(); } catch (MelderError) { Melder_throw ("KlattGrid example not created."); }; } // y is the heigth in units of the height of one section, // y1 is the heigth from the top to the split between the uppper, non-diffed, and lower diffed part static void _KlattGrid_queryParallelSplit (KlattGrid me, double dy, double *y, double *y1) { long ny = my vocalTract -> nasal_formants -> formants -> size + my vocalTract -> oral_formants -> formants -> size + my coupling -> tracheal_formants -> formants -> size; long n1 = my vocalTract -> nasal_formants -> formants -> size + (my vocalTract -> oral_formants -> formants -> size > 0 ? 1 : 0); long n2 = ny - n1; if (ny == 0) { *y = 0; *y1 = 0; return; } *y = ny + (ny - 1) * dy; if (n1 == 0) { *y1 = 0.5; } else if (n2 == 0) { *y1 = *y - 0.5; } else { *y1 = n1 + (n1 - 1) * dy + 0.5 * dy; } return; } static void getYpositions (double h1, double h2, double h3, double h4, double h5, double fractionOverlap, double *dy, double *ymin1, double *ymax1, double *ymin2, double *ymax2, double *ymin3, double *ymax3) { // Given: five 'blocks' with relative heights h1..h5 in arbitrary units. // Problem: scale all h1..h5 such that: // 1. blocks h1 and h2 form one unit, with h1 on top of h2, the quotient h1/h2 is fixed // 2. blocks h3 and h4 form one unit, with h3 on top of h4, the quotient h3/h4 is fixed // 3. blocks h1 and h3 have the same baseline. // 4. h5 is always underneath (h1,h2) but may partially overlap (0.45) with h4. // 5. After scaling the new h1+h2 >= 0.3 // 6. Optimally use the vertical space from 0.. 1, i.e the top of h1 or h3 is at 1, // the bottom of h5 is at 0. Preferably scale all blocks with the same factor, if not possible than // scale h3,h4 and h5 the same // // h1 h3 // h2 h4 // h5 /* Cases: x x ^ x x x x x x | h1 x x x x x x x x h3 | h13 ----------------------------------------------------------- h2 x x x x x x x x h4 x x x x x x x x x x x x x x h5 x x x x x x x x */ double h; // h12_min = 0.3; not yet double h13 = h1 > h3 ? h1 : h3; // baselines are now equal if (h2 >= h4) { h = h13 + h2 + h5; } else { // h2 < h4 double maximumOverlap3 = fractionOverlap * h5; if (maximumOverlap3 < (h1 + h2)) { maximumOverlap3 = 0; } else if (maximumOverlap3 > (h4 - h2)) { maximumOverlap3 = h4 - h2; } h = h13 + h4 + h5 - maximumOverlap3; } *dy = 1 / (1.1 * h); *ymin1 = 1 - (h13 + h2) * *dy; *ymax1 = *ymin1 + (h1 + h2) * *dy; *ymin2 = 1 - (h13 + h4) * *dy; *ymax2 = *ymin2 + (h3 + h4) * *dy; *ymin3 = 0; *ymax3 = h5 * *dy; } void KlattGrid_drawVocalTract (KlattGrid me, Graphics g, int filterModel, int withTrachea) { VocalTractGrid_CouplingGrid_draw (my vocalTract, withTrachea ? my coupling : NULL, g, filterModel); } void KlattGrid_draw (KlattGrid me, Graphics g, int filterModel) { double xs1, xs2, ys1, ys2, xf1, xf2, yf1, yf2; double xp1, xp2, yp1, yp2, xc1, xc2, yc1, yc2; double dy, r, xs, ys; double xmin = 0, xmax2 = 0.90, xmax3 = 0.95, xmax = 1, ymin = 0, ymax = 1; double xws[6]; double height_phonation = 0.3; double dy_phonation = 0.5, dy_vocalTract_p = 0.5, dy_frication = 0.5; connections tf = connections_create (2); if (tf == 0) { return; } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_setLineWidth (g, 2); long nff = my frication -> frication_formants -> formants -> size - 1 + 1; double yh_frication = nff > 0 ? nff + (nff - 1) * dy_frication : 1; double yh_phonation = 1 + dy_phonation + 1; double yout_phonation, yout_frication; dy = height_phonation / yh_phonation; // 1 vertical unit in source section height units if (filterModel == KlattGrid_FILTER_CASCADE) { // Cascade section // source connection tract connection, out // frication double xw[6] = {0, 1.75, 0.125, 3, 0.25, 0.125 }; double yin_vocalTract_c, yout_vocalTract_c; rel_to_abs (xw, xws, 5, xmax2 - xmin); // limit height of frication unit dy ! height_phonation = yh_phonation / (yh_phonation + yh_frication); if (height_phonation < 0.3) { height_phonation = 0.3; } dy = height_phonation / yh_phonation; xs1 = xmin; xs2 = xs1 + xw[1]; ys2 = ymax; ys1 = ys2 - height_phonation; PhonationGrid_draw_inside (my phonation, g, xs1, xs2, ys1, ys2, dy_phonation, &yout_phonation); // units in cascade have same heigth as units in source part. xc1 = xmin + xws[2]; xc2 = xc1 + xw[3]; yc2 = yout_phonation + dy / 2; yc1 = yc2 - dy; VocalTractGrid_CouplingGrid_drawCascade_inline (my vocalTract, my coupling, g, xc1, xc2, yc1, yc2, &yin_vocalTract_c, &yout_vocalTract_c); tf -> x[1] = xc2; tf -> y[1] = yout_vocalTract_c; Graphics_line (g, xs2, yout_phonation, xc1, yin_vocalTract_c); xf1 = xmin + xws[2]; xf2 = xf1 + xw[3]; yf2 = ymax - height_phonation; yf1 = 0; FricationGrid_draw_inside (my frication, g, xf1, xf2, yf1, yf2, dy_frication, &yout_frication); } else { // Parallel // source connection tract connection, out // frication double yf_parallel, yh_parallel, yh_overlap = 0.3, yin_vocalTract_p, yout_vocalTract_p; double xw[6] = { 0, 1.75, 0.125, 3, 0.25, 0.125 }; rel_to_abs (xw, xws, 5, xmax2 - xmin); // optimize the vertical space for source, parallel and frication // source part is relatively fixed. let the number of vertical section units be the divisor // connector line from source to parallel has to be horizontal // determine y's of source and parallel section _KlattGrid_queryParallelSplit (me, dy_vocalTract_p, &yh_parallel, &yf_parallel); if (yh_parallel == 0) { yh_parallel = yh_phonation; yf_parallel = yh_parallel / 2; yh_overlap = -0.1; } height_phonation = yh_phonation / (yh_phonation + yh_frication); if (height_phonation < 0.3) { height_phonation = 0.3; } double yunit = (ymax - ymin) / (yh_parallel + (1 - yh_overlap) * yh_frication); // some overlap double ycs = ymax - 0.5 * height_phonation; // source output connector double ycp = ymax - yf_parallel * yunit; // parallel input connector double ytrans_phonation = ycs > ycp ? ycp - ycs : 0; double ytrans_parallel = ycp > ycs ? ycs - ycp : 0; // source, tract, frication xs1 = xmin; xs2 = xs1 + xw[1]; double h1 = yh_phonation / 2, h2 = h1, h3 = yf_parallel, h4 = yh_parallel - h3, h5 = yh_frication; getYpositions (h1, h2, h3, h4, h5, yh_overlap, &dy, &ys1, &ys2, &yp1, &yp2, &yf1, &yf2); PhonationGrid_draw_inside (my phonation, g, xs1, xs2, ys1, ys2, dy_phonation, &yout_phonation); xp1 = xmin + xws[2]; xp2 = xp1 + xw[3]; VocalTractGrid_CouplingGrid_drawParallel_inline (my vocalTract, my coupling, g, xp1, xp2, yp1, yp2, dy_vocalTract_p, &yin_vocalTract_p, &yout_vocalTract_p); tf -> x[1] = xp2; tf -> y[1] = yout_vocalTract_p; Graphics_line (g, xs2, yout_phonation, xp1, yin_vocalTract_p); xf1 = xmin /*+ 0.5 * xws[1]*/; xf2 = xf1 + 0.55 * (xw[2] + xws[3]); FricationGrid_draw_inside (my frication, g, xf1, xf2, yf1, yf2, dy_frication, &yout_frication); } tf -> x[2] = xf2; tf -> y[2] = yout_frication; r = (xmax3 - xmax2) / 2; xs = xmax2 + r / 2; ys = (ymax - ymin) / 2; summer_drawConnections (g, xs, ys, r, tf, 1, 0.6); Graphics_arrow (g, xs + r, ys, xmax, ys); Graphics_unsetInner (g); connections_free (tf); } /**** Query, Add, Remove, Extract Replace ********/ #define PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE(Name,name,tierType) \ double KlattGrid_get##Name##AtTime (KlattGrid me, double t) \ { return RealTier_getValueAtTime ((RealTier) my phonation -> name, t); } \ void KlattGrid_add##Name##Point (KlattGrid me, double t, double value) \ { RealTier_addPoint ((RealTier) my phonation -> name, t, value);} \ void KlattGrid_remove##Name##Points (KlattGrid me, double t1, double t2) \ { AnyTier_removePointsBetween ((RealTier) my phonation -> name, t1, t2); } \ tierType KlattGrid_extract##Name##Tier (KlattGrid me) \ { return Data_copy ((tierType) my phonation -> name); } \ void KlattGrid_replace##Name##Tier (KlattGrid me, tierType thee) \ { try {\ if (my xmin != thy xmin || my xmax != thy xmax) Melder_throw ("Domains must be equal"); \ auto##tierType any = Data_copy ((tierType) thee); \ forget (my phonation -> name); \ my phonation -> name = any.transfer(); \ } catch (MelderError) { Melder_throw (me, ": tier not replaced."); } \ } // Generate 55 functions PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (Pitch, pitch, PitchTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (VoicingAmplitude, voicingAmplitude, IntensityTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (Flutter, flutter, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (Power1, power1, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (Power2, power2, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (OpenPhase, openPhase, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (CollisionPhase, collisionPhase, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (DoublePulsing, doublePulsing, RealTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (SpectralTilt, spectralTilt, IntensityTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (AspirationAmplitude, aspirationAmplitude, IntensityTier) PhonationGrid_QUERY_ADD_REMOVE_EXTRACT_REPLACE (BreathinessAmplitude, breathinessAmplitude, IntensityTier) FormantGrid *KlattGrid_getAddressOfFormantGrid (KlattGrid me, int formantType) { return formantType == KlattGrid_ORAL_FORMANTS ? & (my vocalTract -> oral_formants) : formantType == KlattGrid_NASAL_FORMANTS ? & (my vocalTract -> nasal_formants) : formantType == KlattGrid_FRICATION_FORMANTS ? & (my frication -> frication_formants) : formantType == KlattGrid_TRACHEAL_FORMANTS ? & (my coupling -> tracheal_formants) : formantType == KlattGrid_NASAL_ANTIFORMANTS ? & (my vocalTract -> nasal_antiformants) : formantType == KlattGrid_TRACHEAL_ANTIFORMANTS ? & (my coupling -> tracheal_antiformants) : formantType == KlattGrid_DELTA_FORMANTS ? & (my coupling -> delta_formants) : 0; } Ordered *KlattGrid_getAddressOfAmplitudes (KlattGrid me, int formantType) { return formantType == KlattGrid_ORAL_FORMANTS ? & (my vocalTract -> oral_formants_amplitudes) : formantType == KlattGrid_NASAL_FORMANTS ? & (my vocalTract -> nasal_formants_amplitudes) : formantType == KlattGrid_FRICATION_FORMANTS ? & (my frication -> frication_formants_amplitudes) : formantType == KlattGrid_TRACHEAL_FORMANTS ? & (my coupling -> tracheal_formants_amplitudes) : NULL; } #define KlattGrid_QUERY_ADD_REMOVE(Name) \ double KlattGrid_get##Name##AtTime (KlattGrid me, int formantType, long iformant, double t) \ { \ FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); \ return FormantGrid_get##Name##AtTime ((FormantGrid) *fg, iformant, t); \ } \ void KlattGrid_add##Name##Point (KlattGrid me, int formantType, long iformant, double t, double value) \ { \ FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); \ FormantGrid_add##Name##Point ((FormantGrid) *fg, iformant, t, value); \ } \ void KlattGrid_remove##Name##Points (KlattGrid me, int formantType, long iformant, double t1, double t2) \ { \ FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); \ FormantGrid_remove##Name##PointsBetween ((FormantGrid) *fg, iformant, t1, t2); \ } // 6 functions KlattGrid_QUERY_ADD_REMOVE (Formant) KlattGrid_QUERY_ADD_REMOVE (Bandwidth) void KlattGrid_formula_frequencies (KlattGrid me, int formantType, const wchar_t *expression, Interpreter interpreter) { FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); FormantGrid_formula_frequencies (*fg, expression, interpreter, 0); } void KlattGrid_formula_bandwidths (KlattGrid me, int formantType, const wchar_t *expression, Interpreter interpreter) { FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); FormantGrid_formula_bandwidths (*fg, expression, interpreter, 0); } void KlattGrid_formula_amplitudes (KlattGrid me, int formantType, const wchar_t *expression, Interpreter interpreter) { try { Ordered *ordered = KlattGrid_getAddressOfAmplitudes (me, formantType); Formula_compile (interpreter, *ordered, expression, kFormula_EXPRESSION_TYPE_NUMERIC, TRUE); for (long irow = 1; irow <= (*ordered) -> size; irow++) { RealTier amplitudes = (RealTier) (*ordered) -> item[irow]; for (long icol = 1; icol <= amplitudes -> points -> size; icol++) { struct Formula_Result result; Formula_run (irow, icol, & result); if (result. result.numericResult == NUMundefined) { Melder_throw ("Cannot put an undefined value into the tier.\nFormula not finished."); } ( (RealPoint) amplitudes -> points -> item [icol]) -> value = result. result.numericResult; } } } catch (MelderError) { Melder_throw (me, ": formula not finished on amplitudes."); } } double KlattGrid_getAmplitudeAtTime (KlattGrid me, int formantType, long iformant, double t) { Ordered *ordered = KlattGrid_getAddressOfAmplitudes (me, formantType); if (iformant < 0 || iformant > (*ordered) -> size) { return NUMundefined; } return RealTier_getValueAtTime ( (RealTier) (*ordered) -> item[iformant], t); } void KlattGrid_addAmplitudePoint (KlattGrid me, int formantType, long iformant, double t, double value) { Ordered *ordered = KlattGrid_getAddressOfAmplitudes (me, formantType); if (iformant < 0 || iformant > (*ordered) -> size) { Melder_throw (L"Formant does not exist."); } RealTier_addPoint ( (RealTier) (*ordered) -> item[iformant], t, value); } void KlattGrid_removeAmplitudePoints (KlattGrid me, int formantType, long iformant, double t1, double t2) { Ordered *ordered = KlattGrid_getAddressOfAmplitudes (me, formantType); if (iformant < 0 || iformant > (*ordered) ->size) { return; } AnyTier_removePointsBetween ( (*ordered) -> item[iformant], t1, t2); } IntensityTier KlattGrid_extractAmplitudeTier (KlattGrid me, int formantType, long iformant) { try { Ordered *ordered = KlattGrid_getAddressOfAmplitudes (me, formantType); if (iformant < 0 || iformant > (*ordered) ->size) { Melder_throw ("Formant does not exist."); } autoIntensityTier thee = Data_copy ( (IntensityTier) (*ordered) -> item[iformant]); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no IntensityTier extracted."); } } void KlattGrid_replaceAmplitudeTier (KlattGrid me, int formantType, long iformant, IntensityTier thee) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Domains must be equal"); } Ordered *ordered = KlattGrid_getAddressOfAmplitudes (me, formantType); if (iformant < 0 || iformant > (*ordered) -> size) { Melder_throw ("Formant does not exist."); } autoIntensityTier any = Data_copy (thee); forget ( ( (Thing *) (*ordered) -> item) [iformant]); (*ordered) -> item[iformant] = any.transfer(); } catch (MelderError) { Melder_throw (me, ": no ampitude tier replaced."); } } FormantGrid KlattGrid_extractFormantGrid (KlattGrid me, int formantType) { try { FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); autoFormantGrid thee = Data_copy (*fg); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no FormantGrid extracted."); } } void KlattGrid_replaceFormantGrid (KlattGrid me, int formantType, FormantGrid thee) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Domains must be equal"); } FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); autoFormantGrid any = Data_copy (thee); forget (*fg); *fg = any.transfer(); } catch (MelderError) { Melder_throw (me, ": no FormantGrid replaced."); } } void KlattGrid_addFormant (KlattGrid me, int formantType, long position) { try { FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); if (*fg == 0) { Melder_throw (L"Formant type ", formantType, " does not exist."); } long nof = (*fg) -> formants -> size; if (position > nof || position < 1) { position = nof + 1; } if (formantType == KlattGrid_NASAL_ANTIFORMANTS || formantType == KlattGrid_TRACHEAL_ANTIFORMANTS || formantType == KlattGrid_DELTA_FORMANTS) { FormantGrid_addFormantAndBandwidthTiers (*fg, position); return; } Ordered *ordered = KlattGrid_getAddressOfAmplitudes (me, formantType); long noa = (*ordered) -> size; if (nof != noa) { Melder_throw ("The number of formants (", nof, ") and the number of amplitudes (", noa, ") must be equal."); } FormantGrid_addFormantAndBandwidthTiers (*fg, position); try { autoIntensityTier it = IntensityTier_create (my xmin, my xmax); Ordered_addItemPos ( (*ordered), it.transfer(), position); } catch (MelderError) { // restore original FormantGrid_removeFormantAndBandwidthTiers (*fg, position); } } catch (MelderError) { Melder_throw (me, ": no formant added."); } } void KlattGrid_removeFormant (KlattGrid me, int formantType, long position) { FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); if (position < 1 || position > (*fg) -> formants -> size) { return; } FormantGrid_removeFormantAndBandwidthTiers (*fg, position); if (formantType == KlattGrid_NASAL_ANTIFORMANTS || formantType == KlattGrid_TRACHEAL_ANTIFORMANTS || formantType == KlattGrid_DELTA_FORMANTS) { return; // Done, no amplitudes } Ordered *ordered = KlattGrid_getAddressOfAmplitudes (me, formantType); Collection_removeItem (*ordered, position); } void KlattGrid_addFormantAndBandwidthTier (KlattGrid me, int formantType, long position) { FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); FormantGrid_addFormantAndBandwidthTiers (*fg, position); } void KlattGrid_removeFormantAndBandwidthTier (KlattGrid me, int formantType, long position) { FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, formantType); FormantGrid_removeFormantAndBandwidthTiers (*fg, position); } double KlattGrid_getDeltaFormantAtTime (KlattGrid me, long iformant, double t) { return FormantGrid_getFormantAtTime (my coupling -> delta_formants, iformant, t); } void KlattGrid_addDeltaFormantPoint (KlattGrid me, long iformant, double t, double value) { FormantGrid_addFormantPoint (my coupling -> delta_formants, iformant, t, value); } void KlattGrid_removeDeltaFormantPoints (KlattGrid me, long iformant, double t1, double t2) { FormantGrid_removeFormantPointsBetween (my coupling -> delta_formants, iformant, t1, t2); } double KlattGrid_getDeltaBandwidthAtTime (KlattGrid me, long iformant, double t) { return FormantGrid_getBandwidthAtTime (my coupling -> delta_formants, iformant, t); } void KlattGrid_addDeltaBandwidthPoint (KlattGrid me, long iformant, double t, double value) { FormantGrid_addBandwidthPoint (my coupling -> delta_formants, iformant, t, value); } void KlattGrid_removeDeltaBandwidthPoints (KlattGrid me, long iformant, double t1, double t2) { FormantGrid_removeBandwidthPointsBetween (my coupling -> delta_formants, iformant, t1, t2); } FormantGrid KlattGrid_extractDeltaFormantGrid (KlattGrid me) { try { FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, KlattGrid_DELTA_FORMANTS); autoFormantGrid thee = Data_copy (*fg); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no delta FormantGrid extracted."); } } void KlattGrid_replaceDeltaFormantGrid (KlattGrid me, FormantGrid thee) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Domains must be equal"); } FormantGrid *fg = KlattGrid_getAddressOfFormantGrid (me, KlattGrid_DELTA_FORMANTS); autoFormantGrid him = Data_copy (thee); forget (*fg); *fg = him.transfer(); } catch (MelderError) { Melder_throw (me, ": no delta FormantGrid replaced."); } } FormantGrid KlattGrid_to_oralFormantGrid_openPhases (KlattGrid me, double fadeFraction) { try { if (my vocalTract -> oral_formants -> formants -> size == 0 && my vocalTract -> oral_formants -> bandwidths -> size == 0) { Melder_throw ("Formant grid is empty."); } if (fadeFraction < 0) { fadeFraction = 0; } if (fadeFraction >= 0.5) { Melder_throw ("Fade fraction must be smaller than 0.5"); } my coupling -> options -> fadeFraction = fadeFraction; autoFormantGrid thee = Data_copy ( (FormantGrid) my vocalTract -> oral_formants); KlattGrid_setGlottisCoupling (me); FormantGrid_CouplingGrid_updateOpenPhases (thee.peek(), my coupling); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no \"open phase\" oral FormantGrid created."); } } PointProcess KlattGrid_extractPointProcess_glottalClosures (KlattGrid me) { try { // Update PhonationTier autoPhonationTier pt = PhonationGrid_to_PhonationTier (my phonation); autoPointProcess thee = PhonationTier_to_PointProcess_closures (pt.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no glottal closure points extracted."); } } double KlattGrid_getFricationAmplitudeAtTime (KlattGrid me, double t) { return RealTier_getValueAtTime (my frication -> fricationAmplitude, t); } void KlattGrid_addFricationAmplitudePoint (KlattGrid me, double t, double value) { RealTier_addPoint (my frication -> fricationAmplitude, t, value); } void KlattGrid_removeFricationAmplitudePoints (KlattGrid me, double t1, double t2) { AnyTier_removePointsBetween (my frication -> fricationAmplitude, t1, t2); } IntensityTier KlattGrid_extractFricationAmplitudeTier (KlattGrid me) { return Data_copy (my frication -> fricationAmplitude); } void KlattGrid_replaceFricationAmplitudeTier (KlattGrid me, IntensityTier thee) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Domains must be equal"); } autoIntensityTier him = Data_copy (thee); forget (my frication -> fricationAmplitude); my frication -> fricationAmplitude = him.transfer(); } catch (MelderError) { Melder_throw (me, ": no frication amplitude tier replaced."); } } double KlattGrid_getFricationBypassAtTime (KlattGrid me, double t) { return RealTier_getValueAtTime (my frication -> bypass, t); } void KlattGrid_addFricationBypassPoint (KlattGrid me, double t, double value) { RealTier_addPoint (my frication -> bypass, t, value); } void KlattGrid_removeFricationBypassPoints (KlattGrid me, double t1, double t2) { AnyTier_removePointsBetween (my frication -> bypass, t1, t2); } IntensityTier KlattGrid_extractFricationBypassTier (KlattGrid me) { return Data_copy (my frication -> bypass); } void KlattGrid_replaceFricationBypassTier (KlattGrid me, IntensityTier thee) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Domains must be equal"); } autoIntensityTier him = Data_copy (thee); forget (my frication -> bypass); my frication -> bypass = him.transfer(); } catch (MelderError) { Melder_throw (me, ": no frication bypass tier replaced."); } } void KlattGrid_setGlottisCoupling (KlattGrid me) { try { forget (my coupling -> glottis); my coupling -> glottis = PhonationGrid_to_PhonationTier (my phonation); if (my coupling -> glottis == 0) { Melder_throw ("Empty phonation tier."); } } catch (MelderError) { Melder_throw (me, ": no coupling could be set."); } } Sound KlattGrid_to_Sound_aspiration (KlattGrid me, double samplingFrequency) { return PhonationGrid_to_Sound_aspiration (my phonation, samplingFrequency); } Sound KlattGrid_to_Sound_phonation (KlattGrid me) { return PhonationGrid_to_Sound (my phonation, 0, my options -> samplingFrequency); } Sound KlattGrid_to_Sound (KlattGrid me) { try { autoSound thee = 0; PhonationGridPlayOptions pp = my phonation -> options; FricationGridPlayOptions pf = my frication -> options; double samplingFrequency = my options -> samplingFrequency; if (pp -> voicing) { KlattGrid_setGlottisCoupling (me); } if (pp -> aspiration || pp -> voicing) { // No vocal tract filtering if no glottal source signal present autoSound source = PhonationGrid_to_Sound (my phonation, my coupling, samplingFrequency); thee.reset (Sound_VocalTractGrid_CouplingGrid_filter (source.peek(), my vocalTract, my coupling)); } if (pf -> endFricationFormant > 0 || pf -> bypass) { autoSound frication = FricationGrid_to_Sound (my frication, samplingFrequency); if (thee.peek() != 0) { _Sounds_add_inline (thee.peek(), frication.peek()); } else { thee.reset (frication.transfer()); } } if (thee.peek() == 0) { thee.reset (Sound_createEmptyMono (my xmin, my xmax, samplingFrequency)); } else if (my options -> scalePeak) { Vector_scale (thee.peek(), 0.99); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Sound created."); } } void KlattGrid_playSpecial (KlattGrid me) { try { autoSound thee = KlattGrid_to_Sound (me); KlattGridPlayOptions him = my options; if (his scalePeak) { Vector_scale (thee.peek(), 0.99); } if (his xmin == 0 && his xmax == 0) { his xmin = my xmin; his xmax = my xmax; } Sound_playPart (thee.peek(), his xmin, his xmax, 0, 0); } catch (MelderError) { Melder_throw (me, ": not played."); } } void KlattGrid_play (KlattGrid me) { KlattGrid_setDefaultPlayOptions (me); KlattGrid_playSpecial (me); } /************************* Sound(s) & KlattGrid **************************************************/ Sound Sound_KlattGrid_filter_frication (Sound me, KlattGrid thee) { return Sound_FricationGrid_filter (me, thy frication); } Sound Sound_KlattGrid_filterByVocalTract (Sound me, KlattGrid thee, int filterModel) { try { if (my xmin != thy xmin || my xmax != thy xmax) { Melder_throw ("Domains must be equal."); } KlattGrid_setDefaultPlayOptions (thee); thy coupling -> options -> openglottis = 0; // don't trust openglottis info! thy vocalTract -> options -> filterModel = filterModel; autoSound him = Sound_VocalTractGrid_CouplingGrid_filter (me, thy vocalTract, thy coupling); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": not filtered by KlattGrid."); } } /******************* KlattTable to KlattGrid *********************/ KlattGrid KlattTable_to_KlattGrid (KlattTable me, double frameDuration) { try { Table kt = (Table) me; long nrows = my rows -> size; double tmin = 0, tmax = nrows * frameDuration; double dBNul = -300; double dB_offset = -20 * log10 (2.0e-5) - 87; // in KlattTable maximum in DB_to_LIN is at 87 dB : 32767 double dB_offset_voicing = 20 * log10 (320000 / 32767); // V'[n] in range (-320000,32000) double dB_offset_noise = -20 * log10 (32.767 / 8.192); // noise in range (-8192,8192) // double dB_offset_noise = -20 * log10 (320000/32767) - 20 * log10 (32.767 / 8.192); double ap[7] = {0, 0.4, 0.15, 0.06, 0.04, 0.022, 0.03 }; long numberOfFormants = 6; long numberOfNasalFormants = 1; long numberOfNasalAntiFormants = numberOfNasalFormants; long numberOfTrachealFormants = 0; long numberOfTrachealAntiFormants = numberOfTrachealFormants; long numberOfFricationFormants = 6; long numberOfDeltaFormants = 1; autoKlattGrid thee = KlattGrid_create (tmin, tmax, numberOfFormants, numberOfNasalFormants, numberOfNasalAntiFormants, numberOfTrachealFormants, numberOfTrachealAntiFormants, numberOfFricationFormants, numberOfDeltaFormants); for (long irow = 1; irow <= nrows; irow++) { double t = (irow - 1) * frameDuration; long icol = 1; double val = Table_getNumericValue_Assert (kt, irow, icol) / 10; // F0hz10 double f0 = val; RealTier_addPoint (thy phonation -> pitch, t, f0); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // AVdb // dB values below 13 were put to zero in the DBtoLIN function val -= 7; if (val < 13) { val = dBNul; } // RealTier_addPoint (thy source -> voicingAmplitude, t, val); for (long kf = 1; kf <= 6; kf++) { icol++; double fk = val = Table_getNumericValue_Assert (kt, irow, icol); // Fhz RealTier_addPoint ( (RealTier) thy vocalTract -> oral_formants -> formants -> item[kf], t, val); RealTier_addPoint ( (RealTier) thy frication -> frication_formants -> formants -> item[kf], t, val); // only amplitudes and bandwidths in frication section icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // Bhz if (val <= 0) { val = fk / 10; } RealTier_addPoint ( (RealTier) thy vocalTract -> oral_formants -> bandwidths -> item[kf], t, val); } icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // FNZhz RealTier_addPoint ( (RealTier) thy vocalTract -> nasal_antiformants -> formants -> item[1], t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // BNZhz RealTier_addPoint ( (RealTier) thy vocalTract -> nasal_antiformants -> bandwidths -> item[1], t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // FNPhz RealTier_addPoint ( (RealTier) thy vocalTract -> nasal_formants -> formants -> item[1], t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // BNPhz RealTier_addPoint ( (RealTier) thy vocalTract -> nasal_formants -> bandwidths -> item[1], t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // ah if (val < 13) { val = dBNul; } else { val += 20 * log10 (0.05) + dB_offset_noise; } RealTier_addPoint (thy phonation -> aspirationAmplitude, t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // Kopen double openPhase = f0 > 0 ? (val / 16000) * f0 : 0.7; RealTier_addPoint (thy phonation -> openPhase, t, openPhase); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // Aturb breathinessAmplitude during voicing (max is 8192) if (val < 13) { val = dBNul; } else { val += 20 * log10 (0.1) + dB_offset_noise; } RealTier_addPoint (thy phonation -> breathinessAmplitude, t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // TLTdb RealTier_addPoint (thy phonation -> spectralTilt, t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // AF if (val < 13) { val = dBNul; } else { val += 20 * log10 (0.25) + dB_offset_noise; } RealTier_addPoint (thy frication -> fricationAmplitude, t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // Kskew ??? //RealTier_addPoint (, t, val); for (long kf = 1; kf <= 6; kf++) { icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // Ap if (val < 13) { val = dBNul; } else { val += 20 * log10 (ap[kf]) + dB_offset; } RealTier_addPoint ( (RealTier) thy vocalTract -> oral_formants_amplitudes -> item[kf], t, val); RealTier_addPoint ( (RealTier) thy frication -> frication_formants_amplitudes -> item[kf], t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // Bhz RealTier_addPoint ( (RealTier) thy frication -> frication_formants -> bandwidths -> item[kf], t, val); } icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // ANP if (val < 13) { val = dBNul; } else { val += 20 * log10 (0.6) + dB_offset; } RealTier_addPoint ( (RealTier) thy vocalTract -> nasal_formants_amplitudes -> item[1], t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // AB if (val < 13) { val = dBNul; } else { val += 20 * log10 (0.05) + dB_offset_noise; } RealTier_addPoint (thy frication -> bypass, t, val); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // AVpdb RealTier_addPoint (thy phonation -> voicingAmplitude, t, val + dB_offset_voicing); icol++; val = Table_getNumericValue_Assert (kt, irow, icol); // Gain0 val -= 3; if (val <= 0) { val = 57; } RealTier_addPoint (thy gain, t, val + dB_offset); } // We don't need the following low-pass: we do not use oversampling !! //RealTier_addPoint (thy tracheal_formants -> formants -> item[1], 0.5*(tmin+tmax), 0.095*samplingFrequency); //RealTier_addPoint (thy tracheal_formants -> bandwidths -> item[1], 0.5*(tmin+tmax), 0.063*samplingFrequency); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no KlattGrid created."); } } KlattGrid Sound_to_KlattGrid_simple (Sound me, double timeStep, long maximumNumberOfFormants, double maximumFormantFrequency, double windowLength, double preEmphasisFrequency, double minimumPitch, double maximumPitch, double pitchFloorIntensity, int subtractMean) { try { long numberOfFormants = maximumNumberOfFormants; long numberOfNasalFormants = 1; long numberOfNasalAntiFormants = numberOfNasalFormants; long numberOfTrachealFormants = 1; long numberOfTrachealAntiFormants = numberOfTrachealFormants; long numberOfFricationFormants = maximumNumberOfFormants; long numberOfDeltaFormants = 1; autoSound sound = Data_copy (me); Vector_subtractMean (sound.peek()); autoFormant f = Sound_to_Formant_burg (sound.peek(), timeStep, maximumNumberOfFormants, maximumFormantFrequency, windowLength, preEmphasisFrequency); autoFormantGrid fgrid = Formant_downto_FormantGrid (f.peek()); autoPitch p = Sound_to_Pitch (sound.peek(), timeStep, minimumPitch, maximumPitch); autoPitchTier ptier = Pitch_to_PitchTier (p.peek()); autoIntensity i = Sound_to_Intensity (sound.peek(), pitchFloorIntensity, timeStep, subtractMean); autoIntensityTier itier = Intensity_downto_IntensityTier (i.peek()); autoKlattGrid thee = KlattGrid_create (my xmin, my xmax, numberOfFormants, numberOfNasalFormants, numberOfNasalAntiFormants, numberOfTrachealFormants, numberOfTrachealAntiFormants, numberOfFricationFormants, numberOfDeltaFormants); KlattGrid_replacePitchTier (thee.peek(), ptier.peek()); KlattGrid_replaceFormantGrid (thee.peek(), KlattGrid_ORAL_FORMANTS, fgrid.peek()); KlattGrid_replaceVoicingAmplitudeTier (thee.peek(), itier.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no simple KlattGrid created."); } } /* End of file KlattGrid.cpp */ sources_5316/dwtools/Configuration_and_Procrustes.cpp0000644000176700017670000000331211606610672022010 0ustar paulpaul/* Configuration_and_Procrustes.c * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020424 GPL djmw 20020704 Changed header NUMclasses.h to SVD.h djmw 20041022 Added orthogonal argument to Configurations_to_Procrustes. */ #include "Configuration_and_Procrustes.h" #include "NUM2.h" Procrustes Configurations_to_Procrustes (Configuration me, Configuration thee, int orthogonal) { try { if (my numberOfRows != thy numberOfRows || my numberOfColumns != thy numberOfColumns) { Melder_throw ("Configurations must have the same number of points and the same dimension."); } autoProcrustes p = Procrustes_create (my numberOfColumns); double *translation = 0, *scale = 0; if (! orthogonal) { translation = p -> t; scale = & (p -> s); } NUMProcrustes (my data, thy data, my numberOfRows, my numberOfColumns, p -> r, translation, scale); return p.transfer(); } catch (MelderError) { Melder_throw ("Procrustes from two Configurations not created."); } } /* End of file Configuration_and_Procrustes.c */ sources_5316/dwtools/FilterBank.h0000644000176700017670000001164511631435420015616 0ustar paulpaul#ifndef _FilterBank_h_ #define _FilterBank_h_ /* FilterBank.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010609 djmw 20020813 GPL header djmw 20040702 Corrected MELTOBARK formula. djmw 20110306 Latest modification. */ #include "TableOfReal.h" #include "Spectrum.h" #include "MFCC.h" #include "Intensity.h" #include "PCA.h" #define HZTOBARK(x) NUMhertzToBark2(x) #define HZTOMEL(x) NUMhertzToMel2(x) #define BARKTOHZ(x) NUMbarkToHertz2(x) #define MELTOHZ(x) NUMmelToHertz2(x) #define BARKTOMEL(x) HZTOMEL(BARKTOHZ(x)) #define MELTOBARK(x) HZTOBARK(MELTOHZ(x)) #define FilterBank_DBREF 4e-10 #define FilterBank_DBFAC 1 #define FilterBank_DBFLOOR -20 #define FilterBank_HERTZ 1 #define FilterBank_BARK 2 #define FilterBank_MEL 3 Thing_define (FilterBank, Matrix) { // new methods: public: virtual int v_getFrequencyScale () { return FilterBank_HERTZ; } }; Thing_define (BarkFilter, FilterBank) { // overridden methods: protected: virtual int v_getFrequencyScale () { return FilterBank_BARK; } }; /* Interpretation: xmin, xmax, x1, dx, nx like Sampled. ymin, ymax lowest and highest frequencies in Barks. y1 mid of first filter (bark). dy distance between filters (bark). ny the number of filters. */ double FilterBank_getFrequencyInHertz (I, double f, int scale_from); double FilterBank_getFrequencyInBark (I, double f, int scale_from); double FilterBank_getFrequencyInMel (I, double f, int scale_from); int FilterBank_getFrequencyScale (I); void FilterBank_drawFrequencyScales (I, Graphics g, int horizontalScale, double xmin, double xmax, int verticalScale, double ymin, double ymax, int garnish); void BarkFilter_drawSekeyHansonFilterFunctions (BarkFilter me, Graphics g, int freqScale, int fromFilter, int toFilter, double zmin, double zmax, int dbScale, double ymin, double ymax, int garnish); void FilterBank_drawTimeSlice (I, Graphics g, double t, double fmin, double fmax, double min, double max, const wchar_t *xlabel, int garnish); BarkFilter BarkFilter_create (double tmin, double tmax, long nt, double dt, double t1, double fmin, double fmax, long nf, double df, long f1); BarkFilter Matrix_to_BarkFilter (I); Thing_define (MelFilter, FilterBank) { // overridden methods: protected: virtual int v_getFrequencyScale () { return FilterBank_MEL; } }; /* Interpretation: xmin, xmax, x1, dx, nx like Sampled. ymin, ymax lowest and highest frequencies in mels. y1 mid of first filter (mels). dy distance between filters (mel). ny the number of filters. */ MelFilter MelFilter_create (double tmin, double tmax, long nt, double dt, double t1, double fmin, double fmax, long nf, double df, double f1); MelFilter Matrix_to_MelFilter (I); void MelFilter_drawFilterFunctions (MelFilter me, Graphics g, int freqScale, int fromFilter, int toFilter, double zmin, double zmax, int dbScale, double ymin, double ymax, int garnish); MFCC MelFilter_to_MFCC (MelFilter me, long numberOfCoefficients); Thing_define (FormantFilter, FilterBank) { // overridden methods: protected: //virtual int v_getFrequencyScale (); // David, is dit correct? ja // new methods: public: //virtual void v_drawFilterFunction (int from, int to, void *dwrawclosure); // David, is dit correct? ja }; FormantFilter FormantFilter_create (double tmin, double tmax, long nt, double dt, double t1, double fmin, double fmax, long nf, double df, double f1); void FormantFilter_drawFilterFunctions (FormantFilter me, Graphics g, double bandwidth, int freqScale, int fromFilter, int toFilter, double zmin, double zmax, int dbScale, double ymin, double ymax, int garnish); FormantFilter Matrix_to_FormantFilter (I); void FilterBank_equalizeIntensities (I, double intensity_db); Matrix FilterBank_to_Matrix (I); /* Generieke ...Filters_to_Matrix */ Spectrum FormantFilter_to_Spectrum_slice (FormantFilter me, double t); /* Calculate amplitude spectrum at time t. power[i] = ref * 10 ^ (my z[i][t] / 10) spec->z[1][i] = sqrt(power[i]) = sqrt(ref) * 10 ^ (my z[i][t] / (2*10)) spec->z[2][i] = 0 */ Intensity FilterBank_to_Intensity (I); void FilterBank_and_PCA_drawComponent (I, PCA thee, Graphics g, long component, double dblevel, double frequencyOffset, double scale, double tmin, double tmax, double fmin, double fmax); #endif /* _FilterBank_h_ */ sources_5316/dwtools/Minimizers.cpp0000644000176700017670000003747711725110316016267 0ustar paulpaul/* Minimizers.cpp * * Copyright (C) 2001-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* David Weenink, 20011016 djmw 20011016 removed some causes for compiler warnings djmw 20030205 Latest modification djmw 20030701 Removed non-GPL minimizations djmw 20040421 Bug removed: delayed message when learning was interrupted by user. djmw 20080122 float -> double djmw 20110304 Thing_new */ #include "NUM2.h" #include "Graphics.h" #include "Minimizers.h" #define SIGN(x,s) ((s) < 0 ? -fabs (x) : fabs(x)) #define GOLD 1.618034 #define CGOLD 0.3819660 #define ITMAX 100.0 #define TINY 1.0e-20 #define ZEPS 1.0e-10 #define EPS 1.0e-10 #define TOL 2e-4 #define SHFT(a, b, c, d) (a) = (b); (b) = (c); (c) = (d); #define MOV3(a, b, c, d, e, f) (a) = (d); (b) = (e); (c) = (f); #define FUNC1(fx, x) for (i=1; i <= my nParameters; i++) my ptry[i] = p[i] + (x) * direction[i]; \ (fx) = my func (my object, my ptry); #define DFUNC1(df, x) for (i=1; i <= my nParameters; i++) my ptry[i] = p[i] + (x) * direction[i]; \ my dfunc (my object, my ptry, my dp); for (df=0, i=1; i <= my nParameters; i++) df += my dp[i] * direction[i]; Thing_implement (Minimizer, Thing, 0); void structMinimizer :: v_destroy () { NUMvector_free (p, 1); NUMvector_free (history, 1); Minimizer_Parent :: v_destroy (); } static void classMinimizer_after (I, Any aclosure) { iam (Minimizer); (void) aclosure; if (my success || ! my gmonitor) { return; } if (my start == 1) { wchar_t s[35]; Minimizer_drawHistory (me, my gmonitor, 0, my maxNumOfIterations, 0, 1.1 * my history[1], 1); swprintf (s, 35, L"Dimension of search space: %6ld", my nParameters); Graphics_textTop (my gmonitor, 0, s); } Graphics_setInner (my gmonitor); Graphics_line (my gmonitor, my iteration, my history[my iteration], my iteration, my history[my iteration]); Graphics_unsetInner (my gmonitor); Melder_monitor ( (double) (my iteration) / my maxNumOfIterations, L"Iterations: ", Melder_integer (my iteration), L", Function calls: ", Melder_integer (my funcCalls), L", Cost: ", Melder_double (my minimum)); } void Minimizer_init (I, long nParameters, Data object) { iam (Minimizer); my nParameters = nParameters; my p = NUMvector (1, nParameters); my object = object; my minimum = 1.0e30; my after = classMinimizer_after; Minimizer_reset (me, 0); /* added 27/11/97 */ } void Minimizer_setParameters (Minimizer me, Any parameters) { my v_setParameters (parameters); } static void monitor_off (Minimizer me) { Melder_monitor (1.1, NULL); if (my gmonitor) { Graphics_clearWs (my gmonitor); // DON'T forget (my gmonitor) my gmonitor = NULL; } } void Minimizer_minimize (Minimizer me, long maxNumOfIterations, double tolerance, int monitor) { try { my tolerance = tolerance; if (maxNumOfIterations <= 0) { return; } if (my iteration + maxNumOfIterations > my maxNumOfIterations) { double *history; my maxNumOfIterations += maxNumOfIterations; if (my history) { my history++; /* arrays start at 1 !! */ } history = (double *) Melder_realloc (my history, my maxNumOfIterations * sizeof (double)); my history = --history; /* arrays start at 1 !! */ } if (monitor) { my gmonitor = (Graphics) Melder_monitor (0.0, L"Starting..."); } my start = 1; /* for my after() */ my v_minimize (); if (monitor) { monitor_off (me); } if (my success) Melder_casual ("Minimizer_minimize: minimum %f reached \n" "after %ld iterations and %ld function calls.", my minimum, my iteration, my funcCalls); } catch (MelderError) { if (monitor) { monitor_off (me); // temporarily until better monitor facilities } Melder_clearError(); // memory error in history mechanism is not fatal } } void Minimizer_minimizeManyTimes (Minimizer me, long numberOfTimes, long maxIterationsPerTime, double tolerance) { double fopt = my minimum; int monitorSingle = numberOfTimes == 1; autoNUMvector popt (NUMvector_copy (my p, 1, my nParameters), 1); if (! monitorSingle) { Melder_progress (0.0, L"Minimize many times"); } /* on first iteration start with current parameters 27/11/97 */ for (long i = 1; i <= numberOfTimes; i++) { Minimizer_minimize (me, maxIterationsPerTime, tolerance, monitorSingle); Melder_casual ("Current %ld: minimum = %.17g", i, my minimum); if (my minimum < fopt) { NUMvector_copyElements (my p, popt.peek(), 1, my nParameters); fopt = my minimum; } Minimizer_reset (me, 0); if (! monitorSingle) { try { Melder_progress ( (double) i / numberOfTimes, Melder_integer (i), L" from ", Melder_integer (numberOfTimes)); therror } catch (MelderError) { Melder_clearError (); // interrurpt, no error break; } } } if (! monitorSingle) { Melder_progress (1.0, 0); } Minimizer_reset (me, popt.peek()); } static void Minimizer_setAfterEachIteration (Minimizer me, void (*after) (I, Any aclosure), Any aclosure) { my after = after; my aclosure = aclosure; } void Minimizer_reset (Minimizer me, const double guess[]) { if (guess) { for (long i = 1; i <= my nParameters; i++) { my p[i] = guess[i]; } } else { for (long i = 1; i <= my nParameters; i++) { my p[i] = NUMrandomUniform (-1, 1); } } /* Don't use NUMdvector_free: realloc in Minimizer_minimize */ if (my history != 0) { my history++; Melder_free (my history); } my maxNumOfIterations = my success = my funcCalls = my iteration = 0; my minimum = 1.0e38; my v_reset (); } void Minimizer_drawHistory (Minimizer me, Graphics g, long iFrom, long iTo, double hmin, double hmax, int garnish) { if (my history == 0) { return; } autoNUMvector history (1, my iteration); for (long i = 1; i <= my iteration; i++) { history[i] = my history[i]; } if (iTo <= iFrom) { iFrom = 1; iTo = my iteration; } long itmin = iFrom, itmax = iTo; if (itmin < 1) { itmin = 1; } if (itmax > my iteration) { itmax = my iteration; } if (hmax <= hmin) { NUMvector_extrema (history.peek(), itmin, itmax, & hmin, & hmax); } if (hmax <= hmin) { hmin -= 0.5 * fabs (hmin); hmax += 0.5 * fabs (hmax); } Graphics_setInner (g); Graphics_setWindow (g, iFrom, iTo, hmin, hmax); Graphics_function (g, history.peek(), itmin, itmax, itmin, itmax); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Number of iterations"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } double Minimizer_getMinimum (Minimizer me) { return my minimum; } /************** class SteepestDescentMinimizer **********************/ Thing_implement (SteepestDescentMinimizer, Minimizer, 0); void structSteepestDescentMinimizer :: v_minimize () { autoNUMvector dp (1, nParameters); autoNUMvector dpp (1, nParameters); double fret = func (object, p); while (iteration < maxNumOfIterations) { dfunc (object, p, dp.peek()); for (long i = 1; i <= nParameters; i++) { dpp[i] = - eta * dp[i] + momentum * dpp[i]; p[i] += dpp[i]; } history[++iteration] = minimum = func (object, p); success = 2.0 * fabs (fret - minimum) < tolerance * (fabs (fret) + fabs (minimum)); if (after) { try { after (this, aclosure); } catch (MelderError) { Melder_casual ("Interrupted after %ld iterations.", iteration); Melder_clearError (); break; } } if (success) { break; } fret = minimum; } } void structSteepestDescentMinimizer :: v_setParameters (Any parameters) { if (p) { SteepestDescentMinimizer_parameters thee = (SteepestDescentMinimizer_parameters) parameters; eta = thy eta; momentum = thy momentum; } else { eta = 0.1; momentum = 0.9; } } SteepestDescentMinimizer SteepestDescentMinimizer_create (long nParameters, Data object, double (*func) (Data object, const double p[]), void (*dfunc) (Data object, const double p[], double dp[])) { try { autoSteepestDescentMinimizer me = Thing_new (SteepestDescentMinimizer); Minimizer_init (me.peek(), nParameters, object); my func = func; my dfunc = dfunc; return me.transfer(); } catch (MelderError) { Melder_throw ("SteepestDescentMinimizer not created."); } } /***************** class VDSmagtMinimizer ******************************/ Thing_implement (VDSmagtMinimizer, Minimizer, 0); void structVDSmagtMinimizer :: v_minimize () { int decrease_direction_found = 1; int l_iteration = 1; // David, dat is gevaarlijk: een locale variabele met dezelfde naam als een member; daarom hernoemd, maar is het correct? yes, we can iterate in steps, therefore local and global counter double rtemp, rtemp2; // df is estimate of function reduction obtainable during line search // restart = 2 => line search in direction of steepest descent // restart = 1 => line search with Powell-restart. // flag = 1 => no decrease in function value during previous line search; // flag = 2 => line search did not decrease gradient // OK; must restart if (restart_flag) { minimum = func (object, p); dfunc (object, p, dp); df = minimum; restart = 2; one_up = flag = 0; gcg0 = gopt_sq = 0.0; } restart_flag = 1; while (++ this -> iteration <= maxNumOfIterations) { if (flag & 1) { if (one_up) { decrease_direction_found = 0; this -> iteration --; break; } else { one_up = 1; } } else { one_up = 0; } if (flag & 2) { restart = 2; /* flag & 1 ??? */ } else if (fabs ( (double) gcg0) > 0.2 * gopt_sq) { restart = 1; } if (restart == 0) { rtemp = rtemp2 = 0.0; for (long i = 1; i <= nParameters; i++) { rtemp += gc[i] * grst[i]; rtemp2 += gc[i] * srst[i]; } gamma = rtemp / gamma_in; if (fabs (beta * gropt - gamma * rtemp2) > 0.2 * gopt_sq) { restart = 1; } else { for (long i = 1; i <= nParameters; i++) { s[i] = beta * s[i] + gamma * srst[i] - gc[i]; } } } if (restart == 2) { for (long i = 1; i <= nParameters; i++) { s[i] = - dp[i]; } restart = 1; } else if (restart == 1) { gamma_in = gropt - gr0; for (long i = 1; i <= nParameters; i++) { srst[i] = s[i]; s[i] = beta * s[i] - gc[i]; grst[i] = gc[i] - g0[i]; } restart = 0; } // Begin line search // lineSearch_iteration = #iterations during current line search flag = 0; lineSearch_iteration = 0; rtemp = 0.0; for (long i = 1; i <= nParameters; i++) { rtemp += dp[i] * s[i]; g0[i] = dp[i]; } gr0 = gropt = rtemp; if (l_iteration == 1) { alphamin = fabs (df / gropt); } if (gr0 > 0) { flag = 1; restart = 2; continue; } f0 = minimum; // alpha = length of step along line; // dalpha = change in alpha // alphamin = position of min along line alplim = -1; again = -1; rtemp = fabs (df / gropt); dalpha = alphamin < rtemp ? alphamin : rtemp; alphamin = 0; do { do { if (lineSearch_iteration) { if (! (fch == 0)) { gr2s += (temp + temp) / dalpha; } if (alplim < -0.5) { dalpha = 9.0 * alphamin; } else { dalpha = 0.5 * (alplim - alphamin); } grs = gropt + dalpha * gr2s; if (gropt * grs < 0) { dalpha *= gropt / (gropt - grs); } } alpha = alphamin + dalpha; for (long i = 1; i <= nParameters; i++) { pc[i] = p[i] + dalpha * s[i]; } fc = func (object, pc); dfunc (object, pc, gc); l_iteration ++; lineSearch_iteration++; gsq = grc = 0.0; for (long i = 1; i <= nParameters; i++) { gsq += gc[i] * gc[i]; grc += gc[i] * s[i]; } fch = fc - minimum; gr2s = (grc - gropt) / dalpha; temp = (fch + fch) / dalpha - grc - gropt; if ( (fc < minimum) || ( (fc == minimum) && (grc / gropt > -1))) { double *tmp; gopt_sq = gsq; history [this ->iteration] = minimum = fc; tmp = p; p = pc; pc = tmp; tmp = dp; dp = gc; gc = tmp; if (grc *gropt <= 0) { alplim = alphamin; } alphamin = alpha; gropt = grc; dalpha = - dalpha; success = gsq < tolerance; if (after) { try { after (this, aclosure); } catch (MelderError) { Melder_casual ("Interrupted after %ld iterations.", this -> iteration); Melder_clearError (); break; } } if (success) { return; } if (fabs (gropt / gr0) < lineSearchGradient) { break; } } else { alplim = alpha; } } while (lineSearch_iteration <= lineSearchMaxNumOfIterations); fc = history [this -> iteration] = minimum; rtemp = 0.0; for (long i = 1; i <= nParameters; i++) { pc[i] = p[i]; gc[i] = dp[i]; rtemp += gc[i] * g0[i]; } gcg0 = rtemp; if (fabs (gropt - gr0) > tolerance) { beta = (gopt_sq - gcg0) / (gropt - gr0); if (fabs (beta * gropt) < 0.2 * gopt_sq) { break; } } again++; if (again > 0) { flag += 2; } } while (flag < 1); if (f0 <= minimum) { flag += 1; } df = gr0 * alphamin; } if (this -> iteration > maxNumOfIterations) { this -> iteration = maxNumOfIterations; } if (decrease_direction_found) { restart_flag = 0; } } void structVDSmagtMinimizer :: v_destroy () { NUMvector_free (dp, 1); NUMvector_free (pc, 1); NUMvector_free (gc, 1); NUMvector_free (g0, 1); NUMvector_free (s, 1); NUMvector_free (srst, 1); NUMvector_free (grst, 1); VDSmagtMinimizer_Parent :: v_destroy (); } void structVDSmagtMinimizer :: v_reset () { restart_flag = 1; } void structVDSmagtMinimizer :: v_setParameters (Any parameters) { if (parameters) { VDSmagtMinimizer_parameters vdspars = (VDSmagtMinimizer_parameters) parameters; // David, weer link: dezelfde naam,: Nu niet meer lineSearchGradient = vdspars -> lineSearchGradient; lineSearchMaxNumOfIterations = vdspars -> lineSearchMaxNumOfIterations; } } VDSmagtMinimizer VDSmagtMinimizer_create (long nParameters, Data object, double (*func) (Data object, const double x[]), void (*dfunc) (Data object, const double x[], double dx[])) { try { autoVDSmagtMinimizer me = Thing_new (VDSmagtMinimizer); Minimizer_init (me.peek(), nParameters, object); my dp = NUMvector (1, nParameters); my pc = NUMvector (1, nParameters); my gc = NUMvector (1, nParameters); my g0 = NUMvector (1, nParameters); my s = NUMvector (1, nParameters); my srst = NUMvector (1, nParameters); my grst = NUMvector (1, nParameters); my func = func; my dfunc = dfunc; my lineSearchGradient = 0.9; my lineSearchMaxNumOfIterations = 5; return me.transfer(); } catch (MelderError) { Melder_throw ("VDSmagtMinimizer not created."); } } /************ class LineMinimizer *******************************/ void structLineMinimizer :: v_destroy () { NUMvector_free (ptry, 1); NUMvector_free (direction, 1); LineMinimizer_Parent :: v_destroy (); } Thing_implement (LineMinimizer, Minimizer, 0); void LineMinimizer_init (I, long nParameters, Data object, double (*func) (Data, const double [])) { iam (LineMinimizer); Minimizer_init (me, nParameters, object); my direction = NUMvector (1, nParameters); my ptry = NUMvector (1, nParameters); my func = func; my maxLineStep = 100; } /* End of file Minimizers.c 657*/ sources_5316/dwtools/Sound_to_Pitch2.cpp0000644000176700017670000002344711647026235017145 0ustar paulpaul/* Sound_to_Pitch2.c * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20021106 Latest modification djmw 20041124 Changed call to Sound_to_Spectrum. djmw 20070103 Sound interface changes */ #include "Sound_to_Pitch2.h" #include "Pitch_extensions.h" #include "Sound_and_Spectrum.h" #include "Sound_to_SPINET.h" #include "SPINET_to_Pitch.h" #include "NUM2.h" static int spec_enhance_SHS (double a[], long n) { if (n < 2) { return 0; } autoNUMvector posmax (1, (n + 1) / 2); long nmax = 0; if (a[1] > a[2]) { posmax[++nmax] = 1; } for (long i = 2; i <= n - 1; i++) if (a[i] > a[i - 1] && a[i] >= a[i + 1]) { posmax[++nmax] = i; } if (a[n] > a[n - 1]) { posmax[++nmax] = n; } if (nmax == 1) { for (long j = 1; j <= posmax[1] - 3; j++) { a[j] = 0; } for (long j = posmax[1] + 3; j <= n; j++) { a[j] = 0; } } else { for (long i = 2; i <= nmax; i++) { for (long j = posmax[i - 1] + 3; j <= posmax[i] - 3; j++) { a[j] = 0; } } } return 1; } static void spec_smoooth_SHS (double a[], long n) { double ai, aim1 = 0; for (long i = 1; i <= n - 1; i++) { ai = a[i]; a[i] = (aim1 + 2 * ai + a[i + 1]) / 4; aim1 = ai; } } Pitch Sound_to_Pitch_shs (Sound me, double timeStep, double minimumPitch, double maximumFrequency, double ceiling, long maxnSubharmonics, long maxnCandidates, double compressionFactor, long nPointsPerOctave) { try { double firstTime, newSamplingFrequency = 2 * maximumFrequency; double windowDuration = 2 / minimumPitch, halfWindow = windowDuration / 2; double atans = nPointsPerOctave * NUMlog2 (65.0 / 50.0) - 1; // Number of speech samples in the downsampled signal in each frame: // 100 for windowDuration == 0.04 and newSamplingFrequency == 2500 long nx = floor (windowDuration * newSamplingFrequency + 0.5); // The minimum number of points for the fft is 256. long nfft = 1; while ( (nfft *= 2) < nx || nfft <= 128) { ; } long nfft2 = nfft / 2 + 1; double frameDuration = nfft / newSamplingFrequency; double df = newSamplingFrequency / nfft; // The number of points on the octave scale double fminl2 = NUMlog2 (minimumPitch), fmaxl2 = NUMlog2 (maximumFrequency); long nFrequencyPoints = (fmaxl2 - fminl2) * nPointsPerOctave; double dfl2 = (fmaxl2 - fminl2) / (nFrequencyPoints - 1); autoSound sound = Sound_resample (me, newSamplingFrequency, 50); long numberOfFrames; Sampled_shortTermAnalysis (sound.peek(), windowDuration, timeStep, &numberOfFrames, &firstTime); autoSound frame = Sound_createSimple (1, frameDuration, newSamplingFrequency); autoSound hamming = Sound_createHamming (nx / newSamplingFrequency, newSamplingFrequency); autoPitch thee = Pitch_create (my xmin, my xmax, numberOfFrames, timeStep, firstTime, ceiling, maxnCandidates); autoNUMvector cc (1, numberOfFrames); autoNUMvector specAmp (1, nfft2); autoNUMvector fl2 (1, nfft2); autoNUMvector yv2 (1, nfft2); autoNUMvector arctg (1, nFrequencyPoints); autoNUMvector al2 (1, nFrequencyPoints); Melder_assert (frame->nx >= nx); Melder_assert (hamming->nx == nx); // Compute the absolute value of the globally largest amplitude w.r.t. the global mean. double globalMean, globalPeak; Sound_localMean (sound.peek(), sound -> xmin, sound -> xmax, &globalMean); Sound_localPeak (sound.peek(), sound -> xmin, sound -> xmax, globalMean, &globalPeak); /* For the cubic spline interpolation we need the frequencies on an octave scale, i.e., a log2 scale. All frequencies must be DIFFERENT, otherwise the cubic spline interpolation will give corrupt results. Because log2(f==0) is not defined, we use the heuristic: f[2]-f[1] == f[3]-f[2]. */ for (long i = 2; i <= nfft2; i++) { fl2[i] = NUMlog2 ( (i - 1) * df); } fl2[1] = 2 * fl2[2] - fl2[3]; // Calculate frequencies regularly spaced on a log2-scale and // the frequency weighting function. for (long i = 1; i <= nFrequencyPoints; i++) { arctg[i] = 0.5 + atan (3 * (i - atans) / nPointsPerOctave) / NUMpi; } // Perform the analysis on all frames. for (long i = 1; i <= numberOfFrames; i++) { Pitch_Frame pitchFrame = &thy frame[i]; double hm = 1, f0, pitch_strength, localMean, localPeak; double tmid = Sampled_indexToX (thee.peek(), i); /* The center of this frame */ long nx_tmp = frame -> nx; // Copy a frame from the sound, apply a hamming window. Get local 'intensity' frame -> nx = nx; /*begin vies */ Sound_into_Sound (sound.peek(), frame.peek(), tmid - halfWindow); Sounds_multiply (frame.peek(), hamming.peek()); Sound_localMean (sound.peek(), tmid - 3 * halfWindow, tmid + 3 * halfWindow, &localMean); Sound_localPeak (sound.peek(), tmid - halfWindow, tmid + halfWindow, localMean, &localPeak); pitchFrame -> intensity = localPeak > globalPeak ? 1 : localPeak / globalPeak; frame -> nx = nx_tmp; /* einde vies */ // Get the Fourier spectrum. autoSpectrum spec = Sound_to_Spectrum (frame.peek(), 1); Melder_assert (spec->nx == nfft2); // From complex spectrum to amplitude spectrum. for (long j = 1; j <= nfft2; j++) { double rs = spec -> z[1][j], is = spec -> z[2][j]; specAmp[j] = sqrt (rs * rs + is * is); } // Enhance the peaks in the spectrum. spec_enhance_SHS (specAmp.peek(), nfft2); // Smooth the enhanced spectrum. spec_smoooth_SHS (specAmp.peek(), nfft2); // Go to a logarithmic scale and perform cubic spline interpolation to get // spectral values for the increased number of frequency points. NUMspline (fl2.peek(), specAmp.peek(), nfft2, 1e30, 1e30, yv2.peek()); for (long j = 1; j <= nFrequencyPoints; j++) { double f = fminl2 + (j - 1) * dfl2; NUMsplint (fl2.peek(), specAmp.peek(), yv2.peek(), nfft2, f, &al2[j]); } // Multiply by frequency selectivity of the auditory system. for (long j = 1; j <= nFrequencyPoints; j++) al2[j] = al2[j] > 0 ? al2[j] * arctg[j] : 0; // The subharmonic summation. Shift spectra in octaves and sum. Pitch_Frame_init (pitchFrame, maxnCandidates); autoNUMvector sumspec (1, nFrequencyPoints); pitchFrame -> nCandidates = 0; /* !!!!! */ for (long m = 1; m <= maxnSubharmonics + 1; m++) { long kb = 1 + floor (nPointsPerOctave * NUMlog2 (m)); for (long k = kb; k <= nFrequencyPoints; k++) { sumspec[k - kb + 1] += al2[k] * hm; } hm *= compressionFactor; } // First register the voiceless candidate (always present). Pitch_Frame_addPitch (pitchFrame, 0, 0, maxnCandidates); /* Get the best local estimates for the pitch as the maxima of the subharmonic sum spectrum by parabolic interpolation on three points: The formula for a parabole with a maximum is: y(x) = a - b (x - c)^2 with a, b, c >= 0 The three points are (-x, y1), (0, y2) and (x, y3). The solution for a (the maximum) and c (the position) is: a = (2 y1 (4 y2 + y3) - y1^2 - (y3 - 4 y2)^2)/( 8 (y1 - 2 y2 + y3) c = dx (y1 - y3) / (2 (y1 - 2 y2 + y3)) (b = (2 y2 - y1 - y3) / (2 dx^2) ) */ for (long k = 2; k <= nFrequencyPoints - 1; k++) { double y1 = sumspec[k - 1], y2 = sumspec[k], y3 = sumspec[k + 1]; if (y2 > y1 && y2 >= y3) { double denum = y1 - 2 * y2 + y3, tmp = y3 - 4 * y2; double x = dfl2 * (y1 - y3) / (2 * denum); double f = pow (2, fminl2 + (k - 1) * dfl2 + x); double strength = (2 * y1 * (4 * y2 + y3) - y1 * y1 - tmp * tmp) / (8 * denum); Pitch_Frame_addPitch (pitchFrame, f, strength, maxnCandidates); } } /* Check whether f0 corresponds to an actual periodicity T = 1 / f0: correlate two signal periods of duration T, one starting at the middle of the interval and one starting T seconds before. If there is periodicity the correlation coefficient should be high. However, some sounds do not show any regularity, or very low frequency and regularity, and nevertheless have a definite pitch, e.g. Shepard sounds. */ Pitch_Frame_getPitch (pitchFrame, &f0, &pitch_strength); if (f0 > 0) { cc[i] = Sound_correlateParts (sound.peek(), tmid - 1.0 / f0, tmid, 1.0 / f0); } } // Base V/UV decision on correlation coefficients. // Resize the pitch strengths w.r.t. the cc. double vuvCriterium = 0.52; for (long i = 1; i <= numberOfFrames; i++) { Pitch_Frame_resizeStrengths (& thy frame[i], cc[i], vuvCriterium); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Pitch (shs) created."); } } Pitch Sound_to_Pitch_SPINET (Sound me, double timeStep, double windowDuration, double minimumFrequencyHz, double maximumFrequencyHz, long nFilters, double ceiling, int maxnCandidates) { try { autoSPINET him = Sound_to_SPINET (me, timeStep, windowDuration, minimumFrequencyHz, maximumFrequencyHz, nFilters, 0.4, 0.6); autoPitch thee = SPINET_to_Pitch (him.peek(), 0.15, ceiling, maxnCandidates); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Pitch (SPINET) created."); } } /* End of file Sound_to_Pitch2.cpp */ sources_5316/dwtools/AffineTransform_def.h0000644000176700017670000000217611627171475017512 0ustar paulpaul/* AffineTransform_def.h * * Copyright (C) 1993-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT AffineTransform oo_DEFINE_CLASS (AffineTransform, Data) oo_LONG (n) oo_DOUBLE_VECTOR (t, n) oo_DOUBLE_MATRIX (r, n, n) #if oo_DECLARING // new methods: virtual void v_transform (double **in, long nrows, double **out); virtual Any v_invert (); #endif oo_END_CLASS(AffineTransform) #undef ooSTRUCT /* End of file AffineTransform_def.h */ sources_5316/dwtools/LongSound_extensions.cpp0000644000176700017670000002310411725102201020300 0ustar paulpaul/* LongSound_extensions.c * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020627 GPL header djmw 20030913 changed 'f' to 'file' as argument in Melder_checkSoundFile djmw 20060206 Set errno = 0: "An application that needs to examine the value of errno to determine the error should set it to 0 before a function call, then inspect it before a subsequent function call." djmw 20061213 MelderFile_truncate also works for MacOS X djmw 20061212 Header unistd.h for MacOS X added. djmw 20070129 Sounds may be multichannel djmw 20071030 MelderFile->wpath to MelderFile->path */ #include "LongSound_extensions.h" #if defined (_WIN32) #include #elif defined(linux) #include #include #include #elif defined (macintosh) #include #endif #include "NUM2.h" #include /* Precondition: size (my buffer) >= nbuf */ static void _LongSound_to_multichannel_buffer (LongSound me, short *buffer, long nbuf, int nchannels, int ichannel, long ibuf) { long numberOfReads = (my nx - 1) / nbuf + 1; long n_to_read = 0; if (ibuf <= numberOfReads) { n_to_read = ibuf == numberOfReads ? (my nx - 1) % nbuf + 1 : nbuf; long imin = (ibuf - 1) * nbuf + 1; LongSound_readAudioToShort (me, my buffer, imin, n_to_read); therror for (long i = 1; i <= n_to_read; i++) { buffer[nchannels * (i - 1) + ichannel] = my buffer[i]; } } if (ibuf >= numberOfReads) { for (long i = n_to_read + 1; i <= nbuf; i++) { buffer[nchannels * (i - 1) + ichannel] = 0; } } } void LongSounds_writeToStereoAudioFile16 (LongSound me, LongSound thee, int audioFileType, MelderFile file) { try { long nbuf = my nmax < thy nmax ? my nmax : thy nmax; long nx = my nx > thy nx ? my nx : thy nx; long numberOfReads = (nx - 1) / nbuf + 1, numberOfBitsPerSamplePoint = 16; if (thy numberOfChannels != my numberOfChannels || my numberOfChannels != 1) { Melder_throw ("LongSounds must be mono."); } if (my sampleRate != thy sampleRate) { Melder_throw ("Sample rates must be equal."); } /* Allocate a stereo buffer of size (2 * the smallest)! WE SUPPOSE THAT SMALL IS LARGE ENOUGH. Read the same number of samples from both files, despite potential differences in internal buffer size. */ long nchannels = 2; autoNUMvector buffer (1, nchannels * nbuf); autoMelderFile f = MelderFile_create (file, Melder_macAudioFileType (audioFileType), L"PpgB", Melder_winAudioFileExtension (audioFileType)); MelderFile_writeAudioFileHeader (file, audioFileType, my sampleRate, nx, nchannels, numberOfBitsPerSamplePoint); therror for (long i = 1; i <= numberOfReads; i++) { long n_to_write = i == numberOfReads ? (nx - 1) % nbuf + 1 : nbuf; _LongSound_to_multichannel_buffer (me, buffer.peek(), nbuf, nchannels, 1, i); _LongSound_to_multichannel_buffer (thee, buffer.peek(), nbuf, nchannels, 2, i); MelderFile_writeShortToAudio (file, nchannels, Melder_defaultAudioFileEncoding (audioFileType, numberOfBitsPerSamplePoint), buffer.peek(), n_to_write); } MelderFile_writeAudioFileTrailer (file, audioFileType, my sampleRate, nx, nchannels, numberOfBitsPerSamplePoint); therror f.close (); } catch (MelderError) { Melder_throw (me, ": no stereo audio file created."); } } /* BSD systems provide ftruncate, several others supply chsize, and a few may provide a (possibly undocumented) fcntl option F_FREESP. Under MS-DOS, you can sometimes use write(fd, "", 0). However, there is no portable solution, nor a way to delete blocks at the beginning. */ static void MelderFile_truncate (MelderFile me, long size) { #if defined(_WIN32) HANDLE hFile; DWORD fdwAccess = GENERIC_READ | GENERIC_WRITE, fPos; DWORD fdwShareMode = 0; /* File cannot be shared */ LPSECURITY_ATTRIBUTES lpsa = NULL; DWORD fdwCreate = OPEN_EXISTING; LARGE_INTEGER fileSize; MelderFile_close (me); hFile = CreateFileW (my path, fdwAccess, fdwShareMode, lpsa, fdwCreate, FILE_ATTRIBUTE_NORMAL, NULL); if (hFile == INVALID_HANDLE_VALUE) { Melder_throw ("Can't open file ", MelderFile_messageName (me), "."); } // Set current file pointer to position 'size' fileSize.LowPart = size; fileSize.HighPart = 0; /* Limit the file size to 2^32 - 2 bytes */ fPos = SetFilePointer (hFile, fileSize.LowPart, &fileSize.HighPart, FILE_BEGIN); if (fPos == 0xFFFFFFFF) { Melder_throw ("Can't set the position at size ", size, "for file ", MelderFile_messageName (me), "."); } // Limit the file size as the current position of the file pointer. SetEndOfFile (hFile); CloseHandle (hFile); #elif defined(linux) || defined(macintosh) MelderFile_close (me); if (truncate (Melder_peekWcsToUtf8 (my path), size) == -1) Melder_throw ("Truncating failed for file ", MelderFile_messageName (me), " (", Melder_peekUtf8ToWcs (strerror (errno)), ")."); #else Melder_throw ("Don't know what to do."); #endif } static void writePartToOpenFile16 (LongSound me, int audioFileType, long imin, long n, MelderFile file) { long offset = imin; long numberOfBuffers = (n - 1) / my nmax + 1, numberOfBitsPerSamplePoint = 16; long numberOfSamplesInLastBuffer = (n - 1) % my nmax + 1; if (file -> filePointer) { for (long ibuffer = 1; ibuffer <= numberOfBuffers; ibuffer ++) { long numberOfSamplesToCopy = ibuffer < numberOfBuffers ? my nmax : numberOfSamplesInLastBuffer; LongSound_readAudioToShort (me, my buffer, offset, numberOfSamplesToCopy); offset += numberOfSamplesToCopy; MelderFile_writeShortToAudio (file, my numberOfChannels, Melder_defaultAudioFileEncoding (audioFileType, numberOfBitsPerSamplePoint), my buffer, numberOfSamplesToCopy); } } /* * We "have" no samples any longer. */ my imin = 1; my imax = 0; } void LongSounds_appendToExistingSoundFile (Collection me, MelderFile file) { long pre_append_endpos = 0, numberOfBitsPerSamplePoint = 16; try { if (my size < 1) { Melder_throw ("No Sound or LongSound objects to append."); } /* We have to open with "r+" mode because this will position the stream at the beginning of the file. The "a" mode does not allow us to seek before the end-of-file. For Linux: If the file is already opened (e.g. by a LongSound) object we should deny access! Under Windows deny access is default?! */ autofile f = Melder_fopen (file, "r+b"); file -> filePointer = f; // essential !! double sampleRate_d; long startOfData, numberOfSamples; int numberOfChannels, encoding; int audioFileType = MelderFile_checkSoundFile (file, &numberOfChannels, &encoding, &sampleRate_d, &startOfData, &numberOfSamples); if (audioFileType == 0) { Melder_throw ("Not a sound file."); } // Check whether all the sample rates and channels match. long sampleRate = sampleRate_d; for (long i = 1; i <= my size; i++) { int sampleRatesMatch, numbersOfChannelsMatch; Sampled data = (Sampled) my item [i]; if (data -> classInfo == classSound) { Sound sound = (Sound) data; sampleRatesMatch = floor (1.0 / sound -> dx + 0.5) == sampleRate; numbersOfChannelsMatch = sound -> ny == numberOfChannels; numberOfSamples += sound -> nx; } else { LongSound longSound = (LongSound) data; sampleRatesMatch = longSound -> sampleRate == sampleRate; numbersOfChannelsMatch = longSound -> numberOfChannels == numberOfChannels; numberOfSamples += longSound -> nx; } if (! sampleRatesMatch) { Melder_throw ("Sample rates do not match."); } if (! numbersOfChannelsMatch) { Melder_throw ("Cannot mix stereo and mono."); } } // Search the end of the file, count the number of bytes and append. MelderFile_seek (file, 0, SEEK_END); therror pre_append_endpos = MelderFile_tell (file); therror errno = 0; for (long i = 1; i <= my size; i++) { Sampled data = (Sampled) my item [i]; if (data -> classInfo == classSound) { Sound sound = (Sound) data; MelderFile_writeFloatToAudio (file, sound -> ny, Melder_defaultAudioFileEncoding (audioFileType, numberOfBitsPerSamplePoint), sound -> z, sound -> nx, true); } else { LongSound longSound = (LongSound) data; writePartToOpenFile16 (longSound, audioFileType, 1, longSound -> nx, file); } if (errno != 0) { Melder_throw ("Error during writing."); } } // Update header MelderFile_rewind (file); MelderFile_writeAudioFileHeader (file, audioFileType, sampleRate, numberOfSamples, numberOfChannels, numberOfBitsPerSamplePoint); therror MelderFile_writeAudioFileTrailer (file, audioFileType, sampleRate, numberOfSamples, numberOfChannels, numberOfBitsPerSamplePoint); f.close (file); return; } catch (MelderError) { if (errno != 0 && pre_append_endpos > 0) { // Restore file at original size int error = errno; MelderFile_truncate (file, pre_append_endpos); Melder_throw ("File ", MelderFile_messageName (file), L" restored to original size (", strerror (error), ")."); } throw; } } /* End of file LongSound_extensions.cpp */ sources_5316/dwtools/DTW_and_TextGrid.h0000644000176700017670000000257211734654527016705 0ustar paulpaul#ifndef _DTW_and_TextGrid_h_ #define _DTW_and_TextGrid_h_ /* DTW_and_TextGrid.h * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20060906 djmw 20120328 Latest modification */ #include "DTW.h" #include "TextGrid.h" #include "Table.h" TextTier DTW_and_TextTier_to_TextTier (DTW me, TextTier thee, double precision); IntervalTier DTW_and_IntervalTier_to_IntervalTier (DTW me, IntervalTier thee, double precision); TextGrid DTW_and_TextGrid_to_TextGrid (DTW me, TextGrid thee, double precision); /* Purpose: Create the new TextGrid with all times determined by the DTW. */ Table DTW_and_IntervalTier_to_Table (DTW me, IntervalTier thee, double precision); #endif /* _DTW_and_TextGrid_h_ */ sources_5316/dwtools/SPINET.h0000644000176700017670000000303611627252056014601 0ustar paulpaul#ifndef _SPINET_h_ #define _SPINET_h_ /* SPINET.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19970408 djmw 20020813 GPL header djmw 20110306 Latest modification. */ #include "Sampled2.h" #include "Graphics.h" #include "SPINET_def.h" oo_CLASS_CREATE (SPINET, Sampled2); SPINET SPINET_create (double tmin, double tmax, long nt, double dt, double t1, double minimumFrequency, double maximumFrequency, long nFilters, double excitationErbProportion, double inhibitionErbProportion); void SPINET_spectralRepresentation (SPINET me, Graphics g, double fromTime, double toTime, double fromErb, double toErb, double minimum, double maximum, int enhanced, int garnish); void SPINET_drawSpectrum (SPINET me, Graphics g, double time, double fromErb, double toErb, double minimum, double maximum, int enhanced, int garnish); #endif /* _SPINET_h_ */ sources_5316/dwtools/SPINET.cpp0000644000176700017670000001227411725110527015133 0ustar paulpaul/* SPINET.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20061212 Changed info to Melder_writeLine format. djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20080122 float -> double djmw 20110304 Thing_new */ #include "SPINET.h" #include "Sound_extensions.h" #include "NUM2.h" #include "oo_DESTROY.h" #include "SPINET_def.h" #include "oo_COPY.h" #include "SPINET_def.h" #include "oo_EQUAL.h" #include "SPINET_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "SPINET_def.h" #include "oo_WRITE_TEXT.h" #include "SPINET_def.h" #include "oo_WRITE_BINARY.h" #include "SPINET_def.h" #include "oo_READ_TEXT.h" #include "SPINET_def.h" #include "oo_READ_BINARY.h" #include "SPINET_def.h" #include "oo_DESCRIPTION.h" #include "SPINET_def.h" Thing_implement (SPINET, Sampled2, 0); void structSPINET :: v_info () { structData :: v_info (); double miny, maxy, mins, maxs; if (! Sampled2_getWindowExtrema_d (this, y, 1, nx, 1, ny, & miny, & maxy) || ! Sampled2_getWindowExtrema_d (this, s, 1, nx, 1, ny, & mins, & maxs)) { return; } MelderInfo_writeLine2 (L"Minimum power: ", Melder_double (miny)); MelderInfo_writeLine2 (L"Maximum power: ", Melder_double (maxy)); MelderInfo_writeLine2 (L"Minimum power rectified: ", Melder_double (mins)); MelderInfo_writeLine2 (L"Maximum powerrectified: ", Melder_double (maxs)); } SPINET SPINET_create (double tmin, double tmax, long nt, double dt, double t1, double minimumFrequency, double maximumFrequency, long nFilters, double excitationErbProportion, double inhibitionErbProportion) { try { autoSPINET me = Thing_new (SPINET); double minErb = NUMhertzToErb (minimumFrequency); double maxErb = NUMhertzToErb (maximumFrequency); double dErb = (maxErb - minErb) / nFilters; Sampled2_init (me.peek(), tmin, tmax, nt, dt, t1, minErb - dErb / 2, maxErb + dErb / 2, nFilters, dErb, minErb); my y = NUMmatrix (1, nFilters, 1, nt); my s = NUMmatrix (1, nFilters, 1, nt); my gamma = 4; my excitationErbProportion = excitationErbProportion; my inhibitionErbProportion = inhibitionErbProportion; return me.transfer(); } catch (MelderError) { Melder_throw ("SPINET not created."); } } void SPINET_spectralRepresentation (SPINET me, Graphics g, double fromTime, double toTime, double fromErb, double toErb, double minimum, double maximum, int enhanced, int garnish) { double **z = enhanced ? my s : my y; autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); for (long j = 1; j <= my ny; j++) { for (long i = 1; i <= my nx; i++) { thy z[j][i] = z[j][i]; } } Matrix_paintCells (thee.peek(), g, fromTime, toTime, fromErb, toErb, minimum, maximum); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Time (s)"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_textLeft (g, 1, L"Frequency (ERB)"); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_textTop (g, 0, enhanced ? L"Cooperative interaction output" : L"Gammatone filterbank output"); } } void SPINET_drawSpectrum (SPINET me, Graphics g, double time, double fromErb, double toErb, double minimum, double maximum, int enhanced, int garnish) { long ifmin, ifmax, icol = Sampled2_xToColumn (me, time); double **z = enhanced ? my s : my y; if (icol < 1 || icol > my nx) { return; } if (toErb <= fromErb) { fromErb = my ymin; toErb = my ymax; } Sampled2_getWindowSamplesY (me, fromErb, toErb, &ifmin, &ifmax); autoNUMvector spec (1, my ny); for (long i = 1; i <= my ny; i++) { spec[i] = z[i][icol]; } if (maximum <= minimum) { NUMvector_extrema (spec.peek(), ifmin, ifmax, &minimum, &maximum); } if (maximum <= minimum) { minimum -= 1; maximum += 1; } for (long i = ifmin; i <= ifmax; i++) { if (spec[i] > maximum) { spec[i] = maximum; } else if (spec[i] < minimum) { spec[i] = minimum; } } Graphics_setInner (g); Graphics_setWindow (g, fromErb, toErb, minimum, maximum); Graphics_function (g, spec.peek(), ifmin, ifmax, Sampled2_rowToY (me, ifmin), Sampled2_rowToY (me, ifmax)); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Frequency (ERB)"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_textLeft (g, 1, L"strength"); Graphics_marksLeft (g, 2, 1, 1, 0); } } /* End of file SPINET.cpp */ sources_5316/dwtools/MFCC_def.h0000664000176700017670000000202307756124210015120 0ustar paulpaul/* MFCC_def.h * * Copyright (C) 1993-2002 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header */ #define ooSTRUCT MFCC oo_DEFINE_CLASS (MFCC, Sampled) oo_DOUBLE (maximumFrequency_mel) /* from Sound */ oo_INT (nCoefficients) oo_FLOAT_MATRIX (z, my nCoefficients, my nx) oo_END_CLASS (MFCC) #undef ooSTRUCT /* End of file MFCC_def.h */ sources_5316/dwtools/EditDistanceTable.cpp0000664000176700017670000005335311756754232017461 0ustar paulpaul/* EditDistanceTable.c * * Copyright (C) 2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20120407 First implementation */ #include "EditDistanceTable.h" #include "oo_DESTROY.h" #include "EditDistanceTable_def.h" #include "oo_COPY.h" #include "EditDistanceTable_def.h" #include "oo_EQUAL.h" #include "EditDistanceTable_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "EditDistanceTable_def.h" #include "oo_WRITE_TEXT.h" #include "EditDistanceTable_def.h" #include "oo_WRITE_BINARY.h" #include "EditDistanceTable_def.h" #include "oo_READ_TEXT.h" #include "EditDistanceTable_def.h" #include "oo_READ_BINARY.h" #include "EditDistanceTable_def.h" #include "oo_DESCRIPTION.h" #include "EditDistanceTable_def.h" // prototypes EditCostsTable EditCostsTable_createDefault (); /* The insertion, deletion and substitution costs are specified in a TableOfReal * 1..n-2 target symbols/alphabet * 1..m-2 source symbols/alphabet * row n-1 and col m-1 specify nomatch symbols * cells [n][1..m-2] specify insertion costs * cells [1..n-1][m] specify deletion costs * cell [n-1][m-1] if nomatch target == nomatch source * cell [n][m] if nomatch target != nomatch source */ Thing_implement (WarpingPath, Data, 0); WarpingPath WarpingPath_create (long length) { try { autoWarpingPath me = Thing_new (WarpingPath); my d_path = NUMvector (1, length); my _capacity = my d_pathLength = length; return me.transfer(); } catch (MelderError) { Melder_throw ("WarpPath not created."); } } static void WarpingPath_reset (WarpingPath me) { for (long i = 1; i <= my _capacity; i++) { my d_path[i].x = my d_path[i].y = 0; } my d_pathLength = my _capacity; } static void WarpingPath_getPath (WarpingPath me, short **psi, long iy, long ix) { // psi[0..nrows-1][0..ncols-1] long index = my d_pathLength; my d_path[index].x = ix; my d_path[index].y = iy; while (!(ix == 0 && iy == 0)) { if (psi[iy][ix] == WARPING_fromLeft) { ix--; } else if (psi[iy][ix] == WARPING_fromBelow) { iy--; } else { // WARPING_fromDiag ix--; iy--; } my d_path[--index].x = ix; my d_path[index].y = iy; } if (index > 1) { long k = 1; for (long i = index; i <= my d_pathLength; i++) { my d_path[k++] = my d_path[i]; my d_path[i].x = my d_path[i].y = 0; } my d_pathLength = k - 1; } } static void WarpingPath_shiftPathByOne (WarpingPath me) { for (long i = 1; i <= my d_pathLength; i++) { (my d_path[i].x)++; (my d_path[i].y)++; } } long WarpingPath_getColumnsFromRowIndex (WarpingPath me, long iy, long *ix1, long *ix2) { if (iy <= 0) { return 0; } *ix1 = 0; *ix2 = 0; for (long i = 1; i <= my d_pathLength; i++) { if (my d_path[i].y < iy) { continue; } else if (my d_path[i].y == iy) { if (*ix1 == 0) *ix1 = my d_path[i].x; *ix2 = my d_path[i].x; } else { break; } } return *ix2 - *ix1 + 1; } long WarpingPath_getRowsFromColumnIndex (WarpingPath me, long ix, long *iy1, long *iy2) { if (ix <= 0) { return 0; } *iy1 = 0; *iy2 = 0; for (long i = 1; i <= my d_pathLength; i++) { if (my d_path[i].x < ix) { continue; } else if (my d_path[i].x == ix) { if (*iy1 == 0) *iy1 = my d_path[i].y; *iy2 = my d_path[i].y; } else { break; } } return *iy2 - *iy1 + 1; } Thing_implement (EditCostsTable, TableOfReal, 0); void structEditCostsTable :: v_info () { EditDistanceTable_Parent :: v_info (); MelderInfo_writeLine3 (L"Target:", Melder_integer (numberOfRows - 2), L" symbols."); MelderInfo_writeLine3 (L"Source:", Melder_integer (numberOfColumns - 2), L" symbols."); } bool structEditCostsTable :: v_matchTargetSymbol (const wchar_t *targetSymbol, const wchar_t *symbol) { return Melder_wcsequ (targetSymbol, symbol); } bool structEditCostsTable :: v_matchSourceSymbol (const wchar_t *sourceSymbol, const wchar_t *symbol) { return Melder_wcsequ (sourceSymbol, symbol); } bool structEditCostsTable :: v_matchTargetWithSourceSymbol (const wchar_t *targetSymbol, const wchar_t *sourceSymbol) { return Melder_wcsequ (targetSymbol, sourceSymbol); } EditCostsTable EditCostsTable_create (long targetAlphabetSize, long sourceAlphabetSize) { try{ autoEditCostsTable me = Thing_new (EditCostsTable); TableOfReal_init (me.peek(), targetAlphabetSize + 2, sourceAlphabetSize + 2); return me.transfer(); } catch (MelderError) { Melder_throw ("EditCostsTable not created."); } } EditCostsTable EditCostsTable_createDefault () { try { autoEditCostsTable me = EditCostsTable_create (0, 0); my data[1][1] = 0; // default substitution cost (nomatch == nomatch) my data[2][2] = 2; // default substitution cost (nomatch != nomatch) my data[2][1] = 1; // default insertion cost my data[1][2] = 1; // default deletion cost return me.transfer(); } catch (MelderError) { Melder_throw ("Default EditCostsTable not created."); } } void EditCostsTable_setDefaultCosts (EditCostsTable me, double insertionCosts, double deletionCosts, double substitutionCosts) { my data[my numberOfRows - 1][my numberOfColumns - 1] = 0; my data[my numberOfRows][my numberOfColumns] = substitutionCosts; my data[my numberOfRows][my numberOfColumns - 1] = deletionCosts; my data[my numberOfRows - 1][my numberOfColumns] = insertionCosts; } long EditCostsTable_getTargetIndex (EditCostsTable me, const wchar_t *symbol) { for (long i = 1; i <= my numberOfRows - 2; i++) { if (my v_matchTargetSymbol (my rowLabels[i], symbol)) { return i; } } return 0; } long EditCostsTable_getSourceIndex (EditCostsTable me, const wchar_t *symbol) { for (long j = 1; j <= my numberOfColumns - 2; j++) { if (my v_matchSourceSymbol (my columnLabels[j], symbol)) { return j; } } return 0; } void EditCostsTable_setInsertionCosts (EditCostsTable me, wchar_t *targets, double cost) { for (wchar_t *token = Melder_firstToken (targets); token != 0; token = Melder_nextToken ()) { long irow = EditCostsTable_getTargetIndex (me, token); irow = irow > 0 ? irow : my numberOfRows - 1; // nomatch condition to penultimate row my data[irow][my numberOfColumns] = cost; } } void EditCostsTable_setDeletionCosts (EditCostsTable me, wchar_t *sources, double cost) { for (wchar_t *token = Melder_firstToken (sources); token != 0; token = Melder_nextToken ()) { long icol = EditCostsTable_getSourceIndex (me, token); icol = icol > 0 ? icol : my numberOfColumns - 1; // nomatch condition to penultimate column my data[my numberOfRows][icol] = cost; } } void EditCostsTable_setOthersCosts (EditCostsTable me, double insertionCost, double deletionCost, double substitutionCost_equal, double substitutionCost_unequal) { my data[my numberOfRows - 1][my numberOfColumns] = insertionCost; my data[my numberOfRows][my numberOfColumns - 1] = deletionCost; my data[my numberOfRows - 1][my numberOfColumns - 1] = substitutionCost_equal; my data[my numberOfRows][my numberOfColumns] = substitutionCost_unequal; } double EditCostsTable_getOthersCost (EditCostsTable me, int costType) { return costType == 1 ? my data[my numberOfRows - 1][my numberOfColumns] : //insertion costType == 2 ? my data[my numberOfRows][my numberOfColumns - 1] : // deletion costType == 3 ? my data[my numberOfRows - 1][my numberOfColumns - 1] : // equality my data[my numberOfRows][my numberOfColumns]; // inequality } void EditCostsTable_setSubstitutionCosts (EditCostsTable me, wchar_t *targets, wchar_t *sources, double cost) { try { autoNUMvector targetIndex (1, my numberOfRows); autoNUMvector sourceIndex (1, my numberOfRows); long ntargets = 0; for (wchar_t *token = Melder_firstToken (targets); token != 0; token = Melder_nextToken ()) { long index = EditCostsTable_getTargetIndex (me, token); if (index > 0) { targetIndex[++ntargets] = index; } } if (ntargets == 0 && targets != 0 && targets[1] != '\0') { ntargets = 1; targetIndex[1] = my numberOfRows - 1; } long nsources = 0; for (wchar_t *token = Melder_firstToken (sources); token != 0; token = Melder_nextToken ()) { long index = EditCostsTable_getSourceIndex (me, token); if (index > 0) { sourceIndex[++nsources] = index; } } if (nsources == 0 && sources != 0 && sources[1] != '\0') { nsources = 1; sourceIndex[1] = my numberOfColumns - 1; } for (long i = 1; i <= ntargets; i++) { long irow = targetIndex[i]; for (long j = 1; j <= nsources; j++) { my data [irow][sourceIndex[j]] = cost; } } } catch (MelderError) { Melder_throw (me, ": substitution costs not set."); } } double EditCostsTable_getInsertionCost (EditCostsTable me, const wchar_t *symbol) { long irow = EditCostsTable_getTargetIndex (me, symbol); irow = irow == 0 ? my numberOfRows - 1 : irow; // others is penultimate row return my data[irow][my numberOfColumns]; } double EditCostsTable_getDeletionCost (EditCostsTable me, const wchar_t *sourceSymbol) { long icol = EditCostsTable_getSourceIndex (me, sourceSymbol); icol = icol == 0 ? my numberOfColumns - 1 : icol; // others is penultimate column return my data[my numberOfRows][icol]; } double EditCostsTable_getSubstitutionCost (EditCostsTable me, const wchar_t *symbol, const wchar *replacement) { long irow = EditCostsTable_getTargetIndex (me, symbol); long icol = EditCostsTable_getSourceIndex (me, replacement); if (irow == 0 && icol == 0) { // nomatch irow = my numberOfRows; icol = my numberOfColumns; if (my v_matchTargetWithSourceSymbol (symbol, replacement)) { --irow; --icol; } } else { irow = irow == 0 ? my numberOfRows - 1 : irow; icol = icol == 0 ? my numberOfColumns - 1 : icol; } return my data[irow][icol]; } TableOfReal EditCostsTable_to_TableOfReal (EditCostsTable me) { try { autoTableOfReal thee = TableOfReal_create (my numberOfRows, my numberOfColumns); for (long j = 1; j <= my numberOfColumns; j++) { thy columnLabels[j] = Melder_wcsdup (my columnLabels[j]); } for (long i = 1; i <= my numberOfRows; i++) { thy rowLabels[i] = Melder_wcsdup (my rowLabels[i]); } NUMmatrix_copyElements (my data, thy data, 1, my numberOfRows, 1, my numberOfColumns); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to TableOfReal."); } } Thing_implement (EditDistanceTable, TableOfReal, 0); void structEditDistanceTable :: v_info () { EditDistanceTable_Parent :: v_info (); MelderInfo_writeLine3 (L"Target:", Melder_integer (numberOfRows), L" symbols."); MelderInfo_writeLine3 (L"Source:", Melder_integer (numberOfColumns), L" symbols."); } EditDistanceTable EditDistanceTable_create (Strings target, Strings source) { try { autoEditDistanceTable me = Thing_new (EditDistanceTable); long nsources = source -> numberOfStrings, ntargets = target -> numberOfStrings; TableOfReal_init (me.peek(), ntargets + 1, nsources + 1); TableOfReal_setColumnLabel (me.peek(), 1, L""); for (long j = 1; j <= nsources; j++) { my columnLabels[j + 1] = Melder_wcsdup (source -> strings[j]); } TableOfReal_setRowLabel (me.peek(), 1, L""); for (long i = 1; i <= ntargets; i++) { my rowLabels[i + 1] = Melder_wcsdup (target -> strings[i]); } my d_warpingPath = WarpingPath_create (ntargets + nsources + 1); my d_editCostsTable = EditCostsTable_createDefault (); EditDistanceTable_findPath (me.peek(), 0); return me.transfer(); } catch (MelderError) { Melder_throw ("EditDistanceTable not created."); } } void EditDistanceTable_setEditCosts (EditDistanceTable me, EditCostsTable thee) { try { forget (my d_editCostsTable); autoEditCostsTable ect = (EditCostsTable) Data_copy (thee); my d_editCostsTable = ect.transfer(); } catch (MelderError) { Melder_throw (me, ": edit costs not set."); } } EditDistanceTable EditDistanceTable_createFromCharacterStrings (const wchar_t *chars1, const wchar_t *chars2) { try { autoStrings s1 = Strings_createAsCharacters (chars1); autoStrings s2 = Strings_createAsCharacters (chars2); autoEditDistanceTable me = EditDistanceTable_create (s1.peek(), s2.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("EditDistanceTable not created from character strings."); } } static void NUMrationalize (double x, long *numerator, long *denominator) { double epsilon = 1e-6; *numerator = 1; for (*denominator = 1; *denominator <= 100000; (*denominator) ++) { double numerator_d = x * *denominator, rounded = floor (numerator_d + 0.5); if (fabs (rounded - numerator_d) < epsilon) { *numerator = rounded; return; } } *denominator = 0; /* Failure. */ } static void fixRows (TableOfReal me, long *rowmin, long *rowmax) { if (*rowmax < *rowmin) { *rowmin = 1; *rowmax = my numberOfRows; } else if (*rowmin < 1) *rowmin = 1; else if (*rowmax > my numberOfRows) *rowmax = my numberOfRows; } static void print4 (wchar_t *buffer, double value, int iformat, int width, int precision) { wchar_t formatString [40]; if (value == NUMundefined) wcscpy (buffer, L"undefined"); else if (iformat == 4) { long numerator, denominator; NUMrationalize (value, & numerator, & denominator); if (numerator == 0) swprintf (buffer, 40, L"0"); else if (denominator > 1) swprintf (buffer, 40, L"%ld/%ld", numerator, denominator); else swprintf (buffer, 40, L"%.7g", value); } else { swprintf (formatString, 40, L"%%%d.%d%c", width, precision, iformat == 1 ? 'f' : iformat == 2 ? 'e' : 'g'); swprintf (buffer, 40, formatString, value); } } static double getMaxRowLabelWidth (TableOfReal me, Graphics graphics, long rowmin, long rowmax) { double maxWidth = 0.0; if (! my rowLabels) return 0.0; fixRows (me, & rowmin, & rowmax); for (long irow = rowmin; irow <= rowmax; irow ++) if (my rowLabels [irow] && my rowLabels [irow] [0]) { double textWidth = Graphics_textWidth_ps (graphics, my rowLabels [irow], TRUE); /* SILIPA is bigger than XIPA */ if (textWidth > maxWidth) maxWidth = textWidth; } return maxWidth; } static double getLeftMargin (Graphics graphics) { return Graphics_dxMMtoWC (graphics, 1); } static double getLineSpacing (Graphics graphics) { return Graphics_dyMMtoWC (graphics, 1.5 * Graphics_inqFontSize (graphics) * 25.4 / 72); } void EditDistanceTable_draw (EditDistanceTable me, Graphics graphics, int iformat, int precision, double angle) { long rowmin = 1, rowmax = my numberOfRows; Graphics_setInner (graphics); Graphics_setWindow (graphics, 0.5, my numberOfColumns + 0.5, 0, 1); double leftMargin = getLeftMargin (graphics); // not earlier! double lineSpacing = getLineSpacing (graphics); // not earlier! double maxTextWidth = getMaxRowLabelWidth (me, graphics, rowmin, rowmax); double y = 1 + 0.1 * lineSpacing; autoNUMmatrix onPath (1, my numberOfRows, 1, my numberOfColumns); for (long i = 1; i <= my d_warpingPath -> d_pathLength; i++) { structPairOfInteger poi = my d_warpingPath -> d_path[i]; onPath[poi.y] [poi.x] = true; } for (long irow = my numberOfRows; irow > 0; irow --) { Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); if (my rowLabels && my rowLabels [irow] && my rowLabels [irow] [0]) Graphics_text (graphics, 0.5 - leftMargin, y, my rowLabels [irow]); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_HALF); for (long icol = 1; icol <= my numberOfColumns; icol ++) { wchar_t text [40]; print4 (text, my data [irow] [icol], iformat, 0, precision); Graphics_setBold (graphics, onPath[irow][icol]); Graphics_text (graphics, icol, y, text); if (onPath[irow][icol]) { Graphics_rectangle (graphics, icol-0.5, icol+0.5, y - 0.5*lineSpacing, y + 0.5*lineSpacing); } } y -= lineSpacing; Graphics_setBold (graphics, false); } double left = 0.5; if (maxTextWidth > 0.0) left -= maxTextWidth + 2 * leftMargin; Graphics_line (graphics, left, y, my numberOfColumns + 0.5, y); Graphics_setTextRotation (graphics, angle); if (angle < 0) { y -= 0.3*lineSpacing; Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_HALF); } else if (angle > 0) { Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); y -= 0.3*lineSpacing; } else { Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_TOP); } for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (my columnLabels && my columnLabels [icol] && my columnLabels [icol] [0]) Graphics_text (graphics, icol, y, my columnLabels [icol]); } Graphics_setTextRotation (graphics, 0); y -= lineSpacing; Graphics_line (graphics, 0.5, y, 0.5, 1 + 0.5 * lineSpacing); Graphics_unsetInner (graphics); } void EditDistanceTable_drawEditOperations (EditDistanceTable me, Graphics graphics) { const wchar_t *oinsertion = L"i", *insertion = L"*", *odeletion = L"d", *deletion = L"*", *osubstitution = L"s", *oequal = L""; Graphics_setWindow (graphics, 0.5, my d_warpingPath -> d_pathLength - 0.5, 0, 1); // pathLength-1 symbols double lineSpacing = getLineSpacing (graphics); double ytarget = 1 - lineSpacing, ysource = ytarget - 2 * lineSpacing, yoper = ysource - lineSpacing; Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_BOTTOM); for (long i = 2; i <= my d_warpingPath -> d_pathLength; i++) { structPairOfInteger p = my d_warpingPath -> d_path[i], p1 = my d_warpingPath -> d_path[i - 1]; double x = i - 1; if (p.x == p1.x) { // insertion Graphics_text (graphics, x, ytarget, my rowLabels[p.y]); Graphics_text (graphics, x, ysource, deletion); Graphics_text (graphics, x, yoper, oinsertion); } else if (p.y == p1.y) { // deletion Graphics_text (graphics, x, ytarget, insertion); Graphics_text (graphics, x, ysource, my columnLabels[p.x]); Graphics_text (graphics, x, yoper, odeletion); } else { // substitution ? Graphics_text (graphics, x, ytarget, my rowLabels[p.y]); Graphics_text (graphics, x, ysource, my columnLabels[p.x]); Graphics_text (graphics, x, yoper, (Melder_wcsequ (my rowLabels[p.y], my columnLabels[p.x]) ? oequal : osubstitution)); } Graphics_line (graphics, x, ysource + lineSpacing, x, ytarget - 0.1 * lineSpacing); } } void EditDistanceTable_setDefaultCosts (EditDistanceTable me, double insertionCosts, double deletionCosts, double substitutionCosts) { EditCostsTable_setDefaultCosts (my d_editCostsTable, insertionCosts, deletionCosts, substitutionCosts); EditDistanceTable_findPath (me, 0); } TableOfReal EditDistanceTable_to_TableOfReal_directions (EditDistanceTable me) { TableOfReal tor; EditDistanceTable_findPath (me, &tor); return tor; } void EditDistanceTable_findPath (EditDistanceTable me, TableOfReal *directions) { try { /* What do we have to do to source to get target? * Origin [0][0] is at bottom-left corner * Target vertical, source horizontal * Going in the vertical direction is a deletion, horizontal is insertion, diagonal is substitution */ long numberOfSources = my numberOfColumns - 1, numberOfTargets = my numberOfRows - 1; autoNUMmatrix psi (0, numberOfTargets, 0, numberOfSources); autoNUMmatrix delta (0, numberOfTargets, 0, numberOfSources); for (long j = 1; j <= numberOfSources; j++) { delta[0][j] = delta[0][j - 1] + EditCostsTable_getDeletionCost (my d_editCostsTable, my columnLabels[j+1]); psi[0][j] = WARPING_fromLeft; } for (long i = 1; i <= numberOfTargets; i++) { delta[i][0] = delta[i - 1][0] + EditCostsTable_getInsertionCost (my d_editCostsTable, my rowLabels[i+1]); psi[i][0] = WARPING_fromBelow; } for (long j = 1; j <= numberOfSources; j++) { for (long i = 1; i <= numberOfTargets; i++) { // the substitution, deletion and insertion costs. double left = delta[i][j - 1] + EditCostsTable_getInsertionCost (my d_editCostsTable, my rowLabels[i+1]); double bottom = delta[i - 1][j] + EditCostsTable_getDeletionCost (my d_editCostsTable, my columnLabels[j+1]); double mindist = delta[i - 1][j - 1] + EditCostsTable_getSubstitutionCost (my d_editCostsTable, my rowLabels[i+1], my columnLabels[j+1]); // diag psi[i][j] = WARPING_fromDiag; if (bottom < mindist) { mindist = bottom; psi[i][j] = WARPING_fromBelow; } if (left < mindist) { mindist = left; psi[i][j] = WARPING_fromLeft; } delta[i][j] = mindist; } } // find minimum distance in last column long iy = numberOfTargets, ix = numberOfSources; WarpingPath_reset (my d_warpingPath); WarpingPath_getPath (my d_warpingPath, psi.peek(), iy, ix); WarpingPath_shiftPathByOne (my d_warpingPath); for (long i = 0; i <= numberOfTargets; i++) { for (long j = 0; j <= numberOfSources; j++) { my data[i+1][j+1] = delta[i][j]; } } if (directions != 0) { autoTableOfReal him = EditDistanceTable_to_TableOfReal (me); for (long i = 0; i <= numberOfTargets; i++) { for (long j = 0; j <= numberOfSources; j++) { his data[i+1][j+1] = psi[i][j]; } } *directions = him.transfer(); } } catch (MelderError) { Melder_throw (me, ": minimum path not found."); } } TableOfReal EditDistanceTable_to_TableOfReal (EditDistanceTable me) { try { autoTableOfReal thee = TableOfReal_create (my numberOfRows, my numberOfColumns); for (long j = 1; j <= my numberOfColumns; j++) { thy columnLabels[j] = Melder_wcsdup (my columnLabels[j]); } for (long i = 1; i <= my numberOfRows; i++) { thy rowLabels[i] = Melder_wcsdup (my rowLabels[i]); } NUMmatrix_copyElements (my data, thy data, 1, my numberOfRows, 1, my numberOfColumns); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no TableOfReal created."); } } /* End of file EditDistanceTable.cpp */ sources_5316/dwtools/Confusion.h0000644000176700017670000000730011627173415015541 0ustar paulpaul#ifndef _Confusion_h_ #define _Confusion_h_ /* Confusion.h * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "TableOfReal.h" #include "Categories.h" #include "Graphics.h" #include "Matrix.h" Thing_define (Confusion, TableOfReal) { // overridden methods: virtual void v_info (); }; /* A Confusion matrix has both row and column labels. */ Confusion Confusion_create (long numberOfStimuli, long numberOfResponses); Confusion Confusion_createSimple (const wchar *labels); Confusion Categories_to_Confusion (Categories me, Categories thee); void Confusion_increase (Confusion me, const wchar_t *stimulus, const wchar_t *response); /* data['stim']['resp'] += 1; */ double Confusion_getValue (Confusion me, const wchar_t *stim, const wchar_t *resp); /* data['stim']['resp'] ; */ void Confusion_getEntropies (Confusion me, double *h, double *hx, double *hy, double *hygx, double *hxgy, double *uygx, double *uxgy, double *uxy); /* x is column variable, y is row variable * *h entropy of whole table; * *hx entropy of x variable * *hy entropy of y variable * *hygx entropy of y given x * *hxgy entropy of x given y * *uygx dependency of y on x * *uxgy dependency of x on y * *uxy symmetrical dependency */ void Confusion_getFractionCorrect (Confusion me, double *fraction, long *numberOfCorrect); void Confusion_Matrix_draw (Confusion me, Matrix thee, Graphics g, long index, double lowerPercentage, double xmin, double xmax, double ymin, double ymax, int garnish); /* 1. Draw my rowLabels centered at ( matrix->z[i][1], matrix->z[i][2]). * 2. Draw arrows and circles according to: * for (i=1; i <= my numberOfRows; i++) * { * if (index != 0 && index != i) continue; * draw circle at i of width: my z[i][i]/rowSum; * for (j=1; j <= my numberOfColumns; j++) * { * if (i != j && 100*my data[i][j]/rowSum > lowerPercentage) * draw arrow from i to j of width: my data[i][j]/rowSum; * } * } */ Matrix Confusion_difference (Confusion me, Confusion thee); /* return matrix with the difference between the two confusion matrices */ long Confusion_getNumberOfEntries (Confusion me); Confusion Confusion_groupStimuli (Confusion me, const wchar_t *labels, const wchar_t *newLabel, long newpos); Confusion Confusion_groupResponses (Confusion me, const wchar_t *labels, const wchar_t *newLabel, long newpos); Confusion Confusion_group (Confusion me, const wchar_t *labels, const wchar_t *newLabel, long newpos); Confusion Confusion_condense (Confusion me, const wchar_t *search, const wchar_t *replace, long maximumNumberOfReplaces, int use_regexp); /* Group row and column labels according to search and replace. */ Confusion TableOfReal_to_Confusion (I); TableOfReal Confusion_to_TableOfReal_marginals (I); /* Create a table with one extra row and one extra column with marginals, i.e., column and row sums. */ void Confusion_drawAsNumbers (I, Graphics g, int marginals, int iformat, int precision); // option marginals draw one extra row and column with sums. #endif /* _Confusion_h_ */ sources_5316/dwtools/Eigen_and_Procrustes.h0000644000176700017670000000217211535130317017672 0ustar paulpaul#ifndef _Eigen_and_Procrustes_h_ #define _Eigen_and_Procrustes_h_ /* Eigen_and_Procrustes.h * Copyright (C) 2004-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * djmw 20041025 Initial version * djmw 20110307 Latest modification */ #include "Eigen.h" #include "Procrustes.h" #ifdef __cplusplus extern "C" { #endif Procrustes Eigens_to_Procrustes (I, thou, long evec_from, long evec_to); #ifdef __cplusplus } #endif #endif /* _Eigen_and_Procrustes_h_ */ sources_5316/dwtools/Pattern.cpp0000644000176700017670000000637511627244345015562 0ustar paulpaul/* Pattern.c * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20041203 Added _Pattern_checkElements. djmw 20071017 Melder_error

djmw 20110304 Thing_new */ #include "Pattern.h" Thing_implement (Pattern, Matrix, 2); int _Pattern_checkElements (Pattern me) { for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) { if (my z[i][j] < 0 || my z[i][j] > 1) { return 0; } } } return 1; } void Pattern_init (I, long ny, long nx) { iam (Pattern); my ny = ny; my nx = nx; Matrix_init (me, 1, nx, nx, 1, 1, 1, ny, ny, 1, 1); } Pattern Pattern_create (long ny, long nx) { try { autoPattern me = Thing_new (Pattern); Pattern_init (me.peek(), ny, nx); return me.transfer(); } catch (MelderError) { Melder_throw ("Pattern not created."); } } void Pattern_normalize (I, int choice, double pmin, double pmax) { iam (Pattern); if (pmin == pmax) { (void) Matrix_getWindowExtrema (me, 1, my nx, 1, my ny, & pmin, & pmax); } if (pmin == pmax) { return; } if (choice == 1) { for (long i = 1; i <= my ny; i++) { for (long j = 1; j <= my nx; j++) { my z[i][j] = (my z[i][j] - pmin) / (pmax - pmin); } } } else { /* default choice */ for (long i = 1; i <= my ny; i++) { double sum = 0; for (long j = 1; j <= my nx; j++) { sum += (my z[i][j] -= pmin); } for (long j = 1; j <= my nx; j++) { my z[i][j] *= 1.0 / sum; } } } } void Pattern_draw (I, Graphics g, long pattern, double xmin, double xmax, double ymin, double ymax, int garnish) { iam (Pattern); Matrix_drawRows (me, g, xmin, xmax, pattern - 0.5, pattern + 0.5, ymin, ymax); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } Pattern Matrix_to_Pattern (I, int join) { iam (Matrix); try { if (join < 1) { join = 1; } if ( (my ny % join) != 0) { Melder_throw (L"Number of rows is not a multiple of join factor."); } autoPattern thee = Pattern_create (my ny / join, join * my nx); long r = 0, c = 1; for (long i = 1; i <= my ny; i++) { if ( (i - 1) % join == 0) { r++; c = 1; } for (long j = 1; j <= my nx; j++) { thy z[r][c++] = my z[i][j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Pattern created."); } } Matrix Pattern_to_Matrix (Pattern me) { try { autoMatrix thee = Thing_new (Matrix); my structMatrix :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Matrix."); } } /* End of file Pattern.cpp */ sources_5316/dwtools/KlattGridEditors.h0000644000176700017670000003230111627241233017006 0ustar paulpaul#ifndef _KlattGridEditors_h_ #define _KlattGridEditors_h_ /* KlattGridEditors.h * * Copyright (C) 2009-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "KlattGrid.h" #include "PitchTier.h" #include "IntensityTier.h" #include "RealTierEditor.h" #include "FormantGridEditor.h" Thing_define (KlattGrid_realTierEditor, RealTierEditor) { // new data: public: KlattGrid klattgrid; // overridden methods: virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_play (double tmin, double tmax); }; void KlattGrid_realTierEditor_init (KlattGrid_realTierEditor me, GuiObject parent, const wchar_t *title, KlattGrid klattgrid, RealTier data); Thing_define (KlattGrid_openPhaseTierEditor, KlattGrid_realTierEditor) { // overridden methods: virtual double v_minimumLegalValue () { return 0.0; } virtual double v_maximumLegalValue () { return 1.0; } virtual const wchar * v_quantityText () { return L"Open phase (0..1)"; } virtual const wchar * v_quantityKey () { return L"Open phase"; } virtual const wchar * v_rightTickUnits () { return L""; } virtual double v_defaultYmin () { return 0.0; } virtual double v_defaultYmax () { return 1.0; } virtual const wchar * v_setRangeTitle () { return L"Set open phase range..."; } virtual const wchar * v_defaultYminText () { return L"0.0"; } virtual const wchar * v_defaultYmaxText () { return L"1.0"; } virtual const wchar * v_yminText () { return L"Minimum (0..1)"; } virtual const wchar * v_ymaxText () { return L"Maximum (0..1)"; } virtual const wchar * v_yminKey () { return L"Minimum"; } virtual const wchar * v_ymaxKey () { return L"Maximum"; } }; KlattGrid_openPhaseTierEditor KlattGrid_openPhaseTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_collisionPhaseTierEditor, KlattGrid_realTierEditor) { // overridden methods: virtual double v_minimumLegalValue () { return 0.0; } virtual double v_maximumLegalValue () { return 1.0; } virtual const wchar * v_quantityText () { return L"Collision phase (0..1)"; } virtual const wchar * v_quantityKey () { return L"Collision phase"; } virtual const wchar * v_rightTickUnits () { return L""; } virtual double v_defaultYmin () { return 0.0; } virtual double v_defaultYmax () { return 0.1; } virtual const wchar * v_setRangeTitle () { return L"Set collision phase range..."; } virtual const wchar * v_defaultYminText () { return L"0.0"; } virtual const wchar * v_defaultYmaxText () { return L"0.1"; } virtual const wchar * v_yminText () { return L"Minimum (0..1)"; } virtual const wchar * v_ymaxText () { return L"Maximum (0..1)"; } virtual const wchar * v_yminKey () { return L"Minimum"; } virtual const wchar * v_ymaxKey () { return L"Maximum"; } }; KlattGrid_collisionPhaseTierEditor KlattGrid_collisionPhaseTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_power1TierEditor, KlattGrid_realTierEditor) { // overridden methods: virtual double v_minimumLegalValue () { return 0.0; } virtual const wchar * v_quantityText () { return L"Power1"; } virtual const wchar * v_quantityKey () { return L"Power1"; } virtual const wchar * v_rightTickUnits () { return L""; } virtual double v_defaultYmin () { return 0.0; } virtual double v_defaultYmax () { return 4.0; } virtual const wchar * v_setRangeTitle () { return L"Set power1 range..."; } virtual const wchar * v_defaultYminText () { return L"0"; } virtual const wchar * v_defaultYmaxText () { return L"4"; } virtual const wchar * v_yminText () { return L"Minimum"; } virtual const wchar * v_ymaxText () { return L"Maximum"; } virtual const wchar * v_yminKey () { return L"Minimum"; } virtual const wchar * v_ymaxKey () { return L"Maximum"; } }; KlattGrid_power1TierEditor KlattGrid_power1TierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_power2TierEditor, KlattGrid_realTierEditor) { // overridden methods: virtual double v_minimumLegalValue () { return 0.0; } virtual const wchar * v_quantityText () { return L"Power2"; } virtual const wchar * v_quantityKey () { return L"Power2"; } virtual const wchar * v_rightTickUnits () { return L""; } virtual double v_defaultYmin () { return 0.0; } virtual double v_defaultYmax () { return 5.0; } virtual const wchar * v_setRangeTitle () { return L"Set power2 range..."; } virtual const wchar * v_defaultYminText () { return L"0"; } virtual const wchar * v_defaultYmaxText () { return L"5"; } virtual const wchar * v_yminText () { return L"Minimum"; } virtual const wchar * v_ymaxText () { return L"Maximum"; } virtual const wchar * v_yminKey () { return L"Minimum"; } virtual const wchar * v_ymaxKey () { return L"Maximum"; } }; KlattGrid_power2TierEditor KlattGrid_power2TierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_doublePulsingTierEditor, KlattGrid_realTierEditor) { // overridden methods: virtual double v_minimumLegalValue () { return 0.0; } virtual double v_maximumLegalValue () { return 1.0; } virtual const wchar * v_quantityText () { return L"Double pulsing (0..1)"; } virtual const wchar * v_quantityKey () { return L"Double pulsing"; } virtual const wchar * v_rightTickUnits () { return L""; } virtual double v_defaultYmin () { return 0.0; } virtual double v_defaultYmax () { return 1.0; } virtual const wchar * v_setRangeTitle () { return L"Set double pulsing range..."; } virtual const wchar * v_defaultYminText () { return L"0.0"; } virtual const wchar * v_defaultYmaxText () { return L"1.0"; } virtual const wchar * v_yminText () { return L"Minimum (0..1)"; } virtual const wchar * v_ymaxText () { return L"Maximum (0..1)"; } virtual const wchar * v_yminKey () { return L"Minimum"; } virtual const wchar * v_ymaxKey () { return L"Maximum"; } }; KlattGrid_doublePulsingTierEditor KlattGrid_doublePulsingTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_pitchTierEditor, KlattGrid_realTierEditor) { // overridden methods: void v_createHelpMenuItems (EditorMenu menu); virtual double v_minimumLegalValue () { return 0.0; } virtual const wchar * v_quantityText () { return L"Frequency (Hz)"; } virtual const wchar * v_quantityKey () { return L"Frequency"; } virtual const wchar * v_rightTickUnits () { return L" Hz"; } virtual double v_defaultYmin () { return 50.0; } virtual double v_defaultYmax () { return 600.0; } virtual const wchar * v_setRangeTitle () { return L"Set frequency range..."; } virtual const wchar * v_defaultYminText () { return L"50.0"; } virtual const wchar * v_defaultYmaxText () { return L"600.0"; } virtual const wchar * v_yminText () { return L"Minimum frequency (Hz)"; } virtual const wchar * v_ymaxText () { return L"Maximum frequency (Hz)"; } virtual const wchar * v_yminKey () { return L"Minimum frequency"; } virtual const wchar * v_ymaxKey () { return L"Maximum frequency"; } }; KlattGrid_pitchTierEditor KlattGrid_pitchTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_flutterTierEditor, KlattGrid_realTierEditor) { // overridden methods: virtual double v_minimumLegalValue () { return 0.0; } virtual double v_maximumLegalValue () { return 1.0; } virtual const wchar * v_quantityText () { return L"Flutter (0..1)"; } virtual const wchar * v_quantityKey () { return L"Flutter"; } virtual const wchar * v_rightTickUnits () { return L""; } virtual double v_defaultYmin () { return 0.0; } virtual double v_defaultYmax () { return 1.0; } virtual const wchar * v_setRangeTitle () { return L"Set flutter range..."; } virtual const wchar * v_defaultYminText () { return L"0.0"; } virtual const wchar * v_defaultYmaxText () { return L"1.0"; } virtual const wchar * v_yminText () { return L"Minimum (0..1)"; } virtual const wchar * v_ymaxText () { return L"Maximum (0..1)"; } virtual const wchar * v_yminKey () { return L"Minimum"; } virtual const wchar * v_ymaxKey () { return L"Maximum"; } }; KlattGrid_flutterTierEditor KlattGrid_flutterTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_intensityTierEditor, KlattGrid_realTierEditor) { // overridden methods: void v_createHelpMenuItems (EditorMenu menu); virtual const wchar * v_quantityText () { return L"Intensity (dB)"; } virtual const wchar * v_quantityKey () { return L"Intensity"; } virtual const wchar * v_rightTickUnits () { return L" dB"; } virtual double v_defaultYmin () { return 50.0; } virtual double v_defaultYmax () { return 100.0; } virtual const wchar * v_setRangeTitle () { return L"Set intensity range..."; } virtual const wchar * v_defaultYminText () { return L"50.0"; } virtual const wchar * v_defaultYmaxText () { return L"100.0"; } virtual const wchar * v_yminText () { return L"Minimum intensity (dB)"; } virtual const wchar * v_ymaxText () { return L"Maximum intensity (dB)"; } virtual const wchar * v_yminKey () { return L"Minimum intensity"; } virtual const wchar * v_ymaxKey () { return L"Maximum intensity"; } }; void KlattGrid_intensityTierEditor_init (KlattGrid_intensityTierEditor me, GuiObject parent, const wchar_t *title, KlattGrid klattgrid, RealTier tier); Thing_define (KlattGrid_decibelTierEditor, KlattGrid_intensityTierEditor) { // overridden methods: virtual const wchar * v_quantityText () { return L"Amplitude (dB)"; } virtual const wchar * v_quantityKey () { return L"Amplitude"; } virtual const wchar * v_rightTickUnits () { return L" dB"; } virtual double v_defaultYmin () { return -30.0; } virtual double v_defaultYmax () { return 30.0; } virtual const wchar * v_setRangeTitle () { return L"Set amplitude range..."; } virtual const wchar * v_defaultYminText () { return L"-30.0"; } virtual const wchar * v_defaultYmaxText () { return L"30.0"; } virtual const wchar * v_yminText () { return L"Minimum amplitude (dB)"; } virtual const wchar * v_ymaxText () { return L"Maximum amplitude (dB)"; } virtual const wchar * v_yminKey () { return L"Minimum amplitude"; } virtual const wchar * v_ymaxKey () { return L"Maximum amplitude"; } }; KlattGrid_decibelTierEditor KlattGrid_decibelTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid, RealTier data); Thing_define (KlattGrid_voicingAmplitudeTierEditor, KlattGrid_intensityTierEditor) { }; KlattGrid_voicingAmplitudeTierEditor KlattGrid_voicingAmplitudeTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_aspirationAmplitudeTierEditor, KlattGrid_intensityTierEditor) { }; KlattGrid_aspirationAmplitudeTierEditor KlattGrid_aspirationAmplitudeTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_breathinessAmplitudeTierEditor, KlattGrid_intensityTierEditor) { }; KlattGrid_breathinessAmplitudeTierEditor KlattGrid_breathinessAmplitudeTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_spectralTiltTierEditor, KlattGrid_intensityTierEditor) { // overridden methods: virtual double v_defaultYmin () { return -50.0; } virtual double v_defaultYmax () { return 10.0; } virtual const wchar * v_defaultYminText () { return L"-50.0"; } virtual const wchar * v_defaultYmaxText () { return L"10.0"; } }; KlattGrid_spectralTiltTierEditor KlattGrid_spectralTiltTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_fricationBypassTierEditor, KlattGrid_intensityTierEditor) { // overridden methods: virtual double v_defaultYmin () { return -50.0; } virtual double v_defaultYmax () { return 10.0; } virtual const wchar * v_defaultYminText () { return L"-50.0"; } virtual const wchar * v_defaultYmaxText () { return L"10.0"; } }; KlattGrid_fricationBypassTierEditor KlattGrid_fricationBypassTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_fricationAmplitudeTierEditor, KlattGrid_intensityTierEditor) { }; KlattGrid_fricationAmplitudeTierEditor KlattGrid_fricationAmplitudeTierEditor_create (GuiObject parent, const wchar_t *title, KlattGrid klattgrid); Thing_define (KlattGrid_formantGridEditor, FormantGridEditor) { // new data: public: KlattGrid klattgrid; // overridden methods: virtual void v_play (double tmin, double tmax); virtual bool v_hasSourceMenu () { return false; } }; KlattGrid_formantGridEditor KlattGrid_formantGridEditor_create (GuiObject parent, const wchar_t *title, KlattGrid data, int formantType); #endif // _KlattGridEditors_h_ sources_5316/dwtools/HMM.cpp0000644000176700017670000016535111741614246014564 0ustar paulpaul/* HMM.cpp * * Copyright (C) 2010-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20110304 Thing_new */ #include "Distributions_and_Strings.h" #include "HMM.h" #include "Index.h" #include "NUM2.h" #include "Strings_extensions.h" #include "oo_DESTROY.h" #include "HMM_def.h" #include "oo_COPY.h" #include "HMM_def.h" #include "oo_EQUAL.h" #include "HMM_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "HMM_def.h" #include "oo_WRITE_TEXT.h" #include "HMM_def.h" #include "oo_WRITE_BINARY.h" #include "HMM_def.h" #include "oo_READ_TEXT.h" #include "HMM_def.h" #include "oo_READ_BINARY.h" #include "HMM_def.h" #include "oo_DESCRIPTION.h" #include "HMM_def.h" /* Whenever a routine returns ln(p), the result for p=0 is -INFINITY. On IEEE floating point hardware this number behaves reasonably. This means that when the variable q equals INFINITY, q + a -> INFINITY, where a is a finite number. */ // helpers int NUMget_line_intersection_with_circle (double xc, double yc, double r, double a, double b, double *x1, double *y1, double *x2, double *y2); void HMM_Observation_init (I, const wchar_t *label, long numberOfComponents, long dimension, long storage); HMM_Observation HMM_Observation_create (const wchar_t *label, long numberOfComponents, long dimension, long storage); long HMM_and_HMM_ObservationSequence_getLongestSequence (HMM me, HMM_ObservationSequence thee, long symbolNumber); long StringsIndex_getLongestSequence (StringsIndex me, long index, long *pos); long Strings_getLongestSequence (Strings me, wchar_t *string, long *pos); void HMM_State_init (I, const wchar_t *label); HMM_State HMM_State_create (const wchar_t *label); HMM_BaumWelch HMM_BaumWelch_create (long nstates, long nsymbols, long capacity); void HMM_BaumWelch_getGamma (HMM_BaumWelch me); HMM_BaumWelch HMM_forward (HMM me, long *obs, long nt); void HMM_BaumWelch_reInit (HMM_BaumWelch me); void HMM_and_HMM_BaumWelch_getXi (HMM me, HMM_BaumWelch thee, long *obs); void HMM_and_HMM_BaumWelch_reestimate (HMM me, HMM_BaumWelch thee); void HMM_and_HMM_BaumWelch_addEstimate (HMM me, HMM_BaumWelch thee, long *obs); void HMM_and_HMM_BaumWelch_forward (HMM me, HMM_BaumWelch thee, long *obs); void HMM_and_HMM_BaumWelch_backward (HMM me, HMM_BaumWelch thee, long *obs); void HMM_and_HMM_Viterbi_decode (HMM me, HMM_Viterbi thee, long *obs); double HMM_getProbabilityOfObservations (HMM me, long *obs, long numberOfTimes); TableOfReal StringsIndex_to_TableOfReal_transitions (StringsIndex me, int probabilities); StringsIndex HMM_and_HMM_StateSequence_to_StringsIndex (HMM me, HMM_StateSequence thee); HMM_Viterbi HMM_Viterbi_create (long nstates, long ntimes); HMM_Viterbi HMM_to_HMM_Viterbi (HMM me, long *obs, long ntimes); // evaluate the numbers given to probabilities static double *NUMwstring_to_probs (wchar_t *s, long nwanted) { long numbers_found; autoNUMvector numbers (NUMstring_to_numbers (s, &numbers_found), 1); if (numbers_found != nwanted) { Melder_throw ("You supplied ", numbers_found, ", while ", nwanted, " numbers needed."); } double sum = 0; for (long i = 1; i <= numbers_found; i++) { if (numbers[i] < 0) { Melder_throw ("Numbers have to be positive."); } sum += numbers[i]; } if (sum <= 0) { Melder_throw ("All probabilities cannot be zero."); } for (long i = 1; i <= numbers_found; i++) { numbers[i] /= sum; } return numbers.transfer(); } int NUMget_line_intersection_with_circle (double xc, double yc, double r, double a, double b, double *x1, double *y1, double *x2, double *y2) { double ca = a * a + 1, bmyc = (b - yc); double cb = 2 * (a * bmyc - xc); double cc = bmyc * bmyc + xc * xc - r * r; long nroots = NUMsolveQuadraticEquation (ca, cb, cc, x1, x2); if (nroots == 1) { *y1 = a * *x1 + b; *x2 = *x1; *y2 = *y1; } else if (nroots == 2) { if (*x1 > *x2) { double tmp = *x1; *x1 = *x2; *x2 = tmp; } *y1 = *x1 * a + b; *y2 = *x2 * a + b; } return nroots; } // D(l_1,l_2)=1/n( log p(O_2|l_1) - log p(O_2|l_2) static double HMM_and_HMM_getCrossEntropy_asym (HMM me, HMM thee, long observationLength) { autoHMM_ObservationSequence os = HMM_to_HMM_ObservationSequence (thee, 0, observationLength); double ce = HMM_and_HMM_ObservationSequence_getCrossEntropy (me, os.peek()); if (ce == NUMundefined || ce == INFINITY) { return ce; } double ce2 = HMM_and_HMM_ObservationSequence_getCrossEntropy (thee, os.peek()); if (ce2 == NUMundefined || ce2 == INFINITY) { return ce2; } return ce - ce2; } /**************** HMM_Observation ******************************/ Thing_implement (HMM_Observation, Data, 0); void HMM_Observation_init (I, const wchar_t *label, long numberOfComponents, long dimension, long storage) { iam (HMM_Observation); my label = Melder_wcsdup (label); my gm = GaussianMixture_create (numberOfComponents, dimension, storage); } HMM_Observation HMM_Observation_create (const wchar_t *label, long numberOfComponents, long dimension, long storage) { try { autoHMM_Observation me = Thing_new (HMM_Observation); HMM_Observation_init (me.peek(), label, numberOfComponents, dimension, storage); return me.transfer(); } catch (MelderError) { Melder_throw ("HMM_Observation not created."); } } long Strings_getLongestSequence (Strings me, wchar_t *string, long *pos) { long length = 0, longest = 0, lpos = 0; for (long i = 1; i <= my numberOfStrings; i++) { if (Melder_wcsequ (my strings[i], string)) { if (length == 0) { lpos = i; } length++; } else { if (length > 0) { if (length > longest) { longest = length; *pos = lpos; } length = 0; } } } return length; } long StringsIndex_getLongestSequence (StringsIndex me, long index, long *pos) { long length = 0, longest = 0, lpos = 0; for (long i = 1; i <= my numberOfElements; i++) { if (my classIndex[i] == index) { if (length == 0) { lpos = i; } length++; } else { if (length > 0) { if (length > longest) { longest = length; *pos = lpos; } length = 0; } } } return length; } /**************** HMM_State ******************************/ Thing_implement (HMM_State, Data, 0); void HMM_State_init (I, const wchar_t *label) { iam (HMM_State); my label = Melder_wcsdup (label); } HMM_State HMM_State_create (const wchar_t *label) { try { autoHMM_State me = Thing_new (HMM_State); HMM_State_init (me.peek(), label); return me.transfer(); } catch (MelderError) { Melder_throw ("HMM_State not created."); } } void HMM_State_setLabel (HMM_State me, wchar_t *label) { Melder_free (my label); my label = Melder_wcsdup (label); } /**************** HMM_BaumWelch ******************************/ Thing_implement (HMM_BaumWelch, Data, 0); void structHMM_BaumWelch :: v_destroy () { for (long it = 1; it <= numberOfTimes; it++) { NUMmatrix_free (xi[it], 1, 1); } NUMvector_free (xi, 1); NUMvector_free (scale, 1); NUMmatrix_free (beta, 1, 1); NUMmatrix_free (alpha, 1, 1); NUMmatrix_free (gamma, 1, 1); } HMM_BaumWelch HMM_BaumWelch_create (long nstates, long nsymbols, long capacity) { try { autoHMM_BaumWelch me = Thing_new (HMM_BaumWelch); my numberOfTimes = my capacity = capacity; my numberOfStates = nstates; my numberOfSymbols = nsymbols; my alpha = NUMmatrix (1, nstates, 1, capacity); my beta = NUMmatrix (1, nstates, 1, capacity); my scale = NUMvector (1, capacity); my xi = NUMvector (1, capacity); my aij_num = NUMmatrix (0, nstates, 1, nstates + 1); my aij_denom = NUMmatrix (0, nstates, 1, nstates + 1); my bik_num = NUMmatrix (1, nstates, 1, nsymbols); my bik_denom = NUMmatrix (1, nstates, 1, nsymbols); my gamma = NUMmatrix (1, nstates, 1, capacity); for (long it = 1; it <= capacity; it++) { my xi[it] = NUMmatrix (1, nstates, 1, nstates); } return me.transfer(); } catch (MelderError) { Melder_throw ("HMM_BaumWelch not created."); } } void HMM_BaumWelch_getGamma (HMM_BaumWelch me) { for (long it = 1; it <= my numberOfTimes; it++) { double sum = 0.0; for (long is = 1; is <= my numberOfStates; is++) { my gamma[is][it] = my alpha[is][it] * my beta[is][it]; sum += my gamma[is][it]; } for (long is = 1; is <= my numberOfStates; is++) { my gamma[is][it] /= sum; } } } /**************** HMM_Viterbi ******************************/ Thing_implement (HMM_Viterbi, Data, 0); HMM_Viterbi HMM_Viterbi_create (long nstates, long ntimes) { try { autoHMM_Viterbi me = Thing_new (HMM_Viterbi); my numberOfTimes = ntimes; my numberOfStates = nstates; my viterbi = NUMmatrix (1, nstates, 1 , ntimes); my bp = NUMmatrix (1, nstates, 1 , ntimes); my path = NUMvector (1, ntimes); return me.transfer(); } catch (MelderError) { Melder_throw ("HMM_Viterbi not created."); } } /******************* HMM_ObservationSequence & HMM_StateSequence ***/ Thing_implement (HMM_ObservationSequence, Table, 0); HMM_ObservationSequence HMM_ObservationSequence_create (long numberOfItems, long dataLength) { try { autoHMM_ObservationSequence me = Thing_new (HMM_ObservationSequence); Table_initWithoutColumnNames (me.peek(), numberOfItems, dataLength + 1); return me.transfer(); } catch (MelderError) { Melder_throw ("HMM_ObservationSequence not created."); } } long HMM_ObservationSequence_getNumberOfObservations (HMM_ObservationSequence me) { return my rows -> size; } void HMM_ObservationSequence_removeObservation (HMM_ObservationSequence me, long index) { Table_removeRow ( (Table) me, index); } Strings HMM_ObservationSequence_to_Strings (HMM_ObservationSequence me) { try { long numberOfStrings = my rows -> size; autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, numberOfStrings); for (long i = 1; i <= numberOfStrings; i++) { thy strings[i] = Melder_wcsdup_f (Table_getStringValue_Assert ( (Table) me, i, 1)); (thy numberOfStrings) ++; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Strings created."); } } HMM_ObservationSequence Strings_to_HMM_ObservationSequence (Strings me) { try { autoHMM_ObservationSequence thee = HMM_ObservationSequence_create (my numberOfStrings, 0); for (long i = 1; i <= my numberOfStrings; i++) { Table_setStringValue ( (Table) thee.peek(), i, 1, my strings[i]); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no HMM_ObservationSequence created."); } } StringsIndex HMM_ObservationSequence_to_StringsIndex (HMM_ObservationSequence me) { try { autoStrings s = HMM_ObservationSequence_to_Strings (me); autoStringsIndex thee = Strings_to_StringsIndex (s.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no StringsIndex created."); } } long HMM_and_HMM_ObservationSequence_getLongestSequence (HMM me, HMM_ObservationSequence thee, long symbolNumber) { autoStringsIndex si = HMM_and_HMM_ObservationSequence_to_StringsIndex (me, thee); // TODO (void) symbolNumber; return 1; } Thing_implement (HMM_ObservationSequences, Collection, 0); HMM_ObservationSequences HMM_ObservationSequences_create () { try { autoHMM_ObservationSequences me = Thing_new (HMM_ObservationSequences); Collection_init (me.peek(), classHMM_ObservationSequence, 1000); return me.transfer(); } catch (MelderError) { Melder_throw ("HMM_ObservationSequences not created."); } } long HMM_ObservationSequences_getLongestSequence (HMM_ObservationSequences me) { long longest = 0; for (long i = 1; i <= my size; i++) { HMM_ObservationSequence thee = (HMM_ObservationSequence) my item[i]; if (thy rows -> size > longest) { longest = thy rows -> size; } } return longest; } Thing_implement (HMM_StateSequence, Strings, 0); HMM_StateSequence HMM_StateSequence_create (long numberOfItems) { try { autoHMM_StateSequence me = Thing_new (HMM_StateSequence); my strings = NUMvector (1, numberOfItems); return me.transfer(); } catch (MelderError) { Melder_throw ("HMM_StateSequence not created."); } } Strings HMM_StateSequence_to_Strings (HMM_StateSequence me) { try { autoStrings thee = Thing_new (Strings); my structStrings :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Strings created."); } } /**************** HMM ******************************/ Thing_implement (HMM, Data, 0); void structHMM :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of states: ", Melder_integer (numberOfStates)); for (long i = 1; i <= numberOfStates; i++) { HMM_State hmms = (HMM_State) states -> item[i]; MelderInfo_writeLine2 (L" ", hmms -> label); } MelderInfo_writeLine2 (L"Number of symbols: ", Melder_integer (numberOfObservationSymbols)); for (long i = 1; i <= numberOfObservationSymbols; i++) { HMM_Observation hmms = (HMM_Observation) observationSymbols -> item[i]; MelderInfo_writeLine2 (L" ", hmms -> label); } } static void HMM_init (HMM me, long numberOfStates, long numberOfObservationSymbols, int leftToRight) { my numberOfStates = numberOfStates; my numberOfObservationSymbols = numberOfObservationSymbols; my componentStorage = 1; my leftToRight = leftToRight; my states = Ordered_create (); my observationSymbols = Ordered_create (); my transitionProbs = NUMmatrix (0, numberOfStates, 1, numberOfStates + 1); my emissionProbs = NUMmatrix (1, numberOfStates, 1, numberOfObservationSymbols); } HMM HMM_create (int leftToRight, long numberOfStates, long numberOfObservationSymbols) { try { autoHMM me = Thing_new (HMM); HMM_init (me.peek(), numberOfStates, numberOfObservationSymbols, leftToRight); HMM_setDefaultStates (me.peek()); HMM_setDefaultObservations (me.peek()); HMM_setDefaultTransitionProbs (me.peek()); HMM_setDefaultStartProbs (me.peek()); HMM_setDefaultEmissionProbs (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("HMM not created."); } } void HMM_setDefaultStates (HMM me) { autoMelderString label; for (long i = 1; i <= my numberOfStates; i++) { MelderString_append (&label, L"S", Melder_integer (i)); autoHMM_State hmms = HMM_State_create (label.string); HMM_addState (me, hmms.transfer()); MelderString_empty (&label); } } HMM HMM_createFullContinuousModel (int leftToRight, long numberOfStates, long numberOfObservationSymbols, long numberOfFeatureStreams, long *dimensionOfStream, long *numberOfGaussiansforStream) { (void) leftToRight; (void) numberOfStates; (void) numberOfObservationSymbols; (void) numberOfFeatureStreams; (void) dimensionOfStream; (void) numberOfGaussiansforStream; return NULL; } HMM HMM_createContinuousModel (int leftToRight, long numberOfStates, long numberOfObservationSymbols, long numberOfMixtureComponentsPerSymbol, long componentDimension, long componentStorage) { try { MelderString label = { 0 }; autoHMM me = Thing_new (HMM); HMM_init (me.peek(), numberOfStates, numberOfObservationSymbols, leftToRight); my numberOfMixtureComponents = numberOfMixtureComponentsPerSymbol; my componentDimension = componentDimension; my componentStorage = componentStorage; for (long i = 1; i <= numberOfStates; i++) { MelderString_append (&label, L"S", Melder_integer (i)); autoHMM_State state = HMM_State_create (label.string); HMM_addState (me.peek(), state.transfer()); MelderString_empty (&label); } for (long j = 1; j <= numberOfObservationSymbols; j++) { MelderString_append (&label, L"s", Melder_integer (j)); autoHMM_Observation obs = HMM_Observation_create (label.string, numberOfMixtureComponentsPerSymbol, componentDimension, componentStorage); HMM_addObservation (me.peek(), obs.transfer()); MelderString_empty (&label); } HMM_setDefaultTransitionProbs (me.peek()); HMM_setDefaultStartProbs (me.peek()); HMM_setDefaultEmissionProbs (me.peek()); HMM_setDefaultMixingProbabilities (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("Continuous model HMM not created."); } } // for a simple non-hidden model leave either states empty or symbols empty !!! HMM HMM_createSimple (int leftToRight, const wchar_t *states_string, const wchar_t *symbols_string) { try { autoHMM me = Thing_new (HMM); const wchar_t *states = states_string; const wchar_t *symbols = symbols_string; long numberOfStates = Melder_countTokens (states_string); long numberOfObservationSymbols = Melder_countTokens (symbols_string); if (numberOfStates == 0 and numberOfObservationSymbols == 0) { Melder_throw ("No states and symbols."); } if (numberOfStates > 0) { if (numberOfObservationSymbols <= 0) { numberOfObservationSymbols = numberOfStates; symbols = states_string; my notHidden = 1; } } else if (numberOfObservationSymbols > 0) { numberOfStates = numberOfObservationSymbols; states = symbols_string; my notHidden = 1; } HMM_init (me.peek(), numberOfStates, numberOfObservationSymbols, leftToRight); for (wchar_t *token = Melder_firstToken (states); token != 0; token = Melder_nextToken ()) { autoHMM_State state = HMM_State_create (token); HMM_addState (me.peek(), state.transfer()); } for (wchar_t *token = Melder_firstToken (symbols); token != NULL; token = Melder_nextToken ()) { autoHMM_Observation symbol = HMM_Observation_create (token, 0, 0, 0); HMM_addObservation (me.peek(), symbol.transfer()); } HMM_setDefaultTransitionProbs (me.peek()); HMM_setDefaultStartProbs (me.peek()); HMM_setDefaultEmissionProbs (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("Simple HMM not created."); } } void HMM_setDefaultObservations (HMM me) { autoMelderString symbol; const wchar_t *def = my notHidden ? L"S" : L"s"; for (long i = 1; i <= my numberOfObservationSymbols; i++) { MelderString_append (&symbol, def, Melder_integer (i)); autoHMM_Observation hmms = HMM_Observation_create (symbol.string, 0, 0, 0); HMM_addObservation (me, hmms.transfer()); MelderString_empty (&symbol); } } void HMM_setDefaultTransitionProbs (HMM me) { for (long i = 1; i <= my numberOfStates; i++) { double p = my leftToRight ? 1.0 / (my numberOfStates - i + 1) : 1.0 / my numberOfStates; for (long j = 1; j <= my numberOfStates; j++) { my transitionProbs[i][j] = my leftToRight && j < i ? 0 : p; } } // leftToRight must have end state! if (my leftToRight) my transitionProbs[my numberOfStates][my numberOfStates] = my transitionProbs[my numberOfStates][my numberOfStates + 1] = 0.5; } void HMM_setDefaultStartProbs (HMM me) { double p = 1.0 / my numberOfStates; for (long j = 1; j <= my numberOfStates; j++) { my transitionProbs[0][j] = p; } } void HMM_setDefaultEmissionProbs (HMM me) { double p = 1.0 / my numberOfObservationSymbols; for (long i = 1; i <= my numberOfStates; i++) for (long j = 1; j <= my numberOfObservationSymbols; j++) { my emissionProbs[i][j] = my notHidden ? (i == j ? 1 : 0) : p; } } void HMM_setDefaultMixingProbabilities (HMM me) { double mp = 1.0 / my numberOfMixtureComponents; for (long is = 1; is <= my numberOfObservationSymbols; is++) { HMM_Observation hmmo = (HMM_Observation) my observationSymbols -> item[is]; for (long im = 1; im <= my numberOfMixtureComponents; im++) { hmmo -> gm -> mixingProbabilities[im] = mp; } } } void HMM_setStartProbabilities (HMM me, wchar_t *probs) { try { autoNUMvector p (NUMwstring_to_probs (probs, my numberOfStates), 1); for (long i = 1; i <= my numberOfStates; i++) { my transitionProbs[0][i] = p[i]; } } catch (MelderError) { Melder_throw (me, ": no start probabilities set."); } } void HMM_setTransitionProbabilities (HMM me, long state_number, wchar_t *state_probs) { try { if (state_number > my states -> size) { Melder_throw (L"State number too large."); } autoNUMvector p (NUMwstring_to_probs (state_probs, my numberOfStates + 1), 1); for (long i = 1; i <= my numberOfStates + 1; i++) { my transitionProbs[state_number][i] = p[i]; } } catch (MelderError) { Melder_throw (me, ": no transition probabilities set."); } } void HMM_setEmissionProbabilities (HMM me, long state_number, wchar_t *emission_probs) { try { if (state_number > my states -> size) { Melder_throw (L"State number too large."); } if (my notHidden) { Melder_throw (L"The emission probs of this model are fixed."); } autoNUMvector p (NUMwstring_to_probs (emission_probs, my numberOfObservationSymbols), 1); for (long i = 1; i <= my numberOfObservationSymbols; i++) { my emissionProbs[state_number][i] = p[i]; } } catch (MelderError) { Melder_throw (me, ": no emission probabilities set."); } } void HMM_addObservation (HMM me, thou) { thouart (HMM_Observation); long ns = my observationSymbols -> size + 1; if (ns > my numberOfObservationSymbols) { Melder_throw ("Observation list is full."); } Ordered_addItemPos (my observationSymbols, thee, ns); } void HMM_addState (HMM me, thou) { thouart (HMM_State); long ns = my states -> size + 1; if (ns > my numberOfStates) { Melder_throw ("States list is full."); } Ordered_addItemPos (my states, thee, ns); } TableOfReal HMM_extractTransitionProbabilities (HMM me) { try { autoTableOfReal thee = TableOfReal_create (my numberOfStates + 1, my numberOfStates + 1); for (long is = 1; is <= my numberOfStates; is++) { HMM_State hmms = (HMM_State) my states -> item[is]; TableOfReal_setRowLabel (thee.peek(), is + 1, hmms -> label); TableOfReal_setColumnLabel (thee.peek(), is, hmms -> label); for (long js = 1; js <= my numberOfStates; js++) { thy data[is + 1][js] = my transitionProbs[is][js]; } } TableOfReal_setRowLabel (thee.peek(), 1, L"START"); TableOfReal_setColumnLabel (thee.peek(), my numberOfStates + 1, L"END"); for (long is = 1; is <= my numberOfStates; is++) { thy data[1][is] = my transitionProbs[0][is]; thy data[is + 1][my numberOfStates + 1] = my transitionProbs[is][my numberOfStates + 1]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no transition probabilities extracted."); } } TableOfReal HMM_extractEmissionProbabilities (HMM me) { try { autoTableOfReal thee = TableOfReal_create (my numberOfStates, my numberOfObservationSymbols); for (long js = 1; js <= my numberOfObservationSymbols; js++) { HMM_Observation hmms = (HMM_Observation) my observationSymbols -> item[js]; TableOfReal_setColumnLabel (thee.peek(), js, hmms -> label); } for (long is = 1; is <= my numberOfStates; is++) { HMM_State hmms = (HMM_State) my states -> item[is]; TableOfReal_setRowLabel (thee.peek(), is, hmms -> label); for (long js = 1; js <= my numberOfObservationSymbols; js++) { thy data[is][js] = my emissionProbs[is][js]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no emission probabilities extracted."); }; } double HMM_getExpectedValueOfDurationInState (HMM me, long istate) { if (istate < 0 || istate > my numberOfStates) { return NUMundefined; } return 1 / (1 - my transitionProbs[istate][istate]); } double HMM_getProbabilityOfStayingInState (HMM me, long istate, long numberOfTimeUnits) { if (istate < 0 || istate > my numberOfStates) { return NUMundefined; } return pow (my transitionProbs[istate][istate], numberOfTimeUnits - 1) * (1 - my transitionProbs[istate][istate]); } double HMM_and_HMM_getCrossEntropy (HMM me, HMM thee, long observationLength, int symmetric) { double ce1 = HMM_and_HMM_getCrossEntropy_asym (me, thee, observationLength); if (! symmetric || ce1 == NUMundefined || ce1 == INFINITY) { return ce1; } double ce2 = HMM_and_HMM_getCrossEntropy_asym (thee, me, observationLength); if (ce2 == NUMundefined || ce2 == INFINITY) { return ce2; } return (ce1 + ce2) / 2; } double HMM_and_HMM_and_HMM_ObservationSequence_getCrossEntropy (HMM me, HMM thee, HMM_ObservationSequence him) { double ce1 = HMM_and_HMM_ObservationSequence_getCrossEntropy (me, him); if (ce1 == NUMundefined || ce1 == INFINITY) { return ce1; } double ce2 = HMM_and_HMM_ObservationSequence_getCrossEntropy (thee, him); if (ce2 == NUMundefined || ce2 == INFINITY) { return ce2; } return (ce1 + ce2) / 2; } void HMM_draw (HMM me, Graphics g, int garnish) { double xwidth = sqrt (my numberOfStates); double rstate = 0.3 / xwidth, r = xwidth / 3.0; double xmax = 1.2 * xwidth / 2, xmin = -xmax, ymin = xmin, ymax = xmax; autoNUMvector xs (1, my numberOfStates); autoNUMvector ys (1, my numberOfStates); Graphics_setWindow (g, xmin, xmax, ymin, ymax); // heuristic: all states on a circle until we have a better graph drawing algorithm. xs[1] = ys[1] = 0; if (my numberOfStates > 1) { for (long is = 1; is <= my numberOfStates; is++) { double alpha = - NUMpi + NUMpi * 2 * (is - 1) / my numberOfStates; xs[is] = r * cos (alpha); ys[is] = r * sin (alpha); } } // reorder the positions such that state number 1 is most left and last state number is right. // if > 5 may be one in the middle with the most connections // ... // find fontsize int fontSize = Graphics_inqFontSize (g); const wchar_t *widest_label = L""; double max_width = 0; for (long is = 1; is <= my numberOfStates; is++) { HMM_State hmms = (HMM_State) my states -> item[is]; double w = hmms -> label == NULL ? 0 : Graphics_textWidth (g, hmms -> label); if (w > max_width) { widest_label = hmms -> label; max_width = w; } } int new_fontSize = fontSize; while (max_width > 2 * rstate && new_fontSize > 4) { new_fontSize --; Graphics_setFontSize (g, new_fontSize); max_width = Graphics_textWidth (g, widest_label); } Graphics_setFontSize (g, new_fontSize); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (long is = 1; is <= my numberOfStates; is++) { HMM_State hmms = (HMM_State) my states -> item[is]; Graphics_circle (g, xs[is], ys[is], rstate); Graphics_text (g, xs[is], ys[is], hmms -> label); } // draw connections from is to js // 1 -> 2 / 2-> : increase / decrease angle between 1 and 2 with pi /10 // use cos(a+b) and cos(a -b) rules double cosb = cos (NUMpi / 10), sinb = sin (NUMpi / 10); for (long is = 1; is <= my numberOfStates; is++) { double x1 = xs[is], y1 = ys[is]; for (long js = 1; js <= my numberOfStates; js++) { if (my transitionProbs[is][js] > 0 && is != js) { double x2 = xs[js], y2 = ys[js]; double dx = x2 - x1, dy = y2 - y1, h = sqrt (dx * dx + dy * dy), cosa = dx / h, sina = dy / h; double cosabp = cosa * cosb - sina * sinb, cosabm = cosa * cosb + sina * sinb; double sinabp = cosa * sinb + sina * cosb, sinabm = -cosa * sinb + sina * cosb; Graphics_arrow (g, x1 + rstate * cosabp, y1 + rstate * sinabp, x2 - rstate * cosabm, y2 - rstate * sinabm); } if (is == js) { double dx = - x1, dy = - y1, h = sqrt (dx * dx + dy * dy), cosa = dx / h, sina = dy / h; Graphics_doubleArrow (g, x1 - rstate * cosa, y1 - rstate * sina, x1 - 1.4 * rstate * cosa, y1 - 1.4 * rstate * sina); } } } if (garnish) { Graphics_drawInnerBox (g); } } void HMM_unExpandPCA (HMM me) { if (my componentDimension <= 0) { return; // nothing to do } for (long is = 1; is <= my numberOfObservationSymbols; is++) { HMM_Observation s = (HMM_Observation) my observationSymbols -> item[is]; GaussianMixture_unExpandPCA (s -> gm); } } HMM_ObservationSequence HMM_to_HMM_ObservationSequence (HMM me, long startState, long numberOfItems) { try { autoHMM_ObservationSequence thee = HMM_ObservationSequence_create (numberOfItems, my componentDimension); autoNUMvector obs; autoNUMvector buf; if (my componentDimension > 0) { obs.reset (1, my componentDimension); buf.reset (1, my componentDimension); } long istate = startState == 0 ? NUMgetIndexFromProbability (my transitionProbs[0], my numberOfStates, NUMrandomUniform (0, 1)) : startState; for (long i = 1; i <= numberOfItems; i++) { // Emit a symbol from istate long isymbol = NUMgetIndexFromProbability (my emissionProbs[istate], my numberOfObservationSymbols, NUMrandomUniform (0, 1)); HMM_Observation s = (HMM_Observation) my observationSymbols -> item[isymbol]; if (my componentDimension > 0) { wchar_t *name; GaussianMixture_generateOneVector (s -> gm, obs.peek(), &name, buf.peek()); for (long j = 1; j <= my componentDimension; j++) { Table_setNumericValue ( (Table) thee.peek(), i, 1 + j, obs[j]); } } Table_setStringValue ( (Table) thee.peek(), i, 1, s -> label); // get next state istate = NUMgetIndexFromProbability (my transitionProbs[istate], my numberOfStates + 1, NUMrandomUniform (0, 1)); if (istate == my numberOfStates + 1) { // final state for (long j = numberOfItems; j > i; j--) { HMM_ObservationSequence_removeObservation (thee.peek(), j); } break; } } HMM_unExpandPCA (me); return thee.transfer(); } catch (MelderError) { HMM_unExpandPCA (me); Melder_throw (me, ":no HMM_ObservationSequence created."); } } HMM_BaumWelch HMM_forward (HMM me, long *obs, long nt) { try { autoHMM_BaumWelch thee = HMM_BaumWelch_create (my numberOfStates, my numberOfObservationSymbols, nt); HMM_and_HMM_BaumWelch_forward (me, thee.peek(), obs); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no HMM_BaumWelch created."); } } HMM_Viterbi HMM_to_HMM_Viterbi (HMM me, long *obs, long ntimes) { try { autoHMM_Viterbi thee = HMM_Viterbi_create (my numberOfStates, ntimes); HMM_and_HMM_Viterbi_decode (me, thee.peek(), obs); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no HMM_Viterbi created."); } } void HMM_BaumWelch_reInit (HMM_BaumWelch me) { my totalNumberOfSequences = 0; my lnProb = 0; /* The _num and _denum matrices are asigned as += in the iteration loop and therefore need to be zeroed at the start of each new iteration. The elements of alpha, beta, scale, gamma & xi are always calculated directly and need not be initialised. */ for (long is = 0; is <= my numberOfStates; is++) { for (long js = 1; js <= my numberOfStates + 1; js++) { my aij_num[is][js] = 0; my aij_denom[is][js] = 0; } } for (long is = 1; is <= my numberOfStates; is++) { for (long js = 1; js <= my numberOfSymbols; js++) { my bik_num[is][js] = 0; my bik_denom[is][js] = 0; } } } void HMM_and_HMM_ObservationSequences_learn (HMM me, HMM_ObservationSequences thee, double delta_lnp, double minProb) { try { // act as if all observation sequences are in memory long capacity = HMM_ObservationSequences_getLongestSequence (thee); autoHMM_BaumWelch bw = HMM_BaumWelch_create (my numberOfStates, my numberOfObservationSymbols, capacity); bw -> minProb = minProb; MelderInfo_open (); long iter = 0; double lnp; do { lnp = bw -> lnProb; HMM_BaumWelch_reInit (bw.peek()); for (long ios = 1; ios <= thy size; ios++) { MelderInfo_writeLine2 (L"Observation sequence: ", Melder_integer (ios)); HMM_ObservationSequence hmm_os = (HMM_ObservationSequence) thy item[ios]; autoStringsIndex si = HMM_and_HMM_ObservationSequence_to_StringsIndex (me, hmm_os); long *obs = si -> classIndex, nobs = si -> numberOfElements; // convenience // Interpretation of unknowns: end of sequence long istart = 1, iend = nobs; while (istart <= nobs) { while (istart <= nobs && obs[istart] == 0) { istart++; }; if (istart > nobs) { break; } iend = istart + 1; while (iend <= nobs && obs[iend] != 0) { iend++; } iend --; bw -> numberOfTimes = iend - istart + 1; (bw -> totalNumberOfSequences) ++; MelderInfo_writeLine2 (L" sub observation: ", Melder_integer (bw -> totalNumberOfSequences)); HMM_and_HMM_BaumWelch_forward (me, bw.peek(), obs + istart - 1); // get new alphas HMM_and_HMM_BaumWelch_backward (me, bw.peek(), obs + istart - 1); // get new betas HMM_BaumWelch_getGamma (bw.peek()); HMM_and_HMM_BaumWelch_getXi (me, bw.peek(), obs + istart - 1); HMM_and_HMM_BaumWelch_addEstimate (me, bw.peek(), obs + istart - 1); istart = iend + 1; } } // we have processed all observation sequences, now it time to estimate new probabilities. iter++; HMM_and_HMM_BaumWelch_reestimate (me, bw.peek()); MelderInfo_writeLine4 (L"Iteration: ", Melder_integer (iter), L" ln(prob): ", Melder_double (bw -> lnProb)); } while (fabs ( (lnp - bw -> lnProb) / bw -> lnProb) > delta_lnp); MelderInfo_writeLine1 (L"******** Learning summary *********"); MelderInfo_writeLine3 (L" Processed ", Melder_integer (thy size), L" sequences,"); MelderInfo_writeLine3 (L" consisting of ", Melder_integer (bw -> totalNumberOfSequences), L" observation sequences."); MelderInfo_writeLine3 (L" Longest observation sequence had ", Melder_integer (capacity), L" items"); } catch (MelderError) { Melder_throw (me, " & ", thee, ": not learned."); } } // xc1 < xc2 void HMM_and_HMM_StateSequence_drawTrellis (HMM me, HMM_StateSequence thee, Graphics g, int connect, int garnish) { long numberOfTimes = thy numberOfStrings; autoStringsIndex si = HMM_and_HMM_StateSequence_to_StringsIndex (me, thee); double xmin = 0, xmax = numberOfTimes + 1, ymin = 0.5, ymax = my numberOfStates + 0.5; Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); double r = 0.2 / (numberOfTimes > my numberOfStates ? numberOfTimes : my numberOfStates); for (long it = 1; it <= numberOfTimes; it++) { for (long js = 1; js <= my numberOfStates; js++) { double xc = it, yc = js, x2 = it, y2 = js; Graphics_circle (g, xc, yc, r); if (it > 1) { for (long is = 1; is <= my numberOfStates; is++) { bool indexedConnection = si -> classIndex[it - 1] == is && si -> classIndex[it] == js; Graphics_setLineWidth (g, indexedConnection ? 2 : 1); Graphics_setLineType (g, indexedConnection ? Graphics_DRAWN : Graphics_DOTTED); double x1 = it - 1, y1 = is; if (connect || indexedConnection) { double a = (y1 - y2) / (x1 - x2), b = y1 - a * x1; // double xs11 = x1 - r / (a * a + 1), ys11 = a * xs11 + b; double xs12 = x1 + r / (a * a + 1), ys12 = a * xs12 + b; double xs21 = x2 - r / (a * a + 1), ys21 = a * xs21 + b; // double xs22 = x2 + r / (a * a + 1), ys22 = a * xs22 + b; Graphics_line (g, xs12, ys12, xs21, ys21); } } } } } Graphics_unsetInner (g); Graphics_setLineWidth (g, 1); Graphics_setLineType (g, Graphics_DRAWN); if (garnish) { Graphics_drawInnerBox (g); for (long js = 1; js <= my numberOfStates; js++) { HMM_State hmms = (HMM_State) my states -> item[js]; Graphics_markLeft (g, js, 0, 0, 0, hmms -> label); } Graphics_marksBottomEvery (g, 1, 1, 1, 1, 0); Graphics_textBottom (g, 1, L"Time index"); } } void HMM_drawBackwardProbabilitiesIllustration (Graphics g, bool garnish) { double xmin = 0, xmax = 1, ymin = 0, ymax = 1; Graphics_setWindow (g, xmin, xmax, ymin, ymax); double xleft = 0.1, xright = 0.9, r = 0.03; long np = 6; double dy = (1 - 0.3) / (np - 1); double x0 = xleft, y0 = 0.5; Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_circle (g, x0, y0, r); double x = xright, y = 0.9; for (long i = 1; i <= np; i++) { if (i < 4 or i == np) { Graphics_circle (g, x, y, r); double xx = x0 - x, yy = y - y0; double c = sqrt (xx * xx + yy * yy); double cosa = xx / c, sina = yy / c; Graphics_line (g, x0 - r * cosa, y0 + r * sina, x + r * cosa, y - r * sina); } else if (i == 4) { double ddy = 3*dy/4; Graphics_fillCircle (g, x, y + dy - ddy, 0.5 * r); Graphics_fillCircle (g, x, y + dy - 2 * ddy, 0.5 * r); Graphics_fillCircle (g, x, y + dy - 3 * ddy, 0.5 * r); } y -= dy; } if (garnish) { double x1 = xright + 1.5 * r, x2 = x1 - 0.2, y1 = 0.9; Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_text (g, x1, y1, L"%s__1_"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x2, y1, L"%a__%i1_"); y1 = 0.9 - dy; Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_text (g, x1, y1, L"%s__2_"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x2, y1, L"%a__%i2_"); y1 = 0.9 - (np - 1) * dy; Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_text (g, x1, y1, L"%s__%N_"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x2, y1, L"%a__%%iN%_"); Graphics_setTextAlignment (g, Graphics_RIGHT, Graphics_HALF); Graphics_text (g, x0 - 1.5 * r, y0, L"%s__%i_"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (g, x0, 0, L"%t"); Graphics_text (g, x, 0, L"%t+1"); double y3 = 0.10; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x0, y3, L"%\\be__%t_(%i)%"); Graphics_text (g, x, y3, L"%\\be__%t+1_(%j)"); } } void HMM_drawForwardProbabilitiesIllustration (Graphics g, bool garnish) { double xmin = 0, xmax = 1, ymin = 0, ymax = 1; Graphics_setWindow (g, xmin, xmax, ymin, ymax); double xleft = 0.1, xright = 0.9, r = 0.03; long np = 6; double dy = (1 - 0.3) / (np - 1); double x0 = xright, y0 = 0.5; Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_circle (g, x0, y0, r); double x = xleft, y = 0.9; for (long i = 1; i <= np; i++) { if (i < 4 or i == np) { Graphics_circle (g, x, y, r); double xx = x0 - x, yy = y - y0; double c = sqrt (xx * xx + yy * yy); double cosa = xx / c, sina = yy / c; Graphics_line (g, x0 - r * cosa, y0 + r * sina, x + r * cosa, y - r * sina); } else if (i == 4) { double ddy = 3*dy/4; Graphics_fillCircle (g, x, y + dy - ddy, 0.5 * r); Graphics_fillCircle (g, x, y + dy - 2 * ddy, 0.5 * r); Graphics_fillCircle (g, x, y + dy - 3 * ddy, 0.5 * r); } y -= dy; } if (garnish) { double x1 = xleft - 1.5 * r, x2 = x1 + 0.2, y1 = 0.9; Graphics_setTextAlignment (g, Graphics_RIGHT, Graphics_HALF); Graphics_text (g, x1, y1, L"%s__1_"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x2, y1, L"%a__1%j_"); y1 = 0.9 - dy; Graphics_setTextAlignment (g, Graphics_RIGHT, Graphics_HALF); Graphics_text (g, x1, y1, L"%s__2_"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x2, y1, L"%a__2%j_"); y1 = 0.9 - (np - 1) * dy; Graphics_setTextAlignment (g, Graphics_RIGHT, Graphics_HALF); Graphics_text (g, x1, y1, L"%s__%N_"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x2, y1, L"%a__%%Nj%_"); Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_text (g, x0 + 1.5 * r, y0, L"%s__%j_"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (g, x, 0, L"%t"); Graphics_text (g, x0, 0, L"%t+1"); double y3 = 0.10; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x, y3, L"%\\al__%t_(%i)%"); Graphics_text (g, x0, y3, L"%\\al__%t+1_(%j)"); } } void HMM_drawForwardAndBackwardProbabilitiesIllustration (Graphics g, bool garnish) { double xfrac = 0.1, xs = 1 / (0.5 - xfrac), r = 0.03; Graphics_Viewport vp = Graphics_insetViewport (g, 0, 0.5-xfrac, 0, 1); HMM_drawForwardProbabilitiesIllustration (g, false); Graphics_resetViewport (g, vp); Graphics_insetViewport (g, 0.5 + xfrac, 1, 0, 1); HMM_drawBackwardProbabilitiesIllustration (g, false); Graphics_resetViewport (g, vp); Graphics_setWindow (g, 0, xs, 0, 1); if (garnish) { double rx1 = 1 + xs * 2 * xfrac + 0.1, rx2 = rx1 + 0.9 - 0.1, y1 = 0.1; Graphics_line (g, 0.9 + r, 0.5, rx1 - r, 0.5); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (g, 0.9, 0.5 + r, L"%s__%i_"); Graphics_text (g, rx1, 0.5 + r, L"%s__%j_"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_TOP); Graphics_text (g, 1.0 + xfrac * xs, 0.5, L"%a__%%ij%_%b__%j_(O__%t+1_)"); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (g, 0.1, 0, L"%t-1"); Graphics_text (g, 0.9, 0, L"%t"); Graphics_text (g, rx1, 0, L"%t+1"); Graphics_text (g, rx2, 0, L"%t+2"); Graphics_setLineType (g, Graphics_DASHED); double x4 = rx1 - 0.06, x3 = 0.9 + 0.06; Graphics_line (g, x3, 0.7, x3, 0); Graphics_line (g, x4, 0.7, x4, 0); Graphics_setLineType (g, Graphics_DRAWN); Graphics_arrow (g, x4, y1, x4 + 0.2, y1); Graphics_arrow (g, x3, y1, x3 - 0.2, y1); Graphics_setTextAlignment (g, Graphics_RIGHT, Graphics_BOTTOM); Graphics_text (g, x3 - 0.01, y1, L"\\al__%t_(i)"); Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_BOTTOM); Graphics_text (g, x4 + 0.01, y1, L"\\be__%t+1_(j)"); } } void HMM_and_HMM_BaumWelch_getXi (HMM me, HMM_BaumWelch thee, long *obs) { for (long it = 1; it <= thy numberOfTimes - 1; it++) { double sum = 0.0; for (long is = 1; is <= thy numberOfStates; is++) { for (long js = 1; js <= thy numberOfStates; js++) { thy xi[it][is][js] = thy alpha[is][it] * thy beta[js][it + 1] * my transitionProbs[is][js] * my emissionProbs[js][ obs[it + 1] ]; sum += thy xi[it][is][js]; } } for (long is = 1; is <= my numberOfStates; is++) for (long js = 1; js <= my numberOfStates; js++) { thy xi[it][is][js] /= sum; } } } void HMM_and_HMM_BaumWelch_addEstimate (HMM me, HMM_BaumWelch thee, long *obs) { long is; // yes, outside for (is = 1; is <= my numberOfStates; is++) { // only for valid start states with p > 0 if (my transitionProbs[0][is] > 0) { thy aij_num[0][is] += thy gamma[is][1]; thy aij_denom[0][is] += 1; } } for (is = 1; is <= my numberOfStates; is++) { double gammasum = 0.0; for (long it = 1; it <= thy numberOfTimes - 1; it++) { gammasum += thy gamma[is][it]; } for (long js = 1; js <= my numberOfStates; js++) { double xisum = 0.0; for (long it = 1; it <= thy numberOfTimes - 1; it++) { xisum += thy xi[it][is][js]; } // zero probs signal invalid connections, don't reestimate if (my transitionProbs[is][js] > 0) { thy aij_num[is][js] += xisum; thy aij_denom[is][js] += gammasum; } } /* Only reestimate the emissionProbs for a hidden markov model. A not hidden model is emulated with fixed emissionProbs. */ if (!my notHidden) { gammasum += thy gamma[is][thy numberOfTimes]; // Now sum all, add last term for (long k = 1; k <= my numberOfObservationSymbols; k++) { double gammasum_k = 0.0; for (long it = 1; it <= thy numberOfTimes; it++) { if (obs[it] == k) { gammasum_k += thy gamma[is][it]; } } // only reestimate probs > 0 ! if (my emissionProbs[is][k] > 0) { thy bik_num[is][k] += gammasum_k; thy bik_denom[is][k] += gammasum; } } } // For a left-to-right model the final state determines the transition prob to go to the END state if (my leftToRight) { thy aij_num[is][my numberOfStates + 1] += thy gamma[is][thy numberOfTimes]; thy aij_denom[is][my numberOfStates + 1] += 1; } } } void HMM_and_HMM_BaumWelch_reestimate (HMM me, HMM_BaumWelch thee) { double p; /* If we only have a couple of training sequences and they all happen to start with the same symbol, one or more starting probabilities can be zero. What to do with the P_k (see Rabiner formulas 109-110)? */ for (long is = 1; is <= my numberOfStates; is++) { /* If we have not enough observation sequences it can happen that some probabilities become zero. This means that for some future observation sequences the probability evaluation returns p=0 for sequences where these transitions turn up. This makes recognition impossible and also comparisons between models are difficult. We can prevent this from happening by asumimg a minimal probability for valid transitions i.e. which have initially p > 0. */ if (my transitionProbs[0][is] > 0) { p = thy aij_num[0][is] / thy aij_denom[0][is]; my transitionProbs[0][is] = p > 0 ? p : thy minProb; } for (long js = 1; js <= my numberOfStates; js++) { if (my transitionProbs[is][js] > 0) { p = thy aij_num[is][js] / thy aij_denom[is][js]; my transitionProbs[is][js] = p > 0 ? p : thy minProb; } } if (! my notHidden) { for (long k = 1; k <= my numberOfObservationSymbols; k++) { if (my emissionProbs[is][k] > 0) { p = thy bik_num[is][k] / thy bik_denom[is][k]; my emissionProbs[is][k] = p > 0 ? p : thy minProb; } } } if (my leftToRight && my transitionProbs[is][my numberOfStates + 1] > 0) { p = thy aij_num[is][my numberOfStates + 1] / thy aij_denom[is][my numberOfStates + 1]; my transitionProbs[is][my numberOfStates + 1] = p > 0 ? p : thy minProb; } } } void HMM_and_HMM_BaumWelch_forward (HMM me, HMM_BaumWelch thee, long *obs) { // initialise at t = 1 & scale thy scale[1] = 0; for (long js = 1; js <= my numberOfStates; js++) { thy alpha[js][1] = my transitionProbs[0][js] * my emissionProbs[js][ obs[1] ]; thy scale[1] += thy alpha[js][1]; } for (long js = 1; js <= my numberOfStates; js++) { thy alpha[js][1] /= thy scale[1]; } // recursion for (long it = 2; it <= thy numberOfTimes; it++) { thy scale[it] = 0.0; for (long js = 1; js <= my numberOfStates; js++) { double sum = 0.0; for (long is = 1; is <= my numberOfStates; is++) { sum += thy alpha[is][it - 1] * my transitionProbs[is][js]; } thy alpha[js][it] = sum * my emissionProbs[js][ obs[it] ]; thy scale[it] += thy alpha[js][it]; } for (long js = 1; js <= my numberOfStates; js++) { thy alpha[js][it] /= thy scale[it]; } } for (long it = 1; it <= thy numberOfTimes; it++) { thy lnProb += log (thy scale[it]); } } void HMM_and_HMM_BaumWelch_backward (HMM me, HMM_BaumWelch thee, long *obs) { for (long is = 1; is <= my numberOfStates; is++) { thy beta[is][thy numberOfTimes] = 1.0 / thy scale[thy numberOfTimes]; } for (long it = thy numberOfTimes - 1; it >= 1; it--) { for (long is = 1; is <= my numberOfStates; is++) { double sum = 0.0; for (long js = 1; js <= my numberOfStates; js++) { sum += thy beta[js][it + 1] * my transitionProbs[is][js] * my emissionProbs[js][ obs[it + 1] ]; } thy beta[is][it] = sum / thy scale[it]; } } } /*************************** HMM decoding ***********************************/ // precondition: valid symbols, i.e. 1 <= o[i] <= my numberOfSymbols for i=1..nt void HMM_and_HMM_Viterbi_decode (HMM me, HMM_Viterbi thee, long *obs) { long ntimes = thy numberOfTimes; // initialisation for (long is = 1; is <= my numberOfStates; is++) { thy viterbi[is][1] = my transitionProbs[0][is] * my emissionProbs[is][ obs[1] ]; thy bp[is][1] = 0; } // recursion for (long it = 2; it <= ntimes; it++) { for (long is = 1; is <= my numberOfStates; is++) { // all transitions isp -> is from previous time to current double max_score = -1; // any negative number is ok for (long isp = 1; isp <= my numberOfStates; isp++) { double score = thy viterbi[isp][it - 1] * my transitionProbs[isp][is]; // * my emissionProbs[is][ obs[it] ] if (score > max_score) { max_score = score; thy bp[is][it] = isp; } } thy viterbi[is][it] = max_score * my emissionProbs[is][ obs[it] ]; } } // path starts at state with best end probability thy path[ntimes] = 1; thy prob = thy viterbi[1][ntimes]; for (long is = 2; is <= my numberOfStates; is++) { if (thy viterbi[is][ntimes] > thy prob) { thy prob = thy viterbi[ thy path[ntimes] = is ][ntimes]; } } // trace back and get path for (long it = ntimes; it > 1; it--) { thy path[it - 1] = thy bp[ thy path[it] ][it]; } } HMM_StateSequence HMM_and_HMM_ObservationSequence_to_HMM_StateSequence (HMM me, HMM_ObservationSequence thee) { try { autoStringsIndex si = HMM_and_HMM_ObservationSequence_to_StringsIndex (me, thee); long *obs = si -> classIndex; // convenience long numberOfUnknowns = StringsIndex_countItems (si.peek(), 0); if (numberOfUnknowns > 0) { Melder_throw ("Unknown observation symbol(s) (# = ", Melder_integer (numberOfUnknowns), L")."); } long numberOfTimes = thy rows -> size; autoHMM_Viterbi v = HMM_to_HMM_Viterbi (me, obs, numberOfTimes); autoHMM_StateSequence him = HMM_StateSequence_create (numberOfTimes); // trace the path and get states for (long it = 1; it <= numberOfTimes; it++) { HMM_State hmms = (HMM_State) my states -> item[ v -> path[it] ]; his strings [it] = Melder_wcsdup (hmms -> label); his numberOfStrings ++; } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no HMM_StateSequence created."); } } double HMM_and_HMM_StateSequence_getProbability (HMM me, HMM_StateSequence thee) { autoStringsIndex si = HMM_and_HMM_StateSequence_to_StringsIndex (me, thee); long numberOfUnknowns = StringsIndex_countItems (si.peek(), 0); long *index = si -> classIndex; if (index == 0) { return NUMundefined; } if (numberOfUnknowns > 0) { Melder_warning (L"Unknown states (# = ", Melder_integer (numberOfUnknowns), L")."); return NUMundefined; } double p0 = my transitionProbs [0][ index[1] ]; if (p0 == 0) { Melder_throw ("You cannot start with this state."); } double lnp = log (p0); for (long it = 2; it <= thy numberOfStrings; it++) { lnp += log (my transitionProbs[ index[it - 1] ] [ index[it] ]); } return lnp; } double HMM_getProbabilityAtTimeBeingInState (HMM me, long itime, long istate) { if (istate < 1 || istate > my numberOfStates) { return NUMundefined; } autoNUMvector scale (1, itime); autoNUMvector alpha_t (1, my numberOfStates); autoNUMvector alpha_tm1 (1, my numberOfStates); for (long js = 1; js <= my numberOfStates; js++) { alpha_t[js] = my transitionProbs[0][js]; scale[1] += alpha_t[js]; } for (long js = 1; js <= my numberOfStates; js++) { alpha_t[js] /= scale[1]; } // recursion for (long it = 2; it <= itime; it++) { for (long js = 1; js <= my numberOfStates; js++) { alpha_tm1[js] = alpha_t[js]; } for (long js = 1; js <= my numberOfStates; js++) { double sum = 0.0; for (long is = 1; is <= my numberOfStates; is++) { sum += alpha_tm1[is] * my transitionProbs[is][js]; } alpha_t[js] = sum; scale[it] += alpha_t[js]; } for (long js = 1; js <= my numberOfStates; js++) { alpha_t[js] /= scale[it]; } } double lnp = 0.0; for (long it = 1; it <= itime; it++) { lnp += log (scale[it]); } lnp = alpha_t[istate] > 0 ? lnp + log (alpha_t[istate]) : -INFINITY; // p = 0 -> ln(p)=-infinity return lnp; } double HMM_getProbabilityAtTimeBeingInStateEmittingSymbol (HMM me, long itime, long istate, long isymbol) { // for a notHidden model emissionProbs may be zero! if (isymbol < 1 || isymbol > my numberOfObservationSymbols || my emissionProbs[istate][isymbol] == 0) { return NUMundefined; } double lnp = HMM_getProbabilityAtTimeBeingInState (me, itime, istate); return lnp != NUMundefined && lnp != -INFINITY ? lnp + log (my emissionProbs[istate][isymbol]) : lnp; } double HMM_getProbabilityOfObservations (HMM me, long *obs, long numberOfTimes) { autoNUMvector scale (1, numberOfTimes); autoNUMvector alpha_t (1, my numberOfStates); autoNUMvector alpha_tm1 (1, my numberOfStates); // initialise for (long js = 1; js <= my numberOfStates; js++) { alpha_t[js] = my transitionProbs[0][js] * my emissionProbs[js][ obs[1] ]; scale[1] += alpha_t[js]; } if (scale[1] == 0) { Melder_throw ("The observation sequence starts with a symbol which state has starting probability zero."); } for (long js = 1; js <= my numberOfStates; js++) { alpha_t[js] /= scale[1]; } // recursion for (long it = 2; it <= numberOfTimes; it++) { for (long js = 1; js <= my numberOfStates; js++) { alpha_tm1[js] = alpha_t[js]; } for (long js = 1; js <= my numberOfStates; js++) { double sum = 0.0; for (long is = 1; is <= my numberOfStates; is++) { sum += alpha_tm1[is] * my transitionProbs[is][js]; } alpha_t[js] = sum * my emissionProbs[js][ obs[it] ]; scale[it] += alpha_t[js]; } if (scale[it] <= 0) { return -INFINITY; } for (long js = 1; js <= my numberOfStates; js++) { alpha_t[js] /= scale[it]; } } double lnp = 0; for (long it = 1; it <= numberOfTimes; it++) { lnp += log (scale[it]); } return lnp; } double HMM_and_HMM_ObservationSequence_getProbability (HMM me, HMM_ObservationSequence thee) { autoStringsIndex si = HMM_and_HMM_ObservationSequence_to_StringsIndex (me, thee); long *index = si -> classIndex; long numberOfUnknowns = StringsIndex_countItems (si.peek(), 0); if (numberOfUnknowns > 0) { Melder_throw ("Unknown observations (# = ", numberOfUnknowns, ")."); } return HMM_getProbabilityOfObservations (me, index, thy rows -> size); } double HMM_and_HMM_ObservationSequence_getCrossEntropy (HMM me, HMM_ObservationSequence thee) { double lnp = HMM_and_HMM_ObservationSequence_getProbability (me, thee); return lnp == NUMundefined ? NUMundefined : (lnp == -INFINITY ? INFINITY : -lnp / (NUMln10 * HMM_ObservationSequence_getNumberOfObservations (thee))); } double HMM_and_HMM_ObservationSequence_getPerplexity (HMM me, HMM_ObservationSequence thee) { double ce = HMM_and_HMM_ObservationSequence_getCrossEntropy (me, thee); return ce == NUMundefined ? NUMundefined : (ce == INFINITY ? INFINITY : pow (2, ce)); } HMM HMM_createFromHMM_ObservationSequence (HMM_ObservationSequence me, long numberOfStates, int leftToRight) { try { autoHMM thee = Thing_new (HMM); autoStrings s = HMM_ObservationSequence_to_Strings (me); autoDistributions d = Strings_to_Distributions (s.peek()); long numberOfObservationSymbols = d -> numberOfRows; thy notHidden = numberOfStates < 1; numberOfStates = numberOfStates > 0 ? numberOfStates : numberOfObservationSymbols; HMM_init (thee.peek(), numberOfStates, numberOfObservationSymbols, leftToRight); for (long i = 1; i <= numberOfObservationSymbols; i++) { const wchar_t *label = d -> rowLabels[i]; autoHMM_Observation hmmo = HMM_Observation_create (label, 0, 0, 0); HMM_addObservation (thee.peek(), hmmo.transfer()); if (thy notHidden) { autoHMM_State hmms = HMM_State_create (label); HMM_addState (thee.peek(), hmms.transfer()); } } if (! thy notHidden) { HMM_setDefaultStates (thee.peek()); } HMM_setDefaultTransitionProbs (thee.peek()); HMM_setDefaultStartProbs (thee.peek()); HMM_setDefaultEmissionProbs (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no HMM created."); } } TableOfReal HMM_ObservationSequence_to_TableOfReal_transitions (HMM_ObservationSequence me, int probabilities) { try { autoStrings thee = HMM_ObservationSequence_to_Strings (me); autoTableOfReal him = Strings_to_TableOfReal_transitions (thee.peek(), probabilities); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no transitions created."); } } StringsIndex HMM_and_HMM_ObservationSequence_to_StringsIndex (HMM me, HMM_ObservationSequence thee) { try { autoStrings classes = Thing_new (Strings); classes -> strings = NUMvector (1, my numberOfObservationSymbols); for (long is = 1; is <= my numberOfObservationSymbols; is++) { HMM_Observation hmmo = (HMM_Observation) my observationSymbols -> item[is]; classes -> strings[is] = Melder_wcsdup (hmmo -> label); (classes -> numberOfStrings) ++; } autoStrings obs = HMM_ObservationSequence_to_Strings (thee); autoStringsIndex him = Stringses_to_StringsIndex (obs.peek(), classes.peek()); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no StringsIndex created."); } } StringsIndex HMM_and_HMM_StateSequence_to_StringsIndex (HMM me, HMM_StateSequence thee) { try { autoStrings classes = Thing_new (Strings); classes -> strings = NUMvector (1, my numberOfObservationSymbols); for (long is = 1; is <= my numberOfStates; is++) { HMM_State hmms = (HMM_State) my states -> item[is]; classes -> strings[is] = Melder_wcsdup (hmms -> label); (classes -> numberOfStrings) ++; } autoStrings sts = HMM_StateSequence_to_Strings (thee); autoStringsIndex him = Stringses_to_StringsIndex (sts.peek(), classes.peek()); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no StringsIndex created."); } } TableOfReal HMM_and_HMM_ObservationSequence_to_TableOfReal_transitions (HMM me, HMM_ObservationSequence thee, int probabilities) { try { autoStringsIndex si = HMM_and_HMM_ObservationSequence_to_StringsIndex (me, thee); autoTableOfReal him = StringsIndex_to_TableOfReal_transitions (si.peek(), probabilities); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no transition table created for HMM_ObservationSequence."); } } TableOfReal HMM_and_HMM_StateSequence_to_TableOfReal_transitions (HMM me, HMM_StateSequence thee, int probabilities) { try { autoStringsIndex si = HMM_and_HMM_StateSequence_to_StringsIndex (me, thee); autoTableOfReal him = StringsIndex_to_TableOfReal_transitions (si.peek(), probabilities); return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no transition table created for HMM_StateSequence."); } } TableOfReal StringsIndex_to_TableOfReal_transitions (StringsIndex me, int probabilities) { try { long numberOfTypes = my classes -> size; autoTableOfReal thee = TableOfReal_create (numberOfTypes + 1, numberOfTypes + 1); for (long i = 1; i <= numberOfTypes; i++) { SimpleString s = (SimpleString) my classes -> item[i]; TableOfReal_setRowLabel (thee.peek(), i, s -> string); TableOfReal_setColumnLabel (thee.peek(), i, s -> string); } for (long i = 2; i <= my numberOfElements; i++) { if (my classIndex[i - 1] > 0 && my classIndex[i] > 0) { // a zero is a restart! thy data [my classIndex[i - 1]][my classIndex[i]] ++; } } double sum = 0; for (long i = 1; i <= numberOfTypes; i++) { double rowSum = 0, colSum = 0; for (long j = 1; j <= numberOfTypes; j++) { rowSum += thy data[i][j]; } thy data[i][numberOfTypes + 1] = rowSum; for (long j = 1; j <= numberOfTypes; j++) { colSum += thy data[j][i]; } thy data[numberOfTypes + 1][i] = colSum; sum += colSum; } thy data[numberOfTypes + 1][numberOfTypes + 1] = sum; if (probabilities && sum > 0) { for (long i = 1; i <= numberOfTypes; i++) { if (thy data[i][numberOfTypes + 1] > 0) { for (long j = 1; j <= numberOfTypes; j++) { thy data[i][j] /= thy data[i][numberOfTypes + 1]; } } } for (long i = 1; i <= numberOfTypes; i++) { thy data[i][numberOfTypes + 1] /= sum; thy data[numberOfTypes + 1][i] /= sum; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no transition table created."); } } TableOfReal Strings_to_TableOfReal_transitions (Strings me, int probabilities) { try { autoStringsIndex him = Strings_to_StringsIndex (me); autoTableOfReal thee = StringsIndex_to_TableOfReal_transitions (him.peek(), probabilities); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no transition table created."); } } /* End of file HMM.cpp */ sources_5316/dwtools/Excitations.cpp0000644000176700017670000000605611627236745016440 0ustar paulpaul/* Excitations.cpp * * Copyright (C) 1993-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20071009 wchar_t djmw 20071017 Melder_error djmw 20090914 getItem modified djmw 20110304 Thing_new */ #include "Excitations.h" /* static int readText (I, FILE *f) { iam (Excitations); my itemClass = classExcitation; return inherited (Ordered) readText (me, f); } static int readBinary (I, FILE *f) { iam (Excitations); my itemClass = classExcitation; return inherited (Ordered) readBinary (me, f); } */ Thing_implement (Excitations, Ordered, 0); Excitations Excitations_create (long initialCapacity) { try { autoExcitations me = Thing_new (Excitations); Ordered_init (me.peek(), classExcitation, initialCapacity); return me.transfer(); } catch (MelderError) { Melder_throw ("Excitations not created."); } } Pattern Excitations_to_Pattern (Excitations me, long join) { try { Melder_assert (my size > 0); Matrix m = (Matrix) my item[1]; if (join < 1) { join = 1; } if ( (my size % join) != 0) { Melder_throw ("Number of rows is not a multiple of join."); } autoPattern thee = Pattern_create (my size / join, join * m -> nx); long r = 0, c = 1; for (long i = 1; i <= my size; i++) { double *z = ( (Matrix) my item[i])->z[1]; if ( (i - 1) % join == 0) { r++; c = 1; } for (long j = 1; j <= m -> nx; j++) { thy z[r][c++] = z[j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Pattern created."); } } TableOfReal Excitations_to_TableOfReal (Excitations me) { try { Melder_assert (my size > 0); Matrix m = (Matrix) my item[1]; autoTableOfReal thee = TableOfReal_create (my size, m -> nx); for (long i = 1; i <= my size; i++) { double *z = ( (Matrix) my item[i]) -> z[1]; for (long j = 1; j <= m -> nx; j++) { thy data[i][j] = z[j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no TableOfReal created."); } } Excitation Excitations_getItem (Excitations me, long item) { try { if (item < 1 || item > my size) { Melder_throw ("Not a valid element number."); } autoExcitation thee = Data_copy ( (Excitation) my item[item]); Thing_setName (thee.peek(), Thing_getName ( (Thing) my item[item])); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Excitation created."); } } /* End of file Excitations.cpp */ sources_5316/stat/0000755000176700017670000000000011755137264012711 5ustar paulpaulsources_5316/stat/praat_Stat.cpp0000644000176700017670000021662411734356473015534 0ustar paulpaul/* praat_Stat.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2011/05/01 */ #include "praat.h" #include "Distributions_and_Strings.h" #include "LogisticRegression.h" #include "Matrix.h" #include "PairDistribution.h" #include "Table.h" #include "TableEditor.h" #include "UnicodeData.h" #undef iam #define iam iam_LOOP static wchar_t formatBuffer [32] [40]; static int formatIndex = 0; static wchar_t * Table_messageColumn (Table me, long column) { if (++ formatIndex == 32) formatIndex = 0; if (my columnHeaders [column]. label != NULL && my columnHeaders [column]. label [0] != '\0') swprintf (formatBuffer [formatIndex], 40, L"\"%.39ls\"", my columnHeaders [column]. label); else swprintf (formatBuffer [formatIndex], 40, L"%ld", column); return formatBuffer [formatIndex]; } /***** DISTRIBUTIONS *****/ DIRECT (Distributionses_add) autoCollection me = praat_getSelectedObjects (); autoDistributions thee = Distributions_addMany (me.peek()); praat_new (thee.transfer(), L"added"); END FORM (Distributionses_getMeanAbsoluteDifference, L"Get mean difference", 0) NATURAL (L"Column number", L"1") OK DO Distributions me = NULL, thee = NULL; LOOP { (me ? thee : me) = (Distributions) OBJECT; } Melder_informationReal (Distributionses_getMeanAbsoluteDifference (me, thee, GET_INTEGER (L"Column number")), NULL); END FORM (Distributions_getProbability, L"Get probability", 0) NATURAL (L"Column number", L"1") SENTENCE (L"String", L"") OK DO LOOP { iam (Distributions); double probability = Distributions_getProbability (me, GET_STRING (L"String"), GET_INTEGER (L"Column number")); therror Melder_informationReal (probability, NULL); } END DIRECT (Distributions_help) Melder_help (L"Distributions"); END FORM (Distributions_to_Strings, L"To Strings", 0) NATURAL (L"Column number", L"1") NATURAL (L"Number of strings", L"1000") OK DO LOOP { iam (Distributions); autoStrings thee = Distributions_to_Strings (me, GET_INTEGER (L"Column number"), GET_INTEGER (L"Number of strings")); praat_new (thee.transfer(), my name); } END FORM (Distributions_to_Strings_exact, L"To Strings (exact)", 0) NATURAL (L"Column number", L"1") OK DO LOOP { iam (Distributions); autoStrings thee = Distributions_to_Strings_exact (me, GET_INTEGER (L"Column number")); praat_new (thee.transfer(), my name); } END /***** LOGISTICREGRESSION *****/ FORM (LogisticRegression_drawBoundary, L"LogisticRegression: Draw boundary", 0) WORD (L"Horizontal factor", L"") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0 (= auto)") WORD (L"Vertical factor", L"") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0 (= auto)") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (LogisticRegression); long xfactor = Regression_getFactorIndexFromFactorName_e (me, GET_STRING (L"Horizontal factor")); therror long yfactor = Regression_getFactorIndexFromFactorName_e (me, GET_STRING (L"Vertical factor")); therror LogisticRegression_drawBoundary (me, GRAPHICS, xfactor, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), yfactor, GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_INTEGER (L"Garnish")); therror } END /***** PAIRDISTRIBUTION *****/ DIRECT (PairDistribution_getFractionCorrect_maximumLikelihood) LOOP { iam (PairDistribution); double fractionCorrect = PairDistribution_getFractionCorrect_maximumLikelihood (me); therror Melder_informationReal (fractionCorrect, NULL); } END DIRECT (PairDistribution_getFractionCorrect_probabilityMatching) LOOP { iam (PairDistribution); double fractionCorrect = PairDistribution_getFractionCorrect_probabilityMatching (me); therror Melder_informationReal (fractionCorrect, NULL); } END DIRECT (PairDistribution_getNumberOfPairs) LOOP { iam (PairDistribution); Melder_information (Melder_integer (my pairs -> size)); } END FORM (PairDistribution_getString1, L"Get string1", 0) NATURAL (L"Pair number", L"1") OK DO LOOP { iam (PairDistribution); const wchar *string1 = PairDistribution_getString1 (me, GET_INTEGER (L"Pair number")); therror Melder_information (string1); } END FORM (PairDistribution_getString2, L"Get string2", 0) NATURAL (L"Pair number", L"1") OK DO LOOP { iam (PairDistribution); const wchar *string2 = PairDistribution_getString2 (me, GET_INTEGER (L"Pair number")); therror Melder_information (string2); } END FORM (PairDistribution_getWeight, L"Get weight", 0) NATURAL (L"Pair number", L"1") OK DO LOOP { iam (PairDistribution); double weight = PairDistribution_getWeight (me, GET_INTEGER (L"Pair number")); therror Melder_information (Melder_double (weight)); } END DIRECT (PairDistribution_help) Melder_help (L"PairDistribution"); END DIRECT (PairDistribution_removeZeroWeights) LOOP { iam (PairDistribution); PairDistribution_removeZeroWeights (me); therror praat_dataChanged (me); } END FORM (PairDistribution_to_Stringses, L"Generate two Strings objects", 0) NATURAL (L"Number", L"1000") SENTENCE (L"Name of first Strings", L"input") SENTENCE (L"Name of second Strings", L"output") OK DO LOOP { iam (PairDistribution); Strings strings1_, strings2_; PairDistribution_to_Stringses (me, GET_INTEGER (L"Number"), & strings1_, & strings2_); autoStrings strings1 = strings1_, strings2 = strings2_; // UGLY praat_new (strings1.transfer(), GET_STRING (L"Name of first Strings")); praat_new (strings2.transfer(), GET_STRING (L"Name of second Strings")); } END DIRECT (PairDistribution_to_Table) LOOP { iam (PairDistribution); autoTable thee = PairDistribution_to_Table (me); praat_new (thee.transfer(), my name); } END /***** PAIRDISTRIBUTION & DISTRIBUTIONS *****/ FORM (PairDistribution_Distributions_getFractionCorrect, L"PairDistribution & Distributions: Get fraction correct", 0) NATURAL (L"Column", L"1") OK DO PairDistribution me = NULL; Distributions thee = NULL; LOOP { if (CLASS == classPairDistribution) me = (PairDistribution) OBJECT; if (CLASS == classDistributions) thee = (Distributions) OBJECT; } double fractionCorrect = PairDistribution_Distributions_getFractionCorrect (me, thee, GET_INTEGER (L"Column")); therror Melder_informationReal (fractionCorrect, NULL); END /***** TABLE *****/ DIRECT (Tables_append) autoCollection collection = Collection_create (classTable, 10); Collection_dontOwnItems (collection.peek()); LOOP { iam (Table); Collection_addItem (collection.peek(), me); } autoTable thee = Tables_append (collection.peek()); praat_new (thee.transfer(), L"appended"); END FORM (Table_appendColumn, L"Table: Append column", 0) WORD (L"Label", L"newcolumn") OK DO LOOP { iam (Table); Table_appendColumn (me, GET_STRING (L"Label")); therror praat_dataChanged (OBJECT); } END FORM (Table_appendDifferenceColumn, L"Table: Append difference column", 0) WORD (L"left Columns", L"") WORD (L"right Columns", L"") WORD (L"Label", L"diff") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"left Columns")); therror long jcol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"right Columns")); therror Table_appendDifferenceColumn (me, icol, jcol, GET_STRING (L"Label")); therror praat_dataChanged (me); } END FORM (Table_appendProductColumn, L"Table: Append product column", 0) WORD (L"left Columns", L"") WORD (L"right Columns", L"") WORD (L"Label", L"diff") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"left Columns")); therror long jcol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"right Columns")); therror Table_appendProductColumn (me, icol, jcol, GET_STRING (L"Label")); therror praat_dataChanged (me); } END FORM (Table_appendQuotientColumn, L"Table: Append quotient column", 0) WORD (L"left Columns", L"") WORD (L"right Columns", L"") WORD (L"Label", L"diff") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"left Columns")); therror long jcol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"right Columns")); therror Table_appendQuotientColumn (me, icol, jcol, GET_STRING (L"Label")); therror praat_dataChanged (me); } END FORM (Table_appendSumColumn, L"Table: Append sum column", 0) WORD (L"left Columns", L"") WORD (L"right Columns", L"") WORD (L"Label", L"diff") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"left Columns")); therror long jcol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"right Columns")); therror Table_appendSumColumn (me, icol, jcol, GET_STRING (L"Label")); therror praat_dataChanged (me); } END DIRECT (Table_appendRow) LOOP { iam (Table); Table_appendRow (me); praat_dataChanged (me); } END FORM (Table_collapseRows, L"Table: Collapse rows", 0) LABEL (L"", L"Columns with factors (independent variables):") TEXTFIELD (L"factors", L"speaker dialect age vowel") LABEL (L"", L"Columns to sum:") TEXTFIELD (L"columnsToSum", L"number cost") LABEL (L"", L"Columns to average:") TEXTFIELD (L"columnsToAverage", L"price") LABEL (L"", L"Columns to medianize:") TEXTFIELD (L"columnsToMedianize", L"vot") LABEL (L"", L"Columns to average logarithmically:") TEXTFIELD (L"columnsToAverageLogarithmically", L"duration") LABEL (L"", L"Columns to medianize logarithmically:") TEXTFIELD (L"columnsToMedianizeLogarithmically", L"F0 F1 F2 F3") LABEL (L"", L"Columns not mentioned above will be ignored.") OK DO LOOP { iam (Table); autoTable thee = Table_collapseRows (me, GET_STRING (L"factors"), GET_STRING (L"columnsToSum"), GET_STRING (L"columnsToAverage"), GET_STRING (L"columnsToMedianize"), GET_STRING (L"columnsToAverageLogarithmically"), GET_STRING (L"columnsToMedianizeLogarithmically")); praat_new (thee.transfer(), my name, L"_pooled"); } END FORM (Table_createWithColumnNames, L"Create Table with column names", 0) WORD (L"Name", L"table") INTEGER (L"Number of rows", L"10") LABEL (L"", L"Column names:") TEXTFIELD (L"columnNames", L"speaker dialect age vowel F0 F1 F2") OK DO autoTable me = Table_createWithColumnNames (GET_INTEGER (L"Number of rows"), GET_STRING (L"columnNames")); praat_new (me.transfer(), GET_STRING (L"Name")); END FORM (Table_createWithoutColumnNames, L"Create Table without column names", 0) WORD (L"Name", L"table") INTEGER (L"Number of rows", L"10") NATURAL (L"Number of columns", L"3") OK DO autoTable me = Table_createWithoutColumnNames (GET_INTEGER (L"Number of rows"), GET_INTEGER (L"Number of columns")); praat_new (me.transfer(), GET_STRING (L"Name")); END FORM (Table_drawEllipse, L"Draw ellipse (standard deviation)", 0) WORD (L"Horizontal column", L"") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0 (= auto)") WORD (L"Vertical column", L"") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0 (= auto)") POSITIVE (L"Number of sigmas", L"2.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Table); long xcolumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Horizontal column")); therror long ycolumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Vertical column")); therror Table_drawEllipse_e (me, GRAPHICS, xcolumn, ycolumn, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Number of sigmas"), GET_INTEGER (L"Garnish")); therror } END FORM (Table_drawRowFromDistribution, L"Table: Draw row from distribution", 0) WORD (L"Column with distribution", L"") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column with distribution")); therror long row = Table_drawRowFromDistribution (me, icol); therror Melder_information (Melder_integer (row)); } END DIRECT (Table_edit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot edit a Table from batch."); LOOP { iam (Table); autoTableEditor editor = TableEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); praat_installEditor (editor.transfer(), IOBJECT); therror } END FORM (Table_extractRowsWhereColumn_number, L"Table: Extract rows where column (number)", 0) WORD (L"Extract all rows where column...", L"") RADIO_ENUM (L"...is...", kMelder_number, DEFAULT) REAL (L"...the number", L"0.0") OK DO double value = GET_REAL (L"...the number"); LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Extract all rows where column...")); therror autoTable thee = Table_extractRowsWhereColumn_number (me, icol, GET_ENUM (kMelder_number, L"...is..."), value); praat_new (thee.transfer(), my name, L"_", Table_messageColumn (static_cast OBJECT, icol), L"_", NUMdefined (value) ? Melder_integer ((long) round (value)) : L"undefined"); praat_dataChanged (me); // WHY? } END FORM (Table_extractRowsWhereColumn_text, L"Table: Extract rows where column (text)", 0) WORD (L"Extract all rows where column...", L"") OPTIONMENU_ENUM (L"...", kMelder_string, DEFAULT) SENTENCE (L"...the text", L"hi") OK DO const wchar_t *value = GET_STRING (L"...the text"); LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Extract all rows where column...")); therror autoTable thee = Table_extractRowsWhereColumn_string (me, icol, GET_ENUM (kMelder_string, L"..."), value); praat_new (thee.transfer(), my name, L"_", value); praat_dataChanged (me); // WHY? } END FORM (Table_formula, L"Table: Formula", L"Table: Formula...") WORD (L"Column label", L"") TEXTFIELD (L"formula", L"abs (self)") OK DO LOOP { iam (Table); try { long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror Table_formula (me, icol, GET_STRING (L"formula"), interpreter); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); // in case of error, the Table may have partially changed throw; } } END FORM (Table_formula_columnRange, L"Table: Formula (column range)", L"Table: Formula...") WORD (L"From column label", L"") WORD (L"To column label", L"") TEXTFIELD (L"formula", L"log10 (self)") OK DO LOOP { iam (Table); try { long icol1 = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"From column label")); therror long icol2 = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"To column label")); therror Table_formula_columnRange (me, icol1, icol2, GET_STRING (L"formula"), interpreter); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); // in case of error, the Table may have partially changed throw; } } END FORM (Table_getColumnIndex, L"Table: Get column index", 0) SENTENCE (L"Column label", L"") OK DO LOOP { iam (Table); Melder_information (Melder_integer (Table_findColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")))); } END FORM (Table_getColumnLabel, L"Table: Get column label", 0) NATURAL (L"Column number", L"1") OK DO LOOP { iam (Table); long icol = GET_INTEGER (L"Column number"); if (icol > my numberOfColumns) Melder_throw ("Column number must not be greater than number of columns."); Melder_information (my columnHeaders [icol]. label); } END FORM (Table_getGroupMean, L"Table: Get group mean", 0) WORD (L"Column label", L"salary") WORD (L"Group column", L"gender") SENTENCE (L"Group", L"F") OK DO LOOP { iam (Table); long column = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror long groupColumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Group column")); therror Melder_information (Melder_double (Table_getGroupMean (static_cast
ONLY_OBJECT, column, groupColumn, GET_STRING (L"Group")))); } END FORM (Table_getMaximum, L"Table: Get maximum", 0) SENTENCE (L"Column label", L"") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror double maximum = Table_getMaximum (me, icol); therror Melder_information (Melder_double (maximum)); } END FORM (Table_getMean, L"Table: Get mean", 0) SENTENCE (L"Column label", L"") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror double mean = Table_getMean (me, icol); therror Melder_information (Melder_double (mean)); } END FORM (Table_getMinimum, L"Table: Get minimum", 0) SENTENCE (L"Column label", L"") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror double minimum = Table_getMinimum (me, icol); therror Melder_information (Melder_double (minimum)); } END FORM (Table_getQuantile, L"Table: Get quantile", 0) SENTENCE (L"Column label", L"") POSITIVE (L"Quantile", L"0.50 (= median)") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror double quantile = Table_getQuantile (me, icol, GET_REAL (L"Quantile")); therror Melder_information (Melder_double (quantile)); } END FORM (Table_getStandardDeviation, L"Table: Get standard deviation", 0) SENTENCE (L"Column label", L"") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror double stdev = Table_getStdev (me, icol); therror Melder_information (Melder_double (stdev)); } END DIRECT (Table_getNumberOfColumns) LOOP { iam (Table); Melder_information (Melder_integer (my numberOfColumns)); } END DIRECT (Table_getNumberOfRows) LOOP { iam (Table); Melder_information (Melder_integer (my rows -> size)); } END FORM (Table_getValue, L"Table: Get value", 0) NATURAL (L"Row number", L"1") WORD (L"Column label", L"") OK DO LOOP { iam (Table); long rowNumber = GET_INTEGER (L"Row number"); Table_checkSpecifiedRowNumberWithinRange (me, rowNumber); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror Melder_information (((TableRow) my rows -> item [rowNumber]) -> cells [icol]. string); } END DIRECT (Table_help) Melder_help (L"Table"); END FORM (Table_insertColumn, L"Table: Insert column", 0) NATURAL (L"Position", L"1") WORD (L"Label", L"newcolumn") OK DO LOOP { iam (Table); Table_insertColumn (me, GET_INTEGER (L"Position"), GET_STRING (L"Label")); therror praat_dataChanged (me); } END FORM (Table_insertRow, L"Table: Insert row", 0) NATURAL (L"Position", L"1") OK DO LOOP { iam (Table); Table_insertRow (me, GET_INTEGER (L"Position")); therror praat_dataChanged (me); } END FORM (Table_list, L"Table: List", 0) BOOLEAN (L"Include row numbers", true) OK DO LOOP { iam (Table); Table_list (me, GET_INTEGER (L"Include row numbers")); } END FORM_READ (Table_readFromTableFile, L"Read Table from table file", 0, true) praat_newWithFile (Table_readFromTableFile (file), MelderFile_name (file), file); END FORM_READ (Table_readFromCommaSeparatedFile, L"Read Table from comma-separated file", 0, true) praat_newWithFile (Table_readFromCharacterSeparatedTextFile (file, ','), MelderFile_name (file), file); END FORM_READ (Table_readFromTabSeparatedFile, L"Read Table from tab-separated file", 0, true) praat_newWithFile (Table_readFromCharacterSeparatedTextFile (file, '\t'), MelderFile_name (file), file); END FORM (Table_removeColumn, L"Table: Remove column", 0) WORD (L"Column label", L"") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror Table_removeColumn (me, icol); therror praat_dataChanged (me); } END FORM (Table_removeRow, L"Table: Remove row", 0) NATURAL (L"Row number", L"1") OK DO LOOP { iam (Table); Table_removeRow (me, GET_INTEGER (L"Row number")); therror praat_dataChanged (me); } END FORM (Table_reportCorrelation_kendallTau, L"Report correlation (Kendall tau)", 0) WORD (L"left Columns", L"") WORD (L"right Columns", L"") POSITIVE (L"One-tailed unconfidence", L"0.025") OK DO LOOP { iam (Table); long column1 = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"left Columns")); therror long column2 = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"right Columns")); therror double unconfidence = GET_REAL (L"One-tailed unconfidence"); double correlation, significance, lowerLimit, upperLimit; correlation = Table_getCorrelation_kendallTau (me, column1, column2, unconfidence, & significance, & lowerLimit, & upperLimit); MelderInfo_open (); MelderInfo_writeLine5 (L"Correlation between column ", Table_messageColumn (me, column1), L" and column ", Table_messageColumn (me, column2), L":"); MelderInfo_writeLine3 (L"Correlation = ", Melder_double (correlation), L" (Kendall's tau-b)"); MelderInfo_writeLine3 (L"Significance from zero = ", Melder_double (significance), L" (one-tailed)"); MelderInfo_writeLine3 (L"Confidence interval (", Melder_double (100 * (1.0 - 2.0 * unconfidence)), L"%):"); MelderInfo_writeLine5 (L" Lower limit = ", Melder_double (lowerLimit), L" (lowest tau that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_writeLine5 (L" Upper limit = ", Melder_double (upperLimit), L" (highest tau that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_close (); } END FORM (Table_reportCorrelation_pearsonR, L"Report correlation (Pearson r)", 0) WORD (L"left Columns", L"") WORD (L"right Columns", L"") POSITIVE (L"One-tailed unconfidence", L"0.025") OK DO LOOP { iam (Table); long column1 = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"left Columns")); therror long column2 = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"right Columns")); therror double unconfidence = GET_REAL (L"One-tailed unconfidence"); double correlation, significance, lowerLimit, upperLimit; correlation = Table_getCorrelation_pearsonR (me, column1, column2, unconfidence, & significance, & lowerLimit, & upperLimit); MelderInfo_open (); MelderInfo_writeLine5 (L"Correlation between column ", Table_messageColumn (me, column1), L" and column ", Table_messageColumn (me, column2), L":"); MelderInfo_writeLine3 (L"Correlation = ", Melder_double (correlation), L" (Pearson's r)"); MelderInfo_writeLine2 (L"Number of degrees of freedom = ", Melder_integer (my rows -> size - 2)); MelderInfo_writeLine3 (L"Significance from zero = ", Melder_double (significance), L" (one-tailed)"); MelderInfo_writeLine3 (L"Confidence interval (", Melder_double (100 * (1.0 - 2.0 * unconfidence)), L"%):"); MelderInfo_writeLine5 (L" Lower limit = ", Melder_double (lowerLimit), L" (lowest r that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_writeLine5 (L" Upper limit = ", Melder_double (upperLimit), L" (highest r that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_close (); } END FORM (Table_reportDifference_studentT, L"Report difference (Student t)", 0) WORD (L"left Columns", L"") WORD (L"right Columns", L"") POSITIVE (L"One-tailed unconfidence", L"0.025") OK DO LOOP { iam (Table); long column1 = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"left Columns")); therror long column2 = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"right Columns")); therror double unconfidence = GET_REAL (L"One-tailed unconfidence"); double difference, t, numberOfDegreesOfFreedom, significance, lowerLimit, upperLimit; difference = Table_getDifference_studentT (me, column1, column2, unconfidence, & t, & numberOfDegreesOfFreedom, & significance, & lowerLimit, & upperLimit); MelderInfo_open (); MelderInfo_writeLine5 (L"Difference between column ", Table_messageColumn (me, column1), L" and column ", Table_messageColumn (me, column2), L":"); MelderInfo_writeLine2 (L"Difference = ", Melder_double (difference)); MelderInfo_writeLine2 (L"Student's t = ", Melder_double (t)); MelderInfo_writeLine2 (L"Number of degrees of freedom = ", Melder_double (numberOfDegreesOfFreedom)); MelderInfo_writeLine3 (L"Significance from zero = ", Melder_double (significance), L" (one-tailed)"); MelderInfo_writeLine3 (L"Confidence interval (", Melder_double (100 * (1.0 - 2.0 * unconfidence)), L"%):"); MelderInfo_writeLine5 (L" Lower limit = ", Melder_double (lowerLimit), L" (lowest difference that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_writeLine5 (L" Upper limit = ", Melder_double (upperLimit), L" (highest difference that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_close (); } END FORM (Table_reportGroupDifference_studentT, L"Report group difference (Student t)", 0) WORD (L"Column", L"salary") WORD (L"Group column", L"gender") SENTENCE (L"Group 1", L"F") SENTENCE (L"Group 2", L"M") POSITIVE (L"One-tailed unconfidence", L"0.025") OK DO LOOP { iam (Table); long column = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column")); therror long groupColumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Group column")); therror double unconfidence = GET_REAL (L"One-tailed unconfidence"); wchar_t *group1 = GET_STRING (L"Group 1"), *group2 = GET_STRING (L"Group 2"); double mean, tFromZero, numberOfDegreesOfFreedom, significanceFromZero, lowerLimit, upperLimit; mean = Table_getGroupDifference_studentT (me, column, groupColumn, group1, group2, unconfidence, & tFromZero, & numberOfDegreesOfFreedom, & significanceFromZero, & lowerLimit, & upperLimit); MelderInfo_open (); MelderInfo_write4 (L"Difference in column ", Table_messageColumn (me, column), L" between groups ", group1); MelderInfo_writeLine5 (L" and ", group2, L" of column ", Table_messageColumn (me, groupColumn), L":"); MelderInfo_writeLine2 (L"Difference = ", Melder_double (mean)); MelderInfo_writeLine2 (L"Student's t = ", Melder_double (tFromZero)); MelderInfo_writeLine2 (L"Number of degrees of freedom = ", Melder_double (numberOfDegreesOfFreedom)); MelderInfo_writeLine3 (L"Significance from zero = ", Melder_double (significanceFromZero), L" (one-tailed)"); MelderInfo_writeLine3 (L"Confidence interval (", Melder_double (100 * (1.0 - 2.0 * unconfidence)), L"%):"); MelderInfo_writeLine5 (L" Lower limit = ", Melder_double (lowerLimit), L" (lowest difference that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_writeLine5 (L" Upper limit = ", Melder_double (upperLimit), L" (highest difference that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_close (); } END FORM (Table_reportGroupDifference_wilcoxonRankSum, L"Report group difference (Wilcoxon rank sum)", 0) WORD (L"Column", L"salary") WORD (L"Group column", L"gender") SENTENCE (L"Group 1", L"F") SENTENCE (L"Group 2", L"M") OK DO LOOP { iam (Table); long column = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column")); therror long groupColumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Group column")); therror wchar_t *group1 = GET_STRING (L"Group 1"), *group2 = GET_STRING (L"Group 2"); double areaUnderCurve, rankSum, significanceFromZero; areaUnderCurve = Table_getGroupDifference_wilcoxonRankSum (me, column, groupColumn, group1, group2, & rankSum, & significanceFromZero); MelderInfo_open (); MelderInfo_write4 (L"Difference in column ", Table_messageColumn (me, column), L" between groups ", group1); MelderInfo_writeLine5 (L" and ", group2, L" of column ", Table_messageColumn (me, groupColumn), L":"); MelderInfo_writeLine2 (L"Larger: ", areaUnderCurve < 0.5 ? group1 : areaUnderCurve > 0.5 ? group2 : L"(both equal)"); MelderInfo_writeLine2 (L"Area under curve: ", Melder_double (areaUnderCurve)); MelderInfo_writeLine2 (L"Rank sum: ", Melder_double (rankSum)); MelderInfo_writeLine3 (L"Significance from zero: ", Melder_double (significanceFromZero), L" (one-tailed)"); MelderInfo_close (); } END FORM (Table_reportGroupMean_studentT, L"Report group mean (Student t)", 0) WORD (L"Column", L"salary") WORD (L"Group column", L"gender") SENTENCE (L"Group", L"F") POSITIVE (L"One-tailed unconfidence", L"0.025") OK DO LOOP { iam (Table); long column = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column")); therror long groupColumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Group column")); therror double unconfidence = GET_REAL (L"One-tailed unconfidence"); wchar_t *group = GET_STRING (L"Group"); double mean, tFromZero, numberOfDegreesOfFreedom, significanceFromZero, lowerLimit, upperLimit; mean = Table_getGroupMean_studentT (me, column, groupColumn, group, unconfidence, & tFromZero, & numberOfDegreesOfFreedom, & significanceFromZero, & lowerLimit, & upperLimit); MelderInfo_open (); MelderInfo_write4 (L"Mean in column ", Table_messageColumn (me, column), L" of group ", group); MelderInfo_writeLine3 (L" of column ", Table_messageColumn (me, groupColumn), L":"); MelderInfo_writeLine2 (L"Mean = ", Melder_double (mean)); MelderInfo_writeLine2 (L"Student's t from zero = ", Melder_double (tFromZero)); MelderInfo_writeLine2 (L"Number of degrees of freedom = ", Melder_double (numberOfDegreesOfFreedom)); MelderInfo_writeLine3 (L"Significance from zero = ", Melder_double (significanceFromZero), L" (one-tailed)"); MelderInfo_writeLine3 (L"Confidence interval (", Melder_double (100 * (1.0 - 2.0 * unconfidence)), L"%):"); MelderInfo_writeLine5 (L" Lower limit = ", Melder_double (lowerLimit), L" (lowest difference that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_writeLine5 (L" Upper limit = ", Melder_double (upperLimit), L" (highest difference that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_close (); } END FORM (Table_reportMean_studentT, L"Report mean (Student t)", 0) WORD (L"Column", L"") POSITIVE (L"One-tailed unconfidence", L"0.025") OK DO LOOP { iam (Table); long column = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column")); therror double unconfidence = GET_REAL (L"One-tailed unconfidence"); double mean, tFromZero, numberOfDegreesOfFreedom, significanceFromZero, lowerLimit, upperLimit; mean = Table_getMean_studentT (me, column, unconfidence, & tFromZero, & numberOfDegreesOfFreedom, & significanceFromZero, & lowerLimit, & upperLimit); MelderInfo_open (); MelderInfo_writeLine3 (L"Mean of column ", Table_messageColumn (me, column), L":"); MelderInfo_writeLine2 (L"Mean = ", Melder_double (mean)); MelderInfo_writeLine2 (L"Student's t from zero = ", Melder_double (tFromZero)); MelderInfo_writeLine2 (L"Number of degrees of freedom = ", Melder_double (numberOfDegreesOfFreedom)); MelderInfo_writeLine3 (L"Significance from zero = ", Melder_double (significanceFromZero), L" (one-tailed)"); MelderInfo_writeLine3 (L"Confidence interval (", Melder_double (100 * (1.0 - 2.0 * unconfidence)), L"%):"); MelderInfo_writeLine5 (L" Lower limit = ", Melder_double (lowerLimit), L" (lowest value that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_writeLine5 (L" Upper limit = ", Melder_double (upperLimit), L" (highest value that cannot be rejected with " UNITEXT_GREEK_SMALL_LETTER_ALPHA " = ", Melder_double (unconfidence), L")"); MelderInfo_close (); } END FORM (Table_rowsToColumns, L"Table: Rows to columns", 0) LABEL (L"", L"Columns with factors (independent variables):") TEXTFIELD (L"factors", L"dialect gender speaker") WORD (L"Column to transpose", L"vowel") LABEL (L"", L"Columns to expand:") TEXTFIELD (L"columnsToExpand", L"duration F0 F1 F2 F3") LABEL (L"", L"Columns not mentioned above will be ignored.") OK DO const wchar_t *columnLabel = GET_STRING (L"Column to transpose"); LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, columnLabel); therror autoTable thee = Table_rowsToColumns (me, GET_STRING (L"factors"), icol, GET_STRING (L"columnsToExpand")); praat_new (thee.transfer(), NAME, L"_nested"); } END FORM (Table_scatterPlot, L"Scatter plot", 0) WORD (L"Horizontal column", L"") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0 (= auto)") WORD (L"Vertical column", L"") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0 (= auto)") WORD (L"Column with marks", L"") NATURAL (L"Font size", L"12") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Table); long xcolumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Horizontal column")); therror long ycolumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Vertical column")); therror long markColumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column with marks")); therror Table_scatterPlot (me, GRAPHICS, xcolumn, ycolumn, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), markColumn, GET_INTEGER (L"Font size"), GET_INTEGER (L"Garnish")); } END FORM (Table_scatterPlot_mark, L"Scatter plot (marks)", 0) WORD (L"Horizontal column", L"") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0 (= auto)") WORD (L"Vertical column", L"") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0 (= auto)") POSITIVE (L"Mark size (mm)", L"1.0") BOOLEAN (L"Garnish", 1) SENTENCE (L"Mark string (+xo.)", L"+") OK DO autoPraatPicture picture; LOOP { iam (Table); long xcolumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Horizontal column")); therror long ycolumn = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Vertical column")); therror Table_scatterPlot_mark (me, GRAPHICS, xcolumn, ycolumn, GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range"), GET_REAL (L"Mark size"), GET_STRING (L"Mark string"), GET_INTEGER (L"Garnish")); } END FORM (Table_searchColumn, L"Table: Search column", 0) WORD (L"Column label", L"") WORD (L"Value", L"") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror Melder_information (Melder_integer (Table_searchColumn (me, icol, GET_STRING (L"Value")))); } END FORM (Table_setColumnLabel_index, L"Set column label", 0) NATURAL (L"Column number", L"1") SENTENCE (L"Label", L"") OK DO LOOP { iam (Table); Table_setColumnLabel (me, GET_INTEGER (L"Column number"), GET_STRING (L"Label")); therror praat_dataChanged (me); } END FORM (Table_setColumnLabel_label, L"Set column label", 0) SENTENCE (L"Old label", L"") SENTENCE (L"New label", L"") OK DO LOOP { iam (Table); Table_setColumnLabel (me, Table_findColumnIndexFromColumnLabel (me, GET_STRING (L"Old label")), GET_STRING (L"New label")); therror praat_dataChanged (me); } END FORM (Table_setNumericValue, L"Table: Set numeric value", 0) NATURAL (L"Row number", L"1") WORD (L"Column label", L"") REAL_OR_UNDEFINED (L"Numeric value", L"1.5") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror Table_setNumericValue (me, GET_INTEGER (L"Row number"), icol, GET_REAL (L"Numeric value")); therror praat_dataChanged (me); } END FORM (Table_setStringValue, L"Table: Set string value", 0) NATURAL (L"Row number", L"1") WORD (L"Column label", L"") SENTENCE (L"String value", L"xx") OK DO LOOP { iam (Table); long icol = Table_getColumnIndexFromColumnLabel (me, GET_STRING (L"Column label")); therror Table_setStringValue (me, GET_INTEGER (L"Row number"), icol, GET_STRING (L"String value")); therror praat_dataChanged (me); } END DIRECT (Table_randomizeRows) LOOP { iam (Table); Table_randomizeRows (me); praat_dataChanged (me); } END FORM (Table_sortRows, L"Table: Sort rows", 0) LABEL (L"", L"One or more column labels for sorting:") TEXTFIELD (L"columnLabels", L"dialect gender name") OK DO LOOP { iam (Table); Table_sortRows_string (me, GET_STRING (L"columnLabels")); therror praat_dataChanged (me); } END DIRECT (Table_to_LinearRegression) LOOP { iam (Table); autoLinearRegression thee = Table_to_LinearRegression (me); praat_new (thee.transfer(), NAME); } END FORM (Table_to_LogisticRegression, L"Table: To LogisticRegression", 0) LABEL (L"", L"Factors (column names):") TEXTFIELD (L"factors", L"F0 F1 duration") WORD (L"Dependent 1 (column name)", L"e") WORD (L"Dependent 2 (column name)", L"i") OK DO LOOP { iam (Table); autoLogisticRegression thee = Table_to_LogisticRegression (me, GET_STRING (L"factors"), GET_STRING (L"Dependent 1"), GET_STRING (L"Dependent 2")); praat_new (thee.transfer(), NAME); } END FORM (Table_to_TableOfReal, L"Table: Down to TableOfReal", 0) WORD (L"Column for row labels", L"") OK DO LOOP { iam (Table); long icol = Table_findColumnIndexFromColumnLabel (me, GET_STRING (L"Column for row labels")); therror autoTableOfReal thee = Table_to_TableOfReal (me, icol); praat_new (thee.transfer(), NAME); } END FORM_WRITE (Table_writeToCommaSeparatedFile, L"Save Table as comma-separated file", 0, L"Table") LOOP { iam (Table); Table_writeToCommaSeparatedFile (me, file); therror } END FORM_WRITE (Table_writeToTabSeparatedFile, L"Save Table as tab-separated file", 0, L"Table") LOOP { iam (Table); Table_writeToTabSeparatedFile (me, file); therror } END /***** TABLEOFREAL *****/ DIRECT (TablesOfReal_append) autoCollection tables = Collection_create (classTableOfReal, 10); Collection_dontOwnItems (tables.peek()); LOOP { iam (TableOfReal); Collection_addItem (tables.peek(), me); } autoTableOfReal thee = static_cast (TablesOfReal_appendMany (tables.peek())); praat_new (thee.transfer(), L"appended"); END FORM (TableOfReal_create, L"Create TableOfReal", 0) WORD (L"Name", L"table") NATURAL (L"Number of rows", L"10") NATURAL (L"Number of columns", L"3") OK DO autoTableOfReal me = TableOfReal_create (GET_INTEGER (L"Number of rows"), GET_INTEGER (L"Number of columns")); praat_new (me.transfer(), GET_STRING (L"Name")); END FORM (TableOfReal_drawAsNumbers, L"Draw as numbers", 0) NATURAL (L"From row", L"1") INTEGER (L"To row", L"0 (= all)") RADIO (L"Format", 3) RADIOBUTTON (L"decimal") RADIOBUTTON (L"exponential") RADIOBUTTON (L"free") RADIOBUTTON (L"rational") NATURAL (L"Precision", L"5") OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawAsNumbers (me, GRAPHICS, GET_INTEGER (L"From row"), GET_INTEGER (L"To row"), GET_INTEGER (L"Format"), GET_INTEGER (L"Precision")); } END FORM (TableOfReal_drawAsNumbers_if, L"Draw as numbers if...", 0) NATURAL (L"From row", L"1") INTEGER (L"To row", L"0 (= all)") RADIO (L"Format", 3) RADIOBUTTON (L"decimal") RADIOBUTTON (L"exponential") RADIOBUTTON (L"free") RADIOBUTTON (L"rational") NATURAL (L"Precision", L"5") LABEL (L"", L"Condition:") TEXTFIELD (L"condition", L"self <> 0") OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawAsNumbers_if (me, GRAPHICS, GET_INTEGER (L"From row"), GET_INTEGER (L"To row"), GET_INTEGER (L"Format"), GET_INTEGER (L"Precision"), GET_STRING (L"condition"), interpreter); } END FORM (TableOfReal_drawAsSquares, L"Draw table as squares", 0) INTEGER (L"From row", L"1") INTEGER (L"To row", L"0") INTEGER (L"From column", L"1") INTEGER (L"To column", L"0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawAsSquares (me, GRAPHICS, GET_INTEGER (L"From row"), GET_INTEGER (L"To row"), GET_INTEGER (L"From column"), GET_INTEGER (L"To column"), GET_INTEGER (L"Garnish")); } END FORM (TableOfReal_drawHorizontalLines, L"Draw horizontal lines", 0) NATURAL (L"From row", L"1") INTEGER (L"To row", L"0 (= all)") OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawHorizontalLines (me, GRAPHICS, GET_INTEGER (L"From row"), GET_INTEGER (L"To row")); } END FORM (TableOfReal_drawLeftAndRightLines, L"Draw left and right lines", 0) NATURAL (L"From row", L"1") INTEGER (L"To row", L"0 (= all)") OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawLeftAndRightLines (me, GRAPHICS, GET_INTEGER (L"From row"), GET_INTEGER (L"To row")); } END FORM (TableOfReal_drawTopAndBottomLines, L"Draw top and bottom lines", 0) NATURAL (L"From row", L"1") INTEGER (L"To row", L"0 (= all)") OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawTopAndBottomLines (me, GRAPHICS, GET_INTEGER (L"From row"), GET_INTEGER (L"To row")); } END FORM (TableOfReal_drawVerticalLines, L"Draw vertical lines", 0) NATURAL (L"From row", L"1") INTEGER (L"To row", L"0 (= all)") OK DO autoPraatPicture picture; LOOP { iam (TableOfReal); TableOfReal_drawVerticalLines (me, GRAPHICS, GET_INTEGER (L"From row"), GET_INTEGER (L"To row")); } END DIRECT (TableOfReal_extractColumnLabelsAsStrings) LOOP { iam (TableOfReal); autoStrings thee = TableOfReal_extractColumnLabelsAsStrings (me); praat_new (thee.transfer(), my name); } END FORM (TableOfReal_extractColumnRanges, L"Extract column ranges", 0) LABEL (L"", L"Create a new TableOfReal from the following columns:") TEXTFIELD (L"ranges", L"1 2") LABEL (L"", L"To supply rising or falling ranges, use e.g. 2:6 or 5:3.") OK DO LOOP { iam (TableOfReal); autoTableOfReal thee = TableOfReal_extractColumnRanges (me, GET_STRING (L"ranges")); praat_new (thee.transfer(), my name, L"_cols"); } END FORM (TableOfReal_extractColumnsWhere, L"Extract columns where", 0) LABEL (L"", L"Extract all columns with at least one cell where:") TEXTFIELD (L"condition", L"col mod 3 = 0 ; this example extracts every third column") OK DO LOOP { iam (TableOfReal); autoTableOfReal thee = TableOfReal_extractColumnsWhere (me, GET_STRING (L"condition"), interpreter); praat_new (thee.transfer(), my name, L"_cols"); } END FORM (TableOfReal_extractColumnsWhereLabel, L"Extract column where label", 0) OPTIONMENU_ENUM (L"Extract all columns whose label...", kMelder_string, DEFAULT) SENTENCE (L"...the text", L"a") OK DO const wchar_t *text = GET_STRING (L"...the text"); LOOP { iam (TableOfReal); autoTableOfReal thee = TableOfReal_extractColumnsWhereLabel (me, GET_ENUM (kMelder_string, L"Extract all columns whose label..."), text); praat_new (thee.transfer(), my name, L"_", text); } END FORM (TableOfReal_extractColumnsWhereRow, L"Extract columns where row", 0) NATURAL (L"Extract all columns where row...", L"1") OPTIONMENU_ENUM (L"...is...", kMelder_number, DEFAULT) REAL (L"...the value", L"0.0") OK DO long row = GET_INTEGER (L"Extract all columns where row..."); double value = GET_REAL (L"...the value"); LOOP { iam (TableOfReal); autoTableOfReal thee = TableOfReal_extractColumnsWhereRow (me, row, GET_ENUM (kMelder_number, L"...is..."), value); praat_new (thee.transfer(), my name, L"_", Melder_integer (row), L"_", Melder_integer (round (value))); } END DIRECT (TableOfReal_extractRowLabelsAsStrings) LOOP { iam (TableOfReal); autoStrings thee = TableOfReal_extractRowLabelsAsStrings (me); praat_new (thee.transfer(), my name); } END FORM (TableOfReal_extractRowRanges, L"Extract row ranges", 0) LABEL (L"", L"Create a new TableOfReal from the following rows:") TEXTFIELD (L"ranges", L"1 2") LABEL (L"", L"To supply rising or falling ranges, use e.g. 2:6 or 5:3.") OK DO LOOP { iam (TableOfReal); autoTableOfReal thee = TableOfReal_extractRowRanges (me, GET_STRING (L"ranges")); praat_new (thee.transfer(), my name, L"_rows"); } END FORM (TableOfReal_extractRowsWhere, L"Extract rows where", 0) LABEL (L"", L"Extract all rows with at least one cell where:") TEXTFIELD (L"condition", L"row mod 3 = 0 ; this example extracts every third row") OK DO LOOP { iam (TableOfReal); autoTableOfReal thee = TableOfReal_extractRowsWhere (me, GET_STRING (L"condition"), interpreter); praat_new (thee.transfer(), my name, L"_rows"); } END FORM (TableOfReal_extractRowsWhereColumn, L"Extract rows where column", 0) NATURAL (L"Extract all rows where column...", L"1") OPTIONMENU_ENUM (L"...is...", kMelder_number, DEFAULT) REAL (L"...the value", L"0.0") OK DO long column = GET_INTEGER (L"Extract all rows where column..."); double value = GET_REAL (L"...the value"); LOOP { iam (TableOfReal); autoTableOfReal thee = TableOfReal_extractRowsWhereColumn (me, column, GET_ENUM (kMelder_number, L"...is..."), value); praat_new (thee.transfer(), my name, L"_", Melder_integer (column), L"_", Melder_integer (round (value))); } END FORM (TableOfReal_extractRowsWhereLabel, L"Extract rows where label", 0) OPTIONMENU_ENUM (L"Extract all rows whose label...", kMelder_string, DEFAULT) SENTENCE (L"...the text", L"a") OK DO const wchar_t *text = GET_STRING (L"...the text"); LOOP { iam (TableOfReal); autoTableOfReal thee = TableOfReal_extractRowsWhereLabel (me, GET_ENUM (kMelder_string, L"Extract all rows whose label..."), text); praat_new (thee.transfer(), my name, L"_", text); } END FORM (TableOfReal_formula, L"TableOfReal: Formula", L"Formula...") LABEL (L"", L"for row from 1 to nrow do for col from 1 to ncol do self [row, col] = ...") TEXTFIELD (L"formula", L"if col = 5 then self + self [6] else self fi") OK DO LOOP { iam (TableOfReal); try { TableOfReal_formula (me, GET_STRING (L"formula"), interpreter, NULL); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); throw; } } END FORM (TableOfReal_getColumnIndex, L"Get column index", 0) SENTENCE (L"Column label", L"") OK DO LOOP { iam (TableOfReal); long columnNumber = TableOfReal_columnLabelToIndex (me, GET_STRING (L"Column label")); therror Melder_information (Melder_integer (columnNumber)); } END FORM (TableOfReal_getColumnLabel, L"Get column label", 0) NATURAL (L"Column number", L"1") OK DO LOOP { iam (TableOfReal); long columnNumber = GET_INTEGER (L"Column number"); if (columnNumber > my numberOfColumns) Melder_throw (me, ": column number must not be greater than number of columns."); Melder_information (my columnLabels == NULL ? L"" : my columnLabels [columnNumber]); } END FORM (TableOfReal_getColumnMean_index, L"Get column mean", 0) NATURAL (L"Column number", L"1") OK DO LOOP { iam (TableOfReal); long columnNumber = GET_INTEGER (L"Column number"); if (columnNumber > my numberOfColumns) Melder_throw (me, ": column number must not be greater than number of columns."); double columnMean = TableOfReal_getColumnMean (me, columnNumber); therror Melder_informationReal (columnMean, NULL); } END FORM (TableOfReal_getColumnMean_label, L"Get column mean", 0) SENTENCE (L"Column label", L"") OK DO LOOP { iam (TableOfReal); long columnNumber = TableOfReal_columnLabelToIndex (me, GET_STRING (L"Column label")); if (columnNumber == 0) Melder_throw (me, ": column label does not exist."); double columnMean = TableOfReal_getColumnMean (me, columnNumber); therror Melder_informationReal (columnMean, NULL); } END FORM (TableOfReal_getColumnStdev_index, L"Get column standard deviation", 0) NATURAL (L"Column number", L"1") OK DO LOOP { iam (TableOfReal); long columnNumber = GET_INTEGER (L"Column number"); if (columnNumber > my numberOfColumns) Melder_throw (me, ": column number must not be greater than number of columns."); double stdev = TableOfReal_getColumnStdev (me, columnNumber); therror Melder_informationReal (stdev, NULL); } END FORM (TableOfReal_getColumnStdev_label, L"Get column standard deviation", 0) SENTENCE (L"Column label", L"1") OK DO LOOP { iam (TableOfReal); long columnNumber = TableOfReal_columnLabelToIndex (me, GET_STRING (L"Column label")); if (columnNumber == 0) Melder_throw (me, ": column label does not exist."); double stdev = TableOfReal_getColumnStdev (me, columnNumber); therror Melder_informationReal (stdev, NULL); } END DIRECT (TableOfReal_getNumberOfColumns) LOOP { iam (TableOfReal); Melder_information (Melder_integer (my numberOfColumns)); } END DIRECT (TableOfReal_getNumberOfRows) LOOP { iam (TableOfReal); Melder_information (Melder_integer (my numberOfRows)); } END FORM (TableOfReal_getRowIndex, L"Get row index", 0) SENTENCE (L"Row label", L"") OK DO LOOP { iam (TableOfReal); long rowNumber = TableOfReal_rowLabelToIndex (me, GET_STRING (L"Row label")); therror Melder_information (Melder_integer (rowNumber)); } END FORM (TableOfReal_getRowLabel, L"Get row label", 0) NATURAL (L"Row number", L"1") OK DO LOOP { iam (TableOfReal); long rowNumber = GET_INTEGER (L"Row number"); if (rowNumber > my numberOfRows) Melder_throw (me, ": row number must not be greater than number of rows."); Melder_information (my rowLabels == NULL ? L"" : my rowLabels [rowNumber]); } END FORM (TableOfReal_getValue, L"Get value", 0) NATURAL (L"Row number", L"1") NATURAL (L"Column number", L"1") OK DO LOOP { iam (TableOfReal); long rowNumber = GET_INTEGER (L"Row number"), columnNumber = GET_INTEGER (L"Column number"); if (rowNumber > my numberOfRows) Melder_throw (me, ": row number must not exceed number of rows."); if (columnNumber > my numberOfColumns) Melder_throw (me, ": column number must not exceed number of columns."); Melder_informationReal (my data [rowNumber] [columnNumber], NULL); } END DIRECT (TableOfReal_help) Melder_help (L"TableOfReal"); END FORM (TableOfReal_insertColumn, L"Insert column", 0) NATURAL (L"Column number", L"1") OK DO LOOP { iam (TableOfReal); TableOfReal_insertColumn (me, GET_INTEGER (L"Column number")); therror praat_dataChanged (me); } END FORM (TableOfReal_insertRow, L"Insert row", 0) NATURAL (L"Row number", L"1") OK DO LOOP { iam (TableOfReal); TableOfReal_insertRow (me, GET_INTEGER (L"Row number")); therror praat_dataChanged (me); } END FORM_READ (TableOfReal_readFromHeaderlessSpreadsheetFile, L"Read TableOfReal from headerless spreadsheet file", 0, true) praat_newWithFile (TableOfReal_readFromHeaderlessSpreadsheetFile (file), MelderFile_name (file), file); END FORM (TableOfReal_removeColumn, L"Remove column", 0) NATURAL (L"Column number", L"1") OK DO LOOP { iam (TableOfReal); TableOfReal_removeColumn (me, GET_INTEGER (L"Column number")); praat_dataChanged (me); } END FORM (TableOfReal_removeRow, L"Remove row", 0) NATURAL (L"Row number", L"1") OK DO LOOP { iam (TableOfReal); TableOfReal_removeRow (me, GET_INTEGER (L"Row number")); praat_dataChanged (me); } END FORM (TableOfReal_setColumnLabel_index, L"Set column label", 0) NATURAL (L"Column number", L"1") SENTENCE (L"Label", L"") OK DO LOOP { iam (TableOfReal); TableOfReal_setColumnLabel (me, GET_INTEGER (L"Column number"), GET_STRING (L"Label")); praat_dataChanged (me); } END FORM (TableOfReal_setColumnLabel_label, L"Set column label", 0) SENTENCE (L"Old label", L"") SENTENCE (L"New label", L"") OK DO LOOP { iam (TableOfReal); long columnNumber = TableOfReal_columnLabelToIndex (me, GET_STRING (L"Old label")); therror TableOfReal_setColumnLabel (me, columnNumber, GET_STRING (L"New label")); praat_dataChanged (me); } END FORM (TableOfReal_setRowLabel_index, L"Set row label", 0) NATURAL (L"Row number", L"1") SENTENCE (L"Label", L"") OK DO LOOP { iam (TableOfReal); TableOfReal_setRowLabel (me, GET_INTEGER (L"Row number"), GET_STRING (L"Label")); praat_dataChanged (me); } END FORM (TableOfReal_setValue, L"Set value", L"TableOfReal: Set value...") NATURAL (L"Row number", L"1") NATURAL (L"Column number", L"1") REAL_OR_UNDEFINED (L"New value", L"0.0") OK DO LOOP { iam (TableOfReal); long rowNumber = GET_INTEGER (L"Row number"), columnNumber = GET_INTEGER (L"Column number"); if (rowNumber > my numberOfRows) Melder_throw (me, ": row number too large."); if (columnNumber > my numberOfColumns) Melder_throw (me, ": column number too large."); my data [rowNumber] [columnNumber] = GET_REAL (L"New value"); praat_dataChanged (me); } END FORM (TableOfReal_setRowLabel_label, L"Set row label", 0) SENTENCE (L"Old label", L"") SENTENCE (L"New label", L"") OK DO LOOP { iam (TableOfReal); long rowNumber = TableOfReal_rowLabelToIndex (me, GET_STRING (L"Old label")); therror TableOfReal_setRowLabel (me, rowNumber, GET_STRING (L"New label")); praat_dataChanged (me); } END FORM (TableOfReal_sortByColumn, L"Sort rows by column", 0) INTEGER (L"Column", L"1") INTEGER (L"Secondary column", L"0") OK DO LOOP { iam (TableOfReal); TableOfReal_sortByColumn (me, GET_INTEGER (L"Column"), GET_INTEGER (L"Secondary column")); praat_dataChanged (me); } END FORM (TableOfReal_sortByLabel, L"Sort rows by label", 0) LABEL (L"", L"Secondary sorting keys:") INTEGER (L"Column1", L"1") INTEGER (L"Column2", L"0") OK DO LOOP { iam (TableOfReal); TableOfReal_sortByLabel (me, GET_INTEGER (L"Column1"), GET_INTEGER (L"Column2")); praat_dataChanged (me); } END DIRECT (TableOfReal_to_Matrix) LOOP { iam (TableOfReal); autoMatrix thee = TableOfReal_to_Matrix (me); praat_new (thee.transfer(), my name); } END FORM (TableOfReal_to_Table, L"TableOfReal: To Table", 0) SENTENCE (L"Label of first column", L"rowLabel") OK DO LOOP { iam (TableOfReal); autoTable thee = TableOfReal_to_Table (me, GET_STRING (L"Label of first column")); praat_new (thee.transfer(), my name); } END FORM_WRITE (TableOfReal_writeToHeaderlessSpreadsheetFile, L"Save TableOfReal as spreadsheet", 0, L"txt") LOOP { iam (TableOfReal); TableOfReal_writeToHeaderlessSpreadsheetFile (me, file); } END DIRECT (StatisticsTutorial) Melder_help (L"Statistics"); END static bool isTabSeparated_8bit (int nread, const char *header) { for (long i = 0; i < nread; i ++) { if (header [i] == '\t') return true; if (header [i] == '\n' || header [i] == '\r') return false; } return false; } static bool isTabSeparated_utf16be (int nread, const char *header) { for (long i = 2; i < nread; i += 2) { if (header [i] == '\0' && header [i + 1] == '\t') return true; if (header [i] == '\0' && (header [i + 1] == '\n' || header [i + 1] == '\r')) return false; } return false; } static bool isTabSeparated_utf16le (int nread, const char *header) { for (long i = 2; i < nread; i += 2) { if (header [i + 1] == '\0' && header [i] == '\t') return true; if (header [i + 1] == '\0' && (header [i] == '\n' || header [i] == '\r')) return false; } return false; } static Any tabSeparatedFileRecognizer (int nread, const char *header, MelderFile file) { /* * A table is recognized if it has at least one tab symbol, * which must be before the first newline symbol (if any). */ unsigned char *uheader = (unsigned char *) header; bool isTabSeparated = uheader [0] == 0xef && uheader [1] == 0xff ? isTabSeparated_utf16be (nread, header) : uheader [0] == 0xff && uheader [1] == 0xef ? isTabSeparated_utf16le (nread, header) : isTabSeparated_8bit (nread, header); if (! isTabSeparated) return NULL; return Table_readFromCharacterSeparatedTextFile (file, '\t'); } void praat_TableOfReal_init (ClassInfo klas); /* Buttons for TableOfReal and for its subclasses. */ void praat_TableOfReal_init (ClassInfo klas) { praat_addAction1 (klas, 1, L"Save as headerless spreadsheet file...", 0, 0, DO_TableOfReal_writeToHeaderlessSpreadsheetFile); praat_addAction1 (klas, 1, L"Write to headerless spreadsheet file...", 0, praat_HIDDEN, DO_TableOfReal_writeToHeaderlessSpreadsheetFile); praat_addAction1 (klas, 0, L"Draw -", 0, 0, 0); praat_addAction1 (klas, 0, L"Draw as numbers...", 0, 1, DO_TableOfReal_drawAsNumbers); praat_addAction1 (klas, 0, L"Draw as numbers if...", 0, 1, DO_TableOfReal_drawAsNumbers_if); praat_addAction1 (klas, 0, L"Draw as squares...", 0, 1, DO_TableOfReal_drawAsSquares); praat_addAction1 (klas, 0, L"-- draw lines --", 0, 1, 0); praat_addAction1 (klas, 0, L"Draw vertical lines...", 0, 1, DO_TableOfReal_drawVerticalLines); praat_addAction1 (klas, 0, L"Draw horizontal lines...", 0, 1, DO_TableOfReal_drawHorizontalLines); praat_addAction1 (klas, 0, L"Draw left and right lines...", 0, 1, DO_TableOfReal_drawLeftAndRightLines); praat_addAction1 (klas, 0, L"Draw top and bottom lines...", 0, 1, DO_TableOfReal_drawTopAndBottomLines); praat_addAction1 (klas, 0, L"Query -", 0, 0, 0); praat_addAction1 (klas, 1, L"Get number of rows", 0, 1, DO_TableOfReal_getNumberOfRows); praat_addAction1 (klas, 1, L"Get number of columns", 0, 1, DO_TableOfReal_getNumberOfColumns); praat_addAction1 (klas, 1, L"Get row label...", 0, 1, DO_TableOfReal_getRowLabel); praat_addAction1 (klas, 1, L"Get column label...", 0, 1, DO_TableOfReal_getColumnLabel); praat_addAction1 (klas, 1, L"Get row index...", 0, 1, DO_TableOfReal_getRowIndex); praat_addAction1 (klas, 1, L"Get column index...", 0, 1, DO_TableOfReal_getColumnIndex); praat_addAction1 (klas, 1, L"-- get value --", 0, 1, 0); praat_addAction1 (klas, 1, L"Get value...", 0, 1, DO_TableOfReal_getValue); if (klas == classTableOfReal) { praat_addAction1 (klas, 1, L"-- get statistics --", 0, 1, 0); praat_addAction1 (klas, 1, L"Get column mean (index)...", 0, 1, DO_TableOfReal_getColumnMean_index); praat_addAction1 (klas, 1, L"Get column mean (label)...", 0, 1, DO_TableOfReal_getColumnMean_label); praat_addAction1 (klas, 1, L"Get column stdev (index)...", 0, 1, DO_TableOfReal_getColumnStdev_index); praat_addAction1 (klas, 1, L"Get column stdev (label)...", 0, 1, DO_TableOfReal_getColumnStdev_label); } praat_addAction1 (klas, 0, L"Modify -", 0, 0, 0); praat_addAction1 (klas, 0, L"Formula...", 0, 1, DO_TableOfReal_formula); praat_addAction1 (klas, 0, L"Set value...", 0, 1, DO_TableOfReal_setValue); praat_addAction1 (klas, 0, L"Sort by label...", 0, 1, DO_TableOfReal_sortByLabel); praat_addAction1 (klas, 0, L"Sort by column...", 0, 1, DO_TableOfReal_sortByColumn); praat_addAction1 (klas, 0, L"-- structure --", 0, 1, 0); praat_addAction1 (klas, 0, L"Remove row (index)...", 0, 1, DO_TableOfReal_removeRow); praat_addAction1 (klas, 0, L"Remove column (index)...", 0, 1, DO_TableOfReal_removeColumn); praat_addAction1 (klas, 0, L"Insert row (index)...", 0, 1, DO_TableOfReal_insertRow); praat_addAction1 (klas, 0, L"Insert column (index)...", 0, 1, DO_TableOfReal_insertColumn); praat_addAction1 (klas, 0, L"-- set --", 0, 1, 0); praat_addAction1 (klas, 0, L"Set row label (index)...", 0, 1, DO_TableOfReal_setRowLabel_index); praat_addAction1 (klas, 0, L"Set row label (label)...", 0, 1, DO_TableOfReal_setRowLabel_label); praat_addAction1 (klas, 0, L"Set column label (index)...", 0, 1, DO_TableOfReal_setColumnLabel_index); praat_addAction1 (klas, 0, L"Set column label (label)...", 0, 1, DO_TableOfReal_setColumnLabel_label); praat_addAction1 (klas, 0, L"Synthesize -", 0, 0, 0); praat_addAction1 (klas, 0, L"Append", 0, 1, DO_TablesOfReal_append); praat_addAction1 (klas, 0, L"Extract part -", 0, 0, 0); praat_addAction1 (klas, 0, L"Extract row ranges...", 0, 1, DO_TableOfReal_extractRowRanges); praat_addAction1 (klas, 0, L"Extract rows where column...", 0, 1, DO_TableOfReal_extractRowsWhereColumn); praat_addAction1 (klas, 0, L"Extract rows where label...", 0, 1, DO_TableOfReal_extractRowsWhereLabel); praat_addAction1 (klas, 0, L"Extract rows where...", 0, 1, DO_TableOfReal_extractRowsWhere); praat_addAction1 (klas, 0, L"Extract column ranges...", 0, 1, DO_TableOfReal_extractColumnRanges); praat_addAction1 (klas, 0, L"Extract columns where row...", 0, 1, DO_TableOfReal_extractColumnsWhereRow); praat_addAction1 (klas, 0, L"Extract columns where label...", 0, 1, DO_TableOfReal_extractColumnsWhereLabel); praat_addAction1 (klas, 0, L"Extract columns where...", 0, 1, DO_TableOfReal_extractColumnsWhere); praat_addAction1 (klas, 0, L"Extract -", 0, 0, 0); praat_addAction1 (klas, 0, L"Extract row labels as Strings", 0, 1, DO_TableOfReal_extractRowLabelsAsStrings); praat_addAction1 (klas, 0, L"Extract column labels as Strings", 0, 1, DO_TableOfReal_extractColumnLabelsAsStrings); praat_addAction1 (klas, 0, L"Convert -", 0, 0, 0); praat_addAction1 (klas, 0, L"To Table...", 0, 1, DO_TableOfReal_to_Table); praat_addAction1 (klas, 0, L"To Matrix", 0, 1, DO_TableOfReal_to_Matrix); } void praat_uvafon_stat_init (); void praat_uvafon_stat_init () { Thing_recognizeClassesByName (classTableOfReal, classDistributions, classPairDistribution, classTable, classLinearRegression, classLogisticRegression, NULL); Data_recognizeFileType (tabSeparatedFileRecognizer); praat_addMenuCommand (L"Objects", L"New", L"Tables", 0, 0, 0); praat_addMenuCommand (L"Objects", L"New", L"Create Table with column names...", 0, 1, DO_Table_createWithColumnNames); praat_addMenuCommand (L"Objects", L"New", L"Create Table without column names...", 0, 1, DO_Table_createWithoutColumnNames); praat_addMenuCommand (L"Objects", L"New", L"Create Table...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_Table_createWithoutColumnNames); praat_addMenuCommand (L"Objects", L"New", L"Create TableOfReal...", 0, 1, DO_TableOfReal_create); praat_addMenuCommand (L"Objects", L"Open", L"Read TableOfReal from headerless spreadsheet file...", 0, 0, DO_TableOfReal_readFromHeaderlessSpreadsheetFile); praat_addMenuCommand (L"Objects", L"Open", L"Read Table from tab-separated file...", 0, 0, DO_Table_readFromTabSeparatedFile); praat_addMenuCommand (L"Objects", L"Open", L"Read Table from comma-separated file...", 0, 0, DO_Table_readFromCommaSeparatedFile); praat_addMenuCommand (L"Objects", L"Open", L"Read Table from whitespace-separated file...", 0, 0, DO_Table_readFromTableFile); praat_addMenuCommand (L"Objects", L"Open", L"Read Table from table file...", 0, praat_HIDDEN, DO_Table_readFromTableFile); praat_addAction1 (classDistributions, 0, L"Distributions help", 0, 0, DO_Distributions_help); praat_TableOfReal_init (classDistributions); praat_addAction1 (classDistributions, 1, L"Get probability (label)...", L"Get value...", 1, DO_Distributions_getProbability); praat_addAction1 (classDistributions, 0, L"-- get from two --", L"Get probability (label)...", 1, 0); praat_addAction1 (classDistributions, 2, L"Get mean absolute difference...", L"-- get from two --", 1, DO_Distributionses_getMeanAbsoluteDifference); praat_addAction1 (classDistributions, 0, L"-- add --", L"Append", 1, 0); praat_addAction1 (classDistributions, 0, L"Add", L"-- add --", 1, DO_Distributionses_add); praat_addAction1 (classDistributions, 0, L"Generate", 0, 0, 0); praat_addAction1 (classDistributions, 0, L"To Strings...", 0, 0, DO_Distributions_to_Strings); praat_addAction1 (classDistributions, 0, L"To Strings (exact)...", 0, 0, DO_Distributions_to_Strings_exact); praat_addAction1 (classLogisticRegression, 0, L"Draw boundary...", 0, 0, DO_LogisticRegression_drawBoundary); praat_addAction1 (classPairDistribution, 0, L"PairDistribution help", 0, 0, DO_PairDistribution_help); praat_addAction1 (classPairDistribution, 0, L"To Table", 0, 0, DO_PairDistribution_to_Table); praat_addAction1 (classPairDistribution, 1, L"To Stringses...", 0, 0, DO_PairDistribution_to_Stringses); praat_addAction1 (classPairDistribution, 0, L"Query -", 0, 0, 0); praat_addAction1 (classPairDistribution, 1, L"Get number of pairs", 0, 1, DO_PairDistribution_getNumberOfPairs); praat_addAction1 (classPairDistribution, 1, L"Get string1...", 0, 1, DO_PairDistribution_getString1); praat_addAction1 (classPairDistribution, 1, L"Get string2...", 0, 1, DO_PairDistribution_getString2); praat_addAction1 (classPairDistribution, 1, L"Get weight...", 0, 1, DO_PairDistribution_getWeight); praat_addAction1 (classPairDistribution, 1, L"-- get fraction correct --", 0, 1, 0); praat_addAction1 (classPairDistribution, 1, L"Get fraction correct (maximum likelihood)", 0, 1, DO_PairDistribution_getFractionCorrect_maximumLikelihood); praat_addAction1 (classPairDistribution, 1, L"Get fraction correct (probability matching)", 0, 1, DO_PairDistribution_getFractionCorrect_probabilityMatching); praat_addAction1 (classPairDistribution, 0, L"Modify -", 0, 0, 0); praat_addAction1 (classPairDistribution, 1, L"Remove zero weights", 0, 0, DO_PairDistribution_removeZeroWeights); praat_addAction1 (classTable, 0, L"Table help", 0, 0, DO_Table_help); praat_addAction1 (classTable, 1, L"Save as tab-separated file...", 0, 0, DO_Table_writeToTabSeparatedFile); praat_addAction1 (classTable, 1, L"Save as comma-separated file...", 0, 0, DO_Table_writeToCommaSeparatedFile); praat_addAction1 (classTable, 1, L"Save as table file...", 0, praat_HIDDEN, DO_Table_writeToTabSeparatedFile); praat_addAction1 (classTable, 1, L"Write to table file...", 0, praat_HIDDEN, DO_Table_writeToTabSeparatedFile); praat_addAction1 (classTable, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_Table_edit); praat_addAction1 (classTable, 1, L"Edit", 0, praat_HIDDEN, DO_Table_edit); praat_addAction1 (classTable, 0, L"Draw -", 0, 0, 0); praat_addAction1 (classTable, 0, L"Scatter plot...", 0, 1, DO_Table_scatterPlot); praat_addAction1 (classTable, 0, L"Scatter plot (mark)...", 0, 1, DO_Table_scatterPlot_mark); praat_addAction1 (classTable, 0, L"Draw ellipse (standard deviation)...", 0, 1, DO_Table_drawEllipse); praat_addAction1 (classTable, 0, L"Query -", 0, 0, 0); praat_addAction1 (classTable, 1, L"List...", 0, 1, DO_Table_list); praat_addAction1 (classTable, 1, L"-- get structure --", 0, 1, 0); praat_addAction1 (classTable, 1, L"Get number of rows", 0, 1, DO_Table_getNumberOfRows); praat_addAction1 (classTable, 1, L"Get number of columns", 0, 1, DO_Table_getNumberOfColumns); praat_addAction1 (classTable, 1, L"Get column label...", 0, 1, DO_Table_getColumnLabel); praat_addAction1 (classTable, 1, L"Get column index...", 0, 1, DO_Table_getColumnIndex); praat_addAction1 (classTable, 1, L"-- get value --", 0, 1, 0); praat_addAction1 (classTable, 1, L"Get value...", 0, 1, DO_Table_getValue); praat_addAction1 (classTable, 1, L"Search column...", 0, 1, DO_Table_searchColumn); praat_addAction1 (classTable, 1, L"-- statistics --", 0, 1, 0); praat_addAction1 (classTable, 1, L"Statistics tutorial", 0, 1, DO_StatisticsTutorial); praat_addAction1 (classTable, 1, L"-- get stats --", 0, 1, 0); praat_addAction1 (classTable, 1, L"Get quantile...", 0, 1, DO_Table_getQuantile); praat_addAction1 (classTable, 1, L"Get minimum...", 0, 1, DO_Table_getMinimum); praat_addAction1 (classTable, 1, L"Get maximum...", 0, 1, DO_Table_getMaximum); praat_addAction1 (classTable, 1, L"Get mean...", 0, 1, DO_Table_getMean); praat_addAction1 (classTable, 1, L"Get group mean...", 0, 1, DO_Table_getGroupMean); praat_addAction1 (classTable, 1, L"Get standard deviation...", 0, 1, DO_Table_getStandardDeviation); praat_addAction1 (classTable, 1, L"-- report stats --", 0, 1, 0); praat_addAction1 (classTable, 1, L"Report mean (Student t)...", 0, 1, DO_Table_reportMean_studentT); /*praat_addAction1 (classTable, 1, L"Report standard deviation...", 0, 1, DO_Table_reportStandardDeviation);*/ praat_addAction1 (classTable, 1, L"Report difference (Student t)...", 0, 1, DO_Table_reportDifference_studentT); praat_addAction1 (classTable, 1, L"Report group mean (Student t)...", 0, 1, DO_Table_reportGroupMean_studentT); praat_addAction1 (classTable, 1, L"Report group difference (Student t)...", 0, 1, DO_Table_reportGroupDifference_studentT); praat_addAction1 (classTable, 1, L"Report group difference (Wilcoxon rank sum)...", 0, 1, DO_Table_reportGroupDifference_wilcoxonRankSum); praat_addAction1 (classTable, 1, L"Report correlation (Pearson r)...", 0, 1, DO_Table_reportCorrelation_pearsonR); praat_addAction1 (classTable, 1, L"Report correlation (Kendall tau)...", 0, 1, DO_Table_reportCorrelation_kendallTau); praat_addAction1 (classTable, 0, L"Modify -", 0, 0, 0); praat_addAction1 (classTable, 0, L"Set string value...", 0, 1, DO_Table_setStringValue); praat_addAction1 (classTable, 0, L"Set numeric value...", 0, 1, DO_Table_setNumericValue); praat_addAction1 (classTable, 0, L"Formula...", 0, 1, DO_Table_formula); praat_addAction1 (classTable, 0, L"Formula (column range)...", 0, 1, DO_Table_formula_columnRange); praat_addAction1 (classTable, 0, L"Sort rows...", 0, 1, DO_Table_sortRows); praat_addAction1 (classTable, 0, L"Randomize rows", 0, 1, DO_Table_randomizeRows); praat_addAction1 (classTable, 0, L"-- structure --", 0, 1, 0); praat_addAction1 (classTable, 0, L"Append row", 0, 1, DO_Table_appendRow); praat_addAction1 (classTable, 0, L"Append column...", 0, 1, DO_Table_appendColumn); praat_addAction1 (classTable, 0, L"Append sum column...", 0, 1, DO_Table_appendSumColumn); praat_addAction1 (classTable, 0, L"Append difference column...", 0, 1, DO_Table_appendDifferenceColumn); praat_addAction1 (classTable, 0, L"Append product column...", 0, 1, DO_Table_appendProductColumn); praat_addAction1 (classTable, 0, L"Append quotient column...", 0, 1, DO_Table_appendQuotientColumn); praat_addAction1 (classTable, 0, L"Remove row...", 0, 1, DO_Table_removeRow); praat_addAction1 (classTable, 0, L"Remove column...", 0, 1, DO_Table_removeColumn); praat_addAction1 (classTable, 0, L"Insert row...", 0, 1, DO_Table_insertRow); praat_addAction1 (classTable, 0, L"Insert column...", 0, 1, DO_Table_insertColumn); praat_addAction1 (classTable, 0, L"-- set --", 0, 1, 0); praat_addAction1 (classTable, 0, L"Set column label (index)...", 0, 1, DO_Table_setColumnLabel_index); praat_addAction1 (classTable, 0, L"Set column label (label)...", 0, 1, DO_Table_setColumnLabel_label); praat_addAction1 (classTable, 0, L"Analyse -", 0, 0, 0); praat_addAction1 (classTable, 0, L"To linear regression", 0, 1, DO_Table_to_LinearRegression); praat_addAction1 (classTable, 0, L"To logistic regression...", 0, 1, DO_Table_to_LogisticRegression); praat_addAction1 (classTable, 0, L"Synthesize -", 0, 0, 0); praat_addAction1 (classTable, 0, L"Append", 0, 1, DO_Tables_append); praat_addAction1 (classTable, 0, L"Generate -", 0, 0, 0); praat_addAction1 (classTable, 1, L"Draw row from distribution...", 0, 1, DO_Table_drawRowFromDistribution); praat_addAction1 (classTable, 0, L"Extract -", 0, 0, 0); praat_addAction1 (classTable, 0, L"Extract rows where column (number)...", 0, 1, DO_Table_extractRowsWhereColumn_number); praat_addAction1 (classTable, 0, L"Extract rows where column...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_Table_extractRowsWhereColumn_number); praat_addAction1 (classTable, 0, L"Select rows where column...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_Table_extractRowsWhereColumn_number); praat_addAction1 (classTable, 0, L"Extract rows where column (text)...", 0, 1, DO_Table_extractRowsWhereColumn_text); praat_addAction1 (classTable, 0, L"Collapse rows...", 0, 1, DO_Table_collapseRows); praat_addAction1 (classTable, 0, L"Rows to columns...", 0, 1, DO_Table_rowsToColumns); praat_addAction1 (classTable, 0, L"Down to TableOfReal...", 0, 0, DO_Table_to_TableOfReal); praat_addAction1 (classTableOfReal, 0, L"TableOfReal help", 0, 0, DO_TableOfReal_help); praat_TableOfReal_init (classTableOfReal); praat_addAction2 (classPairDistribution, 1, classDistributions, 1, L"Get fraction correct...", 0, 0, DO_PairDistribution_Distributions_getFractionCorrect); } /* End of file praat_Stat.cpp */ sources_5316/stat/Distributions_and_Strings.h0000644000176700017670000000207711611106464020252 0ustar paulpaul/* Distributions_and_Strings.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Distributions.h" #include "Strings.h" Strings Distributions_to_Strings (Distributions me, long column, long numberOfStrings); Strings Distributions_to_Strings_exact (Distributions me, long column); Distributions Strings_to_Distributions (Strings me); /* End of file Distributions_and_Strings.h */ sources_5316/stat/TableEditor.cpp0000644000176700017670000003746211753751531015624 0ustar paulpaul/* TableEditor.cpp * * Copyright (C) 2006-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "TableEditor.h" #include "machine.h" #include "EditorM.h" Thing_implement (TableEditor, Editor, 0); #define SIZE_INCHES 40 /********** EDITOR METHODS **********/ void structTableEditor :: v_destroy () { forget (graphics); TableEditor_Parent :: v_destroy (); } static void updateVerticalScrollBar (TableEditor me) { Table table = static_cast
(my data); #if motif /*int value, slider, incr, pincr; XmScrollBarGetValues (my verticalScrollBar, & value, & slider, & incr, & pincr); XmScrollBarSetValues (my verticalScrollBar, my topRow, slider, incr, pincr, False);*/ XtVaSetValues (my verticalScrollBar, XmNvalue, my topRow, XmNmaximum, table -> rows -> size + 1, NULL); #endif } static void updateHorizontalScrollBar (TableEditor me) { Table table = static_cast
(my data); #if motif /*int value, slider, incr, pincr; XmScrollBarGetValues (my horizontalScrollBar, & value, & slider, & incr, & pincr); XmScrollBarSetValues (my horizontalScrollBar, my topRow, slider, incr, pincr, False);*/ XtVaSetValues (my horizontalScrollBar, XmNvalue, my leftColumn, XmNmaximum, table -> numberOfColumns + 1, NULL); #endif } void structTableEditor :: v_dataChanged () { Table table = static_cast
(data); if (topRow > table -> rows -> size) topRow = table -> rows -> size; if (leftColumn > table -> numberOfColumns) leftColumn = table -> numberOfColumns; updateVerticalScrollBar (this); updateHorizontalScrollBar (this); Graphics_updateWs (graphics); } /********** FILE MENU **********/ /********** EDIT MENU **********/ #ifndef macintosh static void menu_cb_Cut (EDITOR_ARGS) { // BUG: why only on Mac? EDITOR_IAM (TableEditor); GuiText_cut (my text); } static void menu_cb_Copy (EDITOR_ARGS) { EDITOR_IAM (TableEditor); GuiText_copy (my text); } static void menu_cb_Paste (EDITOR_ARGS) { EDITOR_IAM (TableEditor); GuiText_paste (my text); } static void menu_cb_Erase (EDITOR_ARGS) { EDITOR_IAM (TableEditor); GuiText_remove (my text); } #endif /********** VIEW MENU **********/ /********** HELP MENU **********/ static void menu_cb_TableEditorHelp (EDITOR_ARGS) { EDITOR_IAM (TableEditor); Melder_help (L"TableEditor"); } /********** DRAWING AREA **********/ void structTableEditor :: v_draw () { Table table = static_cast
(data); double spacing = 2.0; // millimetres at both edges double columnWidth, cellWidth; /* * We fit 200 rows in 40 inches, which is 14.4 points per row. */ long rowmin = topRow, rowmax = rowmin + 197; long colmin = leftColumn, colmax = colmin + (kTableEditor_MAXNUM_VISIBLE_COLUMNS - 1); if (rowmax > table -> rows -> size) rowmax = table -> rows -> size; if (colmax > table -> numberOfColumns) colmax = table -> numberOfColumns; Graphics_clearWs (graphics); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_HALF); Graphics_setWindow (graphics, 0.0, 1.0, rowmin + 197.5, rowmin - 2.5); Graphics_setColour (graphics, Graphics_SILVER); Graphics_fillRectangle (graphics, 0.0, 1.0, rowmin - 2.5, rowmin - 0.5); Graphics_setColour (graphics, Graphics_BLACK); Graphics_line (graphics, 0.0, rowmin - 0.5, 1.0, rowmin - 0.5); Graphics_setWindow (graphics, 0.0, Graphics_dxWCtoMM (graphics, 1.0), rowmin + 197.5, rowmin - 2.5); /* * Determine the width of the column with the row numbers. */ columnWidth = Graphics_textWidth (graphics, L"row"); for (long irow = rowmin; irow <= rowmax; irow ++) { cellWidth = Graphics_textWidth (graphics, Melder_integer (irow)); if (cellWidth > columnWidth) columnWidth = cellWidth; } columnLeft [0] = columnWidth + 2 * spacing; Graphics_setColour (graphics, Graphics_SILVER); Graphics_fillRectangle (graphics, 0.0, columnLeft [0], rowmin - 0.5, rowmin + 197.5); Graphics_setColour (graphics, Graphics_BLACK); Graphics_line (graphics, columnLeft [0], rowmin - 0.5, columnLeft [0], rowmin + 197.5); /* * Determine the width of the columns. */ for (long icol = colmin; icol <= colmax; icol ++) { const wchar_t *columnLabel = table -> columnHeaders [icol]. label; columnWidth = Graphics_textWidth (graphics, Melder_integer (icol)); if (columnLabel == NULL) columnLabel = L""; cellWidth = Graphics_textWidth (graphics, columnLabel); if (cellWidth > columnWidth) columnWidth = cellWidth; for (long irow = rowmin; irow <= rowmax; irow ++) { const wchar_t *cell = Table_getStringValue_Assert (table, irow, icol); Melder_assert (cell != NULL); if (cell [0] == '\0') cell = L"?"; cellWidth = Graphics_textWidth (graphics, cell); if (cellWidth > columnWidth) columnWidth = cellWidth; } columnRight [icol - colmin] = columnLeft [icol - colmin] + columnWidth + 2 * spacing; if (icol < colmax) columnLeft [icol - colmin + 1] = columnRight [icol - colmin]; } /* * Show the row numbers. */ Graphics_text (graphics, columnLeft [0] / 2, rowmin - 1, L"row"); for (long irow = rowmin; irow <= rowmax; irow ++) { Graphics_text1 (graphics, columnLeft [0] / 2, irow, Melder_integer (irow)); } /* * Show the column labels. */ for (long icol = colmin; icol <= colmax; icol ++) { double mid = (columnLeft [icol - colmin] + columnRight [icol - colmin]) / 2; const wchar_t *columnLabel = table -> columnHeaders [icol]. label; if (columnLabel == NULL || columnLabel [0] == '\0') columnLabel = L"?"; Graphics_text1 (graphics, mid, rowmin - 2, Melder_integer (icol)); Graphics_text (graphics, mid, rowmin - 1, columnLabel); } /* * Show the cell contents. */ for (long irow = rowmin; irow <= rowmax; irow ++) { for (long icol = colmin; icol <= colmax; icol ++) { double mid = (columnLeft [icol - colmin] + columnRight [icol - colmin]) / 2; const wchar_t *cell = Table_getStringValue_Assert (table, irow, icol); Melder_assert (cell != NULL); if (cell [0] == '\0') cell = L"?"; Graphics_text (graphics, mid, irow, cell); } } } int structTableEditor :: v_click (double xclick, double yWC, bool shiftKeyPressed) { Table table = static_cast
(data); return 1; } static void gui_text_cb_change (I, GuiTextEvent event) { iam (TableEditor); (void) event; Table table = static_cast
(my data); my broadcastDataChanged (); } static void gui_drawingarea_cb_expose (I, GuiDrawingAreaExposeEvent event) { iam (TableEditor); (void) event; if (my graphics == NULL) return; my v_draw (); } static void gui_drawingarea_cb_click (I, GuiDrawingAreaClickEvent event) { iam (TableEditor); if (my graphics == NULL) return; if (gtk && event -> type != BUTTON_PRESS) return; double xWC, yWC; Graphics_DCtoWC (my graphics, event -> x, event -> y, & xWC, & yWC); // TODO: implement selection } static void gui_drawingarea_cb_resize (I, GuiDrawingAreaResizeEvent event) { iam (TableEditor); if (my graphics == NULL) return; Graphics_updateWs (my graphics); } void structTableEditor :: v_createChildren () { Table table = static_cast
(data); GuiObject form; // a form inside a form; needed to keep key presses away from the drawing area #if gtk form = d_windowForm; #elif motif form = XmCreateForm (d_windowForm, "buttons", NULL, 0); XtVaSetValues (form, XmNleftAttachment, XmATTACH_FORM, XmNrightAttachment, XmATTACH_FORM, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, Machine_getMenuBarHeight (), XmNbottomAttachment, XmATTACH_FORM, XmNtraversalOn, False, // needed in order to redirect all keyboard input to the text widget NULL); #endif /***** Create text field. *****/ #if gtk text = GuiText_create (NULL, 0, 0, 0, Machine_getTextHeight (), 0); gtk_box_pack_start (GTK_BOX (form), GTK_WIDGET (text), FALSE, FALSE, 3); GuiObject_show (text); #else text = GuiText_createShown (form, 0, 0, 0, Machine_getTextHeight (), 0); #endif GuiText_setChangeCallback (text, gui_text_cb_change, this); /***** Create drawing area. *****/ #if gtk GuiObject table_container = gtk_table_new (2, 2, FALSE); gtk_box_pack_start (GTK_BOX (form), GTK_WIDGET (table_container), TRUE, TRUE, 3); GuiObject_show (table_container); drawingArea = GuiDrawingArea_create (NULL, 0, 0, 0, 0, gui_drawingarea_cb_expose, gui_drawingarea_cb_click, NULL, gui_drawingarea_cb_resize, this, 0); // need to turn off double buffering, otherwise we receive the expose events // delayed by one event, see also FunctionEditor.c gtk_widget_set_double_buffered (GTK_WIDGET (drawingArea), FALSE); gtk_table_attach (GTK_TABLE (table_container), GTK_WIDGET (drawingArea), 0, 1, 0, 1, (GtkAttachOptions) (GTK_EXPAND | GTK_FILL), (GtkAttachOptions) (GTK_EXPAND | GTK_FILL), 0, 0); GuiObject_show (drawingArea); #else drawingArea = GuiDrawingArea_createShown (form, 0, - Machine_getScrollBarWidth (), Machine_getTextHeight (), - Machine_getScrollBarWidth (), gui_drawingarea_cb_expose, gui_drawingarea_cb_click, NULL, NULL, this, 0); #endif /***** Create horizontal scroll bar. *****/ #if gtk GtkAdjustment *hadj = GTK_ADJUSTMENT (gtk_adjustment_new (1, 1, table -> numberOfColumns + 1, 1, 3, 1)); horizontalScrollBar = gtk_hscrollbar_new (hadj); gtk_table_attach (GTK_TABLE (table_container), GTK_WIDGET (horizontalScrollBar), 0, 1, 1, 2, (GtkAttachOptions) (GTK_EXPAND | GTK_FILL), (GtkAttachOptions) 0, 0, 0); GuiObject_show (horizontalScrollBar); #elif motif horizontalScrollBar = XtVaCreateManagedWidget ("horizontalScrollBar", xmScrollBarWidgetClass, form, XmNorientation, XmHORIZONTAL, XmNleftAttachment, XmATTACH_FORM, XmNleftOffset, 0, XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, Machine_getScrollBarWidth (), XmNbottomAttachment, XmATTACH_FORM, XmNheight, Machine_getScrollBarWidth (), XmNminimum, 1, XmNmaximum, table -> numberOfColumns + 1, XmNvalue, 1, XmNsliderSize, 1, XmNincrement, 1, XmNpageIncrement, 3, NULL); #endif /***** Create vertical scroll bar. *****/ #if gtk GtkAdjustment *vadj = GTK_ADJUSTMENT (gtk_adjustment_new (1, 1, table -> rows -> size + 1, 1, 10, 1)); verticalScrollBar = gtk_vscrollbar_new (vadj); gtk_table_attach (GTK_TABLE (table_container), GTK_WIDGET (verticalScrollBar), 1, 2, 0, 1, (GtkAttachOptions) 0, (GtkAttachOptions) (GTK_EXPAND | GTK_FILL), 0, 0); GuiObject_show (verticalScrollBar); #elif motif verticalScrollBar = XtVaCreateManagedWidget ("verticalScrollBar", xmScrollBarWidgetClass, form, XmNorientation, XmVERTICAL, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, Machine_getTextHeight (), XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, Machine_getScrollBarWidth (), XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, 0, XmNwidth, Machine_getScrollBarWidth (), XmNminimum, 1, XmNmaximum, table -> rows -> size + 1, XmNvalue, 1, XmNsliderSize, 1, XmNincrement, 1, XmNpageIncrement, 10, NULL); #endif GuiObject_show (form); } void structTableEditor :: v_createMenus () { TableEditor_Parent :: v_createMenus (); #ifndef macintosh Editor_addCommand (this, L"Edit", L"-- cut copy paste --", 0, NULL); Editor_addCommand (this, L"Edit", L"Cut text", 'X', menu_cb_Cut); Editor_addCommand (this, L"Edit", L"Cut", Editor_HIDDEN, menu_cb_Cut); Editor_addCommand (this, L"Edit", L"Copy text", 'C', menu_cb_Copy); Editor_addCommand (this, L"Edit", L"Copy", Editor_HIDDEN, menu_cb_Copy); Editor_addCommand (this, L"Edit", L"Paste text", 'V', menu_cb_Paste); Editor_addCommand (this, L"Edit", L"Paste", Editor_HIDDEN, menu_cb_Paste); Editor_addCommand (this, L"Edit", L"Erase text", 0, menu_cb_Erase); Editor_addCommand (this, L"Edit", L"Erase", Editor_HIDDEN, menu_cb_Erase); #endif } void structTableEditor :: v_createHelpMenuItems (EditorMenu menu) { TableEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"TableEditor help", '?', menu_cb_TableEditorHelp); } #if gtk #define gui_cb_scroll(name, var) \ void gui_cb_ ## name ## Scroll(GtkRange *rng, gpointer void_me) { \ iam(TableEditor); \ double var = gtk_range_get_value(rng); \ do #elif motif #define gui_cb_scroll(name, var) \ void gui_cb_ ## name ## Scroll(GUI_ARGS) { \ GUI_IAM(TableEditor); \ int var; \ { int slider, incr, pincr; \ XmScrollBarGetValues(w, &var, &slider, &incr, &pincr); } \ do #elif ! useCarbon #define gui_cb_scroll(name, var) \ void gui_cb_ ## name ## Scroll(GUI_ARGS) { \ GUI_IAM(TableEditor); \ int var; \ do #endif #define gui_cb_scroll_end while (0); } static gui_cb_scroll(horizontal, value) { if ((int)value != my leftColumn) { my leftColumn = value; my v_draw (); } } gui_cb_scroll_end static gui_cb_scroll(vertical, value) { if ((int)value != my topRow) { my topRow = value; my v_draw (); } } gui_cb_scroll_end #if gtk static gboolean gui_cb_drawing_area_scroll(GuiObject w, GdkEventScroll *event, gpointer void_me) { iam(TableEditor); double hv = gtk_range_get_value(GTK_RANGE(my horizontalScrollBar)); double hi = gtk_range_get_adjustment(GTK_RANGE(my horizontalScrollBar))->step_increment; double vv = gtk_range_get_value(GTK_RANGE(my verticalScrollBar)); double vi = gtk_range_get_adjustment(GTK_RANGE(my verticalScrollBar))->step_increment; switch (event->direction) { case GDK_SCROLL_UP: gtk_range_set_value(GTK_RANGE(my verticalScrollBar), vv - vi); break; case GDK_SCROLL_DOWN: gtk_range_set_value(GTK_RANGE(my verticalScrollBar), vv + vi); break; case GDK_SCROLL_LEFT: gtk_range_set_value(GTK_RANGE(my horizontalScrollBar), hv - hi); break; case GDK_SCROLL_RIGHT: gtk_range_set_value(GTK_RANGE(my horizontalScrollBar), hv + hi); break; } return TRUE; } #endif TableEditor TableEditor_create (GuiObject parent, const wchar_t *title, Table table) { try { autoTableEditor me = Thing_new (TableEditor); Editor_init (me.peek(), parent, 0, 0, 700, 500, title, table); #if motif Melder_assert (XtWindow (my drawingArea)); #endif my topRow = 1; my leftColumn = 1; my selectedColumn = 1; my selectedRow = 1; my graphics = Graphics_create_xmdrawingarea (my drawingArea); double size_pixels = SIZE_INCHES * Graphics_getResolution (my graphics); Graphics_setWsViewport (my graphics, 0, size_pixels, 0, size_pixels); Graphics_setWsWindow (my graphics, 0, size_pixels, 0, size_pixels); Graphics_setViewport (my graphics, 0, size_pixels, 0, size_pixels); Graphics_setFont (my graphics, kGraphics_font_COURIER); Graphics_setFontSize (my graphics, 12); Graphics_setUnderscoreIsSubscript (my graphics, FALSE); Graphics_setAtSignIsLink (my graphics, TRUE); #if gtk g_signal_connect(G_OBJECT(my drawingArea), "scroll-event", G_CALLBACK(gui_cb_drawing_area_scroll), me.peek()); g_signal_connect(G_OBJECT(my horizontalScrollBar), "value-changed", G_CALLBACK(gui_cb_horizontalScroll), me.peek()); g_signal_connect(G_OBJECT(my verticalScrollBar), "value-changed", G_CALLBACK(gui_cb_verticalScroll), me.peek()); #elif motif XtAddCallback (my horizontalScrollBar, XmNvalueChangedCallback, gui_cb_horizontalScroll, (XtPointer) me.peek()); XtAddCallback (my horizontalScrollBar, XmNdragCallback, gui_cb_horizontalScroll, (XtPointer) me.peek()); XtAddCallback (my verticalScrollBar, XmNvalueChangedCallback, gui_cb_verticalScroll, (XtPointer) me.peek()); XtAddCallback (my verticalScrollBar, XmNdragCallback, gui_cb_verticalScroll, (XtPointer) me.peek()); #endif return me.transfer(); } catch (MelderError) { Melder_throw ("TableEditor not created."); } } /* End of file TableEditor.cpp */ sources_5316/stat/PairDistribution.cpp0000644000176700017670000002677011622366410016712 0ustar paulpaul/* PairDistribution.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "PairDistribution.h" #include "oo_DESTROY.h" #include "PairDistribution_def.h" #include "oo_COPY.h" #include "PairDistribution_def.h" #include "oo_EQUAL.h" #include "PairDistribution_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "PairDistribution_def.h" #include "oo_WRITE_TEXT.h" #include "PairDistribution_def.h" #include "oo_READ_TEXT.h" #include "PairDistribution_def.h" #include "oo_WRITE_BINARY.h" #include "PairDistribution_def.h" #include "oo_READ_BINARY.h" #include "PairDistribution_def.h" #include "oo_DESCRIPTION.h" #include "PairDistribution_def.h" Thing_implement (PairProbability, Data, 0); void structPairDistribution :: v_info () { PairDistribution_Parent :: v_info (); MelderInfo_writeLine2 (L"Number of pairs: ", Melder_integer (pairs -> size)); } Thing_implement (PairDistribution, Data, 0); PairProbability PairProbability_create (const wchar_t *string1, const wchar_t *string2, double weight) { autoPairProbability me = Thing_new (PairProbability); my string1 = Melder_wcsdup (string1); my string2 = Melder_wcsdup (string2); my weight = weight; return me.transfer(); } PairDistribution PairDistribution_create () { try { autoPairDistribution me = Thing_new (PairDistribution); my pairs = Ordered_create (); therror return me.transfer(); } catch (MelderError) { Melder_throw ("PairDistribution not created."); } } static void PairDistribution_checkSpecifiedPairNumber (PairDistribution me, long pairNumber) { if (pairNumber < 1) Melder_throw (me, ": the specified pair number is ", pairNumber, ", but should be at least 1."); if (pairNumber > my pairs -> size) Melder_throw (me, ": the specified pair number is ", pairNumber, ", but should be at most my number of pairs (", my pairs -> size, ")."); } const wchar * PairDistribution_getString1 (PairDistribution me, long pairNumber) { try { PairDistribution_checkSpecifiedPairNumber (me, pairNumber); PairProbability prob = static_cast (my pairs -> item [pairNumber]); return prob -> string1; } catch (MelderError) { Melder_throw (me, ": string1 not retrieved."); } } const wchar * PairDistribution_getString2 (PairDistribution me, long pairNumber) { try { PairDistribution_checkSpecifiedPairNumber (me, pairNumber); PairProbability prob = static_cast (my pairs -> item [pairNumber]); return prob -> string2; } catch (MelderError) { Melder_throw (me, ": string2 not retrieved."); } } double PairDistribution_getWeight (PairDistribution me, long pairNumber) { try { PairDistribution_checkSpecifiedPairNumber (me, pairNumber); PairProbability prob = static_cast (my pairs -> item [pairNumber]); return prob -> weight; } catch (MelderError) { Melder_throw (me, ": weight not retrieved."); } } void PairDistribution_add (PairDistribution me, const wchar *string1, const wchar *string2, double weight) { PairProbability pair = PairProbability_create (string1, string2, weight); therror Collection_addItem (my pairs, pair); } void PairDistribution_removeZeroWeights (PairDistribution me) { for (long ipair = my pairs -> size; ipair > 0; ipair --) { PairProbability prob = static_cast (my pairs -> item [ipair]); if (prob -> weight <= 0.0) { Collection_removeItem (my pairs, ipair); } } } static double PairDistributions_getTotalWeight_checkPositive (PairDistribution me) throw (MelderError) { double totalWeight = 0.0; for (long ipair = 1; ipair <= my pairs -> size; ipair ++) { PairProbability prob = static_cast (my pairs -> item [ipair]); totalWeight += prob -> weight; } if (totalWeight <= 0.0) { Melder_throw (me, ": the total probability weight is ", Melder_half (totalWeight), " but should be greater than zero for this operation."); } return totalWeight; } void PairDistribution_to_Stringses (PairDistribution me, long nout, Strings *strings1_out, Strings *strings2_out) { try { *strings1_out = *strings2_out = NULL; long nin = my pairs -> size, iin; if (nin < 1) Melder_throw ("No candidates."); if (nout < 1) Melder_throw (L"Number of generated string pairs should be positive."); double total = PairDistributions_getTotalWeight_checkPositive (me); autoStrings strings1 = Thing_new (Strings); strings1 -> numberOfStrings = nout; strings1 -> strings = NUMvector (1, nout); autoStrings strings2 = Thing_new (Strings); strings2 -> numberOfStrings = nout; strings2 -> strings = NUMvector (1, nout); for (long iout = 1; iout <= nout; iout ++) { do { double rand = NUMrandomUniform (0, total), sum = 0.0; for (iin = 1; iin <= nin; iin ++) { PairProbability prob = static_cast (my pairs -> item [iin]); sum += prob -> weight; if (rand <= sum) break; } } while (iin > nin); /* Guard against rounding errors. */ PairProbability prob = static_cast (my pairs -> item [iin]); if (! prob -> string1 || ! prob -> string2) Melder_throw ("No string in probability pair ", iin, "."); strings1 -> strings [iout] = Melder_wcsdup (prob -> string1); strings2 -> strings [iout] = Melder_wcsdup (prob -> string2); } *strings1_out = strings1.transfer(); *strings2_out = strings2.transfer(); } catch (MelderError) { Melder_throw (me, ": generation of Stringses not performed."); } } void PairDistribution_peekPair (PairDistribution me, wchar_t **string1, wchar_t **string2) { try { *string1 = *string2 = NULL; double total = 0.0; long nin = my pairs -> size, iin; PairProbability prob; if (nin < 1) Melder_throw ("No candidates."); for (iin = 1; iin <= nin; iin ++) { prob = static_cast (my pairs -> item [iin]); total += prob -> weight; } do { double rand = NUMrandomUniform (0, total), sum = 0.0; for (iin = 1; iin <= nin; iin ++) { prob = static_cast (my pairs -> item [iin]); sum += prob -> weight; if (rand <= sum) break; } } while (iin > nin); /* Guard against rounding errors. */ prob = static_cast (my pairs -> item [iin]); if (! prob -> string1 || ! prob -> string2) Melder_throw ("No string in probability pair ", iin, L"."); *string1 = prob -> string1; *string2 = prob -> string2; } catch (MelderError) { Melder_throw (me, ": pair not peeked."); } } static int compare (PairProbability me, PairProbability thee) throw () { return wcscmp (my string1, thy string1); } static double PairDistribution_getFractionCorrect (PairDistribution me, int which) { try { double correct = 0.0; long pairmin = 1, ipair; autoPairDistribution thee = Data_copy (me); NUMsort_p (thy pairs -> size, thy pairs -> item, (int (*) (const void *, const void *)) compare); double total = PairDistributions_getTotalWeight_checkPositive (thee.peek()); do { long pairmax = pairmin; wchar_t *firstInput = ((PairProbability) thy pairs -> item [pairmin]) -> string1; for (ipair = pairmin + 1; ipair <= thy pairs -> size; ipair ++) { PairProbability prob = static_cast (thy pairs -> item [ipair]); if (! wcsequ (prob -> string1, firstInput)) { pairmax = ipair - 1; break; } } if (ipair > thy pairs -> size) pairmax = thy pairs -> size; if (which == 0) { double pmax = 0.0; for (ipair = pairmin; ipair <= pairmax; ipair ++) { PairProbability prob = static_cast (thy pairs -> item [ipair]); double p = prob -> weight / total; if (p > pmax) pmax = p; } correct += pmax; } else { double sum = 0.0, p2 = 0.0; for (ipair = pairmin; ipair <= pairmax; ipair ++) { PairProbability prob = static_cast (thy pairs -> item [ipair]); double p = prob -> weight / total; sum += p; p2 += p * p; } correct += p2 / sum; } pairmin = pairmax + 1; } while (pairmin <= thy pairs -> size); return correct; } catch (MelderError) { Melder_throw (me, ": could not compute my fraction correct."); } } double PairDistribution_getFractionCorrect_maximumLikelihood (PairDistribution me) { return PairDistribution_getFractionCorrect (me, 0); } double PairDistribution_getFractionCorrect_probabilityMatching (PairDistribution me) { return PairDistribution_getFractionCorrect (me, 1); } double PairDistribution_Distributions_getFractionCorrect (PairDistribution me, Distributions dist, long column) { try { double correct = 0.0; long pairmin = 1; wchar_t string [1000]; Distributions_checkSpecifiedColumnNumberWithinRange (dist, column); autoPairDistribution thee = Data_copy (me); NUMsort_p (thy pairs -> size, thy pairs -> item, (int (*) (const void *, const void *)) compare); double total = PairDistributions_getTotalWeight_checkPositive (thee.peek()); do { long pairmax = pairmin, length, ipair; double sum = 0.0, sumDist = 0.0; wchar_t *firstInput = ((PairProbability) thy pairs -> item [pairmin]) -> string1; for (ipair = pairmin + 1; ipair <= thy pairs -> size; ipair ++) { PairProbability prob = static_cast (thy pairs -> item [ipair]); if (! wcsequ (prob -> string1, firstInput)) { pairmax = ipair - 1; break; } } if (ipair > thy pairs -> size) pairmax = thy pairs -> size; for (ipair = pairmin; ipair <= pairmax; ipair ++) { PairProbability prob = static_cast (thy pairs -> item [ipair]); double p = prob -> weight / total, pout = 0.0; swprintf (string, 1000, L"%ls \\-> %ls", prob -> string1, prob -> string2); for (long idist = 1; idist <= dist -> numberOfRows; idist ++) { if (wcsequ (string, dist -> rowLabels [idist])) { pout = dist -> data [idist] [column]; break; } } sum += p * pout; } swprintf (string, 1000, L"%ls \\-> ", firstInput); length = wcslen (string); for (long idist = 1; idist <= dist -> numberOfRows; idist ++) { if (wcsnequ (string, dist -> rowLabels [idist], length)) { sumDist += dist -> data [idist] [column]; } } if (sumDist != 0.0) correct += sum / sumDist; pairmin = pairmax + 1; } while (pairmin <= thy pairs -> size); return correct; } catch (MelderError) { Melder_throw (me, " & ", dist, ": could not compute our fraction correct."); } } Table PairDistribution_to_Table (PairDistribution me) { try { autoTable thee = Table_createWithColumnNames (my pairs -> size, L"string1 string2 weight"); for (long ipair = 1; ipair <= my pairs -> size; ipair ++) { PairProbability prob = static_cast (my pairs -> item [ipair]); Table_setStringValue (thee.peek(), ipair, 1, prob -> string1); therror Table_setStringValue (thee.peek(), ipair, 2, prob -> string2); therror Table_setNumericValue (thee.peek(), ipair, 3, prob -> weight); therror } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Table."); } } /* End of file PairDistribution.cpp */ sources_5316/stat/Regression.h0000644000176700017670000000247111621526445015201 0ustar paulpaul#ifndef _Regression_h_ #define _Regression_h_ /* Regression.h * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Table.h" #include "Regression_def.h" oo_CLASS_CREATE (RegressionParameter, Data); oo_CLASS_CREATE (Regression, Data); void Regression_init (I); void Regression_addParameter (I, const wchar *label, double minimum, double maximum, double value); long Regression_getFactorIndexFromFactorName_e (I, const wchar *factorName); Thing_define (LinearRegression, Regression) { }; LinearRegression LinearRegression_create (void); LinearRegression Table_to_LinearRegression (Table me); /* End of file Regression.h */ #endif sources_5316/stat/Makefile0000644000176700017670000000117711704273736014356 0ustar paulpaul# Makefile of the library "stat" # Paul Boersma, 14 January 2012 include ../makefile.defs CPPFLAGS = -I ../num -I ../kar -I ../sys -I ../dwsys -I ../dwtools -I ../fon -I ../stat OBJECTS = Table.o TableEditor.o Regression.o manual_statistics.o praat_Stat.o \ TableOfReal.o Distributions.o Distributions_and_Strings.o PairDistribution.o \ LogisticRegression.o .PHONY: all clean all: libstat.a libstat.a: $(OBJECTS) touch libstat.a rm libstat.a ar cq libstat.a $(OBJECTS) $(RANLIB) libstat.a clean: $(RM) $(OBJECTS) $(RM) libstat.a $(OBJECTS): *.h ../num/NUM.h ../kar/*.h ../sys/*.h ../dwsys/*.h ../dwtools/*.h ../fon/*.h sources_5316/stat/LogisticRegression.h0000644000176700017670000000264511625721240016674 0ustar paulpaul#ifndef _LogisticRegression_h_ #define _LogisticRegression_h_ /* LogisticRegression.h * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Regression.h" #include "LogisticRegression_def.h" oo_CLASS_CREATE (LogisticRegression, Regression); LogisticRegression LogisticRegression_create (const wchar *dependent1, const wchar *dependent2); LogisticRegression Table_to_LogisticRegression (Table me, const wchar *columnsWithFactors_string, const wchar *columnWithDependent1_string, const wchar *columnWithDependent2_string); void LogisticRegression_drawBoundary (LogisticRegression me, Graphics graphics, long colx, double xmin, double xmax, long coly, double ymin, double ymax, bool garnish); /* End of file LogisticRegression.h */ #endif sources_5316/stat/Table.cpp0000644000176700017670000024365511654071213014450 0ustar paulpaul/* Table.cpp * * Copyright (C) 2002-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2003/05/19 Melder_atof * pb 2004/07/25 Melder_double * pb 2004/10/16 struct tags * pb 2005/03/04 Melder_NUMBER * pb 2005/04/25 Table_getLogisticRegression * pb 2005/04/25 Table_to_Matrix * pb 2005/06/16 enums -> ints * pb 2005/09/13 Table_readFromCharacterSeparatedTextFile * pb 2005/09/26 sorting by string now also works * pb 2006/01/24 getMatrixStr * pb 2006/01/26 Table_extractRowsWhereColumn_string * pb 2006/04/16 Table_createWithColumnNames * pb 2006/04/16 moved Melder_isStringNumeric to melder_atof.c * pb 2006/04/17 getColStr * pb 2007/04/19 Table_pool * pb 2006/04/24 Table_scatterPlot * pb 2006/08/27 Table_drawEllipse * pb 2006/10/29 TableOfReal_to_Table * pb 2006/11/25 Table_getGroupDifference_studentT * pb 2006/12/10 MelderInfo * pb 2007/03/17 exported Table_numericize for optimizers * pb 2007/05/07 renamed Table_pool to Table_collapseRows * pb 2007/05/07 Table_rowsToColumns * pb 2007/06/28 Table_getGroupMean_studentT, Table_getGroupMean * pb 2007/10/01 can write as encoding * pb 2007/10/13 made Table_getExtrema global * pb 2007/11/18 refactoring * pb 2008/01/02 Table_drawRowFromDistribution * pb 2008/04/30 new Formula API * pb 2009/01/18 Interpreter argument in formula * pb 2009/10/21 Table_randomizeRows * pb 2010/03/04 Wilcoxon rank sum * pb 2010/06/23 report number of degrees of freedom in t-tests * pb 2011/03/15 C++ * pb 2011/04/15 C++ */ #include #include "Table.h" #include "NUM2.h" #include "Formula.h" #include "SSCP.h" #include "oo_DESTROY.h" #include "Table_def.h" #include "oo_COPY.h" #include "Table_def.h" #include "oo_EQUAL.h" #include "Table_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Table_def.h" #include "oo_WRITE_TEXT.h" #include "Table_def.h" #include "oo_WRITE_BINARY.h" #include "Table_def.h" #include "oo_READ_TEXT.h" #include "Table_def.h" #include "oo_READ_BINARY.h" #include "Table_def.h" #include "oo_DESCRIPTION.h" #include "Table_def.h" Thing_implement (TableRow, Data, 0); Thing_implement (Table, Data, 0); void structTable :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of rows: ", Melder_integer (rows -> size)); MelderInfo_writeLine2 (L"Number of columns: ", Melder_integer (numberOfColumns)); } const wchar * structTable :: v_getColStr (long columnNumber) { if (columnNumber < 1 || columnNumber > numberOfColumns) return NULL; return columnHeaders [columnNumber]. label ? columnHeaders [columnNumber]. label : L""; } double structTable :: v_getMatrix (long rowNumber, long columnNumber) { if (rowNumber < 1 || rowNumber > rows -> size) return NUMundefined; if (columnNumber < 1 || columnNumber > numberOfColumns) return NUMundefined; wchar *stringValue = ((TableRow) rows -> item [rowNumber]) -> cells [columnNumber]. string; return stringValue == NULL ? NUMundefined : Melder_atof (stringValue); } const wchar * structTable :: v_getMatrixStr (long rowNumber, long columnNumber) { if (rowNumber < 1 || rowNumber > rows -> size) return L""; if (columnNumber < 1 || columnNumber > numberOfColumns) return L""; wchar *stringValue = ((TableRow) rows -> item [rowNumber]) -> cells [columnNumber]. string; return stringValue == NULL ? L"" : stringValue; } double structTable :: v_getColIndex (const wchar *columnLabel) { return Table_findColumnIndexFromColumnLabel (this, columnLabel); } static TableRow TableRow_create (long numberOfColumns) { autoTableRow me = Thing_new (TableRow); my numberOfColumns = numberOfColumns; my cells = NUMvector (1, numberOfColumns); return me.transfer(); } void Table_initWithoutColumnNames (I, long numberOfRows, long numberOfColumns) { iam (Table); if (numberOfColumns < 1) Melder_throw ("Cannot create table without columns."); my numberOfColumns = numberOfColumns; my columnHeaders = NUMvector (1, numberOfColumns); my rows = Ordered_create (); therror for (long irow = 1; irow <= numberOfRows; irow ++) { Table_appendRow (me); } } Table Table_createWithoutColumnNames (long numberOfRows, long numberOfColumns) { try { autoTable me = Thing_new (Table); Table_initWithoutColumnNames (me.peek(), numberOfRows, numberOfColumns); therror return me.transfer(); } catch (MelderError) { Melder_throw ("Table not created."); } } void Table_initWithColumnNames (I, long numberOfRows, const wchar *columnNames) { iam (Table); Table_initWithoutColumnNames (me, numberOfRows, Melder_countTokens (columnNames)); therror long icol = 0; for (wchar *columnName = Melder_firstToken (columnNames); columnName != NULL; columnName = Melder_nextToken ()) { icol ++; Table_setColumnLabel (me, icol, columnName); therror } } Table Table_createWithColumnNames (long numberOfRows, const wchar *columnNames) { try { autoTable me = Thing_new (Table); Table_initWithColumnNames (me.peek(), numberOfRows, columnNames); return me.transfer(); } catch (MelderError) { Melder_throw ("Table not created."); } } void Table_appendRow (Table me) { try { autoTableRow row = TableRow_create (my numberOfColumns); Collection_addItem (my rows, row.transfer()); } catch (MelderError) { Melder_throw (me, ": row not appended."); } } void Table_appendColumn (Table me, const wchar *label) { try { Table_insertColumn (me, my numberOfColumns + 1, label); } catch (MelderError) { Melder_throw (me, ": column \"", label, "\" not appended."); } } void Table_checkSpecifiedRowNumberWithinRange (Table me, long rowNumber) { if (rowNumber < 1) Melder_throw (me, ": the specified row number is ", rowNumber, ", but should be at least 1."); if (rowNumber > my rows -> size) Melder_throw (me, ": the specified row number (", rowNumber, ") exceeds my number of rows (", my rows -> size, ")."); } void Table_removeRow (Table me, long rowNumber) { try { if (my rows -> size == 1) Melder_throw (me, ": cannot remove my only row."); Table_checkSpecifiedRowNumberWithinRange (me, rowNumber); Collection_removeItem (my rows, rowNumber); for (long icol = 1; icol <= my numberOfColumns; icol ++) my columnHeaders [icol]. numericized = FALSE; } catch (MelderError) { Melder_throw (me, ": row ", rowNumber, " not removed."); } } void Table_checkSpecifiedColumnNumberWithinRange (Table me, long columnNumber) { if (columnNumber < 1) Melder_throw (me, ": the specified column number is ", columnNumber, ", but should be at least 1."); if (columnNumber > my numberOfColumns) Melder_throw (me, ": the specified column number is ", columnNumber, ", but should be at most my number of columns (", my numberOfColumns, ")."); } void Table_removeColumn (Table me, long columnNumber) { try { if (my numberOfColumns == 1) Melder_throw (me, ": cannot remove my only column."); Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); /* * Changes without error. */ Melder_free (my columnHeaders [columnNumber]. label); for (long icol = columnNumber; icol < my numberOfColumns; icol ++) my columnHeaders [icol] = my columnHeaders [icol + 1]; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); Melder_free (row -> cells [columnNumber]. string); for (long icol = columnNumber; icol < row -> numberOfColumns; icol ++) row -> cells [icol] = row -> cells [icol + 1]; row -> numberOfColumns --; } my numberOfColumns --; } catch (MelderError) { Melder_throw (me, ": column ", columnNumber, " not removed."); } } void Table_insertRow (Table me, long rowNumber) { try { /* * Check without changes. */ if (rowNumber < 1) Melder_throw (me, ": the specified row number is ", rowNumber, ", but should be at least 1."); if (rowNumber > my rows -> size + 1) Melder_throw (me, ": the specified row number is ", rowNumber, ", but should be at most my number of rows (", my rows -> size, ") plus 1."); autoTableRow row = TableRow_create (my numberOfColumns); /* * Safe change. */ Ordered_addItemPos (my rows, row.transfer(), rowNumber); therror /* * Changes without error. */ for (long icol = 1; icol <= my numberOfColumns; icol ++) my columnHeaders [icol]. numericized = FALSE; } catch (MelderError) { Melder_throw (me, ": row ", rowNumber, " not inserted."); } } void Table_insertColumn (Table me, long columnNumber, const wchar *label) { try { /* * Check without changes. */ if (columnNumber < 1) Melder_throw (me, ": the specified column number is ", columnNumber, ", but should be at least 1."); if (columnNumber > my numberOfColumns + 1) Melder_throw (me, ": the specified column number is ", columnNumber, ", but should be at most my number of columns (", my numberOfColumns, ") plus 1."); autoTable thee = Table_createWithoutColumnNames (my rows -> size, my numberOfColumns + 1); autostring newLabel = Melder_wcsdup (label); /* * Changes without error. */ /* * Transfer column headers to larger structure. */ for (long icol = 1; icol < columnNumber; icol ++) { Melder_assert (thy columnHeaders [icol]. label == NULL); // make room... thy columnHeaders [icol] = my columnHeaders [icol]; // ...fill in and dangle... my columnHeaders [icol]. label = NULL; // ...undangle } thy columnHeaders [columnNumber]. label = newLabel.transfer(); thy columnHeaders [columnNumber]. numericized = false; for (long icol = my numberOfColumns + 1; icol > columnNumber; icol --) { Melder_assert (thy columnHeaders [icol]. label == NULL); // make room... thy columnHeaders [icol] = my columnHeaders [icol - 1]; // ...fill in and dangle... my columnHeaders [icol - 1]. label = NULL; // ...undangle } /* * Transfer rows to larger structure. */ for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow myRow = static_cast (my rows -> item [irow]), thyRow = static_cast (thy rows -> item [irow]); for (long icol = 1; icol < columnNumber; icol ++) { Melder_assert (thyRow -> cells [icol]. string == NULL); // make room... thyRow -> cells [icol] = myRow -> cells [icol]; // ...fill in and dangle... myRow -> cells [icol]. string = NULL; // ...undangle } Melder_assert (thyRow -> cells [columnNumber]. string == NULL); Melder_assert (thyRow -> cells [columnNumber]. number == 0.0); for (long icol = myRow -> numberOfColumns + 1; icol > columnNumber; icol --) { Melder_assert (thyRow -> cells [icol]. string == NULL); // make room... thyRow -> cells [icol] = myRow -> cells [icol - 1]; // ...fill in and dangle... myRow -> cells [icol - 1]. string = NULL; // ...undangle } } /* * Transfer larger structure with column headers to me. */ NUMvector_free (my columnHeaders, 1); // make room... my columnHeaders = thy columnHeaders; // ...fill in and dangle... thy columnHeaders = NULL; // ...undangle /* * Transfer larger structure with rows to me. */ forget (my rows); // make room... my rows = thy rows; // ...fill in and dangle... thy rows = NULL; // ...undangle /* * Update my state. */ my numberOfColumns ++; } catch (MelderError) { Melder_throw (me, ": column not inserted."); } } void Table_setColumnLabel (Table me, long columnNumber, const wchar *label) { try { /* * Check without changes. */ Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); autostring newLabel = Melder_wcsdup (label); /* * Changes without error. */ Melder_free (my columnHeaders [columnNumber]. label); my columnHeaders [columnNumber]. label = newLabel.transfer(); } catch (MelderError) { Melder_throw (me, ": column label not set."); } } long Table_findColumnIndexFromColumnLabel (Table me, const wchar *label) { for (long icol = 1; icol <= my numberOfColumns; icol ++) if (my columnHeaders [icol]. label && wcsequ (my columnHeaders [icol]. label, label)) return icol; return 0; } long Table_getColumnIndexFromColumnLabel (Table me, const wchar *columnLabel) { long columnNumber = Table_findColumnIndexFromColumnLabel (me, columnLabel); if (columnNumber == 0) Melder_throw (me, ": there is no column named \"", columnLabel, "\"."); return columnNumber; } long * Table_getColumnIndicesFromColumnLabelString (Table me, const wchar *string, long *numberOfTokens) { *numberOfTokens = 0; autoMelderTokens tokens (string, numberOfTokens); if (*numberOfTokens < 1) Melder_throw (me, ": you specified an empty list of columns."); autoNUMvector columns (1, *numberOfTokens); for (long icol = 1; icol <= *numberOfTokens; icol ++) { columns [icol] = Table_getColumnIndexFromColumnLabel (me, tokens [icol]); } return columns.transfer(); } long Table_searchColumn (Table me, long columnNumber, const wchar *value) { for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [columnNumber]. string != NULL && wcsequ (row -> cells [columnNumber]. string, value)) return irow; } return 0; } void Table_setStringValue (Table me, long rowNumber, long columnNumber, const wchar *value) { try { /* * Check without changes. */ Table_checkSpecifiedRowNumberWithinRange (me, rowNumber); Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); autostring newValue = Melder_wcsdup (value); /* * Change without errors. */ TableRow row = static_cast (my rows -> item [rowNumber]); Melder_free (row -> cells [columnNumber]. string); row -> cells [columnNumber]. string = newValue.transfer(); my columnHeaders [columnNumber]. numericized = FALSE; } catch (MelderError) { Melder_throw (me, ": string value not set."); } } void Table_setNumericValue (Table me, long rowNumber, long columnNumber, double value) { try { /* * Check without changes. */ Table_checkSpecifiedRowNumberWithinRange (me, rowNumber); Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); autostring newValue = Melder_wcsdup (Melder_double (value)); /* * Change without errors. */ TableRow row = static_cast (my rows -> item [rowNumber]); Melder_free (row -> cells [columnNumber]. string); row -> cells [columnNumber]. string = newValue.transfer(); my columnHeaders [columnNumber]. numericized = FALSE; } catch (MelderError) { Melder_throw (me, ": numeric value not set."); } } static bool Table_isCellNumeric_ErrorFalse (Table me, long rowNumber, long columnNumber) { if (rowNumber < 1 || rowNumber > my rows -> size) return false; if (columnNumber < 1 || columnNumber > my numberOfColumns) return false; TableRow row = static_cast (my rows -> item [rowNumber]); const wchar *cell = row -> cells [columnNumber]. string; if (cell == NULL) return true; // the value --undefined-- /* * Skip leading white space, in order to separately detect "?" and "--undefined--". */ while (*cell == ' ' || *cell == '\t' || *cell == '\n' || *cell == '\r') cell ++; if (cell [0] == '\0') return true; // only white space: the value --undefined-- if (cell [0] == '?' || wcsnequ (cell, L"--undefined--", 13)) { /* * See whether there is anything else besides "?" or "--undefined--" and white space. */ cell += ( cell [0] == '?' ) ? 1 : 13; while (*cell == ' ' || *cell == '\t' || *cell == '\n' || *cell == '\r') cell ++; return *cell == '\0'; // only white space after the "?" or "--undefined--" } return Melder_isStringNumeric_nothrow (cell); } static bool Table_isColumnNumeric_ErrorFalse (Table me, long columnNumber) { if (columnNumber < 1 || columnNumber > my numberOfColumns) return false; for (long irow = 1; irow <= my rows -> size; irow ++) { if (! Table_isCellNumeric_ErrorFalse (me, irow, columnNumber)) return false; } return true; } static long stringCompare_column; static int stringCompare_NoError (const void *first, const void *second) { TableRow me = * (TableRow *) first, thee = * (TableRow *) second; wchar *firstString = my cells [stringCompare_column]. string; wchar *secondString = thy cells [stringCompare_column]. string; return wcscmp (firstString ? firstString : L"", secondString ? secondString : L""); } static void sortRowsByStrings_Assert (Table me, long columnNumber) { Melder_assert (columnNumber >= 1 && columnNumber <= my numberOfColumns); stringCompare_column = columnNumber; qsort (& my rows -> item [1], (unsigned long) my rows -> size, sizeof (TableRow), stringCompare_NoError); } static int indexCompare_NoError (const void *first, const void *second) { TableRow me = * (TableRow *) first, thee = * (TableRow *) second; if (my sortingIndex < thy sortingIndex) return -1; if (my sortingIndex > thy sortingIndex) return +1; return 0; } static void sortRowsByIndex_NoError (Table me) { qsort (& my rows -> item [1], (unsigned long) my rows -> size, sizeof (TableRow), indexCompare_NoError); } void Table_numericize_Assert (Table me, long columnNumber) { Melder_assert (columnNumber >= 1 && columnNumber <= my numberOfColumns); if (my columnHeaders [columnNumber]. numericized) return; if (Table_isColumnNumeric_ErrorFalse (me, columnNumber)) { for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); const wchar *string = row -> cells [columnNumber]. string; row -> cells [columnNumber]. number = string == NULL || string [0] == '\0' || (string [0] == '?' && string [1] == '\0') ? NUMundefined : Melder_atof (string); } } else { long iunique = 0; const wchar *previousString = NULL; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); row -> sortingIndex = irow; } sortRowsByStrings_Assert (me, columnNumber); for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); const wchar *string = row -> cells [columnNumber]. string; if (string == NULL) string = L""; if (previousString == NULL || ! wcsequ (string, previousString)) { iunique ++; } row -> cells [columnNumber]. number = iunique; previousString = string; } sortRowsByIndex_NoError (me); } my columnHeaders [columnNumber]. numericized = TRUE; } static void Table_numericize_checkDefined (Table me, long columnNumber) { Table_numericize_Assert (me, columnNumber); for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [columnNumber]. number == NUMundefined) Melder_throw (me, ": the cell in row ", irow, " of column \"", my columnHeaders [columnNumber]. label ? my columnHeaders [columnNumber]. label : Melder_integer (columnNumber), " is undefined."); } } const wchar * Table_getStringValue_Assert (Table me, long rowNumber, long columnNumber) { Melder_assert (rowNumber >= 1 && rowNumber <= my rows -> size); Melder_assert (columnNumber >= 1 && columnNumber <= my numberOfColumns); TableRow row = static_cast (my rows -> item [rowNumber]); return row -> cells [columnNumber]. string ? row -> cells [columnNumber]. string : L""; } double Table_getNumericValue_Assert (Table me, long rowNumber, long columnNumber) { Melder_assert (rowNumber >= 1 && rowNumber <= my rows -> size); Melder_assert (columnNumber >= 1 && columnNumber <= my numberOfColumns); TableRow row = static_cast (my rows -> item [rowNumber]); Table_numericize_Assert (me, columnNumber); return row -> cells [columnNumber]. number; } double Table_getMean (Table me, long columnNumber) { try { Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); Table_numericize_checkDefined (me, columnNumber); if (my rows -> size < 1) return NUMundefined; double sum = 0.0; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); sum += row -> cells [columnNumber]. number; } return sum / my rows -> size; } catch (MelderError) { Melder_throw (me, ": cannot compute mean of column ", columnNumber, "."); } } double Table_getMaximum (Table me, long columnNumber) { try { Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); Table_numericize_checkDefined (me, columnNumber); if (my rows -> size < 1) return NUMundefined; TableRow firstRow = static_cast (my rows -> item [1]); double maximum = firstRow -> cells [columnNumber]. number; for (long irow = 2; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [columnNumber]. number > maximum) maximum = row -> cells [columnNumber]. number; } return maximum; } catch (MelderError) { Melder_throw (me, ": cannot compute maximum of column ", columnNumber, "."); } } double Table_getMinimum (Table me, long columnNumber) { try { Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); Table_numericize_checkDefined (me, columnNumber); if (my rows -> size < 1) return NUMundefined; TableRow firstRow = static_cast (my rows -> item [1]); double minimum = firstRow -> cells [columnNumber]. number; for (long irow = 2; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [columnNumber]. number < minimum) minimum = row -> cells [columnNumber]. number; } return minimum; } catch (MelderError) { Melder_throw (me, ": cannot compute minimum of column ", columnNumber, "."); } } double Table_getGroupMean (Table me, long columnNumber, long groupColumnNumber, const wchar *group) { try { Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); Table_numericize_checkDefined (me, columnNumber); long n = 0; double sum = 0.0; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (Melder_wcsequ (row -> cells [groupColumnNumber]. string, group)) { n += 1; sum += row -> cells [columnNumber]. number; } } if (n < 1) return NUMundefined; double mean = sum / n; return mean; } catch (MelderError) { Melder_throw (me, ": cannot compute mean of column ", columnNumber, " for group \"", group, "\" of column ", groupColumnNumber, "."); } } double Table_getQuantile (Table me, long columnNumber, double quantile) { try { Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); Table_numericize_checkDefined (me, columnNumber); if (my rows -> size < 1) return NUMundefined; autoNUMvector sortingColumn (1, my rows -> size); for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); sortingColumn [irow] = row -> cells [columnNumber]. number; } NUMsort_d (my rows -> size, sortingColumn.peek()); return NUMquantile (my rows -> size, sortingColumn.peek(), quantile); } catch (MelderError) { Melder_throw (me, ": cannot compute the ", quantile, " quantile of column ", columnNumber, "."); } } double Table_getStdev (Table me, long columnNumber) { try { double mean = Table_getMean (me, columnNumber); // already checks for columnNumber and undefined cells if (my rows -> size < 2) return NUMundefined; double sum = 0.0; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); double d = row -> cells [columnNumber]. number - mean; sum += d * d; } return sqrt (sum / (my rows -> size - 1)); } catch (MelderError) { Melder_throw (me, ": cannot compute the standard deviation of column ", columnNumber, "."); } } long Table_drawRowFromDistribution (Table me, long columnNumber) { try { Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); Table_numericize_checkDefined (me, columnNumber); if (my rows -> size < 1) Melder_throw (me, ": no rows."); double total = 0.0; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); total += row -> cells [columnNumber]. number; } if (total <= 0.0) Melder_throw (me, ": the total weight of column ", columnNumber, " is not positive."); long irow; do { double rand = NUMrandomUniform (0, total), sum = 0.0; for (irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); sum += row -> cells [columnNumber]. number; if (rand <= sum) break; } } while (irow > my rows -> size); /* Guard against rounding errors. */ return irow; } catch (MelderError) { Melder_throw (me, ": cannot draw a row from the distribution of column ", columnNumber, "."); } } Table Table_extractRowsWhereColumn_number (Table me, long columnNumber, int which_Melder_NUMBER, double criterion) { try { Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); Table_numericize_Assert (me, columnNumber); // extraction should work even if cells are not defined autoTable thee = Table_create (0, my numberOfColumns); for (long icol = 1; icol <= my numberOfColumns; icol ++) { thy columnHeaders [icol]. label = Melder_wcsdup (my columnHeaders [icol]. label); } for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (Melder_numberMatchesCriterion (row -> cells [columnNumber]. number, which_Melder_NUMBER, criterion)) { autoTableRow newRow = Data_copy (row); Collection_addItem (thy rows, newRow.transfer()); } } if (thy rows -> size == 0) { Melder_warning (L"No row matches criterion."); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": rows not extracted."); } } Table Table_extractRowsWhereColumn_string (Table me, long columnNumber, int which_Melder_STRING, const wchar *criterion) { try { Table_checkSpecifiedColumnNumberWithinRange (me, columnNumber); autoTable thee = Table_create (0, my numberOfColumns); for (long icol = 1; icol <= my numberOfColumns; icol ++) { autostring newLabel = Melder_wcsdup (my columnHeaders [icol]. label); thy columnHeaders [icol]. label = newLabel.transfer(); } for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (Melder_stringMatchesCriterion (row -> cells [columnNumber]. string, which_Melder_STRING, criterion)) { autoTableRow newRow = Data_copy (row); Collection_addItem (thy rows, newRow.transfer()); therror } } if (thy rows -> size == 0) { Melder_warning (L"No row matches criterion."); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": rows not extracted."); } } static void Table_columns_checkExist (Table me, wchar **columnNames, long n) { for (long i = 1; i <= n; i ++) { if (Table_findColumnIndexFromColumnLabel (me, columnNames [i]) == 0) Melder_throw (me, ": column \"", columnNames [i], "\" does not exist."); } } static void Table_columns_checkCrossSectionEmpty (wchar **factors, long nfactors, wchar **vars, long nvars) { for (long ifactor = 1; ifactor <= nfactors; ifactor ++) { for (long ivar = 1; ivar <= nvars; ivar ++) { if (wcsequ (factors [ifactor], vars [ivar])) Melder_throw ("Factor \"", factors [ifactor], "\" is also used as dependent variable."); } } } Table Table_collapseRows (Table me, const wchar *factors_string, const wchar *columnsToSum_string, const wchar *columnsToAverage_string, const wchar *columnsToMedianize_string, const wchar *columnsToAverageLogarithmically_string, const wchar *columnsToMedianizeLogarithmically_string) { bool originalChanged = false; try { Melder_assert (factors_string != NULL); /* * Parse the six strings of tokens. */ long numberOfFactors; autoMelderTokens factors (factors_string, & numberOfFactors); if (numberOfFactors < 1) Melder_throw ("In order to pool table data, you must supply at least one independent variable."); Table_columns_checkExist (me, factors.peek(), numberOfFactors); long numberToSum; autoMelderTokens columnsToSum; if (columnsToSum_string) { columnsToSum.reset (columnsToSum_string, & numberToSum); Table_columns_checkExist (me, columnsToSum.peek(), numberToSum); Table_columns_checkCrossSectionEmpty (factors.peek(), numberOfFactors, columnsToSum.peek(), numberToSum); } long numberToAverage; autoMelderTokens columnsToAverage; if (columnsToAverage_string) { columnsToAverage.reset (columnsToAverage_string, & numberToAverage); Table_columns_checkExist (me, columnsToAverage.peek(), numberToAverage); Table_columns_checkCrossSectionEmpty (factors.peek(), numberOfFactors, columnsToAverage.peek(), numberToAverage); } long numberToMedianize; autoMelderTokens columnsToMedianize; if (columnsToMedianize_string) { columnsToMedianize.reset (columnsToMedianize_string, & numberToMedianize); Table_columns_checkExist (me, columnsToMedianize.peek(), numberToMedianize); Table_columns_checkCrossSectionEmpty (factors.peek(), numberOfFactors, columnsToMedianize.peek(), numberToMedianize); } long numberToAverageLogarithmically; autoMelderTokens columnsToAverageLogarithmically; if (columnsToAverageLogarithmically_string) { columnsToAverageLogarithmically.reset (columnsToAverageLogarithmically_string, & numberToAverageLogarithmically); Table_columns_checkExist (me, columnsToAverageLogarithmically.peek(), numberToAverageLogarithmically); Table_columns_checkCrossSectionEmpty (factors.peek(), numberOfFactors, columnsToAverageLogarithmically.peek(), numberToAverageLogarithmically); } long numberToMedianizeLogarithmically; autoMelderTokens columnsToMedianizeLogarithmically; if (columnsToMedianizeLogarithmically_string) { columnsToMedianizeLogarithmically.reset (columnsToMedianizeLogarithmically_string, & numberToMedianizeLogarithmically); Table_columns_checkExist (me, columnsToMedianizeLogarithmically.peek(), numberToMedianizeLogarithmically); Table_columns_checkCrossSectionEmpty (factors.peek(), numberOfFactors, columnsToMedianizeLogarithmically.peek(), numberToMedianizeLogarithmically); } autoTable thee = Table_createWithoutColumnNames (0, numberOfFactors + numberToSum + numberToAverage + numberToMedianize + numberToAverageLogarithmically + numberToMedianizeLogarithmically); Melder_assert (thy numberOfColumns > 0); autoNUMvector sortingColumn; if (numberToMedianize > 0 || numberToMedianizeLogarithmically > 0) { sortingColumn.reset (1, my rows -> size); } /* * Set the column names. Within the dependent variables, the same name may occur more than once. */ autoNUMvector columns (1, thy numberOfColumns); { long icol = 0; for (long i = 1; i <= numberOfFactors; i ++) { Table_setColumnLabel (thee.peek(), ++ icol, factors [i]); columns [icol] = Table_findColumnIndexFromColumnLabel (me, factors [i]); } for (long i = 1; i <= numberToSum; i ++) { Table_setColumnLabel (thee.peek(), ++ icol, columnsToSum [i]); columns [icol] = Table_findColumnIndexFromColumnLabel (me, columnsToSum [i]); } for (long i = 1; i <= numberToAverage; i ++) { Table_setColumnLabel (thee.peek(), ++ icol, columnsToAverage [i]); columns [icol] = Table_findColumnIndexFromColumnLabel (me, columnsToAverage [i]); } for (long i = 1; i <= numberToMedianize; i ++) { Table_setColumnLabel (thee.peek(), ++ icol, columnsToMedianize [i]); columns [icol] = Table_findColumnIndexFromColumnLabel (me, columnsToMedianize [i]); } for (long i = 1; i <= numberToAverageLogarithmically; i ++) { Table_setColumnLabel (thee.peek(), ++ icol, columnsToAverageLogarithmically [i]); columns [icol] = Table_findColumnIndexFromColumnLabel (me, columnsToAverageLogarithmically [i]); } for (long i = 1; i <= numberToMedianizeLogarithmically; i ++) { Table_setColumnLabel (thee.peek(), ++ icol, columnsToMedianizeLogarithmically [i]); columns [icol] = Table_findColumnIndexFromColumnLabel (me, columnsToMedianizeLogarithmically [i]); } Melder_assert (icol == thy numberOfColumns); } /* * Make sure that all the columns in the original table that we will use in the pooled table are defined. */ for (long icol = 1; icol <= thy numberOfColumns; icol ++) { Table_numericize_checkDefined (me, columns [icol]); } /* * Remember the present sorting of the original table. * (This is safe: the sorting index may change only vacuously when numericizing.) * But this cannot be done before the previous block! */ for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); row -> sortingIndex = irow; } /* * We will now sort the original table temporarily, by the factors (independent variables) only. */ Table_sortRows_Assert (me, columns.peek(), numberOfFactors); /* This works only because the factors come first. */ originalChanged = true; /* * Find stretches of identical factors. */ for (long irow = 1; irow <= my rows -> size; irow ++) { long rowmin = irow, rowmax = irow; for (;;) { bool identical = true; if (++ rowmax > my rows -> size) break; for (long icol = 1; icol <= numberOfFactors; icol ++) { if (((TableRow) my rows -> item [rowmax]) -> cells [columns [icol]]. number != ((TableRow) my rows -> item [rowmin]) -> cells [columns [icol]]. number) { identical = false; break; } } if (! identical) break; } rowmax --; /* * We have the stretch. */ Table_insertRow (thee.peek(), thy rows -> size + 1); therror { long icol = 0; for (long i = 1; i <= numberOfFactors; i ++) { ++ icol; Table_setStringValue (thee.peek(), thy rows -> size, icol, ((TableRow) my rows -> item [rowmin]) -> cells [columns [icol]]. string); therror } for (long i = 1; i <= numberToSum; i ++) { ++ icol; double sum = 0.0; for (long jrow = rowmin; jrow <= rowmax; jrow ++) { sum += ((TableRow) my rows -> item [jrow]) -> cells [columns [icol]]. number; } Table_setNumericValue (thee.peek(), thy rows -> size, icol, sum); therror } for (long i = 1; i <= numberToAverage; i ++) { ++ icol; double sum = 0.0; for (long jrow = rowmin; jrow <= rowmax; jrow ++) { sum += ((TableRow) my rows -> item [jrow]) -> cells [columns [icol]]. number; } Table_setNumericValue (thee.peek(), thy rows -> size, icol, sum / (rowmax - rowmin + 1)); therror } for (long i = 1; i <= numberToMedianize; i ++) { ++ icol; for (long jrow = rowmin; jrow <= rowmax; jrow ++) { sortingColumn [jrow] = ((TableRow) my rows -> item [jrow]) -> cells [columns [icol]]. number; } NUMsort_d (rowmax - rowmin + 1, & sortingColumn [rowmin - 1]); double median = NUMquantile (rowmax - rowmin + 1, & sortingColumn [rowmin - 1], 0.5); Table_setNumericValue (thee.peek(), thy rows -> size, icol, median); therror } for (long i = 1; i <= numberToAverageLogarithmically; i ++) { ++ icol; double sum = 0.0; for (long jrow = rowmin; jrow <= rowmax; jrow ++) { double value = ((TableRow) my rows -> item [jrow]) -> cells [columns [icol]]. number; if (value <= 0.0) Melder_throw ( "The cell in column \"", columnsToAverageLogarithmically [i], "\" of row ", jrow, " of ", me, " is not positive.\nCannot average logarithmically."); sum += log (value); } Table_setNumericValue (thee.peek(), thy rows -> size, icol, exp (sum / (rowmax - rowmin + 1))); therror } for (long i = 1; i <= numberToMedianizeLogarithmically; i ++) { ++ icol; for (long jrow = rowmin; jrow <= rowmax; jrow ++) { double value = ((TableRow) my rows -> item [jrow]) -> cells [columns [icol]]. number; if (value <= 0.0) Melder_throw ( "The cell in column \"", columnsToMedianizeLogarithmically [i], "\" of row ", jrow, " of ", me, " is not positive.\nCannot medianize logarithmically."); sortingColumn [jrow] = log (value); } NUMsort_d (rowmax - rowmin + 1, & sortingColumn [rowmin - 1]); double median = NUMquantile (rowmax - rowmin + 1, & sortingColumn [rowmin - 1], 0.5); Table_setNumericValue (thee.peek(), thy rows -> size, icol, exp (median)); therror } Melder_assert (icol == thy numberOfColumns); } irow = rowmax; } if (originalChanged) sortRowsByIndex_NoError (me); // unsort the original table return thee.transfer(); } catch (MelderError) { if (originalChanged) sortRowsByIndex_NoError (me); // unsort the original table // UGLY throw; return NULL; } } static wchar ** _Table_getLevels (Table me, long column, long *numberOfLevels) { try { for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); row -> sortingIndex = irow; } long columns [2] = { 0, column }; Table_sortRows_Assert (me, columns, 1); *numberOfLevels = 0; long irow = 1; while (irow <= my rows -> size) { double value = ((TableRow) my rows -> item [irow]) -> cells [column]. number; (*numberOfLevels) ++; while (++ irow <= my rows -> size && ((TableRow) my rows -> item [irow]) -> cells [column]. number == value) { } } autostringvector result (1, *numberOfLevels); *numberOfLevels = 0; irow = 1; while (irow <= my rows -> size) { double value = ((TableRow) my rows -> item [irow]) -> cells [column]. number; result [++ *numberOfLevels] = Melder_wcsdup (Table_getStringValue_Assert (me, irow, column)); while (++ irow <= my rows -> size && ((TableRow) my rows -> item [irow]) -> cells [column]. number == value) { } } sortRowsByIndex_NoError (me); // unsort the original table return result.transfer(); } catch (MelderError) { sortRowsByIndex_NoError (me); // unsort the original table // UGLY throw; return NULL; } } Table Table_rowsToColumns (Table me, const wchar *factors_string, long columnToTranspose, const wchar *columnsToExpand_string) { bool originalChanged = false; try { Melder_assert (factors_string != NULL); long numberOfFactors = 0, numberToExpand = 0, numberOfLevels = 0; bool warned = false; /* * Parse the two strings of tokens. */ autoMelderTokens factors_names (factors_string, & numberOfFactors); if (numberOfFactors < 1) Melder_throw ("In order to nest table data, you must supply at least one independent variable."); Table_columns_checkExist (me, factors_names.peek(), numberOfFactors); autoMelderTokens columnsToExpand_names (columnsToExpand_string, & numberToExpand); if (numberToExpand < 1) Melder_throw ("In order to nest table data, you must supply at least one dependent variable (to expand)."); Table_columns_checkExist (me, columnsToExpand_names.peek(), numberToExpand); Table_columns_checkCrossSectionEmpty (factors_names.peek(), numberOfFactors, columnsToExpand_names.peek(), numberToExpand); wchar ** dummy = _Table_getLevels (me, columnToTranspose, & numberOfLevels); autostringvector levels_names (dummy, 1, numberOfLevels); /* * Get the column numbers for the factors. */ autoNUMvector factorColumns (1, numberOfFactors); for (long ifactor = 1; ifactor <= numberOfFactors; ifactor ++) { factorColumns [ifactor] = Table_findColumnIndexFromColumnLabel (me, factors_names [ifactor]); /* * Make sure that all the columns in the original table that we will use in the nested table are defined. */ Table_numericize_checkDefined (me, factorColumns [ifactor]); } /* * Get the column numbers for the expandable variables. */ autoNUMvector columnsToExpand (1, numberToExpand); for (long iexpand = 1; iexpand <= numberToExpand; iexpand ++) { columnsToExpand [iexpand] = Table_findColumnIndexFromColumnLabel (me, columnsToExpand_names [iexpand]); Table_numericize_checkDefined (me, columnsToExpand [iexpand]); } /* * Create the new table, with column names. */ autoTable thee = Table_createWithoutColumnNames (0, numberOfFactors + (numberOfLevels * numberToExpand)); Melder_assert (thy numberOfColumns > 0); for (long ifactor = 1; ifactor <= numberOfFactors; ifactor ++) { Table_setColumnLabel (thee.peek(), ifactor, factors_names [ifactor]); } autoMelderString columnLabel; for (long iexpand = 1; iexpand <= numberToExpand; iexpand ++) { for (long ilevel = 1; ilevel <= numberOfLevels; ilevel ++) { MelderString_copy (& columnLabel, columnsToExpand_names [iexpand]); therror MelderString_appendCharacter (& columnLabel, '.'); therror MelderString_append (& columnLabel, levels_names [ilevel]); therror Table_setColumnLabel (thee.peek(), numberOfFactors + (iexpand - 1) * numberOfLevels + ilevel, columnLabel.string); therror } } /* * Remember the present sorting of the original table. * (This is safe: the sorting index may change only vacuously when numericizing.) * But this cannot be done before the previous blocks that numericize! */ for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); row -> sortingIndex = irow; } /* * We will now sort the original table temporarily, by the factors (independent variables) only. */ Table_sortRows_Assert (me, factorColumns.peek(), numberOfFactors); originalChanged = true; /* * Find stretches of identical factors. */ for (long irow = 1; irow <= my rows -> size; irow ++) { long rowmin = irow, rowmax = irow; for (;;) { bool identical = true; if (++ rowmax > my rows -> size) break; for (long ifactor = 1; ifactor <= numberOfFactors; ifactor ++) { if (((TableRow) my rows -> item [rowmax]) -> cells [factorColumns [ifactor]]. number != ((TableRow) my rows -> item [rowmin]) -> cells [factorColumns [ifactor]]. number) { identical = false; break; } } if (! identical) break; } #if 0 if (rowmax - rowmin > numberOfLevels && ! warned) { Melder_warning (L"Some rows of the original table have not been included in the new table. " "You could perhaps add more factors."); warned = true; } #endif rowmax --; /* * We have the stretch. */ Table_insertRow (thee.peek(), thy rows -> size + 1); therror TableRow thyRow = static_cast (thy rows -> item [thy rows -> size]); for (long ifactor = 1; ifactor <= numberOfFactors; ifactor ++) { Table_setStringValue (thee.peek(), thy rows -> size, ifactor, ((TableRow) my rows -> item [rowmin]) -> cells [factorColumns [ifactor]]. string); therror } for (long iexpand = 1; iexpand <= numberToExpand; iexpand ++) { for (long jrow = rowmin; jrow <= rowmax; jrow ++) { TableRow myRow = static_cast (my rows -> item [jrow]); double value = myRow -> cells [columnsToExpand [iexpand]]. number; long level = myRow -> cells [columnToTranspose]. number; long thyColumn = numberOfFactors + (iexpand - 1) * numberOfLevels + level; if (thyRow -> cells [thyColumn]. string != NULL && ! warned) { Melder_warning (L"Some information from the original table has not been included in the new table. " "You could perhaps add more factors."); warned = true; } Table_setNumericValue (thee.peek(), thy rows -> size, thyColumn, value); therror } } irow = rowmax; } if (originalChanged) sortRowsByIndex_NoError (me); // unsort the original table return thee.transfer(); } catch (MelderError) { if (originalChanged) sortRowsByIndex_NoError (me); // unsort the original table // UGLY throw; return NULL; } } static long *cellCompare_columns, cellCompare_numberOfColumns; static int cellCompare_NoError (const void *first, const void *second) { TableRow me = * (TableRow *) first, thee = * (TableRow *) second; for (long icol = 1; icol <= cellCompare_numberOfColumns; icol ++) { if (my cells [cellCompare_columns [icol]]. number < thy cells [cellCompare_columns [icol]]. number) return -1; if (my cells [cellCompare_columns [icol]]. number > thy cells [cellCompare_columns [icol]]. number) return +1; } return 0; } void Table_sortRows_Assert (Table me, long *columns, long numberOfColumns) { for (long icol = 1; icol <= numberOfColumns; icol ++) { Table_numericize_Assert (me, columns [icol]); } cellCompare_columns = columns; cellCompare_numberOfColumns = numberOfColumns; qsort (& my rows -> item [1], (unsigned long) my rows -> size, sizeof (TableRow), cellCompare_NoError); } void Table_sortRows_string (Table me, const wchar *columns_string) { try { long numberOfColumns; autoMelderTokens columns_tokens (columns_string, & numberOfColumns); if (numberOfColumns < 1) Melder_throw (me, ": you specified an empty list of columns."); autoNUMvector columns (1, numberOfColumns); for (long icol = 1; icol <= numberOfColumns; icol ++) { columns [icol] = Table_findColumnIndexFromColumnLabel (me, columns_tokens [icol]); if (columns [icol] == 0) Melder_throw ("Column \"", columns_tokens [icol], L"\" does not exist."); } Table_sortRows_Assert (me, columns.peek(), numberOfColumns); } catch (MelderError) { Melder_throw (me, ": rows not sorted."); } } void Table_randomizeRows (Table me) { for (long irow = 1; irow <= my rows -> size; irow ++) { long jrow = NUMrandomInteger (irow, my rows -> size); TableRow tmp = static_cast (my rows -> item [irow]); my rows -> item [irow] = my rows -> item [jrow]; my rows -> item [jrow] = tmp; } } Table Tables_append (Collection me) { try { if (my size == 0) Melder_throw ("Cannot add zero tables."); Table thee = static_cast
(my item [1]); long nrow = thy rows -> size; long ncol = thy numberOfColumns; Table firstTable = thee; for (long itab = 2; itab <= my size; itab ++) { thee = static_cast
(my item [itab]); nrow += thy rows -> size; if (thy numberOfColumns != ncol) Melder_throw ("Numbers of columns do not match."); for (long icol = 1; icol <= ncol; icol ++) { if (! Melder_wcsequ (thy columnHeaders [icol]. label, firstTable -> columnHeaders [icol]. label)) Melder_throw ("The label of column ", icol, " of ", thee, " (", thy columnHeaders [icol]. label, L") does not match the label of column ", icol, " of ", firstTable, " (", firstTable -> columnHeaders [icol]. label, ")."); } } autoTable him = Table_createWithoutColumnNames (nrow, ncol); for (long icol = 1; icol <= ncol; icol ++) { Table_setColumnLabel (him.peek(), icol, thy columnHeaders [icol]. label); } nrow = 0; for (long itab = 1; itab <= my size; itab ++) { thee = static_cast
(my item [itab]); for (long irow = 1; irow <= thy rows -> size; irow ++) { nrow ++; for (long icol = 1; icol <= ncol; icol ++) { Table_setStringValue (him.peek(), nrow, icol, Table_getStringValue_Assert (thee, irow, icol)); therror } } } return him.transfer(); } catch (MelderError) { Melder_throw ("Table objects not appended."); } } void Table_appendSumColumn (Table me, long column1, long column2, const wchar *label) { // safe try { /* * Check without change. */ Table_checkSpecifiedColumnNumberWithinRange (me, column1); Table_checkSpecifiedColumnNumberWithinRange (me, column2); Table_numericize_checkDefined (me, column1); Table_numericize_checkDefined (me, column2); autoTable thee = Table_createWithoutColumnNames (my rows -> size, 1); for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow myRow = static_cast (my rows -> item [irow]); Table_setNumericValue (thee.peek(), irow, 1, myRow -> cells [column1]. number + myRow -> cells [column2]. number); therror } /* * Safe change. */ Table_appendColumn (me, label); therror /* * Change without error. */ for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow myRow = static_cast (my rows -> item [irow]); TableRow thyRow = static_cast (thy rows -> item [irow]); TableCell myCell = & myRow -> cells [my numberOfColumns]; TableCell thyCell = & thyRow -> cells [1]; Melder_assert (myCell -> string == NULL); // make room... myCell -> string = thyCell -> string; // ...fill in and dangle... thyCell -> string = NULL; // ...undangle } } catch (MelderError) { Melder_throw (me, ": sum column not appended."); } } void Table_appendDifferenceColumn (Table me, long column1, long column2, const wchar *label) { // safe try { /* * Check without change. */ Table_checkSpecifiedColumnNumberWithinRange (me, column1); Table_checkSpecifiedColumnNumberWithinRange (me, column2); Table_numericize_checkDefined (me, column1); Table_numericize_checkDefined (me, column2); autoTable thee = Table_createWithoutColumnNames (my rows -> size, 1); for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow myRow = static_cast (my rows -> item [irow]); Table_setNumericValue (thee.peek(), irow, 1, myRow -> cells [column1]. number - myRow -> cells [column2]. number); therror } /* * Safe change. */ Table_appendColumn (me, label); therror /* * Change without error. */ for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow myRow = static_cast (my rows -> item [irow]); TableRow thyRow = static_cast (thy rows -> item [irow]); TableCell myCell = & myRow -> cells [my numberOfColumns]; TableCell thyCell = & thyRow -> cells [1]; Melder_assert (myCell -> string == NULL); // make room... myCell -> string = thyCell -> string; // ...fill in and dangle... thyCell -> string = NULL; // ...undangle } } catch (MelderError) { Melder_throw (me, ": difference column not appended."); } } void Table_appendProductColumn (Table me, long column1, long column2, const wchar *label) { // safe try { /* * Check without change. */ Table_checkSpecifiedColumnNumberWithinRange (me, column1); Table_checkSpecifiedColumnNumberWithinRange (me, column2); Table_numericize_checkDefined (me, column1); Table_numericize_checkDefined (me, column2); autoTable thee = Table_createWithoutColumnNames (my rows -> size, 1); for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow myRow = static_cast (my rows -> item [irow]); Table_setNumericValue (thee.peek(), irow, 1, myRow -> cells [column1]. number * myRow -> cells [column2]. number); therror } /* * Safe change. */ Table_appendColumn (me, label); therror /* * Change without error. */ for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow myRow = static_cast (my rows -> item [irow]); TableRow thyRow = static_cast (thy rows -> item [irow]); TableCell myCell = & myRow -> cells [my numberOfColumns]; TableCell thyCell = & thyRow -> cells [1]; Melder_assert (myCell -> string == NULL); // make room... myCell -> string = thyCell -> string; // ...fill in and dangle... thyCell -> string = NULL; // ...undangle } } catch (MelderError) { Melder_throw (me, ": product column not appended."); } } void Table_appendQuotientColumn (Table me, long column1, long column2, const wchar *label) { // safe try { /* * Check without change. */ Table_checkSpecifiedColumnNumberWithinRange (me, column1); Table_checkSpecifiedColumnNumberWithinRange (me, column2); Table_numericize_checkDefined (me, column1); Table_numericize_checkDefined (me, column2); autoTable thee = Table_createWithoutColumnNames (my rows -> size, 1); for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow myRow = static_cast (my rows -> item [irow]); double value = myRow -> cells [column2]. number == 0.0 ? NUMundefined : myRow -> cells [column1]. number / myRow -> cells [column2]. number; Table_setNumericValue (thee.peek(), irow, 1, value); therror } /* * Safe change. */ Table_appendColumn (me, label); therror /* * Change without error. */ for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow myRow = static_cast (my rows -> item [irow]); TableRow thyRow = static_cast (thy rows -> item [irow]); TableCell myCell = & myRow -> cells [my numberOfColumns]; TableCell thyCell = & thyRow -> cells [1]; Melder_assert (myCell -> string == NULL); // make room... myCell -> string = thyCell -> string; // ...fill in and dangle... thyCell -> string = NULL; // ...undangle } } catch (MelderError) { Melder_throw (me, ": quotient column not appended."); } } void Table_formula_columnRange (Table me, long fromColumn, long toColumn, const wchar *expression, Interpreter interpreter) { try { Table_checkSpecifiedColumnNumberWithinRange (me, fromColumn); Table_checkSpecifiedColumnNumberWithinRange (me, toColumn); Formula_compile (interpreter, me, expression, kFormula_EXPRESSION_TYPE_UNKNOWN, TRUE); therror for (long irow = 1; irow <= my rows -> size; irow ++) { for (long icol = fromColumn; icol <= toColumn; icol ++) { struct Formula_Result result; Formula_run (irow, icol, & result); therror if (result. expressionType == kFormula_EXPRESSION_TYPE_STRING) { Table_setStringValue (me, irow, icol, result. result.stringResult); Melder_free (result. result.stringResult); } else if (result. expressionType == kFormula_EXPRESSION_TYPE_NUMERIC) { Table_setNumericValue (me, irow, icol, result. result.numericResult); } else if (result. expressionType == kFormula_EXPRESSION_TYPE_NUMERIC_ARRAY) { Melder_throw (me, ": cannot put arrays into cells."); } else if (result. expressionType == kFormula_EXPRESSION_TYPE_STRING_ARRAY) { Melder_throw (me, ": cannot put arrays into cells."); } } } } catch (MelderError) { Melder_throw (me, ": application of formula not completed."); } } void Table_formula (Table me, long icol, const wchar *expression, Interpreter interpreter) { Table_formula_columnRange (me, icol, icol, expression, interpreter); } double Table_getCorrelation_pearsonR (Table me, long column1, long column2, double significanceLevel, double *out_significance, double *out_lowerLimit, double *out_upperLimit) { long n = my rows -> size, irow; double correlation; double sum1 = 0.0, sum2 = 0.0, sum12 = 0.0, sum11 = 0.0, sum22 = 0.0, mean1, mean2; if (out_significance) *out_significance = NUMundefined; if (out_lowerLimit) *out_lowerLimit = NUMundefined; if (out_upperLimit) *out_upperLimit = NUMundefined; if (column1 < 1 || column1 > my numberOfColumns) return NUMundefined; if (column2 < 1 || column2 > my numberOfColumns) return NUMundefined; if (n < 2) return NUMundefined; Table_numericize_Assert (me, column1); Table_numericize_Assert (me, column2); for (irow = 1; irow <= n; irow ++) { TableRow row = static_cast (my rows -> item [irow]); sum1 += row -> cells [column1]. number; sum2 += row -> cells [column2]. number; } mean1 = sum1 / n; mean2 = sum2 / n; for (irow = 1; irow <= n; irow ++) { TableRow row = static_cast (my rows -> item [irow]); double d1 = row -> cells [column1]. number - mean1, d2 = row -> cells [column2]. number - mean2; sum12 += d1 * d2; sum11 += d1 * d1; sum22 += d2 * d2; } correlation = sum11 == 0.0 || sum22 == 0.0 ? NUMundefined : sum12 / sqrt (sum11 * sum22); if (out_significance && NUMdefined (correlation) && n >= 3) *out_significance = fabs (correlation) == 1.0 ? 0.0 : /* One-sided: */ NUMstudentQ (fabs (correlation) * sqrt ((n - 2) / (1 - correlation * correlation)), n - 2); if ((out_lowerLimit || out_upperLimit) && NUMdefined (correlation) && n >= 4) { if (fabs (correlation) == 1.0) { if (out_lowerLimit) *out_lowerLimit = correlation; if (out_upperLimit) *out_upperLimit = correlation; } else { double z = 0.5 * log ((1.0 + correlation) / (1.0 - correlation)); double dz = NUMinvGaussQ (significanceLevel) / sqrt (n - 3); if (out_lowerLimit) *out_lowerLimit = tanh (z - dz); if (out_upperLimit) *out_upperLimit = tanh (z + dz); } } return correlation; } double Table_getCorrelation_kendallTau (Table me, long column1, long column2, double significanceLevel, double *out_significance, double *out_lowerLimit, double *out_upperLimit) { long n = my rows -> size, irow, jrow; double correlation, denominator; long numberOfConcordants = 0, numberOfDiscordants = 0, numberOfExtra1 = 0, numberOfExtra2 = 0; if (out_significance) *out_significance = NUMundefined; if (out_lowerLimit) *out_lowerLimit = NUMundefined; if (out_upperLimit) *out_upperLimit = NUMundefined; if (column1 < 1 || column1 > my numberOfColumns) return NUMundefined; if (column2 < 1 || column2 > my numberOfColumns) return NUMundefined; Table_numericize_Assert (me, column1); Table_numericize_Assert (me, column2); for (irow = 1; irow < n; irow ++) { TableRow rowi = static_cast (my rows -> item [irow]); for (jrow = irow + 1; jrow <= n; jrow ++) { TableRow rowj = static_cast (my rows -> item [jrow]); double diff1 = rowi -> cells [column1]. number - rowj -> cells [column1]. number; double diff2 = rowi -> cells [column2]. number - rowj -> cells [column2]. number; double concord = diff1 * diff2; if (concord > 0.0) { numberOfConcordants ++; } else if (concord < 0.0) { numberOfDiscordants ++; } else if (diff1 != 0.0) { numberOfExtra1 ++; } else { numberOfExtra2 ++; } } } denominator = sqrt ((numberOfConcordants + numberOfDiscordants + numberOfExtra1) * (numberOfConcordants + numberOfDiscordants + numberOfExtra2)); correlation = denominator == 0.0 ? NUMundefined : (numberOfConcordants - numberOfDiscordants) / denominator; if ((out_significance || out_lowerLimit || out_upperLimit) && NUMdefined (correlation) && n >= 2) { double standardError = sqrt ((4 * n + 10.0) / (9 * n * (n - 1))); if (out_significance) *out_significance = NUMgaussQ (fabs (correlation) / standardError); /* One-sided. */ if (out_lowerLimit) *out_lowerLimit = correlation - NUMinvGaussQ (significanceLevel) * standardError; if (out_upperLimit) *out_upperLimit = correlation + NUMinvGaussQ (significanceLevel) * standardError; } return correlation; } double Table_getDifference_studentT (Table me, long column1, long column2, double significanceLevel, double *out_t, double *out_numberOfDegreesOfFreedom, double *out_significance, double *out_lowerLimit, double *out_upperLimit) { if (out_t) *out_t = NUMundefined; if (out_numberOfDegreesOfFreedom) *out_numberOfDegreesOfFreedom = NUMundefined; if (out_significance) *out_significance = NUMundefined; if (out_lowerLimit) *out_lowerLimit = NUMundefined; if (out_upperLimit) *out_upperLimit = NUMundefined; long n = my rows -> size; if (n < 1) return NUMundefined; if (column1 < 1 || column1 > my numberOfColumns) return NUMundefined; if (column2 < 1 || column2 > my numberOfColumns) return NUMundefined; Table_numericize_Assert (me, column1); Table_numericize_Assert (me, column2); double sum = 0.0; for (long irow = 1; irow <= n; irow ++) { TableRow row = static_cast (my rows -> item [irow]); sum += row -> cells [column1]. number - row -> cells [column2]. number; } double meanDifference = sum / n; long degreesOfFreedom = n - 1; if (out_numberOfDegreesOfFreedom) *out_numberOfDegreesOfFreedom = degreesOfFreedom; if (degreesOfFreedom >= 1 && (out_t || out_significance || out_lowerLimit || out_upperLimit)) { double sumOfSquares = 0.0; for (long irow = 1; irow <= n; irow ++) { TableRow row = static_cast (my rows -> item [irow]); double diff = (row -> cells [column1]. number - row -> cells [column2]. number) - meanDifference; sumOfSquares += diff * diff; } double standardError = sqrt (sumOfSquares / degreesOfFreedom / n); if (out_t && standardError != 0.0 ) *out_t = meanDifference / standardError; if (out_significance) *out_significance = standardError == 0.0 ? 0.0 : NUMstudentQ (fabs (meanDifference) / standardError, degreesOfFreedom); if (out_lowerLimit) *out_lowerLimit = meanDifference - standardError * NUMinvStudentQ (significanceLevel, degreesOfFreedom); if (out_upperLimit) *out_upperLimit = meanDifference + standardError * NUMinvStudentQ (significanceLevel, degreesOfFreedom); } return meanDifference; } double Table_getMean_studentT (Table me, long column, double significanceLevel, double *out_tFromZero, double *out_numberOfDegreesOfFreedom, double *out_significanceFromZero, double *out_lowerLimit, double *out_upperLimit) { double mean = 0.0, var = 0.0, standardError; long n = my rows -> size; if (out_tFromZero) *out_tFromZero = NUMundefined; if (out_numberOfDegreesOfFreedom) *out_numberOfDegreesOfFreedom = NUMundefined; if (out_significanceFromZero) *out_significanceFromZero = NUMundefined; if (out_lowerLimit) *out_lowerLimit = NUMundefined; if (out_upperLimit) *out_upperLimit = NUMundefined; if (n < 1) return NUMundefined; if (column < 1 || column > my numberOfColumns) return NUMundefined; long degreesOfFreedom = n - 1; if (out_numberOfDegreesOfFreedom) *out_numberOfDegreesOfFreedom = degreesOfFreedom; Table_numericize_Assert (me, column); for (long irow = 1; irow <= n; irow ++) { TableRow row = static_cast (my rows -> item [irow]); mean += row -> cells [column]. number; } mean /= n; if (n >= 2 && (out_tFromZero || out_significanceFromZero || out_lowerLimit || out_upperLimit)) { for (long irow = 1; irow <= n; irow ++) { TableRow row = static_cast (my rows -> item [irow]); double diff = row -> cells [column]. number - mean; var += diff * diff; } standardError = sqrt (var / degreesOfFreedom / n); if (out_tFromZero && standardError != 0.0 ) *out_tFromZero = mean / standardError; if (out_significanceFromZero) *out_significanceFromZero = standardError == 0.0 ? 0.0 : NUMstudentQ (fabs (mean) / standardError, degreesOfFreedom); if (out_lowerLimit) *out_lowerLimit = mean - standardError * NUMinvStudentQ (significanceLevel, degreesOfFreedom); if (out_upperLimit) *out_upperLimit = mean + standardError * NUMinvStudentQ (significanceLevel, degreesOfFreedom); } return mean; } double Table_getGroupMean_studentT (Table me, long column, long groupColumn, const wchar *group, double significanceLevel, double *out_tFromZero, double *out_numberOfDegreesOfFreedom, double *out_significanceFromZero, double *out_lowerLimit, double *out_upperLimit) { if (out_tFromZero) *out_tFromZero = NUMundefined; if (out_numberOfDegreesOfFreedom) *out_numberOfDegreesOfFreedom = NUMundefined; if (out_significanceFromZero) *out_significanceFromZero = NUMundefined; if (out_lowerLimit) *out_lowerLimit = NUMundefined; if (out_upperLimit) *out_upperLimit = NUMundefined; if (column < 1 || column > my numberOfColumns) return NUMundefined; Table_numericize_Assert (me, column); long n = 0; double sum = 0.0; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [groupColumn]. string != NULL) { if (wcsequ (row -> cells [groupColumn]. string, group)) { n += 1; sum += row -> cells [column]. number; } } } if (n < 1) return NUMundefined; double mean = sum / n; long degreesOfFreedom = n - 1; if (out_numberOfDegreesOfFreedom) *out_numberOfDegreesOfFreedom = degreesOfFreedom; if (degreesOfFreedom >= 1 && (out_tFromZero || out_significanceFromZero || out_lowerLimit || out_upperLimit)) { double sumOfSquares = 0.0; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [groupColumn]. string != NULL) { if (wcsequ (row -> cells [groupColumn]. string, group)) { double diff = row -> cells [column]. number - mean; sumOfSquares += diff * diff; } } } double standardError = sqrt (sumOfSquares / degreesOfFreedom / n); if (out_tFromZero && standardError != 0.0 ) *out_tFromZero = mean / standardError; if (out_significanceFromZero) *out_significanceFromZero = standardError == 0.0 ? 0.0 : NUMstudentQ (fabs (mean) / standardError, degreesOfFreedom); if (out_lowerLimit) *out_lowerLimit = mean - standardError * NUMinvStudentQ (significanceLevel, degreesOfFreedom); if (out_upperLimit) *out_upperLimit = mean + standardError * NUMinvStudentQ (significanceLevel, degreesOfFreedom); } return mean; } double Table_getGroupDifference_studentT (Table me, long column, long groupColumn, const wchar *group1, const wchar *group2, double significanceLevel, double *out_tFromZero, double *out_numberOfDegreesOfFreedom, double *out_significanceFromZero, double *out_lowerLimit, double *out_upperLimit) { if (out_tFromZero) *out_tFromZero = NUMundefined; if (out_numberOfDegreesOfFreedom) *out_numberOfDegreesOfFreedom = NUMundefined; if (out_significanceFromZero) *out_significanceFromZero = NUMundefined; if (out_lowerLimit) *out_lowerLimit = NUMundefined; if (out_upperLimit) *out_upperLimit = NUMundefined; if (column < 1 || column > my numberOfColumns) return NUMundefined; if (groupColumn < 1 || groupColumn > my numberOfColumns) return NUMundefined; Table_numericize_Assert (me, column); long n1 = 0, n2 = 0; double sum1 = 0.0, sum2 = 0.0; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [groupColumn]. string != NULL) { if (wcsequ (row -> cells [groupColumn]. string, group1)) { n1 ++; sum1 += row -> cells [column]. number; } else if (wcsequ (row -> cells [groupColumn]. string, group2)) { n2 ++; sum2 += row -> cells [column]. number; } } } if (n1 < 1 || n2 < 1) return NUMundefined; long degreesOfFreedom = n1 + n2 - 2; if (out_numberOfDegreesOfFreedom) *out_numberOfDegreesOfFreedom = degreesOfFreedom; double mean1 = sum1 / n1; double mean2 = sum2 / n2; double difference = mean1 - mean2; if (degreesOfFreedom >= 1 && (out_tFromZero || out_significanceFromZero || out_lowerLimit || out_upperLimit)) { double sumOfSquares = 0.0; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [groupColumn]. string != NULL) { if (wcsequ (row -> cells [groupColumn]. string, group1)) { double diff = row -> cells [column]. number - mean1; sumOfSquares += diff * diff; } else if (wcsequ (row -> cells [groupColumn]. string, group2)) { double diff = row -> cells [column]. number - mean2; sumOfSquares += diff * diff; } } } double standardError = sqrt (sumOfSquares / degreesOfFreedom * (1.0 / n1 + 1.0 / n2)); if (out_tFromZero && standardError != 0.0 ) *out_tFromZero = difference / standardError; if (out_significanceFromZero) *out_significanceFromZero = standardError == 0.0 ? 0.0 : NUMstudentQ (fabs (difference) / standardError, degreesOfFreedom); if (out_lowerLimit) *out_lowerLimit = difference - standardError * NUMinvStudentQ (significanceLevel, degreesOfFreedom); if (out_upperLimit) *out_upperLimit = difference + standardError * NUMinvStudentQ (significanceLevel, degreesOfFreedom); } return difference; } double Table_getGroupDifference_wilcoxonRankSum (Table me, long column, long groupColumn, const wchar *group1, const wchar *group2, double *out_rankSum, double *out_significanceFromZero) { if (out_rankSum) *out_rankSum = NUMundefined; if (out_significanceFromZero) *out_significanceFromZero = NUMundefined; if (column < 1 || column > my numberOfColumns) return NUMundefined; if (groupColumn < 1 || groupColumn > my numberOfColumns) return NUMundefined; Table_numericize_Assert (me, column); long n1 = 0, n2 = 0; for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [groupColumn]. string != NULL) { if (wcsequ (row -> cells [groupColumn]. string, group1)) { n1 ++; } else if (wcsequ (row -> cells [groupColumn]. string, group2)) { n2 ++; } } } long n = n1 + n2; if (n1 < 1 || n2 < 1 || n < 3) return NUMundefined; Table ranks = Table_createWithoutColumnNames (n, 3); // column 1 = group, 2 = value, 3 = rank for (long irow = 1, jrow = 0; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); if (row -> cells [groupColumn]. string != NULL) { if (wcsequ (row -> cells [groupColumn]. string, group1)) { Table_setNumericValue (ranks, ++ jrow, 1, 1.0); Table_setNumericValue (ranks, jrow, 2, row -> cells [column]. number); } else if (wcsequ (row -> cells [groupColumn]. string, group2)) { Table_setNumericValue (ranks, ++ jrow, 1, 2.0); Table_setNumericValue (ranks, jrow, 2, row -> cells [column]. number); } } } Table_numericize_Assert (ranks, 1); Table_numericize_Assert (ranks, 2); Table_numericize_Assert (ranks, 3); long columns [1+1] = { 0, 2 }; // we're gonna sort by column 2 Table_sortRows_Assert (ranks, columns, 1); // we sort by one column only double totalNumberOfTies3 = 0.0; for (long irow = 1; irow <= ranks -> rows -> size; irow ++) { TableRow row = static_cast (ranks -> rows -> item [irow]); double value = row -> cells [2]. number; long rowOfLastTie = irow + 1; for (; rowOfLastTie <= ranks -> rows -> size; rowOfLastTie ++) { TableRow row2 = static_cast (ranks -> rows -> item [rowOfLastTie]); double value2 = row2 -> cells [2]. number; if (value2 != value) break; } rowOfLastTie --; double averageRank = 0.5 * ((double) irow + (double) rowOfLastTie); for (long jrow = irow; jrow <= rowOfLastTie; jrow ++) { Table_setNumericValue (ranks, jrow, 3, averageRank); } long numberOfTies = rowOfLastTie - irow + 1; totalNumberOfTies3 += (double) (numberOfTies - 1) * (double) numberOfTies * (double) (numberOfTies + 1); } Table_numericize_Assert (ranks, 3); double maximumRankSum = (double) n1 * (double) n2, rankSum = 0.0; for (long irow = 1; irow <= ranks -> rows -> size; irow ++) { TableRow row = static_cast (ranks -> rows -> item [irow]); if (row -> cells [1]. number == 1.0) rankSum += row -> cells [3]. number; } rankSum -= 0.5 * (double) n1 * ((double) n1 + 1.0); double stdev = sqrt (maximumRankSum * ((double) n + 1.0 - totalNumberOfTies3 / n / (n - 1)) / 12.0); if (out_rankSum) *out_rankSum = rankSum; if (out_significanceFromZero) *out_significanceFromZero = NUMgaussQ (fabs (rankSum - 0.5 * maximumRankSum) / stdev); forget (ranks); return rankSum / maximumRankSum; } double Table_getFisherF (Table me, long col1, long col2); double Table_getOneWayAnovaSignificance (Table me, long col1, long col2); double Table_getFisherFLowerLimit (Table me, long col1, long col2, double significanceLevel); double Table_getFisherFUpperLimit (Table me, long col1, long col2, double significanceLevel); bool Table_getExtrema (Table me, long icol, double *minimum, double *maximum) { long n = my rows -> size, irow; if (icol < 1 || icol > my numberOfColumns || n == 0) { *minimum = *maximum = NUMundefined; return false; } Table_numericize_Assert (me, icol); *minimum = *maximum = ((TableRow) my rows -> item [1]) -> cells [icol]. number; for (irow = 2; irow <= n; irow ++) { double value = ((TableRow) my rows -> item [irow]) -> cells [icol]. number; if (value < *minimum) *minimum = value; if (value > *maximum) *maximum = value; } return true; } void Table_scatterPlot_mark (Table me, Graphics g, long xcolumn, long ycolumn, double xmin, double xmax, double ymin, double ymax, double markSize_mm, const wchar *mark, int garnish) { long n = my rows -> size, irow; if (xcolumn < 1 || xcolumn > my numberOfColumns || ycolumn < 1 || ycolumn > my numberOfColumns) return; Table_numericize_Assert (me, xcolumn); Table_numericize_Assert (me, ycolumn); if (xmin == xmax) { if (! Table_getExtrema (me, xcolumn, & xmin, & xmax)) return; if (xmin == xmax) xmin -= 0.5, xmax += 0.5; } if (ymin == ymax) { if (! Table_getExtrema (me, ycolumn, & ymin, & ymax)) return; if (ymin == ymax) ymin -= 0.5, ymax += 0.5; } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (irow = 1; irow <= n; irow ++) { TableRow row = static_cast (my rows -> item [irow]); Graphics_mark (g, row -> cells [xcolumn]. number, row -> cells [ycolumn]. number, markSize_mm, mark); } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, TRUE, TRUE, FALSE); if (my columnHeaders [xcolumn]. label) Graphics_textBottom (g, TRUE, my columnHeaders [xcolumn]. label); Graphics_marksLeft (g, 2, TRUE, TRUE, FALSE); if (my columnHeaders [ycolumn]. label) Graphics_textLeft (g, TRUE, my columnHeaders [ycolumn]. label); } } void Table_scatterPlot (Table me, Graphics g, long xcolumn, long ycolumn, double xmin, double xmax, double ymin, double ymax, long markColumn, int fontSize, int garnish) { long n = my rows -> size; int saveFontSize = Graphics_inqFontSize (g); if (xcolumn < 1 || xcolumn > my numberOfColumns || ycolumn < 1 || ycolumn > my numberOfColumns) return; Table_numericize_Assert (me, xcolumn); Table_numericize_Assert (me, ycolumn); if (xmin == xmax) { if (! Table_getExtrema (me, xcolumn, & xmin, & xmax)) return; if (xmin == xmax) xmin -= 0.5, xmax += 0.5; } if (ymin == ymax) { if (! Table_getExtrema (me, ycolumn, & ymin, & ymax)) return; if (ymin == ymax) ymin -= 0.5, ymax += 0.5; } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_setFontSize (g, fontSize); for (long irow = 1; irow <= n; irow ++) { TableRow row = static_cast (my rows -> item [irow]); const wchar *mark = row -> cells [markColumn]. string; if (mark) Graphics_text (g, row -> cells [xcolumn]. number, row -> cells [ycolumn]. number, mark); } Graphics_setFontSize (g, saveFontSize); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, TRUE, TRUE, FALSE); if (my columnHeaders [xcolumn]. label) Graphics_textBottom (g, TRUE, my columnHeaders [xcolumn]. label); Graphics_marksLeft (g, 2, TRUE, TRUE, FALSE); if (my columnHeaders [ycolumn]. label) Graphics_textLeft (g, TRUE, my columnHeaders [ycolumn]. label); } } void Table_drawEllipse_e (Table me, Graphics g, long xcolumn, long ycolumn, double xmin, double xmax, double ymin, double ymax, double numberOfSigmas, int garnish) { try { if (xcolumn < 1 || xcolumn > my numberOfColumns || ycolumn < 1 || ycolumn > my numberOfColumns) return; Table_numericize_Assert (me, xcolumn); Table_numericize_Assert (me, ycolumn); if (xmin == xmax) { if (! Table_getExtrema (me, xcolumn, & xmin, & xmax)) return; if (xmin == xmax) xmin -= 0.5, xmax += 0.5; } if (ymin == ymax) { if (! Table_getExtrema (me, ycolumn, & ymin, & ymax)) return; if (ymin == ymax) ymin -= 0.5, ymax += 0.5; } autoTableOfReal tableOfReal = TableOfReal_create (my rows -> size, 2); for (long irow = 1; irow <= my rows -> size; irow ++) { tableOfReal -> data [irow] [1] = Table_getNumericValue_Assert (me, irow, xcolumn); tableOfReal -> data [irow] [2] = Table_getNumericValue_Assert (me, irow, ycolumn); } autoSSCP sscp = TableOfReal_to_SSCP (tableOfReal.peek(), 0, 0, 0, 0); SSCP_drawConcentrationEllipse (sscp.peek(), g, numberOfSigmas, 0, 1, 2, xmin, xmax, ymin, ymax, garnish); } catch (MelderError) { Melder_clearError (); // drawing errors shall be ignored } } static const wchar *visibleString (const wchar *s) { return s != NULL && s [0] != '\0' ? s : L"?"; } void Table_list (Table me, bool includeRowNumbers) { MelderInfo_open (); if (includeRowNumbers) { MelderInfo_write1 (L"row"); if (my numberOfColumns > 0) MelderInfo_write1 (L"\t"); } for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (icol > 1) MelderInfo_write1 (L"\t"); MelderInfo_write1 (visibleString (my columnHeaders [icol]. label)); } MelderInfo_write1 (L"\n"); for (long irow = 1; irow <= my rows -> size; irow ++) { if (includeRowNumbers) { MelderInfo_write1 (Melder_integer (irow)); if (my numberOfColumns > 0) MelderInfo_write1 (L"\t"); } TableRow row = static_cast (my rows -> item [irow]); for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (icol > 1) MelderInfo_write1 (L"\t"); MelderInfo_write1 (visibleString (row -> cells [icol]. string)); } MelderInfo_write1 (L"\n"); } MelderInfo_close (); } static void _Table_writeToCharacterSeparatedFile (Table me, MelderFile file, wchar kar) { autoMelderString buffer; for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (icol != 1) MelderString_appendCharacter (& buffer, kar); wchar *s = my columnHeaders [icol]. label; MelderString_append (& buffer, s != NULL && s [0] != '\0' ? s : L"?"); therror } MelderString_appendCharacter (& buffer, '\n'); therror for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (icol != 1) MelderString_appendCharacter (& buffer, kar); wchar *s = row -> cells [icol]. string; MelderString_append (& buffer, s != NULL && s [0] != '\0' ? s : L"?"); therror } MelderString_appendCharacter (& buffer, '\n'); therror } MelderFile_writeText (file, buffer.string); therror } void Table_writeToTabSeparatedFile (Table me, MelderFile file) { try { _Table_writeToCharacterSeparatedFile (me, file, '\t'); } catch (MelderError) { Melder_throw (me, ": not written to tab-separated file."); } } void Table_writeToCommaSeparatedFile (Table me, MelderFile file) { try { _Table_writeToCharacterSeparatedFile (me, file, ','); } catch (MelderError) { Melder_throw (me, ": not written to comma-separated file."); } } Table Table_readFromTableFile (MelderFile file) { Table me = NULL; try { autostring string = MelderFile_readText (file); long nrow, ncol, nelements; /* * Count columns. */ ncol = 0; wchar *p = & string [0]; for (;;) { wchar kar = *p++; if (kar == '\n' || kar == '\0') break; if (kar == ' ' || kar == '\t') continue; ncol ++; do { kar = *p++; } while (kar != ' ' && kar != '\t' && kar != '\n' && kar != '\0'); if (kar == '\n' || kar == '\0') break; } if (ncol < 1) Melder_throw ("No columns."); /* * Count elements. */ p = & string [0]; nelements = 0; for (;;) { wchar kar = *p++; if (kar == '\0') break; if (kar == ' ' || kar == '\t' || kar == '\n') continue; nelements ++; do { kar = *p++; } while (kar != ' ' && kar != '\t' && kar != '\n' && kar != '\0'); if (kar == '\0') break; } /* * Check if all columns are complete. */ if (nelements == 0 || nelements % ncol != 0) Melder_throw ("The number of elements (", nelements, ") is not a multiple of the number of columns (", ncol, ")."); /* * Create empty table. */ nrow = nelements / ncol - 1; me = Table_create (nrow, ncol); therror /* * Read elements. */ p = & string [0]; for (long icol = 1; icol <= ncol; icol ++) { while (*p == ' ' || *p == '\t') { Melder_assert (*p != '\0'); p ++; } static MelderString buffer = { 0 }; MelderString_empty (& buffer); while (*p != ' ' && *p != '\t' && *p != '\n') { MelderString_appendCharacter (& buffer, *p); p ++; } Table_setColumnLabel (me, icol, buffer.string); MelderString_empty (& buffer); } for (long irow = 1; irow <= nrow; irow ++) { TableRow row = static_cast (my rows -> item [irow]); for (long icol = 1; icol <= ncol; icol ++) { while (*p == ' ' || *p == '\t' || *p == '\n') { Melder_assert (*p != '\0'); p ++; } static MelderString buffer = { 0 }; MelderString_empty (& buffer); while (*p != ' ' && *p != '\t' && *p != '\n' && *p != '\0') { MelderString_appendCharacter (& buffer, *p); p ++; } row -> cells [icol]. string = Melder_wcsdup_f (buffer.string); MelderString_empty (& buffer); } } return me; } catch (MelderError) { forget (me); Melder_throw ("Table object not read from space-separated text file ", file, "."); } } Table Table_readFromCharacterSeparatedTextFile (MelderFile file, wchar separator) { try { autostring string = MelderFile_readText (file); /* * Kill final new-line symbols. */ for (long length = wcslen (string.peek()); length > 0 && string [length - 1] == '\n'; length = wcslen (string.peek())) string [length - 1] = '\0'; /* * Count columns. */ long ncol = 1; const wchar *p = & string [0]; for (;;) { wchar kar = *p++; if (kar == '\0') Melder_throw (L"No rows."); if (kar == '\n') break; if (kar == separator) ncol ++; } /* * Count rows. */ long nrow = 1; for (;;) { wchar kar = *p++; if (kar == '\0') break; if (kar == '\n') nrow ++; } /* * Create empty table. */ autoTable me = Table_create (nrow, ncol); /* * Read column names. */ p = & string [0]; for (long icol = 1; icol <= ncol; icol ++) { static MelderString buffer = { 0 }; MelderString_empty (& buffer); while (*p != separator && *p != '\n') { Melder_assert (*p != '\0'); MelderString_appendCharacter (& buffer, *p); therror p ++; } p ++; Table_setColumnLabel (me.peek(), icol, buffer.string); therror MelderString_empty (& buffer); } /* * Read cells. */ for (long irow = 1; irow <= nrow; irow ++) { TableRow row = static_cast (my rows -> item [irow]); for (long icol = 1; icol <= ncol; icol ++) { static MelderString buffer = { 0 }; MelderString_empty (& buffer); while (*p != separator && *p != '\n' && *p != '\0') { MelderString_appendCharacter (& buffer, *p); therror p ++; } if (*p == '\0') { if (irow != nrow) Melder_fatal ("irow %ld, nrow %ld, icol %ld, ncol %ld", irow, nrow, icol, ncol); if (icol != ncol) Melder_throw ("Last row incomplete."); } else if (*p == '\n') { if (icol != ncol) Melder_throw ("Row ", irow, " incomplete."); p ++; } else { Melder_assert (*p == separator); p ++; } row -> cells [icol]. string = Melder_wcsdup (buffer.string); MelderString_empty (& buffer); } } return me.transfer(); } catch (MelderError) { Melder_throw ("Table object not read from character-separated text file ", file, "."); } } /* End of file Table.cpp */ sources_5316/stat/LogisticRegression_def.h0000644000176700017670000000207511622371455017515 0ustar paulpaul/* LogisticRegression_def.h * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT LogisticRegression oo_DEFINE_CLASS (LogisticRegression, Regression) oo_STRING (dependent1) oo_STRING (dependent2) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (LogisticRegression) #undef ooSTRUCT /* End of file LogisticRegression_def.h */ sources_5316/stat/Distributions_and_Strings.cpp0000644000176700017670000000660311614454335020612 0ustar paulpaul/* Distributions_and_Strings.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2003/07/28 factored out Distributions_peek * pb 2007/08/12 wchar * pb 2011/03/20 C++ */ #include "Distributions_and_Strings.h" Strings Distributions_to_Strings (Distributions me, long column, long numberOfStrings) { try { autoStrings thee = Thing_new (Strings); thy numberOfStrings = numberOfStrings; thy strings = NUMvector (1, numberOfStrings); for (long istring = 1; istring <= numberOfStrings; istring ++) { wchar *string; Distributions_peek (me, column, & string); therror thy strings [istring] = Melder_wcsdup (string); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Strings not generated."); } } Strings Distributions_to_Strings_exact (Distributions me, long column) { try { long total = 0; long istring = 0; if (column > my numberOfColumns) Melder_throw ("No column ", column, "."); if (my numberOfRows < 1) Melder_throw ("No candidates."); for (long irow = 1; irow <= my numberOfRows; irow ++) { double value = my data [irow] [column]; if (value != floor (value)) Melder_throw ("Non-integer value ", value, " in row ", irow, "."); if (value < 0.0) Melder_throw ("Found a negative value ", value, " in row ", irow, "."); total += value; } if (total <= 0) Melder_throw ("Column total not positive."); autoStrings thee = Thing_new (Strings); thy numberOfStrings = total; thy strings = NUMvector (1, total); for (long irow = 1; irow <= my numberOfRows; irow ++) { long number = my data [irow] [column]; wchar *string = my rowLabels [irow]; if (! string) Melder_throw ("No string in row ", irow, "."); for (long i = 1; i <= number; i ++) { thy strings [++ istring] = Melder_wcsdup (string); } } Strings_randomize (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Strings not generated."); } } Distributions Strings_to_Distributions (Strings me) { try { autoDistributions thee = Distributions_create (my numberOfStrings, 1); long idist = 0; for (long i = 1; i <= my numberOfStrings; i ++) { wchar *string = my strings [i]; long where = 0; long j = 1; for (; j <= idist; j ++) if (wcsequ (thy rowLabels [j], string)) { where = j; break; } if (where) { thy data [j] [1] += 1.0; } else { thy rowLabels [++ idist] = Melder_wcsdup (string); thy data [idist] [1] = 1.0; } } thy numberOfRows = idist; TableOfReal_sortByLabel (thee.peek(), 1, 0); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": distribution not computed."); } } /* End of file Distributions_and_Strings.cpp */ sources_5316/stat/Regression.cpp0000644000176700017670000001306411633710351015526 0ustar paulpaul/* Regression.cpp * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Regression.h" #include "NUM2.h" #include "oo_DESTROY.h" #include "Regression_def.h" #include "oo_COPY.h" #include "Regression_def.h" #include "oo_EQUAL.h" #include "Regression_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Regression_def.h" #include "oo_WRITE_TEXT.h" #include "Regression_def.h" #include "oo_WRITE_BINARY.h" #include "Regression_def.h" #include "oo_READ_TEXT.h" #include "Regression_def.h" #include "oo_READ_BINARY.h" #include "Regression_def.h" #include "oo_DESCRIPTION.h" #include "Regression_def.h" Thing_implement (RegressionParameter, Data, 0); void structRegression :: v_info () { Regression_Parent :: v_info (); MelderInfo_writeLine1 (L"Factors:"); MelderInfo_writeLine2 (L" Number of factors: ", Melder_integer (parameters -> size)); for (long ivar = 1; ivar <= parameters -> size; ivar ++) { RegressionParameter parm = static_cast (parameters -> item [ivar]); MelderInfo_writeLine4 (L" Factor ", Melder_integer (ivar), L": ", parm -> label); } MelderInfo_writeLine1 (L"Fitted coefficients:"); MelderInfo_writeLine2 (L" Intercept: ", Melder_double (intercept)); for (long ivar = 1; ivar <= parameters -> size; ivar ++) { RegressionParameter parm = static_cast (parameters -> item [ivar]); MelderInfo_writeLine4 (L" Coefficient of factor ", parm -> label, L": ", Melder_double (parm -> value)); } MelderInfo_writeLine1 (L"Ranges of values:"); for (long ivar = 1; ivar <= parameters -> size; ivar ++) { RegressionParameter parm = static_cast (parameters -> item [ivar]); MelderInfo_writeLine6 (L" Range of factor ", parm -> label, L": minimum ", Melder_double (parm -> minimum), L", maximum ", Melder_double (parm -> maximum)); } } Thing_implement (Regression, Data, 0); void Regression_init (I) { iam (Regression); my parameters = Ordered_create (); therror } void Regression_addParameter (I, const wchar *label, double minimum, double maximum, double value) { iam (Regression); try { autoRegressionParameter thee = Thing_new (RegressionParameter); thy label = Melder_wcsdup (label); thy minimum = minimum; thy maximum = maximum; thy value = value; Collection_addItem (my parameters, thee.transfer()); } catch (MelderError) { Melder_throw (me, ": parameter not added."); } } long Regression_getFactorIndexFromFactorName_e (I, const wchar *factorName) { iam (Regression); for (long iparm = 1; iparm <= my parameters -> size; iparm ++) { RegressionParameter parm = static_cast (my parameters -> item [iparm]); if (Melder_wcsequ (factorName, parm -> label)) return iparm; } Melder_throw (Thing_messageName (me), L" has no parameter named \"", factorName, L"\"."); } Thing_implement (LinearRegression, Regression, 0); LinearRegression LinearRegression_create (void) { try { autoLinearRegression me = Thing_new (LinearRegression); Regression_init (me.peek()); therror return me.transfer(); } catch (MelderError) { Melder_throw ("LinearRegression not created."); } } LinearRegression Table_to_LinearRegression (Table me) { try { long numberOfIndependentVariables = my numberOfColumns - 1, numberOfParameters = my numberOfColumns; long numberOfCells = my rows -> size, icell, ivar; if (numberOfParameters < 1) /* Includes intercept. */ Melder_throw ("Not enough columns (has to be more than 1)."); if (numberOfCells < numberOfParameters) { Melder_warning (L"Solution is not unique (more parameters than cases)."); } autoNUMmatrix u (1, numberOfCells, 1, numberOfParameters); autoNUMvector b (1, numberOfCells); autoNUMvector x (1, numberOfParameters); autoLinearRegression thee = LinearRegression_create (); for (ivar = 1; ivar <= numberOfIndependentVariables; ivar ++) { double minimum = Table_getMinimum (me, ivar); therror double maximum = Table_getMaximum (me, ivar); therror Regression_addParameter (thee.peek(), my columnHeaders [ivar]. label, minimum, maximum, 0.0); therror } for (icell = 1; icell <= numberOfCells; icell ++) { for (ivar = 1; ivar < numberOfParameters; ivar ++) { u [icell] [ivar] = Table_getNumericValue_Assert (me, icell, ivar); } u [icell] [numberOfParameters] = 1.0; /* For the intercept. */ b [icell] = Table_getNumericValue_Assert (me, icell, my numberOfColumns); /* The dependent variable. */ } NUMsolveEquation (u.peek(), numberOfCells, numberOfParameters, b.peek(), NUMeps * numberOfCells, x.peek()); thy intercept = x [numberOfParameters]; for (ivar = 1; ivar <= numberOfIndependentVariables; ivar ++) { RegressionParameter parm = static_cast (thy parameters -> item [ivar]); parm -> value = x [ivar]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": linear regression not performed."); } } /* End of file Regression.cpp */ sources_5316/stat/TableOfReal.h0000644000176700017670000001036611631441442015175 0ustar paulpaul#ifndef _TableOfReal_h_ #define _TableOfReal_h_ /* TableOfReal.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* TableOfReal inherits from Data */ #include "Collection.h" #include "Strings.h" #include "Table.h" #include "Interpreter_decl.h" #include "TableOfReal_def.h" oo_CLASS_CREATE (TableOfReal, Data); void TableOfReal_init (TableOfReal me, long numberOfRows, long numberOfColumns); TableOfReal TableOfReal_create (long numberOfRows, long numberOfColumns); void TableOfReal_removeRow (TableOfReal me, long irow); void TableOfReal_removeColumn (TableOfReal me, long icol); void TableOfReal_insertRow (TableOfReal me, long irow); void TableOfReal_insertColumn (TableOfReal me, long icol); void TableOfReal_setRowLabel (TableOfReal me, long irow, const wchar_t *label); void TableOfReal_setColumnLabel (TableOfReal me, long icol, const wchar_t *label); long TableOfReal_rowLabelToIndex (TableOfReal me, const wchar_t *label); long TableOfReal_columnLabelToIndex (TableOfReal me, const wchar_t *label); double TableOfReal_getColumnMean (TableOfReal me, long icol); double TableOfReal_getColumnStdev (TableOfReal me, long icol); TableOfReal Table_to_TableOfReal (Table me, long labelColumn); Table TableOfReal_to_Table (TableOfReal me, const wchar_t *labelOfFirstColumn); void TableOfReal_formula (TableOfReal me, const wchar_t *expression, Interpreter interpreter, TableOfReal target); void TableOfReal_drawAsNumbers (TableOfReal me, Graphics g, long rowmin, long rowmax, int iformat, int precision); void TableOfReal_drawAsNumbers_if (TableOfReal me, Graphics g, long rowmin, long rowmax, int iformat, int precision, const wchar_t *conditionFormula, Interpreter interpreter); void TableOfReal_drawAsSquares (TableOfReal me, Graphics g, long rowmin, long rowmax, long colmin, long colmax, int garnish); void TableOfReal_drawVerticalLines (TableOfReal me, Graphics g, long rowmin, long rowmax); void TableOfReal_drawHorizontalLines (TableOfReal me, Graphics g, long rowmin, long rowmax); void TableOfReal_drawLeftAndRightLines (TableOfReal me, Graphics g, long rowmin, long rowmax); void TableOfReal_drawTopAndBottomLines (TableOfReal me, Graphics g, long rowmin, long rowmax); Any TablesOfReal_append (TableOfReal me, TableOfReal thee); Any TablesOfReal_appendMany (Collection me); void TableOfReal_sortByLabel (TableOfReal me, long column1, long column2); void TableOfReal_sortByColumn (TableOfReal me, long column1, long column2); void TableOfReal_writeToHeaderlessSpreadsheetFile (TableOfReal me, MelderFile file); TableOfReal TableOfReal_readFromHeaderlessSpreadsheetFile (MelderFile file); TableOfReal TableOfReal_extractRowRanges (TableOfReal me, const wchar_t *ranges); TableOfReal TableOfReal_extractColumnRanges (TableOfReal me, const wchar_t *ranges); TableOfReal TableOfReal_extractRowsWhereColumn (TableOfReal me, long icol, int which_Melder_NUMBER, double criterion); TableOfReal TableOfReal_extractColumnsWhereRow (TableOfReal me, long icol, int which_Melder_NUMBER, double criterion); TableOfReal TableOfReal_extractRowsWhereLabel (TableOfReal me, int which_Melder_STRING, const wchar_t *criterion); TableOfReal TableOfReal_extractColumnsWhereLabel (TableOfReal me, int which_Melder_STRING, const wchar_t *criterion); TableOfReal TableOfReal_extractRowsWhere (TableOfReal me, const wchar_t *condition, Interpreter interpreter); TableOfReal TableOfReal_extractColumnsWhere (TableOfReal me, const wchar_t *condition, Interpreter interpreter); Strings TableOfReal_extractRowLabelsAsStrings (TableOfReal me); Strings TableOfReal_extractColumnLabelsAsStrings (TableOfReal me); /* End of file TableOfReal.h */ #endif sources_5316/stat/Distributions.cpp0000644000176700017670000001411011622371130016235 0ustar paulpaul/* Distributions.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Distributions.h" Thing_implement (Distributions, TableOfReal, 0); void structDistributions :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of distributions: ", Melder_integer (numberOfColumns)); MelderInfo_writeLine2 (L"Number of values: ", Melder_integer (numberOfRows)); } Distributions Distributions_create (long numberOfRows, long numberOfColumns) { try { autoDistributions me = Thing_new (Distributions); TableOfReal_init (me.peek(), numberOfRows, numberOfColumns); therror return me.transfer(); } catch (MelderError) { Melder_throw ("Distributions not created."); } } void Distributions_checkSpecifiedColumnNumberWithinRange (Distributions me, long columnNumber) { if (columnNumber < 1) Melder_throw (me, ": the specified column number is ", columnNumber, ", but should be at least 1."); if (columnNumber > my numberOfColumns) Melder_throw (me, ": the specified column number is ", columnNumber, ", but should be at most my number of columns (", my numberOfColumns, ")."); } int Distributions_peek (Distributions me, long column, wchar **string) { Distributions_checkSpecifiedColumnNumberWithinRange (me, column); if (my numberOfRows < 1) Melder_throw (me, ": I have no candidates."); double total = 0.0; for (long irow = 1; irow <= my numberOfRows; irow ++) { total += my data [irow] [column]; } if (total <= 0.0) Melder_throw (me, ": the total weight of column ", column, " is not positive."); long irow; do { double rand = NUMrandomUniform (0, total), sum = 0.0; for (irow = 1; irow <= my numberOfRows; irow ++) { sum += my data [irow] [column]; if (rand <= sum) break; } } while (irow > my numberOfRows); // guard against rounding errors *string = my rowLabels [irow]; if (! *string) Melder_throw (me, ": no string in row ", irow, "."); return 1; } int Distributions_peek_opt (Distributions me, long column, long *number) { Distributions_checkSpecifiedColumnNumberWithinRange (me, column); if (my numberOfRows < 1) Melder_throw (me, ": I have no candidates."); double total = 0.0; for (long irow = 1; irow <= my numberOfRows; irow ++) { total += my data [irow] [column]; } if (total <= 0.0) Melder_throw (me, ": the total weight of column ", column, " is not positive."); long irow; do { double rand = NUMrandomUniform (0, total), sum = 0.0; for (irow = 1; irow <= my numberOfRows; irow ++) { sum += my data [irow] [column]; if (rand <= sum) break; } } while (irow > my numberOfRows); /* Guard against rounding errors. */ if (my rowLabels [irow] == NULL) Melder_throw (me, ": no string in row ", irow, "."); *number = irow; return 1; } double Distributions_getProbability (Distributions me, const wchar *string, long column) { long row, rowOfString = 0; double total = 0.0; if (column < 1 || column > my numberOfColumns) return NUMundefined; for (row = 1; row <= my numberOfRows; row ++) { total += my data [row] [column]; if (my rowLabels [row] && wcsequ (my rowLabels [row], string)) rowOfString = row; } if (total <= 0.0) return NUMundefined; if (rowOfString == 0) return 0.0; return my data [rowOfString] [column] / total; } double Distributionses_getMeanAbsoluteDifference (Distributions me, Distributions thee, long column) { if (column < 1 || column > my numberOfColumns || column > thy numberOfColumns || my numberOfRows != thy numberOfRows) return NUMundefined; double total = 0.0; for (long irow = 1; irow <= my numberOfRows; irow ++) { total += fabs (my data [irow] [column] - thy data [irow] [column]); } return total / my numberOfRows; } static void unicize (Distributions me) { /* Must have been sorted beforehand. */ long nrow = 0, ifrom = 1; for (long irow = 1; irow <= my numberOfRows; irow ++) { if (irow == my numberOfRows || (my rowLabels [irow] == NULL) != (my rowLabels [irow + 1] == NULL) || (my rowLabels [irow] != NULL && ! wcsequ (my rowLabels [irow], my rowLabels [irow + 1]))) { /* * Detected a change. */ nrow ++; long ito = irow; /* * Move row 'ifrom' to 'nrow'. May be the same row. */ if (ifrom != nrow) { Melder_free (my rowLabels [nrow]); my rowLabels [nrow] = my rowLabels [ifrom]; /* Surface copy. */ my rowLabels [ifrom] = NULL; /* Undangle. */ for (long icol = 1; icol <= my numberOfColumns; icol ++) my data [nrow] [icol] = my data [ifrom] [icol]; } /* * Purge rows from 'ifrom'+1 to 'ito'. */ for (long j = ifrom + 1; j <= ito; j ++) { Melder_free (my rowLabels [j]); for (long icol = 1; icol <= my numberOfColumns; icol ++) my data [nrow] [icol] += my data [j] [icol]; } ifrom = ito + 1; } } my numberOfRows = nrow; } Distributions Distributions_addTwo (Distributions me, Distributions thee) { try { autoDistributions him = static_cast (TablesOfReal_append (me, thee)); TableOfReal_sortByLabel (him.peek(), 0, 0); unicize (him.peek()); return him.transfer(); } catch (MelderError) { Melder_throw (me, " & ", thee, ": not added."); } } Distributions Distributions_addMany (Collection me) { try { autoDistributions thee = static_cast (TablesOfReal_appendMany (me)); TableOfReal_sortByLabel (thee.peek(), 0, 0); unicize (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw ("Distributions objects not added."); } } /* End of file Distributions.cpp */ sources_5316/stat/LogisticRegression.cpp0000644000176700017670000004005411633710351017223 0ustar paulpaul/* LogisticRegression.cpp * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2005/05/01 created * pb 2006/12/10 MelderInfo * pb 2007/08/12 wchar * pb 2007/10/01 can write as encoding * pb 2007/11/18 split off from Regression.c * pb 2011/03/20 C++ */ #include "LogisticRegression.h" #include "UnicodeData.h" #include "oo_DESTROY.h" #include "LogisticRegression_def.h" #include "oo_COPY.h" #include "LogisticRegression_def.h" #include "oo_EQUAL.h" #include "LogisticRegression_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "LogisticRegression_def.h" #include "oo_WRITE_TEXT.h" #include "LogisticRegression_def.h" #include "oo_WRITE_BINARY.h" #include "LogisticRegression_def.h" #include "oo_READ_TEXT.h" #include "LogisticRegression_def.h" #include "oo_READ_BINARY.h" #include "LogisticRegression_def.h" #include "oo_DESCRIPTION.h" #include "LogisticRegression_def.h" Thing_implement (LogisticRegression, Regression, 0); void structLogisticRegression :: v_info () { LogisticRegression_Parent :: v_info (); MelderInfo_writeLine2 (L"Dependent 1: ", dependent1); MelderInfo_writeLine2 (L"Dependent 2: ", dependent2); MelderInfo_writeLine1 (L"Interpretation:"); MelderInfo_write6 (L" ln (P(", dependent2, L")/P(", dependent1, L")) " UNITEXT_ALMOST_EQUAL_TO L" ", Melder_fixed (intercept, 6)); for (long ivar = 1; ivar <= parameters -> size; ivar ++) { RegressionParameter parm = static_cast (parameters -> item [ivar]); MelderInfo_write4 (parm -> value < 0.0 ? L" - " : L" + ", Melder_fixed (fabs (parm -> value), 6), L" * ", parm -> label); } MelderInfo_writeLine1 (NULL); MelderInfo_writeLine1 (L"Log odds ratios:"); for (long ivar = 1; ivar <= parameters -> size; ivar ++) { RegressionParameter parm = static_cast (parameters -> item [ivar]); MelderInfo_writeLine4 (L" Log odds ratio of factor ", parm -> label, L": ", Melder_fixed ((parm -> maximum - parm -> minimum) * parm -> value, 6)); } MelderInfo_writeLine1 (L"Odds ratios:"); for (long ivar = 1; ivar <= parameters -> size; ivar ++) { RegressionParameter parm = static_cast (parameters -> item [ivar]); MelderInfo_writeLine4 (L" Odds ratio of factor ", parm -> label, L": ", Melder_double (exp ((parm -> maximum - parm -> minimum) * parm -> value))); } } LogisticRegression LogisticRegression_create (const wchar *dependent1, const wchar *dependent2) { try { autoLogisticRegression me = Thing_new (LogisticRegression); Regression_init (me.peek()); therror my dependent1 = Melder_wcsdup (dependent1); my dependent2 = Melder_wcsdup (dependent2); return me.transfer(); } catch (MelderError) { Melder_throw ("LogisticRegression not created."); } } static LogisticRegression _Table_to_LogisticRegression (Table me, long *factors, long numberOfFactors, long dependent1, long dependent2) { long numberOfParameters = numberOfFactors + 1; long numberOfCells = my rows -> size, numberOfY0 = 0, numberOfY1 = 0, numberOfData = 0; double logLikelihood = 1e300, previousLogLikelihood = 2e300; if (numberOfParameters < 1) // includes intercept Melder_throw ("Not enough columns (has to be more than 1)."); /* * Divide up the contents of the table into a number of independent variables (x) and two dependent variables (y0 and y1). */ autoNUMmatrix x (1, numberOfCells, 0, numberOfFactors); // column 0 is the intercept autoNUMvector y0 (1, numberOfCells); autoNUMvector y1 (1, numberOfCells); autoNUMvector meanX (1, numberOfFactors); autoNUMvector stdevX (1, numberOfFactors); autoNUMmatrix smallMatrix (0, numberOfFactors, 0, numberOfParameters); autoLogisticRegression thee = LogisticRegression_create (my columnHeaders [dependent1]. label, my columnHeaders [dependent2]. label); for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { double minimum = Table_getMinimum (me, factors [ivar]); therror double maximum = Table_getMaximum (me, factors [ivar]); therror Regression_addParameter (thee.peek(), my columnHeaders [factors [ivar]]. label, minimum, maximum, 0.0); therror } for (long icell = 1; icell <= numberOfCells; icell ++) { y0 [icell] = Table_getNumericValue_Assert (me, icell, dependent1); y1 [icell] = Table_getNumericValue_Assert (me, icell, dependent2); numberOfY0 += y0 [icell]; numberOfY1 += y1 [icell]; numberOfData += y0 [icell] + y1 [icell]; x [icell] [0] = 1.0; /* Intercept. */ for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { x [icell] [ivar] = Table_getNumericValue_Assert (me, icell, factors [ivar]); meanX [ivar] += x [icell] [ivar] * (y0 [icell] + y1 [icell]); } } if (numberOfY0 == 0 && numberOfY1 == 0) Melder_throw ("No data in either class. Cannot determine result."); if (numberOfY0 == 0) Melder_throw ("No data in class ", my columnHeaders [dependent1]. label, ". Cannot determine result."); if (numberOfY1 == 0) Melder_throw ("No data in class ", my columnHeaders [dependent2]. label, ". Cannot determine result."); /* * Normalize the data. */ for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { meanX [ivar] /= numberOfData; for (long icell = 1; icell <= numberOfCells; icell ++) { x [icell] [ivar] -= meanX [ivar]; } } for (long icell = 1; icell <= numberOfCells; icell ++) { for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { stdevX [ivar] += x [icell] [ivar] * x [icell] [ivar] * (y0 [icell] + y1 [icell]); } } for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { stdevX [ivar] = sqrt (stdevX [ivar] / numberOfData); for (long icell = 1; icell <= numberOfCells; icell ++) { x [icell] [ivar] /= stdevX [ivar]; } } /* * Initial state of iteration: the null model. */ thy intercept = log ((double) numberOfY1 / (double) numberOfY0); // initial state of intercept: best guess for average log odds for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { RegressionParameter parm = static_cast (thy parameters -> item [ivar]); parm -> value = 0.0; // initial state of dependence: none } long iteration = 1; for (; iteration <= 100; iteration ++) { previousLogLikelihood = logLikelihood; for (long ivar = 0; ivar <= numberOfFactors; ivar ++) { for (long jvar = ivar; jvar <= numberOfParameters; jvar ++) { smallMatrix [ivar] [jvar] = 0.0; } } /* * Compute the current log likelihood. */ logLikelihood = 0.0; for (long icell = 1; icell <= numberOfCells; icell ++) { double fittedLogit = thy intercept, fittedP, fittedQ, fittedLogP, fittedLogQ, fittedPQ, fittedVariance; for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { RegressionParameter parm = static_cast (thy parameters -> item [ivar]); fittedLogit += parm -> value * x [icell] [ivar]; } /* * Basically we have fittedP = 1.0 / (1.0 + exp (- fittedLogit)), * but that works neither for fittedP values near 0 nor for values near 1. */ if (fittedLogit > 15.0) { /* * For large fittedLogit, fittedLogP = ln (1/(1+exp(-fittedLogit))) = -ln (1+exp(-fittedLogit)) =~ - exp(-fittedLogit) */ fittedLogP = - exp (- fittedLogit); fittedLogQ = - fittedLogit; fittedPQ = exp (- fittedLogit); fittedP = exp (fittedLogP); fittedQ = 1.0 - fittedP; } else if (fittedLogit < -15.0) { fittedLogP = fittedLogit; fittedLogQ = - exp (fittedLogit); fittedPQ = exp (fittedLogit); fittedP = exp (fittedLogP); fittedQ = 1 - fittedP; } else { fittedP = 1.0 / (1.0 + exp (- fittedLogit)); fittedLogP = log (fittedP); fittedQ = 1.0 - fittedP; fittedLogQ = log (fittedQ); fittedPQ = fittedP * fittedQ; } logLikelihood += -2 * (y1 [icell] * fittedLogP + y0 [icell] * fittedLogQ); /* * Matrix shifting stuff. * Suppose a + b Sk + c Tk = ln (pk / qk), * where {a, b, c} are the coefficients to be optimized, * Sk and Tk are properties of stimulus k, * and pk and qk are the fitted probabilities for y1 and y0, respectively, given stimulus k. * Then ln pk = - ln (1 + qk / pk) = - ln (1 + exp (- (a + b Sk + c Tk))) * d ln pk / da = 1 / (1 + exp (a + b Sk + c Tk)) = qk * d ln pk / db = qk Sk * d ln pk / dc = qk Tk * d ln qk / da = - pk * Now LL = Sum(k) (y1k ln pk + y0k ln qk) * so that dLL/da = Sum(k) (y1k d ln pk / da + y0k ln qk / da) = Sum(k) (y1k qk - y0k pk) */ fittedVariance = fittedPQ * (y0 [icell] + y1 [icell]); for (long ivar = 0; ivar <= numberOfFactors; ivar ++) { /* * The last column gets the gradient of LL: dLL/da, dLL/db, dLL/dc. */ smallMatrix [ivar] [numberOfParameters] += x [icell] [ivar] * (y1 [icell] * fittedQ - y0 [icell] * fittedP); for (long jvar = ivar; jvar <= numberOfFactors; jvar ++) { smallMatrix [ivar] [jvar] += x [icell] [ivar] * x [icell] [jvar] * fittedVariance; } } } if (fabs (logLikelihood - previousLogLikelihood) < 1e-11) { break; } /* * Make matrix symmetric. */ for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { for (long jvar = 0; jvar < ivar; jvar ++) { smallMatrix [ivar] [jvar] = smallMatrix [jvar] [ivar]; } } /* * Invert matrix in the simplest way, and shift and wipe the last column with it. */ for (long ivar = 0; ivar <= numberOfFactors; ivar ++) { double pivot = smallMatrix [ivar] [ivar]; /* Save diagonal. */ smallMatrix [ivar] [ivar] = 1.0; for (long jvar = 0; jvar <= numberOfParameters; jvar ++) { smallMatrix [ivar] [jvar] /= pivot; } for (long jvar = 0; jvar <= numberOfFactors; jvar ++) { if (jvar != ivar) { double temp = smallMatrix [jvar] [ivar]; smallMatrix [jvar] [ivar] = 0.0; for (long kvar = 0; kvar <= numberOfParameters; kvar ++) { smallMatrix [jvar] [kvar] -= temp * smallMatrix [ivar] [kvar]; } } } } /* * Update the parameters from the last column of smallMatrix. */ thy intercept += smallMatrix [0] [numberOfParameters]; for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { RegressionParameter parm = static_cast (thy parameters -> item [ivar]); parm -> value += smallMatrix [ivar] [numberOfParameters]; } } if (iteration > 100) { Melder_warning (L"Logistic regression has not converged in 100 iterations. The results are unreliable."); } for (long ivar = 1; ivar <= numberOfFactors; ivar ++) { RegressionParameter parm = static_cast (thy parameters -> item [ivar]); parm -> value /= stdevX [ivar]; thy intercept -= parm -> value * meanX [ivar]; } return thee.transfer(); } LogisticRegression Table_to_LogisticRegression (Table me, const wchar *factors_columnLabelString, const wchar *dependent1_columnLabel, const wchar *dependent2_columnLabel) { try { long numberOfFactors; autoNUMvector factors_columnIndices (Table_getColumnIndicesFromColumnLabelString (me, factors_columnLabelString, & numberOfFactors), 1); long dependent1_columnIndex = Table_getColumnIndexFromColumnLabel (me, dependent1_columnLabel); therror long dependent2_columnIndex = Table_getColumnIndexFromColumnLabel (me, dependent2_columnLabel); therror autoLogisticRegression thee = _Table_to_LogisticRegression (me, factors_columnIndices.peek(), numberOfFactors, dependent1_columnIndex, dependent2_columnIndex); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": logistic regression not performed."); } } static inline double NUMmin2 (double a, double b) { return a < b ? a : b; } static inline double NUMmax2 (double a, double b) { return a > b ? a : b; } void LogisticRegression_drawBoundary (LogisticRegression me, Graphics graphics, long colx, double xleft, double xright, long coly, double ybottom, double ytop, bool garnish) { RegressionParameter parmx = static_cast (my parameters -> item [colx]); RegressionParameter parmy = static_cast (my parameters -> item [coly]); if (xleft == xright) { xleft = parmx -> minimum; xright = parmx -> maximum; } if (ybottom == ytop) { ybottom = parmy -> minimum; ytop = parmy -> maximum; } double intercept = my intercept; for (long iparm = 1; iparm <= my parameters -> size; iparm ++) { if (iparm != colx && iparm != coly) { RegressionParameter parm = static_cast (my parameters -> item [iparm]); intercept += parm -> value * (0.5 * (parm -> minimum + parm -> maximum)); } } Graphics_setInner (graphics); Graphics_setWindow (graphics, xleft, xright, ybottom, ytop); double xbottom = (intercept + parmy -> value * ybottom) / - parmx -> value; double xtop = (intercept + parmy -> value * ytop) / - parmx -> value; double yleft = (intercept + parmx -> value * xleft) / - parmy -> value; double yright = (intercept + parmx -> value * xright) / - parmy -> value; double xmin = NUMmin2 (xleft, xright), xmax = NUMmax2 (xleft, xright); double ymin = NUMmin2 (ybottom, ytop), ymax = NUMmax2 (ybottom, ytop); //Melder_casual ("LogisticRegression_drawBoundary: %f %f %f %f %f %f %f %f", // xmin, xmax, xbottom, xtop, ymin, ymax, yleft, yright); if (xbottom >= xmin && xbottom <= xmax) { // line goes through bottom? if (xtop >= xmin && xtop <= xmax) // line goes through top? Graphics_line (graphics, xbottom, ybottom, xtop, ytop); // draw from bottom to top else if (yleft >= ymin && yleft <= ymax) // line goes through left? Graphics_line (graphics, xbottom, ybottom, xleft, yleft); // draw from bottom to left else if (yright >= ymin && yright <= ymax) // line goes through right? Graphics_line (graphics, xbottom, ybottom, xright, yright); // draw from bottom to right } else if (yleft >= ymin && yleft <= ymax) { // line goes through left? if (yright >= ymin && yright <= ymax) // line goes through right? Graphics_line (graphics, xleft, yleft, xright, yright); // draw from left to right else if (xtop >= xmin && xtop <= xmax) // line goes through top? Graphics_line (graphics, xleft, yleft, xtop, ytop); // draw from left to top } else if (xtop >= xmin && xtop <= xmax) { // line goes through top? if (yright >= ymin && yright <= ymax) // line goes through right? Graphics_line (graphics, xtop, ytop, xright, yright); // draw from top to right } Graphics_unsetInner (graphics); if (garnish) { Graphics_drawInnerBox (graphics); Graphics_textBottom (graphics, true, parmx -> label); Graphics_marksBottom (graphics, 2, true, true, false); Graphics_textLeft (graphics, true, parmy -> label); Graphics_marksLeft (graphics, 2, true, true, false); } } /* Table Table_LogisticRegression_addProbabilities (Table me, LogisticRegression thee) { for (icell = 1; icell <= numberOfCells; icell ++) { double fittedLogit = parameters [0], fittedP, fittedQ, fittedLogP, fittedLogQ; for (ivar = 1; ivar <= numberOfIndependentVariables; ivar ++) { fittedLogit += parameters [ivar] * Table_getNumericValue_Assert (me, icell, ivar); } if (fittedLogit > 15.0) { fittedLogP = - exp (- fittedLogit); fittedLogQ = - fittedLogit; fittedP = exp (fittedLogP); fittedQ = 1.0 - fittedP; } else if (fittedLogit < -15.0) { fittedLogP = fittedLogit; fittedLogQ = - exp (fittedLogit); fittedP = exp (fittedLogP); fittedQ = 1 - fittedP; } else { fittedP = 1.0 / (1.0 + exp (- fittedLogit)); fittedLogP = log (fittedP); fittedQ = 1.0 - fittedP; fittedLogQ = log (fittedQ); } Table_setNumericValue (thee, icell, numberOfIndependentVariables + 1, fittedQ); Table_setNumericValue (thee, icell, numberOfIndependentVariables + 2, fittedP); } } */ /* End of file LogisticRegression.cpp */ sources_5316/stat/manual_statistics.cpp0000644000176700017670000002571511627220545017147 0ustar paulpaul/* manual_statistics.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" void manual_statistics_init (ManPages me); void manual_statistics_init (ManPages me) { MAN_BEGIN (L"Statistics", L"ppgb", 20060506) INTRO (L"This is the tutorial about basic statistical techniques in Praat, which work " "with the @Table object or even directly from the @Goodies menu. It assumes that you are familiar with the @Intro.") NORMAL (L"(Under construction..................)") NORMAL (L"Goodies menu:") LIST_ITEM (L"\\bu @@Difference of two proportions@") NORMAL (L"For a selected Table:") LIST_ITEM (L"\\bu @@Logistic regression@") NORMAL (L"For more sophisticated techniques, see:") LIST_ITEM (L"\\bu @@Principal component analysis@") LIST_ITEM (L"\\bu @@Multidimensional scaling@") LIST_ITEM (L"\\bu @@Discriminant analysis@") MAN_END MAN_BEGIN (L"Difference of two proportions", L"ppgb", 20090717) INTRO (L"This page explains how you compute the significance of a difference between two proportions " "with a %\\ci^2 (chi-square) test.") ENTRY (L"1. Example of normal use") NORMAL (L"Suppose that you are interested in proving that for a certain experimental participant Task B is easier than Task A." "You let the participant perform Task A 110 times, and she turns out to perform this task correctly 71 times. " "You also let her perform Task B 120 times, and she performs this task correctly 93 times. " "The following table summarizes the results of your experiment:") CODE1 (L"\t\tCorrect\tIncorrect") CODE1 (L"\tTask A\t71\t39") CODE1 (L"\tTask B\t93\t27") NORMAL (L"The null hypothesis is that both tasks are equally difficult for the participant " "and that the probability that she performs Task A correctly is equal to " "the probability that she performs Task B correctly.") NORMAL (L"To compute the probability that the observed proportions are at least as different as 93/120 and 71/110 " "if the null hypothesis is true, go to ##Report difference of two proportions# in the @Goodies menu " "and fill in the four values 71, 39, 93, and 27. The resulting two-tailed %p is 0.04300, suggesting " "that the null hypothesis can be rejected and the two tasks are not equally difficult for the participant " "(if the possibility that Task A is easier for her than Task B can be ruled out a priori, " "then the resulting one-tailed %p is 0.02150).") ENTRY (L"2. Example of incorrect use: areal features") NORMAL (L"An anonymous linguist once proposed that there was a causal relation between blood groups and the incidence " "of dental fricatives. He noticed that dental fricatives occurred mainly in languages whose speakers " "predominantly had blood group O. To prove his point, he tabulated 100 languages:") CODE1 (L"\t\t\tHas /\\tf/ or /\\dh/\t\tNo dental fricatives") CODE1 (L"\tGroup O\t\t24\t\t11") CODE1 (L"\tGroup A or B\t\t29\t\t36") NORMAL (L"Since %p < 0.05, the linguist regarded his hypothesis as being supported by the facts. " "However, this %\\ci^2 test assumes that the 100 languages are independent, but they are not. " "Two adjacent languages tend to correlate in their probability of having dental fricatives, " "and their speakers tend to correlate in their blood groups. Both are %%areal features%, " "which undermine the independence assumed by the %\\ci^2 test. The actual null hypothesis " "that the test rejected was the combined hypothesis that dental fricatives correlate with blood group " "%and that the 100 languages are independent.") NORMAL (L"Another anonymous linguist proposed that those Limburgian dialects that had lost their tone contrast " "compensated this by having larger vowel inventories. He drew up a table of the dialects of 100 villages:") CODE1 (L"\t\t\tHas tone\t\tHas no tone") CODE1 (L"\tHas over 25 vowels\t\t10\t\t7") CODE1 (L"\tHas under 25 vowels\t\t80\t\t3") NORMAL (L"This result is very significant (%p < 10^^-4^), but only shows that %either there is a relation between " "tone and the number of vowels %or that the dialects are not independent. And since adjacent dialects are " "arguably dependent both with respect to tone and the number of vowels, the statistical significance does " "not allow us to draw any conclusion about the relationship between tone and the number of vowels.") ENTRY (L"3. Example of problematic use: pooling participants") NORMAL (L"An anonymous student decided to do the Task A versus Task B experiment described above, " "but did not let one participant perform all the 230 tasks. Instead, she let 5 participants perform 46 tasks each " "(22 times task A, 24 times Task B). The pooled data were:") CODE1 (L"\t\tCorrect\tIncorrect") CODE1 (L"\tTask A\t71\t39") CODE1 (L"\tTask B\t104\t16") NORMAL (L"The resulting %p is 0.00016. So what is the conclusion, if the measurements can clearly be dependent? " "Well, if the null hypothesis is that all five participants are equally good at Task A as at Task B, " "then this hypothesis can be rejected. The conclusion must be that %%these five participants% have on average " "more trouble with Task A than with Task B. The student incorrectly concluded, however, that Task A was " "more difficult for the average population than Task B. In order to be able to draw such a conclusion, " "however, a different test would be required, namely one that takes into account that the five participants " "form a random sample from the total population. The simplest such test would be a sign test over " "the participants: count those participants who score better on Task A than on Task B and see whether this number " "is reliably less than 50 percent of all participants. For five participants, such a sign test " "would %never reach significance at a two-tailed 5 percent level (2*0.5^5 = 0.0625).") ENTRY (L"4. Example of problematic use: pooling participants") NORMAL (L"Our purpose was to disprove the null hypothesis that listeners' perception does not depend on the language " "they think they hear. However, certain vowel tokens acoustically in between the Dutch /\\as/ and the Dutch /\\ct/ " "were perceived 50 percent of the time as /\\as/ and 50 percent of the time as /\\ct/ when Dutch learners of Spanish thought " "they were hearing Dutch, but 60 percent of the time as /\\ct/ when they thought they were hearing Spanish. " "The responses of 40 listeners, all of whom underwent both language modes, is combined in the following table:") CODE1 (L"\t\t/\\as/\t/\\ct/") CODE1 (L"\tDutch mode\t200\t200") CODE1 (L"\tSpanish mode\t160\t240") NORMAL (L"The result was %p = 0.0056, which reliably showed that these 40 listeners on average shifted their category " "boundary toward /\\as/ when they thought that the language they were listening to was Spanish. " "The conclusion is that not all listeners were indifferent to the language mode, " "so that mode-dependent perception must exist. The explanation in this case was that the Spanish /a/ " "(which Dutch learners of Spanish identify with their /\\as/) is more auditorily front than Dutch /\\as/; " "in order to reject the null hypothesis that language modes exist but that their direction is random for each " "learner, i.e. the population average of the shift is zero, a separate test was required to show that the observed " "shift is representative of the population of Dutch learners of Spanish " "(this is easier to accomplish for 40 participants than for 5).") MAN_END MAN_BEGIN (L"Logistic regression", L"ppgb", 20110131) INTRO (L"This page explains how you do logistic regression with Praat. " "You start by saving a table in a text file. " "The following example contains natural stimuli (female speaker) with measured F1 and duration values, " "and the responses of a certain listener who is presented each stimulus 10 times.") CODE1 (L" F1 Dur /ae/ /E/") CODE1 (L" 764 87 2 8") CODE1 (L" 674 104 3 7") CODE1 (L" 574 126 0 10") CODE1 (L" 566 93 1 9") CODE1 (L" 618 118 1 9") CODE1 (L"1025 147 10 0") CODE1 (L" 722 117 7 3") CODE1 (L" 696 169 9 1") CODE1 (L"1024 124 10 0") CODE1 (L" 752 92 6 4") NORMAL (L"In this table we see 10 different stimuli, each characterized by a certain combination " "of the factors (independent variables) %F1 (first formant in Hertz) and %Dur (duration in milliseconds). " "The first row of the table means that there was a stimulus with an F1 of 764 Hz and a duration of 87 ms, " "and that the listener responded to this stimulus 2 times with the response category /\\ae/, " "and the remaining 8 times with the category /\\ep/.") NORMAL (L"A table as above can be typed into a text file. The columns can be separated with spaces and/or tab stops. " "The file can be read into Praat with ##Read Table from table file...#. " "The command ##To logistic regression...# will become available in the #Statistics menu.") ENTRY (L"What does it do?") /*SCRIPT (4.5, 4, "Axes... 60 180 900 500\n" "Marks bottom every... 1 30 yes yes no\n" "Marks left every... 1 50 yes yes no\n" "Text bottom... yes Duration (ms)\n" "Text left... yes F1 (Hz)\n" "mdur_ae = 135\n" "mdur_ep = 95\n" "sdur = 25\n" "mf1_ae = 780\n" "mf1_ep = 620\n" "sf1 = 60\n" "Draw ellipse... mdur_ae-sdur mdur_ae+sdur mf1_ae-sf1 mf1_ae+sf1\n" "Text... mdur_ae Centre mf1_ae Half /\\ae/\n" "Draw ellipse... mdur_ep-sdur mdur_ep+sdur mf1_ep-sf1 mf1_ep+sf1\n" "Text... mdur_ep Centre mf1_ep Half /\\ep/\n" "Draw inner box\n" )*/ NORMAL (L"The logistic regression method will find values %\\al, %%\\be__F1_% and %%\\be__dur_% " "that optimize") FORMULA (L"%\\al + %%\\be__F1_% %F1__%k_ + %%\\be__dur_% %Dur__%k_ = ln (%p__%k_(/\\ep/)/%p__%k_(/\\ae/))") NORMAL (L"where %k runs from 1 to 10, and %p__%k_(/\\ae/) + %p__%k_(/\\ep/) = 1.") NORMAL (L"The optimization criterion is %%maximum likelihood%, i.e. those %\\al, %%\\be__F1_% and %%\\be__dur_% " "will be chosen that lead to values for %p__%k_(/\\ae/) and %p__%k_(/\\ep/) that make the observations in the table " "most likely.") NORMAL (L"Praat will create an object of type #LogisticRegression in the list. " "When you then click the #Info button, Praat will write the values of %\\al (the %intercept), " "%%\\be__F1_% and %%\\be__dur_% into the Info window (as well as much other information).") NORMAL (L"The number of factors does not have to be 2; it can be 1 or more. " "The number of dependent categories is always 2.") MAN_END } /* End of file manual_statistics.c */ sources_5316/stat/Distributions.h0000644000176700017670000000322311622371164015714 0ustar paulpaul#ifndef _Distributions_h_ #define _Distributions_h_ /* Distributions.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Distributions inherits from TableOfReal */ #include "TableOfReal.h" Thing_define (Distributions, TableOfReal) { // overridden methods: protected: virtual void v_info (); }; Distributions Distributions_create (long numberOfRows, long numberOfColumns); int Distributions_peek (Distributions me, long column, wchar **string); int Distributions_peek_opt (Distributions me, long column, long *row); double Distributions_getProbability (Distributions me, const wchar *string, long column); double Distributionses_getMeanAbsoluteDifference (Distributions me, Distributions thee, long column); Distributions Distributions_addTwo (Distributions me, Distributions thee); Distributions Distributions_addMany (Collection me); void Distributions_checkSpecifiedColumnNumberWithinRange (Distributions me, long columnNumber); /* End of file Distributions.h */ #endif sources_5316/stat/TableOfReal_def.h0000644000176700017670000000371011622414406016006 0ustar paulpaul/* TableOfReal_def.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT TableOfReal oo_DEFINE_CLASS (TableOfReal, Data) oo_LONG (numberOfRows) oo_LONG (numberOfColumns) oo_STRING_VECTOR (rowLabels, numberOfRows) oo_STRING_VECTOR (columnLabels, numberOfColumns) oo_DOUBLE_MATRIX (data, numberOfRows, numberOfColumns) #if oo_DECLARING // overridden methods: virtual void v_info (); virtual bool v_hasGetNrow () { return true; } virtual double v_getNrow () { return numberOfRows; } virtual bool v_hasGetNcol () { return true; } virtual double v_getNcol () { return numberOfColumns; } virtual bool v_hasGetRowStr () { return true; } virtual const wchar * v_getRowStr (long irow); virtual bool v_hasGetColStr () { return true; } virtual const wchar * v_getColStr (long icol); virtual bool v_hasGetMatrix () { return true; } virtual double v_getMatrix (long irow, long icol); virtual bool v_hasGetRowIndex () { return true; } virtual double v_getRowIndex (const wchar_t *rowLabel); virtual bool v_hasGetColIndex () { return true; } virtual double v_getColIndex (const wchar_t *columnLabel); #endif oo_END_CLASS (TableOfReal) #undef ooSTRUCT /* End of file TableOfReal_def.h */ sources_5316/stat/Regression_def.h0000644000176700017670000000252011622371732016010 0ustar paulpaul/* Regression_def.h * * Copyright (C) 2005-2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT RegressionParameter oo_DEFINE_CLASS (RegressionParameter, Data) oo_STRING (label) oo_DOUBLE (minimum) oo_DOUBLE (maximum) oo_DOUBLE (value) #if oo_DECLARING || oo_COPYING oo_LONG (tableColumnIndex) #endif oo_END_CLASS (RegressionParameter) #undef ooSTRUCT #define ooSTRUCT Regression oo_DEFINE_CLASS (Regression, Data) oo_DOUBLE (intercept) oo_COLLECTION (Ordered, parameters, RegressionParameter, 0) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (Regression) #undef ooSTRUCT /* End of file Regression_def.h */ sources_5316/stat/Table.h0000644000176700017670000001637011641021732014102 0ustar paulpaul#ifndef _Table_h_ #define _Table_h_ /* Table.h * * Copyright (C) 2002-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection.h" #include "Graphics.h" #include "Interpreter_decl.h" #include "Table_def.h" oo_CLASS_CREATE (TableRow, Data); oo_CLASS_CREATE (Table, Data); void Table_initWithColumnNames (I, long numberOfRows, const wchar_t *columnNames); Table Table_createWithColumnNames (long numberOfRows, const wchar_t *columnNames); void Table_initWithoutColumnNames (I, long numberOfRows, long numberOfColumns); Table Table_createWithoutColumnNames (long numberOfRows, long numberOfColumns); #define Table_create Table_createWithoutColumnNames Table Tables_append (Collection me); void Table_appendRow (Table me); void Table_appendColumn (Table me, const wchar_t *label); void Table_appendSumColumn (Table me, long column1, long column2, const wchar_t *label); void Table_appendDifferenceColumn (Table me, long column1, long column2, const wchar_t *label); void Table_appendProductColumn (Table me, long column1, long column2, const wchar_t *label); void Table_appendQuotientColumn (Table me, long column1, long column2, const wchar_t *label); void Table_removeRow (Table me, long row); void Table_removeColumn (Table me, long column); void Table_insertRow (Table me, long row); void Table_insertColumn (Table me, long column, const wchar_t *label); void Table_setColumnLabel (Table me, long column, const wchar_t *label); long Table_findColumnIndexFromColumnLabel (Table me, const wchar_t *label); long Table_getColumnIndexFromColumnLabel (Table me, const wchar_t *columnLabel); long * Table_getColumnIndicesFromColumnLabelString (Table me, const wchar_t *string, long *numberOfTokens); long Table_searchColumn (Table me, long column, const wchar_t *value); /* * Procedure for reading strings or numbers from table cells: * use the following two calls exclusively. */ const wchar * Table_getStringValue_Assert (Table me, long row, long column); double Table_getNumericValue_Assert (Table me, long row, long column); /* * Procedure for writing strings or numbers into table cells: * use the following two calls exclusively. */ void Table_setStringValue (Table me, long row, long column, const wchar_t *value); void Table_setNumericValue (Table me, long row, long column, double value); /* For optimizations only (e.g. conversion to Matrix or TableOfReal). */ void Table_numericize_Assert (Table me, long columnNumber); double Table_getQuantile (Table me, long column, double quantile); double Table_getMean (Table me, long column); double Table_getMaximum (Table me, long icol); double Table_getMinimum (Table me, long icol); double Table_getGroupMean (Table me, long column, long groupColumn, const wchar_t *group); double Table_getStdev (Table me, long column); long Table_drawRowFromDistribution (Table me, long column); double Table_getCorrelation_pearsonR (Table me, long column1, long column2, double significanceLevel, double *out_significance, double *out_lowerLimit, double *out_upperLimit); double Table_getCorrelation_kendallTau (Table me, long column1, long column2, double significanceLevel, double *out_significance, double *out_lowerLimit, double *out_upperLimit); double Table_getMean_studentT (Table me, long column, double significanceLevel, double *out_tFromZero, double *out_numberOfDegreesOfFreedom, double *out_significanceFromZero, double *out_lowerLimit, double *out_upperLimit); double Table_getDifference_studentT (Table me, long column1, long column2, double significanceLevel, double *out_t, double *out_numberOfDegreesOfFreedom, double *out_significance, double *out_lowerLimit, double *out_upperLimit); double Table_getGroupMean_studentT (Table me, long column, long groupColumn, const wchar *group1, double significanceLevel, double *out_tFromZero, double *out_numberOfDegreesOfFreedom, double *out_significanceFromZero, double *out_lowerLimit, double *out_upperLimit); double Table_getGroupDifference_studentT (Table me, long column, long groupColumn, const wchar *group1, const wchar *group2, double significanceLevel, double *out_tFromZero, double *out_numberOfDegreesOfFreedom, double *out_significanceFromZero, double *out_lowerLimit, double *out_upperLimit); double Table_getGroupDifference_wilcoxonRankSum (Table me, long column, long groupColumn, const wchar *group1, const wchar *group2, double *out_rankSum, double *out_significanceFromZero); double Table_getVarianceRatio (Table me, long column1, long column2, double significanceLevel, double *out_significance, double *out_lowerLimit, double *out_upperLimit); bool Table_getExtrema (Table me, long icol, double *minimum, double *maximum); void Table_formula (Table me, long column, const wchar *formula, Interpreter interpreter); void Table_formula_columnRange (Table me, long column1, long column2, const wchar *expression, Interpreter interpreter); void Table_sortRows_Assert (Table me, long *columns, long numberOfColumns); void Table_sortRows_string (Table me, const wchar *columns_string); void Table_randomizeRows (Table me); void Table_scatterPlot (Table me, Graphics g, long xcolumn, long ycolumn, double xmin, double xmax, double ymin, double ymax, long markColumn, int fontSize, int garnish); void Table_scatterPlot_mark (Table me, Graphics g, long xcolumn, long ycolumn, double xmin, double xmax, double ymin, double ymax, double markSize_mm, const wchar *mark, int garnish); void Table_drawEllipse_e (Table me, Graphics g, long xcolumn, long ycolumn, double xmin, double xmax, double ymin, double ymax, double numberOfSigmas, int garnish); void Table_list (Table me, bool includeRowNumbers); void Table_writeToTabSeparatedFile (Table me, MelderFile file); void Table_writeToCommaSeparatedFile (Table me, MelderFile file); Table Table_readFromTableFile (MelderFile file); Table Table_readFromCharacterSeparatedTextFile (MelderFile file, wchar separator); Table Table_extractRowsWhereColumn_number (Table me, long column, int which_Melder_NUMBER, double criterion); Table Table_extractRowsWhereColumn_string (Table me, long column, int which_Melder_STRING, const wchar_t *criterion); Table Table_collapseRows (Table me, const wchar *factors_string, const wchar *columnsToSum_string, const wchar *columnsToAverage_string, const wchar *columnsToMedianize_string, const wchar *columnsToAverageLogarithmically_string, const wchar *columnsToMedianizeLogarithmically_string); Table Table_rowsToColumns (Table me, const wchar *factors_string, long columnToTranspose, const wchar_t *columnsToExpand_string); void Table_checkSpecifiedRowNumberWithinRange (Table me, long rowNumber); void Table_checkSpecifiedColumnNumberWithinRange (Table me, long columnNumber); /* End of file Table.h */ #endif sources_5316/stat/PairDistribution.h0000644000176700017670000000415211625721240016344 0ustar paulpaul#ifndef _PairDistribution_h_ #define _PairDistribution_h_ /* PairDistribution.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Strings.h" #include "Table.h" #include "Distributions.h" #include "PairDistribution_def.h" oo_CLASS_CREATE (PairProbability, Data); oo_CLASS_CREATE (PairDistribution, Data); PairProbability PairProbability_create (const wchar *string1, const wchar *string2, double weight); PairDistribution PairDistribution_create (void); const wchar * PairDistribution_getString1 (PairDistribution me, long pairNumber); const wchar * PairDistribution_getString2 (PairDistribution me, long pairNumber); double PairDistribution_getWeight (PairDistribution me, long pairNumber); void PairDistribution_add (PairDistribution me, const wchar *string1, const wchar *string2, double weight); void PairDistribution_removeZeroWeights (PairDistribution me); void PairDistribution_to_Stringses (PairDistribution me, long nout, Strings *strings1, Strings *strings2); void PairDistribution_peekPair (PairDistribution me, wchar **string1, wchar **string2); double PairDistribution_getFractionCorrect_maximumLikelihood (PairDistribution me); double PairDistribution_getFractionCorrect_probabilityMatching (PairDistribution me); double PairDistribution_Distributions_getFractionCorrect (PairDistribution me, Distributions thee, long column); Table PairDistribution_to_Table (PairDistribution me); /* End of file PairDistribution.h */ #endif sources_5316/stat/Table_def.h0000644000176700017670000000503411734343754014731 0ustar paulpaul/* Table_def.h * * Copyright (C) 2002-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT TableCell oo_DEFINE_STRUCT (TableCell) oo_STRING (string) #if oo_DECLARING || oo_COPYING oo_DOUBLE (number) #endif oo_END_STRUCT (TableCell) #undef ooSTRUCT #define ooSTRUCT TableRow oo_DEFINE_CLASS (TableRow, Data) #if oo_DECLARING || oo_COPYING oo_LONG (sortingIndex) #endif oo_LONG (numberOfColumns) oo_STRUCT_VECTOR (TableCell, cells, numberOfColumns) oo_END_CLASS (TableRow) #undef ooSTRUCT #define ooSTRUCT TableColumnHeader oo_DEFINE_STRUCT (TableColumnHeader) oo_STRING (label) #if oo_DECLARING || oo_COPYING oo_INT (numericized) #endif oo_END_STRUCT (TableColumnHeader) #undef ooSTRUCT #define ooSTRUCT Table oo_DEFINE_CLASS (Table, Data) oo_LONG (numberOfColumns) oo_STRUCT_VECTOR (TableColumnHeader, columnHeaders, numberOfColumns) oo_COLLECTION (Ordered, rows, TableRow, 0) #if oo_DECLARING // functions: TableRow f_peekRow (long i) { return static_cast (rows -> item [i]); } // overridden methods: virtual void v_info (); virtual bool v_hasGetNrow () { return true; } virtual double v_getNrow () { return rows -> size; } virtual bool v_hasGetNcol () { return true; } virtual double v_getNcol () { return numberOfColumns; } virtual bool v_hasGetColStr () { return true; } virtual const wchar * v_getColStr (long columnNumber); virtual bool v_hasGetMatrix () { return true; } virtual double v_getMatrix (long rowNumber, long columnNumber); virtual bool v_hasGetMatrixStr () { return true; } virtual const wchar * v_getMatrixStr (long rowNumber, long columnNumber); virtual bool v_hasGetColIndex () { return true; } virtual double v_getColIndex (const wchar *columnLabel); #endif oo_END_CLASS (Table) #undef ooSTRUCT /* End of file Table_def.h */ sources_5316/stat/PairDistribution_def.h0000644000176700017670000000235311622366460017171 0ustar paulpaul/* PairDistribution_def.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT PairProbability oo_DEFINE_CLASS (PairProbability, Data) oo_STRING (string1) oo_STRING (string2) oo_DOUBLE (weight) oo_END_CLASS (PairProbability) #undef ooSTRUCT #define ooSTRUCT PairDistribution oo_DEFINE_CLASS (PairDistribution, Data) oo_COLLECTION (Ordered, pairs, PairProbability, 0) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (PairDistribution) #undef ooSTRUCT /* End of file PairDistribution_def.h */ sources_5316/stat/TableOfReal.cpp0000644000176700017670000013422711755137264015546 0ustar paulpaul/* TableOfReal.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include "TableOfReal.h" #include "NUM2.h" #include "Matrix.h" #include "Formula.h" #include "oo_DESTROY.h" #include "TableOfReal_def.h" #include "oo_COPY.h" #include "TableOfReal_def.h" #include "oo_EQUAL.h" #include "TableOfReal_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "TableOfReal_def.h" #include "oo_WRITE_BINARY.h" #include "TableOfReal_def.h" #include "oo_READ_BINARY.h" #include "TableOfReal_def.h" #include "oo_DESCRIPTION.h" #include "TableOfReal_def.h" static void fprintquotedstring (MelderFile file, const wchar_t *s) { MelderFile_writeCharacter (file, '\"'); if (s) { wchar_t c; while ((c = *s ++) != '\0') { MelderFile_writeCharacter (file, c); if (c == '\"') MelderFile_writeCharacter (file, c); } } MelderFile_writeCharacter (file, '\"'); } void structTableOfReal :: v_writeText (MelderFile file) { texputi4 (file, numberOfColumns, L"numberOfColumns", 0,0,0,0,0); MelderFile_write1 (file, L"\ncolumnLabels []: "); if (numberOfColumns < 1) MelderFile_write1 (file, L"(empty)"); MelderFile_write1 (file, L"\n"); for (long i = 1; i <= numberOfColumns; i ++) { fprintquotedstring (file, columnLabels [i]); MelderFile_writeCharacter (file, '\t'); } texputi4 (file, numberOfRows, L"numberOfRows", 0,0,0,0,0); for (long i = 1; i <= numberOfRows; i ++) { MelderFile_write3 (file, L"\nrow [", Melder_integer (i), L"]: "); fprintquotedstring (file, rowLabels [i]); for (long j = 1; j <= numberOfColumns; j ++) { double x = data [i] [j]; MelderFile_write2 (file, L"\t", Melder_double (x)); } } } void structTableOfReal :: v_readText (MelderReadText a_text) { numberOfColumns = texgeti4 (a_text); if (numberOfColumns >= 1) { columnLabels = NUMvector (1, numberOfColumns); for (long i = 1; i <= numberOfColumns; i ++) columnLabels [i] = texgetw2 (a_text); } numberOfRows = texgeti4 (a_text); if (numberOfRows >= 1) { rowLabels = NUMvector (1, numberOfRows); } if (numberOfRows >= 1 && numberOfColumns >= 1) { data = NUMmatrix (1, numberOfRows, 1, numberOfColumns); for (long i = 1; i <= numberOfRows; i ++) { rowLabels [i] = texgetw2 (a_text); for (long j = 1; j <= numberOfColumns; j ++) data [i] [j] = texgetr8 (a_text); } } } void structTableOfReal :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of rows: ", Melder_integer (numberOfRows)); MelderInfo_writeLine2 (L"Number of columns: ", Melder_integer (numberOfColumns)); } const wchar * structTableOfReal :: v_getRowStr (long irow) { if (irow < 1 || irow > numberOfRows) return NULL; return rowLabels [irow] ? rowLabels [irow] : L""; } const wchar * structTableOfReal :: v_getColStr (long icol) { if (icol < 1 || icol > numberOfColumns) return NULL; return columnLabels [icol] ? columnLabels [icol] : L""; } double structTableOfReal :: v_getMatrix (long irow, long icol) { if (irow < 1 || irow > numberOfRows) return NUMundefined; if (icol < 1 || icol > numberOfColumns) return NUMundefined; return data [irow] [icol]; } double structTableOfReal :: v_getRowIndex (const wchar_t *rowLabel) { return TableOfReal_rowLabelToIndex (this, rowLabel); } double structTableOfReal :: v_getColIndex (const wchar_t *columnLabel) { return TableOfReal_columnLabelToIndex (this, columnLabel); } Thing_implement (TableOfReal, Data, 0); void TableOfReal_init (TableOfReal me, long numberOfRows, long numberOfColumns) { if (numberOfRows < 1 || numberOfColumns < 1) Melder_throw ("Cannot create cell-less table."); my numberOfRows = numberOfRows; my numberOfColumns = numberOfColumns; my rowLabels = NUMvector (1, numberOfRows); my columnLabels = NUMvector (1, numberOfColumns); my data = NUMmatrix (1, my numberOfRows, 1, my numberOfColumns); } TableOfReal TableOfReal_create (long numberOfRows, long numberOfColumns) { try { autoTableOfReal me = Thing_new (TableOfReal); TableOfReal_init (me.peek(), numberOfRows, numberOfColumns); return me.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal not created."); } } /***** QUERY *****/ long TableOfReal_rowLabelToIndex (TableOfReal me, const wchar_t *label) { for (long irow = 1; irow <= my numberOfRows; irow ++) if (my rowLabels [irow] && wcsequ (my rowLabels [irow], label)) return irow; return 0; } long TableOfReal_columnLabelToIndex (TableOfReal me, const wchar_t *label) { for (long icol = 1; icol <= my numberOfColumns; icol ++) if (my columnLabels [icol] && wcsequ (my columnLabels [icol], label)) return icol; return 0; } double TableOfReal_getColumnMean (TableOfReal me, long columnNumber) { double sum = 0.0; if (columnNumber < 1 || columnNumber > my numberOfColumns) return NUMundefined; if (my numberOfRows < 1) return NUMundefined; for (long irow = 1; irow <= my numberOfRows; irow ++) sum += my data [irow] [columnNumber]; return sum / my numberOfRows; } double TableOfReal_getColumnStdev (TableOfReal me, long columnNumber) { double mean = TableOfReal_getColumnMean (me, columnNumber), sum = 0.0, d; if (columnNumber < 1 || columnNumber > my numberOfColumns) return NUMundefined; if (my numberOfRows < 2) return NUMundefined; for (long irow = 1; irow <= my numberOfRows; irow ++) sum += ( d = my data [irow] [columnNumber] - mean, d * d ); return sqrt (sum / (my numberOfRows - 1)); } /***** MODIFY *****/ void TableOfReal_removeRow (TableOfReal me, long rowNumber) { try { if (my numberOfRows == 1) Melder_throw (Thing_messageName (me), " has only one row, and a TableOfReal without rows cannot exist."); if (rowNumber < 1 || rowNumber > my numberOfRows) Melder_throw ("No row ", rowNumber, "."); autoNUMmatrix data (1, my numberOfRows - 1, 1, my numberOfColumns); for (long icol = 1; icol <= my numberOfColumns; icol ++) { for (long irow = 1; irow < rowNumber; irow ++) data [irow] [icol] = my data [irow] [icol]; for (long irow = rowNumber; irow < my numberOfRows; irow ++) data [irow] [icol] = my data [irow + 1] [icol]; } /* * Change without error. */ Melder_free (my rowLabels [rowNumber]); for (long irow = rowNumber; irow < my numberOfRows; irow ++) my rowLabels [irow] = my rowLabels [irow + 1]; NUMmatrix_free (my data, 1, 1); my data = data.transfer(); my numberOfRows --; } catch (MelderError) { Melder_throw (me, ": row ", rowNumber, " not removed."); } } void TableOfReal_insertRow (TableOfReal me, long rowNumber) { try { if (rowNumber < 1 || rowNumber > my numberOfRows + 1) Melder_throw ("Cannot create row ", rowNumber, "."); autoNUMmatrix data (1, my numberOfRows + 1, 1, my numberOfColumns); autoNUMvector rowLabels (1, my numberOfRows + 1); // not autostringvector... for (long irow = 1; irow < rowNumber; irow ++) { rowLabels [irow] = my rowLabels [irow]; // ...because this is a dangling copy for (long icol = 1; icol <= my numberOfColumns; icol ++) data [irow] [icol] = my data [irow] [icol]; } for (long irow = my numberOfRows + 1; irow > rowNumber; irow --) { rowLabels [irow] = my rowLabels [irow - 1]; for (long icol = 1; icol <= my numberOfColumns; icol ++) data [irow] [icol] = my data [irow - 1] [icol]; } /* * Change without error. */ NUMvector_free (my rowLabels, 1); my rowLabels = rowLabels.transfer(); NUMmatrix_free (my data, 1, 1); my data = data.transfer(); my numberOfRows ++; } catch (MelderError) { Melder_throw (me, ": row at position ", rowNumber, " not inserted."); } } void TableOfReal_removeColumn (TableOfReal me, long columnNumber) { try { if (my numberOfColumns == 1) Melder_throw ("Cannot remove the only column."); if (columnNumber < 1 || columnNumber > my numberOfColumns) Melder_throw ("No column ", columnNumber, "."); autoNUMmatrix data (1, my numberOfRows, 1, my numberOfColumns - 1); for (long irow = 1; irow <= my numberOfRows; irow ++) { for (long icol = 1; icol < columnNumber; icol ++) data [irow] [icol] = my data [irow] [icol]; for (long icol = columnNumber; icol < my numberOfColumns; icol ++) data [irow] [icol] = my data [irow] [icol + 1]; } /* * Change without error. */ Melder_free (my columnLabels [columnNumber]); for (long icol = columnNumber; icol < my numberOfColumns; icol ++) my columnLabels [icol] = my columnLabels [icol + 1]; NUMmatrix_free (my data, 1, 1); my data = data.transfer(); my numberOfColumns --; } catch (MelderError) { Melder_throw (me, ": column at position ", columnNumber, " not inserted."); } } void TableOfReal_insertColumn (TableOfReal me, long columnNumber) { try { if (columnNumber < 1 || columnNumber > my numberOfColumns + 1) Melder_throw ("Cannot create column ", columnNumber, "."); autoNUMmatrix data (1, my numberOfRows, 1, my numberOfColumns + 1); autoNUMvector columnLabels (1, my numberOfColumns + 1); // not autostringvector... for (long j = 1; j < columnNumber; j ++) { columnLabels [j] = my columnLabels [j]; // ...because this is a dangling copy for (long i = 1; i <= my numberOfRows; i ++) data [i] [j] = my data [i] [j]; } for (long j = my numberOfColumns + 1; j > columnNumber; j --) { columnLabels [j] = my columnLabels [j - 1]; for (long i = 1; i <= my numberOfRows; i ++) data [i] [j] = my data [i] [j - 1]; } /* * Change without error. */ NUMvector_free (my columnLabels, 1); my columnLabels = columnLabels.transfer(); NUMmatrix_free (my data, 1, 1); my data = data.transfer(); my numberOfColumns ++; } catch (MelderError) { Melder_throw (me, ": column at position ", columnNumber, " not inserted."); } } void TableOfReal_setRowLabel (TableOfReal me, long rowNumber, const wchar_t *label) { try { if (rowNumber < 1 || rowNumber > my numberOfRows) return; autostring newLabel = Melder_wcsdup (label); /* * Change without error. */ Melder_free (my rowLabels [rowNumber]); my rowLabels [rowNumber] = newLabel.transfer(); } catch (MelderError) { Melder_throw (me, ": label of row ", rowNumber, " not set."); } } void TableOfReal_setColumnLabel (TableOfReal me, long columnNumber, const wchar_t *label) { try { if (columnNumber < 1 || columnNumber > my numberOfColumns) return; autostring newLabel = Melder_wcsdup (label); /* * Change without error. */ Melder_free (my columnLabels [columnNumber]); my columnLabels [columnNumber] = newLabel.transfer(); } catch (MelderError) { Melder_throw (me, ": label of column ", columnNumber, " not set."); } } void TableOfReal_formula (TableOfReal me, const wchar *expression, Interpreter interpreter, TableOfReal thee) { try { Formula_compile (interpreter, me, expression, kFormula_EXPRESSION_TYPE_NUMERIC, TRUE); therror if (thee == NULL) thee = me; for (long irow = 1; irow <= my numberOfRows; irow ++) { for (long icol = 1; icol <= my numberOfColumns; icol ++) { struct Formula_Result result; Formula_run (irow, icol, & result); therror thy data [irow] [icol] = result. result.numericResult; } } } catch (MelderError) { Melder_throw (me, ": formula not completed."); } } /***** EXTRACT PART *****/ static void copyRowLabels (TableOfReal me, TableOfReal thee) { Melder_assert (me != thee); Melder_assert (my numberOfRows == thy numberOfRows); for (long irow = 1; irow <= my numberOfRows; irow ++) { thy rowLabels [irow] = Melder_wcsdup (my rowLabels [irow]); } } static void copyColumnLabels (TableOfReal me, TableOfReal thee) { Melder_assert (me != thee); Melder_assert (my numberOfColumns == thy numberOfColumns); for (long icol = 1; icol <= my numberOfColumns; icol ++) { thy columnLabels [icol] = Melder_wcsdup (my columnLabels [icol]); } } static void copyRow (TableOfReal me, long myRow, TableOfReal thee, long thyRow) { Melder_assert (me != thee); Melder_assert (my numberOfColumns == thy numberOfColumns); thy rowLabels [thyRow] = Melder_wcsdup (my rowLabels [myRow]); for (long icol = 1; icol <= my numberOfColumns; icol ++) { thy data [thyRow] [icol] = my data [myRow] [icol]; } } static void copyColumn (TableOfReal me, long myCol, TableOfReal thee, long thyCol) { Melder_assert (me != thee); Melder_assert (my numberOfRows == thy numberOfRows); thy columnLabels [thyCol] = Melder_wcsdup (my columnLabels [myCol]); for (long irow = 1; irow <= my numberOfRows; irow ++) { thy data [irow] [thyCol] = my data [irow] [myCol]; } } TableOfReal TableOfReal_extractRowsWhereColumn (TableOfReal me, long column, int which_Melder_NUMBER, double criterion) { try { if (column < 1 || column > my numberOfColumns) Melder_throw ("No such column: ", column, "."); long n = 0; for (long irow = 1; irow <= my numberOfRows; irow ++) { if (Melder_numberMatchesCriterion (my data [irow] [column], which_Melder_NUMBER, criterion)) { n ++; } } if (n == 0) Melder_throw ("No row matches this criterion."); autoTableOfReal thee = TableOfReal_create (n, my numberOfColumns); copyColumnLabels (me, thee.peek()); n = 0; for (long irow = 1; irow <= my numberOfRows; irow ++) if (Melder_numberMatchesCriterion (my data [irow] [column], which_Melder_NUMBER, criterion)) copyRow (me, irow, thee.peek(), ++ n); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": rows not extracted."); } } TableOfReal TableOfReal_extractRowsWhereLabel (TableOfReal me, int which_Melder_STRING, const wchar_t *criterion) { try { long n = 0; for (long irow = 1; irow <= my numberOfRows; irow ++) { if (Melder_stringMatchesCriterion (my rowLabels [irow], which_Melder_STRING, criterion)) { n ++; } } if (n == 0) Melder_throw (L"No row matches this criterion."); autoTableOfReal thee = TableOfReal_create (n, my numberOfColumns); copyColumnLabels (me, thee.peek()); n = 0; for (long irow = 1; irow <= my numberOfRows; irow ++) if (Melder_stringMatchesCriterion (my rowLabels [irow], which_Melder_STRING, criterion)) copyRow (me, irow, thee.peek(), ++ n); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": rows not extracted."); } } TableOfReal TableOfReal_extractColumnsWhereRow (TableOfReal me, long row, int which_Melder_NUMBER, double criterion) { try { if (row < 1 || row > my numberOfRows) Melder_throw ("No such row: ", row, "."); long n = 0; for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (Melder_numberMatchesCriterion (my data [row] [icol], which_Melder_NUMBER, criterion)) { n ++; } } if (n == 0) Melder_throw ("No column matches this criterion."); autoTableOfReal thee = TableOfReal_create (my numberOfRows, n); copyRowLabels (me, thee.peek()); n = 0; for (long icol = 1; icol <= my numberOfColumns; icol ++) if (Melder_numberMatchesCriterion (my data [row] [icol], which_Melder_NUMBER, criterion)) copyColumn (me, icol, thee.peek(), ++ n); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": columns not extracted."); } } TableOfReal TableOfReal_extractColumnsWhereLabel (TableOfReal me, int which_Melder_STRING, const wchar_t *criterion) { try { long n = 0; for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (Melder_stringMatchesCriterion (my columnLabels [icol], which_Melder_STRING, criterion)) { n ++; } } if (n == 0) Melder_throw ("No column matches this criterion."); autoTableOfReal thee = TableOfReal_create (my numberOfRows, n); copyRowLabels (me, thee.peek()); n = 0; for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (Melder_stringMatchesCriterion (my columnLabels [icol], which_Melder_STRING, criterion)) { copyColumn (me, icol, thee.peek(), ++ n); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": columns not extracted."); } } /* * Acceptable ranges e.g. "1 4 2 3:7 4:3 3:5:2" --> * 1, 4, 2, 3, 4, 5, 6, 7, 4, 3, 3, 4, 5, 4, 3, 2 * Overlap is allowed. Ranges can go up and down. */ static long *getElementsOfRanges (const wchar *ranges, long maximumElement, long *numberOfElements, const wchar *elementType) { /* * Count the elements. */ long previousElement = 0; *numberOfElements = 0; const wchar *p = & ranges [0]; for (;;) { while (*p == ' ' || *p == '\t') p ++; if (*p == '\0') break; if (isdigit (*p)) { long currentElement = wcstol (p, NULL, 10); if (currentElement == 0) Melder_throw ("No such ", elementType, L": 0 (minimum is 1)."); if (currentElement > maximumElement) Melder_throw ("No such ", elementType, ": ", currentElement, " (maximum is ", maximumElement, ")."); *numberOfElements += 1; previousElement = currentElement; do { p ++; } while (isdigit (*p)); } else if (*p == ':') { if (previousElement == 0) Melder_throw ("Cannot start range with colon."); do { p ++; } while (*p == ' ' || *p == '\t'); if (*p == '\0') Melder_throw ("Cannot end range with colon."); if (! isdigit (*p)) Melder_throw ("End of range should be a positive whole number."); long currentElement = wcstol (p, NULL, 10); if (currentElement == 0) Melder_throw ("No such ", elementType, ": 0 (minimum is 1)."); if (currentElement > maximumElement) Melder_throw ("No such ", elementType, ": ", currentElement, " (maximum is ", maximumElement, ")."); if (currentElement > previousElement) { *numberOfElements += currentElement - previousElement; } else { *numberOfElements += previousElement - currentElement; } previousElement = currentElement; do { p ++; } while (isdigit (*p)); } else { Melder_throw ("Start of range should be a positive whole number."); } } /* * Create room for the elements. */ autoNUMvector elements (1, *numberOfElements); /* * Store the elements. */ previousElement = 0; *numberOfElements = 0; p = & ranges [0]; for (;;) { while (*p == ' ' || *p == '\t') p ++; if (*p == '\0') break; if (isdigit (*p)) { long currentElement = wcstol (p, NULL, 10); elements [++ *numberOfElements] = currentElement; previousElement = currentElement; do { p ++; } while (isdigit (*p)); } else if (*p == ':') { do { p ++; } while (*p == ' ' || *p == '\t'); long currentElement = wcstol (p, NULL, 10); if (currentElement > previousElement) { for (long ielement = previousElement + 1; ielement <= currentElement; ielement ++) { elements [++ *numberOfElements] = ielement; } } else { for (long ielement = previousElement - 1; ielement >= currentElement; ielement --) { elements [++ *numberOfElements] = ielement; } } previousElement = currentElement; do { p ++; } while (isdigit (*p)); } } return elements.transfer(); } TableOfReal TableOfReal_extractRowRanges (TableOfReal me, const wchar *ranges) { try { long numberOfElements; autoNUMvector elements (getElementsOfRanges (ranges, my numberOfRows, & numberOfElements, L"row"), 1); autoTableOfReal thee = TableOfReal_create (numberOfElements, my numberOfColumns); copyColumnLabels (me, thee.peek()); for (long ielement = 1; ielement <= numberOfElements; ielement ++) copyRow (me, elements [ielement], thee.peek(), ielement); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": row ranges not extracted."); } } TableOfReal TableOfReal_extractColumnRanges (TableOfReal me, const wchar *ranges) { try { long numberOfElements; autoNUMvector elements (getElementsOfRanges (ranges, my numberOfColumns, & numberOfElements, L"column"), 1); autoTableOfReal thee = TableOfReal_create (my numberOfRows, numberOfElements); copyRowLabels (me, thee.peek()); for (long ielement = 1; ielement <= numberOfElements; ielement ++) copyColumn (me, elements [ielement], thee.peek(), ielement); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": column ranges not extracted."); } } TableOfReal TableOfReal_extractRowsWhere (TableOfReal me, const wchar_t *condition, Interpreter interpreter) { try { Formula_compile (interpreter, me, condition, kFormula_EXPRESSION_TYPE_NUMERIC, TRUE); therror /* * Count the new number of rows. */ long numberOfElements = 0; for (long irow = 1; irow <= my numberOfRows; irow ++) { for (long icol = 1; icol <= my numberOfColumns; icol ++) { struct Formula_Result result; Formula_run (irow, icol, & result); therror if (result. result.numericResult != 0.0) { numberOfElements ++; break; } } } if (numberOfElements < 1) Melder_throw ("No rows match this condition."); /* * Create room for the result. */ autoTableOfReal thee = TableOfReal_create (numberOfElements, my numberOfColumns); copyColumnLabels (me, thee.peek()); /* * Store the result. */ numberOfElements = 0; for (long irow = 1; irow <= my numberOfRows; irow ++) { for (long icol = 1; icol <= my numberOfColumns; icol ++) { struct Formula_Result result; Formula_run (irow, icol, & result); if (result. result.numericResult != 0.0) { copyRow (me, irow, thee.peek(), ++ numberOfElements); break; } } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": rows not extracted."); } } TableOfReal TableOfReal_extractColumnsWhere (TableOfReal me, const wchar_t *condition, Interpreter interpreter) { try { Formula_compile (interpreter, me, condition, kFormula_EXPRESSION_TYPE_NUMERIC, TRUE); therror /* * Count the new number of columns. */ long numberOfElements = 0; for (long icol = 1; icol <= my numberOfColumns; icol ++) { for (long irow = 1; irow <= my numberOfRows; irow ++) { struct Formula_Result result; Formula_run (irow, icol, & result); therror if (result. result.numericResult != 0.0) { numberOfElements ++; break; } } } if (numberOfElements < 1) Melder_throw ("No columns match this condition."); /* * Create room for the result. */ autoTableOfReal thee = TableOfReal_create (my numberOfRows, numberOfElements); copyRowLabels (me, thee.peek()); /* * Store the result. */ numberOfElements = 0; for (long icol = 1; icol <= my numberOfColumns; icol ++) { for (long irow = 1; irow <= my numberOfRows; irow ++) { struct Formula_Result result; Formula_run (irow, icol, & result); therror if (result. result.numericResult != 0.0) { copyColumn (me, icol, thee.peek(), ++ numberOfElements); break; } } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": columns not extracted."); } } /***** EXTRACT *****/ Strings TableOfReal_extractRowLabelsAsStrings (TableOfReal me) { try { autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, my numberOfRows); thy numberOfStrings = my numberOfRows; for (long irow = 1; irow <= my numberOfRows; irow ++) { thy strings [irow] = Melder_wcsdup (my rowLabels [irow] ? my rowLabels [irow] : L""); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": row labels not extracted."); } } Strings TableOfReal_extractColumnLabelsAsStrings (TableOfReal me) { try { autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, my numberOfColumns); thy numberOfStrings = my numberOfColumns; for (long icol = 1; icol <= my numberOfColumns; icol ++) { thy strings [icol] = Melder_wcsdup (my columnLabels [icol] ? my columnLabels [icol] : L""); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": column labels not extracted."); } } /***** DRAW *****/ static void NUMrationalize (double x, long *numerator, long *denominator) { double epsilon = 1e-6; *numerator = 1; for (*denominator = 1; *denominator <= 100000; (*denominator) ++) { double numerator_d = x * *denominator, rounded = floor (numerator_d + 0.5); if (fabs (rounded - numerator_d) < epsilon) { *numerator = rounded; return; } } *denominator = 0; /* Failure. */ } static void print4 (wchar_t *buffer, double value, int iformat, int width, int precision) { wchar_t formatString [40]; if (value == NUMundefined) wcscpy (buffer, L"undefined"); else if (iformat == 4) { long numerator, denominator; NUMrationalize (value, & numerator, & denominator); if (numerator == 0) swprintf (buffer, 40, L"0"); else if (denominator > 1) swprintf (buffer, 40, L"%ld/%ld", numerator, denominator); else swprintf (buffer, 40, L"%.7g", value); } else { swprintf (formatString, 40, L"%%%d.%d%c", width, precision, iformat == 1 ? 'f' : iformat == 2 ? 'e' : 'g'); swprintf (buffer, 40, formatString, value); } } static void fixRows (TableOfReal me, long *rowmin, long *rowmax) { if (*rowmax < *rowmin) { *rowmin = 1; *rowmax = my numberOfRows; } else if (*rowmin < 1) *rowmin = 1; else if (*rowmax > my numberOfRows) *rowmax = my numberOfRows; } static void fixColumns (TableOfReal me, long *colmin, long *colmax) { if (*colmax < *colmin) { *colmin = 1; *colmax = my numberOfColumns; } else if (*colmin < 1) *colmin = 1; else if (*colmax > my numberOfColumns) *colmax = my numberOfColumns; } static double getMaxRowLabelWidth (TableOfReal me, Graphics graphics, long rowmin, long rowmax) { double maxWidth = 0.0; if (! my rowLabels) return 0.0; fixRows (me, & rowmin, & rowmax); for (long irow = rowmin; irow <= rowmax; irow ++) if (my rowLabels [irow] && my rowLabels [irow] [0]) { double textWidth = Graphics_textWidth_ps (graphics, my rowLabels [irow], TRUE); /* SILIPA is bigger than XIPA */ if (textWidth > maxWidth) maxWidth = textWidth; } return maxWidth; } static double getLeftMargin (Graphics graphics) { return Graphics_dxMMtoWC (graphics, 1); } static double getLineSpacing (Graphics graphics) { return Graphics_dyMMtoWC (graphics, 1.5 * Graphics_inqFontSize (graphics) * 25.4 / 72); } static double getMaxColumnLabelHeight (TableOfReal me, Graphics graphics, long colmin, long colmax) { double maxHeight = 0.0, lineSpacing = getLineSpacing (graphics); if (! my columnLabels) return 0.0; fixRows (me, & colmin, & colmax); for (long icol = colmin; icol <= colmax; icol ++) if (my columnLabels [icol] && my columnLabels [icol] [0]) { if (! maxHeight) maxHeight = lineSpacing; } return maxHeight; } void TableOfReal_drawAsNumbers (TableOfReal me, Graphics graphics, long rowmin, long rowmax, int iformat, int precision) { fixRows (me, & rowmin, & rowmax); Graphics_setInner (graphics); Graphics_setWindow (graphics, 0.5, my numberOfColumns + 0.5, 0, 1); double leftMargin = getLeftMargin (graphics); // not earlier! double lineSpacing = getLineSpacing (graphics); // not earlier! double maxTextWidth = getMaxRowLabelWidth (me, graphics, rowmin, rowmax); double maxTextHeight = getMaxColumnLabelHeight (me, graphics, 1, my numberOfColumns); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_BOTTOM); for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (my columnLabels && my columnLabels [icol] && my columnLabels [icol] [0]) Graphics_text (graphics, icol, 1, my columnLabels [icol]); } for (long irow = rowmin; irow <= rowmax; irow ++) { double y = 1 - lineSpacing * (irow - rowmin + 0.6); Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); if (my rowLabels && my rowLabels [irow] && my rowLabels [irow] [0]) Graphics_text (graphics, 0.5 - leftMargin, y, my rowLabels [irow]); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_HALF); for (long icol = 1; icol <= my numberOfColumns; icol ++) { wchar_t text [40]; print4 (text, my data [irow] [icol], iformat, 0, precision); Graphics_text (graphics, icol, y, text); } } if (maxTextHeight) { double left = 0.5; if (maxTextWidth > 0.0) left -= maxTextWidth + 2 * leftMargin; Graphics_line (graphics, left, 1, my numberOfColumns + 0.5, 1); } Graphics_unsetInner (graphics); } void TableOfReal_drawAsNumbers_if (TableOfReal me, Graphics graphics, long rowmin, long rowmax, int iformat, int precision, const wchar_t *conditionFormula, Interpreter interpreter) { try { autoMatrix original = TableOfReal_to_Matrix (me); autoMatrix conditions = original.clone (); fixRows (me, & rowmin, & rowmax); Graphics_setInner (graphics); Graphics_setWindow (graphics, 0.5, my numberOfColumns + 0.5, 0, 1); double leftMargin = getLeftMargin (graphics); // not earlier! double lineSpacing = getLineSpacing (graphics); // not earlier! double maxTextWidth = getMaxRowLabelWidth (me, graphics, rowmin, rowmax); double maxTextHeight = getMaxColumnLabelHeight (me, graphics, 1, my numberOfColumns); Matrix_formula (original.peek(), conditionFormula, interpreter, conditions.peek()); therror Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_BOTTOM); for (long icol = 1; icol <= my numberOfColumns; icol ++) { if (my columnLabels && my columnLabels [icol] && my columnLabels [icol] [0]) Graphics_text (graphics, icol, 1, my columnLabels [icol]); } for (long irow = rowmin; irow <= rowmax; irow ++) { double y = 1 - lineSpacing * (irow - rowmin + 0.6); Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); if (my rowLabels && my rowLabels [irow] && my rowLabels [irow] [0]) Graphics_text (graphics, 0.5 - leftMargin, y, my rowLabels [irow]); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_HALF); for (long icol = 1; icol <= my numberOfColumns; icol ++) if (conditions -> z [irow] [icol] != 0.0) { wchar_t text [40]; print4 (text, my data [irow] [icol], iformat, 0, precision); Graphics_text (graphics, icol, y, text); } } if (maxTextHeight) { double left = 0.5; if (maxTextWidth > 0.0) left -= maxTextWidth + 2 * leftMargin; Graphics_line (graphics, left, 1, my numberOfColumns + 0.5, 1); } Graphics_unsetInner (graphics); } catch (MelderError) { Melder_throw (me, ": numbers not drawn."); } } void TableOfReal_drawVerticalLines (TableOfReal me, Graphics graphics, long rowmin, long rowmax) { long colmin = 1, colmax = my numberOfColumns; fixRows (me, & rowmin, & rowmax); Graphics_setInner (graphics); Graphics_setWindow (graphics, colmin - 0.5, colmax + 0.5, 0, 1); double lineSpacing = getLineSpacing (graphics); // not earlier! double maxTextWidth = getMaxRowLabelWidth (me, graphics, rowmin, rowmax); double maxTextHeight = getMaxColumnLabelHeight (me, graphics, 1, my numberOfColumns); if (maxTextWidth > 0.0) colmin -= 1; for (long col = colmin + 1; col <= colmax; col ++) Graphics_line (graphics, col - 0.5, 1 + maxTextHeight, col - 0.5, 1 - lineSpacing * (rowmax - rowmin + 1)); Graphics_unsetInner (graphics); } void TableOfReal_drawLeftAndRightLines (TableOfReal me, Graphics graphics, long rowmin, long rowmax) { long colmin = 1, colmax = my numberOfColumns; fixRows (me, & rowmin, & rowmax); Graphics_setInner (graphics); Graphics_setWindow (graphics, colmin - 0.5, colmax + 0.5, 0, 1); double lineSpacing = getLineSpacing (graphics); double maxTextWidth = getMaxRowLabelWidth (me, graphics, rowmin, rowmax); double maxTextHeight = getMaxColumnLabelHeight (me, graphics, 1, my numberOfColumns); double left = 0.5; if (maxTextWidth > 0.0) left -= maxTextWidth + 2 * lineSpacing; double right = colmax + 0.5; double top = 1 + maxTextHeight; double bottom = 1 - lineSpacing * (rowmax - rowmin + 1); Graphics_line (graphics, left, top, left, bottom); Graphics_line (graphics, right, top, right, bottom); Graphics_unsetInner (graphics); } void TableOfReal_drawHorizontalLines (TableOfReal me, Graphics graphics, long rowmin, long rowmax) { long colmin = 1, colmax = my numberOfColumns; fixRows (me, & rowmin, & rowmax); Graphics_setInner (graphics); Graphics_setWindow (graphics, colmin - 0.5, colmax + 0.5, 0, 1); double lineSpacing = getLineSpacing (graphics); double maxTextWidth = getMaxRowLabelWidth (me, graphics, rowmin, rowmax); double maxTextHeight = getMaxColumnLabelHeight (me, graphics, 1, my numberOfColumns); double left = 0.5; double top = rowmin; if (maxTextWidth > 0.0) left -= maxTextWidth + 2 * lineSpacing; if (maxTextHeight > 0.0) rowmin -= 1; double right = colmax + 0.5; for (long irow = rowmin; irow < rowmax; irow ++) { double y = 1 - lineSpacing * (irow - top + 1); Graphics_line (graphics, left, y, right, y); } Graphics_unsetInner (graphics); } void TableOfReal_drawTopAndBottomLines (TableOfReal me, Graphics graphics, long rowmin, long rowmax) { long colmin = 1, colmax = my numberOfColumns; fixRows (me, & rowmin, & rowmax); Graphics_setInner (graphics); Graphics_setWindow (graphics, colmin - 0.5, colmax + 0.5, 0, 1); double lineSpacing = getLineSpacing (graphics); double maxTextWidth = getMaxRowLabelWidth (me, graphics, rowmin, rowmax); double maxTextHeight = getMaxColumnLabelHeight (me, graphics, 1, my numberOfColumns); double left = 0.5; if (maxTextWidth > 0.0) left -= maxTextWidth + 2 * lineSpacing; double right = colmax + 0.5; double top = 1 + maxTextHeight; double bottom = 1 - lineSpacing * (rowmax - rowmin + 1); Graphics_line (graphics, left, top, right, top); Graphics_line (graphics, left, bottom, right, bottom); Graphics_unsetInner (graphics); } void TableOfReal_drawAsSquares (TableOfReal me, Graphics graphics, long rowmin, long rowmax, long colmin, long colmax, int garnish) { double dx = 1, dy = 1; Graphics_Colour colour = Graphics_inqColour (graphics); fixRows (me, & rowmin, & rowmax); fixColumns (me, & colmin, & colmax); Graphics_setInner (graphics); Graphics_setWindow (graphics, colmin - 0.5, colmax + 0.5, rowmin - 0.5, rowmax + 0.5); double datamax = my data [rowmin] [colmin]; for (long irow = 1; irow <= my numberOfRows; irow ++) for (long icol = 1; icol <= my numberOfColumns; icol ++) if (fabs (my data [irow] [icol]) > datamax) datamax = fabs (my data [irow] [icol]); for (long irow = rowmin; irow <= rowmax; irow ++) { double y = rowmax + rowmin - irow; for (long icol = colmin; icol <= colmax; icol ++) { double x = icol; /* two neighbouring squares should not touch -> 0.95 */ double d = 0.95 * sqrt (fabs (my data [irow] [icol]) / datamax); double x1WC = x - d * dx / 2, x2WC = x + d * dx / 2; double y1WC = y - d * dy / 2, y2WC = y + d * dy / 2; if (my data [irow] [icol] > 0) Graphics_setColour (graphics, Graphics_WHITE); Graphics_fillRectangle (graphics, x1WC, x2WC, y1WC, y2WC); Graphics_setColour (graphics, colour); Graphics_rectangle (graphics, x1WC, x2WC , y1WC, y2WC); } } Graphics_setGrey (graphics, 0.0); Graphics_unsetInner (graphics); if (garnish) { for (long irow = rowmin; irow <= rowmax; irow ++) if (my rowLabels [irow]) Graphics_markLeft (graphics, rowmax + rowmin - irow, 0, 0, 0, my rowLabels [irow]); for (long icol = colmin; icol <= colmax; icol ++) if (my columnLabels [icol]) Graphics_markTop (graphics, icol, 0, 0, 0, my columnLabels [icol]); } } Any TablesOfReal_append (TableOfReal me, TableOfReal thee) { try { if (thy numberOfColumns != my numberOfColumns) Melder_throw (L"Numbers of columns are ", my numberOfColumns, " and ", thy numberOfColumns, " but should be equal."); autoTableOfReal him = static_cast (_Thing_new (my classInfo)); TableOfReal_init (him.peek(), my numberOfRows + thy numberOfRows, my numberOfColumns); therror /* Unsafe: new attributes not initialized. */ for (long icol = 1; icol <= my numberOfColumns; icol ++) { TableOfReal_setColumnLabel (him.peek(), icol, my columnLabels [icol]); } for (long irow = 1; irow <= my numberOfRows; irow ++) { TableOfReal_setRowLabel (him.peek(), irow, my rowLabels [irow]); for (long icol = 1; icol <= my numberOfColumns; icol ++) his data [irow] [icol] = my data [irow] [icol]; } for (long irow = 1; irow <= thy numberOfRows; irow ++) { long hisRow = irow + my numberOfRows; TableOfReal_setRowLabel (him.peek(), hisRow, thy rowLabels [irow]); for (long icol = 1; icol <= my numberOfColumns; icol ++) his data [hisRow] [icol] = thy data [irow] [icol]; } return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal objects not appended."); } } Any TablesOfReal_appendMany (Collection me) { try { if (my size == 0) Melder_throw ("Cannot add zero tables."); TableOfReal thee = static_cast (my item [1]); long totalNumberOfRows = thy numberOfRows; long numberOfColumns = thy numberOfColumns; for (long itab = 2; itab <= my size; itab ++) { thee = static_cast (my item [itab]); totalNumberOfRows += thy numberOfRows; if (thy numberOfColumns != numberOfColumns) Melder_throw ("Numbers of columns do not match."); } autoTableOfReal him = static_cast (_Thing_new (thy classInfo)); TableOfReal_init (him.peek(), totalNumberOfRows, numberOfColumns); therror /* Unsafe: new attributes not initialized. */ for (long icol = 1; icol <= numberOfColumns; icol ++) { TableOfReal_setColumnLabel (him.peek(), icol, thy columnLabels [icol]); } totalNumberOfRows = 0; for (long itab = 1; itab <= my size; itab ++) { thee = static_cast (my item [itab]); for (long irow = 1; irow <= thy numberOfRows; irow ++) { totalNumberOfRows ++; TableOfReal_setRowLabel (him.peek(), totalNumberOfRows, thy rowLabels [irow]); for (long icol = 1; icol <= numberOfColumns; icol ++) his data [totalNumberOfRows] [icol] = thy data [irow] [icol]; } } Melder_assert (totalNumberOfRows == his numberOfRows); return him.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal objects not appended."); } } static void TableOfReal_sort (TableOfReal me, bool useLabels, long column1, long column2) { for (long irow = 1; irow < my numberOfRows; irow ++) for (long jrow = irow + 1; jrow <= my numberOfRows; jrow ++) { wchar_t *tmpString; if (useLabels) { if (my rowLabels [irow] != NULL) { if (my rowLabels [jrow] != NULL) { int compare = wcscmp (my rowLabels [irow], my rowLabels [jrow]); if (compare < 0) continue; if (compare > 0) goto swap; } else goto swap; } else if (my rowLabels [jrow] != NULL) continue; } /* * If we arrive here, the two labels are equal or both NULL (or useLabels is FALSE). */ if (column1 > 0 && column1 <= my numberOfColumns) { if (my data [irow] [column1] < my data [jrow] [column1]) continue; if (my data [irow] [column1] > my data [jrow] [column1]) goto swap; } if (column2 > 0 && column2 <= my numberOfColumns) { if (my data [irow] [column2] < my data [jrow] [column2]) continue; if (my data [irow] [column2] > my data [jrow] [column2]) goto swap; } /* * If we arrive here, everything is equal. */ continue; swap: tmpString = my rowLabels [irow]; my rowLabels [irow] = my rowLabels [jrow]; my rowLabels [jrow] = tmpString; for (long icol = 1; icol <= my numberOfColumns; icol ++) { double tmpValue = my data [irow] [icol]; my data [irow] [icol] = my data [jrow] [icol]; my data [jrow] [icol] = tmpValue; } } } void TableOfReal_sortByLabel (TableOfReal me, long column1, long column2) { TableOfReal_sort (me, true, column1, column2); } void TableOfReal_sortByColumn (TableOfReal me, long column1, long column2) { TableOfReal_sort (me, false, column1, column2); } TableOfReal Table_to_TableOfReal (Table me, long labelColumn) { try { if (labelColumn < 1 || labelColumn > my numberOfColumns) labelColumn = 0; autoTableOfReal thee = TableOfReal_create (my rows -> size, labelColumn ? my numberOfColumns - 1 : my numberOfColumns); for (long icol = 1; icol <= my numberOfColumns; icol ++) { Table_numericize_Assert (me, icol); } if (labelColumn) { for (long icol = 1; icol < labelColumn; icol ++) { TableOfReal_setColumnLabel (thee.peek(), icol, my columnHeaders [icol]. label); } for (long icol = labelColumn + 1; icol <= my numberOfColumns; icol ++) { TableOfReal_setColumnLabel (thee.peek(), icol - 1, my columnHeaders [icol]. label); } for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); wchar_t *string = row -> cells [labelColumn]. string; TableOfReal_setRowLabel (thee.peek(), irow, string ? string : L""); for (long icol = 1; icol < labelColumn; icol ++) { thy data [irow] [icol] = row -> cells [icol]. number; // Optimization. //thy data [irow] [icol] = Table_getNumericValue_Assert (me, irow, icol); } for (long icol = labelColumn + 1; icol <= my numberOfColumns; icol ++) { thy data [irow] [icol - 1] = row -> cells [icol]. number; // Optimization. //thy data [irow] [icol - 1] = Table_getNumericValue_Assert (me, irow, icol); } } } else { for (long icol = 1; icol <= my numberOfColumns; icol ++) { TableOfReal_setColumnLabel (thee.peek(), icol, my columnHeaders [icol]. label); } for (long irow = 1; irow <= my rows -> size; irow ++) { TableRow row = static_cast (my rows -> item [irow]); for (long icol = 1; icol <= my numberOfColumns; icol ++) { thy data [irow] [icol] = row -> cells [icol]. number; // Optimization. //thy data [irow] [icol] = Table_getNumericValue_Assert (me, irow, icol); } } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to TableOfReal."); } } Table TableOfReal_to_Table (TableOfReal me, const wchar_t *labelOfFirstColumn) { try { autoTable thee = Table_createWithoutColumnNames (my numberOfRows, my numberOfColumns + 1); Table_setColumnLabel (thee.peek(), 1, labelOfFirstColumn); for (long icol = 1; icol <= my numberOfColumns; icol ++) { wchar_t *columnLabel = my columnLabels [icol]; thy columnHeaders [icol + 1]. label = Melder_wcsdup (columnLabel && columnLabel [0] ? columnLabel : L"?"); } for (long irow = 1; irow <= thy rows -> size; irow ++) { wchar_t *stringValue = my rowLabels [irow]; TableRow row = static_cast (thy rows -> item [irow]); row -> cells [1]. string = Melder_wcsdup (stringValue && stringValue [0] ? stringValue : L"?"); for (long icol = 1; icol <= my numberOfColumns; icol ++) { double numericValue = my data [irow] [icol]; row -> cells [icol + 1]. string = Melder_wcsdup (Melder_double (numericValue)); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Table."); } } void TableOfReal_writeToHeaderlessSpreadsheetFile (TableOfReal me, MelderFile file) { try { autoMelderString buffer; MelderString_copy (& buffer, L"rowLabel"); therror for (long icol = 1; icol <= my numberOfColumns; icol ++) { MelderString_appendCharacter (& buffer, '\t'); therror wchar_t *s = my columnLabels [icol]; MelderString_append (& buffer, s != NULL && s [0] != '\0' ? s : L"?"); therror } MelderString_appendCharacter (& buffer, '\n'); therror for (long irow = 1; irow <= my numberOfRows; irow ++) { wchar_t *s = my rowLabels [irow]; MelderString_append (& buffer, s != NULL && s [0] != '\0' ? s : L"?"); therror for (long icol = 1; icol <= my numberOfColumns; icol ++) { MelderString_appendCharacter (& buffer, '\t'); therror double x = my data [irow] [icol]; MelderString_append (& buffer, Melder_double (x)); therror } MelderString_appendCharacter (& buffer, '\n'); therror } MelderFile_writeText (file, buffer.string); therror } catch (MelderError) { Melder_throw (me, ": not saved to tab-separated file."); } } TableOfReal TableOfReal_readFromHeaderlessSpreadsheetFile (MelderFile file) { try { autostring string = MelderFile_readText (file); long nrow, ncol, nelements; /* * Count columns. */ ncol = 0; wchar_t *p = & string [0]; for (;;) { wchar_t kar = *p++; if (kar == '\n' || kar == '\0') break; if (kar == ' ' || kar == '\t') continue; ncol ++; do { kar = *p++; } while (kar != ' ' && kar != '\t' && kar != '\n' && kar != '\0'); if (kar == '\n' || kar == '\0') break; } ncol --; if (ncol < 1) Melder_throw ("No columns."); /* * Count elements. */ p = & string [0]; nelements = 0; for (;;) { wchar_t kar = *p++; if (kar == '\0') break; if (kar == ' ' || kar == '\t' || kar == '\n') continue; nelements ++; do { kar = *p++; } while (kar != ' ' && kar != '\t' && kar != '\n' && kar != '\0'); if (kar == '\0') break; } /* * Check if all columns are complete. */ if (nelements == 0 || nelements % (ncol + 1) != 0) Melder_throw ("The number of elements (", nelements, ") is not a multiple of the number of columns plus 1 (", ncol + 1, ")."); /* * Create empty table. */ nrow = nelements / (ncol + 1) - 1; autoTableOfReal me = TableOfReal_create (nrow, ncol); /* * Read elements. */ p = & string [0]; while (*p == ' ' || *p == '\t') { Melder_assert (*p != '\0'); p ++; } while (*p != ' ' && *p != '\t') { Melder_assert (*p != '\0'); p ++; } // ignore the header of the zeroth column ("rowLabel" perhaps) for (long icol = 1; icol <= ncol; icol ++) { while (*p == ' ' || *p == '\t') { Melder_assert (*p != '\0'); p ++; } static MelderString buffer = { 0 }; MelderString_empty (& buffer); while (*p != ' ' && *p != '\t' && *p != '\n') { MelderString_appendCharacter (& buffer, *p); therror p ++; } TableOfReal_setColumnLabel (me.peek(), icol, buffer.string); MelderString_empty (& buffer); } for (long irow = 1; irow <= nrow; irow ++) { while (*p == ' ' || *p == '\t' || *p == '\n') { Melder_assert (*p != '\0'); p ++; } static MelderString buffer = { 0 }; MelderString_empty (& buffer); while (*p != ' ' && *p != '\t') { MelderString_appendCharacter (& buffer, *p); therror p ++; } TableOfReal_setRowLabel (me.peek(), irow, buffer.string); MelderString_empty (& buffer); for (long icol = 1; icol <= ncol; icol ++) { while (*p == ' ' || *p == '\t' || *p == '\n') { Melder_assert (*p != '\0'); p ++; } MelderString_empty (& buffer); while (*p != ' ' && *p != '\t' && *p != '\n' && *p != '\0') { MelderString_appendCharacter (& buffer, *p); therror p ++; } my data [irow] [icol] = Melder_atof (buffer.string); /* If cell contains a string, this will be 0. */ MelderString_empty (& buffer); } } return me.transfer(); } catch (MelderError) { Melder_throw ("TableOfReal: tab-separated file ", file, " not read."); } } /* End of file TableOfReal.cpp */ sources_5316/stat/TableEditor.h0000644000176700017670000000321011621124714015240 0ustar paulpaul#ifndef _TableEditor_h_ #define _TableEditor_h_ /* TableEditor.h * * Copyright (C) 2006-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Editor.h" #include "Table.h" #define kTableEditor_MAXNUM_VISIBLE_COLUMNS 100 Thing_define (TableEditor, Editor) { // new data: public: long topRow, leftColumn, selectedRow, selectedColumn; GuiObject text, drawingArea, horizontalScrollBar, verticalScrollBar; double columnLeft [kTableEditor_MAXNUM_VISIBLE_COLUMNS], columnRight [kTableEditor_MAXNUM_VISIBLE_COLUMNS]; Graphics graphics; // overridden methods: virtual void v_destroy (); virtual void v_createChildren (); virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_dataChanged (); // new methods: virtual void v_draw (); virtual int v_click (double xWC, double yWC, bool shiftKeyPressed); }; TableEditor TableEditor_create (GuiObject parent, const wchar *title, Table table); /* End of file TableEditor.h */ #endif sources_5316/makefiles/0000755000176700017670000000000011747223266013675 5ustar paulpaulsources_5316/makefiles/makefile.defs.mingw640000644000176700017670000000125311747223216017603 0ustar paulpaul# File: makefile.defs.mingw64 # System: MinGW # Paul Boersma, 29 April 2012 CC = /mingw64/bin/gcc -std=gnu99 -isystem /mingw64/include CXX = /mingw64/bin/g++ -isystem /mingw64/include/c++/4.7.0 -isystem /mingw64/include -Wshadow -m64 CFLAGS = -DWINVER=0x0500 -D_WIN32_WINNT=0x0500 -D_WIN32_IE=0x0500 -DUNICODE -Dmain=wingwmain -O2 CXXFLAGS = $(CFLAGS) LINK = /mingw64/bin/g++ EXECUTABLE = Praat.exe LIBS = -L/mingw64/lib -lwinmm -lwsock32 -lcomctl32 -lole32 -lgdi32 /mingw64/lib/GdiPlus.dll -lcomdlg32 -static-libgcc -static-libstdc++ -mwindows AR = /mingw64/bin/ar RANLIB = /mingw64/bin/ranlib WINDRES = /mingw64/bin/windres ICON = praat_win.o MAIN_ICON = main/praat_win.o sources_5316/makefiles/makefile.defs.mingw32c0000644000176700017670000000122611747223176017746 0ustar paulpaul# File: makefile.defs.mingw32c # System: MinGW # Paul Boersma, 29 April 2012 CC = /mingw32/bin/gcc -std=gnu99 -isystem /mingw32/include CXX = /mingw32/bin/g++ -isystem /mingw32/include/c++/4.7.0 -isystem /mingw32/include -Wshadow CFLAGS = -DWINVER=0x0500 -D_WIN32_WINNT=0x0500 -D_WIN32_IE=0x0500 -DUNICODE -DCONSOLE_APPLICATION -O2 CXXFLAGS = $(CFLAGS) LINK = /mingw32/bin/g++ EXECUTABLE = praatcon.exe LIBS = -L/mingw32/lib -lwinmm -lwsock32 -lcomctl32 -lole32 -lgdi32 -lgdiplus -lcomdlg32 -static-libgcc -static-libstdc++ AR = /mingw32/bin/ar RANLIB = /mingw32/bin/ranlib WINDRES = /mingw32/bin/windres ICON = praat_win.o MAIN_ICON = main/praat_win.o sources_5316/makefiles/makefile.defs.mingw320000644000176700017670000000122711747223151017575 0ustar paulpaul# File: makefile.defs.mingw32 # System: MinGW # Paul Boersma, 29 April 2012 CC = /mingw32/bin/gcc -std=gnu99 -isystem /mingw32/include CXX = /mingw32/bin/g++ -isystem /mingw32/include/c++/4.7.0 -isystem /mingw32/include -Wshadow CFLAGS = -DWINVER=0x0500 -D_WIN32_WINNT=0x0500 -D_WIN32_IE=0x0500 -DUNICODE -Dmain=wingwmain -O2 CXXFLAGS = $(CFLAGS) LINK = /mingw32/bin/g++ EXECUTABLE = Praat.exe LIBS = -L/mingw32/lib -lwinmm -lwsock32 -lcomctl32 -lole32 -lgdi32 -lgdiplus -lcomdlg32 -static-libgcc -static-libstdc++ -mwindows AR = /mingw32/bin/ar RANLIB = /mingw32/bin/ranlib WINDRES = /mingw32/bin/windres ICON = praat_win.o MAIN_ICON = main/praat_win.o sources_5316/makefiles/makefile.defs.linux0000644000176700017670000000064011632126513017441 0ustar paulpaul# File: makefile.defs.linux # System: Linux # Paul Boersma, 8 September 2011 CC = gcc -std=gnu99 CXX = g++ CFLAGS = -DUNIX -Dlinux `pkg-config --cflags gtk+-2.0` -Werror=missing-prototypes -Werror=implicit -Wreturn-type -Wunused -Wunused-parameter -Wuninitialized -O CXXFLAGS = $(CFLAGS) -Wshadow LINK = g++ EXECUTABLE = praat LIBS = `pkg-config --libs gtk+-2.0` -lm -lasound RANLIB = ls ICON = MAIN_ICON = sources_5316/makefiles/makefile.defs.mingw64c0000644000176700017670000000125211747223266017752 0ustar paulpaul# File: makefile.defs.mingw64c # System: MinGW # Paul Boersma, 29 April 2012 CC = /mingw64/bin/gcc -std=gnu99 -isystem /mingw64/include CXX = /mingw64/bin/g++ -isystem /mingw64/include/c++/4.7.0 -isystem /mingw64/include -Wshadow -m64 CFLAGS = -DWINVER=0x0500 -D_WIN32_WINNT=0x0500 -D_WIN32_IE=0x0500 -DUNICODE -DCONSOLE_APPLICATION -O2 CXXFLAGS = $(CFLAGS) LINK = /mingw64/bin/g++ EXECUTABLE = praatcon.exe LIBS = -L/mingw64/lib -lwinmm -lwsock32 -lcomctl32 -lole32 -lgdi32 /mingw64/lib/GdiPlus.dll -lcomdlg32 -static-libgcc -static-libstdc++ AR = /mingw64/bin/ar RANLIB = /mingw64/bin/ranlib WINDRES = /mingw64/bin/windres ICON = praat_win.o MAIN_ICON = main/praat_win.o sources_5316/FFNet/0000755000176700017670000000000011756720062012673 5ustar paulpaulsources_5316/FFNet/FFNet_Pattern_Activation.h0000644000176700017670000000361011607516554017670 0ustar paulpaul#ifndef _FFNet_Pattern_Activation_h_ #define _FFNet_Pattern_Activation_h_ /* FFNet_Pattern_Activation.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 1994. djmw 20020712 GPL header. djmw 20030701 Removed non-GPL minimizations. djmw 20110714 Latest modification. */ #include "FFNet.h" #include "Pattern.h" #include "Activation.h" #include "Minimizers.h" #ifdef __cplusplus extern "C" { #endif void FFNet_Pattern_Activation_learnSD (FFNet me, Pattern p, Activation a, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType); /* Steepest Descent minimization */ void FFNet_Pattern_Activation_learnSM (FFNet me, Pattern p, Activation a, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType); double FFNet_Pattern_Activation_getCosts_total (FFNet me, Pattern p, Activation a, int costFunctionType); double FFNet_Pattern_Activation_getCosts_average (FFNet me, Pattern p, Activation a, int costFunctionType); Activation FFNet_Pattern_to_Activation (FFNet me, Pattern p, long layer); /* Calculate the activations at a layer */ /* if (layer<1 || layer > my nLayers) layer = my nLayers; */ #ifdef __cplusplus } #endif #endif /* _FFNet_Pattern_Activation_h_ */ sources_5316/FFNet/FFNet_Activation_Categories.h0000644000176700017670000000260711535130316020331 0ustar paulpaul#ifndef _FFNet_Activation_Categories_h_ #define _FFNet_Activation_Categories_h_ /* FFNet_Activation_Categories.h * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950109 djmw 20020712 GPL header djmw 20110307 Latest modification */ #include "FFNet.h" #include "Activation.h" #include "Categories.h" #ifdef __cplusplus extern "C" { #endif Categories FFNet_Activation_to_Categories (FFNet me, Activation activation, int labeling); /* labeling = 1 : winner-takes-all */ /* labeling = 2 : stochastic */ Activation FFNet_Categories_to_Activation (FFNet me, Categories labels); /* Postcondition: my outputCategories != NULL; */ #ifdef __cplusplus } #endif #endif /* _FFNet_Activation_Categories_h_ */ sources_5316/FFNet/FFNet_Activation_Categories.cpp0000644000176700017670000000646411632231437020675 0ustar paulpaul/* FFNet_Activation_Categories.cpp * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19960322 djmw 20020712 GPL header djmw 20040416 Better error messages djmw 20071014 Melder_error */ #include "FFNet_Activation_Categories.h" static long winnerTakesAll (I, const double activation[]) { iam (FFNet); long pos = 1; double max = activation[1]; for (long i = 2; i <= my nOutputs; i++) { if (activation[i] > max) { max = activation[i]; pos = i; } } return pos; } static long stochastic (I, const double activation[]) { iam (FFNet); long i; double range = 0; for (i = 1; i <= my nOutputs; i++) { range += activation[i]; } double number = NUMrandomUniform (0, range); double lower = 0; for (i = 1; i <= my nOutputs; i++) { lower += activation[i]; if (number < lower) { break; } } return i; } Categories FFNet_Activation_to_Categories (FFNet me, Activation activation, int labeling) { try { Categories categories = (Categories) my outputCategories; long (*labelingFunction) (I, const double act[]); if (my outputCategories == 0) { Melder_throw ("No Categories (has the FFNet been trained yet?)."); } if (my nOutputs != activation->nx) { Melder_throw ("Number of columns and number of outputs must be equal."); } autoCategories thee = Categories_create (); labelingFunction = labeling == 2 ? stochastic : winnerTakesAll; for (long i = 1; i <= activation->ny; i++) { long index = labelingFunction (me, activation -> z[i]); autoSimpleString item = Data_copy ( (SimpleString) categories -> item[index]); Collection_addItem (thee.peek(), item.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Categories created."); } } Activation FFNet_Categories_to_Activation (FFNet me, Categories thee) { try { autoCategories uniq = Categories_selectUniqueItems (thee, 1); if (my outputCategories == 0) { Melder_throw ("The FFNet does not have categories."); } long nl = OrderedOfString_isSubsetOf (uniq.peek(), my outputCategories, 0); if (nl == 0) { Melder_throw ("The Categories do not match the categories of the FFNet."); } autoActivation him = Activation_create (thy size, my nOutputs); for (long i = 1; i <= thy size; i++) { const wchar *citem = OrderedOfString_itemAtIndex_c (thee, i); long pos = OrderedOfString_indexOfItem_c (my outputCategories, citem); if (pos < 1) { Melder_throw ("The FFNet doesn't know the category ", citem, "."); } his z[i][pos] = 1.0; } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no Activation created."); } } /* End of file FFNet_Activation_Categories.c */ sources_5316/FFNet/Makefile0000644000176700017670000000120711634156704014334 0ustar paulpaul# Makefile of the library "FFNet" # David Weenink, 22 February 2010 include ../makefile.defs CPPFLAGS = -I ../num -I ../dwtools -I ../fon -I ../sys -I ../dwsys -I ../stat OBJECTS = FFNet.o \ FFNet_Eigen.o FFNet_Matrix.o FFNet_Pattern.o \ FFNet_Activation_Categories.o FFNet_Pattern_Activation.o \ FFNet_Pattern_Categories.o \ praat_FFNet_init.o manual_FFNet.o .PHONY: all clean all: libFFNet.a clean: $(RM) $(OBJECTS) $(RM) libFFNet.a libFFNet.a: $(OBJECTS) touch libFFNet.a rm libFFNet.a ar cq libFFNet.a $(OBJECTS) $(RANLIB) libFFNet.a $(OBJECTS): *.h ../num/NUM.h ../sys/*.h ../dwtools/*.h ../fon/*.h ../dwsys/*.h ../stat/*.h sources_5316/FFNet/FFNet_Pattern_Categories.h0000644000176700017670000000361211607527747017664 0ustar paulpaul#ifndef _FFNet_Pattern_Categories_h_ #define _FFNet_Pattern_Categories_h_ /* FFNet_Pattern_Categories.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19960821 djmw 20020712 GPL header djmw 20110307 Latest mofification. */ #include "FFNet.h" #include "Pattern.h" #include "Categories.h" #include "Minimizers.h" #ifdef __cplusplus extern "C" { #endif void FFNet_Pattern_Categories_learnSD (FFNet me, Pattern p, Categories c, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType); /* Steepest descent */ void FFNet_Pattern_Categories_learnSM (FFNet me, Pattern p, Categories c, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType); /* Conj. Gradient vdSmagt */ double FFNet_Pattern_Categories_getCosts_total (FFNet me, Pattern p, Categories c, int costFunctionType); double FFNet_Pattern_Categories_getCosts_average (FFNet me, Pattern p, Categories c, int costFunctionType); Categories FFNet_Pattern_to_Categories (FFNet me, Pattern p, int labeling); /* classify the Pattern */ /* labeling = 1 : winner-takes-all */ /* labeling = 2 : stochastic */ /* Preconditions: I have labels */ #ifdef __cplusplus } #endif #endif /* _FFNet_Pattern_Categories_h_ */ sources_5316/FFNet/praat_FFNet_init.cpp0000644000176700017670000007041611652051730016555 0ustar paulpaul/* praat_FFNet_init.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020408 GPL djmw 20020408 added FFNet_help djmw 20030701 Removed non-GPL minimizations djmw 20040526 Removed bug in FFNet_drawCostHistory interface. djmw 20041123 Latest modification djmw 20061218 Changed to Melder_information format. djmw 20080902 Melder_error<1...> djmw 20071011 REQUIRE requires L"". djmw 20071024 Use MelderString_append in FFNet_createNameFromTopology djmw 20100511 FFNet query outputs */ #include #include "praat.h" #include "Discriminant.h" #include "PCA.h" #include "Minimizers.h" #include "FFNet_Eigen.h" #include "FFNet_Matrix.h" #include "FFNet_Pattern.h" #include "FFNet_Activation_Categories.h" #include "FFNet_Pattern_Activation.h" #include "FFNet_Pattern_Categories.h" /* Routines to be removed sometime in the future: 20040422, 2.4.04: FFNet_drawWeightsToLayer use FFNet_drawWeights 20040422, 2.4.04: FFNet_weightsToMatrix use FFNet_extractWeights */ #undef iam #define iam iam_LOOP static wchar_t const *QUERY_BUTTON = L"Query -"; static wchar_t const *DRAW_BUTTON = L"Draw -"; static wchar_t const *MODIFY_BUTTON = L"Modify -"; static wchar_t const *EXTRACT_BUTTON = L"Extract -"; /**************** New FFNet ***************************/ static void FFNet_create_addCommonFields_inputOutput (void *dia) { NATURAL (L"Number of inputs", L"4") NATURAL (L"Number of outputs", L"3") } static void FFNet_create_checkCommonFields_inputOutput (void *dia, long *numberOfInputs, long *numberOfOutputs) { *numberOfInputs = GET_INTEGER (L"Number of inputs"); *numberOfOutputs = GET_INTEGER (L"Number of outputs"); } static void FFNet_create_addCommonFields_hidden (void *dia) { INTEGER (L"Number of units in hidden layer 1", L"0") INTEGER (L"Number of units in hidden layer 2", L"0") } static void FFNet_create_checkCommonFields_hidden (void *dia, long *numberOfHidden1, long *numberOfHidden2) { *numberOfHidden1 = GET_INTEGER (L"Number of units in hidden layer 1"); *numberOfHidden2 = GET_INTEGER (L"Number of units in hidden layer 2"); if (*numberOfHidden1 < 0 || *numberOfHidden2 < 0) { Melder_throw ("The number of units in a hidden layer must be geater equal zero"); } } static void FFNet_create_addCommonFields (void *dia) { FFNet_create_addCommonFields_inputOutput (dia); FFNet_create_addCommonFields_hidden (dia); } static void FFNet_create_checkCommonFields (void *dia, long *numberOfInputs, long *numberOfOutputs, long *numberOfHidden1, long *numberOfHidden2) { FFNet_create_checkCommonFields_inputOutput (dia, numberOfInputs, numberOfOutputs); FFNet_create_checkCommonFields_hidden (dia, numberOfHidden1, numberOfHidden2); } FORM (FFNet_create, L"Create FFNet", L"Create FFNet...") WORD (L"Name", L"4-3") FFNet_create_addCommonFields (dia); OK DO long numberOfInputs, numberOfOutputs, numberOfHidden1, numberOfHidden2; FFNet_create_checkCommonFields (dia, &numberOfInputs, &numberOfOutputs, &numberOfHidden1, &numberOfHidden2); autoFFNet thee = FFNet_create (numberOfInputs, numberOfHidden1, numberOfHidden2, numberOfOutputs, 0); praat_new (thee.transfer(), GET_STRING (L"Name")); END FORM (FFNet_create_linearOutputs, L"Create FFNet", L"Create FFNet (linear outputs)...") WORD (L"Name", L"4-3L") FFNet_create_addCommonFields (dia); OK DO long numberOfInputs, numberOfOutputs, numberOfHidden1, numberOfHidden2; FFNet_create_checkCommonFields (dia, &numberOfInputs, &numberOfOutputs, &numberOfHidden1, &numberOfHidden2); autoFFNet thee = FFNet_create (numberOfInputs, numberOfHidden1, numberOfHidden2, numberOfOutputs, 1); praat_new (thee.transfer(), GET_STRING (L"Name")); END FORM (FFNet_createIrisExample, L"Create iris example", L"Create iris example...") LABEL (L"", L"For the feedforward neural net we need to know the:") FFNet_create_addCommonFields_hidden (dia); OK DO long numberOfHidden1, numberOfHidden2; FFNet_create_checkCommonFields_hidden (dia, &numberOfHidden1, &numberOfHidden2); praat_new (FFNet_createIrisExample (numberOfHidden1, numberOfHidden2), 0); END DIRECT (FFNet_getNumberOfInputs) LOOP { iam (FFNet); Melder_information (Melder_integer (my nUnitsInLayer[0]), L" units"); } END DIRECT (FFNet_getNumberOfOutputs) LOOP { iam (FFNet); Melder_information (Melder_integer (my nUnitsInLayer[my nLayers]), L" units"); } END FORM (FFNet_getNumberOfHiddenUnits, L"FFNet: Get number of hidden units", L"FFNet: Get number of hidden units...") NATURAL (L"Hidden layer number", L"1") OK DO LOOP { iam (FFNet); long layerNumber = GET_INTEGER (L"Hidden layer number"); long numberOfUnits = 0; if (layerNumber > 0 && layerNumber <= my nLayers - 1) { numberOfUnits = my nUnitsInLayer[layerNumber]; } Melder_information (Melder_integer (numberOfUnits), L" units"); } END FORM (FFNet_getCategoryOfOutputUnit, L"FFNet: Get category of output unit", L"") NATURAL (L"Output unit", L"1") OK DO LOOP { iam (FFNet); Categories c = (Categories) my outputCategories; long unit = GET_INTEGER (L"Output unit"); if (unit > c -> size) { Melder_throw (L"Output unit cannot be larger than ", c -> size, L"."); } SimpleString ss = (SimpleString) c -> item[unit]; Melder_information (ss -> string); } END FORM (FFNet_getOutputUnitOfCategory, L"FFNet: Get output unit of category", L"") SENTENCE (L"Category", L"u") OK DO LOOP { iam (FFNet); Categories c = my outputCategories; wchar_t *category = GET_STRING (L"Category"); long index = 0; for (long i = 1; i <= c -> size; i++) { SimpleString s = (SimpleString) c -> item[i]; if (Melder_wcsequ (s -> string, category)) { index = i; break; } } Melder_information (Melder_integer (index)); } END FORM (FFNet_getBias, L"FFNet: Get bias", 0) NATURAL (L"Layer", L"1") NATURAL (L"Unit", L"1") OK DO LOOP { iam (FFNet); long layer = GET_INTEGER (L"Layer"); long unit = GET_INTEGER (L"Unit"); double bias = FFNet_getBias (me, layer, unit); Melder_information (Melder_double (bias), L"(bias for unit ", Melder_integer (unit), L"in layer ", Melder_integer (layer), L")."); } END FORM (FFNet_setBias, L"FFNet: Set bias", 0) NATURAL (L"Layer", L"1") NATURAL (L"Unit", L"1") REAL (L"Value", L"0.0") OK DO LOOP { iam (FFNet); FFNet_setBias (me, GET_INTEGER (L"Layer"), GET_INTEGER (L"Unit"), GET_REAL (L"Value")); } END FORM (FFNet_getWeight, L"FFNet: Get weight", 0) NATURAL (L"Layer", L"1") NATURAL (L"Unit", L"1") NATURAL (L"Unit from", L"1") OK DO LOOP { iam (FFNet); long layer = GET_INTEGER (L"Layer"); long unit = GET_INTEGER (L"Unit"); long unitf = GET_INTEGER (L"Unit from"); double w = FFNet_getWeight (me, layer, unit, unitf); Melder_information (Melder_double (w), L"(weight between unit ", Melder_integer (unit), L" in layer ", Melder_integer (layer), L", and unit ", Melder_integer (unitf), L"in layer ", Melder_integer (layer - 1)); } END FORM (FFNet_setWeight, L"FFNet: Set weight", 0) NATURAL (L"Layer", L"1") NATURAL (L"Unit", L"1") NATURAL (L"Unit (from)", L"1") REAL (L"Value", L"0.0") OK DO LOOP { iam (FFNet); long layer = GET_INTEGER (L"Layer"); long unit = GET_INTEGER (L"Unit"); long unitf = GET_INTEGER (L"Unit (from)"); FFNet_setWeight (me, layer, unit, unitf, GET_REAL (L"Value")); } END FORM (FFNet_getNumberOfHiddenWeights, L"FFNet: Get number of hidden weights", L"FFNet: Get number of hidden weights...") NATURAL (L"Hidden layer number", L"1") OK DO LOOP { iam (FFNet); long layerNumber = GET_INTEGER (L"Hidden layer number"); long numberOfWeights = 0; if (layerNumber > 0 && layerNumber <= my nLayers - 1) { numberOfWeights = my nUnitsInLayer[layerNumber] * (my nUnitsInLayer[layerNumber - 1] + 1); } Melder_information (Melder_integer (numberOfWeights), L" weights (including biases)"); } END DIRECT (FFNet_getNumberOfOutputWeights) LOOP { iam (FFNet); Melder_information (Melder_integer (my nUnitsInLayer[my nLayers] * (my nUnitsInLayer[my nLayers - 1] + 1)), L" weights"); } END /**************** New Pattern ***************************/ FORM (Pattern_create, L"Create Pattern", 0) WORD (L"Name", L"1x1") NATURAL (L"Dimension of a pattern", L"1") NATURAL (L"Number of patterns", L"1") OK DO praat_new (Pattern_create (GET_INTEGER (L"Number of patterns"), GET_INTEGER (L"Dimension of a pattern")), GET_STRING (L"Name")); END /**************** New Categories ***************************/ FORM (Categories_create, L"Create Categories", L"") WORD (L"Name", L"empty") OK DO praat_new (Categories_create (), GET_STRING (L"Name")); END DIRECT (FFNet_help) Melder_help (L"Feedforward neural networks"); END DIRECT (FFNet_getMinimum) LOOP { iam (FFNet); Melder_information (Melder_double (FFNet_getMinimum (me))); } END FORM (FFNet_reset, L"FFNet: Reset", L"FFNet: Reset...") LABEL (L"", L"Warning: this command destroys all previous learning.") LABEL (L"", L"New weights will be randomly chosen from the interval [-range, +range].") POSITIVE (L"Range", L"0.1") OK DO LOOP { iam (FFNet); FFNet_reset (me, GET_REAL (L"Range")); praat_dataChanged (OBJECT); } END FORM (FFNet_selectBiasesInLayer, L"FFNet: Select biases", L"FFNet: Select biases...") LABEL (L"", L"WARNING: This command induces very specific behaviour ") LABEL (L"", L"during a following learning phase.") NATURAL (L"Layer number", L"1") OK DO LOOP { iam (FFNet); FFNet_selectBiasesInLayer (me, GET_INTEGER (L"Layer number")); praat_dataChanged (OBJECT); } END DIRECT (FFNet_selectAllWeights) LOOP { iam (FFNet); FFNet_selectAllWeights (me); praat_dataChanged (me); } END DIRECT (FFNet_drawTopology) autoPraatPicture picture; LOOP { iam (FFNet); FFNet_drawTopology (me, GRAPHICS); } END FORM (FFNet_drawWeightsToLayer, L"FFNet: Draw weights to layer", 0) LABEL (L"", L"Warning: Disapproved. Use \"Draw weights..\" instead.") NATURAL (L"Layer number", L"1") RADIO (L"Scale", 1) RADIOBUTTON (L"by maximum of all weights to layer") RADIOBUTTON (L"by maximum weight from 'from-unit'") RADIOBUTTON (L"by maximum weight to 'to-unit'") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (FFNet); FFNet_drawWeightsToLayer (me, GRAPHICS, GET_INTEGER (L"Layer number"), GET_INTEGER (L"Scale"), GET_INTEGER (L"Garnish")); } END FORM (FFNet_drawWeights, L"FFNet: Draw weights", L"FFNet: Draw weights...") NATURAL (L"Layer number", L"1") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (FFNet); FFNet_drawWeights (me, GRAPHICS, GET_INTEGER (L"Layer number"), GET_INTEGER (L"Garnish")); } END FORM (FFNet_drawCostHistory, L"FFNet: Draw cost history", L"FFNet: Draw cost history...") INTEGER (L"left Iteration_range", L"0") INTEGER (L"right Iteration_range", L"0") REAL (L"left Cost_range", L"0.0") REAL (L"right Cost_range", L"0.0") BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (FFNet); FFNet_drawCostHistory (me, GRAPHICS, GET_INTEGER (L"left Iteration_range"), GET_INTEGER (L"right Iteration_range"), GET_REAL (L"left Cost_range"), GET_REAL (L"right Cost_range"), GET_INTEGER (L"Garnish")); } END FORM (FFNet_extractWeights, L"FFNet: Extract weights", L"FFNet: Extract weights...") NATURAL (L"Layer number", L"1") OK DO LOOP { iam (FFNet); praat_new (FFNet_extractWeights (me, GET_INTEGER (L"Layer number")), 0); } END FORM (FFNet_weightsToMatrix, L"FFNet: Weights to Matrix ", 0) LABEL (L"", L"Warning: Use \"Extract weights..\" instead.") NATURAL (L"Layer number", L"1") OK DO LOOP { iam (FFNet); praat_new (FFNet_weightsToMatrix (me, GET_INTEGER (L"Layer number"), 0), my name); } END /******************* FFNet && Activation *************************************/ FORM (FFNet_Activation_to_Categories, L"FFNet & Activation: To Categories", 0) RADIO (L"Kind of labeling", 1) RADIOBUTTON (L"Winner-takes-all") RADIOBUTTON (L"Stochastic") OK DO FFNet me = FIRST (FFNet); Activation thee = FIRST (Activation); praat_new (FFNet_Activation_to_Categories (me, thee, GET_INTEGER (L"Kind of labeling")), my name, L"_", thy name); END /******************* FFNet && Eigen ******************************************/ FORM (FFNet_Eigen_drawIntersection, L"FFnet & Eigen: Draw intersection", 0) INTEGER (L"X-component", L"1") INTEGER (L"Y-component", L"2") REAL (L"xmin", L"0.0") REAL (L"xmax", L"0.0") REAL (L"ymin", L"0.0") REAL (L"ymax", L"0.0") OK DO FFNet me = FIRST (FFNet); Eigen thee = FIRST (Eigen); autoPraatPicture picture; long pcx = GET_INTEGER (L"X-component"); long pcy = GET_INTEGER (L"Y-component"); REQUIRE (pcx != 0 && pcy != 0, L"X and Y component must differ from 0.") FFNet_Eigen_drawIntersection (me, thee, GRAPHICS, pcx, pcy, GET_REAL (L"xmin"), GET_REAL (L"xmax"), GET_REAL (L"ymin"), GET_REAL (L"ymax")); END FORM (FFNet_PCA_drawDecisionPlaneInEigenspace, L"FFNet & PCA: Draw decision plane", L"") NATURAL (L"Unit number", L"1") NATURAL (L"Layer number", L"1") NATURAL (L"Horizontal eigenvector number", L"1") NATURAL (L"Vertical eigenvector number", L"2") REAL (L"left Horizontal range", L"0.0") REAL (L"right Horizontal range", L"0.0") REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0") OK DO autoPraatPicture picture; FFNet me = FIRST (FFNet); PCA thee = FIRST (PCA); FFNet_Eigen_drawDecisionPlaneInEigenspace (me, thee, GRAPHICS, GET_INTEGER (L"Unit number"), GET_INTEGER (L"Layer number"), GET_INTEGER (L"Horizontal eigenvector number"), GET_INTEGER (L"Vertical eigenvector number"), GET_REAL (L"left Horizontal range"), GET_REAL (L"right Horizontal range"), GET_REAL (L"left Vertical range"), GET_REAL (L"right Vertical range")); END /************************* FFNet && Categories **********************************/ DIRECT (FFNet_Categories_to_Activation) FFNet me = FIRST (FFNet); Categories thee = FIRST (Categories); praat_new (FFNet_Categories_to_Activation (me, thee), my name); END /************************* FFNet && Matrix **********************************/ FORM (FFNet_weightsFromMatrix, L"Replace weights by values from Matrix", 0) NATURAL (L"Layer", L"1") OK DO FFNet me = FIRST (FFNet); Matrix thee = FIRST (Matrix); praat_new (FFNet_weightsFromMatrix (me, thee, GET_INTEGER (L"Layer")), my name); END /************************* FFNet && Pattern **********************************/ FORM (FFNet_Pattern_drawActivation, L"Draw an activation", 0) NATURAL (L"Pattern (row) number", L"1"); OK DO autoPraatPicture picture; FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); FFNet_Pattern_drawActivation (me, thee, GRAPHICS, GET_INTEGER (L"Pattern")); END FORM (FFNet_Pattern_to_Activation, L"To activations in layer", 0) NATURAL (L"Layer", L"1") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); praat_new (FFNet_Pattern_to_Activation (me, thee, GET_INTEGER (L"Layer")), my name, L"_", thy name); END DIRECT (hint_FFNet_and_Pattern_classify) Melder_information (L"You can use the FFNet as a classifier by selecting a\n" "FFNet and a Pattern together and choosing \"To Categories...\"."); END DIRECT (hint_FFNet_and_Pattern_and_Categories_learn) Melder_information (L"You can teach a FFNet to classify by selecting a\n" "FFNet, a Pattern and a Categories together and choosing \"Learn...\"."); END FORM (FFNet_Pattern_to_Categories, L"FFNet & Pattern: To Categories", L"FFNet & Pattern: To Categories...") RADIO (L"Determine output category as", 1) RADIOBUTTON (L"Winner-takes-all") RADIOBUTTON (L"Stochastic") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); praat_new (FFNet_Pattern_to_Categories (me, thee, GET_INTEGER (L"Determine output category as")), my name, L"_", thy name); END /*********** FFNet Pattern Activation **********************************/ FORM (FFNet_Pattern_Activation_getCosts_total, L"FFNet & Pattern & Activation: Get total costs", L"FFNet & Pattern & Activation: Get total costs...") RADIO (L"Cost function", 1) RADIOBUTTON (L"Minimum-squared-error") RADIOBUTTON (L"Minimum-cross-entropy") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); Activation him = FIRST (Activation); Melder_information (Melder_double (FFNet_Pattern_Activation_getCosts_total (me, thee, him, GET_INTEGER (L"Cost function")))); END FORM (FFNet_Pattern_Activation_getCosts_average, L"FFNet & Pattern & Activation: Get average costs", L"FFNet & Pattern & Activation: Get average costs...") RADIO (L"Cost function", 1) RADIOBUTTON (L"Minimum-squared-error") RADIOBUTTON (L"Minimum-cross-entropy") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); Activation him = FIRST (Activation); Melder_information (Melder_double (FFNet_Pattern_Activation_getCosts_average (me, thee, him, GET_INTEGER (L"Cost function")))); END FORM (FFNet_Pattern_Activation_learnSD, L"FFNet & Pattern & Activation: Learn slow", 0) NATURAL (L"Maximum number of epochs", L"100") POSITIVE (L"Tolerance of minimizer", L"1e-7") LABEL (L"Specifics", L"Specific for this minimization") POSITIVE (L"Learning rate", L"0.1") REAL (L"Momentum", L"0.9") RADIO (L"Cost function", 1) RADIOBUTTON (L"Minimum-squared-error") RADIOBUTTON (L"Minimum-cross-entropy") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); Activation him = FIRST (Activation); struct structSteepestDescentMinimizer_parameters p; p.eta = GET_REAL (L"Learning rate"); p.momentum = GET_REAL (L"Momentum"); return FFNet_Pattern_Activation_learnSD (me, thee, him, GET_INTEGER (L"Maximum number of epochs"), GET_REAL (L"Tolerance of minimizer"), & p, GET_INTEGER (L"Cost function")); END FORM (FFNet_Pattern_Activation_learnSM, L"FFNet & Pattern & Activation: Learn", 0) NATURAL (L"Maximum number of epochs", L"100") POSITIVE (L"Tolerance of minimizer", L"1e-7") RADIO (L"Cost function", 1) RADIOBUTTON (L"Minimum-squared-error") RADIOBUTTON (L"Minimum-cross-entropy") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); Activation him = FIRST (Activation); return FFNet_Pattern_Activation_learnSM (me, thee, him, GET_INTEGER (L"Maximum number of epochs"), GET_REAL (L"Tolerance of minimizer"), NULL, GET_INTEGER (L"Cost function")); END /*********** FFNet Pattern Categories **********************************/ FORM (FFNet_Pattern_Categories_getCosts_total, L"FFNet & Pattern & Categories: Get total costs", L"FFNet & Pattern & Categories: Get total costs...") RADIO (L"Cost function", 1) RADIOBUTTON (L"Minimum-squared-error") RADIOBUTTON (L"Minimum-cross-entropy") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); Categories him = FIRST (Categories); Melder_information (Melder_double (FFNet_Pattern_Categories_getCosts_total (me, thee, him, GET_INTEGER (L"Cost function")))); END FORM (FFNet_Pattern_Categories_getCosts_average, L"FFNet & Pattern & Categories: Get average costs", L"FFNet & Pattern & Categories: Get average costs...") RADIO (L"Cost function", 1) RADIOBUTTON (L"Minimum-squared-error") RADIOBUTTON (L"Minimum-cross-entropy") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); Categories him = FIRST (Categories); Melder_information (Melder_double (FFNet_Pattern_Categories_getCosts_average (me, thee, him, GET_INTEGER (L"Cost function")))); END FORM (Pattern_Categories_to_FFNet, L"Pattern & Categories: To FFNet", L"Pattern & Categories: To FFNet...") INTEGER (L"Number of units in hidden layer 1", L"0") INTEGER (L"Number of units in hidden layer 2", L"0") OK DO Pattern me = FIRST (Pattern); Categories thee = FIRST (Categories); long nHidden1 = GET_INTEGER (L"Number of units in hidden layer 1"); long nHidden2 = GET_INTEGER (L"Number of units in hidden layer 2"); if (nHidden1 < 1) { nHidden1 = 0; } if (nHidden2 < 1) { nHidden2 = 0; } autoCategories uniq = Categories_selectUniqueItems (thee, 1); long numberOfOutputs = uniq -> size; if (numberOfOutputs < 1) Melder_throw ("There are not enough categories in the Categories.\n" "Please try again with more categories in the Categories."); autoFFNet ffnet = FFNet_create (my nx, nHidden1, nHidden2, numberOfOutputs, 0); FFNet_setOutputCategories (ffnet.peek(), uniq.peek()); autostring ffnetName = FFNet_createNameFromTopology (ffnet.peek()); praat_new (ffnet.transfer(), ffnetName.peek()); END FORM (FFNet_Pattern_Categories_learnSM, L"FFNet & Pattern & Categories: Learn", L"FFNet & Pattern & Categories: Learn...") NATURAL (L"Maximum number of epochs", L"100") POSITIVE (L"Tolerance of minimizer", L"1e-7") RADIO (L"Cost function", 1) RADIOBUTTON (L"Minimum-squared-error") RADIOBUTTON (L"Minimum-cross-entropy") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); Categories him = FIRST (Categories); FFNet_Pattern_Categories_learnSM (me, thee, him, GET_INTEGER (L"Maximum number of epochs"), GET_REAL (L"Tolerance of minimizer"), NULL, GET_INTEGER (L"Cost function")); END FORM (FFNet_Pattern_Categories_learnSD, L"FFNet & Pattern & Categories: Learn slow", L"FFNet & Pattern & Categories: Learn slow...") NATURAL (L"Maximum number of epochs", L"100") POSITIVE (L"Tolerance of minimizer", L"1e-7") LABEL (L"Specifics", L"Specific for this minimization") POSITIVE (L"Learning rate", L"0.1") REAL (L"Momentum", L"0.9") RADIO (L"Cost function", 1) RADIOBUTTON (L"Minimum-squared-error") RADIOBUTTON (L"Minimum-cross-entropy") OK DO FFNet me = FIRST (FFNet); Pattern thee = FIRST (Pattern); Categories him = FIRST (Categories); struct structSteepestDescentMinimizer_parameters p; p.eta = GET_REAL (L"Learning rate"); p.momentum = GET_REAL (L"Momentum"); FFNet_Pattern_Categories_learnSD (me, thee, him, GET_INTEGER (L"Maximum number of epochs"), GET_REAL (L"Tolerance of minimizer"), &p, GET_INTEGER (L"Cost function")); END void praat_uvafon_FFNet_init (); void praat_uvafon_FFNet_init () { Thing_recognizeClassesByName (classFFNet, NULL); praat_addMenuCommand (L"Objects", L"New", L"Neural nets", 0, 0, 0); praat_addMenuCommand (L"Objects", L"New", L"Feedforward neural networks", 0, 1, DO_FFNet_help); praat_addMenuCommand (L"Objects", L"New", L"-- FFNet --", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Create iris example...", 0, 1, DO_FFNet_createIrisExample); praat_addMenuCommand (L"Objects", L"New", L"Create FFNet...", 0, 1, DO_FFNet_create); praat_addMenuCommand (L"Objects", L"New", L"Advanced", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Create Pattern...", 0, 2, DO_Pattern_create); praat_addMenuCommand (L"Objects", L"New", L"Create Categories...", 0, 2, DO_Categories_create); praat_addMenuCommand (L"Objects", L"New", L"Create FFNet (linear outputs)...", 0, 2, DO_FFNet_create_linearOutputs); praat_addAction1 (classFFNet, 0, L"FFNet help", 0, 0, DO_FFNet_help); praat_addAction1 (classFFNet, 0, DRAW_BUTTON, 0, 0, 0); praat_addAction1 (classFFNet, 0, L"Draw topology", 0, 1, DO_FFNet_drawTopology); praat_addAction1 (classFFNet, 0, L"Draw weights...", 0, 1, DO_FFNet_drawWeights); praat_addAction1 (classFFNet, 0, L"Draw weights to layer...", 0, praat_DEPTH_1 | praat_HIDDEN, DO_FFNet_drawWeightsToLayer); praat_addAction1 (classFFNet, 0, L"Draw cost history...", 0, 1, DO_FFNet_drawCostHistory); praat_addAction1 (classFFNet, 0, QUERY_BUTTON, 0, 0, 0); praat_addAction1 (classFFNet, 0, L"Query structure", 0, 1, 0); praat_addAction1 (classFFNet, 1, L"Get number of outputs", 0, 2, DO_FFNet_getNumberOfOutputs); praat_addAction1 (classFFNet, 1, L"Get number of hidden units...", 0, 2, DO_FFNet_getNumberOfHiddenUnits); praat_addAction1 (classFFNet, 1, L"Get number of inputs", 0, 2, DO_FFNet_getNumberOfInputs); praat_addAction1 (classFFNet, 1, L"Get number of hidden weights...", 0, 2, DO_FFNet_getNumberOfHiddenWeights); praat_addAction1 (classFFNet, 1, L"Get number of output weights", 0, 2, DO_FFNet_getNumberOfOutputWeights); praat_addAction1 (classFFNet, 1, L"Get category of output unit...", 0, 2, DO_FFNet_getCategoryOfOutputUnit); praat_addAction1 (classFFNet, 1, L"Get output unit of category...", 0, 2, DO_FFNet_getOutputUnitOfCategory); praat_addAction1 (classFFNet, 0, L"-- FFNet weights --", 0, 1, 0); praat_addAction1 (classFFNet, 1, L"Get bias...", 0, 1, DO_FFNet_getBias); praat_addAction1 (classFFNet, 1, L"Get weight...", 0, 1, DO_FFNet_getWeight); praat_addAction1 (classFFNet, 1, L"Get minimum", 0, 1, DO_FFNet_getMinimum); praat_addAction1 (classFFNet, 0, MODIFY_BUTTON, 0, 0, 0); praat_addAction1 (classFFNet, 1, L"Set bias...", 0, 1, DO_FFNet_setBias); praat_addAction1 (classFFNet, 1, L"Set weight...", 0, 1, DO_FFNet_setWeight); praat_addAction1 (classFFNet, 1, L"Reset...", 0, 1, DO_FFNet_reset); praat_addAction1 (classFFNet, 0, L"Select biases...", 0, 1, DO_FFNet_selectBiasesInLayer); praat_addAction1 (classFFNet, 0, L"Select all weights", 0, 1, DO_FFNet_selectAllWeights); praat_addAction1 (classFFNet, 0, EXTRACT_BUTTON, 0, 0, 0); praat_addAction1 (classFFNet, 0, L"Extract weights...", 0, 1, DO_FFNet_extractWeights); praat_addAction1 (classFFNet, 0, L"Weights to Matrix...", 0, praat_DEPTH_1 | praat_HIDDEN, DO_FFNet_weightsToMatrix); praat_addAction1 (classFFNet, 0, L"& Pattern: Classify?", 0, 0, DO_hint_FFNet_and_Pattern_classify); praat_addAction1 (classFFNet, 0, L"& Pattern & Categories: Learn?", 0, 0, DO_hint_FFNet_and_Pattern_and_Categories_learn); praat_addAction2 (classFFNet, 1, classActivation, 1, L"Analyse", 0, 0, 0); praat_addAction2 (classFFNet, 1, classActivation, 1, L"To Categories...", 0, 0, DO_FFNet_Activation_to_Categories); praat_addAction2 (classFFNet, 1, classEigen, 1, L"Draw", 0, 0, 0); praat_addAction2 (classFFNet, 1, classEigen, 1, L"Draw hyperplane intersections", 0, 0, DO_FFNet_Eigen_drawIntersection); praat_addAction2 (classFFNet, 1, classCategories, 1, L"Analyse", 0, 0, 0); praat_addAction2 (classFFNet, 1, classCategories, 1, L"To Activation", 0, 0, DO_FFNet_Categories_to_Activation); praat_addAction2 (classFFNet, 1, classMatrix, 1, L"Modify", 0, 0, 0); praat_addAction2 (classFFNet, 1, classMatrix, 1, L"Weights from Matrix...", 0, 0, DO_FFNet_weightsFromMatrix); praat_addAction2 (classFFNet, 1, classPattern, 1, L"Draw", 0, 0, 0); praat_addAction2 (classFFNet, 1, classPattern, 1, L"Draw activation...", 0, 0, DO_FFNet_Pattern_drawActivation); praat_addAction2 (classFFNet, 1, classPattern, 1, L"Analyse", 0, 0, 0); praat_addAction2 (classFFNet, 1, classPattern, 1, L"To Categories...", 0, 0, DO_FFNet_Pattern_to_Categories); praat_addAction2 (classFFNet, 1, classPattern, 1, L"To Activation...", 0, 0, DO_FFNet_Pattern_to_Activation); praat_addAction2 (classFFNet, 1, classPCA, 1, L"Draw decision plane...", 0, 0, DO_FFNet_PCA_drawDecisionPlaneInEigenspace); praat_addAction2 (classPattern, 1, classCategories, 1, L"To FFNet...", 0, 0, DO_Pattern_Categories_to_FFNet); praat_addAction3 (classFFNet, 1, classPattern, 1, classActivation, 1, L"Get total costs...", 0, 0, DO_FFNet_Pattern_Activation_getCosts_total); praat_addAction3 (classFFNet, 1, classPattern, 1, classActivation, 1, L"Get average costs...", 0, 0, DO_FFNet_Pattern_Activation_getCosts_average); praat_addAction3 (classFFNet, 1, classPattern, 1, classActivation, 1, L"Learn", 0, 0, 0); praat_addAction3 (classFFNet, 1, classPattern, 1, classActivation, 1, L"Learn...", 0, 0, DO_FFNet_Pattern_Activation_learnSM); praat_addAction3 (classFFNet, 1, classPattern, 1, classActivation, 1, L"Learn slow...", 0, 0, DO_FFNet_Pattern_Activation_learnSD); praat_addAction3 (classFFNet, 1, classPattern, 1, classCategories, 1, L"Get total costs...", 0, 0, DO_FFNet_Pattern_Categories_getCosts_total); praat_addAction3 (classFFNet, 1, classPattern, 1, classCategories, 1, L"Get average costs...", 0, 0, DO_FFNet_Pattern_Categories_getCosts_average); praat_addAction3 (classFFNet, 1, classPattern, 1, classCategories, 1, L"Learn", 0, 0, 0); praat_addAction3 (classFFNet, 1, classPattern, 1, classCategories, 1, L"Learn...", 0, 0, DO_FFNet_Pattern_Categories_learnSM); praat_addAction3 (classFFNet, 1, classPattern, 1, classCategories, 1, L"Learn slow...", 0, 0, DO_FFNet_Pattern_Categories_learnSD); INCLUDE_MANPAGES (manual_FFNet_init) } /* End of file praat_FFnet_init.cpp */sources_5316/FFNet/manual_FFNet.cpp0000644000176700017670000006302211630135436015675 0ustar paulpaul/* manual_FFNet.c * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020408 GPL */ #include "ManPagesM.h" #include "FFNet.h" static void drawFFNet_345 (Graphics g) { autoFFNet me = FFNet_create (3, 4, 0, 5, 0); FFNet_drawTopology (me.peek(), g); } void manual_FFNet_init (ManPages me); void manual_FFNet_init (ManPages me) { MAN_BEGIN (L"epoch", L"djmw", 20040428) INTRO (L"A term that is often used in the context of machine learning. An epoch is one complete " "presentation of the %%data set to be learned% to a learning machine.") NORMAL (L"Learning machines like @@FFNet|feedforward neural nets@ that use iterative algorithms " "often need many epochs during their learning phase.") NORMAL (L"A @@Discriminant|discriminant classifier@ is also a learning machine. " "However, in contrast with neural nets a discriminant classifier only needs one epoch to learn.") MAN_END MAN_BEGIN (L"Feedforward neural networks", L"djmw", 20040511) INTRO (L"This tutorial describes the use of @FFNet feedforward neural networks in P\\s{RAAT}. ") NORMAL (L"@@Feedforward neural networks 1. What is a feedforward neural network?|1. What is a feedforward neural network?@") LIST_ITEM (L" @@Feedforward neural networks 1.1. The learning phase|1.1 The learning phase") LIST_ITEM (L" @@Feedforward neural networks 1.2. The classification phase|1.2 The classification phase") NORMAL (L"@@Feedforward neural networks 2. Quick start|2. Quick start@") NORMAL (L"@@Feedforward neural networks 3. FFNet versus discriminant classifier|3. FFNet versus discriminant classifier@") NORMAL (L"@@Feedforward neural networks 4. Command overview|4. Command overview@") MAN_END MAN_BEGIN (L"Feedforward neural networks 1. What is a feedforward neural network?", L"djmw", 20040426) INTRO (L"A feedforward neural network is a biologically inspired classification algorithm. " "It consist of a (possibly large) number of simple neuron-like processing %units, organized in %layers. " "Every unit in a layer is connected with all the units in the previous layer. " "These connections are not all equal, each connection may have a different strength or %weight. " "The weights on these connections encode the knowledge of a network. " "Often the units in a neural network are also called %nodes.") NORMAL (L"Data enters at the inputs and passes through the network, layer by layer, until it arrives at the outputs. " "During normal operation, that is when it acts as a classifier, there is no feedback between layers. " "This is why they are called %%feedforward% neural networks. ") NORMAL (L"In the following figure we see an example of a 2-layered network with, from top to bottom: " "an output layer with 5 units, a %hidden layer with 4 units, respectively. The network has 3 input units.") PICTURE (5, 5, drawFFNet_345) NORMAL (L"The 3 inputs are shown as circles and these do not belong to any layer of the network (although the inputs " "sometimes are considered as a virtual layer with layer number 0). Any layer that is not an output layer is a " "%hidden layer. This network therefore has 1 hidden layer and 1 output layer. The figure also shows all the " "connections between the units in different layers. A layer only connects to the previous layer. ") NORMAL (L"The operation of this network can be divided into two phases:") NORMAL (L"@@Feedforward neural networks 1.1. The learning phase|1. The learning phase") NORMAL (L"@@Feedforward neural networks 1.2. The classification phase|2. The classification phase") MAN_END MAN_BEGIN (L"Feedforward neural networks 1.1. The learning phase", L"djmw", 20040428) INTRO (L"During the learning phase the weights in the FFNet will be modified. " "All weights are modified in such a way that when a pattern is presented, " "the output unit with the correct category, hopefully, will have the largest output value.") ENTRY (L"How does learning take place?") NORMAL (L"The FFNet uses a %supervised learning algorithm: besides the input pattern, " "the neural net also needs to know to what category the pattern belongs. " "Learning proceeds as follows: a pattern is presented at the inputs. " "The pattern will be transformed in its passage through the layers of the network until it " "reaches the output layer. The units in the output layer all belong to a different category. " "The outputs of the network as they are now are compared with the outputs as they ideally would " "have been if this pattern were correctly classified: in the latter case " "the unit with the correct category would have had the largest output value and the " "output values of the other output units would have been very small. " "On the basis of this comparison all the connection weights are modified a little bit to guarantee that, the next time " "this same pattern is presented at the inputs, the value of the output unit that corresponds with the correct category " "is a little bit higher than it is now and that, at the same time, the output values of all the other incorrect outputs are a " "little bit lower than they are now. (The differences between the actual outputs and the idealized outputs " "are propagated back from the top layer to lower layers to be used at these layers to modify connection weights. " "This is why the term %%backpropagation network% is also often used to describe this type of neural network.") NORMAL (L"If you perform the procedure above once for every pattern and category pair in your data " "set you have have performed 1 @epoch of learning.") NORMAL (L"The hope is that eventually, probably after many epochs, " "the neural net will remember these pattern-category pairs. " "You even hope that the neural net when the learning phase has terminated, will be able to %generalize " "and has learned to " "@@FFNet & Pattern: To Categories...|classify@ correctly any unknown pattern presented to it. ") NORMAL (L"Because real-life data many times contains noise as well as partly contradictory information " "these hopes can only be partly fulfilled. ") NORMAL (L"For @@FFNet & Pattern & Categories: Learn...|learning@ you " "need to select 3 different objects together: a FFNet (the %classifier), " "a Pattern (the %inputs) and a Categories (the %%correct outputs%).") ENTRY (L"How long will the learning phase take?") NORMAL (L"In general this question is hard to answer. It depends on the size of the neural network, " "the number of patterns to be learned, the number of epochs, the tolerance of the minimizer " "and the speed of your computer, how much computing time the learning phase may take. ") NORMAL (L"If computing time becomes excessive in your interactive environment then consider using the " "powerful @@Scripting|scripting@ facilities in P\\s{RAAT} to process your learning job as a batch job. ") MAN_END MAN_BEGIN (L"Feedforward neural networks 1.2. The classification phase", L"djmw", 20040428) INTRO (L"In the classification phase the weights of the network are fixed. ") NORMAL (L"A pattern, presented at the inputs, will be transformed from layer to layer until it reaches the output layer. " "Now classification can occur by selecting the category associated with the output unit that has " "the largest output value. " "For classification we only need to select an FFNet and a Pattern together and " "choose @@FFNet & Pattern: To Categories...|To Categories...@. ") NORMAL (L"In contrast to the @@Feedforward neural networks 1.1. The learning phase|learning phase@ classification is very fast.") MAN_END MAN_BEGIN (L"Feedforward neural networks 2. Quick start", L"djmw", 20040426) INTRO (L"You may create the iris example set with the @@Create iris example...@ command " "that you will find under the ##Neural nets# option in the #New menu. " "Three new objects will appear in the @@List of Objects@: a @FFNet, a @Categories and " "a @Pattern.") NORMAL (L"The #Pattern contains the @@iris data set@ in a 150 rows by 4 columns matrix. " "To guarantee that every cell in the Pattern is in the [0,1] interval, all measurement " "values were divided by 10. In the #Categories the three iris species %setosa, " "%versicolor, and %virginica were categorized with the numbers #1, #2 and #3, respectively. " "Because there are 4 data columns in the Pattern and 3 different iris species in the Categories, " "the newly created #FFNet has 4 inputs and 3 outputs. " "If you have entered a positive number in one of the fields in the form, the FFNet will have " "this number of units in a %%hidden layer%. The name of the newly created FFNet " "will reflect its topology. If you did opt for the default, 0 hidden units, the FFNet will be named 4-3.") ENTRY (L"Learning the iris data") NORMAL (L"The first thing you probably might want to do is to let the #FFNet learn the association in " "each pattern-category pair. To do this select all three objects together and choose " "@@FFNet & Pattern & Categories: Learn...|Learn...@. " "A form will appear, asking you to supply some settings for " "the learning algorithm. Learning starts after you have clicked the OK-button. " "Since the example network does not have too many weights that need to be adjusted and " "the learning data set is very small and computers nowadays are very fast, this will only take a " "very short time.") ENTRY (L"Classify") NORMAL (L"Now, if you are curious how well the FFNet has learned the iris data, you may select the " "#FFNet and the #Pattern together and choose @@FFNet & Pattern: To Categories...|To Categories...@. " "A new #Categories appears in the ##List of Objects# with the name %4-3_iris (if %%4-3% was the name of the FFNet and %iris% the name of the Pattern). " "We have two different Categories in the list of objects, the topmost one has the original categories, the other " "the categories as were assigned by the FFNet classifier. The obvious thing to do now is to compare the " "original categories with the assigned categories by making a @@Confusion|confusion table@. " "Select the two #Categories and choose @@Categories: To Confusion|To Confusion@ and a newly " "created @Confusion appears. Pressing the @Info button will show you an info window with, " "among others, the fraction correct. ") NORMAL (L"You might also want to " "@@Feedforward neural networks 3. FFNet versus discriminant classifier|compare the FFNet classifier with a discriminant classifier@.") ENTRY (L"Create other neural net topologies") NORMAL (L"With a #Pattern and a #Categories selected together, you can for example create a new #FFNet of a different topology.") MAN_END MAN_BEGIN (L"Feedforward neural networks 3. FFNet versus discriminant classifier", L"djmw", 20040426) NORMAL (L"You might want to compare the FFNet classifier with a discriminant classifier. " "Unlike the FFNet, a @@Discriminant|discriminant@ classifier does not need any iterative procedure in the " "learning phase and can be used immediately after creation for classification. " "The following three simple steps will give you the confusion matrix based on discriminant analysis:") LIST_ITEM (L"1. Select the Pattern and the Categories together and choose ##To Discriminant#. " "A newly created Discriminant will appear.") LIST_ITEM (L"2. Select the Discriminant and the Pattern together and choose ##To Categories...#. A newly created @Categories will appear.") LIST_ITEM (L"3. Select the two appropriate Categories and choose @@categories: To Confusion|To Confusion@. " "A newly created @Confusion will appear. After pushing the @Info button, the info window will " "show you the fraction correct.") NORMAL (L"See also the @@Discriminant analysis@ tutorial for more information.") MAN_END MAN_BEGIN (L"Feedforward neural networks 4. Command overview", L"djmw", 20040426) INTRO (L"FFNet commands") ENTRY (L"Creation:") LIST_ITEM (L"\\bu @@Pattern & Categories: To FFNet...@") LIST_ITEM (L"\\bu @@Create FFNet...@") ENTRY (L"Learning:") LIST_ITEM (L"\\bu @@FFNet & Pattern & Categories: Learn...@") LIST_ITEM (L"\\bu @@FFNet & Pattern & Categories: Learn slow...@") ENTRY (L"Classification:") LIST_ITEM (L"\\bu @@FFNet & Pattern: To Categories...@") ENTRY (L"Drawing:") LIST_ITEM (L"\\bu @@FFNet: Draw topology@") LIST_ITEM (L"\\bu @@FFNet: Draw weights...@") LIST_ITEM (L"\\bu @@FFNet: Draw cost history...@") ENTRY (L"Queries") LIST_ITEM (L"\\bu @@FFNet & Pattern & Categories: Get total costs...@") LIST_ITEM (L"\\bu @@FFNet & Pattern & Categories: Get average costs...@") LIST_ITEM (L"\\bu @@FFNet & Pattern & Activation: Get total costs...@") LIST_ITEM (L"\\bu @@FFNet & Pattern & Activation: Get average costs...@") ENTRY (L"Analysis:") LIST_ITEM (L"\\bu ##FFNet & Pattern: To Activation...#") ENTRY (L"Modification:") LIST_ITEM (L"\\bu @@FFNet: Reset...@") LIST_ITEM (L"\\bu ##FFNet: Select biases...#") LIST_ITEM (L"\\bu ##FFNet: Select all weights#") MAN_END MAN_BEGIN (L"FFNet", L"djmw", 19961015) INTRO (L"One of the @@types of objects@ in P\\s{RAAT}.") NORMAL (L"A #FFNet models a feedforward neural net. A feedforward " "neural net can %learn associations between its %input and its %output. " "The @@Feedforward neural networks@ tutorial gives you an introduction to feedforward neural nets.") MAN_END MAN_BEGIN (L"FFNet: Draw topology", L"djmw", 19970218) INTRO (L"You can choose this command after selecting 1 or more @FFNet's.") ENTRY (L"Behaviour") NORMAL (L"Draws all units and all connections of a feedforward neural net.") MAN_END MAN_BEGIN (L"FFNet: Draw weights...", L"djmw", 20040422) INTRO (L"Draws the weights in a layer of the selected @FFNet feedforward neural net.") ENTRY (L"Settings") TAG (L"##Layer number") DEFINITION (L"determines the layer.") TAG (L"##Garnish") DEFINITION (L"determines whether additional information is drawn.") ENTRY (L"Behaviour") NORMAL (L"The weights are arranged in a matrix. The columns of this matrix are indexed by the units in the layer, " "while the rows are indexed by the units in the previous layer. There is one extra row for the biases." "The values of the weights are shown as rectangles. The area of a rectangle is proportional " "to the value. Negative values are shown as filled black rectangles.") MAN_END MAN_BEGIN (L"FFNet: Draw cost history...", L"djmw", 19970218) INTRO (L"You can choose this command after selecting 1 or more @FFNet's.") ENTRY (L"Settings") TAG (L"##Iteration range") DEFINITION (L"determines the horizontal range of the plot.") TAG (L"##Cost range") DEFINITION (L"determines the vertical range of the plot.") TAG (L"##Garnish") DEFINITION (L"determines whether a box and axis labels are drawn.") ENTRY (L"Behaviour") NORMAL (L"Draws the history of the cost versus iteration number during previous learning.") MAN_END MAN_BEGIN (L"FFNet: Extract weights...", L"djmw", 20040422) INTRO (L"Extract all the weights, from all the units in the specified layer of the selected " "@FFNet, to a @TableOfReal.") ENTRY (L"Settings") TAG (L"##Layer number") DEFINITION (L"determines the layer.") ENTRY (L"Behaviour") NORMAL (L"The weights will be arranged in the TableOfReal as follows: ") NORMAL (L"The table columns will be indexed by the unit numbers in the selected layer, " "while the rows will be indexed by the unit numbers from the previous layer. " "There will be one extra row to accommodate the bias weights. " "The rows and columns are labelled with layer number and unit number as \"L%i-%j\", where %i is the layer number and " "%j the unit number from that layer. The layer number for the rows is one less than the layer number in the columns. " "The last row is labelled as \"Bias\".") MAN_END MAN_BEGIN (L"FFNet: Get number of outputs", L"djmw", 20040420) INTRO (L"Queries the selected @FFNet for the number of output units in the output layer. ") MAN_END MAN_BEGIN (L"FFNet: Get number of inputs", L"djmw", 20040420) INTRO (L"Queries the selected @FFNet for the number of inputs. ") NORMAL (L"For a network with only one layer, the inputs are connected directly to the output layer. " "In a two-layer network the inputs are connected to a hidden layer.") MAN_END MAN_BEGIN (L"FFNet: Get number of hidden units...", L"djmw", 20040420) INTRO (L"Queries the selected @FFNet for the number of units in a hidden layer.") ENTRY (L"Settings") TAG (L"##Hidden layer number") DEFINITION (L"determines the layer that is queried.") ENTRY (L"Layer numbering") NORMAL (L"The number of hidden layers is always one less than the total number of layers in a FFNet. " "A network with the output units connected to the inputs therefore has only 1 layer, the output layer and " "no hidden layers. ") MAN_END MAN_BEGIN (L"FFNet: Get number of hidden weights...", L"djmw", 20040420) INTRO (L"Queries the selected @FFNet for the number of weights in a hidden layer.") ENTRY (L"Settings") TAG (L"##Hidden layer number") DEFINITION (L"determines the layer that is queried.") MAN_END MAN_BEGIN (L"FFNet: Reset...", L"djmw", 20040420) INTRO (L"You can choose this command after selecting 1 or more @FFNet's.") ENTRY (L"WARNING") NORMAL (L"This command destroys all previous learning.") ENTRY (L"Settings") TAG (L"##Range") DEFINITION (L"determines the upper limit of the [-%range, +%range] interval from " "which new weights will be randomly selected.") ENTRY (L"Behaviour") NORMAL (L"All (selected) weights are reset to random numbers uniformly drawn from the interval [-%range, +%range]. " "This command also clears the cost history.") MAN_END MAN_BEGIN (L"FFNet: Select biases...", L"djmw", 20040422) INTRO (L"Selects only the biases in one particular layer as subject for modification during learning of the @FFNet.") ENTRY (L"Settings") TAG (L"##Layer number") DEFINITION (L"determines the layer whose biases will be modified.") ENTRY (L"Behaviour") NORMAL (L"This command induces very specific behaviour during a following learning phase. " "Instead of all the weights, only the biases in the specified layer will be changed during learning and the " "rest of the weights stay fixed. ") MAN_END #define FFNet_Create_COMMON_HELP_INOUT \ ENTRY (L"Settings")\ TAG (L"##Number of inputs")\ DEFINITION (L"the dimension of the input of the neural net.")\ TAG (L"##Number of outputs (\\>_ 1)#")\ DEFINITION (L"the number of different categories that you want the net to learn.") #define FFNet_Create_COMMON_HELP_HIDDEN \ TAG (L"##Number of units in hidden layer 1#, ##Number of units in hidden layer 2#") \ DEFINITION (L"determine the number of units in the hidden layers. " \ "If you want a neural net with no hidden layers, both numbers have to be 0. "\ "If you want a neural net with only 1 hidden layer then one of these numbers has to differ from 0. ") MAN_BEGIN (L"Create FFNet...", L"djmw", 20040420) INTRO (L"Create a new feedforward neural net of type @FFNet.") FFNet_Create_COMMON_HELP_INOUT FFNet_Create_COMMON_HELP_HIDDEN MAN_END MAN_BEGIN (L"Create FFNet (linear outputs)...", L"djmw", 20040422) INTRO (L"Create a @FFNet feedforward neural network whose output units are linear.") FFNet_Create_COMMON_HELP_INOUT FFNet_Create_COMMON_HELP_HIDDEN MAN_END MAN_BEGIN (L"Create iris example...", L"djmw", 20040423) INTRO (L"A @FFNet feedforward neural net will be created together with two other objects: " "a @Pattern and a @Categories. The Pattern will contain the observations in the @@iris data set@, " "and the Categories will contain the 3 different iris species categorized by numbers.") ENTRY (L"Settings") FFNet_Create_COMMON_HELP_HIDDEN NORMAL (L"For this simple data you can leave both hidden layers empty.") MAN_END MAN_BEGIN (L"iris data set", L"djmw", 19961015) NORMAL (L"A data set with 150 random samples of flowers from the iris species %setosa, " "%versicolor, and %virginica collected by @@Anderson (1935)@. From each species there are 50 observations for " "sepal length, sepal width, petal length, and petal width in cm. This dataset was " "used by @@Fisher (1936)@ in his initiation of the linear-discriminant-function technique.") MAN_END MAN_BEGIN (L"FFNet: Pattern", L"djmw", 19960918) INTRO (L"A @Pattern is a @Matrix in which each row forms one input pattern (vector) for the neural net.") NORMAL (L"The number of columns is the dimensionality of the input. " "The number of rows is the number of patterns.") MAN_END MAN_BEGIN (L"FFNet: Categories", L"djmw", 19960918) INTRO (L"The categories for training a neural net with a @Pattern. ") ENTRY (L"Preconditions") NORMAL (L"The number of categories in a @Categories must equal the number of rows in #Pattern.") MAN_END MAN_BEGIN (L"Activation", L"djmw", 20041118) INTRO (L"A @Matrix whose elements must be >= 0 and <= 1. " "Classification: the response of a particular layer in a neural net to a @Pattern." "Learning: the desired response of the output layer in a neural net to a @Pattern.") MAN_END MAN_BEGIN (L"FFNet: Principal components", L"djmw", 19960918) INTRO (L"When you select @FFNet and @Eigen the decision planes of layer 1 are drawn in the PC-plane.\n") MAN_END MAN_BEGIN (L"FFNet & Pattern: To Categories...", L"djmw", 19960918) INTRO (L"The @FFNet is used as a classifier. Each pattern from the @Pattern will be " "classified into one of the FFNet's categories.") MAN_END MAN_BEGIN (L"Pattern & Categories: To FFNet...", L"djmw", 20040422) INTRO (L"Create a new @FFNet feedforward neural network. " "The number of inputs of the newly created FFNet will be equal to the number of " "columns in the @Pattern and the number of outputs " "will be equal to the number of unique categories in the @Categories.") ENTRY (L"Settings") FFNet_Create_COMMON_HELP_HIDDEN MAN_END MAN_BEGIN (L"FFNet & Pattern & Categories: Learn slow...", L"djmw", 19960918) INTRO (L"To learn an association you have to select a @FFNet, a @Pattern and a @Categories object.") ENTRY (L"Preconditions") LIST_ITEM (L"The number of columns in a #Pattern must equal the number of input units of #FFNet.") ENTRY (L" Algorithm") NORMAL (L"Steepest descent") ENTRY (L"Preconditions") LIST_ITEM (L"The number of rows in a #Pattern must equal the number of categories in a #Categories.") LIST_ITEM (L"The number of unique categories in a #Categories must equal the number of output units in #FFNet.") MAN_END MAN_BEGIN (L"FFNet & Pattern & Categories: Learn...", L"djmw", 20040511) INTRO (L"You can choose this command after selecting one @Pattern, one @Categories and one @FFNet.") ENTRY (L"Settings") TAG (L"##Maximum number of epochs") DEFINITION (L"the maximum number of times that the complete #Pattern dataset will be presented to the neural net.") TAG (L"##Tolerance of minimizer") DEFINITION (L"when the difference in costs between two successive learning cycles is " "smaller than this value, the minimization process will be stopped.") NORMAL (L"##Cost function") LIST_ITEM (L"Minimum-squared-error:") LIST_ITEM (L" %costs = \\su__%allPatterns_ \\su__%allOutputs_ (%o__%k_ - d__%k_)^2, where") LIST_ITEM (L" %o__%k_ : actual output of unit %k") LIST_ITEM (L" %d__%k_ : desired output of unit %k") LIST_ITEM (L"Minimum-cross-entropy:") LIST_ITEM (L" %costs = - \\su__%allPatterns_ \\su__%allOutputs_ (%d__%k_ \\.c ln %o__%k_ + (1-%d__%k_) \\.c ln (1-%o__%k_))") ENTRY (L"Algorithm") NORMAL (L"The minimization procedure is a variant of conjugate gradient minimization, " "see for example @@Press et al. (1992)@, chapter 10, or @@Nocedal & Wright (1999)@, chapter 5.") MAN_END MAN_BEGIN (L"FFNet & Pattern & Categories: Get total costs...", L"djmw", 20041118) INTRO (L"Query the selected @FFNet, @Pattern and @Categories for the total costs.") ENTRY (L"Algorithm") NORMAL (L"All patterns are propagated and the total costs are calculated as is shown in @@FFNet & Pattern & Categories: Learn...@. ") MAN_END MAN_BEGIN (L"FFNet & Pattern & Activation: Get total costs...", L"djmw", 20041118) INTRO (L"Query the selected @FFNet, @Pattern and @Activation for the total costs.") ENTRY (L"Algorithm") NORMAL (L"All patterns are propagated and the total costs are calculated as is shown in @@FFNet & Pattern & Categories: Learn...@. ") MAN_END MAN_BEGIN (L"FFNet & Pattern & Categories: Get average costs...", L"djmw", 20041118) INTRO (L"Query the selected @FFNet, @Pattern and @Categories for the average costs.") ENTRY (L"Algorithm") NORMAL (L"All patterns are propagated and the total costs are calculated as is shown in @@FFNet & Pattern & Categories: Learn...@. " "These total costs are then divided by the number of patterns.") MAN_END MAN_BEGIN (L"FFNet & Pattern & Activation: Get average costs...", L"djmw", 20041118) INTRO (L"Query the selected @FFNet, @Pattern and @Activation for the average costs.") ENTRY (L"Algorithm") NORMAL (L"All patterns are propagated and the total costs are calculated as is shown in @@FFNet & Pattern & Categories: Learn...@. " "These total costs are then divided by the number of patterns.") MAN_END MAN_BEGIN (L"Anderson (1935)", L"djmw", 20040423) NORMAL (L"E. Anderson (1935): \"The irises of the Gasp\\e' peninsula.\" " "%%Bulletin of the American Iris Society% #59: 2\\--5.") MAN_END MAN_BEGIN (L"Fisher (1936)", L"djmw", 19980114) NORMAL (L"R.A. Fisher (1936): \"The use of multiple measurements in taxonomic " "problems.\" %%Annals of Eugenics% #7: 179\\--188.") MAN_END MAN_BEGIN (L"Nocedal & Wright (1999)", L"djmw", 20040511) NORMAL (L"J. Nocedal & S.J. Wright (1999): %%Numerical optimization.% Springer.") MAN_END } /* End of file manual_FFNet.c */ sources_5316/FFNet/FFNet_Pattern_Categories.cpp0000644000176700017670000001131511620744317020203 0ustar paulpaul/* FFNet_Pattern_Categories.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020712 GPL header. djmw 20020910 changes. djmw 20030701 Removed non-GPL minimizations. djmw 20041118 Added FFNet_Pattern_Categories_getCosts. */ #include "FFNet_Activation_Categories.h" #include "FFNet_Pattern_Categories.h" #include "FFNet_Pattern_Activation.h" static void _FFNet_Pattern_Categories_checkDimensions (FFNet me, Pattern p, Categories c) { if (my nInputs != p -> nx) Melder_throw (L"The Pattern and the FFNet do not match.\n" "The number of colums in the Pattern must equal the number of inputs in the FFNet."); if (p -> ny != c -> size) Melder_throw (L"The Pattern and the categories do not match.\n" "The number of rows in the Pattern must equal the number of categories."); if (! _Pattern_checkElements (p)) Melder_throw (L"The elements in the Pattern are not all " "in the interval [0, 1].\nThe input of the neural net can only process values that are between 0 " "and 1.\nYou could use \"Formula...\" to scale the Pattern values first."); } static void _FFNet_Pattern_Categories_learn (FFNet me, Pattern p, Categories c, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType, void (*learn) (FFNet, Pattern, Activation, long, double, Any, int)) { _FFNet_Pattern_Categories_checkDimensions (me, p, c); autoActivation activation = FFNet_Categories_to_Activation (me, c); double min, max; Matrix_getWindowExtrema (p, 0, 0, 0, 0, &min, &max); learn (me, p, activation.peek(), maxNumOfEpochs, tolerance, parameters, costFunctionType); } double FFNet_Pattern_Categories_getCosts_total (FFNet me, Pattern p, Categories c, int costFunctionType) { try { _FFNet_Pattern_Categories_checkDimensions (me, p, c); autoActivation activation = FFNet_Categories_to_Activation (me, c); return FFNet_Pattern_Activation_getCosts_total (me, p, activation.peek(), costFunctionType); } catch (MelderError) { return NUMundefined; } } double FFNet_Pattern_Categories_getCosts_average (FFNet me, Pattern p, Categories c, int costFunctionType) { double costs = FFNet_Pattern_Categories_getCosts_total (me, p, c, costFunctionType); return costs == NUMundefined ? NUMundefined : costs / p -> ny; } void FFNet_Pattern_Categories_learnSM (FFNet me, Pattern p, Categories c, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType) { _FFNet_Pattern_Categories_learn (me, p, c, maxNumOfEpochs, tolerance, parameters, costFunctionType, FFNet_Pattern_Activation_learnSM); } void FFNet_Pattern_Categories_learnSD (FFNet me, Pattern p, Categories c, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType) { _FFNet_Pattern_Categories_learn (me, p, c, maxNumOfEpochs, tolerance, parameters, costFunctionType, FFNet_Pattern_Activation_learnSD); } Categories FFNet_Pattern_to_Categories (FFNet me, Pattern thee, int labeling) { try { if (my outputCategories == 0) { Melder_throw ("The FFNet has no output categories."); } if (my nInputs != thy nx) Melder_throw ("The number of colums in the Pattern (", thy nx, ") must equal the number of inputs in the FFNet (", my nInputs, L")."); if (! _Pattern_checkElements (thee)) Melder_throw ("The elements in the Pattern are not all in the interval [0, 1].\n" "The input of the neural net can only process values that are between 0 and 1.\n" "You could use \"Formula...\" to scale the Pattern values first."); autoCategories him = Categories_create (); for (long k = 1; k <= thy ny; k++) { FFNet_propagate (me, thy z[k], 0); long index = FFNet_getWinningUnit (me, labeling); autoData item = Data_copy ( (Data) my outputCategories -> item[index]); Collection_addItem (him.peek(), item.transfer()); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": no Categories created."); } } /* End of file FFNet_Pattern_Categories.cpp */ sources_5316/FFNet/FFNet_Matrix.h0000644000176700017670000000323711535130316015327 0ustar paulpaul#ifndef _FFNet_Matrix_h_ #define _FFNet_Matrix_h_ /* FFNet_Matrix.h * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950206 djmw 20020712 GPL header djmw 20110307 Latest modification */ #include "Matrix.h" #include "FFNet.h" #ifdef __cplusplus extern "C" { #endif /* The Matrix organization is as follows: */ /* */ /* nx = nUnitsInLayer[layer] */ /* ny = nUnitsInLayer[layer-1]+1 */ /* xmin = 1 xmax = nx */ /* ymin = 1 ymax = ny */ /* dx = dy = 1 */ /* x1 = y1 = 1 */ /* */ Matrix FFNet_weightsToMatrix (FFNet me, long layer, int deltaWeights); /* (delta) weights connected to layer into Matrix */ FFNet FFNet_weightsFromMatrix (FFNet me, Matrix matrix, long layer); /* creates a new FFNet in which the weights that connect to layer are */ /* replaced by the weights in the matrix */ #ifdef __cplusplus } #endif #endif /* _FFNet_Matrix_h_ */ sources_5316/FFNet/FFNet_Pattern_Activation.cpp0000644000176700017670000001632311610034064020211 0ustar paulpaul/* FFNet_Pattern_Activation.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19960826 djmw 20020712 GPL header djmw 20030701 Removed non-GPL minimizations djmw 20040416 More precise error messages. djmw 20041118 Added FFNet_Pattern_Categories_getCosts. */ #include "Graphics.h" #include "FFNet_Pattern_Activation.h" static double func (Data object, const double p[]) { FFNet me = (FFNet) object; Minimizer thee = my minimizer; double fp = 0; for (long j = 1, k = 1; k <= my nWeights; k++) { my dw[k] = 0.0; if (my wSelected[k]) { my w[k] = p[j++]; } } for (long i = 1; i <= my nPatterns; i++) { FFNet_propagate (me, my inputPattern[i], NULL); fp += FFNet_computeError (me, my targetActivation[i]); FFNet_computeDerivative (me); /* derivative (cumulative) */ for (long k = 1; k <= my nWeights; k++) { my dw[k] += my dwi[k]; } } thy funcCalls++; return fp; } static void dfunc_optimized (Data object, const double p[], double dp[]) { FFNet me = (FFNet) object; (void) p; long j = 1; for (long k = 1; k <= my nWeights; k++) { if (my wSelected[k]) { dp[j++] = my dw[k]; } } } static void _FFNet_Pattern_Activation_checkDimensions (FFNet me, Pattern p, Activation a) { if (my nInputs != p -> nx) Melder_throw (L"The Pattern and the FFNet do not match.\n" "The number of colums in the Pattern must equal the number of inputs in the FFNet."); if (my nOutputs != a -> nx) Melder_throw (L"The Activation and the FFNet do not match.\n" "The number of colums in the Activation must equal the number of outputs in the FFNet."); if (p -> ny != a -> ny) Melder_throw (L"The Pattern and the Activation do not match.\n" "The number of rows in the Pattern must equal the number of rows in the Activation."); if (! _Pattern_checkElements (p)) Melder_throw (L"The elements in the Pattern are not all " "in the interval [0, 1].\nThe input of the neural net can only process values that are between 0 " "and 1.\nYou could use a \"Formula...\" to scale the Pattern values first."); if (! _Activation_checkElements (a)) Melder_throw (L"The elements in the Activation are not " "all in the interval [0, 1].\nThe output of the neural net can only process values that are " "between 0 and 1.\nYou could use \"Formula...\" to scale the Activation values first."); } static void _FFNet_Pattern_Activation_learn (FFNet me, Pattern pattern, Activation activation, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType, int reset) { try { _FFNet_Pattern_Activation_checkDimensions (me, pattern, activation); Minimizer_setParameters (my minimizer, parameters); // Link the things to be learned my nPatterns = pattern -> ny; my inputPattern = pattern -> z; my targetActivation = activation -> z; FFNet_setCostFunction (me, costFunctionType); if (reset) { autoNUMvector wbuf (1, my dimension); long k = 1; for (long i = 1; i <= my nWeights; i++) { if (my wSelected[i]) { wbuf[k++] = my w[i]; } } Minimizer_reset (my minimizer, wbuf.peek()); } Minimizer_minimize (my minimizer, maxNumOfEpochs, tolerance, 1); // Unlink my nPatterns = 0; my inputPattern = NULL; my targetActivation = NULL; } catch (MelderError) { my nPatterns = 0; my inputPattern = 0; my targetActivation = 0; } } void FFNet_Pattern_Activation_learnSD (FFNet me, Pattern p, Activation a, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType) { int resetMinimizer = 0; /* Did we choose another minimizer */ if (my minimizer != 0 && ! Thing_member (my minimizer, classSteepestDescentMinimizer)) { forget (my minimizer); resetMinimizer = 1; } /* create the minimizer if it doesn't exist */ if (my minimizer == 0) { resetMinimizer = 1; my minimizer = (Minimizer) SteepestDescentMinimizer_create (my dimension, me, func, dfunc_optimized); } _FFNet_Pattern_Activation_learn (me, p, a, maxNumOfEpochs, tolerance, parameters, costFunctionType, resetMinimizer); } void FFNet_Pattern_Activation_learnSM (FFNet me, Pattern p, Activation a, long maxNumOfEpochs, double tolerance, Any parameters, int costFunctionType) { int resetMinimizer = 0; /* Did we choose another minimizer */ if (my minimizer != 0 && ! Thing_member (my minimizer, classVDSmagtMinimizer)) { forget (my minimizer); resetMinimizer = 1; } /* create the minimizer if it doesn't exist */ if (my minimizer == 0) { resetMinimizer = 1; my minimizer = (Minimizer) VDSmagtMinimizer_create (my dimension, me, func, dfunc_optimized); } _FFNet_Pattern_Activation_learn (me, p, a, maxNumOfEpochs, tolerance, parameters, costFunctionType, resetMinimizer); } double FFNet_Pattern_Activation_getCosts_total (FFNet me, Pattern p, Activation a, int costFunctionType) { try { _FFNet_Pattern_Activation_checkDimensions (me, p, a); FFNet_setCostFunction (me, costFunctionType); double cost = 0; for (long i = 1; i <= p -> ny; i++) { FFNet_propagate (me, p -> z[i], NULL); cost += FFNet_computeError (me, a -> z[i]); } return cost; } catch (MelderError) { return NUMundefined; } } double FFNet_Pattern_Activation_getCosts_average (FFNet me, Pattern p, Activation a, int costFunctionType) { double costs = FFNet_Pattern_Activation_getCosts_total (me, p, a, costFunctionType); return costs == NUMundefined ? NUMundefined : costs / p -> ny; } Activation FFNet_Pattern_to_Activation (FFNet me, Pattern p, long layer) { try { if (layer < 1 || layer > my nLayers) { layer = my nLayers; } if (my nInputs != p -> nx) Melder_throw ("The Pattern and the FFNet do not match. " "The number of colums in the Pattern (", p -> nx, ") must equal the number of inputs " "in the FFNet (", my nInputs, ")."); if (! _Pattern_checkElements (p)) Melder_throw ("The elements in the Activation are not all in the interval [0, 1].\n" "The output units of the neural net can only process values that are between 0 and 1.\n" "You could use \"Formula...\" to scale the Activation values first."); long nPatterns = p -> ny; autoActivation thee = Activation_create (nPatterns, my nUnitsInLayer[layer]); for (long i = 1; i <= nPatterns; i++) { FFNet_propagateToLayer (me, p -> z[i], thy z[i], layer); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Activation created."); } } /* End of file FFNet_Pattern_Activation.cpp */ sources_5316/FFNet/FFNet_def.h0000644000176700017670000000523011627146313014622 0ustar paulpaul/* FFNet_def.h * * Copyright (C) 1994-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19961104 djmw 20020712 GPL header djmw 20060529 Added version number to oo_Collection djmw 20080122 float -> double */ #define ooSTRUCT FFNet oo_DEFINE_CLASS (FFNet, Data) oo_LONG (nLayers) /* number of layers */ oo_LONG_VECTOR_FROM (nUnitsInLayer, 0, nLayers) oo_INT (outputsAreLinear) oo_INT (nonLinearityType) oo_INT (costFunctionType) oo_COLLECTION (Categories, outputCategories, SimpleString, 0) oo_LONG (nWeights) /* number of weights */ oo_DOUBLE_VECTOR (w, nWeights) #if ! oo_READING && ! oo_WRITING && ! oo_COMPARING oo_LONG (nNodes) oo_LONG (nInputs) oo_LONG (nOutputs) oo_LONG (dimension) #if oo_DECLARING double (*nonLinearity) (I, double /* x */, double * /* deriv */); void *nlClosure; double (*costFunction) (I, const double * /* target */); void *cfClosure; #endif #if oo_DECLARING oo_DOUBLE (accumulatedCost) oo_LONG (nPatterns) oo_LONG (currentPattern) double **inputPattern, **targetActivation; #endif #if oo_DECLARING || oo_DESTROYING oo_OBJECT (Minimizer, 0, minimizer) #endif oo_DOUBLE_VECTOR (activity, nNodes) oo_LONG_VECTOR (isbias, nNodes) oo_LONG_VECTOR (nodeFirst, nNodes) oo_LONG_VECTOR (nodeLast, nNodes) oo_LONG_VECTOR (wFirst, nNodes) oo_LONG_VECTOR (wLast, nNodes) oo_DOUBLE_VECTOR (deriv, nNodes) oo_DOUBLE_VECTOR (error, nNodes) oo_LONG_VECTOR (wSelected, nWeights) oo_DOUBLE_VECTOR (dw, nWeights) oo_DOUBLE_VECTOR (dwi, nWeights) #endif #if oo_READING bookkeeping (this); FFNet_setNonLinearity (this, nonLinearityType); FFNet_setCostFunction (this, costFunctionType); #endif #if oo_COPYING thy nonLinearity = nonLinearity; thy nlClosure = nlClosure; thy costFunction = costFunction; thy cfClosure = cfClosure; #endif #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (FFNet) #undef ooSTRUCT /* End of file FFNet_def.h */ sources_5316/FFNet/FFNet_Matrix.cpp0000644000176700017670000000515711627146405015675 0ustar paulpaul/* FFNet_Matrix.cpp * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950206 djmw 20020712 GPL header */ #include "FFNet_Matrix.h" Matrix FFNet_weightsToMatrix (FFNet me, long layer, int deltaWeights) { try { if (layer < 1 || layer > my nLayers) { Melder_throw ("Layer must be > 0 and < ", my nLayers, "."); } autoMatrix thee = Matrix_create ( 0.5, my nUnitsInLayer[layer] + 0.5, my nUnitsInLayer[layer], 1, 1, 0.5, my nUnitsInLayer[layer - 1] + 1 + 0.5, my nUnitsInLayer[layer - 1] + 1, 1, 1); long node = 1; for (long i = 0; i < layer; i++) { node += my nUnitsInLayer[i] + 1; } for (long i = 1; i <= my nUnitsInLayer[layer]; i++, node++) { long k = 1; for (long j = my wFirst[node]; j <= my wLast[node]; j++) { thy z[k++][i] = deltaWeights ? my dwi[j] : my w[j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no Matrix created."); } } FFNet FFNet_weightsFromMatrix (FFNet me, Matrix him, long layer) { try { if (layer < 1 || layer > my nLayers) { Melder_throw ("Layer must be > 0 and < ", my nLayers, "."); } if (my nUnitsInLayer[layer] != his nx) Melder_throw (L"The #columns (", his nx, ") must equal " "#units (", my nUnitsInLayer[layer], ") in layer ", layer, "."); long nunits = my nUnitsInLayer[layer - 1] + 1; if (nunits != his ny) { Melder_throw (" The #rows (", his ny, ") must equal #units (", nunits , ") in layer ", layer - 1, "."); } autoFFNet thee = (FFNet) Data_copy (me); long node = 1; for (long i = 0; i < layer; i++) { node += thy nUnitsInLayer[i] + 1; } for (long i = 1; i <= thy nUnitsInLayer[layer]; i++, node++) { long k = 1; for (long j = thy wFirst[node]; j <= thy wLast[node]; j++, k++) { thy w[j] = his z[k][i]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no FFNet created."); } } /* End of file FFNet_Matrix.cpp */ sources_5316/FFNet/FFNet.cpp0000644000176700017670000006342411631626365014355 0ustar paulpaul/* FFNet.cpp * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020712 GPL header djmw 20040420 Modified FFNet_create and FFNet_init parameters. djmw 20040422 FFNet_drawActivation: nodes with activity > 0.05 had incorrect size. djmw 20040422 FFNet_extractWeights added. djmw 20040425 FFNet_drawTopology fill input units; increase distance from arrow for output labels djmw 20040513 Info changes. djmw 20040526 Adapted FFNet_drawCostHistory. djmw 20050131 Reversed sign of derivative in minimumCrossEntropy. djmw 20060811 Changed %d to %ld in sprintf for longs. djmw 20061212 Changed info to Melder_writeLine format. djmw 20070902 FFNet_createNameFromTopology to wchar_t djmw 20071014 Melder_error djmw 20080121 float -> double djmw 20110304 Thing_new */ #include "FFNet_Matrix.h" #include "Matrix_extensions.h" #include "TableOfReal_extensions.h" #include "Pattern.h" #include "Collection.h" #include "Categories.h" static void bookkeeping (FFNet me); #include "oo_DESTROY.h" #include "FFNet_def.h" #include "oo_COPY.h" #include "FFNet_def.h" #include "oo_EQUAL.h" #include "FFNet_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "FFNet_def.h" #include "oo_WRITE_TEXT.h" #include "FFNet_def.h" #include "oo_WRITE_BINARY.h" #include "FFNet_def.h" #include "oo_READ_TEXT.h" #include "FFNet_def.h" #include "oo_READ_BINARY.h" #include "FFNet_def.h" #include "oo_DESCRIPTION.h" #include "FFNet_def.h" Thing_implement (FFNet, Data, 0); static void FFNet_checkLayerNumber (FFNet me, long layer) { if (layer < 1 || layer > my nLayers) { if (layer == 0) { Melder_throw (L"A Layer number of 0 is not allowed."); } else if (layer < 0) { Melder_throw (L"A negative layer number is not allowed."); } else if (layer > my nLayers) { Melder_throw (L"A layer number of ", layer, " is too big."); } Melder_error_ ("This FFNet has ", layer, " layer", (my nLayers > 1 ? "s\n" : "\n")); if (my nLayers == 1) { Melder_throw (L"Layer number must be equal to 1."); } else if (my nLayers == 2) { Melder_throw (L"Layer number must be equal to 1 or 2."); } else if (my nLayers == 3) { Melder_throw (L"Layer number must be equal to 1, 2 or 3."); } else { Melder_throw (L"Layer number must be in the range 1 to ", my nLayers); } } } wchar_t *FFNet_createNameFromTopology (FFNet me) { MelderString name = { 0 }; MelderString_copy (&name, Melder_integer (my nUnitsInLayer[0])); for (long i = 1; i <= my nLayers; i++) { MelderString_appendCharacter (&name, '-'); MelderString_append (&name, Melder_integer (my nUnitsInLayer[i])); } return name.string; } /****** non-linearities ****************************************************/ static double sigmoid (I, double x, double *deriv) { double act = NUMsigmoid (x); (void) void_me; *deriv = act * (1.0 - act); return act; } /* ******************* cost functions ****************************************/ /* For the errors calculated in the cost functions: if target > activity ==> error > 0 if target < activity ==> error < 0 */ static double minimumSquaredError (I, const double target[]) { iam (FFNet); long k = my nNodes - my nOutputs + 1; double cost = 0.0; for (long i = 1; i <= my nOutputs; i++, k++) { double e = my error[k] = target[i] - my activity[k]; cost += e * e; } return 0.5 * cost; } /* E = - sum (i=1; i=nPatterns; sum (k=1;k=nOutputs; t[k]*ln (o[k]) + (1-t[k])ln (1-o[k]))) */ /* dE/do[k] = -(1-t[k])/ (1-o[k]) + t[k]/o[k] */ /* werkt niet bij (grote?) netten */ static double minimumCrossEntropy (I, const double target[]) { iam (FFNet); long k = my nNodes - my nOutputs + 1; double cost = 0.0; for (long i = 1; i <= my nOutputs; i++, k++) { double t1 = 1.0 - target[i]; double o1 = 1.0 - my activity[k]; cost -= target[i] * log (my activity[k]) + t1 * log (o1); my error[k] = -t1 / o1 + target[i] / my activity[k]; } return cost; } /* *********************************************************************** */ void bookkeeping (FFNet me) { long nWeights = 0; my nNodes = my nUnitsInLayer[0]; for (long i = 1; i <= my nLayers; i++) { my nNodes += my nUnitsInLayer[i] + 1; nWeights += my nUnitsInLayer[i] * (my nUnitsInLayer[i - 1] + 1); } if (my nWeights > 0 && my nWeights != nWeights) { Melder_throw ("Number of weights is incorret."); } my nWeights = nWeights; // The following test is essential because when an FFNet is read from file the w array already exists if (my w == 0) { my w = NUMvector (1, my nWeights); } my activity = NUMvector (1, my nNodes); my isbias = NUMvector (1, my nNodes); my nodeFirst = NUMvector (1, my nNodes); my nodeLast = NUMvector (1, my nNodes); my wFirst = NUMvector (1, my nNodes); my wLast = NUMvector (1, my nNodes); my wSelected = NUMvector (1, my nWeights); my error = NUMvector (1, my nNodes); my deriv = NUMvector (1, my nNodes); my dwi = NUMvector (1, my nWeights); my dw = NUMvector (1, my nWeights); my nInputs = my nUnitsInLayer[0]; my nOutputs = my nUnitsInLayer[my nLayers]; my isbias[my nInputs + 1] = my activity[my nInputs + 1] = 1; long n = my nUnitsInLayer[0] + 2; long firstNodeInPrevious = 1, lastWeightInPrevious = 0; for (long j = 1; j <= my nLayers; j++, n++) { for (long i = 1; i <= my nUnitsInLayer[j]; i++, n++) { my isbias[n] = 0; my nodeFirst[n] = firstNodeInPrevious; my nodeLast[n] = my nodeFirst[n] + my nUnitsInLayer[j - 1]; my wFirst[n] = lastWeightInPrevious + (i - 1) * (my nUnitsInLayer[j - 1] + 1) + 1; my wLast[n] = my wFirst[n] + my nUnitsInLayer[j - 1]; } if (j != my nLayers) { my isbias[n] = my activity[n] = 1; } lastWeightInPrevious = my wLast[n - 1]; firstNodeInPrevious += my nUnitsInLayer[j - 1] + 1; } FFNet_selectAllWeights (me); } void structFFNet :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of layers: ", Melder_integer (nLayers)); MelderInfo_writeLine2 (L"Total number of units: ", Melder_integer (FFNet_getNumberOfUnits (this))); MelderInfo_writeLine4 (L" Number of units in layer ", Melder_integer (nLayers), L" (output): ", Melder_integer (nUnitsInLayer[nLayers])); for (long i = nLayers - 1; i >= 1; i--) { MelderInfo_writeLine4 (L" Number of units in layer ", Melder_integer (i), L" (hidden): ", Melder_integer (nUnitsInLayer[i])); } MelderInfo_writeLine2 (L" Number of units in layer 0 (input): ", Melder_integer (nUnitsInLayer[0])); MelderInfo_writeLine2 (L"Outputs are linear: ", Melder_boolean (outputsAreLinear)); MelderInfo_writeLine5 (L"Number of weights: ", Melder_integer (nWeights), L" (", Melder_integer (FFNet_dimensionOfSearchSpace (this)), L" selected)"); MelderInfo_writeLine2 (L"Number of nodes: ", Melder_integer (nNodes)); } void FFNet_init (FFNet me, long numberOfInputs, long nodesInLayer1, long nodesInLayer2, long numberOfOutputs, int outputsAreLinear) { long numberOfLayers = 3; if (numberOfInputs < 1) { Melder_throw ("Number of inputs must be a natrural number."); } if (numberOfOutputs < 1) { Melder_throw ("Number of outputs must be a natrural number."); } if (nodesInLayer1 < 1) { numberOfLayers--; } if (nodesInLayer2 < 1) { numberOfLayers--; } my nLayers = numberOfLayers; my nUnitsInLayer = NUMvector (0, numberOfLayers); my nUnitsInLayer[numberOfLayers--] = numberOfOutputs; if (nodesInLayer2 > 0) { my nUnitsInLayer[numberOfLayers--] = nodesInLayer2; } if (nodesInLayer1 > 0) { my nUnitsInLayer[numberOfLayers--] = nodesInLayer1; } my nUnitsInLayer[numberOfLayers] = numberOfInputs; Melder_assert (numberOfLayers == 0); my outputsAreLinear = outputsAreLinear; bookkeeping (me); FFNet_setCostFunction (me, FFNet_COST_MSE); FFNet_setNonLinearity (me, FFNet_NONLIN_SIGMOID); FFNet_reset (me, 0.1); } void FFNet_setOutputCategories (FFNet me, Categories thee) { autoCategories uniq = Categories_selectUniqueItems (thee, 1); if (uniq -> size == thy size) { forget (my outputCategories); my outputCategories = uniq.transfer(); } } FFNet FFNet_create (long numberOfInputs, long numberInLayer1, long numberInLayer2, long numberOfOutputs, int outputsAreLinear) { try { autoFFNet me = Thing_new (FFNet); FFNet_init (me.peek(), numberOfInputs, numberInLayer1, numberInLayer2, numberOfOutputs, outputsAreLinear); return me.transfer(); } catch (MelderError) { Melder_throw ("FFNet not created."); } } void FFNet_setNonLinearity (FFNet me, int nonLinearityType) { my nonLinearityType = nonLinearityType; my nonLinearity = sigmoid; my nlClosure = NULL; } void FFNet_setCostFunction (FFNet me, int costType) { my costFunctionType = costType; if (costType == 2) { my costFunction = minimumCrossEntropy; } else { my costFunction = minimumSquaredError; } my cfClosure = NULL; } double FFNet_getBias (FFNet me, long layer, long unit) { try { long node = FFNet_getNodeNumberFromUnitNumber (me, unit, layer); if (node < 1) { Melder_throw ("Not a valid unit / layer combination."); } long bias_unit = my wLast[node]; return my w[bias_unit]; } catch (MelderError) { return NUMundefined; } } void FFNet_setBias (FFNet me, long layer, long unit, double value) { long node = FFNet_getNodeNumberFromUnitNumber (me, unit, layer); if (node < 1) { Melder_throw ("Not a valid unit / layer combination."); } long bias_unit = my wLast[node]; // ??? +1 my w[bias_unit] = value; } void FFNet_setWeight (FFNet me, long layer, long unit, long unit_from, double value) { long node = FFNet_getNodeNumberFromUnitNumber (me, unit, layer); if (node < 1) { Melder_throw ("Not a valid unit / layer combination."); } long nodef = FFNet_getNodeNumberFromUnitNumber (me, unit_from, layer - 1); if (nodef < 1) { Melder_throw ("Not a valid unit / layer combination."); } long w_unit = my wFirst[node] + unit_from - 1; my w[w_unit] = value; } double FFNet_getWeight (FFNet me, long layer, long unit, long unit_from) { long node = FFNet_getNodeNumberFromUnitNumber (me, unit, layer); if (node < 1) { Melder_throw ("Not a valid unit / layer combination."); } long nodef = FFNet_getNodeNumberFromUnitNumber (me, unit_from, layer - 1); if (nodef < 1) { Melder_throw ("Not a valid unit / layer combination."); } long w_unit = my wFirst[node] + unit_from - 1; return my w[w_unit]; } void FFNet_reset (FFNet me, double wrange) { for (long i = 1; i <= my nWeights; i++) if (my wSelected[i]) { my w[i] = NUMrandomUniform (-wrange, wrange); } for (long i = 1; i <= my nNodes; i++) { my activity[i] = (my isbias[i] ? 1.0 : 0.0); } my accumulatedCost = 0.0; forget (my minimizer); } /***** OPERATION: ***********************************************************/ /* step 1 */ void FFNet_propagate (FFNet me, const double input[], double output[]) { // clamp input pattern on the network for (long i = 1; i <= my nUnitsInLayer[0]; i++) { my activity[i] = input[i]; } // on hidden units use activation function long k = 1, nNodes = my outputsAreLinear ? my nNodes - my nOutputs : my nNodes; for (long i = my nUnitsInLayer[0] + 2; i <= nNodes; i++) { if (my isbias[i]) { continue; } double act = 0.0; for (long j = my nodeFirst[i]; j <= my nodeLast[i]; j++, k++) { act += my w[k] * my activity[j]; } my activity[i] = my nonLinearity (me, act, & my deriv[i]); } // on output units use another activation function if (my outputsAreLinear) { for (long i = nNodes + 1; i <= my nNodes; i++) { if (my isbias[i]) { continue; } double act = 0.0; for (long j = my nodeFirst[i]; j <= my nodeLast[i]; j++, k++) { act += my w[k] * my activity[j]; } my activity[i] = act; my deriv[i] = 1.0; } } k = my nNodes - my nOutputs + 1; if (output) for (long i = 1; i <= my nOutputs; i++, k++) { output[i] = my activity[k]; } } double FFNet_computeError (FFNet me, const double target[]) { // compute error at output layer double cost = my costFunction (me, target); for (long i = 1; i <= my nNodes - my nOutputs; i++) { my error[i] = 0.0; } // backpropagation of errors from output to first hidden layer for (long i = my nNodes; i > my nInputs + 1; i--) { if (my isbias[i]) { continue; } my error[i] *= my deriv[i]; if (my nodeFirst[i] > my nInputs + 1) { long k = my wFirst[i]; for (long j = my nodeFirst[i]; j <= my nodeLast[i] - 1; j++, k++) { my error[j] += my error[i] * my w[k]; } } } return cost; } void FFNet_computeDerivative (FFNet me) { long k = 1; for (long i = my nInputs + 2; i <= my nNodes; i++) { if (! my isbias[i]) { for (long j = my nodeFirst[i]; j <= my nodeLast[i]; j++, k++) { my dwi[k] = - my error[i] * my activity[j]; } } } } /******* end operation ******************************************************/ long FFNet_getWinningUnit (FFNet me, int labeling) { long pos = 1, k = my nNodes - my nOutputs; if (labeling == 2) { /* stochastic */ double sum = 0; for (long i = 1; i <= my nOutputs; i++) { sum += my activity[k + i]; } double random = NUMrandomUniform (0, sum); for (pos = my nOutputs; pos >= 2; pos--) if (random > (sum -= my activity[k + pos])) { break; } } else { /* winner-takes-all */ double max = my activity[k + 1]; for (long i = 2; i <= my nOutputs; i++) if (my activity[k + i] > max) { max = my activity[k + i]; pos = i; } } return pos; } void FFNet_propagateToLayer (FFNet me, const double input[], double activity[], long layer) { Melder_assert (activity); long k = 0; FFNet_propagate (me, input, 0); for (long i = 0; i < layer; i++) { k += my nUnitsInLayer[i] + 1; } for (long i = 1; i <= my nUnitsInLayer[layer]; i++) { activity[i] = my activity[k + i]; } } void FFNet_selectAllWeights (FFNet me) { for (long i = 1; i <= my nWeights; i++) { my wSelected[i] = 1; } my dimension = my nWeights; } long FFNet_dimensionOfSearchSpace (FFNet me) { long n = 0; for (long i = 1; i <= my nWeights; i++) { if (my wSelected[i]) { n++; } } return n; } void FFNet_selectBiasesInLayer (FFNet me, long layer) { long node = my nUnitsInLayer[0] + 1; if (layer < 1 || layer > my nLayers) { return; } for (long i = 1; i <= my nWeights; i++) { my wSelected[i] = 0; } for (long i = 1; i < layer; i++) { node += my nUnitsInLayer[i] + 1; } for (long i = node + 1; i <= node + my nUnitsInLayer[layer]; i++) { my wSelected[my wLast[i]] = 1; } my dimension = my nUnitsInLayer[layer]; } void FFNet_weightConnectsUnits (FFNet me, long index, long *fromUnit, long *toUnit, long *layer) { Melder_assert (index > 0 && index <= my nWeights); long i = 1, np = 0, nw = my nUnitsInLayer[1] * (my nInputs + 1); while (index > nw) { i++; nw += (np = my nUnitsInLayer[i] * (my nUnitsInLayer[i - 1] + 1)); } if (i > 1) { index -= nw - np; } *fromUnit = index % (my nUnitsInLayer[i - 1] + 1); *toUnit = (index - 1) / (my nUnitsInLayer[i - 1] + 1) + 1; *layer = i; } long FFNet_getNodeNumberFromUnitNumber (FFNet me, long unit, long layer) { if (layer < 0 || layer > my nLayers || unit > my nUnitsInLayer[layer]) { return -1; } long node = unit; for (long i = 0; i < layer; i++) { node += my nUnitsInLayer[i] + 1; } return node; } void FFNet_nodeToUnitInLayer (FFNet me, long node, long *unit, long *layer) { Melder_assert (node > 0 && node <= my nNodes); long i = 0, nn = my nUnitsInLayer[0] + 1; while (node > nn) { nn += my nUnitsInLayer[++i] + 1; } if (i > 0) { node -= nn - (my nUnitsInLayer[i] + 1); } *unit = node % (my nUnitsInLayer[i] + 1); *layer = i; } long FFNet_getNumberOfWeights (FFNet me) { return my nWeights; } long FFNet_getNumberOfLayers (FFNet me) { return my nLayers; } long FFNet_getNumberOfUnits (FFNet me) { return my nNodes - my nLayers; } long FFNet_getNumberOfHiddenLayers (FFNet me) { return my nLayers - 1; } long FFNet_getNumberOfUnitsInLayer (FFNet me, int layer) { if (layer > my nLayers || layer < 0) { return 0; } return my nUnitsInLayer[layer]; } double FFNet_getMinimum (FFNet me) { return my minimizer ? Minimizer_getMinimum (my minimizer) : NUMundefined; } void FFNet_drawTopology (FFNet me, Graphics g) { long maxNumOfUnits = my nUnitsInLayer[0]; int dxIsFixed = 1; double dy = 1.0 / (my nLayers + 1); for (long i = 1; i <= my nLayers; i++) { if (my nUnitsInLayer[i] > maxNumOfUnits) { maxNumOfUnits = my nUnitsInLayer[i]; } } double dx = 1.0 / maxNumOfUnits; double radius = dx / 10; Graphics_setInner (g); Graphics_setWindow (g, 0.0, 1.0, 0.0, 1.0); for (long i = 0; i <= my nLayers; i++) { double dx2 = dx, x2WC, y2WC = dy / 2 + i * dy; double x2 = (maxNumOfUnits - my nUnitsInLayer[i] + 1) * dx2 / 2; /* draw the units */ if (! dxIsFixed) { dx2 = 1.0 / my nUnitsInLayer[i]; x2 = dx2 / 2; } if (i == 0) { Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_TOP); x2WC = x2; for (long j = 1; j <= my nInputs; j++) { Graphics_arrow (g, x2WC, y2WC - radius - dy / 4, x2WC, y2WC - radius); x2WC += dx2; } } Graphics_setColour (g, Graphics_RED); x2WC = x2; for (long j = 1; j <= my nUnitsInLayer[i]; j++) { Graphics_circle (g, x2WC, y2WC, radius); if (i > 0) { Graphics_fillCircle (g, x2WC, y2WC, radius); } x2WC += dx2; } Graphics_setColour (g, Graphics_BLACK); if (i > 0) { double dx1 = dx; double x1 = (maxNumOfUnits - my nUnitsInLayer[i - 1] + 1) * dx1 / 2; double y1WC = y2WC - dy; if (! dxIsFixed) { dx1 = 1.0 / my nUnitsInLayer[i - 1]; x1 = dx1 / 2; } x2WC = x2; for (long j = 1; j <= my nUnitsInLayer[i]; j++) { double x1WC = x1; for (long k = 1; k <= my nUnitsInLayer[i - 1]; k++) { double xd = x2WC - x1WC; double cosa = xd / sqrt (xd * xd + dy * dy); double sina = dy / sqrt (xd * xd + dy * dy); Graphics_line (g, x1WC + radius * cosa, y1WC + radius * sina, x2WC - radius * cosa, y2WC - radius * sina); x1WC += dx1; } x2WC += dx2; } } if (i == my nLayers) { x2WC = x2; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); for (long j = 1; j <= my nOutputs; j++) { Graphics_arrow (g, x2WC, y2WC + radius, x2WC, y2WC + radius + dy / 4); if (my outputCategories) { Categories_drawItem (my outputCategories, g, j, x2WC, y2WC + radius + dy / 4); } x2WC += dx2; } } } Graphics_unsetInner (g); } void FFNet_drawActivation (FFNet me, Graphics g) { long node = 1, maxNumOfUnits = my nUnitsInLayer[0]; int dxIsFixed = 1; Graphics_Colour colour = Graphics_inqColour (g); double dy = 1.0 / (my nLayers + 1); Graphics_setInner (g); Graphics_setWindow (g, 0.0, 1.0, 0.0, 1.0); for (long i = 1; i <= my nLayers; i++) { if (my nUnitsInLayer[i] > maxNumOfUnits) { maxNumOfUnits = my nUnitsInLayer[i]; } } double dx = 1.0 / maxNumOfUnits; double r1 = dx / 2; /* May touch when neighbouring activities are both 1 (very rare). */ for (long i = 0; i <= my nLayers; i++, node++) { double dx2 = dx, x2WC, y2WC = dy / 2 + i * dy; double x2 = (maxNumOfUnits - my nUnitsInLayer[i] + 1) * dx2 / 2; if (! dxIsFixed) { dx2 = 1.0 / my nUnitsInLayer[i]; x2 = dx2 / 2; } x2WC = x2; for (long j = 1; j <= my nUnitsInLayer[i]; j++, node++) { double activity = my activity[node]; double radius = r1 * (fabs (activity) < 0.05 ? 0.05 : fabs (activity)); /*Graphics_setColour (g, activity < 0 ? Graphics_BLACK : Graphics_RED);*/ Graphics_circle (g, x2WC, y2WC, radius); if (activity < 0) { Graphics_fillCircle (g, x2WC, y2WC, radius); } x2WC += dx2; } } Graphics_setColour (g, colour); Graphics_unsetInner (g); } /* This routine is deprecated since praat-4.2.4 20040422 and will be removed in the future. */ void FFNet_drawWeightsToLayer (FFNet me, Graphics g, int layer, int scaling, int garnish) { if (layer < 1 || layer > my nLayers) { Melder_throw ("Layer must be in [1,", my nLayers, "]."); } autoMatrix weights = FFNet_weightsToMatrix (me, layer, 0); Matrix_scale (weights.peek(), scaling); Matrix_drawAsSquares (weights.peek(), g, 0, 0, 0, 0, 0); if (garnish) { double x1WC, x2WC, y1WC, y2WC; wchar_t text[30]; Graphics_inqWindow (g, & x1WC, & x2WC, & y1WC, & y2WC); swprintf (text, 30, L"Units in layer %ld ->", layer); Graphics_textBottom (g, 0, text); if (layer == 1) { wcscpy (text, L"Input units ->"); } else { swprintf (text, 30, L"Units in layer %ld ->", layer - 1); } Graphics_textLeft (g, 0, text); /* how do I find out the current settings ??? */ Graphics_setTextAlignment (g, Graphics_RIGHT, Graphics_HALF); Graphics_setInner (g); Graphics_text (g, 0.5, weights->ny, L"bias"); Graphics_unsetInner (g); } } void FFNet_drawWeights (FFNet me, Graphics g, long layer, int garnish) { autoTableOfReal thee = FFNet_extractWeights (me, layer); TableOfReal_drawAsSquares (thee.peek(), g, 1, thy numberOfRows, 1, thy numberOfColumns, garnish); } void FFNet_drawCostHistory (FFNet me, Graphics g, long iFrom, long iTo, double costMin, double costMax, int garnish) { if (my minimizer) Minimizer_drawHistory (my minimizer, g, iFrom, iTo, costMin, costMax, 0); if (garnish) { Graphics_drawInnerBox (g); Graphics_textLeft (g, 1, my costFunctionType == FFNet_COST_MSE ? L"Minimum squared error" : L"Minimum cross entropy"); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_textBottom (g, 1, L"Number of epochs"); Graphics_marksBottom (g, 2, 1, 1, 0); } } Collection FFNet_createIrisExample (long numberOfHidden1, long numberOfHidden2) { try { autoCollection c = Collection_create (classData, 3); autoCategories uniq = Categories_sequentialNumbers (3); autoFFNet me = FFNet_create (4, numberOfHidden1, numberOfHidden2, 3, 0); FFNet_setOutputCategories (me.peek(), uniq.peek()); autostring name = FFNet_createNameFromTopology (me.peek()); Thing_setName (me.peek(), name.peek()); Collection_addItem (c.peek(), me.transfer()); autoTableOfReal iris = TableOfReal_createIrisDataset (); // Scale data to interval [0-1] for (long i = 1; i <= 150; i++) { for (long j = 1; j <= 4; j++) { iris -> data[i][j] /= 10.0; } } Pattern thee = 0; Categories him = 0; TableOfReal_to_Pattern_and_Categories (iris.peek(), 0, 0, 0, 0, &thee, &him); autoPattern ap = thee; autoCategories ac = him; Thing_setName (ap.peek(), L"iris"); Thing_setName (ac.peek(), L"iris"); Collection_addItem (c.peek(), ap.transfer()); Collection_addItem (c.peek(), ac.transfer()); return c.transfer(); } catch (MelderError) { Melder_throw ("Iris example not created."); } } TableOfReal FFNet_extractWeights (FFNet me, long layer) { try { FFNet_checkLayerNumber (me, layer); long numberOfUnitsFrom = my nUnitsInLayer[layer - 1] + 1; long numberOfUnitsTo = my nUnitsInLayer[layer]; autoTableOfReal thee = TableOfReal_create (numberOfUnitsFrom, numberOfUnitsTo); wchar_t label[20]; for (long i = 1; i <= numberOfUnitsFrom - 1; i++) { swprintf (label, 20, L"L%ld-%ld", layer - 1, i); TableOfReal_setRowLabel (thee.peek(), i, label); } TableOfReal_setRowLabel (thee.peek(), numberOfUnitsFrom, L"Bias"); for (long i = 1; i <= numberOfUnitsTo; i++) { swprintf (label, 20, L"L%ld-%ld", layer, i); TableOfReal_setColumnLabel (thee.peek(), i, label); } long node = 1; for (long i = 0; i < layer; i++) { node += my nUnitsInLayer[i] + 1; } for (long i = 1; i <= numberOfUnitsTo; i++, node++) { long k = 1; for (long j = my wFirst[node]; j <= my wLast[node]; j++) { thy data[k++][i] = my w[j]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no TableOfReal created."); } } FFNet FFNet_and_TabelOfReal_to_FFNet (FFNet me, TableOfReal him, long layer) { try { FFNet_checkLayerNumber (me, layer); if ( (my nUnitsInLayer[layer] != his numberOfColumns) || (my nUnitsInLayer[layer] == his numberOfColumns && my nUnitsInLayer[layer - 1] + 1 == his numberOfRows)) { long trys[3], rows[3], cols[3], ntry = my nLayers > 3 ? 3 : my nLayers, ok = 0; if (my nLayers > 3) { Melder_throw ("Dimensions don't fit."); } for (long i = 1; i <= ntry; i++) { cols[i] = my nUnitsInLayer[i] == his numberOfColumns; rows[i] = my nUnitsInLayer[i - 1] + 1 == his numberOfRows; trys[i] = rows[i] && cols[i]; if (trys[i]) { ok ++; } } if (! rows[layer]) Melder_throw ("The number of rows in the TableOfReal does not equal \n" "the number of units in the layer that connect to layer ", layer, L"."); else Melder_throw ("The number of columns in the TableOfReal does not equal \n" "the number of units in layer ", layer, L"."); if (ok == 0) { Melder_throw ("Please quit, there is no appropriate layer in the FFNet for this TableOfReal."); } else { if (ok == 1) Melder_throw ("Please try again with layer number ", trys[1] ? trys[1] : (trys[2] ? trys[2] : trys[3]), L"."); else { Melder_throw ("Please try again with one of the other two layer numbers."); } } } autoFFNet thee = Data_copy (me); long node = 1; for (long i = 0; i < layer; i++) { node += thy nUnitsInLayer[i] + 1; } for (long i = 1; i <= thy nUnitsInLayer[layer]; i++, node++) { long k = 1; for (long j = thy wFirst[node]; j <= thy wLast[node]; j++, k++) { thy w[j] = his data[k][i]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no FFNet created."); } } /* End of file FFNet.cpp */ sources_5316/FFNet/FFNet.h0000644000176700017670000002220211627146073014005 0ustar paulpaul#ifndef _FFNet_h_ #define _FFNet_h_ /* FFNet.h * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19970515 djmw 20020712 GPL header. djmw 20031025 Added FFNet_getMinimum. djmw 20040420 FFNet_create and Pattern&Categories: To FFNet changes. djmw 20040422 FFNet_extractWeights added. djmw 20040505 FFNet_getNodeNumberFromUnitNumber added. djmw 20071024 Latest modification. djmw 20080121 float -> double */ #include "Data.h" #include "Categories.h" #include "Minimizers.h" #include "TableOfReal.h" #include "FFNet_def.h" oo_CLASS_CREATE (FFNet, Data); /* Parameters: * long nLayers : the #layers in the net (exclusive the inputs) * nUnitsInLayer : array[0..nLayers] the #units in each layer * nUnitsInLayer[0] : #inputs * nUnitsInLayer[nLayers] :#outputs * nWeights : the total #weights in the net (inclusive bias) * double *w : array[1..nWeights] with the connection strengths * *activity : array[1..nNodes] with activities * outputLabels : labels belonging to the outputs * BOOKKEEPING: * long nNodes : total #nodes: bias modelled as unit with constant activity) * *isbias : array[1..nNodes] set 1 if node is bias else 0 * *nodeFirst : array[1..nNodes] first node connected to this unit * *nodeLast: : array[1..nNodes] last node connected to this unit * *wFirst : array[1..nNodes] first index in *w for this unit * *wLast : array[1..nNodes] last (inclusive the bias) * LEARNING: * int *wSelected : array[1..nWeights] weights selected for minimization * double *deriv : array[1..nNodes] derivative of nonlinearity at node * *error : array[1..nNodes] the error at node * *dw : array[1..nWeights] total derivative for weights * *dwi : array[1..nWeights] derivative per pattern * long dimension : dimension of minimizer space (<= my nWeights) * long nPatterns : the #patterns to be learned * double **inputPattern: matrix[1..nPatterns][1..nInputs] * double **targetActivation: matrix[1..nPatterns][1..nOutputs] * double accumulatedCost : accumulated costs of testing/training with patterns * * A network consists of nLayers layers. Layer numbering is from 0...nLayers. * Layer 0 is the input layer, the highest numbered layer is the output layer * (nLayers <= 4) * Each layer consists of a number of units. The biases of all the units in a layer * are modelled with connections to an extra unit in the lower layer (with constant * activity 1.0). Nodes refers to 'units' + 'bias units'. * The variable 'nNodes' is the total number of nodes (inclusive bias nodes). * E.g. the topology (2,3,4), i.e., 2 inputs, 3 units in the first layer * and 4 units in the second layer (outputs) is modelled * with (2+1)+ (3+1)+ (4) = 11 nodes. * The numbering of the weights is as follows (indices 1..nWeights): * E.g., topology (I,H,O) (I inputs, H hidden units and O output units) * There are a total of H* (I+1) + O* (H+1) weights in this net. * w[1] - w[I] : I (1)->H (1), I (2)->H (1) ... I (I)->H (1) * w[I+1] : bias->H (1) * w[ (I+1)+1] - w[2 (I+1)-1] : I (1)->H (2), I (2)->H (2) ... I (I)->H (2) * w[2 (I+1)] : bias->H (2) * ... * w[ (H-1) (I+1)+1] - w[H (I+1)-1] : I (1)->H (H), I (2)->H (H) ... I (I)->H (H) * w[H (I+1)] : bias->H (H) * M = H (I+1) * w[M+1] - w[M+H] : H (1)->O (1), H (2)->O (1) ... H (H)->O (1) * w[M+H+1] : bias->O (1) * w[M+ (H+1)+1] - w (M+2 (H+1)-1) : H (1)->O (2), H (2)->O (2) ... H (H)->O (2) * w[M+2 (H+1)] : bias->O (1) * ... * w[M+ (O-1)* (H+1)+1] - w[M+O (H+1)-1] : H (1)->O (O), H (2)->O (O) ... H (H)->O (O) * w[m+o (h+1)-1] : bias->O (O) * * Internals: * * A number of auxiliary arrays for efficient calculations have been setup. * For a node k we need to know: * 1. isbias[1..nNodes] : usage: if (isbias[k]) ... * true if node k is a bias node. There are nLayers bias nodes * 2. nodeFirst[1..nNodes] : usage is j=nodeFirst[k]; * j is the first node that is connected to k . * 3. nodeLast[1..nNodes] : usage is j=nodeLast[k] * j is the last node that is connected to k (bias included). * For the calculation of the errors, during learning, in unit k we need to * know which weights from the preceeding layer connect to it. * 4. wFirst[1..nNodes] : usage j=wFirst[k] * w[j] is first weight to node k. * 5. wLast[1..nNodes] : usage j=wLast[k] * w[j] is last weight to node k. */ /* FFNet::copy * copy everything except minimizer, patterns and inputs. */ void FFNet_init (FFNet me, long numberOfInputs, long nodesInLayer1, long nodesInLayer2, long numberOfOutputs, int outputsAreLinear); FFNet FFNet_create (long numberOfInputs, long numberInLayer1, long numberInLayer2, long numberOfOutputs, int outputsAreLinear ); wchar_t * FFNet_createNameFromTopology (FFNet me); /* Create names as -, --, --- for 1, 2 or 3 layer networks. */ #define FFNet_COST_MSE 1 void FFNet_setCostFunction (FFNet me, int type); #define FFNet_NONLIN_SIGMOID 1 void FFNet_setNonLinearity (FFNet me, int type); void FFNet_setOutputCategories (FFNet me, Categories thee); double FFNet_getBias (FFNet me, long layer, long unit); void FFNet_setBias (FFNet me, long layer, long node, double value); void FFNet_setWeight (FFNet me, long later, long node, long node_from, double value); double FFNet_getWeight (FFNet me, long later, long node, long node_from); void FFNet_reset (FFNet me, double wrange); /* reset the neural net: * initialize all (selected) weights and biases with random numbers from the * interval (-wrange, wrange). * forget links with minimizer. */ void FFNet_propagateToLayer (FFNet me, const double input[], double activity[], long layer); /* propagate the input through the net to layer and calculate the activities */ void FFNet_propagate (FFNet me, const double input[], double output[]); /* step (1) feed forward input from "input layer" to "output layer" * if output != NULL the output activity is copied into output. * postcondition: my activities defined */ double FFNet_computeError (FFNet me, const double target[]); /* step (2) calculate error on output nodes w.r.t. desired output */ /* step (3) backpropagate this error to previous nodes */ /* precondition: step (1) */ void FFNet_computeDerivative (FFNet me); /* step (4) compute derivative in my dwi */ /* Precondition: step (3) */ long FFNet_getWinningUnit (FFNet me, int labeling); /* labeling = 1 : winner-takes-all */ /* labeling = 2 : stochastic */ void FFNet_selectAllWeights (FFNet me); void FFNet_selectBiasesInLayer (FFNet me, long layer); long FFNet_dimensionOfSearchSpace (FFNet me); /* count the selected weights */ long FFNet_getNumberOfWeights (FFNet me); /* return my nWeights */ void FFNet_weightConnectsUnits (FFNet me, long index, long *fromUnit, long *toUnit, long *layer); /* * w[index] connects unit fromUnit in "layer-1" with unit toUnit in "layer". * fromUnit returns 0 then w[index] is bias. */ long FFNet_getNodeNumberFromUnitNumber (FFNet me, long unit, long layer); void FFNet_nodeToUnitInLayer (FFNet me, long node, long *unit, long *layer); /* translate node index to unit "unit" in layer "layer" */ long FFNet_getNumberOfLayers (FFNet me); long FFNet_getNumberOfUnits (FFNet me); long FFNet_getNumberOfHiddenLayers (FFNet me); long FFNet_getNumberOfUnitsInLayer (FFNet me, int layer); double FFNet_getMinimum (FFNet me); void FFNet_drawTopology (FFNet me, Graphics g); void FFNet_drawActivation (FFNet me, Graphics g); void FFNet_drawWeightsToLayer (FFNet me, Graphics g, int toLayer, int scaling, int garnish); /* Deprecated: the strengths of the weights that connect to the nodes in later 'layer' */ /* are drawn with boxes. The area of each box corresponds to the strength. */ /* Black boxes have negative strength? */ void FFNet_drawCostHistory (FFNet me, Graphics g, long from_iteration, long to_iteration, double from_cost, double to_cost, int garnish); /* draw cost vs epochs */ Collection FFNet_createIrisExample (long numberOfHidden1, long numberOfHidden2); TableOfReal FFNet_extractWeights (FFNet me, long layer); void FFNet_drawWeights (FFNet me, Graphics g, long layer, int garnish); FFNet FFNet_and_TabelOfReal_to_FFNet (FFNet me, TableOfReal him, long layer); #endif /* _FFNet_h_ */ sources_5316/FFNet/FFNet_Eigen.h0000644000176700017670000000303411535130317015106 0ustar paulpaul#ifndef _FFNet_Eigen_h_ #define _FFNet_Eigen_h_ /* FFNet_Eigen.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19940726 djmw 20110307 Latest modification. */ #include "FFNet.h" #include "Eigen.h" #ifdef __cplusplus extern "C" { #endif void FFNet_Eigen_drawIntersection (FFNet me, Eigen eigen, Graphics g, long pcx, long pcy, double xmin, double xmax, double ymin, double ymax); /* Draw intersections of hyperplanes of units in layer 1 with eigenplane */ /* formed by pcx and pcy. */ /* pcx (pcy) > 0 : negative values left (bottom), positive right (top) */ /* pcx (pcy) < 0 : negative values right (top). */ void FFNet_Eigen_drawDecisionPlaneInEigenspace (FFNet me, thou, Graphics g, long unit, long layer, long pcx, long pcy, double xmin, double xmax, double ymin, double ymax); #ifdef __cplusplus } #endif #endif /* _FFNet_Eigen_h_ */ sources_5316/FFNet/FFNet_Eigen.cpp0000644000176700017670000001317711634154426015461 0ustar paulpaul/* FFNet_Eigen.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020712 GPL header djmw 20071202 Melder_warning */ #include "FFNet_Eigen.h" #include "Graphics.h" #include "NUM2.h" void FFNet_Eigen_drawIntersection (FFNet me, Eigen eigen, Graphics g, long pcx, long pcy, double xmin, double xmax, double ymin, double ymax) { long ix = labs (pcx), iy = labs (pcy); long numberOfEigenvalues = eigen -> numberOfEigenvalues; long dimension = eigen -> dimension; if (ix > numberOfEigenvalues || iy > numberOfEigenvalues || my nInputs != dimension) { return; } Melder_assert (ix > 0 && iy > 0); double x1, x2, y1, y2; if (xmax <= xmin || ymax <= ymin) { Graphics_inqWindow (g, & x1, & x2, & y1, & y2); } if (xmax <= xmin) { xmin = x1; xmax = x2; } if (ymax <= ymin) { ymin = y1; ymax = y2; } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); for (long i = 1; i <= my nUnitsInLayer[1]; i++) { long unitOffset = my nInputs + 1; double c1 = 0.0, c2 = 0.0, bias = my w[ my wLast[unitOffset + i] ]; double x[6], y[6], xs[3], ys[3]; int ns = 0; for (long j = 1; j <= my nInputs; j++) { c1 += my w[ my wFirst[unitOffset + i] + j - 1 ] * eigen->eigenvectors[ix][j]; c2 += my w[ my wFirst[unitOffset + i] + j - 1 ] * eigen->eigenvectors[iy][j]; } x[1] = x[2] = x[5] = xmin; x[3] = x[4] = xmax; y[1] = y[4] = y[5] = ymin; y[2] = y[3] = ymax; for (long j = 1; j <= 4; j++) { double p1 = c1 * x[j ] + c2 * y[j ] + bias; double p2 = c1 * x[j + 1] + c2 * y[j + 1] + bias; double r = fabs (p1) / (fabs (p1) + fabs (p2)); if (p1 *p2 > 0 || r == 0.0) { continue; } if (++ns > 2) { break; } xs[ns] = x[j] + (x[j + 1] - x[j]) * r; ys[ns] = y[j] + (y[j + 1] - y[j]) * r; } if (ns < 2) { Melder_casual ("Intersection for unit %ld outside range", i); } else { Graphics_line (g, xs[1], ys[1], xs[2], ys[2]); } } Graphics_unsetInner (g); } /* Draw the intersection line of the decision hyperplane 'w.e-b' of the weights of unit i from layer j with the plane spanned by eigenvectors pcx and pcy. */ void FFNet_Eigen_drawDecisionPlaneInEigenspace (FFNet me, thou, Graphics g, long unit, long layer, long pcx, long pcy, double xmin, double xmax, double ymin, double ymax) { thouart (Eigen); if (layer < 1 || layer > my nLayers) { return; } if (unit < 1 || unit > my nUnitsInLayer[layer]) { return; } if (pcx > thy numberOfEigenvalues || pcy > thy numberOfEigenvalues) { return; } if (my nUnitsInLayer[layer - 1] != thy dimension) { return; } double x1, x2, y1, y2; Graphics_inqWindow (g, & x1, & x2, & y1, & y2); if (xmax <= xmin) { xmin = x1; xmax = x2; } if (ymax <= ymin) { ymin = y1; ymax = y2; } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); long node = FFNet_getNodeNumberFromUnitNumber (me, unit, layer); if (node < 1) { return; } /* Suppose p1 and p2 are the two points in the eigenplane, spanned by the eigenvectors e1 and e2, where the neural net decision hyperplane intersects these eigenvectors. Their coordinates in the eigenplane will be (x0*e1, 0) and (0,y0*e2). At the same time, the two points are part of the decision hyperplane of the chosen unit. The hyperplane equation is: w.e+bias = 0, where 'w' is the weight vector, 'e' is the input vector and 'b' is the bias. This results in two equations for the unknown x0 and y0: w.(x0*e1)+bias = 0 w.(y0*e2)+bias = 0 This suggests the solution for x0 and y0: x0 = -bias / (w.e1) y0 = -bias / (w.e2) If w.e1 != 0 && w.e2 != 0 p1 = (x0, 0) and p2 = (0, y0) If w.e1 == 0 && w.e2 != 0 The line is parallel to e1 and intersects e2 at y0. If w.e2 == 0 && w.e1 != 0 The line is parallel to e2 and intersects e1 at x0. If w.e1 == 0 && w.e2 == 0 Both planes are parallel, no intersection. */ long iw = my wFirst[node] - 1; double we1 = 0, we2 = 0; for (long i = 1; i <= my nUnitsInLayer[layer - 1]; i++) { we1 += my w[iw + i] * thy eigenvectors[pcx][i]; we2 += my w[iw + i] * thy eigenvectors[pcy][i]; } double bias = my w[my wLast[node]]; x1 = xmin; x2 = xmax; y1 = ymin; y2 = ymax; if (we1 != 0) { x1 = -bias / we1; y1 = 0; } if (we2 != 0) { x2 = 0; y2 = -bias / we2; } if (we1 == 0 && we2 == 0) { Melder_warning (L"We cannot draw the intersection of the neural net decision plane\n" "for unit ", Melder_integer (unit), L" in layer ", Melder_integer (layer), L" with the plane spanned by the eigenvectors because \nboth planes are parallel."); return; } double xi[3], yi[3]; /* Intersections */ double ni = NUMgetIntersectionsWithRectangle (x1, y1, x2, y2, xmin, ymin, xmax, ymax, xi, yi); if (ni == 2) { Graphics_line (g, xi[1], yi[1], xi[2], yi[2]); } else Melder_warning (L"There were no intersections in the drawing area.\n" "Please enlarge the drawing area."); Graphics_unsetInner (g); } /* End of file FFNet_Eigen.cpp */ sources_5316/FFNet/FFNet_Pattern.h0000644000176700017670000000216211535130316015474 0ustar paulpaul#ifndef _FFNet_Pattern_h_ #define _FFNet_Pattern_h_ /* FFNet_Pattern.h * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950113 djmw 20020712 GPL header djmw 20110307 Latest modification */ #include "Pattern.h" #include "FFNet.h" #ifdef __cplusplus extern "C" { #endif void FFNet_Pattern_drawActivation( FFNet me, Pattern pattern, Graphics g, long ipattern ); #ifdef __cplusplus } #endif #endif /* _FFNet_Pattern_h_ */ sources_5316/FFNet/FFNet_Pattern.cpp0000644000176700017670000000212211606610760016030 0ustar paulpaul/* FFNet_Pattern.cpp * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950113 djmw 20020712 GPL header */ #include "FFNet_Pattern.h" void FFNet_Pattern_drawActivation (FFNet me, Pattern pattern, Graphics g, long index) { if (index < 1 || index > pattern->ny) { return; } FFNet_propagate (me, pattern->z[index], NULL); FFNet_drawActivation (me, g); } /* End of file FFNet_Pattern.cpp */ sources_5316/gram/0000755000176700017670000000000011753755326012667 5ustar paulpaulsources_5316/gram/OTGrammar_ex_NPA.cpp0000644000176700017670000000724311613556117016414 0ustar paulpaul/* OTGrammar_ex_NPA.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2007/07/23 constraint plasticity * pb 2007/08/12 wchar * pb 2011/03/29 C++ * pb 2011/07/12 C++ */ #include "OTGrammar.h" OTGrammar OTGrammar_create_NPA_grammar (void) { try { OTGrammarCandidate candidate; OTGrammarTableau tableau; OTGrammarConstraint constraint; autoOTGrammar me = Thing_new (OTGrammar); my constraints = NUMvector (1, my numberOfConstraints = 3); constraint = & my constraints [1]; constraint -> name = Melder_wcsdup (L"*G\\s{ESTURE}"); constraint -> ranking = 102.7; constraint -> plasticity = 1.0; constraint = & my constraints [2]; constraint -> name = Melder_wcsdup (L"*R\\s{EPLACE} (n, m)"); constraint -> ranking = 100.0; constraint -> plasticity = 1.0; constraint = & my constraints [3]; constraint -> name = Melder_wcsdup (L"*R\\s{EPLACE} (t, p)"); constraint -> ranking = 112.0; constraint -> plasticity = 1.0; my tableaus = NUMvector (1, my numberOfTableaus = 2); tableau = & my tableaus [1]; tableau -> input = Melder_wcsdup (L"an+pa"); tableau -> candidates = NUMvector (1, tableau -> numberOfCandidates = 2); candidate = & tableau -> candidates [1]; candidate -> output = Melder_wcsdup (L"anpa"); candidate -> marks = NUMvector (1, candidate -> numberOfConstraints = 3); candidate -> marks [1] = 1; candidate = & tableau -> candidates [2]; candidate -> output = Melder_wcsdup (L"ampa"); candidate -> marks = NUMvector (1, candidate -> numberOfConstraints = 3); candidate -> marks [2] = 1; tableau = & my tableaus [2]; tableau -> input = Melder_wcsdup (L"at+ma"); tableau -> candidates = NUMvector (1, tableau -> numberOfCandidates = 2); candidate = & tableau -> candidates [1]; candidate -> output = Melder_wcsdup (L"atma"); candidate -> marks = NUMvector (1, candidate -> numberOfConstraints = 3); candidate -> marks [1] = 1; candidate = & tableau -> candidates [2]; candidate -> output = Melder_wcsdup (L"apma"); candidate -> marks = NUMvector (1, candidate -> numberOfConstraints = 3); candidate -> marks [3] = 1; OTGrammar_checkIndex (me.peek()); therror OTGrammar_newDisharmonies (me.peek(), 0.0); return me.transfer(); } catch (MelderError) { Melder_throw ("Nasal place assimilation grammar not created."); } } PairDistribution OTGrammar_create_NPA_distribution (void) { try { autoPairDistribution me = PairDistribution_create (); PairDistribution_add (me.peek(), L"at+ma", L"atma", 100); PairDistribution_add (me.peek(), L"at+ma", L"apma", 0); PairDistribution_add (me.peek(), L"an+pa", L"anpa", 20); PairDistribution_add (me.peek(), L"an+pa", L"ampa", 80); return me.transfer(); } catch (MelderError) { Melder_throw ("Nasal place assimilation distribution not created."); } } /* End of file OTGrammar_ex_NPA.cpp */ sources_5316/gram/Makefile0000644000176700017670000000126611704274153014322 0ustar paulpaul# Makefile of the library "gram" # Paul Boersma, 14 January 2012 include ../makefile.defs CPPFLAGS = -I ../num -I ../kar -I ../sys -I ../dwsys -I ../stat -I ../dwtools -I ../fon OBJECTS = Network.o \ OTGrammar.o OTGrammarEditor.o manual_gram.o praat_gram.o OTMulti.o OTMultiEditor.o \ OTGrammar_ex_metrics.o OTGrammar_ex_NoCoda.o OTGrammar_ex_NPA.o OTGrammar_ex_tongueRoot.o .PHONY: all clean all: libgram.a clean: $(RM) $(OBJECTS) $(RM) libgram.a libgram.a: $(OBJECTS) touch libgram.a rm libgram.a ar cq libgram.a $(OBJECTS) $(RANLIB) libgram.a $(OBJECTS): *.h ../num/NUM.h ../kar/*.h ../sys/*.h ../dwsys/*.h ../stat/*.h ../dwtools/*.h ../fon/*.h sources_5316/gram/Network.h0000644000176700017670000000361411731375223014463 0ustar paulpaul#ifndef _Network_h_ #define _Network_h_ /* Network.h * * Copyright (C) 2009-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" #include "Graphics.h" #include "Network_enums.h" #include "Network_def.h" oo_CLASS_CREATE (Network, Data); Network Network_create (double minimumActivity, double maximumActivity, double spreadingRate, double selfExcitation, double minimumWeight, double maximumWeight, double learningRate, double leak, double xmin, double xmax, double ymin, double ymax, long numberOfNodes, long numberOfConnections); Network Network_create_rectangle (double minimumActivity, double maximumActivity, double spreadingRate, double selfExcitation, double minimumWeight, double maximumWeight, double learningRate, double leak, long numberOfRows, long numberOfColumns, bool bottomRowClamped, double initialMinimumWeight, double initialMaximumWeight); Network Network_create_rectangle_vertical (double minimumActivity, double maximumActivity, double spreadingRate, double selfExcitation, double minimumWeight, double maximumWeight, double learningRate, double leak, long numberOfRows, long numberOfColumns, bool bottomRowClamped, double initialMinimumWeight, double initialMaximumWeight); /* End of file Network.h */ #endif sources_5316/gram/OTMulti.cpp0000644000176700017670000015510211647117522014724 0ustar paulpaul/* OTMulti.cpp * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2005/06/11 the very beginning of computational bidirectional multi-level OT * pb 2006/05/16 guarded against cells with many violations * pb 2006/05/17 draw disharmonies above tableau * pb 2007/05/19 decision strategies * pb 2007/08/12 wchar * pb 2007/10/01 leak and constraint plasticity * pb 2007/10/01 can write as encoding * pb 2007/11/14 drawTableau: corrected direction of arrows for positive satisfactions * pb 2008/04/14 OTMulti_getConstraintIndexFromName * pb 2009/03/18 modern enums * pb 2010/06/05 corrected colours * pb 2011/03/01 multiple update rules; more decision strategies * pb 2011/03/29 C++ * pb 2011/04/27 Melder_debug 41 and 42 * pb 2011/05/15 prevented zero sums of probabilities in MaxEnt */ #include "OTMulti.h" #include "oo_DESTROY.h" #include "OTMulti_def.h" #include "oo_COPY.h" #include "OTMulti_def.h" #include "oo_EQUAL.h" #include "OTMulti_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "OTMulti_def.h" #include "oo_WRITE_BINARY.h" #include "OTMulti_def.h" #include "oo_READ_BINARY.h" #include "OTMulti_def.h" #include "oo_DESCRIPTION.h" #include "OTMulti_def.h" void structOTMulti :: v_info () { structData :: v_info (); long numberOfViolations = 0; for (long icand = 1; icand <= numberOfCandidates; icand ++) { for (long icons = 1; icons <= numberOfConstraints; icons ++) { numberOfViolations += candidates [icand]. marks [icons]; } } MelderInfo_writeLine2 (L"Decision strategy: ", kOTGrammar_decisionStrategy_getText (decisionStrategy)); MelderInfo_writeLine2 (L"Number of constraints: ", Melder_integer (numberOfConstraints)); MelderInfo_writeLine2 (L"Number of candidates: ", Melder_integer (numberOfCandidates)); MelderInfo_writeLine2 (L"Number of violation marks: ", Melder_integer (numberOfViolations)); } void structOTMulti :: v_writeText (MelderFile file) { MelderFile_write7 (file, L"\n<", kOTGrammar_decisionStrategy_getText (decisionStrategy), L">\n", Melder_double (leak), L" ! leak\n", Melder_integer (numberOfConstraints), L" constraints"); for (long icons = 1; icons <= numberOfConstraints; icons ++) { OTConstraint constraint = & constraints [icons]; MelderFile_write1 (file, L"\n\t\""); for (const wchar *p = & constraint -> name [0]; *p; p ++) { if (*p =='\"') MelderFile_writeCharacter (file, '\"'); // double any quotes within quotes MelderFile_writeCharacter (file, *p); } MelderFile_write6 (file, L"\" ", Melder_double (constraint -> ranking), L" ", Melder_double (constraint -> disharmony), L" ", Melder_double (constraint -> plasticity)); } MelderFile_write3 (file, L"\n\n", Melder_integer (numberOfCandidates), L" candidates"); for (long icand = 1; icand <= numberOfCandidates; icand ++) { OTCandidate candidate = & candidates [icand]; MelderFile_write1 (file, L"\n\t\""); for (const wchar *p = & candidate -> string [0]; *p; p ++) { if (*p =='\"') MelderFile_writeCharacter (file, '\"'); // double any quotes within quotes MelderFile_writeCharacter (file, *p); } MelderFile_write1 (file, L"\" "); for (long icons = 1; icons <= candidate -> numberOfConstraints; icons ++) { MelderFile_write2 (file, L" ", Melder_integer (candidate -> marks [icons])); } } } void OTMulti_checkIndex (OTMulti me) { if (my index) return; my index = NUMvector (1, my numberOfConstraints); for (long icons = 1; icons <= my numberOfConstraints; icons ++) my index [icons] = icons; OTMulti_sort (me); } void structOTMulti :: v_readText (MelderReadText text) { int localVersion = Thing_version; OTMulti_Parent :: v_readText (text); if (localVersion >= 1) { try { decisionStrategy = texgete1 (text, kOTGrammar_decisionStrategy_getValue); therror } catch (MelderError) { Melder_throw ("Decision strategy not read."); } } if (localVersion >= 2) { try { leak = texgetr8 (text); } catch (MelderError) { Melder_throw ("Trying to read leak."); } } if ((numberOfConstraints = texgeti4 (text)) < 1) Melder_throw ("No constraints."); constraints = NUMvector (1, numberOfConstraints); for (long icons = 1; icons <= numberOfConstraints; icons ++) { OTConstraint constraint = & constraints [icons]; constraint -> name = texgetw2 (text); constraint -> ranking = texgetr8 (text); constraint -> disharmony = texgetr8 (text); if (localVersion < 2) { constraint -> plasticity = 1.0; } else { try { constraint -> plasticity = texgetr8 (text); } catch (MelderError) { Melder_throw ("Plasticity of constraint ", icons, " not read."); } } } if ((numberOfCandidates = texgeti4 (text)) < 1) Melder_throw ("No candidates."); candidates = NUMvector (1, numberOfCandidates); for (long icand = 1; icand <= numberOfCandidates; icand ++) { OTCandidate candidate = & candidates [icand]; candidate -> string = texgetw2 (text); candidate -> numberOfConstraints = numberOfConstraints; // redundancy, needed for writing binary candidate -> marks = NUMvector (1, candidate -> numberOfConstraints); for (long icons = 1; icons <= candidate -> numberOfConstraints; icons ++) { candidate -> marks [icons] = texgeti2 (text); } } OTMulti_checkIndex (this); } Thing_implement (OTMulti, Data, 2); long OTMulti_getConstraintIndexFromName (OTMulti me, const wchar *name) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { if (Melder_wcsequ (my constraints [icons]. name, name)) { return icons; } } return 0; } static OTMulti constraintCompare_grammar; static int constraintCompare (const void *first, const void *second) { OTMulti me = constraintCompare_grammar; long icons = * (long *) first, jcons = * (long *) second; OTConstraint ci = & my constraints [icons], cj = & my constraints [jcons]; /* * Sort primarily by disharmony. */ if (ci -> disharmony > cj -> disharmony) return -1; if (ci -> disharmony < cj -> disharmony) return +1; /* * Tied constraints are sorted alphabetically. */ return wcscmp (my constraints [icons]. name, my constraints [jcons]. name); } void OTMulti_sort (OTMulti me) { constraintCompare_grammar = me; qsort (& my index [1], my numberOfConstraints, sizeof (long), constraintCompare); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [my index [icons]]; constraint -> tiedToTheLeft = icons > 1 && my constraints [my index [icons - 1]]. disharmony == constraint -> disharmony; constraint -> tiedToTheRight = icons < my numberOfConstraints && my constraints [my index [icons + 1]]. disharmony == constraint -> disharmony; } } void OTMulti_newDisharmonies (OTMulti me, double evaluationNoise) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; constraint -> disharmony = constraint -> ranking + NUMrandomGauss (0, evaluationNoise); } OTMulti_sort (me); } int OTMulti_compareCandidates (OTMulti me, long icand1, long icand2) { int *marks1 = my candidates [icand1]. marks; int *marks2 = my candidates [icand2]. marks; if (my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int numberOfMarks1 = marks1 [my index [icons]]; int numberOfMarks2 = marks2 [my index [icons]]; /* * Count tied constraints as one. */ while (my constraints [my index [icons]]. tiedToTheRight) { icons ++; numberOfMarks1 += marks1 [my index [icons]]; numberOfMarks2 += marks2 [my index [icons]]; } if (numberOfMarks1 < numberOfMarks2) return -1; /* Candidate 1 is better than candidate 2. */ if (numberOfMarks1 > numberOfMarks2) return +1; /* Candidate 2 is better than candidate 1. */ } } else if (my decisionStrategy == kOTGrammar_decisionStrategy_HARMONIC_GRAMMAR || my decisionStrategy == kOTGrammar_decisionStrategy_MAXIMUM_ENTROPY) { double disharmony1 = 0.0, disharmony2 = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { disharmony1 += my constraints [icons]. disharmony * marks1 [icons]; disharmony2 += my constraints [icons]. disharmony * marks2 [icons]; } if (disharmony1 < disharmony2) return -1; /* Candidate 1 is better than candidate 2. */ if (disharmony1 > disharmony2) return +1; /* Candidate 2 is better than candidate 1. */ } else if (my decisionStrategy == kOTGrammar_decisionStrategy_LINEAR_OT) { double disharmony1 = 0.0, disharmony2 = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { if (my constraints [icons]. disharmony > 0.0) { disharmony1 += my constraints [icons]. disharmony * marks1 [icons]; disharmony2 += my constraints [icons]. disharmony * marks2 [icons]; } } if (disharmony1 < disharmony2) return -1; /* Candidate 1 is better than candidate 2. */ if (disharmony1 > disharmony2) return +1; /* Candidate 2 is better than candidate 1. */ } else if (my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) { double disharmony1 = 0.0, disharmony2 = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { disharmony1 += exp (my constraints [icons]. disharmony) * marks1 [icons]; disharmony2 += exp (my constraints [icons]. disharmony) * marks2 [icons]; } if (disharmony1 < disharmony2) return -1; /* Candidate 1 is better than candidate 2. */ if (disharmony1 > disharmony2) return +1; /* Candidate 2 is better than candidate 1. */ } else if (my decisionStrategy == kOTGrammar_decisionStrategy_POSITIVE_HG) { double disharmony1 = 0.0, disharmony2 = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { double constraintDisharmony = my constraints [icons]. disharmony > 1.0 ? my constraints [icons]. disharmony : 1.0; disharmony1 += constraintDisharmony * marks1 [icons]; disharmony2 += constraintDisharmony * marks2 [icons]; } if (disharmony1 < disharmony2) return -1; /* Candidate 1 is better than candidate 2. */ if (disharmony1 > disharmony2) return +1; /* Candidate 2 is better than candidate 1. */ } else { Melder_fatal ("Unimplemented decision strategy."); } return 0; /* None of the comparisons found a difference between the two candidates. Hence, they are equally good. */ } int OTMulti_candidateMatches (OTMulti me, long icand, const wchar *form1, const wchar *form2) { const wchar *string = my candidates [icand]. string; return (form1 [0] == '\0' || wcsstr (string, form1)) && (form2 [0] == '\0' || wcsstr (string, form2)); } static void _OTMulti_fillInHarmonies (OTMulti me, const wchar *form1, const wchar *form2) { if (my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) return; for (long icand = 1; icand <= my numberOfCandidates; icand ++) if (OTMulti_candidateMatches (me, icand, form1, form2)) { OTCandidate candidate = & my candidates [icand]; int *marks = candidate -> marks; double disharmony = 0.0; if (my decisionStrategy == kOTGrammar_decisionStrategy_HARMONIC_GRAMMAR || my decisionStrategy == kOTGrammar_decisionStrategy_MAXIMUM_ENTROPY) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { disharmony += my constraints [icons]. disharmony * marks [icons]; } } else if (my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { disharmony += exp (my constraints [icons]. disharmony) * marks [icons]; } } else if (my decisionStrategy == kOTGrammar_decisionStrategy_LINEAR_OT) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { if (my constraints [icons]. disharmony > 0.0) { disharmony += my constraints [icons]. disharmony * marks [icons]; } } } else if (my decisionStrategy == kOTGrammar_decisionStrategy_POSITIVE_HG) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { double constraintDisharmony = my constraints [icons]. disharmony > 1.0 ? my constraints [icons]. disharmony : 1.0; disharmony += constraintDisharmony * marks [icons]; } } else { Melder_fatal ("_OTMulti_fillInHarmonies: unimplemented decision strategy."); } candidate -> harmony = - disharmony; } } static void _OTMulti_fillInProbabilities (OTMulti me, const wchar *form1, const wchar *form2) { double maximumHarmony = -1e300; for (long icand = 1; icand <= my numberOfCandidates; icand ++) if (OTMulti_candidateMatches (me, icand, form1, form2)) { OTCandidate candidate = & my candidates [icand]; if (candidate -> harmony > maximumHarmony) { maximumHarmony = candidate -> harmony; } } for (long icand = 1; icand <= my numberOfCandidates; icand ++) if (OTMulti_candidateMatches (me, icand, form1, form2)) { OTCandidate candidate = & my candidates [icand]; candidate -> probability = exp (candidate -> harmony - maximumHarmony); Melder_assert (candidate -> probability >= 0.0 && candidate -> probability <= 1.0); } double sumOfProbabilities = 0.0; for (long icand = 1; icand <= my numberOfCandidates; icand ++) if (OTMulti_candidateMatches (me, icand, form1, form2)) { OTCandidate candidate = & my candidates [icand]; sumOfProbabilities += candidate -> probability; } Melder_assert (sumOfProbabilities > 0.0); // Because at least one of them is 1.0. for (long icand = 1; icand <= my numberOfCandidates; icand ++) if (OTMulti_candidateMatches (me, icand, form1, form2)) { OTCandidate candidate = & my candidates [icand]; candidate -> probability /= sumOfProbabilities; } } class MelderError_OTMulti_NoMatchingCandidate: public MelderError {}; long OTMulti_getWinner (OTMulti me, const wchar *form1, const wchar *form2) { try { long icand_best = 0; if (my decisionStrategy == kOTGrammar_decisionStrategy_MAXIMUM_ENTROPY || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) { _OTMulti_fillInHarmonies (me, form1, form2); _OTMulti_fillInProbabilities (me, form1, form2); double cutOff = NUMrandomUniform (0.0, 1.0); double sumOfProbabilities = 0.0; for (long icand = 1; icand <= my numberOfCandidates; icand ++) if (OTMulti_candidateMatches (me, icand, form1, form2)) { sumOfProbabilities += my candidates [icand]. probability; if (sumOfProbabilities > cutOff) { icand_best = icand; break; } } } else { long numberOfBestCandidates = 0; for (long icand = 1; icand <= my numberOfCandidates; icand ++) if (OTMulti_candidateMatches (me, icand, form1, form2)) { if (icand_best == 0) { icand_best = icand; numberOfBestCandidates = 1; } else { int comparison = OTMulti_compareCandidates (me, icand, icand_best); if (comparison == -1) { icand_best = icand; // the current candidate is the unique best candidate found so far numberOfBestCandidates = 1; } else if (comparison == 0) { numberOfBestCandidates += 1; // the current candidate is equally good as the best found before /* * Give all candidates that are equally good an equal chance to become the winner. */ if (Melder_debug == 41) { icand_best = icand_best; // keep first } else if (Melder_debug == 42) { icand_best = icand; // take last } else if (NUMrandomUniform (0.0, numberOfBestCandidates) < 1.0) { // default: take random icand_best = icand; } } } } } if (icand_best == 0) { Melder_error_ ("The forms ", form1, " and ", form2, " do not match any candidate."); throw MelderError_OTMulti_NoMatchingCandidate (); // BUG: NYI } return icand_best; } catch (MelderError) { Melder_throw (me, ": winner not determined."); } } static void OTMulti_modifyRankings (OTMulti me, long iwinner, long iloser, enum kOTGrammar_rerankingStrategy updateRule, double plasticity, double relativePlasticityNoise) { bool *grammarHasChanged = NULL; // to be implemented bool warnIfStalled = false; // to be implemented if (iwinner == iloser) return; OTCandidate winner = & my candidates [iwinner], loser = & my candidates [iloser]; double step = relativePlasticityNoise == 0.0 ? plasticity : NUMrandomGauss (plasticity, relativePlasticityNoise * plasticity); bool multiplyStepByNumberOfViolations = my decisionStrategy == kOTGrammar_decisionStrategy_HARMONIC_GRAMMAR || my decisionStrategy == kOTGrammar_decisionStrategy_LINEAR_OT || my decisionStrategy == kOTGrammar_decisionStrategy_MAXIMUM_ENTROPY || my decisionStrategy == kOTGrammar_decisionStrategy_POSITIVE_HG || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY; if (Melder_debug != 0) { /* * Perhaps override the standard update rule. */ if (Melder_debug == 26) multiplyStepByNumberOfViolations = false; // OT-GLA else if (Melder_debug == 27) multiplyStepByNumberOfViolations = true; // HG-GLA } if (updateRule == kOTGrammar_rerankingStrategy_SYMMETRIC_ONE) { long icons = NUMrandomInteger (1, my numberOfConstraints); OTConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= loserMarks - winnerMarks; constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak); if (grammarHasChanged != NULL) *grammarHasChanged = true; } if (winnerMarks > loserMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak); if (grammarHasChanged != NULL) *grammarHasChanged = true; } } else if (updateRule == kOTGrammar_rerankingStrategy_SYMMETRIC_ALL) { bool changed = false; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= loserMarks - winnerMarks; constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak); changed = true; } if (winnerMarks > loserMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak); changed = true; } } if (changed && my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG) { double sumOfWeights = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { sumOfWeights += my constraints [icons]. ranking; } double averageWeight = sumOfWeights / my numberOfConstraints; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { my constraints [icons]. ranking -= averageWeight; } } if (grammarHasChanged != NULL) *grammarHasChanged = changed; } else if (updateRule == kOTGrammar_rerankingStrategy_WEIGHTED_UNCANCELLED) { int winningConstraints = 0, losingConstraints = 0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) losingConstraints ++; if (winnerMarks > loserMarks) winningConstraints ++; } if (winningConstraints != 0) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= loserMarks - winnerMarks; constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak) / losingConstraints; //constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak) * winningConstraints; if (grammarHasChanged != NULL) *grammarHasChanged = true; } if (winnerMarks > loserMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak) / winningConstraints; //constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak) * losingConstraints; if (grammarHasChanged != NULL) *grammarHasChanged = true; } } } } else if (updateRule == kOTGrammar_rerankingStrategy_WEIGHTED_ALL) { int winningConstraints = 0, losingConstraints = 0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > 0) losingConstraints ++; if (winnerMarks > 0) winningConstraints ++; } if (winningConstraints != 0) for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > 0) { if (multiplyStepByNumberOfViolations) constraintStep *= loserMarks - winnerMarks; constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak) / losingConstraints; if (grammarHasChanged != NULL) *grammarHasChanged = true; } if (winnerMarks > 0) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak) / winningConstraints; if (grammarHasChanged != NULL) *grammarHasChanged = true; } } } else if (updateRule == kOTGrammar_rerankingStrategy_EDCD || updateRule == kOTGrammar_rerankingStrategy_EDCD_WITH_VACATION) { /* * Determine the crucial winner mark. */ double pivotRanking; bool equivalent = true; long icons = 1; for (; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [my index [icons]]; // order is important, so indirect int loserMarks = loser -> marks [my index [icons]]; if (loserMarks < winnerMarks) break; if (loserMarks > winnerMarks) equivalent = false; } if (icons > my numberOfConstraints) { // completed the loop? if (warnIfStalled && ! equivalent) Melder_warning ("Correct output is harmonically bounded (by having strict superset violations as compared to the learner's output)! EDCD stalls.\n" "Correct output: ", loser -> string, "\nLearner's output: ", winner -> string); return; } /* * Determine the stratum into which some constraints will be demoted. */ pivotRanking = my constraints [my index [icons]]. ranking; if (updateRule == kOTGrammar_rerankingStrategy_EDCD_WITH_VACATION) { long numberOfConstraintsToDemote = 0; for (icons = 1; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) { OTConstraint constraint = & my constraints [icons]; if (constraint -> ranking >= pivotRanking) { numberOfConstraintsToDemote += 1; } } } if (numberOfConstraintsToDemote > 0) { for (icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; if (constraint -> ranking < pivotRanking) { constraint -> ranking -= numberOfConstraintsToDemote * step * constraint -> plasticity; if (grammarHasChanged != NULL) *grammarHasChanged = true; } } } } /* * Demote all the uniquely violated constraints in the loser * that have rankings not lower than the pivot. */ for (icons = 1; icons <= my numberOfConstraints; icons ++) { long numberOfConstraintsDemoted = 0; int winnerMarks = winner -> marks [my index [icons]]; // For the vacation version, the order is important, so indirect. int loserMarks = loser -> marks [my index [icons]]; if (loserMarks > winnerMarks) { OTConstraint constraint = & my constraints [my index [icons]]; double constraintStep = step * constraint -> plasticity; if (constraint -> ranking >= pivotRanking) { numberOfConstraintsDemoted += 1; constraint -> ranking = pivotRanking - numberOfConstraintsDemoted * constraintStep; // This preserves the order of the demotees. if (grammarHasChanged != NULL) *grammarHasChanged = true; } } } } else if (updateRule == kOTGrammar_rerankingStrategy_DEMOTION_ONLY) { /* * Determine the crucial loser mark. */ long crucialLoserMark; OTConstraint offendingConstraint; long icons = 1; for (; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [my index [icons]]; /* Order is important, so indirect. */ int loserMarks = loser -> marks [my index [icons]]; if (my constraints [my index [icons]]. tiedToTheRight) Melder_throw ("Demotion-only learning cannot handle tied constraints."); if (loserMarks < winnerMarks) { if (my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { Melder_throw ("Demotion-only learning step: Loser wins! Should never happen."); } else { // do nothing; the whole demotion-only idea does not really apply very well to non-OT decision strategies } } if (loserMarks > winnerMarks) break; } if (icons > my numberOfConstraints) { // completed the loop? if (my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { Melder_throw ("(OTGrammar_step:) Loser equals correct candidate: loser \"", loser -> string, "\", winner \"", winner -> string, "\"."); } else { // do nothing } } else { crucialLoserMark = icons; /* * Demote the highest uniquely violated constraint in the loser. */ offendingConstraint = & my constraints [my index [crucialLoserMark]]; double constraintStep = step * offendingConstraint -> plasticity; offendingConstraint -> ranking -= constraintStep; if (grammarHasChanged != NULL) *grammarHasChanged = true; } } else { Melder_assert (updateRule == kOTGrammar_rerankingStrategy_WEIGHTED_ALL_UP_HIGHEST_DOWN); bool changed = false; long numberOfUp = 0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (winnerMarks > loserMarks) { numberOfUp ++; } } if (numberOfUp > 0) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (winnerMarks > loserMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak) / numberOfUp; } } long crucialLoserMark, winnerMarks = 0, loserMarks = 0; OTConstraint offendingConstraint; long icons = 1; for (; icons <= my numberOfConstraints; icons ++) { winnerMarks = winner -> marks [my index [icons]]; /* Order is important, so indirect. */ loserMarks = loser -> marks [my index [icons]]; if (my constraints [my index [icons]]. tiedToTheRight) Melder_throw ("Demotion-only learning cannot handle tied constraints."); if (loserMarks < winnerMarks) { if (my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { Melder_throw ("Demotion-only learning step: Loser wins! Should never happen."); } else { // do nothing; the whole demotion-only idea does not really apply very well to non-OT decision strategies } } if (loserMarks > winnerMarks) break; } if (icons > my numberOfConstraints) { // completed the loop? if (my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { Melder_throw ("(OTGrammar_step:) Loser equals correct candidate: loser \"", loser -> string, "\", winner \"", winner -> string, "\"."); } else { // do nothing } } else { crucialLoserMark = icons; /* * Demote the highest uniquely violated constraint in the loser. */ offendingConstraint = & my constraints [my index [crucialLoserMark]]; double constraintStep = step * offendingConstraint -> plasticity; if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; offendingConstraint -> ranking -= /*numberOfUp **/ constraintStep * (1.0 - offendingConstraint -> ranking * my leak); } } if (grammarHasChanged != NULL) *grammarHasChanged = changed; } } int OTMulti_learnOne (OTMulti me, const wchar *form1, const wchar *form2, enum kOTGrammar_rerankingStrategy updateRule, int direction, double plasticity, double relativePlasticityNoise) { long iloser = OTMulti_getWinner (me, form1, form2); therror if (direction & OTMulti_LEARN_FORWARD) { long iwinner = OTMulti_getWinner (me, form1, L""); therror OTMulti_modifyRankings (me, iwinner, iloser, updateRule, plasticity, relativePlasticityNoise); therror } if (direction & OTMulti_LEARN_BACKWARD) { long iwinner = OTMulti_getWinner (me, form2, L""); therror OTMulti_modifyRankings (me, iwinner, iloser, updateRule, plasticity, relativePlasticityNoise); therror } return 1; } static Table OTMulti_createHistory (OTMulti me, long storeHistoryEvery, long numberOfData) { try { long numberOfSamplingPoints = numberOfData / storeHistoryEvery; /* E.g. 0, 20, 40, ... */ autoTable thee = Table_createWithoutColumnNames (1 + numberOfSamplingPoints, 3 + my numberOfConstraints); Table_setColumnLabel (thee.peek(), 1, L"Datum"); Table_setColumnLabel (thee.peek(), 2, L"Form1"); Table_setColumnLabel (thee.peek(), 3, L"Form2"); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { Table_setColumnLabel (thee.peek(), 3 + icons, my constraints [icons]. name); } Table_setNumericValue (thee.peek(), 1, 1, 0); therror Table_setStringValue (thee.peek(), 1, 2, L"(initial)"); therror Table_setStringValue (thee.peek(), 1, 3, L"(initial)"); therror for (long icons = 1; icons <= my numberOfConstraints; icons ++) { Table_setNumericValue (thee.peek(), 1, 3 + icons, my constraints [icons]. ranking); therror } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": history not created."); } } static int OTMulti_updateHistory (OTMulti me, Table thee, long storeHistoryEvery, long idatum, const wchar *form1, const wchar *form2) { try { if (idatum % storeHistoryEvery == 0) { long irow = 1 + idatum / storeHistoryEvery; Table_setNumericValue (thee, irow, 1, idatum); therror Table_setStringValue (thee, irow, 2, form1); therror Table_setStringValue (thee, irow, 3, form2); therror for (long icons = 1; icons <= my numberOfConstraints; icons ++) { Table_setNumericValue (thee, irow, 3 + icons, my constraints [icons]. ranking); therror } } return 1; } catch (MelderError) { Melder_throw (me, ": history not updated."); } } void OTMulti_PairDistribution_learn (OTMulti me, PairDistribution thee, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int direction, double initialPlasticity, long replicationsPerPlasticity, double plasticityDecrement, long numberOfPlasticities, double relativePlasticityNoise, long storeHistoryEvery, Table *history_out) { long idatum = 0, numberOfData = numberOfPlasticities * replicationsPerPlasticity; try { double plasticity = initialPlasticity; autoMelderMonitor monitor (L"Learning from partial pairs..."); if (monitor.graphics()) { Graphics_clearWs (monitor.graphics()); } autoTable history; if (storeHistoryEvery) { history.reset (OTMulti_createHistory (me, storeHistoryEvery, numberOfData)); } for (long iplasticity = 1; iplasticity <= numberOfPlasticities; iplasticity ++) { for (long ireplication = 1; ireplication <= replicationsPerPlasticity; ireplication ++) { wchar *form1, *form2; PairDistribution_peekPair (thee, & form1, & form2); therror ++ idatum; if (monitor.graphics() && idatum % (numberOfData / 400 + 1) == 0) { long numberOfDrawnConstraints = my numberOfConstraints < 14 ? my numberOfConstraints : 14; if (numberOfDrawnConstraints > 0) { double sumOfRankings = 0.0; for (long icons = 1; icons <= numberOfDrawnConstraints; icons ++) { sumOfRankings += my constraints [icons]. ranking; } double meanRanking = sumOfRankings / numberOfDrawnConstraints; Graphics_setWindow (monitor.graphics(), 0, numberOfData, meanRanking - 50, meanRanking + 50); for (long icons = 1; icons <= numberOfDrawnConstraints; icons ++) { Graphics_setGrey (monitor.graphics(), (double) icons / numberOfDrawnConstraints); Graphics_line (monitor.graphics(), idatum, my constraints [icons]. ranking, idatum, my constraints [icons]. ranking+1); } Graphics_flushWs (monitor.graphics()); /* Because drawing is faster than progress loop. */ } } try { Melder_monitor ((double) idatum / numberOfData, L"Processing partial pair ", Melder_integer (idatum), L" out of ", Melder_integer (numberOfData), L":\n ", form1, L" ", form2); } catch (MelderError) { if (history_out) *history_out = history.transfer(); // so that we can inspect throw; } OTMulti_newDisharmonies (me, evaluationNoise); therror try { OTMulti_learnOne (me, form1, form2, updateRule, direction, plasticity, relativePlasticityNoise); therror } catch (MelderError) { if (history.peek()) { OTMulti_updateHistory (me, history.peek(), storeHistoryEvery, idatum, form1, form2); therror } throw; } if (history.peek()) { OTMulti_updateHistory (me, history.peek(), storeHistoryEvery, idatum, form1, form2); therror } } plasticity *= plasticityDecrement; } if (history_out) *history_out = history.transfer(); } catch (MelderError) { if (idatum > 1) Melder_error_ ("Only ", idatum - 1, " input-output pairs out of ", numberOfData, " were processed."); Melder_throw (me, " & ", thee, ": learning from partial pairs not completed."); } } static long OTMulti_crucialCell (OTMulti me, long icand, long iwinner, long numberOfOptimalCandidates, const wchar *form1, const wchar *form2) { if (my numberOfCandidates < 2) return 0; // if there is only one candidate, all cells can be greyed if (OTMulti_compareCandidates (me, icand, iwinner) == 0) { // candidate equally good as winner? if (numberOfOptimalCandidates > 1) { /* All cells are important. */ } else { long secondBest = 0; for (long jcand = 1; jcand <= my numberOfCandidates; jcand ++) { if (OTMulti_candidateMatches (me, jcand, form1, form2) && OTMulti_compareCandidates (me, jcand, iwinner) != 0) { // a non-optimal candidate? if (secondBest == 0) { secondBest = jcand; // first guess } else if (OTMulti_compareCandidates (me, jcand, secondBest) < 0) { secondBest = jcand; // better guess } } } if (secondBest == 0) return 0; // if all candidates are equally good, all cells can be greyed return OTMulti_crucialCell (me, secondBest, iwinner, 1, form1, form2); } } else { int *candidateMarks = my candidates [icand]. marks; int *winnerMarks = my candidates [iwinner]. marks; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int numberOfCandidateMarks = candidateMarks [my index [icons]]; int numberOfWinnerMarks = winnerMarks [my index [icons]]; if (numberOfCandidateMarks > numberOfWinnerMarks) { return icons; } } } return my numberOfConstraints; /* Nothing grey. */ } static double OTMulti_constraintWidth (Graphics g, OTConstraint constraint, bool showDisharmony) { wchar text [100], *newLine; double maximumWidth = showDisharmony ? 0.8 * Graphics_textWidth_ps (g, Melder_fixed (constraint -> disharmony, 1), TRUE) : 0.0, firstWidth, secondWidth; wcscpy (text, constraint -> name); newLine = wcschr (text, '\n'); if (newLine) { *newLine = '\0'; firstWidth = Graphics_textWidth_ps (g, text, true); if (firstWidth > maximumWidth) maximumWidth = firstWidth; secondWidth = Graphics_textWidth_ps (g, newLine + 1, true); if (secondWidth > maximumWidth) maximumWidth = secondWidth; return maximumWidth; } firstWidth = Graphics_textWidth_ps (g, text, true); if (firstWidth > maximumWidth) maximumWidth = firstWidth; return maximumWidth; } void OTMulti_drawTableau (OTMulti me, Graphics g, const wchar *form1, const wchar *form2, bool vertical, bool showDisharmonies) { long winner, winner1 = 0, winner2 = 0; double x, y, fontSize = Graphics_inqFontSize (g); Graphics_Colour colour = Graphics_inqColour (g); wchar text [200]; bool bidirectional = form1 [0] != '\0' && form2 [0] != '\0'; try { winner = OTMulti_getWinner (me, form1, form2); therror } catch (MelderError) { Melder_clearError (); Graphics_setWindow (g, 0.0, 1.0, 0.0, 1.0); Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_rectangle (g, 0, 1, 0, 1); Graphics_text (g, 0.0, 0.5, L"(no matching candidates)"); return; } if (bidirectional) { winner1 = OTMulti_getWinner (me, form1, L""); winner2 = OTMulti_getWinner (me, form2, L""); } Graphics_setWindow (g, 0.0, 1.0, 0.0, 1.0); const double margin = Graphics_dxMMtoWC (g, 1.0); const double fingerWidth = Graphics_dxMMtoWC (g, 7.0) * fontSize / 12.0; const double doubleLineDx = Graphics_dxMMtoWC (g, 0.9); const double doubleLineDy = Graphics_dyMMtoWC (g, 0.9); const double rowHeight = Graphics_dyMMtoWC (g, 1.5 * fontSize * 25.4 / 72); const double descent = rowHeight * 0.5; const double worldAspectRatio = Graphics_dyMMtoWC (g, 1.0) / Graphics_dxMMtoWC (g, 1.0); // because Graphics_textWidth measures in the x direction only /* * Compute height of header row. */ double headerHeight; if (vertical) { headerHeight = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; double constraintTextWidth = Graphics_textWidth (g, constraint -> name); if (constraintTextWidth > headerHeight) headerHeight = constraintTextWidth; } headerHeight += margin * 2; headerHeight *= worldAspectRatio; } else { headerHeight = rowHeight; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; if (wcschr (constraint -> name, '\n')) { headerHeight += 0.7 * rowHeight; break; } } } /* * Compute longest candidate string. * Also count the number of optimal candidates (if there are more than one, the fingers will be drawn in red). */ double candWidth = Graphics_textWidth_ps (g, form1, TRUE) + Graphics_textWidth_ps (g, form2, true); long numberOfMatchingCandidates = 0; long numberOfOptimalCandidates = 0; long numberOfOptimalCandidates1 = 0; long numberOfOptimalCandidates2 = 0; for (long icand = 1; icand <= my numberOfCandidates; icand ++) { if ((form1 [0] != '\0' && OTMulti_candidateMatches (me, icand, form1, L"")) || (form2 [0] != '\0' && OTMulti_candidateMatches (me, icand, form2, L"")) || (form1 [0] == '\0' && form2 [0] == '\0')) { double width = Graphics_textWidth_ps (g, my candidates [icand]. string, true); if (width > candWidth) candWidth = width; numberOfMatchingCandidates ++; if (OTMulti_compareCandidates (me, icand, winner) == 0) { numberOfOptimalCandidates ++; } if (winner1 != 0 && OTMulti_compareCandidates (me, icand, winner1) == 0) { numberOfOptimalCandidates1 ++; } if (winner2 != 0 && OTMulti_compareCandidates (me, icand, winner2) == 0) { numberOfOptimalCandidates2 ++; } } } candWidth += fingerWidth * (bidirectional ? 3 : 1) + margin * 3; /* * Compute tableau width. */ double tableauWidth = candWidth + doubleLineDx; if (vertical) { tableauWidth += rowHeight * my numberOfConstraints / worldAspectRatio; } else { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; tableauWidth += OTMulti_constraintWidth (g, constraint, showDisharmonies); } tableauWidth += margin * 2 * my numberOfConstraints; } /* * Draw box. */ x = doubleLineDx; // left side of tableau y = 1.0 - doubleLineDy; if (showDisharmonies) y -= 0.6 * rowHeight; Graphics_rectangle (g, x, x + tableauWidth, y - headerHeight - numberOfMatchingCandidates * rowHeight - doubleLineDy, y); /* * Draw input. */ y -= headerHeight; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text2 (g, x + 0.5 * candWidth, y + 0.5 * headerHeight, form1, form2); Graphics_rectangle (g, x, x + candWidth, y, y + headerHeight); /* * Draw constraint names. */ x += candWidth + doubleLineDx; if (vertical) Graphics_setTextRotation (g, 90.0); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [my index [icons]]; double width = vertical ? rowHeight / worldAspectRatio : OTMulti_constraintWidth (g, constraint, showDisharmonies) + margin * 2; if (wcschr (constraint -> name, '\n')) { wchar *newLine; wcscpy (text, constraint -> name); newLine = wcschr (text, '\n'); *newLine = '\0'; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_TOP); Graphics_text (g, x + 0.5 * width, y + headerHeight, text); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (g, x + 0.5 * width, y, newLine + 1); } else if (vertical) { Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_text (g, x + 0.5 * width, y + margin, constraint -> name); } else { Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x + 0.5 * width, y + 0.5 * headerHeight, constraint -> name); } if (showDisharmonies) { Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_setFontSize (g, 0.8 * fontSize); Graphics_text (g, x + 0.5 * width, y + headerHeight, Melder_fixed (constraint -> disharmony, 1)); Graphics_setFontSize (g, fontSize); } Graphics_line (g, x, y, x, y + headerHeight); Graphics_line (g, x, y, x + width, y); x += width; } if (vertical) Graphics_setTextRotation (g, 0.0); /* * Draw candidates. */ y -= doubleLineDy; for (long icand = 1; icand <= my numberOfCandidates; icand ++) if ((form1 [0] != '\0' && OTMulti_candidateMatches (me, icand, form1, L"")) || (form2 [0] != '\0' && OTMulti_candidateMatches (me, icand, form2, L"")) || (form1 [0] == '\0' && form2 [0] == '\0')) { long crucialCell = OTMulti_crucialCell (me, icand, winner, numberOfOptimalCandidates, form1, form2); int candidateIsOptimal = OTMulti_compareCandidates (me, icand, winner) == 0; int candidateIsOptimal1 = winner1 != 0 && OTMulti_compareCandidates (me, icand, winner1) == 0; int candidateIsOptimal2 = winner2 != 0 && OTMulti_compareCandidates (me, icand, winner2) == 0; /* * Draw candidate transcription. */ x = doubleLineDx; y -= rowHeight; Graphics_setTextAlignment (g, Graphics_RIGHT, Graphics_HALF); Graphics_text (g, x + candWidth - margin, y + descent, my candidates [icand]. string); if (candidateIsOptimal) { Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_setFontSize (g, (int) ((bidirectional ? 1.2 : 1.5) * fontSize)); if (numberOfOptimalCandidates > 1) Graphics_setColour (g, Graphics_RED); Graphics_text (g, x + margin, y + descent - Graphics_dyMMtoWC (g, 0.5) * fontSize / 12.0, bidirectional ? L"\\Vr" : L"\\pf"); Graphics_setColour (g, colour); Graphics_setFontSize (g, (int) fontSize); } if (candidateIsOptimal1) { Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_setFontSize (g, (int) (1.5 * fontSize)); if (numberOfOptimalCandidates1 > 1) Graphics_setColour (g, Graphics_RED); Graphics_text (g, x + margin + fingerWidth, y + descent - Graphics_dyMMtoWC (g, 0.5) * fontSize / 12.0, L"\\pf"); Graphics_setColour (g, colour); Graphics_setFontSize (g, (int) fontSize); } if (candidateIsOptimal2) { Graphics_setTextAlignment (g, Graphics_RIGHT, Graphics_HALF); Graphics_setFontSize (g, (int) (1.5 * fontSize)); if (numberOfOptimalCandidates2 > 1) Graphics_setColour (g, Graphics_RED); Graphics_setTextRotation (g, 180); Graphics_text (g, x + margin + fingerWidth * 2, y + descent - Graphics_dyMMtoWC (g, 0.0) * fontSize / 12.0, L"\\pf"); Graphics_setTextRotation (g, 0); Graphics_setColour (g, colour); Graphics_setFontSize (g, (int) fontSize); } Graphics_rectangle (g, x, x + candWidth, y, y + rowHeight); /* * Draw grey cell backgrounds. */ if (! bidirectional && my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { x = candWidth + 2 * doubleLineDx; Graphics_setGrey (g, 0.9); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int index = my index [icons]; OTConstraint constraint = & my constraints [index]; double width = vertical ? rowHeight / worldAspectRatio : OTMulti_constraintWidth (g, constraint, showDisharmonies) + margin * 2; if (icons > crucialCell) Graphics_fillRectangle (g, x, x + width, y, y + rowHeight); x += width; } Graphics_setColour (g, colour); } /* * Draw cell marks. */ x = candWidth + 2 * doubleLineDx; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int index = my index [icons]; OTConstraint constraint = & my constraints [index]; double width = vertical ? rowHeight / worldAspectRatio : OTMulti_constraintWidth (g, constraint, showDisharmonies) + margin * 2; wchar markString [40]; markString [0] = '\0'; if (bidirectional && my candidates [icand]. marks [index] > 0) { if ((candidateIsOptimal1 || candidateIsOptimal2) && ! candidateIsOptimal) { wcscat (markString, L"\\<-"); } } if (bidirectional && my candidates [icand]. marks [index] < 0) { if (candidateIsOptimal && ! candidateIsOptimal1) { wcscat (markString, L"\\<-"); } if (candidateIsOptimal && ! candidateIsOptimal2) { wcscat (markString, L"\\<-"); } } /* * An exclamation mark can be drawn in this cell only if both of the following conditions are met: * 1. the candidate is not optimal; * 2. this is the crucial cell, i.e. the cells after it are drawn in grey. */ if (! bidirectional && icons == crucialCell && ! candidateIsOptimal && my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { int winnerMarks = my candidates [winner]. marks [index]; if (winnerMarks + 1 > 5) { wcscat (markString, Melder_integer (winnerMarks + 1)); } else { for (long imark = 1; imark <= winnerMarks + 1; imark ++) wcscat (markString, L"*"); } for (long imark = my candidates [icand]. marks [index]; imark < 0; imark ++) wcscat (markString, L"+"); wcscat (markString, L"!"); if (my candidates [icand]. marks [index] - (winnerMarks + 2) + 1 > 5) { wcscat (markString, Melder_integer (my candidates [icand]. marks [index] - (winnerMarks + 2) + 1)); } else { for (long imark = winnerMarks + 2; imark <= my candidates [icand]. marks [index]; imark ++) wcscat (markString, L"*"); } } else { if (my candidates [icand]. marks [index] > 5) { wcscat (markString, Melder_integer (my candidates [icand]. marks [index])); } else { for (long imark = 1; imark <= my candidates [icand]. marks [index]; imark ++) wcscat (markString, L"*"); for (long imark = my candidates [icand]. marks [index]; imark < 0; imark ++) wcscat (markString, L"+"); } } if (bidirectional && my candidates [icand]. marks [index] > 0) { if (candidateIsOptimal && ! candidateIsOptimal1) { wcscat (markString, L"\\->"); } if (candidateIsOptimal && ! candidateIsOptimal2) { wcscat (markString, L"\\->"); } } if (bidirectional && my candidates [icand]. marks [index] < 0) { if ((candidateIsOptimal1 || candidateIsOptimal2) && ! candidateIsOptimal) { wcscat (markString, L"\\->"); } } Graphics_text (g, x + 0.5 * width, y + descent, markString); Graphics_setColour (g, colour); Graphics_line (g, x, y, x, y + rowHeight); Graphics_line (g, x, y + rowHeight, x + width, y + rowHeight); x += width; } } /* * Draw box. */ x = doubleLineDx; /* Left side of tableau. */ y = 1.0 - doubleLineDy; if (showDisharmonies) y -= 0.6 * rowHeight; Graphics_rectangle (g, x, x + tableauWidth, y - headerHeight - numberOfMatchingCandidates * rowHeight - doubleLineDy, y); } void OTMulti_reset (OTMulti me, double ranking) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; constraint -> disharmony = constraint -> ranking = ranking; } OTMulti_sort (me); } void OTMulti_setRanking (OTMulti me, long constraint, double ranking, double disharmony) { try { if (constraint < 1) Melder_throw ("The constraint number should be positive, not ", constraint, "."); if (constraint > my numberOfConstraints) Melder_throw ("Constraint ", constraint, " does not exist (there are only ", my numberOfConstraints, " constraints)."); my constraints [constraint]. ranking = ranking; my constraints [constraint]. disharmony = disharmony; OTMulti_sort (me); } catch (MelderError) { Melder_throw (me, ": ranking not set."); } } void OTMulti_setConstraintPlasticity (OTMulti me, long constraint, double plasticity) { try { if (constraint < 1) Melder_throw ("The constraint number should be positive, not ", constraint, "."); if (constraint > my numberOfConstraints) Melder_throw ("Constraint ", constraint, " does not exist (there are only ", my numberOfConstraints, " constraints)."); my constraints [constraint]. plasticity = plasticity; } catch (MelderError) { Melder_throw (me, ": constraint plasticity not set."); } } void OTMulti_removeConstraint (OTMulti me, const wchar *constraintName) { try { long removed = 0; if (my numberOfConstraints <= 1) Melder_throw (me, ": cannot remove last constraint."); /* * Look for the constraint to be removed. */ for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTConstraint constraint = & my constraints [icons]; if (wcsequ (constraint -> name, constraintName)) { removed = icons; break; } } if (removed == 0) Melder_throw ("No constraint \"", constraintName, "\"."); /* * Remove the constraint while reusing the memory space. */ my numberOfConstraints -= 1; /* * Shift constraints. */ Melder_free (my constraints [removed]. name); for (long icons = removed; icons <= my numberOfConstraints; icons ++) { my constraints [icons] = my constraints [icons + 1]; } /* * Shift tableau rows. */ for (long icand = 1; icand <= my numberOfCandidates; icand ++) { OTCandidate candidate = & my candidates [icand]; candidate -> numberOfConstraints -= 1; for (long icons = removed; icons <= my numberOfConstraints; icons ++) { candidate -> marks [icons] = candidate -> marks [icons + 1]; } } /* * Rebuild index. */ for (long icons = 1; icons <= my numberOfConstraints; icons ++) my index [icons] = icons; OTMulti_sort (me); } catch (MelderError) { Melder_throw (me, ": constraint not removed."); } } void OTMulti_generateOptimalForm (OTMulti me, const wchar *form1, const wchar *form2, wchar *optimalForm, double evaluationNoise) { try { OTMulti_newDisharmonies (me, evaluationNoise); long winner = OTMulti_getWinner (me, form1, form2); therror wcscpy (optimalForm, my candidates [winner]. string); } catch (MelderError) { Melder_throw (me, ": optimal form not generated."); } } Strings OTMulti_Strings_generateOptimalForms (OTMulti me, Strings thee, double evaluationNoise) { try { autoStrings outputs = Thing_new (Strings); long n = thy numberOfStrings; outputs -> numberOfStrings = n; outputs -> strings = NUMvector (1, n); for (long i = 1; i <= n; i ++) { wchar output [100]; OTMulti_generateOptimalForm (me, thy strings [i], L"", output, evaluationNoise); therror outputs -> strings [i] = Melder_wcsdup (output); } return outputs.transfer(); } catch (MelderError) { Melder_throw (me, " & ", thee, ": optimal forms not generated."); } } Strings OTMulti_generateOptimalForms (OTMulti me, const wchar *form1, const wchar *form2, long numberOfTrials, double evaluationNoise) { try { autoStrings outputs = Thing_new (Strings); outputs -> numberOfStrings = numberOfTrials; outputs -> strings = NUMvector (1, numberOfTrials); for (long i = 1; i <= numberOfTrials; i ++) { wchar output [100]; OTMulti_generateOptimalForm (me, form1, form2, output, evaluationNoise); therror outputs -> strings [i] = Melder_wcsdup (output); } return outputs.transfer(); } catch (MelderError) { Melder_throw (me, ": optimal forms not generated."); } } Distributions OTMulti_to_Distribution (OTMulti me, const wchar *form1, const wchar *form2, long numberOfTrials, double evaluationNoise) { try { long totalNumberOfOutputs = 0, iout = 0; /* * Count the total number of outputs. */ for (long icand = 1; icand <= my numberOfCandidates; icand ++) { if (OTMulti_candidateMatches (me, icand, form1, form2)) { totalNumberOfOutputs ++; } } /* * Create the distribution. One row for every output form. */ autoDistributions thee = Distributions_create (totalNumberOfOutputs, 1); autoNUMvector index (1, my numberOfCandidates); /* * Set the row labels to the output strings. */ iout = 0; for (long icand = 1; icand <= my numberOfCandidates; icand ++) { if (OTMulti_candidateMatches (me, icand, form1, form2)) { thy rowLabels [++ iout] = Melder_wcsdup (my candidates [icand]. string); index [icand] = iout; } } /* * Compute a number of outputs and store the results. */ for (long itrial = 1; itrial <= numberOfTrials; itrial ++) { OTMulti_newDisharmonies (me, evaluationNoise); long iwinner = OTMulti_getWinner (me, form1, form2); therror thy data [index [iwinner]] [1] += 1; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": distribution not computed."); } } /* End of file OTMulti.cpp */ sources_5316/gram/OTMulti.h0000644000176700017670000000634311647117546014401 0ustar paulpaul#ifndef _OTMulti_h_ #define _OTMulti_h_ /* OTMulti.h * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Graphics.h" #include "PairDistribution.h" #include "Distributions.h" #include "OTGrammar.h" #include "OTMulti_def.h" oo_CLASS_CREATE (OTMulti, Data); long OTMulti_getConstraintIndexFromName (OTMulti me, const wchar *name); void OTMulti_checkIndex (OTMulti me); void OTMulti_sort (OTMulti me); /* Low level: meant to maintain the invariant * my constraints [my index [i]]. disharmony >= my constraints [my index [i+1]]. disharmony * Therefore, call after every direct assignment to the 'disharmony' attribute. * Tied constraints should not exist. */ void OTMulti_newDisharmonies (OTMulti me, double evaluationNoise); int OTMulti_candidateMatches (OTMulti me, long icand, const wchar *form1, const wchar *form2); int OTMulti_compareCandidates (OTMulti me, long icand1, long icand2); long OTMulti_getWinner (OTMulti me, const wchar *form1, const wchar *form2); #define OTMulti_LEARN_FORWARD 1 #define OTMulti_LEARN_BACKWARD 2 #define OTMulti_LEARN_BIDIRECTIONALLY 3 int OTMulti_learnOne (OTMulti me, const wchar *form1, const wchar *form2, enum kOTGrammar_rerankingStrategy updateRule, int direction, double plasticity, double relativePlasticityNoise); void OTMulti_PairDistribution_learn (OTMulti me, PairDistribution thee, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int direction, double initialPlasticity, long replicationsPerPlasticity, double plasticityDecrement, long numberOfPlasticities, double relativePlasticityNoise, long storeHistoryEvery, Table *history_out); void OTMulti_drawTableau (OTMulti me, Graphics g, const wchar *form1, const wchar *form2, bool vertical, bool showDisharmonies); void OTMulti_reset (OTMulti me, double ranking); void OTMulti_setRanking (OTMulti me, long constraint, double ranking, double disharmony); void OTMulti_setConstraintPlasticity (OTMulti me, long constraint, double plasticity); void OTMulti_removeConstraint (OTMulti me, const wchar *constraintName); void OTMulti_generateOptimalForm (OTMulti me, const wchar *form1, const wchar *form2, wchar *optimalForm, double evaluationNoise); Strings OTMulti_generateOptimalForms (OTMulti me, const wchar *form1, const wchar *form2, long numberOfTrials, double evaluationNoise); Distributions OTMulti_to_Distribution (OTMulti me, const wchar *form1, const wchar *form2, long numberOfTrials, double evaluationNoise); Strings OTMulti_Strings_generateOptimalForms (OTMulti me, Strings forms, double evaluationNoise); /* End of file OTMulti.h */ #endif sources_5316/gram/OTMultiEditor.h0000644000176700017670000000267111652005471015535 0ustar paulpaul#ifndef _OTMultiEditor_h_ #define _OTMultiEditor_h_ /* OTMultiEditor.h * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "HyperPage.h" #include "OTMulti.h" Thing_define (OTMultiEditor, HyperPage) { // new data: public: const wchar *form1, *form2; GuiObject form1Text, form2Text; long selectedConstraint; bool d_constraintsAreDrawnVertically; // overridden methods: virtual bool v_editable () { return true; } virtual void v_createChildren (); virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_draw (); virtual int v_goToPage (const wchar *title); }; OTMultiEditor OTMultiEditor_create (GuiObject parent, const wchar *title, OTMulti grammar); /* End of file OTMultiEditor.h */ #endif sources_5316/gram/OTGrammar_ex_tongueRoot.cpp0000644000176700017670000001376011613556207020144 0ustar paulpaul/* OTGrammar_ex_tongueRoot.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "OTGrammar.h" static const wchar *vowels [] = { L"i", L"e", L"\\sw", L"\\ic", L"\\ep", L"a" }; #define i 0 #define e 1 #define schwa 2 #undef I #define I 3 #define E 4 #define a 5 #define isatr(v) ((v) <= schwa) #define isrtr(v) ((v) >= I) #define fliptr(v) (((v) + 3) % 6) static void countVowelViolations (int *marks, int ncons, int v) { if (v == I) marks [1] ++; if (v == schwa) marks [2] ++; if (ncons == 9) { if (v == E) marks [6] ++; if (v == a) marks [7] ++; if (v == e) marks [8] ++; if (v == i) marks [9] ++; } } static void OTGrammarCandidate_init (OTGrammarCandidate me, int ncons, int v1, int v2) { wchar buffer [100]; swprintf (buffer, 100, L"%lst%ls", vowels [v1], vowels [v2]); my output = Melder_wcsdup (buffer); my marks = NUMvector (1, my numberOfConstraints = ncons); /* * Count vowel-gesture violations. */ countVowelViolations (my marks, ncons, v1); countVowelViolations (my marks, ncons, v2); /* * Count contour-gesture violations. */ if (isatr (v1) != isatr (v2)) my marks [5] ++; } OTGrammar OTGrammar_create_tongueRoot_grammar (int small_large, int equal_random_infant_Wolof) { try { int ncons = small_large == 1 ? 5 : 9, itab, v1, v2; autoOTGrammar me = Thing_new (OTGrammar); my constraints = NUMvector (1, my numberOfConstraints = ncons); my constraints [1]. name = Melder_wcsdup (L"*[rtr / hi]"); my constraints [2]. name = Melder_wcsdup (L"*[atr / lo]"); my constraints [3]. name = Melder_wcsdup (L"P\\s{ARSE}\n(rtr)"); my constraints [4]. name = Melder_wcsdup (L"P\\s{ARSE}\n(atr)"); my constraints [5]. name = Melder_wcsdup (L"*G\\s{ESTURE}\n(contour)"); if (ncons == 9) { my constraints [6]. name = Melder_wcsdup (L"*[rtr / mid]"); my constraints [7]. name = Melder_wcsdup (L"*[rtr / lo]"); my constraints [8]. name = Melder_wcsdup (L"*[atr / mid]"); my constraints [9]. name = Melder_wcsdup (L"*[atr / hi]"); } if (equal_random_infant_Wolof == 1) { /* equal? */ for (long icons = 1; icons <= ncons; icons ++) my constraints [icons]. ranking = 100.0; } else if (equal_random_infant_Wolof == 2) { /* random? */ for (long icons = 1; icons <= ncons; icons ++) my constraints [icons]. ranking = NUMrandomGauss (100.0, 10.0); } else if (equal_random_infant_Wolof == 3) { /* infant (= cannot speak) ? */ for (long icons = 1; icons <= ncons; icons ++) my constraints [icons]. ranking = 100.0; /* Structural constraints. */ my constraints [3]. ranking = 50.0; /* Faithfulness constraints. */ my constraints [4]. ranking = 50.0; } else { /* adult Wolof */ my constraints [1]. ranking = 100.0; my constraints [2]. ranking = 10.0; my constraints [3]. ranking = 50.0; my constraints [4]. ranking = 20.0; my constraints [5]. ranking = 30.0; if (ncons == 9) { my constraints [6]. ranking = 0.0; my constraints [7]. ranking = -10.0; my constraints [8]. ranking = 0.0; my constraints [9]. ranking = -10.0; } } if (ncons == 9) { my fixedRankings = NUMvector (1, my numberOfFixedRankings = 4); my fixedRankings [1]. higher = 1, my fixedRankings [1]. lower = 6; my fixedRankings [2]. higher = 6, my fixedRankings [2]. lower = 7; my fixedRankings [3]. higher = 2, my fixedRankings [3]. lower = 8; my fixedRankings [4]. higher = 8, my fixedRankings [4]. lower = 9; } my tableaus = NUMvector (1, my numberOfTableaus = 36); itab = 1; for (v1 = 0; v1 < 6; v1 ++) for (v2 = 0; v2 < 6; v2 ++) { OTGrammarTableau tableau = & my tableaus [itab]; wchar buffer [100]; swprintf (buffer, 100, L"%lst%ls", vowels [v1], vowels [v2]); tableau -> input = Melder_wcsdup (buffer); tableau -> candidates = NUMvector (1, tableau -> numberOfCandidates = 4); /* * Generate the four tongue-root variants as output candidates. */ OTGrammarCandidate_init (& tableau -> candidates [1], ncons, v1, v2); therror /* Faithful: no PARSE constraints violated. */ OTGrammarCandidate_init (& tableau -> candidates [2], ncons, fliptr (v1), v2); therror /* First vowel flipped: violated one PARSE constraint. */ OTGrammarCandidate_init (& tableau -> candidates [3], ncons, v1, fliptr (v2)); therror /* Second vowel flipped. */ OTGrammarCandidate_init (& tableau -> candidates [4], ncons, fliptr (v1), fliptr (v2)); therror /* Both vowels flipped. */ /* * Count PARSE violations. */ if (isatr (v1)) { tableau -> candidates [2]. marks [4] ++; tableau -> candidates [4]. marks [4] ++; } else { tableau -> candidates [2]. marks [3] ++; tableau -> candidates [4]. marks [3] ++; } if (isatr (v2)) { tableau -> candidates [3]. marks [4] ++; tableau -> candidates [4]. marks [4] ++; } else { tableau -> candidates [3]. marks [3] ++; tableau -> candidates [4]. marks [3] ++; } itab ++; } OTGrammar_checkIndex (me.peek()); therror OTGrammar_newDisharmonies (me.peek(), 0.0); for (long icons = 1; icons <= my numberOfConstraints; icons ++) my constraints [icons]. plasticity = 1.0; return me.transfer(); } catch (MelderError) { Melder_throw ("Tongue root grammar not created."); } } /* End of file OTGrammar_ex_tongueRoot.cpp */ sources_5316/gram/praat_gram.cpp0000644000176700017670000015542211744134741015511 0ustar paulpaul/* praat_gram.c * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2011/05/03 */ #include "praat.h" #include "Network.h" #include "OTGrammar.h" #include "OTMulti.h" #include "OTGrammarEditor.h" #include "OTMultiEditor.h" #undef iam #define iam iam_LOOP /***** HELP *****/ DIRECT (OT_learning_tutorial) Melder_help (L"OT learning"); END DIRECT (OTGrammar_help) Melder_help (L"OTGrammar"); END /***** NETWORK *****/ static void UiForm_addNetworkFields (UiForm dia) { LABEL (L"", L"Activity spreading settings:") REAL (L"left Activity range", L"-1.0") REAL (L"right Activity range", L"1.0") REAL (L"Spreading rate", L"1.0") REAL (L"Self-excitation", L"1.0") LABEL (L"", L"Weight update settings:") REAL (L"left Weight range", L"-1.0") REAL (L"right Weight range", L"1.0") REAL (L"Learning rate", L"0.1") REAL (L"Leak", L"0.0") } FORM (Create_empty_Network, L"Create empty Network", 0) WORD (L"Name", L"network") UiForm_addNetworkFields (dia); LABEL (L"", L"World coordinates:") REAL (L"left x range", L"0.0") REAL (L"right x range", L"10.0") REAL (L"left y range", L"0.0") REAL (L"right y range", L"10.0") OK DO autoNetwork me = Network_create (GET_REAL (L"left Activity range"), GET_REAL (L"right Activity range"), GET_REAL (L"Spreading rate"), GET_REAL (L"Self-excitation"), GET_REAL (L"left Weight range"), GET_REAL (L"right Weight range"), GET_REAL (L"Learning rate"), GET_REAL (L"Leak"), GET_REAL (L"left x range"), GET_REAL (L"right x range"), GET_REAL (L"left y range"), GET_REAL (L"right y range"), 0, 0); praat_new (me.transfer(), GET_STRING (L"Name")); END FORM (Create_rectangular_Network, L"Create rectangular Network", 0) UiForm_addNetworkFields (dia); LABEL (L"", L"Structure settings:") NATURAL (L"Number of rows", L"10") NATURAL (L"Number of columns", L"10") BOOLEAN (L"Bottom row clamped", 1) LABEL (L"", L"Initial state settings:") REAL (L"left Initial weight range", L"-0.1") REAL (L"right Initial weight range", L"0.1") OK DO autoNetwork me = Network_create_rectangle (GET_REAL (L"left Activity range"), GET_REAL (L"right Activity range"), GET_REAL (L"Spreading rate"), GET_REAL (L"Self-excitation"), GET_REAL (L"left Weight range"), GET_REAL (L"right Weight range"), GET_REAL (L"Learning rate"), GET_REAL (L"Leak"), GET_INTEGER (L"Number of rows"), GET_INTEGER (L"Number of columns"), GET_INTEGER (L"Bottom row clamped"), GET_REAL (L"left Initial weight range"), GET_REAL (L"right Initial weight range")); praat_new (me.transfer(), L"rectangle_", Melder_integer (GET_INTEGER (L"Number of rows")), L"_", Melder_integer (GET_INTEGER (L"Number of columns"))); END FORM (Create_rectangular_Network_vertical, L"Create rectangular Network (vertical)", 0) UiForm_addNetworkFields (dia); LABEL (L"", L"Structure settings:") NATURAL (L"Number of rows", L"10") NATURAL (L"Number of columns", L"10") BOOLEAN (L"Bottom row clamped", 1) LABEL (L"", L"Initial state settings:") REAL (L"left Initial weight range", L"-0.1") REAL (L"right Initial weight range", L"0.1") OK DO autoNetwork me = Network_create_rectangle_vertical (GET_REAL (L"left Activity range"), GET_REAL (L"right Activity range"), GET_REAL (L"Spreading rate"), GET_REAL (L"Self-excitation"), GET_REAL (L"left Weight range"), GET_REAL (L"right Weight range"), GET_REAL (L"Learning rate"), GET_REAL (L"Leak"), GET_INTEGER (L"Number of rows"), GET_INTEGER (L"Number of columns"), GET_INTEGER (L"Bottom row clamped"), GET_REAL (L"left Initial weight range"), GET_REAL (L"right Initial weight range")); praat_new (me.transfer(), L"rectangle_", Melder_integer (GET_INTEGER (L"Number of rows")), L"_", Melder_integer (GET_INTEGER (L"Number of columns"))); END FORM (Network_addConnection, L"Network: Add connection", 0) NATURAL (L"From node", L"1") NATURAL (L"To node", L"2") REAL (L"Weight", L"0.0") REAL (L"Plasticity", L"1.0") OK DO LOOP { iam_LOOP (Network); me -> f_addConnection (GET_INTEGER (L"From node"), GET_INTEGER (L"To node"), GET_REAL (L"Weight"), GET_REAL (L"Plasticity")); therror praat_dataChanged (me); } END FORM (Network_addNode, L"Network: Add node", 0) REAL (L"x", L"5.0") REAL (L"y", L"5.0") REAL (L"Activity", L"0.0") BOOLEAN (L"Clamping", 0) OK DO LOOP { iam_LOOP (Network); me -> f_addNode (GET_REAL (L"x"), GET_REAL (L"y"), GET_REAL (L"Activity"), GET_INTEGER (L"Clamping")); therror praat_dataChanged (me); } END FORM (Network_draw, L"Draw Network", 0) BOOLEAN (L"Colour", 1) OK DO autoPraatPicture picture; LOOP { iam_LOOP (Network); me -> f_draw (GRAPHICS, GET_INTEGER (L"Colour")); } END FORM (Network_getActivity, L"Network: Get activity", 0) NATURAL (L"Node", L"1") OK DO iam_ONLY (Network); double activity = me -> f_getActivity (GET_INTEGER (L"Node")); therror Melder_information (Melder_double (activity)); END FORM (Network_getWeight, L"Network: Get weight", 0) NATURAL (L"Connection", L"1") OK DO iam_ONLY (Network); double weight = me -> f_getWeight (GET_INTEGER (L"Connection")); therror Melder_information (Melder_double (weight)); END FORM (Network_normalizeActivities, L"Network: Normalize activities", 0) INTEGER (L"From node", L"1") INTEGER (L"To node", L"0 (= all)") OK DO LOOP { iam_LOOP (Network); me -> f_normalizeActivities (GET_INTEGER (L"From node"), GET_INTEGER (L"To node")); therror praat_dataChanged (me); } END FORM (Network_setActivationSpreadingRule, L"Network: Set activation spreading rule", 0) RADIO_ENUM (L"Activation spreading rule", kNetwork_activationSpreadingRule, DEFAULT) OK iam_ONLY (Network); SET_ENUM (L"Activation spreading rule", kNetwork_activationSpreadingRule, my d_activationSpreadingRule); DO iam_ONLY (Network); my f_setActivationSpreadingRule (GET_ENUM (kNetwork_activationSpreadingRule, L"Activation spreading rule")); praat_dataChanged (me); END FORM (Network_setActivity, L"Network: Set activity", 0) NATURAL (L"Node", L"1") REAL (L"Activity", L"1.0") OK DO LOOP { iam_LOOP (Network); me -> f_setActivity (GET_INTEGER (L"Node"), GET_REAL (L"Activity")); therror praat_dataChanged (me); } END FORM (Network_setClamping, L"Network: Set clamping", 0) NATURAL (L"Node", L"1") BOOLEAN (L"Clamping", 1) OK DO LOOP { iam_LOOP (Network); me -> f_setClamping (GET_INTEGER (L"Node"), GET_INTEGER (L"Clamping")); therror praat_dataChanged (me); } END FORM (Network_setWeight, L"Network: Set weight", 0) NATURAL (L"Connection", L"1") REAL (L"Weight", L"1.0") OK DO LOOP { iam_LOOP (Network); me -> f_setWeight (GET_INTEGER (L"Connection"), GET_REAL (L"Weight")); therror praat_dataChanged (me); } END FORM (Network_setWeightUpdateRule, L"Network: Set weight update rule", 0) RADIO_ENUM (L"Weight update rule", kNetwork_weightUpdateRule, DEFAULT) OK iam_ONLY (Network); SET_ENUM (L"Weight update rule", kNetwork_weightUpdateRule, my d_weightUpdateRule); DO iam_ONLY (Network); my f_setWeightUpdateRule (GET_ENUM (kNetwork_weightUpdateRule, L"Weight update rule")); praat_dataChanged (me); END FORM (Network_spreadActivities, L"Network: Spread activities", 0) NATURAL (L"Number of steps", L"20") OK DO LOOP { iam_LOOP (Network); me -> f_spreadActivities (GET_INTEGER (L"Number of steps")); praat_dataChanged (me); } END DIRECT (Network_updateWeights) LOOP { iam_LOOP (Network); me -> f_updateWeights (); praat_dataChanged (me); } END FORM (Network_zeroActivities, L"Network: Zero activities", 0) INTEGER (L"From node", L"1") INTEGER (L"To node", L"0 (= all)") OK DO LOOP { iam (Network); me -> f_zeroActivities (GET_INTEGER (L"From node"), GET_INTEGER (L"To node")); therror praat_dataChanged (me); } END /***** OTGRAMMAR *****/ FORM (Create_metrics_grammar, L"Create metrics grammar", 0) OPTIONMENU (L"Initial ranking", 1) OPTION (L"Equal") OPTION (L"Foot form high") OPTION (L"WSP high") OPTIONMENU (L"Trochaicity constraint", 1) OPTION (L"FtNonfinal") OPTION (L"Trochaic") BOOLEAN (L"Include FootBimoraic", 0) BOOLEAN (L"Include FootBisyllabic", 0) BOOLEAN (L"Include Peripheral", 0) OPTIONMENU (L"Nonfinality constraint", 1) OPTION (L"Nonfinal") OPTION (L"MainNonfinal") OPTION (L"HeadNonfinal") BOOLEAN (L"Overt forms have secondary stress", 1) BOOLEAN (L"Include *Clash and *Lapse", 0) BOOLEAN (L"Include codas", 0) OK DO praat_new (OTGrammar_create_metrics (GET_INTEGER (L"Initial ranking"), GET_INTEGER (L"Trochaicity constraint"), GET_INTEGER (L"Include FootBimoraic"), GET_INTEGER (L"Include FootBisyllabic"), GET_INTEGER (L"Include Peripheral"), GET_INTEGER (L"Nonfinality constraint"), GET_INTEGER (L"Overt forms have secondary stress"), GET_INTEGER (L"Include *Clash and *Lapse"), GET_INTEGER (L"Include codas")), GET_STRING (L"Initial ranking")); END DIRECT (Create_NoCoda_grammar) autoOTGrammar me = OTGrammar_create_NoCoda_grammar (); praat_new (me.transfer(), L"NoCoda"); END DIRECT (Create_NPA_grammar) autoOTGrammar me = OTGrammar_create_NPA_grammar (); praat_new (me.transfer(), L"assimilation"); END DIRECT (Create_NPA_distribution) autoPairDistribution me = OTGrammar_create_NPA_distribution (); praat_new (me.transfer(), L"assimilation"); END FORM (Create_tongue_root_grammar, L"Create tongue-root grammar", L"Create tongue-root grammar...") RADIO (L"Constraint set", 1) RADIOBUTTON (L"Five") RADIOBUTTON (L"Nine") RADIO (L"Ranking", 3) RADIOBUTTON (L"Equal") RADIOBUTTON (L"Random") RADIOBUTTON (L"Infant") RADIOBUTTON (L"Wolof") OK DO autoOTGrammar me = OTGrammar_create_tongueRoot_grammar (GET_INTEGER (L"Constraint set"), GET_INTEGER (L"Ranking")); praat_new (me.transfer(), GET_STRING (L"Ranking")); END FORM (OTGrammar_drawTableau, L"Draw tableau", L"OT learning") SENTENCE (L"Input string", L"") OK DO autoPraatPicture picture; LOOP { iam (OTGrammar); OTGrammar_drawTableau (me, GRAPHICS, false, GET_STRING (L"Input string")); } END FORM (OTGrammar_drawTableau_narrowly, L"Draw tableau (narrowly)", L"OT learning") SENTENCE (L"Input string", L"") OK DO autoPraatPicture picture; LOOP { iam (OTGrammar); OTGrammar_drawTableau (me, GRAPHICS, true, GET_STRING (L"Input string")); } END DIRECT (OTGrammar_edit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot edit from batch."); LOOP { iam (OTGrammar); autoOTGrammarEditor editor = OTGrammarEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); praat_installEditor (editor.transfer(), IOBJECT); therror } END FORM (OTGrammar_evaluate, L"OTGrammar: Evaluate", 0) REAL (L"Evaluation noise", L"2.0") OK DO LOOP { iam (OTGrammar); OTGrammar_newDisharmonies (me, GET_REAL (L"Evaluation noise")); praat_dataChanged (me); } END FORM (OTGrammar_generateInputs, L"Generate inputs", L"OTGrammar: Generate inputs...") NATURAL (L"Number of trials", L"1000") OK DO LOOP { iam (OTGrammar); autoStrings thee = OTGrammar_generateInputs (me, GET_INTEGER (L"Number of trials")); praat_new (thee.transfer(), my name, L"_in"); } END FORM (OTGrammar_getCandidate, L"Get candidate", 0) NATURAL (L"Tableau number", L"1") NATURAL (L"Candidate number", L"1") OK DO iam_ONLY (OTGrammar); OTGrammarTableau tableau; long itab = GET_INTEGER (L"Tableau number"), icand = GET_INTEGER (L"Candidate number"); if (itab > my numberOfTableaus) Melder_throw ("The specified tableau number should not exceed the number of tableaus."); tableau = & my tableaus [itab]; if (icand > tableau -> numberOfCandidates) Melder_throw ("The specified candidate should not exceed the number of candidates."); Melder_information (tableau -> candidates [icand]. output); END FORM (OTGrammar_getConstraint, L"Get constraint name", 0) NATURAL (L"Constraint number", L"1") OK DO iam_ONLY (OTGrammar); long icons = GET_INTEGER (L"Constraint number"); if (icons > my numberOfConstraints) Melder_throw ("The specified constraint number should not exceed the number of constraints."); Melder_information (my constraints [icons]. name); END FORM (OTGrammar_getDisharmony, L"Get disharmony", 0) NATURAL (L"Constraint number", L"1") OK DO iam_ONLY (OTGrammar); long icons = GET_INTEGER (L"Constraint number"); if (icons > my numberOfConstraints) Melder_throw ("The specified constraint number should not exceed the number of constraints."); Melder_information (Melder_double (my constraints [icons]. disharmony)); END FORM (OTGrammar_getInput, L"Get input", 0) NATURAL (L"Tableau number", L"1") OK DO iam_ONLY (OTGrammar); long itab = GET_INTEGER (L"Tableau number"); if (itab > my numberOfTableaus) Melder_throw ("The specified tableau number should not exceed the number of tableaus."); Melder_information (my tableaus [itab]. input); END DIRECT (OTGrammar_getInputs) LOOP { iam (OTGrammar); autoStrings thee = OTGrammar_getInputs (me); praat_new (thee.transfer(), my name, L"_in"); } END FORM (OTGrammar_getInterpretiveParse, L"OTGrammar: Interpretive parse", 0) SENTENCE (L"Partial output", L"") OK DO iam_ONLY (OTGrammar); long bestInput, bestOutput; OTGrammar_getInterpretiveParse (me, GET_STRING (L"Partial output"), & bestInput, & bestOutput); therror Melder_information (L"Best input = ", Melder_integer (bestInput), L": ", my tableaus [bestInput]. input, L"\nBest output = ", Melder_integer (bestOutput), L": ", my tableaus [bestInput]. candidates [bestOutput]. output); END FORM (OTGrammar_getNumberOfCandidates, L"Get number of candidates", 0) NATURAL (L"Tableau number", L"1") OK DO iam_ONLY (OTGrammar); long itab = GET_INTEGER (L"Tableau number"); if (itab > my numberOfTableaus) Melder_throw ("The specified tableau number should not exceed the number of tableaus."); Melder_information (Melder_integer (my tableaus [itab]. numberOfCandidates)); END DIRECT (OTGrammar_getNumberOfConstraints) iam_ONLY (OTGrammar); Melder_information (Melder_integer (my numberOfConstraints)); END FORM (OTGrammar_getNumberOfOptimalCandidates, L"Get number of optimal candidates", 0) NATURAL (L"Tableau number", L"1") OK DO iam_ONLY (OTGrammar); long itab = GET_INTEGER (L"Tableau number"); if (itab > my numberOfTableaus) Melder_throw ("The specified tableau number should not exceed the number of tableaus."); Melder_information (Melder_integer (OTGrammar_getNumberOfOptimalCandidates (me, itab))); END DIRECT (OTGrammar_getNumberOfTableaus) iam_ONLY (OTGrammar); Melder_information (Melder_integer (my numberOfTableaus)); END FORM (OTGrammar_getNumberOfViolations, L"Get number of violations", 0) NATURAL (L"Tableau number", L"1") NATURAL (L"Candidate number", L"1") NATURAL (L"Constraint number", L"1") OK DO iam_ONLY (OTGrammar); long itab = GET_INTEGER (L"Tableau number"), icand = GET_INTEGER (L"Candidate number"), icons = GET_INTEGER (L"Constraint number"); if (itab > my numberOfTableaus) Melder_throw ("The specified tableau number should not exceed the number of tableaus."); if (icand > my tableaus [itab]. numberOfCandidates) Melder_throw ("The specified candidate should not exceed the number of candidates."); if (icons > my numberOfConstraints) Melder_throw ("The specified constraint number should not exceed the number of constraints."); Melder_information (Melder_integer (my tableaus [itab]. candidates [icand]. marks [icons])); END FORM (OTGrammar_compareCandidates, L"Compare candidates", 0) NATURAL (L"Tableau number 1", L"1") NATURAL (L"Candidate number 1", L"1") NATURAL (L"Tableau number 2", L"1") NATURAL (L"Candidate number 2", L"2") OK DO iam_ONLY (OTGrammar); long itab1 = GET_INTEGER (L"Tableau number 1"), icand1 = GET_INTEGER (L"Candidate number 1"); long itab2 = GET_INTEGER (L"Tableau number 2"), icand2 = GET_INTEGER (L"Candidate number 2"); if (itab1 > my numberOfTableaus) Melder_throw ("The specified tableau (number 1) should not exceed the number of tableaus."); if (itab2 > my numberOfTableaus) Melder_throw ("The specified tableau (number 2) should not exceed the number of tableaus."); if (icand1 > my tableaus [itab1]. numberOfCandidates) Melder_throw ("The specified candidate (number 1) should not exceed the number of candidates for this tableau."); if (icand2 > my tableaus [itab1]. numberOfCandidates) Melder_throw ("The specified candidate (number 2) should not exceed the number of candidates for this tableau."); Melder_information (Melder_integer (OTGrammar_compareCandidates (me, itab1, icand1, itab2, icand2))); END FORM (OTGrammar_getRankingValue, L"Get ranking value", 0) NATURAL (L"Constraint number", L"1") OK DO iam_ONLY (OTGrammar); long icons = GET_INTEGER (L"Constraint number"); if (icons > my numberOfConstraints) Melder_throw ("The specified constraint number should not exceed the number of constraints."); Melder_information (Melder_double (my constraints [icons]. ranking)); END FORM (OTGrammar_getWinner, L"Get winner", 0) NATURAL (L"Tableau", L"1") OK DO iam_ONLY (OTGrammar); long itab = GET_INTEGER (L"Tableau"); if (itab > my numberOfTableaus) Melder_throw ("The specified tableau number should not exceed the number of tableaus."); Melder_information (Melder_integer (OTGrammar_getWinner (me, itab))); END FORM (OTGrammar_inputToOutput, L"OTGrammar: Input to output", L"OTGrammar: Input to output...") SENTENCE (L"Input form", L"") REAL (L"Evaluation noise", L"2.0") OK DO iam_ONLY (OTGrammar); wchar output [100]; OTGrammar_inputToOutput (me, GET_STRING (L"Input form"), output, GET_REAL (L"Evaluation noise")); Melder_information (output); praat_dataChanged (me); END FORM (OTGrammar_inputToOutputs, L"OTGrammar: Input to outputs", L"OTGrammar: Input to outputs...") NATURAL (L"Trials", L"1000") REAL (L"Evaluation noise", L"2.0") SENTENCE (L"Input form", L"") OK DO iam_ONLY (OTGrammar); autoStrings thee = OTGrammar_inputToOutputs (me, GET_STRING (L"Input form"), GET_INTEGER (L"Trials"), GET_REAL (L"Evaluation noise")); praat_new (thee.transfer(), my name, L"_out"); praat_dataChanged (me); END FORM (OTGrammar_inputsToOutputs, L"OTGrammar: Inputs to outputs", L"OTGrammar: Inputs to outputs...") REAL (L"Evaluation noise", L"2.0") OK DO iam_ONLY (OTGrammar); thouart_ONLY (Strings); autoStrings him = OTGrammar_inputsToOutputs (me, thee, GET_REAL (L"Evaluation noise")); praat_new (him.transfer(), my name, L"_out"); praat_dataChanged (me); END FORM (OTGrammar_isCandidateGrammatical, L"Is candidate grammatical?", 0) NATURAL (L"Tableau", L"1") NATURAL (L"Candidate", L"1") OK DO iam_ONLY (OTGrammar); long itab = GET_INTEGER (L"Tableau"); if (itab > my numberOfTableaus) Melder_throw ("The specified tableau number should not exceed the number of tableaus."); long icand = GET_INTEGER (L"Candidate"); if (icand > my tableaus [itab]. numberOfCandidates) Melder_throw ("The specified candidate should not exceed the number of candidates."); Melder_information (Melder_integer (OTGrammar_isCandidateGrammatical (me, itab, icand))); END FORM (OTGrammar_isCandidateSinglyGrammatical, L"Is candidate singly grammatical?", 0) NATURAL (L"Tableau", L"1") NATURAL (L"Candidate", L"1") OK DO iam_ONLY (OTGrammar); long itab = GET_INTEGER (L"Tableau"); if (itab > my numberOfTableaus) Melder_throw ("The specified tableau number should not exceed the number of tableaus."); long icand = GET_INTEGER (L"Candidate"); if (icand > my tableaus [itab]. numberOfCandidates) Melder_throw ("The specified candidate should not exceed the number of candidates."); Melder_information (Melder_integer (OTGrammar_isCandidateSinglyGrammatical (me, itab, icand))); END FORM (OTGrammar_isPartialOutputGrammatical, L"Is partial output grammatical?", 0) SENTENCE (L"Partial output", L"") OK DO iam_ONLY (OTGrammar); Melder_information (Melder_integer (OTGrammar_isPartialOutputGrammatical (me, GET_STRING (L"Partial output")))); END FORM (OTGrammar_isPartialOutputSinglyGrammatical, L"Is partial output singly grammatical?", 0) SENTENCE (L"Partial output", L"") OK DO iam_ONLY (OTGrammar); Melder_information (Melder_integer (OTGrammar_isPartialOutputSinglyGrammatical (me, GET_STRING (L"Partial output")))); END FORM (OTGrammar_learn, L"OTGrammar: Learn", L"OTGrammar & 2 Strings: Learn...") REAL (L"Evaluation noise", L"2.0") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) REAL (L"Plasticity", L"0.1") REAL (L"Rel. plasticity spreading", L"0.1") BOOLEAN (L"Honour local rankings", 1) NATURAL (L"Number of chews", L"1") OK DO iam_ONLY (OTGrammar); Strings inputs = NULL, outputs = NULL; WHERE (SELECTED && CLASS == classStrings) { if (! inputs) inputs = (Strings) OBJECT; else outputs = (Strings) OBJECT; } try { OTGrammar_learn (me, inputs, outputs, GET_REAL (L"Evaluation noise"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Honour local rankings"), GET_REAL (L"Plasticity"), GET_REAL (L"Rel. plasticity spreading"), GET_INTEGER (L"Number of chews")); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); // partial change throw; } END FORM (OTGrammar_learnFromPartialOutputs, L"OTGrammar: Learn from partial adult outputs", 0) REAL (L"Evaluation noise", L"2.0") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) REAL (L"Plasticity", L"0.1") REAL (L"Rel. plasticity spreading", L"0.1") BOOLEAN (L"Honour local rankings", 1) NATURAL (L"Number of chews", L"1") INTEGER (L"Store history every", L"0") OK DO iam_ONLY (OTGrammar); thouart_ONLY (Strings); OTHistory history = NULL; try { OTGrammar_learnFromPartialOutputs (me, thee, GET_REAL (L"Evaluation noise"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Honour local rankings"), GET_REAL (L"Plasticity"), GET_REAL (L"Rel. plasticity spreading"), GET_INTEGER (L"Number of chews"), GET_INTEGER (L"Store history every"), & history); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); // e.g. in case of partial learning Melder_flushError (NULL); // trickle down to save history } if (history) praat_new (history, my name); END FORM (OTGrammar_learnOne, L"OTGrammar: Learn one", L"OTGrammar: Learn one...") SENTENCE (L"Input string", L"") SENTENCE (L"Output string", L"") REAL (L"Evaluation noise", L"2.0") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) REAL (L"Plasticity", L"0.1") REAL (L"Rel. plasticity spreading", L"0.1") BOOLEAN (L"Honour local rankings", 1) OK DO LOOP try { iam (OTGrammar); OTGrammar_learnOne (me, GET_STRING (L"Input string"), GET_STRING (L"Output string"), GET_REAL (L"Evaluation noise"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Honour local rankings"), GET_REAL (L"Plasticity"), GET_REAL (L"Rel. plasticity spreading"), TRUE, TRUE, NULL); praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (OBJECT); throw; } END FORM (OTGrammar_learnOneFromPartialOutput, L"OTGrammar: Learn one from partial adult output", 0) LABEL (L"", L"Partial adult surface form (e.g. overt form):") SENTENCE (L"Partial output", L"") REAL (L"Evaluation noise", L"2.0") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) REAL (L"Plasticity", L"0.1") REAL (L"Rel. plasticity spreading", L"0.1") BOOLEAN (L"Honour local rankings", 1) NATURAL (L"Number of chews", L"1") OK DO LOOP try { iam (OTGrammar); OTGrammar_learnOneFromPartialOutput (me, GET_STRING (L"Partial output"), GET_REAL (L"Evaluation noise"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Honour local rankings"), GET_REAL (L"Plasticity"), GET_REAL (L"Rel. plasticity spreading"), GET_INTEGER (L"Number of chews"), TRUE); praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (OBJECT); throw; } END FORM (OTGrammar_removeConstraint, L"OTGrammar: Remove constraint", 0) SENTENCE (L"Constraint name", L"") OK DO LOOP { iam (OTGrammar); OTGrammar_removeConstraint (me, GET_STRING (L"Constraint name")); therror praat_dataChanged (me); } END FORM (OTGrammar_removeHarmonicallyBoundedCandidates, L"OTGrammar: Remove harmonically bounded candidates", 0) BOOLEAN (L"Singly", 0) OK DO LOOP { iam (OTGrammar); OTGrammar_removeHarmonicallyBoundedCandidates (me, GET_INTEGER (L"Singly")); therror praat_dataChanged (me); } END FORM (OTGrammar_resetAllRankings, L"OTGrammar: Reset all rankings", 0) REAL (L"Ranking", L"100.0") OK DO LOOP { iam (OTGrammar); OTGrammar_reset (me, GET_REAL (L"Ranking")); praat_dataChanged (me); } END FORM (OTGrammar_resetToRandomTotalRanking, L"OTGrammar: Reset to random total ranking", 0) REAL (L"Maximum ranking", L"100.0") POSITIVE (L"Ranking distance", L"1.0") OK DO LOOP { iam (OTGrammar); OTGrammar_resetToRandomTotalRanking (me, GET_REAL (L"Maximum ranking"), GET_REAL (L"Ranking distance")); praat_dataChanged (me); } END FORM (OTGrammar_setConstraintPlasticity, L"OTGrammar: Set constraint plasticity", 0) NATURAL (L"Constraint", L"1") REAL (L"Plasticity", L"1.0") OK DO LOOP { iam (OTGrammar); OTGrammar_setConstraintPlasticity (me, GET_INTEGER (L"Constraint"), GET_REAL (L"Plasticity")); praat_dataChanged (OBJECT); } END FORM (OTGrammar_setDecisionStrategy, L"OTGrammar: Set decision strategy", 0) RADIO_ENUM (L"Decision strategy", kOTGrammar_decisionStrategy, DEFAULT) OK iam_ONLY (OTGrammar); SET_ENUM (L"Decision strategy", kOTGrammar_decisionStrategy, my decisionStrategy); DO iam_ONLY (OTGrammar); my decisionStrategy = GET_ENUM (kOTGrammar_decisionStrategy, L"Decision strategy"); praat_dataChanged (me); END FORM (OTGrammar_setLeak, L"OTGrammar: Set leak", 0) REAL (L"Leak", L"0.0") OK iam_ONLY (OTGrammar); SET_REAL (L"Leak", my leak); DO iam_ONLY (OTGrammar); my leak = GET_REAL (L"Leak"); praat_dataChanged (me); END FORM (OTGrammar_setRanking, L"OTGrammar: Set ranking", 0) NATURAL (L"Constraint", L"1") REAL (L"Ranking", L"100.0") REAL (L"Disharmony", L"100.0") OK DO LOOP { iam (OTGrammar); OTGrammar_setRanking (me, GET_INTEGER (L"Constraint"), GET_REAL (L"Ranking"), GET_REAL (L"Disharmony")); therror praat_dataChanged (me); } END FORM (OTGrammar_Distributions_getFractionCorrect, L"OTGrammar & Distributions: Get fraction correct...", 0) NATURAL (L"Column number", L"1") REAL (L"Evaluation noise", L"2.0") INTEGER (L"Replications", L"100000") OK DO iam_ONLY (OTGrammar); thouart_ONLY (Distributions); double result = OTGrammar_Distributions_getFractionCorrect (me, thee, GET_INTEGER (L"Column number"), GET_REAL (L"Evaluation noise"), GET_INTEGER (L"Replications")); therror praat_dataChanged (me); Melder_informationReal (result, NULL); END FORM (OTGrammar_Distributions_learnFromPartialOutputs, L"OTGrammar & Distributions: Learn from partial outputs", L"OT learning 6. Shortcut to OT learning") NATURAL (L"Column number", L"1") REAL (L"Evaluation noise", L"2.0") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) REAL (L"Initial plasticity", L"1.0") NATURAL (L"Replications per plasticity", L"100000") REAL (L"Plasticity decrement", L"0.1") NATURAL (L"Number of plasticities", L"4") REAL (L"Rel. plasticity spreading", L"0.1") BOOLEAN (L"Honour local rankings", 1) NATURAL (L"Number of chews", L"1") INTEGER (L"Store history every", L"0") OK DO iam_ONLY (OTGrammar); thouart_ONLY (Distributions); OTHistory history = NULL; try { OTGrammar_Distributions_learnFromPartialOutputs (me, thee, GET_INTEGER (L"Column number"), GET_REAL (L"Evaluation noise"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Honour local rankings"), GET_REAL (L"Initial plasticity"), GET_INTEGER (L"Replications per plasticity"), GET_REAL (L"Plasticity decrement"), GET_INTEGER (L"Number of plasticities"), GET_REAL (L"Rel. plasticity spreading"), GET_INTEGER (L"Number of chews"), GET_INTEGER (L"Store history every"), & history); praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); Melder_flushError (NULL); } if (history) praat_new (history, my name); END FORM (OTGrammar_Distributions_listObligatoryRankings, L"OTGrammar & Distributions: Get fraction correct...", 0) NATURAL (L"Column number", L"1") OK DO iam_ONLY (OTGrammar); thouart_ONLY (Distributions); OTGrammar_Distributions_listObligatoryRankings (me, thee, GET_INTEGER (L"Column number")); therror END FORM (OTGrammar_PairDistribution_findPositiveWeights, L"OTGrammar & PairDistribution: Find positive weights", L"OTGrammar & PairDistribution: Find positive weights...") POSITIVE (L"Weight floor", L"1.0") POSITIVE (L"Margin of separation", L"1.0") OK DO iam_ONLY (OTGrammar); thouart_ONLY (PairDistribution); OTGrammar_PairDistribution_findPositiveWeights_e (me, thee, GET_REAL (L"Weight floor"), GET_REAL (L"Margin of separation")); therror praat_dataChanged (me); END FORM (OTGrammar_PairDistribution_getFractionCorrect, L"OTGrammar & PairDistribution: Get fraction correct...", 0) REAL (L"Evaluation noise", L"2.0") INTEGER (L"Replications", L"100000") OK DO iam_ONLY (OTGrammar); thouart_ONLY (PairDistribution); double result; try { result = OTGrammar_PairDistribution_getFractionCorrect (me, thee, GET_REAL (L"Evaluation noise"), GET_INTEGER (L"Replications")); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); throw; } Melder_informationReal (result, NULL); END FORM (OTGrammar_PairDistribution_getMinimumNumberCorrect, L"OTGrammar & PairDistribution: Get minimum number correct...", 0) REAL (L"Evaluation noise", L"2.0") INTEGER (L"Replications per input", L"1000") OK DO iam_ONLY (OTGrammar); thouart_ONLY (PairDistribution); long result; try { result = OTGrammar_PairDistribution_getMinimumNumberCorrect (me, thee, GET_REAL (L"Evaluation noise"), GET_INTEGER (L"Replications per input")); praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); throw; } Melder_information (Melder_integer (result)); END FORM (OTGrammar_PairDistribution_learn, L"OTGrammar & PairDistribution: Learn", L"OT learning 6. Shortcut to OT learning") REAL (L"Evaluation noise", L"2.0") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) POSITIVE (L"Initial plasticity", L"1.0") NATURAL (L"Replications per plasticity", L"100000") REAL (L"Plasticity decrement", L"0.1") NATURAL (L"Number of plasticities", L"4") REAL (L"Rel. plasticity spreading", L"0.1") BOOLEAN (L"Honour local rankings", 1) NATURAL (L"Number of chews", L"1") OK DO iam_ONLY (OTGrammar); thouart_ONLY (PairDistribution); try { OTGrammar_PairDistribution_learn (me, thee, GET_REAL (L"Evaluation noise"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Honour local rankings"), GET_REAL (L"Initial plasticity"), GET_INTEGER (L"Replications per plasticity"), GET_REAL (L"Plasticity decrement"), GET_INTEGER (L"Number of plasticities"), GET_REAL (L"Rel. plasticity spreading"), GET_INTEGER (L"Number of chews")); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); throw; } END DIRECT (OTGrammar_PairDistribution_listObligatoryRankings) iam_ONLY (OTGrammar); thouart_ONLY (PairDistribution); OTGrammar_PairDistribution_listObligatoryRankings (me, thee); therror END FORM (OTGrammar_to_Distributions, L"OTGrammar: Compute output distributions", L"OTGrammar: To output Distributions...") NATURAL (L"Trials per input", L"100000") REAL (L"Evaluation noise", L"2.0") OK DO LOOP { iam (OTGrammar); try { autoDistributions thee = OTGrammar_to_Distribution (me, GET_INTEGER (L"Trials per input"), GET_REAL (L"Evaluation noise")); praat_new (thee.transfer(), my name, L"_out"); praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); throw; } } END FORM (OTGrammar_to_PairDistribution, L"OTGrammar: Compute output distributions", 0) NATURAL (L"Trials per input", L"100000") REAL (L"Evaluation noise", L"2.0") OK DO LOOP try { iam (OTGrammar); autoPairDistribution thee = OTGrammar_to_PairDistribution (me, GET_INTEGER (L"Trials per input"), GET_REAL (L"Evaluation noise")); praat_new (thee.transfer(), my name, L"_out"); praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (OBJECT); throw; } END DIRECT (OTGrammar_measureTypology) LOOP try { iam (OTGrammar); autoDistributions thee = OTGrammar_measureTypology (me); praat_new (thee.transfer(), my name, L"_out"); praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (OBJECT); throw; } END FORM_WRITE (OTGrammar_writeToHeaderlessSpreadsheetFile, L"Write OTGrammar to spreadsheet", 0, L"txt") iam_ONLY (OTGrammar); OTGrammar_writeToHeaderlessSpreadsheetFile (me, file); therror END FORM (OTMulti_drawTableau, L"Draw tableau", L"OT learning") SENTENCE (L"Partial form 1", L"") SENTENCE (L"Partial form 2", L"") BOOLEAN (L"Show disharmonies", 1) OK DO autoPraatPicture picture; LOOP { iam (OTMulti); OTMulti_drawTableau (me, GRAPHICS, GET_STRING (L"Partial form 1"), GET_STRING (L"Partial form 2"), false, GET_INTEGER (L"Show disharmonies")); } END FORM (OTMulti_drawTableau_narrowly, L"Draw tableau (narrowly)", L"OT learning") SENTENCE (L"Partial form 1", L"") SENTENCE (L"Partial form 2", L"") BOOLEAN (L"Show disharmonies", 1) OK DO autoPraatPicture picture; LOOP { iam (OTMulti); OTMulti_drawTableau (me, GRAPHICS, GET_STRING (L"Partial form 1"), GET_STRING (L"Partial form 2"), true, GET_INTEGER (L"Show disharmonies")); } END DIRECT (OTMulti_edit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot edit an OTMulti from batch."); LOOP { iam (OTMulti); autoOTMultiEditor editor = OTMultiEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); praat_installEditor (editor.transfer(), IOBJECT); therror } END FORM (OTMulti_evaluate, L"OTMulti: Evaluate", 0) REAL (L"Evaluation noise", L"2.0") OK DO iam_ONLY (OTMulti); OTMulti_newDisharmonies (me, GET_REAL (L"Evaluation noise")); praat_dataChanged (me); END FORM (OTMulti_generateOptimalForms, L"OTMulti: Generate optimal forms", 0) SENTENCE (L"Partial form 1", L"") SENTENCE (L"Partial form 2", L"") NATURAL (L"Number of trials", L"1000") REAL (L"Evaluation noise", L"2.0") OK DO iam_ONLY (OTMulti); autoStrings thee = OTMulti_generateOptimalForms (me, GET_STRING (L"Partial form 1"), GET_STRING (L"Partial form 2"), GET_INTEGER (L"Number of trials"), GET_REAL (L"Evaluation noise")); praat_new (thee.transfer(), my name, L"_out"); praat_dataChanged (me); END FORM (OTMulti_getCandidate, L"Get candidate", 0) NATURAL (L"Candidate", L"1") OK DO iam_ONLY (OTMulti); long icand = GET_INTEGER (L"Candidate"); if (icand > my numberOfCandidates) Melder_throw ("The specified candidate number should not exceed the number of candidates."); Melder_information (my candidates [icand]. string); END FORM (OTMulti_getConstraint, L"Get constraint name", 0) NATURAL (L"Constraint number", L"1") OK DO iam_ONLY (OTMulti); long icons = GET_INTEGER (L"Constraint number"); if (icons > my numberOfConstraints) Melder_throw ("The specified constraint number should not exceed the number of constraints."); Melder_information (my constraints [icons]. name); END FORM (OTMulti_getConstraintIndexFromName, L"OTMulti: Get constraint number", 0) SENTENCE (L"Constraint name", L"") OK DO iam_ONLY (OTMulti); Melder_information (Melder_integer (OTMulti_getConstraintIndexFromName (me, GET_STRING (L"Constraint name")))); END FORM (OTMulti_getDisharmony, L"Get disharmony", 0) NATURAL (L"Constraint number", L"1") OK DO iam_ONLY (OTMulti); long icons = GET_INTEGER (L"Constraint number"); if (icons > my numberOfConstraints) Melder_throw ("The specified constraint number should not exceed the number of constraints."); Melder_information (Melder_double (my constraints [icons]. disharmony)); END DIRECT (OTMulti_getNumberOfCandidates) iam_ONLY (OTMulti); Melder_information (Melder_integer (my numberOfCandidates)); END DIRECT (OTMulti_getNumberOfConstraints) iam_ONLY (OTMulti); Melder_information (Melder_integer (my numberOfConstraints)); END FORM (OTMulti_getNumberOfViolations, L"Get number of violations", 0) NATURAL (L"Candidate number", L"1") NATURAL (L"Constraint number", L"1") OK DO iam_ONLY (OTMulti); long icand = GET_INTEGER (L"Candidate number"); if (icand > my numberOfCandidates) Melder_throw ("The specified candidate number should not exceed the number of candidates."); long icons = GET_INTEGER (L"Constraint number"); if (icons > my numberOfConstraints) Melder_throw ("The specified constraint number should not exceed the number of constraints."); Melder_information (Melder_integer (my candidates [icand]. marks [icons])); END FORM (OTMulti_getRankingValue, L"Get ranking value", 0) NATURAL (L"Constraint number", L"1") OK DO iam_ONLY (OTMulti); long icons = GET_INTEGER (L"Constraint number"); if (icons > my numberOfConstraints) Melder_throw ("The specified constraint number should not exceed the number of constraints."); Melder_information (Melder_double (my constraints [icons]. ranking)); END FORM (OTMulti_getWinner, L"OTMulti: Get winner", 0) SENTENCE (L"Partial form 1", L"") SENTENCE (L"Partial form 2", L"") OK DO iam_ONLY (OTMulti); Melder_information (Melder_integer (OTMulti_getWinner (me, GET_STRING (L"Partial form 1"), GET_STRING (L"Partial form 2")))); END FORM (OTMulti_generateOptimalForm, L"OTMulti: Generate optimal form", 0) SENTENCE (L"Partial form 1", L"") SENTENCE (L"Partial form 2", L"") REAL (L"Evaluation noise", L"2.0") OK DO iam_ONLY (OTMulti); wchar output [100]; OTMulti_generateOptimalForm (me, GET_STRING (L"Partial form 1"), GET_STRING (L"Partial form 2"), output, GET_REAL (L"Evaluation noise")); therror Melder_information (output); praat_dataChanged (me); END FORM (OTMulti_learnOne, L"OTMulti: Learn one", 0) SENTENCE (L"Partial form 1", L"") SENTENCE (L"Partial form 2", L"") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) OPTIONMENU (L"Direction", 3) OPTION (L"forward") OPTION (L"backward") OPTION (L"bidirectionally") POSITIVE (L"Plasticity", L"0.1") REAL (L"Rel. plasticity spreading", L"0.1") OK DO LOOP { iam (OTMulti); try { OTMulti_learnOne (me, GET_STRING (L"Partial form 1"), GET_STRING (L"Partial form 2"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Direction"), GET_REAL (L"Plasticity"), GET_REAL (L"Rel. plasticity spreading")); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); throw; } } END FORM (OTMulti_removeConstraint, L"OTMulti: Remove constraint", 0) SENTENCE (L"Constraint name", L"") OK DO LOOP { iam (OTMulti); OTMulti_removeConstraint (me, GET_STRING (L"Constraint name")); therror praat_dataChanged (me); } END FORM (OTMulti_resetAllRankings, L"OTMulti: Reset all rankings", 0) REAL (L"Ranking", L"100.0") OK DO LOOP { iam (OTMulti); OTMulti_reset (me, GET_REAL (L"Ranking")); therror praat_dataChanged (me); } END FORM (OTMulti_setConstraintPlasticity, L"OTMulti: Set constraint plasticity", 0) NATURAL (L"Constraint", L"1") REAL (L"Plasticity", L"1.0") OK DO LOOP { iam (OTMulti); OTMulti_setConstraintPlasticity (me, GET_INTEGER (L"Constraint"), GET_REAL (L"Plasticity")); therror praat_dataChanged (me); } END FORM (OTMulti_setDecisionStrategy, L"OTMulti: Set decision strategy", 0) RADIO_ENUM (L"Decision strategy", kOTGrammar_decisionStrategy, DEFAULT) OK iam_ONLY (OTMulti); SET_ENUM (L"Decision strategy", kOTGrammar_decisionStrategy, my decisionStrategy); DO iam_ONLY (OTMulti); my decisionStrategy = GET_ENUM (kOTGrammar_decisionStrategy, L"Decision strategy"); praat_dataChanged (me); END FORM (OTMulti_setLeak, L"OTGrammar: Set leak", 0) REAL (L"Leak", L"0.0") OK iam_ONLY (OTMulti); SET_REAL (L"Leak", my leak); DO iam_ONLY (OTMulti); my leak = GET_REAL (L"Leak"); praat_dataChanged (me); END FORM (OTMulti_setRanking, L"OTMulti: Set ranking", 0) NATURAL (L"Constraint", L"1") REAL (L"Ranking", L"100.0") REAL (L"Disharmony", L"100.0") OK DO LOOP { iam (OTMulti); OTMulti_setRanking (me, GET_INTEGER (L"Constraint"), GET_REAL (L"Ranking"), GET_REAL (L"Disharmony")); therror praat_dataChanged (me); } END FORM (OTMulti_to_Distribution, L"OTMulti: Compute output distribution", 0) SENTENCE (L"Partial form 1", L"") SENTENCE (L"Partial form 2", L"") NATURAL (L"Number of trials", L"100000") POSITIVE (L"Evaluation noise", L"2.0") OK DO LOOP { iam (OTMulti); try { autoDistributions thee = OTMulti_to_Distribution (me, GET_STRING (L"Partial form 1"), GET_STRING (L"Partial form 2"), GET_INTEGER (L"Number of trials"), GET_REAL (L"Evaluation noise")); praat_new (thee.transfer(), my name, L"_out"); praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); throw; } } END FORM (OTMulti_PairDistribution_learn, L"OTMulti & PairDistribution: Learn", 0) REAL (L"Evaluation noise", L"2.0") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) OPTIONMENU (L"Direction", 3) OPTION (L"forward") OPTION (L"backward") OPTION (L"bidirectionally") POSITIVE (L"Initial plasticity", L"1.0") NATURAL (L"Replications per plasticity", L"100000") REAL (L"Plasticity decrement", L"0.1") NATURAL (L"Number of plasticities", L"4") REAL (L"Rel. plasticity spreading", L"0.1") INTEGER (L"Store history every", L"0") OK DO iam_ONLY (OTMulti); thouart_ONLY (PairDistribution); Table history = NULL; try { OTMulti_PairDistribution_learn (me, thee, GET_REAL (L"Evaluation noise"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Direction"), GET_REAL (L"Initial plasticity"), GET_INTEGER (L"Replications per plasticity"), GET_REAL (L"Plasticity decrement"), GET_INTEGER (L"Number of plasticities"), GET_REAL (L"Rel. plasticity spreading"), GET_INTEGER (L"Store history every"), & history); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); // e.g. in case of partial learning Melder_flushError (NULL); // trickle down to save history } if (history) praat_new (history, my name); END FORM (OTMulti_Strings_generateOptimalForms, L"OTGrammar: Inputs to outputs", L"OTGrammar: Inputs to outputs...") REAL (L"Evaluation noise", L"2.0") OK DO iam_ONLY (OTMulti); thouart_ONLY (Strings); autoStrings him = OTMulti_Strings_generateOptimalForms (me, thee, GET_REAL (L"Evaluation noise")); praat_new (him.transfer(), my name, L"_out"); praat_dataChanged (me); END /***** buttons *****/ void praat_uvafon_gram_init (void); void praat_uvafon_gram_init (void) { Thing_recognizeClassesByName (classNetwork, classOTGrammar, classOTHistory, classOTMulti, NULL); Thing_recognizeClassByOtherName (classOTGrammar, L"OTCase"); praat_addMenuCommand (L"Objects", L"New", L"Constraint grammars", 0, 0, 0); praat_addMenuCommand (L"Objects", L"New", L"OT learning tutorial", 0, 1, DO_OT_learning_tutorial); praat_addMenuCommand (L"Objects", L"New", L"-- tableau grammars --", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Create NoCoda grammar", 0, 1, DO_Create_NoCoda_grammar); praat_addMenuCommand (L"Objects", L"New", L"Create place assimilation grammar", 0, 1, DO_Create_NPA_grammar); praat_addMenuCommand (L"Objects", L"New", L"Create place assimilation distribution", 0, 1, DO_Create_NPA_distribution); praat_addMenuCommand (L"Objects", L"New", L"Create tongue-root grammar...", 0, 1, DO_Create_tongue_root_grammar); praat_addMenuCommand (L"Objects", L"New", L"Create metrics grammar...", 0, 1, DO_Create_metrics_grammar); praat_addAction1 (classOTGrammar, 0, L"OTGrammar help", 0, 0, DO_OTGrammar_help); praat_addAction1 (classOTGrammar, 0, L"View & Edit", 0, praat_ATTRACTIVE, DO_OTGrammar_edit); praat_addAction1 (classOTGrammar, 0, L"Edit", 0, praat_HIDDEN, DO_OTGrammar_edit); praat_addAction1 (classOTGrammar, 0, L"Draw tableau...", 0, 0, DO_OTGrammar_drawTableau); praat_addAction1 (classOTGrammar, 0, L"Draw tableau (narrowly)...", 0, 0, DO_OTGrammar_drawTableau_narrowly); praat_addAction1 (classOTGrammar, 1, L"Save as headerless spreadsheet file...", 0, 0, DO_OTGrammar_writeToHeaderlessSpreadsheetFile); praat_addAction1 (classOTGrammar, 1, L"Write to headerless spreadsheet file...", 0, praat_HIDDEN, DO_OTGrammar_writeToHeaderlessSpreadsheetFile); praat_addAction1 (classOTGrammar, 0, L"Query -", 0, 0, 0); praat_addAction1 (classOTGrammar, 1, L"Get number of constraints", 0, 1, DO_OTGrammar_getNumberOfConstraints); praat_addAction1 (classOTGrammar, 1, L"Get constraint...", 0, 1, DO_OTGrammar_getConstraint); praat_addAction1 (classOTGrammar, 1, L"Get ranking value...", 0, 1, DO_OTGrammar_getRankingValue); praat_addAction1 (classOTGrammar, 1, L"Get disharmony...", 0, 1, DO_OTGrammar_getDisharmony); praat_addAction1 (classOTGrammar, 1, L"Get number of tableaus", 0, 1, DO_OTGrammar_getNumberOfTableaus); praat_addAction1 (classOTGrammar, 1, L"Get input...", 0, 1, DO_OTGrammar_getInput); praat_addAction1 (classOTGrammar, 1, L"Get number of candidates...", 0, 1, DO_OTGrammar_getNumberOfCandidates); praat_addAction1 (classOTGrammar, 1, L"Get candidate...", 0, 1, DO_OTGrammar_getCandidate); praat_addAction1 (classOTGrammar, 1, L"Get number of violations...", 0, 1, DO_OTGrammar_getNumberOfViolations); praat_addAction1 (classOTGrammar, 1, L"-- parse --", 0, 1, 0); praat_addAction1 (classOTGrammar, 1, L"Get winner...", 0, 1, DO_OTGrammar_getWinner); praat_addAction1 (classOTGrammar, 1, L"Compare candidates...", 0, 1, DO_OTGrammar_compareCandidates); praat_addAction1 (classOTGrammar, 1, L"Get number of optimal candidates...", 0, 1, DO_OTGrammar_getNumberOfOptimalCandidates); praat_addAction1 (classOTGrammar, 1, L"Is candidate grammatical...", 0, 1, DO_OTGrammar_isCandidateGrammatical); praat_addAction1 (classOTGrammar, 1, L"Is candidate singly grammatical...", 0, 1, DO_OTGrammar_isCandidateSinglyGrammatical); praat_addAction1 (classOTGrammar, 1, L"Get interpretive parse...", 0, 1, DO_OTGrammar_getInterpretiveParse); praat_addAction1 (classOTGrammar, 1, L"Is partial output grammatical...", 0, 1, DO_OTGrammar_isPartialOutputGrammatical); praat_addAction1 (classOTGrammar, 1, L"Is partial output singly grammatical...", 0, 1, DO_OTGrammar_isPartialOutputSinglyGrammatical); praat_addAction1 (classOTGrammar, 0, L"Generate inputs...", 0, 0, DO_OTGrammar_generateInputs); praat_addAction1 (classOTGrammar, 0, L"Get inputs", 0, 0, DO_OTGrammar_getInputs); praat_addAction1 (classOTGrammar, 0, L"Measure typology", 0, 0, DO_OTGrammar_measureTypology); praat_addAction1 (classOTGrammar, 0, L"Evaluate", 0, 0, 0); praat_addAction1 (classOTGrammar, 0, L"Evaluate...", 0, 0, DO_OTGrammar_evaluate); praat_addAction1 (classOTGrammar, 0, L"Input to output...", 0, 0, DO_OTGrammar_inputToOutput); praat_addAction1 (classOTGrammar, 0, L"Input to outputs...", 0, 0, DO_OTGrammar_inputToOutputs); praat_addAction1 (classOTGrammar, 0, L"To output Distributions...", 0, 0, DO_OTGrammar_to_Distributions); praat_addAction1 (classOTGrammar, 0, L"To PairDistribution...", 0, 0, DO_OTGrammar_to_PairDistribution); praat_addAction1 (classOTGrammar, 0, L"Modify ranking -", 0, 0, 0); praat_addAction1 (classOTGrammar, 0, L"Set ranking...", 0, 1, DO_OTGrammar_setRanking); praat_addAction1 (classOTGrammar, 0, L"Reset all rankings...", 0, 1, DO_OTGrammar_resetAllRankings); praat_addAction1 (classOTGrammar, 0, L"Reset to random total ranking...", 0, 1, DO_OTGrammar_resetToRandomTotalRanking); praat_addAction1 (classOTGrammar, 0, L"Learn one...", 0, 1, DO_OTGrammar_learnOne); praat_addAction1 (classOTGrammar, 0, L"Learn one from partial output...", 0, 1, DO_OTGrammar_learnOneFromPartialOutput); praat_addAction1 (classOTGrammar, 0, L"Modify behaviour -", 0, 0, 0); praat_addAction1 (classOTGrammar, 1, L"Set harmony computation method...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_OTGrammar_setDecisionStrategy); praat_addAction1 (classOTGrammar, 1, L"Set decision strategy...", 0, 1, DO_OTGrammar_setDecisionStrategy); praat_addAction1 (classOTGrammar, 1, L"Set leak...", 0, 1, DO_OTGrammar_setLeak); praat_addAction1 (classOTGrammar, 1, L"Set constraint plasticity...", 0, 1, DO_OTGrammar_setConstraintPlasticity); praat_addAction1 (classOTGrammar, 0, L"Modify structure -", 0, 0, 0); praat_addAction1 (classOTGrammar, 0, L"Remove constraint...", 0, 1, DO_OTGrammar_removeConstraint); praat_addAction1 (classOTGrammar, 0, L"Remove harmonically bounded candidates...", 0, 1, DO_OTGrammar_removeHarmonicallyBoundedCandidates); { void praat_TableOfReal_init (ClassInfo klas); praat_TableOfReal_init (classOTHistory); } praat_addAction1 (classOTMulti, 0, L"View & Edit", 0, praat_ATTRACTIVE, DO_OTMulti_edit); praat_addAction1 (classOTMulti, 0, L"Edit", 0, praat_HIDDEN, DO_OTMulti_edit); praat_addAction1 (classOTMulti, 0, L"Draw tableau...", 0, 0, DO_OTMulti_drawTableau); praat_addAction1 (classOTMulti, 0, L"Draw tableau (narrowly)...", 0, 0, DO_OTMulti_drawTableau_narrowly); praat_addAction1 (classOTMulti, 0, L"Query -", 0, 0, 0); praat_addAction1 (classOTMulti, 1, L"Get number of constraints", 0, 1, DO_OTMulti_getNumberOfConstraints); praat_addAction1 (classOTMulti, 1, L"Get constraint...", 0, 1, DO_OTMulti_getConstraint); praat_addAction1 (classOTMulti, 1, L"Get constraint number...", 0, 1, DO_OTMulti_getConstraintIndexFromName); praat_addAction1 (classOTMulti, 1, L"Get ranking value...", 0, 1, DO_OTMulti_getRankingValue); praat_addAction1 (classOTMulti, 1, L"Get disharmony...", 0, 1, DO_OTMulti_getDisharmony); praat_addAction1 (classOTMulti, 1, L"Get number of candidates", 0, 1, DO_OTMulti_getNumberOfCandidates); praat_addAction1 (classOTMulti, 1, L"Get candidate...", 0, 1, DO_OTMulti_getCandidate); praat_addAction1 (classOTMulti, 1, L"Get number of violations...", 0, 1, DO_OTMulti_getNumberOfViolations); praat_addAction1 (classOTMulti, 1, L"-- parse --", 0, 1, 0); praat_addAction1 (classOTMulti, 1, L"Get winner...", 0, 1, DO_OTMulti_getWinner); praat_addAction1 (classOTMulti, 0, L"Evaluate", 0, 0, 0); praat_addAction1 (classOTMulti, 0, L"Evaluate...", 0, 0, DO_OTMulti_evaluate); praat_addAction1 (classOTMulti, 0, L"Get output...", 0, 0, DO_OTMulti_generateOptimalForm); praat_addAction1 (classOTMulti, 0, L"Get outputs...", 0, 0, DO_OTMulti_generateOptimalForms); praat_addAction1 (classOTMulti, 0, L"To output Distribution...", 0, 0, DO_OTMulti_to_Distribution); praat_addAction1 (classOTMulti, 0, L"Modify ranking", 0, 0, 0); praat_addAction1 (classOTMulti, 0, L"Set ranking...", 0, 0, DO_OTMulti_setRanking); praat_addAction1 (classOTMulti, 0, L"Reset all rankings...", 0, 0, DO_OTMulti_resetAllRankings); praat_addAction1 (classOTMulti, 0, L"Learn one...", 0, 0, DO_OTMulti_learnOne); praat_addAction1 (classOTMulti, 0, L"Modify behaviour -", 0, 0, 0); praat_addAction1 (classOTMulti, 1, L"Set decision strategy...", 0, 1, DO_OTMulti_setDecisionStrategy); praat_addAction1 (classOTMulti, 1, L"Set leak...", 0, 1, DO_OTMulti_setLeak); praat_addAction1 (classOTMulti, 1, L"Set constraint plasticity...", 0, 1, DO_OTMulti_setConstraintPlasticity); praat_addAction1 (classOTMulti, 0, L"Modify structure -", 0, 0, 0); praat_addAction1 (classOTMulti, 0, L"Remove constraint...", 0, 1, DO_OTMulti_removeConstraint); praat_addAction2 (classOTGrammar, 1, classDistributions, 1, L"Learn from partial outputs...", 0, 0, DO_OTGrammar_Distributions_learnFromPartialOutputs); praat_addAction2 (classOTGrammar, 1, classDistributions, 1, L"Get fraction correct...", 0, 0, DO_OTGrammar_Distributions_getFractionCorrect); praat_addAction2 (classOTGrammar, 1, classDistributions, 1, L"List obligatory rankings...", 0, praat_HIDDEN, DO_OTGrammar_Distributions_listObligatoryRankings); praat_addAction2 (classOTGrammar, 1, classPairDistribution, 1, L"Learn...", 0, 0, DO_OTGrammar_PairDistribution_learn); praat_addAction2 (classOTGrammar, 1, classPairDistribution, 1, L"Find positive weights...", 0, 0, DO_OTGrammar_PairDistribution_findPositiveWeights); praat_addAction2 (classOTGrammar, 1, classPairDistribution, 1, L"Get fraction correct...", 0, 0, DO_OTGrammar_PairDistribution_getFractionCorrect); praat_addAction2 (classOTGrammar, 1, classPairDistribution, 1, L"Get minimum number correct...", 0, 0, DO_OTGrammar_PairDistribution_getMinimumNumberCorrect); praat_addAction2 (classOTGrammar, 1, classPairDistribution, 1, L"List obligatory rankings", 0, 0, DO_OTGrammar_PairDistribution_listObligatoryRankings); praat_addAction2 (classOTGrammar, 1, classStrings, 1, L"Inputs to outputs...", 0, 0, DO_OTGrammar_inputsToOutputs); praat_addAction2 (classOTGrammar, 1, classStrings, 1, L"Learn from partial outputs...", 0, 0, DO_OTGrammar_learnFromPartialOutputs); praat_addAction2 (classOTGrammar, 1, classStrings, 2, L"Learn...", 0, 0, DO_OTGrammar_learn); praat_addAction2 (classOTMulti, 1, classPairDistribution, 1, L"Learn...", 0, 0, DO_OTMulti_PairDistribution_learn); praat_addAction2 (classOTMulti, 1, classStrings, 1, L"Get outputs...", 0, 0, DO_OTMulti_Strings_generateOptimalForms); praat_addMenuCommand (L"Objects", L"New", L"Symmetric networks", 0, 0, 0); praat_addMenuCommand (L"Objects", L"New", L"Create empty Network...", 0, 1, DO_Create_empty_Network); praat_addMenuCommand (L"Objects", L"New", L"Create rectangular Network...", 0, 1, DO_Create_rectangular_Network); praat_addMenuCommand (L"Objects", L"New", L"Create rectangular Network (vertical)...", 0, 1, DO_Create_rectangular_Network_vertical); praat_addAction1 (classNetwork, 0, L"Draw...", 0, 0, DO_Network_draw); praat_addAction1 (classNetwork, 0, L"Query -", 0, 0, 0); praat_addAction1 (classNetwork, 1, L"Get activity...", 0, 0, DO_Network_getActivity); praat_addAction1 (classNetwork, 1, L"Get weight...", 0, 0, DO_Network_getWeight); praat_addAction1 (classNetwork, 0, L"Modify -", 0, 0, 0); praat_addAction1 (classNetwork, 0, L"Add node...", 0, 1, DO_Network_addNode); praat_addAction1 (classNetwork, 0, L"Add connection...", 0, 1, DO_Network_addConnection); praat_addAction1 (classNetwork, 1, L"-- activity --", 0, 1, 0); praat_addAction1 (classNetwork, 0, L"Set activity...", 0, 1, DO_Network_setActivity); praat_addAction1 (classNetwork, 0, L"Set clamping...", 0, 1, DO_Network_setClamping); praat_addAction1 (classNetwork, 0, L"Zero activities...", 0, 1, DO_Network_zeroActivities); praat_addAction1 (classNetwork, 0, L"Normalize activities...", 0, 1, DO_Network_normalizeActivities); praat_addAction1 (classNetwork, 0, L"Spread activities...", 0, 1, DO_Network_spreadActivities); praat_addAction1 (classNetwork, 1, L"Set activation spreading rule...", 0, 1, DO_Network_setActivationSpreadingRule); praat_addAction1 (classNetwork, 1, L"-- weight --", 0, 1, 0); praat_addAction1 (classNetwork, 0, L"Set weight...", 0, 1, DO_Network_setWeight); praat_addAction1 (classNetwork, 0, L"Update weights", 0, 1, DO_Network_updateWeights); praat_addAction1 (classNetwork, 1, L"Set weight update rule...", 0, 1, DO_Network_setWeightUpdateRule); } /* End of file praat_gram.c */ sources_5316/gram/OTGrammar_enums.h0000644000176700017670000000433511551255106016070 0ustar paulpaul/* OTGrammar_enums.h * * Copyright (C) 2006-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2011/04/13 */ enums_begin (kOTGrammar_decisionStrategy, 0) enums_add (kOTGrammar_decisionStrategy, 0, OPTIMALITY_THEORY, L"OptimalityTheory") enums_add (kOTGrammar_decisionStrategy, 1, HARMONIC_GRAMMAR, L"HarmonicGrammar") enums_add (kOTGrammar_decisionStrategy, 2, LINEAR_OT, L"LinearOT") enums_add (kOTGrammar_decisionStrategy, 3, EXPONENTIAL_HG, L"ExponentialHG") enums_add (kOTGrammar_decisionStrategy, 4, MAXIMUM_ENTROPY, L"MaximumEntropy") enums_add (kOTGrammar_decisionStrategy, 5, POSITIVE_HG, L"PositiveHG") enums_add (kOTGrammar_decisionStrategy, 6, EXPONENTIAL_MAXIMUM_ENTROPY, L"ExponentialMaximumEntropy") enums_end (kOTGrammar_decisionStrategy, 6, OPTIMALITY_THEORY) enums_begin (kOTGrammar_rerankingStrategy, 0) enums_add (kOTGrammar_rerankingStrategy, 0, DEMOTION_ONLY, L"Demotion only") enums_add (kOTGrammar_rerankingStrategy, 1, SYMMETRIC_ONE, L"Symmetric one") enums_add (kOTGrammar_rerankingStrategy, 2, SYMMETRIC_ALL, L"Symmetric all") enums_add (kOTGrammar_rerankingStrategy, 3, WEIGHTED_UNCANCELLED, L"Weighted uncancelled") enums_add (kOTGrammar_rerankingStrategy, 4, WEIGHTED_ALL, L"Weighted all") enums_add (kOTGrammar_rerankingStrategy, 5, EDCD, L"EDCD") enums_add (kOTGrammar_rerankingStrategy, 6, EDCD_WITH_VACATION, L"EDCD with vacation") enums_add (kOTGrammar_rerankingStrategy, 7, WEIGHTED_ALL_UP_HIGHEST_DOWN, L"Weighted all up, highest down") enums_end (kOTGrammar_rerankingStrategy, 7, SYMMETRIC_ALL) /* End of file OTGrammar_enums.h */ sources_5316/gram/OTGrammar_def.h0000644000176700017670000000535111621503323015471 0ustar paulpaul/* OTGrammar_def.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT OTGrammarConstraint oo_DEFINE_STRUCT (OTGrammarConstraint) oo_STRING (name) oo_DOUBLE (ranking) oo_DOUBLE (disharmony) oo_FROM (2) oo_DOUBLE (plasticity) oo_ENDFROM #if oo_READING if (localVersion < 2) { plasticity = 1.0; } #endif #if !oo_READING && !oo_WRITING oo_INT (tiedToTheLeft) oo_INT (tiedToTheRight) #endif oo_END_STRUCT (OTGrammarConstraint) #undef ooSTRUCT #define ooSTRUCT OTGrammarFixedRanking oo_DEFINE_STRUCT (OTGrammarFixedRanking) oo_LONG (higher) oo_LONG (lower) oo_END_STRUCT (OTGrammarFixedRanking) #undef ooSTRUCT #define ooSTRUCT OTGrammarCandidate oo_DEFINE_STRUCT (OTGrammarCandidate) oo_STRING (output) oo_LONG (numberOfConstraints) oo_INT_VECTOR (marks, numberOfConstraints) #if !oo_READING && !oo_WRITING oo_DOUBLE (harmony) oo_DOUBLE (probability) oo_LONG (numberOfPotentialPartialOutputsMatching) oo_BOOLEAN_VECTOR (partialOutputMatches, numberOfPotentialPartialOutputsMatching) #endif oo_END_STRUCT (OTGrammarCandidate) #undef ooSTRUCT #define ooSTRUCT OTGrammarTableau oo_DEFINE_STRUCT (OTGrammarTableau) oo_STRING (input) oo_LONG (numberOfCandidates) oo_STRUCT_VECTOR (OTGrammarCandidate, candidates, numberOfCandidates) oo_END_STRUCT (OTGrammarTableau) #undef ooSTRUCT #define ooSTRUCT OTGrammar oo_DEFINE_CLASS (OTGrammar, Data) oo_FROM (1) oo_ENUM (kOTGrammar_decisionStrategy, decisionStrategy) oo_ENDFROM oo_FROM (2) oo_DOUBLE (leak) oo_ENDFROM oo_LONG (numberOfConstraints) oo_STRUCT_VECTOR (OTGrammarConstraint, constraints, numberOfConstraints) oo_LONG_VECTOR (index, numberOfConstraints) oo_LONG (numberOfFixedRankings) oo_STRUCT_VECTOR (OTGrammarFixedRanking, fixedRankings, numberOfFixedRankings) oo_LONG (numberOfTableaus) oo_STRUCT_VECTOR (OTGrammarTableau, tableaus, numberOfTableaus) #if oo_READING OTGrammar_sort (this); #endif #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (OTGrammar) #undef ooSTRUCT /* End of file OTGrammar_def.h */ sources_5316/gram/OTGrammarEditor.h0000644000176700017670000000252211652005471016024 0ustar paulpaul#ifndef _OTGrammarEditor_h_ #define _OTGrammarEditor_h_ /* OTGrammar.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "HyperPage.h" #include "OTGrammar.h" Thing_define (OTGrammarEditor, HyperPage) { // new data: public: long selected; bool d_constraintsAreDrawnVertically; // overridden methods: virtual bool v_editable () { return true; } virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_draw (); virtual int v_goToPage (const wchar *title); }; OTGrammarEditor OTGrammarEditor_create (GuiObject parent, const wchar *title, OTGrammar ot); /* End of file OTGrammarEditor.h */ #endif sources_5316/gram/OTGrammar_ex_metrics.cpp0000644000176700017670000005126611613556056017452 0ustar paulpaul/* OTGrammar_ex_metrics.cpp * * Copyright (C) 2001-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2001/11/25 * pb 2002/07/16 GPL * pb 2003/03/31 removeConstraint * pb 2003/05/09 added Peripheral and MainNonfinal * pb 2004/01/14 added HeadNonfinal * pb 2004/01/25 added overtFormsHaveSecondaryStress * pb 2004/07/27 added Clash and Lapse * pb 2004/08/11 complete rewrite in order to include WeightByPosition and *MoraicConsonant * pb 2004/12/03 corrected *Lapse * pb 2007/07/23 constraint plasticity * pb 2007/08/12 wchar * pb 2011/03/29 C++ * pb 2011/06/29 C++ */ #include "OTGrammar.h" #define WSP 1 #define FtNonfinal 2 #define Iambic 3 #define Parse 4 #define FootBin 5 #define WFL 6 #define WFR 7 #define Main_L 8 #define Main_R 9 #define AFL 10 #define AFR 11 #define Nonfinal 12 #define Trochaic 13 #define FootBimoraic 14 #define FootBisyllabic 15 #define Peripheral 16 #define MainNonfinal 17 #define HeadNonfinal 18 #define Clash 19 #define Lapse 20 #define WeightByPosition 21 #define MoraicConsonant 22 #define NUMBER_OF_CONSTRAINTS 22 static const wchar *constraintNames [1+NUMBER_OF_CONSTRAINTS] = { 0, L"WSP", L"FtNonfinal", L"Iambic", L"Parse", L"FootBin", L"WFL", L"WFR", L"Main-L", L"Main-R", L"AFL", L"AFR", L"Nonfinal", L"Trochaic", L"FtBimor", L"FtBisyl", L"Peripheral", L"MainNonfinal", L"HeadNonfinal", L"*Clash", L"*Lapse", L"WeightByPosition", L"*C\\mu" }; static void addCandidate (OTGrammarTableau me, long numberOfSyllables, int stress [], int footedToTheLeft [], int footedToTheRight [], int surfaceWeightPattern [], int overtFormsHaveSecondaryStress) { static const wchar *syllable [] = { L"L", L"L1", L"L2", L"H", L"H1", L"H2", L"K", L"K1", L"K2", L"J", L"J1", L"J2" }; static const wchar *syllableWithoutSecondaryStress [] = { L"L", L"L1", L"L", L"H", L"H1", L"H", L"K", L"K1", L"K", L"J", L"J1", L"J" }; wchar output [100]; wcscpy (output, L"["); for (long isyll = 1; isyll <= numberOfSyllables; isyll ++) { if (isyll > 1) wcscat (output, L" "); wcscat (output, ( overtFormsHaveSecondaryStress ? syllable : syllableWithoutSecondaryStress ) [stress [isyll] + 3 * (surfaceWeightPattern [isyll] - 1)]); } wcscat (output, L"] \\-> /"); for (long isyll = 1; isyll <= numberOfSyllables; isyll ++) { if (isyll > 1) wcscat (output, L" "); if (footedToTheRight [isyll] || (! footedToTheLeft [isyll] && stress [isyll] != 0)) wcscat (output, L"("); wcscat (output, syllable [stress [isyll] + 3 * (surfaceWeightPattern [isyll] - 1)]); if (footedToTheLeft [isyll] || (! footedToTheRight [isyll] && stress [isyll] != 0)) wcscat (output, L")"); } wcscat (output, L"/"); my candidates [++ my numberOfCandidates]. output = Melder_wcsdup (output); } static void fillSurfaceWeightPattern (OTGrammarTableau me, long numberOfSyllables, int stress [], int footedToTheLeft [], int footedToTheRight [], int underlyingWeightPattern [], int overtFormsHaveSecondaryStress) { int surfaceWeightPattern [1+7], minSurfaceWeight [1+7], maxSurfaceWeight [1+7]; int weight1, weight2, weight3, weight4, weight5; for (long isyll = 1; isyll <= numberOfSyllables; isyll ++) { if (underlyingWeightPattern [isyll] < 3) { minSurfaceWeight [isyll] = maxSurfaceWeight [isyll] = underlyingWeightPattern [isyll]; /* L -> L; H -> H */ } else { minSurfaceWeight [isyll] = 3, maxSurfaceWeight [isyll] = 4; /* C -> { J, K } */ } } surfaceWeightPattern [6] = surfaceWeightPattern [7] = 1; /* Constant L. */ for (weight1 = minSurfaceWeight [1]; weight1 <= maxSurfaceWeight [1]; weight1 ++) { surfaceWeightPattern [1] = weight1; for (weight2 = minSurfaceWeight [2]; weight2 <= maxSurfaceWeight [2]; weight2 ++) { surfaceWeightPattern [2] = weight2; if (numberOfSyllables == 2) { addCandidate (me, 2, stress, footedToTheLeft, footedToTheRight, surfaceWeightPattern, overtFormsHaveSecondaryStress); } else for (weight3 = minSurfaceWeight [3]; weight3 <= maxSurfaceWeight [3]; weight3 ++) { surfaceWeightPattern [3] = weight3; if (numberOfSyllables == 3) { addCandidate (me, 3, stress, footedToTheLeft, footedToTheRight, surfaceWeightPattern, overtFormsHaveSecondaryStress); } else for (weight4 = minSurfaceWeight [4]; weight4 <= maxSurfaceWeight [4]; weight4 ++) { surfaceWeightPattern [4] = weight4; if (numberOfSyllables == 4) { addCandidate (me, 4, stress, footedToTheLeft, footedToTheRight, surfaceWeightPattern, overtFormsHaveSecondaryStress); } else for (weight5 = minSurfaceWeight [5]; weight5 <= maxSurfaceWeight [5]; weight5 ++) { surfaceWeightPattern [5] = weight5; addCandidate (me, numberOfSyllables, stress, footedToTheLeft, footedToTheRight, surfaceWeightPattern, overtFormsHaveSecondaryStress); } } } } } } static void path (OTGrammarTableau me, long numberOfSyllables, int stress [], int startingSyllable, int footedToTheLeft_in [], int footedToTheRight_in [], int underlyingWeightPattern [], int overtFormsHaveSecondaryStress) { int footedToTheLeft [10], footedToTheRight [10]; long isyll; /* Localize all arguments. */ for (isyll = 1; isyll <= startingSyllable; isyll ++) { footedToTheLeft [isyll] = footedToTheLeft_in [isyll]; footedToTheRight [isyll] = footedToTheRight_in [isyll]; } for (isyll = startingSyllable + 1; isyll <= numberOfSyllables; isyll ++) footedToTheLeft [isyll] = footedToTheRight [isyll] = 0; if (startingSyllable > numberOfSyllables) { fillSurfaceWeightPattern (me, numberOfSyllables, stress, footedToTheLeft, footedToTheRight, underlyingWeightPattern, overtFormsHaveSecondaryStress); } else { path (me, numberOfSyllables, stress, startingSyllable + 1, footedToTheLeft, footedToTheRight, underlyingWeightPattern, overtFormsHaveSecondaryStress); if (stress [startingSyllable] == 0 && startingSyllable < numberOfSyllables && stress [startingSyllable + 1] != 0) { footedToTheLeft [startingSyllable + 1] = TRUE; footedToTheRight [startingSyllable] = TRUE; path (me, numberOfSyllables, stress, startingSyllable + 1, footedToTheLeft, footedToTheRight, underlyingWeightPattern, overtFormsHaveSecondaryStress); footedToTheLeft [startingSyllable + 1] = FALSE; footedToTheRight [startingSyllable] = FALSE; } if (stress [startingSyllable] == 0 && startingSyllable > 1 && stress [startingSyllable - 1] != 0 && ! footedToTheLeft [startingSyllable - 1]) { footedToTheRight [startingSyllable - 1] = TRUE; footedToTheLeft [startingSyllable] = TRUE; path (me, numberOfSyllables, stress, startingSyllable + 1, footedToTheLeft, footedToTheRight, underlyingWeightPattern, overtFormsHaveSecondaryStress); } } } static void fillOvertStressPattern (OTGrammarTableau me, long numberOfSyllables, int stress [], int underlyingWeightPattern [], int overtFormsHaveSecondaryStress) { int footedToTheLeft [10], footedToTheRight [10]; for (int isyll = 1; isyll <= numberOfSyllables; isyll ++) footedToTheLeft [isyll] = footedToTheRight [isyll] = 0; path (me, numberOfSyllables, stress, 1, footedToTheLeft, footedToTheRight, underlyingWeightPattern, overtFormsHaveSecondaryStress); } static void fillTableau (OTGrammarTableau me, long numberOfSyllables, int underlyingWeightPattern [], int overtFormsHaveSecondaryStress, int includeCodas) { wchar input [100]; static int numberOfCandidates_noCodas [1+7] = { 0, 1, 6, 24, 88, 300, 984, 3136 }; static int numberOfCandidates_codas [1+7] = { 0, 1, 24, 192, 1408, 9600, 984, 3136 }; wcscpy (input, L"|"); for (long isyll = 1; isyll <= numberOfSyllables; isyll ++) { static const wchar *syllable_noCodas [] = { L"", L"L", L"H" }; static const wchar *syllable_codas [] = { L"", L"cv", L"cv:", L"cvc" }; if (isyll > 1) wcscat (input, includeCodas ? L"." : L" "); wcscat (input, ( includeCodas ? syllable_codas : syllable_noCodas ) [underlyingWeightPattern [isyll]]); } wcscat (input, L"|"); my input = Melder_wcsdup (input); my candidates = NUMvector (1, ( includeCodas ? numberOfCandidates_codas : numberOfCandidates_noCodas ) [numberOfSyllables]); for (long mainStressed = 1; mainStressed <= numberOfSyllables; mainStressed ++) { int stress [10]; stress [mainStressed] = 1; for (int secondary1 = FALSE; secondary1 <= TRUE; secondary1 ++) { stress [mainStressed <= 1 ? 2 : 1] = secondary1 ? 2 : 0; if (numberOfSyllables == 2) { fillOvertStressPattern (me, 2, stress, underlyingWeightPattern, overtFormsHaveSecondaryStress); } else for (int secondary2 = FALSE; secondary2 <= TRUE; secondary2 ++) { stress [mainStressed <= 2 ? 3 : 2] = secondary2 ? 2 : 0; if (numberOfSyllables == 3) { fillOvertStressPattern (me, 3, stress, underlyingWeightPattern, overtFormsHaveSecondaryStress); } else for (int secondary3 = FALSE; secondary3 <= TRUE; secondary3 ++) { stress [mainStressed <= 3 ? 4 : 3] = secondary3 ? 2 : 0; if (numberOfSyllables == 4) { fillOvertStressPattern (me, 4, stress, underlyingWeightPattern, overtFormsHaveSecondaryStress); } else for (int secondary4 = FALSE; secondary4 <= TRUE; secondary4 ++) { stress [mainStressed <= 4 ? 5 : 4] = secondary4 ? 2 : 0; if (numberOfSyllables == 5) { fillOvertStressPattern (me, 5, stress, underlyingWeightPattern, overtFormsHaveSecondaryStress); } else for (int secondary5 = FALSE; secondary5 <= TRUE; secondary5 ++) { stress [mainStressed <= 5 ? 6 : 5] = secondary5 ? 2 : 0; if (numberOfSyllables == 6) { fillOvertStressPattern (me, 6, stress, underlyingWeightPattern, overtFormsHaveSecondaryStress); } else for (int secondary6 = FALSE; secondary6 <= TRUE; secondary6 ++) { stress [mainStressed <= 6 ? 7 : 6] = secondary6 ? 2 : 0; fillOvertStressPattern (me, 7, stress, underlyingWeightPattern, overtFormsHaveSecondaryStress); } } } } } } } } static void computeViolationMarks (OTGrammarCandidate me) { #define isHeavy(s) ((s) == 'H' || (s) == 'J') #define isLight(s) ((s) == 'L' || (s) == 'K') #define isSyllable(s) (isHeavy (s) || isLight (s)) #define isStress(s) ((s) == '1' || (s) == '2') int depth; wchar *firstSlash = wcschr (my output, '/'); wchar *lastSlash = & my output [wcslen (my output) - 1]; my marks = NUMvector (1, my numberOfConstraints = NUMBER_OF_CONSTRAINTS); /* Violations of WSP: count all H not followed by 1 or 2. */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (isHeavy (p [0]) && ! isStress (p [1])) my marks [WSP] ++; } /* Violations of FtNonfinal: count all heads followed by ). */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (isStress (p [0]) && p [1] == ')') my marks [FtNonfinal] ++; } /* Violations of Iambic: count all heads not followed by ). */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (isStress (p [0]) && p [1] != ')') my marks [Iambic] ++; } /* Violations of Parse and Peripheral: count all syllables not between (). */ depth = 0; for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (p [0] == '(') depth ++; else if (p [0] == ')') depth --; else if (isSyllable (p [0]) && depth != 1) { my marks [Parse] ++; if (p != firstSlash + 1 && p != lastSlash - 1) my marks [Peripheral] ++; } } /* Violations of FootBin: count all (L1) and (L2). */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (isLight (p [0]) && p [-1] == '(' && isStress (p [1]) && p [2] == ')') my marks [FootBin] ++; } /* Violations of WFL: count all initial / not followed by (. */ if (firstSlash [1] != '(') my marks [WFL] = 1; /* Violations of WFR: count all final / not preceded by ). */ if (lastSlash [-1] != ')') my marks [WFR] = 1; /* Violations of Main_L: count syllables from foot containing X1 to left edge. */ { wchar *p = wcschr (firstSlash, '1'); for (; *p != '('; p --) { } for (; p != firstSlash; p --) { if (isSyllable (p [0])) my marks [Main_L] ++; } } /* Violations of Main_R: count syllables from foot containing X1 to right edge. */ { wchar *p = wcschr (firstSlash, '1'); for (; *p != ')'; p ++) { } for (; p != lastSlash; p ++) { if (isSyllable (p [0])) my marks [Main_R] ++; } } /* Violations of AFL: count syllables from every foot to left edge. */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (p [0] == '(') { for (wchar *q = p; q != firstSlash; q --) { if (isSyllable (q [0])) my marks [AFL] ++; } } } /* Violations of AFR: count syllables from every foot to right edge. */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (p [0] == ')') { for (wchar *q = p; q != lastSlash; q ++) { if (isSyllable (q [0])) my marks [AFR] ++; } } } /* Violations of Nonfinal: count all final / preceded by ). */ if (lastSlash [-1] == ')') my marks [Nonfinal] = 1; /* Violations of Trochaic: count all heads not preceded by (. */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (isStress (p [0]) && p [-2] != '(') my marks [Trochaic] ++; } /* Violations of FootBimoraic: count weight between (). */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (p [0] == '(') { int weight = 0; for (p ++; p [0] != ')'; p ++) { if (isHeavy (p [0])) weight += 2; else if (isLight (p [0])) weight += 1; } if (weight != 2) my marks [FootBimoraic] ++; } } /* Violations of FootBisyllabic: count all (X1) and (X2). */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (isSyllable (p [0]) && p [-1] == '(' && isStress (p [1]) && p [2] == ')') my marks [FootBisyllabic] ++; } /* Violations of MainNonfinal: count all final / preceded by ) preceded by 1 in the same foot. */ if (lastSlash [-1] == ')') { for (wchar *p = lastSlash - 2; ; p --) { if (p [0] == '2') break; if (p [0] == '1') { my marks [MainNonfinal] = 1; break; } } } /* Violations of HeadNonfinal: count all final / preceded by ) directly preceded by 1, plus MainNonfinal. */ if (lastSlash [-1] == ')') { if (lastSlash [-2] == '1') { my marks [HeadNonfinal] = 2; } else { for (wchar *p = lastSlash - 2; ; p --) { if (p [0] == '2') break; if (p [0] == '1') { my marks [HeadNonfinal] = 1; break; } } } } /* Violations of *Clash: count all 1 and 2 followed by an 1 or 2 after the next L or H. */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (isStress (p [0])) { for (wchar *q = p + 1; q != lastSlash; q ++) { if (isSyllable (q [0])) { if (isStress (q [1])) { my marks [Clash] ++; } break; } } } } /* Violations of *Lapse: count all sequences of three unstressed syllables. */ depth = 0; for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (isSyllable (p [0])) { if (isStress (p [1])) { depth = 0; } else { if (++ depth > 2) { my marks [Lapse] ++; } } } } /* Violations of WeightByPosition: count all K. */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (p [0] == 'K') my marks [WeightByPosition] ++; } /* Violations of *MoraicConsonant: count all J. */ for (wchar *p = firstSlash + 1; p != lastSlash; p ++) { if (p [0] == 'J') my marks [MoraicConsonant] ++; } } static void replaceOutput (OTGrammarCandidate me) { int abstract = FALSE; Melder_assert (my output != NULL); wchar newOutput [100], *q = & newOutput [0]; for (const wchar *p = & my output [0]; *p != '\0'; p ++) { if (p [0] == ' ') { *q ++ = p [-1] == ']' || p [1] == '/' ? ' ' : '.'; } else if (isSyllable (p [0])) { *q ++ = 'c'; if (abstract) { *q ++ = 'V'; if (isStress (p [1])) { *q ++ = p [1]; } if (p [0] == 'L') { ; } else if (p [0] == 'H') { *q ++ = 'V'; } else if (p [0] == 'K') { *q ++ = 'c'; } else { *q ++ = 'C'; } } else { *q ++ = 'v'; if (p [0] == 'L') { ; } else if (p [0] == 'H') { *q ++ = ':'; } else { *q ++ = 'c'; } } } else if (isStress (p [0]) && abstract) { ; } else { if (p [0] == '/') abstract = TRUE; *q ++ = p [0]; } } *q = '\0'; Melder_free (my output); my output = Melder_wcsdup_f (newOutput); } OTGrammar OTGrammar_create_metrics (int equal_footForm_wsp, int trochaicityConstraint, int includeFootBimoraic, int includeFootBisyllabic, int includePeripheral, int nonfinalityConstraint, int overtFormsHaveSecondaryStress, int includeClashAndLapse, int includeCodas) { try { int numberOfSyllables; int underlyingWeightPattern [1+7], maximumUnderlyingWeight = includeCodas ? 3 : 2; long numberOfTableaus = includeCodas ? 9 + 27 + 81 + 243 + 2 : 62; autoOTGrammar me = Thing_new (OTGrammar); my constraints = NUMvector (1, my numberOfConstraints = NUMBER_OF_CONSTRAINTS); for (long icons = 1; icons <= NUMBER_OF_CONSTRAINTS; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; constraint -> name = Melder_wcsdup (constraintNames [icons]); constraint -> ranking = 100.0; constraint -> plasticity = 1.0; } if (equal_footForm_wsp >= 2) { /* Foot form constraints high. */ my constraints [FtNonfinal]. ranking = 101.0; my constraints [Iambic]. ranking = 101.0; my constraints [Trochaic]. ranking = -1e9; } if (equal_footForm_wsp == 3) { /* Quantity sensitivity high, foot form constraints in the second stratum. */ my constraints [WSP]. ranking = 102.0; } my tableaus = NUMvector (1, numberOfTableaus); for (numberOfSyllables = 2; numberOfSyllables <= 7; numberOfSyllables ++) { long numberOfUnderlyingWeightPatterns = numberOfSyllables > 5 ? 1 : (long) floor (pow (maximumUnderlyingWeight, numberOfSyllables) + 0.5); for (long isyll = 1; isyll <= numberOfSyllables; isyll ++) { underlyingWeightPattern [isyll] = 1; /* L or cv */ } for (long iweightPattern = 1; iweightPattern <= numberOfUnderlyingWeightPatterns; iweightPattern ++) { fillTableau (& my tableaus [++ my numberOfTableaus], numberOfSyllables, underlyingWeightPattern, overtFormsHaveSecondaryStress, includeCodas); /* * Cycle to next underlying weight pattern. */ underlyingWeightPattern [numberOfSyllables] += 1; for (long isyll = numberOfSyllables; isyll >= 2; isyll --) { if (underlyingWeightPattern [isyll] > maximumUnderlyingWeight) { underlyingWeightPattern [isyll] = 1; underlyingWeightPattern [isyll - 1] += 1; } } } } /* Compute violation marks. */ for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { computeViolationMarks (& tableau -> candidates [icand]); therror } } OTGrammar_checkIndex (me.peek()); therror OTGrammar_newDisharmonies (me.peek(), 0.0); if (trochaicityConstraint == 1) { OTGrammar_removeConstraint (me.peek(), L"Trochaic"); } else { OTGrammar_removeConstraint (me.peek(), L"FtNonfinal"); } if (! includeFootBimoraic) OTGrammar_removeConstraint (me.peek(), L"FtBimor"); if (! includeFootBisyllabic) OTGrammar_removeConstraint (me.peek(), L"FtBisyl"); if (! includePeripheral) OTGrammar_removeConstraint (me.peek(), L"Peripheral"); if (nonfinalityConstraint == 1) { OTGrammar_removeConstraint (me.peek(), L"MainNonfinal"); OTGrammar_removeConstraint (me.peek(), L"HeadNonfinal"); } else if (nonfinalityConstraint == 2) { OTGrammar_removeConstraint (me.peek(), L"HeadNonfinal"); OTGrammar_removeConstraint (me.peek(), L"Nonfinal"); } else { OTGrammar_removeConstraint (me.peek(), L"MainNonfinal"); OTGrammar_removeConstraint (me.peek(), L"Nonfinal"); } if (! includeClashAndLapse) { OTGrammar_removeConstraint (me.peek(), L"*Clash"); OTGrammar_removeConstraint (me.peek(), L"*Lapse"); } if (! includeCodas) { OTGrammar_removeConstraint (me.peek(), L"WeightByPosition"); OTGrammar_removeConstraint (me.peek(), L"*C\\mu"); } if (includeCodas) { for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { replaceOutput (& tableau -> candidates [icand]); } } } return me.transfer(); } catch (MelderError) { Melder_throw ("Metrics grammar not created."); } } /* End of file OTGrammar_ex_metrics.cpp */ sources_5316/gram/OTMulti_def.h0000644000176700017670000000402411621503323015171 0ustar paulpaul/* OTMulti_def.h * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT OTConstraint oo_DEFINE_STRUCT (OTConstraint) oo_STRING (name) oo_DOUBLE (ranking) oo_DOUBLE (disharmony) oo_FROM (2) oo_DOUBLE (plasticity) oo_ENDFROM #if oo_READING if (localVersion < 2) { plasticity = 1.0; } #endif #if !oo_READING && !oo_WRITING oo_INT (tiedToTheLeft) oo_INT (tiedToTheRight) #endif oo_END_STRUCT (OTConstraint) #undef ooSTRUCT #define ooSTRUCT OTCandidate oo_DEFINE_STRUCT (OTCandidate) oo_STRING (string) oo_LONG (numberOfConstraints) oo_INT_VECTOR (marks, numberOfConstraints) #if !oo_READING && !oo_WRITING oo_DOUBLE (harmony) oo_DOUBLE (probability) #endif oo_END_STRUCT (OTCandidate) #undef ooSTRUCT #define ooSTRUCT OTMulti oo_DEFINE_CLASS (OTMulti, Data) oo_FROM (1) oo_ENUM (kOTGrammar_decisionStrategy, decisionStrategy) oo_ENDFROM oo_FROM (2) oo_DOUBLE (leak) oo_ENDFROM oo_LONG (numberOfConstraints) oo_STRUCT_VECTOR (OTConstraint, constraints, numberOfConstraints) oo_LONG_VECTOR (index, numberOfConstraints) oo_LONG (numberOfCandidates) oo_STRUCT_VECTOR (OTCandidate, candidates, numberOfCandidates) #if oo_READING OTMulti_sort (this); #endif #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (OTMulti) #undef ooSTRUCT /* End of file OTMulti_def.h */ sources_5316/gram/manual_gram.cpp0000644000176700017670000025623011647047257015665 0ustar paulpaul/* manual_gram.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" #include "OTGrammar.h" static void draw_NoCoda_pat (Graphics g) { OTGrammar ot = OTGrammar_create_NoCoda_grammar (); OTGrammar_drawTableau (ot, g, false, L"pat"); forget (ot); } static void draw_NoCoda_pa (Graphics g) { OTGrammar ot = OTGrammar_create_NoCoda_grammar (); OTGrammar_drawTableau (ot, g, false, L"pa"); forget (ot); } static void draw_NoCoda_reverse (Graphics g) { OTGrammar ot = OTGrammar_create_NoCoda_grammar (); ot -> index [1] = 2; ot -> index [2] = 1; OTGrammar_drawTableau (ot, g, false, L"pat"); forget (ot); } static void draw_NPA_assimilate_anpa (Graphics g) { OTGrammar ot = OTGrammar_create_NPA_grammar (); ot -> index [1] = 3; ot -> index [2] = 1; ot -> index [3] = 2; OTGrammar_drawTableau (ot, g, false, L"an+pa"); forget (ot); } static void draw_NPA_assimilate_atma (Graphics g) { OTGrammar ot = OTGrammar_create_NPA_grammar (); ot -> index [1] = 3; ot -> index [2] = 1; ot -> index [3] = 2; OTGrammar_drawTableau (ot, g, false, L"at+ma"); forget (ot); } static void draw_NPA_faithful_anpa (Graphics g) { OTGrammar ot = OTGrammar_create_NPA_grammar (); ot -> index [1] = 3; ot -> index [2] = 2; ot -> index [3] = 1; OTGrammar_drawTableau (ot, g, false, L"an+pa"); forget (ot); } static void draw_NPA_faithful_atma (Graphics g) { OTGrammar ot = OTGrammar_create_NPA_grammar (); ot -> index [1] = 3; ot -> index [2] = 2; ot -> index [3] = 1; OTGrammar_drawTableau (ot, g, false, L"at+ma"); forget (ot); } static void draw_Wolof_ItI (Graphics g) { OTGrammar ot = OTGrammar_create_tongueRoot_grammar (1, 4); OTGrammar_drawTableau (ot, g, false, L"\\ict\\ic"); forget (ot); } static void draw_Wolof_itE (Graphics g) { OTGrammar ot = OTGrammar_create_tongueRoot_grammar (1, 4); OTGrammar_drawTableau (ot, g, false, L"it\\ep"); forget (ot); } static void draw_Wolof_etE (Graphics g) { OTGrammar ot = OTGrammar_create_tongueRoot_grammar (1, 4); OTGrammar_drawTableau (ot, g, false, L"et\\ep"); forget (ot); } static void draw_Wolof_schwatschwa (Graphics g) { OTGrammar ot = OTGrammar_create_tongueRoot_grammar (1, 4); OTGrammar_drawTableau (ot, g, false, L"\\swt\\sw"); forget (ot); } static void draw_Infant_swtI (Graphics g) { OTGrammar ot = OTGrammar_create_tongueRoot_grammar (1, 3); ot -> constraints [1]. disharmony = 3; ot -> constraints [2]. disharmony = 4; ot -> constraints [3]. disharmony = 2; ot -> constraints [4]. disharmony = 1; ot -> constraints [5]. disharmony = 5; OTGrammar_sort (ot); OTGrammar_drawTableau (ot, g, false, L"\\swt\\ic"); forget (ot); } void manual_gram_init (ManPages me); void manual_gram_init (ManPages me) { MAN_BEGIN (L"constraints", L"ppgb", 20021105) INTRO (L"In @@Optimality Theory@, the `rules' that an output form has to satisfy. Since there can be many constraints " "and these constraints can conflict with each other, the constraints are %violable and the highest-ranked constraints " "have the largest say in determining the optimal output.") NORMAL (L"See the @@OT learning@ tutorial for many examples.") MAN_END MAN_BEGIN (L"Create tongue-root grammar...", L"ppgb", 20021204) INTRO (L"A command in the @@New menu@ for creating an @OTGrammar object with a tongue-root-harmony grammar.") NORMAL (L"These OTGrammar grammars only accept inputs of the form V__1_tV__2_, where V__1_ and V__2_ are " "chosen from the six front vowels i, \\ic, e, \\ep, \\sw, and a. In a text field, these " "vowels should be typed as $$##i#$, $$##\\bsic#$, $$##e#$, $$##\\bsep#$, $$##\\bssw#$, " "and $$##a#$, respectively (see @@Special symbols@).") NORMAL (L"The following phonological features are relevant:") LIST_ITEM (L"\t\tATR\tRTR") LIST_ITEM (L"\thigh\ti\t\\ic") LIST_ITEM (L"\tmid\te\t\\ep") LIST_ITEM (L"\tlow\t\\sw\ta") ENTRY (L"Constraints") NORMAL (L"The resulting OTGrammar will usually contain at least the following five constraints:") TAG (L"*[rtr / hi]") DEFINITION (L"\"do not implement [retracted tongue root] if the vowel is high.\"") TAG (L"*[atr / lo]") DEFINITION (L"\"do not implement [advanced tongue root] if the vowel is low.\"") TAG (L"P\\s{ARSE} (rtr)") DEFINITION (L"\"make an underlying [retracted tongue root] specification surface.\"") TAG (L"P\\s{ARSE} (atr)") DEFINITION (L"\"make an underlying [advanced tongue root] specification surface.\"") TAG (L"*G\\s{ESTURE} (contour)") DEFINITION (L"\"do not go from advanced to retracted tongue root, nor the other way around, within a word.\"") NORMAL (L"This set of constraints thus comprises: ") LIST_ITEM (L"\\bu two %%##grounding conditions#% (@@Archangeli & Pulleyblank (1994)@), " "which we can see as gestural constraints;") LIST_ITEM (L"\\bu two %%##faithfulness constraints#%, which favour the similarity between input and output, " "and can be seen as implementing the principle of maximization of perceptual contrast;") LIST_ITEM (L"\\bu a %%##harmony constraint#%, which, if crucially ranked higher than at least one faithfulness constraint, " "forces %%##tongue-root harmony#%.") NORMAL (L"In addition, there may be the following four constraints:") TAG (L"*[rtr / mid]") DEFINITION (L"\"do not implement [retracted tongue root] if the vowel is mid; universally ranked lower " "than *[rtr / hi].\"") TAG (L"*[rtr / lo]") DEFINITION (L"\"do not implement [retracted tongue root] if the vowel is low; universally ranked lower " "than *[rtr / mid].\"") TAG (L"*[atr / mid]") DEFINITION (L"\"do not implement [advanced tongue root] if the vowel is mid; universally ranked lower " "than *[atr / lo].\"") TAG (L"*[atr / hi]") DEFINITION (L"\"do not implement [advanced tongue root] if the vowel is high; universally ranked lower " "than *[atr / mid].\"") NORMAL (L"The universal rankings referred to are due to the %%##local-ranking principle#% (@@Boersma (1998)@). " "A learning algorithm may enforce this principle, e.g., if *[rtr / hi] falls down the ranking scale, " "*[rtr / mid] may be pushed along.") NORMAL (L"For information on learning these tongue-root grammars, see @@OT learning@ " "and @@Boersma (2000)@.") MAN_END MAN_BEGIN (L"Optimality Theory", L"ppgb", 20021105) INTRO (L"A framework for transferring one linguistic representation into another, " "e.g. transferring an underlying form into a surface form. Before @@Prince & Smolensky (1993)@, " "phonologists tended to this with a sequentially ordered set of rules, each of which transferred a representation " "into another. With @OT (that's the abbreviation), there are no intermediate steps in the derivation, but a set of ranked " "@constraints chooses the optimal output form from a set of candidates.") NORMAL (L"In Praat, you can draw Optimality-Theoretic tableaus and simulate Optimality-Theoretic learning. " "See the @@OT learning@ tutorial.") MAN_END MAN_BEGIN (L"OT", L"ppgb", 20021105) INTRO (L"An abbreviation for @@Optimality Theory@.") MAN_END MAN_BEGIN (L"OT learning", L"ppgb", 20070423) INTRO (L"This tutorial describes how you can draw Optimality-Theoretic and Harmonic-Grammar tableaus and " "simulate Optimality-Theoretic and Harmonic-Grammar learning with Praat.") NORMAL (L"You can read this tutorial sequentially with the help of the \"< 1\" and \"1 >\" buttons.") LIST_ITEM (L"1. @@OT learning 1. Kinds of grammars|Kinds of grammars@ (ordinal and stochastic, @OTGrammar)") LIST_ITEM (L"2. @@OT learning 2. The grammar|The grammar@") LIST_ITEM1 (L"2.1. @@OT learning 2.1. Viewing a grammar|Viewing a grammar@ (N\\s{O}C\\s{ODA} example, @OTGrammarEditor)") LIST_ITEM1 (L"2.2. @@OT learning 2.2. Inside the grammar|Inside the grammar@ (saving, inspecting)") LIST_ITEM1 (L"2.3. @@OT learning 2.3. Defining your own grammar|Defining your own grammar@") LIST_ITEM1 (L"2.4. @@OT learning 2.4. Evaluation|Evaluation@ (noise)") LIST_ITEM1 (L"2.5. @@OT learning 2.5. Editing a grammar|Editing a grammar@") LIST_ITEM1 (L"2.6. @@OT learning 2.6. Variable output|Variable output@ (place assimilation example)") LIST_ITEM1 (L"2.7. @@OT learning 2.7. Tableau pictures|Tableau pictures@ (printing, EPS)") LIST_ITEM1 (L"2.8. @@OT learning 2.8. Asking for one output|Asking for one output@") LIST_ITEM1 (L"2.9. @@OT learning 2.9. Output distributions|Output distributions@") LIST_ITEM (L"3. @@OT learning 3. Generating language data|Generating language data@") LIST_ITEM1 (L"3.1. @@OT learning 3.1. Data from a pair distribution|Data from a pair distribution@") LIST_ITEM1 (L"3.2. @@OT learning 3.2. Data from another grammar|Data from another grammar@ (tongue-root-harmony example)") LIST_ITEM (L"4. @@OT learning 4. Learning an ordinal grammar|Learning an ordinal grammar@") LIST_ITEM (L"5. @@OT learning 5. Learning a stochastic grammar|Learning a stochastic grammar@") LIST_ITEM (L"6. @@OT learning 6. Shortcut to grammar learning|Shortcut to grammar learning@") LIST_ITEM (L"7. @@OT learning 7. Learning from overt forms|Learning from overt forms@") MAN_END MAN_BEGIN (L"OT learning 1. Kinds of grammars", L"ppgb", 20100330) INTRO (L"This is chapter 1 of the @@OT learning@ tutorial.") NORMAL (L"According to @@Prince & Smolensky (1993)@, an @@Optimality Theory|Optimality-Theoretic@ (@OT) grammar " "consists of a number of ranked @constraints. " "For every possible input (usually an underlying form), GEN (the generator) generates a (possibly very large) number of " "%%output candidates%, and the ranking order of the constraints determines the winning candidate, " "which becomes the single optimal output.") NORMAL (L"According to @@Prince & Smolensky (1993)@ and @@Smolensky & Legendre (2006)@, a Harmonic Grammar (HG) " "consists of a number of weighted @constraints. " "The winning candidate, which becomes the single optimal output, is the one with the greatest %harmony, which " "is a measure of goodness determined by the weights of the constraints violated by each candidate.") NORMAL (L"In OT, ranking is %strict, i.e., if a constraint %A is ranked higher than the constraints %B, %C, and %D, " "a candidate that violates only constraint %A will always be beaten by any candidate that respects %A " "(and any higher constraints), even if it violates %B, %C, and %D.") NORMAL (L"In HG, weighting is %additive, i.e., a candidate that only violates a constraint %A with a weight of 100 " "has a harmony of -100 and will therefore beat a candidate that violates both a constraint %B with a weight of 70 " "and a constraint %C with a weight of 40 and therefore has a harmony of only -110. Also, two violations of constraint %B " "(harmony 2 * -70 = -140) are worse than one violation of constraint %A (harmony -100).") ENTRY (L"1. Ordinal OT grammars") NORMAL (L"Because only the ranking order of the constraints plays a role in evaluating the output candidates, " "Prince & Smolensky took an OT grammar to contain no absolute ranking values, i.e., they accepted only an ordinal relation " "between the constraint rankings. For such a grammar, @@Tesar & Smolensky (1998)@ devised an on-line learning algorithm " "(Error-Driven Constraint Demotion, EDCD) that changes the ranking order " "whenever the form produced by the learner is different from the adult form " "(a corrected version of the algorithm can be found in @@Boersma (2009b)@). Such a learning step " "can sometimes lead to a large change in the behaviour of the grammar.") ENTRY (L"2. Stochastic OT grammars") NORMAL (L"The EDCD algorithm is fast and convergent. As a model of language acquisition, however, its drawbacks are that it " "is extremely sensitive to errors in the learning data and that it does not show realistic gradual learning curves. " "For these reasons, @@Boersma (1997)@ " "proposed stochastic OT grammars in which every constraint has a %%ranking value% along a continuous ranking scale, " "and a small amount of %noise is added to this ranking value at evaluation time. " "The associated error-driven on-line learning algorithm (Gradual Learning Algorithm, GLA) effects small changes in the " "ranking values of the constraints with every learning step. An added virtue of the GLA is that it can learn " "languages with optionality and variation, which was something that EDCD could not do. " "For how this algorithm works on some traditional phonological problems, see @@Boersma & Hayes (2001)@.") NORMAL (L"Ordinal OT grammars can be seen as a special case of the more general stochastic OT grammars: " "they have integer ranking values (%strata) and zero evaluation noise. " "In Praat, therefore, every constraint is taken to have a ranking value, " "so that you can do stochastic as well as ordinal OT.") ENTRY (L"3. Categorical Harmonic Grammars") NORMAL (L"@@J\\a\"ger (2003)@ and @@Soderstrom, Mathis & Smolensky (2006)@ devised an on-line learning algorithm " "for Harmonic Grammars (stochastic gradient ascent). As proven by @@Fischer (2005)@, " "this algorithm is guaranteed to converge upon a correct grammar, if there exists one that handles the data.") ENTRY (L"4. Stochastic Harmonic Grammars") NORMAL (L"There are two kinds of stochastic models of HG, namely MaxEnt (= Maximum Entropy) grammars " "(@@Smolensky (1986)@, @@J\\a\"ger (2003)@), in which the probablity of a candidate winning depends on its harmony, " "and Noisy HG (@@Boersma & Escudero (2008)@, @@Boersma & Pater (2008)@), in which noise is added to constraint weights " "at evaluation time, as in Stochastic OT.") NORMAL (L"The algorithm by @@J\\a\"ger (2003)@ and @@Soderstrom, Mathis & Smolensky (2006)@ " "can learn languages with optionality and variation (@@Boersma & Pater (2008)@).") ENTRY (L"The OTGrammar object") NORMAL (L"An OT grammar is implemented as an @OTGrammar object. " "In an OTGrammar object, you specify all the constraints, all the possible inputs and all their possible outputs.") MAN_END MAN_BEGIN (L"OT learning 2. The grammar", L"ppgb", 20000122) INTRO (L"This is chapter 2 of the @@OT learning@ tutorial.") NORMAL (L"We can ask the grammar to produce an output form for any input form that is in its list of tableaus.") LIST_ITEM (L"2.1. @@OT learning 2.1. Viewing a grammar|Viewing a grammar@ (N\\s{O}C\\s{ODA} example, @OTGrammarEditor)") LIST_ITEM (L"2.2. @@OT learning 2.2. Inside the grammar|Inside the grammar@ (saving, inspecting)") LIST_ITEM (L"2.3. @@OT learning 2.3. Defining your own grammar|Defining your own grammar@") LIST_ITEM (L"2.4. @@OT learning 2.4. Evaluation|Evaluation@ (noise)") LIST_ITEM (L"2.5. @@OT learning 2.5. Editing a grammar|Editing a grammar@") LIST_ITEM (L"2.6. @@OT learning 2.6. Variable output|Variable output@ (place assimilation example)") LIST_ITEM (L"2.7. @@OT learning 2.7. Tableau pictures|Tableau pictures@ (printing, EPS files)") LIST_ITEM (L"2.8. @@OT learning 2.8. Asking for one output|Asking for one output@") LIST_ITEM (L"2.9. @@OT learning 2.9. Output distributions|Output distributions@") MAN_END MAN_BEGIN (L"OT learning 2.1. Viewing a grammar", L"ppgb", 20070725) NORMAL (L"Consider a language where the underlying form /pat/ leads to the surface form [pa], " "presumably because the structural constraint N\\s{O}C\\s{ODA} outranks the faithfulness constraint P\\s{ARSE}.") NORMAL (L"To create such a grammar in Praat, choose ##Create NoCoda grammar# from the Optimality Theory submenu of the @@New menu@. " "An @OTGrammar object will then appear in the list of objects. " "If you click ##View & Edit#, an @OTGrammarEditor will show up, containing:") LIST_ITEM (L"1. the constraint list, sorted by %#disharmony (= ranking value + noise):") LIST_ITEM1 (L" ") LIST_ITEM1 (L"\t\t %%ranking value%\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 100.000\t 100.000\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 90.000\t 1.000") LIST_ITEM1 (L" ") LIST_ITEM (L"2. the tableaus for the two possible inputs /pat/ and /pa/:") PICTURE (3.0, 1.0, draw_NoCoda_pat) PICTURE (3.0, 0.7, draw_NoCoda_pa) NORMAL (L"From the first tableau, we see that the underlying form /pat/ will surface as [pa], " "because the alternative [pat] violates a constraint (namely, N\\s{O}C\\s{ODA}) with a higher disharmony than does [pa], " "which only violates P\\s{ARSE}, which has a lower disharmony.") NORMAL (L"Note the standard OT tableau layout: asterisks (*) showing violations, exclamation marks (!) showing crucial violations, " "greying of cells that do not contribute to determining the winning candidate, and a finger (\\pf) pointing to the winner " "(this may look like a plus sign (+) if you don't have the Zapf Dingbats font installed on your computer or printer). " "An HG tableau contains asterisks and a pointing finger, but no exclamation marks or grey cells.") NORMAL (L"The second tableau shows that /pa/ always surfaces as [pa], which is no wonder since this is " "the only candidate. All cells are grey because none of them contributes to the determination of the winner.") MAN_END MAN_BEGIN (L"OT learning 2.2. Inside the grammar", L"ppgb", 20110129) NORMAL (L"You can save an @OTGrammar grammar as a text file by choosing @@Save as text file...@ from the #Save menu " "of the Objects window. For the N\\s{O}C\\s{ODA} example, the contents of the file will look like:") CODE (L"File type = \"ooTextFile\"") CODE (L"Object class = \"OTGrammar 2\"") CODE (L"decisionStrategy = ") CODE (L"leak = 0") CODE (L"2 constraints") CODE (L"constraint [1]: \"N\\bss{O}C\\bss{ODA}\" 100 100 1 ! NOCODA") CODE (L"constraint [2]: \"P\\bss{ARSE}\" 90 90 1 ! PARSE") CODE (L" ") CODE (L"0 fixed rankings") CODE (L" ") CODE (L"2 tableaus") CODE (L"input [1]: \"pat\" 2") CODE1 (L"candidate [1]: \"pa\" 0 1") CODE1 (L"candidate [2]: \"pat\" 1 0") CODE (L"input [2]: \"pa\" 1") CODE1 (L"candidate [1]: \"pa\" 0 0") NORMAL (L"To understand more about this data structure, consult the @OTGrammar class description " "or click #Inspect after selecting the OTGrammar object. The $$\"\\bss{...}\"$ braces ensure that " "the constraint names show up with their traditional small capitals (see @@Text styles@).") NORMAL (L"You can read this text file into Praat again with @@Read from file...@ from the #Open menu in the Objects window.") MAN_END MAN_BEGIN (L"OT learning 2.3. Defining your own grammar", L"ppgb", 20110129) NORMAL (L"By editing a text file created from an example in the @@New menu@, you can define your own OT grammars.") NORMAL (L"As explained at @@Save as text file...@, Praat is quite resilient about its text file formats. " "As long as the strings and numbers appear in the correct order, you can redistribute the data " "across the lines, add all kinds of comments, or leave the comments out. " "For the N\\s{O}C\\s{ODA} example, the text file could also have looked like:") CODE (L"\"ooTextFile\"") CODE (L"\"OTGrammar 2\"") CODE (L"") CODE (L"0.0 ! leak") CODE (L"2 ! number of constraints") CODE (L"\"N\\bss{O}C\\bss{ODA}\" 100 100 1") CODE (L"\"P\\bss{ARSE}\" 90 90 1") CODE (L"0 ! number of fixed rankings") CODE (L"2 ! number of accepted inputs") CODE (L"\"pat\" 2 ! input form with number of output candidates") CODE1 (L"\"pa\" 0 1 ! first candidate with violations") CODE1 (L"\"pat\" 1 0 ! second candidate with violations") CODE (L"\"pa\" 1 ! input form with number of candidates") CODE1 (L"\"pa\" 0 0") NORMAL (L"To define your own grammar, you just provide a number of constraints and their rankings, " "and all the possible input forms with all their output candidates, and all the constraint violations " "for each candidate. The order in which you specify the constraints is free (you don't have to specify " "the highest-ranked first), as long as the violations are in the same order; you could also have reversed " "the order of the two input forms, as long as the corresponding candidates follow them; " "and, you could also have reversed the order of the candidates within the /pat/ tableau, " "as long as the violations follow the output forms. Thus, you could just as well have written:") CODE (L"\"ooTextFile\"") CODE (L"\"OTGrammar 2\"") CODE (L" 0.0") CODE (L"2") CODE (L"\"P\\bss{ARSE}\" 90 90 1.0") CODE (L"\"N\\bss{O}C\\bss{ODA}\" 100 100 1.0") CODE (L"0") CODE (L"2") CODE (L"\"pa\" 1") CODE1 (L"\"pa\" 0 0") CODE (L"\"pat\" 2") CODE1 (L"\"pat\" 0 1") CODE1 (L"\"pa\" 1 0") NORMAL (L"The $$$ thing in the above refers to the %%decision strategy%. " "In this tutorial I mostly assume OT's strict ranking, " "but you can experiment with Smolensky's $$$ (where the constraint disharmonies represent addable, " "possibly negative weights), or with Frank Keller's $$$ (like Harmonic Grammar, but with the restriction " "that negative disharmonies do not count), or with $$$ (like Harmonic Grammar, but with the restriction " "that disharmonies below 1.0 have weight 1.0), or with $$$ (where the weights are exp(disharmony), somewhere " "between Harmonic Grammar and Linear OT), or with a $$$ grammar " "(where the probability that a candidate is chosen is proportional to exp(-disharmony)).") NORMAL (L"The $$leak$ thing in the above refers to the amount to which constraint weights (especially in Harmonic Grammar) " "can leak while learning.") MAN_END MAN_BEGIN (L"OT learning 2.4. Evaluation", L"ppgb", 20070725) NORMAL (L"In an Optimality-Theoretic model of grammar, %#evaluation refers to the determination " "of the winning candidate on the basis of the constraint ranking.") NORMAL (L"In an ordinal OT model of grammar, repeated evaluations will yield the same winner again and again. " "We can simulate this behaviour with our N\\s{O}C\\s{ODA} example. " "In the editor, you can choose ##Evaluate (zero noise)# or use its keyboard shortcut Command-0 (= Command-zero). " "Repeated evaluations (keep Command-0 pressed) will always yield the following grammar:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 100.000\t 100.000\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 90.000\t 1.000") NORMAL (L"In a stochastic OT model of grammar, repeated evaluations will yield different disharmonies each time. " "To see this, choose ##Evaluate (noise 2.0)# or use its keyboard shortcut Command-2. " "Repeated evaluations will yield grammars like the following:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 100.000\t 100.427\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 87.502\t 1.000") NORMAL (L"and") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 100.000\t 101.041\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 90.930\t 1.000") NORMAL (L"and") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 100.000\t 96.398\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 89.482\t 1.000") NORMAL (L"The disharmonies vary around the ranking values, " "according to a Gaussian distribution with a standard deviation of 2.0. " "The winner will still be [pa] in almost all cases, because the probability of bridging " "the gap between the two ranking values is very low, namely 0.02 per cent according " "to @@Boersma (1998)@, page 332.") NORMAL (L"With a noise much higher than 2.0, the chances of P\\s{ARSE} outranking N\\s{O}C\\s{ODA} will rise. " "To see this, choose ##Evaluate...# and supply 5.0 for the noise. Typical outcomes are:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 100.000\t 92.634\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 86.931\t 1.000") NORMAL (L"and") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 100.000\t 101.162\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 85.311\t 1.000") NORMAL (L"and") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 99.778\t 1.000") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 100.000\t 98.711\t 1.000") NORMAL (L"In the last case, the order of the constraints has been reversed. " "You will see that [pat] has become the winning candidate:") PICTURE (3.0, 1.0, draw_NoCoda_reverse) NORMAL (L"However, in the remaining part of this tutorial, we will stick with a noise " "with a standard deviation of 2.0. This specific number ensures that we can " "model fairly rigid rankings by giving the constraints a ranking difference of 10, a nice round number. " "Also, the learning algorithm will separate many constraints in such a way that " "the differences between their ranking values are in the vicinity of 10.") MAN_END MAN_BEGIN (L"OT learning 2.5. Editing a grammar", L"ppgb", 20110808) NORMAL (L"In the N\\s{O}C\\s{ODA} example, the winning candidate for the input /pat/ was always [pa].") NORMAL (L"To make [pat] the winner instead, N\\s{O}C\\s{ODA} should be ranked lower than P\\s{ARSE}. " "To achieve this even with zero noise, go to the editor and select the N\\s{O}C\\s{ODA} constraint by clicking on it " "(a spade symbol \\sp will mark the selected constraint), " "and choose ##Edit ranking...# from the #Edit menu, or use the keyboard shortcut Command-E.") NORMAL (L"In the resulting command window, we lower the ranking of the constraint from 100 to 80, and click OK. " "This is what you will see in the editor:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t\\sp ##N\\s{O}C\\s{ODA}#\t 80.000\t 103.429\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 88.083\t 1.000") PICTURE (3.0, 1.0, draw_NoCoda_pat) NORMAL (L"Nothing has happened to the tableau, because the disharmonies still have their old values. So choose " "##Evaluate (noise 2.0)# (Command-2) or ##Evaluate (zero noise)# (Command-0). The new disharmonies " "will centre around the new ranking values, and we see that [pat] becomes the new winner:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 90.000\t 90.743\t 1.000") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 80.000\t 81.581\t 1.000") PICTURE (3.0, 1.0, draw_NoCoda_reverse) MAN_END MAN_BEGIN (L"OT learning 2.6. Variable output", L"ppgb", 20070725) NORMAL (L"Each time you press Command-2, which invokes the command ##Evaluate (noise 2.0)# from the #Edit menu, " "you will see the disharmonies changing. If the distance between the constraint rankings is 10, however, " "the winning candidates will very probably stay the same.") NORMAL (L"So starting from the N\\s{O}C\\s{ODA} example, we edit the rankings of the constraints again, " "setting the ranking value of P\\s{ARSE} to 88 and that of N\\s{O}C\\s{ODA} to 85. If we now press Command-2 " "repeatedly, we will get [pat] in most of the cases, " "but we will see the finger pointing at [pa] in 14 percent of the cases:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 88.000\t 87.421\t 1.000") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 85.000\t 85.585\t 1.000") PICTURE (3.0, 1.0, draw_NoCoda_reverse) NORMAL (L"but") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##N\\s{O}C\\s{ODA}#\t 85.000\t 87.128\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE}#\t 88.000\t 85.076\t 1.000") PICTURE (3.0, 1.0, draw_NoCoda_pat) NORMAL (L"As a more functionally oriented example, we consider nasal place assimilation. " "Suppose that the underlying sequence /an+pa/ surfaces as the assimilated [ampa] " "in 80 percent of the cases, and as the faithful [anpa] in the remaining 20 percent, " "while the non-nasal stop /t/ never assimilates. " "This can be achieved by having the articulatory constraint *G\\s{ESTURE} " "ranked at a short distance above *R\\s{EPLACE} (n, m):") CODE (L"\"ooTextFile\"") CODE (L"\"OTGrammar 2\"") CODE (L"decisionStrategy = ") CODE (L"leak = 0.0") CODE (L"3 constraints") CODE (L"\"*G\\bss{ESTURE}\" 102.7 0 1") CODE (L"\"*R\\bss{EPLACE} (n, m)\" 100.0 0 1") CODE (L"\"*R\\bss{EPLACE} (t, p)\" 112.0 0 1") CODE (L"0 fixed rankings") CODE (L"2 tableaus") CODE (L"\"an+pa\" 2") CODE1 (L"\"anpa\" 1 0 0") CODE1 (L"\"ampa\" 0 1 0") CODE (L"\"at+ma\" 2") CODE1 (L"\"atma\" 1 0 0") CODE1 (L"\"apma\" 0 0 1") NORMAL (L"You can create this grammar with ##Create place assimilation grammar# from the @@New menu@. " "In the editor, it will often look like follows:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (t, p)#\t 112.000\t 109.806\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE}#\t 102.700\t 102.742\t 1.000") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (n, m)#\t 100.000\t 101.044\t 1.000") PICTURE (4.0, 1.0, draw_NPA_assimilate_anpa) PICTURE (4.0, 1.0, draw_NPA_assimilate_atma) NORMAL (L"If you keep the Command-2 keys pressed, however, you will see that the tableaus change " "into something like the following in approximately 20 percent of the cases:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (t, p)#\t 112.000\t 113.395\t 1.000") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (n, m)#\t 100.000\t 103.324\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE}#\t 102.700\t 101.722\t 1.000") PICTURE (4.0, 1.0, draw_NPA_faithful_anpa) PICTURE (4.0, 1.0, draw_NPA_faithful_atma) NORMAL (L"We see that /at+ma/ always surfaces at [atma], because *R\\s{EPLACE} (t, p) is ranked much higher " "than the other two, and that the output of /an+pa/ is variable because of the close rankings " "of *G\\s{ESTURE} and *R\\s{EPLACE} (n, m).") NORMAL (L"If you try this with a Harmonic Grammar or in Linear OT, you will see the same kind of variation. " "Although in HG, e.g. in @@Smolensky & Legendre (2006)@, the variation is usually obtained at the candidate level, " "namely by giving each candidate a probability proportional to exp(%harmony/%temperature), " "in our version of HG the variation comes about at the constraint level, " "namely by the noise that is temporarily added to the ranking of each constraint at evaluation time.") MAN_END MAN_BEGIN (L"OT learning 2.7. Tableau pictures", L"ppgb", 20110129) NORMAL (L"To show a tableau in the @@Picture window@ instead of in the editor, " "you select an @OTGrammar object and click ##Draw tableau...#. " "After you specify the input form, a tableau is drawn with the current font and size " "at the location of the current selection (%viewport) in the Picture window. The top left corner of the tableau " "is aligned with the top left corner of the selection. You can draw more than one object into the Picture " "window, whose menus also allow you to add a lot of graphics of your own design.") NORMAL (L"Besides printing the entire picture (with @@Print...@), you can save a part of it to an EPS file " "for inclusion into your favourite word processor (with @@Save as EPS file...@). " "For the latter to succeed, make sure that the selection includes at least your tableau; " "otherwise, some part of your tableau may end up truncated.") MAN_END MAN_BEGIN (L"OT learning 2.8. Asking for one output", L"ppgb", 20110808) NORMAL (L"To ask the grammar to produce a single output for a specified input form, " "you can choose @@OTGrammar: Input to output...@. The command window will ask you to provide " "an input form and the strength of the noise (the standard value is 2.0 again). " "This will perform an evaluation and write the result into the Info window.") NORMAL (L"If you are viewing the grammar in the @OTGrammarEditor, you will see the disharmonies change, " "and if the grammar allows variation, you will see that the winner in the tableau in the editor " "varies with the winner shown in the Info window.") NORMAL (L"Since the editor shows more information than the Info window, " "this command is not very useful except for purposes of scripting. " "See the following page for some related but more useful commands.") MAN_END MAN_BEGIN (L"OT learning 2.9. Output distributions", L"ppgb", 20110808) NORMAL (L"To ask the grammar to produce %many outputs for a specified input form, " "and collect them in a @Strings object, " "you select an @OTGrammar and choose @@OTGrammar: Input to outputs...|Input to outputs...@.") NORMAL (L"For example, select the object \"OTGrammar assimilation\" from our place assimilation example " "(@@OT learning 2.6. Variable output|\\SS2.6@), and click ##Input to outputs...#. " "In the resulting command window, you specify 1000 trials, a noise strength of 2.0, and \"an+pa\" for the input form.") NORMAL (L"After you click OK, a @Strings object will appear in the list. " "If you click Info, you will see that it contains 1000 strings. " "If you click Inspect, you will see that most of the strings are \"ampa\", " "but some of them are \"anpa\". These are the output forms computed from 1000 evaluations " "for the input /an+pa/.") NORMAL (L"To count how many instances of [ampa] and [anpa] were generated, you select the @Strings object " "and click @@Strings: To Distributions|To Distributions@. You will see a new @Distributions object appear in the list. " "If you draw this to the Picture window (with ##Draw as numbers...#), you will see something like:") LIST_ITEM (L"\tampa\t815") LIST_ITEM (L"\tanpa\t185") NORMAL (L"which means that our grammar, when fed with 1000 /an+pa/ inputs, produced [ampa] 815 times, " "and [anpa] 185 times, which is consistent with our initial guess that a ranking difference of 2.7 " "would cause approximately an 80\\% - 20\\% distribution of [ampa] and [anpa].") ENTRY (L"Checking the distribution hypothesis") NORMAL (L"To see whether the guess of a 2.7 ranking difference is correct, we perform 1,000,000 trials instead of 1000. " "The output distribution (if you have enough memory in your computer) becomes something like " "(set the %Precision to 7 in the #Draw command window):") LIST_ITEM (L"\tampa\t830080") LIST_ITEM (L"\tanpa\t169920") NORMAL (L"The expected values under the 80\\% - 20\\% distribution hypothesis are:") LIST_ITEM (L"\tampa\t800000") LIST_ITEM (L"\tanpa\t200000") NORMAL (L"We compute (e.g. with @@Calculator...@) a %\\ci^2 of 30080^2/800000 + 30080^2/200000 = 5655.04, " "which, of course, is much too high for a distribution with a single degree of freedom. " "So the ranking difference must be smaller. If it is 2.4 (change the ranking of *G\\s{ESTURE} to 102.4), " "the numbers become something like") LIST_ITEM (L"\tampa\t801974") LIST_ITEM (L"\tanpa\t198026") NORMAL (L"which gives a %\\ci^2 of 24.35. By using the Calculator with the formula $$chiSquareQ (24.35, 1)$, " "we find that values larger than this have a probability of 8\\.c10^^-7^ " "under the 80\\% - 20\\% distribution hypothesis, which must therefore be rejected again.") NORMAL (L"Rather than continuing this iterative procedure to find the correct ranking values for an " "80\\% - 20\\% grammar, we will use the Gradual Learning Algorithm " "(@@OT learning 5. Learning a stochastic grammar|\\SS5@) to determine the rankings automatically, " "without any memory of past events other than the memory associated with maintaining the ranking values.") ENTRY (L"Measuring all inputs") NORMAL (L"To measure the outcomes of all the possible inputs at once, you select an @OTGrammar " "and choose @@OTGrammar: To output Distributions...|To output Distributions...@. " "As an example, try this on our place assimilation grammar. You can supply 1000000 for the number of trials, " "and the usual 2.0 for the standard deviation of the noise. " "After you click OK, a @Distributions object will appear in the list. " "If you draw this to the Picture window, the result will look like:") LIST_ITEM (L"\t/an+pa/ \\-> anpa\t169855") LIST_ITEM (L"\t/an+pa/ \\-> ampa\t830145") LIST_ITEM (L"\t/at+ma/ \\-> atma\t999492") LIST_ITEM (L"\t/at+ma/ \\-> apma\t508") NORMAL (L"We see that the number of [apma] outputs is not zero. This is due to the difference of 9.3 " "between the rankings of *R\\s{EPLACE} (t, p) and *G\\s{ESTURE}. If you rank " "*R\\s{EPLACE} (t, p) at 116.0, the number of produced [apma] reduces to about one in a million, " "as you can easily check with some patience.") MAN_END MAN_BEGIN (L"OT learning 3. Generating language data", L"ppgb", 20021204) NORMAL (L"A learner needs two things: a grammar that she can adjust (@@OT learning 2. The grammar|\\SS2@), and language data.") LIST_ITEM (L"3.1. @@OT learning 3.1. Data from a pair distribution|Data from a pair distribution@") LIST_ITEM (L"3.2. @@OT learning 3.2. Data from another grammar|Data from another grammar@ (tongue-root-harmony example)") MAN_END MAN_BEGIN (L"OT learning 3.1. Data from a pair distribution", L"ppgb", 20110131) NORMAL (L"If the grammar contains faithfulness constraints, the learner needs pairs of " "underlying and adult surface forms. For our place assimilation example, she needs a lot of " "/at+ma/ - [atma] pairs, and four times as many /an+pa/ - [ampa] pairs as /an+pa/ - [anpa] pairs. " "We can specify this language-data distribution in a @PairDistribution object, " "which we could simply save as a text file:") CODE (L"\"ooTextFile\"") CODE (L"\"PairDistribution\"") CODE (L"4 pairs") CODE (L"\"at+ma\" \"atma\" 100") CODE (L"\"at+ma\" \"apma\" 0") CODE (L"\"an+pa\" \"anpa\" 20") CODE (L"\"an+pa\" \"ampa\" 80") NORMAL (L"The values appear to represent percentages, but they could also have been 1.0, 0.0, 0.2, and 0.8, " "or any other values with the same proportions. We could also have left out the second pair " "and specified \"3 pairs\" instead of \"4 pairs\" in the third line.") NORMAL (L"We can create this pair distribution with ##Create place assimilation distribution# from the " "Optimality Theory submenu of the @@New menu@ in the Objects window. To see that it really contains " "the above data, you can draw it to the Picture window. To change the values, use Inspect " "(in which case you should remember to click Change after any change).") NORMAL (L"To generate input-output pairs from the above distribution, select the @PairDistribution and click " "@@PairDistribution: To Stringses...|To Stringses...@. " "If you then just click OK, there will appear two @Strings objects in the list, called \"input\" " "(underlying forms) and \"output\" (surface forms). Both contain 1000 strings. If you Inspect them both, " "you can see that e.g. the 377th string in \"input\" corresponds to the 377th string in \"output\", " "i.e., the two series of strings are aligned. See also the example at @@PairDistribution: To Stringses...@.") NORMAL (L"These two Strings objects are sufficient to help an @OTGrammar grammar to change its constraint rankings " "in such a way that the output distributions generated by the grammar match the output distributions " "in the language data. See @@OT learning 5. Learning a stochastic grammar|\\SS5@.") MAN_END MAN_BEGIN (L"OT learning 3.2. Data from another grammar", L"ppgb", 20110128) NORMAL (L"Instead of generating input-output pairs directly from a @PairDistribution object, " "you can also generate input forms and their winning outputs from an @OTGrammar grammar. Of course, " "that's what the language data presented to real children comes from. Our example will be " "a tongue-root harmony grammar.") NORMAL (L"Choose @@Create tongue-root grammar...@ from the Optimality Theory submenu of the @@New menu@. " "Set %%Constraint set% to \"Five\", and %Ranking to \"Wolof\". Click OK. An object called " "\"OTGrammar Wolof\" will appear in the list. Click ##View & Edit#. You will see the following grammar " "appear in the @OTGrammarEditor:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*[rtr / hi]#\t 100.000\t 100.000\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (rtr)#\t 50.000\t 50.000\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE} (contour)#\t 30.000\t 30.000\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (atr)#\t 20.000\t 20.000\t 1.000") LIST_ITEM1 (L"\t##*[atr / lo]#\t 10.000\t 10.000\t 1.000") NORMAL (L"This simplified Wolof grammar, with five constraints with clearly different rankings, is equivalent " "to the traditional OT ranking") FORMULA (L"*[rtr / hi] >> P\\s{ARSE} (rtr) >> *G\\s{ESTURE} (contour) >> P\\s{ARSE} (atr) >> *[atr / lo]") NORMAL (L"These constraints are based on a description of Wolof by " "@@Archangeli & Pulleyblank (1994)|Archangeli & Pulleyblank (1994: 225\\--239)@. " "For the meaning of these constraints, see @@Boersma (1998)|Boersma (1998: 295)@, " "or the @@Create tongue-root grammar...@ manual page.") NORMAL (L"For each input, there are four output candidates: " "the vowel heights will be the same as those in the input, but the tongue-root values of V__1_ and V__2_ are varied. " "For example, for the input [ita] we will have the four candidates " "[ita], [it\\sw], [\\icta], and [\\ict\\sw].") NORMAL (L"With this way of generating candidates, we see that the five constraints are completely ranked. " "First, the absolute prohibition on surface [\\ic] shows that *[rtr / hi] outranks RTR faithfulness " "(otherwise, [\\ict\\ic] would have been the winner):") PICTURE (4.0, 1.5, draw_Wolof_ItI) NORMAL (L"Second, the faithful surfacing of the disharmonic /it\\ep/ shows that RTR faithfulness must outrank " "the harmony (anti-contour) constraint (otherwise, [ite] would have been the winner):") PICTURE (4.0, 1.5, draw_Wolof_itE) NORMAL (L"Third, the RTR-dominant harmonicization of underlying disharmonic /et\\ep/ shows that harmony must outrank ATR faithfulness " "(otherwise, [et\\ep] would have won):") PICTURE (4.0, 1.5, draw_Wolof_etE) NORMAL (L"Finally, the faithful surfacing of the low ATR vowel /\\sw/ even if not forced by harmony, shows that " "ATR faithfulness outranks *[atr / lo] (otherwise, [ata] would have been the winning candidate):") PICTURE (4.0, 1.5, draw_Wolof_schwatschwa) NORMAL (L"These four ranking arguments clearly establish the crucial rankings of all five constraints.") ENTRY (L"Generating inputs from the grammar") NORMAL (L"According to @@Prince & Smolensky (1993)@, the input to an OT grammar can be %anything. " "This is the idea of %%##richness of the base%#. " "When doing a practical investigation, however, we are only interested in the inputs " "that will illustrate the properties of our partial grammars. " "In the case of simplified Wolof, this means the 36 possible V__1_tV__2_ sequences " "where V__1_ and V__2_ are any of the six front vowels i, \\ic, e, \\ep, \\sw, and a " "(see @@Create tongue-root grammar...@).") NORMAL (L"A set of inputs can be generated from an @OTGrammar object by inspecting the list of tableaus. " "So select the Wolof tongue-root grammar and choose @@OTGrammar: Generate inputs...|Generate inputs...@. " "Set %%Number of trials% to 100, and click OK. A @Strings object named \"Wolof_in\" " "will appear in the list. Click Inspect and examine the 100 input strings. " "You will see that they have been randomly chosen from the 36 possible V__1_tV__2_ sequences " "as described at @@Create tongue-root grammar...@:") FORMULA (L"\\epta, et\\ep, \\epti, it\\ep, \\ept\\ep, iti, \\ept\\ic, it\\ic, \\icti, et\\ep, ...") NORMAL (L"Thus, when asked to generate a random input, these grammars produce any of the 36 possible V__1_tV__2_ " "sequences, all with equal probability.") ENTRY (L"Generating outputs from the grammar") NORMAL (L"To compute the outputs for the above set of input forms, select %both the @OTGrammar object " "%and the input @Strings object, and choose @@OTGrammar & Strings: Inputs to outputs...|Inputs to outputs...@, " "perhaps specifying zero evaluation noise. " "A new Strings objects called \"Wolof_out\" will appear in the list. " "If you Inspect it, you will see that it contains a string sequence aligned with the original input strings:") FORMULA (L"\\epta, \\ept\\ep, \\epti, it\\ep, \\ept\\ep, iti, \\epti, iti, iti, \\ept\\ep, ...") NORMAL (L"In this way, we have created two Strings objects, which together form a series of input-output pairs " "needed for learning a grammar that contains faithfulness constraints.") MAN_END MAN_BEGIN (L"OT learning 4. Learning an ordinal grammar", L"ppgb", 20100331) NORMAL (L"With the data from a tongue-root-harmony language with five completely ranked constraints, " "we can have a throw at learning this language, starting with a grammar in which all the constraints " "are ranked at the same height, or randomly ranked, or with articulatory constraints outranking " "faithfulness constraints.") NORMAL (L"Let's try the third of these. Create an infant tongue-root grammar by choosing " "@@Create tongue-root grammar...@ and specifying \"Five\" for the constraint set " "and \"Infant\" for the ranking. The result after a single evaluation will be like:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*G\\s{ESTURE} (contour)#\t 100.000\t 100.631\t 1.000") LIST_ITEM1 (L"\t##*[atr / lo]#\t 100.000\t 100.244\t 1.000") LIST_ITEM1 (L"\t##*[rtr / hi]#\t 100.000\t 97.086\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (rtr)#\t 50.000\t 51.736\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (atr)#\t 50.000\t 46.959\t 1.000") NORMAL (L"Such a grammar produces all kinds of non-adult results. For instance, the input /\\swt\\ic/ " "will surface as [at\\ic]:") PICTURE (4.0, 1.5, draw_Infant_swtI) NORMAL (L"The adult form is very different: [\\swti]. The cause of the discrepancy is in the order of " "the constraints *[atr / lo] and *[rtr / hi], which militate against [\\sw] and [\\ic], respectively. " "Simply reversing the rankings of these two constraints would solve the problem in this case. " "More generally, @@Tesar & Smolensky (1998)@ claim that demoting all the constraints that cause the " "adult form to lose into the stratum just below the highest-ranked constraint " "violated in the learner's form (here, moving *[atr / lo] just below *[rtr / hi] " "into the same stratum as P\\s{ARSE} (rtr)), " "will guarantee convergence to the target grammar, " "%%if there is no variation in the data% (Tesar & Smolensky's algorithm is actually incorrect, " "but can be repaired easily, as shown by @@Boersma (2009b)@).") NORMAL (L"But Tesar & Smolensky's algorithm cannot be used for variable data, since all constraints would be " "tumbling down, exchanging places and producing wildly different grammars at each learning step. " "Since language data do tend to be variable, we need a gradual and balanced learning algorithm, " "and the following algorithm is guaranteed to converge " "to the target language, if that language can be described by a stochastic OT grammar.") NORMAL (L"The reaction of the learner to hearing the mismatch between the adult [\\swti] and her own [at\\ic], " "is simply:") LIST_ITEM (L"1. to move the constraints violated in her own form, i.e. *[rtr / hi] and P\\s{ARSE} (atr), " "up by a small step along the ranking scale, thus decreasing the probability that her form will be the winner " "at the next evaluation of the same input;") LIST_ITEM (L"2. and to move the constraints violated in the adult form, namely *[atr / lo] and P\\s{ARSE} (rtr), " "down along the ranking scale, thus increasing the probability that the adult form will be the learner's " "winner the next time.") NORMAL (L"If the small reranking step (the %#plasticity) is 0.1, the grammar will become:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*G\\s{ESTURE} (contour)#\t 100.000\t 100.631\t 1.000") LIST_ITEM1 (L"\t##*[atr / lo]#\t 99.900\t 100.244\t 1.000") LIST_ITEM1 (L"\t##*[rtr / hi]#\t 100.100\t 97.086\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (rtr)#\t 49.900\t 51.736\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (atr)#\t 50.100\t 46.959\t 1.000") NORMAL (L"The disharmonies, of course, will be different at the next evaluation, with a probability slightly higher " "than 50\\% that *[rtr / hi] will outrank *[atr / lo]. Thus the relative rankings of these two grounding " "constraints have moved into the direction of the adult grammar, in which they are ranked at opposite " "ends of the grammar.") NORMAL (L"Note that the relative rankings of P\\s{ARSE} (atr) and P\\s{ARSE} (rtr) are " "now moving in a direction opposite to where they will have to end up in this RTR-dominant language. " "This does not matter: the procedure will converge nevertheless.") NORMAL (L"We are now going to simulate the infant who learns simplified Wolof. Take an adult Wolof grammar " "and generate 1000 input strings and the corresponding 1000 output strings " "following the procedure described in @@OT learning 3.2. Data from another grammar|\\SS3.2@. " "Now select the infant @OTGrammar and both @Strings objects, and choose @@OTGrammar & 2 Strings: Learn...|Learn...@. " "After you click OK, the learner processes each of the 1000 input-output pairs in succession, " "gradually changing the constraint ranking in case of a mismatch. The resulting grammar may look like:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*[rtr / hi]#\t 100.800\t 98.644\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE} (contour)#\t 89.728\t 94.774\t 1.000") LIST_ITEM1 (L"\t##*[atr / lo]#\t 89.544\t 86.442\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (rtr)#\t 66.123\t 65.010\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (atr)#\t 63.553\t 64.622\t 1.000") NORMAL (L"We already see some features of the target grammar, namely the top ranking of *[rtr / hi] " "and RTR dominance (the mutual ranking of the P\\s{ARSE} constraints). The steps have not been exactly 0.1, " "because we also specified a relative plasticity spreading of 0.1, thus giving steps typically in the range of 0.7 to 1.3. " "The step is also multiplied by the %%constraint plasticity%, which is simply 1.000 in all examples in this tutorial; " "you could set it to 0.0 to prevent a constraint from moving up or down at all. " "The %leak is the part of the constraint weight (especially in Harmonic Grammar) that is thrown away whenever a constraint is reranked; " "e.g if the leak is 0.01 and the step is 0.11, the constraint weight is multiplied by (1 \\-- 0.01\\.c0.11) = 0.9989 before " "the learning step is taken; in this way you could implement forgetful learning of correlations.") NORMAL (L"After learning once more with the same data, the result is:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*[rtr / hi]#\t 100.800\t 104.320\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (rtr)#\t 81.429\t 82.684\t 1.000") LIST_ITEM1 (L"\t##*[atr / lo]#\t 79.966\t 78.764\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE} (contour)#\t 81.316\t 78.166\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (atr)#\t 77.991\t 77.875\t 1.000") NORMAL (L"This grammar now sometimes produces faithful disharmonic utterances, because the P\\s{ARSE} now often " "outrank the gestural constraints at evaluation time. But there is still a lot of variation produced. " "Learning once more with the same data gives:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*[rtr / hi]#\t 100.800\t 100.835\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (rtr)#\t 86.392\t 82.937\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE} (contour)#\t 81.855\t 81.018\t 1.000") LIST_ITEM1 (L"\t##*[atr / lo]#\t 78.447\t 78.457\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (atr)#\t 79.409\t 76.853\t 1.000") NORMAL (L"By inspecting the first column, you can see that the ranking values are already in the same order as in the target grammar, " "so that the learner will produce 100 percent correct adult utterances if her evaluation noise is zero. However, " "with a noise of 2.0, there will still be variation. For instance, the disharmonies above will " "produce [ata] instead of [\\swt\\sw] for underlying /\\swt\\sw/. Learning seven times more " "with the same data gives a reasonable proficiency:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*[rtr / hi]#\t 100.800\t 99.167\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (rtr)#\t 91.580\t 93.388\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE} (contour)#\t 85.487\t 86.925\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (atr)#\t 80.369\t 78.290\t 1.000") LIST_ITEM1 (L"\t##*[atr / lo]#\t 75.407\t 74.594\t 1.000") NORMAL (L"No input forms have error rates above 4 percent now, so the child has learned a lot with only 10,000 data, " "which may be on the order of the number of input data she receives every day.") NORMAL (L"We could have sped up the learning process appreciably by using a plasticity of 1.0 instead of 0.1. " "This would have given a comparable grammar after only 1000 data. After 10,000 data, we would have") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*[rtr / hi]#\t 107.013\t 104.362\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (rtr)#\t 97.924\t 99.984\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE} (contour)#\t 89.679\t 89.473\t 1.000") LIST_ITEM1 (L"\t##P\\s{ARSE} (atr)#\t 81.479\t 83.510\t 1.000") LIST_ITEM1 (L"\t##*[atr / lo]#\t 73.067\t 72.633\t 1.000") NORMAL (L"With this grammar, all the error rates are below 0.2 percent. We see that crucially ranked constraints " "will become separated after a while by a gap of about 10 along the ranking scale.") NORMAL (L"If we have three constraints obligatorily ranked as A >> B >> C in the adult grammar, with ranking differences of 8 between " "A and B and between B and C in the learner's grammar (giving an error rate of 0.2\\% ), the ranking A >> C has a chance of less than 1 in 100 million " "to be reversed at evaluation time. This relativity of error rates is an empirical prediction of our stochastic OT grammar model.") NORMAL (L"Our Harmonic Grammars with constraint noise (Noisy HG) are slightly different in that respect, " "but are capable of learning a constraint ranking for any language that can be generated from an ordinal ranking. " "As proved by @@Boersma & Pater (2008)@, the same learning rule as was devised for MaxEnt grammars by @@J\\a\"ger (2003)@ " "is able to learn all languages generated by %nonnoisy HG grammars as well; " "the GLA, by contrast, failed to converge on 0.4 percent of randomly generated OT languages " "(failures of the GLA on ordinal grammars were discovered first by @@Pater (2008)@). " "This learning rule for HG and MaxEnt is the same as the GLA described above, " "except that the learning step of each constraint is multiplied by " "the difference of the number of violations of this constraint between the correct form and the incorrect winner; " "this multiplication is crucial (without it, stochastic gradient ascent is not guaranteed to converge), " "as was noted by J\\a\"ger for MaxEnt. The same procedure for updating weights occurs " "in @@Soderstrom, Mathis & Smolensky (2006)@, who propose " "an incremental version (formulas 21 and 35d) of the harmony version (formulas 14 and 18) " "of the learning equation for Boltzmann machines (formula 13). " "The differences between the three implementations is that in Stochastic OT and Noisy HG the evaluation noise (or %temperature) is in the constraint rankings, " "in MaxEnt it is in the candidate probabilities, and in Boltzmann machines it is in the activities (i.e. the constraint violations). " "The upate procedure is also similar to that of the %perceptron, a neural network invented by @@Rosenblatt (1962)@ " "for classifying continuous inputs.") MAN_END MAN_BEGIN (L"OT learning 5. Learning a stochastic grammar", L"ppgb", 20070725) NORMAL (L"Having shown that the algorithm can learn deep obligatory rankings, we will now see " "that it also performs well in replicating the variation in the language environment.") NORMAL (L"Create a place assimilation grammar as described in @@OT learning 2.6. Variable output|\\SS2.6@, " "and set all its rankings to 100.000:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*G\\s{ESTURE}#\t 100.000\t 100.000\t 1.000") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (t, p)#\t 100.000\t 100.000\t 1.000") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (n, m)#\t 100.000\t 100.000\t 1.000") NORMAL (L"Create a place assimilation distribution and generate 1000 string pairs (@@OT learning 3.1. Data from a pair distribution|\\SS3.1@). " "Select the grammar and the two @Strings objects, and learn with a plasticity of 0.1:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (t, p)#\t 104.540\t 103.140\t 1.000") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (n, m)#\t 96.214\t 99.321\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE}#\t 99.246\t 97.861") NORMAL (L"The output distributions are now (using @@OTGrammar: To output Distributions...@, see @@OT learning 2.9. Output distributions|\\SS2.9@):") LIST_ITEM1 (L"\t/an+pa/ \\-> anpa\t14.3\\% ") LIST_ITEM1 (L"\t/an+pa/ \\-> ampa\t85.7\\% ") LIST_ITEM1 (L"\t/at+ma/ \\-> atma\t96.9\\% ") LIST_ITEM1 (L"\t/at+ma/ \\-> apma\t3.1\\% ") NORMAL (L"After another 10,000 new string pairs, we have:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (t, p)#\t 106.764\t 107.154\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE}#\t 97.899\t 97.161\t 1.000") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (n, m)#\t 95.337\t 96.848\t 1.000") NORMAL (L"With the following output distributions (measured with a million draws):") LIST_ITEM1 (L"\t/an+pa/ \\-> anpa\t18.31\\% ") LIST_ITEM1 (L"\t/an+pa/ \\-> ampa\t81.69\\% ") LIST_ITEM1 (L"\t/at+ma/ \\-> atma\t99.91\\% ") LIST_ITEM1 (L"\t/at+ma/ \\-> apma\t0.09\\% ") NORMAL (L"The error rate is acceptably low, but the accuracy in reproducing the 80\\% - 20\\% " "distribution could be better. This is because the relatively high plasticity of 0.1 " "can only give a coarse approximation. So we lower the plasticity to 0.001, " "and supply 100,000 new data:") LIST_ITEM1 (L"\t\t %%ranking value\t %disharmony\t %plasticity") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (t, p)#\t 106.810\t 107.184\t 1.000") LIST_ITEM1 (L"\t##*G\\s{ESTURE}#\t 97.782\t 99.682\t 1.000") LIST_ITEM1 (L"\t##*R\\s{EPLACE} (n, m)#\t 95.407\t 98.760\t 1.000") NORMAL (L"With the following output distributions:") LIST_ITEM1 (L"\t/an+pa/ \\-> anpa\t20.08\\% ") LIST_ITEM1 (L"\t/an+pa/ \\-> ampa\t79.92\\% ") LIST_ITEM1 (L"\t/at+ma/ \\-> atma\t99.94\\% ") LIST_ITEM1 (L"\t/at+ma/ \\-> apma\t0.06\\% ") NORMAL (L"So besides learning obligatory rankings like a child does, " "the algorithm can also replicate very well the probabilities of the environment. " "This means that a GLA learner can learn stochastic grammars.") MAN_END MAN_BEGIN (L"OT learning 6. Shortcut to grammar learning", L"ppgb", 20070523) INTRO (L"Once you have mastered the tedious procedures of making Praat learn stochastic grammars, " "as described in the previous chapters of this tutorial, you can try a faster procedure, " "which simply involves selecting an @OTGrammar object together with a @PairDistribution object, " "and clicking ##Learn...#. Once you click OK, Praat will feed the selected grammar with input/output " "pairs drawn from the selected distribution, and the grammar will be modified every time its output " "is different from the given output. Here is the meaning of the arguments:") TAG (L"%%Evaluation noise% (standard value: 2.0)") DEFINITION (L"the standard deviation of the noise added to the ranking of each constraint at evaluation time.") TAG (L"%%Strategy% (standard value: Symmetric all)") DEFINITION (L"what to do when the learner's output is different from the given output. Possibilities:") LIST_ITEM1 (L"Demotion only: lower the ranking of every constraint that is violated more in the correct output " "than in the learner's output. This algorithm crashes if there is variation in the data, i.e. if some inputs " "can have more than one possible adult outputs.") LIST_ITEM1 (L"Symmetric one: lower the ranking of the highest-ranked constraint that is violated more in the adult output " "than in the learner's output, and raise the ranking of the highest-ranked constraint that is violated more " "in the learner's output than in the adult output. This is the \"minimal\" algorithm described and refuted in " "@@Boersma (1998)@, chapters 14-15.") LIST_ITEM1 (L"Symmetric all: lower the ranking of all constraints that are violated more in the adult output " "than in the learner's output, and raise the ranking of all constraints that are violated more " "in the learner's output than in the adult output. This is the algorithm described in @@Boersma & Hayes (2001)@.") LIST_ITEM1 (L"Weighted uncancelled: the same as \"Symmetric all\", but the size of the learning step " "is divided by the number of moving constraints. This makes sure that the average ranking of all the constraints " "is constant.") LIST_ITEM1 (L"Weighted all: the \"Symmetric all\" strategy can reworded as follows: \"lower the ranking of all constraints " "that are violated in the adult output, and raise the ranking of all constraints that are violated in the learner's output\". " "Do that, but divide the size of the learning step by the number of moving constraints.") LIST_ITEM1 (L"EDCD: Error-Driven Constraint Demotion, the algorithm described by @@Tesar & Smolensky (1998)@. " "All constraints that prefer the adult form and are ranked above the highest-ranked constraint that prefers the learner's form, " "are demoted to the ranking of that last constraint minus 1.0.") TAG (L"%%Initial plasticity% (standard value: 1.0)") TAG (L"%%Replications per plasticity% (standard value: 100000)") TAG (L"%%Plasticity decrement% (standard value: 0.1)") TAG (L"%%Number of plasticities% (standard value: 4)") DEFINITION (L"these four arguments determine the %%learning scheme%, i.e. the number of times the grammar will " "receive data at a certain plasticity. With the standard values, there will be 100000 data while the plasticity is 1.0 " "(the initial plasticity), 100000 data while the plasticity is 0.1, 100000 data while the plasticity is 0.01, " "and 100000 data while the plasticity is 0.001. If you want learning at a constant plasticity, set the " "%%number of plasticities% to 1. Note that for the decision strategies of HarmonicGrammar, LinearOT, PositiveHG or MaximumEntropy " "the learning step for a constraint equals the plasticity multiplied by the difference between the " "numbers of violations of this constraint in the adult output and in the learner's output.") TAG (L"%%Rel. plasticity spreading% (standard value: 0.1)") DEFINITION (L"if this is not 0, the size of the learning step will vary randomly. For instance, if the plasticity is set to 0.01, " "and the relative plasticity spreading is 0.1, you will get actual learning steps that could be anywhere between 0.007 " "and 0.013, according to a Gaussian distribution with mean 0.01 and standard deviation 0.001.") TAG (L"%%Honour local rankings% (standard value: on)") DEFINITION (L"if this is on, the fixed rankings that you supplied in the grammar will be maintained during learning: " "if a constraint falls below a constraint that is supposed to be universally lower-ranked, this second constraint " "will be demoted as well.") TAG (L"%%Number of chews% (standard value: 1)") DEFINITION (L"the number of times that each input-output pair is fed to the grammar. Setting this number to 20 " "will give a slightly different (perhaps more accurate) result than simply raising the plasticity by a factor of 20.") MAN_END MAN_BEGIN (L"OT learning 7. Learning from overt forms", L"ppgb", 20031220) INTRO (L"In order to be able to learn phonological production, both EDCD and GLA require pairs of underlying form " "and surface form. However, the language-learning child hears neither of these forms: she only hears ##%%overt forms%#, " "with less structural information than the underlying and surface forms contain.") ENTRY (L"Interpretive parsing") NORMAL (L"The language-learning child has to construct both the surface form and the underlying form from the overt form " "that she hears. @@Tesar & Smolensky (1998)@ proposed that the child computes a surface form from the " "overt form by using the same constraint ranking as in production. For instance, the overt form [\\si \\si\\'^ \\si], which " "is a sequence of three syllables with stress on the second syllable, will be interpreted as the surface form " "/(\\si \\si\\'^) \\si/ in iambic left-aligning languages (I\\s{AMBIC} >> T\\s{ROCHAIC}, and A\\s{LL}F\\s{EET}L\\s{EFT} " ">> A\\s{LL}F\\s{EET}R\\s{IGHT}), but as the surface form /\\si (\\si\\'^ \\si)/ in trochaic right-aligning languages. " "Tesar & Smolensky call this procedure @@Robust Interpretive Parsing@, because it works even if the listener's grammar " "would never produce such a form. For instance, if I\\s{AMBIC} >> A\\s{LL}F\\s{EET}R\\s{IGHT} >> T\\s{ROCHAIC} >> " "A\\s{LL}F\\s{EET}L\\s{EFT}, the listener herself would produce the iambic right-aligned /\\si (\\si \\si\\'^)/ " "for any trisyllabic underlying form, though she will still interpret [\\si \\si\\'^ \\si] as /(\\si \\si\\'^) \\si/, " "which is illegal in her own grammar. Hearing forms that are illegal in one's own grammar is of course a common " "situation for language-learning children.") NORMAL (L"In Tesar & Smolensky's view, the underlying form can be trivially computed from the surface form, " "since the surface form %contains enough information. For instance, the surface form /(\\si \\si\\'^) \\si/ must " "lead to the underlying form \\|f\\si \\si \\si\\|f if all parentheses and stress marks are removed. Since " "@@McCarthy & Prince (1995)@, this %containment view of surface representations has been abandoned. " "In Praat, therefore, the underlying form is not trivially computed from the surface form, " "but all the tableaus are scanned for the surface form that violates the least high-ranked constraints (in the usual " "OT sense), as long as it contains the given overt form. For instance, if I\\s{AMBIC} >> A\\s{LL}F\\s{EET}R\\s{IGHT} " ">> T\\s{ROCHAIC} >> A\\s{LL}F\\s{EET}L\\s{EFT}, the overt form [\\si \\si\\'^ \\si] occurs in two candidates: " "the surface form /(\\si \\si\\'^) \\si/ in the tableau for the underlying form \\|f\\si \\si \\si\\|f, and " "the surface form /\\si (\\si\\'^ \\si)/ in the tableau for the underlying form \\|f\\si \\si \\si\\|f. The best candidate " "is the surface form /(\\si \\si\\'^) \\si/ in the tableau for the underlying form \\|f\\si \\si \\si\\|f. Hence, " "Praat's version of Robust Interpretive Parsing will map the overt form [\\si \\si\\'^ \\si] to the underlying form " "\\|f\\si \\si \\si\\|f (the 'winning tableau') and to the surface form /(\\si \\si\\'^) \\si/ (to be sure, " "this is the same result as in Tesar & Smolensky's " "version, but crucial differences between the two versions will appear when faithfulness constraints are involved).") NORMAL (L"In Praat, you can do interpretive parsing. For example, create a grammar with ##Create metrics grammar...# " "from the @@New menu@. Then choose ##Get interpretive parse...# from the #Query submenu and supply \"[L1 L L]\" for the " "overt form, which means a sequence of three light syllables with a main stress on the first. The Info window will show you " "the optimal underlying and surface forms, given the current constraint ranking.") ENTRY (L"Learning from partial forms") NORMAL (L"Now that the learning child can convert an overt form to an underlying-surface pair, she can compare this " "surface form to the surface form that she herself would have derived from this underlying form. For instance, " "If I\\s{AMBIC} >> A\\s{LL}F\\s{EET}R\\s{IGHT} >> T\\s{ROCHAIC} >> A\\s{LL}F\\s{EET}L\\s{EFT}, the winning " "tableau is \\|f\\si \\si \\si\\|f, and the perceived adult surface form is /(\\si \\si\\'^) \\si/. " "But from the underlying form \\|f\\si \\si \\si\\|f, the learner will derive /\\si (\\si \\si\\'^)/ as her own surface form. " "The two surface forms are different, so that the learner can take action by reranking one or more constraints, " "perhaps with EDCD or GLA.") NORMAL (L"In Praat, you can learn from partial forms. Select the metrics grammar and choose ##Learn from one partial output...#, " "and supply \"[L1 L L]\". If you do this several times, you will see that the winner for the tableau \"|L L L|\" will become one of " "the two forms with overt part \"[L1 L L]\".") NORMAL (L"To run a whole simulation, you supply a @Distributions object with one column, perhaps from a text file. The following " "text file shows the overt forms for Latin, with the bisyllabic forms occurring more often than the trisyllabic forms:") CODE (L"\"ooTextFile\"") CODE (L"\"Distributions\"") CODE (L"1 column with numeric data") CODE (L" \"Latin\"") CODE (L"28 rows") CODE (L"\"[L1 L]\" 25") CODE (L"\"[L1 H]\" 25") CODE (L"\"[H1 L]\" 25") CODE (L"\"[H1 H]\" 25") CODE (L"\"[L1 L L]\" 5") CODE (L"\"[H1 L L]\" 5") CODE (L"\"[L H1 L]\" 5") CODE (L"\"[H H1 L]\" 5") CODE (L"\"[L1 L H]\" 5") CODE (L"\"[H1 L H]\" 5") CODE (L"\"[L H1 H]\" 5") CODE (L"\"[H H1 H]\" 5") CODE (L"\"[L L1 L L]\" 1") CODE (L"\"[L H1 L L]\" 1") CODE (L"\"[L L H1 L]\" 1") CODE (L"\"[L H H1 L]\" 1") CODE (L"\"[L L1 L H]\" 1") CODE (L"\"[L H1 L H]\" 1") CODE (L"\"[L L H1 H]\" 1") CODE (L"\"[L H H1 H]\" 1") CODE (L"\"[H L1 L L]\" 1") CODE (L"\"[H H1 L L]\" 1") CODE (L"\"[H L H1 L]\" 1") CODE (L"\"[H H H1 L]\" 1") CODE (L"\"[H L1 L H]\" 1") CODE (L"\"[H H1 L H]\" 1") CODE (L"\"[H L H1 H]\" 1") CODE (L"\"[H H H1 H]\" 1") NORMAL (L"Read this file into Praat with @@Read from file...@. A @Distributions object then appears in the object list. " "Click @@Distributions: To Strings...|To Strings...@, then OK. A @Strings object containing 1000 strings, drawn randomly " "from the distribution, with relative frequencies as in the text file, will appear in the list. Click @Inspect to check the contents.") NORMAL (L"You can now select the @OTGrammar together with the @Strings and choose ##Learn from partial outputs...#. " "A thousand times, Praat will construct a surface form from the overt form by interpretive parsing, " "and also construct the underlying form in the same way, from which it will construct another surface form by evaluating the " "tableau. Whenever the two surface forms are not identical, some constraints will be reranked. In the current implementation, " "the disharmonies for interpretive parsing and for production are the same, i.e., " "if the evaluation noise is not zero, the disharmonies are randomly renewed before each interpretive parsing " "but stay the same for the subsequent virtual production.") MAN_END /* MAN_BEGIN (L"OTGrammar examples", L"ppgb", 20001027) ENTRY (L"Safety margin and stochastic evaluation") NORMAL (L"What is a %small demotion step? This must be taken relative to another quantity. " "This quantity is the evaluation noise.") NORMAL (L"If the %%ranking spreading% were zero, the demotions in the GLA would immediately stop once that " "a constraint has fallen below its competitors. If the data contain an error, the grammar " "will change to an incorrect state, and the learner has to make an error to correct it. " "Though the error ratio is now one (because of the constant demotion step), " "the learner's behaviour can still be described as a `tit-for-tat' strategy, " "which is an unknown phenomenon in human speech variation.") NORMAL (L"The solution is to have a finite ranking spreading: in this way, the learner will continue making " "errors (though less than 50\\% ) after the constraint has fallen below its competitors. " "For instance, with a ranking spreading of 2.0, the distance between the constraints will be about " "10 after a few thousand relevant data: the %%safety margin%. " "If the mean demotion step is 0.1, there is no chance " "that a modest amount of erroneous data will reverse the ranking. It is true, however, that " "one erroneous datum will decrease the constraint distance by 0.1, so that the learner will have to " "make one mistake herself to restore the original distance. But this is only natural, " "as she may well wait a long time before doing this: " "on the average, the same number of thousands of data. This is the %%patient error-matching learner%.") ENTRY (L"Learning from surface data alone") NORMAL (L"Many a young learner will take the adult surface forms, as perceived by herself, " "as her underlying forms. In other words, the input to her grammar will equal " "the output of the adult grammar.") NORMAL (L"We can simulate what happens here by taking the adult output as the input to the learning algorithms:") LIST_ITEM (L"1. Create a five-constraint Wolof grammar.") LIST_ITEM (L"2. Generate 1000 input strings.") LIST_ITEM (L"3. Compute the 1000 output strings.") LIST_ITEM (L"4. Create a five-constraint \"equal\" grammar.") LIST_ITEM (L"5. Select this monostratal grammar and the output strings only, " "and click ##Learn output (T&S)#. See @@OTAnyGrammar & Strings: Learn output (T&S)@.") NORMAL (L"The result will be a grammar where the faithfulness constraints outrank all the " "gestural constraints that can be violated in any output string:") LIST_ITEM (L"##*[rtr / hi]# 100.000 100.000") LIST_ITEM (L"##P\\s{ARSE} (atr)# 100.000 100.000") LIST_ITEM (L"##P\\s{ARSE} (rtr)# 100.000 100.000") LIST_ITEM (L"##*G\\s{ESTURE} (contour)# 99.000 99.000") LIST_ITEM (L"##*[atr / lo]# 99.000 99.000") NORMAL (L"You will get a comparable result with @@OTAnyGrammar & Strings: Learn output (GLA)...@.") NORMAL (L"The resulting grammar represents the learner's state after the acquisition of " "all the relevant gestures. The learner will now faithfully reproduce /et\\ep/ " "if that were in her lexicon. Before being able to render such an underlying form as [\\ept\\ep], " "she must learn that faithfulness can be violated.") ENTRY (L"Example 2: When underlying forms are irrelevant") NORMAL (L"Underlying forms are relevant only if faithfulness constraints are involved. " "If a grammar only contains constraints that evaluate the output, " "we need no input strings for our simulations. However, " "if the relevant constraint had fixed rankings, there would only be a single possible output, " "which seems uninteresting. An interesting output-only grammar, therefore, necessarily " "features stochastic evaluation, and at least some of the constraints wil have rankings that " "are close to each other.") NORMAL (L"#%Example. @@Hayes & MacEachern (1998)@ identify 11 output-oriented constraints " "for the forms of quatrains in English folk verse.") LIST_ITEM (L"1. Create a folk-verse grammar with equal constraint rankings (all 100). " "You may find it in the file ##folkVerse.OTGrammar# in the #demo directory of your #Praat distribution, " "or get it from ##http://www.fon.hum.uva.nl/praat/folkVerse.OTGrammar#.") LIST_ITEM (L"2. Generate 1000 input strings. They will all be empty strings.") LIST_ITEM (L"3. Read the file that contains the surface distribution of the possible outputs. " "It is in the #demo folder or at ##http://www.fon.hum.uva.nl/praat/folkVerse.Distributions#. " "A @Distributions object will appear in the list. " "Column \"Actual\" is the last column of table (10) in Hayes & MacEachern (1998).") LIST_ITEM (L"4. From this surface distribution, create a list of 1000 output strings, " "using @@Distributions: To Strings...@ (set %column to 1).") LIST_ITEM (L"5. Select the grammar, the \"input strings\", and the output strings, " "and learn in the usual way. After learning, you can see that some constraints have risen above 100, " "and some have fallen below 100.") NORMAL (L"With each of the 1000 outputs, the learner can be regarded as having generated a quatrain herself " "and compared it to a quatrain in her folk-verse environment. If these quatrains are equal " "(a 10\\% chance or so), nothing happens. Otherwise, the learner will demote the highest " "violated constraint (i.e., the one that is most disharmonic during her stochastic evaluation) " "in the heard quatrain that is not (or less) violated in the winner (the quatrain that she generated herself). " "She will also promote the highest violated constraint in the winner " "that is not (or less) violated in the heard quatrain.") NORMAL (L"We are next going to generate a set of 589 quatrains, in order to be able to compare " "the behaviours of our folk-verse grammar and the English folk-verse writers:") LIST_ITEM (L"1. Select the learned grammar and generate 589 (empty) input strings.") LIST_ITEM (L"2. Select the learned grammar and the so-called input strings, " "and generate the output strings.") LIST_ITEM (L"3. To see the distribution of the output strings, choose @@Strings: To Distributions@, " "and draw the resulting @Distributions object to your Picture window.") LIST_ITEM (L"4. You can now compare the two distributions.") NORMAL (L"Instead of generating the data from a @Distributions, you could have generated them from " "the target grammar in table (9) of Hayes & MacEachern (1998). " "Such a grammar is in your #demo folder (##folkVerse59.OTGrammar#) " "or at ##http://www.fon.hum.uva.nl/praat/folkVerse59.OTGrammar#. " "Because of the loosening of the tie between two of the constraints (see H & McE, fn. 43), " "this grammar will give different distributions from the \"actual\" values, " "but our algorithm will learn them correctly, provided you choose ##Symmetric all# " "or ##weighted uncancelled# for the learning strategy.") MAN_END */ MAN_BEGIN (L"OTGrammar", L"ppgb", 20041110) INTRO (L"One of the @@types of objects@ in Praat. See the @@OT learning@ tutorial.") ENTRY (L"Inside an OTGrammar") NORMAL (L"With @Inspect, you will see the following attributes:") TAG (L"%constraints") DEFINITION (L"a list of constraints. Each constraint contains the following attributes:") TAG1 (L"%name") DEFINITION1 (L"the fixed name of the constraint, for instance \"P\\s{ARSE}\".") TAG1 (L"%ranking") DEFINITION1 (L"the continuous ranking value; will change during learning.") TAG1 (L"%disharmony") DEFINITION1 (L"the effective ranking value during stochastic evaluation; with a non-zero evaluation noise, " "this will be different from %ranking.") TAG (L"%fixedRankings") DEFINITION (L"an often empty list of locally ranked pairs of constraints. " "Each local-ranking pair contains the following attributes:") TAG1 (L"%higher") DEFINITION1 (L"the index of the universally higher-ranked of the two constraints, " "a number between 1 and the number of constraints.") TAG1 (L"%lower") DEFINITION1 (L"the index of the universally lower-ranked of the two constraints.") TAG (L"%tableaus") DEFINITION (L"a list of tableaus. Each tableau contains the following attributes:") TAG1 (L"%input") DEFINITION1 (L"the input string of the tableau. For production grammaras, the underlying form of the utterance, for example " "\\|fan+pa\\|f or \\|fb\\rt\\ic\\ng + \\s{PAST}\\|f.") TAG1 (L"%candidates") DEFINITION1 (L"a list of output candidates. Each output candidate consists of:") TAG2 (L"%output") DEFINITION2 (L"the output string of the tableau. In generative phonology: the surface form of the utterance, for example " "[anpa] or [ampa] or [b\\rt\\ct:t] or [b\\rt\\ae\\ng]. In functional phonology: the combination of the articulatory " "and the perceptual results, for example [anpa]-/anpa/ or [ampa]-/ampa/ or [b\\rt\\ct:t]-/b\\rt\\ct:t/ or " "[b\\rt\\ae\\ng]-/b\\rt\\ae\\ng/.") TAG2 (L"%marks") DEFINITION2 (L"a list of the number of violations of each constraint for this output form. If there are 13 constraints, " "this list will contain 13 integer numbers for each candidate.") ENTRY (L"OTGrammar creation") NORMAL (L"You can easily create some #OTGrammar examples from the @@New menu@, " "or type your own grammars into a text file and read the file into Praat. See the @@OT learning@ tutorial.") ENTRY (L"OTGrammar actions") NORMAL (L"You can perform the following actions on selected #OTGrammar objects:") LIST_ITEM (L"@@OTGrammar: Generate inputs...@") /*LIST_ITEM (L"@@OTGrammar: Sort...@")*/ LIST_ITEM (L"@@OTGrammar: Input to output...@") LIST_ITEM (L"@@OTGrammar: Input to outputs...@ (compute the output distribution for a given input)") LIST_ITEM (L"@@OTGrammar: To output Distributions...@") LIST_ITEM (L"@@OTGrammar & Strings: Inputs to outputs...@") LIST_ITEM (L"@@OTGrammar: Learn one...@") LIST_ITEM (L"@@OTGrammar & 2 Strings: Learn...@") NORMAL (L"You can view an #OTGrammar in an @OTGrammarEditor.") MAN_END MAN_BEGIN (L"OTGrammar: Generate inputs...", L"ppgb", 19981230) INTRO (L"A command to create a @Strings object from a selected @OTGrammar.") NORMAL (L"A practical grammar-specific implementation of the %%richness of the base%: " "the inputs are drawn at random with equal probabilities from the inputs associated with the tableaus. " "For an example, see @@OT learning 3.2. Data from another grammar@.") ENTRY (L"Setting") TAG (L"##Number of trials") DEFINITION (L"the number of times a string will be drawn from the possible inputs to the grammar.") MAN_END MAN_BEGIN (L"OTGrammar: Input to output...", L"ppgb", 20030916) INTRO (L"A command to ask the selected @OTGrammar object to evaluate the candidates associated with a specified input form.") NORMAL (L"See @@OT learning 2.8. Asking for one output@ for tutorial information.") ENTRY (L"Settings") TAG (L"##Input form") DEFINITION (L"the input form whose surface form you want to know. If this string is not in the list " "of the possible inputs of the selected OTGrammar, you will get an error message.") TAG (L"##Noise# (standard value: 2.0)") DEFINITION (L"the standard deviation of the noise added to the ranking value of every constraint during evaluation. " "See @@OT learning 2.4. Evaluation@.") MAN_END MAN_BEGIN (L"OTGrammar: Input to outputs...", L"ppgb", 20030916) INTRO (L"A command to ask the selected @OTGrammar object to evaluate a number of times the candidates associated " "with a specified input form. The result is a @Distributions object.") NORMAL (L"See @@OT learning 2.9. Output distributions@ for tutorial information and examples.") ENTRY (L"Settings") TAG (L"##Trials# (standard value: 1000)") DEFINITION (L"the number of evaluations that you want to perform.") TAG (L"##Noise# (standard value: 2.0)") DEFINITION (L"the standard deviation of the noise added to the ranking value of every constraint during the evaluations. " "See @@OT learning 2.4. Evaluation@.") TAG (L"##Input form") DEFINITION (L"the input form whose surface forms you want to measure. If this string is not in the list " "of the possible inputs of the selected OTGrammar, you will get an error message.") MAN_END MAN_BEGIN (L"OTGrammar: Learn one...", L"ppgb", 20011120) INTRO (L"Causes every selected @OTGrammar object to process one input/output pair " "according to the Gradual Learning Algorithm " "by @@Boersma (1998)@ and @@Boersma (2000)@. See @@OT learning 4. Learning an ordinal grammar@ " "and @@OT learning 5. Learning a stochastic grammar@.") MAN_END MAN_BEGIN (L"OTGrammar: To output Distributions...", L"ppgb", 19981230) INTRO (L"A command to ask the selected @OTGrammar object to evaluate a number of times the candidates associated " "with every input form. The result is a @Distributions object. See @@OT learning 2.9. Output distributions@.") MAN_END MAN_BEGIN (L"OTGrammar & PairDistribution: Find positive weights...", L"ppgb", 20080331) INTRO (L"A command to change the weights of the selected @OTGrammar on the basis of the language data " "in the selected @PairDistribution.") NORMAL (L"This command works only if the decision strategy of the selected OTGrammar is " "HarmonicGrammar, LinearOT, PositiveHG, or ExponentialHG. Also, " "the selected PairDistribution must contain exactly one non-zero-probability output for every possible input of the grammar.") NORMAL (L"The procedure follows the linear programming method by @@Pater, Potts & Bhatt (2007)@. " "This method tries to find a special correct weighting of the constraints, " "namely one that minimizes the sum of the constraint weights.") ENTRY (L"Settings") TAG (L"##Weight floor# (standard value: 1.0)") DEFINITION (L"After the command finishes, every weight will have at least this value.") TAG (L"##Margin of separation# (standard value: 1.0)") DEFINITION (L"After the command finishes, the harmony of every optimal (and correct) output candidate " "will be at least this much greater than the harmony of any competitor in the same tableau.") MAN_END MAN_BEGIN (L"OTGrammar & Strings: Inputs to outputs...", L"ppgb", 19981230) INTRO (L"An action that creates a @Strings object from a selected @OTGrammar and a selected @Strings.") NORMAL (L"The selected Strings object is considered as a list of inputs to the OTGrammar grammar.") ENTRY (L"Settings") TAG (L"##Noise") DEFINITION (L"the standard deviation of the noise that will be temporarily added to the ranking value at each evaluation.") NORMAL (L"The resulting Strings object will contain the output string of the grammar for each of the input strings.") NORMAL (L"See @@OT learning 3.2. Data from another grammar@.") MAN_END MAN_BEGIN (L"OTGrammar & 2 Strings: Learn...", L"ppgb", 20100331) INTRO (L"Causes the selected @OTGrammar object to process a number of input/output pairs " "according to the Gradual Learning Algorithm by @@Boersma (1997)@ and @@Boersma & Hayes (2001)@ " "or with any other reranking strategies. See @@OT learning 4. Learning an ordinal grammar@ " "and @@OT learning 5. Learning a stochastic grammar@.") MAN_END MAN_BEGIN (L"OTGrammarEditor", L"ppgb", 20030316) INTRO (L"One of the @editors in Praat, for viewing and editing the grammar in an @OTGrammar object.") NORMAL (L"See the @@OT learning@ tutorial for examples.") ENTRY (L"Usage") NORMAL (L"The menu command that you will probably use most often if you investigate variation, " "is the ##Evaluate (noise 2.0)# command, which you can invoke from the #Edit menu or by pressing Command-2.") NORMAL (L"This command performs a new evaluation with the current ranking values. Some noise is added to the " "ranking values, so that the %#disharmonies of the constraint will change. This may cause a change in the " "ranking order of the constraints, which in its turn may cause a different candidate to win in some tableaus.") MAN_END MAN_BEGIN (L"Robust Interpretive Parsing", L"ppgb", 20021105) INTRO (L"The mapping from overt forms to surface forms in the acquisition model by @@Tesar & Smolensky (1998)@.") NORMAL (L"In Praat, you can do robust interpretive parsing on any @OTGrammar object. " "See @@OT learning 7. Learning from overt forms@.") MAN_END } /* End of file manual_gram.cpp */ sources_5316/gram/OTGrammar.h0000644000176700017670000001760311647047127014673 0ustar paulpaul#ifndef _OTGrammar_h_ #define _OTGrammar_h_ /* OTGrammar.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Strings.h" #include "Graphics.h" #include "PairDistribution.h" #include "Distributions.h" #include "TableOfReal.h" #include "OTGrammar_enums.h" #include "OTGrammar_def.h" oo_CLASS_CREATE (OTGrammar, Data); Thing_define (OTHistory, TableOfReal) { }; void OTGrammar_sort (OTGrammar me); /* Low level: meant to maintain the invariant * my constraints [my index [i]]. disharmony >= my constraints [my index [i+1]]. disharmony * Therefore, call after every direct assignment to the 'disharmony' attribute. * Tied constraints are sorted alphabetically. */ void OTGrammar_newDisharmonies (OTGrammar me, double spreading); long OTGrammar_getTableau (OTGrammar me, const wchar *input); int OTGrammar_compareCandidates (OTGrammar me, long itab1, long icand1, long itab2, long icand2); /* * Function: * to compare the optimality of candidates icand1 in tableau itab1 * and icand2 in tableau itab2. * Return value: * -1 if candidate icand1 is more optimal than candidate icand2; * +1 if candidate icand2 is more optimal than candidate icand1; * 0 if both candidates are equally optimal. * Algorithm: * the current disharmony ranking is considered. * Takes into account crucial ties: if multiple constraints are ranked at * exactly the same height (disharmony), they count as a single constraint. * This is original OT. To get Anttila's and GLA's variationist interpretation * of ties instead (even in EDCD), make sure you introduce a bit of noise * (e.g. 1e-6 if the strata are 1.0 apart). That makes * the probability of ties almost zero. */ /* Productive parsing. */ long OTGrammar_getWinner (OTGrammar me, long itab); /* Gives randomized results in case of tied candidates. */ long OTGrammar_getNumberOfOptimalCandidates (OTGrammar me, long itab); bool OTGrammar_isCandidateGrammatical (OTGrammar me, long itab, long icand); bool OTGrammar_isCandidateSinglyGrammatical (OTGrammar me, long itab, long icand); /* Interpretive parsing. */ void OTGrammar_getInterpretiveParse (OTGrammar me, const wchar *partialOutput, long *bestTableau, long *bestCandidate); /* Gives randomized results in case of tied candidates. */ bool OTGrammar_isPartialOutputGrammatical (OTGrammar me, const wchar *partialOutput); /* Is there an input for which this partial output is contained in any of the optimal outputs? */ bool OTGrammar_isPartialOutputSinglyGrammatical (OTGrammar me, const wchar *partialOutput); /* Is every optimal output that contains this partial output the only optimal output in its tableau? */ void OTGrammar_drawTableau (OTGrammar me, Graphics g, bool vertical, const wchar *input); Strings OTGrammar_generateInputs (OTGrammar me, long numberOfTrials); Strings OTGrammar_getInputs (OTGrammar me); void OTGrammar_inputToOutput (OTGrammar me, const wchar *input, wchar *output, double evaluationNoise); Strings OTGrammar_inputsToOutputs (OTGrammar me, Strings inputs, double evaluationNoise); Strings OTGrammar_inputToOutputs (OTGrammar me, const wchar *input, long n, double evaluationNoise); Distributions OTGrammar_to_Distribution (OTGrammar me, long trialsPerInput, double evaluationNoise); PairDistribution OTGrammar_to_PairDistribution (OTGrammar me, long trialsPerInput, double evaluationNoise); Distributions OTGrammar_measureTypology (OTGrammar me); void OTGrammar_learnOne (OTGrammar me, const wchar *input, const wchar *adultOutput, double rankingSpreading, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double demotionMean, double relativeDemotionSpreading, int newDisharmonies, int warnIfStalled, int *grammarHasChanged); void OTGrammar_learn (OTGrammar me, Strings inputs, Strings outputs, double rankingSpreading, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double demotionMean, double relativeDemotionSpreading, long numberOfChews); void OTGrammar_PairDistribution_learn (OTGrammar me, PairDistribution thee, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double initialPlasticity, long replicationsPerPlasticity, double plasticityDecrement, long numberOfPlasticities, double relativePlasticityNoise, long numberOfChews); bool OTGrammar_PairDistribution_findPositiveWeights_e (OTGrammar me, PairDistribution thee, double weightFloor, double marginOfSeparation); void OTGrammar_learnOneFromPartialOutput (OTGrammar me, const wchar *partialAdultOutput, double rankingSpreading, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double demotionMean, double relativeDemotionSpreading, long numberOfChews, int warnIfStalled); void OTGrammar_learnFromPartialOutputs (OTGrammar me, Strings partialOutputs, double rankingSpreading, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double demotionMean, double relativeDemotionSpreading, long numberOfChews, long storeHistoryEvery, OTHistory *history); void OTGrammar_Distributions_learnFromPartialOutputs (OTGrammar me, Distributions thee, long columnNumber, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double initialPlasticity, long replicationsPerPlasticity, double plasticityDecrement, long numberOfPlasticities, double relativePlasticityNoise, long numberOfChews, long storeHistoryEvery, OTHistory *history_out); double OTGrammar_PairDistribution_getFractionCorrect (OTGrammar me, PairDistribution thee, double evaluationNoise, long numberOfInputs); long OTGrammar_PairDistribution_getMinimumNumberCorrect (OTGrammar me, PairDistribution thee, double evaluationNoise, long numberOfReplications); double OTGrammar_Distributions_getFractionCorrect (OTGrammar me, Distributions thee, long columnNumber, double evaluationNoise, long numberOfInputs); void OTGrammar_checkIndex (OTGrammar me); OTGrammar OTGrammar_create_NoCoda_grammar (void); OTGrammar OTGrammar_create_NPA_grammar (void); PairDistribution OTGrammar_create_NPA_distribution (void); OTGrammar OTGrammar_create_tongueRoot_grammar (int small_large, int equal_random_infant_Wolof); OTGrammar OTGrammar_create_metrics (int equal_footForm_wsp, int trochaicityConstraint, int includeFootBimoraic, int includeFootBisyllabic, int includePeripheral, int nonfinalityConstraint, int overtFormsHaveSecondaryStress, int includeClashAndLapse, int includeCodas); /* T&S: 1, FALSE, FALSE, FALSE, 1, TRUE, FALSE, FALSE */ void OTGrammar_reset (OTGrammar me, double ranking); void OTGrammar_resetToRandomTotalRanking (OTGrammar me, double maximumRanking, double rankingDistance); void OTGrammar_setRanking (OTGrammar me, long constraint, double ranking, double disharmony); void OTGrammar_setConstraintPlasticity (OTGrammar me, long constraint, double plasticity); void OTGrammar_removeConstraint (OTGrammar me, const wchar *constraintName); void OTGrammar_removeHarmonicallyBoundedCandidates (OTGrammar me, int singly); void OTGrammar_PairDistribution_listObligatoryRankings (OTGrammar me, PairDistribution thee); void OTGrammar_Distributions_listObligatoryRankings (OTGrammar me, Distributions thee, long columnNumber); void OTGrammar_writeToHeaderlessSpreadsheetFile (OTGrammar me, MelderFile file); /* End of file OTGrammar.h */ #endif sources_5316/gram/Network_enums.h0000644000176700017670000000255511743375502015700 0ustar paulpaul/* Network_enums.h * * Copyright (C) 2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ enums_begin (kNetwork_weightUpdateRule, 0) enums_add (kNetwork_weightUpdateRule, 0, HEBBIAN, L"Hebbian") enums_add (kNetwork_weightUpdateRule, 1, INSTAR, L"instar") enums_add (kNetwork_weightUpdateRule, 2, OUTSTAR, L"outstar") enums_add (kNetwork_weightUpdateRule, 3, INOUTSTAR, L"inoutstar") enums_end (kNetwork_weightUpdateRule, 3, HEBBIAN) enums_begin (kNetwork_activationSpreadingRule, 0) enums_add (kNetwork_activationSpreadingRule, 0, SIGMOID, L"sigmoid") enums_add (kNetwork_activationSpreadingRule, 1, LINEAR, L"linear") enums_end (kNetwork_activationSpreadingRule, 1, SIGMOID) /* End of file Network_enums.h */ sources_5316/gram/Network.cpp0000644000176700017670000003635711744133736015035 0ustar paulpaul/* Network.cpp * * Copyright (C) 2009-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2009/02/27 created * pb 2009/03/05 setClamping * pb 2009/05/14 zeroActivities, normalizeActivities * pb 2009/06/11 connection plasticities * pb 2011/03/29 C++ * pb 2012/03/18 more weight update rules: instar, outstar, inoutstar * pb 2012/04/19 more activation spreading rules: linear */ #include "Network.h" #include "oo_DESTROY.h" #include "Network_def.h" #include "oo_COPY.h" #include "Network_def.h" #include "oo_EQUAL.h" #include "Network_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Network_def.h" #include "oo_WRITE_TEXT.h" #include "Network_def.h" #include "oo_READ_TEXT.h" #include "Network_def.h" #include "oo_WRITE_BINARY.h" #include "Network_def.h" #include "oo_READ_BINARY.h" #include "Network_def.h" #include "oo_DESCRIPTION.h" #include "Network_def.h" #include "enums_getText.h" #include "Network_enums.h" #include "enums_getValue.h" #include "Network_enums.h" void structNetwork :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Leak: ", Melder_double (d_leak)); MelderInfo_writeLine2 (L"Number of nodes: ", Melder_integer (d_numberOfNodes)); MelderInfo_writeLine2 (L"Number of connections: ", Melder_integer (d_numberOfConnections)); } Thing_implement (Network, Data, 3); void structNetwork :: f_init (double minimumActivity, double maximumActivity, double spreadingRate, double selfExcitation, double minimumWeight, double maximumWeight, double learningRate, double leak, double xmin, double xmax, double ymin, double ymax, long numberOfNodes, long numberOfConnections) { d_minimumActivity = minimumActivity; d_maximumActivity = maximumActivity; d_spreadingRate = spreadingRate; d_selfExcitation = selfExcitation; d_minimumWeight = minimumWeight; d_maximumWeight = maximumWeight; d_learningRate = learningRate; d_leak = leak; d_xmin = xmin; d_xmax = xmax; d_ymin = ymin; d_ymax = ymax; d_numberOfNodes = numberOfNodes; d_nodes = NUMvector (1, numberOfNodes); d_numberOfConnections = numberOfConnections; d_connections = NUMvector (1, numberOfConnections); } Network Network_create (double minimumActivity, double maximumActivity, double spreadingRate, double selfExcitation, double minimumWeight, double maximumWeight, double learningRate, double leak, double xmin, double xmax, double ymin, double ymax, long numberOfNodes, long numberOfConnections) { try { autoNetwork me = Thing_new (Network); me -> f_init (minimumActivity, maximumActivity, spreadingRate, selfExcitation, minimumWeight, maximumWeight, learningRate, leak, xmin, xmax, ymin, ymax, numberOfNodes, numberOfConnections); therror return me.transfer(); } catch (MelderError) { Melder_throw ("Network not created."); } } double structNetwork :: f_getActivity (long nodeNumber) { try { if (nodeNumber <= 0 || nodeNumber > d_numberOfNodes) Melder_throw (this, ": node number (", nodeNumber, ") out of the range 1..", d_numberOfNodes, "."); return d_nodes [nodeNumber]. activity; } catch (MelderError) { Melder_throw (this, ": activity not gotten."); } } void structNetwork :: f_setActivity (long nodeNumber, double activity) { try { if (nodeNumber <= 0 || nodeNumber > d_numberOfNodes) Melder_throw (this, ": node number (", nodeNumber, ") out of the range 1..", d_numberOfNodes, "."); d_nodes [nodeNumber]. activity = activity; } catch (MelderError) { Melder_throw (this, ": activity not set."); } } double structNetwork :: f_getWeight (long connectionNumber) { try { if (connectionNumber <= 0 || connectionNumber > d_numberOfConnections) Melder_throw (this, ": connection number (", connectionNumber, ") out of the range 1..", d_numberOfConnections, "."); return d_connections [connectionNumber]. weight; } catch (MelderError) { Melder_throw (this, ": weight not gotten."); } } void structNetwork :: f_setWeight (long connectionNumber, double weight) { try { if (connectionNumber <= 0 || connectionNumber > d_numberOfConnections) Melder_throw (this, ": connection number (", connectionNumber, ") out of the range 1..", d_numberOfConnections, "."); d_connections [connectionNumber]. weight = weight; } catch (MelderError) { Melder_throw (this, ": weight not set."); } } void structNetwork :: f_setClamping (long nodeNumber, bool clamped) { try { if (nodeNumber <= 0 || nodeNumber > d_numberOfNodes) Melder_throw (this, ": node number (", nodeNumber, ") out of the range 1..", d_numberOfNodes, "."); d_nodes [nodeNumber]. clamped = clamped; } catch (MelderError) { Melder_throw (this, ": clamping not set."); } } void structNetwork :: f_spreadActivities (long numberOfSteps) { for (long istep = 1; istep <= numberOfSteps; istep ++) { for (long inode = 1; inode <= d_numberOfNodes; inode ++) { NetworkNode node = & d_nodes [inode]; node -> excitation = node -> activity * d_selfExcitation; } for (long iconn = 1; iconn <= d_numberOfConnections; iconn ++) { NetworkConnection connection = & d_connections [iconn]; NetworkNode nodeFrom = & d_nodes [connection -> nodeFrom]; NetworkNode nodeTo = & d_nodes [connection -> nodeTo]; nodeFrom -> excitation += nodeTo -> activity * d_connections [iconn]. weight; nodeTo -> excitation += nodeFrom -> activity * d_connections [iconn]. weight; } for (long inode = 1; inode <= d_numberOfNodes; inode ++) { NetworkNode node = & d_nodes [inode]; if (! node -> clamped) { switch (d_activationSpreadingRule) { case kNetwork_activationSpreadingRule_SIGMOID: node -> activity = (d_maximumActivity - d_minimumActivity) * NUMsigmoid (d_spreadingRate * node -> excitation) + d_minimumActivity; break; case kNetwork_activationSpreadingRule_LINEAR: node -> activity = d_spreadingRate * node -> excitation; break; } } } } } void structNetwork :: f_zeroActivities (long nodeMin, long nodeMax) { if (d_numberOfNodes < 1) return; if (nodeMax == 0) { nodeMin = 1; nodeMax = d_numberOfNodes; } if (nodeMin < 1) nodeMin = 1; if (nodeMax > d_numberOfNodes) nodeMax = d_numberOfNodes; for (long inode = nodeMin; inode <= nodeMax; inode ++) { d_nodes [inode]. activity = 0.0; } } void structNetwork :: f_normalizeActivities (long nodeMin, long nodeMax) { if (d_numberOfNodes < 1) return; if (nodeMax == 0) { nodeMin = 1; nodeMax = d_numberOfNodes; } if (nodeMin < 1) nodeMin = 1; if (nodeMax > d_numberOfNodes) nodeMax = d_numberOfNodes; if (nodeMax < nodeMin) return; double sum = 0.0; for (long inode = nodeMin; inode <= nodeMax; inode ++) { sum += d_nodes [inode]. activity; } double average = sum / (nodeMax - nodeMin + 1); for (long inode = nodeMin; inode <= nodeMax; inode ++) { d_nodes [inode]. activity -= average; } } void structNetwork :: f_updateWeights () { for (long iconn = 1; iconn <= d_numberOfConnections; iconn ++) { NetworkConnection connection = & d_connections [iconn]; NetworkNode nodeFrom = & d_nodes [connection -> nodeFrom]; NetworkNode nodeTo = & d_nodes [connection -> nodeTo]; switch (d_weightUpdateRule) { case kNetwork_weightUpdateRule_HEBBIAN: connection -> weight += connection -> plasticity * d_learningRate * nodeFrom -> activity * nodeTo -> activity - d_leak * connection -> weight; if (connection -> weight < d_minimumWeight) connection -> weight = d_minimumWeight; else if (connection -> weight > d_maximumWeight) connection -> weight = d_maximumWeight; break; case kNetwork_weightUpdateRule_INSTAR: connection -> weight += connection -> plasticity * d_learningRate * nodeTo -> activity * (nodeFrom -> activity - connection -> weight); break; case kNetwork_weightUpdateRule_OUTSTAR: connection -> weight += connection -> plasticity * d_learningRate * nodeFrom -> activity * (nodeTo -> activity - connection -> weight); break; case kNetwork_weightUpdateRule_INOUTSTAR: connection -> weight += connection -> plasticity * d_learningRate * (2 * nodeFrom -> activity * nodeTo -> activity - (nodeFrom -> activity + nodeTo -> activity) * connection -> weight); break; } } } Network Network_create_rectangle (double minimumActivity, double maximumActivity, double spreadingRate, double selfExcitation, double minimumWeight, double maximumWeight, double learningRate, double leak, long numberOfRows, long numberOfColumns, bool bottomRowClamped, double initialMinimumWeight, double initialMaximumWeight) { try { autoNetwork me = Network_create (minimumActivity, maximumActivity, spreadingRate, selfExcitation, minimumWeight, maximumWeight, learningRate, leak, 0.0, numberOfColumns, 0.0, numberOfRows, numberOfRows * numberOfColumns, numberOfRows * (numberOfColumns - 1) + numberOfColumns * (numberOfRows - 1)); /* * Define nodes. */ for (long inode = 1; inode <= my d_numberOfNodes; inode ++) { NetworkNode node = & my d_nodes [inode]; node -> x = (inode - 1) % numberOfColumns + 0.5; node -> y = (inode - 1) / numberOfColumns + 0.5; node -> clamped = bottomRowClamped && inode <= numberOfColumns; node -> activity = NUMrandomUniform (my d_minimumActivity, my d_maximumActivity); } /* * Define connections. */ long iconn = 0; for (long irow = 1; irow <= numberOfRows; irow ++) { for (long icol = 1; icol <= numberOfColumns - 1; icol ++) { NetworkConnection conn = & my d_connections [++ iconn]; conn -> nodeFrom = (irow - 1) * numberOfColumns + icol; conn -> nodeTo = conn -> nodeFrom + 1; conn -> weight = NUMrandomUniform (initialMinimumWeight, initialMaximumWeight); conn -> plasticity = 1.0; } } for (long irow = 1; irow <= numberOfRows - 1; irow ++) { for (long icol = 1; icol <= numberOfColumns; icol ++) { NetworkConnection conn = & my d_connections [++ iconn]; conn -> nodeFrom = (irow - 1) * numberOfColumns + icol; conn -> nodeTo = conn -> nodeFrom + numberOfColumns; conn -> weight = NUMrandomUniform (initialMinimumWeight, initialMaximumWeight); conn -> plasticity = 1.0; } } Melder_assert (iconn == my d_numberOfConnections); return me.transfer(); } catch (MelderError) { Melder_throw ("Rectangular network not created."); } } Network Network_create_rectangle_vertical (double minimumActivity, double maximumActivity, double spreadingRate, double selfExcitation, double minimumWeight, double maximumWeight, double learningRate, double leak, long numberOfRows, long numberOfColumns, bool bottomRowClamped, double initialMinimumWeight, double initialMaximumWeight) { try { autoNetwork me = Network_create (minimumActivity, maximumActivity, spreadingRate, selfExcitation, minimumWeight, maximumWeight, learningRate, leak, 0.0, numberOfColumns, 0.0, numberOfRows, numberOfRows * numberOfColumns, numberOfColumns * numberOfColumns * (numberOfRows - 1)); /* * Define nodes. */ for (long inode = 1; inode <= my d_numberOfNodes; inode ++) { NetworkNode node = & my d_nodes [inode]; node -> x = (inode - 1) % numberOfColumns + 0.5; node -> y = (inode - 1) / numberOfColumns + 0.5; node -> clamped = bottomRowClamped && inode <= numberOfColumns; node -> activity = NUMrandomUniform (my d_minimumActivity, my d_maximumActivity); } /* * Define connections. */ long iconn = 0; for (long icol = 1; icol <= numberOfColumns; icol ++) { for (long jcol = 1; jcol <= numberOfColumns; jcol ++) { for (long irow = 1; irow <= numberOfRows - 1; irow ++) { NetworkConnection conn = & my d_connections [++ iconn]; conn -> nodeFrom = (irow - 1) * numberOfColumns + icol; conn -> nodeTo = irow * numberOfColumns + jcol; conn -> weight = NUMrandomUniform (initialMinimumWeight, initialMaximumWeight); conn -> plasticity = 1.0; } } } Melder_assert (iconn == my d_numberOfConnections); return me.transfer(); } catch (MelderError) { Melder_throw ("Vertical rectangular network not created."); } } void structNetwork :: f_draw (Graphics graphics, bool colour) { double saveLineWidth = Graphics_inqLineWidth (graphics); Graphics_setInner (graphics); Graphics_setWindow (graphics, d_xmin, d_xmax, d_ymin, d_ymax); Graphics_setColour (graphics, Graphics_SILVER); Graphics_fillRectangle (graphics, d_xmin, d_xmax, d_ymin, d_ymax); /* * Draw connections. */ for (long iconn = 1; iconn <= d_numberOfConnections; iconn ++) { NetworkConnection conn = & d_connections [iconn]; if (conn -> weight != 0.0) { NetworkNode nodeFrom = & d_nodes [conn -> nodeFrom]; NetworkNode nodeTo = & d_nodes [conn -> nodeTo]; Graphics_setLineWidth (graphics, fabs (conn -> weight) * 6.0); Graphics_setColour (graphics, conn -> weight < 0.0 ? Graphics_WHITE : Graphics_BLACK); Graphics_line (graphics, nodeFrom -> x, nodeFrom -> y, nodeTo -> x, nodeTo -> y); } } Graphics_setLineWidth (graphics, 1.0); /* * Draw nodes. */ for (long inode = 1; inode <= d_numberOfNodes; inode ++) { NetworkNode node = & d_nodes [inode]; double diameter = fabs (node -> activity) * 5.0; if (diameter != 0.0) { Graphics_setColour (graphics, colour ? ( node -> activity < 0.0 ? Graphics_BLUE : Graphics_RED ) : ( node -> activity < 0.0 ? Graphics_WHITE : Graphics_BLACK)); Graphics_fillCircle_mm (graphics, node -> x, node -> y, diameter); } if (node -> clamped) { Graphics_setColour (graphics, Graphics_BLACK); Graphics_setLineWidth (graphics, 2.0); Graphics_circle_mm (graphics, node -> x, node -> y, 5.0); } } Graphics_setColour (graphics, Graphics_BLACK); Graphics_setLineWidth (graphics, saveLineWidth); Graphics_unsetInner (graphics); } void structNetwork :: f_addNode (double x, double y, double activity, bool clamped) { try { NUMvector_append (& d_nodes, 1, & d_numberOfNodes); d_nodes [d_numberOfNodes]. x = x; d_nodes [d_numberOfNodes]. y = y; d_nodes [d_numberOfNodes]. activity = activity; d_nodes [d_numberOfNodes]. clamped = clamped; } catch (MelderError) { Melder_throw (this, ": node not added."); } } void structNetwork :: f_addConnection (long nodeFrom, long nodeTo, double weight, double plasticity) { try { NUMvector_append (& d_connections, 1, & d_numberOfConnections); d_connections [d_numberOfConnections]. nodeFrom = nodeFrom; d_connections [d_numberOfConnections]. nodeTo = nodeTo; d_connections [d_numberOfConnections]. weight = weight; d_connections [d_numberOfConnections]. plasticity = plasticity; } catch (MelderError) { Melder_throw (this, ": connection not added."); } } void structNetwork :: f_setWeightUpdateRule (enum kNetwork_weightUpdateRule weightUpdateRule) { d_weightUpdateRule = weightUpdateRule; } void structNetwork :: f_setActivationSpreadingRule (enum kNetwork_activationSpreadingRule activationSpreadingRule) { d_activationSpreadingRule = activationSpreadingRule; } /* End of file Network.cpp */ sources_5316/gram/Network_def.h0000644000176700017670000000640711753755326015316 0ustar paulpaul/* Network_def.h * * Copyright (C) 2009-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT NetworkNode oo_DEFINE_STRUCT (NetworkNode) oo_DOUBLE (x) oo_DOUBLE (y) oo_BOOLEAN (clamped) oo_DOUBLE (activity) #if ! oo_READING && ! oo_WRITING oo_DOUBLE (excitation) #endif oo_END_STRUCT (NetworkNode) #undef ooSTRUCT #define ooSTRUCT NetworkConnection oo_DEFINE_STRUCT (NetworkConnection) oo_LONG (nodeFrom) oo_LONG (nodeTo) oo_DOUBLE (weight) oo_FROM (1) oo_DOUBLE (plasticity) oo_ENDFROM #if oo_READING if (localVersion < 1) { plasticity = 1.0; } #endif oo_END_STRUCT (NetworkConnection) #undef ooSTRUCT #define ooSTRUCT Network oo_DEFINE_CLASS (Network, Data) oo_DOUBLE (d_minimumActivity) oo_DOUBLE (d_maximumActivity) oo_FROM (3) oo_ENUM (kNetwork_activationSpreadingRule, d_activationSpreadingRule) oo_ENDFROM oo_DOUBLE (d_spreadingRate) oo_DOUBLE (d_selfExcitation) oo_DOUBLE (d_minimumWeight) oo_DOUBLE (d_maximumWeight) oo_FROM (2) oo_ENUM (kNetwork_weightUpdateRule, d_weightUpdateRule) oo_ENDFROM oo_DOUBLE (d_learningRate) oo_DOUBLE (d_leak) oo_DOUBLE (d_xmin) oo_DOUBLE (d_xmax) oo_DOUBLE (d_ymin) oo_DOUBLE (d_ymax) oo_LONG (d_numberOfNodes) oo_STRUCT_VECTOR (NetworkNode, d_nodes, d_numberOfNodes) oo_LONG (d_numberOfConnections) oo_STRUCT_VECTOR (NetworkConnection, d_connections, d_numberOfConnections) #if oo_DECLARING // functions: void f_init (double minimumActivity, double maximumActivity, double spreadingRate, double selfExcitation, double minimumWeight, double maximumWeight, double learningRate, double leak, double xmin, double xmax, double ymin, double ymax, long numberOfNodes, long numberOfConnections); void f_addNode (double x, double y, double activity, bool clamped); void f_addConnection (long nodeFrom, long nodeTo, double weight, double plasticity); void f_draw (Graphics graphics, bool colour); double f_getActivity (long inode); void f_setActivity (long inode, double activity); double f_getWeight (long iconn); void f_setWeight (long iconn, double weight); void f_setClamping (long inode, bool clamped); void f_zeroActivities (long nodeMin, long nodeMax); void f_normalizeActivities (long nodeMin, long nodeMax); void f_spreadActivities (long numberOfSteps); void f_updateWeights (); void f_setWeightUpdateRule (enum kNetwork_weightUpdateRule weightUpdateRule); void f_setActivationSpreadingRule (enum kNetwork_activationSpreadingRule activationSpreadingRule); // overridden methods: virtual void v_info (); #endif oo_END_CLASS (Network) #undef ooSTRUCT /* End of file Network_def.h */ sources_5316/gram/OTMultiEditor.cpp0000644000176700017670000002243211652005471016065 0ustar paulpaul/* OTMultiEditor.cpp * * Copyright (C) 2005-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * a selection of changes: * pb 2005/07/04 created * pb 2007/10/01 constraint plasticity * pb 2011/03/01 multiple update rules */ #include "OTMultiEditor.h" #include "EditorM.h" #include "machine.h" Thing_implement (OTMultiEditor, HyperPage, 0); static void menu_cb_evaluate (EDITOR_ARGS) { EDITOR_IAM (OTMultiEditor); EDITOR_FORM (L"Evaluate", 0) REAL (L"Evaluation noise", L"2.0") EDITOR_OK EDITOR_DO Editor_save (me, L"Evaluate"); OTMulti_newDisharmonies ((OTMulti) my data, GET_REAL (L"Evaluation noise")); Graphics_updateWs (my g); my broadcastDataChanged (); EDITOR_END } static void menu_cb_evaluate_noise_2_0 (EDITOR_ARGS) { EDITOR_IAM (OTMultiEditor); Editor_save (me, L"Evaluate (noise 2.0)"); OTMulti_newDisharmonies ((OTMulti) my data, 2.0); Graphics_updateWs (my g); my broadcastDataChanged (); } static void menu_cb_evaluate_tinyNoise (EDITOR_ARGS) { EDITOR_IAM (OTMultiEditor); Editor_save (me, L"Evaluate (tiny noise)"); OTMulti_newDisharmonies ((OTMulti) my data, 1e-9); Graphics_updateWs (my g); my broadcastDataChanged (); } static void menu_cb_editRanking (EDITOR_ARGS) { EDITOR_IAM (OTMultiEditor); EDITOR_FORM (L"Edit ranking", 0) LABEL (L"constraint", L""); REAL (L"Ranking value", L"100.0"); REAL (L"Disharmony", L"100.0"); EDITOR_OK OTMulti grammar = (OTMulti) my data; OTConstraint constraint; if (my selectedConstraint < 1 || my selectedConstraint > grammar -> numberOfConstraints) Melder_throw ("Select a constraint first."); constraint = & grammar -> constraints [grammar -> index [my selectedConstraint]]; SET_STRING (L"constraint", constraint -> name) SET_REAL (L"Ranking value", constraint -> ranking) SET_REAL (L"Disharmony", constraint -> disharmony) EDITOR_DO OTMulti grammar = (OTMulti) my data; OTConstraint constraint = & grammar -> constraints [grammar -> index [my selectedConstraint]]; Editor_save (me, L"Edit ranking"); constraint -> ranking = GET_REAL (L"Ranking value"); constraint -> disharmony = GET_REAL (L"Disharmony"); OTMulti_sort (grammar); Graphics_updateWs (my g); my broadcastDataChanged (); EDITOR_END } static void menu_cb_learnOne (EDITOR_ARGS) { EDITOR_IAM (OTMultiEditor); EDITOR_FORM (L"Learn one", L"OTGrammar: Learn one...") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) OPTIONMENU (L"Direction", 3) OPTION (L"forward") OPTION (L"backward") OPTION (L"bidirectionally") REAL (L"Plasticity", L"0.1") REAL (L"Rel. plasticity spreading", L"0.1") EDITOR_OK EDITOR_DO Editor_save (me, L"Learn one"); Melder_free (my form1); Melder_free (my form2); my form1 = GuiText_getString (my form1Text); my form2 = GuiText_getString (my form2Text); OTMulti_learnOne ((OTMulti) my data, my form1, my form2, GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Direction"), GET_REAL (L"Plasticity"), GET_REAL (L"Rel. plasticity spreading")); therror Graphics_updateWs (my g); my broadcastDataChanged (); EDITOR_END } static void menu_cb_removeConstraint (EDITOR_ARGS) { EDITOR_IAM (OTMultiEditor); OTMulti grammar = (OTMulti) my data; if (my selectedConstraint < 1 || my selectedConstraint > grammar -> numberOfConstraints) Melder_throw ("Select a constraint first."); OTConstraint constraint = & grammar -> constraints [grammar -> index [my selectedConstraint]]; Editor_save (me, L"Remove constraint"); OTMulti_removeConstraint (grammar, constraint -> name); Graphics_updateWs (my g); my broadcastDataChanged (); } static void menu_cb_resetAllRankings (EDITOR_ARGS) { EDITOR_IAM (OTMultiEditor); EDITOR_FORM (L"Reset all rankings", 0) REAL (L"Ranking", L"100.0") EDITOR_OK EDITOR_DO Editor_save (me, L"Reset all rankings"); OTMulti_reset ((OTMulti) my data, GET_REAL (L"Ranking")); Graphics_updateWs (my g); my broadcastDataChanged (); EDITOR_END } static void menu_cb_OTLearningTutorial (EDITOR_ARGS) { EDITOR_IAM (OTMultiEditor); (void) me; Melder_help (L"OT learning"); } static void do_limit (OTMultiEditor me) { Melder_free (my form1); Melder_free (my form2); my form1 = GuiText_getString (my form1Text); my form2 = GuiText_getString (my form2Text); Graphics_updateWs (my g); } static void gui_button_cb_limit (I, GuiButtonEvent event) { (void) event; iam (OTMultiEditor); do_limit (me); } static void gui_cb_limit (GUI_ARGS) { GUI_IAM (OTMultiEditor); do_limit (me); } void structOTMultiEditor :: v_createChildren () { OTMultiEditor_Parent :: v_createChildren (); #if defined (macintosh) #define STRING_SPACING 8 #else #define STRING_SPACING 2 #endif int height = Machine_getTextHeight (), y = Machine_getMenuBarHeight () + 4; GuiButton_createShown (d_windowForm, 4, 124, y, y + height, L"Partial forms:", gui_button_cb_limit, this, #ifdef _WIN32 GuiButton_DEFAULT // BUG: clickedCallback should work for texts #else 0 #endif ); form1Text = GuiText_createShown (d_windowForm, 124 + STRING_SPACING, 274 + STRING_SPACING, y, Gui_AUTOMATIC, 0); #if motif /* TODO */ XtAddCallback (form1Text, XmNactivateCallback, gui_cb_limit, (XtPointer) this); #endif form2Text = GuiText_createShown (d_windowForm, 274 + 2 * STRING_SPACING, 424 + 2 * STRING_SPACING, y, Gui_AUTOMATIC, 0); #if motif /* TODO */ XtAddCallback (form2Text, XmNactivateCallback, gui_cb_limit, (XtPointer) this); #endif } void structOTMultiEditor :: v_createMenus () { OTMultiEditor_Parent :: v_createMenus (); Editor_addCommand (this, L"Edit", L"-- edit ot --", 0, NULL); Editor_addCommand (this, L"Edit", L"Evaluate...", 0, menu_cb_evaluate); Editor_addCommand (this, L"Edit", L"Evaluate (noise 2.0)", '2', menu_cb_evaluate_noise_2_0); Editor_addCommand (this, L"Edit", L"Evaluate (tiny noise)", '9', menu_cb_evaluate_tinyNoise); Editor_addCommand (this, L"Edit", L"Edit ranking...", 'E', menu_cb_editRanking); Editor_addCommand (this, L"Edit", L"Reset all rankings...", 'R', menu_cb_resetAllRankings); Editor_addCommand (this, L"Edit", L"Learn one...", '1', menu_cb_learnOne); Editor_addCommand (this, L"Edit", L"-- remove --", 0, NULL); Editor_addCommand (this, L"Edit", L"Remove constraint", 0, menu_cb_removeConstraint); } void structOTMultiEditor :: v_createHelpMenuItems (EditorMenu menu) { OTMultiEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"OT learning tutorial", 0, menu_cb_OTLearningTutorial); } static OTMulti drawTableau_grammar; static const wchar *drawTableau_form1, *drawTableau_form2; static bool drawTableau_constraintsAreDrawnVertically; static void drawTableau (Graphics g) { OTMulti_drawTableau (drawTableau_grammar, g, drawTableau_form1, drawTableau_form2, drawTableau_constraintsAreDrawnVertically, true); } void structOTMultiEditor :: v_draw () { OTMulti grammar = (OTMulti) data; static MelderString buffer = { 0 }; double rowHeight = 0.25, tableauHeight = 2 * rowHeight; Graphics_clearWs (g); HyperPage_listItem (this, L"\t\t %%ranking value\t %disharmony\t %plasticity"); for (long icons = 1; icons <= grammar -> numberOfConstraints; icons ++) { OTConstraint constraint = & grammar -> constraints [grammar -> index [icons]]; MelderString_empty (& buffer); MelderString_append (& buffer, L"\t", icons == selectedConstraint ? L"\\sp " : L" ", L"@@", Melder_integer (icons), L"|", constraint -> name, L"@\t ", Melder_fixed (constraint -> ranking, 3)); MelderString_append (& buffer, L"\t ", Melder_fixed (constraint -> disharmony, 3)); MelderString_append (& buffer, L"\t ", Melder_fixed (constraint -> plasticity, 6)); HyperPage_listItem (this, buffer.string); } Graphics_setAtSignIsLink (g, FALSE); drawTableau_grammar = grammar; for (long icand = 1; icand <= grammar -> numberOfCandidates; icand ++) { if (OTMulti_candidateMatches (grammar, icand, form1, form2)) { tableauHeight += rowHeight; } } drawTableau_form1 = form1; drawTableau_form2 = form2; drawTableau_constraintsAreDrawnVertically = d_constraintsAreDrawnVertically; HyperPage_picture (this, 20, tableauHeight, drawTableau); Graphics_setAtSignIsLink (g, TRUE); } int structOTMultiEditor :: v_goToPage (const wchar *title) { if (title == NULL) return 1; selectedConstraint = wcstol (title, NULL, 10); return 1; } OTMultiEditor OTMultiEditor_create (GuiObject parent, const wchar *title, OTMulti grammar) { try { autoOTMultiEditor me = Thing_new (OTMultiEditor); my data = grammar; my form1 = Melder_wcsdup (L""); my form2 = Melder_wcsdup (L""); HyperPage_init (me.peek(), parent, title, grammar); return me.transfer(); } catch (MelderError) { Melder_throw ("OTMulti window not created."); } } /* End of file OTMultiEditor.cpp */ sources_5316/gram/OTGrammarEditor.cpp0000644000176700017670000002454411652005440016363 0ustar paulpaul/* OTGrammarEditor.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * a selection of changes: * pb 2003/05/27 learnOne and learnOneFromPartialOutput * pb 2008/05/31 ExponentialMaximumEntropy */ #include "OTGrammarEditor.h" #include "EditorM.h" Thing_implement (OTGrammarEditor, HyperPage, 0); static void menu_cb_evaluate (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); EDITOR_FORM (L"Evaluate", 0) REAL (L"Noise", L"2.0") EDITOR_OK EDITOR_DO Editor_save (me, L"Evaluate"); OTGrammar_newDisharmonies ((OTGrammar) my data, GET_REAL (L"Noise")); Graphics_updateWs (my g); my broadcastDataChanged (); EDITOR_END } static void menu_cb_evaluate_noise_2_0 (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); Editor_save (me, L"Evaluate (noise 2.0)"); OTGrammar_newDisharmonies ((OTGrammar) my data, 2.0); Graphics_updateWs (my g); my broadcastDataChanged (); } static void menu_cb_evaluate_tinyNoise (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); Editor_save (me, L"Evaluate (tiny noise)"); OTGrammar_newDisharmonies ((OTGrammar) my data, 1e-9); Graphics_updateWs (my g); my broadcastDataChanged (); } static void menu_cb_evaluate_zeroNoise (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); Editor_save (me, L"Evaluate (zero noise)"); OTGrammar_newDisharmonies ((OTGrammar) my data, 0.0); Graphics_updateWs (my g); my broadcastDataChanged (); } static void menu_cb_editConstraint (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); EDITOR_FORM (L"Edit constraint", 0) LABEL (L"constraint", L""); REAL (L"Ranking value", L"100.0"); REAL (L"Disharmony", L"100.0"); REAL (L"Plasticity", L"1.0"); EDITOR_OK OTGrammar ot = (OTGrammar) my data; OTGrammarConstraint constraint; if (my selected < 1 || my selected > ot -> numberOfConstraints) Melder_throw ("Select a constraint first."); constraint = & ot -> constraints [ot -> index [my selected]]; SET_STRING (L"constraint", constraint -> name) SET_REAL (L"Ranking value", constraint -> ranking) SET_REAL (L"Disharmony", constraint -> disharmony) SET_REAL (L"Plasticity", constraint -> plasticity) EDITOR_DO OTGrammar ot = (OTGrammar) my data; OTGrammarConstraint constraint = & ot -> constraints [ot -> index [my selected]]; Editor_save (me, L"Edit constraint"); constraint -> ranking = GET_REAL (L"Ranking value"); constraint -> disharmony = GET_REAL (L"Disharmony"); constraint -> plasticity = GET_REAL (L"Plasticity"); OTGrammar_sort (ot); Graphics_updateWs (my g); my broadcastDataChanged (); EDITOR_END } static void menu_cb_learnOne (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); EDITOR_FORM (L"Learn one", L"OTGrammar: Learn one...") LABEL (L"", L"Underlying form:") SENTENCE (L"Input string", L"") LABEL (L"", L"Adult surface form:") SENTENCE (L"Output string", L"") REAL (L"Evaluation noise", L"2.0") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) REAL (L"Plasticity", L"0.1") REAL (L"Rel. plasticity spreading", L"0.1") BOOLEAN (L"Honour local rankings", 1) EDITOR_OK EDITOR_DO Editor_save (me, L"Learn one"); OTGrammar_learnOne ((OTGrammar) my data, GET_STRING (L"Input string"), GET_STRING (L"Output string"), GET_REAL (L"Evaluation noise"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Honour local rankings"), GET_REAL (L"Plasticity"), GET_REAL (L"Rel. plasticity spreading"), TRUE, TRUE, NULL); OTGrammar_sort ((OTGrammar) my data); Graphics_updateWs (my g); my broadcastDataChanged (); EDITOR_END } static void menu_cb_learnOneFromPartialOutput (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); EDITOR_FORM (L"Learn one from partial adult output", 0) LABEL (L"", L"Partial adult surface form (e.g. overt form):") SENTENCE (L"Partial output", L"") REAL (L"Evaluation noise", L"2.0") OPTIONMENU_ENUM (L"Update rule", kOTGrammar_rerankingStrategy, SYMMETRIC_ALL) REAL (L"Plasticity", L"0.1") REAL (L"Rel. plasticity spreading", L"0.1") BOOLEAN (L"Honour local rankings", 1) NATURAL (L"Number of chews", L"1") EDITOR_OK EDITOR_DO Editor_save (me, L"Learn one from partial output"); OTGrammar_learnOneFromPartialOutput ((OTGrammar) my data, GET_STRING (L"Partial output"), GET_REAL (L"Evaluation noise"), GET_ENUM (kOTGrammar_rerankingStrategy, L"Update rule"), GET_INTEGER (L"Honour local rankings"), GET_REAL (L"Plasticity"), GET_REAL (L"Rel. plasticity spreading"), GET_INTEGER (L"Number of chews"), TRUE); OTGrammar_sort ((OTGrammar) my data); Graphics_updateWs (my g); my broadcastDataChanged (); EDITOR_END } static void menu_cb_removeConstraint (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); OTGrammar ot = (OTGrammar) my data; OTGrammarConstraint constraint; if (my selected < 1 || my selected > ot -> numberOfConstraints) Melder_throw ("Select a constraint first."); constraint = & ot -> constraints [ot -> index [my selected]]; Editor_save (me, L"Remove constraint"); OTGrammar_removeConstraint (ot, constraint -> name); Graphics_updateWs (my g); my broadcastDataChanged (); } static void menu_cb_resetAllRankings (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); EDITOR_FORM (L"Reset all rankings", 0) REAL (L"Ranking", L"100.0") EDITOR_OK EDITOR_DO Editor_save (me, L"Reset all rankings"); OTGrammar_reset ((OTGrammar) my data, GET_REAL (L"Ranking")); Graphics_updateWs (my g); my broadcastDataChanged (); EDITOR_END } static void menu_cb_OTGrammarEditor_help (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); Melder_help (L"OTGrammarEditor"); } static void menu_cb_OTGrammar_help (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); Melder_help (L"OTGrammar"); } static void menu_cb_OTLearningTutorial (EDITOR_ARGS) { EDITOR_IAM (OTGrammarEditor); Melder_help (L"OT learning"); } void structOTGrammarEditor :: v_createMenus () { OTGrammarEditor_Parent :: v_createMenus (); Editor_addCommand (this, L"Edit", L"-- edit ot --", 0, NULL); Editor_addCommand (this, L"Edit", L"Evaluate...", 0, menu_cb_evaluate); Editor_addCommand (this, L"Edit", L"Evaluate (noise 2.0)", '2', menu_cb_evaluate_noise_2_0); Editor_addCommand (this, L"Edit", L"Evaluate (zero noise)", '0', menu_cb_evaluate_zeroNoise); Editor_addCommand (this, L"Edit", L"Evaluate (tiny noise)", '9', menu_cb_evaluate_tinyNoise); Editor_addCommand (this, L"Edit", L"Edit constraint...", 'E', menu_cb_editConstraint); Editor_addCommand (this, L"Edit", L"Reset all rankings...", 'R', menu_cb_resetAllRankings); Editor_addCommand (this, L"Edit", L"Learn one...", 0, menu_cb_learnOne); Editor_addCommand (this, L"Edit", L"Learn one from partial output...", '1', menu_cb_learnOneFromPartialOutput); Editor_addCommand (this, L"Edit", L"-- remove ot --", 0, NULL); Editor_addCommand (this, L"Edit", L"Remove constraint", 0, menu_cb_removeConstraint); } void structOTGrammarEditor :: v_createHelpMenuItems (EditorMenu menu) { OTGrammarEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"OTGrammarEditor help", '?', menu_cb_OTGrammarEditor_help); EditorMenu_addCommand (menu, L"OTGrammar help", 0, menu_cb_OTGrammar_help); EditorMenu_addCommand (menu, L"OT learning tutorial", 0, menu_cb_OTLearningTutorial); } static OTGrammar drawTableau_ot; static const wchar *drawTableau_input; static bool drawTableau_constraintsAreDrawnVertically; static void drawTableau (Graphics g) { OTGrammar_drawTableau (drawTableau_ot, g, drawTableau_constraintsAreDrawnVertically, drawTableau_input); } void structOTGrammarEditor :: v_draw () { OTGrammar ot = (OTGrammar) data; static wchar text [1000]; Graphics_clearWs (g); if (ot -> decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG || ot -> decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) { HyperPage_listItem (this, L"\t\t %%ranking value\t %disharmony\t %plasticity\t %%e^^disharmony"); } else { HyperPage_listItem (this, L"\t\t %%ranking value\t %disharmony\t %plasticity"); } for (long icons = 1; icons <= ot -> numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & ot -> constraints [ot -> index [icons]]; if (ot -> decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG || ot -> decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) { swprintf (text, 1000, L"\t%ls@@%ld|%ls@\t %.3f\t %.3f\t %.6f\t %ls", icons == selected ? L"\\sp " : L" ", icons, constraint -> name, constraint -> ranking, constraint -> disharmony, constraint -> plasticity, Melder_float (Melder_half (exp (constraint -> disharmony)))); } else { swprintf (text, 1000, L"\t%ls@@%ld|%ls@\t %.3f\t %.3f\t %.6f", icons == selected ? L"\\sp " : L" ", icons, constraint -> name, constraint -> ranking, constraint -> disharmony, constraint -> plasticity); } HyperPage_listItem (this, text); } Graphics_setAtSignIsLink (g, FALSE); for (long itab = 1; itab <= ot -> numberOfTableaus; itab ++) { OTGrammarTableau tableau = & ot -> tableaus [itab]; double rowHeight = 0.25; double tableauHeight = rowHeight * (tableau -> numberOfCandidates + 2); drawTableau_ot = ot; drawTableau_input = tableau -> input; drawTableau_constraintsAreDrawnVertically = d_constraintsAreDrawnVertically; HyperPage_picture (this, 20, tableauHeight, drawTableau); } Graphics_setAtSignIsLink (g, TRUE); } int structOTGrammarEditor :: v_goToPage (const wchar *title) { if (title == NULL) return 1; selected = wcstol (title, NULL, 10); return 1; } OTGrammarEditor OTGrammarEditor_create (GuiObject parent, const wchar *title, OTGrammar ot) { try { autoOTGrammarEditor me = Thing_new (OTGrammarEditor); my data = ot; HyperPage_init (me.peek(), parent, title, ot); return me.transfer(); } catch (MelderError) { Melder_throw ("OTGrammar window not created."); } } /* End of file OTGrammarEditor.cpp */ sources_5316/gram/OTGrammar_ex_NoCoda.cpp0000644000176700017670000000517611633506732017144 0ustar paulpaul/* OTGrammar_ex_NoCoda.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "OTGrammar.h" OTGrammar OTGrammar_create_NoCoda_grammar (void) { try { OTGrammarCandidate candidate; OTGrammarTableau tableau; OTGrammarConstraint constraint; autoOTGrammar me = Thing_new (OTGrammar); my constraints = NUMvector (1, my numberOfConstraints = 2); constraint = & my constraints [1]; constraint -> name = Melder_wcsdup (L"N\\s{O}C\\s{ODA}"); constraint -> ranking = 100.0; constraint -> plasticity = 1.0; constraint = & my constraints [2]; constraint -> name = Melder_wcsdup (L"P\\s{ARSE}"); constraint -> ranking = 90.0; constraint -> plasticity = 1.0; my tableaus = NUMvector (1, my numberOfTableaus = 2); tableau = & my tableaus [1]; tableau -> input = Melder_wcsdup (L"pat"); tableau -> candidates = NUMvector (1, tableau -> numberOfCandidates = 2); candidate = & tableau -> candidates [1]; candidate -> output = Melder_wcsdup (L"pa"); candidate -> marks = NUMvector (1, candidate -> numberOfConstraints = 2); candidate -> marks [2] = 1; candidate = & tableau -> candidates [2]; candidate -> output = Melder_wcsdup (L"pat"); candidate -> marks = NUMvector (1, candidate -> numberOfConstraints = 2); candidate -> marks [1] = 1; tableau = & my tableaus [2]; tableau -> input = Melder_wcsdup (L"pa"); tableau -> candidates = NUMvector (1, tableau -> numberOfCandidates = 1); candidate = & tableau -> candidates [1]; candidate -> output = Melder_wcsdup (L"pa"); candidate -> marks = NUMvector (1, candidate -> numberOfConstraints = 2); OTGrammar_checkIndex (me.peek()); therror OTGrammar_newDisharmonies (me.peek(), 0.0); return me.transfer(); } catch (MelderError) { Melder_throw ("NoCoda grammar not created."); } } /* End of file OTGrammar_ex_NoCoda.cpp */ sources_5316/gram/OTGrammar.cpp0000644000176700017670000034135611647117261015230 0ustar paulpaul/* OTGrammar.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2002/11/04 randomize in case of equal candidates * pb 2003/05/08 better superset violation warning * pb 2003/05/23 made superset violation warning conditional * pb 2003/10/15 backtrack in case of failing multiple chews for EDCD * pb 2003/10/15 crucial ties option * pb 2004/01/17 OTGrammar_Distributions_getFractionCorrect * pb 2004/08/08 OTGrammar_removeHarmonicallyBoundedCandidates * pb 2004/08/09 bug removal: more complete OTGrammar_save and restore (affected multiple-chew correctness), * changing the 114.5 in Boersma (Phonology 2003) to 118.1 * pb 2004/08/09 suppressed superset violation in case of identical constraint violation patterns such * as for /(L L2) L (L2 L) (L1 L)/ and /(L2 L) L (L L2) (L1 L)/, thus restricting the warning to cases * of *strict* superset violations * pb 2004/08/11 repaired memory leak in OTGrammarTableau_removeCandidate_unstripped * pb 2004/09/10 monitor rankings during learning from PairDistribution or Distributions * pb 2004/10/16 struct structOTxx * pb 2005/01/24 write to headerless spreadsheet file * pb 2005/04/19 OTHistory * pb 2005/06/30 learning from partial pairs * pb 2005/12/11 OTGrammar_honourlocalRankings: * pb 2005/12/11 OTGrammar_PairDistribution_listObligatoryRankings (depth 1) * pb 2006/01/05 new decision strategies: HarmonicGrammar and LinearOT * pb 2006/01/21 better procedure name * pb 2006/02/02 new decision strategy: ExponentialHG * pb 2006/12/08 MelderInfo * pb 2007/04/22 multiply learning step by number of violations (for HarmonicGrammar and LinearOT) * pb 2007/04/25 new decision strategy: MaximumEntropy * pb 2007/04/30 many improvements * pb 2007/05/20 new decision strategy: PositiveHG * pb 2007/06/21 corrected PositiveHG * pb 2007/06/21 made spreadsheet file readable as Table * pb 2007/07/24 leak and constraint plasticity * pb 2007/07/27 leak and constraint plasticity also written... * pb 2007/08/08 wchar * pb 2007/10/01 can write as encoding * pb 2008/03/03 EDCD with vacation * pb 2008/03/07 Demote one with vacation * pb 2008/03/07 Reset to random total ranking * pb 2008/03/27 Exponential HG: reset average weight to zero after every change * pb 2008/03/28 Exponential HG: set update rule to HG-GLA rather than OT-GLA * pb 2008/03/31 OTGrammar_PairDistribution_findPositiveWeights * pb 2008/04/08 made (OTGrammar & Distributions) learnFromPartialOutputs and getFractionCorrect five times faster * pb 2008/04/12 split off NUMlinprog * pb 2008/05/31 new decision strategy: ExponentialMaximumEntropy * pb 2009/03/09 new update rule: Weighted all up, highest down * pb 2009/07/07 OTGrammar_PairDistribution_getMinimumNumberCorrect * pb 2010/06/05 corrected colours * pb 2011/03/01 renamed "strategy" to "updateRule", "meanLearningStep" to "plasticity", "rankingSpreading" to "evaluationNoise" * pb 2011/03/22 C++ * pb 2011/04/27 Melder_debug 41 and 42 * pb 2011/07/14 C++ */ #include "OTGrammar.h" #include "NUM.h" #include "oo_DESTROY.h" #include "OTGrammar_def.h" #include "oo_COPY.h" #include "OTGrammar_def.h" #include "oo_EQUAL.h" #include "OTGrammar_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "OTGrammar_def.h" #include "oo_WRITE_BINARY.h" #include "OTGrammar_def.h" #include "oo_READ_BINARY.h" #include "OTGrammar_def.h" #include "oo_DESCRIPTION.h" #include "OTGrammar_def.h" #include "enums_getText.h" #include "OTGrammar_enums.h" #include "enums_getValue.h" #include "OTGrammar_enums.h" void structOTGrammar :: v_info () { structData :: v_info (); long numberOfCandidates = 0, numberOfViolations = 0; for (long itab = 1; itab <= numberOfTableaus; itab ++) { numberOfCandidates += tableaus [itab]. numberOfCandidates; for (long icand = 1; icand <= tableaus [itab]. numberOfCandidates; icand ++) for (long icons = 1; icons <= numberOfConstraints; icons ++) numberOfViolations += tableaus [itab]. candidates [icand]. marks [icons]; } MelderInfo_writeLine2 (L"Decision strategy: ", kOTGrammar_decisionStrategy_getText (decisionStrategy)); MelderInfo_writeLine2 (L"Number of constraints: ", Melder_integer (numberOfConstraints)); MelderInfo_writeLine2 (L"Number of tableaus: ", Melder_integer (numberOfTableaus)); MelderInfo_writeLine2 (L"Number of candidates: ", Melder_integer (numberOfCandidates)); MelderInfo_writeLine2 (L"Number of violation marks: ", Melder_integer (numberOfViolations)); } void structOTGrammar :: v_writeText (MelderFile file) { MelderFile_write7 (file, L"\n<", kOTGrammar_decisionStrategy_getText (decisionStrategy), L">\n", Melder_double (leak), L" ! leak\n", Melder_integer (numberOfConstraints), L" constraints"); for (long icons = 1; icons <= numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & constraints [icons]; MelderFile_write3 (file, L"\nconstraint [", Melder_integer (icons), L"]: \""); for (const wchar *p = & constraint -> name [0]; *p; p ++) { if (*p =='\"') MelderFile_writeCharacter (file, '\"'); // Double any quotes within quotes. MelderFile_writeCharacter (file, *p); } MelderFile_write7 (file, L"\" ", Melder_double (constraint -> ranking), L" ", Melder_double (constraint -> disharmony), L" ", Melder_double (constraint -> plasticity), L" ! "); for (const wchar *p = & constraint -> name [0]; *p; p ++) { if (*p == '\n') MelderFile_writeCharacter (file, ' '); else if (*p == '\\' && p [1] == 's' && p [2] == '{') p += 2; else if (*p == '}') { } else MelderFile_writeCharacter (file, *p); } } MelderFile_write3 (file, L"\n\n", Melder_integer (numberOfFixedRankings), L" fixed rankings"); for (long irank = 1; irank <= numberOfFixedRankings; irank ++) { OTGrammarFixedRanking fixedRanking = & fixedRankings [irank]; MelderFile_write4 (file, L"\n ", Melder_integer (fixedRanking -> higher), L" ", Melder_integer (fixedRanking -> lower)); } MelderFile_write3 (file, L"\n\n", Melder_integer (numberOfTableaus), L" tableaus"); for (long itab = 1; itab <= numberOfTableaus; itab ++) { OTGrammarTableau tableau = & tableaus [itab]; MelderFile_write3 (file, L"\ninput [", Melder_integer (itab), L"]: \""); for (const wchar *p = & tableau -> input [0]; *p; p ++) { if (*p =='\"') MelderFile_writeCharacter (file, '\"'); // Double any quotes within quotes. MelderFile_writeCharacter (file, *p); } MelderFile_write2 (file, L"\" ", Melder_integer (tableau -> numberOfCandidates)); for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate candidate = & tableau -> candidates [icand]; MelderFile_write3 (file, L"\n candidate [", Melder_integer (icand), L"]: \""); for (const wchar *p = & candidate -> output [0]; *p; p ++) { if (*p =='\"') MelderFile_writeCharacter (file, '\"'); // Double any quotes within quotes. MelderFile_writeCharacter (file, *p); } MelderFile_writeCharacter (file, '\"'); for (long icons = 1; icons <= candidate -> numberOfConstraints; icons ++) { MelderFile_write2 (file, L" ", Melder_integer (candidate -> marks [icons])); } } } } void OTGrammar_checkIndex (OTGrammar me) { int icons; if (my index) return; my index = NUMvector (1, my numberOfConstraints); for (icons = 1; icons <= my numberOfConstraints; icons ++) my index [icons] = icons; OTGrammar_sort (me); } void structOTGrammar :: v_readText (MelderReadText text) { int localVersion = Thing_version; OTGrammar_Parent :: v_readText (text); if (localVersion >= 1) { try { decisionStrategy = texgete1 (text, kOTGrammar_decisionStrategy_getValue); therror } catch (MelderError) { Melder_throw ("Trying to read decision strategy."); } } if (localVersion >= 2) { try { leak = texgetr8 (text); } catch (MelderError) { Melder_throw ("Trying to read leak."); } } try { numberOfConstraints = texgeti4 (text); } catch (MelderError) { Melder_throw ("Trying to read number of constraints."); } if (numberOfConstraints < 1) Melder_throw ("No constraints."); constraints = NUMvector (1, numberOfConstraints); for (long icons = 1; icons <= numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & constraints [icons]; try { constraint -> name = texgetw2 (text); } catch (MelderError) { Melder_throw ("Trying to read name of constraint ", icons, "."); } try { constraint -> ranking = texgetr8 (text); } catch (MelderError) { Melder_throw ("Trying to read ranking of constraint ", icons, "."); } try { constraint -> disharmony = texgetr8 (text); } catch (MelderError) { Melder_throw ("Trying to read disharmony of constraint ", icons, "."); } if (localVersion < 2) { constraint -> plasticity = 1.0; } else { try { constraint -> plasticity = texgetr8 (text); } catch (MelderError) { Melder_throw ("Trying to read plasticity of constraint ", icons, "."); } } } try { numberOfFixedRankings = texgeti4 (text); } catch (MelderError) { Melder_throw ("Trying to read number of fixed rankings."); } if (numberOfFixedRankings >= 1) { fixedRankings = NUMvector (1, numberOfFixedRankings); for (long irank = 1; irank <= numberOfFixedRankings; irank ++) { OTGrammarFixedRanking fixedRanking = & fixedRankings [irank]; try { fixedRanking -> higher = texgeti4 (text); } catch (MelderError) { Melder_throw ("Trying to read the higher of constraint pair ", irank, "."); } try { fixedRanking -> lower = texgeti4 (text); } catch (MelderError) { Melder_throw ("Trying to read the lower of constraint pair ", irank, "."); } } } try { numberOfTableaus = texgeti4 (text); } catch (MelderError) { Melder_throw ("Trying to read number of tableaus."); } if (numberOfTableaus < 1) Melder_throw (L"No tableaus."); tableaus = NUMvector (1, numberOfTableaus); for (long itab = 1; itab <= numberOfTableaus; itab ++) { OTGrammarTableau tableau = & tableaus [itab]; try { tableau -> input = texgetw2 (text); } catch (MelderError) { Melder_throw ("Trying to read input of tableau ", itab, "."); } try { tableau -> numberOfCandidates = texgeti4 (text); } catch (MelderError) { Melder_throw ("Trying to read number of candidates of tableau ", itab, "."); } if (tableau -> numberOfCandidates < 1) Melder_throw ("No candidates in tableau ", itab, " (input: ", tableau -> input, ")" " in line ", MelderReadText_getLineNumber (text), itab == 1 ? L"." : ", or perhaps wrong number of candidates for input " L_LEFT_GUILLEMET, itab == 1 ? NULL : tableaus [itab - 1]. input, itab == 1 ? NULL : L_RIGHT_GUILLEMET L"."); tableau -> candidates = NUMvector (1, tableau -> numberOfCandidates); for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate candidate = & tableau -> candidates [icand]; try { candidate -> output = texgetw2 (text); } catch (MelderError) { Melder_throw ("Trying to read candidate ", icand, " of tableau ", itab, " (input: ", tableau -> input, ") in line ", MelderReadText_getLineNumber (text), "."); } candidate -> numberOfConstraints = numberOfConstraints; // redundancy, needed for writing binary candidate -> marks = NUMvector (1, candidate -> numberOfConstraints); for (long icons = 1; icons <= candidate -> numberOfConstraints; icons ++) { try { candidate -> marks [icons] = texgeti2 (text); } catch (MelderError) { Melder_throw ("Trying to read number of violations of constraint ", icons, " (", constraints [icons]. name, ")" " of candidate ", icand, " (", candidate -> output, ")" " of tableau ", itab, " (input: ", tableau -> input, ")" " in line ", MelderReadText_getLineNumber (text), L"."); } } } } OTGrammar_checkIndex (this); } Thing_implement (OTGrammar, Data, 2); Thing_implement (OTHistory, TableOfReal, 0); static OTGrammar constraintCompare_grammar; static int constraintCompare (const void *first, const void *second) { OTGrammar me = constraintCompare_grammar; long icons = * (long *) first, jcons = * (long *) second; OTGrammarConstraint ci = & my constraints [icons], cj = & my constraints [jcons]; /* * Sort primarily by disharmony. */ if (ci -> disharmony > cj -> disharmony) return -1; if (ci -> disharmony < cj -> disharmony) return +1; /* * Tied constraints are sorted alphabetically. */ return wcscmp (my constraints [icons]. name, my constraints [jcons]. name); } void OTGrammar_sort (OTGrammar me) { constraintCompare_grammar = me; qsort (& my index [1], my numberOfConstraints, sizeof (long), constraintCompare); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [my index [icons]]; constraint -> tiedToTheLeft = icons > 1 && my constraints [my index [icons - 1]]. disharmony == constraint -> disharmony; constraint -> tiedToTheRight = icons < my numberOfConstraints && my constraints [my index [icons + 1]]. disharmony == constraint -> disharmony; } } void OTGrammar_newDisharmonies (OTGrammar me, double spreading) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; constraint -> disharmony = constraint -> ranking + NUMrandomGauss (0, spreading) /*NUMrandomUniform (-spreading, spreading)*/; } OTGrammar_sort (me); } long OTGrammar_getTableau (OTGrammar me, const wchar *input) { long n = my numberOfTableaus; for (long i = 1; i <= n; i ++) if (wcsequ (my tableaus [i]. input, input)) return i; Melder_throw ("Input \"", input, "\" not in list of tableaus."); } static void _OTGrammar_fillInHarmonies (OTGrammar me, long itab) { if (my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) return; OTGrammarTableau tableau = & my tableaus [itab]; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate candidate = & tableau -> candidates [icand]; int *marks = candidate -> marks; double disharmony = 0.0; if (my decisionStrategy == kOTGrammar_decisionStrategy_HARMONIC_GRAMMAR || my decisionStrategy == kOTGrammar_decisionStrategy_MAXIMUM_ENTROPY) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { disharmony += my constraints [icons]. disharmony * marks [icons]; } } else if (my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { disharmony += exp (my constraints [icons]. disharmony) * marks [icons]; } } else if (my decisionStrategy == kOTGrammar_decisionStrategy_LINEAR_OT) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { if (my constraints [icons]. disharmony > 0.0) { disharmony += my constraints [icons]. disharmony * marks [icons]; } } } else if (my decisionStrategy == kOTGrammar_decisionStrategy_POSITIVE_HG) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { double constraintDisharmony = my constraints [icons]. disharmony > 1.0 ? my constraints [icons]. disharmony : 1.0; disharmony += constraintDisharmony * marks [icons]; } } else { Melder_fatal ("_OTGrammar_fillInHarmonies: unimplemented decision strategy."); } candidate -> harmony = - disharmony; } } int OTGrammar_compareCandidates (OTGrammar me, long itab1, long icand1, long itab2, long icand2) { int *marks1 = my tableaus [itab1]. candidates [icand1]. marks; int *marks2 = my tableaus [itab2]. candidates [icand2]. marks; if (my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int numberOfMarks1 = marks1 [my index [icons]]; int numberOfMarks2 = marks2 [my index [icons]]; /* * Count tied constraints as one. */ while (my constraints [my index [icons]]. tiedToTheRight) { icons ++; numberOfMarks1 += marks1 [my index [icons]]; numberOfMarks2 += marks2 [my index [icons]]; } if (numberOfMarks1 < numberOfMarks2) return -1; /* Candidate 1 is better than candidate 2. */ if (numberOfMarks1 > numberOfMarks2) return +1; /* Candidate 2 is better than candidate 1. */ } /* If we arrive here, None of the comparisons found a difference between the two candidates. Hence, they are equally good. */ return 0; } else if (my decisionStrategy == kOTGrammar_decisionStrategy_HARMONIC_GRAMMAR || my decisionStrategy == kOTGrammar_decisionStrategy_MAXIMUM_ENTROPY) { double disharmony1 = 0.0, disharmony2 = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { disharmony1 += my constraints [icons]. disharmony * marks1 [icons]; disharmony2 += my constraints [icons]. disharmony * marks2 [icons]; } if (disharmony1 < disharmony2) return -1; /* Candidate 1 is better than candidate 2. */ if (disharmony1 > disharmony2) return +1; /* Candidate 2 is better than candidate 1. */ } else if (my decisionStrategy == kOTGrammar_decisionStrategy_LINEAR_OT) { double disharmony1 = 0.0, disharmony2 = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { if (my constraints [icons]. disharmony > 0.0) { disharmony1 += my constraints [icons]. disharmony * marks1 [icons]; disharmony2 += my constraints [icons]. disharmony * marks2 [icons]; } } if (disharmony1 < disharmony2) return -1; /* Candidate 1 is better than candidate 2. */ if (disharmony1 > disharmony2) return +1; /* Candidate 2 is better than candidate 1. */ } else if (my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) { double disharmony1 = 0.0, disharmony2 = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { disharmony1 += exp (my constraints [icons]. disharmony) * marks1 [icons]; disharmony2 += exp (my constraints [icons]. disharmony) * marks2 [icons]; } if (disharmony1 < disharmony2) return -1; /* Candidate 1 is better than candidate 2. */ if (disharmony1 > disharmony2) return +1; /* Candidate 2 is better than candidate 1. */ } else if (my decisionStrategy == kOTGrammar_decisionStrategy_POSITIVE_HG) { double disharmony1 = 0.0, disharmony2 = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { double constraintDisharmony = my constraints [icons]. disharmony > 1.0 ? my constraints [icons]. disharmony : 1.0; disharmony1 += constraintDisharmony * marks1 [icons]; disharmony2 += constraintDisharmony * marks2 [icons]; } if (disharmony1 < disharmony2) return -1; /* Candidate 1 is better than candidate 2. */ if (disharmony1 > disharmony2) return +1; /* Candidate 2 is better than candidate 1. */ } else Melder_fatal ("Unimplemented decision strategy."); return 0; /* The two total disharmonies are equal. */ } static void _OTGrammar_fillInProbabilities (OTGrammar me, long itab) { OTGrammarTableau tableau = & my tableaus [itab]; double maximumHarmony = tableau -> candidates [1]. harmony; for (long icand = 2; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate candidate = & tableau -> candidates [icand]; if (candidate -> harmony > maximumHarmony) { maximumHarmony = candidate -> harmony; } } for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate candidate = & tableau -> candidates [icand]; candidate -> probability = exp (candidate -> harmony - maximumHarmony); Melder_assert (candidate -> probability >= 0.0 && candidate -> probability <= 1.0); } double sumOfProbabilities = 0.0; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate candidate = & tableau -> candidates [icand]; sumOfProbabilities += candidate -> probability; } Melder_assert (sumOfProbabilities > 0.0); // Because at least one of them is 1.0. for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate candidate = & tableau -> candidates [icand]; candidate -> probability /= sumOfProbabilities; } } long OTGrammar_getWinner (OTGrammar me, long itab) { long icand_best = 1; if (my decisionStrategy == kOTGrammar_decisionStrategy_MAXIMUM_ENTROPY || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) { _OTGrammar_fillInHarmonies (me, itab); _OTGrammar_fillInProbabilities (me, itab); double cutOff = NUMrandomUniform (0.0, 1.0); double sumOfProbabilities = 0.0; for (long icand = 1; icand <= my tableaus [itab]. numberOfCandidates; icand ++) { sumOfProbabilities += my tableaus [itab]. candidates [icand]. probability; if (sumOfProbabilities > cutOff) { icand_best = icand; break; } } } else { long numberOfBestCandidates = 1; for (long icand = 2; icand <= my tableaus [itab]. numberOfCandidates; icand ++) { int comparison = OTGrammar_compareCandidates (me, itab, icand, itab, icand_best); if (comparison == -1) { icand_best = icand; // the current candidate is the unique best candidate found so far numberOfBestCandidates = 1; } else if (comparison == 0) { numberOfBestCandidates += 1; // the current candidate is equally good as the best found before /* * Give all candidates that are equally good an equal chance to become the winner. */ if (Melder_debug == 41) { icand_best = icand_best; // keep first } else if (Melder_debug == 42) { icand_best = icand; // take last } else if (NUMrandomUniform (0.0, numberOfBestCandidates) < 1.0) { // default: take random icand_best = icand; } } } } return icand_best; } long OTGrammar_getNumberOfOptimalCandidates (OTGrammar me, long itab) { if (my decisionStrategy == kOTGrammar_decisionStrategy_MAXIMUM_ENTROPY || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) return 1; long icand_best = 1, icand, numberOfBestCandidates = 1; for (icand = 2; icand <= my tableaus [itab]. numberOfCandidates; icand ++) { int comparison = OTGrammar_compareCandidates (me, itab, icand, itab, icand_best); if (comparison == -1) { icand_best = icand; /* The current candidate is the best candidate found so far. */ numberOfBestCandidates = 1; } else if (comparison == 0) { numberOfBestCandidates += 1; /* The current candidate is equally good as the best found before. */ } } return numberOfBestCandidates; } bool OTGrammar_isCandidateGrammatical (OTGrammar me, long itab, long icand) { for (long jcand = 1; jcand <= my tableaus [itab]. numberOfCandidates; jcand ++) { if (jcand != icand && OTGrammar_compareCandidates (me, itab, jcand, itab, icand) < 0) return false; } return true; } bool OTGrammar_isCandidateSinglyGrammatical (OTGrammar me, long itab, long icand) { for (long jcand = 1; jcand <= my tableaus [itab]. numberOfCandidates; jcand ++) { if (jcand != icand && OTGrammar_compareCandidates (me, itab, jcand, itab, icand) <= 0) return false; } return true; } void OTGrammar_getInterpretiveParse (OTGrammar me, const wchar *partialOutput, long *bestTableau, long *bestCandidate) { try { long itab_best = 0, icand_best = 0, numberOfBestCandidates = 0; for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate cand = & tableau -> candidates [icand]; if (wcsstr (cand -> output, partialOutput)) { /* T&S idea of surface->overt mapping */ if (itab_best == 0) { itab_best = itab; /* The first compatible input/output pair found is the first guess for the best candidate. */ icand_best = icand; numberOfBestCandidates = 1; } else { int comparison = OTGrammar_compareCandidates (me, itab, icand, itab_best, icand_best); if (comparison == -1) { itab_best = itab; /* The current input/output pair is the best candidate found so far. */ icand_best = icand; numberOfBestCandidates = 1; } else if (comparison == 0) { numberOfBestCandidates += 1; /* The current input/output pair is equally good as the best found before. */ /* * Give all candidates that are equally good an equal chance to become the winner. */ if (Melder_debug == 41) { itab_best = itab_best; icand_best = icand_best; // keep first } else if (Melder_debug == 42) { itab_best = itab; icand_best = icand; // take last } else if (NUMrandomUniform (0.0, numberOfBestCandidates) < 1.0) { // default: take random itab_best = itab; icand_best = icand; } } } } } } if (itab_best == 0) Melder_throw ("The partial output \"", partialOutput, "\" does not match any candidate for any input form."); if (bestTableau != NULL) *bestTableau = itab_best; if (bestCandidate != NULL) *bestCandidate = icand_best; } catch (MelderError) { Melder_throw ("Interpretive parse not computed."); } } static void OTGrammar_getInterpretiveParse_opt (OTGrammar me, long ipartialOutput, long *bestTableau, long *bestCandidate) { try { long itab_best = 0, icand_best = 0, numberOfBestCandidates = 0; for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate cand = & tableau -> candidates [icand]; Melder_assert (cand -> partialOutputMatches != NULL); if (cand -> partialOutputMatches [ipartialOutput]) { /* T&S idea of surface->overt mapping */ if (itab_best == 0) { itab_best = itab; /* The first compatible input/output pair found is the first guess for the best candidate. */ icand_best = icand; numberOfBestCandidates = 1; } else { int comparison = OTGrammar_compareCandidates (me, itab, icand, itab_best, icand_best); if (comparison == -1) { itab_best = itab; /* The current input/output pair is the best candidate found so far. */ icand_best = icand; numberOfBestCandidates = 1; } else if (comparison == 0) { numberOfBestCandidates += 1; /* The current input/output pair is equally good as the best found before. */ /* * Give all candidates that are equally good an equal chance to become the winner. */ if (Melder_debug == 41) { itab_best = itab_best; icand_best = icand_best; // keep first } else if (Melder_debug == 42) { itab_best = itab; icand_best = icand; // take last } else if (NUMrandomUniform (0.0, numberOfBestCandidates) < 1.0) { // default: take random itab_best = itab; icand_best = icand; } } } } } } Melder_assert (itab_best != 0); if (bestTableau != NULL) *bestTableau = itab_best; if (bestCandidate != NULL) *bestCandidate = icand_best; } catch (MelderError) { Melder_throw ("Interpretive parse not computed."); } } bool OTGrammar_isPartialOutputGrammatical (OTGrammar me, const wchar *partialOutput) { for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { if (wcsstr (tableau -> candidates [icand]. output, partialOutput)) { if (OTGrammar_isCandidateGrammatical (me, itab, icand)) { return true; } } } } return false; } bool OTGrammar_isPartialOutputSinglyGrammatical (OTGrammar me, const wchar *partialOutput) { bool found = false; for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { if (wcsstr (tableau -> candidates [icand]. output, partialOutput)) { if (OTGrammar_isCandidateGrammatical (me, itab, icand)) { found = true; /* * All other grammatical candidates should match. */ for (long jcand = 1; jcand <= tableau -> numberOfCandidates; jcand ++) { if (OTGrammar_compareCandidates (me, itab, jcand, itab, icand) == 0) { if (wcsstr (tableau -> candidates [jcand]. output, partialOutput) == NULL) { return false; // Partial output is multiply optimal. } } } } } } } return found; } static int OTGrammar_crucialCell (OTGrammar me, long itab, long icand, long iwinner, long numberOfOptimalCandidates) { int icons; OTGrammarTableau tableau = & my tableaus [itab]; if (tableau -> numberOfCandidates < 2) return 0; /* If there is only one candidate, all cells can be greyed. */ if (my decisionStrategy != kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) return my numberOfConstraints; /* Nothing grey. */ if (OTGrammar_compareCandidates (me, itab, icand, itab, iwinner) == 0) { /* Candidate equally good as winner? */ if (numberOfOptimalCandidates > 1) { /* All cells are important. */ } else { long jcand, secondBest = 0; for (jcand = 1; jcand <= tableau -> numberOfCandidates; jcand ++) { if (OTGrammar_compareCandidates (me, itab, jcand, itab, iwinner) != 0) { /* A non-optimal candidate? */ if (secondBest == 0) { secondBest = jcand; /* First guess. */ } else if (OTGrammar_compareCandidates (me, itab, jcand, itab, secondBest) < 0) { secondBest = jcand; /* Better guess. */ } } } if (secondBest == 0) return 0; /* If all candidates are equally good, all cells can be greyed. */ return OTGrammar_crucialCell (me, itab, secondBest, iwinner, 1); } } else { int *candidateMarks = tableau -> candidates [icand]. marks; int *winnerMarks = tableau -> candidates [iwinner]. marks; for (icons = 1; icons <= my numberOfConstraints; icons ++) { int numberOfCandidateMarks = candidateMarks [my index [icons]]; int numberOfWinnerMarks = winnerMarks [my index [icons]]; while (my constraints [my index [icons]]. tiedToTheRight) { icons ++; numberOfCandidateMarks += candidateMarks [my index [icons]]; numberOfWinnerMarks += winnerMarks [my index [icons]]; } if (numberOfCandidateMarks > numberOfWinnerMarks) return icons; } } return my numberOfConstraints; /* Nothing grey. */ } static double OTGrammar_constraintWidth (Graphics g, const wchar *name) { wchar text [100], *newLine; wcscpy (text, name); newLine = wcschr (text, '\n'); if (newLine) { double firstWidth, secondWidth; *newLine = '\0'; firstWidth = Graphics_textWidth (g, text); secondWidth = Graphics_textWidth (g, newLine + 1); return firstWidth > secondWidth ? firstWidth : secondWidth; } return Graphics_textWidth (g, text); } void OTGrammar_drawTableau (OTGrammar me, Graphics g, bool vertical, const wchar *input) { try { double x, y, fontSize = Graphics_inqFontSize (g); Graphics_Colour colour = Graphics_inqColour (g); wchar text [200]; const long itab = OTGrammar_getTableau (me, input); _OTGrammar_fillInHarmonies (me, itab); const long winner = OTGrammar_getWinner (me, itab); Graphics_setWindow (g, 0.0, 1.0, 0.0, 1.0); const double margin = Graphics_dxMMtoWC (g, 1.0); const double fingerWidth = Graphics_dxMMtoWC (g, 7.0) * fontSize / 12.0; const double doubleLineDx = Graphics_dxMMtoWC (g, 0.9); const double doubleLineDy = Graphics_dyMMtoWC (g, 0.9); const double rowHeight = Graphics_dyMMtoWC (g, 1.5 * fontSize * 25.4 / 72); const double descent = rowHeight * 0.5; const double worldAspectRatio = Graphics_dyMMtoWC (g, 1.0) / Graphics_dxMMtoWC (g, 1.0); // because Graphics_textWidth measures in the x direction only /* * Compute the height of the header row. */ double headerHeight; if (vertical) { headerHeight = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; double constraintTextWidth = Graphics_textWidth (g, constraint -> name); if (constraintTextWidth > headerHeight) headerHeight = constraintTextWidth; } headerHeight += margin * 2; headerHeight *= worldAspectRatio; } else { headerHeight = rowHeight; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; if (wcschr (constraint -> name, '\n')) { headerHeight *= 1.6; break; } } } /* * Compute longest candidate string. * Also count the number of optimal candidates (if there are more than one, the fingers will be drawn in red). */ double candWidth = Graphics_textWidth (g, input); OTGrammarTableau tableau = & my tableaus [itab]; long numberOfOptimalCandidates = 0; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { double width = Graphics_textWidth (g, tableau -> candidates [icand]. output); if (OTGrammar_compareCandidates (me, itab, icand, itab, winner) == 0) { width += fingerWidth; numberOfOptimalCandidates ++; } if (width > candWidth) candWidth = width; } candWidth += margin * 3; /* * Compute tableau width. */ double tableauWidth = candWidth + doubleLineDx; if (vertical) { tableauWidth += rowHeight * my numberOfConstraints / worldAspectRatio; } else { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; tableauWidth += OTGrammar_constraintWidth (g, constraint -> name); } tableauWidth += margin * 2 * my numberOfConstraints; } /* * Draw box. */ x = doubleLineDx; // left side of tableau y = 1.0 - doubleLineDy; Graphics_rectangle (g, x, x + tableauWidth, y - headerHeight - tableau -> numberOfCandidates * rowHeight - doubleLineDy, y); /* * Draw input. */ y -= headerHeight; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x + 0.5 * candWidth, y + 0.5 * headerHeight, input); Graphics_rectangle (g, x, x + candWidth, y, y + headerHeight); /* * Draw constraint names. */ x += candWidth + doubleLineDx; if (vertical) Graphics_setTextRotation (g, 90.0); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [my index [icons]]; double width = vertical ? rowHeight / worldAspectRatio : OTGrammar_constraintWidth (g, constraint -> name) + margin * 2; if (wcschr (constraint -> name, '\n') && ! vertical) { wchar *newLine; wcscpy (text, constraint -> name); newLine = wcschr (text, '\n'); *newLine = '\0'; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_TOP); Graphics_text (g, x + 0.5 * width, y + headerHeight, text); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (g, x + 0.5 * width, y, newLine + 1); } else if (vertical) { Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_text (g, x + 0.5 * width, y + margin, constraint -> name); } else { Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, x + 0.5 * width, y + 0.5 * headerHeight, constraint -> name); } if (constraint -> tiedToTheLeft) Graphics_setLineType (g, Graphics_DOTTED); Graphics_line (g, x, y, x, y + headerHeight); Graphics_setLineType (g, Graphics_DRAWN); Graphics_line (g, x, y, x + width, y); x += width; } if (vertical) Graphics_setTextRotation (g, 0.0); /* * Draw candidates. */ y -= doubleLineDy; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { long crucialCell = OTGrammar_crucialCell (me, itab, icand, winner, numberOfOptimalCandidates); bool candidateIsOptimal = OTGrammar_compareCandidates (me, itab, icand, itab, winner) == 0; /* * Draw candidate transcription. */ x = doubleLineDx; y -= rowHeight; Graphics_setTextAlignment (g, Graphics_RIGHT, Graphics_HALF); Graphics_text (g, x + candWidth - margin, y + descent, tableau -> candidates [icand]. output); if (candidateIsOptimal) { Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); Graphics_setFontSize (g, (int) (1.5 * fontSize)); if (numberOfOptimalCandidates > 1) Graphics_setColour (g, Graphics_RED); Graphics_text (g, x + margin, y + descent - Graphics_dyMMtoWC (g, 1.0) * fontSize / 12.0, L"\\pf"); Graphics_setColour (g, colour); Graphics_setFontSize (g, (int) fontSize); } Graphics_rectangle (g, x, x + candWidth, y, y + rowHeight); /* * Draw grey cell backgrounds. */ x = candWidth + 2 * doubleLineDx; Graphics_setGrey (g, 0.9); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int index = my index [icons]; OTGrammarConstraint constraint = & my constraints [index]; double width = vertical ? rowHeight / worldAspectRatio : OTGrammar_constraintWidth (g, constraint -> name) + margin * 2; if (icons > crucialCell) Graphics_fillRectangle (g, x, x + width, y, y + rowHeight); x += width; } Graphics_setColour (g, colour); /* * Draw cell marks. */ x = candWidth + 2 * doubleLineDx; Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int index = my index [icons]; OTGrammarConstraint constraint = & my constraints [index]; double width = vertical ? rowHeight / worldAspectRatio : OTGrammar_constraintWidth (g, constraint -> name) + margin * 2; wchar markString [40]; markString [0] = '\0'; if (my decisionStrategy == kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { /* * An exclamation mark can be drawn in this cell only if all of the following conditions are met: * 1. the candidate is not optimal; * 2. the constraint is not tied; * 3. this is the crucial cell, i.e. the cells after it are drawn in grey. */ if (icons == crucialCell && ! candidateIsOptimal && ! constraint -> tiedToTheLeft && ! constraint -> tiedToTheRight) { int winnerMarks = tableau -> candidates [winner]. marks [index]; for (long imark = 1; imark <= winnerMarks + 1; imark ++) wcscat (markString, L"*"); for (long imark = tableau -> candidates [icand]. marks [index]; imark < 0; imark ++) wcscat (markString, L"+"); wcscat (markString, L"!"); for (long imark = winnerMarks + 2; imark <= tableau -> candidates [icand]. marks [index]; imark ++) wcscat (markString, L"*"); } else { if (! candidateIsOptimal && (constraint -> tiedToTheLeft || constraint -> tiedToTheRight) && crucialCell >= 1 && constraint -> disharmony == my constraints [my index [crucialCell]]. disharmony) { Graphics_setColour (g, Graphics_RED); } for (long imark = 1; imark <= tableau -> candidates [icand]. marks [index]; imark ++) wcscat (markString, L"*"); for (long imark = tableau -> candidates [icand]. marks [index]; imark < 0; imark ++) wcscat (markString, L"+"); } } else { for (long imark = 1; imark <= tableau -> candidates [icand]. marks [index]; imark ++) wcscat (markString, L"*"); for (long imark = tableau -> candidates [icand]. marks [index]; imark < 0; imark ++) wcscat (markString, L"+"); } Graphics_text (g, x + 0.5 * width, y + descent, markString); Graphics_setColour (g, colour); if (constraint -> tiedToTheLeft) Graphics_setLineType (g, Graphics_DOTTED); Graphics_line (g, x, y, x, y + rowHeight); Graphics_setLineType (g, Graphics_DRAWN); Graphics_line (g, x, y + rowHeight, x + width, y + rowHeight); x += width; } /* * Draw harmony. */ if (my decisionStrategy != kOTGrammar_decisionStrategy_OPTIMALITY_THEORY) { Graphics_setTextAlignment (g, Graphics_LEFT, Graphics_HALF); double value = tableau -> candidates [icand]. harmony; if (my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY) { //value = value > -1e-300 ? 1000 : value < -1e300 ? -1000 : - log (- value); Graphics_text (g, x, y + descent, Melder_float (Melder_half (value))); } else { Graphics_text (g, x, y + descent, Melder_fixed (value, 3)); } } } /* * Draw box. */ x = doubleLineDx; // left side of tableau y = 1.0 - doubleLineDy; Graphics_rectangle (g, x, x + tableauWidth, y - headerHeight - tableau -> numberOfCandidates * rowHeight - doubleLineDy, y); } catch (MelderError) { Melder_throw (me, ": tableau not drawn."); } } Strings OTGrammar_generateInputs (OTGrammar me, long numberOfTrials) { try { autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, thy numberOfStrings = numberOfTrials); for (long i = 1; i <= numberOfTrials; i ++) { long itab = NUMrandomInteger (1, my numberOfTableaus); thy strings [i] = Melder_wcsdup (my tableaus [itab]. input); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": inputs not generated."); } } Strings OTGrammar_getInputs (OTGrammar me) { try { autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, thy numberOfStrings = my numberOfTableaus); for (long i = 1; i <= my numberOfTableaus; i ++) { thy strings [i] = Melder_wcsdup (my tableaus [i]. input); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": inputs not gotten."); } } void OTGrammar_inputToOutput (OTGrammar me, const wchar *input, wchar *output, double evaluationNoise) { try { OTGrammar_newDisharmonies (me, evaluationNoise); long itab = OTGrammar_getTableau (me, input); long winner = OTGrammar_getWinner (me, itab); if (winner == 0) Melder_throw ("No winner"); wcscpy (output, my tableaus [itab]. candidates [winner]. output); } catch (MelderError) { Melder_throw (me, ": output not computed from input \"", input, "\"."); } } Strings OTGrammar_inputsToOutputs (OTGrammar me, Strings inputs, double evaluationNoise) { try { autoStrings him = Thing_new (Strings); long n = inputs -> numberOfStrings; his numberOfStrings = n; his strings = NUMvector (1, n); for (long i = 1; i <= n; i ++) { wchar output [100]; OTGrammar_inputToOutput (me, inputs -> strings [i], output, evaluationNoise); therror his strings [i] = Melder_wcsdup (output); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": outputs not computed."); } } Strings OTGrammar_inputToOutputs (OTGrammar me, const wchar *input, long n, double evaluationNoise) { try { autoStrings thee = Thing_new (Strings); thy numberOfStrings = n; thy strings = NUMvector (1, n); for (long i = 1; i <= n; i ++) { wchar output [100]; OTGrammar_inputToOutput (me, input, output, evaluationNoise); therror thy strings [i] = Melder_wcsdup (output); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": output not computed."); } } Distributions OTGrammar_to_Distribution (OTGrammar me, long trialsPerInput, double noise) { try { long totalNumberOfOutputs = 0, nout = 0; /* * Count the total number of outputs. */ for (long itab = 1; itab <= my numberOfTableaus; itab ++) totalNumberOfOutputs += my tableaus [itab]. numberOfCandidates; /* * Create the distribution. One row for every output form. */ autoDistributions thee = Distributions_create (totalNumberOfOutputs, 1); /* * Measure every input form. */ autoMelderProgress progress (L"OTGrammar: compute output distribution."); for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; Melder_progress ((itab - 0.5) / my numberOfTableaus, L"Measuring input \"", tableau -> input, L"\""); /* * Set the row labels to the output strings. */ for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { static MelderString buffer = { 0 }; MelderString_empty (& buffer); MelderString_append (& buffer, tableau -> input, L" \\-> ", tableau -> candidates [icand]. output); thy rowLabels [nout + icand] = Melder_wcsdup (buffer.string); } /* * Compute a number of outputs and store the results. */ for (long itrial = 1; itrial <= trialsPerInput; itrial ++) { OTGrammar_newDisharmonies (me, noise); long iwinner = OTGrammar_getWinner (me, itab); thy data [nout + iwinner] [1] += 1; } /* * Update the offset. */ nout += tableau -> numberOfCandidates; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": output distribution not computed."); } } PairDistribution OTGrammar_to_PairDistribution (OTGrammar me, long trialsPerInput, double noise) { try { long totalNumberOfOutputs = 0, nout = 0; /* * Count the total number of outputs. */ for (long itab = 1; itab <= my numberOfTableaus; itab ++) totalNumberOfOutputs += my tableaus [itab]. numberOfCandidates; /* * Create the distribution. One row for every output form. */ autoPairDistribution thee = PairDistribution_create (); /* * Measure every input form. */ autoMelderProgress progress (L"OTGrammar: compute output distribution."); for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; Melder_progress ((itab - 0.5) / my numberOfTableaus, L"Measuring input \"", tableau -> input, L"\""); /* * Copy the input and output strings to the target object. */ for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { PairDistribution_add (thee.peek(), tableau -> input, tableau -> candidates [icand]. output, 0); } /* * Compute a number of outputs and store the results. */ PairProbability *p = (PairProbability *) thy pairs -> item; // may have changed after PairDistribution_add !!! for (long itrial = 1; itrial <= trialsPerInput; itrial ++) { OTGrammar_newDisharmonies (me, noise); long iwinner = OTGrammar_getWinner (me, itab); p [nout + iwinner] -> weight += 1; } /* * Update the offset. */ nout += tableau -> numberOfCandidates; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": output distribution not computed."); } } static bool honoursFixedRankings (OTGrammar me) { for (long i = 1; i <= my numberOfFixedRankings; i ++) { long higher = my fixedRankings [i]. higher, lower = my fixedRankings [i]. lower; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { if (my index [icons] == higher) break; // detected higher before lower: OK if (my index [icons] == lower) return false; } } return true; } Distributions OTGrammar_measureTypology (OTGrammar me) { try { long totalNumberOfOutputs = 0, nout = 0, ncons = my numberOfConstraints, nperm, factorial [1+12]; if (ncons > 12) Melder_throw ("Cannot handle more than 12 constraints."); factorial [0] = 1; for (long icons = 1; icons <= ncons; icons ++) { factorial [icons] = factorial [icons - 1] * icons; } nperm = factorial [ncons]; /* * Count the total number of outputs. */ for (long itab = 1; itab <= my numberOfTableaus; itab ++) totalNumberOfOutputs += my tableaus [itab]. numberOfCandidates; /* * Create the distribution. One row for every output form. */ autoDistributions thee = Distributions_create (totalNumberOfOutputs, 1); /* * Measure every input form. */ autoMelderProgress progress (L"Measuring typology..."); for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; Melder_progress ((itab - 0.5) / my numberOfTableaus, L"Measuring input \"", tableau -> input, L"\""); /* * Set the row labels to the output strings. */ for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { static MelderString buffer = { 0 }; MelderString_empty (& buffer); MelderString_append (& buffer, tableau -> input, L" \\-> ", tableau -> candidates [icand]. output); thy rowLabels [nout + icand] = Melder_wcsdup_f (buffer.string); } /* * Compute a number of outputs and store the results. */ for (long iperm = 0; iperm < nperm; iperm ++) { long permleft = iperm, iwinner; /* Initialize to 12345 before permuting. */ for (long icons = 1; icons <= ncons; icons ++) { my index [icons] = icons; } for (long icons = 1; icons < ncons; icons ++) { long fac = factorial [ncons - icons], shift = permleft / fac, dummy; /* * Swap constraint with the one at a distance 'shift'. */ dummy = my index [icons]; my index [icons] = my index [icons + shift]; my index [icons + shift] = dummy; permleft %= fac; } if (honoursFixedRankings (me)) { iwinner = OTGrammar_getWinner (me, itab); thy data [nout + iwinner] [1] += 1; } } /* * Update the offset. */ nout += tableau -> numberOfCandidates; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": typology not measured."); } } static double learningStep (double mean, double relativeSpreading) { return relativeSpreading == 0.0 ? mean : NUMrandomGauss (mean, relativeSpreading * mean); } static void OTGrammar_honourLocalRankings (OTGrammar me, double plasticity, double relativePlasticityNoise, int *grammarHasChanged) { int improved; do { improved = FALSE; for (long irank = 1; irank <= my numberOfFixedRankings; irank ++) { OTGrammarFixedRanking fixedRanking = & my fixedRankings [irank]; OTGrammarConstraint higher = & my constraints [fixedRanking -> higher], lower = & my constraints [fixedRanking -> lower]; while (higher -> ranking <= lower -> ranking) { lower -> ranking -= learningStep (plasticity, relativePlasticityNoise); if (grammarHasChanged != NULL) *grammarHasChanged = TRUE; improved = TRUE; } } } while (improved); } static void OTGrammar_modifyRankings (OTGrammar me, long itab, long iwinner, long iloser, int updateRule, int honourLocalRankings, double plasticity, double relativePlasticityNoise, int warnIfStalled, int *grammarHasChanged) { try { OTGrammarTableau tableau = & my tableaus [itab]; OTGrammarCandidate winner = & tableau -> candidates [iwinner], loser = & tableau -> candidates [iloser]; double step = learningStep (plasticity, relativePlasticityNoise); bool multiplyStepByNumberOfViolations = my decisionStrategy == kOTGrammar_decisionStrategy_HARMONIC_GRAMMAR || my decisionStrategy == kOTGrammar_decisionStrategy_LINEAR_OT || my decisionStrategy == kOTGrammar_decisionStrategy_MAXIMUM_ENTROPY || my decisionStrategy == kOTGrammar_decisionStrategy_POSITIVE_HG || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG || my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_MAXIMUM_ENTROPY; if (Melder_debug != 0) { /* * Perhaps override the standard update rule. */ if (Melder_debug == 26) multiplyStepByNumberOfViolations = false; // OT-GLA else if (Melder_debug == 27) multiplyStepByNumberOfViolations = true; // HG-GLA } if (updateRule == kOTGrammar_rerankingStrategy_SYMMETRIC_ONE) { long icons = NUMrandomInteger (1, my numberOfConstraints); OTGrammarConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= loserMarks - winnerMarks; constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak); if (grammarHasChanged != NULL) *grammarHasChanged = true; } if (winnerMarks > loserMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak); if (grammarHasChanged != NULL) *grammarHasChanged = true; } } else if (updateRule == kOTGrammar_rerankingStrategy_SYMMETRIC_ALL) { bool changed = false; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= loserMarks - winnerMarks; constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak); changed = true; } if (winnerMarks > loserMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak); changed = true; } } if (changed && my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG) { double sumOfWeights = 0.0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { sumOfWeights += my constraints [icons]. ranking; } double averageWeight = sumOfWeights / my numberOfConstraints; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { my constraints [icons]. ranking -= averageWeight; } } if (grammarHasChanged != NULL) *grammarHasChanged = changed; } else if (updateRule == kOTGrammar_rerankingStrategy_WEIGHTED_UNCANCELLED) { int winningConstraints = 0, losingConstraints = 0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) losingConstraints ++; if (winnerMarks > loserMarks) winningConstraints ++; } if (winningConstraints != 0) for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= loserMarks - winnerMarks; constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak) / losingConstraints; //constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak) * winningConstraints; if (grammarHasChanged != NULL) *grammarHasChanged = true; } if (winnerMarks > loserMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak) / winningConstraints; //constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak) * losingConstraints; if (grammarHasChanged != NULL) *grammarHasChanged = true; } } } else if (updateRule == kOTGrammar_rerankingStrategy_WEIGHTED_ALL) { int winningConstraints = 0, losingConstraints = 0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > 0) losingConstraints ++; if (winnerMarks > 0) winningConstraints ++; } if (winningConstraints != 0) for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > 0) { if (multiplyStepByNumberOfViolations) constraintStep *= loserMarks - winnerMarks; constraint -> ranking -= constraintStep * (1.0 + constraint -> ranking * my leak) / losingConstraints; if (grammarHasChanged != NULL) *grammarHasChanged = true; } if (winnerMarks > 0) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak) / winningConstraints; if (grammarHasChanged != NULL) *grammarHasChanged = true; } } } else if (updateRule == kOTGrammar_rerankingStrategy_EDCD || updateRule == kOTGrammar_rerankingStrategy_EDCD_WITH_VACATION) { /* * Determine the crucial winner mark. */ double pivotRanking; bool equivalent = true; long icons = 1; for (; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [my index [icons]]; // the order is important, therefore indirect int loserMarks = loser -> marks [my index [icons]]; if (loserMarks < winnerMarks) break; if (loserMarks > winnerMarks) equivalent = false; } if (icons > my numberOfConstraints) { // completed the loop? if (warnIfStalled && ! equivalent) Melder_warning ("Correct output is harmonically bounded (by having strict superset violations as compared to the learner's output)! EDCD stalls.\n" "Input: ", tableau -> input, "\nCorrect output: ", loser -> output, "\nLearner's output: ", winner -> output); return; } /* * Determine the stratum into which some constraints will be demoted. */ pivotRanking = my constraints [my index [icons]]. ranking; if (updateRule == kOTGrammar_rerankingStrategy_EDCD_WITH_VACATION) { long numberOfConstraintsToDemote = 0; for (icons = 1; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (loserMarks > winnerMarks) { OTGrammarConstraint constraint = & my constraints [icons]; if (constraint -> ranking >= pivotRanking) { numberOfConstraintsToDemote += 1; } } } if (numberOfConstraintsToDemote > 0) { for (icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; if (constraint -> ranking < pivotRanking) { constraint -> ranking -= numberOfConstraintsToDemote * step * constraint -> plasticity; if (grammarHasChanged != NULL) *grammarHasChanged = true; } } } } /* * Demote all the uniquely violated constraints in the loser * that have rankings not lower than the pivot. */ for (icons = 1; icons <= my numberOfConstraints; icons ++) { long numberOfConstraintsDemoted = 0; int winnerMarks = winner -> marks [my index [icons]]; // for the vacation version, the order is important, therefore indirect int loserMarks = loser -> marks [my index [icons]]; if (loserMarks > winnerMarks) { OTGrammarConstraint constraint = & my constraints [my index [icons]]; double constraintStep = step * constraint -> plasticity; if (constraint -> ranking >= pivotRanking) { numberOfConstraintsDemoted += 1; constraint -> ranking = pivotRanking - numberOfConstraintsDemoted * constraintStep; // this preserves the order of the demotees if (grammarHasChanged != NULL) *grammarHasChanged = true; } } } } else if (updateRule == kOTGrammar_rerankingStrategy_DEMOTION_ONLY) { /* * Determine the crucial loser mark. */ long crucialLoserMark; OTGrammarConstraint offendingConstraint; long icons = 1; for (; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [my index [icons]]; /* Order is important, so indirect. */ int loserMarks = loser -> marks [my index [icons]]; if (my constraints [my index [icons]]. tiedToTheRight) Melder_throw ("Demotion-only learning cannot handle tied constraints."); if (loserMarks < winnerMarks) Melder_throw ("Demotion-only learning step: Loser wins! Should never happen."); if (loserMarks > winnerMarks) break; } if (icons > my numberOfConstraints) // completed the loop? Melder_throw ("Loser equals correct candidate."); crucialLoserMark = icons; /* * Demote the highest uniquely violated constraint in the loser. */ offendingConstraint = & my constraints [my index [crucialLoserMark]]; double constraintStep = step * offendingConstraint -> plasticity; offendingConstraint -> ranking -= constraintStep; if (grammarHasChanged != NULL) *grammarHasChanged = true; } else { Melder_assert (updateRule == kOTGrammar_rerankingStrategy_WEIGHTED_ALL_UP_HIGHEST_DOWN); bool changed = false; long numberOfUp = 0; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (winnerMarks > loserMarks) { numberOfUp ++; } } if (numberOfUp > 0) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; double constraintStep = step * constraint -> plasticity; int winnerMarks = winner -> marks [icons]; int loserMarks = loser -> marks [icons]; if (winnerMarks > loserMarks) { if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; constraint -> ranking += constraintStep * (1.0 - constraint -> ranking * my leak) / numberOfUp; } } long crucialLoserMark, winnerMarks = 0, loserMarks = 0; OTGrammarConstraint offendingConstraint; long icons = 1; for (; icons <= my numberOfConstraints; icons ++) { winnerMarks = winner -> marks [my index [icons]]; // the order is important, therefore indirect loserMarks = loser -> marks [my index [icons]]; if (my constraints [my index [icons]]. tiedToTheRight) Melder_throw ("Demotion-only learning cannot handle tied constraints."); if (loserMarks < winnerMarks) Melder_throw ("Demotion-only learning step: Loser wins! Should never happen."); if (loserMarks > winnerMarks) break; } if (icons > my numberOfConstraints) // completed the loop? Melder_throw ("Loser equals correct candidate."); crucialLoserMark = icons; /* * Demote the highest uniquely violated constraint in the loser. */ offendingConstraint = & my constraints [my index [crucialLoserMark]]; double constraintStep = step * offendingConstraint -> plasticity; if (multiplyStepByNumberOfViolations) constraintStep *= winnerMarks - loserMarks; offendingConstraint -> ranking -= /*numberOfUp **/ constraintStep * (1.0 - offendingConstraint -> ranking * my leak); } if (grammarHasChanged != NULL) *grammarHasChanged = changed; } if (honourLocalRankings && my numberOfFixedRankings) { OTGrammar_honourLocalRankings (me, plasticity, relativePlasticityNoise, grammarHasChanged); } } catch (MelderError) { Melder_throw (me, ": rankings not modified."); } } void OTGrammar_learnOne (OTGrammar me, const wchar *underlyingForm, const wchar *adultOutput, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double plasticity, double relativePlasticityNoise, int newDisharmonies, int warnIfStalled, int *grammarHasChanged) { try { if (newDisharmonies) OTGrammar_newDisharmonies (me, evaluationNoise); if (grammarHasChanged != NULL) *grammarHasChanged = FALSE; /* * Evaluate the input in the learner's hypothesis. */ long itab = OTGrammar_getTableau (me, underlyingForm); OTGrammarTableau tableau = & my tableaus [itab]; /* * Determine the "winner", i.e. the candidate that wins in the learner's grammar * (Tesar & Smolensky call this the "loser"). */ long iwinner = OTGrammar_getWinner (me, itab); OTGrammarCandidate winner = & tableau -> candidates [iwinner]; /* * Error-driven: compare the adult winner (the correct candidate) and the learner's winner. */ if (wcsequ (winner -> output, adultOutput)) return; // as far as we know, the grammar is already correct: don't update rankings /* * Find (perhaps the learner's interpretation of) the adult winner (the "loser") in the learner's own tableau * (Tesar & Smolensky call this the "winner"). */ long iloser = 1; for (; iloser <= tableau -> numberOfCandidates; iloser ++) { OTGrammarCandidate loser = & tableau -> candidates [iloser]; if (wcsequ (loser -> output, adultOutput)) break; } if (iloser > tableau -> numberOfCandidates) Melder_throw ("Cannot generate adult output \"", adultOutput, L"\"."); /* * Now we know that the current hypothesis prefers the (wrong) learner's winner over the (correct) adult output. * The grammar will have to change. */ OTGrammar_modifyRankings (me, itab, iwinner, iloser, updateRule, honourLocalRankings, plasticity, relativePlasticityNoise, warnIfStalled, grammarHasChanged); therror } catch (MelderError) { Melder_throw (me, ": not learned from input \"", underlyingForm, "\" and adult output \"", adultOutput, "\"."); } } void OTGrammar_learn (OTGrammar me, Strings inputs, Strings outputs, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double plasticity, double relativePlasticityNoise, long numberOfChews) { if (! inputs) inputs = outputs; try { long n = inputs -> numberOfStrings; if (outputs -> numberOfStrings != n) Melder_throw ("Numbers of strings in input and output are not equal."); for (long i = 1; i <= n; i ++) { for (long ichew = 1; ichew <= numberOfChews; ichew ++) { OTGrammar_learnOne (me, inputs -> strings [i], outputs -> strings [i], evaluationNoise, updateRule, honourLocalRankings, plasticity, relativePlasticityNoise, TRUE, TRUE, NULL); therror } } } catch (MelderError) { Melder_throw (me, ": not learned from ", inputs, " (inputs) and ", outputs, " (outputs)."); } } void OTGrammar_PairDistribution_learn (OTGrammar me, PairDistribution thee, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double initialPlasticity, long replicationsPerPlasticity, double plasticityDecrement, long numberOfPlasticities, double relativePlasticityNoise, long numberOfChews) { long idatum = 0, numberOfData = numberOfPlasticities * replicationsPerPlasticity; try { double plasticity = initialPlasticity; autoMelderMonitor monitor (L"Learning with full knowledge..."); if (monitor.graphics()) { Graphics_clearWs (monitor.graphics()); } for (long iplasticity = 1; iplasticity <= numberOfPlasticities; iplasticity ++) { for (long ireplication = 1; ireplication <= replicationsPerPlasticity; ireplication ++) { wchar *input, *output; PairDistribution_peekPair (thee, & input, & output); therror ++ idatum; if (monitor.graphics() && idatum % (numberOfData / 400 + 1) == 0) { Graphics_setWindow (monitor.graphics(), 0, numberOfData, 50, 150); for (long icons = 1; icons <= 14 && icons <= my numberOfConstraints; icons ++) { Graphics_setGrey (monitor.graphics(), (double) icons / 14); Graphics_line (monitor.graphics(), idatum, my constraints [icons]. ranking, idatum, my constraints [icons]. ranking+1); } Graphics_flushWs (monitor.graphics()); // because drawing is faster than progress loop } Melder_monitor ((double) idatum / numberOfData, L"Processing input-output pair ", Melder_integer (idatum), L" out of ", Melder_integer (numberOfData), L": ", input, L" -> ", output); therror for (long ichew = 1; ichew <= numberOfChews; ichew ++) { OTGrammar_learnOne (me, input, output, evaluationNoise, updateRule, honourLocalRankings, plasticity, relativePlasticityNoise, TRUE, TRUE, NULL); therror } } plasticity *= plasticityDecrement; } } catch (MelderError) { if (idatum > 1) Melder_error_ ("Only ", idatum - 1, " input-output pairs out of ", numberOfData, " were processed."); Melder_throw (me, ": did not complete learning from ", thee, "."); } } static long PairDistribution_getNumberOfAttestedOutputs (PairDistribution me, const wchar *input, wchar **attestedOutput) { long result = 0; for (long ipair = 1; ipair <= my pairs -> size; ipair ++) { PairProbability pair = (PairProbability) my pairs -> item [ipair]; if (wcsequ (pair -> string1, input) && pair -> weight > 0.0) { if (attestedOutput != NULL) *attestedOutput = pair -> string2; result ++; } } return result; } bool OTGrammar_PairDistribution_findPositiveWeights_e (OTGrammar me, PairDistribution thee, double weightFloor, double marginOfSeparation) { NUMlinprog linprog = NULL; try { bool result = false; if (my decisionStrategy != kOTGrammar_decisionStrategy_HARMONIC_GRAMMAR && my decisionStrategy != kOTGrammar_decisionStrategy_LINEAR_OT && my decisionStrategy != kOTGrammar_decisionStrategy_POSITIVE_HG && my decisionStrategy != kOTGrammar_decisionStrategy_EXPONENTIAL_HG) { Melder_throw ("To find positive weights, the decision strategy has to be HarmonicGrammar, LinearOT, PositiveHG, or ExponentialHG."); } autoNUMvector optimalCandidates (1, my numberOfTableaus); /* * Check that there is exactly one optimal output for each input. */ for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tab = & my tableaus [itab]; wchar *attestedOutput = NULL; long numberOfAttestedOutputs = PairDistribution_getNumberOfAttestedOutputs (thee, tab -> input, & attestedOutput); if (numberOfAttestedOutputs == 0) { Melder_throw ("Input \"", my tableaus [itab]. input, "\" has no attested output."); } else if (numberOfAttestedOutputs > 1) { Melder_throw ("Input \"", my tableaus [itab]. input, "\" has more than one attested output."); } else { Melder_assert (attestedOutput != NULL); for (long icand = 1; icand <= tab -> numberOfCandidates; icand ++) { OTGrammarCandidate cand = & tab -> candidates [icand]; if (wcsequ (attestedOutput, cand -> output)) { optimalCandidates [itab] = icand; } } } Melder_assert (optimalCandidates [itab] != 0); } /* * Create linear programming problem. */ linprog = NUMlinprog_new (false); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { NUMlinprog_addVariable (linprog, weightFloor, NUMundefined, 1.0); } for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tab = & my tableaus [itab]; long ioptimalCandidate = optimalCandidates [itab]; Melder_assert (ioptimalCandidate >= 1); Melder_assert (ioptimalCandidate <= tab -> numberOfCandidates); OTGrammarCandidate optimalCandidate = & tab -> candidates [ioptimalCandidate]; for (long icand = 1; icand <= tab -> numberOfCandidates; icand ++) if (icand != ioptimalCandidate) { OTGrammarCandidate cand = & tab -> candidates [icand]; NUMlinprog_addConstraint (linprog, marginOfSeparation, NUMundefined); therror for (long icons = 1; icons <= my numberOfConstraints; icons ++) { NUMlinprog_addConstraintCoefficient (linprog, cand -> marks [icons] - optimalCandidate -> marks [icons]); } } } NUMlinprog_run (linprog); therror for (long icons = 1; icons <= my numberOfConstraints; icons ++) { double weighting = NUMlinprog_getPrimalValue (linprog, icons); Melder_assert (weighting >= weightFloor); my constraints [icons]. ranking = my constraints [icons]. disharmony = my decisionStrategy == kOTGrammar_decisionStrategy_EXPONENTIAL_HG ? log (weighting) : weighting; } NUMlinprog_delete (linprog); return result; } catch (MelderError) { NUMlinprog_delete (linprog); Melder_throw (me, ": positive weights not found."); } } void OTGrammar_reset (OTGrammar me, double ranking) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; constraint -> disharmony = constraint -> ranking = ranking; } OTGrammar_sort (me); } void OTGrammar_resetToRandomTotalRanking (OTGrammar me, double maximumRanking, double rankingDistance) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; constraint -> ranking = 0.0; } OTGrammar_newDisharmonies (me, 1.0); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [my index [icons]]; constraint -> disharmony = constraint -> ranking = maximumRanking - (icons - 1) * rankingDistance; } OTGrammar_sort (me); } void OTGrammar_setRanking (OTGrammar me, long constraint, double ranking, double disharmony) { try { if (constraint < 1 || constraint > my numberOfConstraints) Melder_throw ("There is no constraint with number ", constraint, "."); my constraints [constraint]. ranking = ranking; my constraints [constraint]. disharmony = disharmony; OTGrammar_sort (me); } catch (MelderError) { Melder_throw (me, ": ranking of constraint ", constraint, " not set."); } } void OTGrammar_setConstraintPlasticity (OTGrammar me, long constraint, double plasticity) { try { if (constraint < 1 || constraint > my numberOfConstraints) Melder_throw ("There is no constraint with number ", constraint, "."); my constraints [constraint]. plasticity = plasticity; } catch (MelderError) { Melder_throw (me, ": plasticity of constraint ", constraint, " not set."); } } long theSaveNumberOfConstraints, *theSaveIndex; double *theSaveRankings, *theSaveDisharmonies; int *theSaveTiedToTheLeft, *theSaveTiedToTheRight; static void OTGrammar_save (OTGrammar me) { if (my numberOfConstraints != theSaveNumberOfConstraints) { NUMvector_free (theSaveIndex, 1); theSaveIndex = NULL; NUMvector_free (theSaveRankings, 1); theSaveRankings = NULL; NUMvector_free (theSaveDisharmonies, 1); theSaveDisharmonies = NULL; NUMvector_free (theSaveTiedToTheLeft, 1); theSaveTiedToTheLeft = NULL; NUMvector_free (theSaveTiedToTheRight, 1); theSaveTiedToTheRight = NULL; theSaveNumberOfConstraints = my numberOfConstraints; } if (theSaveIndex == NULL) theSaveIndex = NUMvector (1, my numberOfConstraints); if (theSaveRankings == NULL) theSaveRankings = NUMvector (1, my numberOfConstraints); if (theSaveDisharmonies == NULL) theSaveDisharmonies = NUMvector (1, my numberOfConstraints); if (theSaveTiedToTheLeft == NULL) theSaveTiedToTheLeft = NUMvector (1, my numberOfConstraints); if (theSaveTiedToTheRight == NULL) theSaveTiedToTheRight = NUMvector (1, my numberOfConstraints); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { theSaveIndex [icons] = my index [icons]; theSaveRankings [icons] = my constraints [icons]. ranking; theSaveDisharmonies [icons] = my constraints [icons]. disharmony; theSaveTiedToTheLeft [icons] = my constraints [icons]. tiedToTheLeft; theSaveTiedToTheRight [icons] = my constraints [icons]. tiedToTheRight; } } static void OTGrammar_restore (OTGrammar me) { for (long icons = 1; icons <= my numberOfConstraints; icons ++) { my index [icons] = theSaveIndex [icons]; my constraints [icons]. ranking = theSaveRankings [icons]; my constraints [icons]. disharmony = theSaveDisharmonies [icons]; my constraints [icons]. tiedToTheLeft = theSaveTiedToTheLeft [icons]; my constraints [icons]. tiedToTheRight = theSaveTiedToTheRight [icons]; } } void OTGrammar_learnOneFromPartialOutput (OTGrammar me, const wchar *partialAdultOutput, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double plasticity, double relativePlasticityNoise, long numberOfChews, int warnIfStalled) { try { OTGrammar_newDisharmonies (me, evaluationNoise); if (numberOfChews > 1 && updateRule == kOTGrammar_rerankingStrategy_EDCD) { OTGrammar_save (me); } long ichew = 1; for (; ichew <= numberOfChews; ichew ++) { long assumedAdultInputTableau, assumedAdultCandidate; OTGrammar_getInterpretiveParse (me, partialAdultOutput, & assumedAdultInputTableau, & assumedAdultCandidate); int grammarHasChanged; OTGrammar_learnOne (me, my tableaus [assumedAdultInputTableau]. input, my tableaus [assumedAdultInputTableau]. candidates [assumedAdultCandidate]. output, evaluationNoise, updateRule, honourLocalRankings, plasticity, relativePlasticityNoise, FALSE, warnIfStalled, & grammarHasChanged); therror if (! grammarHasChanged) return; } if (numberOfChews > 1 && updateRule == kOTGrammar_rerankingStrategy_EDCD && ichew > numberOfChews) { /* * Is the partial output form grammatical by now? */ long assumedAdultInputTableau, assumedAdultCandidate; OTGrammar_getInterpretiveParse (me, partialAdultOutput, & assumedAdultInputTableau, & assumedAdultCandidate); OTGrammarCandidate learnerCandidate = & my tableaus [assumedAdultInputTableau]. candidates [OTGrammar_getWinner (me, assumedAdultInputTableau)]; if (! wcsequ (learnerCandidate -> output, my tableaus [assumedAdultInputTableau]. candidates [assumedAdultCandidate]. output)) { /* Still ungrammatical? */ /* * Backtrack as in Tesar & Smolensky 2000:69. */ OTGrammar_restore (me); } } } catch (MelderError) { Melder_throw (me, ": not learned from partial adult output \"", partialAdultOutput, "\"."); } } static void OTGrammar_learnOneFromPartialOutput_opt (OTGrammar me, long ipartialAdultOutput, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double plasticity, double relativePlasticityNoise, long numberOfChews, int warnIfStalled) { try { OTGrammar_newDisharmonies (me, evaluationNoise); if (numberOfChews > 1 && updateRule == kOTGrammar_rerankingStrategy_EDCD) { OTGrammar_save (me); } long ichew = 1; for (; ichew <= numberOfChews; ichew ++) { long assumedAdultInputTableau, assumedAdultCandidate; OTGrammar_getInterpretiveParse_opt (me, ipartialAdultOutput, & assumedAdultInputTableau, & assumedAdultCandidate); int grammarHasChanged; OTGrammar_learnOne (me, my tableaus [assumedAdultInputTableau]. input, my tableaus [assumedAdultInputTableau]. candidates [assumedAdultCandidate]. output, evaluationNoise, updateRule, honourLocalRankings, plasticity, relativePlasticityNoise, FALSE, warnIfStalled, & grammarHasChanged); therror if (! grammarHasChanged) return; } if (numberOfChews > 1 && updateRule == kOTGrammar_rerankingStrategy_EDCD && ichew > numberOfChews) { /* * Is the partial output form grammatical by now? */ long assumedAdultInputTableau, assumedAdultCandidate; OTGrammar_getInterpretiveParse_opt (me, ipartialAdultOutput, & assumedAdultInputTableau, & assumedAdultCandidate); OTGrammarCandidate learnerCandidate = & my tableaus [assumedAdultInputTableau]. candidates [OTGrammar_getWinner (me, assumedAdultInputTableau)]; if (! wcsequ (learnerCandidate -> output, my tableaus [assumedAdultInputTableau]. candidates [assumedAdultCandidate]. output)) { /* Still ungrammatical? */ /* * Backtrack as in Tesar & Smolensky 2000:69. */ OTGrammar_restore (me); } } } catch (MelderError) { Melder_throw (me, ": not learned from partial adult output ", ipartialAdultOutput, "."); } } static OTHistory OTGrammar_createHistory (OTGrammar me, long storeHistoryEvery, long numberOfData) { try { long numberOfSamplingPoints = numberOfData / storeHistoryEvery, icons; // e.g. 0, 20, 40, ... autoOTHistory thee = Thing_new (OTHistory); TableOfReal_init (thee.peek(), 2 + numberOfSamplingPoints * 2, 1 + my numberOfConstraints); therror TableOfReal_setColumnLabel (thee.peek(), 1, L"Datum"); for (icons = 1; icons <= my numberOfConstraints; icons ++) { TableOfReal_setColumnLabel (thee.peek(), icons + 1, my constraints [icons]. name); } TableOfReal_setRowLabel (thee.peek(), 1, L"Initial state"); thy data [1] [1] = 0; for (icons = 1; icons <= my numberOfConstraints; icons ++) { thy data [1] [icons + 1] = my constraints [icons]. ranking; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": history not created."); } } static void OTGrammar_updateHistory (OTGrammar me, OTHistory thee, long storeHistoryEvery, long idatum, const wchar *input) { try { if (idatum % storeHistoryEvery == 0) { long irow = 2 * idatum / storeHistoryEvery; TableOfReal_setRowLabel (thee, irow, input); thy data [irow] [1] = idatum; thy data [irow + 1] [1] = idatum; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { thy data [irow] [icons + 1] = my constraints [icons]. disharmony; thy data [irow + 1] [icons + 1] = my constraints [icons]. ranking; } } } catch (MelderError) { Melder_throw (me, ": history not updated."); } } static void OTGrammar_finalizeHistory (OTGrammar me, OTHistory thee, long idatum) { try { TableOfReal_setRowLabel (thee, thy numberOfRows, L"Final state"); thy data [thy numberOfRows] [1] = idatum; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { thy data [thy numberOfRows] [icons + 1] = my constraints [icons]. ranking; } } catch (MelderError) { Melder_throw (me, ": history not finalized."); } } void OTGrammar_learnFromPartialOutputs (OTGrammar me, Strings partialOutputs, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double plasticity, double relativePlasticityNoise, long numberOfChews, long storeHistoryEvery, OTHistory *history_out) { try { autoOTHistory history; if (storeHistoryEvery) { history.reset (OTGrammar_createHistory (me, storeHistoryEvery, partialOutputs -> numberOfStrings)); } try { for (long idatum = 1; idatum <= partialOutputs -> numberOfStrings; idatum ++) { try { OTGrammar_learnOneFromPartialOutput (me, partialOutputs -> strings [idatum], evaluationNoise, updateRule, honourLocalRankings, plasticity, relativePlasticityNoise, numberOfChews, FALSE); therror } catch (MelderError) { if (history.peek()) { OTGrammar_updateHistory (me, history.peek(), storeHistoryEvery, idatum, partialOutputs -> strings [idatum]); therror // so that we can inspect } throw; } if (history.peek()) { OTGrammar_updateHistory (me, history.peek(), storeHistoryEvery, idatum, partialOutputs -> strings [idatum]); therror } } if (history.peek()) { OTGrammar_finalizeHistory (me, history.peek(), partialOutputs -> numberOfStrings); } *history_out = history.transfer(); } catch (MelderError) { *history_out = history.transfer(); // so that we can inspect throw; } } catch (MelderError) { Melder_throw (me, ": not learned from partial outputs ", partialOutputs, "."); } } static void OTGrammar_opt_deleteOutputMatching (OTGrammar me) { for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tab = & my tableaus [itab]; for (long icand = 1; icand <= tab -> numberOfCandidates; icand ++) { OTGrammarCandidate cand = & tab -> candidates [icand]; cand -> numberOfPotentialPartialOutputsMatching = 0; NUMvector_free (cand -> partialOutputMatches, 1); cand -> partialOutputMatches = NULL; } } } static void OTGrammar_Distributions_opt_createOutputMatching (OTGrammar me, Distributions thee, long columnNumber) { try { if (columnNumber > thy numberOfColumns) Melder_throw ("No column ", columnNumber, " in Distributions."); if (thy numberOfRows < 1) Melder_throw ("No candidates in Distributions."); for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tab = & my tableaus [itab]; for (long icand = 1; icand <= tab -> numberOfCandidates; icand ++) { OTGrammarCandidate cand = & tab -> candidates [icand]; cand -> numberOfPotentialPartialOutputsMatching = thy numberOfRows; cand -> partialOutputMatches = NUMvector (1, thy numberOfRows); } } for (long ipartialOutput = 1; ipartialOutput <= thy numberOfRows; ipartialOutput ++) { if (thy data [ipartialOutput] [columnNumber] > 0.0) { wchar *partialOutput = thy rowLabels [ipartialOutput]; bool foundPartialOutput = false; for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tab = & my tableaus [itab]; for (long icand = 1; icand <= tab -> numberOfCandidates; icand ++) { OTGrammarCandidate cand = & tab -> candidates [icand]; if (wcsstr (cand -> output, partialOutput)) { foundPartialOutput = true; cand -> partialOutputMatches [ipartialOutput] = true; } } } if (! foundPartialOutput) Melder_throw ("The partial output \"", partialOutput, "\" does not match any candidate for any input form."); } } } catch (MelderError) { OTGrammar_opt_deleteOutputMatching (me); throw; } } void OTGrammar_Distributions_learnFromPartialOutputs (OTGrammar me, Distributions thee, long columnNumber, double evaluationNoise, enum kOTGrammar_rerankingStrategy updateRule, int honourLocalRankings, double initialPlasticity, long replicationsPerPlasticity, double plasticityDecrement, long numberOfPlasticities, double relativePlasticityNoise, long numberOfChews, long storeHistoryEvery, OTHistory *history_out) { long idatum = 0; const long numberOfData = numberOfPlasticities * replicationsPerPlasticity; try { autoOTHistory history; OTGrammar_Distributions_opt_createOutputMatching (me, thee, columnNumber); autoMelderMonitor monitor (L"Learning with limited knowledge..."); if (monitor.graphics()) { Graphics_clearWs (monitor.graphics()); } if (storeHistoryEvery) { history.reset (OTGrammar_createHistory (me, storeHistoryEvery, numberOfData)); } try { double plasticity = initialPlasticity; for (long iplasticity = 1; iplasticity <= numberOfPlasticities; iplasticity ++) { for (long ireplication = 1; ireplication <= replicationsPerPlasticity; ireplication ++) { long ipartialOutput; Distributions_peek_opt (thee, columnNumber, & ipartialOutput); therror ++ idatum; if (monitor.graphics() && idatum % (numberOfData / 400 + 1) == 0) { Graphics_setWindow (monitor.graphics(), 0, numberOfData, 50, 150); for (long icons = 1; icons <= 14 && icons <= my numberOfConstraints; icons ++) { Graphics_setGrey (monitor.graphics(), (double) icons / 14); Graphics_line (monitor.graphics(), idatum, my constraints [icons]. ranking, idatum, my constraints [icons]. ranking+1); } Graphics_flushWs (monitor.graphics()); /* Because drawing is faster than progress loop. */ } Melder_monitor ((double) idatum / numberOfData, L"Processing partial output ", Melder_integer (idatum), L" out of ", Melder_integer (numberOfData), L": ", thy rowLabels [ipartialOutput]); therror try { OTGrammar_learnOneFromPartialOutput_opt (me, ipartialOutput, evaluationNoise, updateRule, honourLocalRankings, plasticity, relativePlasticityNoise, numberOfChews, FALSE); therror // no warning if stalled: RIP form is allowed to be harmonically bounded } catch (MelderError) { if (history.peek()) { OTGrammar_updateHistory (me, history.peek(), storeHistoryEvery, idatum, thy rowLabels [ipartialOutput]); } throw; } if (history.peek()) { OTGrammar_updateHistory (me, history.peek(), storeHistoryEvery, idatum, thy rowLabels [ipartialOutput]); } } plasticity *= plasticityDecrement; } if (history.peek()) { OTGrammar_finalizeHistory (me, history.peek(), numberOfData); } OTGrammar_opt_deleteOutputMatching (me); if (history_out) *history_out = history.transfer(); } catch (MelderError) { OTGrammar_opt_deleteOutputMatching (me); if (history_out) *history_out = history.transfer(); // so that we can inspect throw; } } catch (MelderError) { if (idatum > 1) Melder_error_ ("Only ", idatum - 1, " input-output pairs out of ", numberOfData, " were processed."); Melder_throw (me, " & ", thee, ": not learned from partial outputs."); } } double OTGrammar_PairDistribution_getFractionCorrect (OTGrammar me, PairDistribution thee, double evaluationNoise, long numberOfInputs) { try { long numberOfCorrect = 0; for (long ireplication = 1; ireplication <= numberOfInputs; ireplication ++) { wchar *input, *adultOutput; PairDistribution_peekPair (thee, & input, & adultOutput); therror OTGrammar_newDisharmonies (me, evaluationNoise); long inputTableau = OTGrammar_getTableau (me, input); OTGrammarCandidate learnerCandidate = & my tableaus [inputTableau]. candidates [OTGrammar_getWinner (me, inputTableau)]; if (wcsequ (learnerCandidate -> output, adultOutput)) numberOfCorrect ++; } return (double) numberOfCorrect / numberOfInputs; } catch (MelderError) { Melder_throw (me, " & ", thee, ": fraction correct not computed."); } } long OTGrammar_PairDistribution_getMinimumNumberCorrect (OTGrammar me, PairDistribution thee, double evaluationNoise, long numberOfReplications) { try { long minimumNumberCorrect = numberOfReplications; for (long ipair = 1; ipair <= thy pairs -> size; ipair ++) { PairProbability prob = (PairProbability) thy pairs -> item [ipair]; if (prob -> weight > 0.0) { long numberOfCorrect = 0; wchar *input = prob -> string1, *adultOutput = prob -> string2; long inputTableau = OTGrammar_getTableau (me, input); for (long ireplication = 1; ireplication <= numberOfReplications; ireplication ++) { OTGrammar_newDisharmonies (me, evaluationNoise); OTGrammarCandidate learnerCandidate = & my tableaus [inputTableau]. candidates [OTGrammar_getWinner (me, inputTableau)]; if (wcsequ (learnerCandidate -> output, adultOutput)) numberOfCorrect ++; } if (numberOfCorrect < minimumNumberCorrect) minimumNumberCorrect = numberOfCorrect; } } return minimumNumberCorrect; } catch (MelderError) { Melder_throw (me, " & ", thee, ": minimum number correct not computed."); } } double OTGrammar_Distributions_getFractionCorrect (OTGrammar me, Distributions thee, long columnNumber, double evaluationNoise, long numberOfInputs) { try { long numberOfCorrect = 0; OTGrammar_Distributions_opt_createOutputMatching (me, thee, columnNumber); for (long ireplication = 1; ireplication <= numberOfInputs; ireplication ++) { long ipartialOutput; Distributions_peek_opt (thee, columnNumber, & ipartialOutput); therror OTGrammar_newDisharmonies (me, evaluationNoise); long assumedAdultInputTableau, assumedAdultCandidate; OTGrammar_getInterpretiveParse_opt (me, ipartialOutput, & assumedAdultInputTableau, & assumedAdultCandidate); therror OTGrammarCandidate learnerCandidate = & my tableaus [assumedAdultInputTableau]. candidates [OTGrammar_getWinner (me, assumedAdultInputTableau)]; if (wcsequ (learnerCandidate -> output, my tableaus [assumedAdultInputTableau]. candidates [assumedAdultCandidate]. output)) numberOfCorrect ++; } OTGrammar_opt_deleteOutputMatching (me); return (double) numberOfCorrect / numberOfInputs; } catch (MelderError) { Melder_throw (me, " & ", thee, ": fraction correct not computed."); } } void OTGrammar_removeConstraint (OTGrammar me, const wchar *constraintName) { try { long removed = 0; if (my numberOfConstraints <= 1) Melder_throw ("Cannot remove last remaining constraint."); /* * Look for the constraint to be removed. */ for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [icons]; if (wcsequ (constraint -> name, constraintName)) { removed = icons; break; } } if (removed == 0) Melder_throw ("No such constraint."); /* * Remove the constraint while reusing the memory space. */ my numberOfConstraints -= 1; /* * Shift constraints. */ Melder_free (my constraints [removed]. name); for (long icons = removed; icons <= my numberOfConstraints; icons ++) { my constraints [icons] = my constraints [icons + 1]; } /* * Remove or shift fixed rankings. */ for (long ifixed = my numberOfFixedRankings; ifixed > 0; ifixed --) { OTGrammarFixedRanking fixed = & my fixedRankings [ifixed]; if (fixed -> higher == removed || fixed -> lower == removed) { /* * Remove fixed ranking. */ my numberOfFixedRankings -= 1; if (my numberOfFixedRankings == 0) { NUMvector_free (my fixedRankings, 1); my fixedRankings = NULL; } for (long jfixed = ifixed; jfixed <= my numberOfFixedRankings; jfixed ++) { my fixedRankings [jfixed] = my fixedRankings [jfixed + 1]; } } else { /* * Shift fixed ranking. */ if (fixed -> higher > removed) fixed -> higher -= 1; if (fixed -> lower > removed) fixed -> lower -= 1; } } /* * Shift tableau rows. */ for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate candidate = & tableau -> candidates [icand]; candidate -> numberOfConstraints -= 1; for (long icons = removed; icons <= my numberOfConstraints; icons ++) { candidate -> marks [icons] = candidate -> marks [icons + 1]; } } } /* * Rebuild index. */ for (long icons = 1; icons <= my numberOfConstraints; icons ++) my index [icons] = icons; OTGrammar_sort (me); } catch (MelderError) { Melder_throw (me, ": constraint \"", constraintName, "\" not removed."); } } static void OTGrammarTableau_removeCandidate_unstripped (OTGrammarTableau me, long candidateNumber) { Melder_assert (candidateNumber >= 1); if (candidateNumber > my numberOfCandidates) Melder_fatal ("icand %ld, ncand %ld", candidateNumber, my numberOfCandidates); /* * Free up memory associated with this candidate. */ Melder_free (my candidates [candidateNumber]. output); NUMvector_free (my candidates [candidateNumber]. marks, 1); // dangle /* * Remove. */ my numberOfCandidates -= 1; /* * Shift. */ for (long jcand = candidateNumber; jcand <= my numberOfCandidates; jcand ++) { OTGrammarCandidate candj = & my candidates [jcand]; OTGrammarCandidate candj1 = & my candidates [jcand + 1]; candj -> output = candj1 -> output; candj -> marks = candj1 -> marks; // undangle } } static bool OTGrammarTableau_isHarmonicallyBounded (OTGrammarTableau me, long icand, long jcand) { OTGrammarCandidate candi = & my candidates [icand], candj = & my candidates [jcand]; bool equal = true; if (icand == jcand) return false; for (long icons = 1; icons <= candi -> numberOfConstraints; icons ++) { if (candi -> marks [icons] < candj -> marks [icons]) return false; if (candi -> marks [icons] > candj -> marks [icons]) equal = false; } return ! equal; } static bool OTGrammarTableau_candidateIsPossibleWinner (OTGrammar me, long itab, long icand) { OTGrammar_save (me); OTGrammar_reset (me, 100.0); for (;;) { int grammarHasChanged; double previousStratum = 101.0; OTGrammar_learnOne (me, my tableaus [itab]. input, my tableaus [itab]. candidates [icand]. output, 1e-3, kOTGrammar_rerankingStrategy_EDCD, FALSE, 1.0, 0.0, TRUE, TRUE, & grammarHasChanged); if (! grammarHasChanged) { OTGrammar_restore (me); return true; } OTGrammar_newDisharmonies (me, 0.0); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { double stratum = my constraints [my index [icons]]. ranking; #if 0 if (stratum < 50.0 - my numberOfConstraints) { OTGrammar_restore (me); return false; // we detected a tumble } #else if (stratum < previousStratum) { if (stratum < previousStratum - 1.0) { OTGrammar_restore (me); return false; // we detected a vacated stratum } previousStratum = stratum; } #endif } } return false; /* Cannot occur. */ } void OTGrammar_removeHarmonicallyBoundedCandidates (OTGrammar me, int singly) { try { /* * First, the candidates that are harmonically bounded by one or more single other candidates have to be removed; * otherwise, EDCD will stall. */ for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tab = & my tableaus [itab]; for (long icand = tab -> numberOfCandidates; icand >= 1; icand --) { for (long jcand = 1; jcand <= tab -> numberOfCandidates; jcand ++) { if (OTGrammarTableau_isHarmonicallyBounded (tab, icand, jcand)) { OTGrammarTableau_removeCandidate_unstripped (tab, icand); break; } } } tab -> candidates = (OTGrammarCandidate) realloc (& tab -> candidates [1], sizeof (struct structOTGrammarCandidate) * tab -> numberOfCandidates) - 1; } if (! singly) { for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tab = & my tableaus [itab]; for (long icand = tab -> numberOfCandidates; icand >= 1; icand --) { if (! OTGrammarTableau_candidateIsPossibleWinner (me, itab, icand)) { OTGrammarTableau_removeCandidate_unstripped (tab, icand); } } tab -> candidates = (OTGrammarCandidate) realloc (& tab -> candidates [1], sizeof (struct structOTGrammarCandidate) * tab -> numberOfCandidates) - 1; } } } catch (MelderError) { Melder_throw (me, ": not all harmonically bounded candidates were removed."); } } Thing_define (OTGrammar_List4, Data) { // new data: public: long hi1, lo1, hi2, lo2; }; Thing_implement (OTGrammar_List4, Data, 0); void OTGrammar_PairDistribution_listObligatoryRankings (OTGrammar me, PairDistribution thee) { /* * Save. */ OTGrammarFixedRanking savedFixedRankings = my fixedRankings; // dangle... my fixedRankings = NULL; // ...undangle long savedNumberOfFixedRankings = my numberOfFixedRankings; OTGrammar_save (me); try { long ifixedRanking, icons, jcons, kcons, lcons, ipair = 0, npair = my numberOfConstraints * (my numberOfConstraints - 1); long ilist, jlist, itrial, iform; int improved; double evaluationNoise = 1e-9; /* * Add room for two more fixed rankings. */ my fixedRankings = NUMvector (1, my numberOfFixedRankings + 2); for (ifixedRanking = 1; ifixedRanking <= my numberOfFixedRankings; ifixedRanking ++) { my fixedRankings [ifixedRanking]. higher = savedFixedRankings [ifixedRanking]. higher; my fixedRankings [ifixedRanking]. lower = savedFixedRankings [ifixedRanking]. lower; } /* * Test whether there are rankings at all for these output data. */ OTGrammar_reset (me, 100.0); for (itrial = 1; itrial <= 40; itrial ++) { int grammarHasChangedDuringCycle = FALSE; OTGrammar_honourLocalRankings (me, 1.0, 0.0, & grammarHasChangedDuringCycle); OTGrammar_newDisharmonies (me, evaluationNoise); for (iform = 1; iform <= thy pairs -> size; iform ++) { PairProbability prob = (PairProbability) thy pairs -> item [iform]; if (prob -> weight > 0.0) { int grammarHasChanged; OTGrammar_learnOne (me, prob -> string1, prob -> string2, evaluationNoise, kOTGrammar_rerankingStrategy_EDCD, TRUE /* honour fixed rankings; very important */, 1.0, 0.0, FALSE, TRUE, & grammarHasChanged); therror if (grammarHasChanged) { OTGrammar_newDisharmonies (me, evaluationNoise); } grammarHasChangedDuringCycle |= grammarHasChanged; } } if (! grammarHasChangedDuringCycle) break; } if (itrial > 40) { MelderInfo_writeLine1 (L"There are no total rankings that generate these input-output pairs."); throw MelderError (); } /* * Test learnability of every possible ranked pair. */ my numberOfFixedRankings ++; autoNUMmatrix obligatory (1, my numberOfConstraints, 1, my numberOfConstraints); MelderInfo_open (); autoMelderProgress progress (L"Finding obligatory rankings."); for (icons = 1; icons <= my numberOfConstraints; icons ++) { for (jcons = 1; jcons <= my numberOfConstraints; jcons ++) if (icons != jcons) { my fixedRankings [my numberOfFixedRankings]. higher = icons; my fixedRankings [my numberOfFixedRankings]. lower = jcons; OTGrammar_reset (me, 100.0); Melder_progress ((double) ipair / npair, Melder_integer (ipair + 1), L"/", Melder_integer (npair), L": Trying ranking ", my constraints [icons]. name, L" >> ", my constraints [jcons]. name); ipair ++; for (itrial = 1; itrial <= 40; itrial ++) { int grammarHasChangedDuringCycle = FALSE; OTGrammar_honourLocalRankings (me, 1.0, 0.0, & grammarHasChangedDuringCycle); OTGrammar_newDisharmonies (me, evaluationNoise); for (iform = 1; iform <= thy pairs -> size; iform ++) { PairProbability prob = (PairProbability) thy pairs -> item [iform]; if (prob -> weight > 0.0) { int grammarHasChanged; OTGrammar_learnOne (me, prob -> string1, prob -> string2, evaluationNoise, kOTGrammar_rerankingStrategy_EDCD, TRUE /* honour fixed rankings; very important */, 1.0, 0.0, FALSE, TRUE, & grammarHasChanged); therror if (grammarHasChanged) { OTGrammar_newDisharmonies (me, evaluationNoise); } grammarHasChangedDuringCycle |= grammarHasChanged; } } if (! grammarHasChangedDuringCycle) break; } if (itrial > 40) { obligatory [jcons] [icons] = TRUE; MelderInfo_writeLine3 (my constraints [jcons]. name, L" >> ", my constraints [icons]. name); MelderInfo_close (); } } } my numberOfFixedRankings ++; Melder_progress (0.0, L""); npair = npair * npair; autoOrdered list = Ordered_create (); for (icons = 1; icons <= my numberOfConstraints; icons ++) { for (jcons = 1; jcons <= my numberOfConstraints; jcons ++) if (icons != jcons && ! obligatory [jcons] [icons]) { my fixedRankings [my numberOfFixedRankings - 1]. higher = icons; my fixedRankings [my numberOfFixedRankings - 1]. lower = jcons; for (kcons = icons; kcons <= my numberOfConstraints; kcons ++) { for (lcons = 1; lcons <= my numberOfConstraints; lcons ++) if (kcons != lcons && ! obligatory [lcons] [kcons]) { if (icons == kcons && jcons >= lcons) continue; if (icons == lcons && jcons == kcons) continue; if (jcons == kcons && obligatory [lcons] [icons]) continue; if (icons == lcons && obligatory [jcons] [kcons]) continue; if (obligatory [lcons] [icons] && obligatory [jcons] [kcons]) continue; my fixedRankings [my numberOfFixedRankings]. higher = kcons; my fixedRankings [my numberOfFixedRankings]. lower = lcons; OTGrammar_reset (me, 100.0); Melder_progress ((double) ipair / npair, Melder_integer (ipair + 1), L"/", Melder_integer (npair)); ipair ++; for (itrial = 1; itrial <= 40; itrial ++) { int grammarHasChangedDuringCycle = FALSE; OTGrammar_honourLocalRankings (me, 1.0, 0.0, & grammarHasChangedDuringCycle); OTGrammar_newDisharmonies (me, evaluationNoise); for (iform = 1; iform <= thy pairs -> size; iform ++) { PairProbability prob = (PairProbability) thy pairs -> item [iform]; if (prob -> weight > 0.0) { int grammarHasChanged; OTGrammar_learnOne (me, prob -> string1, prob -> string2, evaluationNoise, kOTGrammar_rerankingStrategy_EDCD, TRUE /* honour fixed rankings; very important */, 1.0, 0.0, FALSE, TRUE, & grammarHasChanged); therror if (grammarHasChanged) { OTGrammar_newDisharmonies (me, evaluationNoise); } grammarHasChangedDuringCycle |= grammarHasChanged; } } if (! grammarHasChangedDuringCycle) break; } if (itrial > 40) { autoOTGrammar_List4 listElement = Thing_new (OTGrammar_List4); listElement -> hi1 = jcons; listElement -> lo1 = icons; listElement -> hi2 = lcons; listElement -> lo2 = kcons; Collection_addItem (list.peek(), listElement.transfer()); } } } } } Melder_progress (1.0, L""); /* * Improve list. */ improved = TRUE; while (improved) { improved = FALSE; for (ilist = 1; ilist <= list -> size; ilist ++) { for (jlist = 1; jlist <= list -> size; jlist ++) if (ilist != jlist) { OTGrammar_List4 elA = (OTGrammar_List4) list -> item [ilist], elB = (OTGrammar_List4) list -> item [jlist]; long ahi1 = elA -> hi1, alo1 = elA -> lo1, ahi2 = elA -> hi2, alo2 = elA -> lo2; long bhi1 = elB -> hi1, blo1 = elB -> lo1, bhi2 = elB -> hi2, blo2 = elB -> lo2; improved |= (ahi1 == bhi1 || obligatory [bhi1] [ahi1]) && (ahi2 == bhi2 || obligatory [bhi2] [ahi2]) && (alo1 == blo1 || obligatory [alo1] [blo1]) && (alo2 == blo2 || obligatory [alo2] [blo2]); improved |= (ahi1 == bhi2 || obligatory [bhi2] [ahi1]) && (ahi2 == bhi1 || obligatory [bhi1] [ahi2]) && (alo1 == blo2 || obligatory [alo1] [blo2]) && (alo2 == blo1 || obligatory [alo2] [blo1]); if (improved) { Collection_removeItem (list.peek(), jlist); break; } } if (improved) break; } } improved = TRUE; while (improved) { improved = FALSE; for (ilist = 1; ilist <= list -> size; ilist ++) { for (jlist = 1; jlist <= list -> size; jlist ++) if (ilist != jlist) { OTGrammar_List4 elA = (OTGrammar_List4) list -> item [ilist], elB = (OTGrammar_List4) list -> item [jlist]; long ahi1 = elA -> hi1, alo1 = elA -> lo1, ahi2 = elA -> hi2, alo2 = elA -> lo2; long bhi1 = elB -> hi1, blo1 = elB -> lo1, bhi2 = elB -> hi2, blo2 = elB -> lo2; improved |= ahi1 == bhi1 && alo1 == blo1 && ahi2 == bhi2 && blo2 == bhi1 && alo2 == alo1; improved |= ahi1 == bhi2 && alo1 == blo2 && ahi2 == bhi1 && blo1 == bhi2 && alo2 == alo1; improved |= ahi2 == bhi1 && alo2 == blo1 && ahi1 == bhi2 && blo2 == bhi1 && alo1 == alo2; improved |= ahi2 == bhi2 && alo2 == blo2 && ahi1 == bhi1 && blo1 == bhi2 && alo1 == alo2; if (improved) { Collection_removeItem (list.peek(), jlist); break; } } if (improved) break; } } for (ilist = 1; ilist <= list -> size; ilist ++) { OTGrammar_List4 el = (OTGrammar_List4) list -> item [ilist]; MelderInfo_write4 (my constraints [el -> hi1]. name, L" >> ", my constraints [el -> lo1]. name, L" OR "); MelderInfo_writeLine3 (my constraints [el -> hi2]. name, L" >> ", my constraints [el -> lo2]. name); MelderInfo_close (); } MelderInfo_close (); /* * Remove room. */ NUMvector_free (my fixedRankings, 1); // dangle /* * Restore. */ my numberOfFixedRankings = savedNumberOfFixedRankings; my fixedRankings = savedFixedRankings; // undangle OTGrammar_restore (me); } catch (MelderError) { MelderInfo_close (); /* * Remove room. */ NUMvector_free (my fixedRankings, 1); // dangle /* * Restore. */ my numberOfFixedRankings = savedNumberOfFixedRankings; my fixedRankings = savedFixedRankings; // undangle OTGrammar_restore (me); Melder_throw (me, ": obligatory rankings not listed."); } } void OTGrammar_Distributions_listObligatoryRankings (OTGrammar me, Distributions thee, long columnNumber) { /* * Save. */ OTGrammarFixedRanking savedFixedRankings = my fixedRankings; my fixedRankings = NULL; OTGrammar_save (me); try { long ifixedRanking, icons, jcons, kcons, ipair = 0, npair = my numberOfConstraints * (my numberOfConstraints - 1); /* * Add room for one more fixed ranking. */ my numberOfFixedRankings ++; my fixedRankings = NUMvector (1, my numberOfFixedRankings); for (ifixedRanking = 1; ifixedRanking < my numberOfFixedRankings; ifixedRanking ++) { my fixedRankings [ifixedRanking]. higher = savedFixedRankings [ifixedRanking]. higher; my fixedRankings [ifixedRanking]. lower = savedFixedRankings [ifixedRanking]. lower; } /* * Test learnability of every possible ranked pair. */ MelderInfo_open (); autoMelderProgress progress (L"Finding obligatory rankings."); for (icons = 1; icons <= my numberOfConstraints; icons ++) { for (jcons = 1; jcons <= my numberOfConstraints; jcons ++) if (icons != jcons) { my fixedRankings [my numberOfFixedRankings]. higher = icons; my fixedRankings [my numberOfFixedRankings]. lower = jcons; OTGrammar_reset (me, 100.0); Melder_progress ((double) ipair / npair, Melder_integer (ipair + 1), L"/", Melder_integer (npair), L": Trying ranking ", my constraints [icons]. name, L" >> ", my constraints [jcons]. name); ipair ++; Melder_progressOff (); OTGrammar_Distributions_learnFromPartialOutputs (me, thee, columnNumber, 1e-9, kOTGrammar_rerankingStrategy_EDCD, TRUE /* honour fixed rankings; very important */, 1.0, 1000, 0.0, 1, 0.0, 1, 0, NULL); therror Melder_progressOn (); for (kcons = 1; kcons <= my numberOfConstraints; kcons ++) { if (my constraints [kcons]. ranking < 0.0) { MelderInfo_writeLine3 (my constraints [jcons]. name, L" >> ", my constraints [icons]. name); break; } } } } MelderInfo_close (); /* * Remove room. */ NUMvector_free (my fixedRankings, 1); // dangle /* * Restore. */ my numberOfFixedRankings --; my fixedRankings = savedFixedRankings; // undangle OTGrammar_restore (me); } catch (MelderError) { MelderInfo_close (); /* * Remove room. */ NUMvector_free (my fixedRankings, 1); // dangle /* * Restore. */ my numberOfFixedRankings --; my fixedRankings = savedFixedRankings; // undangle OTGrammar_restore (me); Melder_throw (me, ": obligatory rankings not listed."); } } static void printConstraintNames (OTGrammar me, MelderString *buffer) { wchar text [200]; bool secondLine = false; for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [my index [icons]]; if (wcschr (constraint -> name, '\n')) { wchar *newLine; wcscpy (text, constraint -> name); newLine = wcschr (text, '\n'); *newLine = '\0'; MelderString_append (buffer, L"\t", text); secondLine = true; } else { MelderString_append (buffer, L"\t", constraint -> name); } } MelderString_appendCharacter (buffer, '\n'); if (secondLine) { MelderString_appendCharacter (buffer, '\t'); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [my index [icons]]; wchar *newLine = wcschr (constraint -> name, '\n'); MelderString_append (buffer, L"\t", newLine ? newLine + 1 : L""); } MelderString_appendCharacter (buffer, '\n'); } } void OTGrammar_writeToHeaderlessSpreadsheetFile (OTGrammar me, MelderFile file) { try { autoMelderString buffer; MelderString_append (& buffer, L"CONSTRAINTS\t"); printConstraintNames (me, & buffer); MelderString_append (& buffer, L"rankings\t"); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [my index [icons]]; MelderString_append (& buffer, L"\t", Melder_double (constraint -> ranking)); } MelderString_append (& buffer, L"\ndisharmonies\t"); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { OTGrammarConstraint constraint = & my constraints [my index [icons]]; MelderString_append (& buffer, L"\t", Melder_double (constraint -> disharmony)); } MelderString_appendCharacter (& buffer, '\n'); for (long itab = 1; itab <= my numberOfTableaus; itab ++) { OTGrammarTableau tableau = & my tableaus [itab]; long winner = OTGrammar_getWinner (me, itab), numberOfOptimalCandidates = 0; for (long icons = 1; icons <= my numberOfConstraints + 1; icons ++) { MelderString_appendCharacter (& buffer, '\t'); } MelderString_append (& buffer, L"\nINPUT\t", tableau -> input); printConstraintNames (me, & buffer); for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { if (OTGrammar_compareCandidates (me, itab, icand, itab, winner) == 0) { numberOfOptimalCandidates ++; } } for (long icand = 1; icand <= tableau -> numberOfCandidates; icand ++) { OTGrammarCandidate candidate = & tableau -> candidates [icand]; bool candidateIsOptimal = OTGrammar_compareCandidates (me, itab, icand, itab, winner) == 0; long crucialCell = OTGrammar_crucialCell (me, itab, icand, winner, numberOfOptimalCandidates); MelderString_append (& buffer, candidateIsOptimal == false ? L"loser" : numberOfOptimalCandidates > 1 ? L"co-winner" : L"winner", L"\t", candidate -> output); for (long icons = 1; icons <= my numberOfConstraints; icons ++) { int index = my index [icons]; OTGrammarConstraint constraint = & my constraints [index]; wchar markString [40]; markString [0] = '\0'; /* * An exclamation mark can be drawn in this cell only if all of the following conditions are met: * 1. the candidate is not optimal; * 2. the constraint is not tied; * 3. this is the crucial cell, i.e. the cells after it are drawn in grey. */ if (icons == crucialCell && ! candidateIsOptimal && ! constraint -> tiedToTheLeft && ! constraint -> tiedToTheRight) { int winnerMarks = tableau -> candidates [winner]. marks [index]; for (long imark = 1; imark <= winnerMarks + 1; imark ++) wcscat (markString, L"*"); wcscat (markString, L"!"); for (long imark = winnerMarks + 2; imark <= candidate -> marks [index]; imark ++) wcscat (markString, L"*"); } else { if (! candidateIsOptimal && (constraint -> tiedToTheLeft || constraint -> tiedToTheRight) && crucialCell >= 1 && constraint -> disharmony == my constraints [my index [crucialCell]]. disharmony) { wcscat (markString, L"="); } for (long imark = 1; imark <= candidate -> marks [index]; imark ++) wcscat (markString, L"*"); } MelderString_append (& buffer, L"\t", markString); } MelderString_appendCharacter (& buffer, '\n'); } } MelderFile_writeText (file, buffer.string); therror } catch (MelderError) { Melder_throw (me, ": not saved to tab-separated file ", file, "."); } } /* End of file OTGrammar.cpp */ sources_5316/sys/0000755000176700017670000000000011757244435012555 5ustar paulpaulsources_5316/sys/melder_debug.cpp0000644000176700017670000000542211576441257015702 0ustar paulpaul/* melder_debug.cpp * * Copyright (C) 2000-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2011/06/16 */ #include "melder.h" int Melder_debug = 0; /* If Melder_debug is set to the following values in Praat, the behaviour of that program changes in the following way: 1: Windows: use C-clock instead of multimedia-clock in melder_audio.c. 2: Windows: always reset waveOut, even when played to end, in melder_audio.c. 3: Windows: reset waveOut if unprepareHeader fails, and retry, in melder_audio.c. STAY: 20010214 4: Windows: fewer callbacks during sound play, in melder_audio.c. STAY: 20010214 6: Windows: info on metafile properties in Picture.c. 8: Windows: don't reset waveIn, in SoundRecorder.c. 9: flush Error in FunctionEditor_Sound_draw 10: geometric pens 11: clicked item in option menu in Ui.c. 12: no forced update event in XmUpdateDisplay on Mac 14: switches off the progress window in melder.c 15: don't use TrueType IPA fonts, but always bitmaps instead 16: Linux: open /dev/dsp without O_NDELAY 17: debugging on in Formula.c 18: no endian assumptions in abcio.c 19: show path name in UiOutfile_do 20: trace PortAudio 21: Mac: list supported document formats when printing 22: UTF-8 tests in logo 23: recognize special chunks in WAV files 24: measure buttons in drawing area 25: read crooked Manipulation files (January 2008) 26: force OT-GLA 27: force HG-GLA 28: don't use GSL in NUMfisherQ 29: use GSL in NUMinvFisherQ 30: pitch path finder: use octave jump cost across voiceless parts 31: Pitch analysis: formant pulling on 32: show info on file names in ExperimentMFC 33: trace the Pitch path finder 34: trace memory allocation and deallocation 35: debugging on for QuickTime movie file opening 36: debugging on for images 37: debug autoThing 38: debug autoNUMvector 39: debug autostring 40: debug Thing_new 41: OTGrammar_getWinner: always first choice rather than random choice 42: OTGrammar_getWinner: always last choice rather than random choice 43: trace class table initialization 1264: Mac: Sound_recordFixedTime uses microphone "FW Solo (1264)" (negative values are for David) */ /* End of file melder_debug.cpp */ sources_5316/sys/praat_menuCommands.cpp0000644000176700017670000004337011643516014017072 0ustar paulpaul/* praat_menuCommands.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "praatP.h" #include "praat_script.h" #define praat_MAXNUM_FIXED_COMMANDS 1000 static long theNumberOfCommands = 0; static struct structPraat_Command *theCommands; void praat_menuCommands_init (void) { theCommands = Melder_calloc_f (struct structPraat_Command, praat_MAXNUM_FIXED_COMMANDS + 1); } static int compareMenuCommands (const void *void_me, const void *void_thee) { praat_Command me = (praat_Command) void_me, thee = (praat_Command) void_thee; int compare; if (my window) { if (! thy window) return 1; compare = wcscmp (my window, thy window); if (compare) return compare; } else if (thy window) return -1; if (my menu) { if (! thy menu) return 1; compare = wcscmp (my menu, thy menu); if (compare) return compare; } else if (thy menu) return -1; if (my sortingTail < thy sortingTail) return -1; return 1; } void praat_sortMenuCommands (void) { for (long i = 1; i <= theNumberOfCommands; i ++) theCommands [i]. sortingTail = i; qsort (& theCommands [1], theNumberOfCommands, sizeof (struct structPraat_Command), compareMenuCommands); } static long lookUpMatchingMenuCommand (const wchar *window, const wchar *menu, const wchar *title) { /* * A menu command is fully specified by its environment (window + menu) and its title. */ for (long i = 1; i <= theNumberOfCommands; i ++) { const wchar *tryWindow = theCommands [i]. window; const wchar *tryMenu = theCommands [i]. menu; const wchar *tryTitle = theCommands [i]. title; if ((window == tryWindow || (window && tryWindow && wcsequ (window, tryWindow))) && (menu == tryMenu || (menu && tryMenu && wcsequ (menu, tryMenu))) && (title == tryTitle || (title && tryTitle && wcsequ (title, tryTitle)))) return i; } return 0; // not found } static void do_menu (I, unsigned long modified) { void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *) = (void (*) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)) void_me; Melder_assert (callback != NULL); for (long i = 1; i <= theNumberOfCommands; i ++) { praat_Command me = & theCommands [i]; if (my callback == callback) { if (my title != NULL && ! wcsstr (my title, L"...")) { UiHistory_write (L"\n"); UiHistory_write (my title); } try { callback (NULL, NULL, NULL, my title, modified, NULL); therror } catch (MelderError) { Melder_error_ ("Command \"", my title, "\" not executed."); Melder_flushError (NULL); } praat_updateSelection (); return; } if (my callback == DO_RunTheScriptFromAnyAddedMenuCommand && my script == (void *) void_me) { if (my title != NULL && ! wcsstr (my title, L"...")) { UiHistory_write (L"\nexecute "); UiHistory_write (my script); } else { UiHistory_write (L"\nexecute \""); UiHistory_write (my script); UiHistory_write (L"\""); } try { DO_RunTheScriptFromAnyAddedMenuCommand (NULL, my script, NULL, NULL, false, NULL); therror } catch (MelderError) { Melder_error_ ("Command \"", my title, "\" not executed."); Melder_flushError (NULL); } praat_updateSelection (); return; } } } static void gui_button_cb_menu (I, GuiButtonEvent event) { do_menu (void_me, event -> shiftKeyPressed | event -> commandKeyPressed | event -> optionKeyPressed | event -> extraControlKeyPressed); } static void gui_cb_menu (GUI_ARGS) { /* * Convert a Motif callback into a Ui callback, and catch modifier keys and special mouse buttons. * Call that callback! * Catch the error queue for menu commands without dots (...). */ (void) w; #if defined (macintosh) EventRecord *event = (EventRecord *) call; enum { cmdKey = 256, shiftKey = 512, optionKey = 2048, controlKey = 4096 }; int modified = event -> what == mouseDown && (event -> modifiers & (cmdKey | shiftKey | optionKey | controlKey)) != 0; #elif defined (_WIN32) int modified = FALSE; #else #if gtk // TODO: We kunnen bij GDK events geregistreren om key en button press af te vangen, maar dan // wordt dit geen gewoon 'activate' signaal meer. int modified = 0; // TODO: Dit implementeert het gedrag van Motif, en impliceert dat een toggled Call alleen een // 'naar positief' is en niet de terug toggle 'naar negatief'. if (G_OBJECT_TYPE(w) == GTK_TYPE_RADIO_MENU_ITEM && !gtk_check_menu_item_get_active(GTK_CHECK_MENU_ITEM(w))) { //g_debug("Gotcha!"); return; } #elif motif XButtonPressedEvent *event = (XButtonPressedEvent *) ((XmDrawingAreaCallbackStruct *) call) -> event; int modified = event -> type == ButtonPress && ((event -> state & (ShiftMask | ControlMask | Mod1Mask)) != 0 || event -> button == Button2 || event -> button == Button3); #endif #endif do_menu (void_me, modified); } static GuiObject windowMenuToWidget (const wchar *window, const wchar *menu) { return wcsequ (window, L"Picture") ? praat_picture_resolveMenu (menu) : wcsequ (window, L"Objects") ? praat_objects_resolveMenu (menu) : NULL; } GuiObject praat_addMenuCommand (const wchar *window, const wchar *menu, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)) { long position; int depth = flags, unhidable = FALSE, hidden = FALSE, key = 0; unsigned long motifFlags = 0; if (flags > 7) { depth = ((flags & praat_DEPTH_7) >> 16); unhidable = (flags & praat_UNHIDABLE) != 0; hidden = (flags & praat_HIDDEN) != 0 && ! unhidable; key = flags & 0x000000FF; motifFlags = key ? flags & (0x006000FF | GuiMenu_BUTTON_STATE_MASK) : flags & GuiMenu_BUTTON_STATE_MASK; } if (callback && ! title) { Melder_error_ ("praat_addMenuCommand: command with callback has no title. Window \"", window, "\", menu \"", menu, "\"."); Melder_flushError (NULL); return NULL; } /* Determine the position of the new command. */ if (after) { /* Search for existing command with same selection. */ long found = lookUpMatchingMenuCommand (window, menu, after); if (found) { position = found + 1; /* After 'after'. */ } else { Melder_error_ ("praat_addMenuCommand: the command \"", title, "\" cannot be put after \"", after, "\",\n" "in the menu \"", menu, "\" in the window \"", window, "\"\n" "because the latter command does not exist."); Melder_flushError (NULL); return NULL; } } else { position = theNumberOfCommands + 1; /* At end. */ } /* Increment the command area. */ if (theNumberOfCommands >= praat_MAXNUM_FIXED_COMMANDS) { Melder_flushError ("praat_addMenuCommand: too many menu commands."); return NULL; } theNumberOfCommands += 1; /* Make room for insertion. */ for (long i = theNumberOfCommands; i > position; i --) theCommands [i] = theCommands [i - 1]; memset (& theCommands [position], 0, sizeof (struct structPraat_Command)); /* Insert new command. */ theCommands [position]. window = Melder_wcsdup_f (window); theCommands [position]. menu = Melder_wcsdup_f (menu); theCommands [position]. title = Melder_wcsdup_f (title); theCommands [position]. depth = depth; theCommands [position]. callback = callback; /* NULL for a separator or cascade button. */ theCommands [position]. executable = callback != NULL; theCommands [position]. script = NULL; theCommands [position]. hidden = hidden; theCommands [position]. unhidable = unhidable; if (! theCurrentPraatApplication -> batch) { GuiObject parent = NULL; /* WHERE TO PUT IT? * Determine parent menu widget. * This is not going to fail: * if 'depth' is inappropriate, the alleged subitem will be put in the top menu. */ if (depth == 0) { parent = windowMenuToWidget (window, menu); /* Not a subitem: in the top menu. */ } else { for (long i = position - 1; i > 0; i --) { if (theCommands [i]. depth == depth - 1) { if (theCommands [i]. callback == NULL && theCommands [i]. title != NULL && theCommands [i]. title [0] != '-') /* Cascade button? */ #if gtk parent = gtk_menu_item_get_submenu (GTK_MENU_ITEM (theCommands [i]. button)); #elif motif XtVaGetValues (theCommands [i]. button, XmNsubMenuId, & parent, NULL); /* The relevant menu title. */ #endif break; } } if (! parent) parent = windowMenuToWidget (window, menu); /* Fallback: a subitem without a menu title. */ } if (! parent) return NULL; /* WHAT TO PUT THERE? */ if (title == NULL || title [0] == '-') { theCommands [position]. button = GuiMenu_addSeparator (parent); } else if (callback == NULL) { (void) GuiMenuBar_addMenu2 (parent, title, 0, & theCommands [position]. button); /* Cascade button with submenu. */ } else { theCommands [position]. button = GuiMenu_addItem (parent, title, motifFlags, gui_cb_menu, (void *) callback); } if (hidden) GuiObject_hide (theCommands [position]. button); } return theCommands [position]. button; } void praat_addMenuCommandScript (const wchar *window, const wchar *menu, const wchar *title, const wchar *after, int depth, const wchar *script) { try { Melder_assert (window && menu && title && after && script); if (wcslen (script) && ! wcslen (title)) Melder_throw ("Command with script has no title. Window \"", window, "\", menu \"", menu, "\"."); /* * Determine the position of the new command. */ long position; if (wcslen (after)) { /* Search for existing command with same selection. */ long found = lookUpMatchingMenuCommand (window, menu, after); if (found) { position = found + 1; /* After 'after'. */ } else { /*Melder_throw ("The menu command \"", title, "\" cannot be put after \"", after, "\",\n" "in the menu \"", menu, "\" in the window \"", window, "\"\n" "because the latter command does not exist.", title, after, menu, window);*/ position = theNumberOfCommands + 1; // default: at end } } else { position = theNumberOfCommands + 1; /* At end. */ } /* * Increment the command area. */ if (theNumberOfCommands >= praat_MAXNUM_FIXED_COMMANDS) Melder_throw ("Too many menu commands (maximum ", praat_MAXNUM_FIXED_COMMANDS, ")."); theNumberOfCommands += 1; /* * Make room for insertion. */ for (long i = theNumberOfCommands; i > position; i --) theCommands [i] = theCommands [i - 1]; memset (& theCommands [position], 0, sizeof (struct structPraat_Command)); /* * Insert new command. */ theCommands [position]. window = Melder_wcsdup_f (window); theCommands [position]. menu = Melder_wcsdup_f (menu); theCommands [position]. title = wcslen (title) ? Melder_wcsdup_f (title) : NULL; /* Allow old-fashioned untitled separators. */ theCommands [position]. depth = depth; theCommands [position]. callback = wcslen (script) ? DO_RunTheScriptFromAnyAddedMenuCommand : NULL; /* NULL for a separator or cascade button. */ theCommands [position]. executable = wcslen (script) != 0; if (wcslen (script) == 0) { theCommands [position]. script = Melder_wcsdup_f (L""); /* Empty string, which will be needed to signal origin. */ } else { structMelderFile file = { 0 }; Melder_relativePathToFile (script, & file); theCommands [position]. script = Melder_wcsdup_f (Melder_fileToPath (& file)); } theCommands [position]. after = wcslen (after) ? Melder_wcsdup_f (after) : NULL; if (praatP.phase >= praat_READING_BUTTONS) { static long uniqueID = 0; theCommands [position]. uniqueID = ++ uniqueID; } if (! theCurrentPraatApplication -> batch) { GuiObject parent = NULL; /* WHERE TO PUT IT? * Determine parent menu widget. * This is not going to fail: * if 'depth' is inappropriate, the alleged subitem will be put in the top menu. */ if (depth == 0) { parent = windowMenuToWidget (window, menu); /* Not a subitem: in the top menu. */ } else { for (long i = position - 1; i > 0; i --) { if (theCommands [i]. depth == depth - 1) { if (theCommands [i]. callback == NULL && theCommands [i]. title != NULL && theCommands [i]. title [0] != '-') /* Cascade button? */ #if gtk parent = gtk_menu_item_get_submenu (GTK_MENU_ITEM (theCommands [i]. button)); #elif motif XtVaGetValues (theCommands [i]. button, XmNsubMenuId, & parent, NULL); /* The relevant menu title. */ #endif break; } } if (! parent) parent = windowMenuToWidget (window, menu); /* Fallback: a subitem without a menu title. */ } if (parent) { /* WHAT TO PUT THERE? */ if (title [0] == '\0' || title [0] == '-') { theCommands [position]. button = GuiMenu_addSeparator (parent); } else if (script [0] == '\0') { (void) GuiMenuBar_addMenu2 (parent, title, 0, & theCommands [position]. button); } else { theCommands [position]. button = GuiMenu_addItem (parent, title, 0, gui_cb_menu, (void *) theCommands [position]. script); /* Not just "script"!! */ } } } if (praatP.phase >= praat_HANDLING_EVENTS) praat_sortMenuCommands (); } catch (MelderError) { Melder_throw ("Script menu command not added."); } } void praat_hideMenuCommand (const wchar *window, const wchar *menu, const wchar *title) { if (theCurrentPraatApplication -> batch || ! window || ! menu || ! title) return; long found = lookUpMatchingMenuCommand (window, menu, title); if (! found) return; praat_Command command = & theCommands [found]; if (! command -> hidden && ! command -> unhidable) { command -> hidden = TRUE; if (praatP.phase >= praat_READING_BUTTONS) command -> toggled = ! command -> toggled; if (command -> button) GuiObject_hide (command -> button); } } void praat_showMenuCommand (const wchar *window, const wchar *menu, const wchar *title) { if (theCurrentPraatApplication -> batch || ! window || ! menu || ! title) return; long found = lookUpMatchingMenuCommand (window, menu, title); if (! found) return; praat_Command command = & theCommands [found]; if (command -> hidden) { command -> hidden = FALSE; if (praatP.phase >= praat_READING_BUTTONS) command -> toggled = ! command -> toggled; if (command -> button) GuiObject_show (command -> button); } } void praat_saveMenuCommands (FILE *f) { long maxID = 0; for (long i = 1; i <= theNumberOfCommands; i ++) if (theCommands [i]. uniqueID > maxID) maxID = theCommands [i]. uniqueID; for (long id = 1; id <= maxID; id ++) /* Sorted. */ for (long i = 1; i <= theNumberOfCommands; i ++) { praat_Command me = & theCommands [i]; if (my uniqueID == id && ! my hidden && my window && my menu && my title) { fwprintf (f, L"Add menu command... \"%ls\" \"%ls\" \"%ls\" \"%ls\" %d %ls\n", my window, my menu, my title, my after ? my after : L"", my depth, my script ? my script : L""); break; } } for (long i = 1; i <= theNumberOfCommands; i ++) { praat_Command me = & theCommands [i]; if (my toggled && my window && my menu && my title && ! my uniqueID && ! my script) fwprintf (f, L"%ls menu command... \"%ls\" \"%ls\" %ls\n", my hidden ? L"Hide" : L"Show", my window, my menu, my title); } } /***** FIXED BUTTONS *****/ void praat_addFixedButtonCommand (GuiObject parent, const wchar *title, void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *), int x, int y) { praat_Command me = & theCommands [++ theNumberOfCommands]; my window = Melder_wcsdup_f (L"Objects"); my title = title; my callback = callback; my unhidable = TRUE; if (theCurrentPraatApplication -> batch) { my button = NULL; } else { GuiObject button = my button = GuiButton_create (parent, x, x + 82, Gui_AUTOMATIC, -y, title, gui_button_cb_menu, (void *) callback, 0); // BUG: shouldn't convert a function pointer to a void pointer GuiObject_setSensitive (button, false); GuiObject_show (button); } my executable = False; } void praat_sensitivizeFixedButtonCommand (const wchar *title, int sensitive) { long i = 1; for (; i <= theNumberOfCommands; i ++) if (wcsequ (theCommands [i]. title, title)) break; // search theCommands [i]. executable = sensitive; if (! theCurrentPraatApplication -> batch && ! Melder_backgrounding) GuiObject_setSensitive (theCommands [i]. button, sensitive); } int praat_doMenuCommand (const wchar *command, const wchar *arguments, Interpreter interpreter) { long i = 1; while (i <= theNumberOfCommands && (! theCommands [i]. executable || ! wcsequ (theCommands [i]. title, command) || (! wcsequ (theCommands [i]. window, L"Objects") && ! wcsequ (theCommands [i]. window, L"Picture")))) i ++; if (i > theNumberOfCommands) return 0; theCommands [i]. callback (NULL, arguments, interpreter, command, false, NULL); therror return 1; } long praat_getNumberOfMenuCommands (void) { return theNumberOfCommands; } praat_Command praat_getMenuCommand (long i) { return i < 1 || i > theNumberOfCommands ? NULL : & theCommands [i]; } void praat_addCommandsToEditor (Editor me) { const wchar *windowName = my classInfo -> className; for (long i = 1; i <= theNumberOfCommands; i ++) if (wcsequ (theCommands [i]. window, windowName)) { if (! Editor_addCommandScript (me, theCommands [i]. menu, theCommands [i]. title, 0, theCommands [i]. script)) Melder_flushError ("To fix this, go to Praat->Preferences->Buttons->Editors, " "and remove the script from this menu.\n" "You may want to install the script in a different menu."); } } /* End of file praat_menuCommands.cpp */ sources_5316/sys/Formula.h0000644000176700017670000000276011611106371014321 0ustar paulpaul#ifndef _Formula_h_ #define _Formula_h_ /* Formula.h * * Copyright (C) 1990-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Thing.h" #define kFormula_EXPRESSION_TYPE_NUMERIC 0 #define kFormula_EXPRESSION_TYPE_STRING 1 #define kFormula_EXPRESSION_TYPE_NUMERIC_ARRAY 2 #define kFormula_EXPRESSION_TYPE_STRING_ARRAY 3 #define kFormula_EXPRESSION_TYPE_UNKNOWN 4 struct Formula_NumericArray { long numberOfRows, numberOfColumns; double **data; }; struct Formula_Result { int expressionType; union { double numericResult; wchar *stringResult; struct Formula_NumericArray numericArrayResult; } result; }; void Formula_compile (Any interpreter, Any data, const wchar *expression, int expressionType, int optimize); void Formula_run (long row, long col, struct Formula_Result *result); /* End of file Formula.h */ #endif sources_5316/sys/melder_textencoding.cpp0000644000176700017670000005716411604622440017304 0ustar paulpaul/* melder_textencoding.cpp * * Copyright (C) 2007-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/06/02 utf8 <-> wcs * pb 2007/06/14 separated from melder_strings.c and melder_alloc.c * pb 2007/06/16 text encoding preferences * pb 2007/08/12 prefs in wchar_t * pb 2007/09/04 Melder_malloc rather than malloc in Melder_wcsToAscii (had caused an error in counting memory leaks) * pb 2007/10/06 Melder_peekWcsToCfstring * pb 2007/12/09 made MelderFile_writeCharacter compatible with the ISO Latin-1 preference * pb 2007/12/09 made MelderFile_readText ignore null bytes * pb 2008/11/05 split off from melder_encodings.c * pb 2010/03/08 support for Unicode values above 0xFFFF * pb 2011/04/05 C++ * pb 2011/07/04 C++ */ #include "melder.h" #include "Preferences.h" #include "UnicodeData.h" #include "abcio.h" #if defined (macintosh) #include "macport_on.h" #include #include "macport_off.h" #endif static struct { enum kMelder_textInputEncoding inputEncoding; enum kMelder_textOutputEncoding outputEncoding; } preferences; void Melder_setInputEncoding (enum kMelder_textInputEncoding encoding) { preferences. inputEncoding = encoding; } int Melder_getInputEncoding (void) { return preferences. inputEncoding; } void Melder_setOutputEncoding (enum kMelder_textOutputEncoding encoding) { preferences. outputEncoding = encoding; } int Melder_getOutputEncoding (void) { return preferences. outputEncoding; } void Melder_textEncoding_prefs (void) { Preferences_addEnum (L"TextEncoding.inputEncoding", & preferences. inputEncoding, kMelder_textInputEncoding, DEFAULT); Preferences_addEnum (L"TextEncoding.outputEncoding", & preferences. outputEncoding, kMelder_textOutputEncoding, DEFAULT); } bool Melder_isValidAscii (const wchar_t *text) { for (; *text != '\0'; text ++) { if (sizeof (wchar_t) == 2) { unsigned short kar = *text; if (kar > 127) return false; } else { if (*text > 127) return false; } } return true; } bool Melder_isEncodable (const wchar_t *text, int outputEncoding) { switch (outputEncoding) { case kMelder_textOutputEncoding_ASCII: { for (; *text != '\0'; text ++) { if (sizeof (wchar_t) == 2) { unsigned short kar = *text; if (kar > 127) return false; } else { if (*text > 127) return false; } } return true; } break; case kMelder_textOutputEncoding_ISO_LATIN1: { for (; *text != '\0'; text ++) { if (sizeof (wchar_t) == 2) { unsigned short kar = *text; if (kar > 255) return false; } else { if (*text > 255) return false; } } return true; } break; case kMelder_textOutputEncoding_UTF8: case kMelder_textOutputEncoding_UTF16: case kMelder_textOutputEncoding_ASCII_THEN_UTF16: case kMelder_textOutputEncoding_ISO_LATIN1_THEN_UTF16: { return true; } } return false; } bool Melder_strIsValidUtf8 (const char *string) { for (const unsigned char *p = (const unsigned char *) & string [0]; *p != '\0'; p ++) { unsigned long kar = *p; if (kar <= 0x7F) { ; } else if (kar <= 0xC1) { return false; } else if (kar <= 0xDF) { if ((* ++ p & 0xC0) != 0x80) return false; } else if (kar <= 0xEF) { if ((* ++ p & 0xC0) != 0x80) return false; if ((* ++ p & 0xC0) != 0x80) return false; } else if (kar <= 0xF4) { if ((* ++ p & 0xC0) != 0x80) return false; if ((* ++ p & 0xC0) != 0x80) return false; if ((* ++ p & 0xC0) != 0x80) return false; } else { return false; } } return true; } long Melder_killReturns_inline (char *text) { const char *from; char *to; for (from = text, to = text; *from != '\0'; from ++, to ++) { if (*from == 13) { /* Carriage return? */ if (from [1] == '\n') { /* Followed by linefeed? Must be a Windows text. */ from ++; /* Ignore carriage return. */ *to = '\n'; /* Copy linefeed. */ } else { /* Bare carriage return? Must be a Macintosh text. */ *to = '\n'; /* Change to linefeed. */ } } else { *to = *from; } } *to = '\0'; /* Closing null byte. */ return to - text; } long Melder_killReturns_inlineW (wchar_t *text) { const wchar_t *from; wchar_t *to; for (from = text, to = text; *from != '\0'; from ++, to ++) { if (*from == 13) { /* Carriage return? */ if (from [1] == '\n' || from [1] == 0x0085 /* NextLine */) { /* Followed by linefeed? Must be a Windows text. */ from ++; /* Ignore carriage return. */ *to = '\n'; /* Copy linefeed. */ } else { /* Bare carriage return? Must be a Macintosh text. */ *to = '\n'; /* Change to linefeed (10). */ } } else if (*from == 0x0085 /* NextLine */ || *from == 0x000C /* FormFeed */ || *from == UNICODE_LINE_SEPARATOR || *from == UNICODE_PARAGRAPH_SEPARATOR) { *to = '\n'; } else { *to = *from; } } *to = '\0'; /* Closing null char. */ return to - text; } wchar Melder_decodeMacRoman [256] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_DIAERESIS, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_RING_ABOVE, UNICODE_LATIN_CAPITAL_LETTER_C_WITH_CEDILLA, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_ACUTE, UNICODE_LATIN_CAPITAL_LETTER_N_WITH_TILDE, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DIAERESIS, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS, UNICODE_LATIN_SMALL_LETTER_A_WITH_ACUTE, UNICODE_LATIN_SMALL_LETTER_A_WITH_GRAVE, UNICODE_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX, UNICODE_LATIN_SMALL_LETTER_A_WITH_DIAERESIS, UNICODE_LATIN_SMALL_LETTER_A_WITH_TILDE, UNICODE_LATIN_SMALL_LETTER_A_WITH_RING_ABOVE, UNICODE_LATIN_SMALL_LETTER_C_WITH_CEDILLA, UNICODE_LATIN_SMALL_LETTER_E_WITH_ACUTE, UNICODE_LATIN_SMALL_LETTER_E_WITH_GRAVE, UNICODE_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX, UNICODE_LATIN_SMALL_LETTER_E_WITH_DIAERESIS, UNICODE_LATIN_SMALL_LETTER_I_WITH_ACUTE, UNICODE_LATIN_SMALL_LETTER_I_WITH_GRAVE, UNICODE_LATIN_SMALL_LETTER_I_WITH_CIRCUMFLEX, UNICODE_LATIN_SMALL_LETTER_I_WITH_DIAERESIS, UNICODE_LATIN_SMALL_LETTER_N_WITH_TILDE, UNICODE_LATIN_SMALL_LETTER_O_WITH_ACUTE, UNICODE_LATIN_SMALL_LETTER_O_WITH_GRAVE, UNICODE_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX, UNICODE_LATIN_SMALL_LETTER_O_WITH_DIAERESIS, UNICODE_LATIN_SMALL_LETTER_O_WITH_TILDE, UNICODE_LATIN_SMALL_LETTER_U_WITH_ACUTE, UNICODE_LATIN_SMALL_LETTER_U_WITH_GRAVE, UNICODE_LATIN_SMALL_LETTER_U_WITH_CIRCUMFLEX, UNICODE_LATIN_SMALL_LETTER_U_WITH_DIAERESIS, UNICODE_DAGGER, UNICODE_DEGREE_SIGN, UNICODE_CENT_SIGN, UNICODE_POUND_SIGN, UNICODE_SECTION_SIGN, UNICODE_BULLET, UNICODE_PILCROW_SIGN, UNICODE_LATIN_SMALL_LETTER_SHARP_S, UNICODE_REGISTERED_SIGN, UNICODE_COPYRIGHT_SIGN, UNICODE_TRADE_MARK_SIGN, UNICODE_ACUTE_ACCENT, UNICODE_DIAERESIS, UNICODE_NOT_EQUAL_TO, UNICODE_LATIN_CAPITAL_LETTER_AE, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_STROKE, UNICODE_INFINITY, UNICODE_PLUS_MINUS_SIGN, UNICODE_LESS_THAN_OR_EQUAL_TO, UNICODE_GREATER_THAN_OR_EQUAL_TO, UNICODE_YEN_SIGN, UNICODE_MICRO_SIGN, UNICODE_PARTIAL_DIFFERENTIAL, UNICODE_N_ARY_SUMMATION, UNICODE_N_ARY_PRODUCT, UNICODE_GREEK_SMALL_LETTER_PI, UNICODE_INTEGRAL, UNICODE_FEMININE_ORDINAL_INDICATOR, UNICODE_MASCULINE_ORDINAL_INDICATOR, UNICODE_GREEK_CAPITAL_LETTER_OMEGA, UNICODE_LATIN_SMALL_LETTER_AE, UNICODE_LATIN_SMALL_LETTER_O_WITH_STROKE, UNICODE_INVERTED_QUESTION_MARK, UNICODE_INVERTED_EXCLAMATION_MARK, UNICODE_NOT_SIGN, UNICODE_SQUARE_ROOT, UNICODE_LATIN_SMALL_LETTER_F_WITH_HOOK, UNICODE_ALMOST_EQUAL_TO, UNICODE_INCREMENT, UNICODE_LEFT_POINTING_DOUBLE_ANGLE_QUOTATION_MARK, UNICODE_RIGHT_POINTING_DOUBLE_ANGLE_QUOTATION_MARK, UNICODE_HORIZONTAL_ELLIPSIS, UNICODE_NO_BREAK_SPACE, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_GRAVE, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_TILDE, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_TILDE, UNICODE_LATIN_CAPITAL_LIGATURE_OE, UNICODE_LATIN_SMALL_LIGATURE_OE, UNICODE_EN_DASH, UNICODE_EM_DASH, UNICODE_LEFT_DOUBLE_QUOTATION_MARK, UNICODE_RIGHT_DOUBLE_QUOTATION_MARK, UNICODE_LEFT_SINGLE_QUOTATION_MARK, UNICODE_RIGHT_SINGLE_QUOTATION_MARK, UNICODE_DIVISION_SIGN, UNICODE_LOZENGE, UNICODE_LATIN_SMALL_LETTER_Y_WITH_DIAERESIS, UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_DIAERESIS, UNICODE_FRACTION_SLASH, UNICODE_EURO_SIGN, UNICODE_SINGLE_LEFT_POINTING_ANGLE_QUOTATION_MARK, UNICODE_SINGLE_RIGHT_POINTING_ANGLE_QUOTATION_MARK, UNICODE_LATIN_SMALL_LIGATURE_FI, UNICODE_LATIN_SMALL_LIGATURE_FL, UNICODE_DOUBLE_DAGGER, UNICODE_MIDDLE_DOT, UNICODE_SINGLE_LOW_9_QUOTATION_MARK, UNICODE_DOUBLE_LOW_9_QUOTATION_MARK, UNICODE_PER_MILLE_SIGN, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_ACUTE, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_DIAERESIS, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_GRAVE, UNICODE_LATIN_CAPITAL_LETTER_I_WITH_ACUTE, UNICODE_LATIN_CAPITAL_LETTER_I_WITH_CIRCUMFLEX, UNICODE_LATIN_CAPITAL_LETTER_I_WITH_DIAERESIS, UNICODE_LATIN_CAPITAL_LETTER_I_WITH_GRAVE, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_ACUTE, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX, 0xf8ff /* Apple logo */, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_GRAVE, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_ACUTE, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_CIRCUMFLEX, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_GRAVE, UNICODE_LATIN_SMALL_LETTER_DOTLESS_I, UNICODE_MODIFIER_LETTER_CIRCUMFLEX_ACCENT, UNICODE_SMALL_TILDE, UNICODE_MACRON, UNICODE_BREVE, UNICODE_DOT_ABOVE, UNICODE_RING_ABOVE, UNICODE_CEDILLA, UNICODE_DOUBLE_ACUTE_ACCENT, UNICODE_OGONEK, UNICODE_CARON }; wchar_t Melder_decodeWindowsLatin1 [256] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, UNICODE_EURO_SIGN, 129, UNICODE_SINGLE_LOW_9_QUOTATION_MARK, UNICODE_LATIN_SMALL_LETTER_F_WITH_HOOK, UNICODE_DOUBLE_LOW_9_QUOTATION_MARK, UNICODE_HORIZONTAL_ELLIPSIS, UNICODE_DAGGER, UNICODE_DOUBLE_DAGGER, UNICODE_MODIFIER_LETTER_CIRCUMFLEX_ACCENT, UNICODE_PER_MILLE_SIGN, UNICODE_LATIN_CAPITAL_LETTER_S_WITH_CARON, UNICODE_SINGLE_LEFT_POINTING_ANGLE_QUOTATION_MARK, UNICODE_LATIN_CAPITAL_LIGATURE_OE, 141, UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_CARON, 143, 144, UNICODE_LEFT_SINGLE_QUOTATION_MARK, UNICODE_RIGHT_SINGLE_QUOTATION_MARK, UNICODE_LEFT_DOUBLE_QUOTATION_MARK, UNICODE_RIGHT_DOUBLE_QUOTATION_MARK, UNICODE_BULLET, UNICODE_EN_DASH, UNICODE_EM_DASH, UNICODE_SMALL_TILDE, UNICODE_TRADE_MARK_SIGN, UNICODE_LATIN_SMALL_LETTER_S_WITH_CARON, UNICODE_SINGLE_RIGHT_POINTING_ANGLE_QUOTATION_MARK, UNICODE_LATIN_SMALL_LIGATURE_OE, 157, UNICODE_LATIN_SMALL_LETTER_Z_WITH_CARON, UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_DIAERESIS, 160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, 171, 172, 173, 174, 175, 176, 177, 178, 179, 180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 191, 192, 193, 194, 195, 196, 197, 198, 199, 200, 201, 202, 203, 204, 205, 206, 207, 208, 209, 210, 211, 212, 213, 214, 215, 216, 217, 218, 219, 220, 221, 222, 223, 224, 225, 226, 227, 228, 229, 230, 231, 232, 233, 234, 235, 236, 237, 238, 239, 240, 241, 242, 243, 244, 245, 246, 247, 248, 249, 250, 251, 252, 253, 254, 255 }; void Melder_8bitToWcs_inline (const char *string, wchar *wcs, int inputEncoding) { wchar *q = & wcs [0]; if (inputEncoding == 0) { inputEncoding = preferences. inputEncoding; /* * In case the preferences weren't initialized yet, use the platform defaults: */ if (inputEncoding == 0) { #if defined (macintosh) inputEncoding = kMelder_textInputEncoding_UTF8_THEN_MACROMAN; #elif defined (_WIN32) inputEncoding = kMelder_textInputEncoding_UTF8_THEN_WINDOWS_LATIN1; #else inputEncoding = kMelder_textInputEncoding_UTF8_THEN_ISO_LATIN1; #endif } } if (inputEncoding == kMelder_textInputEncoding_UTF8 || inputEncoding == kMelder_textInputEncoding_UTF8_THEN_ISO_LATIN1 || inputEncoding == kMelder_textInputEncoding_UTF8_THEN_WINDOWS_LATIN1 || inputEncoding == kMelder_textInputEncoding_UTF8_THEN_MACROMAN) { if (Melder_strIsValidUtf8 (string)) { inputEncoding = kMelder_textInputEncoding_UTF8; } else if (inputEncoding == kMelder_textInputEncoding_UTF8_THEN_ISO_LATIN1) { inputEncoding = kMelder_textInputEncoding_ISO_LATIN1; } else if (inputEncoding == kMelder_textInputEncoding_UTF8_THEN_WINDOWS_LATIN1) { inputEncoding = kMelder_textInputEncoding_WINDOWS_LATIN1; } else if (inputEncoding == kMelder_textInputEncoding_UTF8_THEN_MACROMAN) { inputEncoding = kMelder_textInputEncoding_MACROMAN; } else { Melder_assert (inputEncoding == kMelder_textInputEncoding_UTF8); Melder_throw ("Text is not valid UTF-8; please try a different text input encoding."); } } const unsigned char *p = (const unsigned char *) & string [0]; if (inputEncoding == kMelder_textInputEncoding_UTF8) { while (*p != '\0') { uint32_t kar = * p ++; if (kar <= 0x7F) { * q ++ = kar; } else if (kar <= 0xDF) { unsigned long kar2 = * p ++; * q ++ = ((kar & 0x1F) << 6) | (kar2 & 0x3F); } else if (kar <= 0xEF) { unsigned long kar2 = * p ++, kar3 = * p ++; * q ++ = ((kar & 0x0F) << 12) | ((kar2 & 0x3F) << 6) | (kar3 & 0x3F); } else if (kar <= 0xF4) { unsigned long kar2 = * p ++, kar3 = * p ++, kar4 = * p ++; kar = ((kar & 0x07) << 18) | ((kar2 & 0x3F) << 12) | ((kar3 & 0x3F) << 6) | (kar4 & 0x3F); if (sizeof (wchar_t) == 2) { /* * Convert to UTF-16 surrogate pair. */ kar -= 0x10000; * q ++ = 0xD800 | (kar >> 10); * q ++ = 0xDC00 | (kar & 0x3FF); } else { * q ++ = kar; } } } } else if (inputEncoding == kMelder_textInputEncoding_ISO_LATIN1) { while (*p != '\0') { * q ++ = * p ++; } } else if (inputEncoding == kMelder_textInputEncoding_WINDOWS_LATIN1) { while (*p != '\0') { * q ++ = Melder_decodeWindowsLatin1 [* p ++]; } } else if (inputEncoding == kMelder_textInputEncoding_MACROMAN) { while (*p != '\0') { * q ++ = Melder_decodeMacRoman [* p ++]; } } else if (inputEncoding != kMelder_textInputEncoding_UTF8) { Melder_fatal ("Unknown text input encoding %d.", inputEncoding); } * q = '\0'; (void) Melder_killReturns_inlineW (wcs); } wchar * Melder_8bitToWcs (const char *string, int inputEncoding) { if (string == NULL) return NULL; autostring result = Melder_malloc (wchar, strlen (string) + 1); Melder_8bitToWcs_inline (string, result.peek(), inputEncoding); return result.transfer(); } wchar * Melder_utf8ToWcs (const char *string) { if (string == NULL) return NULL; autostring result = Melder_malloc (wchar, strlen (string) + 1); Melder_8bitToWcs_inline (string, result.peek(), kMelder_textInputEncoding_UTF8); return result.transfer(); } wchar * Melder_peekUtf8ToWcs (const char *textA) { if (textA == NULL) return NULL; static MelderString buffers [11] = { { 0 } }; static int ibuffer = 0; if (++ ibuffer == 11) ibuffer = 0; MelderString_empty (& buffers [ibuffer]); unsigned long n = strlen (textA), i, j; for (i = 0, j = 0; i <= n; i ++) { unsigned char kar = textA [i]; if (kar <= 0x7F) { MelderString_appendCharacter (& buffers [ibuffer], kar); } else if (kar <= 0xC1) { MelderString_appendCharacter (& buffers [ibuffer], UNICODE_REPLACEMENT_CHARACTER); } else if (kar <= 0xDF) { unsigned char kar2 = textA [++ i]; if (kar2 == '\0' || ! (kar2 & 0x80) || (kar2 & 0x40)) MelderString_appendCharacter (& buffers [ibuffer], UNICODE_REPLACEMENT_CHARACTER); MelderString_appendCharacter (& buffers [ibuffer], ((kar & 0x1F) << 6) | (kar2 & 0x3F)); } else if (kar <= 0xEF) { unsigned char kar2 = textA [++ i]; if (kar2 == '\0' || ! (kar2 & 0x80) || (kar2 & 0x40)) MelderString_appendCharacter (& buffers [ibuffer], UNICODE_REPLACEMENT_CHARACTER); unsigned char kar3 = textA [++ i]; if (kar3 == '\0' || ! (kar3 & 0x80) || (kar3 & 0x40)) MelderString_appendCharacter (& buffers [ibuffer], UNICODE_REPLACEMENT_CHARACTER); MelderString_appendCharacter (& buffers [ibuffer], ((kar & 0x0F) << 12) | ((kar2 & 0x3F) << 6) | (kar3 & 0x3F)); } else if (kar <= 0xF4) { unsigned char kar2 = textA [++ i]; if (kar2 == '\0' || ! (kar2 & 0x80) || (kar2 & 0x40)) MelderString_appendCharacter (& buffers [ibuffer], UNICODE_REPLACEMENT_CHARACTER); unsigned char kar3 = textA [++ i]; if (kar3 == '\0' || ! (kar3 & 0x80) || (kar3 & 0x40)) MelderString_appendCharacter (& buffers [ibuffer], UNICODE_REPLACEMENT_CHARACTER); unsigned char kar4 = textA [++ i]; if (kar4 == '\0' || ! (kar4 & 0x80) || (kar4 & 0x40)) MelderString_appendCharacter (& buffers [ibuffer], UNICODE_REPLACEMENT_CHARACTER); unsigned long character = ((kar & 0x07) << 18) | ((kar2 & 0x3F) << 12) | ((kar3 & 0x3F) << 6) | (kar4 & 0x3F); if (sizeof (wchar_t) == 2) { /* * Convert to UTF-16 surrogate pair. */ character -= 0x10000; MelderString_appendCharacter (& buffers [ibuffer], 0xD800 | (character >> 10)); MelderString_appendCharacter (& buffers [ibuffer], 0xDC00 | (character & 0x3FF)); } else { MelderString_appendCharacter (& buffers [ibuffer], character); } } else { MelderString_appendCharacter (& buffers [ibuffer], UNICODE_REPLACEMENT_CHARACTER); } } return buffers [ibuffer]. string; } unsigned long wcslen_utf8 (const wchar_t *wcs, bool expandNewlines) { long length = 0; for (const wchar_t *p = & wcs [0]; *p != '\0'; p ++) { if (sizeof (wchar_t) == 2) { unsigned short kar = *p; if (kar <= 0x007F) { #ifdef _WIN32 if (expandNewlines && kar == '\n') length ++; #else (void) expandNewlines; #endif length ++; } else if (kar <= 0x07FF) { length += 2; } else if (kar >= 0xD800 && kar <= 0xDBFF) { unsigned short kar2 = * ++ p; Melder_assert (kar2 >= 0xDC00 && kar2 <= 0xDFFF); length += 4; } else { Melder_assert (kar <= 0xD7FF || kar >= 0xE000); length += 3; } } else { unsigned long kar = *p; if (kar <= 0x00007F) { #ifdef _WIN32 if (expandNewlines && kar == '\n') length ++; #else (void) expandNewlines; #endif length ++; } else if (kar <= 0x0007FF) { length += 2; } else if (kar <= 0x00FFFF) { length += 3; } else { Melder_assert (kar <= 0x10FFFF); length += 4; } } } return length; } unsigned long wcslen_utf16 (const wchar_t *wcs, bool expandNewlines) { long length = 0; for (const wchar_t *p = & wcs [0]; *p != '\0'; p ++) { if (sizeof (wchar_t) == 2) { #ifdef _WIN32 unsigned short kar = *p; if (expandNewlines && kar == '\n') length ++; #else (void) expandNewlines; #endif length ++; } else { unsigned long kar = *p; if (kar <= 0x00007F) { #ifdef _WIN32 if (expandNewlines && kar == '\n') length ++; #else (void) expandNewlines; #endif length ++; } else if (kar >= 0x10000) { length += 2; } else { length += 1; } } } return length; } void Melder_wcsToUtf8_inline (const wchar_t *wcs, char *utf8) { long n = wcslen (wcs), i, j; for (i = 0, j = 0; i < n; i ++) { unsigned long kar = sizeof (wchar_t) == 2 ? (unsigned short) wcs [i] : wcs [i]; // crucial cast: prevents sign extension if (kar <= 0x00007F) { #ifdef _WIN32 if (kar == '\n') utf8 [j ++] = 13; #endif utf8 [j ++] = kar; } else if (kar <= 0x0007FF) { utf8 [j ++] = 0xC0 | (kar >> 6); utf8 [j ++] = 0x80 | (kar & 0x00003F); } else if (kar <= 0x00FFFF) { if (sizeof (wchar_t) == 2) { if ((kar & 0xF800) == 0xD800) { if (kar > 0xDBFF) Melder_fatal ("Incorrect Unicode value (first surrogate member %lX).", kar); unsigned long kar2 = (unsigned short) wcs [++ i]; // crucial cast: prevents sign extension if (kar2 < 0xDC00 || kar2 > 0xDFFF) Melder_fatal ("Incorrect Unicode value (second surrogate member %lX).", kar2); kar = (((kar & 0x3FF) << 10) | (kar2 & 0x3FF)) + 0x10000; // decode UTF-16 utf8 [j ++] = 0xF0 | (kar >> 18); utf8 [j ++] = 0x80 | ((kar >> 12) & 0x00003F); utf8 [j ++] = 0x80 | ((kar >> 6) & 0x00003F); utf8 [j ++] = 0x80 | (kar & 0x00003F); } else { utf8 [j ++] = 0xE0 | (kar >> 12); utf8 [j ++] = 0x80 | ((kar >> 6) & 0x00003F); utf8 [j ++] = 0x80 | (kar & 0x00003F); } } else { utf8 [j ++] = 0xE0 | (kar >> 12); utf8 [j ++] = 0x80 | ((kar >> 6) & 0x00003F); utf8 [j ++] = 0x80 | (kar & 0x00003F); } } else { utf8 [j ++] = 0xF0 | (kar >> 18); utf8 [j ++] = 0x80 | ((kar >> 12) & 0x00003F); utf8 [j ++] = 0x80 | ((kar >> 6) & 0x00003F); utf8 [j ++] = 0x80 | (kar & 0x00003F); } } utf8 [j] = '\0'; } char * Melder_wcsToUtf8 (const wchar *string) { if (string == NULL) return NULL; autostring8 result = Melder_malloc (char, wcslen_utf8 (string, true) + 1); Melder_wcsToUtf8_inline (string, result.peek()); return result.transfer(); } char * Melder_peekWcsToUtf8 (const wchar *text) { if (text == NULL) return NULL; static char *buffer [11] = { NULL }; static long bufferSize [11] = { 0 }; static int ibuffer = 0; if (++ ibuffer == 11) ibuffer = 0; long sizeNeeded = wcslen (text) * 4 + 1; if ((bufferSize [ibuffer] - sizeNeeded) * sizeof (char) >= 10000) { Melder_free (buffer [ibuffer]); bufferSize [ibuffer] = 0; } if (sizeNeeded > bufferSize [ibuffer]) { sizeNeeded = sizeNeeded * 1.61803 + 100; buffer [ibuffer] = (char *) Melder_realloc_f (buffer [ibuffer], sizeNeeded * sizeof (char)); bufferSize [ibuffer] = sizeNeeded; } Melder_wcsToUtf8_inline (text, buffer [ibuffer]); return buffer [ibuffer]; } const MelderUtf16 * Melder_peekWcsToUtf16 (const wchar *text) { if (text == NULL) return NULL; static MelderString16 buffers [11] = { { 0 } }; static int ibuffer = 0; if (++ ibuffer == 11) ibuffer = 0; MelderString16_empty (& buffers [ibuffer]); unsigned long n = wcslen (text); for (unsigned long i = 0; i <= n; i ++) { #ifdef _WIN32 if (text [i] == '\n') MelderString16_appendCharacter (& buffers [ibuffer], 13); #endif MelderString16_appendCharacter (& buffers [ibuffer], text [i]); } return buffers [ibuffer]. string; } #if defined (macintosh) const void * Melder_peekWcsToCfstring (const wchar_t *text) { if (text == NULL) return NULL; static CFStringRef cfString [11]; static int icfString = 0; if (++ icfString == 11) icfString = 0; if (cfString [icfString] != NULL) CFRelease (cfString [icfString]); cfString [icfString] = CFStringCreateWithCString (NULL, Melder_peekWcsToUtf8 (text), kCFStringEncodingUTF8); return cfString [icfString]; } #endif /* End of file melder_textencoding.cpp */ sources_5316/sys/ManPages.cpp0000644000176700017670000010435211724373643014757 0ustar paulpaul/* ManPages.cpp * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include "ManPages.h" #include "longchar.h" #include "Interpreter.h" #include "praat.h" Thing_implement (ManPages, Data, 0); #define LONGEST_FILE_NAME 55 static int isAllowedFileNameCharacter (int c) { return isalnum (c) || c == '_' || c == '-' || c == '+'; } static int isSingleWordCharacter (int c) { return isalnum (c) || c == '_'; } static long lookUp_unsorted (ManPages me, const wchar_t *title); void structManPages :: v_destroy () { if (dynamic && pages) { for (long ipage = 1; ipage <= pages -> size; ipage ++) { ManPage page = (ManPage) pages -> item [ipage]; Melder_free (page -> title); Melder_free (page -> author); if (page -> paragraphs) { ManPage_Paragraph par; for (par = page -> paragraphs; par -> type; par ++) Melder_free (par -> text); NUMvector_free (page -> paragraphs, 0); } if (ipage == 1) { NUMvector_free (page -> linksHither, 1); NUMvector_free (page -> linksThither, 1); } } } if (pages && titles) for (long ipage = 1; ipage <= pages -> size; ipage ++) { Melder_free (titles [ipage]); } forget (pages); NUMvector_free (titles, 1); ManPages_Parent :: v_destroy (); } static const wchar *extractLink (const wchar *text, const wchar *p, wchar *link) { wchar *to = link, *max = link + 300; if (p == NULL) p = text; /* * Search for next '@' that is not in a backslash sequence. */ for (;;) { p = wcschr (p, '@'); if (! p) return NULL; /* No more '@'. */ if (p - text <= 0 || (p [-1] != '\\' && (p - text <= 1 || p [-2] != '\\'))) break; p ++; } Melder_assert (*p == '@'); if (p [1] == '@') { const wchar *from = p + 2; while (*from != '@' && *from != '|' && *from != '\0') { if (to >= max) { Melder_throw ("(ManPages::grind:) Link starting with \"@@\" is too long:\n", text); } *to ++ = *from ++; } if (*from == '|') { from ++; while (*from != '@' && *from != '\0') from ++; } if (*from) p = from + 1; else p = from; /* Skip '@' but not '\0'. */ } else { const wchar *from = p + 1; while (isSingleWordCharacter (*from)) { if (to >= max) { Melder_throw ("(ManPages::grind:) Link starting with \"@@\" is too long:\n", text); } *to ++ = *from ++; } p = from; } *to = '\0'; return p; } static void readOnePage (ManPages me, MelderReadText text) { wchar *title; try { title = texgetw2 (text); } catch (MelderError) { Melder_throw ("Cannot find page title."); } /* * Check whether a page with this title is already present. */ if (lookUp_unsorted (me, title)) { Melder_free (title); // memory leak repaired, ppgb 20061228 return; } ManPage page = Thing_new (ManPage); page -> title = title; /* * Add the page early, so that lookUp can find it. */ Collection_addItem (my pages, page); try { page -> author = texgetw2 (text); } catch (MelderError) { Melder_throw ("Cannot find author."); } try { page -> date = texgetu4 (text); } catch (MelderError) { Melder_throw ("Cannot find date."); } try { page -> recordingTime = texgetr8 (text); } catch (MelderError) { Melder_throw ("Cannot find recording time."); } page -> paragraphs = NUMvector (0, 500); ManPage_Paragraph par = & page -> paragraphs [0]; for (;; par ++) { wchar link [501], fileName [256]; try { par -> type = texgete1 (text, kManPage_type_getValue); } catch (MelderError) { if (Melder_hasError (L"end of text")) { Melder_clearError (); break; } else { throw; } } if (par -> type == kManPage_type_SCRIPT) { par -> width = texgetr4 (text); par -> height = texgetr4 (text); } try { par -> text = texgetw2 (text); } catch (MelderError) { Melder_throw ("Cannot find text."); } for (const wchar *p = extractLink (par -> text, NULL, link); p != NULL; p = extractLink (par -> text, p, link)) { /* * Now, `link' contains the link text, with spaces and all. * Transform it into a file name. */ structMelderFile file2 = { 0 }; if (link [0] == '\\' && link [1] == 'F' && link [2] == 'I') { /* * A link to a sound file: see if it exists. */ MelderDir_relativePathToFile (& my rootDirectory, link + 3, & file2); if (! MelderFile_exists (& file2)) { Melder_warning (L"Cannot find sound file ", MelderFile_messageName (& file2), L"."); } } else if (link [0] == '\\' && link [1] == 'S' && link [2] == 'C') { /* * A link to a script: see if it exists. */ wchar_t *p = link + 3; if (*p == '\"') { wchar_t *q = fileName; p ++; while (*p != '\"' && *p != '\0') * q ++ = * p ++; *q = '\0'; } else { wchar_t *q = fileName; while (*p != ' ' && *p != '\0') * q ++ = * p ++; // One word, up to the next space. *q = '\0'; } MelderDir_relativePathToFile (& my rootDirectory, fileName, & file2); if (! MelderFile_exists (& file2)) { Melder_warning (L"Cannot find script ", MelderFile_messageName (& file2), L"."); } my executable = TRUE; } else { wchar_t *q; /* * A link to another page: follow it. */ for (q = link; *q; q ++) if (! isAllowedFileNameCharacter (*q)) *q = '_'; wcscpy (fileName, link); wcscat (fileName, L".man"); MelderDir_getFile (& my rootDirectory, fileName, & file2); try { autoMelderReadText text2 = MelderReadText_createFromFile (& file2); try { readOnePage (me, text2.peek()); } catch (MelderError) { Melder_throw ("File ", & file2, "."); } } catch (MelderError) { /* * Second try: with upper case. */ Melder_clearError (); link [0] = toupper (link [0]); wcscpy (fileName, link); wcscat (fileName, L".man"); MelderDir_getFile (& my rootDirectory, fileName, & file2); autoMelderReadText text2 = MelderReadText_createFromFile (& file2); try { readOnePage (me, text2.peek()); } catch (MelderError) { Melder_throw ("File ", & file2, "."); } } } } } ++ par; // Room for the last paragraph (because counting starts at 0). ++ par; // Room for the final zero-type paragraph. Melder_realloc (page -> paragraphs, sizeof (struct structManPage_Paragraph) * (par - page -> paragraphs)); } void structManPages :: v_readText (MelderReadText text) { dynamic = TRUE; pages = Ordered_create (); MelderDir_copy (& Data_directoryBeingRead, & rootDirectory); readOnePage (this, text); } ManPages ManPages_create (void) { ManPages me = Thing_new (ManPages); my pages = Ordered_create (); return me; } void ManPages_addPage (ManPages me, const wchar_t *title, const wchar_t *author, long date, struct structManPage_Paragraph paragraphs []) { autoManPage page = Thing_new (ManPage); page -> title = title; page -> paragraphs = & paragraphs [0]; page -> author = author; page -> date = date; Collection_addItem (my pages, page.transfer()); } static int pageCompare (const void *first, const void *second) { ManPage me = * (ManPage *) first, thee = * (ManPage *) second; const wchar_t *p = my title, *q = thy title; for (;;) { int plower = tolower (*p), qlower = tolower (*q); if (plower < qlower) return -1; if (plower > qlower) return 1; if (plower == '\0') return wcscmp (my title, thy title); p ++, q ++; } return 0; /* Should not occur. */ } static long lookUp_unsorted (ManPages me, const wchar_t *title) { long i; /* * First try to match an unaltered 'title' with the titles of the man pages. */ for (i = 1; i <= my pages -> size; i ++) { ManPage page = (ManPage) my pages -> item [i]; if (wcsequ (page -> title, title)) return i; } /* * If that fails, try to find the upper-case variant. */ if (islower (title [0])) { wchar_t upperTitle [300]; wcscpy (upperTitle, title); upperTitle [0] = toupper (upperTitle [0]); for (i = 1; i <= my pages -> size; i ++) { ManPage page = (ManPage) my pages -> item [i]; if (wcsequ (page -> title, upperTitle)) return i; } } return 0; } static long lookUp_sorted (ManPages me, const wchar_t *title) { static ManPage dummy; ManPage *page; if (! dummy) dummy = Thing_new (ManPage); dummy -> title = title; page = (ManPage *) bsearch (& dummy, & my pages -> item [1], my pages -> size, sizeof (ManPage), pageCompare); if (page) return (page - (ManPage *) & my pages -> item [1]) + 1; if (islower (title [0]) || isupper (title [0])) { wchar_t caseSwitchedTitle [300]; wcscpy (caseSwitchedTitle, title); caseSwitchedTitle [0] = islower (title [0]) ? toupper (caseSwitchedTitle [0]) : tolower (caseSwitchedTitle [0]); dummy -> title = caseSwitchedTitle; page = (ManPage *) bsearch (& dummy, & my pages -> item [1], my pages -> size, sizeof (ManPage), pageCompare); if (page) return (page - (ManPage *) & my pages -> item [1]) + 1; } return 0; } static void grind (ManPages me) { long ipage, ndangle = 0, jpage, grandNlinks, ilinkHither, ilinkThither; long *grandLinksHither, *grandLinksThither; qsort (& my pages -> item [1], my pages -> size, sizeof (ManPage), pageCompare); /* * First pass: count and check links: fill in nlinksHither and nlinksThither. */ grandNlinks = 0; for (ipage = 1; ipage <= my pages -> size; ipage ++) { ManPage page = (ManPage) my pages -> item [ipage]; int ipar; for (ipar = 0; page -> paragraphs [ipar]. type; ipar ++) { const wchar_t *text = page -> paragraphs [ipar]. text, *p; wchar_t link [301]; if (text) for (p = extractLink (text, NULL, link); p != NULL; p = extractLink (text, p, link)) { if (link [0] == '\\' && ((link [1] == 'F' && link [2] == 'I') || (link [1] == 'S' && link [2] == 'C'))) continue; /* Ignore "FILE" links. */ if ((jpage = lookUp_sorted (me, link)) != 0) { page -> nlinksThither ++; ((ManPage) my pages -> item [jpage]) -> nlinksHither ++; grandNlinks ++; } else { MelderInfo_writeLine5 (L"Page \"", page -> title, L"\" contains a dangling link to \"", link, L"\"."); ndangle ++; } } therror; } } if (ndangle) { MelderInfo_close (); Melder_warning ("(ManPages::grind:) ", ndangle, " dangling links encountered. See console window."); } /* * Second pass: allocate memory: fill in linksHither and linksThither. * Some optimization required: use only two mallocs. * Forget nlinksHither and nlinksThither. */ if (grandNlinks == 0) { my ground = TRUE; return; } if (! (grandLinksHither = NUMvector (1, grandNlinks)) || ! (grandLinksThither = NUMvector (1, grandNlinks))) { Melder_flushError (NULL); return; } ilinkHither = ilinkThither = 0; for (ipage = 1; ipage <= my pages -> size; ipage ++) { ManPage page = (ManPage) my pages -> item [ipage]; page -> linksHither = grandLinksHither + ilinkHither; page -> linksThither = grandLinksThither + ilinkThither; ilinkHither += page -> nlinksHither; ilinkThither += page -> nlinksThither; page -> nlinksHither = 0; page -> nlinksThither = 0; } Melder_assert (ilinkHither == grandNlinks && ilinkThither == grandNlinks); /* * Third pass: remember the links: fill in linksThither [1..nlinksThither] and linksHither [1..nlinksHither]. * Rebuild nlinksHither and nlinksThither. */ for (ipage = 1; ipage <= my pages -> size; ipage ++) { ManPage page = (ManPage) my pages -> item [ipage]; int ipar; for (ipar = 0; page -> paragraphs [ipar]. type; ipar ++) { const wchar_t *text = page -> paragraphs [ipar]. text, *p; wchar_t link [301]; if (text) for (p = extractLink (text, NULL, link); p != NULL; p = extractLink (text, p, link)) { if (link [0] == '\\' && ((link [1] == 'F' && link [2] == 'I') || (link [1] == 'S' && link [2] == 'C'))) continue; /* Ignore "FILE" links. */ if ((jpage = lookUp_sorted (me, link)) != 0) { int ilink, alreadyPresent = FALSE; for (ilink = 1; ilink <= page -> nlinksThither; ilink ++) { if (page -> linksThither [ilink] == jpage) { alreadyPresent = TRUE; break; } } if (! alreadyPresent) { ManPage otherPage = (ManPage) my pages -> item [jpage]; page -> linksThither [++ page -> nlinksThither] = jpage; otherPage -> linksHither [++ otherPage -> nlinksHither] = ipage; } } } therror; } } my ground = TRUE; } long ManPages_uniqueLinksHither (ManPages me, long ipage) { ManPage page = (ManPage) my pages -> item [ipage]; long result = page -> nlinksHither, ilinkHither, ilinkThither; for (ilinkHither = 1; ilinkHither <= page -> nlinksHither; ilinkHither ++) { long link = page -> linksHither [ilinkHither]; for (ilinkThither = 1; ilinkThither <= page -> nlinksThither; ilinkThither ++) if (page -> linksThither [ilinkThither] == link) { result --; break; } } return result; } long ManPages_lookUp (ManPages me, const wchar_t *title) { if (! my ground) grind (me); return lookUp_sorted (me, title); } static long ManPages_lookUp_caseSensitive (ManPages me, const wchar_t *title) { if (! my ground) grind (me); for (long i = 1; i <= my pages -> size; i ++) { ManPage page = (ManPage) my pages -> item [i]; if (wcsequ (page -> title, title)) return i; } return 0; } const wchar_t **ManPages_getTitles (ManPages me, long *numberOfTitles) { if (! my ground) grind (me); if (! my titles) { my titles = NUMvector (1, my pages -> size); // TODO for (long i = 1; i <= my pages -> size; i ++) { ManPage page = (ManPage) my pages -> item [i]; my titles [i] = Melder_wcsdup_f (page -> title); } } *numberOfTitles = my pages -> size; return my titles; } static struct stylesInfo { const wchar_t *htmlIn, *htmlOut; } stylesInfo [] = { { 0 }, /* INTRO: */ { L"

", L"

" }, /* ENTRY: */ { L"

", L"

" }, /* NORMAL: */ { L"

", L"

" }, /* LIST_ITEM: */ { L"
", L"" }, /* TAG: */ { L"
", L"" }, /* DEFINITION: */ { L"
", L"" }, /* CODE: */ { L"", L"
" }, /* PROTOTYPE: */ { L"

", L"

" }, /* FORMULA: */ { L"
", L"
" }, /* PICTURE: */ { L"

", L"

" }, /* SCRIPT: */ { L"

", L"

" }, /* LIST_ITEM1: */ { L"
   ", L"" }, /* LIST_ITEM2: */ { L"
      ", L"" }, /* LIST_ITEM3: */ { L"
         ", L"" }, /* TAG1: */ { L"
   ", L"" }, /* TAG2: */ { L"
      ", L"" }, /* TAG3: */ { L"
         ", L"" }, /* DEFINITION1: */ { L"
   ", L"" }, /* DEFINITION2: */ { L"
      ", L"" }, /* DEFINITION3: */ { L"
         ", L"" }, /* CODE1: */ { L"   ", L"
" }, /* CODE2: */ { L"      ", L"
" }, /* CODE3: */ { L"         ", L"
" }, /* CODE4: */ { L"            ", L"
" }, /* CODE5: */ { L"               ", L"
" } }; static void writeParagraphsAsHtml (ManPages me, MelderFile file, ManPage_Paragraph paragraphs, MelderString *buffer) { long numberOfPictures = 0; bool inList = false, inItalic = false, inBold = false; bool inSub = false, inCode = false, inSuper = false, ul = false, inSmall = false; bool wordItalic = false, wordBold = false, wordCode = false, letterSuper = false; for (ManPage_Paragraph paragraph = paragraphs; paragraph -> type != 0; paragraph ++) { const wchar_t *p = paragraph -> text; int type = paragraph -> type, inTable; bool isListItem = type == kManPage_type_LIST_ITEM || (type >= kManPage_type_LIST_ITEM1 && type <= kManPage_type_LIST_ITEM3); bool isTag = type == kManPage_type_TAG || (type >= kManPage_type_TAG1 && type <= kManPage_type_TAG3); bool isDefinition = type == kManPage_type_DEFINITION || (type >= kManPage_type_DEFINITION1 && type <= kManPage_type_DEFINITION3); /*bool isCode = type == kManPage_type_CODE || (type >= kManPage_type_CODE1 && type <= kManPage_type_CODE5);*/ if (type == kManPage_type_PICTURE) { numberOfPictures ++; structMelderFile pdfFile; MelderFile_copy (file, & pdfFile); pdfFile. path [wcslen (pdfFile. path) - 5] = '\0'; // delete extension ".html" wcscat (pdfFile. path, Melder_wcscat (L"_", Melder_integer (numberOfPictures), L".pdf")); Graphics graphics = Graphics_create_pdffile (& pdfFile, 100, 0.0, paragraph -> width, 0.0, paragraph -> height); Graphics_setFont (graphics, kGraphics_font_TIMES); Graphics_setFontStyle (graphics, 0); Graphics_setFontSize (graphics, 12); Graphics_setWrapWidth (graphics, 0); Graphics_setViewport (graphics, 0.0, paragraph -> width, 0.0, paragraph -> height); paragraph -> draw (graphics); Graphics_setViewport (graphics, 0, 1, 0, 1); Graphics_setWindow (graphics, 0, 1, 0, 1); Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_BOTTOM); forget (graphics); structMelderFile tiffFile; MelderFile_copy (file, & tiffFile); tiffFile. path [wcslen (tiffFile. path) - 5] = '\0'; // delete extension ".html" wcscat (tiffFile. path, Melder_wcscat (L"_", Melder_integer (numberOfPictures), L".png")); system (Melder_peekWcsToUtf8 (Melder_wcscat (L"/usr/local/bin/gs -q -dNOPAUSE " "-r200x200 -sDEVICE=png16m -sOutputFile=", tiffFile.path, L" ", pdfFile. path, L" quit.ps"))); MelderFile_delete (& pdfFile); MelderString_append (buffer, Melder_wcscat (L"

")); continue; } if (type == kManPage_type_SCRIPT) { autoInterpreter interpreter = Interpreter_createFromEnvironment (NULL); numberOfPictures ++; structMelderFile pdfFile; MelderFile_copy (file, & pdfFile); pdfFile. path [wcslen (pdfFile. path) - 5] = '\0'; // delete extension ".html" wcscat (pdfFile. path, Melder_wcscat (L"_", Melder_integer (numberOfPictures), L".pdf")); Graphics graphics = Graphics_create_pdffile (& pdfFile, 100, 0.0, paragraph -> width, 0.0, paragraph -> height); Graphics_setFont (graphics, kGraphics_font_TIMES); Graphics_setFontStyle (graphics, 0); Graphics_setFontSize (graphics, 12); Graphics_setWrapWidth (graphics, 0); static structPraatApplication praatApplication; static structPraatObjects praatObjects; static structPraatPicture praatPicture; theCurrentPraatApplication = & praatApplication; theCurrentPraatApplication -> batch = true; theCurrentPraatObjects = (PraatObjects) & praatObjects; theCurrentPraatPicture = (PraatPicture) & praatPicture; theCurrentPraatPicture -> graphics = graphics; theCurrentPraatPicture -> font = kGraphics_font_TIMES; theCurrentPraatPicture -> fontSize = 12; theCurrentPraatPicture -> lineType = Graphics_DRAWN; theCurrentPraatPicture -> colour = Graphics_BLACK; theCurrentPraatPicture -> lineWidth = 1.0; theCurrentPraatPicture -> arrowSize = 1.0; theCurrentPraatPicture -> x1NDC = 0; theCurrentPraatPicture -> x2NDC = paragraph -> width; theCurrentPraatPicture -> y1NDC = 0; theCurrentPraatPicture -> y2NDC = paragraph -> height; Graphics_setViewport (graphics, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setWindow (graphics, 0.0, 1.0, 0.0, 1.0); long x1DC, y1DC, x2DC, y2DC; Graphics_WCtoDC (graphics, 0.0, 0.0, & x1DC, & y2DC); Graphics_WCtoDC (graphics, 1.0, 1.0, & x2DC, & y1DC); Graphics_resetWsViewport (graphics, x1DC, x2DC, y1DC, y2DC); Graphics_setWsWindow (graphics, 0, paragraph -> width, 0, paragraph -> height); theCurrentPraatPicture -> x1NDC = 0; theCurrentPraatPicture -> x2NDC = paragraph -> width; theCurrentPraatPicture -> y1NDC = 0; theCurrentPraatPicture -> y2NDC = paragraph -> height; Graphics_setViewport (graphics, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); { // scope autoMelderProgressOff progress; autoMelderWarningOff warning; autoMelderSaveDefaultDir saveDir; if (! MelderDir_isNull (& my rootDirectory)) { Melder_setDefaultDir (& my rootDirectory); } try { autostring text = Melder_wcsdup (p); Interpreter_run (interpreter.peek(), text.peek()); } catch (MelderError) { Melder_flushError (NULL); } } Graphics_setViewport (graphics, 0, 1, 0, 1); Graphics_setWindow (graphics, 0, 1, 0, 1); Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_BOTTOM); forget (graphics); structMelderFile tiffFile; MelderFile_copy (file, & tiffFile); tiffFile. path [wcslen (tiffFile. path) - 5] = '\0'; // delete extension ".html" wcscat (tiffFile. path, Melder_wcscat (L"_", Melder_integer (numberOfPictures), L".png")); system (Melder_peekWcsToUtf8 (Melder_wcscat (L"/usr/local/bin/gs -q -dNOPAUSE " "-r200x200 -sDEVICE=png16m -sOutputFile=", tiffFile.path, L" ", pdfFile. path, L" quit.ps"))); MelderFile_delete (& pdfFile); MelderString_append (buffer, Melder_wcscat (L"

")); theCurrentPraatApplication = & theForegroundPraatApplication; theCurrentPraatObjects = & theForegroundPraatObjects; theCurrentPraatPicture = & theForegroundPraatPicture; continue; } if (isListItem || isTag || isDefinition) { if (! inList) { ul = isListItem && p [0] == '\\' && p [1] == 'b' && p [2] == 'u'; MelderString_append (buffer, ul ? L"
    \n" : L"
    \n"); inList = true; } if (ul && p [0] == '\\' && p [1] == 'b' && p [2] == 'u' && p [3] == ' ') p += 3; MelderString_append (buffer, ul ? L"
  • " : stylesInfo [paragraph -> type]. htmlIn, L"\n"); } else { if (inList) { MelderString_append (buffer, ul ? L"
\n" : L"\n"); inList = ul = false; } MelderString_append (buffer, stylesInfo [paragraph -> type]. htmlIn, L"\n"); } inTable = *p == '\t'; if (inTable) { MelderString_append (buffer, L"
"); p ++; } /* * Leading spaces should be visible (mainly used in code fragments). */ while (*p == ' ') { MelderString_append (buffer, L" "); p ++; } while (*p) { if (wordItalic && ! isSingleWordCharacter (*p)) { MelderString_append (buffer, L""); wordItalic = FALSE; } if (wordBold && ! isSingleWordCharacter (*p)) { MelderString_append (buffer, L""); wordBold = FALSE; } if (wordCode && ! isSingleWordCharacter (*p)) { MelderString_append (buffer, L""); wordCode = FALSE; } if (*p == '@') { wchar_t link [301], linkText [301], *q = link; if (p [1] == '@') { p += 2; while (*p != '@' && *p != '|' && *p != '\0') *q++ = *p++; *q = '\0'; /* Close link. */ if (*p == '|') { p ++; /* Skip '|'. */ q = linkText; while (*p != '@' && *p != '\0') *q++ = *p++; *q = '\0'; /* Close link text. */ } else { wcscpy (linkText, link); } if (*p) p ++; } else { p ++; while (isSingleWordCharacter (*p) && *p != '\0') *q++ = *p++; *q = '\0'; /* Close link. */ wcscpy (linkText, link); } /* * We write the link in the following format: * linkText * If "link" (initial lower case) is not in the manual, we write "Link.html" instead. * All spaces and strange symbols in "link" are replaced by underscores, * because it will be a file name (see ManPages_writeAllToHtmlDir). * The file name will have no more than 30 or 60 characters, and no less than 1. */ MelderString_append (buffer, L"", linkText, L""); } else if (*p == '%') { if (inItalic) { MelderString_append (buffer, L""); inItalic = FALSE; p ++; } else if (p [1] == '%') { MelderString_append (buffer, L""); inItalic = TRUE; p += 2; } else if (p [1] == '#') { MelderString_append (buffer, L""); wordItalic = TRUE; wordBold = TRUE; p += 2; } else { MelderString_append (buffer, L""); wordItalic = TRUE; p ++; } } else if (*p == '_') { if (inSub) { /*if (wordItalic) { MelderString_append (buffer, L""); wordItalic = FALSE; } if (wordBold) { MelderString_append (buffer, L""); wordBold = FALSE; }*/ MelderString_append (buffer, L""); inSub = FALSE; p ++; } else if (p [1] == '_') { if (wordItalic) { MelderString_append (buffer, L""); wordItalic = FALSE; } if (wordBold) { MelderString_append (buffer, L""); wordBold = FALSE; } MelderString_append (buffer, L""); inSub = TRUE; p += 2; } else { MelderString_append (buffer, L"_"); p ++; } } else if (*p == '#') { if (inBold) { MelderString_append (buffer, L""); inBold = FALSE; p ++; } else if (p [1] == '#') { MelderString_append (buffer, L""); inBold = TRUE; p += 2; } else if (p [1] == '%') { MelderString_append (buffer, L""); wordBold = TRUE; wordItalic = TRUE; p += 2; } else { MelderString_append (buffer, L""); wordBold = TRUE; p ++; } } else if (*p == '$') { if (inCode) { MelderString_append (buffer, L""); inCode = FALSE; p ++; } else if (p [1] == '$') { MelderString_append (buffer, L""); inCode = TRUE; p += 2; } else { MelderString_append (buffer, L""); wordCode = TRUE; p ++; } } else if (*p == '^') { if (inSuper) { /*if (wordItalic) { MelderString_append (buffer, L""); wordItalic = FALSE; } if (wordBold) { MelderString_append (buffer, L""); wordBold = FALSE; }*/ MelderString_append (buffer, L""); inSuper = FALSE; p ++; } else if (p [1] == '^') { /*if (wordItalic) { MelderString_append (buffer, L""); wordItalic = FALSE; } if (wordBold) { MelderString_append (buffer, L""); wordBold = FALSE; }*/ MelderString_append (buffer, L""); inSuper = TRUE; p += 2; } else { /*if (wordItalic) { MelderString_append (buffer, L""); wordItalic = FALSE; } if (wordBold) { MelderString_append (buffer, L""); wordBold = FALSE; }*/ MelderString_append (buffer, L""); letterSuper = TRUE; p ++; } } else if (*p == '}') { if (inSmall) { MelderString_append (buffer, L""); inSmall = FALSE; p ++; } else { MelderString_append (buffer, L"}"); p ++; } } else if (*p == '\\' && p [1] == 's' && p [2] == '{') { MelderString_append (buffer, L""); inSmall = TRUE; p += 3; } else if (*p == '\t' && inTable) { MelderString_append (buffer, L""); p ++; } else if (*p == '<') { MelderString_append (buffer, L"<"); p ++; } else if (*p == '>') { MelderString_append (buffer, L">"); p ++; } else if (*p == '&') { MelderString_append (buffer, L"&"); p ++; } else { /*if (wordItalic && ! isSingleWordCharacter (*p)) { MelderString_append (buffer, L""); wordItalic = FALSE; } if (wordBold && ! isSingleWordCharacter (*p)) { MelderString_append (buffer, L""); wordBold = FALSE; } if (wordCode && ! isSingleWordCharacter (*p)) { MelderString_append (buffer, L""); wordCode = FALSE; }*/ if (*p == '\\') { int kar1 = *++p, kar2 = *++p; Longchar_Info info = Longchar_getInfo (kar1, kar2); if (info -> unicode < 127) { MelderString_appendCharacter (buffer, info -> unicode ? info -> unicode : '?'); } else { MelderString_append (buffer, L"&#", Melder_integer (info -> unicode), L";"); } p ++; } else { if (*p < 127) { MelderString_appendCharacter (buffer, *p); } else { MelderString_append (buffer, L"&#", Melder_integer (*p), L";"); } p ++; } if (letterSuper) { if (wordItalic) { MelderString_append (buffer, L""); wordItalic = FALSE; } if (wordBold) { MelderString_append (buffer, L""); wordBold = FALSE; } MelderString_append (buffer, L""); letterSuper = FALSE; } } } if (inItalic || wordItalic) { MelderString_append (buffer, L""); inItalic = wordItalic = FALSE; } if (inBold || wordBold) { MelderString_append (buffer, L""); inBold = wordBold = FALSE; } if (inCode || wordCode) { MelderString_append (buffer, L""); inCode = wordCode = FALSE; } if (inSub) { MelderString_append (buffer, L""); inSub = FALSE; } if (inSuper || letterSuper) { MelderString_append (buffer, L""); inSuper = letterSuper = FALSE; } if (inTable) { MelderString_append (buffer, L"
"); inTable = FALSE; } MelderString_append (buffer, stylesInfo [paragraph -> type]. htmlOut, L"\n"); } if (inList) { MelderString_append (buffer, ul ? L"\n" : L"\n"); inList = FALSE; } } static const wchar *month [] = { L"", L"January", L"February", L"March", L"April", L"May", L"June", L"July", L"August", L"September", L"October", L"November", L"December" }; static void writePageAsHtml (ManPages me, MelderFile file, long ipage, MelderString *buffer) { ManPage page = (ManPage) my pages -> item [ipage]; ManPage_Paragraph paragraphs = page -> paragraphs; MelderString_append (buffer, L"\n" L"", page -> title, L"\n\n"); MelderString_append (buffer, L"
" L"
" L"\n", page -> title, L"\n
\n"); writeParagraphsAsHtml (me, file, paragraphs, buffer); therror if (ManPages_uniqueLinksHither (me, ipage)) { long ilink, jlink, lastParagraph = 0; while (page -> paragraphs [lastParagraph]. type != 0) lastParagraph ++; if (lastParagraph > 0) { const wchar_t *text = page -> paragraphs [lastParagraph - 1]. text; if (text && text [0] && text [wcslen (text) - 1] != ':') MelderString_append (buffer, L"

Links to this page

\n"); } MelderString_append (buffer, L"\n"); } MelderString_append (buffer, L"
\n
\n\t

© ", page -> author); if (page -> date) { long date = page -> date; int imonth = date % 10000 / 100; if (imonth < 0 || imonth > 12) imonth = 0; MelderString_append (buffer, L", ", month [imonth], L" ", Melder_integer (date % 100)); MelderString_append (buffer, L", ", Melder_integer (date / 10000)); } MelderString_append (buffer, L"

\n
\n\n\n"); } void ManPages_writeOneToHtmlFile (ManPages me, long ipage, MelderFile file) { static MelderString buffer = { 0 }; MelderString_empty (& buffer); writePageAsHtml (me, file, ipage, & buffer); therror MelderFile_writeText (file, buffer.string); } void ManPages_writeAllToHtmlDir (ManPages me, const wchar *dirPath) { structMelderDir dir; Melder_pathToDir (dirPath, & dir); for (long ipage = 1; ipage <= my pages -> size; ipage ++) { ManPage page = (ManPage) my pages -> item [ipage]; wchar fileName [256]; wcscpy (fileName, page -> title); for (wchar *p = fileName; *p; p ++) if (! isAllowedFileNameCharacter (*p)) *p = '_'; if (fileName [0] == '\0') wcscpy (fileName, L"_"); // no empty file names please fileName [LONGEST_FILE_NAME] = '\0'; wcscat (fileName, L".html"); static MelderString buffer = { 0 }; MelderString_empty (& buffer); structMelderFile file = { 0 }; MelderDir_getFile (& dir, fileName, & file); writePageAsHtml (me, & file, ipage, & buffer); /* * An optimization because reading is much faster than writing: * we write the file only if the old file is different or doesn't exist. */ autostring oldText; try { oldText.reset (MelderFile_readText (& file)); } catch (MelderError) { Melder_clearError (); } if (oldText.peek() == NULL // doesn't the file exist yet? || wcscmp (buffer.string, oldText.peek())) // isn't the old file identical to the new text? { MelderFile_writeText (& file, buffer.string); // then write the new text } } } /* End of file ManPages.cpp */ sources_5316/sys/Strings.cpp0000644000176700017670000003036111633661466014715 0ustar paulpaul/* Strings.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2003/07/02 corrected Strings_randomize so that the first element can sometimes go to the first place * pb 2004/03/21 Strings_createAsFileList now accepts spaces in directory names on Unix and Mac * pb 2004/04/20 the previous thing now done with backslashes rather than double quotes, * because double quotes prevent the expansion of the wildcard asterisk * pb 2006/02/14 Strings_createAsDirectoryList for Windows * pb 2006/03/08 allow 1,000,000 file names in Strings_createAsFileList * pb 2006/09/19 Strings_createAsDirectoryList for Mac and Unix * pb 2006/10/04 return fewer errors in Strings_createAsFileList and Strings_createAsDirectoryList * pb 2006/10/28 erased MacOS 9 stuff * pb 2006/12/10 MelderInfo * pb 2007/01/24 Strings_createAsFileList: removed gigantic memory leak * pb 2007/01/24 Strings_createAsFileList: used stat instead of platform-specific struct dirent. entry * pb 2007/08/10 wchar_t * pb 2007/10/01 can write as encoding * pb 2007/10/01 corrected nativization * pb 2007/11/17 getVectorStr * pb 2007/12/10 Strings_createAsFileList precomposes characters * pb 2011/05/03 Windows: ignore file or directory names starting with '.' * pb 2011/05/15 C++ */ //#define USE_STAT 1 #ifndef USE_STAT #if defined (_WIN32) #define USE_STAT 0 #else #define USE_STAT 1 #endif #endif #if USE_STAT #include //#define __USE_BSD #include #include #endif #if defined (_WIN32) #include "winport_on.h" #include #include "winport_off.h" #endif #include "Strings.h" #include "longchar.h" #include "oo_DESTROY.h" #include "Strings_def.h" #include "oo_COPY.h" #include "Strings_def.h" #include "oo_EQUAL.h" #include "Strings_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Strings_def.h" #include "oo_WRITE_TEXT.h" #include "Strings_def.h" #include "oo_READ_TEXT.h" #include "Strings_def.h" #include "oo_WRITE_BINARY.h" #include "Strings_def.h" #include "oo_READ_BINARY.h" #include "Strings_def.h" #include "oo_DESCRIPTION.h" #include "Strings_def.h" Thing_implement (Strings, Data, 0); static long Strings_totalLength (Strings me) { long totalLength = 0; for (long i = 1; i <= my numberOfStrings; i ++) { totalLength += wcslen (my strings [i]); } return totalLength; } static long Strings_maximumLength (Strings me) { long maximumLength = 0; for (long i = 1; i <= my numberOfStrings; i ++) { long length = wcslen (my strings [i]); if (length > maximumLength) { maximumLength = length; } } return maximumLength; } void structStrings :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of strings: ", Melder_integer (numberOfStrings)); MelderInfo_writeLine3 (L"Total length: ", Melder_integer (Strings_totalLength (this)), L" characters"); MelderInfo_writeLine3 (L"Longest string: ", Melder_integer (Strings_maximumLength (this)), L" characters"); } const wchar * structStrings :: v_getVectorStr (long icol) { if (icol < 1 || icol > numberOfStrings) return L""; wchar *stringValue = strings [icol]; return stringValue == NULL ? L"" : stringValue; } #define Strings_createAsFileOrDirectoryList_TYPE_FILE 0 #define Strings_createAsFileOrDirectoryList_TYPE_DIRECTORY 1 static Strings Strings_createAsFileOrDirectoryList (const wchar *path, int type) { #if USE_STAT /* * Initialize. */ DIR *d = NULL; try { autoMelderString filePath, searchDirectory, left, right; /* * Parse the path. * Example: in /Users/paul/sounds/h*.wav", * the search directory is "/Users/paul/sounds", * the left environment is "h", and the right environment is ".wav". */ MelderString_copy (& searchDirectory, path); wchar *asterisk = wcsrchr (searchDirectory. string, '*'); if (asterisk != NULL) { *asterisk = '\0'; searchDirectory. length = asterisk - searchDirectory. string; // probably superfluous, but correct wchar *lastSlash = wcsrchr (searchDirectory. string, Melder_DIRECTORY_SEPARATOR); if (lastSlash != NULL) { *lastSlash = '\0'; // This fixes searchDirectory. searchDirectory. length = lastSlash - searchDirectory. string; // probably superfluous, but correct MelderString_copy (& left, lastSlash + 1); } else { MelderString_copy (& left, searchDirectory. string); // quickly save... MelderString_empty (& searchDirectory); // ...before destruction } MelderString_copy (& right, asterisk + 1); } char buffer8 [1+kMelder_MAXPATH]; Melder_wcsTo8bitFileRepresentation_inline (searchDirectory. string, buffer8); d = opendir (buffer8 [0] ? buffer8 : "."); if (d == NULL) Melder_throw ("Cannot open directory ", searchDirectory. string, "."); //Melder_casual ("opened"); autoStrings me = Thing_new (Strings); my strings = NUMvector (1, 1000000); struct dirent *entry; while ((entry = readdir (d)) != NULL) { MelderString_copy (& filePath, searchDirectory. string [0] ? searchDirectory. string : L"."); MelderString_appendCharacter (& filePath, Melder_DIRECTORY_SEPARATOR); wchar_t bufferW [1+kMelder_MAXPATH]; Melder_8bitFileRepresentationToWcs_inline (entry -> d_name, bufferW); MelderString_append (& filePath, bufferW); //Melder_casual ("read %s", filePath. string); Melder_wcsTo8bitFileRepresentation_inline (filePath. string, buffer8); struct stat stats; if (stat (buffer8, & stats) != 0) { Melder_throw ("Cannot look at file ", filePath. string, "."); //stats. st_mode = -1L; } //Melder_casual ("statted %s", filePath. string); //Melder_casual ("file %s mode %s", filePath. string, Melder_integer (stats. st_mode / 4096)); if ((type == Strings_createAsFileOrDirectoryList_TYPE_FILE && S_ISREG (stats. st_mode)) || (type == Strings_createAsFileOrDirectoryList_TYPE_DIRECTORY && S_ISDIR (stats. st_mode))) { Melder_8bitFileRepresentationToWcs_inline (entry -> d_name, bufferW); unsigned long length = wcslen (bufferW); if (bufferW [0] != '.' && (left. length == 0 || wcsnequ (bufferW, left. string, left. length)) && (right. length == 0 || (length >= right. length && wcsequ (bufferW + (length - right. length), right. string)))) { my strings [++ my numberOfStrings] = Melder_wcsdup (bufferW); } } } closedir (d); Strings_sort (me.peek()); return me.transfer(); } catch (MelderError) { if (d) closedir (d); // "finally" throw; } #elif defined (_WIN32) try { wchar searchPath [1+kMelder_MAXPATH]; int len = wcslen (path), hasAsterisk = wcschr (path, '*') != NULL, endsInSeparator = len != 0 && path [len - 1] == '\\'; autoStrings me = Thing_new (Strings); my strings = NUMvector (1, 1000000); swprintf (searchPath, 1+kMelder_MAXPATH, L"%ls%ls%ls", path, hasAsterisk || endsInSeparator ? L"" : L"\\", hasAsterisk ? L"" : L"*"); WIN32_FIND_DATAW findData; HANDLE searchHandle = FindFirstFileW (searchPath, & findData); if (searchHandle != INVALID_HANDLE_VALUE) { do { if ((type == Strings_createAsFileOrDirectoryList_TYPE_FILE && (findData. dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) == 0) || (type == Strings_createAsFileOrDirectoryList_TYPE_DIRECTORY && (findData. dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) != 0)) { if (findData. cFileName [0] != '.') { my strings [++ my numberOfStrings] = Melder_wcsdup (findData. cFileName); } } } while (FindNextFileW (searchHandle, & findData)); FindClose (searchHandle); } Strings_sort (me.peek()); return me.transfer(); } catch (MelderError) { throw; } #endif } Strings Strings_createAsFileList (const wchar *path) { try { return Strings_createAsFileOrDirectoryList (path, Strings_createAsFileOrDirectoryList_TYPE_FILE); } catch (MelderError) { Melder_throw ("Strings object not created as file list."); } } Strings Strings_createAsDirectoryList (const wchar *path) { try { return Strings_createAsFileOrDirectoryList (path, Strings_createAsFileOrDirectoryList_TYPE_DIRECTORY); } catch (MelderError) { Melder_throw ("Strings object not created as directory list."); } } Strings Strings_readFromRawTextFile (MelderFile file) { try { autoMelderReadText text = MelderReadText_createFromFile (file); /* * Count number of strings. */ long n = MelderReadText_getNumberOfLines (text.peek()); /* * Create. */ autoStrings me = Thing_new (Strings); if (n > 0) my strings = NUMvector (1, n); my numberOfStrings = n; /* * Read strings. */ for (long i = 1; i <= n; i ++) { wchar_t *line = MelderReadText_readLine (text.peek()); my strings [i] = Melder_wcsdup (line); } return me.transfer(); } catch (MelderError) { Melder_throw ("Strings not read from raw text file ", file, "."); } } void Strings_writeToRawTextFile (Strings me, MelderFile file) { autoMelderString buffer; for (long i = 1; i <= my numberOfStrings; i ++) { MelderString_append (& buffer, my strings [i], L"\n"); } MelderFile_writeText (file, buffer.string); } void Strings_randomize (Strings me) { for (long i = 1; i < my numberOfStrings; i ++) { long other = NUMrandomInteger (i, my numberOfStrings); wchar_t *dummy = my strings [other]; my strings [other] = my strings [i]; my strings [i] = dummy; } } void Strings_genericize (Strings me) { autostring buffer = Melder_calloc (wchar, Strings_maximumLength (me) * 3 + 1); for (long i = 1; i <= my numberOfStrings; i ++) { const wchar *p = (const wchar *) my strings [i]; while (*p) { if (*p > 126) { // backslashes are not converted, i.e. genericize^2 == genericize Longchar_genericizeW (my strings [i], buffer.peek()); autostring newString = Melder_wcsdup (buffer.peek()); /* * Replace string only if copying was OK. */ Melder_free (my strings [i]); my strings [i] = newString.transfer(); break; } p ++; } } } void Strings_nativize (Strings me) { autostring buffer = Melder_calloc (wchar, Strings_maximumLength (me) + 1); for (long i = 1; i <= my numberOfStrings; i ++) { Longchar_nativizeW (my strings [i], buffer.peek(), false); autostring newString = Melder_wcsdup (buffer.peek()); /* * Replace string only if copying was OK. */ Melder_free (my strings [i]); my strings [i] = newString.transfer(); } } void Strings_sort (Strings me) { NUMsort_str (my numberOfStrings, my strings); } void Strings_remove (Strings me, long position) { Melder_assert (position >= 1); Melder_assert (position <= my numberOfStrings); Melder_free (my strings [position]); for (long i = position; i < my numberOfStrings; i ++) { my strings [i] = my strings [i + 1]; } my numberOfStrings --; } void Strings_replace (Strings me, long position, const wchar *text) { Melder_assert (position >= 1); Melder_assert (position <= my numberOfStrings); if (Melder_wcsequ (my strings [position], text)) return; // nothing to change /* * Create without change. */ autostring newString = Melder_wcsdup (text); /* * Change without error. */ Melder_free (my strings [position]); my strings [position] = newString.transfer(); } void Strings_insert (Strings me, long position, const wchar *text) { if (position == 0) position = my numberOfStrings + 1; Melder_assert (position >= 1); Melder_assert (position <= my numberOfStrings + 1); /* * Create without change. */ autostring newString = Melder_wcsdup (text); /* * Change without error. */ for (long i = my numberOfStrings + 1; i > position; i --) { my strings [i] = my strings [i - 1]; } my strings [position] = newString.transfer(); my numberOfStrings ++; } /* End of file Strings.cpp */ sources_5316/sys/melder_time.cpp0000644000176700017670000000520211546675653015554 0ustar paulpaul/* melder_time.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2008/01/30 moved from Melder_audio.c * pb 2008/01/31 Win: use QueryPerformanceCounter * pb 2008/03/18 moved Melder_stopwatch here and made it call Melder_clock * pb 2011/04/05 C++ */ #include "melder.h" #if defined (macintosh) || defined (UNIX) #include #elif defined (_WIN32) #include #endif double Melder_clock (void) { #if defined (macintosh) || defined (UNIX) /* * The clock counts the number of seconds elapsed since 1969. */ struct timeval timeVal; struct timezone timeZone; gettimeofday (& timeVal, & timeZone); return timeVal. tv_sec + 1e-6 * timeVal. tv_usec; #elif defined (_WIN32) /* * The clock counts the number of ticks since system start-up. */ static double clockFrequency = -1.0; // we can use a static, because the clock frequency does not change while the computer is running if (clockFrequency == -1.0) { // not initialized? LARGE_INTEGER clockFrequency_longlong; QueryPerformanceFrequency (& clockFrequency_longlong); // returns 0 if the system does not have a performance counter clockFrequency = (double) clockFrequency_longlong.QuadPart; // the compiler has to support 64-bit integers } if (clockFrequency == 0.0) { // this will be true if the system does not have a performance counter return GetTickCount () / 1000.0; // fallback: only millisecond resolution, and potentially jumpy } LARGE_INTEGER clockCount; QueryPerformanceCounter (& clockCount); return (double) clockCount.QuadPart / clockFrequency; #else return 0; #endif } double Melder_stopwatch (void) { static double lastTime; double now = Melder_clock (); double timeElapsed = lastTime == 0 ? -1.0 : now - lastTime; //Melder_casual ("%ld %ld %ld %lf %lf", now, lastTime, now - lastTime, (now - lastTime) / (double) CLOCKS_PER_SEC, timeElapsed); lastTime = now; return timeElapsed; } /* End of file melder_time.cpp */ sources_5316/sys/praat_actions.cpp0000644000176700017670000010523611751733541016112 0ustar paulpaul/* praat_actions.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "praatP.h" #include "praat_script.h" #include "longchar.h" #include "machine.h" #define BUTTON_WIDTH 240 #define praat_MAXNUM_LOOSE_COMMANDS 5000 static long theNumberOfActions = 0; static struct structPraat_Command *theActions; static GuiObject praat_writeMenuTitle, praat_writeMenu, praat_writeMenuSeparator; static GuiObject praat_dynamicMenu, praat_dynamicMenuWindow; static void fixSelectionSpecification (ClassInfo *class1, int *n1, ClassInfo *class2, int *n2, ClassInfo *class3, int *n3) { /* * Function: * sort the specification pairs *class(i), *n(i) according to class name, with NULL classes at the end. * Postconditions: * if (*class2 != NULL) *class1 != NULL; * if (*class3 != NULL) *class2 != NULL; * (*class1) -> className <= (*class2) -> className <= (*class3) -> className; * Usage: * Called by praat_addAction () and praat_removeAction (). */ /* Fix unusual input bubblewise. */ if (*class1 == NULL && *class2 != NULL) { *class1 = *class2; *n1 = *n2; *class2 = NULL; *n2 = 0; } if (*class2 == NULL && *class3 != NULL) { *class2 = *class3; *n2 = *n3; *class3 = NULL; *n3 = 0; if (*class1 == NULL && *class2 != NULL) { *class1 = *class2; *n1 = *n2; *class2 = NULL; *n2 = 0; } } /* Now: if *class3, then *class2, and if *class2, then *class1. * Bubble-sort the input by class name. */ if (*class2 && wcscmp ((*class1) -> className, (*class2) -> className) > 0) { ClassInfo helpClass = *class1; *class1 = *class2; *class2 = helpClass; int helpN = *n1; *n1 = *n2; *n2 = helpN; } if (*class3 && wcscmp ((*class2) -> className, (*class3) -> className) > 0) { ClassInfo helpClass = *class2; *class2 = *class3; *class3 = helpClass; int helpN = *n2; *n2 = *n3; *n3 = helpN; if (wcscmp ((*class1) -> className, (*class2) -> className) > 0) { ClassInfo helpClass = *class1; *class1 = *class2; *class2 = helpClass; int helpN = *n1; *n1 = *n2; *n2 = helpN; } } } static long lookUpMatchingAction (ClassInfo class1, ClassInfo class2, ClassInfo class3, ClassInfo class4, const wchar *title) { /* * An action command is fully specified by its environment (the selected classes) and its title. * Precondition: * class1, class2, and class3 must be in sorted order. */ for (long i = 1; i <= theNumberOfActions; i ++) if (class1 == theActions [i]. class1 && class2 == theActions [i]. class2 && class3 == theActions [i]. class3 && class4 == theActions [i]. class4 && title && theActions [i]. title && wcsequ (theActions [i]. title, title)) return i; return 0; /* Not found. */ } void praat_addAction (ClassInfo class1, int n1, ClassInfo class2, int n2, ClassInfo class3, int n3, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)) { praat_addAction4 (class1, n1, class2, n2, class3, n3, NULL, 0, title, after, flags, callback); } void praat_addAction1 (ClassInfo class1, int n1, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)) { praat_addAction4 (class1, n1, NULL, 0, NULL, 0, NULL, 0, title, after, flags, callback); } void praat_addAction2 (ClassInfo class1, int n1, ClassInfo class2, int n2, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)) { praat_addAction4 (class1, n1, class2, n2, NULL, 0, NULL, 0, title, after, flags, callback); } void praat_addAction3 (ClassInfo class1, int n1, ClassInfo class2, int n2, ClassInfo class3, int n3, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)) { praat_addAction4 (class1, n1, class2, n2, class3, n3, NULL, 0, title, after, flags, callback); } void praat_addAction4 (ClassInfo class1, int n1, ClassInfo class2, int n2, ClassInfo class3, int n3, ClassInfo class4, int n4, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)) { try { int depth = flags, unhidable = FALSE, hidden = FALSE, key = 0, attractive = 0; unsigned long motifFlags = 0; if (flags > 7) { depth = ((flags & praat_DEPTH_7) >> 16); unhidable = (flags & praat_UNHIDABLE) != 0; hidden = (flags & praat_HIDDEN) != 0 && ! unhidable; key = flags & 0x000000FF; motifFlags = key ? flags & (0x002000FF | GuiMenu_BUTTON_STATE_MASK) : flags & GuiMenu_BUTTON_STATE_MASK; attractive = (motifFlags & praat_ATTRACTIVE) != 0; } fixSelectionSpecification (& class1, & n1, & class2, & n2, & class3, & n3); if (callback && ! title) Melder_throw ("An action command with callback has no title. Classes: ", class1 ? class1 -> className : L"", L" ", class2 ? class2 -> className : L"", L" ", class3 ? class3 -> className : L"", L" ", class4 ? class4 -> className : L"", L"."); if (! class1) Melder_throw ("The action command \"", title, "\" has no first class."); /* * Determine the position of the new command. */ long position; if (after) { // search for existing command with same selection long found = lookUpMatchingAction (class1, class2, class3, class4, after); if (found == 0) Melder_throw ("The action command \"", title, "\" cannot be put after \"", after, "\",\n" "because the latter command does not exist."); position = found + 1; // after 'after' } else { position = theNumberOfActions + 1; // at end } /* * Increment the command area. */ if (theNumberOfActions >= praat_MAXNUM_LOOSE_COMMANDS) Melder_throw ("Too many action commands (maximum ", praat_MAXNUM_LOOSE_COMMANDS, ")."); theNumberOfActions += 1; /* * Make room for insertion. */ for (long i = theNumberOfActions; i > position; i --) theActions [i] = theActions [i - 1]; memset (& theActions [position], 0, sizeof (struct structPraat_Command)); /* * Insert new command. */ theActions [position]. class1 = class1; theActions [position]. n1 = n1; theActions [position]. class2 = class2; theActions [position]. n2 = n2; theActions [position]. class3 = class3; theActions [position]. n3 = n3; theActions [position]. class4 = class4; theActions [position]. n4 = n4; theActions [position]. title = Melder_wcsdup_f (title); theActions [position]. depth = depth; theActions [position]. callback = callback; /* NULL for a separator. */ theActions [position]. button = NULL; theActions [position]. script = NULL; theActions [position]. hidden = hidden; theActions [position]. unhidable = unhidable; theActions [position]. attractive = attractive; } catch (MelderError) { Melder_flushError (NULL); } } static void deleteDynamicMenu (void) { if (praatP.phase != praat_HANDLING_EVENTS) return; //static int deletions; //Melder_information(Melder_integer(++deletions)); if (praat_dynamicMenu) { GuiObject_destroy (praat_dynamicMenu); praat_dynamicMenu = NULL; for (int i = 1; i <= theNumberOfActions; i ++) theActions [i]. button = NULL; if (praat_writeMenu) { // ppgb 20080103: put into praat_dynamicMenu condition GuiObject_destroy (praat_writeMenu); praat_writeMenuSeparator = NULL; // RFC: Beter? Nog beter? #if gtk praat_writeMenu = gtk_menu_new (); gtk_menu_item_set_submenu (GTK_MENU_ITEM (praat_writeMenuTitle), GTK_WIDGET (praat_writeMenu)); #elif motif praat_writeMenu = XmCreatePulldownMenu (praatP.menuBar, "Save", NULL, 0); XtVaSetValues (praat_writeMenuTitle, XmNsubMenuId, praat_writeMenu, NULL); #endif } } } static void updateDynamicMenu (void) { if (praatP.phase != praat_HANDLING_EVENTS) return; praat_sortActions (); deleteDynamicMenu (); praat_show (); } void praat_addActionScript (const wchar *className1, int n1, const wchar *className2, int n2, const wchar *className3, int n3, const wchar *title, const wchar *after, int depth, const wchar *script) { try { ClassInfo class1 = NULL, class2 = NULL, class3 = NULL; Melder_assert (className1 && className2 && className3 && title && after && script); if (wcslen (className1)) { class1 = Thing_classFromClassName (className1); therror } if (wcslen (className2)) { class2 = Thing_classFromClassName (className2); therror } if (wcslen (className3)) { class3 = Thing_classFromClassName (className3); therror } fixSelectionSpecification (& class1, & n1, & class2, & n2, & class3, & n3); if (wcslen (script) && ! wcslen (title)) Melder_throw ("Command with callback has no title. Classes: ", className1, " ", className2, " ", className3, "."); if (! wcslen (className1)) Melder_throw ("Command \"", title, "\" has no first class."); /* * If the button already exists, remove it. */ long found = lookUpMatchingAction (class1, class2, class3, NULL, title); if (found) { theNumberOfActions --; for (long i = found; i <= theNumberOfActions; i ++) theActions [i] = theActions [i + 1]; } /* * Determine the position of the new command. */ long position; if (wcslen (after)) { /* Search for existing command with same selection. */ long found = lookUpMatchingAction (class1, class2, class3, NULL, after); if (found) { position = found + 1; // after 'after' } else { position = theNumberOfActions + 1; // at end } } else { position = theNumberOfActions + 1; // at end } /* * Increment the command area. */ if (theNumberOfActions >= praat_MAXNUM_LOOSE_COMMANDS) Melder_throw ("Too many actions (maximum is ", praat_MAXNUM_LOOSE_COMMANDS, ")."); theNumberOfActions += 1; /* * Make room for insertion. */ for (long i = theNumberOfActions; i > position; i --) theActions [i] = theActions [i - 1]; memset (& theActions [position], 0, sizeof (struct structPraat_Command)); /* * Insert new command. */ theActions [position]. class1 = class1; theActions [position]. n1 = n1; theActions [position]. class2 = class2; theActions [position]. n2 = n2; theActions [position]. class3 = class3; theActions [position]. n3 = n3; theActions [position]. title = wcslen (title) ? Melder_wcsdup_f (title) : NULL; // allow old-fashioned untitled separators theActions [position]. depth = depth; theActions [position]. callback = wcslen (script) ? DO_RunTheScriptFromAnyAddedMenuCommand : NULL; // NULL for a separator theActions [position]. button = NULL; if (wcslen (script) == 0) { theActions [position]. script = NULL; } else { structMelderFile file = { 0 }; Melder_relativePathToFile (script, & file); theActions [position]. script = Melder_wcsdup_f (Melder_fileToPath (& file)); } theActions [position]. after = wcslen (after) ? Melder_wcsdup_f (after) : NULL; theActions [position]. phase = praatP.phase; if (praatP.phase >= praat_READING_BUTTONS) { static long uniqueID = 0; theActions [position]. uniqueID = ++ uniqueID; } updateDynamicMenu (); } catch (MelderError) { Melder_throw ("Praat: script action not added."); } } void praat_removeAction (ClassInfo class1, ClassInfo class2, ClassInfo class3, const wchar *title) { try { int n1, n2, n3; fixSelectionSpecification (& class1, & n1, & class2, & n2, & class3, & n3); long found = lookUpMatchingAction (class1, class2, class3, NULL, title); if (! found) { Melder_throw ("Action command \"", class1 -> className, class2 ? L" & ": L"", class2 -> className, class3 ? L" & ": L"", class3 -> className, ": ", title, "\" not found."); } Melder_free (theActions [found]. title); theNumberOfActions --; for (long i = found; i <= theNumberOfActions; i ++) theActions [i] = theActions [i + 1]; } catch (MelderError) { Melder_throw ("Praat: action not removed."); } } void praat_removeAction_classNames (const wchar_t *className1, const wchar_t *className2, const wchar_t *className3, const wchar_t *title) { try { ClassInfo class1 = NULL, class2 = NULL, class3 = NULL; Melder_assert (className1 && className2 && className3 && title); if (wcslen (className1)) { class1 = Thing_classFromClassName (className1); therror } if (wcslen (className2)) { class2 = Thing_classFromClassName (className2); therror } if (wcslen (className3)) { class3 = Thing_classFromClassName (className3); therror } praat_removeAction (class1, class2, class3, title); therror updateDynamicMenu (); } catch (MelderError) { Melder_throw ("Praat: action not removed."); } } void praat_hideAction (ClassInfo class1, ClassInfo class2, ClassInfo class3, const wchar *title) { try { int n1, n2, n3; fixSelectionSpecification (& class1, & n1, & class2, & n2, & class3, & n3); long found = lookUpMatchingAction (class1, class2, class3, NULL, title); if (! found) { Melder_throw ("Praat: action command \"", class1 ? class1 -> className : NULL, class2 ? " & ": NULL, class2 ? class2 -> className : NULL, class3 ? " & ": NULL, class3 ? class3 -> className : NULL, ": ", title, "\" not found."); } if (! theActions [found]. hidden) { theActions [found]. hidden = TRUE; if (praatP.phase >= praat_READING_BUTTONS) theActions [found]. toggled = ! theActions [found]. toggled; updateDynamicMenu (); } } catch (MelderError) { Melder_throw ("Praat: action not hidden."); } } void praat_hideAction_classNames (const wchar_t *className1, const wchar_t *className2, const wchar_t *className3, const wchar_t *title) { try { ClassInfo class1 = NULL, class2 = NULL, class3 = NULL; Melder_assert (className1 && className2 && className3 && title); if (wcslen (className1)) { class1 = Thing_classFromClassName (className1); therror } if (wcslen (className2)) { class2 = Thing_classFromClassName (className2); therror } if (wcslen (className3)) { class3 = Thing_classFromClassName (className3); therror } praat_hideAction (class1, class2, class3, title); therror } catch (MelderError) { Melder_throw ("Praat: action not hidden."); } } void praat_showAction (ClassInfo class1, ClassInfo class2, ClassInfo class3, const wchar *title) { try { int n1, n2, n3; fixSelectionSpecification (& class1, & n1, & class2, & n2, & class3, & n3); long found = lookUpMatchingAction (class1, class2, class3, NULL, title); if (! found) { Melder_throw ("Action command \"", class1 ? class1 -> className : NULL, class2 ? L" & ": NULL, class2 ? class2 -> className : NULL, class3 ? L" & ": NULL, class3 ? class3 -> className : NULL, L": ", title, "\" not found."); } if (theActions [found]. hidden) { theActions [found]. hidden = FALSE; if (praatP.phase >= praat_READING_BUTTONS) theActions [found]. toggled = ! theActions [found]. toggled; updateDynamicMenu (); } } catch (MelderError) { Melder_throw ("Praat: action not shown."); } } void praat_showAction_classNames (const wchar *className1, const wchar *className2, const wchar *className3, const wchar *title) { try { ClassInfo class1 = NULL, class2 = NULL, class3 = NULL; Melder_assert (className1 && className2 && className3 && title); if (wcslen (className1)) { class1 = Thing_classFromClassName (className1); therror } if (wcslen (className2)) { class2 = Thing_classFromClassName (className2); therror } if (wcslen (className3)) { class3 = Thing_classFromClassName (className3); therror } praat_showAction (class1, class2, class3, title); therror } catch (MelderError) { Melder_throw ("Praat: action not shown."); } } static int compareActions (const void *void_me, const void *void_thee) { praat_Command me = (praat_Command) void_me, thee = (praat_Command) void_thee; int compare; compare = wcscmp (my class1 -> className, thy class1 -> className); if (compare) return my class1 == classData ? -1 : thy class1 == classData ? 1 : compare; if (my class2) { if (! thy class2) return 1; compare = wcscmp (my class2 -> className, thy class2 -> className); if (compare) return compare; } else if (thy class2) return -1; if (my class3) { if (! thy class3) return 1; compare = wcscmp (my class3 -> className, thy class3 -> className); if (compare) return compare; } else if (thy class3) return -1; if (my sortingTail < thy sortingTail) return -1; return 1; } void praat_sortActions (void) { for (long i = 1; i <= theNumberOfActions; i ++) theActions [i]. sortingTail = i; qsort (& theActions [1], theNumberOfActions, sizeof (struct structPraat_Command), compareActions); } static const wchar *numberString (int number) { return number == 1 ? L"one" : number == 2 ? L"two" : number == 3 ? L"three" : L"any number of"; } static const wchar *classString (ClassInfo klas) { return klas == classData ? L"" : klas -> className; } static const wchar *objectString (int number) { return number == 1 ? L"object" : L"objects"; } static bool allowExecutionHook (void *closure) { void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *) = (void (*) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)) closure; Melder_assert (sizeof (callback) == sizeof (void *)); long numberOfMatchingCallbacks = 0, firstMatchingCallback = 0; for (long i = 1; i <= theNumberOfActions; i ++) { praat_Command me = & theActions [i]; if (my callback == callback) { int sel1, sel2 = 0, sel3 = 0, sel4 = 0; if (! my class1) Melder_throw ("No class1???"); numberOfMatchingCallbacks += 1; if (! firstMatchingCallback) firstMatchingCallback = i; sel1 = my class1 == classData ? theCurrentPraatObjects -> totalSelection : praat_selection (my class1); if (sel1 == 0) continue; if (my class2 && (sel2 = praat_selection (my class2)) == 0) continue; if (my class3 && (sel3 = praat_selection (my class3)) == 0) continue; if (my class4 && (sel4 = praat_selection (my class4)) == 0) continue; if (sel1 + sel2 + sel3 + sel4 != theCurrentPraatObjects -> totalSelection) continue; if ((my n1 && sel1 != my n1) || (my n2 && sel2 != my n2) || (my n3 && sel3 != my n3) || (my n4 && sel4 != my n4)) continue; return true; // found a matching action } } if (numberOfMatchingCallbacks == 1) { praat_Command me = & theActions [firstMatchingCallback]; Melder_error_ ("Selection changed! It should be:"); if (my class1) Melder_error_ (" ", numberString (my n1), " ", classString (my class1), " ", objectString (my n1)); if (my class2) Melder_error_ (" ", numberString (my n2), " ", classString (my class2), " ", objectString (my n2)); if (my class3) Melder_error_ (" ", numberString (my n3), " ", classString (my class3), " ", objectString (my n3)); if (my class4) Melder_error_ (" ", numberString (my n4), " ", classString (my class4), " ", objectString (my n4)); throw MelderError (); } else { Melder_throw ("Selection changed!"); } return false; } static void do_menu (I, bool modified) { /* * Convert a Gui callback into a Ui callback, and catch modifier keys and special mouse buttons. * Call that callback! * Catch the error queue for menu commands without dots (...). */ void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *) = (void (*) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)) void_me; for (long i = 1; i <= theNumberOfActions; i ++) { praat_Command me = & theActions [i]; if (my callback == callback) { if (my title != NULL && ! wcsstr (my title, L"...")) { UiHistory_write (L"\n"); UiHistory_write (my title); } Ui_setAllowExecutionHook (allowExecutionHook, (void *) callback); // BUG: one shouldn't assign a function pointer to a void pointer try { callback (NULL, NULL, NULL, my title, modified, NULL); therror } catch (MelderError) { Melder_error_ ("Command \"", my title, "\" not executed."); Melder_flushError (NULL); } Ui_setAllowExecutionHook (NULL, NULL); praat_updateSelection (); return; } if (my callback == DO_RunTheScriptFromAnyAddedMenuCommand && my script == (void *) void_me) { if (my title != NULL && ! wcsstr (my title, L"...")) { UiHistory_write (L"\nexecute "); UiHistory_write (my script); } else { UiHistory_write (L"\nexecute \""); UiHistory_write (my script); UiHistory_write (L"\""); } try { DO_RunTheScriptFromAnyAddedMenuCommand (NULL, my script, NULL, NULL, false, NULL); therror } catch (MelderError) { Melder_error_ ("Command \"", my title, "\" not executed."); Melder_flushError (NULL); } praat_updateSelection (); return; } } } static void cb_menu (GUI_ARGS) { (void) w; bool modified = false; if (call) { #if defined (macintosh) EventRecord *event = (EventRecord *) call; enum { cmdKey = 256, shiftKey = 512, optionKey = 2048, controlKey = 4096 }; modified = event -> what == mouseDown && (event -> modifiers & (cmdKey | shiftKey | optionKey | controlKey)) != 0; #elif defined (_WIN32) modified = false; // TODO: implement #else modified = false; // TODO: implement #endif } do_menu (void_me, modified); } static void gui_button_cb_menu (I, GuiButtonEvent event) { do_menu (void_me, event -> shiftKeyPressed | event -> commandKeyPressed | event -> optionKeyPressed | event -> extraControlKeyPressed); } void praat_actions_show (void) { /* * The selection has changed; * kill the dynamic menu and the write menu. */ if (! theCurrentPraatApplication -> batch) { deleteDynamicMenu (); if (! Melder_backgrounding) { GuiObject_setSensitive (praat_writeMenuTitle, False); if (praat_writeMenuSeparator) GuiObject_hide (praat_writeMenuSeparator); if (praat_dynamicMenu) GuiObject_hide (praat_dynamicMenu); for (long i = theNumberOfActions; i >= 1; i --) { praat_Command me = & theActions [i]; if (! my visible) continue; if (my button) { if (GuiObject_parent (my button) == praat_dynamicMenu) /* Unmanage only level-1 visible buttons. */ GuiObject_hide (my button); else if (my title && (wcsnequ (my title, L"Save ", 5) || wcsnequ (my title, L"Write ", 6) || wcsnequ (my title, L"Append to ", 10))) GuiObject_hide (my button); } } /* * BUG: Despite all these precautions, * creating and removing a lot of objects from a script * still leaves several seconds of flashing after the script finishes. * Events remaining? */ } /* Determine the visibility and sensitivity of all the actions. */ if (theCurrentPraatObjects -> totalSelection != 0 && ! Melder_backgrounding) GuiObject_setSensitive (praat_writeMenuTitle, True); } for (long i = 1; i <= theNumberOfActions; i ++) { int sel1 = 0, sel2 = 0, sel3 = 0, sel4 = 0; int n1 = theActions [i]. n1, n2 = theActions [i]. n2, n3 = theActions [i]. n3, n4 = theActions [i]. n4; /* Clean up from previous selection. */ theActions [i]. visible = FALSE; theActions [i]. executable = FALSE; /* Match the actually selected classes with the selection required for this visibility. */ if (! theActions [i]. class1) continue; /* At least one class selected. */ sel1 = theActions [i]. class1 == classData ? theCurrentPraatObjects -> totalSelection : praat_selection (theActions [i]. class1); if (sel1 == 0) continue; if (theActions [i]. class2 && (sel2 = praat_selection (theActions [i]. class2)) == 0) continue; if (theActions [i]. class3 && (sel3 = praat_selection (theActions [i]. class3)) == 0) continue; if (theActions [i]. class4 && (sel4 = praat_selection (theActions [i]. class4)) == 0) continue; if (sel1 + sel2 + sel3 + sel4 != theCurrentPraatObjects -> totalSelection) continue; /* Other classes selected? Do not show. */ theActions [i]. visible = ! theActions [i]. hidden; /* Match the actually selected objects with the selection required for this action. */ if (! theActions [i]. callback) continue; /* Separators are not executable. */ if ((n1 && sel1 != n1) || (n2 && sel2 != n2) || (n3 && sel3 != n3) || (n4 && sel4 != n4)) continue; theActions [i]. executable = TRUE; } /* Create a new column of buttons in the dynamic menu. */ if (! theCurrentPraatApplication -> batch && ! Melder_backgrounding) { GuiObject currentSubmenu1 = NULL, currentSubmenu2 = NULL; int writeMenuGoingToSeparate = FALSE; if (! praat_dynamicMenu) { #if gtk praat_dynamicMenu = gtk_vbutton_box_new (); gtk_button_box_set_layout (GTK_BUTTON_BOX (praat_dynamicMenu), GTK_BUTTONBOX_START); GuiObject viewport = gtk_bin_get_child (GTK_BIN (praat_dynamicMenuWindow)); gtk_container_add (GTK_CONTAINER (viewport), GTK_WIDGET (praat_dynamicMenu)); #elif motif praat_dynamicMenu = XmCreateRowColumn (praat_dynamicMenuWindow, "menu", NULL, 0); #endif } for (long i = 1; i <= theNumberOfActions; i ++) { /* Add buttons or make existing buttons sensitive (executable). */ praat_Command me = & theActions [i]; if (my depth == 0) currentSubmenu1 = NULL, currentSubmenu2 = NULL; /* Prevent attachment of later deep actions to earlier submenus after removal of label. */ if (my depth == 1) currentSubmenu2 = NULL; /* Prevent attachment of later deep actions to earlier submenus after removal of label. */ if (! my visible) continue; if (my callback) { /* Apparently a true command: create a button in the dynamic menu. * If it is a subcommand (depth > 0), put it in the current submenu, * but only if this exists (umbrella against stray submenu specifications). */ if (! my button) { GuiObject parent = my depth > 1 && currentSubmenu2 ? currentSubmenu2 : my depth > 0 && currentSubmenu1 ? currentSubmenu1 : praat_dynamicMenu; if (wcsnequ (my title, L"Save ", 5) || wcsnequ (my title, L"Write ", 6) || wcsnequ (my title, L"Append to ", 10)) { parent = praat_writeMenu; if (! praat_writeMenuSeparator) { if (writeMenuGoingToSeparate) praat_writeMenuSeparator = GuiMenu_addSeparator (parent); else if (wcsequ (my title, L"Save as binary file...")) writeMenuGoingToSeparate = TRUE; } } if (parent == praat_dynamicMenu) { my button = GuiButton_createShown (praat_dynamicMenu, #if defined (_WIN32) 4, BUTTON_WIDTH - 16, Gui_AUTOMATIC, Gui_AUTOMATIC, #elif defined (macintosh) /* * Keep 5 pixels distance on both sides for shadow. */ 9, BUTTON_WIDTH - 16, Gui_AUTOMATIC, Gui_AUTOMATIC, #else Gui_AUTOMATIC, Gui_AUTOMATIC, Gui_AUTOMATIC, Gui_AUTOMATIC, #endif my title, gui_button_cb_menu, my callback == DO_RunTheScriptFromAnyAddedMenuCommand ? (void *) my script : (void *) my callback, ( my executable ? 0 : GuiButton_INSENSITIVE ) | ( my attractive ? GuiButton_ATTRACTIVE : 0 )); #if gtk /* Dit soort onzin zou eigenlijk in GuiButton moeten */ gtk_button_set_alignment (GTK_BUTTON (my button), 0.0f, 0.5f); #endif } else { my button = GuiMenu_addItem (parent, my title, ( my executable ? 0 : GuiMenu_INSENSITIVE ), cb_menu, my callback == DO_RunTheScriptFromAnyAddedMenuCommand ? (void *) my script : (void *) my callback); } } else if (wcsnequ (my title, L"Save ", 5) || wcsnequ (my title, L"Write ", 6) || wcsnequ (my title, L"Append to ", 10)) { if (writeMenuGoingToSeparate) { if (! praat_writeMenuSeparator) praat_writeMenuSeparator = GuiMenu_addSeparator (praat_writeMenu); GuiObject_show (praat_writeMenuSeparator); } else if (wcsequ (my title, L"Save as binary file...")) { writeMenuGoingToSeparate = TRUE; } #if motif GuiObject_show (my button); #endif GuiObject_setSensitive (my button, my executable); } else { GuiObject_setSensitive (my button, my executable); if (GuiObject_parent (my button) == praat_dynamicMenu) GuiObject_show (my button); } } else if (i == theNumberOfActions || theActions [i + 1]. depth == 0) { /* * Apparently a labelled separator. */ if (! my button) { my button = GuiLabel_createShown (praat_dynamicMenu, 0, BUTTON_WIDTH - 20, Gui_AUTOMATIC, Gui_AUTOMATIC, my title, 0); } else { if (GuiObject_parent (my button) == praat_dynamicMenu) GuiObject_show (my button); } } else if (my title == NULL || my title [0] == '-') { /* * Apparently a separator in a submenu. */ if (currentSubmenu2 || currentSubmenu1) { /* These separators are not shown in a flattened menu. */ if (! my button) { // RFC: Beter? #if gtk my button = GuiMenu_addSeparator (currentSubmenu2 ? currentSubmenu2 : currentSubmenu1); #elif motif my button = XmCreateSeparator (currentSubmenu2 ? currentSubmenu2 : currentSubmenu1, "separator", NULL, 0); #endif GuiObject_show (my button); } } } else { /* * Apparently a submenu. */ if (! my button) { if (my depth == 0) { #if gtk currentSubmenu1 = GuiMenuBar_addMenu3 (praat_dynamicMenu, my title, 0, & my button); /* Dit soort onzin zou eigenlijk in GuiButton moeten */ gtk_button_set_alignment (GTK_BUTTON (my button), 0.0f, 0.5f); #elif motif GuiObject cascadeButton; my button = XmCreateMenuBar (praat_dynamicMenu, "dynamicSubmenuBar", 0, 0); currentSubmenu1 = GuiMenuBar_addMenu2 (my button, my title, 0, & cascadeButton); #endif #if defined (_WIN32) GuiObject_size (cascadeButton, BUTTON_WIDTH - 24, 19); GuiObject_size (my button, BUTTON_WIDTH - 20, 21); #elif defined (macintosh) GuiObject_size (cascadeButton, BUTTON_WIDTH - 29, 19); GuiObject_size (my button, BUTTON_WIDTH - 25, 22); #endif } else { currentSubmenu2 = GuiMenuBar_addMenu2 (currentSubmenu1 ? currentSubmenu1 : praat_dynamicMenu, my title, 0, & my button); } GuiObject_show (my button); } else { if (GuiObject_parent (my button) == praat_dynamicMenu) GuiObject_show (my button); } } } GuiObject_show (praat_dynamicMenu); } } void praat_actions_createWriteMenu (GuiObject bar) { if (theCurrentPraatApplication -> batch) return; #if gtk praat_writeMenu = GuiMenuBar_addMenu2 (bar, L"Save", GuiMenu_INSENSITIVE, & praat_writeMenuTitle); #elif motif praat_writeMenuTitle = XtVaCreateManagedWidget ("Save", xmCascadeButtonWidgetClass, bar, NULL); praat_writeMenu = XmCreatePulldownMenu (bar, "Save", NULL, 0); // the name is irrelevant XtVaSetValues (praat_writeMenuTitle, XmNsubMenuId, praat_writeMenu, NULL); #endif GuiObject_setSensitive (praat_writeMenuTitle, False); } void praat_actions_init (void) { theActions = Melder_calloc_f (struct structPraat_Command, 1 + praat_MAXNUM_LOOSE_COMMANDS); } void praat_actions_createDynamicMenu (GuiObject form, int width) { if (theCurrentPraatApplication -> batch) return; #if gtk praat_dynamicMenu = gtk_vbutton_box_new (); gtk_button_box_set_layout (GTK_BUTTON_BOX (praat_dynamicMenu), GTK_BUTTONBOX_START); /* Oh yes, we are lazy */ praat_dynamicMenuWindow = gtk_scrolled_window_new (NULL, NULL); gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (praat_dynamicMenuWindow), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); gtk_scrolled_window_add_with_viewport (GTK_SCROLLED_WINDOW (praat_dynamicMenuWindow), GTK_WIDGET (praat_dynamicMenu)); gtk_container_add (GTK_CONTAINER (form), GTK_WIDGET (praat_dynamicMenuWindow)); gtk_widget_set_size_request (GTK_WIDGET (praat_dynamicMenuWindow), width, -1); #elif motif praat_dynamicMenuWindow = XmCreateScrolledWindow (form, "menuWindow", NULL, 0); #if defined (macintosh) XtVaSetValues (praat_dynamicMenuWindow, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, Machine_getMainWindowMenuBarHeight (), XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, -1, XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, -1, XmNwidth, width, NULL); #else XtVaSetValues (praat_dynamicMenuWindow, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, Machine_getMenuBarHeight (), XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, -3, XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, -3, XmNwidth, width, NULL); #endif praat_dynamicMenu = XmCreateRowColumn (praat_dynamicMenuWindow, "menu", NULL, 0); #endif GuiObject_show (praat_dynamicMenu); GuiObject_show (praat_dynamicMenuWindow); } void praat_saveAddedActions (FILE *f) { long maxID = 0; for (long iaction = 1; iaction <= theNumberOfActions; iaction ++) { if (theActions [iaction]. uniqueID > maxID) maxID = theActions [iaction]. uniqueID; } for (long ident = 1; ident <= maxID; ident ++) for (long iaction = 1; iaction <= theNumberOfActions; iaction ++) { praat_Command me = & theActions [iaction]; if (my uniqueID == ident && ! my hidden && my title) { fwprintf (f, L"Add action command... %ls %d %ls %d %ls %d \"%ls\" \"%ls\" %d %ls\n", my class1 -> className, my n1, my class2 ? my class2 -> className : L"\"\"", my n2, my class3 ? my class3 -> className : L"\"\"", my n3, my title, my after ? my after : L"", my depth, my script ? my script : L""); break; } } for (long iaction = 1; iaction <= theNumberOfActions; iaction ++) { praat_Command me = & theActions [iaction]; if (my toggled && my title && ! my uniqueID && ! my script) fwprintf (f, L"%ls action command... %ls %ls %ls %ls\n", my hidden ? L"Hide" : L"Show", my class1 -> className, my class2 ? my class2 -> className : L"\"\"", my class3 ? my class3 -> className : L"\"\"", my title); } } int praat_doAction (const wchar *command, const wchar *arguments, Interpreter interpreter) { long i = 1; while (i <= theNumberOfActions && (! theActions [i]. executable || wcscmp (theActions [i]. title, command))) i ++; if (i > theNumberOfActions) return 0; /* Not found. */ theActions [i]. callback (NULL, arguments, interpreter, command, false, NULL); therror return 1; } long praat_getNumberOfActions (void) { return theNumberOfActions; } praat_Command praat_getAction (long i) { return i < 0 || i > theNumberOfActions ? NULL : & theActions [i]; } void praat_background (void) { if (Melder_batch) return; if (Melder_backgrounding) return; deleteDynamicMenu (); praat_list_background (); Melder_backgrounding = true; if (! praatP.dontUsePictureWindow) praat_picture_background (); } void praat_foreground (void) { if (Melder_batch) return; if (! Melder_backgrounding) return; Melder_backgrounding = false; praat_list_foreground (); praat_show (); if (! praatP.dontUsePictureWindow) praat_picture_foreground (); } /* End of file praat_actions.c */ sources_5316/sys/ManPages.h0000644000176700017670000000340111621236562014407 0ustar paulpaul#ifndef _ManPages_h_ #define _ManPages_h_ /* ManPages.h * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPage.h" #include "Collection.h" Thing_define (ManPages, Data) { // new data: public: Ordered pages; const wchar **titles; int ground, dynamic, executable; structMelderDir rootDirectory; // overridden methods: protected: virtual void v_destroy (); virtual void v_readText (MelderReadText text); }; ManPages ManPages_create (void); void ManPages_addPage (ManPages me, const wchar *title, const wchar *author, long date, struct structManPage_Paragraph paragraphs []); /* All string and struct arguments must be statically allocated and not change after adding them to the ManPages. */ long ManPages_lookUp (ManPages me, const wchar_t *title); void ManPages_writeOneToHtmlFile (ManPages me, long ipage, MelderFile file); void ManPages_writeAllToHtmlDir (ManPages me, const wchar *dirPath); long ManPages_uniqueLinksHither (ManPages me, long ipage); const wchar **ManPages_getTitles (ManPages me, long *numberOfTitles); /* End of file ManPages.h */ #endif sources_5316/sys/Script.h0000644000176700017670000000172511621526445014171 0ustar paulpaul#ifndef _Script_h_ #define _Script_h_ /* Script.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" Thing_define (Script, Data) { // new data: public: structMelderFile file; }; Script Script_createFromFile (MelderFile file); /* End of file Script.h */ #endif sources_5316/sys/oo_READ_BINARY.h0000644000176700017670000001240111724667353015202 0ustar paulpaul/* oo_READ_BINARY.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) \ x = binget##storage (f); therror #define oo_ARRAY(type,storage,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (int i = 0; i < n; i ++) { \ x [i] = binget##storage (f); \ } #define oo_SET(type,storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) { \ x [i] = binget##storage (f); \ } #define oo_VECTOR(type,storage,x,min,max) \ if (max >= min) { \ x = NUMvector_readBinary_##storage (min, max, f); therror \ } #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) \ if (row2 >= row1 && col2 >= col1) { \ x = NUMmatrix_readBinary_##storage (row1, row2, col1, col2, f); therror \ } #define oo_ENUMx(type,storage,Type,x) \ x = binget##storage (f, Type##_MIN, Type##_MAX, L"" #Type); #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (int i = 0; i < n; i ++) { \ x [i] = binget##storage (f, Type##_MIN, Type##_MAX, L"" #Type); \ } #define oo_ENUMx_SET(type,storage,Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) { \ x [i] = binget##storage (f, Type##_MIN, Type##_MAX, L"" #Type); \ } #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) \ if (max >= min) { \ x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) { \ x [i] = binget##storage (f, Type##_MIN, Type##_MAX, L"" #Type); \ } #define oo_STRINGx(storage,x) \ x = binget##storage (f); therror #define oo_STRINGx_ARRAY(storage,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (int i = 0; i < n; i ++) { \ x [i] = binget##storage (f); \ } #define oo_STRINGx_SET(storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) { \ x [i] = binget##storage (f); \ } #define oo_STRINGx_VECTOR(storage,x,min,max) \ if (max >= min) { \ x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) { \ x [i] = binget##storage (f); \ } \ } #define oo_STRUCT(Type,x) \ x. readBinary (f); therror #define oo_STRUCT_ARRAY(Type,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (int i = 0; i < n; i ++) { \ x [i]. readBinary (f); therror \ } #define oo_STRUCT_SET(Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) { \ x [i]. readBinary (f); therror \ } #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ if (max >= min) { \ x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) { \ x [i]. readBinary (f); therror \ } \ } #define oo_OBJECT(Class,version,x) \ if (bingetex (f)) { \ long saveVersion = Thing_version; \ x = Thing_new (Class); \ Thing_version = version; \ x -> v_readBinary (f); therror \ Thing_version = saveVersion; \ } #define oo_COLLECTION(Class,x,ItemClass,version) \ { \ long n = bingeti4 (f); \ x = Class##_create (); therror \ for (long i = 1; i <= n; i ++) { \ long saveVersion = Thing_version; \ auto##ItemClass item = (ItemClass) Thing_new (ItemClass); \ Thing_version = version; \ item.peek() -> v_readBinary (f); therror \ Thing_version = saveVersion; \ Collection_addItem (x, item.transfer()); \ } \ } #define oo_FILE(x) #define oo_DIR(x) #define oo_DEFINE_STRUCT(Type) \ void struct##Type :: readBinary (FILE *f) { \ int localVersion = Thing_version; (void) localVersion; #define oo_END_STRUCT(Type) \ } #define oo_DEFINE_CLASS(Class,Parent) \ void struct##Class :: v_readBinary (FILE *f) { \ int localVersion = Thing_version; (void) localVersion; \ if (localVersion > this -> classInfo -> version) \ Melder_throw ("The format of this file is too new. Download a newer version of Praat."); \ Class##_Parent :: v_readBinary (f); therror #define oo_END_CLASS(Class) \ } #define oo_IF(condition) \ if (condition) { #define oo_ENDIF \ } #define oo_FROM(from) \ if (localVersion >= from) { #define oo_ENDFROM \ } #define oo_VERSION(version) \ Thing_version = version; #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 0 #define oo_READING 1 #define oo_READING_TEXT 0 #define oo_READING_BINARY 1 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 0 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_READ_BINARY.h */ sources_5316/sys/GuiMenu.cpp0000644000176700017670000003774211753742334014644 0ustar paulpaul/* GuiMenu.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2002/03/11 Mach * pb 2004/10/21 on Unix, Ctrl becomes the command key * pb 2007/06/09 wchar_t * pb 2007/12/13 Gui * sdk 2008/02/08 GTK * sdk 2008/03/24 GTK * pb 2010/11/28 removed explicit Motif * pb 2011/04/06 C++ */ #include "GuiP.h" #define _motif_SHIFT_MASK 1 #define _motif_COMMAND_MASK 2 #define _motif_OPTION_MASK 4 GuiObject GuiMenuBar_addMenu (GuiObject bar, const wchar_t *title, long flags) { GuiObject menu = NULL, menuTitle; menu = GuiMenuBar_addMenu2 (bar, title, flags, & menuTitle); return menu; } GuiObject GuiMenuBar_addMenu2 (GuiObject bar, const wchar_t *title, long flags, GuiObject *menuTitle) { GuiObject menu; #if gtk *menuTitle = gtk_menu_item_new_with_label (Melder_peekWcsToUtf8 (title)); menu = gtk_menu_new (); GtkAccelGroup *ag = GTK_IS_MENU_BAR (bar) ? (GtkAccelGroup *) g_object_get_data (G_OBJECT (bar), "accel-group") : (GtkAccelGroup *) gtk_menu_get_accel_group (GTK_MENU (bar)); gtk_menu_set_accel_group (GTK_MENU (menu), ag); if (flags & GuiMenu_INSENSITIVE) gtk_widget_set_sensitive (GTK_WIDGET (menu), FALSE); gtk_menu_item_set_submenu (GTK_MENU_ITEM (*menuTitle), GTK_WIDGET (menu)); gtk_menu_shell_append (GTK_MENU_SHELL (bar), GTK_WIDGET (*menuTitle)); gtk_widget_show (GTK_WIDGET (menu)); gtk_widget_show (GTK_WIDGET (*menuTitle)); #elif win *menuTitle = XmCreateCascadeButton (bar, Melder_peekWcsToUtf8 (title), NULL, 0); if (wcsequ (title, L"Help")) XtVaSetValues (bar, XmNmenuHelpWidget, *menuTitle, NULL); menu = XmCreatePulldownMenu (bar, Melder_peekWcsToUtf8 (title), NULL, 0); if (flags & GuiMenu_INSENSITIVE) XtSetSensitive (menu, False); XtVaSetValues (*menuTitle, XmNsubMenuId, menu, NULL); XtManageChild (*menuTitle); #elif mac #if useCarbon *menuTitle = XmCreateCascadeButton (bar, Melder_peekWcsToUtf8 (title), NULL, 0); if (wcsequ (title, L"Help")) XtVaSetValues (bar, XmNmenuHelpWidget, *menuTitle, NULL); menu = XmCreatePulldownMenu (bar, Melder_peekWcsToUtf8 (title), NULL, 0); if (flags & GuiMenu_INSENSITIVE) XtSetSensitive (menu, False); XtVaSetValues (*menuTitle, XmNsubMenuId, menu, NULL); XtManageChild (*menuTitle); #else #endif #endif return menu; } #if gtk static void set_position (GtkMenu *menu, gint *px, gint *py, gpointer data) { gint w, h; GtkWidget *button = (GtkWidget *) g_object_get_data (G_OBJECT (menu), "button"); if (GTK_WIDGET (menu) -> requisition. width < button->allocation.width) gtk_widget_set_size_request (GTK_WIDGET (menu), button->allocation.width, -1); gdk_window_get_origin (button->window, px, py); *px += button->allocation.x; *py += button->allocation.y + button->allocation.height; /* Dit is vreemd */ } static gint button_press (GtkWidget *widget, GdkEvent *event) { gint w, h; GtkWidget *button = (GtkWidget *) g_object_get_data (G_OBJECT (widget), "button"); /* gdk_window_get_size (button->window, &w, &h); gtk_widget_set_usize (widget, w, 0);*/ if (event->type == GDK_BUTTON_PRESS) { GdkEventButton *bevent = (GdkEventButton *) event; gtk_menu_popup (GTK_MENU (widget), NULL, NULL, (GtkMenuPositionFunc) set_position, NULL, bevent->button, bevent->time); return TRUE; } return FALSE; } GuiObject GuiMenuBar_addMenu3 (GuiObject parent, const wchar_t *title, long flags, GuiObject *button) { GuiObject menu; menu = gtk_menu_new (); *button = gtk_button_new_with_label (Melder_peekWcsToUtf8 (title)); g_signal_connect_object (G_OBJECT (*button), "event", GTK_SIGNAL_FUNC (button_press), G_OBJECT (menu), G_CONNECT_SWAPPED); g_object_set_data (G_OBJECT (menu), "button", *button); if (flags & GuiMenu_INSENSITIVE) gtk_widget_set_sensitive (GTK_WIDGET (menu), FALSE); gtk_menu_attach_to_widget (GTK_MENU (menu), GTK_WIDGET (*button), NULL); /* TODO: Free button? */ gtk_container_add (GTK_CONTAINER (parent), GTK_WIDGET (*button)); gtk_widget_show (GTK_WIDGET (menu)); gtk_widget_show (GTK_WIDGET (*button)); return menu; } #endif #if gtk #include static GSList *group = NULL; #endif void GuiMenuItem_check (GuiObject menuItem, bool check) { Melder_assert (menuItem != NULL); #if gtk gulong handlerId = (gulong) g_object_get_data (G_OBJECT (menuItem), "handlerId"); void (*commandCallback) (GuiObject, XtPointer, XtPointer) = (void (*) (GuiObject, XtPointer, XtPointer)) g_object_get_data (G_OBJECT (menuItem), "commandCallback"); void *commandClosure = g_object_get_data (G_OBJECT (menuItem), "commandClosure"); //Melder_casual ("GuiMenuItem_check %ld %ld %ld", handlerId, commandCallback, commandClosure); g_signal_handler_disconnect (G_OBJECT (menuItem), handlerId); gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM (menuItem), check); handlerId = g_signal_connect (G_OBJECT (menuItem), "toggled", G_CALLBACK (commandCallback), (gpointer) commandClosure); g_object_set_data (G_OBJECT (menuItem), "handlerId", (gpointer) handlerId); #elif win XmToggleButtonGadgetSetState (menuItem, check, False); #elif mac #if useCarbon XmToggleButtonGadgetSetState (menuItem, check, False); #else #endif #endif } #if win || mac && useCarbon static void NativeMenuItem_setText (GuiObject me) { int acc = my motiff.pushButton.acceleratorChar, modifiers = my motiff.pushButton.acceleratorModifiers; #if win static MelderString title = { 0 }; if (acc == 0) { MelderString_copy (& title, _GuiWin_expandAmpersands (my name)); } else { static const wchar_t *keyStrings [256] = { 0, L"<-", L"->", L"Up", L"Down", L"PAUSE", L"Del", L"Ins", L"Backspace", L"Tab", L"LineFeed", L"Home", L"End", L"Enter", L"PageUp", L"PageDown", L"Esc", L"F1", L"F2", L"F3", L"F4", L"F5", L"F6", L"F7", L"F8", L"F9", L"F10", L"F11", L"F12", 0, 0, 0, L"Space", L"!", L"\"", L"#", L"$", L"%", L"&", L"\'", L"(", L")", L"*", L"+", L",", L"-", L".", L"/", L"0", L"1", L"2", L"3", L"4", L"5", L"6", L"7", L"8", L"9", L":", L";", L"<", L"=", L">", L"?", L"@", L"A", L"B", L"C", L"D", L"E", L"F", L"G", L"H", L"I", L"J", L"K", L"L", L"M", L"N", L"O", L"P", L"Q", L"R", L"S", L"T", L"U", L"V", L"W", L"X", L"Y", L"Z", L"[", L"\\", L"]", L"^", L"_", L"`", L"a", L"b", L"c", L"d", L"e", L"f", L"g", L"h", L"i", L"j", L"k", L"l", L"m", L"n", L"o", L"p", L"q", L"r", L"s", L"t", L"u", L"v", L"w", L"x", L"y", L"z", L"{", L"|", L"}", L"~", L"Del", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, L"[", L"]", L",", L"?", L".", L"\\", L";", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, L"-", L"`", L"=", L"\'", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; const wchar_t *keyString = keyStrings [acc] ? keyStrings [acc] : L"???"; MelderString_empty (& title); MelderString_append (&title, _GuiWin_expandAmpersands (my name), L"\t", modifiers & _motif_COMMAND_MASK ? L"Ctrl-" : NULL, modifiers & _motif_OPTION_MASK ? L"Alt-" : NULL, modifiers & _motif_SHIFT_MASK ? L"Shift-" : NULL, keyString); } ModifyMenu (my nat.entry.handle, my nat.entry.id, MF_BYCOMMAND | MF_STRING, my nat.entry.id, title.string); #elif mac static int theGlyphs [1+31] = { 0, kMenuLeftArrowDashedGlyph, kMenuRightArrowDashedGlyph, kMenuUpArrowDashedGlyph, kMenuDownwardArrowDashedGlyph, 0, kMenuDeleteRightGlyph, 0, kMenuDeleteLeftGlyph, kMenuTabRightGlyph, 0, 0, 0, kMenuReturnGlyph, kMenuPageUpGlyph, kMenuPageDownGlyph, kMenuEscapeGlyph, kMenuF1Glyph, kMenuF2Glyph, kMenuF3Glyph, kMenuF4Glyph, kMenuF5Glyph, kMenuF6Glyph, kMenuF7Glyph, kMenuF8Glyph, kMenuF9Glyph, kMenuF10Glyph, kMenuF11Glyph, kMenuF12Glyph, 0, 0, 0 }; SetMenuItemTextWithCFString (my nat.entry.handle, my nat.entry.item, (CFStringRef) Melder_peekWcsToCfstring (my name)); if (acc > 32) { SetItemCmd (my nat.entry.handle, my nat.entry.item, acc); } else { Melder_assert (acc > 0 && acc < 32); SetItemCmd (my nat.entry.handle, my nat.entry.item, ' '); /* Funny that this should be needed. */ SetMenuItemKeyGlyph (my nat.entry.handle, my nat.entry.item, theGlyphs [acc]); } SetMenuItemModifiers (my nat.entry.handle, my nat.entry.item, ( modifiers & _motif_OPTION_MASK ? kMenuOptionModifier : 0 ) + ( modifiers & _motif_SHIFT_MASK ? kMenuShiftModifier : 0 ) + ( modifiers & _motif_COMMAND_MASK ? 0 : kMenuNoCommandModifier )); #endif } #endif GuiObject GuiMenu_addItem (GuiObject menu, const wchar_t *title, long flags, void (*commandCallback) (GuiObject, XtPointer, XtPointer), const void *closure) { Boolean toggle = flags & (GuiMenu_CHECKBUTTON | GuiMenu_RADIO_FIRST | GuiMenu_RADIO_NEXT | GuiMenu_TOGGLE_ON) ? True : False; GuiObject button; int accelerator = flags & 127; Melder_assert (title != NULL); #if gtk if (toggle) { if (flags & (GuiMenu_RADIO_FIRST)) group = NULL; if (flags & (GuiMenu_RADIO_FIRST | GuiMenu_RADIO_NEXT)) { button = gtk_radio_menu_item_new_with_label (group, Melder_peekWcsToUtf8 (title)); group = gtk_radio_menu_item_get_group (GTK_RADIO_MENU_ITEM (button)); //Melder_casual ("Created a radio menu item with title %ls, group %ld", title, group); } else { button = gtk_check_menu_item_new_with_label (Melder_peekWcsToUtf8 (title)); } } else { button = gtk_menu_item_new_with_label (Melder_peekWcsToUtf8 (title)); } gtk_menu_shell_append (GTK_MENU_SHELL (menu), GTK_WIDGET (button)); #elif win button = XtVaCreateManagedWidget (Melder_peekWcsToUtf8 (title), toggle ? xmToggleButtonGadgetClass : xmPushButtonGadgetClass, menu, NULL); #elif mac #if useCarbon button = XtVaCreateManagedWidget (Melder_peekWcsToUtf8 (title), toggle ? xmToggleButtonGadgetClass : xmPushButtonGadgetClass, menu, NULL); #else #endif #endif Melder_assert (button != NULL); if (flags & GuiMenu_INSENSITIVE) GuiObject_setSensitive (button, false); if (flags & GuiMenu_TOGGLE_ON) #if gtk gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM (button), TRUE); #elif win XmToggleButtonGadgetSetState (button, True, False); #elif mac #if useCarbon XmToggleButtonGadgetSetState (button, True, False); #else #endif #endif if (accelerator) { /* * For printable characters, the Command key is assumed. */ if (accelerator >= 32) flags |= GuiMenu_COMMAND; #if gtk static const guint acceleratorKeys [] = { 0, GDK_Left, GDK_Right, GDK_Up, GDK_Down, GDK_Pause, GDK_Delete, GDK_Insert, GDK_BackSpace, GDK_Tab, GDK_Return, GDK_Home, GDK_End, GDK_Return, GDK_Page_Up, GDK_Page_Down, GDK_Escape, GDK_F1, GDK_F2, GDK_F3, GDK_F4, GDK_F5, GDK_F6, GDK_F7, GDK_F8, GDK_F9, GDK_F10, GDK_F11, GDK_F12, 0, 0, 0 }; GdkModifierType modifiers = (GdkModifierType) 0; if (flags & GuiMenu_COMMAND) modifiers = (GdkModifierType) (modifiers | GDK_CONTROL_MASK); if (flags & GuiMenu_SHIFT) modifiers = (GdkModifierType) (modifiers | GDK_SHIFT_MASK); if (flags & GuiMenu_OPTION) modifiers = (GdkModifierType) (modifiers | GDK_MOD1_MASK); guint key; if (accelerator < 32) { key = acceleratorKeys [accelerator]; } else { // gdk key symbols in the ASCII range are equal to ASCII key = accelerator; } GtkAccelGroup *ag = gtk_menu_get_accel_group (GTK_MENU (menu)); if (key != 0) gtk_widget_add_accelerator (GTK_WIDGET (button), toggle ? "toggled" : "activate", ag, key, modifiers, GTK_ACCEL_VISIBLE); #elif win int modifiers = 0; if (flags & GuiMenu_COMMAND) modifiers |= _motif_COMMAND_MASK; if (flags & GuiMenu_SHIFT) modifiers |= _motif_SHIFT_MASK; if (flags & GuiMenu_OPTION) modifiers |= _motif_OPTION_MASK; if (accelerator > 0 && accelerator < 32) { button -> shell -> motiff.shell.lowAccelerators [modifiers] |= 1 << accelerator; } else if (accelerator == '?' || accelerator == '{' || accelerator == '}' || accelerator == '\"' || accelerator == '<' || accelerator == '>' || accelerator == '|' || accelerator == '_' || accelerator == '+' || accelerator == '~') { modifiers |= _motif_SHIFT_MASK; } button -> motiff.pushButton.acceleratorChar = accelerator; button -> motiff.pushButton.acceleratorModifiers = modifiers; NativeMenuItem_setText (button); #elif mac #if useCarbon int modifiers = 0; if (flags & GuiMenu_COMMAND) modifiers |= _motif_COMMAND_MASK; if (flags & GuiMenu_SHIFT) modifiers |= _motif_SHIFT_MASK; if (flags & GuiMenu_OPTION) modifiers |= _motif_OPTION_MASK; if (accelerator > 0 && accelerator < 32) { button -> shell -> motiff.shell.lowAccelerators [modifiers] |= 1 << accelerator; } else if (accelerator == '?' || accelerator == '{' || accelerator == '}' || accelerator == '\"' || accelerator == '<' || accelerator == '>' || accelerator == '|' || accelerator == '_' || accelerator == '+' || accelerator == '~') { modifiers |= _motif_SHIFT_MASK; } button -> motiff.pushButton.acceleratorChar = accelerator; button -> motiff.pushButton.acceleratorModifiers = modifiers; NativeMenuItem_setText (button); #else #endif #endif } #if mac && useCarbon if (flags & GuiMenu_ATTRACTIVE) { //Melder_casual ("attractive!"); SetItemStyle (button -> nat.entry.handle, button -> nat.entry.item, bold); } #endif #if gtk if (commandCallback != NULL) { if (flags == GuiMenu_TAB) { GtkWidget *shell = gtk_widget_get_toplevel (gtk_menu_get_attach_widget (GTK_MENU (menu))); //Melder_casual ("tab set in window %ld", shell); g_object_set_data (G_OBJECT (shell), "tabCallback", (gpointer) commandCallback); g_object_set_data (G_OBJECT (shell), "tabClosure", (gpointer) closure); } else if (flags == (GuiMenu_TAB | GuiMenu_SHIFT)) { GtkWidget *shell = gtk_widget_get_toplevel (gtk_menu_get_attach_widget (GTK_MENU (menu))); //Melder_casual ("shift-tab set in window %ld", shell); g_object_set_data (G_OBJECT (shell), "shiftTabCallback", (gpointer) commandCallback); g_object_set_data (G_OBJECT (shell), "shiftTabClosure", (gpointer) closure); } else { gulong handlerId = g_signal_connect (G_OBJECT (button), toggle ? "toggled" : "activate", G_CALLBACK (commandCallback), (gpointer) closure); g_object_set_data (G_OBJECT (button), "handlerId", (gpointer) handlerId); g_object_set_data (G_OBJECT (button), "commandCallback", (gpointer) commandCallback); g_object_set_data (G_OBJECT (button), "commandClosure", (gpointer) closure); } } else { gtk_widget_set_sensitive (GTK_WIDGET (button), FALSE); } gtk_widget_show (GTK_WIDGET (button)); #elif win XtAddCallback (button, toggle ? XmNvalueChangedCallback : XmNactivateCallback, commandCallback, (XtPointer) closure); #elif mac #if useCarbon XtAddCallback (button, toggle ? XmNvalueChangedCallback : XmNactivateCallback, commandCallback, (XtPointer) closure); #else #endif #endif return button; } GuiObject GuiMenu_addSeparator (GuiObject menu) { #if gtk GuiObject separator = gtk_separator_menu_item_new (); gtk_menu_shell_append (GTK_MENU_SHELL (menu), GTK_WIDGET (separator)); gtk_widget_show (GTK_WIDGET (separator)); return separator; #elif win return XtVaCreateManagedWidget ("menuSeparator", xmSeparatorGadgetClass, menu, NULL); #elif mac #if useCarbon return XtVaCreateManagedWidget ("menuSeparator", xmSeparatorGadgetClass, menu, NULL); #else return NULL; // TODO #endif #endif } /* End of file GuiMenu.cpp */ sources_5316/sys/Picture.h0000644000176700017670000001041611752476042014337 0ustar paulpaul#ifndef _Picture_h_ #define _Picture_h_ /* Picture.h * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* A self-recording picture inside a DrawingArea widget. All drawing is kept in a Graphics. If the picture is sensitive, the user can select the viewport by dragging the mouse across the drawing area. If the viewport is smaller than the entire drawing area, it is highlighted. Usage: You should put highlighting off during drawing. Do not use the workstation Graphics routines, like clearWs, flushWs, closeWs, updateWs, setWsViewport. Example: Picture p = Picture_create (myDrawingArea); Any g = Picture_getGraphics (p); Picture_unhighlight (p); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_text (g, 0.5, 0.7, L"Hello"); Graphics_text (g, 0.5, 0.6, L"there"); Picture_highlight (p); ... (event handling) Picture_unhighlight (p); Graphics_text (g, 0.5, 0.3, L"Goodbye"); Picture_highlight (p); ... (event handling) Picture_writeToEpsFile (p, L"HelloGoodbye.eps"); Picture_print (p, GraphicsPostscript_FINE); Picture_remove (& p); */ #ifdef macintosh #define Picture PictureNotMac #endif #include "Graphics.h" typedef struct structPicture *Picture; Picture Picture_create (GuiObject drawingArea, Boolean sensitive); /* Function: create an empty self-recording picture inside 'drawingArea'. Precondition: 'drawingArea' must have been realized. Postconditions: a Graphics has been created from Graphics_create_macintosh or Graphics_create_xwindow; the workstation viewport of this Graphics is [0, 1] x [0, 1]; selection is [0, 1] x [0, 1] (NDC), which is invisible; */ Graphics Picture_getGraphics (Picture me); /* Function: return the Graphics object. Usage: send the graphics output that you want to be in the picture to this Graphics, bracketed by calls to Picture_startRecording and Picture_stopRecording. */ void Picture_unhighlight (Picture me); /* Function: hide the viewport. Usage: call just before sending graphics output. */ void Picture_highlight (Picture me); /* Function: visualize the viewport. Usage: call just after sending graphics output. */ void Picture_setSelectionChangedCallback (Picture me, void (*selectionChangedCallback) (Picture, XtPointer closure, double x1NDC, double x2NDC, double y1NDC, double y2NDC), XtPointer selectionChangedClosure); void Picture_setMouseSelectsInnerViewport (Picture me, int mouseSelectsInnerViewport); void Picture_remove (Picture *me); /* Function: remove a Picture from memory. Preconditions: none Postconditions: *me == NULL; */ void Picture_erase (Picture me); /* Clears the screen. */ void Picture_writeToPraatPictureFile (Picture me, MelderFile file); void Picture_readFromPraatPictureFile (Picture me, MelderFile file); void Picture_writeToEpsFile (Picture me, MelderFile file, int includeFonts, int useSilipaPS); void Picture_writeToPdfFile (Picture me, MelderFile file); void Picture_print (Picture me); void Picture_printToPostScriptPrinter (Picture me, int spots, int paperSize, int rotation, double magnification); #ifdef macintosh void Picture_copyToClipboard (Picture me); #endif #ifdef _WIN32 void Picture_copyToClipboard (Picture me); void Picture_writeToWindowsMetafile (Picture me, MelderFile file); #endif void Picture_setSelection (Picture me, double x1NDC, double x2NDC, double y1NDC, double y2NDC, Boolean notify); /* Preconditions: 0.0 <= x1NDC < x2NDC <= 1.0; 0.0 <= y1NDC < y2NDC <= 1.0; */ void Picture_background (Picture me); void Picture_foreground (Picture me); void Picture_selfExpose (Picture me); /* End of file Picture.h */ #endif sources_5316/sys/praat_objectMenus.cpp0000644000176700017670000006350611752477416016742 0ustar paulpaul/* praat_objectMenus.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2002/12/01 allow string expressions in calculator * pb 2003/03/09 simplified calculator * pb 2004/11/16 Win: more room for fixed buttons * pb 2004/12/05 renamed script running procedures * pb 2005/07/06 repaired a memory leak in creating a script editor from a double click * pb 2005/08/22 renamed the Control menu to "Praat" on all systems (like on the Mac) * pb 2005/11/18 HTML files are considered scripts (this is just for testing) * pb 2006/08/12 allowed renaming with European characters * pb 2006/10/20 embedded scripts * pb 2006/12/26 theCurrentPraat * pb 2007/01/26 layout objects window * pb 2007/06/10 wchar_t * pb 2007/08/12 wchar_t * pb 2008/04/30 new Formula API * pb 2009/01/17 arguments to UiForm callbacks * pb 2011/05/03 C++ */ #include #include "praatP.h" #include "praat_script.h" #include "ScriptEditor.h" #include "ButtonEditor.h" #include "DataEditor.h" #include "site.h" #undef iam #define iam iam_LOOP #define EDITOR theCurrentPraatObjects -> list [IOBJECT]. editors /********** Callbacks of the fixed buttons. **********/ DIRECT (Remove) WHERE_DOWN (SELECTED) praat_removeObject (IOBJECT); praat_show (); END FORM (Rename, L"Rename object", L"Rename...") LABEL (L"rename object", L"New name:") TEXTFIELD (L"newName", L"") OK { int IOBJECT; WHERE (SELECTED) SET_STRING (L"newName", NAME) } DO wchar_t *string = GET_STRING (L"newName"); if (theCurrentPraatObjects -> totalSelection == 0) Melder_throw ("Selection changed!\nNo object selected. Cannot rename."); if (theCurrentPraatObjects -> totalSelection > 1) Melder_throw (L"Selection changed!\nCannot rename more than one object at a time."); WHERE (SELECTED) break; praat_cleanUpName (string); /* This is allowed because "string" is local and dispensible. */ static MelderString fullName = { 0 }; MelderString_empty (& fullName); MelderString_append (& fullName, Thing_className ((Thing) OBJECT), L" ", string); if (! wcsequ (fullName.string, FULL_NAME)) { Melder_free (FULL_NAME), FULL_NAME = Melder_wcsdup_f (fullName.string); MelderString listName = { 0 }; MelderString_append (& listName, Melder_integer (ID), L". ", fullName.string); praat_list_renameAndSelect (IOBJECT, listName.string); MelderString_free (& listName); for (int ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) if (EDITOR [ieditor]) Thing_setName ((Thing) EDITOR [ieditor], fullName.string); Thing_setName ((Thing) OBJECT, string); } END FORM (Copy, L"Copy object", L"Copy...") LABEL (L"copy object", L"Name of new object:") TEXTFIELD (L"newName", L"") OK { int IOBJECT; WHERE (SELECTED) SET_STRING (L"newName", NAME) } DO if (theCurrentPraatObjects -> totalSelection == 0) Melder_throw ("Selection changed!\nNo object selected. Cannot copy."); if (theCurrentPraatObjects -> totalSelection > 1) Melder_throw ("Selection changed!\nCannot copy more than one object at a time."); WHERE (SELECTED) { wchar_t *name = GET_STRING (L"newName"); praat_new1 (Data_copy ((Data) OBJECT), name); } END DIRECT (Info) if (theCurrentPraatObjects -> totalSelection == 0) Melder_throw ("Selection changed!\nNo object selected. Cannot query."); if (theCurrentPraatObjects -> totalSelection > 1) Melder_throw ("Selection changed!\nCannot query more than one object at a time."); WHERE (SELECTED) Thing_infoWithId ((Thing) OBJECT, ID); END DIRECT (Inspect) if (theCurrentPraatObjects -> totalSelection == 0) Melder_throw ("Selection changed!\nNo object selected. Cannot inspect."); if (theCurrentPraatApplication -> batch) { Melder_throw ("Cannot inspect data from batch."); } else { WHERE (SELECTED) { praat_installEditor (DataEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, OBJECT), IOBJECT); therror } } END /********** The fixed menus. **********/ static GuiObject praatMenu, newMenu, readMenu, goodiesMenu, preferencesMenu, applicationHelpMenu, helpMenu; GuiObject praat_objects_resolveMenu (const wchar_t *menu) { return wcsequ (menu, L"Praat") || wcsequ (menu, L"Control") ? praatMenu : wcsequ (menu, L"New") || wcsequ (menu, L"Create") ? newMenu : wcsequ (menu, L"Open") || wcsequ (menu, L"Read") ? readMenu : wcsequ (menu, L"Help") ? helpMenu : wcsequ (menu, L"Goodies") ? goodiesMenu : wcsequ (menu, L"Preferences") ? preferencesMenu : #ifdef macintosh wcsequ (menu, L"ApplicationHelp") ? applicationHelpMenu : #else wcsequ (menu, L"ApplicationHelp") ? helpMenu : #endif newMenu; /* Default. */ } /********** Callbacks of the Praat menu. **********/ DIRECT (About) praat_showLogo (FALSE); END DIRECT (Memory_info) praat_memoryInfo (); END DIRECT (praat_newScript) autoScriptEditor editor = ScriptEditor_createFromText (theCurrentPraatApplication -> topShell, NULL, NULL); editor.transfer(); // the user becomes the owner END DIRECT (praat_openScript) autoScriptEditor editor = ScriptEditor_createFromText (theCurrentPraatApplication -> topShell, NULL, NULL); TextEditor_showOpen (editor.peek()); editor.transfer(); // the user becomes the owner END static ButtonEditor theButtonEditor; static void cb_ButtonEditor_destruction (Editor editor, void *closure) { (void) editor; (void) closure; theButtonEditor = NULL; } FORM (praat_debug, L"Set debugging options", 0) LABEL (L"", L"Setting the following to anything other than zero") LABEL (L"", L"will alter the behaviour of this program") LABEL (L"", L"in inpredictable ways.") INTEGER (L"Debug option", L"0") OK SET_INTEGER (L"Debug option", Melder_debug) DO Melder_debug = GET_INTEGER (L"Debug option"); END DIRECT (praat_editButtons) if (theButtonEditor) { theButtonEditor -> raise (); } else { theButtonEditor = ButtonEditor_create (theCurrentPraatApplication -> topShell); theButtonEditor -> setDestructionCallback (cb_ButtonEditor_destruction, NULL); } END FORM (praat_addMenuCommand, L"Add menu command", L"Add menu command...") WORD (L"Window", L"Objects") WORD (L"Menu", L"New") SENTENCE (L"Command", L"Hallo...") SENTENCE (L"After command", L"") INTEGER (L"Depth", L"0") LABEL (L"", L"Script file:") TEXTFIELD (L"Script", L"/u/miep/hallo.praat") OK DO praat_addMenuCommandScript (GET_STRING (L"Window"), GET_STRING (L"Menu"), GET_STRING (L"Command"), GET_STRING (L"After command"), GET_INTEGER (L"Depth"), GET_STRING (L"Script")); END FORM (praat_hideMenuCommand, L"Hide menu command", L"Hide menu command...") WORD (L"Window", L"Objects") WORD (L"Menu", L"New") SENTENCE (L"Command", L"Hallo...") OK DO praat_hideMenuCommand (GET_STRING (L"Window"), GET_STRING (L"Menu"), GET_STRING (L"Command")); END FORM (praat_showMenuCommand, L"Show menu command", L"Show menu command...") WORD (L"Window", L"Objects") WORD (L"Menu", L"New") SENTENCE (L"Command", L"Hallo...") OK DO praat_showMenuCommand (GET_STRING (L"Window"), GET_STRING (L"Menu"), GET_STRING (L"Command")); END FORM (praat_addAction, L"Add action command", L"Add action command...") WORD (L"Class 1", L"Sound") INTEGER (L"Number 1", L"0") WORD (L"Class 2", L"") INTEGER (L"Number 2", L"0") WORD (L"Class 3", L"") INTEGER (L"Number 3", L"0") SENTENCE (L"Command", L"Play reverse") SENTENCE (L"After command", L"Play") INTEGER (L"Depth", L"0") LABEL (L"", L"Script file:") TEXTFIELD (L"Script", L"/u/miep/playReverse.praat") OK DO praat_addActionScript (GET_STRING (L"Class 1"), GET_INTEGER (L"Number 1"), GET_STRING (L"Class 2"), GET_INTEGER (L"Number 2"), GET_STRING (L"Class 3"), GET_INTEGER (L"Number 3"), GET_STRING (L"Command"), GET_STRING (L"After command"), GET_INTEGER (L"Depth"), GET_STRING (L"Script")); END FORM (praat_hideAction, L"Hide action command", L"Hide action command...") WORD (L"Class 1", L"Sound") WORD (L"Class 2", L"") WORD (L"Class 3", L"") SENTENCE (L"Command", L"Play") OK DO praat_hideAction_classNames (GET_STRING (L"Class 1"), GET_STRING (L"Class 2"), GET_STRING (L"Class 3"), GET_STRING (L"Command")); END FORM (praat_showAction, L"Show action command", L"Show action command...") WORD (L"Class 1", L"Sound") WORD (L"Class 2", L"") WORD (L"Class 3", L"") SENTENCE (L"Command", L"Play") OK DO praat_showAction_classNames (GET_STRING (L"Class 1"), GET_STRING (L"Class 2"), GET_STRING (L"Class 3"), GET_STRING (L"Command")); END /********** Callbacks of the Preferences menu. **********/ FORM (TextInputEncodingSettings, L"Text reading preferences", L"Unicode") RADIO_ENUM (L"Encoding of 8-bit text files", kMelder_textInputEncoding, DEFAULT) OK SET_ENUM (L"Encoding of 8-bit text files", kMelder_textInputEncoding, Melder_getInputEncoding ()) DO Melder_setInputEncoding (GET_ENUM (kMelder_textInputEncoding, L"Encoding of 8-bit text files")); END FORM (TextOutputEncodingSettings, L"Text writing preferences", L"Unicode") RADIO_ENUM (L"Output encoding", kMelder_textOutputEncoding, DEFAULT) OK SET_ENUM (L"Output encoding", kMelder_textOutputEncoding, Melder_getOutputEncoding ()) DO Melder_setOutputEncoding (GET_ENUM (kMelder_textOutputEncoding, L"Output encoding")); END /********** Callbacks of the Goodies menu. **********/ FORM (praat_calculator, L"Calculator", L"Calculator") LABEL (L"", L"Type any numeric formula or string formula:") TEXTFIELD (L"expression", L"5*5") LABEL (L"", L"Note that you can include many special functions in your formula,") LABEL (L"", L"including statistical functions and acoustics-auditory conversions.") LABEL (L"", L"For details, click Help.") OK DO if (interpreter == NULL) { interpreter = Interpreter_create (NULL, NULL); try { Interpreter_anyExpression (interpreter, GET_STRING (L"expression"), NULL); forget (interpreter); } catch (MelderError) { forget (interpreter); throw; } } else { Interpreter_anyExpression (interpreter, GET_STRING (L"expression"), NULL); } END DIRECT (praat_listReadableTypesOfObjects) Thing_listReadableClasses (); END FORM (praat_reportDifferenceOfTwoProportions, L"Report difference of two proportions", L"Difference of two proportions") INTEGER (L"left Row 1", L"71") INTEGER (L"right Row 1", L"39") INTEGER (L"left Row 2", L"93") INTEGER (L"right Row 2", L"27") OK DO double a = GET_INTEGER (L"left Row 1"), b = GET_INTEGER (L"right Row 1"); double c = GET_INTEGER (L"left Row 2"), d = GET_INTEGER (L"right Row 2"); double n = a + b + c + d; double aexp, bexp, cexp, dexp, crossDifference, x2; REQUIRE (a >= 0 && b >= 0 && c >= 0 && d >= 0, L"Numbers must not be negative.") REQUIRE ((a > 0 || b > 0) && (c > 0 || d > 0), L"Row totals must be positive.") REQUIRE ((a > 0 || c > 0) && (b > 0 || d > 0), L"Column totals must be positive.") MelderInfo_open (); MelderInfo_writeLine4 (L"Observed row 1 = ", Melder_integer (a), L" ", Melder_integer (b)); MelderInfo_writeLine4 (L"Observed row 2 = ", Melder_integer (c), L" ", Melder_integer (d)); aexp = (a + b) * (a + c) / n; bexp = (a + b) * (b + d) / n; cexp = (a + c) * (c + d) / n; dexp = (b + d) * (c + d) / n; MelderInfo_writeLine1 (L""); MelderInfo_writeLine4 (L"Expected row 1 = ", Melder_double (aexp), L" ", Melder_double (bexp)); MelderInfo_writeLine4 (L"Expected row 2 = ", Melder_double (cexp), L" ", Melder_double (dexp)); /* * Continuity correction: * bring the observed numbers closer to the expected numbers by 0.5 (if possible). */ if (a < aexp) { a += 0.5; if (a > aexp) a = aexp; } else if (a > aexp) { a -= 0.5; if (a < aexp) a = aexp; } if (b < bexp) { b += 0.5; if (b > bexp) b = bexp; } else if (b > bexp) { b -= 0.5; if (b < bexp) b = bexp; } if (c < cexp) { c += 0.5; if (c > cexp) c = cexp; } else if (c > cexp) { c -= 0.5; if (c < cexp) c = cexp; } if (d < dexp) { d += 0.5; if (d > dexp) d = dexp; } else if (d > dexp) { d -= 0.5; if (d < dexp) d = dexp; } MelderInfo_writeLine1 (L""); MelderInfo_writeLine4 (L"Corrected observed row 1 = ", Melder_double (a), L" ", Melder_double (b)); MelderInfo_writeLine4 (L"Corrected observed row 2 = ", Melder_double (c), L" ", Melder_double (d)); n = a + b + c + d; crossDifference = a * d - b * c; x2 = n * crossDifference * crossDifference / (a + b) / (c + d) / (a + c) / (b + d); MelderInfo_writeLine1 (L""); MelderInfo_writeLine2 (L"Chi-square = ", Melder_double (x2)); MelderInfo_writeLine2 (L"Two-tailed p = ", Melder_double (NUMchiSquareQ (x2, 1))); MelderInfo_close (); END /********** Callbacks of the Open menu. **********/ static void readFromFile (MelderFile file) { autoData object = (Data) Data_readFromFile (file); if (object.peek() && Thing_member (object.peek(), classManPages) && ! Melder_batch) { ManPages pages = (ManPages) object.peek(); ManPage firstPage = static_cast (pages -> pages -> item [1]); Manual_create (theCurrentPraatApplication -> topShell, firstPage -> title, object.transfer(), true); therror if (pages -> executable) Melder_warning (L"These manual pages contain links to executable scripts.\n" "Only navigate these pages if you trust their author!"); return; } if (object.peek() && Thing_member (object.peek(), classScript) && ! Melder_batch) { ScriptEditor_createFromScript (theCurrentPraatApplication -> topShell, NULL, (Script) object.peek()); return; } praat_new1 (object.transfer(), MelderFile_name (file)); therror praat_updateSelection (); } FORM_READ (Data_readFromFile, L"Read Object(s) from file", 0, true) readFromFile (file); END /********** Callbacks of the Save menu. **********/ FORM_WRITE (Data_writeToTextFile, L"Save Object(s) as one text file", 0, 0) if (theCurrentPraatObjects -> totalSelection == 1) { LOOP { iam (Data); Data_writeToTextFile (me, file); therror } } else { autoCollection set = praat_getSelectedObjects (); Data_writeToTextFile (set.peek(), file); therror } END FORM_WRITE (Data_writeToShortTextFile, L"Save Object(s) as one short text file", 0, 0) if (theCurrentPraatObjects -> totalSelection == 1) { LOOP { iam (Data); Data_writeToShortTextFile (me, file); therror } } else { autoCollection set = praat_getSelectedObjects (); Data_writeToShortTextFile (set.peek(), file); therror } END FORM_WRITE (Data_writeToBinaryFile, L"Save Object(s) as one binary file", 0, 0) if (theCurrentPraatObjects -> totalSelection == 1) { LOOP { iam (Data); Data_writeToBinaryFile (me, file); therror } } else { autoCollection set = praat_getSelectedObjects (); Data_writeToBinaryFile (set.peek(), file); therror } END FORM (ManPages_saveToHtmlDirectory, L"Save all pages as HTML files", 0) LABEL (L"", L"Type a directory name:") TEXTFIELD (L"directory", L"") OK structMelderDir currentDirectory = { { 0 } }; Melder_getDefaultDir (& currentDirectory); SET_STRING (L"directory", Melder_dirToPath (& currentDirectory)) DO wchar *directory = GET_STRING (L"directory"); LOOP { iam (ManPages); ManPages_writeAllToHtmlDir (me, directory); } END DIRECT (ManPages_view) LOOP { iam (ManPages); ManPage firstPage = static_cast (my pages -> item [1]); autoManual manual = Manual_create (theCurrentPraatApplication -> topShell, firstPage -> title, me, false); if (my executable) Melder_warning (L"These manual pages contain links to executable scripts.\n" "Only navigate these pages if you trust their author!"); praat_installEditor (manual.transfer(), IOBJECT); } END /********** Callbacks of the Help menu. **********/ FORM (SearchManual, L"Search manual", L"Manual") LABEL (L"", L"Search for strings (separate with spaces):") TEXTFIELD (L"query", L"") OK DO if (theCurrentPraatApplication -> batch) Melder_throw (L"Cannot view a manual from batch."); Manual manPage = Manual_create (theCurrentPraatApplication -> topShell, L"Intro", theCurrentPraatApplication -> manPages, false); Manual_search (manPage, GET_STRING (L"query")); END FORM (GoToManualPage, L"Go to manual page", 0) {long numberOfPages; const wchar_t **pages = ManPages_getTitles (theCurrentPraatApplication -> manPages, & numberOfPages); LIST (L"Page", numberOfPages, pages, 1)} OK DO if (theCurrentPraatApplication -> batch) Melder_throw (L"Cannot view a manual from batch."); Manual manPage = Manual_create (theCurrentPraatApplication -> topShell, L"Intro", theCurrentPraatApplication -> manPages, false); HyperPage_goToPage_i (manPage, GET_INTEGER (L"Page")); therror END FORM (WriteManualToHtmlDirectory, L"Save all pages as HTML files", 0) LABEL (L"", L"Type a directory name:") TEXTFIELD (L"directory", L"") OK structMelderDir currentDirectory = { { 0 } }; Melder_getDefaultDir (& currentDirectory); SET_STRING (L"directory", Melder_dirToPath (& currentDirectory)) DO wchar *directory = GET_STRING (L"directory"); ManPages_writeAllToHtmlDir (theCurrentPraatApplication -> manPages, directory); END /********** Menu descriptions. **********/ void praat_show (void) { /* * (De)sensitivize the fixed buttons as appropriate for the current selection. */ praat_sensitivizeFixedButtonCommand (L"Remove", theCurrentPraatObjects -> totalSelection != 0); praat_sensitivizeFixedButtonCommand (L"Rename...", theCurrentPraatObjects -> totalSelection == 1); praat_sensitivizeFixedButtonCommand (L"Copy...", theCurrentPraatObjects -> totalSelection == 1); praat_sensitivizeFixedButtonCommand (L"Info", theCurrentPraatObjects -> totalSelection == 1); praat_sensitivizeFixedButtonCommand (L"Inspect", theCurrentPraatObjects -> totalSelection != 0); praat_actions_show (); if (theCurrentPraatApplication == & theForegroundPraatApplication && theButtonEditor) theButtonEditor -> dataChanged (); } /********** Menu descriptions. **********/ void praat_addFixedButtons (GuiObject form) { // Het is bagger, ik weet het, maar kom maar met een betere oplossing... bijvoorkeur zonder #defines #if gtk GuiObject buttons1 = NULL, buttons2 = NULL, buttons3 = NULL; if (form) { buttons1 = gtk_hbutton_box_new (); buttons2 = gtk_hbutton_box_new (); buttons3 = gtk_hbutton_box_new (); gtk_button_box_set_layout (GTK_BUTTON_BOX (buttons1), GTK_BUTTONBOX_START); gtk_button_box_set_layout (GTK_BUTTON_BOX (buttons2), GTK_BUTTONBOX_START); gtk_button_box_set_layout (GTK_BUTTON_BOX (buttons3), GTK_BUTTONBOX_START); gtk_box_pack_end (GTK_BOX (form), GTK_WIDGET (buttons3), FALSE, FALSE, 0); gtk_box_pack_end (GTK_BOX (form), GTK_WIDGET (buttons2), FALSE, FALSE, 0); gtk_box_pack_end (GTK_BOX (form), GTK_WIDGET (buttons1), FALSE, FALSE, 0); gtk_widget_show (GTK_WIDGET (buttons1)); gtk_widget_show (GTK_WIDGET (buttons2)); gtk_widget_show (GTK_WIDGET (buttons3)); } praat_addFixedButtonCommand (buttons1, L"Rename...", DO_Rename, 8, 70); praat_addFixedButtonCommand (buttons1, L"Copy...", DO_Copy, 98, 70); praat_addFixedButtonCommand (buttons2, L"Inspect", DO_Inspect, 8, 40); praat_addFixedButtonCommand (buttons2, L"Info", DO_Info, 98, 40); praat_addFixedButtonCommand (buttons3, L"Remove", DO_Remove, 8, 10); #else praat_addFixedButtonCommand (form, L"Rename...", DO_Rename, 8, 70); praat_addFixedButtonCommand (form, L"Copy...", DO_Copy, 98, 70); praat_addFixedButtonCommand (form, L"Inspect", DO_Inspect, 8, 40); praat_addFixedButtonCommand (form, L"Info", DO_Info, 98, 40); praat_addFixedButtonCommand (form, L"Remove", DO_Remove, 8, 10); #endif } static void searchProc (void) { DO_SearchManual (NULL, NULL, NULL, NULL, false, NULL); } static MelderString itemTitle_about = { 0 }; static Any scriptRecognizer (int nread, const char *header, MelderFile file) { const wchar_t *name = MelderFile_name (file); if (nread < 2) return NULL; if ((header [0] == '#' && header [1] == '!') || wcsstr (name, L".praat") == name + wcslen (name) - 6 || wcsstr (name, L".html") == name + wcslen (name) - 5) { return Script_createFromFile (file); } return NULL; } static void cb_openDocument (MelderFile file) { try { readFromFile (file); therror } catch (MelderError) { Melder_flushError (NULL); } } void praat_addMenus (GuiObject bar) { GuiObject button; Melder_setSearchProc (searchProc); Data_recognizeFileType (scriptRecognizer); /* * Create the menu titles in the bar. */ if (! theCurrentPraatApplication -> batch) { #ifdef macintosh praatMenu = GuiMenuBar_addMenu (bar ? praatP.topBar : NULL, L"\024", 0); /* Apple icon. */ #else praatMenu = GuiMenuBar_addMenu (bar, L"Praat", 0); #endif newMenu = GuiMenuBar_addMenu (bar, L"New", 0); readMenu = GuiMenuBar_addMenu (bar, L"Open", 0); praat_actions_createWriteMenu (bar); #ifdef macintosh applicationHelpMenu = GuiMenuBar_addMenu (bar ? praatP.topBar : NULL, L"Help", 0); #endif helpMenu = GuiMenuBar_addMenu (bar, L"Help", 0); } MelderString_append (& itemTitle_about, L"About ", Melder_peekUtf8ToWcs (praatP.title), L"..."); #ifdef macintosh praat_addMenuCommand (L"Objects", L"Praat", itemTitle_about.string, 0, praat_UNHIDABLE, DO_About); #endif #ifdef UNIX praat_addMenuCommand (L"Objects", L"Praat", itemTitle_about.string, 0, praat_UNHIDABLE, DO_About); praat_addMenuCommand (L"Objects", L"Praat", L"-- script --", 0, 0, 0); #endif praat_addMenuCommand (L"Objects", L"Praat", L"Debug...", 0, praat_HIDDEN, DO_praat_debug); praat_addMenuCommand (L"Objects", L"Praat", L"Statistics...", 0, 0, DO_Memory_info); praat_addMenuCommand (L"Objects", L"Praat", L"-- script --", 0, 0, 0); praat_addMenuCommand (L"Objects", L"Praat", L"Run script...", 0, praat_HIDDEN, DO_praat_runScript); praat_addMenuCommand (L"Objects", L"Praat", L"New Praat script", 0, 0, DO_praat_newScript); praat_addMenuCommand (L"Objects", L"Praat", L"Open Praat script...", 0, 0, DO_praat_openScript); praat_addMenuCommand (L"Objects", L"Praat", L"-- buttons --", 0, 0, 0); praat_addMenuCommand (L"Objects", L"Praat", L"Add menu command...", 0, praat_HIDDEN, DO_praat_addMenuCommand); praat_addMenuCommand (L"Objects", L"Praat", L"Hide menu command...", 0, praat_HIDDEN, DO_praat_hideMenuCommand); praat_addMenuCommand (L"Objects", L"Praat", L"Show menu command...", 0, praat_HIDDEN, DO_praat_showMenuCommand); praat_addMenuCommand (L"Objects", L"Praat", L"Add action command...", 0, praat_HIDDEN, DO_praat_addAction); praat_addMenuCommand (L"Objects", L"Praat", L"Hide action command...", 0, praat_HIDDEN, DO_praat_hideAction); praat_addMenuCommand (L"Objects", L"Praat", L"Show action command...", 0, praat_HIDDEN, DO_praat_showAction); button = praat_addMenuCommand (L"Objects", L"Praat", L"Goodies", 0, praat_UNHIDABLE, 0); #if gtk if (button) goodiesMenu = gtk_menu_item_get_submenu (GTK_MENU_ITEM (button)); #elif motif if (button) XtVaGetValues (button, XmNsubMenuId, & goodiesMenu, NULL); #endif praat_addMenuCommand (L"Objects", L"Goodies", L"Calculator...", 0, 'U', DO_praat_calculator); praat_addMenuCommand (L"Objects", L"Goodies", L"Report difference of two proportions...", 0, 0, DO_praat_reportDifferenceOfTwoProportions); praat_addMenuCommand (L"Objects", L"Goodies", L"List readable types of objects...", 0, 0, DO_praat_listReadableTypesOfObjects); button = praat_addMenuCommand (L"Objects", L"Praat", L"Preferences", 0, praat_UNHIDABLE, 0); #if gtk if (button) preferencesMenu = gtk_menu_item_get_submenu (GTK_MENU_ITEM (button)); #elif motif if (button) XtVaGetValues (button, XmNsubMenuId, & preferencesMenu, NULL); #endif praat_addMenuCommand (L"Objects", L"Preferences", L"Buttons...", 0, praat_UNHIDABLE, DO_praat_editButtons); /* Cannot be hidden. */ praat_addMenuCommand (L"Objects", L"Preferences", L"-- encoding prefs --", 0, 0, 0); praat_addMenuCommand (L"Objects", L"Preferences", L"Text reading preferences...", 0, 0, DO_TextInputEncodingSettings); praat_addMenuCommand (L"Objects", L"Preferences", L"Text writing preferences...", 0, 0, DO_TextOutputEncodingSettings); praat_addMenuCommand (L"Objects", L"Open", L"Read from file...", 0, praat_ATTRACTIVE + 'O', DO_Data_readFromFile); praat_addAction1 (classData, 0, L"Save as text file...", 0, 0, DO_Data_writeToTextFile); praat_addAction1 (classData, 0, L"Write to text file...", 0, praat_HIDDEN, DO_Data_writeToTextFile); praat_addAction1 (classData, 0, L"Save as short text file...", 0, 0, DO_Data_writeToShortTextFile); praat_addAction1 (classData, 0, L"Write to short text file...", 0, praat_HIDDEN, DO_Data_writeToShortTextFile); praat_addAction1 (classData, 0, L"Save as binary file...", 0, 0, DO_Data_writeToBinaryFile); praat_addAction1 (classData, 0, L"Write to binary file...", 0, praat_HIDDEN, DO_Data_writeToBinaryFile); praat_addAction1 (classManPages, 1, L"Save to HTML directory...", 0, 0, DO_ManPages_saveToHtmlDirectory); praat_addAction1 (classManPages, 1, L"View", 0, 0, DO_ManPages_view); } void praat_addMenus2 (void) { static MelderString itemTitle_search = { 0 }; praat_addMenuCommand (L"Objects", L"ApplicationHelp", L"-- manual --", 0, 0, 0); praat_addMenuCommand (L"Objects", L"ApplicationHelp", L"Go to manual page...", 0, 0, DO_GoToManualPage); praat_addMenuCommand (L"Objects", L"ApplicationHelp", L"Write manual to HTML directory...", 0, praat_HIDDEN, DO_WriteManualToHtmlDirectory); MelderString_empty (& itemTitle_search); MelderString_append (& itemTitle_search, L"Search ", Melder_peekUtf8ToWcs (praatP.title), L" manual..."); praat_addMenuCommand (L"Objects", L"ApplicationHelp", itemTitle_search.string, 0, 'M', DO_SearchManual); #ifdef _WIN32 praat_addMenuCommand (L"Objects", L"Help", L"-- about --", 0, 0, 0); praat_addMenuCommand (L"Objects", L"Help", itemTitle_about.string, 0, praat_UNHIDABLE, DO_About); #endif #if defined (macintosh) || defined (_WIN32) Gui_setOpenDocumentCallback (cb_openDocument); #endif } /* End of file praat_objectMenus.cpp */ sources_5316/sys/macport_off.h0000644000176700017670000000157011651727055015225 0ustar paulpaul/* macport_off.h * * Copyright (C) 1993-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #undef Polygon #undef Pattern #undef Boolean #undef Collection #undef Picture #undef Movie /* End of file macport_off.h */ sources_5316/sys/DataEditor.h0000644000176700017670000000552511631506124014740 0ustar paulpaul#ifndef _DataEditor_h_ #define _DataEditor_h /* DataEditor.h * * Copyright (C) 1995-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Editor.h" Thing_declare (DataSubEditor); Thing_declare (VectorEditor); Thing_declare (MatrixEditor); Thing_declare (StructEditor); Thing_declare (ClassEditor); Thing_declare (DataEditor); typedef struct structDataSubEditor_FieldData { GuiObject label, button, text; void *address; Data_Description description; long minimum, maximum, min2, max2; wchar *history; // the full prefix of the members int rank; // should the button open a StructEditor (0) or VectorEditor (1) or MatrixEditor (2) ? } *DataSubEditor_FieldData; #define kDataSubEditor_MAXNUM_ROWS 12 Thing_define (DataSubEditor, Editor) { // new data: public: DataEditor d_root; void *d_address; Data_Description d_description; GuiObject d_scrollBar; int d_irow, d_topField, d_numberOfFields; struct structDataSubEditor_FieldData d_fieldData [1 + kDataSubEditor_MAXNUM_ROWS]; // overridden methods: virtual void v_destroy (); virtual bool v_scriptable () { return false; } virtual void v_createChildren (); virtual void v_createHelpMenuItems (EditorMenu menu); // new methods: virtual long v_countFields () { return 0; } virtual void v_showMembers () { } }; Thing_define (VectorEditor, DataSubEditor) { // new data: public: long d_minimum, d_maximum; // overridden methods: virtual long v_countFields (); virtual void v_showMembers (); }; Thing_define (MatrixEditor, DataSubEditor) { // new data: public: long d_minimum, d_maximum, d_min2, d_max2; // overridden methods: virtual long v_countFields (); virtual void v_showMembers (); }; Thing_define (StructEditor, DataSubEditor) { // overridden methods: virtual long v_countFields (); virtual void v_showMembers (); }; Thing_define (ClassEditor, StructEditor) { // overridden methods: virtual void v_showMembers (); }; Thing_define (DataEditor, ClassEditor) { // new data: public: Collection d_children; // overridden methods: void v_destroy (); void v_dataChanged (); }; DataEditor DataEditor_create (GuiObject parent, const wchar *title, Any data); /* End of file DataEditor.h */ #endif sources_5316/sys/Preferences.h0000644000176700017670000000534311611106371015155 0ustar paulpaul#ifndef _Preferences_h_ #define _Preferences_h_ /* Preferences.h * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "melder.h" /* * All strings added with Preferences_addString should have the following buffer size, * which conveniently equals the size of the path buffer in MelderFile so that * file paths can be used as preferences. */ #define Preferences_STRING_BUFFER_SIZE 1+kMelder_MAXPATH enum kPreferences_dummy { dummy1 = 1, dummy2 = 2 }; void Preferences_addByte (const wchar_t *string, signed char *value, signed char defaultValue); void Preferences_addShort (const wchar_t *string, short *value, short defaultValue); void Preferences_addInt (const wchar_t *string, int *value, int defaultValue); void Preferences_addLong (const wchar_t *string, long *value, long defaultValue); void Preferences_addUbyte (const wchar_t *string, unsigned char *value, unsigned char defaultValue); void Preferences_addUshort (const wchar_t *string, unsigned short *value, unsigned short defaultValue); void Preferences_addUint (const wchar_t *string, unsigned int *value, unsigned int defaultValue); void Preferences_addUlong (const wchar_t *string, unsigned long *value, unsigned long defaultValue); void Preferences_addBool (const wchar_t *string, bool *value, bool defaultValue); void Preferences_addDouble (const wchar_t *string, double *value, double defaultValue); void Preferences_addString (const wchar_t *string, wchar_t *value, const wchar_t *defaultValue); void _Preferences_addEnum (const wchar_t *string, enum kPreferences_dummy *value, int min, int max, const wchar_t *(*getText) (int value), int (*getValue) (const wchar_t *text), enum kPreferences_dummy defaultValue); #define Preferences_addEnum(string,value,enumerated,defaultValue) \ _Preferences_addEnum (string, (enum kPreferences_dummy *) value, enumerated##_MIN, enumerated##_MAX, \ enumerated##_getText, enumerated##_getValue, (enum kPreferences_dummy) enumerated##_##defaultValue) void Preferences_read (MelderFile file); void Preferences_write (MelderFile file); /* End of file Preferences.h */ #endif sources_5316/sys/enums.h0000644000176700017670000000226610726031113014041 0ustar paulpaul#ifndef _enums_h_ #define _enums_h_ /* enums.h * * Copyright (C) 2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/06 */ #define enums_begin(type,minimum) enum type { type##_MIN = minimum, #define enums_add(type,value,which,text) type##_##which = value, #define enums_alt(type,which,text) #define enums_end(type,maximum,def) type##_MAX = maximum, \ type##_DEFAULT = type##_##def }; \ const wchar_t * type##_getText (int value); \ int type##_getValue (const wchar_t *text); /* End of file enums.h */ #endif sources_5316/sys/Picture.cpp0000644000176700017670000005430411752475725014705 0ustar paulpaul/* Picture.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2003/07/19 extra null byte in Windows metafile name * pb 2004/02/19 outer selection * pb 2004/09/05 inner selection * pb 2005/05/19 EPS files have the option to switch off the screen preview * pb 2005/09/18 useSilipaPS * pb 2006/10/28 erased MacOS 9 stuff * pb 2007/11/30 erased Graphics_printf * sdk 2008/05/09 Picture_selfExpose * pb 2009/07/22 Picture_writeToPdfFile * fb 2010/03/01 cairo fix for black 1px borders * pb 2011/05/15 C++ * pb 2011/07/08 C++ */ #include "melder.h" #include "Gui.h" #include "Printer.h" #include "Picture.h" #include "site.h" struct structPicture { GuiObject drawingArea; Graphics graphics, selectionGraphics; Boolean sensitive; double selx1, selx2, sely1, sely2; // selection in NDC co-ordinates void (*selectionChangedCallback) (struct structPicture *, XtPointer, double, double, double, double); XtPointer selectionChangedClosure; int backgrounding, mouseSelectsInnerViewport; #if gtk bool selectionInProgress; double ixstart, iystart; #endif }; static void drawMarkers (Picture me) /* * The drawing area is a square measuring 12x12 inches. */ #define SIDE 12 /* * The selection grid has a resolution of 1/2 inch. */ #define SQUARES 24 /* * Vertical and horizontal lines every 3 inches. */ #define YELLOW_GRID 3 { int i; /* Fill the entire canvas with GC's background. */ Graphics_setColour (my selectionGraphics, Graphics_WHITE); Graphics_fillRectangle (my selectionGraphics, 0, SIDE, 0, SIDE); /* Draw yellow grid lines for coarse navigation. */ Graphics_setColour (my selectionGraphics, Graphics_YELLOW); for (i = YELLOW_GRID; i < SIDE; i += YELLOW_GRID) { Graphics_line (my selectionGraphics, 0, i, SIDE, i); Graphics_line (my selectionGraphics, i, 0, i, SIDE); } /* Draw red ticks and numbers for feedback on viewport measurement. */ Graphics_setColour (my selectionGraphics, Graphics_RED); for (i = 1; i < SIDE; i ++) { double x = i; Graphics_setTextAlignment (my selectionGraphics, Graphics_CENTRE, Graphics_TOP); Graphics_text1 (my selectionGraphics, x, SIDE, Melder_integer (i)); Graphics_setTextAlignment (my selectionGraphics, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text1 (my selectionGraphics, x, 0, Melder_integer (i)); } for (i = 1; i < SQUARES ; i ++) { /* Vertical ticks. */ double x = 0.5 * i; Graphics_line (my selectionGraphics, x, SIDE - 0.04, x, SIDE); Graphics_line (my selectionGraphics, x, 0, x, 0.04); } for (i = 1; i < SIDE; i ++) { double y = SIDE - i; Graphics_setTextAlignment (my selectionGraphics, Graphics_LEFT, Graphics_HALF); Graphics_text1 (my selectionGraphics, 0.04, y, Melder_integer (i)); Graphics_setTextAlignment (my selectionGraphics, Graphics_RIGHT, Graphics_HALF); Graphics_text1 (my selectionGraphics, SIDE - 0.03, y, Melder_integer (i)); } for (i = 1; i < SQUARES; i ++) { /* Horizontal ticks. */ double y = SIDE - 0.5 * i; Graphics_line (my selectionGraphics, SIDE - 0.04, y, SIDE, y); Graphics_line (my selectionGraphics, 0, y, 0.04, y); } Graphics_setColour (my selectionGraphics, Graphics_BLACK); } static void drawSelection (Picture me, int high) { double dx, dy; if (my backgrounding) return; dy = 2.8 * Graphics_inqFontSize (my graphics) / 72.0; dx = 1.5 * dy; if (dy > 0.4 * (my sely2 - my sely1)) dy = 0.4 * (my sely2 - my sely1); if (dx > 0.4 * (my selx2 - my selx1)) dx = 0.4 * (my selx2 - my selx1); if (high) { Graphics_highlight2 (my selectionGraphics, my selx1, my selx2, my sely1, my sely2, my selx1 + dx, my selx2 - dx, my sely1 + dy, my sely2 - dy); } else { Graphics_unhighlight2 (my selectionGraphics, my selx1, my selx2, my sely1, my sely2, my selx1 + dx, my selx2 - dx, my sely1 + dy, my sely2 - dy); } } //static double test = 0.0; static void gui_drawingarea_cb_expose (I, GuiDrawingAreaExposeEvent event) { iam (Picture); #if gtk // g_debug("EXPOSE DRAWING AREA"); // save old cairo contexts cairo_t *cgr = (cairo_t *) Graphics_x_getCR (my graphics); Melder_assert (cgr != NULL); cairo_t *csgr = (cairo_t *) Graphics_x_getCR (my selectionGraphics); // set new cairo contexts Graphics_x_setCR (my graphics, gdk_cairo_create (GDK_DRAWABLE (GTK_WIDGET (event -> widget) -> window))); Graphics_x_setCR (my selectionGraphics, gdk_cairo_create (GDK_DRAWABLE (GTK_WIDGET (event -> widget) -> window))); // - Graphics_x_setCR(my graphics, Graphics_x_getCR(my selectionGraphics)); // g_debug ("%d %d %d %d\n", event->x, event->y, event->width, event->height); cairo_rectangle ((cairo_t *) Graphics_x_getCR (my graphics), (double) event->x, (double) event->y, (double) event->width, (double) event->height); cairo_clip ((cairo_t *) Graphics_x_getCR (my graphics)); drawMarkers (me); Graphics_play ((Graphics) my graphics, (Graphics) my graphics); drawSelection (me, 1); // cairo_set_source_rgb(Graphics_x_getCR (my graphics), test / 3.0, test / 2.0, test); // cairo_fill(Graphics_x_getCR (my graphics)); cairo_destroy ((cairo_t *) Graphics_x_getCR (my selectionGraphics)); cairo_destroy ((cairo_t *) Graphics_x_getCR (my graphics)); // restore old cairo contexts Graphics_x_setCR (my graphics, cgr); Graphics_x_setCR (my selectionGraphics, csgr); // test+=0.1; // if (test > 3) test = 0.1; // g_debug("%d", test); #elif defined (macintosh) && 0 WindowPtr window = (WindowPtr) ((EventRecord *) call) -> message; static RgnHandle visRgn; Rect rect; long x1DC, x2DC, y1DC, y2DC; Graphics_inqWsViewport (my selectionGraphics, & x1DC, & x2DC, & y1DC, & y2DC); SetRect (& rect, x1DC, y1DC, x2DC, y2DC); /* No clearing needed; macintosh clips to update region. */ if (visRgn == NULL) visRgn = NewRgn (); GetPortVisibleRegion (GetWindowPort (window), visRgn); if (RectInRgn (& rect, visRgn)) { drawMarkers (me); Graphics_play ((Graphics) my graphics, (Graphics) my graphics); drawSelection (me, 1); } #elif defined (_WIN32) || 1 (void) event; drawMarkers (me); Graphics_play ((Graphics) my graphics, (Graphics) my graphics); drawSelection (me, 1); #endif } // TODO: Paul, als praat nu 100dpi zou zijn waarom zie ik hier dan nog 72.0 onder? // Stefan, die 72.0 is het aantal font-punten per inch, // gewoon een vaste verhouding die niks met pixels te maken heeft. // TODO: Paul, deze code is bagger :) En dient door event-model-extremisten te worden veroordeeld. // Stefan, zoals gezegd, er zijn goede redenen waarom sommige platforms dit synchroon oplossen; // misschien maar splitsen tussen die platforms en platforms die met events kunnen werken. static void gui_drawingarea_cb_click (I, GuiDrawingAreaClickEvent event) { iam (Picture); int xstart = event -> x; int ystart = event -> y; double xWC, yWC; #if gtk int ix, iy; Graphics_DCtoWC (my selectionGraphics, xstart, ystart, & xWC, & yWC); ix = 1 + floor (xWC * SQUARES / SIDE); iy = SQUARES - floor (yWC * SQUARES / SIDE); // if (my ixstart < 1 || my ixstart > SQUARES || my iystart < 1 || my iystart > SQUARES) return; if (my selectionInProgress == 0) { if (event->type == BUTTON_PRESS) { my selectionInProgress = 1; my ixstart = ix; my iystart = iy; } } else { int ix1, ix2, iy1, iy2; if (ix < my ixstart) { ix1 = ix; ix2 = my ixstart; } else { ix1 = my ixstart; ix2 = ix; } if (iy < my iystart) { iy1 = iy; iy2 = my iystart; } else { iy1 = my iystart; iy2 = iy; } if (my mouseSelectsInnerViewport) { int fontSize = Graphics_inqFontSize (my graphics); double xmargin = fontSize * 4.2 / 72.0, ymargin = fontSize * 2.8 / 72.0; if (xmargin > ix2 - ix1 + 1) xmargin = ix2 - ix1 + 1; if (ymargin > iy2 - iy1 + 1) ymargin = iy2 - iy1 + 1; Picture_setSelection (me, 0.5 * (ix1 - 1) - xmargin, 0.5 * ix2 + xmargin, 0.5 * (SQUARES - iy2) - ymargin, 0.5 * (SQUARES + 1 - iy1) + ymargin, False); } else { Picture_setSelection (me, 0.5 * (ix1 - 1), 0.5 * ix2, 0.5 * (SQUARES - iy2), 0.5 * (SQUARES + 1 - iy1), False); } if (event->type == BUTTON_RELEASE) { my selectionInProgress = 0; if (my selectionChangedCallback) { //Melder_casual ("selectionChangedCallback from gui_drawingarea_cb_click"); my selectionChangedCallback (me, my selectionChangedClosure, my selx1, my selx2, my sely1, my sely2); } } } #else int ixstart, iystart, ix, iy, oldix = 0, oldiy = 0; Graphics_DCtoWC (my selectionGraphics, xstart, ystart, & xWC, & yWC); ix = ixstart = 1 + floor (xWC * SQUARES / SIDE); iy = iystart = SQUARES - floor (yWC * SQUARES / SIDE); if (ixstart < 1 || ixstart > SQUARES || iystart < 1 || iystart > SQUARES) return; if (event -> shiftKeyPressed) { int ix1 = 1 + floor (my selx1 * SQUARES / SIDE); int ix2 = floor (my selx2 * SQUARES / SIDE); int iy1 = SQUARES + 1 - floor (my sely2 * SQUARES / SIDE); int iy2 = SQUARES - floor (my sely1 * SQUARES / SIDE); ixstart = ix < (ix1 + ix2) / 2 ? ix2 : ix1; iystart = iy < (iy1 + iy2) / 2 ? iy2 : iy1; } while (Graphics_mouseStillDown (my selectionGraphics)) { if (ix >= 1 && ix <= SQUARES && iy >= 1 && iy <= SQUARES && (ix != oldix || iy != oldiy)) { int ix1, ix2, iy1, iy2; if (ix < ixstart) { ix1 = ix; ix2 = ixstart; } else { ix1 = ixstart; ix2 = ix; } if (iy < iystart) { iy1 = iy; iy2 = iystart; } else { iy1 = iystart; iy2 = iy; } if (my mouseSelectsInnerViewport) { int fontSize = Graphics_inqFontSize (my graphics); double xmargin = fontSize * 4.2 / 72.0, ymargin = fontSize * 2.8 / 72.0; if (xmargin > ix2 - ix1 + 1) xmargin = ix2 - ix1 + 1; if (ymargin > iy2 - iy1 + 1) ymargin = iy2 - iy1 + 1; Picture_setSelection (me, 0.5 * (ix1 - 1) - xmargin, 0.5 * ix2 + xmargin, 0.5 * (SQUARES - iy2) - ymargin, 0.5 * (SQUARES + 1 - iy1) + ymargin, False); } else { Picture_setSelection (me, 0.5 * (ix1 - 1), 0.5 * ix2, 0.5 * (SQUARES - iy2), 0.5 * (SQUARES + 1 - iy1), False); #if gtk Graphics_flushWs (my graphics); #endif } oldix = ix; oldiy = iy; } Graphics_getMouseLocation (my selectionGraphics, & xWC, & yWC); ix = 1 + floor (xWC * SQUARES / SIDE); iy = SQUARES - floor (yWC * SQUARES / SIDE); } if (my selectionChangedCallback) { //Melder_casual ("selectionChangedCallback from gui_drawingarea_cb_click"); my selectionChangedCallback (me, my selectionChangedClosure, my selx1, my selx2, my sely1, my sely2); } #endif } Picture Picture_create (GuiObject drawingArea, Boolean sensitive) { Picture me = NULL; try { me = Melder_calloc (struct structPicture, 1); #if gtk my selectionInProgress = 0; #endif my drawingArea = drawingArea; /* * The initial viewport is a rectangle 6 inches wide and 4 inches high. */ my selx1 = 0.0; my selx2 = 6.0; my sely1 = 8.0; my sely2 = 12.0; my sensitive = sensitive && drawingArea; if (drawingArea) { /* The drawing area must have been realized; see manual at XtWindow. */ my graphics = Graphics_create_xmdrawingarea (my drawingArea); GuiDrawingArea_setExposeCallback (my drawingArea, gui_drawingarea_cb_expose, me); } else { /* * Create a dummy Graphics. * This has device coordinates from 0 to 32767. * This will be mapped on an area of 12x12 inches, * so the resolution is 32767 / 12 = 2731. */ my graphics = Graphics_create (2731); } Graphics_setWsWindow (my graphics, 0.0, 12.0, 0.0, 12.0); Graphics_setViewport (my graphics, my selx1, my selx2, my sely1, my sely2); if (my sensitive) { my selectionGraphics = Graphics_create_xmdrawingarea (my drawingArea); Graphics_setWindow (my selectionGraphics, 0, 12, 0, 12); GuiDrawingArea_setClickCallback (my drawingArea, gui_drawingarea_cb_click, me); } Graphics_startRecording (my graphics); return me; } catch (MelderError) { if (me) Melder_free (me); Melder_throw ("Picture not created."); } } void Picture_setSelectionChangedCallback (Picture me, void (*selectionChangedCallback) (Picture, XtPointer, double, double, double, double), XtPointer selectionChangedClosure) { my selectionChangedCallback = selectionChangedCallback; my selectionChangedClosure = selectionChangedClosure; } void Picture_setMouseSelectsInnerViewport (Picture me, int mouseSelectsInnerViewport) { my mouseSelectsInnerViewport = mouseSelectsInnerViewport; } void Picture_remove (Picture *pme) { Picture me = *pme; if (! me) return; Picture_erase (me); forget (my graphics); if (my sensitive) forget (my selectionGraphics); Melder_free (me); *pme = NULL; } Graphics Picture_getGraphics (Picture me) { return my graphics; } void Picture_unhighlight (Picture me) { if (my drawingArea) drawSelection (me, 0); // unselect } void Picture_highlight (Picture me) { if (my drawingArea) drawSelection (me, 1); // select } void Picture_erase (Picture me) { Graphics_clearRecording (my graphics); Graphics_clearWs (my graphics); if (my drawingArea) { drawMarkers (me); drawSelection (me, 1); } } void Picture_writeToPraatPictureFile (Picture me, MelderFile file) { try { autofile f = Melder_fopen (file, "wb"); if (fprintf (f, "PraatPictureFile") < 0) Melder_throw ("Write error."); Graphics_writeRecordings (my graphics, f); f.close (file); } catch (MelderError) { Melder_throw ("Cannot write Praat picture file ", file, "."); } } void Picture_readFromPraatPictureFile (Picture me, MelderFile file) { try { autofile f = Melder_fopen (file, "rb"); char line [200]; int n = fread (line, 1, 199, f); line [n] = '\0'; const char *tag = "PraatPictureFile"; char *end = strstr (line, tag); if (! end) Melder_throw ("This is not a Praat picture file."); *end = '\0'; rewind (f); fread (line, 1, end - line + strlen (tag), f); Graphics_readRecordings (my graphics, f); Graphics_updateWs (my graphics); f.close (file); } catch (MelderError) { Melder_throw ("Praat picture not read from file ", file); } } #ifdef macintosh static size_t appendBytes (void *info, const void *buffer, size_t count) { CFDataAppendBytes ((CFMutableDataRef) info, (const UInt8 *) buffer, count); return count; } void Picture_copyToClipboard (Picture me) { /* * Find the clipboard and clear it. */ PasteboardRef clipboard = NULL; PasteboardCreate (kPasteboardClipboard, & clipboard); PasteboardClear (clipboard); /* * Add a PDF flavour to the clipboard. */ static CGDataConsumerCallbacks callbacks = { appendBytes, NULL }; CFDataRef data = CFDataCreateMutable (kCFAllocatorDefault, 0); CGDataConsumerRef consumer = CGDataConsumerCreate ((void *) data, & callbacks); int resolution = 600; CGRect rect = CGRectMake (0, 0, (my selx2 - my selx1) * resolution, (my sely1 - my sely2) * resolution); CGContextRef context = CGPDFContextCreate (consumer, & rect, NULL); //my selx1 * RES, (12 - my sely2) * RES, my selx2 * RES, (12 - my sely1) * RES) Graphics graphics = Graphics_create_pdf (context, resolution, my selx1, my selx2, my sely1, my sely2); Graphics_play ((Graphics) my graphics, graphics); forget (graphics); PasteboardPutItemFlavor (clipboard, (PasteboardItemID) 1, kUTTypePDF, data, kPasteboardFlavorNoFlags); CFRelease (data); /* * Forget the clipboard. */ CFRelease (clipboard); } #endif #ifdef _WIN32 /* Windows pictures. */ #define WIN_WIDTH 7.5 #define WIN_HEIGHT 11 static HENHMETAFILE copyToMetafile (Picture me) { RECT rect; HDC dc; PRINTDLG defaultPrinter; int resolution; memset (& defaultPrinter, 0, sizeof (PRINTDLG)); defaultPrinter. lStructSize = sizeof (PRINTDLG); defaultPrinter. Flags = PD_RETURNDEFAULT | PD_RETURNDC; PrintDlg (& defaultPrinter); SetRect (& rect, my selx1 * 2540, (12 - my sely2) * 2540, my selx2 * 2540, (12 - my sely1) * 2540); dc = CreateEnhMetaFile (defaultPrinter. hDC, NULL, & rect, L"Praat\0"); if (! dc) Melder_throw ("Cannot create Windows metafile."); resolution = GetDeviceCaps (dc, LOGPIXELSX); // Virtual PC: 360 if (Melder_debug == 6) { DEVMODE *devMode = * (DEVMODE **) defaultPrinter. hDevMode; MelderInfo_open (); MelderInfo_writeLine1 (L"DEVICE CAPS:"); MelderInfo_writeLine4 (L"aspect x ", Melder_integer (GetDeviceCaps (dc, ASPECTX)), L" y ", Melder_integer (GetDeviceCaps (dc, ASPECTY))); MelderInfo_writeLine4 (L"res(pixels) hor ", Melder_integer (GetDeviceCaps (dc, HORZRES)), L" vert ", Melder_integer (GetDeviceCaps (dc, VERTRES))); MelderInfo_writeLine4 (L"size(mm) hor ", Melder_integer (GetDeviceCaps (dc, HORZSIZE)), L" vert ", Melder_integer (GetDeviceCaps (dc, VERTSIZE))); MelderInfo_writeLine4 (L"pixels/inch hor ", Melder_integer (GetDeviceCaps (dc, LOGPIXELSX)), L" vert ", Melder_integer (GetDeviceCaps (dc, LOGPIXELSY))); MelderInfo_writeLine4 (L"physicalOffset(pixels) hor ", Melder_integer (GetDeviceCaps (dc, PHYSICALOFFSETX)), L" vert ", Melder_integer (GetDeviceCaps (dc, PHYSICALOFFSETY))); MelderInfo_writeLine1 (L"PRINTER:"); MelderInfo_writeLine2 (L"dmFields ", Melder_integer (devMode -> dmFields)); if (devMode -> dmFields & DM_YRESOLUTION) MelderInfo_writeLine2 (L"y resolution ", Melder_integer (devMode -> dmYResolution)); if (devMode -> dmFields & DM_PRINTQUALITY) MelderInfo_writeLine2 (L"print quality ", Melder_integer (devMode -> dmPrintQuality)); if (devMode -> dmFields & DM_PAPERWIDTH) MelderInfo_writeLine2 (L"paper width ", Melder_integer (devMode -> dmPaperWidth)); if (devMode -> dmFields & DM_PAPERLENGTH) MelderInfo_writeLine2 (L"paper length ", Melder_integer (devMode -> dmPaperLength)); if (devMode -> dmFields & DM_PAPERSIZE) MelderInfo_writeLine2 (L"paper size ", Melder_integer (devMode -> dmPaperSize)); if (devMode -> dmFields & DM_ORIENTATION) MelderInfo_writeLine2 (L"orientation ", Melder_integer (devMode -> dmOrientation)); MelderInfo_close (); } autoGraphics pictGraphics = Graphics_create_screen ((void *) dc, NULL, resolution); Graphics_setWsViewport (pictGraphics.peek(), 0, WIN_WIDTH * resolution, 0, WIN_HEIGHT * resolution); Graphics_setWsWindow (pictGraphics.peek(), 0.0, WIN_WIDTH, 12.0 - WIN_HEIGHT, 12.0); Graphics_play ((Graphics) my graphics, pictGraphics.peek()); HENHMETAFILE metafile = CloseEnhMetaFile (dc); return metafile; } void Picture_copyToClipboard (Picture me) { try { HENHMETAFILE metafile = copyToMetafile (me); OpenClipboard (NULL); EmptyClipboard (); SetClipboardData (CF_ENHMETAFILE, metafile); CloseClipboard (); /* * We should NOT call DeleteEnhMetaFile, * because the clipboard becomes the owner of this global memory object. */ } catch (MelderError) { Melder_throw ("Picture not copied to clipboard."); } } void Picture_writeToWindowsMetafile (Picture me, MelderFile file) { try { HENHMETAFILE metafile = copyToMetafile (me); MelderFile_delete (file); // overwrite any existing file with the same name DeleteEnhMetaFile (CopyEnhMetaFile (metafile, file -> path)); DeleteEnhMetaFile (metafile); } catch (MelderError) { Melder_throw ("Picture not written to Windows metafile ", file); } } #endif void Picture_writeToEpsFile (Picture me, MelderFile file, int includeFonts, int useSilipaPS) { try { MelderFile_delete (file); // to kill resources as well (fopen only kills data fork) /* BUG: no message if file cannot be deleted (e.g. because still open by Microsoft Word 2001 after reading). */ { // scope autoGraphics ps = Graphics_create_epsfile (file, 600, thePrinter. spots, my selx1, my selx2, my sely1, my sely2, includeFonts, useSilipaPS); Graphics_play ((Graphics) my graphics, ps.peek()); } MelderFile_setMacTypeAndCreator (file, 'EPSF', 'vgrd'); } catch (MelderError) { Melder_throw ("Picture not written to EPS file ", file); } } void Picture_writeToPdfFile (Picture me, MelderFile file) { try { autoGraphics graphics = Graphics_create_pdffile (file, 300, my selx1, my selx2, my sely1, my sely2); Graphics_play ((Graphics) my graphics, graphics.peek()); } catch (MelderError) { Melder_throw ("Picture not written to PDF file ", file, "."); } } static void print (I, Graphics printer) { iam (Picture); Graphics_play ((Graphics) my graphics, printer); } void Picture_print (Picture me) { try { Printer_print (print, me); therror } catch (MelderError) { Melder_flushError ("Picture not printed."); } } void Picture_setSelection (Picture me, double x1NDC, double x2NDC, double y1NDC, double y2NDC, Boolean notify) { if (my drawingArea) { #if gtk long x1, x2, y1, y2; Graphics_WCtoDC (my selectionGraphics, my selx1, my sely1, & x1, & y1); Graphics_WCtoDC (my selectionGraphics, my selx2, my sely2, & x2, & y2); gtk_widget_queue_draw_area (GTK_WIDGET (my drawingArea), x1, y2, abs (x2 - x1), abs (y2 - y1)); #else drawSelection (me, 0); // unselect #endif } my selx1 = x1NDC; my selx2 = x2NDC; my sely1 = y1NDC; my sely2 = y2NDC; if (my drawingArea) { #if gtk long x1, x2, y1, y2; Graphics_WCtoDC (my selectionGraphics, my selx1, my sely1, & x1, & y1); Graphics_WCtoDC (my selectionGraphics, my selx2, my sely2, & x2, & y2); gtk_widget_queue_draw_area (GTK_WIDGET (my drawingArea), x1, y2, abs (x2 - x1), abs (y2 - y1)); #else drawSelection (me, 1); // select #endif } if (notify && my selectionChangedCallback) { //Melder_casual ("selectionChangedCallback from Picture_setSelection"); my selectionChangedCallback (me, my selectionChangedClosure, my selx1, my selx2, my sely1, my sely2); } } void Picture_background (Picture me) { my backgrounding = TRUE; } void Picture_foreground (Picture me) { my backgrounding = FALSE; } #if gtk void Picture_selfExpose (Picture me) { if (my drawingArea) { long x1, x2, y1, y2; Graphics_WCtoDC (my selectionGraphics, my selx1, my sely1, & x1, & y1); Graphics_WCtoDC (my selectionGraphics, my selx2, my sely2, & x2, & y2); gtk_widget_queue_draw_area (GTK_WIDGET (my drawingArea), x1, y2, abs (x2 - x1), abs (y2 - y1)); } } #endif /* End of file Picture.cpp */ sources_5316/sys/DemoEditor.cpp0000644000176700017670000003063311753752150015313 0ustar paulpaul/* DemoEditor.cpp * * Copyright (C) 2009-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "DemoEditor.h" #include "machine.h" #include "praatP.h" #include "UnicodeData.h" Thing_implement (DemoEditor, Editor, 0); static DemoEditor theDemoEditor; /***** DemoEditor methods *****/ void structDemoEditor :: v_destroy () { Melder_free (praatPicture); forget (graphics); theDemoEditor = NULL; DemoEditor_Parent :: v_destroy (); } void structDemoEditor :: v_info () { DemoEditor_Parent :: v_info (); MelderInfo_writeLine2 (L"Colour: ", Graphics_Colour_name (((PraatPicture) praatPicture) -> colour)); MelderInfo_writeLine2 (L"Font: ", kGraphics_font_getText (((PraatPicture) praatPicture) -> font)); MelderInfo_writeLine2 (L"Font size: ", Melder_integer (((PraatPicture) praatPicture) -> fontSize)); } void structDemoEditor :: v_goAway () { if (waitingForInput) { userWantsToClose = true; } else { DemoEditor_Parent :: v_goAway (); } } void structDemoEditor :: v_createMenus () { DemoEditor_Parent :: v_createMenus (); } static void gui_drawingarea_cb_expose (I, GuiDrawingAreaExposeEvent event) { iam (DemoEditor); (void) event; if (my graphics == NULL) return; // Could be the case in the very beginning. /* * Erase the background. Don't record this erasure! */ Graphics_stopRecording (my graphics); // the only place in Praat (the Picture window has a separate Graphics for erasing)? Graphics_setColour (my graphics, Graphics_WHITE); Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_fillRectangle (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_BLACK); Graphics_startRecording (my graphics); Graphics_play (my graphics, my graphics); } static void gui_drawingarea_cb_click (I, GuiDrawingAreaClickEvent event) { iam (DemoEditor); if (my graphics == NULL) return; // Could be the case in the very beginning. if (gtk && event -> type != BUTTON_PRESS) return; my clicked = true; my keyPressed = false; my x = event -> x; my y = event -> y; my key = UNICODE_BULLET; my shiftKeyPressed = event -> shiftKeyPressed; my commandKeyPressed = event -> commandKeyPressed; my optionKeyPressed = event -> optionKeyPressed; my extraControlKeyPressed = event -> extraControlKeyPressed; } static void gui_drawingarea_cb_key (I, GuiDrawingAreaKeyEvent event) { iam (DemoEditor); if (my graphics == NULL) return; // Could be the case in the very beginning. my clicked = false; my keyPressed = true; my x = 0; my y = 0; my key = event -> key; my shiftKeyPressed = event -> shiftKeyPressed; my commandKeyPressed = event -> commandKeyPressed; my optionKeyPressed = event -> optionKeyPressed; my extraControlKeyPressed = event -> extraControlKeyPressed; } static void gui_drawingarea_cb_resize (I, GuiDrawingAreaResizeEvent event) { iam (DemoEditor); if (my graphics == NULL) return; // Could be the case in the very beginning. Dimension marginWidth = 0, marginHeight = 0; Graphics_setWsViewport (my graphics, marginWidth, event -> width - marginWidth, marginHeight, event -> height - marginHeight); Graphics_setWsWindow (my graphics, 0, 100, 0, 100); Graphics_setViewport (my graphics, 0, 100, 0, 100); Graphics_updateWs (my graphics); } void structDemoEditor :: v_createChildren () { drawingArea = GuiDrawingArea_createShown (d_windowForm, 0, 0, 0, 0, gui_drawingarea_cb_expose, gui_drawingarea_cb_click, gui_drawingarea_cb_key, gui_drawingarea_cb_resize, this, 0); #if gtk gtk_widget_set_double_buffered (GTK_WIDGET (drawingArea), FALSE); #endif } void DemoEditor_init (DemoEditor me, GuiObject parent) { Editor_init (me, parent, 0, 0, 1024, 768, L"", NULL); my graphics = Graphics_create_xmdrawingarea (my drawingArea); Graphics_setColour (my graphics, Graphics_WHITE); Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_fillRectangle (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_BLACK); Graphics_startRecording (my graphics); //Graphics_setViewport (my graphics, 0, 100, 0, 100); //Graphics_setWindow (my graphics, 0, 100, 0, 100); //Graphics_line (my graphics, 0, 100, 100, 0); struct structGuiDrawingAreaResizeEvent event = { my drawingArea, 0 }; event. width = GuiObject_getWidth (my drawingArea); event. height = GuiObject_getHeight (my drawingArea); gui_drawingarea_cb_resize (me, & event); } DemoEditor DemoEditor_create (GuiObject parent) { try { autoDemoEditor me = Thing_new (DemoEditor); DemoEditor_init (me.peek(), parent); return me.transfer(); } catch (MelderError) { Melder_throw ("Demo window not created."); } } void Demo_open (void) { #ifndef CONSOLE_APPLICATION if (Melder_batch) { /* * Batch scripts have to be able to run demos. */ //Melder_batch = false; } if (theDemoEditor == NULL) { theDemoEditor = DemoEditor_create ((GuiObject) Melder_topShell); Melder_assert (theDemoEditor != NULL); //GuiObject_show (theDemoEditor -> d_windowForm); theDemoEditor -> praatPicture = Melder_calloc_f (structPraatPicture, 1); theCurrentPraatPicture = (PraatPicture) theDemoEditor -> praatPicture; theCurrentPraatPicture -> graphics = theDemoEditor -> graphics; theCurrentPraatPicture -> font = kGraphics_font_HELVETICA; theCurrentPraatPicture -> fontSize = 10; theCurrentPraatPicture -> lineType = Graphics_DRAWN; theCurrentPraatPicture -> colour = Graphics_BLACK; theCurrentPraatPicture -> lineWidth = 1.0; theCurrentPraatPicture -> arrowSize = 1.0; theCurrentPraatPicture -> x1NDC = 0; theCurrentPraatPicture -> x2NDC = 100; theCurrentPraatPicture -> y1NDC = 0; theCurrentPraatPicture -> y2NDC = 100; } if (theDemoEditor -> waitingForInput) Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); theCurrentPraatPicture = (PraatPicture) theDemoEditor -> praatPicture; #endif } void Demo_close (void) { theCurrentPraatPicture = & theForegroundPraatPicture; } int Demo_windowTitle (const wchar_t *title) { autoDemoOpen demo; Thing_setName (theDemoEditor, title); return 1; } int Demo_show (void) { if (theDemoEditor == NULL) return 0; autoDemoOpen demo; GuiObject_show (theDemoEditor -> d_windowForm); GuiWindow_drain (theDemoEditor -> d_windowShell); return 1; } void Demo_waitForInput (Interpreter interpreter) { if (theDemoEditor == NULL) return; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } //GuiObject_show (theDemoEditor -> d_windowForm); theDemoEditor -> clicked = false; theDemoEditor -> keyPressed = false; theDemoEditor -> waitingForInput = true; #if ! defined (CONSOLE_APPLICATION) { // scope autoMelderSaveDefaultDir saveDir; bool wasBackgrounding = Melder_backgrounding; if (wasBackgrounding) praat_foreground (); try { #if gtk do { gtk_main_iteration (); } while (! theDemoEditor -> clicked && ! theDemoEditor -> keyPressed && ! theDemoEditor -> userWantsToClose); #elif defined (_WIN32) do { XEvent event; GuiNextEvent (& event); XtDispatchEvent (& event); } while (! theDemoEditor -> clicked && ! theDemoEditor -> keyPressed && ! theDemoEditor -> userWantsToClose); #elif defined (macintosh) #if useCarbon do { XEvent event; GuiNextEvent (& event); XtDispatchEvent (& event); } while (! theDemoEditor -> clicked && ! theDemoEditor -> keyPressed && ! theDemoEditor -> userWantsToClose); #else #endif #endif } catch (MelderError) { Melder_flushError ("An error made it to the outer level in the Demo window; should not occur! Please write to paul.boersma@uva.nl"); } if (wasBackgrounding) praat_background (); } #endif theDemoEditor -> waitingForInput = false; if (theDemoEditor -> userWantsToClose) { Interpreter_stop (interpreter); forget (theDemoEditor); Melder_throw ("You interrupted the script."); } } bool Demo_clicked (void) { if (theDemoEditor == NULL) return false; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } return theDemoEditor -> clicked; } double Demo_x (void) { if (theDemoEditor == NULL) return NUMundefined; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } Graphics_setInner (theDemoEditor -> graphics); double xWC, yWC; Graphics_DCtoWC (theDemoEditor -> graphics, theDemoEditor -> x, theDemoEditor -> y, & xWC, & yWC); Graphics_unsetInner (theDemoEditor -> graphics); return xWC; } double Demo_y (void) { if (theDemoEditor == NULL) return NUMundefined; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } Graphics_setInner (theDemoEditor -> graphics); double xWC, yWC; Graphics_DCtoWC (theDemoEditor -> graphics, theDemoEditor -> x, theDemoEditor -> y, & xWC, & yWC); Graphics_unsetInner (theDemoEditor -> graphics); return yWC; } bool Demo_keyPressed (void) { if (theDemoEditor == NULL) return false; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } return theDemoEditor -> keyPressed; } wchar Demo_key (void) { if (theDemoEditor == NULL) return 0; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } return theDemoEditor -> key; } bool Demo_shiftKeyPressed (void) { if (theDemoEditor == NULL) return false; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } return theDemoEditor -> shiftKeyPressed; } bool Demo_commandKeyPressed (void) { if (theDemoEditor == NULL) return false; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } return theDemoEditor -> commandKeyPressed; } bool Demo_optionKeyPressed (void) { if (theDemoEditor == NULL) return false; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } return theDemoEditor -> optionKeyPressed; } bool Demo_extraControlKeyPressed (void) { if (theDemoEditor == NULL) return false; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } return theDemoEditor -> extraControlKeyPressed; } bool Demo_input (const wchar_t *keys) { if (theDemoEditor == NULL) return false; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } return wcschr (keys, theDemoEditor -> key) != NULL; } bool Demo_clickedIn (double left, double right, double bottom, double top) { if (theDemoEditor == NULL || ! theDemoEditor -> clicked) return false; if (theDemoEditor -> waitingForInput) { Melder_throw ("You cannot work with the Demo window while it is waiting for input. " "Please click or type into the Demo window or close it."); } double xWC = Demo_x (), yWC = Demo_y (); return xWC >= left && xWC < right && yWC >= bottom && yWC < top; } /* End of file DemoEditor.cpp */ sources_5316/sys/Simple_def.h0000644000176700017670000000242611724661154014774 0ustar paulpaul/* Simple_def.h * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT SimpleInt oo_DEFINE_CLASS (SimpleInt, Data) oo_INT (number) oo_END_CLASS (SimpleInt) #undef ooSTRUCT #define ooSTRUCT SimpleLong oo_DEFINE_CLASS (SimpleLong, Data) oo_LONG (number) oo_END_CLASS (SimpleLong) #undef ooSTRUCT #define ooSTRUCT SimpleDouble oo_DEFINE_CLASS (SimpleDouble, Data) oo_DOUBLE (number) oo_END_CLASS (SimpleDouble) #undef ooSTRUCT #define ooSTRUCT SimpleString oo_DEFINE_CLASS (SimpleString, Data) oo_STRING (string) oo_END_CLASS (SimpleString) #undef ooSTRUCT /* End of file Simple_def.h */ sources_5316/sys/site.h0000644000176700017670000000165011611106371013655 0ustar paulpaul#ifndef _site_h_ #define _site_h_ /* site.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ wchar_t *Site_getPrintCommand (void); void Site_setPrintCommand (const wchar_t *text); void Site_prefs (void); /* End of file site.h */ #endif sources_5316/sys/Collection.h0000644000176700017670000002326211724661150015015 0ustar paulpaul#ifndef _Collection_h_ #define _Collection_h_ /* Collection.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * Collection objects contain a number of items whose class is a subclass of Data. */ #include "Simple.h" Thing_define (Collection, Data) { // new data: public: ClassInfo itemClass; // the class of which all items must be members (see Thing_member) long _capacity, size; bool _dontOwnItems; Any *item; // [1..size] // overridden methods: public: virtual void v_info (); virtual void v_destroy (); // destroys all the items virtual void v_copy (Any data_to); // copies all the items virtual bool v_equal (Any data2); // compares 'my item [i]' with 'thy item [i]', i = 1..size virtual bool v_canWriteAsEncoding (int outputEncoding); virtual void v_writeText (MelderFile openFile); virtual void v_readText (MelderReadText text); virtual void v_writeBinary (FILE *f); virtual void v_readBinary (FILE *f); static Data_Description s_description; virtual Data_Description v_description () { return s_description; } virtual long v_position (Any data) { (void) data; return size + 1; // at end }; }; /* An object of type Collection is a collection of items of any class. It is the owner of its items. You can access the items in the collection as item [1] through item [size]. There can be no NULL items. Attributes: _capacity >= size // private; grows as you add items. size // the current number of items. item [1..size] // the items. */ void Collection_init (Collection me, ClassInfo itemClass, long initialCapacity); Collection Collection_create (ClassInfo itemClass, long initialCapacity); /* Function: return a new empty Collection, or NULL if out of memory. Preconditions: initialCapacity >= 1; Postconditions: my _capacity == initialCapacity; */ void Collection_dontOwnItems (Collection me); /* Data_copy, Data_equal, Data_writeXXX, Data_readXXX try to copy, compare, write, or read all the items. However, if any of the items is not of class Data, these routines fail with a message and return 0. */ void Collection_addItem (Collection me, Thing item); /* Function: add the 'item' to the collection. Return 0 if out of memory, else 1. Preconditions: item != NULL; Postconditions if result == 1: my size >= my old size + 1; if (my size > my old _capacity) my _capacity == 2 * my old _capacity; When calling this function, you transfer ownership of 'item' to the Collection, unless dontOwnItems is on. For a SortedSet, this may mean that the Collection immediately disposes of 'item', if that item already occurred in the Collection. */ void Collection_removeItem (Collection me, long position); /* Function: remove the item at 'position' from the collection and from memory. Preconditions: 1 <= position <= my size; Postconditions: my size == my old size - 1; my _capacity not changed; */ void Collection_undangleItem (Collection me, Thing item); /* Function: remove the item from the collection, without destroying it. Postconditions: item not found || my size == my old size - 1; Usage: this is the way in which an item can detach itself from a list; often used just before the item is destroyed, hence the name of this procedure. */ Any Collection_subtractItem (Collection me, long position); /* Function: remove the item at 'position' from the collection and transfer ownership to the caller. Return value: the subtracted item; the caller is responsible for eventually removing it. Preconditions: 1 <= position <= my size; Postconditions: my size == my old size - 1; my _capacity not changed; */ void Collection_removeAllItems (Collection me); /* Function: remove all items from the collection and from memory. Postconditions: my size == 0; my _capacity not changed; */ void Collection_shrinkToFit (Collection me); /* Function: release as much memory as possible without affecting the items. Postconditions: my _capacity == max (my size, 1); */ Any Collections_merge (Collection me, Collection thee); /* Function: merge two Collections into a new one. Postconditions: result -> size >= my size; result -> size >= thy size; */ /* For the inheritors. */ void _Collection_insertItem (Collection me, Thing item, long position); /* Methods: static long position (I, Any data, long hint); Question asked by Collection_addItem: return a position for the data. Collection::position always returns my size + 1 (add item at the end). */ /********** class Ordered **********/ Thing_define (Ordered, Collection) { }; Ordered Ordered_create (void); void Ordered_init (Ordered me, ClassInfo itemClass, long initialCapacity); /* Behaviour: Collection_addItem (Ordered) inserts an item at the end. */ void Ordered_addItemPos (Ordered me, Thing data, long position); /* Function: insert an item at 'position'. If 'position' is less than 1 or greater than the current 'size', insert the item at the end. */ /********** class Sorted **********/ /* A Sorted is a sorted Collection. */ Thing_define (Sorted, Collection) { // new methods: public: virtual long v_position (Any data); static int s_compare (Any data1, Any data2); virtual Data_CompareFunction v_getCompareFunction () { return s_compare; } // should compare the keys of two items; returns negative if me < thee, 0 if me == thee, and positive if me > thee }; void Sorted_init (Sorted me, ClassInfo itemClass, long initialCapacity); /* Behaviour: Collection_addItem (Sorted) inserts an item at such a position that the collection stays sorted. Collections_merge (Sorted) yields a Sorted. */ /***** Two routines for optimization. ******/ /* If you want to add a large group of items, it is best to call Sorted_addItem_unsorted () repeatedly, and finish with Sorted_sort (); this uses the fast 'heapsort' algorithm. Calling Collection_addItem () repeatedly would be slower, because on the average half the collection is moved in memory with every insertion. */ void Sorted_addItem_unsorted (Sorted me, Thing data); /* Function: add an item to the collection, quickly at the end. Warning: this leaves the collection unsorted; follow by Sorted_sort (). */ void Sorted_sort (Sorted me); /* Call this after a number of calls to Sorted_addItem_unsorted (). */ /* The procedure used is 'heapsort'. */ /********** class SortedSet **********/ Thing_define (SortedSet, Sorted) { // every item must be unique (by key) // functions: public: bool hasItem (Any a_item) { return v_position (a_item) == 0; } // overridden methods: protected: virtual long v_position (Any data); // returns 0 (refusal) if the key of 'data' already occurs }; void SortedSet_init (SortedSet me, ClassInfo itemClass, long initialCapacity); /* Behaviour: Collection_addItem (SortedSet) refuses to insert an item if this item already occurs. Equality is there when the compare routine returns 0. Collections_merge (SortedSet) yields a SortedSet that is the union of the two sources. */ /********** class SortedSetOfInt **********/ Thing_define (SortedSetOfInt, SortedSet) { // overridden methods: static int s_compare (Any data1, Any data2); virtual Data_CompareFunction v_getCompareFunction () { return s_compare; } }; void SortedSetOfInt_init (SortedSetOfInt me); SortedSetOfInt SortedSetOfInt_create (void); /********** class SortedSetOfLong **********/ Thing_define (SortedSetOfLong, SortedSet) { // overridden methods: static int s_compare (Any data1, Any data2); virtual Data_CompareFunction v_getCompareFunction () { return s_compare; } }; void SortedSetOfLong_init (SortedSetOfLong me); SortedSetOfLong SortedSetOfLong_create (void); /********** class SortedSetOfDouble **********/ Thing_define (SortedSetOfDouble, SortedSet) { // overridden methods: static int s_compare (Any data1, Any data2); virtual Data_CompareFunction v_getCompareFunction () { return s_compare; } }; void SortedSetOfDouble_init (SortedSetOfDouble me); SortedSetOfDouble SortedSetOfDouble_create (void); template class SortedSetOfDouble_vector : public structSortedSetOfDouble { T& operator[] (long i) { return (T) item [i]; } }; /********** class SortedSetOfString **********/ Thing_define (SortedSetOfString, SortedSet) { // functions: public: void addString (const wchar *string); // overridden methods: protected: static int s_compare (Any data1, Any data2); virtual Data_CompareFunction v_getCompareFunction () { return s_compare; } }; void SortedSetOfString_init (SortedSetOfString me); SortedSetOfString SortedSetOfString_create (void); long SortedSetOfString_lookUp (SortedSetOfString me, const wchar_t *string); /********** class Cyclic **********/ Thing_define (Cyclic, Collection) { // the cyclic list (a, b, c, d) equals (b, c, d, a) but not (d, c, a, b) // functions: public: void cycleLeft (); void unicize (); // overridden methods: protected: static int s_compare (Any data1, Any data2); virtual Data_CompareFunction v_getCompareFunction () { return s_compare; } }; void Cyclic_init (Cyclic me, ClassInfo itemClass, long initialCapacity); /* End of file Collection.h */ #endif sources_5316/sys/praat.h0000644000176700017670000006347111752477412014046 0ustar paulpaul/* praat.h * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Editor.h" #include "Manual.h" #include "Preferences.h" /* The explanations in this header file assume that you put your extra commands in praat_Sybil.cpp and the main() function in main_Sybil.cpp, but these files may have different names if you are not Sybil. Linking with the rest of Praat will create an executable that has all the functionality of the basic Praat, plus everything that you made available in praat_Sybil.cpp. */ /* Program example: // File main_Sybil.cpp: // int main (unsigned int argc, char **argv) { praat_init ("Praat_Sybil", argc, argv); // Obligatory. INCLUDE_LIBRARY (praat_Fon_init) // Optional: inherit phonetic stuff. INCLUDE_LIBRARY (praat_Sybil_init) // Optional: add Sybil's things. INCLUDE_MANPAGES (manual_Sybil) praat_run (); // Obligatory. } // File praat_Sybil.cpp: // void praat_Sybil (void) { ... ... } The dots consist of, in any order: Thing_recognizeClassesByName (...); Data_recognizeFileType (...); praat_addMenuCommand (...); praat_addAction (...); All of these statements are optional and may occur more than once. To make any class string-readable, use Thing_recognizeClassesByName (). String-readable classes are known by Thing_newFromClassName () and can therefore be read by Data_readFromTextFile () and Data_readFromBinaryFile (). */ void praat_init (const char *title, unsigned int argc, char **argv); void praat_run (void); void praat_setStandAloneScriptText (wchar *text); // call before praat_init if you want to create a stand-alone application without Objects and Picture window void praat_addAction (ClassInfo class1, int n1, ClassInfo class2, int n2, ClassInfo class3, int n3, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure)); /* 'class2', 'class3', 'title', 'after', and 'callback' may be NULL; 'title' is reference-copied. */ void praat_addAction1 (ClassInfo class1, int n1, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure)); void praat_addAction2 (ClassInfo class1, int n1, ClassInfo class2, int n2, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure)); void praat_addAction3 (ClassInfo class1, int n1, ClassInfo class2, int n2, ClassInfo class3, int n3, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure)); void praat_addAction4 (ClassInfo class1, int n1, ClassInfo class2, int n2, ClassInfo class3, int n3, ClassInfo class4, int n4, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure)); /* 'title' is the name that will appear in the dynamic menu, and also the command that is used in command files. 'callback' refers to a function prototyped like this: static int DO_Class_action (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, void *closure); this function should return 0 if the command failed, and 1 if the command was executed successfully; this function will be called by 'praat' when the user clicks a menu command, in which case 'sendingForm', 'sendingString' and 'closure' will be NULL; it is also called by scripts, in which case 'sendingString' is the argument list (after the dots). When called by Ui (after UiForm_create), 'sendingForm' is the UiForm, and 'closure' is the closure you passed to UiForm_create (which may be an editor). The availability of the dynamic commands depends on the current selection: e.g., if the user has selected three objects of type Matrix and nothing else, the commands registered with praat_addAction (classMatrix, n, 0, 0, 0, 0, "xxx", "xxxx", x, DO_xxx) are visible, and those with n=0 or n=3 are executable (the buttons are sensitive) and, if chosen, performed on each of these three objects; if the user has selected one object of type Artword and one of type Speaker, the commands from praat_addAction (classArtword, 1, classSpeaker, 1, ...) are executable. You may want to restrict the availability to one object for commands that write objects to file, commands that present information in a dialog, or the Edit command. */ #define praat_INSENSITIVE GuiMenu_INSENSITIVE #define praat_CHECKBUTTON GuiMenu_CHECKBUTTON #define praat_TOGGLE_ON GuiMenu_TOGGLE_ON #define praat_ATTRACTIVE GuiMenu_ATTRACTIVE #define praat_RADIO_FIRST GuiMenu_RADIO_FIRST #define praat_RADIO_NEXT GuiMenu_RADIO_NEXT #define praat_HIDDEN 0x00004000 #define praat_UNHIDABLE 0x00008000 #define praat_DEPTH_1 0x00010000 #define praat_DEPTH_2 0x00020000 #define praat_DEPTH_3 0x00030000 #define praat_DEPTH_4 0x00040000 #define praat_DEPTH_5 0x00050000 #define praat_DEPTH_6 0x00060000 #define praat_DEPTH_7 0x00070000 #define praat_CTRL 0x00200000 void praat_removeAction (ClassInfo class1, ClassInfo class2, ClassInfo class3, const wchar *title); /* 'class2' and 'class3' may be NULL. */ /* 'title' may be NULL; reference-copied. */ GuiObject praat_addMenuCommand (const wchar *window, const wchar *menu, const wchar *title, const wchar *after, unsigned long flags, void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *)); /* All strings are reference-copied; 'title', 'after', and 'callback' may be NULL. */ #define praat_MAXNUM_EDITORS 5 #include "Ui.h" typedef struct { ClassInfo klas; // the class Data object; // the instance wchar *name; // the name of the object as it appears in the List long id; // the unique number of the object int selected; // is the name of the object inverted in the list? Editor editors [praat_MAXNUM_EDITORS]; // are there editors open with this Object in it? structMelderFile file; // is this (very large) Object (partially) in a file? int _beingCreated; } structPraat_Object, *praat_Object; #define praat_MAXNUM_OBJECTS 10000 /* Maximum number of objects in the list. */ typedef struct { /* Readonly */ MelderString batchName; /* The name of the command file when called from batch. */ int batch; /* Was the program called from the command line? */ GuiObject topShell; /* The application shell: parent of editors and standard dialogs. */ ManPages manPages; } structPraatApplication, *PraatApplication; typedef struct { /* Readonly */ int n; /* The current number of objects in the list. */ structPraat_Object list [1 + praat_MAXNUM_OBJECTS]; /* The list of objects: list [1..n]. */ int totalSelection; /* The total number of selected objects, <= n. */ int numberOfSelected [1 + 1000]; /* For each (readable) class. */ int totalBeingCreated; long uniqueId; } structPraatObjects, *PraatObjects; typedef struct { /* Readonly */ Graphics graphics; /* The Graphics associated with the Picture window or HyperPage window or Demo window. */ int font, fontSize, lineType; Graphics_Colour colour; double lineWidth, arrowSize, x1NDC, x2NDC, y1NDC, y2NDC; } structPraatPicture, *PraatPicture; extern structPraatApplication theForegroundPraatApplication; extern PraatApplication theCurrentPraatApplication; extern structPraatObjects theForegroundPraatObjects; extern PraatObjects theCurrentPraatObjects; extern structPraatPicture theForegroundPraatPicture; extern PraatPicture theCurrentPraatPicture; /* The global objects containing the state of the application; only reachable from interface files. */ Data praat_onlyObject (ClassInfo klas); /* Returns a selected Data of class 'klas'. */ Data praat_onlyObject_generic (ClassInfo klas); /* Returns a selected Data of class 'klas' or a subclass. */ praat_Object praat_onlyScreenObject (void); wchar *praat_name (int iobject); void praat_write_do (Any dia, const wchar *extension); void praat_new1 (Data me, const wchar *s1); void praat_new2 (Data me, const wchar *s1, const wchar *s2); void praat_new3 (Data me, const wchar *s1, const wchar *s2, const wchar *s3); void praat_new4 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); void praat_new5 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); void praat_new6 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); void praat_new7 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); void praat_new8 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); void praat_new9 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); void praat_newWithFile1 (Data me, const wchar *s1, MelderFile file); void praat_newWithFile2 (Data me, const wchar *s1, const wchar *s2, MelderFile file); void praat_newWithFile3 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, MelderFile file); void praat_newWithFile4 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, MelderFile file); void praat_newWithFile5 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, MelderFile file); void praat_name2 (wchar *name, ClassInfo klas1, ClassInfo klas2); /* Macros for description of forms (dialog boxes). FORM prompts the user for arguments to DO_proc. Macros for FORM: FORM (proc, title, helpString) 'proc' is the 'cb' argument of the corresponding VERB macro. 'title' is the title of the standard dialog, shown in its title bar. 'helpString' may be NULL. INTEGER (name, initialString) NATURAL (name, initialString) REAL (name, initialString) REAL_OR_UNDEFINED (name, initialString) POSITIVE (name, initialString) WORD (name, initialString) SENTENCE (name, initialString) COLOUR (name, initialString) CHANNEL (name, initialString) the name is also the string displayed in the label. BOOLEAN (name, initialValue) the name is also the title of the check box; the initial value is 0 (off) or 1 (on). LABEL (name, initialLabelString) 'name' is not shown but can still be used by the SETs TEXTFIELD (name, initialString) 'name' is not shown but can still be used by the SETs RADIO (name, initialValue) the name is also the string displayed in the label; this should be followed by two or more RADIOBUTTONs. The initial value is between 1 and the number of radio buttons. RADIOBUTTON (name) the name is also the title of the button. OPTIONMENU (name, initialValue) the name is also the string displayed in the label; this should be followed by two or more OPTIONs. The initial value is between 1 and the number of options. OPTION (name) the name is also the title of the button. OK this statement is obligatory. SET_XXXXXX (name, value) sets the value of REAL..LIST. DO The order of the macros should be: FORM one or more from REAL..LIST OK zero or more SETs DO ... END See Ui.h for more information. Between DO and END, you should return 0 if something is wrong; if everything is alright, you should trickle down to END; never return 1! E.g. NOT return praat_new1 (...); BUT if (! praat_new1 (...)) return 0; This is because END updates the selection if an object was created. */ #ifndef _EditorM_h_ #define FORM(proc,name,helpTitle) \ static void DO_##proc (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *buttonClosure) { \ static UiForm dia; \ if (dia == NULL) { \ Any radio = 0; \ (void) radio; \ dia = UiForm_create (theCurrentPraatApplication -> topShell, name, DO_##proc, buttonClosure, invokingButtonTitle, helpTitle); #define REAL(label,def) UiForm_addReal (dia, label, def); #define REAL_OR_UNDEFINED(label,def) UiForm_addRealOrUndefined (dia, label, def); #define POSITIVE(label,def) UiForm_addPositive (dia, label, def); #define INTEGER(label,def) UiForm_addInteger (dia, label, def); #define NATURAL(label,def) UiForm_addNatural (dia, label, def); #define WORD(label,def) UiForm_addWord (dia, label, def); #define SENTENCE(label,def) UiForm_addSentence (dia, label, def); #define BOOLEAN(label,def) UiForm_addBoolean (dia, label, def); #define LABEL(name,label) UiForm_addLabel (dia, name, label); #define TEXTFIELD(name,def) UiForm_addText (dia, name, def); #define RADIO(label,def) radio = UiForm_addRadio (dia, label, def); #define RADIOBUTTON(label) UiRadio_addButton (radio, label); #define OPTIONMENU(label,def) radio = UiForm_addOptionMenu (dia, label, def); #define OPTION(label) UiOptionMenu_addButton (radio, label); #define RADIOBUTTONS_ENUM(labelProc,min,max) { for (int itext = min; itext <= max; itext ++) RADIOBUTTON (labelProc) } #define OPTIONS_ENUM(labelProc,min,max) { for (int itext = min; itext <= max; itext ++) OPTION (labelProc) } #define RADIO_ENUM(label,enum,def) \ RADIO (label, enum##_##def - enum##_MIN + 1) \ for (int ienum = enum##_MIN; ienum <= enum##_MAX; ienum ++) \ OPTION (enum##_getText (ienum)) #define OPTIONMENU_ENUM(label,enum,def) \ OPTIONMENU (label, enum##_##def - enum##_MIN + 1) \ for (int ienum = enum##_MIN; ienum <= enum##_MAX; ienum ++) \ OPTION (enum##_getText (ienum)) #define LIST(label,n,str,def) UiForm_addList (dia, label, n, str, def); #define FILE_IN(label) UiForm_addFileIn (dia, label); #define FILE_OUT(label,def) UiForm_addFileOut (dia, label, def); #define COLOUR(label,def) UiForm_addColour (dia, label, def); #define CHANNEL(label,def) UiForm_addChannel (dia, label, def); #define OK UiForm_finish (dia); } if (sendingForm == NULL && sendingString == NULL) { #define SET_REAL(name,value) UiForm_setReal (dia, name, value); #define SET_INTEGER(name,value) UiForm_setInteger (dia, name, value); #define SET_STRING(name,value) UiForm_setString (dia, name, value); #define SET_ENUM(name,enum,value) SET_STRING (name, enum##_getText (value)) #define DO \ UiForm_do (dia, modified); \ } else if (sendingForm == NULL) { \ UiForm_parseString (dia, sendingString, interpreter); \ } else { \ try { \ int IOBJECT = 0; \ (void) IOBJECT; \ { #define DO_ALTERNATIVE(alternative) \ UiForm_do (dia, modified); \ } else if (sendingForm == NULL) { \ try { \ UiForm_parseString (dia, sendingString, interpreter); \ } catch (MelderError) { \ wchar *parkedError = Melder_wcsdup_f (Melder_getError ()); \ Melder_clearError (); \ try { \ DO_##alternative (NULL, sendingString, interpreter, invokingButtonTitle, modified, buttonClosure); \ } catch (MelderError) { \ Melder_clearError (); \ Melder_error_ (parkedError); \ Melder_free (parkedError); \ throw; \ } \ Melder_free (parkedError); \ } \ } else { \ try { \ int IOBJECT = 0; \ (void) IOBJECT; \ { #define END \ } \ } catch (MelderError) { \ praat_updateSelection (); \ throw; \ } \ praat_updateSelection (); \ } \ } #define DIRECT(proc) \ static void DO_##proc (UiForm dummy1, const wchar *dummy2, Interpreter dummy3, const wchar *dummy4, bool dummy5, void *dummy6) { \ (void) dummy1; (void) dummy2; (void) dummy3; (void) dummy4; (void) dummy5; (void) dummy6; \ { \ try { \ int IOBJECT = 0; \ (void) IOBJECT; \ { #define FORM_READ(proc,title,help,allowMult) \ static void DO_##proc (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *okClosure) { \ static UiForm dia; \ (void) interpreter; \ (void) modified; \ (void) okClosure; \ if (dia == NULL) \ dia = UiInfile_create (theCurrentPraatApplication -> topShell, title, DO_##proc, okClosure, invokingButtonTitle, help, allowMult); \ if (sendingForm == NULL && sendingString == NULL) { \ UiInfile_do (dia); \ } else { \ try { \ MelderFile file; \ int IOBJECT = 0; \ structMelderFile file2 = { 0 }; \ (void) IOBJECT; \ if (sendingString == NULL) { \ file = UiFile_getFile (dia); \ } else { \ Melder_relativePathToFile (sendingString, & file2); \ file = & file2; \ } \ { #define FORM_WRITE(proc,title,help,ext) \ static void DO_##proc (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *okClosure) { \ static Any dia; \ (void) interpreter; \ (void) modified; \ (void) okClosure; \ if (dia == NULL) \ dia = UiOutfile_create (theCurrentPraatApplication -> topShell, title, DO_##proc, okClosure, invokingButtonTitle, help); \ if (sendingForm == NULL && sendingString == NULL) { \ praat_write_do (dia, ext); \ } else { \ try { \ MelderFile file; \ int IOBJECT = 0; \ structMelderFile file2 = { 0 }; \ (void) IOBJECT; \ if (sendingString == NULL) { \ file = UiFile_getFile (dia); \ } else { \ Melder_relativePathToFile (sendingString, & file2); \ file = & file2; \ } \ { /* Callbacks should return 1 if OK, and 0 if failure. Macros for DO_proc: GET_REAL (name) GET_INTEGER (name) GET_STRING (name) GET_COLOUR (name) GET_FILE (name) REQUIRE (condition, errorMessage) throws an error if condition false. */ #define GET_REAL(name) UiForm_getReal (dia, name) #define GET_INTEGER(name) UiForm_getInteger (dia, name) #define GET_STRING(name) UiForm_getString (dia, name) #define GET_ENUM(enum,name) (enum) enum##_getValue (GET_STRING (name)) #define GET_COLOUR(name) UiForm_getColour (dia, name) #define GET_FILE(name) UiForm_getFile (dia, name) #define REQUIRE(c,t) if (! (c)) Melder_throw (t); #endif // _EditorM_h_ #define WHERE(condition) for (IOBJECT = 1; IOBJECT <= theCurrentPraatObjects -> n; IOBJECT ++) if (condition) #define WHERE_DOWN(condition) for (IOBJECT = theCurrentPraatObjects -> n; IOBJECT > 0; IOBJECT --) if (condition) #define SELECTED (theCurrentPraatObjects -> list [IOBJECT]. selected) #define CLASS (theCurrentPraatObjects -> list [IOBJECT]. klas) #define OBJECT (theCurrentPraatObjects -> list [IOBJECT]. object) #define GRAPHICS theCurrentPraatPicture -> graphics #define FULL_NAME (theCurrentPraatObjects -> list [IOBJECT]. name) #define ID (theCurrentPraatObjects -> list [IOBJECT]. id) #define ID_AND_FULL_NAME Melder_wcscat (Melder_integer (ID), L". ", FULL_NAME) #define NAME praat_name (IOBJECT) #define EVERY(proc) WHERE (SELECTED) proc; #define EVERY_CHECK(proc) EVERY (if (! proc) return 0) #define EVERY_TO(proc) EVERY_CHECK (praat_new1 (proc, NAME)) #define ONLY(klas) praat_onlyObject (klas) #define ONLY_GENERIC(klas) praat_onlyObject_generic (klas) #define ONLY_OBJECT (praat_onlyScreenObject () -> object) Data praat_firstObject (ClassInfo klas); Data praat_firstObject_generic (ClassInfo klas); Data praat_firstObject_any (); #define FIRST(Klas) (Klas) praat_firstObject (class##Klas) #define FIRST_GENERIC(Klas) (Klas) praat_firstObject_generic (class##Klas) #define FIRST_ANY(Klas) (Klas) praat_firstObject_any () #define EVERY_DRAW(proc) \ praat_picture_open (); WHERE (SELECTED) proc; praat_picture_close (); return 1; /* Used by praat_Sybil.c, if you put an Editor on the screen: */ int praat_installEditor (Editor editor, int iobject); /* This routine adds a reference to a new editor (unless it is NULL) to the screen object which is in the list at position 'iobject'. It sets the destroyCallback and dataChangedCallback as appropriate for Praat: the destroyCallback will set the now dangling reference to NULL, so that a subsequent click on the "Edit" button will create a new editor; the dataChangedCallback will notify an open DataEditor with the same data, after that data will have changed. Return value: normally 1, but 0 if 'editor' is NULL. A typical calling sequence is: DIRECT (Spectrogram_edit) if (praat.batch) Melder_throw ("Cannot edit a Spectrogram from batch."); else WHERE (SELECTED) praat_installEditor (SpectrogramEditor_create (praat.topShell, ID_AND_FULL_NAME, OBJECT), IOBJECT); END */ int praat_installEditor2 (Editor editor, int iobject1, int iobject2); int praat_installEditor3 (Editor editor, int iobject1, int iobject2, int iobject3); int praat_installEditorN (Editor editor, Ordered objects); void praat_dataChanged (Any object); /* Call this after changing a screen object. */ /* Associated editors and data editors will be notified (with Editor_dataChanged). */ /* Used by praat.cpp, praat_Basic.cpp, and praat_Sybil.cpp; defined in praat_picture.cpp. */ void praat_picture_open (); void praat_picture_close (); /* These two routines should bracket drawing commands. */ /* See also the EVERY_DRAW macro. */ /* For main.cpp */ #define INCLUDE_LIBRARY(praat_xxx_init) \ { extern void praat_xxx_init (void); praat_xxx_init (); } #define INCLUDE_MANPAGES(manual_xxx_init) \ { extern void manual_xxx_init (ManPages me); manual_xxx_init (theCurrentPraatApplication -> manPages); } /* For text-only applications that do not want to see that irritating Picture window. */ /* Works only if called before praat_init. */ /* The program will crash if you still try to use drawing routines. */ void praat_dontUsePictureWindow (); /* Before praat_init: */ void praat_setLogo (double width_mm, double height_mm, void (*draw) (Graphics g)); /* Removing objects from the list. */ /* To remove the selected objects of class Klas from the list: */ /* for (i = praat.n; i >= 1; i --) // Down! if (praat.list[i].selected && Thing_member (praat.list[i].object, classKlas) praat_removeObject (i); praat_show (); // Needed because the selection has changed. */ void praat_removeObject (int i); /* i = 1..praat.n */ void praat_show (void); // forces an update of the dynamic menu void praat_updateSelection (); /* If you require the correct selection immediately after calling praat_new. */ void praat_addCommandsToEditor (Editor me); #define iam_LOOP(klas) klas me = static_cast (OBJECT) #define iam_ONLY(klas) klas me = static_cast (ONLY (class##klas)) #define thouart_ONLY(klas) klas thee = static_cast (ONLY (class##klas)) #define heis_ONLY(klas) klas him = static_cast (ONLY (class##klas)) #define LOOP for (IOBJECT = 1; IOBJECT <= theCurrentPraatObjects -> n; IOBJECT ++) if (SELECTED) Collection praat_getSelectedObjects (); struct autoPraatPicture { autoPraatPicture () { praat_picture_open (); } ~autoPraatPicture () { praat_picture_close (); } }; static inline void praat_new (Data newData, const wchar *s1) { praat_new1 (newData, s1); therror } static inline void praat_new (Data newData, const wchar *s1, const wchar *s2) { praat_new2 (newData, s1, s2); therror } static inline void praat_new (Data newData, const wchar *s1, const wchar *s2, const wchar *s3) { praat_new3 (newData, s1, s2, s3); therror } static inline void praat_new (Data newData, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4) { praat_new4 (newData, s1, s2, s3, s4); therror } static inline void praat_new (Data newData, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5) { praat_new5 (newData, s1, s2, s3, s4, s5); therror } static inline void praat_new (Data newData, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6) { praat_new6 (newData, s1, s2, s3, s4, s5, s6); therror } static inline void praat_new (Data newData, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7) { praat_new7 (newData, s1, s2, s3, s4, s5, s6, s7); therror } static inline void praat_new (Data newData, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8) { praat_new8 (newData, s1, s2, s3, s4, s5, s6, s7, s8); therror } static inline void praat_new (Data newData, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9) { praat_new9 (newData, s1, s2, s3, s4, s5, s6, s7, s8, s9); therror } static inline void praat_newWithFile (Data newData, const wchar *s1, MelderFile file) { praat_newWithFile1 (newData, s1, file); therror } static inline void praat_newWithFile (Data newData, const wchar *s1, const wchar *s2, MelderFile file) { praat_newWithFile2 (newData, s1, s2, file); therror } static inline void praat_newWithFile (Data newData, const wchar *s1, const wchar *s2, const wchar *s3, MelderFile file) { praat_newWithFile3 (newData, s1, s2, s3, file); therror } static inline void praat_newWithFile (Data newData, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, MelderFile file) { praat_newWithFile4 (newData, s1, s2, s3, s4, file); therror } static inline void praat_newWithFile (Data newData, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, MelderFile file) { praat_newWithFile5 (newData, s1, s2, s3, s4, s5, file); therror } /* End of file praat.h */ sources_5316/sys/ButtonEditor.cpp0000644000176700017670000002626311633661466015714 0ustar paulpaul/* ButtonEditor.cpp * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ButtonEditor.h" #include "praatP.h" #include "praat_script.h" #include "EditorM.h" #include "machine.h" Thing_implement (ButtonEditor, HyperPage, 0); #if defined (_WIN32) #define BUTTON_WIDTH 72 #elif defined (macintosh) #define BUTTON_WIDTH 72 #else #define BUTTON_WIDTH 96 #endif static void drawMenuCommand (ButtonEditor me, praat_Command cmd, long i) { static MelderString text = { 0 }; int isAdded = cmd -> uniqueID != 0 || cmd -> script != NULL; int isHidden = cmd -> hidden; int isToggled = cmd -> toggled; const wchar_t *clickText = isHidden ? (isToggled ? (isAdded ? L"REMOVED" : L"HIDDEN") : L"hidden") : (isToggled ? L"SHOWN" : (isAdded ? (cmd -> uniqueID ? L"ADDED" : L"START-UP") : L"shown")); MelderString_empty (& text); if (cmd -> unhidable) { MelderString_append (& text, L"#unhidable "); } else { MelderString_append (& text, L"@@m", Melder_integer (i), L"|", clickText, L"@ "); } MelderString_append (& text, cmd -> window, L": "); if (cmd -> menu) { MelderString_append (& text, cmd -> menu, L": "); } if (cmd -> title) { if (cmd -> executable) { MelderString_append (& text, L"@@p", Melder_integer (i), L"|", cmd -> title, L"@"); } else { MelderString_append (& text, cmd -> title); } } else { MelderString_append (& text, L"---------"); } if (cmd -> after) { MelderString_append (& text, L", %%%%after \"", cmd -> after, L"\"%%"); } if (cmd -> script) { MelderString_append (& text, L", script \"", Melder_peekExpandBackslashes (cmd -> script), L"\""); } HyperPage_any (me, text.string, my font, my fontSize, cmd -> callback ? 0 : Graphics_ITALIC, 0.0, cmd -> depth * 0.3, 0.4, 0.0, 0.0, 0); } static void drawAction (ButtonEditor me, praat_Command cmd, long i) { static MelderString text = { 0 }; int isAdded = cmd -> uniqueID != 0 || cmd -> script != NULL; int isHidden = cmd -> hidden, isToggled = cmd -> toggled; const wchar_t *clickText = isHidden ? (isToggled ? (isAdded ? L"REMOVED" : L"HIDDEN") : L"hidden") : (isToggled ? L"SHOWN" : (isAdded ? (cmd -> uniqueID ? L"ADDED" : L"START-UP") : L"shown")); int n1 = cmd -> n1; MelderString_empty (& text); if (cmd -> class4) { MelderString_append (& text, L"#unhidable "); } else { MelderString_append (& text, L"@@a", Melder_integer (i), L"|", clickText, L"@ "); } MelderString_append (& text, cmd -> class1 -> className); if (n1) { MelderString_append (& text, L" (", Melder_integer (n1), L")"); } if (cmd -> class2) { int n2 = cmd -> n2; MelderString_append (& text, L" & ", cmd -> class2 -> className); if (n2) { MelderString_append (& text, L" (", Melder_integer (n2), L")"); } } if (cmd -> class3) { int n3 = cmd -> n3; MelderString_append (& text, L" & ", cmd -> class3 -> className); if (n3) { MelderString_append (& text, L" (", Melder_integer (n3), L")"); } } if (cmd -> class4) { int n4 = cmd -> n4; MelderString_append (& text, L" & ", cmd -> class4 -> className); if (n4) { MelderString_append (& text, L" (", Melder_integer (n4), L")"); } } MelderString_append (& text, L": "); if (cmd -> title) { if (cmd -> executable) { MelderString_append (& text, L"@@e", Melder_integer (i), L"|", cmd -> title, L"@"); } else { MelderString_append (& text, cmd -> title); } } else { MelderString_append (& text, L"---------"); } if (cmd -> after) { MelderString_append (& text, L", %%%%after \"", cmd -> after, L"\"%%"); } if (cmd -> script) { MelderString_append (& text, L", script \"", Melder_peekExpandBackslashes (cmd -> script), L"\""); } HyperPage_any (me, text.string, my font, my fontSize, cmd -> callback ? 0 : Graphics_ITALIC, 0.0, cmd -> depth * 0.3, 0.4, 0.0, 0.0, 0); } void structButtonEditor :: v_draw () { Graphics_clearWs (g); switch (show) { case 1: for (long i = 1, n = praat_getNumberOfMenuCommands (); i <= n; i ++) { praat_Command cmd = praat_getMenuCommand (i); if (wcsequ (cmd -> window, L"Objects")) drawMenuCommand (this, praat_getMenuCommand (i), i); } break; case 2: for (long i = 1, n = praat_getNumberOfMenuCommands (); i <= n; i ++) { praat_Command cmd = praat_getMenuCommand (i); if (wcsequ (cmd -> window, L"Picture")) drawMenuCommand (this, praat_getMenuCommand (i), i); } break; case 3: for (long i = 1, n = praat_getNumberOfMenuCommands (); i <= n; i ++) { praat_Command cmd = praat_getMenuCommand (i); if (! wcsequ (cmd -> window, L"Objects") && ! wcsequ (cmd -> window, L"Picture")) drawMenuCommand (this, praat_getMenuCommand (i), i); } break; case 4: for (long i = 1, n = praat_getNumberOfActions (); i <= n; i ++) { praat_Command cmd = praat_getAction (i); const wchar *klas = cmd -> class1 -> className; if (wcscmp (klas, L"N") < 0) drawAction (this, praat_getAction (i), i); } break; case 5: for (long i = 1, n = praat_getNumberOfActions (); i <= n; i ++) { praat_Command cmd = praat_getAction (i); const wchar *klas = cmd -> class1 -> className; if (wcscmp (klas, L"N") >= 0) drawAction (this, praat_getAction (i), i); } break; } } int structButtonEditor :: v_goToPage (const wchar_t *title) { if (! title || ! title [0]) return 0; if (wcsequ (title, L"Buttons")) return 1; switch (title [0]) { case 'a': { /* Toggle visibility of action.*/ long i = wcstol (& title [1], NULL, 10); praat_Command action = praat_getAction (i); if (! action) return 0; if (action -> hidden) praat_showAction (action -> class1, action -> class2, action -> class3, action -> title); else praat_hideAction (action -> class1, action -> class2, action -> class3, action -> title); } break; case 'm': { /* Toggle visibility of menu command. */ long i = wcstol (& title [1], NULL, 10); praat_Command menuCommand = praat_getMenuCommand (i); if (! menuCommand) return 0; if (menuCommand -> hidden) praat_showMenuCommand (menuCommand -> window, menuCommand -> menu, menuCommand -> title); else praat_hideMenuCommand (menuCommand -> window, menuCommand -> menu, menuCommand -> title); } break; case 'e': { /* Execute action. */ long i = wcstol (& title [1], NULL, 10); praat_Command action = praat_getAction (i); if (! action || ! action -> callback) return 0; if (action -> title) { UiHistory_write (L"\n"); UiHistory_write (action -> title); } if (action -> script) { try { DO_RunTheScriptFromAnyAddedMenuCommand (NULL, action -> script, NULL, NULL, false, NULL); } catch (MelderError) { Melder_flushError ("Command not executed."); } } else { try { action -> callback (NULL, NULL, NULL, NULL, false, NULL); } catch (MelderError) { Melder_flushError ("Command not executed."); } } praat_updateSelection (); } break; case 'p': { /* Perform menu command. */ long i = wcstol (& title [1], NULL, 10); praat_Command menuCommand = praat_getMenuCommand (i); if (! menuCommand || ! menuCommand -> callback) return 0; if (menuCommand -> title) { UiHistory_write (L"\n"); UiHistory_write (menuCommand -> title); } if (menuCommand -> script) { try { DO_RunTheScriptFromAnyAddedMenuCommand (NULL, menuCommand -> script, NULL, NULL, false, NULL); } catch (MelderError) { Melder_flushError ("Command not executed."); } } else { try { menuCommand -> callback (NULL, NULL, NULL, NULL, false, NULL); } catch (MelderError) { Melder_flushError ("Command not executed."); } } praat_updateSelection (); } break; default: break; } return 0; } static void which (ButtonEditor me, int show) { my show = show; #if motif GuiRadioButton_setValue (my button1, show == 1); GuiRadioButton_setValue (my button2, show == 2); GuiRadioButton_setValue (my button3, show == 3); GuiRadioButton_setValue (my button4, show == 4); GuiRadioButton_setValue (my button5, show == 5); #endif HyperPage_goToPage (me, L"Buttons"); } static void gui_radiobutton_cb_objects (I, GuiRadioButtonEvent event) { (void) event; which ((ButtonEditor) void_me, 1); } static void gui_radiobutton_cb_picture (I, GuiRadioButtonEvent event) { (void) event; which ((ButtonEditor) void_me, 2); } static void gui_radiobutton_cb_editors (I, GuiRadioButtonEvent event) { (void) event; which ((ButtonEditor) void_me, 3); } static void gui_radiobutton_cb_actionsAM (I, GuiRadioButtonEvent event) { (void) event; which ((ButtonEditor) void_me, 4); } static void gui_radiobutton_cb_actionsNZ (I, GuiRadioButtonEvent event) { (void) event; which ((ButtonEditor) void_me, 5); } void structButtonEditor :: v_createChildren () { ButtonEditor_Parent :: v_createChildren (); #if gtk void *group = NULL; #endif int x = 3, y = Machine_getMenuBarHeight () + 4; button1 = GuiRadioButton_createShown (holder, x, x + BUTTON_WIDTH, y, Gui_AUTOMATIC, L"Objects", gui_radiobutton_cb_objects, this, GuiRadioButton_SET); x += BUTTON_WIDTH + 5; button2 = GuiRadioButton_createShown (holder, x, x + BUTTON_WIDTH, y, Gui_AUTOMATIC, L"Picture", gui_radiobutton_cb_picture, this, 0); x += BUTTON_WIDTH + 5; button3 = GuiRadioButton_createShown (holder, x, x + BUTTON_WIDTH, y, Gui_AUTOMATIC, L"Editors", gui_radiobutton_cb_editors, this, 0); x += BUTTON_WIDTH + 5; button4 = GuiRadioButton_createShown (holder, x, x + BUTTON_WIDTH + 30, y, Gui_AUTOMATIC, L"Actions A-M", gui_radiobutton_cb_actionsAM, this, 0); x += BUTTON_WIDTH + 35; button5 = GuiRadioButton_createShown (holder, x, x + BUTTON_WIDTH + 30, y, Gui_AUTOMATIC, L"Actions N-Z", gui_radiobutton_cb_actionsNZ, this, 0); #if gtk group = GuiRadioButton_getGroup (button1); GuiRadioButton_setGroup (button2, group); group = GuiRadioButton_getGroup (button2); GuiRadioButton_setGroup (button3, group); group = GuiRadioButton_getGroup (button3); GuiRadioButton_setGroup (button4, group); group = GuiRadioButton_getGroup (button4); GuiRadioButton_setGroup (button5, group); #endif } static void menu_cb_ButtonEditorHelp (EDITOR_ARGS) { EDITOR_IAM (ButtonEditor); Melder_help (L"ButtonEditor"); } void structButtonEditor :: v_createHelpMenuItems (EditorMenu menu) { ButtonEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"ButtonEditor help", '?', menu_cb_ButtonEditorHelp); } ButtonEditor ButtonEditor_create (GuiObject parent) { try { autoButtonEditor me = Thing_new (ButtonEditor); HyperPage_init (me.peek(), parent, L"Buttons", NULL); which (me.peek(), 1); return me.transfer(); } catch (MelderError) { Melder_throw ("Buttons window not created."); } } /* End of file ButtonEditor.cpp */ sources_5316/sys/sendsocket.c0000644000176700017670000001013510520752715015053 0ustar paulpaul/* sendsocket.c * * Copyright (C) 1999-2006 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 1999/12/21 * pb 2002/03/07 GPL * pb 2003/12/19 return NULL if no error * pb 2004/10/11 re-included windows.h include file (undoes fix of CW5 include-file bug) * pb 2004/10/11 user-readable error messages * pb 2006/10/28 erased MacOS 9 stuff */ #include #include #include #if defined (UNIX) || defined (macintosh) #if defined (macintosh) /* Prevent some warnings with MacOS X 10.4.2 / CodeWarrior 9.6 / Xcode 2.0 */ #define GATEWAY 0 #define SENDFILE 0 #endif #include #include #include #include #include #include #include #elif defined (_WIN32) #include #include #endif #include "sendsocket.h" char * sendsocket (const char *hostNameAndPort, const char *command) { static char result [200]; char hostName [61], *colon; int port; if (strlen (hostNameAndPort) > 60) return "Cannot send to socket because the host-name-and-port string is too long."; strcpy (hostName, hostNameAndPort); colon = strchr (hostName, ':'); if (colon == NULL) return "Cannot send to socket because a colon is missing.\nHost name and port should be in the format \"hostName:port\"."; *colon = '\0'; port = atoi (colon + 1); { struct hostent *host; struct sockaddr_in his_addr; /* Address of remote host. */ int stat, sokket = -1; long bytesSent; result [0] = '\0'; /* No error yet. */ #ifdef _WIN32 { static int initialized; if (! initialized) { WSADATA wsaData; WORD requestedWinsockVersion = MAKEWORD (1,1); /* Require version 1.1. */ if (WSAStartup (requestedWinsockVersion, & wsaData)) { return "Cannot send to socket because the socket library (WINSOCK.DLL) is not available, " "too old, or otherwise unusable."; } initialized = 1; } } #endif if (isdigit (hostName [0])) { if ((his_addr. sin_addr.s_addr = inet_addr ((char *) hostName)) == 0xFFFFFFFF) { sprintf (result, "Cannot send to socket because the hostname \"%s\" is invalid.", hostName); return result; } his_addr. sin_family = AF_INET; } else if ((host = gethostbyname (hostName)) != NULL) { his_addr. sin_family = host -> h_addrtype; memcpy (& his_addr. sin_addr, host -> h_addr, host -> h_length); } else { sprintf (result, "Cannot send to socket because the host \"%s\" is unknown.", hostName); return result; } his_addr. sin_port = htons (port); sokket = socket (AF_INET, SOCK_STREAM, IPPROTO_TCP); if (sokket < 0) { strcpy (result, "Cannot send to socket because the socket cannot be created."); goto end; } stat = connect (sokket, (struct sockaddr *) & his_addr, sizeof (struct sockaddr_in)); if (stat != 0) { strcpy (result, "Cannot send to socket because the connection cannot be made."); goto end; } /* Melder_casual ("Connected to port %d on host %s.", ntohs (his_addr. sin_port), inet_ntoa (his_addr. sin_addr)); */ bytesSent = send (sokket, command, strlen (command) + 1, 0); /* Include null byte. */ if (bytesSent < 0) { strcpy (result, "Data not sent to socket."); goto end; } /* Melder_casual ("sendsocket: %d bytes written.", bytesSent); */ end: if (sokket >= 0) { #if defined (UNIX) || defined (macintosh) close (sokket); #elif defined (_WIN32) closesocket (sokket); #endif } } return result [0] == '\0' ? NULL: result; } /* End of file sendsocket.c */ sources_5316/sys/Makefile0000644000176700017670000000351711704273570014215 0ustar paulpaul# Makefile of the library "sys" # Paul Boersma, 14 January 2012 include ../makefile.defs CPPFLAGS = -I ../num -I ../sys -I ../dwsys -I ../kar -I ../external/portaudio -I ../external/flac -I ../external/mp3 OBJECTS = abcio.o lispio.o complex.o \ melder_ftoa.o melder_atof.o melder_error.o melder_alloc.o melder.o melder_strings.o \ melder_token.o melder_files.o melder_audio.o melder_audiofiles.o \ melder_debug.o melder_sysenv.o melder_info.o melder_quantity.o \ melder_textencoding.o melder_readtext.o melder_writetext.o melder_console.o melder_time.o \ Thing.o Data.o Simple.o Collection.o Strings.o \ Graphics.o Graphics_linesAndAreas.o Graphics_text.o Graphics_colour.o \ Graphics_image.o Graphics_mouse.o Graphics_record.o \ Graphics_utils.o Graphics_grey.o Graphics_altitude.o \ GraphicsPostscript.o Graphics_surface.o \ ManPage.o ManPages.o Script.o machine.o \ GraphicsScreen.o Printer.o \ Preferences.o site.o \ Picture.o Ui.o UiFile.o UiPause.o Editor.o DataEditor.o HyperPage.o Manual.o TextEditor.o \ praat.o praat_actions.o praat_menuCommands.o praat_picture.o sendpraat.o sendsocket.o \ praat_script.o praat_statistics.o praat_logo.o \ praat_objectMenus.o InfoEditor.o ScriptEditor.o ButtonEditor.o Interpreter.o Formula.o \ StringsEditor.o DemoEditor.o \ motifEmulator.o GuiText.o GuiWindow.o Gui.o GuiObject.o GuiDrawingArea.o \ GuiMenu.o GuiButton.o GuiLabel.o GuiCheckButton.o GuiRadioButton.o \ GuiDialog.o GuiRowColumn.o GuiList.o GuiFileSelect.o .PHONY: all clean all: libsys.a clean: $(RM) $(OBJECTS) $(RM) libsys.a libsys.a: $(OBJECTS) touch libsys.a rm libsys.a ar cq libsys.a $(OBJECTS) $(RANLIB) libsys.a $(OBJECTS): *.h ../num/NUM.h ../dwsys/*.h ../kar/*.h ../external/portaudio/*.h ../external/flac/*.h ../external/mp3/mp3.h sources_5316/sys/UiP.h0000644000176700017670000000216511614213165013413 0ustar paulpaul/* UiP.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * Private stuff for communication between Ui.c and UiFile.cpp. */ #include "Ui.h" extern bool (*theAllowExecutionHookHint) (void *closure); extern void *theAllowExecutionClosureHint; typedef struct structUiFileSelector *UiFileSelector; UiFileSelector UiFileSelector_create (GuiObject parent, const char *label, int direction, const char *defaultValue); /* End of file UiP.h */ sources_5316/sys/oo_COPY.h0000644000176700017670000001035611724670235014175 0ustar paulpaul/* oo_COPY.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) \ thy x = x; #define oo_ARRAY(type,storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ thy x [i] = x [i]; #define oo_SET(type,storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ thy x [i] = x [i]; #define oo_VECTOR(type,storage,x,min,max) \ if (x) thy x = NUMvector_copy (x, min, max); #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) \ if (x) thy x = NUMmatrix_copy (x, row1, row2, col1, col2); #define oo_ENUMx(type,storage,Type,x) \ thy x = x; #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) \ for (int i = 0; i < n; i ++) thy x [i] = x [i]; #define oo_ENUMx_SET(type,storage,Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) thy x [i] = x [i]; #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) \ if (x) thy x = NUMvector_copy (x, min, max); #define oo_STRINGx(storage,x) \ if (x) thy x = Melder_wcsdup (x); #define oo_STRINGx_ARRAY(storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ if (x [i]) thy x [i] = Melder_wcsdup (x [i]); #define oo_STRINGx_SET(storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ if (x [i]) thy x [i] = Melder_wcsdup (x [i]); #define oo_STRINGx_VECTOR(storage,x,min,max) \ if (x) { \ thy x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) \ if (x [i]) thy x [i] = Melder_wcsdup (x [i]); \ } #define oo_STRUCT(Type,x) \ x. copy (& thy x); #define oo_STRUCT_ARRAY(Type,x,cap,n) \ for (int i = 0; i < n; i ++) \ x [i]. copy (& thy x [i]); #define oo_STRUCT_SET(Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ x [i]. copy (& thy x [i]); #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ if (x) { \ thy x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) \ x [i]. copy (& thy x [i]); \ } #define oo_STRUCT_MATRIX_FROM(Type,x,row1,row2,col1,col2) \ if (x) { \ thy x = NUMmatrix (row1, row2, col1, col2); \ for (long i = row1; i <= row2; i ++) \ for (long j = col1; j <= col2; j ++) \ x [i] [j]. copy (& thy x [i] [j]); \ } #define oo_WIDGET(x) \ !!!! Can never copy Widgets... !!!! #define oo_WIDGET_ARRAY(x,cap,n) \ !!!! Can never copy Widgets... !!!! #define oo_WIDGET_SET(x,setType) \ !!!! Can never copy Widgets... !!!! #define oo_WIDGET_VECTOR_FROM(x,cap,min,max) \ !!!! Can never copy Widgets... !!!! #define oo_OBJECT(Class,version,x) \ if (x) thy x = Data_copy (x); #define oo_COLLECTION(Class,x,ItemClass,version) \ if (x) thy x = Data_copy (x); #define oo_FILE(x) \ MelderFile_copy (& x, & thy x); #define oo_DIR(x) \ MelderDir_copy (& x, & thy x); #define oo_DEFINE_STRUCT(Type) \ void struct##Type :: copy (Type thee) { #define oo_END_STRUCT(Type) \ } #define oo_DEFINE_CLASS(Class,Parent) \ void struct##Class :: v_copy (thou) { \ thouart (Class); \ Class##_Parent :: v_copy (thee); #define oo_END_CLASS(Class) \ } #define oo_IF(condition) \ if (condition) { #define oo_ENDIF \ } #define oo_FROM(from) #define oo_ENDFROM #define oo_VERSION(version) #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 1 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 0 #define oo_READING 0 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 0 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_COPY.h */ sources_5316/sys/abcio.cpp0000644000176700017670000023417511634626610014343 0ustar paulpaul/* abcio.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2003/05/19 accept percent signs in getReal * pb 2004/10/01 Melder_double instead of %.17g * pb 2006/02/17 support for Intel-based Macs * pb 2006/02/20 corrected bingeti3, bingeti3LE, binputi3, binputi3LE * pb 2006/03/28 support for systems where a long is not 32 bits and a short is not 16 bits * pb 2007/07/21 MelderReadString * pb 2007/08/14 check for NULL pointer before Melder_isValidAscii * pb 2009/03/18 modern enums * fb 2010/02/26 UTF-16 via bin(get|put)utf16() * pb 2010/03/09 more support for Unicode values above 0xFFFF * pb 2010/12/23 corrected bingeti3 and bingeti3LE for 64-bit systems * pb 2011/03/30 C++ */ #include "melder.h" #include "NUM.h" #include #ifdef macintosh #include #endif #include "abcio.h" /********** ASCII I/O **********/ #define WCHAR_MINUS_1 (sizeof (wchar_t) == 2 ? 0xFFFF : 0xFFFFFFFF) static long getInteger (MelderReadText me) { wchar buffer [41], c; /* * Look for the first numeric character. */ for (c = MelderReadText_getChar (me); c != '-' && ! isdigit (c) && c != '+'; c = MelderReadText_getChar (me)) { if (c == 0) Melder_throw ("Early end of text detected while looking for an integer (line ", MelderReadText_getLineNumber (me), ")."); if (c == '!') { // end-of-line comment? while ((c = MelderReadText_getChar (me)) != '\n' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected in comment while looking for an integer (line ", MelderReadText_getLineNumber (me), ")."); } } if (c == '\"') Melder_throw ("Found a string while looking for an integer in text (line ", MelderReadText_getLineNumber (me), ")."); if (c == '<') Melder_throw ("Found an enumerated value while looking for an integer in text (line ", MelderReadText_getLineNumber (me), ")."); while (c != ' ' && c != '\n' && c != '\t' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected in comment (line ", MelderReadText_getLineNumber (me), ")."); c = MelderReadText_getChar (me); } } int i = 0; for (; i < 40; i ++) { buffer [i] = c; c = MelderReadText_getChar (me); if (c == 0) { break; } // this may well be OK here if (c == ' ' || c == '\n' || c == '\t' || c == '\r') break; } if (i >= 40) Melder_throw ("Found strange text while looking for an integer in text (line ", MelderReadText_getLineNumber (me), ")."); buffer [i + 1] = '\0'; return wcstol (buffer, NULL, 10); } static unsigned long getUnsigned (MelderReadText me) { wchar buffer [41], c; for (c = MelderReadText_getChar (me); ! isdigit (c) && c != '+'; c = MelderReadText_getChar (me)) { if (c == 0) Melder_throw ("Early end of text detected while looking for an unsigned integer (line ", MelderReadText_getLineNumber (me), ")."); if (c == '!') { // end-of-line comment? while ((c = MelderReadText_getChar (me)) != '\n' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected in comment while looking for an unsigned integer (line ", MelderReadText_getLineNumber (me), ")."); } } if (c == '\"') Melder_throw ("Found a string while looking for an unsigned integer in text (line ", MelderReadText_getLineNumber (me), ")."); if (c == '<') Melder_throw ("Found an enumerated value while looking for an unsigned integer in text (line ", MelderReadText_getLineNumber (me), ")."); if (c == '-') Melder_throw ("Found a negative value while looking for an unsigned integer in text (line ", MelderReadText_getLineNumber (me), ")."); while (c != ' ' && c != '\n' && c != '\t' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected in comment (line ", MelderReadText_getLineNumber (me), ")."); c = MelderReadText_getChar (me); } } int i = 0; for (i = 0; i < 40; i ++) { buffer [i] = c; c = MelderReadText_getChar (me); if (c == 0) { break; } // this may well be OK here if (c == ' ' || c == '\n' || c == '\t' || c == '\r') break; } if (i >= 40) Melder_throw ("Found strange text while searching for an unsigned integer in text (line ", MelderReadText_getLineNumber (me), ")."); buffer [i + 1] = '\0'; return wcstoul (buffer, NULL, 10); } static double getReal (MelderReadText me) { int i; wchar_t buffer [41], c, *slash; do { for (c = MelderReadText_getChar (me); c != '-' && ! isdigit (c) && c != '+'; c = MelderReadText_getChar (me)) { if (c == 0) Melder_throw ("Early end of text detected while looking for a real number (line ", MelderReadText_getLineNumber (me), ")."); if (c == '!') { // end-of-line comment? while ((c = MelderReadText_getChar (me)) != '\n' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected in comment while looking for a real number (line ", MelderReadText_getLineNumber (me), ")."); } } if (c == '\"') Melder_throw ("Found a string while looking for a real number in text (line ", MelderReadText_getLineNumber (me), ")."); if (c == '<') Melder_throw ("Found an enumerated value while looking for a real number in text (line ", MelderReadText_getLineNumber (me), ")."); while (c != ' ' && c != '\n' && c != '\t' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected in comment while looking for a real number (line ", MelderReadText_getLineNumber (me), ")."); c = MelderReadText_getChar (me); } } for (i = 0; i < 40; i ++) { buffer [i] = c; c = MelderReadText_getChar (me); if (c == 0) { break; } // this may well be OK here if (c == ' ' || c == '\n' || c == '\t' || c == '\r') break; } if (i >= 40) Melder_throw ("Found strange text while searching for a real number in text (line ", MelderReadText_getLineNumber (me), ")."); } while (i == 0 && buffer [0] == '+'); // guard against single '+' symbols, which occur in complex numbers buffer [i + 1] = '\0'; slash = wcschr (buffer, '/'); if (slash) { double numerator, denominator; *slash = '\0'; numerator = Melder_atof (buffer), denominator = Melder_atof (slash + 1); if (numerator == HUGE_VAL || denominator == HUGE_VAL || denominator == 0.0) return HUGE_VAL; return numerator / denominator; } return Melder_atof (buffer); } static short getEnum (MelderReadText me, int (*getValue) (const wchar *)) { wchar buffer [41], c; for (c = MelderReadText_getChar (me); c != '<'; c = MelderReadText_getChar (me)) { if (c == 0) Melder_throw ("Early end of text detected while looking for an enumerated value (line ", MelderReadText_getLineNumber (me), ")."); if (c == '!') { /* End-of-line comment? */ while ((c = MelderReadText_getChar (me)) != '\n' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected in comment while looking for an enumerated value (line ", MelderReadText_getLineNumber (me), ")."); } } if (c == '-' || isdigit (c) || c == '+') Melder_throw ("Found a number while looking for an enumerated value in text (line ", MelderReadText_getLineNumber (me), ")."); if (c == '\"') Melder_throw ("Found a string while looking for an enumerated value in text (line ", MelderReadText_getLineNumber (me), ")."); while (c != ' ' && c != '\n' && c != '\t' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected in comment while looking for an enumerated value (line ", MelderReadText_getLineNumber (me), ")."); c = MelderReadText_getChar (me); } } int i = 0; for (; i < 40; i ++) { c = MelderReadText_getChar (me); // read past first '<' if (c == 0) Melder_throw ("Early end of text detected while reading an enumerated value (line ", MelderReadText_getLineNumber (me), ")."); if (c == ' ' || c == '\n' || c == '\t' || c == '\r') Melder_throw ("No matching '>' while reading an enumerated value (line ", MelderReadText_getLineNumber (me), ")."); if (c == '>') break; // the expected closing bracket; not added to the buffer buffer [i] = c; } if (i >= 40) Melder_throw ("Found strange text while reading an enumerated value in text (line ", MelderReadText_getLineNumber (me), ")."); buffer [i] = '\0'; int value = getValue (buffer); if (value < 0) Melder_throw ("\"", buffer, "\" is not a value of the enumerated type."); return value; } static wchar * getString (MelderReadText me) { static MelderString buffer = { 0 }; MelderString_empty (& buffer); for (wchar c = MelderReadText_getChar (me); c != '\"'; c = MelderReadText_getChar (me)) { if (c == 0) Melder_throw ("Early end of text detected while looking for a string (line ", MelderReadText_getLineNumber (me), ")."); if (c == '!') { // end-of-line comment? while ((c = MelderReadText_getChar (me)) != '\n' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected in comment while looking for a string (line ", MelderReadText_getLineNumber (me), ")."); } } if (c == '-' || isdigit (c) || c == '+') Melder_throw ("Found a number while looking for a string in text (line ", MelderReadText_getLineNumber (me), ")."); if (c == '<') Melder_throw ("Found an enumerated value while looking for a string in text (line ", MelderReadText_getLineNumber (me), ")."); while (c != ' ' && c != '\n' && c != '\t' && c != '\r') { if (c == 0) Melder_throw ("Early end of text detected while looking for a string (line ", MelderReadText_getLineNumber (me), ")."); c = MelderReadText_getChar (me); } } for (int i = 0; 1; i ++) { wchar c = MelderReadText_getChar (me); // read past first '"' if (c == 0) Melder_throw ("Early end of text detected while reading a string (line ", MelderReadText_getLineNumber (me), ")."); if (c == '\"') { wchar_t next = MelderReadText_getChar (me); if (next == 0) { break; } // closing quote is last character in file: OK if (next != '\"') { if (next == ' ' || next == '\n' || next == '\t' || next == '\r') { // closing quote is followed by whitespace: it is OK to skip this whitespace (no need to "ungetChar") } else { wchar_t kar2 [2] = { next, '\0' }; Melder_throw ("Character ", kar2, " following quote (line ", MelderReadText_getLineNumber (me), "). End of string or undoubled quote?"); } break; // the expected closing double quote; not added to the buffer } // else: add only one of the two quotes to the buffer } MelderString_appendCharacter (& buffer, c); } return buffer. string; } #undef false #undef true #include "enums_getText.h" #include "abcio_enums.h" #include "enums_getValue.h" #include "abcio_enums.h" int texgeti1 (MelderReadText text) { try { long externalValue = getInteger (text); if (externalValue < -128 || externalValue > +127) Melder_throw ("Value (", externalValue, ") out of range (-128 .. +127)."); return (int) externalValue; } catch (MelderError) { Melder_throw ("Signed small integer not read from text file."); } } int texgeti2 (MelderReadText text) { try { long externalValue = getInteger (text); if (externalValue < -32768 || externalValue > +32767) Melder_throw ("Value (", externalValue, ") out of range (-32768 .. +32767)."); return (int) externalValue; } catch (MelderError) { Melder_throw ("Signed short integer not read from text file."); } } long texgeti4 (MelderReadText text) { try { long externalValue = getInteger (text); return externalValue; } catch (MelderError) { Melder_throw ("Signed integer not read from text file."); } } unsigned int texgetu1 (MelderReadText text) { try { long externalValue = getUnsigned (text); if (externalValue > 255) Melder_throw ("Value (", externalValue, ") out of range (0 .. 255)."); return (unsigned int) externalValue; } catch (MelderError) { Melder_throw ("Unsigned small integer not read from text file."); } } unsigned int texgetu2 (MelderReadText text) { try { long externalValue = getUnsigned (text); if (externalValue > 65535) Melder_throw ("Value (", externalValue, ") out of range (0 .. 65535)."); return (unsigned int) externalValue; } catch (MelderError) { Melder_throw ("Unsigned short integer not read from text file."); } } unsigned long texgetu4 (MelderReadText text) { try { long externalValue = getUnsigned (text); return externalValue; } catch (MelderError) { Melder_throw ("Unsigned integer not read from text file."); } } double texgetr4 (MelderReadText text) { return getReal (text); } double texgetr8 (MelderReadText text) { return getReal (text); } double texgetr10 (MelderReadText text) { return getReal (text); } fcomplex texgetc8 (MelderReadText text) { fcomplex z; z.re = getReal (text); z.im = getReal (text); return z; } dcomplex texgetc16 (MelderReadText text) { dcomplex z; z.re = getReal (text); z.im = getReal (text); return z; } short texgete1 (MelderReadText text, int (*getValue) (const wchar_t *)) { return getEnum (text, getValue); } short texgete2 (MelderReadText text, int (*getValue) (const wchar_t *)) { return getEnum (text, getValue); } short texgeteb (MelderReadText text) { return getEnum (text, kBoolean_getValue); } short texgeteq (MelderReadText text) { return getEnum (text, kQuestion_getValue); } short texgetex (MelderReadText text) { return getEnum (text, kExistence_getValue); } char *texgets2 (MelderReadText text) { return Melder_wcsToUtf8 (getString (text)); } char *texgets4 (MelderReadText text) { return Melder_wcsToUtf8 (getString (text)); } wchar_t *texgetw2 (MelderReadText text) { return Melder_wcsdup (getString (text)); } wchar_t *texgetw4 (MelderReadText text) { return Melder_wcsdup (getString (text)); } void texindent (MelderFile file) { file -> indent += 4; } void texexdent (MelderFile file) { file -> indent -= 4; } void texresetindent (MelderFile file) { file -> indent = 0; } void texputintro (MelderFile file, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { if (file -> verbose) { MelderFile_write1 (file, L"\n"); for (int iindent = 1; iindent <= file -> indent; iindent ++) { MelderFile_write1 (file, L" "); } MelderFile_write6 (file, s1 && s1 [0] == 'd' && s1 [1] == '_' ? & s1 [2] : & s1 [0], s2 && s2 [0] == 'd' && s2 [1] == '_' ? & s2 [2] : & s2 [0], s3 && s3 [0] == 'd' && s3 [1] == '_' ? & s3 [2] : & s3 [0], s4 && s4 [0] == 'd' && s4 [1] == '_' ? & s4 [2] : & s4 [0], s5 && s5 [0] == 'd' && s5 [1] == '_' ? & s5 [2] : & s5 [0], s6 && s6 [0] == 'd' && s6 [1] == '_' ? & s6 [2] : & s6 [0]); } file -> indent += 4; } #define PUTLEADER \ MelderFile_write1 (file, L"\n"); \ if (file -> verbose) { \ for (int iindent = 1; iindent <= file -> indent; iindent ++) { \ MelderFile_write1 (file, L" "); \ } \ MelderFile_write6 (file, \ s1 && s1 [0] == 'd' && s1 [1] == '_' ? & s1 [2] : & s1 [0], \ s2 && s2 [0] == 'd' && s2 [1] == '_' ? & s2 [2] : & s2 [0], \ s3 && s3 [0] == 'd' && s3 [1] == '_' ? & s3 [2] : & s3 [0], \ s4 && s4 [0] == 'd' && s4 [1] == '_' ? & s4 [2] : & s4 [0], \ s5 && s5 [0] == 'd' && s5 [1] == '_' ? & s5 [2] : & s5 [0], \ s6 && s6 [0] == 'd' && s6 [1] == '_' ? & s6 [2] : & s6 [0]); \ } void texputi1 (MelderFile file, int i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = " : NULL, Melder_integer (i), file -> verbose ? L" " : NULL); } void texputi2 (MelderFile file, int i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = " : NULL, Melder_integer (i), file -> verbose ? L" " : NULL); } void texputi4 (MelderFile file, long i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = " : NULL, Melder_integer (i), file -> verbose ? L" " : NULL); } void texputu1 (MelderFile file, unsigned int u, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = " : NULL, Melder_integer (u), file -> verbose ? L" " : NULL); } void texputu2 (MelderFile file, unsigned int u, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = " : NULL, Melder_integer (u), file -> verbose ? L" " : NULL); } void texputu4 (MelderFile file, unsigned long u, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = " : NULL, Melder_integer (u), file -> verbose ? L" " : NULL); } void texputr4 (MelderFile file, double x, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = " : NULL, Melder_single (x), file -> verbose ? L" " : NULL); } void texputr8 (MelderFile file, double x, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = " : NULL, Melder_double (x), file -> verbose ? L" " : NULL); } void texputc8 (MelderFile file, fcomplex z, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write5 (file, file -> verbose ? L" = " : NULL, Melder_single (z.re), file -> verbose ? L" + " : L" ", Melder_single (z.im), file -> verbose ? L" i " : NULL); } void texputc16 (MelderFile file, dcomplex z, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write5 (file, file -> verbose ? L" = " : NULL, Melder_double (z.re), file -> verbose ? L" + " : L" ", Melder_double (z.im), file -> verbose ? L" i " : NULL); } void texpute1 (MelderFile file, int i, const wchar_t * (*getText) (int), const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = <" : L"<", getText (i), file -> verbose ? L"> " : L">"); } void texpute2 (MelderFile file, int i, const wchar_t * (*getText) (int), const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = <" : L"<", getText (i), file -> verbose ? L"> " : L">"); } void texputeb (MelderFile file, bool i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L" = " : NULL, i ? L"" : L"", file -> verbose ? L" " : NULL); } void texputeq (MelderFile file, bool i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L"? " : NULL, i ? L"" : L"", file -> verbose ? L" " : NULL); } void texputex (MelderFile file, bool i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write3 (file, file -> verbose ? L"? " : NULL, i ? L"" : L"", file -> verbose ? L" " : NULL); } void texputs1 (MelderFile file, const char *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write1 (file, file -> verbose ? L" = \"" : L"\""); if (s != NULL) { char c; while ((c = *s ++) != '\0') { MelderFile_writeCharacter (file, c); if (c == '\"') MelderFile_writeCharacter (file, c); // double any internal quotes } } MelderFile_write1 (file, file -> verbose ? L"\" " : L"\""); } void texputs2 (MelderFile file, const char *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write1 (file, file -> verbose ? L" = \"" : L"\""); if (s != NULL) { char c; while ((c = *s ++) != '\0') { MelderFile_writeCharacter (file, c); if (c == '\"') MelderFile_writeCharacter (file, c); // double any internal quotes } } MelderFile_write1 (file, file -> verbose ? L"\" " : L"\""); } void texputs4 (MelderFile file, const char *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write1 (file, file -> verbose ? L" = \"" : L"\""); if (s != NULL) { char c; while ((c = *s ++) != '\0') { MelderFile_writeCharacter (file, c); if (c == '\"') MelderFile_writeCharacter (file, c); // double any internal quotes } } MelderFile_write1 (file, file -> verbose ? L"\" " : L"\""); } void texputw2 (MelderFile file, const wchar_t *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write1 (file, file -> verbose ? L" = \"" : L"\""); if (s != NULL) { wchar_t c; while ((c = *s ++) != '\0') { MelderFile_writeCharacter (file, c); if (c == '\"') MelderFile_writeCharacter (file, c); // double any internal quotes } } MelderFile_write1 (file, file -> verbose ? L"\" " : L"\""); } void texputw4 (MelderFile file, const wchar_t *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { PUTLEADER MelderFile_write1 (file, file -> verbose ? L" = \"" : L"\""); if (s != NULL) { wchar_t c; while ((c = *s ++) != '\0') { MelderFile_writeCharacter (file, c); if (c == '\"') MelderFile_writeCharacter (file, c); // double any internal quotes } } MelderFile_write1 (file, file -> verbose ? L"\" " : L"\""); } /********** machine-independent binary I/O **********/ /* Optimizations for machines for which some of the formats are native. */ /* On which machines is "short" a two's complement Big-Endian (MSB-first) 2-byte word? */ #if defined (macintosh) && TARGET_RT_BIG_ENDIAN == 1 #define binario_shortBE2 (sizeof (short) == 2) #define binario_shortLE2 0 #elif defined (_WIN32) || defined (macintosh) && TARGET_RT_LITTLE_ENDIAN == 1 #define binario_shortBE2 0 #define binario_shortLE2 (sizeof (short) == 2) #else #define binario_shortBE2 0 #define binario_shortLE2 0 #endif /* On which machines is "long" a two's complement Big-Endian (MSB-first) 4-byte word? */ #if defined (macintosh) && TARGET_RT_BIG_ENDIAN == 1 #define binario_longBE4 (sizeof (long) == 4) #define binario_longLE4 0 #elif defined (_WIN32) || defined (macintosh) && TARGET_RT_LITTLE_ENDIAN == 1 #define binario_longBE4 0 #define binario_longLE4 (sizeof (long) == 4) #else #define binario_longBE4 0 #define binario_longLE4 0 #endif /* On which machines is "float" IEEE, four bytes, Most Significant Bit first? */ #if defined (macintosh) && TARGET_RT_BIG_ENDIAN == 1 #define binario_floatIEEE4msb (sizeof (float) == 4) #define binario_floatIEEE4lsb 0 #elif defined (_WIN32) || defined (macintosh) && TARGET_RT_LITTLE_ENDIAN == 1 #define binario_floatIEEE4msb 0 #define binario_floatIEEE4lsb (sizeof (float) == 4) #else #define binario_floatIEEE4msb 0 #define binario_floatIEEE4lsb 0 #endif /* On which machines is "double" IEEE, eight bytes, Most Significant Bit first? */ #if defined (macintosh) && TARGET_RT_BIG_ENDIAN == 1 #define binario_doubleIEEE8msb (sizeof (double) == 8) #define binario_doubleIEEE8lsb 0 #elif defined (_WIN32) || defined (macintosh) && TARGET_RT_LITTLE_ENDIAN == 1 #define binario_doubleIEEE8msb 0 #define binario_doubleIEEE8lsb (sizeof (double) == 8) #else #define binario_doubleIEEE8msb 0 #define binario_doubleIEEE8lsb 0 #endif /* The routines bingetr4, bingetr8, binputr4, and binputr8, were implemented by Paul Boersma from the descriptions of the IEEE floating-point formats, as found in the MC68881/MC68882 User's Manual by Motorola (second edition, 1989). The following copyright notice only refers to the code of bingetr10 and binputr10. */ /* Copyright (C) 1988-1991 Apple Computer, Inc. * All rights reserved. * * Warranty Information * Even though Apple has reviewed this software, Apple makes no warranty * or representation, either express or implied, with respect to this * software, its quality, accuracy, merchantability, or fitness for a * particular purpose. As a result, this software is provided "as is," * and you, its user, are assuming the entire risk as to its quality * and accuracy. * * This code may be used and freely distributed as long as it includes * this copyright notice and the above warranty information. * * Machine-independent I/O routines for IEEE floating-point numbers. * * NaN's and infinities are converted to HUGE_VAL or HUGE, which * happens to be infinity on IEEE machines. Unfortunately, it is * impossible to preserve NaN's in a machine-independent way. * Infinities are, however, preserved on IEEE machines. * * These routines have been tested on the following machines: * Apple Macintosh, MPW 3.1 C compiler * Apple Macintosh, THINK C compiler * Silicon Graphics IRIS, MIPS compiler * Cray X/MP and Y/MP * Digital Equipment VAX * * * Implemented by Malcolm Slaney and Ken Turkowski. * * Malcolm Slaney contributions during 1988-1990 include big- and little- * endian file I/O, conversion to and from Motorola's extended 80-bit * floating-point format, and conversions to and from IEEE single- * precision floating-point format. * * In 1991, Ken Turkowski implemented the conversions to and from * IEEE double-precision format, added more precision to the extended * conversions, and accommodated conversions involving +/- infinity, * NaN's, and denormalized numbers. */ // QUESTION: do the following work correctly if a long is 64 bits? # define FloatToUnsigned(f) \ ((unsigned long)(((long)((f) - 2147483648.0)) + 2147483647L + 1)) # define UnsignedToFloat(u) \ (((double)((long)((u) - 2147483647L - 1))) + 2147483648.0) /**************************************************************** * Extended precision IEEE floating-point conversion routines. ****************************************************************/ /* * C O N V E R T T O I E E E E X T E N D E D */ /* * C O N V E R T F R O M I E E E E X T E N D E D */ /*************** End of Apple Computer intermezzo. ***************/ static void readError (FILE *f, const char *text) { Melder_throw (feof (f) ? "Reached end of file" : "Error in file", " while trying to read ", text); } static void writeError (const char *text) { Melder_throw ("Error in file while trying to write ", text); } unsigned int bingetu1 (FILE *f) { try { int externalValue = getc (f); // either -1 (EOF) or in the range 0..255 if (externalValue < 0) readError (f, "a byte."); return (unsigned int) externalValue; } catch (MelderError) { Melder_throw ("Unsigned integer not read from 1 byte in binary file."); } } void binputu1 (unsigned int u, FILE *f) { try { if (putc (u, f) < 0) writeError ("a byte."); } catch (MelderError) { Melder_throw ("Unsigned integer not written to 1 byte in binary file."); } } int bingeti1 (FILE *f) { try { int externalValue = getc (f); if (externalValue < 0) readError (f, "a byte."); return (signed char) externalValue; // this converts e.g. 200 to -56 } catch (MelderError) { Melder_throw ("Signed integer not read from 1 byte in binary file."); } } void binputi1 (int u, FILE *f) { try { if (putc (u, f) < 0) writeError ("a byte."); } catch (MelderError) { Melder_throw ("Signed integer not written to 1 byte in binary file."); } } int bingete1 (FILE *f, int min, int max, const wchar *type) { try { int externalValue = getc (f); if (externalValue < 0) readError (f, "a byte."); int result = (signed char) externalValue; // this converts e.g. 200 to -56, so the enumerated type is signed if (result < min || result > max) Melder_throw (result, " is not a value of enumerated type <", type, ">."); return result; } catch (MelderError) { Melder_throw ("Enumerated type not read from 1 byte in binary file."); } } void binpute1 (int value, FILE *f) { try { if (putc (value, f) < 0) writeError ("a byte."); } catch (MelderError) { Melder_throw ("Enumerated type not written to 1 byte in binary file."); } } static int bitsInReadBuffer = 0; static unsigned char readBuffer; #define macro_bingetb(nbits) \ unsigned int bingetb##nbits (FILE *f) { \ unsigned char result; \ if (bitsInReadBuffer < nbits) { \ int externalValue = fgetc (f); \ if (externalValue < 0) readError (f, "a bit."); \ readBuffer = (unsigned char) externalValue; \ bitsInReadBuffer = 8; \ } \ result = readBuffer << (8 - bitsInReadBuffer); \ bitsInReadBuffer -= nbits; \ return result >> (8 - nbits); \ } macro_bingetb (1) macro_bingetb (2) macro_bingetb (3) macro_bingetb (4) macro_bingetb (5) macro_bingetb (6) macro_bingetb (7) void bingetb (FILE *f) { (void) f; bitsInReadBuffer = 0; } int bingeti2 (FILE *f) { try { if (binario_shortBE2 && Melder_debug != 18) { signed short s; if (fread (& s, sizeof (signed short), 1, f) != 1) readError (f, "a signed short integer."); return (int) s; // with sign extension if an int is 4 bytes } else { unsigned char bytes [2]; if (fread (bytes, sizeof (unsigned char), 2, f) != 2) readError (f, "two bytes."); uint16_t externalValue = ((uint16_t) bytes [0] << 8) | (uint16_t) bytes [1]; return (int) (int16_t) externalValue; // with sign extension if an int is 4 bytes } } catch (MelderError) { Melder_throw ("Signed integer not read from 2 bytes in binary file."); } } unsigned int bingetu2 (FILE *f) { try { if (binario_shortBE2 && Melder_debug != 18) { unsigned short s; if (fread (& s, sizeof (unsigned short), 1, f) != 1) readError (f, "an unsigned short integer."); return s; // without sign extension } else { unsigned char bytes [2]; if (fread (bytes, sizeof (unsigned char), 2, f) != 2) readError (f, "two bytes."); uint16_t externalValue = ((uint16_t) bytes [0] << 8) | (uint16_t) bytes [1]; return (unsigned int) externalValue; } } catch (MelderError) { Melder_throw ("Unsigned integer not read from 2 bytes in binary file."); } } int bingete2 (FILE *f, int min, int max, const wchar_t *type) { try { short result; if (binario_shortBE2 && Melder_debug != 18) { if (fread (& result, sizeof (short), 1, f) != 1) readError (f, "a signed short integer."); } else { unsigned char bytes [2]; if (fread (bytes, sizeof (unsigned char), 2, f) != 2) readError (f, "two bytes."); uint16_t externalValue = ((uint16_t) bytes [0] << 8) | (uint16_t) bytes [1]; result = (short) (int16_t) externalValue; } if (result < min || result > max) Melder_throw (result, " is not a value of enumerated type \"", type, L"\"."); return (int) result; } catch (MelderError) { Melder_throw ("Enumerated value not read from 2 bytes in binary file."); } } long bingeti3 (FILE *f) { try { unsigned char bytes [3]; if (fread (bytes, sizeof (unsigned char), 3, f) != 3) readError (f, "three bytes."); uint32_t externalValue = ((uint32_t) bytes [0] << 16) | ((uint32_t) bytes [1] << 8) | (uint32_t) bytes [2]; if ((bytes [0] & 128) != 0) // is the 24-bit sign bit on? externalValue |= 0xFF000000; // extend negative sign to 32 bits return (long) (int32_t) externalValue; // first convert signedness, then perhaps extend sign to 64 bits! } catch (MelderError) { Melder_throw ("Signed long integer not read from 3 bytes in binary file."); } } long bingeti4 (FILE *f) { try { if (binario_longBE4 && Melder_debug != 18) { long l; if (fread (& l, sizeof (long), 1, f) != 1) readError (f, "a signed long integer."); return l; } else { unsigned char bytes [4]; if (fread (bytes, sizeof (unsigned char), 4, f) != 4) readError (f, "four bytes."); return ((unsigned long) bytes [0] << 24) | ((unsigned long) bytes [1] << 16) | ((unsigned long) bytes [2] << 8) | (unsigned long) bytes [3]; // 32 or 64 bits } } catch (MelderError) { Melder_throw ("Signed long integer not read from 4 bytes in binary file."); } } unsigned long bingetu4 (FILE *f) { try { if (binario_longBE4 && Melder_debug != 18) { unsigned long l; if (fread (& l, sizeof (unsigned long), 1, f) != 1) readError (f, "an unsigned long integer."); return l; } else { unsigned char bytes [4]; if (fread (bytes, sizeof (unsigned char), 4, f) != 4) readError (f, "four bytes."); return ((unsigned long) bytes [0] << 24) | ((unsigned long) bytes [1] << 16) | ((unsigned long) bytes [2] << 8) | (unsigned long) bytes [3]; // 32 or 64 bits } } catch (MelderError) { Melder_throw ("Unsigned long integer not read from 4 bytes in binary file."); } } int bingeti2LE (FILE *f) { try { if (binario_shortLE2 && Melder_debug != 18) { signed short s; if (fread (& s, sizeof (signed short), 1, f) != 1) readError (f, "a signed short integer."); return (int) s; // with sign extension if an int is 4 bytes } else { unsigned char bytes [2]; if (fread (bytes, sizeof (unsigned char), 2, f) != 2) readError (f, "two bytes."); uint16_t externalValue = ((uint16_t) bytes [1] << 8) | (uint16_t) bytes [0]; return (int) (int16_t) externalValue; // with sign extension if an int is 4 bytes } } catch (MelderError) { Melder_throw ("Signed integer not read from 2 bytes in binary file."); } } unsigned int bingetu2LE (FILE *f) { try { if (binario_shortLE2 && Melder_debug != 18) { unsigned short s; if (fread (& s, sizeof (unsigned short), 1, f) != 1) readError (f, "an unsigned short integer."); return s; // without sign extension } else { unsigned char bytes [2]; if (fread (bytes, sizeof (unsigned char), 2, f) != 2) readError (f, "two bytes."); uint16_t externalValue = ((uint16_t) bytes [1] << 8) | (uint16_t) bytes [0]; return (unsigned int) externalValue; } } catch (MelderError) { Melder_throw ("Unsigned integer not read from 2 bytes in binary file."); } } long bingeti3LE (FILE *f) { try { unsigned char bytes [3]; if (fread (bytes, sizeof (unsigned char), 3, f) != 3) readError (f, "three bytes."); uint32_t externalValue = ((uint32_t) bytes [2] << 16) | ((uint32_t) bytes [1] << 8) | (uint32_t) bytes [0]; if ((bytes [2] & 128) != 0) // is the 24-bit sign bit on? externalValue |= 0xFF000000; // extend negative sign to 32 bits return (long) (int32_t) externalValue; // first convert signedness, then perhaps extend sign to 64 bits! } catch (MelderError) { Melder_throw ("Signed long integer not read from 3 bytes in binary file."); } } long bingeti4LE (FILE *f) { try { if (binario_longLE4 && Melder_debug != 18) { long l; if (fread (& l, sizeof (long), 1, f) != 1) readError (f, "a signed long integer."); return l; } else { unsigned char bytes [4]; if (fread (bytes, sizeof (unsigned char), 4, f) != 4) readError (f, "four bytes."); return ((unsigned long) bytes [3] << 24) | ((unsigned long) bytes [2] << 16) | ((unsigned long) bytes [1] << 8) | (unsigned long) bytes [0]; // 32 or 64 bits } } catch (MelderError) { Melder_throw ("Signed long integer not read from 4 bytes in binary file."); } } unsigned long bingetu4LE (FILE *f) { try { if (binario_longLE4 && Melder_debug != 18) { unsigned long l; if (fread (& l, sizeof (unsigned long), 1, f) != 1) readError (f, "an unsigned long integer."); return l; } else { unsigned char bytes [4]; if (fread (bytes, sizeof (unsigned char), 4, f) != 4) readError (f, "four bytes."); return ((unsigned long) bytes [3] << 24) | ((unsigned long) bytes [2] << 16) | ((unsigned long) bytes [1] << 8) | (unsigned long) bytes [0]; // 32 or 64 bits } } catch (MelderError) { Melder_throw ("Unsigned long integer not read from 4 bytes in binary file."); } } double bingetr4 (FILE *f) { try { if (binario_floatIEEE4msb && Melder_debug != 18) { float x; if (fread (& x, sizeof (float), 1, f) != 1) readError (f, "a single-precision floating-point number."); return x; } else { unsigned char bytes [4]; if (fread (bytes, sizeof (unsigned char), 4, f) != 4) readError (f, "four bytes."); long exponent = ((unsigned long) (bytes [0] & 0x7F) << 1) | ((unsigned long) (bytes [1] & 0x80) >> 7); // 32 or 64 bits unsigned long mantissa = ((unsigned long) (bytes [1] & 0x7F) << 16) | ((unsigned long) bytes [2] << 8) | (unsigned long) bytes [3]; // 32 or 64 bits double x; if (exponent == 0) if (mantissa == 0) x = 0.0; else x = ldexp (UnsignedToFloat (mantissa), exponent - 149); // denormalized else if (exponent == 0x00FF) // Infinity or Not-a-Number x = HUGE_VAL; else // finite x = ldexp (UnsignedToFloat (mantissa | 0x00800000), exponent - 150); return bytes [0] & 0x80 ? - x : x; } } catch (MelderError) { Melder_throw ("Floating-point number not read from 4 bytes in binary file."); } } double bingetr4LE (FILE *f) { try { if (binario_floatIEEE4lsb && Melder_debug != 18) { float x; if (fread (& x, sizeof (float), 1, f) != 1) readError (f, "a single-precision floating-point number."); return x; } else { unsigned char bytes [4]; if (fread (bytes, sizeof (unsigned char), 4, f) != 4) readError (f, "four bytes."); long exponent = ((unsigned long) (bytes [3] & 0x7F) << 1) | ((unsigned long) (bytes [2] & 0x80) >> 7); // 32 or 64 bits unsigned long mantissa = ((unsigned long) (bytes [2] & 0x7F) << 16) | ((unsigned long) bytes [1] << 8) | (unsigned long) bytes [0]; // 32 or 64 bits double x; if (exponent == 0) if (mantissa == 0) x = 0.0; else x = ldexp (UnsignedToFloat (mantissa), exponent - 149); // denormalized else if (exponent == 0x00FF) // Infinity or Not-a-Number. */ x = HUGE_VAL; else // finite x = ldexp (UnsignedToFloat (mantissa | 0x00800000), exponent - 150); return bytes [3] & 0x80 ? - x : x; } } catch (MelderError) { Melder_throw ("Floating-point number not read from 4 bytes in binary file."); } } double bingetr8 (FILE *f) { try { if (binario_doubleIEEE8msb && Melder_debug != 18) { double x; if (fread (& x, sizeof (double), 1, f) != 1) readError (f, "a double-precision floating-point number."); return x; } else { unsigned char bytes [8]; if (fread (bytes, sizeof (unsigned char), 8, f) != 8) readError (f, "eight bytes."); Melder_assert (sizeof (long) >= 4); long exponent = ((unsigned long) (bytes [0] & 0x7F) << 4) | ((unsigned long) (bytes [1] & 0xF0) >> 4); unsigned long highMantissa = ((unsigned long) (bytes [1] & 0x0F) << 16) | ((unsigned long) bytes [2] << 8) | (unsigned long) bytes [3]; unsigned long lowMantissa = ((unsigned long) bytes [4] << 24) | ((unsigned long) bytes [5] << 16) | ((unsigned long) bytes [6] << 8) | (unsigned long) bytes [7]; double x; if (exponent == 0) if (highMantissa == 0 && lowMantissa == 0) x = 0.0; else x = ldexp (UnsignedToFloat (highMantissa), exponent - 1042) + ldexp (UnsignedToFloat (lowMantissa), exponent - 1074); // denormalized else if (exponent == 0x07FF) // Infinity or Not-a-Number x = HUGE_VAL; else x = ldexp (UnsignedToFloat (highMantissa | 0x00100000), exponent - 1043) + ldexp (UnsignedToFloat (lowMantissa), exponent - 1075); return bytes [0] & 0x80 ? - x : x; } } catch (MelderError) { Melder_throw ("Floating-point number not read from 8 bytes in binary file."); } } double bingetr10 (FILE *f) { try { unsigned char bytes [10]; if (fread (bytes, sizeof (unsigned char), 10, f) != 10) readError (f, "ten bytes."); long exponent = ((bytes [0] & 0x7F) << 8) | bytes [1]; unsigned long highMantissa = ((unsigned long) bytes [2] << 24) | ((unsigned long) bytes [3] << 16) | ((unsigned long) bytes [4] << 8) | (unsigned long) bytes [5]; unsigned long lowMantissa = ((unsigned long) bytes [6] << 24) | ((unsigned long) bytes [7] << 16) | ((unsigned long) bytes [8] << 8) | (unsigned long) bytes [9]; double x; if (exponent == 0 && highMantissa == 0 && lowMantissa == 0) x = 0; else if (exponent == 0x7FFF) x = HUGE_VAL; /* Infinity or NaN */ else { exponent -= 16383; x = ldexp (UnsignedToFloat (highMantissa), exponent - 31); x += ldexp (UnsignedToFloat (lowMantissa), exponent - 63); } return bytes [0] & 0x80 ? - x : x; } catch (MelderError) { Melder_throw ("Floating-point number not read from 10 bytes in binary file."); } } static int bitsInWriteBuffer = 0; static unsigned char writeBuffer = 0; #define macro_binputb(nbits) \ void binputb##nbits (unsigned int value, FILE *f) { \ if (bitsInWriteBuffer + nbits > 8) { \ if (fputc (writeBuffer, f) < 0) writeError ("a bit."); \ bitsInWriteBuffer = 0; \ writeBuffer = 0; \ } \ writeBuffer |= (value << (8 - nbits)) >> bitsInWriteBuffer; \ bitsInWriteBuffer += nbits; \ } macro_binputb (1) macro_binputb (2) macro_binputb (3) macro_binputb (4) macro_binputb (5) macro_binputb (6) macro_binputb (7) void binputb (FILE *f) { if (bitsInWriteBuffer == 0) return; if (fputc (writeBuffer, f) < 0) writeError ("a bit."); // flush bitsInWriteBuffer = 0; writeBuffer = 0; } void binputi2 (int i, FILE *f) { try { if (binario_shortBE2 && Melder_debug != 18) { short s = i; if (fwrite (& s, sizeof (short), 1, f) != 1) writeError ("a signed short integer."); } else { char bytes [2]; bytes [0] = i >> 8; bytes [1] = i; if (fwrite (bytes, sizeof (char), 2, f) != 2) writeError ("two bytes."); } } catch (MelderError) { Melder_throw ("Signed integer not written to 2 bytes in binary file."); } } void binputu2 (unsigned int u, FILE *f) { try { if (binario_shortBE2 && Melder_debug != 18) { unsigned short s = u; if (fwrite (& s, sizeof (unsigned short), 1, f) != 1) writeError ("an unsigned short integer."); } else { char bytes [2]; bytes [0] = u >> 8; bytes [1] = u; if (fwrite (bytes, sizeof (char), 2, f) != 2) writeError ("two bytes."); } } catch (MelderError) { Melder_throw ("Unsigned integer not written to 2 bytes in binary file."); } } void binpute2 (int value, FILE *f) { try { if (binario_shortBE2 && Melder_debug != 18) { short s = value; if (fwrite (& s, sizeof (short), 1, f) != 1) writeError ("a signed short integer"); } else { char bytes [2]; bytes [0] = value >> 8; bytes [1] = value; if (fwrite (bytes, sizeof (char), 2, f) != 2) writeError ("two bytes."); } } catch (MelderError) { Melder_throw ("Enumerated value not written to 2 bytes in binary file."); } } void binputi3 (long i, FILE *f) { try { char bytes [3]; bytes [0] = i >> 16; bytes [1] = i >> 8; bytes [2] = i; if (fwrite (bytes, sizeof (char), 3, f) != 3) writeError ("three bytes"); } catch (MelderError) { Melder_throw ("Signed integer not written to 3 bytes in binary file."); } } void binputi4 (long i, FILE *f) { try { if (binario_longBE4 && Melder_debug != 18) { if (fwrite (& i, sizeof (long), 1, f) != 1) writeError ("a signed long integer."); } else { char bytes [4]; bytes [0] = i >> 24; bytes [1] = i >> 16; bytes [2] = i >> 8; bytes [3] = i; if (fwrite (bytes, sizeof (char), 4, f) != 4) writeError ("four bytes."); } } catch (MelderError) { Melder_throw ("Signed integer not written to 4 bytes in binary file."); } } void binputu4 (unsigned long u, FILE *f) { try { if (binario_longBE4 && Melder_debug != 18) { if (fwrite (& u, sizeof (unsigned long), 1, f) != 1) writeError ("an unsigned long integer."); } else { char bytes [4]; bytes [0] = u >> 24; bytes [1] = u >> 16; bytes [2] = u >> 8; bytes [3] = u; if (fwrite (bytes, sizeof (char), 4, f) != 4) writeError ("four bytes."); } } catch (MelderError) { Melder_throw ("Unsigned integer not written to 4 bytes in binary file."); } } void binputi2LE (int i, FILE *f) { try { if (binario_shortLE2 && Melder_debug != 18) { short s = i; if (fwrite (& s, sizeof (short), 1, f) != 1) writeError ("a signed short integer."); } else { char bytes [2]; bytes [1] = i >> 8; bytes [0] = i; if (fwrite (bytes, sizeof (char), 2, f) != 2) writeError ("two bytes."); } } catch (MelderError) { Melder_throw ("Signed integer not written to 2 bytes in binary file."); } } void binputu2LE (unsigned int u, FILE *f) { try { if (binario_shortLE2 && Melder_debug != 18) { unsigned short s = u; if (fwrite (& s, sizeof (unsigned short), 1, f) != 1) writeError ("an unsigned short integer."); } else { char bytes [2]; bytes [1] = u >> 8; bytes [0] = u; if (fwrite (bytes, sizeof (char), 2, f) != 2) writeError ("two bytes."); } } catch (MelderError) { Melder_throw ("Unsigned integer not written to 2 bytes in binary file."); } } void binputi3LE (long i, FILE *f) { try { char bytes [3]; bytes [2] = i >> 16; bytes [1] = i >> 8; bytes [0] = i; if (fwrite (bytes, sizeof (char), 3, f) != 3) writeError ("three bytes"); } catch (MelderError) { Melder_throw ("Signed integer not written to 3 bytes in binary file."); } } void binputi4LE (long i, FILE *f) { try { if (binario_longLE4 && Melder_debug != 18) { if (fwrite (& i, sizeof (long), 1, f) != 1) writeError ("a signed long integer."); } else { char bytes [4]; bytes [3] = i >> 24; bytes [2] = i >> 16; bytes [1] = i >> 8; bytes [0] = i; if (fwrite (bytes, sizeof (char), 4, f) != 4) writeError ("four bytes."); } } catch (MelderError) { Melder_throw ("Signed integer not written to 4 bytes in binary file."); } } void binputu4LE (unsigned long u, FILE *f) { try { if (binario_longLE4 && Melder_debug != 18) { if (fwrite (& u, sizeof (unsigned long), 1, f) != 1) writeError ("an unsigned long integer."); } else { char bytes [4]; bytes [3] = u >> 24; bytes [2] = u >> 16; bytes [1] = u >> 8; bytes [0] = u; if (fwrite (bytes, sizeof (char), 4, f) != 4) writeError ("four bytes."); } } catch (MelderError) { Melder_throw ("Unsigned integer not written to 4 bytes in binary file."); } } void binputr4 (double x, FILE *f) { try { if (binario_floatIEEE4msb && Melder_debug != 18) { float x4 = x; if (fwrite (& x4, sizeof (float), 1, f) != 1) writeError ("a single-precision floating-point number."); } else { unsigned char bytes [4]; int sign, exponent; double fMantissa, fsMantissa; unsigned long mantissa; if (x < 0.0) { sign = 0x0100; x *= -1; } else sign = 0; if (x == 0.0) { exponent = 0; mantissa = 0; } else { fMantissa = frexp (x, & exponent); if ((exponent > 128) || ! (fMantissa < 1)) // Infinity or Not-a-Number { exponent = sign | 0x00FF; mantissa = 0; } // Infinity else { /* Finite. */ exponent += 126; // add bias if (exponent <= 0) { // denormalized fMantissa = ldexp (fMantissa, exponent - 1); exponent = 0; } exponent |= sign; fMantissa = ldexp (fMantissa, 24); fsMantissa = floor (fMantissa); mantissa = FloatToUnsigned (fsMantissa) & 0x007FFFFF; } } bytes [0] = exponent >> 1; bytes [1] = (exponent << 7) | (mantissa >> 16); bytes [2] = mantissa >> 8; bytes [3] = mantissa; if (fwrite (bytes, sizeof (unsigned char), 4, f) != 4) writeError ("four bytes."); } } catch (MelderError) { Melder_throw ("Floating-point number not written to 4 bytes in binary file."); } } void binputr4LE (double x, FILE *f) { try { if (binario_floatIEEE4lsb && Melder_debug != 18) { float x4 = x; if (fwrite (& x4, sizeof (float), 1, f) != 1) writeError ("a single-precision floating-point number."); } else { unsigned char bytes [4]; int sign, exponent; double fMantissa, fsMantissa; unsigned long mantissa; if (x < 0.0) { sign = 0x0100; x *= -1; } else sign = 0; if (x == 0.0) { exponent = 0; mantissa = 0; } else { fMantissa = frexp (x, & exponent); if ((exponent > 128) || ! (fMantissa < 1)) // Infinity or Not-a-Number { exponent = sign | 0x00FF; mantissa = 0; } // Infinity else { /* Finite. */ exponent += 126; // add bias if (exponent <= 0) { // denormalized fMantissa = ldexp (fMantissa, exponent - 1); exponent = 0; } exponent |= sign; fMantissa = ldexp (fMantissa, 24); fsMantissa = floor (fMantissa); mantissa = FloatToUnsigned (fsMantissa) & 0x007FFFFF; } } bytes [3] = exponent >> 1; bytes [2] = (exponent << 7) | (mantissa >> 16); bytes [1] = mantissa >> 8; bytes [0] = mantissa; if (fwrite (bytes, sizeof (unsigned char), 4, f) != 4) writeError ("four bytes."); } } catch (MelderError) { Melder_throw ("Floating-point number not written to 4 bytes in binary file."); } } void binputr8 (double x, FILE *f) { try { if (binario_doubleIEEE8msb && Melder_debug != 18) { if (fwrite (& x, sizeof (double), 1, f) != 1) writeError ("a double-precision floating-point number."); } else { unsigned char bytes [8]; int sign, exponent; double fMantissa, fsMantissa; unsigned long highMantissa, lowMantissa; if (x < 0.0) { sign = 0x0800; x *= -1; } else sign = 0; if (x == 0.0) { exponent = 0; highMantissa = 0; lowMantissa = 0; } else { fMantissa = frexp (x, & exponent); if ((exponent > 1024) || ! (fMantissa < 1)) // Infinity or Not-a-Number { exponent = sign | 0x07FF; highMantissa = 0; lowMantissa = 0; } // Infinity else { /* Finite. */ exponent += 1022; // add bias if (exponent <= 0) { // denormalized fMantissa = ldexp (fMantissa, exponent - 1); exponent = 0; } exponent |= sign; fMantissa = ldexp (fMantissa, 21); fsMantissa = floor (fMantissa); highMantissa = FloatToUnsigned (fsMantissa) & 0x000FFFFF; fMantissa = ldexp (fMantissa - fsMantissa, 32); fsMantissa = floor (fMantissa); lowMantissa = FloatToUnsigned (fsMantissa); } } bytes [0] = exponent >> 4; bytes [1] = (exponent << 4) | (highMantissa >> 16); bytes [2] = highMantissa >> 8; bytes [3] = highMantissa; bytes [4] = lowMantissa >> 24; bytes [5] = lowMantissa >> 16; bytes [6] = lowMantissa >> 8; bytes [7] = lowMantissa; if (fwrite (bytes, sizeof (unsigned char), 8, f) != 8) writeError ("eight bytes."); } } catch (MelderError) { Melder_throw ("Floating-point number not written to 8 bytes in binary file."); } } void binputr10 (double x, FILE *f) { try { unsigned char bytes [10]; int sign, exponent; double fMantissa, fsMantissa; unsigned long highMantissa, lowMantissa; if (x < 0.0) { sign = 0x8000; x *= -1; } else sign = 0; if (x == 0.0) { exponent = 0; highMantissa = 0; lowMantissa = 0; } else { fMantissa = frexp (x, & exponent); if ((exponent > 16384) || ! (fMantissa < 1)) // Infinity or Not-a-Number { exponent = sign | 0x7FFF; highMantissa = 0; lowMantissa = 0; } // Infinity else { /* Finite */ exponent += 16382; /* Add bias. */ if (exponent < 0) { /* Denormalized. */ fMantissa = ldexp (fMantissa, exponent); exponent = 0; } exponent |= sign; fMantissa = ldexp (fMantissa, 32); fsMantissa = floor (fMantissa); highMantissa = FloatToUnsigned (fsMantissa); fMantissa = ldexp (fMantissa - fsMantissa, 32); fsMantissa = floor (fMantissa); lowMantissa = FloatToUnsigned (fsMantissa); } } bytes [0] = exponent >> 8; bytes [1] = exponent; bytes [2] = highMantissa >> 24; bytes [3] = highMantissa >> 16; bytes [4] = highMantissa >> 8; bytes [5] = highMantissa; bytes [6] = lowMantissa >> 24; bytes [7] = lowMantissa >> 16; bytes [8] = lowMantissa >> 8; bytes [9] = lowMantissa; if (fwrite (bytes, sizeof (unsigned char), 10, f) != 10) writeError ("ten bytes."); } catch (MelderError) { Melder_throw ("Floating-point number not written to 10 bytes in binary file."); } } fcomplex bingetc8 (FILE *f) { try { fcomplex result; result. re = bingetr4 (f); result. im = bingetr4 (f); return result; } catch (MelderError) { Melder_throw ("Complex number not read from 8 bytes in binary file."); fcomplex result = { 0 }; return result; } } dcomplex bingetc16 (FILE *f) { try { dcomplex result; result. re = bingetr8 (f); result. im = bingetr8 (f); return result; } catch (MelderError) { Melder_throw ("Complex number not read from 16 bytes in binary file."); dcomplex result = { 0 }; return result; } } void binputc8 (fcomplex z, FILE *f) { try { binputr4 (z. re, f); binputr4 (z. im, f); } catch (MelderError) { Melder_throw ("Complex number not written to 8 bytes in binary file."); } } void binputc16 (dcomplex z, FILE *f) { try { binputr8 (z. re, f); binputr8 (z. im, f); } catch (MelderError) { Melder_throw ("Complex number not written to 16 bytes in binary file."); } } char * bingets1 (FILE *f) { try { unsigned int length = bingetu1 (f); autostring8 result = Melder_malloc (char, length + 1); if (fread (result.peek(), sizeof (char), length, f) != length) Melder_throw (feof (f) ? "Reached end of file" : "Error in file", " while trying to read ", length, " one-byte characters."); result [length] = 0; // trailing null byte return result.transfer(); } catch (MelderError) { Melder_throw ("Text not read from a binary file."); } } char * bingets2 (FILE *f) { try { unsigned int length = bingetu2 (f); autostring8 result = Melder_malloc (char, length + 1); if (fread (result.peek(), sizeof (char), length, f) != length) Melder_throw (feof (f) ? "Reached end of file" : "Error in file", " while trying to read ", length, " one-byte characters."); result [length] = 0; // trailing null byte return result.transfer(); } catch (MelderError) { Melder_throw ("Text not read from a binary file."); } } char * bingets4 (FILE *f) { try { unsigned long length = bingetu4 (f); autostring8 result = Melder_malloc (char, length + 1); if (fread (result.peek(), sizeof (char), length, f) != length) Melder_throw (feof (f) ? "Reached end of file" : "Error in file", " while trying to read ", length, " one-byte characters."); result [length] = 0; // trailing null byte return result.transfer(); } catch (MelderError) { Melder_throw ("Text not read from a binary file."); } } wchar * bingetw1 (FILE *f) { try { autostring result = NULL; unsigned short length = bingetu1 (f); if (length == 0xFF) { // an escape for encoding /* * UTF-16 */ length = bingetu1 (f); result.reset (Melder_malloc (wchar, length + 1)); for (unsigned short i = 0; i < length; i ++) { if (sizeof (wchar_t) == 2) { result [i] = bingetu2 (f); } else { uint16_t kar = bingetu2 (f); if ((kar & 0xF800) == 0xD800) { if (kar > 0xDBFF) Melder_throw ("Incorrect Unicode value (first surrogate member ", kar, ")."); uint16_t kar2 = bingetu2 (f); if (kar2 < 0xDC00 || kar2 > 0xDFFF) Melder_throw ("Incorrect Unicode value (second surrogate member ", kar2, ")."); result [i] = (((kar & 0x3FF) << 10) | (kar2 & 0x3FF)) + 0x10000; } else { result [i] = kar; } } } } else { /* * ASCII */ result.reset (Melder_malloc (wchar, length + 1)); for (unsigned short i = 0; i < length; i ++) { result [i] = bingetu1 (f); } } result [length] = L'\0'; return result.transfer(); } catch (MelderError) { Melder_throw ("Text not read from a binary file."); } } wchar * bingetw2 (FILE *f) { try { autostring result = NULL; unsigned short length = bingetu2 (f); if (length == 0xFFFF) { // an escape for encoding /* * UTF-16 */ length = bingetu2 (f); result.reset (Melder_malloc (wchar, length + 1)); for (unsigned short i = 0; i < length; i ++) { if (sizeof (wchar_t) == 2) { result [i] = bingetu2 (f); } else { unsigned short kar = bingetu2 (f); if ((kar & 0xF800) == 0xD800) { if (kar > 0xDBFF) Melder_throw ("Incorrect Unicode value (first surrogate member ", kar, ")."); unsigned short kar2 = bingetu2 (f); if (kar2 < 0xDC00 || kar2 > 0xDFFF) Melder_throw ("Incorrect Unicode value (second surrogate member ", kar2, ")."); result [i] = (((kar & 0x3FF) << 10) | (kar2 & 0x3FF)) + 0x10000; } else { result [i] = kar; } } } } else { /* * ASCII */ result.reset (Melder_malloc (wchar, length + 1)); for (unsigned short i = 0; i < length; i ++) { result [i] = bingetu1 (f); } } result [length] = L'\0'; return result.transfer(); } catch (MelderError) { Melder_throw ("Text not read from a binary file."); } } wchar * bingetw4 (FILE *f) { try { autostring result = NULL; unsigned long length = bingetu4 (f); if (length == 0xFFFFFFFF) { // an escape for encoding /* * UTF-16 */ length = bingetu4 (f); result.reset (Melder_malloc (wchar, length + 1)); for (unsigned long i = 0; i < length; i ++) { if (sizeof (wchar_t) == 2) { result [i] = bingetu2 (f); } else { unsigned short kar = bingetu2 (f); if ((kar & 0xF800) == 0xD800) { if (kar > 0xDBFF) Melder_throw ("Incorrect Unicode value (first surrogate member ", kar, ")."); unsigned short kar2 = bingetu2 (f); if (kar2 < 0xDC00 || kar2 > 0xDFFF) Melder_throw ("Incorrect Unicode value (second surrogate member ", kar2, ")."); result [i] = (((kar & 0x3FF) << 10) | (kar2 & 0x3FF)) + 0x10000; } else { result [i] = kar; } } } } else { /* * ASCII */ result.reset (Melder_malloc (wchar, length + 1)); for (unsigned long i = 0; i < length; i ++) { result [i] = bingetu1 (f); } } result [length] = L'\0'; return result.transfer(); } catch (MelderError) { Melder_throw ("Text not read from a binary file."); } } void binputs1 (const char *s, FILE *f) { try { if (s == NULL) { binputu1 (0, f); } else { unsigned long length = strlen (s); if (length > 255) { Melder_warning ("Text of ", length, " characters truncated to 255 characters."); length = 255; } binputu1 (length, f); if (fwrite (s, sizeof (char), length, f) != length) Melder_throw ("Error in file while trying to write ", length, " one-byte characters."); } } catch (MelderError) { Melder_throw ("Text not written to a binary file."); } } void binputs2 (const char *s, FILE *f) { try { if (s == NULL) { binputu2 (0, f); } else { unsigned long length = strlen (s); if (length > 65535) { Melder_warning ("Text of ", length, " characters truncated to 65535 characters."); length = 65535; } binputu2 (length, f); if (fwrite (s, sizeof (char), length, f) != length) Melder_throw ("Error in file while trying to write ", length, " one-byte characters."); } } catch (MelderError) { Melder_throw ("Text not written to a binary file."); } } void binputs4 (const char *s, FILE *f) { try { if (s == NULL) { binputu4 (0, f); } else { unsigned long length = strlen (s); binputu4 (length, f); if (fwrite (s, sizeof (char), length, f) != length) Melder_throw ("Error in file while trying to write ", length, " one-byte characters."); } } catch (MelderError) { Melder_throw ("Text not written to a binary file."); } } static inline void binpututf16 (wchar_t character, FILE *f) { if (sizeof (wchar_t) == 2) { // wchar_t is UTF-16? binputu2 (character, f); } else { // wchar_t is UTF-32. MelderUtf32 kar = character; if (kar <= 0xFFFF) { binputu2 (character, f); } else if (kar <= 0x10FFFF) { kar -= 0x10000; binputu2 (0xD800 | (kar >> 10), f); binputu2 (0xDC00 | (kar & 0x3FF), f); } else { Melder_fatal ("Impossible Unicode value."); } } } void binputw1 (const wchar_t *s, FILE *f) { try { if (s == NULL) { binputu1 (0, f); } else { unsigned long length = wcslen (s); if (length > 254) { Melder_warning ("Text of ", length, " characters truncated to 254 characters."); length = 254; } if (Melder_isValidAscii (s)) { /* * ASCII */ binputu1 (length, f); for (unsigned long i = 0; i < length; i ++) { binputu1 (s [i], f); } } else { /* * UTF-16 */ binputu1 (0xFF, f); // an escape for multibyte encoding binputu1 (length, f); for (unsigned long i = 0; i < length; i ++) { binpututf16 (s [i], f); } } } } catch (MelderError) { Melder_throw ("Text not written to a binary file."); } } void binputw2 (const wchar_t *s, FILE *f) { try { if (s == NULL) { binputu2 (0, f); } else { unsigned long length = wcslen (s); if (length > 65534) { Melder_warning ("Text of ", length, " characters truncated to 65534 characters."); length = 65534; } if (Melder_isValidAscii (s)) { /* * ASCII */ binputu2 (length, f); for (unsigned long i = 0; i < length; i ++) { binputu1 (s [i], f); } } else { /* * UTF-16 */ binputu2 (0xFFFF, f); // an escape for multibyte encoding binputu2 (length, f); for (unsigned long i = 0; i < length; i ++) { binpututf16 (s [i], f); } } } } catch (MelderError) { Melder_throw ("Text not written to a binary file."); } } void binputw4 (const wchar_t *s, FILE *f) { try { if (s == NULL) { binputu4 (0, f); } else { unsigned long length = wcslen (s); if (Melder_isValidAscii (s)) { /* * ASCII */ binputu4 (length, f); for (unsigned long i = 0; i < length; i ++) { binputu1 (s [i], f); } } else { /* * UTF-16 */ binputu4 (0xFFFFFFFF, f); // an escape for multibyte encoding binputu4 (length, f); for (unsigned long i = 0; i < length; i ++) { binpututf16 (s [i], f); } } } } catch (MelderError) { Melder_throw ("Text not written to a binary file."); } } /********** machine-independent cache I/O **********/ #define my me -> #define START(x) char *ptr = (char *) & (x); #define READ * ptr ++ = * f -> ptr ++; #define WRITE * f -> ptr ++ = * ptr ++; CACHE * memopen (size_t nbytes) { CACHE *me; if (nbytes < 1) return NULL; me = Melder_malloc (CACHE, 1); my base = Melder_malloc (unsigned char, nbytes); my max = my base + nbytes; my ptr = my base; return me; } int memclose (CACHE *me) { if (! me || ! my base) return EOF; Melder_free (my base); Melder_free (me); return 0; } size_t memread (void *ptr, size_t size, size_t nmemb, CACHE *me) { size_t nbytes = size * nmemb; memcpy (ptr, my ptr, nbytes); my ptr += nbytes; return nmemb; } size_t memwrite (const void *ptr, size_t size, size_t nmemb, CACHE *me) { size_t nbytes = size * nmemb; Melder_assert (my ptr + nbytes <= my max); memcpy (my ptr, ptr, nbytes); my ptr += nbytes; return nmemb; } void memprint1 (CACHE *me, const char *s1) { (void) memwrite (s1, 1, strlen (s1), me); } void memprint2 (CACHE *me, const char *s1, const char *s2) { (void) memwrite (s1, 1, strlen (s1), me); (void) memwrite (s2, 1, strlen (s2), me); } void memprint3 (CACHE *me, const char *s1, const char *s2, const char *s3) { (void) memwrite (s1, 1, strlen (s1), me); (void) memwrite (s2, 1, strlen (s2), me); (void) memwrite (s3, 1, strlen (s3), me); } void memprint4 (CACHE *me, const char *s1, const char *s2, const char *s3, const char *s4) { (void) memwrite (s1, 1, strlen (s1), me); (void) memwrite (s2, 1, strlen (s2), me); (void) memwrite (s3, 1, strlen (s3), me); (void) memwrite (s4, 1, strlen (s4), me); } void memprint5 (CACHE *me, const char *s1, const char *s2, const char *s3, const char *s4, const char *s5) { (void) memwrite (s1, 1, strlen (s1), me); (void) memwrite (s2, 1, strlen (s2), me); (void) memwrite (s3, 1, strlen (s3), me); (void) memwrite (s4, 1, strlen (s4), me); (void) memwrite (s5, 1, strlen (s5), me); } unsigned int cacgetu1 (CACHE *me) { return * (unsigned char *) my ptr ++; } void cacputu1 (unsigned int u, CACHE *me) { * (unsigned char *) my ptr ++ = u; } int cacgeti1 (CACHE *me) { return * (signed char *) my ptr ++; } void cacputi1 (int u, CACHE *me) { * (signed char *) my ptr ++ = u; } int cacgete1 (CACHE *me, const wchar_t *type) { int result = * (signed char *) my ptr ++; if (result < 0) Melder_throw ("(cacgete1:) ", result, " is not a value of enumerated type \"", type, "\"."); return result; } void cacpute1 (int value, CACHE *me) { * (signed char *) my ptr ++ = value; } int memseek (CACHE *me, long offset, int whence) { my ptr = whence == 0 ? my base + offset : my ptr + offset; return 0; } long memtell (CACHE *me) { return my ptr - my base; } void memrewind (CACHE *me) { my ptr = my base; } #define macro_cacgetb(nbits) \ unsigned int cacgetb##nbits (CACHE *f) { \ unsigned char result; \ if (bitsInReadBuffer < nbits) { readBuffer = * f -> ptr ++; bitsInReadBuffer = 8; } \ result = readBuffer << (8 - bitsInReadBuffer); \ bitsInReadBuffer -= nbits; \ return result >> (8 - nbits); \ } macro_cacgetb (1) macro_cacgetb (2) macro_cacgetb (3) macro_cacgetb (4) macro_cacgetb (5) macro_cacgetb (6) macro_cacgetb (7) void cacgetb (CACHE *f) { (void) f; bitsInReadBuffer = 0; } int cacgeti2 (CACHE *f) { if (binario_shortBE2) { short s; START (s) READ READ return s; /* With sign extension if an int is 4 bytes. */ } else { unsigned char bytes [2]; START (bytes) READ READ return (signed short) (((unsigned short) bytes [0] << 8) | (unsigned short) bytes [1]); } } unsigned int cacgetu2 (CACHE *f) { if (binario_shortBE2) { unsigned short s; START (s) READ READ return s; /* Without sign extension. */ } else { unsigned char bytes [2]; START (bytes) READ READ return ((unsigned short) bytes [0] << 8) | (unsigned short) bytes [1]; } } int cacgete2 (CACHE *f, const wchar_t *type) { signed short s; if (binario_shortBE2) { START (s) READ READ } else { unsigned char bytes [2]; START (bytes) READ READ s = ((unsigned short) bytes [0] << 8) | (unsigned short) bytes [1]; } if (s < 0) Melder_throw ("(cacgete2:) ", s, " is not a value of enumerated type \"", type, "\"."); return s; } long cacgeti4 (CACHE *f) { if (binario_longBE4) { long l; START (l) READ READ READ READ return l; } else { unsigned char bytes [4]; START (bytes) READ READ READ READ return ((unsigned long) bytes [0] << 24) | ((unsigned long) bytes [1] << 16) | ((unsigned long) bytes [2] << 8) | (unsigned long) bytes [3]; } } unsigned long cacgetu4 (CACHE *f) { if (binario_longBE4) { unsigned long l; START (l) READ READ READ READ return l; } else { unsigned char bytes [4]; START (bytes) READ READ READ READ return ((unsigned long) bytes [0] << 24) | ((unsigned long) bytes [1] << 16) | ((unsigned long) bytes [2] << 8) | (unsigned long) bytes [3]; } } int cacgeti2LE (CACHE *f) { unsigned char bytes [2]; START (bytes) READ READ return (signed short) (((unsigned short) bytes [1] << 8) | (unsigned short) bytes [0]); } unsigned int cacgetu2LE (CACHE *f) { unsigned char bytes [2]; START (bytes) READ READ return ((unsigned short) bytes [1] << 8) | (unsigned short) bytes [0]; } long cacgeti4LE (CACHE *f) { unsigned char bytes [4]; START (bytes) READ READ READ READ return ((unsigned long) bytes [3] << 24) | ((unsigned long) bytes [2] << 16) | ((unsigned long) bytes [1] << 8) | (unsigned long) bytes [0]; } unsigned long cacgetu4LE (CACHE *f) { unsigned char bytes [4]; START (bytes) READ READ READ READ return ((unsigned long) bytes [3] << 24) | ((unsigned long) bytes [2] << 16) | ((unsigned long) bytes [1] << 8) | (unsigned long) bytes [0]; } double cacgetr4 (CACHE *f) { if (binario_floatIEEE4msb) { float x; START (x) READ READ READ READ return x; } else { unsigned char bytes [4]; double x; long exponent; unsigned long mantissa; START (bytes) READ READ READ READ exponent = ((unsigned long) (bytes [0] & 0x7F) << 1) | ((unsigned long) (bytes [1] & 0x80) >> 7); mantissa = ((unsigned long) (bytes [1] & 0x7F) << 16) | ((unsigned long) bytes [2] << 8) | (unsigned long) bytes [3]; if (exponent == 0) if (mantissa == 0) x = 0.0; else x = ldexp (UnsignedToFloat (mantissa), exponent - 149); /* Denormalized. */ else if (exponent == 0x00FF) /* Infinity or Not-a-Number. */ x = HUGE_VAL; else /* Finite. */ x = ldexp (UnsignedToFloat (mantissa | 0x00800000), exponent - 150); return bytes [0] & 0x80 ? - x : x; } } double cacgetr8 (CACHE *f) { if (binario_doubleIEEE8msb) { double x; START (x) READ READ READ READ READ READ READ READ return x; } else { unsigned char bytes [8]; double x; long exponent; unsigned long highMantissa, lowMantissa; START (bytes) READ READ READ READ READ READ READ READ exponent = ((unsigned long) (bytes [0] & 0x7F) << 4) | ((unsigned long) (bytes [1] & 0xF0) >> 4); highMantissa = ((unsigned long) (bytes [1] & 0x0F) << 16) | ((unsigned long) bytes [2] << 8) | (unsigned long) bytes [3]; lowMantissa = ((unsigned long) bytes [4] << 24) | ((unsigned long) bytes [5] << 16) | ((unsigned long) bytes [6] << 8) | (unsigned long) bytes [7]; if (exponent == 0) if (highMantissa == 0 && lowMantissa == 0) x = 0.0; else x = ldexp (UnsignedToFloat (highMantissa), exponent - 1042) + ldexp (UnsignedToFloat (lowMantissa), exponent - 1074); /* Denormalized. */ else if (exponent == 0x07FF) /* Infinity of Not-a-Number. */ x = HUGE_VAL; else x = ldexp (UnsignedToFloat (highMantissa | 0x00100000), exponent - 1043) + ldexp (UnsignedToFloat (lowMantissa), exponent - 1075); return bytes [0] & 0x80 ? - x : x; } } double cacgetr10 (CACHE *f) { unsigned char bytes [10]; double x; long exponent; unsigned long highMantissa, lowMantissa; START (bytes) READ READ READ READ READ READ READ READ READ READ exponent = ((unsigned long) (bytes [0] & 0x7F) << 8) | bytes [1]; highMantissa = ((unsigned long) bytes [2] << 24) | ((unsigned long) bytes [3] << 16) | ((unsigned long) bytes [4] << 8) | (unsigned long) bytes [5]; lowMantissa = ((unsigned long) bytes [6] << 24) | ((unsigned long) bytes [7] << 16) | ((unsigned long) bytes [8] << 8) | (unsigned long) bytes [9]; if (exponent == 0 && highMantissa == 0 && lowMantissa == 0) x = 0; else if (exponent == 0x7FFF) x = HUGE_VAL; /* Infinity or NaN */ else { exponent -= 16383; x = ldexp (UnsignedToFloat (highMantissa), exponent - 31); x += ldexp (UnsignedToFloat (lowMantissa), exponent - 63); } return bytes [0] & 0x80 ? - x : x; } #define macro_cacputb(nbits) \ void cacputb##nbits (unsigned int value, CACHE *f) { \ if (bitsInWriteBuffer + nbits > 8) { * f -> ptr ++ = writeBuffer; bitsInWriteBuffer = 0; writeBuffer = 0; } \ writeBuffer |= (value << (8 - nbits)) >> bitsInWriteBuffer; \ bitsInWriteBuffer += nbits; \ } macro_cacputb (1) macro_cacputb (2) macro_cacputb (3) macro_cacputb (4) macro_cacputb (5) macro_cacputb (6) macro_cacputb (7) void cacputb (CACHE *f) { if (bitsInWriteBuffer == 0) return; cacputu1 (writeBuffer, f); /* Flush. */ bitsInWriteBuffer = 0; writeBuffer = 0; } void cacputi2 (int i, CACHE *f) { if (binario_shortBE2) { short s = i; START (s) WRITE WRITE } else { char bytes [2]; bytes [0] = i >> 8; bytes [1] = i; { START (bytes) WRITE WRITE } } } void cacputu2 (unsigned int u, CACHE *f) { if (binario_shortBE2) { unsigned short s = u; START (s) WRITE WRITE } else { char bytes [2]; bytes [0] = u >> 8; bytes [1] = u; { START (bytes) WRITE WRITE } } } void cacpute2 (int value, CACHE *f) { if (binario_shortBE2) { signed short s = value; START (s) WRITE WRITE } else { char bytes [2]; bytes [0] = value >> 8; bytes [1] = value; { START (bytes) WRITE WRITE } } } void cacputi4 (long i, CACHE *f) { if (binario_longBE4) { START (i) WRITE WRITE WRITE WRITE } else { char bytes [4]; bytes [0] = i >> 24; bytes [1] = i >> 16; bytes [2] = i >> 8; bytes [3] = i; { START (bytes) WRITE WRITE WRITE WRITE } } } void cacputu4 (unsigned long u, CACHE *f) { if (binario_longBE4) { START (u) WRITE WRITE WRITE WRITE } else { char bytes [4]; bytes [0] = u >> 24; bytes [1] = u >> 16; bytes [2] = u >> 8; bytes [3] = u; { START (bytes) WRITE WRITE WRITE WRITE } } } void cacputi2LE (int i, CACHE *f) { char bytes [2]; bytes [1] = i >> 8; bytes [0] = i; { START (bytes) WRITE WRITE } } void cacputu2LE (unsigned int u, CACHE *f) { char bytes [2]; bytes [1] = u >> 8; bytes [0] = u; { START (bytes) WRITE WRITE } } void cacputi4LE (long i, CACHE *f) { char bytes [4]; bytes [3] = i >> 24; bytes [2] = i >> 16; bytes [1] = i >> 8; bytes [0] = i; { START (bytes) WRITE WRITE WRITE WRITE } } void cacputu4LE (unsigned long u, CACHE *f) { char bytes [4]; bytes [3] = u >> 24; bytes [2] = u >> 16; bytes [1] = u >> 8; bytes [0] = u; { START (bytes) WRITE WRITE WRITE WRITE } } void cacputr4 (double x, CACHE *f) { if (binario_floatIEEE4msb) { float x4 = x; START (x4) WRITE WRITE WRITE WRITE } else { unsigned char bytes [4]; int sign, exponent; double fMantissa, fsMantissa; unsigned long mantissa; if (x < 0.0) { sign = 0x0100; x *= -1; } else sign = 0; if (x == 0.0) { exponent = 0; mantissa = 0; } else { fMantissa = frexp (x, & exponent); if ((exponent > 128) || ! (fMantissa < 1)) /* Infinity or Not-a-Number. */ { exponent = sign | 0x00FF; mantissa = 0; } /* Infinity. */ else { /* Finite. */ exponent += 126; /* Add bias. */ if (exponent <= 0) { /* Denormalized. */ fMantissa = ldexp (fMantissa, exponent - 1); exponent = 0; } exponent |= sign; fMantissa = ldexp (fMantissa, 24); fsMantissa = floor (fMantissa); mantissa = FloatToUnsigned (fsMantissa) & 0x007FFFFF; } } bytes [0] = exponent >> 1; bytes [1] = (exponent << 7) | (mantissa >> 16); bytes [2] = mantissa >> 8; bytes [3] = mantissa; { START (bytes) WRITE WRITE WRITE WRITE } } } void cacputr8 (double x, CACHE *f) { if (binario_doubleIEEE8msb) { START (x) WRITE WRITE WRITE WRITE WRITE WRITE WRITE WRITE } else { unsigned char bytes [8]; int sign, exponent; double fMantissa, fsMantissa; unsigned long highMantissa, lowMantissa; if (x < 0.0) { sign = 0x0800; x *= -1; } else sign = 0; if (x == 0.0) { exponent = 0; highMantissa = 0; lowMantissa = 0; } else { fMantissa = frexp (x, & exponent); if ((exponent > 1024) || ! (fMantissa < 1)) /* Infinity or Not-a-Number. */ { exponent = sign | 0x07FF; highMantissa = 0; lowMantissa = 0; } /* Infinity. */ else { /* Finite. */ exponent += 1022; /* Add bias. */ if (exponent <= 0) { /* Denormalized. */ fMantissa = ldexp (fMantissa, exponent - 1); exponent = 0; } exponent |= sign; fMantissa = ldexp (fMantissa, 21); fsMantissa = floor (fMantissa); highMantissa = FloatToUnsigned (fsMantissa) & 0x000FFFFF; fMantissa = ldexp (fMantissa - fsMantissa, 32); fsMantissa = floor (fMantissa); lowMantissa = FloatToUnsigned (fsMantissa); } } bytes [0] = exponent >> 4; bytes [1] = (exponent << 4) | (highMantissa >> 16); bytes [2] = highMantissa >> 8; bytes [3] = highMantissa; bytes [4] = lowMantissa >> 24; bytes [5] = lowMantissa >> 16; bytes [6] = lowMantissa >> 8; bytes [7] = lowMantissa; { START (bytes) WRITE WRITE WRITE WRITE WRITE WRITE WRITE WRITE } } } void cacputr10 (double x, CACHE *f) { unsigned char bytes [10]; int sign, exponent; double fMantissa, fsMantissa; unsigned long highMantissa, lowMantissa; if (x < 0.0) { sign = 0x8000; x *= -1; } else sign = 0; if (x == 0.0) { exponent = 0; highMantissa = 0; lowMantissa = 0; } else { fMantissa = frexp (x, & exponent); if ((exponent > 16384) || ! (fMantissa < 1)) /* Infinity or Not-a-Number. */ { exponent = sign | 0x7FFF; highMantissa = 0; lowMantissa = 0; } /* Infinity. */ else { /* Finite */ exponent += 16382; /* Add bias. */ if (exponent < 0) { /* Denormalized. */ fMantissa = ldexp (fMantissa, exponent); exponent = 0; } exponent |= sign; fMantissa = ldexp (fMantissa, 32); fsMantissa = floor (fMantissa); highMantissa = FloatToUnsigned (fsMantissa); fMantissa = ldexp (fMantissa - fsMantissa, 32); fsMantissa = floor (fMantissa); lowMantissa = FloatToUnsigned (fsMantissa); } } bytes [0] = exponent >> 8; bytes [1] = exponent; bytes [2] = highMantissa >> 24; bytes [3] = highMantissa >> 16; bytes [4] = highMantissa >> 8; bytes [5] = highMantissa; bytes [6] = lowMantissa >> 24; bytes [7] = lowMantissa >> 16; bytes [8] = lowMantissa >> 8; bytes [9] = lowMantissa; { START (bytes) WRITE WRITE WRITE WRITE WRITE WRITE WRITE WRITE WRITE WRITE } } fcomplex cacgetc8 (CACHE *f) { fcomplex result; result. re = cacgetr4 (f); result. im = cacgetr4 (f); return result; } dcomplex cacgetc16 (CACHE *f) { dcomplex result; result. re = cacgetr8 (f); result. im = cacgetr8 (f); return result; } void cacputc8 (fcomplex z, CACHE *f) { cacputr4 (z. re, f); cacputr4 (z. im, f); } void cacputc16 (dcomplex z, CACHE *f) { cacputr8 (z. re, f); cacputr8 (z. im, f); } char * cacgets1 (CACHE *f) { try { unsigned int length = (unsigned char) * f -> ptr ++; autostring8 result = Melder_malloc (char, length + 1); memread (result.peek(), 1, length, f); result [length] = 0; // trailing null byte return result.transfer(); } catch (MelderError) { Melder_throw ("Cannot read string from cache."); } } char * cacgets2 (CACHE *f) { try { unsigned int length = cacgetu2 (f); autostring8 result = Melder_malloc (char, length + 1); memread (result.peek(), 1, length, f); result [length] = 0; // trailing null byte return result.transfer(); } catch (MelderError) { Melder_throw ("Cannot read string from cache."); } } char * cacgets4 (CACHE *f) { try { unsigned long length = cacgetu4 (f); autostring8 result = Melder_malloc (char, length + 1); memread (result.peek(), 1, length, f); result [length] = 0; // trailing null byte return result.transfer(); } catch (MelderError) { Melder_throw ("Cannot read string from cache."); } } void cacputs1 (const char *s, CACHE *f) { unsigned int length = s ? strlen (s) : 0; if (length > 255) length = 255; * f -> ptr ++ = length; if (s) memwrite (s, 1, length, f); } void cacputs2 (const char *s, CACHE *f) { unsigned int length = s ? strlen (s) : 0; if (length > 65535) length = 65535; cacputu2 (length, f); if (s) memwrite (s, 1, length, f); } void cacputs4 (const char *s, CACHE *f) { unsigned long length = s ? strlen (s) : 0; cacputu4 (length, f); if (s) memwrite (s, 1, length, f); } /* End of file abcio.cpp */ sources_5316/sys/praat_logo.cpp0000644000176700017670000001171311623770347015411 0ustar paulpaul/* praat_logo.c * * Copyright (C) 1996-2010 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2006/12/28 theCurrentPraat * pb 2007/06/10 wchar_t * pb 2007/12/09 enums * sdk 2008/03/24 GTK * pb 2009/06/02 date updated * pb 2010/01/10 date and authorship updated * pb 2010/07/29 removed GuiDialog_show */ #include "praatP.h" #include "Picture.h" #include "praat_version.h" static void logo_defaultDraw (Graphics g) { Graphics_setColour (g, Graphics_MAGENTA); Graphics_fillRectangle (g, 0, 1, 0, 1); Graphics_setGrey (g, 0.5); Graphics_fillRectangle (g, 0.05, 0.95, 0.1, 0.9); Graphics_setTextAlignment (g, Graphics_CENTRE, Graphics_HALF); Graphics_setColour (g, Graphics_YELLOW); Graphics_setFont (g, kGraphics_font_TIMES); Graphics_setFontSize (g, 24); Graphics_setFontStyle (g, Graphics_ITALIC); Graphics_setUnderscoreIsSubscript (g, FALSE); /* Because program names may contain underscores. */ Graphics_text (g, 0.5, 0.6, Melder_peekUtf8ToWcs (praatP.title)); Graphics_setFontStyle (g, 0); Graphics_setFontSize (g, 12); Graphics_text (g, 0.5, 0.25, L"\\s{Built on the} %%Praat shell%\\s{,\\co Paul Boersma, 1992-2011"); } static struct { double width_mm, height_mm; void (*draw) (Graphics g); GuiObject dia, form, drawingArea; Graphics graphics; } theLogo = { 90, 40, logo_defaultDraw }; #if motif static void logo_timeOut (XtPointer closure, XtIntervalId *id) { (void) closure; (void) id; GuiObject_hide (theLogo.form); } #endif void praat_setLogo (double width_mm, double height_mm, void (*draw) (Graphics g)) { theLogo.width_mm = width_mm; theLogo.height_mm = height_mm; theLogo.draw = draw; } static void gui_drawingarea_cb_expose (I, GuiDrawingAreaExposeEvent event) { if (theLogo.graphics == NULL) theLogo.graphics = Graphics_create_xmdrawingarea (theLogo.drawingArea); #if gtk Graphics_x_setCR (theLogo.graphics, gdk_cairo_create (GDK_DRAWABLE (GTK_WIDGET (event -> widget) -> window))); cairo_rectangle ((cairo_t *) Graphics_x_getCR (theLogo.graphics), (double) event->x, (double) event->y, (double) event->width, (double) event->height); cairo_clip ((cairo_t *) Graphics_x_getCR (theLogo.graphics)); theLogo.draw (theLogo.graphics); cairo_destroy ((cairo_t *) Graphics_x_getCR (theLogo.graphics)); #elif motif (void) void_me; (void) event; if (theLogo.graphics == NULL) theLogo.graphics = Graphics_create_xmdrawingarea (theLogo.drawingArea); theLogo.draw (theLogo.graphics); #endif } static void gui_drawingarea_cb_click (I, GuiDrawingAreaClickEvent event) { (void) void_me; (void) event; GuiObject_hide (theLogo.form); } static void gui_cb_goAway (I) { (void) void_me; GuiObject_hide (theLogo.form); } void praat_showLogo (int autoPopDown) { #if gtk static const gchar *authors [3] = { "Paul Boersma", "David Weenink", NULL }; GuiObject dialog = gtk_about_dialog_new (); #define xstr(s) str(s) #define str(s) #s gtk_about_dialog_set_version (GTK_ABOUT_DIALOG (dialog), xstr (PRAAT_VERSION_STR)); gtk_about_dialog_set_copyright (GTK_ABOUT_DIALOG (dialog), "Copyright (C) 1992-" xstr(PRAAT_YEAR) " by Paul Boersma and David Weenink"); gtk_about_dialog_set_license (GTK_ABOUT_DIALOG (dialog), "GPL"); gtk_about_dialog_set_website (GTK_ABOUT_DIALOG (dialog), "http://www.praat.org"); //gtk_about_dialog_set_authors (GTK_ABOUT_DIALOG (dialog), authors); g_signal_connect (GTK_DIALOG (dialog), "response", G_CALLBACK (gtk_widget_destroy), NULL); gtk_dialog_run (GTK_DIALOG (dialog)); #else if (theCurrentPraatApplication -> batch || ! theLogo.draw) return; if (! theLogo.dia) { theLogo.dia = GuiDialog_create (theCurrentPraatApplication -> topShell, 100, 100, Gui_AUTOMATIC, Gui_AUTOMATIC, L"About", gui_cb_goAway, NULL, 0); #if gtk theLogo.form = GTK_DIALOG (theLogo.dia) -> vbox; #else theLogo.form = theLogo.dia; #endif theLogo.drawingArea = GuiDrawingArea_createShown (theLogo.form, 0, (int) (theLogo.width_mm / 25.4 * Gui_getResolution (theLogo.drawingArea)), 0, (int) (theLogo.height_mm / 25.4 * Gui_getResolution (theLogo.drawingArea)), gui_drawingarea_cb_expose, gui_drawingarea_cb_click, NULL, NULL, NULL, 0); } GuiObject_show (theLogo.form); GuiObject_show (theLogo.dia); #if motif if (autoPopDown) GuiAddTimeOut (2000, logo_timeOut, (XtPointer) NULL); #endif #endif } /* End of file praat_logo.c */ sources_5316/sys/winport_on.h0000644000176700017670000000155711632655437015134 0ustar paulpaul/* winport_on.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define Graphics WindowsGraphics #define Data WindowsData #define Polygon WindowsPolygon /* End of file winport_on.h */ sources_5316/sys/melder_strings.cpp0000644000176700017670000003717611633675037016317 0ustar paulpaul/* melder_strings.cpp * * Copyright (C) 2006-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "melder.h" #include "UnicodeData.h" #define my me -> #define FREE_THRESHOLD_BYTES 10000 static double totalNumberOfAllocations = 0, totalNumberOfDeallocations = 0, totalAllocationSize = 0, totalDeallocationSize = 0; void MelderString_free (MelderString *me) { if (my string == NULL) return; Melder_free (my string); if (Melder_debug == 34) fprintf (stderr, "from MelderString_free\t%p\t%ld\t%ld\n", my string, my bufferSize, sizeof (wchar)); totalNumberOfDeallocations += 1; totalDeallocationSize += my bufferSize * sizeof (wchar); my bufferSize = 0; my length = 0; } void MelderString16_free (MelderString16 *me) { if (my string == NULL) return; Melder_free (my string); if (Melder_debug == 34) fprintf (stderr, "from MelderString16_free\t%p\t%ld\t%ld\n", my string, my bufferSize, 2L); totalNumberOfDeallocations += 1; totalDeallocationSize += my bufferSize * sizeof (MelderUtf16); my bufferSize = 0; my length = 0; } #define expandIfNecessary(type) \ if (sizeNeeded > my bufferSize) { \ Melder_assert (my bufferSize >= 0); \ Melder_assert (sizeNeeded >= 0); \ sizeNeeded = 1.618034 * sizeNeeded + 100; \ Melder_assert (sizeNeeded > 0); \ if (my string) { \ totalNumberOfDeallocations += 1; \ totalDeallocationSize += my bufferSize * sizeof (type); \ } \ long bytesNeeded = sizeNeeded * sizeof (type); \ Melder_assert (bytesNeeded > 0); \ try { \ if (Melder_debug == 34) fprintf (stderr, "from MelderString:expandIfNecessary\t%p\t%ld\t%ld\n", my string, sizeNeeded, sizeof (type)); \ my string = (type *) Melder_realloc (my string, bytesNeeded); \ } catch (MelderError) { \ my bufferSize = 0; \ my length = 0; \ throw; \ } \ totalNumberOfAllocations += 1; \ totalAllocationSize += bytesNeeded; \ my bufferSize = sizeNeeded; \ } void MelderString_empty (MelderString *me) { if (my bufferSize * sizeof (wchar) >= FREE_THRESHOLD_BYTES) { MelderString_free (me); } unsigned long sizeNeeded = 1; expandIfNecessary (wchar) my string [0] = '\0'; my length = 0; } void MelderString16_empty (MelderString16 *me) { if (my bufferSize * sizeof (wchar) >= FREE_THRESHOLD_BYTES) { MelderString16_free (me); } unsigned long sizeNeeded = 1; expandIfNecessary (MelderUtf16) my string [0] = '\0'; my length = 0; } void MelderString_copy (MelderString *me, const wchar *source) { if (my bufferSize * sizeof (wchar) >= FREE_THRESHOLD_BYTES) MelderString_free (me); if (source == NULL) source = L""; unsigned long length = wcslen (source); unsigned long sizeNeeded = length + 1; expandIfNecessary (wchar) wcscpy (my string, source); my length = length; } void MelderString_ncopy (MelderString *me, const wchar *source, unsigned long n) { if (my bufferSize * sizeof (wchar) >= FREE_THRESHOLD_BYTES) MelderString_free (me); if (source == NULL) source = L""; unsigned long length = wcslen (source); if (length > n) length = n; unsigned long sizeNeeded = length + 1; expandIfNecessary (wchar) wcsncpy (my string, source, length); my string [length] = '\0'; my length = length; } void MelderString_append (MelderString *me, const wchar *s1) { if (s1 == NULL) s1 = L""; unsigned long length1 = wcslen (s1); unsigned long sizeNeeded = my length + length1 + 1; expandIfNecessary (wchar) wcscpy (my string + my length, s1); my length += length1; } void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2) { if (s1 == NULL) s1 = L""; if (s2 == NULL) s2 = L""; unsigned long length1 = wcslen (s1); unsigned long length2 = wcslen (s2); unsigned long sizeNeeded = my length + length1 + length2 + 1; expandIfNecessary (wchar) wcscpy (my string + my length, s1); my length += length1; wcscpy (my string + my length, s2); my length += length2; } void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3) { if (s1 == NULL) s1 = L""; if (s2 == NULL) s2 = L""; if (s3 == NULL) s3 = L""; unsigned long length1 = wcslen (s1); unsigned long length2 = wcslen (s2); unsigned long length3 = wcslen (s3); unsigned long sizeNeeded = my length + length1 + length2 + length3 + 1; expandIfNecessary (wchar) wcscpy (my string + my length, s1); my length += length1; wcscpy (my string + my length, s2); my length += length2; wcscpy (my string + my length, s3); my length += length3; } void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4) { if (s1 == NULL) s1 = L""; if (s2 == NULL) s2 = L""; if (s3 == NULL) s3 = L""; if (s4 == NULL) s4 = L""; unsigned long length1 = wcslen (s1); unsigned long length2 = wcslen (s2); unsigned long length3 = wcslen (s3); unsigned long length4 = wcslen (s4); unsigned long sizeNeeded = my length + length1 + length2 + length3 + length4 + 1; expandIfNecessary (wchar) wcscpy (my string + my length, s1); my length += length1; wcscpy (my string + my length, s2); my length += length2; wcscpy (my string + my length, s3); my length += length3; wcscpy (my string + my length, s4); my length += length4; } void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5) { if (s1 == NULL) s1 = L""; if (s2 == NULL) s2 = L""; if (s3 == NULL) s3 = L""; if (s4 == NULL) s4 = L""; if (s5 == NULL) s5 = L""; unsigned long length1 = wcslen (s1); unsigned long length2 = wcslen (s2); unsigned long length3 = wcslen (s3); unsigned long length4 = wcslen (s4); unsigned long length5 = wcslen (s5); unsigned long sizeNeeded = my length + length1 + length2 + length3 + length4 + length5 + 1; expandIfNecessary (wchar) wcscpy (my string + my length, s1); my length += length1; wcscpy (my string + my length, s2); my length += length2; wcscpy (my string + my length, s3); my length += length3; wcscpy (my string + my length, s4); my length += length4; wcscpy (my string + my length, s5); my length += length5; } void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6) { if (s1 == NULL) s1 = L""; if (s2 == NULL) s2 = L""; if (s3 == NULL) s3 = L""; if (s4 == NULL) s4 = L""; if (s5 == NULL) s5 = L""; if (s6 == NULL) s6 = L""; unsigned long length1 = wcslen (s1); unsigned long length2 = wcslen (s2); unsigned long length3 = wcslen (s3); unsigned long length4 = wcslen (s4); unsigned long length5 = wcslen (s5); unsigned long length6 = wcslen (s6); unsigned long sizeNeeded = my length + length1 + length2 + length3 + length4 + length5 + length6 + 1; expandIfNecessary (wchar) wcscpy (my string + my length, s1); my length += length1; wcscpy (my string + my length, s2); my length += length2; wcscpy (my string + my length, s3); my length += length3; wcscpy (my string + my length, s4); my length += length4; wcscpy (my string + my length, s5); my length += length5; wcscpy (my string + my length, s6); my length += length6; } void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7) { if (s1 == NULL) s1 = L""; if (s2 == NULL) s2 = L""; if (s3 == NULL) s3 = L""; if (s4 == NULL) s4 = L""; if (s5 == NULL) s5 = L""; if (s6 == NULL) s6 = L""; if (s7 == NULL) s7 = L""; unsigned long length1 = wcslen (s1); unsigned long length2 = wcslen (s2); unsigned long length3 = wcslen (s3); unsigned long length4 = wcslen (s4); unsigned long length5 = wcslen (s5); unsigned long length6 = wcslen (s6); unsigned long length7 = wcslen (s7); unsigned long sizeNeeded = my length + length1 + length2 + length3 + length4 + length5 + length6 + length7 + 1; expandIfNecessary (wchar) wcscpy (my string + my length, s1); my length += length1; wcscpy (my string + my length, s2); my length += length2; wcscpy (my string + my length, s3); my length += length3; wcscpy (my string + my length, s4); my length += length4; wcscpy (my string + my length, s5); my length += length5; wcscpy (my string + my length, s6); my length += length6; wcscpy (my string + my length, s7); my length += length7; } void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8) { if (s1 == NULL) s1 = L""; if (s2 == NULL) s2 = L""; if (s3 == NULL) s3 = L""; if (s4 == NULL) s4 = L""; if (s5 == NULL) s5 = L""; if (s6 == NULL) s6 = L""; if (s7 == NULL) s7 = L""; if (s8 == NULL) s8 = L""; unsigned long length1 = wcslen (s1); unsigned long length2 = wcslen (s2); unsigned long length3 = wcslen (s3); unsigned long length4 = wcslen (s4); unsigned long length5 = wcslen (s5); unsigned long length6 = wcslen (s6); unsigned long length7 = wcslen (s7); unsigned long length8 = wcslen (s8); unsigned long sizeNeeded = my length + length1 + length2 + length3 + length4 + length5 + length6 + length7 + length8 + 1; expandIfNecessary (wchar) wcscpy (my string + my length, s1); my length += length1; wcscpy (my string + my length, s2); my length += length2; wcscpy (my string + my length, s3); my length += length3; wcscpy (my string + my length, s4); my length += length4; wcscpy (my string + my length, s5); my length += length5; wcscpy (my string + my length, s6); my length += length6; wcscpy (my string + my length, s7); my length += length7; wcscpy (my string + my length, s8); my length += length8; } void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9) { if (s1 == NULL) s1 = L""; if (s2 == NULL) s2 = L""; if (s3 == NULL) s3 = L""; if (s4 == NULL) s4 = L""; if (s5 == NULL) s5 = L""; if (s6 == NULL) s6 = L""; if (s7 == NULL) s7 = L""; if (s8 == NULL) s8 = L""; if (s9 == NULL) s9 = L""; unsigned long length1 = wcslen (s1); unsigned long length2 = wcslen (s2); unsigned long length3 = wcslen (s3); unsigned long length4 = wcslen (s4); unsigned long length5 = wcslen (s5); unsigned long length6 = wcslen (s6); unsigned long length7 = wcslen (s7); unsigned long length8 = wcslen (s8); unsigned long length9 = wcslen (s9); unsigned long sizeNeeded = my length + length1 + length2 + length3 + length4 + length5 + length6 + length7 + length8 + length9 + 1; expandIfNecessary (wchar) wcscpy (my string + my length, s1); my length += length1; wcscpy (my string + my length, s2); my length += length2; wcscpy (my string + my length, s3); my length += length3; wcscpy (my string + my length, s4); my length += length4; wcscpy (my string + my length, s5); my length += length5; wcscpy (my string + my length, s6); my length += length6; wcscpy (my string + my length, s7); my length += length7; wcscpy (my string + my length, s8); my length += length8; wcscpy (my string + my length, s9); my length += length9; } void MelderString_appendCharacter (MelderString *me, wchar character) { unsigned long sizeNeeded = my length + 2; // make room for character and null byte expandIfNecessary (wchar) my string [my length] = character; my length ++; my string [my length] = L'\0'; } void MelderString16_appendCharacter (MelderString16 *me, wchar character) { unsigned long sizeNeeded = my length + 3; // make room for character, potential surrogate character, and null byte expandIfNecessary (MelderUtf16) if (sizeof (wchar) == 2) { // wchar is UTF-16? my string [my length] = character; my length ++; } else { // wchar is UTF-32. MelderUtf32 kar = character; if (kar <= 0xFFFF) { my string [my length] = character; my length ++; } else if (kar <= 0x10FFFF) { kar -= 0x10000; my string [my length] = 0xD800 | (kar >> 10); my length ++; my string [my length] = 0xDC00 | (kar & 0x3FF); my length ++; } else { my string [my length] = UNICODE_REPLACEMENT_CHARACTER; my length ++; } } my string [my length] = '\0'; } void MelderString_get (MelderString *me, wchar *destination) { if (my string) { wcscpy (destination, my string); } else { destination [0] = L'\0'; } } double MelderString_allocationCount (void) { return totalNumberOfAllocations; } double MelderString_deallocationCount (void) { return totalNumberOfDeallocations; } double MelderString_allocationSize (void) { return totalAllocationSize; } double MelderString_deallocationSize (void) { return totalDeallocationSize; } #define NUMBER_OF_BUFFERS 33 static MelderString buffer [NUMBER_OF_BUFFERS] = { { 0 } }; static int ibuffer = 0; const wchar * Melder_wcscat (const wchar *s1, const wchar *s2) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; MelderString_empty (& buffer [ibuffer]); MelderString_append (& buffer [ibuffer], s1, s2); return buffer [ibuffer].string; } const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; MelderString_empty (& buffer [ibuffer]); MelderString_append (& buffer [ibuffer], s1, s2, s3); return buffer [ibuffer].string; } const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; MelderString_empty (& buffer [ibuffer]); MelderString_append (& buffer [ibuffer], s1, s2, s3, s4); return buffer [ibuffer].string; } const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; MelderString_empty (& buffer [ibuffer]); MelderString_append (& buffer [ibuffer], s1, s2, s3, s4, s5); return buffer [ibuffer].string; } const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; MelderString_empty (& buffer [ibuffer]); MelderString_append (& buffer [ibuffer], s1, s2, s3, s4, s5, s6); return buffer [ibuffer].string; } const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; MelderString_empty (& buffer [ibuffer]); MelderString_append (& buffer [ibuffer], s1, s2, s3, s4, s5, s6, s7); return buffer [ibuffer].string; } const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; MelderString_empty (& buffer [ibuffer]); MelderString_append (& buffer [ibuffer], s1, s2, s3, s4, s5, s6, s7, s8); return buffer [ibuffer].string; } const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; MelderString_empty (& buffer [ibuffer]); MelderString_append (& buffer [ibuffer], s1, s2, s3, s4, s5, s6, s7, s8, s9); return buffer [ibuffer].string; } /* End of file melder_strings.cpp */ sources_5316/sys/machine.cpp0000644000176700017670000000666411613302421014656 0ustar paulpaul/* machine.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2004/06/17 Machine_getMainWindowMenuBarHeight () * pb 2011/05/15 C++ */ #include "machine.h" #include "melder.h" #define LookAndFeel_MOTIF 0 #define LookAndFeel_SGI 1 #define LookAndFeel_CDE 2 #define LookAndFeel_SOLARIS 3 #define LookAndFeel_HP 4 #define LookAndFeel_SUN4 5 #define LookAndFeel_MAC 6 #define LookAndFeel_WIN32 7 #define LookAndFeel_LINUX 8 static int lookAndFeel; int Machine_getMenuBarHeight (void) { static int heights [] = { 26, /* Motif */ 24, /* SGI */ 28, /* CDE */ 26, /* Solaris */ 26, /* HP */ 26, /* Sun4 */ 36, /* Mac */ 0, /* Win32 */ 30 /* Linux */ }; return heights [lookAndFeel]; } int Machine_getMainWindowMenuBarHeight (void) { #ifdef macintoshXXX return 0; #else return Machine_getMenuBarHeight (); #endif } int Machine_getTitleBarHeight (void) { static int heights [] = { /* Mostly copied from menu-bar height. */ 26, /* Motif */ 24, /* SGI */ 28, /* CDE */ 26, /* Solaris */ 26, /* HP */ 26, /* Sun4 */ 22, /* Mac */ 20, /* Win32 */ 30 /* Linux */ }; return heights [lookAndFeel]; } int Machine_getScrollBarWidth (void) { static int widths [] = { 22, /* Motif */ 22, /* SGI */ 22, /* CDE */ 22, /* Solaris */ 22, /* HP */ 22, /* Sun4 */ 16, /* Mac */ 17, /* Win32 */ 18 /* Linux */ }; return widths [lookAndFeel]; } int Machine_getTextHeight (void) { static int heights [] = { 29, /* Motif */ 29, /* SGI */ 25, /* CDE */ 29, /* Solaris */ 29, /* HP */ 29, /* Sun4 */ 22, /* Mac */ 20, /* Win32 */ 29 /* Linux */ }; return heights [lookAndFeel]; } void Machine_initLookAndFeel (unsigned int argc, char **argv) { /* * Determining the appropriate look-and-feel: the default depends on the client machine. */ #if defined (macintosh) lookAndFeel = LookAndFeel_MAC; return; #elif defined (_WIN32) lookAndFeel = LookAndFeel_WIN32; return; #elif defined (linux) lookAndFeel = LookAndFeel_LINUX; #endif /* * Command line may override the look-and-feel. */ if (argc > 1) { if (strequ (argv [1], "-sgi")) lookAndFeel = LookAndFeel_SGI; else if (strequ (argv [1], "-motif")) lookAndFeel = LookAndFeel_MOTIF; else if (strequ (argv [1], "-cde")) lookAndFeel = LookAndFeel_CDE; else if (strequ (argv [1], "-solaris")) lookAndFeel = LookAndFeel_SOLARIS; else if (strequ (argv [1], "-hp")) lookAndFeel = LookAndFeel_HP; else if (strequ (argv [1], "-sun4")) lookAndFeel = LookAndFeel_SUN4; else if (strequ (argv [1], "-mac")) lookAndFeel = LookAndFeel_MAC; else if (strequ (argv [1], "-linux")) lookAndFeel = LookAndFeel_LINUX; } } /* End of file machine.cpp */ sources_5316/sys/StringsEditor.h0000644000176700017670000000237411621124714015517 0ustar paulpaul#ifndef _StringsEditor_h_ #define _StringsEditor_h_ /* StringsEditor.h * * Copyright (C) 1993-2011 David Weenink & Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Editor.h" #include "Strings.h" Thing_define (StringsEditor, Editor) { // new data: public: GuiObject list, text; // overridden methods: virtual void v_destroy (); virtual void v_createChildren (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_dataChanged (); }; StringsEditor StringsEditor_create (GuiObject parent, const wchar *title, Strings data); /* End of file StringsEditor.h */ #endif sources_5316/sys/winport_off.h0000644000176700017670000000150311632655470015256 0ustar paulpaul/* winport_off.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #undef Graphics #undef Data #undef Polygon /* End of file winport_off.h */ sources_5316/sys/praat_picture.cpp0000644000176700017670000023562711752476204016136 0ustar paulpaul/* praat_picture.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "praatP.h" #include "Picture.h" #include "Printer.h" #include "machine.h" #include "Formula.h" static bool praat_mouseSelectsInnerViewport; void praat_picture_prefs (void) { Preferences_addEnum (L"Picture.font", & theCurrentPraatPicture -> font, kGraphics_font, DEFAULT); Preferences_addInt (L"Picture.fontSize", & theCurrentPraatPicture -> fontSize, 10); Preferences_addBool (L"Picture.mouseSelectsInnerViewport", & praat_mouseSelectsInnerViewport, false); } /***** static variable *****/ static Picture praat_picture; /********** CALLBACKS OF THE PICTURE MENUS **********/ /***** "Font" MENU: font part *****/ #if 0 static GuiObject praatButton_times, praatButton_helvetica, praatButton_palatino, praatButton_courier; #endif static GuiObject praatButton_fonts [1 + kGraphics_font_MAX]; static void updateFontMenu (void) { if (! theCurrentPraatApplication -> batch) { if (theCurrentPraatPicture -> font < kGraphics_font_MIN) theCurrentPraatPicture -> font = kGraphics_font_MIN; if (theCurrentPraatPicture -> font > kGraphics_font_MAX) theCurrentPraatPicture -> font = kGraphics_font_MAX; // we no longer have New Century Schoolbook for (int i = kGraphics_font_MIN; i <= kGraphics_font_MAX; i ++) { GuiMenuItem_check (praatButton_fonts [i], theCurrentPraatPicture -> font == i); } } } static void setFont (kGraphics_font font) { { autoPraatPicture picture; Graphics_setFont (GRAPHICS, font); } theCurrentPraatPicture -> font = font; if (theCurrentPraatPicture == & theForegroundPraatPicture) { updateFontMenu (); } } DIRECT (Times) setFont (kGraphics_font_TIMES); END DIRECT (Helvetica) setFont (kGraphics_font_HELVETICA); END DIRECT (Palatino) setFont (kGraphics_font_PALATINO); END DIRECT (Courier) setFont (kGraphics_font_COURIER); END /***** "Font" MENU: size part *****/ static GuiObject praatButton_10, praatButton_12, praatButton_14, praatButton_18, praatButton_24; static void updateSizeMenu (void) { if (! theCurrentPraatApplication -> batch) { GuiMenuItem_check (praatButton_10, theCurrentPraatPicture -> fontSize == 10); GuiMenuItem_check (praatButton_12, theCurrentPraatPicture -> fontSize == 12); GuiMenuItem_check (praatButton_14, theCurrentPraatPicture -> fontSize == 14); GuiMenuItem_check (praatButton_18, theCurrentPraatPicture -> fontSize == 18); GuiMenuItem_check (praatButton_24, theCurrentPraatPicture -> fontSize == 24); } } static void setFontSize (int fontSize) { //Melder_casual("Praat picture: set font size %d", fontSize); { autoPraatPicture picture; Graphics_setFontSize (GRAPHICS, fontSize); } theCurrentPraatPicture -> fontSize = fontSize; if (theCurrentPraatPicture == & theForegroundPraatPicture) { updateSizeMenu (); } } DIRECT (10) setFontSize (10); END DIRECT (12) setFontSize (12); END DIRECT (14) setFontSize (14); END DIRECT (18) setFontSize (18); END DIRECT (24) setFontSize (24); END FORM (Font_size, L"Praat picture: Font size", L"Font menu") NATURAL (L"Font size (points)", L"10") OK SET_INTEGER (L"Font size", (long) theCurrentPraatPicture -> fontSize); DO setFontSize (GET_INTEGER (L"Font size")); END /*static void setFontSize_keepInnerViewport (int fontSize) { double xmargin = praat_size * 4.2 / 72.0, ymargin = praat_size * 2.8 / 72.0; if (xmargin > 0.4 * (x2NDC - x1NDC)) xmargin = 0.4 * (x2NDC - x1NDC); if (ymargin > 0.4 * (y2NDC - y1NDC)) ymargin = 0.4 * (y2NDC - y1NDC); x1NDC += xmargin; x2NDC -= xmargin; y1NDC += ymargin; y2NDC -= ymargin; xmargin = fontSize * 4.2 / 72.0, ymargin = fontSize * 2.8 / 72.0; if (xmargin > 2 * (x2NDC - x1NDC)) xmargin = 2 * (x2NDC - x1NDC); if (ymargin > 2 * (y2NDC - y1NDC)) ymargin = 2 * (y2NDC - y1NDC); x1NDC -= xmargin; x2NDC += xmargin; y1NDC -= ymargin; y2NDC += ymargin; { autoPraatPicture picture; Graphics_setFontSize (GRAPHICS, praat_size = fontSize); } Picture_setSelection (praat_picture, x1NDC, x2NDC, y1NDC, y2NDC, False); updateSizeMenu (); }*/ /***** "Select" MENU *****/ static GuiObject praatButton_innerViewport, praatButton_outerViewport; static void updateViewportMenu (void) { if (! theCurrentPraatApplication -> batch) { GuiMenuItem_check (praatButton_innerViewport, praat_mouseSelectsInnerViewport ? 1 : 0); GuiMenuItem_check (praatButton_outerViewport, praat_mouseSelectsInnerViewport ? 0 : 1); } } DIRECT (MouseSelectsInnerViewport) if (theCurrentPraatPicture != & theForegroundPraatPicture) Melder_throw ("Mouse commands are not available inside pictures."); { // scope autoPraatPicture picture; Picture_setMouseSelectsInnerViewport (praat_picture, praat_mouseSelectsInnerViewport = true); } updateViewportMenu (); END DIRECT (MouseSelectsOuterViewport) if (theCurrentPraatPicture != & theForegroundPraatPicture) Melder_throw ("Mouse commands are not available inside pictures."); { // scope autoPraatPicture picture; Picture_setMouseSelectsInnerViewport (praat_picture, praat_mouseSelectsInnerViewport = false); } updateViewportMenu (); END FORM (SelectInnerViewport, L"Praat picture: Select inner viewport", L"Select inner viewport...") LABEL (L"", L"The viewport is the selected rectangle in the Picture window.") LABEL (L"", L"It is where your next drawing will appear.") LABEL (L"", L"The rectangle you select here will not include the margins.") LABEL (L"", L"") REAL (L"left Horizontal range (inches)", L"0.0") REAL (L"right Horizontal range (inches)", L"6.0") REAL (L"left Vertical range (inches)", L"0.0") REAL (L"right Vertical range (inches)", L"6.0") OK double xmargin = theCurrentPraatPicture -> fontSize * 4.2 / 72.0, ymargin = theCurrentPraatPicture -> fontSize * 2.8 / 72.0; if (ymargin > 0.4 * (theCurrentPraatPicture -> y2NDC - theCurrentPraatPicture -> y1NDC)) ymargin = 0.4 * (theCurrentPraatPicture -> y2NDC - theCurrentPraatPicture -> y1NDC); if (xmargin > 0.4 * (theCurrentPraatPicture -> x2NDC - theCurrentPraatPicture -> x1NDC)) xmargin = 0.4 * (theCurrentPraatPicture -> x2NDC - theCurrentPraatPicture -> x1NDC); SET_REAL (L"left Horizontal range", theCurrentPraatPicture -> x1NDC + xmargin); SET_REAL (L"right Horizontal range", theCurrentPraatPicture -> x2NDC - xmargin); SET_REAL (L"left Vertical range", 12 - theCurrentPraatPicture -> y2NDC + ymargin); SET_REAL (L"right Vertical range", 12 - theCurrentPraatPicture -> y1NDC - ymargin); DO //if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("Viewport commands are not available inside manuals."); double left = GET_REAL (L"left Horizontal range"), right = GET_REAL (L"right Horizontal range"); double top = GET_REAL (L"left Vertical range"), bottom = GET_REAL (L"right Vertical range"); double xmargin = theCurrentPraatPicture -> fontSize * 4.2 / 72.0, ymargin = theCurrentPraatPicture -> fontSize * 2.8 / 72.0; if (theCurrentPraatPicture != & theForegroundPraatPicture) { long x1DC, x2DC, y1DC, y2DC; Graphics_inqWsViewport (GRAPHICS, & x1DC, & x2DC, & y1DC, & y2DC); double x1wNDC, x2wNDC, y1wNDC, y2wNDC; Graphics_inqWsWindow (GRAPHICS, & x1wNDC, & x2wNDC, & y1wNDC, & y2wNDC); double wDC = (x2DC - x1DC) / (x2wNDC - x1wNDC); double hDC = abs (y2DC - y1DC) / (y2wNDC - y1wNDC); xmargin *= Graphics_getResolution (GRAPHICS) / wDC; ymargin *= Graphics_getResolution (GRAPHICS) / hDC; } if (xmargin > 2 * (right - left)) xmargin = 2 * (right - left); if (ymargin > 2 * (bottom - top)) ymargin = 2 * (bottom - top); if (left == right) { Melder_throw ("The left and right edges of the viewport cannot be equal.\nPlease change the horizontal range."); } if (left > right) { double temp; temp = left; left = right; right = temp; } if (top == bottom) { Melder_throw ("The top and bottom edges of the viewport cannot be equal.\nPlease change the vertical range."); } theCurrentPraatPicture -> x1NDC = left - xmargin; theCurrentPraatPicture -> x2NDC = right + xmargin; if (theCurrentPraatPicture == & theForegroundPraatPicture) { if (top > bottom) { double temp; temp = top; top = bottom; bottom = temp; } theCurrentPraatPicture -> y1NDC = 12-bottom - ymargin; theCurrentPraatPicture -> y2NDC = 12-top + ymargin; Picture_setSelection (praat_picture, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC, False); } else if (theCurrentPraatObjects != & theForegroundPraatObjects) { // in manual? if (top > bottom) { double temp; temp = top; top = bottom; bottom = temp; } double x1wNDC, x2wNDC, y1wNDC, y2wNDC; Graphics_inqWsWindow (GRAPHICS, & x1wNDC, & x2wNDC, & y1wNDC, & y2wNDC); double height_NDC = y2wNDC - y1wNDC; theCurrentPraatPicture -> y1NDC = height_NDC-bottom - ymargin; theCurrentPraatPicture -> y2NDC = height_NDC-top + ymargin; } else { if (top < bottom) { double temp; temp = top; top = bottom; bottom = temp; } theCurrentPraatPicture -> y1NDC = bottom - ymargin; theCurrentPraatPicture -> y2NDC = top + ymargin; } END FORM (SelectOuterViewport, L"Praat picture: Select outer viewport", L"Select outer viewport...") LABEL (L"", L"The viewport is the selected rectangle in the Picture window.") LABEL (L"", L"It is where your next drawing will appear.") LABEL (L"", L"The rectangle you select here will include the margins.") LABEL (L"", L"") REAL (L"left Horizontal range (inches)", L"0.0") REAL (L"right Horizontal range (inches)", L"6.0") REAL (L"left Vertical range (inches)", L"0.0") REAL (L"right Vertical range (inches)", L"6.0") OK SET_REAL (L"left Horizontal range", theCurrentPraatPicture -> x1NDC); SET_REAL (L"right Horizontal range", theCurrentPraatPicture -> x2NDC); SET_REAL (L"left Vertical range", 12 - theCurrentPraatPicture -> y2NDC); SET_REAL (L"right Vertical range", 12 - theCurrentPraatPicture -> y1NDC); DO //if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("Viewport commands are not available inside manuals."); double left = GET_REAL (L"left Horizontal range"), right = GET_REAL (L"right Horizontal range"); double top = GET_REAL (L"left Vertical range"), bottom = GET_REAL (L"right Vertical range"); if (left == right) { Melder_throw ("The left and right edges of the viewport cannot be equal.\nPlease change the horizontal range."); } if (left > right) { double temp; temp = left; left = right; right = temp; } if (top == bottom) { Melder_throw ("The top and bottom edges of the viewport cannot be equal.\nPlease change the vertical range."); } theCurrentPraatPicture -> x1NDC = left; theCurrentPraatPicture -> x2NDC = right; if (theCurrentPraatPicture == & theForegroundPraatPicture) { if (top > bottom) { double temp; temp = top; top = bottom; bottom = temp; } theCurrentPraatPicture -> y1NDC = 12-bottom; theCurrentPraatPicture -> y2NDC = 12-top; Picture_setSelection (praat_picture, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC, False); } else if (theCurrentPraatObjects != & theForegroundPraatObjects) { // in manual? if (top > bottom) { double temp; temp = top; top = bottom; bottom = temp; } double x1wNDC, x2wNDC, y1wNDC, y2wNDC; Graphics_inqWsWindow (GRAPHICS, & x1wNDC, & x2wNDC, & y1wNDC, & y2wNDC); double height_NDC = y2wNDC - y1wNDC; theCurrentPraatPicture -> y1NDC = height_NDC-bottom; theCurrentPraatPicture -> y2NDC = height_NDC-top; } else { if (top < bottom) { double temp; temp = top; top = bottom; bottom = temp; } theCurrentPraatPicture -> y1NDC = bottom; theCurrentPraatPicture -> y2NDC = top; } END FORM (ViewportText, L"Praat picture: Viewport text", L"Viewport text...") RADIO (L"Horizontal alignment", 2) RADIOBUTTON (L"Left") RADIOBUTTON (L"Centre") RADIOBUTTON (L"Right") RADIO (L"Vertical alignment", 2) RADIOBUTTON (L"Bottom") RADIOBUTTON (L"Half") RADIOBUTTON (L"Top") REAL (L"Rotation (degrees)", L"0") TEXTFIELD (L"text", L"") OK DO double x1WC, x2WC, y1WC, y2WC; int hor = GET_INTEGER (L"Horizontal alignment") - 1; int vert = GET_INTEGER (L"Vertical alignment") - 1; autoPraatPicture picture; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); Graphics_setWindow (GRAPHICS, 0, 1, 0, 1); Graphics_setTextAlignment (GRAPHICS, hor, vert); Graphics_setTextRotation (GRAPHICS, GET_REAL (L"Rotation")); Graphics_text (GRAPHICS, hor == 0 ? 0 : hor == 1 ? 0.5 : 1, vert == 0 ? 0 : vert == 1 ? 0.5 : 1, GET_STRING (L"text")); Graphics_setTextRotation (GRAPHICS, 0.0); Graphics_setWindow (GRAPHICS, x1WC, x2WC, y1WC, y2WC); END /***** "Pen" MENU *****/ static GuiObject praatButton_lines [3]; static GuiObject praatButton_black, praatButton_white, praatButton_red, praatButton_green, praatButton_blue, praatButton_yellow, praatButton_cyan, praatButton_magenta, praatButton_maroon, praatButton_lime, praatButton_navy, praatButton_teal, praatButton_purple, praatButton_olive, praatButton_pink, praatButton_silver, praatButton_grey; static void updatePenMenu (void) { if (! theCurrentPraatApplication -> batch) { for (int i = Graphics_DRAWN; i <= Graphics_DASHED; i ++) { GuiMenuItem_check (praatButton_lines [i], theCurrentPraatPicture -> lineType == i); } GuiMenuItem_check (praatButton_black, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_BLACK)); GuiMenuItem_check (praatButton_white, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_WHITE)); GuiMenuItem_check (praatButton_red, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_RED)); GuiMenuItem_check (praatButton_green, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_GREEN)); GuiMenuItem_check (praatButton_blue, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_BLUE)); GuiMenuItem_check (praatButton_yellow, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_YELLOW)); GuiMenuItem_check (praatButton_cyan, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_CYAN)); GuiMenuItem_check (praatButton_magenta, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_MAGENTA)); GuiMenuItem_check (praatButton_maroon, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_MAROON)); GuiMenuItem_check (praatButton_lime, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_LIME)); GuiMenuItem_check (praatButton_navy, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_NAVY)); GuiMenuItem_check (praatButton_teal, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_TEAL)); GuiMenuItem_check (praatButton_purple, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_PURPLE)); GuiMenuItem_check (praatButton_olive, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_OLIVE)); GuiMenuItem_check (praatButton_pink, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_PINK)); GuiMenuItem_check (praatButton_silver, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_SILVER)); GuiMenuItem_check (praatButton_grey, Graphics_Colour_equal (theCurrentPraatPicture -> colour, Graphics_GREY)); } } static void setLineType (int lineType) { { autoPraatPicture picture; Graphics_setLineType (GRAPHICS, lineType); } theCurrentPraatPicture -> lineType = lineType; if (theCurrentPraatPicture == & theForegroundPraatPicture) { updatePenMenu (); } } DIRECT (Solid_line) setLineType (Graphics_DRAWN); END DIRECT (Dotted_line) setLineType (Graphics_DOTTED); END DIRECT (Dashed_line) setLineType (Graphics_DASHED); END DIRECT (Dashed_dotted_line) setLineType (Graphics_DASHED_DOTTED); END FORM (Line_width, L"Praat picture: Line width", 0) POSITIVE (L"Line width", L"1.0") OK SET_REAL (L"Line width", theCurrentPraatPicture -> lineWidth); DO double lineWidth = GET_REAL (L"Line width"); { autoPraatPicture picture; Graphics_setLineWidth (GRAPHICS, lineWidth); } theCurrentPraatPicture -> lineWidth = lineWidth; END FORM (Arrow_size, L"Praat picture: Arrow size", 0) POSITIVE (L"Arrow size", L"1.0") OK SET_REAL (L"Arrow size", theCurrentPraatPicture -> arrowSize); DO double arrowSize = GET_REAL (L"Arrow size"); { autoPraatPicture picture; Graphics_setArrowSize (GRAPHICS, arrowSize); } theCurrentPraatPicture -> arrowSize = arrowSize; END static void setColour (Graphics_Colour colour) { { autoPraatPicture picture; Graphics_setColour (GRAPHICS, colour); } theCurrentPraatPicture -> colour = colour; if (theCurrentPraatPicture == & theForegroundPraatPicture) { updatePenMenu (); } } DIRECT (Black) setColour (Graphics_BLACK); END DIRECT (White) setColour (Graphics_WHITE); END DIRECT (Red) setColour (Graphics_RED); END DIRECT (Green) setColour (Graphics_GREEN); END DIRECT (Blue) setColour (Graphics_BLUE); END DIRECT (Yellow) setColour (Graphics_YELLOW); END DIRECT (Cyan) setColour (Graphics_CYAN); END DIRECT (Magenta) setColour (Graphics_MAGENTA); END DIRECT (Maroon) setColour (Graphics_MAROON); END DIRECT (Lime) setColour (Graphics_LIME); END DIRECT (Navy) setColour (Graphics_NAVY); END DIRECT (Teal) setColour (Graphics_TEAL); END DIRECT (Purple) setColour (Graphics_PURPLE); END DIRECT (Olive) setColour (Graphics_OLIVE); END DIRECT (Pink) setColour (Graphics_PINK); END DIRECT (Silver) setColour (Graphics_SILVER); END DIRECT (Grey) setColour (Graphics_GREY); END FORM (Colour, L"Praat picture: Colour", 0) COLOUR (L"Colour (0-1, name, or {r,g,b})", L"0.0") OK DO Graphics_Colour colour = GET_COLOUR (L"Colour"); { autoPraatPicture picture; Graphics_setColour (GRAPHICS, colour); } theCurrentPraatPicture -> colour = colour; if (theCurrentPraatPicture == & theForegroundPraatPicture) { updatePenMenu (); } END /***** "File" MENU *****/ FORM_READ (Picture_readFromPraatPictureFile, L"Read picture from praat picture file", 0, false) Picture_readFromPraatPictureFile (praat_picture, file); END static void DO_Picture_writeToEpsFile (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter, const wchar_t *invokingButtonTitle, bool modified, void *dummy) { static Any dia; (void) interpreter; (void) modified; (void) dummy; if (! dia) dia = UiOutfile_create (theCurrentPraatApplication -> topShell, L"Save as EPS file", DO_Picture_writeToEpsFile, NULL, invokingButtonTitle, NULL); if (sendingForm == NULL && sendingString == NULL) { UiOutfile_do (dia, L"praat.eps"); } else { MelderFile file; structMelderFile file2 = { 0 }; if (sendingString == NULL) file = UiFile_getFile (dia); else { Melder_relativePathToFile (sendingString, & file2); file = & file2; } Picture_writeToEpsFile (praat_picture, file, TRUE, FALSE); } } /*FORM_WRITE (Picture_writeToEpsFile, L"Save picture as Encapsulated PostScript file", 0, L"praat.eps") if (! Picture_writeToEpsFile (praat_picture, fileName, TRUE)) return 0; END*/ static void DO_Picture_writeToFontlessEpsFile_xipa (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter, const wchar_t *invokingButtonTitle, bool modified, void *dummy) { static Any dia; (void) interpreter; (void) modified; (void) dummy; if (! dia) dia = UiOutfile_create (theCurrentPraatApplication -> topShell, L"Save as fontless EPS file", DO_Picture_writeToFontlessEpsFile_xipa, NULL, invokingButtonTitle, NULL); if (sendingForm == NULL && sendingString == NULL) { UiOutfile_do (dia, L"praat.eps"); } else { MelderFile file; structMelderFile file2 = { 0 }; if (sendingString == NULL) file = UiFile_getFile (dia); else { Melder_relativePathToFile (sendingString, & file2); file = & file2; } Picture_writeToEpsFile (praat_picture, file, FALSE, FALSE); } } static void DO_Picture_writeToFontlessEpsFile_silipa (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter, const wchar_t *invokingButtonTitle, bool modified, void *dummy) { static Any dia; (void) interpreter; (void) modified; (void) dummy; if (! dia) dia = UiOutfile_create (theCurrentPraatApplication -> topShell, L"Save as fontless EPS file", DO_Picture_writeToFontlessEpsFile_silipa, NULL, invokingButtonTitle, NULL); if (sendingForm == NULL && sendingString == NULL) { UiOutfile_do (dia, L"praat.eps"); } else { MelderFile file; structMelderFile file2 = { 0 }; if (sendingString == NULL) file = UiFile_getFile (dia); else { Melder_relativePathToFile (sendingString, & file2); file = & file2; } Picture_writeToEpsFile (praat_picture, file, FALSE, TRUE); } } static void DO_Picture_writeToPdfFile (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter, const wchar_t *invokingButtonTitle, bool modified, void *dummy) { static Any dia; (void) interpreter; (void) modified; (void) dummy; if (! dia) dia = UiOutfile_create (theCurrentPraatApplication -> topShell, L"Save as PDF file", DO_Picture_writeToPdfFile, NULL, invokingButtonTitle, NULL); if (sendingForm == NULL && sendingString == NULL) { UiOutfile_do (dia, L"praat.pdf"); } else { MelderFile file; structMelderFile file2 = { 0 }; if (sendingString == NULL) file = UiFile_getFile (dia); else { Melder_relativePathToFile (sendingString, & file2); file = & file2; } Picture_writeToPdfFile (praat_picture, file); } } static void DO_Picture_writeToPraatPictureFile (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter, const wchar_t *invokingButtonTitle, bool modified, void *dummy) { static Any dia; (void) interpreter; (void) modified; (void) dummy; if (! dia) dia = UiOutfile_create (theCurrentPraatApplication -> topShell, L"Save as Praat picture file", DO_Picture_writeToPraatPictureFile, NULL, invokingButtonTitle, NULL); if (sendingForm == NULL && sendingString == NULL) { UiOutfile_do (dia, L"praat.prapic"); } else { MelderFile file; structMelderFile file2 = { 0 }; if (sendingString == NULL) file = UiFile_getFile (dia); else { Melder_relativePathToFile (sendingString, & file2); file = & file2; } Picture_writeToPraatPictureFile (praat_picture, file); } } #ifdef macintosh DIRECT (Page_setup) Printer_pageSetup (); END #endif DIRECT (PostScript_settings) Printer_postScriptSettings (); END DIRECT (Print) Picture_print (praat_picture); END #ifdef _WIN32 static void DO_Picture_writeToWindowsMetafile (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter, const wchar_t *invokingButtonTitle, bool modified, void *dummy) { static Any dia; (void) interpreter; (void) modified; (void) dummy; if (! dia) dia = UiOutfile_create (theCurrentPraatApplication -> topShell, L"Save as Windows metafile", DO_Picture_writeToWindowsMetafile, NULL, invokingButtonTitle, NULL); if (sendingForm == NULL && sendingString == NULL) { UiOutfile_do (dia, L"praat.emf"); } else { MelderFile file; structMelderFile file2 = { 0 }; if (sendingString == NULL) file = UiFile_getFile (dia); else { Melder_relativePathToFile (sendingString, & file2); file = & file2; } Picture_writeToWindowsMetafile (praat_picture, file); } } #endif #if defined (_WIN32) || defined (macintosh) DIRECT (Copy_picture_to_clipboard) Picture_copyToClipboard (praat_picture); END #endif /***** "Edit" MENU *****/ DIRECT (Undo) Graphics_undoGroup (GRAPHICS); if (theCurrentPraatPicture != & theForegroundPraatPicture) { Graphics_play (GRAPHICS, GRAPHICS); } Graphics_updateWs (GRAPHICS); END DIRECT (Erase_all) if (theCurrentPraatPicture == & theForegroundPraatPicture) { Picture_erase (praat_picture); /* This kills the recording. */ } else { Graphics_clearRecording (GRAPHICS); Graphics_clearWs (GRAPHICS); } END /***** "World" MENU *****/ FORM (Text, L"Praat picture: Text", L"Text...") REAL (L"Horizontal position", L"0.0") OPTIONMENU (L"Horizontal alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") REAL (L"Vertical position", L"0.0") OPTIONMENU (L"Vertical alignment", 2) OPTION (L"Bottom") OPTION (L"Half") OPTION (L"Top") LABEL (L"", L"Text:") TEXTFIELD (L"text", L"") OK DO autoPraatPicture picture; Graphics_setTextAlignment (GRAPHICS, GET_INTEGER (L"Horizontal alignment") - 1, GET_INTEGER (L"Vertical alignment") - 1); Graphics_setInner (GRAPHICS); Graphics_text (GRAPHICS, GET_REAL (L"Horizontal position"), GET_REAL (L"Vertical position"), GET_STRING (L"text")); Graphics_unsetInner (GRAPHICS); END FORM (Text_special, L"Praat picture: Text special", 0) REAL (L"Horizontal position", L"0.0") OPTIONMENU (L"Horizontal alignment", 2) OPTION (L"left") OPTION (L"centre") OPTION (L"right") REAL (L"Vertical position", L"0.0") OPTIONMENU (L"Vertical alignment", 2) OPTION (L"bottom") OPTION (L"half") OPTION (L"top") OPTIONMENU_ENUM (L"Font", kGraphics_font, DEFAULT) NATURAL (L"Font size", L"10") SENTENCE (L"Rotation (degrees or dx;dy)", L"0") LABEL (L"", L"Text:") TEXTFIELD (L"text", L"") OK DO kGraphics_font currentFont = Graphics_inqFont (GRAPHICS); int currentSize = Graphics_inqFontSize (GRAPHICS); autoPraatPicture picture; Graphics_setTextAlignment (GRAPHICS, GET_INTEGER (L"Horizontal alignment") - 1, GET_INTEGER (L"Vertical alignment") - 1); Graphics_setInner (GRAPHICS); Graphics_setFont (GRAPHICS, GET_ENUM (kGraphics_font, L"Font")); Graphics_setFontSize (GRAPHICS, GET_INTEGER (L"Font size")); wchar_t *rotation = GET_STRING (L"Rotation"), *semicolon; if ((semicolon = wcschr (rotation, ';')) != NULL) Graphics_setTextRotation_vector (GRAPHICS, Melder_atof (rotation), Melder_atof (semicolon + 1)); else Graphics_setTextRotation (GRAPHICS, Melder_atof (rotation)); Graphics_text (GRAPHICS, GET_REAL (L"Horizontal position"), GET_REAL (L"Vertical position"), GET_STRING (L"text")); Graphics_setFont (GRAPHICS, currentFont); Graphics_setFontSize (GRAPHICS, currentSize); Graphics_setTextRotation (GRAPHICS, 0.0); Graphics_unsetInner (GRAPHICS); END static void dia_line (Any dia) { REAL (L"From x", L"0.0") REAL (L"From y", L"0.0") REAL (L"To x", L"1.0") REAL (L"To y", L"1.0") } FORM (DrawLine, L"Praat picture: Draw line", 0) dia_line (dia); OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_line (GRAPHICS, GET_REAL (L"From x"), GET_REAL (L"From y"), GET_REAL (L"To x"), GET_REAL (L"To y")); Graphics_unsetInner (GRAPHICS); END FORM (DrawArrow, L"Praat picture: Draw arrow", 0) dia_line (dia); OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_arrow (GRAPHICS, GET_REAL (L"From x"), GET_REAL (L"From y"), GET_REAL (L"To x"), GET_REAL (L"To y")); Graphics_unsetInner (GRAPHICS); END FORM (DrawDoubleArrow, L"Praat picture: Draw double arrow", 0) dia_line (dia); OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_doubleArrow (GRAPHICS, GET_REAL (L"From x"), GET_REAL (L"From y"), GET_REAL (L"To x"), GET_REAL (L"To y")); Graphics_unsetInner (GRAPHICS); END Thing_define (PraatPictureFunction, Data) { // new data: public: double xmin, xmax, dx, x1; long nx; // overridden methods: virtual bool v_hasGetXmin () { return true; } virtual double v_getXmin () { return xmin; } virtual bool v_hasGetXmax () { return true; } virtual double v_getXmax () { return xmax; } virtual bool v_hasGetNx () { return true; } virtual double v_getNx () { return nx; } virtual bool v_hasGetDx () { return true; } virtual double v_getDx () { return dx; } virtual bool v_hasGetX () { return true; } virtual double v_getX (long ix) { return x1 + (ix - 1) * dx; } }; Thing_implement (PraatPictureFunction, Data, 0); FORM (DrawFunction, L"Praat picture: Draw function", 0) LABEL (L"", L"This command assumes that the x and y axes") LABEL (L"", L"have been set by a Draw command or by \"Axes...\".") REAL (L"From x", L"0.0") REAL (L"To x", L"0.0 (= all)") NATURAL (L"Number of horizontal steps", L"1000") LABEL (L"", L"Formula:") TEXTFIELD (L"formula", L"x^2 - x^4") OK DO double x1WC, x2WC, y1WC, y2WC; double fromX = GET_REAL (L"From x"), toX = GET_REAL (L"To x"); long n = GET_INTEGER (L"Number of horizontal steps"); wchar *formula = GET_STRING (L"formula"); if (n < 2) return; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); if (fromX == toX) fromX = x1WC, toX = x2WC; autoNUMvector y (1, n); autoPraatPictureFunction function = Thing_new (PraatPictureFunction); function -> xmin = x1WC; function -> xmax = x2WC; function -> nx = n; function -> x1 = fromX; function -> dx = (toX - fromX) / (n - 1); Formula_compile (interpreter, function.peek(), formula, kFormula_EXPRESSION_TYPE_NUMERIC, TRUE); therror for (long i = 1; i <= n; i ++) { struct Formula_Result result; Formula_run (1, i, & result); therror y [i] = result. result.numericResult; } autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_function (GRAPHICS, y.peek(), 1, n, fromX, toX); Graphics_unsetInner (GRAPHICS); END static void dia_rectangle (Any dia) { REAL (L"From x", L"0.0") REAL (L"To x", L"1.0") REAL (L"From y", L"0.0") REAL (L"To y", L"1.0") } FORM (DrawRectangle, L"Praat picture: Draw rectangle", 0) dia_rectangle (dia); OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_rectangle (GRAPHICS, GET_REAL (L"From x"), GET_REAL (L"To x"), GET_REAL (L"From y"), GET_REAL (L"To y")); Graphics_unsetInner (GRAPHICS); END FORM (PaintRectangle, L"Praat picture: Paint rectangle", 0) COLOUR (L"Colour (0-1, name, or {r,g,b})", L"0.5") dia_rectangle (dia); OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_setColour (GRAPHICS, GET_COLOUR (L"Colour")); Graphics_fillRectangle (GRAPHICS, GET_REAL (L"From x"), GET_REAL (L"To x"), GET_REAL (L"From y"), GET_REAL (L"To y")); Graphics_unsetInner (GRAPHICS); END FORM (DrawRoundedRectangle, L"Praat picture: Draw rounded rectangle", 0) dia_rectangle (dia); POSITIVE (L"Radius (mm)", L"3.0") OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_roundedRectangle (GRAPHICS, GET_REAL (L"From x"), GET_REAL (L"To x"), GET_REAL (L"From y"), GET_REAL (L"To y"), GET_REAL (L"Radius")); Graphics_unsetInner (GRAPHICS); END FORM (PaintRoundedRectangle, L"Praat picture: Paint rounded rectangle", 0) COLOUR (L"Colour (0-1, name, or {r,g,b})", L"0.5") dia_rectangle (dia); POSITIVE (L"Radius (mm)", L"3.0") OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_setColour (GRAPHICS, GET_COLOUR (L"Colour")); Graphics_fillRoundedRectangle (GRAPHICS, GET_REAL (L"From x"), GET_REAL (L"To x"), GET_REAL (L"From y"), GET_REAL (L"To y"), GET_REAL (L"Radius")); Graphics_unsetInner (GRAPHICS); END FORM (DrawArc, L"Praat picture: Draw arc", 0) REAL (L"Centre x", L"0.0") REAL (L"Centre y", L"0.0") POSITIVE (L"Radius (along x)", L"1.0") REAL (L"From angle (degrees)", L"0.0") REAL (L"To angle (degrees)", L"90.0") OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_arc (GRAPHICS, GET_REAL (L"Centre x"), GET_REAL (L"Centre y"), GET_REAL (L"Radius"), GET_REAL (L"From angle"), GET_REAL (L"To angle")); Graphics_unsetInner (GRAPHICS); END FORM (DrawEllipse, L"Praat picture: Draw ellipse", 0) dia_rectangle (dia); OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_ellipse (GRAPHICS, GET_REAL (L"From x"), GET_REAL (L"To x"), GET_REAL (L"From y"), GET_REAL (L"To y")); Graphics_unsetInner (GRAPHICS); END FORM (PaintEllipse, L"Praat picture: Paint ellipse", 0) COLOUR (L"Colour (0-1, name, or {r,g,b})", L"0.5") dia_rectangle (dia); OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_setColour (GRAPHICS, GET_COLOUR (L"Colour")); Graphics_fillEllipse (GRAPHICS, GET_REAL (L"From x"), GET_REAL (L"To x"), GET_REAL (L"From y"), GET_REAL (L"To y")); Graphics_unsetInner (GRAPHICS); END FORM (DrawCircle, L"Praat picture: Draw circle", 0) REAL (L"Centre x", L"0.0") REAL (L"Centre y", L"0.0") POSITIVE (L"Radius (along x)", L"1.0") OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_circle (GRAPHICS, GET_REAL (L"Centre x"), GET_REAL (L"Centre y"), GET_REAL (L"Radius")); Graphics_unsetInner (GRAPHICS); END FORM (PaintCircle, L"Praat picture: Paint circle", 0) COLOUR (L"Colour (0-1, name, or {r,g,b})", L"0.5") REAL (L"Centre x", L"0") REAL (L"Centre y", L"0") POSITIVE (L"Radius (along x)", L"1.0") OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_setColour (GRAPHICS, GET_COLOUR (L"Colour")); Graphics_fillCircle (GRAPHICS, GET_REAL (L"Centre x"), GET_REAL (L"Centre y"), GET_REAL (L"Radius")); Graphics_unsetInner (GRAPHICS); END FORM (DrawCircle_mm, L"Praat picture: Draw circle (mm)", 0) REAL (L"Centre x", L"0.0") REAL (L"Centre y", L"0.0") POSITIVE (L"Diameter (mm)", L"5.0") OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_circle_mm (GRAPHICS, GET_REAL (L"Centre x"), GET_REAL (L"Centre y"), GET_REAL (L"Diameter")); Graphics_unsetInner (GRAPHICS); END FORM (PaintCircle_mm, L"Praat picture: Paint circle (mm)", 0) COLOUR (L"Colour (0-1, name, or {r,g,b})", L"0.5") REAL (L"Centre x", L"0.0") REAL (L"Centre y", L"0.0") POSITIVE (L"Diameter (mm)", L"5.0") OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_setColour (GRAPHICS, GET_COLOUR (L"Colour")); Graphics_fillCircle_mm (GRAPHICS, GET_REAL (L"Centre x"), GET_REAL (L"Centre y"), GET_REAL (L"Diameter")); Graphics_unsetInner (GRAPHICS); END FORM (InsertPictureFromFile, L"Praat picture: Insert picture from file", L"Insert picture from file...") LABEL (L"", L"File name:") TEXTFIELD (L"fileName", L"~/Desktop/paul.jpg") dia_rectangle (dia); OK DO autoPraatPicture picture; Graphics_setInner (GRAPHICS); Graphics_imageFromFile (GRAPHICS, GET_STRING (L"fileName"), GET_REAL (L"From x"), GET_REAL (L"To x"), GET_REAL (L"From y"), GET_REAL (L"To y")); Graphics_unsetInner (GRAPHICS); END FORM (Axes, L"Praat picture: Axes", L"Axes...") REAL (L"left Left and right", L"0.0") REAL (L"right Left and right", L"1.0") REAL (L"left Bottom and top", L"0.0") REAL (L"right Bottom and top", L"1.0") OK double x1WC, x2WC, y1WC, y2WC; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); SET_REAL (L"left Left and right", x1WC); SET_REAL (L"right Left and right", x2WC); SET_REAL (L"left Bottom and top", y1WC); SET_REAL (L"right Bottom and top", y2WC); DO double left = GET_REAL (L"left Left and right"), right = GET_REAL (L"right Left and right"); double top = GET_REAL (L"right Bottom and top"), bottom = GET_REAL (L"left Bottom and top"); REQUIRE (right != left, L"Left and right must not be equal.") REQUIRE (top != bottom, L"Top and bottom must not be equal.") autoPraatPicture picture; Graphics_setWindow (GRAPHICS, left, right, bottom, top); END /***** "Margins" MENU *****/ DIRECT (DrawInnerBox) autoPraatPicture picture; Graphics_drawInnerBox (GRAPHICS); END FORM (Text_left, L"Praat picture: Text left", L"Text left/right/top/bottom...") BOOLEAN (L"Far", 1) TEXTFIELD (L"text", L"") OK DO autoPraatPicture picture; Graphics_textLeft (GRAPHICS, GET_INTEGER (L"Far"), GET_STRING (L"text")); END FORM (Text_right, L"Praat picture: Text right", L"Text left/right/top/bottom...") BOOLEAN (L"Far", 1) TEXTFIELD (L"text", L"") OK DO autoPraatPicture picture; Graphics_textRight (GRAPHICS, GET_INTEGER (L"Far"), GET_STRING (L"text")); END FORM (Text_top, L"Praat picture: Text top", L"Text left/right/top/bottom...") BOOLEAN (L"Far", 0) TEXTFIELD (L"text", L"") OK DO autoPraatPicture picture; Graphics_textTop (GRAPHICS, GET_INTEGER (L"Far"), GET_STRING (L"text")); END FORM (Text_bottom, L"Praat picture: Text bottom", L"Text left/right/top/bottom...") BOOLEAN (L"Far", 1) TEXTFIELD (L"text", L"") OK DO autoPraatPicture picture; Graphics_textBottom (GRAPHICS, GET_INTEGER (L"Far"), GET_STRING (L"text")); END static void dia_marksEvery (Any dia) { POSITIVE (L"Units", L"1.0") POSITIVE (L"Distance", L"0.1") BOOLEAN (L"Write numbers", 1) BOOLEAN (L"Draw ticks", 1) BOOLEAN (L"Draw dotted lines", 1) } static void do_marksEvery (Any dia, void (*Graphics_marksEvery) (Graphics, double, double, bool, bool, bool)) { autoPraatPicture picture; Graphics_marksEvery (GRAPHICS, GET_REAL (L"Units"), GET_REAL (L"Distance"), GET_INTEGER (L"Write numbers"), GET_INTEGER (L"Draw ticks"), GET_INTEGER (L"Draw dotted lines")); } FORM (Marks_left_every, L"Praat picture: Marks left every...", L"Marks left/right/top/bottom every...") dia_marksEvery (dia); OK DO do_marksEvery (dia, Graphics_marksLeftEvery); END FORM (Marks_right_every, L"Praat picture: Marks right every...", L"Marks left/right/top/bottom every...") dia_marksEvery (dia); OK DO do_marksEvery (dia, Graphics_marksRightEvery); END FORM (Marks_bottom_every, L"Praat picture: Marks bottom every...", L"Marks left/right/top/bottom every...") dia_marksEvery (dia); OK DO do_marksEvery (dia, Graphics_marksBottomEvery); END FORM (Marks_top_every, L"Praat picture: Marks top every...", L"Marks left/right/top/bottom every...") dia_marksEvery (dia); OK DO do_marksEvery (dia, Graphics_marksTopEvery); END static void dia_marks (Any dia) { NATURAL (L"Number of marks", L"6") BOOLEAN (L"Write numbers", 1) BOOLEAN (L"Draw ticks", 1) BOOLEAN (L"Draw dotted lines", 1) } static void do_marks (Any dia, void (*Graphics_marks) (Graphics, int, bool, bool, bool)) { long numberOfMarks = GET_INTEGER (L"Number of marks"); REQUIRE (numberOfMarks >= 2, L"`Number of marks' must be at least 2.") autoPraatPicture picture; Graphics_marks (GRAPHICS, numberOfMarks, GET_INTEGER (L"Write numbers"), GET_INTEGER (L"Draw ticks"), GET_INTEGER (L"Draw dotted lines")); } FORM (Marks_left, L"Praat picture: Marks left", L"Marks left/right/top/bottom...") dia_marks (dia); OK DO do_marks (dia, Graphics_marksLeft); END FORM (Marks_right, L"Praat picture: Marks right", L"Marks left/right/top/bottom...") dia_marks (dia); OK DO do_marks (dia, Graphics_marksRight); END FORM (Marks_bottom, L"Praat picture: Marks bottom", L"Marks left/right/top/bottom...") dia_marks (dia); OK DO do_marks (dia, Graphics_marksBottom); END FORM (Marks_top, L"Praat picture: Marks top", L"Marks left/right/top/bottom...") dia_marks (dia); OK DO do_marks (dia, Graphics_marksTop); END static void dia_marksLogarithmic (Any dia) { NATURAL (L"Marks per decade", L"3") BOOLEAN (L"Write numbers", 1) BOOLEAN (L"Draw ticks", 1) BOOLEAN (L"Draw dotted lines", 1) } static void do_marksLogarithmic (Any dia, void (*Graphics_marksLogarithmic) (Graphics, int, bool, bool, bool)) { long numberOfMarksPerDecade = GET_INTEGER (L"Marks per decade"); autoPraatPicture picture; Graphics_marksLogarithmic (GRAPHICS, numberOfMarksPerDecade, GET_INTEGER (L"Write numbers"), GET_INTEGER (L"Draw ticks"), GET_INTEGER (L"Draw dotted lines")); } FORM (marksLeftLogarithmic, L"Praat picture: Logarithmic marks left", L"Logarithmic marks left/right/top/bottom...") dia_marksLogarithmic (dia); OK DO do_marksLogarithmic (dia, Graphics_marksLeftLogarithmic); END FORM (marksRightLogarithmic, L"Praat picture: Logarithmic marks right", L"Logarithmic marks left/right/top/bottom...") dia_marksLogarithmic (dia); OK DO do_marksLogarithmic (dia, Graphics_marksRightLogarithmic); END FORM (marksBottomLogarithmic, L"Praat picture: Logarithmic marks bottom", L"Logarithmic marks left/right/top/bottom...") dia_marksLogarithmic (dia); OK DO do_marksLogarithmic (dia, Graphics_marksBottomLogarithmic); END FORM (marksTopLogarithmic, L"Praat picture: Logarithmic marks top", L"Logarithmic marks left/right/top/bottom...") dia_marksLogarithmic (dia); OK DO do_marksLogarithmic (dia, Graphics_marksTopLogarithmic); END static void sortBoundingBox (double *x1WC, double *x2WC, double *y1WC, double *y2WC) { double temp; if (*x1WC > *x2WC) temp = *x1WC, *x1WC = *x2WC, *x2WC = temp; if (*y1WC > *y2WC) temp = *y1WC, *y1WC = *y2WC, *y2WC = temp; } static void dia_oneMark (Any dia) { REAL (L"Position", L"0.0") BOOLEAN (L"Write number", 1) BOOLEAN (L"Draw tick", 1) BOOLEAN (L"Draw dotted line", 1) LABEL (L"", L"Draw text:") TEXTFIELD (L"text", L"") } FORM (Mark_left, L"Praat picture: One mark left", L"One mark left/right/top/bottom...") dia_oneMark (dia); OK DO double position = GET_REAL (L"Position"); double x1WC, x2WC, y1WC, y2WC, dy; { autoPraatPicture picture; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); } sortBoundingBox (& x1WC, & x2WC, & y1WC, & y2WC); dy = 0.2 * (y2WC - y1WC); if (position < y1WC - dy || position > y2WC + dy) Melder_throw ("\"Position\" must be between ", y1WC, " and ", y2WC, "."); autoPraatPicture picture; Graphics_markLeft (GRAPHICS, position, GET_INTEGER (L"Write number"), GET_INTEGER (L"Draw tick"), GET_INTEGER (L"Draw dotted line"), GET_STRING (L"text")); END FORM (Mark_right, L"Praat picture: One mark right", L"One mark left/right/top/bottom...") dia_oneMark (dia); OK DO double position = GET_REAL (L"Position"); double x1WC, x2WC, y1WC, y2WC, dy; { autoPraatPicture picture; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); } sortBoundingBox (& x1WC, & x2WC, & y1WC, & y2WC); dy = 0.2 * (y2WC - y1WC); if (position < y1WC - dy || position > y2WC + dy) Melder_throw ("\"Position\" must be between ", y1WC, " and ", y2WC, "."); autoPraatPicture picture; Graphics_markRight (GRAPHICS, position, GET_INTEGER (L"Write number"), GET_INTEGER (L"Draw tick"), GET_INTEGER (L"Draw dotted line"), GET_STRING (L"text")); END FORM (Mark_top, L"Praat picture: One mark top", L"One mark left/right/top/bottom...") dia_oneMark (dia); OK DO double position = GET_REAL (L"Position"); double x1WC, x2WC, y1WC, y2WC, dx; { autoPraatPicture picture; // WHY? Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); } sortBoundingBox (& x1WC, & x2WC, & y1WC, & y2WC); dx = 0.2 * (x2WC - x1WC); if (position < x1WC - dx || position > x2WC + dx) Melder_throw ("\"Position\" must be between ", x1WC, " and ", x2WC, "."); autoPraatPicture picture; Graphics_markTop (GRAPHICS, position, GET_INTEGER (L"Write number"), GET_INTEGER (L"Draw tick"), GET_INTEGER (L"Draw dotted line"), GET_STRING (L"text")); END FORM (Mark_bottom, L"Praat picture: One mark bottom", L"One mark left/right/top/bottom...") dia_oneMark (dia); OK DO double position = GET_REAL (L"Position"); double x1WC, x2WC, y1WC, y2WC, dx; { autoPraatPicture picture; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); } sortBoundingBox (& x1WC, & x2WC, & y1WC, & y2WC); dx = 0.2 * (x2WC - x1WC); if (position < x1WC - dx || position > x2WC + dx) Melder_throw ("\"Position\" must be between ", x1WC, " and ", x2WC, "."); autoPraatPicture picture; Graphics_markBottom (GRAPHICS, position, GET_INTEGER (L"Write number"), GET_INTEGER (L"Draw tick"), GET_INTEGER (L"Draw dotted line"), GET_STRING (L"text")); END static void dia_oneLogarithmicMark (Any dia) { REAL (L"Position", L"1.0") BOOLEAN (L"Write number", 1) BOOLEAN (L"Draw tick", 1) BOOLEAN (L"Draw dotted line", 1) LABEL (L"", L"Draw text:") TEXTFIELD (L"text", L"") } FORM (LogarithmicMark_left, L"Praat picture: One logarithmic mark left", L"One logarithmic mark left/right/top/bottom...") dia_oneLogarithmicMark (dia); OK DO double position = GET_REAL (L"Position"); double x1WC, x2WC, y1WC, y2WC, dy; { autoPraatPicture picture; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); } sortBoundingBox (& x1WC, & x2WC, & y1WC, & y2WC); dy = 0.2 * (y2WC - y1WC); if (position < pow (10, y1WC - dy) || position > pow (10, y2WC + dy)) Melder_throw ("\"Position\" must be between ", pow (10, y1WC), " and ", pow (10, y2WC), "."); autoPraatPicture picture; Graphics_markLeftLogarithmic (GRAPHICS, position, GET_INTEGER (L"Write number"), GET_INTEGER (L"Draw tick"), GET_INTEGER (L"Draw dotted line"), GET_STRING (L"text")); END FORM (LogarithmicMark_right, L"Praat picture: One logarithmic mark right", L"One logarithmic mark left/right/top/bottom...") dia_oneLogarithmicMark (dia); OK DO double position = GET_REAL (L"Position"); double x1WC, x2WC, y1WC, y2WC, dy; { autoPraatPicture picture; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); } sortBoundingBox (& x1WC, & x2WC, & y1WC, & y2WC); dy = 0.2 * (y2WC - y1WC); if (position < pow (10, y1WC - dy) || position > pow (10, y2WC + dy)) Melder_throw ("\"Position\" must be between ", pow (10, y1WC), " and ", pow (10, y2WC), "."); autoPraatPicture picture; Graphics_markRightLogarithmic (GRAPHICS, position, GET_INTEGER (L"Write number"), GET_INTEGER (L"Draw tick"), GET_INTEGER (L"Draw dotted line"), GET_STRING (L"text")); END FORM (LogarithmicMark_top, L"Praat picture: One logarithmic mark top", L"One logarithmic mark left/right/top/bottom...") dia_oneLogarithmicMark (dia); OK DO double position = GET_REAL (L"Position"); double x1WC, x2WC, y1WC, y2WC, dx; { autoPraatPicture picture; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); } sortBoundingBox (& x1WC, & x2WC, & y1WC, & y2WC); dx = 0.2 * (x2WC - x1WC); if (position < pow (10, x1WC - dx) || position > pow (10, x2WC + dx)) Melder_throw ("\"Position\" must be between ", pow (10, x1WC), " and ", pow (10, x2WC), "."); autoPraatPicture picture; Graphics_markTopLogarithmic (GRAPHICS, position, GET_INTEGER (L"Write number"), GET_INTEGER (L"Draw tick"), GET_INTEGER (L"Draw dotted line"), GET_STRING (L"text")); END FORM (LogarithmicMark_bottom, L"Praat picture: One logarithmic mark bottom", L"One logarithmic mark left/right/top/bottom...") dia_oneLogarithmicMark (dia); OK DO double position = GET_REAL (L"Position"); double x1WC, x2WC, y1WC, y2WC, dx; { autoPraatPicture picture; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); } sortBoundingBox (& x1WC, & x2WC, & y1WC, & y2WC); dx = 0.2 * (x2WC - x1WC); if (position < pow (10, x1WC - dx) || position > pow (10, x2WC + dx)) Melder_throw ("\"Position\" must be between ", pow (10, x1WC), " and ", pow (10, x2WC), "."); autoPraatPicture picture; Graphics_markBottomLogarithmic (GRAPHICS, position, GET_INTEGER (L"Write number"), GET_INTEGER (L"Draw tick"), GET_INTEGER (L"Draw dotted line"), GET_STRING (L"text")); END FORM (dxMMtoWC, L"Compute horizontal distance in world coordinates", 0) REAL (L"Distance (mm)", L"10.0") OK DO Graphics_setFontSize (GRAPHICS, theCurrentPraatPicture -> fontSize); Graphics_setViewport (GRAPHICS, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setInner (GRAPHICS); double wc = Graphics_dxMMtoWC (GRAPHICS, GET_REAL (L"Distance")); Graphics_unsetInner (GRAPHICS); Melder_informationReal (wc, L"(world coordinates)"); END FORM (dxWCtoMM, L"Compute horizontal distance in millimetres", 0) REAL (L"Distance (wc)", L"0.1") OK DO Graphics_setFontSize (GRAPHICS, theCurrentPraatPicture -> fontSize); Graphics_setViewport (GRAPHICS, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setInner (GRAPHICS); double mm = Graphics_dxWCtoMM (GRAPHICS, GET_REAL (L"Distance")); Graphics_unsetInner (GRAPHICS); Melder_informationReal (mm, L"mm"); END FORM (dyMMtoWC, L"Compute vertical distance in world coordinates", 0) REAL (L"Distance (mm)", L"10.0") OK DO Graphics_setFontSize (GRAPHICS, theCurrentPraatPicture -> fontSize); Graphics_setViewport (GRAPHICS, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setInner (GRAPHICS); double wc = Graphics_dyMMtoWC (GRAPHICS, GET_REAL (L"Distance")); Graphics_unsetInner (GRAPHICS); Melder_informationReal (wc, L"(world coordinates)"); END FORM (dyWCtoMM, L"Compute vertical distance in millimetres", 0) REAL (L"Distance (wc)", L"1.0") OK DO Graphics_setFontSize (GRAPHICS, theCurrentPraatPicture -> fontSize); Graphics_setViewport (GRAPHICS, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setInner (GRAPHICS); double mm = Graphics_dyWCtoMM (GRAPHICS, GET_REAL (L"Distance")); Graphics_unsetInner (GRAPHICS); Melder_informationReal (mm, L"mm"); END FORM (textWidth_wc, L"Text width in world coordinates", 0) TEXTFIELD (L"text", L"Hello world") OK DO Graphics_setFont (GRAPHICS, static_cast (theCurrentPraatPicture -> font)); Graphics_setFontSize (GRAPHICS, theCurrentPraatPicture -> fontSize); Graphics_setViewport (GRAPHICS, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setInner (GRAPHICS); double wc = Graphics_textWidth (GRAPHICS, GET_STRING (L"text")); Graphics_unsetInner (GRAPHICS); Melder_informationReal (wc, L"(world coordinates)"); END FORM (textWidth_mm, L"Text width in millimetres", 0) TEXTFIELD (L"text", L"Hello world") OK DO Graphics_setFont (GRAPHICS, static_cast (theCurrentPraatPicture -> font)); Graphics_setFontSize (GRAPHICS, theCurrentPraatPicture -> fontSize); Graphics_setViewport (GRAPHICS, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setInner (GRAPHICS); double mm = Graphics_dxWCtoMM (GRAPHICS, Graphics_textWidth (GRAPHICS, GET_STRING (L"text"))); Graphics_unsetInner (GRAPHICS); Melder_informationReal (mm, L"mm"); END FORM (textWidth_ps_wc, L"PostScript text width in world coordinates", 0) RADIO (L"Phonetic font", 1) RADIOBUTTON (L"XIPA") RADIOBUTTON (L"SILIPA") TEXTFIELD (L"text", L"Hello world") OK DO Graphics_setFont (GRAPHICS, static_cast (theCurrentPraatPicture -> font)); Graphics_setFontSize (GRAPHICS, theCurrentPraatPicture -> fontSize); Graphics_setViewport (GRAPHICS, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setInner (GRAPHICS); double wc = Graphics_textWidth_ps (GRAPHICS, GET_STRING (L"text"), GET_INTEGER (L"Phonetic font") - 1); Graphics_unsetInner (GRAPHICS); Melder_informationReal (wc, L"(world coordinates)"); END FORM (textWidth_ps_mm, L"PostScript text width in millimetres", 0) RADIO (L"Phonetic font", 1) RADIOBUTTON (L"XIPA") RADIOBUTTON (L"SILIPA") TEXTFIELD (L"text", L"Hello world") OK DO Graphics_setFont (GRAPHICS, static_cast (theCurrentPraatPicture -> font)); Graphics_setFontSize (GRAPHICS, theCurrentPraatPicture -> fontSize); Graphics_setViewport (GRAPHICS, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setInner (GRAPHICS); double mm = Graphics_textWidth_ps_mm (GRAPHICS, GET_STRING (L"text"), GET_INTEGER (L"Phonetic font") - 1); Graphics_unsetInner (GRAPHICS); Melder_informationReal (mm, L"mm"); END DIRECT (SearchManual) Melder_search (); END DIRECT (PictureWindowHelp) Melder_help (L"Picture window"); END DIRECT (AboutSpecialSymbols) Melder_help (L"Special symbols"); END DIRECT (AboutTextStyles) Melder_help (L"Text styles"); END DIRECT (PhoneticSymbols) Melder_help (L"Phonetic symbols"); END DIRECT (Picture_settings_report) MelderInfo_open (); MelderInfo_writeLine3 (L"Outer viewport left: ", Melder_double (theCurrentPraatPicture -> x1NDC), L" inches"); MelderInfo_writeLine3 (L"Outer viewport right: ", Melder_double (theCurrentPraatPicture -> x2NDC), L" inches"); MelderInfo_writeLine3 (L"Outer viewport top: ", Melder_double (12 - theCurrentPraatPicture -> y2NDC), L" inches"); MelderInfo_writeLine3 (L"Outer viewport bottom: ", Melder_double (12 - theCurrentPraatPicture -> y1NDC), L" inches"); MelderInfo_writeLine3 (L"Font size: ", Melder_double (theCurrentPraatPicture -> fontSize), L" points"); double xmargin = theCurrentPraatPicture -> fontSize * 4.2 / 72.0, ymargin = theCurrentPraatPicture -> fontSize * 2.8 / 72.0; if (ymargin > 0.4 * (theCurrentPraatPicture -> y2NDC - theCurrentPraatPicture -> y1NDC)) ymargin = 0.4 * (theCurrentPraatPicture -> y2NDC - theCurrentPraatPicture -> y1NDC); if (xmargin > 0.4 * (theCurrentPraatPicture -> x2NDC - theCurrentPraatPicture -> x1NDC)) xmargin = 0.4 * (theCurrentPraatPicture -> x2NDC - theCurrentPraatPicture -> x1NDC); MelderInfo_writeLine3 (L"Inner viewport left: ", Melder_double (theCurrentPraatPicture -> x1NDC + xmargin), L" inches"); MelderInfo_writeLine3 (L"Inner viewport right: ", Melder_double (theCurrentPraatPicture -> x2NDC - xmargin), L" inches"); MelderInfo_writeLine3 (L"Inner viewport top: ", Melder_double (12 - theCurrentPraatPicture -> y2NDC + ymargin), L" inches"); MelderInfo_writeLine3 (L"Inner viewport bottom: ", Melder_double (12 - theCurrentPraatPicture -> y1NDC - ymargin), L" inches"); MelderInfo_writeLine2 (L"Font: ", kGraphics_font_getText (theCurrentPraatPicture -> font)); MelderInfo_writeLine2 (L"Line type: ", theCurrentPraatPicture -> lineType == Graphics_DRAWN ? L"Solid" : theCurrentPraatPicture -> lineType == Graphics_DOTTED ? L"Dotted" : theCurrentPraatPicture -> lineType == Graphics_DASHED ? L"Dashed" : theCurrentPraatPicture -> lineType == Graphics_DASHED_DOTTED ? L"Dashed-dotted" : L"(unknown)"); MelderInfo_writeLine2 (L"Line width: ", Melder_double (theCurrentPraatPicture -> lineWidth)); MelderInfo_writeLine2 (L"Arrow size: ", Melder_double (theCurrentPraatPicture -> arrowSize)); MelderInfo_writeLine2 (L"Colour: ", Graphics_Colour_name (theCurrentPraatPicture -> colour)); MelderInfo_writeLine2 (L"Red: ", Melder_double (theCurrentPraatPicture -> colour. red)); MelderInfo_writeLine2 (L"Green: ", Melder_double (theCurrentPraatPicture -> colour. green)); MelderInfo_writeLine2 (L"Blue: ", Melder_double (theCurrentPraatPicture -> colour. blue)); double x1WC, x2WC, y1WC, y2WC; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); MelderInfo_writeLine2 (L"Axis left: ", Melder_double (x1WC)); MelderInfo_writeLine2 (L"Axis right: ", Melder_double (x2WC)); MelderInfo_writeLine2 (L"Axis bottom: ", Melder_double (y1WC)); MelderInfo_writeLine2 (L"Axis top: ", Melder_double (y2WC)); MelderInfo_close (); END /********** **********/ static void cb_selectionChanged (Picture p, XtPointer closure, double selx1, double selx2, double sely1, double sely2) /* The user selected a new viewport in the picture window. */ { (void) closure; Melder_assert (p == praat_picture); theCurrentPraatPicture -> x1NDC = selx1; theCurrentPraatPicture -> x2NDC = selx2; theCurrentPraatPicture -> y1NDC = sely1; theCurrentPraatPicture -> y2NDC = sely2; if (praat_mouseSelectsInnerViewport) { int fontSize = Graphics_inqFontSize (GRAPHICS); double xmargin = fontSize * 4.2 / 72.0, ymargin = fontSize * 2.8 / 72.0; if (ymargin > 0.4 * (theCurrentPraatPicture -> y2NDC - theCurrentPraatPicture -> y1NDC)) ymargin = 0.4 * (theCurrentPraatPicture -> y2NDC - theCurrentPraatPicture -> y1NDC); if (xmargin > 0.4 * (theCurrentPraatPicture -> x2NDC - theCurrentPraatPicture -> x1NDC)) xmargin = 0.4 * (theCurrentPraatPicture -> x2NDC - theCurrentPraatPicture -> x1NDC); UiHistory_write (L"\nSelect inner viewport... "); UiHistory_write (Melder_single (theCurrentPraatPicture -> x1NDC + xmargin)); UiHistory_write (L" "); UiHistory_write (Melder_single (theCurrentPraatPicture -> x2NDC - xmargin)); UiHistory_write (L" "); UiHistory_write (Melder_single (12 - theCurrentPraatPicture -> y2NDC + ymargin)); UiHistory_write (L" "); UiHistory_write (Melder_single (12 - theCurrentPraatPicture -> y1NDC - ymargin)); } else { UiHistory_write (L"\nSelect outer viewport... "); UiHistory_write (Melder_single (theCurrentPraatPicture -> x1NDC)); UiHistory_write (L" "); UiHistory_write (Melder_single (theCurrentPraatPicture -> x2NDC)); UiHistory_write (L" "); UiHistory_write (Melder_single (12 - theCurrentPraatPicture -> y2NDC)); UiHistory_write (L" "); UiHistory_write (Melder_single (12 - theCurrentPraatPicture -> y1NDC)); } } /***** Public functions. *****/ static GuiObject shell, fileMenu, editMenu, marginsMenu, worldMenu, selectMenu, fontMenu, penMenu, helpMenu; GuiObject praat_picture_resolveMenu (const wchar_t *menu) { return wcsequ (menu, L"File") ? fileMenu : wcsequ (menu, L"Edit") ? editMenu : wcsequ (menu, L"Margins") ? marginsMenu : wcsequ (menu, L"World") ? worldMenu : wcsequ (menu, L"Select") ? selectMenu : wcsequ (menu, L"Font") ? fontMenu : wcsequ (menu, L"Pen") ? penMenu : wcsequ (menu, L"Help") ? helpMenu : editMenu; /* Default. */ } void praat_picture_exit (void) { Picture_remove (& praat_picture); } void praat_picture_open (void) { Graphics_markGroup (GRAPHICS); // we start a group of graphics output here if (theCurrentPraatPicture == & theForegroundPraatPicture && ! theCurrentPraatApplication -> batch) { #if gtk gtk_window_present (GTK_WINDOW (shell)); #elif motif XtMapWidget (shell); XMapRaised (XtDisplay (shell), XtWindow (shell)); #endif Picture_unhighlight (praat_picture); } /* Foregoing drawing routines may have changed some of the output attributes */ /* that can be set by the user. */ /* Make sure that they have the right values before every drawing. */ /* This is especially necessary after an 'erase picture': */ /* the output attributes that were set by the user before the 'erase' */ /* must be recorded before copying to a PostScript file. */ Graphics_setFont (GRAPHICS, static_cast (theCurrentPraatPicture -> font)); Graphics_setFontSize (GRAPHICS, theCurrentPraatPicture -> fontSize); Graphics_setLineType (GRAPHICS, theCurrentPraatPicture -> lineType); Graphics_setLineWidth (GRAPHICS, theCurrentPraatPicture -> lineWidth); Graphics_setArrowSize (GRAPHICS, theCurrentPraatPicture -> arrowSize); Graphics_setColour (GRAPHICS, theCurrentPraatPicture -> colour); Graphics_setViewport (GRAPHICS, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); /* The following will dump the axes to the PostScript file after Erase all. BUG: should be somewhere else. */ double x1WC, x2WC, y1WC, y2WC; Graphics_inqWindow (GRAPHICS, & x1WC, & x2WC, & y1WC, & y2WC); Graphics_setWindow (GRAPHICS, x1WC, x2WC, y1WC, y2WC); } void praat_picture_close (void) { if (theCurrentPraatPicture != & theForegroundPraatPicture) return; if (! theCurrentPraatApplication -> batch) { Picture_highlight (praat_picture); #if gtk // TODO: Tijdelijke fix; dit exposed de selectie, maar voor bijvoorbeeld 'text' die buiten // de selectie valt is dit geen optie. Het mooiste zou zijn als na praat_picture_close // bekend zou zijn wat de 'dirty' regio is van het scherm. Om vervolgens alleen dat te exposen Picture_selfExpose (praat_picture); #endif } } Graphics praat_picture_editor_open (bool eraseFirst) { if (eraseFirst) Picture_erase (praat_picture); praat_picture_open (); return GRAPHICS; } void praat_picture_editor_close (void) { praat_picture_close (); } void praat_picture_init (void) { GuiObject dialog, scrollWindow, menuBar, drawingArea = NULL; int margin, width, height, resolution, x, y; static MelderString itemTitle_search = { 0 }; theCurrentPraatPicture -> lineType = Graphics_DRAWN; theCurrentPraatPicture -> colour = Graphics_BLACK; theCurrentPraatPicture -> lineWidth = 1.0; theCurrentPraatPicture -> arrowSize = 1.0; theCurrentPraatPicture -> x1NDC = 0.0; theCurrentPraatPicture -> x2NDC = 6.0; theCurrentPraatPicture -> y1NDC = 8.0; theCurrentPraatPicture -> y2NDC = 12.0; if (! theCurrentPraatApplication -> batch) { char pictureWindowTitle [100]; // Ook al eerder gezien... Migreren naar UI? double screenX, screenY, screenWidth, screenHeight; Gui_getWindowPositioningBounds (& screenX, & screenY, & screenWidth, & screenHeight); resolution = Gui_getResolution (theCurrentPraatApplication -> topShell); #if defined (macintosh) margin = 2, width = 6 * resolution + 20; height = 9 * resolution + Machine_getMenuBarHeight () + 24; x = screenX + screenWidth - width - 14; y = screenY + 0; width += margin * 2; #elif defined (_WIN32) margin = 2, width = 6 * resolution + 22; height = 9 * resolution + 24; x = screenX + screenWidth - width - 17; y = screenY + 0; #else margin = 0, width = 6 * resolution + 30; height = width * 3 / 2 + Machine_getTitleBarHeight (); x = screenX + screenWidth - width - 10; y = screenY + 0; width += margin * 2; #endif sprintf (pictureWindowTitle, "%s Picture", praatP.title); dialog = GuiWindow_create (theCurrentPraatApplication -> topShell, x, y, width, height, Melder_peekUtf8ToWcs (pictureWindowTitle), NULL, NULL, 0); shell = GuiObject_parent (dialog); #ifdef UNIX #if motif XtVaSetValues (dialog, XmNhighlightThickness, 1, NULL); #endif #endif menuBar = Gui_addMenuBar (dialog); } if (! theCurrentPraatApplication -> batch) { fileMenu = GuiMenuBar_addMenu (menuBar, L"File", 0); editMenu = GuiMenuBar_addMenu (menuBar, L"Edit", 0); marginsMenu = GuiMenuBar_addMenu (menuBar, L"Margins", 0); worldMenu = GuiMenuBar_addMenu (menuBar, L"World", 0); selectMenu = GuiMenuBar_addMenu (menuBar, L"Select", 0); penMenu = GuiMenuBar_addMenu (menuBar, L"Pen", 0); fontMenu = GuiMenuBar_addMenu (menuBar, L"Font", 0); helpMenu = GuiMenuBar_addMenu (menuBar, L"Help", 0); } praat_addMenuCommand (L"Picture", L"File", L"Picture info", 0, 0, DO_Picture_settings_report); praat_addMenuCommand (L"Picture", L"File", L"Picture settings report", 0, praat_HIDDEN, DO_Picture_settings_report); praat_addMenuCommand (L"Picture", L"File", L"-- read --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"File", L"Read from praat picture file...", 0, 0, DO_Picture_readFromPraatPictureFile); praat_addMenuCommand (L"Picture", L"File", L"-- write --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"File", L"Save as praat picture file...", 0, 0, DO_Picture_writeToPraatPictureFile); praat_addMenuCommand (L"Picture", L"File", L"Write to praat picture file...", 0, praat_HIDDEN, DO_Picture_writeToPraatPictureFile); #ifdef _WIN32 praat_addMenuCommand (L"Picture", L"File", L"Save as Windows metafile...", 0, 0, DO_Picture_writeToWindowsMetafile); praat_addMenuCommand (L"Picture", L"File", L"Write to Windows metafile...", 0, praat_HIDDEN, DO_Picture_writeToWindowsMetafile); #endif #if defined (macintosh) praat_addMenuCommand (L"Picture", L"File", L"Save as PDF file...", 0, 'S', DO_Picture_writeToPdfFile); praat_addMenuCommand (L"Picture", L"File", L"Write to PDF file...", 0, praat_HIDDEN, DO_Picture_writeToPdfFile); praat_addMenuCommand (L"Picture", L"File", L"Save EPS file", 0, 0, NULL); praat_addMenuCommand (L"Picture", L"File", L"PostScript settings...", 0, 1, DO_PostScript_settings); praat_addMenuCommand (L"Picture", L"File", L"Save as EPS file...", 0, 1, DO_Picture_writeToEpsFile); praat_addMenuCommand (L"Picture", L"File", L"Write to EPS file...", 0, praat_HIDDEN + praat_DEPTH_1, DO_Picture_writeToEpsFile); praat_addMenuCommand (L"Picture", L"File", L"Save as fontless EPS file (XIPA)...", 0, 1, DO_Picture_writeToFontlessEpsFile_xipa); praat_addMenuCommand (L"Picture", L"File", L"Write to fontless EPS file (XIPA)...", 0, praat_HIDDEN + praat_DEPTH_1, DO_Picture_writeToFontlessEpsFile_xipa); praat_addMenuCommand (L"Picture", L"File", L"Save as fontless EPS file (SILIPA)...", 0, 1, DO_Picture_writeToFontlessEpsFile_silipa); praat_addMenuCommand (L"Picture", L"File", L"Write to fontless EPS file (SILIPA)...", 0, praat_HIDDEN + praat_DEPTH_1, DO_Picture_writeToFontlessEpsFile_silipa); #else praat_addMenuCommand (L"Picture", L"File", L"PostScript settings...", 0, 0, DO_PostScript_settings); praat_addMenuCommand (L"Picture", L"File", L"Save as EPS file...", 0, 'S', DO_Picture_writeToEpsFile); praat_addMenuCommand (L"Picture", L"File", L"Write to EPS file...", 0, praat_HIDDEN, DO_Picture_writeToEpsFile); praat_addMenuCommand (L"Picture", L"File", L"Save as fontless EPS file (XIPA)...", 0, 0, DO_Picture_writeToFontlessEpsFile_xipa); praat_addMenuCommand (L"Picture", L"File", L"Write to fontless EPS file (XIPA)...", 0, praat_HIDDEN, DO_Picture_writeToFontlessEpsFile_xipa); praat_addMenuCommand (L"Picture", L"File", L"Save as fontless EPS file (SILIPA)...", 0, 0, DO_Picture_writeToFontlessEpsFile_silipa); praat_addMenuCommand (L"Picture", L"File", L"Write to fontless EPS file (SILIPA)...", 0, praat_HIDDEN, DO_Picture_writeToFontlessEpsFile_silipa); #endif praat_addMenuCommand (L"Picture", L"File", L"-- print --", 0, 0, 0); #if defined (macintosh) praat_addMenuCommand (L"Picture", L"File", L"Page setup...", 0, 0, DO_Page_setup); #endif praat_addMenuCommand (L"Picture", L"File", L"Print...", 0, 'P', DO_Print); praat_addMenuCommand (L"Picture", L"Edit", L"Undo", 0, 'Z', DO_Undo); #if defined (macintosh) || defined (_WIN32) praat_addMenuCommand (L"Picture", L"Edit", L"-- clipboard --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Edit", L"Copy to clipboard", 0, 'C', DO_Copy_picture_to_clipboard); #endif praat_addMenuCommand (L"Picture", L"Edit", L"-- erase --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Edit", L"Erase all", 0, 'E', DO_Erase_all); praat_addMenuCommand (L"Picture", L"Margins", L"Draw inner box", 0, 0, DO_DrawInnerBox); praat_addMenuCommand (L"Picture", L"Margins", L"-- text --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Margins", L"Text left...", 0, 0, DO_Text_left); praat_addMenuCommand (L"Picture", L"Margins", L"Text right...", 0, 0, DO_Text_right); praat_addMenuCommand (L"Picture", L"Margins", L"Text top...", 0, 0, DO_Text_top); praat_addMenuCommand (L"Picture", L"Margins", L"Text bottom...", 0, 0, DO_Text_bottom); praat_addMenuCommand (L"Picture", L"Margins", L"-- marks every --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Margins", L"Marks left every...", 0, 0, DO_Marks_left_every); praat_addMenuCommand (L"Picture", L"Margins", L"Marks right every...", 0, 0, DO_Marks_right_every); praat_addMenuCommand (L"Picture", L"Margins", L"Marks bottom every...", 0, 0, DO_Marks_bottom_every); praat_addMenuCommand (L"Picture", L"Margins", L"Marks top every...", 0, 0, DO_Marks_top_every); praat_addMenuCommand (L"Picture", L"Margins", L"-- one mark --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Margins", L"One mark left...", 0, 0, DO_Mark_left); praat_addMenuCommand (L"Picture", L"Margins", L"One mark right...", 0, 0, DO_Mark_right); praat_addMenuCommand (L"Picture", L"Margins", L"One mark bottom...", 0, 0, DO_Mark_bottom); praat_addMenuCommand (L"Picture", L"Margins", L"One mark top...", 0, 0, DO_Mark_top); praat_addMenuCommand (L"Picture", L"Margins", L"-- marks --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Margins", L"Marks", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Margins", L"Marks left...", 0, 1, DO_Marks_left); praat_addMenuCommand (L"Picture", L"Margins", L"Marks right...", 0, 1, DO_Marks_right); praat_addMenuCommand (L"Picture", L"Margins", L"Marks bottom...", 0, 1, DO_Marks_bottom); praat_addMenuCommand (L"Picture", L"Margins", L"Marks top...", 0, 1, DO_Marks_top); praat_addMenuCommand (L"Picture", L"Margins", L"Logarithmic marks", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Margins", L"Logarithmic marks left...", 0, 1, DO_marksLeftLogarithmic); praat_addMenuCommand (L"Picture", L"Margins", L"Logarithmic marks right...", 0, 1, DO_marksRightLogarithmic); praat_addMenuCommand (L"Picture", L"Margins", L"Logarithmic marks bottom...", 0, 1, DO_marksBottomLogarithmic); praat_addMenuCommand (L"Picture", L"Margins", L"Logarithmic marks top...", 0, 1, DO_marksTopLogarithmic); praat_addMenuCommand (L"Picture", L"Margins", L"One logarithmic mark", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Margins", L"One logarithmic mark left...", 0, 1, DO_LogarithmicMark_left); praat_addMenuCommand (L"Picture", L"Margins", L"One logarithmic mark right...", 0, 1, DO_LogarithmicMark_right); praat_addMenuCommand (L"Picture", L"Margins", L"One logarithmic mark bottom...", 0, 1, DO_LogarithmicMark_bottom); praat_addMenuCommand (L"Picture", L"Margins", L"One logarithmic mark top...", 0, 1, DO_LogarithmicMark_top); praat_addMenuCommand (L"Picture", L"Margins", L"-- axes --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Margins", L"Axes...", 0, 0, DO_Axes); praat_addMenuCommand (L"Picture", L"World", L"Text...", 0, 0, DO_Text); praat_addMenuCommand (L"Picture", L"World", L"Text special...", 0, 0, DO_Text_special); praat_addMenuCommand (L"Picture", L"World", L"-- line --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"World", L"Draw line...", 0, 0, DO_DrawLine); praat_addMenuCommand (L"Picture", L"World", L"Draw arrow...", 0, 0, DO_DrawArrow); praat_addMenuCommand (L"Picture", L"World", L"Draw two-way arrow...", 0, 0, DO_DrawDoubleArrow); praat_addMenuCommand (L"Picture", L"World", L"-- function --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"World", L"Draw function...", 0, 0, DO_DrawFunction); praat_addMenuCommand (L"Picture", L"World", L"-- rectangle --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"World", L"Draw rectangle...", 0, 0, DO_DrawRectangle); praat_addMenuCommand (L"Picture", L"World", L"Paint rectangle...", 0, 0, DO_PaintRectangle); praat_addMenuCommand (L"Picture", L"World", L"Draw rounded rectangle...", 0, 0, DO_DrawRoundedRectangle); praat_addMenuCommand (L"Picture", L"World", L"Paint rounded rectangle...", 0, 0, DO_PaintRoundedRectangle); praat_addMenuCommand (L"Picture", L"World", L"-- arc --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"World", L"Draw arc...", 0, 0, DO_DrawArc); praat_addMenuCommand (L"Picture", L"World", L"Draw ellipse...", 0, 0, DO_DrawEllipse); praat_addMenuCommand (L"Picture", L"World", L"Paint ellipse...", 0, 0, DO_PaintEllipse); praat_addMenuCommand (L"Picture", L"World", L"Draw circle...", 0, 0, DO_DrawCircle); praat_addMenuCommand (L"Picture", L"World", L"Paint circle...", 0, 0, DO_PaintCircle); praat_addMenuCommand (L"Picture", L"World", L"Draw circle (mm)...", 0, 0, DO_DrawCircle_mm); praat_addMenuCommand (L"Picture", L"World", L"Paint circle (mm)...", 0, 0, DO_PaintCircle_mm); #if defined (macintosh) || defined (_WIN32) praat_addMenuCommand (L"Picture", L"World", L"-- picture --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"World", L"Insert picture from file...", 0, 0, DO_InsertPictureFromFile); #endif praat_addMenuCommand (L"Picture", L"World", L"-- axes --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"World", L"Axes...", 0, 0, DO_Axes); praat_addMenuCommand (L"Picture", L"World", L"Measure", 0, 0, 0); praat_addMenuCommand (L"Picture", L"World", L"Horizontal mm to wc...", 0, 1, DO_dxMMtoWC); praat_addMenuCommand (L"Picture", L"World", L"Horizontal wc to mm...", 0, 1, DO_dxWCtoMM); praat_addMenuCommand (L"Picture", L"World", L"Vertical mm to wc...", 0, 1, DO_dyMMtoWC); praat_addMenuCommand (L"Picture", L"World", L"Vertical wc to mm...", 0, 1, DO_dyWCtoMM); praat_addMenuCommand (L"Picture", L"World", L"-- text measure --", 0, 1, 0); praat_addMenuCommand (L"Picture", L"World", L"Text width (wc)...", 0, 1, DO_textWidth_wc); praat_addMenuCommand (L"Picture", L"World", L"Text width (mm)...", 0, 1, DO_textWidth_mm); praat_addMenuCommand (L"Picture", L"World", L"PostScript text width (wc)...", 0, 1, DO_textWidth_ps_wc); praat_addMenuCommand (L"Picture", L"World", L"PostScript text width (mm)...", 0, 1, DO_textWidth_ps_mm); praatButton_innerViewport = praat_addMenuCommand (L"Picture", L"Select", L"Mouse selects inner viewport", 0, praat_RADIO_FIRST, DO_MouseSelectsInnerViewport); praatButton_outerViewport = praat_addMenuCommand (L"Picture", L"Select", L"Mouse selects outer viewport", 0, praat_RADIO_NEXT, DO_MouseSelectsOuterViewport); praat_addMenuCommand (L"Picture", L"Select", L"-- select --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Select", L"Select inner viewport...", 0, 0, DO_SelectInnerViewport); praat_addMenuCommand (L"Picture", L"Select", L"Select outer viewport...", 0, 0, DO_SelectOuterViewport); praat_addMenuCommand (L"Picture", L"Select", L"Viewport...", 0, praat_HIDDEN, DO_SelectOuterViewport); praat_addMenuCommand (L"Picture", L"Select", L"-- viewport drawing --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Select", L"Viewport text...", 0, 0, DO_ViewportText); praatButton_lines [Graphics_DRAWN] = praat_addMenuCommand (L"Picture", L"Pen", L"Solid line", 0, praat_RADIO_FIRST, DO_Solid_line); praat_addMenuCommand (L"Picture", L"Pen", L"Plain line", 0, praat_RADIO_NEXT | praat_HIDDEN, DO_Solid_line); praatButton_lines [Graphics_DOTTED] = praat_addMenuCommand (L"Picture", L"Pen", L"Dotted line", 0, praat_RADIO_NEXT, DO_Dotted_line); praatButton_lines [Graphics_DASHED] = praat_addMenuCommand (L"Picture", L"Pen", L"Dashed line", 0, praat_RADIO_NEXT, DO_Dashed_line); praatButton_lines [Graphics_DASHED_DOTTED] = praat_addMenuCommand (L"Picture", L"Pen", L"Dashed-dotted line", 0, praat_RADIO_NEXT, DO_Dashed_dotted_line); praat_addMenuCommand (L"Picture", L"Pen", L"-- line width --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Pen", L"Line width...", 0, 0, DO_Line_width); praat_addMenuCommand (L"Picture", L"Pen", L"Arrow size...", 0, 0, DO_Arrow_size); praat_addMenuCommand (L"Picture", L"Pen", L"-- colour --", 0, 0, 0); praat_addMenuCommand (L"Picture", L"Pen", L"Colour...", 0, 0, DO_Colour); praatButton_black = praat_addMenuCommand (L"Picture", L"Pen", L"Black", 0, praat_CHECKBUTTON, DO_Black); praatButton_white = praat_addMenuCommand (L"Picture", L"Pen", L"White", 0, praat_CHECKBUTTON, DO_White); praatButton_red = praat_addMenuCommand (L"Picture", L"Pen", L"Red", 0, praat_CHECKBUTTON, DO_Red); praatButton_green = praat_addMenuCommand (L"Picture", L"Pen", L"Green", 0, praat_CHECKBUTTON, DO_Green); praatButton_blue = praat_addMenuCommand (L"Picture", L"Pen", L"Blue", 0, praat_CHECKBUTTON, DO_Blue); praatButton_yellow = praat_addMenuCommand (L"Picture", L"Pen", L"Yellow", 0, praat_CHECKBUTTON, DO_Yellow); praatButton_cyan = praat_addMenuCommand (L"Picture", L"Pen", L"Cyan", 0, praat_CHECKBUTTON, DO_Cyan); praatButton_magenta = praat_addMenuCommand (L"Picture", L"Pen", L"Magenta", 0, praat_CHECKBUTTON, DO_Magenta); praatButton_maroon = praat_addMenuCommand (L"Picture", L"Pen", L"Maroon", 0, praat_CHECKBUTTON, DO_Maroon); praatButton_lime = praat_addMenuCommand (L"Picture", L"Pen", L"Lime", 0, praat_CHECKBUTTON, DO_Lime); praatButton_navy = praat_addMenuCommand (L"Picture", L"Pen", L"Navy", 0, praat_CHECKBUTTON, DO_Navy); praatButton_teal = praat_addMenuCommand (L"Picture", L"Pen", L"Teal", 0, praat_CHECKBUTTON, DO_Teal); praatButton_purple = praat_addMenuCommand (L"Picture", L"Pen", L"Purple", 0, praat_CHECKBUTTON, DO_Purple); praatButton_olive = praat_addMenuCommand (L"Picture", L"Pen", L"Olive", 0, praat_CHECKBUTTON, DO_Olive); praatButton_pink = praat_addMenuCommand (L"Picture", L"Pen", L"Pink", 0, praat_CHECKBUTTON, DO_Pink); praatButton_silver = praat_addMenuCommand (L"Picture", L"Pen", L"Silver", 0, praat_CHECKBUTTON, DO_Silver); praatButton_grey = praat_addMenuCommand (L"Picture", L"Pen", L"Grey", 0, praat_CHECKBUTTON, DO_Grey); praat_addMenuCommand (L"Picture", L"Font", L"Font size...", 0, 0, DO_Font_size); praatButton_10 = praat_addMenuCommand (L"Picture", L"Font", L"10", 0, praat_CHECKBUTTON, DO_10); praatButton_12 = praat_addMenuCommand (L"Picture", L"Font", L"12", 0, praat_CHECKBUTTON, DO_12); praatButton_14 = praat_addMenuCommand (L"Picture", L"Font", L"14", 0, praat_CHECKBUTTON, DO_14); praatButton_18 = praat_addMenuCommand (L"Picture", L"Font", L"18", 0, praat_CHECKBUTTON, DO_18); praatButton_24 = praat_addMenuCommand (L"Picture", L"Font", L"24", 0, praat_CHECKBUTTON, DO_24); praat_addMenuCommand (L"Picture", L"Font", L"-- font ---", 0, 0, 0); praatButton_fonts [kGraphics_font_TIMES] = praat_addMenuCommand (L"Picture", L"Font", L"Times", 0, praat_RADIO_FIRST, DO_Times); praatButton_fonts [kGraphics_font_HELVETICA] = praat_addMenuCommand (L"Picture", L"Font", L"Helvetica", 0, praat_RADIO_NEXT, DO_Helvetica); praatButton_fonts [kGraphics_font_PALATINO] = praat_addMenuCommand (L"Picture", L"Font", L"Palatino", 0, praat_RADIO_NEXT, DO_Palatino); praatButton_fonts [kGraphics_font_COURIER] = praat_addMenuCommand (L"Picture", L"Font", L"Courier", 0, praat_RADIO_NEXT, DO_Courier); praat_addMenuCommand (L"Picture", L"Help", L"Picture window help", 0, '?', DO_PictureWindowHelp); praat_addMenuCommand (L"Picture", L"Help", L"About special symbols", 0, 0, DO_AboutSpecialSymbols); praat_addMenuCommand (L"Picture", L"Help", L"About text styles", 0, 0, DO_AboutTextStyles); praat_addMenuCommand (L"Picture", L"Help", L"Phonetic symbols", 0, 0, DO_PhoneticSymbols); praat_addMenuCommand (L"Picture", L"Help", L"-- manual --", 0, 0, 0); MelderString_empty (& itemTitle_search); MelderString_append (& itemTitle_search, L"Search ", Melder_peekUtf8ToWcs (praatP.title), L" manual..."); praat_addMenuCommand (L"Picture", L"Help", itemTitle_search.string, 0, 'M', DO_SearchManual); if (! theCurrentPraatApplication -> batch) { width = height = resolution * 12; #if gtk // TODO: GuiScrollWindow scrollWindow = gtk_scrolled_window_new (NULL, NULL); gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrollWindow), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); #elif motif XtManageChild (menuBar); #if defined (macintosh) || defined (_WIN32) scrollWindow = XmCreateScrolledWindow (dialog, "scrolledWindow", NULL, 0); XtVaSetValues (scrollWindow, XmNleftAttachment, XmATTACH_FORM, XmNleftOffset, margin, XmNrightAttachment, XmATTACH_FORM, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, Machine_getMenuBarHeight () + margin, XmNbottomAttachment, XmATTACH_FORM, NULL); #else scrollWindow = XtVaCreateWidget ( "scrolledWindow", xmScrolledWindowWidgetClass, dialog, XmNscrollingPolicy, XmAUTOMATIC, XmNrightAttachment, XmATTACH_FORM, XmNbottomAttachment, XmATTACH_FORM, XmNleftAttachment, XmATTACH_FORM, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, Machine_getMenuBarHeight (), NULL); #endif #endif #if gtk drawingArea = GuiDrawingArea_create (scrollWindow, 0, width, 0, height, NULL, NULL, NULL, NULL, NULL, 0); gtk_scrolled_window_add_with_viewport (GTK_SCROLLED_WINDOW (scrollWindow), GTK_WIDGET (drawingArea)); gtk_container_add (GTK_CONTAINER (dialog), GTK_WIDGET (scrollWindow)); GuiObject_show (menuBar); GuiObject_show (drawingArea); #elif motif drawingArea = GuiDrawingArea_createShown (scrollWindow, 0, width, 0, height, NULL, NULL, NULL, NULL, NULL, 0); #endif GuiObject_show (scrollWindow); GuiObject_show (dialog); } // TODO: Paul: deze moet VOOR de update functies anders krijgen die void_me 0x0 praat_picture = Picture_create (drawingArea, ! theCurrentPraatApplication -> batch); // READ THIS! Picture_setSelectionChangedCallback (praat_picture, cb_selectionChanged, NULL); theCurrentPraatPicture -> graphics = static_cast (Picture_getGraphics (praat_picture)); updatePenMenu (); updateFontMenu (); updateSizeMenu (); updateViewportMenu (); } void praat_picture_prefsChanged (void) { updateFontMenu (); updateSizeMenu (); updateViewportMenu (); Graphics_setFontSize (theCurrentPraatPicture -> graphics, theCurrentPraatPicture -> fontSize); /* So that the thickness of the selection rectangle is correct. */ Picture_setMouseSelectsInnerViewport (praat_picture, praat_mouseSelectsInnerViewport); } void praat_picture_background (void) { /*praat_picture_open (); Picture_background (praat_picture);*/ } void praat_picture_foreground (void) { /*praat_picture_close (); Picture_foreground (praat_picture);*/ } /* End of file praat_picture.c */ sources_5316/sys/GuiDrawingArea.cpp0000644000176700017670000003753611753741756016134 0ustar paulpaul/* GuiDrawingArea.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/28 extracted from Motif * sdk 2008/03/24 GTK * sdk 2008/07/01 GTK resize callback * fb 2010/02/23 GTK * pb 2010/07/13 GTK key event * pb 2010/11/28 removed Motif * pb 2011/04/06 C++ * pb 2011/06/05 all callbacks protected against exceptions */ #include "GuiP.h" #if gtk #include "gdk/gdkkeysyms.h" #endif #undef iam #define iam(x) x me = (x) void_me #if win || mac #define iam_drawingarea \ Melder_assert (widget -> widgetClass == xmDrawingAreaWidgetClass); \ GuiDrawingArea me = (GuiDrawingArea) widget -> userData #else #define iam_drawingarea \ GuiDrawingArea me = (GuiDrawingArea) _GuiObject_getUserData (widget) #endif typedef struct structGuiDrawingArea { GuiObject widget; void (*exposeCallback) (void *boss, GuiDrawingAreaExposeEvent event); void *exposeBoss; void (*clickCallback) (void *boss, GuiDrawingAreaClickEvent event); void *clickBoss; void (*keyCallback) (void *boss, GuiDrawingAreaKeyEvent event); void *keyBoss; void (*resizeCallback) (void *boss, GuiDrawingAreaResizeEvent event); void *resizeBoss; } *GuiDrawingArea; #if gtk static void _GuiGtkDrawingArea_destroyCallback (GuiObject widget, gpointer void_me) { (void) widget; iam (GuiDrawingArea); Melder_free (me); } // static void _GuiGtkDrawingArea_activateCallback (GtkAction *action, gpointer void_me) { //iam (GuiDrawingArea); // TODO: compliled niet /* struct structGuiDrawingAreaEvent event = { widget, 0 }; if (my activateCallback != NULL) { my activateCallback (my activateBoss, & event); }*/ // } static gboolean _GuiGtkDrawingArea_exposeCallback (GuiObject widget, GdkEventExpose *expose, gpointer void_me) { iam (GuiDrawingArea); // TODO: that helps agains the damaged regions outside the rect where the // Graphics drawing is done, but where does that margin come from in the // first place?? Additionally this causes even more flickering //gdk_window_clear_area(widget->window, expose->area.x, expose->area.y, expose->area.width, expose->area.height); if (my exposeCallback) { struct structGuiDrawingAreaExposeEvent event = { widget, 0 }; event. x = expose -> area. x; event. y = expose -> area. y; event. width = expose -> area. width; event. height = expose -> area. height; try { my exposeCallback (my exposeBoss, & event); } catch (MelderError) { Melder_flushError ("Redrawing not completed"); } return TRUE; // let the expose callback handle redrawing } return FALSE; // let GTK+ handle redrawing } static gboolean _GuiGtkDrawingArea_clickCallback (GuiObject widget, GdkEvent *e, gpointer void_me) { iam (GuiDrawingArea); if (my clickCallback) { struct structGuiDrawingAreaClickEvent event = { widget, 0 }; //Melder_casual("event type %ld", (long)e->type); switch (e -> type) { case GDK_BUTTON_PRESS: event. type = BUTTON_PRESS; event. button = ((GdkEventButton *) e) -> button; break; case GDK_BUTTON_RELEASE: event. type = BUTTON_RELEASE; event. button = ((GdkEventButton *) e) -> button; break; case GDK_MOTION_NOTIFY: event. type = MOTION_NOTIFY; event. button = ((GdkEventMotion *) e) -> state & GDK_BUTTON1_MASK ? 1 : ((GdkEventMotion *) e) -> state & GDK_BUTTON2_MASK ? 2 : ((GdkEventMotion *) e) -> state & GDK_BUTTON3_MASK ? 3 : ((GdkEventMotion *) e) -> state & GDK_BUTTON4_MASK ? 4 : ((GdkEventMotion *) e) -> state & GDK_BUTTON5_MASK ? 5 : 0; break; default: // Do NOTHING return FALSE; } event. x = ((GdkEventButton *) e) -> x; event. y = ((GdkEventButton *) e) -> y; event. shiftKeyPressed = (((GdkEventButton *) e) -> state & GDK_SHIFT_MASK) != 0; if (e -> type == GDK_BUTTON_PRESS || 1) { try { my clickCallback (my clickBoss, & event); } catch (MelderError) { Melder_flushError ("Mouse click not completely handled."); } return TRUE; } } return FALSE; } static gboolean _GuiGtkDrawingArea_keyCallback (GuiObject widget, GdkEvent *gevent, gpointer void_me) { iam (GuiDrawingArea); //Melder_casual ("_GuiGtkDrawingArea_keyCallback"); if (my keyCallback && gevent -> type == GDK_KEY_PRESS) { struct structGuiDrawingAreaKeyEvent event = { widget, 0 }; GdkEventKey *gkeyEvent = (GdkEventKey *) gevent; event. key = gkeyEvent -> keyval; /* * Translate with the help of /usr/include/gtk-2.0/gdk/gdkkeysyms.h */ if (event. key == GDK_Escape) event. key = 27; if (event. key == GDK_Left) event. key = 0x2190; if (event. key == GDK_Up) event. key = 0x2191; if (event. key == GDK_Right) event. key = 0x2192; if (event. key == GDK_Down) event. key = 0x2193; event. shiftKeyPressed = (gkeyEvent -> state & GDK_SHIFT_MASK) != 0; event. commandKeyPressed = (gkeyEvent -> state & GDK_CONTROL_MASK) != 0; event. optionKeyPressed = (gkeyEvent -> state & GDK_MOD1_MASK) != 0; event. extraControlKeyPressed = false; try { my keyCallback (my keyBoss, & event); } catch (MelderError) { Melder_flushError ("Key press not completely handled."); } /* * FIXME: here we should empty the type-ahead buffer */ return TRUE; } return FALSE; // if the drawing area has no keyCallback, the system will send the key press to a text field. } static gboolean _GuiGtkDrawingArea_resizeCallback (GuiObject widget, GtkAllocation *allocation, gpointer void_me) { iam (GuiDrawingArea); if (my resizeCallback) { struct structGuiDrawingAreaResizeEvent event = { widget, 0 }; event. width = allocation -> width; event. height = allocation -> height; //g_debug("%d %d", allocation->width, allocation->height); try { my resizeCallback (my clickBoss, & event); } catch (MelderError) { Melder_flushError ("Window resizing not completely handled."); } return TRUE; } return FALSE; } #elif win void _GuiWinDrawingArea_destroy (GuiObject widget) { iam_drawingarea; DestroyWindow (widget -> window); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiWinDrawingArea_update (GuiObject widget) { iam_drawingarea; PAINTSTRUCT paintStruct; BeginPaint (widget -> window, & paintStruct); if (my exposeCallback) { struct structGuiDrawingAreaExposeEvent event = { widget }; try { my exposeCallback (my exposeBoss, & event); } catch (MelderError) { Melder_flushError ("Redrawing not completed"); } } EndPaint (widget -> window, & paintStruct); } void _GuiWinDrawingArea_handleClick (GuiObject widget, int x, int y) { iam_drawingarea; if (my clickCallback) { struct structGuiDrawingAreaClickEvent event = { widget, 0 }; event. x = x; event. y = y; event. shiftKeyPressed = GetKeyState (VK_SHIFT) < 0; try { my clickCallback (my clickBoss, & event); } catch (MelderError) { Melder_flushError ("Mouse click not completely handled."); } } } void _GuiWinDrawingArea_handleKey (GuiObject widget, TCHAR kar) { // TODO: event? iam_drawingarea; if (my keyCallback) { struct structGuiDrawingAreaKeyEvent event = { widget, 0 }; event. key = kar; if (event. key == VK_LEFT) event. key = 0x2190; if (event. key == VK_RIGHT) event. key = 0x2192; if (event. key == VK_UP) event. key = 0x2191; if (event. key == VK_DOWN) event. key = 0x2193; event. shiftKeyPressed = GetKeyState (VK_SHIFT) < 0; // TODO: event -> key? try { my keyCallback (my keyBoss, & event); } catch (MelderError) { Melder_flushError ("Key press not completely handled."); } } } void _GuiWinDrawingArea_shellResize (GuiObject widget) { iam_drawingarea; if (my resizeCallback) { struct structGuiDrawingAreaResizeEvent event = { widget }; event. width = widget -> width; event. height = widget -> height; try { my resizeCallback (my resizeBoss, & event); } catch (MelderError) { Melder_flushError ("Window resizing not completely handled."); } } } #elif mac #if useCarbon void _GuiMacDrawingArea_destroy (GuiObject widget) { iam_drawingarea; Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiMacDrawingArea_update (GuiObject widget) { iam_drawingarea; if (my exposeCallback) { struct structGuiDrawingAreaExposeEvent event = { widget }; _GuiMac_clipOnParent (widget); try { my exposeCallback (my exposeBoss, & event); } catch (MelderError) { Melder_flushError ("Redrawing not completed"); } GuiMac_clipOff (); } } void _GuiMacDrawingArea_handleClick (GuiObject widget, EventRecord *macEvent) { iam_drawingarea; if (my clickCallback) { struct structGuiDrawingAreaClickEvent event = { widget, 0 }; event. x = macEvent -> where. h; event. y = macEvent -> where. v; event. shiftKeyPressed = (macEvent -> modifiers & shiftKey) != 0; event. commandKeyPressed = (macEvent -> modifiers & cmdKey) != 0; event. optionKeyPressed = (macEvent -> modifiers & optionKey) != 0; event. extraControlKeyPressed = (macEvent -> modifiers & controlKey) != 0; try { my clickCallback (my clickBoss, & event); } catch (MelderError) { Melder_flushError ("Mouse click not completely handled."); } } } bool _GuiMacDrawingArea_tryToHandleKey (GuiObject widget, EventRecord *macEvent) { iam_drawingarea; if (my keyCallback) { struct structGuiDrawingAreaKeyEvent event = { widget, 0 }; event. key = macEvent -> message & charCodeMask; if (event. key == 28) event. key = 0x2190; if (event. key == 29) event. key = 0x2192; if (event. key == 30) event. key = 0x2191; if (event. key == 31) event. key = 0x2193; event. shiftKeyPressed = (macEvent -> modifiers & shiftKey) != 0; event. commandKeyPressed = (macEvent -> modifiers & cmdKey) != 0; event. optionKeyPressed = (macEvent -> modifiers & optionKey) != 0; event. extraControlKeyPressed = (macEvent -> modifiers & controlKey) != 0; try { my keyCallback (my keyBoss, & event); } catch (MelderError) { Melder_flushError ("Key press not completely handled."); } return true; } return false; } void _GuiMacDrawingArea_shellResize (GuiObject widget) { iam_drawingarea; if (my resizeCallback) { struct structGuiDrawingAreaResizeEvent event = { widget, 0 }; event. width = widget -> width; event. height = widget -> height; try { my resizeCallback (my resizeBoss, & event); } catch (MelderError) { Melder_flushError ("Window resizing not completely handled."); } } } #else #endif #endif GuiObject GuiDrawingArea_create (GuiObject parent, int left, int right, int top, int bottom, void (*exposeCallback) (void *boss, GuiDrawingAreaExposeEvent event), void (*clickCallback) (void *boss, GuiDrawingAreaClickEvent event), void (*keyCallback) (void *boss, GuiDrawingAreaKeyEvent event), void (*resizeCallback) (void *boss, GuiDrawingAreaResizeEvent event), void *boss, unsigned long flags) { GuiDrawingArea me = Melder_calloc_f (struct structGuiDrawingArea, 1); my exposeCallback = exposeCallback; my exposeBoss = boss; my clickCallback = clickCallback; my clickBoss = boss; my keyCallback = keyCallback; my keyBoss = boss; my resizeCallback = resizeCallback; my resizeBoss = boss; #if gtk my widget = gtk_drawing_area_new (); GdkEventMask mask = (GdkEventMask) (GDK_EXPOSURE_MASK // receive exposure events | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK // receive click events | GDK_BUTTON_MOTION_MASK // receive motion notifies when a button is pressed | GDK_KEY_PRESS_MASK | GDK_KEY_RELEASE_MASK | GDK_POINTER_MOTION_HINT_MASK); // receive fewer motion notify events (the cb might take time) gtk_widget_set_events (GTK_WIDGET (my widget), mask); // TODO: maybe make this a composite widget and use connect_after for expose? // see http://library.gnome.org/devel/gdk/stable/gdk-Windows.html#COMPOSITED-WINDOWS g_signal_connect (G_OBJECT(my widget), "expose-event", G_CALLBACK (_GuiGtkDrawingArea_exposeCallback), me); g_signal_connect (G_OBJECT (my widget), "destroy", G_CALLBACK (_GuiGtkDrawingArea_destroyCallback), me); g_signal_connect (G_OBJECT (my widget), "button-press-event", G_CALLBACK (_GuiGtkDrawingArea_clickCallback), me); g_signal_connect (G_OBJECT (my widget), "button-release-event", G_CALLBACK (_GuiGtkDrawingArea_clickCallback), me); g_signal_connect (G_OBJECT (my widget), "motion-notify-event", G_CALLBACK (_GuiGtkDrawingArea_clickCallback), me); if (parent != NULL) { g_signal_connect (G_OBJECT (gtk_widget_get_toplevel (GTK_WIDGET (parent))), "key-press-event", G_CALLBACK (_GuiGtkDrawingArea_keyCallback), me); } g_signal_connect (G_OBJECT (my widget), "size-allocate", G_CALLBACK (_GuiGtkDrawingArea_resizeCallback), me); // g_signal_connect (GTK_WIDGET (my widget), "activate", // G_CALLBACK (_GuiGtkDrawingArea_activateCallback), me); /* // Positioning is done by the container this widget gets child of // For a container allowing positioning by pixel coordinates, see GtkFixed, // but it is not as flexible as a typical layout (*box, table, etc.) // _GuiObject_position (my widget, left, right, top, bottom); */ _GuiObject_setUserData (my widget, me); GuiObject_size (my widget, right - left, bottom - top); #elif win my widget = _Gui_initializeWidget (xmDrawingAreaWidgetClass, parent, L"drawingArea"); _GuiObject_setUserData (my widget, me); my widget -> window = CreateWindowEx (0, _GuiWin_getDrawingAreaClassName (), L"drawingArea", WS_CHILD | WS_BORDER | WS_CLIPSIBLINGS, my widget -> x, my widget -> y, my widget -> width, my widget -> height, my widget -> parent -> window, NULL, theGui.instance, NULL); SetWindowLongPtr (my widget -> window, GWLP_USERDATA, (LONG_PTR) my widget); _GuiObject_position (my widget, left, right, top, bottom); #elif mac #if useCarbon my widget = _Gui_initializeWidget (xmDrawingAreaWidgetClass, parent, L"drawingArea"); _GuiObject_setUserData (my widget, me); _GuiObject_position (my widget, left, right, top, bottom); #else #endif #endif return my widget; } GuiObject GuiDrawingArea_createShown (GuiObject parent, int left, int right, int top, int bottom, void (*exposeCallback) (void *boss, GuiDrawingAreaExposeEvent event), void (*clickCallback) (void *boss, GuiDrawingAreaClickEvent event), void (*keyCallback) (void *boss, GuiDrawingAreaKeyEvent event), void (*resizeCallback) (void *boss, GuiDrawingAreaResizeEvent event), void *boss, unsigned long flags) { GuiObject me = GuiDrawingArea_create (parent, left, right, top, bottom, exposeCallback, clickCallback, keyCallback, resizeCallback, boss, flags); #if gtk gtk_container_add (GTK_CONTAINER (parent), GTK_WIDGET (me)); #endif GuiObject_show (me); return me; } void GuiDrawingArea_setExposeCallback (GuiObject widget, void (*callback) (void *boss, GuiDrawingAreaExposeEvent event), void *boss) { GuiDrawingArea me = (GuiDrawingArea) _GuiObject_getUserData (widget); if (me != NULL) { my exposeCallback = callback; my exposeBoss = boss; } } void GuiDrawingArea_setClickCallback (GuiObject widget, void (*callback) (void *boss, GuiDrawingAreaClickEvent event), void *boss) { GuiDrawingArea me = (GuiDrawingArea) _GuiObject_getUserData (widget); if (me != NULL) { my clickCallback = callback; my clickBoss = boss; } } /* End of file GuiDrawingArea.cpp */ sources_5316/sys/GuiButton.cpp0000644000176700017670000002275711753741756015222 0ustar paulpaul/* GuiButton.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb & sdk 2007/12/25 gtk * fb 2010/02/23 GTK * pb 2010/06/14 HandleControlClick * pb 2010/08/10 removed Motif * pb 2011/02/07 GuiButton_ATTRACTIVE * pb 2011/04/06 C++ */ #include "GuiP.h" #undef iam #define iam(x) x me = (x) void_me #if win || mac #define iam_button \ Melder_assert (widget -> widgetClass == xmPushButtonWidgetClass); \ GuiButton me = (GuiButton) widget -> userData #else #define iam_button \ GuiButton me = (GuiButton) _GuiObject_getUserData (widget) #endif typedef struct structGuiButton { GuiObject widget; void (*activateCallback) (void *boss, GuiButtonEvent event); void *activateBoss; } *GuiButton; #if gtk static void _GuiGtkButton_destroyCallback (GuiObject widget, gpointer void_me) { (void) widget; iam (GuiButton); Melder_free (me); } static void _GuiGtkButton_activateCallback (GuiObject widget, gpointer void_me) { iam (GuiButton); struct structGuiButtonEvent event = { widget, 0 }; if (my activateCallback != NULL) { try { my activateCallback (my activateBoss, & event); } catch (MelderError) { Melder_error_ ("Your click on button \"", GTK_WIDGET (widget) -> name, "\" was not completely handled."); Melder_flushError (NULL); } } } #elif win void _GuiWinButton_destroy (GuiObject widget) { iam_button; if (widget == widget -> shell -> defaultButton) widget -> shell -> defaultButton = NULL; // remove dangling reference if (widget == widget -> shell -> cancelButton) widget -> shell -> cancelButton = NULL; // remove dangling reference _GuiNativeControl_destroy (widget); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiWinButton_handleClick (GuiObject widget) { iam_button; if (my activateCallback != NULL) { struct structGuiButtonEvent event = { widget, 0 }; try { my activateCallback (my activateBoss, & event); } catch (MelderError) { Melder_error_ ("Your click on button \"", widget -> name, "\" was not completely handled."); Melder_flushError (NULL); } } } bool _GuiWinButton_tryToHandleShortcutKey (GuiObject widget) { iam_button; if (my activateCallback != NULL) { struct structGuiButtonEvent event = { widget, 0 }; try { my activateCallback (my activateBoss, & event); } catch (MelderError) { Melder_error_ ("Your click on button \"", widget -> name, "\" was not completely handled."); Melder_flushError (NULL); } return true; } return false; } #elif mac #if useCarbon void _GuiMacButton_destroy (GuiObject widget) { iam_button; if (widget == widget -> shell -> defaultButton) widget -> shell -> defaultButton = NULL; // remove dangling reference if (widget == widget -> shell -> cancelButton) widget -> shell -> cancelButton = NULL; // remove dangling reference _GuiNativeControl_destroy (widget); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiMacButton_handleClick (GuiObject widget, EventRecord *macEvent) { iam_button; _GuiMac_clipOnParent (widget); bool pushed = HandleControlClick (widget -> nat.control.handle, macEvent -> where, macEvent -> modifiers, NULL); GuiMac_clipOff (); if (pushed && my activateCallback != NULL) { struct structGuiButtonEvent event = { widget, 0 }; //enum { cmdKey = 256, shiftKey = 512, optionKey = 2048, controlKey = 4096 }; Melder_assert (macEvent -> what == mouseDown); event. shiftKeyPressed = (macEvent -> modifiers & shiftKey) != 0; event. commandKeyPressed = (macEvent -> modifiers & cmdKey) != 0; event. optionKeyPressed = (macEvent -> modifiers & optionKey) != 0; event. extraControlKeyPressed = (macEvent -> modifiers & controlKey) != 0; try { my activateCallback (my activateBoss, & event); } catch (MelderError) { Melder_error_ ("Your click on button \"", widget -> name, "\" was not completely handled."); Melder_flushError (NULL); } } } bool _GuiMacButton_tryToHandleShortcutKey (GuiObject widget, EventRecord *macEvent) { iam_button; if (my activateCallback != NULL) { struct structGuiButtonEvent event = { widget, 0 }; // ignore modifier keys for Enter try { my activateCallback (my activateBoss, & event); } catch (MelderError) { Melder_error_ ("Your click on button \"", widget -> name, "\" was not completely handled."); Melder_flushError (NULL); } return true; } return false; } #else #endif #endif GuiObject GuiButton_create (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*activateCallback) (void *boss, GuiButtonEvent event), void *activateBoss, unsigned long flags) { GuiButton me = Melder_calloc_f (struct structGuiButton, 1); my activateCallback = activateCallback; my activateBoss = activateBoss; #if gtk my widget = gtk_button_new_with_label (Melder_peekWcsToUtf8 (buttonText)); _GuiObject_setUserData (my widget, me); // _GuiObject_position (my widget, left, right, top, bottom); // TODO: use gtk_box_pack_start(GTK_BOX(parent), my widget, FALSE, FALSE, ?) if (parent) gtk_container_add (GTK_CONTAINER (parent), GTK_WIDGET (my widget)); if (flags & GuiButton_DEFAULT || flags & GuiButton_ATTRACTIVE) { GTK_WIDGET_SET_FLAGS (my widget, GTK_CAN_DEFAULT); GtkWidget *shell = gtk_widget_get_toplevel (GTK_WIDGET (my widget)); gtk_window_set_default (GTK_WINDOW (shell), GTK_WIDGET (my widget)); } else if (1) { gtk_button_set_focus_on_click (GTK_BUTTON (my widget), false); GTK_WIDGET_UNSET_FLAGS (my widget, GTK_CAN_DEFAULT); } g_signal_connect (G_OBJECT (my widget), "destroy", G_CALLBACK (_GuiGtkButton_destroyCallback), me); g_signal_connect (GTK_BUTTON (my widget), "clicked", G_CALLBACK (_GuiGtkButton_activateCallback), me); // if (flags & GuiButton_CANCEL) { // parent -> shell -> cancelButton = parent -> cancelButton = my widget; // } #elif win my widget = _Gui_initializeWidget (xmPushButtonWidgetClass, parent, buttonText); _GuiObject_setUserData (my widget, me); my widget -> window = CreateWindow (L"button", _GuiWin_expandAmpersands (my widget -> name), WS_CHILD | ( flags & (GuiButton_DEFAULT | GuiButton_ATTRACTIVE) ? BS_DEFPUSHBUTTON : BS_PUSHBUTTON ) | WS_CLIPSIBLINGS, my widget -> x, my widget -> y, my widget -> width, my widget -> height, my widget -> parent -> window, (HMENU) 1, theGui.instance, NULL); SetWindowLongPtr (my widget -> window, GWLP_USERDATA, (LONG_PTR) my widget); SetWindowFont (my widget -> window, GetStockFont (ANSI_VAR_FONT), FALSE); _GuiObject_position (my widget, left, right, top, bottom); if (flags & GuiButton_DEFAULT || flags & GuiButton_ATTRACTIVE) { parent -> shell -> defaultButton = parent -> defaultButton = my widget; } if (flags & GuiButton_CANCEL) { parent -> shell -> cancelButton = parent -> cancelButton = my widget; } #elif mac #if useCarbon my widget = _Gui_initializeWidget (xmPushButtonWidgetClass, parent, buttonText); _GuiObject_setUserData (my widget, me); CreatePushButtonControl (my widget -> macWindow, & my widget -> rect, NULL, & my widget -> nat.control.handle); Melder_assert (my widget -> nat.control.handle != NULL); SetControlReference (my widget -> nat.control.handle, (long) my widget); my widget -> isControl = true; _GuiNativeControl_setFont (my widget, flags & GuiButton_ATTRACTIVE ? /*1*/0 : 0, 13); _GuiNativeControl_setTitle (my widget); _GuiObject_position (my widget, left, right, top, bottom); if (flags & GuiButton_DEFAULT || flags & GuiButton_ATTRACTIVE) { parent -> shell -> defaultButton = parent -> defaultButton = my widget; Boolean set = true; SetControlData (my widget -> nat.control.handle, kControlEntireControl, kControlPushButtonDefaultTag, sizeof (Boolean), & set); } if (flags & GuiButton_CANCEL) { parent -> shell -> cancelButton = parent -> cancelButton = my widget; } #else #endif #endif if (flags & GuiButton_INSENSITIVE) { GuiObject_setSensitive (my widget, false); } return my widget; } GuiObject GuiButton_createShown (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*clickedCallback) (void *boss, GuiButtonEvent event), void *clickedBoss, unsigned long flags) { GuiObject me = GuiButton_create (parent, left, right, top, bottom, buttonText, clickedCallback, clickedBoss, flags); GuiObject_show (me); return me; } void GuiButton_setString (GuiObject widget, const wchar_t *text) { #if gtk gtk_button_set_label (GTK_BUTTON (widget), Melder_peekWcsToUtf8 (text)); #elif win Melder_free (widget -> name); widget -> name = Melder_wcsdup_f (text); _GuiNativeControl_setTitle (widget); #elif mac #if useCarbon Melder_free (widget -> name); widget -> name = Melder_wcsdup_f (text); _GuiNativeControl_setTitle (widget); #else #endif #endif } /* End of file GuiButton.cpp */ sources_5316/sys/Graphics_text.cpp0000644000176700017670000022600511752473263016070 0ustar paulpaul/* Graphics_text.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2004/01/28 Windows: for PostScript, download Times New Roman instead of Times * pb 2004/02/02 Windows: my metafile instead of my printer for high resolution in metafiles and clipboards * pb 2004/02/04 EPS files: secondary fonts * pb 2004/03/13 EPS files: secondary font for Palatino as well * pb 2004/08/20 Windows EPS files: if "include fonts" is off, take SILDoulosIPA rather than SILDoulosIPA-Regular * pb 2004/10/24 better slant correction * pb 2004/11/28 Melder_debug == 15 to force bitmapped IPA * pb 2004/12/02 Linux: xipa support * pb 2005/02/03 TeX-xipa10-Praat-Regular * pb 2005/03/08 psEncoding; SILIPA93 encoding for Windows and Mac * pb 2005/03/15 find PostScript Courier with -p- * pb 2005/09/18 useSilipaPS, including bold * pb 2005/10/27 corrected character width for Symbol (should not depend on SILIPA setting) * pb 2005/11/11 Windows: font sizes up to 500 * pb 2006/10/20 links are recorded in DC (no longer WC) * pb 2007/06/11 wchar_t * pb 2007/08/01 reintroduced yIsZeroAtTheTop * pb 2007/08/25 use Charis SIL or Doulos SIL rather than SILDoulos IPA93 * pb 2007/09/29 correct counting of UTF-8 bytes * pb 2007/12/09 enums * pb 2008/03/24 cairo * pb 2009/03/14 switched kerning off * pb 2009/09/17 made Quartz part resistant against missing QuickDraw IPA font * pb 2010/05/13 support for XOR mode via GDK * pb 2010/06/29 Mac: handle missing phonetic fonts better * pb 2010/07/13 cairo: rotated text * pb 2011/03/17 C++ */ #include #include "UnicodeData.h" #include "GraphicsP.h" #include "longchar.h" #include "Printer.h" extern const char * ipaSerifRegularPS []; extern const char * ipaSerifRegular24 [1 + 255-33+1 + 1] [24 + 1]; /* * When computing the width of a text by adding the widths of the separate characters, * we will make a correction for systems that make slanted characters overlap the character box to their right. * The effect is especially strong on Mac (older versions). * The slant correction is taken relative to the font size. */ #define POSTSCRIPT_SLANT_CORRECTION 0.1 #define SLANT_CORRECTION POSTSCRIPT_SLANT_CORRECTION /* * The Praat PostScript and the Mac character encodings have fi and fl ligature symbols. * The ISO8859-1 character encoding, which is used on Xwin and Win, has not. */ #if mac #define HAS_FI_AND_FL_LIGATURES TRUE #else #define HAS_FI_AND_FL_LIGATURES ( my postScript == TRUE ) #endif #if win #define win_MAXIMUM_FONT_SIZE 500 static HFONT screenFonts [1 + kGraphics_font_DINGBATS] [1+win_MAXIMUM_FONT_SIZE] [1 + Graphics_BOLD_ITALIC]; static HFONT printerFonts [1 + kGraphics_font_DINGBATS] [1+win_MAXIMUM_FONT_SIZE] [1 + Graphics_BOLD_ITALIC]; static int ipaAvailable = FALSE; static int win_size2isize (int size) { return size > win_MAXIMUM_FONT_SIZE ? win_MAXIMUM_FONT_SIZE : size; } static int win_isize2size (int isize) { return isize; } #elif mac #include "macport_on.h" #include #include #include #include "macport_off.h" static ATSFontRef theTimesAtsuiFont, theHelveticaAtsuiFont, theCourierAtsuiFont, theSymbolAtsuiFont, thePalatinoAtsuiFont, theIpaTimesAtsuiFont, theIpaPalatinoAtsuiFont, theZapfDingbatsAtsuiFont, theArabicAtsuiFont; static RGBColor theWhiteColour = { 0xFFFF, 0xFFFF, 0xFFFF }, theBlueColour = { 0, 0, 0xFFFF }; #endif #if win static bool charisAvailable = false, doulosAvailable = false; static int CALLBACK fontFuncEx_charis (const LOGFONTW *oldLogFont, const TEXTMETRICW *oldTextMetric, unsigned long fontType, LPARAM lparam) { const LPENUMLOGFONTW logFont = (LPENUMLOGFONTW) oldLogFont; (void) oldTextMetric; (void) fontType; (void) lparam; charisAvailable = TRUE; return 1; } static int CALLBACK fontFuncEx_doulos (const LOGFONTW *oldLogFont, const TEXTMETRICW *oldTextMetric, unsigned long fontType, LPARAM lparam) { const LPENUMLOGFONTW logFont = (LPENUMLOGFONTW) oldLogFont; (void) oldTextMetric; (void) fontType; (void) lparam; doulosAvailable = TRUE; return 1; } static HFONT loadFont (GraphicsScreen me, int font, int size, int style) { LOGFONTW spec; static int ipaInited; if (my printer || my metafile) { spec. lfHeight = - win_isize2size (size) * my resolution / 72.0; } else { spec. lfHeight = - win_isize2size (size) * my resolution / 72.0; } spec. lfWidth = 0; spec. lfEscapement = spec. lfOrientation = 0; spec. lfWeight = style & Graphics_BOLD ? FW_BOLD : 0; spec. lfItalic = style & Graphics_ITALIC ? 1 : 0; spec. lfUnderline = spec. lfStrikeOut = 0; spec. lfCharSet = font == kGraphics_font_SYMBOL ? SYMBOL_CHARSET : font >= kGraphics_font_IPATIMES ? DEFAULT_CHARSET : ANSI_CHARSET; spec. lfOutPrecision = spec. lfClipPrecision = spec. lfQuality = 0; spec. lfPitchAndFamily = ( font == kGraphics_font_COURIER ? FIXED_PITCH : font == kGraphics_font_IPATIMES ? DEFAULT_PITCH : VARIABLE_PITCH ) | ( font == kGraphics_font_HELVETICA ? FF_SWISS : font == kGraphics_font_COURIER ? FF_MODERN : font >= kGraphics_font_IPATIMES ? FF_DONTCARE : FF_ROMAN ); if (font == kGraphics_font_IPATIMES && ! ipaInited && Melder_debug != 15) { LOGFONTW logFont; logFont. lfCharSet = DEFAULT_CHARSET; logFont. lfPitchAndFamily = 0; wcscpy (logFont. lfFaceName, L"Charis SIL"); EnumFontFamiliesExW (my d_gdiGraphicsContext, & logFont, fontFuncEx_charis, 0, 0); wcscpy (logFont. lfFaceName, L"Doulos SIL"); EnumFontFamiliesExW (my d_gdiGraphicsContext, & logFont, fontFuncEx_doulos, 0, 0); ipaInited = TRUE; if (! charisAvailable && ! doulosAvailable) { /* BUG: The next warning may cause reentry of drawing (on window exposure) and lead to crash. Some code must be non-reentrant !! */ Melder_warning (L"The phonetic font is not available.\nSeveral characters will not look correct.\nSee www.praat.org"); } else { ipaAvailable = true; } } wcscpy (spec. lfFaceName, font == kGraphics_font_HELVETICA ? L"Arial" : font == kGraphics_font_TIMES ? L"Times New Roman" : font == kGraphics_font_COURIER ? L"Courier New" : font == kGraphics_font_PALATINO ? L"Book Antiqua" : font == kGraphics_font_SYMBOL ? L"Symbol" : font == kGraphics_font_IPATIMES ? ( doulosAvailable && style == 0 ? L"Doulos SIL" : charisAvailable ? L"Charis SIL" : L"Times New Roman" ) : font == kGraphics_font_DINGBATS ? L"Wingdings" : L""); return CreateFontIndirectW (& spec); } #endif static void charSize (I, _Graphics_widechar *lc) { iam (Graphics); if (my screen) { iam (GraphicsScreen); #if cairo if (my duringXor) { Longchar_Info info = Longchar_getInfoFromNative (lc -> kar); int normalSize = my fontSize * my resolution / 72.0; int smallSize = (3 * normalSize + 2) / 4; int size = lc -> size < 100 ? smallSize : normalSize; lc -> width = 10; lc -> baseline *= my fontSize * 0.01; lc -> code = lc -> kar; lc -> font.string = NULL; lc -> font.integer = 0; lc -> size = size; } else { if (my d_cairoGraphicsContext == NULL) return; Longchar_Info info = Longchar_getInfoFromNative (lc -> kar); int font, size, style; int normalSize = my fontSize * my resolution / 72.0; int smallSize = (3 * normalSize + 2) / 4; size = lc -> size < 100 ? smallSize : normalSize; cairo_text_extents_t extents; enum _cairo_font_slant slant = (lc -> style & Graphics_ITALIC ? CAIRO_FONT_SLANT_ITALIC : CAIRO_FONT_SLANT_NORMAL); enum _cairo_font_weight weight = (lc -> style & Graphics_BOLD ? CAIRO_FONT_WEIGHT_BOLD : CAIRO_FONT_WEIGHT_NORMAL); cairo_set_font_size (my d_cairoGraphicsContext, size); font = info -> alphabet == Longchar_SYMBOL ? kGraphics_font_SYMBOL : info -> alphabet == Longchar_PHONETIC ? kGraphics_font_IPATIMES : info -> alphabet == Longchar_DINGBATS ? kGraphics_font_DINGBATS : lc -> font.integer; switch (font) { case kGraphics_font_HELVETICA: cairo_select_font_face (my d_cairoGraphicsContext, "Helvetica", slant, weight); break; case kGraphics_font_TIMES: cairo_select_font_face (my d_cairoGraphicsContext, "Times New Roman", slant, weight); break; case kGraphics_font_COURIER: cairo_select_font_face (my d_cairoGraphicsContext, "Courier", slant, weight); break; case kGraphics_font_PALATINO: cairo_select_font_face (my d_cairoGraphicsContext, "Palatino", slant, weight); break; case kGraphics_font_SYMBOL: cairo_select_font_face (my d_cairoGraphicsContext, "Symbol", slant, weight); break; case kGraphics_font_IPATIMES: cairo_select_font_face (my d_cairoGraphicsContext, "Doulos SIL", slant, weight); break; case kGraphics_font_DINGBATS: cairo_select_font_face (my d_cairoGraphicsContext, "Dingbats", slant, weight); break; default: cairo_select_font_face (my d_cairoGraphicsContext, "Sans", slant, weight); break; } wchar_t buffer [2] = { lc -> kar, 0 }; cairo_text_extents (my d_cairoGraphicsContext, Melder_peekWcsToUtf8 (buffer), & extents); lc -> width = extents.x_advance; lc -> baseline *= my fontSize * 0.01; lc -> code = lc -> kar; lc -> font.string = NULL; lc -> font.integer = font; lc -> size = size; } #elif win Longchar_Info info = Longchar_getInfoFromNative (lc -> kar); int font, size, style; HFONT fontInfo; int normalSize = win_size2isize (my fontSize); int smallSize = (3 * normalSize + 2) / 4; font = info -> alphabet == Longchar_SYMBOL ? kGraphics_font_SYMBOL : info -> alphabet == Longchar_PHONETIC ? kGraphics_font_IPATIMES : info -> alphabet == Longchar_DINGBATS ? kGraphics_font_DINGBATS : lc -> font.integer; size = lc -> size < 100 ? smallSize : normalSize; style = lc -> style & (Graphics_ITALIC | Graphics_BOLD); // take out Graphics_CODE fontInfo = my printer || my metafile ? printerFonts [font] [size] [style] : screenFonts [font] [size] [style]; if (! fontInfo) { fontInfo = loadFont (me, font, size, style); if (! fontInfo) return; if (my printer || my metafile) { printerFonts [font] [size] [style] = fontInfo; } else { screenFonts [font] [size] [style] = fontInfo; } } if (font == kGraphics_font_IPATIMES && ! ipaAvailable) { int overstrike = ipaSerifRegular24 [info -> psEncoding - 32] [0] [0] == 'o'; lc -> code = info -> psEncoding; if (overstrike) lc -> width = 0; else lc -> width = strlen (ipaSerifRegular24 [info -> psEncoding - 32] [0]); } else { SIZE extent; wchar_t code; lc -> code = font == kGraphics_font_IPATIMES || font == kGraphics_font_TIMES || font == kGraphics_font_HELVETICA || font == kGraphics_font_COURIER ? (unsigned short) lc -> kar : info -> winEncoding; if (lc -> code == 0) { _Graphics_widechar *lc2; if (lc -> kar == UNICODE_LATIN_SMALL_LETTER_SCHWA_WITH_HOOK) { info = Longchar_getInfo ('s', 'w'); lc -> kar = info -> unicode; lc -> code = info -> winEncoding; for (lc2 = lc + 1; lc2 -> kar != '\0'; lc2 ++) { } lc2 [1]. kar = '\0'; while (lc2 - lc > 0) { lc2 [0] = lc2 [-1]; lc2 --; } lc [1]. kar = UNICODE_MODIFIER_LETTER_RHOTIC_HOOK; } else if (lc -> kar == UNICODE_LATIN_SMALL_LETTER_L_WITH_MIDDLE_TILDE) { info = Longchar_getInfo ('l', ' '); lc -> kar = info -> unicode; lc -> code = info -> winEncoding; for (lc2 = lc + 1; lc2 -> kar != '\0'; lc2 ++) { } lc2 [1]. kar = '\0'; while (lc2 - lc > 0) { lc2 [0] = lc2 [-1]; lc2 --; } lc [1]. kar = UNICODE_COMBINING_TILDE_OVERLAY; } } SelectFont (my d_gdiGraphicsContext, fontInfo); GetTextExtentPoint32W (my d_gdiGraphicsContext, (code = (unsigned short) lc -> code, & code), 1, & extent); // UTF-32 BUG lc -> width = extent. cx; } lc -> baseline *= my fontSize * 0.01 * my resolution / 72.0; lc -> font.string = NULL; lc -> font.integer = font; // kGraphics_font_HELVETICA .. kGraphics_font_DINGBATS lc -> size = size; // 0..4 instead of 10..24 lc -> style = style; // without Graphics_CODE #elif mac Longchar_Info info = Longchar_getInfoFromNative (lc -> kar); int normalSize = my fontSize * my resolution / 72.0; lc -> size = lc -> size < 100 ? (3 * normalSize + 2) / 4 : /*lc -> size > 100 ? 1.2 * normalSize :*/ normalSize; lc -> baseline *= 0.01 * normalSize; long saveFont = lc -> font.integer; // save! lc -> font.string = NULL; // this erases font.integer! ATSFontRef atsuiFont = info -> alphabet == Longchar_SYMBOL ? theSymbolAtsuiFont : info -> alphabet == Longchar_PHONETIC ? ( my font == kGraphics_font_TIMES && lc -> style == 0 ? theIpaTimesAtsuiFont : theIpaPalatinoAtsuiFont ) : lc -> kar == '/' ? thePalatinoAtsuiFont : /* Override Courier. */ info -> alphabet == Longchar_DINGBATS ? theZapfDingbatsAtsuiFont: saveFont == kGraphics_font_COURIER ? theCourierAtsuiFont : my font == kGraphics_font_TIMES ? theTimesAtsuiFont : my font == kGraphics_font_HELVETICA ? theHelveticaAtsuiFont : my font == kGraphics_font_COURIER ? theCourierAtsuiFont : theTimesAtsuiFont; Melder_assert (atsuiFont != 0); lc -> font.integer = (long) atsuiFont; lc -> code = lc -> kar; if (lc -> code == 0) { _Graphics_widechar *lc2; if (lc -> kar == UNICODE_LATIN_SMALL_LETTER_SCHWA_WITH_HOOK) { info = Longchar_getInfo ('s', 'w'); lc -> kar = info -> unicode; lc -> code = info -> unicode; for (lc2 = lc + 1; lc2 -> kar != '\0'; lc2 ++) { } lc2 [1]. kar = '\0'; while (lc2 - lc > 0) { lc2 [0] = lc2 [-1]; lc2 --; } lc [1]. kar = UNICODE_MODIFIER_LETTER_RHOTIC_HOOK; } else if (lc -> kar == UNICODE_LATIN_SMALL_LETTER_L_WITH_MIDDLE_TILDE) { info = Longchar_getInfo ('l', ' '); lc -> kar = info -> unicode; lc -> code = info -> unicode; for (lc2 = lc + 1; lc2 -> kar != '\0'; lc2 ++) { } lc2 [1]. kar = '\0'; while (lc2 - lc > 0) { lc2 [0] = lc2 [-1]; lc2 --; } lc [1]. kar = UNICODE_COMBINING_TILDE_OVERLAY; } } /* * Define the text layout. */ static ATSUTextLayout textLayout; if (textLayout == NULL) { OSStatus err = ATSUCreateTextLayout (& textLayout); if (err != 0) Melder_fatal ("Graphics_text/ATSUCreateTextLayout: unknown MacOS error %d.", (int) err); } uint16_t code16 [2]; if (lc -> kar <= 0xFFFF) { code16 [0] = lc -> kar; OSStatus err = ATSUSetTextPointerLocation (textLayout, & code16 [0], kATSUFromTextBeginning, kATSUToTextEnd, 1); // BUG: not 64-bit if (err != 0) Melder_fatal ("Graphics_text/ATSUSetTextPointerLocation low Unicode: unknown MacOS error %d.", (int) err); } else { MelderUtf32 kar = lc -> kar - 0x10000; code16 [0] = 0xD800 + (kar >> 10); code16 [1] = 0xDC00 + (kar & 0x3FF); OSStatus err = ATSUSetTextPointerLocation (textLayout, & code16 [0], kATSUFromTextBeginning, kATSUToTextEnd, 2); // BUG: not 64-bit if (err != 0) Melder_fatal ("Graphics_text/ATSUSetTextPointerLocation high Unicode: unknown MacOS error %d.", (int) err); } static ATSUFontFallbacks fontFallbacks = NULL; if (fontFallbacks == NULL) { ATSUCreateFontFallbacks (& fontFallbacks); ATSUSetObjFontFallbacks (fontFallbacks, 0, NULL, kATSUDefaultFontFallbacks); } ATSUAttributeTag attributeTags [] = { kATSUCGContextTag, kATSULineFontFallbacksTag }; ByteCount valueSizes [] = { sizeof (CGContextRef), sizeof (ATSUFontFallbacks) }; ATSUAttributeValuePtr values [] = { & my d_macGraphicsContext, & fontFallbacks }; ATSUSetLayoutControls (textLayout, 2, attributeTags, valueSizes, values); ATSUSetTransientFontMatching (textLayout, true); /* * Set styles: font, size, colour, bold, italic. */ static ATSUStyle atsuStyle; if (atsuStyle == NULL) { ATSUCreateStyle (& atsuStyle); } Fixed fontSize = lc -> size << 16; Boolean boldStyle = (lc -> style & Graphics_BOLD) != 0; Boolean italicStyle = (lc -> style & Graphics_ITALIC) != 0; ATSUAttributeTag styleAttributeTags [] = { kATSUFontTag, kATSUSizeTag, kATSUColorTag, kATSUQDBoldfaceTag, kATSUQDItalicTag }; ByteCount styleValueSizes [] = { sizeof (ATSUFontID), sizeof (Fixed), sizeof (RGBColor), sizeof (Boolean), sizeof (Boolean) }; ATSUAttributeValuePtr styleValues [] = { & atsuiFont, & fontSize, lc -> link ? & theBlueColour : & my d_macColour, & boldStyle, & italicStyle }; ATSUSetAttributes (atsuStyle, 5, styleAttributeTags, styleValueSizes, styleValues); ATSUSetRunStyle (textLayout, atsuStyle, 0, 1); ATSUTextMeasurement textBefore, textAfter, ascent, descent; ATSUGetUnjustifiedBounds (textLayout, kATSUFromTextBeginning, kATSUToTextEnd, & textBefore, & textAfter, & ascent, & descent); lc -> width = textAfter / 65536.0; #endif } else if (my postScript) { iam (GraphicsPostscript); int normalSize = (int) ((double) my fontSize * (double) my resolution / 72.0); Longchar_Info info = Longchar_getInfoFromNative (lc -> kar); int font = info -> alphabet == Longchar_SYMBOL ? kGraphics_font_SYMBOL : info -> alphabet == Longchar_PHONETIC ? kGraphics_font_IPATIMES : info -> alphabet == Longchar_DINGBATS ? kGraphics_font_DINGBATS : lc -> font.integer; int style = lc -> style == Graphics_ITALIC ? Graphics_ITALIC : lc -> style == Graphics_BOLD || lc -> link ? Graphics_BOLD : lc -> style == Graphics_BOLD_ITALIC ? Graphics_BOLD_ITALIC : 0; if (! my fontInfos [font] [style]) { const char *fontInfo, *secondaryFontInfo = NULL, *tertiaryFontInfo = NULL; if (font == kGraphics_font_COURIER) { fontInfo = style == Graphics_BOLD ? "Courier-Bold" : style == Graphics_ITALIC ? "Courier-Oblique" : style == Graphics_BOLD_ITALIC ? "Courier-BoldOblique" : "Courier"; secondaryFontInfo = style == Graphics_BOLD ? "CourierNewPS-BoldMT" : style == Graphics_ITALIC ? "CourierNewPS-ItalicMT" : style == Graphics_BOLD_ITALIC ? "CourierNewPS-BoldItalicMT" : "CourierNewPSMT"; tertiaryFontInfo = style == Graphics_BOLD ? "CourierNew-Bold" : style == Graphics_ITALIC ? "CourierNew-Italic" : style == Graphics_BOLD_ITALIC ? "CourierNew-BoldItalic" : "CourierNew"; } else if (font == kGraphics_font_TIMES) { fontInfo = style == Graphics_BOLD ? "Times-Bold" : style == Graphics_ITALIC ? "Times-Italic" : style == Graphics_BOLD_ITALIC ? "Times-BoldItalic" : "Times-Roman"; secondaryFontInfo = style == Graphics_BOLD ? "TimesNewRomanPS-BoldMT" : style == Graphics_ITALIC ? "TimesNewRomanPS-ItalicMT" : style == Graphics_BOLD_ITALIC ? "TimesNewRomanPS-BoldItalicMT" : "TimesNewRomanPSMT"; tertiaryFontInfo = style == Graphics_BOLD ? "TimesNewRoman-Bold" : style == Graphics_ITALIC ? "TimesNewRoman-Italic" : style == Graphics_BOLD_ITALIC ? "TimesNewRoman-BoldItalic" : "TimesNewRoman"; } else if (font == kGraphics_font_PALATINO) { fontInfo = style == Graphics_BOLD ? "Palatino-Bold" : style == Graphics_ITALIC ? "Palatino-Italic" : style == Graphics_BOLD_ITALIC ? "Palatino-BoldItalic" : "Palatino-Roman"; secondaryFontInfo = style == Graphics_BOLD ? "BookAntiquaPS-BoldMT" : style == Graphics_ITALIC ? "BookAntiquaPS-ItalicMT" : style == Graphics_BOLD_ITALIC ? "BookAntiquaPS-BoldItalicMT" : "BookAntiquaPSMT"; tertiaryFontInfo = style == Graphics_BOLD ? "BookAntiqua-Bold" : style == Graphics_ITALIC ? "BookAntiqua-Italic" : style == Graphics_BOLD_ITALIC ? "BookAntiqua-BoldItalic" : "BookAntiqua"; } else if (font == kGraphics_font_IPATIMES) { if (my includeFonts && ! my loadedXipa) { const char **p; for (p = & ipaSerifRegularPS [0]; *p; p ++) my d_printf (my d_file, "%s", *p); my loadedXipa = TRUE; } fontInfo = my useSilipaPS ? (style == Graphics_BOLD || style == Graphics_BOLD_ITALIC ? "SILDoulosIPA93Bold" : "SILDoulosIPA93Regular") : "TeX-xipa10-Praat-Regular"; } else if (font == kGraphics_font_SYMBOL) { fontInfo = "Symbol"; } else if (font == kGraphics_font_DINGBATS) { fontInfo = "ZapfDingbats"; } else { fontInfo = style == Graphics_BOLD ? "Helvetica-Bold" : style == Graphics_ITALIC ? "Helvetica-Oblique" : style == Graphics_BOLD_ITALIC ? "Helvetica-BoldOblique" : "Helvetica"; secondaryFontInfo = style == Graphics_BOLD ? "Arial-BoldMT" : style == Graphics_ITALIC ? "Arial-ItalicMT" : style == Graphics_BOLD_ITALIC ? "Arial-BoldItalicMT" : "ArialMT"; tertiaryFontInfo = style == Graphics_BOLD ? "Arial-Bold" : style == Graphics_ITALIC ? "Arial-Italic" : style == Graphics_BOLD_ITALIC ? "Arial-BoldItalic" : "Arial"; } my fontInfos [font] [style] = Melder_malloc_f (char, 100); if (font == kGraphics_font_IPATIMES || font == kGraphics_font_SYMBOL || font == kGraphics_font_DINGBATS) { strcpy (my fontInfos [font] [style], fontInfo); } else { sprintf (my fontInfos [font] [style], "%s-Praat", fontInfo); if (thePrinter. fontChoiceStrategy == kGraphicsPostscript_fontChoiceStrategy_LINOTYPE) { my d_printf (my d_file, "/%s /%s-Praat PraatEncode\n", fontInfo, fontInfo); } else if (thePrinter. fontChoiceStrategy == kGraphicsPostscript_fontChoiceStrategy_MONOTYPE) { my d_printf (my d_file, "/%s /%s-Praat PraatEncode\n", tertiaryFontInfo, fontInfo); } else if (thePrinter. fontChoiceStrategy == kGraphicsPostscript_fontChoiceStrategy_PS_MONOTYPE) { my d_printf (my d_file, "/%s /%s-Praat PraatEncode\n", secondaryFontInfo, fontInfo); } else { /* Automatic font choice strategy. */ if (secondaryFontInfo != NULL) { my d_printf (my d_file, "/%s /Font resourcestatus\n" "{ pop pop /%s /%s-Praat PraatEncode }\n" "{ /%s /%s-Praat PraatEncode }\n" "ifelse\n", secondaryFontInfo, secondaryFontInfo, fontInfo, fontInfo, fontInfo); } else { my d_printf (my d_file, "/%s /%s-Praat PraatEncode\n", fontInfo, fontInfo); } } } } lc -> font.integer = 0; lc -> font.string = my fontInfos [font] [style]; /* * Convert size and baseline information to device coordinates. */ lc -> size *= normalSize * 0.01; lc -> baseline *= normalSize * 0.01; if (font == kGraphics_font_COURIER) { lc -> width = 600; // Courier } else if (style == 0) { if (font == kGraphics_font_TIMES) lc -> width = info -> ps.times; else if (font == kGraphics_font_HELVETICA) lc -> width = info -> ps.helvetica; else if (font == kGraphics_font_PALATINO) lc -> width = info -> ps.palatino; else if (font == kGraphics_font_SYMBOL) lc -> width = info -> ps.times; else if (my useSilipaPS) lc -> width = info -> ps.timesItalic; else lc -> width = info -> ps.times; // XIPA } else if (style == Graphics_BOLD) { if (font == kGraphics_font_TIMES) lc -> width = info -> ps.timesBold; else if (font == kGraphics_font_HELVETICA) lc -> width = info -> ps.helveticaBold; else if (font == kGraphics_font_PALATINO) lc -> width = info -> ps.palatinoBold; else if (font == kGraphics_font_SYMBOL) lc -> width = info -> ps.times; else if (my useSilipaPS) lc -> width = info -> ps.timesBoldItalic; else lc -> width = info -> ps.times; // Symbol, IPA } else if (style == Graphics_ITALIC) { if (font == kGraphics_font_TIMES) lc -> width = info -> ps.timesItalic; else if (font == kGraphics_font_HELVETICA) lc -> width = info -> ps.helvetica; else if (font == kGraphics_font_PALATINO) lc -> width = info -> ps.palatinoItalic; else if (font == kGraphics_font_SYMBOL) lc -> width = info -> ps.times; else if (my useSilipaPS) lc -> width = info -> ps.timesItalic; else lc -> width = info -> ps.times; // Symbol, IPA } else if (style == Graphics_BOLD_ITALIC) { if (font == kGraphics_font_TIMES) lc -> width = info -> ps.timesBoldItalic; else if (font == kGraphics_font_HELVETICA) lc -> width = info -> ps.helveticaBold; else if (font == kGraphics_font_PALATINO) lc -> width = info -> ps.palatinoBoldItalic; else if (font == kGraphics_font_SYMBOL) lc -> width = info -> ps.times; else if (my useSilipaPS) lc -> width = info -> ps.timesBoldItalic; else lc -> width = info -> ps.times; // Symbol, IPA } lc -> width *= lc -> size / 1000.0; lc -> code = font == kGraphics_font_IPATIMES && my useSilipaPS ? info -> macEncoding : info -> psEncoding; if (lc -> code == 0) { _Graphics_widechar *lc2; if (lc -> kar == UNICODE_LATIN_SMALL_LETTER_SCHWA_WITH_HOOK) { info = Longchar_getInfo ('s', 'w'); lc -> kar = info -> unicode; lc -> code = info -> macEncoding; lc -> width = info -> ps.timesItalic * lc -> size / 1000.0; for (lc2 = lc + 1; lc2 -> kar != '\0'; lc2 ++) { } lc2 [1]. kar = '\0'; while (lc2 - lc > 0) { lc2 [0] = lc2 [-1]; lc2 --; } lc [1]. kar = UNICODE_MODIFIER_LETTER_RHOTIC_HOOK; } else if (lc -> kar == UNICODE_LATIN_SMALL_LETTER_L_WITH_MIDDLE_TILDE) { info = Longchar_getInfo ('l', ' '); lc -> code = info -> macEncoding; lc -> kar = info -> unicode; lc -> width = info -> ps.timesItalic * lc -> size / 1000.0; for (lc2 = lc + 1; lc2 -> kar != '\0'; lc2 ++) { } lc2 [1]. kar = '\0'; while (lc2 - lc > 0) { lc2 [0] = lc2 [-1]; lc2 --; } lc [1]. kar = UNICODE_COMBINING_TILDE_OVERLAY; } } } } static void charDraw (I, int xDC, int yDC, _Graphics_widechar *lc, const wchar_t *codes, const char *codes8, const MelderUtf16 *codes16, int nchars, int width) { iam (Graphics); //Melder_casual ("nchars %d first %d %c rightToLeft %d", nchars, lc->kar, lc -> kar, lc->rightToLeft); if (my postScript) { iam (GraphicsPostscript); bool onlyRegular = lc -> font.string [0] == 'S' || (lc -> font.string [0] == 'T' && lc -> font.string [1] == 'e'); // Symbol & SILDoulos ! int slant = (lc -> style & Graphics_ITALIC) && onlyRegular; int thick = (lc -> style & Graphics_BOLD) && onlyRegular; if (lc -> font.string != my lastFid || lc -> size != my lastSize) my d_printf (my d_file, my languageLevel == 1 ? "/%s %d FONT\n" : "/%s %d selectfont\n", my lastFid = lc -> font.string, my lastSize = lc -> size); if (lc -> link) my d_printf (my d_file, "0 0 1 setrgbcolor\n"); for (int i = -3; i <= 3; i ++) { if (i != 0 && ! thick) continue; my d_printf (my d_file, "%d %d M ", xDC + i, yDC); if (my textRotation || slant) { my d_printf (my d_file, "gsave currentpoint translate "); if (my textRotation) my d_printf (my d_file, "%.6g rotate 0 0 M\n", (double) my textRotation); if (slant) my d_printf (my d_file, "[1 0 0.25 1 0 0] concat 0 0 M\n"); } my d_printf (my d_file, "("); const char *kars = codes8; while (*kars) { if (*kars == '(' || *kars == ')' || *kars == '\\') { my d_printf (my d_file, "\\%c", *kars); } else if (*kars >= 32 && *kars <= 126) { my d_printf (my d_file, "%c", *kars); } else { my d_printf (my d_file, "\\%d%d%d", *(unsigned char*)kars / 64, (*(unsigned char*)kars % 64) / 8, *(unsigned char*)kars % 8); } kars ++; } my d_printf (my d_file, ") show\n"); if (my textRotation || slant) my d_printf (my d_file, "grestore\n"); } if (lc -> link) my d_printf (my d_file, "0 0 0 setrgbcolor\n"); } else if (my screen) { iam (GraphicsScreen); #if cairo if (my duringXor) { } else { if (my d_cairoGraphicsContext == NULL) return; // TODO! } int font = lc -> font.integer; int needBitmappedIPA = 0; #elif win int font = lc -> font.integer; int needBitmappedIPA = font == kGraphics_font_IPATIMES && ! ipaAvailable; #elif mac int needBitmappedIPA = 0; ATSFontRef atsuiFont = (ATSFontRef) lc -> font.integer; Melder_assert (atsuiFont != 0); /* * Define the text layout. */ static ATSUTextLayout theAtsuiTextLayout; if (theAtsuiTextLayout == NULL) { OSStatus err = ATSUCreateTextLayout (& theAtsuiTextLayout); if (err != 0) { if (err == kATSUInvalidFontID) { Melder_fatal ("Praat detected an invalid font ID and will now crash, beause this is a system error. " "Please use Font Book to check for duplicate or corrupted fonts."); } else { Melder_fatal ("Graphics_text/ATSUCreateTextLayout drawing: unknown MacOS error %d.", (int) err); } } } bool hasHighUnicodeValues = false; for (long i = 0; i < nchars; i ++) { hasHighUnicodeValues |= codes [i] > 0xFFFF; } if (hasHighUnicodeValues) { nchars = wcslen_utf16 (codes, 0); OSStatus err = ATSUSetTextPointerLocation (theAtsuiTextLayout, Melder_peekWcsToUtf16 (codes), kATSUFromTextBeginning, kATSUToTextEnd, nchars); if (err != 0) Melder_fatal ("Graphics_text/ATSUSetTextPointerLocation hasHighUnicodeValues true: unknown MacOS error %d.", (int) err); } else { OSStatus err = ATSUSetTextPointerLocation (theAtsuiTextLayout, codes16, kATSUFromTextBeginning, kATSUToTextEnd, nchars); if (err != 0) Melder_fatal ("Graphics_text/ATSUSetTextPointerLocation hasHighUnicodeValues false: unknown MacOS error %d.", (int) err); } static ATSUFontFallbacks fontFallbacks = NULL; if (fontFallbacks == NULL) { ATSUCreateFontFallbacks (& fontFallbacks); ATSUSetObjFontFallbacks (fontFallbacks, 0, NULL, kATSUDefaultFontFallbacks); ATSUSetObjFontFallbacks (fontFallbacks, 1, & theArabicAtsuiFont, kATSUSequentialFallbacksPreferred); } ATSUAttributeTag attributeTags [] = { kATSUCGContextTag, kATSULineFontFallbacksTag }; ByteCount valueSizes [] = { sizeof (CGContextRef), sizeof (ATSUFontFallbacks) }; ATSUAttributeValuePtr values [] = { & my d_macGraphicsContext, & fontFallbacks }; ATSUSetLayoutControls (theAtsuiTextLayout, 2, attributeTags, valueSizes, values); ATSUSetTransientFontMatching (theAtsuiTextLayout, true); /* * Set styles: font, size, colour, bold, italic. */ static ATSUStyle theAtsuStyle; if (theAtsuStyle == NULL) { ATSUCreateStyle (& theAtsuStyle); } Fixed fontSize = lc -> size << 16; Boolean boldStyle = (lc -> style & Graphics_BOLD) != 0; Boolean italicStyle = (lc -> style & Graphics_ITALIC) != 0; Fract kerningOff = FloatToFract (1.0); ATSUAttributeTag styleAttributeTags [] = { kATSUFontTag, kATSUSizeTag, kATSUColorTag, kATSUQDBoldfaceTag, kATSUQDItalicTag, kATSUKerningInhibitFactorTag }; ByteCount styleValueSizes [] = { sizeof (ATSUFontID), sizeof (Fixed), sizeof (RGBColor), sizeof (Boolean), sizeof (Boolean), sizeof (Fract) }; ATSUAttributeValuePtr styleValues [] = { & atsuiFont, & fontSize, lc -> link ? & theBlueColour : my duringXor ? & theWhiteColour : & my d_macColour, & boldStyle, & italicStyle, & kerningOff }; ATSUSetAttributes (theAtsuStyle, 6, styleAttributeTags, styleValueSizes, styleValues); ATSUSetRunStyle (theAtsuiTextLayout, theAtsuStyle, 0, nchars); /* * Draw. */ CGContextSaveGState (my d_macGraphicsContext); CGContextTranslateCTM (my d_macGraphicsContext, xDC, yDC); if (my yIsZeroAtTheTop) CGContextScaleCTM (my d_macGraphicsContext, 1.0, -1.0); CGContextRotateCTM (my d_macGraphicsContext, my textRotation * NUMpi / 180.0); if (my duringXor) { CGContextSetBlendMode (my d_macGraphicsContext, kCGBlendModeDifference); CGContextSetAllowsAntialiasing (my d_macGraphicsContext, false); OSStatus err = ATSUDrawText (theAtsuiTextLayout, kATSUFromTextBeginning, kATSUToTextEnd, 0, 0); if (err != 0) Melder_fatal ("Graphics_text/ATSUDrawText during Xor: unknown MacOS error %d.", (int) err); CGContextSetBlendMode (my d_macGraphicsContext, kCGBlendModeNormal); CGContextSetAllowsAntialiasing (my d_macGraphicsContext, true); } else { OSStatus err = ATSUDrawText (theAtsuiTextLayout, kATSUFromTextBeginning, kATSUToTextEnd, 0, 0); if (err != 0) Melder_fatal ("Graphics_text/ATSUDrawText: unknown MacOS error %d.", (int) err); } CGContextRestoreGState (my d_macGraphicsContext); return; #endif /* * First handle the most common case: text without rotation. */ if (my textRotation == 0.0) { /* * Unrotated text could be a link. If so, it will be blue. */ #if cairo if (my duringXor) { } else { if (lc -> link) _Graphics_setColour (me, Graphics_BLUE); } #elif win #endif /* * The most common case: a native font. */ if (! needBitmappedIPA) { #if cairo if (my duringXor) { static GdkFont *font = NULL; if (font == NULL) { font = gdk_font_load ("-*-courier-medium-r-normal--*-120-*-*-*-*-iso8859-1"); } gdk_draw_text_wc (my d_window, font, my d_gdkGraphicsContext, xDC, yDC, (const GdkWChar *) codes, nchars); } else { enum _cairo_font_slant slant = (lc -> style & Graphics_ITALIC ? CAIRO_FONT_SLANT_ITALIC : CAIRO_FONT_SLANT_NORMAL); enum _cairo_font_weight weight = (lc -> style & Graphics_BOLD ? CAIRO_FONT_WEIGHT_BOLD : CAIRO_FONT_WEIGHT_NORMAL); cairo_set_font_size (my d_cairoGraphicsContext, lc -> size); switch (font) { case kGraphics_font_HELVETICA: cairo_select_font_face (my d_cairoGraphicsContext, "Helvetica", slant, weight); break; case kGraphics_font_TIMES: cairo_select_font_face (my d_cairoGraphicsContext, "Times", slant, weight); break; case kGraphics_font_COURIER: cairo_select_font_face (my d_cairoGraphicsContext, "Courier", slant, weight); break; case kGraphics_font_PALATINO: cairo_select_font_face (my d_cairoGraphicsContext, "Palatino", slant, weight); break; case kGraphics_font_SYMBOL: cairo_select_font_face (my d_cairoGraphicsContext, "Symbol", slant, weight); break; case kGraphics_font_IPATIMES: cairo_select_font_face (my d_cairoGraphicsContext, "Doulos SIL", slant, weight); break; case kGraphics_font_DINGBATS: cairo_select_font_face (my d_cairoGraphicsContext, "Dingbats", slant, weight); break; default: cairo_select_font_face (my d_cairoGraphicsContext, "Sans", slant, weight); break; } cairo_move_to (my d_cairoGraphicsContext, xDC, yDC); cairo_show_text (my d_cairoGraphicsContext, Melder_peekWcsToUtf8 (codes)); } #elif win if (my duringXor) { int descent = (1.0/216) * my fontSize * my resolution; int ascent = (1.0/72) * my fontSize * my resolution; int maxWidth = 800, maxHeight = 200; int baseline = 100, top = baseline - ascent - 1, bottom = baseline + descent + 1; static int inited = 0; static HDC dc; static HBITMAP bitmap; if (! inited) { dc = CreateCompatibleDC (my d_gdiGraphicsContext); bitmap = CreateCompatibleBitmap (my d_gdiGraphicsContext, maxWidth, maxHeight); SelectBitmap (dc, bitmap); SetBkMode (dc, TRANSPARENT); // not the default! SelectPen (dc, GetStockPen (BLACK_PEN)); SelectBrush (dc, GetStockBrush (BLACK_BRUSH)); SetTextAlign (dc, TA_LEFT | TA_BASELINE | TA_NOUPDATECP); // baseline is not the default! inited = 1; } width += 4; // For slant. Rectangle (dc, 0, top, width, bottom); SelectFont (dc, my printer || my metafile ? printerFonts [font] [lc -> size] [lc -> style] : screenFonts [font] [lc -> size] [lc -> style]); SetTextColor (dc, my d_winForegroundColour); TextOutW (dc, 0, baseline, (const wchar *) codes16, nchars); BitBlt (my d_gdiGraphicsContext, xDC, yDC - ascent, width, bottom - top, dc, 0, top, SRCINVERT); } else { SelectPen (my d_gdiGraphicsContext, my d_winPen), SelectBrush (my d_gdiGraphicsContext, my d_winBrush); if (lc -> link) SetTextColor (my d_gdiGraphicsContext, RGB (0, 0, 255)); else SetTextColor (my d_gdiGraphicsContext, my d_winForegroundColour); SelectFont (my d_gdiGraphicsContext, my printer || my metafile ? printerFonts [font] [lc -> size] [lc -> style] : screenFonts [font] [lc -> size] [lc -> style]); TextOutW (my d_gdiGraphicsContext, xDC, yDC, (const wchar *) codes16, nchars); if (lc -> link) SetTextColor (my d_gdiGraphicsContext, my d_winForegroundColour); SelectPen (my d_gdiGraphicsContext, GetStockPen (BLACK_PEN)), SelectBrush (my d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); } #endif } else { /* * A non-rotated bitmap IPA font. */ for (int ichar = 0; ichar < nchars; ichar ++) { int irow, icol, code = ((unsigned char *) codes8) [ichar], ncol; int overstrike = ipaSerifRegular24 [code - 32] [0] [0] == 'o'; ncol = strlen (ipaSerifRegular24 [code - 32] [0]); if (overstrike) xDC -= 10; for (irow = 0; irow < 24; irow ++) { const char *row = ipaSerifRegular24 [code - 32] [irow]; int jrow = yDC - 18 + irow; for (icol = 0; icol < ncol; icol ++) { if (row [icol] == '#') #if cairo if (my duringXor) { } else { cairo_move_to (my d_cairoGraphicsContext, xDC, jrow); cairo_line_to (my d_cairoGraphicsContext, xDC, jrow); } #elif win SetPixel (my d_gdiGraphicsContext, xDC, jrow, my d_winForegroundColour); #endif xDC ++; } row ++; xDC -= ncol; } xDC += overstrike ? 10 : ncol; } #if cairo if (my duringXor) { } else { cairo_stroke (my d_cairoGraphicsContext); } #endif } /* * Back to normal colour. */ #if cairo if (my duringXor) { } else { if (lc -> link) _Graphics_setColour (me, my colour); } #elif win #endif } else { /* * Rotated text. This time, the easiest case is the bitmap IPA font; */ if (needBitmappedIPA) { int ichar, dx1 = 0; double cosa, sina; if (my textRotation == 90.0f) { cosa = 0.0; sina = 1.0; } else if (my textRotation == 270.0f) { cosa = 0.0; sina = -1.0; } else { double a = my textRotation * NUMpi / 180.0; cosa = cos (a); sina = sin (a); } for (ichar = 0; ichar < nchars; ichar ++) { int irow, icol, code = ((unsigned char *) codes8) [ichar]; int ncol = strlen (ipaSerifRegular24 [code - 32] [0]); for (irow = 0; irow < 24; irow ++) { const char *row = ipaSerifRegular24 [code - 32] [irow]; double dy1 = irow - 18; for (icol = 0; icol < ncol; icol ++) { if (row [icol] == '#') { int xp = xDC + (int) (cosa * dx1 + sina * dy1); int yp = yDC - (int) (sina * dx1 - cosa * dy1); #if cairo if (my duringXor) { } else { cairo_move_to (my d_cairoGraphicsContext, xp, yp); cairo_line_to (my d_cairoGraphicsContext, xp, yp); } #elif win SetPixel (my d_gdiGraphicsContext, xp, yp, my d_winForegroundColour); #endif } dx1 ++; } row ++; dx1 -= ncol; } dx1 += ncol; } #if cairo if (my duringXor) { } else { cairo_stroke (my d_cairoGraphicsContext); } #endif } else { /* * Rotated native font. */ #if cairo enum _cairo_font_slant slant = (lc -> style & Graphics_ITALIC ? CAIRO_FONT_SLANT_ITALIC : CAIRO_FONT_SLANT_NORMAL); enum _cairo_font_weight weight = (lc -> style & Graphics_BOLD ? CAIRO_FONT_WEIGHT_BOLD : CAIRO_FONT_WEIGHT_NORMAL); cairo_set_font_size (my d_cairoGraphicsContext, lc -> size); switch (font) { case kGraphics_font_HELVETICA: cairo_select_font_face (my d_cairoGraphicsContext, "Helvetica", slant, weight); break; case kGraphics_font_TIMES: cairo_select_font_face (my d_cairoGraphicsContext, "Times" , slant, weight); break; case kGraphics_font_COURIER: cairo_select_font_face (my d_cairoGraphicsContext, "Courier" , slant, weight); break; case kGraphics_font_PALATINO: cairo_select_font_face (my d_cairoGraphicsContext, "Palatino" , slant, weight); break; case kGraphics_font_SYMBOL: cairo_select_font_face (my d_cairoGraphicsContext, "Symbol" , slant, weight); break; case kGraphics_font_IPATIMES: cairo_select_font_face (my d_cairoGraphicsContext, "IPA Times", slant, weight); break; case kGraphics_font_DINGBATS: cairo_select_font_face (my d_cairoGraphicsContext, "Dingbats" , slant, weight); break; default: cairo_select_font_face (my d_cairoGraphicsContext, "Sans" , slant, weight); break; } cairo_save (my d_cairoGraphicsContext); cairo_translate (my d_cairoGraphicsContext, xDC, yDC); //cairo_scale (my d_cairoGraphicsContext, 1, -1); cairo_rotate (my d_cairoGraphicsContext, - my textRotation * NUMpi / 180.0); cairo_move_to (my d_cairoGraphicsContext, 0, 0); cairo_show_text (my d_cairoGraphicsContext, Melder_peekWcsToUtf8 (codes)); cairo_restore (my d_cairoGraphicsContext); return; #elif win if (1) { SelectPen (my d_gdiGraphicsContext, my d_winPen), SelectBrush (my d_gdiGraphicsContext, my d_winBrush); if (lc -> link) SetTextColor (my d_gdiGraphicsContext, RGB (0, 0, 255)); else SetTextColor (my d_gdiGraphicsContext, my d_winForegroundColour); SelectFont (my d_gdiGraphicsContext, my printer || my metafile ? printerFonts [font] [lc -> size] [lc -> style] : screenFonts [font] [lc -> size] [lc -> style]); int restore = SaveDC (my d_gdiGraphicsContext); SetGraphicsMode (my d_gdiGraphicsContext, GM_ADVANCED); double a = my textRotation * NUMpi / 180.0, cosa = cos (a), sina = sin (a); XFORM rotate = { cosa, - sina, sina, cosa, 0, 0 }; ModifyWorldTransform (my d_gdiGraphicsContext, & rotate, MWT_RIGHTMULTIPLY); XFORM translate = { 1, 0, 0, 1, xDC, yDC }; ModifyWorldTransform (my d_gdiGraphicsContext, & translate, MWT_RIGHTMULTIPLY); TextOutW (my d_gdiGraphicsContext, 0 /*xDC*/, 0 /*yDC*/, (const wchar *) codes16, nchars); RestoreDC (my d_gdiGraphicsContext, restore); if (lc -> link) SetTextColor (my d_gdiGraphicsContext, my d_winForegroundColour); SelectPen (my d_gdiGraphicsContext, GetStockPen (BLACK_PEN)), SelectBrush (my d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); return; } #endif int ascent = (1.0/72) * my fontSize * my resolution; int descent = (1.0/216) * my fontSize * my resolution; int ix, iy /*, baseline = 1 + ascent * 2*/; double cosa, sina; #if win int maxWidth = 1000, maxHeight = 600; // BUG: printer??? int baseline = maxHeight / 4, top = baseline - ascent - 1, bottom = baseline + descent + 1; static int inited = 0; static HDC dc; static HBITMAP bitmap; if (! inited) { dc = CreateCompatibleDC (my d_gdiGraphicsContext); bitmap = CreateBitmap (/*my d_gdiGraphicsContext,*/ maxWidth, maxHeight, 1, 1, NULL); SelectBitmap (dc, bitmap); inited = 1; } #endif width += 4; /* Leave room for slant. */ #if win SelectPen (dc, GetStockPen (WHITE_PEN)); SelectBrush (dc, GetStockBrush (WHITE_BRUSH)); SetTextAlign (dc, TA_LEFT | TA_BASELINE | TA_NOUPDATECP); // baseline is not the default! Rectangle (dc, 0, top, maxWidth, bottom + 1); //Rectangle (dc, 0, 0, maxWidth, maxHeight); SelectPen (dc, GetStockPen (BLACK_PEN)); SelectBrush (dc, GetStockBrush (NULL_BRUSH)); SelectFont (dc, my printer || my metafile ? printerFonts [font] [lc -> size] [lc -> style] : screenFonts [font] [lc -> size] [lc -> style]); TextOutW (dc, 0, baseline, (const wchar *) codes16, nchars); #endif if (my textRotation == 90.0) { cosa = 0.0; sina = 1.0; } else if (my textRotation == 270.0) { cosa = 0.0; sina = -1.0; } else { double a = my textRotation * NUMpi / 180.0; cosa = cos (a); sina = sin (a); } for (ix = 0; ix < width; ix ++) { double dx1 = ix; #if win for (iy = top; iy <= bottom; iy ++) { if (GetPixel (dc, ix, iy) == RGB (0, 0, 0)) { /* Black? */ int dy1 = iy - baseline; /* Translate, rotate, translate. */ int xp = xDC + (int) (cosa * dx1 + sina * dy1); int yp = yDC - (int) (sina * dx1 - cosa * dy1); SetPixel (my d_gdiGraphicsContext, xp, yp, my d_winForegroundColour); } } #endif } } } } } static void initText (I) { iam (Graphics); if (my screen) { iam (GraphicsScreen); (void) me; } } static void exitText (I) { iam (Graphics); if (my screen) { iam (GraphicsScreen); (void) me; } } #define MAX_LINK_LENGTH 300 static long bufferSize; static _Graphics_widechar *theWidechar; static wchar_t *charCodes; static char *charCodes8; static MelderUtf16 *charCodes16; static int initBuffer (const wchar_t *txt) { try { long sizeNeeded = wcslen (txt) + 1; /* It is true that some characters are split into two, but all of these are backslash sequences. */ if (sizeNeeded > bufferSize) { sizeNeeded += sizeNeeded / 2 + 100; Melder_free (theWidechar); Melder_free (charCodes); Melder_free (charCodes8); Melder_free (charCodes16); theWidechar = Melder_calloc (_Graphics_widechar, sizeNeeded); charCodes = Melder_calloc (wchar_t, sizeNeeded); charCodes8 = Melder_calloc (char, sizeNeeded); charCodes16 = Melder_calloc (MelderUtf16, sizeNeeded); bufferSize = sizeNeeded; } return 1; } catch (MelderError) { bufferSize = 0; Melder_flushError (NULL); return 0; } } static int numberOfLinks = 0; static Graphics_Link links [100]; /* A maximum of 100 links per string. */ static void charSizes (Graphics me, _Graphics_widechar string []) { /* * Measure the size of each character. */ _Graphics_widechar *character; for (character = string; character -> kar > '\t'; character ++) charSize (me, character); /* * Each character has been garnished with information about the character's width. * Make a correction for systems that make slanted characters overlap the character box to their right. * We must do this after the previous loop, because we query the size of the *next* character. * * Keep this in SYNC with psTextWidth. */ for (character = string; character -> kar > '\t'; character ++) { if ((character -> style & Graphics_ITALIC) != 0) { _Graphics_widechar *nextCharacter = character + 1; if (nextCharacter -> kar <= '\t') { character -> width += SLANT_CORRECTION / 72 * my fontSize * my resolution; } else if (((nextCharacter -> style & Graphics_ITALIC) == 0 && nextCharacter -> baseline >= character -> baseline) || (character -> baseline == 0 && nextCharacter -> baseline > 0)) { if (nextCharacter -> kar == '.' || nextCharacter -> kar == ',') character -> width += SLANT_CORRECTION / 144 * my fontSize * my resolution; else character -> width += SLANT_CORRECTION / 72 * my fontSize * my resolution; } } } } /* * The routine textWidth determines the fractional width of a text, in device coordinates. */ static double textWidth (_Graphics_widechar string []) { _Graphics_widechar *character; double width = 0; for (character = string; character -> kar > '\t'; character ++) width += character -> width; return width; } static void drawOneCell (Graphics me, int xDC, int yDC, _Graphics_widechar lc []) { int nchars = 0; double width = textWidth (lc), dx, dy; /* * We must continue even if width is zero (for adjusting textY). */ _Graphics_widechar *plc, *lastlc; int inLink = 0; switch (my horizontalTextAlignment) { case Graphics_LEFT: dx = 2; break; case Graphics_CENTRE: dx = - width / 2; break; case Graphics_RIGHT: dx = width ? - width - 1 : 0; break; // if width is zero, do not step left default: dx = 2; break; } switch (my verticalTextAlignment) { case Graphics_BOTTOM: dy = (0.4/72) * my fontSize * my resolution; break; case Graphics_HALF: dy = (-0.3/72) * my fontSize * my resolution; break; case Graphics_TOP: dy = (-1.0/72) * my fontSize * my resolution; break; case Graphics_BASELINE: dy = 0; break; default: dy = 0; break; } #if mac if (my screen) { GraphicsQuartz_initDraw ((GraphicsScreen) me); } #endif if (my textRotation) { double xbegin = dx, x = xbegin, cosa, sina; if (my textRotation == 90.0f) { cosa = 0.0; sina = 1.0; } else if (my textRotation == 270.0f) { cosa = 0.0; sina = -1.0; } else { double a = my textRotation * NUMpi / 180.0; cosa = cos (a); sina = sin (a); } for (plc = lc; plc -> kar > '\t'; plc ++) { _Graphics_widechar *next = plc + 1; charCodes [nchars] = plc -> code; // buffer... charCodes8 [nchars] = plc -> code; // buffer... charCodes16 [nchars ++] = plc -> code; // buffer... x += plc -> width; /* * We can draw stretches of characters: * they have different styles, baselines, sizes, or fonts, * or if there is a break between them, * or if we cannot rotate multiple characters, * which is the case on bitmap printers. */ if (next->kar < ' ' || next->style != plc->style || next->baseline != plc->baseline || next->size != plc->size || next->font.integer != plc->font.integer || next->font.string != plc->font.string || next->rightToLeft != plc->rightToLeft || (my screen && my resolution > 150)) { double dy2 = dy + plc -> baseline; double xr = cosa * xbegin - sina * dy2; double yr = sina * xbegin + cosa * dy2; charCodes [nchars] = '\0'; // ...and flush charCodes8 [nchars] = '\0'; // ...and flush charCodes16 [nchars] = '\0'; // ...and flush charDraw (me, xDC + xr, my yIsZeroAtTheTop ? yDC - yr : yDC + yr, plc, charCodes, charCodes8, charCodes16, nchars, x - xbegin); nchars = 0; xbegin = x; } } } else { double xbegin = xDC + dx, x = xbegin, y = my yIsZeroAtTheTop ? yDC - dy : yDC + dy; lastlc = lc; if (my wrapWidth) { /* * Replace some spaces with new-line symbols. */ int xmax = xDC + my wrapWidth * my scaleX; for (plc = lc; plc -> kar >= ' '; plc ++) { if (x > xmax) { // wrap (if wrapWidth is too small, each word will be on a separate line) while (plc >= lastlc) { if (plc -> kar == ' ' && ! plc -> link) // keep links contiguous break; plc --; } if (plc <= lastlc) break; // hopeless situation: no spaces; get over it lastlc = plc; plc -> kar = '\n'; // replace space with newline x = xDC + dx + my secondIndent * my scaleX; } else { x += plc -> width; } } xbegin = x = xDC + dx; /* Re-initialize for second pass. */ } for (plc = lc; plc -> kar > '\t'; plc ++) { _Graphics_widechar *next = plc + 1; if (plc -> link) { if (! inLink) { double descent = ( my yIsZeroAtTheTop ? -(0.3/72) : (0.3/72) ) * my fontSize * my resolution; links [++ numberOfLinks]. x1 = x; links [numberOfLinks]. y1 = y - descent; links [numberOfLinks]. y2 = y + 3 * descent; inLink = TRUE; } } else if (inLink) { links [numberOfLinks]. x2 = x; inLink = FALSE; } if (plc -> kar == '\n') { xbegin = x = xDC + dx + my secondIndent * my scaleX; y = my yIsZeroAtTheTop ? y + (1.2/72) * my fontSize * my resolution : y - (1.2/72) * my fontSize * my resolution; } else { charCodes [nchars] = plc -> code; // buffer... charCodes8 [nchars] = plc -> code; // buffer... charCodes16 [nchars ++] = plc -> code; // buffer... x += plc -> width; if (next->kar < ' ' || next->style != plc->style || next->baseline != plc->baseline || next->size != plc->size || next->link != plc->link || next->font.integer != plc->font.integer || next->font.string != plc->font.string || next->rightToLeft != plc->rightToLeft) { charCodes [nchars] = '\0'; // ...and flush charCodes8 [nchars] = '\0'; // ...and flush charCodes16 [nchars] = '\0'; // ...and flush charDraw (me, xbegin, my yIsZeroAtTheTop ? y - plc -> baseline : y + plc -> baseline, plc, charCodes, charCodes8, charCodes16, nchars, x - xbegin); nchars = 0; xbegin = x; } } } if (inLink) { links [numberOfLinks]. x2 = x; inLink = FALSE; } my textX = (x - my deltaX) / my scaleX; my textY = (( my yIsZeroAtTheTop ? y + dy : y - dy ) - my deltaY) / my scaleY; } #if mac if (my screen) { GraphicsQuartz_exitDraw ((GraphicsScreen) me); } #endif } static struct { double width; short alignment; } tabs [1 + 20] = { { 0, Graphics_CENTRE }, { 1, Graphics_CENTRE }, { 1, Graphics_CENTRE }, { 1, Graphics_CENTRE }, { 1, Graphics_CENTRE }, { 1, Graphics_CENTRE }, { 1, Graphics_CENTRE }, { 1, Graphics_CENTRE }, { 1, Graphics_CENTRE } }; /* * The routine 'drawCells' handles table and layout. */ static void drawCells (Graphics me, double xWC, double yWC, _Graphics_widechar lc []) { _Graphics_widechar *plc; int itab = 0, saveTextAlignment = my horizontalTextAlignment; double saveWrapWidth = my wrapWidth; numberOfLinks = 0; for (plc = lc; /* No stop condition. */ ; plc ++) { charSizes (me, plc); drawOneCell (me, xWC * my scaleX + my deltaX, yWC * my scaleY + my deltaY, plc); while (plc -> kar != '\0' && plc -> kar != '\t') plc ++; // Find end of cell. if (plc -> kar == '\0') break; // End of text? if (plc -> kar == '\t') { // Go to next cell. xWC += ( tabs [itab]. alignment == Graphics_LEFT ? tabs [itab]. width : tabs [itab]. alignment == Graphics_CENTRE ? 0.5 * tabs [itab]. width : 0 ) * my fontSize / 12.0; itab ++; xWC += ( tabs [itab]. alignment == Graphics_LEFT ? 0 : tabs [itab]. alignment == Graphics_CENTRE ? 0.5 * tabs [itab]. width : tabs [itab]. width ) * my fontSize / 12.0; my horizontalTextAlignment = tabs [itab]. alignment; my wrapWidth = tabs [itab]. width * my fontSize / 12.0; } } my horizontalTextAlignment = saveTextAlignment; my wrapWidth = saveWrapWidth; } static void parseTextIntoCellsLinesRuns (Graphics me, const wchar_t *txt, _Graphics_widechar a_widechar []) { wchar_t kar; const wchar_t *in = txt; int nquote = 0; _Graphics_widechar *out = & a_widechar [0]; unsigned int charSuperscript = 0, charSubscript = 0, charItalic = 0, charBold = 0; unsigned int wordItalic = 0, wordBold = 0, wordCode = 0, wordLink = 0; unsigned int globalSuperscript = 0, globalSubscript = 0, globalItalic = 0, globalBold = 0, globalCode = 0, globalLink = 0; unsigned int globalSmall = 0; numberOfLinks = 0; while ((kar = *in++) != '\0') { if (kar == '^' && my circumflexIsSuperscript) { if (globalSuperscript) globalSuperscript = 0; else if (in [0] == '^') { globalSuperscript = 1; in ++; } else charSuperscript = 1; wordItalic = wordBold = wordCode = 0; continue; } else if (kar == '_' && my underscoreIsSubscript) { if (globalSubscript) { globalSubscript = 0; wordItalic = wordBold = wordCode = 0; continue; } else if (in [0] == '_') { globalSubscript = 1; in ++; wordItalic = wordBold = wordCode = 0; continue; } else if (! my dollarSignIsCode) { charSubscript = 1; wordItalic = wordBold = wordCode = 0; continue; } // not in manuals else ; // A normal underscore in manuals. } else if (kar == '%' && my percentSignIsItalic) { if (globalItalic) globalItalic = 0; else if (in [0] == '%') { globalItalic = 1; in ++; } else if (my dollarSignIsCode) wordItalic = 1; // in manuals else charItalic = 1; continue; } else if (kar == '#' && my numberSignIsBold) { if (globalBold) globalBold = 0; else if (in [0] == '#') { globalBold = 1; in ++; } else if (my dollarSignIsCode) wordBold = 1; // in manuals else charBold = 1; continue; } else if (kar == '$' && my dollarSignIsCode) { if (globalCode) globalCode = 0; else if (in [0] == '$') { globalCode = 1; in ++; } else wordCode = 1; continue; } else if (kar == '@' && my atSignIsLink // recognize links && ! my textRotation) // no links allowed in rotated text, because links are identified by 2-point rectangles { wchar_t *to, *max; /* * We will distinguish: * 1. The link text: the text shown to the user, drawn in blue. * 2. The link info: the information saved in the Graphics object when the user clicks the link; * this may be a page title in a manual or any other information. * The link info is equal to the link text in the following cases: * 1. A single-word link: "this is a @Link that consists of one word". * 2. Longer links without '|' in them: "@@Link with spaces@". * The link info is unequal to the link text in the following case: * 3. Longer links with '|' in them: "@@Page linked to|Text shown in blue@" */ if (globalLink) { /* * Detected the third '@' in strings like "@@Link with spaces@". * This closes the link text (which will be shown in blue). */ globalLink = 0; // close the drawn link text (the normal colour will take over) continue; // the '@' must not be drawn } else if (in [0] == '@') { /* * Detected the second '@' in strings like "@@Link with spaces@". * A format like "@@Page linked to|Text shown in blue@" is permitted. * First step: collect the page text (the link information); * it is everything between "@@" and "|" or "@" or end of string. */ const wchar_t *from = in + 1; // start with first character after "@@" if (! links [++ numberOfLinks]. name) // make room for saving link info links [numberOfLinks]. name = Melder_calloc_f (wchar_t, MAX_LINK_LENGTH + 1); to = links [numberOfLinks]. name, max = to + MAX_LINK_LENGTH; while (*from && *from != '@' && *from != '|' && to < max) // until end-of-string or '@' or '|'... * to ++ = * from ++; // ... copy one character *to = '\0'; // close saved link info /* * Second step: collect the link text that is to be drawn. * Its characters will be collected during the normal cycles of the loop. * If the link info is equal to the link text, no action is needed. * If, on the other hand, there is a separate link info, this will have to be skipped. */ if (*from == '|') in += to - links [numberOfLinks]. name + 1; /* Skip link info + '|'. */ /* * We are entering the link-text-collection mode. */ globalLink = 1; /* * Both '@' must be skipped and must not be drawn. */ in ++; // skip second '@' continue; // do not draw } else { /* * Detected a single-word link, like in "this is a @Link that consists of one word". * First step: collect the page text: letters, digits, and underscores. */ const wchar_t *from = in; // start with first character after "@" if (! links [++ numberOfLinks]. name) // make room for saving link info links [numberOfLinks]. name = Melder_calloc_f (wchar_t, MAX_LINK_LENGTH + 1); to = links [numberOfLinks]. name, max = to + MAX_LINK_LENGTH; while (*from && (isalnum (*from) || *from == '_') && to < max) // until end-of-word... *to ++ = *from++; // ... copy one character *to = '\0'; // close saved link info /* * Second step: collect the link text that is to be drawn. * Its characters will be collected during the normal cycles of the loop. * The link info is equal to the link text, so no skipping is needed. */ wordLink = 1; // enter the single-word link-text-collection mode } continue; } else if (kar == '\\') { /* * Detected backslash sequence: backslash + kar1 + kar2... */ wchar_t kar1, kar2; /* * ... except if kar1 or kar2 is null: in that case, draw the backslash. */ if (! (kar1 = in [0]) || ! (kar2 = in [1])) { ; // normal backslash symbol /* * Catch "\s{", which means: small characters until corresponding '}'. */ } else if (kar2 == '{') { if (kar1 == 's') globalSmall = 1; in += 2; continue; /* * Default action: translate the backslash sequence into the long character 'kar1,kar2'. */ } else { kar = Longchar_getInfo (kar1, kar2) -> unicode; in += 2; } } else if (kar == '\"') { kar = ++nquote & 1 ? UNICODE_LEFT_DOUBLE_QUOTATION_MARK : UNICODE_RIGHT_DOUBLE_QUOTATION_MARK; } else if (kar == '\'') { kar = UNICODE_RIGHT_SINGLE_QUOTATION_MARK; } else if (kar == '`') { kar = UNICODE_LEFT_SINGLE_QUOTATION_MARK; } else if (kar >= 32 && kar <= 126) { if (kar == 'f') { if (in [0] == 'i' && HAS_FI_AND_FL_LIGATURES) { kar = UNICODE_LATIN_SMALL_LIGATURE_FI; in ++; } else if (in [0] == 'l' && HAS_FI_AND_FL_LIGATURES) { kar = UNICODE_LATIN_SMALL_LIGATURE_FL; in ++; } } else if (kar == '}') { if (globalSmall) { globalSmall = 0; continue; } } } else if (kar == '\t') { out -> kar = '\t'; out -> rightToLeft = false; wordItalic = wordBold = wordCode = wordLink = 0; globalSubscript = globalSuperscript = globalItalic = globalBold = globalCode = globalLink = globalSmall = 0; charItalic = charBold = charSuperscript = charSubscript = 0; out ++; continue; // do not draw } else if (kar == '\n') { kar = ' '; } if (wordItalic | wordBold | wordCode | wordLink) { if (! isalnum (kar) && kar != '_') // FIXME: this test could be more precise. wordItalic = wordBold = wordCode = wordLink = 0; } out -> style = (wordLink | globalLink) && my fontStyle != Graphics_CODE ? Graphics_BOLD : ((my fontStyle & Graphics_ITALIC) | charItalic | wordItalic | globalItalic ? Graphics_ITALIC : 0) + ((my fontStyle & Graphics_BOLD) | charBold | wordBold | globalBold ? Graphics_BOLD : 0); out -> font.string = NULL; out -> font.integer = my fontStyle == Graphics_CODE || wordCode || globalCode || kar == '/' || kar == '|' ? kGraphics_font_COURIER : my font; out -> link = wordLink | globalLink; out -> baseline = charSuperscript | globalSuperscript ? 34 : charSubscript | globalSubscript ? -25 : 0; out -> size = globalSmall || out -> baseline != 0 ? 80 : 100; if (kar == '/') { out -> baseline -= out -> size / 12; out -> size += out -> size / 10; } out -> code = '?'; // does this have any meaning? out -> kar = kar; out -> rightToLeft = (kar >= 0x0590 && kar <= 0x06FF) || (kar >= 0xFE70 && kar <= 0xFEFF) || (kar >= 0xFB1E && kar <= 0xFDFF); charItalic = charBold = charSuperscript = charSubscript = 0; out ++; } out -> kar = '\0'; // end of text out -> rightToLeft = false; } double Graphics_textWidth (Graphics me, const wchar_t *txt) { double width; if (! initBuffer (txt)) return 0.0; initText (me); parseTextIntoCellsLinesRuns (me, txt, theWidechar); charSizes (me, theWidechar); width = textWidth (theWidechar); exitText (me); return width / my scaleX; } void Graphics_textRect (Graphics me, double x1, double x2, double y1, double y2, const wchar_t *txt) { _Graphics_widechar *plc, *startOfLine; double width = 0.0, lineHeight = (1.1 / 72) * my fontSize * my resolution; long x1DC = x1 * my scaleX + my deltaX + 2, x2DC = x2 * my scaleX + my deltaX - 2; long y1DC = y1 * my scaleY + my deltaY, y2DC = y2 * my scaleY + my deltaY; int availableHeight = my yIsZeroAtTheTop ? y1DC - y2DC : y2DC - y1DC, availableWidth = x2DC - x1DC; int linesAvailable = availableHeight / lineHeight, linesNeeded = 1, lines, iline; if (linesAvailable <= 0) linesAvailable = 1; if (availableWidth <= 0) return; if (! initBuffer (txt)) return; initText (me); parseTextIntoCellsLinesRuns (me, txt, theWidechar); charSizes (me, theWidechar); for (plc = theWidechar; plc -> kar > '\t'; plc ++) { width += plc -> width; if (width > availableWidth) { if (++ linesNeeded > linesAvailable) break; width = 0.0; } } lines = linesNeeded > linesAvailable ? linesAvailable : linesNeeded; startOfLine = theWidechar; for (iline = 1; iline <= lines; iline ++) { width = 0.0; for (plc = startOfLine; plc -> kar > '\t'; plc ++) { int flush = FALSE; width += plc -> width; if (width > availableWidth) flush = TRUE; /* * Trick for incorporating end-of-text. */ if (! flush && plc [1]. kar <= '\t') { Melder_assert (iline == lines); plc ++; /* Brr. */ flush = TRUE; } if (flush) { int saveKar = plc -> kar, direction = my yIsZeroAtTheTop ? -1 : 1; int x = my horizontalTextAlignment == Graphics_LEFT ? x1DC : my horizontalTextAlignment == Graphics_RIGHT ? x2DC : 0.5 * (x1 + x2) * my scaleX + my deltaX; int y = my verticalTextAlignment == Graphics_BOTTOM ? y1DC + direction * (lines - iline) * lineHeight : my verticalTextAlignment == Graphics_TOP ? y2DC - direction * (iline - 1) * lineHeight : 0.5 * (y1 + y2) * my scaleY + my deltaY + 0.5 * direction * (lines - iline*2 + 1) * lineHeight; plc -> kar = '\0'; drawOneCell (me, x, y, startOfLine); plc -> kar = saveKar; startOfLine = plc; break; } } } exitText (me); } void Graphics_text (Graphics me, double xWC, double yWC, const wchar_t *txt) { if (my wrapWidth == 0.0 && wcschr (txt, '\n') && my textRotation == 0.0) { double lineSpacingWC = (1.2/72) * my fontSize * my resolution / fabs (my scaleY); long numberOfLines = 1; for (const wchar_t *p = & txt [0]; *p != '\0'; p ++) { if (*p == '\n') { numberOfLines ++; } } yWC += my verticalTextAlignment == Graphics_TOP ? 0 : my verticalTextAlignment == Graphics_HALF ? 0.5 * (numberOfLines - 1) * lineSpacingWC: (numberOfLines - 1) * lineSpacingWC; autostring linesToDraw = Melder_wcsdup_f (txt); wchar *p = & linesToDraw [0]; for (;;) { wchar_t *newline = wcschr (p, '\n'); if (newline != NULL) *newline = '\0'; Graphics_text (me, xWC, yWC, p); yWC -= lineSpacingWC; if (newline != NULL) { p = newline + 1; } else { break; } } return; } if (! initBuffer (txt)) return; initText (me); parseTextIntoCellsLinesRuns (me, txt, theWidechar); drawCells (me, xWC, yWC, theWidechar); exitText (me); if (my recording) { char *txt_utf8 = Melder_peekWcsToUtf8 (txt); int length = strlen (txt_utf8) / sizeof (double) + 1; op (TEXT, 3 + length); put (xWC); put (yWC); sput (txt_utf8, length) } } double Graphics_inqTextX (Graphics me) { return my textX; } double Graphics_inqTextY (Graphics me) { return my textY; } int Graphics_getLinks (Graphics_Link **plinks) { *plinks = & links [0]; return numberOfLinks; } static double psTextWidth (_Graphics_widechar string [], int useSilipaPS) { _Graphics_widechar *character; /* * The following has to be kept IN SYNC with GraphicsPostscript::charSize. */ double textWidth = 0; for (character = string; character -> kar > '\t'; character ++) { Longchar_Info info = Longchar_getInfoFromNative (character -> kar); int font = info -> alphabet == Longchar_SYMBOL ? kGraphics_font_SYMBOL : info -> alphabet == Longchar_PHONETIC ? kGraphics_font_IPATIMES : info -> alphabet == Longchar_DINGBATS ? kGraphics_font_DINGBATS : character -> font.integer; int style = character -> style == Graphics_ITALIC ? Graphics_ITALIC : character -> style == Graphics_BOLD || character -> link ? Graphics_BOLD : character -> style == Graphics_BOLD_ITALIC ? Graphics_BOLD_ITALIC : 0; double size = character -> size * 0.01; double charWidth = 600; /* Courier. */ if (font == kGraphics_font_COURIER) { charWidth = 600; } else if (style == 0) { if (font == kGraphics_font_TIMES) charWidth = info -> ps.times; else if (font == kGraphics_font_HELVETICA) charWidth = info -> ps.helvetica; else if (font == kGraphics_font_PALATINO) charWidth = info -> ps.palatino; else if (font == kGraphics_font_IPATIMES && useSilipaPS) charWidth = info -> ps.timesItalic; else charWidth = info -> ps.times; /* Symbol, IPA. */ } else if (style == Graphics_BOLD) { if (font == kGraphics_font_TIMES) charWidth = info -> ps.timesBold; else if (font == kGraphics_font_HELVETICA) charWidth = info -> ps.helveticaBold; else if (font == kGraphics_font_PALATINO) charWidth = info -> ps.palatinoBold; else if (font == kGraphics_font_IPATIMES && useSilipaPS) charWidth = info -> ps.timesBoldItalic; else charWidth = info -> ps.times; } else if (style == Graphics_ITALIC) { if (font == kGraphics_font_TIMES) charWidth = info -> ps.timesItalic; else if (font == kGraphics_font_HELVETICA) charWidth = info -> ps.helvetica; else if (font == kGraphics_font_PALATINO) charWidth = info -> ps.palatinoItalic; else if (font == kGraphics_font_IPATIMES && useSilipaPS) charWidth = info -> ps.timesItalic; else charWidth = info -> ps.times; } else if (style == Graphics_BOLD_ITALIC) { if (font == kGraphics_font_TIMES) charWidth = info -> ps.timesBoldItalic; else if (font == kGraphics_font_HELVETICA) charWidth = info -> ps.helveticaBold; else if (font == kGraphics_font_PALATINO) charWidth = info -> ps.palatinoBoldItalic; else if (font == kGraphics_font_IPATIMES && useSilipaPS) charWidth = info -> ps.timesBoldItalic; else charWidth = info -> ps.times; } charWidth *= size / 1000.0; textWidth += charWidth; } /* * The following has to be kept IN SYNC with charSizes (). */ for (character = string; character -> kar > '\t'; character ++) { if ((character -> style & Graphics_ITALIC) != 0) { _Graphics_widechar *nextCharacter = character + 1; if (nextCharacter -> kar <= '\t') { textWidth += POSTSCRIPT_SLANT_CORRECTION; } else if (((nextCharacter -> style & Graphics_ITALIC) == 0 && nextCharacter -> baseline >= character -> baseline) || (character -> baseline == 0 && nextCharacter -> baseline > 0)) { if (nextCharacter -> kar == '.' || nextCharacter -> kar == ',') textWidth += 0.5 * POSTSCRIPT_SLANT_CORRECTION; else textWidth += POSTSCRIPT_SLANT_CORRECTION; } } } return textWidth; } double Graphics_textWidth_ps_mm (Graphics me, const wchar_t *txt, bool useSilipaPS) { if (! initBuffer (txt)) return 0.0; parseTextIntoCellsLinesRuns (me, txt, theWidechar); return psTextWidth (theWidechar, useSilipaPS) * (double) my fontSize * (25.4 / 72.0); } double Graphics_textWidth_ps (Graphics me, const wchar_t *txt, bool useSilipaPS) { return Graphics_dxMMtoWC (me, Graphics_textWidth_ps_mm (me, txt, useSilipaPS)); } #if mac static ATSFontRef findFont (CFStringRef name) { ATSFontRef fontRef = ATSFontFindFromPostScriptName (name, kATSOptionFlagsDefault); if (fontRef == 0 || fontRef == kATSUInvalidFontID) { fontRef = ATSFontFindFromName (name, kATSOptionFlagsDefault); if (fontRef == 0 || fontRef == kATSUInvalidFontID) { return 0; } } return fontRef; } bool _GraphicsMac_tryToInitializeAtsuiFonts (void) { if (theTimesAtsuiFont != 0) return true; // once theTimesAtsuiFont = findFont (CFSTR ("Times")); if (! theTimesAtsuiFont) theTimesAtsuiFont = findFont (CFSTR ("Times New Roman")); theHelveticaAtsuiFont = findFont (CFSTR ("Helvetica")); if (! theHelveticaAtsuiFont) theHelveticaAtsuiFont = findFont (CFSTR ("Arial")); theCourierAtsuiFont = findFont (CFSTR ("Courier")); if (! theCourierAtsuiFont) theCourierAtsuiFont = findFont (CFSTR ("Courier New")); theSymbolAtsuiFont = findFont (CFSTR ("Symbol")); thePalatinoAtsuiFont = findFont (CFSTR ("Palatino")); if (! thePalatinoAtsuiFont) thePalatinoAtsuiFont = findFont (CFSTR ("Book Antiqua")); if (! thePalatinoAtsuiFont) thePalatinoAtsuiFont = theTimesAtsuiFont; theZapfDingbatsAtsuiFont = findFont (CFSTR ("Zapf Dingbats")); if (! theZapfDingbatsAtsuiFont) theZapfDingbatsAtsuiFont = theTimesAtsuiFont; if (! theTimesAtsuiFont || ! theHelveticaAtsuiFont || ! theCourierAtsuiFont || ! theSymbolAtsuiFont) { Melder_warning (L"Praat cannot find one or more of the fonts Times (or Times New Roman), " "Helvetica (or Arial), Courier (or Courier New), and Symbol. " "Praat will have limited capabilities for international text."); return false; } theIpaTimesAtsuiFont = findFont (CFSTR ("Doulos SIL")); theIpaPalatinoAtsuiFont = findFont (CFSTR ("Charis SIL")); if (! theIpaTimesAtsuiFont) { if (theIpaPalatinoAtsuiFont) { theIpaTimesAtsuiFont = theIpaPalatinoAtsuiFont; } else { Melder_warning (L"Praat cannot find the Charis SIL or Doulos SIL font.\n" "Phonetic characters will not look well."); // because ATSUI will use the "last resort font" theIpaTimesAtsuiFont = theTimesAtsuiFont; theIpaPalatinoAtsuiFont = thePalatinoAtsuiFont; } } else if (! theIpaPalatinoAtsuiFont) { theIpaPalatinoAtsuiFont = theIpaTimesAtsuiFont; } Melder_assert (theTimesAtsuiFont != 0); ATSUFindFontFromName (NULL, 0, 0, 0, 0, kFontArabicLanguage, & theArabicAtsuiFont); return true; } #endif void _GraphicsScreen_text_init (GraphicsScreen me) { /* BUG: should be done as late as possible. */ #if mac if (theTimesAtsuiFont == 0) { Melder_assert (_GraphicsMac_tryToInitializeAtsuiFonts ()); // should have been handled when setting my useQuartz to true } #elif win int font, size, style; if (my printer || my metafile) for (font = kGraphics_font_MIN; font <= kGraphics_font_DINGBATS; font ++) for (size = 0; size <= 4; size ++) for (style = 0; style <= Graphics_BOLD_ITALIC; style ++) if (printerFonts [font] [size] [style]) { DeleteObject (printerFonts [font] [size] [style]); printerFonts [font] [size] [style] = 0; } #endif } /* Output attributes. */ void Graphics_setTextAlignment (Graphics me, int hor, int vert) { if (hor != Graphics_NOCHANGE) my horizontalTextAlignment = hor; if (vert != Graphics_NOCHANGE) my verticalTextAlignment = vert; if (my recording) { op (SET_TEXT_ALIGNMENT, 2); put (hor); put (vert); } } void Graphics_setFont (Graphics me, enum kGraphics_font font) { my font = font; if (my recording) { op (SET_FONT, 1); put (font); } } void Graphics_setFontSize (Graphics me, int size) { my fontSize = size; if (my recording) { op (SET_FONT_SIZE, 1); put (size); } } void Graphics_setFontStyle (Graphics me, int style) { my fontStyle = style; if (my recording) { op (SET_FONT_STYLE, 1); put (style); } } void Graphics_setItalic (Graphics me, bool onoff) { if (onoff) my fontStyle |= Graphics_ITALIC; else my fontStyle &= ~ Graphics_ITALIC; } void Graphics_setBold (Graphics me, bool onoff) { if (onoff) my fontStyle |= Graphics_BOLD; else my fontStyle &= ~ Graphics_BOLD; } void Graphics_setCode (Graphics me, bool onoff) { if (onoff) my fontStyle |= Graphics_CODE; else my fontStyle &= ~ Graphics_CODE; } void Graphics_setTextRotation (Graphics me, double angle) { my textRotation = angle; if (my recording) { op (SET_TEXT_ROTATION, 1); put (angle); } } void Graphics_setWrapWidth (Graphics me, double wrapWidth) { my wrapWidth = wrapWidth; if (my recording) { op (SET_WRAP_WIDTH, 1); put (wrapWidth); } } void Graphics_setSecondIndent (Graphics me, double indent) { my secondIndent = indent; if (my recording) { op (SET_SECOND_INDENT, 1); put (indent); } } void Graphics_setPercentSignIsItalic (Graphics me, bool isItalic) { my percentSignIsItalic = isItalic; if (my recording) { op (SET_PERCENT_SIGN_IS_ITALIC, 1); put (isItalic); } } void Graphics_setNumberSignIsBold (Graphics me, bool isBold) { my numberSignIsBold = isBold; if (my recording) { op (SET_NUMBER_SIGN_IS_BOLD, 1); put (isBold); } } void Graphics_setCircumflexIsSuperscript (Graphics me, bool isSuperscript) { my circumflexIsSuperscript = isSuperscript; if (my recording) { op (SET_CIRCUMFLEX_IS_SUPERSCRIPT, 1); put (isSuperscript); } } void Graphics_setUnderscoreIsSubscript (Graphics me, bool isSubscript) { my underscoreIsSubscript = isSubscript; if (my recording) { op (SET_UNDERSCORE_IS_SUBSCRIPT, 1); put (isSubscript); } } void Graphics_setDollarSignIsCode (Graphics me, bool isCode) { my dollarSignIsCode = isCode; if (my recording) { op (SET_DOLLAR_SIGN_IS_CODE, 1); put (isCode); } } void Graphics_setAtSignIsLink (Graphics me, bool isLink) { my atSignIsLink = isLink; if (my recording) { op (SET_AT_SIGN_IS_LINK, 1); put (isLink); } } /* Inquiries. */ enum kGraphics_font Graphics_inqFont (Graphics me) { return my font; } int Graphics_inqFontSize (Graphics me) { return my fontSize; } int Graphics_inqFontStyle (Graphics me) { return my fontStyle; } /* End of file Graphics_text.cpp */ sources_5316/sys/ButtonEditor.h0000644000176700017670000000243411620770711015341 0ustar paulpaul#ifndef _ButtonEditor_h_ #define _ButtonEditor_h_ /* ButtonEditor.h * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "HyperPage.h" Thing_define (ButtonEditor, HyperPage) { // new data: public: int show; GuiObject button1, button2, button3, button4, button5; // overridden methods: virtual bool v_scriptable () { return false; } virtual void v_createChildren (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_draw (); virtual int v_goToPage (const wchar *title); }; ButtonEditor ButtonEditor_create (GuiObject parent); /* End of file ButtonEditor.h */ #endif sources_5316/sys/Simple.h0000644000176700017670000000230011724661151014142 0ustar paulpaul#ifndef _Simple_h_ #define _Simple_h_ /* Simple.h * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" #include "Simple_def.h" oo_CLASS_CREATE (SimpleInt, Data); oo_CLASS_CREATE (SimpleLong, Data); oo_CLASS_CREATE (SimpleDouble, Data); oo_CLASS_CREATE (SimpleString, Data); SimpleInt SimpleInt_create (int number); SimpleLong SimpleLong_create (long number); SimpleDouble SimpleDouble_create (double number); SimpleString SimpleString_create (const wchar_t *string); /* End of file Simple.h */ #endif sources_5316/sys/UiPause.h0000644000176700017670000000412711611106371014266 0ustar paulpaul#ifndef _UiPause_h_ #define _UiPause_h_ /* UiPause.h * * Copyright (C) 2009-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Gui.h" #include "Interpreter_decl.h" void UiPause_begin (GuiObject topShell, const wchar *title, Interpreter interpreter); void UiPause_real (const wchar *label, const wchar *defaultValue); void UiPause_positive (const wchar *label, const wchar *defaultValue); void UiPause_integer (const wchar *label, const wchar *defaultValue); void UiPause_natural (const wchar *label, const wchar *defaultValue); void UiPause_word (const wchar *label, const wchar *defaultValue); void UiPause_sentence (const wchar *label, const wchar *defaultValue); void UiPause_text (const wchar *label, const wchar *defaultValue); void UiPause_boolean (const wchar *label, int defaultValue); void UiPause_choice (const wchar *label, int defaultValue); void UiPause_optionMenu (const wchar *label, int defaultValue); void UiPause_option (const wchar *label); void UiPause_comment (const wchar *label); int UiPause_end (int numberOfContinueButtons, int defaultContinueButton, int cancelContinueButton, const wchar *continueText1, const wchar *continueText2, const wchar *continueText3, const wchar *continueText4, const wchar *continueText5, const wchar *continueText6, const wchar *continueText7, const wchar *continueText8, const wchar *continueText9, const wchar *continueText10, Interpreter interpreter); /* End of file UiPause.h */ #endif sources_5316/sys/Graphics.h0000644000176700017670000005307011753736261014472 0ustar paulpaul#ifndef _Graphics_h_ #define _Graphics_h_ /* Graphics.h * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Thing.h" #include "Graphics_enums.h" typedef struct { double red, green, blue; } Graphics_Colour; typedef struct { double x1NDC, x2NDC, y1NDC, y2NDC; } Graphics_Viewport; #if defined (UNIX) || defined (macintosh) && ! useCarbon typedef void *GuiObject; #else Thing_declare (GuiObject); #endif typedef struct { unsigned char link, rightToLeft; short style, size, baseline; unsigned long code; wchar_t kar; double width; union { long integer; const char *string; } font; int cell, line, run; } _Graphics_widechar; Thing_define (Graphics, Thing) { // new data: public: /* Device constants. */ bool screen; /* A boolean for whether we are a graphic screen (which may include a non-PostScript printer. */ bool postScript; /* A boolean for whether we are a PostScript device. */ bool printer; /* A boolean for whether we are a printer. */ bool metafile; /* A boolean for whether we are a high-resolution metafile or clipboard. */ bool yIsZeroAtTheTop; /* A boolean for whether vertical cooordinates increase from top to bottom (as on most screens, but not PostScript). */ GuiObject d_drawingArea; /* Also used as a boolean. */ int resolution; /* Dots per inch. */ long d_x1DCmin, d_x2DCmax, d_y1DCmin, d_y2DCmax; /* Maximum dimensions of the output device. */ /* x1DCmin < x2DCmax; y1DCmin < y2DCmax; */ /* The point (x1DCmin, y1DCmin) can be either in the top left */ /* or in the bottom left, depending on the yIsZeroAtTheTop flag. */ /* Device variables. */ long d_x1DC, d_x2DC, d_y1DC, d_y2DC; /* Current dimensions of the output device, or: */ /* device coordinates of the viewport rectangle. */ /* x1DCmin <= x1DC < x2DC <= x2DCmax; */ /* y1DCmin <= y1DC < y2DC <= y2DCmax; */ /* Graphics_create_xxxxxx sets these coordinates to */ /* x1DCmin, x2DCmax, y1DCmin, and y2DCmax. */ /* They can be changed by Graphics_setWsViewport. */ double d_x1wNDC, d_x2wNDC, d_y1wNDC, d_y2wNDC; /* Normalized device coordinates of */ /* the device viewport rectangle. */ /* The point (x1wNDC, y1wNDC) is always in the bottom left. */ /* Graphics_create_xxxxxx sets these coordinates to */ /* 0.0, 1.0, 0.0, and 1.0. */ /* They can be changed by Graphics_setWsWindow. */ double d_x1NDC, d_x2NDC, d_y1NDC, d_y2NDC; /* Normalized device coordinates of the user output viewport, */ /* which is a part of the device viewport rectangle. */ /* x1wNDC <= x1NDC < x2NDC <= x2wNDC; */ /* y1wNDC <= y1NDC < y2NDC <= y2wNDC; */ /* Graphics_create_xxxxxx sets these coordinates to */ /* 0.0, 1.0, 0.0, and 1.0. */ /* They can be changed by Graphics_setViewport. */ double d_x1WC, d_x2WC, d_y1WC, d_y2WC; /* World coordinates of the user output viewport rectangle. */ /* They bear a relation to the "real" world, */ /* and are used in the drawing routines. */ /* Graphics_create_xxxxxx sets these coordinates to */ /* 0.0, 1.0, 0.0, and 1.0. */ /* They can be changed by Graphics_setWindow. */ double deltaX, deltaY, scaleX, scaleY; /* Current coordinate transformation. */ /* Graphics state. */ int lineType; Graphics_Colour colour; double lineWidth, arrowSize; int horizontalTextAlignment, verticalTextAlignment; double textRotation, wrapWidth, secondIndent, textX, textY; enum kGraphics_font font; int fontSize, fontStyle; int percentSignIsItalic, numberSignIsBold, circumflexIsSuperscript, underscoreIsSubscript; int dollarSignIsCode, atSignIsLink; bool recording, duringXor; long irecord, nrecord; double *record; Graphics_Viewport outerViewport; /* For Graphics_(un)setInner (). */ double horTick, vertTick; /* For Graphics_mark(s)XXX (). */ double paperWidth, paperHeight; // overridden methods: virtual void v_destroy (); // new methods: virtual void v_polyline (long numberOfPoints, long *xyDC, bool close) { (void) numberOfPoints; (void) xyDC; (void) close; } virtual void v_fillArea (long numberOfPoints, long *xyDC) { (void) numberOfPoints; (void) xyDC; } virtual void v_rectangle (long a_x1DC, long a_x2DC, long a_y1DC, long a_y2DC) { (void) a_x1DC; (void) a_x2DC; (void) a_y1DC; (void) a_y2DC; } virtual void v_fillRectangle (long a_x1DC, long a_x2DC, long a_y1DC, long a_y2DC) { (void) a_x1DC; (void) a_x2DC; (void) a_y1DC; (void) a_y2DC; } virtual void v_circle (double xDC, double yDC, double rDC) { (void) xDC; (void) yDC; (void) rDC; } virtual void v_ellipse (long a_x1DC, long a_x2DC, long a_y1DC, long a_y2DC) { (void) a_x1DC; (void) a_x2DC; (void) a_y1DC; (void) a_y2DC; } virtual void v_arc (long xDC, long yDC, long rDC, double fromAngle, double toAngle) { (void) xDC; (void) yDC; (void) rDC; (void) fromAngle; (void) toAngle; } virtual void v_fillCircle (long xDC, long yDC, long rDC) { (void) xDC; (void) yDC; (void) rDC; } virtual void v_fillEllipse (long a_x1DC, long a_x2DC, long a_y1DC, long a_y2DC) { (void) a_x1DC; (void) a_x2DC; (void) a_y1DC; (void) a_y2DC; } virtual void v_button (long a_x1DC, long a_x2DC, long a_y1DC, long a_y2DC) { v_rectangle (a_x1DC, a_x2DC, a_y1DC, a_y2DC); // the simplest implementation } virtual void v_roundedRectangle (long x1DC, long x2DC, long y1DC, long y2DC, long r); virtual void v_fillRoundedRectangle (long x1DC, long x2DC, long y1DC, long y2DC, long r); virtual void v_arrowHead (long xDC, long yDC, double angle); virtual bool v_mouseStillDown () { return false; } virtual void v_getMouseLocation (double *xWC, double *yWC) { *xWC = *yWC = NUMundefined; } virtual void v_flushWs () { } virtual void v_clearWs () { } virtual void v_updateWs () { } }; Graphics Graphics_create (int resolution); Graphics Graphics_create_postscriptjob (MelderFile file, int resolution, enum kGraphicsPostscript_spots spots, enum kGraphicsPostscript_paperSize paperSize, enum kGraphicsPostscript_orientation rotation, double magnification); Graphics Graphics_create_epsfile (MelderFile file, int resolution, enum kGraphicsPostscript_spots spots, double xmin, double xmax, double ymin, double ymax, bool includeFonts, bool useSilipaPS); Graphics Graphics_create_pdffile (MelderFile file, int resolution, double x1inches, double x2inches, double y1inches, double y2inches); Graphics Graphics_create_pdf (void *context, int resolution, double x1inches, double x2inches, double y1inches, double y2inches); Graphics Graphics_create_postscriptprinter (void); Graphics Graphics_create_screenPrinter (void *display, void *window); Graphics Graphics_create_screen (void *display, void *window, int resolution); Graphics Graphics_create_xmdrawingarea (/* GuiObject */ void *drawingArea); int Graphics_getResolution (Graphics me); void Graphics_setWsViewport (Graphics me, long x1DC, long x2DC, long y1DC, long y2DC); void Graphics_resetWsViewport (Graphics me, long x1DC, long x2DC, long y1DC, long y2DC); void Graphics_setWsWindow (Graphics me, double x1NDC, double x2NDC, double y1NDC, double y2NDC); void Graphics_inqWsViewport (Graphics me, long *x1DC, long *x2DC, long *y1DC, long *y2DC); void Graphics_inqWsWindow (Graphics me, double *x1NDC, double *x2NDC, double *y1NDC, double *y2NDC); void Graphics_clearWs (Graphics me); void Graphics_flushWs (Graphics me); void Graphics_updateWs (Graphics me); void Graphics_DCtoWC (Graphics me, long xDC, long yDC, double *xWC, double *yWC); void Graphics_WCtoDC (Graphics me, double xWC, double yWC, long *xDC, long *yDC); void Graphics_setViewport (Graphics me, double x1NDC, double x2NDC, double y1NDC, double y2NDC); Graphics_Viewport Graphics_insetViewport (Graphics me, double x1rel, double x2rel, double y1rel, double y2rel); void Graphics_resetViewport (Graphics me, Graphics_Viewport viewport); void Graphics_setWindow (Graphics me, double x1, double x2, double y1, double y2); void Graphics_polyline (Graphics me, long numberOfPoints, double *x, double *y); void Graphics_polyline_closed (Graphics me, long numberOfPoints, double *x, double *y); void Graphics_text (Graphics me, double x, double y, const wchar_t *text); void Graphics_text1 (Graphics me, double x, double y, const wchar_t *s1); void Graphics_text2 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2); void Graphics_text3 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3); void Graphics_text4 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4); void Graphics_text5 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5); void Graphics_text6 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void Graphics_text7 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7); void Graphics_text8 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8); void Graphics_text9 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8, const wchar_t *s9); void Graphics_textRect (Graphics me, double x1, double x2, double y1, double y2, const wchar_t *text); double Graphics_textWidth (Graphics me, const wchar_t *text); double Graphics_textWidth_ps (Graphics me, const wchar_t *text, bool useSilipaPS); double Graphics_textWidth_ps_mm (Graphics me, const wchar_t *text, bool useSilipaPS); void Graphics_fillArea (Graphics me, long numberOfPoints, double *x, double *y); void Graphics_cellArray (Graphics me, double **z, long ix1, long ix2, double x1, double x2, long iy1, long iy2, double y1, double y2, double minimum, double maximum); void Graphics_cellArray8 (Graphics me, unsigned char **z, long ix1, long ix2, double x1, double x2, long iy1, long iy2, double y1, double y2, unsigned char minimum, unsigned char maximum); void Graphics_image (Graphics me, double **z, long ix1, long ix2, double x1, double x2, long iy1, long iy2, double y1, double y2, double minimum, double maximum); void Graphics_image8 (Graphics me, unsigned char **z, long ix1, long ix2, double x1, double x2, long iy1, long iy2, double y1, double y2, unsigned char minimum, unsigned char maximum); void Graphics_imageFromFile (Graphics me, const wchar_t *relativeFileName, double x1, double x2, double y1, double y2); void Graphics_line (Graphics me, double x1, double y1, double x2, double y2); void Graphics_rectangle (Graphics me, double x1, double x2, double y1, double y2); void Graphics_fillRectangle (Graphics me, double x1, double x2, double y1, double y2); void Graphics_roundedRectangle (Graphics me, double x1, double x2, double y1, double y2, double r_mm); void Graphics_fillRoundedRectangle (Graphics me, double x1, double x2, double y1, double y2, double r_mm); void Graphics_function (Graphics me, double y [], long ix1, long ix2, double x1, double x2); /* y [ix1..ix2] */ void Graphics_function16 (Graphics me, int16_t y [], int stagger, long ix1, long ix2, double x1, double x2); /* y [ix1..ix2] or y [ix1*2..ix2*2] */ void Graphics_circle (Graphics me, double x, double y, double r); void Graphics_fillCircle (Graphics me, double x, double y, double r); void Graphics_circle_mm (Graphics me, double x, double y, double d); void Graphics_fillCircle_mm (Graphics me, double x, double y, double d); void Graphics_rectangle_mm (Graphics me, double x, double y, double horizontalSide_mm, double verticalSide_mm); void Graphics_fillRectangle_mm (Graphics me, double x, double y, double horizontalSide_mm, double verticalSide_mm); void Graphics_arc (Graphics me, double x, double y, double r, double fromAngle, double toAngle); void Graphics_fillArc (Graphics me, double x, double y, double r, double fromAngle, double toAngle); void Graphics_ellipse (Graphics me, double x1, double x2, double y1, double y2); void Graphics_fillEllipse (Graphics me, double x1, double x2, double y1, double y2); void Graphics_arrow (Graphics me, double x1, double y1, double x2, double y2); void Graphics_doubleArrow (Graphics me, double x1, double y1, double x2, double y2); void Graphics_arcArrow (Graphics me, double x, double y, double r, double fromAngle, double toAngle, int arrowAtStart, int arrowAtEnd); void Graphics_mark (Graphics me, double x, double y, double size_mm, const wchar_t *markString); void Graphics_button (Graphics me, double x1, double x2, double y1, double y2); void Graphics_innerRectangle (Graphics me, double x1, double x2, double y1, double y2); extern Graphics_Colour Graphics_BLACK, Graphics_WHITE, Graphics_RED, Graphics_GREEN, Graphics_BLUE, Graphics_CYAN, Graphics_MAGENTA, Graphics_YELLOW, Graphics_MAROON, Graphics_LIME, Graphics_NAVY, Graphics_TEAL, Graphics_PURPLE, Graphics_OLIVE, Graphics_PINK, Graphics_SILVER, Graphics_GREY; const wchar_t * Graphics_Colour_name (Graphics_Colour colour); static inline bool Graphics_Colour_equal (Graphics_Colour colour1, Graphics_Colour colour2) { return colour1. red == colour2. red && colour1. green == colour2. green && colour1. blue == colour2. blue; } void Graphics_setColour (Graphics me, Graphics_Colour colour); void Graphics_setGrey (Graphics me, double grey); void Graphics_xorOn (Graphics me, Graphics_Colour colour); void Graphics_xorOff (Graphics me); void Graphics_highlight (Graphics me, double x1, double x2, double y1, double y2); void Graphics_unhighlight (Graphics me, double x1, double x2, double y1, double y2); void Graphics_highlight2 (Graphics me, double x1, double x2, double y1, double y2, double innerX1, double innerX2, double innerY1, double innerY2); void Graphics_unhighlight2 (Graphics me, double x1, double x2, double y1, double y2, double innerX1, double innerX2, double innerY1, double innerY2); #define Graphics_NOCHANGE -1 #define Graphics_LEFT kGraphics_horizontalAlignment_LEFT #define Graphics_CENTRE kGraphics_horizontalAlignment_CENTRE #define Graphics_RIGHT kGraphics_horizontalAlignment_RIGHT #define Graphics_BOTTOM 0 #define Graphics_HALF 1 #define Graphics_TOP 2 #define Graphics_BASELINE 3 void Graphics_setTextAlignment (Graphics me, int horizontal, int vertical); void Graphics_setFont (Graphics me, enum kGraphics_font font); void Graphics_setFontSize (Graphics me, int height); void Graphics_setFontStyle (Graphics me, int style); void Graphics_setItalic (Graphics me, bool onoff); void Graphics_setBold (Graphics me, bool onoff); void Graphics_setCode (Graphics me, bool onoff); #define Graphics_NORMAL 0 #define Graphics_BOLD 1 #define Graphics_ITALIC 2 #define Graphics_BOLD_ITALIC 3 #define Graphics_CODE 4 void Graphics_setTextRotation (Graphics me, double angle); void Graphics_setTextRotation_vector (Graphics me, double dx, double dy); void Graphics_setWrapWidth (Graphics me, double wrapWidth); void Graphics_setSecondIndent (Graphics me, double indent); double Graphics_inqTextX (Graphics me); double Graphics_inqTextY (Graphics me); typedef struct { double x1, x2, y1, y2; wchar_t *name; } Graphics_Link; int Graphics_getLinks (Graphics_Link **plinks); void Graphics_setNumberSignIsBold (Graphics me, bool isBold); void Graphics_setPercentSignIsItalic (Graphics me, bool isItalic); void Graphics_setCircumflexIsSuperscript (Graphics me, bool isSuperscript); void Graphics_setUnderscoreIsSubscript (Graphics me, bool isSubscript); void Graphics_setDollarSignIsCode (Graphics me, bool isCode); void Graphics_setAtSignIsLink (Graphics me, bool isLink); void Graphics_setLineType (Graphics me, int lineType); #define Graphics_DRAWN 0 #define Graphics_DOTTED 1 #define Graphics_DASHED 2 #define Graphics_DASHED_DOTTED 3 void Graphics_setLineWidth (Graphics me, double lineWidth); void Graphics_setArrowSize (Graphics me, double arrorSize); void Graphics_inqViewport (Graphics me, double *x1NDC, double *x2NDC, double *y1NDC, double *y2NDC); void Graphics_inqWindow (Graphics me, double *x1WC, double *x2WC, double *y1WC, double *y2WC); enum kGraphics_font Graphics_inqFont (Graphics me); int Graphics_inqFontSize (Graphics me); int Graphics_inqFontStyle (Graphics me); int Graphics_inqLineType (Graphics me); double Graphics_inqLineWidth (Graphics me); double Graphics_inqArrowSize (Graphics me); Graphics_Colour Graphics_inqColour (Graphics me); void Graphics_contour (Graphics me, double **z, long ix1, long ix2, double x1WC, double x2WC, long iy1, long iy2, double y1WC, double y2WC, double height); void Graphics_altitude (Graphics me, double **z, long ix1, long ix2, double x1, double x2, long iy1, long iy2, double y1, double y2, int numberOfBorders, double borders []); void Graphics_grey (Graphics me, double **z, long ix1, long ix2, double x1, double x2, long iy1, long iy2, double y1, double y2, int numberOfBorders, double borders []); #define Graphics_gray Graphics_grey void Graphics_surface (Graphics me, double **z, long ix1, long ix2, double x1, double x2, long iy1, long iy2, double y1, double y2, double minimum, double maximum, double elevation, double azimuth); void Graphics_setInner (Graphics me); void Graphics_unsetInner (Graphics me); void Graphics_drawInnerBox (Graphics me); void Graphics_textLeft (Graphics me, bool far, const wchar_t *text); void Graphics_textRight (Graphics me, bool far, const wchar_t *text); void Graphics_textBottom (Graphics me, bool far, const wchar_t *text); void Graphics_textTop (Graphics me, bool far, const wchar_t *text); void Graphics_marksLeft (Graphics me, int numberOfMarks, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksRight (Graphics me, int numberOfMarks, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksBottom (Graphics me, int numberOfMarks, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksTop (Graphics me, int numberOfMarks, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksLeftLogarithmic (Graphics me, int numberOfMarksPerDecade, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksRightLogarithmic (Graphics me, int numberOfMarksPerDecade, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksBottomLogarithmic (Graphics me, int numberOfMarksPerDecade, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksTopLogarithmic (Graphics me, int numberOfMarksPerDecade, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_markLeft (Graphics me, double yWC, bool hasNumber, bool hasTick, bool hasDottedLine, const wchar_t *text); void Graphics_markRight (Graphics me, double yWC, bool hasNumber, bool hasTick, bool hasDottedLine, const wchar_t *text); void Graphics_markBottom (Graphics me, double xWC, bool hasNumber, bool hasTick, bool hasDottedLine, const wchar_t *text); void Graphics_markTop (Graphics me, double xWC, bool hasNumber, bool hasTick, bool hasDottedLine, const wchar_t *text); void Graphics_markLeftLogarithmic (Graphics me, double y /* > 0 */, bool hasNumber, bool hasTick, bool hasDottedLine, const wchar_t *text); void Graphics_markRightLogarithmic (Graphics me, double y, bool hasNumber, bool hasTick, bool hasDottedLine, const wchar_t *text); void Graphics_markBottomLogarithmic (Graphics me, double x, bool hasNumber, bool hasTick, bool hasDottedLine, const wchar_t *text); void Graphics_markTopLogarithmic (Graphics me, double x, bool hasNumber, bool hasTick, bool hasDottedLine, const wchar_t *text); void Graphics_marksLeftEvery (Graphics me, double units, double distance, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksRightEvery (Graphics me, double units, double distance, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksBottomEvery (Graphics me, double units, double distance, bool haveNumbers, bool haveTicks, bool haveDottedLines); void Graphics_marksTopEvery (Graphics me, double units, double distance, bool haveNumbers, bool haveTicks, bool haveDottedLines); void *Graphics_x_getCR (Graphics me); void Graphics_x_setCR (Graphics me, void *cr); void *Graphics_x_getGC (Graphics me); bool Graphics_startRecording (Graphics me); bool Graphics_stopRecording (Graphics me); void Graphics_clearRecording (Graphics me); void Graphics_play (Graphics from, Graphics to); void Graphics_writeRecordings (Graphics me, FILE *f); void Graphics_readRecordings (Graphics me, FILE *f); void Graphics_markGroup (Graphics me); void Graphics_undoGroup (Graphics me); double Graphics_dxMMtoWC (Graphics me, double dx_mm); double Graphics_dyMMtoWC (Graphics me, double dy_mm); double Graphics_distanceWCtoMM (Graphics me, double x1WC, double y1WC, double x2WC, double y2WC); double Graphics_dxWCtoMM (Graphics me, double dxWC); double Graphics_dyWCtoMM (Graphics me, double dyWC); bool Graphics_mouseStillDown (Graphics me); void Graphics_waitMouseUp (Graphics me); void Graphics_getMouseLocation (Graphics me, double *xWC, double *yWC); void Graphics_nextSheetOfPaper (Graphics me); /* End of file Graphics.h */ #endif sources_5316/sys/site.cpp0000644000176700017670000000251711564044121014214 0ustar paulpaul/* site.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2004/10/21 simplified print command * pb 2005/03/02 pref string buffer 260 bytes long * pb 2007/08/12 wchar_t * pb 2007/12/09 preferences * pb 2011/05/15 C++ */ #include "Preferences.h" #include #include "site.h" static wchar_t printCommand [Preferences_STRING_BUFFER_SIZE]; wchar_t * Site_getPrintCommand (void) { return printCommand; } void Site_setPrintCommand (const wchar_t *text) { wcscpy (printCommand, text); } void Site_prefs (void) { Preferences_addString (L"Site.printCommand", printCommand, L"lp -c %s"); } /* End of file site.cpp */ sources_5316/sys/Graphics_enums.h0000644000176700017670000000720410727056712015673 0ustar paulpaul/* Graphics_enums.h * * Copyright (C) 1992-2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/09 */ enums_begin (kGraphics_font, 0) enums_add (kGraphics_font, 0, HELVETICA, L"Helvetica") enums_add (kGraphics_font, 1, TIMES, L"Times") enums_add (kGraphics_font, 2, COURIER, L"Courier") enums_add (kGraphics_font, 3, PALATINO, L"Palatino") enums_end (kGraphics_font, 3, TIMES) enums_begin (kGraphics_horizontalAlignment, 0) enums_add (kGraphics_horizontalAlignment, 0, LEFT, L"left") enums_add (kGraphics_horizontalAlignment, 1, CENTRE, L"centre") enums_alt (kGraphics_horizontalAlignment, CENTRE, L"center") enums_add (kGraphics_horizontalAlignment, 2, RIGHT, L"right") /* For reading old preferences files: */ enums_alt (kGraphics_horizontalAlignment, LEFT, L"0") enums_alt (kGraphics_horizontalAlignment, CENTRE, L"1") enums_alt (kGraphics_horizontalAlignment, RIGHT, L"2") enums_end (kGraphics_horizontalAlignment, 2, CENTRE) enums_begin (kGraphicsPostscript_spots, 0) enums_add (kGraphicsPostscript_spots, 0, FINE, L"finest") enums_add (kGraphicsPostscript_spots, 1, PHOTOCOPYABLE, L"photocopyable") /* For reading old preferences files: */ enums_alt (kGraphicsPostscript_spots, FINE, L"0") enums_alt (kGraphicsPostscript_spots, PHOTOCOPYABLE, L"1") enums_end (kGraphicsPostscript_spots, 1, FINE) enums_begin (kGraphicsPostscript_paperSize, 0) enums_add (kGraphicsPostscript_paperSize, 0, A4, L"A4") enums_add (kGraphicsPostscript_paperSize, 1, A3, L"A3") enums_add (kGraphicsPostscript_paperSize, 2, US_LETTER, L"US Letter") /* For reading old preferences files: */ enums_alt (kGraphicsPostscript_paperSize, A4, L"0") enums_alt (kGraphicsPostscript_paperSize, A3, L"1") enums_alt (kGraphicsPostscript_paperSize, US_LETTER, L"2") enums_end (kGraphicsPostscript_paperSize, 2, A4) enums_begin (kGraphicsPostscript_orientation, 0) enums_add (kGraphicsPostscript_orientation, 0, PORTRAIT, L"portrait") enums_add (kGraphicsPostscript_orientation, 1, LANDSCAPE, L"landscape") /* For reading old preferences files: */ enums_alt (kGraphicsPostscript_orientation, PORTRAIT, L"0") enums_alt (kGraphicsPostscript_orientation, LANDSCAPE, L"1") enums_end (kGraphicsPostscript_orientation, 1, PORTRAIT) enums_begin (kGraphicsPostscript_fontChoiceStrategy, 0) enums_add (kGraphicsPostscript_fontChoiceStrategy, 0, AUTOMATIC, L"automatic") enums_add (kGraphicsPostscript_fontChoiceStrategy, 1, LINOTYPE, L"Linotype") enums_add (kGraphicsPostscript_fontChoiceStrategy, 2, MONOTYPE, L"Monotype") enums_add (kGraphicsPostscript_fontChoiceStrategy, 3, PS_MONOTYPE, L"PS Monotype") /* For reading old preferences files: */ enums_alt (kGraphicsPostscript_fontChoiceStrategy, AUTOMATIC, L"0") enums_alt (kGraphicsPostscript_fontChoiceStrategy, LINOTYPE, L"1") enums_alt (kGraphicsPostscript_fontChoiceStrategy, MONOTYPE, L"2") enums_alt (kGraphicsPostscript_fontChoiceStrategy, PS_MONOTYPE, L"3") enums_end (kGraphicsPostscript_fontChoiceStrategy, 3, AUTOMATIC) /* End of file Graphics_enums.h */ sources_5316/sys/melder_ftoa.cpp0000644000176700017670000002066011604541632015534 0ustar paulpaul/* melder_ftoa.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2002/11/30 Melder_fixed * pb 2002/12/01 Melder_single, Melder_half * pb 2003/05/13 Melder_percent * pb 2003/05/19 Melder_fixed: include a minimum precision of 1 digit * pb 2004/04/04 Melder_bigInteger * pb 2006/04/16 separated from melder.c * pb 2006/12/10 A and W versions * pb 2006/12/29 removed future bug * pb 2007/11/30 Melder_float * pb 2008/01/06 Mac: use strtod instead of wcstod for speed * pb 2010/10/16 Melder_naturalLogarithm * pb 2011/04/05 C++ */ #include "melder.h" #include "NUM.h" /********** NUMBER TO STRING CONVERSION **********/ #define NUMBER_OF_BUFFERS 32 /* = maximum number of arguments to a function call */ #define MAXIMUM_NUMERIC_STRING_LENGTH 386 /* = sign + 308 + point + 60 + e + sign + 3 + null byte + (\.c10^^ - 1) + 4 extra */ static wchar_t buffers [NUMBER_OF_BUFFERS] [MAXIMUM_NUMERIC_STRING_LENGTH + 1]; static int ibuffer = 0; const wchar_t * Melder_integer (long value) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%ld", value); return buffers [ibuffer]; } const wchar_t * Melder_bigInteger (double value) { wchar_t *text; int trillions, billions, millions, thousands, units, firstDigitPrinted = FALSE; if (fabs (value) > 1e15) return Melder_double (value); if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; text = buffers [ibuffer]; text [0] = L'\0'; if (value < 0.0) { swprintf (text, MAXIMUM_NUMERIC_STRING_LENGTH, L"-"); value = - value; } trillions = floor (value / 1e12); value -= trillions * 1e12; billions = floor (value / 1e9); value -= billions * 1e9; millions = floor (value / 1e6); value -= millions * 1e6; thousands = floor (value / 1e3); value -= thousands * 1e3; units = value; if (trillions) { swprintf (text + wcslen (text), MAXIMUM_NUMERIC_STRING_LENGTH, L"%d,", trillions); firstDigitPrinted = TRUE; } if (billions || firstDigitPrinted) { swprintf (text + wcslen (text), MAXIMUM_NUMERIC_STRING_LENGTH, firstDigitPrinted ? L"%03d," : L"%d,", billions); firstDigitPrinted = TRUE; } if (millions || firstDigitPrinted) { swprintf (text + wcslen (text), MAXIMUM_NUMERIC_STRING_LENGTH, firstDigitPrinted ? L"%03d," : L"%d,", millions); firstDigitPrinted = TRUE; } if (thousands || firstDigitPrinted) { swprintf (text + wcslen (text), MAXIMUM_NUMERIC_STRING_LENGTH, firstDigitPrinted ? L"%03d," : L"%d,", thousands); firstDigitPrinted = TRUE; } swprintf (text + wcslen (text), MAXIMUM_NUMERIC_STRING_LENGTH, firstDigitPrinted ? L"%03d" : L"%d", units); return text; } const wchar_t * Melder_boolean (bool value) { return value ? L"yes" : L"no"; } const wchar * Melder_double (double value) { if (value == NUMundefined) return L"--undefined--"; if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; #if defined (macintosh) /* * OPTIMIZATION: strtod may be 100 times faster than wcstod on the Mac. 20080106 */ static char buffer [MAXIMUM_NUMERIC_STRING_LENGTH + 1]; sprintf (buffer, "%.15g", value); if (strtod (buffer, NULL) != value) { sprintf (buffer, "%.16g", value); if (strtod (buffer, NULL) != value) { sprintf (buffer, "%.17g", value); } } #if 0 wchar_t *to = & buffers [ibuffer] [0]; char *from = & buffer [0]; for (; (*to++ = *from++) != '\0';) ; *to = '\0'; #else Melder_8bitToWcs_inline (buffer, buffers [ibuffer], kMelder_textInputEncoding_UTF8); // guaranteed not to fail #endif #else swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.15g", value); if (wcstod (buffers [ibuffer], NULL) != value) { swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.16g", value); if (wcstod (buffers [ibuffer], NULL) != value) { swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.17g", value); } } #endif return buffers [ibuffer]; } const wchar_t * Melder_single (double value) { if (value == NUMundefined) return L"--undefined--"; if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.9g", value); return buffers [ibuffer]; } const wchar_t * Melder_half (double value) { if (value == NUMundefined) return L"--undefined--"; if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.4g", value); return buffers [ibuffer]; } const wchar_t * Melder_fixed (double value, int precision) { int minimumPrecision; if (value == NUMundefined) return L"--undefined--"; if (value == 0.0) return L"0"; if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; if (precision > 60) precision = 60; minimumPrecision = - (int) floor (log10 (value)); swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.*f", minimumPrecision > precision ? minimumPrecision : precision, value); return buffers [ibuffer]; } const wchar_t * Melder_fixedExponent (double value, int exponent, int precision) { double factor = pow (10, exponent); int minimumPrecision; if (value == NUMundefined) return L"--undefined--"; if (value == 0.0) return L"0"; if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; if (precision > 60) precision = 60; value /= factor; minimumPrecision = - (int) floor (log10 (value)); swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.*fE%d", minimumPrecision > precision ? minimumPrecision : precision, value, exponent); return buffers [ibuffer]; } const wchar_t * Melder_percent (double value, int precision) { int minimumPrecision; if (value == NUMundefined) return L"--undefined--"; if (value == 0.0) return L"0"; if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; if (precision > 60) precision = 60; value *= 100.0; minimumPrecision = - (int) floor (log10 (value)); swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.*f%%", minimumPrecision > precision ? minimumPrecision : precision, value); return buffers [ibuffer]; } const wchar_t * Melder_float (const wchar_t *number) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; if (wcschr (number, 'e') == NULL) { wcscpy (buffers [ibuffer], number); } else { wchar_t *b = buffers [ibuffer]; const wchar_t *n = number; while (*n != 'e') *(b++) = *(n++); *b = '\0'; if (number [0] == '1' && number [1] == 'e') { wcscpy (buffers [ibuffer], L"10^^"); b = buffers [ibuffer] + 4; } else { wcscat (buffers [ibuffer], L"\\.c10^^"); b += 7; } Melder_assert (*n == 'e'); if (*++n == '+') n ++; /* Ignore leading plus sign in exponent. */ if (*n == '-') *(b++) = *(n++); /* Copy sign of negative exponent. */ while (*n == '0') n ++; /* Ignore leading zeroes in exponent. */ while (*n >= '0' && *n <= '9') *(b++) = *(n++); *(b++) = '^'; while (*n != '\0') *(b++) = *(n++); *b = '\0'; } return buffers [ibuffer]; } const wchar_t * Melder_naturalLogarithm (double lnNumber) { if (lnNumber == NUMundefined) return L"--undefined--"; if (lnNumber == -INFINITY) return L"0"; double log10Number = lnNumber * NUMlog10e; if (log10Number < -41) { if (++ ibuffer == NUMBER_OF_BUFFERS) ibuffer = 0; long ceiling = ceil (log10Number); double remainder = log10Number - ceiling; double remainder10 = pow (10, remainder); while (remainder10 < 1.0) { remainder10 *= 10; ceiling --; } swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.15g", remainder10); if (wcstod (buffers [ibuffer], NULL) != remainder10) { swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.16g", remainder10); if (wcstod (buffers [ibuffer], NULL) != remainder10) swprintf (buffers [ibuffer], MAXIMUM_NUMERIC_STRING_LENGTH, L"%.17g", remainder10); } swprintf (buffers [ibuffer] + wcslen (buffers [ibuffer]), 100, L"e-%ld", ceiling); } else { return Melder_double (exp (lnNumber)); } return buffers [ibuffer]; } /* End of file melder_ftoa.cpp */ sources_5316/sys/GuiP.h0000644000176700017670000002644211753741756013606 0ustar paulpaul#ifndef _GuiP_h_ #define _GuiP_h_ /* GuiP.h * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Gui.h" /* * In GUI implementations, we order everything by ease of programming: Unix, Windows, Macintosh. */ #if defined (UNIX) #define uni 1 #define win 0 #define mac 0 #endif #if defined (_WIN32) #define uni 0 #define win 1 #define mac 0 #endif #if defined (macintosh) #define uni 0 #define win 0 #define mac 1 #endif void _GuiObject_position (GuiObject me, int left, int right, int top, int bottom); void * _GuiObject_getUserData (GuiObject me); void _GuiObject_setUserData (GuiObject me, void *userData); #if gtk #elif motif #if win #include #include #endif #if win || mac /* #define MEMBER(widget,klas) (widget -> widgetClass == xm##klas##WidgetClass) #define MEMBER2(widget,klas1,klas2) (MEMBER (widget, klas1) || MEMBER (widget, klas2)) #define MEMBER3(widget,klas1,klas2,klas3) (MEMBER2 (widget, klas1, klas2) || MEMBER (widget, klas3)) #define MEMBER4(widget,klas1,klas2,klas3,klas4) (MEMBER3 (widget, klas1, klas2, klas3) || MEMBER (widget, klas4)) #define MEMBER5(widget,klas1,klas2,klas3,klas4,klas5) (MEMBER4 (widget, klas1, klas2, klas3, klas4) || MEMBER (widget, klas5)) */ #define MEMBER(widget,klas) ((widget -> widgetClass & xm##klas##WidgetClass) != 0) #define MEMBER2(widget,klas1,klas2) ((widget -> widgetClass & (xm##klas1##WidgetClass | xm##klas2##WidgetClass)) != 0) #define MEMBER3(widget,klas1,klas2,klas3) ((widget -> widgetClass & (xm##klas1##WidgetClass | xm##klas2##WidgetClass | xm##klas3##WidgetClass)) != 0) #define MEMBER4(widget,klas1,klas2,klas3,klas4) ((widget -> widgetClass & (xm##klas1##WidgetClass | xm##klas2##WidgetClass | xm##klas3##WidgetClass | xm##klas4##WidgetClass)) != 0) #define MEMBER5(widget,klas1,klas2,klas3,klas4,klas5) ((widget -> widgetClass & (xm##klas1##WidgetClass | xm##klas2##WidgetClass | xm##klas3##WidgetClass | xm##klas4##WidgetClass | xm##klas5##WidgetClass)) != 0) #define MAXNUM_CALLBACKS 3 /* E.g., maximum number of activate callbacks for a PushButton. */ typedef struct { struct { XtCallbackProc proc; XtPointer closure; } pairs [MAXNUM_CALLBACKS]; } XtCallbackList; class structGuiObject { public: long magicNumber; unsigned long widgetClass; GuiObject parent, previousSibling, nextSibling, firstChild; wchar_t *name; bool inMenu, nativized, managed, insensitive; GuiObject textFocus; /* For shells. */ GuiObject shell; /* My shell ancestor. */ /* Native. */ #if win HWND window; union { /* XtShell: */ struct { GuiObject menuBar; int uniqueItemID, duringMoveWindow; } shell; /* XmPushButton (if in menu), XmToggleButton (if in menu), XmCascadeButton (if in menu): */ struct { HMENU handle; ULONG_PTR id; } entry; /* XmMenuBar, XmPulldownMenu: */ struct { HMENU handle; ULONG_PTR id; } menu; } nat; #elif mac Rect rect; /* Window coordinates. */ WindowPtr macWindow; bool isControl; struct { /* XtShell: */ struct { WindowPtr ptr; ControlRef rootControl; } window; /* XmPushButton (if not in menu), XmToggleButton (if not in menu), XmScrollBar, XmLabel (sometimes), XmCascadeButton (if not in menu or bar): */ struct { ControlHandle handle; bool isBevel, isPopup; } control; /* XmPushButton (if in menu), XmToggleButton (if in menu), XmCascadeButton (if in menu): */ struct { MenuHandle handle; int item; } entry; /* XmPulldownMenu: */ struct { MenuHandle handle; int item /* if cascading */; int id; } menu; } nat; #endif /* Motif */ union { struct { GuiObject horizontalBar, verticalBar, clipWindow, workWindow; } scrolledWindow; struct { XtCallbackList moveCallbacks; } drawingArea; struct { bool active, isDialog, canFullScreen; unsigned long lowAccelerators [8]; XtCallbackProc goAwayCallback; XtPointer goAwayClosure; } shell; struct { unsigned char acceleratorChar; int acceleratorModifiers; } pushButton; struct { int inBar; } cascadeButton; struct { unsigned char acceleratorChar; int acceleratorModifiers; XtCallbackList valueChangedCallbacks; } toggleButton; struct { XtCallbackList valueChangedCallbacks, dragCallbacks; } scrollBar; } motiff; /* Resources. */ int x, y, width, height; bool isRadioButton; /* For radio buttons and check buttons. */ int radioBehavior, rowColumnType; /* For row-columns. */ int orientation; /* For row-columns and scroll bars. */ GuiObject defaultButton, cancelButton; /* For forms and shells. */ int dialogStyle; /* For forms and shells. */ GuiObject messageText; /* For message boxes. */ bool autoUnmanage; /* For bulletin boards. */ GuiObject subMenuId, popUpButton; /* For cascade buttons and their menus. */ long increment, pageIncrement, sliderSize; /* For scroll bars. */ long minimum, maximum, value; /* For scales and scroll bars. */ XtCallbackProc activateCallback, destroyCallback; XtPointer activateClosure, destroyClosure; int leftAttachment, rightAttachment, topAttachment, bottomAttachment; int leftOffset, rightOffset, topOffset, bottomOffset; int leftPosition, rightPosition, topPosition, bottomPosition; int deleteResponse; /* For shells. */ void *userData; }; #define my me -> extern struct Gui { GuiObject textFocus; bool duringUpdate; #if win HINSTANCE instance; /* First argument of WinMain. */ #elif mac WindowPtr modalDialog; #endif } theGui; void _Gui_callCallbacks (GuiObject w, XtCallbackList *callbacks, XtPointer call); #if mac void _GuiMac_clipOnParent (GuiObject me); void _GuiMac_clipOffValid (GuiObject me); void _GuiMac_clipOffInvalid (GuiObject me); #elif win wchar_t * _GuiWin_getDrawingAreaClassName (void); #endif GuiObject _Gui_initializeWidget (int widgetClass, GuiObject parent, const wchar_t *name); void _Gui_invalidateWidget (GuiObject me); void _Gui_validateWidget (GuiObject me); void _Gui_manageScrolledWindow (GuiObject me); void _GuiNativeControl_check (GuiObject me, Boolean value); void _GuiNativeControl_destroy (GuiObject me); void _GuiNativeControl_setFont (GuiObject me, int style, int size); void _GuiNativeControl_setTitle (GuiObject me); void _GuiNativeControl_show (GuiObject me); void _GuiNativeControl_hide (GuiObject me); void _GuiNativeControl_setSensitive (GuiObject me); wchar_t * _GuiWin_expandAmpersands (const wchar_t *title); /********** GuiButton.cpp **********/ #if win void _GuiWinButton_destroy (GuiObject widget); void _GuiWinButton_handleClick (GuiObject widget); bool _GuiWinButton_tryToHandleShortcutKey (GuiObject widget); #elif mac void _GuiMacButton_destroy (GuiObject widget); void _GuiMacButton_handleClick (GuiObject widget, EventRecord *macEvent); bool _GuiMacButton_tryToHandleShortcutKey (GuiObject widget, EventRecord *macEvent); #endif /********** GuiCheckButton.cpp **********/ #if win void _GuiWinCheckButton_destroy (GuiObject widget); void _GuiWinCheckButton_handleClick (GuiObject widget); #elif mac void _GuiMacCheckButton_destroy (GuiObject widget); void _GuiMacCheckButton_handleClick (GuiObject widget, EventRecord *macEvent); #endif /********** GuiDrawingArea.cpp **********/ #if win void _GuiWinDrawingArea_destroy (GuiObject widget); void _GuiWinDrawingArea_update (GuiObject widget); void _GuiWinDrawingArea_handleClick (GuiObject widget, int x, int y); void _GuiWinDrawingArea_handleKey (GuiObject widget, TCHAR kar); void _GuiWinDrawingArea_shellResize (GuiObject widget); #elif mac void _GuiMacDrawingArea_destroy (GuiObject widget); void _GuiMacDrawingArea_update (GuiObject widget); void _GuiMacDrawingArea_handleClick (GuiObject widget, EventRecord *macEvent); bool _GuiMacDrawingArea_tryToHandleKey (GuiObject widget, EventRecord *macEvent); void _GuiMacDrawingArea_shellResize (GuiObject widget); #endif /********** GuiLabel.cpp **********/ #if win void _GuiWinLabel_destroy (GuiObject widget); #elif mac void _GuiMacLabel_destroy (GuiObject widget); #endif /********** GuiList.cpp **********/ #if win void _GuiWinList_destroy (GuiObject widget); void _GuiWinList_map (GuiObject widget); void _GuiWinList_destroy (GuiObject widget); void _GuiWinList_handleClick (GuiObject widget); #elif mac void _GuiMacList_destroy (GuiObject widget); void _GuiMacList_map (GuiObject widget); void _GuiMacList_activate (GuiObject widget, bool activate); void _GuiMacList_handleClick (GuiObject widget, EventRecord *event); void _GuiMacList_handleControlClick (GuiObject widget, EventRecord *event); void _GuiMacList_move (GuiObject widget); void _GuiMacList_resize (GuiObject widget); void _GuiMacList_shellResize (GuiObject widget); void _GuiMacList_update (GuiObject widget, RgnHandle visRgn); #endif /********** GuiRadioButton.cpp **********/ #if win void _GuiWinRadioButton_destroy (GuiObject widget); void _GuiWinRadioButton_handleClick (GuiObject widget); #elif mac void _GuiMacRadioButton_destroy (GuiObject widget); void _GuiMacRadioButton_handleClick (GuiObject widget, EventRecord *macEvent); #endif /********** GuiText.cpp **********/ #if win void _GuiWinText_destroy (GuiObject widget); void _GuiWinText_map (GuiObject widget); #elif mac void _GuiMacText_destroy (GuiObject widget); void _GuiMacText_map (GuiObject widget); #endif void _GuiText_handleFocusReception (GuiObject widget); void _GuiText_handleFocusLoss (GuiObject widget); #if mac void _GuiMac_clearTheTextFocus (void); #endif void _GuiText_setTheTextFocus (GuiObject widget); void _GuiText_handleValueChanged (GuiObject widget); void _GuiText_unmanage (GuiObject widget); #if mac void _GuiMacText_move (GuiObject widget); void _GuiMacText_shellResize (GuiObject widget); void _GuiMacText_resize (GuiObject widget); void _GuiMacText_update (GuiObject widget); int _GuiMacText_tryToHandleKey (EventHandlerCallRef eventHandlerCallRef, EventRef eventRef, GuiObject widget, unsigned char keyCode, unsigned char charCode, EventRecord *event); int _GuiMacText_tryToHandleReturnKey (EventHandlerCallRef eventHandlerCallRef, EventRef eventRef, GuiObject widget, EventRecord *event); int _GuiMacText_tryToHandleClipboardShortcut (EventHandlerCallRef eventHandlerCallRef, EventRef eventRef, GuiObject widget, unsigned char charCode, EventRecord *event); void _GuiMacText_handleClick (GuiObject widget, EventRecord *event); void _GuiMac_makeTextCaretBlink (void); #endif void _GuiText_init (void); void _GuiText_exit (void); #endif #endif /* End of file GuiP.h */ #endif sources_5316/sys/melder_enums.h0000644000176700017670000001264211476541043015403 0ustar paulpaul/* melder_enums.h * * Copyright (C) 2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/07 */ enums_begin (kMelder_number, 1) enums_add (kMelder_number, 1, EQUAL_TO, L"equal to") enums_add (kMelder_number, 2, NOT_EQUAL_TO, L"not equal to") enums_add (kMelder_number, 3, LESS_THAN, L"less than") enums_add (kMelder_number, 4, LESS_THAN_OR_EQUAL_TO, L"less than or equal to") enums_add (kMelder_number, 5, GREATER_THAN, L"greater than") enums_add (kMelder_number, 6, GREATER_THAN_OR_EQUAL_TO, L"greater than or equal to") /* For reading old preferences files: */ enums_alt (kMelder_number, EQUAL_TO, L"1") enums_alt (kMelder_number, NOT_EQUAL_TO, L"2") enums_alt (kMelder_number, LESS_THAN, L"3") enums_alt (kMelder_number, LESS_THAN_OR_EQUAL_TO, L"4") enums_alt (kMelder_number, GREATER_THAN, L"5") enums_alt (kMelder_number, GREATER_THAN_OR_EQUAL_TO, L"6") enums_end (kMelder_number, 6, EQUAL_TO) enums_begin (kMelder_string, 1) enums_add (kMelder_string, 1, EQUAL_TO, L"is equal to") enums_add (kMelder_string, 2, NOT_EQUAL_TO, L"is not equal to") enums_add (kMelder_string, 3, CONTAINS, L"contains") enums_add (kMelder_string, 4, DOES_NOT_CONTAIN, L"does not contain") enums_add (kMelder_string, 5, STARTS_WITH, L"starts with") enums_add (kMelder_string, 6, DOES_NOT_START_WITH, L"does not start with") enums_add (kMelder_string, 7, ENDS_WITH, L"ends with") enums_add (kMelder_string, 8, DOES_NOT_END_WITH, L"does not end with") enums_add (kMelder_string, 9, MATCH_REGEXP, L"matches (regex)") /* For reading old preferences files: */ enums_alt (kMelder_string, EQUAL_TO, L"1") enums_alt (kMelder_string, NOT_EQUAL_TO, L"2") enums_alt (kMelder_string, CONTAINS, L"3") enums_alt (kMelder_string, DOES_NOT_CONTAIN, L"4") enums_alt (kMelder_string, STARTS_WITH, L"5") enums_alt (kMelder_string, DOES_NOT_START_WITH, L"6") enums_alt (kMelder_string, ENDS_WITH, L"7") enums_alt (kMelder_string, DOES_NOT_END_WITH, L"8") enums_alt (kMelder_string, MATCH_REGEXP, L"9") enums_end (kMelder_string, 9, EQUAL_TO) enums_begin (kMelder_textInputEncoding, 1) enums_add (kMelder_textInputEncoding, 1, UTF8, L"UTF-8") enums_add (kMelder_textInputEncoding, 2, UTF8_THEN_ISO_LATIN1, L"try UTF-8, then ISO Latin-1") enums_add (kMelder_textInputEncoding, 3, ISO_LATIN1, L"ISO Latin-1") enums_add (kMelder_textInputEncoding, 4, UTF8_THEN_WINDOWS_LATIN1, L"try UTF-8, then Windows Latin-1") enums_add (kMelder_textInputEncoding, 5, WINDOWS_LATIN1, L"Windows Latin-1") enums_add (kMelder_textInputEncoding, 6, UTF8_THEN_MACROMAN, L"try UTF-8, then MacRoman") enums_add (kMelder_textInputEncoding, 7, MACROMAN, L"MacRoman") /* For reading old preferences files: */ enums_alt (kMelder_textInputEncoding, UTF8, L"1") enums_alt (kMelder_textInputEncoding, UTF8_THEN_ISO_LATIN1, L"2") enums_alt (kMelder_textInputEncoding, ISO_LATIN1, L"3") enums_alt (kMelder_textInputEncoding, UTF8_THEN_WINDOWS_LATIN1, L"4") enums_alt (kMelder_textInputEncoding, WINDOWS_LATIN1, L"5") enums_alt (kMelder_textInputEncoding, UTF8_THEN_MACROMAN, L"6") enums_alt (kMelder_textInputEncoding, MACROMAN, L"7") #if defined (macintosh) enums_end (kMelder_textInputEncoding, 7, UTF8_THEN_MACROMAN) #elif defined (_WIN32) enums_end (kMelder_textInputEncoding, 7, UTF8_THEN_WINDOWS_LATIN1) #else enums_end (kMelder_textInputEncoding, 7, UTF8_THEN_ISO_LATIN1) #endif enums_begin (kMelder_textOutputEncoding, 1) enums_add (kMelder_textOutputEncoding, 1, UTF8, L"UTF-8") enums_add (kMelder_textOutputEncoding, 2, UTF16, L"UTF-16") enums_add (kMelder_textOutputEncoding, 3, ASCII_THEN_UTF16, L"try ASCII, then UTF-16") enums_add (kMelder_textOutputEncoding, 4, ISO_LATIN1_THEN_UTF16, L"try ISO Latin-1, then UTF-16") /* For reading old preferences files: */ enums_alt (kMelder_textOutputEncoding, UTF8, L"1") enums_alt (kMelder_textOutputEncoding, UTF16, L"2") enums_alt (kMelder_textOutputEncoding, ASCII_THEN_UTF16, L"3") enums_alt (kMelder_textOutputEncoding, ISO_LATIN1_THEN_UTF16, L"4") enums_end (kMelder_textOutputEncoding, 4, ASCII_THEN_UTF16) enums_begin (kMelder_asynchronicityLevel, 0) enums_add (kMelder_asynchronicityLevel, 0, SYNCHRONOUS, L"synchronous (nothing)") enums_add (kMelder_asynchronicityLevel, 1, CALLING_BACK, L"calling back (view running cursor)") enums_add (kMelder_asynchronicityLevel, 2, INTERRUPTABLE, L"interruptable (Escape key stops playing)") enums_add (kMelder_asynchronicityLevel, 3, ASYNCHRONOUS, L"asynchronous (anything)") /* For reading old preferences files: */ enums_alt (kMelder_asynchronicityLevel, SYNCHRONOUS, L"0") enums_alt (kMelder_asynchronicityLevel, CALLING_BACK, L"1") enums_alt (kMelder_asynchronicityLevel, INTERRUPTABLE, L"2") enums_alt (kMelder_asynchronicityLevel, ASYNCHRONOUS, L"3") enums_end (kMelder_asynchronicityLevel, 3, ASYNCHRONOUS) /* End of file melder_enums.h */ sources_5316/sys/Data.h0000644000176700017670000004072611724662321013600 0ustar paulpaul#ifndef _Data_h_ #define _Data_h_ /* Data.h * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Data inherits from Thing. */ /* It adds the functionality of reproduction, comparison, reading, and writing. */ #include "Thing.h" typedef struct structData_Description { const wchar *name; /* The name of this field. */ int type; /* bytewa..inheritwa, see below */ int offset; /* The offset of this field in the enveloping struct. */ int size; /* The size of this field if it is in an array. */ const wchar *tagName; /* For structs: tag; for classes: class name; for enums: type name. */ void *tagType; /* For structs: offset table; for classes: class pointer; for enums: enum pointer. */ int rank; /* 0 = single, 1 = vector, 2 = matrix, 3 = set, -1 = array. */ const wchar *min1, *max1; /* For vectors and matrices. */ const wchar *min2, *max2; /* For matrices. */ } *Data_Description; Thing_define (Data, Thing) { // new methods: public: virtual void v_copy (Any data_to); virtual bool v_equal (Any otherData); virtual Data_Description v_description () { return NULL; } virtual bool v_writable () { return true; } virtual bool v_canWriteAsEncoding (int outputEncoding); virtual void v_writeText (MelderFile openFile); virtual void v_readText (MelderReadText text); virtual void v_writeBinary (FILE *f); virtual void v_readBinary (FILE *f); // messages for scripting: virtual bool v_hasGetNrow () { return false; } virtual double v_getNrow () { return NUMundefined; } virtual bool v_hasGetNcol () { return false; } virtual double v_getNcol () { return NUMundefined; } virtual bool v_hasGetXmin () { return false; } virtual double v_getXmin () { return NUMundefined; } virtual bool v_hasGetXmax () { return false; } virtual double v_getXmax () { return NUMundefined; } virtual bool v_hasGetYmin () { return false; } virtual double v_getYmin () { return NUMundefined; } virtual bool v_hasGetYmax () { return false; } virtual double v_getYmax () { return NUMundefined; } virtual bool v_hasGetNx () { return false; } virtual double v_getNx () { return NUMundefined; } virtual bool v_hasGetNy () { return false; } virtual double v_getNy () { return NUMundefined; } virtual bool v_hasGetDx () { return false; } virtual double v_getDx () { return NUMundefined; } virtual bool v_hasGetDy () { return false; } virtual double v_getDy () { return NUMundefined; } virtual bool v_hasGetX () { return false; } virtual double v_getX (long ix) { return NUMundefined; (void) ix; } virtual bool v_hasGetY () { return false; } virtual double v_getY (long iy) { return NUMundefined; (void) iy; } virtual bool v_hasGetRowStr () { return false; } virtual const wchar * v_getRowStr (long irow) { return NULL; (void) irow; } virtual bool v_hasGetColStr () { return false; } virtual const wchar * v_getColStr (long icol) { return NULL; (void) icol; } virtual bool v_hasGetCell () { return false; } virtual double v_getCell () { return NUMundefined; } virtual bool v_hasGetCellStr () { return false; } virtual const wchar * v_getCellStr () { return NULL; } virtual bool v_hasGetVector () { return false; } virtual double v_getVector (long irow, long icol) { return NUMundefined; (void) irow; (void) icol; } virtual bool v_hasGetVectorStr () { return false; } virtual const wchar * v_getVectorStr (long icol) { return NULL; (void) icol; } virtual bool v_hasGetMatrix () { return false; } virtual double v_getMatrix (long irow, long icol) { return NUMundefined; (void) irow; (void) icol; } virtual bool v_hasGetMatrixStr () { return false; } virtual const wchar * v_getMatrixStr (long irow, long icol) { return NULL; (void) irow; (void) icol; } virtual bool v_hasGetFunction0 () { return false; } virtual double v_getFunction0 () { return NUMundefined; } virtual bool v_hasGetFunction1 () { return false; } virtual double v_getFunction1 (long irow, double x) { return NUMundefined; (void) irow; (void) x; } virtual bool v_hasGetFunction2 () { return false; } virtual double v_getFunction2 (double x, double y) { return NUMundefined; (void) x; (void) y; } virtual bool v_hasGetRowIndex () { return false; } virtual double v_getRowIndex (const wchar *rowLabel) { return NUMundefined; (void) rowLabel; } virtual bool v_hasGetColIndex () { return false; } virtual double v_getColIndex (const wchar *colLabel) { return NUMundefined; (void) colLabel; } }; template T* Data_copy (T* data) { return static_cast (_Data_copy (data)); } Any _Data_copy (Data me); /* Message: "return a deep copy of yourself." Postconditions: result -> name == NULL; // the only attribute NOT copied */ bool Data_equal (Data data1, Data data2); /* Message: "return 1 if the shallow or deep attributes of 'data1' and 'data2' are equal; otherwise, return 0." Comment: Data_equal (data, Data_copy (data)) should always return 1; the names are not compared. */ typedef int (*Data_CompareFunction) (Any data1, Any data2); bool Data_canWriteAsEncoding (Data me, int outputEncoding); /* Message: "Can you write yourself in that encoding?" The answer depends on whether all members can be written in that encoding. */ bool Data_canWriteText (Data me); /* Message: "Can you write yourself as text?" The answer depends on whether the subclass defines the 'writeText' method. */ MelderFile Data_createTextFile ( Data me, MelderFile file, bool verbose ); // returns the input MelderFile in order to be caught by an autoMelderFile void Data_writeText (Data me, MelderFile openFile); /* Message: "try to write yourself as text to an open file." Return value: 1 if OK, 0 in case of failure. Failures: I/O error. Disk full. Description: The format depends on the 'writeText' method defined by the subclass. */ void Data_writeToTextFile (Data me, MelderFile file); /* Message: "try to write yourself as text to a file". Description: The first line is 'File type = "ooTextFile"'. Your class name is written in the second line, e.g., if you are a Person, the second line will be 'Object class = "Person"'. The format of the lines after the second line is the same as in Data_writeText. */ void Data_writeToShortTextFile (Data me, MelderFile file); /* Message: "try to write yourself as text to a file". Description: The first line is 'File type = "ooTextFile short"'. Your class name is written in the second line, e.g., if you are a Person, the second line will be '"Person"'. The format of the lines after the second line is the same as in Data_writeText. */ bool Data_canWriteBinary (Data me); /* Message: "Can you write yourself as binary data?" The answer depends on whether the subclass defines the 'writeBinary' method. */ void Data_writeBinary (Data me, FILE *f); /* Message: "try to write yourself as binary data to an open file." Failures: I/O error. Disk full. Description: The format depends on the 'writeBinary' method defined by the subclass, but is machine independent because it always uses 'most significant byte first' and IEEE floating-point format. */ void Data_writeToBinaryFile (Data me, MelderFile file); /* Message: "try to write yourself as binary data to a file". Description: First, your class name is written in the file, e.g., if you are a Person, the file will start with "PersonBinaryFile". The format of the file after this is the same as in Data_writeBinary. */ bool Data_canWriteLisp (Data me); /* Message: "Can you write yourself as a sequece of LISP objects?" The answer depends on whether the subclass defines a 'writeLisp' method. */ void Data_writeLisp (Data me, FILE *f); /* Message: "try to write yourself as a sequence of LISP objects to the stream ." Failures: I/O error. Disk full. Description: The format depends on the 'writeLisp' method defined by the subclass. */ void Data_writeLispToConsole (Data me); /* Message: "try to write yourself as a sequence of LISP objects to the standard output." Return value: 1 if OK, 0 in case of failure. Description: The format is the same as in Data_writeLisp. The standard output will most often be a window named "Console". */ /* The routines Data_readXXX assume that a class can be read from its name (a string). You should have called Thing_recognizeClassesByName () for all the classes that you want to read by name. This call is best placed in the beginning of main (). */ bool Data_canReadText (Data me); /* Message: "Can you read yourself as text?" The answer depends on whether the subclass defines a 'readText' method, but is preferably the same as the answer from Data_canWriteText. */ void Data_readText (Data me, MelderReadText text); /* Message: "try to read yourself as text from a string." Failures: The 'readText' method of the subclass failed. I/O error. Early end of file detected. Description: The format depends on the 'readText' method defined by the subclass, but is preferably the same as the format produced by the 'writeText' method. */ Any Data_readFromTextFile (MelderFile file); /* Message: "try to read a Data as text from a file". Description: The Data's class name is read from the first line, e.g., if the first line is "PersonTextFile", the Data will be a Person. The format of the lines after the first line is the same as in Data_readText. Return value: the new object. Failures: Error opening file . The file does not contain an object. (plus those from Data_readText) */ bool Data_canReadBinary (Data me); /* Message: "Can you read yourself as binary data?" The answer depends on whether the subclass defines a 'readBinary' method, but is preferably the same as the answer from Data_canWriteBinary. */ void Data_readBinary (Data me, FILE *f); /* Message: "try to read yourself as binary data from the stream ." Failures: The 'readBinary' method of the subclass throws an error. I/O error. Early end of file detected. Description: The format depends on the 'readBinary' method defined by the subclass, but is preferably the same as the format produced by the 'writeBinary' method. */ Any Data_readFromBinaryFile (MelderFile file); /* Message: "try to read a Data as binary data from a file". Description: The Data's class name is read from the start of the file, e.g., if the file starts with is "PersonBinaryFile", the Data will be a Person. The format of the file after this is the same as in Data_readBinary. Return value: the new object. Failures: Error opening file . The file does not contain an object. (plus those from Data_readBinary) */ void Data_recognizeFileType (Any (*recognizer) (int nread, const char *header, MelderFile fs)); /* Purpose: to make sure that a file can be read by Data_readFromFile. Arguments: recognizer a routine that tries to identify a file as being of a certain type, from the information in the header of the file and/or from the file name. If the identification succeeds, the recognizer routine should call the routine that actually reads the file. nread the length of the header of the file. The maximum value of nread is 512, but it is smaller if the file is shorter than 512 bytes. header a buffer that contains the first nread bytes of the file; the data were put there by Data_readFromFile before calling the recognizers. The first byte is in header [0]. fileName the name of the file that is to be recognized. The recognizer routine uses this name to actually read the file if it positively identifies the file. The recognizer routine may also use %fileName in the recognition process; e.g. some files with raw sound data have names that make them recognizable as files with raw sound data. Defining a file-type recognizer: You define a file-type recognizer as in the following example, which tries to identify and read a Sun audio file. A Sun audio file should contain at least 24 bytes and start with the string ".snd": Any Sound_sunAudioFileRecognizer (int nread, const char *header, const char *fileName) { if (nread >= 24 && strnequ (& header [0], ".snd", 4)) return Sound_readFromSunAudioFile (fileName); else return NULL; } From this example, we see that if the file is recognized, it should be read immediately, and the resulting object (always a descendant of class Data) should be returned. We also see that the return value NULL is used for notifying Data_readFromFile of the fact that the file is not a Sun audio file. Registering a file-type recognizer: You would put a statement like the following in the initialization section of your program: Data_recognizeFileType (Sound_sunAudioFileRecognizer); After this, Data_readFromFile is able to read Sun audio files. */ Any Data_readFromFile (MelderFile file); /* Purpose: to read a file with data of any kind. Return value: the object read from the file fs, or NULL if the file was not recognized (an error message is queued in that case). Behaviour: Data_readFromFile first checks whether the file is a text file that is readable by Data_readFromTextFile, or a binary file written by Data_writeToBinaryFile, or a file as written by Data_writeToLispFile. If one of these succeeds, the file is read and the resulting object is returned. If not, the recognizers installed with Data_recognizeFileType are tried. If this also fails, Data_readFromFile returns NULL. */ extern structMelderDir Data_directoryBeingRead; /* The values of 'type' in struct descriptions. */ #define bytewa 1 #define intwa 2 #define longwa 3 #define ubytewa 4 #define uintwa 5 #define ulongwa 6 #define boolwa 7 #define floatwa 8 #define doublewa 9 #define fcomplexwa 10 #define dcomplexwa 11 #define enumwa 12 #define lenumwa 13 #define booleanwa 14 #define questionwa 15 #define stringwa 16 #define lstringwa 17 #define maxsingletypewa lstringwa #define structwa 18 #define widgetwa 19 #define objectwa 20 #define collectionwa 21 #define inheritwa 22 /* Recursive routines for working with struct members. */ int Data_Description_countMembers (Data_Description structDescription); /* Including inherited members. */ Data_Description Data_Description_findMatch (Data_Description structDescription, const wchar_t *member); /* Find the location of member 'member' in a struct. */ /* If 'structDescription' describes a class, the ancestor classes are also searched. */ Data_Description Data_Description_findNumberUse (Data_Description structDescription, const wchar_t *string); /* Find the first member that uses member 'string' in its size description (max1 or max2 fields). */ /* Retrieving data from object + description. */ long Data_Description_integer (void *structAddress, Data_Description description); /* Convert data found at a certain offset from 'address' to an integer, according to the given 'description'. */ int Data_Description_evaluateInteger (void *structAddress, Data_Description structDescription, const wchar_t *formula, long *result); /* * Translates a string like '100' or 'numberOfHorses' or 'numberOfCows - 1' to an integer. * The 'algorithm' does some wild guesses as to the meanings of the 'min1' and 'max1' strings. * A full-fledged interpretation is preferable... * Returns 0 if 'formula' cannot be parsed to a number. */ /* End of file Data.h */ #endif sources_5316/sys/GuiFileSelect.cpp0000644000176700017670000002773211753741756015764 0ustar paulpaul/* GuiFileSelect.cpp * * Copyright (C) 2010-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2010/07/26 split off from UiFile.c * pb 2010/11/27 GuiFileSelect_getDirectoryName () * pb 2011/04/06 C++ * pb 2011/07/05 C++ */ #include "Gui.h" #ifdef _WIN32 #include #endif SortedSetOfString GuiFileSelect_getInfileNames (GuiObject parent, const wchar *title, bool allowMultipleFiles) { autoSortedSetOfString me = SortedSetOfString_create (); #if gtk (void) parent; GuiObject dialog = gtk_file_chooser_dialog_new (Melder_peekWcsToUtf8 (title), NULL, GTK_FILE_CHOOSER_ACTION_OPEN, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT, NULL); gtk_file_chooser_set_select_multiple (GTK_FILE_CHOOSER (dialog), allowMultipleFiles); if (gtk_dialog_run (GTK_DIALOG (dialog)) == GTK_RESPONSE_ACCEPT) { GSList *infileNames_list = gtk_file_chooser_get_filenames (GTK_FILE_CHOOSER (dialog)); for (GSList *element = infileNames_list; element != NULL; element = g_slist_next (element)) { char *infileName_utf8 = (char *) element -> data; my addString (Melder_peekUtf8ToWcs (infileName_utf8)); therror g_free (infileName_utf8); } g_slist_free (infileNames_list); } gtk_widget_destroy (GTK_WIDGET (dialog)); #elif defined (macintosh) (void) parent; OSStatus err; NavDialogRef dialogRef; NavDialogCreationOptions dialogOptions; NavGetDefaultDialogCreationOptions (& dialogOptions); dialogOptions. optionFlags |= kNavDontAutoTranslate; //dialogOptions. windowTitle = (CFStringRef) Melder_peekWcsToCfstring (title); if (! allowMultipleFiles) dialogOptions. optionFlags &= ~ kNavAllowMultipleFiles; err = NavCreateChooseFileDialog (& dialogOptions, NULL, NULL, NULL, NULL, NULL, & dialogRef); if (err == noErr) { NavReplyRecord reply; [(NSOpenPanel *) dialogRef setTitle: (NSString *) Melder_peekWcsToCfstring (title)]; NavDialogRun (dialogRef); err = NavDialogGetReply (dialogRef, & reply); if (err == noErr && reply. validRecord) { long numberOfSelectedFiles; AECountItems (& reply. selection, & numberOfSelectedFiles); for (int ifile = 1; ifile <= numberOfSelectedFiles; ifile ++) { AEKeyword keyWord; DescType typeCode; Size actualSize = 0; FSRef machFile; structMelderFile file; if ((err = AEGetNthPtr (& reply. selection, ifile, typeFSRef, & keyWord, & typeCode, & machFile, sizeof (FSRef), & actualSize)) == noErr) Melder_machToFile (& machFile, & file); my addString (Melder_fileToPath (& file)); therror } NavDisposeReply (& reply); } NavDialogDispose (dialogRef); } #elif defined (_WIN32) static OPENFILENAMEW openFileName, dummy; static wchar_t fullFileName [3000+2]; ZeroMemory (& openFileName, sizeof (OPENFILENAMEW)); openFileName. lStructSize = sizeof (OPENFILENAMEW); openFileName. hwndOwner = parent ? (HWND) XtWindow (parent) : NULL; openFileName. hInstance = NULL; openFileName. lpstrFilter = L"All Files\0*.*\0"; ZeroMemory (fullFileName, (3000+2) * sizeof (wchar_t)); openFileName. lpstrCustomFilter = NULL; openFileName. nMaxCustFilter = 0; openFileName. lpstrFile = fullFileName; openFileName. nMaxFile = 3000; openFileName. lpstrFileTitle = NULL; openFileName. nMaxFileTitle = 0; openFileName. lpstrInitialDir = NULL; openFileName. lpstrTitle = title; openFileName. Flags = OFN_EXPLORER | OFN_LONGNAMES | OFN_FILEMUSTEXIST | OFN_HIDEREADONLY | (allowMultipleFiles ? OFN_ALLOWMULTISELECT : 0); openFileName. lpstrDefExt = NULL; openFileName. lpfnHook = NULL; openFileName. lpTemplateName = NULL; openFileName. pvReserved = NULL; openFileName. dwReserved = 0; openFileName. FlagsEx = 0; OSVERSIONINFO osVersionInfo; ZeroMemory (& osVersionInfo, sizeof (OSVERSIONINFO)); osVersionInfo. dwOSVersionInfoSize = sizeof (OSVERSIONINFO); GetVersionEx (& osVersionInfo); if (GetOpenFileNameW (& openFileName)) { int firstFileNameLength = wcslen (fullFileName); if (fullFileName [firstFileNameLength + 1] == '\0') { /* * The user selected one file. */ my addString (fullFileName); therror } else { /* * The user selected multiple files. * 'fullFileName' is a directory name; the file names follow. */ structMelderDir dir; Melder_pathToDir (fullFileName, & dir); for (const wchar_t *p = & fullFileName [firstFileNameLength + 1]; *p != '\0'; p += wcslen (p) + 1) { structMelderFile file; MelderDir_getFile (& dir, p, & file); my addString (Melder_fileToPath (& file)); therror } } } #endif return me.transfer(); } wchar * GuiFileSelect_getOutfileName (GuiObject parent, const wchar *title, const wchar *defaultName) { wchar *outfileName = NULL; #if gtk (void) parent; static structMelderFile file; GuiObject dialog = gtk_file_chooser_dialog_new (Melder_peekWcsToUtf8 (title), NULL, GTK_FILE_CHOOSER_ACTION_SAVE, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_SAVE, GTK_RESPONSE_ACCEPT, NULL); gtk_file_chooser_set_do_overwrite_confirmation (GTK_FILE_CHOOSER (dialog), TRUE); if (file. path [0] != '\0') { gtk_file_chooser_set_filename (GTK_FILE_CHOOSER (dialog), Melder_peekWcsToUtf8 (file. path)); } gtk_file_chooser_set_current_name (GTK_FILE_CHOOSER (dialog), Melder_peekWcsToUtf8 (defaultName)); if (gtk_dialog_run (GTK_DIALOG (dialog)) == GTK_RESPONSE_ACCEPT) { char *outfileName_utf8 = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (dialog)); outfileName = Melder_utf8ToWcs (outfileName_utf8); g_free (outfileName_utf8); Melder_pathToFile (outfileName, & file); } gtk_widget_destroy (GTK_WIDGET (dialog)); #elif defined (macintosh) (void) parent; const wchar *lastSlash = wcsrchr (defaultName, Melder_DIRECTORY_SEPARATOR); OSStatus err; NavDialogRef dialogRef; NavDialogCreationOptions dialogOptions; NavGetDefaultDialogCreationOptions (& dialogOptions); dialogOptions. windowTitle = (CFStringRef) Melder_peekWcsToCfstring (title); //dialogOptions. message = (CFStringRef) Melder_peekWcsToCfstring (title); dialogOptions. saveFileName = (CFStringRef) Melder_peekWcsToCfstring (lastSlash ? lastSlash + 1 : defaultName); dialogOptions. optionFlags |= kNavNoTypePopup; err = NavCreatePutFileDialog (& dialogOptions, 0, 0, NULL, NULL, & dialogRef); if (err == noErr) { NavReplyRecord reply; NavDialogRun (dialogRef); err = NavDialogGetReply (dialogRef, & reply); if (Melder_debug == 19) { Melder_casual ("err %d %d", err, reply. validRecord); } if (err == noErr && reply. validRecord) { AEKeyword keyWord; DescType typeCode; Size actualSize = 0; FSRef machFile; if ((err = AEGetNthPtr (& reply. selection, 1, typeFSRef, & keyWord, & typeCode, & machFile, sizeof (FSRef), & actualSize)) == noErr) { CFStringRef outfileName_cf = NavDialogGetSaveFileName (dialogRef); // "Get", therefore it's not ours. /* * machFile contains the directory as e.g. "/" or "/Users/jane"; in the latter (most usual) case, append a slash. */ char directoryPath_utf8 [1000]; FSRefMakePath (& machFile, (unsigned char *) directoryPath_utf8, 999); if (! (directoryPath_utf8 [0] == '/' && directoryPath_utf8 [1] == '\0')) strcat (directoryPath_utf8, "/"); structMelderFile file; Melder_8bitToWcs_inline (directoryPath_utf8, file. path, kMelder_textInputEncoding_UTF8); // BUG throwable int dirLength = wcslen (file. path); int n = CFStringGetLength (outfileName_cf); wchar_t *p = file. path + dirLength; for (int i = 0; i < n; i ++, p ++) *p = CFStringGetCharacterAtIndex (outfileName_cf, i); *p = '\0'; outfileName = Melder_wcsdup_f (file. path); } NavDisposeReply (& reply); } NavDialogDispose (dialogRef); } #elif defined (_WIN32) OPENFILENAMEW openFileName; static wchar_t customFilter [100+2]; static wchar_t fullFileName [300+2]; long n = wcslen (defaultName); for (long i = 0; i <= n; i ++) { fullFileName [i] = defaultName [i]; } openFileName. lStructSize = sizeof (OPENFILENAMEW); openFileName. hwndOwner = parent ? (HWND) XtWindow (parent) : NULL; openFileName. lpstrFilter = NULL; /* like *.txt */ openFileName. lpstrCustomFilter = customFilter; openFileName. nMaxCustFilter = 100; openFileName. lpstrFile = fullFileName; openFileName. nMaxFile = 300; openFileName. lpstrFileTitle = NULL; openFileName. lpstrInitialDir = NULL; openFileName. lpstrTitle = title; openFileName. Flags = OFN_LONGNAMES | OFN_OVERWRITEPROMPT | OFN_EXPLORER | OFN_HIDEREADONLY; openFileName. lpstrDefExt = NULL; if (GetSaveFileNameW (& openFileName)) { outfileName = Melder_wcsdup_f (fullFileName); } #endif return outfileName; } wchar * GuiFileSelect_getDirectoryName (GuiObject parent, const wchar *title) { wchar *directoryName = NULL; #if gtk (void) parent; static structMelderFile file; GuiObject dialog = gtk_file_chooser_dialog_new (Melder_peekWcsToUtf8 (title), NULL, GTK_FILE_CHOOSER_ACTION_SELECT_FOLDER, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, "Choose", GTK_RESPONSE_ACCEPT, NULL); if (file. path [0] != '\0') { gtk_file_chooser_set_filename (GTK_FILE_CHOOSER (dialog), Melder_peekWcsToUtf8 (file. path)); } if (gtk_dialog_run (GTK_DIALOG (dialog)) == GTK_RESPONSE_ACCEPT) { char *directoryName_utf8 = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (dialog)); directoryName = Melder_utf8ToWcs (directoryName_utf8); g_free (directoryName_utf8); Melder_pathToFile (directoryName, & file); } gtk_widget_destroy (GTK_WIDGET (dialog)); #elif defined (macintosh) (void) parent; OSStatus err; NavDialogRef dialogRef; NavDialogCreationOptions dialogOptions; NavGetDefaultDialogCreationOptions (& dialogOptions); dialogOptions. windowTitle = (CFStringRef) Melder_peekWcsToCfstring (title); dialogOptions. optionFlags |= kNavDontAutoTranslate; dialogOptions. optionFlags &= ~ kNavAllowMultipleFiles; err = NavCreateChooseFolderDialog (& dialogOptions, NULL, NULL, NULL, & dialogRef); if (err == noErr) { NavReplyRecord reply; NavDialogRun (dialogRef); err = NavDialogGetReply (dialogRef, & reply); if (Melder_debug == 19) { Melder_casual ("err %d %d", err, reply. validRecord); } if (err == noErr && reply. validRecord) { AEKeyword keyWord; DescType typeCode; Size actualSize = 0; FSRef machFile; structMelderFile file; if ((err = AEGetNthPtr (& reply. selection, 1, typeFSRef, & keyWord, & typeCode, & machFile, sizeof (FSRef), & actualSize)) == noErr) { Melder_machToFile (& machFile, & file); directoryName = Melder_wcsdup_f (Melder_fileToPath (& file)); } NavDisposeReply (& reply); } NavDialogDispose (dialogRef); } #elif defined (_WIN32) static wchar fullFileName [3000+2]; static bool comInited = false; if (! comInited) { CoInitializeEx (NULL, COINIT_APARTMENTTHREADED); comInited = true; } static BROWSEINFO info; info. hwndOwner = parent ? (HWND) XtWindow (parent) : NULL; info. ulFlags = BIF_USENEWUI; info. pidlRoot = NULL; // everything on the computer should be browsable info. pszDisplayName = NULL; // this would only give the bare directory name, not the full path info. lpszTitle = title; LPITEMIDLIST idList = SHBrowseForFolder (& info); SHGetPathFromIDList (idList, fullFileName); CoTaskMemFree (idList); directoryName = Melder_wcsdup_f (fullFileName); #endif return directoryName; } /* End of file GuiFileSelect.cpp */ sources_5316/sys/Gui.cpp0000644000176700017670000001153511753741756014016 0ustar paulpaul/* Gui.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2002/03/11 Mach * pb 2004/10/21 on Unix, Ctrl becomes the command key * pb 2007/06/09 wchar_t * pb 2007/12/13 Gui * pb 2007/12/30 Gui * sdk 2008/02/08 GTK * sdk 2008/03/24 GDK * pb 2010/05/14 resolution always 72 pixels/inch * pb 2010/11/29 removed explicit Motif * pb 2011/04/06 C++ */ #include "Gui.h" #include // floor GuiObject Gui_addMenuBar (GuiObject form) { GuiObject menuBar; #if gtk menuBar = gtk_menu_bar_new (); gtk_box_pack_start (GTK_BOX (form), GTK_WIDGET (menuBar), FALSE, FALSE, 0); // we need an accelerator group for each window we're creating accelerated menus on GuiObject topwin = gtk_widget_get_toplevel (GTK_WIDGET (form)); GtkAccelGroup *ag = gtk_accel_group_new (); gtk_window_add_accel_group (GTK_WINDOW (topwin), ag); // unfortunately, menu-bars don't fiddle with accel-groups, so we need a way // to pass it to the sub-menus created upon this bar for their items to have // access to the accel-group g_object_set_data (G_OBJECT (menuBar), "accel-group", ag); #elif defined (_WIN32) || defined (macintosh) && useCarbon menuBar = XmCreateMenuBar (form, "menuBar", NULL, 0); XtVaSetValues (menuBar, XmNleftAttachment, XmATTACH_FORM, XmNrightAttachment, XmATTACH_FORM, NULL); #else menuBar = NULL; // TODO #endif return menuBar; } int Gui_getResolution (GuiObject widget) { static int resolution = 0; if (resolution == 0) { #if defined (macintosh) (void) widget; CGDirectDisplayID display = CGMainDisplayID (); CGSize size = CGDisplayScreenSize (display); resolution = floor (25.4 * (double) CGDisplayPixelsWide (display) / size.width + 0.5); //resolution = 72; #elif defined (_WIN32) (void) widget; resolution = 100; #elif gtk resolution = gdk_screen_get_resolution (gdk_display_get_default_screen (gtk_widget_get_display (GTK_WIDGET (widget)))); #else Melder_fatal ("Gui_getResolution: unknown platform."); #endif } return 100; // in conformance with most other applications; and so that fonts always look the same size in the Demo window return resolution; } void Gui_getWindowPositioningBounds (double *x, double *y, double *width, double *height) { #if defined (macintosh) HIRect rect; #if useCarbon HIWindowGetAvailablePositioningBounds (kCGNullDirectDisplay, kHICoordSpaceScreenPixel, & rect); #else #endif if (x) *x = rect. origin. x; if (y) *y = rect. origin. y; if (width) *width = rect. size. width; if (height) *height = rect. size. height - 22; // subtract title bar height (or is it the menu height?) #elif defined (_WIN32) #if 1 RECT rect; SystemParametersInfo (SPI_GETWORKAREA, 0, & rect, 0); // BUG: use GetMonitorInfo instead if (x) *x = rect. left; if (y) *y = rect. top; if (width) *width = rect. right - rect. left - 2 * GetSystemMetrics (SM_CXSIZEFRAME); if (height) *height = rect.bottom - rect.top - GetSystemMetrics (SM_CYCAPTION) - 2 * GetSystemMetrics (SM_CYSIZEFRAME); #else HMONITOR monitor = MonitorFromWindow (HWND window, MONITOR_DEFAULTTONEAREST); MONITORINFO monitorInfo; monitorInfo. cbSize = sizeof (MONITORINFO); GetMonitorInfo (monitor, & monitorInfo); if (x) *x = monitorInfo. rcWork. left; if (y) *y = monitorInfo. rcWork. top; if (width) *width = monitorInfo. rcWork. right - monitorInfo. rcWork. left; if (height) *height = monitorInfo. rcWork.bottom - monitorInfo. rcWork.top /*- GetSystemMetrics (SM_CYMINTRACK)*/; // SM_CXSIZEFRAME SM_CYCAPTION #endif #elif gtk GdkScreen *screen = gdk_screen_get_default (); /* if (parent != NULL) { GuiObject parent_win = gtk_widget_get_ancestor (GTK_WIDGET (parent), GTK_TYPE_WINDOW); if (parent_win != NULL) { screen = gtk_window_get_screen (GTK_WINDOW (parent_win)); } } */ if (x) *x = 0; if (y) *y = 0; if (width) *width = gdk_screen_get_width (screen); if (height) *height = gdk_screen_get_height (screen); #else if (x) *x = 0; if (y) *y = 0; if (width) *width = WidthOfScreen (DefaultScreenOfDisplay (XtDisplay (parent))); if (height) *height = HeightOfScreen (DefaultScreenOfDisplay (XtDisplay (parent))); #endif } /* End of file Gui.cpp */ sources_5316/sys/melder_alloc.cpp0000644000176700017670000002601111613555057015677 0ustar paulpaul/* melder_alloc.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2006/12/10 separated from melder.c * pb 2007/05/24 wcsdup, wcsToAscii, asciiToWcs * pb 2007/08/14 underscores for names _Melder_malloc and _Melder_calloc * pb 2007/12/05 Melder_wcsequ_firstCharacterCaseInsensitive * pb 2009/03/14 counting reallocs moving and in situ * pb 2009/07/31 tracing by Melder_debug 34 * pb 2010/12/28 split into _e and _f versions, and created a rainy-day fund * pb 2011/04/05 C++ */ #include "melder.h" #include #include static double totalNumberOfAllocations = 0, totalNumberOfDeallocations = 0, totalAllocationSize = 0, totalNumberOfMovingReallocs = 0, totalNumberOfReallocsInSitu = 0; /* * The rainy-day fund. * * Typically, memory allocation for data is entirely checked by using the _e versions of the allocation routines, * which will call Melder_error if they are out of memory. * When data allocation is indeed out of memory, * the application will present an error message to the user saying that the data could not be created. * * By contrast, it is not practical to check the allocation of user interface elements, * because the application cannot perform correctly if an interface element is missing or incorrect. * For such situations, the application will typically use the _f versions of the allocation routines, * which, if out of memory, will free a "rainy-day fund" and retry. * In this way, the interface element can usually still be allocated; * the application will present an error message telling the user to save her work and quit the application. * If the user doesn't do that, the application will crash upon the next failing allocation of a _f routine. */ #define theRainyDayFund_SIZE 300000 static char *theRainyDayFund = NULL; void Melder_alloc_init (void) { theRainyDayFund = (char *) malloc (theRainyDayFund_SIZE); // called at application initialization, so cannot fail assert (theRainyDayFund != NULL); } void * _Melder_malloc (unsigned long size) { if (size <= 0) Melder_throw ("Can never allocate ", size, " bytes."); void *result = malloc (size); if (result == NULL) Melder_throw ("Out of memory: there is not enough room for another ", size, " bytes."); if (Melder_debug == 34) { Melder_casual ("Melder_malloc\t%ld\t%ld\t1", result, size); } totalNumberOfAllocations += 1; totalAllocationSize += size; return result; } void * _Melder_malloc_f (unsigned long size) { if (size <= 0) Melder_fatal ("(Melder_malloc_f:) Can never allocate %ld bytes.", size); void *result = malloc (size); if (result == NULL) { if (theRainyDayFund != NULL) free (theRainyDayFund); result = malloc (size); if (result != NULL) { Melder_flushError ("Praat is very low on memory.\nSave your work and quit Praat.\nIf you don't do that, Praat may crash."); } else { Melder_fatal ("Out of memory: there is not enough room for another %ld bytes.", size); } } totalNumberOfAllocations += 1; totalAllocationSize += size; return result; } void _Melder_free (void **ptr) { if (*ptr == NULL) return; free (*ptr); if (Melder_debug == 34) { Melder_casual ("Melder_free\t%ld\t?\t?", *ptr); } *ptr = NULL; totalNumberOfDeallocations += 1; } void * Melder_realloc (void *ptr, long size) { if (size <= 0) Melder_throw ("Can never allocate ", size, " bytes."); void *result = realloc (ptr, size); // will not show in the statistics... if (result == NULL) Melder_throw ("Out of memory. Could not extend room to ", size, " bytes."); if (ptr == NULL) { // is it like malloc? if (Melder_debug == 34) { Melder_casual ("Melder_realloc\t%ld\t%ld\t1", result, size); } totalNumberOfAllocations += 1; totalAllocationSize += size; } else if (result != ptr) { // did realloc do a malloc-and-free? totalNumberOfAllocations += 1; totalAllocationSize += size; totalNumberOfDeallocations += 1; totalNumberOfMovingReallocs += 1; } else { totalNumberOfReallocsInSitu += 1; } return result; } void * Melder_realloc_f (void *ptr, long size) { void *result; if (size <= 0) Melder_fatal ("(Melder_realloc_f:) Can never allocate %ld bytes.", size); result = realloc (ptr, size); /* Will not show in the statistics... */ if (result == NULL) { if (theRainyDayFund != NULL) free (theRainyDayFund); result = realloc (ptr, size); if (result != NULL) { Melder_flushError ("Praat is very low on memory.\nSave your work and quit Praat.\nIf you don't do that, Praat may crash."); } else { Melder_fatal ("Out of memory. Could not extend room to %ld bytes.", size); } } if (ptr == NULL) { /* Is it like malloc? */ totalNumberOfAllocations += 1; totalAllocationSize += size; } else if (result != ptr) { /* Did realloc do a malloc-and-free? */ totalNumberOfAllocations += 1; totalAllocationSize += size; totalNumberOfDeallocations += 1; totalNumberOfMovingReallocs += 1; } else { totalNumberOfReallocsInSitu += 1; } return result; } void * _Melder_calloc (long nelem, long elsize) { void *result; if (nelem <= 0) Melder_throw ("Can never allocate ", nelem, " elements."); if (elsize <= 0) Melder_throw ("Can never allocate elements whose size is ", elsize, " bytes."); result = calloc (nelem, elsize); if (result == NULL) Melder_throw ("Out of memory: there is not enough room for ", nelem, " more elements whose sizes are ", elsize, " bytes each."); if (Melder_debug == 34) { Melder_casual ("Melder_calloc\t%ld\t%ld\t%ld", result, nelem, elsize); } totalNumberOfAllocations += 1; totalAllocationSize += nelem * elsize; return result; } void * _Melder_calloc_f (long nelem, long elsize) { void *result; if (nelem <= 0) Melder_fatal ("(Melder_calloc_f:) Can never allocate %ld elements.", nelem); if (elsize <= 0) Melder_fatal ("(Melder_calloc_f:) Can never allocate elements whose size is %ld bytes.", elsize); result = calloc (nelem, elsize); if (result == NULL) { if (theRainyDayFund != NULL) free (theRainyDayFund); result = calloc (nelem, elsize); if (result != NULL) { Melder_flushError ("Praat is very low on memory.\nSave your work and quit Praat.\nIf you don't do that, Praat may crash."); } else { Melder_fatal ("Out of memory: there is not enough room for %ld more elements whose sizes are %ld bytes each.", nelem, elsize); } } totalNumberOfAllocations += 1; totalAllocationSize += nelem * elsize; return result; } char * Melder_strdup (const char *string) { if (! string) return NULL; long size = strlen (string) + 1; char *result = (char *) malloc (size * sizeof (char)); if (result == NULL) Melder_throw ("Out of memory: there is not enough room to duplicate a text of ", size - 1, " characters."); strcpy (result, string); if (Melder_debug == 34) { Melder_casual ("Melder_strdup\t%ld\t%ld\t1", result, size); } totalNumberOfAllocations += 1; totalAllocationSize += size; return result; } char * Melder_strdup_f (const char *string) { if (! string) return NULL; long size = strlen (string) + 1; char *result = (char *) malloc (size * sizeof (char)); if (result == NULL) { if (theRainyDayFund != NULL) free (theRainyDayFund); result = (char *) malloc (size * sizeof (char)); if (result != NULL) { Melder_flushError ("Praat is very low on memory.\nSave your work and quit Praat.\nIf you don't do that, Praat may crash."); } else { Melder_fatal ("Out of memory: there is not enough room to duplicate a text of %ld characters.", size - 1); } } strcpy (result, string); totalNumberOfAllocations += 1; totalAllocationSize += size; return result; } wchar_t * Melder_wcsdup (const wchar_t *string) { if (! string) return NULL; long size = wcslen (string) + 1; wchar *result = (wchar *) malloc (size * sizeof (wchar)); if (result == NULL) Melder_throw ("Out of memory: there is not enough room to duplicate a text of ", size - 1, " characters."); wcscpy (result, string); if (Melder_debug == 34) { Melder_casual ("Melder_wcsdup\t%ld\t%ld\t4", result, size); } totalNumberOfAllocations += 1; totalAllocationSize += size * sizeof (wchar_t); return result; } wchar_t * Melder_wcsdup_f (const wchar_t *string) { if (! string) return NULL; long size = wcslen (string) + 1; wchar *result = (wchar *) malloc (size * sizeof (wchar_t)); if (result == NULL) { if (theRainyDayFund != NULL) free (theRainyDayFund); result = (wchar *) malloc (size * sizeof (wchar_t)); if (result != NULL) { Melder_flushError ("Praat is very low on memory.\nSave your work and quit Praat.\nIf you don't do that, Praat may crash."); } else { Melder_fatal ("Out of memory: there is not enough room to duplicate a text of %ld characters.", size - 1); } } wcscpy (result, string); totalNumberOfAllocations += 1; totalAllocationSize += size * sizeof (wchar_t); return result; } double Melder_allocationCount (void) { return totalNumberOfAllocations; } double Melder_deallocationCount (void) { return totalNumberOfDeallocations; } double Melder_allocationSize (void) { return totalAllocationSize; } double Melder_reallocationsInSituCount (void) { return totalNumberOfReallocsInSitu; } double Melder_movingReallocationsCount (void) { return totalNumberOfMovingReallocs; } int Melder_strcmp (const char *string1, const char *string2) { if (string1 == NULL) string1 = ""; if (string2 == NULL) string2 = ""; return strcmp (string1, string2); } int Melder_strncmp (const char *string1, const char *string2, unsigned long n) { if (string1 == NULL) string1 = ""; if (string2 == NULL) string2 = ""; return strncmp (string1, string2, n); } int Melder_wcscmp (const wchar_t *string1, const wchar_t *string2) { if (string1 == NULL) string1 = L""; if (string2 == NULL) string2 = L""; return wcscmp (string1, string2); } int Melder_wcsncmp (const wchar_t *string1, const wchar_t *string2, unsigned long n) { if (string1 == NULL) string1 = L""; if (string2 == NULL) string2 = L""; return wcsncmp (string1, string2, n); } bool Melder_wcsequ_firstCharacterCaseInsensitive (const wchar_t *string1, const wchar_t *string2) { if (string1 == NULL) string1 = L""; if (string2 == NULL) string2 = L""; if (towlower (*string1) != towlower (*string2)) return false; if (*string1 == '\0') return true; return ! wcscmp (string1 + 1, string2 + 1); } wchar_t * Melder_wcstok (wchar_t *string, const wchar_t *delimiter, wchar_t **last) { #if defined (__MINGW32__) (void) last; return wcstok (string, delimiter); #else return wcstok (string, delimiter, last); #endif } /* End of file melder_alloc.cpp */ sources_5316/sys/macport_on.h0000644000176700017670000000174311651726762015075 0ustar paulpaul/* macport_on.h * * Copyright (C) 1993-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define Polygon MacintoshPolygon #define Pattern MacintoshPattern #define Boolean MacintoshBoolean #define Collection MacintoshCollection #define Picture MacintoshPicture #define Movie QuickTimeMovie /* End of file macport_on.h */ sources_5316/sys/enums_getValue.h0000644000176700017670000000263111161334465015703 0ustar paulpaul/* enums_getValue.h * * Copyright (C) 2007-2009 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2009/03/21 */ /* See enums.h */ /* For C files. */ #undef enums_begin #undef enums_add #undef enums_alt #undef enums_end #define enums_begin(type,minimum) int type##_getValue (const wchar_t *testText) { #define enums_add(type,value,which,text) if (Melder_wcsequ_firstCharacterCaseInsensitive (testText, text)) return type##_##which; #define enums_alt(type,which,text) if (Melder_wcsequ_firstCharacterCaseInsensitive (testText, text)) return type##_##which; #define enums_end(type,maximum,def) \ if (wcsequ (testText, L"\t")) return type##_DEFAULT; \ if (wcsequ (testText, L"\n")) return maximum; \ return -1; } /* End of file enums_getValue.h */ sources_5316/sys/oo.h0000644000176700017670000004131211724670723013341 0ustar paulpaul#ifndef _oo_h_ #define _oo_h_ /* oo.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /*** Single types. ***/ /* The possible storage types give these binary formats: */ /* i1: store as signed big-endian integer in 1 byte (-128..127). */ /* i2: store as signed big-endian integer in 2 bytes (-32768..32767). */ /* i4: store as signed big-endian integer in 4 bytes. */ /* u1: store as unsigned big-endian integer integer in 1 byte (0..255). */ /* u2: store as unsigned big-endian integer in 2 bytes (0..65535). */ /* u4: store as unsigned big-endian integer in 4 bytes. */ /* i1LE ... u4LE: store as little-endian integers. */ /* r4: store as 4-byte IEEE MSB-first floating point format. */ /* r8: store as 8-byte IEEE MSB-first floating point format. */ /* r10: store as 10-byte IEEE/Apple MSB-first floating point format. */ /* c8: store real and imaginary part as r4. */ /* c16: store real and imaginary part as r4. */ /* For text format, reading imposes the same restrictions for the integer types, */ /* and the real numbers are written with a precision of 8, 17, or 20 characters. */ /* Single types. Declarations like: int x; */ #define oo_BYTE(x) oo_SIMPLE (signed char, i1, x) #define oo_INT(x) oo_SIMPLE (int, i2, x) #define oo_LONG(x) oo_SIMPLE (long, i4, x) #define oo_UBYTE(x) oo_SIMPLE (unsigned char, u1, x) #define oo_UINT(x) oo_SIMPLE (unsigned int, u2, x) #define oo_ULONG(x) oo_SIMPLE (unsigned long, u4, x) #define oo_BOOL(x) oo_SIMPLE (unsigned char, u1, x) #define oo_FLOAT(x) oo_SIMPLE (double, r4, x) #define oo_DOUBLE(x) oo_SIMPLE (double, r8, x) #define oo_FCOMPLEX(x) oo_SIMPLE (fcomplex, c8, x) #define oo_DCOMPLEX(x) oo_SIMPLE (dcomplex, c16, x) #define oo_POINTER(x) oo_SIMPLE (void *, dummy, x) /* Arrays with compile-time allocation of capacity. Declarations like: int x [cap]; */ /* 'cap' is a compile-time expression evaluating to a positive integer (e.g., 3). */ /* First index is always 0, last index is 'n' - 1. */ /* Actual number of elements 'n' may vary during run-time and while structure exists, */ /* but must never be greater than 'cap'. */ #define oo_BYTE_ARRAY(x,cap,n) oo_ARRAY (signed char, i1, x, cap, n) #define oo_INT_ARRAY(x,cap,n) oo_ARRAY (int, i2, x, cap, n) #define oo_LONG_ARRAY(x,cap,n) oo_ARRAY (long, i4, x, cap, n) #define oo_UBYTE_ARRAY(x,cap,n) oo_ARRAY (unsigned char, u1, x, cap, n) #define oo_UINT_ARRAY(x,cap,n) oo_ARRAY (unsigned int, u2, x, cap, n) #define oo_ULONG_ARRAY(x,cap,n) oo_ARRAY (unsigned long, u4, x, cap, n) #define oo_BOOL_ARRAY(x,cap,n) oo_ARRAY (unsigned char, u1, x, cap, n) #define oo_FLOAT_ARRAY(x,cap,n) oo_ARRAY (double, r4, x, cap, n) #define oo_DOUBLE_ARRAY(x,cap,n) oo_ARRAY (double, r8, x, cap, n) #define oo_FCOMPLEX_ARRAY(x,cap,n) oo_ARRAY (fcomplex, c8, x, cap, n) #define oo_DCOMPLEX_ARRAY(x,cap,n) oo_ARRAY (dcomplex, c16, x, cap, n) #define oo_POINTER_ARRAY(x,cap,n) oo_ARRAY (void *, dummy, x, cap, n) /* Sets with compile-time allocation of capacity. Declarations like: int x [1 + setType_MAX]; */ /* First index is always 0, last index is setType_MAX. */ #define oo_BYTE_SET(x,setType) oo_SET (signed char, i1, x, setType) #define oo_INT_SET(x,setType) oo_SET (int, i2, x, setType) #define oo_LONG_SET(x,setType) oo_SET (long, i4, x, setType) #define oo_UBYTE_SET(x,setType) oo_SET (unsigned char, u1, x, setType) #define oo_UINT_SET(x,setType) oo_SET (unsigned int, u2, x, setType) #define oo_ULONG_SET(x,setType) oo_SET (unsigned long, u4, x, setType) #define oo_BOOL_SET(x,setType) oo_SET (unsigned char, u1, x, setType) #define oo_FLOAT_SET(x,setType) oo_SET (double, r4, x, setType) #define oo_DOUBLE_SET(x,setType) oo_SET (double, r8, x, setType) #define oo_FCOMPLEX_SET(x,setType) oo_SET (fcomplex, c8, x, setType) #define oo_DCOMPLEX_SET(x,setType) oo_SET (dcomplex, c16, x, setType) #define oo_POINTER_SET(x,setType) oo_SET (void *, dummy, x, setType) /* Arrays with run-time allocation of size. Declarations like: int *x; */ /* First index is 'min', last index is 'max'. */ /* While the structure exists, 'max' may become less than the value it had at the time of allocation. */ #define oo_BYTE_VECTOR_FROM(x,min,max) oo_VECTOR (signed char, i1, x, min, max) #define oo_INT_VECTOR_FROM(x,min,max) oo_VECTOR (int, i2, x, min, max) #define oo_LONG_VECTOR_FROM(x,min,max) oo_VECTOR (long, i4, x, min, max) #define oo_UBYTE_VECTOR_FROM(x,min,max) oo_VECTOR (unsigned char, u1, x, min, max) #define oo_UINT_VECTOR_FROM(x,min,max) oo_VECTOR (unsigned int, u2, x, min, max) #define oo_ULONG_VECTOR_FROM(x,min,max) oo_VECTOR (unsigned long, u4, x, min, max) #define oo_BOOL_VECTOR_FROM(x,min,max) oo_VECTOR (unsigned char, u1, x, min, max) #define oo_FLOAT_VECTOR_FROM(x,min,max) oo_VECTOR (double, r4, x, min, max) #define oo_DOUBLE_VECTOR_FROM(x,min,max) oo_VECTOR (double, r8, x, min, max) #define oo_FCOMPLEX_VECTOR_FROM(x,min,max) oo_VECTOR (fcomplex, c8, x, min, max) #define oo_DCOMPLEX_VECTOR_FROM(x,min,max) oo_VECTOR (dcomplex, c16, x, min, max) #define oo_POINTER_VECTOR_FROM(x,min,max) oo_VECTOR (void *, dummy, x, min, max) #define oo_BYTE_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (signed char, i1, x, row1, row2, col1, col2) #define oo_INT_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (int, i2, x, row1, row2, col1, col2) #define oo_LONG_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (long, i4, x, row1, row2, col1, col2) #define oo_UBYTE_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (unsigned char, u1, x, row1, row2, col1, col2) #define oo_UINT_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (unsigned int, u2, x, row1, row2, col1, col2) #define oo_ULONG_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (unsigned long, u4, x, row1, row2, col1, col2) #define oo_BOOL_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (unsigned char, u1, x, row1, row2, col1, col2) #define oo_FLOAT_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (double, r4, x, row1, row2, col1, col2) #define oo_DOUBLE_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (double, r8, x, row1, row2, col1, col2) #define oo_FCOMPLEX_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (fcomplex, c8, x, row1, row2, col1, col2) #define oo_DCOMPLEX_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (dcomplex, c16, x, row1, row2, col1, col2) #define oo_POINTER_MATRIX_FROM(x,row1,row2,col1,col2) oo_MATRIX (void *, dummy, x, row1, row2, col1, col2) /* The same arrays, with the first index fixed at 1. */ #define oo_BYTE_VECTOR(x,n) oo_VECTOR (signed char, i1, x, 1, n) #define oo_INT_VECTOR(x,n) oo_VECTOR (int, i2, x, 1, n) #define oo_LONG_VECTOR(x,n) oo_VECTOR (long, i4, x, 1, n) #define oo_UBYTE_VECTOR(x,n) oo_VECTOR (unsigned char, u1, x, 1, n) #define oo_UINT_VECTOR(x,n) oo_VECTOR (unsigned int, u2, x, 1, n) #define oo_ULONG_VECTOR(x,n) oo_VECTOR (unsigned long, u4, x, 1, n) #define oo_BOOL_VECTOR(x,n) oo_VECTOR (unsigned char, u1, x, 1, n) #define oo_FLOAT_VECTOR(x,n) oo_VECTOR (double, r4, x, 1, n) #define oo_DOUBLE_VECTOR(x,n) oo_VECTOR (double, r8, x, 1, n) #define oo_FCOMPLEX_VECTOR(x,n) oo_VECTOR (fcomplex, c8, x, 1, n) #define oo_DCOMPLEX_VECTOR(x,n) oo_VECTOR (dcomplex, c16, x, 1, n) #define oo_POINTER_VECTOR(x,n) oo_VECTOR (void *, dummy, x, 1, n) #define oo_BYTE_MATRIX(x,nrow,ncol) oo_MATRIX (signed char, i1, x, 1, nrow, 1, ncol) #define oo_INT_MATRIX(x,nrow,ncol) oo_MATRIX (int, i2, x, 1, nrow, 1, ncol) #define oo_LONG_MATRIX(x,nrow,ncol) oo_MATRIX (long, i4, x, 1, nrow, 1, ncol) #define oo_UBYTE_MATRIX(x,nrow,ncol) oo_MATRIX (unsigned char, u1, x, 1, nrow, 1, ncol) #define oo_UINT_MATRIX(x,nrow,ncol) oo_MATRIX (unsigned int, u2, x, 1, nrow, 1, ncol) #define oo_ULONG_MATRIX(x,nrow,ncol) oo_MATRIX (unsigned long, u4, x, 1, nrow, 1, ncol) #define oo_BOOL_MATRIX(x,nrow,ncol) oo_MATRIX (unsigned char, u1, x, 1, nrow, 1, ncol) #define oo_FLOAT_MATRIX(x,nrow,ncol) oo_MATRIX (double, r4, x, 1, nrow, 1, ncol) #define oo_DOUBLE_MATRIX(x,nrow,ncol) oo_MATRIX (double, r8, x, 1, nrow, 1, ncol) #define oo_FCOMPLEX_MATRIX(x,nrow,ncol) oo_MATRIX (fcomplex, c8, x, 1, nrow, 1, ncol) #define oo_DCOMPLEX_MATRIX(x,nrow,ncol) oo_MATRIX (dcomplex, c16, x, 1, nrow, 1, ncol) #define oo_POINTER_MATRIX(x,nrow,ncol) oo_MATRIX (void *, dummy, x, 1, nrow, 1, ncol) /*** Enumerated types. ***/ /* The possible storage types give these binary formats: */ /* e1: store as signed big-endian integer in 1 byte. */ /* e2: store in signed big-endian integer in 2 bytes. */ /* eb: store as byte 170 (false) or byte 185 (true). */ /* eq: store as byte 150 (no) or byte 165 (yes). */ /* ex: store as byte 226 (absent) or byte 241 (present). */ /* For text format, the value is written as a string between '<' and '>'. */ #define oo_ENUM(Type,x) oo_ENUMx (signed char, e1, Type, x) #define oo_LENUM(Type,x) oo_ENUMx (short, e2, Type, x) #define oo_ENUM_ARRAY(Type,x,cap,n) oo_ENUMx_ARRAY (signed char, e1, Type, x, cap, n) #define oo_LENUM_ARRAY(Type,x,cap,n) oo_ENUMx_ARRAY (short, e2, Type, x, cap, n) #define oo_ENUM_SET(Type,x,setType) oo_ENUMx_SET (signed char, e1, Type, x, setType) #define oo_LENUM_SET(Type,x,setType) oo_ENUMx_SET (short, e2, Type, x, setType) #define oo_ENUM_VECTOR_FROM(Type,x,min,max) oo_ENUMx_VECTOR (signed char, e1, Type, x, min, max) #define oo_LENUM_VECTOR_FROM(Type,x,min,max) oo_ENUMx_VECTOR (short, e2, Type, x, min, max) #define oo_ENUM_VECTOR(Type,x,n) oo_ENUMx_VECTOR (signed char, e1, Type, x, 1, n) #define oo_LENUM_VECTOR(Type,x,n) oo_ENUMx_VECTOR (short, e2, Type, x, 1, n) #define oo_BOOLEAN(x) oo_SIMPLE (signed char, eb, x) #define oo_BOOLEAN_ARRAY(x,cap,n) oo_ARRAY (signed char, eb, x, cap, n) #define oo_BOOLEAN_SET(x,setType) oo_ARRAY (signed char, eb, x, setType) #define oo_BOOLEAN_VECTOR_FROM(x,min,max) oo_VECTOR (signed char, eb, x, min, max) #define oo_BOOLEAN_VECTOR(x,n) oo_VECTOR (signed char, eb, x, 1, n) #define oo_QUESTION(x) oo_SIMPLE (signed char, eq, x) #define oo_QUESTION_ARRAY(x,cap,n) oo_ARRAY (signed char, eq, x, cap, n) #define oo_QUESTION_SET(x,setType) oo_ARRAY (signed char, eq, x, setType) #define oo_QUESTION_VECTOR_FROM(x,min,max) oo_VECTOR (signed char, eq, x, min, max) #define oo_QUESTION_VECTOR(x,n) oo_VECTOR (signed char, eq, x, 1, n) /*** Strings. ***/ /* The possible storage types give these binary formats: */ /* s2: store as sequence of bytes, preceded with 2 bytes (u2) to denote length. */ /* w2: store as sequence of characters (u2), preceded with 2 bytes (u2) to denote length. */ /* s4: store as sequence of bytes, preceded with 4 bytes (u4) to denote length. */ /* w4: store as sequence of characters (u2), preceded with 4 bytes (u4) to denote length. */ #define oo_STRING(x) oo_STRINGx (w2, x) #define oo_LSTRING(x) oo_STRINGx (w4, x) #define oo_STRING_ARRAY(x,cap,n) oo_STRINGx_ARRAY (w2, x, cap, n) #define oo_LSTRING_ARRAY(x,cap,n) oo_STRINGx_ARRAY (w4, x, cap, n) #define oo_STRING_SET(x,setType) oo_STRINGx_SET (w2, x, setType) #define oo_LSTRING_SET(x,setType) oo_STRINGx_SET (w4, x, setType) #define oo_STRING_VECTOR_FROM(x,min,max) oo_STRINGx_VECTOR (w2, x, min, max) #define oo_LSTRING_VECTOR_FROM(x,min,max) oo_STRINGx_VECTOR (w4, x, min, max) #define oo_STRING_VECTOR(x,n) oo_STRINGx_VECTOR (w2, x, 1, n) #define oo_LSTRING_VECTOR(x,n) oo_STRINGx_VECTOR (w4, x, 1, n) /*** Structs. ***/ #define oo_STRUCT_VECTOR(Type,x,n) oo_STRUCT_VECTOR_FROM (Type, x, 1, n) #define oo_STRUCT_MATRIX(Type,x,nrow,ncol) oo_STRUCT_MATRIX_FROM (Type, x, 1, nrow, 1, ncol) /*** Widgets. */ #define oo_WIDGET_VECTOR(Type,x,n) oo_WIDGET_VECTOR_FROM (Type, x, 1, n) /*** Class declaration in header file. ***/ #define oo_CLASS_CREATE(klas,parent) \ typedef _Thing_auto auto##klas; \ extern struct structClassInfo theClassInfo_##klas; \ extern ClassInfo class##klas /********** Definitions for header files only. **********/ /* These are undef'ed and redefined in the header files that implement methods, */ /* like oo_DESTROY.h, oo_COPY.h, oo_EQUAL.h, oo_WRITE_TEXT.h, etc. */ /* Types. */ #define oo_SIMPLE(type,storage,x) type x; #define oo_ARRAY(type,storage,x,cap,n) type x [cap]; #define oo_SET(type,storage,x,setType) type x [1 + setType##_MAX]; #define oo_VECTOR(type,storage,x,min,max) type *x; #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) type **x; #define oo_ENUMx(type,storage,Type,x) type x; #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) type x [cap]; #define oo_ENUMx_SET(type,storage,Type,x,setType) type x [1 + setType##_MAX]; #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) type *x; #define oo_STRINGx(storage,x) wchar_t *x; #define oo_STRINGx_ARRAY(storage,x,cap,n) wchar_t *x [cap]; #define oo_STRINGx_SET(storage,x,setType) wchar_t *x [1 + setType##_MAX]; #define oo_STRINGx_VECTOR(storage,x,min,max) wchar_t **x; #define oo_STRUCT(Type,x) struct struct##Type x; #define oo_STRUCT_ARRAY(Type,x,cap,n) struct struct##Type x [cap]; #define oo_STRUCT_SET(Type,x,setType) struct struct##Type x [1 + setType##_MAX]; #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) Type x; #define oo_STRUCT_MATRIX_FROM(Type,x,row1,row2,col1,col2) struct struct##Type **x; #define oo_WIDGET(x) GuiObject x; #define oo_WIDGET_ARRAY(x,cap,n) GuiObject x [cap]; #define oo_WIDGET_SET(x,setType) GuiObject x [1 + setType##_MAX]; #define oo_WIDGET_VECTOR_FROM(x,min,max) GuiObject *x; #define oo_OBJECT(Class,version,x) Class x; #define oo_COLLECTION(Class,x,ItemClass,version) Class x; #define oo_FILE(x) structMelderFile x; #define oo_DIR(x) structMelderDir x; /* Struct and class definitions. */ #define oo_DEFINE_STRUCT(T) \ typedef struct struct##T *T; \ struct struct##T { #define oo_END_STRUCT(T) \ void destroy (); \ void copy (T data_to); \ bool equal (T otherData); \ Data_Description description (); \ static Data_Description s_description; \ bool canWriteAsEncoding (int outputEncoding); \ void writeText (MelderFile openFile); \ void readText (MelderReadText text); \ void writeBinary (FILE *f); \ void readBinary (FILE *f); \ }; #define oo_DEFINE_CLASS(klas,parent) \ typedef class struct##klas *klas; \ typedef struct##parent klas##_Parent; \ class struct##klas : public struct##parent { \ public: #define oo_END_CLASS(Class) \ virtual void v_destroy (); \ virtual void v_copy (Any data_to); \ virtual bool v_equal (Any otherData); \ static Data_Description s_description; \ virtual Data_Description v_description () { return s_description; } \ virtual bool v_canWriteAsEncoding (int outputEncoding); \ virtual void v_writeText (MelderFile openFile); \ virtual void v_readText (MelderReadText text); \ virtual void v_writeBinary (FILE *f); \ virtual void v_readBinary (FILE *f); \ }; /*** Miscellaneous. ***/ /* For fields that should only be destroyed, copied, compared, read, or written if 'condition': */ #define oo_IF(condition) #define oo_ENDIF /* For fields that should not be read in older versions: */ #define oo_FROM(from) #define oo_ENDFROM /* For OBJECT fields that have version numbers: */ #define oo_VERSION(version) /* Examples of the usage of the following macros: For code that should only appear in reading methods (consistency checks etc.), use: #if oo_READING For code that should only appear in writing methods (e.g., debugging statements), use: #if oo_WRITING For fields that are not destroyed, copied, or compared, either (i.e., only declarations), use: #if oo_DECLARING For fields that do not take part in I/O (e.g. redundant or temporary fields), use: #if ! oo_READING && ! oo_WRITING For fields that should not be read (e.g., when expanding a database file), use: #if ! oo_READING For fields that should not be written (e.g., when shrinking a database file), use: #if ! oo_WRITING The last two should be temporary situations, because the output files do not match the input files! */ #define oo_DECLARING 1 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ASCII 0 #define oo_READING 0 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 0 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo.h */ #endif sources_5316/sys/GuiRadioButton.cpp0000644000176700017670000002010511753754150016152 0ustar paulpaul/* GuiRadioButton.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/26 extracted from Motif * sdk 2007/12/27 gtk * pb 2010/05/15 prevented procreation of valueChanged events in GuiRadioButton_setValue * pb 2010/06/14 HandleControlClick * pb 2010/11/28 removed Motif * pb 2011/04/06 C++ */ #include "GuiP.h" #undef iam #define iam(x) x me = (x) void_me #if win || mac #define iam_radiobutton \ Melder_assert (widget -> widgetClass == xmToggleButtonWidgetClass); \ GuiRadioButton me = (GuiRadioButton) widget -> userData #else #define iam_radiobutton \ GuiRadioButton me = (GuiRadioButton) _GuiObject_getUserData (widget) #endif typedef struct structGuiRadioButton { GuiObject widget; void (*valueChangedCallback) (void *boss, GuiRadioButtonEvent event); void *valueChangedBoss; #if gtk gulong valueChangedHandlerId; #endif } *GuiRadioButton; #if gtk static void _GuiGtkRadioButton_destroyCallback (GuiObject widget, gpointer void_me) { (void) widget; iam (GuiRadioButton); Melder_free (me); } static void _GuiGtkRadioButton_valueChangedCallback (GuiObject widget, gpointer void_me) { iam (GuiRadioButton); struct structGuiRadioButtonEvent event = { widget }; if (my valueChangedCallback != NULL) { my valueChangedCallback (my valueChangedBoss, & event); } } #elif win void _GuiWinRadioButton_destroy (GuiObject widget) { iam_radiobutton; _GuiNativeControl_destroy (widget); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiWinRadioButton_handleClick (GuiObject widget) { iam_radiobutton; if (my valueChangedCallback != NULL) { struct structGuiRadioButtonEvent event = { widget }; my valueChangedCallback (my valueChangedBoss, & event); } } #elif mac #if useCarbon void _GuiMacRadioButton_destroy (GuiObject widget) { iam_radiobutton; _GuiNativeControl_destroy (widget); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiMacRadioButton_handleClick (GuiObject widget, EventRecord *macEvent) { iam_radiobutton; _GuiMac_clipOnParent (widget); bool clicked = HandleControlClick (widget -> nat.control.handle, macEvent -> where, macEvent -> modifiers, NULL); GuiMac_clipOff (); if (clicked) { if (widget -> parent -> radioBehavior) { /* * Deselect the sister buttons. */ for (GuiObject sibling = widget -> parent -> firstChild; sibling != NULL; sibling = sibling -> nextSibling) { if (sibling -> widgetClass == xmToggleButtonWidgetClass && sibling != widget) SetControlValue (sibling -> nat.control.handle, 0); } } if (my valueChangedCallback != NULL) { struct structGuiRadioButtonEvent event = { widget }; my valueChangedCallback (my valueChangedBoss, & event); } } } #else #endif #endif GuiObject GuiRadioButton_create (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*valueChangedCallback) (void *boss, GuiRadioButtonEvent event), void *valueChangedBoss, unsigned long flags) { GuiRadioButton me = Melder_calloc_f (struct structGuiRadioButton, 1); my valueChangedCallback = valueChangedCallback; my valueChangedBoss = valueChangedBoss; #if gtk my widget = gtk_radio_button_new_with_label (NULL, Melder_peekWcsToUtf8 (buttonText)); _GuiObject_setUserData (my widget, me); // _GuiObject_position (my widget, left, right, top, bottom); if (GTK_IS_BOX (parent)) { gtk_container_add (GTK_CONTAINER (parent), GTK_WIDGET (my widget)); } if (flags & GuiRadioButton_SET) { gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (my widget), TRUE); } if (flags & GuiCheckButton_INSENSITIVE) { GuiObject_setSensitive (my widget, FALSE); } g_signal_connect (G_OBJECT (my widget), "destroy", G_CALLBACK (_GuiGtkRadioButton_destroyCallback), me); my valueChangedHandlerId = g_signal_connect (GTK_TOGGLE_BUTTON (my widget), "toggled", G_CALLBACK (_GuiGtkRadioButton_valueChangedCallback), me); #elif win my widget = _Gui_initializeWidget (xmToggleButtonWidgetClass, parent, buttonText); _GuiObject_setUserData (my widget, me); my widget -> isRadioButton = true; my widget -> window = CreateWindow (L"button", _GuiWin_expandAmpersands (buttonText), WS_CHILD | ( my widget -> parent -> radioBehavior ? BS_AUTORADIOBUTTON : BS_RADIOBUTTON ) | WS_CLIPSIBLINGS, my widget -> x, my widget -> y, my widget -> width, my widget -> height, my widget -> parent -> window, (HMENU) 1, theGui.instance, NULL); SetWindowLongPtr (my widget -> window, GWLP_USERDATA, (LONG_PTR) my widget); SetWindowFont (my widget -> window, GetStockFont (ANSI_VAR_FONT), FALSE); _GuiObject_position (my widget, left, right, top, bottom); if (flags & GuiRadioButton_SET) { Button_SetCheck (my widget -> window, BST_CHECKED); } if (flags & GuiRadioButton_INSENSITIVE) { GuiObject_setSensitive (my widget, false); } #elif mac #if useCarbon my widget = _Gui_initializeWidget (xmToggleButtonWidgetClass, parent, buttonText); _GuiObject_setUserData (my widget, me); my widget -> isRadioButton = true; CreateRadioButtonControl (my widget -> macWindow, & my widget -> rect, NULL, (flags & GuiRadioButton_SET) != 0, true, & my widget -> nat.control.handle); Melder_assert (my widget -> nat.control.handle != NULL); SetControlReference (my widget -> nat.control.handle, (long) my widget); my widget -> isControl = true; _GuiNativeControl_setFont (my widget, 0, 13); _GuiNativeControl_setTitle (my widget); _GuiObject_position (my widget, left, right, top, bottom); if (flags & GuiRadioButton_INSENSITIVE) { GuiObject_setSensitive (my widget, false); } #endif #endif return my widget; } GuiObject GuiRadioButton_createShown (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*valueChangedCallback) (void *boss, GuiRadioButtonEvent event), void *valueChangedBoss, unsigned long flags) { GuiObject me = GuiRadioButton_create (parent, left, right, top, bottom, buttonText, valueChangedCallback, valueChangedBoss, flags); GuiObject_show (me); return me; } bool GuiRadioButton_getValue (GuiObject widget) { bool value = false; #if gtk value = gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (widget)); // gtk_check_button inherits from gtk_toggle_button #elif win value = (Button_GetState (widget -> window) & 0x0003) == BST_CHECKED; #elif mac #if useCarbon value = GetControlValue (widget -> nat.control.handle); #else #endif #endif return value; } void GuiRadioButton_setValue (GuiObject widget, bool value) { /* * The value should be set without calling the valueChanged callback. */ #if gtk iam_radiobutton; g_signal_handler_disconnect (GTK_TOGGLE_BUTTON (my widget), my valueChangedHandlerId); gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (my widget), value); my valueChangedHandlerId = g_signal_connect (GTK_TOGGLE_BUTTON (my widget), "toggled", G_CALLBACK (_GuiGtkRadioButton_valueChangedCallback), me); #elif win Button_SetCheck (widget -> window, value ? BST_CHECKED : BST_UNCHECKED); #elif mac #if useCarbon SetControlValue (widget -> nat.control.handle, value); #else #endif #endif } #if gtk void * GuiRadioButton_getGroup (GuiObject widget) { return (void *) gtk_radio_button_get_group (GTK_RADIO_BUTTON (widget)); } void GuiRadioButton_setGroup (GuiObject widget, void *group) { gtk_radio_button_set_group (GTK_RADIO_BUTTON (widget), (GSList *) group); } #endif /* End of file GuiRadioButton.cpp */ sources_5316/sys/ManPage.cpp0000644000176700017670000000170211622221173014552 0ustar paulpaul/* ManPage.cpp * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPage.h" #include "enums_getText.h" #include "ManPage_enums.h" #include "enums_getValue.h" #include "ManPage_enums.h" Thing_implement (ManPage, Thing, 0); /* End of file ManPage.cpp */ sources_5316/sys/Graphics_utils.cpp0000644000176700017670000011322311747340424016235 0ustar paulpaul/* Graphics_utils.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include "GraphicsP.h" /***** UTILITIES: *****/ /***** THESE ROUINTES OUTPUT TO CURRENT GRAPHICS BY CALLING PRIMITIVES. *****/ /***** THE TWO UTILITIES "Graphics_grey" AND "Graphics_altitude" *****/ /***** ARE IN DIFFERENT FILES BECAUSE THEY NEED LOCAL SUBROUTINES. *****/ /********** Utility functions. **********/ static MelderString theGraphicsTextBuffer = { 0 }; void Graphics_text1 (Graphics me, double x, double y, const wchar_t *s1) { MelderString_copy (& theGraphicsTextBuffer, s1); // make a copy because s1 may be a temporary string (Melder_integer or so) Graphics_text (me, x, y, theGraphicsTextBuffer.string); } void Graphics_text2 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2) { MelderString_empty (& theGraphicsTextBuffer); MelderString_append (& theGraphicsTextBuffer, s1, s2); Graphics_text (me, x, y, theGraphicsTextBuffer.string); } void Graphics_text3 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3) { MelderString_empty (& theGraphicsTextBuffer); MelderString_append (& theGraphicsTextBuffer, s1, s2, s3); Graphics_text (me, x, y, theGraphicsTextBuffer.string); } void Graphics_text4 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4) { MelderString_empty (& theGraphicsTextBuffer); MelderString_append (& theGraphicsTextBuffer, s1, s2, s3, s4); Graphics_text (me, x, y, theGraphicsTextBuffer.string); } void Graphics_text5 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5) { MelderString_empty (& theGraphicsTextBuffer); MelderString_append (& theGraphicsTextBuffer, s1, s2, s3, s4, s5); Graphics_text (me, x, y, theGraphicsTextBuffer.string); } void Graphics_text6 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { MelderString_empty (& theGraphicsTextBuffer); MelderString_append (& theGraphicsTextBuffer, s1, s2, s3, s4, s5, s6); Graphics_text (me, x, y, theGraphicsTextBuffer.string); } void Graphics_text7 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7) { MelderString_empty (& theGraphicsTextBuffer); MelderString_append (& theGraphicsTextBuffer, s1, s2, s3, s4, s5, s6, s7); Graphics_text (me, x, y, theGraphicsTextBuffer.string); } void Graphics_text8 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8) { MelderString_empty (& theGraphicsTextBuffer); MelderString_append (& theGraphicsTextBuffer, s1, s2, s3, s4, s5, s6, s7, s8); Graphics_text (me, x, y, theGraphicsTextBuffer.string); } void Graphics_text9 (Graphics me, double x, double y, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8, const wchar_t *s9) { MelderString_empty (& theGraphicsTextBuffer); MelderString_append (& theGraphicsTextBuffer, s1, s2, s3, s4, s5, s6, s7, s8, s9); Graphics_text (me, x, y, theGraphicsTextBuffer.string); } /********** Drawing into margins. **********/ void Graphics_drawInnerBox (Graphics me) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; int lineType = my lineType; double lineWidth = my lineWidth; Graphics_Colour colour = my colour; Graphics_setInner (me); Graphics_setWindow (me, 0, 1, 0, 1); Graphics_setLineType (me, Graphics_DRAWN); Graphics_setLineWidth (me, 2.0 * lineWidth); Graphics_setColour (me, Graphics_BLACK); Graphics_rectangle (me, 0, 1, 0, 1); Graphics_unsetInner (me); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setLineType (me, lineType); Graphics_setLineWidth (me, lineWidth); Graphics_setColour (me, colour); } void Graphics_textLeft (Graphics me, bool farr, const wchar_t *text) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; int vert = farr ? Graphics_TOP : Graphics_BOTTOM; Graphics_Colour colour = my colour; Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, 0, 1, 0, 1); Graphics_setTextRotation (me, 90); Graphics_setTextAlignment (me, Graphics_CENTRE, vert); if (! farr) Graphics_setInner (me); Graphics_text (me, 0, 0.5, text); if (! farr) Graphics_unsetInner (me); Graphics_setTextRotation (me, 0); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setColour (me, colour); } void Graphics_textRight (Graphics me, bool farr, const wchar_t *text) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; int vert = farr ? Graphics_TOP : Graphics_BOTTOM; Graphics_Colour colour = my colour; Graphics_setColour (me, Graphics_BLACK); Graphics_setTextAlignment (me, Graphics_CENTRE, vert); Graphics_setWindow (me, 0, 1, 0, 1); Graphics_setTextRotation (me, 270); if (! farr) Graphics_setInner (me); Graphics_text (me, 1, 0.5, text); if (! farr) Graphics_unsetInner (me); Graphics_setTextRotation (me, 0); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setColour (me, colour); } void Graphics_textBottom (Graphics me, bool farr, const wchar_t *text) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; Graphics_Colour colour = my colour; Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, 0, 1, 0, 1); if (farr) { Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (me, 0.5, 0, text); } else { Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_TOP); Graphics_setInner (me); Graphics_text (me, 0.5, - my vertTick, text); Graphics_unsetInner (me); } Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setColour (me, colour); } void Graphics_textTop (Graphics me, bool farr, const wchar_t *text) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; Graphics_Colour colour = my colour; Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, 0, 1, 0, 1); if (farr) { Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_TOP); Graphics_text (me, 0.5, 1, text); } else { Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_BOTTOM); Graphics_setInner (me); Graphics_text (me, 0.5, 1 + my vertTick, text); Graphics_unsetInner (me); } Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setColour (me, colour); } void Graphics_marksLeft (Graphics me, int numberOfMarks, bool haveNumbers, bool haveTicks, bool haveDottedLines) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; int lineType = my lineType; double lineWidth = my lineWidth; Graphics_Colour colour = my colour; if (numberOfMarks < 2) return; Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, 0, 1, y1WC, y2WC); Graphics_setTextAlignment (me, Graphics_RIGHT, Graphics_HALF); Graphics_setInner (me); if (haveTicks) { Graphics_setLineType (me, Graphics_DRAWN); Graphics_setLineWidth (me, 2.0 * lineWidth); } for (int i = 1; i <= numberOfMarks; i ++) { double f = (i - 1.0) / (numberOfMarks - 1), yWC = y1WC + (y2WC - y1WC) * f; if (haveNumbers) Graphics_text1 (me, - my horTick, yWC, Melder_float (Melder_half (yWC))); if (haveTicks) Graphics_line (me, - my horTick, yWC, 0, yWC); } if (haveTicks) Graphics_setLineWidth (me, lineWidth); if (haveDottedLines && numberOfMarks > 2) { Graphics_setLineType (me, Graphics_DOTTED); Graphics_setLineWidth (me, 0.67 * lineWidth); for (int i = 2; i < numberOfMarks; i ++) { double f = (i - 1.0) / (numberOfMarks - 1), yWC = y1WC + (y2WC - y1WC) * f; Graphics_line (me, 0, yWC, 1, yWC); } Graphics_setLineWidth (me, lineWidth); } Graphics_unsetInner (me); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setLineType (me, lineType); Graphics_setColour (me, colour); } void Graphics_marksRight (Graphics me, int numberOfMarks, bool haveNumbers, bool haveTicks, bool haveDottedLines) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; int lineType = my lineType; double lineWidth = my lineWidth; Graphics_Colour colour = my colour; if (numberOfMarks < 2) return; Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, 0, 1, y1WC, y2WC); Graphics_setTextAlignment (me, Graphics_LEFT, Graphics_HALF); Graphics_setInner (me); if (haveTicks) { Graphics_setLineType (me, Graphics_DRAWN); Graphics_setLineWidth (me, 2.0 * lineWidth); } for (int i = 1; i <= numberOfMarks; i ++) { double f = (i - 1.0) / (numberOfMarks - 1), yWC = y1WC + (y2WC - y1WC) * f; if (haveNumbers) Graphics_text1 (me, 1 + my horTick, yWC, Melder_float (Melder_half (yWC))); if (haveTicks) Graphics_line (me, 1, yWC, 1 + my horTick, yWC); } if (haveTicks) Graphics_setLineWidth (me, lineWidth); if (haveDottedLines && numberOfMarks > 2) { Graphics_setLineType (me, Graphics_DOTTED); Graphics_setLineWidth (me, 0.67 * lineWidth); for (int i = 2; i < numberOfMarks; i ++) { double f = (i - 1.0) / (numberOfMarks - 1), yWC = y1WC + (y2WC - y1WC) * f; Graphics_line (me, 0, yWC, 1, yWC); } Graphics_setLineWidth (me, lineWidth); } Graphics_unsetInner (me); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setLineType (me, lineType); Graphics_setColour (me, colour); } void Graphics_marksBottom (Graphics me, int numberOfMarks, bool haveNumbers, bool haveTicks, bool haveDottedLines) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; int lineType = my lineType; double lineWidth = my lineWidth; Graphics_Colour colour = my colour; if (numberOfMarks < 2) return; Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, x1WC, x2WC, 0, 1); Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_TOP); Graphics_setInner (me); if (haveTicks) { Graphics_setLineType (me, Graphics_DRAWN); Graphics_setLineWidth (me, 2.0 * lineWidth); } for (int i = 1; i <= numberOfMarks; i ++) { double f = (i - 1.0) / (numberOfMarks - 1), xWC = x1WC + (x2WC - x1WC) * f; if (haveNumbers) Graphics_text1 (me, xWC, - my vertTick, Melder_float (Melder_half (xWC))); if (haveTicks) Graphics_line (me, xWC, - my vertTick, xWC, 0); } if (haveTicks) Graphics_setLineWidth (me, lineWidth); if (haveDottedLines && numberOfMarks > 2) { Graphics_setLineType (me, Graphics_DOTTED); Graphics_setLineWidth (me, 0.67 * lineWidth); for (int i = 2; i < numberOfMarks; i ++) { double f = (i - 1.0) / (numberOfMarks - 1), xWC = x1WC + (x2WC - x1WC) * f; Graphics_line (me, xWC, 0, xWC, 1); } Graphics_setLineWidth (me, lineWidth); } Graphics_unsetInner (me); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setLineType (me, lineType); Graphics_setColour (me, colour); } void Graphics_marksTop (Graphics me, int numberOfMarks, bool haveNumbers, bool haveTicks, bool haveDottedLines) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; int lineType = my lineType; double lineWidth = my lineWidth; Graphics_Colour colour = my colour; if (numberOfMarks < 2) return; Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, x1WC, x2WC, 0, 1); Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_BOTTOM); Graphics_setInner (me); if (haveTicks) { Graphics_setLineType (me, Graphics_DRAWN); Graphics_setLineWidth (me, 2.0 * lineWidth); } for (int i = 1; i <= numberOfMarks; i ++) { double f = (i - 1.0) / (numberOfMarks - 1), xWC = x1WC + (x2WC - x1WC) * f; if (haveNumbers) Graphics_text1 (me, xWC, 1 + my vertTick, Melder_float (Melder_half (xWC))); if (haveTicks) Graphics_line (me, xWC, 1, xWC, 1 + my vertTick); } if (haveTicks) Graphics_setLineWidth (me, lineWidth); if (haveDottedLines && numberOfMarks > 2) { Graphics_setLineType (me, Graphics_DOTTED); Graphics_setLineWidth (me, 0.67 * lineWidth); for (int i = 2; i < numberOfMarks; i ++) { double f = (i - 1.0) / (numberOfMarks - 1), xWC = x1WC + (x2WC - x1WC) * f; Graphics_line (me, xWC, 0, xWC, 1); } Graphics_setLineWidth (me, lineWidth); } Graphics_unsetInner (me); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setLineType (me, lineType); Graphics_setColour (me, colour); } #define MAXNUM_MARKS_PER_DECADE 7 static double decade_y [1 + MAXNUM_MARKS_PER_DECADE] [1 + MAXNUM_MARKS_PER_DECADE] = { { 0 }, { 0, 10 }, { 0, 10, 30 }, { 0, 10, 20, 50 }, { 0, 10, 20, 30, 50 }, { 0, 10, 20, 30, 50, 70 }, { 0, 10, 15, 20, 30, 50, 70 }, { 0, 10, 15, 20, 30, 40, 50, 70 } }; void Graphics_marksLeftLogarithmic (Graphics me, int numberOfMarksPerDecade, bool haveNumbers, bool haveTicks, bool haveDottedLines) { double x1 = my d_x1WC, x2 = my d_x2WC, y1 = my d_y1WC, y2 = my d_y2WC; int lineType = my lineType; double lineWidth = my lineWidth; Graphics_Colour colour = my colour; if (numberOfMarksPerDecade < 1) numberOfMarksPerDecade = 1; if (numberOfMarksPerDecade > MAXNUM_MARKS_PER_DECADE) numberOfMarksPerDecade = MAXNUM_MARKS_PER_DECADE; if (y1 > 300 || y2 > 300) return; double py1 = pow (10, y1 + ( y1 < y2 ? -1e-6 : 1e-6 )); double py2 = pow (10, y2 + ( y1 < y2 ? 1e-6 : -1e-6 )); Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, 0, 1, y1, y2); Graphics_setTextAlignment (me, Graphics_RIGHT, Graphics_HALF); Graphics_setInner (me); for (int i = 1; i <= numberOfMarksPerDecade; i ++) { double y = decade_y [numberOfMarksPerDecade] [i]; while (y < (y1= (y1 MAXNUM_MARKS_PER_DECADE) numberOfMarksPerDecade = MAXNUM_MARKS_PER_DECADE; if (y1 > 300 || y2 > 300) return; double py1 = pow (10, y1 + ( y1 < y2 ? -1e-6 : 1e-6 )); double py2 = pow (10, y2 + ( y1 < y2 ? 1e-6 : -1e-6 )); Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, 0, 1, y1, y2); Graphics_setTextAlignment (me, Graphics_LEFT, Graphics_HALF); Graphics_setInner (me); for (int i = 1; i <= numberOfMarksPerDecade; i ++) { double y = decade_y [numberOfMarksPerDecade] [i]; while (y < (y1= (y1 MAXNUM_MARKS_PER_DECADE) numberOfMarksPerDecade = MAXNUM_MARKS_PER_DECADE; if (x1 > 300 || x2 > 300) return; double px1 = pow (10, x1 + ( x1 < x2 ? -1e-6 : 1e-6 )); double px2 = pow (10, x2 + ( x1 < x2 ? 1e-6 : -1e-6 )); Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, x1, x2, 0, 1); Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_BOTTOM); Graphics_setInner (me); for (int i = 1; i <= numberOfMarksPerDecade; i ++) { double x = decade_y [numberOfMarksPerDecade] [i]; while (x < (x1= (x1 MAXNUM_MARKS_PER_DECADE) numberOfMarksPerDecade = MAXNUM_MARKS_PER_DECADE; if (x1 > 300 || x2 > 300) return; double px1 = pow (10, x1 + ( x1 < x2 ? -1e-6 : 1e-6 )); double px2 = pow (10, x2 + ( x1 < x2 ? 1e-6 : -1e-6 )); Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, x1, x2, 0, 1); Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_TOP); Graphics_setInner (me); for (int i = 1; i <= numberOfMarksPerDecade; i ++) { double x = decade_y [numberOfMarksPerDecade] [i]; while (x < (x1= (x1 last) return; Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, 0, 1, y1WC, y2WC); Graphics_setTextAlignment (me, Graphics_LEFT, Graphics_HALF); Graphics_setInner (me); if (haveTicks) { Graphics_setLineType (me, Graphics_DRAWN); Graphics_setLineWidth (me, 2.0 * lineWidth); } for (int i = first; i <= last; i ++) { double yWC = i * distance; if (haveNumbers) Graphics_text1 (me, 1 + my horTick, yWC, Melder_float (Melder_half (yWC / units))); if (haveTicks) Graphics_line (me, 1, yWC, 1 + my horTick, yWC); } if (haveTicks) Graphics_setLineWidth (me, lineWidth); if (haveDottedLines) { Graphics_setLineType (me, Graphics_DOTTED); Graphics_setLineWidth (me, 0.67 * lineWidth); for (int i = first; i <= last; i ++) { double yWC = i * distance; Graphics_line (me, 0, yWC, 1, yWC); } Graphics_setLineWidth (me, lineWidth); } Graphics_unsetInner (me); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setLineType (me, lineType); Graphics_setColour (me, colour); } void Graphics_marksBottomEvery (Graphics me, double units, double distance, bool haveNumbers, bool haveTicks, bool haveDottedLines) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; int lineType = my lineType, first, last; double lineWidth = my lineWidth; Graphics_Colour colour = my colour; distance *= units; first = ceil (( x1WC < x2WC ? x1WC : x2WC ) / distance - 1e-5); last = floor (( x1WC < x2WC ? x2WC : x1WC) / distance + 1e-5); Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, x1WC, x2WC, 0, 1); Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_TOP); Graphics_setInner (me); if (haveTicks) { Graphics_setLineType (me, Graphics_DRAWN); Graphics_setLineWidth (me, 2.0 * lineWidth); } for (int i = first; i <= last; i ++) { double xWC = i * distance; if (haveNumbers) Graphics_text1 (me, xWC, - my vertTick, Melder_float (Melder_half (xWC / units))); if (haveTicks) Graphics_line (me, xWC, - my vertTick, xWC, 0); } if (haveTicks) Graphics_setLineWidth (me, lineWidth); if (haveDottedLines) { Graphics_setLineType (me, Graphics_DOTTED); Graphics_setLineWidth (me, 0.67 * lineWidth); for (int i = first; i <= last; i ++) { double xWC = i * distance; Graphics_line (me, xWC, 0, xWC, 1); } Graphics_setLineWidth (me, lineWidth); } Graphics_unsetInner (me); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setLineType (me, lineType); Graphics_setColour (me, colour); } void Graphics_marksTopEvery (Graphics me, double units, double distance, bool haveNumbers, bool haveTicks, bool haveDottedLines) { double x1WC = my d_x1WC, x2WC = my d_x2WC, y1WC = my d_y1WC, y2WC = my d_y2WC; int lineType = my lineType, first, last; double lineWidth = my lineWidth; Graphics_Colour colour = my colour; distance *= units; first = ceil (( x1WC < x2WC ? x1WC : x2WC ) / distance - 1e-5); last = floor (( x1WC < x2WC ? x2WC : x1WC) / distance + 1e-5); Graphics_setColour (me, Graphics_BLACK); Graphics_setWindow (me, x1WC, x2WC, 0, 1); Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_BOTTOM); Graphics_setInner (me); if (haveTicks) { Graphics_setLineType (me, Graphics_DRAWN); Graphics_setLineWidth (me, 2.0 * lineWidth); } for (int i = first; i <= last; i ++) { double xWC = i * distance; if (haveNumbers) Graphics_text1 (me, xWC, 1 + my vertTick, Melder_float (Melder_half (xWC / units))); if (haveTicks) Graphics_line (me, xWC, 1, xWC, 1 + my vertTick); } if (haveTicks) Graphics_setLineWidth (me, lineWidth); if (haveDottedLines) { Graphics_setLineType (me, Graphics_DOTTED); Graphics_setLineWidth (me, 0.67 * lineWidth); for (int i = first; i <= last; i ++) { double xWC = i * distance; Graphics_line (me, xWC, 0, xWC, 1); } Graphics_setLineWidth (me, lineWidth); } Graphics_unsetInner (me); Graphics_setWindow (me, x1WC, x2WC, y1WC, y2WC); Graphics_setLineType (me, lineType); Graphics_setColour (me, colour); } void Graphics_mark (Graphics me, double x, double y, double size_mm, const wchar_t *markString) { int mark; if (! markString || ! markString [0]) mark = 0; else if (! markString [1]) { if (markString [0] == '+') mark = 1; else if (markString [0] == 'x') mark = 2; else if (markString [0] == 'o') mark = 3; else if (markString [0] == '.') mark = 0; else mark = -1; } else mark = -1; if (mark == -1) { int oldSize = my fontSize; int oldHorizontalAlignment = my horizontalTextAlignment; int oldVerticalAlignment = my verticalTextAlignment; Graphics_setFontSize (me, size_mm * 72 / 25.4); Graphics_setTextAlignment (me, Graphics_CENTRE, Graphics_HALF); Graphics_text (me, x, y, markString); Graphics_setFontSize (me, oldSize); Graphics_setTextAlignment (me, oldHorizontalAlignment, oldVerticalAlignment); } else if (mark == 0) { Graphics_fillCircle_mm (me, x, y, size_mm); } else if (mark == 1) { double dx = 0.5 * Graphics_dxMMtoWC (me, size_mm); double dy = 0.5 * Graphics_dyMMtoWC (me, size_mm); Graphics_line (me, x - dx, y, x + dx, y); Graphics_line (me, x, y - dy, x, y + dy); } else if (mark == 2) { double dx = 0.4 * Graphics_dxMMtoWC (me, size_mm); double dy = 0.4 * Graphics_dyMMtoWC (me, size_mm); Graphics_line (me, x - dx, y - dy, x + dx, y + dy); Graphics_line (me, x + dx, y - dy, x - dx, y + dy); } else { Graphics_circle_mm (me, x, y, size_mm); } } void Graphics_setTextRotation_vector (Graphics me, double dx, double dy) { double angle; if (dy == 0.0) { angle = dx >= 0.0 ? 0.0 : 180.0; } else if (dx == 0.0) { angle = dy > 0.0 ? 90.0 : 270.0; } else { double dxDC = dx * my scaleX, dyDC = my yIsZeroAtTheTop ? -dy * my scaleY : dy * my scaleY; angle = atan2 (dyDC, dxDC) * (180 / NUMpi); } Graphics_setTextRotation (me, angle); } /* End of file Graphics_utils.cpp */ sources_5316/sys/oo_DESTROY.h0000644000176700017670000000750311724670447014561 0ustar paulpaul/* oo_DESTROY.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) #define oo_ARRAY(type,storage,x,cap,n) #define oo_SET(type,storage,x,setType) #define oo_VECTOR(type,storage,x,min,max) \ NUMvector_free (x, min); #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) \ NUMmatrix_free (x, row1, col1); #define oo_ENUMx(type,storage,Type,x) #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) #define oo_ENUMx_SET(type,storage,Type,x,setType) #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) \ NUMvector_free (x, min); #define oo_STRINGx(storage,x) \ Melder_free (x); #define oo_STRINGx_ARRAY(storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ Melder_free (x [i]); #define oo_STRINGx_SET(storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ Melder_free (x [i]); #define oo_STRINGx_VECTOR(storage,x,min,max) \ if (x) { \ for (long i = min; i <= max; i ++) \ Melder_free (x [i]); \ NUMvector_free (x, min); \ } #define oo_STRUCT(Type,x) \ x. destroy (); #define oo_STRUCT_ARRAY(Type,x,cap,n) \ for (int i = 0; i < n; i ++) \ x [i]. destroy (); #define oo_STRUCT_SET(Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ x [i]. destroy (); #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ if (x) { \ for (long i = min; i <= max; i ++) \ x [i]. destroy (); \ NUMvector_free (x, min); \ } #define oo_STRUCT_MATRIX_FROM(Type,x,row1,row2,col1,col2) \ if (x) { \ for (long i = row1; i <= row2; i ++) \ for (long j = col1; j <= col2; j ++) \ x [i] [j] -> destroy (); \ NUMmatrix_free (x, row1, col1); \ } #define oo_WIDGET(x) \ if (x) XtDestroyWidget (x); #define oo_WIDGET_ARRAY(x,cap,n) \ for (int i = 0; i < n; i ++) \ if (x [i]) XtDestroyWidget (x [i]); #define oo_WIDGET_SET(x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ if (x [i]) XtDestroyWidget (x [i]); #define oo_WIDGET_VECTOR_FROM(x,min,max) \ if (x) { \ for (long i = min; i <= max; i ++) \ XtDestroyWidget (x [i]); \ NUMvector_free (sizeof (GuiObject), x, min, 0); \ } #define oo_OBJECT(Class,version,x) \ forget (x); #define oo_COLLECTION(Class,x,ItemClass,version) \ forget (x); #define oo_FILE(x) #define oo_DIR(x) #define oo_DEFINE_STRUCT(Struct) \ void struct##Struct :: destroy () { #define oo_END_STRUCT(Type) \ } #define oo_DEFINE_CLASS(Class,Parent) \ void struct##Class :: v_destroy () { \ #define oo_END_CLASS(Class) \ Class##_Parent :: v_destroy (); \ } #define oo_IF(condition) \ if (condition) { #define oo_ENDIF \ } #define oo_FROM(from) #define oo_ENDFROM #define oo_VERSION(version) #define oo_DECLARING 0 #define oo_DESTROYING 1 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 0 #define oo_READING 0 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 0 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_DESTROY.h */ sources_5316/sys/Preferences.cpp0000644000176700017670000001664611724662321015527 0ustar paulpaul/* Preferences.cpp * * Copyright (C) 1996-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Preferences.h" #include "Collection.h" /* * Though Preference inherits from Data, * we will use SimpleString routines with it. */ Thing_define (Preference, SimpleString) { // new data: public: int type; void *value; int min, max; const wchar * (*getText) (int value); int (*getValue) (const wchar *text); // overridden methods: void v_destroy (); }; Thing_implement (Preference, SimpleString, 0); /* Warning: copy methods etc. not implemented. */ void structPreference :: v_destroy () { Melder_free (string); Preference_Parent :: v_destroy (); } static SortedSetOfString thePreferences; static void Preferences_add (const wchar *string, int type, void *value, int min, int max, const wchar *(*getText) (int value), int (*getValue) (const wchar *text)) { Preference me = Thing_new (Preference); my string = Melder_wcsdup_f (string); my type = type; my value = value; my min = min; my max = max; my getText = getText; my getValue = getValue; if (! thePreferences) thePreferences = SortedSetOfString_create (); Collection_addItem (thePreferences, me); } void Preferences_addByte (const wchar_t *string, signed char *value, signed char defaultValue) { *value = defaultValue; Preferences_add (string, bytewa, value, 0, 0, NULL, NULL); } void Preferences_addInt (const wchar_t *string, int *value, int defaultValue) { *value = defaultValue; Preferences_add (string, intwa, value, 0, 0, NULL, NULL); } void Preferences_addLong (const wchar_t *string, long *value, long defaultValue) { *value = defaultValue; Preferences_add (string, longwa, value, 0, 0, NULL, NULL); } void Preferences_addUbyte (const wchar_t *string, unsigned char *value, unsigned char defaultValue) { *value = defaultValue; Preferences_add (string, ubytewa, value, 0, 0, NULL, NULL); } void Preferences_addUint (const wchar_t *string, unsigned int *value, unsigned int defaultValue) { *value = defaultValue; Preferences_add (string, uintwa, value, 0, 0, NULL, NULL); } void Preferences_addUlong (const wchar_t *string, unsigned long *value, unsigned long defaultValue) { *value = defaultValue; Preferences_add (string, ulongwa, value, 0, 0, NULL, NULL); } void Preferences_addBool (const wchar_t *string, bool *value, bool defaultValue) { *value = defaultValue; Preferences_add (string, boolwa, value, 0, 0, NULL, NULL); } void Preferences_addDouble (const wchar_t *string, double *value, double defaultValue) { *value = defaultValue; Preferences_add (string, doublewa, value, 0, 0, NULL, NULL); } void Preferences_addString (const wchar_t *string, wchar_t *value, const wchar_t *defaultValue) { wcscpy (value, defaultValue); Preferences_add (string, stringwa, value, 0, 0, NULL, NULL); } void _Preferences_addEnum (const wchar_t *string, enum kPreferences_dummy *value, int min, int max, const wchar_t *(*getText) (int value), int (*getValue) (const wchar_t *text), enum kPreferences_dummy defaultValue) { { *value = defaultValue; Preferences_add (string, enumwa, value, min, max, getText, getValue); } } void Preferences_read (MelderFile file) { /* * It is possible (see praat.c) that this routine is called * before any preferences have been registered. * In that case, do nothing. */ if (! thePreferences) return; try { autoMelderReadText text = MelderReadText_createFromFile (file); for (;;) { wchar *line = MelderReadText_readLine (text.peek()); if (line == NULL) return; // OK: we have read past the last line wchar *value = wcsstr (line, L": "); if (value == NULL) return; // OK: we have read past the last key-value pair *value = '\0', value += 2; long ipref = SortedSetOfString_lookUp (thePreferences, line); if (! ipref) continue; // skip unrecognized keys Preference pref = (Preference) thePreferences -> item [ipref]; switch (pref -> type) { case bytewa: * (signed char *) pref -> value = wcstol (value, NULL, 10); break; case intwa: * (int *) pref -> value = wcstol (value, NULL, 10); break; case longwa: * (long *) pref -> value = wcstol (value, NULL, 10); break; case ubytewa: * (unsigned char *) pref -> value = wcstoul (value, NULL, 10); break; case uintwa: * (unsigned int *) pref -> value = wcstoul (value, NULL, 10); break; case ulongwa: * (unsigned long *) pref -> value = wcstoul (value, NULL, 10); break; case boolwa: * (bool *) pref -> value = wcsnequ (value, L"yes", 3) ? true : wcsnequ (value, L"no", 2) ? false : wcstol (value, NULL, 10) != 0; break; case doublewa: * (double *) pref -> value = Melder_atof (value); break; case stringwa: { wcsncpy ((wchar *) pref -> value, value, Preferences_STRING_BUFFER_SIZE); ((wchar *) pref -> value) [Preferences_STRING_BUFFER_SIZE - 1] = '\0'; break; } case enumwa: { int intValue = pref -> getValue (value); if (intValue < 0) intValue = pref -> getValue (L"\t"); // look for the default * (enum kPreferences_dummy *) pref -> value = (enum kPreferences_dummy) intValue; break; } } } } catch (MelderError) { Melder_clearError (); // this is done during start-up, so it should never fail } } void Preferences_write (MelderFile file) { if (! thePreferences || thePreferences -> size == 0) return; static MelderString buffer = { 0 }; for (long ipref = 1; ipref <= thePreferences -> size; ipref ++) { Preference pref = (Preference) thePreferences -> item [ipref]; MelderString_append (& buffer, pref -> string, L": "); switch (pref -> type) { case bytewa: MelderString_append (& buffer, Melder_integer (* (signed char *) pref -> value)); break; case intwa: MelderString_append (& buffer, Melder_integer (* (int *) pref -> value)); break; case longwa: MelderString_append (& buffer, Melder_integer (* (long *) pref -> value)); break; case ubytewa: MelderString_append (& buffer, Melder_integer (* (unsigned char *) pref -> value)); break; case uintwa: MelderString_append (& buffer, Melder_integer (* (unsigned int *) pref -> value)); break; case ulongwa: MelderString_append (& buffer, Melder_integer (* (unsigned long *) pref -> value)); break; case boolwa: MelderString_append (& buffer, Melder_boolean (* (bool *) pref -> value)); break; case doublewa: MelderString_append (& buffer, Melder_double (* (double *) pref -> value)); break; case stringwa: MelderString_append (& buffer, (const wchar *) pref -> value); break; case enumwa: MelderString_append (& buffer, pref -> getText (* (enum kPreferences_dummy *) pref -> value)); break; } MelderString_appendCharacter (& buffer, '\n'); } try { MelderFile_writeText (file, buffer.string); } catch (MelderError) { Melder_clearError (); } forget (thePreferences); } /* End of file Preferences.cpp */ sources_5316/sys/Graphics_record.cpp0000644000176700017670000004200211752476027016354 0ustar paulpaul/* Graphics_record.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2004/02/15 highlight2 * pb 2007/03/14 arrowSize * pb 2007/08/08 text is saved as UTF-8 * pb 2008/01/19 removed 16M limitation on number of elements (-> double) * sdk 2008/03/24 cairo * pb 2009/07/09 RGB colours * pb 2009/08/10 image from file * pb 2010/07/11 Graphics_clearRecording () * pb 2011/03/17 C++ * pb 2011/06/18 Graphics_polyline_closed () */ #include "GraphicsP.h" #define RECORDING_HEADER_LENGTH 2 double * _Graphics_check (Graphics me, long number) { static bool messageHasAlreadyBeenShownOnce = false; double *result = NULL; double *record = my record; long nrecord = my nrecord; if (nrecord == 0) { nrecord = 1000; try { record = Melder_malloc (double, 1 + nrecord); } catch (MelderError) { if (messageHasAlreadyBeenShownOnce) { Melder_clearError (); } else { messageHasAlreadyBeenShownOnce = true; Melder_flushError ("_Graphics_growRecorder: out of memory.\n" "This message will not show up on future occasions."); // because of loop danger when redrawing } return NULL; } my record = record; my nrecord = nrecord; } if (nrecord < my irecord + RECORDING_HEADER_LENGTH + number) { while (nrecord < my irecord + RECORDING_HEADER_LENGTH + number) nrecord *= 2; try { record = (double *) Melder_realloc (record, (1 + nrecord) * sizeof (double)); } catch (MelderError) { if (messageHasAlreadyBeenShownOnce) { Melder_clearError (); } else { messageHasAlreadyBeenShownOnce = true; Melder_flushError ("_Graphics_growRecorder: out of memory.\n" "This message will not show up on future occasions."); // because of loop danger when redrawing } return NULL; } my record = record; my nrecord = nrecord; } result = my record + my irecord; my irecord += number + RECORDING_HEADER_LENGTH; return result; } /***** RECORD AND PLAY *****/ bool Graphics_startRecording (Graphics me) { bool wasRecording = my recording; my recording = true; return wasRecording; } bool Graphics_stopRecording (Graphics me) { bool wasRecording = my recording; my recording = false; return wasRecording; } void Graphics_clearRecording (Graphics me) { if (my record) { Melder_free (my record); my irecord = 0; my nrecord = 0; } } // TODO: Paul, ik zou er een enorme fan van zijn als bij deze functie // ook een bounding box van events kan worden meegeven. void Graphics_play (Graphics me, Graphics thee) { double *p = my record, *endp = p + my irecord; bool wasRecording = my recording; if (! p) return; my recording = false; /* Temporarily, in case me == thee. */ while (p < endp) { #define get (* ++ p) #define mget(n) (p += n, p - n) #define sget(n) ((char *) (p += n, p - n + 1)) // #define skip(x1, x2, y1, y2) if ((((x1 >= thy x1DC && x1 <= thy x2DC) || (x2 >= thy x1DC && x2 <= thy x2DC)) && ((y1 >= thy y1DC && y1 <= thy y2DC) || (y2 >= thy y1DC && y2 <= thy y2DC))) == FALSE) { g_debug("SKIP!"); break; } int opcode = (int) get; (void) (long) get; // ignore number of arguments switch (opcode) { case SET_VIEWPORT: { double x1NDC = get, x2NDC = get, y1NDC = get, y2NDC = get; // skip(x1NDC, x2NDC, y1NDC, y2NDC) Graphics_setViewport (thee, x1NDC, x2NDC, y1NDC, y2NDC); } break; case SET_INNER: Graphics_setInner (thee); break; case UNSET_INNER: Graphics_unsetInner (thee); break; case SET_WINDOW: { double x1 = get, x2 = get, y1 = get, y2 = get; // skip(x1, x2, y1, y2) Graphics_setWindow (thee, x1, x2, y1, y2); } break; case TEXT: { double x = get, y = get; long length = get; char *text_utf8 = sget (length); // skip(x, x, y, y) Graphics_text (thee, x, y, Melder_peekUtf8ToWcs (text_utf8)); } break; case POLYLINE: { long n = get; double *x = mget (n), *y = mget (n); Graphics_polyline (thee, n, & x [1], & y [1]); } break; case LINE: { double x1 = get, y1 = get, x2 = get, y2 = get; // skip(x1, x2, y1, y2) Graphics_line (thee, x1, y1, x2, y2); } break; case ARROW: { double x1 = get, y1 = get, x2 = get, y2 = get; Graphics_arrow (thee, x1, y1, x2, y2); } break; case FILL_AREA: { long n = get; double *x = mget (n), *y = mget (n); Graphics_fillArea (thee, n, & x [1], & y [1]); } break; case FUNCTION: { long n = get; double x1 = get, x2 = get, *y = mget (n); Graphics_function (thee, y, 1, n, x1, x2); } break; case RECTANGLE: { double x1 = get, x2 = get, y1 = get, y2 = get; Graphics_rectangle (thee, x1, x2, y1, y2); } break; case FILL_RECTANGLE: { double x1 = get, x2 = get, y1 = get, y2 = get; // skip(x1, x2, y1, y2) Graphics_fillRectangle (thee, x1, x2, y1, y2); } break; case CIRCLE: { double x = get, y = get, r = get; Graphics_circle (thee, x, y, r); } break; case FILL_CIRCLE: { double x = get, y = get, r = get; Graphics_fillCircle (thee, x, y, r); } break; case ARC: { double x = get, y = get, r = get, fromAngle = get, toAngle = get; Graphics_arc (thee, x, y, r, fromAngle, toAngle); } break; case ARC_ARROW: { double x = get, y = get, r = get, fromAngle = get, toAngle = get; int arrowAtStart = get, arrowAtEnd = get; Graphics_arcArrow (thee, x, y, r, fromAngle, toAngle, arrowAtStart, arrowAtEnd); } break; case HIGHLIGHT: { double x1 = get, x2 = get, y1 = get, y2 = get; Graphics_highlight (thee, x1, x2, y1, y2); } break; case CELL_ARRAY: { double x1 = get, x2 = get, y1 = get, y2 = get, minimum = get, maximum = get; long nrow = get, ncol = get; /* * We don't copy all the data into a new matrix. * Instead, we create row pointers z [1..nrow] that point directly into the recorded data. * This works because the data is a packed array of double, just as Graphics_cellArray expects. */ double **z = Melder_malloc_f (double *, nrow); z [0] = p + 1; for (long irow = 1; irow < nrow; irow ++) z [irow] = z [irow - 1] + ncol; p += nrow * ncol; Graphics_cellArray (thee, z, 0, ncol - 1, x1, x2, 0, nrow - 1, y1, y2, minimum, maximum); Melder_free (z); } break; case SET_FONT: Graphics_setFont (thee, (enum kGraphics_font) get); break; case SET_FONT_SIZE: Graphics_setFontSize (thee, (int) get); break; case SET_FONT_STYLE: Graphics_setFontStyle (thee, (int) get); break; case SET_TEXT_ALIGNMENT: { int hor = get, vert = get; Graphics_setTextAlignment (thee, hor, vert); } break; case SET_TEXT_ROTATION: Graphics_setTextRotation (thee, get); break; case SET_LINE_TYPE: Graphics_setLineType (thee, (int) get); break; case SET_LINE_WIDTH: Graphics_setLineWidth (thee, get); break; case SET_STANDARD_COLOUR: // only used in old Praat picture files { int standardColour = (int) get; Graphics_Colour colour = standardColour == 0 ? Graphics_BLACK : standardColour == 1 ? Graphics_WHITE : standardColour == 2 ? Graphics_RED : standardColour == 3 ? Graphics_GREEN : standardColour == 4 ? Graphics_BLUE : standardColour == 5 ? Graphics_CYAN : standardColour == 6 ? Graphics_MAGENTA : standardColour == 7 ? Graphics_YELLOW : standardColour == 8 ? Graphics_MAROON : standardColour == 9 ? Graphics_LIME : standardColour == 10 ? Graphics_NAVY : standardColour == 11 ? Graphics_TEAL : standardColour == 12 ? Graphics_PURPLE : standardColour == 13 ? Graphics_OLIVE : standardColour == 14 ? Graphics_PINK : standardColour == 15 ? Graphics_SILVER : Graphics_GREY; Graphics_setColour (thee, colour); } break; case SET_GREY: Graphics_setGrey (thee, get); break; case MARK_GROUP: Graphics_markGroup (thee); break; case ELLIPSE: { double x1 = get, x2 = get, y1 = get, y2 = get; Graphics_ellipse (thee, x1, x2, y1, y2); } break; case FILL_ELLIPSE: { double x1 = get, x2 = get, y1 = get, y2 = get; Graphics_fillEllipse (thee, x1, x2, y1, y2); } break; case CIRCLE_MM: { double x = get, y = get, d = get; Graphics_circle_mm (thee, x, y, d); } break; case FILL_CIRCLE_MM: { double x = get, y = get, d = get; Graphics_fillCircle_mm (thee, x, y, d); } break; case IMAGE8: { double x1 = get, x2 = get, y1 = get, y2 = get, minimum = get, maximum = get; long nrow = get, ncol = get; unsigned char **z = NUMmatrix (1, nrow, 1, ncol); // BUG memory for (long irow = 1; irow <= nrow; irow ++) for (long icol = 1; icol <= ncol; icol ++) z [irow] [icol] = get; Graphics_image8 (thee, z, 1, ncol, x1, x2, 1, nrow, y1, y2, minimum, maximum); NUMmatrix_free (z, 1, 1); } break; case UNHIGHLIGHT: { double x1 = get, x2 = get, y1 = get, y2 = get; Graphics_unhighlight (thee, x1, x2, y1, y2); } break; #if motif case XOR_ON: { Graphics_Colour colour; colour. red = get, colour. green = get, colour. blue = get; Graphics_xorOn (thee, colour); } break; case XOR_OFF: Graphics_xorOff (thee); break; #endif case RECTANGLE_MM: { double x = get, y = get, horSide = get, vertSide = get; Graphics_rectangle_mm (thee, x, y, horSide, vertSide); } break; case FILL_RECTANGLE_MM: { double x = get, y = get, horSide = get, vertSide = get; Graphics_fillRectangle_mm (thee, x, y, horSide, vertSide); } break; case SET_WS_WINDOW: { double x1NDC = get, x2NDC = get, y1NDC = get, y2NDC = get; Graphics_setWsWindow (thee, x1NDC, x2NDC, y1NDC, y2NDC); } break; case SET_WRAP_WIDTH: Graphics_setWrapWidth (thee, get); break; case SET_SECOND_INDENT: Graphics_setSecondIndent (thee, get); break; case SET_PERCENT_SIGN_IS_ITALIC: Graphics_setPercentSignIsItalic (thee, (bool) get); break; case SET_NUMBER_SIGN_IS_BOLD: Graphics_setNumberSignIsBold (thee, (bool) get); break; case SET_CIRCUMFLEX_IS_SUPERSCRIPT: Graphics_setCircumflexIsSuperscript (thee, (bool) get); break; case SET_UNDERSCORE_IS_SUBSCRIPT: Graphics_setUnderscoreIsSubscript (thee, (bool) get); break; case SET_DOLLAR_SIGN_IS_CODE: Graphics_setDollarSignIsCode (thee, (bool) get); break; case SET_AT_SIGN_IS_LINK: Graphics_setAtSignIsLink (thee, (bool) get); break; case BUTTON: { double x1 = get, x2 = get, y1 = get, y2 = get; Graphics_button (thee, x1, x2, y1, y2); } break; case ROUNDED_RECTANGLE: { double x1 = get, x2 = get, y1 = get, y2 = get, r = get; Graphics_roundedRectangle (thee, x1, x2, y1, y2, r); } break; case FILL_ROUNDED_RECTANGLE: { double x1 = get, x2 = get, y1 = get, y2 = get, r = get; Graphics_fillRoundedRectangle (thee, x1, x2, y1, y2, r); } break; case FILL_ARC: { double x = get, y = get, r = get, fromAngle = get, toAngle = get; Graphics_fillArc (thee, x, y, r, fromAngle, toAngle); } break; case INNER_RECTANGLE: { double x1 = get, x2 = get, y1 = get, y2 = get; Graphics_innerRectangle (thee, x1, x2, y1, y2); } break; case CELL_ARRAY8: { double x1 = get, x2 = get, y1 = get, y2 = get, minimum = get, maximum = get; long nrow = get, ncol = get; unsigned char **z = NUMmatrix (1, nrow, 1, ncol); // BUG memory for (long irow = 1; irow <= nrow; irow ++) for (long icol = 1; icol <= ncol; icol ++) z [irow] [icol] = get; Graphics_cellArray8 (thee, z, 1, ncol, x1, x2, 1, nrow, y1, y2, minimum, maximum); NUMmatrix_free (z, 1, 1); } break; case IMAGE: { double x1 = get, x2 = get, y1 = get, y2 = get, minimum = get, maximum = get; long nrow = get, ncol = get; /* * We don't copy all the data into a new matrix. * Instead, we create row pointers z [1..nrow] that point directly into the recorded data. * This works because the data is a packed array of double, just as Graphics_image expects. */ double **z = Melder_malloc_f (double *, nrow); z [0] = p + 1; for (long irow = 1; irow < nrow; irow ++) z [irow] = z [irow - 1] + ncol; p += nrow * ncol; Graphics_image (thee, z, 0, ncol - 1, x1, x2, 0, nrow - 1, y1, y2, minimum, maximum); Melder_free (z); } break; case HIGHLIGHT2: { double x1 = get, x2 = get, y1 = get, y2 = get, innerX1 = get, innerX2 = get, innerY1 = get, innerY2 = get; Graphics_highlight2 (thee, x1, x2, y1, y2, innerX1, innerX2, innerY1, innerY2); } break; case UNHIGHLIGHT2: { double x1 = get, x2 = get, y1 = get, y2 = get, innerX1 = get, innerX2 = get, innerY1 = get, innerY2 = get; Graphics_unhighlight2 (thee, x1, x2, y1, y2, innerX1, innerX2, innerY1, innerY2); } break; case SET_ARROW_SIZE: Graphics_setArrowSize (thee, get); break; case DOUBLE_ARROW: { double x1 = get, y1 = get, x2 = get, y2 = get; Graphics_doubleArrow (thee, x1, y1, x2, y2); } break; case SET_RGB_COLOUR: { Graphics_Colour colour; colour. red = get, colour. green = get, colour. blue = get; Graphics_setColour (thee, colour); } break; case IMAGE_FROM_FILE: { double x1 = get, x2 = get, y1 = get, y2 = get; long length = get; char *text_utf8 = sget (length); Graphics_imageFromFile (thee, Melder_peekUtf8ToWcs (text_utf8), x1, x2, y1, y2); } break; case POLYLINE_CLOSED: { long n = get; double *x = mget (n), *y = mget (n); Graphics_polyline_closed (thee, n, & x [1], & y [1]); } break; default: my recording = wasRecording; Melder_flushError ("Graphics_play: unknown opcode (%d).\n%f %f", opcode, p [-1], p [1]); return; } } my recording = wasRecording; } /* For debugging: #define binputi4(o,f) ascputi4(o,f,"") #define binputr4(o,f) ascputr4(o,f,"") */ void Graphics_writeRecordings (Graphics me, FILE *f) { double *p = my record, *endp = p + my irecord; if (! p) return; binputi4 (my irecord, f); while (p < endp) { #define get (* ++ p) int opcode = (int) get; binputr4 ((float) opcode, f); long numberOfArguments = (long) get; const long largestIntegerRepresentableAs32BitFloat = 0x00FFFFFF; if (numberOfArguments > largestIntegerRepresentableAs32BitFloat) { binputr4 (-1.0, f); binputi4 (numberOfArguments, f); //Melder_warning ("This picture is very large!"); } else { binputr4 ((float) numberOfArguments, f); } if (opcode == TEXT) { binputr4 (get, f); /* x */ binputr4 (get, f); /* y */ binputr4 (get, f); /* length */ Melder_assert (sizeof (double) == 8); if ((long) fwrite (++ p, 8, numberOfArguments - 3, f) < numberOfArguments - 3) // text Melder_throw ("Error writing graphics recordings."); p += numberOfArguments - 4; } else { for (long i = numberOfArguments; i > 0; i --) binputr4 (get, f); } } } void Graphics_readRecordings (Graphics me, FILE *f) { long old_irecord = my irecord; long added_irecord = 0; double *p = NULL, *endp = NULL; long numberOfArguments = 0; int opcode = 0; try { added_irecord = bingeti4 (f); p = _Graphics_check (me, added_irecord - RECORDING_HEADER_LENGTH); if (! p) return; Melder_assert (my irecord == old_irecord + added_irecord); endp = p + added_irecord; while (p < endp) { opcode = (int) bingetr4 (f); put (opcode); numberOfArguments = (long) bingetr4 (f); if (numberOfArguments == -1) { numberOfArguments = bingeti4 (f); } put (numberOfArguments); if (opcode == TEXT) { put (bingetr4 (f)); // x put (bingetr4 (f)); // y put (bingetr4 (f)); // length if ((long) fread (++ p, 8, numberOfArguments - 3, f) < numberOfArguments - 3) // text Melder_throw ("Error reading graphics recordings."); p += numberOfArguments - 4; } else { for (long i = numberOfArguments; i > 0; i --) put (bingetr4 (f)); } } } catch (MelderError) { my irecord = old_irecord; Melder_throw ("Error reading graphics record ", added_irecord - (long) (endp - p), " out of ", added_irecord, ".\nOpcode ", opcode, ", args ", numberOfArguments, "."); } } void Graphics_markGroup (Graphics me) { if (my recording) { op (MARK_GROUP, 0); } } void Graphics_undoGroup (Graphics me) { long lastMark = 0; // not yet found long jrecord = 0; while (jrecord < my irecord) { // keep looking for marks until the end int opcode = (int) my record [++ jrecord]; long number = (long) my record [++ jrecord]; if (opcode == MARK_GROUP) lastMark = jrecord - 1; // found a mark jrecord += number; } if (jrecord != my irecord) Melder_flushError ("jrecord != my irecord: %ld, %ld", jrecord, my irecord); if (lastMark > 0) // found? my irecord = lastMark - 1; // forget all graphics from and including the last mark } /* End of file Graphics_record.cpp */ sources_5316/sys/lispio.h0000644000176700017670000000652311614424562014224 0ustar paulpaul#ifndef _lispio_h_ #define _lispio_h_ /* lispio.h * * Copyright (C) 1994-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "melder.h" /* A LISP object is a list or an atom. */ typedef struct Lispio { long length; const char *string; } Lispio; /* A LISP sequence is a sequence of LISP objects. */ typedef struct LispioSeq { long length; const char *string; } LispioSeq; /* All of the following routines expect and return structures without leading spaces. */ /* Moreover, a Lispio has no trailing spaces. */ int Lispio_openList (const Lispio *me, LispioSeq *thee); /* Function: strip the leading '(' and spaces; strip the trailing ')'. Return value: my length != 0 && my string [0] == '('; // Am I a list? Postconditions: result == 0 || thy length <= my length - 2; */ int Lispio_openListFromFile (LispioSeq *me, FILE *f, char *buffer, long maxLength); /* Arguments: f: an open text stream; buffer [0..maxLength-1]: a buffer preallocated on the heap; Return value: 0: failure: Not a list: expected leading '(' but found character '%c'. Early end-of-file detected: no matching ')': depth %ld instead of 0. Buffer too small for list: list longer than bytes. EOF: normal end of file. 1: OK. Warning: 'me' and all the structures derived from 'me' are valid until the next Lispio_openListFromFile (). Example: reading all lists in a file: LispioSeq entry; autofile f = Melder_fopen (fileName, "r"); autostring8 buffer = Melder_malloc (200000); for (;;) { int status = Lispio_openListFromFile (& entry, f, buffer, 200000); if (! status) goto error; if (status == EOF) break; // Leave loop. if (! myProcessList (entry)) goto error; } f.close (file); */ char * Lispio_string (const Lispio *me); /* Return value: a new null-terminated C string, or NULL if out of memory. Postcondition: result == NULL || strlen (result) == my length && result [0..my length-1] == my string [0..my length-1]; */ int Lispio_equal (const Lispio *me, const Lispio *thee); /* Returns thy length == my length && thy string [0..my length-1] == my string [0..my length-1]; */ int Lispio_strequ (const Lispio *me, const char *string); /* Returns strlen (string) == my length && string [0..my length-1] == my string [0..my length-1]; */ int Lispio_read (LispioSeq *me, Lispio *first); /* Return value: 1 if something was found; 0 otherwise. Example: cycle through all the LISP objects in a sequence: while (Lispio_read (& sequence, & object)) processObject (& object); */ long Lispio_count (const LispioSeq *me); int Lispio_isInteger (const Lispio *me); int Lispio_integer (const Lispio *me, long *value); /* End of file lispio.h */ #endif sources_5316/sys/oo_undef.h0000644000176700017670000000355211541430714014515 0ustar paulpaul/* oo_undef.h * * Copyright (C) 1994-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2011/03/03 */ #undef oo_SIMPLE #undef oo_ARRAY #undef oo_SET #undef oo_VECTOR #undef oo_MATRIX #undef oo_ENUMx #undef oo_ENUMx_ARRAY #undef oo_ENUMx_SET #undef oo_ENUMx_VECTOR #undef oo_STRINGx #undef oo_STRINGx_ARRAY #undef oo_STRINGx_SET #undef oo_STRINGx_VECTOR #undef oo_STRUCT #undef oo_STRUCT_ARRAY #undef oo_STRUCT_SET #undef oo_STRUCT_VECTOR_FROM #undef oo_STRUCT_MATRIX_FROM #undef oo_WIDGET #undef oo_WIDGET_ARRAY #undef oo_WIDGET_SET #undef oo_WIDGET_VECTOR_FROM #undef oo_OBJECT #undef oo_COLLECTION #undef oo_FILE #undef oo_DIR #undef oo_DEFINE_STRUCT #undef oo_END_STRUCT #undef oo_DEFINE_CLASS #undef oo_END_CLASS #undef oo_IF #undef oo_ENDIF #undef oo_FROM #undef oo_ENDFROM #undef oo_VERSION #undef oo_DECLARING #undef oo_DESTROYING #undef oo_COPYING #undef oo_EQUALLING #undef oo_COMPARING #undef oo_VALIDATING_ENCODING #undef oo_READING #undef oo_READING_TEXT #undef oo_READING_BINARY #undef oo_READING_CACHE #undef oo_READING_LISP #undef oo_WRITING #undef oo_WRITING_TEXT #undef oo_WRITING_BINARY #undef oo_WRITING_CACHE #undef oo_WRITING_LISP #undef oo_DESCRIBING /* End of file oo_undef.h */ sources_5316/sys/GraphicsScreen.cpp0000644000176700017670000004100311752473707016160 0ustar paulpaul/* GraphicsScreen.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/05/28 GPL * pb 2004/10/18 ReleaseDC * pb 2007/08/01 reintroduced yIsZeroAtTheTop * sdk 2008/03/24 cairo * sdk 2008/05/09 cairo * pb 2009/07/24 quartz * fb 2010/02/23 cairo & clipping on updateWs() * pb 2010/05/13 support XOR mode * pb 2010/07/13 split erasure of recording off from Graphics_clearWs * pb 2011/03/17 C++ */ #include "GraphicsP.h" #include "Printer.h" #if win //#include "winport_on.h" #include //#include "winport_off.h" //using namespace Gdiplus; static bool _GraphicsWindows_tryToInitializeGdiPlus (void) { Gdiplus::GdiplusStartupInput gdiplusStartupInput; ULONG_PTR gdiplusToken; GdiplusStartup (& gdiplusToken, & gdiplusStartupInput, NULL); return true; } #elif mac #include "macport_on.h" static RGBColor theBlackColour = { 0, 0, 0 }; static bool _GraphicsMacintosh_tryToInitializeQuartz (void) { return _GraphicsMac_tryToInitializeAtsuiFonts (); } #endif Thing_implement (GraphicsScreen, Graphics, 0); void structGraphicsScreen :: v_destroy () { #if cairo if (d_gdkGraphicsContext != NULL) { g_object_unref (d_gdkGraphicsContext); d_gdkGraphicsContext = NULL; } if (d_cairoGraphicsContext != NULL) { cairo_destroy (d_cairoGraphicsContext); d_cairoGraphicsContext = NULL; } #elif win if (d_gdiGraphicsContext != NULL) { SelectPen (d_gdiGraphicsContext, GetStockPen (BLACK_PEN)); SelectBrush (d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); d_gdiGraphicsContext = NULL; } if (d_winPen != NULL) { DeleteObject (d_winPen); d_winPen = NULL; } if (d_winBrush != NULL) { DeleteObject (d_winBrush); d_winBrush = NULL; } /* * No ReleaseDC here, because we have not created it ourselves, * not even with GetDC. */ #elif mac if (d_macPort == NULL) { CGContextEndPage (d_macGraphicsContext); CGContextRelease (d_macGraphicsContext); } #endif GraphicsScreen_Parent :: v_destroy (); } void structGraphicsScreen :: v_flushWs () { #if cairo // Ik weet niet of dit is wat het zou moeten zijn ;) // gdk_window_process_updates (my window, TRUE); gdk_flush (); // TODO: een aanroep die de eventuele grafische buffer ledigt, // zodat de gebruiker de grafica ziet ook al blijft Praat in hetzelfde event zitten #elif win /*GdiFlush ();*/ #elif mac if (d_drawingArea) GuiWindow_drain (d_drawingArea); #endif } void Graphics_flushWs (Graphics me) { my v_flushWs (); } void structGraphicsScreen :: v_clearWs () { #if cairo GdkRectangle rect; if (this -> d_x1DC < this -> d_x2DC) { rect.x = this -> d_x1DC; rect.width = this -> d_x2DC - this -> d_x1DC; } else { rect.x = this -> d_x2DC; rect.width = this -> d_x1DC - this -> d_x2DC; } if (this -> d_y1DC < this -> d_y2DC) { rect.y = this -> d_y1DC; rect.height = this -> d_y2DC - this -> d_y1DC; } else { rect.y = this -> d_y2DC; rect.height = this -> d_y1DC - this -> d_y2DC; } if (d_cairoGraphicsContext == NULL) { //Melder_casual("Clear and null"); //gdk_window_clear (this -> window); //gdk_window_invalidate_rect (this -> window, & rect, true); // BUG: it seems weird that this is necessary. } else { //Melder_casual("Clear and not null"); cairo_set_source_rgb (d_cairoGraphicsContext, 1.0, 1.0, 1.0); cairo_rectangle (d_cairoGraphicsContext, rect.x, rect.y, rect.width, rect.height); cairo_fill (d_cairoGraphicsContext); cairo_set_source_rgb (d_cairoGraphicsContext, 0.0, 0.0, 0.0); } #elif win RECT rect; rect. left = rect. top = 0; rect. right = d_x2DC - d_x1DC; rect. bottom = d_y2DC - d_y1DC; FillRect (d_gdiGraphicsContext, & rect, GetStockBrush (WHITE_BRUSH)); /*if (d_winWindow) SendMessage (d_winWindow, WM_ERASEBKGND, (WPARAM) d_gdiGraphicsContext, 0);*/ #elif mac QDBeginCGContext (d_macPort, & d_macGraphicsContext); CGContextSetAlpha (d_macGraphicsContext, 1.0); CGContextSetBlendMode (d_macGraphicsContext, kCGBlendModeNormal); //CGContextSetAllowsAntialiasing (my macGraphicsContext, false); int shellHeight = GuiMac_clipOn_graphicsContext (d_drawingArea, d_macGraphicsContext); CGContextSetRGBFillColor (d_macGraphicsContext, 1.0, 1.0, 1.0, 1.0); CGContextFillRect (d_macGraphicsContext, CGRectMake (this -> d_x1DC, shellHeight - this -> d_y1DC, this -> d_x2DC - this -> d_x1DC, this -> d_y1DC - this -> d_y2DC)); QDEndCGContext (d_macPort, & d_macGraphicsContext); #endif } void Graphics_clearWs (Graphics me) { my v_clearWs (); } void structGraphicsScreen :: v_updateWs () { /* * A function that invalidates the graphics. * This function is typically called by the owner of the drawing area * whenever the data to be displayed in the drawing area has changed; * the idea is to generate an expose event to which the drawing area will * respond by redrawing its contents from the (changed) data. */ #if gtk //GdkWindow *window = gtk_widget_get_parent_window (GTK_WIDGET (my drawingArea)); GdkRectangle rect; if (this -> d_x1DC < this -> d_x2DC) { rect.x = this -> d_x1DC; rect.width = this -> d_x2DC - this -> d_x1DC; } else { rect.x = this -> d_x2DC; rect.width = this -> d_x1DC - this -> d_x2DC; } if (this -> d_y1DC < this -> d_y2DC) { rect.y = this -> d_y1DC; rect.height = this -> d_y2DC - this -> d_y1DC; } else { rect.y = this -> d_y2DC; rect.height = this -> d_y1DC - this -> d_y2DC; } if (d_cairoGraphicsContext && d_drawingArea) { // update clipping rectangle to new graphics size cairo_reset_clip (d_cairoGraphicsContext); cairo_rectangle (d_cairoGraphicsContext, rect.x, rect.y, rect.width, rect.height); cairo_clip (d_cairoGraphicsContext); } gdk_window_clear (d_window); gdk_window_invalidate_rect (d_window, & rect, true); //gdk_window_process_updates (d_window, true); #elif win //clear (this); // lll if (d_winWindow) InvalidateRect (d_winWindow, NULL, TRUE); #elif mac Rect r; if (d_drawingArea) GuiMac_clipOn (d_drawingArea); // to prevent invalidating invisible parts of the canvas SetRect (& r, this -> d_x1DC, this -> d_y1DC, this -> d_x2DC, this -> d_y2DC); SetPort (d_macPort); /*EraseRect (& r);*/ InvalWindowRect (GetWindowFromPort ((CGrafPtr) d_macPort), & r); if (d_drawingArea) GuiMac_clipOff (); #endif } void Graphics_updateWs (Graphics me) { if (me) my v_updateWs (); } static int GraphicsScreen_init (GraphicsScreen me, void *voidDisplay, void *voidWindow, int resolution) { /* Fill in new members. */ #if cairo my d_display = (GdkDisplay *) gdk_display_get_default (); _GraphicsScreen_text_init (me); my resolution = 100; my d_window = GDK_DRAWABLE (GTK_WIDGET (voidDisplay) -> window); my d_gdkGraphicsContext = gdk_gc_new (my d_window); my d_cairoGraphicsContext = gdk_cairo_create (my d_window); #elif win if (my printer) { my d_gdiGraphicsContext = (HDC) voidWindow; } else if (voidDisplay) { my d_gdiGraphicsContext = (HDC) voidDisplay; my metafile = TRUE; } else { my d_winWindow = (HWND) voidWindow; my d_gdiGraphicsContext = GetDC (my d_winWindow); // window must have a constant display context; see XtInitialize () } Melder_assert (my d_gdiGraphicsContext != NULL); my resolution = resolution; SetBkMode (my d_gdiGraphicsContext, TRANSPARENT); // not the default! /* * Create pens and brushes. */ my d_winPen = CreatePen (PS_SOLID, 0, RGB (0, 0, 0)); my d_winBrush = CreateSolidBrush (RGB (0, 0, 0)); SelectBrush (my d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); SetTextAlign (my d_gdiGraphicsContext, TA_LEFT | TA_BASELINE | TA_NOUPDATECP); // baseline is not the default! _GraphicsScreen_text_init (me); #elif mac (void) voidDisplay; my d_macPort = (GrafPtr) voidWindow; my d_macColour = theBlackColour; my resolution = resolution; my d_depth = my resolution > 150 ? 1 : 8; /* BUG: replace by true depth (1=black/white) */ (void) my d_macGraphicsContext; // will be retreived from QuickDraw with every drawing command! _GraphicsScreen_text_init (me); #endif return 1; } Graphics Graphics_create_screen (void *display, void *window, int resolution) { GraphicsScreen me = Thing_new (GraphicsScreen); my screen = true; my yIsZeroAtTheTop = true; Graphics_init (me); Graphics_setWsViewport ((Graphics) me, 0, 100, 0, 100); #if mac GraphicsScreen_init (me, display, GetWindowPort ((WindowRef) window), resolution); #else GraphicsScreen_init (me, display, window, resolution); #endif return (Graphics) me; } Graphics Graphics_create_screenPrinter (void *display, void *window) { GraphicsScreen me = Thing_new (GraphicsScreen); my screen = true; my yIsZeroAtTheTop = true; my printer = true; #ifdef macintosh _GraphicsMacintosh_tryToInitializeQuartz (); #endif Graphics_init (me); my paperWidth = (double) thePrinter. paperWidth / thePrinter. resolution; my paperHeight = (double) thePrinter. paperHeight / thePrinter. resolution; my d_x1DC = my d_x1DCmin = thePrinter. resolution / 2; my d_x2DC = my d_x2DCmax = (my paperWidth - 0.5) * thePrinter. resolution; my d_y1DC = my d_y1DCmin = thePrinter. resolution / 2; my d_y2DC = my d_y2DCmax = (my paperHeight - 0.5) * thePrinter. resolution; #if win /* * Map page coordinates to paper coordinates. */ my d_x1DC -= GetDeviceCaps ((HDC) window, PHYSICALOFFSETX); my d_x2DC -= GetDeviceCaps ((HDC) window, PHYSICALOFFSETX); my d_y1DC -= GetDeviceCaps ((HDC) window, PHYSICALOFFSETY); my d_y2DC -= GetDeviceCaps ((HDC) window, PHYSICALOFFSETY); #endif Graphics_setWsWindow ((Graphics) me, 0, my paperWidth - 1.0, 13.0 - my paperHeight, 12.0); GraphicsScreen_init (me, display, window, thePrinter. resolution); return (Graphics) me; } #if mac /* Drawing areas support resize callbacks. * However, Mac drawing areas also support move callbacks. * This is the only way for a graphics driver to get notified of a move, * which would bring about a change in device coordinates. * On Xwin and Win, we are not interested in moves, because we draw in widget coordinates. */ static void cb_move (GUI_ARGS) { iam (GraphicsScreen); Dimension width, height; XtVaGetValues (w, XmNwidth, & width, XmNheight, & height, NULL); /* The four values returned are probably equal to the previous ones. * However, the following call forces a new computation of the device coordinates * by widgetToWindowCoordinates (). */ Graphics_setWsViewport ((Graphics) me, 0 /* Left x value in widget coordinates */, width, 0, height); Graphics_updateWs ((Graphics) me); } #endif Graphics Graphics_create_xmdrawingarea (void *w) { /* w = XmDrawingArea widget */ GraphicsScreen me = Thing_new (GraphicsScreen); #if gtk GtkRequisition realsize; #elif motif Dimension width, height; #endif my d_drawingArea = static_cast (w); /* Now !!!!!!!!!! */ my screen = true; my yIsZeroAtTheTop = true; #if win my d_useGdiplus = _GraphicsWindows_tryToInitializeGdiPlus (); #elif mac _GraphicsMacintosh_tryToInitializeQuartz (); #endif Graphics_init (me); therror #ifdef macintosh GraphicsScreen_init (me, XtDisplay (my d_drawingArea), GetWindowPort ((WindowRef) XtWindow (my d_drawingArea)), Gui_getResolution (my d_drawingArea)); #else #if gtk GraphicsScreen_init (me, GTK_WIDGET (my d_drawingArea), GTK_WIDGET (my d_drawingArea), Gui_getResolution (my d_drawingArea)); #elif motif GraphicsScreen_init (me, XtDisplay (my d_drawingArea), XtWindow (my d_drawingArea), Gui_getResolution (my d_drawingArea)); #endif #endif #if gtk // fb: is really the request meant or rather the actual size, aka allocation? gtk_widget_size_request (GTK_WIDGET (my d_drawingArea), & realsize); // HIER WAS IK // g_debug("--> %d %d", realsize.width, realsize.height); Graphics_setWsViewport ((Graphics) me, 0, realsize.width, 0, realsize.height); #elif motif XtVaGetValues (my d_drawingArea, XmNwidth, & width, XmNheight, & height, NULL); Graphics_setWsViewport ((Graphics) me, 0, width, 0, height); #endif #ifdef macintosh XtAddCallback (my d_drawingArea, XmNmoveCallback, cb_move, (XtPointer) me); #endif return (Graphics) me; } Graphics Graphics_create_pdffile (MelderFile file, int resolution, double x1inches, double x2inches, double y1inches, double y2inches) { GraphicsScreen me = Thing_new (GraphicsScreen); my screen = true; my yIsZeroAtTheTop = true; #ifdef macintosh _GraphicsMacintosh_tryToInitializeQuartz (); #endif Graphics_init (me); therror my resolution = resolution; #ifdef macintosh CFURLRef url = CFURLCreateWithFileSystemPath (NULL, (CFStringRef) Melder_peekWcsToCfstring (file -> path), kCFURLPOSIXPathStyle, false); CGRect rect = CGRectMake (0, 0, (x2inches - x1inches) * 72, (y2inches - y1inches) * 72); // don't tire PDF viewers with funny origins CFStringRef key = (CFStringRef) Melder_peekWcsToCfstring (L"Creator"); CFStringRef value = (CFStringRef) Melder_peekWcsToCfstring (L"Praat"); CFIndex numberOfValues = 1; CFDictionaryRef dictionary = CFDictionaryCreate (NULL, (const void **) & key, (const void **) & value, numberOfValues, & kCFTypeDictionaryKeyCallBacks, & kCFTypeDictionaryValueCallBacks); my d_macGraphicsContext = CGPDFContextCreateWithURL (url, & rect, dictionary); CFRelease (url); CFRelease (dictionary); my d_x1DC = my d_x1DCmin = 0; my d_x2DC = my d_x2DCmax = 7.5 * resolution; my d_y1DC = my d_y1DCmin = 0; my d_y2DC = my d_y2DCmax = 11.0 * resolution; Graphics_setWsWindow ((Graphics) me, 0, 7.5, 1.0, 12.0); CGContextBeginPage (my d_macGraphicsContext, & rect); CGContextScaleCTM (my d_macGraphicsContext, 72.0/resolution, 72.0/resolution); CGContextTranslateCTM (my d_macGraphicsContext, - x1inches * resolution, (12.0 - y1inches) * resolution); CGContextScaleCTM (my d_macGraphicsContext, 1.0, -1.0); #endif return (Graphics) me; } Graphics Graphics_create_pdf (void *context, int resolution, double x1inches, double x2inches, double y1inches, double y2inches) { GraphicsScreen me = Thing_new (GraphicsScreen); my screen = true; my yIsZeroAtTheTop = true; #ifdef macintosh _GraphicsMacintosh_tryToInitializeQuartz (); #endif Graphics_init (me); my resolution = resolution; #ifdef macintosh my d_macGraphicsContext = static_cast (context); CGRect rect = CGRectMake (0, 0, (x2inches - x1inches) * 72, (y2inches - y1inches) * 72); // don't tire PDF viewers with funny origins my d_x1DC = my d_x1DCmin = 0; my d_x2DC = my d_x2DCmax = 7.5 * resolution; my d_y1DC = my d_y1DCmin = 0; my d_y2DC = my d_y2DCmax = 11.0 * resolution; Graphics_setWsWindow ((Graphics) me, 0, 7.5, 1.0, 12.0); CGContextBeginPage (my d_macGraphicsContext, & rect); CGContextScaleCTM (my d_macGraphicsContext, 72.0/resolution, 72.0/resolution); CGContextTranslateCTM (my d_macGraphicsContext, - x1inches * resolution, (12.0 - y1inches) * resolution); CGContextScaleCTM (my d_macGraphicsContext, 1.0, -1.0); #endif return (Graphics) me; } #if cairo void *Graphics_x_getCR (Graphics me) { return ((GraphicsScreen) me) -> d_cairoGraphicsContext; } void Graphics_x_setCR (Graphics me, void *cairoGraphicsContext) { ((GraphicsScreen) me) -> d_cairoGraphicsContext = (cairo_t *) cairoGraphicsContext; } #endif #if mac void GraphicsQuartz_initDraw (GraphicsScreen me) { if (my d_macPort) { QDBeginCGContext (my d_macPort, & my d_macGraphicsContext); //CGContextSetAlpha (my macGraphicsContext, 1.0); //CGContextSetAllowsAntialiasing (my macGraphicsContext, false); if (my d_drawingArea != NULL) { int shellHeight = GuiMac_clipOn_graphicsContext (my d_drawingArea, my d_macGraphicsContext); CGContextTranslateCTM (my d_macGraphicsContext, 0, shellHeight); } else if (my printer) { CGContextTranslateCTM (my d_macGraphicsContext, 0, my d_y2DC - my d_y1DC); } CGContextScaleCTM (my d_macGraphicsContext, 1.0, -1.0); } } void GraphicsQuartz_exitDraw (GraphicsScreen me) { if (my d_macPort) { CGContextSynchronize (my d_macGraphicsContext); QDEndCGContext (my d_macPort, & my d_macGraphicsContext); } } #endif /* End of file GraphicsScreen.cpp */ sources_5316/sys/enums_getText.h0000644000176700017670000000226611161323237015552 0ustar paulpaul/* enums_getText.h * * Copyright (C) 2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/04 */ /* See enums.h */ /* For C files. */ #undef enums_begin #undef enums_add #undef enums_alt #undef enums_end #define enums_begin(type,minimum) const wchar_t * type##_getText (int testValue) { return #define enums_add(type,value,which,text) testValue == type##_##which ? text : #define enums_alt(type,which,text) #define enums_end(type,maximum,def) type##_getText (type##_DEFAULT); } /* End of file enums_getText.h */ sources_5316/sys/Simple.cpp0000644000176700017670000000374511724661150014512 0ustar paulpaul/* Simple.cpp * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Simple.h" #include "oo_DESTROY.h" #include "Simple_def.h" #include "oo_COPY.h" #include "Simple_def.h" #include "oo_EQUAL.h" #include "Simple_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Simple_def.h" #include "oo_WRITE_TEXT.h" #include "Simple_def.h" #include "oo_WRITE_BINARY.h" #include "Simple_def.h" #include "oo_READ_TEXT.h" #include "Simple_def.h" #include "oo_READ_BINARY.h" #include "Simple_def.h" #include "oo_DESCRIPTION.h" #include "Simple_def.h" Thing_implement (SimpleInt, Data, 0); SimpleInt SimpleInt_create (int number) { autoSimpleInt me = Thing_new (SimpleInt); my number = number; return me.transfer(); } Thing_implement (SimpleLong, Data, 0); SimpleLong SimpleLong_create (long number) { autoSimpleLong me = Thing_new (SimpleLong); my number = number; return me.transfer(); } Thing_implement (SimpleDouble, Data, 0); SimpleDouble SimpleDouble_create (double number) { autoSimpleDouble me = Thing_new (SimpleDouble); my number = number; return me.transfer(); } Thing_implement (SimpleString, Data, 0); SimpleString SimpleString_create (const wchar_t *string) { autoSimpleString me = Thing_new (SimpleString); my string = Melder_wcsdup (string); return me.transfer(); } /* End of file Simple.cpp */ sources_5316/sys/sendpraat.h0000644000176700017670000000037211533433523014677 0ustar paulpaul/* sendpraat.h */ /* Paul Boersma, September 27, 2000 */ #ifdef __cplusplus extern "C" { #endif char *sendpraat (void *display, const char *programName, long timeOut, const char *text); #ifdef __cplusplus } #endif /* End of file sendpraat.h */ sources_5316/sys/melder_readtext.cpp0000644000176700017670000002327111646364737016443 0ustar paulpaul/* melder_readtext.cpp * * Copyright (C) 2008-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2008/11/04 split off from melder_strings.c and melder_encodings.c * pb 2010/03/09 support Unicode values above 0xFFFF * pb 2011/04/05 C++ * pb 2011/07/03 C++ */ #include "melder.h" #include "UnicodeData.h" #include "abcio.h" #define my me -> wchar MelderReadText_getChar (MelderReadText me) { if (my stringW != NULL) { if (* my readPointerW == '\0') return 0; return * my readPointerW ++; } else { if (* my readPointer8 == '\0') return 0; if (my input8Encoding == kMelder_textInputEncoding_UTF8) { unsigned long kar = * (unsigned char *) my readPointer8 ++; if (kar <= 0x7F) { return kar; } else if (kar <= 0xDF) { unsigned long kar2 = * (unsigned char *) my readPointer8 ++; return ((kar & 0x1F) << 6) | (kar2 & 0x3F); } else if (kar <= 0xEF) { unsigned long kar2 = * (unsigned char *) my readPointer8 ++; unsigned long kar3 = * (unsigned char *) my readPointer8 ++; return ((kar & 0x0F) << 12) | ((kar2 & 0x3F) << 6) | (kar3 & 0x3F); } else if (kar <= 0xF4) { unsigned long kar2 = * (unsigned char *) my readPointer8 ++; unsigned long kar3 = * (unsigned char *) my readPointer8 ++; unsigned long kar4 = * (unsigned char *) my readPointer8 ++; return ((kar & 0x07) << 18) | ((kar2 & 0x3F) << 12) | ((kar3 & 0x3F) << 6) | (kar4 & 0x3F); // BUG: should be UTF-16 on Windows } } else if (my input8Encoding == kMelder_textInputEncoding_MACROMAN) { return Melder_decodeMacRoman [* (unsigned char *) my readPointer8 ++]; } else if (my input8Encoding == kMelder_textInputEncoding_WINDOWS_LATIN1) { return Melder_decodeWindowsLatin1 [* (unsigned char *) my readPointer8 ++]; } return * (unsigned char *) my readPointer8 ++; } } wchar * MelderReadText_readLine (MelderReadText me) { if (my stringW != NULL) { Melder_assert (my readPointerW != NULL); Melder_assert (my readPointer8 == NULL); if (*my readPointerW == '\0') { // tried to read past end of file return NULL; } wchar *result = my readPointerW; wchar *newline = wcschr (result, '\n'); if (newline != NULL) { *newline = '\0'; my readPointerW = newline + 1; } else { my readPointerW += wcslen (result); } return result; } else { Melder_assert (my string8 != NULL); Melder_assert (my readPointerW == NULL); Melder_assert (my readPointer8 != NULL); if (*my readPointer8 == '\0') { // tried to read past end of file return NULL; } char *result8 = my readPointer8; char *newline = strchr (result8, '\n'); if (newline != NULL) { *newline = '\0'; my readPointer8 = newline + 1; } else { my readPointer8 += strlen (result8); } static wchar *textW = NULL; static size_t size = 0; size_t sizeNeeded = strlen (result8) + 1; if (sizeNeeded > size) { Melder_free (textW); textW = Melder_malloc_f (wchar, sizeNeeded + 100); size = sizeNeeded + 100; } Melder_8bitToWcs_inline (result8, textW, my input8Encoding); return textW; } } long MelderReadText_getNumberOfLines (MelderReadText me) { long n = 0; if (my stringW != NULL) { wchar_t *p = & my stringW [0]; for (; *p != '\0'; p ++) if (*p == '\n') n ++; if (p - my stringW > 1 && p [-1] != '\n') n ++; } else { char *p = & my string8 [0]; for (; *p != '\0'; p ++) if (*p == '\n') n ++; if (p - my string8 > 1 && p [-1] != '\n') n ++; } return n; } const wchar_t * MelderReadText_getLineNumber (MelderReadText me) { long result = 1; if (my stringW != NULL) { wchar *p = my stringW; while (my readPointerW - p > 0) { if (*p == '\0' || *p == '\n') result ++; p ++; } } else { char *p = my string8; while (my readPointer8 - p > 0) { if (*p == '\0' || *p == '\n') result ++; p ++; } return Melder_integer (result); } return Melder_integer (result); } static wchar * _MelderFile_readText (MelderFile file, char **string8) { try { int type = 0; // 8-bit autostring text; autofile f = Melder_fopen (file, "rb"); fseek (f, 0, SEEK_END); unsigned long length = ftell (f); rewind (f); if (length >= 2) { int firstByte = fgetc (f), secondByte = fgetc (f); if (firstByte == 0xFE && secondByte == 0xFF) { type = 1; // big-endian 16-bit } else if (firstByte == 0xFF && secondByte == 0xFE) { type = 2; // little-endian 16-bit } } if (type == 0) { rewind (f); // length and type already set correctly. autostring8 text8bit = Melder_malloc (char, length + 1); fread (text8bit.peek(), sizeof (char), length, f); text8bit [length] = '\0'; /* * Count and repair null bytes. */ if (length > 0) { long numberOfNullBytes = 0; for (char *p = & text8bit [length - 1]; (long) (p - text8bit.peek()) >= 0; p --) { if (*p == '\0') { numberOfNullBytes += 1; /* * Shift. */ for (char *q = p; (unsigned long) (q - text8bit.peek()) < length; q ++) { *q = q [1]; } } } if (numberOfNullBytes > 0) { Melder_warning ("Ignored ", numberOfNullBytes, " null bytes in text file ", file, "."); } } if (string8 != NULL) { *string8 = text8bit.transfer(); (void) Melder_killReturns_inline (*string8); return NULL; // OK } else { text.reset (Melder_8bitToWcs (text8bit.peek(), 0)); } } else { length = length / 2 - 1; // Byte Order Mark subtracted. Length = number of UTF-16 codes text.reset (Melder_malloc (wchar, length + 1)); if (type == 1) { for (unsigned long i = 0; i < length; i ++) { unsigned short kar = bingetu2 (f); if (sizeof (wchar_t) == 2) { // wchar is UTF-16? text [i] = kar; } else { // wchar_t is UTF-32. unsigned long kar1 = kar; if (kar1 < 0xD800) { text [i] = kar1; } else if (kar1 < 0xDC00) { length --; unsigned long kar2 = bingetu2 (f); if (kar2 >= 0xDC00 && kar2 <= 0xDFFF) { text [i] = 0x10000 + ((kar1 & 0x3FF) << 10) + (kar2 & 0x3FF); } else { text [i] = UNICODE_REPLACEMENT_CHARACTER; } } else if (kar1 < 0xE000) { text [i] = UNICODE_REPLACEMENT_CHARACTER; } else if (kar1 <= 0xFFFF) { text [i] = kar1; } else { Melder_fatal ("MelderFile_readText: unsigned short greater than 0xFFFF: should not occur."); } } } } else { for (unsigned long i = 0; i < length; i ++) { unsigned short kar = bingetu2LE (f); if (sizeof (wchar) == 2) { // wchar is UTF-16? text [i] = kar; } else { // wchar is UTF-32 unsigned long kar1 = kar; if (kar1 < 0xD800) { text [i] = kar1; } else if (kar1 < 0xDC00) { length --; unsigned long kar2 = bingetu2LE (f); if (kar2 >= 0xDC00 && kar2 <= 0xDFFF) { text [i] = 0x10000 + ((kar1 & 0x3FF) << 10) + (kar2 & 0x3FF); } else { text [i] = UNICODE_REPLACEMENT_CHARACTER; } } else if (kar1 < 0xE000) { text [i] = UNICODE_REPLACEMENT_CHARACTER; } else if (kar1 <= 0xFFFF) { text [i] = kar1; } else { Melder_fatal ("MelderFile_readText: unsigned short greater than 0xFFFF: should not occur."); } } } } text [length] = '\0'; (void) Melder_killReturns_inlineW (text.peek()); } f.close (file); return text.transfer(); } catch (MelderError) { Melder_throw ("Error reading file ", file, "."); } } wchar_t * MelderFile_readText (MelderFile file) { return _MelderFile_readText (file, NULL); } MelderReadText MelderReadText_createFromFile (MelderFile file) { autoMelderReadText me = Melder_calloc (struct structMelderReadText, 1); my stringW = _MelderFile_readText (file, & my string8); if (my stringW != NULL) { my readPointerW = & my stringW [0]; } else { Melder_assert (my string8 != NULL); my readPointer8 = & my string8 [0]; my input8Encoding = Melder_getInputEncoding (); if (my input8Encoding == kMelder_textInputEncoding_UTF8 || my input8Encoding == kMelder_textInputEncoding_UTF8_THEN_ISO_LATIN1 || my input8Encoding == kMelder_textInputEncoding_UTF8_THEN_WINDOWS_LATIN1 || my input8Encoding == kMelder_textInputEncoding_UTF8_THEN_MACROMAN) { if (Melder_strIsValidUtf8 (my string8)) { my input8Encoding = kMelder_textInputEncoding_UTF8; } else if (my input8Encoding == kMelder_textInputEncoding_UTF8) { Melder_throw ("Text is not valid UTF-8; please try a different text input encoding."); } else if (my input8Encoding == kMelder_textInputEncoding_UTF8_THEN_ISO_LATIN1) { my input8Encoding = kMelder_textInputEncoding_ISO_LATIN1; } else if (my input8Encoding == kMelder_textInputEncoding_UTF8_THEN_WINDOWS_LATIN1) { my input8Encoding = kMelder_textInputEncoding_WINDOWS_LATIN1; } else if (my input8Encoding == kMelder_textInputEncoding_UTF8_THEN_MACROMAN) { my input8Encoding = kMelder_textInputEncoding_MACROMAN; } } } return me.transfer(); } MelderReadText MelderReadText_createFromString (const wchar_t *string); void MelderReadText_delete (MelderReadText me) { if (me == NULL) return; Melder_free (my stringW); Melder_free (my string8); Melder_free (me); } /* End of file melder_readtext.cpp */ sources_5316/sys/melder.h0000644000176700017670000016374311757242277014216 0ustar paulpaul#ifndef _melder_h_ #define _melder_h_ /* melder.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include #include #define strequ ! strcmp #define strnequ ! strncmp #define wcsequ ! wcscmp #define wcsnequ ! wcsncmp #define Melder_strequ ! Melder_strcmp #define Melder_strnequ ! Melder_strncmp #define Melder_wcsequ ! Melder_wcscmp #define Melder_wcsnequ ! Melder_wcsncmp #include #include #include #ifdef __MINGW32__ #define swprintf _snwprintf #endif #include #include typedef wchar_t wchar; typedef int8_t int8; typedef uint8_t uint8; typedef int16_t int16; typedef uint16_t uint16; typedef int32_t int32; typedef uint32_t uint32; typedef int64_t int64; typedef uint64_t uint64; bool Melder_wcsequ_firstCharacterCaseInsensitive (const wchar *string1, const wchar *string2); #include "enums.h" #include "melder_enums.h" #ifndef TRUE #define TRUE 1 #endif #ifndef FALSE #define FALSE 0 #endif #ifndef NULL #define NULL ((void *) 0) #endif /********** NUMBER TO STRING CONVERSION **********/ /* The following routines return a static string, chosen from a circularly used set of 11 buffers. You can call at most 11 of them in one Melder_casual call, for instance. */ const wchar * Melder_integer (long value); const wchar * Melder_bigInteger (double value); const wchar * Melder_boolean (bool value); // "yes" or "no" const wchar * Melder_double (double value); // "--undefined--" or something in the "%.15g", "%.16g", or "%.17g" formats const wchar * Melder_single (double value); // "--undefined--" or something in the "%.8g" format const wchar * Melder_half (double value); // "--undefined--" or something in the "%.4g" format const wchar * Melder_fixed (double value, int precision); // "--undefined--" or something in the "%.*f" format const wchar * Melder_fixedExponent (double value, int exponent, int precision); /* if exponent is -2 and precision is 2: 67E-2, 0.00024E-2 */ const wchar * Melder_percent (double value, int precision); /* "--undefined--" or, if precision is 3: "0" or "34.400%" or "0.014%" or "0.001%" or "0.0000007%" */ const wchar * Melder_float (const wchar *number); /* turns 1e+4 into 10^^4, or -1.23456e-78 into -1.23456\.c10^^-78 */ const wchar * Melder_naturalLogarithm (double lnNumber); // turns -10000 into "1.135483865315339e-4343" /********** STRING TO NUMBER CONVERSION **********/ int Melder_isStringNumeric_nothrow (const wchar *string); double Melder_atof (const wchar *string); /* * "3.14e-3" -> 3.14e-3 * "15.6%" -> 0.156 * "fghfghj" -> NUMundefined */ /********** CONSOLE **********/ void Melder_writeToConsole (const wchar *message, bool useStderr); /********** MEMORY ALLOCATION ROUTINES **********/ /* These routines call malloc, free, realloc, and calloc. */ /* If out of memory, the non-f versions throw an error message (like "Out of memory"); */ /* the f versions open up a rainy day fund or crash Praat. */ /* These routines also maintain a count of the total number of blocks allocated. */ void Melder_alloc_init (void); // to be called around program start-up void * _Melder_malloc (unsigned long size); #define Melder_malloc(type,numberOfElements) (type *) _Melder_malloc ((numberOfElements) * sizeof (type)) void * _Melder_malloc_f (unsigned long size); #define Melder_malloc_f(type,numberOfElements) (type *) _Melder_malloc_f ((numberOfElements) * sizeof (type)) void * Melder_realloc (void *pointer, long size); void * Melder_realloc_f (void *pointer, long size); void * _Melder_calloc (long numberOfElements, long elementSize); #define Melder_calloc(type,numberOfElements) (type *) _Melder_calloc (numberOfElements, sizeof (type)) void * _Melder_calloc_f (long numberOfElements, long elementSize); #define Melder_calloc_f(type,numberOfElements) (type *) _Melder_calloc_f (numberOfElements, sizeof (type)) char * Melder_strdup (const char *string); char * Melder_strdup_f (const char *string); wchar * Melder_wcsdup (const wchar *string); wchar * Melder_wcsdup_f (const wchar *string); int Melder_strcmp (const char *string1, const char *string2); // regards null string as empty string int Melder_wcscmp (const wchar *string1, const wchar *string2); // regards null string as empty string int Melder_strncmp (const char *string1, const char *string2, unsigned long n); int Melder_wcsncmp (const wchar *string1, const wchar *string2, unsigned long n); wchar * Melder_wcstok (wchar *string, const wchar *delimiter, wchar **last); // circumvents platforms where wcstok has only two arguments wchar * Melder_wcsdecompose (const wchar *string); wchar * Melder_wcsprecompose (const wchar *string); wchar * Melder_wcsExpandBackslashSequences (const wchar *string); wchar * Melder_wcsReduceBackslashSequences (const wchar *string); void Melder_wcsReduceBackslashSequences_inline (const wchar *string); /* * Text encodings. */ void Melder_textEncoding_prefs (void); void Melder_setInputEncoding (enum kMelder_textInputEncoding encoding); int Melder_getInputEncoding (void); void Melder_setOutputEncoding (enum kMelder_textOutputEncoding encoding); int Melder_getOutputEncoding (void); /* * Some other encodings. Although not used in the above set/get functions, * these constants should stay separate from the above encoding constants * because they occur in the same fields of struct MelderFile. */ #define kMelder_textInputEncoding_FLAC 0x464C4143 #define kMelder_textOutputEncoding_ASCII 0x41534349 #define kMelder_textOutputEncoding_ISO_LATIN1 0x4C415401 #define kMelder_textOutputEncoding_FLAC 0x464C4143 typedef uint16 MelderUtf16; typedef uint32 MelderUtf32; bool Melder_isValidAscii (const wchar *string); bool Melder_strIsValidUtf8 (const char *string); bool Melder_isEncodable (const wchar *string, int outputEncoding); extern wchar Melder_decodeMacRoman [256]; extern wchar Melder_decodeWindowsLatin1 [256]; long Melder_killReturns_inlineW (wchar *text); unsigned long wcslen_utf8 (const wchar *wcs, bool expandNewlines); unsigned long wcslen_utf16 (const wchar *wcs, bool expandNewlines); unsigned long wcslen_utf32 (const wchar *wcs, bool expandNewlines); void Melder_8bitToWcs_inline (const char *string, wchar *wcs, int inputEncoding); // errors: Text is not valid UTF-8. wchar * Melder_8bitToWcs (const char *string, int inputEncoding); // errors: Out of memory; Text is not valid UTF-8. wchar * Melder_utf8ToWcs (const char *string); // errors: Out of memory; Text is not valid UTF-8. void Melder_wcsToUtf8_inline (const wchar *wcs, char *utf8); char * Melder_wcsToUtf8 (const wchar *string); // errors: Out of memory. void Melder_wcsTo8bitFileRepresentation_inline (const wchar *wcs, char *utf8); void Melder_8bitFileRepresentationToWcs_inline (const char *utf8, wchar *wcs); extern "C" wchar * Melder_peekUtf8ToWcs (const char *string); extern "C" char * Melder_peekWcsToUtf8 (const wchar *string); extern "C" const MelderUtf16 * Melder_peekWcsToUtf16 (const wchar *string); const void * Melder_peekWcsToCfstring (const wchar *string); void Melder_fwriteWcsAsUtf8 (const wchar *ptr, size_t n, FILE *f); /* * Some often used characters. */ #define L_LEFT_SINGLE_QUOTE L"\u2018" #define L_RIGHT_SINGLE_QUOTE L"\u2019" #define L_LEFT_DOUBLE_QUOTE L"\u201c" #define L_RIGHT_DOUBLE_QUOTE L"\u201d" #define L_LEFT_GUILLEMET L"\u00ab" #define L_RIGHT_GUILLEMET L"\u00bb" #define Melder_free(pointer) _Melder_free ((void **) & (pointer)) void _Melder_free (void **pointer); /* Preconditions: none (*pointer may be NULL). Postconditions: *pointer == NULL; */ double Melder_allocationCount (void); /* Returns the total number of successful calls to Melder_malloc, Melder_realloc (if 'ptr' is NULL), Melder_calloc, and Melder_strdup, since the start of the process. Mainly for debugging purposes. */ double Melder_deallocationCount (void); /* Returns the total number of successful calls to Melder_free, since the start of the process. Mainly for debugging purposes. */ double Melder_allocationSize (void); /* Returns the total number of bytes allocated in calls to Melder_malloc, Melder_realloc (if moved), Melder_calloc, and Melder_strdup, since the start of the process. Mainly for debugging purposes. */ double Melder_reallocationsInSituCount (void); double Melder_movingReallocationsCount (void); /********** FILES **********/ #if defined (_WIN32) #define Melder_DIRECTORY_SEPARATOR '\\' #else #define Melder_DIRECTORY_SEPARATOR '/' #endif struct FLAC__StreamDecoder; struct FLAC__StreamEncoder; #define kMelder_MAXPATH 1023 /* excluding the null byte */ struct structMelderFile { FILE *filePointer; wchar path [kMelder_MAXPATH+1]; bool openForReading, openForWriting, verbose, requiresCRLF; unsigned long outputEncoding; int indent; struct FLAC__StreamEncoder *flacEncoder; }; typedef struct structMelderFile *MelderFile; struct structMelderDir { wchar path [kMelder_MAXPATH+1]; }; typedef struct structMelderDir *MelderDir; #if defined (macintosh) void Melder_machToFile (void *void_fsref, MelderFile file); void Melder_machToDir (void *void_fsref, MelderDir dir); void Melder_fileToMach (MelderFile file, void *void_fsref); void Melder_dirToMach (MelderDir dir, void *void_fsref); #endif const wchar * MelderFile_name (MelderFile file); wchar * MelderDir_name (MelderDir dir); void Melder_pathToDir (const wchar *path, MelderDir dir); void Melder_pathToFile (const wchar *path, MelderFile file); void Melder_relativePathToFile (const wchar *path, MelderFile file); wchar * Melder_dirToPath (MelderDir dir); /* Returns a pointer internal to 'dir', like "/u/paul/praats" or "D:\Paul\Praats" */ wchar * Melder_fileToPath (MelderFile file); void MelderFile_copy (MelderFile file, MelderFile copy); void MelderDir_copy (MelderDir dir, MelderDir copy); bool MelderFile_equal (MelderFile file1, MelderFile file2); bool MelderDir_equal (MelderDir dir1, MelderDir dir2); void MelderFile_setToNull (MelderFile file); bool MelderFile_isNull (MelderFile file); void MelderDir_setToNull (MelderDir dir); bool MelderDir_isNull (MelderDir dir); void MelderDir_getFile (MelderDir parent, const wchar *fileName, MelderFile file); void MelderDir_relativePathToFile (MelderDir dir, const wchar *path, MelderFile file); void MelderFile_getParentDir (MelderFile file, MelderDir parent); void MelderDir_getParentDir (MelderDir file, MelderDir parent); bool MelderDir_isDesktop (MelderDir dir); void MelderDir_getSubdir (MelderDir parent, const wchar *subdirName, MelderDir subdir); void Melder_rememberShellDirectory (void); wchar * Melder_getShellDirectory (void); void Melder_getHomeDir (MelderDir homeDir); void Melder_getPrefDir (MelderDir prefDir); void Melder_getTempDir (MelderDir tempDir); bool MelderFile_exists (MelderFile file); bool MelderFile_readable (MelderFile file); long MelderFile_length (MelderFile file); void MelderFile_delete (MelderFile file); /* The following two should be combined with each other and with Windows extension setting: */ FILE * Melder_fopen (MelderFile file, const char *type); #if defined (macintosh) void MelderFile_setMacTypeAndCreator (MelderFile file, long fileType, long creator); unsigned long MelderFile_getMacType (MelderFile file); #else #define MelderFile_setMacTypeAndCreator(f,t,c) (void) 0 #endif void Melder_fclose (MelderFile file, FILE *stream); void Melder_files_cleanUp (void); /* So these will be the future replacements for the above, as soon as we rid of text files: */ MelderFile MelderFile_open (MelderFile file); MelderFile MelderFile_append (MelderFile file); MelderFile MelderFile_create (MelderFile file, const wchar *macType, const wchar *macCreator, const wchar *winExtension); void * MelderFile_read (MelderFile file, long nbytes); char * MelderFile_readLine (MelderFile file); void MelderFile_writeCharacter (MelderFile file, wchar kar); void MelderFile_write1 (MelderFile file, const wchar *s1); void MelderFile_write2 (MelderFile file, const wchar *s1, const wchar *s2); void MelderFile_write3 (MelderFile file, const wchar *s1, const wchar *s2, const wchar *s3); void MelderFile_write4 (MelderFile file, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); void MelderFile_write5 (MelderFile file, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); void MelderFile_write6 (MelderFile file, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); void MelderFile_write7 (MelderFile file, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); void MelderFile_write8 (MelderFile file, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); void MelderFile_write9 (MelderFile file, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); void MelderFile_rewind (MelderFile file); void MelderFile_seek (MelderFile file, long position, int direction); long MelderFile_tell (MelderFile file); void MelderFile_close (MelderFile file); void MelderFile_close_nothrow (MelderFile file); /* Read and write whole text files. */ wchar * MelderFile_readText (MelderFile file); void MelderFile_writeText (MelderFile file, const wchar *text); void MelderFile_appendText (MelderFile file, const wchar *text); void Melder_createDirectory (MelderDir parent, const wchar *subdirName, int mode); void Melder_getDefaultDir (MelderDir dir); void Melder_setDefaultDir (MelderDir dir); void MelderFile_setDefaultDir (MelderFile file); /* Use the following functions to pass unchanged text or file names to Melder_* functions. */ /* Backslashes are replaced by "\bs". */ /* The trick is that they return one of 11 cyclically used static strings, */ /* so you can use up to 11 strings in a single Melder_* call. */ wchar * Melder_peekExpandBackslashes (const wchar *message); const wchar * MelderFile_messageName (MelderFile file); // Calls Melder_peekExpandBackslashes (). /********** STRINGS **********/ /* These are routines for never having to check string boundaries again. */ typedef struct { unsigned long length; unsigned long bufferSize; wchar *string; // a growing buffer, never shrunk (can only be freed by MelderString_free) } MelderString; typedef struct { unsigned long length; unsigned long bufferSize; MelderUtf16 *string; // a growing buffer, never shrunk (can only be freed by MelderString16_free) } MelderString16; void MelderString_free (MelderString *me); // frees the "string" attribute only (and sets other attributes to zero) void MelderString16_free (MelderString16 *me); // frees the "string" attribute only (and sets other attributes to zero) void MelderString_empty (MelderString *me); // sets to empty string (buffer not freed) void MelderString16_empty (MelderString16 *me); // sets to empty string (buffer not freed) void MelderString_copy (MelderString *me, const wchar *source); void MelderString_ncopy (MelderString *me, const wchar *source, unsigned long n); void MelderString_append (MelderString *me, const wchar *s1); void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2); void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3); void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); void MelderString_append (MelderString *me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); void MelderString_appendCharacter (MelderString *me, wchar character); void MelderString16_appendCharacter (MelderString16 *me, wchar character); void MelderString_get (MelderString *me, wchar *destination); // performs no boundary checking double MelderString_allocationCount (void); double MelderString_deallocationCount (void); double MelderString_allocationSize (void); double MelderString_deallocationSize (void); struct structMelderReadText { wchar *stringW, *readPointerW; char *string8, *readPointer8; unsigned long input8Encoding; }; typedef struct structMelderReadText *MelderReadText; MelderReadText MelderReadText_createFromFile (MelderFile file); MelderReadText MelderReadText_createFromString (const wchar *string); wchar MelderReadText_getChar (MelderReadText text); wchar * MelderReadText_readLine (MelderReadText text); long MelderReadText_getNumberOfLines (MelderReadText me); const wchar * MelderReadText_getLineNumber (MelderReadText text); void MelderReadText_delete (MelderReadText text); const wchar * Melder_wcscat (const wchar *s1, const wchar *s2); const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3); const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); const wchar * Melder_wcscat (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); #define Melder_wcscat2 Melder_wcscat #define Melder_wcscat3 Melder_wcscat #define Melder_wcscat4 Melder_wcscat #define Melder_wcscat5 Melder_wcscat #define Melder_wcscat6 Melder_wcscat #define Melder_wcscat7 Melder_wcscat #define Melder_wcscat8 Melder_wcscat #define Melder_wcscat9 Melder_wcscat /********** NUMBER AND STRING COMPARISON **********/ int Melder_numberMatchesCriterion (double value, int which_kMelder_number, double criterion); int Melder_stringMatchesCriterion (const wchar *value, int which_kMelder_string, const wchar *criterion); /********** STRING PARSING **********/ /* These functions regard a string as a sequence of tokens, separated (and perhaps preceded and followed) by white space. The tokens cannot contain spaces themselves (there are no escapes). Typical use: for (token = Melder_firstToken (string); token != NULL; token = Melder_nextToken ()) { ... do something with the token ... } */ long Melder_countTokens (const wchar *string); wchar *Melder_firstToken (const wchar *string); wchar *Melder_nextToken (void); wchar ** Melder_getTokens (const wchar *string, long *n); void Melder_freeTokens (wchar ***tokens); long Melder_searchToken (const wchar *string, wchar **tokens, long n); /********** MESSAGING ROUTINES **********/ /* These functions are called like printf (). Default Melder does fprintf to stderr, except Melder_information, which does fprintf to stdout. These functions show generic, native, and mixed strings correctly, and perform quote conversion, if that flag is not off; see under "NON-ASCII CHARACTERS". The alphabet is Roman, so that symbols from the Symbol and Phonetic alphabets are not translated (by default, \mu is shown as \mu and \as as a). */ void Melder_casual (const char *format, ...); void Melder_casual1 (const wchar *s1); void Melder_casual2 (const wchar *s1, const wchar *s2); void Melder_casual3 (const wchar *s1, const wchar *s2, const wchar *s3); void Melder_casual4 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); void Melder_casual5 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); void Melder_casual6 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); void Melder_casual7 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); void Melder_casual8 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); void Melder_casual9 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); /* Function: Sends a message without user interference. Behaviour: Writes to stderr on Unix, otherwise to a special window. */ /* Give information to stdout (batch), or to an "Info" window (interactive), or to a diverted string. */ void MelderInfo_open (void); /* Clear the Info window in the background. */ void MelderInfo_write1 (const wchar *s1); /* Write a string to the Info window in the background. */ void MelderInfo_write2 (const wchar *s1, const wchar *s2); /* Write two strings to the Info window in the background. */ void MelderInfo_write3 (const wchar *s1, const wchar *s2, const wchar *s3); void MelderInfo_write4 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); void MelderInfo_write5 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); void MelderInfo_write6 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); void MelderInfo_write7 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); void MelderInfo_write8 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); void MelderInfo_write9 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); void MelderInfo_writeLine1 (const wchar *s1); /* Write a string to the Info window in the background; add a new-line. */ void MelderInfo_writeLine2 (const wchar *s1, const wchar *s2); void MelderInfo_writeLine3 (const wchar *s1, const wchar *s2, const wchar *s3); void MelderInfo_writeLine4 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); void MelderInfo_writeLine5 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); void MelderInfo_writeLine6 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); void MelderInfo_writeLine7 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); void MelderInfo_writeLine8 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); void MelderInfo_writeLine9 (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); void MelderInfo_close (void); /* Flush the background info to the Info window. */ void Melder_information (const wchar *s1); void Melder_information (const wchar *s1, const wchar *s2); void Melder_information (const wchar *s1, const wchar *s2, const wchar *s3); void Melder_information (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); void Melder_information (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); void Melder_information (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); void Melder_information (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); void Melder_information (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); void Melder_information (const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); void Melder_informationReal (double value, const wchar *units); /* %.17g or --undefined--; units may be NULL */ void Melder_divertInfo (MelderString *buffer); /* NULL = back to normal. */ class autoMelderDivertInfo { public: autoMelderDivertInfo (MelderString *buffer) { Melder_divertInfo (buffer); } ~autoMelderDivertInfo () { Melder_divertInfo (NULL); } }; void Melder_print (const wchar *s); /* Write formatted text to the Info window without clearing it, and without adding a new-line symbol at the end. */ void Melder_clearInfo (void); /* Clear the Info window. */ const wchar * Melder_getInfo (void); void Melder_help (const wchar *query); void Melder_search (void); void Melder_beep (void); extern int Melder_debug; /* The following trick uses Melder_debug only because it is the only plain variable known to exist at the moment. */ #define Melder_offsetof(klas,member) (char *) & ((klas) & Melder_debug) -> member - (char *) & Melder_debug /********** ERROR **********/ class MelderError { }; typedef class structThing *Thing; wchar *Thing_messageName (Thing me); struct MelderArg { int type; union { const wchar *argW; const char *arg8; }; MelderArg (const wchar * arg) : type (1), argW (arg) { } MelderArg (const char * arg) : type (2), arg8 (arg) { } MelderArg (const double arg) : type (1), argW (Melder_double (arg)) { } MelderArg (const long arg) : type (1), argW (Melder_integer (arg)) { } MelderArg (const unsigned long arg) : type (1), argW (Melder_integer (arg)) { } MelderArg (const int arg) : type (1), argW (Melder_integer (arg)) { } MelderArg (const unsigned int arg) : type (1), argW (Melder_integer (arg)) { } MelderArg (const short arg) : type (1), argW (Melder_integer (arg)) { } MelderArg (const unsigned short arg) : type (1), argW (Melder_integer (arg)) { } MelderArg (Thing arg) : type (1), argW (Thing_messageName (arg)) { } MelderArg (MelderFile arg) : type (1), argW (MelderFile_messageName (arg)) { } }; void Melder_throw (const MelderArg& arg1); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13 = L""); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15 = L""); void Melder_throw (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15, const MelderArg& arg16, const MelderArg& arg17 = L"", const MelderArg& arg18 = L"", const MelderArg& arg19 = L"", const MelderArg& arg20 = L""); void Melder_error_ (const MelderArg& arg1); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13 = L""); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15 = L""); void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15, const MelderArg& arg16, const MelderArg& arg17 = L"", const MelderArg& arg18 = L"", const MelderArg& arg19 = L"", const MelderArg& arg20 = L""); #define therror if (Melder_hasError ()) { Melder_error_ ("PLEASE SEND THIS ENTIRE ERROR MESSAGE TO PAUL.BOERSMA@UVA.NL (file ", __FILE__, ", line ", __LINE__, ")."); throw MelderError (); } #define Melder_throw(...) do { Melder_error_ (__VA_ARGS__); throw MelderError (); } while (false) void Melder_flushError (const char *format, ...); /* Send all deferred error messages to stderr (batch) or to an "Error" dialog, */ /* including, if 'format' is not NULL, the error message generated by this routine. */ bool Melder_hasError (); bool Melder_hasError (const wchar *partialError); /* Returns 1 if there is an error message in store, otherwise 0. */ void Melder_clearError (void); /* Cancel all stored error messages. */ wchar * Melder_getError (void); /* Returns the error string. Mainly used with wcsstr. */ int Melder_fatal (const char *format, ...); /* Give error message, abort program. */ /* Should only be caused by programming errors. */ #ifdef NDEBUG #define Melder_assert(x) ((void) 0) #else #define Melder_assert(x) ((x) ? (void) (0) : (void) _Melder_assert (#x, __FILE__, __LINE__)) #endif int _Melder_assert (const char *condition, const char *fileName, int lineNumber); /* Call Melder_fatal with a message based on the following template: */ /* "Assertion failed in file on line : " */ /********** WARNING: ive warning to stderr (batch) or to a "Warning" dialog **********/ void Melder_warning (const MelderArg& arg1); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13 = L""); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15 = L""); void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15, const MelderArg& arg16, const MelderArg& arg17 = L"", const MelderArg& arg18 = L"", const MelderArg& arg19 = L"", const MelderArg& arg20 = L""); void Melder_warningOff (void); void Melder_warningOn (void); class autoMelderWarningOff { public: autoMelderWarningOff () { Melder_warningOff (); } ~autoMelderWarningOff () { Melder_warningOn (); } }; /********** PROGRESS ROUTINES **********/ void Melder_progress (double progress, const wchar *s1); void Melder_progress (double progress, const wchar *s1, const wchar *s2); void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3); void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); void Melder_progressOff (void); void Melder_progressOn (void); /* Function: Show the progress of a time-consuming process. Arguments: Any of 's1' through 's9' may be NULL. Batch behaviour: Does nothing, always returns 1. Interactive behaviour: Shows the progress of a time-consuming process: - if 'progress' <= 0.0, show a window with text and a Cancel button, and return 1; - if 0.0 < 'progress' < 1.0, show text and a partially filled progress bar, and return 0 if user interrupts, else return 1; - if 'progress' >= 1, hide the window. Usage: - call with 'progress' = 0.0 before the process starts: (void) Melder_progress (0.0, "Starting work..."); - at every turn in your loop, call with 'progress' between 0 and 1: Melder_progress (i / (n + 1.0), L"Working on part ", i, L" out of ", n, L"..."); an exception is thrown if the user clicks Cancel; if you don't want that, catch it: try { Melder_progress (i / (n + 1.0), L"Working on part ", i, L" out of ", n, L"..."); } catch (MelderError) { Melder_clearError (); break; } - after the process has finished, call with 'progress' = 1.0: (void) Melder_progress (1.0, NULL); - the first and third steps can be automated by autoMelderProgress: autoMelderProgress progress ("Starting work..."); */ class autoMelderProgress { public: autoMelderProgress (const wchar *message) { Melder_progress (0.0, message); } ~autoMelderProgress () { Melder_progress (1.0, NULL); } }; void * Melder_monitor (double progress, const wchar *s1); void * Melder_monitor (double progress, const wchar *s1, const wchar *s2); void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3); void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4); void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5); void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6); void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7); void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8); void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9); /* Function: Show the progress of a time-consuming process. Arguments: Any of 's1' through 's9' may be NULL. Batch behaviour: Does nothing, returns NULL if 'progress' <= 0.0 and a non-NULL pointer otherwise. Interactive behaviour: Shows the progress of a time-consuming process: - if 'progress' <= 0.0, show a window with text and a Cancel button and room for a square drawing, and return a Graphics; - if 0.0 < 'progress' < 1.0, show text and a partially filled progress bar, and return NULL if user interrupts, else return a non-NULL pointer; - if 'progress' >= 1, hide the window. Usage: - call with 'progress' = 0.0 before the process starts. - assign the return value to a Graphics: Graphics graphics = Melder_monitor (0.0, L"Starting work..."); - at every turn of your loop, draw something in the Graphics: if (graphics) { // always check; might be batch Graphics_clearWs (graphics); // only if you redraw all every time Graphics_polyline (graphics, ...); Graphics_text (graphics, ...); } - immediately after this in your loop, call with 'progress' between 0 and 1: Melder_monitor (i / (n + 1.0), L"Working on part ", Melder_integer (i), L" out of ", Melder_integer (n), L"..."); an exception is thrown if the user clicks Cancel; if you don't want that, catch it: try { Melder_monitor (i / (n + 1.0), L"Working on part ", Melder_integer (i), L" out of ", Melder_integer (n), L"..."); } catch (MelderError) { Melder_clearError (); break; } - after the process has finished, call with 'progress' = 1.0: (void) Melder_monitor (1.0, NULL); - the first and third steps can be automated by autoMelderMonitor: autoMelderMonitor monitor ("Starting work..."); if (monitor.graphics()) { // always check; might be batch Graphics_clearWs (monitor.graphics()); // only if you redraw all every time Graphics_polyline (monitor.graphics(), ...); Graphics_text (monitor.graphics(), ...); } */ typedef class structGraphics *Graphics; class autoMelderMonitor { Graphics d_graphics; public: autoMelderMonitor (const wchar *message) { d_graphics = (Graphics) Melder_monitor (0.0, message); } ~autoMelderMonitor () { Melder_monitor (1.0, NULL); } Graphics graphics () { return d_graphics; } }; /********** RECORD AND PLAY ROUTINES **********/ int Melder_publish (void *anything); int Melder_record (double duration); int Melder_recordFromFile (MelderFile fs); void Melder_play (void); void Melder_playReverse (void); int Melder_publishPlayed (void); /********** SYSTEM VERSION **********/ extern unsigned long Melder_systemVersion; /* For Macintosh, this is set in the Motif emulator. */ /********** SCRATCH TEXT BUFFERS **********/ extern char Melder_buffer1 [30001], Melder_buffer2 [30001]; /* Every Melder routine uses both of these buffers: one for sprintfing the message, and one for translating this message to a native string. You can use these buffers, but be careful not to call any other routines that use them at the same time; the following routines are guaranteed not to call the Melder library: - Mac Toolbox, XWindows, X Toolkit, Motif, and XVT routines, except those who dispatch events (XtDispatchEvent, xvt_process_pending_events). - Longchar_* This means that you can use these buffers for reading and writing with the Longchar library. */ /********** ENFORCE INTERACTIVE BEHAVIOUR **********/ /* Procedures to enforce interactive behaviour of the Melder_XXXXXX routines. */ void MelderGui_create (/* GuiObject */ void *parent); /* 'parent' is the top-level widget returned by GuiAppInitialize. */ extern bool Melder_batch; // true if run from the batch or from an interactive command-line interface extern bool Melder_backgrounding; /* True if running a script. */ extern bool Melder_consoleIsAnsi; #ifndef CONTROL_APPLICATION extern void *Melder_topShell; // GuiObject #endif /********** OVERRIDE DEFAULT BEHAVIOUR **********/ /* Procedures to override default message methods. */ /* They may chage the string arguments. */ /* Many of these routines are called by MelderMotif_create and MelderXvt_create. */ void Melder_setCasualProc (void (*casualProc) (const wchar *message)); void Melder_setProgressProc (int (*progressProc) (double progress, const wchar *message)); void Melder_setMonitorProc (void * (*monitorProc) (double progress, const wchar *message)); void Melder_setInformationProc (void (*informationProc) (const wchar *message)); void Melder_setHelpProc (void (*help) (const wchar *query)); void Melder_setSearchProc (void (*search) (void)); void Melder_setWarningProc (void (*warningProc) (const wchar *message)); void Melder_setErrorProc (void (*errorProc) (const wchar *message)); void Melder_setFatalProc (void (*fatalProc) (const wchar *message)); void Melder_setPublishProc (int (*publish) (void *)); void Melder_setRecordProc (int (*record) (double)); void Melder_setRecordFromFileProc (int (*recordFromFile) (MelderFile)); void Melder_setPlayProc (void (*play) (void)); void Melder_setPlayReverseProc (void (*playReverse) (void)); void Melder_setPublishPlayedProc (int (*publishPlayed) (void)); double Melder_stopwatch (void); long Melder_killReturns_inline (char *text); /* Replaces all bare returns (Mac) or return / linefeed sequences (Win) with bare linefeeds (generic = Unix). Returns new length of string (equal to or less than old length). */ /********** AUDIO **********/ #if defined (macintosh) || defined (_WIN32) || defined (linux) #define kMelderAudio_inputUsesPortAudio_DEFAULT true // Mac: in order to have CoreAudio // Win: in order to allow recording for over 64 megabytes (paMME) // Linux: in order to use ALSA and therefore be compatible with Ubuntu 10.10 and later #else #define kMelderAudio_inputUsesPortAudio_DEFAULT false #endif void MelderAudio_setInputUsesPortAudio (bool inputUsesPortAudio); bool MelderAudio_getInputUsesPortAudio (void); #if defined (macintosh) || defined (linux) #define kMelderAudio_outputUsesPortAudio_DEFAULT true // Mac: in order to have CoreAudio // Linux: in order to use ALSA and therefore be compatible with Ubuntu 10.10 and later #else #define kMelderAudio_outputUsesPortAudio_DEFAULT false // Win: in order to reduce the long latencies of paMME and to avoid the incomplete implementation of paDirectSound #endif void MelderAudio_setOutputUsesPortAudio (bool outputUsesPortAudio); bool MelderAudio_getOutputUsesPortAudio (void); #if 1 #define kMelderAudio_outputSilenceBefore_DEFAULT 0.0 // Mac: in order to switch off the BOING caused by the automatic gain control #endif void MelderAudio_setOutputSilenceBefore (double silenceBefore); double MelderAudio_getOutputSilenceBefore (void); #if defined (macintosh) #define kMelderAudio_outputSilenceAfter_DEFAULT 0.0 // Mac: in order to reduce the BOING caused by the automatic gain control when the user replays immediately after a sound has finished #else #define kMelderAudio_outputSilenceAfter_DEFAULT 0.5 // Win: in order to get rid of the click on some cards // Linux: in order to get rid of double playing of a sounding buffer #endif void MelderAudio_setOutputSilenceAfter (double silenceAfter); double MelderAudio_getOutputSilenceAfter (void); void MelderAudio_setOutputUsesBlocking (bool outputUsesBlocking); bool MelderAudio_getOutputUsesBlocking (void); void MelderAudio_setUseInternalSpeaker (bool useInternalSpeaker); // for HP-UX and Sun bool MelderAudio_getUseInternalSpeaker (void); void MelderAudio_setOutputMaximumAsynchronicity (enum kMelder_asynchronicityLevel maximumAsynchronicity); enum kMelder_asynchronicityLevel MelderAudio_getOutputMaximumAsynchronicity (void); long MelderAudio_getOutputBestSampleRate (long fsamp); extern bool MelderAudio_isPlaying; void MelderAudio_play16 (const int16_t *buffer, long sampleRate, long numberOfSamples, int numberOfChannels, bool (*playCallback) (void *playClosure, long numberOfSamplesPlayed), // return true to continue, false to stop void *playClosure); bool MelderAudio_stopPlaying (bool isExplicit); // returns true if sound was playing #define MelderAudio_IMPLICIT false #define MelderAudio_EXPLICIT true long MelderAudio_getSamplesPlayed (void); bool MelderAudio_stopWasExplicit (void); void Melder_audio_prefs (void); // in init file /********** AUDIO FILES **********/ /* Audio file types. */ #define Melder_AIFF 1 #define Melder_AIFC 2 #define Melder_WAV 3 #define Melder_NEXT_SUN 4 #define Melder_NIST 5 #define Melder_SOUND_DESIGNER_TWO 6 #define Melder_FLAC 7 #define Melder_MP3 8 #define Melder_NUMBER_OF_AUDIO_FILE_TYPES 8 const wchar * Melder_audioFileTypeString (int audioFileType); /* "AIFF", "AIFC", "WAV", "NeXT/Sun", "NIST", "Sound Designer II", "FLAC", "MP3" */ const wchar * Melder_macAudioFileType (int audioFileType); /* "AIFF", "AIFC", "WAVE", "ULAW", "NIST", "Sd2f", "FLAC", "MP3" */ const wchar * Melder_winAudioFileExtension (int audioFileType); /* ".aiff", ".aifc", ".wav", ".au", ".nist", ".sd2", ".flac", ".mp3" */ /* Audio encodings. */ #define Melder_LINEAR_8_SIGNED 1 #define Melder_LINEAR_8_UNSIGNED 2 #define Melder_LINEAR_16_BIG_ENDIAN 3 #define Melder_LINEAR_16_LITTLE_ENDIAN 4 #define Melder_LINEAR_24_BIG_ENDIAN 5 #define Melder_LINEAR_24_LITTLE_ENDIAN 6 #define Melder_LINEAR_32_BIG_ENDIAN 7 #define Melder_LINEAR_32_LITTLE_ENDIAN 8 #define Melder_MULAW 9 #define Melder_ALAW 10 #define Melder_SHORTEN 11 #define Melder_POLYPHONE 12 #define Melder_IEEE_FLOAT_32_BIG_ENDIAN 13 #define Melder_IEEE_FLOAT_32_LITTLE_ENDIAN 14 #define Melder_FLAC_COMPRESSION_16 15 #define Melder_FLAC_COMPRESSION_24 16 #define Melder_FLAC_COMPRESSION_32 17 #define Melder_MPEG_COMPRESSION_16 18 #define Melder_MPEG_COMPRESSION_24 19 #define Melder_MPEG_COMPRESSION_32 20 int Melder_defaultAudioFileEncoding (int audioFileType, int numberOfBitsPerSamplePoint); /* BIG_ENDIAN, BIG_ENDIAN, LITTLE_ENDIAN, BIG_ENDIAN, LITTLE_ENDIAN, BIG_ENDIAN */ void MelderFile_writeAudioFileHeader (MelderFile file, int audioFileType, long sampleRate, long numberOfSamples, int numberOfChannels, int numberOfBitsPerSamplePoint); void MelderFile_writeAudioFileTrailer (MelderFile file, int audioFileType, long sampleRate, long numberOfSamples, int numberOfChannels, int numberOfBitsPerSamplePoint); void MelderFile_writeAudioFile (MelderFile file, int audioFileType, const short *buffer, long sampleRate, long numberOfSamples, int numberOfChannels, int numberOfBitsPerSamplePoint); int MelderFile_checkSoundFile (MelderFile file, int *numberOfChannels, int *encoding, double *sampleRate, long *startOfData, long *numberOfSamples); /* Returns information about a just opened audio file. * The return value is the audio file type, or 0 if it is not a sound file or in case of error. * The data start at 'startOfData' bytes from the start of the file. */ int Melder_bytesPerSamplePoint (int encoding); void Melder_readAudioToFloat (FILE *f, int numberOfChannels, int encoding, double **buffer, long numberOfSamples); /* Reads channels into buffer [ichannel], which are base-1. */ void Melder_readAudioToShort (FILE *f, int numberOfChannels, int encoding, short *buffer, long numberOfSamples); /* If stereo, buffer will contain alternating left and right values. * Buffer is base-0. */ void MelderFile_writeFloatToAudio (MelderFile file, int numberOfChannels, int encoding, double **buffer, long numberOfSamples, int warnIfClipped); void MelderFile_writeShortToAudio (MelderFile file, int numberOfChannels, int encoding, const short *buffer, long numberOfSamples); void Melder_audioTrigger (void); /********** QUANTITY **********/ #define MelderQuantity_NONE 0 #define MelderQuantity_TIME_SECONDS 1 #define MelderQuantity_FREQUENCY_HERTZ 2 #define MelderQuantity_FREQUENCY_BARK 3 #define MelderQuantity_DISTANCE_FROM_GLOTTIS_METRES 4 #define MelderQuantity_NUMBER_OF_QUANTITIES 4 const wchar * MelderQuantity_getText (int quantity); // e.g. "Time" const wchar * MelderQuantity_getWithUnitText (int quantity); // e.g. "Time (s)" const wchar * MelderQuantity_getLongUnitText (int quantity); // e.g. "seconds" const wchar * MelderQuantity_getShortUnitText (int quantity); // e.g. "s" /********** MISCELLANEOUS **********/ wchar * Melder_getenv (const wchar *variableName); void Melder_system (const wchar *command); // spawn a system command double Melder_clock (void); // seconds since 1969 struct autoMelderProgressOff { autoMelderProgressOff () { Melder_progressOff (); } ~autoMelderProgressOff () { Melder_progressOn (); } }; struct autoMelderString : MelderString { autoMelderString () { length = 0; bufferSize = 0; string = NULL; } ~autoMelderString () { Melder_free (string); } }; struct autoMelderReadText { MelderReadText text; autoMelderReadText (MelderReadText a_text) : text (a_text) { therror; } ~autoMelderReadText () { if (text) MelderReadText_delete (text); } MelderReadText operator-> () const { // as r-value return text; } MelderReadText peek () const { return text; } MelderReadText transfer () { MelderReadText tmp = text; text = NULL; return tmp; } }; class autofile { FILE *ptr; public: autofile (FILE *f) : ptr (f) { therror; } autofile () : ptr (NULL) { } ~autofile () { if (ptr) fclose (ptr); // no error checking, because this is a destructor, only called after a throw, because otherwise you'd use f.close(file) } operator FILE * () { return ptr; } void reset (FILE *f) { if (ptr) fclose (ptr); // BUG: not a normal closure ptr = f; therror; } void close (MelderFile file) { if (ptr) { FILE *tmp = ptr; ptr = NULL; Melder_fclose (file, tmp); therror } } }; class autoMelderFile { MelderFile file; public: autoMelderFile (MelderFile a_file) : file (a_file) { therror; } ~autoMelderFile () { if (file) MelderFile_close_nothrow (file); } void close () { if (file && file -> filePointer) { MelderFile tmp = file; file = NULL; MelderFile_close (tmp); therror } } MelderFile transfer () { MelderFile tmp = file; file = NULL; return tmp; } }; class autoMelderSaveDefaultDir { structMelderDir saveDir; public: autoMelderSaveDefaultDir () { Melder_getDefaultDir (& saveDir); } ~autoMelderSaveDefaultDir () { Melder_setDefaultDir (& saveDir); } }; class autoMelderSetDefaultDir { structMelderDir saveDir; public: autoMelderSetDefaultDir (MelderDir dir) { Melder_getDefaultDir (& saveDir); Melder_setDefaultDir (dir); } ~autoMelderSetDefaultDir () { Melder_setDefaultDir (& saveDir); } }; class autoMelderFileSetDefaultDir { structMelderDir saveDir; public: autoMelderFileSetDefaultDir (MelderFile file) { Melder_getDefaultDir (& saveDir); MelderFile_setDefaultDir (file); } ~autoMelderFileSetDefaultDir () { Melder_setDefaultDir (& saveDir); } }; class autoMelderTokens { wchar **tokens; public: autoMelderTokens () { tokens = NULL; } autoMelderTokens (const wchar *string, long *n) { tokens = Melder_getTokens (string, n); therror } ~autoMelderTokens () { if (tokens) Melder_freeTokens (& tokens); } wchar*& operator[] (long i) { return tokens [i]; } wchar ** peek () const { return tokens; } void reset (const wchar *string, long *n) { if (tokens) Melder_freeTokens (& tokens); tokens = Melder_getTokens (string, n); therror } }; template class _autostring { T *ptr; public: _autostring (T *string) : ptr (string) { //if (Melder_debug == 39) Melder_casual ("autostring: entering constructor from C-string %ld", ptr); therror; //if (Melder_debug == 39) Melder_casual ("autostring: leaving constructor from C-string"); } _autostring () : ptr (0) { //if (Melder_debug == 39) Melder_casual ("autostring: zero constructor"); } ~_autostring () { //if (Melder_debug == 39) Melder_casual ("autostring: entering destructor ptr = %ld", ptr); if (ptr) Melder_free (ptr); //if (Melder_debug == 39) Melder_casual ("autostring: leaving destructor"); } #if 0 void operator= (T *string) { //if (Melder_debug == 39) Melder_casual ("autostring: entering assignment from C-string; old = %ld", ptr); if (ptr) Melder_free (ptr); ptr = string; therror; //if (Melder_debug == 39) Melder_casual ("autostring: leaving assignment from C-string; new = %ld", ptr); } #endif T& operator[] (long i) { return ptr [i]; } T * peek () const { return ptr; } T ** operator& () { return & ptr; } T * transfer () { T *tmp = ptr; ptr = NULL; return tmp; } void reset (T *string) { if (ptr) Melder_free (ptr); ptr = string; therror; } void resize (long new_size) { T *tmp = (T *) Melder_realloc (ptr, new_size * sizeof (T)); ptr = tmp; } private: _autostring& operator= (const _autostring&); // disable copy assignment //autostring (autostring &); // disable copy constructor (trying it this way also disables good things like autostring s1 = wcsdup("hello");) template _autostring (_autostring &); // disable copy constructor }; typedef _autostring autostring; typedef _autostring autostring8; /* End of file melder.h */ #endif sources_5316/sys/praat_version.h0000644000176700017670000000020511757244435015577 0ustar paulpaul#define PRAAT_VERSION_STR 5.3.16 #define PRAAT_VERSION_NUM 5316 #define PRAAT_YEAR 2012 #define PRAAT_MONTH May #define PRAAT_DAY 23 sources_5316/sys/DemoEditor.h0000644000176700017670000000435111623752044014754 0ustar paulpaul#ifndef _DemoEditor_h_ #define _DemoEditor_h_ /* DemoEditor.h * * Copyright (C) 2009-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Editor.h" Thing_define (DemoEditor, Editor) { // new data: public: GuiObject drawingArea; Graphics graphics; void *praatPicture; bool clicked, keyPressed, shiftKeyPressed, commandKeyPressed, optionKeyPressed, extraControlKeyPressed; long x, y; wchar key; bool waitingForInput, userWantsToClose, fullScreen; // overridden methods: virtual void v_destroy (); virtual void v_info (); virtual void v_goAway (); virtual bool v_hasMenuBar () { return false; } virtual bool v_canFullScreen () { return true; } virtual bool v_scriptable () { return false; } virtual void v_createChildren (); virtual void v_createMenus (); }; void DemoEditor_init (DemoEditor me, GuiObject parent); DemoEditor DemoEditor_create (GuiObject parent); void Demo_open (void); void Demo_close (void); struct autoDemoOpen { autoDemoOpen () { Demo_open (); } ~autoDemoOpen () { Demo_close (); } }; int Demo_windowTitle (const wchar_t *title); int Demo_show (void); void Demo_waitForInput (Interpreter interpreter); bool Demo_clicked (void); double Demo_x (void); double Demo_y (void); bool Demo_keyPressed (void); wchar_t Demo_key (void); bool Demo_shiftKeyPressed (void); bool Demo_commandKeyPressed (void); bool Demo_optionKeyPressed (void); bool Demo_extraControlKeyPressed (void); /* Shortcuts: */ bool Demo_input (const wchar_t *keys); bool Demo_clickedIn (double left, double right, double bottom, double top); /* End of file DemoEditor.h */ #endif sources_5316/sys/Interpreter.h0000644000176700017670000000701411622221105015207 0ustar paulpaul#ifndef _Interpreter_h_ #define _Interpreter_h_ /* Interpreter.h * * Copyright (C) 1993-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection.h" #include "Gui.h" #include "Formula.h" Thing_define (InterpreterVariable, SimpleString) { // new data: public: wchar *stringValue; double numericValue; struct Formula_NumericArray numericArrayValue; // overridden methods: protected: virtual void v_destroy (); }; #define Interpreter_MAXNUM_PARAMETERS 400 #define Interpreter_MAXNUM_LABELS 1000 #define Interpreter_MAX_CALL_DEPTH 50 Thing_declare (UiForm); Thing_declare (Editor); Thing_define (Interpreter, Thing) { // new data: public: wchar *environmentName; ClassInfo editorClass; int numberOfParameters, numberOfLabels, callDepth; wchar parameters [1+Interpreter_MAXNUM_PARAMETERS] [100]; unsigned char types [1+Interpreter_MAXNUM_PARAMETERS]; wchar *arguments [1+Interpreter_MAXNUM_PARAMETERS]; wchar choiceArguments [1+Interpreter_MAXNUM_PARAMETERS] [100]; wchar labelNames [1+Interpreter_MAXNUM_LABELS] [100]; long labelLines [1+Interpreter_MAXNUM_LABELS]; wchar dialogTitle [1+100], procedureNames [1+Interpreter_MAX_CALL_DEPTH] [100]; SortedSetOfString variables; bool running, stopped; // overridden methods: protected: virtual void v_destroy (); }; Interpreter Interpreter_create (wchar *environmentName, ClassInfo editorClass); Interpreter Interpreter_createFromEnvironment (Editor editor); void Melder_includeIncludeFiles (wchar **text); long Interpreter_readParameters (Interpreter me, wchar *text); Thing_declare (UiForm); UiForm Interpreter_createForm (Interpreter me, GuiObject parent, const wchar_t *fileName, void (*okCallback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure), void *okClosure); void Interpreter_getArgumentsFromDialog (Interpreter me, Any dialog); void Interpreter_getArgumentsFromString (Interpreter me, const wchar *arguments); void Interpreter_run (Interpreter me, wchar *text); // destroys 'text' void Interpreter_stop (Interpreter me); // can be called from any procedure called deep-down by the interpreter; will stop before next line void Interpreter_voidExpression (Interpreter me, const wchar *expression); void Interpreter_numericExpression (Interpreter me, const wchar *expression, double *value); void Interpreter_stringExpression (Interpreter me, const wchar *expression, wchar **value); void Interpreter_numericArrayExpression (Interpreter me, const wchar *expression, struct Formula_NumericArray *value); void Interpreter_anyExpression (Interpreter me, const wchar *expression, struct Formula_Result *result); InterpreterVariable Interpreter_hasVariable (Interpreter me, const wchar *key); InterpreterVariable Interpreter_lookUpVariable (Interpreter me, const wchar *key); /* End of file Interpreter.h */ #endif sources_5316/sys/GuiDialog.cpp0000644000176700017670000001253711753741756015141 0ustar paulpaul/* GuiDialog.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/30 * fb 2010/02/23 gtk * pb 2010/05/29 repaired memory leak; made dialog front on show * pb 2010/07/29 removed GuiDialog_show * pb 2011/04/06 C++ */ #include "GuiP.h" #undef iam #define iam(x) x me = (x) void_me #if win || mac #define iam_dialog \ GuiDialog me = (GuiDialog) widget -> userData #else #define iam_dialog \ GuiDialog me = (GuiDialog) _GuiObject_getUserData (widget) #endif typedef struct structGuiDialog { GuiObject widget; void (*goAwayCallback) (void *boss); void *goAwayBoss; } *GuiDialog; #if gtk static void _GuiGtkDialog_destroyCallback (GuiObject widget, gpointer void_me) { (void) widget; iam (GuiDialog); Melder_free (me); } static gboolean _GuiGtkDialog_goAwayCallback (GuiObject widget, GdkEvent *event, gpointer void_me) { (void) event; iam (GuiDialog); if (my goAwayCallback != NULL) { my goAwayCallback (my goAwayBoss); } return TRUE; // signal handled (don't destroy dialog) } #elif win || mac static void _GuiMotifDialog_destroyCallback (GuiObject widget, XtPointer void_me, XtPointer call) { (void) widget; (void) call; iam (GuiDialog); Melder_free (me); } static void _GuiMotifDialog_goAwayCallback (GuiObject widget, XtPointer void_me, XtPointer call) { (void) widget; (void) call; iam (GuiDialog); if (my goAwayCallback != NULL) { my goAwayCallback (my goAwayBoss); } } #endif GuiObject GuiDialog_create (GuiObject parent, int x, int y, int width, int height, const wchar_t *title, void (*goAwayCallback) (void *goAwayBoss), void *goAwayBoss, unsigned long flags) { GuiDialog me = Melder_calloc_f (struct structGuiDialog, 1); my goAwayCallback = goAwayCallback; my goAwayBoss = goAwayBoss; #if gtk GuiObject shell = gtk_dialog_new (); if (parent) { GuiObject toplevel = gtk_widget_get_ancestor (GTK_WIDGET (parent), GTK_TYPE_WINDOW); if (toplevel) { gtk_window_set_transient_for (GTK_WINDOW (shell), GTK_WINDOW (toplevel)); gtk_window_set_destroy_with_parent (GTK_WINDOW (shell), TRUE); } } g_signal_connect (G_OBJECT (shell), "delete-event", goAwayCallback ? G_CALLBACK (_GuiGtkDialog_goAwayCallback) : G_CALLBACK (gtk_widget_hide_on_delete), me); if (width == Gui_AUTOMATIC) width = -1; if (height == Gui_AUTOMATIC) height = -1; gtk_window_set_default_size (GTK_WINDOW (shell), width, height); gtk_window_set_modal (GTK_WINDOW (shell), flags & GuiDialog_MODAL); GuiWindow_setTitle (shell, title); my widget = GTK_DIALOG (shell) -> vbox; g_signal_connect (G_OBJECT (my widget), "destroy", G_CALLBACK (_GuiGtkDialog_destroyCallback), me); #elif win GuiObject shell = XmCreateDialogShell (parent, "dialogShell", NULL, 0); XtVaSetValues (shell, XmNdeleteResponse, goAwayCallback ? XmDO_NOTHING : XmUNMAP, XmNx, x, XmNy, y, NULL); if (goAwayCallback) { XmAddWMProtocolCallback (shell, 'delw', _GuiMotifDialog_goAwayCallback, (char *) me); } GuiWindow_setTitle (shell, title); my widget = XmCreateForm (shell, "dialog", NULL, 0); if (width != Gui_AUTOMATIC) XtVaSetValues (my widget, XmNwidth, (Dimension) width, NULL); if (height != Gui_AUTOMATIC) XtVaSetValues (my widget, XmNheight, (Dimension) height, NULL); _GuiObject_setUserData (my widget, me); XtAddCallback (my widget, XmNdestroyCallback, _GuiMotifDialog_destroyCallback, me); XtVaSetValues (my widget, XmNdialogStyle, (flags & GuiDialog_MODAL) ? XmDIALOG_FULL_APPLICATION_MODAL : XmDIALOG_MODELESS, XmNautoUnmanage, False, NULL); #elif mac #if useCarbon GuiObject shell = XmCreateDialogShell (parent, "dialogShell", NULL, 0); XtVaSetValues (shell, XmNdeleteResponse, goAwayCallback ? XmDO_NOTHING : XmUNMAP, XmNx, x, XmNy, y, NULL); if (goAwayCallback) { XmAddWMProtocolCallback (shell, 'delw', _GuiMotifDialog_goAwayCallback, (char *) me); } GuiWindow_setTitle (shell, title); my widget = XmCreateForm (shell, "dialog", NULL, 0); if (width != Gui_AUTOMATIC) XtVaSetValues (my widget, XmNwidth, (Dimension) width, NULL); if (height != Gui_AUTOMATIC) XtVaSetValues (my widget, XmNheight, (Dimension) height, NULL); _GuiObject_setUserData (my widget, me); XtAddCallback (my widget, XmNdestroyCallback, _GuiMotifDialog_destroyCallback, me); XtVaSetValues (my widget, XmNdialogStyle, (flags & GuiDialog_MODAL) ? XmDIALOG_FULL_APPLICATION_MODAL : XmDIALOG_MODELESS, XmNautoUnmanage, False, NULL); #else #endif #endif return my widget; } GuiObject GuiDialog_getButtonArea (GuiObject widget) { #if gtk GuiObject shell = GuiObject_parent (widget); Melder_assert (GTK_IS_DIALOG (shell)); return GTK_DIALOG (shell) -> action_area; #else return widget; #endif } /* End of file GuiDialog.cpp */ sources_5316/sys/melder_console.cpp0000644000176700017670000000425311605360025016241 0ustar paulpaul/* melder_console.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* pb 2008/02/17 * pb 2008/10/27 Melder_consoleIsAnsi * pb 2011/04/05 C++ */ #include "melder.h" #include "NUM.h" #ifdef _WIN32 #include #endif bool Melder_consoleIsAnsi = false; void Melder_writeToConsole (const wchar_t *message, bool useStderr) { if (message == NULL) return; #if defined (_WIN32) (void) useStderr; static HANDLE console = NULL; if (console == NULL) { console = CreateFile (L"CONOUT$", GENERIC_WRITE, FILE_SHARE_WRITE, NULL, OPEN_EXISTING, 0, 0); } if (Melder_consoleIsAnsi) { size_t n = wcslen (message); for (long i = 0; i < n; i ++) { unsigned int kar = (unsigned short) message [i]; fputc (kar, stdout); } //} else if (Melder_consoleIsUtf8) { //char *messageA = Melder_peekWcsToUtf8 (message); //fprintf (stdout, "%s", messageA); } else { WriteConsole (console, message, wcslen (message), NULL, NULL); } #else Melder_fwriteWcsAsUtf8 (message, wcslen (message), useStderr ? stderr : stdout); #endif } #if defined (_WIN32) && defined (CONSOLE_APPLICATION) int main (int argc, char *argvA []); extern "C" int wmain (int argc, wchar_t *argvW []); extern "C" int wmain (int argc, wchar_t *argvW []) { char **argvA = NULL; if (argc > 0) { argvA = NUMvector (0, argc - 1); for (int iarg = 0; iarg < argc; iarg ++) { argvA [iarg] = Melder_wcsToUtf8 (argvW [iarg]); } } return main (argc, argvA); } #endif /* End of file melder_console.cpp */ sources_5316/sys/ManPage.h0000644000176700017670000000240111621516020014211 0ustar paulpaul#ifndef _ManPage_h_ #define _ManPage_h_ /* ManPage.h * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Graphics.h" #include "ManPage_enums.h" typedef struct structManPage_Paragraph { short type; const wchar_t *text; double width, height; void (*draw) (Graphics g); } *ManPage_Paragraph; Thing_define (ManPage, Thing) { // new data: public: const wchar *title, *author; long date; struct structManPage_Paragraph *paragraphs; long nlinksHither, nlinksThither; long *linksHither, *linksThither; double recordingTime; }; /* End of file ManPage.h */ #endif sources_5316/sys/Graphics_image.cpp0000644000176700017670000007364211752306100016156 0ustar paulpaul/* Graphics_image.cpp * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2007/04/25 better image drawing on the Mac * pb 2007/08/03 Quartz * pb 2008/01/19 double * pb 2009/08/10 image from file * fb 2010/02/24 GTK * pb 2011/03/17 C++ * pb 2012/04/21 on PostScript, minimal image resolution raised from 106 to 300 dpi * pb 2012/05/08 erased all QuickDraw */ #include "GraphicsP.h" #if win #include #elif mac #include #include "macport_on.h" static void _mac_releaseDataCallback (void *info, const void *data, size_t size) { (void) info; (void) size; Melder_free (data); } #endif #define wdx(x) ((x) * my scaleX + my deltaX) #define wdy(y) ((y) * my scaleY + my deltaY) static void _GraphicsScreen_cellArrayOrImage (GraphicsScreen me, double **z_float, unsigned char **z_byte, long ix1, long ix2, long x1DC, long x2DC, long iy1, long iy2, long y1DC, long y2DC, double minimum, double maximum, long clipx1, long clipx2, long clipy1, long clipy2, int interpolate) { /*long t=clock();*/ long nx = ix2 - ix1 + 1; /* The number of cells along the horizontal axis. */ long ny = iy2 - iy1 + 1; /* The number of cells along the vertical axis. */ double dx = (double) (x2DC - x1DC) / (double) nx; /* Horizontal pixels per cell. Positive. */ double dy = (double) (y2DC - y1DC) / (double) ny; /* Vertical pixels per cell. Negative. */ double scale = 255.0 / (maximum - minimum), offset = 255.0 + minimum * scale; if (x2DC <= x1DC || y1DC <= y2DC) return; if (Melder_debug == 36) Melder_casual ("scale %f", scale); /* Clip by the intersection of the world window and the outline of the cells. */ //Melder_casual ("clipy1 %ld clipy2 %ld", clipy1, clipy2); if (clipx1 < x1DC) clipx1 = x1DC; if (clipx2 > x2DC) clipx2 = x2DC; if (clipy1 > y1DC) clipy1 = y1DC; if (clipy2 < y2DC) clipy2 = y2DC; /* * The first decision is whether we are going to use the standard rectangle drawing * (cellArray only), or whether we are going to write into a bitmap. * The standard drawing is best for small numbers of cells, * provided that some cells are larger than a pixel. */ if (! interpolate && nx * ny < 3000 && (dx > 1.0 || dy < -1.0)) { try { /*unsigned int cellWidth = (unsigned int) dx + 1;*/ unsigned int cellHeight = (unsigned int) (- (int) dy) + 1; long ix, iy; #if cairo cairo_pattern_t *grey [256]; for (int igrey = 0; igrey < sizeof (grey) / sizeof (*grey); igrey ++) { double v = igrey / ((double) (sizeof (grey) / sizeof (*grey)) - 1.0); grey [igrey] = cairo_pattern_create_rgb (v, v, v); } #elif win static HBRUSH greyBrush [256]; RECT rect; if (! greyBrush [0]) for (int igrey = 0; igrey <= 255; igrey ++) greyBrush [igrey] = CreateSolidBrush (RGB (igrey, igrey, igrey)); // once #elif mac GraphicsQuartz_initDraw (me); CGContextSetAlpha (my d_macGraphicsContext, 1.0); CGContextSetBlendMode (my d_macGraphicsContext, kCGBlendModeNormal); #endif autoNUMvector lefts (ix1, ix2 + 1); for (ix = ix1; ix <= ix2 + 1; ix ++) lefts [ix] = x1DC + (long) ((ix - ix1) * dx); for (iy = iy1; iy <= iy2; iy ++) { long bottom = y1DC + (long) ((iy - iy1) * dy), top = bottom - cellHeight; if (top > clipy1 || bottom < clipy2) continue; if (top < clipy2) top = clipy2; if (bottom > clipy1) bottom = clipy1; #if win rect. bottom = bottom; rect. top = top; #endif for (ix = ix1; ix <= ix2; ix ++) { long left = lefts [ix], right = lefts [ix + 1]; long value = offset - scale * ( z_float ? z_float [iy] [ix] : z_byte [iy] [ix] ); if (right < clipx1 || left > clipx2) continue; if (left < clipx1) left = clipx1; if (right > clipx2) right = clipx2; #if cairo cairo_set_source (my d_cairoGraphicsContext, grey [value <= 0 ? 0 : value >= sizeof (grey) / sizeof (*grey) ? sizeof (grey) / sizeof (*grey) : value]); cairo_rectangle (my d_cairoGraphicsContext, left, top, right - left, bottom - top); cairo_fill (my d_cairoGraphicsContext); #elif win rect. left = left; rect. right = right; FillRect (my d_gdiGraphicsContext, & rect, greyBrush [value <= 0 ? 0 : value >= 255 ? 255 : value]); #elif mac double igrey = ( value <= 0 ? 0 : value >= 255 ? 255 : value ) / 255.0; CGContextSetRGBFillColor (my d_macGraphicsContext, igrey, igrey, igrey, 1.0); CGContextFillRect (my d_macGraphicsContext, CGRectMake (left, top, right - left, bottom - top)); #endif } } #if cairo for (int igrey = 0; igrey < sizeof (grey) / sizeof (*grey); igrey ++) cairo_pattern_destroy (grey [igrey]); cairo_paint (my d_cairoGraphicsContext); #elif mac CGContextSetRGBFillColor (my d_macGraphicsContext, 0.0, 0.0, 0.0, 1.0); GraphicsQuartz_exitDraw (me); #endif } catch (MelderError) { } } else { long xDC, yDC; long undersampling = 1; /* * Prepare for off-screen bitmap drawing. */ #if cairo long arrayWidth = clipx2 - clipx1; long arrayHeight = clipy1 - clipy2; if (Melder_debug == 36) Melder_casual ("arrayWidth %f, arrayHeight %f", (double) arrayWidth, (double) arrayHeight); // We're creating an alpha-only surface here (size is 1/4 compared to RGB24 and ARGB) // The grey values are reversed as we let the foreground colour shine through instead of blackening cairo_surface_t *sfc = cairo_image_surface_create (/*CAIRO_FORMAT_A8*/ CAIRO_FORMAT_RGB24, arrayWidth, arrayHeight); unsigned char *bits = cairo_image_surface_get_data (sfc); int scanLineLength = cairo_image_surface_get_stride (sfc); unsigned char grey [256]; if (Melder_debug == 36) Melder_casual ("image surface address %ld, bits address %ld, scanLineLength %d, numberOfGreys %d", sfc, bits, scanLineLength, sizeof(grey)/sizeof(*grey)); for (int igrey = 0; igrey < sizeof (grey) / sizeof (*grey); igrey++) grey [igrey] = 255 - (unsigned char) (igrey * 255.0 / (sizeof (grey) / sizeof (*grey) - 1)); #elif win long bitmapWidth = clipx2 - clipx1, bitmapHeight = clipy1 - clipy2; int igrey; /* * Create a device-independent bitmap, 8 pixels deep, for 256 greys. */ struct { BITMAPINFOHEADER header; RGBQUAD colours [256]; } bitmapInfo; long scanLineLength = (bitmapWidth + 3) & ~3L; HBITMAP bitmap; unsigned char *bits; bitmapInfo. header.biSize = sizeof (BITMAPINFOHEADER); bitmapInfo. header.biWidth = scanLineLength; bitmapInfo. header.biHeight = bitmapHeight; bitmapInfo. header.biPlanes = 1; bitmapInfo. header.biBitCount = 8; bitmapInfo. header.biCompression = 0; bitmapInfo. header.biSizeImage = 0; bitmapInfo. header.biXPelsPerMeter = 0; bitmapInfo. header.biYPelsPerMeter = 0; bitmapInfo. header.biClrUsed = 0; bitmapInfo. header.biClrImportant = 0; for (igrey = 0; igrey <= 255; igrey ++) { bitmapInfo. colours [igrey]. rgbRed = igrey; bitmapInfo. colours [igrey]. rgbGreen = igrey; bitmapInfo. colours [igrey]. rgbBlue = igrey; } bitmap = CreateDIBSection (my d_gdiGraphicsContext /* ignored */, (CONST BITMAPINFO *) & bitmapInfo, DIB_RGB_COLORS, (VOID **) & bits, NULL, 0); #elif mac long bytesPerRow = (clipx2 - clipx1) * 4; Melder_assert (bytesPerRow > 0); long numberOfRows = clipy1 - clipy2; Melder_assert (numberOfRows > 0); unsigned char *imageData = Melder_malloc_f (unsigned char, bytesPerRow * numberOfRows); #endif /* * Draw into the bitmap. */ #if cairo #define ROW_START_ADDRESS (bits + (clipy1 - 1 - yDC) * scanLineLength) #define PUT_PIXEL \ if (1) { \ unsigned char kar = value <= 0 ? 0 : value >= 255 ? 255 : (int) value; \ *pixelAddress ++ = kar; \ *pixelAddress ++ = kar; \ *pixelAddress ++ = kar; \ *pixelAddress ++ = 0; \ } #elif win #define ROW_START_ADDRESS (bits + (clipy1 - 1 - yDC) * scanLineLength) #define PUT_PIXEL *pixelAddress ++ = value <= 0 ? 0 : value >= 255 ? 255 : (int) value; #elif mac #define ROW_START_ADDRESS (imageData + (clipy1 - 1 - yDC) * bytesPerRow) #define PUT_PIXEL \ if (1) { \ unsigned char kar = value <= 0 ? 0 : value >= 255 ? 255 : (int) value; \ *pixelAddress ++ = kar; \ *pixelAddress ++ = kar; \ *pixelAddress ++ = kar; \ *pixelAddress ++ = 0; \ } #endif if (interpolate) { try { autoNUMvector ileft (clipx1, clipx2); autoNUMvector iright (clipx1, clipx2); autoNUMvector rightWeight (clipx1, clipx2); autoNUMvector leftWeight (clipx1, clipx2); for (xDC = clipx1; xDC < clipx2; xDC += undersampling) { double ix_real = ix1 - 0.5 + ((double) nx * (xDC - x1DC)) / (x2DC - x1DC); ileft [xDC] = floor (ix_real), iright [xDC] = ileft [xDC] + 1; rightWeight [xDC] = ix_real - ileft [xDC], leftWeight [xDC] = 1.0 - rightWeight [xDC]; if (ileft [xDC] < ix1) ileft [xDC] = ix1; if (iright [xDC] > ix2) iright [xDC] = ix2; } for (yDC = clipy2; yDC < clipy1; yDC += undersampling) { double iy_real = iy2 + 0.5 - ((double) ny * (yDC - y2DC)) / (y1DC - y2DC); long itop = ceil (iy_real), ibottom = itop - 1; double bottomWeight = itop - iy_real, topWeight = 1.0 - bottomWeight; unsigned char *pixelAddress = ROW_START_ADDRESS; if (itop > iy2) itop = iy2; if (ibottom < iy1) ibottom = iy1; if (z_float) { double *ztop = z_float [itop], *zbottom = z_float [ibottom]; for (xDC = clipx1; xDC < clipx2; xDC += undersampling) { double interpol = rightWeight [xDC] * (topWeight * ztop [iright [xDC]] + bottomWeight * zbottom [iright [xDC]]) + leftWeight [xDC] * (topWeight * ztop [ileft [xDC]] + bottomWeight * zbottom [ileft [xDC]]); double value = offset - scale * interpol; PUT_PIXEL } } else { unsigned char *ztop = z_byte [itop], *zbottom = z_byte [ibottom]; for (xDC = clipx1; xDC < clipx2; xDC += undersampling) { double interpol = rightWeight [xDC] * (topWeight * ztop [iright [xDC]] + bottomWeight * zbottom [iright [xDC]]) + leftWeight [xDC] * (topWeight * ztop [ileft [xDC]] + bottomWeight * zbottom [ileft [xDC]]); double value = offset - scale * interpol; PUT_PIXEL } } } } catch (MelderError) { } } else { try { autoNUMvector ix (clipx1, clipx2); for (xDC = clipx1; xDC < clipx2; xDC += undersampling) ix [xDC] = floor (ix1 + (nx * (xDC - x1DC)) / (x2DC - x1DC)); for (yDC = clipy2; yDC < clipy1; yDC += undersampling) { long iy = ceil (iy2 - (ny * (yDC - y2DC)) / (y1DC - y2DC)); unsigned char *pixelAddress = ROW_START_ADDRESS; Melder_assert (iy >= iy1 && iy <= iy2); if (z_float) { double *ziy = z_float [iy]; for (xDC = clipx1; xDC < clipx2; xDC += undersampling) { double value = offset - scale * ziy [ix [xDC]]; PUT_PIXEL } } else { unsigned char *ziy = z_byte [iy]; for (xDC = clipx1; xDC < clipx2; xDC += undersampling) { double value = offset - scale * ziy [ix [xDC]]; PUT_PIXEL } } } } catch (MelderError) { } } /* * Copy the bitmap to the screen. */ #if cairo cairo_matrix_t clip_trans; cairo_matrix_init_identity (& clip_trans); cairo_matrix_scale (& clip_trans, 1, -1); // we painted in the reverse y-direction cairo_matrix_translate (& clip_trans, - clipx1, - clipy1); cairo_pattern_t *bitmap_pattern = cairo_pattern_create_for_surface (sfc); if (Melder_debug == 36) Melder_casual ("bitmap pattern %ld", bitmap_pattern); if (cairo_status_t status = cairo_pattern_status (bitmap_pattern)) { Melder_casual ("bitmap pattern status: %s", cairo_status_to_string (status)); } else { cairo_pattern_set_matrix (bitmap_pattern, & clip_trans); cairo_save (my d_cairoGraphicsContext); cairo_set_source (my d_cairoGraphicsContext, bitmap_pattern); cairo_paint (my d_cairoGraphicsContext); cairo_restore (my d_cairoGraphicsContext); } cairo_pattern_destroy (bitmap_pattern); #elif win SetDIBitsToDevice (my d_gdiGraphicsContext, clipx1, clipy2, bitmapWidth, bitmapHeight, 0, 0, 0, bitmapHeight, bits, (CONST BITMAPINFO *) & bitmapInfo, DIB_RGB_COLORS); #elif mac CGImageRef image; CGColorSpaceRef colourSpace = CGColorSpaceCreateWithName (kCGColorSpaceGenericRGB); // used to be kCGColorSpaceUserRGB Melder_assert (colourSpace != NULL); if (1) { CGDataProviderRef dataProvider = CGDataProviderCreateWithData (NULL, imageData, bytesPerRow * numberOfRows, _mac_releaseDataCallback // we need this because we cannot release the image data immediately after drawing, // because in PDF files the imageData has to stay available through EndPage ); Melder_assert (dataProvider != NULL); image = CGImageCreate (clipx2 - clipx1, numberOfRows, 8, 32, bytesPerRow, colourSpace, kCGImageAlphaNone, dataProvider, NULL, false, kCGRenderingIntentDefault); CGDataProviderRelease (dataProvider); } else if (0) { Melder_assert (CGBitmapContextCreate != NULL); CGContextRef bitmaptest = CGBitmapContextCreate (imageData, 100, 100, 8, 800, colourSpace, 0); Melder_assert (bitmaptest != NULL); CGContextRef bitmap = CGBitmapContextCreate (NULL/*imageData*/, clipx2 - clipx1, numberOfRows, 8, bytesPerRow, colourSpace, kCGImageAlphaLast); Melder_assert (bitmap != NULL); image = CGBitmapContextCreateImage (bitmap); // release bitmap? } Melder_assert (image != NULL); GraphicsQuartz_initDraw (me); CGContextDrawImage (my d_macGraphicsContext, CGRectMake (clipx1, clipy2, clipx2 - clipx1, clipy1 - clipy2), image); GraphicsQuartz_exitDraw (me); CGColorSpaceRelease (colourSpace); CGImageRelease (image); #endif /* * Clean up. */ #if cairo cairo_surface_destroy (sfc); #elif win DeleteBitmap (bitmap); #endif } #if win end: return; #endif } static void _GraphicsPostscript_cellArrayOrImage (GraphicsPostscript me, double **z_float, unsigned char **z_byte, long ix1, long ix2, long x1DC, long x2DC, long iy1, long iy2, long y1DC, long y2DC, double minimum, double maximum, long clipx1, long clipx2, long clipy1, long clipy2, int interpolate) { long interpolateX = 1, interpolateY = 1; long nx = ix2 - ix1 + 1, ny = iy2 - iy1 + 1, filling = 0; double scale = ( my photocopyable ? 200.1f : 255.1f ) / (maximum - minimum); double offset = 255.1f + minimum * scale; int minimalGrey = my photocopyable ? 55 : 0; my d_printf (my d_file, "gsave N %ld %ld M %ld %ld L %ld %ld L %ld %ld L closepath clip\n", clipx1, clipy1, clipx2 - clipx1, 0L, 0L, clipy2 - clipy1, clipx1 - clipx2, 0L); my d_printf (my d_file, "%ld %ld translate %ld %ld scale\n", x1DC, y1DC, x2DC - x1DC, y2DC - y1DC); if (interpolate) { /* The smallest image resolution is 300 dpi. If a sample takes up more than 25.4/300 mm, the 300 dpi resolution is achieved by interpolation. */ const double smallestImageResolution = 300.0; double colSize_pixels = (double) (x2DC - x1DC) / nx; double rowSize_pixels = (double) (y2DC - y1DC) / ny; double colSize_inches = colSize_pixels / my resolution; double rowSize_inches = rowSize_pixels / my resolution; interpolateX = ceil (colSize_inches * smallestImageResolution); // number of interpolation points per horizontal sample interpolateY = ceil (rowSize_inches * smallestImageResolution); // number of interpolation points per vertical sample } if (interpolateX <= 1 && interpolateY <= 1) { /* Do not interpolate. */ my d_printf (my d_file, "/picstr %ld string def %ld %ld 8 [%ld 0 0 %ld 0 0]\n" "{ currentfile picstr readhexstring pop } image\n", nx, nx, ny, nx, ny); } else if (interpolateX > 1 && interpolateY > 1) { /* Interpolate both horizontally and vertically. */ long nx_new = nx * interpolateX; long ny_new = ny * interpolateY; /* Interpolation between rows requires us to remember two original rows: */ my d_printf (my d_file, "/lorow %ld string def /hirow %ld string def\n", nx, nx); /* New rows (scanlines) are longer: */ my d_printf (my d_file, "/scanline %ld string def\n", nx_new); /* The first four arguments to the 'image' command, /* namely the new number of columns, the new number of rows, the bit depth, and the matrix: */ my d_printf (my d_file, "%ld %ld 8 [%ld 0 0 %ld 0 0]\n", nx_new, ny_new, nx_new, ny_new); /* Since our imageproc is going to output only one scanline at a time, */ /* the outer loop variable (scanline number) has to be initialized outside the imageproc: */ my d_printf (my d_file, "/irow 0 def\n"); /* The imageproc starts here. First, we fill one or two original rows if necessary; */ /* they are read as hexadecimal strings from the current file, i.e. just after the image command. */ my d_printf (my d_file, "{\n" /* First test: are we in the first scanline? If so, read two original rows: */ "irow 0 eq { currentfile lorow readhexstring pop pop lorow hirow copy pop } if\n" /* Second test: did we just pass an original data row? */ /* If so, */ /* (1) move that row backwards; */ /* (2) read a new one unless we just passed the last original row: */ "irow %ld mod %ld eq { hirow lorow copy pop\n" "irow %ld ne { currentfile hirow readhexstring pop pop } if } if\n", interpolateY, interpolateY / 2, ny_new - interpolateY + interpolateY / 2); /* Where are we between those two rows? */ my d_printf (my d_file, "/rowphase irow %ld add %ld mod %ld div def\n", interpolateY - interpolateY / 2, interpolateY, interpolateY); /* Inner loop starts here. It cycles through all new columns: */ my d_printf (my d_file, "0 1 %ld {\n", nx_new - 1); /* Get the inner loop variable: */ my d_printf (my d_file, " /icol exch def\n"); /* Where are the two original columns? */ my d_printf (my d_file, " /locol icol %ld sub %ld idiv def\n", interpolateX / 2, interpolateX); my d_printf (my d_file, " /hicol icol %ld ge { %ld } { icol %ld add %ld idiv } ifelse def\n", nx_new - interpolateX / 2, nx - 1, interpolateX / 2, interpolateX); /* Where are we between those two columns? */ my d_printf (my d_file, " /colphase icol %ld add %ld mod %ld div def\n", interpolateX - interpolateX / 2, interpolateX, interpolateX); /* Four-point interpolation: */ my d_printf (my d_file, " /plow lorow locol get def\n" " /phigh lorow hicol get def\n" " /qlow hirow locol get def\n" " /qhigh hirow hicol get def\n" " /value\n" " plow phigh plow sub colphase mul add 1 rowphase sub mul\n" " qlow qhigh qlow sub colphase mul add rowphase mul\n" " add def\n" " scanline icol value 0 le { 0 } { value 255 ge { 255 } { value } ifelse } ifelse cvi put\n" "} for\n" "/irow irow 1 add def scanline } image\n"); } else if (interpolateX > 1) { /* Interpolate horizontally only. */ long nx_new = nx * interpolateX; /* Remember one original row: */ my d_printf (my d_file, "/row %ld string def\n", nx, nx); /* New rows (scanlines) are longer: */ my d_printf (my d_file, "/scanline %ld string def\n", nx_new); /* The first four arguments to the 'image' command, /* namely the new number of columns, the number of rows, the bit depth, and the matrix: */ my d_printf (my d_file, "%ld %ld 8 [%ld 0 0 %ld 0 0]\n", nx_new, ny, nx_new, ny); /* The imageproc starts here. We fill one original row. */ my d_printf (my d_file, "{\n" "currentfile row readhexstring pop pop\n"); /* Loop starts here. It cycles through all new columns: */ my d_printf (my d_file, "0 1 %ld {\n", nx_new - 1); /* Get the loop variable: */ my d_printf (my d_file, " /icol exch def\n"); /* Where are the two original columns? */ my d_printf (my d_file, " /locol icol %ld sub %ld idiv def\n", interpolateX / 2, interpolateX); my d_printf (my d_file, " /hicol icol %ld ge { %ld } { icol %ld add %ld idiv } ifelse def\n", nx_new - interpolateX / 2, nx - 1, interpolateX / 2, interpolateX); /* Where are we between those two columns? */ my d_printf (my d_file, " /colphase icol %ld add %ld mod %ld div def\n", interpolateX - interpolateX / 2, interpolateX, interpolateX); /* Two-point interpolation: */ my d_printf (my d_file, " /plow row locol get def\n" " /phigh row hicol get def\n" " /value plow phigh plow sub colphase mul add def\n" " scanline icol value 0 le { 0 } { value 255 ge { 255 } { value } ifelse } ifelse cvi put\n" "} for\n" "scanline } image\n"); } else { /* Interpolate vertically only. */ long ny_new = ny * interpolateY; /* Interpolation between rows requires us to remember two original rows: */ my d_printf (my d_file, "/lorow %ld string def /hirow %ld string def\n", nx, nx); /* New rows (scanlines) are equally long: */ my d_printf (my d_file, "/scanline %ld string def\n", nx); /* The first four arguments to the 'image' command, /* namely the number of columns, the new number of rows, the bit depth, and the matrix: */ my d_printf (my d_file, "%ld %ld 8 [%ld 0 0 %ld 0 0]\n", nx, ny_new, nx, ny_new); /* Since our imageproc is going to output only one scanline at a time, */ /* the outer loop variable (scanline number) has to be initialized outside the imageproc: */ my d_printf (my d_file, "/irow 0 def\n"); /* The imageproc starts here. First, we fill one or two original rows if necessary; */ /* they are read as hexadecimal strings from the current file, i.e. just after the image command. */ my d_printf (my d_file, "{\n" /* First test: are we in the first scanline? If so, read two original rows: */ "irow 0 eq { currentfile lorow readhexstring pop pop lorow hirow copy pop } if\n" /* Second test: did we just pass an original data row? */ /* If so, */ /* (1) move that row backwards; */ /* (2) read a new one unless we just passed the last original row: */ "irow %ld mod %ld eq { hirow lorow copy pop\n" "irow %ld ne { currentfile hirow readhexstring pop pop } if } if\n", interpolateY, interpolateY / 2, ny_new - interpolateY + interpolateY / 2); /* Where are we between those two rows? */ my d_printf (my d_file, "/rowphase irow %ld add %ld mod %ld div def\n", interpolateY - interpolateY / 2, interpolateY, interpolateY); /* Inner loop starts here. It cycles through all columns: */ my d_printf (my d_file, "0 1 %ld {\n", nx - 1); /* Get the inner loop variable: */ my d_printf (my d_file, " /icol exch def\n"); /* Two-point interpolation: */ my d_printf (my d_file, " /p lorow icol get def\n" " /q hirow icol get def\n" " /value\n" " p 1 rowphase sub mul\n" " q rowphase mul\n" " add def\n" " scanline icol value 0 le { 0 } { value 255 ge { 255 } { value } ifelse } ifelse cvi put\n" "} for\n" "/irow irow 1 add def scanline } image\n"); } for (long iy = iy1; iy <= iy2; iy ++) for (long ix = ix1; ix <= ix2; ix ++) { int value = (int) (offset - scale * ( z_float ? z_float [iy] [ix] : z_byte [iy] [ix] )); my d_printf (my d_file, "%.2x", value <= minimalGrey ? minimalGrey : value >= 255 ? 255 : value); if (++ filling == 39) { my d_printf (my d_file, "\n"); filling = 0; } } if (filling) my d_printf (my d_file, "\n"); my d_printf (my d_file, "grestore\n"); } static void _cellArrayOrImage (Graphics me, double **z_float, unsigned char **z_byte, long ix1, long ix2, long x1DC, long x2DC, long iy1, long iy2, long y1DC, long y2DC, double minimum, double maximum, long clipx1, long clipx2, long clipy1, long clipy2, int interpolate) { if (my screen) { _GraphicsScreen_cellArrayOrImage (static_cast (me), z_float, z_byte, ix1, ix2, x1DC, x2DC, iy1, iy2, y1DC, y2DC, minimum, maximum, clipx1, clipx2, clipy1, clipy2, interpolate); } else if (my postScript) { _GraphicsPostscript_cellArrayOrImage (static_cast (me), z_float, z_byte, ix1, ix2, x1DC, x2DC, iy1, iy2, y1DC, y2DC, minimum, maximum, clipx1, clipx2, clipy1, clipy2, interpolate); } _Graphics_setColour (me, my colour); } static void cellArrayOrImage (I, double **z_float, unsigned char **z_byte, long ix1, long ix2, double x1WC, double x2WC, long iy1, long iy2, double y1WC, double y2WC, double minimum, double maximum, int interpolate) { iam (Graphics); if (ix2 < ix1 || iy2 < iy1 || minimum == maximum) return; _cellArrayOrImage (me, z_float, z_byte, ix1, ix2, wdx (x1WC), wdx (x2WC), iy1, iy2, wdy (y1WC), wdy (y2WC), minimum, maximum, wdx (my d_x1WC), wdx (my d_x2WC), wdy (my d_y1WC), wdy (my d_y2WC), interpolate); if (my recording) { long nrow = iy2 - iy1 + 1, ncol = ix2 - ix1 + 1, ix, iy; op (interpolate ? ( z_float ? IMAGE : IMAGE8 ) : (z_float ? CELL_ARRAY : CELL_ARRAY8 ), 8 + nrow * ncol); put (x1WC); put (x2WC); put (y1WC); put (y2WC); put (minimum); put (maximum); put (nrow); put (ncol); if (z_float) for (iy = iy1; iy <= iy2; iy ++) { double *row = z_float [iy]; for (ix = ix1; ix <= ix2; ix ++) put (row [ix]); } else for (iy = iy1; iy <= iy2; iy ++) { unsigned char *row = z_byte [iy]; for (ix = ix1; ix <= ix2; ix ++) put (row [ix]); } } } void Graphics_cellArray (Graphics me, double **z, long ix1, long ix2, double x1WC, double x2WC, long iy1, long iy2, double y1WC, double y2WC, double minimum, double maximum) { cellArrayOrImage (me, z, NULL, ix1, ix2, x1WC, x2WC, iy1, iy2, y1WC, y2WC, minimum, maximum, FALSE); } void Graphics_cellArray8 (Graphics me, unsigned char **z, long ix1, long ix2, double x1WC, double x2WC, long iy1, long iy2, double y1WC, double y2WC, unsigned char minimum, unsigned char maximum) { cellArrayOrImage (me, NULL, z, ix1, ix2, x1WC, x2WC, iy1, iy2, y1WC, y2WC, minimum, maximum, FALSE); } void Graphics_image (Graphics me, double **z, long ix1, long ix2, double x1WC, double x2WC, long iy1, long iy2, double y1WC, double y2WC, double minimum, double maximum) { cellArrayOrImage (me, z, NULL, ix1, ix2, x1WC, x2WC, iy1, iy2, y1WC, y2WC, minimum, maximum, TRUE); } void Graphics_image8 (Graphics me, unsigned char **z, long ix1, long ix2, double x1WC, double x2WC, long iy1, long iy2, double y1WC, double y2WC, unsigned char minimum, unsigned char maximum) { cellArrayOrImage (me, NULL, z, ix1, ix2, x1WC, x2WC, iy1, iy2, y1WC, y2WC, minimum, maximum, TRUE); } static void _GraphicsScreen_imageFromFile (GraphicsScreen me, const wchar *relativeFileName, double x1, double x2, double y1, double y2) { long x1DC = wdx (x1), x2DC = wdx (x2), y1DC = wdy (y1), y2DC = wdy (y2); long width = x2DC - x1DC, height = my yIsZeroAtTheTop ? y1DC - y2DC : y2DC - y1DC; #if win if (my d_useGdiplus) { structMelderFile file; Melder_relativePathToFile (relativeFileName, & file); Gdiplus::Image image (file. path); Gdiplus::Graphics dcplus (my d_gdiGraphicsContext); if (x1 == x2 && y1 == y2) { width = image. GetWidth (), x1DC -= width / 2, x2DC = x1DC + width; height = image. GetHeight (), y2DC -= height / 2, y1DC = y2DC + height; } else if (x1 == x2) { width = height * (double) image. GetWidth () / (double) image. GetHeight (); x1DC -= width / 2, x2DC = x1DC + width; } else if (y1 == y2) { height = width * (double) image. GetHeight () / (double) image. GetWidth (); y2DC -= height / 2, y1DC = y2DC + height; } Gdiplus::Rect rect (x1DC, y2DC, width, height); dcplus.DrawImage (& image, rect); } #elif mac structMelderFile file; Melder_relativePathToFile (relativeFileName, & file); char utf8 [500]; Melder_wcsTo8bitFileRepresentation_inline (file. path, utf8); CFStringRef path = CFStringCreateWithCString (NULL, utf8, kCFStringEncodingUTF8); CFURLRef url = CFURLCreateWithFileSystemPath (NULL, path, kCFURLPOSIXPathStyle, false); CFRelease (path); CGImageSourceRef imageSource = CGImageSourceCreateWithURL (url, NULL); //CGDataProviderRef dataProvider = CGDataProviderCreateWithURL (url); CFRelease (url); if (imageSource != NULL) { //if (dataProvider != NULL) { CGImageRef image = CGImageSourceCreateImageAtIndex (imageSource, 0, NULL); //CGImageRef image = CGImageCreateWithJPEGDataProvider (dataProvider, NULL, true, kCGRenderingIntentDefault); CFRelease (imageSource); //CGDataProviderRelease (dataProvider); if (image != NULL) { if (x1 == x2 && y1 == y2) { width = CGImageGetWidth (image), x1DC -= width / 2, x2DC = x1DC + width; height = CGImageGetHeight (image), y2DC -= height / 2, y1DC = y2DC + height; } else if (x1 == x2) { width = height * (double) CGImageGetWidth (image) / (double) CGImageGetHeight (image); x1DC -= width / 2, x2DC = x1DC + width; } else if (y1 == y2) { height = width * (double) CGImageGetHeight (image) / (double) CGImageGetWidth (image); y2DC -= height / 2, y1DC = y2DC + height; } GraphicsQuartz_initDraw (me); CGContextSaveGState (my d_macGraphicsContext); CGContextTranslateCTM (my d_macGraphicsContext, 0, y1DC); CGContextScaleCTM (my d_macGraphicsContext, 1.0, -1.0); CGContextDrawImage (my d_macGraphicsContext, CGRectMake (x1DC, 0, width, height), image); CGContextRestoreGState (my d_macGraphicsContext); GraphicsQuartz_exitDraw (me); CGImageRelease (image); } } #endif } void Graphics_imageFromFile (Graphics me, const wchar *relativeFileName, double x1, double x2, double y1, double y2) { if (my screen) { _GraphicsScreen_imageFromFile (static_cast (me), relativeFileName, x1, x2, y1, y2); } if (my recording) { char *txt_utf8 = Melder_peekWcsToUtf8 (relativeFileName); int length = strlen (txt_utf8) / sizeof (double) + 1; op (IMAGE_FROM_FILE, 5 + length); put (x1); put (x2); put (y1); put (y2); sput (txt_utf8, length) } } /* End of file Graphics_image.cpp */ sources_5316/sys/motifEmulator.cpp0000644000176700017670000054135411753754311016117 0ustar paulpaul/* motifEmulator.cpp * * Copyright (C) 1993-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2002/10/12 external definition of availability of Appearance * pb 2003/11/02 Mac: if the delete response is UNMAP, call XtUnmanageChild rather than just HideWindow * (makes a difference if a warning message is clicked away through the GoAway button) * pb 2003/11/28 Mac: set the above back to just HideWindow plus clearing the modal-dialog and active-text pointers * pb 2003/11/28 Win: did the same for Windows! * (this solved an age old bug in Praat by which the picture window could not be closed twice) * pb 2004/01/01 extracted text handling to GuiText.c * pb 2004/02/28 MacOS X: used SetControlMaximum (32767) to work around MacOS X feature in setting popup control * pb 2004/11/24 separated labels from cascade buttons * pb 2005/09/01 assume that we have Appearance (i.e. System 8.5 or up) * pb 2006/08/07 Windows: remove quotes from around path names when calling the openDocument callback * pb 2006/10/28 erased MacOS 9 stuff * pb 2006/11/06 Carbon control creation functions * pb 2007/01/25 XmATTACH_POSITION * pb 2007/02/13 Win: removed Ctrl-. as meaning Escape * pb 2007/08/07 GuiMacDrawingArea_clipOn_graphicsContext * pb 2007/10/06 wchar_t * pb 2007/10/16 Unicode support in lists * pb 2007/12/15 userData * pb 2007/12/26 extractions to Gui*.c * pb 2007/12/30 extractions to Gui*.c * pb 2008/10/05 better tab navigation * pb 2010/01/04 Mac: implement forward delete * pb 2010/01/08 Mac: support Command-` * pb 2010/06/14 Mac: live scrolling * pb 2010/07/30 Mac: in calling CreatePopupButtonControl, have -12345 as the menu item * (Apple's special number for delayed menu attachment); needed for stand-alone Praat demo window * pb 2011/04/06 C++ */ #if defined (macintosh) && useCarbon || defined (_WIN32) /* The Motif emulator for Macintosh and Windows. */ #define PRAAT_WINDOW_CLASS_NUMBER 1 #include #include #include #include #include #include #include "melder.h" #include "GuiP.h" #include "machine.h" #if win #define SCROLL32 1 #else #define SCROLL32 0 #endif #if mac #include "macport_on.h" #include #endif /* * The MEMBER macros only work if klas1 etc are no macros themselves. * Therefore, we undefine those who are: */ #if win #undef MessageBox #endif #define _motif_SHIFT_MASK 1 #define _motif_COMMAND_MASK 2 #define _motif_OPTION_MASK 4 #if mac void motif_mac_defaultFont (void) { TextFont (systemFont); TextSize (13); TextFace (0); } static BitMap theScreenBits; #endif /* The following variable controls the focus policy of Mac Motif. * The Macintosh focus policy is: there is only one active window at a time, * and a click on an inactive window causes that window to become active, * without responding any further to that click. * This is appropriate for small screens, where multiple windows are usually stacked * on top of one another, and only a small part of background windows is visible. * The Motif focus policy is: all windows are active, and a click in any window causes * that window to respond as if it were in front. * This is appropriate for large screens, where multiple windows are often tiled about the screen. * One of the purposes of Mac Motif is to produce Macintosh look-and-feel, * which would require the Macintosh focus policy, * but as Macintosh screens are growing larger, you might prefer the faster Motif focus policy, * if your screen is large. * Therefore, you can choose: */ static const int BACKGROUND_WINDOWS_ARE_ACTIVE = 0; /* 0 = Mac, 1 = Motif. */ #if win #define CELL_HEIGHT 15 #define MESSAGE_BOX_BUTTON_WIDTH 100 #elif mac static int USE_QUESTION_MARK_HELP_MENU = 0; #define CELL_HEIGHT 16 #define MESSAGE_BOX_BUTTON_WIDTH 120 #endif #if win static void _motif_update (GuiObject me, void *event); #elif mac static void _motif_update (GuiObject me, EventRecord *event); #endif /********** Resource names. **********/ #define motif_RESOURCE(xxx) #xxx, static const char *motif_resourceNames [] = { "XmNnull", #include "motifEmulator_resources.h" "XmNend" }; #undef motif_RESOURCE /* Modes. */ struct Gui theGui; /* Global variable. */ /********** XWindows routines. **********/ void XMapRaised (int displayDummy, Window window) { (void) displayDummy; #if win ShowWindow ((HWND) window, SW_SHOW); SetForegroundWindow ((HWND) window); #elif mac ShowWindow ((WindowPtr) window); if (theGui.modalDialog && theGui.modalDialog != (WindowPtr) window) { SendBehind ((WindowPtr) window, theGui.modalDialog); } else { SelectWindow ((WindowPtr) window); } #endif } int WidthOfScreen (int screen) { (void) screen; #if win return GetSystemMetrics (SM_CXMAXIMIZED); #elif mac return GetQDGlobalsScreenBits (& theScreenBits) -> bounds.right; #endif } int HeightOfScreen (int screen) { (void) screen; #if win return GetSystemMetrics (SM_CYMAXIMIZED); #elif mac return GetQDGlobalsScreenBits (& theScreenBits) -> bounds.bottom - 22; #endif } /********** X Toolkit **********/ void _Gui_callCallbacks (GuiObject w, XtCallbackList *callbacks, XtPointer call) { int i; for (i = 0; i < MAXNUM_CALLBACKS; i ++) if (callbacks -> pairs [i]. proc) callbacks -> pairs [i]. proc (w, callbacks -> pairs [i]. closure, call); } /* Scratch. */ #if mac static Str255 mac_text; #endif /* Convenience. */ #if mac #define PfromCstr(p,c) p [0] = strlen (c), strcpy ((char *) p + 1, c); #endif /* When dispatching events to widgets, we must translate from the identifier of a Macintosh * screen object (Window, Control, menu item) to a GuiObject. * Mac windows and controls have RefCon fields in their WindowRecord or ControlRecord, * so we put a reference to the widget in the appropriate RefCon field at window or control creation time. * Instead of RefCons, the menus are remembered here: */ #if win #define MAXIMUM_NUMBER_OF_MENUS 4000 #elif mac #define MAXIMUM_NUMBER_OF_MENUS 32767 #endif static GuiObject theMenus [1+MAXIMUM_NUMBER_OF_MENUS]; /* We can freely use and reuse these menu ids */ static void (*theOpenDocumentCallback) (MelderFile file); static int (*theQuitApplicationCallback) (void); #if win static int theCommandShow = False; /* Last argument of WinMain. */ static wchar_t theApplicationName [100], theWindowClassName [100], theDrawingAreaClassName [100], theApplicationClassName [100]; wchar_t * _GuiWin_getDrawingAreaClassName (void) { return theDrawingAreaClassName; } static int (*theUserMessageCallback) (void); #define MINIMUM_MENU_ITEM_ID (MAXIMUM_NUMBER_OF_MENUS + 1) #define MAXIMUM_MENU_ITEM_ID 32767 static short theMenuItems [1+MAXIMUM_MENU_ITEM_ID]; /* We can freely use and reuse the item ids 4001..32767 */ #elif mac static GuiObject theMenuBar; /* There is only one menu bar on the Macintosh. */ static int theHelpMenuOffset; /* The number of items in the global help menu before we add the first item. */ static int (*theUserMessageCallbackA) (char *message); static int (*theUserMessageCallbackW) (wchar_t *message); #endif static GuiObject theApplicationShell; /* For global menus. */ #define MAXIMUM_NUMBER_OF_SHELLS 1000 static GuiObject theShells [MAXIMUM_NUMBER_OF_SHELLS]; /* For XmUpdateDisplay and suspend events. */ static int theBackground = False; /* Set by suspend and resume events; used by Motif-style activation methods. */ static int theDialogHint = False; /* Should the shell that is currently being created, have dialog or document looks? */ long numberOfWidgets = 0; long Gui_getNumberOfMotifWidgets (void) { return numberOfWidgets; } static void _motif_addShell (GuiObject me) { int i; for (i = 0; i < MAXIMUM_NUMBER_OF_SHELLS; i ++) if (theShells [i] == NULL) { theShells [i] = me; break; } } static void _motif_removeShell (GuiObject me) { int i; for (i = 0; i < MAXIMUM_NUMBER_OF_SHELLS; i ++) if (theShells [i] == me) { theShells [i] = NULL; break; } } /* AppContext level */ static int theNumberOfWorkProcs; static XtWorkProc theWorkProcs [10]; static XtPointer theWorkProcClosures [10]; static int theNumberOfTimeOuts; static XtTimerCallbackProc theTimeOutProcs [10]; static XtPointer theTimeOutClosures [10]; #if defined (macintosh) static EventLoopTimerRef theTimers [10]; static EventTargetRef theUserFocusEventTarget; #else static clock_t theTimeOutStarts [10]; static unsigned long theTimeOutIntervals [10]; #endif static void Native_move (GuiObject w, int dx, int dy); /* Forward. */ static void cb_scroll (GuiObject scrollBar, XtPointer closure, XtPointer call) { GuiObject scrolledWindow = (GuiObject) closure; GuiObject workWindow = scrolledWindow -> motiff.scrolledWindow.workWindow; int previousShift, newShift, distance; int horizontal = scrolledWindow -> motiff.scrolledWindow.horizontalBar == scrollBar; (void) call; if (! workWindow) return; Melder_assert (scrolledWindow -> motiff.scrolledWindow.clipWindow != NULL); #if win previousShift = horizontal ? scrolledWindow -> motiff.scrolledWindow.clipWindow -> x - workWindow -> x : scrolledWindow -> motiff.scrolledWindow.clipWindow -> y - workWindow -> y; #elif mac previousShift = horizontal ? scrolledWindow -> motiff.scrolledWindow.clipWindow -> rect. left - workWindow -> rect. left : scrolledWindow -> motiff.scrolledWindow.clipWindow -> rect. top - workWindow -> rect. top; /* different? */ #endif newShift = scrollBar -> value; distance = previousShift - newShift; if (horizontal) { workWindow -> x += distance; Native_move (workWindow, distance, 0); } else { workWindow -> y += distance; Native_move (workWindow, 0, distance); } XmUpdateDisplay (NULL); /* If dragging. */ } /* These are like the toolkit's query_geometry methods: */ static int Native_titleWidth (GuiObject me) { #if win if (my parent -> window) { HDC dc = GetDC (my parent -> window); SIZE size; SelectFont (dc, GetStockFont (ANSI_VAR_FONT)); /* Possible BUG. */ GetTextExtentPoint32 (dc, my name, wcslen (my name), & size); ReleaseDC (my parent -> window, dc); return size. cx; } else return 7 * wcslen (my name); #elif mac int width; SetPortWindowPort (my macWindow); motif_mac_defaultFont (); char *nameA = Melder_peekWcsToUtf8 (my name); width = TextWidth ((Ptr) nameA, 0, strlen (nameA)); motif_mac_defaultFont (); return width; #endif } static int NativeLabel_preferredWidth (GuiObject me) { return Native_titleWidth (me) + 10; } static int NativeButton_preferredWidth (GuiObject me) { int width = Native_titleWidth (me) + ( win ? 10 : ( my parent -> rowColumnType == XmMENU_BAR ? 10 : 28 ) ); return width < 41 ? 41 : width; } static int NativeToggleButton_preferredWidth (GuiObject me) { return Native_titleWidth (me) + 25; } static int NativeButton_preferredHeight (GuiObject me) { (void) me; return win ? 22 : ( my parent -> rowColumnType == XmMENU_BAR ? 28 : 20 ); } /***** WIDGET *****/ GuiObject _Gui_initializeWidget (int widgetClass, GuiObject parent, const wchar_t *name) { GuiObject me = Melder_calloc_f (struct structGuiObject, 1); if (Melder_debug == 34) fprintf (stderr, "from _Gui_initializeWidget\t%p\t%ld\t%ld\n", me, 1L, (long) sizeof (struct structGuiObject)); my magicNumber = 15111959; numberOfWidgets ++; my widgetClass = widgetClass; my parent = parent; my inMenu = parent && MEMBER (parent, PulldownMenu); /* * Install me into my parent's list of children. */ if (parent == NULL) { ; } else if (parent -> firstChild == NULL) { parent -> firstChild = me; } else { GuiObject lastChild = parent -> firstChild; while (lastChild -> nextSibling) lastChild = lastChild -> nextSibling; lastChild -> nextSibling = me; my previousSibling = lastChild; } /* * Copy the name into my name. */ my name = Melder_wcsdup_f (name); /* * I am in the same shell as my parent, so I inherit my parent's "shell" attribute. */ if (MEMBER (me, Shell)) { my shell = me; } else { my shell = my parent -> shell; #if mac /* * I am in the same shell as my parent, so I'll inherit my parent's Macintosh WindowRef. */ my macWindow = parent -> macWindow; #endif } /* * The remainder of initialization is about positioning, sizes, attachments, and the contents of a scrolled window. * All of that is irrelevant to menu items. */ if (my inMenu) return me; /* Initial defaults: mainly positioning and sizes. */ switch (my widgetClass) { case xmDrawingAreaWidgetClass: { #if win my x = 2; my y = 2; my width = 100; my height = 100; #endif } break; case xmShellWidgetClass: { #if win my x = 20; my y = 3; my width = 30; my height = 50; #elif mac my x = 20; my y = 30; my width = 10; my height = 10; #endif my deleteResponse = XmDESTROY; } break; case xmTextWidgetClass: { my x = 2; my y = 2; my width = 102; my height = Gui_TEXTFIELD_HEIGHT; } break; case xmPushButtonWidgetClass: { my x = 2; my y = 2; my width = NativeButton_preferredWidth (me); my height = Gui_PUSHBUTTON_HEIGHT; } break; case xmLabelWidgetClass: { my x = 2; my y = 2; my width = NativeLabel_preferredWidth (me); my height = Gui_LABEL_HEIGHT; } break; case xmCascadeButtonWidgetClass: { if (my parent -> rowColumnType == XmMENU_BAR) { wchar_t *hyphen = wcsstr (my name, L" -"); if (hyphen) hyphen [2] = '\0'; /* Chop any trailing spaces. */ my x = 2; my y = 2; my width = NativeButton_preferredWidth (me); my height = NativeButton_preferredHeight (me) + 4; /* BUG: menu bar should be large enough. */ } else { my motiff.cascadeButton.inBar = TRUE; } } break; case xmToggleButtonWidgetClass: { my x = 2; my y = 2; my width = NativeToggleButton_preferredWidth (me); my height = Gui_CHECKBUTTON_HEIGHT; } break; case xmSeparatorWidgetClass: { my width = parent -> width; my height = 10; } break; case xmScrollBarWidgetClass: { my width = 16; my height = 100; } break; case xmMenuBarWidgetClass: { my width = 10; my height = 10; } break; case xmRowColumnWidgetClass: { my width = 10; my height = 10; my orientation = XmVERTICAL; } break; case xmScaleWidgetClass: { my width = 300; my height = win ? 25 : 40; } break; case xmFormWidgetClass: { if (MEMBER (parent, Shell)) { /* * The following trick is necessary for forms that contain scroll bars. */ my width = parent -> width; my height = parent -> height; } else { /* * EXPERIMENT: * this relies on a certain sequence in building up a window: from top to bottom. * If the form is inside a RowColumn of a certain width established by a widget * closer to the top, this width will be copied. The height, of course, should not be copied. * See Praat's SoundRecorder for an example. */ my width = parent -> width; my height = 10; } } break; default: { my width = parent -> width; my height = parent -> height; } } /* Some positions depend on parent. */ if (parent) switch (parent -> widgetClass) { case xmFrameWidgetClass: { my x = 1; my y = 1; my width = parent -> width - 2; my height = parent -> height - 2; } break; case xmScrolledWindowWidgetClass: { my x = 1; my y = 1; my width = parent -> width - 17; /* Exact fit: scroll bar (16) plus border (1). */ my height = parent -> height - 17; if (my widgetClass == xmTextWidgetClass) { my width = 3000; my height = 30000; } // BUG: either put in GuiText or erase } } if (my width < 0) my width = 0; if (my height < 0) my height = 0; #if mac /* Determine enclosing rectangle in macwindow co-ordinates. */ if (! MEMBER (me, Shell) && ! MEMBER (my parent, Shell)) { my rect.left = parent -> rect.left + my x; my rect.top = parent -> rect.top + my y; } my rect.right = my rect.left + my width; my rect.bottom = my rect.top + my height; #endif /* Automatic attachment of dialog to parent shell. */ if (MEMBER2 (me, BulletinBoard, Form) && MEMBER (my parent, Shell)) my leftAttachment = my rightAttachment = my topAttachment = my bottomAttachment = XmATTACH_FORM; if (MEMBER (me, CascadeButton) && wcsequ (name, L"Help")) my rightAttachment = XmATTACH_FORM; /* !!!!!! */ /* A child of a scrolled window will be installed as the workWindow of that scrolled window, * except if it is a scroll bar or if the clipWindow does not exist yet. * This is because the creations of the scroll bars and the clip window will also arrive here. * Our XmScrolledWindow creation method always creates two scroll bars and a clip window, * before you can create any other children. */ if (my parent && MEMBER (my parent, ScrolledWindow) && ! MEMBER (me, ScrollBar) && /* 'me' is one of the two scroll bars, or a new one. */ my parent -> motiff.scrolledWindow.clipWindow != NULL) /* 'me' is probably the clip window now. */ my parent -> motiff.scrolledWindow.workWindow = me; /* Install. */ return me; } /********** CLIPPING AND VIEW VALIDATION ROUTINES **********/ #if mac /* These routines use Mac position information only (i.e., the 'rect' attribute). * They do not use Motif position information (i.e., the 'x', 'y', 'width', and 'height' attributes. */ /* The largest possible rect on a Mac, used for "no clip". */ static Rect _motif_wideRect = { -32768, -32768, 32767, 32767 }; static Rect _motif_clipRect; void _GuiMac_clipOnParent (GuiObject me) { /* The 'clipRect' will be the intersection of the rects of all its ancestors, * stopping before a shell and making side steps at scrolled windows. */ GuiObject parent; Rect clipRect = _motif_wideRect; for (parent = my parent; ! MEMBER (parent, Shell); parent = parent -> parent) { Rect *parentRect = & parent -> rect; if (MEMBER (parent, ScrolledWindow)) { if (MEMBER (me, ScrollBar)) { parentRect = & my rect; } else { if (parent -> motiff.scrolledWindow.clipWindow == NULL) return; /* During destruction. */ parentRect = & parent -> motiff.scrolledWindow.clipWindow -> rect; } } if (parentRect -> left > clipRect. left) clipRect. left = parentRect -> left; if (parentRect -> right < clipRect. right) clipRect. right = parentRect -> right; if (parentRect -> top > clipRect. top) clipRect. top = parentRect -> top; if (parentRect -> bottom < clipRect. bottom) clipRect. bottom = parentRect -> bottom; } /*if (MEMBER (me, PushButton) && me == my shell -> defaultButton) clipRect. left -= 3, clipRect. right += 3, clipRect. top -= 3, clipRect. bottom += 3;*/ SetPortWindowPort (my macWindow); ClipRect (& clipRect); _motif_clipRect = clipRect; } void GuiMac_clipOff (void) { ClipRect (& _motif_wideRect); } void _GuiMac_clipOffValid (GuiObject me) { Rect clipRect = _motif_clipRect; if (my rect. left > clipRect. left) clipRect. left = my rect. left; if (my rect. right < clipRect. right) clipRect. right = my rect. right; if (my rect. top > clipRect. top) clipRect. top = my rect. top; if (my rect. bottom < clipRect. bottom) clipRect. bottom = my rect. bottom; SetPortWindowPort (my macWindow); ValidWindowRect (my macWindow, & clipRect); ClipRect (& _motif_wideRect); } void _GuiMac_clipOffInvalid (GuiObject me) { Rect clipRect = _motif_clipRect; if (my rect. left > clipRect. left) clipRect. left = my rect. left; if (my rect. right < clipRect. right) clipRect. right = my rect. right; if (my rect. top > clipRect. top) clipRect. top = my rect. top; if (my rect. bottom < clipRect. bottom) clipRect. bottom = my rect. bottom; SetPortWindowPort (my macWindow); InvalWindowRect (my macWindow, & clipRect); ClipRect (& _motif_wideRect); } void GuiMac_clipOn (GuiObject me) { GuiObject parent; Rect clipRect = my rect; for (parent = my parent; ! MEMBER (parent, Shell); parent = parent -> parent) { Rect *parentRect = & parent -> rect; if (MEMBER (parent, ScrolledWindow)) { if (MEMBER (me, ScrollBar)) { parentRect = & my rect; } else { Melder_assert (parent -> motiff.scrolledWindow.clipWindow != NULL); parentRect = & parent -> motiff.scrolledWindow.clipWindow -> rect; } } if (parentRect -> left > clipRect. left) clipRect. left = parentRect -> left; if (parentRect -> right < clipRect. right) clipRect. right = parentRect -> right; if (parentRect -> top > clipRect. top) clipRect. top = parentRect -> top; if (parentRect -> bottom < clipRect. bottom) clipRect. bottom = parentRect -> bottom; } SetPortWindowPort (my macWindow); ClipRect (& clipRect); } int GuiMac_clipOn_graphicsContext (GuiObject me, void *graphicsContext) { GuiObject parent; Rect clipRect = my rect; for (parent = my parent; ! MEMBER (parent, Shell); parent = parent -> parent) { Rect *parentRect = & parent -> rect; if (MEMBER (parent, ScrolledWindow)) { if (MEMBER (me, ScrollBar)) { parentRect = & my rect; } else { Melder_assert (parent -> motiff.scrolledWindow.clipWindow != NULL); parentRect = & parent -> motiff.scrolledWindow.clipWindow -> rect; } } if (parentRect -> left > clipRect. left) clipRect. left = parentRect -> left; if (parentRect -> right < clipRect. right) clipRect. right = parentRect -> right; if (parentRect -> top > clipRect. top) clipRect. top = parentRect -> top; if (parentRect -> bottom < clipRect. bottom) clipRect. bottom = parentRect -> bottom; } CGContextClipToRect ((CGContextRef) graphicsContext, CGRectMake (clipRect.left, my shell -> height - clipRect.bottom, clipRect.right - clipRect.left, clipRect.bottom - clipRect.top)); return my shell -> height; } #endif /***** NATIVE *****/ void _GuiNativeControl_check (GuiObject me, Boolean value) { #if win Button_SetCheck (my window, value ? BST_CHECKED : BST_UNCHECKED); #elif mac SetControlValue (my nat.control.handle, value); #endif } void _GuiNativeControl_destroy (GuiObject me) { #if win DestroyWindow (my window); #elif mac _GuiMac_clipOnParent (me); DisposeControl (my nat.control.handle); GuiMac_clipOff (); #endif } void _GuiNativeControl_show (GuiObject me) { #if win ShowWindow (my window, SW_SHOW); #elif mac _GuiMac_clipOnParent (me); if (IsControlVisible (my nat.control.handle)) Draw1Control (my nat.control.handle); else ShowControl (my nat.control.handle); _GuiMac_clipOffValid (me); #endif } void _GuiNativeControl_hide (GuiObject me) { #if win ShowWindow (my window, SW_HIDE); #elif mac _GuiMac_clipOnParent (me); HideControl (my nat.control.handle); _GuiMac_clipOffValid (me); #endif } void _GuiNativeControl_setFont (GuiObject me, int style, int size) { #if win #elif mac ControlFontStyleRec fontStyle; fontStyle. flags = kControlUseFontMask | kControlUseFaceMask | kControlUseSizeMask; fontStyle. font = systemFont; fontStyle. style = style; fontStyle. size = size; SetControlFontStyle (my nat.control.handle, & fontStyle); #endif } void _GuiNativeControl_setSensitive (GuiObject me) { #if win EnableWindow (my window, ! my insensitive); #elif mac _GuiMac_clipOnParent (me); HiliteControl (my nat.control.handle, my insensitive ? 255 : 0); GuiMac_clipOff (); #endif } wchar_t * _GuiWin_expandAmpersands (const wchar_t *title) { static wchar_t buffer [300]; const wchar_t *from = title; wchar_t *to = & buffer [0]; while (*from) { if (*from == '&') * to ++ = '&'; * to ++ = * from ++; } * to = '\0'; return buffer; } void _GuiNativeControl_setTitle (GuiObject me) { #if win HDC dc = GetDC (my window); SelectPen (dc, GetStockPen (NULL_PEN)); SelectBrush (dc, GetStockBrush (LTGRAY_BRUSH)); Rectangle (dc, 0, 0, my width, my height); ReleaseDC (my window, dc); SetWindowText (my window, _GuiWin_expandAmpersands (my name)); #elif mac Melder_assert (my nat.control.handle); if (my widgetClass == xmLabelWidgetClass) { /* * Static Text controls on the Mac do not understand SetControlTitle. */ CFStringRef cfString = (CFStringRef) Melder_peekWcsToCfstring (my name); SetControlData (my nat.control.handle, kControlEntireControl, kControlStaticTextCFStringTag, sizeof (CFStringRef), & cfString); /* SetControlData does not redraw the control. */ if (IsControlVisible (my nat.control.handle)) Draw1Control (my nat.control.handle); } else if (my nat.control.isPopup) { GuiObject menu = my subMenuId, item; if (menu) for (item = menu -> firstChild; item; item = item -> nextSibling) { if (wcsequ (item -> name, my name)) { SetControlValue (my nat.control.handle, item -> nat.entry.item); return; } } SetControlValue (my nat.control.handle, 0); } else { SetControlTitleWithCFString (my nat.control.handle, (CFStringRef) Melder_peekWcsToCfstring (my name)); } #endif } static int _XmScrollBar_check (GuiObject me) { if (my maximum < my minimum) Melder_warning ("XmScrollBar: maximum (", my maximum, ") less than minimum (", my minimum, ")."); else if (my sliderSize > my maximum - my minimum) Melder_warning ("XmScrollBar: slider size (", my sliderSize, ") greater than maximum (", my maximum, ") minus minimum (", my minimum, ")."); else if (my value < my minimum) Melder_warning ("XmScrollBar: value (", my value, ") less than minimum (", my minimum, ")."); else if (my value > my maximum - my sliderSize) Melder_warning ("XmScrollBar: value (", my value, ") greater than maximum (", my maximum, ") minus slider size (", my sliderSize, ")."); else return 1; return 0; } static void NativeScrollBar_set (GuiObject me) { if (! _XmScrollBar_check (me)) return; #if win { SCROLLINFO scrollInfo; scrollInfo. cbSize = sizeof (SCROLLINFO); scrollInfo. fMask = SIF_RANGE | SIF_PAGE | SIF_POS | SIF_DISABLENOSCROLL; #if SCROLL32 if (my maximum == my minimum + my sliderSize) { scrollInfo. nMin = 0; scrollInfo. nMax = 1; scrollInfo. nPage = 1; scrollInfo. nPos = 0; } else { scrollInfo. nMin = 0; scrollInfo. nMax = 32767; scrollInfo. nPage = (32767.0 * my sliderSize) / (my maximum - my minimum); scrollInfo. nPos = ((32767.0 - scrollInfo. nPage) * (my value - my minimum)) / (my maximum - my minimum - my sliderSize); } #else scrollInfo. nMin = my minimum; scrollInfo. nMax = my maximum; scrollInfo. nPage = my sliderSize; scrollInfo. nPos = my value; #endif if (my window) SetScrollInfo (my window, SB_CTL, & scrollInfo, TRUE); } #elif mac if (! my nat.control.handle) return; SetControl32BitMinimum (my nat.control.handle, my minimum); SetControl32BitMaximum (my nat.control.handle, my maximum - my sliderSize); SetControlViewSize (my nat.control.handle, my sliderSize); SetControl32BitValue (my nat.control.handle, my value); #endif } static void NativeMenuItem_delete (GuiObject me) { #if win RemoveMenu (my nat.entry.handle, my nat.entry.id, MF_BYCOMMAND); #elif mac GuiObject subview; DeleteMenuItem (my nat.entry.handle, my nat.entry.item); for (subview = my parent -> firstChild; subview; subview = subview -> nextSibling) { if (subview -> managed && ! MEMBER (subview, PulldownMenu) && subview -> nat.entry.item > my nat.entry.item) subview -> nat.entry.item -= 1; } my nat.entry.item = 0; #endif } static int NativeMenuItem_getPosition (GuiObject me) { int position = 1; #if win /* * The following routine could also be used for Mac. */ GuiObject sibling; for (sibling = my parent -> firstChild; sibling; sibling = sibling -> nextSibling) { if (sibling == me) break; if (sibling -> managed && ! MEMBER (sibling, PulldownMenu)) position += 1; } /* * Bill Gates counts like 0, 1, 2... */ position -= 1; #elif mac /* * A Macintosh menu item shall know its "item number", * which is its dynamic position in the current shape of the menu. * We can use this item number to make changes and * it will be sent to us by MenuSelect () while we handle a mouse-down message in the menu. * (Regrettably, this item number has to change whenever items are unmanaged * or destroyed elsewhere in the menu.) * Basically, the item number is one higher than the item number of the previous sibling. * * "incremental" means that all previous sibling items must have valid item numbers. */ GuiObject prev = my previousSibling; /* * However, there may also be sibling pulldown menus. These have no item number (the associated cascade buttons have). * Also, unmanaged items are not in the native menu structure, so these have no item number either. */ while (prev && (MEMBER (prev, PulldownMenu) || ! prev -> managed)) prev = prev -> previousSibling; if (prev) { /* Is there a previous managed non-pulldown sibling? */ position = prev -> nat.entry.item + 1; /* Then I must be the next item in the native menu structure. */ } else { /* * I must be the first item in the native menu structure, as far as the application is concerned. * However, if the menu is the system's help menu (the question mark in System 7), * the menu already contains a button called "Show balloon help". */ if (my parent -> nat.menu.id == kHMHelpMenuID) { /* Is this the system help menu? */ if (theHelpMenuOffset == 0) /* Haven't we asked yet for the length of the system help menu? */ theHelpMenuOffset = CountMenuItems (my nat.entry.handle); /* So ask now. */ position = theHelpMenuOffset + 1; /* Then I must be the next item in the native menu structure. */ } else { /* This must be a menu of our own. */ position = 1; /* I must be the first item in the native menu structure. */ } } #endif return position; } static void NativeMenuItem_check (GuiObject me, Boolean value) { #if win if (! my managed) return; CheckMenuItem (my nat.entry.handle, my nat.entry.id, MF_BYCOMMAND | ( value ? MF_CHECKED : MF_UNCHECKED )); #elif mac if (! my nat.entry.item) return; CheckMenuItem (my nat.entry.handle, my nat.entry.item, value); #endif } static void NativeMenuItem_setSensitive (GuiObject me) { #if win if (! my managed) return; EnableMenuItem (my nat.entry.handle, my nat.entry.id, MF_BYCOMMAND | ( my insensitive ? MF_GRAYED : MF_ENABLED )); #elif mac if (! my nat.entry.item) return; if (my insensitive) DisableMenuItem (my nat.entry.handle, my nat.entry.item); else EnableMenuItem (my nat.entry.handle, my nat.entry.item); #endif } static void NativeMenuItem_setText (GuiObject me) { int acc = my motiff.pushButton.acceleratorChar, modifiers = my motiff.pushButton.acceleratorModifiers; #if win static MelderString title = { 0 }; if (acc == 0) { MelderString_copy (& title, _GuiWin_expandAmpersands (my name)); } else { static const wchar_t *keyStrings [256] = { 0, L"<-", L"->", L"Up", L"Down", L"PAUSE", L"Del", L"Ins", L"Backspace", L"Tab", L"LineFeed", L"Home", L"End", L"Enter", L"PageUp", L"PageDown", L"Esc", L"F1", L"F2", L"F3", L"F4", L"F5", L"F6", L"F7", L"F8", L"F9", L"F10", L"F11", L"F12", 0, 0, 0, L"Space", L"!", L"\"", L"#", L"$", L"%", L"&", L"\'", L"(", L")", L"*", L"+", L",", L"-", L".", L"/", L"0", L"1", L"2", L"3", L"4", L"5", L"6", L"7", L"8", L"9", L":", L";", L"<", L"=", L">", L"?", L"@", L"A", L"B", L"C", L"D", L"E", L"F", L"G", L"H", L"I", L"J", L"K", L"L", L"M", L"N", L"O", L"P", L"Q", L"R", L"S", L"T", L"U", L"V", L"W", L"X", L"Y", L"Z", L"[", L"\\", L"]", L"^", L"_", L"`", L"a", L"b", L"c", L"d", L"e", L"f", L"g", L"h", L"i", L"j", L"k", L"l", L"m", L"n", L"o", L"p", L"q", L"r", L"s", L"t", L"u", L"v", L"w", L"x", L"y", L"z", L"{", L"|", L"}", L"~", L"Del", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, L"[", L"]", L",", L"?", L".", L"\\", L";", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, L"-", L"`", L"=", L"\'", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; const wchar_t *keyString = keyStrings [acc] ? keyStrings [acc] : L"???"; MelderString_empty (& title); MelderString_append (&title, _GuiWin_expandAmpersands (my name), L"\t", modifiers & _motif_COMMAND_MASK ? L"Ctrl-" : NULL, modifiers & _motif_OPTION_MASK ? L"Alt-" : NULL, modifiers & _motif_SHIFT_MASK ? L"Shift-" : NULL, keyString); } ModifyMenu (my nat.entry.handle, my nat.entry.id, MF_BYCOMMAND | MF_STRING, my nat.entry.id, title.string); #elif mac static int theGlyphs [1+31] = { 0, kMenuLeftArrowDashedGlyph, kMenuRightArrowDashedGlyph, kMenuUpArrowDashedGlyph, kMenuDownwardArrowDashedGlyph, 0, kMenuDeleteRightGlyph, 0, kMenuDeleteLeftGlyph, kMenuTabRightGlyph, 0, 0, 0, kMenuReturnGlyph, kMenuPageUpGlyph, kMenuPageDownGlyph, kMenuEscapeGlyph, kMenuF1Glyph, kMenuF2Glyph, kMenuF3Glyph, kMenuF4Glyph, kMenuF5Glyph, kMenuF6Glyph, kMenuF7Glyph, kMenuF8Glyph, kMenuF9Glyph, kMenuF10Glyph, kMenuF11Glyph, kMenuF12Glyph, 0, 0, 0 }; SetMenuItemTextWithCFString (my nat.entry.handle, my nat.entry.item, (CFStringRef) Melder_peekWcsToCfstring (my name)); if (acc > 32) { SetItemCmd (my nat.entry.handle, my nat.entry.item, acc); } else { Melder_assert (acc > 0 && acc < 32); SetItemCmd (my nat.entry.handle, my nat.entry.item, ' '); /* Funny that this should be needed. */ SetMenuItemKeyGlyph (my nat.entry.handle, my nat.entry.item, theGlyphs [acc]); } SetMenuItemModifiers (my nat.entry.handle, my nat.entry.item, ( modifiers & _motif_OPTION_MASK ? kMenuOptionModifier : 0 ) + ( modifiers & _motif_SHIFT_MASK ? kMenuShiftModifier : 0 ) + ( modifiers & _motif_COMMAND_MASK ? 0 : kMenuNoCommandModifier )); #endif } /********** **********/ /* * We now create the native objects associated with this widget, * but do not show them on the screen yet (ideally). * A reference must be made from widget to native object and back. * On Mac, we normally use the RefCon fields of the windows and controls. * On Win, we use SetWindowLongPtr (window, GWLP_USERDATA, (LONG_PTR) widget). */ static void _GuiNativizeWidget (GuiObject me) { if (my nativized) return; if (my inMenu) { if (MEMBER (me, PulldownMenu)) { #if win int id; for (id = 1; id <= MAXIMUM_NUMBER_OF_MENUS; id ++) if (! theMenus [id]) break; my nat.menu.id = id; theMenus [my nat.menu.id] = me; /* Instead of UserData fields. */ /* * This will be a hierarchical menu. */ my nat.menu.handle = CreatePopupMenu (); #elif mac int ident; for (ident = 1; ident <= MAXIMUM_NUMBER_OF_MENUS; ident ++) if (! theMenus [ident]) break; my nat.menu.id = ident; theMenus [my nat.menu.id] = me; /* Instead of RefCon fields. */ /* * This will be a hierarchical menu. */ CreateNewMenu (my nat.menu.id, 0, & my nat.menu.handle); SetMenuTitleWithCFString (my nat.menu.handle, (CFStringRef) Melder_peekWcsToCfstring (my name)); InsertMenu (my nat.menu.handle, kInsertHierarchicalMenu); #endif } else { /* * Any menu item (push button, toggle button, or cascade button) shall contain its native parent menu handle. */ my nat.entry.handle = my parent -> nat.menu.handle; #if win { /* * A Windows menu item shall have a shell-unique ID, * which we can use to make changes and * which will be sent to us by the WM_COMMAND message. * This ID should be higher than 4000, in order to be different from the menu IDs. * In our implementation, item IDs are application-unique. */ int id; for (id = MINIMUM_MENU_ITEM_ID; id <= MAXIMUM_MENU_ITEM_ID; id ++) if (! theMenuItems [id]) break; my nat.entry.id = id; // install unique ID theMenuItems [id] = TRUE; } #endif } } else switch (my widgetClass) { case xmBulletinBoardWidgetClass: { #if win my window = CreateWindowEx (0, theWindowClassName, L"bulletinBoard", WS_CHILD | WS_BORDER | WS_CLIPSIBLINGS, my x, my y, my width, my height, my parent -> window, NULL, theGui.instance, NULL); SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); #endif } break; case xmDrawingAreaWidgetClass: Melder_fatal ("Should be implemented in GuiDrawingArea."); break; case xmFormWidgetClass: { #if win my window = CreateWindowEx (0, theWindowClassName, L"form", WS_CHILD | WS_CLIPSIBLINGS, my x, my y, my width, my height, my parent -> window, NULL, theGui.instance, NULL); SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); #endif } break; case xmRowColumnWidgetClass: { #if win my window = CreateWindowEx (0, theWindowClassName, L"rowColumn", WS_CHILD | WS_CLIPSIBLINGS, my x, my y, my width, my height, my parent -> window, NULL, theGui.instance, NULL); SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); #endif } break; case xmListWidgetClass: Melder_fatal ("Should be implemented in GuiList."); break; case xmMenuBarWidgetClass: { #if win if (! my shell -> motiff.shell.isDialog && my shell -> nat.shell.menuBar == NULL && my parent -> widgetClass != xmRowColumnWidgetClass) { HMENU bar = CreateMenu (); SetMenu (my shell -> window, bar); my nat.menu.handle = bar; my shell -> nat.shell.menuBar = me; // does this have to be? } else { my widgetClass = xmRowColumnWidgetClass; /* !!!!!!!!!!!!! */ my orientation = XmHORIZONTAL; my rowColumnType = XmMENU_BAR; my window = CreateWindowEx (0, theWindowClassName, L"rowColumn", WS_CHILD, my x, my y, my width, my height, my parent -> window, NULL, theGui.instance, NULL); SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); } #elif mac /* * The first menu bar that occurs in the application shell, * will be positioned in the Macintosh menu bar. * All other menu bars are at the top of their own windows. * This is Motif style, and only works well for Macintoshes with large screens. */ if ((GuiObject) GetWRefCon (my macWindow) == theApplicationShell && theMenuBar == NULL) { theMenuBar = me; } else { my widgetClass = xmRowColumnWidgetClass; /* !!!!!!!!!!!!! */ my orientation = XmHORIZONTAL; my rowColumnType = XmMENU_BAR; } #endif } break; case xmPulldownMenuWidgetClass: { #if win int id; for (id = 1; id <= MAXIMUM_NUMBER_OF_MENUS; id ++) if (! theMenus [id]) break; my nat.menu.id = id; theMenus [my nat.menu.id] = me; /* Instead of UserData fields. */ if (MEMBER (my parent, MenuBar)) { GuiObject menu; UINT beforeID = -1; my nat.menu.handle = CreatePopupMenu (); /* * Insert the menu before the Help menu, if that exists; otherwise, at the end. */ for (menu = my parent -> firstChild; menu != NULL; menu = menu -> nextSibling) { if (MEMBER (menu, PulldownMenu) && wcsequ (menu -> name, L"Help") && menu != me) { beforeID = (UINT) menu -> nat.menu./*handle*/id; break; } } { MENUITEMINFO info; info. cbSize = sizeof (MENUITEMINFO); info. fMask = MIIM_TYPE | MIIM_SUBMENU | MIIM_ID; info. fType = MFT_STRING | ( wcsequ (my name, L"Help") ? MFT_RIGHTJUSTIFY : 0 ); info. dwTypeData = my name; info. hSubMenu = my nat.menu.handle; info. wID = (UINT) my nat.menu./*handle*/id; InsertMenuItem (my parent -> nat.menu.handle, beforeID, 0, & info); } /*else if (beforeID >= 0) InsertMenu (my parent -> nat.menu.handle, beforeID, MF_STRING | MF_POPUP | MF_BYCOMMAND, (UINT) my nat.menu.handle, my name); else AppendMenu (my parent -> nat.menu.handle, MF_STRING | MF_POPUP, (UINT) my nat.menu.handle, my name);*/ DrawMenuBar (my shell -> window); } else if (MEMBER (my parent, RowColumn) && my parent -> rowColumnType == XmMENU_BAR) { my nat.menu.handle = CreatePopupMenu (); } #elif mac int ident; for (ident = 1; ident <= MAXIMUM_NUMBER_OF_MENUS; ident ++) if (! theMenus [ident]) break; my nat.menu.id = ident; theMenus [my nat.menu.id] = me; /* Instead of RefCon fields. */ if (MEMBER (my parent, MenuBar)) { /* * This will be a menu in the Macintosh menu bar. */ if (USE_QUESTION_MARK_HELP_MENU && wcsequ (my name, L"Help")) { HMGetHelpMenu (& my nat.menu.handle, NULL); theMenus [my nat.menu.id] = NULL; my nat.menu.id = kHMHelpMenuID; theMenus [MAXIMUM_NUMBER_OF_MENUS] = me; } else { int beforeID = 0; CreateNewMenu (my nat.menu.id, 0, & my nat.menu.handle); SetMenuTitleWithCFString (my nat.menu.handle, (CFStringRef) Melder_peekWcsToCfstring (my name)); for (ident = 1; ident <= MAXIMUM_NUMBER_OF_MENUS; ident ++) { GuiObject menu = theMenus [ident]; if (menu && wcsequ (menu -> name, L"Help")) { beforeID = ident; break; } } InsertMenu (my nat.menu.handle, beforeID); } } else if (MEMBER (my parent, RowColumn)) { /* * This will be a menu outside the main window, * or at a different place in the main window. * It is implemented as a Mac pop-up menu. */ CreateNewMenu (my nat.menu.id, 0, & my nat.menu.handle); SetMenuTitleWithCFString (my nat.menu.handle, (CFStringRef) Melder_peekWcsToCfstring (my name)); InsertMenu (my nat.menu.handle, -1); } #endif } break; case xmLabelWidgetClass: Melder_fatal ("Should be implemented in GuiLabel."); break; case xmCascadeButtonWidgetClass: { if (! my motiff.cascadeButton.inBar) { #if win my window = CreateWindow (L"button", _GuiWin_expandAmpersands (my name), WS_CHILD | BS_PUSHBUTTON | WS_CLIPSIBLINGS, my x, my y, my width, my height, my parent -> window, (HMENU) 1, theGui.instance, NULL); SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); SetWindowFont (my window, GetStockFont (ANSI_VAR_FONT), FALSE); #elif mac if (wcsstr (my name, L" -") || (my parent -> rowColumnType == XmMENU_BAR && my parent -> y < 5)) { my nat.control.isBevel = true; CreateBevelButtonControl (my macWindow, & my rect, NULL, kControlBevelButtonSmallBevel, kControlBehaviorPushbutton, NULL, 1, kControlBehaviorCommandMenu, 0, & my nat.control.handle); Melder_assert (my nat.control.handle != NULL); SetControlReference (my nat.control.handle, (long) me); my isControl = TRUE; _GuiNativeControl_setFont (me, 0, 13); _GuiNativeControl_setTitle (me); } else { my nat.control.isPopup = true; //Melder_casual("my macWindow %ld, %d-%d x %d-%d", my macWindow, my rect.left, my rect.right, my rect.top, my rect.bottom); CreatePopupButtonControl (my macWindow, & my rect, NULL, -12345, false, 0, teFlushLeft, 0, & my nat.control.handle); Melder_assert (my nat.control.handle != NULL); SetControlReference (my nat.control.handle, (long) me); my isControl = TRUE; _GuiNativeControl_setFont (me, 0, 13); _GuiNativeControl_setTitle (me); SetControlMaximum (my nat.control.handle, 32767); /* The default seems to be 9 on MacOS X. */ } #endif } } break; case xmPushButtonWidgetClass: Melder_fatal ("Should be implemented in GuiButton."); break; case xmTextWidgetClass: Melder_fatal ("Should be implemented in GuiText."); break; case xmToggleButtonWidgetClass: Melder_fatal ("Should be implemented in GuiCheckButton and GuiRadioButton."); break; case xmScaleWidgetClass: { #if win my window = CreateWindow (PROGRESS_CLASS, _GuiWin_expandAmpersands (my name), WS_CHILD | WS_CLIPSIBLINGS, my x, my y, my width, my height, my parent -> window, (HMENU) 1, theGui.instance, NULL); SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); SendMessage (my window, PBM_SETRANGE, (WPARAM) 0, (LPARAM) MAKELONG (0, 1000)); #endif } break; case xmScrollBarWidgetClass: { #if win my window = CreateWindow (L"scrollbar", my name, WS_CHILD | ( wcsequ (my name, L"verticalScrollBar") ? SBS_VERT : SBS_HORZ ) | WS_CLIPSIBLINGS, my x, my y, my width, my height, my parent -> window, (HMENU) 1, theGui.instance, NULL); SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); NativeScrollBar_set (me); #elif mac my nat.control.handle = NewControl (my macWindow, & my rect, (const unsigned char *) "\000", false, 0, 0, 0, kControlScrollBarLiveProc, (long) me); Melder_assert (my nat.control.handle); my isControl = TRUE; #endif my minimum = 0; my maximum = 100; my value = 0; my sliderSize = 100; } break; case xmScrolledWindowWidgetClass: { /* * The space of the scrolled window is completely filled by three of its children: * the two scroll bars and the clip window. The first child you create yourself will be the * work window: this work window can grow larger than the clip window. * While normally every widget is only clipped to the rects of its ancestors, * for a scrolled window the clip window will be inserted into this chain. * Example: if the widget hierarchy is * shell.form.scrolledWindow.column.row.pushButton, * the clipping hierarchy will be * (shell.)form.(scrolledWindow.)clipWindow.column.row.pushButton */ #if win my window = CreateWindowEx (0, theWindowClassName, L"scrolledWindow", WS_CHILD | WS_CLIPSIBLINGS, my x, my y, my width, my height, my parent -> window, NULL, theGui.instance, NULL); SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); #endif my motiff.scrolledWindow.horizontalBar = XmCreateScrollBar (me, "horizontalScrollBar", NULL, 0); my motiff.scrolledWindow.verticalBar = XmCreateScrollBar (me, "verticalScrollBar", NULL, 0); XtVaSetValues (my motiff.scrolledWindow.horizontalBar, XmNorientation, XmHORIZONTAL, XmNleftAttachment, XmATTACH_FORM, XmNbottomAttachment, XmATTACH_FORM, XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, 15, XmNheight, 16, XmNminimum, 0, XmNmaximum, 100, XmNsliderSize, 100, XmNincrement, CELL_HEIGHT, XmNpageIncrement, 101 - CELL_HEIGHT, NULL); XtVaSetValues (my motiff.scrolledWindow.verticalBar, XmNorientation, XmVERTICAL, XmNtopAttachment, XmATTACH_FORM, XmNrightAttachment, XmATTACH_FORM, XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, 15, XmNwidth, 16, XmNminimum, 0, XmNmaximum, 100, XmNsliderSize, 100, XmNincrement, CELL_HEIGHT, XmNpageIncrement, 101 - CELL_HEIGHT, NULL); my motiff.scrolledWindow.clipWindow = XmCreateBulletinBoard (me, "clipWindow", NULL, 0); XtVaSetValues (my motiff.scrolledWindow.clipWindow, XmNleftAttachment, XmATTACH_FORM, XmNleftOffset, 1, /* For border. */ XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, 16, /* For scroll bar. */ XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, 1, /* For border. */ XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, 16, NULL); /* For scroll bar. */ XtAddCallback (my motiff.scrolledWindow.verticalBar, XmNvalueChangedCallback, cb_scroll, (XtPointer) me); XtAddCallback (my motiff.scrolledWindow.verticalBar, XmNdragCallback, cb_scroll, (XtPointer) me); XtAddCallback (my motiff.scrolledWindow.horizontalBar, XmNvalueChangedCallback, cb_scroll, (XtPointer) me); XtAddCallback (my motiff.scrolledWindow.horizontalBar, XmNdragCallback, cb_scroll, (XtPointer) me); } break; case xmShellWidgetClass: { #if win static LPCTSTR className = theApplicationClassName; /* Only for first window. */ my window = CreateWindowEx (theDialogHint ? WS_EX_DLGMODALFRAME /* | WS_EX_TOPMOST */ : 0, className, className, theDialogHint ? WS_CAPTION | WS_SYSMENU : WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, my parent ? my parent -> window : NULL, NULL, theGui.instance, NULL); className = theWindowClassName; /* All later windows. */ SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); #elif mac Rect r = my rect; if (wcsstr (my name, L"fullscreen")) { my motiff.shell.canFullScreen = true; } OffsetRect (& r, 0, 22); CreateNewWindow (kDocumentWindowClass, kWindowCloseBoxAttribute + ( theDialogHint ? 0 : kWindowCollapseBoxAttribute + kWindowResizableAttribute + kWindowFullZoomAttribute), & r, & my nat.window.ptr); SetWRefCon (my nat.window.ptr, (long) me); /* So we can find the widget from the event with GetWRefCon (). */ CreateRootControl (my nat.window.ptr, & my nat.window.rootControl); if (theDialogHint) { SetThemeWindowBackground (my nat.window.ptr, kThemeBrushDialogBackgroundActive, False); } else { SetThemeWindowBackground (my nat.window.ptr, kThemeBrushDialogBackgroundActive, False); } my macWindow = my nat.window.ptr; /* Associate drawing context; child widgets will inherit. */ my motiff.shell.active = true; /* Why? */ SetPortWindowPort (my macWindow); motif_mac_defaultFont (); /* Will be set back after every change. */ #endif my motiff.shell.isDialog = theDialogHint; /* So we can maintain a single Shell class instead of two different. */ } break; default: break; } my nativized = True; } static GuiObject createWidget (int widgetClass, GuiObject parent, const char *name) { GuiObject me = _Gui_initializeWidget (widgetClass, parent, Melder_peekUtf8ToWcs (name)); _GuiNativizeWidget (me); return me; } void _Gui_invalidateWidget (GuiObject me) { if (! my managed) return; /* Should be: visible. */ if (MEMBER (me, Shell) /*|| my widgetClass == xmRowColumnWidgetClass || my widgetClass == xmFormWidgetClass*/) return; /* Composites are not invalidated !!!!! ???? */ #if mac _GuiMac_clipOnParent (me); EraseRect (& my rect); _GuiMac_clipOffInvalid (me); #endif } void _Gui_validateWidget (GuiObject me) { if (! my managed) return; /* Should be: visible. */ if (MEMBER (me, Shell)) return; #if mac _GuiMac_clipOnParent (me); _GuiMac_clipOffValid (me); #endif } static void Native_move (GuiObject me, int dx, int dy) { /* Native_move () changes the native attributes and visual position of the widget: * No Motif attributes (such as 'x' and 'y') are changed. * Usage: * Native_move () is normally called immediately after changing the 'x' or 'y' attribute. * It can be seen as the 'realization' of a Motif move. */ #if win (void) dx; (void) dy; if (! my window) return; // ignore menu items if (MEMBER (me, Shell)) { my nat.shell.duringMoveWindow = True; if (my motiff.shell.isDialog) MoveWindow (my window, my x, my y, my width + 2 * GetSystemMetrics (SM_CXFIXEDFRAME), my height + 2 * GetSystemMetrics (SM_CYFIXEDFRAME) + GetSystemMetrics (SM_CYCAPTION), TRUE); else MoveWindow (my window, my x, my y, my width + 2 * GetSystemMetrics (SM_CXSIZEFRAME), my height + 2 * GetSystemMetrics (SM_CYSIZEFRAME) + GetSystemMetrics (SM_CYCAPTION) + ( my nat.shell.menuBar != NULL ? GetSystemMetrics (SM_CYMENU) : 0 ), TRUE); } else MoveWindow (my window, my x, my y, my width, my height, True); #elif mac /* * On Mac, the 'rect' attribute is changed, as is the position information in the Mac object. * Native_move () calls itself with the same arguments for all the widget's children. */ GuiObject child; if ((dx == 0 && dy == 0) || MEMBER (me, MenuBar) || (my parent && MEMBER (my parent, PulldownMenu))) return; if (! my isControl) _Gui_invalidateWidget (me); /* At old position. BUG: clipping may be wrong because parent may have moved; however, parent will have been erased in that case, so we will not see it. */ /* * Because all non-shell coordinates are port-relative on Mac, we have to adapt them to the new x and y. */ my rect.left += dx, my rect.right += dx; my rect.top += dy, my rect.bottom += dy; if (MEMBER (me, Text)) { _GuiMacText_move (me); } else if (my isControl) { _GuiMac_clipOnParent (me); MoveControl (my nat.control.handle, my rect.left, my rect.top); _GuiMac_clipOffValid (me); } else if (MEMBER (me, List)) { _GuiMacList_move (me); } else if (MEMBER (me, Shell)) { MoveWindow (my nat.window.ptr, my rect.left, my rect.top + 22, 0); } else if (MEMBER (me, DrawingArea)) { _Gui_callCallbacks (me, & my motiff.drawingArea.moveCallbacks, 0); /* Only Mac? */ } if (! my isControl) _Gui_invalidateWidget (me); /* At new position. */ /* * Because all non-shell coordinates are port-relative on Mac, we have to recursively move the children. */ if (! MEMBER (me, Shell)) for (child = my firstChild; child; child = child -> nextSibling) Native_move (child, dx, dy); #endif } #if mac /* * hideControls and reshowControls are only called by shellResizeWidget, * but they must be defined separately because they are recursive. */ static void reshowControls (GuiObject me) { GuiObject child; if (my widgetClass == xmPulldownMenuWidgetClass) return; for (child = my firstChild; child; child = child -> nextSibling) { if (child -> isControl) { /* * This is a Mac control widget. * Let Mac do the redrawing if Motif considers it visible and Mac considers it invisible? */ if (child -> managed && ! IsControlVisible (child -> nat.control.handle)) { _GuiMac_clipOnParent (child); ShowControl (child -> nat.control.handle); _GuiMac_clipOffValid (child); } } else if (! MEMBER (child, Shell)) { /* * This may be a widget with children. * Some of those children may be controls, or contain controls, so recurse. */ reshowControls (child); } } } static void hideControls (GuiObject me) { GuiObject child; if (my widgetClass == xmPulldownMenuWidgetClass) return; for (child = my firstChild; child; child = child -> nextSibling) { if (child -> isControl) { if (child -> managed) { HideControl (child -> nat.control.handle); } } else if (! MEMBER (child, Shell)) { hideControls (child); } } } #endif static void shellResizeWidget (GuiObject me, int dx, int dy, int dw, int dh) { GuiObject child; #if win Melder_assert (! my shell || ! my shell -> nat.shell.duringMoveWindow); if (my window && ! MEMBER (me, Shell)) { /*RECT rect, client; GetWindowRect (my window, & rect); GetClientRect (my window, & client); ScreenToClient (my parent -> window, (LPPOINT) & rect.left); ScreenToClient (my parent -> window, (LPPOINT) & rect.right); if (rect.left!=my x||rect.right!=my x + my width||rect.top !=my y||rect.bottom!=my y +my height) Melder_warning ("class %d x %d left %d y %d top %d width %d right %d height %d bottom %d", my widgetClass, my x, rect.left, my y, rect.top, my width, rect.right, my height, rect.bottom);*/ MoveWindow (my window, my x, my y, my width, my height, TRUE); if (MEMBER (me, DrawingArea)) _GuiWinDrawingArea_shellResize (me); } #elif mac if ((dx == 0 && dy == 0 && dw == 0 && dh == 0) || MEMBER (me, MenuBar) || (my parent && MEMBER (my parent, PulldownMenu))) return; OffsetRect (& my rect, dx, dy); my rect.right += dw; my rect.bottom += dh; if (MEMBER (me, Text)) { _GuiMacText_shellResize (me); } else if (my isControl) { ControlHandle c = my nat.control.handle; /*if (my managed) HideControl (c);*/ if (dx || dy) MoveControl (c, my rect.left, my rect.top); if (dw || dh) SizeControl (c, my width, my height); //if (MEMBER (me, List)) { // (** my nat.list.handle). rView = my rect; // (** my nat.list.handle). cellSize. h = my width; //} } else if (MEMBER (me, List)) { _GuiMacList_shellResize (me); } else if (MEMBER (me, Shell)) { Rect portRect; GetWindowPortBounds (my nat.window.ptr, & portRect); SetPortWindowPort (my nat.window.ptr); /* Erase old area. */ EraseRect (& portRect); SizeWindow (my nat.window.ptr, my width, my height, false); hideControls (me); /* Redraw new area. */ GetWindowPortBounds (my nat.window.ptr, & portRect); InvalWindowRect (my nat.window.ptr, & portRect); } else if (MEMBER (me, DrawingArea)) { _GuiMacDrawingArea_shellResize (me); if (dx != 0 || dy != 0) _Gui_callCallbacks (me, & my motiff.drawingArea.moveCallbacks, 0); } #endif for (child = my firstChild; child; child = child -> nextSibling) { int cdx = 0, cdy = 0, cdw = 0, cdh = 0; if (MEMBER (child, Shell)) continue; if (child -> rightAttachment == XmATTACH_FORM) { if (child -> leftAttachment == XmATTACH_FORM) cdw = dw; else cdx = dw; } if (child -> leftAttachment == XmATTACH_POSITION && child -> rightAttachment == XmATTACH_POSITION) { int xLeft = my width * (child -> leftPosition / 100.0); int xRight = my width * (child -> rightPosition / 100.0); cdx = xLeft - child -> x; cdw = (xRight - xLeft) - child -> width; } if (child -> bottomAttachment == XmATTACH_FORM) { if (child -> topAttachment == XmATTACH_FORM) cdh = dh; else cdy = dh; } if (child -> topAttachment == XmATTACH_POSITION && child -> bottomAttachment == XmATTACH_POSITION) { int yTop = my height * (child -> topPosition / 100.0); int yBottom = my height * (child -> bottomPosition / 100.0); cdy = yTop - child -> y; cdh = (yBottom - yTop) - child -> height; } child -> x += cdx; child -> y += cdy; child -> width += cdw; child -> height += cdh; shellResizeWidget (child, dx + cdx, dy + cdy, cdw, cdh); } if (MEMBER (me, ScrolledWindow)) _Gui_manageScrolledWindow (me); #if mac if (MEMBER (me, Shell)) reshowControls (me); #endif } static void resizeWidget (GuiObject me, int dw, int dh) { GuiObject child; #if win if (my window && ! MEMBER (me, Shell)) { MoveWindow (my window, my x, my y, my width, my height, TRUE); if (MEMBER (me, DrawingArea)) _GuiWinDrawingArea_shellResize (me); } #elif mac { if ((dw == 0 && dh == 0) || (my parent && MEMBER (my parent, PulldownMenu))) return; if (! my isControl) _Gui_invalidateWidget (me); /* At old position. */ my rect.right += dw; my rect.bottom += dh; if (MEMBER (me, Text)) { _GuiMacText_resize (me); } else if (my isControl) { SizeControl (my nat.control.handle, my width, my height); _Gui_validateWidget (me); } else if (MEMBER (me, List)) { _GuiMacList_resize (me); } else if (MEMBER (me, Shell)) { SizeWindow (my macWindow, my width, my height, true); } else if (MEMBER (me, DrawingArea)) { _GuiMacDrawingArea_shellResize (me); } if (! my isControl) _Gui_invalidateWidget (me); /* At new position. */ } #endif if (MEMBER2 (me, Form, ScrolledWindow)) for (child = my firstChild; child; child = child -> nextSibling) { int cdx = 0, cdy = 0, cdw = 0, cdh = 0; if (child -> widgetClass == xmShellWidgetClass) continue; if (child -> rightAttachment == XmATTACH_FORM) { if (child -> leftAttachment == XmATTACH_FORM) cdw = dw; else cdx = dw; } if (child -> leftAttachment == XmATTACH_POSITION && child -> rightAttachment == XmATTACH_POSITION) { int xLeft = my width * (child -> leftPosition / 100.0); int xRight = my width * (child -> rightPosition / 100.0); cdx = xLeft - child -> x; cdw = (xRight - xLeft) - child -> width; } if (child -> bottomAttachment == XmATTACH_FORM) { if (child -> topAttachment == XmATTACH_FORM) cdh = dh; else cdy = dh; } if (child -> topAttachment == XmATTACH_POSITION && child -> bottomAttachment == XmATTACH_POSITION) { int yTop = my height * (child -> topPosition / 100.0); int yBottom = my height * (child -> bottomPosition / 100.0); cdy = yTop - child -> y; cdh = (yBottom - yTop) - child -> height; } if (cdx || cdy) { child -> x += cdx; child -> y += cdy; Native_move (child, cdx, cdy); } if (cdw || cdh) { child -> width += cdw; child -> height += cdh; resizeWidget (child, cdw, cdh); } } if (MEMBER (me, Shell)) { #if mac Rect portRect; int right, bottom; GetWindowPortBounds (my macWindow, & portRect); right = portRect. right, bottom = portRect. bottom; #elif win int right = 1000, bottom = 500; #endif #if mac { Rect rect; SetRect (& rect, right - 15, bottom - 15, right + 1, bottom + 1); ClipRect (& rect); DrawGrowIcon (my macWindow); GuiMac_clipOff (); } #endif for (child = my firstChild; child; child = child -> nextSibling) if (MEMBER2 (child, Form, ScrolledWindow)) { child -> width += dw; child -> height += dh; resizeWidget (child, dw, dh); } } } static void _motif_setValues (GuiObject me, va_list arg) { int resource; Boolean move = False, resize = False, attach = False, scrollset = False; char *text; #if win int oldX = my x, oldY = my y, oldWidth = my width, oldHeight = my height; #endif #if mac Str255 ptext; #endif while (resource = va_arg (arg, int), resource != 0) switch (resource) { case XmNautoUnmanage: my autoUnmanage = va_arg (arg, int); break; case XmNbottomAttachment: my bottomAttachment = va_arg (arg, int); attach = True; break; case XmNbottomOffset: my bottomOffset = va_arg (arg, int); attach = True; break; case XmNbottomPosition: my bottomPosition = va_arg (arg, int); attach = True; break; case XmNcolumns: { int columns = va_arg (arg, int); Melder_assert (MEMBER (me, Text)); my width = columns * 9 + 4; resize = True; } break; case XmNdeleteResponse: Melder_assert (MEMBER (me, Shell)); my deleteResponse = va_arg (arg, int); if (my deleteResponse == XmDO_NOTHING && ! my motiff.shell.goAwayCallback) { #if mac ChangeWindowAttributes (my macWindow, 0, kWindowCloseBoxAttribute); #endif } break; case XmNdialogStyle: Melder_assert (MEMBER2 (me, Form, BulletinBoard)); my shell -> dialogStyle = my dialogStyle = va_arg (arg, int); break; case XmNdialogTitle: Melder_assert (MEMBER2 (me, Form, BulletinBoard)); text = va_arg (arg, char *); #if win SetWindowText (my shell -> window, Melder_peekUtf8ToWcs (text)); #elif mac ptext [0] = strlen (text); strcpy ((char *) ptext + 1, text); SetWTitle (my macWindow, ptext); #endif break; case XmNheight: my height = va_arg (arg, int); if (MEMBER (me, Shell)) { int maximumHeight = #if win GetSystemMetrics (SM_CYMAXIMIZED) - GetSystemMetrics (SM_CYCAPTION) - GetSystemMetrics (SM_CYSIZEFRAME) - GetSystemMetrics (SM_CYMENU) - 15; #elif mac GetQDGlobalsScreenBits (& theScreenBits) -> bounds.bottom - 41; #endif if (my height > maximumHeight) my height = maximumHeight; } resize = True; break; case XmNhorizontalScrollBar: { /* Have to kill my own bar first. */ XtDestroyWidget (my motiff.scrolledWindow.horizontalBar); /* Then replace by new bar. */ my motiff.scrolledWindow.horizontalBar = va_arg (arg, GuiObject); /* Make sure it is in the right position. */ XtVaSetValues (my motiff.scrolledWindow.horizontalBar, XmNorientation, XmHORIZONTAL, XmNleftAttachment, XmATTACH_FORM, XmNbottomAttachment, XmATTACH_FORM, XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, 15, XmNheight, 16, NULL); /* * Note that we may now have a horizontal bar with application-defined scrolling policy, * and a vertical bar with automatic scrolling policy. * This is more flexible than X Motif, but may be simulated in X Motif with the following strategy, * which is compatible with MotifEmulator: * - set the scrolling policy to XmAUTOMATIC: two scroll bars will be created; * - ask for the horizontal scroll bar with XtVaGetValues; * - remove all the callbacks from the horizontal scroll bar with XtRemoveAllCallbacks; * - add your application-defined callback with XtAddCallback. * We just hope now that X Motif does not look into the XmNscrollingPolicy resource after this... */ } break; case XmNiconName: Melder_assert (MEMBER (me, Shell)); text = va_arg (arg, char *); /* Ignore. */ break; case XmNincrement: Melder_assert (MEMBER (me, ScrollBar)); my increment = va_arg (arg, int); break; case XmNlabelString: Melder_assert (MEMBER2 (me, CascadeButton, PushButton)); text = va_arg (arg, char *); Melder_free (my name); my name = Melder_utf8ToWcs (text); // BUG throwable if (my inMenu) { NativeMenuItem_setText (me); } else if (MEMBER (me, CascadeButton) && my motiff.cascadeButton.inBar) { /* BUG: menu title change not implemented */ } else { _GuiNativeControl_setTitle (me); } break; case XmNleftAttachment: my leftAttachment = va_arg (arg, int); attach = True; break; case XmNleftOffset: my leftOffset = va_arg (arg, int); attach = True; break; case XmNleftPosition: my leftPosition = va_arg (arg, int); attach = True; break; case XmNmaximum: my maximum = va_arg (arg, int); if (MEMBER (me, ScrollBar)) scrollset = True; else if (MEMBER (me, Scale)) _Gui_invalidateWidget (me); break; case XmNmenuHelpWidget: (void) va_arg (arg, GuiObject); break; case XmNminimum: my minimum = va_arg (arg, int); if (MEMBER (me, ScrollBar)) scrollset = True; else if (MEMBER (me, Scale)) _Gui_invalidateWidget (me); break; case XmNorientation: Melder_assert (MEMBER3 (me, RowColumn, ScrollBar, Scale)); my orientation = va_arg (arg, int); break; case XmNpageIncrement: Melder_assert (MEMBER (me, ScrollBar)); my pageIncrement = va_arg (arg, int); break; case XmNradioBehavior: Melder_assert (MEMBER (me, RowColumn)); my radioBehavior = va_arg (arg, int); break; case XmNrightAttachment: my rightAttachment = va_arg (arg, int); attach = True; break; case XmNrightOffset: my rightOffset = va_arg (arg, int); attach = True; break; case XmNrightPosition: my rightPosition = va_arg (arg, int); attach = True; break; case XmNrowColumnType: Melder_assert (MEMBER (me, RowColumn)); my rowColumnType = va_arg (arg, int); break; case XmNrows: (void) va_arg (arg, int); break; case XmNscaleHeight: Melder_assert (MEMBER (me, Scale)); my height = va_arg (arg, int); resize = True; break; case XmNscaleWidth: Melder_assert (MEMBER (me, Scale)); my width = va_arg (arg, int); resize = True; break; case XmNscrollingPolicy: (void) va_arg (arg, int); break; case XmNsliderSize: Melder_assert (MEMBER (me, ScrollBar)); my sliderSize = va_arg (arg, int); scrollset = True; break; case XmNspacing: (void) va_arg (arg, int); break; case XmNsubMenuId: Melder_assert (MEMBER (me, CascadeButton)); my subMenuId = va_arg (arg, GuiObject); my subMenuId -> popUpButton = me; if (my inMenu) { #if win #elif mac if (my nat.entry.item) { SetMenuItemHierarchicalID (my nat.entry.handle, my nat.entry.item, my subMenuId -> nat.menu.id); } #endif } else { #if win #elif mac if (my isControl && my nat.control.isPopup) { SetControlData (my nat.control.handle, kControlMenuPart, kControlPopupButtonMenuHandleTag, 4, & my subMenuId -> nat.menu.handle); _GuiNativeControl_setTitle (me); } #endif } break; case XmNtitle: Melder_assert (MEMBER (me, Shell)); text = va_arg (arg, char *); #if mac ptext [0] = strlen (text); strcpy ((char *) ptext + 1, text); SetWTitle (my nat.window.ptr, ptext); #elif win SetWindowText (my window, Melder_peekUtf8ToWcs (text)); #endif break; case XmNtitleString: Melder_assert (MEMBER (me, Scale)); text = va_arg (arg, char *); Melder_free (my name); my name = Melder_utf8ToWcs (text); // BUG throwable _Gui_invalidateWidget (me); break; case XmNtopAttachment: my topAttachment = va_arg (arg, int); attach = True; break; case XmNtopOffset: my topOffset = va_arg (arg, int); attach = True; break; case XmNtopPosition: my topPosition = va_arg (arg, int); attach = True; break; case XmNtraversalOn: (void) va_arg (arg, int); break; case XmNuserData: my userData = va_arg (arg, void *); break; case XmNvalue: my value = va_arg (arg, int); if (MEMBER (me, ScrollBar)) scrollset = True; else if (MEMBER (me, Scale)) { #if win SendMessage (my window, PBM_SETPOS, (WPARAM) my value, 0); #elif mac _Gui_invalidateWidget (me); #endif } break; case XmNverticalScrollBar: { /* Have to kill my own bar first. */ XtDestroyWidget (my motiff.scrolledWindow.verticalBar); /* Then replace by new bar. */ my motiff.scrolledWindow.verticalBar = va_arg (arg, GuiObject); /* Make sure it is in the right position. */ XtVaSetValues (my motiff.scrolledWindow.verticalBar, XmNorientation, XmVERTICAL, XmNtopAttachment, XmATTACH_FORM, XmNrightAttachment, XmATTACH_FORM, XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, 15, XmNwidth, 16, NULL); } break; case XmNwidth: my width = va_arg (arg, int); resize = True; break; case XmNx: my x = va_arg (arg, int); move = True; break; case XmNy: my y = va_arg (arg, int); move = True; break; default: { if (resource < 0 || resource >= sizeof motif_resourceNames / sizeof (char *)) Melder_flushError ("(XtVaSetValues:) Resource out of range (%d).", resource); else Melder_flushError ("(XtVaSetValues:) Unknown resource \"%s\".", motif_resourceNames [resource]); return; /* Because we do not know how to skip this unknown resource." */ } } if (attach) { Melder_assert (MEMBER2 (my parent, Form, ScrolledWindow)); if (my leftAttachment == XmATTACH_FORM) { my x = my leftOffset; move = True; if (my rightAttachment == XmATTACH_FORM) { my width = my parent -> width - my leftOffset - my rightOffset; resize = True; } } else if (my rightAttachment == XmATTACH_FORM) { my x = my parent -> width - my width - my rightOffset; move = True; } if (my leftAttachment == XmATTACH_POSITION && my rightAttachment == XmATTACH_POSITION) { my x = my parent -> width * (my leftPosition / 100.0); int xRight = my parent -> width * (my rightPosition / 100.0); my width = xRight - my x; resize = True; } if (my topAttachment == XmATTACH_FORM) { my y = my topOffset; move = True; if (my bottomAttachment == XmATTACH_FORM) { my height = my parent -> height - my topOffset - my bottomOffset; resize = True; } } else if (my bottomAttachment == XmATTACH_FORM) { my y = my parent -> height - my height - my bottomOffset; move = True; } if (my topAttachment == XmATTACH_POSITION && my bottomAttachment == XmATTACH_POSITION) { my y = my parent -> height * (my topPosition / 100.0); int yBottom = my parent -> height * (my bottomPosition / 100.0); my height = yBottom - my y; resize = True; } } if (move) { #if win Native_move (me, 0, 0); #elif mac int dx, dy; dx = my x - my rect.left + (my parent && my widgetClass != xmShellWidgetClass ? my parent -> rect.left : 0); dy = my y - my rect.top + (my parent && my widgetClass != xmShellWidgetClass ? my parent -> rect.top : 0); Native_move (me, dx, dy); #endif } if (resize) { #if mac int oldWidth = my rect.right - my rect.left, oldHeight = my rect.bottom - my rect.top; #endif resizeWidget (me, my width - oldWidth, my height - oldHeight); } if (scrollset) NativeScrollBar_set (me); } #if mac static GuiObject _motif_findSubwidget (GuiObject me, int x, int y) { if (! my managed) return NULL; if (my firstChild == NULL && my parent != NULL) { Rect *rect; if (MEMBER (my parent, MenuBar)) return NULL; rect = ! MEMBER (me, ScrollBar) && my parent && MEMBER (my parent, ScrolledWindow) ? & my parent -> motiff.scrolledWindow.clipWindow -> rect : & my rect; if (x >= rect -> left && x <= rect -> right && y >= rect -> top && y <= rect -> bottom) return me; else return NULL; } else { GuiObject child = my firstChild; for (child = my firstChild; child != NULL; child = child -> nextSibling) { if (! MEMBER (child, Shell)) { GuiObject result = _motif_findSubwidget (child, x, y); if (result) return result; } } return NULL; } } #endif void _Gui_manageScrolledWindow (GuiObject me) { int workWidth, workHeight, horzAutomatic, vertAutomatic; GuiObject clipWindow, workWindow, horzBar = my motiff.scrolledWindow.horizontalBar, vertBar = my motiff.scrolledWindow.verticalBar; Melder_assert (my widgetClass == xmScrolledWindowWidgetClass); clipWindow = my motiff.scrolledWindow.clipWindow; workWindow = my motiff.scrolledWindow.workWindow; if (clipWindow == NULL || horzBar == NULL || vertBar == NULL) return; /* Apparently during destruction of scrolled window. */ /* * We must find out if the scrolling policy of each bar is automatic. * Otherwise, we must not change them automatically. */ horzAutomatic = horzBar -> motiff.scrollBar.valueChangedCallbacks.pairs [0].proc == cb_scroll; vertAutomatic = vertBar -> motiff.scrollBar.valueChangedCallbacks.pairs [0].proc == cb_scroll; /* * If the work window has been unmanaged or destroyed, the automatic scroll bars should be empty and insensitive. */ if (workWindow == NULL || ! workWindow -> managed) { if (horzAutomatic) XtVaSetValues (horzBar, XmNmaximum, 100, XmNsliderSize, 100, XmNvalue, 0, XmNpageIncrement, 1, NULL); if (vertAutomatic) XtVaSetValues (vertBar, XmNmaximum, 100, XmNsliderSize, 100, XmNvalue, 0, XmNpageIncrement, 1, NULL); return; } workWidth = workWindow -> width > 10 ? workWindow -> width : 10; workHeight = workWindow -> height > 10 ? workWindow -> height : 10; /* * If the scroll bar is automatic, the slider width is set to the visible height of the work window, * and the maximum is set to the entire height of the work window. * If the value becomes greater than the maximum minus the slider size, * the value is reduced and the work window is scrolled up (i.e. moved down). */ if (horzAutomatic) { int maximum = workWidth; int sliderSize = workWidth < clipWindow -> width ? workWidth : clipWindow -> width; int value = horzBar -> value; if (value > maximum - sliderSize) { value = maximum - sliderSize; workWindow -> x += horzBar -> value - value; Native_move (workWindow, horzBar -> value - value, 0); } XtVaSetValues (horzBar, XmNmaximum, maximum, XmNsliderSize, sliderSize, XmNvalue, value, XmNpageIncrement, clipWindow -> width - (CELL_HEIGHT - 1), NULL); } if (vertAutomatic) { /* Automatic? */ int maximum = workHeight; int sliderSize = workHeight < clipWindow -> height ? workHeight : clipWindow -> height; int value = vertBar -> value; if (value > maximum - sliderSize) { value = maximum - sliderSize; workWindow -> y += vertBar -> value - value; Native_move (workWindow, 0, vertBar -> value - value); } XtVaSetValues (vertBar, XmNmaximum, maximum, XmNsliderSize, sliderSize, XmNvalue, value, XmNpageIncrement, clipWindow -> height - (CELL_HEIGHT - 1), NULL); } } static void _motif_manage (GuiObject me) { GuiObject child; int x = 2, y = 2; int width = 0, height = 0, dw, dh; #if mac GuiObject helpMenu = NULL; #endif /*if (my widgetClass == xmScrolledWindowWidgetClass) return; /* Ignore. */ /* * My geometry follows the layout of my children. * If I am a RowColumn, I am growing while my children move. * Because these moves may involve drawing, which needs clipping to my rect, * I have to grow with every managed child separately, * not just after managing all of them. */ for (child = my firstChild; child; child = child -> nextSibling) { if (child -> managed) { int dx = 0, dy = 0; /* By default, the child does not move. */ if (MEMBER (me, RowColumn)) { #if mac if (my rowColumnType == XmMENU_BAR && MEMBER (child, CascadeButton) && child -> rightAttachment == XmATTACH_FORM) helpMenu = child; else #endif { if (x > child -> x) dx = x - child -> x; if (y > child -> y) dy = y - child -> y; child -> x += dx; x = child -> x; child -> y += dy; y = child -> y; if (my orientation != XmHORIZONTAL) { #if win y += child -> height + 1; #elif mac y += child -> height + 8; #endif } else { #if mac if (my rowColumnType == XmMENU_BAR && MEMBER (child, CascadeButton)) x += child -> width - 1; else #endif x += child -> width + 3; } } } if (child -> x + child -> width > width) width = child -> x + child -> width; if (child -> y + child -> height > height) height = child -> y + child -> height; if (MEMBER3 (me, Shell, Form, BulletinBoard)) { /* These widgets grow with their children. */ dw = width - my width, dh = height - my height; if (dw < 0) dw = 0; if (dh < 0) dh = 0; } else if (MEMBER (me, RowColumn)) { /* A RowColumn shrinks and grows with its children. */ dw = width - my width + 2; dh = height - my height + 2; } else { /* ? */ dw = width - my width; dh = height - my height; } my width += dw; my height += dh; #if mac my rect. right += dw; my rect. bottom += dh; #endif /* * Now that I have grown, there is room for my child to move. */ if (MEMBER (me, RowColumn)) Native_move (child, dx, dy); /* * Resize my attached other children. */ #if 0 if (MEMBER3 (me, RowColumn, Form, ScrolledWindow)) { GuiObject child2; for (child2 = my firstChild; child2; child2 = child2 -> nextSibling) if (child2 != child && child2 -> managed) { int cdx = 0, cdy = 0, cdw = 0, cdh = 0; if (child2 -> widgetClass == xmShellWidgetClass) continue; if (child2 -> rightAttachment == XmATTACH_FORM) if (child2 -> leftAttachment == XmATTACH_FORM) cdw = dw; else cdx = dw; if (child2 -> bottomAttachment == XmATTACH_FORM) if (child2 -> topAttachment == XmATTACH_FORM) cdh = dh; else cdy = dh; if (cdx || cdy) { child2 -> x += cdx; child2 -> y += cdy; Native_move (child2, cdx, cdy); } if (cdw || cdh) { child2 -> width += cdw; child2 -> height += cdh; resizeWidget (child2, cdw, cdh); } } } #endif } } #if mac if (helpMenu) { int x_old = helpMenu -> x; my width = my parent -> width; my rect.right = my parent -> rect.right; helpMenu -> x = my width - helpMenu -> width - 2; /*helpMenu -> rect.left = helpMenu -> x; helpMenu -> rect.right = my rect.right - 6;*/ Native_move (helpMenu, helpMenu -> x - x_old, 0); } #endif #if win if (my window) Native_move (me, 0, 0); #elif mac if (MEMBER (me, Shell)) SizeWindow (my nat.window.ptr, my width, my height, true); #endif /* If I have grown, I have to notify my parent. */ if (! MEMBER (me, Shell)) { if (MEMBER4 (my parent, RowColumn, Form, BulletinBoard, Shell)) _motif_manage (my parent); else if (MEMBER (my parent, ScrolledWindow)) _Gui_manageScrolledWindow (my parent); } } /***** X TOOLKIT *****/ static void xt_addCallback (XtCallbackList *callbacks, XtCallbackProc proc, XtPointer closure) { int i; for (i = 0; i < MAXNUM_CALLBACKS; i ++) { if (! callbacks -> pairs [i]. proc) { callbacks -> pairs [i]. proc = proc; callbacks -> pairs [i]. closure = closure; return; } } Melder_assert (i < MAXNUM_CALLBACKS); /* Will always fail if we arrive here. */ } void XtAddCallback (GuiObject me, int kind, XtCallbackProc proc, XtPointer closure) { switch (kind) { case XmNactivateCallback: my activateCallback = proc; my activateClosure = closure; break; case XmNdecrementCallback: break; case XmNdestroyCallback: my destroyCallback = proc; my destroyClosure = closure; break; case XmNdragCallback: Melder_assert (my widgetClass == xmScrollBarWidgetClass); xt_addCallback (& my motiff.scrollBar.dragCallbacks, proc, closure); break; case XmNincrementCallback: break; case XmNmoveCallback: Melder_assert (my widgetClass == xmDrawingAreaWidgetClass); xt_addCallback (& my motiff.drawingArea.moveCallbacks, proc, closure); break; case XmNpageIncrementCallback: break; case XmNpageDecrementCallback: break; case XmNvalueChangedCallback: if (my widgetClass == xmScrollBarWidgetClass) xt_addCallback (& my motiff.scrollBar.valueChangedCallbacks, proc, closure); else if (my widgetClass == xmToggleButtonWidgetClass) xt_addCallback (& my motiff.toggleButton.valueChangedCallbacks, proc, closure); else Melder_assert (False); break; default: if (kind < 0 || kind >= sizeof motif_resourceNames / sizeof (char *)) Melder_flushError ("(XtAddCallback:) Callback name out of range (%d).", kind); else Melder_flushError ("(XtAddCallback:) Unknown callback \"%s\".", motif_resourceNames [kind]); } } XtWorkProcId GuiAddWorkProc (XtWorkProc workProc, XtPointer closure) { int i = 1; while (i < 10 && theWorkProcs [i]) i ++; Melder_assert (i < 10); theWorkProcs [i] = workProc; theWorkProcClosures [i] = closure; theNumberOfWorkProcs ++; return i; } void XtRemoveWorkProc (XtWorkProcId id) { theWorkProcs [id] = NULL; theNumberOfWorkProcs --; } #if defined (macintosh) static pascal void timerAction (EventLoopTimerRef timer, void *closure) { long i = (int) closure; (void) timer; theTimeOutProcs [i] (theTimeOutClosures [i], & i); XtRemoveTimeOut (i); } #endif XtIntervalId GuiAddTimeOut (unsigned long interval, XtTimerCallbackProc proc, XtPointer closure) { long i = 1; while (i < 10 && theTimeOutProcs [i]) i ++; Melder_assert (i < 10); theTimeOutProcs [i] = proc; #if defined (macintosh) { EventLoopRef mainLoop = GetMainEventLoop (); static EventLoopTimerUPP timerUPP; if (timerUPP == NULL) timerUPP = NewEventLoopTimerUPP (timerAction); InstallEventLoopTimer (mainLoop, interval * kEventDurationMillisecond, 0, timerUPP, (void *) i, & theTimers [i]); } #else theTimeOutStarts [i] = clock (); theTimeOutIntervals [i] = (interval * (double) CLOCKS_PER_SEC) / 1000; #endif theTimeOutClosures [i] = closure; theNumberOfTimeOuts ++; return i; } void XtRemoveTimeOut (XtIntervalId id) { theTimeOutProcs [id] = NULL; theNumberOfTimeOuts --; #if defined (macintosh) RemoveEventLoopTimer (theTimers [id]); #endif } void XtDestroyWidget (GuiObject me) { GuiObject subview = my firstChild; /* * Prevent subsequent messages. */ #if win HWND natWindow; if (my window) SetWindowLongPtr (my window, GWLP_USERDATA, 0); #endif if (my widgetClass == xmShellWidgetClass) { XtUnmanageChild (me); #if win natWindow = my window; /* Save for destroy. */ my window = NULL; #elif mac my macWindow = NULL; /* Notify children. */ #endif } if (MEMBER2 (me, Form, BulletinBoard) && MEMBER (my parent, Shell) && #if win my parent -> window #elif mac my parent -> macWindow #endif ) { XtDestroyWidget (my parent); return; } while (subview) { GuiObject nextSibling = subview -> nextSibling; /* Save... */ //if (subview -> widgetClass != xmShellWidgetClass) /* FIX instead of Xm's being_destroyed mark. */ // removed 20090105 XtDestroyWidget (subview); subview = nextSibling; /* ...because we can't dereference dead subview. */ } if (my destroyCallback) my destroyCallback (me, my destroyClosure, NULL); switch (my widgetClass) { case xmLabelWidgetClass: { #if win _GuiWinLabel_destroy (me); #elif mac _GuiMacLabel_destroy (me); #endif } break; case xmCascadeButtonWidgetClass: { #if win if (! my inMenu && ! MEMBER (my parent, MenuBar)) _GuiNativeControl_destroy (me); #elif mac if (my isControl) _GuiNativeControl_destroy (me); #endif } break; case xmScaleWidgetClass: { #if win DestroyWindow (my window); #elif mac _GuiMac_clipOnParent (me); EraseRect (& my rect); GuiMac_clipOff (); #endif } break; case xmShellWidgetClass: { #if win DestroyWindow (natWindow); #elif mac DisposeWindow (my nat.window.ptr); if (my motiff.shell.canFullScreen) SetSystemUIMode (kUIModeNormal, 0); // BUG: assumes there can be only one fullscreenable window #endif _motif_removeShell (me); } break; case xmListWidgetClass: { #if win _GuiWinList_destroy (me); #elif mac _GuiMacList_destroy (me); #endif } break; case xmDrawingAreaWidgetClass: { #if win _GuiWinDrawingArea_destroy (me); #else _GuiMacDrawingArea_destroy (me); #endif } break; case xmRowColumnWidgetClass: case xmFormWidgetClass: case xmBulletinBoardWidgetClass: { #if win DestroyWindow (my window); #endif } break; case xmTextWidgetClass: { #if win _GuiWinText_destroy (me); #elif mac _GuiMacText_destroy (me); #endif } break; case xmPushButtonWidgetClass: { if (my inMenu) { #if win if (my nat.entry.id) theMenuItems [my nat.entry.id] = FALSE; #elif mac DeleteMenuItem (my nat.entry.handle, my nat.entry.item); for (subview = my parent -> firstChild; subview; subview = subview -> nextSibling) { if (subview -> nat.entry.item > my nat.entry.item) subview -> nat.entry.item -= 1; } #endif } else { #if win _GuiWinButton_destroy (me); #elif mac _GuiMacButton_destroy (me); #endif } } break; case xmToggleButtonWidgetClass: { if (my inMenu) { #if win if (my nat.entry.id) theMenuItems [my nat.entry.id] = FALSE; #elif mac DeleteMenuItem (my nat.entry.handle, my nat.entry.item); for (subview = my parent -> firstChild; subview; subview = subview -> nextSibling) { if (subview -> nat.entry.item > my nat.entry.item) subview -> nat.entry.item -= 1; } #endif } else { if (my isRadioButton) { #if win _GuiWinRadioButton_destroy (me); #elif mac _GuiMacRadioButton_destroy (me); #endif } else { #if win _GuiWinCheckButton_destroy (me); #elif mac _GuiMacCheckButton_destroy (me); #endif } } } break; case xmScrollBarWidgetClass: { _GuiNativeControl_destroy (me); } break; case xmScrolledWindowWidgetClass: { /* The scroll bars will be destroyed automatically because they are my children. */ } break; case xmSeparatorWidgetClass: { if (my inMenu) { #if win if (my nat.entry.id) theMenuItems [my nat.entry.id] = FALSE; #elif mac DeleteMenuItem (my nat.entry.handle, my nat.entry.item); for (subview = my parent -> firstChild; subview; subview = subview -> nextSibling) { if (subview -> nat.entry.item > my nat.entry.item) subview -> nat.entry.item -= 1; } #endif } } break; case xmPulldownMenuWidgetClass: { #if win if (MEMBER (my parent, MenuBar)) RemoveMenu (my parent -> nat.menu.handle, (UINT) my nat.menu./*handle*/id, MF_BYCOMMAND); DestroyMenu (my nat.menu.handle); theMenus [my nat.menu.id] = NULL; #elif mac DeleteMenu (my nat.menu.id); DisposeMenu (my nat.menu.handle); theMenus [my nat.menu.id] = NULL; #endif } break; } Melder_free (my name); if (my parent && me == my parent -> firstChild) /* Remove dangling reference. */ my parent -> firstChild = my nextSibling; if (my previousSibling) /* Remove dangling reference. */ my previousSibling -> nextSibling = my nextSibling; if (my nextSibling) /* Remove dangling reference: two-way linked list. */ my nextSibling -> previousSibling = my previousSibling; if (my parent && MEMBER (my parent, ScrolledWindow)) { if (me == my parent -> motiff.scrolledWindow.workWindow) { my parent -> motiff.scrolledWindow.workWindow = NULL; _Gui_manageScrolledWindow (my parent); } else if (me == my parent -> motiff.scrolledWindow.horizontalBar) { my parent -> motiff.scrolledWindow.horizontalBar = NULL; } else if (me == my parent -> motiff.scrolledWindow.verticalBar) { my parent -> motiff.scrolledWindow.verticalBar = NULL; } else if (me == my parent -> motiff.scrolledWindow.clipWindow) { my parent -> motiff.scrolledWindow.clipWindow = NULL; } } Melder_free (me); numberOfWidgets --; } Boolean XtIsManaged (GuiObject me) { return my managed; } Boolean XtIsShell (GuiObject me) { return my widgetClass == xmShellWidgetClass; } void XtMapWidget (GuiObject me) { switch (my widgetClass) { case xmShellWidgetClass: #if win ShowWindow (my window, me == theApplicationShell ? theCommandShow : theCommandShow); //UpdateWindow (my window); #elif mac ShowWindow (my nat.window.ptr); #endif break; default: break; } } static void mapWidget (GuiObject me) { GuiObject child; Melder_assert (my widgetClass != xmPulldownMenuWidgetClass); if (my inMenu) { #if win int position = NativeMenuItem_getPosition (me); switch (my widgetClass) { case xmPushButtonWidgetClass: { InsertMenu (my nat.entry.handle, position, MF_STRING | MF_BYPOSITION | ( my insensitive ? MF_GRAYED : MF_ENABLED ), my nat.entry.id, _GuiWin_expandAmpersands (my name)); } break; case xmToggleButtonWidgetClass: { InsertMenu (my nat.entry.handle, position, MF_STRING | MF_UNCHECKED | MF_BYPOSITION | ( my insensitive ? MF_GRAYED : MF_ENABLED ), my nat.entry.id, _GuiWin_expandAmpersands (my name)); } break; case xmCascadeButtonWidgetClass: { my nat.entry.id = (ULONG_PTR) my subMenuId -> nat.menu.handle; InsertMenu (my nat.entry.handle, position, MF_POPUP | MF_BYPOSITION | ( my insensitive ? MF_GRAYED : MF_ENABLED ), my nat.entry.id, _GuiWin_expandAmpersands (my name)); } break; case xmSeparatorWidgetClass: { InsertMenu (my nat.entry.handle, position, MF_SEPARATOR | MF_BYPOSITION, my nat.entry.id, _GuiWin_expandAmpersands (my name)); } break; } #elif mac GuiObject sibling; int item; /* * Insert a native menu item. */ if (my nat.entry.item) return; /* * A Macintosh menu item shall know its "item number", * which is its dynamic position in the current shape of the menu. */ /* * Position of new native item. */ item = NativeMenuItem_getPosition (me); /* * Shift all other item numbers. */ for (sibling = my parent -> firstChild; sibling; sibling = sibling -> nextSibling) { if (sibling -> managed && sibling -> widgetClass != xmPulldownMenuWidgetClass && sibling -> nat.entry.item >= item) sibling -> nat.entry.item += 1; } /* * Remember. */ my nat.entry.item = item; /* * Set text, sensitivity, submenu. BUGS: should also set toggle state and accelerator text. */ if (my widgetClass == xmSeparatorWidgetClass) { InsertMenuItem (my nat.entry.handle, (unsigned char *) "\001-", my nat.entry.item - 1); } else { InsertMenuItem (my nat.entry.handle, (unsigned char *) "\001 ", my nat.entry.item - 1); SetMenuItemTextWithCFString (my nat.entry.handle, my nat.entry.item, (CFStringRef) Melder_peekWcsToCfstring (my name)); if (my insensitive) DisableMenuItem (my nat.entry.handle, my nat.entry.item); if (mac_text [mac_text [0]] == ':') SetItemStyle (my nat.entry.handle, my nat.entry.item, underline); if (my widgetClass == xmCascadeButtonWidgetClass) { if (my subMenuId) { SetMenuItemHierarchicalID (my nat.entry.handle, my nat.entry.item, my subMenuId -> nat.menu.id); } } /* * All the items in the Apple Menu folder are added to the Apple menu. */ if (my parent -> name [0] == appleMark) AppendResMenu (my nat.entry.handle, 'DRVR'); } #endif } else switch (my widgetClass) { #if win case xmBulletinBoardWidgetClass: case xmDrawingAreaWidgetClass: case xmScrolledWindowWidgetClass: case xmFormWidgetClass: case xmRowColumnWidgetClass: ShowWindow (my window, SW_SHOW); break; #endif case xmShellWidgetClass: { #if win ShowWindow (my window, me == theApplicationShell ? theCommandShow : theCommandShow); #elif mac SelectWindow (my nat.window.ptr); ShowWindow (my nat.window.ptr); #endif if (my dialogStyle == XmDIALOG_FULL_APPLICATION_MODAL) #if mac theGui.modalDialog = my nat.window.ptr #endif ; } break; case xmMenuBarWidgetClass: { #if win DrawMenuBar (my shell -> window); // every window has its own menu bar #elif mac DrawMenuBar (); /* There is a single Mac menu bar for all windows. */ #endif } break; case xmPushButtonWidgetClass: _GuiNativeControl_show (me); break; case xmToggleButtonWidgetClass: _GuiNativeControl_show (me); break; case xmScrollBarWidgetClass: { #if win if (! my window) { my window = CreateWindow (L"scrollbar", my name, WS_CHILD | ( my orientation == XmHORIZONTAL ? SBS_HORZ : SBS_VERT) | WS_CLIPSIBLINGS, my x, my y, my width, my height, my parent -> window, (HMENU) 1, theGui.instance, NULL); SetWindowLongPtr (my window, GWLP_USERDATA, (LONG_PTR) me); NativeScrollBar_set (me); } #endif _GuiNativeControl_show (me); } break; case xmLabelWidgetClass: _GuiNativeControl_show (me); break; case xmCascadeButtonWidgetClass: { #if win if (! MEMBER (my parent, MenuBar)) _GuiNativeControl_show (me); #elif mac if (my isControl) _GuiNativeControl_show (me); #endif } break; case xmScaleWidgetClass: { #if win _GuiNativeControl_show (me); #elif mac _Gui_invalidateWidget (me); #endif } break; case xmTextWidgetClass: { #if win _GuiWinText_map (me); #elif mac _GuiMacText_map (me); #endif } break; case xmListWidgetClass: { #if win _GuiWinList_map (me); #elif mac _GuiMacList_map (me); #endif } break; default: break; } for (child = my firstChild; child != NULL; child = child -> nextSibling) if (child -> managed) mapWidget (child); } void XtManageChild (GuiObject me) { if (my managed) return; if (MEMBER (me, ScrolledWindow)) { XtManageChild (my motiff.scrolledWindow.horizontalBar); XtManageChild (my motiff.scrolledWindow.verticalBar); /*XtManageChild (my motiff.scrolledWindow.clipWindow);*/ } my managed = 1; /* Geometry management if my parent is a manager. */ if (! MEMBER (me, Shell)) { if (MEMBER4 (my parent, RowColumn, Form, BulletinBoard, Shell)) _motif_manage (my parent); if (MEMBER (me, ScrolledWindow)) _Gui_manageScrolledWindow (me); if (MEMBER (my parent, ScrolledWindow)) _Gui_manageScrolledWindow (my parent); } /* Map to the screen (suppose that mapped_when_managed is true). */ /* Condition: the entire up chain has been managed. */ /* Shells or their immediate manager children can be mapped directly. */ if (my parent && MEMBER (my parent, Shell) && MEMBER2 (me, Form, BulletinBoard)) { my parent -> managed = 1; mapWidget (my parent); } else if (my inMenu) { mapWidget (me); } else { int visible = True; GuiObject widget; for (widget = me; widget != NULL; widget = widget -> parent) { if (! widget -> managed && /* If a parent is invisible, so are its children. */ ! MEMBER (widget, PulldownMenu)) /* The exception: "shown" even if not popped up. */ { visible = False; break; } if (MEMBER (widget, Shell)) break; /* Root: end of chain. */ } if (visible) mapWidget (me); } /* I may have been created by XmCreateScrolledText or XmCreateScrolledList. */ /* In that case, my parent should be managed. */ if (MEMBER2 (me, Text, List) && MEMBER (my parent, ScrolledWindow)) XtManageChild (my parent); } void XtManageChildren (GuiObjectList children, Cardinal num_children) { Cardinal i; for (i = 0; i < num_children; i ++) XtManageChild (children [i]); } void XtSetSensitive (GuiObject me, Boolean value) { if (my insensitive != value) return; my insensitive = ! value; if (! my parent) return; switch (my widgetClass) { case xmPushButtonWidgetClass: case xmToggleButtonWidgetClass: { if (my inMenu) { NativeMenuItem_setSensitive (me); } else { _GuiNativeControl_setSensitive (me); } } break; case xmScrollBarWidgetClass: _GuiNativeControl_setSensitive (me); break; case xmLabelWidgetClass: _GuiNativeControl_setSensitive (me); break; case xmCascadeButtonWidgetClass: { if (my inMenu || my motiff.cascadeButton.inBar) { if (my subMenuId) { if (value) { #if mac EnableMenuItem (my subMenuId -> nat.menu.handle, 0); #endif } else { #if mac DisableMenuItem (my subMenuId -> nat.menu.handle, 0); #endif } #if mac DrawMenuBar (); #endif } } else { _GuiNativeControl_setSensitive (me); } } break; case xmPulldownMenuWidgetClass: { if (my popUpButton) XtSetSensitive (my popUpButton, value); } break; default: break; } } void XtUnmanageChild (GuiObject me) { if (! my managed) return; if (my inMenu) { if (! MEMBER (me, PulldownMenu)) NativeMenuItem_delete (me); } else switch (my widgetClass) { case xmShellWidgetClass: #if win _GuiText_handleFocusLoss (my textFocus); ShowWindow (my window, SW_HIDE); #elif mac if (my nat.window.ptr == FrontWindow ()) _GuiMac_clearTheTextFocus (); if (my nat.window.ptr == theGui.modalDialog) theGui.modalDialog = NULL; HideWindow (my nat.window.ptr); #endif if (my firstChild && MEMBER2 (my firstChild, Form, BulletinBoard)) my firstChild -> managed = 0; break; case xmPushButtonWidgetClass: _GuiNativeControl_hide (me); break; case xmToggleButtonWidgetClass: _GuiNativeControl_hide (me); break; case xmLabelWidgetClass: _GuiNativeControl_hide (me); break; case xmCascadeButtonWidgetClass: #if win if (! MEMBER (my parent, MenuBar)) _GuiNativeControl_hide (me); #elif mac if (my isControl) _GuiNativeControl_hide (me); #endif break; case xmScrollBarWidgetClass: _GuiNativeControl_hide (me); break; case xmFormWidgetClass: case xmBulletinBoardWidgetClass: if (MEMBER (my parent, Shell)) XtUnmanageChild (my parent); break; case xmTextWidgetClass: { _GuiText_unmanage (me); } break; default: _Gui_invalidateWidget (me); break; } my managed = 0; if (! MEMBER (me, Shell)) { if (MEMBER4 (my parent, RowColumn, Form, BulletinBoard, Shell)) _motif_manage (my parent); else if (MEMBER (my parent, ScrolledWindow)) _Gui_manageScrolledWindow (my parent); } } void XtUnmanageChildren (GuiObjectList children, Cardinal num_children) { Cardinal i; for (i = 0; i < num_children; i ++) XtUnmanageChild (children [i]); } #if mac static pascal OSErr _motif_processOpenApplicationMessage (const AppleEvent *theAppleEvent, AppleEvent *reply, long handlerRefCon) { (void) theAppleEvent; (void) reply; (void) handlerRefCon; return noErr; Melder_warning (L"Open app event."); } static pascal OSErr _motif_processQuitApplicationMessage (const AppleEvent *theAppleEvent, AppleEvent *reply, long handlerRefCon) { /* This hook shall return noErr if it is OK to quit, otherwise userCanceledErr. It should not exit the application by itself. Here it does!! */ (void) theAppleEvent; (void) reply; (void) handlerRefCon; if (theQuitApplicationCallback) return theQuitApplicationCallback () ? noErr : userCanceledErr; /* BUG anti Mac documentation */ exit (0); return noErr; } static pascal OSErr _motif_processOpenDocumentsMessage (const AppleEvent *theAppleEvent, AppleEvent *reply, long handlerRefCon) { AEDescList documentList; OSErr err; long document, numberOfDocuments; (void) reply; (void) handlerRefCon; err = AEGetParamDesc (theAppleEvent, keyDirectObject, typeAEList, & documentList); if (err) return err; err = AECountItems (& documentList, & numberOfDocuments); for (document = 1; document <= numberOfDocuments; document ++ ) { AEKeyword keyWord; DescType typeCode; Size actualSize; FSRef fsref; err = AEGetNthPtr (& documentList, document, typeFSRef, & keyWord, & typeCode, & fsref, sizeof (fsref), & actualSize); if (! err) { structMelderFile file = { 0 }; Melder_machToFile (& fsref, & file); if (theOpenDocumentCallback) theOpenDocumentCallback (& file); } } AEDisposeDesc (& documentList); return noErr; } static pascal OSErr _motif_processSignalA (const AppleEvent *theAppleEvent, AppleEvent *reply, long handlerRefCon) { static int duringAppleEvent = FALSE; (void) reply; (void) handlerRefCon; if (! duringAppleEvent) { char *buffer; long actualSize; duringAppleEvent = TRUE; //AEInteractWithUser (kNoTimeOut, NULL, NULL); // use time out of 0 to execute immediately (without bringing to foreground) ProcessSerialNumber psn; GetCurrentProcess (& psn); SetFrontProcess (& psn); AEGetParamPtr (theAppleEvent, 1, typeChar, NULL, NULL, 0, & actualSize); buffer = (char *) malloc (actualSize); AEGetParamPtr (theAppleEvent, 1, typeChar, NULL, & buffer [0], actualSize, NULL); if (theUserMessageCallbackA) theUserMessageCallbackA (buffer); free (buffer); duringAppleEvent = FALSE; } return noErr; } static pascal OSErr _motif_processSignalW (const AppleEvent *theAppleEvent, AppleEvent *reply, long handlerRefCon) { static int duringAppleEvent = FALSE; (void) reply; (void) handlerRefCon; if (! duringAppleEvent) { wchar_t *buffer; long actualSize; duringAppleEvent = TRUE; //AEInteractWithUser (kNoTimeOut, NULL, NULL); // use time out of 0 to execute immediately (without bringing to foreground) ProcessSerialNumber psn; GetCurrentProcess (& psn); SetFrontProcess (& psn); AEGetParamPtr (theAppleEvent, 1, typeUnicodeText, NULL, NULL, 0, & actualSize); buffer = (wchar *) malloc (actualSize); AEGetParamPtr (theAppleEvent, 1, typeUnicodeText, NULL, & buffer [0], actualSize, NULL); if (theUserMessageCallbackW) theUserMessageCallbackW (buffer); free (buffer); duringAppleEvent = FALSE; } return noErr; } #elif win static LRESULT CALLBACK windowProc (HWND window, UINT message, WPARAM wParam, LPARAM lParam); #endif GuiObject GuiInitialize (const char *name, unsigned int *argc, char **argv) { (void) argc; #if mac (void) argv; _GuiText_init (); RegisterAppearanceClient (); InitCursor (); FlushEvents (everyEvent, 0); AEInstallEventHandler (kCoreEventClass, kAEOpenApplication, NewAEEventHandlerUPP (_motif_processOpenApplicationMessage), 0, false); AEInstallEventHandler (kCoreEventClass, kAEQuitApplication, NewAEEventHandlerUPP (_motif_processQuitApplicationMessage), 0, false); AEInstallEventHandler (kCoreEventClass, kAEOpenDocuments, NewAEEventHandlerUPP (_motif_processOpenDocumentsMessage), 0, false); AEInstallEventHandler (758934755, 0, NewAEEventHandlerUPP (_motif_processSignalA), 0, false); AEInstallEventHandler (758934756, 0, NewAEEventHandlerUPP (_motif_processSignalW), 0, false); //USE_QUESTION_MARK_HELP_MENU = 1; theUserFocusEventTarget = GetUserFocusEventTarget (); #elif win { HWND window; WNDCLASSEX windowClass; swprintf (theApplicationName, 100, argv [0] ? Melder_peekUtf8ToWcs (argv [0]) : L"Unknown"); swprintf (theApplicationClassName, 100, L"PraatShell%d %ls", PRAAT_WINDOW_CLASS_NUMBER, theApplicationName); swprintf (theWindowClassName, 100, L"PraatChildWindow%d %ls", PRAAT_WINDOW_CLASS_NUMBER, theApplicationName); swprintf (theDrawingAreaClassName, 100, L"PraatDrawingArea%d %ls", PRAAT_WINDOW_CLASS_NUMBER, theApplicationName); window = FindWindow (theWindowClassName, NULL); if (window != NULL) { /* * We are in the second instance of Praat. * The user double-clicked Praat while it was running, * or she dropped a file on the Praat icon, * or she double-clicked a Praat file. */ if (IsIconic (window)) ShowWindow (window, SW_RESTORE); SetForegroundWindow (window); if (theOpenDocumentCallback && argv [3] [0]) { structMelderFile file = { 0 }; /* * The user dropped a file on the Praat icon or double-clicked a Praat file * while Praat was already running. * Windows may have enclosed the path between quotes; * this is especially likely to happen if the path contains spaces, * which on Windows XP is very usual. */ wchar_t *s = Melder_peekUtf8ToWcs (argv [3]); Melder_relativePathToFile (s [0] == ' ' && s [1] == '\"' ? s + 2 : s [0] == '\"' ? s + 1 : s, & file); long l = wcslen (file. path); if (l > 0 && file. path [l - 1] == '\"') file. path [l - 1] = '\0'; theOpenDocumentCallback (& file); } exit (0); // possible problem } sscanf (argv [1], "%p", & theGui.instance); windowClass. cbSize = sizeof (WNDCLASSEX); windowClass. style = CS_HREDRAW | CS_VREDRAW | CS_DBLCLKS | CS_OWNDC // crucial: see GraphicsScreen_init () ; windowClass. lpfnWndProc = windowProc; windowClass. cbClsExtra = 0; windowClass. cbWndExtra = 0; windowClass. hInstance = theGui.instance; windowClass. hIcon = NULL; windowClass. hCursor = LoadCursor (NULL, IDC_ARROW); windowClass. hbrBackground = /*(HBRUSH) (COLOR_WINDOW + 1)*/ GetStockBrush (LTGRAY_BRUSH); windowClass. lpszMenuName = NULL; windowClass. lpszClassName = theWindowClassName; windowClass. hIconSm = NULL; RegisterClassEx (& windowClass); windowClass. hbrBackground = GetStockBrush (WHITE_BRUSH); windowClass. lpszClassName = theDrawingAreaClassName; RegisterClassEx (& windowClass); windowClass. lpszClassName = theApplicationClassName; RegisterClassEx (& windowClass); InitCommonControls (); theCommandShow = atoi (argv [2]); } #endif return theApplicationShell = XmCreateShell (NULL, name, NULL, 0); } GuiObject GuiAppInitialize (const char *name, void *dum2, int dum3, unsigned int *argc, char **argv, void *dum4, void *dum5) { (void) dum4; (void) dum5; return GuiInitialize (name, argc, argv); } GuiObject XtVaCreateManagedWidget (const char *name, int widgetClass, GuiObject parent, ...) { GuiObject me; va_list arg; va_start (arg, parent); me = createWidget (widgetClass, parent, name); _motif_setValues (me, arg); va_end (arg); XtManageChild (me); return me; } GuiObject XtVaCreateWidget (const char *name, int widgetClass, GuiObject parent, ...) { GuiObject me; va_list arg; va_start (arg, parent); me = createWidget (widgetClass, parent, name); _motif_setValues (me, arg); va_end (arg); return me; } void XtVaGetValues (GuiObject me, ...) { char *text; #if mac Str255 ptext; #endif unsigned int resource; va_list arg; va_start (arg, me); while ((resource = va_arg (arg, int)) != 0) switch (resource) { case XmNx: *va_arg (arg, int *) = my x; break; case XmNy: *va_arg (arg, int *) = my y; break; case XmNwidth: *va_arg (arg, int *) = my width; break; case XmNheight: *va_arg (arg, int *) = my height; break; case XmNuserData: *va_arg (arg, void **) = my userData; break; case XmNtitle: case XmNiconName: Melder_assert (my widgetClass == xmShellWidgetClass); #if mac GetWTitle (my nat.window.ptr, ptext); text = Melder_malloc_f (char, ptext [0] + 1); strncpy (text, (char *) ptext + 1, ptext [0]); text [ptext [0]] = 0; *va_arg (arg, char **) = text; #elif win *va_arg (arg, char **) = NULL; #endif break; case XmNlabelString: case XmNtitleString: Melder_assert (my widgetClass == xmCascadeButtonWidgetClass || my widgetClass == xmScaleWidgetClass); text = Melder_wcsToUtf8 (my name); // BUG throwable *va_arg (arg, char **) = text; break; case XmNdialogTitle: Melder_assert (my widgetClass == xmFormWidgetClass || my widgetClass == xmBulletinBoardWidgetClass); #if mac GetWTitle (my macWindow, ptext); text = Melder_malloc_f (char, ptext [0] + 1); strncpy (text, (char *) ptext + 1, ptext [0]); text [ptext [0]] = 0; *va_arg (arg, char **) = text; #elif win *va_arg (arg, char **) = NULL; #endif break; case XmNradioBehavior: Melder_assert (my widgetClass == xmRowColumnWidgetClass); *va_arg (arg, int *) = my radioBehavior; break; case XmNautoUnmanage: *va_arg (arg, int *) = my autoUnmanage; break; case XmNorientation: Melder_assert (my widgetClass == xmRowColumnWidgetClass || my widgetClass == xmScrollBarWidgetClass); *va_arg (arg, int *) = my orientation; break; case XmNrowColumnType: Melder_assert (my widgetClass == xmRowColumnWidgetClass); *va_arg (arg, int *) = my rowColumnType; break; case XmNsubMenuId: Melder_assert (my widgetClass == xmCascadeButtonWidgetClass); *va_arg (arg, GuiObject *) = my subMenuId; break; case XmNdialogStyle: Melder_assert (my widgetClass == xmFormWidgetClass || my widgetClass == xmBulletinBoardWidgetClass); *va_arg (arg, int *) = my dialogStyle; break; case XmNleftAttachment: Melder_assert (my parent -> widgetClass == xmFormWidgetClass); *va_arg (arg, int *) = my leftAttachment; break; case XmNrightAttachment: Melder_assert (my parent -> widgetClass == xmFormWidgetClass); *va_arg (arg, int *) = my rightAttachment; break; case XmNtopAttachment: Melder_assert (my parent -> widgetClass == xmFormWidgetClass); *va_arg (arg, int *) = my topAttachment; break; case XmNbottomAttachment: Melder_assert (my parent -> widgetClass == xmFormWidgetClass); *va_arg (arg, int *) = my bottomAttachment; break; case XmNleftOffset: Melder_assert (my parent -> widgetClass == xmFormWidgetClass); *va_arg (arg, int *) = my leftOffset; break; case XmNrightOffset: Melder_assert (my parent -> widgetClass == xmFormWidgetClass); *va_arg (arg, int *) = my rightOffset; break; case XmNtopOffset: Melder_assert (my parent -> widgetClass == xmFormWidgetClass); *va_arg (arg, int *) = my topOffset; break; case XmNbottomOffset: Melder_assert (my parent -> widgetClass == xmFormWidgetClass); *va_arg (arg, int *) = my bottomOffset; break; case XmNminimum: *va_arg (arg, int *) = my minimum; break; case XmNmaximum: *va_arg (arg, int *) = my maximum; break; case XmNvalue: *va_arg (arg, int *) = my value; break; case XmNincrement: Melder_assert (my widgetClass == xmScrollBarWidgetClass); *va_arg (arg, int *) = my increment; break; case XmNpageIncrement: Melder_assert (my widgetClass == xmScrollBarWidgetClass); *va_arg (arg, int *) = my pageIncrement; break; case XmNsliderSize: Melder_assert (my widgetClass == xmScrollBarWidgetClass); *va_arg (arg, int *) = my sliderSize; break; case XmNdeleteResponse: Melder_assert (my widgetClass == xmShellWidgetClass); *va_arg (arg, int *) = my deleteResponse; break; case XmNcolumns: *va_arg (arg, int *) = 40; break; case XmNhorizontalScrollBar: *va_arg (arg, GuiObject *) = my motiff.scrolledWindow.horizontalBar; break; case XmNverticalScrollBar: *va_arg (arg, GuiObject *) = my motiff.scrolledWindow.verticalBar; break; default: { if (resource < 0 || resource >= sizeof motif_resourceNames / sizeof (char *)) Melder_flushError ("(XtVaGetValues:) Resource out of range (%d).", resource); else Melder_flushError ("(XtVaGetValues:) Unknown resource \"%s\".", motif_resourceNames [resource]); return; } } va_end (arg); } void XtVaSetValues (GuiObject me, ...) { va_list arg; va_start (arg, me); _motif_setValues (me, arg); va_end (arg); } Window XtWindow (GuiObject me) { #if mac return (Window) my macWindow; #elif win return (Window) my window; #endif } /***** MOTIF *****/ void XmAddWMProtocolCallback (GuiObject me, Atom protocol, XtCallbackProc callback, char *closure) { if (protocol == 'delw') { my motiff.shell.goAwayCallback = callback; my motiff.shell.goAwayClosure = closure; #if mac ChangeWindowAttributes (my macWindow, kWindowCloseBoxAttribute, 0); #endif } } GuiObject XmCreateBulletinBoard (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmBulletinBoardWidgetClass, parent, name); } GuiObject XmCreateBulletinBoardDialog (GuiObject parent, const char *name, ArgList dum1, int dum2) { GuiObject shell = XmCreateDialogShell (parent, name, dum1, dum2); return XmCreateBulletinBoard (shell, name, dum1, dum2); } GuiObject XmCreateCascadeButton (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmCascadeButtonWidgetClass, parent, name); } GuiObject XmCreateCascadeButtonGadget (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmCascadeButtonGadgetClass, parent, name); } GuiObject XmCreateDialogShell (GuiObject parent, const char *name, ArgList dum1, int dum2) { GuiObject shell; theDialogHint = True; shell = XmCreateShell (parent, name, dum1, dum2); theDialogHint = False; return shell; } GuiObject XmCreateForm (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmFormWidgetClass, parent, name); } GuiObject XmCreateFormDialog (GuiObject parent, const char *name, ArgList dum1, int dum2) { GuiObject shell = XmCreateDialogShell (parent, name, dum1, dum2); return XmCreateForm (shell, name, dum1, dum2); } GuiObject XmCreateMenuBar (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmMenuBarWidgetClass, parent, name); } GuiObject XmCreatePulldownMenu (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmPulldownMenuWidgetClass, parent, name); } GuiObject XmCreateRadioBox (GuiObject parent, const char *name, ArgList dum1, int dum2) { GuiObject result = createWidget (xmRowColumnWidgetClass, parent, name); (void) dum1; (void) dum2; XtVaSetValues (result, XmNradioBehavior, True, NULL); return result; } GuiObject XmCreateRowColumn (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmRowColumnWidgetClass, parent, name); } GuiObject XmCreateScale (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmScaleWidgetClass, parent, name); } GuiObject XmCreateScrollBar (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmScrollBarWidgetClass, parent, name); } GuiObject XmCreateScrolledWindow (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmScrolledWindowWidgetClass, parent, name); } GuiObject XmCreateSeparator (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmSeparatorWidgetClass, parent, name); } GuiObject XmCreateSeparatorGadget (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmSeparatorWidgetClass, parent, name); } GuiObject XmCreateShell (GuiObject parent, const char *name, ArgList dum1, int dum2) { GuiObject me = createWidget (xmShellWidgetClass, parent, name); (void) dum1; (void) dum2; _motif_addShell (me); return me; } GuiObject XmCreateToggleButtonGadget (GuiObject parent, const char *name, ArgList dum1, int dum2) { (void) dum1; (void) dum2; return createWidget (xmToggleButtonWidgetClass, parent, name); } void XmScaleGetValue (GuiObject me, int *value_return) { Melder_assert (my widgetClass == xmScaleWidgetClass); *value_return = my value; } void XmScaleSetValue (GuiObject me, int value) { Melder_assert (my widgetClass == xmScaleWidgetClass); my value = value; #if win SendMessage (my window, PBM_SETPOS, (WPARAM) value, 0); #elif mac SetPortWindowPort (my macWindow); #endif _motif_update (me, 0); } void XmScrollBarGetValues (GuiObject me, int *value, int *sliderSize, int *increment, int *pageIncrement) { Melder_assert (my widgetClass == xmScrollBarWidgetClass); *value = my value; *sliderSize = my sliderSize; *increment = my increment; *pageIncrement = my pageIncrement; } void XmScrollBarSetValues (GuiObject me, int value, int sliderSize, int increment, int pageIncrement, Boolean notify) { Melder_assert (my widgetClass == xmScrollBarWidgetClass); my value = value; my sliderSize = sliderSize; my increment = increment; my pageIncrement = pageIncrement; NativeScrollBar_set (me); #if mac if (theGui.duringUpdate) _Gui_invalidateWidget (me); /* HACK: necessary because VisRgn has temporarily been changed. */ #endif if (notify) _Gui_callCallbacks (me, & my motiff.scrollBar.valueChangedCallbacks, NULL); } Boolean XmToggleButtonGadgetGetState (GuiObject me) { Melder_assert (MEMBER (me, ToggleButton)); Melder_assert (my inMenu); #if mac short mark; GetItemMark (my nat.entry.handle, my nat.entry.item, & mark); return mark != noMark; #elif win return GetMenuState (my nat.entry.handle, my nat.entry.id, MF_BYCOMMAND) & MF_CHECKED ? True : False; #endif } void XmToggleButtonGadgetSetState (GuiObject me, Boolean value, Boolean notify) { Melder_assert (MEMBER (me, ToggleButton)); Melder_assert (my inMenu); NativeMenuItem_check (me, value); if (notify) _Gui_callCallbacks (me, & my motiff.toggleButton.valueChangedCallbacks, NULL); } #if mac static void _motif_update (GuiObject me, EventRecord *event) { GuiObject subview; RgnHandle visRgn; if (! my managed || my inMenu) return; for (subview = my firstChild; subview != NULL; subview = subview -> nextSibling) { if (subview -> widgetClass != xmShellWidgetClass) /* Only in same mac window. */ _motif_update (subview, event); } visRgn = NewRgn (); GetPortVisibleRegion (GetWindowPort (my macWindow), visRgn); if (! RectInRgn (& my rect, visRgn)) { DisposeRgn (visRgn); return; } SetPortWindowPort (my macWindow); switch (my widgetClass) { case xmPushButtonWidgetClass: case xmToggleButtonWidgetClass: case xmScrollBarWidgetClass: { _GuiMac_clipOnParent (me); Draw1Control (my nat.control.handle); GuiMac_clipOff (); } break; case xmListWidgetClass: _GuiMacList_update (me, visRgn); break; case xmDrawingAreaWidgetClass: _GuiMacDrawingArea_update (me); break; case xmTextWidgetClass: _GuiMacText_update (me); break; case xmLabelWidgetClass: { _GuiMac_clipOnParent (me); Draw1Control (my nat.control.handle); GuiMac_clipOff (); } break; case xmCascadeButtonWidgetClass: { if (my isControl) { /* In window menu bar or in dynamic menu. */ _GuiMac_clipOnParent (me); Draw1Control (my nat.control.handle); /* BUG: should make insensitive if not my shell.active or my macWindow != FrontWindow () */ GuiMac_clipOff (); } } break; case xmRowColumnWidgetClass: { /*if (my rowColumnType == XmMENU_BAR) DrawThemeMenuBarBackground (& my rect, 0, 0);*/ } break; case xmScrolledWindowWidgetClass: { _GuiMac_clipOnParent (me); FrameRect (& my rect); GuiMac_clipOff (); } break; case xmFrameWidgetClass: { _GuiMac_clipOnParent (me); FrameRect (& my rect); GuiMac_clipOff (); } break; case xmScaleWidgetClass: { Rect r = my rect; _GuiMac_clipOnParent (me); InsetRect (& r, 20, 15); FrameRect (& r); InsetRect (& r, 1, 1); if (my value <= my minimum) { EraseRect (& r); } else { Rect active = r, inactive = r; active. right = r. left + (float) (r. right - r. left) * my value / (my maximum - my minimum + 1); PaintRect (& active); inactive. left = active. right; EraseRect ( & inactive); } GuiMac_clipOff (); } break; default: break; } DisposeRgn (visRgn); } #elif win static void _motif_update (GuiObject me, void *event) { (void) me; (void) event; } #endif #if mac static void _motif_processUpdateEvent (EventRecord *event) { WindowPtr macwindow = (WindowPtr) event -> message; GuiObject shell = (GuiObject) GetWRefCon (macwindow); Rect rect; int right, bottom; if (! shell) return; BeginUpdate (macwindow); theGui.duringUpdate = True; SetPortWindowPort (macwindow); if (! shell -> motiff.shell.isDialog) { Rect portRect; GetWindowPortBounds (macwindow, & portRect); right = portRect. right, bottom = portRect. bottom; SetRect (& rect, right - 15, bottom - 15, right + 1, bottom + 1); ClipRect (& rect); DrawGrowIcon (macwindow); GuiMac_clipOff (); } _motif_update (shell, event); EndUpdate (macwindow); theGui.duringUpdate = False; } #endif void XmUpdateDisplay (GuiObject displayDummy) { /* * Send update messages to all shells. */ int i; (void) displayDummy; for (i = 0; i < MAXIMUM_NUMBER_OF_SHELLS; i ++) { GuiObject shell = theShells [i]; #if mac if (shell && shell -> managed) { RgnHandle updateRegion = NewRgn (); GetWindowRegion (shell -> nat.window.ptr, kWindowUpdateRgn, updateRegion); if (Melder_debug != 12 && ! EmptyRgn (updateRegion)) { /* * Hack an update event and send it to me. */ EventRecord event; event. message = (long) shell -> nat.window.ptr; _motif_processUpdateEvent (& event); } #if 0 QDGetDirtyRegion (GetWindowPort (shell -> nat.window.ptr), updateRegion); QDFlushPortBuffer (GetWindowPort (shell -> nat.window.ptr), updateRegion); #endif DisposeRgn (updateRegion); GuiWindow_drain (shell); } #endif } #if win GdiFlush (); #endif } /***** EVENT *****/ static long numberOfTextWidgets = 0, textWidgetLocation = 0; static GuiObject nextTextWidget = NULL; static void _motif_inspectTextWidgets (GuiObject me, GuiObject text) { for (GuiObject sub = my firstChild; sub != NULL; sub = sub -> nextSibling) { if (MEMBER (sub, Shell)) continue; if (MEMBER (sub, Text)) { numberOfTextWidgets ++; if (sub == text) { textWidgetLocation = numberOfTextWidgets; } } else { _motif_inspectTextWidgets (sub, text); } } } static void _motif_getLocatedTextWidget (GuiObject me) { for (GuiObject sub = my firstChild; sub != NULL; sub = sub -> nextSibling) { if (MEMBER (sub, Shell)) continue; if (MEMBER (sub, Text)) { numberOfTextWidgets ++; if (numberOfTextWidgets == textWidgetLocation) { nextTextWidget = sub; } } else { _motif_getLocatedTextWidget (sub); } } } static GuiObject _motif_getNextTextWidget (GuiObject shell, GuiObject text, bool backward) { numberOfTextWidgets = 0; textWidgetLocation = 0; _motif_inspectTextWidgets (shell, text); if (numberOfTextWidgets == 0) return NULL; // no tab navigation if there is no text widget (shouldn't normally occur) Melder_assert (textWidgetLocation >= 1); Melder_assert (textWidgetLocation <= numberOfTextWidgets); if (numberOfTextWidgets == 1) return NULL; // no tab navigation if there is only one text widget nextTextWidget = NULL; if (backward) { textWidgetLocation --; // tab to previous text widget if (textWidgetLocation < 1) textWidgetLocation = numberOfTextWidgets; // if at beginning, then tab around to last text widget } else { textWidgetLocation ++; // tab to next text widget if (textWidgetLocation > numberOfTextWidgets) textWidgetLocation = 1; // if at end, then tab around to first text widget } numberOfTextWidgets = 0; _motif_getLocatedTextWidget (shell); return nextTextWidget; } #if win static void on_scroll (GuiObject me, UINT part, int pos) { if (my maximum == my minimum) return; switch (part) { case SB_LINEUP: my value -= my increment; break; case SB_LINEDOWN: my value += my increment; break; case SB_PAGEUP: my value -= my pageIncrement; break; case SB_PAGEDOWN: my value += my pageIncrement; break; #if SCROLL32 case SB_THUMBTRACK: case SB_THUMBPOSITION: my value = my minimum + pos * ((my maximum - my minimum - my sliderSize) / (32767.0 - (32767.0 * my sliderSize) / (my maximum - my minimum))); break; #else case SB_THUMBTRACK: case SB_THUMBPOSITION: my value = pos; break; #endif default: break; } if (my value < my minimum) my value = my minimum; if (my value > my maximum - my sliderSize) my value = my maximum - my sliderSize; NativeScrollBar_set (me); if (part == SB_THUMBTRACK || part == SB_THUMBPOSITION) _Gui_callCallbacks (me, & my motiff.scrollBar.dragCallbacks, (XtPointer) (ULONG_PTR) part); else _Gui_callCallbacks (me, & my motiff.scrollBar.valueChangedCallbacks, (XtPointer) (ULONG_PTR) part); } #elif mac static pascal void _motif_scrollBarAction (ControlHandle maccontrol, short part) { GuiObject me = (GuiObject) GetControlReference (maccontrol); if (me == NULL || part == 0) return; switch (part) { case kControlUpButtonPart: my value -= my increment; break; case kControlDownButtonPart: my value += my increment; break; case kControlPageUpPart: my value -= my pageIncrement; break; case kControlPageDownPart: my value += my pageIncrement; break; case kControlIndicatorPart: my value = GetControl32BitValue (maccontrol); break; default: break; } if (my value < my minimum) my value = my minimum; if (my value > my maximum - my sliderSize) my value = my maximum - my sliderSize; SetControl32BitValue (maccontrol, my value); if (part == kControlIndicatorPart) { _Gui_callCallbacks (me, & my motiff.scrollBar.dragCallbacks, (XtPointer) (long) part); } else { _Gui_callCallbacks (me, & my motiff.scrollBar.valueChangedCallbacks, (XtPointer) (long) part); } } #endif #if mac static void _motif_activateControls (GuiObject me, Boolean act) { ControlHandle macControl; GuiObject control; UInt16 numberOfControls, icontrol; Melder_assert (MEMBER (me, Shell)); Melder_assert (my nat.window.rootControl); CountSubControls (my nat.window.rootControl, & numberOfControls); SetPortWindowPort (my macWindow); for (icontrol = 1; icontrol <= numberOfControls; icontrol ++) { GetIndexedSubControl (my nat.window.rootControl, icontrol, & macControl); control = (GuiObject) GetControlReference (macControl); if (control && control -> magicNumber == 15111959 && control -> managed) { _GuiMac_clipOnParent (control); HiliteControl (macControl, act && ! control -> insensitive ? 0 : 255 ); GuiMac_clipOff (); } } } static void _motif_activateGrowIcon (GuiObject me, Boolean act) { if (! my motiff.shell.isDialog) { WindowPtr macwindow = my nat.window.ptr; Rect portRect, rect; int right, bottom; Melder_assert (macwindow != NULL); Melder_assert (GetWindowKind (macwindow) == userKind); GetWindowPortBounds (macwindow, & portRect); right = portRect. right, bottom = portRect. bottom; SetRect (& rect, right - 15, bottom - 15, right + 1, bottom + 1); SetPortWindowPort (macwindow); ClipRect (& rect); DrawGrowIcon (macwindow); GuiMac_clipOff (); if (act) ValidWindowRect (macwindow, & rect); } } static void _motif_activateText (GuiObject me, Boolean act) { if (act) { _GuiText_setTheTextFocus (my textFocus); } else { _GuiMac_clearTheTextFocus (); } } static void _motif_activateRest (GuiObject me, Boolean act) { GuiObject sub; if (! my managed) return; SetPortWindowPort (my macWindow); for (sub = my firstChild; sub != NULL; sub = sub -> nextSibling) if (sub -> widgetClass != xmShellWidgetClass) /* Only in same mac window. */ _motif_activateRest (sub, act); if (my isControl) { return; /* Already done by _motif_activateControls. */ } else if (my widgetClass == xmListWidgetClass) { _GuiMacList_activate (me, act); } else if (my widgetClass == xmTextWidgetClass) { /* This is handled on the shell level. */ return; } else if (my widgetClass == xmCascadeButtonWidgetClass && my parent -> widgetClass == xmRowColumnWidgetClass && my parent -> rowColumnType == XmMENU_BAR) { if (! act) { static RGBColor lightGrey = { 32768, 32768, 32768 }, blak; GetForeColor (& blak); RGBForeColor (& lightGrey); _motif_update (me, NULL); RGBForeColor (& blak); } else { _motif_update (me, NULL); } } } static void _motif_processActivateEvent (EventRecord *event) { WindowPtr macwindow = (WindowPtr) event -> message; int act = event -> modifiers & 1; if (GetWindowKind (macwindow) >= userKind) { GuiObject shell = (GuiObject) GetWRefCon (macwindow); if (! shell) return; Melder_assert (GetWindowKind (macwindow) == userKind); if (! BACKGROUND_WINDOWS_ARE_ACTIVE) shell -> motiff.shell.active = act; if (! BACKGROUND_WINDOWS_ARE_ACTIVE) _motif_activateControls (shell, act); _motif_activateGrowIcon (shell, act); if (BACKGROUND_WINDOWS_ARE_ACTIVE && shell -> dialogStyle == XmDIALOG_FULL_APPLICATION_MODAL) { /* * Bypass the Mac activation scheme if Motif style is on. * Deactivate all other shells. */ for (int i = 0; i < MAXIMUM_NUMBER_OF_SHELLS; i ++) { GuiObject otherShell = theShells [i]; if (otherShell && otherShell -> managed && otherShell != shell) { otherShell -> motiff.shell.active = ! act; _motif_activateControls (otherShell, ! act); _motif_activateRest (otherShell, ! act); } } } _motif_activateText (shell, act); if (! BACKGROUND_WINDOWS_ARE_ACTIVE) _motif_activateRest (shell, act); } } static void _motif_processOsEvent (EventRecord *event) { unsigned char messageKind = ((unsigned long) event -> message & 0xFF000000) >> 24; if (messageKind == mouseMovedMessage) { Melder_fatal ("_motif_processOsEvent -- mouseMovedMessage"); Point location = event -> where; } else if (messageKind == suspendResumeMessage && 0) { //Melder_fatal ("_motif_processOsEvent -- suspendResumeMessage"); WindowPtr frontWindow = FrontWindow (); int act = event -> message & resumeFlag ? true : false; theBackground = ! act; for (int i = 0; i < MAXIMUM_NUMBER_OF_SHELLS; i ++) { GuiObject shell = theShells [i]; if (! shell || ! shell -> managed) continue; if (BACKGROUND_WINDOWS_ARE_ACTIVE) { if (theGui.modalDialog && theGui.modalDialog != shell -> nat.window.ptr) continue; } else { if (shell -> nat.window.ptr != frontWindow) continue; } shell -> motiff.shell.active = act; _motif_activateControls (shell, act); _motif_activateGrowIcon (shell, act); _motif_activateText (shell, act); _motif_activateRest (shell, act); } } } static void _motif_processHighLevelEvent (EventRecord *event) { AEProcessAppleEvent (event); } static GuiObject _motif_findDrawingArea (GuiObject me) { GuiObject sub; if (my widgetClass == xmDrawingAreaWidgetClass) return me; for (sub = my firstChild; sub != NULL; sub = sub -> nextSibling) if (sub -> widgetClass != xmShellWidgetClass) { /* Only in same mac window. */ GuiObject drawingArea = _motif_findDrawingArea (sub); if (drawingArea) return drawingArea; } return NULL; /* No DrawingArea found. */ } static int _motif_shell_processKeyboardEquivalent (GuiObject shell, unsigned char kar, int modifiers, EventRecord *event) { WindowPtr macWindow; int imenu; if (! shell) return 0; macWindow = shell -> nat.window.ptr; /* * If the user presses Command-?, i.e. the Command key plus the Shift key plus the "/?" key, * Macintosh sends us the "/" character instead of the "?" character. Fix this. */ if (modifiers == (_motif_COMMAND_MASK | _motif_SHIFT_MASK)) { switch (kar) { case '/': kar = '\?'; break; case '[': kar = '{'; break; case ']': kar = '}'; break; case '\'': kar = '\"'; break; case ',': kar = '<'; break; case '.': kar = '>'; break; case '\\': kar = '|'; break; case '-': kar = '_'; break; case '=': kar = '+'; break; case '`': kar = '~'; break; default: break; } } /* * If the user presses Option-Command-A, Macintosh sends us byte 140 instead of the "A" character. * These bytes are above 128, except Option-Command-I and Option-Command-N, which give 94 and 126 instead, * but since these are shifted characters ("^" and "~"), there will be no confusion. So we fix it all. */ if (modifiers == (_motif_COMMAND_MASK | _motif_OPTION_MASK)) { if (modifiers & _motif_SHIFT_MASK) { /* Ignore the triple modifiers! */ } else { switch ((unsigned char) kar) { case 94: kar = 'I'; break; case 126: kar = 'N'; break; case 140: kar = 'A'; break; case 141: kar = 'C'; break; case 160: kar = 'T'; break; case 167: kar = 'S'; break; case 168: kar = 'R'; break; case 169: kar = 'G'; break; case 171: kar = 'E'; break; case 172: kar = 'U'; break; case 180: kar = 'Y'; break; case 181: kar = 'M'; break; case 182: kar = 'D'; break; case 183: kar = 'W'; break; case 185: kar = 'P'; break; case 186: kar = 'B'; break; case 189: kar = 'Z'; break; case 191: kar = 'O'; break; case 194: kar = 'L'; break; case 195: kar = 'V'; break; case 196: kar = 'F'; break; case 197: kar = 'X'; break; case 198: kar = 'J'; break; case 207: kar = 'Q'; break; case 250: kar = 'H'; break; case 251: kar = 'K'; break; default: break; } } } for (imenu = 1; imenu <= MAXIMUM_NUMBER_OF_MENUS; imenu ++) if (theMenus [imenu] && theMenus [imenu] -> macWindow == macWindow) { GuiObject child; for (child = theMenus [imenu] -> firstChild; child != NULL; child = child -> nextSibling) if ((child -> widgetClass == xmPushButtonWidgetClass || child -> widgetClass == xmToggleButtonWidgetClass) && child -> motiff.pushButton.acceleratorChar == kar && child -> motiff.pushButton.acceleratorModifiers == modifiers) { if (child -> widgetClass == xmPushButtonWidgetClass && child -> activateCallback && ! child -> insensitive) { child -> activateCallback (child, child -> activateClosure, (XtPointer) event); return 1; } else if (child -> widgetClass == xmToggleButtonWidgetClass) { XmToggleButtonGadgetSetState (child, 1 - XmToggleButtonGadgetGetState (child), False); _Gui_callCallbacks (child, & child -> motiff.toggleButton.valueChangedCallbacks, (XtPointer) event); return 1; } } } return 0; } static void _motif_processKeyboardEquivalent (unsigned char kar, int modifiers, EventRecord *event) { /* * First try to send the key command to the active shell. * If that fails, try to send the key command to the application shell. */ if (! _motif_shell_processKeyboardEquivalent ((GuiObject) GetWRefCon (FrontWindow ()), kar, modifiers, event)) _motif_shell_processKeyboardEquivalent (theApplicationShell, kar, modifiers, event); } static bool _motif_processKeyDownEvent (EventHandlerCallRef nextHandler, EventRef eventRef, EventRecord *event) { /* * This routine determines whether a key-down message is a menu shortcut or is meant to go to a text widget. * It has to find this out fast, so it cannot go through all the menu structures for each key-down. * Therefore, every shell maintains a bit list of which of the lower accelerators are used. */ GuiObject shell = (GuiObject) GetWRefCon (FrontWindow ()); if (shell == NULL) { // Probably a system window such as an error dialog or file selection dialog. //CallNextEventHandler (nextHandler, eventRef); return false; } GuiObject text = theGui.textFocus; unsigned char charCode = event -> message & charCodeMask, keyCode = (event -> message & keyCodeMask) >> 8; int modifiers = 0; if (event -> modifiers & cmdKey) modifiers |= _motif_COMMAND_MASK; if (event -> modifiers & optionKey) modifiers |= _motif_OPTION_MASK; if (event -> modifiers & shiftKey) modifiers |= _motif_SHIFT_MASK; //Melder_casual ("char code %d, modifiers %d", charCode, event -> modifiers); if (charCode < 32) { if (charCode == 13) { /* User pressed Return. */ /* * First test for keyboard shortcut. */ if (shell && (shell -> motiff.shell.lowAccelerators [modifiers] & 1 << GuiMenu_ENTER)) { _motif_processKeyboardEquivalent (GuiMenu_ENTER, modifiers, event); return true; } /* * Then look for default button in active window. */ if (shell && shell -> defaultButton) { if (_GuiMacButton_tryToHandleShortcutKey (shell -> defaultButton, event)) { return true; } /* * Otherwise, hand it to a text widget. */ } /* * Then look for a text widget with an activate callback. */ if (_GuiMacText_tryToHandleReturnKey (nextHandler, eventRef, text, event)) return true; /* * Otherwise, hand it to a text widget. */ } else if (charCode == 27) { /* User pressed Escape. */ /* * First test for keyboard shortcut. */ if (shell && (shell -> motiff.shell.lowAccelerators [modifiers] & 1 << GuiMenu_ESCAPE)) { _motif_processKeyboardEquivalent (GuiMenu_ESCAPE, modifiers, event); return true; } /* * Then look for cancel button in active window. */ if (shell && shell -> cancelButton) { if (_GuiMacButton_tryToHandleShortcutKey (shell -> cancelButton, event)) { return true; } /* * Do not hand it to a text widget. */ return true; } /* * Do not hand it to a text widget. */ return true; } else if (charCode == 9) { /* User pressed Tab. */ /* * First test for keyboard shortcut. */ if (shell && (shell -> motiff.shell.lowAccelerators [modifiers] & 1 << GuiMenu_TAB)) { _motif_processKeyboardEquivalent (GuiMenu_TAB, modifiers, event); return true; } /* * Next, try tab navigation. */ if (text) { GuiObject nextTextWidget = _motif_getNextTextWidget (shell, text, modifiers & _motif_SHIFT_MASK); if (nextTextWidget != NULL) { _GuiText_setTheTextFocus (nextTextWidget); GuiText_setSelection (nextTextWidget, 0, 10000000); return true; } } /* * Otherwise, hand it to a text widget. */ } else if (charCode == 8) { /* User pressed Backspace. */ /* * First test for keyboard shortcut. */ if (shell && (shell -> motiff.shell.lowAccelerators [modifiers] & 1 << GuiMenu_BACKSPACE)) { _motif_processKeyboardEquivalent (GuiMenu_BACKSPACE, modifiers, event); return true; } /* * Otherwise, hand it to a text widget. */ } else if (charCode == 5) { /* Help button. Simulate Command-?. */ _motif_processKeyboardEquivalent ('?', _motif_COMMAND_MASK | _motif_SHIFT_MASK, event); return true; } else if (charCode == 16) { /* F1... F12 */ int fkey = keyCode == 0x7A ? 1 : keyCode == 0x78 ? 2 : keyCode == 0x63 ? 3 : keyCode == 0x76 ? 4 : keyCode == 0x60 ? 5 : keyCode == 0x61 ? 6 : keyCode == 0x62 ? 7 : keyCode == 0x64 ? 8 : keyCode == 0x65 ? 9 : keyCode == 0x6D ? 10 : keyCode == 0x67 ? 11 : keyCode == 0x6F ? 12 : 0; if (fkey) _motif_processKeyboardEquivalent (GuiMenu_F1 - 1 + fkey, modifiers, event); return true; } else if (charCode == 11) { _motif_processKeyboardEquivalent (GuiMenu_PAGE_UP, modifiers, event); return true; /* BUG: we should implement a scroll up in the text widget (IM V-193). */ } else if (charCode == 12) { _motif_processKeyboardEquivalent (GuiMenu_PAGE_DOWN, modifiers, event); return true; /* BUG: we should implement a scroll down in the text widget (IM V-193). */ } else if (charCode == 1) { _motif_processKeyboardEquivalent (GuiMenu_HOME, modifiers, event); return true; /* BUG: we should implement a top left scroll in the text widget (IM V-192). */ } else if (charCode == 4) { _motif_processKeyboardEquivalent (GuiMenu_END, modifiers, event); return true; /* BUG: we should implement a bottom right scroll in the text widget (IM V-193). */ } else if (charCode == 28) { /* * First test for keyboard shortcut. */ if (shell && (shell -> motiff.shell.lowAccelerators [modifiers] & 1 << GuiMenu_LEFT_ARROW)) { _motif_processKeyboardEquivalent (GuiMenu_LEFT_ARROW, modifiers, event); return true; } /* * Otherwise, hand it to a text widget. */ } else if (charCode == 29) { if (shell && (shell -> motiff.shell.lowAccelerators [modifiers] & 1 << GuiMenu_RIGHT_ARROW)) { _motif_processKeyboardEquivalent (GuiMenu_RIGHT_ARROW, modifiers, event); return true; } } else if (charCode == 30) { if (shell && (shell -> motiff.shell.lowAccelerators [modifiers] & 1 << GuiMenu_UP_ARROW)) { _motif_processKeyboardEquivalent (GuiMenu_UP_ARROW, modifiers, event); return true; } } else if (charCode == 31) { if (shell && (shell -> motiff.shell.lowAccelerators [modifiers] & 1 << GuiMenu_DOWN_ARROW)) { _motif_processKeyboardEquivalent (GuiMenu_DOWN_ARROW, modifiers, event); return true; } } } else if (charCode == 127) { if (shell && (shell -> motiff.shell.lowAccelerators [modifiers] & 1 << GuiMenu_DELETE)) { _motif_processKeyboardEquivalent (GuiMenu_DELETE, modifiers, event); return true; } /* * Otherwise, hand it to a text widget (forward delete). */ } /* * If the Command key is pressed with a printable character, this is always a menu shortcut. */ else if (modifiers & _motif_COMMAND_MASK) { /* * For shortcuts, the status of the Caps Lock key is immaterial. */ unsigned char kar = toupper (charCode); /* * Command-X/C/V/period are defined even if there is no menu. * The existence of a text widget forces Command-C to mean 'Copy'. * The existence of an editable text widget forces Command-X to mean 'Cut' and Command-V to mean 'Paste'. */ if (_GuiMacText_tryToHandleClipboardShortcut (nextHandler, eventRef, text, kar, event)) return true; #define USE_COMMAND_PERIOD_AS_CANCEL 0 if (USE_COMMAND_PERIOD_AS_CANCEL && kar == '.') { /* * Command-period: first test for "Escape" keyboard shortcut. */ if (shell && (shell -> motiff.shell.lowAccelerators [0] & 1 << GuiMenu_ESCAPE)) { _motif_processKeyboardEquivalent (GuiMenu_ESCAPE, 0, event); return true; } /* * Then look for cancel button in active window. */ if (shell && shell -> cancelButton) { if (_GuiMacButton_tryToHandleShortcutKey (shell -> cancelButton, event)) { return true; } } } /* * The text widget did not catch any Command-X/C/V/period. */ _motif_processKeyboardEquivalent (kar, modifiers, event); /* * After executing a menu shortcut, do not send the key to a text widget as well. */ if (kar == '`') return false; // Command-` means "cycle through Praat's windows" return true; } if (_GuiMacText_tryToHandleKey (nextHandler, eventRef, text, keyCode, charCode, event)) return true; /* Last chance: try drawingArea. */ if (shell) { GuiObject drawingArea = _motif_findDrawingArea (shell); if (drawingArea && _GuiMacDrawingArea_tryToHandleKey (drawingArea, event)) { return true; } } return false; } static void mac_processMenuChoice (long choice, EventRecord *event) { int macMenuID = HiWord (choice), macMenuItem = LoWord (choice); GuiObject menu, item; if (macMenuID == 0) return; menu = theMenus [macMenuID == kHMHelpMenuID ? MAXIMUM_NUMBER_OF_MENUS : macMenuID]; if (menu == NULL) return; item = menu -> firstChild; if (macMenuID == kHMHelpMenuID) macMenuItem -= theHelpMenuOffset; while (item && macMenuItem > 1) { if (item -> widgetClass != xmPulldownMenuWidgetClass && item -> managed) macMenuItem --; /* Count managed buttons and separators only. */ item = item -> nextSibling; } Melder_assert (item != NULL); while (item && ! item -> managed) item = item -> nextSibling; Melder_assert (item != NULL); if (item -> activateCallback) item -> activateCallback (item, item -> activateClosure, (XtPointer) event); else if (item -> widgetClass == xmToggleButtonWidgetClass) { XmToggleButtonGadgetSetState (item, 1 - XmToggleButtonGadgetGetState (item), False); _Gui_callCallbacks (item, & item -> motiff.toggleButton.valueChangedCallbacks, (XtPointer) event); } } static void _motif_processMouseDownEvent (EventRecord *event) { WindowPtr macvenster; int part = FindWindow (event -> where, & macvenster); switch (part) { case inMenuBar: { long choice = MenuSelect (event -> where); mac_processMenuChoice (choice, event); HiliteMenu (0); } break; case inSysWindow: { } break; case inDrag: { RgnHandle greyRegion; Rect greyBounds; if (macvenster != FrontWindow ()) { if (theGui.modalDialog && theGui.modalDialog != macvenster) { SysBeep (1); return; } else { SelectWindow (macvenster); } } greyRegion = GetGrayRgn (); GetRegionBounds (greyRegion, & greyBounds); DragWindow (macvenster, event -> where, & greyBounds); } break; case inGoAway: { if (TrackGoAway (macvenster, event -> where)) { GuiObject shell = (GuiObject) GetWRefCon (macvenster); int deleteResponse; if (! shell) return; deleteResponse = shell -> deleteResponse; /* Save this, in case the callback should kill the widget (XmDO_NOTHING). */ if (shell -> motiff.shell.goAwayCallback) shell -> motiff.shell.goAwayCallback (shell, shell -> motiff.shell.goAwayClosure, event); if (deleteResponse == XmDESTROY) { XtDestroyWidget (shell); } else if (deleteResponse == XmUNMAP) { /* Unmapping is not the same as unmanaging. The following duplicates some of the code of XtUnmanageChild, but does not clear the 'managed' attribute. */ _GuiMac_clearTheTextFocus (); if (macvenster == theGui.modalDialog) theGui.modalDialog = NULL; HideWindow (macvenster); } } } break; case inGrow: { RgnHandle greyRegion = GetGrayRgn (); Rect greyBounds; long newSize; GetRegionBounds (greyRegion, & greyBounds); newSize = GrowWindow (macvenster, event -> where, & greyBounds); if (newSize != 0) { GuiObject shell = (GuiObject) GetWRefCon (macvenster); int oldWidth, oldHeight, newWidth, newHeight; if (! shell) return; oldWidth = shell -> width, oldHeight = shell -> height; newWidth = LoWord (newSize), newHeight = HiWord (newSize); shell -> width = newWidth; shell -> height = newHeight; //Melder_casual ("Grow: old and new size: %d %d %d %d", oldWidth, oldHeight, newWidth, newHeight); shellResizeWidget (shell, 0, 0, newWidth - oldWidth, newHeight - oldHeight); } } break; case inZoomIn: case inZoomOut: { GuiObject shell = (GuiObject) GetWRefCon (macvenster); if (shell) { int oldWidth = shell -> width, oldHeight = shell -> height; Rect bounds; if (shell -> motiff.shell.canFullScreen) { if (part == inZoomOut) { SetSystemUIMode (kUIModeAllSuppressed, 0); Point size = { 3000, 4000 }; ZoomWindowIdeal (macvenster, inZoomOut, & size); } else { SetSystemUIMode (kUIModeNormal, 0); Point size = { 900, 1440 }; ZoomWindowIdeal (macvenster, inZoomIn, & size); } } else { ZoomWindow (macvenster, part, 1); } GetWindowPortBounds (macvenster, & bounds); int newWidth = bounds.right - bounds.left; int newHeight = bounds.bottom - bounds.top; //Melder_casual ("Zoom: old and new size %d %d %d %d", oldWidth, oldHeight, newWidth, newHeight); shell -> width = newWidth; shell -> height = newHeight; shellResizeWidget (shell, 0, 0, newWidth - oldWidth, newHeight - oldHeight); } } break; case inContent: { if (macvenster != FrontWindow ()) { if (theGui.modalDialog && theGui.modalDialog != macvenster) { SysBeep (1); return; } SelectWindow (macvenster); if (! BACKGROUND_WINDOWS_ARE_ACTIVE) return; XmUpdateDisplay (NULL); } if (GetWindowKind (macvenster) == userKind) { ControlHandle maccontrol; ControlPartCode controlPart; SetPortWindowPort (macvenster); GlobalToLocal (& event -> where); maccontrol = FindControlUnderMouse (event -> where, macvenster, & controlPart); if (maccontrol) { GuiObject control = (GuiObject) GetControlReference (maccontrol); if (! control) return; if (control -> magicNumber != 15111959 || ! control -> managed) goto LABEL_clickedOutsideControl; event -> message = controlPart; switch (controlPart) { case kControlListBoxPart: { _GuiMacList_handleControlClick (control, event); } break; case kControlButtonPart: case kControlLabelPart: { if (control -> widgetClass == xmPushButtonWidgetClass) { _GuiMacButton_handleClick (control, event); } else if (control -> widgetClass == xmCascadeButtonWidgetClass) { /* Cascade button. */ GuiObject menu = control -> subMenuId; if (menu && ! control -> insensitive) { Point pos; long choice = 0; _GuiMac_clipOnParent (control); HiliteControl (maccontrol, 10); GuiMac_clipOff (); SetPt (& pos, control -> rect.left + 2, control -> rect.bottom); LocalToGlobal (& pos); choice = PopUpMenuSelect (menu -> nat.menu.handle, pos.v, pos.h, 1); /* Beware: we must unhighlight the cascade button NOW, because callbacks may destroy it. */ _GuiMac_clipOnParent (control); HiliteControl (maccontrol, 0); GuiMac_clipOff (); mac_processMenuChoice (choice, event); } } } break; case kControlCheckBoxPart: { /* Check box or radio button. */ if (control -> isRadioButton) { _GuiMacRadioButton_handleClick (control, event); } else { _GuiMacCheckButton_handleClick (control, event); } } break; case kControlIndicatorPart: // live scrolling case kControlUpButtonPart: case kControlDownButtonPart: case kControlPageUpPart: case kControlPageDownPart: { static ControlActionUPP theControlActionUPP; if (! theControlActionUPP) theControlActionUPP = NewControlActionUPP (_motif_scrollBarAction); HandleControlClick (maccontrol, event -> where, event -> modifiers, theControlActionUPP); } break; case kControlEditTextPart: _GuiMacText_handleClick (control, event); break; default: break; } } else { /* Clicked in content region, but not in a control. */ GuiObject shell, clicked; LABEL_clickedOutsideControl: shell = (GuiObject) GetWRefCon (macvenster); if (! shell) return; clicked = _motif_findSubwidget (shell, event -> where. h, event -> where. v); if (clicked) { if (clicked -> widgetClass == xmListWidgetClass) { _GuiMacList_handleClick (clicked, event); } else if (clicked -> widgetClass == xmTextWidgetClass) { if (clicked -> isControl) { /* A click in the margin of an EditText control !! */ _GuiMacText_handleClick (clicked, event); // BUG?: ; /* Do nothing. To react would feel like clicking after all text. */ } else { _GuiMacText_handleClick (clicked, event); } } else if (clicked -> widgetClass == xmDrawingAreaWidgetClass) { _GuiMacDrawingArea_handleClick (clicked, event); } else if (clicked -> widgetClass == xmCascadeButtonWidgetClass && 0) { GuiObject menu = clicked -> subMenuId; if (menu && ! clicked -> insensitive) { Point pos; long choice = 0; Rect r = clicked -> rect; r.left -= 4; r.right += 4; r.top -= 1; _GuiMac_clipOnParent (clicked); InvertRect (& r); GuiMac_clipOff (); SetPt (& pos, r.left + 1, r.bottom); LocalToGlobal (& pos); choice = PopUpMenuSelect (menu -> nat.menu.handle, pos.v, pos.h, 1); /* Beware: we must unhighlight the cascade button NOW, because callbacks may destroy it. */ SetPortWindowPort (clicked -> macWindow); _motif_update (clicked, NULL); mac_processMenuChoice (choice, event); } } } } } } break; default: break; } } static pascal OSStatus keyDownEventHandler (EventHandlerCallRef nextHandler, EventRef eventRef, void *userData) { (void) nextHandler; (void) userData; EventRecord eventRecord; ConvertEventRefToEventRecord (eventRef, & eventRecord); #if 0 switch (eventRecord. what) { case nullEvent: break; case mouseDown: _motif_processMouseDownEvent (& eventRecord); break; case mouseUp: break; case keyDown: _motif_processKeyDownEvent (nextHandler, eventRef, & eventRecord); break; case keyUp: break; case autoKey: _motif_processKeyDownEvent (nextHandler, eventRef, & eventRecord); break; case updateEvt: _motif_processUpdateEvent (& eventRecord); break; case activateEvt: _motif_processActivateEvent (& eventRecord); break; case osEvt: _motif_processOsEvent (& eventRecord); break; case kHighLevelEvent: _motif_processHighLevelEvent (& eventRecord); break; default: break; } return noErr; #else if (_motif_processKeyDownEvent (nextHandler, eventRef, & eventRecord)) return noErr; #endif return eventNotHandledErr; } #endif void XtNextEvent (XEvent *xevent) { #if win GetMessage (xevent, NULL, 0, 0); #elif mac static EventHandlerUPP keyDownEventHandlerUPP; if (keyDownEventHandlerUPP == NULL) { keyDownEventHandlerUPP = NewEventHandlerUPP (keyDownEventHandler); EventTypeSpec keyDownEventTypeSpecs [2] = { { kEventClassKeyboard, kEventRawKeyDown }, { kEventClassKeyboard, kEventRawKeyRepeat } }; //InstallEventHandler (theUserFocusEventTarget, keyDownEventHandlerUPP, 2, keyDownEventTypeSpecs, NULL, NULL); InstallApplicationEventHandler (keyDownEventHandlerUPP, 2, keyDownEventTypeSpecs, NULL, NULL); } /* * The waiting time should be short enough to allow Melder_progress to wait for an event. * Therefore we take 1 clock tick, so that if Melder_progress updates every 15 clock ticks, * the performance loss will not be more than 7 percent. */ WaitNextEvent (everyEvent, (EventRecord *) xevent, 1, NULL); #endif } static void processWorkProcsAndTimeOuts (void) { long i; if (theNumberOfWorkProcs) for (i = 9; i >= 1; i --) if (theWorkProcs [i]) if (theWorkProcs [i] (theWorkProcClosures [i])) XtRemoveWorkProc (i); #if ! defined (macintosh) if (theNumberOfTimeOuts) { clock_t now = clock (); for (i = 1; i < 10; i ++) if (theTimeOutProcs [i]) { static volatile clock_t timeElapsed; /* Careful: use 32-bit integers circularly; prevent optimization. */ timeElapsed = now - theTimeOutStarts [i]; if (timeElapsed > theTimeOutIntervals [i]) { theTimeOutProcs [i] (theTimeOutClosures [i], & i); XtRemoveTimeOut (i); } } } #endif } void GuiNextEvent (XEvent *xevent) { #if win if (theNumberOfWorkProcs != 0 || theNumberOfTimeOuts != 0) { if (PeekMessage (xevent, 0, 0, 0, PM_REMOVE)) { // Message available? ; // Hand message to XtDispatchEvent. } else { processWorkProcsAndTimeOuts (); // Handle chores during idle time. xevent -> message = 0; // Hand null message to XtDispatchEvent. } } else GetMessage (xevent, NULL, 0, 0); // Be neighbour-friendly: do not hand null events. #elif mac processWorkProcsAndTimeOuts (); XtNextEvent (xevent); #endif } #if win static int win_shell_processKeyboardEquivalent (GuiObject me, int kar, int modifiers) { for (int imenu = 1; imenu <= MAXIMUM_NUMBER_OF_MENUS; imenu ++) if (theMenus [imenu] && theMenus [imenu] -> shell == me) { for (GuiObject child = theMenus [imenu] -> firstChild; child != NULL; child = child -> nextSibling) { if ((child -> widgetClass == xmPushButtonWidgetClass || child -> widgetClass == xmToggleButtonWidgetClass) && child -> motiff.pushButton.acceleratorChar == kar && child -> motiff.pushButton.acceleratorModifiers == modifiers) { if (child -> activateCallback && ! child -> insensitive) { child -> activateCallback (child, child -> activateClosure, 0); return 1; } else if (child -> widgetClass == xmToggleButtonWidgetClass) { XmToggleButtonGadgetSetState (child, 1 - XmToggleButtonGadgetGetState (child), False); _Gui_callCallbacks (child, & child -> motiff.toggleButton.valueChangedCallbacks, 0); return 1; } } } } return 0; } static int win_processKeyboardEquivalent (GuiObject me, int kar, int modifiers) { /* * First try to send the key command to the active shell. * If that fails, try to send the key command to the application shell. */ if (win_shell_processKeyboardEquivalent (me, kar, modifiers)) return 1; if (win_shell_processKeyboardEquivalent (theApplicationShell, kar, modifiers)) return 1; return 0; } static GuiObject _motif_findDrawingArea (GuiObject me) { if (my widgetClass == xmDrawingAreaWidgetClass) return me; for (GuiObject sub = my firstChild; sub != NULL; sub = sub -> nextSibling) if (! MEMBER (sub, Shell)) { /* Only in same top window. */ GuiObject drawingArea = _motif_findDrawingArea (sub); if (drawingArea) return drawingArea; } return NULL; /* No DrawingArea found. */ } #endif void XtDispatchEvent (XEvent *xevent) { #if mac EventRecord *event = (EventRecord *) xevent; switch (event -> what) { case nullEvent: break; case mouseDown: _motif_processMouseDownEvent (event); break; case mouseUp: break; //case keyDown: _motif_processKeyDownEvent (event); break; case keyUp: break; //case autoKey: _motif_processKeyDownEvent (event); break; case updateEvt: _motif_processUpdateEvent (event); break; case activateEvt: _motif_processActivateEvent (event); break; case osEvt: _motif_processOsEvent (event); break; case kHighLevelEvent: _motif_processHighLevelEvent (event); break; default: break; } #else MSG *message = (MSG *) xevent; if (message -> message == 0) return; // null message from PeekMessage during work proc or time out. /*if (message -> message == WM_KEYDOWN || message -> message == WM_SYSKEYDOWN) { int kar = LOWORD (message -> wParam); int modifiers = 0; GuiObject me = (GuiObject) GetWindowLongPtr (message -> hwnd, GWLP_USERDATA); if (GetKeyState (VK_CONTROL) < 0) modifiers |= _motif_COMMAND_MASK; if (GetKeyState (VK_MENU) < 0) modifiers |= _motif_OPTION_MASK; if (GetKeyState (VK_SHIFT) < 0) modifiers |= _motif_SHIFT_MASK; if(kar>=48)Melder_flushError ("modifiers:%s%s%s\nmessage: %s\nkar: %d", modifiers & _motif_COMMAND_MASK ? " control" : "", modifiers & _motif_OPTION_MASK ? " alt" : "", modifiers & _motif_SHIFT_MASK ? " shift" : "", message -> message == WM_KEYDOWN ? "keydown" : "syskeydown", kar); }*/ /* * Intercept accelerators, which may be function keys or Command combinations. * Some Alt-GR combinations denote special characters (e.g. backslash) on some (e.g. German) keyboards; * in such a case, the message is WM_KEYDOWN, and the reported modifier keys are Control (!) and Alt * (on a German keyboard, the backslash can be generated by Ctrl-Alt-ringel-s as well); * otherwise Alt keys give WM_SYSKEYDOWN messages. */ if (message -> message == WM_KEYDOWN && (GetKeyState (VK_CONTROL) < 0 || ! (message -> lParam & (1<<29))) || message -> message == WM_SYSKEYDOWN && GetKeyState (VK_MENU) < 0 && (message -> lParam & (1<<29)) || // R&N 413: Alt key is pressed message -> message == WM_SYSKEYDOWN && GetKeyState (VK_CONTROL) < 0) { int kar = LOWORD (message -> wParam); GuiObject me = (GuiObject) GetWindowLongPtr (message -> hwnd, GWLP_USERDATA); int modifiers = 0; if (GetKeyState (VK_CONTROL) < 0) modifiers |= _motif_COMMAND_MASK; if (GetKeyState (VK_MENU) < 0) modifiers |= _motif_OPTION_MASK; if (GetKeyState (VK_SHIFT) < 0) modifiers |= _motif_SHIFT_MASK; /*if(kar>=48)Melder_casual ("modifiers:%s%s%s\nmessage: %s\nkar: %d", modifiers & _motif_COMMAND_MASK ? " control" : "", modifiers & _motif_OPTION_MASK ? " alt" : "", modifiers & _motif_SHIFT_MASK ? " shift" : "", message -> message == WM_KEYDOWN ? "keydown" : "syskeydown", kar);*/ if (me && my shell) { unsigned long acc = my shell -> motiff.shell.lowAccelerators [modifiers]; //if (kar != VK_CONTROL) Melder_casual ("%d %d", acc, kar); if (kar < 48) { if (kar == VK_BACK) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_BACKSPACE) { win_processKeyboardEquivalent (my shell, GuiMenu_BACKSPACE, modifiers); return; } } else if (kar == VK_TAB) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_TAB) { win_processKeyboardEquivalent (my shell, GuiMenu_TAB, modifiers); return; } } else if (kar == VK_RETURN) { /* Shortcut, default button, or text. */ //Melder_information (L"RETURN ", Melder_integer (acc), L" def ", Melder_integer ((long) my shell -> defaultButton)); if (acc & 1 << GuiMenu_ENTER) { win_processKeyboardEquivalent (my shell, GuiMenu_ENTER, modifiers); return; } else { if (my shell -> defaultButton && _GuiWinButton_tryToHandleShortcutKey (my shell -> defaultButton)) return; } } else if (kar == VK_ESCAPE) { /* Shortcut or cancel button. */ if (acc & 1 << GuiMenu_ESCAPE) { win_processKeyboardEquivalent (my shell, GuiMenu_ESCAPE, modifiers); return; } else { if (my shell -> cancelButton && _GuiWinButton_tryToHandleShortcutKey (my shell -> cancelButton)) return; } return; } else if (kar == VK_PRIOR) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_PAGE_UP) { win_processKeyboardEquivalent (my shell, GuiMenu_PAGE_UP, modifiers); return; } } else if (kar == VK_NEXT) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_PAGE_DOWN) { win_processKeyboardEquivalent (my shell, GuiMenu_PAGE_DOWN, modifiers); return; } } else if (kar == VK_HOME) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_HOME) { win_processKeyboardEquivalent (my shell, GuiMenu_HOME, modifiers); return; } } else if (kar == VK_END) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_END) { win_processKeyboardEquivalent (my shell, GuiMenu_END, modifiers); return; } } else if (kar == VK_LEFT) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_LEFT_ARROW) { win_processKeyboardEquivalent (my shell, GuiMenu_LEFT_ARROW, modifiers); return; } } else if (kar == VK_RIGHT) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_RIGHT_ARROW) { win_processKeyboardEquivalent (my shell, GuiMenu_RIGHT_ARROW, modifiers); return; } } else if (kar == VK_UP) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_UP_ARROW) { win_processKeyboardEquivalent (my shell, GuiMenu_UP_ARROW, modifiers); return; } } else if (kar == VK_DOWN) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_DOWN_ARROW) { win_processKeyboardEquivalent (my shell, GuiMenu_DOWN_ARROW, modifiers); return; } } else if (kar == VK_INSERT) { /* Shortcut. */ win_processKeyboardEquivalent (my shell, GuiMenu_INSERT, modifiers); return; } else if (kar == VK_DELETE) { /* Shortcut or text. */ if (acc & 1 << GuiMenu_DELETE) { win_processKeyboardEquivalent (my shell, GuiMenu_DELETE, modifiers); return; } } else if (kar == VK_HELP) { /* Simulate Command-?. */ win_processKeyboardEquivalent (my shell, '?', modifiers | _motif_SHIFT_MASK); return; } } else if (kar >= VK_F1 && kar <= VK_F12) { /* 112...123 */ /* * She has pressed one of the F keys. */ if (win_processKeyboardEquivalent (my shell, kar - VK_F1 + GuiMenu_F1, modifiers)) return; /* Let windowProc handle Alt-F4 etc. */ /* * If the Command key is pressed with a printable character, this is often a menu shortcut. */ } else if (modifiers & _motif_COMMAND_MASK) { if (MEMBER (me, Text) && (kar == 'X' || kar == 'C' || kar == 'V' || kar == 'Z')) { ; // Let window proc handle text editing. } else if (kar >= 186) { int shift = modifiers & _motif_SHIFT_MASK; /* * BUG: The following is not internationally correct. */ if (kar == 186 && win_processKeyboardEquivalent (my shell, shift ? ':' : ';', modifiers) || kar == 187 && win_processKeyboardEquivalent (my shell, shift ? '+' : '=', modifiers) || kar == 188 && win_processKeyboardEquivalent (my shell, shift ? '<' : ',', modifiers) || kar == 189 && win_processKeyboardEquivalent (my shell, shift ? '_' : '-', modifiers) || kar == 190 && win_processKeyboardEquivalent (my shell, shift ? '>' : '.', modifiers) || kar == 191 && win_processKeyboardEquivalent (my shell, shift ? '?' : '/', modifiers) || kar == 192 && win_processKeyboardEquivalent (my shell, shift ? '~' : '`', modifiers) || kar == 219 && win_processKeyboardEquivalent (my shell, shift ? '{' : '[', modifiers) || /* Alt-GR-ringel-s is here. */ kar == 220 && win_processKeyboardEquivalent (my shell, shift ? '|' : '\\', modifiers) || kar == 221 && win_processKeyboardEquivalent (my shell, shift ? '}' : ']', modifiers) || kar == 222 && win_processKeyboardEquivalent (my shell, shift ? '\"' : '\'', modifiers)) { return; } } else { if (win_processKeyboardEquivalent (my shell, kar, modifiers)) return; /* Handle shortcuts like Ctrl-T and Ctrl-Alt-T. */ /* Let window proc handle international Alt-GR (= Ctrl-Alt) sequences, which are plain characters. */ } } /* Other characters: to text. */ } /* Not me or not my shell: let windowProc handle. */ } else if (message -> message == WM_CHAR) { int kar = LOWORD (message -> wParam); /* * Catch character messages to push buttons and toggle buttons: * divert them to a drawing area, if possible. */ GuiObject me = (GuiObject) GetWindowLongPtr (message -> hwnd, GWLP_USERDATA); if (me && MEMBER2 (me, PushButton, ToggleButton)) { GuiObject drawingArea = _motif_findDrawingArea (my shell); if (drawingArea) { _GuiWinDrawingArea_handleKey (drawingArea, kar); // TODO: event -> key? return; } } /* * Next, try tab navigation. */ if (me && MEMBER (me, Text) && kar == 9) { GuiObject nextTextWidget = _motif_getNextTextWidget (my shell, me, GetKeyState (VK_SHIFT) < 0); if (nextTextWidget != NULL) { _GuiText_setTheTextFocus (nextTextWidget); GuiText_setSelection (nextTextWidget, 0, 10000000); return; } } } else if (message -> message == WM_LBUTTONDOWN) { /* * Catch mouse-down messages to cascade buttons: * post the associated menu, if any. */ GuiObject me = (GuiObject) GetWindowLongPtr (message -> hwnd, GWLP_USERDATA); //Melder_information (Melder_integer ((long) me), L" -- ", Melder_integer ((long) my subMenuId)); if (me && MEMBER (me, CascadeButton) && my subMenuId) { RECT rect; GetWindowRect (my window, & rect); TrackPopupMenu (my subMenuId -> nat.menu.handle, TPM_LEFTBUTTON | TPM_LEFTALIGN | TPM_TOPALIGN, rect.left, rect.bottom - 3, 0, my parent -> window, NULL); return; } } TranslateMessage (xevent); // Generate WM_CHAR messages. DispatchMessage (xevent); #endif } void GuiMainLoop () { for (;;) { XEvent event; GuiNextEvent (& event); XtDispatchEvent (& event); } } #if win extern int main (int argc, char *argv []); int APIENTRY WinMain (HINSTANCE instance, HINSTANCE previousInstance, LPSTR commandLine, int commandShow) { int argc = 4; char instanceString [20], commandShowString [20]; const char *argv [4]; (void) previousInstance; argv [0] = "dummy"; sprintf (instanceString, "%p", instance); sprintf (commandShowString, "%d", commandShow); argv [1] = & instanceString [0]; argv [2] = & commandShowString [0]; argv [3] = Melder_wcsToUtf8 (GetCommandLineW ()); // it's OK to ignore the possibility of low memory if (argv [3] [0] == '\"') { argv [3] ++; // skip quote while (argv [3] [0] != '\"') { argv [3] ++; } argv [3] ++; // skip quote if (argv [3] [0] == ' ') argv [3] ++; } else { while (argv [3] [0] != ' ' && argv [3] [0] != '\0') { argv [3] ++; } if (argv [3] [0] == ' ') argv [3] ++; } return main (argc, (char **) & argv [0]); } static void on_close (HWND window) { GuiObject me = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (me) { if (my widgetClass == xmShellWidgetClass) { int deleteResponse = my deleteResponse; /* Save this, in case the callback should kill the widget (XmDO_NOTHING). */ GuiObject parent = my parent; if (my motiff.shell.goAwayCallback) my motiff.shell.goAwayCallback (me, my motiff.shell.goAwayClosure, NULL); if (deleteResponse == XmDESTROY) { XtDestroyWidget (me); } else if (deleteResponse == XmUNMAP) { /* Unmapping is not the same as unmanaging. One of the oldest bugs in Praat was that in the Windows edition the Picture window could not be closed a second time, and that after it had been closed and opened the scroll bars did not move when the user resized the window. The solution was to use only some of the code from XtUnmanageChild here, without clearing the 'managed' attribute. */ _GuiText_handleFocusLoss (my textFocus); ShowWindow (my window, SW_HIDE); } return; } else FORWARD_WM_CLOSE (window, DefWindowProc); } else FORWARD_WM_CLOSE (window, DefWindowProc); } static GuiObject findItem (GuiObject menu, int id) { GuiObject child = menu -> firstChild; for (child = menu -> firstChild; child != NULL; child = child -> nextSibling) { if (child -> widgetClass == xmPulldownMenuWidgetClass) { GuiObject result = findItem (child, id); if (result) return result; } else { Melder_assert (MEMBER4 (child, PushButton, ToggleButton, CascadeButton, Separator)); if (child -> nat.entry.id == id) return child; } } return NULL; } static void on_command (HWND window, int id, HWND controlWindow, UINT codeNotify) { GuiObject parent = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (parent) { if (controlWindow) { GuiObject control = (GuiObject) GetWindowLongPtr (controlWindow, GWLP_USERDATA); if (control) { switch (control -> widgetClass) { /* * Clicking on a button takes away the focus from a text widget. * We have already been notified of that by EN_KILLFOCUS. * We have to put the focus back (see GuiText.c, parenthesized discussion 1.4); * this has to be done before calling the callbacks, because these may destroy or hide the text widget. */ case xmPushButtonWidgetClass: /* * If EN_KILLFOCUS had not cleared the global text focus, * the following message would not actually do SetFocus! */ _GuiText_setTheTextFocus (control -> shell -> textFocus); _GuiWinButton_handleClick (control); break; case xmToggleButtonWidgetClass: _GuiText_setTheTextFocus (control -> shell -> textFocus); if (control -> isRadioButton) { _GuiWinRadioButton_handleClick (control); } else { _GuiWinCheckButton_handleClick (control); } break; case xmListWidgetClass: if (codeNotify == LBN_SELCHANGE) { _GuiWinList_handleClick (control); } else FORWARD_WM_COMMAND (window, id, controlWindow, codeNotify, DefWindowProc); break; case xmTextWidgetClass: if (codeNotify == EN_CHANGE) { _GuiText_handleValueChanged (control); } else if (codeNotify == EN_SETFOCUS) { _GuiText_handleFocusReception (control); } else if (codeNotify == EN_KILLFOCUS) { _GuiText_handleFocusLoss (control); /* For button clicks (see above). */ } break; default: break; } } else FORWARD_WM_COMMAND (window, id, controlWindow, codeNotify, DefWindowProc); } else { // menu choice GuiObject menuBar = NULL; if (MEMBER (parent, Shell)) menuBar = parent -> nat.shell.menuBar; else if (MEMBER (parent, RowColumn)) menuBar = parent; if (menuBar) { GuiObject item = findItem (menuBar, id); if (item) { if (item -> widgetClass == xmPushButtonWidgetClass) { if (item -> activateCallback) item -> activateCallback (item, item -> activateClosure, 0); } else if (item -> widgetClass == xmToggleButtonWidgetClass) { XmToggleButtonGadgetSetState (item, 1 - XmToggleButtonGadgetGetState (item), False); _Gui_callCallbacks (item, & item -> motiff.toggleButton.valueChangedCallbacks, 0); } } } } } else FORWARD_WM_COMMAND (window, id, controlWindow, codeNotify, DefWindowProc); } static void on_destroy (HWND window) { (void) window; } static void on_lbuttonDown (HWND window, BOOL doubleClick, int x, int y, UINT flags) { GuiObject me = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (me) { if (MEMBER (me, DrawingArea)) { _GuiWinDrawingArea_handleClick (me, x, y); } else FORWARD_WM_LBUTTONDOWN (window, doubleClick, x, y, flags, DefWindowProc); } else FORWARD_WM_LBUTTONDOWN (window, doubleClick, x, y, flags, DefWindowProc); } static void on_paint (HWND window) { GuiObject me = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (me) { if (my widgetClass == xmDrawingAreaWidgetClass) { _GuiWinDrawingArea_update (me); } else FORWARD_WM_PAINT (window, DefWindowProc); } else FORWARD_WM_PAINT (window, DefWindowProc); } static void on_hscroll (HWND window, HWND controlWindow, UINT code, int pos) { GuiObject parent = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (parent) { GuiObject control = (GuiObject) GetWindowLongPtr (controlWindow, GWLP_USERDATA); if (control) { on_scroll (control, code, pos); } else FORWARD_WM_HSCROLL (window, controlWindow, code, pos, DefWindowProc); } else FORWARD_WM_HSCROLL (window, controlWindow, code, pos, DefWindowProc); } static void on_vscroll (HWND window, HWND controlWindow, UINT code, int pos) { GuiObject parent = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (parent) { GuiObject control = (GuiObject) GetWindowLongPtr (controlWindow, GWLP_USERDATA); if (control) { on_scroll (control, code, pos); } else FORWARD_WM_VSCROLL (window, controlWindow, code, pos, DefWindowProc); } else FORWARD_WM_VSCROLL (window, controlWindow, code, pos, DefWindowProc); } static void on_size (HWND window, UINT state, int cx, int cy) { GuiObject me = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (me && MEMBER (me, Shell) && (state == SIZE_RESTORED || state == SIZE_MAXIMIZED)) { int oldWidth = my width, oldHeight = my height; int newWidth = cx; int newHeight = cy; my width = newWidth; my height = newHeight; FORWARD_WM_SIZE (window, state, cx, cy, DefWindowProc); if (! my managed) { } else if (my nat.shell.duringMoveWindow) // Yeah, a BUG fix. Only react to user actions. my nat.shell.duringMoveWindow = False; else if (newWidth != oldWidth || newHeight != oldHeight) { shellResizeWidget (me, 0, 0, newWidth - oldWidth, newHeight - oldHeight); } } else FORWARD_WM_SIZE (window, state, cx, cy, DefWindowProc); } static void on_key (HWND window, UINT key, BOOL down, int repeat, UINT flags) { Melder_assert (down == true); GuiObject me = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (me && key >= VK_LEFT && key <= VK_DOWN) { //Melder_warning ("Widget type ", Melder_integer (my widgetClass)); if (MEMBER (me, Shell)) { GuiObject drawingArea = _motif_findDrawingArea (me); if (drawingArea) { GuiObject textFocus = drawingArea -> shell -> textFocus; // BUG: ignore? _GuiWinDrawingArea_handleKey (drawingArea, key); } else { FORWARD_WM_KEYDOWN (window, key, repeat, flags, DefWindowProc); } } else FORWARD_WM_KEYDOWN (window, key, repeat, flags, DefWindowProc); } else { FORWARD_WM_KEYDOWN (window, key, repeat, flags, DefWindowProc); } } static void on_char (HWND window, TCHAR kar, int repeat) { GuiObject me = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (me) { //Melder_warning ("Widget type ", Melder_integer (my widgetClass)); if (MEMBER (me, Shell)) { GuiObject drawingArea = _motif_findDrawingArea (me); if (drawingArea) { GuiObject textFocus = drawingArea -> shell -> textFocus; // BUG: ignore? _GuiWinDrawingArea_handleKey (drawingArea, kar); } else { FORWARD_WM_CHAR (window, kar, repeat, DefWindowProc); } } else FORWARD_WM_CHAR (window, kar, repeat, DefWindowProc); } else { FORWARD_WM_CHAR (window, kar, repeat, DefWindowProc); } } static void on_move (HWND window, int x, int y) { GuiObject me = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); /*if (me && MEMBER (me, Shell)) { my x = x - ( my motiff.shell.isDialog ? GetSystemMetrics (SM_CXFIXEDFRAME) : GetSystemMetrics (SM_CXSIZEFRAME) ); my y = y - GetSystemMetrics (SM_CYCAPTION) - ( my motiff.shell.isDialog ? GetSystemMetrics (SM_CYFIXEDFRAME) : GetSystemMetrics (SM_CYSIZEFRAME) + GetSystemMetrics (SM_CYMENU) ); }*/ FORWARD_WM_MOVE (window, x, y, DefWindowProc); } static HBRUSH on_ctlColorStatic (HWND window, HDC hdc, HWND controlWindow, int type) { GuiObject parent = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); (void) type; if (parent) { GuiObject control = (GuiObject) GetWindowLongPtr (controlWindow, GWLP_USERDATA); if (control) { SetBkMode (hdc, TRANSPARENT); return GetStockBrush (LTGRAY_BRUSH); } } return FORWARD_WM_CTLCOLORSTATIC (window, hdc, controlWindow, DefWindowProc); } static HBRUSH on_ctlColorBtn (HWND window, HDC hdc, HWND controlWindow, int type) { GuiObject parent = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); (void) type; if (parent) { GuiObject control = (GuiObject) GetWindowLongPtr (controlWindow, GWLP_USERDATA); if (control) { SetBkMode (hdc, TRANSPARENT); return GetStockBrush (LTGRAY_BRUSH); } } return FORWARD_WM_CTLCOLORBTN (window, hdc, controlWindow, DefWindowProc); } static void on_activate (HWND window, UINT state, HWND hActive, BOOL minimized) { GuiObject me = (GuiObject) GetWindowLongPtr (window, GWLP_USERDATA); if (me && my widgetClass == xmShellWidgetClass) { if (state == WA_INACTIVE || minimized) { _GuiText_handleFocusLoss (my textFocus); } else { _GuiText_setTheTextFocus (my textFocus); } return; } else FORWARD_WM_ACTIVATE (window, state, hActive, minimized, DefWindowProc); } static LRESULT CALLBACK windowProc (HWND window, UINT message, WPARAM wParam, LPARAM lParam) { switch (message) { HANDLE_MSG (window, WM_CLOSE, on_close); HANDLE_MSG (window, WM_COMMAND, on_command); HANDLE_MSG (window, WM_DESTROY, on_destroy); HANDLE_MSG (window, WM_LBUTTONDOWN, on_lbuttonDown); HANDLE_MSG (window, WM_PAINT, on_paint); HANDLE_MSG (window, WM_HSCROLL, on_hscroll); HANDLE_MSG (window, WM_VSCROLL, on_vscroll); HANDLE_MSG (window, WM_SIZE, on_size); HANDLE_MSG (window, WM_KEYDOWN, on_key); HANDLE_MSG (window, WM_CHAR, on_char); HANDLE_MSG (window, WM_MOVE, on_move); HANDLE_MSG (window, WM_CTLCOLORBTN, on_ctlColorBtn); HANDLE_MSG (window, WM_CTLCOLORSTATIC, on_ctlColorStatic); HANDLE_MSG (window, WM_ACTIVATE, on_activate); case WM_USER: { /*if (IsIconic (window)) ShowWindow (window, SW_RESTORE); SetForegroundWindow (window);*/ return theUserMessageCallback ? theUserMessageCallback () : 1; } default: return DefWindowProc (window, message, wParam, lParam); } } int motif_win_mouseStillDown (void) { XEvent event; if (! GetCapture ()) SetCapture (theApplicationShell -> window); if (PeekMessage (& event, 0, 0, 0, PM_REMOVE)) { if (event. message == WM_LBUTTONUP) { DispatchMessage (& event); ReleaseCapture (); return False; } } return True; } void motif_win_setUserMessageCallback (int (*userMessageCallback) (void)) { theUserMessageCallback = userMessageCallback; } #endif #if mac void motif_mac_setUserMessageCallbackA (int (*userMessageCallback) (char *message)) { theUserMessageCallbackA = userMessageCallback; } void motif_mac_setUserMessageCallbackW (int (*userMessageCallback) (wchar_t *message)) { theUserMessageCallbackW = userMessageCallback; } #endif void Gui_setOpenDocumentCallback (void (*openDocumentCallback) (MelderFile file)) { theOpenDocumentCallback = openDocumentCallback; } void Gui_setQuitApplicationCallback (int (*quitApplicationCallback) (void)) { theQuitApplicationCallback = quitApplicationCallback; } #endif /* End of file motifEmulator.cpp */ sources_5316/sys/melder_sysenv.cpp0000644000176700017670000000672111633661464016144 0ustar paulpaul/* melder_sysenv.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2004/10/14 made Cygwin-compatible * Eric Carlson & Paul Boersma 2005/05/19 made MinGW-compatible * pb 2006/10/28 erased MacOS 9 stuff * pb 2011/04/05 C++ */ /* * This is a replacement for the CodeWarrior routines getenv and system, * into which many bugs were introduced in the year 2000. */ #if defined (_WIN32) #if ! defined (__CYGWIN__) && ! defined (__MINGW32__) #include #endif #include #include #include #endif #include "melder.h" wchar_t * Melder_getenv (const wchar_t *variableName) { #if defined (macintosh) || defined (UNIX) || defined (__MINGW32__) return Melder_peekUtf8ToWcs (getenv (Melder_peekWcsToUtf8 (variableName))); #elif defined (_WIN32) static wchar_t buffer [11] [255]; static int ibuffer = 0; if (++ ibuffer == 11) ibuffer = 0; long n = GetEnvironmentVariableW (variableName, buffer [ibuffer], 255); if (n == ERROR_ENVVAR_NOT_FOUND) return NULL; return & buffer [ibuffer] [0]; #endif } void Melder_system (const wchar *command) { #if defined (macintosh) || defined (UNIX) if (system (Melder_peekWcsToUtf8 (command)) != 0) Melder_throw ("System command failed."); #elif defined (_WIN32) STARTUPINFO siStartInfo; PROCESS_INFORMATION piProcInfo; wchar_t *comspec = Melder_getenv (L"COMSPEC"); // e.g. "C:\WINDOWS\COMMAND.COM" or "C:\WINNT\windows32\cmd.exe" if (comspec == NULL) { comspec = Melder_getenv (L"ComSpec"); } MelderString buffer = { 0 }; if (comspec != NULL) { MelderString_copy (& buffer, comspec); } else { OSVERSIONINFOEX osVersionInfo; memset (& osVersionInfo, 0, sizeof (OSVERSIONINFOEX)); osVersionInfo. dwOSVersionInfoSize = sizeof (OSVERSIONINFOEX); if (! GetVersionEx ((OSVERSIONINFO *) & osVersionInfo)) { osVersionInfo. dwOSVersionInfoSize = sizeof (OSVERSIONINFO); if (! GetVersionEx ((OSVERSIONINFO *) & osVersionInfo)) Melder_throw ("System command cannot find system version."); } switch (osVersionInfo. dwPlatformId) { case VER_PLATFORM_WIN32_NT: { MelderString_copy (& buffer, L"cmd.exe"); } break; case VER_PLATFORM_WIN32_WINDOWS: { MelderString_copy (& buffer, L"command.com"); } break; default: { MelderString_copy (& buffer, L"command.com"); } } } MelderString_append (& buffer, L" /c ", command); memset (& siStartInfo, 0, sizeof (siStartInfo)); siStartInfo. cb = sizeof (siStartInfo); if (! CreateProcess (NULL, buffer.string, NULL, NULL, TRUE, 0, NULL, NULL, & siStartInfo, & piProcInfo)) Melder_throw ("Cannot create subprocess."); WaitForSingleObject (piProcInfo. hProcess, -1); CloseHandle (piProcInfo. hProcess); CloseHandle (piProcInfo. hThread); #endif } /* End of file melder_sysenv.cpp */ sources_5316/sys/GuiCheckButton.cpp0000644000176700017670000001663211753741756016153 0ustar paulpaul/* GuiCheckButton.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/26 extracted from Motif * sdk 2007/12/27 gtk * sdk 2008/03/24 gtk * fb 2010/02/23 gtk * pb 2010/05/15 prevented procreation of valueChanged events in GuiCheckButton_setValue * pb 2010/06/14 HandleControlClick * pb 2010/11/28 removed Motif * pb 2011/04/06 C++ */ #include "GuiP.h" #undef iam #define iam(x) x me = (x) void_me #if win || mac #define iam_checkbutton \ Melder_assert (widget -> widgetClass == xmToggleButtonWidgetClass); \ GuiCheckButton me = (GuiCheckButton) widget -> userData #else #define iam_checkbutton \ GuiCheckButton me = (GuiCheckButton) _GuiObject_getUserData (widget) #endif typedef struct structGuiCheckButton { GuiObject widget; void (*valueChangedCallback) (void *boss, GuiCheckButtonEvent event); void *valueChangedBoss; #if gtk gulong valueChangedHandlerId; #endif } *GuiCheckButton; #if gtk static void _GuiGtkCheckButton_destroyCallback (GuiObject widget, gpointer void_me) { (void) widget; iam (GuiCheckButton); Melder_free (me); } static void _GuiGtkCheckButton_valueChangedCallback (GuiObject widget, gpointer void_me) { iam (GuiCheckButton); struct structGuiCheckButtonEvent event = { widget }; if (my valueChangedCallback != NULL) { my valueChangedCallback (my valueChangedBoss, & event); } } #elif win void _GuiWinCheckButton_destroy (GuiObject widget) { iam_checkbutton; _GuiNativeControl_destroy (widget); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiWinCheckButton_handleClick (GuiObject widget) { iam_checkbutton; if (my valueChangedCallback != NULL) { struct structGuiCheckButtonEvent event = { widget }; my valueChangedCallback (my valueChangedBoss, & event); } } #elif mac #if useCarbon void _GuiMacCheckButton_destroy (GuiObject widget) { iam_checkbutton; _GuiNativeControl_destroy (widget); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiMacCheckButton_handleClick (GuiObject widget, EventRecord *macEvent) { iam_checkbutton; _GuiMac_clipOnParent (widget); bool clicked = HandleControlClick (widget -> nat.control.handle, macEvent -> where, macEvent -> modifiers, NULL); GuiMac_clipOff (); if (clicked) { if (my valueChangedCallback != NULL) { struct structGuiCheckButtonEvent event = { widget }; my valueChangedCallback (my valueChangedBoss, & event); } } } #else #endif #endif GuiObject GuiCheckButton_create (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*valueChangedCallback) (void *boss, GuiCheckButtonEvent event), void *valueChangedBoss, unsigned long flags) { GuiCheckButton me = Melder_calloc_f (struct structGuiCheckButton, 1); my valueChangedCallback = valueChangedCallback; my valueChangedBoss = valueChangedBoss; #if gtk my widget = gtk_check_button_new_with_label (Melder_peekWcsToUtf8 (buttonText)); _GuiObject_setUserData (my widget, me); _GuiObject_position (my widget, left, right, top, bottom); if (parent && GTK_IS_BOX (parent)) { gtk_container_add (GTK_CONTAINER (parent), GTK_WIDGET (my widget)); } gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (my widget), (flags & GuiCheckButton_SET) != 0); if (flags & GuiCheckButton_INSENSITIVE) { GuiObject_setSensitive (my widget, false); } g_signal_connect (G_OBJECT (my widget), "destroy", G_CALLBACK (_GuiGtkCheckButton_destroyCallback), me); my valueChangedHandlerId = g_signal_connect (GTK_TOGGLE_BUTTON (my widget), "toggled", G_CALLBACK (_GuiGtkCheckButton_valueChangedCallback), me); #elif win my widget = _Gui_initializeWidget (xmToggleButtonWidgetClass, parent, buttonText); _GuiObject_setUserData (my widget, me); my widget -> isRadioButton = false; my widget -> window = CreateWindow (L"button", _GuiWin_expandAmpersands (buttonText), WS_CHILD | BS_AUTOCHECKBOX | WS_CLIPSIBLINGS, my widget -> x, my widget -> y, my widget -> width, my widget -> height, my widget -> parent -> window, (HMENU) 1, theGui.instance, NULL); SetWindowLongPtr (my widget -> window, GWLP_USERDATA, (LONG_PTR) my widget); SetWindowFont (my widget -> window, GetStockFont (ANSI_VAR_FONT), FALSE); _GuiObject_position (my widget, left, right, top, bottom); if (flags & GuiCheckButton_SET) { Button_SetCheck (my widget -> window, BST_CHECKED); } if (flags & GuiCheckButton_INSENSITIVE) { GuiObject_setSensitive (my widget, false); } #elif mac #if useCarbon my widget = _Gui_initializeWidget (xmToggleButtonWidgetClass, parent, buttonText); _GuiObject_setUserData (my widget, me); my widget -> isRadioButton = false; CreateCheckBoxControl (my widget -> macWindow, & my widget -> rect, NULL, (flags & GuiCheckButton_SET) != 0, true, & my widget -> nat.control.handle); Melder_assert (my widget -> nat.control.handle != NULL); SetControlReference (my widget -> nat.control.handle, (long) my widget); my widget -> isControl = true; _GuiNativeControl_setFont (my widget, 0, 13); _GuiNativeControl_setTitle (my widget); _GuiObject_position (my widget, left, right, top, bottom); if (flags & GuiCheckButton_INSENSITIVE) { GuiObject_setSensitive (my widget, false); } #else #endif #endif return my widget; } GuiObject GuiCheckButton_createShown (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*valueChangedCallback) (void *boss, GuiCheckButtonEvent event), void *valueChangedBoss, unsigned long flags) { GuiObject me = GuiCheckButton_create (parent, left, right, top, bottom, buttonText, valueChangedCallback, valueChangedBoss, flags); GuiObject_show (me); return me; } bool GuiCheckButton_getValue (GuiObject widget) { bool value = false; #if gtk value = gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (widget)); // gtk_check_button inherits from gtk_toggle_button #elif win value = (Button_GetState (widget -> window) & 0x0003) == BST_CHECKED; #elif mac #if useCarbon value = GetControlValue (widget -> nat.control.handle); #else #endif #endif return value; } void GuiCheckButton_setValue (GuiObject widget, bool value) { /* * The value should be set without calling the valueChanged callback. */ #if gtk iam_checkbutton; g_signal_handler_disconnect (GTK_TOGGLE_BUTTON (my widget), my valueChangedHandlerId); gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (my widget), value); my valueChangedHandlerId = g_signal_connect (GTK_TOGGLE_BUTTON (my widget), "toggled", G_CALLBACK (_GuiGtkCheckButton_valueChangedCallback), me); #elif win Button_SetCheck (widget -> window, value ? BST_CHECKED : BST_UNCHECKED); #elif mac #if useCarbon SetControlValue (widget -> nat.control.handle, value); #else #endif #endif } /* End of file GuiCheckButton.cpp */ sources_5316/sys/praat_script.cpp0000644000176700017670000005242111633222032015736 0ustar paulpaul/* praat_script.cpp * * Copyright (C) 1993-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2002/10/02 system -> Melder_system * pb 2003/03/09 set UiInterpreter back to NULL * pb 2004/02/22 allow numeric expressions after select/plus/minus * pb 2004/10/27 warning off * pb 2004/12/04 support for multiple open script dialogs with Apply buttons, both from "Run script..." and from added buttons * pb 2005/02/10 corrected bug in nowarn * pb 2005/08/22 renamed Control menu to "Praat" * pb 2006/01/11 local variables * pb 2006/12/28 theCurrentPraat * pb 2007/02/17 corrected the messages about trailing spaces * pb 2007/06/11 wchar * pb 2007/10/04 removed swscanf * pb 2009/01/04 allow proc(args) syntax * pb 2009/01/17 arguments to UiForm callbacks * pb 2009/01/20 pause uses a pause form * pb 2011/03/20 C++ * pb 2011/03/24 command no longer const * pb 2011/07/05 C++ */ #include #include "praatP.h" #include "praat_script.h" #include "sendpraat.h" #include "sendsocket.h" #include "UiPause.h" #include "DemoEditor.h" static int praat_findObjectFromString (Interpreter interpreter, const wchar *string) { try { int IOBJECT; while (*string == ' ') string ++; if (*string >= 'A' && *string <= 'Z') { /* * Find the object by its name. */ static MelderString buffer = { 0 }; MelderString_copy (& buffer, string); wchar *space = wcschr (buffer.string, ' '); if (space == NULL) Melder_throw ("Missing space in name."); *space = '\0'; wchar *className = & buffer.string [0], *givenName = space + 1; WHERE_DOWN (1) { Data object = (Data) OBJECT; if (wcsequ (className, Thing_className ((Thing) OBJECT)) && wcsequ (givenName, object -> name)) return IOBJECT; } Melder_throw ("No object with that name."); } else { /* * Find the object by its ID. */ double value; Interpreter_numericExpression (interpreter, string, & value); long id = (long) value; WHERE (ID == id) return IOBJECT; Melder_throw ("No object with number ", id, "."); } } catch (MelderError) { Melder_throw ("Object \"", string, L"\" does not exist."); } } Editor praat_findEditorFromString (const wchar_t *string) { int IOBJECT; while (*string == ' ') string ++; if (*string >= 'A' && *string <= 'Z') { WHERE_DOWN (1) { for (int ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) { Editor editor = (Editor) theCurrentPraatObjects -> list [IOBJECT]. editors [ieditor]; if (editor != NULL) { const wchar_t *name = wcschr (editor -> name, ' ') + 1; if (wcsequ (name, string)) return editor; } } } } else { WHERE_DOWN (1) { for (int ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) { Editor editor = (Editor) theCurrentPraatObjects -> list [IOBJECT]. editors [ieditor]; if (editor && wcsequ (editor -> name, string)) return editor; } } } Melder_throw ("Editor \"", string, "\" does not exist."); } void praat_executeCommand (Interpreter interpreter, wchar_t *command) { //Melder_casual ("praat_executeCommand: %ld: %ls", interpreter, command); if (command [0] == '\0' || command [0] == '#' || command [0] == '!' || command [0] == ';') /* Skip empty lines and comments. */; else if ((command [0] == '.' || command [0] == '+' || command [0] == '-') && isupper (command [1])) { // selection? int IOBJECT = praat_findObjectFromString (interpreter, command + 1); if (command [0] == '.') praat_deselectAll (); if (command [0] == '-') praat_deselect (IOBJECT); else praat_select (IOBJECT); praat_show (); } else if (islower (command [0])) { // all directives start with a lower-case letter if (wcsnequ (command, L"select ", 7)) { if (wcsnequ (command + 7, L"all", 3) && (command [10] == '\0' || command [10] == ' ' || command [10] == '\t')) { praat_selectAll (); praat_show (); } else { int IOBJECT = praat_findObjectFromString (interpreter, command + 7); praat_deselectAll (); praat_select (IOBJECT); praat_show (); } } else if (wcsnequ (command, L"plus ", 5)) { int IOBJECT = praat_findObjectFromString (interpreter, command + 5); praat_select (IOBJECT); praat_show (); } else if (wcsnequ (command, L"minus ", 6)) { int IOBJECT = praat_findObjectFromString (interpreter, command + 6); praat_deselect (IOBJECT); praat_show (); } else if (wcsnequ (command, L"echo ", 5)) { MelderInfo_open (); MelderInfo_write1 (command + 5); MelderInfo_close (); } else if (wcsnequ (command, L"clearinfo", 9)) { Melder_clearInfo (); } else if (wcsnequ (command, L"print ", 6)) { Melder_print (command + 6); } else if (wcsnequ (command, L"printtab", 8)) { Melder_print (L"\t"); } else if (wcsnequ (command, L"printline", 9)) { if (command [9] == ' ') Melder_print (command + 10); Melder_print (L"\n"); } else if (wcsnequ (command, L"fappendinfo ", 12)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The script command \"fappendinfo\" is not available inside pictures."); structMelderFile file = { 0 }; Melder_relativePathToFile (command + 12, & file); MelderFile_appendText (& file, Melder_getInfo ()); } else if (wcsnequ (command, L"unix ", 5)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The script command \"unix\" is not available inside manuals."); try { Melder_system (command + 5); } catch (MelderError) { Melder_throw ("Unix command \"", command + 5, "\" returned error status;\n" "if you want to ignore this, use `unix_nocheck' instead of `unix'."); } } else if (wcsnequ (command, L"unix_nocheck ", 13)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw (L"The script command \"unix_nocheck\" is not available inside manuals."); try { Melder_system (command + 13); } catch (MelderError) { Melder_clearError (); } } else if (wcsnequ (command, L"system ", 7)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw (L"The script command \"system\" is not available inside manuals."); try { Melder_system (command + 7); } catch (MelderError) { Melder_throw ("System command \"", command + 7, "\" returned error status;\n" "if you want to ignore this, use `system_nocheck' instead of `system'."); } } else if (wcsnequ (command, L"system_nocheck ", 15)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The script command \"system_nocheck\" is not available inside manuals."); try { Melder_system (command + 15); } catch (MelderError) { Melder_clearError (); } } else if (wcsnequ (command, L"nowarn ", 7)) { autoMelderWarningOff nowarn; praat_executeCommand (interpreter, command + 7); } else if (wcsnequ (command, L"noprogress ", 11)) { autoMelderProgressOff noprogress; praat_executeCommand (interpreter, command + 11); } else if (wcsnequ (command, L"nocheck ", 8)) { try { praat_executeCommand (interpreter, command + 8); } catch (MelderError) { Melder_clearError (); } } else if (wcsnequ (command, L"demo ", 5)) { autoDemoOpen demo; praat_executeCommand (interpreter, command + 5); } else if (wcsnequ (command, L"pause ", 6) || wcsequ (command, L"pause")) { if (theCurrentPraatApplication -> batch) return; // in batch we ignore pause statements UiPause_begin (theCurrentPraatApplication -> topShell, L"stop or continue", interpreter); therror UiPause_comment (wcsequ (command, L"pause") ? L"..." : command + 6); therror UiPause_end (1, 1, 0, L"Continue", NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, interpreter); therror } else if (wcsnequ (command, L"execute ", 8)) { praat_executeScriptFromFileNameWithArguments (command + 8); } else if (wcsnequ (command, L"editor", 6)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The script command \"editor\" is not available inside manuals."); if (command [6] == ' ' && isalpha (command [7])) { praatP. editor = praat_findEditorFromString (command + 7); } else if (interpreter && interpreter -> editorClass) { praatP. editor = praat_findEditorFromString (interpreter -> environmentName); } else { Melder_throw ("No editor specified."); } } else if (wcsnequ (command, L"endeditor", 9)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The script command \"endeditor\" is not available inside manuals."); praatP. editor = NULL; } else if (wcsnequ (command, L"sendpraat ", 10)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The script command \"sendpraat\" is not available inside manuals."); wchar programName [41], *q = & programName [0]; #ifdef macintosh #define SENDPRAAT_TIMEOUT 10 #else #define SENDPRAAT_TIMEOUT 0 #endif const wchar *p = command + 10; while (*p == ' ' || *p == '\t') p ++; while (*p != '\0' && *p != ' ' && *p != '\t' && q < programName + 39) *q ++ = *p ++; *q = '\0'; if (q == programName) Melder_throw ("Missing program name after `sendpraat'."); while (*p == ' ' || *p == '\t') p ++; if (*p == '\0') Melder_throw ("Missing command after `sendpraat'."); #if motif char *result = sendpraat (XtDisplay (theCurrentPraatApplication -> topShell), Melder_peekWcsToUtf8 (programName), SENDPRAAT_TIMEOUT, Melder_peekWcsToUtf8 (p)); if (result) Melder_throw (result, "\nMessage to ", programName, " not completed."); #endif } else if (wcsnequ (command, L"sendsocket ", 11)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The script command \"sendsocket\" is not available inside manuals."); wchar hostName [61], *q = & hostName [0]; const wchar_t *p = command + 11; while (*p == ' ' || *p == '\t') p ++; while (*p != '\0' && *p != ' ' && *p != '\t' && q < hostName + 59) *q ++ = *p ++; *q = '\0'; if (q == hostName) Melder_throw ("Missing host name after `sendsocket'."); while (*p == ' ' || *p == '\t') p ++; if (*p == '\0') Melder_throw ("Missing command after `sendsocket'."); char *result = sendsocket (Melder_peekWcsToUtf8 (hostName), Melder_peekWcsToUtf8 (p)); if (result) Melder_throw (result, "\nMessage to ", hostName, " not completed."); } else if (wcsnequ (command, L"filedelete ", 11)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The script command \"filedelete\" is not available inside manuals."); const wchar_t *p = command + 11; structMelderFile file = { 0 }; while (*p == ' ' || *p == '\t') p ++; if (*p == '\0') Melder_throw ("Missing file name after `filedelete'."); Melder_relativePathToFile (p, & file); MelderFile_delete (& file); } else if (wcsnequ (command, L"fileappend ", 11)) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The script command \"fileappend\" is not available inside manuals."); const wchar *p = command + 11; wchar_t path [256], *q = & path [0]; while (*p == ' ' || *p == '\t') p ++; if (*p == '\0') Melder_throw (L"Missing file name after `fileappend'."); if (*p == '\"') { for (;;) { int kar = * ++ p; if (kar == '\"') if (* ++ p == '\"') *q ++ = '\"'; else break; else if (kar == '\0') break; else *q ++ = kar; } } else { for (;;) { int kar = * p; if (kar == '\0' || kar == ' ' || kar == '\t') break; *q ++ = kar; p ++; } } *q = '\0'; if (*p == ' ' || *p == '\t') { structMelderFile file = { 0 }; Melder_relativePathToFile (path, & file); MelderFile_appendText (& file, p + 1); } } else { /* * This must be a formula command: * proc (args) */ Interpreter_voidExpression (interpreter, command); } } else { /* Simulate menu choice. */ wchar *arguments; /* Parse command line into command and arguments. */ /* The separation is formed by the three dots. */ if ((arguments = wcsstr (command, L"...")) == NULL || wcslen (arguments) < 4) { static wchar dummy = { 0 }; arguments = & dummy; } else { arguments += 4; if (arguments [-1] != ' ' && arguments [-1] != '0') { Melder_throw ("There should be a space after the three dots."); } arguments [-1] = '\0'; // new end of "command" } /* See if command exists and is available; ignore separators. */ /* First try loose commands, then fixed commands. */ if (theCurrentPraatObjects == & theForegroundPraatObjects && praatP. editor != NULL) { Editor_doMenuCommand ((Editor) praatP. editor, command, arguments, interpreter); therror } else if (theCurrentPraatObjects != & theForegroundPraatObjects && (wcsnequ (command, L"Save ", 5) || wcsnequ (command, L"Write ", 6) || wcsnequ (command, L"Append ", 7) || wcsequ (command, L"Quit"))) { Melder_throw ("Commands that write files (including Quit) are not available inside manuals."); } else { bool theCommandIsAnExistingAction = false; try { theCommandIsAnExistingAction = praat_doAction (command, arguments, interpreter); } catch (MelderError) { /* * We only get here if the command *was* an existing action. * Anything could have gone wrong in its execution, * but one invisible problem can be checked here. */ if (arguments [0] != '\0' && arguments [wcslen (arguments) - 1] == ' ') { Melder_throw ("It may be helpful to remove the trailing spaces in \"", arguments, "\"."); } else { throw; } } if (! theCommandIsAnExistingAction) { bool theCommandIsAnExistingMenuCommand = false; try { theCommandIsAnExistingMenuCommand = praat_doMenuCommand (command, arguments, interpreter); } catch (MelderError) { /* * We only get here if the command *was* an existing menu command. * Anything could have gone wrong in its execution, * but one invisible problem can be checked here. */ if (arguments [0] != '\0' && arguments [wcslen (arguments) - 1] == ' ') { Melder_throw ("It may be helpful to remove the trailing spaces in \"", arguments, L"\"."); } else { throw; } } if (! theCommandIsAnExistingMenuCommand) { if (wcsnequ (command, L"ARGS ", 5)) { Melder_throw ("Command \"ARGS\" no longer supported. Instead use \"form\" and \"endform\"."); } else if (wcschr (command, '=')) { Melder_throw ("Command \"", command, "\" not recognized.\n" "Probable cause: you are trying to use a variable name that starts with a capital."); } else if (command [0] != '\0' && command [wcslen (command) - 1] == ' ') { Melder_throw ("Command \"", command, "\" not available for current selection. " "It may be helpful to remove the trailing spaces."); } else { Melder_throw ("Command \"", command, "\" not available for current selection."); } } } } praat_updateSelection (); } } void praat_executeCommandFromStandardInput (const char *programName) { char command [1000]; // can be recursive for (;;) { char *newLine; printf ("%s > ", programName); if (! fgets (command, 999, stdin)) Melder_throw ("Cannot read input."); newLine = strchr (command, '\n'); if (newLine) *newLine = '\0'; autostring commandW = Melder_utf8ToWcs (command); try { praat_executeCommand (NULL, commandW.peek()); } catch (MelderError) { Melder_error_ (programName, ": command \"", command, "\" not executed."); Melder_flushError (NULL); } } } void praat_executeScriptFromFile (MelderFile file, const wchar *arguments) { try { autostring text = MelderFile_readText (file); autoMelderFileSetDefaultDir dir (file); // so that relative file names can be used inside the script Melder_includeIncludeFiles (& text); therror autoInterpreter interpreter = Interpreter_createFromEnvironment (praatP.editor); therror if (arguments) { Interpreter_readParameters (interpreter.peek(), text.peek()); therror Interpreter_getArgumentsFromString (interpreter.peek(), arguments); therror } Interpreter_run (interpreter.peek(), text.peek()); therror } catch (MelderError) { Melder_throw ("Script ", file, " not completed."); } } void praat_executeScriptFromFileNameWithArguments (const wchar *nameAndArguments) { wchar_t path [256]; const wchar_t *p, *arguments; structMelderFile file = { 0 }; /* * Split into file name and arguments. */ p = nameAndArguments; while (*p == ' ' || *p == '\t') p ++; if (*p == '\"') { wchar_t *q = path; p ++; // skip quote while (*p != '\"' && *p != '\0') * q ++ = * p ++; *q = '\0'; arguments = p; if (*arguments == '\"') arguments ++; if (*arguments == ' ') arguments ++; } else { wchar_t *q = path; while (*p != ' ' && *p != '\0') * q ++ = * p ++; *q = '\0'; arguments = p; if (*arguments == ' ') arguments ++; } Melder_relativePathToFile (path, & file); praat_executeScriptFromFile (& file, arguments); } void praat_executeScriptFromText (wchar *text) { try { autoInterpreter interpreter = Interpreter_create (NULL, NULL); Interpreter_run (interpreter.peek(), text); } catch (MelderError) { Melder_throw (L"Script not completed."); } } void praat_executeScriptFromDialog (Any dia) { wchar *path = UiForm_getString (dia, L"$file"); structMelderFile file = { 0 }; Melder_pathToFile (path, & file); autostring text = MelderFile_readText (& file); autoMelderFileSetDefaultDir dir (& file); Melder_includeIncludeFiles (& text); therror autoInterpreter interpreter = Interpreter_createFromEnvironment (praatP.editor); Interpreter_readParameters (interpreter.peek(), text.peek()); therror Interpreter_getArgumentsFromDialog (interpreter.peek(), dia); therror autoPraatBackground background; Interpreter_run (interpreter.peek(), text.peek()); } static void secondPassThroughScript (UiForm sendingForm, const wchar_t *sendingString_dummy, Interpreter interpreter_dummy, const wchar_t *invokingButtonTitle, bool modified, void *dummy) { (void) sendingString_dummy; (void) interpreter_dummy; (void) invokingButtonTitle; (void) modified; (void) dummy; praat_executeScriptFromDialog (sendingForm); therror } static void firstPassThroughScript (MelderFile file) { try { autostring text = MelderFile_readText (file); { // scope autoMelderFileSetDefaultDir dir (file); Melder_includeIncludeFiles (& text); therror } autoInterpreter interpreter = Interpreter_createFromEnvironment (praatP.editor); if (Interpreter_readParameters (interpreter.peek(), text.peek()) > 0) { Any form = Interpreter_createForm (interpreter.peek(), praatP.editor ? ((Editor) praatP.editor) -> d_windowForm : theCurrentPraatApplication -> topShell, Melder_fileToPath (file), secondPassThroughScript, NULL); UiForm_destroyWhenUnmanaged (form); UiForm_do (form, false); } else { autoPraatBackground background; praat_executeScriptFromFile (file, NULL); } } catch (MelderError) { Melder_throw ("Script ", file, " not completed."); } } static void fileSelectorOkCallback (UiForm dia, const wchar *sendingString_dummy, Interpreter interpreter_dummy, const wchar *invokingButtonTitle, bool modified, void *dummy) { (void) sendingString_dummy; (void) interpreter_dummy; (void) invokingButtonTitle; (void) modified; (void) dummy; firstPassThroughScript (UiFile_getFile (dia)); } /* * DO_praat_runScript () is the command callback for "Run script...", which is a bit obsolete command, * hidden in the Praat menu, and otherwise replaced by "execute". */ void DO_praat_runScript (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter_dummy, const wchar_t *invokingButtonTitle, bool modified, void *dummy) { (void) interpreter_dummy; (void) modified; (void) dummy; if (sendingForm == NULL && sendingString == NULL) { /* * User clicked the "Run script..." button in the Praat menu. */ static Any file_dialog; if (! file_dialog) file_dialog = UiInfile_create (theCurrentPraatApplication -> topShell, L"Praat: run script", fileSelectorOkCallback, NULL, invokingButtonTitle, NULL, false); UiInfile_do (file_dialog); } else { /* * A script called "Run script..." */ praat_executeScriptFromFileNameWithArguments (sendingString); therror } } void DO_RunTheScriptFromAnyAddedMenuCommand (UiForm sendingForm_dummy, const wchar *scriptPath, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *dummy) { structMelderFile file = { 0 }; (void) sendingForm_dummy; (void) interpreter; (void) invokingButtonTitle; (void) modified; (void) dummy; Melder_relativePathToFile ((wchar_t *) scriptPath, & file); firstPassThroughScript (& file); } void DO_RunTheScriptFromAnyAddedEditorCommand (Editor editor, const wchar *script) { praatP.editor = editor; DO_RunTheScriptFromAnyAddedMenuCommand (NULL, script, NULL, NULL, false, NULL); /*praatP.editor = NULL;*/ } /* End of file praat_script.cpp */ sources_5316/sys/Ui_decl.h0000644000176700017670000000153411621526310014256 0ustar paulpaul#ifndef _Ui_decl_h_ #define _Ui_decl_h_ /* Ui_decl.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ Thing_declare (UiForm); /* End of file Ui_decl.h */ #endif sources_5316/sys/GuiRowColumn.cpp0000644000176700017670000000551411753743571015661 0ustar paulpaul/* GuiRowColumn.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/30 * pb 2010/11/28 removed Motif * pb 2011/04/06 C++ */ #include "GuiP.h" #undef iam #define iam(x) x me = (x) void_me #if win || mac #define iam_rowcolumn \ GuiRowColumn me = (GuiRowColumn) widget -> userData #else #define iam_rowcolumn \ GuiRowColumn me = (GuiRowColumn) _GuiObject_getUserData (widget) #endif typedef struct structGuiRowColumn { GuiObject widget; } *GuiRowColumn; #if win || mac static void _GuiMotifRowColumn_destroyCallback (GuiObject widget, XtPointer void_me, XtPointer call) { (void) widget; (void) call; iam (GuiRowColumn); Melder_free (me); } #endif GuiObject GuiColumn_createShown (GuiObject parent, unsigned long flags) { GuiRowColumn me = Melder_calloc_f (struct structGuiRowColumn, 1); #if gtk #elif win my widget = XtVaCreateManagedWidget ("column1", xmRowColumnWidgetClass, parent, XmNorientation, XmVERTICAL, NULL); _GuiObject_setUserData (my widget, me); XtAddCallback (my widget, XmNdestroyCallback, _GuiMotifRowColumn_destroyCallback, me); #elif mac #if useCarbon my widget = XtVaCreateManagedWidget ("column1", xmRowColumnWidgetClass, parent, XmNorientation, XmVERTICAL, NULL); _GuiObject_setUserData (my widget, me); XtAddCallback (my widget, XmNdestroyCallback, _GuiMotifRowColumn_destroyCallback, me); #else #endif #endif return my widget; } GuiObject GuiRow_createShown (GuiObject parent, unsigned long flags) { GuiRowColumn me = Melder_calloc_f (struct structGuiRowColumn, 1); #if gtk #elif win my widget = XtVaCreateManagedWidget ("column1", xmRowColumnWidgetClass, parent, XmNorientation, XmHORIZONTAL, NULL); _GuiObject_setUserData (my widget, me); XtAddCallback (my widget, XmNdestroyCallback, _GuiMotifRowColumn_destroyCallback, me); #elif mac #if useCarbon my widget = XtVaCreateManagedWidget ("column1", xmRowColumnWidgetClass, parent, XmNorientation, XmHORIZONTAL, NULL); _GuiObject_setUserData (my widget, me); XtAddCallback (my widget, XmNdestroyCallback, _GuiMotifRowColumn_destroyCallback, me); #else #endif #endif return my widget; } /* End of file GuiRowColumn.cpp */ sources_5316/sys/Strings.h0000644000176700017670000000270411625721240014346 0ustar paulpaul#ifndef _Strings_h_ #define _Strings_h_ /* Strings.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" #include "Strings_def.h" oo_CLASS_CREATE (Strings, Data); Strings Strings_createAsFileList (const wchar *path); Strings Strings_createAsDirectoryList (const wchar *path); Strings Strings_readFromRawTextFile (MelderFile file); void Strings_writeToRawTextFile (Strings me, MelderFile file); void Strings_randomize (Strings me); void Strings_genericize (Strings me); void Strings_nativize (Strings me); void Strings_sort (Strings me); void Strings_remove (Strings me, long position); void Strings_replace (Strings me, long position, const wchar *text); void Strings_insert (Strings me, long position, const wchar *text); /* End of file Strings.h */ #endif sources_5316/sys/oo_READ_CACHE.h0000644000176700017670000001202511724670615015016 0ustar paulpaul/* oo_READ_CACHE.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) \ my x = cacget##storage (f); therror #define oo_ARRAY(type,storage,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (int i = 0; i < n; i ++) { \ my x [i] = cacget##storage (f); therror \ } #define oo_SET(type,storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) { \ my x [i] = cacget##storage (f); therror \ } #define oo_VECTOR(type,storage,x,min,max) \ if (max >= min) { \ my x = NUMvector_readCache_##storage (min, max, f); therror \ } #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) \ if (row2 >= row1 && col2 >= col1) { \ my x = NUMmatrix_readCache_##storage (row1, row2, col1, col2, f); therror \ } #define oo_ENUMx(type,storage,Type,x) \ my x = cacget##storage (f, & enum_##Type); therror #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (int i = 0; i < n; i ++) { \ my x [i] = cacget##storage (f, & enum_##Type); therror \ } #define oo_ENUMx_SET(type,storage,Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) { \ my x [i] = cacget##storage (f, & enum_##Type); therror \ } #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) \ if (max >= min) { \ my x = NUMvector (min, max); therror \ for (long i = min; i <= max; i ++) { \ my x [i] = cacget##storage (f, & enum_##Type); therror \ } \ } #define oo_STRINGx(storage,x) \ my x = cacget##storage (f); therror #define oo_STRINGx_ARRAY(storage,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (int i = 0; i < n; i ++) { \ my x [i] = cacget##storage (f); therror \ } #define oo_STRINGx_SET(storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) { \ my x [i] = cacget##storage (f); therror \ } #define oo_STRINGx_VECTOR(storage,x,min,max) \ if (max >= min) { \ my x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) { \ my x [i] = cacget##storage (f); therror \ } \ } #define oo_STRUCT(Type,x) \ Type##_readCache (& my x, f); therror #define oo_STRUCT_ARRAY(Type,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (int i = 0; i < n; i ++) { \ Type##_readCache (& my x [i], f); therror \ } #define oo_STRUCT_SET(Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) { \ Type##_readCache (& my x [i], f); therror \ } #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ if (max >= min) { \ my x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) { \ Type##_readCache (& my x [i], f); \ } \ } #define oo_OBJECT(Class,version,x) \ if (cacgetex (f)) { \ my x = Thing_new (Class); therror \ Data_readCache (my x, f); therror \ } #define oo_COLLECTION(Class,x,ItemClass,version) \ { \ long n = cacgeti4 (f); therror \ my x = Class##_create (); therror \ for (long i = 1; i <= n; i ++) { \ auto#ItemClass item = (ItemClass) Thing_new (ItemClass); \ ((Data_Table) item -> methods) -> readCache (item.peek(), f); therror \ Collection_addItem (my x, item.transfer()); \ } \ } #define oo_DEFINE_STRUCT(Type) \ static void Type##_readCache (Type me, CACHE *f) { \ int localVersion = Thing_version; #define oo_END_STRUCT(Type) \ } #define oo_DEFINE_CLASS(Class,Parent) \ static void class##Class##_readCache (I, CACHE *f) { \ iam (Class); \ int localVersion = Thing_version; (void) localVersion; \ inherited (Class) readCache (me, f); therror #define oo_END_CLASS(Class) \ } #define oo_IF(condition) \ if (condition) { #define oo_ENDIF \ } #define oo_FROM(from) \ if (localVersion >= from) { #define oo_ENDFROM \ } #define oo_VERSION(version) \ Thing_version = version; #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 0 #define oo_READING 1 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 1 #define oo_READING_LISP 0 #define oo_WRITING 0 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_READ_CACHE.h */ sources_5316/sys/StringsEditor.cpp0000644000176700017670000001207211724373643016061 0ustar paulpaul/* StringsEditor.cpp * * Copyright (C) 2007-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "StringsEditor.h" #include "EditorM.h" #include "machine.h" Thing_implement (StringsEditor, Editor, 0); void structStringsEditor :: v_destroy () { StringsEditor_Parent :: v_destroy (); } static void menu_cb_help (EDITOR_ARGS) { EDITOR_IAM (StringsEditor); (void) me; Melder_help (L"StringsEditor"); } void structStringsEditor :: v_createHelpMenuItems (EditorMenu menu) { StringsEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"StringsEditor help", '?', menu_cb_help); } static void updateList (StringsEditor me) { Strings strings = (Strings) my data; GuiList_deleteAllItems (my list); for (long i = 1; i <= strings -> numberOfStrings; i ++) GuiList_insertItem (my list, strings -> strings [i], 0); } static void gui_button_cb_insert (I, GuiButtonEvent event) { (void) event; iam (StringsEditor); Strings strings = (Strings) my data; /* * Find the first selected item. */ long numberOfSelected, *selected = GuiList_getSelectedPositions (my list, & numberOfSelected); long position = selected == NULL ? strings -> numberOfStrings + 1 : selected [1]; NUMvector_free (selected, 1); wchar_t *text = GuiText_getString (my text); /* * Change the data. */ Strings_insert (strings, position, text); /* * Change the list. */ GuiList_insertItem (my list, text, position); GuiList_deselectAllItems (my list); GuiList_selectItem (my list, position); /* * Clean up. */ Melder_free (text); my broadcastDataChanged (); } static void gui_button_cb_append (I, GuiButtonEvent event) { (void) event; iam (StringsEditor); Strings strings = (Strings) my data; wchar_t *text = GuiText_getString (my text); /* * Change the data. */ Strings_insert (strings, 0, text); /* * Change the list. */ GuiList_insertItem (my list, text, 0); GuiList_deselectAllItems (my list); GuiList_selectItem (my list, strings -> numberOfStrings); /* * Clean up. */ Melder_free (text); my broadcastDataChanged (); } static void gui_button_cb_remove (I, GuiButtonEvent event) { (void) event; iam (StringsEditor); long numberOfSelected, *selected = GuiList_getSelectedPositions (my list, & numberOfSelected); for (long iselected = numberOfSelected; iselected >= 1; iselected --) { Strings_remove ((Strings) my data, selected [iselected]); } NUMvector_free (selected, 1); updateList (me); my broadcastDataChanged (); } static void gui_button_cb_replace (I, GuiButtonEvent event) { (void) event; iam (StringsEditor); Strings strings = (Strings) my data; long numberOfSelected, *selected = GuiList_getSelectedPositions (my list, & numberOfSelected); wchar_t *text = GuiText_getString (my text); for (long iselected = 1; iselected <= numberOfSelected; iselected ++) { Strings_replace (strings, selected [iselected], text); GuiList_replaceItem (my list, text, selected [iselected]); } Melder_free (text); my broadcastDataChanged (); } static void gui_list_cb_doubleClick (GuiObject widget, void *void_me, long item) { (void) widget; iam (StringsEditor); Strings strings = (Strings) my data; if (item <= strings -> numberOfStrings) GuiText_setString (my text, strings -> strings [item]); } void structStringsEditor :: v_createChildren () { list = GuiList_create (d_windowForm, 1, 0, Machine_getMenuBarHeight (), -70, true, NULL); //GuiList_setDoubleClickCallback (list, gui_list_cb_doubleClick, this); GuiObject_show (list); text = GuiText_createShown (d_windowForm, 0, 0, Gui_AUTOMATIC, -40, 0); GuiButton_createShown (d_windowForm, 10, 100, Gui_AUTOMATIC, -10, L"Insert", gui_button_cb_insert, this, GuiButton_DEFAULT); GuiButton_createShown (d_windowForm, 110, 200, Gui_AUTOMATIC, -10, L"Append", gui_button_cb_append, this, 0); GuiButton_createShown (d_windowForm, 210, 300, Gui_AUTOMATIC, -10, L"Replace", gui_button_cb_replace, this, 0); GuiButton_createShown (d_windowForm, 310, 400, Gui_AUTOMATIC, -10, L"Remove", gui_button_cb_remove, this, 0); } void structStringsEditor :: v_dataChanged () { updateList (this); } StringsEditor StringsEditor_create (GuiObject parent, const wchar *title, Strings data) { try { autoStringsEditor me = Thing_new (StringsEditor); Editor_init (me.peek(), parent, 20, 40, 600, 600, title, data); updateList (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("Strings window not created."); } } /* End of file StringsEditor.cpp */ sources_5316/sys/Interpreter.cpp0000644000176700017670000017503211724502362015562 0ustar paulpaul/* Interpreter.cpp * * Copyright (C) 1993-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2002/03/25 option menus * pb 2002/06/04 include the script compiler * pb 2002/09/26 removed bug: crashed if a line in a form contained only the word "comment" * pb 2002/11/25 Melder_double * pb 2002/12/10 include files * pb 2002/12/14 more informative error messages * pb 2003/05/19 Melder_atof * pb 2003/07/15 assert * pb 2003/07/19 if undefined fails * pb 2004/10/16 C++ compatible structs * pb 2004/12/06 made Interpreter_getArgumentsFromDialog resistant to changes in the script while the dialog is up * pb 2005/01/01 there can be spaces before the "form" statement * pb 2005/11/26 allow mixing of "option" and "button", as in Ui.c * pb 2006/01/11 local variables * pb 2007/02/05 preferencesDirectory$, homeDirectory$, temporaryDirectory$ * pb 2007/04/02 allow comments (with '#' or ';' or empty lines) in forms * pb 2007/04/19 allow comments with '!' in forms * pb 2007/05/24 some wchar_t * pb 2007/06/09 wchar_t * pb 2007/08/12 more wchar_t * pb 2007/11/30 removed bug: allowed long arguments to the "call" statement (thanks to Ingmar Steiner) * pb 2007/12/10 predefined numeric variables macintosh/windows/unix * pb 2008/04/30 new Formula API * pb 2008/05/01 arrays * pb 2008/05/15 praatVersion, praatVersion$ * pb 2009/01/04 Interpreter_voidExpression * pb 2009/01/17 arguments to UiForm callbacks * pb 2009/01/20 pause forms * pb 2009/03/17 split up structPraat * pb 2009/12/22 invokingButtonTitle * pb 2010/04/30 guard against leading nonbreaking spaces * pb 2011/05/14 C++ */ #include #include "Interpreter.h" #include "praatP.h" extern structMelderDir praatDir; #include "praat_script.h" #include "Formula.h" #include "praat_version.h" #include "UnicodeData.h" #define Interpreter_WORD 1 #define Interpreter_REAL 2 #define Interpreter_POSITIVE 3 #define Interpreter_INTEGER 4 #define Interpreter_NATURAL 5 #define Interpreter_BOOLEAN 6 #define Interpreter_SENTENCE 7 #define Interpreter_TEXT 8 #define Interpreter_CHOICE 9 #define Interpreter_OPTIONMENU 10 #define Interpreter_BUTTON 11 #define Interpreter_OPTION 12 #define Interpreter_COMMENT 13 Thing_implement (InterpreterVariable, SimpleString, 0); void structInterpreterVariable :: v_destroy () { Melder_free (string); Melder_free (stringValue); NUMmatrix_free (numericArrayValue. data, 1, 1); InterpreterVariable_Parent :: v_destroy (); } static InterpreterVariable InterpreterVariable_create (const wchar *key) { try { if (key [0] == 'e' && key [1] == '\0') Melder_throw ("You cannot use 'e' as the name of a variable (e is the constant 2.71...)."); if (key [0] == 'p' && key [1] == 'i' && key [2] == '\0') Melder_throw ("You cannot use 'pi' as the name of a variable (pi is the constant 3.14...)."); if (key [0] == 'u' && key [1] == 'n' && key [2] == 'd' && key [3] == 'e' && key [4] == 'f' && key [5] == 'i' && key [6] == 'n' && key [7] == 'e' && key [8] == 'd' && key [9] == '\0') Melder_throw ("You cannot use 'undefined' as the name of a variable."); autoInterpreterVariable me = Thing_new (InterpreterVariable); my string = Melder_wcsdup (key); return me.transfer(); } catch (MelderError) { Melder_throw ("Interpreter variable not created."); } } Thing_implement (Interpreter, Thing, 0); void structInterpreter :: v_destroy () { Melder_free (environmentName); for (int ipar = 1; ipar <= Interpreter_MAXNUM_PARAMETERS; ipar ++) Melder_free (arguments [ipar]); forget (variables); Interpreter_Parent :: v_destroy (); } Interpreter Interpreter_create (wchar_t *environmentName, ClassInfo editorClass) { try { autoInterpreter me = Thing_new (Interpreter); my variables = SortedSetOfString_create (); my environmentName = Melder_wcsdup (environmentName); my editorClass = editorClass; return me.transfer(); } catch (MelderError) { Melder_throw ("Interpreter not created."); } } Interpreter Interpreter_createFromEnvironment (Editor editor) { if (editor == NULL) return Interpreter_create (NULL, NULL); return Interpreter_create (editor -> name, editor -> classInfo); } void Melder_includeIncludeFiles (wchar **text) { for (int depth = 0; ; depth ++) { wchar *head = *text; long numberOfIncludes = 0; if (depth > 10) Melder_throw ("Include files nested too deep. Probably cyclic."); for (;;) { wchar *includeLocation, *includeFileName, *tail, *newText; long headLength, includeTextLength, newLength; /* Look for an include statement. If not found, we have finished. */ includeLocation = wcsnequ (head, L"include ", 8) ? head : wcsstr (head, L"\ninclude "); if (includeLocation == NULL) break; if (includeLocation != head) includeLocation += 1; numberOfIncludes += 1; /* Separate out the head. */ *includeLocation = '\0'; /* Separate out the name of the include file. */ includeFileName = includeLocation + 8; while (*includeFileName == ' ' || *includeFileName == '\t') includeFileName ++; tail = includeFileName; while (*tail != '\n' && *tail != '\0') tail ++; if (*tail == '\n') { *tail = '\0'; tail += 1; } /* Get the contents of the include file. */ structMelderFile includeFile = { 0 }; Melder_relativePathToFile (includeFileName, & includeFile); autostring includeText; try { includeText.reset (MelderFile_readText (& includeFile)); } catch (MelderError) { Melder_throw ("Include file ", & includeFile, " not read."); } /* Construct the new text. */ headLength = (head - *text) + wcslen (head); includeTextLength = wcslen (includeText.peek()); newLength = headLength + includeTextLength + 1 + wcslen (tail); newText = Melder_malloc (wchar, newLength + 1); wcscpy (newText, *text); wcscpy (newText + headLength, includeText.peek()); wcscpy (newText + headLength + includeTextLength, L"\n"); wcscpy (newText + headLength + includeTextLength + 1, tail); /* Replace the old text with the new. */ Melder_free (*text); *text = newText; /* Cycle. */ head = *text + headLength + includeTextLength + 1; } if (numberOfIncludes == 0) break; } } long Interpreter_readParameters (Interpreter me, wchar *text) { wchar *formLocation = NULL; long npar = 0; my dialogTitle [0] = '\0'; /* * Look for a "form" line. */ {// scope wchar *p = text; for (;;) { while (*p == ' ' || *p == '\t') p ++; if (wcsnequ (p, L"form ", 5)) { formLocation = p; break; } while (*p != '\0' && *p != '\n') p ++; if (*p == '\0') break; p ++; /* Skip newline symbol. */ } } /* * If there is no "form" line, there are no parameters. */ if (formLocation) { wchar *dialogTitle = formLocation + 5, *newLine; while (*dialogTitle == ' ' || *dialogTitle == '\t') dialogTitle ++; newLine = wcschr (dialogTitle, '\n'); if (newLine) *newLine = '\0'; wcscpy (my dialogTitle, dialogTitle); if (newLine) *newLine = '\n'; my numberOfParameters = 0; while (newLine) { wchar_t *line = newLine + 1, *p; int type = 0; while (*line == ' ' || *line == '\t') line ++; while (*line == '#' || *line == ';' || *line == '!' || *line == '\n') { newLine = wcschr (line, '\n'); if (newLine == NULL) Melder_throw ("Unfinished form."); line = newLine + 1; while (*line == ' ' || *line == '\t') line ++; } if (wcsnequ (line, L"endform", 7)) break; if (wcsnequ (line, L"word ", 5)) { type = Interpreter_WORD; p = line + 5; } else if (wcsnequ (line, L"real ", 5)) { type = Interpreter_REAL; p = line + 5; } else if (wcsnequ (line, L"positive ", 9)) { type = Interpreter_POSITIVE; p = line + 9; } else if (wcsnequ (line, L"integer ", 8)) { type = Interpreter_INTEGER; p = line + 8; } else if (wcsnequ (line, L"natural ", 8)) { type = Interpreter_NATURAL; p = line + 8; } else if (wcsnequ (line, L"boolean ", 8)) { type = Interpreter_BOOLEAN; p = line + 8; } else if (wcsnequ (line, L"sentence ", 9)) { type = Interpreter_SENTENCE; p = line + 9; } else if (wcsnequ (line, L"text ", 5)) { type = Interpreter_TEXT; p = line + 5; } else if (wcsnequ (line, L"choice ", 7)) { type = Interpreter_CHOICE; p = line + 7; } else if (wcsnequ (line, L"optionmenu ", 11)) { type = Interpreter_OPTIONMENU; p = line + 11; } else if (wcsnequ (line, L"button ", 7)) { type = Interpreter_BUTTON; p = line + 7; } else if (wcsnequ (line, L"option ", 7)) { type = Interpreter_OPTION; p = line + 7; } else if (wcsnequ (line, L"comment ", 8)) { type = Interpreter_COMMENT; p = line + 8; } else { newLine = wcschr (line, '\n'); if (newLine) *newLine = '\0'; Melder_error_ ("Unknown parameter type:\n\"", line, "\"."); if (newLine) *newLine = '\n'; throw MelderError (); return 0; } /* Example: form Something real Time_(s) 3.14 (= pi) choice Colour 2 button Red button Green button Blue endform my parameters [1] := "Time_(s)" my parameters [2] := "Colour" my parameters [3] := "" my parameters [4] := "" my parameters [5] := "" my arguments [1] := "3.14 (= pi)" my arguments [2] := "2" my arguments [3] := "Red" (funny, but needed in Interpreter_getArgumentsFromString) my arguments [4] := "Green" my arguments [5] := "Blue" */ if (type <= Interpreter_OPTIONMENU) { while (*p == ' ' || *p == '\t') p ++; if (*p == '\n' || *p == '\0') Melder_throw ("Missing parameter:\n\"", line, "\"."); wchar_t *q = my parameters [++ my numberOfParameters]; while (*p != ' ' && *p != '\t' && *p != '\n' && *p != '\0') * (q ++) = * (p ++); *q = '\0'; npar ++; } else { my parameters [++ my numberOfParameters] [0] = '\0'; } while (*p == ' ' || *p == '\t') p ++; newLine = wcschr (p, '\n'); if (newLine) *newLine = '\0'; Melder_free (my arguments [my numberOfParameters]); my arguments [my numberOfParameters] = Melder_wcsdup_f (p); if (newLine) *newLine = '\n'; my types [my numberOfParameters] = type; } } else { npar = my numberOfParameters = 0; } return npar; } UiForm Interpreter_createForm (Interpreter me, GuiObject parent, const wchar *path, void (*okCallback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *), void *okClosure) { UiForm form = UiForm_create (parent, my dialogTitle [0] ? my dialogTitle : L"Script arguments", okCallback, okClosure, NULL, NULL); Any radio = NULL; if (path) UiForm_addText (form, L"$file", path); for (int ipar = 1; ipar <= my numberOfParameters; ipar ++) { /* * Convert underscores to spaces. */ wchar_t parameter [100], *p = & parameter [0]; wcscpy (parameter, my parameters [ipar]); while (*p) { if (*p == '_') *p = ' '; p ++; } switch (my types [ipar]) { case Interpreter_WORD: UiForm_addWord (form, parameter, my arguments [ipar]); break; case Interpreter_REAL: UiForm_addReal (form, parameter, my arguments [ipar]); break; case Interpreter_POSITIVE: UiForm_addPositive (form, parameter, my arguments [ipar]); break; case Interpreter_INTEGER: UiForm_addInteger (form, parameter, my arguments [ipar]); break; case Interpreter_NATURAL: UiForm_addNatural (form, parameter, my arguments [ipar]); break; case Interpreter_BOOLEAN: UiForm_addBoolean (form, parameter, my arguments [ipar] [0] == '1' || my arguments [ipar] [0] == 'y' || my arguments [ipar] [0] == 'Y' || (my arguments [ipar] [0] == 'o' && my arguments [ipar] [1] == 'n')); break; case Interpreter_SENTENCE: UiForm_addSentence (form, parameter, my arguments [ipar]); break; case Interpreter_TEXT: UiForm_addText (form, parameter, my arguments [ipar]); break; case Interpreter_CHOICE: radio = UiForm_addRadio (form, parameter, wcstol (my arguments [ipar], NULL, 10)); break; case Interpreter_OPTIONMENU: radio = UiForm_addOptionMenu (form, parameter, wcstol (my arguments [ipar], NULL, 10)); break; case Interpreter_BUTTON: if (radio) UiRadio_addButton (radio, my arguments [ipar]); break; case Interpreter_OPTION: if (radio) UiOptionMenu_addButton (radio, my arguments [ipar]); break; case Interpreter_COMMENT: UiForm_addLabel (form, parameter, my arguments [ipar]); break; default: UiForm_addWord (form, parameter, my arguments [ipar]); break; } /* * Strip parentheses and colon off parameter name. */ if ((p = wcschr (my parameters [ipar], '(')) != NULL) { *p = '\0'; if (p - my parameters [ipar] > 0 && p [-1] == '_') p [-1] = '\0'; } p = my parameters [ipar]; if (*p != '\0' && p [wcslen (p) - 1] == ':') p [wcslen (p) - 1] = '\0'; } UiForm_finish (form); return form; } void Interpreter_getArgumentsFromDialog (Interpreter me, Any dialog) { for (int ipar = 1; ipar <= my numberOfParameters; ipar ++) { wchar parameter [100], *p; /* * Strip parentheses and colon off parameter name. */ if ((p = wcschr (my parameters [ipar], '(')) != NULL) { *p = '\0'; if (p - my parameters [ipar] > 0 && p [-1] == '_') p [-1] = '\0'; } p = my parameters [ipar]; if (*p != '\0' && p [wcslen (p) - 1] == ':') p [wcslen (p) - 1] = '\0'; /* * Convert underscores to spaces. */ wcscpy (parameter, my parameters [ipar]); p = & parameter [0]; while (*p) { if (*p == '_') *p = ' '; p ++; } switch (my types [ipar]) { case Interpreter_REAL: case Interpreter_POSITIVE: { double value = UiForm_getReal_check (dialog, parameter); therror Melder_free (my arguments [ipar]); my arguments [ipar] = Melder_calloc_f (wchar_t, 40); wcscpy (my arguments [ipar], Melder_double (value)); break; } case Interpreter_INTEGER: case Interpreter_NATURAL: case Interpreter_BOOLEAN: { long value = UiForm_getInteger (dialog, parameter); therror Melder_free (my arguments [ipar]); my arguments [ipar] = Melder_calloc_f (wchar_t, 40); swprintf (my arguments [ipar], 40, L"%ld", value); break; } case Interpreter_CHOICE: case Interpreter_OPTIONMENU: { long integerValue = 0; wchar_t *stringValue = NULL; integerValue = UiForm_getInteger (dialog, parameter); therror stringValue = UiForm_getString (dialog, parameter); therror Melder_free (my arguments [ipar]); my arguments [ipar] = Melder_calloc_f (wchar, 40); swprintf (my arguments [ipar], 40, L"%ld", integerValue); wcscpy (my choiceArguments [ipar], stringValue); break; } case Interpreter_BUTTON: case Interpreter_OPTION: case Interpreter_COMMENT: break; default: { wchar *value = UiForm_getString (dialog, parameter); Melder_free (my arguments [ipar]); my arguments [ipar] = Melder_wcsdup_f (value); break; } } } } void Interpreter_getArgumentsFromString (Interpreter me, const wchar *arguments) { int size = my numberOfParameters; long length = wcslen (arguments); while (size >= 1 && my parameters [size] [0] == '\0') size --; /* Ignore fields without a variable name (button, comment). */ for (int ipar = 1; ipar <= size; ipar ++) { wchar *p = my parameters [ipar]; /* * Ignore buttons and comments again. */ if (! *p) continue; /* * Strip parentheses and colon off parameter name. */ if ((p = wcschr (p, '(')) != NULL) { *p = '\0'; if (p - my parameters [ipar] > 0 && p [-1] == '_') p [-1] = '\0'; } p = my parameters [ipar]; if (*p != '\0' && p [wcslen (p) - 1] == ':') p [wcslen (p) - 1] = '\0'; } for (int ipar = 1; ipar < size; ipar ++) { int ichar = 0; /* * Ignore buttons and comments again. The buttons will keep their labels as "arguments". */ if (my parameters [ipar] [0] == '\0') continue; Melder_free (my arguments [ipar]); // erase the current values, probably the default values my arguments [ipar] = Melder_calloc_f (wchar_t, length + 1); // replace with the actual arguments /* * Skip spaces until next argument. */ while (*arguments == ' ' || *arguments == '\t') arguments ++; /* * The argument is everything up to the next space, or, if that starts with a double quote, * everything between this quote and the matching double quote; * in this case, the argument can represent a double quote by a sequence of two double quotes. * Example: the string * "I said ""hello""" * will be passed to the dialog as a single argument containing the text * I said "hello" */ if (*arguments == '\"') { arguments ++; // do not include leading double quote for (;;) { if (*arguments == '\0') Melder_throw ("Missing matching quote."); if (*arguments == '\"' && * ++ arguments != '\"') break; // remember second quote my arguments [ipar] [ichar ++] = *arguments ++; } } else { while (*arguments != ' ' && *arguments != '\t' && *arguments != '\0') my arguments [ipar] [ichar ++] = *arguments ++; } my arguments [ipar] [ichar] = '\0'; // trailing null byte } /* The last item is handled separately, because it consists of the rest of the line. * Leading spaces are skipped, but trailing spaces are included. */ if (size > 0) { while (*arguments == ' ' || *arguments == '\t') arguments ++; Melder_free (my arguments [size]); my arguments [size] = Melder_wcsdup_f (arguments); } /* * Convert booleans and choices to numbers. */ for (int ipar = 1; ipar <= size; ipar ++) { if (my types [ipar] == Interpreter_BOOLEAN) { wchar_t *arg = & my arguments [ipar] [0]; if (wcsequ (arg, L"1") || wcsequ (arg, L"yes") || wcsequ (arg, L"on") || wcsequ (arg, L"Yes") || wcsequ (arg, L"On") || wcsequ (arg, L"YES") || wcsequ (arg, L"ON")) { wcscpy (arg, L"1"); } else if (wcsequ (arg, L"0") || wcsequ (arg, L"no") || wcsequ (arg, L"off") || wcsequ (arg, L"No") || wcsequ (arg, L"Off") || wcsequ (arg, L"NO") || wcsequ (arg, L"OFF")) { wcscpy (arg, L"0"); } else { Melder_throw ("Unknown value \"", arg, "\" for boolean \"", my parameters [ipar], "\"."); } } else if (my types [ipar] == Interpreter_CHOICE) { int jpar; wchar_t *arg = & my arguments [ipar] [0]; for (jpar = ipar + 1; jpar <= my numberOfParameters; jpar ++) { if (my types [jpar] != Interpreter_BUTTON && my types [jpar] != Interpreter_OPTION) Melder_throw ("Unknown value \"", arg, "\" for choice \"", my parameters [ipar], "\"."); if (wcsequ (my arguments [jpar], arg)) { // the button labels are in the arguments; see Interpreter_readParameters swprintf (arg, 40, L"%d", jpar - ipar); wcscpy (my choiceArguments [ipar], my arguments [jpar]); break; } } if (jpar > my numberOfParameters) Melder_throw ("Unknown value \"", arg, "\" for choice \"", my parameters [ipar], "\"."); } else if (my types [ipar] == Interpreter_OPTIONMENU) { int jpar; wchar_t *arg = & my arguments [ipar] [0]; for (jpar = ipar + 1; jpar <= my numberOfParameters; jpar ++) { if (my types [jpar] != Interpreter_OPTION && my types [jpar] != Interpreter_BUTTON) Melder_throw ("Unknown value \"", arg, "\" for option menu \"", my parameters [ipar], "\"."); if (wcsequ (my arguments [jpar], arg)) { swprintf (arg, 40, L"%d", jpar - ipar); wcscpy (my choiceArguments [ipar], my arguments [jpar]); break; } } if (jpar > my numberOfParameters) Melder_throw ("Unknown value \"", arg, "\" for option menu \"", my parameters [ipar], "\"."); } } } static int Interpreter_addNumericVariable (Interpreter me, const wchar *key, double value) { InterpreterVariable variable = InterpreterVariable_create (key); variable -> numericValue = value; Collection_addItem (my variables, variable); return 1; } static InterpreterVariable Interpreter_addStringVariable (Interpreter me, const wchar *key, const wchar *value) { InterpreterVariable variable = InterpreterVariable_create (key); variable -> stringValue = Melder_wcsdup (value); Collection_addItem (my variables, variable); return variable; } InterpreterVariable Interpreter_hasVariable (Interpreter me, const wchar *key) { long ivar = 0; wchar_t variableNameIncludingProcedureName [1+200]; Melder_assert (key != NULL); if (key [0] == '.') { wcscpy (variableNameIncludingProcedureName, my procedureNames [my callDepth]); wcscat (variableNameIncludingProcedureName, key); } else { wcscpy (variableNameIncludingProcedureName, key); } ivar = SortedSetOfString_lookUp (my variables, variableNameIncludingProcedureName); return ivar ? (InterpreterVariable) my variables -> item [ivar] : NULL; } InterpreterVariable Interpreter_lookUpVariable (Interpreter me, const wchar *key) { InterpreterVariable var = NULL; wchar variableNameIncludingProcedureName [1+200]; Melder_assert (key != NULL); if (key [0] == '.') { wcscpy (variableNameIncludingProcedureName, my procedureNames [my callDepth]); wcscat (variableNameIncludingProcedureName, key); } else { wcscpy (variableNameIncludingProcedureName, key); } var = Interpreter_hasVariable (me, variableNameIncludingProcedureName); if (var) return var; var = InterpreterVariable_create (variableNameIncludingProcedureName); Collection_addItem (my variables, var); return Interpreter_hasVariable (me, variableNameIncludingProcedureName); } static long lookupLabel (Interpreter me, const wchar *labelName) { for (long ilabel = 1; ilabel <= my numberOfLabels; ilabel ++) if (wcsequ (labelName, my labelNames [ilabel])) return ilabel; Melder_throw ("Unknown label \"", labelName, "\"."); } static bool isCommand (const wchar *p) { /* * Things that start with "nowarn", "noprogress", or "nocheck" are commands. */ if (p [0] == 'n' && p [1] == 'o' && (wcsnequ (p + 2, L"warn ", 5) || wcsnequ (p + 2, L"progress ", 9) || wcsnequ (p + 2, L"check ", 6))) return true; if (wcsnequ (p, L"demo ", 5)) return true; /* * Otherwise, things that start with lower case are formulas. */ if (! isupper (*p)) return false; /* * The remaining possibility is things that start with upper case. * If they contain an underscore, they are object names, hence we must have a formula. * Otherwise, we have a command. */ while (isalnum (*p)) p ++; return *p != '_'; } static void parameterToVariable (Interpreter me, int type, const wchar_t *in_parameter, int ipar) { wchar_t parameter [200]; Melder_assert (type != 0); wcscpy (parameter, in_parameter); if (type >= Interpreter_REAL && type <= Interpreter_BOOLEAN) { Interpreter_addNumericVariable (me, parameter, Melder_atof (my arguments [ipar])); } else if (type == Interpreter_CHOICE || type == Interpreter_OPTIONMENU) { Interpreter_addNumericVariable (me, parameter, Melder_atof (my arguments [ipar])); wcscat (parameter, L"$"); Interpreter_addStringVariable (me, parameter, my choiceArguments [ipar]); } else if (type == Interpreter_BUTTON || type == Interpreter_OPTION || type == Interpreter_COMMENT) { /* Do not add a variable. */ } else { wcscat (parameter, L"$"); Interpreter_addStringVariable (me, parameter, my arguments [ipar]); } } void Interpreter_run (Interpreter me, wchar *text) { autoNUMvector lines; // not autostringvector, because the elements are reference copies long lineNumber = 0; bool assertionFailed = false; try { static MelderString valueString = { 0 }; // to divert the info static MelderString assertErrorString = { 0 }; wchar_t *command = text; autoMelderString command2; autoMelderString buffer; long numberOfLines = 0, assertErrorLineNumber = 0, callStack [1 + Interpreter_MAX_CALL_DEPTH]; int atLastLine = FALSE, fromif = FALSE, fromendfor = FALSE, callDepth = 0, chopped = 0, ipar; my callDepth = 0; /* * The "environment" is NULL if we are in the Praat shell, or an editor otherwise. */ if (my editorClass) { praatP. editor = praat_findEditorFromString (my environmentName); } else { praatP. editor = NULL; } /* * Start. */ my running = true; /* * Count lines and set the newlines to zero. */ while (! atLastLine) { wchar_t *endOfLine = command; while (*endOfLine != '\n' && *endOfLine != '\0') endOfLine ++; if (*endOfLine == '\0') atLastLine = TRUE; *endOfLine = '\0'; numberOfLines ++; command = endOfLine + 1; } /* * Remember line starts and labels. */ lines.reset (1, numberOfLines); for (lineNumber = 1, command = text; lineNumber <= numberOfLines; lineNumber ++, command += wcslen (command) + 1 + chopped) { int length; while (*command == ' ' || *command == '\t' || *command == UNICODE_NO_BREAK_SPACE) command ++; // nbsp can occur for scripts copied from the manual length = wcslen (command); /* * Chop trailing spaces? */ /*chopped = 0; while (length > 0) { char kar = command [-- length]; if (kar != ' ' && kar != '\t') break; command [length] = '\0'; chopped ++; }*/ lines [lineNumber] = command; if (wcsnequ (command, L"label ", 6)) { int ilabel; for (ilabel = 1; ilabel <= my numberOfLabels; ilabel ++) if (wcsequ (command + 6, my labelNames [ilabel])) Melder_throw ("Duplicate label \"", command + 6, "\"."); if (my numberOfLabels >= Interpreter_MAXNUM_LABELS) Melder_throw ("Too many labels."); swprintf (my labelNames [++ my numberOfLabels], 50, L"%.47ls", command + 6); my labelLines [my numberOfLabels] = lineNumber; } } /* * Connect continuation lines. */ for (lineNumber = numberOfLines; lineNumber >= 2; lineNumber --) { wchar_t *line = lines [lineNumber]; if (line [0] == '.' && line [1] == '.' && line [2] == '.') { wchar_t *previous = lines [lineNumber - 1]; MelderString_copy (& command2, line + 3); MelderString_get (& command2, previous + wcslen (previous)); static wchar emptyLine [] = { '\0' }; lines [lineNumber] = emptyLine; } } /* * Copy the parameter names and argument values into the array of variables. */ forget (my variables); my variables = SortedSetOfString_create (); for (ipar = 1; ipar <= my numberOfParameters; ipar ++) { wchar_t parameter [200]; /* * Create variable names as-are and variable names without capitals. */ wcscpy (parameter, my parameters [ipar]); parameterToVariable (me, my types [ipar], parameter, ipar); therror if (parameter [0] >= 'A' && parameter [0] <= 'Z') { parameter [0] = tolower (parameter [0]); parameterToVariable (me, my types [ipar], parameter, ipar); therror } } /* * Initialize some variables. */ Interpreter_addStringVariable (me, L"newline$", L"\n"); Interpreter_addStringVariable (me, L"tab$", L"\t"); Interpreter_addStringVariable (me, L"shellDirectory$", Melder_getShellDirectory ()); structMelderDir dir = { { 0 } }; Melder_getDefaultDir (& dir); Interpreter_addStringVariable (me, L"defaultDirectory$", Melder_dirToPath (& dir)); Interpreter_addStringVariable (me, L"preferencesDirectory$", Melder_dirToPath (& praatDir)); Melder_getHomeDir (& dir); Interpreter_addStringVariable (me, L"homeDirectory$", Melder_dirToPath (& dir)); Melder_getTempDir (& dir); Interpreter_addStringVariable (me, L"temporaryDirectory$", Melder_dirToPath (& dir)); #if defined (macintosh) Interpreter_addNumericVariable (me, L"macintosh", 1); Interpreter_addNumericVariable (me, L"windows", 0); Interpreter_addNumericVariable (me, L"unix", 0); #elif defined (_WIN32) Interpreter_addNumericVariable (me, L"macintosh", 0); Interpreter_addNumericVariable (me, L"windows", 1); Interpreter_addNumericVariable (me, L"unix", 0); #elif defined (UNIX) Interpreter_addNumericVariable (me, L"macintosh", 0); Interpreter_addNumericVariable (me, L"windows", 0); Interpreter_addNumericVariable (me, L"unix", 1); #else Interpreter_addNumericVariable (me, L"macintosh", 0); Interpreter_addNumericVariable (me, L"windows", 0); Interpreter_addNumericVariable (me, L"unix", 0); #endif Interpreter_addNumericVariable (me, L"left", 1); // to accommodate scripts from before Praat 5.2.06 Interpreter_addNumericVariable (me, L"right", 2); // to accommodate scripts from before Praat 5.2.06 Interpreter_addNumericVariable (me, L"mono", 1); // to accommodate scripts from before Praat 5.2.06 Interpreter_addNumericVariable (me, L"stereo", 2); // to accommodate scripts from before Praat 5.2.06 Interpreter_addNumericVariable (me, L"all", 0); // to accommodate scripts from before Praat 5.2.06 Interpreter_addNumericVariable (me, L"average", 0); // to accommodate scripts from before Praat 5.2.06 #define xstr(s) str(s) #define str(s) #s Interpreter_addStringVariable (me, L"praatVersion$", L"" xstr(PRAAT_VERSION_STR)); Interpreter_addNumericVariable (me, L"praatVersion", PRAAT_VERSION_NUM); /* * Execute commands. */ #define wordEnd(c) (c == '\0' || c == ' ' || c == '\t') for (lineNumber = 1; lineNumber <= numberOfLines; lineNumber ++) { if (my stopped) break; try { int c0, fail = FALSE; wchar_t *p; MelderString_copy (& command2, lines [lineNumber]); c0 = command2. string [0]; if (c0 == '\0') continue; /* * Substitute variables. */ for (p = & command2. string [0]; *p !='\0'; p ++) if (*p == '\'') { /* * Found a left quote. Search for a matching right quote. */ wchar_t *q = p + 1, varName [300], *r, *s, *colon; int precision = -1, percent = FALSE; while (*q != '\0' && *q != '\'' && q - p < 299) q ++; if (*q == '\0') break; /* No matching right quote: done with this line. */ if (q - p == 1 || q - p >= 299) continue; /* Ignore empty variable names. */ /* * Found a right quote. Get potential variable name. */ for (r = p + 1, s = varName; q - r > 0; r ++, s ++) *s = *r; *s = '\0'; /* Trailing null byte. */ colon = wcschr (varName, ':'); if (colon) { precision = wcstol (colon + 1, NULL, 10); if (wcschr (colon + 1, '%')) percent = TRUE; *colon = '\0'; } InterpreterVariable var = Interpreter_hasVariable (me, varName); if (var) { /* * Found a variable (p points to the left quote, q to the right quote). Substitute. */ int headlen = p - command2.string; const wchar_t *string = var -> stringValue ? var -> stringValue : percent ? Melder_percent (var -> numericValue, precision) : precision >= 0 ? Melder_fixed (var -> numericValue, precision) : Melder_double (var -> numericValue); int arglen = wcslen (string); MelderString_ncopy (& buffer, command2.string, headlen); MelderString_append (& buffer, string, q + 1); MelderString_copy (& command2, buffer.string); // This invalidates p!! (really bad bug 20070203) p = command2.string + headlen + arglen - 1; } else { p = q - 1; /* Go to before next quote. */ } } c0 = command2.string [0]; /* Resume in order to allow things like 'c$' = 5 */ if ((c0 < 'a' || c0 > 'z') && ! (c0 == '.' && command2.string [1] >= 'a' && command2.string [1] <= 'z')) { praat_executeCommand (me, command2.string); therror /* * Interpret control flow and variables. */ } else switch (c0) { case '.': fail = TRUE; break; case 'a': if (wcsnequ (command2.string, L"assert ", 7)) { double value; Interpreter_numericExpression (me, command2.string + 7, & value); therror if (value == 0.0 || value == NUMundefined) { assertionFailed = TRUE; Melder_throw ("Script assertion fails in line ", lineNumber, " (", value ? "undefined" : "false", "):\n ", command2.string + 7); } } else if (wcsnequ (command2.string, L"asserterror ", 12)) { MelderString_copy (& assertErrorString, command2.string + 12); assertErrorLineNumber = lineNumber; } else fail = TRUE; break; case 'b': fail = TRUE; break; case 'c': if (wcsnequ (command2.string, L"call ", 5)) { wchar_t *p = command2.string + 5, *callName, *procName; long iline; int hasArguments, callLength; while (*p == ' ' || *p == '\t') p ++; callName = p; while (*p != '\0' && *p != ' ' && *p != '\t') p ++; if (p == callName) Melder_throw ("Missing procedure name after 'call'."); hasArguments = *p != '\0'; *p = '\0'; /* Close procedure name. */ callLength = wcslen (callName); for (iline = 1; iline <= numberOfLines; iline ++) { wchar_t *linei = lines [iline], *q; int hasParameters; if (linei [0] != 'p' || linei [1] != 'r' || linei [2] != 'o' || linei [3] != 'c' || linei [4] != 'e' || linei [5] != 'd' || linei [6] != 'u' || linei [7] != 'r' || linei [8] != 'e' || linei [9] != ' ') continue; q = lines [iline] + 10; while (*q == ' ' || *q == '\t') q ++; procName = q; while (*q != '\0' && *q != ' ' && *q != '\t') q ++; if (q == procName) Melder_throw ("Missing procedure name after 'procedure'."); hasParameters = *q != '\0'; if (q - procName == callLength && wcsnequ (procName, callName, callLength)) { if (hasArguments && ! hasParameters) Melder_throw ("Call to procedure \"", callName, "\" has too many arguments."); if (hasParameters && ! hasArguments) Melder_throw ("Call to procedure \"", callName, "\" has too few arguments."); if (++ my callDepth > Interpreter_MAX_CALL_DEPTH) Melder_throw ("Call depth greater than ", Interpreter_MAX_CALL_DEPTH, "."); wcscpy (my procedureNames [my callDepth], callName); if (hasParameters) { ++ p; /* First argument. */ ++ q; /* First parameter. */ while (*q) { wchar_t *par, save; static MelderString arg = { 0 }; MelderString_empty (& arg); while (*p == ' ' || *p == '\t') p ++; while (*q == ' ' || *q == '\t') q ++; par = q; while (*q != '\0' && *q != ' ' && *q != '\t') q ++; /* Collect parameter name. */ if (*q) { /* Does anything follow the parameter name? */ if (*p == '\"') { p ++; /* Skip initial quote. */ while (*p != '\0') { if (*p == '\"') { /* Quote signals end-of-string or string-internal quote. */ if (p [1] == '\"') { /* Double quote signals string-internal quote. */ MelderString_appendCharacter (& arg, '\"'); p += 2; /* Skip second quote. */ } else { /* Single quote signals end-of-string. */ break; } } else { MelderString_appendCharacter (& arg, *p ++); } } } else { while (*p != '\0' && *p != ' ' && *p != '\t') MelderString_appendCharacter (& arg, *p ++); /* White space separates. */ } if (*p) { *p = '\0'; p ++; } } else { /* Else rest of line. */ while (*p != '\0') MelderString_appendCharacter (& arg, *p ++); } if (q [-1] == '$') { save = *q; *q = '\0'; InterpreterVariable var = Interpreter_lookUpVariable (me, par); *q = save; therror Melder_free (var -> stringValue); var -> stringValue = Melder_wcsdup_f (arg.string); } else { double value; my callDepth --; Interpreter_numericExpression (me, arg.string, & value); my callDepth ++; save = *q; *q = '\0'; InterpreterVariable var = Interpreter_lookUpVariable (me, par); *q = save; therror var -> numericValue = value; } } } if (callDepth == Interpreter_MAX_CALL_DEPTH) Melder_throw ("Call depth greater than ", Interpreter_MAX_CALL_DEPTH, "."); callStack [++ callDepth] = lineNumber; lineNumber = iline; break; } } if (iline > numberOfLines) Melder_throw ("Procedure \"", callName, "\" not found."); } else fail = TRUE; break; case 'd': if (wcsnequ (command2.string, L"dec ", 4)) { InterpreterVariable var = Interpreter_lookUpVariable (me, command2.string + 4); therror var -> numericValue -= 1.0; } else fail = TRUE; break; case 'e': if (command2.string [1] == 'n' && command2.string [2] == 'd') { if (wcsnequ (command2.string, L"endif", 5) && wordEnd (command2.string [5])) { /* Ignore. */ } else if (wcsnequ (command2.string, L"endfor", 6) && wordEnd (command2.string [6])) { int depth = 0; long iline; for (iline = lineNumber - 1; iline > 0; iline --) { wchar_t *line = lines [iline]; if (line [0] == 'f' && line [1] == 'o' && line [2] == 'r' && line [3] == ' ') { if (depth == 0) { lineNumber = iline - 1; fromendfor = TRUE; break; } /* Go before 'for'. */ else depth --; } else if (wcsnequ (lines [iline], L"endfor", 6) && wordEnd (lines [iline] [6])) { depth ++; } } if (iline <= 0) Melder_throw ("Unmatched 'endfor'."); } else if (wcsnequ (command2.string, L"endwhile", 8) && wordEnd (command2.string [8])) { int depth = 0; long iline; for (iline = lineNumber - 1; iline > 0; iline --) { if (wcsnequ (lines [iline], L"while ", 6)) { if (depth == 0) { lineNumber = iline - 1; break; } /* Go before 'while'. */ else depth --; } else if (wcsnequ (lines [iline], L"endwhile", 8) && wordEnd (lines [iline] [8])) { depth ++; } } if (iline <= 0) Melder_throw ("Unmatched 'endwhile'."); } else if (wcsnequ (command2.string, L"endproc", 7) && wordEnd (command2.string [7])) { if (callDepth == 0) Melder_throw ("Unmatched 'endproc'."); lineNumber = callStack [callDepth --]; -- my callDepth; } else fail = TRUE; } else if (wcsnequ (command2.string, L"else", 4) && wordEnd (command2.string [4])) { int depth = 0; long iline; for (iline = lineNumber + 1; iline <= numberOfLines; iline ++) { if (wcsnequ (lines [iline], L"endif", 5) && wordEnd (lines [iline] [5])) { if (depth == 0) { lineNumber = iline; break; } /* Go after 'endif'. */ else depth --; } else if (wcsnequ (lines [iline], L"if ", 3)) { depth ++; } } if (iline > numberOfLines) Melder_throw ("Unmatched 'else'."); } else if (wcsnequ (command2.string, L"elsif ", 6) || wcsnequ (command2.string, L"elif ", 5)) { if (fromif) { double value; fromif = FALSE; Interpreter_numericExpression (me, command2.string + 5, & value); therror if (value == 0.0) { int depth = 0; long iline; for (iline = lineNumber + 1; iline <= numberOfLines; iline ++) { if (wcsnequ (lines [iline], L"endif", 5) && wordEnd (lines [iline] [5])) { if (depth == 0) { lineNumber = iline; break; } /* Go after 'endif'. */ else depth --; } else if (wcsnequ (lines [iline], L"else", 4) && wordEnd (lines [iline] [4])) { if (depth == 0) { lineNumber = iline; break; } /* Go after 'else'. */ } else if ((wcsnequ (lines [iline], L"elsif", 5) && wordEnd (lines [iline] [5])) || (wcsnequ (lines [iline], L"elif", 4) && wordEnd (lines [iline] [4]))) { if (depth == 0) { lineNumber = iline - 1; fromif = TRUE; break; } /* Go at next 'elsif' or 'elif'. */ } else if (wcsnequ (lines [iline], L"if ", 3)) { depth ++; } } if (iline > numberOfLines) Melder_throw ("Unmatched 'elsif'."); } } else { int depth = 0; long iline; for (iline = lineNumber + 1; iline <= numberOfLines; iline ++) { if (wcsnequ (lines [iline], L"endif", 5) && wordEnd (lines [iline] [5])) { if (depth == 0) { lineNumber = iline; break; } /* Go after 'endif'. */ else depth --; } else if (wcsnequ (lines [iline], L"if ", 3)) { depth ++; } } if (iline > numberOfLines) Melder_throw ("'elsif' not matched with 'endif'."); } } else if (wcsnequ (command2.string, L"exit", 4)) { if (command2.string [4] == '\0') { lineNumber = numberOfLines; /* Go after end. */ } else { Melder_throw (command2.string + 5); } } else if (wcsnequ (command2.string, L"echo ", 5)) { /* * Make sure that lines like "echo = 3" will not be regarded as assignments. */ praat_executeCommand (me, command2.string); therror } else fail = TRUE; break; case 'f': if (command2.string [1] == 'o' && command2.string [2] == 'r' && command2.string [3] == ' ') { /* for_ */ double toValue, loopVariable; wchar_t *frompos = wcsstr (command2.string, L" from "), *topos = wcsstr (command2.string, L" to "); wchar_t *varpos = command2.string + 4, *endvar = frompos; if (! topos) Melder_throw ("Missing \'to\' in \'for\' loop."); if (! endvar) endvar = topos; while (*endvar == ' ') { *endvar = '\0'; endvar --; } while (*varpos == ' ') varpos ++; if (endvar - varpos < 0) Melder_throw ("Missing loop variable after \'for\'."); InterpreterVariable var = Interpreter_lookUpVariable (me, varpos); Interpreter_numericExpression (me, topos + 4, & toValue); therror if (fromendfor) { fromendfor = FALSE; loopVariable = var -> numericValue + 1.0; } else if (frompos) { *topos = '\0'; Interpreter_numericExpression (me, frompos + 6, & loopVariable); therror } else { loopVariable = 1.0; } var -> numericValue = loopVariable; if (loopVariable > toValue) { int depth = 0; long iline; for (iline = lineNumber + 1; iline <= numberOfLines; iline ++) { if (wcsnequ (lines [iline], L"endfor", 6)) { if (depth == 0) { lineNumber = iline; break; } /* Go after 'endfor'. */ else depth --; } else if (wcsnequ (lines [iline], L"for ", 4)) { depth ++; } } if (iline > numberOfLines) Melder_throw ("Unmatched 'for'."); } } else if (wcsnequ (command2.string, L"form ", 5)) { long iline; for (iline = lineNumber + 1; iline <= numberOfLines; iline ++) if (wcsnequ (lines [iline], L"endform", 7)) { lineNumber = iline; break; } /* Go after 'endform'. */ if (iline > numberOfLines) Melder_throw ("Unmatched 'form'."); } else fail = TRUE; break; case 'g': if (wcsnequ (command2.string, L"goto ", 5)) { wchar_t labelName [50], *space; int dojump = TRUE, ilabel; swprintf (labelName, 50, L"%.47ls", command2.string + 5); space = wcschr (labelName, ' '); if (space == labelName) Melder_throw ("Missing label name after 'goto'."); if (space) { double value; *space = '\0'; Interpreter_numericExpression (me, command2.string + 6 + wcslen (labelName), & value); therror if (value == 0.0) dojump = FALSE; } if (dojump) { ilabel = lookupLabel (me, labelName); lineNumber = my labelLines [ilabel]; // loop will add 1 } } else fail = TRUE; break; case 'h': fail = TRUE; break; case 'i': if (command2.string [1] == 'f' && command2.string [2] == ' ') { /* if_ */ double value; Interpreter_numericExpression (me, command2.string + 3, & value); therror if (value == 0.0) { int depth = 0; long iline; for (iline = lineNumber + 1; iline <= numberOfLines; iline ++) { if (wcsnequ (lines [iline], L"endif", 5)) { if (depth == 0) { lineNumber = iline; break; } /* Go after 'endif'. */ else depth --; } else if (wcsnequ (lines [iline], L"else", 4)) { if (depth == 0) { lineNumber = iline; break; } /* Go after 'else'. */ } else if (wcsnequ (lines [iline], L"elsif ", 6) || wcsnequ (lines [iline], L"elif ", 5)) { if (depth == 0) { lineNumber = iline - 1; fromif = TRUE; break; } /* Go at 'elsif'. */ } else if (wcsnequ (lines [iline], L"if ", 3)) { depth ++; } } if (iline > numberOfLines) Melder_throw ("Unmatched 'if'."); } else if (value == NUMundefined) { Melder_throw ("The value of the 'if' condition is undefined."); } } else if (wcsnequ (command2.string, L"inc ", 4)) { InterpreterVariable var = Interpreter_lookUpVariable (me, command2.string + 4); therror var -> numericValue += 1.0; } else fail = TRUE; break; case 'j': fail = TRUE; break; case 'k': fail = TRUE; break; case 'l': if (wcsnequ (command2.string, L"label ", 6)) { ; /* Ignore labels. */ } else fail = TRUE; break; case 'm': fail = TRUE; break; case 'n': fail = TRUE; break; case 'o': fail = TRUE; break; case 'p': if (wcsnequ (command2.string, L"procedure ", 10)) { long iline = lineNumber + 1; for (; iline <= numberOfLines; iline ++) { if (wcsnequ (lines [iline], L"endproc", 7) && wordEnd (lines [iline] [7])) { lineNumber = iline; break; } /* Go after 'endproc'. */ } if (iline > numberOfLines) Melder_throw ("Unmatched 'proc'."); } else if (wcsnequ (command2.string, L"print", 5)) { /* * Make sure that lines like "print = 3" will not be regarded as assingments. */ if (command2.string [5] == ' ' || (wcsnequ (command2.string + 5, L"line", 4) && (command2.string [9] == ' ' || command2.string [9] == '\0'))) { praat_executeCommand (me, command2.string); therror } else fail = TRUE; } else fail = TRUE; break; case 'q': fail = TRUE; break; case 'r': if (wcsnequ (command2.string, L"repeat", 6) && wordEnd (command2.string [6])) { /* Ignore. */ } else fail = TRUE; break; case 's': if (wcsnequ (command2.string, L"stopwatch", 9) && wordEnd (command2.string [9])) { (void) Melder_stopwatch (); /* Reset stopwatch. */ } else fail = TRUE; break; case 't': fail = TRUE; break; case 'u': if (wcsnequ (command2.string, L"until ", 6)) { double value; Interpreter_numericExpression (me, command2.string + 6, & value); therror if (value == 0.0) { int depth = 0; long iline; for (iline = lineNumber - 1; iline > 0; iline --) { if (wcsnequ (lines [iline], L"repeat", 6) && wordEnd (lines [iline] [6])) { if (depth == 0) { lineNumber = iline; break; } /* Go after 'repeat'. */ else depth --; } else if (wcsnequ (lines [iline], L"until ", 6)) { depth ++; } } if (iline <= 0) Melder_throw ("Unmatched 'until'."); } } else fail = TRUE; break; case 'v': fail = TRUE; break; case 'w': if (wcsnequ (command2.string, L"while ", 6)) { double value; Interpreter_numericExpression (me, command2.string + 6, & value); therror if (value == 0.0) { int depth = 0; long iline; for (iline = lineNumber + 1; iline <= numberOfLines; iline ++) { if (wcsnequ (lines [iline], L"endwhile", 8) && wordEnd (lines [iline] [8])) { if (depth == 0) { lineNumber = iline; break; } /* Go after 'endwhile'. */ else depth --; } else if (wcsnequ (lines [iline], L"while ", 6)) { depth ++; } } if (iline > numberOfLines) Melder_throw ("Unmatched 'while'."); } } else fail = TRUE; break; case 'x': fail = TRUE; break; case 'y': fail = TRUE; break; case 'z': fail = TRUE; break; default: break; } if (fail) { /* * Found an unknown word starting with a lower-case letter, optionally preceded by a period. * See whether the word is a variable name. */ wchar_t *p = & command2.string [0]; /* * Variable names consist of a sequence of letters, digits, and underscores, * optionally preceded by a period and optionally followed by a $ and/or #. */ if (*p == '.') p ++; while (isalnum (*p) || *p == '_' || *p == '.') p ++; if (*p == '$') { /* * Assign to a string variable. */ wchar_t *endOfVariable = ++ p; wchar_t *variableName = command2.string; int withFile; while (*p == ' ' || *p == '\t') p ++; /* Go to first token after variable name. */ if (*p == '[') { /* * This must be an assignment to an indexed string variable. */ *endOfVariable = '\0'; static MelderString indexedVariableName = { 0 }; MelderString_copy (& indexedVariableName, command2.string); MelderString_appendCharacter (& indexedVariableName, '['); for (;;) { p ++; // skip opening bracket or comma static MelderString index = { 0 }; MelderString_empty (& index); int depth = 0; while ((depth > 0 || (*p != ',' && *p != ']')) && *p != '\n' && *p != '\0') { MelderString_appendCharacter (& index, *p); if (*p == '[') depth ++; else if (*p == ']') depth --; p ++; } if (*p == '\n' || *p == '\0') Melder_throw ("Missing closing bracket (]) in indexed variable."); double numericIndexValue; Interpreter_numericExpression (me, index.string, & numericIndexValue); therror MelderString_append (& indexedVariableName, Melder_double (numericIndexValue)); MelderString_appendCharacter (& indexedVariableName, *p); if (*p == ']') { break; } } variableName = indexedVariableName.string; p ++; // skip closing bracket } while (*p == ' ' || *p == '\t') p ++; /* Go to first token after (perhaps indexed) variable name. */ if (*p == '=') { withFile = 0; /* Assignment. */ } else if (*p == '<') { withFile = 1; /* Read from file. */ } else if (*p == '>') { if (p [1] == '>') withFile = 2, p ++; /* Append to file. */ else withFile = 3; /* Save to file. */ } else Melder_throw ("Missing '=', '<', or '>' after variable ", variableName, "."); *endOfVariable = '\0'; p ++; while (*p == ' ' || *p == '\t') p ++; /* Go to first token after assignment or I/O symbol. */ if (*p == '\0') { if (withFile != 0) Melder_throw ("Missing file name after variable ", variableName, "."); else Melder_throw ("Missing expression after variable ", variableName, "."); } if (withFile) { structMelderFile file = { 0 }; Melder_relativePathToFile (p, & file); therror if (withFile == 1) { wchar_t *stringValue = MelderFile_readText (& file); therror InterpreterVariable var = Interpreter_lookUpVariable (me, variableName); therror Melder_free (var -> stringValue); var -> stringValue = stringValue; /* var becomes owner */ } else if (withFile == 2) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("Commands that write to a file are not available inside pictures."); InterpreterVariable var = Interpreter_hasVariable (me, variableName); therror if (! var) Melder_throw ("Variable ", variableName, " undefined."); MelderFile_appendText (& file, var -> stringValue); therror } else { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("Commands that write to a file are not available inside pictures."); InterpreterVariable var = Interpreter_hasVariable (me, variableName); therror if (! var) Melder_throw ("Variable ", variableName, " undefined."); MelderFile_writeText (& file, var -> stringValue); therror } } else if (isCommand (p)) { /* * Example: name$ = Get name */ MelderString_empty (& valueString); // empty because command may print nothing; also makes sure that valueString.string exists autoMelderDivertInfo divert (& valueString); praat_executeCommand (me, p); InterpreterVariable var = Interpreter_lookUpVariable (me, variableName); therror Melder_free (var -> stringValue); var -> stringValue = Melder_wcsdup (valueString.string); } else { /* * Evaluate a string expression and assign the result to the variable. * Examples: * sentence$ = subject$ + verb$ + object$ * extension$ = if index (file$, ".") <> 0 * ... then right$ (file$, length (file$) - rindex (file$, ".")) * ... else "" fi */ wchar_t *stringValue; Interpreter_stringExpression (me, p, & stringValue); therror InterpreterVariable var = Interpreter_lookUpVariable (me, variableName); therror Melder_free (var -> stringValue); var -> stringValue = stringValue; /* var becomes owner */ } } else if (*p == '#') { /* * Assign to a numeric array variable. */ wchar_t *endOfVariable = ++ p; while (*p == ' ' || *p == '\t') p ++; // Go to first token after variable name. if (*p == '=') { ; } else Melder_throw ("Missing '=' after variable ", command2.string, "."); *endOfVariable = '\0'; p ++; while (*p == ' ' || *p == '\t') p ++; // Go to first token after assignment or I/O symbol. if (*p == '\0') { Melder_throw ("Missing expression after variable ", command2.string, "."); } struct Formula_NumericArray value; Interpreter_numericArrayExpression (me, p, & value); therror InterpreterVariable var = Interpreter_lookUpVariable (me, command2.string); therror NUMmatrix_free (var -> numericArrayValue. data, 1, 1); var -> numericArrayValue = value; } else { /* * Try to assign to a numeric variable. */ double value; wchar_t *variableName = command2.string; int typeOfAssignment = 0; /* Plain assignment. */ if (*p == '\0') { /* * Command ends here: it may be a PraatShell command. */ praat_executeCommand (me, command2.string); therror continue; // next line } wchar_t *endOfVariable = p; while (*p == ' ' || *p == '\t') p ++; if (*p == '=' || ((*p == '+' || *p == '-' || *p == '*' || *p == '/') && p [1] == '=')) { /* * This must be an assignment (though: "echo = ..." ???) */ typeOfAssignment = *p == '+' ? 1 : *p == '-' ? 2 : *p == '*' ? 3 : *p == '/' ? 4 : 0; *endOfVariable = '\0'; // Close variable name. FIXME: this can be any weird character, e.g. hallo& } else if (*p == '[') { /* * This must be an assignment to an indexed numeric variable. */ *endOfVariable = '\0'; static MelderString indexedVariableName = { 0 }; MelderString_copy (& indexedVariableName, command2.string); MelderString_appendCharacter (& indexedVariableName, '['); for (;;) { p ++; // skip opening bracket or comma static MelderString index = { 0 }; MelderString_empty (& index); int depth = 0; while ((depth > 0 || (*p != ',' && *p != ']')) && *p != '\n' && *p != '\0') { MelderString_appendCharacter (& index, *p); if (*p == '[') depth ++; else if (*p == ']') depth --; p ++; } if (*p == '\n' || *p == '\0') Melder_throw ("Missing closing bracket (]) in indexed variable."); Interpreter_numericExpression (me, index.string, & value); therror MelderString_append (& indexedVariableName, Melder_double (value)); MelderString_appendCharacter (& indexedVariableName, *p); if (*p == ']') { break; } } variableName = indexedVariableName.string; p ++; // skip closing bracket while (*p == ' ' || *p == '\t') p ++; if (*p == '=' || ((*p == '+' || *p == '-' || *p == '*' || *p == '/') && p [1] == '=')) { typeOfAssignment = *p == '+' ? 1 : *p == '-' ? 2 : *p == '*' ? 3 : *p == '/' ? 4 : 0; } } else { /* * Not an assignment: perhaps a PraatShell command (select, echo, execute, pause ...). */ praat_executeCommand (me, variableName); therror continue; // next line } p += typeOfAssignment == 0 ? 1 : 2; while (*p == ' ' || *p == '\t') p ++; if (*p == '\0') Melder_throw ("Missing expression after variable ", variableName, "."); /* * Three classes of assignments: * var = formula * var = Query * var = Object creation */ if (isCommand (p)) { /* * Get the value of the query. */ MelderString_empty (& valueString); autoMelderDivertInfo divert (& valueString); MelderString_appendCharacter (& valueString, 1); praat_executeCommand (me, p); if (valueString.string [0] == 1) { int IOBJECT, result = 0, found = 0; WHERE (SELECTED) { result = IOBJECT; found += 1; } if (found > 1) { Melder_throw ("Multiple objects selected. Cannot assign ID to variable."); } else if (found == 0) { Melder_throw ("No objects selected. Cannot assign ID to variable."); } else { value = theCurrentPraatObjects -> list [result]. id; } } else { value = Melder_atof (valueString.string); // including --undefined-- } } else { /* * Get the value of the formula. */ Interpreter_numericExpression (me, p, & value); therror } /* * Assign the value to a variable. */ if (typeOfAssignment == 0) { /* * Use an existing variable, or create a new one. */ //Melder_casual ("looking up variable %ls", variableName); InterpreterVariable var = Interpreter_lookUpVariable (me, variableName); therror var -> numericValue = value; } else { /* * Modify an existing variable. */ InterpreterVariable var = Interpreter_hasVariable (me, variableName); therror if (var == NULL) Melder_throw ("Unknown variable ", variableName, "."); if (var -> numericValue == NUMundefined) { /* Keep it that way. */ } else { if (typeOfAssignment == 1) { var -> numericValue += value; } else if (typeOfAssignment == 2) { var -> numericValue -= value; } else if (typeOfAssignment == 3) { var -> numericValue *= value; } else if (value == 0) { var -> numericValue = NUMundefined; } else { var -> numericValue /= value; } } } } } // endif fail if (assertErrorLineNumber != 0 && assertErrorLineNumber != lineNumber) { long save_assertErrorLineNumber = assertErrorLineNumber; assertErrorLineNumber = 0; Melder_throw ("Script assertion fails in line ", save_assertErrorLineNumber, ": error " L_LEFT_GUILLEMET " ", assertErrorString.string, " " L_RIGHT_GUILLEMET " not raised. Instead: no error."); } } catch (MelderError) { //Melder_casual ("Error: << %ls >>\nassertErrorLineNumber: %ld\nlineNumber: %ld\nAssert error string: << %ls >>\n", // Melder_getError(), assertErrorLineNumber, lineNumber, assertErrorString.string); if (assertErrorLineNumber == 0) { throw; } else if (assertErrorLineNumber != lineNumber) { if (wcsstr (Melder_getError (), assertErrorString.string)) { Melder_clearError (); assertErrorLineNumber = 0; } else { wchar *errorCopy_nothrow = Melder_wcsdup_f (Melder_getError ()); // UGLY but necessary (1) Melder_clearError (); autostring errorCopy = errorCopy_nothrow; // UGLY but necessary (2) Melder_throw ("Script assertion fails in line ", assertErrorLineNumber, ": error " L_LEFT_GUILLEMET " ", assertErrorString.string, " " L_RIGHT_GUILLEMET " not raised. Instead:\n", errorCopy.peek()); } } } } // endfor lineNumber my numberOfLabels = 0; my running = false; my stopped = false; } catch (MelderError) { if (! wcsnequ (lines [lineNumber], L"exit ", 5) && ! assertionFailed) { // don't show the message twice! while (lines [lineNumber] [0] == '\0') { // did this use to be a continuation line? lineNumber --; Melder_assert (lineNumber > 0); // originally empty lines that stayed empty should not generate errors } Melder_error_ ("Script line ", lineNumber, " not performed or completed:\n" L_LEFT_GUILLEMET " ", lines [lineNumber], " " L_RIGHT_GUILLEMET); } my numberOfLabels = 0; my running = false; my stopped = false; throw; } } void Interpreter_stop (Interpreter me) { //Melder_casual ("Interpreter_stop in: %ld", me); my stopped = true; //Melder_casual ("Interpreter_stop out: %ld", me); } void Interpreter_voidExpression (Interpreter me, const wchar *expression) { Formula_compile (me, NULL, expression, kFormula_EXPRESSION_TYPE_NUMERIC, FALSE); therror struct Formula_Result result; Formula_run (0, 0, & result); therror } void Interpreter_numericExpression (Interpreter me, const wchar *expression, double *value) { Melder_assert (value != NULL); if (wcsstr (expression, L"(=")) { *value = Melder_atof (expression); } else { Formula_compile (me, NULL, expression, kFormula_EXPRESSION_TYPE_NUMERIC, FALSE); therror struct Formula_Result result; Formula_run (0, 0, & result); therror *value = result. result.numericResult; } } void Interpreter_stringExpression (Interpreter me, const wchar *expression, wchar **value) { Formula_compile (me, NULL, expression, kFormula_EXPRESSION_TYPE_STRING, FALSE); therror struct Formula_Result result; Formula_run (0, 0, & result); therror *value = result. result.stringResult; } void Interpreter_numericArrayExpression (Interpreter me, const wchar *expression, struct Formula_NumericArray *value) { Formula_compile (me, NULL, expression, kFormula_EXPRESSION_TYPE_NUMERIC_ARRAY, FALSE); therror struct Formula_Result result; Formula_run (0, 0, & result); therror *value = result. result.numericArrayResult; } void Interpreter_anyExpression (Interpreter me, const wchar_t *expression, struct Formula_Result *result) { Formula_compile (me, NULL, expression, kFormula_EXPRESSION_TYPE_UNKNOWN, FALSE); therror Formula_run (0, 0, result); therror } /* End of file Interpreter.cpp */ sources_5316/sys/abcio_enums.h0000644000176700017670000000234111160251016015167 0ustar paulpaul/* abcio_enums.h * * Copyright (C) 1992-2009 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2009/03/18 */ enums_begin (kBoolean, 0) enums_add (kBoolean, 0, FALSE, L"false") enums_add (kBoolean, 1, TRUE, L"true") enums_end (kBoolean, 1, FALSE) enums_begin (kQuestion, 0) enums_add (kQuestion, 0, NO, L"no") enums_add (kQuestion, 1, YES, L"yes") enums_end (kQuestion, 1, NO) enums_begin (kExistence, 0) enums_add (kExistence, 0, ABSENT, L"absent") enums_add (kExistence, 1, EXISTS, L"exists") enums_end (kExistence, 1, ABSENT) /* End of file abcio_enums.h */ sources_5316/sys/complex.h0000644000176700017670000000435611611106371014366 0ustar paulpaul#ifndef _complex_h_ #define _complex_h_ /* complex.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ typedef struct fcomplex { float re, im; } fcomplex; typedef struct dcomplex { double re, im; } dcomplex; /* * Stack-based complex arithmetic. * Some compilers will issue warnings about returning structs larger than 8 bytes, * but will still work as expected. */ fcomplex fcomplex_add (fcomplex a, fcomplex b); dcomplex dcomplex_add (dcomplex a, dcomplex b); /* Addition: a + b */ fcomplex fcomplex_sub (fcomplex a, fcomplex b); dcomplex dcomplex_sub (dcomplex a, dcomplex b); /* Subtraction: a - b */ fcomplex fcomplex_mul (fcomplex a, fcomplex b); dcomplex dcomplex_mul (dcomplex a, dcomplex b); /* Multiplication: a * b */ fcomplex fcomplex_create (float re, float im); dcomplex dcomplex_create (double re, double im); /* Create a complex number: { re, im } */ fcomplex fcomplex_conjugate (fcomplex z); dcomplex dcomplex_conjugate (dcomplex z); /* Conjugation: { z.re, - z.im } */ fcomplex fcomplex_div (fcomplex a, fcomplex b); dcomplex dcomplex_div (dcomplex a, dcomplex b); /* Division: a / b */ float fcomplex_abs (fcomplex z); double dcomplex_abs (dcomplex z); /* Absolute value: | z | */ fcomplex fcomplex_sqrt (fcomplex z); dcomplex dcomplex_sqrt (dcomplex z); /* Square root: sqrt (z) */ fcomplex fcomplex_rmul (float x, fcomplex a); dcomplex dcomplex_rmul (double x, dcomplex a); /* Multiplication by a real number: x * a */ fcomplex fcomplex_exp (fcomplex z); dcomplex dcomplex_exp (dcomplex z); /* Exponentiation: e^z */ /* End of file complex.h */ #endif sources_5316/sys/Printer.cpp0000644000176700017670000004320611753751163014706 0ustar paulpaul/* Printer.cpp * * Copyright (C) 1998-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2003/02/05 distinct treatment of NT and non-NT * pb 2004/05/25 font choice strategy * pb 2004/09/25 use /tmp as temporary directory * pb 2005/05/19 preference to switch screen preview off * pb 2005/07/21 removed bug in previous change for Linux * pb 2006/10/28 erased MacOS 9 stuff * pb 2006/12/28 theCurrentPraat * pb 2007/04/28 Mac: error messages for failing PostScript passthrough * pb 2007/08/12 wchar_t * pb 2007/10/05 less char * pb 2007/12/09 enums * pb 2009/01/18 arguments to UiForm callbacks * pb 2011/05/15 C++ * pb 2011/07/11 C++ */ #include // close #include "melder.h" #if defined (_WIN32) #include #endif #include "Printer.h" #include "praat.h" // topShell #include "Ui.h" #include "site.h" /* * Everything must look the same on every printer, including on PDF, * so the margins must be constant with respect to the paper, not to the writable page. */ /* exported */ struct Printer thePrinter = { kGraphicsPostscript_spots_DEFAULT, kGraphicsPostscript_paperSize_DEFAULT, kGraphicsPostscript_orientation_DEFAULT, false, true, kGraphicsPostscript_fontChoiceStrategy_DEFAULT, 600, 5100, 6600, 1.0, NULL }; void Printer_prefs (void) { Preferences_addEnum (L"Printer.spots", & thePrinter. spots, kGraphicsPostscript_spots, DEFAULT); Preferences_addEnum (L"Printer.paperSize", & thePrinter. paperSize, kGraphicsPostscript_paperSize, DEFAULT); Preferences_addBool (L"Printer.allowDirectPostScript", & thePrinter. allowDirectPostScript, true); Preferences_addEnum (L"Printer.fontChoiceStrategy", & thePrinter. fontChoiceStrategy, kGraphicsPostscript_fontChoiceStrategy, DEFAULT); } #if defined (macintosh) static PMPrintSession theMacPrintSession; static PMPageFormat theMacPageFormat; static PMPrintSettings theMacPrintSettings; static GrafPtr theMacPort; static PMRect paperSize; #endif #ifdef _WIN32 static PRINTDLG theWinPrint; static HDC theWinDC; #endif #if defined (_WIN32) || defined (macintosh) int Printer_postScript_printf (void *stream, const char *format, ... ) { #if defined (_WIN32) static union { char chars [3002]; short shorts [1501]; } theLine; #elif defined (macintosh) static Handle theLine; #endif int length; va_list args; va_start (args, format); (void) stream; #if defined (_WIN32) vsprintf (theLine.chars + 2, format, args); length = strlen (theLine.chars + 2); theLine.shorts [0] = length; if (length > 0 && theLine.chars [length + 1] == '\n') { theLine.chars [length + 1] = '\r'; theLine.chars [length + 2] = '\n'; theLine.chars [length + 3] = '\0'; length ++; } Escape (theWinDC, POSTSCRIPT_PASSTHROUGH, length + 2, theLine.chars, NULL); #elif defined (macintosh) if (! theLine) { theLine = NewHandle (3000); HLock (theLine); } vsprintf (*theLine, format, args); length = strlen (*theLine); if (length > 0 && (*theLine) [length - 1] == '\n') (*theLine) [length - 1] = '\r'; SetPort (theMacPort); PMSessionPostScriptData (theMacPrintSession, *theLine, strlen (*theLine)); #endif va_end (args); return 1; } #endif #if defined (_WIN32) static void initPostScriptPage (void) { /* * Save the driver's state. */ Printer_postScript_printf (NULL, "/PraatPictureSaveObject save def\n"); /* * The LaserWriter driver puts the coordinates upside down. * According to the PostScript Reference Manual, * "There are few situations in which a PostScript language program * should execute initgraphics explicitly." * This is one of them. BUG: it probably is *not* one of them. Just do something like currentmatrix [1 0 -1 0 0 0] mul setmatrix or whatever it is. */ #if 1 Printer_postScript_printf (NULL, "initmatrix initclip\n"); #else Printer_postScript_printf (NULL, "8 8 scale initclip\n"); #endif } static void exitPostScriptPage (void) { Printer_postScript_printf (NULL, "PraatPictureSaveObject restore\n"); } #endif #if defined (macintosh) static void initPrinter (void) { Boolean result; PMResolution res300 = { 300, 300 }, res600 = { 600, 600 }; if (theMacPrintSettings == NULL) { /* Once. */ PMCreateSession (& theMacPrintSession); /* Initialize the Printing Manager. */ PMCreatePageFormat (& theMacPageFormat); PMCreatePrintSettings (& theMacPrintSettings); PMSessionDefaultPageFormat (theMacPrintSession, theMacPageFormat); PMSessionDefaultPrintSettings (theMacPrintSession, theMacPrintSettings); } PMSessionValidatePageFormat (theMacPrintSession, theMacPageFormat, & result); PMSessionValidatePrintSettings (theMacPrintSession, theMacPrintSettings, & result); /* * BUG. * If we now ask for the available printer resolutions, * we may get the answer that there's only 300 dpi (perhaps PostScript drivers say so?). * So we don't rely on that and have a buggy assumption instead. */ PMSetResolution (theMacPageFormat, & res300); /* Perhaps all printers have this... */ PMSetResolution (theMacPageFormat, & res600); /* ... but this is preferred. */ } #endif #if defined (_WIN32) static void initPrinter (void) { } #endif void Printer_nextPage (void) { #if defined (macintosh) PMSessionEndPage (theMacPrintSession); PMSessionBeginPage (theMacPrintSession, theMacPageFormat, NULL); PMSessionGetGraphicsContext (theMacPrintSession, kPMGraphicsContextQuickdraw, (void **) & theMacPort); SetPort (theMacPort); SetOrigin (- paperSize. left, - paperSize. top); #elif defined (_WIN32) if (thePrinter. postScript) { exitPostScriptPage (); EndPage (theWinDC); StartPage (theWinDC); initPostScriptPage (); } else { if (EndPage (theWinDC) < 0) ; /* BUG: should give the opportunity of cancellation. */ StartPage (theWinDC); /* * Since StartPage has reset the DC, restore some of our non-default settings. */ SetBkMode (theWinDC, TRANSPARENT); SetTextAlign (theWinDC, TA_LEFT | TA_BASELINE | TA_NOUPDATECP); } #endif } int Printer_pageSetup (void) { #if defined (macintosh) Boolean accepted; initPrinter (); PMSessionPageSetupDialog (theMacPrintSession, theMacPageFormat, & accepted); #endif return 1; } static void DO_Printer_postScriptSettings (UiForm dia, const wchar *sendingString_dummy, Interpreter interpreter_dummy, const wchar *invokingButtonTitle, bool modified, void *dummy) { (void) sendingString_dummy; (void) interpreter_dummy; (void) invokingButtonTitle; (void) modified; (void) dummy; #if defined (_WIN32) thePrinter. allowDirectPostScript = GET_INTEGER (L"Allow direct PostScript"); #endif thePrinter. spots = GET_ENUM (kGraphicsPostscript_spots, L"Grey resolution"); #if defined (UNIX) thePrinter. paperSize = GET_ENUM (kGraphicsPostscript_paperSize, L"Paper size"); if (thePrinter. paperSize == kGraphicsPostscript_paperSize_A3) { thePrinter. paperWidth = 842 * thePrinter. resolution / 72; thePrinter. paperHeight = 1191 * thePrinter. resolution / 72; } else if (thePrinter. paperSize == kGraphicsPostscript_paperSize_US_LETTER) { thePrinter. paperWidth = 612 * thePrinter. resolution / 72; thePrinter. paperHeight = 792 * thePrinter. resolution / 72; } else { thePrinter. paperWidth = 595 * thePrinter. resolution / 72; thePrinter. paperHeight = 842 * thePrinter. resolution / 72; } thePrinter. orientation = GET_ENUM (kGraphicsPostscript_orientation, L"Orientation"); thePrinter. magnification = GET_REAL (L"Magnification"); Site_setPrintCommand (GET_STRING (L"printCommand")); #endif thePrinter. fontChoiceStrategy = GET_ENUM (kGraphicsPostscript_fontChoiceStrategy, L"Font choice strategy"); } int Printer_postScriptSettings (void) { static Any dia; if (dia == NULL) { Any radio; dia = UiForm_create (theCurrentPraatApplication -> topShell, L"PostScript settings", DO_Printer_postScriptSettings, NULL, L"PostScript settings...", L"PostScript settings..."); #if defined (_WIN32) BOOLEAN (L"Allow direct PostScript", TRUE); #endif RADIO_ENUM (L"Grey resolution", kGraphicsPostscript_spots, DEFAULT) #if defined (UNIX) RADIO_ENUM (L"Paper size", kGraphicsPostscript_paperSize, DEFAULT); RADIO_ENUM (L"Orientation", kGraphicsPostscript_orientation, DEFAULT); POSITIVE (L"Magnification", L"1.0"); LABEL (L"label", L"Print command:"); #if defined (linux) TEXTFIELD (L"printCommand", L"lpr %s"); #else TEXTFIELD (L"printCommand", L"lp -c %s"); #endif #endif RADIO_ENUM (L"Font choice strategy", kGraphicsPostscript_fontChoiceStrategy, DEFAULT); UiForm_finish (dia); } #if defined (_WIN32) SET_INTEGER (L"Allow direct PostScript", thePrinter. allowDirectPostScript); #endif SET_ENUM (L"Grey resolution", kGraphicsPostscript_spots, thePrinter. spots); #if defined (UNIX) SET_ENUM (L"Paper size", kGraphicsPostscript_paperSize, thePrinter. paperSize); SET_ENUM (L"Orientation", kGraphicsPostscript_orientation, thePrinter. orientation); SET_REAL (L"Magnification", thePrinter. magnification); SET_STRING (L"printCommand", Site_getPrintCommand ()); #endif SET_ENUM (L"Font choice strategy", kGraphicsPostscript_fontChoiceStrategy, thePrinter. fontChoiceStrategy); UiForm_do (dia, false); return 1; } #ifdef _WIN32 static BOOL CALLBACK AbortFunc (HDC hdc, int nCode) { MSG msg; (void) hdc; (void) nCode; while (PeekMessage (& msg, 0, 0, 0, PM_REMOVE)) { TranslateMessage (& msg); DispatchMessage (& msg); } return TRUE; } HDC Printer_getDC (void) { if (! theWinPrint. hDevMode) { memset (& theWinPrint, 0, sizeof (PRINTDLG)); theWinPrint. lStructSize = sizeof (PRINTDLG); theWinPrint. Flags = PD_RETURNDEFAULT | PD_RETURNDC; PrintDlg (& theWinPrint); } return theWinPrint. hDC; } #endif int Printer_print (void (*draw) (void *boss, Graphics g), void *boss) { try { #if defined (UNIX) structMelderFile tempFile = { 0 }; char tempPath_utf8 [] = "/tmp/picXXXXXX"; close (mkstemp (tempPath_utf8)); Melder_pathToFile (Melder_peekUtf8ToWcs (tempPath_utf8), & tempFile); thePrinter. graphics = Graphics_create_postscriptjob (& tempFile, thePrinter. resolution, thePrinter. spots, thePrinter. paperSize, thePrinter. orientation, thePrinter. magnification); draw (boss, thePrinter. graphics); forget (thePrinter. graphics); char command [500]; sprintf (command, Melder_peekWcsToUtf8 (Site_getPrintCommand ()), tempPath_utf8); system (command); MelderFile_delete (& tempFile); #elif defined (_WIN32) int postScriptCode = POSTSCRIPT_PASSTHROUGH; DOCINFO docInfo; DEVMODE *devMode; initPrinter (); if (! theWinPrint. hDevMode) { memset (& theWinPrint, 0, sizeof (PRINTDLG)); theWinPrint. lStructSize = sizeof (PRINTDLG); theWinPrint. Flags = PD_RETURNDEFAULT; if (! PrintDlg (& theWinPrint)) Melder_throw ("Cannot initialize printer."); } if (Melder_backgrounding) { theWinPrint. Flags = PD_RETURNDEFAULT | PD_RETURNDC; if (! PrintDlg (& theWinPrint) || theWinPrint. hDC == NULL) { Melder_throw ("Cannot print from a script on this computer."); } } else { theWinPrint. Flags &= ~ PD_RETURNDEFAULT; theWinPrint. Flags |= PD_RETURNDC; if (! PrintDlg (& theWinPrint)) return 1; } theWinDC = theWinPrint. hDC; thePrinter. postScript = thePrinter. allowDirectPostScript && Escape (theWinDC, QUERYESCSUPPORT, sizeof (int), (LPSTR) & postScriptCode, NULL); /* * The HP colour inkjet printer returns in dmFields: * 0, 1, 8, 9, 10, 11, 12, 13, 14, 15, 23, 24, 25, 26 = DM_ORIENTATION | * DM_PAPERSIZE | DM_COPIES | DM_DEFAULTSOURCE | DM_PRINTQUALITY | * DM_COLOR | DM_DUPLEX | DM_YRESOLUTION | DM_TTOPTION | DM_COLLATE | * DM_ICMMETHOD | DM_ICMINTENT | DM_MEDIATYPE | DM_DITHERTYPE */ devMode = * (DEVMODE **) theWinPrint. hDevMode; thePrinter. resolution = devMode -> dmFields & DM_YRESOLUTION ? devMode -> dmYResolution : devMode -> dmFields & DM_PRINTQUALITY ? ( devMode -> dmPrintQuality > 0 ? devMode -> dmPrintQuality : 300 ) : 300; if (devMode -> dmFields & DM_PAPERWIDTH) { thePrinter. paperWidth = devMode -> dmPaperWidth * thePrinter. resolution / 254; thePrinter. paperHeight = devMode -> dmPaperLength * thePrinter. resolution / 254; } else if (devMode -> dmFields & DM_PAPERSIZE) { static struct { float width, height; } sizes [] = { { 0, 0 }, { 8.5, 11 }, { 8.5, 11 }, { 11, 17 }, { 17, 11 }, { 8.5, 14 }, { 5.5, 8.5 }, { 7.25, 10.5 }, { 297/25.4, 420/25.4 }, { 210/25.4, 297/25.4 }, { 210/25.4, 297/25.4 }, { 148.5/25.4, 210/25.4 }, { 250/25.4, 354/25.4 }, { 182/25.4, 257/25.4 }, { 8.5, 13 }, { 215/25.4, 275/25.4 }, { 10, 14 }, { 11, 17 }, { 8.5, 11 }, { 3.875, 8.875 }, { 4.125, 9.5 }, { 4.5, 10.375 } }; int paperSize = devMode -> dmPaperSize; if (paperSize <= 0 || paperSize > 21) paperSize = 1; thePrinter. paperWidth = sizes [paperSize]. width * thePrinter. resolution; thePrinter. paperHeight = sizes [paperSize]. height * thePrinter. resolution; if (devMode -> dmOrientation == DMORIENT_LANDSCAPE) { long dummy = thePrinter. paperWidth; thePrinter. paperWidth = thePrinter. paperHeight; thePrinter. paperHeight = dummy; } } else { thePrinter. paperWidth = 1000; thePrinter. paperHeight = 1000; } EnableWindow ((HWND) XtWindow (theCurrentPraatApplication -> topShell), FALSE); SetAbortProc (theWinDC, AbortFunc); memset (& docInfo, 0, sizeof (DOCINFO)); docInfo. cbSize = sizeof (DOCINFO); docInfo. lpszDocName = L"Praatjes"; docInfo. lpszOutput = NULL; if (thePrinter. postScript) { StartDoc (theWinDC, & docInfo); StartPage (theWinDC); initPostScriptPage (); thePrinter. graphics = Graphics_create_postscriptprinter (); draw (boss, thePrinter. graphics); forget (thePrinter. graphics); exitPostScriptPage (); EndPage (theWinDC); EndDoc (theWinDC); } else { StartDoc (theWinDC, & docInfo); StartPage (theWinDC); thePrinter. graphics = Graphics_create_screenPrinter (NULL, theWinDC); draw (boss, thePrinter. graphics); forget (thePrinter. graphics); if (EndPage (theWinDC) < 0) { Melder_throw ("Cannot print page."); } else { EndDoc (theWinDC); } } EnableWindow ((HWND) XtWindow (theCurrentPraatApplication -> topShell), TRUE); DeleteDC (theWinDC), theWinDC = NULL; #elif defined (macintosh) Boolean result; initPrinter (); if (Melder_backgrounding) { PMSessionValidatePageFormat (theMacPrintSession, theMacPageFormat, & result); PMSessionValidatePrintSettings (theMacPrintSession, theMacPrintSettings, & result); } else { Boolean accepted; PMSessionPrintDialog (theMacPrintSession, theMacPrintSettings, theMacPageFormat, & accepted); if (! accepted) return 1; // normal cancelled return } PMSessionValidatePageFormat (theMacPrintSession, theMacPageFormat, & result); PMSessionValidatePrintSettings (theMacPrintSession, theMacPrintSettings, & result); PMResolution res; PMGetResolution (theMacPageFormat, & res); thePrinter. resolution = res. hRes; PMGetAdjustedPaperRect (theMacPageFormat, & paperSize); thePrinter. paperWidth = paperSize. right - paperSize. left; thePrinter. paperHeight = paperSize. bottom - paperSize. top; thePrinter. postScript = false; PMOrientation orientation; PMGetOrientation (theMacPageFormat, & orientation); thePrinter. orientation = orientation == kPMLandscape || orientation == kPMReverseLandscape ? kGraphicsPostscript_orientation_LANDSCAPE : kGraphicsPostscript_orientation_PORTRAIT; PMSessionBeginDocument (theMacPrintSession, theMacPrintSettings, theMacPageFormat); // PMSessionBeginCGDocumentNoDialog PMSessionBeginPage (theMacPrintSession, theMacPageFormat, NULL); // PMSessionBeginPageNoDialog PMSessionGetGraphicsContext (theMacPrintSession, kPMGraphicsContextQuickdraw, (void **) & theMacPort); /* * On PostScript, the point (0, 0) is the bottom left corner of the paper, which is fine. * On the screen, however, the point (0, 0) is the top left corner of the writable page. * Since we want paper-related margins, not writable-page-related margins, * we require that this point gets the coordinates (250, 258) or so, * so that the top left corner of the paper gets coordinates (0, 0). * The "left" and "top" attributes of rPaper are negative values (e.g. -250 and -258), * so multiply them by -1. * * Under Carbon, the port has to be set inside the page. */ SetPort (theMacPort); SetOrigin (- paperSize. left, - paperSize. top); thePrinter. graphics = Graphics_create_screenPrinter (NULL, theMacPort); draw (boss, thePrinter. graphics); forget (thePrinter. graphics); if (theMacPort) { PMSessionEndPage (theMacPrintSession); // PMSessionEndPageNoDialog PMSessionEndDocument (theMacPrintSession); // PMSessionEndDocumentNoDialog theMacPort = NULL; } #endif return 1; } catch (MelderError) { #if defined (macintosh) if (theMacPort) { PMSessionEndPage (theMacPrintSession); PMSessionEndDocument (theMacPrintSession); theMacPort = NULL; } #endif Melder_throw ("Not printed."); } } /* End of file Printer.cpp */ sources_5316/sys/oo_EQUAL.h0000644000176700017670000001142511724670615014272 0ustar paulpaul/* oo_EQUAL.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) \ if (x != thy x) return false; #define oo_ARRAY(type,storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ if (x [i] != thy x [i]) return false; \ #define oo_SET(type,storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ if (x [i] != thy x [i]) return false; \ #define oo_VECTOR(type,storage,x,min,max) \ if (! x != ! thy x || \ (x && ! NUMvector_equal (x, thy x, min, max))) return false; #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) \ if (! x != ! thy x || \ (x && ! NUMmatrix_equal (x, thy x, row1, row2, col1, col2))) return false; #define oo_ENUMx(type,storage,Type,x) \ if (x != thy x) return false; #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) \ for (int i = 0; i < n; i ++) if (x [i] != thy x [i]) return false; #define oo_ENUMx_SET(type,storage,Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) if (x [i] != thy x [i]) return false; #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) \ if (! x != ! thy x || \ (x && ! NUMvector_equal (x, thy x, min, max))) return false; #define oo_STRINGx(storage,x) \ if (! Melder_wcsequ (x, thy x)) return false; #define oo_STRINGx_ARRAY(storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ if (! Melder_wcsequ (x [i], thy x [i])) return false; #define oo_STRINGx_SET(storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ if (! Melder_wcsequ (x [i], thy x [i])) return false; #define oo_STRINGx_VECTOR(storage,x,min,max) \ if (! x != ! thy x) return false; \ if (x) { \ for (long i = min; i <= max; i ++) \ if (! Melder_wcsequ (x [i], thy x [i])) return false; \ } #define oo_STRUCT(Type,x) \ if (! x. equal (& thy x)) return false; #define oo_STRUCT_ARRAY(Type,x,cap,n) \ for (int i = 0; i < n; i ++) \ if (! x [i]. equal (& thy x [i])) return false; #define oo_STRUCT_SET(Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ if (! x [i]. equal (& thy x [i])) return false; #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ if (! x != ! thy x) return false; \ if (x) { \ for (long i = min; i <= max; i ++) \ if (! x [i]. equal (& thy x [i])) return false; \ } #define oo_STRUCT_MATRIX_FROM(Type,x,row1,row2,col1,col2) \ if (! x != ! thy x) return false; \ if (x) { \ for (long i = row1; i <= row2; i ++) \ for (long j = col1; j <= col2; j ++) \ if (! x [i] [j]. equal (& thy x [i] [j])) return false; \ } #define oo_WIDGET(x) \ !!!! Can never compare Widgets... !!!! #define oo_WIDGET_ARRAY(x,cap,n) \ !!!! Can never compare Widgets... !!!! #define oo_WIDGET_SET(x,setType) \ !!!! Can never compare Widgets... !!!! #define oo_WIDGET_VECTOR_FROM(x,cap,min,max) \ !!!! Can never compare Widgets... !!!! #define oo_OBJECT(Class,version,x) \ if (! x != ! thy x || (x && ! Data_equal (x, thy x))) return false; #define oo_COLLECTION(Class,x,ItemClass,version) \ if (! x != ! thy x || (x && ! Data_equal (x, thy x))) return false; #define oo_FILE(x) \ if (! MelderFile_equal (& x, & thy x)) return false; #define oo_DIR(x) \ if (! MelderDir_equal (& x, & thy x)) return false; #define oo_DEFINE_STRUCT(Type) \ bool struct##Type :: equal (Type thee) { #define oo_END_STRUCT(Type) \ return true; \ } #define oo_DEFINE_CLASS(Class,Parent) \ bool struct##Class :: v_equal (thou) { \ thouart (Class); \ if (! Class##_Parent :: v_equal (thee)) return false; #define oo_END_CLASS(Class) \ return true; \ } #define oo_IF(condition) \ if (condition) { #define oo_ENDIF \ } #define oo_FROM(from) #define oo_ENDFROM #define oo_VERSION(version) #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 1 #define oo_COMPARING 1 #define oo_VALIDATING_ENCODING 0 #define oo_READING 0 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 0 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_EQUAL.h */ sources_5316/sys/abcio.h0000644000176700017670000003545211611106261013773 0ustar paulpaul#ifndef _abcio_h_ #define _abcio_h_ /* abcio.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "complex.h" #include "melder.h" #include "abcio_enums.h" /* Numeric text input and output. */ int texgeti1 (MelderReadText text); int texgeti2 (MelderReadText text); long texgeti4 (MelderReadText text); unsigned int texgetu1 (MelderReadText text); unsigned int texgetu2 (MelderReadText text); unsigned long texgetu4 (MelderReadText text); double texgetr4 (MelderReadText text); double texgetr8 (MelderReadText text); double texgetr10 (MelderReadText text); fcomplex texgetc8 (MelderReadText text); dcomplex texgetc16 (MelderReadText text); short texgete1 (MelderReadText text, int (*getValue) (const wchar_t *)); short texgete2 (MelderReadText text, int (*getValue) (const wchar_t *)); short texgeteb (MelderReadText text); short texgeteq (MelderReadText text); short texgetex (MelderReadText text); char *texgets2 (MelderReadText text); char *texgets4 (MelderReadText text); wchar_t *texgetw2 (MelderReadText text); wchar_t *texgetw4 (MelderReadText text); void texindent (MelderFile file); void texexdent (MelderFile file); void texresetindent (MelderFile file); void texputintro (MelderFile file, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputi1 (MelderFile file, int i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputi2 (MelderFile file, int i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputi4 (MelderFile file, long i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputu1 (MelderFile file, unsigned int u, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputu2 (MelderFile file, unsigned int u, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputu4 (MelderFile file, unsigned long u, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputr4 (MelderFile file, double x, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputr8 (MelderFile file, double x, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputc8 (MelderFile file, fcomplex z, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputc16 (MelderFile file, dcomplex z, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texpute1 (MelderFile file, int i, const wchar_t * (*getText) (int), const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texpute2 (MelderFile file, int i, const wchar_t * (*getText) (int), const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputeb (MelderFile file, bool i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputeq (MelderFile file, bool i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputex (MelderFile file, bool i, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputs1 (MelderFile file, const char *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputs2 (MelderFile file, const char *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputs4 (MelderFile file, const char *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputw2 (MelderFile file, const wchar_t *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); void texputw4 (MelderFile file, const wchar_t *s, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6); /* Portable device-independent binary input and output. */ /* Works on all machines with 8-bit bytes and chars, and 2's complement integers. */ /* Works independent of byte order or floating-point implementations. */ /* The 42 routines are analogous to fgetc and fputc, who read or write one character: int fgetc (FILE *f); int fputc (int c, FILE *f); // 0..255 */ unsigned int bingetu1 (FILE *f); void binputu1 (unsigned int i, FILE *f); /* 0..255 */ unsigned int bingetu2 (FILE *f); void binputu2 (unsigned int i, FILE *f); /* 0..65535 */ unsigned long bingetu4 (FILE *f); void binputu4 (unsigned long i, FILE *f); /* 0..4294967295 */ int bingeti1 (FILE *f); void binputi1 (int i, FILE *f); /* -128..127 */ int bingeti2 (FILE *f); void binputi2 (int i, FILE *f); /* -32768..32767 */ long bingeti3 (FILE *f); void binputi3 (long i, FILE *f); /* -8388608..2148388607 */ long bingeti4 (FILE *f); void binputi4 (long i, FILE *f); /* -2147483648..2147483647 */ /* Read or write signed or unsigned integers from or to 2 or 4 bytes in the stream 'f', in big-endian byte order (most significant byte first). This is the native integer format on Macintosh and Silicon Graphics Iris. */ int bingeti2LE (FILE *f); void binputi2LE (int i, FILE *f); /* -32768..32767 */ long bingeti3LE (FILE *f); void binputi3LE (long i, FILE *f); /* -8388608..2148388607 */ long bingeti4LE (FILE *f); void binputi4LE (long i, FILE *f); /* -2147483648..2147483647 */ unsigned int bingetu2LE (FILE *f); void binputu2LE (unsigned int i, FILE *f); /* 0..65535 */ unsigned long bingetu4LE (FILE *f); void binputu4LE (unsigned long i, FILE *f); /* 0..4294967295 */ /* Read or write signed or unsigned integers from or to 2 or 4 bytes in the stream 'f', in little-endian byte order (least significant byte first). This is the native integer format on Vax and IBM PC. */ unsigned int bingetb1 (FILE *f); void binputb1 (unsigned int value, FILE *f); /* 0..1*/ unsigned int bingetb2 (FILE *f); void binputb2 (unsigned int value, FILE *f); /* 0..3 */ unsigned int bingetb3 (FILE *f); void binputb3 (unsigned int value, FILE *f); /* 0..7 */ unsigned int bingetb4 (FILE *f); void binputb4 (unsigned int value, FILE *f); /* 0..15 */ unsigned int bingetb5 (FILE *f); void binputb5 (unsigned int value, FILE *f); /* 0..31 */ unsigned int bingetb6 (FILE *f); void binputb6 (unsigned int value, FILE *f); /* 0..63 */ unsigned int bingetb7 (FILE *f); void binputb7 (unsigned int value, FILE *f); /* 0..127 */ void bingetb (FILE *f); void binputb (FILE *f); /* Read or write an unsigned integer from or to a number of bits in the stream 'f'. After an uninterrupted sequence of bingetbxxx or binputbxxx, call bingetb or binputb. Not reentrant: uses a static one-byte buffer. Do not call from interrupt routines. Example 1: int hasTitle = bingetb1 (f); // One bit. int category = bingetb3 (f); // A number in the range 0..7. int sense = bingetb2 (f); // A number in the range 0..3. bingetb (f); Example 2: binputb1 (hasTitle, f); // One bit. binputb3 (category, f); // A number in the range 0..7. binputb2 (sense, f); // A number in the range 0..3. binputb (f); */ int bingete1 (FILE *f, int min, int max, const wchar_t *type); int bingete2 (FILE *f, int min, int max, const wchar_t *type); #define bingeteb bingeti1 #define bingeteq bingeti1 #define bingetex bingeti1 void binpute1 (int value, FILE *f); void binpute2 (int value, FILE *f); #define binputeb binputi1 #define binputeq binputi1 #define binputex binputi1 double bingetr4 (FILE *f); void binputr4 (double x, FILE *f); /* Read or write a real number from or to 4 bytes in the stream 'f', in IEEE single-precision binary real format, with the most significant bit first. NaN's (Not-a-Numbers) and infinities get the value HUGE, which equals infinity on IEEE machines. Absolute values of normalized numbers (23 bits precision): 1.2e-38 .. 3.4e38. Denormalized: from 1.4e-45. This is the native format of a 'float' on Macintosh and Silicon Graphics Iris. */ double bingetr4LE (FILE *f); void binputr4LE (double x, FILE *f); // Least significant bit first. double bingetr8 (FILE *f); void binputr8 (double x, FILE *f); /* Read or write a real number from or to 8 bytes in the stream 'f', in IEEE double-precision binary real format, with the most significant bit first. NaN's (Not-a-Numbers) and infinities get the value HUGE, which equals infinity on IEEE machines. Absolute values of normalized numbers (52 bits precision): 2.2e-308 .. 1.8e308. Denormalized: from 4.9e-324. This is the native format of a 'double' on Silicon Graphics Iris and PowerMac. */ double bingetr10 (FILE *f); void binputr10 (double x, FILE *f); /* Read or write a real number from or to 10 bytes in the stream 'f', in IEEE extended-precision binary real format, with the most significant bit first, as implemented in Motorola's MC68881 floating-point coprocessor. NaN's (Not-a-Numbers) and infinities get the value HUGE, which equals infinity on IEEE machines. Absolute values of normalized numbers (63 bits precision): 8e-4933 .. 6e4931. Denormalized: from 9e-4952. This format is used to encode the sampling rate in AIFF (Audio Interchange File Format) files, and is the native format of a 'double' on 68k Macintosh. */ fcomplex bingetc8 (FILE *f); dcomplex bingetc16 (FILE *f); void binputc8 (fcomplex z, FILE *f); void binputc16 (dcomplex z, FILE *f); char * bingets1 (FILE *f); void binputs1 (const char *s, FILE *f); /* 0..255 characters. */ char * bingets2 (FILE *f); void binputs2 (const char *s, FILE *f); /* 0..65535 characters. */ char * bingets4 (FILE *f); void binputs4 (const char *s, FILE *f); /* 0..4294967295 characters. */ /* Read or write a string from or to wcslen (s) UTF-16LE or ASCII characters + 1, 2, or 4 bytes in the stream 'f', in a Pascal-style format: first the length, then the characters, without a trailing null byte. bingetsxxx returns a new 'malloc'ed null-terminated C string (for the caller to 'free' it), or NULL if out of memory. binputsxxx expects a null-terminated C string whose 'wcslen' fits in 1, 2, or 4 bytes. */ wchar_t * bingetw1 (FILE *f); void binputw1 (const wchar_t *s, FILE *f); wchar_t * bingetw2 (FILE *f); void binputw2 (const wchar_t *s, FILE *f); wchar_t * bingetw4 (FILE *f); void binputw4 (const wchar_t *s, FILE *f); /********** cache I/O **********/ typedef struct { unsigned char *ptr, *base, *max; } CACHE; CACHE * memopen (size_t nbytes); /* The following routines are completely analogous to fxxx, although they do not check for overflow. */ int memclose (CACHE *f); size_t memread (void *ptr, size_t size, size_t nmemb, CACHE *m); size_t memwrite (const void *ptr, size_t size, size_t nmemb, CACHE *m); int memseek (CACHE *f, long offset, int whence); /* No SEEK_END. */ long memtell (CACHE *f); void memrewind (CACHE *me); void memprint1 (CACHE *me, const char *s1); void memprint2 (CACHE *me, const char *s1, const char *s2); void memprint3 (CACHE *me, const char *s1, const char *s2, const char *s3); void memprint4 (CACHE *me, const char *s1, const char *s2, const char *s3, const char *s4); void memprint5 (CACHE *me, const char *s1, const char *s2, const char *s3, const char *s4, const char *s5); /* Portable device-independent binary input and output from and to a CACHE. This rest of this header file is completely analogous to binario.h, with only the following changes: bingetxxx replaced by cacgetxxx; binputxxx replaced by cacputxxx; FILE replaced by CACHE; */ unsigned int cacgetb1 (CACHE *f); void cacputb1 (unsigned int value, CACHE *f); unsigned int cacgetb2 (CACHE *f); void cacputb2 (unsigned int value, CACHE *f); unsigned int cacgetb3 (CACHE *f); void cacputb3 (unsigned int value, CACHE *f); unsigned int cacgetb4 (CACHE *f); void cacputb4 (unsigned int value, CACHE *f); unsigned int cacgetb5 (CACHE *f); void cacputb5 (unsigned int value, CACHE *f); unsigned int cacgetb6 (CACHE *f); void cacputb6 (unsigned int value, CACHE *f); unsigned int cacgetb7 (CACHE *f); void cacputb7 (unsigned int value, CACHE *f); void cacgetb (CACHE *f); void cacputb (CACHE *f); unsigned int cacgetu1 (CACHE *f); void cacputu1 (unsigned int u, CACHE *f); unsigned int cacgetu2 (CACHE *f); void cacputu2 (unsigned int i, CACHE *f); unsigned long cacgetu4 (CACHE *f); void cacputu4 (unsigned long i, CACHE *f); int cacgete1 (CACHE *f, const wchar_t *type); void cacpute1 (int value, CACHE *f); int cacgete2 (CACHE *f, const wchar_t *type); void cacpute2 (int value, CACHE *f); #define cacgeteb cacgeti1 #define cacgeteq cacgeti1 #define cacgetex cacgeti1 #define cacputeb cacputi1 #define cacputeq cacputi1 #define cacputex cacputi1 int cacgeti1 (CACHE *f); void cacputi1 (int i, CACHE *f); int cacgeti2 (CACHE *f); void cacputi2 (int i, CACHE *f); long cacgeti4 (CACHE *f); void cacputi4 (long i, CACHE *f); int cacgeti2LE (CACHE *f); void cacputi2LE (int i, CACHE *f); double cacgetr4 (CACHE *f); void cacputr4 (double x, CACHE *f); double cacgetr8 (CACHE *f); void cacputr8 (double x, CACHE *f); double cacgetr10 (CACHE *f); void cacputr10 (double x, CACHE *f); fcomplex cacgetc8 (CACHE *f); dcomplex cacgetc16 (CACHE *f); void cacputc8 (fcomplex z, CACHE *f); void cacputc16 (dcomplex z, CACHE *f); long cacgeti4LE (CACHE *f); void cacputi4LE (long i, CACHE *f); unsigned int cacgetu2LE (CACHE *f); void cacputu2LE (unsigned int i, CACHE *f); unsigned long cacgetu4LE (CACHE *f); void cacputu4LE (unsigned long i, CACHE *f); char * cacgets1 (CACHE *f); void cacputs1 (const char *s, CACHE *f); char * cacgets2 (CACHE *f); void cacputs2 (const char *s, CACHE *f); char * cacgets4 (CACHE *f); void cacputs4 (const char *s, CACHE *f); /* End of file abcio.h */ #endif sources_5316/sys/melder_writetext.cpp0000644000176700017670000004430411604544564016652 0ustar paulpaul/* melder_writetext.cpp * * Copyright (C) 2007-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/06/02 utf8 <-> wcs * pb 2007/06/14 separated from melder_strings.c and melder_alloc.c * pb 2007/06/16 text encoding preferences * pb 2007/08/12 prefs in wchar_t * pb 2007/09/04 Melder_malloc rather than malloc in Melder_wcsToAscii (had caused an error in counting memory leaks) * pb 2007/10/06 Melder_peekWcsToCfstring * pb 2007/12/09 made MelderFile_writeCharacter compatible with the ISO Latin-1 preference * pb 2007/12/09 made MelderFile_readText ignore null bytes * pb 2008/11/05 split off from melder_encodings.c * pb 2010/03/09 support Unicode values above 0xFFFF * pb 2011/04/05 C++ */ #include "melder.h" #include "Preferences.h" #include "UnicodeData.h" #include "abcio.h" #if defined (macintosh) #include "macport_on.h" //#include #include "macport_off.h" #endif static void Melder_fwriteUnicodeAsUtf8 (unsigned long unicode, FILE *f) { if (unicode <= 0x00007F) { #ifdef _WIN32 if (unicode == '\n') fputc (13, f); #endif fputc (unicode, f); } else if (unicode <= 0x0007FF) { fputc (0xC0 | (unicode >> 6), f); fputc (0x80 | (unicode & 0x00003F), f); } else if (unicode <= 0x00FFFF) { fputc (0xE0 | (unicode >> 12), f); fputc (0x80 | ((unicode >> 6) & 0x00003F), f); fputc (0x80 | (unicode & 0x00003F), f); } else { fputc (0xF0 | (unicode >> 18), f); fputc (0x80 | ((unicode >> 12) & 0x00003F), f); fputc (0x80 | ((unicode >> 6) & 0x00003F), f); fputc (0x80 | (unicode & 0x00003F), f); } } void Melder_fwriteWcsAsUtf8 (const wchar *ptr, size_t n, FILE *f) { /* * Precondition: * the string's encoding is either UTF-32 or UTF-16. * Failure: * if the precondition does not hold, we don't crash, * but the characters that are written may be incorrect. */ for (size_t i = 0; i < n; i ++) { if (sizeof (wchar_t) == 4) { /* * We are likely to be on Macintosh or Linux. * We assume that the string's encoding is UTF-32. */ Melder_fwriteUnicodeAsUtf8 (ptr [i], f); } else if (sizeof (wchar_t) == 2) { /* * We are likely to be on Windows. * We assume that the string's encoding is UTF-16; * if it turns out to be otherwise, we write question marks. */ unsigned long kar1 = (unsigned short) ptr [i]; // potential intermediate conversion from signed short to unsigned short if (kar1 < 0xD800) { Melder_fwriteUnicodeAsUtf8 (kar1, f); // a character from the Basic Multilingual Plane } else if (kar1 < 0xDC00) { /* * We detected a surrogate code point * and will therefore translate two UTF-16 words into one Unicode supplementary character. */ unsigned long kar2 = ptr [++ i]; if (kar2 == 0) { // string exhausted? // Melder_fatal ("Detected a bare (final) high surrogate in UTF-16."); Melder_fwriteUnicodeAsUtf8 (UNICODE_REPLACEMENT_CHARACTER, f); return; } if (kar2 >= 0xDC00 && kar2 <= 0xDFFF) { Melder_fwriteUnicodeAsUtf8 (0x10000 + ((kar1 - 0xD800) << 10) + (kar2 - 0xDC00), f); } else { // Melder_fatal ("Detected a bare high surrogate in UTF-16."); Melder_fwriteUnicodeAsUtf8 (UNICODE_REPLACEMENT_CHARACTER, f); i --; // try to interpret the next character in the normal way } } else if (kar1 < 0xE000) { // Melder_fatal ("Detected a bare low surrogate in UTF-16."); Melder_fwriteUnicodeAsUtf8 (UNICODE_REPLACEMENT_CHARACTER, f); } else if (kar1 <= 0xFFFF) { Melder_fwriteUnicodeAsUtf8 (kar1, f); // a character from the Basic Multilingual Plane } else { Melder_fatal ("Melder_fwriteWcsAsUtf8: unsigned short greater than 0xFFFF: should not occur."); } } else { Melder_fatal ("Melder_fwriteWcsAsUtf8: unsupported size of wide character."); } } } void MelderFile_writeText (MelderFile file, const wchar *text) { autofile f = Melder_fopen (file, "wb"); int outputEncoding = Melder_getOutputEncoding (); if (outputEncoding == kMelder_textOutputEncoding_UTF8) { Melder_fwriteWcsAsUtf8 (text, wcslen (text), f); } else if ((outputEncoding == kMelder_textOutputEncoding_ASCII_THEN_UTF16 && Melder_isValidAscii (text)) || (outputEncoding == kMelder_textOutputEncoding_ISO_LATIN1_THEN_UTF16 && Melder_isEncodable (text, kMelder_textOutputEncoding_ISO_LATIN1))) { #ifdef _WIN32 #define flockfile(f) (void) 0 #define funlockfile(f) (void) 0 #define putc_unlocked putc #endif flockfile (f); size_t n = wcslen (text); for (size_t i = 0; i < n; i ++) { unsigned long kar = sizeof (wchar_t) == 2 ? (unsigned short) text [i] : text [i]; #ifdef _WIN32 if (kar == '\n') putc_unlocked (13, f); #endif putc_unlocked (kar, f); } funlockfile (f); } else { binputu2 (0xFEFF, f); // Byte Order Mark long n = wcslen (text); for (long i = 0; i < n; i ++) { if (sizeof (wchar_t) == 2) { // wchar_t is UTF-16? unsigned short kar = text [i]; #ifdef _WIN32 if (kar == '\n') binputu2 (13, f); #endif binputu2 (kar, f); } else { // wchar_t is UTF-32. unsigned long kar = text [i]; #ifdef _WIN32 if (kar == '\n') binputu2 (13, f); #endif if (kar <= 0xFFFF) { binputu2 (kar, f); } else if (kar <= 0x10FFFF) { kar -= 0x10000; binputu2 (0xD800 | (kar >> 10), f); binputu2 (0xDC00 | (kar & 0x3ff), f); } else { binputu2 (UNICODE_REPLACEMENT_CHARACTER, f); } } } } f.close (file); MelderFile_setMacTypeAndCreator (file, 'TEXT', 0); } void MelderFile_appendText (MelderFile file, const wchar *text) { autofile f; try { f.reset (Melder_fopen (file, "rb")); } catch (MelderError) { Melder_clearError (); // it's OK if the file didn't exist yet... MelderFile_writeText (file, text); // because then we just "write" return; } /* * The file already exists and is open. Determine its type. */ int firstByte = fgetc (f), secondByte = fgetc (f); f.close (file); int type = 0; if (firstByte == 0xfe && secondByte == 0xff) { type = 1; // big-endian 16-bit } else if (firstByte == 0xff && secondByte == 0xfe) { type = 2; // little-endian 16-bit } if (type == 0) { int outputEncoding = Melder_getOutputEncoding (); if (outputEncoding == kMelder_textOutputEncoding_UTF8) { // TODO: read as file's encoding autofile f = Melder_fopen (file, "ab"); Melder_fwriteWcsAsUtf8 (text, wcslen (text), f); f.close (file); } else if ((outputEncoding == kMelder_textOutputEncoding_ASCII_THEN_UTF16 && Melder_isEncodable (text, kMelder_textOutputEncoding_ASCII)) || (outputEncoding == kMelder_textOutputEncoding_ISO_LATIN1_THEN_UTF16 && Melder_isEncodable (text, kMelder_textOutputEncoding_ISO_LATIN1))) { /* * Append ASCII or ISOLatin1 text to ASCII or ISOLatin1 file. */ autofile f = Melder_fopen (file, "ab"); size_t n = wcslen (text); for (size_t i = 0; i < n; i ++) { unsigned long kar = sizeof (wchar_t) == 2 ? (unsigned short) text [i] : text [i]; #ifdef _WIN32 if (kar == '\n') fputc (13, f); #endif fputc (kar, f); } f.close (file); } else { /* * Convert to wide character file. */ autostring oldText = MelderFile_readText (file); autofile f = Melder_fopen (file, "wb"); binputu2 (0xfeff, f); unsigned long n = wcslen (oldText.peek()); for (unsigned long i = 0; i < n; i ++) { if (sizeof (wchar_t) == 2) { // wchar_t is UTF-16? wchar_t kar = oldText [i]; #ifdef _WIN32 if (kar == '\n') binputu2 (13, f); #endif binputu2 (kar, f); } else { // wchar_t is UTF-32. unsigned long kar = oldText [i]; #ifdef _WIN32 if (kar == '\n') binputu2 (13, f); #endif if (kar <= 0xFFFF) { binputu2 (kar, f); } else if (kar <= 0x10FFFF) { kar -= 0x10000; binputu2 (0xD800 | (kar >> 10), f); binputu2 (0xDC00 | (kar & 0x3ff), f); } else { binputu2 (UNICODE_REPLACEMENT_CHARACTER, f); } } } n = wcslen (text); for (unsigned long i = 0; i < n; i ++) { if (sizeof (wchar_t) == 2) { // wchar_t is UTF-16? unsigned short kar = text [i]; #ifdef _WIN32 if (kar == '\n') binputu2 (13, f); #endif binputu2 (kar, f); } else { // wchar_t is UTF-32. unsigned long kar = text [i]; #ifdef _WIN32 if (kar == '\n') binputu2 (13, f); #endif if (kar <= 0xFFFF) { binputu2 (kar, f); } else if (kar <= 0x10FFFF) { kar -= 0x10000; binputu2 (0xD800 | (kar >> 10), f); binputu2 (0xDC00 | (kar & 0x3ff), f); } else { binputu2 (UNICODE_REPLACEMENT_CHARACTER, f); } } } f.close (file); } } else { autofile f = Melder_fopen (file, "ab"); unsigned long n = wcslen (text); for (unsigned long i = 0; i < n; i ++) { if (type == 1) { if (sizeof (wchar) == 2) { // wchar is UTF-16? unsigned short kar = text [i]; #ifdef _WIN32 if (kar == '\n') binputu2 (13, f); #endif binputu2 (kar, f); } else { // wchar is UTF-32 unsigned long kar = text [i]; #ifdef _WIN32 if (kar == '\n') binputu2 (13, f); #endif if (kar <= 0xFFFF) { binputu2 (kar, f); } else if (kar <= 0x10FFFF) { kar -= 0x10000; binputu2 (0xD800 | (kar >> 10), f); binputu2 (0xDC00 | (kar & 0x3ff), f); } else { binputu2 (UNICODE_REPLACEMENT_CHARACTER, f); } } } else { if (sizeof (wchar) == 2) { // wchar is UTF-16? unsigned short kar = text [i]; #ifdef _WIN32 if (kar == '\n') binputu2LE (13, f); #endif binputu2LE (kar, f); } else { // wchar is UTF-32 unsigned long kar = text [i]; #ifdef _WIN32 if (kar == '\n') binputu2LE (13, f); #endif if (kar <= 0xFFFF) { binputu2LE (kar, f); } else if (kar <= 0x10FFFF) { kar -= 0x10000; binputu2LE (0xD800 | (kar >> 10), f); binputu2LE (0xDC00 | (kar & 0x3ff), f); } else { binputu2LE (UNICODE_REPLACEMENT_CHARACTER, f); } } } } f.close (file); } MelderFile_setMacTypeAndCreator (file, 'TEXT', 0); } static void _MelderFile_write (MelderFile file, const wchar_t *string) { if (string == NULL) return; unsigned long length = wcslen (string); FILE *f = file -> filePointer; if (file -> outputEncoding == kMelder_textOutputEncoding_ASCII || file -> outputEncoding == kMelder_textOutputEncoding_ISO_LATIN1) { for (unsigned long i = 0; i < length; i ++) { char kar = string [i]; if (kar == '\n' && file -> requiresCRLF) putc (13, f); putc (kar, f); } } else if (file -> outputEncoding == kMelder_textOutputEncoding_UTF8) { for (unsigned long i = 0; i < length; i ++) { unsigned long kar = sizeof (wchar_t) == 2 ? (unsigned short) string [i] : string [i]; if (kar <= 0x00007F) { if (kar == '\n' && file -> requiresCRLF) putc (13, f); putc (kar, f); } else if (kar <= 0x0007FF) { putc (0xC0 | (kar >> 6), f); putc (0x80 | (kar & 0x00003F), f); } else if (kar <= 0x00FFFF) { if (sizeof (wchar_t) == 2) { if ((kar & 0xF800) == 0xD800) { if (kar > 0xDBFF) Melder_fatal ("Incorrect Unicode value (first surrogate member %lX).", kar); unsigned long kar2 = (unsigned short) string [++ i]; // crucial cast: prevents sign extension if (kar2 < 0xDC00 || kar2 > 0xDFFF) Melder_fatal ("Incorrect Unicode value (second surrogate member %lX).", kar2); kar = (((kar & 0x3FF) << 10) | (kar2 & 0x3FF)) + 0x10000; // decode UTF-16 putc (0xF0 | (kar >> 18), f); putc (0x80 | ((kar >> 12) & 0x00003F), f); putc (0x80 | ((kar >> 6) & 0x00003F), f); putc (0x80 | (kar & 0x00003F), f); } else { putc (0xE0 | (kar >> 12), f); putc (0x80 | ((kar >> 6) & 0x00003F), f); putc (0x80 | (kar & 0x00003F), f); } } else { putc (0xE0 | (kar >> 12), f); putc (0x80 | ((kar >> 6) & 0x00003F), f); putc (0x80 | (kar & 0x00003F), f); } } else { putc (0xF0 | (kar >> 18), f); putc (0x80 | ((kar >> 12) & 0x00003F), f); putc (0x80 | ((kar >> 6) & 0x00003F), f); putc (0x80 | (kar & 0x00003F), f); } } } else { for (unsigned long i = 0; i < length; i ++) { unsigned long kar = sizeof (wchar_t) == 2 ? (unsigned short) string [i] : string [i]; if (kar == '\n' && file -> requiresCRLF) binputu2 (13, f); if (sizeof (wchar_t) == 2) { // wchar_t is UTF-16? binputu2 (kar, f); } else { // wchar_t is UTF-32. if (kar <= 0xFFFF) { binputu2 (kar, f); } else if (kar <= 0x10FFFF) { kar -= 0x10000; binputu2 (0xD800 | (kar >> 10), f); binputu2 (0xDC00 | (kar & 0x3ff), f); } else { binputu2 (UNICODE_REPLACEMENT_CHARACTER, f); } } } } } void MelderFile_writeCharacter (MelderFile file, wchar_t character) { FILE *f = file -> filePointer; unsigned long kar = sizeof (wchar_t) == 2 ? (unsigned short) character : character; if (file -> outputEncoding == kMelder_textOutputEncoding_ASCII || file -> outputEncoding == kMelder_textOutputEncoding_ISO_LATIN1) { if (kar == '\n' && file -> requiresCRLF) putc (13, f); putc (kar, f); } else if (file -> outputEncoding == kMelder_textOutputEncoding_UTF8) { if (kar <= 0x00007F) { if (kar == '\n' && file -> requiresCRLF) putc (13, f); putc (kar, f); } else if (kar <= 0x0007FF) { putc (0xC0 | (kar >> 6), f); putc (0x80 | (kar & 0x00003F), f); } else if (kar <= 0x00FFFF) { if (sizeof (wchar_t) == 2) { if ((kar & 0xF800) == 0xD800) { static unsigned long buffer; // NOT REENTRANT if (kar >= 0xD800 && kar <= 0xDBFF) { buffer = kar; } else { kar = (((buffer & 0x3FF) << 10) | (kar & 0x3FF)) + 0x10000; // decode UTF-16 putc (0xF0 | (kar >> 18), f); putc (0x80 | ((kar >> 12) & 0x00003F), f); putc (0x80 | ((kar >> 6) & 0x00003F), f); putc (0x80 | (kar & 0x00003F), f); } } else { putc (0xE0 | (kar >> 12), f); putc (0x80 | ((kar >> 6) & 0x00003F), f); putc (0x80 | (kar & 0x00003F), f); } } else { putc (0xE0 | (kar >> 12), f); putc (0x80 | ((kar >> 6) & 0x00003F), f); putc (0x80 | (kar & 0x00003F), f); } } else { putc (0xF0 | (kar >> 18), f); putc (0x80 | ((kar >> 12) & 0x00003F), f); putc (0x80 | ((kar >> 6) & 0x00003F), f); putc (0x80 | (kar & 0x00003F), f); } } else { if (kar == '\n' && file -> requiresCRLF) binputu2 (13, f); if (sizeof (wchar_t) == 2) { // wchar_t is UTF-16? binputu2 (kar, f); } else { // wchar_t is UTF-32. if (kar <= 0xFFFF) { binputu2 (kar, f); } else if (kar <= 0x10FFFF) { kar -= 0x10000; binputu2 (0xD800 | (kar >> 10), f); binputu2 (0xDC00 | (kar & 0x3ff), f); } else { binputu2 (UNICODE_REPLACEMENT_CHARACTER, f); } } } } void MelderFile_write1 (MelderFile file, const wchar_t *s1) { if (file -> filePointer == NULL) return; _MelderFile_write (file, s1); } void MelderFile_write2 (MelderFile file, const wchar_t *s1, const wchar_t *s2) { if (file -> filePointer == NULL) return; _MelderFile_write (file, s1); _MelderFile_write (file, s2); } void MelderFile_write3 (MelderFile file, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3) { if (file -> filePointer == NULL) return; _MelderFile_write (file, s1); _MelderFile_write (file, s2); _MelderFile_write (file, s3); } void MelderFile_write4 (MelderFile file, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4) { if (file -> filePointer == NULL) return; _MelderFile_write (file, s1); _MelderFile_write (file, s2); _MelderFile_write (file, s3); _MelderFile_write (file, s4); } void MelderFile_write5 (MelderFile file, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5) { if (file -> filePointer == NULL) return; _MelderFile_write (file, s1); _MelderFile_write (file, s2); _MelderFile_write (file, s3); _MelderFile_write (file, s4); _MelderFile_write (file, s5); } void MelderFile_write6 (MelderFile file, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { if (file -> filePointer == NULL) return; _MelderFile_write (file, s1); _MelderFile_write (file, s2); _MelderFile_write (file, s3); _MelderFile_write (file, s4); _MelderFile_write (file, s5); _MelderFile_write (file, s6); } void MelderFile_write7 (MelderFile file, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7) { if (file -> filePointer == NULL) return; _MelderFile_write (file, s1); _MelderFile_write (file, s2); _MelderFile_write (file, s3); _MelderFile_write (file, s4); _MelderFile_write (file, s5); _MelderFile_write (file, s6); _MelderFile_write (file, s7); } void MelderFile_write8 (MelderFile file, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8) { if (file -> filePointer == NULL) return; _MelderFile_write (file, s1); _MelderFile_write (file, s2); _MelderFile_write (file, s3); _MelderFile_write (file, s4); _MelderFile_write (file, s5); _MelderFile_write (file, s6); _MelderFile_write (file, s7); _MelderFile_write (file, s8); } void MelderFile_write9 (MelderFile file, const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8, const wchar_t *s9) { if (file -> filePointer == NULL) return; _MelderFile_write (file, s1); _MelderFile_write (file, s2); _MelderFile_write (file, s3); _MelderFile_write (file, s4); _MelderFile_write (file, s5); _MelderFile_write (file, s6); _MelderFile_write (file, s7); _MelderFile_write (file, s8); _MelderFile_write (file, s9); } /* End of file melder_writetext.cpp */ sources_5316/sys/ManPage_enums.h0000644000176700017670000000427511160271650015440 0ustar paulpaul/* ManPage_enums.h * * Copyright (C) 1996-2009 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2009/03/18 */ enums_begin (kManPage_type, 1) enums_add (kManPage_type, 1, INTRO, L"intro") enums_add (kManPage_type, 2, ENTRY, L"entry") enums_add (kManPage_type, 3, NORMAL, L"normal") enums_add (kManPage_type, 4, LIST_ITEM, L"list_item") enums_add (kManPage_type, 5, TAG, L"tag") enums_add (kManPage_type, 6, DEFINITION, L"definition") enums_add (kManPage_type, 7, CODE, L"code") enums_add (kManPage_type, 8, PROTOTYPE, L"prototype") enums_add (kManPage_type, 9, FORMULA, L"formula") enums_add (kManPage_type, 10, PICTURE, L"picture") enums_add (kManPage_type, 11, SCRIPT, L"script") enums_add (kManPage_type, 12, LIST_ITEM1, L"list_item1") enums_add (kManPage_type, 13, LIST_ITEM2, L"list_item2") enums_add (kManPage_type, 14, LIST_ITEM3, L"list_item3") enums_add (kManPage_type, 15, TAG1, L"tag1") enums_add (kManPage_type, 16, TAG2, L"tag2") enums_add (kManPage_type, 17, TAG3, L"tag3") enums_add (kManPage_type, 18, DEFINITION1, L"definition1") enums_add (kManPage_type, 19, DEFINITION2, L"definition2") enums_add (kManPage_type, 20, DEFINITION3, L"definition3") enums_add (kManPage_type, 21, CODE1, L"code1") enums_add (kManPage_type, 22, CODE2, L"code2") enums_add (kManPage_type, 23, CODE3, L"code3") enums_add (kManPage_type, 24, CODE4, L"code4") enums_add (kManPage_type, 25, CODE5, L"code5") enums_add (kManPage_type, 26, PAGE_TITLE, L"page_title") enums_end (kManPage_type, 26, NORMAL) /* End of file ManPage_enums.h */ sources_5316/sys/Collection.cpp0000644000176700017670000004504011724661150015346 0ustar paulpaul/* Collection.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection.h" /********** class Collection **********/ void structCollection :: v_destroy () { if (item != NULL) { if (! _dontOwnItems) { for (long i = 1; i <= size; i ++) { forget (((Thing *) item) [i]); } } item ++; // base 1 Melder_free (item); } Collection_Parent :: v_destroy (); } void structCollection :: v_info () { MelderInfo_writeLine2 (Melder_integer (size), L" items"); } void structCollection :: v_copy (thou) { thouart (Collection); thy item = NULL; // kill shallow copy of item // BUG Collection_Parent :: v_copy (thee); therror thy itemClass = itemClass; thy _capacity = _capacity; thy size = size; thy item = Melder_calloc (void *, _capacity); // filled with NULL thy item --; // immediately turn from base-0 into base-1 // BUG use NUMvector for (long i = 1; i <= size; i ++) { Thing itempie = (Thing) item [i]; if (_dontOwnItems) { thy item [i] = itempie; // reference copy: if me doesn't own the items, then thee shouldn't either // NOTE: the items don't have to be Data } else { if (! Thing_member (itempie, classData)) Melder_throw ("Cannot copy item of class ", Thing_className (itempie), "."); thy item [i] = Data_copy ((Data) itempie); } } } bool structCollection :: v_equal (thou) { thouart (Collection); if (! Collection_Parent :: v_equal (thee)) return false; if (size != thy size) return false; for (long i = 1; i <= size; i ++) { if (! Thing_member ((Thing) item [i], classData)) Melder_throw ("Collection::equal: " "cannot compare items of class ", Thing_className ((Thing) item [i]), "."); if (! Thing_member ((Thing) thy item [i], classData)) Melder_throw ("Collection::equal: " "cannot compare items of class ", Thing_className ((Thing) thy item [i]), "."); bool equal = Data_equal ((Data) item [i], (Data) thy item [i]); //Melder_casual ("classCollection_equal: %d, items %ld, types %ls and %ls", // equal, i, Thing_className (my item [i]), Thing_className (thy item [i])); if (! equal) return false; } return true; } bool structCollection :: v_canWriteAsEncoding (int encoding) { for (long i = 1; i <= size; i ++) { Data data = (Data) item [i]; if (data -> name != NULL && ! Melder_isEncodable (data -> name, encoding)) return false; if (! Data_canWriteAsEncoding (data, encoding)) return false; } return true; } void structCollection :: v_writeText (MelderFile file) { texputi4 (file, size, L"size", 0,0,0,0,0); texputintro (file, L"item []: ", size ? NULL : L"(empty)", 0,0,0,0); for (long i = 1; i <= size; i ++) { Thing thing = (Thing) item [i]; ClassInfo classInfo = thing -> classInfo; texputintro (file, L"item [", Melder_integer (i), L"]:", 0,0,0); if (! Thing_member (thing, classData) || ! Data_canWriteText ((Data) thing)) Melder_throw ("Objects of class ", classInfo -> className, " cannot be written."); texputw2 (file, classInfo -> version > 0 ? Melder_wcscat (classInfo -> className, L" ", Melder_integer (classInfo -> version)) : classInfo -> className, L"class", 0,0,0,0,0); texputw2 (file, thing -> name, L"name", 0,0,0,0,0); Data_writeText ((Data) thing, file); texexdent (file); } texexdent (file); } void structCollection :: v_readText (MelderReadText text) { if (Thing_version < 0) { long l_size; wchar_t *line = MelderReadText_readLine (text); if (line == NULL || ! swscanf (line, L"%ld", & l_size) || l_size < 0) Melder_throw ("Collection::readText: cannot read size."); Collection_init (this, NULL, l_size); for (long i = 1; i <= l_size; i ++) { long itemNumberRead; int n = 0, length, stringsRead; char klas [200], nameTag [2000]; do { line = MelderReadText_readLine (text); if (line == NULL) Melder_throw ("Missing object line."); } while (wcsncmp (line, L"Object ", 7)); stringsRead = swscanf (line, L"Object %ld: class %s %s%n", & itemNumberRead, klas, nameTag, & n); if (stringsRead < 2) Melder_throw ("Collection::readText: cannot read header of object ", i, "."); if (itemNumberRead != i) Melder_throw ("Collection::readText: read item number ", itemNumberRead, " while expecting ", i, "."); if (stringsRead == 3 && ! strequ (nameTag, "name")) Melder_throw ("Collection::readText: wrong header at object ", i, "."); this -> item [i] = Thing_newFromClassNameA (klas); therror Thing_version = -1; /* Override. */ this -> size ++; if (! Thing_member ((Thing) item [i], classData) || ! Data_canReadText ((Data) item [i])) Melder_throw ("Cannot read item of class ", Thing_className ((Thing) item [i]), " in collection."); Data_readText ((Data) item [i], text); therror if (stringsRead == 3) { if (line [n] == ' ') n ++; // skip space character length = wcslen (line+n); if (length > 0 && (line+n) [length - 1] == '\n') (line+n) [length - 1] = '\0'; Thing_setName ((Thing) item [i], line+n); } } } else { long l_size = texgeti4 (text); Collection_init (this, NULL, l_size); for (long i = 1; i <= l_size; i ++) { long saveVersion = Thing_version; /* The version of the Collection... */ autostring8 className = texgets2 (text); this -> item [i] = Thing_newFromClassNameA (className.peek()); therror this -> size ++; if (! Thing_member ((Thing) item [i], classData) || ! Data_canReadText ((Data) item [i])) Melder_throw ("Cannot read item of class ", Thing_className ((Thing) item [i]), " in collection."); autostring objectName = texgetw2 (text); Thing_setName ((Thing) item [i], objectName.peek()); therror Data_readText ((Data) item [i], text); therror Thing_version = saveVersion; } } } void structCollection :: v_writeBinary (FILE *f) { binputi4 (size, f); for (long i = 1; i <= size; i ++) { Thing thing = (Thing) item [i]; ClassInfo classInfo = thing -> classInfo; if (! Thing_member (thing, classData) || ! Data_canWriteBinary ((Data) thing)) Melder_throw ("Objects of class ", classInfo -> className, L" cannot be written."); binputw1 (classInfo -> version > 0 ? Melder_wcscat (classInfo -> className, L" ", Melder_integer (classInfo -> version)) : classInfo -> className, f); binputw2 (thing -> name, f); Data_writeBinary ((Data) thing, f); } } void structCollection :: v_readBinary (FILE *f) { if (Thing_version < 0) { long l_size = bingeti4 (f); therror if (l_size < 0) Melder_throw ("Empty collection."); Collection_init (this, NULL, l_size); therror for (long i = 1; i <= l_size; i ++) { char klas [200], name [2000]; if (fscanf (f, "%s%s", klas, name) < 2) Melder_throw ("Cannot read class and name."); item [i] = Thing_newFromClassNameA (klas); therror Thing_version = -1; /* Override. */ this -> size ++; if (! Thing_member ((Thing) item [i], classData)) Melder_throw ("Cannot read item of class ", Thing_className ((Thing) item [i]), "."); if (fgetc (f) != ' ') Melder_throw ("Cannot read space."); Data_readBinary ((Data) item [i], f); therror if (strcmp (name, "?")) Thing_setName ((Thing) item [i], Melder_peekUtf8ToWcs (name)); } } else { long l_size = bingeti4 (f); therror Collection_init (this, NULL, l_size); therror for (long i = 1; i <= l_size; i ++) { long saveVersion = Thing_version; // the version of the Collection... autostring8 klas = bingets1 (f); item [i] = Thing_newFromClassNameA (klas.peek()); therror this -> size ++; if (! Thing_member ((Thing) item [i], classData) || ! Data_canReadBinary ((Data) item [i])) Melder_throw ("Objects of class ", Thing_className ((Thing) item [i]), " cannot be read."); autostring name = bingetw2 (f); Thing_setName ((Thing) item [i], name.peek()); therror Data_readBinary ((Data) item [i], f); therror Thing_version = saveVersion; } } } static struct structData_Description theCollection_description [] = { { L"size", longwa, Melder_offsetof (Collection, size), sizeof (long) }, { L"item", objectwa, Melder_offsetof (Collection, item), sizeof (Data), L"Data", & theClassInfo_Data, 1, 0, L"size" }, { 0 } }; Data_Description structCollection :: s_description = & theCollection_description [0]; Thing_implement (Collection, Data, 0); void Collection_init (Collection me, ClassInfo itemClass_, long initialCapacity) { my itemClass = itemClass_; my _capacity = initialCapacity >= 1 ? initialCapacity : 1; my size = 0; my item = Melder_calloc (void *, my _capacity); my item --; // base 1 } Collection Collection_create (ClassInfo itemClass, long initialCapacity) { autoCollection me = Thing_new (Collection); Collection_init (me.peek(), itemClass, initialCapacity); return me.transfer(); } void Collection_dontOwnItems (Collection me) { Melder_assert (my size == 0); my _dontOwnItems = true; } void _Collection_insertItem (Collection me, Thing data, long pos) { if (my size >= my _capacity) { /* * Check without change. */ Any *dum = (Any *) Melder_realloc (my item + 1, 2 * my _capacity * sizeof (Any)); /* * From here: change without error. */ my item = dum - 1; my _capacity *= 2; } my size ++; for (long i = my size; i > pos; i --) my item [i] = my item [i - 1]; my item [pos] = data; } void Collection_addItem (Collection me, Thing data) { try { Melder_assert (data != NULL); long index = my v_position (data); if (index != 0) { _Collection_insertItem (me, data, index); } else { if (! my _dontOwnItems) forget (data); // could not insert; I am the owner, so I must dispose of the data } } catch (MelderError) { Melder_throw (me, ": item not added."); } } void Collection_removeItem (Collection me, long pos) { Melder_assert (pos >= 1 && pos <= my size); if (! my _dontOwnItems) forget (((Thing *) my item) [pos]); for (long i = pos; i < my size; i ++) my item [i] = my item [i + 1]; my size --; } void Collection_undangleItem (Collection me, Thing item) { for (long i = my size; i > 0; i --) if (my item [i] == item) { for (long j = i; j < my size; j ++) my item [j] = my item [j + 1]; my size --; } } Any Collection_subtractItem (Collection me, long pos) { Melder_assert (pos >= 1 && pos <= my size); Any result = my item [pos]; for (long i = pos; i < my size; i ++) my item [i] = my item [i + 1]; my size --; return result; } void Collection_removeAllItems (Collection me) { if (! my _dontOwnItems) for (long i = 1; i <= my size; i ++) forget (((Thing *) my item) [i]); my size = 0; } void Collection_shrinkToFit (Collection me) { my _capacity = my size ? my size : 1; my item = (Any *) Melder_realloc (my item + 1, my _capacity * sizeof (Any)) - 1; } Any Collections_merge (Collection me, Collection thee) { try { if (my classInfo != thy classInfo) Melder_throw ("Objects are of different class."); if (my _dontOwnItems != thy _dontOwnItems) Melder_throw ("Cannot mix data and references."); autoCollection him = Data_copy (me); for (long i = 1; i <= thy size; i ++) { Thing item = (Thing) thy item [i]; if (my _dontOwnItems) { Collection_addItem (him.peek(), item); } else { if (! Thing_member (item, classData)) Melder_throw ("Cannot copy item of class ", Thing_className (item), "."); Collection_addItem (him.peek(), Data_copy ((Data) item)); } } return him.transfer(); } catch (MelderError) { Melder_throw (me, " and ", thee, " not merged." ); } } /********** class Ordered **********/ Thing_implement (Ordered, Collection, 0); void Ordered_init (Ordered me, ClassInfo itemClass, long initialMaximumLength) { Collection_init (me, itemClass, initialMaximumLength); } Ordered Ordered_create (void) { autoOrdered me = Thing_new (Ordered); Ordered_init (me.peek(), NULL, 10); return me.transfer(); } void Ordered_addItemPos (Ordered me, Thing data, long position) { Melder_assert (data); if (position < 1 || position > my size) position = my size + 1; _Collection_insertItem (me, data, position); } /********** class Sorted **********/ Thing_implement (Sorted, Collection, 0); long structSorted :: v_position (Any data) { Data_CompareFunction compare = v_getCompareFunction (); if (size == 0 || compare (data, item [size]) >= 0) return size + 1; if (compare (data, item [1]) < 0) return 1; /* Binary search. */ long left = 1, right = size; while (left < right - 1) { long mid = (left + right) / 2; if (compare (data, item [mid]) >= 0) left = mid; else right = mid; } Melder_assert (right == left + 1); return right; } int structSorted :: s_compare (Any data1, Any data2) { (void) data1; (void) data2; return 0; // in the base class, all are equal } void Sorted_init (Sorted me, ClassInfo itemClass, long initialCapacity) { Collection_init (me, itemClass, initialCapacity); } void Sorted_addItem_unsorted (Sorted me, Thing data) { _Collection_insertItem (me, data, my size + 1); } void Sorted_sort (Sorted me) { NUMsort_p (my size, my item, (int (*) (const void *, const void *)) my v_getCompareFunction ()); } /********** class SortedSet **********/ long structSortedSet :: v_position (Any data) { Data_CompareFunction compare = v_getCompareFunction (); if (size == 0) return 1; // empty set? then 'data' is going to be the first item int where = compare (data, item [size]); // compare with last item if (where > 0) return size + 1; // insert at end if (where == 0) return 0; if (compare (data, item [1]) < 0) return 1; // compare with first item long left = 1, right =size; while (left < right - 1) { long mid = (left + right) / 2; if (compare (data, item [mid]) >= 0) left = mid; else right = mid; } Melder_assert (right == left + 1); if (! compare (data, item [left]) || ! compare (data, item [right])) return 0; return right; } Thing_implement (SortedSet, Sorted, 0); void SortedSet_init (SortedSet me, ClassInfo itemClass, long initialCapacity) { Sorted_init (me, itemClass, initialCapacity); } /********** class SortedSetOfInt **********/ Thing_implement (SortedSetOfInt, SortedSet, 0); int structSortedSetOfInt :: s_compare (I, thou) { iam (SimpleInt); thouart (SimpleInt); if (my number < thy number) return -1; if (my number > thy number) return +1; return 0; } void SortedSetOfInt_init (SortedSetOfInt me) { SortedSet_init (me, classSimpleInt, 10); } SortedSetOfInt SortedSetOfInt_create (void) { autoSortedSetOfInt me = Thing_new (SortedSetOfInt); SortedSetOfInt_init (me.peek()); return me.transfer(); } /********** class SortedSetOfLong **********/ Thing_implement (SortedSetOfLong, SortedSet, 0); int structSortedSetOfLong :: s_compare (I, thou) { iam (SimpleLong); thouart (SimpleLong); if (my number < thy number) return -1; if (my number > thy number) return +1; return 0; } void SortedSetOfLong_init (SortedSetOfLong me) { SortedSet_init (me, classSimpleLong, 10); } SortedSetOfLong SortedSetOfLong_create (void) { autoSortedSetOfLong me = Thing_new (SortedSetOfLong); SortedSetOfLong_init (me.peek()); return me.transfer(); } /********** class SortedSetOfDouble **********/ int structSortedSetOfDouble :: s_compare (I, thou) { iam (SimpleDouble); thouart (SimpleDouble); if (my number < thy number) return -1; if (my number > thy number) return +1; return 0; } Thing_implement (SortedSetOfDouble, SortedSet, 0); void SortedSetOfDouble_init (SortedSetOfDouble me) { SortedSet_init (me, classSimpleDouble, 10); } SortedSetOfDouble SortedSetOfDouble_create (void) { autoSortedSetOfDouble me = Thing_new (SortedSetOfDouble); SortedSetOfDouble_init (me.peek()); return me.transfer(); } /********** class SortedSetOfString **********/ Thing_implement (SortedSetOfString, SortedSet, 0); int structSortedSetOfString :: s_compare (I, thou) { iam (SimpleString); thouart (SimpleString); return wcscmp (my string, thy string); } void SortedSetOfString_init (SortedSetOfString me) { SortedSet_init (me, classSimpleString, 10); } SortedSetOfString SortedSetOfString_create (void) { autoSortedSetOfString me = Thing_new (SortedSetOfString); SortedSetOfString_init (me.peek()); return me.transfer(); } long SortedSetOfString_lookUp (SortedSetOfString me, const wchar_t *string) { SimpleString *items = (SimpleString *) my item; long numberOfItems = my size; long left = 1, right = numberOfItems; int atStart, atEnd; if (numberOfItems == 0) return 0; atEnd = wcscmp (string, items [numberOfItems] -> string); if (atEnd > 0) return 0; if (atEnd == 0) return numberOfItems; atStart = wcscmp (string, items [1] -> string); if (atStart < 0) return 0; if (atStart == 0) return 1; while (left < right - 1) { long mid = (left + right) / 2; int here = wcscmp (string, items [mid] -> string); if (here == 0) return mid; if (here > 0) left = mid; else right = mid; } Melder_assert (right == left + 1); return 0; } void structSortedSetOfString :: addString (const wchar *string) { static SimpleString simp; if (simp == NULL) { simp = SimpleString_create (L""); Melder_free (simp -> string); } simp -> string = (wchar *) string; // reference copy long index = v_position (simp); if (index == 0) return; // OK: already there: do not add autoSimpleString newSimp = SimpleString_create (string); _Collection_insertItem (this, newSimp.transfer(), index); } /********** class Cyclic **********/ Thing_implement (Cyclic, Collection, 0); int structCyclic :: s_compare (I, thou) { (void) void_me; (void) void_thee; Melder_fatal ("Cyclic::compare: subclass responsibility."); return 0; } void structCyclic :: cycleLeft () { if (size == 0) return; // for size == 1 no motion will take place either, but in that case the algorithm determines that automatically Data help = (Data) item [1]; for (long i = 1; i < size; i ++) item [i] = item [i + 1]; item [size] = help; } void structCyclic :: unicize () { Data_CompareFunction compare = v_getCompareFunction (); if (size <= 1) return; long lowest = 1; for (long i = 1; i <= size; i ++) if (compare (item [i], item [lowest]) < 0) lowest = i; for (long i = 1; i < lowest; i ++) cycleLeft (); } void Cyclic_init (Cyclic me, ClassInfo itemClass, long initialCapacity) { Collection_init (me, itemClass, initialCapacity); } /* End of file Collection.cpp */ sources_5316/sys/Thing.h0000644000176700017670000002754511662505361014005 0ustar paulpaul#ifndef _Thing_h_ #define _Thing_h_ /* Thing.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* The root class of all objects. */ /* Anyone who uses Thing can also use: */ /* Arrays with any bounds and 1 or two indices, math, and numerics: */ #include "NUM.h" /* Including math.h */ /* The messaging mechanism: */ #include "melder.h" /* Including stdio.h string.h etc. */ /* The macros for struct and class definitions: */ #include "oo.h" /* The input/output mechanism: */ #include "abcio.h" /* Public. */ typedef void *Any; /* Prevent compile-time type checking. */ /* Use the macros 'I' and 'thou' for objects in the formal parameter lists (if the explicit type cannot be used). Use the macros 'iam' and 'thouart' as the first declaration in a function definition. After this, the object 'me' or 'thee' has the right class (for the compiler), so that you can use the macros 'my' and 'thy' to refer to members. Example: int Person_getAge (I) { iam (Person); return my age; } */ #define I Any void_me #define thou Any void_thee #define iam(klas) klas me = (klas) void_me #define thouart(klas) klas thee = (klas) void_thee #define my me -> #define thy thee -> #define his him -> typedef struct structClassInfo *ClassInfo; struct structClassInfo { const wchar *className; ClassInfo parent; long size; Thing (* _new) (); long version; long sequentialUniqueIdOfReadableClass; Thing dummyObject; }; #define Thing_declare(klas) \ typedef class struct##klas *klas; \ typedef _Thing_auto auto##klas; \ extern ClassInfo class##klas #define Thing_define(klas,parentKlas) \ Thing_declare (klas); \ typedef struct##parentKlas klas##_Parent; \ extern struct structClassInfo theClassInfo_##klas; \ class struct##klas : public struct##parentKlas #define Thing_implement(klas,parentKlas,version) \ static Thing _##klas##_new () { return (Thing) new struct##klas; } \ struct structClassInfo theClassInfo_##klas = { L"" #klas, & theClassInfo_##parentKlas, sizeof (class struct##klas), _##klas##_new, version, 0, NULL }; \ ClassInfo class##klas = & theClassInfo_##klas /* * Thing has no parent class, so instead of using the Thing_define macro * we write out the stuff that does exist. */ typedef class structThing *Thing; extern ClassInfo classThing; extern struct structClassInfo theClassInfo_Thing; class structThing { public: ClassInfo classInfo; wchar *name; void * operator new (size_t size) { return Melder_calloc (char, size); } void operator delete (void *ptr, size_t size) { (void) size; Melder_free (ptr); } // new methods: virtual void v_destroy () { Melder_free (name); }; /* * derived::v_destroy calls base::v_destroy at end */ virtual void v_info (); /* * Implement as follows: call a set of MelderInfo_writeXXX describing your data. * * Thing::v_info writes object id, object name, and date; * derived::v_info often calls base::v_info at start and then writes information on the new data, * but a few ancestors can be skipped if their data have new meanings. */ virtual void v_checkConstraints () { }; /* * derived::v_checkConstraints typically calls base::v_checkConstraints at start */ virtual void v_nameChanged () { }; /* * derived::v_nameChanged may call base::_nameChanged at start, middle or end */ }; #define forget(thing) do { _Thing_forget (thing); thing = NULL; } while (0) /* Function: free all memory associated with 'thing'. Postcondition: thing == NULL; */ #define forget_nozero(thing) do { _Thing_forget_nozero (thing); delete thing; } while (false) /* Function: free all memory associated with 'thing'. */ /* All functions with 'Thing me' as the first argument assume that it is not NULL. */ const wchar * Thing_className (Thing me); /* Return your class name. */ bool Thing_member (Thing me, ClassInfo klas); /* return true if you are a 'klas', i.e., if you are an object of the class 'klas' or of one of the classes derived from 'klas'. E.g., Thing_member (object, classThing) will always return true. */ bool Thing_subclass (ClassInfo klas, ClassInfo ancestor); /* return true if is a subclass of , i.e., if equals , or if the parent class of is a subclass of . E.g., Thing_subclass (classX, classThing) will always return true. */ void Thing_info (Thing me); void Thing_infoWithId (Thing me, unsigned long id); #define Thing_new(Klas) (Klas) _Thing_new (class##Klas) /* Function: return a new object of class 'klas'. Postconditions: result -> classInfo == class'klas'; other members are 0. */ Any _Thing_new (ClassInfo klas); /* Function: return a new object of class 'klas'. Postconditions: result -> classInfo == 'klas'; other members are 0. */ void Thing_recognizeClassesByName (ClassInfo readableClass, ...); /* Function: make Thing_classFromClassName () and Thing_newFromClassName () recognize a class from its name (a string). Arguments: as many classes as you want; finish with a NULL. It is not an error if a class occurs more than once in the list. Behaviour: calling this routine more than once, each time for different classes, has the same result as calling it once for all these classes together. Thing can remember up to 1000 string-readable classes. Usage: you should call this routine for all classes that you want to read by name, e.g., with Data_readFromTextFile () or Data_readFromBinaryFile (), or with Data_readText () or Data_readBinary () if the object is a Collection. Calls to this routine should preferably be put in the beginning of main (). */ void Thing_recognizeClassByOtherName (ClassInfo readableClass, const wchar *otherName); long Thing_listReadableClasses (void); Any Thing_newFromClassNameA (const char *className); Any Thing_newFromClassName (const wchar *className); /* Function: return a new object of class 'className', or NULL if the class name is not recognized. Postconditions: result -> classInfo == class'className'; other members are 0. Side effect: see Thing_classFromClassName. */ ClassInfo Thing_classFromClassName (const wchar_t *className); /* Function: Return the class info table of class 'className', or NULL if it is not recognized. E.g. the value returned from Thing_classFromClassName (L"PietjePuk") will be equal to classPietjePuk. Side effect: Sets the global variable Thing_version. If 'className' equals L"PietjePuk 300", the value returned will be classPietjePuk, and Thing_version will be set to 300. */ #define Thing_dummyObject(klas) \ (klas) _Thing_dummyObject (class##klas) Thing _Thing_dummyObject (ClassInfo classInfo); wchar * Thing_getName (Thing me); /* Return a pointer to your internal name (which can be NULL). */ wchar * Thing_messageName (Thing me); void Thing_setName (Thing me, const wchar_t *name); /* Function: remember that you are called 'name'. Postconditions: my name *and* my name are copies of 'name'. */ void Thing_swap (Thing me, Thing thee); /* Function: Swap my and thy contents. Precondition: my classInfo == thy classInfo; Postconditions: my xxx == thy old xxx; thy xxx == my old xxx; Usage: Swap two objects without changing any references to them. */ /* For the macros. */ void _Thing_forget (Thing me); void _Thing_forget_nozero (Thing me); void * _Thing_check (Thing me, ClassInfo table, const char *fileName, int line); /* Macros 'iam', 'thouart', 'heis'. */ /* For debugging. */ long Thing_getTotalNumberOfThings (void); /* This number is 0 initially, increments at every successful `new', and decrements at every `forget'. */ extern long Thing_version; /* Set by Thing_classFromClassName. */ template class _Thing_auto { T *d_ptr; public: /* * Things like * autoPitch pitch (Pitch_create (...)); * and * autoPitch pitch = Pitch_create (...); * should work. */ _Thing_auto (T *a_ptr) : d_ptr (a_ptr) { therror; // if this happens, the destructor won't be called, but that is not necessary anyway } _Thing_auto () : d_ptr (NULL) { } /* * pitch should be destroyed when going out of scope, * both at the end of the try block and when a throw occurs. */ ~_Thing_auto () { if (d_ptr) forget (d_ptr); } T* peek () const { return d_ptr; } /* * The expression * pitch.d_ptr -> xmin * should be abbreviatable by * pitch -> xmin */ T* operator-> () const { // as r-value return d_ptr; } T& operator* () const { // as l-value return *d_ptr; } /* * There are two ways to access the pointer; with and without transfer of ownership. * * Without transfer: * autoPitch pitch = Sound_to_Pitch (...); * Pitch_draw (pitch.peek()); * * With transfer: * return thee.transfer(); * and * *out_pitch = pitch.transfer(); * *out_pulses = pulses.transfer(); * and * Collection_addItem (me, pitch.transfer()); * and * praat_new (pitch.transfer(), my name); */ T* transfer () { T* temp = d_ptr; d_ptr = NULL; // make the pointer non-automatic again return temp; } //operator T* () { return d_ptr; } // this way only if peek() and transfer() are the same, e.g. in case of reference counting // template Y* operator= (_Thing_auto& a) { } /* * An autoThing can be cloned. This can be used for giving ownership without losing ownership. */ T* clone () const { return static_cast (Data_copy (d_ptr)); } /* * Replacing a pointer in an existing autoThing should be an exceptional phenomenon, * and therefore has to be done explicitly (rather than via an assignment), * so that you can easily spot ugly places in your source code. * In order not to leak memory, the old object is destroyed. */ void reset (T* const ptr) { if (d_ptr) forget (d_ptr); d_ptr = ptr; therror; } private: /* * The compiler should prevent initializations like * autoPitch pitch2 = pitch; */ template _Thing_auto (_Thing_auto &); // copy constructor //_Thing_auto (const _Thing_auto &); /* * The compiler should prevent assignments like * pitch2 = pitch; */ _Thing_auto& operator= (const _Thing_auto&); // copy assignment //template _Thing_auto& operator= (const _Thing_auto&); }; template class autoThingVector { T* d_ptr; long d_from, d_to; public: autoThingVector (long from, long to) : d_from (from), d_to (to) { d_ptr = static_cast (NUMvector (sizeof (T), from, to)); } autoThingVector (T *ptr, long from, long to) : d_ptr (ptr), d_from (from), d_to (to) { therror } autoThingVector () : d_ptr (NULL), d_from (1), d_to (0) { } ~autoThingVector () { if (d_ptr) { for (long i = d_from; i <= d_to; i ++) forget (d_ptr [i]); NUMvector_free (sizeof (T), d_ptr, d_from); } } T& operator[] (long i) { return d_ptr [i]; } T* peek () const { return d_ptr; } T* transfer () { T* temp = d_ptr; d_ptr = NULL; // make the pointer non-automatic again return temp; } void reset (long from, long to) { if (d_ptr) { for (long i = d_from; i <= d_to; i ++) forget (d_ptr [i]); NUMvector_free (sizeof (T), d_ptr, d_from); d_ptr = NULL; } d_from = from; // this assignment is safe, because d_ptr is NULL d_to = to; d_ptr = static_cast (NUMvector (sizeof (T), from, to)); } }; /* End of file Thing.h */ #endif sources_5316/sys/oo_DESCRIPTION.h0000644000176700017670000005430111724670615015206 0ustar paulpaul/* oo_DESCRIPTION.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #undef oo_BYTE #define oo_BYTE(x) { L"" #x, bytewa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char) }, #undef oo_INT #define oo_INT(x) { L"" #x, intwa, Melder_offsetof (ooSTRUCT, x), sizeof (int) }, #undef oo_LONG #define oo_LONG(x) { L"" #x, longwa, Melder_offsetof (ooSTRUCT, x), sizeof (long) }, #undef oo_UBYTE #define oo_UBYTE(x) { L"" #x, ubytewa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned char) }, #undef oo_UINT #define oo_UINT(x) { L"" #x, uintwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned int) }, #undef oo_ULONG #define oo_ULONG(x) { L"" #x, ulongwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned long) }, #undef oo_BOOL #define oo_BOOL(x) { L"" #x, boolwa, Melder_offsetof (ooSTRUCT, x), sizeof (bool) }, #undef oo_FLOAT #define oo_FLOAT(x) { L"" #x, floatwa, Melder_offsetof (ooSTRUCT, x), sizeof (double) }, #undef oo_DOUBLE #define oo_DOUBLE(x) { L"" #x, doublewa, Melder_offsetof (ooSTRUCT, x), sizeof (double) }, #undef oo_FCOMPLEX #define oo_FCOMPLEX(x) { L"" #x, fcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (fcomplex) }, #undef oo_DCOMPLEX #define oo_DCOMPLEX(x) { L"" #x, dcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (dcomplex) }, #undef oo_BYTE_ARRAY #define oo_BYTE_ARRAY(x,cap,n) { L"" #x, bytewa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_INT_ARRAY #define oo_INT_ARRAY(x,cap,n) { L"" #x, intwa, Melder_offsetof (ooSTRUCT, x), sizeof (int), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_LONG_ARRAY #define oo_LONG_ARRAY(x,cap,n) { L"" #x, longwa, Melder_offsetof (ooSTRUCT, x), sizeof (long), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_UBYTE_ARRAY #define oo_UBYTE_ARRAY(x,cap,n) { L"" #x, ubytewa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned char), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_UINT_ARRAY #define oo_UINT_ARRAY(x,cap,n) { L"" #x, uintwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned int), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_ULONG_ARRAY #define oo_ULONG_ARRAY(x,cap,n) { L"" #x, ulongwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned long), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_BOOL_ARRAY #define oo_BOOL_ARRAY(x,cap,n) { L"" #x, boolwa, Melder_offsetof (ooSTRUCT, x), sizeof (bool), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_FLOAT_ARRAY #define oo_FLOAT_ARRAY(x,cap,n) { L"" #x, floatwa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_DOUBLE_ARRAY #define oo_DOUBLE_ARRAY(x,cap,n) { L"" #x, doublewa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_FCOMPLEX_ARRAY #define oo_FCOMPLEX_ARRAY(x,cap,n) { L"" #x, fcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (fcomplex), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_DCOMPLEX_ARRAY #define oo_DCOMPLEX_ARRAY(x,cap,n) { L"" #x, dcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (dcomplex), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_BYTE_SET #define oo_BYTE_SET(x,setType) { L"" #x, bytewa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, /* BUG function pointer to pointer */ #undef oo_INT_SET #define oo_INT_SET(x,setType) { L"" #x, intwa, Melder_offsetof (ooSTRUCT, x), sizeof (int), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_LONG_SET #define oo_LONG_SET(x,setType) { L"" #x, longwa, Melder_offsetof (ooSTRUCT, x), sizeof (long), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_UBYTE_SET #define oo_UBYTE_SET(x,setType) { L"" #x, ubytewa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned char), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_UINT_SET #define oo_UINT_SET(x,setType) { L"" #x, uintwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned int), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_ULONG_SET #define oo_ULONG_SET(x,setType) { L"" #x, ulongwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned long), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_BOOL_SET #define oo_BOOL_SET(x,setType) { L"" #x, boolwa, Melder_offsetof (ooSTRUCT, x), sizeof (bool), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_FLOAT_SET #define oo_FLOAT_SET(x,setType) { L"" #x, floatwa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_DOUBLE_SET #define oo_DOUBLE_SET(x,setType) { L"" #x, doublewa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_FCOMPLEX_SET #define oo_FCOMPLEX_SET(x,setType) { L"" #x, fcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (fcomplex), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_DCOMPLEX_SET #define oo_DCOMPLEX_SET(x,setType) { L"" #x, dcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (dcomplex), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_BYTE_VECTOR_FROM #define oo_BYTE_VECTOR_FROM(x,min,max) { L"" #x, bytewa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 1, L"" #min, L"" #max }, #undef oo_INT_VECTOR_FROM #define oo_INT_VECTOR_FROM(x,min,max) { L"" #x, intwa, Melder_offsetof (ooSTRUCT, x), sizeof (int), 0, 0, 1, L"" #min, L"" #max }, #undef oo_LONG_VECTOR_FROM #define oo_LONG_VECTOR_FROM(x,min,max) { L"" #x, longwa, Melder_offsetof (ooSTRUCT, x), sizeof (long), 0, 0, 1, L"" #min, L"" #max }, #undef oo_UBYTE_VECTOR_FROM #define oo_UBYTE_VECTOR_FROM(x,min,max) { L"" #x, ubytewa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned char), 0, 0, 1, L"" #min, L"" #max }, #undef oo_UINT_VECTOR_FROM #define oo_UINT_VECTOR_FROM(x,min,max) { L"" #x, uintwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned int), 0, 0, 1, L"" #min, L"" #max }, #undef oo_ULONG_VECTOR_FROM #define oo_ULONG_VECTOR_FROM(x,min,max) { L"" #x, ulongwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned long), 0, 0, 1, L"" #min, L"" #max }, #undef oo_BOOL_VECTOR_FROM #define oo_BOOL_VECTOR_FROM(x,min,max) { L"" #x, boolwa, Melder_offsetof (ooSTRUCT, x), sizeof (bool), 0, 0, 1, L"" #min, L"" #max }, #undef oo_FLOAT_VECTOR_FROM #define oo_FLOAT_VECTOR_FROM(x,min,max) { L"" #x, floatwa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 1, L"" #min, L"" #max }, #undef oo_DOUBLE_VECTOR_FROM #define oo_DOUBLE_VECTOR_FROM(x,min,max) { L"" #x, doublewa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 1, L"" #min, L"" #max }, #undef oo_FCOMPLEX_VECTOR_FROM #define oo_FCOMPLEX_VECTOR_FROM(x,min,max) { L"" #x, fcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (fcomplex), 0, 0, 1, L"" #min, L"" #max }, #undef oo_DCOMPLEX_VECTOR_FROM #define oo_DCOMPLEX_VECTOR_FROM(x,min,max) { L"" #x, dcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (dcomplex), 0, 0, 1, L"" #min, L"" #max }, #undef oo_BYTE_MATRIX_FROM #define oo_BYTE_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, bytewa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_INT_MATRIX_FROM #define oo_INT_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, intwa, Melder_offsetof (ooSTRUCT, x), sizeof (int), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_LONG_MATRIX_FROM #define oo_LONG_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, longwa, Melder_offsetof (ooSTRUCT, x), sizeof (long), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_UBYTE_MATRIX_FROM #define oo_UBYTE_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, ubytewa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned char), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_UINT_MATRIX_FROM #define oo_UINT_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, uintwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned int), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_ULONG_MATRIX_FROM #define oo_ULONG_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, ulongwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned long), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_BOOL_MATRIX_FROM #define oo_BOOL_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, boolwa, Melder_offsetof (ooSTRUCT, x), sizeof (bool), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_FLOAT_MATRIX_FROM #define oo_FLOAT_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, floatwa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_DOUBLE_MATRIX_FROM #define oo_DOUBLE_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, doublewa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_FCOMPLEX_MATRIX_FROM #define oo_FCOMPLEX_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, fcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (fcomplex), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_DCOMPLEX_MATRIX_FROM #define oo_DCOMPLEX_MATRIX_FROM(x,r1,r2,c1,c2) { L"" #x, dcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (dcomplex), 0, 0, 2, L"" #r1, L"" #r2, L"" #c1, L"" #c2 }, #undef oo_BYTE_VECTOR #define oo_BYTE_VECTOR(x,n) { L"" #x, bytewa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_INT_VECTOR #define oo_INT_VECTOR(x,n) { L"" #x, intwa, Melder_offsetof (ooSTRUCT, x), sizeof (int), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_LONG_VECTOR #define oo_LONG_VECTOR(x,n) { L"" #x, longwa, Melder_offsetof (ooSTRUCT, x), sizeof (long), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_UBYTE_VECTOR #define oo_UBYTE_VECTOR(x,n) { L"" #x, ubytewa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned char), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_UINT_VECTOR #define oo_UINT_VECTOR(x,n) { L"" #x, uintwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned int), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_ULONG_VECTOR #define oo_ULONG_VECTOR(x,n) { L"" #x, ulongwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned long), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_BOOL_VECTOR #define oo_BOOL_VECTOR(x,n) { L"" #x, boolwa, Melder_offsetof (ooSTRUCT, x), sizeof (bool), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_FLOAT_VECTOR #define oo_FLOAT_VECTOR(x,n) { L"" #x, floatwa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_DOUBLE_VECTOR #define oo_DOUBLE_VECTOR(x,n) { L"" #x, doublewa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_FCOMPLEX_VECTOR #define oo_FCOMPLEX_VECTOR(x,n) { L"" #x, fcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (fcomplex), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_DCOMPLEX_VECTOR #define oo_DCOMPLEX_VECTOR(x,n) { L"" #x, dcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (dcomplex), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_BYTE_MATRIX #define oo_BYTE_MATRIX(x,nrow,ncol) { L"" #x, bytewa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_INT_MATRIX #define oo_INT_MATRIX(x,nrow,ncol) { L"" #x, intwa, Melder_offsetof (ooSTRUCT, x), sizeof (int), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_LONG_MATRIX #define oo_LONG_MATRIX(x,nrow,ncol) { L"" #x, longwa, Melder_offsetof (ooSTRUCT, x), sizeof (long), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_UBYTE_MATRIX #define oo_UBYTE_MATRIX(x,nrow,ncol) { L"" #x, ubytewa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned char), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_UINT_MATRIX #define oo_UINT_MATRIX(x,nrow,ncol) { L"" #x, uintwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned int), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_ULONG_MATRIX #define oo_ULONG_MATRIX(x,nrow,ncol) { L"" #x, ulongwa, Melder_offsetof (ooSTRUCT, x), sizeof (unsigned long), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_BOOL_MATRIX #define oo_BOOL_MATRIX(x,nrow,ncol) { L"" #x, boolwa, Melder_offsetof (ooSTRUCT, x), sizeof (bool), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_FLOAT_MATRIX #define oo_FLOAT_MATRIX(x,nrow,ncol) { L"" #x, floatwa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_DOUBLE_MATRIX #define oo_DOUBLE_MATRIX(x,nrow,ncol) { L"" #x, doublewa, Melder_offsetof (ooSTRUCT, x), sizeof (double), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_FCOMPLEX_MATRIX #define oo_FCOMPLEX_MATRIX(x,nrow,ncol) { L"" #x, fcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (fcomplex), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_DCOMPLEX_MATRIX #define oo_DCOMPLEX_MATRIX(x,nrow,ncol) { L"" #x, dcomplexwa, Melder_offsetof (ooSTRUCT, x), sizeof (dcomplex), 0, 0, 2, (const wchar *) 0, L"" #nrow, (const wchar *) 0, L"" #ncol }, #undef oo_ENUM #define oo_ENUM(Type,x) { L"" #x, enumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), L"" #Type, (void *) Type##_getText }, #undef oo_LENUM #define oo_LENUM(Type,x) { L"" #x, lenumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed short), L"" #Type, (void *) Type##_getText }, #undef oo_ENUM_ARRAY #define oo_ENUM_ARRAY(Type,x,cap,n) { L"" #x, enumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), L"" #Type, (void *) Type##_getText, - cap, (const wchar *) 0, L"" #n }, #undef oo_LENUM_ARRAY #define oo_LENUM_ARRAY(Type,x,cap,n) { L"" #x, lenumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed short), L"" #Type, (void *) Type##_getText, - cap, (const wchar *) 0, L"" #n }, #undef oo_ENUM_SET #define oo_ENUM_SET(Type,x,setType) { L"" #x, enumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), L"" #Type, (void *) Type##_getText, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_LENUM_SET #define oo_LENUM_SET(Type,x,setType) { L"" #x, lenumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed short), L"" #Type, (void *) Type##_getText, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_ENUM_VECTOR_FROM #define oo_ENUM_VECTOR_FROM(Type,x,min,max) { L"" #x, enumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), L"" #Type, (void *) Type##_getText, 1, L"" #min, L"" #max }, #undef oo_LENUM_VECTOR_FROM #define oo_LENUM_VECTOR_FROM(Type,x,min,max) { L"" #x, lenumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed short), L"" #Type, (void *) Type##_getText, 1, L"" #min, L"" #max }, #undef oo_ENUM_VECTOR #define oo_ENUM_VECTOR(Type,x,n) { L"" #x, enumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), L"" #Type, (void *) Type##_getText, 1, (const wchar *) 0, L"" #n }, #undef oo_LENUM_VECTOR #define oo_LENUM_VECTOR(Type,x,n) { L"" #x, lenumwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed short), L"" #Type, (void *) Type##_getText, 1, (const wchar *) 0, L"" #n }, #undef oo_BOOLEAN #define oo_BOOLEAN(x) { L"" #x, booleanwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char) }, #undef oo_BOOLEAN_ARRAY #define oo_BOOLEAN_ARRAY(x,cap,n) { L"" #x, booleanwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_BOOLEAN_SET #define oo_BOOLEAN_SET(x,setType) { L"" #x, booleanwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_BOOLEAN_VECTOR_FROM #define oo_BOOLEAN_VECTOR_FROM(x,min,max) { L"" #x, booleanwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, (const wchar *) 1, L"" #min, L"" #max }, #undef oo_BOOLEAN_VECTOR #define oo_BOOLEAN_VECTOR(x,n) { L"" #x, booleanwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_QUESTION #define oo_QUESTION(x) { L"" #x, questionwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char) }, #undef oo_QUESTION_ARRAY #define oo_QUESTION_ARRAY(x,cap,n) { L"" #x, questionwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_QUESTION_SET #define oo_QUESTION_SET(x,setType) { L"" #x, questionwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_QUESTION_VECTOR_FROM #define oo_QUESTION_VECTOR_FROM(x,min,max) { L"" #x, questionwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 1, L"" #min, L"" #max }, #undef oo_QUESTION_VECTOR #define oo_QUESTION_VECTOR(x,n) { L"" #x, questionwa, Melder_offsetof (ooSTRUCT, x), sizeof (signed char), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_STRING #define oo_STRING(x) { L"" #x, stringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *) }, #undef oo_LSTRING #define oo_LSTRING(x) { L"" #x, lstringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *) }, #undef oo_STRING_ARRAY #define oo_STRING_ARRAY(x,cap,n) { L"" #x, stringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_LSTRING_ARRAY #define oo_LSTRING_ARRAY(x,cap,n) { L"" #x, lstringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *), 0, 0, - cap, (const wchar *) 0, L"" #n }, #undef oo_STRING_SET #define oo_STRING_SET(x,setType) { L"" #x, stringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_LSTRING_SET #define oo_LSTRING_SET(x,setType) { L"" #x, lstringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #undef oo_STRING_VECTOR_FROM #define oo_STRING_VECTOR_FROM(x,min,max) { L"" #x, stringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *), 0, 0, 1, L"" #min, L"" #max }, #undef oo_LSTRING_VECTOR_FROM #define oo_LSTRING_VECTOR_FROM(x,min,max) { L"" #x, lstringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *), 0, 0, 1, L"" #min, L"" #max }, #undef oo_STRING_VECTOR #define oo_STRING_VECTOR(x,n) { L"" #x, stringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *), 0, 0, 1, (const wchar *) 0, L"" #n }, #undef oo_LSTRING_VECTOR #define oo_LSTRING_VECTOR(x,n) { L"" #x, lstringwa, Melder_offsetof (ooSTRUCT, x), sizeof (wchar_t *), 0, 0, 1, (const wchar *) 0, L"" #n }, #define oo_STRUCT(Type,x) { L"" #x, structwa, Melder_offsetof (ooSTRUCT, x), sizeof (struct struct##Type), L"" #Type, & struct##Type :: s_description }, #define oo_STRUCT_ARRAY(Type,x,cap,n) { L"" #x, structwa, Melder_offsetof (ooSTRUCT, x), sizeof (struct struct##Type), L"" #Type, & struct##Type :: s_description, - cap, (const wchar *) 0, L"" #n }, #define oo_STRUCT_SET(Type,x,setType) { L"" #x, structwa, Melder_offsetof (ooSTRUCT, x), sizeof (struct struct##Type), L"" #Type, & struct##Type :: s_description, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) { L"" #x, structwa, Melder_offsetof (ooSTRUCT, x), sizeof (struct struct##Type), L"" #Type, & struct##Type :: s_description, 1, L"" #min, L"" #max }, #undef oo_STRUCT_VECTOR #define oo_STRUCT_VECTOR(Type,x,n) { L"" #x, structwa, Melder_offsetof (ooSTRUCT, x), sizeof (struct struct##Type), L"" #Type, & struct##Type :: s_description, 1, (const wchar *) 0, L"" #n }, #define oo_WIDGET(x) { L"" #x, widgetwa, Melder_offsetof (ooSTRUCT, x), sizeof (GuiObject) }, #define oo_WIDGET_ARRAY(x,cap,n) { L"" #x, widgetwa, Melder_offsetof (ooSTRUCT, x), sizeof (GuiObject), 0, 0, - cap, (const wchar *) 0, L"" #n }, #define oo_WIDGET_SET(x,setType) { L"" #x, widgetwa, Melder_offsetof (ooSTRUCT, x), sizeof (GuiObject), 0, 0, 3, (const wchar *) setType##_getText, (const wchar *) setType##_getValue }, #define oo_WIDGET_VECTOR_FROM(x,min,max) { L"" #x, widgetwa, Melder_offsetof (ooSTRUCT, x), sizeof (GuiObject), 0, 0, 1, L"" #min, L"" #max }, #undef oo_WIDGET_VECTOR #define oo_WIDGET_VECTOR(Type,x,n) { L"" #x, widgetwa, Melder_offsetof (ooSTRUCT, x), sizeof (GuiObject), 0, 0, 1, 0, #n }, #define oo_OBJECT(Type,version,x) { L"" #x, objectwa, Melder_offsetof (ooSTRUCT, x), sizeof (Type), L"" #Type, & theClassInfo_##Type }, #define oo_COLLECTION(Type,x,ItemType,version) { L"" #x, collectionwa, Melder_offsetof (ooSTRUCT, x), sizeof (class struct##ItemType), L"" #Type, & theClassInfo_##Type, 0, (const wchar_t *) & theClassInfo_##ItemType }, #define oo_FILE(x) #define oo_DIR(x) #define oo_DEFINE_STRUCT(Type) \ static struct structData_Description the##Type##_description [] = { #define oo_END_STRUCT(Type) \ { 0 } \ }; \ Data_Description struct##Type :: s_description = & the##Type##_description [0]; #define oo_DEFINE_CLASS(Class,Parent) \ static struct structData_Description the##Class##_description [] = { \ { L"" #Class, inheritwa, 0, sizeof (class struct##Class), L"" #Class, & theClassInfo_##Parent }, #define oo_END_CLASS(Class) \ { 0 } \ }; \ Data_Description struct##Class :: s_description = & the##Class##_description [0]; #define oo_IF(condition) #define oo_ENDIF #define oo_FROM(from) #define oo_ENDFROM #define oo_VERSION(version) #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 0 #define oo_READING 0 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 0 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 1 /* End of file oo_DESCRIPTION.h */ sources_5316/sys/Script.cpp0000644000176700017670000000174311622340132014510 0ustar paulpaul/* Script.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Script.h" Thing_implement (Script, Data, 0); Script Script_createFromFile (MelderFile file) { autoScript me = Thing_new (Script); MelderFile_copy (file, & my file); return me.transfer(); } /* End of file Script.cpp */ sources_5316/sys/GraphicsP.h0000644000176700017670000001473311752247522014611 0ustar paulpaul#ifndef _GraphicsP_h_ #define _GraphicsP_h_ /* GraphicsP.h * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Graphics.h" #include "Gui.h" #if defined (_WIN32) #include #elif defined (macintosh) #include "macport_on.h" #include #include #include "macport_off.h" #endif void Graphics_init (Graphics me); /* Postconditions: my font == Graphics_FONT_HELVETICA; my fontSize == 9; my fontStyle == Graphics_NORMAL; */ #define kGraphics_font_SYMBOL (kGraphics_font_MAX + 1) #define kGraphics_font_IPATIMES (kGraphics_font_MAX + 2) #define kGraphics_font_DINGBATS (kGraphics_font_MAX + 3) Thing_define (GraphicsScreen, Graphics) { // new data: public: #if defined (UNIX) GdkDisplay *d_display; GdkDrawable *d_window; GdkGC *d_gdkGraphicsContext; cairo_t *d_cairoGraphicsContext; #elif defined (_WIN32) HWND d_winWindow; HDC d_gdiGraphicsContext; COLORREF d_winForegroundColour; HPEN d_winPen; HBRUSH d_winBrush; bool d_fatNonSolid; bool d_useGdiplus; #elif defined (macintosh) GrafPtr d_macPort; int d_macFont, d_macStyle; int d_depth; RGBColor d_macColour; CGContextRef d_macGraphicsContext; #endif // overridden methods: protected: virtual void v_destroy (); virtual void v_polyline (long numberOfPoints, long *xyDC, bool close); virtual void v_fillArea (long numberOfPoints, long *xyDC); virtual void v_rectangle (long x1DC, long x2DC, long y1DC, long y2DC); virtual void v_fillRectangle (long x1DC, long x2DC, long y1DC, long y2DC); virtual void v_circle (double xDC, double yDC, double rDC); virtual void v_ellipse (long x1DC, long x2DC, long y1DC, long y2DC); virtual void v_arc (long xDC, long yDC, long rDC, double fromAngle, double toAngle); virtual void v_fillCircle (long xDC, long yDC, long rDC); virtual void v_fillEllipse (long x1DC, long x2DC, long y1DC, long y2DC); virtual void v_button (long x1DC, long x2DC, long y1DC, long y2DC); virtual void v_roundedRectangle (long x1DC, long x2DC, long y1DC, long y2DC, long r); virtual void v_arrowHead (long xDC, long yDC, double angle); virtual bool v_mouseStillDown (); virtual void v_getMouseLocation (double *xWC, double *yWC); virtual void v_flushWs (); virtual void v_clearWs (); virtual void v_updateWs (); }; #if defined (UNIX) #define mac 0 #define win 0 #define cairo 1 #define pango 1 #elif defined (_WIN32) #define mac 0 #define win 1 #define cairo 0 #define pango 0 #elif defined (macintosh) #define mac 1 #define win 0 #define cairo 0 #define pango 0 #endif Thing_define (GraphicsPostscript, Graphics) { // new data: public: FILE *d_file; int (*d_printf) (void *stream, const char *format, ...); int languageLevel; int photocopyable, spotsDensity, spotsAngle, landscape, includeFonts, loadedXipa, useSilipaPS; double magnification; char *fontInfos [1 + kGraphics_font_DINGBATS] [1 + Graphics_BOLD_ITALIC]; const char *lastFid; int job, eps, pageNumber, lastSize; // overridden methods: virtual void v_destroy (); virtual void v_polyline (long numberOfPoints, long *xyDC, bool close); virtual void v_fillArea (long numberOfPoints, long *xyDC); virtual void v_rectangle (long x1DC, long x2DC, long y1DC, long y2DC); virtual void v_fillRectangle (long x1DC, long x2DC, long y1DC, long y2DC); virtual void v_circle (double xDC, double yDC, double rDC); virtual void v_ellipse (long x1DC, long x2DC, long y1DC, long y2DC); virtual void v_arc (long xDC, long yDC, long rDC, double fromAngle, double toAngle); virtual void v_fillCircle (long xDC, long yDC, long rDC); virtual void v_fillEllipse (long x1DC, long x2DC, long y1DC, long y2DC); virtual void v_arrowHead (long xDC, long yDC, double angle); }; /* Opcodes for recording. */ double * _Graphics_check (Graphics me, long number); #define put(f) * ++ p = (double) (f) #define op(opcode,number) double *p = _Graphics_check (me, number); if (! p) return; put (opcode); put (number) #define mput(n,a) { double *f = a; for (long l = 0; l < n; l ++) put (f [l]); } #define sput(s,l) { put (l); strcpy ((char *) (p + 1), s); p += l; } /* When adding opcodes in the following list, add them at the end. */ /* Otherwise, old picture files will become incompatible with the current Graphics. */ enum opcode { SET_VIEWPORT = 101, SET_INNER, UNSET_INNER, SET_WINDOW, /* 105 */ TEXT, POLYLINE, LINE, ARROW, FILL_AREA, FUNCTION, RECTANGLE, FILL_RECTANGLE, /* 113 */ CIRCLE, FILL_CIRCLE, ARC, ARC_ARROW, HIGHLIGHT, CELL_ARRAY, /* 119 */ SET_FONT, SET_FONT_SIZE, SET_FONT_STYLE, /* 122 */ SET_TEXT_ALIGNMENT, SET_TEXT_ROTATION, /* 124 */ SET_LINE_TYPE, SET_LINE_WIDTH, /* 126 */ SET_STANDARD_COLOUR, SET_GREY, /* 128 */ MARK_GROUP, ELLIPSE, FILL_ELLIPSE, CIRCLE_MM, FILL_CIRCLE_MM, IMAGE8, /* 134 */ UNHIGHLIGHT, XOR_ON, XOR_OFF, RECTANGLE_MM, FILL_RECTANGLE_MM, /* 139 */ SET_WS_WINDOW, SET_WRAP_WIDTH, SET_SECOND_INDENT, /* 142 */ SET_PERCENT_SIGN_IS_ITALIC, SET_NUMBER_SIGN_IS_BOLD, /* 144 */ SET_CIRCUMFLEX_IS_SUPERSCRIPT, SET_UNDERSCORE_IS_SUBSCRIPT, /* 146 */ SET_DOLLAR_SIGN_IS_CODE, SET_AT_SIGN_IS_LINK, /* 148 */ BUTTON, ROUNDED_RECTANGLE, FILL_ROUNDED_RECTANGLE, FILL_ARC, /* 152 */ INNER_RECTANGLE, CELL_ARRAY8, IMAGE, HIGHLIGHT2, UNHIGHLIGHT2, /* 157 */ SET_ARROW_SIZE, DOUBLE_ARROW, SET_RGB_COLOUR, IMAGE_FROM_FILE, /* 161 */ POLYLINE_CLOSED }; void _GraphicsScreen_text_init (GraphicsScreen me); void _Graphics_fillRectangle (Graphics me, long x1DC, long x2DC, long y1DC, long y2DC); void _Graphics_setColour (Graphics me, Graphics_Colour colour); void _Graphics_setGrey (Graphics me, double grey); void _Graphics_colour_init (Graphics me); bool _GraphicsMac_tryToInitializeAtsuiFonts (void); #ifdef macintosh void GraphicsQuartz_initDraw (GraphicsScreen me); void GraphicsQuartz_exitDraw (GraphicsScreen me); #endif /* End of file GraphicsP.h */ #endif sources_5316/sys/melder_info.cpp0000644000176700017670000002272711633766375015563 0ustar paulpaul/* melder_info.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* pb 2002/03/07 GPL * pb 2006/12/08 separated from melder.c * pb 2006/12/17 removed Melder_info and made Melder_print safe * pb 2006/12/19 all functions number 1 through 9 * pb 2007/06/11 wchar_t * pb 2007/08/14 faster * pb 2007/10/05 got rid of MelderStringA_copyW * pb 2007/12/13 Melder_writeToConsole * pb 2011/04/05 C++ */ #include "melder.h" #include "NUM.h" // NUMundefined static void defaultInformation (const wchar_t *message) { Melder_writeToConsole (message, false); } static void (*theInformation) (const wchar_t *) = defaultInformation; void Melder_setInformationProc (void (*information) (const wchar_t *)) { theInformation = information ? information : defaultInformation; } static MelderString theForegroundBuffer = { 0 }, *theInfos = & theForegroundBuffer; void MelderInfo_open (void) { MelderString_empty (theInfos); } void MelderInfo_write1 (const wchar_t *s1) { MelderString_append (theInfos, s1); } void MelderInfo_write2 (const wchar_t *s1, const wchar_t *s2) { MelderString_append (theInfos, s1, s2); } void MelderInfo_write3 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3) { MelderString_append (theInfos, s1, s2, s3); } void MelderInfo_write4 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4) { MelderString_append (theInfos, s1, s2, s3, s4); } void MelderInfo_write5 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5) { MelderString_append (theInfos, s1, s2, s3, s4, s5); } void MelderInfo_write6 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { MelderString_append (theInfos, s1, s2, s3, s4, s5, s6); } void MelderInfo_write7 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7) { MelderString_append (theInfos, s1, s2, s3, s4, s5, s6, s7); } void MelderInfo_write8 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8) { MelderString_append (theInfos, s1, s2, s3, s4, s5, s6, s7, s8); } void MelderInfo_write9 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8, const wchar_t *s9) { MelderString_append (theInfos, s1, s2, s3, s4, s5, s6, s7, s8, s9); } void MelderInfo_writeLine1 (const wchar_t *s1) { MelderString_append (theInfos, s1); MelderString_appendCharacter (theInfos, '\n'); } void MelderInfo_writeLine2 (const wchar_t *s1, const wchar_t *s2) { MelderString_append (theInfos, s1, s2); MelderString_appendCharacter (theInfos, '\n'); } void MelderInfo_writeLine3 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3) { MelderString_append (theInfos, s1, s2, s3); MelderString_appendCharacter (theInfos, '\n'); } void MelderInfo_writeLine4 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4) { MelderString_append (theInfos, s1, s2, s3, s4); MelderString_appendCharacter (theInfos, '\n'); } void MelderInfo_writeLine5 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5) { MelderString_append (theInfos, s1, s2, s3, s4, s5); MelderString_appendCharacter (theInfos, '\n'); } void MelderInfo_writeLine6 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { MelderString_append (theInfos, s1, s2, s3, s4, s5, s6); MelderString_appendCharacter (theInfos, '\n'); } void MelderInfo_writeLine7 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7) { MelderString_append (theInfos, s1, s2, s3, s4, s5, s6, s7); MelderString_appendCharacter (theInfos, '\n'); } void MelderInfo_writeLine8 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8) { MelderString_append (theInfos, s1, s2, s3, s4, s5, s6, s7, s8); MelderString_appendCharacter (theInfos, '\n'); } void MelderInfo_writeLine9 (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8, const wchar_t *s9) { MelderString_append (theInfos, s1, s2, s3, s4, s5, s6, s7, s8, s9); MelderString_appendCharacter (theInfos, '\n'); } void MelderInfo_close (void) { if (theInfos == & theForegroundBuffer) { /* When writing to the Info window or the console, we must add a newline symbol, because a subsequent Melder_print call has to start on the next line. When writing to a diverted string, we must *not* add a newline symbol, because scripts expect returned strings without appended newlines! */ if (theInfos -> length == 0 || theInfos -> string [theInfos -> length - 1] != '\n') { // Only if no newline there yet. MelderString_appendCharacter (theInfos, '\n'); } theInformation (theInfos -> string ? theInfos -> string : L""); } } void Melder_informationReal (double value, const wchar_t *units) { MelderInfo_open (); if (value == NUMundefined) MelderInfo_write1 (L"--undefined--"); else if (units == NULL) MelderInfo_write1 (Melder_double (value)); else MelderInfo_write3 (Melder_double (value), L" ", units); MelderInfo_close (); } void Melder_divertInfo (MelderString *buffer) { theInfos = buffer == NULL ? & theForegroundBuffer : buffer; } void Melder_clearInfo (void) { if (theInfos == & theForegroundBuffer) { MelderString_empty (theInfos); theInformation (L""); } } const wchar_t * Melder_getInfo (void) { return theInfos -> string ? theInfos -> string : L""; } void Melder_print (const wchar_t *s) { //Melder_assert (theInfos == & theForegroundBuffer); // Never diverted. /* * This procedure is always called from a script; therefore, this is unlikely to be called when the info is diverted. * Unlikely, but not impossible! * The small possibility occurs when the script, having diverted the info through an assignment command, * causes the progress bar to move. If the user chooses Run while the progress bar moves, * the script will start to run and may call print: * pitch = To Pitch... 0 75 600 * Therefore, we write into the Info window explicitly. The results will still be strange, * and a better solution would be to disallow the script from running (BUG: accept fewer events in waitWhileProgress). */ if (theInformation == defaultInformation) { theInformation ((wchar_t *) s); // Do not print the previous lines again. } else { MelderString_append (& theForegroundBuffer, s); theInformation (theForegroundBuffer. string); } } void Melder_information (const wchar_t *s1) { MelderString_empty (theInfos); MelderString_append (theInfos, s1); MelderInfo_close (); } void Melder_information (const wchar_t *s1, const wchar_t *s2) { MelderString_empty (theInfos); MelderString_append (theInfos, s1, s2); MelderInfo_close (); } void Melder_information (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3) { MelderString_empty (theInfos); MelderString_append (theInfos, s1, s2, s3); MelderInfo_close (); } void Melder_information (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4) { MelderString_empty (theInfos); MelderString_append (theInfos, s1, s2, s3, s4); MelderInfo_close (); } void Melder_information (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5) { MelderString_empty (theInfos); MelderString_append (theInfos, s1, s2, s3, s4, s5); MelderInfo_close (); } void Melder_information (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6) { MelderString_empty (theInfos); MelderString_append (theInfos, s1, s2, s3, s4, s5, s6); MelderInfo_close (); } void Melder_information (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7) { MelderString_empty (theInfos); MelderString_append (theInfos, s1, s2, s3, s4, s5, s6, s7); MelderInfo_close (); } void Melder_information (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8) { MelderString_empty (theInfos); MelderString_append (theInfos, s1, s2, s3, s4, s5, s6, s7, s8); MelderInfo_close (); } void Melder_information (const wchar_t *s1, const wchar_t *s2, const wchar_t *s3, const wchar_t *s4, const wchar_t *s5, const wchar_t *s6, const wchar_t *s7, const wchar_t *s8, const wchar_t *s9) { MelderString_empty (theInfos); MelderString_append (theInfos, s1, s2, s3, s4, s5, s6, s7, s8, s9); MelderInfo_close (); } /* End of file melder_info.cpp */ sources_5316/sys/GuiObject.cpp0000644000176700017670000002072211753743231015131 0ustar paulpaul/* GuiObject.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/26 abstraction from motif * pb 2007/12/28 _GuiObject_position: allow the combination of fixed height and automatic position * sdk 2008/03/24 GTK * sdk 2008/07/01 GTK get sizes * fb 2010/02/23 GTK * pb 2010/11/28 removed Motif * pb 2011/04/06 C++ */ #include "GuiP.h" #include "machine.h" static int _Gui_defaultHeight (GuiObject me) { #if win || mac && useCarbon WidgetClass klas = XtClass (me); if (klas == xmLabelWidgetClass) return Gui_LABEL_HEIGHT; if (klas == xmPushButtonWidgetClass) return Gui_PUSHBUTTON_HEIGHT; if (klas == xmTextWidgetClass) return Gui_TEXTFIELD_HEIGHT; if (klas == xmToggleButtonWidgetClass) return #ifdef UNIX Gui_CHECKBUTTON_HEIGHT; // BUG #else my isRadioButton ? Gui_RADIOBUTTON_HEIGHT : Gui_CHECKBUTTON_HEIGHT; #endif #endif return 100; } void _GuiObject_position (GuiObject me, int left, int right, int top, int bottom) { #if gtk // TODO: ...nog even te creatief #elif win || mac && useCarbon if (left >= 0) { if (right > 0) { XtVaSetValues (me, XmNx, left, XmNwidth, right - left, NULL); } else if (right == Gui_AUTOMATIC) { XtVaSetValues (me, XmNx, left, NULL); } else { XtVaSetValues (me, XmNleftAttachment, XmATTACH_FORM, XmNleftOffset, left, XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, - right, NULL); } } else if (left == Gui_AUTOMATIC) { Melder_assert (right <= 0); if (right > Gui_AUTOMATIC + 3000) XtVaSetValues (me, XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, - right, NULL); else if (right != Gui_AUTOMATIC) XtVaSetValues (me, XmNwidth, right - Gui_AUTOMATIC, NULL); } else { Melder_assert (right <= 0); XtVaSetValues (me, XmNrightAttachment, XmATTACH_FORM, XmNrightOffset, - right, XmNwidth, right - left, NULL); } if (top >= 0) { if (bottom > 0) { XtVaSetValues (me, XmNy, top, XmNheight, bottom - top, NULL); } else if (bottom == Gui_AUTOMATIC) { XtVaSetValues (me, XmNy, top, XmNheight, _Gui_defaultHeight (me), NULL); } else { XtVaSetValues (me, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, top, XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, - bottom, NULL); } } else if (top == Gui_AUTOMATIC) { Melder_assert (bottom <= 0); if (bottom > Gui_AUTOMATIC + 3000) XtVaSetValues (me, XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, - bottom, XmNheight, _Gui_defaultHeight (me), NULL); else if (bottom != Gui_AUTOMATIC) XtVaSetValues (me, XmNheight, bottom - Gui_AUTOMATIC, NULL); } else { Melder_assert (bottom <= 0); XtVaSetValues (me, XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, - bottom, XmNheight, bottom - top, NULL); } #endif } void * _GuiObject_getUserData (GuiObject me) { void *userData = NULL; #if gtk userData = (void *) g_object_get_data (G_OBJECT (me), "praat"); #elif win XtVaGetValues (me, XmNuserData, & userData, NULL); #elif mac #if useCarbon XtVaGetValues (me, XmNuserData, & userData, NULL); #else #endif #endif return userData; } void _GuiObject_setUserData (GuiObject me, void *userData) { #if gtk g_object_set_data (G_OBJECT (me), "praat", userData); #elif win XtVaSetValues (me, XmNuserData, userData, NULL); #elif mac #if useCarbon XtVaSetValues (me, XmNuserData, userData, NULL); #else #endif #endif } void GuiObject_destroy (GuiObject me) { #if gtk gtk_widget_destroy (GTK_WIDGET (me)); #elif win XtDestroyWidget (me); #elif mac #if useCarbon XtDestroyWidget (me); #else #endif #endif } long GuiObject_getHeight (GuiObject me) { long height = 0; #if gtk height = GTK_WIDGET (me) -> allocation.height; #elif win height = my height; #elif mac #if useCarbon height = my height; #else #endif #endif return height; } long GuiObject_getWidth (GuiObject me) { long width = 0; #if gtk width = GTK_WIDGET (me) -> allocation.width; #elif win width = my width; #elif mac #if useCarbon width = my width; #else #endif #endif return width; } long GuiObject_getX (GuiObject me) { long x = 0; #if gtk x = GTK_WIDGET (me) -> allocation.x; #elif win x = my x; #elif mac #if useCarbon x = my x; #else #endif #endif return x; } long GuiObject_getY (GuiObject me) { long y = 0; #if gtk y = GTK_WIDGET (me) -> allocation.y; #elif win y = my y; #elif mac #if useCarbon y = my y; #else #endif #endif return y; } void GuiObject_move (GuiObject me, long x, long y) { #if gtk #elif win || mac && useCarbon if (x != Gui_AUTOMATIC) { if (y != Gui_AUTOMATIC) { XtVaSetValues (me, XmNx, (Position) x, XmNy, (Position) y, NULL); // 64-bit-compatible } else { XtVaSetValues (me, XmNx, (Position) x, NULL); // 64-bit-compatible } } else if (y != Gui_AUTOMATIC) { XtVaSetValues (me, XmNy, (Position) y, NULL); // 64-bit-compatible } #endif } void GuiObject_hide (GuiObject me) { #if gtk GuiObject parent = gtk_widget_get_parent (GTK_WIDGET (me)); if (parent != NULL && GTK_IS_DIALOG (parent)) { // I am the top vbox of a dialog gtk_widget_hide (GTK_WIDGET (parent)); } else { gtk_widget_hide (GTK_WIDGET (me)); } #elif win XtUnmanageChild (me); // nothing, because the scrolled window is not a widget #elif mac #if useCarbon XtUnmanageChild (me); if (my widgetClass == xmListWidgetClass) { XtUnmanageChild (my parent); // the containing scrolled window; BUG if created with XmScrolledList? } #else #endif #endif } GuiObject GuiObject_parent (GuiObject me) { #if gtk return gtk_widget_get_parent (GTK_WIDGET (me)); #elif win return my parent; #elif mac #if useCarbon return my parent; #else return NULL; // TODO #endif #endif } void GuiObject_setSensitive (GuiObject me, bool sensitive) { #if gtk gtk_widget_set_sensitive (GTK_WIDGET (me), sensitive); #elif win XtSetSensitive (me, sensitive); #elif mac #if useCarbon XtSetSensitive (me, sensitive); #else #endif #endif } void GuiObject_show (GuiObject me) { #if gtk GuiObject parent = gtk_widget_get_parent (GTK_WIDGET (me)); if (GTK_IS_WINDOW (parent)) { // I am a window's vbox gtk_widget_show (GTK_WIDGET (me)); gtk_window_present (GTK_WINDOW (parent)); } else if (GTK_IS_DIALOG (parent)) { // I am a dialog's vbox, and therefore automatically shown gtk_window_present (GTK_WINDOW (parent)); } else { gtk_widget_show (GTK_WIDGET (me)); } #elif win XtManageChild (me); GuiObject parent = my parent; if (parent -> widgetClass == xmShellWidgetClass) { XMapRaised (XtDisplay (parent), XtWindow (parent)); } else if (mac && my widgetClass == xmListWidgetClass) { XtManageChild (parent); // the containing scrolled window; BUG if created with XmScrolledList? } #elif mac #if useCarbon XtManageChild (me); GuiObject parent = my parent; if (parent -> widgetClass == xmShellWidgetClass) { XMapRaised (XtDisplay (parent), XtWindow (parent)); } else if (mac && my widgetClass == xmListWidgetClass) { XtManageChild (parent); // the containing scrolled window; BUG if created with XmScrolledList? } #else #endif #endif } void GuiObject_size (GuiObject me, long width, long height) { #if gtk if (width == Gui_AUTOMATIC || width <= 0) width = -1; if (height == Gui_AUTOMATIC || height <= 0) height = -1; gtk_widget_set_size_request (GTK_WIDGET (me), width, height); #elif win || mac && useCarbon if (width != Gui_AUTOMATIC) { if (height != Gui_AUTOMATIC) { XtVaSetValues (me, XmNwidth, (Dimension) width, XmNheight, (Dimension) height, NULL); // 64-bit-compatible } else { XtVaSetValues (me, XmNwidth, (Dimension) width, NULL); // 64-bit-compatible } } else if (height != Gui_AUTOMATIC) { XtVaSetValues (me, XmNheight, (Dimension) height, NULL); // 64-bit-compatible } #endif } /* End of file GuiObject.cpp */ sources_5316/sys/Graphics_surface.cpp0000644000176700017670000001062611625405212016520 0ustar paulpaul/* Graphics_surface.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Graphics.h" void Graphics_surface (Graphics me, double **z, long ix1, long ix2, double x1, double x2, long iy1, long iy2, double y1, double y2, double minimum, double maximum, double elevation, double azimuth) { double dx, dy; /* 'sum' is the running sum of the x and y indices of the back corner of each tetragon. * The x and y indices of the back corner of the backmost tetragon are ix2 and iy2, * The x and y indices of the front corner of the frontmost tetragon are ix1 and iy1, * so that the x and y indices of its back corner are ix1 + 1 and iy1 + 1. */ long maxsum = ix2 + iy2, minsum = (ix1 + 1) + (iy1 + 1), sum; (void) elevation; /* BUG */ (void) azimuth; /* BUG */ if (ix2 <= ix1 || iy2 <= iy1) return; dx = (x2 - x1) / (ix2 - ix1); dy = (y2 - y1) / (iy2 - iy1); /* We start at the back of the surface plot. * This part of the picture may be overdrawn by points more forward. */ for (sum = maxsum; sum >= minsum; sum --) { /* We are going to cycle over a diagonal sequence of points. * Compute the row boundaries of this sequence. */ long iymin = iy1 + 1, iymax = iy2, iy; if (iymin < sum - ix2) iymin = sum - ix2; if (iymax > sum - (ix1 + 1)) iymax = sum - (ix1 + 1); for (iy = iymin; iy <= iymax; iy ++) { /* Compute the indices of all four points. */ long ix = sum - iy; long ixback = ix, ixfront = ix - 1, ixleft = ix - 1, ixright = ix; long iyback = iy, iyfront = iy - 1, iyleft = iy, iyright = iy - 1; /* Compute the world coordinates of all four points. */ double xback = x1 + (ixback - ix1) * dx, xright = xback; double xfront = x1 + (ixfront - ix1) * dx, xleft = xfront; double yback = y1 + (iyback - iy1) * dy, yleft = yback; double yfront = y1 + (iyfront - iy1) * dy, yright = yfront; double zback = z [iyback] [ixback], zfront = z [iyfront] [ixfront]; double zleft = z [iyleft] [ixleft], zright = z [iyright] [ixright]; /* The Graphics library uses a two-dimensional world, so we have to convert * to 2-D world coordinates, which we call x [0..3] and y [0..3]. * We suppose that world coordinate "x" = 0 is in the centre of the figure, * and that the left and right borders of the figure have world coordinates -1 and +1. * Also, we suppose that the bottom and top are around 'minimum' and 'maximum'. */ double x [5], y [5]; /* Elevation and azimuth fixed??? */ double up = 0.3 * (maximum - minimum), xscale = 1 / (x2 - x1), yscale = 1 / (y2 - y1); /* The back point. */ x [0] = (xback - x1) * xscale - (yback - y1) * yscale; y [0] = up * ((xback - x1) * xscale + (yback - y1) * yscale) + zback; /* The right point. */ x [1] = (xright - x1) * xscale - (yright - y1) * yscale; y [1] = up * ((xright - x1) * xscale + (yright - y1) * yscale) + zright; /* The front point. */ x [2] = (xfront - x1) * xscale - (yfront - y1) * yscale; y [2] = up * ((xfront - x1) * xscale + (yfront - y1) * yscale) + zfront; /* The left point. */ x [3] = (xleft - x1) * xscale - (yleft - y1) * yscale; y [3] = up * ((xleft - x1) * xscale + (yleft - y1) * yscale) + zleft; /* Paint the tetragon in the average grey value, white at the top. * This gives the idea of height. */ Graphics_setGrey (me, (0.25 * (zback + zright + zfront + zleft) - minimum) / (maximum - minimum)); Graphics_fillArea (me, 4, & x [0], & y [0]); /* Draw the borders of the tetragon in black. * This gives the idea of steepness and viewing angle. */ Graphics_setGrey (me, 0); x [4] = x [0]; y [4] = y [0]; /* Close polygon. */ Graphics_polyline (me, 5, & x [0], & y [0]); } } } /* End of file Graphics_surface.cpp */ sources_5316/sys/GuiList.cpp0000644000176700017670000007242411753754376014660 0ustar paulpaul/* GuiList.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/26 abstraction from Motif * pb 2009/01/31 NUMlvector_free has to be followed by assigning a NULL * fb 2010/02/23 GTK * pb 2010/06/14 HandleControlClick * pb 2010/07/05 blockSelectionChangedCallback * pb 2010/11/28 removed Motif * pb 2011/04/06 C++ */ #include "GuiP.h" #include "NUM.h" #undef iam #define iam(x) x me = (x) void_me #if win || mac #define iam_list \ Melder_assert (widget -> widgetClass == xmListWidgetClass); \ GuiList me = (GuiList) widget -> userData #else #define iam_list \ GuiList me = (GuiList) _GuiObject_getUserData (widget) #endif #if win #define CELL_HEIGHT 15 #elif mac #define CELL_HEIGHT 18 #define USE_MAC_LISTBOX_CONTROL 0 #endif typedef struct structGuiList { GuiObject widget; bool allowMultipleSelection, blockSelectionChangedCallback; void (*selectionChangedCallback) (void *boss, GuiListEvent event); void *selectionChangedBoss; void (*doubleClickCallback) (void *boss, GuiListEvent event); void *doubleClickBoss; #if gtk GtkListStore *liststore; #elif win #elif mac GuiObject scrolled; ListHandle macListHandle; #endif } *GuiList; #if gtk static void _GuiGtkList_destroyCallback (gpointer void_me) { iam (GuiList); Melder_free (me); } static void _GuiGtkList_selectionChangedCallback (GtkTreeSelection *sel, gpointer void_me) { iam (GuiList); if (my selectionChangedCallback != NULL && ! my blockSelectionChangedCallback) { //Melder_casual ("Selection changed."); struct structGuiListEvent event = { GTK_WIDGET (gtk_tree_selection_get_tree_view (sel)) }; my selectionChangedCallback (my selectionChangedBoss, & event); } } #elif win void _GuiWinList_destroy (GuiObject widget) { iam_list; DestroyWindow (widget -> window); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiWinList_map (GuiObject widget) { iam_list; ShowWindow (widget -> window, SW_SHOW); } void _GuiWinList_handleClick (GuiObject widget) { iam_list; if (my selectionChangedCallback != NULL) { struct structGuiListEvent event = { widget }; my selectionChangedCallback (my selectionChangedBoss, & event); } } #elif mac #if useCarbon void _GuiMacList_destroy (GuiObject widget) { iam_list; _GuiMac_clipOnParent (widget); if (widget -> isControl) { DisposeControl (widget -> nat.control.handle); } else { LDispose (my macListHandle); } GuiMac_clipOff (); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiMacList_map (GuiObject widget) { iam_list; if (widget -> isControl) { _GuiNativeControl_show (widget); Melder_casual ("showing a list"); //_GuiMac_clipOnParent (widget); //LSetDrawingMode (true, my macListHandle); //_GuiMac_clipOffInvalid (widget); } else { _GuiMac_clipOnParent (widget); LSetDrawingMode (true, my macListHandle); _GuiMac_clipOffInvalid (widget); } } void _GuiMacList_activate (GuiObject widget, bool activate) { iam_list; _GuiMac_clipOnParent (widget); LActivate (activate, my macListHandle); GuiMac_clipOff (); } void _GuiMacList_handleControlClick (GuiObject widget, EventRecord *macEvent) { iam_list; _GuiMac_clipOnParent (widget); bool pushed = HandleControlClick (widget -> nat.control.handle, macEvent -> where, macEvent -> modifiers, NULL); GuiMac_clipOff (); if (pushed && my selectionChangedCallback) { struct structGuiListEvent event = { widget }; my selectionChangedCallback (my selectionChangedBoss, & event); } } void _GuiMacList_handleClick (GuiObject widget, EventRecord *macEvent) { iam_list; _GuiMac_clipOnParent (widget); bool doubleClick = LClick (macEvent -> where, macEvent -> modifiers, my macListHandle); GuiMac_clipOff (); if (my selectionChangedCallback) { struct structGuiListEvent event = { widget }; my selectionChangedCallback (my selectionChangedBoss, & event); } if (doubleClick && my doubleClickCallback) { struct structGuiListEvent event = { widget }; my doubleClickCallback (my doubleClickBoss, & event); } } void _GuiMacList_move (GuiObject widget) { iam_list; (** my macListHandle). rView = widget -> rect; } void _GuiMacList_resize (GuiObject widget) { iam_list; (** my macListHandle). rView = widget -> rect; SetPortWindowPort (widget -> macWindow); (** my macListHandle). cellSize. h = widget -> width; if (widget -> parent -> widgetClass == xmScrolledWindowWidgetClass) _Gui_manageScrolledWindow (widget -> parent); } void _GuiMacList_shellResize (GuiObject widget) { iam_list; (** my macListHandle). rView = widget -> rect; (** my macListHandle). cellSize. h = widget -> width; } void _GuiMacList_update (GuiObject widget, RgnHandle visRgn) { iam_list; _GuiMac_clipOnParent (widget); if (widget -> isControl) { Draw1Control (widget -> nat.control.handle); } else { LUpdate (visRgn, my macListHandle); } GuiMac_clipOff (); } #else #endif #endif #if mac && useCarbon static pascal void mac_listDefinition (short message, Boolean select, Rect *rect, Cell cell, short dataOffset, short dataLength, ListHandle handle) { GuiObject widget = (GuiObject) GetListRefCon (handle); (void) cell; switch (message) { case lDrawMsg: case lHiliteMsg: // We redraw everything, even when just highlighting. The reason is anti-aliasing. Melder_assert (widget != NULL); SetPortWindowPort (widget -> macWindow); _GuiMac_clipOnParent (widget); /* * In order that highlighting (which by default turns only the white pixels into pink) * does not leave light-grey specks around the glyphs (in the anti-aliasing regions), * we simply draw the glyphs on a pink background if the item is selected. */ /* * Erase the background. */ static RGBColor whiteColour = { 0xFFFF, 0xFFFF, 0xFFFF }, blackColour = { 0, 0, 0 }; RGBForeColor (& whiteColour); PaintRect (rect); RGBForeColor (& blackColour); /* * Pink (or any other colour the user prefers) if the item is selected. */ if (select) { LMSetHiliteMode (LMGetHiliteMode () & ~ 128L); InvertRect (rect); } /* * Draw the text on top of this. */ CGContextRef macGraphicsContext; QDBeginCGContext (GetWindowPort (widget -> macWindow), & macGraphicsContext); int shellHeight = GuiMac_clipOn_graphicsContext (widget, macGraphicsContext); static ATSUFontFallbacks fontFallbacks = NULL; if (fontFallbacks == NULL) { ATSUCreateFontFallbacks (& fontFallbacks); ATSUSetObjFontFallbacks (fontFallbacks, 0, NULL, kATSUDefaultFontFallbacks); } char *text_utf8 = (char *) *(*handle) -> cells + dataOffset; strncpy (Melder_buffer1, text_utf8, dataLength); Melder_buffer1 [dataLength] = '\0'; wchar_t *text_wcs = Melder_peekUtf8ToWcs (Melder_buffer1); const MelderUtf16 *text_utf16 = Melder_peekWcsToUtf16 (text_wcs); UniCharCount runLength = wcslen (text_wcs); // BUG ATSUTextLayout textLayout; ATSUStyle style; ATSUCreateStyle (& style); Fixed fontSize = 13 << 16; Boolean boldStyle = 0; Boolean italicStyle = 0; ATSUAttributeTag styleAttributeTags [] = { kATSUSizeTag, kATSUQDBoldfaceTag, kATSUQDItalicTag }; ByteCount styleValueSizes [] = { sizeof (Fixed), sizeof (Boolean), sizeof (Boolean) }; ATSUAttributeValuePtr styleValues [] = { & fontSize, & boldStyle, & italicStyle }; ATSUSetAttributes (style, 3, styleAttributeTags, styleValueSizes, styleValues); OSStatus err = ATSUCreateTextLayoutWithTextPtr (text_utf16, kATSUFromTextBeginning, kATSUToTextEnd, runLength, 1, & runLength, & style, & textLayout); Melder_assert (err == 0); ATSUAttributeTag attributeTags [] = { kATSUCGContextTag, kATSULineFontFallbacksTag }; ByteCount valueSizes [] = { sizeof (CGContextRef), sizeof (ATSUFontFallbacks) }; ATSUAttributeValuePtr values [] = { & macGraphicsContext, & fontFallbacks }; ATSUSetLayoutControls (textLayout, 2, attributeTags, valueSizes, values); ATSUSetTransientFontMatching (textLayout, true); CGContextTranslateCTM (macGraphicsContext, rect -> left, shellHeight - rect -> bottom + 4); err = ATSUDrawText (textLayout, kATSUFromTextBeginning, kATSUToTextEnd, 0 /*xDC << 16*/, 0 /*(shellHeight - yDC) << 16*/); Melder_assert (err == 0); CGContextSynchronize (macGraphicsContext); ATSUDisposeTextLayout (textLayout); ATSUDisposeStyle (style); QDEndCGContext (GetWindowPort (widget -> macWindow), & macGraphicsContext); GuiMac_clipOff (); break; /* case lHiliteMsg: Melder_assert (me != NULL); SetPortWindowPort (my macWindow); _GuiMac_clipOnParent (me); LMSetHiliteMode (LMGetHiliteMode () & ~ 128L); InvertRect (rect); GuiMac_clipOff (); break;*/ } } #endif #if gtk enum { COLUMN_STRING, N_COLUMNS }; #endif GuiObject GuiList_create (GuiObject parent, int left, int right, int top, int bottom, bool allowMultipleSelection, const wchar_t *header) { GuiList me = Melder_calloc_f (struct structGuiList, 1); my allowMultipleSelection = allowMultipleSelection; #if gtk GtkCellRenderer *renderer = NULL; GtkTreeViewColumn *col = NULL; GtkTreeSelection *sel = NULL; GtkListStore *liststore = NULL; liststore = gtk_list_store_new (1, G_TYPE_STRING); // 1 column, of type String (this is a vararg list) GuiObject scrolled = gtk_scrolled_window_new (NULL, NULL); gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolled), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); my widget = gtk_tree_view_new_with_model (GTK_TREE_MODEL (liststore)); gtk_container_add (GTK_CONTAINER (scrolled), GTK_WIDGET (my widget)); gtk_widget_show (GTK_WIDGET (scrolled)); gtk_tree_view_set_rubber_banding (GTK_TREE_VIEW (my widget), allowMultipleSelection ? GTK_SELECTION_MULTIPLE : GTK_SELECTION_SINGLE); g_object_unref (liststore); // Destroys the widget after the list is destroyed _GuiObject_setUserData (my widget, me); /* nog een functie die je niet moet vergeten */ renderer = gtk_cell_renderer_text_new (); col = gtk_tree_view_column_new (); gtk_tree_view_column_pack_start (col, renderer, TRUE); gtk_tree_view_column_add_attribute (col, renderer, "text", 0); // zeroeth column if (header != NULL) gtk_tree_view_column_set_title (col, Melder_peekWcsToUtf8 (header)); gtk_tree_view_append_column (GTK_TREE_VIEW (my widget), col); g_object_set_data_full (G_OBJECT (my widget), "guiList", me, (GDestroyNotify) _GuiGtkList_destroyCallback); /* GtkCellRenderer *renderer; GtkTreeViewColumn *col; my widget = gtk_tree_view_new_with_model (GTK_TREE_MODEL (liststore)); renderer = gtk_cell_renderer_text_new (); col = gtk_tree_view_column_new (); gtk_tree_view_column_pack_start (col, renderer, TRUE); gtk_tree_view_column_add_attribute (col, renderer, "text", COL_ID); gtk_tree_view_column_set_title (col, " ID "); gtk_tree_view_append_column (GTK_TREE_VIEW (view), col); renderer = gtk_cell_renderer_text_new (); col = gtk_tree_view_column_new (); gtk_tree_view_column_pack_start (col, renderer, TRUE); gtk_tree_view_column_add_attribute (col, renderer, "text", COL_TYPE); gtk_tree_view_column_set_title (col, " Type "); gtk_tree_view_append_column (GTK_TREE_VIEW (view), col); renderer = gtk_cell_renderer_text_new (); col = gtk_tree_view_column_new (); gtk_tree_view_column_pack_start (col, renderer, TRUE); gtk_tree_view_column_add_attribute (col, renderer, "text", COL_NAME); gtk_tree_view_column_set_title (col, " Name "); gtk_tree_view_append_column (GTK_TREE_VIEW (view), col); */ sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (my widget)); if (allowMultipleSelection) { gtk_tree_selection_set_mode (sel, GTK_SELECTION_MULTIPLE); } else { gtk_tree_selection_set_mode (sel, GTK_SELECTION_SINGLE); } if (GTK_IS_BOX (parent)) { gtk_box_pack_start (GTK_BOX (parent), GTK_WIDGET (scrolled), TRUE, TRUE, 0); } g_signal_connect (sel, "changed", G_CALLBACK (_GuiGtkList_selectionChangedCallback), me); #elif win my widget = _Gui_initializeWidget (xmListWidgetClass, parent, L"list"); _GuiObject_setUserData (my widget, me); my widget -> window = CreateWindowEx (0, L"listbox", L"list", WS_CHILD | WS_BORDER | WS_VSCROLL | LBS_NOTIFY | WS_CLIPSIBLINGS | ( allowMultipleSelection ? LBS_EXTENDEDSEL : 0 ), my widget -> x, my widget -> y, my widget -> width, my widget -> height, my widget -> parent -> window, NULL, theGui.instance, NULL); SetWindowLongPtr (my widget -> window, GWLP_USERDATA, (LONG_PTR) my widget); SetWindowFont (my widget -> window, GetStockFont (ANSI_VAR_FONT), FALSE); /*if (MEMBER (my parent, ScrolledWindow)) { XtDestroyWidget (my widget -> parent -> motiff.scrolledWindow.horizontalBar); my widget -> parent -> motiff.scrolledWindow.horizontalBar = NULL; XtDestroyWidget (my widget -> parent -> motiff.scrolledWindow.verticalBar); my widget -> parent -> motiff.scrolledWindow.verticalBar = NULL; }*/ _GuiObject_position (my widget, left, right, top, bottom); #elif mac #if useCarbon my scrolled = XmCreateScrolledWindow (parent, "scrolled", NULL, 0); _GuiObject_position (my scrolled, left, right, top, bottom); my widget = _Gui_initializeWidget (xmListWidgetClass, my scrolled, L"list"); _GuiObject_setUserData (my widget, me); if (USE_MAC_LISTBOX_CONTROL) { CreateListBoxControl (my widget -> macWindow, & my widget -> rect, false, 1000, 1, true, true, CELL_HEIGHT, 400, false, NULL, & my widget -> nat.control.handle); GetControlData (my widget -> nat.control.handle, kControlEntireControl, kControlListBoxListHandleTag, sizeof (my macListHandle), & my macListHandle, NULL); SetControlReference (my widget -> nat.control.handle, (long) my widget); my widget -> isControl = TRUE; _GuiNativeControl_setFont (my widget, 0, 12); } else { Rect dataBounds = { 0, 0, 0, 1 }; Point cSize; SetPt (& cSize, my widget -> rect.right - my widget -> rect.left + 1, CELL_HEIGHT); static ListDefSpec listDefSpec; if (listDefSpec. u. userProc == NULL) { listDefSpec. defType = kListDefUserProcType; listDefSpec. u. userProc = mac_listDefinition; } CreateCustomList (& my widget -> rect, & dataBounds, cSize, & listDefSpec, my widget -> macWindow, false, false, false, false, & my macListHandle); SetListRefCon (my macListHandle, (long) my widget); } if (allowMultipleSelection) SetListSelectionFlags (my macListHandle, lExtendDrag | lNoRect); XtVaSetValues (my widget, XmNwidth, right > 0 ? right - left + 100 : 530, NULL); #else #endif #endif return my widget; } GuiObject GuiList_createShown (GuiObject parent, int left, int right, int top, int bottom, bool allowMultipleSelection, const wchar_t *header) { GuiObject widget = GuiList_create (parent, left, right, top, bottom, allowMultipleSelection, header); GuiObject_show (widget); return widget; } void GuiList_deleteAllItems (GuiObject widget) { #if gtk iam_list; my blockSelectionChangedCallback = true; GtkListStore *list_store = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (widget))); gtk_list_store_clear (list_store); my blockSelectionChangedCallback = false; #elif win ListBox_ResetContent (widget -> window); #elif mac #if useCarbon iam_list; _GuiMac_clipOnParent (widget); LDelRow (0, 0, my macListHandle); GuiMac_clipOff (); #else #endif #endif } void GuiList_deleteItem (GuiObject widget, long position) { #if gtk iam_list; my blockSelectionChangedCallback = true; GtkTreeIter iter; GtkTreeModel *tree_model = gtk_tree_view_get_model (GTK_TREE_VIEW (widget)); if (gtk_tree_model_iter_nth_child (tree_model, &iter, NULL, (gint) (position - 1))) { gtk_list_store_remove (GTK_LIST_STORE (tree_model), & iter); } my blockSelectionChangedCallback = false; #elif win ListBox_DeleteString (widget -> window, position - 1); #elif mac #if useCarbon iam_list; _GuiMac_clipOnParent (widget); LDelRow (1, position - 1, my macListHandle); GuiMac_clipOff (); long n = (** my macListHandle). dataBounds. bottom; XtVaSetValues (widget, XmNheight, n * CELL_HEIGHT, NULL); #else #endif #endif } void GuiList_deselectAllItems (GuiObject widget) { #if gtk iam_list; my blockSelectionChangedCallback = true; GtkTreeSelection *selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (widget)); gtk_tree_selection_unselect_all (selection); my blockSelectionChangedCallback = false; #elif win ListBox_SetSel (widget -> window, False, -1); #elif mac #if useCarbon iam_list; long n = (** my macListHandle). dataBounds. bottom; Cell cell; cell.h = 0; _GuiMac_clipOnParent (widget); for (long i = 0; i < n; i ++) { cell.v = i; LSetSelect (false, cell, my macListHandle); } GuiMac_clipOff (); #endif #endif } void GuiList_deselectItem (GuiObject widget, long position) { #if gtk iam_list; my blockSelectionChangedCallback = true; GtkTreeSelection *selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (widget)); /* GtkListStore *list_store = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (widget))); GtkTreePath *path = gtk_tree_path_new_from_indices ((gint) position);*/ GtkTreeIter iter; // gtk_tree_model_get_iter (GTK_TREE_MODEL (list_store), & iter, path); // gtk_tree_path_free (path); GtkTreeModel *tree_model = gtk_tree_view_get_model (GTK_TREE_VIEW(widget)); if (gtk_tree_model_iter_nth_child (tree_model, &iter, NULL, (gint) (position - 1))) { gtk_tree_selection_unselect_iter (selection, & iter); } my blockSelectionChangedCallback = false; #elif win ListBox_SetSel (widget -> window, False, position - 1); #elif mac #if useCarbon iam_list; Cell cell; cell. h = 0; cell. v = position - 1; _GuiMac_clipOnParent (widget); LSetSelect (false, cell, my macListHandle); GuiMac_clipOff (); #endif #endif } long * GuiList_getSelectedPositions (GuiObject widget, long *numberOfSelectedPositions) { *numberOfSelectedPositions = 0; long *selectedPositions = NULL; #if gtk GtkTreeSelection *selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (widget)); GtkListStore *list_store = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (widget))); int n = gtk_tree_selection_count_selected_rows (selection); if (n > 0) { GList *list = gtk_tree_selection_get_selected_rows (selection, (GtkTreeModel **) & list_store); long ipos = 1; *numberOfSelectedPositions = n; selectedPositions = NUMvector (1, *numberOfSelectedPositions); Melder_assert (selectedPositions != NULL); for (GList *l = g_list_first (list); l != NULL; l = g_list_next (l)) { gint *index = gtk_tree_path_get_indices ((GtkTreePath *) l -> data); selectedPositions [ipos] = index [0] + 1; ipos ++; } g_list_foreach (list, (GFunc) gtk_tree_path_free, NULL); g_list_free (list); // TODO: probably one big bug // Much nicer is: gtk_tree_selection_selected_foreach () // But requires a structure + function // Structure must contain the iterator (ipos) and // selectedPositions // fb: don't think that using the above function would be nicer, // the code is not that confusing -- 20100223 } return selectedPositions; #elif win int n = ListBox_GetSelCount (widget -> window), *indices; if (n == 0) { return selectedPositions; } if (n == -1) { // single selection int selection = ListBox_GetCurSel (widget -> window); if (selection == -1) return False; n = 1; indices = Melder_calloc_f (int, n); indices [0] = selection; } else { indices = Melder_calloc_f (int, n); ListBox_GetSelItems (widget -> window, n, indices); } *numberOfSelectedPositions = n; selectedPositions = NUMvector (1, *numberOfSelectedPositions); Melder_assert (selectedPositions != NULL); for (long ipos = 1; ipos <= *numberOfSelectedPositions; ipos ++) { selectedPositions [ipos] = indices [ipos - 1] + 1; // convert from zero-based list of zero-based indices } Melder_free (indices); #elif mac #if useCarbon iam_list; long n = (** my macListHandle). dataBounds. bottom; Cell cell; cell.h = 0; if (n < 1) { return selectedPositions; } selectedPositions = NUMvector (1, n); // probably too big (ergo, probably reallocable), but the caller will throw it away anyway for (long i = 1; i <= n; i ++) { cell. v = i - 1; if (LGetSelect (false, & cell, my macListHandle)) { selectedPositions [++ *numberOfSelectedPositions] = i; } } if (*numberOfSelectedPositions == 0) { NUMvector_free (selectedPositions, 1); selectedPositions = NULL; } #endif #endif return selectedPositions; } long GuiList_getBottomPosition (GuiObject widget) { #if gtk // TODO return 1; #elif win long bottom = ListBox_GetTopIndex (widget -> window) + widget -> height / ListBox_GetItemHeight (widget -> window, 0); if (bottom < 1) bottom = 1; long n = ListBox_GetCount (widget -> window); if (bottom > n) bottom = n; return bottom; #elif mac #if useCarbon iam_list; Melder_assert (widget -> parent -> widgetClass == xmScrolledWindowWidgetClass); GuiObject clipWindow = widget -> parent -> motiff.scrolledWindow.clipWindow; GuiObject workWindow = widget -> parent -> motiff.scrolledWindow.workWindow; long top = (clipWindow -> rect.top - workWindow -> rect.top + 5) / CELL_HEIGHT + 1; long visible = (clipWindow -> rect.bottom - clipWindow -> rect.top - 5) / CELL_HEIGHT + 1; long n = (** my macListHandle). dataBounds. bottom; if (visible > n) visible = n; long bottom = top + visible - 1; if (bottom < 1) bottom = 1; if (bottom > n) bottom = n; return bottom; #else return 1; // TODO #endif #endif } long GuiList_getNumberOfItems (GuiObject widget) { long numberOfItems = 0; #if gtk GtkTreeModel *model = gtk_tree_view_get_model (GTK_TREE_VIEW (widget)); numberOfItems = gtk_tree_model_iter_n_children (model, NULL); #elif win numberOfItems = ListBox_GetCount (widget -> window); #elif mac #if useCarbon iam_list; numberOfItems = (** my macListHandle). dataBounds. bottom; #else #endif #endif return numberOfItems; } long GuiList_getTopPosition (GuiObject widget) { #if gtk // TODO return 1; #elif win long top = ListBox_GetTopIndex (widget -> window); if (top < 1) top = 1; long n = ListBox_GetCount (widget -> window); if (top > n) top = 0; return top; #elif mac #if useCarbon iam_list; Melder_assert (widget -> parent -> widgetClass == xmScrolledWindowWidgetClass); GuiObject clipWindow = widget -> parent -> motiff.scrolledWindow.clipWindow; GuiObject workWindow = widget -> parent -> motiff.scrolledWindow.workWindow; long top = (clipWindow -> rect.top - workWindow -> rect.top + 5) / CELL_HEIGHT + 1; if (top < 1) top = 1; long n = (** my macListHandle). dataBounds. bottom; if (top > n) top = 0; return top; #else return 1; // TODO #endif #endif } void GuiList_insertItem (GuiObject widget, const wchar_t *itemText, long position) { /* * 'position' is the position of the new item in the list after insertion: * a value of 1 therefore puts the new item at the top of the list; * a value of 0 is special: the item is put at the bottom of the list. */ #if gtk iam_list; my blockSelectionChangedCallback = true; GtkListStore *list_store = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (widget))); gtk_list_store_insert_with_values (list_store, NULL, (gint) position - 1, COLUMN_STRING, Melder_peekWcsToUtf8 (itemText), -1); my blockSelectionChangedCallback = false; // TODO: Tekst opsplitsen // does GTK know the '0' trick? // it does know about NULL, to append in another function #elif win if (position) ListBox_InsertString (widget -> window, position - 1, itemText); // win lists start with item 0 else ListBox_AddString (widget -> window, itemText); // insert at end #elif mac #if useCarbon iam_list; long n = (** my macListHandle). dataBounds. bottom; if (position == 0) position = n + 1; // insert at end Cell cell; cell.h = 0; cell. v = position - 1; // mac lists start with item 0 _GuiMac_clipOnParent (widget); LAddRow (1, position - 1, my macListHandle); const char *itemText_utf8 = Melder_peekWcsToUtf8 (itemText); // although defProc will convert again... LSetCell (itemText_utf8, (short) strlen (itemText_utf8), cell, my macListHandle); (** my macListHandle). visible. bottom = n + 1; _GuiMac_clipOffInvalid (widget); XtVaSetValues (widget, XmNheight, (n + 1) * CELL_HEIGHT, NULL); #else #endif #endif } void GuiList_replaceItem (GuiObject widget, const wchar_t *itemText, long position) { #if gtk iam_list; my blockSelectionChangedCallback = true; GtkTreeIter iter; GtkTreeModel *tree_model = gtk_tree_view_get_model (GTK_TREE_VIEW (widget)); if (gtk_tree_model_iter_nth_child (tree_model, &iter, NULL, (gint) (position - 1))) { gtk_list_store_set (GTK_LIST_STORE (tree_model), & iter, COLUMN_STRING, Melder_peekWcsToUtf8 (itemText), -1); } my blockSelectionChangedCallback = false; /* GtkTreePath *path = gtk_tree_path_new_from_indices ((gint) position); GtkTreeIter iter; GtkListStore *list_store = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (widget))); gtk_tree_model_get_iter (GTK_TREE_MODEL (list_store), & iter, path); gtk_tree_path_free (path);*/ // gtk_list_store_set (list_store, & iter, 0, Melder_peekWcsToUtf8 (itemText), -1); // TODO: Tekst opsplitsen #elif win long nativePosition = position - 1; // convert from 1-based to zero-based ListBox_DeleteString (widget -> window, nativePosition); ListBox_InsertString (widget -> window, nativePosition, itemText); #elif mac #if useCarbon iam_list; _GuiMac_clipOnParent (widget); Cell cell; cell.h = 0; cell.v = position - 1; const char *itemText_utf8 = Melder_peekWcsToUtf8 (itemText); LSetCell (itemText_utf8, strlen (itemText_utf8), cell, my macListHandle); LDraw (cell, my macListHandle); GuiMac_clipOff (); #else #endif #endif } void GuiList_selectItem (GuiObject widget, long position) { #if gtk iam_list; my blockSelectionChangedCallback = true; GtkTreeSelection *selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (widget)); GtkTreePath *path = gtk_tree_path_new_from_indices ((gint) position - 1, -1); gtk_tree_selection_select_path(selection, path); gtk_tree_path_free (path); my blockSelectionChangedCallback = false; // TODO: check of het bovenstaande werkt, dan kan dit weg // GtkListStore *list_store = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (widget))); // GtkTreePath *path = gtk_tree_path_new_from_indices ((gint) position); // GtkTreeIter iter; // gtk_tree_model_get_iter (GTK_TREE_MODEL (list_store), & iter, path); // gtk_tree_selection_select_iter (selection, & iter); #elif win iam_list; if (! my allowMultipleSelection) { ListBox_SetCurSel (widget -> window, position - 1); } else { ListBox_SetSel (widget -> window, True, position - 1); } #elif mac #if useCarbon iam_list; Cell cell; cell.h = 0; _GuiMac_clipOnParent (widget); if (! my allowMultipleSelection) { long n = (** my macListHandle). dataBounds. bottom; for (long i = 0; i < n; i ++) if (i != position - 1) { cell.v = i; LSetSelect (false, cell, my macListHandle); } } cell.v = position - 1; LSetSelect (true, cell, my macListHandle); GuiMac_clipOff (); #else #endif #endif } void GuiList_setDoubleClickCallback (GuiObject widget, void (*callback) (void *boss, GuiListEvent event), void *boss) { GuiList me = (GuiList) _GuiObject_getUserData (widget); if (me != NULL) { my doubleClickCallback = callback; my doubleClickBoss = boss; } } void GuiList_setSelectionChangedCallback (GuiObject widget, void (*callback) (void *boss, GuiListEvent event), void *boss) { GuiList me = (GuiList) _GuiObject_getUserData (widget); if (me != NULL) { my selectionChangedCallback = callback; my selectionChangedBoss = boss; } } void GuiList_setTopPosition (GuiObject widget, long topPosition) { //Melder_casual ("Set top position %ld", topPosition); #if gtk // GtkListStore *list_store = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (widget))); GtkTreePath *path = gtk_tree_path_new_from_indices ((gint) topPosition); gtk_tree_view_scroll_to_cell (GTK_TREE_VIEW (widget), path, NULL, FALSE, 0.0, 0.0); gtk_tree_path_free (path); #elif win ListBox_SetTopIndex (widget -> window, topPosition - 1); #elif mac #if useCarbon iam_list; //_GuiMac_clipOnParent (widget); //LScroll (0, topPosition - (** my macListHandle). visible. top - 1, my macListHandle); // TODO: implement //GuiMac_clipOff (); //my scrolled -> motiff.scrolledWindow.verticalBar; // TODO: implement XtVaSetValues (widget, XmNy, - (topPosition - 1) * CELL_HEIGHT, NULL); #else #endif #endif } /* End of file GuiList.cpp */ sources_5316/sys/GraphicsPostscript.cpp0000644000176700017670000003255511747340510017114 0ustar paulpaul/* GraphicsPostscript.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include /* For 'floor' and 'ceil' in BoundingBox. */ #include /* For creation date. */ #include "GraphicsP.h" #include "Printer.h" Thing_implement (GraphicsPostscript, Graphics, 0); static void downloadPrologAndSetUp (GraphicsPostscript me) { /* * Procedures section of the document prolog: procedure definitions valid for all pages. */ my d_printf (my d_file, "%%%%BeginProlog\n"); my d_printf (my d_file, "%%%%BeginResource: procset (ppgb GraphicsPostscript procs) 1.0 0\n"); my d_printf (my d_file, "/N { newpath } bind def /M { newpath moveto } bind def /L { rlineto } bind def\n"); my d_printf (my d_file, "/F { 10 { 1 exch rlineto } repeat } bind def\n"); my d_printf (my d_file, "/C { 0 360 arc stroke } bind def /FC { 0 360 arc fill } bind def\n"); my d_printf (my d_file, "/PraatEncoding [\n" " /dotlessi/Aogonek/aogonek/Cacute/cacute/Ccaron/ccaron/Dcaron/dcaron/Dbar\n" " /dbar/Ecaron/ecaron/Eogonek/eogonek/Gcaron/gcaron/Lslash/lslash/Nacute\n" " /nacute/Ncaron/ncaron/Ohungarumlaut/ohungarumlaut/Rcaron/rcaron/Sacute/sacute/Scaron\n" " /scaron/Tcaron/space/exclam/quotedbl/numbersign/dollar/percent/ampersand/quotesinglright\n" " /parenleft/parenright/asterisk/plus/comma/hyphen/period/slash/zero/one\n" " /two/three/four/five/six/seven/eight/nine/colon/semicolon\n" " /less/equal/greater/question/at/A/B/C/D/E/F/G/H/I/J/K/L/M/N/O/P/Q/R/S/T/U/V/W/X/Y/Z\n" " /bracketleft/backslash/bracketright/asciicircum/underscore/quotesinglleft\n" " /a/b/c/d/e/f/g/h/i/j/k/l/m/n/o/p/q/r/s/t/u/v/w/x/y/z/braceleft/bar/braceright/asciitilde\n" " /Zdot/Adieresis/Aring/Ccedilla/Eacute/Ntilde/Odieresis/Udieresis/aacute/agrave/acircumflex\n" " /adieresis/atilde/aring/ccedilla/eacute/egrave/ecircumflex/edieresis/iacute/igrave/icircumflex\n"); my d_printf (my d_file, " /idieresis/ntilde/oacute/ograve/ocircumflex/odieresis/otilde/uacute/ugrave/ucircumflex/udieresis\n" " /dagger/degree/cent/sterling/section/bullet/paragraph/germandbls/registered/copyright/trademark\n" " /acute/dieresis/notequal/AE/Oslash/infinity/plusminus/lessequal/greaterequal/yen/mu\n" " /partialdiff/summation/product/pi/integral/ordfeminine/ordmasculine/Omega/ae/oslash\n" " /questiondown/exclamdown/logicalnot/radical/florin/approxequal/Delta/guillemotleft/guillemotright\n" " /ellipsis/zdot/Agrave/Atilde/Otilde/OE/oe/endash/emdash/quotedblleft/quotedblright\n" " /quoteleft/quoteright/divide/lozenge/ydieresis/Ydieresis/fraction/currency\n" " /guilsinglleft/guilsinglright/fi/fl/daggerdbl/periodcentered/quotesinglbase/quotedblbase\n" " /perthousand/Acircumflex/Ecircumflex/Aacute/Edieresis/Egrave/Iacute/Icircumflex/Idieresis\n" " /Igrave/Oacute/Ocircumflex/apple/Ograve/Uacute/Ucircumflex/Ugrave/tcaron\n" " /Uhungarumlaut/uhungarumlaut/Uring/uring/Yacute/yacute/Zacute/zacute/Zcaron/zcaron ] def\n"); my d_printf (my d_file, "/PraatEncode { /font exch def /base exch def\n" " /basedict base findfont def /new basedict maxlength dict def\n" " basedict { exch dup dup /FID ne exch /Encoding ne and\n" " { exch new 3 1 roll put } { pop pop } ifelse } forall\n" " new /FontName font put new /Encoding PraatEncoding put font new definefont pop } def\n"); my d_printf (my d_file, "%%%%EndResource\n"); my d_printf (my d_file, "%%%%EndProlog\n"); /* * Document setup: graphics state changes persistent across showpage calls. */ my d_printf (my d_file, "%%%%BeginSetup\n"); //my d_printf (my d_file, "%d %d { dup mul exch dup mul add 1.0 exch sub } setscreen\n", my spotsDensity, my spotsAngle); my d_printf (my d_file, "true setstrokeadjust\n"); my d_printf (my d_file, "%%%%EndSetup\n"); } static void initPage (GraphicsPostscript me) { ++ my pageNumber; if (my printer && my pageNumber > 1) downloadPrologAndSetUp (me); // has to be repeated for every page if (my job) { my d_printf (my d_file, "%%%%Page: %d %d\n", my pageNumber, my pageNumber); /*my d_printf (my d_file, "save\n");*/ my d_printf (my d_file, "%%%%BeginPageSetup\n"); } my d_printf (my d_file, "%g setlinewidth 2 setlinejoin\n", my resolution / 192.0); /* 0.375 point */ if (my job || my printer) { if (my landscape) my d_printf (my d_file, "%d 0 translate 90 rotate ", (int) (my paperHeight * 72 * my magnification)); } my d_printf (my d_file, "%.6g dup scale\n", 72.0 * my magnification / my resolution); if (my job) my d_printf (my d_file, "%%%%EndPageSetup\n"); my lastFid = NULL; } static void exitPage (GraphicsPostscript me) { int font, style; /* * A showpage is only needed if we are printing to a file. * If we are printing directly to a printer, the page will be ejected * by EndPage (Windows NT/2000/XP/Vista) or PMSessionEndPage (MacOSX). */ if (my d_file) { if (my job) { /*my d_printf (my d_file, "restore\n");*/ my d_printf (my d_file, "showpage\n"); } else if (my eps) { my d_printf (my d_file, "showpage %% redefined by encapsulating program\n"); } } for (font = 0; font <= kGraphics_font_DINGBATS; font ++) for (style = 0; style <= Graphics_BOLD_ITALIC; style ++) Melder_free (my fontInfos [font] [style]); my loadedXipa = FALSE; /* BUG. Include this because of the unpredictable page order with DSC? */ } void structGraphicsPostscript :: v_destroy () { exitPage (this); if (d_file) { if (job) { d_printf (d_file, "%%%%Trailer\n"); d_printf (d_file, "%%%%Pages: %d\n", pageNumber); } d_printf (d_file, "%%%%EOF\n"); // BUG. Correct according to DSC. But not good in EPS files? fclose (d_file); } GraphicsPostscript_Parent :: v_destroy (); } Graphics Graphics_create_postscriptjob (MelderFile file, int resolution, enum kGraphicsPostscript_spots spots, enum kGraphicsPostscript_paperSize paperSize, enum kGraphicsPostscript_orientation rotation, double magnification) { autoGraphicsPostscript me = Thing_new (GraphicsPostscript); time_t today; my postScript = true, my yIsZeroAtTheTop = true, my languageLevel = 2; my job = TRUE, my eps = FALSE, my printer = FALSE; my d_printf = (int (*)(void *, const char*, ...)) fprintf; Graphics_init (me.peek()); my resolution = resolution; /* Virtual resolution; may not be equal to that of the printer; */ /* there is no problem if this always equals 600 dpi. */ my photocopyable = spots == kGraphicsPostscript_spots_PHOTOCOPYABLE; if (my photocopyable) { my spotsDensity = 85; my spotsAngle = 35; } else { my spotsDensity = 106; my spotsAngle = 46; } if (paperSize == kGraphicsPostscript_paperSize_A3) my paperWidth = 842 / 72.0, my paperHeight = 1191 / 72.0; else if (paperSize == kGraphicsPostscript_paperSize_US_LETTER) my paperWidth = 612 / 72.0, my paperHeight = 792 / 72.0; else my paperWidth = 595 / 72.0, my paperHeight = 842 / 72.0; my landscape = rotation == kGraphicsPostscript_orientation_LANDSCAPE; my magnification = magnification; my includeFonts = TRUE; my d_file = Melder_fopen (file, "w"); /* * The Device Coordinates are the PostScript user coordinates. * They are chosen in such a way that a distance of 1 in device coordinates * equals one dot if the printer's resolution is 'resolution' dots per inch. * Take a sensible default margin: half an inch on all sides. */ my d_x1DC = my d_x1DCmin = resolution / 2; my d_x2DC = my d_x2DCmax = (my paperWidth - 0.5) * resolution; my d_y1DC = my d_y1DCmin = resolution / 2; my d_y2DC = my d_y2DCmax = (my paperHeight - 0.5) * resolution; /* * Now don't just set x1wNDC etc, but force computation of the scaling as well. */ Graphics_setWsWindow ((Graphics) me.peek(), 0, my paperWidth - 1.0, 13.0 - my paperHeight, 12.0); /* * We will adhere to version 3.0 of the Document Structuring Conventions for print jobs. */ my d_printf (my d_file, "%%!PS-Adobe-3.0\n"); my d_printf (my d_file, "%%%%Creator: Praat Shell 4.2\n"); my d_printf (my d_file, "%%%%Title: %s\n", Melder_peekWcsToUtf8 (MelderFile_name (file))); today = time (NULL); my d_printf (my d_file, "%%%%CreationDate: %s", ctime (& today)); /* Contains newline symbol. */ my d_printf (my d_file, "%%%%PageOrder: Special\n"); my d_printf (my d_file, "%%%%Pages: (atend)\n"); my d_printf (my d_file, "%%%%EndComments\n"); downloadPrologAndSetUp (me.peek()); initPage (me.peek()); return (Graphics) me.transfer(); } #if defined (macintosh) static int Eps_postScript_printf (void *stream, const char *format, ... ) { static char theLine [3002]; char *p; va_list args; va_start (args, format); vsprintf (theLine, format, args); va_end (args); for (p = theLine; *p != '\0'; p ++) if (*p == '\n') *p = '\r'; return fwrite (theLine, sizeof (char), strlen (theLine), reinterpret_cast (stream)); } #endif Graphics Graphics_create_epsfile (MelderFile file, int resolution, enum kGraphicsPostscript_spots spots, double x1inches, double x2inches, double y1inches, double y2inches, bool includeFonts, bool useSilipaPS) { autoGraphicsPostscript me = Thing_new (GraphicsPostscript); time_t today; int left, right, top, bottom; my postScript = true, my languageLevel = 2; my job = false, my eps = true, my printer = false; #if defined (macintosh) /* Replace newlines with carriage returns to be compatible with MS Word 5.1. */ my d_printf = Eps_postScript_printf; #else my d_printf = (int (*)(void *, const char*, ...)) fprintf; #endif Graphics_init (me.peek()); my resolution = resolution; /* Virtual resolution; may not be equal to that of the printer; */ /* there is no problem if this always equals 600 dpi. */ my photocopyable = spots == kGraphicsPostscript_spots_PHOTOCOPYABLE; if (my photocopyable) { my spotsDensity = 85; my spotsAngle = 35; } else { my spotsDensity = 106; my spotsAngle = 46; } my paperWidth = 7.5, my paperHeight = 11.0; my landscape = FALSE; my magnification = 1.0; my includeFonts = includeFonts; my useSilipaPS = useSilipaPS; my d_file = Melder_fopen (file, "w"); my d_x1DC = my d_x1DCmin = 0; my d_x2DC = my d_x2DCmax = my paperWidth * resolution; /* 600 dpi -> 4500 virtual dots */ my d_y1DC = my d_y1DCmin = 0; my d_y2DC = my d_y2DCmax = my paperHeight * resolution; /* 600 dpi -> 6600 virtual dots */ Graphics_setWsWindow ((Graphics) me.peek(), 0, my paperWidth, 12.0 - my paperHeight, 12.0); // force scaling /* * We will honour version 3.0 of the DSC for Encapsulated PostScript files, * which includes supplying the bounding box information. */ left = (int) floor (x1inches * 72); right = (int) ceil (x2inches * 72); top = (int) ceil ((y2inches - my d_y1wNDC) * 72); bottom = (int) floor ((y1inches - my d_y1wNDC) * 72); my d_printf (my d_file, "%%!PS-Adobe-3.0 EPSF-3.0\n"); my d_printf (my d_file, "%%%%BoundingBox: %d %d %d %d\n", left, bottom, right, top); my d_printf (my d_file, "%%%%Creator: Praat Shell 5.1\n"); /* * In an EPS file without screen preview, the file name will be visible anyway. * This leaves us room to show a warning that should keep users from thinking anything is wrong. */ my d_printf (my d_file, "%%%%Title: NO SCREEN PREVIEW, BUT WILL PRINT CORRECTLY\n"); today = time (NULL); my d_printf (my d_file, "%%%%CreationDate: %s", ctime (& today)); /* Contains newline symbol. */ my d_printf (my d_file, "%%%%EndComments\n"); downloadPrologAndSetUp (me.peek()); initPage (me.peek()); return (Graphics) me.transfer(); } #ifndef UNIX Graphics Graphics_create_postscriptprinter (void) { GraphicsPostscript me = Thing_new (GraphicsPostscript); my postScript = TRUE, my languageLevel = 2; my job = FALSE, my eps = FALSE, my printer = TRUE; my d_printf = Printer_postScript_printf; Graphics_init (me); my resolution = thePrinter. resolution; /* Virtual resolution. */ my photocopyable = thePrinter. spots == kGraphicsPostscript_spots_PHOTOCOPYABLE; if (my photocopyable) { my spotsDensity = 85; my spotsAngle = 35; } else { my spotsDensity = 106; my spotsAngle = 46; } my paperWidth = (double) thePrinter. paperWidth / my resolution; my paperHeight = (double) thePrinter. paperHeight / my resolution; my landscape = thePrinter. orientation == kGraphicsPostscript_orientation_LANDSCAPE; my magnification = thePrinter. magnification; my includeFonts = TRUE; my d_x1DC = my d_x1DCmin = my resolution / 2; my d_x2DC = my d_x2DCmax = (my paperWidth - 0.5) * my resolution; my d_y1DC = my d_y1DCmin = my resolution / 2; my d_y2DC = my d_y2DCmax = (my paperHeight - 0.5) * my resolution; Graphics_setWsWindow ((Graphics) me, 0, my paperWidth - 1.0, 13.0 - my paperHeight, 12.0); downloadPrologAndSetUp (me); initPage (me); return (Graphics) me; } #endif void Graphics_nextSheetOfPaper (Graphics graphics) { if (graphics -> postScript) { GraphicsPostscript me = static_cast (graphics); exitPage (me); if (my printer) Printer_nextPage (); initPage (me); } else if (graphics -> printer) { Printer_nextPage (); } } /* End of file GraphicsPostscript.cpp */ sources_5316/sys/praatP.h0000644000176700017670000001702311622337602014146 0ustar paulpaul/* praatP.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "praat.h" void praat_addActionScript (const wchar *className1, int n1, const wchar *className2, int n2, const wchar *className3, int n3, const wchar *title, const wchar *after, int depth, const wchar *script); /* No strings may be NULL; unspecify them by giving an empty string. 'title' and 'script' are deep-copied. */ void praat_removeAction_classNames (const wchar *className1, const wchar *className2, const wchar *className3, const wchar *title); /* No arguments may be NULL; unspecify them by giving an empty string. */ /* 'title' is deep-copied. */ void praat_hideAction (ClassInfo class1, ClassInfo class2, ClassInfo class3, const wchar *title); void praat_hideAction_classNames (const wchar *className1, const wchar *className2, const wchar *className3, const wchar *title); void praat_showAction (ClassInfo class1, ClassInfo class2, ClassInfo class3, const wchar_t *title); void praat_showAction_classNames (const wchar *className1, const wchar *className2, const wchar *className3, const wchar *title); void praat_sortActions (); void praat_addMenuCommandScript (const wchar *window, const wchar *menu, const wchar *title, const wchar *after, int depth, const wchar *script); /* All strings are deep-copied and may not be NULL; unspecify them by giving an empty string. */ /* For the Praat objects window: 'window' is "Objects", 'menu' is "Praat", "New", "Open", "Help", "Preferences", or "Goodies". For the Praat picture window: 'window' is "Picture", 'menu' is "File", "Edit", "Margins", "World", "Select", "Pen", "Font", or "Help". */ void praat_hideMenuCommand (const wchar *window, const wchar *menu, const wchar *title); void praat_showMenuCommand (const wchar *window, const wchar *menu, const wchar *title); void praat_saveMenuCommands (FILE *f); void praat_addFixedButtonCommand (GuiObject parent, const wchar *title, void (*callback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *), int x, int y); void praat_sensitivizeFixedButtonCommand (const wchar *title, int sensitive); void praat_sortMenuCommands (); #define praat_MAXNUM_MENUS 20 /* Maximum number of added New, Open, Save, or Help menus. */ #define praat_MAXNUM_FILE_TYPE_RECOGNIZERS 50 /* File types recognizable by 'Read from file...'. */ typedef struct structPraat_Command { ClassInfo class1, class2, class3, class4; // selected classes short n1, n2, n3, n4; // number of selected objects of each class; 0 means "any number" const wchar *title; // button text = command text void (*callback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure); // multi-purpose /* If both sendingForm and sendingString are NULL, this routine is an activate callback; you should directly execute the command, or call UiForm_do(dialog) if you need arguments; UiForm_do will call this routine again with sendingForm = dialog. */ /* If sendingForm exists, this routine is an ok callback, and you should execute the command. */ /* If sendingString exists (apparently from a command file), UiForm_parseString should be called, which will call this routine again with sendingForm. */ /* All of these things are normally taken care of by the macros defined in praat.h. */ signed char visible, /* Selected classes match class1, class2, and class3? */ executable, /* Command actually executable? Button not grey? */ depth, /* 1 = subcommand */ hidden, toggled, phase, unhidable, attractive; GuiObject button; const wchar *window, *menu; const wchar *script; // if 'callback' equals DO_RunTheScriptFromAnyAddedMenuCommand const wchar *after; // title of previous command, often NULL long uniqueID; // for sorting the added commands long sortingTail; } *praat_Command; #define praat_STARTING_UP 1 #define praat_READING_BUTTONS 2 #define praat_HANDLING_EVENTS 3 long praat_getIdOfSelected (ClassInfo klas, int inplace); wchar * praat_getNameOfSelected (ClassInfo klas, int inplace); int praat_selection (ClassInfo klas); /* How many objects of this class (excluding subclasses) are currently selected? */ /* Used by praat.cpp; defined in praat_picture.cpp. */ void praat_picture_init (); void praat_picture_exit (); void praat_picture_prefs (); void praat_picture_prefsChanged (); /* Praat shell tells Picture window that preferences have been changed (after reading the prefs file). Picture window will update the font menu. */ GuiObject praat_picture_resolveMenu (const wchar *menu); void praat_picture_background (); void praat_picture_foreground (); /* The following routines are a bit private (used by praat_script.c). */ /* If you must call them, follow them by praat_show (). */ void praat_deselect (int i); void praat_deselectAll (); void praat_select (int i); void praat_selectAll (); void praat_list_background (); void praat_list_foreground (); // updates the list of objects after backgrounding void praat_background (); void praat_foreground (); Editor praat_findEditorFromString (const wchar_t *string); void praat_showLogo (int autoPopDown); /* Communication with praat_menuCommands.cpp: */ void praat_menuCommands_init (); void praat_menuCommands_exit (); int praat_doMenuCommand (const wchar *command, const wchar *arguments, Interpreter interpreter); // 0 = not found long praat_getNumberOfMenuCommands (); praat_Command praat_getMenuCommand (long i); /* Communication with praat_actions.cpp: */ void praat_actions_show (); void praat_actions_createWriteMenu (GuiObject bar); void praat_actions_init (); // creates space for action commands void praat_actions_createDynamicMenu (GuiObject form, int leftOffset); void praat_saveAddedActions (FILE *f); int praat_doAction (const wchar *command, const wchar *arguments, Interpreter interpreter); // 0 = not found long praat_getNumberOfActions (); // for ButtonEditor praat_Command praat_getAction (long i); // for ButtonEditor /* Communication with praat_statistics.cpp: */ void praat_statistics_prefs (); // at init time void praat_statistics_prefsChanged (); // after reading prefs file void praat_statistics_exit (); // at exit time void praat_memoryInfo (); /* Communication with praat_objectMenus.cpp: */ GuiObject praat_objects_resolveMenu (const wchar *menu); void praat_addFixedButtons (GuiObject form); void praat_addMenus (GuiObject bar); void praat_addMenus2 (); void praat_cleanUpName (wchar *name); void praat_list_renameAndSelect (int position, const wchar *name); extern struct PraatP { int dontUsePictureWindow; // see praat_dontUsePictureWindow () char *title; GuiObject topBar, menuBar; int phase; Editor editor; // scripting environment } praatP; struct autoPraatBackground { autoPraatBackground () { praat_background (); } ~autoPraatBackground () { try { praat_foreground (); } catch (...) { Melder_clearError (); } } }; /* End of file praatP.h */ sources_5316/sys/Interpreter_decl.h0000644000176700017670000000160511611104702016177 0ustar paulpaul#ifndef _Interpreter_decl_h_ #define _Interpreter_decl_h_ /* Interpreter_decl.h * * Copyright (C) 1993-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ Thing_declare (Interpreter); /* End of file Interpreter_decl.h */ #endif sources_5316/sys/GuiText.cpp0000644000176700017670000016346211753744765014675 0ustar paulpaul/* GuiText.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2003/12/30 this file separated from motifEmulator.c * pb 2004/01/01 Mac: MLTE * pb 2004/03/11 Mac: tried to make compatible with MacOS X 10.1.x * pb 2005/09/01 Mac: GuiText_undo and GuiText_redo * pb 2006/10/29 Mac: erased MacOS 9 stuff * pb 2006/11/10 comments * pb 2007/02/15 Mac: GuiText_updateChangeCountAfterSave * pb 2007/05/30 GuiText_getStringW * pb 2007/05/31 Mac: CreateEditUnicodeTextControl * pb 2007/06/01 Mac: erased TextEdit stuff as well as changeCount * pb 2007/06/11 GuiText_getSelectionW, GuiText_replaceW * pb 2007/06/12 let command-key combinations pass through * pb 2007/12/15 erased ASCII versions * pb 2007/12/25 Gui * sdk 2007/12/27 first GTK version * pb 2008/10/05 better implicit selection (namely, none) * fb 2010/02/23 GTK * fb 2010/02/26 GTK & GuiText_set(Undo|Redo)Item() & history for GTK * fb 2010/03/02 history: merge same events together * pb 2010/03/11 support Unicode values above 0xFFFF * pb 2010/05/14 GTK changedCallback * pb 2010/05/30 GTK selections * pb 2010/11/28 removed Motif * pb 2011/04/06 C++ */ #include "GuiP.h" #undef iam #define iam(x) x me = (x) void_me #if win || mac && useCarbon #define iam_text \ Melder_assert (widget -> widgetClass == xmTextWidgetClass); \ GuiText me = (GuiText) widget -> userData #else #define iam_text \ GuiText me = (GuiText) _GuiObject_getUserData (widget) #endif #if !mac #if gtk typedef gchar * history_data; #elif win typedef char * history_data; #endif typedef struct _history_entry_s history_entry; struct _history_entry_s { history_entry *prev, *next; long first, last; history_data text; bool type_del : 1; }; #endif typedef struct structGuiText { GuiObject widget; void (*changeCallback) (void *boss, GuiTextEvent event); void *changeBoss; #if mac TXNObject macMlteObject; TXNFrameID macMlteFrameId; #else history_entry *prev, *next; GuiObject undo_item, redo_item; bool history_change : 1; #endif #if win || mac bool editable; #endif } *GuiText; #if win || mac && useCarbon #if mac #define isTextControl(w) ((w) -> isControl != 0) #define isMLTE(w) ((w) -> macMlteObject != NULL) #endif #if win static HFONT font10, font12, font14, font18, font24; #endif /* * (1) KEYBOARD FOCUS * * (1.1) In Motif, the native GUI system handles all that we want: * every window with text widgets has one text focus widget, * which will receive global text focus when the window is activated. * The global text focus is visible to the user. * The focus changes whenever the user clicks in a text widget that does not have focus. * * (1.2) In Windows, the native GUI system handles almost all of the above. * The exception is that windows have no own text focus widgets; * there is only a single global text focus. This means that when the user * clicks on a non-active window, none of the text widgets in this window * will automatically receive text focus. Yet, the user expects automatic text focus behaviour * (click a window, then type immediately) in text edit windows (like Praat's script editor) * and in windows that have a single text widget (like Praat's TextGrid editor). * For this reason, the WM_COMMAND message handler in Gui.c intercepts the EN_SETFOCUS notification. * This handler calls _GuiText_handleFocusReception (), which records * the new text focus widget in its window. When a window is activated, * we set the global focus explicitly to this window's own text focus widget, * by calling _GuiText_setTheTextFocus (). * * (1.3) On Macintosh, we have to handle all of this explicitly. * * (1.4) On Win and Mac, we implement a feature not available in Motif: * the use of Command-X, Command-C, and Command-V to cut, copy, and paste in text widgets, * even in dialogs, where there are no menus for which these three commands could be keyboard shortcuts. * For this reason, _GuiText_handleFocusReception () also stores the global text focus, * so that the keyboard shortcut handler in Gui.c knows what widget to cut from, copy from, or paste into. * (It is true that Windows itself stores the global text focus, but this is not always a text widget; * we want it to always be a text widget, e.g. in the TextGrid editor it is always the text widget, * never the drawing area, that receives key strokes. In Motif, we will have to program this text * preference explicitly; see the discussion in FunctionEditor.c.) */ void _GuiText_handleFocusReception (GuiObject widget) { /* * On Windows, this is called: * 1. on a user click in a text widget: WM_COMMAND -> EN_SETFOCUS; * 2. on window activation: _GuiText_setTheTextFocus () -> SetFocus -> WM_COMMAND -> EN_SETFOCUS; * 3. on a user click in a push button or toggle button, which would otherwise draw the * focus away from the text widgets: WM_COMMAND -> _GuiText_setTheTextFocus (). * * On Macintosh, this is called: * 1. on a user click in a text widget: handleControlClick & handleTextEditClick -> _GuiText_setTheTextFocus (); * 2. on window activation: handleActivateEvent -> _GuiText_setTheTextFocus (). */ widget -> shell -> textFocus = widget; /* see (1.2) */ theGui.textFocus = widget; /* see (1.4) */ } void _GuiText_handleFocusLoss (GuiObject widget) { /* * me is going out of sight; * it must stop having global focus. */ /* * On Windows, this is called: * 1. on window deactivation * 2. on window closure * 3. on text unmanaging * 4. on window unmanaging * * On Macintosh, this is called: * 1. on window deactivation * 2. on window closure * 3. on text unmanaging * 4. on window unmanaging */ if (widget == theGui.textFocus) theGui.textFocus = NULL; } #if mac void _GuiMac_clearTheTextFocus (void) { if (theGui.textFocus) { GuiText textFocus = (GuiText) theGui.textFocus -> userData; _GuiMac_clipOnParent (theGui.textFocus); if (isTextControl (theGui.textFocus)) { ClearKeyboardFocus (theGui.textFocus -> macWindow); } else if (isMLTE (textFocus)) { TXNFocus (textFocus -> macMlteObject, 0); TXNActivate (textFocus -> macMlteObject, textFocus -> macMlteFrameId, 0); } GuiMac_clipOff (); _GuiText_handleFocusLoss (theGui.textFocus); } } #endif void _GuiText_setTheTextFocus (GuiObject widget) { if (widget == NULL || theGui.textFocus == widget || ! widget -> managed) return; /* Perhaps not-yet-managed. Test: open Praat's DataEditor with a Sound, then type. */ #if gtk gtk_widget_grab_focus (GTK_WIDGET (widget)); #elif win SetFocus (widget -> window); /* Will send an EN_SETFOCUS notification, which will call _GuiText_handleFocusReception (). */ #elif mac iam_text; _GuiMac_clearTheTextFocus (); _GuiMac_clipOnParent (widget); if (isTextControl (widget)) { SetKeyboardFocus (widget -> macWindow, widget -> nat.control.handle, kControlEditTextPart); } else if (isMLTE (me)) { TXNActivate (my macMlteObject, my macMlteFrameId, 1); TXNFocus (my macMlteObject, 1); } GuiMac_clipOff (); _GuiText_handleFocusReception (widget); #endif } /* * CHANGE NOTIFICATION */ void _GuiText_handleValueChanged (GuiObject widget) { iam_text; if (my changeCallback) { struct structGuiTextEvent event = { widget }; my changeCallback (my changeBoss, & event); } } /* * EVENT HANDLING */ #if mac int _GuiMacText_tryToHandleReturnKey (EventHandlerCallRef eventHandlerCallRef, EventRef eventRef, GuiObject widget, EventRecord *event) { if (widget && widget -> activateCallback) { widget -> activateCallback (widget, widget -> activateClosure, (XtPointer) event); return 1; } return 0; /* Not handled. */ } int _GuiMacText_tryToHandleClipboardShortcut (EventHandlerCallRef eventHandlerCallRef, EventRef eventRef, GuiObject widget, unsigned char charCode, EventRecord *event) { if (widget) { iam_text; if (isTextControl (widget)) { if (charCode == 'X' || charCode == 'C' || charCode == 'V') { if (! my editable && (charCode == 'X' || charCode == 'V')) return 0; CallNextEventHandler (eventHandlerCallRef, eventRef); _GuiText_handleValueChanged (widget); return 1; } } else if (isMLTE (me)) { if (charCode == 'X' && my editable) { if (event -> what != autoKey) GuiText_cut (widget); return 1; } if (charCode == 'C') { if (event -> what != autoKey) GuiText_copy (widget); return 1; } if (charCode == 'V' && my editable) { GuiText_paste (widget); return 1; } } } return 0; /* Not handled. */ } int _GuiMacText_tryToHandleKey (EventHandlerCallRef eventHandlerCallRef, EventRef eventRef, GuiObject widget, unsigned char keyCode, unsigned char charCode, EventRecord *event) { (void) keyCode; if (widget) { iam_text; if (my editable) { _GuiMac_clipOnParent (widget); //Melder_casual ("char code %d", charCode); if (isTextControl (widget)) { CallNextEventHandler (eventHandlerCallRef, eventRef); } else if (isMLTE (me)) { //static long key = 0; Melder_casual ("key %ld", ++key); //TXNKeyDown (my macMlteObject, event); // Tends never to be called. CallNextEventHandler (eventHandlerCallRef, eventRef); } GuiMac_clipOff (); if (charCode > 31 || charCode < 28) { // arrows do not change the value of the text _GuiText_handleValueChanged (widget); } return 1; } } return 0; /* Not handled. */ } void _GuiMacText_handleClick (GuiObject widget, EventRecord *event) { iam_text; _GuiText_setTheTextFocus (widget); _GuiMac_clipOnParent (widget); if (isTextControl (widget)) { HandleControlClick (widget -> nat.control.handle, event -> where, event -> modifiers, NULL); } else if (isMLTE (me)) { LocalToGlobal (& event -> where); TXNClick (my macMlteObject, event); /* Handles text selection and scrolling. */ GlobalToLocal (& event -> where); } GuiMac_clipOff (); } #endif /* * LAYOUT */ #if mac void _GuiMacText_move (GuiObject widget) { iam_text; if (isTextControl (widget)) { _GuiMac_clipOnParent (widget); MoveControl (widget -> nat.control.handle, widget -> rect.left + 3, widget -> rect.top + 3); _GuiMac_clipOffValid (widget); } else if (isMLTE (me)) { TXNSetFrameBounds (my macMlteObject, widget -> rect. top, widget -> rect. left, widget -> rect. bottom, widget -> rect. right, my macMlteFrameId); } } void _GuiMacText_shellResize (GuiObject widget) { iam_text; /* * Shell erasure, and therefore text erasure, has been handled by caller. * Reshowing will be handled by caller. */ if (isTextControl (widget)) { MoveControl (widget -> nat.control.handle, widget -> rect.left + 3, widget -> rect.top + 3); SizeControl (widget -> nat.control.handle, widget -> width - 6, widget -> height - 6); /* * Control reshowing will explicitly be handled by caller. */ } else if (isMLTE (me)) { TXNSetFrameBounds (my macMlteObject, widget -> rect. top, widget -> rect. left, widget -> rect. bottom, widget -> rect. right, my macMlteFrameId); } } void _GuiMacText_resize (GuiObject widget) { iam_text; if (isTextControl (widget)) { SizeControl (widget -> nat.control.handle, widget -> width - 6, widget -> height - 6); /* * Container widgets will have been invalidated. * So in order not to make the control flash, we validate it. */ _Gui_validateWidget (widget); } else if (isMLTE (me)) { TXNSetFrameBounds (my macMlteObject, widget -> rect. top, widget -> rect. left, widget -> rect. bottom, widget -> rect. right, my macMlteFrameId); } } #endif void _GuiText_unmanage (GuiObject widget) { #if win _GuiText_handleFocusLoss (widget); _GuiNativeControl_hide (widget); #elif mac iam_text; /* * Just _GuiText_handleFocusLoss () is not enough, * because that can leave a visible blinking cursor. */ if (isTextControl (widget)) { if (widget == theGui.textFocus) _GuiMac_clearTheTextFocus (); /* Remove visible blinking cursor. */ _GuiNativeControl_hide (widget); } else if (isMLTE (me)) { } #endif /* * The caller will set the unmanage flag to zero, and remanage the parent. */ } /* * VISIBILITY */ #if win void _GuiWinText_destroy (GuiObject widget) { if (widget == theGui.textFocus) theGui.textFocus = NULL; // remove dangling reference if (widget == widget -> shell -> textFocus) widget -> shell -> textFocus = NULL; // remove dangling reference iam_text; DestroyWindow (widget -> window); Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiWinText_map (GuiObject widget) { iam_text; ShowWindow (widget -> window, SW_SHOW); } #elif mac void _GuiMacText_destroy (GuiObject widget) { if (widget == theGui.textFocus) theGui.textFocus = NULL; // remove dangling reference if (widget == widget -> shell -> textFocus) widget -> shell -> textFocus = NULL; // remove dangling reference iam_text; if (isTextControl (widget)) { _GuiMac_clipOnParent (widget); DisposeControl (widget -> nat.control.handle); GuiMac_clipOff (); } else if (isMLTE (me)) { TXNDeleteObject (my macMlteObject); } Melder_free (me); // NOTE: my widget is not destroyed here } void _GuiMacText_update (GuiObject widget) { iam_text; _GuiMac_clipOnParent (widget); if (isTextControl (widget)) { Draw1Control (widget -> nat.control.handle); } else if (isMLTE (me)) { TXNDraw (my macMlteObject, NULL); } GuiMac_clipOff (); } void _GuiMacText_map (GuiObject widget) { iam_text; if (isTextControl (widget)) { _GuiNativeControl_show (widget); } else if (isMLTE (me)) { } } #endif #endif #if mac && useCarbon || win static long NativeText_getLength (GuiObject widget) { #if win return Edit_GetTextLength (widget -> window); #elif mac iam_text; if (isTextControl (widget)) { Size size; CFStringRef cfString; GetControlData (widget -> nat.control.handle, kControlEntireControl, kControlEditTextCFStringTag, sizeof (CFStringRef), & cfString, NULL); size = CFStringGetLength (cfString); CFRelease (cfString); return size; } else if (isMLTE (me)) { #if 1 /* * From the reference page of TXNDataSize: * "If you are using Unicode and you want to know the number of characters, * divide the returned ByteCount value by sizeof(UniChar) or 2, * since MLTE uses the 16-bit Unicode Transformation Format (UTF-16)." */ return TXNDataSize (my macMlteObject) / sizeof (UniChar); #else long length = 0, dataSize = TXNDataSize (my macMlteObject); ItemCount numberOfRuns; TXNCountRunsInRange (my macMlteObject, 0, dataSize, & numberOfRuns); for (long irun = 0; irun < numberOfRuns; irun ++) { unsigned long left, right; TXNDataType dataType; TXNGetIndexedRunInfoFromRange (my macMlteObject, irun, 0, dataSize, & left, & right, & dataType, 0, NULL); if (dataType == kTXNTextData || dataType == kTXNUnicodeTextData) { Handle han; TXNGetDataEncoded (my macMlteObject, left, right, & han, kTXNUnicodeTextData); if (han) { long size = GetHandleSize (han) / 2; length += size; DisposeHandle (han); } } } return length; #endif } return 0; // Should not occur. #endif } static void NativeText_getText (GuiObject widget, wchar_t *buffer, long length) { #if win GetWindowText (widget -> window, buffer, length + 1); #elif mac iam_text; if (isTextControl (widget)) { CFStringRef cfString; GetControlData (widget -> nat.control.handle, kControlEntireControl, kControlEditTextCFStringTag, sizeof (CFStringRef), & cfString, NULL); UniChar *macText = Melder_malloc_f (UniChar, length + 1); CFRange range = { 0, length }; CFStringGetCharacters (cfString, range, macText); CFRelease (cfString); long j = 0; for (long i = 0; i < length; i ++) { unsigned long kar = macText [i]; if (kar < 0xD800 || kar > 0xDFFF) { buffer [j ++] = kar; } else { Melder_assert (kar >= 0xD800 && kar <= 0xDBFF); unsigned long kar1 = macText [++ i]; Melder_assert (kar1 >= 0xDC00 && kar1 <= 0xDFFF); buffer [j ++] = 0x10000 + ((kar & 0x3FF) << 10) + (kar1 & 0x3FF); } } buffer [j] = '\0'; Melder_free (macText); } else if (isMLTE (me)) { #if 1 Handle han; TXNGetDataEncoded (my macMlteObject, 0, length, & han, kTXNUnicodeTextData); long j = 0; for (long i = 0; i < length; i ++) { unsigned long kar = ((UniChar *) *han) [i]; if (kar < 0xD800 || kar > 0xDFFF) { buffer [j ++] = kar; } else { Melder_assert (kar >= 0xD800 && kar <= 0xDBFF); unsigned long kar1 = ((UniChar *) *han) [++ i]; Melder_assert (kar1 >= 0xDC00 && kar1 <= 0xDFFF); buffer [j ++] = 0x10000 + ((kar & 0x3FF) << 10) + (kar1 & 0x3FF); } } buffer [j] = '\0'; DisposeHandle (han); #else long dataSize = TXNDataSize (my macMlteObject); ItemCount numberOfRuns; TXNCountRunsInRange (my macMlteObject, 0, dataSize, & numberOfRuns); for (long irun = 0; irun < numberOfRuns; irun ++) { unsigned long left, right; TXNDataType dataType; TXNGetIndexedRunInfoFromRange (my macMlteObject, irun, 0, dataSize, & left, & right, & dataType, 0, NULL); if (dataType == kTXNTextData || dataType == kTXNUnicodeTextData) { Handle han; TXNGetDataEncoded (my macMlteObject, left, right, & han, kTXNUnicodeTextData); if (han) { long size = GetHandleSize (han) / 2; wcsncpy (buffer, (wchar_t *) *han, size); buffer += size; DisposeHandle (han); } } } buffer [0] = '\0'; return; #endif } #endif buffer [length] = '\0'; // superfluous? } /* * SELECTION */ static int NativeText_getSelectionRange (GuiObject widget, long *out_left, long *out_right) { unsigned long left, right; #ifndef unix Melder_assert (MEMBER (widget, Text)); #endif #if win SendMessage (widget -> window, EM_GETSEL, (WPARAM) & left, (LPARAM) & right); // 32-bit (R&N: 579) #elif mac iam_text; if (isTextControl (widget)) { ControlEditTextSelectionRec rec; GetControlData (widget -> nat.control.handle, kControlEntireControl, kControlEditTextSelectionTag, sizeof (rec), & rec, NULL); left = rec.selStart; right = rec. selEnd; } else if (isMLTE (me)) { TXNGetSelection (my macMlteObject, & left, & right); } #endif if (out_left) *out_left = left; if (out_right) *out_right = right; return right > left; } /* * PACKAGE */ void _GuiText_init (void) { #if mac //short font; TXNMacOSPreferredFontDescription defaults = { 0 }; //GetFNum ("\006Monaco", & font); //defaults. fontID = font; defaults. pointSize = 0x000B0000; defaults. fontStyle = kTXNDefaultFontStyle; defaults. encoding = /*kTXNMacOSEncoding*/ kTXNSystemDefaultEncoding; TXNInitTextension (& defaults, 1, 0); #endif } void _GuiText_exit (void) { #if mac TXNTerminateTextension (); #endif } #endif #if !mac /* * Undo/Redo history functions */ static void _GuiText_delete(GuiObject widget, int from_pos, int to_pos) { #if gtk if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gtk_editable_delete_text (GTK_EDITABLE (widget), from_pos, to_pos); } else { GtkTextBuffer *buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); GtkTextIter from_it, to_it; gtk_text_buffer_get_iter_at_offset(buffer, &from_it, from_pos); gtk_text_buffer_get_iter_at_offset(buffer, &to_it, to_pos); gtk_text_buffer_delete_interactive(buffer, &from_it, &to_it, gtk_text_view_get_editable(GTK_TEXT_VIEW(widget))); gtk_text_buffer_place_cursor(buffer, &to_it); } #elif win #endif } static void _GuiText_insert(GuiObject widget, int from_pos, int to_pos, const history_data text) { #if gtk if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gint from_pos_gint = from_pos; gtk_editable_insert_text (GTK_EDITABLE (widget), text, to_pos - from_pos, &from_pos_gint); } else { GtkTextBuffer *buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); GtkTextIter it; gtk_text_buffer_get_iter_at_offset(buffer, &it, from_pos); gtk_text_buffer_insert_interactive(buffer, &it, text, to_pos - from_pos, gtk_text_view_get_editable(GTK_TEXT_VIEW(widget))); gtk_text_buffer_get_iter_at_offset(buffer, &it, to_pos); gtk_text_buffer_place_cursor(buffer, &it); } #elif win #endif } /* Tests the previous elements of the history for mergability with the one to insert given via parameters. * If successful, it returns a pointer to the last valid entry in the merged history list, otherwise * returns NULL. * Specifically the function expands the previous insert/delete event(s) * - with the current, if current also is an insert/delete event and the ranges of previous and current event match * - with the previous delete and current insert event, in case the ranges of both event-pairs respectively match */ static history_entry * history_addAndMerge(void *void_me, history_data text_new, long first, long last, bool deleted) { iam(GuiText); history_entry *he = NULL; if (!(my prev)) return NULL; if (my prev->type_del == deleted) { // extend the last history event by this one if (my prev->first == last) { // most common for backspace key presses he = my prev; text_new = (char *) realloc(text_new, sizeof(*text_new) * (he->last - first + 1)); memcpy(text_new + last - first, he->text, sizeof(*text_new) * (he->last - he->first + 1)); free(he->text); he->text = text_new; he->first = first; } else if (my prev->last == first) { // most common for ordinary text insertion he = my prev; he->text = (char *) realloc(he->text, sizeof(*he->text) * (last - he->first + 1)); memcpy(he->text + he->last - he->first, text_new, sizeof(*he->text) * (last - first + 1)); free(text_new); he->last = last; } else if (deleted && my prev->first == first) { // most common for delete key presses he = my prev; he->text = (char *) realloc(he->text, sizeof(*he->text) * (last - first + he->last - he->first + 1)); memcpy(he->text + he->last - he->first, text_new, sizeof(*he->text) * (last - first + 1)); free(text_new); he->last = last + he->last - he->first; } } else { // prev->type_del != deleted, no simple expansion possible, check for double expansion if (!deleted && my prev->prev && my prev->prev->prev) { history_entry *del_one = my prev; history_entry *ins_mult = del_one->prev; history_entry *del_mult = ins_mult->prev; long from1 = del_mult->first, to1 = del_mult->last; long from2 = ins_mult->first, to2 = ins_mult->last; long from3 = del_one->first, to3 = del_one->last; if (from3 == first && to3 == last && from2 == from1 && to2 == to1 && to1 == first && !ins_mult->type_del && del_mult->type_del) { // most common for overwriting text /* So the layout is as follows: * * del_mult ins_mult del_one current (parameters) * [del, from1, to1, "uvw"] [ins, from1, to1, "abc"] [del, to1, to3, "x"] [ins, to1, to3, "d"] * n >= 1 characters n characters 1 character 1 character * * So merge those four events into two events by expanding del_mult by del_one and ins_mult by current */ del_mult->text = (char *) realloc(del_mult->text, sizeof(*del_mult->text) * (to3 - from1 + 1)); ins_mult->text = (char *) realloc(ins_mult->text, sizeof(*ins_mult->text) * (to3 - from1 + 1)); memcpy(del_mult->text + to1 - from1, del_one->text, sizeof(*del_mult->text) * (to3 - to1 + 1)); memcpy(ins_mult->text + to1 - from1, text_new , sizeof(*del_mult->text) * (to3 - to1 + 1)); del_mult->last = to3; ins_mult->last = to3; free(del_one->text); free(del_one); free(text_new); my prev = he = ins_mult; } } } return he; } /* Inserts a new history action, thereby removing any remaining 'redo' steps; * text_new a newly allocated string that will be freed by a history function * (history_add or history_clear) */ static void history_add(void *void_me, history_data text_new, long first, long last, bool deleted) { iam(GuiText); // delete all newer entries; from here on there is no 'Redo' until the next 'Undo' is performed history_entry *old_hnext = my next, *hnext; while (old_hnext) { hnext = old_hnext->next; free(old_hnext->text); free(old_hnext); old_hnext = hnext; } my next = NULL; history_entry *he = history_addAndMerge(void_me, text_new, first, last, deleted); if (he == NULL) { he = (history_entry *) malloc(sizeof(history_entry)); he->first = first; he->last = last; he->type_del = deleted; he->text = text_new; he->prev = my prev; he->next = NULL; if (my prev) my prev->next = he; } my prev = he; he->next = NULL; if (my undo_item) GuiObject_setSensitive(my undo_item, TRUE); if (my redo_item) GuiObject_setSensitive(my redo_item, FALSE); } static bool history_has_undo(void *void_me) { iam(GuiText); return my prev != NULL; } static bool history_has_redo(void *void_me) { iam(GuiText); return my next != NULL; } static void history_do(void *void_me, bool undo) { iam(GuiText); history_entry *he = undo ? my prev : my next; if (he == NULL) // TODO: this function should not be called in that case return; my history_change = 1; if (undo ^ he->type_del) { _GuiText_delete(my widget, he->first, he->last); } else { _GuiText_insert(my widget, he->first, he->last, he->text); } my history_change = 0; if (undo) { my next = my prev; my prev = my prev->prev; } else { my prev = my next; my next = my next->next; } if (my undo_item) GuiObject_setSensitive(my undo_item, history_has_undo(me)); if (my redo_item) GuiObject_setSensitive(my redo_item, history_has_redo(me)); } static void history_clear(void *void_me) { iam(GuiText); history_entry *h1, *h2; h1 = my prev; while (h1) { h2 = h1->prev; free(h1->text); free(h1); h1 = h2; } my prev = NULL; h1 = my next; while (h1) { h2 = h1->next; free(h1->text); free(h1); h1 = h2; } my next = NULL; if (my undo_item) GuiObject_setSensitive(my undo_item, FALSE); if (my redo_item) GuiObject_setSensitive(my redo_item, FALSE); } #endif /* * CALLBACKS */ #if gtk static void _GuiGtkEntry_history_delete_cb (GtkEditable *ed, gint from, gint to, gpointer void_me) { iam (GuiText); if (my history_change) return; history_add (me, gtk_editable_get_chars (GTK_EDITABLE (ed), from, to), from, to, 1); } static void _GuiGtkEntry_history_insert_cb (GtkEditable *ed, gchar *utf8_text, gint len, gint *from, gpointer void_me) { (void) ed; iam (GuiText); if (my history_change) return; gchar *text = (gchar *) malloc (sizeof (gchar) * (len + 1)); strcpy (text, utf8_text); history_add (me, text, *from, *from + len, 0); } static void _GuiGtkTextBuf_history_delete_cb (GtkTextBuffer *buffer, GtkTextIter *from, GtkTextIter *to, gpointer void_me) { iam (GuiText); if (my history_change) return; int from_pos = gtk_text_iter_get_offset (from); int to_pos = gtk_text_iter_get_offset (to); history_add (me, gtk_text_buffer_get_text (buffer, from, to, FALSE), from_pos, to_pos, 1); } static void _GuiGtkTextBuf_history_insert_cb (GtkTextBuffer *buffer, GtkTextIter *from, gchar *utf8_text, gint len, gpointer void_me) { (void) buffer; iam (GuiText); if (my history_change) return; int from_pos = gtk_text_iter_get_offset (from); gchar *text = (gchar *) malloc (sizeof (gchar) * (len + 1)); strcpy (text, utf8_text); history_add (me, text, from_pos, from_pos + len, 0); } static void _GuiGtkText_valueChangedCallback (GuiObject widget, gpointer void_me) { iam (GuiText); Melder_assert (me != NULL); if (my changeCallback != NULL) { struct structGuiTextEvent event = { widget }; my changeCallback (my changeBoss, & event); } } static void _GuiGtkText_destroyCallback (GuiObject widget, gpointer void_me) { (void) widget; iam (GuiText); if (my undo_item) g_object_unref (my undo_item); if (my redo_item) g_object_unref (my redo_item); my undo_item = NULL; my redo_item = NULL; history_clear (me); Melder_free (me); } #elif win #elif mac #endif GuiObject GuiText_create (GuiObject parent, int left, int right, int top, int bottom, unsigned long flags) { GuiText me = Melder_calloc_f (struct structGuiText, 1); #if gtk if (flags & GuiText_SCROLLED) { GtkWrapMode ww; GuiObject scrolled = gtk_scrolled_window_new (NULL, NULL); gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolled), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); my widget = gtk_text_view_new (); gtk_container_add (GTK_CONTAINER (scrolled), GTK_WIDGET (my widget)); gtk_widget_show (GTK_WIDGET (scrolled)); gtk_text_view_set_editable (GTK_TEXT_VIEW (my widget), (flags & GuiText_NONEDITABLE) == 0); if ((flags & GuiText_WORDWRAP) != 0) ww = GTK_WRAP_WORD_CHAR; else ww = GTK_WRAP_NONE; gtk_text_view_set_wrap_mode (GTK_TEXT_VIEW (my widget), ww); GtkTextBuffer *buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (my widget)); g_signal_connect (G_OBJECT (buffer), "delete-range", G_CALLBACK (_GuiGtkTextBuf_history_delete_cb), me); g_signal_connect (G_OBJECT (buffer), "insert-text", G_CALLBACK (_GuiGtkTextBuf_history_insert_cb), me); g_signal_connect (G_OBJECT (buffer), "changed", G_CALLBACK (_GuiGtkText_valueChangedCallback), me); gtk_container_add (GTK_CONTAINER (parent), GTK_WIDGET (scrolled)); } else { my widget = gtk_entry_new (); gtk_editable_set_editable (GTK_EDITABLE (my widget), (flags & GuiText_NONEDITABLE) == 0); g_signal_connect (G_OBJECT (my widget), "delete-text", G_CALLBACK (_GuiGtkEntry_history_delete_cb), me); g_signal_connect (G_OBJECT (my widget), "insert-text", G_CALLBACK (_GuiGtkEntry_history_insert_cb), me); g_signal_connect (GTK_EDITABLE (my widget), "changed", G_CALLBACK (_GuiGtkText_valueChangedCallback), me); //GTK_WIDGET_UNSET_FLAGS (my widget, GTK_CAN_DEFAULT); if (GTK_IS_BOX (parent)) { gtk_container_add (GTK_CONTAINER (parent), GTK_WIDGET (my widget)); } gtk_entry_set_activates_default (GTK_ENTRY (my widget), true); } _GuiObject_setUserData (my widget, me); _GuiObject_position (my widget, left, right, top, bottom); my prev = NULL; my next = NULL; my history_change = 0; my undo_item = NULL; my redo_item = NULL; g_signal_connect (G_OBJECT (my widget), "destroy", G_CALLBACK (_GuiGtkText_destroyCallback), me); #elif win my widget = _Gui_initializeWidget (xmTextWidgetClass, parent, flags & GuiText_SCROLLED ? L"scrolledText" : L"text"); _GuiObject_setUserData (my widget, me); my editable = (flags & GuiText_NONEDITABLE) == 0; my widget -> window = CreateWindow (L"edit", NULL, WS_CHILD | WS_BORDER | ( flags & GuiText_WORDWRAP ? ES_AUTOVSCROLL : ES_AUTOHSCROLL ) | ES_MULTILINE | WS_CLIPSIBLINGS | ( flags & GuiText_SCROLLED ? WS_HSCROLL | WS_VSCROLL : 0 ), my widget -> x, my widget -> y, my widget -> width, my widget -> height, my widget -> parent -> window, (HMENU) 1, theGui.instance, NULL); SetWindowLongPtr (my widget -> window, GWLP_USERDATA, (LONG_PTR) my widget); if (! font10) { font10 = CreateFont (13, 0, 0, 0, 0, 0, 0, 0, DEFAULT_CHARSET, 0, 0, 0, 0/*FIXED_PITCH | FF_MODERN*/, /*L"Doulos SIL"*/L"Courier New"); font12 = CreateFont (16, 0, 0, 0, 0, 0, 0, 0, DEFAULT_CHARSET, 0, 0, 0, 0/*FIXED_PITCH | FF_MODERN*/, /*L"Doulos SIL"*/L"Courier New"); font14 = CreateFont (19, 0, 0, 0, 0, 0, 0, 0, DEFAULT_CHARSET, 0, 0, 0, 0/*FIXED_PITCH | FF_MODERN*/, /*L"Doulos SIL"*/L"Courier New"); font18 = CreateFont (24, 0, 0, 0, 0, 0, 0, 0, DEFAULT_CHARSET, 0, 0, 0, 0/*FIXED_PITCH | FF_MODERN*/, /*L"Doulos SIL"*/L"Courier New"); font24 = CreateFont (32, 0, 0, 0, 0, 0, 0, 0, DEFAULT_CHARSET, 0, 0, 0, 0/*FIXED_PITCH | FF_MODERN*/, /*L"Doulos SIL"*/L"Courier New"); } SetWindowFont (my widget -> window, font12 /*theScrolledHint ? font : GetStockFont (ANSI_VAR_FONT)*/, FALSE); Edit_LimitText (my widget -> window, 0); _GuiObject_position (my widget, left, right, top, bottom); /* * The first created text widget shall attract the input focus. */ if (! my widget -> shell -> textFocus) { my widget -> shell -> textFocus = my widget; /* Even if not-yet-managed. But in that case it will not receive global focus. */ } #elif mac #if useCarbon if (flags & GuiText_SCROLLED) { my widget = _Gui_initializeWidget (xmTextWidgetClass, parent, L"scrolledText"); _GuiObject_setUserData (my widget, me); my editable = (flags & GuiText_NONEDITABLE) == 0; TXNLongRect destRect; TXNMargins margins; TXNControlData controlData; TXNControlTag controlTag = kTXNMarginsTag; TXNNewObject (NULL, /* No file. */ my widget -> macWindow, & my widget -> rect, kTXNWantHScrollBarMask | kTXNWantVScrollBarMask | kTXNMonostyledTextMask | kTXNDrawGrowIconMask, kTXNTextEditStyleFrameType, kTXNTextensionFile, /*kTXNMacOSEncoding*/ kTXNSystemDefaultEncoding, & my macMlteObject, & my macMlteFrameId, me); destRect. left = 0; destRect. top = 0; destRect. right = 10000; destRect. bottom = 2000000000; TXNSetRectBounds (my macMlteObject, NULL, & destRect, FALSE); margins. leftMargin = 3; margins. topMargin = 3; margins. rightMargin = 0; margins. bottomMargin = 0; controlData. marginsPtr = & margins; TXNSetTXNObjectControls (my macMlteObject, FALSE, 1, & controlTag, & controlData); _GuiObject_position (my widget, left, right, top, bottom); } else { my widget = _Gui_initializeWidget (xmTextWidgetClass, parent, L"text"); _GuiObject_setUserData (my widget, me); my editable = (flags & GuiText_NONEDITABLE) == 0; Rect r = my widget -> rect; InsetRect (& r, 3, 3); CreateEditUnicodeTextControl (my widget -> macWindow, & r, NULL, false, NULL, & my widget -> nat.control.handle); SetControlReference (my widget -> nat.control.handle, (long) my widget); my widget -> isControl = TRUE; _GuiObject_position (my widget, left, right, top, bottom); } /* * The first created text widget shall attract the input focus. */ if (! my widget -> shell -> textFocus) { my widget -> shell -> textFocus = my widget; /* Even if not-yet-managed. But in that case it will not receive global focus. */ } #else #endif #endif return my widget; } GuiObject GuiText_createShown (GuiObject parent, int left, int right, int top, int bottom, unsigned long flags) { GuiObject me = GuiText_create (parent, left, right, top, bottom, flags); GuiObject_show (me); return me; } void GuiText_copy (GuiObject widget) { #if gtk if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gtk_editable_copy_clipboard (GTK_EDITABLE (widget)); } else if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_TEXT_VIEW) { GtkTextBuffer *buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); GtkClipboard *cb = gtk_clipboard_get(GDK_SELECTION_CLIPBOARD); gtk_text_buffer_copy_clipboard(buffer, cb); } #elif win if (! NativeText_getSelectionRange (widget, NULL, NULL)) return; SendMessage (widget -> window, WM_COPY, 0, 0); #elif mac #if useCarbon iam_text; if (! NativeText_getSelectionRange (widget, NULL, NULL)) return; if (isTextControl (widget)) { HandleControlKey (widget -> nat.control.handle, 0, 'C', cmdKey); } else if (isMLTE (me)) { TXNCopy (my macMlteObject); } #else #endif #endif } void GuiText_cut (GuiObject widget) { #if gtk if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gtk_editable_cut_clipboard (GTK_EDITABLE (widget)); } else if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_TEXT_VIEW) { GtkTextBuffer *buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); GtkClipboard *cb = gtk_clipboard_get(GDK_SELECTION_CLIPBOARD); gtk_text_buffer_cut_clipboard(buffer, cb, gtk_text_view_get_editable(GTK_TEXT_VIEW(widget))); } #elif win iam_text; if (! my editable || ! NativeText_getSelectionRange (widget, NULL, NULL)) return; SendMessage (widget -> window, WM_CUT, 0, 0); /* This will send the EN_CHANGE message, hence no need to call the valueChangedCallbacks. */ UpdateWindow (widget -> window); #elif mac #if useCarbon iam_text; if (! my editable || ! NativeText_getSelectionRange (widget, NULL, NULL)) return; if (isTextControl (widget)) { _GuiMac_clipOnParent (widget); HandleControlKey (widget -> nat.control.handle, 0, 'X', cmdKey); GuiMac_clipOff (); } else if (isMLTE (me)) { TXNCut (my macMlteObject); } _GuiText_handleValueChanged (widget); #else #endif #endif } wchar_t * GuiText_getSelection (GuiObject widget) { #if gtk // first = gtk_text_iter_get_offset (& start); // last = gtk_text_iter_get_offset (& end); if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gint start, end; gtk_editable_get_selection_bounds (GTK_EDITABLE (widget), & start, & end); if (end > start) { // at least one character selected? gchar *text = gtk_editable_get_chars (GTK_EDITABLE (widget), start, end); wchar_t *result = Melder_utf8ToWcs (text); g_free (text); return result; } } else if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_TEXT_VIEW) { GtkTextBuffer *textBuffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (widget)); if (gtk_text_buffer_get_has_selection (textBuffer)) { // at least one character selected? GtkTextIter start, end; gtk_text_buffer_get_selection_bounds (textBuffer, & start, & end); gchar *text = gtk_text_buffer_get_text (textBuffer, & start, & end, TRUE); wchar_t *result = Melder_utf8ToWcs (text); g_free (text); return result; } } #elif win long start, end; NativeText_getSelectionRange (widget, & start, & end); if (end > start) { // at least one character selected? /* * Get all text. */ long length = NativeText_getLength (widget); wchar_t *result = Melder_malloc_f (wchar_t, length + 1); NativeText_getText (widget, result, length); /* * Zoom in on selection. */ length = end - start; memmove (result, result + start, length * sizeof (wchar_t)); /* Not because of realloc, but because of free! */ result [length] = '\0'; result = (wchar *) Melder_realloc_f (result, (length + 1) * sizeof (wchar_t)); /* Optional. */ Melder_killReturns_inlineW (result); /* AFTER zooming! */ return result; } #elif mac #if useCarbon long start, end; NativeText_getSelectionRange (widget, & start, & end); if (end > start) { // at least one character selected? /* * Get all text. */ long length = NativeText_getLength (widget); wchar_t *result = Melder_malloc_f (wchar_t, length + 1); NativeText_getText (widget, result, length); /* * Zoom in on selection. */ #if mac for (long i = 0; i < start; i ++) if (result [i] > 0xFFFF) { start --; end --; } for (long i = start; i < end; i ++) if (result [i] > 0xFFFF) { end --; } #endif length = end - start; memmove (result, result + start, length * sizeof (wchar_t)); /* Not because of realloc, but because of free! */ result [length] = '\0'; result = (wchar *) Melder_realloc_f (result, (length + 1) * sizeof (wchar_t)); /* Optional. */ Melder_killReturns_inlineW (result); /* AFTER zooming! */ return result; } #else #endif #endif return NULL; // zero characters selected } wchar_t * GuiText_getString (GuiObject widget) { long first, last; return GuiText_getStringAndSelectionPosition (widget, & first, & last); } wchar_t * GuiText_getStringAndSelectionPosition (GuiObject widget, long *first, long *last) { #if gtk if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gint first_gint, last_gint; gtk_editable_get_selection_bounds (GTK_EDITABLE (widget), & first_gint, & last_gint); *first = first_gint; *last = last_gint; return Melder_utf8ToWcs (gtk_entry_get_text (GTK_ENTRY (widget))); } else if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_TEXT_VIEW) { GtkTextBuffer *textBuffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (widget)); GtkTextIter start, end; gtk_text_buffer_get_start_iter (textBuffer, & start); gtk_text_buffer_get_end_iter (textBuffer, & end); gchar *text = gtk_text_buffer_get_text (textBuffer, & start, & end, TRUE); // TODO: Hidden chars ook maar doen he? wchar_t *result = Melder_utf8ToWcs (text); g_free (text); gtk_text_buffer_get_selection_bounds (textBuffer, & start, & end); *first = gtk_text_iter_get_offset (& start); *last = gtk_text_iter_get_offset (& end); return result; } return NULL; #elif win long length = NativeText_getLength (widget); wchar_t *result = Melder_malloc_f (wchar_t, length + 1); NativeText_getText (widget, result, length); NativeText_getSelectionRange (widget, first, last); long numberOfLeadingLineBreaks = 0, numberOfSelectedLineBreaks = 0; for (long i = 0; i < *first; i ++) if (result [i] == 13) numberOfLeadingLineBreaks ++; for (long i = *first; i < *last; i ++) if (result [i] == 13) numberOfSelectedLineBreaks ++; *first -= numberOfLeadingLineBreaks; *last -= numberOfLeadingLineBreaks + numberOfSelectedLineBreaks; Melder_killReturns_inlineW (result); return result; #elif mac #if useCarbon long length = NativeText_getLength (widget); // UTF-16 length; should be enough for UTF-32 buffer wchar_t *result = Melder_malloc_f (wchar_t, length + 1); NativeText_getText (widget, result, length); NativeText_getSelectionRange (widget, first, last); // 'first' and 'last' are expressed in UTF-16 words for (long i = 0; i < *first; i ++) if (result [i] > 0xFFFF) { (*first) --; (*last) --; } for (long i = *first; i < *last; i ++) if (result [i] > 0xFFFF) { (*last) --; } Melder_killReturns_inlineW (result); return result; #else return NULL; // TODO #endif #endif } void GuiText_paste (GuiObject widget) { #if gtk if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gtk_editable_paste_clipboard (GTK_EDITABLE (widget)); } else if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_TEXT_VIEW) { GtkTextBuffer *buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); GtkClipboard *cb = gtk_clipboard_get(GDK_SELECTION_CLIPBOARD); gtk_text_buffer_paste_clipboard(buffer, cb, NULL, gtk_text_view_get_editable(GTK_TEXT_VIEW(widget))); } #elif win iam_text; if (! my editable) return; SendMessage (widget -> window, WM_PASTE, 0, 0); /* This will send the EN_CHANGE message, hence no need to call the valueChangedCallbacks. */ UpdateWindow (widget -> window); #elif mac #if useCarbon iam_text; if (! my editable) return; if (isTextControl (widget)) { _GuiMac_clipOnParent (widget); HandleControlKey (widget -> nat.control.handle, 0, 'V', cmdKey); GuiMac_clipOff (); } else if (isMLTE (me)) { TXNPaste (my macMlteObject); } _GuiText_handleValueChanged (widget); #else #endif #endif } void GuiText_redo (GuiObject widget) { #if mac #if useCarbon iam_text; if (isMLTE (me)) { TXNRedo (my macMlteObject); } _GuiText_handleValueChanged (widget); #else #endif #else iam_text; history_do(me, 0); #endif } void GuiText_remove (GuiObject widget) { #if gtk if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gtk_editable_delete_selection (GTK_EDITABLE (widget)); } else if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_TEXT_VIEW) { GtkTextBuffer *buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(widget)); gtk_text_buffer_delete_selection(buffer, TRUE, gtk_text_view_get_editable(GTK_TEXT_VIEW(widget))); } #elif win iam_text; if (! my editable || ! NativeText_getSelectionRange (widget, NULL, NULL)) return; SendMessage (widget -> window, WM_CLEAR, 0, 0); /* This will send the EN_CHANGE message, hence no need to call the valueChangedCallbacks. */ UpdateWindow (widget -> window); #elif mac #if useCarbon iam_text; if (! my editable || ! NativeText_getSelectionRange (widget, NULL, NULL)) return; if (isTextControl (widget)) { _GuiMac_clipOnParent (widget); HandleControlKey (widget -> nat.control.handle, 0, 8, 0); /* Backspace key. */ GuiMac_clipOff (); } else if (isMLTE (me)) { TXNClear (my macMlteObject); } _GuiText_handleValueChanged (widget); #else #endif #endif } void GuiText_replace (GuiObject widget, long from_pos, long to_pos, const wchar_t *text) { #if gtk gchar *newText = Melder_peekWcsToUtf8 (text); if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gtk_editable_delete_text (GTK_EDITABLE (widget), from_pos, to_pos); gint from_pos_gint = from_pos; gtk_editable_insert_text (GTK_EDITABLE (widget), newText, g_utf8_strlen (newText, -1), & from_pos_gint); } else if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_TEXT_VIEW) { GtkTextBuffer *buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW(widget)); GtkTextIter from_it, to_it; gtk_text_buffer_get_iter_at_offset (buffer, & from_it, from_pos); gtk_text_buffer_get_iter_at_offset (buffer, & to_it, to_pos); gtk_text_buffer_delete_interactive (buffer, & from_it, & to_it, gtk_text_view_get_editable (GTK_TEXT_VIEW (widget))); gtk_text_buffer_insert_interactive (buffer, & from_it, newText, g_utf8_strlen (newText, -1), gtk_text_view_get_editable (GTK_TEXT_VIEW (widget))); } #elif win const wchar_t *from; wchar_t *winText = Melder_malloc_f (wchar_t, 2 * wcslen (text) + 1), *to; /* All new lines plus one null byte. */ Melder_assert (MEMBER (widget, Text)); /* * Replace all LF with CR/LF. */ for (from = text, to = winText; *from != '\0'; from ++, to ++) if (*from == '\n') { *to = 13; * ++ to = '\n'; } else *to = *from; *to = '\0'; /* * We DON'T replace any text without selecting it, so we can deselect any other text, * thus allowing ourselves to select [from_pos, to_pos] and use the REPLACESEL message. */ GuiText_setSelection (widget, from_pos, to_pos); Edit_ReplaceSel (widget -> window, winText); Melder_free (winText); UpdateWindow (widget -> window); #elif mac #if useCarbon iam_text; long length = wcslen (text), i; wchar_t *macText = Melder_malloc_f (wchar_t, length + 1); Melder_assert (widget -> widgetClass == xmTextWidgetClass); wcsncpy (macText, text, length); macText [length] = '\0'; /* * Replace all LF with CR. */ for (i = 0; i < length; i ++) if (macText [i] == '\n') macText [i] = 13; /* * We DON'T replace any text without selecting it, so we can deselect any other text, * thus allowing ourselves to select [from_pos, to_pos] and use selection replacement. */ if (my widget -> managed) _GuiMac_clipOnParent (widget); if (isTextControl (widget)) { // BUG: this is not UTF-32-savvy; this is acceptable because it isn't used in Praat long oldLength = NativeText_getLength (widget); wchar_t *totalText = Melder_malloc_f (wchar_t, oldLength - (to_pos - from_pos) + length + 1); wchar_t *oldText = Melder_malloc_f (wchar_t, oldLength + 1); NativeText_getText (widget, oldText, oldLength); wcsncpy (totalText, oldText, from_pos); wcscpy (totalText + from_pos, macText); wcscpy (totalText + from_pos + length, oldText + to_pos); CFStringRef totalText_cfstring = (CFStringRef) Melder_peekWcsToCfstring (totalText); SetControlData (widget -> nat.control.handle, kControlEntireControl, kControlEditTextCFStringTag, sizeof (CFStringRef), & totalText_cfstring); Melder_free (oldText); Melder_free (totalText); } else if (isMLTE (me)) { long oldLength = NativeText_getLength (widget); wchar_t *oldText = Melder_malloc_f (wchar_t, oldLength + 1); NativeText_getText (widget, oldText, oldLength); long numberOfLeadingHighUnicodeValues = 0, numberOfSelectedHighUnicodeValues = 0; for (long i = 0; i < from_pos; i ++) if (oldText [i] > 0xFFFF) numberOfLeadingHighUnicodeValues ++; for (long i = from_pos; i < to_pos; i ++) if (oldText [i] > 0xFFFF) numberOfSelectedHighUnicodeValues ++; from_pos += numberOfLeadingHighUnicodeValues; to_pos += numberOfLeadingHighUnicodeValues + numberOfSelectedHighUnicodeValues; const UniChar *macText_utf16 = Melder_peekWcsToUtf16 (macText); TXNSetData (my macMlteObject, kTXNUnicodeTextData, macText_utf16, wcslen_utf16 (macText, 0) * 2, from_pos, to_pos); } Melder_free (macText); if (widget -> managed) { if (isTextControl (widget)) { Draw1Control (widget -> nat.control.handle); } else if (isMLTE (me)) { } GuiMac_clipOff (); } _GuiText_handleValueChanged (widget); #else #endif #endif } void GuiText_scrollToSelection (GuiObject widget) { #if gtk GtkTextBuffer *textBuffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (widget)); GtkTextIter start, end; gtk_text_buffer_get_selection_bounds (textBuffer, & start, & end); //GtkTextMark *mark = gtk_text_buffer_create_mark (textBuffer, NULL, & start, true); gtk_text_view_scroll_to_iter (GTK_TEXT_VIEW (widget), & start, 0.1, false, 0.0, 0.0); //gtk_text_view_scroll_to_mark (GTK_TEXT_VIEW (widget), mark, 0.1, false, 0.0, 0.0); #elif win Edit_ScrollCaret (widget -> window); #elif mac #if useCarbon iam_text; if (isTextControl (widget)) { ; } else if (isMLTE (me)) { TXNShowSelection (my macMlteObject, false); } #else #endif #endif } void GuiText_setChangeCallback (GuiObject widget, void (*changeCallback) (void *boss, GuiTextEvent event), void *changeBoss) { iam_text; my changeCallback = changeCallback; my changeBoss = changeBoss; } void GuiText_setFontSize (GuiObject widget, int size) { #if gtk GtkRcStyle *modStyle = gtk_widget_get_modifier_style (GTK_WIDGET (widget)); PangoFontDescription *fontDesc = modStyle -> font_desc != NULL ? modStyle->font_desc : pango_font_description_copy (GTK_WIDGET (widget) -> style -> font_desc); pango_font_description_set_absolute_size (fontDesc, size * PANGO_SCALE); modStyle -> font_desc = fontDesc; gtk_widget_modify_style (GTK_WIDGET (widget), modStyle); #elif win iam_text; // a trick to update the window. BUG: why doesn't UpdateWindow seem to suffice? long first, last; wchar *text = GuiText_getStringAndSelectionPosition (my widget, & first, & last); GuiText_setString (my widget, L""); // erase all UpdateWindow (my widget -> window); if (size <= 10) { SetWindowFont (my widget -> window, font10, FALSE); } else if (size <= 12) { SetWindowFont (my widget -> window, font12, FALSE); } else if (size <= 14) { SetWindowFont (my widget -> window, font14, FALSE); } else if (size <= 18) { SetWindowFont (my widget -> window, font18, FALSE); } else { SetWindowFont (my widget -> window, font24, FALSE); } GuiText_setString (my widget, text); Melder_free (text); GuiText_setSelection (my widget, first, last); UpdateWindow (my widget -> window); #elif mac #if useCarbon iam_text; if (isMLTE (me)) { TXNTypeAttributes attr; attr. tag = kTXNQDFontSizeAttribute; attr. size = kTXNFontSizeAttributeSize; attr. data. dataValue = (unsigned long) size << 16; TXNSetTypeAttributes (my macMlteObject, 1, & attr, 0, 2000000000); } #else #endif #endif } void GuiText_setRedoItem (GuiObject widget, GuiObject item) { #if gtk iam_text; if (my redo_item) g_object_unref (my redo_item); my redo_item = item; if (my redo_item) { g_object_ref (my redo_item); GuiObject_setSensitive (my redo_item, history_has_redo (me)); } #elif win #elif mac #endif } void GuiText_setSelection (GuiObject widget, long first, long last) { if (widget != NULL) { #if gtk if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_ENTRY) { gtk_editable_select_region (GTK_EDITABLE (widget), first, last); } else if (G_OBJECT_TYPE (G_OBJECT (widget)) == GTK_TYPE_TEXT_VIEW) { GtkTextBuffer *buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (widget)); GtkTextIter from_it, to_it; gtk_text_buffer_get_iter_at_offset (buffer, & from_it, first); gtk_text_buffer_get_iter_at_offset (buffer, & to_it, last); gtk_text_buffer_select_range (buffer, & from_it, & to_it); } #elif win /* 'first' and 'last' are the positions of the selection in the text when separated by LF alone. */ /* We have to convert this to the positions that the selection has in a text separated by CR/LF sequences. */ wchar_t *text = GuiText_getString (widget); if (first < 0) first = 0; if (last < 0) last = 0; long length = wcslen (text); if (first >= length) first = length; if (last >= length) last = length; long numberOfLeadingLineBreaks = 0, numberOfSelectedLineBreaks = 0; for (long i = 0; i < first; i ++) if (text [i] == '\n') numberOfLeadingLineBreaks ++; for (long i = first; i < last; i ++) if (text [i] == '\n') numberOfSelectedLineBreaks ++; first += numberOfLeadingLineBreaks; last += numberOfLeadingLineBreaks + numberOfSelectedLineBreaks; Melder_free (text); Edit_SetSel (widget -> window, first, last); UpdateWindow (widget -> window); #elif mac #if useCarbon iam_text; wchar_t *text = GuiText_getString (widget); if (first < 0) first = 0; if (last < 0) last = 0; long length = wcslen (text); if (first >= length) first = length; if (last >= length) last = length; long numberOfLeadingHighUnicodeValues = 0, numberOfSelectedHighUnicodeValues = 0; for (long i = 0; i < first; i ++) if (text [i] > 0xFFFF) numberOfLeadingHighUnicodeValues ++; for (long i = first; i < last; i ++) if (text [i] > 0xFFFF) numberOfSelectedHighUnicodeValues ++; first += numberOfLeadingHighUnicodeValues; last += numberOfLeadingHighUnicodeValues + numberOfSelectedHighUnicodeValues; Melder_free (text); if (isTextControl (widget)) { ControlEditTextSelectionRec rec = { first, last }; SetControlData (widget -> nat.control.handle, kControlEntireControl, kControlEditTextSelectionTag, sizeof (rec), & rec); } else if (isMLTE (me)) { TXNSetSelection (my macMlteObject, first, last); } #else #endif #endif } } void GuiText_setString (GuiObject widget, const wchar_t *text) { #if gtk if (G_OBJECT_TYPE (widget) == GTK_TYPE_ENTRY) { gtk_entry_set_text (GTK_ENTRY (widget), Melder_peekWcsToUtf8 (text)); } else if (G_OBJECT_TYPE (widget) == GTK_TYPE_TEXT_VIEW) { GtkTextBuffer *textBuffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (widget)); gchar *textUtf8 = Melder_peekWcsToUtf8 (text); //gtk_text_buffer_set_text (textBuffer, textUtf8, strlen (textUtf8)); // length in bytes! GtkTextIter start, end; gtk_text_buffer_get_start_iter (textBuffer, & start); gtk_text_buffer_get_end_iter (textBuffer, & end); gtk_text_buffer_delete_interactive (textBuffer, & start, & end, gtk_text_view_get_editable (GTK_TEXT_VIEW (widget))); gtk_text_buffer_insert_interactive (textBuffer, & start, textUtf8, strlen (textUtf8), gtk_text_view_get_editable (GTK_TEXT_VIEW (widget))); } #elif win const wchar_t *from; wchar_t *winText = Melder_malloc_f (wchar_t, 2 * wcslen (text) + 1), *to; /* All new lines plus one null byte. */ /* * Replace all LF with CR/LF. */ for (from = text, to = winText; *from != '\0'; from ++, to ++) if (*from == '\n') { *to = 13; * ++ to = '\n'; } else *to = *from; *to = '\0'; SetWindowText (widget -> window, winText); Melder_free (winText); UpdateWindow (widget -> window); #elif mac #if useCarbon iam_text; long length_utf32 = wcslen (text), length_utf16 = wcslen_utf16 (text, false); UniChar *macText = Melder_malloc_f (UniChar, length_utf16 + 1); Melder_assert (widget -> widgetClass == xmTextWidgetClass); /* * Convert from UTF-32 to UTF-16 and replace all LF with CR. */ long j = 0; for (long i = 0; i < length_utf32; i ++) { MelderUtf32 kar = text [i]; if (kar == '\n') { // LF macText [j ++] = 13; // CR } else if (kar <= 0xFFFF) { macText [j ++] = kar; } else { Melder_assert (kar <= 0x10FFFF); kar -= 0x10000; macText [j ++] = 0xD800 | (kar >> 10); // first UTF-16 surrogate character macText [j ++] = 0xDC00 | (kar & 0x3FF); // second UTF-16 surrogate character } } macText [j] = '\0'; if (j != length_utf16) Melder_fatal ("GuiText_setString: incorrect number of UTF-16 words (%ld instead of %ld): <<%ls>>.", j, length_utf16, text); if (isTextControl (widget)) { CFStringRef cfString = CFStringCreateWithCharacters (NULL, macText, length_utf16); SetControlData (widget -> nat.control.handle, kControlEntireControl, kControlEditTextCFStringTag, sizeof (CFStringRef), & cfString); CFRelease (cfString); } else if (isMLTE (me)) { TXNSetData (my macMlteObject, kTXNUnicodeTextData, macText, length_utf16*2, 0, NativeText_getLength (widget)); } Melder_free (macText); if (widget -> managed) { if (theGui.duringUpdate) { _Gui_invalidateWidget (widget); /* HACK: necessary because VisRgn has temporarily been changed (not used in Praat any longer). */ } else { if (isTextControl (widget)) { _GuiMac_clipOnParent (widget); Draw1Control (widget -> nat.control.handle); GuiMac_clipOff (); } else if (isMLTE (me)) { } } } _GuiText_handleValueChanged (widget); #else #endif #endif } void GuiText_setUndoItem (GuiObject widget, GuiObject item) { #if gtk iam_text; if (my undo_item) g_object_unref (my undo_item); my undo_item = item; if (my undo_item) { g_object_ref (my undo_item); GuiObject_setSensitive(my undo_item, history_has_undo(me)); } #elif win #elif mac #endif } void GuiText_undo (GuiObject widget) { #if gtk iam_text; history_do (me, 1); #elif win #elif mac #if useCarbon iam_text; if (isMLTE (me)) { TXNUndo (my macMlteObject); } _GuiText_handleValueChanged (widget); #else #endif #endif } /* End of file GuiText.cpp */ sources_5316/sys/HyperPage.cpp0000644000176700017670000012353311632120305015131 0ustar paulpaul/* HyperPage.cpp * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include "HyperPage.h" #include "Printer.h" #include "Preferences.h" #include "machine.h" #include "praat.h" #include "EditorM.h" Thing_implement (HyperPage, Editor, 0); #define PAGE_HEIGHT 320.0 #define SCREEN_HEIGHT 15.0 #define PAPER_TOP 12.0 #define TOP_MARGIN 0.8 #define PAPER_BOTTOM (13.0 - (double) thePrinter. paperHeight / thePrinter. resolution) #define BOTTOM_MARGIN 0.5 static double resolution; static enum kGraphics_font prefs_font; static int prefs_fontSize; void HyperPage_prefs (void) { Preferences_addEnum (L"HyperPage.font", & prefs_font, kGraphics_font, DEFAULT); Preferences_addInt (L"HyperPage.fontSize", & prefs_fontSize, 12); } /********** class HyperLink **********/ Thing_implement (HyperLink, Data, 0); HyperLink HyperLink_create (const wchar_t *name, double x1DC, double x2DC, double y1DC, double y2DC) { autoHyperLink me = Thing_new (HyperLink); Thing_setName (me.peek(), name); my x1DC = x1DC, my x2DC = x2DC, my y1DC = y1DC, my y2DC = y2DC; return me.transfer(); } static void saveHistory (HyperPage me, const wchar_t *title) { if (! title) return; /* * The page title will be saved at the top. Go there. */ while (my historyPointer < 19 && my history [my historyPointer]. page) my historyPointer ++; /* * If the page title to be saved is already at the top, ignore it. */ if (my history [my historyPointer]. page) { if (wcsequ (my history [my historyPointer]. page, title)) return; } else if (my historyPointer > 0 && wcsequ (my history [my historyPointer - 1]. page, title)) { my historyPointer --; return; } /* * If the history buffer is full, shift it. */ if (my historyPointer == 19 && my history [my historyPointer]. page) { int i; Melder_free (my history [0]. page); for (i = 0; i < 19; i ++) my history [i] = my history [i + 1]; } /* * Add the page title to the top of the history list. */ my history [my historyPointer]. page = Melder_wcsdup_f (title); } /******************************************************************************** * * Before drawing or printing. * */ static void initScreen (HyperPage me) { my d_y = PAGE_HEIGHT + my top / 5.0; my d_x = 0; my previousBottomSpacing = 0.0; forget (my links); my links = Collection_create (classHyperLink, 100); } void HyperPage_initSheetOfPaper (HyperPage me) { int reflect = my mirror && (my d_printingPageNumber & 1) == 0; wchar *leftHeader = reflect ? my outsideHeader : my insideHeader; wchar *rightHeader = reflect ? my insideHeader : my outsideHeader; wchar *leftFooter = reflect ? my outsideFooter : my insideFooter; wchar *rightFooter = reflect ? my insideFooter : my outsideFooter; my d_y = PAPER_TOP - TOP_MARGIN; my d_x = 0; my previousBottomSpacing = 0.0; Graphics_setFont (my ps, kGraphics_font_TIMES); Graphics_setFontSize (my ps, 12); Graphics_setFontStyle (my ps, Graphics_ITALIC); if (leftHeader) { Graphics_setTextAlignment (my ps, Graphics_LEFT, Graphics_TOP); Graphics_text (my ps, 0.7, PAPER_TOP, leftHeader); } if (my middleHeader) { Graphics_setTextAlignment (my ps, Graphics_CENTRE, Graphics_TOP); Graphics_text (my ps, 0.7 + 3, PAPER_TOP, my middleHeader); } if (rightHeader) { Graphics_setTextAlignment (my ps, Graphics_RIGHT, Graphics_TOP); Graphics_text (my ps, 0.7 + 6, PAPER_TOP, rightHeader); } if (leftFooter) { Graphics_setTextAlignment (my ps, Graphics_LEFT, Graphics_BOTTOM); Graphics_text (my ps, 0.7, PAPER_BOTTOM, leftFooter); } if (my middleFooter) { Graphics_setTextAlignment (my ps, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (my ps, 0.7 + 3, PAPER_BOTTOM, my middleFooter); } if (rightFooter) { Graphics_setTextAlignment (my ps, Graphics_RIGHT, Graphics_BOTTOM); Graphics_text (my ps, 0.7 + 6, PAPER_BOTTOM, rightFooter); } Graphics_setFontStyle (my ps, Graphics_NORMAL); if (my d_printingPageNumber) Graphics_text1 (my ps, 0.7 + ( reflect ? 0 : 6 ), PAPER_BOTTOM, Melder_integer (my d_printingPageNumber)); Graphics_setTextAlignment (my ps, Graphics_LEFT, Graphics_BOTTOM); } static void updateVerticalScrollBar (HyperPage me); int HyperPage_any (I, const wchar_t *text, enum kGraphics_font font, int size, int style, double minFooterDistance, double x, double secondIndent, double topSpacing, double bottomSpacing, unsigned long method) { iam (HyperPage); double heightGuess; if (my rightMargin == 0) return 0; // Melder_assert (my rightMargin != 0); heightGuess = size * (1.2/72) * ((long) size * wcslen (text) / (int) (my rightMargin * 150)); if (! my printing) { Graphics_Link *paragraphLinks; int numberOfParagraphLinks, ilink; if (my entryHint && (method & HyperPage_USE_ENTRY_HINT) && wcsequ (text, my entryHint)) { my entryPosition = my d_y; } my d_y -= ( my previousBottomSpacing > topSpacing ? my previousBottomSpacing : topSpacing ) * size / 12.0; my d_y -= size * (1.2/72); my d_x = x; if (/* my d_y > PAGE_HEIGHT + 2.0 + heightGuess || */ my d_y < PAGE_HEIGHT - SCREEN_HEIGHT) { my d_y -= heightGuess; } else { Graphics_setFont (my g, font); Graphics_setFontSize (my g, size); Graphics_setWrapWidth (my g, my rightMargin - x - 0.1); Graphics_setSecondIndent (my g, secondIndent); Graphics_setFontStyle (my g, style); Graphics_text (my g, my d_x, my d_y, text); numberOfParagraphLinks = Graphics_getLinks (& paragraphLinks); if (my links) for (ilink = 1; ilink <= numberOfParagraphLinks; ilink ++) { HyperLink link = HyperLink_create (paragraphLinks [ilink]. name, paragraphLinks [ilink]. x1, paragraphLinks [ilink]. x2, paragraphLinks [ilink]. y1, paragraphLinks [ilink]. y2); Collection_addItem (my links, link); } if (method & HyperPage_ADD_BORDER) { Graphics_setLineWidth (my g, 2); Graphics_line (my g, 0.0, my d_y, my rightMargin, my d_y); Graphics_setLineWidth (my g, 1); } /* * The text may have wrapped. * Ask the Graphics manager by how much, and update our text position accordingly. */ my d_y = Graphics_inqTextY (my g); } } else { Graphics_setFont (my ps, font); Graphics_setFontSize (my ps, size); my d_y -= my d_y == PAPER_TOP - TOP_MARGIN ? 0 : ( my previousBottomSpacing > topSpacing ? my previousBottomSpacing : topSpacing ) * size / 12.0; my d_y -= size * (1.2/72); if (my d_y < PAPER_BOTTOM + BOTTOM_MARGIN + minFooterDistance + size * (1.2/72) * (wcslen (text) / (6.0 * 10))) { Graphics_nextSheetOfPaper (my ps); if (my d_printingPageNumber) my d_printingPageNumber ++; HyperPage_initSheetOfPaper (me); Graphics_setFont (my ps, font); Graphics_setFontSize (my ps, size); my d_y -= size * (1.2/72); } my d_x = 0.7 + x; Graphics_setWrapWidth (my ps, 6.0 - x); Graphics_setSecondIndent (my ps, secondIndent); Graphics_setFontStyle (my ps, style); Graphics_text (my ps, my d_x, my d_y, text); if (method & HyperPage_ADD_BORDER) { Graphics_setLineWidth (my ps, 3); /*Graphics_line (my ps, 0.7, my d_y, 6.7, my d_y);*/ Graphics_line (my ps, 0.7, my d_y + size * (1.2/72) + 0.07, 6.7, my d_y + size * (1.2/72) + 0.07); Graphics_setLineWidth (my ps, 1); } my d_y = Graphics_inqTextY (my ps); } my previousBottomSpacing = bottomSpacing; return 1; } int HyperPage_pageTitle (I, const wchar_t *title) { iam (HyperPage); return HyperPage_any (me, title, my font, my fontSize * 2, 0, 2.0, 0.0, 0.0, my printing ? 0.4/2 : 0.2/2, 0.3/2, HyperPage_ADD_BORDER); } int HyperPage_intro (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 0.03, 0.0, 0.1, 0.1, 0); } int HyperPage_entry (I, const wchar_t *title) { iam (HyperPage); return HyperPage_any (me, title, my font, my fontSize * 1.4, Graphics_BOLD, 0.5, 0.0, 0.0, 0.25/1.4, 0.1/1.4, HyperPage_USE_ENTRY_HINT); } int HyperPage_paragraph (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 0.03, 0.0, 0.1, 0.1, 0); } int HyperPage_listItem (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 0.30, 0.2, 0.0, 0.0, 0); } int HyperPage_listItem1 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 0.57, 0.2, 0.0, 0.0, 0); } int HyperPage_listItem2 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 0.84, 0.2, 0.0, 0.0, 0); } int HyperPage_listItem3 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 1.11, 0.2, 0.0, 0.0, 0); } int HyperPage_listTag (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.2, 0.03, 0.0, 0.1, 0.03, 0); } int HyperPage_listTag1 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.2, 0.50, 0.0, 0.05, 0.03, 0); } int HyperPage_listTag2 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.2, 0.97, 0.0, 0.03, 0.03, 0); } int HyperPage_listTag3 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.2, 1.44, 0.0, 0.03, 0.03, 0); } int HyperPage_definition (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 0.5, 0.0, 0.03, 0.1, 0); } int HyperPage_definition1 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 0.97, 0.0, 0.03, 0.05, 0); } int HyperPage_definition2 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 1.44, 0.0, 0.03, 0.03, 0); } int HyperPage_definition3 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 1.93, 0.0, 0.03, 0.03, 0); } int HyperPage_code (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, kGraphics_font_COURIER, my fontSize * 0.86, 0, 0.0, 0.3, 0.5, 0.0, 0.0, 0); } int HyperPage_code1 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, kGraphics_font_COURIER, my fontSize * 0.86, 0, 0.0, 0.6, 0.5, 0.0, 0.0, 0); } int HyperPage_code2 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, kGraphics_font_COURIER, my fontSize * 0.86, 0, 0.0, 0.9, 0.5, 0.0, 0.0, 0); } int HyperPage_code3 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, kGraphics_font_COURIER, my fontSize * 0.86, 0, 0.0, 1.2, 0.5, 0.0, 0.0, 0); } int HyperPage_code4 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, kGraphics_font_COURIER, my fontSize * 0.86, 0, 0.0, 1.5, 0.5, 0.0, 0.0, 0); } int HyperPage_code5 (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, kGraphics_font_COURIER, my fontSize * 0.86, 0, 0.0, 1.8, 0.5, 0.0, 0.0, 0); } int HyperPage_prototype (I, const wchar_t *text) { iam (HyperPage); return HyperPage_any (me, text, my font, my fontSize, 0, 0.0, 0.03, 0.5, 0.0, 0.0, 0); } int HyperPage_formula (I, const wchar_t *formula) { iam (HyperPage); double topSpacing = 0.2, bottomSpacing = 0.2, minFooterDistance = 0.0; kGraphics_font font = my font; int size = my fontSize; if (! my printing) { my d_y -= ( my previousBottomSpacing > topSpacing ? my previousBottomSpacing : topSpacing ) * size / 12.0; my d_y -= size * (1.2/72); if (my d_y > PAGE_HEIGHT + 2.0 || my d_y < PAGE_HEIGHT - SCREEN_HEIGHT) { } else { Graphics_setFont (my g, font); Graphics_setFontStyle (my g, 0); Graphics_setFontSize (my g, size); Graphics_setWrapWidth (my g, 0); Graphics_setTextAlignment (my g, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (my g, my rightMargin / 2, my d_y, formula); Graphics_setTextAlignment (my g, Graphics_LEFT, Graphics_BOTTOM); } } else { Graphics_setFont (my ps, font); Graphics_setFontStyle (my ps, 0); Graphics_setFontSize (my ps, size); my d_y -= my d_y == PAPER_TOP - TOP_MARGIN ? 0 : ( my previousBottomSpacing > topSpacing ? my previousBottomSpacing : topSpacing ) * size / 12.0; my d_y -= size * (1.2/72); if (my d_y < PAPER_BOTTOM + BOTTOM_MARGIN + minFooterDistance) { Graphics_nextSheetOfPaper (my ps); if (my d_printingPageNumber) my d_printingPageNumber ++; HyperPage_initSheetOfPaper (me); Graphics_setFont (my ps, font); Graphics_setFontSize (my ps, size); my d_y -= size * (1.2/72); } Graphics_setWrapWidth (my ps, 0); Graphics_setTextAlignment (my ps, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text (my ps, 3.7, my d_y, formula); Graphics_setTextAlignment (my ps, Graphics_LEFT, Graphics_BOTTOM); } my previousBottomSpacing = bottomSpacing; return 1; } int HyperPage_picture (I, double width_inches, double height_inches, void (*draw) (Graphics g)) { iam (HyperPage); double topSpacing = 0.1, bottomSpacing = 0.1, minFooterDistance = 0.0; kGraphics_font font = my font; int size = my fontSize; width_inches *= width_inches < 0.0 ? -1.0 : size / 12.0; height_inches *= height_inches < 0.0 ? -1.0 : size / 12.0; if (! my printing) { my d_y -= ( my previousBottomSpacing > topSpacing ? my previousBottomSpacing : topSpacing ) * size / 12.0; if (my d_y > PAGE_HEIGHT + height_inches || my d_y < PAGE_HEIGHT - SCREEN_HEIGHT) { my d_y -= height_inches; } else { my d_y -= height_inches; Graphics_setFont (my g, font); Graphics_setFontStyle (my g, 0); Graphics_setFontSize (my g, size); my d_x = width_inches > my rightMargin ? 0 : 0.5 * (my rightMargin - width_inches); Graphics_setWrapWidth (my g, 0); Graphics_setViewport (my g, my d_x, my d_x + width_inches, my d_y, my d_y + height_inches); draw (my g); Graphics_setViewport (my g, 0, 1, 0, 1); Graphics_setWindow (my g, 0, 1, 0, 1); Graphics_setTextAlignment (my g, Graphics_LEFT, Graphics_BOTTOM); } } else { Graphics_setFont (my ps, font); Graphics_setFontStyle (my ps, 0); Graphics_setFontSize (my ps, size); my d_y -= my d_y == PAPER_TOP - TOP_MARGIN ? 0 : ( my previousBottomSpacing > topSpacing ? my previousBottomSpacing : topSpacing ) * size / 12.0; my d_y -= height_inches; if (my d_y < PAPER_BOTTOM + BOTTOM_MARGIN + minFooterDistance) { Graphics_nextSheetOfPaper (my ps); if (my d_printingPageNumber) my d_printingPageNumber ++; HyperPage_initSheetOfPaper (me); Graphics_setFont (my ps, font); Graphics_setFontSize (my ps, size); my d_y -= height_inches; } my d_x = 3.7 - 0.5 * width_inches; if (my d_x < 0) my d_x = 0; Graphics_setWrapWidth (my ps, 0); Graphics_setViewport (my ps, my d_x, my d_x + width_inches, my d_y, my d_y + height_inches); draw (my ps); Graphics_setViewport (my ps, 0, 1, 0, 1); Graphics_setWindow (my ps, 0, 1, 0, 1); Graphics_setTextAlignment (my ps, Graphics_LEFT, Graphics_BOTTOM); } my previousBottomSpacing = bottomSpacing; return 1; } int HyperPage_script (I, double width_inches, double height_inches, const wchar_t *script) { iam (HyperPage); wchar_t *text = Melder_wcsdup_f (script); Interpreter interpreter = Interpreter_createFromEnvironment (NULL); double topSpacing = 0.1, bottomSpacing = 0.1, minFooterDistance = 0.0; kGraphics_font font = my font; int size = my fontSize; double true_width_inches = width_inches * ( width_inches < 0.0 ? -1.0 : size / 12.0 ); double true_height_inches = height_inches * ( height_inches < 0.0 ? -1.0 : size / 12.0 ); if (! my printing) { my d_y -= ( my previousBottomSpacing > topSpacing ? my previousBottomSpacing : topSpacing ) * size / 12.0; if (my d_y > PAGE_HEIGHT + true_height_inches || my d_y < PAGE_HEIGHT - SCREEN_HEIGHT) { my d_y -= true_height_inches; } else { my d_y -= true_height_inches; Graphics_setFont (my g, font); Graphics_setFontStyle (my g, 0); Graphics_setFontSize (my g, size); my d_x = true_width_inches > my rightMargin ? 0 : 0.5 * (my rightMargin - true_width_inches); Graphics_setWrapWidth (my g, 0); long x1DCold, x2DCold, y1DCold, y2DCold; Graphics_inqWsViewport (my g, & x1DCold, & x2DCold, & y1DCold, & y2DCold); double x1NDCold, x2NDCold, y1NDCold, y2NDCold; Graphics_inqWsWindow (my g, & x1NDCold, & x2NDCold, & y1NDCold, & y2NDCold); { if (my praatApplication == NULL) my praatApplication = Melder_calloc_f (structPraatApplication, 1); if (my praatObjects == NULL) my praatObjects = Melder_calloc_f (structPraatObjects, 1); if (my praatPicture == NULL) my praatPicture = Melder_calloc_f (structPraatPicture, 1); theCurrentPraatApplication = (PraatApplication) my praatApplication; theCurrentPraatApplication -> batch = true; // prevent creation of editor windows theCurrentPraatApplication -> topShell = theForegroundPraatApplication. topShell; // needed for UiForm_create () in dialogs theCurrentPraatObjects = (PraatObjects) my praatObjects; theCurrentPraatPicture = (PraatPicture) my praatPicture; theCurrentPraatPicture -> graphics = my g; // has to draw into HyperPage rather than Picture window theCurrentPraatPicture -> font = font; theCurrentPraatPicture -> fontSize = size; theCurrentPraatPicture -> lineType = Graphics_DRAWN; theCurrentPraatPicture -> colour = Graphics_BLACK; theCurrentPraatPicture -> lineWidth = 1.0; theCurrentPraatPicture -> arrowSize = 1.0; theCurrentPraatPicture -> x1NDC = my d_x; theCurrentPraatPicture -> x2NDC = my d_x + true_width_inches; theCurrentPraatPicture -> y1NDC = my d_y; theCurrentPraatPicture -> y2NDC = my d_y + true_height_inches; Graphics_setViewport (my g, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setWindow (my g, 0.0, 1.0, 0.0, 1.0); long x1DC, y1DC, x2DC, y2DC; Graphics_WCtoDC (my g, 0.0, 0.0, & x1DC, & y2DC); Graphics_WCtoDC (my g, 1.0, 1.0, & x2DC, & y1DC); Graphics_resetWsViewport (my g, x1DC, x2DC, y1DC, y2DC); Graphics_setWsWindow (my g, 0, width_inches, 0, height_inches); theCurrentPraatPicture -> x1NDC = 0; theCurrentPraatPicture -> x2NDC = width_inches; theCurrentPraatPicture -> y1NDC = 0; theCurrentPraatPicture -> y2NDC = height_inches; Graphics_setViewport (my g, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); { // scope autoMelderProgressOff progress; autoMelderWarningOff warning; autoMelderSaveDefaultDir saveDir; if (! MelderDir_isNull (& my rootDirectory)) { Melder_setDefaultDir (& my rootDirectory); } try { Interpreter_run (interpreter, text); } catch (MelderError) { if (my scriptErrorHasBeenNotified) { Melder_clearError (); } else { Melder_flushError (NULL); my scriptErrorHasBeenNotified = true; } } } Graphics_setLineType (my g, Graphics_DRAWN); Graphics_setLineWidth (my g, 1.0); Graphics_setArrowSize (my g, 1.0); Graphics_setColour (my g, Graphics_BLACK); /*Graphics_Link *paragraphLinks; long numberOfParagraphLinks = Graphics_getLinks (& paragraphLinks); if (my links) for (long ilink = 1; ilink <= numberOfParagraphLinks; ilink ++) { HyperLink link = HyperLink_create (paragraphLinks [ilink]. name, paragraphLinks [ilink]. x1, paragraphLinks [ilink]. x2, paragraphLinks [ilink]. y1, paragraphLinks [ilink]. y2); Collection_addItem (my links, link); }*/ theCurrentPraatApplication = & theForegroundPraatApplication; theCurrentPraatObjects = & theForegroundPraatObjects; theCurrentPraatPicture = & theForegroundPraatPicture; } Graphics_resetWsViewport (my g, x1DCold, x2DCold, y1DCold, y2DCold); Graphics_setWsWindow (my g, x1NDCold, x2NDCold, y1NDCold, y2NDCold); Graphics_setViewport (my g, 0, 1, 0, 1); Graphics_setWindow (my g, 0, 1, 0, 1); Graphics_setTextAlignment (my g, Graphics_LEFT, Graphics_BOTTOM); } } else { Graphics_setFont (my ps, font); Graphics_setFontStyle (my ps, 0); Graphics_setFontSize (my ps, size); my d_y -= my d_y == PAPER_TOP - TOP_MARGIN ? 0 : ( my previousBottomSpacing > topSpacing ? my previousBottomSpacing : topSpacing ) * size / 12.0; my d_y -= true_height_inches; if (my d_y < PAPER_BOTTOM + BOTTOM_MARGIN + minFooterDistance) { Graphics_nextSheetOfPaper (my ps); if (my d_printingPageNumber) my d_printingPageNumber ++; HyperPage_initSheetOfPaper (me); Graphics_setFont (my ps, font); Graphics_setFontSize (my ps, size); my d_y -= true_height_inches; } my d_x = 3.7 - 0.5 * true_width_inches; if (my d_x < 0) my d_x = 0; Graphics_setWrapWidth (my ps, 0); long x1DCold, x2DCold, y1DCold, y2DCold; Graphics_inqWsViewport (my ps, & x1DCold, & x2DCold, & y1DCold, & y2DCold); double x1NDCold, x2NDCold, y1NDCold, y2NDCold; Graphics_inqWsWindow (my ps, & x1NDCold, & x2NDCold, & y1NDCold, & y2NDCold); { if (my praatApplication == NULL) my praatApplication = Melder_calloc_f (structPraatApplication, 1); if (my praatObjects == NULL) my praatObjects = Melder_calloc_f (structPraatObjects, 1); if (my praatPicture == NULL) my praatPicture = Melder_calloc_f (structPraatPicture, 1); theCurrentPraatApplication = (PraatApplication) my praatApplication; theCurrentPraatApplication -> batch = true; theCurrentPraatObjects = (PraatObjects) my praatObjects; theCurrentPraatPicture = (PraatPicture) my praatPicture; theCurrentPraatPicture -> graphics = my ps; theCurrentPraatPicture -> font = font; theCurrentPraatPicture -> fontSize = size; theCurrentPraatPicture -> lineType = Graphics_DRAWN; theCurrentPraatPicture -> colour = Graphics_BLACK; theCurrentPraatPicture -> lineWidth = 1.0; theCurrentPraatPicture -> arrowSize = 1.0; theCurrentPraatPicture -> x1NDC = my d_x; theCurrentPraatPicture -> x2NDC = my d_x + true_width_inches; theCurrentPraatPicture -> y1NDC = my d_y; theCurrentPraatPicture -> y2NDC = my d_y + true_height_inches; Graphics_setViewport (my ps, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); Graphics_setWindow (my ps, 0.0, 1.0, 0.0, 1.0); long x1DC, y1DC, x2DC, y2DC; Graphics_WCtoDC (my ps, 0.0, 0.0, & x1DC, & y2DC); Graphics_WCtoDC (my ps, 1.0, 1.0, & x2DC, & y1DC); long shift = (long) (Graphics_getResolution (my ps) * true_height_inches) + (y1DCold - y2DCold); Graphics_resetWsViewport (my ps, x1DC, x2DC, y1DC + shift, y2DC + shift); Graphics_setWsWindow (my ps, 0, width_inches, 0, height_inches); theCurrentPraatPicture -> x1NDC = 0; theCurrentPraatPicture -> x2NDC = width_inches; theCurrentPraatPicture -> y1NDC = 0; theCurrentPraatPicture -> y2NDC = height_inches; Graphics_setViewport (my ps, theCurrentPraatPicture -> x1NDC, theCurrentPraatPicture -> x2NDC, theCurrentPraatPicture -> y1NDC, theCurrentPraatPicture -> y2NDC); { // scope autoMelderProgressOff progress; autoMelderWarningOff warning; autoMelderSaveDefaultDir saveDir; if (! MelderDir_isNull (& my rootDirectory)) { Melder_setDefaultDir (& my rootDirectory); } try { Interpreter_run (interpreter, text); } catch (MelderError) { Melder_clearError (); } } Graphics_setLineType (my ps, Graphics_DRAWN); Graphics_setLineWidth (my ps, 1.0); Graphics_setArrowSize (my ps, 1.0); Graphics_setColour (my ps, Graphics_BLACK); theCurrentPraatApplication = & theForegroundPraatApplication; theCurrentPraatObjects = & theForegroundPraatObjects; theCurrentPraatPicture = & theForegroundPraatPicture; } Graphics_resetWsViewport (my ps, x1DCold, x2DCold, y1DCold, y2DCold); Graphics_setWsWindow (my ps, x1NDCold, x2NDCold, y1NDCold, y2NDCold); Graphics_setViewport (my ps, 0, 1, 0, 1); Graphics_setWindow (my ps, 0, 1, 0, 1); Graphics_setTextAlignment (my ps, Graphics_LEFT, Graphics_BOTTOM); } my previousBottomSpacing = bottomSpacing; forget (interpreter); Melder_free (text); return 1; } static void print (I, Graphics graphics) { iam (HyperPage); my ps = graphics; Graphics_setDollarSignIsCode (graphics, TRUE); Graphics_setAtSignIsLink (graphics, TRUE); my printing = TRUE; HyperPage_initSheetOfPaper (me); my v_draw (); my printing = FALSE; } /********** class HyperPage **********/ void structHyperPage :: v_destroy () { forget (links); Melder_free (entryHint); forget (g); for (int i = 0; i < 20; i ++) Melder_free (history [i]. page); Melder_free (currentPageTitle); if (praatApplication != NULL) { for (int iobject = ((PraatObjects) praatObjects) -> n; iobject >= 1; iobject --) { Melder_free (((PraatObjects) praatObjects) -> list [iobject]. name); forget (((PraatObjects) praatObjects) -> list [iobject]. object); } Melder_free (praatApplication); Melder_free (praatObjects); Melder_free (praatPicture); } HyperPage_Parent :: v_destroy (); } static void gui_drawingarea_cb_expose (I, GuiDrawingAreaExposeEvent event) { iam (HyperPage); (void) event; if (my g == NULL) return; // Could be the case in the very beginning. Graphics_clearWs (my g); initScreen (me); my v_draw (); if (my entryHint && my entryPosition) { Melder_free (my entryHint); my top = 5.0 * (PAGE_HEIGHT - my entryPosition); if (my top < 0) my top = 0; Graphics_clearWs (my g); initScreen (me); my v_draw (); updateVerticalScrollBar (me); } } static void gui_drawingarea_cb_click (I, GuiDrawingAreaClickEvent event) { iam (HyperPage); if (my g == NULL) return; // Could be the case in the very beginning. if (gtk && event -> type != BUTTON_PRESS) return; if (! my links) return; for (long ilink = 1; ilink <= my links -> size; ilink ++) { HyperLink link = (HyperLink) my links -> item [ilink]; if (event -> y > link -> y2DC && event -> y < link -> y1DC && event -> x > link -> x1DC && event -> x < link -> x2DC) { saveHistory (me, my currentPageTitle); try { HyperPage_goToPage (me, link -> name); } catch (MelderError) { Melder_flushError (NULL); } return; } } } static void menu_cb_postScriptSettings (EDITOR_ARGS) { EDITOR_IAM (HyperPage); Printer_postScriptSettings (); } #ifdef macintosh static void menu_cb_pageSetup (EDITOR_ARGS) { EDITOR_IAM (HyperPage); Printer_pageSetup (); } #endif static void menu_cb_print (EDITOR_ARGS) { EDITOR_IAM (HyperPage); EDITOR_FORM (L"Print", 0) SENTENCE (L"Left or inside header", L"") SENTENCE (L"Middle header", L"") LABEL (L"", L"Right or outside header:") TEXTFIELD (L"Right or outside header", L"") SENTENCE (L"Left or inside footer", L"") SENTENCE (L"Middle footer", L"") SENTENCE (L"Right or outside footer", L"") BOOLEAN (L"Mirror even/odd headers", TRUE) INTEGER (L"First page number", L"0 (= no page numbers)") EDITOR_OK my v_defaultHeaders (cmd); if (my d_printingPageNumber) SET_INTEGER (L"First page number", my d_printingPageNumber + 1) EDITOR_DO my insideHeader = GET_STRING (L"Left or inside header"); my middleHeader = GET_STRING (L"Middle header"); my outsideHeader = GET_STRING (L"Right or outside header"); my insideFooter = GET_STRING (L"Left or inside footer"); my middleFooter = GET_STRING (L"Middle footer"); my outsideFooter = GET_STRING (L"Right or outside footer"); my mirror = GET_INTEGER (L"Mirror even/odd headers"); my d_printingPageNumber = GET_INTEGER (L"First page number"); Printer_print (print, me); EDITOR_END } static void menu_cb_font (EDITOR_ARGS) { EDITOR_IAM (HyperPage); EDITOR_FORM (L"Font", 0) RADIO (L"Font", 1) RADIOBUTTON (L"Times") RADIOBUTTON (L"Helvetica") EDITOR_OK SET_INTEGER (L"Font", my font == kGraphics_font_TIMES ? 1 : my font == kGraphics_font_HELVETICA ? 2 : my font == kGraphics_font_PALATINO ? 3 : 1); EDITOR_DO int font = GET_INTEGER (L"Font"); prefs_font = my font = font == 1 ? kGraphics_font_TIMES : kGraphics_font_HELVETICA; if (my g) Graphics_updateWs (my g); EDITOR_END } static void updateSizeMenu (HyperPage me) { GuiMenuItem_check (my fontSizeButton_10, my fontSize == 10); GuiMenuItem_check (my fontSizeButton_12, my fontSize == 12); GuiMenuItem_check (my fontSizeButton_14, my fontSize == 14); GuiMenuItem_check (my fontSizeButton_18, my fontSize == 18); GuiMenuItem_check (my fontSizeButton_24, my fontSize == 24); } static void setFontSize (HyperPage me, int fontSize) { prefs_fontSize = my fontSize = fontSize; if (my g) Graphics_updateWs (my g); updateSizeMenu (me); } static void menu_cb_10 (EDITOR_ARGS) { EDITOR_IAM (HyperPage); setFontSize (me, 10); } static void menu_cb_12 (EDITOR_ARGS) { EDITOR_IAM (HyperPage); setFontSize (me, 12); } static void menu_cb_14 (EDITOR_ARGS) { EDITOR_IAM (HyperPage); setFontSize (me, 14); } static void menu_cb_18 (EDITOR_ARGS) { EDITOR_IAM (HyperPage); setFontSize (me, 18); } static void menu_cb_24 (EDITOR_ARGS) { EDITOR_IAM (HyperPage); setFontSize (me, 24); } static void menu_cb_fontSize (EDITOR_ARGS) { EDITOR_IAM (HyperPage); EDITOR_FORM (L"Font size", 0) NATURAL (L"Font size (points)", L"12") EDITOR_OK SET_INTEGER (L"Font size", my fontSize) EDITOR_DO setFontSize (me, GET_INTEGER (L"Font size")); EDITOR_END } static void menu_cb_searchForPage (EDITOR_ARGS) { EDITOR_IAM (HyperPage); EDITOR_FORM (L"Search for page", 0) TEXTFIELD (L"Page", L"a") EDITOR_OK EDITOR_DO HyperPage_goToPage (me, GET_STRING (L"Page")); therror // BUG EDITOR_END } /******************************************************************************** * * The vertical scroll bar controls and/or mirrors * the position of the viewable area within the page. * A page can be PAGE_HEIGHT inches high, so 'my top' (and the scroll-bar 'value') * may take on values between 0 and PAGE_HEIGHT * 5 (fifth inches). * Hence, the 'minimum' is 0. * The viewable area shows a certain number of fifth inches; * hence the 'sliderSize' is height / resolution * 5, * and the 'maximum' is PAGE_HEIGHT * 5. * The 'increment' is 1, so the arrows move the page by one fifth of an inch. * The 'pageIncrement' is sliderSize - 1. */ static void createVerticalScrollBar (HyperPage me, GuiObject parent) { #if gtk int maximumScrollBarValue = (int) (PAGE_HEIGHT * 5); GtkObject *adj = gtk_adjustment_new (1, 1, maximumScrollBarValue, 1, 1, maximumScrollBarValue - 1); my verticalScrollBar = gtk_vscrollbar_new (GTK_ADJUSTMENT (adj)); GuiObject_show (my verticalScrollBar); gtk_box_pack_end (GTK_BOX (parent), GTK_WIDGET (my verticalScrollBar), false, false, 3); #elif motif // TODO: Kan dit niet een algemele gui klasse worden? my verticalScrollBar = XtVaCreateManagedWidget ("verticalScrollBar", xmScrollBarWidgetClass, parent, XmNorientation, XmVERTICAL, XmNrightAttachment, XmATTACH_FORM, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, Machine_getMenuBarHeight () + Machine_getTextHeight () + 12, XmNbottomAttachment, XmATTACH_FORM, XmNbottomOffset, Machine_getScrollBarWidth (), XmNwidth, Machine_getScrollBarWidth (), XmNminimum, 0, XmNmaximum, (int) (PAGE_HEIGHT * 5), XmNsliderSize, 25, XmNvalue, 0, XmNincrement, 1, XmNpageIncrement, 24, NULL); #endif } static void updateVerticalScrollBar (HyperPage me) /* We cannot call this immediately after creation. */ /* This has to be called after changing 'my topParagraph'. */ { Dimension width, height; int sliderSize; #if motif XtVaGetValues (my drawingArea, XmNwidth, & width, XmNheight, & height, NULL); #endif sliderSize = 25 /*height / resolution * 5*/; /* Don't change slider unless you clip value! */ #if gtk GtkAdjustment *adj = gtk_range_get_adjustment (GTK_RANGE (my verticalScrollBar)); adj -> page_size = sliderSize; //gtk_adjustment_set_value (adj, value); gtk_adjustment_changed (adj); gtk_range_set_increments (GTK_RANGE (my verticalScrollBar), 1, sliderSize - 1); #elif motif XmScrollBarSetValues (my verticalScrollBar, my top, sliderSize, 1, sliderSize - 1, False); #endif my history [my historyPointer]. top = 0/*my top*/; } #if gtk static void gui_cb_verticalScroll (GtkRange *rng, gpointer void_me) { iam (HyperPage); double value = gtk_range_get_value (GTK_RANGE (rng)); if (value != my top) { my top = value; Graphics_clearWs (my g); initScreen (me); my v_draw (); // do not wait for expose event updateVerticalScrollBar (me); } } #else static void gui_cb_verticalScroll (GUI_ARGS) { GUI_IAM (HyperPage); int value, sliderSize, incr, pincr; #if gtk double value = gtk_range_get_value (GTK_RANGE (w)); #elif motif XmScrollBarGetValues (w, & value, & sliderSize, & incr, & pincr); #endif if (value != my top) { my top = value; Graphics_clearWs (my g); initScreen (me); my v_draw (); // do not wait for expose event updateVerticalScrollBar (me); } } #endif static void menu_cb_pageUp (EDITOR_ARGS) { EDITOR_IAM (HyperPage); int value, sliderSize, incr, pincr; if (! my verticalScrollBar) return; #if gtk value = gtk_range_get_value (GTK_RANGE (my verticalScrollBar)); sliderSize = 1; pincr = PAGE_HEIGHT * 5 - 1; #elif motif XmScrollBarGetValues (my verticalScrollBar, & value, & sliderSize, & incr, & pincr); #endif value -= pincr; if (value < 0) value = 0; if (value != my top) { my top = value; Graphics_clearWs (my g); initScreen (me); my v_draw (); // do not wait for expose event updateVerticalScrollBar (me); } } static void menu_cb_pageDown (EDITOR_ARGS) { EDITOR_IAM (HyperPage); int value, sliderSize, incr, pincr; if (! my verticalScrollBar) return; #if gtk value = gtk_range_get_value (GTK_RANGE (my verticalScrollBar)); sliderSize = 1; pincr = PAGE_HEIGHT * 5 - 1; #elif motif XmScrollBarGetValues (my verticalScrollBar, & value, & sliderSize, & incr, & pincr); #endif value += pincr; if (value > (int) (PAGE_HEIGHT * 5) - sliderSize) value = (int) (PAGE_HEIGHT * 5) - sliderSize; if (value != my top) { my top = value; Graphics_clearWs (my g); initScreen (me); my v_draw (); // do not wait for expose event updateVerticalScrollBar (me); } } /********** **********/ static void do_back (HyperPage me) { if (my historyPointer <= 0) return; autostring page = Melder_wcsdup_f (my history [-- my historyPointer]. page); // temporary, because pointer will be moved int top = my history [my historyPointer]. top; if (my v_goToPage (page.peek())) { my top = top; HyperPage_clear (me); updateVerticalScrollBar (me); } } static void menu_cb_back (EDITOR_ARGS) { EDITOR_IAM (HyperPage); do_back (me); } static void gui_button_cb_back (I, GuiButtonEvent event) { (void) event; iam (HyperPage); do_back (me); } static void do_forth (HyperPage me) { if (my historyPointer >= 19 || ! my history [my historyPointer + 1]. page) return; autostring page = Melder_wcsdup_f (my history [++ my historyPointer]. page); int top = my history [my historyPointer]. top; if (my v_goToPage (page.peek())) { my top = top; HyperPage_clear (me); updateVerticalScrollBar (me); } } static void menu_cb_forth (EDITOR_ARGS) { EDITOR_IAM (HyperPage); do_forth (me); } static void gui_button_cb_forth (I, GuiButtonEvent event) { (void) event; iam (HyperPage); do_forth (me); } void structHyperPage :: v_createMenus () { HyperPage_Parent :: v_createMenus (); Editor_addCommand (this, L"File", L"PostScript settings...", 0, menu_cb_postScriptSettings); #ifdef macintosh Editor_addCommand (this, L"File", L"Page setup...", 0, menu_cb_pageSetup); #endif Editor_addCommand (this, L"File", L"Print page...", 'P', menu_cb_print); Editor_addCommand (this, L"File", L"-- close --", 0, NULL); if (v_hasHistory ()) { Editor_addMenu (this, L"Go to", 0); Editor_addCommand (this, L"Go to", L"Search for page...", 0, menu_cb_searchForPage); Editor_addCommand (this, L"Go to", L"Back", GuiMenu_OPTION | GuiMenu_LEFT_ARROW, menu_cb_back); Editor_addCommand (this, L"Go to", L"Forward", GuiMenu_OPTION | GuiMenu_RIGHT_ARROW, menu_cb_forth); Editor_addCommand (this, L"Go to", L"-- page --", 0, NULL); Editor_addCommand (this, L"Go to", L"Page up", GuiMenu_PAGE_UP, menu_cb_pageUp); Editor_addCommand (this, L"Go to", L"Page down", GuiMenu_PAGE_DOWN, menu_cb_pageDown); } Editor_addMenu (this, L"Font", 0); Editor_addCommand (this, L"Font", L"Font size...", 0, menu_cb_fontSize); fontSizeButton_10 = Editor_addCommand (this, L"Font", L"10", GuiMenu_CHECKBUTTON, menu_cb_10); fontSizeButton_12 = Editor_addCommand (this, L"Font", L"12", GuiMenu_CHECKBUTTON, menu_cb_12); fontSizeButton_14 = Editor_addCommand (this, L"Font", L"14", GuiMenu_CHECKBUTTON, menu_cb_14); fontSizeButton_18 = Editor_addCommand (this, L"Font", L"18", GuiMenu_CHECKBUTTON, menu_cb_18); fontSizeButton_24 = Editor_addCommand (this, L"Font", L"24", GuiMenu_CHECKBUTTON, menu_cb_24); Editor_addCommand (this, L"Font", L"-- font --", 0, NULL); Editor_addCommand (this, L"Font", L"Font...", 0, menu_cb_font); } /********** **********/ static void gui_drawingarea_cb_resize (I, GuiDrawingAreaResizeEvent event) { iam (HyperPage); if (my g == NULL) return; Graphics_setWsViewport (my g, 0, event -> width, 0, event -> height); Graphics_setWsWindow (my g, 0.0, my rightMargin = event -> width / resolution, PAGE_HEIGHT - event -> height / resolution, PAGE_HEIGHT); Graphics_updateWs (my g); updateVerticalScrollBar (me); } static void gui_button_cb_previousPage (I, GuiButtonEvent event) { (void) event; iam (HyperPage); HyperPage_goToPage_i (me, my v_getCurrentPageNumber () > 1 ? my v_getCurrentPageNumber () - 1 : my v_getNumberOfPages ()); } static void gui_button_cb_nextPage (I, GuiButtonEvent event) { (void) event; iam (HyperPage); long currentPageNumber = my v_getCurrentPageNumber (); HyperPage_goToPage_i (me, currentPageNumber < my v_getNumberOfPages () ? currentPageNumber + 1 : 1); } void structHyperPage :: v_createChildren () { int height = Machine_getTextHeight (); int y = Machine_getMenuBarHeight () + 4; #if gtk holder = gtk_hbox_new (FALSE, 0); gtk_box_pack_start (GTK_BOX (d_windowForm), GTK_WIDGET (holder), false, false, 0); GuiObject_show (holder); #elif motif holder = d_windowForm; #endif /***** Create navigation buttons. *****/ if (v_hasHistory ()) { GuiButton_createShown (holder, 4, 48, y, y + height, L"<", gui_button_cb_back, this, 0); GuiButton_createShown (holder, 54, 98, y, y + height, L">", gui_button_cb_forth, this, 0); } if (v_isOrdered ()) { GuiButton_createShown (holder, 174, 218, y, y + height, L"< 1", gui_button_cb_previousPage, this, 0); GuiButton_createShown (holder, 224, 268, y, y + height, L"1 >", gui_button_cb_nextPage, this, 0); } #if gtk GuiObject scrollBox = gtk_hbox_new (false, 0); gtk_box_pack_end (GTK_BOX (d_windowForm), GTK_WIDGET (scrollBox), true, true, 0); drawingArea = GuiDrawingArea_create (GTK_WIDGET (scrollBox), 0, 600, 0, 800, gui_drawingarea_cb_expose, gui_drawingarea_cb_click, NULL, gui_drawingarea_cb_resize, this, GuiDrawingArea_BORDER); gtk_widget_set_double_buffered (GTK_WIDGET (drawingArea), FALSE); gtk_box_pack_start (GTK_BOX (scrollBox), GTK_WIDGET (drawingArea), true, true, 0); createVerticalScrollBar (this, scrollBox); GuiObject_show (drawingArea); GuiObject_show (scrollBox); #elif motif /***** Create scroll bar. *****/ createVerticalScrollBar (this, d_windowForm); /***** Create drawing area. *****/ drawingArea = GuiDrawingArea_createShown (d_windowForm, 0, - Machine_getScrollBarWidth (), y + height + 8, - Machine_getScrollBarWidth (), gui_drawingarea_cb_expose, gui_drawingarea_cb_click, NULL, gui_drawingarea_cb_resize, this, GuiDrawingArea_BORDER); #endif } void HyperPage_init (HyperPage me, GuiObject parent, const wchar *title, Data data) { resolution = Gui_getResolution (parent); Editor_init (me, parent, 0, 0, 6 * resolution + 30, 800, title, data); therror #if motif Melder_assert (XtWindow (my drawingArea)); #endif my g = Graphics_create_xmdrawingarea (my drawingArea); Graphics_setAtSignIsLink (my g, TRUE); Graphics_setDollarSignIsCode (my g, TRUE); Graphics_setFont (my g, kGraphics_font_TIMES); if (prefs_font != kGraphics_font_TIMES && prefs_font != kGraphics_font_HELVETICA) prefs_font = kGraphics_font_TIMES; // ensure Unicode compatibility my font = prefs_font; setFontSize (me, prefs_fontSize); struct structGuiDrawingAreaResizeEvent event = { my drawingArea, 0 }; event. width = GuiObject_getWidth (my drawingArea); event. height = GuiObject_getHeight (my drawingArea); gui_drawingarea_cb_resize (me, & event); #if gtk g_signal_connect (G_OBJECT (my verticalScrollBar), "value-changed", G_CALLBACK (gui_cb_verticalScroll), me); #elif motif XtAddCallback (my verticalScrollBar, XmNvalueChangedCallback, gui_cb_verticalScroll, (XtPointer) me); XtAddCallback (my verticalScrollBar, XmNdragCallback, gui_cb_verticalScroll, (XtPointer) me); #endif updateVerticalScrollBar (me); // scroll to the top (my top == 0) } void HyperPage_clear (HyperPage me) { Graphics_updateWs (my g); forget (my links); } void structHyperPage :: v_dataChanged () { int oldError = Melder_hasError (); // this method can be called during error time (void) v_goToPage (currentPageTitle); if (Melder_hasError () && ! oldError) Melder_flushError (NULL); HyperPage_clear (this); updateVerticalScrollBar (this); } int HyperPage_goToPage (I, const wchar_t *title) { iam (HyperPage); switch (my v_goToPage (title)) { case -1: return 0; case 0: HyperPage_clear (me); return 0; } saveHistory (me, title); /* Last chance: HyperPage_clear will destroy "title" !!! */ Melder_free (my currentPageTitle); my currentPageTitle = Melder_wcsdup_f (title); my top = 0; HyperPage_clear (me); updateVerticalScrollBar (me); /* Scroll to the top (my top == 0). */ return 1; } void HyperPage_goToPage_i (I, long i) { iam (HyperPage); my v_goToPage_i (i); // catch -> HyperPage_clear (me); ? my top = 0; HyperPage_clear (me); updateVerticalScrollBar (me); /* Scroll to the top (my top == 0). */ } void HyperPage_setEntryHint (I, const wchar_t *hint) { iam (HyperPage); Melder_free (my entryHint); my entryHint = Melder_wcsdup_f (hint); } /* End of file HyperPage.cpp */ sources_5316/sys/Ui.cpp0000644000176700017670000016231211751211620013623 0ustar paulpaul/* Ui.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include #include "longchar.h" #include "machine.h" #include "Gui.h" #include "Collection.h" #include "UiP.h" #include "Editor.h" #include "Graphics.h" /* colours. */ /***** class UiField: the things that have values in an UiForm dialog *****/ /* Values for 'type'. */ #define UI_REAL 1 #define UI_REAL_OR_UNDEFINED 2 #define UI_POSITIVE 3 #define UI_INTEGER 4 #define UI_NATURAL 5 #define UI_WORD 6 #define UI_SENTENCE 7 #define UI_COLOUR 8 #define UI_CHANNEL 9 #define UI_LABELLEDTEXT_MIN UI_REAL #define UI_LABELLEDTEXT_MAX UI_CHANNEL #define UI_LABEL 10 #define UI_TEXT 11 #define UI_BOOLEAN 12 #define UI_RADIO 13 #define UI_OPTIONMENU 14 #define UI_LIST 15 Thing_implement (UiField, Thing, 0); void structUiField :: v_destroy () { Melder_free (formLabel); Melder_free (stringValue); Melder_free (stringValueA); Melder_free (stringDefaultValue); forget (options); UiField_Parent :: v_destroy (); } static UiField UiField_create (int type, const wchar_t *name) { autoUiField me = Thing_new (UiField); wchar shortName [101], *p; my type = type; my formLabel = Melder_wcsdup (name); wcscpy (shortName, name); /* * Strip parentheses and colon off parameter name. */ //p = wcschr (shortName, ':'); /* ppgb 20101015: no idea why this used to be here */ //if (p) *p = '\0'; if ((p = (wchar *) wcschr (shortName, '(')) != NULL) { *p = '\0'; if (p - shortName > 0 && p [-1] == ' ') p [-1] = '\0'; } p = shortName; if (*p != '\0' && p [wcslen (p) - 1] == ':') p [wcslen (p) - 1] = '\0'; Thing_setName (me.peek(), shortName); return me.transfer(); } /***** class UiOption: radio buttons and menu options *****/ Thing_define (UiOption, Thing) { // new data: public: GuiObject toggle; }; Thing_implement (UiOption, Thing, 0); static Any UiOption_create (const wchar_t *label) { UiOption me = Thing_new (UiOption); Thing_setName (me, label); return me; } static void gui_radiobutton_cb_toggled (I, GuiRadioButtonEvent event) { #if !gtk iam (UiField); for (int i = 1; i <= my options -> size; i ++) { UiOption b = static_cast (my options -> item [i]); GuiRadioButton_setValue (b -> toggle, b -> toggle == event -> toggle); } #endif } Any UiRadio_addButton (I, const wchar_t *label) { iam (UiField); UiOption thee; if (me == NULL) return NULL; Melder_assert (my type == UI_RADIO || my type == UI_OPTIONMENU); thee = static_cast (UiOption_create (label)); Collection_addItem (my options, thee); return thee; } #if motif // TODO: Ik denk dat dit Native GTK gedrag is (als dit alleen het label update) static void cb_optionChanged (GuiObject w, XtPointer void_me, XtPointer call) { iam (UiField); (void) call; for (int i = 1; i <= my options -> size; i ++) { UiOption b = static_cast (my options -> item [i]); #if motif if (b -> toggle == w) { XtVaSetValues (my cascadeButton, XmNlabelString, Melder_peekWcsToUtf8 (b -> name), NULL); XmToggleButtonSetState (b -> toggle, TRUE, FALSE); if (Melder_debug == 11) { Melder_warning (i, " \"", b -> name, "\""); } } else { XmToggleButtonSetState (b -> toggle, FALSE, FALSE); } #endif } } #endif Any UiOptionMenu_addButton (I, const wchar_t *label) { iam (UiField); UiOption thee; if (me == NULL) return NULL; Melder_assert (my type == UI_RADIO || my type == UI_OPTIONMENU); thee = static_cast (UiOption_create (label)); Collection_addItem (my options, thee); return thee; } /***** Things to do with UiField objects. *****/ static void UiField_setDefault (UiField me) { switch (my type) { case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: case UI_INTEGER: case UI_NATURAL: case UI_WORD: case UI_SENTENCE: case UI_COLOUR: case UI_CHANNEL: case UI_TEXT: { GuiText_setString (my text, my stringDefaultValue); } break; case UI_BOOLEAN: { GuiCheckButton_setValue (my toggle, my integerDefaultValue); } break; case UI_RADIO: { for (int i = 1; i <= my options -> size; i ++) { UiOption b = static_cast (my options -> item [i]); GuiRadioButton_setValue (b -> toggle, i == my integerDefaultValue); } } break; case UI_OPTIONMENU: { #if gtk gtk_combo_box_set_active (GTK_COMBO_BOX (my cascadeButton), my integerDefaultValue - 1); #elif motif for (int i = 1; i <= my options -> size; i ++) { UiOption b = static_cast (my options -> item [i]); XmToggleButtonSetState (b -> toggle, i == my integerDefaultValue, False); if (i == my integerDefaultValue) { XtVaSetValues (my cascadeButton, XmNlabelString, Melder_peekWcsToUtf8 (b -> name), NULL); } } #endif } break; case UI_LIST: { GuiList_selectItem (my list, my integerDefaultValue); } } } static int colourToValue (UiField me, wchar_t *string) { wchar_t *p = string; while (*p == ' ' || *p == '\t') p ++; *p = tolower (*p); int first = *p; if (first == '{') { my colourValue. red = Melder_atof (++ p); p = (wchar *) wcschr (p, ','); if (p == NULL) return 0; my colourValue. green = Melder_atof (++ p); p = (wchar *) wcschr (p, ','); if (p == NULL) return 0; my colourValue. blue = Melder_atof (++ p); } else { *p = tolower (*p); if (wcsequ (p, L"black")) my colourValue = Graphics_BLACK; else if (wcsequ (p, L"white")) my colourValue = Graphics_WHITE; else if (wcsequ (p, L"red")) my colourValue = Graphics_RED; else if (wcsequ (p, L"green")) my colourValue = Graphics_GREEN; else if (wcsequ (p, L"blue")) my colourValue = Graphics_BLUE; else if (wcsequ (p, L"yellow")) my colourValue = Graphics_YELLOW; else if (wcsequ (p, L"cyan")) my colourValue = Graphics_CYAN; else if (wcsequ (p, L"magenta")) my colourValue = Graphics_MAGENTA; else if (wcsequ (p, L"maroon")) my colourValue = Graphics_MAROON; else if (wcsequ (p, L"lime")) my colourValue = Graphics_LIME; else if (wcsequ (p, L"navy")) my colourValue = Graphics_NAVY; else if (wcsequ (p, L"teal")) my colourValue = Graphics_TEAL; else if (wcsequ (p, L"purple")) my colourValue = Graphics_PURPLE; else if (wcsequ (p, L"olive")) my colourValue = Graphics_OLIVE; else if (wcsequ (p, L"pink")) my colourValue = Graphics_PINK; else if (wcsequ (p, L"silver")) my colourValue = Graphics_SILVER; else if (wcsequ (p, L"grey")) my colourValue = Graphics_GREY; else { *p = first; return 0; } *p = first; } return 1; } static void UiField_widgetToValue (UiField me) { switch (my type) { case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: { autostring dirty = GuiText_getString (my text); // the text as typed by the user Interpreter_numericExpression (NULL, dirty.peek(), & my realValue); therror /* * Put a clean version of the new value in the form. * If the value is equal to the default, make sure that any default comments are included. */ if (my realValue == Melder_atof (my stringDefaultValue)) { GuiText_setString (my text, my stringDefaultValue); } else { wchar_t clean [40]; wcscpy (clean, Melder_double (my realValue)); /* * If the default is overtly real, the shown value must be as well. */ if ((wcschr (my stringDefaultValue, '.') || wcschr (my stringDefaultValue, 'e')) && ! (wcschr (clean, '.') || wcschr (clean, 'e'))) { wcscat (clean, L".0"); } GuiText_setString (my text, clean); } if (my realValue == NUMundefined && my type != UI_REAL_OR_UNDEFINED) Melder_throw (L_LEFT_DOUBLE_QUOTE, my name, L_RIGHT_DOUBLE_QUOTE L" has the value \"undefined\"."); if (my type == UI_POSITIVE && my realValue <= 0.0) Melder_throw (L_LEFT_DOUBLE_QUOTE, my name, L_RIGHT_DOUBLE_QUOTE L" must be greater than 0.0."); } break; case UI_INTEGER: case UI_NATURAL: case UI_CHANNEL: { autostring dirty = GuiText_getString (my text); if (my type == UI_CHANNEL && (wcsequ (dirty.peek(), L"Left") || wcsequ (dirty.peek(), L"Mono"))) { my integerValue = 1; } else if (my type == UI_CHANNEL && (wcsequ (dirty.peek(), L"Right") || wcsequ (dirty.peek(), L"Stereo"))) { my integerValue = 2; } else { double realValue; Interpreter_numericExpression (NULL, dirty.peek(), & realValue); therror my integerValue = floor (realValue + 0.5); } if (my integerValue == wcstol (my stringDefaultValue, NULL, 10)) { GuiText_setString (my text, my stringDefaultValue); } else { GuiText_setString (my text, Melder_integer (my integerValue)); } if (my type == UI_NATURAL && my integerValue < 1) Melder_throw (L_LEFT_DOUBLE_QUOTE, my name, L_RIGHT_DOUBLE_QUOTE L" must be a positive whole number."); } break; case UI_WORD: { Melder_free (my stringValue); my stringValue = GuiText_getString (my text); wchar_t *p = my stringValue; while (*p != '\0') { if (*p == ' ' || *p == '\t') *p = '\0'; p ++; } GuiText_setString (my text, my stringValue); } break; case UI_SENTENCE: case UI_TEXT: { Melder_free (my stringValue); my stringValue = GuiText_getString (my text); } break; case UI_BOOLEAN: { my integerValue = GuiCheckButton_getValue (my toggle); } break; case UI_RADIO: { my integerValue = 0; for (int i = 1; i <= my options -> size; i ++) { UiOption b = static_cast (my options -> item [i]); if (GuiRadioButton_getValue (b -> toggle)) my integerValue = i; } if (my integerValue == 0) Melder_throw ("No option chosen for " L_LEFT_DOUBLE_QUOTE, my name, L_RIGHT_DOUBLE_QUOTE "."); } break; case UI_OPTIONMENU: { my integerValue = 0; #if gtk // TODO: Graag even een check :) my integerValue = gtk_combo_box_get_active (GTK_COMBO_BOX (my cascadeButton)) + 1; #elif motif for (int i = 1; i <= my options -> size; i ++) { UiOption b = static_cast (my options -> item [i]); if (XmToggleButtonGetState (b -> toggle)) my integerValue = i; } #endif if (my integerValue == 0) Melder_throw ("No option chosen for " L_LEFT_DOUBLE_QUOTE, my name, L_RIGHT_DOUBLE_QUOTE "."); } break; case UI_LIST: { long numberOfSelected, *selected = GuiList_getSelectedPositions (my list, & numberOfSelected); // BUG memory if (selected == NULL) { Melder_warning (L"No items selected."); my integerValue = 1; } else { if (numberOfSelected > 1) Melder_warning (L"More than one item selected."); my integerValue = selected [1]; NUMvector_free (selected, 1); } } break; case UI_COLOUR: { autostring string = GuiText_getString (my text); if (colourToValue (me, string.peek())) { // do nothing } else { Interpreter_numericExpression (NULL, string.peek(), & my colourValue. red); therror my colourValue. green = my colourValue. blue = my colourValue. red; } } } } static void UiField_stringToValue (UiField me, const wchar *string, Interpreter interpreter) { switch (my type) { case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: { if (wcsspn (string, L" \t") == wcslen (string)) Melder_throw (L"Argument `", my name, L"' empty."); Interpreter_numericExpression (interpreter, string, & my realValue); if (my realValue == NUMundefined && my type != UI_REAL_OR_UNDEFINED) Melder_throw (L"\"", my name, "\" has the value \"undefined\"."); if (my type == UI_POSITIVE && my realValue <= 0.0) Melder_throw ("\"", my name, "\" must be greater than 0."); } break; case UI_INTEGER: case UI_NATURAL: case UI_CHANNEL: { if (wcsspn (string, L" \t") == wcslen (string)) Melder_throw ("Argument \"", my name, "\" empty."); if (my type == UI_CHANNEL && (wcsequ (string, L"All") || wcsequ (string, L"Average"))) { my integerValue = 0; } else if (my type == UI_CHANNEL && (wcsequ (string, L"Left") || wcsequ (string, L"Mono"))) { my integerValue = 1; } else if (my type == UI_CHANNEL && (wcsequ (string, L"Right") || wcsequ (string, L"Stereo"))) { my integerValue = 2; } else { double realValue; Interpreter_numericExpression (interpreter, string, & realValue); my integerValue = floor (realValue + 0.5); } if (my type == UI_NATURAL && my integerValue < 1) Melder_throw ("\"", my name, "\" must be a positive whole number."); } break; case UI_WORD: case UI_SENTENCE: case UI_TEXT: { Melder_free (my stringValue); my stringValue = Melder_wcsdup_f (string); } break; case UI_BOOLEAN: { if (! string [0]) Melder_throw ("Empty argument for toggle button."); my integerValue = string [0] == '1' || string [0] == 'y' || string [0] == 'Y' || string [0] == 't' || string [0] == 'T'; } break; case UI_RADIO: case UI_OPTIONMENU: { my integerValue = 0; for (int i = 1; i <= my options -> size; i ++) { UiOption b = static_cast (my options -> item [i]); if (wcsequ (string, b -> name)) my integerValue = i; } if (my integerValue == 0) { /* * Retry with different case. */ for (int i = 1; i <= my options -> size; i ++) { UiOption b = static_cast (my options -> item [i]); wchar_t name2 [100]; wcscpy (name2, b -> name); if (islower (name2 [0])) name2 [0] = toupper (name2 [0]); else if (isupper (name2 [0])) name2 [0] = tolower (name2 [0]); if (wcsequ (string, name2)) my integerValue = i; } } if (my integerValue == 0) { Melder_throw ("Field \"", my name, "\" cannot have the value \"", string, "\"."); } } break; case UI_LIST: { long i = 1; for (; i <= my numberOfStrings; i ++) if (wcsequ (string, my strings [i])) break; if (i > my numberOfStrings) Melder_throw ("Field \"", my name, "\" cannot have the value \"", string, "\"."); my integerValue = i; } break; case UI_COLOUR: { autostring string2 = Melder_wcsdup_f (string); if (colourToValue (me, string2.peek())) { /* OK */ } else { try { Interpreter_numericExpression (interpreter, string2.peek(), & my colourValue. red); my colourValue. green = my colourValue. blue = my colourValue. red; } catch (MelderError) { Melder_clearError (); Melder_throw ("Cannot compute a colour from \"", string2.peek(), "\"."); } } } break; default: { Melder_throw ("Unknown field type ", my type, "."); } } } /***** History mechanism. *****/ static MelderString theHistory = { 0 }; void UiHistory_write (const wchar_t *string) { MelderString_append (& theHistory, string); } wchar_t *UiHistory_get (void) { return theHistory.string; } void UiHistory_clear (void) { MelderString_empty (& theHistory); } /***** class UiForm: dialog windows *****/ Thing_implement (UiForm, Thing, 0); bool (*theAllowExecutionHookHint) (void *closure) = NULL; void *theAllowExecutionClosureHint = NULL; void Ui_setAllowExecutionHook (bool (*allowExecutionHook) (void *closure), void *allowExecutionClosure) { theAllowExecutionHookHint = allowExecutionHook; theAllowExecutionClosureHint = allowExecutionClosure; } void structUiForm :: v_destroy () { for (int ifield = 1; ifield <= numberOfFields; ifield ++) forget (field [ifield]); if (d_dialogForm) { GuiObject_destroy (GuiObject_parent (d_dialogForm)); } Melder_free (invokingButtonTitle); Melder_free (helpTitle); UiForm_Parent :: v_destroy (); } static void gui_button_cb_revert (I, GuiButtonEvent event) { (void) event; iam (UiForm); for (int ifield = 1; ifield <= my numberOfFields; ifield ++) UiField_setDefault (my field [ifield]); } static void gui_dialog_cb_close (I) { iam (UiForm); if (my cancelCallback) my cancelCallback (me, my buttonClosure); GuiObject_hide (my d_dialogForm); if (my destroyWhenUnmanaged) forget (me); } static void gui_button_cb_cancel (I, GuiButtonEvent event) { (void) event; iam (UiForm); if (my cancelCallback) my cancelCallback (me, my buttonClosure); GuiObject_hide (my d_dialogForm); if (my destroyWhenUnmanaged) forget (me); } void UiForm_widgetsToValues (I) { iam (UiForm); try { for (int ifield = 1; ifield <= my numberOfFields; ifield ++) UiField_widgetToValue (my field [ifield]); } catch (MelderError) { Melder_throw ("Please correct command window " L_LEFT_DOUBLE_QUOTE, my name, L_RIGHT_DOUBLE_QUOTE " or cancel."); } } static void UiForm_okOrApply (I, GuiObject button, int hide) { iam (UiForm); if (my allowExecutionHook && ! my allowExecutionHook (my allowExecutionClosure)) { Melder_error_ ("Cannot execute command window " L_LEFT_DOUBLE_QUOTE, my name, L_RIGHT_DOUBLE_QUOTE L"."); Melder_flushError (NULL); return; } try { UiForm_widgetsToValues (me); } catch (MelderError) { Melder_flushError (NULL); return; } /* In the next, w must become my okButton? */ /*XtRemoveCallback (w, XmNactivateCallback, UiForm_ok, void_me); /* FIX */ if (my okButton) GuiObject_setSensitive (my okButton, false); for (int i = 1; i <= my numberOfContinueButtons; i ++) if (my continueButtons [i]) GuiObject_setSensitive (my continueButtons [i], false); if (my applyButton) GuiObject_setSensitive (my applyButton, false); if (my cancelButton) GuiObject_setSensitive (my cancelButton, false); if (my revertButton) GuiObject_setSensitive (my revertButton, false); if (my helpButton) GuiObject_setSensitive (my helpButton, false); #if motif XmUpdateDisplay (my d_dialogForm); #endif if (my isPauseForm) { for (int i = 1; i <= my numberOfContinueButtons; i ++) { if (button == my continueButtons [i]) { my clickedContinueButton = i; } } } /* * Keep the gate for error handling. */ try { my okCallback (me, NULL, NULL, NULL, false, my buttonClosure); therror /* * Write everything to history. Before destruction! */ if (! my isPauseForm) { UiHistory_write (L"\n"); UiHistory_write (my invokingButtonTitle); int size = my numberOfFields; while (size >= 1 && my field [size] -> type == UI_LABEL) size --; // ignore trailing fields without a value for (int ifield = 1; ifield <= size; ifield ++) { UiField field = my field [ifield]; switch (field -> type) { case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: { UiHistory_write (L" "); UiHistory_write (Melder_double (field -> realValue)); } break; case UI_INTEGER: case UI_NATURAL: case UI_CHANNEL: { UiHistory_write (L" "); UiHistory_write (Melder_integer (field -> integerValue)); } break; case UI_WORD: case UI_SENTENCE: case UI_TEXT: { if (ifield < size && (field -> stringValue [0] == '\0' || wcschr (field -> stringValue, ' '))) { UiHistory_write (L" \""); UiHistory_write (field -> stringValue); // BUG: should double any double quotes UiHistory_write (L"\""); } else { UiHistory_write (L" "); UiHistory_write (field -> stringValue); } } break; case UI_BOOLEAN: { UiHistory_write (field -> integerValue ? L" yes" : L" no"); } break; case UI_RADIO: case UI_OPTIONMENU: { UiOption b = static_cast (field -> options -> item [field -> integerValue]); if (ifield < size && (b -> name [0] == '\0' || wcschr (b -> name, ' '))) { UiHistory_write (L" \""); UiHistory_write (b -> name); UiHistory_write (L"\""); } else { UiHistory_write (L" "); UiHistory_write (b -> name); } } break; case UI_LIST: { if (ifield < size && (field -> strings [field -> integerValue] [0] == '\0' || wcschr (field -> strings [field -> integerValue], ' '))) { UiHistory_write (L" \""); UiHistory_write (field -> strings [field -> integerValue]); UiHistory_write (L"\""); } else { UiHistory_write (L" "); UiHistory_write (field -> strings [field -> integerValue]); } } break; case UI_COLOUR: { UiHistory_write (L" "); UiHistory_write (Graphics_Colour_name (field -> colourValue)); } } } } if (hide) { GuiObject_hide (my d_dialogForm); if (my destroyWhenUnmanaged) { forget (me); return; } } } catch (MelderError) { /* * If a solution has already been suggested, or the "error" was actually a conscious user action, do not add anything more. */ if (! wcsstr (Melder_getError (), L"Please ") && ! wcsstr (Melder_getError (), L"You could ") && ! wcsstr (Melder_getError (), L"You interrupted ") && ! wcsstr (Melder_getError (), L"Interrupted!")) { /* * Otherwise, show a generic message. */ if (wcsstr (Melder_getError (), L"Selection changed!")) { Melder_error_ ("Please change the selection in the object list, or click Cancel in the command window " L_LEFT_DOUBLE_QUOTE, my name, L_RIGHT_DOUBLE_QUOTE L"."); } else { Melder_error_ ("Please change something in the command window " L_LEFT_DOUBLE_QUOTE, my name, L_RIGHT_DOUBLE_QUOTE L", or click Cancel in that window."); } } Melder_flushError (NULL); } if (my okButton) GuiObject_setSensitive (my okButton, true); for (int i = 1; i <= my numberOfContinueButtons; i ++) if (my continueButtons [i]) GuiObject_setSensitive (my continueButtons [i], true); if (my applyButton) GuiObject_setSensitive (my applyButton, true); if (my cancelButton) GuiObject_setSensitive (my cancelButton, true); if (my revertButton) GuiObject_setSensitive (my revertButton, true); if (my helpButton) GuiObject_setSensitive (my helpButton, true); } static void gui_button_cb_ok (I, GuiButtonEvent event) { (void) event; iam (UiForm); UiForm_okOrApply (me, event -> button, true); } static void gui_button_cb_apply (I, GuiButtonEvent event) { (void) event; iam (UiForm); UiForm_okOrApply (me, event -> button, false); } static void gui_button_cb_help (I, GuiButtonEvent event) { (void) event; iam (UiForm); Melder_help (my helpTitle); } UiForm UiForm_create (GuiObject parent, const wchar *title, void (*okCallback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure), void *buttonClosure, const wchar *invokingButtonTitle, const wchar *helpTitle) { autoUiForm me = Thing_new (UiForm); my d_dialogParent = parent; Thing_setName (me.peek(), title); my okCallback = okCallback; my buttonClosure = buttonClosure; my invokingButtonTitle = Melder_wcsdup (invokingButtonTitle); my helpTitle = Melder_wcsdup (helpTitle); return me.transfer(); } void UiForm_setPauseForm (I, int numberOfContinueButtons, int defaultContinueButton, int cancelContinueButton, const wchar *continue1, const wchar *continue2, const wchar *continue3, const wchar *continue4, const wchar *continue5, const wchar *continue6, const wchar *continue7, const wchar *continue8, const wchar *continue9, const wchar *continue10, void (*cancelCallback) (Any dia, void *closure)) { iam (UiForm); my isPauseForm = true; my numberOfContinueButtons = numberOfContinueButtons; my defaultContinueButton = defaultContinueButton; my cancelContinueButton = cancelContinueButton; my continueTexts [1] = continue1; my continueTexts [2] = continue2; my continueTexts [3] = continue3; my continueTexts [4] = continue4; my continueTexts [5] = continue5; my continueTexts [6] = continue6; my continueTexts [7] = continue7; my continueTexts [8] = continue8; my continueTexts [9] = continue9; my continueTexts [10] = continue10; my cancelCallback = cancelCallback; } static void commonOkCallback (UiForm dia, const wchar *dummy, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure) { EditorCommand cmd = (EditorCommand) closure; (void) dia; (void) dummy; (void) invokingButtonTitle; (void) modified; cmd -> commandCallback (cmd -> d_editor, cmd, cmd -> d_uiform, NULL, interpreter); therror } UiForm UiForm_createE (EditorCommand cmd, const wchar *title, const wchar *invokingButtonTitle, const wchar *helpTitle) { Editor editor = (Editor) cmd -> d_editor; UiForm dia = UiForm_create (editor -> d_windowForm, title, commonOkCallback, cmd, invokingButtonTitle, helpTitle); dia -> command = cmd; return dia; } static UiField UiForm_addField (UiForm me, int type, const wchar *label) { if (my numberOfFields == MAXIMUM_NUMBER_OF_FIELDS) Melder_throw ("Cannot have more than ", MAXIMUM_NUMBER_OF_FIELDS, "in a form."); return my field [++ my numberOfFields] = UiField_create (type, label); } Any UiForm_addReal (I, const wchar *label, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_REAL, label); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } Any UiForm_addRealOrUndefined (I, const wchar *label, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_REAL_OR_UNDEFINED, label); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } Any UiForm_addPositive (I, const wchar *label, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_POSITIVE, label); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } Any UiForm_addInteger (I, const wchar *label, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_INTEGER, label); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } Any UiForm_addNatural (I, const wchar *label, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_NATURAL, label); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } Any UiForm_addWord (I, const wchar *label, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_WORD, label); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } Any UiForm_addSentence (I, const wchar *label, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_SENTENCE, label); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } Any UiForm_addLabel (I, const wchar *name, const wchar *label) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_LABEL, name); thy stringValue = Melder_wcsdup (label); return thee.transfer(); } Any UiForm_addBoolean (I, const wchar *label, int defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_BOOLEAN, label); thy integerDefaultValue = defaultValue; return thee.transfer(); } Any UiForm_addText (I, const wchar *name, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_TEXT, name); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } Any UiForm_addRadio (I, const wchar *label, int defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_RADIO, label); thy integerDefaultValue = defaultValue; thy options = Ordered_create (); return thee.transfer(); } Any UiForm_addOptionMenu (I, const wchar *label, int defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_OPTIONMENU, label); thy integerDefaultValue = defaultValue; thy options = Ordered_create (); return thee.transfer(); } Any UiForm_addList (I, const wchar *label, long numberOfStrings, const wchar **strings, long defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_LIST, label); thy numberOfStrings = numberOfStrings; thy strings = strings; thy integerDefaultValue = defaultValue; return thee.transfer(); } Any UiForm_addColour (I, const wchar *label, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_COLOUR, label); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } Any UiForm_addChannel (I, const wchar *label, const wchar *defaultValue) { iam (UiForm); autoUiField thee = UiForm_addField (me, UI_CHANNEL, label); thy stringDefaultValue = Melder_wcsdup (defaultValue); return thee.transfer(); } #define DIALOG_X 150 #define DIALOG_Y 70 #define HELP_BUTTON_WIDTH 60 #define STANDARDS_BUTTON_WIDTH 100 #define REVERT_BUTTON_WIDTH 60 #define STOP_BUTTON_WIDTH 50 #define HELP_BUTTON_X 20 #define LIST_HEIGHT 192 static MelderString theFinishBuffer = { 0 }; static void appendColon (void) { long length = theFinishBuffer.length; if (length < 1) return; wchar_t lastCharacter = theFinishBuffer.string [length - 1]; if (lastCharacter == ':' || lastCharacter == '?' || lastCharacter == '.') return; MelderString_appendCharacter (& theFinishBuffer, ':'); } void UiForm_finish (I) { iam (UiForm); if (! my d_dialogParent && ! my isPauseForm) return; int size = my numberOfFields; int dialogHeight = 0, x = Gui_LEFT_DIALOG_SPACING, y; int textFieldHeight = Gui_TEXTFIELD_HEIGHT; int dialogWidth = 520, dialogCentre = dialogWidth / 2, fieldX = dialogCentre + Gui_LABEL_SPACING / 2; int labelWidth = fieldX - Gui_LABEL_SPACING - x, fieldWidth = labelWidth, halfFieldWidth = fieldWidth / 2 - 6; #if gtk GuiObject form, buttons; int numberOfRows = 0, row = 0; #else GuiObject form, buttons; // Define? #endif /* Compute height. Cannot leave this to the default geometry management system. */ for (long ifield = 1; ifield <= my numberOfFields; ifield ++ ) { UiField thee = my field [ifield], previous = my field [ifield - 1]; dialogHeight += ifield == 1 ? Gui_TOP_DIALOG_SPACING : thy type == UI_RADIO || previous -> type == UI_RADIO ? Gui_VERTICAL_DIALOG_SPACING_DIFFERENT : thy type >= UI_LABELLEDTEXT_MIN && thy type <= UI_LABELLEDTEXT_MAX && wcsnequ (thy name, L"right ", 6) && previous -> type >= UI_LABELLEDTEXT_MIN && previous -> type <= UI_LABELLEDTEXT_MAX && wcsnequ (previous -> name, L"left ", 5) ? - textFieldHeight : Gui_VERTICAL_DIALOG_SPACING_SAME; thy y = dialogHeight; dialogHeight += thy type == UI_BOOLEAN ? Gui_CHECKBUTTON_HEIGHT : thy type == UI_RADIO ? thy options -> size * Gui_RADIOBUTTON_HEIGHT + (thy options -> size - 1) * Gui_RADIOBUTTON_SPACING : thy type == UI_OPTIONMENU ? Gui_OPTIONMENU_HEIGHT : thy type == UI_LIST ? LIST_HEIGHT : thy type == UI_LABEL && thy stringValue [0] != '\0' && thy stringValue [wcslen (thy stringValue) - 1] != '.' && ifield != my numberOfFields ? textFieldHeight #ifdef _WIN32 - 6 : #else - 10 : #endif textFieldHeight; #if gtk numberOfRows += wcsnequ (thy name, L"left ", 5); #endif } dialogHeight += 2 * Gui_BOTTOM_DIALOG_SPACING + Gui_PUSHBUTTON_HEIGHT; my d_dialogForm = GuiDialog_create (my d_dialogParent, DIALOG_X, DIALOG_Y, dialogWidth, dialogHeight, my name, gui_dialog_cb_close, me, 0); #if gtk form = gtk_table_new (numberOfRows, 3, false); gtk_table_set_col_spacing (GTK_TABLE (form), 0, 5); gtk_container_add (GTK_CONTAINER (my d_dialogForm), GTK_WIDGET (form)); gtk_widget_show (GTK_WIDGET (form)); buttons = GTK_DIALOG (GuiObject_parent (my d_dialogForm)) -> action_area; #else form = my d_dialogForm; buttons = my d_dialogForm; #endif for (long ifield = 1; ifield <= size; ifield ++) { UiField field = my field [ifield]; y = field -> y; switch (field -> type) { case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: case UI_INTEGER: case UI_NATURAL: case UI_WORD: case UI_SENTENCE: case UI_COLOUR: case UI_CHANNEL: { int ylabel = y; #if defined (macintosh) ylabel += 3; #endif if (wcsnequ (field -> name, L"left ", 5)) { MelderString_copy (& theFinishBuffer, field -> formLabel + 5); appendColon (); GuiObject label = GuiLabel_createShown (form, x, x + labelWidth, ylabel, ylabel + textFieldHeight, theFinishBuffer.string, GuiLabel_RIGHT); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (label), 0, 1, row, row + 1); #endif field -> text = GuiText_createShown (form, fieldX, fieldX + halfFieldWidth, y, Gui_AUTOMATIC, 0); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (field -> text), 1, 2, row, row + 1); #endif } else if (wcsnequ (field -> name, L"right ", 6)) { field -> text = GuiText_createShown (form, fieldX + halfFieldWidth + 12, fieldX + fieldWidth, y, Gui_AUTOMATIC, 0); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (field -> text), 2, 3, row, row + 1); row += 1; #endif } else { MelderString_copy (& theFinishBuffer, field -> formLabel); appendColon (); GuiObject label = GuiLabel_createShown (form, x, x + labelWidth, ylabel, ylabel + textFieldHeight, theFinishBuffer.string, GuiLabel_RIGHT); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (label), 0, 1, row, row + 1); #endif field -> text = GuiText_createShown (form, fieldX, fieldX + fieldWidth, // or once the dialog is a Form: - Gui_RIGHT_DIALOG_SPACING, y, Gui_AUTOMATIC, 0); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (field -> text), 1, 3, row, row + 1); row += 1; #endif } } break; case UI_TEXT: { field -> text = GuiText_createShown (form, x, x + dialogWidth - Gui_LEFT_DIALOG_SPACING - Gui_RIGHT_DIALOG_SPACING, y, Gui_AUTOMATIC, 0); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (field -> text), 0, 3, row, row + 1); row += 1; #endif } break; case UI_LABEL: { MelderString_copy (& theFinishBuffer, field -> stringValue); field -> text = GuiLabel_createShown (form, x, dialogWidth /* allow to extend into the margin */, y + 5, y + 5 + textFieldHeight, theFinishBuffer.string, 0); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (field -> text), 0, 3, row, row + 1); row += 1; #endif } break; case UI_RADIO: { int ylabel = y; #if gtk void *group = NULL; #endif #if defined (macintosh) ylabel += 1; #endif MelderString_copy (& theFinishBuffer, field -> formLabel); appendColon (); GuiObject label = GuiLabel_createShown (form, x, x + labelWidth, ylabel, ylabel + Gui_RADIOBUTTON_HEIGHT, theFinishBuffer.string, GuiLabel_RIGHT); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (label), 0, 1, row, row + 1); #endif for (long ibutton = 1; ibutton <= field -> options -> size; ibutton ++) { UiOption button = static_cast (field -> options -> item [ibutton]); MelderString_copy (& theFinishBuffer, button -> name); button -> toggle = GuiRadioButton_createShown (form, fieldX, dialogWidth /* allow to extend into the margin */, y + (ibutton - 1) * (Gui_RADIOBUTTON_HEIGHT + Gui_RADIOBUTTON_SPACING), Gui_AUTOMATIC, theFinishBuffer.string, gui_radiobutton_cb_toggled, field, 0); #if gtk if (group != NULL) { GuiRadioButton_setGroup (button -> toggle, group); } group = GuiRadioButton_getGroup (button -> toggle); gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (button -> toggle), 1, 3, row, row + 1); row += 1; #endif } } break; case UI_OPTIONMENU: { int ylabel = y; #if defined (macintosh) ylabel += 2; #endif GuiObject bar, box; MelderString_copy (& theFinishBuffer, field -> formLabel); appendColon (); GuiObject label = GuiLabel_createShown (form, x, x + labelWidth, ylabel, ylabel + Gui_OPTIONMENU_HEIGHT, theFinishBuffer.string, GuiLabel_RIGHT); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (label), 0, 1, row, row + 1); #endif #if motif bar = XmCreateMenuBar (form, "UiOptionMenu", NULL, 0); XtVaSetValues (bar, XmNx, fieldX - 4, XmNy, y - 4 #if defined (macintosh) - 1 #endif , XmNwidth, fieldWidth + 8, XmNheight, Gui_OPTIONMENU_HEIGHT + 8, NULL); #endif // TODO: dit wil natuurlijk heel graag in GuiComboBox.c ;) #if gtk field -> cascadeButton = gtk_combo_box_new_text (); gtk_combo_box_set_focus_on_click (GTK_COMBO_BOX (field -> cascadeButton), false); GTK_WIDGET_UNSET_FLAGS (field -> cascadeButton, GTK_CAN_DEFAULT); gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (field -> cascadeButton), 1, 3, row, row + 1); row += 1; #elif motif box = GuiMenuBar_addMenu2 (bar, L"choice", 0, & field -> cascadeButton); XtVaSetValues (bar, XmNwidth, fieldWidth + 8, NULL); XtVaSetValues (field -> cascadeButton, XmNx, 4, XmNy, 4, XmNwidth, fieldWidth, XmNheight, Gui_OPTIONMENU_HEIGHT, NULL); #endif for (long ibutton = 1; ibutton <= field -> options -> size; ibutton ++) { UiOption button = static_cast (field -> options -> item [ibutton]); MelderString_copy (& theFinishBuffer, button -> name); #if gtk gtk_combo_box_append_text (GTK_COMBO_BOX (field -> cascadeButton), Melder_peekWcsToUtf8 (theFinishBuffer.string)); #elif motif button -> toggle = XtVaCreateManagedWidget (Melder_peekWcsToUtf8 (theFinishBuffer.string), xmToggleButtonWidgetClass, box, NULL); XtAddCallback (button -> toggle, XmNvalueChangedCallback, cb_optionChanged, (XtPointer) field); #endif } #if gtk GuiObject_show (field -> cascadeButton); #elif motif GuiObject_show (bar); #endif } break; case UI_BOOLEAN: { MelderString_copy (& theFinishBuffer, field -> formLabel); /*GuiLabel_createShown (form, x, x + labelWidth, y, y + Gui_CHECKBUTTON_HEIGHT, theFinishBuffer.string, GuiLabel_RIGHT); */ field -> toggle = GuiCheckButton_createShown (form, fieldX, dialogWidth /* allow to extend into the margin */, y, Gui_AUTOMATIC, theFinishBuffer.string, NULL, NULL, 0); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (field -> toggle), 1, 3, row, row + 1); row += 1; #endif } break; case UI_LIST: { int listWidth = my numberOfFields == 1 ? dialogWidth - fieldX : fieldWidth; MelderString_copy (& theFinishBuffer, field -> formLabel); appendColon (); GuiObject label = GuiLabel_createShown (form, x, x + labelWidth, y + 1, y + 21, theFinishBuffer.string, GuiLabel_RIGHT); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), GTK_WIDGET (label), 0, 1, row, row + 1); #endif field -> list = GuiList_create (form, fieldX, fieldX + listWidth, y, y + LIST_HEIGHT, false, theFinishBuffer.string); for (long i = 1; i <= field -> numberOfStrings; i ++) { GuiList_insertItem (field -> list, field -> strings [i], 0); } GuiObject_show (field -> list); #if gtk gtk_table_attach_defaults (GTK_TABLE (form), gtk_widget_get_parent (GTK_WIDGET (field -> list)), 1, 3, row, row + 1); row += 1; #endif } break; } } for (long ifield = 1; ifield <= my numberOfFields; ifield ++) UiField_setDefault (my field [ifield]); /*separator = XmCreateSeparatorGadget (column, "separator", NULL, 0);*/ y = dialogHeight - Gui_BOTTOM_DIALOG_SPACING - Gui_PUSHBUTTON_HEIGHT; if (my helpTitle) { my helpButton = GuiButton_createShown (buttons, HELP_BUTTON_X, HELP_BUTTON_X + HELP_BUTTON_WIDTH, y, Gui_AUTOMATIC, L"Help", gui_button_cb_help, me, 0); #if gtk gtk_button_box_set_child_secondary (GTK_BUTTON_BOX (buttons), GTK_WIDGET (my helpButton), TRUE); #endif } if (my numberOfFields > 1 || (my numberOfFields > 0 && my field [1] -> type != UI_LABEL)) { if (my isPauseForm) { my revertButton = GuiButton_createShown (buttons, HELP_BUTTON_X, HELP_BUTTON_X + REVERT_BUTTON_WIDTH, y, Gui_AUTOMATIC, L"Revert", gui_button_cb_revert, me, 0); } else { my revertButton = GuiButton_createShown (buttons, HELP_BUTTON_X + HELP_BUTTON_WIDTH + Gui_HORIZONTAL_DIALOG_SPACING, HELP_BUTTON_X + HELP_BUTTON_WIDTH + Gui_HORIZONTAL_DIALOG_SPACING + STANDARDS_BUTTON_WIDTH, y, Gui_AUTOMATIC, L"Standards", gui_button_cb_revert, me, 0); } #if gtk gtk_button_box_set_child_secondary (GTK_BUTTON_BOX (buttons), GTK_WIDGET (my revertButton), TRUE); #endif } if (my isPauseForm) { x = HELP_BUTTON_X + REVERT_BUTTON_WIDTH + Gui_HORIZONTAL_DIALOG_SPACING; if (my cancelContinueButton == 0) { my cancelButton = GuiButton_createShown (buttons, x, x + STOP_BUTTON_WIDTH, y, Gui_AUTOMATIC, L"Stop", gui_button_cb_cancel, me, GuiButton_CANCEL); x += STOP_BUTTON_WIDTH + 7; } else { x += 30; } int room = dialogWidth - Gui_RIGHT_DIALOG_SPACING - x; int roomPerContinueButton = room / my numberOfContinueButtons; int horizontalSpacing = my numberOfContinueButtons > 7 ? Gui_HORIZONTAL_DIALOG_SPACING - 2 * (my numberOfContinueButtons - 7) : Gui_HORIZONTAL_DIALOG_SPACING; int continueButtonWidth = roomPerContinueButton - horizontalSpacing; for (int i = 1; i <= my numberOfContinueButtons; i ++) { x = dialogWidth - Gui_RIGHT_DIALOG_SPACING - roomPerContinueButton * (my numberOfContinueButtons - i + 1) + horizontalSpacing; my continueButtons [i] = GuiButton_createShown (buttons, x, x + continueButtonWidth, y, Gui_AUTOMATIC, my continueTexts [i], gui_button_cb_ok, me, i == my defaultContinueButton ? GuiButton_DEFAULT : 0); } } else { x = dialogWidth - Gui_RIGHT_DIALOG_SPACING - Gui_OK_BUTTON_WIDTH - 2 * Gui_HORIZONTAL_DIALOG_SPACING - Gui_APPLY_BUTTON_WIDTH - Gui_CANCEL_BUTTON_WIDTH; my cancelButton = GuiButton_createShown (buttons, x, x + Gui_CANCEL_BUTTON_WIDTH, y, Gui_AUTOMATIC, L"Cancel", gui_button_cb_cancel, me, GuiButton_CANCEL); x = dialogWidth - Gui_RIGHT_DIALOG_SPACING - Gui_OK_BUTTON_WIDTH - Gui_HORIZONTAL_DIALOG_SPACING - Gui_APPLY_BUTTON_WIDTH; if (my numberOfFields > 1 || my field [1] -> type != UI_LABEL) { my applyButton = GuiButton_createShown (buttons, x, x + Gui_APPLY_BUTTON_WIDTH, y, Gui_AUTOMATIC, L"Apply", gui_button_cb_apply, me, 0); } x = dialogWidth - Gui_RIGHT_DIALOG_SPACING - Gui_OK_BUTTON_WIDTH; my okButton = GuiButton_createShown (buttons, x, x + Gui_OK_BUTTON_WIDTH, y, Gui_AUTOMATIC, my isPauseForm ? L"Continue" : L"OK", gui_button_cb_ok, me, GuiButton_DEFAULT); } /*GuiObject_show (separator);*/ } void UiForm_destroyWhenUnmanaged (I) { iam (UiForm); my destroyWhenUnmanaged = true; } void UiForm_do (I, bool modified) { iam (UiForm); my allowExecutionHook = theAllowExecutionHookHint; my allowExecutionClosure = theAllowExecutionClosureHint; /* Prevent double callbacks: */ /*XtRemoveCallback (my okButton, XmNactivateCallback, UiForm_ok, (XtPointer) me);*/ /* This is the only place where this callback is installed. Moved from UiForm_close ppgb950613. */ /*XtAddCallback (my okButton, XmNactivateCallback, UiForm_ok, (XtPointer) me);*/ GuiObject_show (my d_dialogForm); if (modified) UiForm_okOrApply (me, NULL, true); } void UiForm_parseString (I, const wchar *arguments, Interpreter interpreter) { iam (UiForm); int size = my numberOfFields; while (size >= 1 && my field [size] -> type == UI_LABEL) size --; /* Ignore trailing fields without a value. */ for (int i = 1; i < size; i ++) { static wchar_t stringValue [3000]; int ichar = 0; if (my field [i] -> type == UI_LABEL) continue; /* Ignore non-trailing fields without a value. */ /* * Skip spaces until next argument. */ while (*arguments == ' ' || *arguments == '\t') arguments ++; /* * The argument is everything up to the next space, or, if that starts with a double quote, * everything between this quote and the matching double quote; * in this case, the argument can represent a double quote by a sequence of two double quotes. * Example: the string * "I said ""hello""" * will be passed to the dialog as a single argument containing the text * I said "hello" */ if (*arguments == '\"') { arguments ++; /* Do not include leading double quote. */ for (;;) { if (*arguments == '\0') Melder_throw ("Missing matching quote."); if (*arguments == '\"' && * ++ arguments != '\"') break; // remember second quote stringValue [ichar ++] = *arguments ++; } } else { while (*arguments != ' ' && *arguments != '\t' && *arguments != '\0') stringValue [ichar ++] = *arguments ++; } stringValue [ichar] = '\0'; // trailing null byte try { UiField_stringToValue (my field [i], stringValue, interpreter); } catch (MelderError) { Melder_throw ("Don't understand contents of field \"", my field [i] -> name, "\"."); } } /* * The last item is handled separately, because it consists of the rest of the line. * Leading spaces are skipped, but trailing spaces are included. */ if (size > 0) { while (*arguments == ' ' || *arguments == '\t') arguments ++; try { UiField_stringToValue (my field [size], arguments, interpreter); } catch (MelderError) { Melder_throw ("Don't understand contents of field \"", my field [size] -> name, "\"."); } } my okCallback (me, NULL, interpreter, NULL, false, my buttonClosure); therror } void UiForm_parseStringE (EditorCommand cmd, const wchar *arguments, Interpreter interpreter) { UiForm_parseString (cmd -> d_uiform, arguments, interpreter); } static UiField findField (UiForm me, const wchar *fieldName) { for (int ifield = 1; ifield <= my numberOfFields; ifield ++) if (wcsequ (fieldName, my field [ifield] -> name)) return my field [ifield]; return NULL; } static void fatalField (UiForm dia) { Melder_fatal ("Wrong field in command window \"%s\".", Melder_peekWcsToUtf8 (dia -> name)); } void UiForm_setReal (I, const wchar_t *fieldName, double value) { iam (UiForm); UiField field = findField (me, fieldName); if (field == NULL) Melder_fatal ("(UiForm_setReal:) No field \"%s\" in command window \"%s\".", Melder_peekWcsToUtf8 (fieldName), Melder_peekWcsToUtf8 (my name)); switch (field -> type) { case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: { if (value == Melder_atof (field -> stringDefaultValue)) { GuiText_setString (field -> text, field -> stringDefaultValue); } else { wchar_t s [40]; wcscpy (s, Melder_double (value)); /* * If the default is overtly real, the shown value must be as well. */ if ((wcschr (field -> stringDefaultValue, '.') || wcschr (field -> stringDefaultValue, 'e')) && ! (wcschr (s, '.') || wcschr (s, 'e'))) { wcscat (s, L".0"); } GuiText_setString (field -> text, s); } } break; case UI_COLOUR: { GuiText_setString (field -> text, Melder_double (value)); // some grey value } break; default: { Melder_fatal ("Wrong field in command window \"%s\".", Melder_peekWcsToUtf8 (my name)); } } } void UiForm_setInteger (I, const wchar_t *fieldName, long value) { iam (UiForm); UiField field = findField (me, fieldName); if (field == NULL) Melder_fatal ("(UiForm_setInteger:) No field \"%s\" in command window \"%s\".", Melder_peekWcsToUtf8 (fieldName), Melder_peekWcsToUtf8 (my name)); switch (field -> type) { case UI_INTEGER: case UI_NATURAL: case UI_CHANNEL: { if (value == wcstol (field -> stringDefaultValue, NULL, 10)) { GuiText_setString (field -> text, field -> stringDefaultValue); } else { GuiText_setString (field -> text, Melder_integer (value)); } } break; case UI_BOOLEAN: { GuiCheckButton_setValue (field -> toggle, value); } break; case UI_RADIO: { if (value < 1 || value > field -> options -> size) value = 1; /* Guard against incorrect prefs file. */ for (int i = 1; i <= field -> options -> size; i ++) { UiOption b = static_cast (field -> options -> item [i]); GuiRadioButton_setValue (b -> toggle, i == value); } } break; case UI_OPTIONMENU: { if (value < 1 || value > field -> options -> size) value = 1; /* Guard against incorrect prefs file. */ #if gtk gtk_combo_box_set_active (GTK_COMBO_BOX (field -> cascadeButton), value - 1); #elif motif for (int i = 1; i <= field -> options -> size; i ++) { UiOption b = static_cast (field -> options -> item [i]); XmToggleButtonSetState (b -> toggle, i == value, False); if (i == value) { XtVaSetValues (field -> cascadeButton, XmNlabelString, Melder_peekWcsToUtf8 (b -> name), NULL); } } #endif } break; case UI_LIST: { if (value < 1 || value > field -> numberOfStrings) value = 1; /* Guard against incorrect prefs file. */ GuiList_selectItem (field -> list, value); } break; default: { fatalField (me); } } } void UiForm_setString (I, const wchar *fieldName, const wchar *value) { iam (UiForm); UiField field = findField (me, fieldName); if (field == NULL) Melder_fatal ("(UiForm_setString:) No field \"%s\" in command window \"%s\".", Melder_peekWcsToUtf8 (fieldName), Melder_peekWcsToUtf8 (my name)); if (value == NULL) value = L""; /* Accept NULL strings. */ switch (field -> type) { case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: case UI_INTEGER: case UI_NATURAL: case UI_WORD: case UI_SENTENCE: case UI_COLOUR: case UI_CHANNEL: case UI_TEXT: { GuiText_setString (field -> text, value); } break; case UI_LABEL: { GuiLabel_setString (field -> text, value); } break; case UI_RADIO: { bool found = false; for (int i = 1; i <= field -> options -> size; i ++) { UiOption b = static_cast (field -> options -> item [i]); if (wcsequ (value, b -> name)) { GuiRadioButton_setValue (b -> toggle, true); found = true; } else { GuiRadioButton_setValue (b -> toggle, false); } } /* If not found: do nothing (guard against incorrect prefs file). */ } break; case UI_OPTIONMENU: { int integerValue = 0; for (int i = 1; i <= field -> options -> size; i ++) { UiOption b = static_cast (field -> options -> item [i]); if (wcsequ (value, b -> name)) { integerValue = i; break; } } #if gtk gtk_combo_box_set_active (GTK_COMBO_BOX (field -> cascadeButton), integerValue - 1); #else for (int i = 1; i <= field -> options -> size; i ++) { UiOption b = static_cast (field -> options -> item [i]); XmToggleButtonSetState (b -> toggle, i == integerValue, False); if (i == integerValue) XtVaSetValues (field -> cascadeButton, XmNlabelString, Melder_peekWcsToUtf8 (value), NULL); } #endif /* If not found: do nothing (guard against incorrect prefs file). */ } break; case UI_LIST: { long i; for (i = 1; i <= field -> numberOfStrings; i ++) if (wcsequ (value, field -> strings [i])) break; if (i > field -> numberOfStrings) i = 1; /* Guard against incorrect prefs file. */ GuiList_selectItem (field -> list, i); } break; default: { fatalField (me); } } } static UiField findField_check (UiForm me, const wchar *fieldName) { UiField result = findField (me, fieldName); if (result == NULL) { Melder_throw ("Cannot find field \"", fieldName, "\" in form.\n" "The script may have changed while the form was open.\n" "Please click Cancel in the form and try again."); } return result; } double UiForm_getReal (I, const wchar *fieldName) { iam (UiForm); UiField field = findField (me, fieldName); if (field == NULL) Melder_fatal ("(UiForm_getReal:) No field \"%s\" in command window \"%s\".", Melder_peekWcsToUtf8 (fieldName), Melder_peekWcsToUtf8 (my name)); switch (field -> type) { case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: { return field -> realValue; } break; default: { fatalField (me); } } return 0.0; } double UiForm_getReal_check (I, const wchar *fieldName) { iam (UiForm); UiField field = findField_check (me, fieldName); switch (field -> type) { case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: { return field -> realValue; } break; default: { Melder_throw ("Cannot find a real value in field \"", fieldName, "\" in the form.\n" "The script may have changed while the form was open.\n" "Please click Cancel in the form and try again."); } } return 0.0; } long UiForm_getInteger (I, const wchar *fieldName) { iam (UiForm); UiField field = findField (me, fieldName); if (field == NULL) Melder_fatal ("(UiForm_getInteger:) No field \"%s\" in command window \"%s\".", Melder_peekWcsToUtf8 (fieldName), Melder_peekWcsToUtf8 (my name)); switch (field -> type) { case UI_INTEGER: case UI_NATURAL: case UI_CHANNEL: case UI_BOOLEAN: case UI_RADIO: case UI_OPTIONMENU: case UI_LIST: { return field -> integerValue; } break; default: { fatalField (me); } } return 0L; } long UiForm_getInteger_check (I, const wchar *fieldName) { iam (UiForm); UiField field = findField_check (me, fieldName); switch (field -> type) { case UI_INTEGER: case UI_NATURAL: case UI_CHANNEL: case UI_BOOLEAN: case UI_RADIO: case UI_OPTIONMENU: case UI_LIST: { return field -> integerValue; } break; default: { Melder_throw ("Cannot find an integer value in field \"", fieldName, "\" in the form.\n" "The script may have changed while the form was open.\n" "Please click Cancel in the form and try again."); } } return 0L; } wchar * UiForm_getString (I, const wchar *fieldName) { iam (UiForm); UiField field = findField (me, fieldName); if (field == NULL) Melder_fatal ("(UiForm_getString:) No field \"%s\" in command window \"%s\".", Melder_peekWcsToUtf8 (fieldName), Melder_peekWcsToUtf8 (my name)); switch (field -> type) { case UI_WORD: case UI_SENTENCE: case UI_TEXT: { return field -> stringValue; } break; case UI_RADIO: case UI_OPTIONMENU: { UiOption b = static_cast (field -> options -> item [field -> integerValue]); return b -> name; } break; case UI_LIST: { return (wchar_t *) field -> strings [field -> integerValue]; } break; default: { fatalField (me); } } return NULL; } wchar * UiForm_getString_check (I, const wchar *fieldName) { iam (UiForm); UiField field = findField_check (me, fieldName); switch (field -> type) { case UI_WORD: case UI_SENTENCE: case UI_TEXT: { return field -> stringValue; } break; case UI_RADIO: case UI_OPTIONMENU: { UiOption b = static_cast (field -> options -> item [field -> integerValue]); return b -> name; } break; case UI_LIST: { return (wchar_t *) field -> strings [field -> integerValue]; } break; default: { Melder_throw ("Cannot find a string in field \"", fieldName, "\" in the form.\n" "The script may have changed while the form was open.\n" "Please click Cancel in the form and try again."); } } return NULL; } Graphics_Colour UiForm_getColour (I, const wchar *fieldName) { iam (UiForm); UiField field = findField (me, fieldName); if (field == NULL) Melder_fatal ("(UiForm_getColour:) No field \"%s\" in command window \"%s\".", Melder_peekWcsToUtf8 (fieldName), Melder_peekWcsToUtf8 (my name)); switch (field -> type) { case UI_COLOUR: { return field -> colourValue; } break; default: { fatalField (me); } } return Graphics_BLACK; } Graphics_Colour UiForm_getColour_check (I, const wchar *fieldName) { iam (UiForm); UiField field = findField_check (me, fieldName); switch (field -> type) { case UI_COLOUR: { return field -> colourValue; } break; default: { Melder_throw ("Cannot find a real value in field \"", fieldName, "\" in the form.\n" "The script may have changed while the form was open.\n" "Please click Cancel in the form and try again."); } } return Graphics_BLACK; } void UiForm_Interpreter_addVariables (I, Interpreter interpreter) { iam (UiForm); static MelderString lowerCaseFieldName = { 0 }; for (int ifield = 1; ifield <= my numberOfFields; ifield ++) { UiField field = my field [ifield]; MelderString_copy (& lowerCaseFieldName, field -> name); /* * Change e.g. "Number of people" to "number_of_people". */ lowerCaseFieldName.string [0] = towlower (lowerCaseFieldName.string [0]); for (wchar_t *p = & lowerCaseFieldName.string [0]; *p != '\0'; p ++) { if (*p == ' ') *p = '_'; } switch (field -> type) { case UI_INTEGER: case UI_NATURAL: case UI_CHANNEL: case UI_BOOLEAN: { InterpreterVariable var = Interpreter_lookUpVariable (interpreter, lowerCaseFieldName.string); therror var -> numericValue = field -> integerValue; } break; case UI_REAL: case UI_REAL_OR_UNDEFINED: case UI_POSITIVE: { InterpreterVariable var = Interpreter_lookUpVariable (interpreter, lowerCaseFieldName.string); therror var -> numericValue = field -> realValue; } break; case UI_RADIO: case UI_OPTIONMENU: { InterpreterVariable var = Interpreter_lookUpVariable (interpreter, lowerCaseFieldName.string); therror var -> numericValue = field -> integerValue; MelderString_appendCharacter (& lowerCaseFieldName, '$'); var = Interpreter_lookUpVariable (interpreter, lowerCaseFieldName.string); therror Melder_free (var -> stringValue); UiOption b = static_cast (field -> options -> item [field -> integerValue]); var -> stringValue = Melder_wcsdup_f (b -> name); } break; case UI_LIST: { InterpreterVariable var = Interpreter_lookUpVariable (interpreter, lowerCaseFieldName.string); therror var -> numericValue = field -> integerValue; MelderString_appendCharacter (& lowerCaseFieldName, '$'); var = Interpreter_lookUpVariable (interpreter, lowerCaseFieldName.string); therror Melder_free (var -> stringValue); var -> stringValue = Melder_wcsdup_f ((wchar *) field -> strings [field -> integerValue]); } break; case UI_WORD: case UI_SENTENCE: case UI_TEXT: { MelderString_appendCharacter (& lowerCaseFieldName, '$'); InterpreterVariable var = Interpreter_lookUpVariable (interpreter, lowerCaseFieldName.string); therror Melder_free (var -> stringValue); var -> stringValue = Melder_wcsdup_f (field -> stringValue); } break; case UI_COLOUR: { // to be implemented } break; default: { } } } } int UiForm_getClickedContinueButton (UiForm me) { return my clickedContinueButton; } /* End of file Ui.cpp */ sources_5316/sys/GuiWindow.cpp0000644000176700017670000001400311753745127015173 0ustar paulpaul/* GuiWindow.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2004/01/07 this file separated from Gui.c * pb 2004/02/12 don't trust window modification feedback on MacOS 9 * pb 2004/04/06 GuiWindow_drain separated from XmUpdateDisplay * pb 2006/10/28 erased MacOS 9 stuff * pb 2007/06/19 wchar_t * pb 2007/12/30 extraction * pb 2010/07/29 removed GuiWindow_show * pb 2010/11/28 removed explicit Motif * pb 2011/04/06 C++ */ #include "GuiP.h" #include "UnicodeData.h" #undef iam #define iam(x) x me = (x) void_me typedef struct structGuiWindow { GuiObject widget; void (*goAwayCallback) (void *boss); void *goAwayBoss; } *GuiWindow; #if gtk static gboolean _GuiWindow_destroyCallback (GuiObject widget, GdkEvent *event, gpointer void_me) { (void) widget; iam (GuiWindow); Melder_free (me); return TRUE; } static gboolean _GuiWindow_goAwayCallback (GuiObject widget, GdkEvent *event, gpointer void_me) { (void) widget; iam (GuiWindow); if (my goAwayCallback != NULL) { my goAwayCallback (my goAwayBoss); } return TRUE; } #elif win || mac && useCarbon static void _GuiMotifWindow_destroyCallback (GuiObject widget, XtPointer void_me, XtPointer call) { (void) widget; (void) call; iam (GuiWindow); //Melder_casual ("destroying window widget"); Melder_free (me); } static void _GuiMotifWindow_goAwayCallback (GuiObject widget, XtPointer void_me, XtPointer call) { (void) widget; (void) call; iam (GuiWindow); if (my goAwayCallback != NULL) { my goAwayCallback (my goAwayBoss); } } #endif GuiObject GuiWindow_create (GuiObject parent, int x, int y, int width, int height, const wchar_t *title, void (*goAwayCallback) (void *goAwayBoss), void *goAwayBoss, unsigned long flags) { GuiWindow me = Melder_calloc_f (struct structGuiWindow, 1); my goAwayCallback = goAwayCallback; my goAwayBoss = goAwayBoss; #if gtk (void) parent; static bool gtkHasBeenInitialized = false; if (! gtkHasBeenInitialized) { gtk_disable_setlocale (); // otherwise 1.5 will be written "1,5" on computers with a French or German locale gtk_init_check (NULL, NULL); gtkHasBeenInitialized = true; } GuiObject shell = gtk_window_new (GTK_WINDOW_TOPLEVEL); g_signal_connect (G_OBJECT (shell), "delete-event", goAwayCallback ? G_CALLBACK (_GuiWindow_goAwayCallback) : G_CALLBACK (gtk_widget_hide), me); g_signal_connect (G_OBJECT (shell), "destroy-event", G_CALLBACK (_GuiWindow_destroyCallback), me); // TODO: Paul ik denk dat Gui_AUTOMATIC voor GTK gewoon -1 moet zijn veel minder (onnodig) gezeur if (width == Gui_AUTOMATIC) width = -1; if (height == Gui_AUTOMATIC) height = -1; gtk_window_set_default_size (GTK_WINDOW (shell), width, height); GuiWindow_setTitle (shell, title); my widget = gtk_vbox_new (FALSE, 0); gtk_container_add (GTK_CONTAINER (shell), GTK_WIDGET (my widget)); _GuiObject_setUserData (my widget, me); #elif win || mac && useCarbon (void) parent; GuiObject shell = XmCreateShell (NULL, flags & GuiWindow_FULLSCREEN ? "Praatwulgfullscreen" : "Praatwulg", NULL, 0); XtVaSetValues (shell, XmNdeleteResponse, goAwayCallback ? XmDO_NOTHING : XmUNMAP, NULL); if (x != Gui_AUTOMATIC) XtVaSetValues (shell, XmNx, x, NULL); if (y != Gui_AUTOMATIC) XtVaSetValues (shell, XmNy, y, NULL); if (width != Gui_AUTOMATIC) XtVaSetValues (shell, XmNwidth, (Dimension) width, NULL); if (height != Gui_AUTOMATIC) XtVaSetValues (shell, XmNheight, (Dimension) height, NULL); if (goAwayCallback) { XmAddWMProtocolCallback (shell, 'delw', _GuiMotifWindow_goAwayCallback, (char *) me); } GuiWindow_setTitle (shell, title); my widget = XmCreateForm (shell, "dialog", NULL, 0); _GuiObject_setUserData (my widget, me); XtAddCallback (my widget, XmNdestroyCallback, _GuiMotifWindow_destroyCallback, me); XtVaSetValues (my widget, XmNdialogStyle, XmDIALOG_MODELESS, XmNautoUnmanage, False, NULL); #endif return my widget; } void GuiWindow_setTitle (GuiObject shell, const wchar_t *title) { #if gtk gtk_window_set_title (GTK_WINDOW (shell), Melder_peekWcsToUtf8 (title)); #elif mac #if useCarbon SetWindowTitleWithCFString (shell -> nat.window.ptr, (CFStringRef) Melder_peekWcsToCfstring (title)); #else #endif #elif win SetWindowText (shell -> window, title); #endif } int GuiWindow_setDirty (GuiObject shell, int dirty) { #if mac #if useCarbon SetWindowModified (shell -> nat.window.ptr, dirty); #else #endif return 1; #else (void) shell; (void) dirty; return 0; #endif } void GuiWindow_drain (GuiObject me) { #if gtk //gdk_window_flush (gtk_widget_get_window (me)); gdk_flush (); #elif mac #if useCarbon QDFlushPortBuffer (GetWindowPort (my macWindow), NULL); /* * The following TRICK cost me half a day to work out. * It turns out that after a call to QDFlushPortBuffer (), * it takes MacOS ages to compute a new dirty region while * the next graphics commands are executed. Such a dirty region * could well be the region that includes all the pixels drawn by * the graphics commands, and nothing else. One can imagine * that such a thing takes five seconds when the graphics is * a simple Graphics_function () of e.g. noise. */ static Rect bounds = { -32768, -32768, 32767, 32767 }; QDAddRectToDirtyRegion (GetWindowPort (my macWindow), & bounds); #else #endif #else (void) me; #endif } /* End of file GuiWindow.cpp */ sources_5316/sys/Graphics_linesAndAreas.cpp0000644000176700017670000012764411753724444017627 0ustar paulpaul/* Graphics_linesAndAreas.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "GraphicsP.h" /* Normally on, because e.g. the intensity contour in the Sound window should not run through the play buttons: */ #define FUNCTIONS_ARE_CLIPPED 1 #define POSTSCRIPT_MAXPATH 1000 #define LINE_WIDTH_IN_PIXELS(me) ( my resolution > 192 ? my lineWidth * (my resolution / 192.0) : my lineWidth ) #define ORDER_DC { long temp; if (x1DC > x2DC) temp = x1DC, x1DC = x2DC, x2DC = temp; \ if (yIsZeroAtTheTop == (y2DC > y1DC)) temp = y1DC, y1DC = y2DC, y2DC = temp; } static void psPrepareLine (GraphicsPostscript me) { double lineWidth_pixels = LINE_WIDTH_IN_PIXELS (me); if (my lineType == Graphics_DOTTED) my d_printf (my d_file, "[%ld %ld] 0 setdash\n", (long) (my resolution / 100), (long) (my resolution / 75 + lineWidth_pixels)); else if (my lineType == Graphics_DASHED) my d_printf (my d_file, "[%ld %ld] 0 setdash\n", (long) (my resolution / 25), (long) (my resolution / 50 + lineWidth_pixels)); else if (my lineType == Graphics_DASHED_DOTTED) my d_printf (my d_file, "[%ld %ld %ld %ld] 0 setdash\n", (long) (my resolution / 100), (long) (my resolution / 60 + lineWidth_pixels), (long) (my resolution / 25), (long) (my resolution / 60 + lineWidth_pixels)); if (my lineWidth != 1.0) my d_printf (my d_file, "%g setlinewidth\n", lineWidth_pixels); } static void psRevertLine (GraphicsPostscript me) { if (my lineType != Graphics_DRAWN) my d_printf (my d_file, "[] 0 setdash\n"); if (my lineWidth != 1.0) my d_printf (my d_file, "%g setlinewidth\n", my resolution > 192 ? my resolution / 192.0 : 1.0); // 0.375 point } #if cairo static void gdkPrepareLine (GraphicsScreen me) { gdk_gc_set_line_attributes (my d_gdkGraphicsContext, my lineWidth, my lineType >= Graphics_DOTTED ? GDK_LINE_ON_OFF_DASH : GDK_LINE_SOLID, GDK_CAP_ROUND, GDK_JOIN_ROUND); } static void gdkRevertLine (GraphicsScreen me) { if (my lineType >= Graphics_DOTTED) { gdk_gc_set_line_attributes (my d_gdkGraphicsContext, my lineWidth, GDK_LINE_SOLID, GDK_CAP_ROUND, GDK_JOIN_ROUND); } } static void cairoPrepareLine (GraphicsScreen me) { if (my d_cairoGraphicsContext == NULL) return; double dotted_line [] = { 2, 2 }; double dashed_line [] = { 6, 2 }; double dashed_dotted_line [] = { 6, 2, 2, 2 }; cairo_save (my d_cairoGraphicsContext); switch (my lineType) { case Graphics_DOTTED: cairo_set_dash (my d_cairoGraphicsContext, dotted_line, 2, 1.0); break; case Graphics_DASHED: cairo_set_dash (my d_cairoGraphicsContext, dashed_line, 2, 1.0); break; case Graphics_DASHED_DOTTED: cairo_set_dash (my d_cairoGraphicsContext, dashed_dotted_line, 4, 1.0); break; } cairo_set_line_width (my d_cairoGraphicsContext, my lineWidth); } static void cairoRevertLine (GraphicsScreen me) { if (my d_cairoGraphicsContext == NULL) return; if (my lineType >= Graphics_DOTTED) { cairo_set_dash (my d_cairoGraphicsContext, NULL, 0, 0); } cairo_restore (my d_cairoGraphicsContext); } #elif win #define MY_BRUSH SelectPen (d_gdiGraphicsContext, GetStockPen (NULL_PEN)), SelectBrush (d_gdiGraphicsContext, d_winBrush); #define DEFAULT SelectPen (d_gdiGraphicsContext, GetStockPen (BLACK_PEN)), SelectBrush (d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); static void winPrepareLine (GraphicsScreen me) { HPEN newPen; int lineWidth_pixels = LINE_WIDTH_IN_PIXELS (me) + 0.5; if (! lineWidth_pixels) lineWidth_pixels = 1; my d_fatNonSolid = my lineType != Graphics_DRAWN && my lineWidth > 1; if (Melder_debug == 10) { LOGBRUSH brush; brush. lbStyle = BS_SOLID; brush. lbColor = my d_winForegroundColour; brush. lbHatch = my lineType == Graphics_DRAWN ? 0 : my lineType == Graphics_DOTTED ? PS_DOT : my lineType == Graphics_DASHED ? PS_DASH : PS_DASHDOT; newPen = ExtCreatePen (PS_GEOMETRIC, lineWidth_pixels, & brush, 0, NULL); } else { /*newPen = CreatePen (my lineType == Graphics_DRAWN ? PS_SOLID : my lineType == Graphics_DOTTED ? PS_DOT : my lineType == Graphics_DASHED ? PS_DASH : PS_DASHDOT, my fatNonSolid ? 1 : lineWidth_pixels, my foregroundColour);*/ LOGPEN pen; pen. lopnStyle = my lineType == Graphics_DRAWN ? PS_SOLID : my lineType == Graphics_DOTTED ? PS_DOT : my lineType == Graphics_DASHED ? PS_DASH : PS_DASHDOT; pen. lopnWidth. x = my d_fatNonSolid ? 1 : lineWidth_pixels; pen. lopnWidth. y = 0; pen. lopnColor = my d_winForegroundColour | 0x02000000; newPen = CreatePenIndirect (& pen); } SelectPen (my d_gdiGraphicsContext, newPen); DeletePen (my d_winPen); my d_winPen = newPen; } #elif mac static void quartzPrepareLine (GraphicsScreen me) { if (my duringXor) { CGContextSetBlendMode (my d_macGraphicsContext, kCGBlendModeDifference); CGContextSetAllowsAntialiasing (my d_macGraphicsContext, false); CGContextSetRGBStrokeColor (my d_macGraphicsContext, 1.0, 1.0, 1.0, 1.0); } else { CGContextSetRGBStrokeColor (my d_macGraphicsContext, my d_macColour.red / 65536.0, my d_macColour.green / 65536.0, my d_macColour.blue / 65536.0, 1.0); } double lineWidth_pixels = LINE_WIDTH_IN_PIXELS (me); CGContextSetLineWidth (my d_macGraphicsContext, lineWidth_pixels); CGFloat lengths [4]; if (my lineType == Graphics_DOTTED) lengths [0] = my resolution > 192 ? my resolution / 100.0 : 2, lengths [1] = my resolution > 192 ? my resolution / 75.0 + lineWidth_pixels : 2; if (my lineType == Graphics_DASHED) lengths [0] = my resolution > 192 ? my resolution / 25 : 6, lengths [1] = my resolution > 192 ? my resolution / 50.0 + lineWidth_pixels : 2; if (my lineType == Graphics_DASHED_DOTTED) lengths [0] = my resolution > 192 ? my resolution / 25 : 6, lengths [1] = my resolution > 192 ? my resolution / 50.0 + lineWidth_pixels : 2; lengths [2] = my resolution > 192 ? my resolution / 100.0 : 2; lengths [3] = my resolution > 192 ? my resolution / 50.0 + lineWidth_pixels : 2; CGContextSetLineDash (my d_macGraphicsContext, 0.0, my lineType == Graphics_DRAWN ? NULL : lengths, my lineType == 0 ? 0 : my lineType == Graphics_DASHED_DOTTED ? 4 : 2); } static void quartzRevertLine (GraphicsScreen me) { if (my duringXor) { CGContextSetBlendMode (my d_macGraphicsContext, kCGBlendModeNormal); CGContextSetAllowsAntialiasing (my d_macGraphicsContext, true); } } static void quartzPrepareFill (GraphicsScreen me) { CGContextSetAlpha (my d_macGraphicsContext, 1.0); CGContextSetBlendMode (my d_macGraphicsContext, kCGBlendModeNormal); CGContextSetRGBFillColor (my d_macGraphicsContext, my d_macColour.red / 65536.0, my d_macColour.green / 65536.0, my d_macColour.blue / 65536.0, 1.0); } static RGBColor theBlackColour = { 0, 0, 0 }; #endif /* First level. */ void structGraphicsScreen :: v_polyline (long numberOfPoints, long *xyDC, bool close) { #if cairo if (duringXor) { gdkPrepareLine (this); for (long i = 0; i < numberOfPoints - 1; i ++) { gdk_draw_line (d_window, d_gdkGraphicsContext, xyDC [i + i], xyDC [i + i + 1], xyDC [i + i + 2], xyDC [i + i + 3]); } gdkRevertLine (this); } else { if (d_cairoGraphicsContext == NULL) return; cairoPrepareLine (this); // cairo_new_path (d_cairoGraphicsContext); // move_to() automatically creates a new path cairo_move_to (d_cairoGraphicsContext, (double) xyDC [0], (double) xyDC [1]); for (long i = 1; i < numberOfPoints; i ++) { cairo_line_to (d_cairoGraphicsContext, (double) xyDC [i + i], (double) xyDC [i + i + 1]); } if (close) cairo_close_path (d_cairoGraphicsContext); cairo_stroke (d_cairoGraphicsContext); cairoRevertLine (this); } #elif win winPrepareLine (this); POINT *points = Melder_malloc (POINT, numberOfPoints + close); if (points) { for (long i = 0; i < numberOfPoints; i ++) { points [i]. x = *xyDC, xyDC ++; points [i]. y = *xyDC, xyDC ++; } if (close) points [numberOfPoints] = points [0]; Polyline (d_gdiGraphicsContext, points, numberOfPoints + close); if (d_fatNonSolid) { for (long i = 0; i < numberOfPoints; i ++) points [i]. x -= 1; if (close) points [numberOfPoints] = points [0]; Polyline (d_gdiGraphicsContext, points, numberOfPoints + close); for (long i = 0; i < numberOfPoints; i ++) { points [i]. x += 1; points [i]. y -= 1; } if (close) points [numberOfPoints] = points [0]; Polyline (d_gdiGraphicsContext, points, numberOfPoints + close); } } DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareLine (this); CGContextBeginPath (d_macGraphicsContext); CGContextMoveToPoint (d_macGraphicsContext, xyDC [0], xyDC [1]); // starts a new subpath for (long i = 1; i < numberOfPoints; i ++) { CGContextAddLineToPoint (d_macGraphicsContext, xyDC [i + i], xyDC [i + i + 1]); } if (close) CGContextClosePath (d_macGraphicsContext); // closes only the subpath CGContextStrokePath (d_macGraphicsContext); quartzRevertLine (this); GraphicsQuartz_exitDraw (this); #endif } void structGraphicsPostscript :: v_polyline (long numberOfPoints, long *xyDC, bool close) { long nn = numberOfPoints + numberOfPoints; psPrepareLine (this); d_printf (d_file, "N %ld %ld moveto\n", xyDC [0], xyDC [1]); for (long i = 2, ipath = 1; i < nn; i += 2) { long dx = xyDC [i] - xyDC [i - 2], dy = xyDC [i + 1] - xyDC [i - 1]; if (dx == 1 && i < nn - 20 && xyDC [i + 2] - xyDC [i] == 1 && xyDC [i + 4] - xyDC [i + 2] == 1 && xyDC [i + 6] - xyDC [i + 4] == 1 && xyDC [i + 8] - xyDC [i + 6] == 1 && xyDC [i + 10] - xyDC [i + 8] == 1 && xyDC [i + 12] - xyDC [i + 10] == 1 && xyDC [i + 14] - xyDC [i + 12] == 1 && xyDC [i + 16] - xyDC [i + 14] == 1 && xyDC [i + 18] - xyDC [i + 16] == 1) { d_printf (d_file, "%ld %ld %ld %ld %ld %ld %ld %ld %ld %ld F\n", xyDC [i + 19] - xyDC [i + 17], xyDC [i + 17] - xyDC [i + 15], xyDC [i + 15] - xyDC [i + 13], xyDC [i + 13] - xyDC [i + 11], xyDC [i + 11] - xyDC [i + 9], xyDC [i + 9] - xyDC [i + 7], xyDC [i + 7] - xyDC [i + 5], xyDC [i + 5] - xyDC [i + 3], xyDC [i + 3] - xyDC [i + 1], dy); ipath += 9; i += 18; } else if (dx != 0 || dy != 0 || i < 4) { d_printf (d_file, "%ld %ld L\n", dx, dy); } if (++ ipath >= POSTSCRIPT_MAXPATH && i != nn - 2) { d_printf (d_file, "currentpoint stroke moveto\n"); ipath = 1; } } if (close) d_printf (d_file, "closepath "); d_printf (d_file, "stroke\n"); psRevertLine (this); } void structGraphicsScreen :: v_fillArea (long numberOfPoints, long *xyDC) { #if cairo if (d_cairoGraphicsContext == NULL) return; // cairo_new_path (d_cairoGraphicsContext); // move_to() automatically creates a new path cairo_move_to (d_cairoGraphicsContext, xyDC [0], xyDC [1]); for (long i = 1; i < numberOfPoints; i ++) cairo_line_to (d_cairoGraphicsContext, xyDC [i + i], xyDC [i + i + 1]); cairo_close_path (d_cairoGraphicsContext); cairo_fill (d_cairoGraphicsContext); #elif win MY_BRUSH BeginPath (d_gdiGraphicsContext); MoveToEx (d_gdiGraphicsContext, xyDC [0], xyDC [1], NULL); for (long i = 1; i < numberOfPoints; i ++) LineTo (d_gdiGraphicsContext, xyDC [i + i], xyDC [i + i + 1]); EndPath (d_gdiGraphicsContext); FillPath (d_gdiGraphicsContext); DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareFill (this); CGContextBeginPath (d_macGraphicsContext); CGContextMoveToPoint (d_macGraphicsContext, xyDC [0], xyDC [1]); for (long i = 1; i < numberOfPoints; i ++) { CGContextAddLineToPoint (d_macGraphicsContext, xyDC [i + i], xyDC [i + i + 1]); } CGContextFillPath (d_macGraphicsContext); GraphicsQuartz_exitDraw (this); #endif } void structGraphicsPostscript :: v_fillArea (long numberOfPoints, long *xyDC) { long nn = numberOfPoints + numberOfPoints; d_printf (d_file, "N %ld %ld M\n", xyDC [0], xyDC [1]); /* * Very old (?) printers have path size restrictions. * That's no reason to truncate the path on newer printers. */ #if 0 if (numberOfPoints > POSTSCRIPT_MAXPATH) { Melder_warning (L"GraphicsPostscript::fillArea: path truncated."); numberOfPoints = POSTSCRIPT_MAXPATH, nn = numberOfPoints + numberOfPoints; } #endif for (long i = 2; i < nn; i += 2) { d_printf (d_file, "%ld %ld L\n", xyDC [i] - xyDC [i - 2], xyDC [i + 1] - xyDC [i - 1]); } d_printf (d_file, "closepath fill\n"); } /* Second level. */ void structGraphicsScreen :: v_rectangle (long x1DC, long x2DC, long y1DC, long y2DC) { ORDER_DC #if cairo if (d_cairoGraphicsContext == NULL) return; int width = x2DC - x1DC, height = y1DC - y2DC; if (width <= 0 || height <= 0) return; cairoPrepareLine (this); cairo_rectangle (d_cairoGraphicsContext, x1DC, y2DC, width, height); cairo_stroke (d_cairoGraphicsContext); cairoRevertLine (this); #elif win winPrepareLine (this); Rectangle (d_gdiGraphicsContext, x1DC, y2DC, x2DC + 1, y1DC + 1); DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareLine (this); CGContextStrokeRect (d_macGraphicsContext, CGRectMake (x1DC - 0.5, y2DC - 0.5, x2DC - x1DC, y1DC - y2DC)); quartzRevertLine (this); GraphicsQuartz_exitDraw (this); #else long xyDC [8]; xyDC [0] = x1DC; xyDC [1] = y1DC; xyDC [2] = x2DC; xyDC [3] = y1DC; xyDC [4] = x2DC; xyDC [5] = y2DC; xyDC [6] = x1DC; xyDC [7] = y2DC; v_polyline (5, & xyDC [0], true); #endif } void structGraphicsPostscript :: v_rectangle (long x1DC, long x2DC, long y1DC, long y2DC) { psPrepareLine (this); d_printf (d_file, "N %ld %ld M %ld %ld lineto %ld %ld lineto %ld %ld lineto closepath stroke\n", x1DC, y1DC, x2DC, y1DC, x2DC, y2DC, x1DC, y2DC); psRevertLine (this); } void structGraphicsScreen :: v_fillRectangle (long x1DC, long x2DC, long y1DC, long y2DC) { ORDER_DC #if cairo if (d_cairoGraphicsContext == NULL) return; int width = x2DC - x1DC + 1, height = y1DC - y2DC + 1; if (width <= 0 || height <= 0) return; cairo_rectangle (d_cairoGraphicsContext, x1DC, y2DC, width, height); cairo_fill (d_cairoGraphicsContext); #elif win RECT rect; rect. left = x1DC, rect. right = x2DC, rect. top = y2DC, rect. bottom = y1DC; /* Superfluous? */ MY_BRUSH Rectangle (d_gdiGraphicsContext, x1DC, y2DC, x2DC + 1, y1DC + 1); DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareFill (this); CGContextFillRect (d_macGraphicsContext, CGRectMake (x1DC, y2DC, x2DC - x1DC, y1DC - y2DC)); GraphicsQuartz_exitDraw (this); #else long xyDC [10]; xyDC [0] = x1DC; xyDC [1] = y1DC; xyDC [2] = x2DC; xyDC [3] = y1DC; xyDC [4] = x2DC; xyDC [5] = y2DC; xyDC [6] = x1DC; xyDC [7] = y2DC; xyDC [8] = x1DC; xyDC [9] = y1DC; v_fillArea (5, & xyDC [0]); #endif } void structGraphicsPostscript :: v_fillRectangle (long x1DC, long x2DC, long y1DC, long y2DC) { d_printf (d_file, "N %ld %ld M %ld %ld lineto %ld %ld lineto %ld %ld lineto closepath fill\n", x1DC, y1DC, x2DC, y1DC, x2DC, y2DC, x1DC, y2DC); } void structGraphicsScreen :: v_circle (double xDC, double yDC, double rDC) { #if cairo if (duringXor) { gdkPrepareLine (this); gdk_draw_arc (d_window, d_gdkGraphicsContext, FALSE, xDC - rDC, yDC - rDC, rDC + rDC, rDC + rDC, 0, 360 * 64); gdkRevertLine (this); } else { if (d_cairoGraphicsContext == NULL) return; cairoPrepareLine (this); cairo_new_path (d_cairoGraphicsContext); cairo_arc (d_cairoGraphicsContext, xDC, yDC, rDC, 0.0, 2 * M_PI); cairo_stroke (d_cairoGraphicsContext); cairoRevertLine (this); } #elif win winPrepareLine (this); Ellipse (d_gdiGraphicsContext, xDC - rDC, yDC - rDC, xDC + rDC + 1, yDC + rDC + 1); DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareLine (this); CGContextBeginPath (d_macGraphicsContext); CGContextAddArc (d_macGraphicsContext, xDC, yDC, rDC, 0.0, NUM2pi, 0); CGContextStrokePath (d_macGraphicsContext); quartzRevertLine (this); GraphicsQuartz_exitDraw (this); #endif } void structGraphicsPostscript :: v_circle (double xDC, double yDC, double rDC) { psPrepareLine (this); d_printf (d_file, "N %ld %ld %ld C\n", (long) xDC, (long) yDC, (long) rDC); psRevertLine (this); } void structGraphicsScreen :: v_ellipse (long x1DC, long x2DC, long y1DC, long y2DC) { ORDER_DC #if cairo if (d_cairoGraphicsContext == NULL) return; cairoPrepareLine (this); cairo_new_path (d_cairoGraphicsContext); cairo_save (d_cairoGraphicsContext); cairo_translate (d_cairoGraphicsContext, 0.5 * (x2DC + x1DC), 0.5 * (y2DC + y1DC)); cairo_scale (d_cairoGraphicsContext, 0.5 * (x2DC - x1DC), 0.5 * (y2DC - y1DC)); cairo_arc (d_cairoGraphicsContext, 0.0, 0.0, 1.0, 0.0, 2 * M_PI); cairo_restore (d_cairoGraphicsContext); cairo_stroke (d_cairoGraphicsContext); cairoRevertLine (this); #elif win winPrepareLine (this); Ellipse (d_gdiGraphicsContext, x1DC, y2DC, x2DC + 1, y1DC + 1); DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareLine (this); CGContextBeginPath (d_macGraphicsContext); CGContextSaveGState (d_macGraphicsContext); CGContextTranslateCTM (d_macGraphicsContext, 0.5 * (x2DC + x1DC), 0.5 * (y2DC + y1DC)); CGContextScaleCTM (d_macGraphicsContext, 0.5 * (x2DC - x1DC), 0.5 * (y2DC - y1DC)); CGContextAddArc (d_macGraphicsContext, 0.0, 0.0, 1.0, 0.0, NUM2pi, 0); CGContextScaleCTM (d_macGraphicsContext, 2.0 / (x2DC - x1DC), 2.0 / (y2DC - y1DC)); CGContextStrokePath (d_macGraphicsContext); CGContextRestoreGState (d_macGraphicsContext); quartzRevertLine (this); GraphicsQuartz_exitDraw (this); #endif } void structGraphicsPostscript :: v_ellipse (long x1DC, long x2DC, long y1DC, long y2DC) { if (x1DC != x2DC && y1DC != y2DC) { // prevent division by zero psPrepareLine (this); /* To draw an ellipse, we will have to 'translate' and 'scale' and draw a circle. */ /* However, we have to scale back before the actual 'stroke', */ /* because we want the normal line thickness; */ /* So we cannot use 'gsave' and 'grestore', which clear the path (Cookbook 3). */ d_printf (d_file, "gsave %f %f translate %f %f scale N 0 0 1 0 360 arc\n" " %f %f scale stroke grestore\n", 0.5 * (x2DC + x1DC), 0.5 * (y2DC + y1DC), 0.5 * (x2DC - x1DC), 0.5 * (y2DC - y1DC), 2.0 / (x2DC - x1DC), 2.0 / (y2DC - y1DC)); psRevertLine (this); } } void structGraphicsScreen :: v_arc (long xDC, long yDC, long rDC, double fromAngle, double toAngle) { #if cairo if (d_cairoGraphicsContext == NULL) return; cairoPrepareLine (this); cairo_new_path (d_cairoGraphicsContext); cairo_arc (d_cairoGraphicsContext, xDC, yDC, rDC, -toAngle * (M_PI / 180.0), -fromAngle * (M_PI / 180.0)); cairo_stroke (d_cairoGraphicsContext); cairoRevertLine (this); #elif win int arcAngle = (int) toAngle - (int) fromAngle; POINT pt; if (arcAngle < 0.0) arcAngle += 360; winPrepareLine (this); MoveToEx (d_gdiGraphicsContext, xDC + rDC * cos (NUMpi / 180 * fromAngle), yDC - rDC * sin (NUMpi / 180 * fromAngle), & pt); AngleArc (d_gdiGraphicsContext, xDC, yDC, rDC, fromAngle, arcAngle); DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareLine (this); CGContextBeginPath (d_macGraphicsContext); CGContextAddArc (d_macGraphicsContext, xDC, yDC, rDC, NUM2pi - NUMpi / 180 * toAngle, NUM2pi - NUMpi / 180 * fromAngle, 0); CGContextStrokePath (d_macGraphicsContext); quartzRevertLine (this); GraphicsQuartz_exitDraw (this); #endif } void structGraphicsPostscript :: v_arc (long xDC, long yDC, long rDC, double fromAngle, double toAngle) { psPrepareLine (this); d_printf (d_file, "N %ld %ld %ld %f %f arc stroke\n", xDC, yDC, rDC, fromAngle, toAngle); psRevertLine (this); } /* Third level. */ void structGraphicsScreen :: v_fillCircle (long xDC, long yDC, long rDC) { #if cairo if (d_cairoGraphicsContext == NULL) return; cairo_new_path (d_cairoGraphicsContext); cairo_arc (d_cairoGraphicsContext, xDC, yDC, rDC, 0, 2 * M_PI); cairo_fill (d_cairoGraphicsContext); #elif win MY_BRUSH /* * NT cannot fill circles that span less than five pixels... */ Ellipse (d_gdiGraphicsContext, xDC - rDC - 1, yDC - rDC - 1, xDC + rDC + 1, yDC + rDC + 1); DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareFill (this); CGContextBeginPath (d_macGraphicsContext); CGContextAddArc (d_macGraphicsContext, xDC, yDC, rDC, 0.0, NUM2pi, 0); CGContextFillPath (d_macGraphicsContext); GraphicsQuartz_exitDraw (this); #else v_circle (xDC, yDC, rDC); #endif } void structGraphicsPostscript :: v_fillCircle (long xDC, long yDC, long rDC) { d_printf (d_file, "N %ld %ld %ld FC\n", xDC, yDC, rDC); } void structGraphicsScreen :: v_fillEllipse (long x1DC, long x2DC, long y1DC, long y2DC) { ORDER_DC #if cairo if (d_cairoGraphicsContext == NULL) return; cairo_new_path (d_cairoGraphicsContext); cairo_save (d_cairoGraphicsContext); cairo_translate (d_cairoGraphicsContext, 0.5 * (x2DC + x1DC), 0.5 * (y2DC + y1DC)); cairo_scale (d_cairoGraphicsContext, 0.5 * (x2DC - x1DC), 0.5 * (y2DC - y1DC)); cairo_arc (d_cairoGraphicsContext, 0.0, 0.0, 1.0, 0.0, 2 * M_PI); cairo_restore (d_cairoGraphicsContext); cairo_fill (d_cairoGraphicsContext); #elif win MY_BRUSH Ellipse (d_gdiGraphicsContext, x1DC, y2DC, x2DC + 1, y1DC + 1); DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareFill (this); CGContextBeginPath (d_macGraphicsContext); CGContextSaveGState (d_macGraphicsContext); CGContextTranslateCTM (d_macGraphicsContext, 0.5 * (x2DC + x1DC), 0.5 * (y2DC + y1DC)); CGContextScaleCTM (d_macGraphicsContext, 0.5 * (x2DC - x1DC), 0.5 * (y2DC - y1DC)); CGContextAddArc (d_macGraphicsContext, 0.0, 0.0, 1.0, 0.0, NUM2pi, 0); CGContextScaleCTM (d_macGraphicsContext, 2.0 / (x2DC - x1DC), 2.0 / (y2DC - y1DC)); CGContextFillPath (d_macGraphicsContext); CGContextRestoreGState (d_macGraphicsContext); GraphicsQuartz_exitDraw (this); #else v_ellipse (x1DC, x2DC, y1DC, y2DC); #endif } void structGraphicsPostscript :: v_fillEllipse (long x1DC, long x2DC, long y1DC, long y2DC) { d_printf (d_file, "gsave %ld %ld translate %ld %ld scale N 0 0 1 FC grestore\n", (x2DC + x1DC) / 2, (y2DC + y1DC) / 2, (x2DC - x1DC) / 2, (y2DC - y1DC) / 2); } void structGraphicsScreen :: v_button (long x1DC, long x2DC, long y1DC, long y2DC) { ORDER_DC #if cairo if (x2DC <= x1DC || y1DC <= y2DC) return; cairo_save (d_cairoGraphicsContext); if (d_drawingArea && 0) { // clip to drawing area int w, h; gdk_drawable_get_size (d_window, & w, & h); cairo_rectangle (d_cairoGraphicsContext, 0, 0, w, h); cairo_clip (d_cairoGraphicsContext); } cairo_set_line_width (d_cairoGraphicsContext, 1.0); double left = x1DC - 0.5, right = x2DC - 0.5, top = y2DC + 0.5, bottom = y1DC + 0.5; double width = right - left, height = bottom - top; cairo_set_source_rgb (d_cairoGraphicsContext, 0.1, 0.1, 0.1); // dark grey cairo_rectangle (d_cairoGraphicsContext, left, top, width, height); cairo_stroke (d_cairoGraphicsContext); left ++, right --, top ++, bottom --, width -= 2, height -= 2; if (width > 0 && height > 0) { cairo_set_source_rgb (d_cairoGraphicsContext, 0.3, 0.3, 0.3); cairo_move_to (d_cairoGraphicsContext, left + 1, bottom); cairo_line_to (d_cairoGraphicsContext, right, bottom); cairo_line_to (d_cairoGraphicsContext, right, top + 1); cairo_stroke (d_cairoGraphicsContext); cairo_set_source_rgb (d_cairoGraphicsContext, 1.0, 1.0, 1.0); cairo_move_to (d_cairoGraphicsContext, left, bottom); cairo_line_to (d_cairoGraphicsContext, left, top); cairo_line_to (d_cairoGraphicsContext, right, top); cairo_stroke (d_cairoGraphicsContext); left += 0.5, right -= 0.5, top += 0.5, bottom -= 0.5, width -= 1, height -= 1; if (width > 0 && height > 0) { cairo_set_source_rgb (d_cairoGraphicsContext, 0.65, 0.65, 0.65); cairo_rectangle (d_cairoGraphicsContext, left, top, width, height); cairo_fill (d_cairoGraphicsContext); } } cairo_restore (d_cairoGraphicsContext); #elif win RECT rect; rect. left = x1DC, rect. right = x2DC, rect. top = y2DC, rect. bottom = y1DC; DrawEdge (d_gdiGraphicsContext, & rect, EDGE_RAISED, BF_RECT); SelectPen (d_gdiGraphicsContext, GetStockPen (NULL_PEN)); SelectBrush (d_gdiGraphicsContext, GetStockBrush (LTGRAY_BRUSH)); Rectangle (d_gdiGraphicsContext, x1DC + 1, y2DC + 1, x2DC - 1, y1DC - 1); SelectPen (d_gdiGraphicsContext, GetStockPen (BLACK_PEN)); SelectBrush (d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); #elif mac int width, height; Rect rect; RGBColor rgb; width = x2DC - x1DC, height = y1DC - y2DC; if (width <= 0 || height <= 0) return; if (d_drawingArea) GuiMac_clipOn (d_drawingArea); SetPort (d_macPort); /* Dark grey. */ rgb. red = rgb. green = rgb. blue = (int) (unsigned int) (0.1 * 65535.0); RGBForeColor (& rgb); SetRect (& rect, x1DC - 1, y2DC - 1, x2DC, y1DC); FrameRect (& rect); if (width > 2 && height > 2) { rgb. red = rgb. green = rgb. blue = (int) (unsigned int) (0.3 * 65535.0); RGBForeColor (& rgb); MoveTo (x1DC, y1DC - 2); LineTo (x2DC - 2, y1DC - 2); MoveTo (x2DC - 2, y1DC - 2); LineTo (x2DC - 2, y2DC); rgb. red = rgb. green = rgb. blue = (int) (unsigned int) (1.0 * 65535.0); RGBForeColor (& rgb); MoveTo (x1DC, y1DC - 2); LineTo (x1DC, y2DC); MoveTo (x1DC, y2DC); LineTo (x2DC - 2, y2DC); if (width > 4 && height > 4) { rgb. red = rgb. green = rgb. blue = (int) (unsigned int) (0.65 * 65535.0); RGBForeColor (& rgb); SetRect (& rect, x1DC + 1, y2DC + 1, x2DC - 2, y1DC - 2); PaintRect (& rect); } } RGBForeColor (& theBlackColour); if (d_drawingArea) GuiMac_clipOff (); #endif } void structGraphics :: v_roundedRectangle (long x1DC, long x2DC, long y1DC, long y2DC, long r) { long dy = yIsZeroAtTheTop ? - r : r, xyDC [4]; ORDER_DC xyDC [0] = x1DC + r; xyDC [1] = y1DC; xyDC [2] = x2DC - r; xyDC [3] = y1DC; v_polyline (2, xyDC, false); v_arc (x2DC - r, y1DC + dy, r, -90, 0); xyDC [0] = x2DC; xyDC [1] = y1DC + dy; xyDC [2] = x2DC; xyDC [3] = y2DC - dy; v_polyline (2, xyDC, false); v_arc (x2DC - r, y2DC - dy, r, 0, 90); xyDC [0] = x2DC - r; xyDC [1] = y2DC; xyDC [2] = x1DC + r; xyDC [3] = y2DC; v_polyline (2, xyDC, false); v_arc (x1DC + r, y2DC - dy, r, 90, 180); xyDC [0] = x1DC; xyDC [1] = y2DC - dy; xyDC [2] = x1DC; xyDC [3] = y1DC + dy; v_polyline (2, xyDC, false); v_arc (x1DC + r, y1DC + dy, r, 180, 270); } void structGraphicsScreen :: v_roundedRectangle (long x1DC, long x2DC, long y1DC, long y2DC, long r) { #if win long dy = yIsZeroAtTheTop ? - r : r, xyDC [4]; ORDER_DC winPrepareLine (this); RoundRect (d_gdiGraphicsContext, x1DC, y2DC, x2DC + 1, y1DC + 1, r + r, r + r); DEFAULT return; #else GraphicsScreen_Parent :: v_roundedRectangle (x1DC, x2DC, y1DC, y2DC, r); #endif } /* Fourth level. */ void structGraphics :: v_fillRoundedRectangle (long x1DC, long x2DC, long y1DC, long y2DC, long r) { long dy = yIsZeroAtTheTop ? - r : r; ORDER_DC v_fillCircle (x2DC - r, y1DC + dy, r); v_fillCircle (x2DC - r, y2DC - dy, r); v_fillCircle (x1DC + r, y2DC - dy, r); v_fillCircle (x1DC + r, y1DC + dy, r); v_fillRectangle (x1DC, x2DC, y1DC + dy, y2DC - dy); v_fillRectangle (x1DC + r, x2DC - r, y1DC, y2DC); } /* Fifth level. */ #define wdx(x) ((x) * my scaleX + my deltaX) #define wdy(y) ((y) * my scaleY + my deltaY) void Graphics_polyline (Graphics me, long numberOfPoints, double *xWC, double *yWC) { // base 0 if (numberOfPoints == 0) return; long *xyDC; try { xyDC = Melder_malloc (long, 2 * numberOfPoints); } catch (MelderError) { /* * Out of memory: silently refuse to draw. */ Melder_clearError (); return; } for (long i = 0; i < numberOfPoints; i ++) { xyDC [i + i] = wdx (xWC [i]); xyDC [i + i + 1] = wdy (yWC [i]); } my v_polyline (numberOfPoints, xyDC, false); Melder_free (xyDC); if (my recording) { op (POLYLINE, 1 + 2 * numberOfPoints); put (numberOfPoints); mput (numberOfPoints, & xWC [0]) mput (numberOfPoints, & yWC [0]) } } void Graphics_polyline_closed (Graphics me, long numberOfPoints, double *xWC, double *yWC) { // base 0 if (numberOfPoints == 0) return; long *xyDC; try { xyDC = Melder_malloc (long, 2 * numberOfPoints); } catch (MelderError) { /* * Out of memory: silently refuse to draw. */ Melder_clearError (); return; } for (long i = 0; i < numberOfPoints; i ++) { xyDC [i + i] = wdx (xWC [i]); xyDC [i + i + 1] = wdy (yWC [i]); } my v_polyline (numberOfPoints, xyDC, true); Melder_free (xyDC); if (my recording) { op (POLYLINE_CLOSED, 1 + 2 * numberOfPoints); put (numberOfPoints); mput (numberOfPoints, & xWC [0]) mput (numberOfPoints, & yWC [0]) } } void Graphics_line (Graphics me, double x1WC, double y1WC, double x2WC, double y2WC) { long xyDC [4]; xyDC [0] = wdx (x1WC); xyDC [1] = wdy (y1WC); xyDC [2] = wdx (x2WC); xyDC [3] = wdy (y2WC); my v_polyline (2, xyDC, false); if (my recording) { op (LINE, 4); put (x1WC); put (y1WC); put (x2WC); put (y2WC); } } void Graphics_fillArea (Graphics me, long numberOfPoints, double *xWC, double *yWC) { long *xyDC; try { xyDC = Melder_malloc (long, 2 * numberOfPoints); } catch (MelderError) { /* * Out of memory: silently refuse to draw. */ Melder_clearError (); return; } for (long i = 0; i < numberOfPoints; i ++) { xyDC [i + i] = wdx (xWC [i]); xyDC [i + i + 1] = wdy (yWC [i]); } my v_fillArea (numberOfPoints, xyDC); Melder_free (xyDC); if (my recording) { op (FILL_AREA, 1 + 2 * numberOfPoints); put (numberOfPoints); mput (numberOfPoints, & xWC [0]) mput (numberOfPoints, & yWC [0]) } } #define MACRO_Graphics_function(TYPE) \ long x1DC, x2DC; \ long clipy1 = wdy (my d_y1WC), clipy2 = wdy (my d_y2WC); \ double dx, offsetX, translation, scale; \ long i, n = ix2 - ix1 + 1; \ \ if (ix2 <= ix1 || my scaleX == 0.0) return; \ \ dx = (x2WC - x1WC) / (n - 1); \ offsetX = x1WC - ix1 * dx; \ /* xDC = wdx (offsetX + i * dx) */ \ translation = wdx (offsetX); \ scale = dx * my scaleX; \ x1DC = translation + ix1 * scale; \ x2DC = translation + ix2 * scale; \ if (n > (x2DC - x1DC + 1) * 2) { /* Optimize: draw one vertical line for each device x coordinate. */ \ long numberOfPixels = x2DC - x1DC + 1, k = 0; \ long numberOfPointsActuallyDrawn = numberOfPixels * 2; \ long *xyDC; \ TYPE lastMini; \ if (numberOfPointsActuallyDrawn < 1) return; \ xyDC = Melder_malloc_f (long, 2 * numberOfPointsActuallyDrawn); \ for (i = 0; i < numberOfPixels; i ++) { \ long j, jmin = ix1 + i / scale, jmax = ix1 + (i + 1) / scale; \ TYPE mini, maxi; \ long minDC, maxDC; \ if (jmin > ix2) jmin = ix2; \ if (jmax > ix2) jmax = ix2; \ mini = yWC [STAGGER (jmin)], maxi = mini; \ for (j = jmin + 1; j <= jmax; j ++) { /* One point overlap. */ \ TYPE value = yWC [STAGGER (j)]; \ if (value > maxi) maxi = value; \ else if (value < mini) mini = value; \ } \ minDC = wdy (mini); \ maxDC = wdy (maxi); \ if (my yIsZeroAtTheTop) { \ if (minDC > clipy1) minDC = clipy1; \ if (maxDC > clipy1) maxDC = clipy1; \ if (maxDC < clipy2) maxDC = clipy2; \ if (minDC < clipy2) minDC = clipy2; \ } else { \ if (minDC < clipy1) minDC = clipy1; \ if (maxDC < clipy1) maxDC = clipy1; \ if (maxDC > clipy2) maxDC = clipy2; \ if (minDC > clipy2) minDC = clipy2; \ } \ if (i == 0) { \ if (yWC [STAGGER (jmin)] < yWC [STAGGER (jmax)]) { \ xyDC [k ++] = x1DC; \ xyDC [k ++] = minDC; \ xyDC [k ++] = x1DC; \ xyDC [k ++] = maxDC; \ } else { \ xyDC [k ++] = x1DC; \ xyDC [k ++] = maxDC; \ xyDC [k ++] = x1DC; \ xyDC [k ++] = minDC; \ } \ } else if (minDC == xyDC [k - 1]) { \ xyDC [k ++] = x1DC + i; \ xyDC [k ++] = maxDC; \ } else if (maxDC == xyDC [k - 1]) { \ xyDC [k ++] = x1DC + i; \ xyDC [k ++] = minDC; \ } else if (mini > lastMini) { \ xyDC [k ++] = x1DC + i; \ xyDC [k ++] = minDC; \ xyDC [k ++] = x1DC + i; \ xyDC [k ++] = maxDC; \ } else { \ xyDC [k ++] = x1DC + i; \ xyDC [k ++] = maxDC; \ xyDC [k ++] = x1DC + i; \ xyDC [k ++] = minDC; \ } \ lastMini = mini; \ } \ if (k > 1) my v_polyline (k / 2, xyDC, false); \ Melder_free (xyDC); \ } else { /* Normal. */ \ long *xyDC = Melder_malloc_f (long, 2 * n); \ for (i = 0; i < n; i ++) { \ long ix = ix1 + i; \ long value = wdy (yWC [STAGGER (ix)]); \ xyDC [i + i] = translation + ix * scale; \ if (my yIsZeroAtTheTop) { \ if (FUNCTIONS_ARE_CLIPPED && value > clipy1) value = clipy1; \ if (FUNCTIONS_ARE_CLIPPED && value < clipy2) value = clipy2; \ } else { \ if (FUNCTIONS_ARE_CLIPPED && value < clipy1) value = clipy1; \ if (FUNCTIONS_ARE_CLIPPED && value > clipy2) value = clipy2; \ } \ xyDC [i + i + 1] = value; \ } \ my v_polyline (n, xyDC, false); \ Melder_free (xyDC); \ } void Graphics_function (Graphics me, double yWC [], long ix1, long ix2, double x1WC, double x2WC) { #define STAGGER(i) (i) MACRO_Graphics_function (double) #undef STAGGER if (my recording) { op (FUNCTION, 3 + n); put (n); put (x1WC); put (x2WC); mput (n, & yWC [ix1]) } } void Graphics_function16 (Graphics me, int16_t yWC [], int stagger, long ix1, long ix2, double x1WC, double x2WC) { if (stagger == 1) { #define STAGGER(i) ((i) + (i)) MACRO_Graphics_function (int16_t) #undef STAGGER } else if (stagger > 1) { #define STAGGER(i) ((stagger + 1) * (i)) MACRO_Graphics_function (int16_t) #undef STAGGER } else { #define STAGGER(i) (i) MACRO_Graphics_function (int16_t) #undef STAGGER } } void Graphics_rectangle (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC) { my v_rectangle (wdx (x1WC), wdx (x2WC), wdy (y1WC), wdy (y2WC)); if (my recording) { op (RECTANGLE, 4); put (x1WC); put (x2WC); put (y1WC); put (y2WC); } } void Graphics_fillRectangle (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC) { my v_fillRectangle (wdx (x1WC), wdx (x2WC), wdy (y1WC), wdy (y2WC)); if (my recording) { op (FILL_RECTANGLE, 4); put (x1WC); put (x2WC); put (y1WC); put (y2WC); } } void Graphics_roundedRectangle (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC, double r_mm) { my v_roundedRectangle (wdx (x1WC), wdx (x2WC), wdy (y1WC), wdy (y2WC), ceil (r_mm * my resolution / 25.4)); if (my recording) { op (ROUNDED_RECTANGLE, 5); put (x1WC); put (x2WC); put (y1WC); put (y2WC); put (r_mm); } } void Graphics_fillRoundedRectangle (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC, double r_mm) { my v_fillRoundedRectangle (wdx (x1WC), wdx (x2WC), wdy (y1WC), wdy (y2WC), ceil (r_mm * my resolution / 25.4)); if (my recording) { op (FILL_ROUNDED_RECTANGLE, 5); put (x1WC); put (x2WC); put (y1WC); put (y2WC); put (r_mm); } } void Graphics_button (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC) { my v_button (wdx (x1WC), wdx (x2WC), wdy (y1WC), wdy (y2WC)); if (my recording) { op (BUTTON, 4); put (x1WC); put (x2WC); put (y1WC); put (y2WC); } } void Graphics_innerRectangle (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC) { int dy = my yIsZeroAtTheTop ? -1 : 1; my v_rectangle (wdx (x1WC) + 1, wdx (x2WC) - 1, wdy (y1WC) + dy, wdy (y2WC) - dy); if (my recording) { op (INNER_RECTANGLE, 4); put (x1WC); put (x2WC); put (y1WC); put (y2WC); } } void Graphics_circle (Graphics me, double xWC, double yWC, double rWC) { my v_circle (wdx (xWC), wdy (yWC), my scaleX * rWC); if (my recording) { op (CIRCLE, 3); put (xWC); put (yWC); put (rWC); } } void Graphics_circle_mm (Graphics me, double xWC, double yWC, double diameter) { my v_circle (wdx (xWC), wdy (yWC), 0.5 * diameter * my resolution / 25.4); if (my recording) { op (CIRCLE_MM, 3); put (xWC); put (yWC); put (diameter); } } void Graphics_fillCircle (Graphics me, double xWC, double yWC, double rWC) { my v_fillCircle (wdx (xWC), wdy (yWC), ceil (my scaleX * rWC)); if (my recording) { op (FILL_CIRCLE, 3); put (xWC); put (yWC); put (rWC); } } void Graphics_fillCircle_mm (Graphics me, double xWC, double yWC, double diameter) { my v_fillCircle (wdx (xWC), wdy (yWC), ceil (0.5 * diameter * my resolution / 25.4)); if (my recording) { op (FILL_CIRCLE_MM, 3); put (xWC); put (yWC); put (diameter); } } void Graphics_rectangle_mm (Graphics me, double xWC, double yWC, double horSide, double vertSide) { long xDC = wdx (xWC), yDC = wdy (yWC); long halfHorSide = ceil (0.5 * horSide * my resolution / 25.4); long halfVertSide = ceil (0.5 * vertSide * my resolution / 25.4); if (my yIsZeroAtTheTop) { my v_rectangle (xDC - halfHorSide, xDC + halfHorSide, yDC + halfVertSide, yDC - halfVertSide); } else { my v_rectangle (xDC - halfHorSide, xDC + halfHorSide, yDC - halfVertSide, yDC + halfVertSide); } if (my recording) { op (RECTANGLE_MM, 4); put (xWC); put (yWC); put (horSide); put (vertSide); } } void Graphics_fillRectangle_mm (Graphics me, double xWC, double yWC, double horSide, double vertSide) { long xDC = wdx (xWC), yDC = wdy (yWC); long halfHorSide = ceil (0.5 * horSide * my resolution / 25.4); long halfVertSide = ceil (0.5 * vertSide * my resolution / 25.4); if (my yIsZeroAtTheTop) { my v_fillRectangle (xDC - halfHorSide, xDC + halfHorSide, yDC + halfVertSide, yDC - halfVertSide); } else { my v_fillRectangle (xDC - halfHorSide, xDC + halfHorSide, yDC - halfVertSide, yDC + halfVertSide); } if (my recording) { op (FILL_RECTANGLE_MM, 4); put (xWC); put (yWC); put (horSide); put (vertSide); } } void Graphics_ellipse (Graphics me, double x1, double x2, double y1, double y2) { my v_ellipse (wdx (x1), wdx (x2), wdy (y1), wdy (y2)); if (my recording) { op (ELLIPSE, 4); put (x1); put (x2); put (y1); put (y2); } } void Graphics_fillEllipse (Graphics me, double x1, double x2, double y1, double y2) { my v_fillEllipse (wdx (x1), wdx (x2), wdy (y1), wdy (y2)); if (my recording) { op (FILL_ELLIPSE, 4); put (x1); put (x2); put (y1); put (y2); } } void Graphics_arc (Graphics me, double xWC, double yWC, double rWC, double fromAngle, double toAngle) { my v_arc (wdx (xWC), wdy (yWC), my scaleX * rWC, fromAngle, toAngle); if (my recording) { op (ARC, 5); put (xWC); put (yWC); put (rWC); put (fromAngle); put (toAngle); } } void Graphics_fillArc (Graphics me, double xWC, double yWC, double rWC, double fromAngle, double toAngle) { my v_arc (wdx (xWC), wdy (yWC), my scaleX * rWC, fromAngle, toAngle); // NYI v_fillArc if (my recording) { op (FILL_ARC, 5); put (xWC); put (yWC); put (rWC); put (fromAngle); put (toAngle); } } /* Arrows. */ void structGraphics :: v_arrowHead (long xDC, long yDC, double angle) { (void) xDC; (void) yDC; (void) angle; } void structGraphicsScreen :: v_arrowHead (long xDC, long yDC, double angle) { #if cairo if (d_cairoGraphicsContext == NULL) return; double size = 10.0 * resolution * arrowSize / 75.0; // TODO: die 75 zou dat niet de scherm resolutie moeten worden? cairo_new_path (d_cairoGraphicsContext); cairo_move_to (d_cairoGraphicsContext, xDC + cos ((angle + 160) * NUMpi / 180) * size, yDC - sin ((angle + 160) * NUMpi / 180) * size); cairo_line_to (d_cairoGraphicsContext, xDC, yDC); cairo_line_to (d_cairoGraphicsContext, xDC + cos ((angle - 160) * NUMpi / 180) * size, yDC - sin ((angle - 160) * NUMpi / 180) * size); cairo_close_path (d_cairoGraphicsContext); cairo_fill (d_cairoGraphicsContext); #elif win double size = 10.0 * resolution * arrowSize / 72.0; MY_BRUSH BeginPath (d_gdiGraphicsContext); MoveToEx (d_gdiGraphicsContext, xDC + cos ((angle + 160) * NUMpi / 180) * size, yDC - sin ((angle + 160) * NUMpi / 180) * size, NULL); LineTo (d_gdiGraphicsContext, xDC, yDC); LineTo (d_gdiGraphicsContext, xDC + cos ((angle - 160) * NUMpi / 180) * size, yDC - sin ((angle - 160) * NUMpi / 180) * size); EndPath (d_gdiGraphicsContext); FillPath (d_gdiGraphicsContext); DEFAULT #elif mac GraphicsQuartz_initDraw (this); quartzPrepareFill (this); CGContextSaveGState (d_macGraphicsContext); CGContextBeginPath (d_macGraphicsContext); CGContextTranslateCTM (d_macGraphicsContext, xDC, yDC); CGContextRotateCTM (d_macGraphicsContext, - angle * NUMpi / 180); CGContextMoveToPoint (d_macGraphicsContext, 0.0, 0.0); double size = 10.0 * resolution * arrowSize / 72.0; double radius = resolution * arrowSize / 30; CGContextAddArc (d_macGraphicsContext, - size, 0.0, radius, - NUMpi / 3.0, NUMpi / 3.0, 0); CGContextAddLineToPoint (d_macGraphicsContext, 0.0, 0.0); CGContextFillPath (d_macGraphicsContext); CGContextRestoreGState (d_macGraphicsContext); GraphicsQuartz_exitDraw (this); #endif } void structGraphicsPostscript :: v_arrowHead (long xDC, long yDC, double angle) { long length = resolution * arrowSize / 10, radius = resolution * arrowSize / 30; d_printf (d_file, "gsave %ld %ld translate %f rotate\n" "N 0 0 M -%ld 0 %ld -60 60 arc closepath fill grestore\n", xDC, yDC, angle, length, radius); } void Graphics_arrow (Graphics me, double x1WC, double y1WC, double x2WC, double y2WC) { double angle = (180.0 / NUMpi) * atan2 ((wdy (y2WC) - wdy (y1WC)) * (my yIsZeroAtTheTop ? -1 : 1), wdx (x2WC) - wdx (x1WC)); double size = my screen ? 10.0 * my resolution * my arrowSize / 72.0 : my resolution * my arrowSize / 10; long xyDC [4]; xyDC [0] = wdx (x1WC); xyDC [1] = wdy (y1WC); xyDC [2] = wdx (x2WC) + (my screen ? 0.7 : 0.6) * cos ((angle - 180) * NUMpi / 180) * size; xyDC [3] = wdy (y2WC) + (my yIsZeroAtTheTop ? -1.0 : 1.0) * (my screen ? 0.7 : 0.6) * sin ((angle - 180) * NUMpi / 180) * size; my v_polyline (2, xyDC, false); my v_arrowHead (wdx (x2WC), wdy (y2WC), angle); if (my recording) { op (ARROW, 4); put (x1WC); put (y1WC); put (x2WC); put (y2WC); } } void Graphics_doubleArrow (Graphics me, double x1WC, double y1WC, double x2WC, double y2WC) { double angle = (180.0 / NUMpi) * atan2 ((wdy (y2WC) - wdy (y1WC)) * (my yIsZeroAtTheTop ? -1 : 1), wdx (x2WC) - wdx (x1WC)); double size = my screen ? 10.0 * my resolution * my arrowSize / 72.0 : my resolution * my arrowSize / 10; long xyDC [4]; xyDC [0] = wdx (x1WC) + (my screen ? 0.7 : 0.6) * cos (angle * NUMpi / 180) * size; xyDC [1] = wdy (y1WC) + (my yIsZeroAtTheTop ? -1.0 : 1.0) * (my screen ? 0.7 : 0.6) * sin (angle * NUMpi / 180) * size; xyDC [2] = wdx (x2WC) + (my screen ? 0.7 : 0.6) * cos ((angle - 180) * NUMpi / 180) * size; xyDC [3] = wdy (y2WC) + (my yIsZeroAtTheTop ? -1.0 : 1.0) * (my screen ? 0.7 : 0.6) * sin ((angle - 180) * NUMpi / 180) * size; my v_polyline (2, xyDC, false); my v_arrowHead (wdx (x1WC), wdy (y1WC), angle + 180); //my v_polyline (2, xyDC); my v_arrowHead (wdx (x2WC), wdy (y2WC), angle); if (my recording) { op (DOUBLE_ARROW, 4); put (x1WC); put (y1WC); put (x2WC); put (y2WC); } } void Graphics_arcArrow (Graphics me, double xWC, double yWC, double rWC, double fromAngle, double toAngle, int arrowAtStart, int arrowAtEnd) { my v_arc (wdx (xWC), wdy (yWC), my scaleX * rWC, fromAngle, toAngle); if (arrowAtStart) my v_arrowHead ( wdx (xWC + rWC * cos (fromAngle * (NUMpi / 180.0))), wdy (yWC + rWC * sin (fromAngle * (NUMpi / 180.0))), fromAngle - 90); if (arrowAtEnd) my v_arrowHead ( wdx (xWC + rWC * cos (toAngle * (NUMpi / 180.0))), wdy (yWC + rWC * sin (toAngle * (NUMpi / 180.0))), toAngle + 90); if (my recording) { op (ARC_ARROW, 7); put (xWC); put (yWC); put (rWC); put (fromAngle); put (toAngle); put (arrowAtStart); put (arrowAtEnd); } } /* Output attributes. */ void Graphics_setLineType (Graphics me, int lineType) { my lineType = lineType; if (my recording) { op (SET_LINE_TYPE, 1); put (lineType); } } void Graphics_setLineWidth (Graphics me, double lineWidth) { my lineWidth = lineWidth; if (my recording) { op (SET_LINE_WIDTH, 1); put (lineWidth); } } void Graphics_setArrowSize (Graphics me, double arrowSize) { my arrowSize = arrowSize; if (my recording) { op (SET_ARROW_SIZE, 1); put (arrowSize); } } /* Inquiries. */ int Graphics_inqLineType (Graphics me) { return my lineType; } double Graphics_inqLineWidth (Graphics me) { return my lineWidth; } double Graphics_inqArrowSize (Graphics me) { return my arrowSize; } /* End of file Graphics_linesAndAreas.cpp */ sources_5316/sys/TextEditor.h0000644000176700017670000000351011623751546015016 0ustar paulpaul#ifndef _TextEditor_h_ #define _TextEditor_h_ /* TextEditor.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Editor.h" Thing_define (TextEditor, Editor) { // new data: public: structMelderFile file; GuiObject textWidget; UiForm openDialog, saveDialog, printDialog, findDialog; int dirty, fontSize; GuiObject dirtyNewDialog, dirtyOpenDialog, dirtyCloseDialog; GuiObject fontSizeButton_10, fontSizeButton_12, fontSizeButton_14, fontSizeButton_18, fontSizeButton_24; // functions: void init (GuiObject parent, const wchar *initialText); // overridden methods: virtual void v_destroy (); virtual void v_nameChanged (); virtual void v_goAway (); virtual void v_createChildren (); virtual void v_createMenus (); virtual bool v_hasQueryMenu () { return false; } // new methods: virtual bool v_fileBased () { return true; }; // if true, have New, Open..., Save; if false, have Clear virtual void v_clear () { } }; TextEditor TextEditor_create ( GuiObject parent, const wchar *initialText // may be NULL ); void TextEditor_showOpen (TextEditor me); void TextEditor_prefs (void); /* End of file TextEditor.h */ #endif sources_5316/sys/melder_files.cpp0000644000176700017670000007732411646364143015724 0ustar paulpaul/* melder_files.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * rvs&pb 2002/03/07 url support * pb 2002/03/10 Mach compatibility * pb 2003/09/12 MelderFile_getMacType * pb 2003/09/14 MelderDir_relativePathToFile * pb 2004/09/25 use /tmp as temporary directory * pb 2004/10/16 C++ compatible structs * pb 2005/11/07 Windows: use %USERPROFILE% rather than %HOMESHARE%%HOMEPATH% * rvs&pb 2005/11/18 url support * pb 2006/01/21 MelderFile_writeText does not create temporary file * pb 2006/08/03 openForWriting * rvs 2006/08/12 curl: do not fail on error * pb 2006/08/12 check whether unicodeName exists * pb 2006/10/28 erased MacOS 9 stuff * Erez Volk 2007/05/14 FLAC support * pb 2007/05/28 wchar_t * pb 2007/06/09 more wchar_t * pb 2007/08/12 more wchar_t * pb 2007/10/05 FSFindFolder * pb 2008/11/01 warn after finding final tabs (not just spaces) in file names * pb 2010/12/14 more high Unicode compatibility * pb 2011/04/05 C++ */ #include using namespace std; #if defined (UNIX) || defined __MWERKS__ #include #endif #if defined (UNIX) #include #endif #if defined (CURLPRESENT) #include #endif #ifdef _WIN32 #include #endif #if defined (macintosh) #include "macport_on.h" #include #include "macport_off.h" #endif #include #include "melder.h" #include "flac_FLAC_stream_encoder.h" #include "abcio.h" #if defined (macintosh) #include #define UNIX #include #include "UnicodeData.h" #endif static wchar_t theShellDirectory [kMelder_MAXPATH+1]; void Melder_rememberShellDirectory (void) { structMelderDir shellDir = { { 0 } }; Melder_getDefaultDir (& shellDir); wcscpy (theShellDirectory, Melder_dirToPath (& shellDir)); } wchar_t * Melder_getShellDirectory (void) { return & theShellDirectory [0]; } void Melder_wcsTo8bitFileRepresentation_inline (const wchar_t *wcs, char *utf8) { #if defined (_WIN32) int n = wcslen (wcs), i, j; for (i = 0, j = 0; i < n; i ++) { utf8 [j ++] = wcs [i] <= 255 ? wcs [i] : '?'; // The usual replacement on Windows. } utf8 [j] = '\0'; #elif defined (macintosh) /* On the Mac, the POSIX path name is stored in canonically decomposed UTF-8 encoding. The path is probably in precomposed UTF-32. So we first convert to UTF-16, then turn into CFString, then decompose, then convert to UTF-8. */ UniChar unipath [kMelder_MAXPATH+1]; long n = wcslen (wcs), n_utf16 = 0; for (long i = 0; i < n; i ++) { uint32_t kar = wcs [i]; if (kar <= 0xFFFF) { unipath [n_utf16 ++] = kar; // including null byte } else if (kar <= 0x10FFFF) { kar -= 0x10000; unipath [n_utf16 ++] = 0xD800 | (kar >> 10); unipath [n_utf16 ++] = 0xDC00 | (kar & 0x3FF); } else { unipath [n_utf16 ++] = UNICODE_REPLACEMENT_CHARACTER; } } unipath [n_utf16] = '\0'; CFStringRef cfpath = CFStringCreateWithCharacters (NULL, unipath, n_utf16); CFMutableStringRef cfpath2 = CFStringCreateMutableCopy (NULL, 0, cfpath); CFRelease (cfpath); CFStringNormalize (cfpath2, kCFStringNormalizationFormD); // Mac requires decomposed characters. CFStringGetCString (cfpath2, (char *) utf8, kMelder_MAXPATH+1, kCFStringEncodingUTF8); // Mac POSIX requires UTF-8. CFRelease (cfpath2); #else Melder_wcsToUtf8_inline (wcs, utf8); #endif } #if ! defined (_WIN32) void Melder_8bitFileRepresentationToWcs_inline (const char *path, wchar_t *wpath) { #if defined (macintosh) CFStringRef cfpath = CFStringCreateWithCString (NULL, path, kCFStringEncodingUTF8); Melder_assert (cfpath != 0); CFMutableStringRef cfpath2 = CFStringCreateMutableCopy (NULL, 0, cfpath); CFRelease (cfpath); CFStringNormalize (cfpath2, kCFStringNormalizationFormC); // Praat requires composed characters. long n_utf16 = CFStringGetLength (cfpath2); long n_wcs = 0; for (long i = 0; i < n_utf16; i ++) { uint32_t kar = CFStringGetCharacterAtIndex (cfpath2, i); if (kar >= 0xD800 && kar <= 0xDBFF) { uint32_t kar2 = CFStringGetCharacterAtIndex (cfpath2, ++ i); if (kar2 >= 0xDC00 && kar2 <= 0xDFFF) { kar = (((kar & 0x3FF) << 10) | (kar2 & 0x3FF)) + 0x10000; } else { kar = UNICODE_REPLACEMENT_CHARACTER; } } wpath [n_wcs ++] = kar; } wpath [n_wcs] = '\0'; CFRelease (cfpath2); #else Melder_8bitToWcs_inline (path, wpath, kMelder_textInputEncoding_UTF8); #endif } #endif #if defined (macintosh) void Melder_machToFile (void *void_fsref, MelderFile file) { FSRef *fsref = (FSRef *) void_fsref; char path [kMelder_MAXPATH+1]; FSRefMakePath (fsref, (unsigned char *) path, kMelder_MAXPATH); // Decomposed UTF-8. Melder_8bitFileRepresentationToWcs_inline (path, file -> path); } void Melder_machToDir (void *void_fsref, MelderDir dir) { FSRef *fsref = (FSRef *) void_fsref; char path [kMelder_MAXPATH+1]; FSRefMakePath (fsref, (unsigned char *) path, kMelder_MAXPATH); // Decomposed UTF-8. Melder_8bitFileRepresentationToWcs_inline (path, dir -> path); } void Melder_fileToMach (MelderFile file, void *void_fsref) { char path [kMelder_MAXPATH+1]; Melder_wcsTo8bitFileRepresentation_inline (file -> path, path); OSStatus err = FSPathMakeRef ((unsigned char *) path, (FSRef *) void_fsref, NULL); if (err != noErr && err != fnfErr) Melder_throw ("Error #", err, " translating file name ", file -> path, "."); } void Melder_dirToMach (MelderDir dir, void *void_fsref) { char path [kMelder_MAXPATH+1]; Melder_wcsTo8bitFileRepresentation_inline (dir -> path, path); OSStatus err = FSPathMakeRef ((unsigned char *) path, (FSRef *) void_fsref, NULL); if (err != noErr && err != fnfErr) Melder_throw ("Error #", err, " translating dir name ", dir -> path, "."); } #endif const wchar_t * MelderFile_name (MelderFile file) { #if defined (UNIX) wchar_t *slash = wcsrchr (file -> path, '/'); return slash ? slash + 1 : file -> path; #elif defined (_WIN32) wchar_t *backslash = wcsrchr (file -> path, '\\'); return backslash ? backslash + 1 : file -> path; #endif } wchar_t * MelderDir_name (MelderDir dir) { #if defined (UNIX) wchar_t *slash = wcsrchr (dir -> path, '/'); return slash ? slash + 1 : dir -> path; #elif defined (_WIN32) wchar_t *backslash = wcsrchr (dir -> path, '\\'); return backslash ? backslash + 1 : dir -> path; #endif } void Melder_pathToDir (const wchar *path, MelderDir dir) { wcscpy (dir -> path, path); } void Melder_pathToFile (const wchar *path, MelderFile file) { /* * This handles complete path names only. * Unlike Melder_relativePathToFile, this handles Windows file names with slashes in them. * * Used if we know for sure that we have a complete path name, * i.e. if the program determined the name (fileselector, printing, prefs). */ wcscpy (file -> path, path); } void Melder_relativePathToFile (const wchar *path, MelderFile file) { /* * This handles complete and partial path names, * and translates slashes to native directory separators (unlike Melder_pathToFile). * * Used if we do not know for sure that we have a complete path name, * i.e. if the user determined the name (scripting). */ #if defined (UNIX) /* * We assume that Unix complete path names start with a slash. */ if (path [0] == '~' && path [1] == '/') { swprintf (file -> path, kMelder_MAXPATH+1, L"%ls%ls", Melder_peekUtf8ToWcs (getenv ("HOME")), & path [1]); } else if (path [0] == '/' || wcsequ (path, L"") || wcsstr (path, L"://")) { wcscpy (file -> path, path); } else { structMelderDir dir = { { 0 } }; Melder_getDefaultDir (& dir); /* BUG */ if (dir. path [0] == '/' && dir. path [1] == '\0') { wcscpy (file -> path, L"/"); wcscat (file -> path, path); } else { wcscpy (file -> path, dir. path); wcscat (file -> path, L"/"); wcscat (file -> path, path); } } #elif defined (_WIN32) /* * We assume that Win32 complete path names look like: * C:\WINDOWS\CTRL32.DLL * LPT1: * \\host\path */ if (wcschr (path, '/') && ! wcsstr (path, L"://")) { wchar_t winPath [kMelder_MAXPATH+1]; wcscpy (winPath, path); for (;;) { wchar_t *slash = wcschr (winPath, '/'); if (slash == NULL) break; *slash = '\\'; } Melder_relativePathToFile (winPath, file); return; } if (wcschr (path, ':') || path [0] == '\\' && path [1] == '\\' || wcsequ (path, L"")) { wcscpy (file -> path, path); } else { structMelderDir dir = { { 0 } }; Melder_getDefaultDir (& dir); /* BUG */ static MelderString buffer = { 0 }; MelderString_empty (& buffer); MelderString_append (& buffer, dir. path, dir. path [0] != '\0' && dir. path [wcslen (dir. path) - 1] == '\\' ? L"" : L"\\", path); wcscpy (file -> path, buffer.string); } #endif } wchar * Melder_dirToPath (MelderDir dir) { return & dir -> path [0]; } wchar * Melder_fileToPath (MelderFile file) { return & file -> path [0]; } void MelderFile_copy (MelderFile file, MelderFile copy) { wcscpy (copy -> path, file -> path); } void MelderDir_copy (MelderDir dir, MelderDir copy) { wcscpy (copy -> path, dir -> path); } bool MelderFile_equal (MelderFile file1, MelderFile file2) { return wcsequ (file1 -> path, file2 -> path); } bool MelderDir_equal (MelderDir dir1, MelderDir dir2) { return wcsequ (dir1 -> path, dir2 -> path); } void MelderFile_setToNull (MelderFile file) { file -> path [0] = '\0'; } bool MelderFile_isNull (MelderFile file) { return file -> path [0] == '\0'; } void MelderDir_setToNull (MelderDir dir) { dir -> path [0] = '\0'; } bool MelderDir_isNull (MelderDir dir) { return dir -> path [0] == '\0'; } void MelderDir_getFile (MelderDir parent, const wchar_t *fileName, MelderFile file) { #if defined (UNIX) if (parent -> path [0] == '/' && parent -> path [1] == '\0') { swprintf (file -> path, kMelder_MAXPATH+1, L"/%ls", fileName); } else { swprintf (file -> path, kMelder_MAXPATH+1, L"%ls/%ls", parent -> path, fileName); } #elif defined (_WIN32) if (wcsrchr (file -> path, '\\') - file -> path == wcslen (file -> path) - 1) { swprintf (file -> path, kMelder_MAXPATH+1, L"%ls%ls", parent -> path, fileName); } else { swprintf (file -> path, kMelder_MAXPATH+1, L"%ls\\%ls", parent -> path, fileName); } #endif } void MelderDir_relativePathToFile (MelderDir dir, const wchar_t *path, MelderFile file) { structMelderDir saveDir = { { 0 } }; Melder_getDefaultDir (& saveDir); Melder_setDefaultDir (dir); Melder_relativePathToFile (path, file); Melder_setDefaultDir (& saveDir); } #ifndef UNIX static void Melder_getDesktop (MelderDir dir) { dir -> path [0] = '\0'; } #endif void MelderFile_getParentDir (MelderFile file, MelderDir parent) { #if defined (UNIX) /* * The parent of /usr/hello.txt is /usr. * The parent of /hello.txt is /. */ wchar_t *slash; wcscpy (parent -> path, file -> path); slash = wcsrchr (parent -> path, '/'); if (slash) *slash = '\0'; if (parent -> path [0] == '\0') wcscpy (parent -> path, L"/"); #elif defined (_WIN32) /* * The parent of C:\WINDOWS\CTRL.DLL is C:\WINDOWS. * The parent of E:\Praat.exe is E:\. * The parent of \\Swine\Apps\init.txt is \\Swine\Apps. * The parent of \\Swine\init.txt is \\Swine\. (BUG ?) */ wchar_t *colon; wcscpy (parent -> path, file -> path); colon = wcschr (parent -> path, ':'); if (colon) { wchar_t *backslash = wcsrchr (parent -> path, '\\'); if (backslash) { /* C:\WINDOWS\CTRL.DLL or C:\AUTOEXEC.BAT */ if (backslash - colon == 1) { /* C:\AUTOEXEC.BAT */ * (backslash + 1) = '\0'; /* C:\ */ } else { /* C:\WINDOWS\CTRL.DLL */ *backslash = '\0'; /* C:\WINDOWS */ } } else { /* ??? */ Melder_getDesktop (parent); /* empty string */ } } else if (parent -> path [0] == '\\' && parent -> path [1] == '\\') { wchar_t *backslash = wcsrchr (parent -> path + 2, '\\'); if (backslash) { /* \\Swine\Apps\init.txt or \\Swine\init.txt */ wchar_t *leftBackslash = wcschr (parent -> path + 2, '\\'); if (backslash - leftBackslash == 0) { /* \\Swine\init.txt */ * (backslash + 1) = '\0'; /* \\Swine\ */ } else { /* \\Swine\Apps\init.txt */ *backslash = '\0'; /* \\Swine\Apps */ } } else { /* \\init.txt ??? */ Melder_getDesktop (parent); /* empty string */ } } else { /* Unknown path type. */ Melder_getDesktop (parent); /* empty string */ } #endif } void MelderDir_getParentDir (MelderDir dir, MelderDir parent) { #if defined (UNIX) /* * The parent of /usr/local is /usr. * The parent of /usr is /. * The parent of / is "". */ wchar_t *slash; wcscpy (parent -> path, dir -> path); slash = wcsrchr (parent -> path, '/'); if (slash) { if (slash - parent -> path == 0) { if (slash [1] == '\0') { /* Child is "/". */ parent -> path [0] = '\0'; /* Parent is "". */ } else { /* Child is "/usr". */ slash [1] = '\0'; /* Parent is "/". */ } } else { /* Child is "/usr/local". */ *slash = '\0'; /* Parent is "/usr". */ } } else { parent -> path [0] = '\0'; /* Some failure. Desktop. */ } #elif defined (_WIN32) /* * The parent of C:\WINDOWS is C:\. * The parent of E:\ is the desktop. * The parent of \\Swine\ is the desktop. (BUG ?) */ wchar_t *colon; wcscpy (parent -> path, dir -> path); colon = wcschr (parent -> path, ':'); if (colon) { int length = wcslen (parent -> path); wchar_t *backslash = wcsrchr (parent -> path, '\\'); if (backslash) { /* C:\WINDOWS\FONTS or C:\WINDOWS or C:\ */ if (backslash - parent -> path == length - 1) { /* C:\ */ Melder_getDesktop (parent); /* empty string */ } else if (backslash - colon == 1) { /* C:\WINDOWS */ * (backslash + 1) = '\0'; /* C:\ */ } else { /* C:\WINDOWS\FONTS */ *backslash = '\0'; /* C:\WINDOWS */ } } else { /* LPT1: ??? */ Melder_getDesktop (parent); /* empty string */ } } else if (parent -> path [0] == '\\' && parent -> path [1] == '\\') { int length = wcslen (parent -> path); wchar_t *backslash = wcsrchr (parent -> path + 2, '\\'); if (backslash) { /* \\Swine\Apps\Praats or \\Swine\Apps or \\Swine\ */ if (backslash - parent -> path == length - 1) { /* \\Swine\ */ Melder_getDesktop (parent); /* empty string */ } else { /* \\Swine\Apps\Praats or \\Swine\Apps */ wchar_t *leftBackslash = wcschr (parent -> path + 2, '\\'); if (backslash - leftBackslash == 0) { /* \\Swine\Apps */ * (backslash + 1) = '\0'; /* \\Swine\ */ } else { /* \\Swine\Apps\Praats */ *backslash = '\0'; /* \\Swine\Apps */ } } } else { /* \\Swine ??? */ Melder_getDesktop (parent); /* empty string */ } } else { /* Unknown path type. */ Melder_getDesktop (parent); /* empty string */ } #endif } bool MelderDir_isDesktop (MelderDir dir) { return dir -> path [0] == '\0'; } void MelderDir_getSubdir (MelderDir parent, const wchar *subdirName, MelderDir subdir) { #if defined (UNIX) if (parent -> path [0] == '/' && parent -> path [1] == '\0') { swprintf (subdir -> path, kMelder_MAXPATH+1, L"/%ls", subdirName); } else { swprintf (subdir -> path, kMelder_MAXPATH+1, L"%ls/%ls", parent -> path, subdirName); } #elif defined (_WIN32) int length = wcslen (parent -> path); wchar_t *backslash = wcsrchr (parent -> path, '\\'); if (backslash && backslash - parent -> path == length - 1) { /* C:\ or \\Swine\ */ swprintf (subdir -> path, kMelder_MAXPATH+1, L"%ls%ls", parent -> path, subdirName); } else { /* C:\WINDOWS or \\Swine\Apps or even C: */ swprintf (subdir -> path, kMelder_MAXPATH+1, L"%ls\\%ls", parent -> path, subdirName); } #endif } void Melder_getHomeDir (MelderDir homeDir) { #if defined (UNIX) char *home = getenv ("HOME"); wcscpy (homeDir -> path, home ? Melder_peekUtf8ToWcs (home) : L"/"); #elif defined (_WIN32) if (GetEnvironmentVariable (L"USERPROFILE", homeDir -> path, kMelder_MAXPATH)) { ; /* Ready. */ } else if (GetEnvironmentVariableW (L"HOMEDRIVE", homeDir -> path, kMelder_MAXPATH)) { GetEnvironmentVariable (L"HOMEPATH", homeDir -> path + wcslen (homeDir -> path), kMelder_MAXPATH - wcslen (homeDir -> path)); } else { MelderDir_setToNull (homeDir); /* Windows 95 and 98: alas. */ } #endif } void Melder_getPrefDir (MelderDir prefDir) { #if defined (macintosh) FSRef macFileReference; FSFindFolder (kOnSystemDisk, kPreferencesFolderType, kCreateFolder, & macFileReference); Melder_machToDir (& macFileReference, prefDir); #elif defined (UNIX) /* * Preferences files go into the home directory. */ Melder_getHomeDir (prefDir); #elif defined (_WIN32) /* * On shared systems (NT, 2000, XP), preferences files go into the home directory. * Otherwise (Windows 95 and 98), they go into the Windows directory. */ Melder_getHomeDir (prefDir); if (MelderDir_isNull (prefDir)) { GetWindowsDirectoryW (prefDir -> path, kMelder_MAXPATH); } #endif } void Melder_getTempDir (MelderDir tempDir) { #if defined (macintosh) FSRef macFileReference; FSFindFolder (kOnSystemDisk, kTemporaryFolderType, kCreateFolder, & macFileReference); Melder_machToDir (& macFileReference, tempDir); #else (void) tempDir; #endif } #if defined (macintosh) static long textCreator = 'PpgB'; void MelderFile_setMacTypeAndCreator (MelderFile file, long fileType, long creator) { if (wcsequ (file -> path, L"")) return; OSStatus err; FSRef fsref; FSCatalogInfo info; Melder_fileToMach (file, & fsref); err = FSGetCatalogInfo (& fsref, kFSCatInfoFinderInfo, & info, NULL, NULL, NULL); if (err == noErr) { ((FInfo *) & info. finderInfo) -> fdType = fileType; ((FInfo *) & info. finderInfo) -> fdCreator = creator ? creator : textCreator; FSSetCatalogInfo (& fsref, kFSCatInfoFinderInfo, & info); } } unsigned long MelderFile_getMacType (MelderFile file) { OSStatus err; FSRef fsref; FSCatalogInfo info; Melder_fileToMach (file, & fsref); err = FSGetCatalogInfo (& fsref, kFSCatInfoFinderInfo, & info, NULL, NULL, NULL); if (err == noErr) { return ((FInfo *) & info. finderInfo) -> fdType; } return 0; } #endif #ifdef CURLPRESENT static int curl_initialized = 0; static size_t write_URL_data_to_file (void *buffer, size_t size, size_t nmemb, void *userp) { return fwrite (buffer, size, nmemb, userp); } static size_t read_URL_data_from_file (void *buffer, size_t size, size_t nmemb, void *userp) { return fread (buffer, size, nmemb, userp); } #endif FILE * Melder_fopen (MelderFile file, const char *type) { /* * On the Unix-like systems (including MacOS), the path has to be converted to 8-bit characters in UTF-8 encoding. * On MacOS, the characters also have to be decomposed. */ char utf8path [kMelder_MAXPATH+1]; Melder_wcsTo8bitFileRepresentation_inline (file -> path, utf8path); FILE *f; file -> openForWriting = type [0] == 'w' || type [0] == 'a' || strchr (type, '+'); if (wcsequ (file -> path, L"") && file -> openForWriting) { f = stdout; #ifdef CURLPRESENT } else if (strstr (utf8path, "://") && file -> openForWriting) { Melder_assert (type [0] == 'w'); /* Reject "append" and "random" access. */ f = tmpfile (); /* Open a temporary file for writing. */ } else if (strstr (utf8path, "://") && ! file -> openForWriting) { CURLcode CURLreturn; CURL *CURLhandle; char errorbuffer [CURL_ERROR_SIZE] = ""; f = tmpfile (); /* Open a temporary file for writing. */ if (! curl_initialized) { CURLreturn = curl_global_init (CURL_GLOBAL_ALL); curl_initialized = 1; }; CURLhandle = curl_easy_init (); /* Initialize session. */ /* * Set up the connection parameters. */ /* Debugging: Verbose messages */ /* CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_VERBOSE, 1); */ /* Do not fail on error. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_FAILONERROR, 0); /* Store error messages in a buffer. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_ERRORBUFFER, errorbuffer); /* The file stream to store the URL. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_FILE, f); /* The function to write to the file, necessary for Win32. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_WRITEFUNCTION, write_URL_data_to_file); /* The actual URL to handle. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_URL, utf8path); /* Get the URL and write it to the given file. */ CURLreturn = curl_easy_perform (CURLhandle); /* Handle errors. */ if (CURLreturn) { Melder_error ("%s\n", errorbuffer); f = NULL; }; /* Clean up session. */ curl_easy_cleanup (CURLhandle); /* Do something with the file. Why? */ if (f) rewind (f); #endif } else { #ifdef _WIN32 f = _wfopen (file -> path, Melder_peekUtf8ToWcs (type)); #else f = fopen ((char *) utf8path, type); #endif } if (! f) { wchar_t *path = file -> path; Melder_error_ ("Cannot ", type [0] == 'r' ? "open" : type [0] == 'a' ? "append to" : "create", " file ", file, "."); if (path [0] == '\0') Melder_error_ ("Hint: empty file name."); else if (path [0] == ' ' || path [0] == '\t') Melder_error_ ("Hint: file name starts with a space or tab."); else if (path [wcslen (path) - 1] == ' ' || path [wcslen (path) - 1] == '\t') Melder_error_ ("Hint: file name ends in a space or tab."); else if (wcschr (path, '\n')) Melder_error_ ("Hint: file name contains a newline symbol."); throw MelderError (); return NULL; } return f; } void Melder_fclose (MelderFile file, FILE *f) { if (! f) return; #if defined (CURLPRESENT) if (wcsstr (file -> wpath, L"://") && file -> openForWriting) { unsigned char utf8path [kMelder_MAXPATH+1]; Melder_wcsTo8bitFileRepresentation_inline (file -> path, utf8path); /* Rewind the file. */ if (f) rewind (f); CURLcode CURLreturn; CURL *CURLhandle; char errorbuffer [CURL_ERROR_SIZE] = ""; /* Start global init (necessary only ONCE). */ if (! curl_initialized) { CURLreturn = curl_global_init (CURL_GLOBAL_ALL); curl_initialized = 1; }; CURLhandle = curl_easy_init (); /* Initialize session. */ /* * Set up the connection parameters. */ /* Debugging: Verbose messages */ /* CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_VERBOSE, 1); */ /* Catch FILE: protocol errors. No solution yet */ if (wcsstr (file -> path, L"file://") || wcsstr (file -> path, L"FILE://")) { CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_VERBOSE, 1); } /* Do not return Error pages, just fail. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_FAILONERROR, 1); /* Store error messages in a buffer. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_ERRORBUFFER, errorbuffer); /* Send header. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_HEADER, 1); /* Upload. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_UPLOAD, 1); /* The actual URL to handle. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_URL, utf8path); /* The function to write to the peer, necessary for Win32. */ CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_READFUNCTION, read_URL_data_from_file); CURLreturn = curl_easy_setopt (CURLhandle, CURLOPT_READDATA, f); /* Get the URL and write the file to it. */ CURLreturn = curl_easy_perform (CURLhandle); /* Handle errors. */ if (CURLreturn) { curl_easy_cleanup (CURLhandle); f = NULL; Melder_throw (errorbuffer, "\n"); }; /* Clean up session */ curl_easy_cleanup (CURLhandle); } #endif if (f != stdout && fclose (f) == EOF) Melder_throw ("Error closing file ", file, "."); } void Melder_files_cleanUp (void) { #if defined (CURLPRESENT) if (curl_initialized) { curl_global_cleanup (); curl_initialized = 0; }; #endif } bool MelderFile_exists (MelderFile file) { #if defined (UNIX) char utf8path [kMelder_MAXPATH+1]; Melder_wcsTo8bitFileRepresentation_inline (file -> path, utf8path); struct stat statistics; return ! stat (utf8path, & statistics); #else try { autofile f = Melder_fopen (file, "rb"); f.close (file); return true; } catch (MelderError) { Melder_clearError (); return false; } #endif } bool MelderFile_readable (MelderFile file) { try { autofile f = Melder_fopen (file, "rb"); f.close (file); return true; } catch (MelderError) { Melder_clearError (); return false; } } long MelderFile_length (MelderFile file) { #if defined (UNIX) char utf8path [kMelder_MAXPATH+1]; Melder_wcsTo8bitFileRepresentation_inline (file -> path, utf8path); struct stat statistics; if (stat ((char *) utf8path, & statistics)) return -1; return statistics. st_size; #else try { autofile f = Melder_fopen (file, "r"); fseek (f, 0, SEEK_END); long length = ftell (f); f.close (file); return length; } catch (MelderError) { Melder_clearError (); return -1; } #endif } void MelderFile_delete (MelderFile file) { if (! file) return; #if defined (_WIN32) DeleteFile (file -> path); #else char utf8path [kMelder_MAXPATH+1]; Melder_wcsTo8bitFileRepresentation_inline (file -> path, utf8path); remove ((char *) utf8path); #endif } wchar * Melder_peekExpandBackslashes (const wchar *message) { static wchar names [11] [kMelder_MAXPATH+1]; static int index = 0; const wchar *from; wchar_t *to; if (++ index == 11) index = 0; for (from = & message [0], to = & names [index] [0]; *from != '\0'; from ++, to ++) { *to = *from; if (*from == '\\') { * ++ to = 'b'; * ++ to = 's'; } } *to = '\0'; return & names [index] [0]; } const wchar * MelderFile_messageName (MelderFile file) { return Melder_wcscat (L_LEFT_DOUBLE_QUOTE, file -> path, L_RIGHT_DOUBLE_QUOTE); } void Melder_getDefaultDir (MelderDir dir) { #if defined (_WIN32) GetCurrentDirectory (kMelder_MAXPATH, dir -> path); #else char path [kMelder_MAXPATH+1]; getcwd (path, kMelder_MAXPATH+1); Melder_8bitFileRepresentationToWcs_inline (path, dir -> path); #endif } void Melder_setDefaultDir (MelderDir dir) { #if defined (_WIN32) SetCurrentDirectory (dir -> path); #else chdir (Melder_peekWcsToUtf8 (dir -> path)); #endif } void MelderFile_setDefaultDir (MelderFile file) { structMelderDir dir = { { 0 } }; MelderFile_getParentDir (file, & dir); Melder_setDefaultDir (& dir); } void Melder_createDirectory (MelderDir parent, const wchar_t *dirName, int mode) { #if defined (_WIN32) structMelderFile file = { 0 }; SECURITY_ATTRIBUTES sa; (void) mode; sa. nLength = sizeof (SECURITY_ATTRIBUTES); sa. lpSecurityDescriptor = NULL; sa. bInheritHandle = FALSE; if (wcschr (dirName, ':') || dirName [0] == '/' && dirName [1] == '/') { swprintf (file. path, kMelder_MAXPATH+1, L"%ls", dirName); // absolute path } else { swprintf (file. path, kMelder_MAXPATH+1, L"%ls/%ls", parent -> path, dirName); // relative path } if (! CreateDirectoryW (file. path, & sa) && GetLastError () != ERROR_ALREADY_EXISTS) // ignore if directory already exists Melder_throw ("Cannot create directory ", & file, "."); #else structMelderFile file = { 0 }; if (dirName [0] == '/') { swprintf (file. path, kMelder_MAXPATH+1, L"%ls", dirName); // absolute path } else if (parent -> path [0] == '/' && parent -> path [1] == '\0') { swprintf (file. path, kMelder_MAXPATH+1, L"/%ls", dirName); // relative path in root directory } else { swprintf (file. path, kMelder_MAXPATH+1, L"%ls/%ls", parent -> path, dirName); // relative path } char utf8path [kMelder_MAXPATH+1]; Melder_wcsTo8bitFileRepresentation_inline (file. path, utf8path); if (mkdir (utf8path, mode) == -1 && errno != EEXIST) // ignore if directory already exists Melder_throw ("Cannot create directory ", & file, "."); #endif } /* * Routines for wrapping the file pointers. */ #define my me -> MelderFile MelderFile_open (MelderFile me) { my filePointer = Melder_fopen (me, "rb"); my openForReading = true; return me; } char * MelderFile_readLine (MelderFile me) { long i; static char *buffer; static long capacity; if (! my filePointer) return NULL; if (feof (my filePointer)) return NULL; if (! buffer) { buffer = Melder_malloc (char, capacity = 100); } for (i = 0; 1; i ++) { if (i >= capacity) { buffer = (char *) Melder_realloc (buffer, capacity *= 2); } int c = fgetc (my filePointer); if (feof (my filePointer)) break; if (c == '\n') { c = fgetc (my filePointer); if (feof (my filePointer)) break; /* Ignore last empty line (Unix). */ ungetc (c, my filePointer); break; /* Unix line separator. */ } if (c == '\r') { c = fgetc (my filePointer); if (feof (my filePointer)) break; /* Ignore last empty line (Macintosh). */ if (c == '\n') { c = fgetc (my filePointer); if (feof (my filePointer)) break; /* Ignore last empty line (Windows). */ ungetc (c, my filePointer); break; /* Windows line separator. */ } ungetc (c, my filePointer); break; /* Macintosh line separator. */ } buffer [i] = c; } buffer [i] = '\0'; return buffer; } MelderFile MelderFile_create (MelderFile me, const wchar_t *macType, const wchar_t *macCreator, const wchar_t *winExtension) { my filePointer = Melder_fopen (me, "wb"); my openForWriting = true; // A bit superfluous (will have been set by Melder_fopen). if (my filePointer == stdout) return me; #if defined (macintosh) (void) winExtension; { unsigned long macType_int = macType == NULL || macType [0] == '\0' ? 0 : ((unsigned int) macType [0] << 24) | ((unsigned int) macType [1] << 16) | ((unsigned int) macType [2] << 8) | (unsigned int) macType [3]; unsigned long macCreator_int = macCreator == NULL || macCreator [0] == '\0' ? 0 : ((unsigned int) macCreator [0] << 24) | ((unsigned int) macCreator [1] << 16) | ((unsigned int) macCreator [2] << 8) | (unsigned int) macCreator [3]; MelderFile_setMacTypeAndCreator (me, macType_int, macCreator_int); } #elif defined (_WIN32) (void) macType; (void) macCreator; (void) winExtension; /* BUG */ #else (void) macType; (void) macCreator; (void) winExtension; #endif return me; } void MelderFile_seek (MelderFile me, long position, int direction) { if (! my filePointer) return; if (fseek (my filePointer, position, direction)) { fclose (my filePointer); my filePointer = NULL; Melder_throw ("Cannot seek in file ", me, "."); } } long MelderFile_tell (MelderFile me) { long result = 0; if (! my filePointer) return 0; if ((result = ftell (my filePointer)) == -1) { fclose (my filePointer); my filePointer = NULL; Melder_throw ("Cannot tell in file ", me, "."); } return result; } void MelderFile_rewind (MelderFile me) { if (! my filePointer) return; rewind (my filePointer); } static void _MelderFile_close (MelderFile me, bool mayThrow) { if (my outputEncoding == kMelder_textOutputEncoding_FLAC) { if (my flacEncoder) { FLAC__stream_encoder_finish (my flacEncoder); // This already calls fclose! BUG: we cannot get any error messages out. FLAC__stream_encoder_delete (my flacEncoder); } } else if (my filePointer != NULL) { if (mayThrow) { Melder_fclose (me, my filePointer); } else { fclose (my filePointer); } } /* Set everything to zero, except paths (they stay around for error messages and the like). */ my filePointer = NULL; my openForWriting = my openForReading = false; my indent = 0; my flacEncoder = NULL; } void MelderFile_close (MelderFile me) { _MelderFile_close (me, true); } void MelderFile_close_nothrow (MelderFile me) { _MelderFile_close (me, false); } /* End of file melder_files.cpp */ sources_5316/sys/oo_WRITE_BINARY.h0000644000176700017670000000745311724670615015367 0ustar paulpaul/* oo_WRITE_BINARY.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) \ binput##storage (x, f); #define oo_ARRAY(type,storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ binput##storage (x [i], f); #define oo_SET(type,storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ binput##storage (x [i], f); #define oo_VECTOR(type,storage,x,min,max) \ if (x) \ NUMvector_writeBinary_##storage (x, min, max, f); #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) \ if (x) \ NUMmatrix_writeBinary_##storage (x, row1, row2, col1, col2, f); #define oo_ENUMx(type,storage,Type,x) \ binput##storage (x, f); #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) \ for (int i = 0; i < n; i ++) \ binput##storage (x [i], f); #define oo_ENUMx_SET(type,storage,Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ binput##storage (x [i], f); #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) \ if (x) \ NUMvector_writeBinary_##storage (x, min, max, f); #define oo_STRINGx(storage,x) \ binput##storage (x, f); #define oo_STRINGx_ARRAY(storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ binput##storage (x [i], f); #define oo_STRINGx_SET(storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ binput##storage (x [i], f); #define oo_STRINGx_VECTOR(storage,x,min,max) \ if (max >= min) \ for (long i = min; i <= max; i ++) \ binput##storage (x [i], f); #define oo_STRUCT(Type,x) \ x. writeBinary (f); #define oo_STRUCT_ARRAY(Type,x,cap,n) \ for (int i = 0; i < n; i ++) \ x [i]. writeBinary (f); #define oo_STRUCT_SET(Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ x [i]. writeBinary (f); #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ if (max >= min) \ for (long i = min; i <= max; i ++) \ x [i]. writeBinary (f); #define oo_OBJECT(Class,version,x) \ binputex (x != NULL, f); \ if (x) \ Data_writeBinary (x, f); #define oo_COLLECTION(Class,x,ItemClass,version) \ binputi4 (x ? x -> size : 0, f); \ if (x) { \ for (long i = 1; i <= x -> size; i ++) { \ ItemClass data = (ItemClass) x -> item [i]; \ data -> struct##ItemClass :: v_writeBinary (f); \ } \ } #define oo_FILE(x) #define oo_DIR(x) #define oo_DEFINE_STRUCT(Type) \ void struct##Type :: writeBinary (FILE *f) { #define oo_END_STRUCT(Type) \ } #define oo_DEFINE_CLASS(Class,Parent) \ void struct##Class :: v_writeBinary (FILE *f) { \ Class##_Parent :: v_writeBinary (f); #define oo_END_CLASS(Class) \ } #define oo_IF(condition) \ if (condition) { #define oo_ENDIF \ } #define oo_FROM(from) #define oo_ENDFROM #define oo_VERSION(version) #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 0 #define oo_READING 0 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 1 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 1 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_WRITE_BINARY.h */ sources_5316/sys/Manual.h0000644000176700017670000000402011717711307014130 0ustar paulpaul#ifndef _Manual_h_ #define _Manual_h_ /* Manual.h * * Copyright (C) 1996-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "HyperPage.h" #include "ManPages.h" Thing_define (Manual, HyperPage) { // new data: public: long path, numberOfParagraphs; struct structManPage_Paragraph *paragraphs; GuiObject searchText; GuiObject homeButton, recordButton, playButton, publishButton; int numberOfMatches; long matches [1 + 20], fromPage, toPage; int suppressLinksHither; wchar *printPagesStartingWith; // overridden methods: virtual bool v_scriptable () { return false; } virtual void v_createChildren (); virtual void v_createMenus (); virtual bool v_hasQueryMenu () { return false; } virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_draw (); virtual void v_defaultHeaders (EditorCommand cmd); virtual long v_getNumberOfPages (); virtual long v_getCurrentPageNumber (); virtual int v_goToPage (const wchar *title); virtual void v_goToPage_i (long pageNumber); virtual bool v_hasHistory () { return true; } virtual bool v_isOrdered () { return true; } }; void Manual_init (Manual me, GuiObject parent, const wchar *title, Data data, bool ownData); Manual Manual_create (GuiObject parent, const wchar *title, Data data, bool ownData); void Manual_search (Manual me, const wchar *query); /* End of file Manual.h */ #endif sources_5316/sys/oo_WRITE_TEXT.h0000644000176700017670000001335611724667175015175 0ustar paulpaul/* oo_WRITE_TEXT.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) \ texput##storage (file, x, L"" #x, 0,0,0,0,0); #define oo_ARRAY(type,storage,x,cap,n) \ texputintro (file, L"" #x " []: ", n ? NULL : L"(empty)", 0,0,0,0); \ for (int i = 0; i < n; i ++) \ texput##storage (file, x [i], L"" #x " [", Melder_integer (i), L"]", 0,0,0); \ texexdent (file); #define oo_SET(type,storage,x,setType) \ texputintro (file, L"" #x " []:", 0,0,0,0,0); \ for (int i = 0; i <= setType##_MAX; i ++) \ texput##storage (file, x [i], L"" #x " [", setType##_getText (i), L"]", 0,0,0); \ texexdent (file); #define oo_VECTOR(type,storage,x,min,max) \ if (x) \ NUMvector_writeText_##storage (x, min, max, file, L"" #x); #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) \ if (x) \ NUMmatrix_writeText_##storage (x, row1, row2, col1, col2, file, L"" #x); #define oo_ENUMx(type,storage,Type,x) \ texput##storage (file, x, Type##_getText, L"" #x, 0,0,0,0,0); #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) \ texputintro (file, L"" #x " []:", 0,0,0,0,0); \ for (int i = 0; i < n; i ++) \ texput##storage (file, x [i], Type##_getText, L"" #x " [", Melder_integer (i), L"]", 0,0,0); \ texexdent (file); #define oo_ENUMx_SET(type,storage,Type,x,setType) \ texputintro (file, L"" #x " []: ", n ? NULL : L"(empty)", 0,0,0,0); \ for (int i = 0; i <= setType##_MAX; i ++) \ texput##storage (file, x [i], Type##_getText, L"" #x " [", setType##_getText (i), L"]", 0,0,0); \ texexdent (file); #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) \ texputintro (file, L"" #x " []: ", max >= min ? NULL : L"(empty)", 0,0,0,0); \ for (long i = min; i <= max; i ++) \ texput##storage (file, x [i], Type##_getText, L"" #x " [", Melder_integer (i), L"]", 0,0,0); \ texexdent (file); #define oo_STRINGx(storage,x) \ texput##storage (file, x, L""#x, 0,0,0,0,0); #define oo_STRINGx_ARRAY(storage,x,cap,n) \ texputintro (file, L"" #x " []: ", n ? NULL : L"(empty)", 0,0,0,0); \ for (int i = 0; i < n; i ++) \ texput##storage (file, x [i], L"" #x " [", Melder_integer (i), L"]", 0,0,0); \ texexdent (file); #define oo_STRINGx_SET(storage,x,setType) \ texputintro (file, L"" #x " []:", 0,0,0,0,0); \ for (int i = 0; i <= setType##_MAX; i ++) \ texput##storage (file, x [i], L"" #x " [", setType##_getText (i), L"]", 0,0,0); \ texexdent (file); #define oo_STRINGx_VECTOR(storage,x,min,max) \ texputintro (file, L"" #x " []: ", max >= min ? NULL : L"(empty)", 0,0,0,0); \ for (long i = min; i <= max; i ++) \ texput##storage (file, x [i], L"" #x " [", Melder_integer (i), L"]", 0,0,0); \ texexdent (file); #define oo_STRUCT(Type,x) \ texputintro (file, L"" #x ":", 0,0,0,0,0); \ x. writeText (file); \ texexdent (file); #define oo_STRUCT_ARRAY(Type,x,cap,n) \ texputintro (file, L"" #x " []: ", n ? NULL : L"(empty)", 0,0,0,0); \ for (int i = 0; i < n; i ++) { \ texputintro (file, L"" #x " [", Melder_integer (i), L"]:", 0,0,0); \ x [i]. writeText (file); \ texexdent (file); \ } \ texexdent (file); #define oo_STRUCT_SET(Type,x,setType) \ texputintro (file, L"" #x " []:", 0,0,0,0,0); \ for (int i = 0; i <= setType##_MAX; i ++) { \ texputintro (file, L"" #x " [", setType##_getText (i), L"]:", 0,0,0); \ x [i]. writeText (file); \ texexdent (file); \ } \ texexdent (file); #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ texputintro (file, L"" #x " []: ", max >= min ? NULL : L"(empty)", 0,0,0,0); \ for (long i = min; i <= max; i ++) { \ texputintro (file, L"" #x " [", Melder_integer (i), L"]:", 0,0,0); \ x [i]. writeText (file); \ texexdent (file); \ } \ texexdent (file); #define oo_OBJECT(Class,version,x) \ texputex (file, x != NULL, L"" #x, 0,0,0,0,0); \ if (x) \ Data_writeText (x, file); #define oo_COLLECTION(Class,x,ItemClass,version) \ texputi4 (file, x ? x -> size : 0, L"" #x ": size", 0,0,0,0,0); \ if (x) { \ for (long i = 1; i <= x -> size; i ++) { \ ItemClass data = (ItemClass) x -> item [i]; \ texputintro (file, L"" #x " [", Melder_integer (i), L"]:", 0,0,0); \ data -> struct##ItemClass :: v_writeText (file); \ texexdent (file); \ } \ } #define oo_FILE(x) #define oo_DIR(x) #define oo_DEFINE_STRUCT(Type) \ void struct##Type :: writeText (MelderFile file) { #define oo_END_STRUCT(Type) \ } #define oo_DEFINE_CLASS(Class,Parent) \ void struct##Class :: v_writeText (MelderFile file) { \ Class##_Parent :: v_writeText (file); #define oo_END_CLASS(Class) \ } #define oo_FROM(from) #define oo_ENDFROM #define oo_VERSION(version) #define oo_IF(condition) if (condition) { #define oo_ENDIF } #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 0 #define oo_READING 0 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 1 #define oo_WRITING_TEXT 1 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_WRITE_TEXT.h */ sources_5316/sys/EditorM.h0000644000176700017670000001311011662423034014252 0ustar paulpaul#ifndef _EditorM_h_ #define _EditorM_h_ /* EditorM.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #undef FORM #undef REAL #undef REAL_OR_UNDEFINED #undef POSITIVE #undef INTEGER #undef NATURAL #undef WORD #undef SENTENCE #undef COLOUR #undef CHANNEL #undef BOOLEAN #undef LABEL #undef TEXTFIELD #undef RADIO #undef RADIOBUTTON #undef OPTIONMENU #undef OPTION #undef RADIOBUTTONS_ENUM #undef OPTIONS_ENUM #undef RADIO_ENUM #undef OPTIONMENU_ENUM #undef LIST #undef OK #undef SET_REAL #undef SET_INTEGER #undef SET_STRING #undef DO #undef END #undef DIRECT #undef FORM_WRITE #undef DO_WRITE #undef GET_REAL #undef GET_INTEGER #undef GET_STRING #undef GET_FILE #define REAL(label,def) UiForm_addReal (cmd -> d_uiform, label, def); #define REAL_OR_UNDEFINED(label,def) UiForm_addRealOrUndefined (cmd -> d_uiform, label, def); #define POSITIVE(label,def) UiForm_addPositive (cmd -> d_uiform, label, def); #define INTEGER(label,def) UiForm_addInteger (cmd -> d_uiform, label, def); #define NATURAL(label,def) UiForm_addNatural (cmd -> d_uiform, label, def); #define WORD(label,def) UiForm_addWord (cmd -> d_uiform, label, def); #define SENTENCE(label,def) UiForm_addSentence (cmd -> d_uiform, label, def); #define COLOUR(label,def) UiForm_addColour (cmd -> d_uiform, label, def); #define CHANNEL(label,def) UiForm_addChannel (cmd -> d_uiform, label, def); #define BOOLEAN(label,def) UiForm_addBoolean (cmd -> d_uiform, label, def); #define LABEL(name,label) UiForm_addLabel (cmd -> d_uiform, name, label); #define TEXTFIELD(name,def) UiForm_addText (cmd -> d_uiform, name, def); #define RADIO(label,def) radio = UiForm_addRadio (cmd -> d_uiform, label, def); #define RADIOBUTTON(label) UiRadio_addButton (radio, label); #define OPTIONMENU(label,def) radio = UiForm_addOptionMenu (cmd -> d_uiform, label, def); #define OPTION(label) UiOptionMenu_addButton (radio, label); #define RADIOBUTTONS_ENUM(labelProc,min,max) { for (int itext = min; itext <= max; itext ++) RADIOBUTTON (labelProc) } #define OPTIONS_ENUM(labelProc,min,max) { for (int itext = min; itext <= max; itext ++) OPTION (labelProc) } #define RADIO_ENUM(label,enum,def) \ RADIO (label, enum##_##def - enum##_MIN + 1) \ for (int ienum = enum##_MIN; ienum <= enum##_MAX; ienum ++) \ OPTION (enum##_getText (ienum)) #define OPTIONMENU_ENUM(label,enum,def) \ OPTIONMENU (label, enum##_##def - enum##_MIN + 1) \ for (int ienum = enum##_MIN; ienum <= enum##_MAX; ienum ++) \ OPTION (enum##_getText (ienum)) #define LIST(label,n,str,def) UiForm_addList (cmd -> d_uiform, label, n, str, def); #define SET_REAL(name,value) UiForm_setReal (cmd -> d_uiform, name, value); #define SET_INTEGER(name,value) UiForm_setInteger (cmd -> d_uiform, name, value); #define SET_STRING(name,value) UiForm_setString (cmd -> d_uiform, name, value); #define SET_ENUM(name,enum,value) SET_STRING (name, enum##_getText (value)) #define DIALOG cmd -> d_uiform #define EDITOR_ARGS Editor void_me, EditorCommand cmd, UiForm sendingForm, const wchar *sendingString, Interpreter interpreter #define EDITOR_IAM(klas) iam (klas); (void) me; (void) cmd; (void) sendingForm; (void) sendingString; (void) interpreter #define EDITOR_FORM(title,helpTitle) if (cmd -> d_uiform == NULL) { Any radio = 0; (void) radio; \ cmd -> d_uiform = UiForm_createE (cmd, title, cmd -> itemTitle, helpTitle); #define EDITOR_OK UiForm_finish (cmd -> d_uiform); } if (sendingForm == NULL && sendingString == NULL) { #define EDITOR_DO UiForm_do (cmd -> d_uiform, false); } else if (sendingForm == NULL) { \ UiForm_parseStringE (cmd, sendingString, interpreter); } else { #define EDITOR_END } #define EDITOR_FORM_WRITE(title,helpTitle) \ if (cmd -> d_uiform == NULL) { \ cmd -> d_uiform = UiOutfile_createE (cmd, title, cmd -> itemTitle, helpTitle); \ } if (sendingForm == NULL && sendingString == NULL) { wchar defaultName [300]; defaultName [0] = '\0'; #define EDITOR_DO_WRITE \ UiOutfile_do (cmd -> d_uiform, defaultName); } else { MelderFile file; structMelderFile file2 = { 0 }; \ if (sendingString == NULL) file = UiFile_getFile (sendingForm); \ else { Melder_relativePathToFile (sendingString, & file2); file = & file2; } #define EDITOR_FORM_READ(title,helpTitle) \ if (cmd -> d_uiform == NULL) { \ cmd -> d_uiform = UiInfile_createE (cmd, title, cmd -> itemTitle, helpTitle); \ } if (sendingForm == NULL && sendingString == NULL) { #define EDITOR_DO_READ \ UiInfile_do (cmd -> d_uiform); } else { MelderFile file; structMelderFile file2 = { 0 }; \ if (sendingString == NULL) file = UiFile_getFile (sendingForm); \ else { Melder_relativePathToFile (sendingString, & file2); file = & file2; } #define GET_REAL(name) UiForm_getReal (cmd -> d_uiform, name) #define GET_INTEGER(name) UiForm_getInteger (cmd -> d_uiform, name) #define GET_STRING(name) UiForm_getString (cmd -> d_uiform, name) #define GET_ENUM(enum,name) (enum) enum##_getValue (GET_STRING (name)) #define GET_FILE UiForm_getFile (cmd -> d_uiform) /* End of file EditorM.h */ #endif sources_5316/sys/sendpraat.c0000644000176700017670000005537411753734373014721 0ustar paulpaul/* sendpraat.c */ /* by Paul Boersma */ /* 6 September 2011 */ /* * The sendpraat subroutine (Unix with X11 or GTK; Windows; Macintosh) sends a message * to a running program that uses the Praat shell. * The sendpraat program does the same from a Unix command shell, * from a Windows or DOS console, or from a MacOS X terminal window. * * Newer versions of sendpraat may be found at http://www.praat.org or http://www.fon.hum.uva.nl/praat/sendpraat.html * * On Windows NT, 2000, and XP, this version works only with Praat version 4.3.28 (November 2005) or newer. * On Macintosh, this version works only with Praat version 3.8.75 (October 2000) or newer. * On Unix with GTK, this version works only with Praat version 5.1.33 (May 2010) or newer. * Newer versions of Praat may respond faster or more reliably. */ /******************************************************************* THIS CODE CAN BE COPIED, USED, AND DISTRIBUTED FREELY. IF YOU MODIFY IT, PLEASE KEEP MY NAME AND MARK THE CHANGES. IF YOU IMPROVE IT, PLEASE NOTIFY ME AT paul.boersma@uva.nl. *******************************************************************/ #if defined (_WIN32) #include #include #include #ifdef __MINGW32__ #define swprintf _snwprintf #endif #define gtk 0 #define win 1 #define mac 0 #elif defined (macintosh) || defined (__MACH__) #include #include #include #include #include #include #include #include #ifdef __MACH__ #include #endif #include #define gtk 0 #define win 0 #define mac 1 #elif defined (UNIX) #include #include #include #include #include #include #include #include #include #define gtk 1 #define win 0 #define mac 0 #endif /* * The way to call the sendpraat subroutine from another program. */ char *sendpraat (void *display, const char *programName, long timeOut, const char *text); wchar_t *sendpraatW (void *display, const wchar_t *programName, long timeOut, const wchar_t *text); /* * Parameters: * 'display' is the Display or GdKDisplay pointer, which will be available if you call sendpraat from an X11 or GTK program. * If 'display' is NULL, sendpraat will open the display by itself, and close it after use. * On Windows and Macintosh, sendpraat ignores the 'display' parameter. * 'programName' is the name of the program that receives the message. * This program must have been built with the Praat shell (the most common such programs are Praat and ALS). * On Unix, the program name is usually all lower case, e.g. "praat" or "als", or the name of any other program. * On Windows, you can use either "Praat", "praat", or the name of any other program. * On Macintosh, 'programName' must be "Praat", "praat", "ALS", or the Macintosh signature of any other program. * 'timeOut' is the time (in seconds) after which sendpraat will return with a time-out error message * if the receiving program sends no notification of completion. * On Unix and Macintosh, the message is sent asynchronously if 'timeOut' is 0; * this means that sendpraat will return OK (NULL) without waiting for the receiving program * to handle the message. * On Windows, the time out is ignored. * 'text' contains the contents of the Praat script to be sent to the receiving program. */ static char errorMessage [1000]; static wchar_t errorMessageW [1000]; #if gtk static long theTimeOut; static void handleCompletion (int message) { (void) message; } static void handleTimeOut (int message) { (void) message; sprintf (errorMessage, "Timed out after %ld seconds.", theTimeOut); } #endif char *sendpraat (void *display, const char *programName, long timeOut, const char *text) { char nativeProgramName [100]; #if gtk char *home, pidFileName [256], messageFileName [256]; FILE *pidFile; long pid, wid = 0; #elif win char homeDirectory [256], messageFileName [256], windowName [256]; HWND window; (void) display; (void) timeOut; #elif mac AEDesc programDescriptor; AppleEvent event, reply; OSErr err; UInt32 signature; (void) display; #endif /* * Clean up from an earlier call. */ errorMessage [0] = '\0'; /* * Handle case differences. */ strcpy (nativeProgramName, programName); #if gtk nativeProgramName [0] = tolower (nativeProgramName [0]); #else nativeProgramName [0] = toupper (nativeProgramName [0]); #endif /* * If the text is going to be sent in a file, create its name. * The file is going to be written into the preferences directory of the receiving program. * On Unix, the name will be something like /home/jane/.praat-dir/message. * On Windows, the name will be something like C:\Documents and Settings\Jane\Praat\Message.txt, * or C:\Windows\Praat\Message.txt on older systems. * On Macintosh, the text is NOT going to be sent in a file. */ #if gtk if ((home = getenv ("HOME")) == NULL) { sprintf (errorMessage, "HOME environment variable not set."); return errorMessage; } sprintf (messageFileName, "%s/.%s-dir/message", home, programName); #elif win if (GetEnvironmentVariableA ("USERPROFILE", homeDirectory, 255)) { ; /* Ready. */ } else if (GetEnvironmentVariableA ("HOMEDRIVE", homeDirectory, 255)) { GetEnvironmentVariableA ("HOMEPATH", homeDirectory + strlen (homeDirectory), 255); } else { GetWindowsDirectoryA (homeDirectory, 255); } sprintf (messageFileName, "%s\\%s\\Message.txt", homeDirectory, programName); #endif /* * Save the message file (Unix and Windows only). */ #if gtk || win { FILE *messageFile; if ((messageFile = fopen (messageFileName, "w")) == NULL) { sprintf (errorMessage, "Cannot create message file \"%s\" " "(no privilege to write to directory, or disk full, or program is not called %s).\n", messageFileName, programName); return errorMessage; } #if gtk if (timeOut) fprintf (messageFile, "#%ld\n", (long) getpid ()); /* Write own process ID for callback. */ #endif fprintf (messageFile, "%s", text); fclose (messageFile); } #endif /* * Where shall we send the message? */ #if gtk /* * Get the process ID and the window ID of a running Praat-shell program. */ sprintf (pidFileName, "%s/.%s-dir/pid", home, programName); if ((pidFile = fopen (pidFileName, "r")) == NULL) { sprintf (errorMessage, "Program %s not running (or a version older than 3.6).", programName); return errorMessage; } if (fscanf (pidFile, "%ld%ld", & pid, & wid) < 1) { fclose (pidFile); sprintf (errorMessage, "Program %s not running, or disk has been full.", programName); return errorMessage; } fclose (pidFile); #elif win /* * Get the window handle of the "Objects" window of a running Praat-shell program. */ sprintf (windowName, "PraatShell1 %s", programName); window = FindWindowA (windowName, NULL); if (! window) { sprintf (errorMessage, "Program %s not running (or an old version).", programName); return errorMessage; } #elif mac /* * Convert the program name to a Macintosh signature. * I know of no system routine for this, so I'll just translate the two most common names: */ if (! strcmp (programName, "praat") || ! strcmp (programName, "Praat") || ! strcmp (programName, "PRAAT")) signature = 'PpgB'; else if (! strcmp (programName, "als") || ! strcmp (programName, "Als") || ! strcmp (programName, "ALS")) signature = 'CclA'; else signature = 0; AECreateDesc (typeApplSignature, & signature, 4, & programDescriptor); #endif /* * Send the message. */ #if gtk /* * Be ready to receive notification of completion. */ if (timeOut) signal (SIGUSR2, handleCompletion); /* * Notify running program. */ if (wid != 0) { /* Praat shell version October 21, 1998 or later? Send event to window. */ /* * Notify main window. */ GdkEventClient gevent; g_type_init (); int displaySupplied = display != NULL; if (! displaySupplied) { display = gdk_display_open (":0.0"); /* GdkDisplay* */ if (display == NULL) { sprintf (errorMessage, "Cannot open display :0.0."); return errorMessage; } } gevent. type = GDK_CLIENT_EVENT; gevent. window = 0; gevent. send_event = 1; gevent. message_type = gdk_atom_intern_static_string ("SENDPRAAT"); gevent. data_format = 8; if (! gdk_event_send_client_message_for_display (display, (GdkEvent *) & gevent, wid)) { if (! displaySupplied) gdk_display_close (display); sprintf (errorMessage, "Cannot send message to %s (window %ld). " "The program %s may have been started by a different user, " "or may have crashed.", programName, wid, programName); return errorMessage; } if (! displaySupplied) gdk_display_close (display); } /* * Wait for the running program to notify us of completion, * but do not wait for more than 'timeOut' seconds. */ if (timeOut) { signal (SIGALRM, handleTimeOut); alarm (timeOut); theTimeOut = timeOut; /* Hand an argument to handleTimeOut () in a static variable. */ errorMessage [0] = '\0'; pause (); if (errorMessage [0] != '\0') return errorMessage; } #elif win /* * Notify the running program by sending a WM_USER message to its main window. */ if (SendMessage (window, WM_USER, 0, 0)) { sprintf (errorMessage, "Program %s returns error.", programName); /* BUG? */ return errorMessage; } #elif mac /* * Notify the running program by sending it an Apple event of the magic class 758934755. */ AECreateAppleEvent (758934755, 0, & programDescriptor, kAutoGenerateReturnID, 1, & event); AEPutParamPtr (& event, 1, typeChar, text, strlen (text) + 1); #ifdef __MACH__ err = AESendMessage (& event, & reply, ( timeOut == 0 ? kAENoReply : kAEWaitReply ) | kAECanInteract | kAECanSwitchLayer, timeOut == 0 ? kNoTimeOut : 60 * timeOut); #else err = AESend (& event, & reply, ( timeOut == 0 ? kAENoReply : kAEWaitReply ) | kAECanInteract | kAECanSwitchLayer, kAENormalPriority, timeOut == 0 ? kNoTimeOut : 60 * timeOut, NULL, NULL); #endif if (err != noErr) { if (err == procNotFound || err == connectionInvalid) sprintf (errorMessage, "Could not send message to program \"%s\".\n" "The program is probably not running (or an old version).", programName); else if (err == errAETimeout) sprintf (errorMessage, "Message to program \"%s\" timed out " "after %ld seconds, before completion.", programName, timeOut); else sprintf (errorMessage, "Unexpected sendpraat error %d.\nNotify the author.", err); } AEDisposeDesc (& programDescriptor); AEDisposeDesc (& event); AEDisposeDesc (& reply); #endif /* * Notify the caller of success (NULL pointer) or failure (string with an error message). */ return errorMessage [0] == '\0' ? NULL : errorMessage; } wchar_t *sendpraatW (void *display, const wchar_t *programName, long timeOut, const wchar_t *text) { wchar_t nativeProgramName [100]; #if gtk char *home, pidFileName [256], messageFileName [256]; FILE *pidFile; long pid, wid = 0; #elif win wchar_t homeDirectory [256], messageFileName [256], windowName [256]; HWND window; (void) display; (void) timeOut; #elif mac AEDesc programDescriptor; AppleEvent event, reply; OSErr err; UInt32 signature; (void) display; #endif /* * Clean up from an earlier call. */ errorMessageW [0] = '\0'; /* * Handle case differences. */ wcscpy (nativeProgramName, programName); #if gtk nativeProgramName [0] = tolower (nativeProgramName [0]); #else nativeProgramName [0] = toupper (nativeProgramName [0]); #endif /* * If the text is going to be sent in a file, create its name. * The file is going to be written into the preferences directory of the receiving program. * On Unix, the name will be something like /home/jane/.praat-dir/message. * On Windows, the name will be something like C:\Documents and Settings\Jane\Praat\Message.txt, * or C:\Windows\Praat\Message.txt on older systems. * On Macintosh, the text is NOT going to be sent in a file. */ #if gtk if ((home = getenv ("HOME")) == NULL) { swprintf (errorMessageW, 1000, L"HOME environment variable not set."); return errorMessageW; } sprintf (messageFileName, "%s/.%ls-dir/message", home, programName); #elif win if (GetEnvironmentVariableW (L"USERPROFILE", homeDirectory, 255)) { ; /* Ready. */ } else if (GetEnvironmentVariableW (L"HOMEDRIVE", homeDirectory, 255)) { GetEnvironmentVariableW (L"HOMEPATH", homeDirectory + wcslen (homeDirectory), 255); } else { GetWindowsDirectoryW (homeDirectory, 255); } swprintf (messageFileName, 256, L"%ls\\%ls\\Message.txt", homeDirectory, programName); #endif /* * Save the message file (Unix and Windows only). */ #if gtk FILE *messageFile; if ((messageFile = fopen (messageFileName, "w")) == NULL) { swprintf (errorMessageW, 1000, L"Cannot create message file \"%s\" " L"(no privilege to write to directory, or disk full).\n", messageFileName); return errorMessageW; } if (timeOut) fwprintf (messageFile, L"#%ld\n", getpid ()); /* Write own process ID for callback. */ fwprintf (messageFile, L"\ufeff%ls", text); fclose (messageFile); #elif win FILE *messageFile; if ((messageFile = _wfopen (messageFileName, L"w")) == NULL) { swprintf (errorMessageW, 1000, L"Cannot create message file \"%ls\" " L"(no privilege to write to directory, or disk full).\n", messageFileName); return errorMessageW; } fwprintf (messageFile, L"\ufeff%ls", text); fclose (messageFile); #endif /* * Where shall we send the message? */ #if gtk /* * Get the process ID and the window ID of a running Praat-shell program. */ sprintf (pidFileName, "%s/.%ls-dir/pid", home, programName); if ((pidFile = fopen (pidFileName, "r")) == NULL) { swprintf (errorMessageW, 1000, L"Program %ls not running (or a version older than 3.6).", programName); return errorMessageW; } if (fscanf (pidFile, "%ld%ld", & pid, & wid) < 1) { fclose (pidFile); swprintf (errorMessageW, 1000, L"Program %ls not running, or disk has been full.", programName); return errorMessageW; } fclose (pidFile); #elif win /* * Get the window handle of the "Objects" window of a running Praat-shell program. */ swprintf (windowName, 256, L"PraatShell1 %ls", programName); window = FindWindowW (windowName, NULL); if (! window) { swprintf (errorMessageW, 1000, L"Program %ls not running (or an old version).", programName); return errorMessageW; } #elif mac /* * Convert the program name to a Macintosh signature. * I know of no system routine for this, so I'll just translate the two most common names: */ if (! wcscmp (programName, L"praat") || ! wcscmp (programName, L"Praat") || ! wcscmp (programName, L"PRAAT")) signature = 'PpgB'; else if (! wcscmp (programName, L"als") || ! wcscmp (programName, L"Als") || ! wcscmp (programName, L"ALS")) signature = 'CclA'; else signature = 0; AECreateDesc (typeApplSignature, & signature, 4, & programDescriptor); #endif /* * Send the message. */ #if gtk /* * Be ready to receive notification of completion. */ if (timeOut) signal (SIGUSR2, handleCompletion); /* * Notify running program. */ if (wid != 0) { /* Praat shell version October 21, 1998 or later? Send event to window. */ /* * Notify main window. */ GdkEventClient gevent; int displaySupplied = display != NULL; g_type_init (); if (! displaySupplied) { display = gdk_display_open (":0.0"); /* GdkDisplay* */ if (display == NULL) { swprintf (errorMessageW, 1000, L"Cannot open display :0.0."); return errorMessageW; } } gevent. type = GDK_CLIENT_EVENT; gevent. window = 0; gevent. send_event = 1; gevent. message_type = gdk_atom_intern_static_string ("SENDPRAAT"); gevent. data_format = 8; if (! gdk_event_send_client_message_for_display (display, (GdkEvent *) & gevent, wid)) { if (! displaySupplied) gdk_display_close (display); swprintf (errorMessageW, 1000, L"Cannot send message to %ls (window %ld). " "The program %ls may have been started by a different user, " "or may have crashed.", programName, wid, programName); return errorMessageW; } if (! displaySupplied) gdk_display_close (display); } /* * Wait for the running program to notify us of completion, * but do not wait for more than 'timeOut' seconds. */ if (timeOut) { signal (SIGALRM, handleTimeOut); alarm (timeOut); theTimeOut = timeOut; /* Hand an argument to handleTimeOut () in a static variable. */ errorMessageW [0] = '\0'; pause (); if (errorMessageW [0] != '\0') return errorMessageW; } #elif win /* * Notify the running program by sending a WM_USER message to its main window. */ if (SendMessage (window, WM_USER, 0, 0)) { swprintf (errorMessageW, 1000, L"Program %ls returns error.", programName); /* BUG? */ return errorMessageW; } #elif mac /* * Notify the running program by sending it an Apple event of the magic class 758934755. */ AECreateAppleEvent (758934755, 0, & programDescriptor, kAutoGenerateReturnID, 1, & event); AEPutParamPtr (& event, 1, typeUnicodeText, text, wcslen (text) + 1); #ifdef __MACH__ err = AESendMessage (& event, & reply, ( timeOut == 0 ? kAENoReply : kAEWaitReply ) | kAECanInteract | kAECanSwitchLayer, timeOut == 0 ? kNoTimeOut : 60 * timeOut); #else err = AESend (& event, & reply, ( timeOut == 0 ? kAENoReply : kAEWaitReply ) | kAECanInteract | kAECanSwitchLayer, kAENormalPriority, timeOut == 0 ? kNoTimeOut : 60 * timeOut, NULL, NULL); #endif if (err != noErr) { if (err == procNotFound || err == connectionInvalid) swprintf (errorMessageW, 1000, L"Could not send message to program \"%ls\".\n" L"The program is probably not running (or an old version).", programName); else if (err == errAETimeout) swprintf (errorMessageW, 1000, L"Message to program \"%ls\" timed out " L"after %ld seconds, before completion.", programName, timeOut); else swprintf (errorMessageW, 1000, L"Unexpected sendpraat error %d.\nNotify the author.", err); } AEDisposeDesc (& programDescriptor); AEDisposeDesc (& event); AEDisposeDesc (& reply); #endif /* * Notify the caller of success (NULL pointer) or failure (string with an error message). */ return errorMessageW [0] == '\0' ? NULL : errorMessageW; } /* * To compile sendpraat as a stand-alone program: * temporarily change the following line to "#if 1" instead of "#if 0": */ #if 0 /* * To compile on MacOS X: cc -o sendpraat -framework CoreServices -framework ApplicationServices -I/System/Library/Frameworks/ApplicationServices.framework/Versions/A/Frameworks/AE.framework/Versions/A/Headers -I/System/Library/Frameworks/CoreServices.framework/Versions/A/Frameworks/CarbonCore.framework/Versions/A/Headers sendpraat.c * or else cc -o sendpraat -framework CoreServices -I/System/Library/Frameworks/CoreServices.framework/Versions/A/Frameworks/AE.framework/Versions/A/Headers -I/System/Library/Frameworks/CoreServices.framework/Versions/A/Frameworks/CarbonCore.framework/Versions/A/Headers sendpraat.c * * To compile on Linux: cc -std=gnu99 -o sendpraat -DUNIX `pkg-config --cflags --libs gtk+-2.0` sendpraat.c */ int main (int argc, char **argv) { int iarg, line, length = 0; long timeOut = 10; /* Default. */ char programName [64], *message, *result; if (argc == 1) { printf ("Syntax:\n"); #if win printf (" sendpraat \n"); #else printf (" sendpraat [] \n"); #endif printf ("\n"); printf ("Arguments:\n"); printf (" : the name of a running program that uses the Praat shell.\n"); printf (" : a sequence of Praat shell lines (commands and directives).\n"); #if ! win printf (" : the number of seconds that sendpraat will wait for an answer\n"); printf (" before writing an error message. A of 0 means that\n"); printf (" the message will be sent asynchronously, i.e., that sendpraat\n"); printf (" will return immediately without issuing any error message.\n"); #endif printf ("\n"); printf ("Usage:\n"); printf (" Each line is a separate argument.\n"); printf (" Lines that contain spaces should be put inside double quotes.\n"); printf ("\n"); printf ("Examples:\n"); printf ("\n"); #if win printf (" sendpraat praat Quit\n"); #else printf (" sendpraat 0 praat Quit\n"); #endif printf (" Causes the program \"praat\" to quit (gracefully).\n"); printf (" This works because \"Quit\" is a fixed command in Praat's Control menu.\n"); #if ! win printf (" Sendpraat will return immediately.\n"); #endif printf ("\n"); #if win printf (" sendpraat praat \"Play reverse\"\n"); #else printf (" sendpraat 1000 praat \"Play reverse\"\n"); #endif printf (" Causes the program \"praat\", which can play sounds,\n"); printf (" to play the selected Sound objects backwards.\n"); printf (" This works because \"Play reverse\" is an action command\n"); printf (" that becomes available in Praat's dynamic menu when Sounds are selected.\n"); #if ! win printf (" Sendpraat will allow \"praat\" at most 1000 seconds to perform this.\n"); #endif printf ("\n"); #if win printf (" sendpraat praat \"execute C:\\MyDocuments\\MyScript.praat\"\n"); #elif mac printf (" sendpraat praat \"execute ~/MyResearch/MyProject/MyScript.praat\"\n"); #endif printf (" Causes the program \"praat\" to execute a script.\n"); #if ! win printf (" Sendpraat will allow \"praat\" at most 10 seconds (the default time out).\n"); #endif printf ("\n"); printf (" sendpraat als \"for i from 1 to 5\" \"Draw circle... 0.5 0.5 0.1*i\" \"endfor\"\n"); printf (" Causes the program \"als\" to draw five concentric circles\n"); printf (" into its Picture window.\n"); exit (0); } iarg = 1; #if ! win /* * Get time-out. */ if (isdigit (argv [iarg] [0])) timeOut = atol (argv [iarg ++]); #endif /* * Get program name. */ if (iarg == argc) { fprintf (stderr, "sendpraat: missing program name. Type \"sendpraat\" to get help.\n"); return 1; } strcpy (programName, argv [iarg ++]); /* * Create the message string. */ for (line = iarg; line < argc; line ++) length += strlen (argv [line]) + 1; length --; message = malloc (length + 1); message [0] = '\0'; for (line = iarg; line < argc; line ++) { strcat (message, argv [line]); if (line < argc - 1) strcat (message, "\n"); } /* * Send message. */ result = sendpraat (NULL, programName, timeOut, message); if (result != NULL) { fprintf (stderr, "sendpraat: %s\n", result); exit (1); } exit (0); return 0; } #endif /* End of file sendpraat.c */ sources_5316/sys/ManPagesM.h0000644000176700017670000001605611512127042014525 0ustar paulpaul#ifndef _ManPagesM_h_ #define _ManPagesM_h_ /* ManPagesM.h * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2011/01/05 */ /* ManPages macros. */ #ifndef _ManPages_h_ #include "ManPages.h" #endif #define MAN_BEGIN(t,a,d) { const wchar_t *title = t, *author = a; long date = d; \ static struct structManPage_Paragraph page [] = { #define INTRO(text) { kManPage_type_INTRO, text }, #define ENTRY(text) { kManPage_type_ENTRY, text }, #define NORMAL(text) { kManPage_type_NORMAL, text }, #define LIST_ITEM(text) { kManPage_type_LIST_ITEM, text }, #define LIST_ITEM1(text) { kManPage_type_LIST_ITEM1, text }, #define LIST_ITEM2(text) { kManPage_type_LIST_ITEM2, text }, #define LIST_ITEM3(text) { kManPage_type_LIST_ITEM3, text }, #define TAG(text) { kManPage_type_TAG, text }, #define TAG1(text) { kManPage_type_TAG1, text }, #define TAG2(text) { kManPage_type_TAG2, text }, #define TAG3(text) { kManPage_type_TAG3, text }, #define DEFINITION(text) { kManPage_type_DEFINITION, text }, #define DEFINITION1(text) { kManPage_type_DEFINITION1, text }, #define DEFINITION2(text) { kManPage_type_DEFINITION2, text }, #define DEFINITION3(text) { kManPage_type_DEFINITION3, text }, #define CODE(text) { kManPage_type_CODE, text }, #define CODE1(text) { kManPage_type_CODE1, text }, #define CODE2(text) { kManPage_type_CODE2, text }, #define CODE3(text) { kManPage_type_CODE3, text }, #define CODE4(text) { kManPage_type_CODE4, text }, #define CODE5(text) { kManPage_type_CODE5, text }, #define PROTOTYPE(text) { kManPage_type_PROTOTYPE, text }, #define FORMULA(text) { kManPage_type_FORMULA, text }, #define PICTURE(width,height,draw) { kManPage_type_PICTURE, NULL, width, height, draw }, #define SCRIPT(width,height,text) { kManPage_type_SCRIPT, text, width, height }, #define MAN_END { 0 } }; ManPages_addPage (me, title, author, date, page); } #define Manual_DRAW_WINDOW(height,title,menu) \ "Select inner viewport... 0.2 5.8 0.2 " #height "-0.2\n" \ "Axes... 0 100*5.6 100*(" #height "-0.4) 0\n" \ "Paint rectangle... 0.8 0 560 0 30\n" \ "Paint circle... {1,0.5,0.5} 15 15 8\n" \ "Draw line... 15-5 10 15+5 20\n" \ "Draw line... 15+5 10 15-5 20\n" \ "Paint circle... {1,1,0.25} 40 15 8\n" \ "Draw line... 40-7 15 40+7 15\n" \ "Paint circle... {0.25,1,0.25} 65 15 8\n" \ "Draw rectangle... 65-5 65+5 15-5 15+5\n" \ "Helvetica\n" \ "Text... 280 centre 15 half " title "\n" \ "Paint rectangle... 0.9 0 560 30 60\n" \ "Text... 5 left 45 half " menu "\n" \ "Draw line... 0 30 560 30\n" \ "info$ = Picture info\n" \ "fontSize = extractNumber (info$, \"Font size: \")\n" #define Manual_SETTINGS_WINDOW_HEIGHT(numberOfVerticalFields) 1.4+numberOfVerticalFields*0.4 #define Manual_DRAW_SETTINGS_WINDOW(title,numberOfVerticalFields) \ "Select inner viewport... 0.1 5.3 0.2 1.2+" #numberOfVerticalFields "*0.4\n" \ "height = 100*(1+" #numberOfVerticalFields "*0.4)\n" \ "Axes... 0 100*5.2 height 0\n" \ "Paint rectangle... 0.8 0 520 0 30\n" \ "Paint circle... {1,0.5,0.5} 15 15 8\n" \ "Draw line... 15-5 10 15+5 20\n" \ "Draw line... 15+5 10 15-5 20\n" \ "Helvetica\n" \ "Text... 260 centre 15 half " title "\n" \ "Paint rectangle... 0.9 0 520 30 height\n" \ "Draw line... 0 30 520 30\n" \ "buttonColour$ = \"0.95\"\n" \ "Paint rounded rectangle... 'buttonColour$' 15 85 height-10 height-34 2.0\n" \ "Draw rounded rectangle... 15 85 height-10 height-34 2.0\n" \ "Text... 50 centre height-21 half Help\n" \ "Paint rounded rectangle... 'buttonColour$' 95 195 height-10 height-34 2.0\n" \ "Draw rounded rectangle... 95 195 height-10 height-34 2.0\n" \ "Text... 145 centre height-21 half Standards\n" \ "Paint rounded rectangle... 'buttonColour$' 275 345 height-10 height-34 2.0\n" \ "Draw rounded rectangle... 275 345 height-10 height-34 2.0\n" \ "Text... 310 centre height-21 half Cancel\n" \ "Paint rounded rectangle... 'buttonColour$' 355 425 height-10 height-34 2.0\n" \ "Draw rounded rectangle... 355 425 height-10 height-34 2.0\n" \ "Text... 390 centre height-21 half Apply\n" \ "Line width... 2\n" \ "Paint rounded rectangle... {0.8,0.8,1} 435 505 height-10 height-34 2.0\n" \ "Draw rounded rectangle... 435 505 height-10 height-34 2.0\n" \ "Line width... 1\n" \ "Text... 470 centre height-21 half OK\n" \ "Draw rectangle... 0 520 0 height\n" \ "info$ = Picture info\n" \ "fontSize = extractNumber (info$, \"Font size: \")\n" \ "y = 55\n" #define Manual_DRAW_SETTINGS_WINDOW_FIELD(label,text) \ "Text... 255 right y half " label ":\n" \ "Paint rectangle... white 265 505 y-12 y+12\n" \ "Draw rectangle... 265 505 y-12 y+12\n" \ ";Courier\n" \ "Text... 265 left y half " text "\n" \ "Helvetica\n" \ "y += 40\n" #define Manual_DRAW_SETTINGS_WINDOW_RANGE(label,text1,text2) \ "Text... 255 right y half " label ":\n" \ "Paint rectangle... white 265 370 y-12 y+12\n" \ "Draw rectangle... 265 370 y-12 y+12\n" \ "Paint rectangle... white 380 505 y-12 y+12\n" \ "Draw rectangle... 380 505 y-12 y+12\n" \ ";Courier\n" \ "Text... 265 left y half " text1 "\n" \ "Text... 380 left y half " text2 "\n" \ "Helvetica\n" \ "y += 40\n" #define Manual_DRAW_SETTINGS_WINDOW_BOOLEAN(label,on) \ "if " #on "\n" \ " Paint rectangle... yellow 265 279 y-7 y+7\n" \ " Text special... 272 centre y half Times fontSize*1.2 0 ##\\Vr\n" \ "else\n" \ " Paint rectangle... white 265 279 y-7 y+7\n" \ "endif\n" \ "Draw rectangle... 265 279 y-7 y+7\n" \ "Text... 281 left y half " label "\n" \ "y += 40\n" #define Manual_DRAW_SETTINGS_WINDOW_RADIO(label,text,on) \ "if \"" label "\" <> \"\"\n" \ " Text... 255 right y half " label ":\n" \ "endif\n" \ "if " #on "\n" \ " Paint circle... yellow 272 y 7\n" \ " Paint circle... black 272 y 3\n" \ "else\n" \ " Paint circle... white 272 y 7\n" \ "endif\n" \ "Draw circle... 272 y 7\n" \ "Text... 281 left y half " text "\n" \ "y += 40\n" #define Manual_DRAW_SETTINGS_WINDOW_OPTIONMENU(label,text) \ "Text... 255 right y half " label ":\n" \ "Paint rounded rectangle... 'buttonColour$' 265 505 y-12 y+12 1.0\n" \ "Draw rounded rectangle... 265 505 y-12 y+12 2.0\n" \ "Text... 270 left y half " text "\n" \ "Helvetica\n" \ "y += 40\n" #define Manual_DRAW_SETTINGS_WINDOW_TEXT(label,text) \ "Text... 12 left y half " label ":\n" \ "y += 24\n" \ "Paint rectangle... white 15 505 y-12 y+12\n" \ "Draw rectangle... 15 505 y-12 y+12\n" \ ";Courier\n" \ "Text... 15 left y half " text "\n" \ "Helvetica\n" \ "y += 40\n" /* End of file ManPagesM.h */ #endif sources_5316/sys/machine.h0000644000176700017670000000210511611106073014310 0ustar paulpaul#ifndef _machine_h_ #define _machine_h_ /* machine.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ void Machine_initLookAndFeel (unsigned int argc, char **argv); int Machine_getMenuBarHeight (void); int Machine_getMainWindowMenuBarHeight (void); int Machine_getTitleBarHeight (void); int Machine_getScrollBarWidth (void); int Machine_getTextHeight (void); /* End of file machine.h */ #endif sources_5316/sys/Data.cpp0000644000176700017670000003332311724662321014126 0ustar paulpaul/* Data.cpp * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection.h" Thing_implement (Data, Thing, 0); structMelderDir Data_directoryBeingRead = { { 0 } }; void structData :: v_copy (thou) { thouart (Data); (void) thee; } bool structData :: v_equal (thou) { thouart (Data); (void) thee; return true; } // names of "identical" objects are allowed to be different bool structData :: v_canWriteAsEncoding (int encoding) { (void) encoding; return true; } void structData :: v_writeText (MelderFile openFile) { (void) openFile; } void structData :: v_readText (MelderReadText text) { (void) text; } void structData :: v_writeBinary (FILE *f) { (void) f; } void structData :: v_readBinary (FILE *f) { (void) f; } Any _Data_copy (Data me) { try { if (me == NULL) return NULL; autoData thee = (Data) _Thing_new (my classInfo); my v_copy (thee.peek()); therror Thing_setName (thee.peek(), my name); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not copied."); } } bool Data_equal (Data me, Data thee) { if (my classInfo != thy classInfo) return false; // different class: not equal int offset = sizeof (struct structData); // we already compared the methods, and are going to skip the names if (! memcmp ((char *) me + offset, (char *) thee + offset, my classInfo -> size - offset)) return true; // no shallow differences return my v_equal (thee); } bool Data_canWriteAsEncoding (Data me, int encoding) { return my v_canWriteAsEncoding (encoding); } bool Data_canWriteText (Data me) { return my v_writable (); } void Data_writeText (Data me, MelderFile openFile) { my v_writeText (openFile); therror if (ferror (openFile -> filePointer)) Melder_throw ("I/O error."); } MelderFile Data_createTextFile (Data me, MelderFile file, bool verbose) { autoMelderFile mfile = MelderFile_create (file, L"TEXT", 0, L"txt"); #if defined (_WIN32) file -> requiresCRLF = true; #endif file -> verbose = verbose; file -> outputEncoding = Melder_getOutputEncoding (); if (file -> outputEncoding == kMelder_textOutputEncoding_ASCII_THEN_UTF16) file -> outputEncoding = Data_canWriteAsEncoding (me, kMelder_textOutputEncoding_ASCII) ? kMelder_textOutputEncoding_ASCII : kMelder_textOutputEncoding_UTF16; else if (file -> outputEncoding == kMelder_textOutputEncoding_ISO_LATIN1_THEN_UTF16) file -> outputEncoding = Data_canWriteAsEncoding (me, kMelder_textOutputEncoding_ISO_LATIN1) ? kMelder_textOutputEncoding_ISO_LATIN1 : kMelder_textOutputEncoding_UTF16; if (file -> outputEncoding == kMelder_textOutputEncoding_UTF16) { binputu2 (0xfeff, file -> filePointer); } return mfile.transfer(); } static void _Data_writeToTextFile (Data me, MelderFile file, bool verbose) { try { if (! Data_canWriteText (me)) Melder_throw ("Objects of class ", my classInfo -> className, " cannot be written to a text file."); autoMelderFile mfile = Data_createTextFile (me, file, verbose); #ifndef _WIN32 flockfile (file -> filePointer); // BUG #endif MelderFile_write2 (file, L"File type = \"ooTextFile\"\nObject class = \"", my classInfo -> className); if (my classInfo -> version > 0) MelderFile_write2 (file, L" ", Melder_integer (my classInfo -> version)); MelderFile_write1 (file, L"\"\n"); Data_writeText (me, file); MelderFile_writeCharacter (file, '\n'); #ifndef _WIN32 if (file -> filePointer) funlockfile (file -> filePointer); #endif mfile.close (); MelderFile_setMacTypeAndCreator (file, 'TEXT', 0); } catch (MelderError) { #ifndef _WIN32 if (file -> filePointer) funlockfile (file -> filePointer); // the file pointer is NULL before Data_createTextFile() and after mfile.close() #endif throw; } } void Data_writeToTextFile (Data me, MelderFile file) { try { _Data_writeToTextFile (me, file, true); } catch (MelderError) { Melder_throw (me, ": not written to text file ", file, "."); } } void Data_writeToShortTextFile (Data me, MelderFile file) { try { _Data_writeToTextFile (me, file, false); } catch (MelderError) { Melder_throw (me, ": not written to short text file ", file, "."); } } bool Data_canWriteBinary (Data me) { return my v_writable (); } void Data_writeBinary (Data me, FILE *f) { my v_writeBinary (f); therror if (ferror (f)) Melder_throw ("I/O error."); } void Data_writeToBinaryFile (Data me, MelderFile file) { try { if (! Data_canWriteBinary (me)) Melder_throw ("Objects of class ", my classInfo -> className, L" cannot be written to a generic binary file."); autoMelderFile mfile = MelderFile_create (file, 0, 0, 0); if (fprintf (file -> filePointer, "ooBinaryFile") < 0) Melder_throw ("Cannot write first bytes of file."); binputw1 ( my classInfo -> version > 0 ? Melder_wcscat (my classInfo -> className, L" ", Melder_integer (my classInfo -> version)) : my classInfo -> className, file -> filePointer); Data_writeBinary (me, file -> filePointer); mfile.close (); MelderFile_setMacTypeAndCreator (file, 'BINA', 0); } catch (MelderError) { Melder_throw (me, ": not written to binary file ", file, "."); } } bool Data_canReadText (Data me) { return my v_writable (); } void Data_readText (Data me, MelderReadText text) { try { my v_readText (text); therror } catch (MelderError) { Melder_throw (Thing_className (me), " not read."); } } Any Data_readFromTextFile (MelderFile file) { try { autoMelderReadText text = MelderReadText_createFromFile (file); wchar *line = MelderReadText_readLine (text.peek()); therror if (line == NULL) Melder_throw ("No lines."); wchar *end = wcsstr (line, L"ooTextFile"); // oo format? autoData me = NULL; if (end) { autostring klas = texgetw2 (text.peek()); me.reset ((Data) Thing_newFromClassName (klas.peek())); } else { end = wcsstr (line, L"TextFile"); if (end == NULL) Melder_throw ("Not an old-type text file; should not occur."); *end = '\0'; me.reset ((Data) Thing_newFromClassName (line)); Thing_version = -1; // old version: override version number, which was set to 0 by newFromClassName } MelderFile_getParentDir (file, & Data_directoryBeingRead); Data_readText (me.peek(), text.peek()); therror return me.transfer(); } catch (MelderError) { Melder_throw ("Data not read from text file ", file, "."); } } bool Data_canReadBinary (Data me) { return my v_writable (); } void Data_readBinary (Data me, FILE *f) { try { my v_readBinary (f); therror if (feof (f)) Melder_throw ("Early end of file."); if (ferror (f)) Melder_throw ("I/O error."); } catch (MelderError) { Melder_throw (Thing_className (me), " not read."); } } Any Data_readFromBinaryFile (MelderFile file) { try { autofile f = Melder_fopen (file, "rb"); char line [200]; int n = fread (line, 1, 199, f); line [n] = '\0'; char *end = strstr (line, "ooBinaryFile"); autoData me = NULL; if (end) { fseek (f, strlen ("ooBinaryFile"), 0); autostring8 klas = bingets1 (f); me.reset ((Data) Thing_newFromClassNameA (klas.peek())); } else { end = strstr (line, "BinaryFile"); if (! end) { Melder_throw ("File ", file, " is not a Data binary file."); } *end = '\0'; me.reset ((Data) Thing_newFromClassNameA (line)); Thing_version = -1; // old version: override version number, which was set to 0 by newFromClassName rewind (f); fread (line, 1, end - line + strlen ("BinaryFile"), f); } MelderFile_getParentDir (file, & Data_directoryBeingRead); Data_readBinary (me.peek(), f); therror f.close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("Data not read from binary file ", file, "."); } } /* Generic reading. */ static int numFileTypeRecognizers = 0; static Any (*fileTypeRecognizers [100]) (int nread, const char *header, MelderFile fs); void Data_recognizeFileType (Any (*recognizer) (int nread, const char *header, MelderFile fs)) { Melder_assert (numFileTypeRecognizers < 100); fileTypeRecognizers [++ numFileTypeRecognizers] = recognizer; } Any Data_readFromFile (MelderFile file) { int nread, i; char header [513]; autofile f = Melder_fopen (file, "rb"); nread = fread (& header [0], 1, 512, f); f.close (file); header [nread] = 0; /***** 1. Is this file a text file as defined in Data.cpp? *****/ if (nread > 11) { char *p = strstr (header, "TextFile"); if (p != NULL && p - header < nread - 8 && p - header < 40) return Data_readFromTextFile (file); } if (nread > 22) { char headerCopy [101]; memcpy (headerCopy, header, 100); headerCopy [100] = '\0'; for (i = 0; i < 100; i ++) if (headerCopy [i] == '\0') headerCopy [i] = '\001'; char *p = strstr (headerCopy, "T\001e\001x\001t\001F\001i\001l\001e"); if (p != NULL && p - headerCopy < nread - 15 && p - headerCopy < 80) return Data_readFromTextFile (file); } /***** 2. Is this file a binary file as defined in Data.cpp? *****/ if (nread > 13) { char *p = strstr (header, "BinaryFile"); if (p != NULL && p - header < nread - 10 && p - header < 40) return Data_readFromBinaryFile (file); } /***** 3. Is this file of a type for which a recognizer has been installed? *****/ MelderFile_getParentDir (file, & Data_directoryBeingRead); for (i = 1; i <= numFileTypeRecognizers; i ++) { Data object = (Data) fileTypeRecognizers [i] (nread, header, file); if (object) return object; } /***** 4. Is this a common text file? *****/ for (i = 0; i < nread; i ++) if (header [i] < 32 || header [i] > 126) /* Not ASCII? */ break; if (i >= nread) return Data_readFromTextFile (file); Melder_throw ("File ", file, " not recognized."); } /* Recursive routines for working with struct members. */ int Data_Description_countMembers (Data_Description structDescription) { int count = 0; for (Data_Description desc = structDescription; desc -> name; desc ++) count ++; if (structDescription [0]. type == inheritwa) { Data_Description parentDescription = ((Data) _Thing_dummyObject ((ClassInfo) structDescription [0]. tagType)) -> v_description (); if (parentDescription) return count + Data_Description_countMembers (parentDescription); } return count; } Data_Description Data_Description_findMatch (Data_Description structDescription, const wchar_t *name) { for (Data_Description desc = structDescription; desc -> name; desc ++) if (wcsequ (name, desc -> name)) return desc; if (structDescription [0]. type == inheritwa) { Data_Description parentDescription = ((Data) _Thing_dummyObject ((ClassInfo) structDescription [0]. tagType)) -> v_description (); if (parentDescription) return Data_Description_findMatch (parentDescription, name); } return NULL; /* Not found. */ } Data_Description Data_Description_findNumberUse (Data_Description structDescription, const wchar_t *string) { for (Data_Description desc = structDescription; desc -> name; desc ++) { if (desc -> max1 && wcsequ (desc -> max1, string)) return desc; if (desc -> max2 && wcsequ (desc -> max2, string)) return desc; } if (structDescription [0]. type == inheritwa) { Data_Description parentDescription = ((Data) _Thing_dummyObject ((ClassInfo) structDescription [0]. tagType)) -> v_description (); if (parentDescription) return Data_Description_findNumberUse (parentDescription, string); } return NULL; } /* Retrieving data from object + description. */ long Data_Description_integer (void *address, Data_Description description) { switch (description -> type) { case bytewa: return * (signed char *) ((char *) address + description -> offset); case intwa: return * (int *) ((char *) address + description -> offset); case longwa: return * (long *) ((char *) address + description -> offset); case ubytewa: return * (unsigned char *) ((char *) address + description -> offset); case uintwa: return * (unsigned int *) ((char *) address + description -> offset); case ulongwa: return * (unsigned long *) ((char *) address + description -> offset); case boolwa: return * (bool *) ((char *) address + description -> offset); case objectwa: return (* (Collection *) ((char *) address + description -> offset)) -> size; case collectionwa: return (* (Collection *) ((char *) address + description -> offset)) -> size; default: return 0; } } int Data_Description_evaluateInteger (void *structAddress, Data_Description structDescription, const wchar *formula, long *result) { if (formula == NULL) { // this was a VECTOR_FROM array *result = 1; return 1; } if (formula [0] >= 'a' && formula [0] <= 'z') { wchar buffer [100], *minus1, *psize; Data_Description sizeDescription; wcscpy (buffer, formula); if ((minus1 = wcsstr (buffer, L" - 1")) != NULL) *minus1 = '\0'; // strip trailing " - 1", but remember if ((psize = wcsstr (buffer, L" -> size")) != NULL) *psize = '\0'; // strip trailing " -> size" if (! (sizeDescription = Data_Description_findMatch (structDescription, buffer))) { *result = 0; return 0 /*Melder_error ("Cannot find member \"%ls\".", buffer)*/; } *result = Data_Description_integer (structAddress, sizeDescription); if (minus1) *result -= 1; } else { *result = wcstol (formula, NULL, 10); } return 1; } /* End of file Data.cpp */ sources_5316/sys/TextEditor.cpp0000644000176700017670000006251211640563154015353 0ustar paulpaul/* TextEditor.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Franz Brausse helped with Undo support in 2010 */ #include "TextEditor.h" #include "machine.h" #include "longchar.h" #include "EditorM.h" #include "Preferences.h" #include "UnicodeData.h" Thing_implement (TextEditor, Editor, 0); static int theTextEditorFontSize; void TextEditor_prefs (void) { Preferences_addInt (L"TextEditor.fontSize", & theTextEditorFontSize, 12); } static Collection theOpenTextEditors = NULL; /***** TextEditor methods *****/ void structTextEditor :: v_destroy () { forget (openDialog); forget (saveDialog); forget (printDialog); forget (findDialog); if (theOpenTextEditors) { Collection_undangleItem (theOpenTextEditors, this); } TextEditor_Parent :: v_destroy (); } void structTextEditor :: v_nameChanged () { if (v_fileBased ()) { bool dirtinessAlreadyShown = GuiWindow_setDirty (d_windowShell, dirty); static MelderString windowTitle = { 0 }; MelderString_empty (& windowTitle); if (name == NULL) { MelderString_append (& windowTitle, L"(untitled"); if (dirty && ! dirtinessAlreadyShown) MelderString_append (& windowTitle, L", modified"); MelderString_append (& windowTitle, L")"); } else { MelderString_append (& windowTitle, L"File ", MelderFile_messageName (& file)); if (dirty && ! dirtinessAlreadyShown) MelderString_append (& windowTitle, L" (modified)"); } GuiWindow_setTitle (d_windowShell, windowTitle.string); MelderString_empty (& windowTitle); MelderString_append (& windowTitle, dirty && ! dirtinessAlreadyShown ? L"*" : L"", name == NULL ? L"(untitled)" : MelderFile_name (& file)); #if motif XtVaSetValues (d_windowShell, XmNiconName, Melder_peekWcsToUtf8 (windowTitle.string), NULL); #endif } else { TextEditor_Parent :: v_nameChanged (); } } static void openDocument (TextEditor me, MelderFile file) { if (theOpenTextEditors) { for (long ieditor = 1; ieditor <= theOpenTextEditors -> size; ieditor ++) { TextEditor editor = (TextEditor) theOpenTextEditors -> item [ieditor]; if (editor != me && MelderFile_equal (file, & editor -> file)) { editor -> raise (); Melder_error_ ("Text file ", file, " is already open."); forget (me); // don't forget me before Melder_error_, because "file" is owned by one of my dialogs Melder_flushError (NULL); return; } } } autostring text = MelderFile_readText (file); GuiText_setString (my textWidget, text.peek()); /* * GuiText_setString has invoked the changeCallback, * which has set 'my dirty' to TRUE. Fix this. */ my dirty = FALSE; MelderFile_copy (file, & my file); Thing_setName (me, Melder_fileToPath (file)); } static void newDocument (TextEditor me) { GuiText_setString (my textWidget, L""); // implicitly sets my dirty to TRUE my dirty = FALSE; if (my v_fileBased ()) Thing_setName (me, NULL); } static void saveDocument (TextEditor me, MelderFile file) { autostring text = GuiText_getString (my textWidget); MelderFile_writeText (file, text.peek()); therror my dirty = FALSE; MelderFile_copy (file, & my file); if (my v_fileBased ()) Thing_setName (me, Melder_fileToPath (file)); } static void closeDocument (TextEditor me) { forget (me); } static void cb_open_ok (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter, const wchar_t *invokingButtonTitle, bool modified, I) { iam (TextEditor); (void) sendingString; (void) interpreter; (void) invokingButtonTitle; (void) modified; MelderFile file = UiFile_getFile (sendingForm); openDocument (me, file); } static void cb_showOpen (EditorCommand cmd, UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter) { TextEditor me = (TextEditor) cmd -> d_editor; (void) sendingForm; (void) sendingString; (void) interpreter; if (! my openDialog) my openDialog = UiInfile_create (my d_windowForm, L"Open", cb_open_ok, me, NULL, NULL, false); UiInfile_do (my openDialog); } static void cb_saveAs_ok (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter, const wchar_t *invokingButtonTitle, bool modified, I) { iam (TextEditor); (void) sendingString; (void) interpreter; (void) invokingButtonTitle; (void) modified; MelderFile file = UiFile_getFile (sendingForm); saveDocument (me, file); } static void menu_cb_saveAs (EDITOR_ARGS) { EDITOR_IAM (TextEditor); wchar defaultName [300]; if (! my saveDialog) my saveDialog = UiOutfile_create (my d_windowForm, L"Save", cb_saveAs_ok, me, NULL, NULL); swprintf (defaultName, 300, ! my v_fileBased () ? L"info.txt" : my name ? MelderFile_name (& my file) : L""); UiOutfile_do (my saveDialog, defaultName); } static void gui_button_cb_saveAndOpen (I, GuiButtonEvent event) { (void) event; EditorCommand cmd = (EditorCommand) void_me; TextEditor me = (TextEditor) cmd -> d_editor; GuiObject_hide (my dirtyOpenDialog); if (my name) { try { saveDocument (me, & my file); } catch (MelderError) { Melder_flushError (NULL); return; } cb_showOpen (cmd, NULL, NULL, NULL); } else { menu_cb_saveAs (me, cmd, NULL, NULL, NULL); } } static void gui_button_cb_cancelOpen (I, GuiButtonEvent event) { (void) event; EditorCommand cmd = (EditorCommand) void_me; TextEditor me = (TextEditor) cmd -> d_editor; GuiObject_hide (my dirtyOpenDialog); } static void gui_button_cb_discardAndOpen (I, GuiButtonEvent event) { (void) event; EditorCommand cmd = (EditorCommand) void_me; TextEditor me = (TextEditor) cmd -> d_editor; GuiObject_hide (my dirtyOpenDialog); cb_showOpen (cmd, NULL, NULL, NULL); } static void menu_cb_open (EDITOR_ARGS) { EDITOR_IAM (TextEditor); if (my dirty) { if (my dirtyOpenDialog == NULL) { int buttonWidth = 120, buttonSpacing = 20; my dirtyOpenDialog = GuiDialog_create (my d_windowShell, 150, 70, Gui_LEFT_DIALOG_SPACING + 3 * buttonWidth + 2 * buttonSpacing + Gui_RIGHT_DIALOG_SPACING, Gui_TOP_DIALOG_SPACING + Gui_TEXTFIELD_HEIGHT + Gui_VERTICAL_DIALOG_SPACING_SAME + 2 * Gui_BOTTOM_DIALOG_SPACING + Gui_PUSHBUTTON_HEIGHT, L"Text changed", NULL, NULL, GuiDialog_MODAL); GuiLabel_createShown (my dirtyOpenDialog, Gui_LEFT_DIALOG_SPACING, Gui_AUTOMATIC, Gui_TOP_DIALOG_SPACING, Gui_AUTOMATIC, L"The text has changed! Save changes?", 0); GuiObject buttonArea = GuiDialog_getButtonArea (my dirtyOpenDialog); int x = Gui_LEFT_DIALOG_SPACING, y = - Gui_BOTTOM_DIALOG_SPACING; GuiButton_createShown (buttonArea, x, x + buttonWidth, y - Gui_PUSHBUTTON_HEIGHT, y, L"Discard & Open", gui_button_cb_discardAndOpen, cmd, 0); x += buttonWidth + buttonSpacing; GuiButton_createShown (buttonArea, x, x + buttonWidth, y - Gui_PUSHBUTTON_HEIGHT, y, L"Cancel", gui_button_cb_cancelOpen, cmd, 0); x += buttonWidth + buttonSpacing; GuiButton_createShown (buttonArea, x, x + buttonWidth, y - Gui_PUSHBUTTON_HEIGHT, y, L"Save & Open", gui_button_cb_saveAndOpen, cmd, 0); } GuiObject_show (my dirtyOpenDialog); } else { cb_showOpen (cmd, sendingForm, sendingString, interpreter); } } static void gui_button_cb_saveAndNew (I, GuiButtonEvent event) { (void) event; EditorCommand cmd = (EditorCommand) void_me; TextEditor me = (TextEditor) cmd -> d_editor; GuiObject_hide (my dirtyNewDialog); if (my name) { try { saveDocument (me, & my file); } catch (MelderError) { Melder_flushError (NULL); return; } newDocument (me); } else { menu_cb_saveAs (me, cmd, NULL, NULL, NULL); } } static void gui_button_cb_cancelNew (I, GuiButtonEvent event) { (void) event; EditorCommand cmd = (EditorCommand) void_me; TextEditor me = (TextEditor) cmd -> d_editor; GuiObject_hide (my dirtyNewDialog); } static void gui_button_cb_discardAndNew (I, GuiButtonEvent event) { (void) event; EditorCommand cmd = (EditorCommand) void_me; TextEditor me = (TextEditor) cmd -> d_editor; GuiObject_hide (my dirtyNewDialog); newDocument (me); } static void menu_cb_new (EDITOR_ARGS) { EDITOR_IAM (TextEditor); if (my v_fileBased () && my dirty) { if (! my dirtyNewDialog) { int buttonWidth = 120, buttonSpacing = 20; my dirtyNewDialog = GuiDialog_create (my d_windowShell, 150, 70, Gui_LEFT_DIALOG_SPACING + 3 * buttonWidth + 2 * buttonSpacing + Gui_RIGHT_DIALOG_SPACING, Gui_TOP_DIALOG_SPACING + Gui_TEXTFIELD_HEIGHT + Gui_VERTICAL_DIALOG_SPACING_SAME + 2 * Gui_BOTTOM_DIALOG_SPACING + Gui_PUSHBUTTON_HEIGHT, L"Text changed", NULL, NULL, GuiDialog_MODAL); GuiLabel_createShown (my dirtyNewDialog, Gui_LEFT_DIALOG_SPACING, Gui_AUTOMATIC, Gui_TOP_DIALOG_SPACING, Gui_AUTOMATIC, L"The text has changed! Save changes?", 0); GuiObject buttonArea = GuiDialog_getButtonArea (my dirtyNewDialog); int x = Gui_LEFT_DIALOG_SPACING, y = - Gui_BOTTOM_DIALOG_SPACING; GuiButton_createShown (buttonArea, x, x + buttonWidth, y - Gui_PUSHBUTTON_HEIGHT, y, L"Discard & New", gui_button_cb_discardAndNew, cmd, 0); x += buttonWidth + buttonSpacing; GuiButton_createShown (buttonArea, x, x + buttonWidth, y - Gui_PUSHBUTTON_HEIGHT, y, L"Cancel", gui_button_cb_cancelNew, cmd, 0); x += buttonWidth + buttonSpacing; GuiButton_createShown (buttonArea, x, x + buttonWidth, y - Gui_PUSHBUTTON_HEIGHT, y, L"Save & New", gui_button_cb_saveAndNew, cmd, 0); } GuiObject_show (my dirtyNewDialog); } else { newDocument (me); } } static void menu_cb_clear (EDITOR_ARGS) { EDITOR_IAM (TextEditor); my v_clear (); } static void menu_cb_save (EDITOR_ARGS) { EDITOR_IAM (TextEditor); if (my name) { try { saveDocument (me, & my file); } catch (MelderError) { Melder_flushError (NULL); return; } } else { menu_cb_saveAs (me, cmd, NULL, NULL, NULL); } } static void menu_cb_reopen (EDITOR_ARGS) { EDITOR_IAM (TextEditor); if (my name) { try { openDocument (me, & my file); } catch (MelderError) { Melder_flushError (NULL); return; } } else { Melder_throw ("Cannot reopen from disk, because the text has never been saved yet."); } } static void gui_button_cb_saveAndClose (I, GuiButtonEvent event) { (void) event; iam (TextEditor); GuiObject_hide (my dirtyCloseDialog); if (my name) { try { saveDocument (me, & my file); } catch (MelderError) { Melder_flushError (NULL); return; } closeDocument (me); } else { menu_cb_saveAs (me, Editor_getMenuCommand (me, L"File", L"Save as..."), NULL, NULL, NULL); } } static void gui_button_cb_cancelClose (I, GuiButtonEvent event) { (void) event; iam (TextEditor); GuiObject_hide (my dirtyCloseDialog); } static void gui_button_cb_discardAndClose (I, GuiButtonEvent event) { (void) event; iam (TextEditor); GuiObject_hide (my dirtyCloseDialog); closeDocument (me); } void structTextEditor :: v_goAway () { if (v_fileBased () && dirty) { if (! dirtyCloseDialog) { int buttonWidth = 120, buttonSpacing = 20; dirtyCloseDialog = GuiDialog_create (d_windowShell, 150, 70, Gui_LEFT_DIALOG_SPACING + 3 * buttonWidth + 2 * buttonSpacing + Gui_RIGHT_DIALOG_SPACING, Gui_TOP_DIALOG_SPACING + Gui_TEXTFIELD_HEIGHT + Gui_VERTICAL_DIALOG_SPACING_SAME + 2 * Gui_BOTTOM_DIALOG_SPACING + Gui_PUSHBUTTON_HEIGHT, L"Text changed", NULL, NULL, GuiDialog_MODAL); GuiLabel_createShown (dirtyCloseDialog, Gui_LEFT_DIALOG_SPACING, Gui_AUTOMATIC, Gui_TOP_DIALOG_SPACING, Gui_AUTOMATIC, L"The text has changed! Save changes?", 0); GuiObject buttonArea = GuiDialog_getButtonArea (dirtyCloseDialog); int x = Gui_LEFT_DIALOG_SPACING, y = - Gui_BOTTOM_DIALOG_SPACING; GuiButton_createShown (buttonArea, x, x + buttonWidth, y - Gui_PUSHBUTTON_HEIGHT, y, L"Discard & Close", gui_button_cb_discardAndClose, this, 0); x += buttonWidth + buttonSpacing; GuiButton_createShown (buttonArea, x, x + buttonWidth, y - Gui_PUSHBUTTON_HEIGHT, y, L"Cancel", gui_button_cb_cancelClose, this, 0); x += buttonWidth + buttonSpacing; GuiButton_createShown (buttonArea, x, x + buttonWidth, y - Gui_PUSHBUTTON_HEIGHT, y, L"Save & Close", gui_button_cb_saveAndClose, this, 0); } GuiObject_show (dirtyCloseDialog); } else { closeDocument (this); } } static void menu_cb_undo (EDITOR_ARGS) { EDITOR_IAM (TextEditor); GuiText_undo (my textWidget); } static void menu_cb_redo (EDITOR_ARGS) { EDITOR_IAM (TextEditor); GuiText_redo (my textWidget); } static void menu_cb_cut (EDITOR_ARGS) { EDITOR_IAM (TextEditor); GuiText_cut (my textWidget); // use ((XmAnyCallbackStruct *) call) -> event -> xbutton. time } static void menu_cb_copy (EDITOR_ARGS) { EDITOR_IAM (TextEditor); GuiText_copy (my textWidget); } static void menu_cb_paste (EDITOR_ARGS) { EDITOR_IAM (TextEditor); GuiText_paste (my textWidget); } static void menu_cb_erase (EDITOR_ARGS) { EDITOR_IAM (TextEditor); GuiText_remove (my textWidget); } static bool getSelectedLines (TextEditor me, long *firstLine, long *lastLine) { long left, right; wchar_t *text = GuiText_getStringAndSelectionPosition (my textWidget, & left, & right); long textLength = wcslen (text); Melder_assert (left >= 0); Melder_assert (left <= right); Melder_assert (right <= textLength); long i = 0; *firstLine = 1; /* * Cycle through the text in order to see how many linefeeds we pass. */ for (; i < left; i ++) { if (text [i] == '\n') { (*firstLine) ++; } } if (left == right) return false; *lastLine = *firstLine; for (; i < right; i ++) { if (text [i] == '\n') { (*lastLine) ++; } } Melder_free (text); return true; } static wchar *theFindString = NULL, *theReplaceString = NULL; static void do_find (TextEditor me) { if (theFindString == NULL) return; // e.g. when the user does "Find again" before having done any "Find" long left, right; autostring text = GuiText_getStringAndSelectionPosition (my textWidget, & left, & right); wchar *location = wcsstr (& text [right], theFindString); if (location != NULL) { long index = location - text.peek(); GuiText_setSelection (my textWidget, index, index + wcslen (theFindString)); GuiText_scrollToSelection (my textWidget); #ifdef _WIN32 GuiObject_show (my d_windowForm); #endif } else { /* Try from the start of the document. */ location = wcsstr (text.peek(), theFindString); if (location != NULL) { long index = location - text.peek(); GuiText_setSelection (my textWidget, index, index + wcslen (theFindString)); GuiText_scrollToSelection (my textWidget); #ifdef _WIN32 GuiObject_show (my d_windowForm); #endif } else { Melder_beep (); } } } static void do_replace (TextEditor me) { if (theReplaceString == NULL) return; // e.g. when the user does "Replace again" before having done any "Replace" autostring selection = GuiText_getSelection (my textWidget); if (! Melder_wcsequ (selection.peek(), theFindString)) { do_find (me); return; } long left, right; autostring text = GuiText_getStringAndSelectionPosition (my textWidget, & left, & right); GuiText_replace (my textWidget, left, right, theReplaceString); GuiText_setSelection (my textWidget, left, left + wcslen (theReplaceString)); GuiText_scrollToSelection (my textWidget); #ifdef _WIN32 GuiObject_show (my d_windowForm); #endif } static void menu_cb_find (EDITOR_ARGS) { EDITOR_IAM (TextEditor); EDITOR_FORM (L"Find", 0) LABEL (L"", L"Find:") TEXTFIELD (L"findString", L"") EDITOR_OK if (theFindString != NULL) SET_STRING (L"findString", theFindString); EDITOR_DO Melder_free (theFindString); theFindString = Melder_wcsdup_f (GET_STRING (L"findString")); do_find (me); EDITOR_END } static void menu_cb_findAgain (EDITOR_ARGS) { EDITOR_IAM (TextEditor); do_find (me); } static void menu_cb_replace (EDITOR_ARGS) { EDITOR_IAM (TextEditor); EDITOR_FORM (L"Find", 0) LABEL (L"", L"This is a \"slow\" find-and-replace method;") LABEL (L"", L"if the selected text is identical to the Find string,") LABEL (L"", L"the selected text will be replaced by the Replace string;") LABEL (L"", L"otherwise, the next occurrence of the Find string will be selected.") LABEL (L"", L"So you typically need two clicks on Apply to get a text replaced.") LABEL (L"", L"Find:") TEXTFIELD (L"findString", L"") LABEL (L"", L"Replace with:") TEXTFIELD (L"replaceString", L"") EDITOR_OK if (theFindString != NULL) SET_STRING (L"findString", theFindString); if (theReplaceString != NULL) SET_STRING (L"replaceString", theReplaceString); EDITOR_DO Melder_free (theFindString); theFindString = Melder_wcsdup (GET_STRING (L"findString")); Melder_free (theReplaceString); theReplaceString = Melder_wcsdup (GET_STRING (L"replaceString")); do_replace (me); EDITOR_END } static void menu_cb_replaceAgain (EDITOR_ARGS) { EDITOR_IAM (TextEditor); do_replace (me); } static void menu_cb_whereAmI (EDITOR_ARGS) { EDITOR_IAM (TextEditor); long numberOfLinesLeft, numberOfLinesRight; if (! getSelectedLines (me, & numberOfLinesLeft, & numberOfLinesRight)) { Melder_information (L"The cursor is on line ", Melder_integer (numberOfLinesLeft), L"."); } else if (numberOfLinesLeft == numberOfLinesRight) { Melder_information (L"The selection is on line ", Melder_integer (numberOfLinesLeft), L"."); } else { Melder_information (L"The selection runs from line ", Melder_integer (numberOfLinesLeft), L" to line ", Melder_integer (numberOfLinesRight), L"."); } } static void menu_cb_goToLine (EDITOR_ARGS) { EDITOR_IAM (TextEditor); EDITOR_FORM (L"Go to line", 0) NATURAL (L"Line", L"1") EDITOR_OK long firstLine, lastLine; getSelectedLines (me, & firstLine, & lastLine); SET_INTEGER (L"Line", firstLine); EDITOR_DO autostring text = GuiText_getString (my textWidget); long lineToGo = GET_INTEGER (L"Line"), currentLine = 1; unsigned long left = 0, right = 0; if (lineToGo == 1) { for (; text [right] != '\n' && text [right] != '\0'; right ++) { } } else { for (; text [left] != '\0'; left ++) { if (text [left] == '\n') { currentLine ++; if (currentLine == lineToGo) { left ++; for (right = left; text [right] != '\n' && text [right] != '\0'; right ++) { } break; } } } } if (left == wcslen (text.peek())) { right = left; } else if (text [right] == '\n') { right ++; } GuiText_setSelection (my textWidget, left, right); GuiText_scrollToSelection (my textWidget); EDITOR_END } static void menu_cb_convertToCString (EDITOR_ARGS) { EDITOR_IAM (TextEditor); autostring text = GuiText_getString (my textWidget); wchar buffer [2] = L" "; const wchar *hex [16] = { L"0", L"1", L"2", L"3", L"4", L"5", L"6", L"7", L"8", L"9", L"A", L"B", L"C", L"D", L"E", L"F" }; MelderInfo_open (); MelderInfo_write1 (L"\""); for (wchar *p = & text [0]; *p != '\0'; p ++) { if (*p == '\n') { MelderInfo_write1 (L"\\n\"\n\""); } else if (*p == '\t') { MelderInfo_write1 (L" "); } else if (*p == '\"') { MelderInfo_write1 (L"\\\""); } else if (*p == '\\') { MelderInfo_write1 (L"\\\\"); } else if (*p < 0 || *p > 127) { uint32 kar = *p; if (kar <= 0xFFFF) { MelderInfo_write5 (L"\\u", hex [kar >> 12], hex [(kar >> 8) & 0x0000000F], hex [(kar >> 4) & 0x0000000F], hex [kar & 0x0000000F]); } else { MelderInfo_write9 (L"\\U", hex [kar >> 28], hex [(kar >> 24) & 0x0000000F], hex [(kar >> 20) & 0x0000000F], hex [(kar >> 16) & 0x0000000F], hex [(kar >> 12) & 0x0000000F], hex [(kar >> 8) & 0x0000000F], hex [(kar >> 4) & 0x0000000F], hex [kar & 0x0000000F]); } } else { buffer [0] = *p; MelderInfo_write1 (& buffer [0]); } } MelderInfo_write1 (L"\""); MelderInfo_close (); } /***** 'Font' menu *****/ static void updateSizeMenu (TextEditor me) { if (my fontSizeButton_10) GuiMenuItem_check (my fontSizeButton_10, my fontSize == 10); if (my fontSizeButton_12) GuiMenuItem_check (my fontSizeButton_12, my fontSize == 12); if (my fontSizeButton_14) GuiMenuItem_check (my fontSizeButton_14, my fontSize == 14); if (my fontSizeButton_18) GuiMenuItem_check (my fontSizeButton_18, my fontSize == 18); if (my fontSizeButton_24) GuiMenuItem_check (my fontSizeButton_24, my fontSize == 24); } static void setFontSize (TextEditor me, int fontSize) { GuiText_setFontSize (my textWidget, fontSize); theTextEditorFontSize = my fontSize = fontSize; updateSizeMenu (me); } static void menu_cb_10 (EDITOR_ARGS) { EDITOR_IAM (TextEditor); setFontSize (me, 10); } static void menu_cb_12 (EDITOR_ARGS) { EDITOR_IAM (TextEditor); setFontSize (me, 12); } static void menu_cb_14 (EDITOR_ARGS) { EDITOR_IAM (TextEditor); setFontSize (me, 14); } static void menu_cb_18 (EDITOR_ARGS) { EDITOR_IAM (TextEditor); setFontSize (me, 18); } static void menu_cb_24 (EDITOR_ARGS) { EDITOR_IAM (TextEditor); setFontSize (me, 24); } static void menu_cb_fontSize (EDITOR_ARGS) { EDITOR_IAM (TextEditor); EDITOR_FORM (L"Text window: Font size", 0) NATURAL (L"Font size (points)", L"12") EDITOR_OK SET_INTEGER (L"Font size", (long) my fontSize); EDITOR_DO setFontSize (me, GET_INTEGER (L"Font size")); EDITOR_END } void structTextEditor :: v_createMenus () { TextEditor_Parent :: v_createMenus (); if (v_fileBased ()) { Editor_addCommand (this, L"File", L"New", 'N', menu_cb_new); Editor_addCommand (this, L"File", L"Open...", 'O', menu_cb_open); Editor_addCommand (this, L"File", L"Reopen from disk", 0, menu_cb_reopen); } else { Editor_addCommand (this, L"File", L"Clear", 'N', menu_cb_clear); } Editor_addCommand (this, L"File", L"-- save --", 0, NULL); if (v_fileBased ()) { Editor_addCommand (this, L"File", L"Save", 'S', menu_cb_save); Editor_addCommand (this, L"File", L"Save as...", 0, menu_cb_saveAs); } else { Editor_addCommand (this, L"File", L"Save as...", 'S', menu_cb_saveAs); } Editor_addCommand (this, L"File", L"-- close --", 0, NULL); Editor_addCommand (this, L"Edit", L"Undo", 'Z', menu_cb_undo); Editor_addCommand (this, L"Edit", L"Redo", 'Y', menu_cb_redo); Editor_addCommand (this, L"Edit", L"-- cut copy paste --", 0, NULL); Editor_addCommand (this, L"Edit", L"Cut", 'X', menu_cb_cut); Editor_addCommand (this, L"Edit", L"Copy", 'C', menu_cb_copy); Editor_addCommand (this, L"Edit", L"Paste", 'V', menu_cb_paste); Editor_addCommand (this, L"Edit", L"Erase", 0, menu_cb_erase); Editor_addMenu (this, L"Search", 0); Editor_addCommand (this, L"Search", L"Find...", 'F', menu_cb_find); Editor_addCommand (this, L"Search", L"Find again", 'G', menu_cb_findAgain); Editor_addCommand (this, L"Search", L"Replace...", GuiMenu_SHIFT + 'F', menu_cb_replace); Editor_addCommand (this, L"Search", L"Replace again", GuiMenu_SHIFT + 'G', menu_cb_replaceAgain); Editor_addCommand (this, L"Search", L"-- line --", 0, NULL); Editor_addCommand (this, L"Search", L"Where am I?", 0, menu_cb_whereAmI); Editor_addCommand (this, L"Search", L"Go to line...", 'L', menu_cb_goToLine); Editor_addMenu (this, L"Convert", 0); Editor_addCommand (this, L"Convert", L"Convert to C string", 0, menu_cb_convertToCString); #if defined (macintosh) || defined (UNIX) || defined (_WIN32) Editor_addMenu (this, L"Font", 0); Editor_addCommand (this, L"Font", L"Font size...", 0, menu_cb_fontSize); fontSizeButton_10 = Editor_addCommand (this, L"Font", L"10", GuiMenu_CHECKBUTTON, menu_cb_10); fontSizeButton_12 = Editor_addCommand (this, L"Font", L"12", GuiMenu_CHECKBUTTON, menu_cb_12); fontSizeButton_14 = Editor_addCommand (this, L"Font", L"14", GuiMenu_CHECKBUTTON, menu_cb_14); fontSizeButton_18 = Editor_addCommand (this, L"Font", L"18", GuiMenu_CHECKBUTTON, menu_cb_18); fontSizeButton_24 = Editor_addCommand (this, L"Font", L"24", GuiMenu_CHECKBUTTON, menu_cb_24); #endif } static void gui_text_cb_change (I, GuiTextEvent event) { (void) event; iam (TextEditor); if (! my dirty) { my dirty = TRUE; my v_nameChanged (); } } void structTextEditor :: v_createChildren () { textWidget = GuiText_createShown (d_windowForm, 0, 0, Machine_getMenuBarHeight (), 0, GuiText_SCROLLED); GuiText_setChangeCallback (textWidget, gui_text_cb_change, this); GuiText_setUndoItem (textWidget, Editor_getMenuCommand (this, L"Edit", L"Undo") -> itemWidget); GuiText_setRedoItem (textWidget, Editor_getMenuCommand (this, L"Edit", L"Redo") -> itemWidget); } void structTextEditor :: init (GuiObject parent_, const wchar *initialText_) { Editor_init (this, parent_, 0, 0, 600, 400, NULL, NULL); setFontSize (this, theTextEditorFontSize); if (initialText_) { GuiText_setString (textWidget, initialText_); dirty = FALSE; // was set to TRUE in valueChanged callback Thing_setName (this, NULL); } if (theOpenTextEditors == NULL) { theOpenTextEditors = Collection_create (classTextEditor, 100); Collection_dontOwnItems (theOpenTextEditors); } if (theOpenTextEditors != NULL) { Collection_addItem (theOpenTextEditors, this); } } TextEditor TextEditor_create (GuiObject parent, const wchar *initialText) { try { autoTextEditor me = Thing_new (TextEditor); me.peek() -> init (parent, initialText); return me.transfer(); } catch (MelderError) { Melder_throw ("Text window not created."); } } void TextEditor_showOpen (TextEditor me) { cb_showOpen (Editor_getMenuCommand (me, L"File", L"Open..."), NULL, NULL, NULL); } /* End of file TextEditor.cpp */ sources_5316/sys/Printer.h0000644000176700017670000000322511747315535014352 0ustar paulpaul#ifndef _Printer_h_ #define _Printer_h_ /* Printer.h * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Graphics.h" /* When changing the following structure, update its initialization in Printer.c */ struct Printer { enum kGraphicsPostscript_spots spots; enum kGraphicsPostscript_paperSize paperSize; enum kGraphicsPostscript_orientation orientation; bool postScript, allowDirectPostScript; enum kGraphicsPostscript_fontChoiceStrategy fontChoiceStrategy; long resolution, paperWidth, paperHeight; double magnification; Graphics graphics; }; extern struct Printer thePrinter; #if defined (macintosh) || defined (_WIN32) int Printer_postScript_printf (void *stream, const char *format, ... ); #endif #ifdef _WIN32 HDC Printer_getDC (void); #endif int Printer_pageSetup (void); int Printer_postScriptSettings (void); int Printer_print (void (*draw) (I, Graphics g), I); void Printer_nextPage (void); void Printer_prefs (void); /* End of file Printer.h */ #endif sources_5316/sys/sendsocket.h0000644000176700017670000000206611617237435015071 0ustar paulpaul#ifndef _sendsocket_h_ #define _sendsocket_h_ /* sendsocket.h * * Copyright (C) 1999-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #ifdef __cplusplus extern "C" { #endif char * sendsocket (const char *hostNameAndPort, const char *command); /* * E.g. 'hostNameAndPort' could be "localhost:6667" or "fonsg19.hum.uva.nl:4711". */ #ifdef __cplusplus } #endif /* End of file sendsocket.h */ #endif sources_5316/sys/DataEditor.cpp0000644000176700017670000010626111753736742015312 0ustar paulpaul/* DataEditor.cpp * * Copyright (C) 1995-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define NAME_X 30 #define TEXT_X 250 #define BUTTON_X 250 #define LIST_Y (2 * Gui_TOP_DIALOG_SPACING + Gui_PUSHBUTTON_HEIGHT) #define EDITOR_WIDTH 820 #define EDITOR_HEIGHT (LIST_Y + kDataSubEditor_MAXNUM_ROWS * ROW_HEIGHT + 29 + Machine_getMenuBarHeight ()) #define ROW_HEIGHT 31 #define SCROLL_BAR_WIDTH Machine_getScrollBarWidth () #include "DataEditor.h" #include "EditorM.h" #include "Collection.h" #include "machine.h" static Data_Description Class_getDescription (ClassInfo table) { return ((Data) _Thing_dummyObject (table)) -> v_description (); } /*static const char * typeStrings [] = { "none", "byte", "int", "long", "ubyte", "ushort", "uint", "ulong", "bool", "float", "double", "fcomplex", "dcomplex", "enum", "lenum", "boolean", "question", "stringw", "lstringw", "struct", "widget", "object", "collection" };*/ static int stringLengths [] = { 0, 4, 6, 11, 3, 5, 10, 1, 15, 27, 35, 59, 33, 33, 8, 6, 60, 60 }; static VectorEditor VectorEditor_create (DataEditor root, const wchar *title, void *address, Data_Description description, long minimum, long maximum); static MatrixEditor MatrixEditor_create (DataEditor root, const wchar *title, void *address, Data_Description description, long min1, long max1, long min2, long max2); static StructEditor StructEditor_create (DataEditor root, const wchar *title, void *address, Data_Description description); static ClassEditor ClassEditor_create (DataEditor root, const wchar *title, void *address, Data_Description description); static inline const wchar * strip_d (const wchar *s) { return s && s [0] == 'd' && s [1] == '_' ? & s [2] : & s [0]; } /********** DataSubEditor **********/ Thing_implement (DataSubEditor, Editor, 0); void structDataSubEditor :: v_destroy () { for (int i = 1; i <= kDataSubEditor_MAXNUM_ROWS; i ++) Melder_free (d_fieldData [i]. history); if (d_root && d_root -> d_children) for (int i = d_root -> d_children -> size; i > 0; i --) if (d_root -> d_children -> item [i] == this) Collection_subtractItem (d_root -> d_children, i); DataSubEditor_Parent :: v_destroy (); } static void update (DataSubEditor me) { /* Hide all the existing widgets. */ for (int i = 1; i <= kDataSubEditor_MAXNUM_ROWS; i ++) { my d_fieldData [i]. address = NULL; my d_fieldData [i]. description = NULL; GuiObject_hide (my d_fieldData [i]. label); GuiObject_hide (my d_fieldData [i]. button); GuiObject_hide (my d_fieldData [i]. text); } my d_irow = 0; my v_showMembers (); } static Data_Description DataSubEditor_findNumberUse (DataSubEditor me, const wchar_t *number) { Data_Description structDescription, result; wchar_t string [100]; if (my classInfo == classMatrixEditor) return NULL; // no structs inside if (my classInfo == classVectorEditor) { if (my d_description -> type != structwa) return NULL; // no structs inside structDescription = * (Data_Description *) my d_description -> tagType; } else { /* StructEditor or ClassEditor or DataEditor. */ structDescription = my d_description; } swprintf (string, 100, L"%ls", number); if ((result = Data_Description_findNumberUse (structDescription, string)) != NULL) return result; swprintf (string, 100, L"%ls - 1", number); if ((result = Data_Description_findNumberUse (structDescription, string)) != NULL) return result; return NULL; } static void gui_button_cb_change (I, GuiButtonEvent event) { (void) event; iam (DataSubEditor); int i = 1; for (; i <= kDataSubEditor_MAXNUM_ROWS; i ++) { #if motif bool visible = XtIsManaged (my d_fieldData [i]. text); #elif gtk gboolean visible; g_object_get (G_OBJECT (my d_fieldData [i]. text), "visible", & visible, NULL); #elif ! useCarbon bool visible = false; // TODO #endif if (visible) { int type = my d_fieldData [i]. description -> type; wchar_t *text; if (type > maxsingletypewa) continue; text = GuiText_getString (my d_fieldData [i]. text); switch (type) { case bytewa: { signed char oldValue = * (signed char *) my d_fieldData [i]. address, newValue = wcstol (text, NULL, 10); if (newValue != oldValue) { Data_Description numberUse = DataSubEditor_findNumberUse (me, my d_fieldData [i]. description -> name); if (numberUse) { Melder_error_ ("Changing field \"", strip_d (my d_fieldData [i]. description -> name), "\" would damage the array \"", strip_d (numberUse -> name), "\"."); Melder_flushError (NULL); } else { * (signed char *) my d_fieldData [i]. address = newValue; } } } break; case intwa: { int oldValue = * (int *) my d_fieldData [i]. address, newValue = wcstol (text, NULL, 10); if (newValue != oldValue) { Data_Description numberUse = DataSubEditor_findNumberUse (me, my d_fieldData [i]. description -> name); if (numberUse) { Melder_error_ ("Changing field \"", strip_d (my d_fieldData [i]. description -> name), "\" would damage the array \"", strip_d (numberUse -> name), "\"."); Melder_flushError (NULL); } else { * (int *) my d_fieldData [i]. address = newValue; } } } break; case longwa: { long oldValue = * (long *) my d_fieldData [i]. address, newValue = wcstol (text, NULL, 10); if (newValue != oldValue) { Data_Description numberUse = DataSubEditor_findNumberUse (me, my d_fieldData [i]. description -> name); if (numberUse) { Melder_error_ ("Changing field \"", strip_d (my d_fieldData [i]. description -> name), "\" would damage the array \"", strip_d (numberUse -> name), "\"."); Melder_flushError (NULL); } else { * (long *) my d_fieldData [i]. address = newValue; } } } break; case ubytewa: { * (unsigned char *) my d_fieldData [i]. address = wcstoul (text, NULL, 10); } break; case uintwa: { * (unsigned int *) my d_fieldData [i]. address = wcstoul (text, NULL, 10); } break; case ulongwa: { * (unsigned long *) my d_fieldData [i]. address = wcstoul (text, NULL, 10); } break; case boolwa: { * (bool *) my d_fieldData [i]. address = wcstol (text, NULL, 10); } break; case floatwa: { * (double *) my d_fieldData [i]. address = Melder_atof (text); } break; case doublewa: { * (double *) my d_fieldData [i]. address = Melder_atof (text); } break; case fcomplexwa: { fcomplex *x = (fcomplex *) my d_fieldData [i]. address; swscanf (text, L"%f + %f i", & x -> re, & x -> im); } break; case dcomplexwa: { dcomplex *x = (dcomplex *) my d_fieldData [i]. address; swscanf (text, L"%lf + %lf i", & x -> re, & x -> im); } break; case enumwa: { if (wcslen (text) < 3) goto error; text [wcslen (text) - 1] = '\0'; // remove trailing ">" int value = ((int (*) (const wchar_t *)) (my d_fieldData [i]. description -> tagType)) (text + 1); // skip leading "<" if (value < 0) goto error; * (signed char *) my d_fieldData [i]. address = value; } break; case lenumwa: { if (wcslen (text) < 3) goto error; text [wcslen (text) - 1] = '\0'; // remove trailing ">" int value = ((int (*) (const wchar_t *)) (my d_fieldData [i]. description -> tagType)) (text + 1); // skip leading "<" if (value < 0) goto error; * (signed short *) my d_fieldData [i]. address = value; } break; case booleanwa: { int value = wcsnequ (text, L"", 6) ? 1 : wcsnequ (text, L"", 7) ? 0 : -1; if (value < 0) goto error; * (signed char *) my d_fieldData [i]. address = value; } break; case questionwa: { int value = wcsnequ (text, L"", 5) ? 1 : wcsnequ (text, L"", 4) ? 0 : -1; if (value < 0) goto error; * (signed char *) my d_fieldData [i]. address = value; } break; case stringwa: case lstringwa: { wchar *old = * (wchar_t **) my d_fieldData [i]. address; Melder_free (old); * (wchar **) my d_fieldData [i]. address = Melder_wcsdup_f (text); } break; default: break; } Melder_free (text); } } /* Several collaborators have to be notified of this change: * 1. The owner (creator) of our root DataEditor: so that she can notify other editors, if any. * 2. All our sibling DataSubEditors. */ my d_root -> broadcastDataChanged (); update (me); for (int i = 1; i <= my d_root -> d_children -> size; i ++) { DataSubEditor subeditor = (DataSubEditor) my d_root -> d_children -> item [i]; if (subeditor != me) update (subeditor); } return; error: Melder_error_ ("Edit field \"", strip_d (my d_fieldData [i]. description -> name), "\" or click \"Cancel\"."); Melder_flushError (NULL); } static void gui_button_cb_cancel (I, GuiButtonEvent event) { (void) event; iam (DataSubEditor); update (me); } static void gui_cb_scroll (GUI_ARGS) { GUI_IAM (DataSubEditor); int value, slider, incr, pincr; #if motif XmScrollBarGetValues (w, & value, & slider, & incr, & pincr); #endif my d_topField = value + 1; update (me); } static void gui_button_cb_open (I, GuiButtonEvent event) { iam (DataSubEditor); int ifield = 0; static MelderString name = { 0 }; MelderString_empty (& name); /* Identify the pressed button; it must be one of those created in the list. */ for (int i = 1; i <= kDataSubEditor_MAXNUM_ROWS; i ++) if (my d_fieldData [i]. button == event -> button) { ifield = i; break; } Melder_assert (ifield != 0); /* Launch the appropriate subeditor. */ DataSubEditor_FieldData fieldData = & my d_fieldData [ifield]; if (! fieldData -> description) { Melder_casual ("Not yet implemented."); return; /* Not yet implemented. */ } if (fieldData -> description -> rank == 1 || fieldData -> description -> rank == 3 || fieldData -> description -> rank < 0) { MelderString_append (& name, fieldData -> history, L". ", strip_d (fieldData -> description -> name), L" [", Melder_integer (fieldData -> minimum), L"..", Melder_integer (fieldData -> maximum), L"]"); VectorEditor_create (my d_root, name.string, fieldData -> address, fieldData -> description, fieldData -> minimum, fieldData -> maximum); } else if (fieldData -> description -> rank == 2) { MelderString_append (& name, fieldData -> history, L". ", strip_d (fieldData -> description -> name), L" [", Melder_integer (fieldData -> minimum), L"..", Melder_integer (fieldData -> maximum), L"]"); MelderString_append (& name, L" [", Melder_integer (fieldData -> min2), L"..", Melder_integer (fieldData -> max2), L"]"); MatrixEditor_create (my d_root, name.string, fieldData -> address, fieldData -> description, fieldData -> minimum, fieldData -> maximum, fieldData -> min2, fieldData -> max2); } else if (fieldData -> description -> type == structwa) { MelderString_append (& name, fieldData -> history, L". ", strip_d (fieldData -> description -> name)); StructEditor_create (my d_root, name.string, fieldData -> address, * (Data_Description *) fieldData -> description -> tagType); } else if (fieldData -> description -> type == objectwa || fieldData -> description -> type == collectionwa) { MelderString_append (& name, fieldData -> history, L". ", strip_d (fieldData -> description -> name)); ClassEditor_create (my d_root, name.string, fieldData -> address, Class_getDescription ((ClassInfo) fieldData -> description -> tagType)); } else /*if (fieldData -> description -> type == inheritwa)*/ { ClassEditor_create (my d_root, fieldData -> history, fieldData -> address, fieldData -> description); /* } else { Melder_casual ("Strange editor \"%s\" required (type %d, rank %d).", strip_d (fieldData -> description -> name), fieldData -> description -> type, fieldData -> description -> rank);*/ } } void structDataSubEditor :: v_createChildren () { int x = Gui_LEFT_DIALOG_SPACING, y = Gui_TOP_DIALOG_SPACING + Machine_getMenuBarHeight (), buttonWidth = 120; #if motif GuiButton_createShown (d_windowForm, x, x + buttonWidth, y, Gui_AUTOMATIC, L"Change", gui_button_cb_change, this, 0); x += buttonWidth + Gui_HORIZONTAL_DIALOG_SPACING; GuiButton_createShown (d_windowForm, x, x + buttonWidth, y, Gui_AUTOMATIC, L"Cancel", gui_button_cb_cancel, this, 0); GuiObject scrolledWindow = XmCreateScrolledWindow (d_windowForm, "list", NULL, 0); XtVaSetValues (scrolledWindow, XmNrightAttachment, XmATTACH_FORM, XmNtopAttachment, XmATTACH_FORM, XmNtopOffset, LIST_Y + Machine_getMenuBarHeight (), XmNbottomAttachment, XmATTACH_FORM, XmNleftAttachment, XmATTACH_FORM, NULL); d_scrollBar = XtVaCreateManagedWidget ("verticalScrollBar", xmScrollBarWidgetClass, scrolledWindow, XmNheight, SCROLL_BAR_WIDTH, XmNminimum, 0, XmNmaximum, d_numberOfFields, XmNvalue, 0, XmNsliderSize, d_numberOfFields < kDataSubEditor_MAXNUM_ROWS ? d_numberOfFields : kDataSubEditor_MAXNUM_ROWS, XmNincrement, 1, XmNpageIncrement, kDataSubEditor_MAXNUM_ROWS - 1, NULL); XtVaSetValues (scrolledWindow, XmNverticalScrollBar, d_scrollBar, NULL); GuiObject_show (scrolledWindow); XtAddCallback (d_scrollBar, XmNvalueChangedCallback, gui_cb_scroll, (XtPointer) this); XtAddCallback (d_scrollBar, XmNdragCallback, gui_cb_scroll, (XtPointer) this); GuiObject form = XmCreateForm (scrolledWindow, "list", NULL, 0); #elif gtk GuiObject outerBox = gtk_vbox_new (0, 0); GuiObject buttonBox = gtk_hbutton_box_new (); gtk_button_box_set_layout (GTK_BUTTON_BOX (buttonBox), GTK_BUTTONBOX_START); gtk_box_pack_start (GTK_BOX (outerBox), GTK_WIDGET (buttonBox), 0, 0, 3); GuiButton_createShown (buttonBox, x, x + buttonWidth, y, Gui_AUTOMATIC, L"Change", gui_button_cb_change, this, 0); x += buttonWidth + Gui_HORIZONTAL_DIALOG_SPACING; GuiButton_createShown (buttonBox, x, x + buttonWidth, y, Gui_AUTOMATIC, L"Cancel", gui_button_cb_cancel, this, 0); GuiObject scrolledWindow = gtk_scrolled_window_new (NULL, NULL); GuiObject form = gtk_vbox_new (0, 3); gtk_scrolled_window_add_with_viewport (GTK_SCROLLED_WINDOW (scrolledWindow), GTK_WIDGET (form)); gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolledWindow), GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC); gtk_box_pack_start (GTK_BOX (outerBox), GTK_WIDGET (scrolledWindow), 1, 1, 3); gtk_container_add (GTK_CONTAINER (d_windowForm), GTK_WIDGET (outerBox)); GuiObject_show (outerBox); GuiObject_show (buttonBox); GuiObject_show (scrolledWindow); #elif ! useCarbon GuiObject form = NULL; // TODO #endif for (int i = 1; i <= kDataSubEditor_MAXNUM_ROWS; i ++) { y = Gui_TOP_DIALOG_SPACING + (i - 1) * ROW_HEIGHT; d_fieldData [i]. label = GuiLabel_create (form, 0, 200, y, Gui_AUTOMATIC, L"label", 0); // no fixed x value: sometimes indent d_fieldData [i]. button = GuiButton_create (form, BUTTON_X, BUTTON_X + buttonWidth, y, Gui_AUTOMATIC, L"Open", gui_button_cb_open, this, 0); d_fieldData [i]. text = GuiText_create (form, TEXT_X, 0, y, Gui_AUTOMATIC, 0); } GuiObject_show (form); } static void menu_cb_help (EDITOR_ARGS) { EDITOR_IAM (DataSubEditor); Melder_help (L"Inspect"); } void structDataSubEditor :: v_createHelpMenuItems (EditorMenu menu) { DataSubEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"DataEditor help", '?', menu_cb_help); } static void DataSubEditor_init (DataSubEditor me, DataEditor root, const wchar_t *title, void *address, Data_Description description) { my d_root = root; if (me != root) { Collection_addItem (root -> d_children, me); } my d_address = address; my d_description = description; my d_topField = 1; my d_numberOfFields = my v_countFields (); Editor_init (me, root -> d_windowParent, 0, 0, EDITOR_WIDTH, EDITOR_HEIGHT, title, NULL); therror update (me); } /********** StructEditor **********/ Thing_implement (StructEditor, DataSubEditor, 0); long structStructEditor :: v_countFields () { return Data_Description_countMembers (d_description); } static const wchar * singleTypeToText (void *address, int type, void *tagType, MelderString *buffer) { switch (type) { case bytewa: MelderString_append (buffer, Melder_integer (* (signed char *) address)); break; case intwa: MelderString_append (buffer, Melder_integer (* (int *) address)); break; case longwa: MelderString_append (buffer, Melder_integer (* (long *) address)); break; case ubytewa: MelderString_append (buffer, Melder_integer (* (unsigned char *) address)); break; case uintwa: MelderString_append (buffer, Melder_integer (* (unsigned int *) address)); break; case ulongwa: MelderString_append (buffer, Melder_integer (* (unsigned long *) address)); break; case boolwa: MelderString_append (buffer, Melder_integer (* (bool *) address)); break; case floatwa: MelderString_append (buffer, Melder_single (* (double *) address)); break; case doublewa: MelderString_append (buffer, Melder_double (* (double *) address)); break; case fcomplexwa: { fcomplex value = * (fcomplex *) address; MelderString_append (buffer, Melder_single (value. re), L" + ", Melder_single (value. im), L" i"); } break; case dcomplexwa: { dcomplex value = * (dcomplex *) address; MelderString_append (buffer, Melder_double (value. re), L" + ", Melder_double (value. im), L" i"); } break; case enumwa: MelderString_append (buffer, L"<", ((const wchar_t * (*) (int)) tagType) (* (signed char *) address), L">"); break; case lenumwa: MelderString_append (buffer, L"<", ((const wchar_t * (*) (int)) tagType) (* (signed short *) address), L">"); break; case booleanwa: MelderString_append (buffer, * (signed char *) address ? L"" : L""); break; case questionwa: MelderString_append (buffer, * (signed char *) address ? L"" : L"" ); break; case stringwa: case lstringwa: { wchar_t *string = * (wchar_t **) address; if (string == NULL) { MelderString_empty (buffer); return buffer -> string; } // convert NULL string to empty string return string; // may be much longer than the usual size of 'buffer' } break; default: return L"(unknown)"; } return buffer -> string; // Mind the special return for strings above. } static void showStructMember ( void *structAddress, /* The address of (the first member of) the struct. */ Data_Description structDescription, /* The description of (the first member of) the struct. */ Data_Description memberDescription, /* The description of the current member. */ DataSubEditor_FieldData fieldData, /* The widgets in which to show the info about the current member. */ wchar *history) { int type = memberDescription -> type, rank = memberDescription -> rank, isSingleType = type <= maxsingletypewa && rank == 0; unsigned char *memberAddress = (unsigned char *) structAddress + memberDescription -> offset; static MelderString buffer = { 0 }; MelderString_empty (& buffer); if (type == inheritwa) { MelderString_append (& buffer, L"Class part \"", memberDescription -> name, L"\":"); } else { MelderString_append (& buffer, strip_d (memberDescription -> name), rank == 0 ? L"" : rank == 1 || rank == 3 || rank < 0 ? L" [ ]" : L" [ ] [ ]"); } GuiLabel_setString (fieldData -> label, buffer.string); GuiObject_move (fieldData -> label, type == inheritwa ? 0 : NAME_X, Gui_AUTOMATIC); GuiObject_show (fieldData -> label); /* Show the value (for a single type) or a button (for a composite type). */ if (isSingleType) { #if motif XtVaSetValues (fieldData -> text, XmNcolumns, stringLengths [type], NULL); // TODO: change to GuiObject_size #endif MelderString_empty (& buffer); const wchar_t *text = singleTypeToText (memberAddress, type, memberDescription -> tagType, & buffer); GuiText_setString (fieldData -> text, text); GuiObject_show (fieldData -> text); fieldData -> address = memberAddress; fieldData -> description = memberDescription; fieldData -> rank = 0; } else if (rank == 1) { void *arrayAddress = * (void **) memberAddress; long minimum, maximum; if (arrayAddress == NULL) return; /* No button for empty fields. */ Data_Description_evaluateInteger (structAddress, structDescription, memberDescription -> min1, & minimum); Data_Description_evaluateInteger (structAddress, structDescription, memberDescription -> max1, & maximum); if (maximum < minimum) return; /* No button if no elements. */ fieldData -> address = arrayAddress; /* Indirect. */ fieldData -> description = memberDescription; fieldData -> minimum = minimum; /* Normally 1. */ fieldData -> maximum = maximum; fieldData -> rank = 1; Melder_free (fieldData -> history); fieldData -> history = Melder_wcsdup_f (history); GuiObject_show (fieldData -> button); } else if (rank < 0) { /* * This represents an in-line array. */ long maximum; /* But: capacity = - rank */ Data_Description_evaluateInteger (structAddress, structDescription, memberDescription -> max1, & maximum); if (-- maximum < 0) return; /* Subtract one for zero-based array; no button if no elements. */ fieldData -> address = memberAddress; /* Direct. */ fieldData -> description = memberDescription; fieldData -> minimum = 0; /* In-line arrays start with index 0. */ fieldData -> maximum = maximum; /* Probably between -1 and capacity - 1. */ fieldData -> rank = rank; Melder_free (fieldData -> history); fieldData -> history = Melder_wcsdup_f (history); GuiObject_show (fieldData -> button); } else if (rank == 3) { /* * This represents an in-line set. */ fieldData -> address = memberAddress; /* Direct. */ fieldData -> description = memberDescription; fieldData -> minimum = wcsequ (((const wchar_t * (*) (int)) memberDescription -> min1) (0), L"_") ? 1 : 0; fieldData -> maximum = ((int (*) (const wchar_t *)) memberDescription -> max1) (L"\n"); fieldData -> rank = rank; Melder_free (fieldData -> history); fieldData -> history = Melder_wcsdup_f (history); GuiObject_show (fieldData -> button); } else if (rank == 2) { void *arrayAddress = * (void **) memberAddress; long min1, max1, min2, max2; if (arrayAddress == NULL) return; /* No button for empty fields. */ Data_Description_evaluateInteger (structAddress, structDescription, memberDescription -> min1, & min1); Data_Description_evaluateInteger (structAddress, structDescription, memberDescription -> max1, & max1); Data_Description_evaluateInteger (structAddress, structDescription, memberDescription -> min2, & min2); Data_Description_evaluateInteger (structAddress, structDescription, memberDescription -> max2, & max2); if (max1 < min1 || max2 < min2) return; /* No button if no elements. */ fieldData -> address = arrayAddress; /* Indirect. */ fieldData -> description = memberDescription; fieldData -> minimum = min1; /* Normally 1. */ fieldData -> maximum = max1; fieldData -> min2 = min2; fieldData -> max2 = max2; fieldData -> rank = 2; Melder_free (fieldData -> history); fieldData -> history = Melder_wcsdup_f (history); GuiObject_show (fieldData -> button); } else if (type == structwa) { /* In-line struct. */ fieldData -> address = memberAddress; /* Direct. */ fieldData -> description = memberDescription; fieldData -> rank = 0; Melder_free (fieldData -> history); fieldData -> history = Melder_wcsdup_f (history); GuiObject_show (fieldData -> button); } else if (type == objectwa || type == collectionwa) { fieldData -> address = * (Data *) memberAddress; /* Indirect. */ if (! fieldData -> address) return; /* No button if no object. */ fieldData -> description = memberDescription; fieldData -> rank = 0; Melder_free (fieldData -> history); fieldData -> history = Melder_wcsdup_f (history); GuiObject_show (fieldData -> button); } } static void showStructMembers (DataSubEditor me, void *structAddress, Data_Description structDescription, int fromMember, wchar *history) { int i = 1; Data_Description memberDescription = structDescription; for (; i < fromMember && memberDescription -> name != NULL; i ++, memberDescription ++) (void) 0; for (; memberDescription -> name != NULL; memberDescription ++) { if (++ my d_irow > kDataSubEditor_MAXNUM_ROWS) return; showStructMember (structAddress, structDescription, memberDescription, & my d_fieldData [my d_irow], history); } } void structStructEditor :: v_showMembers () { showStructMembers (this, d_address, d_description, d_topField, name); } static void StructEditor_init (StructEditor me, DataEditor root, const wchar_t *title, void *address, Data_Description description) { DataSubEditor_init (me, root, title, address, description); } static StructEditor StructEditor_create (DataEditor root, const wchar_t *title, void *address, Data_Description description) { try { autoStructEditor me = Thing_new (StructEditor); StructEditor_init (me.peek(), root, title, address, description); return me.transfer(); } catch (MelderError) { Melder_throw ("Struct inspector window not created."); } } /********** VectorEditor **********/ Thing_implement (VectorEditor, DataSubEditor, 0); long structVectorEditor :: v_countFields () { long numberOfElements = d_maximum - d_minimum + 1; if (d_description -> type == structwa) return numberOfElements * (Data_Description_countMembers (* (Data_Description *) d_description -> tagType) + 1); else return numberOfElements; } void structVectorEditor :: v_showMembers () { int type = d_description -> type, isSingleType = type <= maxsingletypewa; int elementSize = type == structwa ? Data_Description_countMembers (* (Data_Description *) d_description -> tagType) + 1 : 1; long firstElement = d_minimum + (d_topField - 1) / elementSize; for (long ielement = firstElement; ielement <= d_maximum; ielement ++) { unsigned char *elementAddress = (unsigned char *) d_address + ielement * d_description -> size; static MelderString buffer = { 0 }; MelderString_empty (& buffer); int skip = ielement == firstElement ? (d_topField - 1) % elementSize : 0; if (++ d_irow > kDataSubEditor_MAXNUM_ROWS) return; DataSubEditor_FieldData fieldData = & d_fieldData [d_irow]; if (isSingleType) { MelderString_append (& buffer, strip_d (d_description -> name), L" [", d_description -> rank == 3 ? ((const wchar_t * (*) (int)) d_description -> min1) (ielement) : Melder_integer (ielement), L"]"); GuiObject_move (fieldData -> label, 0, Gui_AUTOMATIC); GuiLabel_setString (fieldData -> label, buffer.string); GuiObject_show (fieldData -> label); MelderString_empty (& buffer); const wchar_t *text = singleTypeToText (elementAddress, type, d_description -> tagType, & buffer); #if motif XtVaSetValues (fieldData -> text, XmNcolumns, stringLengths [type], NULL); // TODO: change to GuiObject_size #endif GuiText_setString (fieldData -> text, text); GuiObject_show (fieldData -> text); fieldData -> address = elementAddress; fieldData -> description = d_description; } else if (type == structwa) { static MelderString history = { 0 }; MelderString_copy (& history, name); /* Replace things like [1..100] by things like [19]. */ if (history.string [history.length - 1] == ']') { wchar_t *openingBracket = wcsrchr (history.string, '['); Melder_assert (openingBracket != NULL); * openingBracket = '\0'; history.length = openingBracket - history.string; } MelderString_append (& history, L"[", Melder_integer (ielement), L"]"); if (skip) { d_irow --; } else { MelderString_append (& buffer, strip_d (d_description -> name), L" [", Melder_integer (ielement), L"]: ---------------------------"); GuiObject_move (fieldData -> label, 0, Gui_AUTOMATIC); GuiLabel_setString (fieldData -> label, buffer.string); GuiObject_show (fieldData -> label); } showStructMembers (this, elementAddress, * (Data_Description *) d_description -> tagType, skip, history.string); } else if (type == objectwa) { static MelderString history = { 0 }; MelderString_copy (& history, name); if (history.string [history.length - 1] == ']') { wchar_t *openingBracket = wcsrchr (history.string, '['); Melder_assert (openingBracket != NULL); * openingBracket = '\0'; history.length = openingBracket - history.string; } MelderString_append (& history, L"[", Melder_integer (ielement), L"]"); MelderString_append (& buffer, strip_d (d_description -> name), L" [", Melder_integer (ielement), L"]"); GuiObject_move (fieldData -> label, 0, Gui_AUTOMATIC); GuiLabel_setString (fieldData -> label, buffer.string); GuiObject_show (fieldData -> label); Data object = * (Data *) elementAddress; if (object == NULL) return; // no button if no object if (! Class_getDescription (object -> classInfo)) return; // no button if no description for this class fieldData -> address = object; fieldData -> description = Class_getDescription (object -> classInfo); fieldData -> rank = 0; if (fieldData -> history) Melder_free (fieldData -> history); fieldData -> history = Melder_wcsdup_f (history.string); GuiObject_show (fieldData -> button); } } } static VectorEditor VectorEditor_create (DataEditor root, const wchar_t *title, void *address, Data_Description description, long minimum, long maximum) { try { autoVectorEditor me = Thing_new (VectorEditor); my d_minimum = minimum; my d_maximum = maximum; DataSubEditor_init (me.peek(), root, title, address, description); return me.transfer(); } catch (MelderError) { Melder_throw ("Vector inspector window not created."); } } /********** MatrixEditor **********/ Thing_implement (MatrixEditor, DataSubEditor, 0); long structMatrixEditor :: v_countFields () { long numberOfElements = (d_maximum - d_minimum + 1) * (d_max2 - d_min2 + 1); if (d_description -> type == structwa) return numberOfElements * (Data_Description_countMembers (* (Data_Description *) d_description -> tagType) + 1); else return numberOfElements; } void structMatrixEditor :: v_showMembers () { int type = d_description -> type, isSingleType = type <= maxsingletypewa; int elementSize = type == structwa ? Data_Description_countMembers (* (Data_Description *) d_description -> tagType) + 1 : 1; int rowSize = elementSize * (d_max2 - d_min2 + 1); long firstRow = d_minimum + (d_topField - 1) / rowSize; long firstColumn = d_min2 + (d_topField - 1 - (firstRow - d_minimum) * rowSize) / elementSize; for (long irow = firstRow; irow <= d_maximum; irow ++) for (long icolumn = irow == firstRow ? firstColumn : d_min2; icolumn <= d_max2; icolumn ++) { unsigned char *elementAddress = * ((unsigned char **) d_address + irow) + icolumn * d_description -> size; if (++ d_irow > kDataSubEditor_MAXNUM_ROWS) return; DataSubEditor_FieldData fieldData = & d_fieldData [d_irow]; if (isSingleType) { static MelderString buffer = { 0 }; MelderString_empty (& buffer); MelderString_append (& buffer, strip_d (d_description -> name), L" [", Melder_integer (irow), L"] [", Melder_integer (icolumn), L"]"); GuiObject_move (fieldData -> label, 0, Gui_AUTOMATIC); GuiLabel_setString (fieldData -> label, buffer.string); GuiObject_show (fieldData -> label); MelderString_empty (& buffer); const wchar_t *text = singleTypeToText (elementAddress, type, d_description -> tagType, & buffer); #if motif XtVaSetValues (fieldData -> text, XmNcolumns, stringLengths [type], NULL); // TODO: change to GuiObject_size #endif GuiText_setString (fieldData -> text, text); GuiObject_show (fieldData -> text); fieldData -> address = elementAddress; fieldData -> description = d_description; } } } static MatrixEditor MatrixEditor_create (DataEditor root, const wchar_t *title, void *address, Data_Description description, long min1, long max1, long min2, long max2) { try { autoMatrixEditor me = Thing_new (MatrixEditor); my d_minimum = min1; my d_maximum = max1; my d_min2 = min2; my d_max2 = max2; DataSubEditor_init (me.peek(), root, title, address, description); return me.transfer(); } catch (MelderError) { Melder_throw ("Matrix inspector window not created."); } } /********** ClassEditor **********/ Thing_implement (ClassEditor, StructEditor, 0); static void ClassEditor_showMembers_recursive (ClassEditor me, ClassInfo klas) { ClassInfo parentClass = klas -> parent; Data_Description description = Class_getDescription (klas); int classFieldsTraversed = 0; while (Class_getDescription (parentClass) == description) parentClass = parentClass -> parent; if (parentClass != classData) { ClassEditor_showMembers_recursive (me, parentClass); classFieldsTraversed = Data_Description_countMembers (Class_getDescription (parentClass)); Melder_casual ("ClassEditor_showMembers_recursive: classFieldsTraversed = %d", classFieldsTraversed); } showStructMembers (me, my d_address, description, my d_irow ? 1 : my d_topField - classFieldsTraversed, my name); } void structClassEditor :: v_showMembers () { ClassEditor_showMembers_recursive (this, ((Data) d_address) -> classInfo); } static void ClassEditor_init (ClassEditor me, DataEditor root, const wchar_t *title, void *address, Data_Description description) { if (description == NULL) Melder_throw ("Class ", Thing_className ((Thing) address), " cannot be inspected."); StructEditor_init (me, root, title, address, description); } static ClassEditor ClassEditor_create (DataEditor root, const wchar_t *title, void *address, Data_Description description) { try { autoClassEditor me = Thing_new (ClassEditor); ClassEditor_init (me.peek(), root, title, address, description); return me.transfer(); } catch (MelderError) { Melder_throw ("Class inspector window not created."); } } /********** DataEditor **********/ Thing_implement (DataEditor, ClassEditor, 0); void structDataEditor :: v_destroy () { /* Tell my children not to notify me when they die. */ for (int i = 1; i <= d_children -> size; i ++) { DataSubEditor child = (DataSubEditor) d_children -> item [i]; child -> d_root = NULL; } forget (d_children); DataEditor_Parent :: v_destroy (); } void structDataEditor :: v_dataChanged () { /* * Someone else changed our data. * We know that the top-level data is still accessible. */ update (this); /* * But all structure may have changed, * so that we do not know if any of the subeditors contain valid data. */ for (int i = d_children -> size; i >= 1; i --) { DataSubEditor subeditor = (DataSubEditor) d_children -> item [i]; Collection_subtractItem (d_children, i); forget (subeditor); } } DataEditor DataEditor_create (GuiObject parent, const wchar *title, Any data) { try { ClassInfo klas = ((Thing) data) -> classInfo; if (Class_getDescription (klas) == NULL) Melder_throw ("Class ", klas -> className, " cannot be inspected."); autoDataEditor me = Thing_new (DataEditor); my d_children = Collection_create (classDataSubEditor, 10); therror my d_windowParent = parent; ClassEditor_init (me.peek(), me.peek(), title, data, Class_getDescription (klas)); return me.transfer(); } catch (MelderError) { Melder_throw ("Inspector window not created."); } } /* End of file DataEditor.cpp */ sources_5316/sys/InfoEditor.h0000644000176700017670000000210511621124713014750 0ustar paulpaul#ifndef _InfoEditor_h_ #define _InfoEditor_h_ /* InfoEditor.h * * Copyright (C) 2004-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "TextEditor.h" Thing_define (InfoEditor, TextEditor) { // overridden methods: virtual void v_destroy (); virtual bool v_scriptable () { return false; } virtual bool v_fileBased () { return false; } virtual void v_clear (); }; /* End of file InfoEditor.h */ #endif sources_5316/sys/Strings_def.h0000644000176700017670000000220211622364442015161 0ustar paulpaul/* Strings_def.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Strings oo_DEFINE_CLASS (Strings, Data) oo_LONG (numberOfStrings) oo_STRING_VECTOR (strings, numberOfStrings) #if oo_DECLARING // overridden methods: virtual void v_info (); virtual bool v_hasGetVectorStr () { return true; } virtual const wchar * v_getVectorStr (long icol); #endif oo_END_CLASS (Strings) #undef ooSTRUCT /* End of file Strings_def.h */ sources_5316/sys/UiFile.cpp0000644000176700017670000001350411662422627014435 0ustar paulpaul/* UiFile.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "UiP.h" #include "Editor.h" Thing_define (UiFile, Thing) { // new data: public: EditorCommand command; GuiObject parent; structMelderFile file; const wchar *invokingButtonTitle, *helpTitle; void (*okCallback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure); void *okClosure; int shiftKeyPressed; // overridden methods: virtual void v_destroy (); }; void structUiFile :: v_destroy () { Melder_free (invokingButtonTitle); UiFile_Parent :: v_destroy (); } Thing_implement (UiFile, Thing, 0); static void UiFile_init (I, GuiObject parent, const wchar_t *title) { iam (UiFile); my parent = parent; Thing_setName (me, title); } MelderFile UiFile_getFile (I) { iam (UiFile); return & my file; } /********** READING A FILE **********/ Thing_define (UiInfile, UiFile) { // new data: public: bool allowMultipleFiles; }; Thing_implement (UiInfile, UiFile, 0); UiForm UiInfile_create (GuiObject parent, const wchar *title, void (*okCallback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *), void *okClosure, const wchar *invokingButtonTitle, const wchar *helpTitle, bool allowMultipleFiles) { UiInfile me = Thing_new (UiInfile); my okCallback = okCallback; my okClosure = okClosure; my invokingButtonTitle = Melder_wcsdup (invokingButtonTitle); my helpTitle = helpTitle; my allowMultipleFiles = allowMultipleFiles; UiFile_init (me, parent, title); return (UiForm) me; } void UiInfile_do (I) { iam (UiInfile); try { autoSortedSetOfString infileNames = GuiFileSelect_getInfileNames (my parent, my name, my allowMultipleFiles); for (long ifile = 1; ifile <= infileNames -> size; ifile ++) { SimpleString infileName = (SimpleString) infileNames -> item [ifile]; Melder_pathToFile (infileName -> string, & my file); UiHistory_write (L"\n"); UiHistory_write (my invokingButtonTitle); UiHistory_write (L" "); UiHistory_write (infileName -> string); structMelderFile file; MelderFile_copy (& my file, & file); try { my okCallback ((UiForm) me, NULL, NULL, my invokingButtonTitle, false, my okClosure); } catch (MelderError) { Melder_throw ("File ", & file, " not finished."); } } } catch (MelderError) { Melder_flushError (NULL); } } /********** WRITING A FILE **********/ Thing_define (UiOutfile, UiFile) { // new data: public: bool (*allowExecutionHook) (void *closure); void *allowExecutionClosure; // I am owner (see destroy) }; Thing_implement (UiOutfile, UiFile, 0); UiForm UiOutfile_create (GuiObject parent, const wchar_t *title, void (*okCallback) (UiForm, const wchar *, Interpreter, const wchar *, bool, void *), void *okClosure, const wchar *invokingButtonTitle, const wchar_t *helpTitle) { UiOutfile me = Thing_new (UiOutfile); my okCallback = okCallback; my okClosure = okClosure; my invokingButtonTitle = Melder_wcsdup (invokingButtonTitle); my helpTitle = helpTitle; UiFile_init (me, parent, title); my allowExecutionHook = theAllowExecutionHookHint; my allowExecutionClosure = theAllowExecutionClosureHint; return (UiForm) me; } static void commonOutfileCallback (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure) { EditorCommand command = (EditorCommand) closure; (void) invokingButtonTitle; (void) modified; command -> commandCallback (command -> d_editor, command, sendingForm, sendingString, interpreter); therror } UiForm UiOutfile_createE (EditorCommand cmd, const wchar_t *title, const wchar_t *invokingButtonTitle, const wchar_t *helpTitle) { Editor editor = (Editor) cmd -> d_editor; UiOutfile dia = (UiOutfile) UiOutfile_create (editor -> d_windowForm, title, commonOutfileCallback, cmd, invokingButtonTitle, helpTitle); dia -> command = cmd; return (UiForm) dia; // BUG } UiForm UiInfile_createE (EditorCommand cmd, const wchar_t *title, const wchar_t *invokingButtonTitle, const wchar_t *helpTitle) { Editor editor = (Editor) cmd -> d_editor; UiInfile dia = (UiInfile) UiInfile_create (editor -> d_windowForm, title, commonOutfileCallback, cmd, invokingButtonTitle, helpTitle, false); dia -> command = cmd; return (UiForm) dia; // BUG } void UiOutfile_do (I, const wchar_t *defaultName) { iam (UiOutfile); wchar_t *outfileName = GuiFileSelect_getOutfileName (NULL, my name, defaultName); if (outfileName == NULL) return; // cancelled if (my allowExecutionHook && ! my allowExecutionHook (my allowExecutionClosure)) { Melder_flushError ("Dialog `%s' cancelled.", my name); return; } Melder_pathToFile (outfileName, & my file); structMelderFile file; MelderFile_copy (& my file, & file); // save, because okCallback could destroy me UiHistory_write (L"\n"); UiHistory_write (my invokingButtonTitle); try { my okCallback ((UiForm) me, NULL, NULL, my invokingButtonTitle, false, my okClosure); } catch (MelderError) { Melder_error_ ("File ", & file, " not finished."); Melder_flushError (NULL); } UiHistory_write (L" "); UiHistory_write (outfileName); Melder_free (outfileName); } /* End of file UiFile.cpp */ sources_5316/sys/GuiLabel.cpp0000644000176700017670000001202011753741756014744 0ustar paulpaul/* GuiLabel.cpp * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb & sdk 2007/12/28 gtk * pb 2010/11/28 removed Motif * pb 2011/04/06 C++ */ #include "GuiP.h" #undef iam #define iam(x) x me = (x) void_me #if win || mac #define iam_label \ Melder_assert (widget -> widgetClass == xmLabelWidgetClass); \ GuiLabel me = (GuiLabel) widget -> userData #else #define iam_label \ GuiLabel me = (GuiLabel) _GuiObject_getUserData (widget) #endif typedef struct structGuiLabel { GuiObject widget; } *GuiLabel; #if gtk static void _GuiGtkLabel_destroyCallback (GuiObject widget, gpointer void_me) { (void) widget; iam (GuiLabel); Melder_free (me); } #elif win void _GuiWinLabel_destroy (GuiObject widget) { iam_label; _GuiNativeControl_destroy (widget); Melder_free (me); // NOTE: my widget is not destroyed here } #elif mac #if useCarbon void _GuiMacLabel_destroy (GuiObject widget) { iam_label; _GuiNativeControl_destroy (widget); Melder_free (me); // NOTE: my widget is not destroyed here } #else #endif #endif GuiObject GuiLabel_create (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *labelText, unsigned long flags) { GuiLabel me = Melder_calloc_f (struct structGuiLabel, 1); #if gtk my widget = gtk_label_new (Melder_peekWcsToUtf8 (labelText)); _GuiObject_setUserData (my widget, me); _GuiObject_position (my widget, left, right, top, bottom); if (GTK_IS_BOX (parent)) { gtk_box_pack_start (GTK_BOX (parent), GTK_WIDGET (my widget), FALSE, FALSE, 0); } g_signal_connect (G_OBJECT (my widget), "destroy", G_CALLBACK (_GuiGtkLabel_destroyCallback), me); //gtk_label_set_justify (GTK_LABEL (my widget), // flags & GuiLabel_RIGHT ? GTK_JUSTIFY_RIGHT : flags & GuiLabel_CENTRE ? GTK_JUSTIFY_CENTER : GTK_JUSTIFY_LEFT); gtk_misc_set_alignment (GTK_MISC (my widget), flags & GuiLabel_RIGHT ? 1.0 : flags & GuiLabel_CENTRE ? 0.5 : 0.0, 0.5); #elif win my widget = _Gui_initializeWidget (xmLabelWidgetClass, parent, labelText); _GuiObject_setUserData (my widget, me); my widget -> window = CreateWindow (L"static", _GuiWin_expandAmpersands (my widget -> name), WS_CHILD | ( flags & GuiLabel_RIGHT ? SS_RIGHT : flags & GuiLabel_CENTRE ? SS_CENTER : SS_LEFT ) | SS_CENTERIMAGE, my widget -> x, my widget -> y, my widget -> width, my widget -> height, my widget -> parent -> window, (HMENU) 1, theGui.instance, NULL); SetWindowLongPtr (my widget -> window, GWLP_USERDATA, (LONG_PTR) my widget); SetWindowFont (my widget -> window, GetStockFont (ANSI_VAR_FONT), FALSE); _GuiObject_position (my widget, left, right, top, bottom); #elif mac #if useCarbon my widget = _Gui_initializeWidget (xmLabelWidgetClass, parent, labelText); _GuiObject_setUserData (my widget, me); ControlFontStyleRec macFontStyleRecord = { 0 }; // BUG: _GuiNativeControl_setFont will reset alignment (should do inheritance) macFontStyleRecord. flags = kControlUseFontMask | kControlUseSizeMask | kControlUseJustMask; macFontStyleRecord. font = systemFont; macFontStyleRecord. size = 13; macFontStyleRecord. just = ( flags & GuiLabel_RIGHT ? teFlushRight : flags & GuiLabel_CENTRE ? teCenter : teFlushLeft ); CreateStaticTextControl (my widget -> macWindow, & my widget -> rect, NULL, & macFontStyleRecord, & my widget -> nat.control.handle); Melder_assert (my widget -> nat.control.handle != NULL); SetControlReference (my widget -> nat.control.handle, (long) my widget); my widget -> isControl = true; _GuiNativeControl_setTitle (my widget); _GuiObject_position (my widget, left, right, top, bottom); #else #endif #endif return my widget; } GuiObject GuiLabel_createShown (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *labelText, unsigned long flags) { GuiObject me = GuiLabel_create (parent, left, right, top, bottom, labelText, flags); GuiObject_show (me); return me; } void GuiLabel_setString (GuiObject widget, const wchar_t *text) { #if gtk gtk_label_set_text (GTK_LABEL (widget), Melder_peekWcsToUtf8 (text)); #elif win Melder_free (widget -> name); widget -> name = Melder_wcsdup_f (text); _GuiNativeControl_setTitle (widget); #elif mac #if useCarbon Melder_free (widget -> name); widget -> name = Melder_wcsdup_f (text); _GuiNativeControl_setTitle (widget); #else #endif #endif } /* End of file GuiLabel.cpp */ sources_5316/sys/Graphics.cpp0000644000176700017670000002462311747341263015024 0ustar paulpaul/* Graphics.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include "GraphicsP.h" #include "enums_getText.h" #include "Graphics_enums.h" #include "enums_getValue.h" #include "Graphics_enums.h" /***** Methods *****/ Thing_implement (Graphics, Thing, 0); void structGraphics :: v_destroy () { Melder_free (record); Graphics_Parent :: v_destroy (); } /* On Macintosh, the Device Coordinates are Mac window coordinates. * However, we would like to be able to call Graphics_setWsViewport () with widget coordinates. * The following routine computes the conversion. It is called by Graphics_init () and by * Graphics_setWsViewport (). */ static void widgetToWindowCoordinates (I) { #if mac iam (Graphics); if (my screen) { iam (GraphicsScreen); if (my d_drawingArea) { GuiObject widget = my d_drawingArea; int shellX = 0, shellY = 0; do { int x = GuiObject_getX (widget), y = GuiObject_getY (widget); shellX += x; shellY += y; widget = GuiObject_parent (widget); } while (! XtIsShell (widget)); my d_x1DC += shellX; my d_x2DC += shellX; my d_y1DC += shellY; my d_y2DC += shellY; } } #else (void) void_me; #endif } static void computeTrafo (I) { iam (Graphics); double worldScaleX, worldScaleY, workScaleX, workScaleY; worldScaleX = (my d_x2NDC - my d_x1NDC) / (my d_x2WC - my d_x1WC); worldScaleY = (my d_y2NDC - my d_y1NDC) / (my d_y2WC - my d_y1WC); my deltaX = my d_x1NDC - my d_x1WC * worldScaleX; my deltaY = my d_y1NDC - my d_y1WC * worldScaleY; workScaleX = (my d_x2DC - my d_x1DC) / (my d_x2wNDC - my d_x1wNDC); my deltaX = my d_x1DC - (my d_x1wNDC - my deltaX) * workScaleX; my scaleX = worldScaleX * workScaleX; if (my yIsZeroAtTheTop) { workScaleY = ((int) my d_y1DC - (int) my d_y2DC) / (my d_y2wNDC - my d_y1wNDC); my deltaY = my d_y2DC - (my d_y1wNDC - my deltaY) * workScaleY; } else { workScaleY = ((int) my d_y2DC - (int) my d_y1DC) / (my d_y2wNDC - my d_y1wNDC); my deltaY = my d_y1DC - (my d_y1wNDC - my deltaY) * workScaleY; } my scaleY = worldScaleY * workScaleY; } /***** WORKSTATION FUNCTIONS *****/ void Graphics_init (Graphics me) { my d_x1DC = my d_x1DCmin = 0; my d_x2DC = my d_x2DCmax = 32767; my d_y1DC = my d_y1DCmin = 0; my d_y2DC = my d_y2DCmax = 32767; my d_x1WC = my d_x1NDC = my d_x1wNDC = 0.0; my d_x2WC = my d_x2NDC = my d_x2wNDC = 1.0; my d_y1WC = my d_y1NDC = my d_y1wNDC = 0.0; my d_y2WC = my d_y2NDC = my d_y2wNDC = 1.0; widgetToWindowCoordinates (me); computeTrafo (me); my lineWidth = 1.0; my arrowSize = 1.0; my font = kGraphics_font_HELVETICA; my fontSize = 10; my fontStyle = Graphics_NORMAL; my record = NULL; my irecord = my nrecord = 0; my percentSignIsItalic = 1; my numberSignIsBold = 1; my circumflexIsSuperscript = 1; my underscoreIsSubscript = 1; my dollarSignIsCode = 0; my atSignIsLink = 0; } Graphics Graphics_create (int resolution) { Graphics me = (Graphics) Thing_new (Graphics); Graphics_init (me); my resolution = resolution; return me; } int Graphics_getResolution (Graphics me) { return my resolution; } void Graphics_setWsViewport (Graphics me, long x1DC, long x2DC, long y1DC, long y2DC) { if (x1DC < my d_x1DCmin || x2DC > my d_x2DCmax || y1DC < my d_y1DCmin || y2DC > my d_y2DCmax) { static MelderString warning = { 0 }; MelderString_empty (& warning); MelderString_append (& warning, L"Graphics_setWsViewport: coordinates too large:\n", Melder_integer (x1DC), L"..", Melder_integer (x2DC), L" x ", Melder_integer (y1DC), L"..", Melder_integer (y2DC)); MelderString_append (& warning, L" goes outside ", Melder_integer (my d_x1DCmin), L"..", Melder_integer (my d_x2DCmax), L" x ", Melder_integer (my d_y1DCmin), L"..", Melder_integer (my d_y2DCmax), L"."); Melder_warning (warning.string); x1DC = my d_x1DCmin; x2DC = my d_x2DCmax; y1DC = my d_y1DCmin; y2DC = my d_y2DCmax; } my d_x1DC = x1DC; my d_x2DC = x2DC; my d_y1DC = y1DC; my d_y2DC = y2DC; widgetToWindowCoordinates (me); #if win if (my screen && my printer) { GraphicsScreen mescreen = (GraphicsScreen) me; /* * Map page coordinates to paper coordinates. */ mescreen -> d_x1DC -= GetDeviceCaps (mescreen -> d_gdiGraphicsContext, PHYSICALOFFSETX); mescreen -> d_x2DC -= GetDeviceCaps (mescreen -> d_gdiGraphicsContext, PHYSICALOFFSETX); mescreen -> d_y1DC -= GetDeviceCaps (mescreen -> d_gdiGraphicsContext, PHYSICALOFFSETY); mescreen -> d_y2DC -= GetDeviceCaps (mescreen -> d_gdiGraphicsContext, PHYSICALOFFSETY); } #endif computeTrafo (me); } void Graphics_resetWsViewport (Graphics me, long x1DC, long x2DC, long y1DC, long y2DC) { my d_x1DC = x1DC; my d_x2DC = x2DC; my d_y1DC = y1DC; my d_y2DC = y2DC; computeTrafo (me); } void Graphics_inqWsViewport (Graphics me, long *x1DC, long *x2DC, long *y1DC, long *y2DC) { *x1DC = my d_x1DC; *x2DC = my d_x2DC; *y1DC = my d_y1DC; *y2DC = my d_y2DC; } void Graphics_setWsWindow (Graphics me, double x1NDC, double x2NDC, double y1NDC, double y2NDC) { my d_x1wNDC = x1NDC; my d_x2wNDC = x2NDC; my d_y1wNDC = y1NDC; my d_y2wNDC = y2NDC; computeTrafo (me); if (my recording) { op (SET_WS_WINDOW, 4); put (x1NDC); put (x2NDC); put (y1NDC); put (y2NDC); } } void Graphics_inqWsWindow (Graphics me, double *x1NDC, double *x2NDC, double *y1NDC, double *y2NDC) { *x1NDC = my d_x1wNDC; *x2NDC = my d_x2wNDC; *y1NDC = my d_y1wNDC; *y2NDC = my d_y2wNDC; } /***** CO-ORDINATE TRANFORMATIONS *****/ void Graphics_DCtoWC (Graphics me, long xDC, long yDC, double *xWC, double *yWC) { if (my yIsZeroAtTheTop) { *xWC = (xDC + 0.5 - my deltaX) / my scaleX; *yWC = (yDC - 0.5 - my deltaY) / my scaleY; } else { *xWC = (xDC + 0.5 - my deltaX) / my scaleX; *yWC = (yDC + 0.5 - my deltaY) / my scaleY; } } #define wdx(x) ((x) * my scaleX + my deltaX) #define wdy(y) ((y) * my scaleY + my deltaY) void Graphics_WCtoDC (Graphics me, double xWC, double yWC, long *xDC, long *yDC) { *xDC = wdx (xWC); *yDC = wdy (yWC); } /***** OUTPUT PRIMITIVES, RECORDABLE *****/ void Graphics_setViewport (Graphics me, double x1NDC, double x2NDC, double y1NDC, double y2NDC) { my d_x1NDC = x1NDC; my d_x2NDC = x2NDC; my d_y1NDC = y1NDC; my d_y2NDC = y2NDC; computeTrafo (me); if (my recording) { op (SET_VIEWPORT, 4); put (x1NDC); put (x2NDC); put (y1NDC); put (y2NDC); } } void Graphics_setInner (Graphics me) { double margin = 2.8 * my fontSize * my resolution / 72.0; double wDC = (my d_x2DC - my d_x1DC) / (my d_x2wNDC - my d_x1wNDC) * (my d_x2NDC - my d_x1NDC); double hDC = abs (my d_y2DC - my d_y1DC) / (my d_y2wNDC - my d_y1wNDC) * (my d_y2NDC - my d_y1NDC); double dx = 1.5 * margin / wDC; double dy = margin / hDC; my horTick = 0.06 * dx, my vertTick = 0.09 * dy; if (dx > 0.4) dx = 0.4; if (dy > 0.4) dy = 0.4; my horTick /= 1 - 2 * dx, my vertTick /= 1 - 2 * dy; my outerViewport.x1NDC = my d_x1NDC; my outerViewport.x2NDC = my d_x2NDC; my outerViewport.y1NDC = my d_y1NDC; my outerViewport.y2NDC = my d_y2NDC; my d_x1NDC = (1 - dx) * my outerViewport.x1NDC + dx * my outerViewport.x2NDC; my d_x2NDC = (1 - dx) * my outerViewport.x2NDC + dx * my outerViewport.x1NDC; my d_y1NDC = (1 - dy) * my outerViewport.y1NDC + dy * my outerViewport.y2NDC; my d_y2NDC = (1 - dy) * my outerViewport.y2NDC + dy * my outerViewport.y1NDC; computeTrafo (me); if (my recording) { op (SET_INNER, 0); } } void Graphics_unsetInner (Graphics me) { my d_x1NDC = my outerViewport.x1NDC; my d_x2NDC = my outerViewport.x2NDC; my d_y1NDC = my outerViewport.y1NDC; my d_y2NDC = my outerViewport.y2NDC; computeTrafo (me); if (my recording) { op (UNSET_INNER, 0); } } void Graphics_setWindow (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC) { my d_x1WC = x1WC; my d_x2WC = x2WC; my d_y1WC = y1WC; my d_y2WC = y2WC; computeTrafo (me); if (my recording) { op (SET_WINDOW, 4); put (x1WC); put (x2WC); put (y1WC); put (y2WC); } } /***** INQUIRIES TO CURRENT GRAPHICS *****/ void Graphics_inqViewport (Graphics me, double *x1NDC, double *x2NDC, double *y1NDC, double *y2NDC) { *x1NDC = my d_x1NDC; *x2NDC = my d_x2NDC; *y1NDC = my d_y1NDC; *y2NDC = my d_y2NDC; } void Graphics_inqWindow (Graphics me, double *x1WC, double *x2WC, double *y1WC, double *y2WC) { *x1WC = my d_x1WC; *x2WC = my d_x2WC; *y1WC = my d_y1WC; *y2WC = my d_y2WC; } Graphics_Viewport Graphics_insetViewport (Graphics me, double x1rel, double x2rel, double y1rel, double y2rel) { Graphics_Viewport previous; previous.x1NDC = my d_x1NDC; previous.x2NDC = my d_x2NDC; previous.y1NDC = my d_y1NDC; previous.y2NDC = my d_y2NDC; Graphics_setViewport (me, (1 - x1rel) * my d_x1NDC + x1rel * my d_x2NDC, x2rel * my d_x2NDC + (1 - x2rel) * my d_x1NDC, (1 - y1rel) * my d_y1NDC + y1rel * my d_y2NDC, y2rel * my d_y2NDC + (1 - y2rel) * my d_y1NDC); return previous; } void Graphics_resetViewport (Graphics me, Graphics_Viewport viewport) { Graphics_setViewport (me, viewport.x1NDC, viewport.x2NDC, viewport.y1NDC, viewport.y2NDC); } /* Millimetres. */ double Graphics_dxMMtoWC (Graphics me, double dx_mm) { return dx_mm * my resolution / (25.4 * my scaleX); } double Graphics_dyMMtoWC (Graphics me, double dy_mm) { return my yIsZeroAtTheTop ? dy_mm * my resolution / (-25.4 * my scaleY) : dy_mm * my resolution / (25.4 * my scaleY); } double Graphics_distanceWCtoMM (Graphics me, double x1WC, double y1WC, double x2WC, double y2WC) { double dxDC = (x1WC - x2WC) * my scaleX; double dyDC = (y1WC - y2WC) * my scaleY; return sqrt (dxDC * dxDC + dyDC * dyDC) * 25.4 / my resolution; } double Graphics_dxWCtoMM (Graphics me, double dxWC) { return dxWC * my scaleX * 25.4 / my resolution; } double Graphics_dyWCtoMM (Graphics me, double dyWC) { return my yIsZeroAtTheTop ? dyWC * my scaleY * -25.4 / my resolution : dyWC * my scaleY * 25.4 / my resolution; } /* End of file Graphics.cpp */ sources_5316/sys/melder_token.cpp0000644000176700017670000000446511654071566015741 0ustar paulpaul/* melder_token.cpp * * Copyright (C) 2006-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2006/04/16 created * pb 2007/08/10 wchar_t * pb 2007/11/18 moved Melder_get/free/searchToken(s) here * pb 2011/04/05 C++ */ #include "melder.h" #include "NUM.h" long Melder_countTokens (const wchar_t *string) { long numberOfTokens = 0; const wchar_t *p = & string [0]; for (;;) { while (*p == ' ' || *p == '\t' || *p == '\n' || *p == '\r') p ++; if (*p == '\0') return numberOfTokens; numberOfTokens ++; while (*p != ' ' && *p != '\t' && *p != '\n' && *p != '\r') { if (*p == '\0') return numberOfTokens; p ++; } } return 0; // should not occur } static wchar *theMelderToken, *theMelderTokenLast; wchar *Melder_firstToken (const wchar *string) { Melder_free (theMelderToken); theMelderToken = Melder_wcsdup_f (string); return Melder_wcstok (theMelderToken, L" \t\n\r", & theMelderTokenLast); } wchar *Melder_nextToken (void) { return Melder_wcstok (NULL, L" \t\n\r", & theMelderTokenLast); } wchar ** Melder_getTokens (const wchar *string, long *n) { wchar *token; long itoken = 0; *n = Melder_countTokens (string); if (*n == 0) return NULL; autostringvector result (1, *n); for (token = Melder_firstToken (string); token != NULL; token = Melder_nextToken ()) { result [++ itoken] = Melder_wcsdup (token); } return result.transfer(); } void Melder_freeTokens (wchar ***tokens) { NUMvector_free (*tokens, 1); *tokens = NULL; } long Melder_searchToken (const wchar *string, wchar **tokens, long n) { for (long i = 1; i <= n; i ++) { if (wcsequ (string, tokens [i])) return i; } return 0; } /* End of file melder_token.cpp */ sources_5316/sys/Graphics_altitude.cpp0000644000176700017670000001473311624363111016706 0ustar paulpaul/* Graphics_altitude.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2008/01/19 double * pb 2011/03/17 C++ */ #include "Graphics.h" static int empty (double **data, int **right, int **below, long row1, long col1, double height, int row, int col, int ori) { if (ori == 3) { row ++; ori = 1; } else if (ori == 2) { col ++; ori = 4; } if (ori == 1) return (data [row] [col] < height) != (data [row] [col + 1] < height) && ! right [row - row1] [col - col1]; else /* ori == 4 */ return (data [row] [col] < height) != (data [row + 1] [col] < height) && ! below [row - row1] [col - col1]; } #define MAXALTSIDE 50 #define MAXALTPATH (2 * MAXALTSIDE * (MAXALTSIDE - 1) + 2) static long numberOfPoints; static long row1, row2, col1, col2; static int **right, **below; static double *x, *y; static int closed; static double dx, dy, xoff, yoff; static int note (double **z, double height, int row, int col, int ori, int forget) { ++ numberOfPoints; Melder_assert (numberOfPoints <= MAXALTPATH); if (ori == 3) { row ++; ori = 1; } else if (ori == 2) { col ++; ori = 4; } if (ori == 1) { if (forget) right [row - row1] [col - col1] = 1; x [numberOfPoints] = xoff + (col + (height - z [row] [col]) / (z [row] [col + 1] - z [row] [col])) * dx; y [numberOfPoints] = yoff + row * dy; } else { /* ori == 4 */ if (forget) below [row - row1] [col - col1] = 1; x [numberOfPoints] = xoff + col * dx; y [numberOfPoints] = yoff + (row + (height - z [row] [col]) / (z [row + 1] [col] - z [row] [col])) * dy; } return 1; } static void makeContour (Graphics graphics, double **z, double height, int row0, int col0, int ori0) { int row, col, ori, clockwise = 0, edge = 0; numberOfPoints = 0; row = row0; col = col0; ori = ori0; note (z, height, row0, col0, ori0, 0); do { clockwise = ! (ori & 1); do { /* Preference for contours perpendicular to x == y. */ ori = (clockwise ? ori : ori + 2) % 4 + 1; } while (! empty (z, right, below, row1, col1, height, row, col, ori)); if (! closed) switch (ori) { case 1: edge = row == row1; break; case 2: edge = col == col2 - 1; break; case 3: edge = row == row2 - 1; break; case 4: edge = col == col1; break; } if (! edge) { switch (ori) { case 1: row --; break; case 2: col ++; break; case 3: row ++; break; case 4: col --; break; } ori = (ori + 1) % 4 + 1; } if (! note (z, height, row, col, ori, 1)) return; } while (edge == 0 && (row != row0 || col != col0 || ori != ori0)); if (closed) note (z, height, row0, col0, ori0, 1); /* Close the contour. */ Graphics_polyline (graphics, numberOfPoints, & x [1], & y [1]); } static void smallAlt (Graphics graphics, double **z, double height) { int row, col; for (row = 0; row < MAXALTSIDE; row ++) for (col = 0; col < MAXALTSIDE; col ++) right [row] [col] = below [row] [col] = 0; /* Find all the edge contours of this border value. */ closed = 0; for (col = col1; col < col2; col ++) if (empty (z, right, below, row1, col1, height, row1, col, 1)) makeContour (graphics, z, height, row1, col, 1); for (row = row1; row < row2; row ++) if (empty (z, right, below, row1, col1, height, row, col2 - 1, 2)) makeContour (graphics, z, height, row, col2 - 1, 2); for (col = col2 - 1; col >= col1; col --) if (empty (z, right, below, row1, col1, height, row2 - 1, col, 3)) makeContour (graphics, z, height, row2 - 1, col, 3); for (row = row2 - 1; row >= row1; row --) if (empty (z, right, below, row1, col1, height, row, col1, 4)) makeContour (graphics, z, height, row, col1, 4); /* Find all the closed contours of this border value. */ closed = 1; for (row = row1 + 1; row < row2; row ++) for (col = col1; col < col2; col ++) if (empty (z, right, below, row1, col1, height, row, col, 1)) makeContour (graphics, z, height, row, col, 1); for (col = col1 + 1; col < col2; col ++) for (row = row1; row < row2; row ++) if (empty (z, right, below, row1, col1, height, row, col, 4)) makeContour (graphics, z, height, row, col, 4); } void Graphics_contour (Graphics me, double **z, long ix1, long ix2, double x1WC, double x2WC, long iy1, long iy2, double y1WC, double y2WC, double height) { if (ix2 <= ix1 || iy2 <= iy1) return; dx = (x2WC - x1WC) / (ix2 - ix1); dy = (y2WC - y1WC) / (iy2 - iy1); xoff = x1WC - ix1 * dx; yoff = y1WC - iy1 * dy; if (! right) { // static! right = NUMmatrix (0, MAXALTSIDE - 1, 0, MAXALTSIDE - 1); below = NUMmatrix (0, MAXALTSIDE - 1, 0, MAXALTSIDE - 1); x = NUMvector (1, MAXALTPATH); y = NUMvector (1, MAXALTPATH); } for (row1 = iy1; row1 < iy2; row1 += MAXALTSIDE - 1) { for (col1 = ix1; col1 < ix2; col1 += MAXALTSIDE - 1) { if ((row2 = row1 + (MAXALTSIDE - 1)) > iy2) row2 = iy2; if ((col2 = col1 + (MAXALTSIDE - 1)) > ix2) col2 = ix2; smallAlt (me, z, height); } } } void Graphics_altitude (Graphics me, double **z, long ix1, long ix2, double x1WC, double x2WC, long iy1, long iy2, double y1WC, double y2WC, int numberOfBorders, double borders []) { int iborder; if (ix2 <= ix1 || iy2 <= iy1) return; dx = (x2WC - x1WC) / (ix2 - ix1); dy = (y2WC - y1WC) / (iy2 - iy1); xoff = x1WC - ix1 * dx; yoff = y1WC - iy1 * dy; if (! right) { // static! right = NUMmatrix (0, MAXALTSIDE - 1, 0, MAXALTSIDE - 1); below = NUMmatrix (0, MAXALTSIDE - 1, 0, MAXALTSIDE - 1); x = NUMvector (1, MAXALTPATH); y = NUMvector (1, MAXALTPATH); } for (row1 = iy1; row1 < iy2; row1 += MAXALTSIDE - 1) { for (col1 = ix1; col1 < ix2; col1 += MAXALTSIDE - 1) { if ((row2 = row1 + (MAXALTSIDE - 1)) > iy2) row2 = iy2; if ((col2 = col1 + (MAXALTSIDE - 1)) > ix2) col2 = ix2; for (iborder = 1; iborder <= numberOfBorders; iborder ++) { smallAlt (me, z, borders [iborder]); } } } } /* End of file Graphics_altitude.cpp */ sources_5316/sys/Graphics_grey.cpp0000644000176700017670000003723611747342462016060 0ustar paulpaul/* Graphics_grey.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 1994/10/13 * pb 1999/09/09 bug fix: ori = 1 --> ori == 1 * pb 2002/03/07 GPL * pb 2008/01/19 double * pb 2011/03/17 C++ */ #include #include "melder.h" #include "Graphics.h" //#define MAXGREYSIDE 12 #define MAXGREYSIDE 1000 #define MAXGREYPATH (2 * MAXGREYSIDE * (MAXGREYSIDE - 1) + 2) #define MAXGREYEDGECONTOURS (2 * (MAXGREYSIDE - 1)) #define MAXGREYCLOSEDCONTOURS (MAXGREYPATH / 4 + 1) #define MAXGREYEDGEPOINTS (4 * MAXGREYSIDE) typedef struct { int numberOfPoints; int beginRow, beginCol, beginOri; int endRow, endCol, endOri; int lowerGrey, upperGrey; double *x, *y; } structEdgeContour, *EdgeContour; static EdgeContour EdgeContour_create (int numberOfPoints) { EdgeContour result = Melder_calloc (structEdgeContour, 1); result -> numberOfPoints = numberOfPoints; result -> x = NUMvector (1, 2 * numberOfPoints); result -> y = result -> x + numberOfPoints; return result; // LEAK } static void EdgeContour_delete (EdgeContour e) { NUMvector_free (e -> x, 1); Melder_free (e); } typedef struct { int numberOfPoints; int grey, drawn; double xmin, xmax, ymin, ymax, *x, *y; } structClosedContour, *ClosedContour; static ClosedContour ClosedContour_create (int numberOfPoints) { ClosedContour result = Melder_calloc (structClosedContour, 1); result -> numberOfPoints = numberOfPoints; result -> x = NUMvector (1, 2 * numberOfPoints); result -> y = result -> x + numberOfPoints; return result; // LEAK } static void ClosedContour_delete (ClosedContour c) { NUMvector_free (c -> x, 1); Melder_free (c); } typedef struct { int ori, iContour, start, usedAsEntry, grey; double val; } structEdgePoint, *EdgePoint; static Graphics theGraphics; static int numberOfEdgeContours; static EdgeContour *edgeContours; static int numberOfEdgePoints; static structEdgePoint *edgePoints; static int numberOfClosedContours; static ClosedContour *closedContours; static int numberOfPoints; static long row1, row2, col1, col2; static int iBorder, numberOfBorders; static int **right, **below; static double **data, *border, *x, *y; static double dx, dy, xoff, yoff; static int empty (int row, int col, int ori) { if (ori == 3) { row ++; ori = 1; } if (ori == 2) { col ++; ori = 4; } if (ori == 1) return (data [row] [col] < border [iBorder]) != (data [row] [col + 1] < border [iBorder]) && ! right [row - row1] [col - col1]; else /* ori == 4 */ return (data [row] [col] < border [iBorder]) != (data [row + 1] [col] < border [iBorder]) && ! below [row - row1] [col - col1]; } static int note (int row, int col, int ori) { ++ numberOfPoints; Melder_assert (numberOfPoints <= MAXGREYPATH); if (ori == 3) { row ++; ori = 1; } if (ori == 2) { col ++; ori = 4; } if (ori == 1) { right [row - row1] [col - col1] = 1; x [numberOfPoints] = xoff + (col + (border [iBorder] - data [row] [col]) / (data [row] [col + 1] - data [row] [col])) * dx; y [numberOfPoints] = yoff + row * dy; } else /* ori == 4 */ { below [row - row1] [col - col1] = 1; x [numberOfPoints] = xoff + col * dx; y [numberOfPoints] = yoff + (row + (border [iBorder] - data [row] [col]) / (data [row + 1] [col] - data [row] [col])) * dy; } return 1; } static void fillGrey (int numberOfPoints, double *x, double *y, int igrey) /* "igrey" is in between 1 and numberOfBorders + 1. */ { Graphics_setGrey (theGraphics, 1.0 - (igrey - 1.0) / numberOfBorders); Graphics_fillArea (theGraphics, numberOfPoints, & x [1], & y [1]); } static void makeEdgeContour (int row0, int col0, int ori0) { int row, col, ori, clockwise = 0, edge = 0, up = 0, iPoint; EdgeContour e; numberOfPoints = 0; row = row0; col = col0; ori = ori0; note (row0, col0, ori0); do { clockwise = ! (ori & 1); do { /* Preference for contours perpendicular to x == y. */ ori = (clockwise ? ori : ori + 2) % 4 + 1; } while (! empty (row, col, ori)); switch (ori) { case 1: edge = row == row1; break; case 2: edge = col == col2 - 1; break; case 3: edge = row == row2 - 1; break; case 4: edge = col == col1; break; } if (! edge) { switch (ori) { case 1: row --; break; case 2: col ++; break; case 3: row ++; break; case 4: col --; break; } ori = (ori + 1) % 4 + 1; } note (row, col, ori); } while (edge == 0); Melder_assert (numberOfEdgeContours < MAXGREYEDGECONTOURS * numberOfBorders); e = edgeContours [++ numberOfEdgeContours] = EdgeContour_create (numberOfPoints); e -> beginRow = row0; e -> beginCol = col0; e -> beginOri = ori0; e -> endRow = row; e -> endCol = col; e -> endOri = ori; switch (ori0) { case 1: up = data [row0] [col0 + 1] > data [row0] [col0]; break; case 2: up = data [row0 + 1] [col0 + 1] > data [row0] [col0 + 1]; break; case 3: up = data [row0 + 1] [col0] > data [row0 + 1] [col0 + 1]; break; case 4: up = data [row0] [col0] > data [row0 + 1] [col0]; break; } if (up) { e -> lowerGrey = iBorder; e -> upperGrey = iBorder + 1; } else { e -> lowerGrey = iBorder + 1; e -> upperGrey = iBorder; } for (iPoint = 1; iPoint <= numberOfPoints; iPoint ++) { e -> x [iPoint] = x [iPoint]; e -> y [iPoint] = y [iPoint]; } } static void makeClosedContour (int row0, int col0, int ori0) { int row, col, ori, clockwise = 0, up = 0; double x1, y1; ClosedContour c; numberOfPoints = 0; row = row0; col = col0; ori = ori0; do { clockwise = ! (ori & 1); do { /* Preference for contours perpendicular to x == y. */ ori = (clockwise ? ori : ori + 2) % 4 + 1; } while (! empty (row, col, ori)); switch (ori) { case 1: row --; break; case 2: col ++; break; case 3: row ++; break; case 4: col --; break; } ori = (ori + 1) % 4 + 1; note (row, col, ori); } while (row != row0 || col != col0 || ori != ori0); Melder_assert (numberOfClosedContours < MAXGREYCLOSEDCONTOURS * numberOfBorders); c = closedContours [++ numberOfClosedContours] = ClosedContour_create (numberOfPoints); /* Find a point just inside or outside the contour. */ /* Find out whether it is above or below the contour. */ x1 = x [numberOfPoints]; y1 = y [numberOfPoints]; if (ori == 3) { row ++; ori = 1; } else if (ori == 2) { col ++; ori = 4; } if (ori == 1) { if (x1 > xoff + (col + 0.5) * dx) x1 -= 0.01 * dx; else x1 += 0.01 * dx; up = data [row] [col] + ((x1 - xoff) / dx - col) * (data [row] [col + 1] - data [row] [col]) > border [iBorder]; } else { /* ori == 4 */ if (y1 > yoff + (row + 0.5) * dy) y1 -= 0.01 * dy; else y1 += 0.01 * dy; up = data [row] [col] + ((y1 - yoff) / dy - row) * (data [row + 1] [col] - data [row] [col]) > border [iBorder]; } /* Find out whether the point is inside or outside the contour. */ if (! NUMrotationsPointInPolygon (x1, y1, numberOfPoints, x, y)) up = ! up; { int i; double xmin = 1e300, xmax = -1e300, ymin = 1e300, ymax = -1e300; c -> grey = up ? iBorder + 1 : iBorder; for (i = 1; i <= numberOfPoints; i ++) { c -> x [i] = x [i]; c -> y [i] = y [i]; if (x [i] < xmin) xmin = x [i]; if (x [i] > xmax) xmax = x [i]; if (y [i] < ymin) ymin = y [i]; if (y [i] > ymax) ymax = y [i]; } c -> xmin = xmin; c -> xmax = xmax; c -> ymin = ymin; c -> ymax = ymax; } } static void smallGrey (void) { int row, col, i; numberOfEdgeContours = 0; numberOfClosedContours = 0; for (iBorder = 1; iBorder <= numberOfBorders; iBorder ++) { for (row = 0; row < MAXGREYSIDE; row ++) for (col = 0; col < MAXGREYSIDE; col ++) right [row] [col] = below [row] [col] = 0; /* Find all the edge contours of this border value. */ for (col = col1; col < col2; col ++) if (empty (row1, col, 1)) makeEdgeContour (row1, col, 1); for (row = row1; row < row2; row ++) if (empty (row, col2 - 1, 2)) makeEdgeContour (row, col2 - 1, 2); for (col = col2 - 1; col >= col1; col --) if (empty (row2 - 1, col, 3)) makeEdgeContour (row2 - 1, col, 3); for (row = row2 - 1; row >= row1; row --) if (empty (row, col1, 4)) makeEdgeContour (row, col1, 4); /* Find all the closed contours of this border value. */ for (row = row1 + 1; row < row2; row ++) for (col = col1; col < col2; col ++) if (empty (row, col, 1)) makeClosedContour (row, col, 1); for (col = col1 + 1; col < col2; col ++) for (row = row1; row < row2; row ++) if (empty (row, col, 4)) makeClosedContour (row, col, 4); } numberOfEdgePoints = 2 * numberOfEdgeContours + 4; Melder_assert (numberOfEdgePoints <= MAXGREYEDGEPOINTS * numberOfBorders); /* Make a list of all points on the edge. */ /* The edge points include the four corner points. */ for (i = 1; i <= 4; i ++) { EdgePoint p = & edgePoints [i]; p -> ori = i; p -> val = 0; p -> iContour = 0; p -> start = 0; p -> usedAsEntry = 0; p -> grey = -1; } /* The edge points include the first points of the edge contours. */ for (i = 1; i <= numberOfEdgeContours; i ++) { EdgeContour c = edgeContours [i]; EdgePoint p = & edgePoints [i + i + 3]; switch (p -> ori = c -> beginOri) { case 1: p -> val = c -> x [1] - xoff - col1 * dx; break; case 2: p -> val = c -> y [1] - yoff - row1 * dy; break; case 3: p -> val = xoff + col2 * dx - c -> x [1]; break; case 4: p -> val = yoff + row2 * dy - c -> y [1]; break; } p -> iContour = i; p -> start = 1; p -> usedAsEntry = 0; p -> grey = c -> lowerGrey; } /* The edge points include the last points of the edge contours. */ for (i = 1; i <= numberOfEdgeContours; i ++) { EdgeContour c = edgeContours [i]; EdgePoint p = & edgePoints [i + i + 4]; switch (p -> ori = c -> endOri) { case 1: p -> val = c -> x [c -> numberOfPoints] - xoff - col1 * dx; break; case 2: p -> val = c -> y [c -> numberOfPoints] - yoff - row1 * dy; break; case 3: p -> val = xoff + col2 * dx - c -> x [c -> numberOfPoints]; break; case 4: p -> val = yoff + row2 * dy - c -> y [c -> numberOfPoints]; break; } p -> iContour = i; p -> start = 0; p -> usedAsEntry = 0; p -> grey = c -> upperGrey; } /* Sort the list of edge points with keys Ori and Val. */ { int i; for (i = 1; i < numberOfEdgePoints; i ++) { structEdgePoint p; int min = i, j; for (j = i + 1; j <= numberOfEdgePoints; j ++) if (edgePoints [min]. ori > edgePoints [j]. ori || (edgePoints [min]. ori == edgePoints [j]. ori && edgePoints [min]. val > edgePoints [j]. val)) min = j; p = edgePoints [i]; edgePoints [i] = edgePoints [min]; edgePoints [min] = p; } } { int edge0, edge1, darkness; for (edge0 = 1; edge0 <= numberOfEdgePoints; edge0 ++) if (edgePoints [edge0].grey > -1 && ! edgePoints [edge0].usedAsEntry) { int iPoint = 0; edge1 = edge0; do { /* Follow one edge contour. */ EdgePoint p = & edgePoints [edge1]; int iContour = p -> iContour; EdgeContour c = edgeContours [iContour]; Melder_assert (iContour > 0); darkness = p -> grey; p -> usedAsEntry = 1; if (p -> start) { for (i = 1; i <= c -> numberOfPoints; i ++) { Melder_assert (iPoint < MAXGREYPATH); x [++ iPoint] = c -> x [i]; y [iPoint] = c -> y [i]; } for (i = edge1 + 1; i <= numberOfEdgePoints; i ++) if (edgePoints [i].iContour == iContour) edge1 = i; } else { int edge1dummy = edge1; for (i = c -> numberOfPoints; i >= 1; i --) { Melder_assert (iPoint < MAXGREYPATH); x [++ iPoint] = c -> x [i]; y [iPoint] = c -> y [i]; } for (i = 1; i <= edge1dummy - 1; i ++) if (edgePoints [i].iContour == iContour) edge1 = i; } edge1 = edge1 % numberOfEdgePoints + 1; /* Round some corners. */ while (edgePoints [edge1].grey == -1) { ++ iPoint; Melder_assert (iPoint <= MAXGREYPATH); switch (edgePoints [edge1].ori) { case 1: x [iPoint] = xoff + col1 * dx; y [iPoint] = yoff + row1 * dy; break; case 2: x [iPoint] = xoff + col2 * dx; y [iPoint] = yoff + row1 * dy; break; case 3: x [iPoint] = xoff + col2 * dx; y [iPoint] = yoff + row2 * dy; break; case 4: x [iPoint] = xoff + col1 * dx; y [iPoint] = yoff + row2 * dy; break; } edge1 = edge1 % numberOfEdgePoints + 1; } } while (edge1 != edge0); fillGrey (iPoint, x, y, darkness); } } if (numberOfEdgeContours == 0) { int i = 1; while (i <= numberOfBorders && border [i] < data [row1] [col1]) i ++; x [1] = x [4] = xoff + col1 * dx; x [2] = x [3] = xoff + col2 * dx; y [1] = y [2] = yoff + row1 * dy; y [3] = y [4] = yoff + row2 * dy; fillGrey (4, x, y, i); } /* Iterate over all the closed contours. * Those that are not enclosed by any other contour, are filled first. */ { int enclosed, found; do { found = 0; for (i = 1; i <= numberOfClosedContours; i ++) { ClosedContour ci = closedContours [i]; if (! ci -> drawn) { int j = 1; enclosed = 0; while (j <= numberOfClosedContours && ! enclosed) { ClosedContour cj = closedContours [j]; if ((! cj -> drawn) && j != i && ci -> xmin > cj -> xmin && ci -> xmax < cj -> xmax && ci -> ymin > cj -> ymin && ci -> ymax < cj -> ymax) enclosed = NUMrotationsPointInPolygon (ci -> x [1], ci -> y [1], cj -> numberOfPoints, cj -> x, cj -> y); j ++; } if (enclosed == 0) { found = 1; fillGrey (ci -> numberOfPoints, ci -> x, ci -> y, ci -> grey); ci -> drawn = 1; } } } } while (found); } Graphics_setGrey (theGraphics, 0.0); for (i = 1; i <= numberOfEdgeContours; i ++) EdgeContour_delete (edgeContours [i]); for (i = 1; i <= numberOfClosedContours; i ++) ClosedContour_delete (closedContours [i]); } void Graphics_grey (Graphics me, double **z, long ix1, long ix2, double x1WC, double x2WC, long iy1, long iy2, double y1WC, double y2WC, int _numberOfBorders, double borders []) { if (ix2 <= ix1 || iy2 <= iy1) return; /* Static variables. */ theGraphics = me; numberOfBorders = _numberOfBorders; data = z; border = borders; dx = (x2WC - x1WC) / (ix2 - ix1); dy = (y2WC - y1WC) / (iy2 - iy1); xoff = x1WC - ix1 * dx; yoff = y1WC - iy1 * dy; if (! right) { right = NUMmatrix (0, MAXGREYSIDE - 1, 0, MAXGREYSIDE - 1); // BUG memory below = NUMmatrix (0, MAXGREYSIDE - 1, 0, MAXGREYSIDE - 1); x = NUMvector (1, MAXGREYPATH); y = NUMvector (1, MAXGREYPATH); edgeContours = Melder_calloc (EdgeContour, MAXGREYEDGECONTOURS * numberOfBorders) - 1; closedContours = Melder_calloc (ClosedContour, MAXGREYCLOSEDCONTOURS * numberOfBorders) - 1; edgePoints = Melder_calloc (structEdgePoint, MAXGREYEDGEPOINTS * numberOfBorders); } /* The matrix is subdivided into matrices with side MAXGREYSIDE, so that: * 1. All the paths will fit into our memory (we have to remember them all). * 2. The path for filling fits into the PostScript path, which may be max. 1500 points long. */ for (row1 = iy1; row1 < iy2; row1 += MAXGREYSIDE - 1) { row2 = row1 + (MAXGREYSIDE - 1); if (row2 > iy2) row2 = iy2; for (col1 = ix1; col1 < ix2; col1 += MAXGREYSIDE - 1) { col2 = col1 + (MAXGREYSIDE - 1); if (col2 > ix2) col2 = ix2; smallGrey (); } } } /* End of file Graphics_grey.cpp */ sources_5316/sys/Ui.h0000644000176700017670000002545611623705615013311 0ustar paulpaul#ifndef _Ui_h_ #define _Ui_h_ /* Ui.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Graphics.h" #include "Gui.h" #include "Interpreter.h" Thing_declare (EditorCommand); /* Forms for getting arguments from the user. */ /* Example of usage: { static Any dia = NULL; if (dia == NULL) { Any radio; dia = UiForm_create (topShell, // The parent GuiObject of the dialog window. L"Create a new person", // The window title. DO_Person_create, // The routine to call when the user clicks OK. NULL, // The last argument to the OK routine (also for the other buttons). Could be a ScriptEditor, or an EditorCommand, or an Interpreter, or NULL. L"Create person...", // The invoking button title. L"Create person..."); // The help string; may be NULL. UiForm_addNatural (dia, L"Age (years)", L"18"); UiForm_addPositive (dia, L"Length (metres)", L"1.68 (average)"); UiForm_addBoolean (dia, L"Beard", FALSE); radio = UiForm_addRadio (L"Sex", 1); UiRadio_addButton (radio, L"Female"); UiRadio_addButton (radio, L"Male"); UiForm_addWord (dia, L"Colour", L"black"); UiForm_addLabel (dia, L"features", L"Some less conspicuous features:"); UiForm_addNatural (dia, L"Number of birth marks", L"28"); UiForm_addSentence (dia, L"Favourite greeting", L"Good morning"); UiForm_finish (dia); } UiForm_setReal (dia, L"Length", myLength); UiForm_setInteger (dia, L"Number of birth marks", 30); UiForm_do (dia, 0); // Show dialog box. } Real, Positive, Integer, Natural, Word, and Sentence show a label (name) and an editable text field (value). Radio shows a label (name) and has Button children. OptionMenu shows a label (name) and has Button children in a menu. Label only shows its value. Text only shows an editable text field (value). Boolean shows a labeled toggle button which is on (1) or off (0). Button does the same inside a radio box or option menu. List shows a scrollable list. Colour shows a label (name) and an editable text field for a grey value between 0 and 1, a colour name, ar {r,g,b}. Channel shows a label (name) and an editable text field for a natural number or the text Left or Right. As shown in the example, Real, Positive, Integer, Natural, and Word may contain extra text; this text is considered as comments and is erased as soon as you click OK. When you click "Standards", the standard values (including comments) are restored to all items in the form. */ Thing_define (UiField, Thing) { // new data: public: int type; const wchar *formLabel; double realValue, realDefaultValue; long integerValue, integerDefaultValue; wchar *stringValue; const wchar *stringDefaultValue; Graphics_Colour colourValue; char *stringValueA; Ordered options; long numberOfStrings; const wchar **strings; GuiObject text, toggle, list, cascadeButton; int y; // overridden methods: virtual void v_destroy (); }; #define MAXIMUM_NUMBER_OF_FIELDS 50 #define MAXIMUM_NUMBER_OF_CONTINUE_BUTTONS 10 Thing_define (UiForm, Thing) { // new data: public: EditorCommand command; GuiObject d_dialogParent, d_dialogShell, d_dialogForm; void (*okCallback) (UiForm sendingForm, const wchar_t *sendingString, Interpreter interpreter, const wchar_t *invokingButtonTitle, bool modified, void *closure); void (*applyCallback) (Any dia, void *closure); void (*cancelCallback) (Any dia, void *closure); void *buttonClosure; const wchar_t *invokingButtonTitle, *helpTitle; int numberOfContinueButtons, defaultContinueButton, cancelContinueButton, clickedContinueButton; const wchar_t *continueTexts [1 + MAXIMUM_NUMBER_OF_CONTINUE_BUTTONS]; int numberOfFields; UiField field [1 + MAXIMUM_NUMBER_OF_FIELDS]; GuiObject okButton, cancelButton, revertButton, helpButton, applyButton, continueButtons [1 + MAXIMUM_NUMBER_OF_CONTINUE_BUTTONS]; bool destroyWhenUnmanaged, isPauseForm; bool (*allowExecutionHook) (void *closure); void *allowExecutionClosure; // overridden methods: virtual void v_destroy (); }; /* The following routines work on the screen and from batch. */ UiForm UiForm_create (GuiObject parent, const wchar *title, void (*okCallback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure), void *buttonClosure, const wchar *invokingButtonTitle, const wchar *helpTitle); Any UiForm_addReal (I, const wchar *label, const wchar *defaultValue); Any UiForm_addRealOrUndefined (I, const wchar *label, const wchar *defaultValue); Any UiForm_addPositive (I, const wchar *label, const wchar *defaultValue); Any UiForm_addInteger (I, const wchar *label, const wchar *defaultValue); Any UiForm_addNatural (I, const wchar *label, const wchar *defaultValue); Any UiForm_addWord (I, const wchar *label, const wchar *defaultValue); Any UiForm_addSentence (I, const wchar *label, const wchar *defaultValue); Any UiForm_addLabel (I, const wchar *name, const wchar *label); Any UiForm_addBoolean (I, const wchar *label, int defaultValue); Any UiForm_addText (I, const wchar *name, const wchar *defaultValue); Any UiForm_addRadio (I, const wchar *label, int defaultValue); Any UiRadio_addButton (I, const wchar *label); Any UiForm_addOptionMenu (I, const wchar *label, int defaultValue); Any UiOptionMenu_addButton (I, const wchar *label); Any UiForm_addList (I, const wchar *label, long numberOfStrings, const wchar **strings, long defaultValue); Any UiForm_addColour (I, const wchar *label, const wchar *defaultValue); Any UiForm_addChannel (I, const wchar *label, const wchar *defaultValue); void UiForm_finish (I); void UiForm_destroyWhenUnmanaged (I); void UiForm_setPauseForm (I, int numberOfContinueButtons, int defaultContinueButton, int cancelContinueButton, const wchar *continue1, const wchar *continue2, const wchar *continue3, const wchar *continue4, const wchar *continue5, const wchar *continue6, const wchar *continue7, const wchar *continue8, const wchar *continue9, const wchar *continue10, void (*cancelCallback) (Any dia, void *closure)); /* The following three routines set values in widgets. */ /* Do not call from batch. */ /* 'fieldName' is name from UiForm_addXXXXXX (), */ /* without anything from and including the first " (" or ":". */ void UiForm_setString (I, const wchar *fieldName, const wchar *text); /* Real, Positive, Integer, Natural, Word, Sentence, Label, Text, Radio, List. */ void UiForm_setReal (I, const wchar *fieldName, double value); /* Real, Positive. */ void UiForm_setInteger (I, const wchar *fieldName, long value); /* Integer, Natural, Boolean, Radio, List. */ void UiForm_do (I, bool modified); /* Function: put the form on the screen. Behaviour: If the user clicks "OK", the form will call the okCallback that was registered with UiForm_create (). If the okCallback then returns 1, the form will disappear from the screen; if it returns 0, the form will stay on the screen; this can be used for enabling the user to repair mistakes in the form. If the user clicks "Apply", the form will call the okCallback that was registered with UiForm_create (), and the form disappears from the screen. If the user clicks "Cancel", the form disappears from the screen. If the user clicks "Help", the form calls "help" with the "helpTitle" and stays on the screen. When the form disappears from the screen, the values in the fields will remain until the next invocation of UiForm_do () for the same form. Arguments: the above behaviour describes the action when 'modified' is 0. If 'modified' is set, the user does not have to click OK. The form will still appear on the screen, but the okCallback will be called immediately. */ /* The 'okCallback' can use the following four routines to ask arguments. */ /* The field names are the 'label' or 'name' arguments to UiForm_addXXXXXX (), */ /* without anything from parentheses or from a colon. */ /* These routines work from the screen and from batch. */ double UiForm_getReal (I, const wchar *fieldName); // Real, Positive long UiForm_getInteger (I, const wchar *fieldName); // Integer, Natural, Boolean, Radio, List wchar * UiForm_getString (I, const wchar *fieldName); // Word, Sentence, Text, Radio, List Graphics_Colour UiForm_getColour (I, const wchar *fieldName); // Colour MelderFile UiForm_getFile (I, const wchar *fieldName); // FileIn, FileOut double UiForm_getReal_check (I, const wchar *fieldName); long UiForm_getInteger_check (I, const wchar *fieldName); wchar * UiForm_getString_check (I, const wchar *fieldName); Graphics_Colour UiForm_getColour_check (I, const wchar *fieldName); void UiForm_parseString (I, const wchar *arguments, Interpreter interpreter); UiForm UiInfile_create (GuiObject parent, const wchar *title, void (*okCallback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure), void *okClosure, const wchar *invokingButtonTitle, const wchar *helpTitle, bool allowMultipleFiles); UiForm UiOutfile_create (GuiObject parent, const wchar_t *title, void (*okCallback) (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure), void *okClosure, const wchar *invokingButtonTitle, const wchar *helpTitle); void UiInfile_do (Any dia); void UiOutfile_do (Any dia, const wchar *defaultName); MelderFile UiFile_getFile (Any dia); void UiFile_hide (void); /* Hides the visible UiFile that was opened most recently. Normally, file selectors stay open until their okCallback has completed. However, the okCallback may initiate an event loop allowing the user to interact with the application, for instance in Melder_pause (). In order that the user does not have to hide the modal file selector manually (by clicking the Cancel button), the application can call UiFile_hide () before Melder_pause (). */ void UiHistory_write (const wchar_t *string); wchar *UiHistory_get (void); void UiHistory_clear (void); void Ui_setAllowExecutionHook (bool (*allowExecutionHook) (void *closure), void *allowExecutionClosure); void UiForm_widgetsToValues (I); void UiForm_Interpreter_addVariables (I, Interpreter interpreter); int UiForm_getClickedContinueButton (UiForm me); /* End of file Ui.h */ #endif sources_5316/sys/praat.cpp0000644000176700017670000016161711753752517014405 0ustar paulpaul/* praat.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2003/03/12 preferences in home directory on shared Windows machines * pb 2003/06/19 NUMmachar * pb 2003/07/10 GSL initialization * pb 2003/10/03 praat-executeFromFile without arguments * pb 2004/06/17 made Objects label visible on Unix * pb 2004/12/29 removed .praat-user-startUp for Windows (empty file name error) * pb 2005/06/28 TextEditor_prefs * pb 2005/08/22 renamed Control menu to "Praat" * pb 2005/11/18 URL support * pb 2006/02/23 corrected callbacks in praat_installEditorN * pb 2006/08/07 removed quotes from around file paths in openDocument message * pb 2006/09/30 praat_selection () can take NULL as an argument * pb 2006/10/28 removed MacOS 9 stuff * pb 2006/12/26 theCurrentPraat * pb 2007/01/25 width of object list is 50 procent * pb 2007/06/10 wchar_t * pb 2007/06/16 text encoding prefs * pb 2007/08/31 praat_new1-9 * pb 2007/09/02 include Editor prefs * sdk 2008/01/14 GTK * pb 2008/02/01 made sure that praat_dataChanged can be called at error time * pb 2008/03/13 Windows: better file dropping * pb 2008/04/09 removed explicit GSL * pb 2008/11/01 praatcon -a * pb 2009/01/17 arguments to UiForm callbacks * pb 2009/03/17 split up theCurrentPraat into Application, Objects and Picture * pb 2009/12/22 invokingButtonTitle * pb 2010/05/24 sendpraat for GTK * pb 2010/07/29 removed GuiWindow_show * pb 2010/12/08 can read Collections created from multiple objects read from one file (e.g. a labelled sound file) * pb 2011/07/05 C++ */ #include "melder.h" #include "NUMmachar.h" #include #include #if defined (UNIX) || defined (macintosh) #include #include #include #include #endif #if defined (UNIX) || defined __MWERKS__ #include #endif #include "praatP.h" #include "praat_script.h" #include "site.h" #include "machine.h" #include "Printer.h" #include "ScriptEditor.h" #include "Strings.h" #if gtk #include #endif #define EDITOR theCurrentPraatObjects -> list [IOBJECT]. editors #define WINDOW_WIDTH 520 #define WINDOW_HEIGHT 700 structPraatApplication theForegroundPraatApplication; PraatApplication theCurrentPraatApplication = & theForegroundPraatApplication; structPraatObjects theForegroundPraatObjects; PraatObjects theCurrentPraatObjects = & theForegroundPraatObjects; structPraatPicture theForegroundPraatPicture; PraatPicture theCurrentPraatPicture = & theForegroundPraatPicture; struct PraatP praatP; static int doingCommandLineInterface; static char programName [64]; static structMelderDir homeDir = { { 0 } }; /* * praatDirectory: preferences and buttons files. * Unix: /u/miep/.myProg-dir (without slash) * Windows 2000/XP/Vista: \\myserver\myshare\Miep\MyProg * or: C:\Documents and settings\Miep\MyProg * Mac X: /Users/Miep/Library/Preferences/MyProg Prefs */ extern structMelderDir praatDir; structMelderDir praatDir = { { 0 } }; /* * prefs5File: preferences file. * Unix: /u/miep/.myProg-dir/prefs5 * Windows 2000/XP/Vista: \\myserver\myshare\Miep\MyProg\Preferences5.ini * or: C:\Documents and settings\Miep\MyProg\Preferences5.ini * Mac X: /Users/Miep/Library/Preferences/MyProg Prefs/Prefs5 */ static structMelderFile prefs4File = { 0 }, prefs5File = { 0 }; /* * buttons5File: buttons file. * Unix: /u/miep/.myProg-dir/buttons * Windows 2000/XP/Vista: \\myserver\myshare\Miep\MyProg\Buttons5.ini * or: C:\Documents and settings\Miep\MyProg\Buttons5.ini * Mac X: /Users/Miep/Library/Preferences/MyProg Prefs/Buttons5 */ static structMelderFile buttons4File = { 0 }, buttons5File = { 0 }; #if defined (UNIX) static structMelderFile pidFile = { 0 }; /* Like /u/miep/.myProg-dir/pid */ static structMelderFile messageFile = { 0 }; /* Like /u/miep/.myProg-dir/message */ #elif defined (_WIN32) static structMelderFile messageFile = { 0 }; /* Like C:\Windows\myProg\Message.txt */ #endif static GuiObject praatList_objects; /***** selection *****/ long praat_getIdOfSelected (ClassInfo klas, int inplace) { int place = inplace, IOBJECT; if (place == 0) place = 1; if (place > 0) { WHERE (SELECTED && (klas == NULL || CLASS == klas)) { if (place == 1) return ID; place --; } } else { WHERE_DOWN (SELECTED && (klas == NULL || CLASS == klas)) { if (place == -1) return ID; place ++; } } if (inplace) { Melder_throw ("No ", klas ? klas -> className : L"object", " #", inplace, " selected."); } else { Melder_throw ("No ", klas ? klas -> className : L"object", " selected."); } return 0; } wchar * praat_getNameOfSelected (ClassInfo klas, int inplace) { int place = inplace, IOBJECT; if (place == 0) place = 1; if (place > 0) { WHERE (SELECTED && (klas == NULL || CLASS == klas)) { if (place == 1) return klas == NULL ? FULL_NAME : NAME; place --; } } else { WHERE_DOWN (SELECTED && (klas == NULL || CLASS == klas)) { if (place == -1) return klas == NULL ? FULL_NAME : NAME; place ++; } } if (inplace) { Melder_throw ("No ", klas ? klas -> className : L"object", " #", inplace, " selected."); } else { Melder_throw ("No ", klas ? klas -> className : L"object", " selected."); } return 0; // Failure. } int praat_selection (ClassInfo klas) { if (klas == NULL) return theCurrentPraatObjects -> totalSelection; long readableClassId = klas -> sequentialUniqueIdOfReadableClass; if (readableClassId == 0) Melder_fatal ("No sequential unique ID for class %ls.", klas -> className); return theCurrentPraatObjects -> numberOfSelected [readableClassId]; } void praat_deselect (int IOBJECT) { if (! SELECTED) return; SELECTED = FALSE; theCurrentPraatObjects -> totalSelection -= 1; long readableClassId = ((Thing) theCurrentPraatObjects -> list [IOBJECT]. object) -> classInfo -> sequentialUniqueIdOfReadableClass; Melder_assert (readableClassId != 0); theCurrentPraatObjects -> numberOfSelected [readableClassId] -= 1; if (! theCurrentPraatApplication -> batch && ! Melder_backgrounding) { GuiList_deselectItem (praatList_objects, IOBJECT); } } void praat_deselectAll (void) { int IOBJECT; WHERE (1) praat_deselect (IOBJECT); } void praat_select (int IOBJECT) { if (SELECTED) return; SELECTED = TRUE; theCurrentPraatObjects -> totalSelection += 1; Thing object = (Thing) theCurrentPraatObjects -> list [IOBJECT]. object; Melder_assert (object != NULL); long readableClassId = object -> classInfo -> sequentialUniqueIdOfReadableClass; if (readableClassId == 0) Melder_fatal ("No sequential unique ID for class %ls.", object -> classInfo -> className); theCurrentPraatObjects -> numberOfSelected [readableClassId] += 1; if (! theCurrentPraatApplication -> batch && ! Melder_backgrounding) { GuiList_selectItem (praatList_objects, IOBJECT); } } void praat_selectAll (void) { int IOBJECT; WHERE (1) praat_select (IOBJECT); } void praat_list_background (void) { int IOBJECT; WHERE (SELECTED) GuiList_deselectItem (praatList_objects, IOBJECT); } void praat_list_foreground (void) { int IOBJECT; WHERE (SELECTED) { GuiList_selectItem (praatList_objects, IOBJECT); } } Data praat_onlyObject (ClassInfo klas) { int IOBJECT, result = 0, found = 0; WHERE (SELECTED && CLASS == klas) { result = IOBJECT; found += 1; } if (found != 1) return NULL; return theCurrentPraatObjects -> list [result]. object; } Data praat_firstObject (ClassInfo klas) { int IOBJECT; LOOP { if (CLASS == klas) return theCurrentPraatObjects -> list [IOBJECT]. object; } return NULL; // this is often OK } Data praat_onlyObject_generic (ClassInfo klas) { int IOBJECT, result = 0, found = 0; WHERE (SELECTED && Thing_subclass ((ClassInfo) CLASS, klas)) { result = IOBJECT; found += 1; } if (found != 1) return NULL; return theCurrentPraatObjects -> list [result]. object; } Data praat_firstObject_generic (ClassInfo klas) { int IOBJECT; LOOP { if (Thing_subclass ((ClassInfo) CLASS, klas)) return theCurrentPraatObjects -> list [IOBJECT]. object; } return NULL; // this is often OK } praat_Object praat_onlyScreenObject (void) { int IOBJECT, result = 0, found = 0; WHERE (SELECTED) { result = IOBJECT; found += 1; } if (found != 1) Melder_fatal ("praat_onlyScreenObject: found %d objects instead of 1.", found); return & theCurrentPraatObjects -> list [result]; } Data praat_firstObject_any () { int IOBJECT; LOOP { return theCurrentPraatObjects -> list [IOBJECT]. object; } return NULL; // this is often OK } Collection praat_getSelectedObjects (void) { autoCollection thee = Collection_create (NULL, 10); Collection_dontOwnItems (thee.peek()); int IOBJECT; LOOP { iam_LOOP (Data); Collection_addItem (thee.peek(), me); } return thee.transfer(); } wchar_t *praat_name (int IOBJECT) { return wcschr (FULL_NAME, ' ') + 1; } void praat_write_do (Any dia, const wchar_t *extension) { int IOBJECT, found = 0; Data data = NULL; static MelderString defaultFileName = { 0 }; MelderString_empty (& defaultFileName); WHERE (SELECTED) { if (! data) data = (Data) OBJECT; found += 1; } if (found == 1) { MelderString_append (& defaultFileName, data -> name); if (defaultFileName.length > 50) { defaultFileName.string [50] = '\0'; defaultFileName.length = 50; } MelderString_append (& defaultFileName, L".", extension ? extension : Thing_className (data)); } else if (extension == NULL) { MelderString_append (& defaultFileName, L"praat.Collection"); } else { MelderString_append (& defaultFileName, L"praat.", extension); } UiOutfile_do (dia, defaultFileName.string); } static void removeAllReferencesToEditor (Any editor) { int iobject, ieditor; /* * Remove all references to this editor. * It may be editing multiple objects. */ for (iobject = 1; iobject <= theCurrentPraatObjects -> n; iobject ++) for (ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) if (theCurrentPraatObjects -> list [iobject]. editors [ieditor] == editor) theCurrentPraatObjects -> list [iobject]. editors [ieditor] = NULL; if (praatP. editor == editor) praatP. editor = NULL; } static void praat_remove (int iobject) { /* Remove the "object" from the list. */ /* Kill everything to do with selection. */ int ieditor; Melder_assert (iobject >= 1 && iobject <= theCurrentPraatObjects -> n); if (theCurrentPraatObjects -> list [iobject]. _beingCreated) { theCurrentPraatObjects -> list [iobject]. _beingCreated = FALSE; theCurrentPraatObjects -> totalBeingCreated --; } praat_deselect (iobject); /* * To prevent synchronization problems, kill editors before killing the data. */ for (ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) { Editor editor = (Editor) theCurrentPraatObjects -> list [iobject]. editors [ieditor]; /* Save this one reference. */ if (editor) { removeAllReferencesToEditor (editor); forget (editor); } } MelderFile_setToNull (& theCurrentPraatObjects -> list [iobject]. file); Melder_free (theCurrentPraatObjects -> list [iobject]. name); forget (theCurrentPraatObjects -> list [iobject]. object); } void praat_cleanUpName (wchar_t *name) { /* * Replaces spaces and special characters by underscores. */ for (; *name; name ++) { #if 1 if (wcschr (L" ,.:;\\/()[]{}~`\'<>*&^%#@!?$\"|", *name)) *name = '_'; #else if (! iswalnum (*name) && *name != '-' && *name != '+') *name = '_'; #endif } } /***** objects + commands *****/ void praat_newWithFile1 (Data me, const wchar *myName, MelderFile file) { int IOBJECT, ieditor; // must be local: praat_new can be called from within a loop!!! if (me == NULL) Melder_throw ("No object was put into the list."); /* * If my class is Collection, I'll have to be unpacked. */ if (my classInfo == classCollection) { Collection list = (Collection) me; try { for (long idata = 1; idata <= list -> size; idata ++) { Data object = (Data) list -> item [idata]; const wchar *name = object -> name ? object -> name : myName; Melder_assert (name != NULL); praat_new1 (object, name); // recurse } } catch (MelderError) { list -> size = 0; // disown forget (list); throw; } list -> size = 0; // disown forget (list); return; } MelderString name = { 0 }, givenName = { 0 }; if (myName && myName [0]) { MelderString_copy (& givenName, myName); /* * Remove extension. */ wchar *p = wcsrchr (givenName.string, '.'); if (p) *p = '\0'; praat_cleanUpName (givenName.string); } else { MelderString_copy (& givenName, my name && my name [0] ? my name : L"untitled"); } MelderString_append (& name, Thing_className (me), L" ", givenName.string); if (theCurrentPraatObjects -> n == praat_MAXNUM_OBJECTS) { forget (me); Melder_throw ("The Object Window cannot contain more than ", praat_MAXNUM_OBJECTS, " objects. You could remove some objects."); } IOBJECT = ++ theCurrentPraatObjects -> n; Melder_assert (FULL_NAME == NULL); FULL_NAME = Melder_wcsdup_f (name.string); // all right to crash if out of memory ++ theCurrentPraatObjects -> uniqueId; if (! theCurrentPraatApplication -> batch) { // put a new object on the screen, at the bottom of the list #ifdef UNIX #if motif XtVaSetValues (praatList_objects, XmNvisibleItemCount, theCurrentPraatObjects -> n + 2, NULL); #endif #endif MelderString listName = { 0 }; MelderString_append (& listName, Melder_integer (theCurrentPraatObjects -> uniqueId), L". ", name.string); GuiList_insertItem (praatList_objects, listName.string, theCurrentPraatObjects -> n); MelderString_free (& listName); } OBJECT = me; SELECTED = FALSE; CLASS = my classInfo; for (ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) EDITOR [ieditor] = NULL; if (file != NULL) { MelderFile_copy (file, & theCurrentPraatObjects -> list [IOBJECT]. file); } else { MelderFile_setToNull (& theCurrentPraatObjects -> list [IOBJECT]. file); } ID = theCurrentPraatObjects -> uniqueId; theCurrentPraatObjects -> list [IOBJECT]. _beingCreated = TRUE; Thing_setName ((Thing) OBJECT, givenName.string); theCurrentPraatObjects -> totalBeingCreated ++; MelderString_free (& givenName); MelderString_free (& name); } static MelderString thePraatNewName = { 0 }; void praat_newWithFile2 (Data me, const wchar *s1, const wchar *s2, MelderFile file) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2); praat_newWithFile1 (me, thePraatNewName.string, file); } void praat_newWithFile3 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, MelderFile file) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3); praat_newWithFile1 (me, thePraatNewName.string, file); } void praat_newWithFile4 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, MelderFile file) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3, s4); praat_newWithFile1 (me, thePraatNewName.string, file); } void praat_newWithFile5 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, MelderFile file) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3, s4, s5); praat_newWithFile1 (me, thePraatNewName.string, file); } void praat_new1 (Data me, const wchar *s1) { praat_newWithFile1 (me, s1, NULL); } void praat_new2 (Data me, const wchar *s1, const wchar *s2) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2); praat_new1 (me, thePraatNewName.string); } void praat_new3 (Data me, const wchar *s1, const wchar *s2, const wchar *s3) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3); praat_new1 (me, thePraatNewName.string); } void praat_new4 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3, s4); return praat_new1 (me, thePraatNewName.string); } void praat_new5 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3, s4, s5); praat_new1 (me, thePraatNewName.string); } void praat_new6 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3, s4, s5, s6); praat_new1 (me, thePraatNewName.string); } void praat_new7 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3, s4, s5, s6, s7); praat_new1 (me, thePraatNewName.string); } void praat_new8 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3, s4, s5, s6, s7, s8); praat_new1 (me, thePraatNewName.string); } void praat_new9 (Data me, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9) { MelderString_empty (& thePraatNewName); MelderString_append (& thePraatNewName, s1, s2, s3, s4, s5, s6, s7, s8, s9); praat_new1 (me, thePraatNewName.string); } void praat_updateSelection (void) { if (theCurrentPraatObjects -> totalBeingCreated) { int IOBJECT; praat_deselectAll (); WHERE (theCurrentPraatObjects -> list [IOBJECT]. _beingCreated) { praat_select (IOBJECT); theCurrentPraatObjects -> list [IOBJECT]. _beingCreated = FALSE; } theCurrentPraatObjects -> totalBeingCreated = 0; praat_show (); } } static void gui_cb_list (void *void_me, GuiListEvent event) { (void) event; (void) void_me; int IOBJECT, first = TRUE; WHERE (SELECTED) { SELECTED = FALSE; long readableClassId = ((Thing) theCurrentPraatObjects -> list [IOBJECT]. object) -> classInfo -> sequentialUniqueIdOfReadableClass; theCurrentPraatObjects -> numberOfSelected [readableClassId] --; Melder_assert (theCurrentPraatObjects -> numberOfSelected [readableClassId] >= 0); } theCurrentPraatObjects -> totalSelection = 0; long numberOfSelected, *selected = GuiList_getSelectedPositions (praatList_objects, & numberOfSelected); if (selected != NULL) { for (long iselected = 1; iselected <= numberOfSelected; iselected ++) { IOBJECT = selected [iselected]; SELECTED = TRUE; long readableClassId = ((Thing) theCurrentPraatObjects -> list [IOBJECT]. object) -> classInfo -> sequentialUniqueIdOfReadableClass; theCurrentPraatObjects -> numberOfSelected [readableClassId] ++; Melder_assert (theCurrentPraatObjects -> numberOfSelected [readableClassId] > 0); UiHistory_write (first ? L"\nselect " : L"\nplus "); UiHistory_write (FULL_NAME); first = FALSE; theCurrentPraatObjects -> totalSelection += 1; } NUMvector_free (selected, 1); } praat_show (); } void praat_list_renameAndSelect (int position, const wchar_t *name) { if (! theCurrentPraatApplication -> batch) { GuiList_replaceItem (praatList_objects, name, position); /* Void if name equal. */ if (! Melder_backgrounding) GuiList_selectItem (praatList_objects, position); } } /***** objects *****/ void praat_name2 (wchar *name, ClassInfo klas1, ClassInfo klas2) { int i1 = 1, i2; wchar_t *name1, *name2; while (theCurrentPraatObjects -> list [i1]. selected == 0 || theCurrentPraatObjects -> list [i1]. klas != klas1) i1 ++; i2 = 1; /* This late initialization works around a Think C BUG. */ while (theCurrentPraatObjects -> list [i2]. selected == 0 || theCurrentPraatObjects -> list [i2]. klas != klas2) i2 ++; name1 = wcschr (theCurrentPraatObjects -> list [i1]. name, ' ') + 1; name2 = wcschr (theCurrentPraatObjects -> list [i2]. name, ' ') + 1; if (wcsequ (name1, name2)) wcscpy (name, name1); else swprintf (name, 200, L"%ls_%ls", name1, name2); } void praat_removeObject (int i) { int j, ieditor; praat_remove (i); /* Dangle. */ for (j = i; j < theCurrentPraatObjects -> n; j ++) theCurrentPraatObjects -> list [j] = theCurrentPraatObjects -> list [j + 1]; /* Undangle but create second references. */ theCurrentPraatObjects -> list [theCurrentPraatObjects -> n]. name = NULL; /* Undangle or remove second reference. */ theCurrentPraatObjects -> list [theCurrentPraatObjects -> n]. object = NULL; /* Undangle or remove second reference. */ theCurrentPraatObjects -> list [theCurrentPraatObjects -> n]. selected = 0; for (ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) theCurrentPraatObjects -> list [theCurrentPraatObjects -> n]. editors [ieditor] = NULL; /* Undangle or remove second reference. */ MelderFile_setToNull (& theCurrentPraatObjects -> list [theCurrentPraatObjects -> n]. file); /* Undangle or remove second reference. */ -- theCurrentPraatObjects -> n; if (! theCurrentPraatApplication -> batch) { GuiList_deleteItem (praatList_objects, i); #ifdef UNIX //XtVaSetValues (praatList_objects, XmNvisibleItemCount, theCurrentPraatObjects -> n + 1, NULL); #endif } } static void praat_exit (int exit_code) { int IOBJECT; #ifdef _WIN32 if (! theCurrentPraatApplication -> batch) XtDestroyWidget (theCurrentPraatApplication -> topShell); #endif praat_picture_exit (); praat_statistics_exit (); /* Record total memory use across sessions. */ /* * Stop receiving messages. */ #if defined (UNIX) /* * We are going to delete the process id ("pid") file, if it's ours. */ if (pidFile. path [0]) { try { /* * To see whether we own the pid file, * we look into it to see whether its pid equals our pid. * If not, then we are probably living in an old invocation of the program, * and the pid file was written by the latest invocation of the program, * which owns the pid (this means sendpraat can only send to the latest Praat if more than one are open). */ autofile f = Melder_fopen (& pidFile, "r"); long pid; if (fscanf (f, "%ld", & pid) < 1) throw MelderError (); f.close (& pidFile); if (pid == getpid ()) { // is the pid in the pid file equal to our pid? MelderFile_delete (& pidFile); // ...then we own the pid file and can delete it } } catch (MelderError) { Melder_clearError (); // if the pid file is somehow missing or corrupted, we just ignore that } } #endif /* * Save the preferences. */ Preferences_write (& prefs5File); MelderFile_setMacTypeAndCreator (& prefs5File, 'pref', 'PpgB'); /* * Save the script buttons. */ if (! theCurrentPraatApplication -> batch) { try { autofile f = Melder_fopen (& buttons5File, "wb"); fwprintf (f, L"\ufeff# Buttons (1).\n"); fwprintf (f, L"# This file is generated automatically when you quit the %ls program.\n", Melder_peekUtf8ToWcs (praatP.title)); fwprintf (f, L"# It contains the buttons that you added interactively to the fixed or dynamic menus,\n"); fwprintf (f, L"# and the buttons that you hid or showed.\n\n"); praat_saveMenuCommands (f); praat_saveAddedActions (f); f.close (& buttons5File); MelderFile_setMacTypeAndCreator (& buttons5File, 'pref', 'PpgB'); } catch (MelderError) { Melder_clearError (); } } /* * Flush the file-based objects. */ WHERE_DOWN (! MelderFile_isNull (& theCurrentPraatObjects -> list [IOBJECT]. file)) praat_remove (IOBJECT); Melder_files_cleanUp (); /* If a URL is open. */ /* * Finally, leave the program. */ exit (exit_code); } static void cb_Editor_destruction (Editor me, void *closure) { (void) closure; removeAllReferencesToEditor (me); // remove reference(s) to moribund Editor } static void cb_Editor_dataChanged (Editor me, void *closure) { (void) closure; for (int iobject = 1; iobject <= theCurrentPraatObjects -> n; iobject ++) { bool editingThisObject = false; /* * Am I editing this object? */ for (int ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) { if (theCurrentPraatObjects -> list [iobject]. editors [ieditor] == me) { editingThisObject = true; } } if (editingThisObject) { /* * Notify all other editors associated with this object. */ for (int ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) { Editor otherEditor = (Editor) theCurrentPraatObjects -> list [iobject]. editors [ieditor]; if (otherEditor != NULL && otherEditor != me) { otherEditor -> dataChanged (); } } } } } static void cb_Editor_publication (Editor me, void *closure, Data publication) { /* The default publish callback. Works nicely if the publisher invents a name. */ (void) me; (void) closure; try { praat_new1 (publication, NULL); } catch (MelderError) { Melder_flushError (NULL); } praat_updateSelection (); } int praat_installEditor (Editor editor, int IOBJECT) { if (editor == NULL) return 0; for (int ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) { if (EDITOR [ieditor] == NULL) { EDITOR [ieditor] = editor; editor -> setDestructionCallback (cb_Editor_destruction, NULL); editor -> setDataChangedCallback (cb_Editor_dataChanged, NULL); if (! editor -> d_publicationCallback) editor -> setPublicationCallback (cb_Editor_publication, NULL); return 1; } } forget (editor); Melder_throw ("(praat_installEditor:) Cannot have more than ", praat_MAXNUM_EDITORS, " editors with one object."); } int praat_installEditor2 (Editor editor, int i1, int i2) { if (editor == NULL) return 0; int ieditor1 = 0; for (; ieditor1 < praat_MAXNUM_EDITORS; ieditor1 ++) if (theCurrentPraatObjects -> list [i1]. editors [ieditor1] == NULL) break; int ieditor2 = 0; for (; ieditor2 < praat_MAXNUM_EDITORS; ieditor2 ++) if (theCurrentPraatObjects -> list [i2]. editors [ieditor2] == NULL) break; if (ieditor1 < praat_MAXNUM_EDITORS && ieditor2 < praat_MAXNUM_EDITORS) { theCurrentPraatObjects -> list [i1]. editors [ieditor1] = theCurrentPraatObjects -> list [i2]. editors [ieditor2] = editor; editor -> setDestructionCallback (cb_Editor_destruction, NULL); editor -> setDataChangedCallback (cb_Editor_dataChanged, NULL); if (! editor -> d_publicationCallback) editor -> setPublicationCallback (cb_Editor_publication, NULL); } else { forget (editor); Melder_throw ("(praat_installEditor2:) Cannot have more than ", praat_MAXNUM_EDITORS, " editors with one object."); } return 1; } int praat_installEditor3 (Editor editor, int i1, int i2, int i3) { if (! editor) return 0; int ieditor1 = 0; for (; ieditor1 < praat_MAXNUM_EDITORS; ieditor1 ++) if (theCurrentPraatObjects -> list [i1]. editors [ieditor1] == NULL) break; int ieditor2 = 0; for (; ieditor2 < praat_MAXNUM_EDITORS; ieditor2 ++) if (theCurrentPraatObjects -> list [i2]. editors [ieditor2] == NULL) break; int ieditor3 = 0; for (; ieditor3 < praat_MAXNUM_EDITORS; ieditor3 ++) if (theCurrentPraatObjects -> list [i3]. editors [ieditor3] == NULL) break; if (ieditor1 < praat_MAXNUM_EDITORS && ieditor2 < praat_MAXNUM_EDITORS && ieditor3 < praat_MAXNUM_EDITORS) { theCurrentPraatObjects -> list [i1]. editors [ieditor1] = theCurrentPraatObjects -> list [i2]. editors [ieditor2] = theCurrentPraatObjects -> list [i3]. editors [ieditor3] = editor; editor -> setDestructionCallback (cb_Editor_destruction, NULL); editor -> setDataChangedCallback (cb_Editor_dataChanged, NULL); if (! editor -> d_publicationCallback) editor -> setPublicationCallback (cb_Editor_publication, NULL); } else { forget (editor); Melder_throw ("(praat_installEditor3:) Cannot have more than ", praat_MAXNUM_EDITORS, " editors with one object."); } return 1; } int praat_installEditorN (Editor editor, Ordered objects) { long iOrderedObject, iPraatObject; if (editor == NULL) return 0; /* * First check whether all objects in the Ordered are also in the List of Objects (Praat crashes if not), * and check whether there is room to add an editor for each. */ for (iOrderedObject = 1; iOrderedObject <= objects -> size; iOrderedObject ++) { Data object = (Data) objects -> item [iOrderedObject]; for (iPraatObject = 1; iPraatObject <= theCurrentPraatObjects -> n; iPraatObject ++) { if (object == theCurrentPraatObjects -> list [iPraatObject]. object) { int ieditor = 0; for (; ieditor < praat_MAXNUM_EDITORS; ieditor ++) { if (theCurrentPraatObjects -> list [iPraatObject]. editors [ieditor] == NULL) { break; } } if (ieditor >= praat_MAXNUM_EDITORS) { forget (editor); Melder_throw ("Cannot view the same object in more than ", praat_MAXNUM_EDITORS, " windows."); } break; } } Melder_assert (iPraatObject <= theCurrentPraatObjects -> n); /* An element of the Ordered does not occur in the List of Objects. */ } /* * There appears to be room for all elements of the Ordered. The editor window can appear. Install the editor in all objects. */ for (iOrderedObject = 1; iOrderedObject <= objects -> size; iOrderedObject ++) { Data object = (Data) objects -> item [iOrderedObject]; for (iPraatObject = 1; iPraatObject <= theCurrentPraatObjects -> n; iPraatObject ++) { if (object == theCurrentPraatObjects -> list [iPraatObject]. object) { int ieditor = 0; for (; ieditor < praat_MAXNUM_EDITORS; ieditor ++) { if (theCurrentPraatObjects -> list [iPraatObject]. editors [ieditor] == NULL) { theCurrentPraatObjects -> list [iPraatObject]. editors [ieditor] = editor; editor -> setDestructionCallback (cb_Editor_destruction, NULL); editor -> setDataChangedCallback (cb_Editor_dataChanged, NULL); if (! editor -> d_publicationCallback) editor -> setPublicationCallback (cb_Editor_publication, NULL); break; } } Melder_assert (ieditor < praat_MAXNUM_EDITORS); /* We just checked, but nevertheless. */ break; } } Melder_assert (iPraatObject <= theCurrentPraatObjects -> n); /* We already checked, but still. */ } return 1; } void praat_dataChanged (Any object) { /* * This function can be called at error time, which is weird. */ wchar *saveError = NULL; bool duringError = Melder_hasError (); if (duringError) { saveError = Melder_wcsdup_f (Melder_getError ()); Melder_clearError (); } int IOBJECT; WHERE (OBJECT == object) { for (int ieditor = 0; ieditor < praat_MAXNUM_EDITORS; ieditor ++) { Editor editor = (Editor) EDITOR [ieditor]; if (editor != NULL) { editor -> dataChanged (); } } } if (duringError) { Melder_error_ (saveError); // BUG: this appends an empty newline to the original error message Melder_free (saveError); // BUG: who will catch the error? } } static void helpProc (const wchar_t *query) { if (theCurrentPraatApplication -> batch) { Melder_flushError ("Cannot view manual from batch."); return; } try { Manual_create (theCurrentPraatApplication -> topShell, query, theCurrentPraatApplication -> manPages, false); } catch (MelderError) { Melder_flushError ("help: no help on \"%ls\".", query); } } static int publishProc (void *anything) { try { praat_new1 ((Data) anything, NULL); praat_updateSelection (); return 1; } catch (MelderError) { Melder_throw ("Not published."); } } /***** QUIT *****/ FORM (Quit, L"Confirm Quit", L"Quit") LABEL (L"label", L"You have objects in your list!") OK { wchar_t prompt [300]; if (ScriptEditors_dirty ()) { if (theCurrentPraatObjects -> n) swprintf (prompt, 300, L"You have objects and unsaved scripts! Do you still want to quit %ls?", Melder_peekUtf8ToWcs (praatP.title)); else swprintf (prompt, 300, L"You have unsaved scripts! Do you still want to quit %ls?", Melder_peekUtf8ToWcs (praatP.title)); SET_STRING (L"label", prompt); } else if (theCurrentPraatObjects -> n) { swprintf (prompt, 300, L"You have objects in your list! Do you still want to quit %ls?", Melder_peekUtf8ToWcs (praatP.title)); SET_STRING (L"label", prompt); } else { praat_exit (0); } } DO praat_exit (0); END static void gui_cb_quit (GUI_ARGS) { (void) w; (void) void_me; (void) call; DO_Quit (NULL, NULL, NULL, NULL, NULL, NULL); } #if gtk static void gui_cb_quit_gtk (void *p) { DO_Quit (NULL, NULL, NULL, NULL, NULL, NULL); } #endif void praat_dontUsePictureWindow (void) { praatP.dontUsePictureWindow = TRUE; } /********** INITIALIZATION OF THE PRAAT SHELL **********/ #if defined (UNIX) static gboolean cb_userMessage (GtkWidget widget, GdkEventClient *event, gpointer user_data) { (void) widget; (void) user_data; autofile f; try { f.reset (Melder_fopen (& messageFile, "r")); } catch (MelderError) { Melder_clearError (); return true; // OK } long pid; int narg = fscanf (f, "#%ld", & pid); f.close (& messageFile); { // scope autoPraatBackground background; try { praat_executeScriptFromFile (& messageFile, NULL); } catch (MelderError) { Melder_error_ (Melder_peekUtf8ToWcs (praatP.title), L": message not completely handled."); Melder_flushError (NULL); } } if (narg) kill (pid, SIGUSR2); return true; } #elif defined (_WIN32) static int cb_userMessage (void) { autoPraatBackground background; try { praat_executeScriptFromFile (& messageFile, NULL); } catch (MelderError) { Melder_error_ (Melder_peekUtf8ToWcs (praatP.title), L": message not completely handled."); Melder_flushError (NULL); } return 0; } extern "C" char *sendpraat (void *display, const char *programName, long timeOut, const char *text); extern "C" wchar *sendpraatW (void *display, const wchar *programName, long timeOut, const wchar *text); static void cb_openDocument (MelderFile file) { wchar text [500]; wchar *s = file -> path; swprintf (text, 500, L"Read from file... %ls", s [0] == ' ' && s [1] == '\"' ? s + 2 : s [0] == '\"' ? s + 1 : s); long l = wcslen (text); if (l > 0 && text [l - 1] == '\"') text [l - 1] = '\0'; sendpraatW (NULL, Melder_peekUtf8ToWcs (praatP.title), 0, text); } #elif defined (macintosh) static int cb_userMessageA (char *messageA) { autoPraatBackground background; autostring message = Melder_8bitToWcs (messageA, 0); try { praat_executeScriptFromText (message.peek()); } catch (MelderError) { Melder_error_ (praatP.title, ": message not completely handled."); Melder_flushError (NULL); } return 0; } static int cb_userMessageW (wchar *message) { autoPraatBackground background; try { praat_executeScriptFromText (message); } catch (MelderError) { Melder_error_ (praatP.title, ": message not completely handled."); Melder_flushError (NULL); } return 0; } static int cb_quitApplication (void) { DO_Quit (NULL, NULL, NULL, NULL, NULL, NULL); return 0; } #endif static wchar * thePraatStandAloneScriptText = NULL; void praat_setStandAloneScriptText (wchar *text) { thePraatStandAloneScriptText = text; } void praat_init (const char *title, unsigned int argc, char **argv) { static char truncatedTitle [300]; /* Static because praatP.title will point into it. */ #if defined (UNIX) setlocale (LC_ALL, "C"); #elif defined (macintosh) setlocale (LC_ALL, "en_US"); // required to make swprintf work correctly; the default "C" locale does not do that! #endif char *p; #ifdef macintosh Gestalt ('sysv', (long *) & Melder_systemVersion); #endif /* Initialize numerical libraries. */ NUMmachar (); NUMinit (); Melder_alloc_init (); /* Remember the current directory. Only useful for scripts run from batch. */ Melder_rememberShellDirectory (); /* * Install the preferences of the Praat shell, and set the defaults. */ praat_statistics_prefs (); // Number of sessions, memory used... praat_picture_prefs (); // Font... Editor_prefs (); // Erase picture first... HyperPage_prefs (); // Font... Site_prefs (); // Print command... Melder_audio_prefs (); // Use speaker (Sun & HP), output gain (HP)... Melder_textEncoding_prefs (); Printer_prefs (); // Paper size, printer command... TextEditor_prefs (); // Font size... unsigned int iarg_batchName = 1; #if defined (UNIX) || defined (macintosh) || defined (_WIN32) && defined (CONSOLE_APPLICATION) /* * Running the Praat shell from the Unix command line, * or running PRAATCON.EXE from the Windows command prompt: * */ if (argc > iarg_batchName && argv [iarg_batchName] [0] == '-' && argv [iarg_batchName] [1] == 'a' && argv [iarg_batchName] [2] == '\0') { Melder_consoleIsAnsi = true; iarg_batchName ++; } //fprintf (stdout, "Console <%d> <%s>", Melder_consoleIsAnsi, argv [1]); bool hasCommandLineInput = argc > iarg_batchName && argv [iarg_batchName] [0] == '-' && argv [iarg_batchName] [1] == '\0'; MelderString_copy (& theCurrentPraatApplication -> batchName, hasCommandLineInput ? L"" : argc > iarg_batchName && argv [iarg_batchName] [0] != '-' /* funny Mac test */ ? Melder_peekUtf8ToWcs (argv [iarg_batchName]) : L""); Melder_batch = theCurrentPraatApplication -> batchName.string [0] != '\0' || thePraatStandAloneScriptText != NULL; #if defined (_WIN32) && defined (CONSOLE_APPLICATION) if (! Melder_batch) { fprintf (stderr, "Usage: PRAATCON \n"); exit (0); } #endif /* * Running the Praat shell from the command line: * praat - */ if (hasCommandLineInput) { Melder_batch = true; doingCommandLineInterface = TRUE; /* Read from stdin. */ } /* Take from 'title' ("myProg 3.2" becomes "myProg") or from command line ("/ifa/praat" becomes "praat"). */ strcpy (truncatedTitle, argc && argv [0] [0] ? argv [0] : title && title [0] ? title : "praat"); //Melder_fatal ("<%s>", argv [0]); #else #if defined (_WIN32) MelderString_copy (& theCurrentPraatApplication -> batchName, argv [3] ? Melder_peekUtf8ToWcs (argv [3]) : L""); /* The command line. */ #endif Melder_batch = false; // PRAAT.EXE on Windows is always interactive strcpy (truncatedTitle, title && title [0] ? title : "praat"); #endif theCurrentPraatApplication -> batch = Melder_batch; /* * Construct a program name like "myProg 3.2" by removing directory path. */ p = strrchr (truncatedTitle, Melder_DIRECTORY_SEPARATOR); praatP.title = p ? p + 1 : truncatedTitle; /* * Construct a program name like "myProg" for file and directory names. */ strcpy (programName, praatP.title); if ((p = strchr (programName, ' ')) != NULL) *p = '\0'; #if defined (_WIN32) if ((p = strchr (programName, '.')) != NULL) *p = '\0'; /* Chop off ".exe". */ #endif /* * Construct a main-window title like "MyProg 3.2". */ praatP.title [0] = toupper (praatP.title [0]); /* * Get home directory, e.g. "/home/miep/", or "/Users/miep/", or just "/". */ Melder_getHomeDir (& homeDir); /* * Get the program's private directory: * "/u/miep/myProg-dir" (Unix) * "/Users/miep/Library/Preferences/MyProg Prefs" (Macintosh) * "C:\Documents and Settings\Miep\MyProg" (Windows) * and construct a preferences-file name and a script-buttons-file name like * /u/miep/.myProg-dir/prefs (Unix) * /u/miep/.myProg-dir/script_buttons * or * /Users/miep/Library/Preferences/MyProg Prefs/Prefs * /Users/miep/Library/Preferences/MyProg Prefs/Buttons * or * C:\Documents and Settings\Miep\MyProg\Preferences.ini * C:\Documents and Settings\Miep\MyProg\Buttons.ini * On Unix, also create names for process-id and message files. */ { structMelderDir prefParentDir = { { 0 } }; /* Directory under which to store our preferences directory. */ wchar_t name [256]; Melder_getPrefDir (& prefParentDir); /* * Make sure that the program's private directory exists. */ #if defined (UNIX) swprintf (name, 256, L".%ls-dir", Melder_utf8ToWcs (programName)); /* For example .myProg-dir */ #elif defined (macintosh) swprintf (name, 256, L"%ls Prefs", Melder_utf8ToWcs (praatP.title)); /* For example MyProg Prefs */ #elif defined (_WIN32) swprintf (name, 256, L"%ls", Melder_utf8ToWcs (praatP.title)); /* For example MyProg */ #endif #if defined (UNIX) || defined (macintosh) Melder_createDirectory (& prefParentDir, name, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH); #else Melder_createDirectory (& prefParentDir, name, 0); #endif MelderDir_getSubdir (& prefParentDir, name, & praatDir); #if defined (UNIX) MelderDir_getFile (& praatDir, L"prefs", & prefs4File); MelderDir_getFile (& praatDir, L"prefs5", & prefs5File); MelderDir_getFile (& praatDir, L"buttons", & buttons4File); MelderDir_getFile (& praatDir, L"buttons5", & buttons5File); MelderDir_getFile (& praatDir, L"pid", & pidFile); MelderDir_getFile (& praatDir, L"message", & messageFile); #elif defined (_WIN32) MelderDir_getFile (& praatDir, L"Preferences.ini", & prefs4File); MelderDir_getFile (& praatDir, L"Preferences5.ini", & prefs5File); MelderDir_getFile (& praatDir, L"Buttons.ini", & buttons4File); MelderDir_getFile (& praatDir, L"Buttons5.ini", & buttons5File); MelderDir_getFile (& praatDir, L"Message.txt", & messageFile); #elif defined (macintosh) MelderDir_getFile (& praatDir, L"Prefs", & prefs4File); /* We invite trouble if we call it Preferences! */ MelderDir_getFile (& praatDir, L"Prefs5", & prefs5File); MelderDir_getFile (& praatDir, L"Buttons", & buttons4File); MelderDir_getFile (& praatDir, L"Buttons5", & buttons5File); #endif } #if defined (UNIX) if (! Melder_batch) { /* * Make sure that the directory /u/miep/.myProg-dir exists, * and write our process id into the pid file. * Messages from "sendpraat" are caught very early this way, * though they will be responded to much later. */ try { autofile f = Melder_fopen (& pidFile, "w"); fprintf (f, "%ld", (long) getpid ()); f.close (& pidFile); #if motif signal (SIGUSR1, handleMessage); #endif } catch (MelderError) { Melder_clearError (); } } #elif defined (_WIN32) if (! Melder_batch) motif_win_setUserMessageCallback (cb_userMessage); #elif defined (macintosh) #if useCarbon if (! Melder_batch) { motif_mac_setUserMessageCallbackA (cb_userMessageA); motif_mac_setUserMessageCallbackW (cb_userMessageW); Gui_setQuitApplicationCallback (cb_quitApplication); } #else if (! Melder_batch) { Gui_setQuitApplicationCallback (cb_quitApplication); } #endif #endif /* * Make room for commands. */ praat_actions_init (); praat_menuCommands_init (); GuiObject raam = NULL; if (Melder_batch) { #if defined (UNIX) || defined (macintosh) || defined (_WIN32) && defined (CONSOLE_APPLICATION) MelderString_empty (& theCurrentPraatApplication -> batchName); for (unsigned int i = iarg_batchName; i < argc; i ++) { int needsQuoting = strchr (argv [i], ' ') != NULL && (i == iarg_batchName || i < argc - 1); if (i > 1) MelderString_append (& theCurrentPraatApplication -> batchName, L" "); if (needsQuoting) MelderString_append (& theCurrentPraatApplication -> batchName, L"\""); MelderString_append (& theCurrentPraatApplication -> batchName, Melder_peekUtf8ToWcs (argv [i])); if (needsQuoting) MelderString_append (& theCurrentPraatApplication -> batchName, L"\""); } #elif defined (_WIN32) MelderString_copy (& theCurrentPraatApplication -> batchName, Melder_peekUtf8ToWcs (argv [3])); #endif } else { char objectWindowTitle [100]; Machine_initLookAndFeel (argc, argv); sprintf (objectWindowTitle, "%s Objects", praatP.title); #if gtk g_set_application_name (title); raam = GuiWindow_create (NULL, -1, Gui_AUTOMATIC, -1, 600, Melder_peekUtf8ToWcs (objectWindowTitle), gui_cb_quit_gtk, NULL, 0); theCurrentPraatApplication -> topShell = gtk_widget_get_parent (GTK_WIDGET (raam)); GuiObject_show (theCurrentPraatApplication -> topShell); #elif defined (_WIN32) argv [0] = & praatP. title [0]; /* argc == 4 */ Gui_setOpenDocumentCallback (cb_openDocument); theCurrentPraatApplication -> topShell = GuiAppInitialize ("Praatwulg", NULL, 0, & argc, argv, NULL, NULL); double x, y; Gui_getWindowPositioningBounds (& x, & y, NULL, NULL); XtVaSetValues (theCurrentPraatApplication -> topShell, XmNdeleteResponse, XmDO_NOTHING, XmNtitle, objectWindowTitle, XmNx, (int) x + 10, XmNy, (int) y + 0, NULL); XtVaSetValues (theCurrentPraatApplication -> topShell, XmNheight, WINDOW_HEIGHT, NULL); /* Catch Window Manager "Close" and "Quit". */ XmAddWMProtocolCallback (theCurrentPraatApplication -> topShell, 'delw', gui_cb_quit, 0); #elif defined (macintosh) #if useCarbon theCurrentPraatApplication -> topShell = GuiAppInitialize ("Praatwulg", NULL, 0, & argc, argv, NULL, NULL); double x, y; Gui_getWindowPositioningBounds (& x, & y, NULL, NULL); XtVaSetValues (theCurrentPraatApplication -> topShell, XmNdeleteResponse, XmDO_NOTHING, XmNtitle, objectWindowTitle, XmNx, (int) x + 10, XmNy, (int) y + 0, NULL); XtVaSetValues (theCurrentPraatApplication -> topShell, XmNheight, WINDOW_HEIGHT, NULL); /* Catch Window Manager "Close" and "Quit". */ XmAddWMProtocolCallback (theCurrentPraatApplication -> topShell, 'delw', gui_cb_quit, 0); #else #endif #endif } Thing_recognizeClassesByName (classCollection, classStrings, classManPages, classSortedSetOfString, NULL); if (Melder_batch) { Melder_backgrounding = true; praat_addMenus (NULL); praat_addFixedButtons (NULL); } else { GuiObject Raam = NULL; #if gtk GuiObject raHoriz, raLeft; /* I want to have more possibilities for GTK widgets */ #else #define raHoriz Raam #define raLeft Raam #endif #ifdef macintosh MelderGui_create (theCurrentPraatApplication -> topShell); /* BUG: default Melder_assert would call printf recursively!!! */ #endif #if gtk Raam = raam; #elif motif Raam = XmCreateForm (theCurrentPraatApplication -> topShell, "raam", NULL, 0); #endif #ifdef macintosh GuiObject_size (Raam, WINDOW_WIDTH, Gui_AUTOMATIC); praatP.topBar = Gui_addMenuBar (Raam); GuiObject_show (praatP.topBar); #endif praatP.menuBar = Gui_addMenuBar (Raam); praat_addMenus (praatP.menuBar); GuiObject_show (praatP.menuBar); #ifndef UNIX GuiObject_size (Raam, WINDOW_WIDTH, Gui_AUTOMATIC); #endif #if gtk raHoriz = gtk_hpaned_new (); gtk_container_add (GTK_CONTAINER (Raam), GTK_WIDGET (raHoriz)); raLeft = gtk_vbox_new (FALSE, 0); gtk_container_add (GTK_CONTAINER (raHoriz), GTK_WIDGET (raLeft)); #else GuiLabel_createShown (raLeft, 3, -250, Machine_getMainWindowMenuBarHeight () + 5, Gui_AUTOMATIC, L"Objects:", 0); #endif praatList_objects = GuiList_create (raLeft, 0, -250, Machine_getMainWindowMenuBarHeight () + 26, -100, true, L" Objects "); GuiList_setSelectionChangedCallback (praatList_objects, gui_cb_list, 0); //XtVaSetValues (praatList_objects, XmNvisibleItemCount, 20, NULL); GuiObject_show (praatList_objects); praat_addFixedButtons (raLeft); praat_actions_createDynamicMenu (raHoriz, 250); #if gtk GuiObject_show (raLeft); GuiObject_show (raHoriz); #endif GuiObject_show (Raam); #ifdef UNIX try { autofile f = Melder_fopen (& pidFile, "a"); #if gtk fprintf (f, " %ld", (long) GDK_WINDOW_XID (GDK_DRAWABLE (GTK_WIDGET (theCurrentPraatApplication -> topShell) -> window))); #else fprintf (f, " %ld", (long) XtWindow (theCurrentPraatApplication -> topShell)); #endif f.close (& pidFile); } catch (MelderError) { Melder_clearError (); } #endif #ifdef UNIX Preferences_read (MelderFile_readable (& prefs5File) ? & prefs5File : & prefs4File); #endif #if ! defined (CONSOLE_APPLICATION) && ! defined (macintosh) MelderGui_create (theCurrentPraatApplication -> topShell); /* Mac: done this earlier. */ #endif Melder_setHelpProc (helpProc); } Melder_setPublishProc (publishProc); theCurrentPraatApplication -> manPages = ManPages_create (); if (! praatP.dontUsePictureWindow) praat_picture_init (); } static void executeStartUpFile (MelderDir startUpDirectory, const wchar_t *fileNameTemplate) { wchar name [256]; swprintf (name, 256, fileNameTemplate, Melder_peekUtf8ToWcs (programName)); if (! MelderDir_isNull (startUpDirectory)) { // Should not occur on modern systems. structMelderFile startUp = { 0 }; MelderDir_getFile (startUpDirectory, name, & startUp); if (! MelderFile_readable (& startUp)) return; // it's OK if the file doesn't exist try { praat_executeScriptFromFile (& startUp, NULL); } catch (MelderError) { Melder_error_ (praatP.title, ": start-up file ", & startUp, " not completed."); Melder_flushError (NULL); } } } #if gtk #include static gint theKeySnooper (GtkWidget *widget, GdkEventKey *event, gpointer data) { //Melder_casual ("keyval %ld, type %ld", (long) event -> keyval, (long) event -> type); if ((event -> keyval == GDK_Tab || event -> keyval == GDK_KEY_ISO_Left_Tab) && event -> type == GDK_KEY_PRESS) { //Melder_casual ("tab key pressed in window %ld", widget); if (event -> state == 0) { if (GTK_IS_WINDOW (widget)) { GtkWidget *shell = gtk_widget_get_toplevel (GTK_WIDGET (widget)); //Melder_casual ("tab pressed in window %ld", shell); void (*tabCallback) (GuiObject, XtPointer, XtPointer) = (void (*) (GuiObject, XtPointer, XtPointer)) g_object_get_data (G_OBJECT (widget), "tabCallback"); if (tabCallback) { //Melder_casual ("a tab callback exists"); void *tabClosure = g_object_get_data (G_OBJECT (widget), "tabClosure"); tabCallback (widget, tabClosure, tabClosure); return TRUE; } } } else if (event -> state == GDK_SHIFT_MASK) { // BUG: if (GTK_IS_WINDOW (widget)) { GtkWidget *shell = gtk_widget_get_toplevel (GTK_WIDGET (widget)); //Melder_casual ("shift-tab pressed in window %ld", shell); void (*tabCallback) (GuiObject, XtPointer, XtPointer) = (void (*) (GuiObject, XtPointer, XtPointer)) g_object_get_data (G_OBJECT (widget), "shiftTabCallback"); if (tabCallback) { //Melder_casual ("a shift tab callback exists"); void *tabClosure = g_object_get_data (G_OBJECT (widget), "shiftTabClosure"); tabCallback (widget, tabClosure, tabClosure); return TRUE; } } } } return FALSE; // pass event on } #endif void praat_run (void) { FILE *f; praat_addMenus2 (); #ifdef macintosh praat_addMenuCommand (L"Objects", L"Praat", L"Quit", 0, praat_HIDDEN, DO_Quit); // the Quit command is needed for scripts, not for the GUI #else praat_addMenuCommand (L"Objects", L"Praat", L"-- quit --", 0, 0, 0); praat_addMenuCommand (L"Objects", L"Praat", L"Quit", 0, praat_UNHIDABLE + 'Q', DO_Quit); #endif /* * Read the preferences file, and notify those who want to be notified of this, * namely, those who already have a window (namely, the Picture window), * and those that regard the start of a new session as a meaningful event * (namely, the session counter and the cross-session memory counter). */ Preferences_read (MelderFile_readable (& prefs5File) ? & prefs5File : & prefs4File); if (! praatP.dontUsePictureWindow) praat_picture_prefsChanged (); praat_statistics_prefsChanged (); //Melder_error3 (L"batch name <<", theCurrentPraatApplication -> batchName.string, L">>"); //Melder_flushError (NULL); praatP.phase = praat_STARTING_UP; #if defined (UNIX) || defined (macintosh) structMelderDir usrLocal = { { 0 } }; Melder_pathToDir (L"/usr/local", & usrLocal); executeStartUpFile (& usrLocal, L"%ls-startUp"); #endif #if defined (UNIX) || defined (macintosh) executeStartUpFile (& homeDir, L".%ls-user-startUp"); // not on Windows (empty file name error) #endif #if defined (UNIX) || defined (macintosh) || defined (_WIN32) executeStartUpFile (& homeDir, L"%ls-user-startUp"); #endif /* * Plugins. * The Praat phase should remain praat_STARTING_UP, * because any added commands must not be included in the buttons file. */ structMelderFile searchPattern = { 0 }; MelderDir_getFile (& praatDir, L"plugin_*", & searchPattern); try { autoStrings directoryNames = Strings_createAsDirectoryList (Melder_fileToPath (& searchPattern)); if (directoryNames -> numberOfStrings > 0) { for (long i = 1; i <= directoryNames -> numberOfStrings; i ++) { structMelderDir pluginDir = { { 0 } }; structMelderFile plugin = { 0 }; MelderDir_getSubdir (& praatDir, directoryNames -> strings [i], & pluginDir); MelderDir_getFile (& pluginDir, L"setup.praat", & plugin); if (MelderFile_readable (& plugin)) { try { praat_executeScriptFromFile (& plugin, NULL); } catch (MelderError) { Melder_error_ (praatP.title, ": plugin ", & plugin, " contains an error."); Melder_flushError (NULL); } } } } } catch (MelderError) { Melder_clearError (); // in case Strings_createAsDirectoryList () threw an error } Melder_assert (wcsequ (Melder_double (1.5), L"1.5")); // check locale settings; because of the required file portability Praat cannot stand "1,5" { int dummy = 200; Melder_assert ((int) (signed char) dummy == -56); } // bingeti1 relies on this { int dummy = 200; Melder_assert ((int) (unsigned char) dummy == 200); } { uint16_t dummy = 40000; Melder_assert ((int) (int16_t) dummy == -25536); } // bingeti2 relies on this { uint16_t dummy = 40000; Melder_assert ((short) (int16_t) dummy == -25536); } // bingete2 relies on this if (Melder_batch) { if (thePraatStandAloneScriptText != NULL) { try { praat_executeScriptFromText (thePraatStandAloneScriptText); praat_exit (0); } catch (MelderError) { Melder_flushError ("%s: stand-alone script session interrupted.", praatP.title); praat_exit (-1); } } else if (doingCommandLineInterface) { try { praat_executeCommandFromStandardInput (praatP.title); praat_exit (0); } catch (MelderError) { Melder_flushError ("%s: command line session interrupted.", praatP.title); praat_exit (-1); } } else { try { praat_executeScriptFromFileNameWithArguments (theCurrentPraatApplication -> batchName.string); praat_exit (0); } catch (MelderError) { /* * Try to get the error message out; this is a bit complicated... */ structMelderFile batchFile = { 0 }; try { Melder_relativePathToFile (theCurrentPraatApplication -> batchName.string, & batchFile); } catch (MelderError) { praat_exit (-1); } #if defined (_WIN32) && ! defined (CONSOLE_APPLICATION) MelderGui_create (NULL); #endif Melder_error_ (praatP.title, ": command file ", & batchFile, " not completed."); Melder_flushError (NULL); praat_exit (-1); } } } else /* GUI */ { praatP.phase = praat_READING_BUTTONS; /* * Read the added script buttons. Each line separately: every error should be ignored. */ { // scope autostring buttons; try { buttons.reset (MelderFile_readText (& buttons5File)); } catch (MelderError) { try { buttons.reset (MelderFile_readText (& buttons4File)); } catch (MelderError) { Melder_clearError (); } } if (buttons.peek()) { wchar *line = buttons.peek(); for (;;) { wchar_t *newline = wcschr (line, '\n'); if (newline) *newline = '\0'; try { praat_executeCommand (NULL, line); } catch (MelderError) { Melder_clearError (); // ignore this line, but not necessarily the next } if (newline == NULL) break; line = newline + 1; } } } /* * Sort the commands. */ praat_sortMenuCommands (); praat_sortActions (); praatP.phase = praat_HANDLING_EVENTS; #if gtk //gtk_widget_add_events (G_OBJECT (theCurrentPraatApplication -> topShell), GDK_ALL_EVENTS_MASK); g_signal_connect (G_OBJECT (theCurrentPraatApplication -> topShell), "client-event", G_CALLBACK (cb_userMessage), NULL); gtk_key_snooper_install (theKeySnooper, 0); gtk_main (); #else #if defined (_WIN32) if (theCurrentPraatApplication -> batchName.string [0] != '\0') { wchar_t text [500]; /* * The user dropped a file on the Praat icon, while Praat was not running yet. * Windows may have enclosed the path between quotes; * this is especially likely to happen if the path contains spaces (which is usual). * And sometimes, Windows prepends a space before the quote. * Peel all that off. */ wchar_t *s = theCurrentPraatApplication -> batchName.string; swprintf (text, 500, L"Read from file... %ls", s [0] == ' ' && s [1] == '\"' ? s + 2 : s [0] == '\"' ? s + 1 : s); long l = wcslen (text); if (l > 0 && text [l - 1] == '\"') text [l - 1] = '\0'; //Melder_error3 (L"command <<", text, L">>"); //Melder_flushError (NULL); try { praat_executeScriptFromText (text); } catch (MelderError) { Melder_flushError (NULL); } } #endif for (;;) { XEvent event; GuiNextEvent (& event); XtDispatchEvent (& event); } #endif } } /* End of file praat.cpp */ sources_5316/sys/melder_audio.cpp0000644000176700017670000007521411753752264015723 0ustar paulpaul/* melder_audio.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2003/08/22 used getenv ("AUDIODEV") on Sun (thanks to Michel Scheffers) * pb 2003/10/22 fake mono for Linux drivers that do not support mono * pb 2003/12/06 use sys/soundcard.h instead of linux/soundcard.h for FreeBSD compatibility * pb 2004/05/07 removed motif_mac_setNullEventWaitingTime (we nowadays use 1 clock tick everywhere anyway) * pb 2004/08/10 fake mono for Linux drivers etc, also if not asynchronous * pb 2005/02/13 added O_NDELAY when opening /dev/dsp on Linux (suggestion by Rafael Laboissiere) * pb 2005/03/31 undid previous change (four complaints that sound stopped playing) * pb 2005/05/19 redid previous change (with fctrl fix suggested by Rafael Laboissiere) * pb 2005/10/13 edition for OpenBSD * pb 2006/10/28 erased MacOS 9 stuff * pb 2006/12/16 Macintosh uses CoreAudio (via PortAudio) * pb 2007/01/03 best sample rate can be over 64 kHz * pb 2007/05/13 null pointer test for deviceInfo (thanks to Stefan de Konink) * pb 2007/08/12 wchar_t * Stefan de Konink 2007/12/02 big-endian Linux * pb 2007/12/04 enums * pb 2008/06/01 removed SPEXLAB audio server * pb 2008/06/10 made PortAudio and foreground playing optional * pb 2008/07/03 DirectSound * pb 2010/05/09 GTK * pb 2011/02/11 better message * pb 2011/04/05 C++ */ #include "melder.h" #include "Gui.h" #include "Preferences.h" #include "NUM.h" #include #define my me -> #if defined (macintosh) #include #include #elif defined (_WIN32) #include #include #elif defined (linux) #include #include #include #include #include #include #include #if defined (__OpenBSD__) || defined (__NetBSD__) #include #else #include #endif #include #endif #include "../external/portaudio/portaudio.h" static struct { enum kMelder_asynchronicityLevel maximumAsynchronicity; bool useInternalSpeaker, inputUsesPortAudio, outputUsesPortAudio, outputUsesBlocking; double silenceBefore, silenceAfter; } preferences; void Melder_audio_prefs (void) { Preferences_addEnum (L"Audio.maximumAsynchronicity", & preferences. maximumAsynchronicity, kMelder_asynchronicityLevel, DEFAULT); Preferences_addBool (L"Audio.useInternalSpeaker", & preferences. useInternalSpeaker, true); Preferences_addBool (L"Audio.outputUsesPortAudio", & preferences. outputUsesPortAudio, kMelderAudio_outputUsesPortAudio_DEFAULT); Preferences_addBool (L"Audio.outputUsesBlocking", & preferences. outputUsesBlocking, false); Preferences_addDouble (L"Audio.silenceBefore", & preferences. silenceBefore, 0.0); Preferences_addDouble (L"Audio.silenceAfter", & preferences. silenceAfter, 0.5); Preferences_addBool (L"Audio.inputUsesPortAudio2", & preferences.inputUsesPortAudio, kMelderAudio_inputUsesPortAudio_DEFAULT); } void MelderAudio_setOutputMaximumAsynchronicity (enum kMelder_asynchronicityLevel maximumAsynchronicity) { MelderAudio_stopPlaying (MelderAudio_IMPLICIT); preferences. maximumAsynchronicity = maximumAsynchronicity; } enum kMelder_asynchronicityLevel MelderAudio_getOutputMaximumAsynchronicity (void) { return preferences. maximumAsynchronicity; } void MelderAudio_setInputUsesPortAudio (bool inputUsesPortAudio) { preferences. inputUsesPortAudio = inputUsesPortAudio; } bool MelderAudio_getInputUsesPortAudio (void) { return preferences. inputUsesPortAudio; } void MelderAudio_setOutputUsesPortAudio (bool outputUsesPortAudio) { MelderAudio_stopPlaying (MelderAudio_IMPLICIT); preferences. outputUsesPortAudio = outputUsesPortAudio; } bool MelderAudio_getOutputUsesPortAudio (void) { return preferences. outputUsesPortAudio; } void MelderAudio_setOutputUsesBlocking (bool outputUsesBlocking) { MelderAudio_stopPlaying (MelderAudio_IMPLICIT); preferences. outputUsesBlocking = outputUsesBlocking; } bool MelderAudio_getOutputUsesBlocking (void) { return preferences. outputUsesBlocking; } void MelderAudio_setUseInternalSpeaker (bool useInternalSpeaker) { MelderAudio_stopPlaying (MelderAudio_IMPLICIT); preferences. useInternalSpeaker = useInternalSpeaker; } bool MelderAudio_getUseInternalSpeaker (void) { return preferences. useInternalSpeaker; } void MelderAudio_setOutputSilenceBefore (double silenceBefore) { MelderAudio_stopPlaying (MelderAudio_IMPLICIT); preferences. silenceBefore = silenceBefore; } double MelderAudio_getOutputSilenceBefore (void) { return preferences. silenceBefore; } void MelderAudio_setOutputSilenceAfter (double silenceAfter) { MelderAudio_stopPlaying (MelderAudio_IMPLICIT); preferences. silenceAfter = silenceAfter; } double MelderAudio_getOutputSilenceAfter (void) { return preferences. silenceAfter; } long MelderAudio_getOutputBestSampleRate (long fsamp) { #if defined (macintosh) return fsamp; #elif defined (_WIN32) return fsamp == 8000 || fsamp == 11025 || fsamp == 16000 || fsamp == 22050 || fsamp == 32000 || fsamp == 44100 || fsamp == 48000 || fsamp == 96000 ? fsamp : 44100; #elif defined (linux) return fsamp == 44100 || fsamp == 48000 || fsamp == 96000 ? fsamp : 44100; #else return 44100; #endif } bool MelderAudio_isPlaying; static double theStartingTime = 0.0; static struct MelderPlay { const int16_t *buffer; long sampleRate, numberOfSamples, samplesLeft, samplesSent, samplesPlayed; unsigned int asynchronicity; int numberOfChannels; bool explicitStop, fakeMono; bool (*callback) (void *closure, long samplesPlayed); void *closure; #if motif XtWorkProcId workProcId_motif; #elif gtk gint workProcId_gtk; #endif bool usePortAudio, blocking, supports_paComplete; PaStream *stream; double paStartingTime; #if defined (macintosh) #elif defined (linux) int audio_fd, val, err; #elif defined (_WIN32) HWAVEOUT hWaveOut; WAVEHDR waveHeader; MMRESULT status; #endif } thePlay; long MelderAudio_getSamplesPlayed (void) { return thePlay. samplesPlayed; } bool MelderAudio_stopWasExplicit (void) { return thePlay. explicitStop; } /* * The flush () procedure will always have to be invoked after normal play, i.e. in the following cases: * 1. After synchronous play (asynchronicity = 0, 1, or 2). * 2. After interruption of asynchronicity 2 by the ESCAPE key. * 3. After asynchronous play, by the workProc. * 4. After interruption of asynchronicity 3 by MelderAudio_stopPlaying (). */ static bool flush (void) { struct MelderPlay *me = & thePlay; if (my usePortAudio) { if (my stream != NULL) Pa_CloseStream (my stream), my stream = NULL; } else { #if defined (macintosh) #elif defined (linux) /* * As on Sun. */ if (my audio_fd) { ioctl (my audio_fd, SNDCTL_DSP_RESET, (my val = 0, & my val)); close (my audio_fd), my audio_fd = 0; } #elif defined (_WIN32) /* * FIX: Do not reset the sound card if played to the end: * the last 20 milliseconds may be truncated! * This used to happen on Barbertje's Dell PC, not with SoundBlaster. */ if (my samplesPlayed != my numberOfSamples || Melder_debug == 2) waveOutReset (my hWaveOut); my status = waveOutUnprepareHeader (my hWaveOut, & my waveHeader, sizeof (WAVEHDR)); if (/* Melder_debug == 3 && */ my status == WAVERR_STILLPLAYING) { waveOutReset (my hWaveOut); waveOutUnprepareHeader (my hWaveOut, & my waveHeader, sizeof (WAVEHDR)); } waveOutClose (my hWaveOut), my hWaveOut = 0; #endif } if (my fakeMono) { NUMvector_free ((short *) my buffer, 0); my buffer = NULL; } MelderAudio_isPlaying = false; if (my samplesPlayed >= my numberOfSamples) my samplesPlayed = my numberOfSamples; if (my samplesPlayed <= 0) my samplesPlayed = 1; /* * Call the callback for the last time, which is recognizable by the value of MelderAudio_isPlaying. * In this way, the caller of Melder_play16 can be notified. * The caller can examine the actual number of samples played by testing MelderAudio_getSamplesPlayed (). */ if (my callback) my callback (my closure, my samplesPlayed); my callback = 0; my closure = 0; return true; /* Remove workProc if called from workProc. */ } bool MelderAudio_stopPlaying (bool explicitStop) { //Melder_casual ("stop playing!"); struct MelderPlay *me = & thePlay; my explicitStop = explicitStop; if (! MelderAudio_isPlaying || my asynchronicity < kMelder_asynchronicityLevel_ASYNCHRONOUS) return false; (void) flush (); #if motif XtRemoveWorkProc (thePlay. workProcId_motif); #elif gtk gtk_idle_remove (thePlay. workProcId_gtk); #endif return true; } static bool workProc (void *closure) { struct MelderPlay *me = & thePlay; //static long n = 0; //n ++; //Melder_casual("workProc %ld", n); if (my usePortAudio) { if (my blocking) { if (my samplesLeft > 0) { int dsamples = my samplesLeft > 2000 ? 2000 : my samplesLeft; Pa_WriteStream (my stream, (void *) & my buffer [my samplesSent * my numberOfChannels], dsamples); my samplesLeft -= dsamples; my samplesSent += dsamples; my samplesPlayed = (Melder_clock () - theStartingTime - Pa_GetStreamInfo (my stream) -> outputLatency) * my sampleRate; if (my callback && ! my callback (my closure, my samplesPlayed)) return flush (); } else /*if (my samplesPlayed >= my numberOfSamples)*/ { Pa_StopStream (my stream); my samplesPlayed = my numberOfSamples; return flush (); } } else { /* * Not all hostApis support paComplete or wait till all buffers have been played in Pa_StopStream. * Once pa_win_ds implements this, we can simply do: * if (Pa_IsStreamActive (my stream)) { * if (my callback && ! my callback (my closure, my samplesPlayed)) * return flush (); * } else { * my samplesPlayed = my numberOfSamples; * return flush (); * } * But then we also have to use paComplete in the stream callback. */ double timeElapsed = Melder_clock () - theStartingTime - Pa_GetStreamInfo (my stream) -> outputLatency; my samplesPlayed = timeElapsed * my sampleRate; if (my supports_paComplete && Pa_IsStreamActive (my stream)) { if (my callback && ! my callback (my closure, my samplesPlayed)) { Pa_AbortStream (my stream); return flush (); } } else if (my samplesPlayed < my numberOfSamples + my sampleRate / 20) { // allow the latency estimate to be 50 ms off. if (my callback && ! my callback (my closure, my samplesPlayed)) { Pa_AbortStream (my stream); return flush (); } } else { Pa_AbortStream (my stream); my samplesPlayed = my numberOfSamples; return flush (); } Pa_Sleep (10); } } else { #if defined (macintosh) #elif defined (linux) if (my samplesLeft > 0) { int dsamples = my samplesLeft > 500 ? 500 : my samplesLeft; write (my audio_fd, (char *) & my buffer [my samplesSent * my numberOfChannels], 2 * dsamples * my numberOfChannels); my samplesLeft -= dsamples; my samplesSent += dsamples; my samplesPlayed = (Melder_clock () - theStartingTime) * my sampleRate; if (my callback && ! my callback (my closure, my samplesPlayed)) return flush (); } else /*if (my samplesPlayed >= my numberOfSamples)*/ { close (my audio_fd), my audio_fd = 0; my samplesPlayed = my numberOfSamples; return flush (); /*} else { my samplesPlayed = (Melder_clock () - theStartingTime) * my sampleRate; if (my callback && ! my callback (my closure, my samplesPlayed)) return flush ();*/ } #elif defined (_WIN32) if (my waveHeader. dwFlags & WHDR_DONE) { my samplesPlayed = my numberOfSamples; return flush (); } else { static long previousTime = 0; unsigned long currentTime = clock (); if (Melder_debug == 1) { my samplesPlayed = (Melder_clock () - theStartingTime) * my sampleRate; } else { MMTIME mmtime; mmtime. wType = TIME_BYTES; waveOutGetPosition (my hWaveOut, & mmtime, sizeof (MMTIME)); my samplesPlayed = mmtime. u.cb / (2 * my numberOfChannels); } if (/* Melder_debug != 4 || */ currentTime - previousTime > CLOCKS_PER_SEC / 100) { previousTime = currentTime; if (my callback && ! my callback (my closure, my samplesPlayed)) return flush (); } Sleep (10); } #endif } (void) closure; return false; } #if motif static Boolean workProc_motif (XtPointer closure) { return workProc ((void *) closure); } #elif gtk static gint workProc_gtk (gpointer closure) { return ! workProc ((void *) closure); } #endif #if defined (macintosh) # define FloatToUnsigned(f) \ ((unsigned long)(((long)((f) - 2147483648.0)) + 2147483647L + 1)) static void double2real10 (double x, unsigned char *bytes) { int sign, exponent; double fMantissa, fsMantissa; unsigned long highMantissa, lowMantissa; if (x < 0.0) { sign = 0x8000; x *= -1; } else sign = 0; if (x == 0.0) { exponent = 0; highMantissa = 0; lowMantissa = 0; } else { fMantissa = frexp (x, & exponent); if ((exponent > 16384) || ! (fMantissa < 1)) /* Infinity or Not-a-Number. */ { exponent = sign | 0x7FFF; highMantissa = 0; lowMantissa = 0; } /* Infinity. */ else { /* Finite */ exponent += 16382; /* Add bias. */ if (exponent < 0) { /* Denormalized. */ fMantissa = ldexp (fMantissa, exponent); exponent = 0; } exponent |= sign; fMantissa = ldexp (fMantissa, 32); fsMantissa = floor (fMantissa); highMantissa = FloatToUnsigned (fsMantissa); fMantissa = ldexp (fMantissa - fsMantissa, 32); fsMantissa = floor (fMantissa); lowMantissa = FloatToUnsigned (fsMantissa); } } bytes [0] = exponent >> 8; bytes [1] = exponent; bytes [2] = highMantissa >> 24; bytes [3] = highMantissa >> 16; bytes [4] = highMantissa >> 8; bytes [5] = highMantissa; bytes [6] = lowMantissa >> 24; bytes [7] = lowMantissa >> 16; bytes [8] = lowMantissa >> 8; bytes [9] = lowMantissa; } #endif static int thePaStreamCallback (const void *input, void *output, unsigned long frameCount, const PaStreamCallbackTimeInfo* timeInfo, PaStreamCallbackFlags statusFlags, void *userData) { (void) input; (void) timeInfo; (void) userData; struct MelderPlay *me = & thePlay; if (statusFlags & paOutputUnderflow) { if (Melder_debug == 20) Melder_casual ("output underflow"); } if (statusFlags & paOutputOverflow) { if (Melder_debug == 20) Melder_casual ("output overflow"); } if (my samplesLeft > 0) { long dsamples = my samplesLeft > (long) frameCount ? (long) frameCount : my samplesLeft; if (Melder_debug == 20) Melder_casual ("play %ls %ls", Melder_integer (dsamples), Melder_double (Pa_GetStreamCpuLoad (my stream))); memset (output, '\0', 2 * frameCount * my numberOfChannels); memcpy (output, (char *) & my buffer [my samplesSent * my numberOfChannels], 2 * dsamples * my numberOfChannels); my samplesLeft -= dsamples; my samplesSent += dsamples; my samplesPlayed = my samplesSent; } else /*if (my samplesPlayed >= my numberOfSamples)*/ { memset (output, '\0', 2 * frameCount * my numberOfChannels); my samplesPlayed = my numberOfSamples; return my supports_paComplete ? paComplete : paContinue; } return paContinue; } void MelderAudio_play16 (const int16_t *buffer, long sampleRate, long numberOfSamples, int numberOfChannels, bool (*playCallback) (void *playClosure, long numberOfSamplesPlayed), void *playClosure) { struct MelderPlay *me = & thePlay; #ifdef _WIN32 bool wasPlaying = MelderAudio_isPlaying; #endif if (MelderAudio_isPlaying) MelderAudio_stopPlaying (MelderAudio_IMPLICIT); // otherwise, keep "explicitStop" tag my buffer = buffer; my sampleRate = sampleRate; my numberOfSamples = numberOfSamples; my numberOfChannels = numberOfChannels; my callback = playCallback; my closure = playClosure; my asynchronicity = Melder_batch ? kMelder_asynchronicityLevel_SYNCHRONOUS : Melder_backgrounding ? kMelder_asynchronicityLevel_INTERRUPTABLE : kMelder_asynchronicityLevel_ASYNCHRONOUS; if (my asynchronicity > preferences. maximumAsynchronicity) my asynchronicity = preferences. maximumAsynchronicity; my usePortAudio = preferences. outputUsesPortAudio; my blocking = preferences. outputUsesBlocking; my explicitStop = MelderAudio_IMPLICIT; my fakeMono = false; my samplesLeft = numberOfSamples; my samplesSent = 0; my samplesPlayed = 0; MelderAudio_isPlaying = true; if (my usePortAudio) { PaError err; static bool paInitialized = false; if (! paInitialized) { err = Pa_Initialize (); if (err) Melder_fatal ("PortAudio does not initialize: %s", Pa_GetErrorText (err)); paInitialized = true; } my supports_paComplete = Pa_GetHostApiInfo (Pa_GetDefaultHostApi ()) -> type != paDirectSound; PaStreamParameters outputParameters = { 0 }; outputParameters. device = Pa_GetDefaultOutputDevice (); const PaDeviceInfo *deviceInfo = Pa_GetDeviceInfo (outputParameters. device); outputParameters. channelCount = my numberOfChannels; outputParameters. sampleFormat = paInt16; if (deviceInfo != NULL) outputParameters. suggestedLatency = deviceInfo -> defaultLowOutputLatency; outputParameters. hostApiSpecificStreamInfo = NULL; err = Pa_OpenStream (& my stream, NULL, & outputParameters, my sampleRate, paFramesPerBufferUnspecified, paDitherOff, my blocking ? NULL : thePaStreamCallback, me); if (err) Melder_throw ("PortAudio cannot open sound output: ", Pa_GetErrorText (err), "."); theStartingTime = Melder_clock (); if (my blocking) { err = Pa_StartStream (my stream); if (err) Melder_throw ("PortAudio cannot start sound output: ", Pa_GetErrorText (err), "."); if (my asynchronicity == kMelder_asynchronicityLevel_SYNCHRONOUS) { Pa_WriteStream (my stream, buffer, numberOfSamples); Pa_StopStream (my stream); my samplesPlayed = my numberOfSamples; } else if (my asynchronicity <= kMelder_asynchronicityLevel_INTERRUPTABLE) { bool interrupted = false; while (my samplesLeft > 0 && ! interrupted) { long numberOfWriteSamplesAvailableWithoutBlocking = Pa_GetStreamWriteAvailable (my stream); if (Melder_debug == 20) Melder_casual ("Pa_GetStreamWriteAvailable: %ld", numberOfWriteSamplesAvailableWithoutBlocking); long maximumNumberOfSamplesToWrite = 1000; long dsamples = my samplesLeft > maximumNumberOfSamplesToWrite ? maximumNumberOfSamplesToWrite : my samplesLeft; Pa_WriteStream (my stream, (void *) & my buffer [my samplesSent * my numberOfChannels], dsamples); my samplesLeft -= dsamples; my samplesSent += dsamples; my samplesPlayed = (Melder_clock () - theStartingTime - Pa_GetStreamInfo (my stream) -> outputLatency) * my sampleRate; if (my callback && ! my callback (my closure, my samplesPlayed)) interrupted = true; if (my asynchronicity == kMelder_asynchronicityLevel_INTERRUPTABLE && ! interrupted) { #if defined (macintosh) #if useCarbon EventRecord event; if (EventAvail (keyDownMask, & event)) { /* * Remove the event, even if it was a different key. * Otherwise, the key will block the future availability of the Escape key. */ FlushEvents (keyDownMask, 0); /* * Catch Escape and Command-period. */ if ((event. message & charCodeMask) == 27 || ((event. modifiers & cmdKey) && (event. message & charCodeMask) == '.')) { my explicitStop = MelderAudio_EXPLICIT; interrupted = true; } } #else #endif #elif defined (_WIN32) MSG event; if (PeekMessage (& event, 0, 0, 0, PM_REMOVE) && event. message == WM_KEYDOWN) { if (LOWORD (event. wParam) == VK_ESCAPE) { my explicitStop = MelderAudio_EXPLICIT; interrupted = true; } } #endif } if (interrupted) { flush (); return; } } Pa_StopStream (my stream); } else { #if motif my workProcId_motif = GuiAddWorkProc (workProc_motif, NULL); #elif gtk my workProcId_gtk = gtk_idle_add (workProc_gtk, NULL); #endif return; } } else { err = Pa_StartStream (my stream); if (err) Melder_throw ("PortAudio cannot start sound output: ", Pa_GetErrorText (err), "."); my paStartingTime = Pa_GetStreamTime (my stream); if (my asynchronicity <= kMelder_asynchronicityLevel_INTERRUPTABLE) { for (;;) { double timeElapsed = Melder_clock () - theStartingTime - Pa_GetStreamInfo (my stream) -> outputLatency; my samplesPlayed = timeElapsed * my sampleRate; if (my samplesPlayed >= my numberOfSamples + my sampleRate / 20) { my samplesPlayed = my numberOfSamples; break; } bool interrupted = false; if (my asynchronicity != kMelder_asynchronicityLevel_SYNCHRONOUS && my callback && ! my callback (my closure, my samplesPlayed)) interrupted = true; /* * Safe operation: only listen to key-down events. * Do this on the lowest level that will work. */ if (my asynchronicity == kMelder_asynchronicityLevel_INTERRUPTABLE && ! interrupted) { #if defined (macintosh) #if useCarbon EventRecord event; if (EventAvail (keyDownMask, & event)) { /* * Remove the event, even if it was a different key. * Otherwise, the key will block the future availability of the Escape key. */ FlushEvents (keyDownMask, 0); /* * Catch Escape and Command-period. */ if ((event. message & charCodeMask) == 27 || ((event. modifiers & cmdKey) && (event. message & charCodeMask) == '.')) { my explicitStop = MelderAudio_EXPLICIT; interrupted = true; } } #else #endif #elif defined (_WIN32) MSG event; if (PeekMessage (& event, 0, 0, 0, PM_REMOVE) && event. message == WM_KEYDOWN) { if (LOWORD (event. wParam) == VK_ESCAPE) { my explicitStop = MelderAudio_EXPLICIT; interrupted = true; } } #endif } if (interrupted) { flush (); return; } Pa_Sleep (10); } if (my samplesPlayed != my numberOfSamples) { Melder_fatal ("Played %ld instead of %ld samples.", my samplesPlayed, my numberOfSamples); } Pa_AbortStream (my stream); } else /* my asynchronicity == kMelder_asynchronicityLevel_ASYNCHRONOUS */ { #if motif my workProcId_motif = GuiAddWorkProc (workProc_motif, NULL); #elif gtk my workProcId_gtk = gtk_idle_add (workProc_gtk, NULL); #endif return; } } flush (); return; } else { #if defined (macintosh) #elif defined (linux) try { /* Big-endian version added by Stefan de Konink, Nov 29, 2007 */ #if __BYTE_ORDER == __BIG_ENDIAN int fmt = AFMT_S16_BE; #else int fmt = AFMT_S16_LE; #endif /* O_NDELAY option added by Rafael Laboissiere, May 19, 2005 */ if ((my audio_fd = open ("/dev/dsp", O_WRONLY | (Melder_debug == 16 ? 0 : O_NDELAY))) == -1) { Melder_throw (errno == EBUSY ? "Audio device already in use." : "Cannot open audio device.\nPlease switch on PortAudio in Praat's Sound Playing Preferences."); } fcntl (my audio_fd, F_SETFL, 0); /* Added by Rafael Laboissiere, May 19, 2005 */ if (ioctl (my audio_fd, SNDCTL_DSP_SETFMT, /* Changed SND_DSP_SAMPLESIZE to SNDCTL_DSP_SETFMT; Stefan de Konink, Nov 29, 2007 */ (my val = fmt, & my val)) == -1 || /* Error? */ my val != fmt) /* Has sound card overridden our sample size? */ { Melder_throw ("Cannot set sample size to 16 bit."); } if (ioctl (my audio_fd, SNDCTL_DSP_CHANNELS, (my val = my numberOfChannels, & my val)) == -1 || /* Error? */ my val != my numberOfChannels) /* Has sound card overridden our number of channels? */ { /* * There is one specific case in which we can work around the current failure, * namely when we are trying to play in mono but the driver of the sound card supports stereo only * and notified us of this by overriding our number of channels. */ if (my numberOfChannels == 1 && my val == 2) { my fakeMono = true; int16_t *newBuffer = NUMvector (0, 2 * numberOfSamples - 1); for (long isamp = 0; isamp < numberOfSamples; isamp ++) { newBuffer [isamp + isamp] = newBuffer [isamp + isamp + 1] = buffer [isamp]; } my buffer = (const int16_t *) newBuffer; my numberOfChannels = 2; } else { Melder_throw ("Cannot set number of channels to .", my numberOfChannels, "."); } } if (ioctl (my audio_fd, SNDCTL_DSP_SPEED, (my val = my sampleRate, & my val)) == -1 || // error? my val != my sampleRate) /* Has sound card overridden our sampling frequency? */ { Melder_throw ("Cannot set sampling frequency to ", my sampleRate, " Hz."); } theStartingTime = Melder_clock (); if (my asynchronicity == kMelder_asynchronicityLevel_SYNCHRONOUS) { if (write (my audio_fd, & my buffer [0], 2 * numberOfChannels * numberOfSamples) == -1) Melder_throw ("Cannot write audio output."); close (my audio_fd), my audio_fd = 0; /* Drain. Set to zero in order to notify flush (). */ my samplesPlayed = my numberOfSamples; } else if (my asynchronicity <= kMelder_asynchronicityLevel_INTERRUPTABLE) { bool interrupted = false; while (my samplesLeft && ! interrupted) { int dsamples = my samplesLeft > 500 ? 500 : my samplesLeft; if (write (my audio_fd, (char *) & my buffer [my samplesSent * my numberOfChannels], 2 * dsamples * my numberOfChannels) == -1) Melder_throw ("Cannot write audio output."); my samplesLeft -= dsamples; my samplesSent += dsamples; my samplesPlayed = (Melder_clock () - theStartingTime) * my sampleRate; if (my callback && ! my callback (my closure, my samplesPlayed)) interrupted = true; } if (! interrupted) { /* * Wait for playing to end. */ close (my audio_fd), my audio_fd = 0; // BUG: should do a loop my samplesPlayed = my numberOfSamples; } } else /* my asynchronicity == kMelder_asynchronicityLevel_ASYNCHRONOUS */ { my workProcId_gtk = gtk_idle_add (workProc_gtk, NULL); return; } flush (); return; } catch (MelderError) { struct MelderPlay *me = & thePlay; if (my audio_fd) close (my audio_fd), my audio_fd = 0; MelderAudio_isPlaying = false; Melder_throw ("16-bit audio not played."); } #elif defined (_WIN32) try { WAVEFORMATEX waveFormat; MMRESULT err; waveFormat. wFormatTag = WAVE_FORMAT_PCM; waveFormat. nChannels = my numberOfChannels; waveFormat. nSamplesPerSec = my sampleRate; waveFormat. wBitsPerSample = 16; waveFormat. nBlockAlign = my numberOfChannels * waveFormat. wBitsPerSample / 8; waveFormat. nAvgBytesPerSec = waveFormat. nBlockAlign * waveFormat. nSamplesPerSec; waveFormat. cbSize = 0; err = waveOutOpen (& my hWaveOut, WAVE_MAPPER, & waveFormat, 0, 0, CALLBACK_NULL | WAVE_ALLOWSYNC); if (err != MMSYSERR_NOERROR) { MelderAudio_isPlaying = false; if (err == MMSYSERR_ALLOCATED) Melder_throw ("Previous sound is still playing? Should not occur!\n" "Report bug to the author: ", err, "; wasPlaying: ", wasPlaying, "."); if (err == MMSYSERR_BADDEVICEID) Melder_throw ("Cannot play a sound. Perhaps another program is playing a sound at the same time?"); if (err == MMSYSERR_NODRIVER) Melder_throw ("This computer probably has no sound card."); if (err == MMSYSERR_NOMEM) Melder_throw ("Not enough free memory to play any sound at all."); if (err == WAVERR_BADFORMAT) Melder_throw ("Bad sound format? Should not occur! Report bug to the author!"); Melder_throw ("Unknown error ", err, " while trying to play a sound? Report bug to the author!"); } my waveHeader. dwFlags = 0; my waveHeader. lpData = (char *) my buffer; my waveHeader. dwBufferLength = my numberOfSamples * 2 * my numberOfChannels; my waveHeader. dwLoops = 1; my waveHeader. lpNext = NULL; my waveHeader. reserved = 0; err = waveOutPrepareHeader (my hWaveOut, & my waveHeader, sizeof (WAVEHDR)); //waveOutReset (my hWaveOut); if (err != MMSYSERR_NOERROR) { waveOutClose (my hWaveOut), my hWaveOut = 0; MelderAudio_isPlaying = false; if (err == MMSYSERR_INVALHANDLE) Melder_throw ("No device? Should not occur!"); if (err == MMSYSERR_NODRIVER) Melder_throw ("No driver? Should not occur!"); if (err == MMSYSERR_NOMEM) Melder_throw ("Not enough free memory to play this sound.\n" "Remove some objects, play a shorter sound, or buy more memory."); Melder_throw ("Unknown error ", err, " while preparing header? Should not occur!"); } err = waveOutWrite (my hWaveOut, & my waveHeader, sizeof (WAVEHDR)); if (err != MMSYSERR_NOERROR) { waveOutReset (my hWaveOut); waveOutUnprepareHeader (my hWaveOut, & my waveHeader, sizeof (WAVEHDR)); waveOutClose (my hWaveOut), my hWaveOut = 0; MelderAudio_isPlaying = false; Melder_throw ("Error ", err, " while writing audio output."); // BUG: should flush } theStartingTime = Melder_clock (); if (my asynchronicity == kMelder_asynchronicityLevel_SYNCHRONOUS) { while (! (my waveHeader. dwFlags & WHDR_DONE)) { Sleep (10); } my samplesPlayed = my numberOfSamples; } else if (my asynchronicity <= kMelder_asynchronicityLevel_INTERRUPTABLE) { while (! (my waveHeader. dwFlags & WHDR_DONE)) { MSG event; Sleep (10); my samplesPlayed = (Melder_clock () - theStartingTime) * my sampleRate; if (my callback && ! my callback (my closure, my samplesPlayed)) break; if (my asynchronicity == kMelder_asynchronicityLevel_INTERRUPTABLE && PeekMessage (& event, 0, 0, 0, PM_REMOVE) && event. message == WM_KEYDOWN) { if (LOWORD (event. wParam) == VK_ESCAPE) { my explicitStop = MelderAudio_EXPLICIT; break; } } } } else { my workProcId_motif = GuiAddWorkProc (workProc_motif, NULL); return; } flush (); return; } catch (MelderError) { Melder_throw ("16-bit audio not played."); } #else Melder_throw ("Cannot play a sound on this computer.\n16-bit audio not played."); #endif } } /********** WAITING FOR SOUND INPUT **********/ void Melder_audioTrigger (void) { } /* End of file melder_audio.cpp */ sources_5316/sys/Graphics_colour.cpp0000644000176700017670000003502211747251342016400 0ustar paulpaul/* Graphics_colour.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/05/28 GPL * pb 2004/09/09 Xwin: highlight2 * sdk 2008/03/24 cairo * pb 2009/05/09 pink * pb 2009/07/09 RGB colours * pb 2009/12/10 colours identical on all platforms * pb 2009/12/14 Graphics_standardColourToRGBColour * pb 2009/12/20 gotten rid of numbered standard colours * fb 2010/03/01 fix cairo in highlight2 () * pb 2010/05/12 highlighting in GDK instead of Cairo because of the availability of a XOR mode * pb 2010/05/12 xorOn in GDK instead of Cairo because of the availability of a XOR mode * pb 2010/06/05 set my colour in setColour * pb 2011/01/15 Windows: inverted the colour in XOR mode * pb 2011/03/17 C++ */ #include "GraphicsP.h" #include Graphics_Colour Graphics_BLACK = { 0.0, 0.0, 0.0 }, Graphics_WHITE = { 1.0, 1.0, 1.0 }, Graphics_RED = { 0.865, 0.034, 0.026 }, Graphics_GREEN = { 0.000, 0.500, 0.069 }, Graphics_BLUE = { 0.000, 0.000, 0.828 }, Graphics_CYAN = { 0.009, 0.669, 0.918 }, Graphics_MAGENTA = { 0.949, 0.033, 0.519 }, Graphics_YELLOW = { 0.984, 0.951, 0.020 }, Graphics_MAROON = { 0.5, 0.0, 0.0 }, Graphics_LIME = { 0.0, 1.0, 0.0 }, Graphics_NAVY = { 0.0, 0.0, 0.5 }, Graphics_TEAL = { 0.0, 0.5, 0.5 }, Graphics_PURPLE = { 0.5, 0.0, 0.5 }, Graphics_OLIVE = { 0.5, 0.5, 0.0 }, Graphics_PINK = { 1.0, 0.75, 0.75 }, Graphics_SILVER = { 0.75, 0.75, 0.75 }, Graphics_GREY = { 0.5, 0.5, 0.5 }; const wchar_t * Graphics_Colour_name (Graphics_Colour colour) { return Graphics_Colour_equal (colour, Graphics_BLACK) ? L"black" : Graphics_Colour_equal (colour, Graphics_WHITE) ? L"white" : Graphics_Colour_equal (colour, Graphics_RED) ? L"red" : Graphics_Colour_equal (colour, Graphics_GREEN) ? L"green" : Graphics_Colour_equal (colour, Graphics_BLUE) ? L"blue" : Graphics_Colour_equal (colour, Graphics_CYAN) ? L"cyan" : Graphics_Colour_equal (colour, Graphics_MAGENTA) ? L"magenta" : Graphics_Colour_equal (colour, Graphics_YELLOW) ? L"yellow" : Graphics_Colour_equal (colour, Graphics_MAROON) ? L"maroon" : Graphics_Colour_equal (colour, Graphics_LIME) ? L"lime" : Graphics_Colour_equal (colour, Graphics_NAVY) ? L"navy" : Graphics_Colour_equal (colour, Graphics_TEAL) ? L"teal" : Graphics_Colour_equal (colour, Graphics_PURPLE) ? L"purple" : Graphics_Colour_equal (colour, Graphics_OLIVE) ? L"olive" : Graphics_Colour_equal (colour, Graphics_SILVER) ? L"silver" : Graphics_Colour_equal (colour, Graphics_GREY) ? L"grey" : colour. red == colour. green && colour. red == colour. blue ? Melder_fixed (colour. red, 6) : Melder_wcscat (L"{", Melder_fixed (colour. red, 6), L",", Melder_fixed (colour. green, 6), L",", Melder_fixed (colour. blue, 6), L"}"); } #if mac #include "macport_on.h" #include #endif #define wdx(x) ((x) * my scaleX + my deltaX) #define wdy(y) ((y) * my scaleY + my deltaY) void _Graphics_setColour (Graphics graphics, Graphics_Colour colour) { if (graphics -> screen) { GraphicsScreen me = static_cast (graphics); #if cairo if (my d_cairoGraphicsContext == NULL) return; cairo_set_source_rgb (my d_cairoGraphicsContext, colour. red, colour. green, colour. blue); #elif win my d_winForegroundColour = RGB (colour. red * 255, colour. green * 255, colour. blue * 255); SelectPen (my d_gdiGraphicsContext, GetStockPen (BLACK_PEN)); DeleteObject (my d_winPen); my d_winPen = CreatePen (PS_SOLID, 0, my d_winForegroundColour); SelectBrush (my d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); DeleteObject (my d_winBrush); my d_winBrush = CreateSolidBrush (my d_winForegroundColour); #elif mac my d_macColour. red = colour. red * 65535; my d_macColour. green = colour. green * 65535; my d_macColour. blue = colour. blue * 65535; // postpone till drawing #endif } else if (graphics -> postScript) { GraphicsPostscript me = static_cast (graphics); my d_printf (my d_file, "%.6g %.6g %.6g setrgbcolor\n", colour. red, colour. green, colour. blue); } } void Graphics_setColour (Graphics me, Graphics_Colour colour) { my colour = colour; _Graphics_setColour (me, colour); if (my recording) { op (SET_RGB_COLOUR, 3); put (colour. red); put (colour. green); put (colour. blue); } } void _Graphics_setGrey (Graphics graphics, double fgrey) { if (graphics -> screen) { GraphicsScreen me = static_cast (graphics); #if cairo if (my d_cairoGraphicsContext == NULL) return; if (fgrey < 0.0) fgrey = 0.0; else if (fgrey > 1.0) fgrey = 1.0; cairo_set_source_rgb (my d_cairoGraphicsContext, fgrey, fgrey, fgrey); #elif win int lightness = fgrey <= 0 ? 0 : fgrey >= 1.0 ? 255 : fgrey * 255; my d_winForegroundColour = RGB (lightness, lightness, lightness); SelectPen (my d_gdiGraphicsContext, GetStockPen (BLACK_PEN)); DeleteObject (my d_winPen); my d_winPen = CreatePen (PS_SOLID, 0, my d_winForegroundColour); SelectBrush (my d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); DeleteObject (my d_winBrush); my d_winBrush = CreateSolidBrush (my d_winForegroundColour); #elif mac if (fgrey < 0.0) fgrey = 0.0; else if (fgrey > 1.0) fgrey = 1.0; my d_macColour. red = my d_macColour. green = my d_macColour. blue = fgrey * 65535; #endif } else if (graphics -> postScript) { GraphicsPostscript me = static_cast (graphics); if (fgrey < 0.0) fgrey = 0.0; else if (fgrey > 1.0) fgrey = 1.0; my d_printf (my d_file, "%.6g setgray\n", fgrey); } } void Graphics_setGrey (Graphics me, double grey) { my colour. red = my colour. green = my colour. blue = grey; _Graphics_setGrey (me, grey); if (my recording) { op (SET_GREY, 1); put (grey); } } static void highlight (Graphics graphics, long x1DC, long x2DC, long y1DC, long y2DC) { if (graphics -> screen) { GraphicsScreen me = static_cast (graphics); #if cairo if (my d_cairoGraphicsContext == NULL) return; int width = x2DC - x1DC, height = y1DC - y2DC; if (width <= 0 || height <= 0) return; gdk_gc_set_function (my d_gdkGraphicsContext, GDK_XOR); GdkColor pinkXorWhite = { 0, 0x0000, 0x4000, 0x4000 }, black = { 0, 0x0000, 0x0000, 0x0000 }; gdk_gc_set_rgb_fg_color (my d_gdkGraphicsContext, & pinkXorWhite); gdk_draw_rectangle (my d_window, my d_gdkGraphicsContext, TRUE, x1DC, y2DC, width, height); gdk_gc_set_rgb_fg_color (my d_gdkGraphicsContext, & black); gdk_gc_set_function (my d_gdkGraphicsContext, GDK_COPY); gdk_flush (); //tryout 20110207 //cairo_set_source_rgba (my d_cairoGraphicsContext, 1.0, 0.8, 0.8, 0.5); //cairo_set_operator (my d_cairoGraphicsContext, CAIRO_OPERATOR_BITXOR); // this blend mode doesn't exist //cairo_rectangle (my d_cairoGraphicsContext, x1DC, y2DC, width, height); //cairo_fill (my d_cairoGraphicsContext); //cairo_set_source_rgb (my d_cairoGraphicsContext, 0.0, 0.0, 0.0); //cairo_set_operator (my d_cairoGraphicsContext, CAIRO_OPERATOR_OVER); #elif win static HBRUSH highlightBrush; RECT rect; rect. left = x1DC, rect. right = x2DC, rect. top = y2DC, rect. bottom = y1DC; if (! highlightBrush) highlightBrush = CreateSolidBrush (RGB (255, 210, 210)); SelectPen (my d_gdiGraphicsContext, GetStockPen (NULL_PEN)); SelectBrush (my d_gdiGraphicsContext, highlightBrush); SetROP2 (my d_gdiGraphicsContext, R2_NOTXORPEN); Rectangle (my d_gdiGraphicsContext, x1DC, y2DC, x2DC + 1, y1DC + 1); SetROP2 (my d_gdiGraphicsContext, R2_COPYPEN); SelectPen (my d_gdiGraphicsContext, GetStockPen (BLACK_PEN)); SelectBrush (my d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); /* Superfluous? */ #elif mac Rect rect; if (my d_drawingArea) GuiMac_clipOn (my d_drawingArea); SetRect (& rect, x1DC, y2DC, x2DC, y1DC); SetPort (my d_macPort); LMSetHiliteMode (LMGetHiliteMode () & ~ 128L); /* see IM V-61 */ InvertRect (& rect); if (my d_drawingArea) GuiMac_clipOff (); #endif } } void Graphics_highlight (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC) { highlight (me, wdx (x1WC), wdx (x2WC), wdy (y1WC), wdy (y2WC)); if (my recording) { op (HIGHLIGHT, 4); put (x1WC); put (x2WC); put (y1WC); put (y2WC); } } void Graphics_unhighlight (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC) { highlight (me, wdx (x1WC), wdx (x2WC), wdy (y1WC), wdy (y2WC)); if (my recording) { op (UNHIGHLIGHT, 4); put (x1WC); put (x2WC); put (y1WC); put (y2WC); } } static void highlight2 (Graphics graphics, long x1DC, long x2DC, long y1DC, long y2DC, long x1DC_inner, long x2DC_inner, long y1DC_inner, long y2DC_inner) { if (graphics -> screen) { GraphicsScreen me = static_cast (graphics); #if cairo if (my d_cairoGraphicsContext == NULL) return; cairo_save (my d_cairoGraphicsContext); cairo_set_source_rgba (my d_cairoGraphicsContext, 1.0, 0.8, 0.8, 0.5); //cairo_set_operator (my d_cairoGraphicsContext, CAIRO_OPERATOR_XOR); cairo_rectangle (my d_cairoGraphicsContext, x1DC, y2DC, x2DC - x1DC, y2DC_inner - y2DC); // upper cairo_rectangle (my d_cairoGraphicsContext, x1DC, y2DC_inner, x1DC_inner - x1DC, y1DC_inner - y2DC_inner); // left part cairo_rectangle (my d_cairoGraphicsContext, x2DC_inner, y2DC_inner, x2DC - x2DC_inner, y1DC_inner - y2DC_inner); // right part cairo_rectangle (my d_cairoGraphicsContext, x1DC, y1DC_inner, x2DC - x1DC, y1DC - y1DC_inner); // lower cairo_fill (my d_cairoGraphicsContext); cairo_restore (my d_cairoGraphicsContext); #elif win static HBRUSH highlightBrush; if (! highlightBrush) highlightBrush = CreateSolidBrush (RGB (255, 210, 210)); SelectPen (my d_gdiGraphicsContext, GetStockPen (NULL_PEN)); SelectBrush (my d_gdiGraphicsContext, highlightBrush); SetROP2 (my d_gdiGraphicsContext, R2_NOTXORPEN); Rectangle (my d_gdiGraphicsContext, x1DC, y2DC, x2DC + 1, y2DC_inner + 1); Rectangle (my d_gdiGraphicsContext, x1DC, y2DC_inner, x1DC_inner + 1, y1DC_inner + 1); Rectangle (my d_gdiGraphicsContext, x2DC_inner, y2DC_inner, x2DC + 1, y1DC_inner + 1); Rectangle (my d_gdiGraphicsContext, x1DC, y1DC_inner, x2DC + 1, y1DC + 1); SetROP2 (my d_gdiGraphicsContext, R2_COPYPEN); SelectPen (my d_gdiGraphicsContext, GetStockPen (BLACK_PEN)); SelectBrush (my d_gdiGraphicsContext, GetStockBrush (NULL_BRUSH)); /* Superfluous? */ #elif mac Rect rect; if (my d_drawingArea) GuiMac_clipOn (my d_drawingArea); SetPort (my d_macPort); LMSetHiliteMode (LMGetHiliteMode () & ~ 128L); SetRect (& rect, x1DC, y2DC, x2DC, y2DC_inner); InvertRect (& rect); LMSetHiliteMode (LMGetHiliteMode () & ~ 128L); SetRect (& rect, x1DC, y2DC_inner, x1DC_inner, y1DC_inner); InvertRect (& rect); LMSetHiliteMode (LMGetHiliteMode () & ~ 128L); SetRect (& rect, x2DC_inner, y2DC_inner, x2DC, y1DC_inner); InvertRect (& rect); LMSetHiliteMode (LMGetHiliteMode () & ~ 128L); SetRect (& rect, x1DC, y1DC_inner, x2DC, y1DC); InvertRect (& rect); if (my d_drawingArea) GuiMac_clipOff (); #endif } } void Graphics_highlight2 (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC, double x1WC_inner, double x2WC_inner, double y1WC_inner, double y2WC_inner) { highlight2 (me, wdx (x1WC), wdx (x2WC), wdy (y1WC), wdy (y2WC), wdx (x1WC_inner), wdx (x2WC_inner), wdy (y1WC_inner), wdy (y2WC_inner)); if (my recording) { op (HIGHLIGHT2, 8); put (x1WC); put (x2WC); put (y1WC); put (y2WC); put (x1WC_inner); put (x2WC_inner); put (y1WC_inner); put (y2WC_inner); } } void Graphics_unhighlight2 (Graphics me, double x1WC, double x2WC, double y1WC, double y2WC, double x1WC_inner, double x2WC_inner, double y1WC_inner, double y2WC_inner) { #if ! cairo highlight2 (me, wdx (x1WC), wdx (x2WC), wdy (y1WC), wdy (y2WC), wdx (x1WC_inner), wdx (x2WC_inner), wdy (y1WC_inner), wdy (y2WC_inner)); #endif if (my recording) { op (UNHIGHLIGHT2, 8); put (x1WC); put (x2WC); put (y1WC); put (y2WC); put (x1WC_inner); put (x2WC_inner); put (y1WC_inner); put (y2WC_inner); } } void Graphics_xorOn (Graphics graphics, Graphics_Colour colour) { if (graphics -> screen) { GraphicsScreen me = static_cast (graphics); #if cairo GdkColor colourXorWhite = { 0, (uint16_t) (colour. red * 65535.0) ^ 0xFFFF, (uint16_t) (colour. green * 65535.0) ^ 0xFFFF, (uint16_t) (colour. blue * 65535.0) ^ 0xFFFF }; gdk_gc_set_rgb_fg_color (my d_gdkGraphicsContext, & colourXorWhite); gdk_gc_set_function (my d_gdkGraphicsContext, GDK_XOR); //cairo_set_source_rgba (my d_cairoGraphicsContext, 1.0, 0.8, 0.8, 0.5); //cairo_set_operator (my d_cairoGraphicsContext, CAIRO_OPERATOR_XOR); gdk_flush (); #elif win SetROP2 (my d_gdiGraphicsContext, R2_XORPEN); colour. red = ((uint16_t) (colour. red * 65535.0) ^ 0xFFFF) / 65535.0; colour. green = ((uint16_t) (colour. green * 65535.0) ^ 0xFFFF) / 65535.0; colour. blue = ((uint16_t) (colour. blue * 65535.0) ^ 0xFFFF) / 65535.0; _Graphics_setColour (me, colour); #elif mac //CGContextSetBlendMode (my macGraphicsContext, kCGBlendModeDifference); #endif my duringXor = true; if (graphics -> recording) { op (XOR_ON, 3); put (colour. red); put (colour. green); put (colour. blue); } } } void Graphics_xorOff (Graphics graphics) { if (graphics -> screen) { GraphicsScreen me = static_cast (graphics); #if cairo GdkColor black = { 0, 0x0000, 0x0000, 0x0000 }; gdk_gc_set_rgb_fg_color (my d_gdkGraphicsContext, & black); gdk_gc_set_function (my d_gdkGraphicsContext, GDK_COPY); //cairo_set_source_rgba (my d_cairoGraphicsContext, 0.0, 0.0, 0.0, 1.0); //cairo_set_operator (my d_cairoGraphicsContext, CAIRO_OPERATOR_OVER); gdk_flush (); #elif win SetROP2 (my d_gdiGraphicsContext, R2_COPYPEN); _Graphics_setColour (me, my colour); #elif mac //CGContextSetBlendMode (my macGraphicsContext, kCGBlendModeNormal); #endif my duringXor = false; if (graphics -> recording) { op (XOR_OFF, 0); } } } Graphics_Colour Graphics_inqColour (Graphics me) { return my colour; } /* End of file Graphics_colour.cpp */ sources_5316/sys/Gui.h0000644000176700017670000005346411753737113013462 0ustar paulpaul#ifndef _Gui_h_ #define _Gui_h_ /* Gui.h * * Copyright (C) 1993-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #if defined (UNIX) #define gtk 1 #define motif 0 #elif defined (_WIN32) #define gtk 0 #define motif 1 #elif defined (macintosh) #if useCarbon #define gtk 0 #define motif 1 #else #define gtk 0 #define motif 0 #endif #endif #include "Collection.h" #if gtk #include #include #include #elif defined (macintosh) #include "macport_on.h" #include #include #include "macport_off.h" #elif defined (_WIN32) #include "winport_on.h" #include #include #include "winport_off.h" #endif #define GUI_ARGS GuiObject w, XtPointer void_me, XtPointer call #define GUI_IAM(klas) (void) w; (void) void_me; (void) call; iam (klas); #define Gui_LEFT_DIALOG_SPACING 20 #define Gui_RIGHT_DIALOG_SPACING 20 #define Gui_TOP_DIALOG_SPACING 14 #define Gui_BOTTOM_DIALOG_SPACING 20 #define Gui_HORIZONTAL_DIALOG_SPACING 12 #define Gui_VERTICAL_DIALOG_SPACING_SAME 12 #define Gui_VERTICAL_DIALOG_SPACING_DIFFERENT 20 #define Gui_TEXTFIELD_HEIGHT Machine_getTextHeight () #define Gui_LABEL_HEIGHT 16 #define Gui_RADIOBUTTON_HEIGHT 18 #define Gui_RADIOBUTTON_SPACING 8 #define Gui_CHECKBUTTON_HEIGHT 20 #define Gui_LABEL_SPACING 8 #define Gui_OPTIONMENU_HEIGHT 20 #define Gui_PUSHBUTTON_HEIGHT 20 #define Gui_OK_BUTTON_WIDTH 69 #define Gui_CANCEL_BUTTON_WIDTH 69 #define Gui_APPLY_BUTTON_WIDTH 69 #define Gui_AUTOMATIC -32768 #define Gui_HOMOGENEOUS 1 #if gtk typedef GMainContext *AppContext; typedef void *XtPointer; typedef gint Dimension; typedef gboolean Boolean; #define True 1 #define False 0 typedef void *GuiObject; #elif motif typedef class structGuiObject *GuiObject; // Opaque /* * Definitions of X11 types. */ #if defined (macintosh) typedef struct EventRecord XEvent; #else typedef MSG XEvent; #endif typedef unsigned char Boolean; typedef long Cardinal; typedef unsigned int Dimension; typedef int Position; typedef void *Window; typedef char *String; typedef struct Display Display; /*typedef long Time;*/ typedef long Atom; typedef struct { int /* elsewhere: char* */ name; long value; } Arg, *ArgList; /* * Declarations of X11 functions. */ void XMapRaised (int displayDummy, Window window); #define DefaultScreenOfDisplay(d) 0 int WidthOfScreen (int screen); int HeightOfScreen (int screen); /* * Definitions of Xt types. */ typedef void *XtPointer; typedef GuiObject *GuiObjectList; typedef long XtWorkProcId, XtIntervalId; typedef void (*XtCallbackProc) (GuiObject w, XtPointer client_data, XtPointer call_data); typedef Boolean (*XtWorkProc) (XtPointer client_data); typedef void (*XtTimerCallbackProc) (XtPointer, XtIntervalId *); typedef unsigned long WidgetClass; #define False 0 #define True 1 /* * Declarations of Xt functions. */ void XtAddCallback (GuiObject w, int kind, XtCallbackProc proc, XtPointer closure); XtIntervalId GuiAddTimeOut (unsigned long interval, XtTimerCallbackProc timerProc, XtPointer closure); XtWorkProcId GuiAddWorkProc (XtWorkProc workProc, XtPointer closure); void GuiMainLoop (); void GuiNextEvent (XEvent *event); #define XtCalloc Melder_calloc #define XtClass(w) (w) -> widgetClass void XtDestroyWidget (GuiObject w); void XtDispatchEvent (XEvent *event); #define XtDisplay(w) 0 GuiObject GuiInitialize (const char *name, unsigned int *argc, char **argv); Boolean XtIsManaged (GuiObject w); Boolean XtIsShell (GuiObject w); void XtManageChild (GuiObject w); void XtManageChildren (GuiObjectList children, Cardinal num_children); void XtMapWidget (GuiObject w); void XtNextEvent (XEvent *event); void XtRemoveTimeOut (XtIntervalId id); void XtRemoveWorkProc (XtWorkProcId id); void XtSetKeyboardFocus (GuiObject tree, GuiObject descendant); void XtSetSensitive (GuiObject w, Boolean value); void XtUnmanageChild (GuiObject self); void XtUnmanageChildren (GuiObjectList children, Cardinal num_children); GuiObject GuiAppInitialize (const char *name, void *dum1, int dum2, unsigned int *argc, char **argv, void *dum3, void *dum4); GuiObject XtVaCreateWidget (const char *name, int widgetClass, GuiObject parent, ...); GuiObject XtVaCreateManagedWidget (const char *name, int widgetClass, GuiObject parent, ...); void XtVaGetValues (GuiObject w, ...); void XtVaSetValues (GuiObject w, ...); Window XtWindow (GuiObject w); long Gui_getNumberOfMotifWidgets (void); /* * Xm widget classes. */ #define xmBulletinBoardWidgetClass 0x00000001 #define xmDrawingAreaWidgetClass 0x00000002 #define xmFormWidgetClass 0x00000004 #define xmFrameWidgetClass 0x00000008 #define xmLabelWidgetClass 0x00000010 #define xmListWidgetClass 0x00000020 #define xmMenuBarWidgetClass 0x00000040 #define xmPulldownMenuWidgetClass 0x00000100 #define xmPushButtonWidgetClass 0x00000200 #define xmRowColumnWidgetClass 0x00000400 #define xmScaleWidgetClass 0x00000800 #define xmScrollBarWidgetClass 0x00001000 #define xmScrolledWindowWidgetClass 0x00002000 #define xmSeparatorWidgetClass 0x00004000 #define xmShellWidgetClass 0x00008000 #define xmTextWidgetClass 0x00010000 #define xmToggleButtonWidgetClass 0x00020000 #define xmCascadeButtonWidgetClass 0x00040000 #define topLevelShellWidgetClass xmShellWidgetClass #define xmPushButtonGadgetClass xmPushButtonWidgetClass #define xmCascadeButtonGadgetClass xmCascadeButtonWidgetClass #define xmSeparatorGadgetClass xmSeparatorWidgetClass #define xmToggleButtonGadgetClass xmToggleButtonWidgetClass /* * Xm resource names. */ enum { XmNnull, #define motif_RESOURCE(xxx) xxx, #include "motifEmulator_resources.h" #undef motif_RESOURCE XmNend }; /* * Xm enumerated types. * All start at 1, because we have to reserve zero for the dynamic default value. * This is important for the resources set during creation. */ enum /* dialog styles */ { XmDIALOG_MODELESS = 1, XmDIALOG_FULL_APPLICATION_MODAL }; enum /* orientation */ { XmVERTICAL = 1, XmHORIZONTAL }; enum /* attachment */ { XmATTACH_NONE = 1, XmATTACH_FORM, XmATTACH_POSITION }; enum /* rowColumn types */ { XmWORK_AREA = 1, XmMENU_BAR }; enum /* delete responses */ { XmDESTROY = 1, XmUNMAP, XmDO_NOTHING }; enum /* indicator types */ { XmONE_OF_MANY = 1, XmN_OF_MANY }; /* * Declarations of Xm functions. */ void XmAddWMProtocolCallback (GuiObject shell, Atom protocol, XtCallbackProc callback, char *closure); GuiObject XmCreateBulletinBoard (GuiObject, const char *, ArgList, int); GuiObject XmCreateBulletinBoardDialog (GuiObject, const char *, ArgList, int); GuiObject XmCreateCascadeButton (GuiObject, const char *, ArgList, int); GuiObject XmCreateCascadeButtonGadget (GuiObject, const char *, ArgList, int); GuiObject XmCreateDialogShell (GuiObject, const char *, ArgList, int); GuiObject XmCreateForm (GuiObject, const char *, ArgList, int); GuiObject XmCreateFormDialog (GuiObject, const char *, ArgList, int); GuiObject XmCreateMenuBar (GuiObject, const char *, ArgList, int); GuiObject XmCreatePulldownMenu (GuiObject, const char *, ArgList, int); GuiObject XmCreateRadioBox (GuiObject, const char *, ArgList, int); GuiObject XmCreateRowColumn (GuiObject, const char *, ArgList, int); GuiObject XmCreateScale (GuiObject, const char *, ArgList, int); GuiObject XmCreateScrolledWindow (GuiObject, const char *, ArgList, int); GuiObject XmCreateScrollBar (GuiObject, const char *, ArgList, int); GuiObject XmCreateSeparator (GuiObject, const char *, ArgList, int); GuiObject XmCreateSeparatorGadget (GuiObject, const char *, ArgList, int); GuiObject XmCreateShell (GuiObject, const char *, ArgList, int); GuiObject XmCreateToggleButton (GuiObject, const char *, ArgList, int); GuiObject XmCreateToggleButtonGadget (GuiObject, const char *, ArgList, int); void XmScaleGetValue (GuiObject widget, int *value_return); void XmScaleSetValue (GuiObject widget, int value); void XmScrollBarGetValues (GuiObject me, int *value, int *sliderSize, int *increment, int *pageIncrement); void XmScrollBarSetValues (GuiObject me, int value, int sliderSize, int increment, int pageIncrement, Boolean notify); Boolean XmToggleButtonGadgetGetState (GuiObject widget); #define XmToggleButtonGetState XmToggleButtonGadgetGetState void XmToggleButtonGadgetSetState (GuiObject widget, Boolean value, Boolean notify); #define XmToggleButtonSetState XmToggleButtonGadgetSetState void XmUpdateDisplay (GuiObject dummy); #if defined (macintosh) void motif_mac_defaultFont (void); void GuiMac_clipOn (GuiObject widget); /* Clip to the inner area of a drawingArea (for drawing); used by graphics drivers for Macintosh (clipping is automatic for Xwindows). */ int GuiMac_clipOn_graphicsContext (GuiObject me, void *graphicsContext); void GuiMac_clipOff (void); void motif_mac_setUserMessageCallbackA (int (*userMessageCallback) (char *message)); void motif_mac_setUserMessageCallbackW (int (*userMessageCallback) (wchar_t *message)); #elif defined (_WIN32) int motif_win_mouseStillDown (void); void motif_win_setUserMessageCallback (int (*userMessageCallback) (void)); #endif #else typedef void *GuiObject; typedef void *XtPointer; typedef unsigned char Boolean; #define True 1 #define False 0 typedef unsigned int Dimension; #endif /* Button layout and state: */ #define GuiMenu_INSENSITIVE (1 << 8) #define GuiMenu_CHECKBUTTON (1 << 9) #define GuiMenu_TOGGLE_ON (1 << 10) #define GuiMenu_ATTRACTIVE (1 << 11) #define GuiMenu_RADIO_FIRST (1 << 12) #define GuiMenu_RADIO_NEXT (1 << 13) #define GuiMenu_BUTTON_STATE_MASK (GuiMenu_INSENSITIVE|GuiMenu_CHECKBUTTON|GuiMenu_TOGGLE_ON|GuiMenu_ATTRACTIVE|GuiMenu_RADIO_FIRST|GuiMenu_RADIO_NEXT) /* Accelerators: */ #define GuiMenu_OPTION (1 << 21) #define GuiMenu_SHIFT (1 << 22) #define GuiMenu_COMMAND (1 << 23) #define GuiMenu_LEFT_ARROW 1 #define GuiMenu_RIGHT_ARROW 2 #define GuiMenu_UP_ARROW 3 #define GuiMenu_DOWN_ARROW 4 #define GuiMenu_PAUSE 5 #define GuiMenu_DELETE 6 #define GuiMenu_INSERT 7 #define GuiMenu_BACKSPACE 8 #define GuiMenu_TAB 9 #define GuiMenu_LINEFEED 10 #define GuiMenu_HOME 11 #define GuiMenu_END 12 #define GuiMenu_ENTER 13 #define GuiMenu_PAGE_UP 14 #define GuiMenu_PAGE_DOWN 15 #define GuiMenu_ESCAPE 16 #define GuiMenu_F1 17 #define GuiMenu_F2 18 #define GuiMenu_F3 19 #define GuiMenu_F4 20 #define GuiMenu_F5 21 #define GuiMenu_F6 22 #define GuiMenu_F7 23 #define GuiMenu_F8 24 #define GuiMenu_F9 25 #define GuiMenu_F10 26 #define GuiMenu_F11 27 #define GuiMenu_F12 28 GuiObject Gui_addMenuBar (GuiObject form); int Gui_getResolution (GuiObject widget); void Gui_getWindowPositioningBounds (double *x, double *y, double *width, double *height); /* GuiButton creation flags: */ #define GuiButton_DEFAULT 1 #define GuiButton_CANCEL 2 #define GuiButton_INSENSITIVE 4 #define GuiButton_ATTRACTIVE 8 typedef struct structGuiButtonEvent { GuiObject button; bool shiftKeyPressed, commandKeyPressed, optionKeyPressed, extraControlKeyPressed; } *GuiButtonEvent; GuiObject GuiButton_create (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*clickedCallback) (void *boss, GuiButtonEvent event), void *boss, unsigned long flags); GuiObject GuiButton_createShown (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*clickedCallback) (void *boss, GuiButtonEvent event), void *boss, unsigned long flags); void GuiButton_setString (GuiObject widget, const wchar_t *text); // rarely used /* GuiCheckButton creation flags: */ #define GuiCheckButton_SET 1 #define GuiCheckButton_INSENSITIVE 2 typedef struct structGuiCheckButtonEvent { GuiObject toggle; } *GuiCheckButtonEvent; GuiObject GuiCheckButton_create (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*valueChangedCallback) (void *boss, GuiCheckButtonEvent event), void *valueChangedBoss, unsigned long flags); GuiObject GuiCheckButton_createShown (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*valueChangedCallback) (void *boss, GuiCheckButtonEvent event), void *valueChangedBoss, unsigned long flags); bool GuiCheckButton_getValue (GuiObject widget); void GuiCheckButton_setValue (GuiObject widget, bool value); GuiObject GuiColumn_createShown (GuiObject parent, unsigned long flags); GuiObject GuiRow_createShown (GuiObject parent, unsigned long flags); /* GuiDialog creation flags: */ #define GuiDialog_MODAL 1 GuiObject GuiDialog_create (GuiObject parent, int x, int y, int width, int height, const wchar_t *title, void (*goAwayCallback) (void *goAwayBoss), void *goAwayBoss, unsigned long flags); GuiObject GuiDialog_getButtonArea (GuiObject widget); SortedSetOfString GuiFileSelect_getInfileNames (GuiObject parent, const wchar_t *title, bool allowMultipleFiles); wchar_t * GuiFileSelect_getOutfileName (GuiObject parent, const wchar_t *title, const wchar_t *defaultName); wchar_t * GuiFileSelect_getDirectoryName (GuiObject parent, const wchar_t *title); /* GuiDrawingArea creation flags: */ #define GuiDrawingArea_BORDER 1 enum mouse_events { MOTION_NOTIFY = 1, BUTTON_PRESS, BUTTON_RELEASE }; typedef struct structGuiDrawingAreaExposeEvent { GuiObject widget; int x, y, width, height; } *GuiDrawingAreaExposeEvent; typedef struct structGuiDrawingAreaClickEvent { GuiObject widget; int x, y; bool shiftKeyPressed, commandKeyPressed, optionKeyPressed, extraControlKeyPressed; int button; enum mouse_events type; } *GuiDrawingAreaClickEvent; typedef struct structGuiDrawingAreaKeyEvent { GuiObject widget; wchar_t key; bool shiftKeyPressed, commandKeyPressed, optionKeyPressed, extraControlKeyPressed; } *GuiDrawingAreaKeyEvent; typedef struct structGuiDrawingAreaResizeEvent { GuiObject widget; int width, height; } *GuiDrawingAreaResizeEvent; GuiObject GuiDrawingArea_create (GuiObject parent, int left, int right, int top, int bottom, void (*exposeCallback) (void *boss, GuiDrawingAreaExposeEvent event), void (*clickCallback) (void *boss, GuiDrawingAreaClickEvent event), void (*keyCallback) (void *boss, GuiDrawingAreaKeyEvent event), void (*resizeCallback) (void *boss, GuiDrawingAreaResizeEvent event), void *boss, unsigned long flags); GuiObject GuiDrawingArea_createShown (GuiObject parent, int left, int right, int top, int bottom, void (*exposeCallback) (void *boss, GuiDrawingAreaExposeEvent event), void (*clickCallback) (void *boss, GuiDrawingAreaClickEvent event), void (*keyCallback) (void *boss, GuiDrawingAreaKeyEvent event), void (*resizeCallback) (void *boss, GuiDrawingAreaResizeEvent event), void *boss, unsigned long flags); void GuiDrawingArea_setExposeCallback (GuiObject widget, void (*callback) (void *boss, GuiDrawingAreaExposeEvent event), void *boss); void GuiDrawingArea_setClickCallback (GuiObject widget, void (*callback) (void *boss, GuiDrawingAreaClickEvent event), void *boss); /* GuiLabel creation flags: */ #define GuiLabel_CENTRE 1 #define GuiLabel_RIGHT 2 GuiObject GuiLabel_create (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *labelText, unsigned long flags); GuiObject GuiLabel_createShown (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *labelText, unsigned long flags); void GuiLabel_setString (GuiObject widget, const wchar_t *text); typedef struct structGuiListEvent { GuiObject list; } *GuiListEvent; GuiObject GuiList_create (GuiObject parent, int left, int right, int top, int bottom, bool allowMultipleSelection, const wchar_t *header); GuiObject GuiList_createShown (GuiObject parent, int left, int right, int top, int bottom, bool allowMultipleSelection, const wchar_t *header); void GuiList_deleteAllItems (GuiObject me); void GuiList_deleteItem (GuiObject me, long position); void GuiList_deselectAllItems (GuiObject me); void GuiList_deselectItem (GuiObject me, long position); long GuiList_getBottomPosition (GuiObject me); long GuiList_getNumberOfItems (GuiObject me); long * GuiList_getSelectedPositions (GuiObject me, long *numberOfSelected); long GuiList_getTopPosition (GuiObject me); void GuiList_insertItem (GuiObject me, const wchar_t *itemText, long position); void GuiList_replaceItem (GuiObject me, const wchar_t *itemText, long position); void GuiList_setTopPosition (GuiObject me, long topPosition); void GuiList_selectItem (GuiObject me, long position); void GuiList_setSelectionChangedCallback (GuiObject me, void (*callback) (void *boss, GuiListEvent event), void *boss); void GuiList_setDoubleClickCallback (GuiObject me, void (*callback) (void *boss, GuiListEvent event), void *boss); GuiObject GuiMenuBar_addMenu (GuiObject bar, const wchar_t *title, long flags); GuiObject GuiMenuBar_addMenu2 (GuiObject bar, const wchar_t *title, long flags, GuiObject *menuTitle); #if gtk GuiObject GuiMenuBar_addMenu3 (GuiObject parent, const wchar_t *title, long flags, GuiObject *button); #endif /* Flags is a combination of the above defines. */ GuiObject GuiMenu_addItem (GuiObject menu, const wchar_t *title, long flags, void (*commandCallback) (GuiObject, XtPointer, XtPointer), const void *closure); /* Flags is a combination of the above defines. */ GuiObject GuiMenu_addSeparator (GuiObject menu); void GuiMenuItem_check (GuiObject menuItem, bool check); /* GuiRadioButton creation flags: */ #define GuiRadioButton_SET 1 #define GuiRadioButton_INSENSITIVE 2 typedef struct structGuiRadioButtonEvent { GuiObject toggle; } *GuiRadioButtonEvent; GuiObject GuiRadioButton_create (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*valueChangedCallback) (void *boss, GuiRadioButtonEvent event), void *valueChangedBoss, unsigned long flags); GuiObject GuiRadioButton_createShown (GuiObject parent, int left, int right, int top, int bottom, const wchar_t *buttonText, void (*valueChangedCallback) (void *boss, GuiRadioButtonEvent event), void *valueChangedBoss, unsigned long flags); bool GuiRadioButton_getValue (GuiObject widget); void GuiRadioButton_setValue (GuiObject widget, bool value); #if gtk void * GuiRadioButton_getGroup (GuiObject widget); void GuiRadioButton_setGroup (GuiObject widget, void *group); #endif typedef struct structGuiTextEvent { GuiObject text; } *GuiTextEvent; /* GuiText creation flags: */ #define GuiText_SCROLLED 1 #define GuiText_MULTILINE 2 #define GuiText_WORDWRAP 4 #define GuiText_NONEDITABLE 8 GuiObject GuiText_create (GuiObject parent, int left, int right, int top, int bottom, unsigned long flags); GuiObject GuiText_createShown (GuiObject parent, int left, int right, int top, int bottom, unsigned long flags); void GuiText_copy (GuiObject widget); void GuiText_cut (GuiObject widget); wchar_t * GuiText_getSelection (GuiObject widget); wchar_t * GuiText_getString (GuiObject widget); wchar_t * GuiText_getStringAndSelectionPosition (GuiObject widget, long *first, long *last); void GuiText_paste (GuiObject widget); void GuiText_redo (GuiObject widget); void GuiText_remove (GuiObject widget); void GuiText_replace (GuiObject widget, long from_pos, long to_pos, const wchar_t *value); void GuiText_scrollToSelection (GuiObject widget); void GuiText_setChangeCallback (GuiObject widget, void (*changeCallback) (void *boss, GuiTextEvent event), void *changeBoss); void GuiText_setFontSize (GuiObject widget, int size); void GuiText_setRedoItem (GuiObject widget, GuiObject item); void GuiText_setSelection (GuiObject widget, long first, long last); void GuiText_setString (GuiObject widget, const wchar_t *text); void GuiText_setUndoItem (GuiObject widget, GuiObject item); void GuiText_undo (GuiObject widget); void GuiText_updateChangeCountAfterSave (GuiObject widget); /* GuiWindow creation flags: */ #define GuiWindow_FULLSCREEN 1 GuiObject GuiWindow_create (GuiObject parentOfShell, int x, int y, int width, int height, const wchar_t *title, void (*goAwayCallback) (void *goAwayBoss), void *goAwayBoss, unsigned long flags); // returns a Form widget that has a new Shell parent. void GuiWindow_setTitle (GuiObject shell, const wchar_t *title); int GuiWindow_setDirty (GuiObject shell, int dirty); /* Purpose: like on MacOSX you get this little dot in the red close button, and the window proxy icon dims. Return value: TRUE if the system supports this feature, FALSE if not; the point of this is that you can use a different user feedback strategy, like appending the text "(modified)" to the window title, if this feature is not supported. */ void GuiWindow_setFile (GuiObject shell, MelderFile file); /* Purpose: set the window title, and (on MacOS X) the window proxy icon and the window path menu. */ void GuiWindow_drain (GuiObject me); /* Purpose: drain the double graphics buffer. */ void GuiObject_destroy (GuiObject me); long GuiObject_getHeight (GuiObject me); long GuiObject_getWidth (GuiObject me); long GuiObject_getX (GuiObject me); long GuiObject_getY (GuiObject me); void GuiObject_hide (GuiObject me); void GuiObject_move (GuiObject me, long x, long y); GuiObject GuiObject_parent (GuiObject w); void GuiObject_setSensitive (GuiObject me, bool sensitive); void GuiObject_show (GuiObject me); void GuiObject_size (GuiObject me, long width, long height); /********** EVENTS **********/ void Gui_setOpenDocumentCallback (void (*openDocumentCallback) (MelderFile file)); void Gui_setQuitApplicationCallback (int (*quitApplicationCallback) (void)); /* End of file Gui.h */ #endif sources_5316/sys/InfoEditor.cpp0000644000176700017670000000300511623706365015316 0ustar paulpaul/* InfoEditor.cpp * * Copyright (C) 2004-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "InfoEditor.h" Thing_implement (InfoEditor, TextEditor, 0); static InfoEditor theInfoEditor; void structInfoEditor :: v_destroy () { theInfoEditor = NULL; // undangle InfoEditor_Parent :: v_destroy (); } void structInfoEditor :: v_clear () { Melder_clearInfo (); } void gui_information (const wchar *message); // BUG void gui_information (const wchar *message) { if (! theInfoEditor) { theInfoEditor = Thing_new (InfoEditor); theInfoEditor -> structTextEditor :: init ((GuiObject) Melder_topShell, L""); Thing_setName (theInfoEditor, L"Praat Info"); } GuiText_setString (theInfoEditor -> textWidget, message); GuiObject_show (theInfoEditor -> d_windowForm); GuiWindow_drain (theInfoEditor -> d_windowShell); } /* End of file InfoEditor.cpp */ sources_5316/sys/melder_error.cpp0000644000176700017670000004244311632462417015743 0ustar paulpaul/* melder_error.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "melder.h" #include "longchar.h" static void defaultError (const wchar *message) { Melder_writeToConsole (wcsstr (message, L"You interrupted ") ? L"User interrupt: " : L"Error: ", true); Melder_writeToConsole (message, true); Melder_writeToConsole (L"\n", true); } static void (*theError) (const wchar *) = defaultError; // initial setting after start-up; will stay if program is run from batch void Melder_setErrorProc (void (*error) (const wchar *)) { theError = error ? error : defaultError; } static wchar errors [2000+1]; // safe in low-memory situations static void appendErrorA (const char *message) { int length = wcslen (errors), messageLength = strlen (message); if (length + messageLength > 2000) return; for (long i = 0; i < messageLength; i ++) { errors [length + i] = (unsigned char) message [i]; } errors [length + messageLength] = L'\0'; } static void appendErrorALine (const char *message) { int length = wcslen (errors), messageLength = strlen (message); if (length + messageLength > 2000 - 1) return; // 1 == length of "\n" for (long i = 0; i < messageLength; i ++) { errors [length + i] = (unsigned char) message [i]; } errors [length + messageLength] = L'\n'; errors [length + messageLength + 1] = L'\0'; } static void appendErrorW (const wchar *message) { int length = wcslen (errors), messageLength = wcslen (message); if (length + messageLength > 2000) return; wcscpy (errors + length, message); } bool Melder_hasError () { return errors [0] != L'\0'; } bool Melder_hasError (const wchar_t *partialError) { return wcsstr (errors, partialError) != NULL; } void Melder_clearError (void) { errors [0] = L'\0'; } wchar * Melder_getError (void) { return & errors [0]; } void Melder_flushError (const char *format, ...) { va_list arg; va_start (arg, format); if (format) { vsprintf (Melder_buffer1, format, arg); appendErrorALine (Melder_buffer1); } /* "errors" has to be cleared *before* the message is put on the screen. This is because on some platforms the message dialog is synchronous (Melder_flushError will wait until the message dialog is closed), and some operating systems may force an immediate redraw event as soon as the message dialog is closed. We want "errors" to be empty when redrawing! */ static wchar temp [2000+1]; wcscpy (temp, errors); Melder_clearError (); theError (temp); va_end (arg); } void Melder_error_ (const MelderArg& arg1) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } if (arg6.argW) { if (arg6.type == 1) appendErrorW (arg6.argW); else appendErrorA (arg6.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } if (arg6.argW) { if (arg6.type == 1) appendErrorW (arg6.argW); else appendErrorA (arg6.arg8); } if (arg7.argW) { if (arg7.type == 1) appendErrorW (arg7.argW); else appendErrorA (arg7.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } if (arg6.argW) { if (arg6.type == 1) appendErrorW (arg6.argW); else appendErrorA (arg6.arg8); } if (arg7.argW) { if (arg7.type == 1) appendErrorW (arg7.argW); else appendErrorA (arg7.arg8); } if (arg8.argW) { if (arg8.type == 1) appendErrorW (arg8.argW); else appendErrorA (arg8.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } if (arg6.argW) { if (arg6.type == 1) appendErrorW (arg6.argW); else appendErrorA (arg6.arg8); } if (arg7.argW) { if (arg7.type == 1) appendErrorW (arg7.argW); else appendErrorA (arg7.arg8); } if (arg8.argW) { if (arg8.type == 1) appendErrorW (arg8.argW); else appendErrorA (arg8.arg8); } if (arg9.argW) { if (arg9.type == 1) appendErrorW (arg9.argW); else appendErrorA (arg9.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } if (arg6.argW) { if (arg6.type == 1) appendErrorW (arg6.argW); else appendErrorA (arg6.arg8); } if (arg7.argW) { if (arg7.type == 1) appendErrorW (arg7.argW); else appendErrorA (arg7.arg8); } if (arg8.argW) { if (arg8.type == 1) appendErrorW (arg8.argW); else appendErrorA (arg8.arg8); } if (arg9.argW) { if (arg9.type == 1) appendErrorW (arg9.argW); else appendErrorA (arg9.arg8); } if (arg10.argW) { if (arg10.type == 1) appendErrorW (arg10.argW); else appendErrorA (arg10.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } if (arg6.argW) { if (arg6.type == 1) appendErrorW (arg6.argW); else appendErrorA (arg6.arg8); } if (arg7.argW) { if (arg7.type == 1) appendErrorW (arg7.argW); else appendErrorA (arg7.arg8); } if (arg8.argW) { if (arg8.type == 1) appendErrorW (arg8.argW); else appendErrorA (arg8.arg8); } if (arg9.argW) { if (arg9.type == 1) appendErrorW (arg9.argW); else appendErrorA (arg9.arg8); } if (arg10.argW) { if (arg10.type == 1) appendErrorW (arg10.argW); else appendErrorA (arg10.arg8); } if (arg11.argW) { if (arg11.type == 1) appendErrorW (arg11.argW); else appendErrorA (arg11.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } if (arg6.argW) { if (arg6.type == 1) appendErrorW (arg6.argW); else appendErrorA (arg6.arg8); } if (arg7.argW) { if (arg7.type == 1) appendErrorW (arg7.argW); else appendErrorA (arg7.arg8); } if (arg8.argW) { if (arg8.type == 1) appendErrorW (arg8.argW); else appendErrorA (arg8.arg8); } if (arg9.argW) { if (arg9.type == 1) appendErrorW (arg9.argW); else appendErrorA (arg9.arg8); } if (arg10.argW) { if (arg10.type == 1) appendErrorW (arg10.argW); else appendErrorA (arg10.arg8); } if (arg11.argW) { if (arg11.type == 1) appendErrorW (arg11.argW); else appendErrorA (arg11.arg8); } if (arg12.argW) { if (arg12.type == 1) appendErrorW (arg12.argW); else appendErrorA (arg12.arg8); } if (arg13.argW) { if (arg13.type == 1) appendErrorW (arg13.argW); else appendErrorA (arg13.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } if (arg6.argW) { if (arg6.type == 1) appendErrorW (arg6.argW); else appendErrorA (arg6.arg8); } if (arg7.argW) { if (arg7.type == 1) appendErrorW (arg7.argW); else appendErrorA (arg7.arg8); } if (arg8.argW) { if (arg8.type == 1) appendErrorW (arg8.argW); else appendErrorA (arg8.arg8); } if (arg9.argW) { if (arg9.type == 1) appendErrorW (arg9.argW); else appendErrorA (arg9.arg8); } if (arg10.argW) { if (arg10.type == 1) appendErrorW (arg10.argW); else appendErrorA (arg10.arg8); } if (arg11.argW) { if (arg11.type == 1) appendErrorW (arg11.argW); else appendErrorA (arg11.arg8); } if (arg12.argW) { if (arg12.type == 1) appendErrorW (arg12.argW); else appendErrorA (arg12.arg8); } if (arg13.argW) { if (arg13.type == 1) appendErrorW (arg13.argW); else appendErrorA (arg13.arg8); } if (arg14.argW) { if (arg14.type == 1) appendErrorW (arg14.argW); else appendErrorA (arg14.arg8); } if (arg15.argW) { if (arg15.type == 1) appendErrorW (arg15.argW); else appendErrorA (arg15.arg8); } appendErrorW (L"\n"); } void Melder_error_ (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15, const MelderArg& arg16, const MelderArg& arg17, const MelderArg& arg18, const MelderArg& arg19, const MelderArg& arg20) { if (arg1.argW) { if (arg1.type == 1) appendErrorW (arg1.argW); else appendErrorA (arg1.arg8); } if (arg2.argW) { if (arg2.type == 1) appendErrorW (arg2.argW); else appendErrorA (arg2.arg8); } if (arg3.argW) { if (arg3.type == 1) appendErrorW (arg3.argW); else appendErrorA (arg3.arg8); } if (arg4.argW) { if (arg4.type == 1) appendErrorW (arg4.argW); else appendErrorA (arg4.arg8); } if (arg5.argW) { if (arg5.type == 1) appendErrorW (arg5.argW); else appendErrorA (arg5.arg8); } if (arg6.argW) { if (arg6.type == 1) appendErrorW (arg6.argW); else appendErrorA (arg6.arg8); } if (arg7.argW) { if (arg7.type == 1) appendErrorW (arg7.argW); else appendErrorA (arg7.arg8); } if (arg8.argW) { if (arg8.type == 1) appendErrorW (arg8.argW); else appendErrorA (arg8.arg8); } if (arg9.argW) { if (arg9.type == 1) appendErrorW (arg9.argW); else appendErrorA (arg9.arg8); } if (arg10.argW) { if (arg10.type == 1) appendErrorW (arg10.argW); else appendErrorA (arg10.arg8); } if (arg11.argW) { if (arg11.type == 1) appendErrorW (arg11.argW); else appendErrorA (arg11.arg8); } if (arg12.argW) { if (arg12.type == 1) appendErrorW (arg12.argW); else appendErrorA (arg12.arg8); } if (arg13.argW) { if (arg13.type == 1) appendErrorW (arg13.argW); else appendErrorA (arg13.arg8); } if (arg14.argW) { if (arg14.type == 1) appendErrorW (arg14.argW); else appendErrorA (arg14.arg8); } if (arg15.argW) { if (arg15.type == 1) appendErrorW (arg15.argW); else appendErrorA (arg15.arg8); } if (arg16.argW) { if (arg16.type == 1) appendErrorW (arg16.argW); else appendErrorA (arg16.arg8); } if (arg17.argW) { if (arg17.type == 1) appendErrorW (arg17.argW); else appendErrorA (arg17.arg8); } if (arg18.argW) { if (arg18.type == 1) appendErrorW (arg18.argW); else appendErrorA (arg18.arg8); } if (arg19.argW) { if (arg19.type == 1) appendErrorW (arg19.argW); else appendErrorA (arg19.arg8); } if (arg20.argW) { if (arg20.type == 1) appendErrorW (arg20.argW); else appendErrorA (arg20.arg8); } appendErrorW (L"\n"); } /* End of file melder_error.cpp */ sources_5316/sys/melder_quantity.cpp0000644000176700017670000000315711546675171016476 0ustar paulpaul/* melder_quantity.cpp * * Copyright (C) 2007-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/03/17 created * pb 2007/08/14 wchar_t * pb 2008/03/07 typo * pb 2011/04/05 C++ */ #include "melder.h" static const wchar_t * texts [1+MelderQuantity_NUMBER_OF_QUANTITIES] [4] = { { L"", L"", L"", L"" }, { L"Time", L"Time (s)", L"seconds", L"s" }, { L"Frequency", L"Frequency (Hz)", L"Hertz", L"Hz" }, { L"Frequency", L"Frequency (Bark)", L"Bark", L"Bark" }, { L"Distance from glottis", L"Distance from glottis (m)", L"metres", L"m" }, }; const wchar_t * MelderQuantity_getText (int quantity) { return texts [quantity] [0]; } const wchar_t * MelderQuantity_getWithUnitText (int quantity) { return texts [quantity] [1]; } const wchar_t * MelderQuantity_getLongUnitText (int quantity) { return texts [quantity] [2]; } const wchar_t * MelderQuantity_getShortUnitText (int quantity) { return texts [quantity] [3]; } /* End of file melder_quantity.cpp */ sources_5316/sys/praat_script.h0000644000176700017670000000325211622337774015423 0ustar paulpaul#ifndef _praat_script_h_ #define _praat_script_h_ /* praat_script.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Interpreter.h" void praat_executeCommand (Interpreter me, wchar *command); void praat_executeCommandFromStandardInput (const char *programName); void praat_executeScriptFromFile (MelderFile file, const wchar *arguments); void praat_executeScriptFromFileNameWithArguments (const wchar *nameAndArguments); void praat_executeScriptFromText (wchar *text); void praat_executeScriptFromDialog (Any dia); void DO_praat_runScript (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter_dummy, const wchar *invokingButtonTitle, bool modified, void *dummy); void DO_RunTheScriptFromAnyAddedMenuCommand (UiForm sendingForm_dummy, const wchar *scriptPath, Interpreter interpreter_dummy, const wchar *invokingButtonTitle, bool modified, void *dummy); void DO_RunTheScriptFromAnyAddedEditorCommand (Editor editor, const wchar *script); /* End of file praat_script.h */ #endif sources_5316/sys/Editor_enums.h0000644000176700017670000000233610725503422015353 0ustar paulpaul/* Editor_enums.h * * Copyright (C) 1992-2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/05 */ enums_begin (kEditor_writeNameAtTop, 0) enums_add (kEditor_writeNameAtTop, 0, NO, L"no") enums_add (kEditor_writeNameAtTop, 1, FAR, L"far") enums_add (kEditor_writeNameAtTop, 2, NEAR, L"near") /* For reading old preferences files: */ enums_alt (kEditor_writeNameAtTop, NO, L"0") enums_alt (kEditor_writeNameAtTop, FAR, L"1") enums_alt (kEditor_writeNameAtTop, NEAR, L"2") enums_end (kEditor_writeNameAtTop, 2, FAR) /* End of file Editor_enums.h */ sources_5316/sys/oo_READ_TEXT.h0000644000176700017670000001350611724667477015020 0ustar paulpaul/* oo_READ_TEXT.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) \ try { \ x = texget##storage (a_text); \ } catch (MelderError) { \ Melder_throw ("\"", #x, L"\" not read."); \ } #define oo_ARRAY(type,storage,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (long i = 0; i < n; i ++) { \ try { \ x [i] = texget##storage (a_text); \ } catch (MelderError) { \ Melder_throw ("Element ", i+1, " of \"", #x, "\" not read."); \ } \ } #define oo_SET(type,storage,x,setType) \ for (long i = 0; i <= setType##_MAX; i ++) { \ try { \ x [i] = texget##storage (a_text); \ } catch (MelderError) { \ Melder_throw ("Element ", i+1, " of \"", #x, "\" not read."); \ } \ } #define oo_VECTOR(type,storage,x,min,max) \ if (max >= min) { \ x = NUMvector_readText_##storage (min, max, a_text, #x); therror \ } #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) \ if (row2 >= row1 && col2 >= col1) { \ x = NUMmatrix_readText_##storage (row1, row2, col1, col2, a_text, #x); therror \ } #define oo_ENUMx(type,storage,Type,x) \ x = texget##storage (a_text, Type##_getValue); #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (long i = 0; i < n; i ++) { \ x [i] = texget##storage (a_text, Type##_getValue); therror \ } #define oo_ENUMx_SET(type,storage,Type,x,setType) \ for (long i = 0; i <= setType##_MAX; i ++) { \ x [i] = texget##storage (a_text, & Type##_getValue); \ } #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) \ if (max >= min) { \ x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) { \ x [i] = texget##storage (a_text, & Type##_getValue); \ } \ } #define oo_STRINGx(storage,x) \ try { \ x = texget##storage (a_text); \ } catch (MelderError) { \ Melder_throw ("String \"", #x, "\" not read."); \ } #define oo_STRINGx_ARRAY(storage,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (long i = 0; i < n; i ++) { \ x [i] = texget##storage (a_text); \ } #define oo_STRINGx_SET(storage,x,setType) \ for (long i = 0; i <= setType##_MAX; i ++) { \ x [i] = texget##storage (a_text); \ } #define oo_STRINGx_VECTOR(storage,x,min,max) \ if (max >= min) { \ x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) { \ try { \ x [i] = texget##storage (a_text); \ } catch (MelderError) { \ Melder_throw ("Element ", i, " of \"" #x, "\" not read."); \ } \ } \ } #define oo_STRUCT(Type,x) \ x. readText (a_text); therror #define oo_STRUCT_ARRAY(Type,x,cap,n) \ if (n > cap) Melder_throw ("Number of \"", #x, "\" (", n, ") greater than ", cap, "."); \ for (long i = 0; i < n; i ++) { \ x [i]. readText (a_text); therror \ } #define oo_STRUCT_SET(Type,x,setType) \ for (long i = 0; i <= setType##_MAX; i ++) { \ x [i]. readText (a_text); therror \ } #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ if (max >= min) { \ x = NUMvector (min, max); \ for (long i = min; i <= max; i ++) { \ x [i]. readText (a_text); therror \ } \ } #define oo_OBJECT(Class,version,x) \ if (texgetex (a_text) == 1) { \ long saveVersion = Thing_version; \ x = Thing_new (Class); \ Thing_version = version; \ x -> v_readText (a_text); therror \ Thing_version = saveVersion; \ } #define oo_COLLECTION(Class,x,ItemClass,version) \ { \ long n = texgeti4 (a_text); \ x = Class##_create (); therror \ for (long i = 1; i <= n; i ++) { \ long saveVersion = Thing_version; \ auto##ItemClass item = (ItemClass) Thing_new (ItemClass); \ Thing_version = version; \ item.peek() -> v_readText (a_text); therror \ Thing_version = saveVersion; \ Collection_addItem (x, item.transfer()); \ } \ } #define oo_FILE(x) #define oo_DIR(x) #define oo_DEFINE_STRUCT(Type) \ void struct##Type :: readText (MelderReadText a_text) { \ int localVersion = Thing_version; (void) localVersion; #define oo_END_STRUCT(Type) \ } #define oo_DEFINE_CLASS(Class,Parent) \ void struct##Class :: v_readText (MelderReadText a_text) { \ int localVersion = Thing_version; (void) localVersion; \ if (localVersion > this -> classInfo -> version) \ Melder_throw ("The format of this file is too new. Download a newer version of Praat."); \ Class##_Parent :: v_readText (a_text); therror #define oo_END_CLASS(Class) \ } #define oo_IF(condition) \ if (condition) { #define oo_ENDIF \ } #define oo_FROM(from) \ if (localVersion >= from) { #define oo_ENDFROM \ } #define oo_VERSION(version) \ Thing_version = version; #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 0 #define oo_READING 1 #define oo_READING_TEXT 1 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 0 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_READ_TEXT.h */ sources_5316/sys/melder.cpp0000644000176700017670000011753111753751770014542 0ustar paulpaul/* melder.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2002/03/13 Mach * pb 2002/12/11 MelderInfo * pb 2003/12/29 Melder_warning: added XMapRaised because delete response is UNMAP * pb 2004/04/06 motif_information drains text window only, i.e. no longer updates all windows (which used to cause up to seven seconds of delay in a 1-second sound window) * pb 2004/10/24 info buffer can grow * pb 2004/11/28 author notification in Melder_fatal * pb 2005/03/04 number and string comparisons, including regular expressions * pb 2005/06/16 removed enums from number and string comparisons (ints give no compiler warnings) * pb 2005/07/19 Melder_stringMatchesCriterion: regard NULL criterion as empty string * pb 2007/05/24 more wchar * pb 2007/05/26 Melder_stringMatchesCriterionW * pb 2007/06/19 removed some * pb 2007/08/12 wchar in helpProc * pb 2007/12/02 enums * pb 2007/12/13 Melder_writeToConsole * pb 2007/12/18 Gui * sdk 2008/01/22 GTK * pb 2009/01/20 removed pause * fb 2010/02/26 GTK * pb 2010/06/22 GTK: correct hiding and showing again * pb 2010/07/29 removed GuiDialog_show * pb 2010/11/26 even Unix now has a GUI fatal window * pb 2010/12/30 messageFund * pb 2011/04/03 C++ */ #include #include #include #include #include "melder.h" #include "longchar.h" #include "regularExp.h" #ifdef _WIN32 #include #endif #if defined (macintosh) #include "macport_on.h" //#include #include "macport_off.h" #endif #ifndef CONSOLE_APPLICATION #include "Graphics.h" #include "machine.h" #ifdef macintosh #include "macport_on.h" //#include #include #include #include "macport_off.h" #endif #include "Gui.h" #endif #include "enums_getText.h" #include "melder_enums.h" #include "enums_getValue.h" #include "melder_enums.h" /********** Exported variables. **********/ bool Melder_batch; // don't we have a GUI?- Set once at application start-up bool Melder_backgrounding; // are we running a script?- Set and unset dynamically char Melder_buffer1 [30001], Melder_buffer2 [30001]; unsigned long Melder_systemVersion; #ifndef CONSOLE_APPLICATION void *Melder_topShell; // GuiObject #endif static void defaultHelp (const wchar *query) { Melder_error_ ("Don't know how to find help on \"", query, "\"."); Melder_flushError (NULL); } static void defaultSearch (void) { Melder_flushError ("Do not know how to search."); } static void defaultWarning (const wchar *message) { Melder_writeToConsole (L"Warning: ", true); Melder_writeToConsole (message, true); Melder_writeToConsole (L"\n", true); } static void defaultFatal (const wchar *message) { Melder_writeToConsole (L"Fatal error: ", true); Melder_writeToConsole (message, true); Melder_writeToConsole (L"\n", true); } static int defaultPublish (void *anything) { (void) anything; return 0; /* Nothing published. */ } static int defaultRecord (double duration) { (void) duration; return 0; /* Nothing recorded. */ } static int defaultRecordFromFile (MelderFile file) { (void) file; return 0; /* Nothing recorded. */ } static void defaultPlay (void) {} static void defaultPlayReverse (void) {} static int defaultPublishPlayed (void) { return 0; /* Nothing published. */ } /********** Current message methods: initialize to default (batch) behaviour. **********/ static struct { void (*help) (const wchar *query); void (*search) (void); void (*warning) (const wchar *message); void (*fatal) (const wchar *message); int (*publish) (void *anything); int (*record) (double duration); int (*recordFromFile) (MelderFile fs); void (*play) (void); void (*playReverse) (void); int (*publishPlayed) (void); } theMelder = { defaultHelp, defaultSearch, defaultWarning, defaultFatal, defaultPublish, defaultRecord, defaultRecordFromFile, defaultPlay, defaultPlayReverse, defaultPublishPlayed }; /********** CASUAL **********/ void Melder_casual (const char *format, ...) { va_list arg; va_start (arg, format); vsprintf (Melder_buffer1, format, arg); fprintf (stderr, "%s\n", Melder_buffer1); va_end (arg); } /********** PROGRESS **********/ static int theProgressDepth = 0; void Melder_progressOff (void) { theProgressDepth --; } void Melder_progressOn (void) { theProgressDepth ++; } #ifndef CONSOLE_APPLICATION static bool waitWhileProgress (double progress, const wchar *message, GuiObject dia, GuiObject scale, GuiObject label1, GuiObject label2, GuiObject cancelButton) { #if gtk // Wait for all pending events to be processed. If anybody knows how to inspect GTK's // event queue for specific events, dump the code here, please. // Until then, the button click attaches a g_object data key named "pressed" to the cancelButton // which this function reads out in order to tell whether interruption has occurred while (gtk_events_pending ()) gtk_main_iteration (); #elif defined (macintosh) #if useCarbon EventRecord event; while (GetNextEvent (mDownMask, & event)) { WindowPtr macWindow; int part = FindWindow (event. where, & macWindow); if (part == inContent) { if (GetWindowKind (macWindow) == userKind) { SetPortWindowPort (macWindow); GlobalToLocal (& event. where); ControlPartCode controlPart; ControlHandle macControl = FindControlUnderMouse (event. where, macWindow, & controlPart); if (macControl) { GuiObject control = (GuiObject) GetControlReference (macControl); if (control == cancelButton) { FlushEvents (everyEvent, 0); XtUnmanageChild (dia); return false; // don't continue } else { break; } } else { XtDispatchEvent ((XEvent *) & event); } } else { XtDispatchEvent ((XEvent *) & event); } } else { XtDispatchEvent ((XEvent *) & event); } } do { XtNextEvent ((XEvent *) & event); XtDispatchEvent ((XEvent *) & event); } while (event.what); #else // Cocoa #endif #elif defined (_WIN32) XEvent event; while (PeekMessage (& event, 0, 0, 0, PM_REMOVE)) { if (event. message == WM_KEYDOWN) { /* * Ignore all key-down messages, except Escape. */ if (LOWORD (event. wParam) == VK_ESCAPE) { XtUnmanageChild (dia); return false; // don't continue } } else if (event. message == WM_LBUTTONDOWN) { /* * Ignore all mouse-down messages, except click in Interrupt button. */ GuiObject me = (GuiObject) GetWindowLongPtr (event. hwnd, GWLP_USERDATA); if (me == cancelButton) { XtUnmanageChild (dia); return false; // don't continue } } else if (event. message != WM_SYSKEYDOWN) { /* * Process paint messages etc. */ DispatchMessage (& event); } } #else XEvent event; if (XCheckTypedWindowEvent (XtDisplay (cancelButton), XtWindow (cancelButton), ButtonPress, & event)) { XtUnmanageChild (dia); return false; // don't continue } #endif if (progress >= 1.0) { GuiObject_hide (dia); } else { if (progress <= 0.0) progress = 0.0; GuiObject_show (dia); // TODO: prevent raising to the front const wchar *newline = wcschr (message, '\n'); if (newline != NULL) { static MelderString buffer = { 0 }; MelderString_copy (& buffer, message); buffer.string [newline - message] = '\0'; GuiLabel_setString (label1, buffer.string); buffer.string [newline - message] = '\n'; GuiLabel_setString (label2, buffer.string + (newline - message) + 1); } else { GuiLabel_setString (label1, message); GuiLabel_setString (label2, L""); } #if gtk // update progress bar gtk_progress_bar_set_fraction (GTK_PROGRESS_BAR (scale), progress); while (gtk_events_pending ()) gtk_main_iteration (); // check whether cancelButton has the "pressed" key set if (g_object_steal_data (G_OBJECT (cancelButton), "pressed")) return false; // don't continue #elif motif XmScaleSetValue (scale, floor (progress * 1000.0)); XmUpdateDisplay (dia); #endif } return true; // continue } #if gtk static void progress_dia_close (void *wid) { g_object_set_data (G_OBJECT (* (GuiObject *) wid), "pressed", (gpointer) 1); } static void progress_cancel_btn_press (void *wid, GuiButtonEvent event) { (void) event; g_object_set_data (G_OBJECT (* (GuiObject *) wid), "pressed", (gpointer) 1); } #endif static void _Melder_dia_init (GuiObject *dia, GuiObject *scale, GuiObject *label1, GuiObject *label2, GuiObject *cancelButton) { *dia = GuiDialog_create ((GuiObject) Melder_topShell, 200, 100, Gui_AUTOMATIC, Gui_AUTOMATIC, L"Work in progress", #if gtk progress_dia_close, cancelButton, #else NULL, NULL, #endif 0); GuiObject form = *dia; GuiObject buttons = GuiDialog_getButtonArea (*dia); *label1 = GuiLabel_createShown (form, 3, 403, 0, Gui_AUTOMATIC, L"label1", 0); *label2 = GuiLabel_createShown (form, 3, 403, 30, Gui_AUTOMATIC, L"label2", 0); #if gtk *scale = gtk_progress_bar_new (); gtk_container_add (GTK_CONTAINER (form), GTK_WIDGET (*scale)); GuiObject_show (*scale); #elif motif *scale = XmCreateScale (*dia, "scale", NULL, 0); XtVaSetValues (*scale, XmNy, 70, XmNwidth, 400, XmNminimum, 0, XmNmaximum, 1000, XmNorientation, XmHORIZONTAL, #if ! defined (macintosh) XmNscaleHeight, 20, #endif NULL); GuiObject_show (*scale); #endif #if ! defined (macintoshXXX) *cancelButton = GuiButton_createShown (buttons, 0, 400, 170, Gui_AUTOMATIC, L"Interrupt", #if gtk progress_cancel_btn_press, cancelButton, #else NULL, NULL, #endif 0); #endif } #endif static void _Melder_progress (double progress, const wchar *message) { (void) progress; #ifndef CONSOLE_APPLICATION if (! Melder_batch && theProgressDepth >= 0 && Melder_debug != 14) { static clock_t lastTime; static GuiObject dia = NULL, scale = NULL, label1 = NULL, label2 = NULL, cancelButton = NULL; clock_t now = clock (); if (progress <= 0.0 || progress >= 1.0 || now - lastTime > CLOCKS_PER_SEC / 4) // this time step must be much longer than the null-event waiting time { if (dia == NULL) _Melder_dia_init (& dia, & scale, & label1, & label2, & cancelButton); if (! waitWhileProgress (progress, message, dia, scale, label1, label2, cancelButton)) Melder_throw ("Interrupted!"); lastTime = now; } } #endif } static MelderString theProgressBuffer = { 0 }; void Melder_progress (double progress, const wchar *s1) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1); _Melder_progress (progress, theProgressBuffer.string); } void Melder_progress (double progress, const wchar *s1, const wchar *s2) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2); _Melder_progress (progress, theProgressBuffer.string); } void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3); _Melder_progress (progress, theProgressBuffer.string); } void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4); _Melder_progress (progress, theProgressBuffer.string); } void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5); _Melder_progress (progress, theProgressBuffer.string); } void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5, s6); _Melder_progress (progress, theProgressBuffer.string); } void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5, s6, s7); _Melder_progress (progress, theProgressBuffer.string); } void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5, s6, s7, s8); _Melder_progress (progress, theProgressBuffer.string); } void Melder_progress (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5, s6, s7, s8, s9); _Melder_progress (progress, theProgressBuffer.string); } static void * _Melder_monitor (double progress, const wchar *message) { (void) progress; #ifndef CONSOLE_APPLICATION if (! Melder_batch && theProgressDepth >= 0) { static clock_t lastTime; static GuiObject dia = NULL, scale = NULL, label1 = NULL, label2 = NULL, cancelButton = NULL, drawingArea = NULL; clock_t now = clock (); static Any graphics = NULL; if (progress <= 0.0 || progress >= 1.0 || now - lastTime > CLOCKS_PER_SEC / 4) // this time step must be much longer than the null-event waiting time { if (dia == NULL) { _Melder_dia_init (& dia, & scale, & label1, & label2, & cancelButton); drawingArea = GuiDrawingArea_createShown (dia, 0, 400, 230, 430, NULL, NULL, NULL, NULL, NULL, 0); GuiObject_show (dia); graphics = Graphics_create_xmdrawingarea (drawingArea); } if (! waitWhileProgress (progress, message, dia, scale, label1, label2, cancelButton)) Melder_throw ("Interrupted!"); lastTime = now; if (progress == 0.0) return graphics; } } #endif return progress <= 0.0 ? NULL /* no Graphics */ : & progress /* any non-NULL pointer */; } void * Melder_monitor (double progress, const wchar *s1) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1); return _Melder_monitor (progress, theProgressBuffer.string); } void * Melder_monitor (double progress, const wchar *s1, const wchar *s2) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2); return _Melder_monitor (progress, theProgressBuffer.string); } void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3); return _Melder_monitor (progress, theProgressBuffer.string); } void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4); return _Melder_monitor (progress, theProgressBuffer.string); } void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5); return _Melder_monitor (progress, theProgressBuffer.string); } void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5, s6); return _Melder_monitor (progress, theProgressBuffer.string); } void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5, s6, s7); return _Melder_monitor (progress, theProgressBuffer.string); } void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5, s6, s7, s8); return _Melder_monitor (progress, theProgressBuffer.string); } void * Melder_monitor (double progress, const wchar *s1, const wchar *s2, const wchar *s3, const wchar *s4, const wchar *s5, const wchar *s6, const wchar *s7, const wchar *s8, const wchar *s9) { MelderString_empty (& theProgressBuffer); MelderString_append (& theProgressBuffer, s1, s2, s3, s4, s5, s6, s7, s8, s9); return _Melder_monitor (progress, theProgressBuffer.string); } /********** NUMBER AND STRING COMPARISONS **********/ int Melder_numberMatchesCriterion (double value, int which_kMelder_number, double criterion) { return (which_kMelder_number == kMelder_number_EQUAL_TO && value == criterion) || (which_kMelder_number == kMelder_number_NOT_EQUAL_TO && value != criterion) || (which_kMelder_number == kMelder_number_LESS_THAN && value < criterion) || (which_kMelder_number == kMelder_number_LESS_THAN_OR_EQUAL_TO && value <= criterion) || (which_kMelder_number == kMelder_number_GREATER_THAN && value > criterion) || (which_kMelder_number == kMelder_number_GREATER_THAN_OR_EQUAL_TO && value >= criterion); } int Melder_stringMatchesCriterion (const wchar *value, int which_kMelder_string, const wchar *criterion) { if (value == NULL) { value = L""; /* Regard null strings as empty strings, as is usual in Praat. */ } if (criterion == NULL) { criterion = L""; /* Regard null strings as empty strings, as is usual in Praat. */ } if (which_kMelder_string <= kMelder_string_NOT_EQUAL_TO) { int matchPositiveCriterion = wcsequ (value, criterion); return (which_kMelder_string == kMelder_string_EQUAL_TO) == matchPositiveCriterion; } if (which_kMelder_string <= kMelder_string_DOES_NOT_CONTAIN) { int matchPositiveCriterion = wcsstr (value, criterion) != NULL; return (which_kMelder_string == kMelder_string_CONTAINS) == matchPositiveCriterion; } if (which_kMelder_string <= kMelder_string_DOES_NOT_START_WITH) { int matchPositiveCriterion = wcsnequ (value, criterion, wcslen (criterion)); return (which_kMelder_string == kMelder_string_STARTS_WITH) == matchPositiveCriterion; } if (which_kMelder_string <= kMelder_string_DOES_NOT_END_WITH) { int criterionLength = wcslen (criterion), valueLength = wcslen (value); int matchPositiveCriterion = criterionLength <= valueLength && wcsequ (value + valueLength - criterionLength, criterion); return (which_kMelder_string == kMelder_string_ENDS_WITH) == matchPositiveCriterion; } if (which_kMelder_string == kMelder_string_MATCH_REGEXP) { wchar *place = NULL; const wchar *errorMessage; regexp *compiled_regexp = CompileRE ((regularExp_CHAR *) criterion, & errorMessage, 0); if (compiled_regexp == NULL) return FALSE; // BUG: what about removing errorMessage? if (ExecRE (compiled_regexp, NULL, (regularExp_CHAR *) value, NULL, 0, '\0', '\0', NULL, NULL, NULL)) place = (wchar *) compiled_regexp -> startp [0]; free (compiled_regexp); return place != NULL; } return 0; /* Should not occur. */ } void Melder_help (const wchar *query) { theMelder. help (query); } void Melder_search (void) { theMelder. search (); } /********** WARNING **********/ static int theWarningDepth = 0; void Melder_warningOff (void) { theWarningDepth --; } void Melder_warningOn (void) { theWarningDepth ++; } static MelderString theWarningBuffer = { 0 }; void Melder_warning (const MelderArg& arg1) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8), arg6.type == 1 ? arg6.argW : Melder_peekUtf8ToWcs (arg6.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8), arg6.type == 1 ? arg6.argW : Melder_peekUtf8ToWcs (arg6.arg8), arg7.type == 1 ? arg7.argW : Melder_peekUtf8ToWcs (arg7.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8), arg6.type == 1 ? arg6.argW : Melder_peekUtf8ToWcs (arg6.arg8), arg7.type == 1 ? arg7.argW : Melder_peekUtf8ToWcs (arg7.arg8), arg8.type == 1 ? arg8.argW : Melder_peekUtf8ToWcs (arg8.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8), arg6.type == 1 ? arg6.argW : Melder_peekUtf8ToWcs (arg6.arg8), arg7.type == 1 ? arg7.argW : Melder_peekUtf8ToWcs (arg7.arg8), arg8.type == 1 ? arg8.argW : Melder_peekUtf8ToWcs (arg8.arg8), arg9.type == 1 ? arg9.argW : Melder_peekUtf8ToWcs (arg9.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8), arg6.type == 1 ? arg6.argW : Melder_peekUtf8ToWcs (arg6.arg8), arg7.type == 1 ? arg7.argW : Melder_peekUtf8ToWcs (arg7.arg8), arg8.type == 1 ? arg8.argW : Melder_peekUtf8ToWcs (arg8.arg8), arg9.type == 1 ? arg9.argW : Melder_peekUtf8ToWcs (arg9.arg8)); MelderString_append (& theWarningBuffer, arg10.type == 1 ? arg10.argW : Melder_peekUtf8ToWcs (arg10.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8), arg6.type == 1 ? arg6.argW : Melder_peekUtf8ToWcs (arg6.arg8), arg7.type == 1 ? arg7.argW : Melder_peekUtf8ToWcs (arg7.arg8), arg8.type == 1 ? arg8.argW : Melder_peekUtf8ToWcs (arg8.arg8), arg9.type == 1 ? arg9.argW : Melder_peekUtf8ToWcs (arg9.arg8)); MelderString_append (& theWarningBuffer, arg10.type == 1 ? arg10.argW : Melder_peekUtf8ToWcs (arg10.arg8), arg11.type == 1 ? arg11.argW : Melder_peekUtf8ToWcs (arg11.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8), arg6.type == 1 ? arg6.argW : Melder_peekUtf8ToWcs (arg6.arg8), arg7.type == 1 ? arg7.argW : Melder_peekUtf8ToWcs (arg7.arg8), arg8.type == 1 ? arg8.argW : Melder_peekUtf8ToWcs (arg8.arg8), arg9.type == 1 ? arg9.argW : Melder_peekUtf8ToWcs (arg9.arg8)); MelderString_append (& theWarningBuffer, arg10.type == 1 ? arg10.argW : Melder_peekUtf8ToWcs (arg10.arg8), arg11.type == 1 ? arg11.argW : Melder_peekUtf8ToWcs (arg11.arg8), arg12.type == 1 ? arg12.argW : Melder_peekUtf8ToWcs (arg12.arg8), arg13.type == 1 ? arg13.argW : Melder_peekUtf8ToWcs (arg13.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8), arg6.type == 1 ? arg6.argW : Melder_peekUtf8ToWcs (arg6.arg8), arg7.type == 1 ? arg7.argW : Melder_peekUtf8ToWcs (arg7.arg8), arg8.type == 1 ? arg8.argW : Melder_peekUtf8ToWcs (arg8.arg8), arg9.type == 1 ? arg9.argW : Melder_peekUtf8ToWcs (arg9.arg8)); MelderString_append (& theWarningBuffer, arg10.type == 1 ? arg10.argW : Melder_peekUtf8ToWcs (arg10.arg8), arg11.type == 1 ? arg11.argW : Melder_peekUtf8ToWcs (arg11.arg8), arg12.type == 1 ? arg12.argW : Melder_peekUtf8ToWcs (arg12.arg8), arg13.type == 1 ? arg13.argW : Melder_peekUtf8ToWcs (arg13.arg8), arg14.type == 1 ? arg14.argW : Melder_peekUtf8ToWcs (arg14.arg8), arg15.type == 1 ? arg15.argW : Melder_peekUtf8ToWcs (arg15.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_warning (const MelderArg& arg1, const MelderArg& arg2, const MelderArg& arg3, const MelderArg& arg4, const MelderArg& arg5, const MelderArg& arg6, const MelderArg& arg7, const MelderArg& arg8, const MelderArg& arg9, const MelderArg& arg10, const MelderArg& arg11, const MelderArg& arg12, const MelderArg& arg13, const MelderArg& arg14, const MelderArg& arg15, const MelderArg& arg16, const MelderArg& arg17, const MelderArg& arg18, const MelderArg& arg19, const MelderArg& arg20) { if (theWarningDepth < 0) return; MelderString_empty (& theWarningBuffer); MelderString_append (& theWarningBuffer, arg1.type == 1 ? arg1.argW : Melder_peekUtf8ToWcs (arg1.arg8), arg2.type == 1 ? arg2.argW : Melder_peekUtf8ToWcs (arg2.arg8), arg3.type == 1 ? arg3.argW : Melder_peekUtf8ToWcs (arg3.arg8), arg4.type == 1 ? arg4.argW : Melder_peekUtf8ToWcs (arg4.arg8), arg5.type == 1 ? arg5.argW : Melder_peekUtf8ToWcs (arg5.arg8), arg6.type == 1 ? arg6.argW : Melder_peekUtf8ToWcs (arg6.arg8), arg7.type == 1 ? arg7.argW : Melder_peekUtf8ToWcs (arg7.arg8), arg8.type == 1 ? arg8.argW : Melder_peekUtf8ToWcs (arg8.arg8), arg9.type == 1 ? arg9.argW : Melder_peekUtf8ToWcs (arg9.arg8)); MelderString_append (& theWarningBuffer, arg10.type == 1 ? arg10.argW : Melder_peekUtf8ToWcs (arg10.arg8), arg11.type == 1 ? arg11.argW : Melder_peekUtf8ToWcs (arg11.arg8), arg12.type == 1 ? arg12.argW : Melder_peekUtf8ToWcs (arg12.arg8), arg13.type == 1 ? arg13.argW : Melder_peekUtf8ToWcs (arg13.arg8), arg14.type == 1 ? arg14.argW : Melder_peekUtf8ToWcs (arg14.arg8), arg15.type == 1 ? arg15.argW : Melder_peekUtf8ToWcs (arg15.arg8), arg16.type == 1 ? arg16.argW : Melder_peekUtf8ToWcs (arg16.arg8), arg17.type == 1 ? arg17.argW : Melder_peekUtf8ToWcs (arg17.arg8), arg18.type == 1 ? arg18.argW : Melder_peekUtf8ToWcs (arg18.arg8)); MelderString_append (& theWarningBuffer, arg19.type == 1 ? arg19.argW : Melder_peekUtf8ToWcs (arg19.arg8), arg20.type == 1 ? arg20.argW : Melder_peekUtf8ToWcs (arg20.arg8)); theMelder. warning (theWarningBuffer.string); } void Melder_beep (void) { #ifdef macintosh #if useCarbon SysBeep (0); #else //AudioServicesPlayAlertSound (kUserPreferredAlert); #endif #else fprintf (stderr, "\a"); #endif } /*********** FATAL **********/ int Melder_fatal (const char *format, ...) { const char *lead = strstr (format, "Praat cannot start up") ? "" : "Praat will crash. Notify the author (paul.boersma@uva.nl) with the following information:\n"; va_list arg; va_start (arg, format); strcpy (Melder_buffer1, lead); vsprintf (Melder_buffer1 + strlen (lead), format, arg); theMelder. fatal (Melder_peekUtf8ToWcs (Melder_buffer1)); va_end (arg); abort (); return 0; /* Make some compilers happy, some unhappy. */ } int _Melder_assert (const char *condition, const char *fileName, int lineNumber) { return Melder_fatal ("Assertion failed in file \"%s\" at line %d:\n %s\n", fileName, lineNumber, condition); } #ifndef CONSOLE_APPLICATION #if defined (macintosh) static void mac_message (int macAlertType, const wchar *messageW) { DialogRef dialog; static UniChar messageU [4000]; int messageLength = wcslen (messageW); int j = 0; for (int i = 0; i < messageLength && j <= 4000 - 2; i ++) { uint32_t kar = messageW [i]; if (kar <= 0xFFFF) { messageU [j ++] = kar; } else if (kar <= 0x10FFFF) { kar -= 0x10000; messageU [j ++] = 0xD800 | (kar >> 10); messageU [j ++] = 0xDC00 | (kar & 0x3FF); } } #if useCarbon CFStringRef messageCF = CFStringCreateWithCharacters (NULL, messageU, j); CreateStandardAlert (macAlertType, messageCF, NULL, NULL, & dialog); CFRelease (messageCF); RunStandardAlert (dialog, NULL, NULL); #else CFStringRef messageCF = CFStringCreateWithCharacters (NULL, messageU, j); //CreateStandardAlert (macAlertType, messageCF, NULL, NULL, & dialog); CFRelease (messageCF); //RunStandardAlert (dialog, NULL, NULL); #endif } #endif #define theMessageFund_SIZE 100000 static char * theMessageFund = NULL; static void gui_fatal (const wchar *message) { free (theMessageFund); #if gtk GuiObject dialog = gtk_message_dialog_new (GTK_WINDOW (Melder_topShell), GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, "%s", Melder_peekWcsToUtf8 (message)); gtk_dialog_run (GTK_DIALOG (dialog)); gtk_widget_destroy (GTK_WIDGET (dialog)); #elif defined (macintosh) #if useCarbon mac_message (kAlertStopAlert, message); SysError (11); #else mac_message (kAlertStopAlert, message); SysError (11); #endif #elif defined (_WIN32) MessageBox (NULL, message, L"Fatal error", MB_OK | MB_TOPMOST); #endif } static void gui_error (const wchar *message) { bool memoryIsLow = wcsstr (message, L"Out of memory"); if (memoryIsLow) { free (theMessageFund); } #if gtk GuiObject dialog = gtk_message_dialog_new (GTK_WINDOW (Melder_topShell), GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, "%s", Melder_peekWcsToUtf8 (message)); gtk_dialog_run (GTK_DIALOG (dialog)); gtk_widget_destroy (GTK_WIDGET (dialog)); #elif defined (macintosh) #if useCarbon mac_message (kAlertStopAlert, message); XmUpdateDisplay (0); #else mac_message (kAlertStopAlert, message); // TODO #endif #elif defined (_WIN32) MessageBox (NULL, message, L"Message", MB_OK | MB_TOPMOST | MB_ICONEXCLAMATION); // or (HWND) XtWindow ((GuiObject) Melder_topShell) #endif if (memoryIsLow) { theMessageFund = (char *) malloc (theMessageFund_SIZE); if (theMessageFund == NULL) { #if gtk GuiObject dialog = gtk_message_dialog_new (GTK_WINDOW (Melder_topShell), GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, "Praat is very low on memory.\nSave your work and quit Praat.\nIf you don't do that, Praat may crash."); gtk_dialog_run (GTK_DIALOG (dialog)); gtk_widget_destroy (GTK_WIDGET (dialog)); #elif defined (macintosh) #if useCarbon mac_message (kAlertStopAlert, L"Praat is very low on memory.\nSave your work and quit Praat.\nIf you don't do that, Praat may crash."); XmUpdateDisplay (0); #else mac_message (kAlertStopAlert, L"Praat is very low on memory.\nSave your work and quit Praat.\nIf you don't do that, Praat may crash."); // TODO #endif #elif defined (_WIN32) MessageBox (NULL, L"Praat is very low on memory.\nSave your work and quit Praat.\nIf you don't do that, Praat may crash.", L"Message", MB_OK); #endif } } } static void gui_warning (const wchar *message) { #if gtk GuiObject dialog = gtk_message_dialog_new (GTK_WINDOW (Melder_topShell), GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_WARNING, GTK_BUTTONS_OK, "%s", Melder_peekWcsToUtf8 (message)); gtk_dialog_run (GTK_DIALOG (dialog)); gtk_widget_destroy (GTK_WIDGET (dialog)); #elif defined (macintosh) #if useCarbon mac_message (kAlertNoteAlert, message); XmUpdateDisplay (0); #else mac_message (kAlertNoteAlert, message); // TODO #endif #elif defined (_WIN32) MessageBox (NULL, message, L"Warning", MB_OK | MB_TOPMOST); #endif } void gui_information (const wchar *); // BUG: no prototype void MelderGui_create (void *parent) { theMessageFund = (char *) malloc (theMessageFund_SIZE); assert (theMessageFund != NULL); Melder_topShell = (GuiObject) parent; Melder_setInformationProc (gui_information); Melder_setFatalProc (gui_fatal); Melder_setErrorProc (gui_error); Melder_setWarningProc (gui_warning); } #endif int Melder_publish (void *anything) { return theMelder. publish (anything); } int Melder_record (double duration) { return theMelder. record (duration); } int Melder_recordFromFile (MelderFile file) { return theMelder. recordFromFile (file); } void Melder_play (void) { theMelder. play (); } void Melder_playReverse (void) { theMelder. playReverse (); } int Melder_publishPlayed (void) { return theMelder. publishPlayed (); } /********** Procedures to override message methods (e.g., to enforce interactive behaviour). **********/ void Melder_setHelpProc (void (*help) (const wchar *query)) { theMelder. help = help ? help : defaultHelp; } void Melder_setSearchProc (void (*search) (void)) { theMelder. search = search ? search : defaultSearch; } void Melder_setWarningProc (void (*warning) (const wchar *)) { theMelder. warning = warning ? warning : defaultWarning; } void Melder_setFatalProc (void (*fatal) (const wchar *)) { theMelder. fatal = fatal ? fatal : defaultFatal; } void Melder_setPublishProc (int (*publish) (void *)) { theMelder. publish = publish ? publish : defaultPublish; } void Melder_setRecordProc (int (*record) (double)) { theMelder. record = record ? record : defaultRecord; } void Melder_setRecordFromFileProc (int (*recordFromFile) (MelderFile)) { theMelder. recordFromFile = recordFromFile ? recordFromFile : defaultRecordFromFile; } void Melder_setPlayProc (void (*play) (void)) { theMelder. play = play ? play : defaultPlay; } void Melder_setPlayReverseProc (void (*playReverse) (void)) { theMelder. playReverse = playReverse ? playReverse : defaultPlayReverse; } void Melder_setPublishPlayedProc (int (*publishPlayed) (void)) { theMelder. publishPlayed = publishPlayed ? publishPlayed : defaultPublishPlayed; } /* End of file melder.cpp */ sources_5316/sys/melder_atof.cpp0000644000176700017670000000644211546673343015550 0ustar paulpaul/* melder_atof.cpp * * Copyright (C) 2003-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2003/05/19 Melder_atof * pb 2006/04/16 moved Melder_atof from melder.c * pb 2006/04/16 moved Melder_isStringNumeric from Table.c * pb 2006/12/08 guard against null strings * pb 2011/04/05 C++ */ #include "melder.h" #include "NUM.h" static const wchar_t *findEndOfNumericString_nothrow (const wchar_t *string) { const wchar_t *p = & string [0]; /* * Leading white space is OK. */ while (*p == ' ' || *p == '\t' || *p == '\n' || *p == '\r') p ++; /* * Next we accept an optional leading plus or minus. */ if (*p == '+' || *p == '-') p ++; /* * The next character must be a decimal digit. * So we don't allow things like ".5". */ if (*p < '0' || *p > '9') return NULL; /* String is not numeric. */ p ++; /* * Then we accept any number of decimal digits. */ while (*p >= '0' && *p <= '9') p ++; /* * Next we accept an optional decimal point. */ if (*p == '.') { p ++; /* * We accept any number of (even zero) decimal digits after the decimal point. */ while (*p >= '0' && *p <= '9') p ++; } /* * Next we accept an optional exponential E or e. */ if (*p == 'e' || *p == 'E') { p ++; /* * In the exponent we accept an optional leading plus or minus. */ if (*p == '+' || *p == '-') p ++; /* * The exponent must contain a decimal digit. * So we don't allow things like "+2.1E". */ if (*p < '0' || *p > '9') return NULL; /* String is not numeric. */ p ++; /* * Then we accept any number of decimal digits. */ while (*p >= '0' && *p <= '9') p ++; } /* * Next we accept an optional percent sign. */ if (*p == '%') p ++; /* * We have found the end of the numeric string. */ return p; } int Melder_isStringNumeric_nothrow (const wchar_t *string) { if (string == NULL) return false; const wchar_t *p = findEndOfNumericString_nothrow (string); if (p == NULL) return FALSE; /* * We accept only white space after the numeric string. */ while (*p == ' ' || *p == '\t' || *p == '\n' || *p == '\r') p ++; return *p == '\0'; } double Melder_atof (const wchar_t *string) { if (string == NULL) return NUMundefined; const wchar_t *p = findEndOfNumericString_nothrow (string); if (p == NULL) return NUMundefined; Melder_assert (p - string > 0); #if defined (macintosh) /* strtod may be 100 times faster than wcstod: */ return p [-1] == '%' ? 0.01 * strtod (Melder_peekWcsToUtf8 (string), NULL) : strtod (Melder_peekWcsToUtf8 (string), NULL); #else return p [-1] == '%' ? 0.01 * wcstod (string, NULL) : wcstod (string, NULL); #endif } /* End of file melder_atof.cpp */ sources_5316/sys/Formula.cpp0000644000176700017670000051273711724501647014700 0ustar paulpaul/* Formula.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include #if defined (UNIX) #include #endif #include "NUM.h" #include "NUM2.h" #include "regularExp.h" #include "Formula.h" #include "Interpreter.h" #include "Ui.h" #include "praatP.h" #include "UnicodeData.h" #include "UiPause.h" #include "DemoEditor.h" #undef our #define our ((Data_Table) my methods) -> #undef your #define your ((Data_Table) thy methods) -> static Interpreter theInterpreter, theLocalInterpreter; static Data theSource; static const wchar_t *theExpression; static int theExpressionType, theOptimize; static struct Formula_NumericArray theZeroNumericArray = { 0, 0, NULL }; typedef struct structFormulaInstruction { int symbol; int position; union { double number; int label; wchar_t *string; //struct Formula_NumericArray numericArray; Data object; InterpreterVariable variable; } content; } *FormulaInstruction; static FormulaInstruction lexan, parse; static int ilabel, ilexan, iparse, numberOfInstructions, numberOfStringConstants; enum { GEENSYMBOOL_, /* First, all symbols after which "-" is unary. */ /* The list ends with "MINUS_" itself. */ /* Haakjes-openen. */ IF_, THEN_, ELSE_, HAAKJEOPENEN_, RECHTEHAAKOPENEN_, KOMMA_, FROM_, TO_, /* Operatoren met boolean resultaat. */ OR_, AND_, NOT_, EQ_, NE_, LE_, LT_, GE_, GT_, /* Operatoren met reeel resultaat. */ ADD_, SUB_, MUL_, RDIV_, IDIV_, MOD_, POWER_, CALL_, MINUS_, /* Then, the symbols after which "-" is binary. */ /* Haakjes-sluiten. */ ENDIF_, FI_, HAAKJESLUITEN_, RECHTEHAAKSLUITEN_, /* Dingen met een waarde. */ #define LOW_VALUE NUMBER_ NUMBER_, NUMBER_PI_, NUMBER_E_, NUMBER_UNDEFINED_, /* Attributes of objects. */ #define LOW_ATTRIBUTE XMIN_ XMIN_, XMAX_, YMIN_, YMAX_, NX_, NY_, DX_, DY_, ROW_, COL_, NROW_, NCOL_, ROWSTR_, COLSTR_, Y_, X_, #define HIGH_ATTRIBUTE X_ #define HIGH_VALUE HIGH_ATTRIBUTE SELF_, SELFSTR_, OBJECT_, OBJECTSTR_, MATRIKS_, MATRIKSSTR_, STOPWATCH_, /* The following symbols can be followed by "-" only if they are a variable. */ /* Functions of 1 variable; if you add, update the #defines. */ #define LOW_FUNCTION_1 ABS_ ABS_, ROUND_, FLOOR_, CEILING_, SQRT_, SIN_, COS_, TAN_, ARCSIN_, ARCCOS_, ARCTAN_, SINC_, SINCPI_, EXP_, SINH_, COSH_, TANH_, ARCSINH_, ARCCOSH_, ARCTANH_, SIGMOID_, INV_SIGMOID_, ERF_, ERFC_, GAUSS_P_, GAUSS_Q_, INV_GAUSS_Q_, RANDOM_POISSON_, LOG2_, LN_, LOG10_, LN_GAMMA_, HERTZ_TO_BARK_, BARK_TO_HERTZ_, PHON_TO_DIFFERENCE_LIMENS_, DIFFERENCE_LIMENS_TO_PHON_, HERTZ_TO_MEL_, MEL_TO_HERTZ_, HERTZ_TO_SEMITONES_, SEMITONES_TO_HERTZ_, ERB_, HERTZ_TO_ERB_, ERB_TO_HERTZ_, #define HIGH_FUNCTION_1 ERB_TO_HERTZ_ /* Functions of 2 variables; if you add, update the #defines. */ #define LOW_FUNCTION_2 ARCTAN2_ ARCTAN2_, RANDOM_UNIFORM_, RANDOM_INTEGER_, RANDOM_GAUSS_, CHI_SQUARE_P_, CHI_SQUARE_Q_, INCOMPLETE_GAMMAP_, INV_CHI_SQUARE_Q_, STUDENT_P_, STUDENT_Q_, INV_STUDENT_Q_, BETA_, BETA2_, BESSEL_I_, BESSEL_K_, LN_BETA_, SOUND_PRESSURE_TO_PHON_, OBJECTS_ARE_IDENTICAL_, #define HIGH_FUNCTION_2 OBJECTS_ARE_IDENTICAL_ /* Functions of 3 variables; if you add, update the #defines. */ #define LOW_FUNCTION_3 FISHER_P_ FISHER_P_, FISHER_Q_, INV_FISHER_Q_, BINOMIAL_P_, BINOMIAL_Q_, INCOMPLETE_BETA_, INV_BINOMIAL_P_, INV_BINOMIAL_Q_, #define HIGH_FUNCTION_3 INV_BINOMIAL_Q_ /* Functions of a variable number of variables; if you add, update the #defines. */ #define LOW_FUNCTION_N MIN_ MIN_, MAX_, IMIN_, IMAX_, LEFTSTR_, RIGHTSTR_, MIDSTR_, SELECTED_, SELECTEDSTR_, NUMBER_OF_SELECTED_, BEGIN_PAUSE_FORM_, PAUSE_FORM_ADD_REAL_, PAUSE_FORM_ADD_POSITIVE_, PAUSE_FORM_ADD_INTEGER_, PAUSE_FORM_ADD_NATURAL_, PAUSE_FORM_ADD_WORD_, PAUSE_FORM_ADD_SENTENCE_, PAUSE_FORM_ADD_TEXT_, PAUSE_FORM_ADD_BOOLEAN_, PAUSE_FORM_ADD_CHOICE_, PAUSE_FORM_ADD_OPTION_MENU_, PAUSE_FORM_ADD_OPTION_, PAUSE_FORM_ADD_COMMENT_, END_PAUSE_FORM_, CHOOSE_READ_FILESTR_, CHOOSE_WRITE_FILESTR_, CHOOSE_DIRECTORYSTR_, DEMO_WINDOW_TITLE_, DEMO_SHOW_, DEMO_WAIT_FOR_INPUT_, DEMO_INPUT_, DEMO_CLICKED_IN_, DEMO_CLICKED_, DEMO_X_, DEMO_Y_, DEMO_KEY_PRESSED_, DEMO_KEY_, DEMO_SHIFT_KEY_PRESSED_, DEMO_COMMAND_KEY_PRESSED_, DEMO_OPTION_KEY_PRESSED_, DEMO_EXTRA_CONTROL_KEY_PRESSED_, ZERO_NUMAR_, LINEAR_NUMAR_, RANDOM_UNIFORM_NUMAR_, RANDOM_INTEGER_NUMAR_, RANDOM_GAUSS_NUMAR_, NUMBER_OF_ROWS_, NUMBER_OF_COLUMNS_, #define HIGH_FUNCTION_N NUMBER_OF_COLUMNS_ /* String functions. */ #define LOW_STRING_FUNCTION LOW_FUNCTION_STRNUM #define LOW_FUNCTION_STRNUM LENGTH_ LENGTH_, FILE_READABLE_, DELETE_FILE_, CREATE_DIRECTORY_, VARIABLE_EXISTS_, #define HIGH_FUNCTION_STRNUM VARIABLE_EXISTS_ DATESTR_, ENVIRONMENTSTR_, INDEX_, RINDEX_, STARTS_WITH_, ENDS_WITH_, REPLACESTR_, INDEX_REGEX_, RINDEX_REGEX_, REPLACE_REGEXSTR_, EXTRACT_NUMBER_, EXTRACT_WORDSTR_, EXTRACT_LINESTR_, FIXEDSTR_, PERCENTSTR_, #define HIGH_STRING_FUNCTION PERCENTSTR_ /* Range functions. */ #define LOW_RANGE_FUNCTION SUM_ SUM_, #define HIGH_RANGE_FUNCTION SUM_ #define LOW_FUNCTION LOW_FUNCTION_1 #define HIGH_FUNCTION HIGH_RANGE_FUNCTION /* Membership operator. */ PERIOD_, #define hoogsteInvoersymbool PERIOD_ /* Symbols introduced by the parser. */ TRUE_, FALSE_, GOTO_, IFTRUE_, IFFALSE_, INCREMENT_GREATER_GOTO_, LABEL_, DECREMENT_AND_ASSIGN_, ADD_3DOWN_, POP_2_, NUMERIC_ARRAY_ELEMENT_, VARIABLE_REFERENCE_, SELF0_, SELFSTR0_, OBJECTCELL0_, OBJECTCELLSTR0_, OBJECTCELL1_, OBJECTCELLSTR1_, OBJECTCELL2_, OBJECTCELLSTR2_, OBJECTLOCATION0_, OBJECTLOCATIONSTR0_, OBJECTLOCATION1_, OBJECTLOCATIONSTR1_, OBJECTLOCATION2_, OBJECTLOCATIONSTR2_, SELFMATRIKS1_, SELFMATRIKSSTR1_, SELFMATRIKS2_, SELFMATRIKSSTR2_, SELFFUNKTIE1_, SELFFUNKTIESTR1_, SELFFUNKTIE2_, SELFFUNKTIESTR2_, MATRIKS0_, MATRIKSSTR0_, MATRIKS1_, MATRIKSSTR1_, MATRIKS2_, MATRIKSSTR2_, FUNKTIE0_, FUNKTIESTR0_, FUNKTIE1_, FUNKTIESTR1_, FUNKTIE2_, FUNKTIESTR2_, SQR_, /* Symbols introduced by lexical analysis. */ STRING_, NUMERIC_VARIABLE_, STRING_VARIABLE_, NUMERIC_ARRAY_VARIABLE_, STRING_ARRAY_VARIABLE_, VARIABLE_NAME_, INDEXED_NUMERIC_VARIABLE_, INDEXED_STRING_VARIABLE_, END_ #define hoogsteSymbool END_ }; /* The names that start with an underscore (_) do not occur in the formula text: */ /* they are used in error messages and in debugging (see Formula_print). */ static const wchar_t *Formula_instructionNames [1 + hoogsteSymbool] = { L"", L"if", L"then", L"else", L"(", L"[", L",", L"from", L"to", L"or", L"and", L"not", L"=", L"<>", L"<=", L"<", L">=", L">", L"+", L"-", L"*", L"/", L"div", L"mod", L"^", L"_call", L"_neg", L"endif", L"fi", L")", L"]", L"a number", L"pi", L"e", L"undefined", L"xmin", L"xmax", L"ymin", L"ymax", L"nx", L"ny", L"dx", L"dy", L"row", L"col", L"nrow", L"ncol", L"row$", L"col$", L"y", L"x", L"self", L"self$", L"object", L"object$", L"_matriks", L"_matriks$", L"stopwatch", L"abs", L"round", L"floor", L"ceiling", L"sqrt", L"sin", L"cos", L"tan", L"arcsin", L"arccos", L"arctan", L"sinc", L"sincpi", L"exp", L"sinh", L"cosh", L"tanh", L"arcsinh", L"arccosh", L"arctanh", L"sigmoid", L"invSigmoid", L"erf", L"erfc", L"gaussP", L"gaussQ", L"invGaussQ", L"randomPoisson", L"log2", L"ln", L"log10", L"lnGamma", L"hertzToBark", L"barkToHertz", L"phonToDifferenceLimens", L"differenceLimensToPhon", L"hertzToMel", L"melToHertz", L"hertzToSemitones", L"semitonesToHertz", L"erb", L"hertzToErb", L"erbToHertz", L"arctan2", L"randomUniform", L"randomInteger", L"randomGauss", L"chiSquareP", L"chiSquareQ", L"incompleteGammaP", L"invChiSquareQ", L"studentP", L"studentQ", L"invStudentQ", L"beta", L"beta2", L"besselI", L"besselK", L"lnBeta", L"soundPressureToPhon", L"objectsAreIdentical", L"fisherP", L"fisherQ", L"invFisherQ", L"binomialP", L"binomialQ", L"incompleteBeta", L"invBinomialP", L"invBinomialQ", L"min", L"max", L"imin", L"imax", L"left$", L"right$", L"mid$", L"selected", L"selected$", L"numberOfSelected", L"beginPause", L"real", L"positive", L"integer", L"natural", L"word", L"sentence", L"text", L"boolean", L"choice", L"optionMenu", L"option", L"comment", L"endPause", L"chooseReadFile$", L"chooseWriteFile$", L"chooseDirectory$", L"demoWindowTitle", L"demoShow", L"demoWaitForInput", L"demoInput", L"demoClickedIn", L"demoClicked", L"demoX", L"demoY", L"demoKeyPressed", L"demoKey$", L"demoShiftKeyPressed", L"demoCommandKeyPressed", L"demoOptionKeyPressed", L"demoExtraControlKeyPressed", L"zero#", L"linear#", L"randomUniform#", L"randomInteger#", L"randomGauss#", L"numberOfRows", L"numberOfColumns", L"length", L"fileReadable", L"deleteFile", L"createDirectory", L"variableExists", L"date$", L"environment$", L"index", L"rindex", L"startsWith", L"endsWith", L"replace$", L"index_regex", L"rindex_regex", L"replace_regex$", L"extractNumber", L"extractWord$", L"extractLine$", L"fixed$", L"percent$", L"sum", L".", L"_true", L"_false", L"_goto", L"_iftrue", L"_iffalse", L"_incrementGreaterGoto", L"_label", L"_decrementAndAssign", L"_add3Down", L"_pop2", L"_numericArrayElement", L"_variableReference", L"_self0", L"_self0$", L"_objectcell0", L"_objectcell0$", L"_objectcell1", L"_objectcell1$", L"_objectcell2", L"_objectcell2$", L"_objectlocation0", L"_objectlocation0$", L"_objectlocation1", L"_objectlocation1$", L"_objectlocation2", L"_objectlocation2$", L"_selfmatriks1", L"_selfmatriks1$", L"_selfmatriks2", L"_selfmatriks2$", L"_selffunktie1", L"_selffunktie1$", L"_selffunktie2", L"_selffunktie2$", L"_matriks0", L"_matriks0$", L"_matriks1", L"_matriks1$", L"_matriks2", L"_matriks2$", L"_funktie0", L"_funktie0$", L"_funktie1", L"_funktie1$", L"_funktie2", L"_funktie2$", L"_square", L"_string", L"a numeric variable", L"a string variable", L"a numeric array variable", L"a string array variable", L"a variable name", L"an indexed numeric variable", L"an indexed string variable", L"the end of the formula" }; #define nieuwlabel (-- ilabel) #define nieuwlees (lexan [++ ilexan]. symbol) #define oudlees (-- ilexan) static void formulefout (const wchar *message, int position) { static MelderString truncatedExpression = { 0 }; MelderString_ncopy (& truncatedExpression, theExpression, position + 1); Melder_throw (message, L":\n" L_LEFT_GUILLEMET L" ", truncatedExpression.string); } static const wchar *languageNameCompare_searchString; static int languageNameCompare (const void *first, const void *second) { int i = * (int *) first, j = * (int *) second; return wcscmp (i == 0 ? languageNameCompare_searchString : Formula_instructionNames [i], j == 0 ? languageNameCompare_searchString : Formula_instructionNames [j]); } static int Formula_hasLanguageName (const wchar *f) { static int *index; if (index == NULL) { index = NUMvector (1, hoogsteInvoersymbool); for (int tok = 1; tok <= hoogsteInvoersymbool; tok ++) { index [tok] = tok; } qsort (& index [1], hoogsteInvoersymbool, sizeof (int), languageNameCompare); } if (index == NULL) { /* Linear search. */ for (int tok = 1; tok <= hoogsteInvoersymbool; tok ++) { if (wcsequ (f, Formula_instructionNames [tok])) return tok; } } else { /* Binary search. */ int dummy = 0, *found; languageNameCompare_searchString = f; found = (int *) bsearch (& dummy, & index [1], hoogsteInvoersymbool, sizeof (int), languageNameCompare); if (found != NULL) return *found; } return 0; } static void Formula_lexan (void) { /* Purpose: translate the formula text into a series of symbols. Return: 0 in case of error, otherwise 1. Postcondition: if result != 0, then the last symbol is L"END_". Example: the text L"x*7" yields 5 symbols: lexan [0] is empty; lexan [1]. symbol = X_; lexan [2]. symbol = MUL_; lexan [3]. symbol = NUMBER_; lexan [3]. number = 7.00000000e+00; lexan [4]. symbol = END_; */ int kar; /* The character most recently read from theExpression. */ int ikar = -1; /* The position of that character in theExpression. */ #define nieuwkar kar = theExpression [++ ikar] #define oudkar -- ikar int itok = 0; /* Position of most recent symbol in "lexan". */ #define nieuwtok(s) { lexan [++ itok]. symbol = s; lexan [itok]. position = ikar; } #define tokgetal(g) lexan [itok]. content.number = (g) #define tokmatriks(m) lexan [itok]. content.object = (m) static MelderString token = { 0 }; /* String to collect a symbol name in. */ #define stokaan MelderString_empty (& token); #define stokkar { MelderString_appendCharacter (& token, kar); nieuwkar; } #define stokuit (void) 0 ilexan = iparse = ilabel = numberOfStringConstants = 0; do { nieuwkar; if (kar == ' ' || kar == '\t') { ; /* Ignore spaces and tabs. */ } else if (kar == '\0') { nieuwtok (END_) } else if (kar >= '0' && kar <= '9') { stokaan; do stokkar while (kar >= '0' && kar <= '9'); if (kar == '.') do stokkar while (kar >= '0' && kar <= '9'); if (kar == 'e' || kar == 'E') { kar = 'e'; stokkar if (kar == '-') stokkar else if (kar == '+') nieuwkar; if (! (kar >= '0' && kar <= '9')) formulefout (L"Missing exponent", ikar); do stokkar while (kar >= '0' && kar <= '9'); } if (kar == '%') stokkar stokuit; oudkar; nieuwtok (NUMBER_) tokgetal (Melder_atof (token.string)); } else if ((kar >= 'a' && kar <= 'z') || kar >= 192 || (kar == '.' && ((theExpression [ikar + 1] >= 'a' && theExpression [ikar + 1] <= 'z') || theExpression [ikar + 1] >= 192) && (itok == 0 || (lexan [itok]. symbol != MATRIKS_ && lexan [itok]. symbol != MATRIKSSTR_)))) { int tok; bool isString = false, isArray = false; stokaan; do stokkar while ((kar >= 'A' && kar <= 'Z') || (kar >= 'a' && kar <= 'z') || kar >= 192 || (kar >= '0' && kar <= '9') || kar == '_' || kar == '.'); if (kar == '$') { stokkar isString = true; } if (kar == '#') { stokkar isArray = true; } stokuit; oudkar; /* * 'token' now contains a word, possibly ending in a dollar or number sign; * it could be a variable name, a function name, both, or a procedure name. * Try a language or function name first. */ tok = Formula_hasLanguageName (token.string); if (tok) { /* * We have a language name or function name. It MIGHT be meant to be a variable name, though, * regarding the large and expanding number of language names. */ /* * First the constants. They are reserved words and can never be variable names. */ if (tok == NUMBER_PI_) { nieuwtok (NUMBER_) tokgetal (NUMpi); } else if (tok == NUMBER_E_) { nieuwtok (NUMBER_) tokgetal (NUMe); } else if (tok == NUMBER_UNDEFINED_) { nieuwtok (NUMBER_) tokgetal (NUMundefined); /* * One very common language name must be converted to a synonym. */ } else if (tok == FI_) { nieuwtok (ENDIF_) /* * Is it a function name? These may be ambiguous. */ } else if (tok >= LOW_FUNCTION && tok <= HIGH_FUNCTION) { /* * Look ahead to find out whether the next token is a left parenthesis. */ int jkar; jkar = ikar + 1; while (theExpression [jkar] == ' ' || theExpression [jkar] == '\t') jkar ++; if (theExpression [jkar] == '(') { nieuwtok (tok) /* This must be a function name. */ } else { /* * This could be a variable with the same name as a function. */ InterpreterVariable var = Interpreter_hasVariable (theInterpreter, token.string); if (var == NULL) { nieuwtok (VARIABLE_NAME_) lexan [itok]. content.string = Melder_wcsdup_f (token.string); numberOfStringConstants ++; } else { if (isArray) { if (isString) { nieuwtok (STRING_ARRAY_VARIABLE_) } else { nieuwtok (NUMERIC_ARRAY_VARIABLE_) } } else { if (isString) { nieuwtok (STRING_VARIABLE_) } else { nieuwtok (NUMERIC_VARIABLE_) } } lexan [itok]. content.variable = var; } } /* * Not a function name. * Must be a language name (if, then, else, endif, or, and, not, div, mod, x, ncol, stopwatch). * Some can be used as variable names (x, ncol...). */ } else if (tok >= LOW_ATTRIBUTE && tok <= HIGH_ATTRIBUTE) { /* * Look back to find out whether this is an attribute. */ if (itok > 0 && lexan [itok]. symbol == PERIOD_) { /* * This must be an attribute that follows a period. */ nieuwtok (tok) } else if (theSource) { /* * Look for ambiguity. */ if (Interpreter_hasVariable (theInterpreter, token.string)) Melder_throw ( L_LEFT_GUILLEMET, token.string, L_RIGHT_GUILLEMET " is ambiguous: a variable or an attribute of the current object. " "Please change variable name."); if (tok == ROW_ || tok == COL_ || tok == X_ || tok == Y_) { nieuwtok (tok) } else { nieuwtok (MATRIKS_) tokmatriks (theSource); nieuwtok (PERIOD_) nieuwtok (tok) } } else { /* * This must be a variable, since there is no "current object" here. */ InterpreterVariable var = Interpreter_hasVariable (theInterpreter, token.string); if (var == NULL) { nieuwtok (VARIABLE_NAME_) lexan [itok]. content.string = Melder_wcsdup_f (token.string); numberOfStringConstants ++; } else { if (isArray) { if (isString) { nieuwtok (STRING_ARRAY_VARIABLE_) } else { nieuwtok (NUMERIC_ARRAY_VARIABLE_) } } else { if (isString) { nieuwtok (STRING_VARIABLE_) } else { nieuwtok (NUMERIC_VARIABLE_) } } lexan [itok]. content.variable = var; } } } else { nieuwtok (tok) /* This must be a language name. */ } } else { /* * token.string is not a language name */ int jkar = ikar + 1; while (theExpression [jkar] == ' ' || theExpression [jkar] == '\t') jkar ++; if (theExpression [jkar] == '(') { Melder_throw ( "Unknown function " L_LEFT_GUILLEMET, token.string, L_RIGHT_GUILLEMET " in formula."); } else if (theExpression [jkar] == '[' && ! isArray) { if (isString) { nieuwtok (INDEXED_STRING_VARIABLE_) } else { nieuwtok (INDEXED_NUMERIC_VARIABLE_) } lexan [itok]. content.string = Melder_wcsdup_f (token.string); numberOfStringConstants ++; } else { InterpreterVariable var = Interpreter_hasVariable (theInterpreter, token.string); if (var == NULL) { nieuwtok (VARIABLE_NAME_) lexan [itok]. content.string = Melder_wcsdup_f (token.string); numberOfStringConstants ++; } else { if (isArray) { if (isString) { nieuwtok (STRING_ARRAY_VARIABLE_) } else { nieuwtok (NUMERIC_ARRAY_VARIABLE_) } } else { if (isString) { nieuwtok (STRING_VARIABLE_) } else { nieuwtok (NUMERIC_VARIABLE_) } } lexan [itok]. content.variable = var; } } } } else if (kar >= 'A' && kar <= 'Z') { int endsInDollarSign = FALSE; wchar_t *underscore; stokaan; do stokkar while (isalnum (kar) || kar == '_'); if (kar == '$') { stokkar endsInDollarSign = TRUE; } stokuit; oudkar; /* * 'token' now contains a word that could be an object name. */ underscore = wcschr (token.string, '_'); if (wcsequ (token.string, L"Self")) { if (theSource == NULL) formulefout (L"Cannot use \"Self\" if there is no current object.", ikar); nieuwtok (MATRIKS_) tokmatriks (theSource); } else if (wcsequ (token.string, L"Self$")) { if (theSource == NULL) formulefout (L"Cannot use \"Self$\" if there is no current object.", ikar); nieuwtok (MATRIKSSTR_) tokmatriks (theSource); } else if (underscore == NULL) { Melder_throw ( "Unknown symbol " L_LEFT_GUILLEMET , token.string, L_RIGHT_GUILLEMET " in formula " "(variables start with lower case; object names contain an underscore)."); } else if (wcsnequ (token.string, L"Object_", 7)) { long uniqueID = wcstol (token.string + 7, NULL, 10); int i = theCurrentPraatObjects -> n; while (i > 0 && uniqueID != theCurrentPraatObjects -> list [i]. id) i --; if (i == 0) formulefout (L"No such object (note: variables start with lower case)", ikar); nieuwtok (endsInDollarSign ? MATRIKSSTR_ : MATRIKS_) tokmatriks ((Data) theCurrentPraatObjects -> list [i]. object); } else { int i = theCurrentPraatObjects -> n; *underscore = ' '; if (endsInDollarSign) token.string [-- token.length] = '\0'; while (i > 0 && ! wcsequ (token.string, theCurrentPraatObjects -> list [i]. name)) i --; if (i == 0) formulefout (L"No such object (note: variables start with lower case)", ikar); nieuwtok (endsInDollarSign ? MATRIKSSTR_ : MATRIKS_) tokmatriks ((Data) theCurrentPraatObjects -> list [i]. object); } } else if (kar == '(') { nieuwtok (HAAKJEOPENEN_) } else if (kar == ')') { nieuwtok (HAAKJESLUITEN_) } else if (kar == '+') { nieuwtok (ADD_) } else if (kar == '-') { if (itok == 0 || lexan [itok]. symbol <= MINUS_) { nieuwtok (MINUS_) } else { nieuwtok (SUB_) } } else if (kar == '*') { nieuwkar; if (kar == '*') { nieuwtok (POWER_) /* "**" = "^" */ } else { oudkar; nieuwtok (MUL_) } } else if (kar == '/') { nieuwkar; if (kar == '=') { nieuwtok (NE_) /* "/=" = "<>" */ } else { oudkar; nieuwtok (RDIV_) } } else if (kar == '=') { nieuwtok (EQ_) /* "=" */ nieuwkar; if (kar != '=') { oudkar; /* "==" = "=" */ } } else if (kar == '>') { nieuwkar; if (kar == '=') { nieuwtok (GE_) } else { oudkar; nieuwtok (GT_) } } else if (kar == '<') { nieuwkar; if (kar == '=') { nieuwtok (LE_) } else if (kar == '>') { nieuwtok (NE_) } else { oudkar; nieuwtok (LT_) } } else if (kar == '!') { nieuwkar; if (kar == '=') { nieuwtok (NE_) /* "!=" = "<>" */ } else { oudkar; nieuwtok (NOT_) } } else if (kar == ',') { nieuwtok (KOMMA_) } else if (kar == ';') { nieuwtok (END_) } else if (kar == '^') { nieuwtok (POWER_) } else if (kar == '@') { do { nieuwkar; } while (kar == ' ' || kar == '\t'); stokaan; do stokkar while ((kar >= 'A' && kar <= 'Z') || (kar >= 'a' && kar <= 'z') || kar >= 192 || (kar >= '0' && kar <= '9') || kar == '_' || kar == '.'); stokuit; oudkar; nieuwtok (CALL_) lexan [itok]. content.string = Melder_wcsdup_f (token.string); numberOfStringConstants ++; } else if (kar == '\"') { /* * String constant. */ nieuwkar; stokaan; for (;;) { if (kar == '\0') formulefout (L"No closing quote in string constant", ikar); if (kar == '\"') { nieuwkar; if (kar == '\"') stokkar else break; } else { stokkar } } stokuit; oudkar; nieuwtok (STRING_) lexan [itok]. content.string = Melder_wcsdup_f (token.string); numberOfStringConstants ++; } else if (kar == '|') { nieuwtok (OR_) /* "|" = "or" */ nieuwkar; if (kar != '|') { oudkar; /* "||" = "or" */ } } else if (kar == '&') { nieuwtok (AND_) /* "&" = "and" */ nieuwkar; if (kar != '&') { oudkar; /* "&&" = "and" */ } } else if (kar == '[') { nieuwtok (RECHTEHAAKOPENEN_) } else if (kar == ']') { nieuwtok (RECHTEHAAKSLUITEN_) } else if (kar == '.') { nieuwtok (PERIOD_) } else { formulefout (L"Unknown symbol", ikar); } } while (lexan [itok]. symbol != END_); } static void pas (int symbol) { if (symbol == nieuwlees) { return; // success } else { static MelderString melding = { 0 }; MelderString_empty (& melding); const wchar *symbolName1 = Formula_instructionNames [symbol]; const wchar *symbolName2 = Formula_instructionNames [lexan [ilexan]. symbol]; bool needQuotes1 = wcschr (symbolName1, ' ') == NULL; bool needQuotes2 = wcschr (symbolName2, ' ') == NULL; MelderString_append (& melding, L"Expected ", needQuotes1 ? L"\"" : NULL, symbolName1, needQuotes1 ? L"\"" : NULL, L", but found ", needQuotes2 ? L"\"" : NULL, symbolName2, needQuotes2 ? L"\"" : NULL); formulefout (melding.string, lexan [ilexan]. position); } } #define nieuwontleed(s) parse [++ iparse]. symbol = (s) #define parsenumber(g) parse [iparse]. content.number = (g) #define ontleedlabel(l) parse [iparse]. content.label = (l) static void parseExpression (void); static void parsePowerFactor (void) { int symbol = nieuwlees; if (symbol >= LOW_VALUE && symbol <= HIGH_VALUE) { nieuwontleed (symbol); if (symbol == NUMBER_) parsenumber (lexan [ilexan]. content.number); return; } if (symbol == STRING_) { nieuwontleed (symbol); parse [iparse]. content.string = lexan [ilexan]. content.string; // reference copy! return; } if (symbol == NUMERIC_VARIABLE_ || symbol == STRING_VARIABLE_) { nieuwontleed (symbol); parse [iparse]. content.variable = lexan [ilexan]. content.variable; return; } if (symbol == INDEXED_NUMERIC_VARIABLE_ || symbol == INDEXED_STRING_VARIABLE_) { wchar_t *var = lexan [ilexan]. content.string; // Save before incrementing ilexan. if (nieuwlees == RECHTEHAAKOPENEN_) { int n = 0; if (nieuwlees != RECHTEHAAKSLUITEN_) { oudlees; parseExpression (); n ++; while (nieuwlees == KOMMA_) { parseExpression (); n ++; } oudlees; pas (RECHTEHAAKSLUITEN_); } nieuwontleed (NUMBER_); parsenumber (n); nieuwontleed (symbol); } else { Melder_fatal ("Formula:parsePowerFactor (indexed variable): No '['; cannot happen."); } parse [iparse]. content.string = var; return; } if (symbol == NUMERIC_ARRAY_VARIABLE_) { InterpreterVariable var = lexan [ilexan]. content.variable; // Save before incrementing ilexan. if (nieuwlees == RECHTEHAAKOPENEN_) { int n = 0; if (nieuwlees != RECHTEHAAKSLUITEN_) { oudlees; parseExpression (); n ++; while (nieuwlees == KOMMA_) { parseExpression (); n ++; } oudlees; pas (RECHTEHAAKSLUITEN_); } nieuwontleed (NUMBER_); parsenumber (n); nieuwontleed (NUMERIC_ARRAY_ELEMENT_); } else { oudlees; nieuwontleed (NUMERIC_ARRAY_VARIABLE_); } parse [iparse]. content.variable = var; return; } if (symbol == VARIABLE_NAME_) { InterpreterVariable var = Interpreter_hasVariable (theInterpreter, lexan [ilexan]. content.string); if (var == NULL) formulefout (L"Unknown variable", lexan [ilexan]. position); nieuwontleed (NUMERIC_VARIABLE_); parse [iparse]. content.variable = var; return; } if (symbol == SELF_) { symbol = nieuwlees; if (symbol == RECHTEHAAKOPENEN_) { parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (SELFMATRIKS2_); pas (RECHTEHAAKSLUITEN_); return; } oudlees; nieuwontleed (SELFMATRIKS1_); pas (RECHTEHAAKSLUITEN_); return; } if (symbol == HAAKJEOPENEN_) { parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (SELFFUNKTIE2_); pas (HAAKJESLUITEN_); return; } oudlees; nieuwontleed (SELFFUNKTIE1_); pas (HAAKJESLUITEN_); return; } oudlees; nieuwontleed (SELF0_); return; } if (symbol == SELFSTR_) { symbol = nieuwlees; if (symbol == RECHTEHAAKOPENEN_) { parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (SELFMATRIKSSTR2_); pas (RECHTEHAAKSLUITEN_); return; } oudlees; nieuwontleed (SELFMATRIKSSTR1_); pas (RECHTEHAAKSLUITEN_); return; } if (symbol == HAAKJEOPENEN_) { parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (SELFFUNKTIESTR2_); pas (HAAKJESLUITEN_); return; } oudlees; nieuwontleed (SELFFUNKTIESTR1_); pas (HAAKJESLUITEN_); return; } oudlees; nieuwontleed (SELFSTR0_); return; } if (symbol == OBJECT_) { symbol = nieuwlees; if (symbol == RECHTEHAAKOPENEN_) { parseExpression (); // the object's name or ID if (nieuwlees == RECHTEHAAKSLUITEN_) { nieuwontleed (OBJECTCELL0_); } else { oudlees; pas (KOMMA_); parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (OBJECTCELL2_); pas (RECHTEHAAKSLUITEN_); } else { oudlees; nieuwontleed (OBJECTCELL1_); pas (RECHTEHAAKSLUITEN_); } } } else if (symbol == HAAKJEOPENEN_) { // the object's name or ID parseExpression (); if (nieuwlees == HAAKJESLUITEN_) { nieuwontleed (OBJECTLOCATION0_); } else { oudlees; pas (KOMMA_); parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (OBJECTLOCATION2_); pas (HAAKJESLUITEN_); } else { oudlees; nieuwontleed (OBJECTLOCATION1_); pas (HAAKJESLUITEN_); } } } else { formulefout (L"After \"object\" there should be \"(\" or \"[\"", lexan [ilexan]. position); } return; } if (symbol == OBJECTSTR_) { symbol = nieuwlees; if (symbol == RECHTEHAAKOPENEN_) { parseExpression (); // the object's name or ID if (nieuwlees == RECHTEHAAKSLUITEN_) { nieuwontleed (OBJECTCELLSTR0_); } else { oudlees; pas (KOMMA_); parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (OBJECTCELLSTR2_); pas (RECHTEHAAKSLUITEN_); } else { oudlees; nieuwontleed (OBJECTCELLSTR1_); pas (RECHTEHAAKSLUITEN_); } } } else if (symbol == HAAKJEOPENEN_) { // the object's name or ID parseExpression (); if (nieuwlees == HAAKJESLUITEN_) { nieuwontleed (OBJECTLOCATIONSTR0_); } else { oudlees; pas (KOMMA_); parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (OBJECTLOCATIONSTR2_); pas (HAAKJESLUITEN_); } else { oudlees; nieuwontleed (OBJECTLOCATIONSTR1_); pas (HAAKJESLUITEN_); } } } else { formulefout (L"After \"object$\" there should be \"(\" or \"[\"", lexan [ilexan]. position); } return; } if (symbol == HAAKJEOPENEN_) { parseExpression (); pas (HAAKJESLUITEN_); return; } if (symbol == IF_) { int elseLabel = nieuwlabel; // has to be local, int endifLabel = nieuwlabel; // because of recursion parseExpression (); nieuwontleed (IFFALSE_); ontleedlabel (elseLabel); pas (THEN_); parseExpression (); nieuwontleed (GOTO_); ontleedlabel (endifLabel); pas (ELSE_); nieuwontleed (LABEL_); ontleedlabel (elseLabel); parseExpression (); pas (ENDIF_); nieuwontleed (LABEL_); ontleedlabel (endifLabel); return; } if (symbol == MATRIKS_) { Data thee = lexan [ilexan]. content.object; Melder_assert (thee != NULL); symbol = nieuwlees; if (symbol == RECHTEHAAKOPENEN_) { if (nieuwlees == RECHTEHAAKSLUITEN_) { nieuwontleed (MATRIKS0_); parse [iparse]. content.object = thee; } else { oudlees; parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (MATRIKS2_); parse [iparse]. content.object = thee; pas (RECHTEHAAKSLUITEN_); } else { oudlees; nieuwontleed (MATRIKS1_); parse [iparse]. content.object = thee; pas (RECHTEHAAKSLUITEN_); } } } else if (symbol == HAAKJEOPENEN_) { if (nieuwlees == HAAKJESLUITEN_) { nieuwontleed (FUNKTIE0_); parse [iparse]. content.object = thee; } else { oudlees; parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (FUNKTIE2_); parse [iparse]. content.object = thee; pas (HAAKJESLUITEN_); } else { oudlees; nieuwontleed (FUNKTIE1_); parse [iparse]. content.object = thee; pas (HAAKJESLUITEN_); } } } else if (symbol == PERIOD_) { switch (nieuwlees) { case XMIN_: if (! thy v_hasGetXmin ()) { formulefout (L"Attribute \"xmin\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getXmin ()); return; } case XMAX_: if (! thy v_hasGetXmax ()) { formulefout (L"Attribute \"xmax\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getXmax ()); return; } case YMIN_: if (! thy v_hasGetYmin ()) { formulefout (L"Attribute \"ymin\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getYmin ()); return; } case YMAX_: if (! thy v_hasGetYmax ()) { formulefout (L"Attribute \"ymax\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getYmax ()); return; } case NX_: if (! thy v_hasGetNx ()) { formulefout (L"Attribute \"nx\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getNx ()); return; } case NY_: if (! thy v_hasGetNy ()) { formulefout (L"Attribute \"ny\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getNy ()); return; } case DX_: if (! thy v_hasGetDx ()) { formulefout (L"Attribute \"dx\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getDx ()); return; } case DY_: if (! thy v_hasGetDy ()) { formulefout (L"Attribute \"dy\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getDy ()); return; } case NCOL_: if (! thy v_hasGetNcol ()) { formulefout (L"Attribute \"ncol\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getNcol ()); return; } case NROW_: if (! thy v_hasGetNrow ()) { formulefout (L"Attribute \"nrow\" not defined for this object", lexan [ilexan]. position); } else { nieuwontleed (NUMBER_); parsenumber (thy v_getNrow ()); return; } case ROWSTR_: if (! thy v_hasGetRowStr ()) { formulefout (L"Attribute \"row$\" not defined for this object", lexan [ilexan]. position); } else { pas (RECHTEHAAKOPENEN_); parseExpression (); nieuwontleed (ROWSTR_); parse [iparse]. content.object = thee; pas (RECHTEHAAKSLUITEN_); return; } case COLSTR_: if (! thy v_hasGetColStr ()) { formulefout (L"Attribute \"col$\" not defined for this object", lexan [ilexan]. position); } else { pas (RECHTEHAAKOPENEN_); parseExpression (); nieuwontleed (COLSTR_); parse [iparse]. content.object = thee; pas (RECHTEHAAKSLUITEN_); return; } default: formulefout (L"Unknown attribute.", lexan [ilexan]. position); } } else { formulefout (L"After a name of a matrix there should be \"(\", \"[\", or \".\"", lexan [ilexan]. position); } return; } if (symbol == MATRIKSSTR_) { Data thee = lexan [ilexan]. content.object; Melder_assert (thee != NULL); symbol = nieuwlees; if (symbol == RECHTEHAAKOPENEN_) { if (nieuwlees == RECHTEHAAKSLUITEN_) { nieuwontleed (MATRIKSSTR0_); parse [iparse]. content.object = thee; } else { oudlees; parseExpression (); if (nieuwlees == KOMMA_) { parseExpression (); nieuwontleed (MATRIKSSTR2_); parse [iparse]. content.object = thee; pas (RECHTEHAAKSLUITEN_); } else { oudlees; nieuwontleed (MATRIKSSTR1_); parse [iparse]. content.object = thee; pas (RECHTEHAAKSLUITEN_); } } } else { formulefout (L"After a name of a matrix$ there should be \"[\"", lexan [ilexan]. position); } return; } if (symbol >= LOW_FUNCTION_1 && symbol <= HIGH_FUNCTION_1) { pas (HAAKJEOPENEN_); parseExpression (); pas (HAAKJESLUITEN_); nieuwontleed (symbol); return; } if (symbol >= LOW_FUNCTION_2 && symbol <= HIGH_FUNCTION_2) { pas (HAAKJEOPENEN_); parseExpression (); pas (KOMMA_); parseExpression (); pas (HAAKJESLUITEN_); nieuwontleed (symbol); return; } if (symbol >= LOW_FUNCTION_3 && symbol <= HIGH_FUNCTION_3) { pas (HAAKJEOPENEN_); parseExpression (); pas (KOMMA_); parseExpression (); pas (KOMMA_); parseExpression (); pas (HAAKJESLUITEN_); nieuwontleed (symbol); return; } if (symbol >= LOW_FUNCTION_N && symbol <= HIGH_FUNCTION_N) { int n = 0; pas (HAAKJEOPENEN_); if (nieuwlees != HAAKJESLUITEN_) { oudlees; parseExpression (); n ++; while (nieuwlees == KOMMA_) { parseExpression (); n ++; } oudlees; pas (HAAKJESLUITEN_); } nieuwontleed (NUMBER_); parsenumber (n); nieuwontleed (symbol); return; } if (symbol == CALL_) { wchar *procedureName = lexan [ilexan]. content.string; // reference copy! int n = 0; pas (HAAKJEOPENEN_); if (nieuwlees != HAAKJESLUITEN_) { oudlees; parseExpression (); n ++; while (nieuwlees == KOMMA_) { parseExpression (); n ++; } oudlees; pas (HAAKJESLUITEN_); } nieuwontleed (NUMBER_); parsenumber (n); nieuwontleed (CALL_); parse [iparse]. content.string = procedureName; return; } if (symbol >= LOW_STRING_FUNCTION && symbol <= HIGH_STRING_FUNCTION) { if (symbol >= LOW_FUNCTION_STRNUM && symbol <= HIGH_FUNCTION_STRNUM) { pas (HAAKJEOPENEN_); parseExpression (); pas (HAAKJESLUITEN_); } else if (symbol == INDEX_ || symbol == RINDEX_ || symbol == STARTS_WITH_ || symbol == ENDS_WITH_ || symbol == INDEX_REGEX_ || symbol == RINDEX_REGEX_ || symbol == EXTRACT_NUMBER_) { pas (HAAKJEOPENEN_); parseExpression (); pas (KOMMA_); parseExpression (); pas (HAAKJESLUITEN_); } else if (symbol == DATESTR_) { pas (HAAKJEOPENEN_); pas (HAAKJESLUITEN_); } else if (symbol == EXTRACT_WORDSTR_ || symbol == EXTRACT_LINESTR_) { pas (HAAKJEOPENEN_); parseExpression (); pas (KOMMA_); parseExpression (); pas (HAAKJESLUITEN_); } else if (symbol == ENVIRONMENTSTR_) { pas (HAAKJEOPENEN_); parseExpression (); pas (HAAKJESLUITEN_); } else if (symbol == FIXEDSTR_ || symbol == PERCENTSTR_) { pas (HAAKJEOPENEN_); parseExpression (); pas (KOMMA_); parseExpression (); pas (HAAKJESLUITEN_); } else if (symbol == REPLACESTR_ || symbol == REPLACE_REGEXSTR_) { pas (HAAKJEOPENEN_); parseExpression (); pas (KOMMA_); parseExpression (); pas (KOMMA_); parseExpression (); pas (KOMMA_); parseExpression (); pas (HAAKJESLUITEN_); } else { oudlees; // needed for retry if we are going to be in a string comparison? formulefout (L"Function expected", lexan [ilexan + 1]. position); } nieuwontleed (symbol); return; } if (symbol >= LOW_RANGE_FUNCTION && symbol <= HIGH_RANGE_FUNCTION) { if (symbol == SUM_) { //theOptimize = 1; nieuwontleed (NUMBER_); parsenumber (0.0); // initialize the sum pas (HAAKJEOPENEN_); int symbol2 = nieuwlees; if (symbol2 == NUMERIC_VARIABLE_) { // an existing variable nieuwontleed (VARIABLE_REFERENCE_); InterpreterVariable loopVariable = lexan [ilexan]. content.variable; parse [iparse]. content.variable = loopVariable; } else if (symbol2 == VARIABLE_NAME_) { // a new variable InterpreterVariable loopVariable = Interpreter_lookUpVariable (theInterpreter, lexan [ilexan]. content.string); nieuwontleed (VARIABLE_REFERENCE_); parse [iparse]. content.variable = loopVariable; } else { formulefout (L"Numeric variable expected", lexan [ilexan]. position); } // now on stack: sum, loop variable if (nieuwlees == FROM_) { parseExpression (); } else { oudlees; nieuwontleed (NUMBER_); parsenumber (1.0); } nieuwontleed (DECREMENT_AND_ASSIGN_); // this pushes the variable back on the stack // now on stack: sum, loop variable pas (TO_); parseExpression (); // now on stack: sum, loop variable, end value int startLabel = nieuwlabel; int endLabel = nieuwlabel; nieuwontleed (LABEL_); ontleedlabel (startLabel); nieuwontleed (INCREMENT_GREATER_GOTO_); ontleedlabel (endLabel); pas (KOMMA_); parseExpression (); pas (HAAKJESLUITEN_); // now on stack: sum, loop variable, end value, value to add nieuwontleed (ADD_3DOWN_); // now on stack: sum, loop variable, end value nieuwontleed (GOTO_); ontleedlabel (startLabel); nieuwontleed (LABEL_); ontleedlabel (endLabel); nieuwontleed (POP_2_); // now on stack: sum return; } } if (symbol == STOPWATCH_) { nieuwontleed (symbol); return; } oudlees; // needed for retry if we are going to be in a string comparison formulefout (L"Symbol misplaced", lexan [ilexan + 1]. position); } static void parseFactor (void); static void parsePowerFactors (void) { if (nieuwlees == POWER_) { if (ilexan > 2 && lexan [ilexan - 2]. symbol == MINUS_ && lexan [ilexan - 1]. symbol == NUMBER_) { oudlees; formulefout (L"Expressions like -3^4 are ambiguous; use (-3)^4 or -(3^4) or -(3)^4", lexan [ilexan + 1]. position); } parseFactor (); // like a^-b nieuwontleed (POWER_); } else oudlees; } static void parseMinus (void) { parsePowerFactor (); parsePowerFactors (); } static void parseFactor (void) { if (nieuwlees == MINUS_) { parseFactor (); // there can be multiple consecutive minuses nieuwontleed (MINUS_); return; } oudlees; parseMinus (); // like -a^b } static void parseFactors (void) { int sym = nieuwlees; // has to be local, because of recursion if (sym == MUL_ || sym == RDIV_ || sym == IDIV_ || sym == MOD_) { parseFactor (); nieuwontleed (sym); parseFactors (); } else oudlees; } static void parseTerm (void) { parseFactor (); parseFactors (); } static void parseTerms (void) { int symbol = nieuwlees; if (symbol == ADD_ || symbol == SUB_) { parseTerm (); nieuwontleed (symbol); parseTerms (); } else oudlees; } static void parseNot (void) { int symbol; parseTerm (); parseTerms (); symbol = nieuwlees; if (symbol >= EQ_ && symbol <= GT_) { parseTerm (); parseTerms (); nieuwontleed (symbol); } else oudlees; } static void parseAnd (void) { if (nieuwlees == NOT_) { parseAnd (); // like not not not nieuwontleed (NOT_); return; } oudlees; parseNot (); } static void parseOr (void) { parseAnd (); if (nieuwlees == AND_) { int falseLabel = nieuwlabel; int andLabel = nieuwlabel; do { nieuwontleed (IFFALSE_); ontleedlabel (falseLabel); parseAnd (); } while (nieuwlees == AND_); nieuwontleed (IFFALSE_); ontleedlabel (falseLabel); nieuwontleed (TRUE_); nieuwontleed (GOTO_); ontleedlabel (andLabel); nieuwontleed (LABEL_); ontleedlabel (falseLabel); nieuwontleed (FALSE_); nieuwontleed (LABEL_); ontleedlabel (andLabel); } oudlees; } static void parseExpression (void) { parseOr (); if (nieuwlees == OR_) { int trueLabel = nieuwlabel; int orLabel = nieuwlabel; do { nieuwontleed (IFTRUE_); ontleedlabel (trueLabel); parseOr (); } while (nieuwlees == OR_); nieuwontleed (IFTRUE_); ontleedlabel (trueLabel); nieuwontleed (FALSE_); nieuwontleed (GOTO_); ontleedlabel (orLabel); nieuwontleed (LABEL_); ontleedlabel (trueLabel); nieuwontleed (TRUE_); nieuwontleed (LABEL_); ontleedlabel (orLabel); } oudlees; } /* Translate the infix expression "my lexan" into the postfix expression "my parse": remove parentheses and brackets, commas, FROM_, TO_, IF_ THEN_ ELSE_ ENDIF_ OR_ AND_; introduce LABEL_ GOTO_ IFTRUE_ IFFALSE_ TRUE_ FALSE_ SELF0_ SELF1_ SELF2_ MATRIKS0_ MATRIKS1_ MATRIKS2_ Return: 0 if error, otherwise 1. Precondition: "my lexan" contains an END_ symbol. Postconditions: *my lexan not changed. result == 0 || my parse [my numberOfInstructions]. symbol == END_ */ static void Formula_parseExpression (void) { ilabel = ilexan = iparse = 0; if (lexan [1]. symbol == END_) Melder_throw ("Empty formula."); parseExpression (); pas (END_); nieuwontleed (END_); numberOfInstructions = iparse; } static void schuif (int begin, int afstand) { int j; numberOfInstructions -= afstand; for (j = begin; j <= numberOfInstructions; j ++) parse [j] = parse [j + afstand]; } static int vindLabel (int label) { int result = numberOfInstructions; while (parse [result]. symbol != LABEL_ || parse [result]. content.label != label) result --; return result; } static void Formula_optimizeFlow (void) /* Vereenvoudig boolse uitdrukkingen. */ /* Nadien: */ /* de stroom volgt het kortste pad; */ /* als de rekenkundige waarden van boolse uitdrukkingen */ /* in de formule niet voorkomen, zijn alle TRUE_s en FALSE_s weg; */ /* als in de formule geen NOT_s voorkwamen op rekenkundige */ /* uitdrukkingen, zijn alle NOT_s weg; */ /* onbereikbare kode is weg; */ { int i, j, volg; for (;;) { int verbeterd = 0; for (i = 1; i <= numberOfInstructions; i ++) { /* Optimalisatie 1: */ /* true goto x -> goto y / __ ... label x iftrue y */ /* false goto x -> goto y / __ ... label x iffalse y */ if ((parse [i]. symbol == TRUE_ && parse [i + 1]. symbol == GOTO_ && parse [volg = vindLabel (parse [i + 1]. content.label) + 1] . symbol == IFTRUE_) || (parse [i]. symbol == FALSE_ && parse [i + 1]. symbol == GOTO_ && parse [volg = vindLabel (parse [i + 1]. content.label) + 1] . symbol == IFFALSE_)) { verbeterd = 1; parse [i]. symbol = GOTO_; parse [i]. content.label = parse [volg]. content.label; schuif (i + 1, 1); } /* Optimalisatie 2: */ /* true goto x ... label x iffalse y -> */ /* goto z ... label x iffalse y label z */ /* en analoog met false en iftrue. */ if ((parse [i]. symbol == TRUE_ && parse [i + 1]. symbol == GOTO_ && parse [volg = vindLabel (parse [i + 1]. content.label) + 1] . symbol == IFFALSE_) || (parse [i]. symbol == FALSE_ && parse [i + 1]. symbol == GOTO_ && parse [volg = vindLabel (parse [i + 1]. content.label) + 1] . symbol == IFTRUE_)) { verbeterd = 1; parse [i]. symbol = GOTO_; parse [i]. content.label = nieuwlabel; for (j = i + 1; j < volg; j ++) parse [j] = parse [j + 1]; parse [volg]. symbol = LABEL_; parse [volg]. content.label = ilabel; } /* Optimalisatie 3a: */ /* iftrue x goto y label x -> iffalse y label x */ if (parse [i]. symbol == IFTRUE_ && parse [i + 1]. symbol == GOTO_ && parse [i + 2]. symbol == LABEL_ && parse [i]. content.label == parse [i + 2]. content.label) { verbeterd = 1; parse [i]. symbol = IFFALSE_; parse [i]. content.label = parse [i + 1]. content.label; schuif (i + 1, 1); } /* Optimalisatie 3b: */ /* iffalse x goto y label x -> iftrue y label x */ if (parse [i]. symbol == IFFALSE_ && parse [i + 1]. symbol == GOTO_ && parse [i + 2]. symbol == LABEL_ && parse [i]. content.label == parse [i + 2]. content.label) { verbeterd = 1; parse [i]. symbol = IFTRUE_; parse [i]. content.label = parse [i + 1]. content.label; schuif (i + 1, 1); } /* Optimalisatie 4: */ /* verwijder onbereikbare kode: na een GOTO_ hoort een LABEL_. */ if (parse [i]. symbol == GOTO_ && parse [i + 1]. symbol != LABEL_) { verbeterd = 1; j = i + 2; while (parse [j]. symbol != LABEL_) j ++; schuif (i + 1, j - i - 1); } /* Optimalisatie 5: */ /* goto x -> 0 / __ label x */ if (parse [i]. symbol == GOTO_ && parse [i]. symbol == LABEL_ && parse [i]. content.label == parse [i + 1]. content.label) { verbeterd = 1; schuif (i, 1); } /* Optimalisatie 6: */ /* true iffalse x -> 0 */ /* false iftrue x -> 0 */ if ((parse [i]. symbol == TRUE_ && parse [i + 1]. symbol == IFFALSE_) || (parse [i]. symbol == FALSE_ && parse [i + 1]. symbol == IFTRUE_)) { verbeterd = 1; schuif (i, 2); } /* Optimalisatie 7: */ /* true iftrue x -> goto x */ /* false iffalse x -> goto x */ if ((parse [i]. symbol == TRUE_ && parse [i + 1]. symbol == IFTRUE_) || (parse [i]. symbol == FALSE_ && parse [i + 1]. symbol == IFFALSE_)) { verbeterd = 1; parse [i]. symbol = GOTO_; parse [i]. content.label = parse [i + 1]. content.label; schuif (i + 1, 1); } /* Optimalisatie 8: */ /* iftrue x -> iftrue y / __ ... label x goto y */ /* iffalse x -> iffalse y / __ ... label x goto y */ if ((parse [i]. symbol == IFTRUE_ || parse [i]. symbol == IFFALSE_) && parse [volg = vindLabel (parse [i]. content.label) + 1]. symbol == GOTO_) { verbeterd = 1; parse [i]. content.label = parse [volg]. content.label; } /* Optimalisatie 9a: */ /* not iftrue x -> iffalse x */ if (parse [i]. symbol == NOT_ && parse [i + 1]. symbol == IFTRUE_) { verbeterd = 1; parse [i]. symbol = IFFALSE_; parse [i]. content.label = parse [i + 1]. content.label; schuif (i + 1, 1); } /* Optimalisatie 9b: */ /* not iffalse x -> iftrue x */ if (parse [i]. symbol == NOT_ && parse [i + 1]. symbol == IFFALSE_) { verbeterd = 1; parse [i]. symbol = IFTRUE_; parse [i]. content.label = parse [i + 1]. content.label; schuif (i + 1, 1); } /* De volgende optimalisaties ontbreken want zijn hier overbodig: */ /* goto x -> goto y / __ ... label x goto y */ /* trek twee opeenvolgende labels samen */ } /* for i */ /* Verwijder labels waar niet naar verwezen wordt. */ for (i = 1; i <= numberOfInstructions; i ++) if (parse [i]. symbol == LABEL_) { int gevonden = 0; for (j = 1; j <= numberOfInstructions; j ++) if ((parse [j]. symbol == GOTO_ || parse [j]. symbol == IFFALSE_ || parse [j]. symbol == IFTRUE_ || parse [j]. symbol == INCREMENT_GREATER_GOTO_) && parse [i]. content.label == parse [j]. content.label) gevonden = 1; if (! gevonden) { verbeterd = 1; schuif (i, 1); } } if (! verbeterd) break; } } static void Formula_evaluateConstants (void) { for (;;) { bool improved = 0; for (int i = 1; i <= numberOfInstructions; i ++) { int gain = 0; if (parse [i]. symbol == NUMBER_) { if (parse [i]. content.number == 2.0 && parse [i + 1]. symbol == POWER_) { gain = 1; parse [i]. symbol = SQR_; } else if (parse [i + 1]. symbol == MINUS_) { gain = 1; parse [i]. content.number = - parse [i]. content.number; } else if (parse [i + 1]. symbol == SQR_) { gain = 1; parse [i]. content.number *= parse [i]. content.number; } else if (parse [i + 1]. symbol == NUMBER_) { if (parse [i + 2]. symbol == ADD_) { gain = 2; parse [i]. content.number += parse [i + 1]. content.number; } else if (parse [i + 2]. symbol == SUB_) { gain = 2; parse [i]. content.number -= parse [i + 1]. content.number; } else if (parse [i + 2]. symbol == MUL_) { gain = 2; parse [i]. content.number *= parse [i + 1]. content.number; } else if (parse [i + 2]. symbol == RDIV_) { gain = 2; parse [i]. content.number /= parse [i + 1]. content.number; } } } if (gain) { improved = true; schuif (i + 1, gain); } } if (! improved) break; } } static void Formula_removeLabels (void) { /* * First translate symbolic labels (< 0) into instructions locations (> 0). */ for (int i = 1; i <= numberOfInstructions; i ++) { int symboli = parse [i]. symbol; if (symboli == GOTO_ || symboli == IFTRUE_ || symboli == IFFALSE_ || symboli == INCREMENT_GREATER_GOTO_) { int label = parse [i]. content.label; for (int j = 1; j <= numberOfInstructions; j ++) { if (parse [j]. symbol == LABEL_ && parse [j]. content.label == label) { parse [i]. content.label = j; } } } } /* * Then remove the labels, which have become superfluous. */ if (theOptimize) { int i = 1; while (i <= numberOfInstructions) { int symboli = parse [i]. symbol; if (symboli == LABEL_) { schuif (i, 1); // remove one label for (int j = 1; j <= numberOfInstructions; j ++) { int symbolj = parse [j]. symbol; if ((symbolj == GOTO_ || symbolj == IFTRUE_ || symbolj == IFFALSE_ || symbolj == INCREMENT_GREATER_GOTO_) && parse [j]. content.label > i) parse [j]. content.label --; /* Pas een label aan. */ } i --; /* Voorkom ophogen i (overbodig?). */ } i ++; } } numberOfInstructions --; /* Het END_-symbol hoeft niet geinterpreteerd. */ } /* * For debugging. */ static void Formula_print (FormulaInstruction f) { int i = 0, symbol; do { const wchar *instructionName; symbol = f [++ i]. symbol; instructionName = Formula_instructionNames [symbol]; if (symbol == NUMBER_) Melder_casual ("%d %ls %.17g", i, instructionName, f [i]. content.number); else if (symbol == GOTO_ || symbol == IFFALSE_ || symbol == IFTRUE_ || symbol == LABEL_ || symbol == INCREMENT_GREATER_GOTO_) Melder_casual ("%d %ls %d", i, instructionName, f [i]. content.label); else if (symbol == NUMERIC_VARIABLE_) Melder_casual ("%d %ls %ls %ls", i, instructionName, f [i]. content.variable -> string, Melder_double (f [i]. content.variable -> numericValue)); else if (symbol == STRING_VARIABLE_) Melder_casual ("%d %ls %ls %ls", i, instructionName, f [i]. content.variable -> string, f [i]. content.variable -> stringValue); else if (symbol == STRING_ || symbol == VARIABLE_NAME_ || symbol == INDEXED_NUMERIC_VARIABLE_ || symbol == INDEXED_STRING_VARIABLE_) Melder_casual ("%d %ls \"%ls\"", i, instructionName, f [i]. content.string); else if (symbol == MATRIKS_ || symbol == MATRIKSSTR_ || symbol == MATRIKS1_ || symbol == MATRIKSSTR1_ || symbol == MATRIKS2_ || symbol == MATRIKSSTR2_ || symbol == ROWSTR_ || symbol == COLSTR_) { Thing object = (Thing) f [i]. content.object; if (object) { Melder_casual ("%d %ls %s %s", i, instructionName, Melder_peekWcsToUtf8 (Thing_className (object)), Melder_peekWcsToUtf8 (object -> name)); } else { Melder_casual ("%d %ls", i, instructionName); } } else if (symbol == CALL_) Melder_casual ("%d %ls %ls", i, instructionName, f [i]. content.string); else Melder_casual ("%d %ls", i, instructionName); } while (symbol != END_); } void Formula_compile (Any interpreter, Any data, const wchar *expression, int expressionType, int optimize) { theInterpreter = (Interpreter) interpreter; if (theInterpreter == NULL) { if (theLocalInterpreter == NULL) { theLocalInterpreter = Interpreter_create (NULL, NULL); } theInterpreter = theLocalInterpreter; Collection_removeAllItems (theInterpreter -> variables); } theSource = (Data) data; theExpression = expression; theExpressionType = expressionType; theOptimize = optimize; if (! lexan) { lexan = Melder_calloc_f (struct structFormulaInstruction, 3000); lexan [3000 - 1]. symbol = END_; /* Make sure that string cleaning always terminates. */ } if (! parse) parse = Melder_calloc_f (struct structFormulaInstruction, 3000); /* Clean up strings from the previous call. These strings are in a union, that's why this cannot be done later, when a new string is created. */ if (numberOfStringConstants) { ilexan = 1; for (;;) { int symbol = lexan [ilexan]. symbol; if (symbol == STRING_ || symbol == VARIABLE_NAME_ || symbol == INDEXED_NUMERIC_VARIABLE_ || symbol == INDEXED_STRING_VARIABLE_ || symbol == CALL_) Melder_free (lexan [ilexan]. content.string); else if (symbol == END_) break; /* Either the end of a formula, or the end of lexan. */ ilexan ++; } numberOfStringConstants = 0; } Formula_lexan (); therror if (Melder_debug == 17) Formula_print (lexan); Formula_parseExpression (); therror if (Melder_debug == 17) Formula_print (parse); if (theOptimize) { Formula_optimizeFlow (); if (Melder_debug == 17) Formula_print (parse); Formula_evaluateConstants (); if (Melder_debug == 17) Formula_print (parse); } Formula_removeLabels (); if (Melder_debug == 17) Formula_print (parse); } /* * Running. */ static int programPointer; typedef struct structStackel { #define Stackel_NUMBER 0 #define Stackel_STRING 1 #define Stackel_NUMERIC_ARRAY 2 #define Stackel_STRING_ARRAY 3 #define Stackel_VARIABLE -1 int which; /* 0 or negative = no clean-up required, positive = requires clean-up */ union { double number; wchar_t *string; struct Formula_NumericArray numericArray; InterpreterVariable variable; } content; } *Stackel; static void Stackel_cleanUp (Stackel me) { if (my which == Stackel_STRING) { Melder_free (my content.string); } else if (my which == Stackel_NUMERIC_ARRAY) { NUMmatrix_free (my content.numericArray.data, 1, 1); my content.numericArray = theZeroNumericArray; } } static Stackel theStack; static int w, wmax; /* w = stack pointer; */ #define pop & theStack [w --] static inline void pushNumber (double x) { /* inline runs 10 to 20 percent faster on i386; here's the test script: stopwatch Create Sound from formula... test mono 0 100 44100 1/2 * (2*pi*377*x) t = stopwatch echo 't' * Mac: 0.75 -> 0.67 seconds * Win: 1.10 -> 0.90 seconds (20100107) */ Stackel stackel = & theStack [++ w]; if (stackel -> which > Stackel_NUMBER) Stackel_cleanUp (stackel); if (w > wmax) wmax ++; stackel -> which = Stackel_NUMBER; stackel -> content.number = x; } static void pushString (wchar_t *x) { Stackel stackel = & theStack [++ w]; if (stackel -> which > Stackel_NUMBER) Stackel_cleanUp (stackel); if (w > wmax) wmax ++; stackel -> which = Stackel_STRING; stackel -> content.string = x; } static void pushNumericArray (long numberOfRows, long numberOfColumns, double **x) { Stackel stackel = & theStack [++ w]; if (stackel -> which > Stackel_NUMBER) Stackel_cleanUp (stackel); if (w > wmax) wmax ++; stackel -> which = Stackel_NUMERIC_ARRAY; stackel -> content.numericArray.numberOfRows = numberOfRows; stackel -> content.numericArray.numberOfColumns = numberOfColumns; stackel -> content.numericArray.data = x; } static void pushVariable (InterpreterVariable var) { Stackel stackel = & theStack [++ w]; if (stackel -> which > Stackel_NUMBER) Stackel_cleanUp (stackel); if (w > wmax) wmax ++; stackel -> which = Stackel_VARIABLE; stackel -> content.variable = var; } static const wchar *Stackel_whichText (Stackel me) { return my which == Stackel_NUMBER ? L"a number" : my which == Stackel_STRING ? L"a string" : my which == Stackel_NUMERIC_ARRAY ? L"a numeric array" : my which == Stackel_STRING_ARRAY ? L"a string array" : L"???"; } static void do_not (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : x->content.number == 0.0 ? 1.0 : 0.0); } else { Melder_throw ("Cannot negate (\"not\") ", Stackel_whichText (x), "."); } } static void do_eq (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == y->content.number ? 1.0 : 0.0); /* Even if undefined. */ } else if (x->which == Stackel_STRING && y->which == Stackel_STRING) { double result = wcsequ (x->content.string, y->content.string) ? 1.0 : 0.0; pushNumber (result); } else { Melder_throw ("Cannot compare (=) ", Stackel_whichText (x), " to ", Stackel_whichText (y), "."); } } static void do_ne (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number != y->content.number ? 1.0 : 0.0); /* Even if undefined. */ } else if (x->which == Stackel_STRING && y->which == Stackel_STRING) { double result = wcsequ (x->content.string, y->content.string) ? 0.0 : 1.0; pushNumber (result); } else { Melder_throw ("Cannot compare (<>) ", Stackel_whichText (x), " to ", Stackel_whichText (y), "."); } } static void do_le (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : x->content.number <= y->content.number ? 1.0 : 0.0); } else if (x->which == Stackel_STRING && y->which == Stackel_STRING) { double result = wcscmp (x->content.string, y->content.string) <= 0 ? 1.0 : 0.0; pushNumber (result); } else { Melder_throw ("Cannot compare (<=) ", Stackel_whichText (x), " to ", Stackel_whichText (y), "."); } } static void do_lt (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : x->content.number < y->content.number ? 1.0 : 0.0); } else if (x->which == Stackel_STRING && y->which == Stackel_STRING) { double result = wcscmp (x->content.string, y->content.string) < 0 ? 1.0 : 0.0; pushNumber (result); } else { Melder_throw ("Cannot compare (<) ", Stackel_whichText (x), " to ", Stackel_whichText (y), "."); } } static void do_ge (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : x->content.number >= y->content.number ? 1.0 : 0.0); } else if (x->which == Stackel_STRING && y->which == Stackel_STRING) { double result = wcscmp (x->content.string, y->content.string) >= 0 ? 1.0 : 0.0; pushNumber (result); } else { Melder_throw ("Cannot compare (>=) ", Stackel_whichText (x), " to ", Stackel_whichText (y), "."); } } static void do_gt (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : x->content.number > y->content.number ? 1.0 : 0.0); } else if (x->which == Stackel_STRING && y->which == Stackel_STRING) { double result = wcscmp (x->content.string, y->content.string) > 0 ? 1.0 : 0.0; pushNumber (result); } else { Melder_throw ("Cannot compare (>) ", Stackel_whichText (x), " to ", Stackel_whichText (y), "."); } } static void do_add (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : x->content.number + y->content.number); } else if (x->which == Stackel_STRING && y->which == Stackel_STRING) { long length1 = wcslen (x->content.string), length2 = wcslen (y->content.string); wchar_t *result = Melder_malloc (wchar_t, length1 + length2 + 1); wcscpy (result, x->content.string); wcscpy (result + length1, y->content.string); pushString (result); } else { Melder_throw ("Cannot add ", Stackel_whichText (y), " to ", Stackel_whichText (x), "."); } } static void do_sub (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : x->content.number - y->content.number); } else if (x->which == Stackel_STRING && y->which == Stackel_STRING) { long length1 = wcslen (x->content.string), length2 = wcslen (y->content.string), newlength = length1 - length2; wchar_t *result; if (newlength >= 0 && wcsnequ (x->content.string + newlength, y->content.string, length2)) { result = Melder_malloc (wchar_t, newlength + 1); wcsncpy (result, x->content.string, newlength); result [newlength] = '\0'; } else { result = Melder_wcsdup (x->content.string); } pushString (result); } else { Melder_throw ("Cannot subtract (-) ", Stackel_whichText (y), " from ", Stackel_whichText (x), "."); } } static void do_mul (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : x->content.number * y->content.number); } else { Melder_throw ("Cannot multiply (*) ", Stackel_whichText (x), " by ", Stackel_whichText (y), "."); } } static void do_rdiv (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : y->content.number == 0.0 ? NUMundefined : x->content.number / y->content.number); } else { Melder_throw ("Cannot divide (/) ", Stackel_whichText (x), " by ", Stackel_whichText (y), "."); } } static void do_idiv (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : y->content.number == 0.0 ? NUMundefined : floor (x->content.number / y->content.number)); } else { Melder_throw ("Cannot divide (\"div\") ", Stackel_whichText (x), " by ", Stackel_whichText (y), "."); } } static void do_mod (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : y->content.number == 0.0 ? NUMundefined : x->content.number - floor (x->content.number / y->content.number) * y->content.number); } else { Melder_throw ("Cannot divide (\"mod\") ", Stackel_whichText (x), " by ", Stackel_whichText (y), "."); } } static void do_minus (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : - x->content.number); } else { Melder_throw ("Cannot take the opposite (-) of ", Stackel_whichText (x), "."); } } static void do_power (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : pow (x->content.number, y->content.number)); } else { Melder_throw ("Cannot exponentiate (^) ", Stackel_whichText (x), " to ", Stackel_whichText (y), "."); } } static void do_sqr (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : x->content.number * x->content.number); } else { Melder_throw ("Cannot take the square (^ 2) of ", Stackel_whichText (x), "."); } } static void do_function_n_n (double (*f) (double)) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : f (x->content.number)); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires a numeric argument, not ", Stackel_whichText (x), "."); } } static void do_abs (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : fabs (x->content.number)); } else { Melder_throw ("Cannot take the absolute value (abs) of ", Stackel_whichText (x), "."); } } static void do_round (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : floor (x->content.number + 0.5)); } else { Melder_throw ("Cannot round ", Stackel_whichText (x), "."); } } static void do_floor (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : floor (x->content.number)); } else { Melder_throw ("Cannot round down (floor) ", Stackel_whichText (x), "."); } } static void do_ceiling (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : ceil (x->content.number)); } else { Melder_throw ("Cannot round up (ceiling) ", Stackel_whichText (x), "."); } } static void do_sqrt (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : x->content.number < 0.0 ? NUMundefined : sqrt (x->content.number)); } else { Melder_throw ("Cannot take the square root (sqrt) of ", Stackel_whichText (x), "."); } } static void do_sin (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : sin (x->content.number)); } else { Melder_throw ("Cannot take the sine (sin) of ", Stackel_whichText (x), "."); } } static void do_cos (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : cos (x->content.number)); } else { Melder_throw ("Cannot take the cosine (cos) of ", Stackel_whichText (x), "."); } } static void do_tan (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : tan (x->content.number)); } else { Melder_throw ("Cannot take the tangent (tan) of ", Stackel_whichText (x), "."); } } static void do_arcsin (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : fabs (x->content.number) > 1.0 ? NUMundefined : asin (x->content.number)); } else { Melder_throw ("Cannot take the arcsine (arcsin) of ", Stackel_whichText (x), "."); } } static void do_arccos (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : fabs (x->content.number) > 1.0 ? NUMundefined : acos (x->content.number)); } else { Melder_throw ("Cannot take the arccosine (arccos) of ", Stackel_whichText (x), "."); } } static void do_arctan (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : atan (x->content.number)); } else { Melder_throw ("Cannot take the arctangent (arctan) of ", Stackel_whichText (x), "."); } } static void do_exp (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : exp (x->content.number)); } else { Melder_throw ("Cannot exponentiate (exp) ", Stackel_whichText (x), "."); } } static void do_sinh (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : sinh (x->content.number)); } else { Melder_throw ("Cannot take the hyperbolic sine (sinh) of ", Stackel_whichText (x), "."); } } static void do_cosh (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : cosh (x->content.number)); } else { Melder_throw ("Cannot take the hyperbolic cosine (cosh) of ", Stackel_whichText (x), "."); } } static void do_tanh (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : tanh (x->content.number)); } else { Melder_throw ("Cannot take the hyperbolic tangent (tanh) of ", Stackel_whichText (x), "."); } } static void do_log2 (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : x->content.number <= 0.0 ? NUMundefined : log (x->content.number) * NUMlog2e); } else { Melder_throw ("Cannot take the base-2 logarithm (log2) of ", Stackel_whichText (x), "."); } } static void do_ln (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : x->content.number <= 0.0 ? NUMundefined : log (x->content.number)); } else { Melder_throw ("Cannot take the natural logarithm (ln) of ", Stackel_whichText (x), "."); } } static void do_log10 (void) { Stackel x = pop; if (x->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined ? NUMundefined : x->content.number <= 0.0 ? NUMundefined : log10 (x->content.number)); } else { Melder_throw ("Cannot take the base-10 logarithm (log10) of ", Stackel_whichText (x), "."); } } static void do_function_dd_d (double (*f) (double, double)) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : f (x->content.number, y->content.number)); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires two numeric arguments, not ", Stackel_whichText (x), " and ", Stackel_whichText (y), "."); } } static void do_function_dd_d_numar (double (*f) (double, double)) { Stackel n = pop; Melder_assert (n -> which == Stackel_NUMBER); if (n -> content.number != 3) Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires three arguments."); Stackel y = pop, x = pop, a = pop; if (a->which == Stackel_NUMERIC_ARRAY && x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { long numberOfRows = a->content.numericArray.numberOfRows; long numberOfColumns = a->content.numericArray.numberOfColumns; double **newData = NUMmatrix (1, numberOfRows, 1, numberOfColumns); therror for (long irow = 1; irow <= numberOfRows; irow ++) { for (long icol = 1; icol <= numberOfColumns; icol ++) { newData [irow] [icol] = f (x->content.number, y->content.number); } } pushNumericArray (numberOfRows, numberOfColumns, newData); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires one array argument and two numeric arguments, not ", Stackel_whichText (a), ", ", Stackel_whichText (x), " and ", Stackel_whichText (y), "."); } } static void do_function_ll_l_numar (long (*f) (long, long)) { Stackel n = pop; Melder_assert (n -> which == Stackel_NUMBER); if (n -> content.number != 3) Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires three arguments."); Stackel y = pop, x = pop, a = pop; if (a->which == Stackel_NUMERIC_ARRAY && x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { long numberOfRows = a->content.numericArray.numberOfRows; long numberOfColumns = a->content.numericArray.numberOfColumns; double **newData = NUMmatrix (1, numberOfRows, 1, numberOfColumns); therror for (long irow = 1; irow <= numberOfRows; irow ++) { for (long icol = 1; icol <= numberOfColumns; icol ++) { newData [irow] [icol] = f (x->content.number, y->content.number); } } pushNumericArray (numberOfRows, numberOfColumns, newData); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires one array argument and two numeric arguments, not ", Stackel_whichText (a), ", ", Stackel_whichText (x), " and ", Stackel_whichText (y), "."); } } static void do_function_dl_d (double (*f) (double, long)) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : f (x->content.number, y->content.number)); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires two numeric arguments, not ", Stackel_whichText (x), " and ", Stackel_whichText (y), "."); } } static void do_function_ld_d (double (*f) (long, double)) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : f (x->content.number, y->content.number)); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires two numeric arguments, not ", Stackel_whichText (x), " and ", Stackel_whichText (y), "."); } } static void do_function_ll_l (long (*f) (long, long)) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : f (x->content.number, y->content.number)); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires two numeric arguments, not ", Stackel_whichText (x), " and ", Stackel_whichText (y), "."); } } static void do_objects_are_identical (void) { Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { int id1 = x->content.number, id2 = y->content.number; int i = theCurrentPraatObjects -> n; while (i > 0 && id1 != theCurrentPraatObjects -> list [i]. id) i --; if (i == 0) Melder_throw ("Object #", id1, " does not exist in function objectsAreIdentical."); Data object1 = (Data) theCurrentPraatObjects -> list [i]. object; i = theCurrentPraatObjects -> n; while (i > 0 && id2 != theCurrentPraatObjects -> list [i]. id) i --; if (i == 0) Melder_throw ("Object #", id2, " does not exist in function objectsAreIdentical."); Data object2 = (Data) theCurrentPraatObjects -> list [i]. object; pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined ? NUMundefined : Data_equal (object1, object2)); } else { Melder_throw ("The function objectsAreIdentical requires two numeric arguments (object IDs), not ", Stackel_whichText (x), " and ", Stackel_whichText (y), "."); } } static void do_function_ddd_d (double (*f) (double, double, double)) { Stackel z = pop, y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER && z->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined || z->content.number == NUMundefined ? NUMundefined : f (x->content.number, y->content.number, z->content.number)); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires three numeric arguments, not ", Stackel_whichText (x), ", ", Stackel_whichText (y), ", and ", Stackel_whichText (z), "."); } } static void do_function_dll_d (double (*f) (double, long, long)) { Stackel z = pop, y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER && z->which == Stackel_NUMBER) { pushNumber (x->content.number == NUMundefined || y->content.number == NUMundefined || z->content.number == NUMundefined ? NUMundefined : f (x->content.number, y->content.number, z->content.number)); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires three numeric arguments, not ", Stackel_whichText (x), ", ", Stackel_whichText (y), ", and ", Stackel_whichText (z), "."); } } static void do_min (void) { Stackel n = pop, last; double result; Melder_assert (n->which == Stackel_NUMBER); if (n->content.number < 1) Melder_throw ("The function \"min\" requires at least one argument."); last = pop; if (last->which != Stackel_NUMBER) Melder_throw ("The function \"min\" can only have numeric arguments, not ", Stackel_whichText (last), "."); result = last->content.number; for (int j = n->content.number - 1; j > 0; j --) { Stackel previous = pop; if (previous->which != Stackel_NUMBER) Melder_throw ("The function \"min\" can only have numeric arguments, not ", Stackel_whichText (previous), "."); result = result == NUMundefined || previous->content.number == NUMundefined ? NUMundefined : result < previous->content.number ? result : previous->content.number; } pushNumber (result); } static void do_max (void) { Stackel n = pop, last; double result; Melder_assert (n->which == Stackel_NUMBER); if (n->content.number < 1) Melder_throw ("The function \"max\" requires at least one argument."); last = pop; if (last->which != Stackel_NUMBER) Melder_throw ("The function \"max\" can only have numeric arguments, not ", Stackel_whichText (last), "."); result = last->content.number; for (int j = n->content.number - 1; j > 0; j --) { Stackel previous = pop; if (previous->which != Stackel_NUMBER) Melder_throw ("The function \"max\" can only have numeric arguments, not ", Stackel_whichText (previous), "."); result = result == NUMundefined || previous->content.number == NUMundefined ? NUMundefined : result > previous->content.number ? result : previous->content.number; } pushNumber (result); } static void do_imin (void) { Stackel n = pop, last; double minimum, result; Melder_assert (n->which == Stackel_NUMBER); if (n->content.number < 1) Melder_throw ("The function \"imin\" requires at least one argument."); last = pop; if (last->which != Stackel_NUMBER) Melder_throw ("The function \"imin\" can only have numeric arguments, not ", Stackel_whichText (last), "."); minimum = last->content.number; result = n->content.number; for (int j = n->content.number - 1; j > 0; j --) { Stackel previous = pop; if (previous->which != Stackel_NUMBER) Melder_throw ("The function \"imin\" can only have numeric arguments, not ", Stackel_whichText (previous), "."); if (minimum == NUMundefined || previous->content.number == NUMundefined) { minimum = NUMundefined; result = NUMundefined; } else if (previous->content.number < minimum) { minimum = previous->content.number; result = j; } } pushNumber (result); } static void do_imax (void) { Stackel n = pop, last; double maximum, result; Melder_assert (n->which == Stackel_NUMBER); if (n->content.number < 1) Melder_throw ("The function \"imax\" requires at least one argument."); last = pop; if (last->which != Stackel_NUMBER) Melder_throw ("The function \"imax\" can only have numeric arguments, not ", Stackel_whichText (last), "."); maximum = last->content.number; result = n->content.number; for (int j = n->content.number - 1; j > 0; j --) { Stackel previous = pop; if (previous->which != Stackel_NUMBER) Melder_throw ("The function \"imax\" can only have numeric arguments, not ", Stackel_whichText (previous), "."); if (maximum == NUMundefined || previous->content.number == NUMundefined) { maximum = NUMundefined; result = NUMundefined; } else if (previous->content.number > maximum) { maximum = previous->content.number; result = j; } } pushNumber (result); } static void do_zeroNumar (void) { Stackel n = pop; Melder_assert (n -> which == Stackel_NUMBER); int rank = n -> content.number; if (rank < 1) Melder_throw ("The function \"zero#\" requires arguments."); long numberOfRows = 1, numberOfColumns = 1; if (rank > 1) { if (rank > 2) Melder_throw ("The function \"zero#\" cannot have more than two arguments."); Stackel ncol = pop; if (ncol -> which != Stackel_NUMBER) Melder_throw ("In the function \"zero#\", the number of columns has to be a number, not ", Stackel_whichText (ncol), "."); numberOfColumns = ncol -> content.number; } Stackel nrow = pop; if (nrow -> which != Stackel_NUMBER) Melder_throw ("In the function \"zero#\", the number of rows has to be a number, not ", Stackel_whichText (nrow), "."); numberOfRows = nrow -> content.number; if (numberOfRows == NUMundefined) Melder_throw ("In the function \"zero#\", the number of rows is undefined."); if (numberOfColumns == NUMundefined) Melder_throw ("In the function \"zero#\", the number of columns is undefined."); if (numberOfRows <= 0) Melder_throw ("In the function \"zero#\", the number of rows has to be positive."); if (numberOfColumns <= 0) Melder_throw ("In the function \"zero#\", the number of columns has to be positive."); autoNUMmatrix data (1, numberOfRows, 1, numberOfColumns); pushNumericArray (numberOfRows, numberOfColumns, data.transfer()); } static void do_linearNumar (void) { Stackel stackel_narg = pop; Melder_assert (stackel_narg -> which == Stackel_NUMBER); int narg = stackel_narg -> content.number; if (narg < 3 || narg > 4) Melder_throw ("The function \"linear#\" requires three or four arguments."); bool excludeEdges = false; // default if (narg == 4) { Stackel stack_excludeEdges = pop; if (stack_excludeEdges -> which != Stackel_NUMBER) Melder_throw ("In the function \"linear#\", the edge exclusion flag (fourth argument) has to be a number, not ", Stackel_whichText (stack_excludeEdges), "."); excludeEdges = stack_excludeEdges -> content.number; } Stackel stack_numberOfSteps = pop, stack_maximum = pop, stack_minimum = pop; if (stack_minimum -> which != Stackel_NUMBER) Melder_throw ("In the function \"linear#\", the minimum (first argument) has to be a number, not ", Stackel_whichText (stack_minimum), "."); double minimum = stack_minimum -> content.number; if (minimum == NUMundefined) Melder_throw ("Undefined minimum in the function \"linear#\" (first argument)."); if (stack_maximum -> which != Stackel_NUMBER) Melder_throw ("In the function \"linear#\", the maximum (second argument) has to be a number, not ", Stackel_whichText (stack_maximum), "."); double maximum = stack_maximum -> content.number; if (maximum == NUMundefined) Melder_throw ("Undefined maximum in the function \"linear#\" (second argument)."); if (maximum < minimum) Melder_throw ("Maximum (", maximum, L") smaller than minimum (", minimum, ") in function \"linear#\"."); if (stack_numberOfSteps -> which != Stackel_NUMBER) Melder_throw ("In the function \"linear#\", the number of steps (third argument) has to be a number, not ", Stackel_whichText (stack_numberOfSteps), "."); if (stack_numberOfSteps -> content.number == NUMundefined) Melder_throw ("Undefined number of steps in the function \"linear#\" (third argument)."); long numberOfSteps = floor (stack_numberOfSteps -> content.number + 0.5); if (numberOfSteps <= 0) Melder_throw ("In the function \"linear#\", the number of steps (third argument) has to be positive, not ", numberOfSteps, "."); autoNUMmatrix data (1, numberOfSteps, 1, 1); for (long irow = 1; irow <= numberOfSteps; irow ++) { data [irow] [1] = excludeEdges ? minimum + (irow - 0.5) * (maximum - minimum) / numberOfSteps : minimum + (irow - 1) * (maximum - minimum) / (numberOfSteps - 1); } if (! excludeEdges) data [numberOfSteps] [1] = maximum; // remove rounding problems pushNumericArray (numberOfSteps, 1, data.transfer()); } static void do_numberOfRows (void) { Stackel n = pop; Melder_assert (n->which == Stackel_NUMBER); if (n->content.number != 1) Melder_throw ("The function \"numberOfRows\" requires one argument."); Stackel array = pop; if (array->which == Stackel_NUMERIC_ARRAY) { pushNumber (array->content.numericArray.numberOfRows); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires a numeric argument, not ", Stackel_whichText (array), "."); } } static void do_numberOfColumns (void) { Stackel n = pop; Melder_assert (n->which == Stackel_NUMBER); if (n->content.number != 1) Melder_throw ("The function \"numberOfColumns\" requires one argument."); Stackel array = pop; if (array->which == Stackel_NUMERIC_ARRAY) { pushNumber (array->content.numericArray.numberOfColumns); } else { Melder_throw ("The function ", Formula_instructionNames [parse [programPointer]. symbol], " requires a numeric argument, not ", Stackel_whichText (array), "."); } } static void do_numericArrayElement (void) { Stackel n = pop; Melder_assert (n -> which == Stackel_NUMBER); int narg = n -> content.number; if (narg < 1 || narg > 2) Melder_throw ("Array indexing requires one or two arguments."); InterpreterVariable array = parse [programPointer]. content.variable; long row = 1, column = 1; // default if (narg > 1) { Stackel c = pop; if (c -> which != Stackel_NUMBER) Melder_throw ("In array indexing, the column index has to be a number, not ", Stackel_whichText (c), "."); if (c -> content.number == NUMundefined) Melder_throw ("The column index is undefined."); column = floor (c -> content.number + 0.5); if (column <= 0) Melder_throw ("In array indexing, the column index has to be positive."); if (column > array -> numericArrayValue. numberOfColumns) Melder_throw ("Column index out of bounds."); } Stackel r = pop; if (r -> which != Stackel_NUMBER) Melder_throw ("In array indexing, the row index has to be a number, not ", Stackel_whichText (r), "."); if (r -> content.number == NUMundefined) Melder_throw ("The row index is undefined."); row = floor (r -> content.number + 0.5); if (row <= 0) Melder_throw ("In array indexing, the row index has to be positive."); if (row > array -> numericArrayValue. numberOfRows) Melder_throw ("Row index out of bounds."); pushNumber (array -> numericArrayValue. data [row] [column]); } static void do_indexedNumericVariable (void) { Stackel n = pop; Melder_assert (n -> which == Stackel_NUMBER); int nindex = n -> content.number; if (nindex < 1) Melder_throw ("Indexed variables require at least one index."); wchar_t *indexedVariableName = parse [programPointer]. content.string; static MelderString totalVariableName = { 0 }; MelderString_copy (& totalVariableName, indexedVariableName); MelderString_append (& totalVariableName, L"["); w -= nindex; for (int iindex = 1; iindex <= nindex; iindex ++) { Stackel index = & theStack [w + iindex]; if (index -> which != Stackel_NUMBER) Melder_throw ("In indexed variables, the index has to be a number, not ", Stackel_whichText (index), "."); MelderString_append (& totalVariableName, Melder_double (index -> content.number), iindex == nindex ? L"]" : L","); } InterpreterVariable var = Interpreter_hasVariable (theInterpreter, totalVariableName.string); if (var == NULL) Melder_throw ("Undefined indexed variable " L_LEFT_GUILLEMET, totalVariableName.string, L_RIGHT_GUILLEMET "."); pushNumber (var -> numericValue); } static void do_indexedStringVariable (void) { Stackel n = pop; Melder_assert (n -> which == Stackel_NUMBER); int nindex = n -> content.number; if (nindex < 1) Melder_throw ("Indexed variables require at least one index."); wchar_t *indexedVariableName = parse [programPointer]. content.string; static MelderString totalVariableName = { 0 }; MelderString_copy (& totalVariableName, indexedVariableName); MelderString_append (& totalVariableName, L"["); w -= nindex; for (int iindex = 1; iindex <= nindex; iindex ++) { Stackel index = & theStack [w + iindex]; if (index -> which != Stackel_NUMBER) Melder_throw ("In indexed variables, the index has to be a number, not ", Stackel_whichText (index), "."); MelderString_append (& totalVariableName, Melder_double (index -> content.number), iindex == nindex ? L"]" : L","); } InterpreterVariable var = Interpreter_hasVariable (theInterpreter, totalVariableName.string); if (var == NULL) Melder_throw ("Undefined indexed variable " L_LEFT_GUILLEMET, totalVariableName.string, L_RIGHT_GUILLEMET "."); autostring result = Melder_wcsdup (var -> stringValue); pushString (result.transfer()); } static void do_length (void) { Stackel s = pop; if (s->which == Stackel_STRING) { double result = wcslen (s->content.string); pushNumber (result); } else { Melder_throw ("The function \"length\" requires a string, not ", Stackel_whichText (s), "."); } } static void do_fileReadable (void) { Stackel s = pop; if (s->which == Stackel_STRING) { structMelderFile file = { 0 }; Melder_relativePathToFile (s->content.string, & file); pushNumber (MelderFile_readable (& file)); } else { Melder_throw ("The function \"fileReadable\" requires a string, not ", Stackel_whichText (s), "."); } } static void do_dateStr (void) { time_t today = time (NULL); wchar_t *date, *newline; date = Melder_utf8ToWcs (ctime (& today)); newline = wcschr (date, '\n'); if (newline) *newline = '\0'; pushString (date); } static void do_leftStr (void) { //Melder_casual ("entering left$"); Stackel narg = pop; if (narg->content.number == 1 || narg->content.number == 2) { Stackel x = ( narg->content.number == 2 ? pop : NULL ), s = pop; if (s->which == Stackel_STRING && (x == NULL || x->which == Stackel_NUMBER)) { long newlength = x ? x->content.number : 1; long length = wcslen (s->content.string); if (newlength < 0) newlength = 0; if (newlength > length) newlength = length; #if 0 autostring s1; autostring s2 = s1; // copy constructor disabled s1 = s2; #endif autostring result = Melder_malloc (wchar, newlength + 1); wcsncpy (result.peek(), s->content.string, newlength); result [newlength] = '\0'; pushString (result.transfer()); } else { Melder_throw ("The function \"left$\" requires a string, or a string and a number."); } } else { Melder_throw ("The function \"left$\" requires one or two arguments."); } //Melder_casual ("leaving left$"); } static void do_rightStr (void) { Stackel narg = pop; if (narg->content.number == 1 || narg->content.number == 2) { Stackel x = ( narg->content.number == 2 ? pop : NULL ), s = pop; if (s->which == Stackel_STRING && (x == NULL || x->which == Stackel_NUMBER)) { long newlength = x ? x->content.number : 1; long length = wcslen (s->content.string); if (newlength < 0) newlength = 0; if (newlength > length) newlength = length; pushString (Melder_wcsdup (s->content.string + length - newlength)); } else { Melder_throw ("The function \"right$\" requires a string, or a string and a number."); } } else { Melder_throw ("The function \"right$\" requires one or two arguments."); } } static void do_midStr (void) { Stackel narg = pop; if (narg->content.number == 2 || narg->content.number == 3) { Stackel y = ( narg->content.number == 3 ? pop : NULL ), x = pop, s = pop; if (s->which == Stackel_STRING && x->which == Stackel_NUMBER && (y == NULL || y->which == Stackel_NUMBER)) { long newlength = y ? y->content.number : 1; long start = x->content.number; long length = wcslen (s->content.string), finish = start + newlength - 1; autostring result; if (start < 1) start = 1; if (finish > length) finish = length; newlength = finish - start + 1; if (newlength > 0) { result.reset (Melder_malloc (wchar, newlength + 1)); wcsncpy (result.peek(), s->content.string + start - 1, newlength); result [newlength] = '\0'; } else { result.reset (Melder_wcsdup (L"")); } pushString (result.transfer()); } else { Melder_throw ("The function \"mid$\" requires a string and one or two numbers."); } } else { Melder_throw ("The function \"mid$\" requires two or three arguments."); } } static void do_environmentStr (void) { Stackel s = pop; if (s->which == Stackel_STRING) { wchar_t *value = Melder_getenv (s->content.string); autostring result = Melder_wcsdup (value != NULL ? value : L""); pushString (result.transfer()); } else { Melder_throw ("The function \"environment$\" requires a string, not ", Stackel_whichText (s), "."); } } static void do_index (void) { Stackel t = pop, s = pop; if (s->which == Stackel_STRING && t->which == Stackel_STRING) { wchar_t *substring = wcsstr (s->content.string, t->content.string); long result = substring ? substring - s->content.string + 1 : 0; pushNumber (result); } else { Melder_throw ("The function \"index\" requires two strings, not ", Stackel_whichText (s), " and ", Stackel_whichText (t), "."); } } static void do_rindex (void) { Stackel part = pop, whole = pop; if (whole->which == Stackel_STRING && part->which == Stackel_STRING) { wchar_t *lastSubstring = wcsstr (whole->content.string, part->content.string); if (part->content.string [0] == '\0') { long result = wcslen (whole->content.string); pushNumber (result); } else if (lastSubstring) { for (;;) { wchar_t *substring = wcsstr (lastSubstring + 1, part->content.string); if (substring == NULL) break; lastSubstring = substring; } pushNumber (lastSubstring - whole->content.string + 1); } else { pushNumber (0); } } else { Melder_throw ("The function \"rindex\" requires two strings, not ", Stackel_whichText (whole), " and ", Stackel_whichText (part), "."); } } static void do_stringMatchesCriterion (int criterion) { Stackel t = pop, s = pop; if (s->which == Stackel_STRING && t->which == Stackel_STRING) { int result = Melder_stringMatchesCriterion (s->content.string, criterion, t->content.string); pushNumber (result); } else { Melder_throw ("The function \"", Formula_instructionNames [parse [programPointer]. symbol], "\" requires two strings, not ", Stackel_whichText (s), " and ", Stackel_whichText (t), "."); } } static void do_index_regex (int backward) { Stackel t = pop, s = pop; if (s->which == Stackel_STRING && t->which == Stackel_STRING) { const wchar_t *errorMessage; regexp *compiled_regexp = CompileRE ((const regularExp_CHAR *) t->content.string, & errorMessage, 0); if (compiled_regexp == NULL) { pushNumber (NUMundefined); } else if (ExecRE (compiled_regexp, NULL, (const regularExp_CHAR *) s->content.string, NULL, backward, '\0', '\0', NULL, NULL, NULL)) { wchar_t *place = (wchar *) compiled_regexp -> startp [0]; pushNumber (place - s->content.string + 1); free (compiled_regexp); } else { pushNumber (FALSE); } } else { Melder_throw ("The function \"", Formula_instructionNames [parse [programPointer]. symbol], "\" requires two strings, not ", Stackel_whichText (s), " and ", Stackel_whichText (t), "."); } } static void do_replaceStr (void) { Stackel x = pop, u = pop, t = pop, s = pop; if (s->which == Stackel_STRING && t->which == Stackel_STRING && u->which == Stackel_STRING && x->which == Stackel_NUMBER) { long numberOfMatches; autostring result = str_replace_literal (s->content.string, t->content.string, u->content.string, x->content.number, & numberOfMatches); pushString (result.transfer()); } else { Melder_throw ("The function \"replace$\" requires three strings and a number."); } } static void do_replace_regexStr (void) { Stackel x = pop, u = pop, t = pop, s = pop; if (s->which == Stackel_STRING && t->which == Stackel_STRING && u->which == Stackel_STRING && x->which == Stackel_NUMBER) { const wchar_t *errorMessage; regexp *compiled_regexp = CompileRE ((const regularExp_CHAR *) t->content.string, & errorMessage, 0); if (compiled_regexp == NULL) { autostring result = Melder_wcsdup (L""); pushString (result.transfer()); } else { long numberOfMatches; autostring result = str_replace_regexp (s->content.string, compiled_regexp, u->content.string, x->content.number, & numberOfMatches); pushString (result.transfer()); } } else { Melder_throw ("The function \"replace_regex$\" requires three strings and a number."); } } static void do_extractNumber (void) { Stackel t = pop, s = pop; if (s->which == Stackel_STRING && t->which == Stackel_STRING) { wchar_t *substring = wcsstr (s->content.string, t->content.string); if (substring == NULL) { pushNumber (NUMundefined); } else { /* Skip the prompt. */ substring += wcslen (t->content.string); /* Skip white space. */ while (*substring == ' ' || *substring == '\t' || *substring == '\n' || *substring == '\r') substring ++; if (substring [0] == '\0' || wcsnequ (substring, L"--undefined--", 13)) { pushNumber (NUMundefined); } else { wchar_t buffer [101], *slash; int i; for (i = 0; i < 100; i ++) { buffer [i] = *substring; substring ++; if (*substring == '\0' || *substring == ' ' || *substring == '\t' || *substring == '\n' || *substring == '\r') break; } if (i >= 100) { buffer [100] = '\0'; pushNumber (Melder_atof (buffer)); } else { buffer [i + 1] = '\0'; slash = wcschr (buffer, '/'); if (slash) { double numerator, denominator; *slash = '\0'; numerator = Melder_atof (buffer), denominator = Melder_atof (slash + 1); pushNumber (numerator / denominator); } else { pushNumber (Melder_atof (buffer)); } } } } } else { Melder_throw ("The function \"", Formula_instructionNames [parse [programPointer]. symbol], "\" requires two strings, not ", Stackel_whichText (s), " and ", Stackel_whichText (t), "."); } } static void do_extractTextStr (int singleWord) { Stackel t = pop, s = pop; if (s->which == Stackel_STRING && t->which == Stackel_STRING) { wchar_t *substring = wcsstr (s->content.string, t->content.string); autostring result; if (substring == NULL) { result.reset (Melder_wcsdup (L"")); } else { long length; /* Skip the prompt. */ substring += wcslen (t->content.string); if (singleWord) { /* Skip white space. */ while (*substring == ' ' || *substring == '\t' || *substring == '\n' || *substring == '\r') substring ++; } wchar *p = substring; if (singleWord) { /* Proceed until next white space. */ while (*p != '\0' && *p != ' ' && *p != '\t' && *p != '\n' && *p != '\r') p ++; } else { /* Proceed until end of line. */ while (*p != '\0' && *p != '\n' && *p != '\r') p ++; } length = p - substring; result.reset (Melder_malloc (wchar, length + 1)); wcsncpy (result.peek(), substring, length); result [length] = '\0'; } pushString (result.transfer()); } else { Melder_throw ("The function \"", Formula_instructionNames [parse [programPointer]. symbol], "\" requires two strings, not ", Stackel_whichText (s), " and ", Stackel_whichText (t), "."); } } static void do_selected (void) { Stackel n = pop; long result = 0; if (n->content.number == 0) { result = praat_getIdOfSelected (NULL, 0); } else if (n->content.number == 1) { Stackel a = pop; if (a->which == Stackel_STRING) { ClassInfo klas = Thing_classFromClassName (a->content.string); therror result = praat_getIdOfSelected (klas, 0); } else if (a->which == Stackel_NUMBER) { result = praat_getIdOfSelected (NULL, a->content.number); } else { Melder_throw ("The function \"selected\" requires a string (an object type name) and/or a number."); } } else if (n->content.number == 2) { Stackel x = pop, s = pop; if (s->which == Stackel_STRING && x->which == Stackel_NUMBER) { ClassInfo klas = Thing_classFromClassName (s->content.string); therror result = praat_getIdOfSelected (klas, x->content.number); } else { Melder_throw ("The function \"selected\" requires a string (an object type name) and/or a number."); } } else { Melder_throw ("The function \"selected\" requires 0, 1, or 2 arguments, not ", n->content.number, "."); } pushNumber (result); } static void do_selectedStr (void) { Stackel n = pop; wchar_t *name; autostring result; if (n->content.number == 0) { name = praat_getNameOfSelected (NULL, 0); result.reset (Melder_wcsdup (name)); } else if (n->content.number == 1) { Stackel a = pop; if (a->which == Stackel_STRING) { ClassInfo klas = Thing_classFromClassName (a->content.string); therror name = praat_getNameOfSelected (klas, 0); result.reset (Melder_wcsdup (name)); } else if (a->which == Stackel_NUMBER) { name = praat_getNameOfSelected (NULL, a->content.number); result.reset (Melder_wcsdup (name)); } else { Melder_throw ("The function \"selected$\" requires a string (an object type name) and/or a number."); } } else if (n->content.number == 2) { Stackel x = pop, s = pop; if (s->which == Stackel_STRING && x->which == Stackel_NUMBER) { ClassInfo klas = Thing_classFromClassName (s->content.string); therror name = praat_getNameOfSelected (klas, x->content.number); result.reset (Melder_wcsdup (name)); } else { Melder_throw ("The function \"selected$\" requires 0, 1, or 2 arguments, not ", n->content.number, "."); } } pushString (result.transfer()); } static void do_numberOfSelected (void) { Stackel n = pop; long result = 0; if (n->content.number == 0) { result = praat_selection (NULL); } else if (n->content.number == 1) { Stackel s = pop; if (s->which == Stackel_STRING) { ClassInfo klas = Thing_classFromClassName (s->content.string); therror result = praat_selection (klas); } else { Melder_throw ("The function \"numberOfSelected\" requires a string (an object type name), not ", Stackel_whichText (s), "."); } } else { Melder_throw ("The function \"numberOfSelected\" requires 0 or 1 arguments, not ", n->content.number, "."); } pushNumber (result); } static void do_fixedStr (void) { Stackel precision = pop, value = pop; if (value->which == Stackel_NUMBER && precision->which == Stackel_NUMBER) { autostring result = Melder_wcsdup (Melder_fixed (value->content.number, precision->content.number)); pushString (result.transfer()); } else { Melder_throw ("The function \"fixed$\" requires two numbers (value and precision), not ", Stackel_whichText (value), " and ", Stackel_whichText (precision), "."); } } static void do_percentStr (void) { Stackel precision = pop, value = pop; if (value->which == Stackel_NUMBER && precision->which == Stackel_NUMBER) { autostring result = Melder_wcsdup (Melder_percent (value->content.number, precision->content.number)); pushString (result.transfer()); } else { Melder_throw ("The function \"percent$\" requires two numbers (value and precision), not ", Stackel_whichText (value), " and ", Stackel_whichText (precision), "."); } } static void do_deleteFile (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"deleteFile\" is not available inside manuals."); Stackel f = pop; if (f->which == Stackel_STRING) { structMelderFile file = { 0 }; Melder_relativePathToFile (f->content.string, & file); therror MelderFile_delete (& file); pushNumber (1); } else { Melder_throw ("The function \"deleteFile\" requires a string, not ", Stackel_whichText (f), "."); } } static void do_createDirectory (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"createDirectory\" is not available inside manuals."); Stackel f = pop; if (f->which == Stackel_STRING) { structMelderDir currentDirectory = { { 0 } }; Melder_getDefaultDir (& currentDirectory); #if defined (UNIX) || defined (macintosh) Melder_createDirectory (& currentDirectory, f->content.string, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH); therror #else Melder_createDirectory (& currentDirectory, f->content.string, 0); therror #endif pushNumber (1); } else { Melder_throw ("The function \"deleteFile\" requires a string, not ", Stackel_whichText (f), "."); } } static void do_variableExists (void) { Stackel f = pop; if (f->which == Stackel_STRING) { bool result = Interpreter_hasVariable (theInterpreter, f->content.string) != NULL; pushNumber (result); } else { Melder_throw ("The function \"variableExists\" requires a string, not ", Stackel_whichText (f), "."); } } static void do_beginPauseForm (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"beginPauseForm\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 1) { Stackel title = pop; if (title->which == Stackel_STRING) { UiPause_begin (theCurrentPraatApplication -> topShell, title->content.string, theInterpreter); } else { Melder_throw ("The function \"beginPauseForm\" requires a string (the title), not ", Stackel_whichText (title), "."); } } else { Melder_throw ("The function \"beginPauseForm\" requires 1 argument (a title), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddReal (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"real\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; const wchar *defaultString = NULL; if (defaultValue->which == Stackel_STRING) { defaultString = defaultValue->content.string; } else if (defaultValue->which == Stackel_NUMBER) { defaultString = Melder_double (defaultValue->content.number); } else { Melder_throw ("The second argument of \"real\" (the default value) must be a string or a number, not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_real (label->content.string, defaultString); } else { Melder_throw ("The first argument of \"real\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"real\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddPositive (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"positive\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; const wchar *defaultString = NULL; if (defaultValue->which == Stackel_STRING) { defaultString = defaultValue->content.string; } else if (defaultValue->which == Stackel_NUMBER) { defaultString = Melder_double (defaultValue->content.number); } else { Melder_throw ("The second argument of \"positive\" (the default value) must be a string or a number, not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_positive (label->content.string, defaultString); } else { Melder_throw ("The first argument of \"positive\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"positive\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddInteger (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"integer\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; const wchar *defaultString = NULL; if (defaultValue->which == Stackel_STRING) { defaultString = defaultValue->content.string; } else if (defaultValue->which == Stackel_NUMBER) { defaultString = Melder_double (defaultValue->content.number); } else { Melder_throw ("The second argument of \"integer\" (the default value) must be a string or a number, not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_integer (label->content.string, defaultString); } else { Melder_throw ("The first argument of \"integer\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"integer\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddNatural (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"natural\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; const wchar *defaultString = NULL; if (defaultValue->which == Stackel_STRING) { defaultString = defaultValue->content.string; } else if (defaultValue->which == Stackel_NUMBER) { defaultString = Melder_double (defaultValue->content.number); } else { Melder_throw ("The second argument of \"natural\" (the default value) must be a string or a number, not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_natural (label->content.string, defaultString); } else { Melder_throw ("The first argument of \"natural\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"natural\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddWord (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"word\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; if (defaultValue->which != Stackel_STRING) { Melder_throw ("The second argument of \"word\" (the default value) must be a string, not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_word (label->content.string, defaultValue->content.string); } else { Melder_throw ("The first argument of \"word\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"word\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddSentence (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"sentence\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; if (defaultValue->which != Stackel_STRING) { Melder_throw ("The second argument of \"sentence\" (the default value) must be a string, not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_sentence (label->content.string, defaultValue->content.string); } else { Melder_throw ("The first argument of \"sentence\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"sentence\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddText (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"text\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; if (defaultValue->which != Stackel_STRING) { Melder_throw ("The second argument of \"text\" (the default value) must be a string, not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_text (label->content.string, defaultValue->content.string); } else { Melder_throw ("The first argument of \"text\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"text\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddBoolean (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"boolean\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; if (defaultValue->which != Stackel_NUMBER) { Melder_throw ("The second argument of \"boolean\" (the default value) must be a number (0 or 1), not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_boolean (label->content.string, defaultValue->content.number); } else { Melder_throw ("The first argument of \"boolean\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"boolean\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddChoice (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"choice\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; if (defaultValue->which != Stackel_NUMBER) { Melder_throw ("The second argument of \"choice\" (the default value) must be a whole number, not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_choice (label->content.string, defaultValue->content.number); } else { Melder_throw ("The first argument of \"choice\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"choice\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddOptionMenu (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"optionMenu\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 2) { Stackel defaultValue = pop; if (defaultValue->which != Stackel_NUMBER) { Melder_throw ("The second argument of \"optionMenu\" (the default value) must be a whole number, not ", Stackel_whichText (defaultValue), "."); } Stackel label = pop; if (label->which == Stackel_STRING) { UiPause_optionMenu (label->content.string, defaultValue->content.number); } else { Melder_throw ("The first argument of \"optionMenu\" (the label) must be a string, not ", Stackel_whichText (label), "."); } } else { Melder_throw ("The function \"optionMenu\" requires 2 arguments (a label and a default value), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddOption (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"option\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 1) { Stackel text = pop; if (text->which == Stackel_STRING) { UiPause_option (text->content.string); } else { Melder_throw ("The argument of \"option\" must be a string (the text), not ", Stackel_whichText (text), "."); } } else { Melder_throw ("The function \"option\" requires 1 argument (a text), not ", n->content.number, "."); } pushNumber (1); } static void do_pauseFormAddComment (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"comment\" is not available inside manuals."); Stackel n = pop; if (n->content.number == 1) { Stackel text = pop; if (text->which == Stackel_STRING) { UiPause_comment (text->content.string); } else { Melder_throw ("The argument of \"comment\" must be a string (the text), not ", Stackel_whichText (text), "."); } } else { Melder_throw ("The function \"comment\" requires 1 argument (a text), not ", n->content.number, "."); } pushNumber (1); } static void do_endPauseForm (void) { if (theCurrentPraatObjects != & theForegroundPraatObjects) Melder_throw ("The function \"endPause\" is not available inside manuals."); Stackel n = pop; if (n->content.number < 2 || n->content.number > 12) Melder_throw ("The function \"endPause\" requires 2 to 12 arguments, not ", n->content.number, "."); Stackel d = pop; if (d->which != Stackel_NUMBER) Melder_throw ("The last argument of \"endPause\" has to be a number (the default or cancel continue button), not ", Stackel_whichText (d), "."); int numberOfContinueButtons = n->content.number - 1; int cancelContinueButton = 0, defaultContinueButton = d->content.number; Stackel ca = pop; if (ca->which == Stackel_NUMBER) { cancelContinueButton = defaultContinueButton; defaultContinueButton = ca->content.number; numberOfContinueButtons --; if (cancelContinueButton < 1 || cancelContinueButton > numberOfContinueButtons) Melder_throw ("Your last argument of \"endPause\" is the number of the cancel button; it cannot be ", cancelContinueButton, " but has to lie between 1 and ", numberOfContinueButtons, "."); } Stackel co [1+10] = { 0 }; for (int i = numberOfContinueButtons; i >= 1; i --) { co [i] = cancelContinueButton != 0 || i != numberOfContinueButtons ? pop : ca; if (co[i]->which != Stackel_STRING) Melder_throw ("Each of the first ", numberOfContinueButtons, " argument(s) of \"endPause\" has to be a string (a button text), not ", Stackel_whichText (co[i]), "."); } int buttonClicked = UiPause_end (numberOfContinueButtons, defaultContinueButton, cancelContinueButton, co [1] == NULL ? NULL : co[1]->content.string, co [2] == NULL ? NULL : co[2]->content.string, co [3] == NULL ? NULL : co[3]->content.string, co [4] == NULL ? NULL : co[4]->content.string, co [5] == NULL ? NULL : co[5]->content.string, co [6] == NULL ? NULL : co[6]->content.string, co [7] == NULL ? NULL : co[7]->content.string, co [8] == NULL ? NULL : co[8]->content.string, co [9] == NULL ? NULL : co[9]->content.string, co [10] == NULL ? NULL : co[10]->content.string, theInterpreter); therror //Melder_casual ("Button %d", buttonClicked); pushNumber (buttonClicked); } static void do_chooseReadFileStr (void) { Stackel n = pop; if (n->content.number == 1) { Stackel title = pop; if (title->which == Stackel_STRING) { autoSortedSetOfString fileNames = GuiFileSelect_getInfileNames (NULL, title->content.string, false); if (fileNames -> size == 0) { autostring result = Melder_wcsdup (L""); pushString (result.transfer()); } else { SimpleString fileName = (SimpleString) fileNames -> item [1]; autostring result = Melder_wcsdup (fileName -> string); pushString (result.transfer()); } } else { Melder_throw ("The argument of \"chooseReadFile$\" must be a string (the title), not ", Stackel_whichText (title), "."); } } else { Melder_throw ("The function \"chooseReadFile$\" requires 1 argument (a title), not ", n->content.number, "."); } } static void do_chooseWriteFileStr (void) { Stackel n = pop; if (n->content.number == 2) { Stackel defaultName = pop, title = pop; if (title->which == Stackel_STRING && defaultName->which == Stackel_STRING) { autostring result = GuiFileSelect_getOutfileName (NULL, title->content.string, defaultName->content.string); if (result.peek() == NULL) { result.reset (Melder_wcsdup (L"")); } pushString (result.transfer()); } else { Melder_throw ("The arguments of \"chooseWriteFile$\" must be two strings (the title and the default name)."); } } else { Melder_throw ("The function \"chooseWriteFile$\" requires 2 arguments (a title and a default name), not ", n->content.number, "."); } } static void do_chooseDirectoryStr (void) { Stackel n = pop; if (n->content.number == 1) { Stackel title = pop; if (title->which == Stackel_STRING) { autostring result = GuiFileSelect_getDirectoryName (NULL, title->content.string); if (result.peek() == NULL) { result.reset (Melder_wcsdup (L"")); } pushString (result.transfer()); } else { Melder_throw ("The argument of \"chooseDirectory$\" must be a string (the title)."); } } else { Melder_throw ("The function \"chooseDirectory$\" requires 1 argument (a title), not ", n->content.number, "."); } } static void do_demoWindowTitle (void) { Stackel n = pop; if (n->content.number == 1) { Stackel title = pop; if (title->which == Stackel_STRING) { Demo_windowTitle (title->content.string); therror } else { Melder_throw ("The argument of \"demoWindowTitle\" must be a string (the title), not ", Stackel_whichText (title), "."); } } else { Melder_throw ("The function \"demoWindowTitle\" requires 1 argument (a title), not ", Melder_integer (n->content.number), "."); } pushNumber (1); } static void do_demoShow (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoShow\" requires 0 arguments, not ", n->content.number, "."); Demo_show (); therror pushNumber (1); } static void do_demoWaitForInput (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoWaitForInput\" requires 0 arguments, not ", n->content.number, "."); Demo_waitForInput (theInterpreter); therror pushNumber (1); } static void do_demoInput (void) { Stackel n = pop; if (n->content.number == 1) { Stackel keys = pop; if (keys->which == Stackel_STRING) { bool result = Demo_input (keys->content.string); therror pushNumber (result); } else { Melder_throw ("The argument of \"demoInput\" must be a string (the keys), not ", Stackel_whichText (keys), "."); } } else { Melder_throw ("The function \"demoInput\" requires 1 argument (keys), not ", n->content.number, "."); } } static void do_demoClickedIn (void) { Stackel n = pop; if (n->content.number == 4) { Stackel top = pop, bottom = pop, right = pop, left = pop; if (left->which == Stackel_NUMBER && right->which == Stackel_NUMBER && bottom->which == Stackel_NUMBER && top->which == Stackel_NUMBER) { bool result = Demo_clickedIn (left->content.number, right->content.number, bottom->content.number, top->content.number); therror pushNumber (result); } else { Melder_throw ("All arguments of \"demoClickedIn\" must be numbers (the x and y ranges)."); } } else { Melder_throw ("The function \"demoClickedIn\" requires 4 arguments (x and y ranges), not ", n->content.number, "."); } } static void do_demoClicked (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoClicked\" requires 0 arguments, not ", n->content.number, "."); bool result = Demo_clicked (); therror pushNumber (result); } static void do_demoX (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoX\" requires 0 arguments, not ", n->content.number, "."); double result = Demo_x (); therror pushNumber (result); } static void do_demoY (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoY\" requires 0 arguments, not ", n->content.number, L"."); double result = Demo_y (); therror pushNumber (result); } static void do_demoKeyPressed (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoKeyPressed\" requires 0 arguments, not ", n->content.number, "."); bool result = Demo_keyPressed (); therror pushNumber (result); } static void do_demoKey (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoKey\" requires 0 arguments, not ", n->content.number, "."); autostring key = Melder_malloc (wchar, 2); key [0] = Demo_key (); therror key [1] = '\0'; pushString (key.transfer()); } static void do_demoShiftKeyPressed (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoShiftKeyPressed\" requires 0 arguments, not ", n->content.number, "."); bool result = Demo_shiftKeyPressed (); therror pushNumber (result); } static void do_demoCommandKeyPressed (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoCommandKeyPressed\" requires 0 arguments, not ", n->content.number, "."); bool result = Demo_commandKeyPressed (); therror pushNumber (result); } static void do_demoOptionKeyPressed (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoOptionKeyPressed\" requires 0 arguments, not ", n->content.number, "."); bool result = Demo_optionKeyPressed (); therror pushNumber (result); } static void do_demoExtraControlKeyPressed (void) { Stackel n = pop; if (n->content.number != 0) Melder_throw ("The function \"demoControlKeyPressed\" requires 0 arguments, not ", n->content.number, "."); bool result = Demo_extraControlKeyPressed (); therror pushNumber (result); } static long Stackel_getRowNumber (Stackel row, Data thee) { long result = 0; if (row->which == Stackel_NUMBER) { result = floor (row->content.number + 0.5); // round } else if (row->which == Stackel_STRING) { if (! thy v_hasGetRowIndex ()) Melder_throw ("Objects of type ", Thing_className (thee), " do not have row labels, so row indexes have to be numbers."); result = thy v_getRowIndex (row->content.string); if (result == 0) Melder_throw ("Object \"", thy name, "\" has no row labelled \"", row->content.string, "\"."); } else { Melder_throw ("A row index should be a number or a string, not ", Stackel_whichText (row), "."); } return result; } static long Stackel_getColumnNumber (Stackel column, Data thee) { long result = 0; if (column->which == Stackel_NUMBER) { result = floor (column->content.number + 0.5); // round } else if (column->which == Stackel_STRING) { if (! thy v_hasGetColIndex ()) Melder_throw ("Objects of type ", Thing_className (thee), " do not have column labels, so column indexes have to be numbers."); result = thy v_getColIndex (column->content.string); if (result == 0) Melder_throw ("Object \"", thy name, "\" has no column labelled \"", column->content.string, "\"."); } else { Melder_throw ("A column index should be a number or a string, not ", Stackel_whichText (column), "."); } return result; } static void do_self0 (long irow, long icol) { Data me = theSource; if (me == NULL) Melder_throw ("The name \"self\" is restricted to formulas for objects."); if (my v_hasGetCell ()) { pushNumber (my v_getCell ()); } else if (my v_hasGetVector ()) { if (icol == 0) { Melder_throw ("We are not in a loop, hence no implicit column index for the current ", Thing_className (me), " object (self).\nTry using the [column] index explicitly."); } else { pushNumber (my v_getVector (irow, icol)); } } else if (my v_hasGetMatrix ()) { if (irow == 0) { if (icol == 0) { Melder_throw ("We are not in a loop over rows and columns,\n" "hence no implicit row and column indexing for the current ", Thing_className (me), " object (self).\n" "Try using both [row, column] indexes explicitly."); } else { Melder_throw ("We are not in a loop over columns only,\n" "hence no implicit row index for the current ", Thing_className (me), " object (self).\n" "Try using the [row] index explicitly."); } } else { pushNumber (my v_getMatrix (irow, icol)); } } else { Melder_throw (Thing_className (me), " objects (like self) accept no [] indexing."); } } static void do_selfStr0 (long irow, long icol) { Data me = theSource; if (me == NULL) Melder_throw ("The name \"self$\" is restricted to formulas for objects."); if (my v_hasGetCellStr ()) { autostring result = Melder_wcsdup (my v_getCellStr ()); pushString (result.transfer()); } else if (my v_hasGetVectorStr ()) { if (icol == 0) { Melder_throw ("We are not in a loop, hence no implicit column index for the current ", Thing_className (me), " object (self).\nTry using the [column] index explicitly."); } else { autostring result = Melder_wcsdup (my v_getVectorStr (icol)); pushString (result.transfer()); } } else if (my v_hasGetMatrixStr ()) { if (irow == 0) { if (icol == 0) { Melder_throw ("We are not in a loop over rows and columns,\n" "hence no implicit row and column indexing for the current ", Thing_className (me), " object (self).\n" "Try using both [row, column] indexes explicitly."); } else { Melder_throw ("We are not in a loop over columns only,\n" "hence no implicit row index for the current ", Thing_className (me), " object (self).\n" "Try using the [row] index explicitly."); } } else { autostring result = Melder_wcsdup (my v_getMatrixStr (irow, icol)); pushString (result.transfer()); } } else { Melder_throw (Thing_className (me), " objects (like self) accept no [] indexing."); } } static Data getObjectFromUniqueID (Stackel object) { Data thee = NULL; if (object->which == Stackel_NUMBER) { int i = theCurrentPraatObjects -> n; while (i > 0 && object->content.number != theCurrentPraatObjects -> list [i]. id) i --; if (i == 0) { Melder_throw ("No such object: ", object->content.number); } thee = (Data) theCurrentPraatObjects -> list [i]. object; } else if (object->which == Stackel_STRING) { int i = theCurrentPraatObjects -> n; while (i > 0 && ! Melder_wcsequ (object->content.string, theCurrentPraatObjects -> list [i]. name)) i --; if (i == 0) { Melder_throw ("No such object: ", object->content.string); } thee = (Data) theCurrentPraatObjects -> list [i]. object; } else { Melder_throw ("The first argument to \"object\" must be a number (unique ID) or a string (name), not ", Stackel_whichText (object), "."); } return thee; } static void do_objectCell0 (long irow, long icol) { Data thee = getObjectFromUniqueID (pop); if (thy v_hasGetCell ()) { pushNumber (thy v_getCell ()); } else if (thy v_hasGetVector ()) { if (icol == 0) { Melder_throw ("We are not in a loop,\n" "hence no implicit column index for this ", Thing_className (thee), " object.\n" "Try using: object [id, column]."); } else { pushNumber (thy v_getVector (irow, icol)); } } else if (thy v_hasGetMatrix ()) { if (irow == 0) { if (icol == 0) { Melder_throw ("We are not in a loop over rows and columns,\n" "hence no implicit row and column indexing for this ", Thing_className (thee), " object.\n" "Try using: object [id, row, column]."); } else { Melder_throw ("We are not in a loop over columns only,\n" "hence no implicit row index for this ", Thing_className (thee), " object.\n" "Try using: object [id, row]."); } } else { pushNumber (thy v_getMatrix (irow, icol)); } } else { Melder_throw (Thing_className (thee), " objects accept no [] indexing."); } } static void do_matriks0 (long irow, long icol) { Data thee = parse [programPointer]. content.object; if (thy v_hasGetCell ()) { pushNumber (thy v_getCell ()); } else if (thy v_hasGetVector ()) { if (icol == 0) { Melder_throw ("We are not in a loop,\n" "hence no implicit column index for this ", Thing_className (thee), " object.\n" "Try using the [column] index explicitly."); } else { pushNumber (thy v_getVector (irow, icol)); } } else if (thy v_hasGetMatrix ()) { if (irow == 0) { if (icol == 0) { Melder_throw ("We are not in a loop over rows and columns,\n" "hence no implicit row and column indexing for this ", Thing_className (thee), " object.\n" "Try using both [row, column] indexes explicitly."); } else { Melder_throw ("We are not in a loop over columns only,\n" "hence no implicit row index for this ", Thing_className (thee), " object.\n" "Try using the [row] index explicitly."); } } else { pushNumber (thy v_getMatrix (irow, icol)); } } else { Melder_throw (Thing_className (thee), " objects accept no [] indexing."); } } static void do_selfMatriks1 (long irow) { Data me = theSource; Stackel column = pop; if (me == NULL) Melder_throw ("The name \"self\" is restricted to formulas for objects."); long icol = Stackel_getColumnNumber (column, me); if (my v_hasGetVector ()) { pushNumber (my v_getVector (irow, icol)); } else if (my v_hasGetMatrix ()) { if (irow == 0) { Melder_throw ("We are not in a loop,\n" "hence no implicit row index for the current ", Thing_className (me), " object (self).\n" "Try using both [row, column] indexes instead."); } else { pushNumber (my v_getMatrix (irow, icol)); } } else { Melder_throw (Thing_className (me), " objects (like self) accept no [column] indexes."); } } static void do_selfMatriksStr1 (long irow) { Data me = theSource; Stackel column = pop; if (me == NULL) Melder_throw ("The name \"self$\" is restricted to formulas for objects."); long icol = Stackel_getColumnNumber (column, me); if (my v_hasGetVectorStr ()) { autostring result = Melder_wcsdup (my v_getVectorStr (icol)); pushString (result.transfer()); } else if (my v_hasGetMatrixStr ()) { if (irow == 0) { Melder_throw ("We are not in a loop,\n" "hence no implicit row index for the current ", Thing_className (me), " object (self).\n" "Try using both [row, column] indexes instead."); } else { autostring result = Melder_wcsdup (my v_getMatrixStr (irow, icol)); pushString (result.transfer()); } } else { Melder_throw (Thing_className (me), " objects (like self) accept no [column] indexes."); } } static void do_objectCell1 (long irow) { Stackel column = pop; Data thee = getObjectFromUniqueID (pop); long icol = Stackel_getColumnNumber (column, thee); if (thy v_hasGetVector ()) { pushNumber (thy v_getVector (irow, icol)); } else if (thy v_hasGetMatrix ()) { if (irow == 0) { Melder_throw ("We are not in a loop,\n" "hence no implicit row index for this ", Thing_className (thee), " object.\n" "Try using: object [id, row, column]."); } else { pushNumber (thy v_getMatrix (irow, icol)); } } else { Melder_throw (Thing_className (thee), " objects accept no [column] indexes."); } } static void do_matriks1 (long irow) { Data thee = parse [programPointer]. content.object; Stackel column = pop; long icol = Stackel_getColumnNumber (column, thee); if (thy v_hasGetVector ()) { pushNumber (thy v_getVector (irow, icol)); } else if (thy v_hasGetMatrix ()) { if (irow == 0) { Melder_throw ("We are not in a loop,\n" "hence no implicit row index for this ", Thing_className (thee), " object.\n" "Try using both [row, column] indexes instead."); } else { pushNumber (thy v_getMatrix (irow, icol)); } } else { Melder_throw (Thing_className (thee), " objects accept no [column] indexes."); } } static void do_objectCellStr1 (long irow) { Stackel column = pop; Data thee = getObjectFromUniqueID (pop); long icol = Stackel_getColumnNumber (column, thee); if (thy v_hasGetVectorStr ()) { autostring result = Melder_wcsdup (thy v_getVectorStr (icol)); pushString (result.transfer()); } else if (thy v_hasGetMatrixStr ()) { if (irow == 0) { Melder_throw ("We are not in a loop,\n" "hence no implicit row index for this ", Thing_className (thee), " object.\n" "Try using: object [id, row, column]."); } else { autostring result = Melder_wcsdup (thy v_getMatrixStr (irow, icol)); pushString (result.transfer()); } } else { Melder_throw (Thing_className (thee), " objects accept no [column] indexes for string cells."); } } static void do_matrixStr1 (long irow) { Data thee = parse [programPointer]. content.object; Stackel column = pop; long icol = Stackel_getColumnNumber (column, thee); if (thy v_hasGetVectorStr ()) { autostring result = Melder_wcsdup (thy v_getVectorStr (icol)); pushString (result.transfer()); } else if (thy v_hasGetMatrixStr ()) { if (irow == 0) { Melder_throw ("We are not in a loop,\n" "hence no implicit row index for this ", Thing_className (thee), " object.\n" "Try using both [row, column] indexes instead."); } else { autostring result = Melder_wcsdup (thy v_getMatrixStr (irow, icol)); pushString (result.transfer()); } } else { Melder_throw (Thing_className (thee), " objects accept no [column] indexes for string cells."); } } static void do_selfMatriks2 (void) { Data me = theSource; Stackel column = pop, row = pop; if (me == NULL) Melder_throw ("The name \"self\" is restricted to formulas for objects."); long irow = Stackel_getRowNumber (row, me); long icol = Stackel_getColumnNumber (column, me); if (! my v_hasGetMatrix ()) Melder_throw (Thing_className (me), " objects like \"self\" accept no [row, column] indexing."); pushNumber (my v_getMatrix (irow, icol)); } static void do_selfMatriksStr2 (void) { Data me = theSource; Stackel column = pop, row = pop; if (me == NULL) Melder_throw ("The name \"self$\" is restricted to formulas for objects."); long irow = Stackel_getRowNumber (row, me); long icol = Stackel_getColumnNumber (column, me); if (! my v_hasGetMatrixStr ()) Melder_throw (Thing_className (me), " objects like \"self$\" accept no [row, column] indexing for string cells."); autostring result = Melder_wcsdup (my v_getMatrixStr (irow, icol)); pushString (result.transfer()); } static void do_objectCell2 (void) { Stackel column = pop, row = pop; Data thee = getObjectFromUniqueID (pop); long irow = Stackel_getRowNumber (row, thee); long icol = Stackel_getColumnNumber (column, thee); if (! thy v_hasGetMatrix ()) Melder_throw (Thing_className (thee), " objects accept no [id, row, column] indexing."); pushNumber (thy v_getMatrix (irow, icol)); } static void do_matriks2 (void) { Data thee = parse [programPointer]. content.object; Stackel column = pop, row = pop; long irow = Stackel_getRowNumber (row, thee); long icol = Stackel_getColumnNumber (column, thee); if (! thy v_hasGetMatrix ()) Melder_throw (Thing_className (thee), " objects accept no [row, column] indexing."); pushNumber (thy v_getMatrix (irow, icol)); } static void do_objectCellStr2 (void) { Stackel column = pop, row = pop; Data thee = getObjectFromUniqueID (pop); long irow = Stackel_getRowNumber (row, thee); long icol = Stackel_getColumnNumber (column, thee); if (! thy v_hasGetMatrixStr ()) Melder_throw (Thing_className (thee), " objects accept no [id, row, column] indexing for string cells."); autostring result = Melder_wcsdup (thy v_getMatrixStr (irow, icol)); pushString (result.transfer()); } static void do_matriksStr2 (void) { Data thee = parse [programPointer]. content.object; Stackel column = pop, row = pop; long irow = Stackel_getRowNumber (row, thee); long icol = Stackel_getColumnNumber (column, thee); if (! thy v_hasGetMatrixStr ()) Melder_throw (Thing_className (thee), " objects accept no [row, column] indexing for string cells."); autostring result = Melder_wcsdup (thy v_getMatrixStr (irow, icol)); pushString (result.transfer()); } static void do_objectLocation0 (long irow, long icol) { Data thee = getObjectFromUniqueID (pop); if (thy v_hasGetFunction0 ()) { pushNumber (thy v_getFunction0 ()); } else if (thy v_hasGetFunction1 ()) { Data me = theSource; if (me == NULL) Melder_throw ("No current object (we are not in a Formula command),\n" "hence no implicit x value for this ", Thing_className (thee), " object.\n" "Try using: object (id, x)."); if (! my v_hasGetX ()) Melder_throw ("The current ", Thing_className (me), " object gives no implicit x values,\nhence no implicit x value for this ", Thing_className (thee), " object.\n" "Try using: object (id, x)."); double x = my v_getX (icol); pushNumber (thy v_getFunction1 (irow, x)); } else if (thy v_hasGetFunction2 ()) { Data me = theSource; if (me == NULL) Melder_throw ("No current object (we are not in a Formula command),\n" "hence no implicit x or y values for this ", Thing_className (thee), " object.\n" "Try using: object (id, x, y)."); if (! my v_hasGetX ()) Melder_throw ("The current ", Thing_className (me), " object gives no implicit x values,\n" "hence no implicit x value for this ", Thing_className (thee), " object.\n" "Try using: object (id, x, y)."); double x = my v_getX (icol); if (! my v_hasGetY ()) Melder_throw ("The current ", Thing_className (me), L" object gives no implicit y values,\n" "hence no implicit y value for this ", Thing_className (thee), " object.\n" "Try using: object (id, y)."); double y = my v_getY (irow); pushNumber (thy v_getFunction2 (x, y)); } else { Melder_throw (Thing_className (thee), " objects accept no () values."); } } static void do_funktie0 (long irow, long icol) { Data thee = parse [programPointer]. content.object; if (thy v_hasGetFunction0 ()) { pushNumber (thy v_getFunction0 ()); } else if (thy v_hasGetFunction1 ()) { Data me = theSource; if (me == NULL) Melder_throw ("No current object (we are not in a Formula command),\n" "hence no implicit x value for this ", Thing_className (thee), " object.\n" "Try using the (x) argument explicitly."); if (! my v_hasGetX ()) Melder_throw ("The current ", Thing_className (me), " object gives no implicit x values,\nhence no implicit x value for this ", Thing_className (thee), " object.\n" "Try using the (x) argument explicitly."); double x = my v_getX (icol); pushNumber (thy v_getFunction1 (irow, x)); } else if (thy v_hasGetFunction2 ()) { Data me = theSource; if (me == NULL) Melder_throw ("No current object (we are not in a Formula command),\n" "hence no implicit x or y values for this ", Thing_className (thee), " object.\n" "Try using both (x, y) arguments explicitly."); if (! my v_hasGetX ()) Melder_throw ("The current ", Thing_className (me), " object gives no implicit x values,\n" "hence no implicit x value for this ", Thing_className (thee), " object.\n" "Try using both (x, y) arguments explicitly."); double x = my v_getX (icol); if (! my v_hasGetY ()) Melder_throw ("The current ", Thing_className (me), " object gives no implicit y values,\n" "hence no implicit y value for this ", Thing_className (thee), " object.\n" "Try using the (y) argument explicitly."); double y = my v_getY (irow); pushNumber (thy v_getFunction2 (x, y)); } else { Melder_throw (Thing_className (thee), " objects accept no () values."); } } static void do_selfFunktie1 (long irow) { Data me = theSource; Stackel x = pop; if (x->which == Stackel_NUMBER) { if (me == NULL) Melder_throw ("The name \"self\" is restricted to formulas for objects."); if (my v_hasGetFunction1 ()) { pushNumber (my v_getFunction1 (irow, x->content.number)); } else if (my v_hasGetFunction2 ()) { if (! my v_hasGetY ()) Melder_throw ("The current ", Thing_className (me), " object (self) accepts no implicit y values.\n" "Try using both (x, y) arguments instead."); double y = my v_getY (irow); pushNumber (my v_getFunction2 (x->content.number, y)); } else { Melder_throw (Thing_className (me), " objects like \"self\" accept no (x) values."); } } else { Melder_throw (Thing_className (me), " objects like \"self\" accept only numeric x values."); } } static void do_objectLocation1 (long irow) { Stackel x = pop; Data thee = getObjectFromUniqueID (pop); if (x->which == Stackel_NUMBER) { if (thy v_hasGetFunction1 ()) { pushNumber (thy v_getFunction1 (irow, x->content.number)); } else if (thy v_hasGetFunction2 ()) { Data me = theSource; if (me == NULL) Melder_throw ("No current object (we are not in a Formula command),\n" "hence no implicit y value for this ", Thing_className (thee), " object.\n" "Try using: object (id, x, y)."); if (! my v_hasGetY ()) Melder_throw ("The current ", Thing_className (me), " object gives no implicit y values,\n" "hence no implicit y value for this ", Thing_className (thee), " object.\n" "Try using: object (id, x, y)."); double y = my v_getY (irow); pushNumber (thy v_getFunction2 (x->content.number, y)); } else { Melder_throw (Thing_className (thee), " objects accept no (x) values."); } } else { Melder_throw (Thing_className (thee), " objects accept only numeric x values."); } } static void do_funktie1 (long irow) { Data thee = parse [programPointer]. content.object; Stackel x = pop; if (x->which == Stackel_NUMBER) { if (thy v_hasGetFunction1 ()) { pushNumber (thy v_getFunction1 (irow, x->content.number)); } else if (thy v_hasGetFunction2 ()) { Data me = theSource; if (me == NULL) Melder_throw ("No current object (we are not in a Formula command),\n" "hence no implicit y value for this ", Thing_className (thee), " object.\n" "Try using both (x, y) arguments instead."); if (! my v_hasGetY ()) Melder_throw ("The current ", Thing_className (me), " object gives no implicit y values,\n" "hence no implicit y value for this ", Thing_className (thee), " object.\n" "Try using both (x, y) arguments instead."); double y = my v_getY (irow); pushNumber (thy v_getFunction2 (x->content.number, y)); } else { Melder_throw (Thing_className (thee), " objects accept no (x) values."); } } else { Melder_throw (Thing_className (thee), " objects accept only numeric x values."); } } static void do_selfFunktie2 (void) { Data me = theSource; Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { if (me == NULL) Melder_throw ("The name \"self\" is restricted to formulas for objects."); if (! my v_hasGetFunction2 ()) Melder_throw (Thing_className (me), " objects like \"self\" accept no (x, y) values."); pushNumber (my v_getFunction2 (x->content.number, y->content.number)); } else { Melder_throw (Thing_className (me), " objects accept only numeric x values."); } } static void do_objectLocation2 (void) { Stackel y = pop, x = pop; Data thee = getObjectFromUniqueID (pop); if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { if (! thy v_hasGetFunction2 ()) Melder_throw (Thing_className (thee), " objects accept no (x, y) values."); pushNumber (thy v_getFunction2 (x->content.number, y->content.number)); } else { Melder_throw (Thing_className (thee), " objects accept only numeric x values."); } } static void do_funktie2 (void) { Data thee = parse [programPointer]. content.object; Stackel y = pop, x = pop; if (x->which == Stackel_NUMBER && y->which == Stackel_NUMBER) { if (! thy v_hasGetFunction2 ()) Melder_throw (Thing_className (thee), " objects accept no (x, y) values."); pushNumber (thy v_getFunction2 (x->content.number, y->content.number)); } else { Melder_throw (Thing_className (thee), " objects accept only numeric x values."); } } static void do_rowStr (void) { Data thee = parse [programPointer]. content.object; Stackel row = pop; long irow = Stackel_getRowNumber (row, thee); autostring result = Melder_wcsdup (thy v_getRowStr (irow)); if (result.peek() == NULL) Melder_throw ("Row index out of bounds."); pushString (result.transfer()); } static void do_colStr (void) { Data thee = parse [programPointer]. content.object; Stackel col = pop; long icol = Stackel_getColumnNumber (col, thee); autostring result = Melder_wcsdup (thy v_getColStr (icol)); if (result.peek() == NULL) Melder_throw ("Column index out of bounds."); pushString (result.transfer()); } static double NUMarcsinh (double x) { return log (x + sqrt (1.0 + x * x)); } static double NUMarccosh (double x) { return x < 1.0 ? NUMundefined : log (x + sqrt (x * x - 1.0)); } static double NUMarctanh (double x) { return x <= -1.0 || x >= 1.0 ? NUMundefined : 0.5 * log ((1.0 + x) / (1.0 - x)); } static double NUMerf (double x) { return 1.0 - NUMerfcc (x); } void Formula_run (long row, long col, struct Formula_Result *result) { FormulaInstruction f = parse; programPointer = 1; // first symbol of the program if (theStack == NULL) theStack = Melder_calloc_f (struct structStackel, 10000); if (theStack == NULL) Melder_throw ("Out of memory during formula computation."); w = 0, wmax = 0; // start new stack try { while (programPointer <= numberOfInstructions) { int symbol; switch (symbol = f [programPointer]. symbol) { case NUMBER_: { pushNumber (f [programPointer]. content.number); } break; case STOPWATCH_: { pushNumber (Melder_stopwatch ()); } break; case ROW_: { pushNumber (row); } break; case COL_: { pushNumber (col); } break; case X_: { Data me = theSource; if (! my v_hasGetX ()) Melder_throw ("No values for \"x\" for this object."); pushNumber (my v_getX (col)); } break; case Y_: { Data me = theSource; if (! my v_hasGetY ()) Melder_throw ("No values for \"y\" for this object."); pushNumber (my v_getY (row)); } break; case NOT_: { do_not (); } break; case EQ_: { do_eq (); } break; case NE_: { do_ne (); } break; case LE_: { do_le (); } break; case LT_: { do_lt (); } break; case GE_: { do_ge (); } break; case GT_: { do_gt (); } break; case ADD_: { do_add (); } break; case SUB_: { do_sub (); } break; case MUL_: { do_mul (); } break; case RDIV_: { do_rdiv (); } break; case IDIV_: { do_idiv (); } break; case MOD_: { do_mod (); } break; case MINUS_: { do_minus (); } break; case POWER_: { do_power (); /********** Functions of 1 numerical variable: **********/ } break; case ABS_: { do_abs (); } break; case ROUND_: { do_round (); } break; case FLOOR_: { do_floor (); } break; case CEILING_: { do_ceiling (); } break; case SQRT_: { do_sqrt (); } break; case SIN_: { do_sin (); } break; case COS_: { do_cos (); } break; case TAN_: { do_tan (); } break; case ARCSIN_: { do_arcsin (); } break; case ARCCOS_: { do_arccos (); } break; case ARCTAN_: { do_arctan (); } break; case SINC_: { do_function_n_n (NUMsinc); } break; case SINCPI_: { do_function_n_n (NUMsincpi); } break; case EXP_: { do_exp (); } break; case SINH_: { do_sinh (); } break; case COSH_: { do_cosh (); } break; case TANH_: { do_tanh (); } break; case ARCSINH_: { do_function_n_n (NUMarcsinh); } break; case ARCCOSH_: { do_function_n_n (NUMarccosh); } break; case ARCTANH_: { do_function_n_n (NUMarctanh); } break; case SIGMOID_: { do_function_n_n (NUMsigmoid); } break; case INV_SIGMOID_: { do_function_n_n (NUMinvSigmoid); } break; case ERF_: { do_function_n_n (NUMerf); } break; case ERFC_: { do_function_n_n (NUMerfcc); } break; case GAUSS_P_: { do_function_n_n (NUMgaussP); } break; case GAUSS_Q_: { do_function_n_n (NUMgaussQ); } break; case INV_GAUSS_Q_: { do_function_n_n (NUMinvGaussQ); } break; case RANDOM_POISSON_: { do_function_n_n (NUMrandomPoisson); } break; case LOG2_: { do_log2 (); } break; case LN_: { do_ln (); } break; case LOG10_: { do_log10 (); } break; case LN_GAMMA_: { do_function_n_n (NUMlnGamma); } break; case HERTZ_TO_BARK_: { do_function_n_n (NUMhertzToBark); } break; case BARK_TO_HERTZ_: { do_function_n_n (NUMbarkToHertz); } break; case PHON_TO_DIFFERENCE_LIMENS_: { do_function_n_n (NUMphonToDifferenceLimens); } break; case DIFFERENCE_LIMENS_TO_PHON_: { do_function_n_n (NUMdifferenceLimensToPhon); } break; case HERTZ_TO_MEL_: { do_function_n_n (NUMhertzToMel); } break; case MEL_TO_HERTZ_: { do_function_n_n (NUMmelToHertz); } break; case HERTZ_TO_SEMITONES_: { do_function_n_n (NUMhertzToSemitones); } break; case SEMITONES_TO_HERTZ_: { do_function_n_n (NUMsemitonesToHertz); } break; case ERB_: { do_function_n_n (NUMerb); } break; case HERTZ_TO_ERB_: { do_function_n_n (NUMhertzToErb); } break; case ERB_TO_HERTZ_: { do_function_n_n (NUMerbToHertz); /********** Functions of 2 numerical variables: **********/ } break; case ARCTAN2_: { do_function_dd_d (atan2); } break; case RANDOM_UNIFORM_: { do_function_dd_d (NUMrandomUniform); } break; case RANDOM_INTEGER_: { do_function_ll_l (NUMrandomInteger); } break; case RANDOM_GAUSS_: { do_function_dd_d (NUMrandomGauss); } break; case CHI_SQUARE_P_: { do_function_dd_d (NUMchiSquareP); } break; case CHI_SQUARE_Q_: { do_function_dd_d (NUMchiSquareQ); } break; case INCOMPLETE_GAMMAP_: { do_function_dd_d (NUMincompleteGammaP); } break; case INV_CHI_SQUARE_Q_: { do_function_dd_d (NUMinvChiSquareQ); } break; case STUDENT_P_: { do_function_dd_d (NUMstudentP); } break; case STUDENT_Q_: { do_function_dd_d (NUMstudentQ); } break; case INV_STUDENT_Q_: { do_function_dd_d (NUMinvStudentQ); } break; case BETA_: { do_function_dd_d (NUMbeta); } break; case BETA2_: { do_function_dd_d (NUMbeta2); } break; case BESSEL_I_: { do_function_ld_d (NUMbesselI); } break; case BESSEL_K_: { do_function_ld_d (NUMbesselK); } break; case LN_BETA_: { do_function_dd_d (NUMlnBeta); } break; case SOUND_PRESSURE_TO_PHON_: { do_function_dd_d (NUMsoundPressureToPhon); } break; case OBJECTS_ARE_IDENTICAL_: { do_objects_are_identical (); /********** Functions of 3 numerical variables: **********/ } break; case FISHER_P_: { do_function_ddd_d (NUMfisherP); } break; case FISHER_Q_: { do_function_ddd_d (NUMfisherQ); } break; case INV_FISHER_Q_: { do_function_ddd_d (NUMinvFisherQ); } break; case BINOMIAL_P_: { do_function_ddd_d (NUMbinomialP); } break; case BINOMIAL_Q_: { do_function_ddd_d (NUMbinomialQ); } break; case INCOMPLETE_BETA_: { do_function_ddd_d (NUMincompleteBeta); } break; case INV_BINOMIAL_P_: { do_function_ddd_d (NUMinvBinomialP); } break; case INV_BINOMIAL_Q_: { do_function_ddd_d (NUMinvBinomialQ); /********** Functions of a variable number of variables: **********/ } break; case MIN_: { do_min (); } break; case MAX_: { do_max (); } break; case IMIN_: { do_imin (); } break; case IMAX_: { do_imax (); } break; case ZERO_NUMAR_: { do_zeroNumar (); } break; case LINEAR_NUMAR_: { do_linearNumar (); } break; case RANDOM_UNIFORM_NUMAR_: { do_function_dd_d_numar (NUMrandomUniform); } break; case RANDOM_INTEGER_NUMAR_: { do_function_ll_l_numar (NUMrandomInteger); } break; case RANDOM_GAUSS_NUMAR_: { do_function_dd_d_numar (NUMrandomGauss); } break; case NUMBER_OF_ROWS_: { do_numberOfRows (); } break; case NUMBER_OF_COLUMNS_: { do_numberOfColumns (); /********** String functions: **********/ } break; case LENGTH_: { do_length (); } break; case FILE_READABLE_: { do_fileReadable (); } break; case DATESTR_: { do_dateStr (); } break; case LEFTSTR_: { do_leftStr (); } break; case RIGHTSTR_: { do_rightStr (); } break; case MIDSTR_: { do_midStr (); } break; case ENVIRONMENTSTR_: { do_environmentStr (); } break; case INDEX_: { do_index (); } break; case RINDEX_: { do_rindex (); } break; case STARTS_WITH_: { do_stringMatchesCriterion (kMelder_string_STARTS_WITH); } break; case ENDS_WITH_: { do_stringMatchesCriterion (kMelder_string_ENDS_WITH); } break; case REPLACESTR_: { do_replaceStr (); } break; case INDEX_REGEX_: { do_index_regex (FALSE); } break; case RINDEX_REGEX_: { do_index_regex (TRUE); } break; case REPLACE_REGEXSTR_: { do_replace_regexStr (); } break; case EXTRACT_NUMBER_: { do_extractNumber (); } break; case EXTRACT_WORDSTR_: { do_extractTextStr (TRUE); } break; case EXTRACT_LINESTR_: { do_extractTextStr (FALSE); } break; case SELECTED_: { do_selected (); } break; case SELECTEDSTR_: { do_selectedStr (); } break; case NUMBER_OF_SELECTED_: { do_numberOfSelected (); } break; case FIXEDSTR_: { do_fixedStr (); } break; case PERCENTSTR_: { do_percentStr (); } break; case DELETE_FILE_: { do_deleteFile (); } break; case CREATE_DIRECTORY_: { do_createDirectory (); } break; case VARIABLE_EXISTS_: { do_variableExists (); /********** Pause window functions: **********/ } break; case BEGIN_PAUSE_FORM_: { do_beginPauseForm (); } break; case PAUSE_FORM_ADD_REAL_: { do_pauseFormAddReal (); } break; case PAUSE_FORM_ADD_POSITIVE_: { do_pauseFormAddPositive (); } break; case PAUSE_FORM_ADD_INTEGER_: { do_pauseFormAddInteger (); } break; case PAUSE_FORM_ADD_NATURAL_: { do_pauseFormAddNatural (); } break; case PAUSE_FORM_ADD_WORD_: { do_pauseFormAddWord (); } break; case PAUSE_FORM_ADD_SENTENCE_: { do_pauseFormAddSentence (); } break; case PAUSE_FORM_ADD_TEXT_: { do_pauseFormAddText (); } break; case PAUSE_FORM_ADD_BOOLEAN_: { do_pauseFormAddBoolean (); } break; case PAUSE_FORM_ADD_CHOICE_: { do_pauseFormAddChoice (); } break; case PAUSE_FORM_ADD_OPTION_MENU_: { do_pauseFormAddOptionMenu (); } break; case PAUSE_FORM_ADD_OPTION_: { do_pauseFormAddOption (); } break; case PAUSE_FORM_ADD_COMMENT_: { do_pauseFormAddComment (); } break; case END_PAUSE_FORM_: { do_endPauseForm (); } break; case CHOOSE_READ_FILESTR_: { do_chooseReadFileStr (); } break; case CHOOSE_WRITE_FILESTR_: { do_chooseWriteFileStr (); } break; case CHOOSE_DIRECTORYSTR_: { do_chooseDirectoryStr (); /********** Demo window functions: **********/ } break; case DEMO_WINDOW_TITLE_: { do_demoWindowTitle (); } break; case DEMO_SHOW_: { do_demoShow (); } break; case DEMO_WAIT_FOR_INPUT_: { do_demoWaitForInput (); } break; case DEMO_INPUT_: { do_demoInput (); } break; case DEMO_CLICKED_IN_: { do_demoClickedIn (); } break; case DEMO_CLICKED_: { do_demoClicked (); } break; case DEMO_X_: { do_demoX (); } break; case DEMO_Y_: { do_demoY (); } break; case DEMO_KEY_PRESSED_: { do_demoKeyPressed (); } break; case DEMO_KEY_: { do_demoKey (); } break; case DEMO_SHIFT_KEY_PRESSED_: { do_demoShiftKeyPressed (); } break; case DEMO_COMMAND_KEY_PRESSED_: { do_demoCommandKeyPressed (); } break; case DEMO_OPTION_KEY_PRESSED_: { do_demoOptionKeyPressed (); } break; case DEMO_EXTRA_CONTROL_KEY_PRESSED_: { do_demoExtraControlKeyPressed (); /********** **********/ } break; case TRUE_: { pushNumber (1.0); } break; case FALSE_: { pushNumber (0.0); /* Possible compiler BUG: many compilers cannot handle the following assignment. */ /* Those compilers have trouble with praat's AND and OR. */ } break; case IFTRUE_: { Stackel condition = pop; if (condition->which == Stackel_NUMBER) { if (condition->content.number != 0.0) { programPointer = f [programPointer]. content.label - theOptimize; } } else { Melder_throw ("A condition between \"if\" and \"then\" has to be a number, not ", Stackel_whichText (condition), "."); } } break; case IFFALSE_: { Stackel condition = pop; if (condition->which == Stackel_NUMBER) { if (condition->content.number == 0.0) { programPointer = f [programPointer]. content.label - theOptimize; } } else { Melder_throw ("A condition between \"if\" and \"then\" has to be a number, not ", Stackel_whichText (condition), "."); } } break; case GOTO_: { programPointer = f [programPointer]. content.label - theOptimize; } break; case LABEL_: { ; } break; case DECREMENT_AND_ASSIGN_: { Stackel x = pop, v = pop; InterpreterVariable var = v->content.variable; var -> numericValue = x->content.number - 1.0; //Melder_casual ("starting value %f", var -> numericValue); pushVariable (var); } break; case INCREMENT_GREATER_GOTO_: { //Melder_casual ("top of loop, stack depth %d", w); Stackel e = & theStack [w], v = & theStack [w - 1]; Melder_assert (e->which == Stackel_NUMBER); Melder_assert (v->which == Stackel_VARIABLE); InterpreterVariable var = v->content.variable; //Melder_casual ("loop variable %f", var -> numericValue); var -> numericValue += 1.0; //Melder_casual ("loop variable %f", var -> numericValue); //Melder_casual ("end value %f", e->content.number); if (var -> numericValue > e->content.number) { programPointer = f [programPointer]. content.label - theOptimize; } } break; case ADD_3DOWN_: { Stackel x = pop, s = & theStack [w - 2]; Melder_assert (x->which == Stackel_NUMBER); Melder_assert (s->which == Stackel_NUMBER); //Melder_casual ("to add %f", x->content.number); s->content.number += x->content.number; //Melder_casual ("sum %f", s->content.number); } break; case POP_2_: { w -= 2; //Melder_casual ("total %f", theStack[w].content.number); } break; case NUMERIC_ARRAY_ELEMENT_: { do_numericArrayElement (); } break; case INDEXED_NUMERIC_VARIABLE_: { do_indexedNumericVariable (); } break; case INDEXED_STRING_VARIABLE_: { do_indexedStringVariable (); } break; case VARIABLE_REFERENCE_: { InterpreterVariable var = f [programPointer]. content.variable; pushVariable (var); } break; case SELF0_: { do_self0 (row, col); } break; case SELFSTR0_: { do_selfStr0 (row, col); } break; case SELFMATRIKS1_: { do_selfMatriks1 (row); } break; case SELFMATRIKSSTR1_: { do_selfMatriksStr1 (row); } break; case SELFMATRIKS2_: { do_selfMatriks2 (); } break; case SELFMATRIKSSTR2_: { do_selfMatriksStr2 (); } break; case SELFFUNKTIE1_: { do_selfFunktie1 (row); } break; case SELFFUNKTIE2_: { do_selfFunktie2 (); } break; case OBJECTCELL0_: { do_objectCell0 (row, col); } break; case OBJECTCELL1_: { do_objectCell1 (row); } break; case OBJECTCELLSTR1_: { do_objectCellStr1 (row); } break; case OBJECTCELL2_: { do_objectCell2 (); } break; case OBJECTCELLSTR2_: { do_objectCellStr2 (); } break; case OBJECTLOCATION0_: { do_objectLocation0 (row, col); } break; case OBJECTLOCATION1_: { do_objectLocation1 (row); } break; case OBJECTLOCATION2_: { do_objectLocation2 (); } break; case MATRIKS0_: { do_matriks0 (row, col); } break; case MATRIKS1_: { do_matriks1 (row); } break; case MATRIKSSTR1_: { do_matrixStr1 (row); } break; case MATRIKS2_: { do_matriks2 (); } break; case MATRIKSSTR2_: { do_matriksStr2 (); } break; case FUNKTIE0_: { do_funktie0 (row, col); } break; case FUNKTIE1_: { do_funktie1 (row); } break; case FUNKTIE2_: { do_funktie2 (); } break; case ROWSTR_: { do_rowStr (); } break; case COLSTR_: { do_colStr (); } break; case SQR_: { do_sqr (); } break; case STRING_: { autostring string = Melder_wcsdup (f [programPointer]. content.string); pushString (string.transfer()); } break; case NUMERIC_VARIABLE_: { InterpreterVariable var = f [programPointer]. content.variable; pushNumber (var -> numericValue); } break; case STRING_VARIABLE_: { InterpreterVariable var = f [programPointer]. content.variable; autostring string = Melder_wcsdup (var -> stringValue); pushString (string.transfer()); } break; case NUMERIC_ARRAY_VARIABLE_: { InterpreterVariable var = f [programPointer]. content.variable; double **data = NUMmatrix_copy (var -> numericArrayValue. data, 1, var -> numericArrayValue. numberOfRows, 1, var -> numericArrayValue. numberOfColumns); therror pushNumericArray (var -> numericArrayValue. numberOfRows, var -> numericArrayValue. numberOfColumns, data); } break; default: Melder_throw ("Symbol \"", Formula_instructionNames [parse [programPointer]. symbol], "\" without action."); } // endswitch programPointer ++; } // endwhile if (w != 1) Melder_fatal ("Formula: stackpointer ends at %ld instead of 1.", w); if (theExpressionType == kFormula_EXPRESSION_TYPE_NUMERIC) { if (theStack [1]. which == Stackel_STRING) Melder_throw ("Found a string expression instead of a numeric expression."); if (theStack [1]. which == Stackel_NUMERIC_ARRAY) Melder_throw ("Found a numeric array expression instead of a numeric expression."); if (result) { result -> expressionType = kFormula_EXPRESSION_TYPE_NUMERIC; result -> result.numericResult = theStack [1]. content.number; } else { Melder_information (Melder_double (theStack [1]. content.number)); } } else if (theExpressionType == kFormula_EXPRESSION_TYPE_STRING) { if (theStack [1]. which == Stackel_NUMBER) Melder_throw ("Found a numeric expression instead of a string expression."); if (theStack [1]. which == Stackel_NUMERIC_ARRAY) Melder_throw ("Found a numeric array expression instead of a string expression."); if (result) { result -> expressionType = kFormula_EXPRESSION_TYPE_STRING; result -> result.stringResult = theStack [1]. content.string; theStack [1]. content.string = NULL; /* Undangle. */ } else { Melder_information (theStack [1]. content.string); } } else if (theExpressionType == kFormula_EXPRESSION_TYPE_NUMERIC_ARRAY) { if (theStack [1]. which == Stackel_NUMBER) Melder_throw ("Found a numeric expression instead of a numeric array expression."); if (theStack [1]. which == Stackel_STRING) Melder_throw ("Found a string expression instead of a numeric array expression."); if (result) { result -> expressionType = kFormula_EXPRESSION_TYPE_NUMERIC_ARRAY; result -> result.numericArrayResult = theStack [1]. content.numericArray; theStack [1]. content.numericArray = theZeroNumericArray; /* Undangle. */ } else { //Melder_information (theStack [1]. content.string); // TODO: implement } } else { Melder_assert (theExpressionType == kFormula_EXPRESSION_TYPE_UNKNOWN); if (theStack [1]. which == Stackel_NUMBER) { if (result) { result -> expressionType = kFormula_EXPRESSION_TYPE_NUMERIC; result -> result.numericResult = theStack [1]. content.number; } else { Melder_information (Melder_double (theStack [1]. content.number)); } } else { Melder_assert (theStack [1]. which == Stackel_STRING); if (result) { result -> expressionType = kFormula_EXPRESSION_TYPE_STRING; result -> result.stringResult = theStack [1]. content.string; theStack [1]. content.string = NULL; /* Undangle. */ } else { Melder_information (theStack [1]. content.string); } } } /* Clean up the stack (theStack [1] may have been disowned). */ for (w = wmax; w > 0; w --) { Stackel stackel = & theStack [w]; if (stackel -> which > Stackel_NUMBER) Stackel_cleanUp (stackel); } } catch (MelderError) { /* Clean up the stack (theStack [1] may have been disowned). */ for (w = wmax; w > 0; w --) { Stackel stackel = & theStack [w]; if (stackel -> which > Stackel_NUMBER) Stackel_cleanUp (stackel); } Melder_throw ("Formula not run."); } } /* End of file Formula.cpp */ sources_5316/sys/melder_audiofiles.cpp0000644000176700017670000017146611723713166016747 0ustar paulpaul/* melder_audiofiles.cpp * * Copyright (C) 1992-2011 Paul Boersma & David Weenink, 2007 Erez Volk (for FLAC) * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/12/16 corrected bug for cases in which format chunk follows data chunk in WAV file * pb 2003/09/12 Sound Designer II files * pb 2004/05/14 support for reading 24-bit and 32-bit audio files * pb 2004/11/12 writeShortToAudio can write single channels of stereo signal * pb 2004/11/15 fast reading of 16-bit audio files * pb 2006/12/13 32-bit IEEE float audio files * pb 2007/01/24 better error message for DVI ADPCM * Erez Volk 2007/03 FLAC reading * Erez Volk 2007/05/14 FLAC writing * pb 2007/05/17 corrected stereo FLAC writing * Erez Volk 2007/06/02 MP3 reading * pb 2007/10/05 FSOpenResFile * pb 2008/01/19 double * pb 2010/12/23 support for multi-channel sound files * pb 2011/04/05 C++ * pb 2011/05/03 fix WAV files with negative data chunk sizes */ #include "melder.h" #include "abcio.h" #include "math.h" #include "flac_FLAC_metadata.h" #include "flac_FLAC_stream_decoder.h" #include "flac_FLAC_stream_encoder.h" #include "mp3.h" #if defined (macintosh) #include #endif /***** WRITING *****/ #ifndef WAVE_FORMAT_PCM #define WAVE_FORMAT_PCM 0x0001 #endif #define WAVE_FORMAT_IEEE_FLOAT 0x0003 #define WAVE_FORMAT_ALAW 0x0006 #define WAVE_FORMAT_MULAW 0x0007 #define WAVE_FORMAT_DVI_ADPCM 0x0011 void MelderFile_writeAudioFileHeader (MelderFile file, int audioFileType, long sampleRate, long numberOfSamples, int numberOfChannels, int numberOfBitsPerSamplePoint) { try { FILE *f = file -> filePointer; if (f == NULL) return; const int numberOfBytesPerSamplePoint = (numberOfBitsPerSamplePoint + 7) / 8; switch (audioFileType) { case Melder_AIFF: { try { long dataSize = numberOfSamples * numberOfBytesPerSamplePoint * numberOfChannels; /* Form Chunk: contains all other chunks. */ if (fwrite ("FORM", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the FORM statement."); binputi4 (4 + (8 + 4) + (8 + 18) + (8 + 8 + dataSize), f); // the size of the Form Chunk if (fwrite ("AIFF", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the AIFF file type."); /* Format Version Chunk: 8 + 4 bytes. */ if (fwrite ("FVER", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the FVER statement."); binputi4 (4, f); // the size of what follows binputi4 (0xA2805140, f); // time of version /* Common Chunk: 8 + 18 bytes. */ if (fwrite ("COMM", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the COMM statement."); binputi4 (18, f); // the size of what follows binputi2 (numberOfChannels, f); binputi4 (numberOfSamples, f); binputi2 (numberOfBitsPerSamplePoint, f); binputr10 (sampleRate, f); /* Sound Data Chunk: 8 + 8 bytes + samples. */ if (fwrite ("SSND", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the SSND statement."); binputi4 (8 + dataSize, f); // the size of what follows binputi4 (0, f); // offset binputi4 (0, f); // block size } catch (MelderError) { Melder_throw ("AIFF header not written."); } } break; case Melder_AIFC: { try { long dataSize = numberOfSamples * numberOfBytesPerSamplePoint * numberOfChannels; /* Form Chunk: contains all other chunks. */ if (fwrite ("FORM", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the FORM statement."); binputi4 (4 + (8 + 4) + (8 + 24) + (8 + 8 + dataSize), f); // the size of the Form Chunk if (fwrite ("AIFC", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the AIFC file type."); /* Format Version Chunk: 8 + 4 bytes. */ if (fwrite ("FVER", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the FVER statement."); binputi4 (4, f); // the size of what follows binputi4 (0xA2805140, f); // time of version /* Common Chunk: 8 + 24 bytes. */ if (fwrite ("COMM", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the COMM statement."); binputi4 (24, f); // the size of what follows binputi2 (numberOfChannels, f); binputi4 (numberOfSamples, f); binputi2 (numberOfBitsPerSamplePoint, f); binputr10 (sampleRate, f); if (fwrite ("NONE", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the compression type."); binputi2 (0, f); // name of compression /* Sound Data Chunk: 8 + 8 bytes + samples. */ if (fwrite ("SSND", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the SSND statement."); binputi4 (8 + dataSize, f); // the size of what follows binputi4 (0, f); // offset binputi4 (0, f); // block size } catch (MelderError) { Melder_throw ("AIFC header not written."); } } break; case Melder_WAV: { try { long dataSize = numberOfSamples * numberOfBytesPerSamplePoint * numberOfChannels; /* RIFF Chunk: contains all other chunks. */ if (fwrite ("RIFF", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the RIFF statement."); binputi4LE (4 + (12 + 16) + (4 + dataSize), f); if (fwrite ("WAVE", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the WAV file type."); /* Format Chunk: 8 + 16 bytes. */ if (fwrite ("fmt ", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the FMT statement."); binputi4LE (16, f); binputi2LE (WAVE_FORMAT_PCM, f); binputi2LE (numberOfChannels, f); binputi4LE (sampleRate, f); // number of samples per second binputi4LE (sampleRate * numberOfBytesPerSamplePoint * numberOfChannels, f); // average number of bytes per second binputi2LE (numberOfBytesPerSamplePoint * numberOfChannels, f); // block alignment binputi2LE (numberOfBitsPerSamplePoint, f); /* Data Chunk: 8 bytes + samples. */ if (fwrite ("data", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the DATA statement."); binputi4LE (dataSize, f); } catch (MelderError) { Melder_throw ("WAV header not written."); } } break; case Melder_NEXT_SUN: { try { if (fwrite (".snd", 1, 4, f) != 4) Melder_throw ("Error in file while trying to write the .snd file type tag."); binputi4 (32, f); // length of header binputi4 (numberOfSamples * 2 * numberOfChannels, f); // length of data binputi4 (3, f); // 16-bits linear, not mu-law or A-law binputi4 (sampleRate, f); binputi4 (numberOfChannels, f); binputi4 (0, f); binputi4 (0, f); } catch (MelderError) { Melder_throw ("NeXT/Sun header not written."); } } break; case Melder_NIST: { try { char header [1024]; memset (header, 0, 1024); sprintf (header, "NIST_1A\n 1024\n" "channel_count -i %d\n" "sample_count -i %ld\n" "sample_n_bytes -i %d\n" "sample_byte_format -s2 01\n" /* 01=LE 10=BE */ "sample_coding -s3 pcm\n" "sample_rate -i %ld\n" "sample_min -i -32768\n" "sample_max -i 32767\n" "end_head\n", numberOfChannels, numberOfSamples, numberOfBytesPerSamplePoint, sampleRate); if (fwrite (header, 1, 1024, f) != 1024) Melder_throw ("Error in file while trying to write the NIST header."); } catch (MelderError) { Melder_throw ("NIST header not written."); } } break; case Melder_SOUND_DESIGNER_TWO: { Melder_throw ("Cannot yet write Sound Designer II files."); } break; case Melder_FLAC: { try { FLAC__StreamEncoder *encoder = NULL; if (numberOfChannels > (int) FLAC__MAX_CHANNELS) Melder_throw ("FLAC files cannot have more than 8 channels."); if ((encoder = FLAC__stream_encoder_new ()) == NULL) Melder_throw ("Error creating FLAC stream encoder."); FLAC__stream_encoder_set_bits_per_sample (encoder, numberOfBitsPerSamplePoint); FLAC__stream_encoder_set_channels (encoder, numberOfChannels); FLAC__stream_encoder_set_sample_rate (encoder, sampleRate); FLAC__stream_encoder_set_total_samples_estimate (encoder, numberOfSamples); if (FLAC__stream_encoder_init_FILE (encoder, file -> filePointer, NULL, NULL) != FLAC__STREAM_ENCODER_INIT_STATUS_OK) { FLAC__stream_encoder_delete (encoder); Melder_throw ("Error creating FLAC stream encoder"); } file -> flacEncoder = encoder; // only after we know it's correct (for MelderFile_close) file -> outputEncoding = kMelder_textOutputEncoding_FLAC; // only after we know it's correct (for MelderFile_close) } catch (MelderError) { Melder_throw ("FLAC header not written."); } } break; default: Melder_throw ("Unknown audio file type ", audioFileType, "."); } } catch (MelderError) { Melder_throw ("16-bit audio file header not written."); } } void MelderFile_writeAudioFileTrailer (MelderFile file, int audioFileType, long sampleRate, long numberOfSamples, int numberOfChannels, int numberOfBitsPerSamplePoint) { (void) sampleRate; bool shouldPadTheDataToAnEvenNumberOfBytes = audioFileType == Melder_WAV; bool numberOfSamplesIsOdd = (numberOfSamples & 1) != 0; bool numberOfChannelsIsOdd = (numberOfChannels & 1) != 0; int numberOfBytesPerSamplePoint = (numberOfBitsPerSamplePoint + 7) / 8; bool numberOfBytesPerSamplePointIsOdd = (numberOfBytesPerSamplePoint & 1) != 0; bool needToPadOneByte = shouldPadTheDataToAnEvenNumberOfBytes && numberOfSamplesIsOdd && numberOfChannelsIsOdd && numberOfBytesPerSamplePointIsOdd; if (needToPadOneByte && file -> filePointer) binputi1 (0, file -> filePointer); } static const wchar *audioFileTypeString [] = { L"none", L"AIFF", L"AIFC", L"WAV", L"NeXT/Sun", L"NIST", L"Sound Designer II", L"FLAC", L"MP3" }; const wchar * Melder_audioFileTypeString (int audioFileType) { return audioFileType > Melder_NUMBER_OF_AUDIO_FILE_TYPES ? L"unknown" : audioFileTypeString [audioFileType]; } static const wchar *macAudioFileType [1+Melder_NUMBER_OF_AUDIO_FILE_TYPES] = { L"", L"AIFF", L"AIFC", L"WAVE", L"ULAW", L"NIST", L"Sd2f", L"FLAC", L"MP3" }; const wchar * Melder_macAudioFileType (int audioFileType) { return macAudioFileType [audioFileType]; } static const wchar *winAudioFileExtension [1+Melder_NUMBER_OF_AUDIO_FILE_TYPES] = { L"", L".aiff", L".aifc", L".wav", L".au", L".nist", L".sd2", L".flac", L".mp3" }; const wchar * Melder_winAudioFileExtension (int audioFileType) { return winAudioFileExtension [audioFileType]; } static int defaultAudioFileEncoding16 [1+Melder_NUMBER_OF_AUDIO_FILE_TYPES] = { 0, Melder_LINEAR_16_BIG_ENDIAN, Melder_LINEAR_16_BIG_ENDIAN, Melder_LINEAR_16_LITTLE_ENDIAN, Melder_LINEAR_16_BIG_ENDIAN, Melder_LINEAR_16_LITTLE_ENDIAN, Melder_LINEAR_16_BIG_ENDIAN, Melder_FLAC_COMPRESSION_16, Melder_MPEG_COMPRESSION_16 }; static int defaultAudioFileEncoding24 [1+Melder_NUMBER_OF_AUDIO_FILE_TYPES] = { 0, Melder_LINEAR_24_BIG_ENDIAN, Melder_LINEAR_24_BIG_ENDIAN, Melder_LINEAR_24_LITTLE_ENDIAN, Melder_LINEAR_24_BIG_ENDIAN, Melder_LINEAR_24_LITTLE_ENDIAN, Melder_LINEAR_24_BIG_ENDIAN, Melder_FLAC_COMPRESSION_24, Melder_MPEG_COMPRESSION_24 }; static int defaultAudioFileEncoding32 [1+Melder_NUMBER_OF_AUDIO_FILE_TYPES] = { 0, Melder_LINEAR_32_BIG_ENDIAN, Melder_LINEAR_32_BIG_ENDIAN, Melder_LINEAR_32_LITTLE_ENDIAN, Melder_LINEAR_32_BIG_ENDIAN, Melder_LINEAR_32_LITTLE_ENDIAN, Melder_LINEAR_32_BIG_ENDIAN, Melder_FLAC_COMPRESSION_32, Melder_MPEG_COMPRESSION_32 }; int Melder_defaultAudioFileEncoding (int audioFileType, int numberOfBitsPerSamplePoint) { return numberOfBitsPerSamplePoint == 16 ? defaultAudioFileEncoding16 [audioFileType] : numberOfBitsPerSamplePoint == 24 ? defaultAudioFileEncoding24 [audioFileType] : defaultAudioFileEncoding32 [audioFileType]; } void MelderFile_writeAudioFile (MelderFile file, int audioFileType, const short *buffer, long sampleRate, long numberOfSamples, int numberOfChannels, int numberOfBitsPerSamplePoint) { try { autoMelderFile mfile = MelderFile_create (file, macAudioFileType [audioFileType], L"PpgB", winAudioFileExtension [audioFileType]); MelderFile_writeAudioFileHeader (file, audioFileType, sampleRate, numberOfSamples, numberOfChannels, numberOfBitsPerSamplePoint); MelderFile_writeShortToAudio (file, numberOfChannels, defaultAudioFileEncoding16 [audioFileType], buffer, numberOfSamples); MelderFile_writeAudioFileTrailer (file, audioFileType, sampleRate, numberOfSamples, numberOfChannels, numberOfBitsPerSamplePoint); mfile.close (); } catch (MelderError) { Melder_throw ("16-bit audio file not written."); } } /***** READING *****/ int Melder_bytesPerSamplePoint (int encoding) { return encoding == Melder_LINEAR_16_BIG_ENDIAN || encoding == Melder_LINEAR_16_LITTLE_ENDIAN ? 2 : encoding == Melder_LINEAR_24_BIG_ENDIAN || encoding == Melder_LINEAR_24_LITTLE_ENDIAN ? 3 : encoding == Melder_LINEAR_32_BIG_ENDIAN || encoding == Melder_LINEAR_32_LITTLE_ENDIAN || encoding == Melder_IEEE_FLOAT_32_BIG_ENDIAN || encoding == Melder_IEEE_FLOAT_32_LITTLE_ENDIAN ? 4 : 1; } static int ulaw2linear [] = { -32124, -31100, -30076, -29052, -28028, -27004, -25980, -24956, -23932, -22908, -21884, -20860, -19836, -18812, -17788, -16764, -15996, -15484, -14972, -14460, -13948, -13436, -12924, -12412, -11900, -11388, -10876, -10364, -9852, -9340, -8828, -8316, -7932, -7676, -7420, -7164, -6908, -6652, -6396, -6140, -5884, -5628, -5372, -5116, -4860, -4604, -4348, -4092, -3900, -3772, -3644, -3516, -3388, -3260, -3132, -3004, -2876, -2748, -2620, -2492, -2364, -2236, -2108, -1980, -1884, -1820, -1756, -1692, -1628, -1564, -1500, -1436, -1372, -1308, -1244, -1180, -1116, -1052, -988, -924, -876, -844, -812, -780, -748, -716, -684, -652, -620, -588, -556, -524, -492, -460, -428, -396, -372, -356, -340, -324, -308, -292, -276, -260, -244, -228, -212, -196, -180, -164, -148, -132, -120, -112, -104, -96, -88, -80, -72, -64, -56, -48, -40, -32, -24, -16, -8, 0, 32124, 31100, 30076, 29052, 28028, 27004, 25980, 24956, 23932, 22908, 21884, 20860, 19836, 18812, 17788, 16764, 15996, 15484, 14972, 14460, 13948, 13436, 12924, 12412, 11900, 11388, 10876, 10364, 9852, 9340, 8828, 8316, 7932, 7676, 7420, 7164, 6908, 6652, 6396, 6140, 5884, 5628, 5372, 5116, 4860, 4604, 4348, 4092, 3900, 3772, 3644, 3516, 3388, 3260, 3132, 3004, 2876, 2748, 2620, 2492, 2364, 2236, 2108, 1980, 1884, 1820, 1756, 1692, 1628, 1564, 1500, 1436, 1372, 1308, 1244, 1180, 1116, 1052, 988, 924, 876, 844, 812, 780, 748, 716, 684, 652, 620, 588, 556, 524, 492, 460, 428, 396, 372, 356, 340, 324, 308, 292, 276, 260, 244, 228, 212, 196, 180, 164, 148, 132, 120, 112, 104, 96, 88, 80, 72, 64, 56, 48, 40, 32, 24, 16, 8, 0 }; static short alaw2linear[] = { -5504, -5248, -6016, -5760, -4480, -4224, -4992, -4736, -7552, -7296, -8064, -7808, -6528, -6272, -7040, -6784, -2752, -2624, -3008, -2880, -2240, -2112, -2496, -2368, -3776, -3648, -4032, -3904, -3264, -3136, -3520, -3392, -22016, -20992, -24064, -23040, -17920, -16896, -19968, -18944, -30208, -29184, -32256, -31232, -26112, -25088, -28160, -27136, -11008, -10496, -12032, -11520, -8960, -8448, -9984, -9472, -15104, -14592, -16128, -15616, -13056, -12544, -14080, -13568, -344, -328, -376, -360, -280, -264, -312, -296, -472, -456, -504, -488, -408, -392, -440, -424, -88, -72, -120, -104, -24, -8, -56, -40, -216, -200, -248, -232, -152, -136, -184, -168, -1376, -1312, -1504, -1440, -1120, -1056, -1248, -1184, -1888, -1824, -2016, -1952, -1632, -1568, -1760, -1696, -688, -656, -752, -720, -560, -528, -624, -592, -944, -912, -1008, -976, -816, -784, -880, -848, 5504, 5248, 6016, 5760, 4480, 4224, 4992, 4736, 7552, 7296, 8064, 7808, 6528, 6272, 7040, 6784, 2752, 2624, 3008, 2880, 2240, 2112, 2496, 2368, 3776, 3648, 4032, 3904, 3264, 3136, 3520, 3392, 22016, 20992, 24064, 23040, 17920, 16896, 19968, 18944, 30208, 29184, 32256, 31232, 26112, 25088, 28160, 27136, 11008, 10496, 12032, 11520, 8960, 8448, 9984, 9472, 15104, 14592, 16128, 15616, 13056, 12544, 14080, 13568, 344, 328, 376, 360, 280, 264, 312, 296, 472, 456, 504, 488, 408, 392, 440, 424, 88, 72, 120, 104, 24, 8, 56, 40, 216, 200, 248, 232, 152, 136, 184, 168, 1376, 1312, 1504, 1440, 1120, 1056, 1248, 1184, 1888, 1824, 2016, 1952, 1632, 1568, 1760, 1696, 688, 656, 752, 720, 560, 528, 624, 592, 944, 912, 1008, 976, 816, 784, 880, 848 }; static void Melder_checkAiffFile (FILE *f, int *numberOfChannels, int *encoding, double *sampleRate, long *startOfData, long *numberOfSamples) { char data [8], chunkID [4]; bool commonChunkPresent = false, dataChunkPresent = false, isAifc = true; int numberOfBitsPerSamplePoint; /* Read header of AIFF(-C) file: 12 bytes. */ if (fread (data, 1, 4, f) < 4) Melder_throw ("File too small: no FORM statement."); if (! strnequ (data, "FORM", 4)) Melder_throw ("Not an AIFF or AIFC file (FORM statement expected)."); if (fread (data, 1, 4, f) < 4) Melder_throw ("File too small: no size of FORM chunk."); if (fread (data, 1, 4, f) < 4) Melder_throw ("File too small: no file type info (expected AIFF or AIFC)."); if (! strnequ (data, "AIFF", 4) && ! strnequ (data, "AIFC", 4)) Melder_throw ("Not an AIFF or AIFC file (wrong file type info)."); if (strnequ (data, "AIFF", 4)) isAifc = false; /* Search for Common Chunk and Data Chunk. */ while (fread (chunkID, 1, 4, f) == 4) { long chunkSize = bingeti4 (f); if (chunkSize & 1) ++ chunkSize; // round up to nearest even number /* IN SOUND FILES PRODUCED BY THE SGI'S soundeditor PROGRAM, */ /* THE COMMON CHUNK HAS A chunkSize OF 18 INSTEAD OF 38, */ /* ALTHOUGH THE COMMON CHUNK CONTAINS */ /* THE 20-BYTE SEQUENCE "\016not compressed\0". */ /* START FIX OF FOREIGN BUG */ if(strnequ(chunkID,"NONE",4)&& (chunkSize==(14<<24)+('n'<<16)+('o'<<8)+'t'||chunkSize==('t'<<24)+('o'<<16)+('n'<<8)+14)) {Melder_casual("Ha! a buggy SGI \"soundeditor\" file...");for(long i=1;i<=20/*diff*/-8/*header*/;i++)fread(data,1,1,f);continue;} /* FINISH FIX OF FOREIGN BUG */ if (strnequ (chunkID, "COMM", 4)) { /* * Found a Common Chunk. */ commonChunkPresent = true; *numberOfChannels = bingeti2 (f); if (*numberOfChannels < 1) Melder_throw ("Too few sound channels (", *numberOfChannels, ")."); *numberOfSamples = bingeti4 (f); if (*numberOfSamples <= 0) Melder_throw ("Too few samples ", *numberOfSamples, ")."); numberOfBitsPerSamplePoint = bingeti2 (f); if (numberOfBitsPerSamplePoint > 32) Melder_throw ("Too many bits per sample (", numberOfBitsPerSamplePoint, "; the maximum is 32)."); *encoding = numberOfBitsPerSamplePoint > 24 ? Melder_LINEAR_32_BIG_ENDIAN : numberOfBitsPerSamplePoint > 16 ? Melder_LINEAR_24_BIG_ENDIAN : numberOfBitsPerSamplePoint > 8 ? Melder_LINEAR_16_BIG_ENDIAN : Melder_LINEAR_8_SIGNED; *sampleRate = bingetr10 (f); if (*sampleRate <= 0.0) Melder_throw ("Wrong sampling frequency (", *sampleRate, " Hz)."); if (isAifc) { /* * Read compression data; should be "NONE" or "sowt". */ if (fread (data, 1, 4, f) < 4) Melder_throw ("File too small: no compression info."); if (! strnequ (data, "NONE", 4) && ! strnequ (data, "sowt", 4)) { data [4] = '\0'; Melder_throw ("Cannot read compressed AIFC files (compression type ", data, ")."); } if (strnequ (data, "sowt", 4)) *encoding = numberOfBitsPerSamplePoint > 24 ? Melder_LINEAR_32_LITTLE_ENDIAN : numberOfBitsPerSamplePoint > 16 ? Melder_LINEAR_24_LITTLE_ENDIAN : numberOfBitsPerSamplePoint > 8 ? Melder_LINEAR_16_LITTLE_ENDIAN : Melder_LINEAR_8_SIGNED; /* * Read rest of compression info. */ for (long i = 23; i <= chunkSize; i ++) if (fread (data, 1, 1, f) < 1) Melder_throw ("File too small: expected chunk of ", chunkSize, " bytes, but found ", i + 22, "."); } } else if (strnequ (chunkID, "SSND", 4)) { /* * Found a Data Chunk. */ dataChunkPresent = true; *startOfData = ftell (f) + 8; // ignore "offset" (4 bytes) and "blocksize" (4 bytes) if (commonChunkPresent) break; // optimization: do not read whole data chunk if we have already read the common chunk } else // ignore Version Chunk and unknown chunks for (long i = 1; i <= chunkSize; i ++) if (fread (data, 1, 1, f) < 1) Melder_throw ("File too small: expected ", chunkSize, " bytes, but found ", i, "."); } if (! commonChunkPresent) Melder_throw ("Found no Common Chunk."); if (! dataChunkPresent) Melder_throw ("Found no Data Chunk."); } static void Melder_checkWavFile (FILE *f, int *numberOfChannels, int *encoding, double *sampleRate, long *startOfData, long *numberOfSamples) { char data [8], chunkID [4]; bool formatChunkPresent = false, dataChunkPresent = false; int numberOfBitsPerSamplePoint = -1; long dataChunkSize = -1; if (fread (data, 1, 4, f) < 4) Melder_throw ("File too small: no RIFF statement."); if (! strnequ (data, "RIFF", 4)) Melder_throw ("Not a WAV file (RIFF statement expected)."); if (fread (data, 1, 4, f) < 4) Melder_throw ("File too small: no size of RIFF chunk."); if (fread (data, 1, 4, f) < 4) Melder_throw ("File too small: no file type info (expected WAVE statement)."); if (! strnequ (data, "WAVE", 4) && ! strnequ (data, "CDDA", 4)) Melder_throw (L"Not a WAVE or CD audio file (wrong file type info)."); /* Search for Format Chunk and Data Chunk. */ while (fread (chunkID, 1, 4, f) == 4) { long chunkSize = bingeti4LE (f); if (Melder_debug == 23) { Melder_warning (Melder_integer (chunkID [0]), L" ", Melder_integer (chunkID [1]), L" ", Melder_integer (chunkID [2]), L" ", Melder_integer (chunkID [3]), L" ", Melder_integer (chunkSize)); } if (strnequ (chunkID, "fmt ", 4)) { /* * Found a Format Chunk. */ int winEncoding = bingeti2LE (f); formatChunkPresent = true; *numberOfChannels = bingeti2LE (f); if (*numberOfChannels < 1) Melder_throw ("Too few sound channels (", *numberOfChannels, ")."); *sampleRate = (double) bingeti4LE (f); if (*sampleRate <= 0.0) Melder_throw ("Wrong sampling frequency (", *sampleRate, " Hz)."); (void) bingeti4LE (f); // avgBytesPerSec (void) bingeti2LE (f); // blockAlign numberOfBitsPerSamplePoint = bingeti2LE (f); if (numberOfBitsPerSamplePoint == 0) numberOfBitsPerSamplePoint = 16; // the default else if (numberOfBitsPerSamplePoint < 4) Melder_throw ("Too few bits per sample (", numberOfBitsPerSamplePoint, "; the minimum is 4)."); else if (numberOfBitsPerSamplePoint > 32) Melder_throw ("Too few bits per sample (", numberOfBitsPerSamplePoint, "; the maximum is 32)."); switch (winEncoding) { case WAVE_FORMAT_PCM: *encoding = numberOfBitsPerSamplePoint > 24 ? Melder_LINEAR_32_LITTLE_ENDIAN : numberOfBitsPerSamplePoint > 16 ? Melder_LINEAR_24_LITTLE_ENDIAN : numberOfBitsPerSamplePoint > 8 ? Melder_LINEAR_16_LITTLE_ENDIAN : Melder_LINEAR_8_UNSIGNED; break; case WAVE_FORMAT_IEEE_FLOAT: *encoding = Melder_IEEE_FLOAT_32_LITTLE_ENDIAN; break; case WAVE_FORMAT_ALAW: *encoding = Melder_ALAW; break; case WAVE_FORMAT_MULAW: *encoding = Melder_MULAW; break; case WAVE_FORMAT_DVI_ADPCM: Melder_throw ("Cannot read lossy compressed audio files (this one is DVI ADPCM).\n" "Please use uncompressed audio files. If you must open this file,\n" "please use an audio converter program to convert it first to normal (PCM) WAV format\n" "(Praat may have difficulty analysing the poor recording, though)."); default: Melder_throw ("Unsupported Windows audio encoding %d.", winEncoding); } if (chunkSize & 1) chunkSize ++; for (long i = 17; i <= chunkSize; i ++) if (fread (data, 1, 1, f) < 1) Melder_throw ("File too small: expected ", chunkSize, " bytes in fmt chunk, but found ", i, "."); } else if (strnequ (chunkID, "data", 4)) { /* * Found a Data Chunk. */ dataChunkPresent = true; dataChunkSize = chunkSize; *startOfData = ftell (f); if (chunkSize & 1) chunkSize ++; if (chunkSize < 0) { // incorrect data chunk (sometimes -44); assume that the data run till the end of the file fseek (f, 0, SEEK_END); long endOfData = ftell (f); dataChunkSize = chunkSize = endOfData - *startOfData; fseek (f, *startOfData, SEEK_SET); } if (Melder_debug == 23) { for (long i = 1; i <= chunkSize; i ++) if (fread (data, 1, 1, f) < 1) Melder_throw ("File too small: expected ", chunkSize, " bytes of data, but found ", i, "."); } else { if (formatChunkPresent) break; // OPTIMIZATION: do not read the whole data chunk if we have already read the format chunk } } else { // ignore other chunks if (chunkSize & 1) chunkSize ++; for (long i = 1; i <= chunkSize; i ++) if (fread (data, 1, 1, f) < 1) Melder_throw ("File too small: expected ", chunkSize, " bytes, but found ", i, "."); } } if (! formatChunkPresent) Melder_throw (L"Found no Format Chunk."); if (! dataChunkPresent) Melder_throw (L"Found no Data Chunk."); Melder_assert (numberOfBitsPerSamplePoint != -1 && dataChunkSize != -1); *numberOfSamples = dataChunkSize / *numberOfChannels / ((numberOfBitsPerSamplePoint + 7) / 8); } static void Melder_checkNextSunFile (FILE *f, int *numberOfChannels, int *encoding, double *sampleRate, long *startOfData, long *numberOfSamples) { char tag [4]; fread (tag, 1, 4, f); if (strncmp (tag, ".snd", 4)) Melder_throw ("Not a Sun audio file."); *startOfData = bingeti4 (f); if (*startOfData < 24 || *startOfData > 320) Melder_throw ("Cannot read header of audio file. Length ", *startOfData, "."); long dataSize = bingeti4 (f); if (dataSize <= 0) { /* * Incorrect information. Get it from file length. */ long save = ftell (f); fseek (f, 0, SEEK_END); dataSize = ftell (f) - *startOfData; fseek (f, save, SEEK_SET); } long sunEncoding = bingeti4 (f); switch (sunEncoding) { case 1: *encoding = Melder_MULAW; break; case 2: *encoding = Melder_LINEAR_8_SIGNED; break; case 3: *encoding = Melder_LINEAR_16_BIG_ENDIAN; break; case 27: *encoding = Melder_ALAW; break; default: Melder_throw ("Cannot translate audio file encoding ", sunEncoding, "."); } *sampleRate = bingeti4 (f); if (*sampleRate <= 0) Melder_throw ("Impossible sampling frequency ", *sampleRate, " Hz."); *numberOfChannels = bingeti4 (f); if (*numberOfChannels < 1) Melder_throw ("Wrong number of channels in audio file (", *numberOfChannels, ")."); *numberOfSamples = dataSize / Melder_bytesPerSamplePoint (*encoding) / *numberOfChannels; long skip = *startOfData - 24; while (skip -- > 0) (void) fgetc (f); } static int nistGetValue (const char *header, const char *object, double *rval, char *sval) { char obj [30], type [10]; const char *match = strstr (header, object); if (! match) return 0; if (sscanf (match, "%s%s%s", obj, type, sval) != 3) return 0; if (strequ (type, "-i") || strequ (type, "-r")) *rval = atof (sval); else if (strncmp (type, "-s", 2)) return 0; return 1; } static void Melder_checkNistFile (FILE *f, int *numberOfChannels, int *encoding, double *sampleRate, long *startOfData, long *numberOfSamples) { char header [1024], sval [100]; double rval; int numberOfBytesPerSamplePoint; if (fread (header, 1, 1024, f) != 1024) Melder_throw ("Cannot read NISTheader."); if (! strnequ (header, "NIST_1A", 7)) Melder_throw ("Not a NIST sound file."); *startOfData = atol (header + 9); if (! nistGetValue (header, "sample_count", & rval, sval) || rval < 1) Melder_throw ("Incorrect number of samples in NIST file."); *numberOfSamples = rval; if (! nistGetValue (header, "sample_n_bytes", & rval, sval) || rval < 1 || rval > 2) Melder_throw ("Incorrect number of bytes per sample (should be 1 or 2)."); numberOfBytesPerSamplePoint = rval; if (! nistGetValue (header, "channel_count", & rval, sval) || rval < 1) Melder_throw ("Incorrect number of channels."); *numberOfChannels = rval; if (! nistGetValue (header, "sample_rate", sampleRate, sval) || *sampleRate < 1) Melder_throw ("Incorrect sampling frequency ", *sampleRate, " Hz."); *encoding = Melder_LINEAR_16_BIG_ENDIAN; if (nistGetValue (header, "sample_byte_format", & rval, sval) && strequ (sval, "01")) *encoding = Melder_LINEAR_16_LITTLE_ENDIAN; if (numberOfBytesPerSamplePoint == 1) *encoding = Melder_LINEAR_8_SIGNED; if (nistGetValue (header, "sample_coding", & rval, sval)) { if (strnequ (sval, "ulaw", 4)) *encoding = Melder_MULAW; else if (strstr (sval, "embedded-shorten-v")) if (nistGetValue (header, "database_id", & rval, sval) && strequ (sval, "POLYPHONE-NL")) *encoding = Melder_POLYPHONE; else *encoding = Melder_SHORTEN; else if (strnequ (sval, "alaw", 4)) // must be after previous, because some files have "alaw,embedded..." *encoding = Melder_ALAW; } } #ifdef macintosh static double Melder_getNumberFromStrResource (int resourceID) { Handle han = Get1Resource ('STR ', resourceID); if (! han) Melder_throw ("Resource ", resourceID, " not found."); char *pstring = (char *) (*han); int length = (unsigned char) pstring [0]; char string [256]; strncpy (string, & pstring [1], length); string [length] = 0; ReleaseResource (han); return atof (string); } static void MelderFile_checkSoundDesignerTwoFile (MelderFile file, int *numberOfChannels, int *encoding, double *sampleRate, long *startOfData, long *numberOfSamples) { int path = -1; try { FSRef fsRef; Melder_fileToMach (file, & fsRef); path = FSOpenResFile (& fsRef, fsRdPerm); // open resource fork; that's where the header info is if (path == -1) Melder_throw ("Cannot open resource fork."); int sampleSize = 0; try { sampleSize = Melder_getNumberFromStrResource (1000); } catch (MelderError) { Melder_throw ("Sample size not read."); } if (sampleSize < 1 || sampleSize > 4) Melder_throw ("Wrong sample size (", sampleSize, "; should be between 1 and 4)."); *encoding = sampleSize == 1 ? Melder_LINEAR_8_SIGNED : sampleSize == 2 ? Melder_LINEAR_16_BIG_ENDIAN : sampleSize == 3 ? Melder_LINEAR_24_BIG_ENDIAN : Melder_LINEAR_32_BIG_ENDIAN; try { *sampleRate = Melder_getNumberFromStrResource (1001); } catch (MelderError) { Melder_throw (L"Sampling frequency not read."); } if (*sampleRate <= 0.0) Melder_throw ("Wrong sampling frequency (", *sampleRate, " Hz)."); try { *numberOfChannels = Melder_getNumberFromStrResource (1002); } catch (MelderError) { Melder_throw ("Channel number not read."); } if (*numberOfChannels != 1 && *numberOfChannels != 2) Melder_throw ("Wrong number of channels: ", *numberOfChannels); *numberOfSamples = MelderFile_length (file) / sampleSize / *numberOfChannels; if (*numberOfSamples <= 0) Melder_throw ("No samples in file."); *startOfData = 0; if (path != -1) CloseResFile (path); } catch (MelderError) { if (path != -1) CloseResFile (path); Melder_throw (L"Sound Designer II file not read."); } } #endif static void Melder_checkFlacFile (MelderFile file, int *numberOfChannels, int *encoding, double *sampleRate, long *startOfData, long *numberOfSamples) { FLAC__StreamMetadata metadata; FLAC__StreamMetadata_StreamInfo *info; if (! FLAC__metadata_get_streaminfo (Melder_peekWcsToUtf8 (Melder_fileToPath (file)), & metadata)) // FIXME: not Unicode-compatible on Windows. Melder_throw ("Invalid FLAC file"); info = & metadata. data. stream_info; *numberOfChannels = info -> channels; *encoding = Melder_FLAC_COMPRESSION_16; *sampleRate = (double) info -> sample_rate; *startOfData = 0; // meaningless: libFLAC does the I/O *numberOfSamples = info -> total_samples; // FIXME: may lose bits above LONG_MAX if ((FLAC__uint64) *numberOfSamples != info -> total_samples) Melder_throw ("FLAC file too long."); } static void Melder_checkMp3File (FILE *f, int *numberOfChannels, int *encoding, double *sampleRate, long *startOfData, long *numberOfSamples) { MP3_FILE mp3f = mp3f_new (); mp3f_set_file (mp3f, f); if (! mp3f_analyze (mp3f)) { mp3f_delete (mp3f); Melder_throw ("Cannot analyze MP3 file"); } *encoding = Melder_MPEG_COMPRESSION_16; *numberOfChannels = mp3f_channels (mp3f); *sampleRate = mp3f_frequency (mp3f); *numberOfSamples = mp3f_samples (mp3f); if ((MP3F_OFFSET)*numberOfSamples != mp3f_samples (mp3f)) Melder_throw ("MP3 file too long."); *startOfData = 0; // meaningless mp3f_delete (mp3f); } int MelderFile_checkSoundFile (MelderFile file, int *numberOfChannels, int *encoding, double *sampleRate, long *startOfData, long *numberOfSamples) { char data [16]; FILE *f = file -> filePointer; if (f == NULL || fread (data, 1, 16, f) < 16) return 0; rewind (f); if (strnequ (data, "FORM", 4) && strnequ (data + 8, "AIFF", 4)) { Melder_checkAiffFile (f, numberOfChannels, encoding, sampleRate, startOfData, numberOfSamples); return Melder_AIFF; } if (strnequ (data, "FORM", 4) && strnequ (data + 8, "AIFC", 4)) { Melder_checkAiffFile (f, numberOfChannels, encoding, sampleRate, startOfData, numberOfSamples); return Melder_AIFC; } if (strnequ (data, "RIFF", 4) && (strnequ (data + 8, "WAVE", 4) || strnequ (data + 8, "CDDA", 4))) { Melder_checkWavFile (f, numberOfChannels, encoding, sampleRate, startOfData, numberOfSamples); return Melder_WAV; } if (strnequ (data, ".snd", 4)) { Melder_checkNextSunFile (f, numberOfChannels, encoding, sampleRate, startOfData, numberOfSamples); return Melder_NEXT_SUN; } if (strnequ (data, "NIST_1A", 7)) { Melder_checkNistFile (f, numberOfChannels, encoding, sampleRate, startOfData, numberOfSamples); return Melder_NIST; } if (strnequ (data, "fLaC", 4)) { Melder_checkFlacFile (file, numberOfChannels, encoding, sampleRate, startOfData, numberOfSamples); return Melder_FLAC; } if (mp3_recognize (16, data)) { Melder_checkMp3File (f, numberOfChannels, encoding, sampleRate, startOfData, numberOfSamples); return Melder_MP3; } #ifdef macintosh if (MelderFile_getMacType (file) == 'Sd2f') { MelderFile_checkSoundDesignerTwoFile (file, numberOfChannels, encoding, sampleRate, startOfData, numberOfSamples); return Melder_SOUND_DESIGNER_TWO; } #endif return 0; // not a recognized sound file } /* libFLAC works through callbacks, so we need a context struct. */ typedef struct { FILE *file; int numberOfChannels; long numberOfSamples; double *channels [FLAC__MAX_CHANNELS]; } MelderDecodeFlacContext; /* The same goes for MP3 */ typedef struct { int numberOfChannels; long numberOfSamples; double *channels [2]; } MelderDecodeMp3Context; static FLAC__StreamDecoderReadStatus Melder_DecodeFlac_read (const FLAC__StreamDecoder *decoder, FLAC__byte buffer [], size_t *bytes, void *client_data) { MelderDecodeFlacContext *c = (MelderDecodeFlacContext *) client_data; (void) decoder; if (*bytes <= 0) return FLAC__STREAM_DECODER_READ_STATUS_ABORT; *bytes = fread (buffer, sizeof (FLAC__byte), *bytes, c -> file); if (ferror (c -> file)) return FLAC__STREAM_DECODER_READ_STATUS_ABORT; if (*bytes == 0) return FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM; return FLAC__STREAM_DECODER_READ_STATUS_CONTINUE; } static FLAC__StreamDecoderWriteStatus Melder_DecodeFlac_convert (const FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 *const buffer[], void *client_data) { MelderDecodeFlacContext *c = (MelderDecodeFlacContext *) client_data; const FLAC__FrameHeader *header = & frame -> header; long count = header -> blocksize; double multiplier; (void) decoder; switch (header -> bits_per_sample) { case 8: multiplier = (1.0f / 128); break; case 16: multiplier = (1.0f / 32768); break; case 24: multiplier = (1.0f / 8388608); break; case 32: multiplier = (1.0f / 32768 / 65536); break; default: return FLAC__STREAM_DECODER_WRITE_STATUS_ABORT; } for (long i = 0; i < c -> numberOfChannels; ++ i) { const FLAC__int32 *input = buffer [i]; double *output = c -> channels [i]; for (long j = 0; j < count; ++ j) output [j] = ((long) input [j]) * multiplier; c -> channels [i] += count; } return FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE; } static void Melder_DecodeMp3_convert (const MP3F_SAMPLE *channels [MP3F_MAX_CHANNELS], long count, void *context) { MelderDecodeMp3Context *c = (MelderDecodeMp3Context *) context; const MP3F_SAMPLE *input; double *output; for (long i = 0; i < c -> numberOfChannels; ++ i) { input = channels [i]; output = c -> channels [i]; for (long j = 0; j < count; ++ j) output [j] = mp3f_sample_to_float (input [j]); c -> channels [i] += count; } } static void Melder_DecodeFlac_error (const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data) { (void) decoder; (void) client_data; Melder_warning ("FLAC decoder error: ", FLAC__StreamDecoderErrorStatusString [status]); } static void Melder_readFlacFile (FILE *f, int numberOfChannels, double **buffer, long numberOfSamples) { FLAC__StreamDecoder *decoder; MelderDecodeFlacContext c; int result = 0; c.file = f; c.numberOfChannels = numberOfChannels; for (int ichan = 1; ichan <= numberOfChannels; ichan ++) { c.channels [ichan - 1] = & buffer [ichan] [1]; } c.numberOfSamples = numberOfSamples; if ((decoder = FLAC__stream_decoder_new ()) == NULL) goto end; if (FLAC__stream_decoder_init_stream (decoder, Melder_DecodeFlac_read, NULL, NULL, NULL, NULL, Melder_DecodeFlac_convert, NULL, Melder_DecodeFlac_error, &c) != FLAC__STREAM_DECODER_INIT_STATUS_OK) goto end; result = FLAC__stream_decoder_process_until_end_of_stream (decoder); FLAC__stream_decoder_finish (decoder); end: if (decoder) FLAC__stream_decoder_delete (decoder); if (result == 0) Melder_throw ("Error decoding FLAC file."); } static void Melder_readMp3File (FILE *f, int numberOfChannels, double **buffer, long numberOfSamples) { MelderDecodeMp3Context c; int result = 0; c.numberOfChannels = numberOfChannels; for (int ichan = 1; ichan <= numberOfChannels; ichan ++) { c.channels [ichan - 1] = & buffer [ichan] [1]; } c.numberOfSamples = numberOfSamples; MP3_FILE mp3f = mp3f_new (); mp3f_set_file (mp3f, f); mp3f_set_callback (mp3f, Melder_DecodeMp3_convert, &c); result = mp3f_read (mp3f, numberOfSamples); mp3f_delete (mp3f); if (result == 0) Melder_throw ("Error decoding MP3 file."); } void Melder_readAudioToFloat (FILE *f, int numberOfChannels, int encoding, double **buffer, long numberOfSamples) { try { switch (encoding) { case Melder_LINEAR_8_SIGNED: { try { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { int8_t value; if (fread (& value, 1, 1, f) < 1) throw MelderError (); buffer [ichan] [isamp] = value * (1.0 / 128); } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 8-bit).\nMissing samples set to zero."); } } break; case Melder_LINEAR_8_UNSIGNED: try { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = bingetu1 (f) * (1.0 / 128) - 1.0; therror } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 8-bit).\nMissing samples set to zero."); } break; case Melder_LINEAR_16_BIG_ENDIAN: { try { const int numberOfBytesPerSamplePerChannel = 2; if (numberOfChannels > (int) sizeof (double) / numberOfBytesPerSamplePerChannel) { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = bingeti2 (f) * (1.0 / 32768); therror } } } else { // optimize long numberOfBytes = numberOfChannels * numberOfSamples * numberOfBytesPerSamplePerChannel; unsigned char *bytes = (unsigned char *) & buffer [numberOfChannels] [numberOfSamples] + sizeof (double) - numberOfBytes; if (fread (bytes, 1, numberOfBytes, f) < numberOfBytes) throw MelderError (); // read 16-bit data into last quarter of buffer if (numberOfChannels == 1) { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { unsigned char byte1 = * bytes ++, byte2 = * bytes ++; long value = (int16_t) (((uint16_t) byte1 << 8) | (uint16_t) byte2); buffer [1] [isamp] = value * (1.0 / 32768); } } else { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { unsigned char byte1 = * bytes ++, byte2 = * bytes ++; long value = (int16_t) (((uint16_t) byte1 << 8) | (uint16_t) byte2); buffer [ichan] [isamp] = value * (1.0 / 32768); } } } } } catch (MelderError) { Melder_clearError (); Melder_warning (L"File too small (", numberOfChannels, "-channel 16-bit).\nMissing samples set to zero."); } } break; case Melder_LINEAR_16_LITTLE_ENDIAN: { try { const int numberOfBytesPerSamplePerChannel = 2; if (numberOfChannels > (int) sizeof (double) / numberOfBytesPerSamplePerChannel) { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = bingeti2LE (f) * (1.0 / 32768); therror } } } else { // optimize long numberOfBytes = numberOfChannels * numberOfSamples * numberOfBytesPerSamplePerChannel; unsigned char *bytes = (unsigned char *) & buffer [numberOfChannels] [numberOfSamples] + sizeof (double) - numberOfBytes; if (fread (bytes, 1, numberOfBytes, f) < numberOfBytes) throw MelderError (); // read 16-bit data into last quarter of buffer if (numberOfChannels == 1) { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { unsigned char byte1 = * bytes ++, byte2 = * bytes ++; long value = (int16_t) (((uint16_t) byte2 << 8) | (uint16_t) byte1); buffer [1] [isamp] = value * (1.0 / 32768); } } else { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { unsigned char byte1 = * bytes ++, byte2 = * bytes ++; long value = (int16_t) (((uint16_t) byte2 << 8) | (uint16_t) byte1); buffer [ichan] [isamp] = value * (1.0 / 32768); } } } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 16-bit).\nMissing samples set to zero."); } } break; case Melder_LINEAR_24_BIG_ENDIAN: { try { const int numberOfBytesPerSamplePerChannel = 3; if (numberOfChannels > (int) sizeof (double) / numberOfBytesPerSamplePerChannel) { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = bingeti3 (f) * (1.0 / 8388608); therror } } } else { // optimize long numberOfBytes = numberOfChannels * numberOfSamples * numberOfBytesPerSamplePerChannel; unsigned char *bytes = (unsigned char *) & buffer [numberOfChannels] [numberOfSamples] + sizeof (double) - numberOfBytes; if (fread (bytes, 1, numberOfBytes, f) < numberOfBytes) throw MelderError (); // read 24-bit data into last three-eigths of buffer if (numberOfChannels == 1) { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { unsigned char byte1 = * bytes ++, byte2 = * bytes ++, byte3 = * bytes ++; uint32_t unsignedValue = ((uint32_t) byte1 << 16) | ((uint32_t) byte2 << 8) | (uint32_t) byte3; if ((byte1 & 128) != 0) unsignedValue |= 0xFF000000; buffer [1] [isamp] = (int32_t) unsignedValue * (1.0 / 8388608); } } else { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { unsigned char byte1 = * bytes ++, byte2 = * bytes ++, byte3 = * bytes ++; uint32_t unsignedValue = ((uint32_t) byte1 << 16) | ((uint32_t) byte2 << 8) | (uint32_t) byte3; if ((byte1 & 128) != 0) unsignedValue |= 0xFF000000; buffer [ichan] [isamp] = (int32_t) unsignedValue * (1.0 / 8388608); } } } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 24-bit).\nMissing samples set to zero."); } } break; case Melder_LINEAR_24_LITTLE_ENDIAN: { try { const int numberOfBytesPerSamplePerChannel = 3; if (numberOfChannels > (int) sizeof (double) / numberOfBytesPerSamplePerChannel) { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = bingeti3LE (f) * (1.0 / 8388608); therror } } } else { // optimize long numberOfBytes = numberOfChannels * numberOfSamples * numberOfBytesPerSamplePerChannel; unsigned char *bytes = (unsigned char *) & buffer [numberOfChannels] [numberOfSamples] + sizeof (double) - numberOfBytes; if (fread (bytes, 1, numberOfBytes, f) < numberOfBytes) throw MelderError (); // read 24-bit data into last three-eights of buffer if (numberOfChannels == 1) { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { unsigned char byte1 = * bytes ++, byte2 = * bytes ++, byte3 = * bytes ++; uint32_t unsignedValue = ((uint32_t) byte3 << 16) | ((uint32_t) byte2 << 8) | (uint32_t) byte1; if ((byte3 & 128) != 0) unsignedValue |= 0xFF000000; buffer [1] [isamp] = (int32_t) unsignedValue * (1.0 / 8388608); } } else { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { unsigned char byte1 = * bytes ++, byte2 = * bytes ++, byte3 = * bytes ++; uint32_t unsignedValue = ((uint32_t) byte3 << 16) | ((uint32_t) byte2 << 8) | (uint32_t) byte1; if ((byte3 & 128) != 0) unsignedValue |= 0xFF000000; buffer [ichan] [isamp] = (int32_t) unsignedValue * (1.0 / 8388608); } } } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 24-bit).\nMissing samples set to zero."); } } break; case Melder_LINEAR_32_BIG_ENDIAN: try { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = bingeti4 (f) * (1.0 / 32768 / 65536); therror } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 32-bit).\nMissing samples set to zero."); } break; case Melder_LINEAR_32_LITTLE_ENDIAN: try { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = bingeti4LE (f) * (1.0 / 32768 / 65536); therror } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 32-bit).\nMissing samples set to zero."); } break; case Melder_IEEE_FLOAT_32_BIG_ENDIAN: try { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = bingetr4 (f); therror } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 32-bit floating point).\nMissing samples set to zero."); } break; case Melder_IEEE_FLOAT_32_LITTLE_ENDIAN: try { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = bingetr4LE (f); therror } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 32-bit floating point).\nMissing samples set to zero."); } break; case Melder_MULAW: try { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = ulaw2linear [bingetu1 (f)] * (1.0 / 32768); therror } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 8-bit " "-law).\nMissing samples set to zero."); } break; case Melder_ALAW: try { for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { buffer [ichan] [isamp] = alaw2linear [bingetu1 (f)] * (1.0 / 32768); therror } } } catch (MelderError) { Melder_clearError (); Melder_warning ("File too small (", numberOfChannels, "-channel 8-bit A-law).\nMissing samples set to zero."); } break; case Melder_FLAC_COMPRESSION_16: case Melder_FLAC_COMPRESSION_24: case Melder_FLAC_COMPRESSION_32: Melder_readFlacFile (f, numberOfChannels, buffer, numberOfSamples); break; case Melder_MPEG_COMPRESSION_16: case Melder_MPEG_COMPRESSION_24: case Melder_MPEG_COMPRESSION_32: Melder_readMp3File (f, numberOfChannels, buffer, numberOfSamples); break; default: Melder_throw ("Unknown encoding %d.", encoding); } } catch (MelderError) { Melder_throw ("Audio samples not read from file."); } } void Melder_readAudioToShort (FILE *f, int numberOfChannels, int encoding, short *buffer, long numberOfSamples) { try { long n = numberOfSamples * numberOfChannels, i; static const unsigned short byteSwapTest = 3 * 256 + 1; switch (encoding) { case Melder_LINEAR_8_SIGNED: for (i = 0; i < n; i ++) { signed char value; if (! fread (& value, 1, 1, f)) Melder_throw ("File too small (mono 8-bit)."); buffer [i] = value * 256; } break; case Melder_LINEAR_8_UNSIGNED: for (i = 0; i < n; i ++) { buffer [i] = bingetu1 (f) * 256L - 32768; } break; case Melder_LINEAR_16_BIG_ENDIAN: fread (buffer, sizeof (short), n, f); if (* (unsigned char *) & byteSwapTest == 1) { for (i = 0; i < n; i ++) { unsigned short value = buffer [i]; buffer [i] = (value >> 8) + (value << 8); } } break; case Melder_LINEAR_16_LITTLE_ENDIAN: fread (buffer, sizeof (short), n, f); if (* (unsigned char *) & byteSwapTest == 3) { for (i = 0; i < n; i ++) { unsigned short value = buffer [i]; buffer [i] = (value >> 8) + (value << 8); } } break; case Melder_LINEAR_24_BIG_ENDIAN: for (i = 0; i < n; i ++) { buffer [i] = bingeti3 (f) / 256; // BUG: truncation; not ideal } break; case Melder_LINEAR_24_LITTLE_ENDIAN: for (i = 0; i < n; i ++) { buffer [i] = bingeti3LE (f) / 256; // BUG: truncation; not ideal } break; case Melder_LINEAR_32_BIG_ENDIAN: for (i = 0; i < n; i ++) { buffer [i] = bingeti4 (f) / 65536; // BUG: truncation; not ideal } break; case Melder_LINEAR_32_LITTLE_ENDIAN: for (i = 0; i < n; i ++) { buffer [i] = bingeti4LE (f) / 65536; // BUG: truncation; not ideal } break; case Melder_IEEE_FLOAT_32_BIG_ENDIAN: for (i = 0; i < n; i ++) { buffer [i] = bingetr4 (f) * 32768; // BUG: truncation; not ideal } break; case Melder_IEEE_FLOAT_32_LITTLE_ENDIAN: for (i = 0; i < n; i ++) { buffer [i] = bingetr4LE (f) * 32768; // BUG: truncation; not ideal } break; case Melder_MULAW: for (i = 0; i < n; i ++) { buffer [i] = ulaw2linear [bingetu1 (f)]; } break; case Melder_ALAW: for (i = 0; i < n; i ++) { buffer [i] = alaw2linear [bingetu1 (f)]; } break; default: Melder_throw ("Unknown encoding %d.", encoding); } } catch (MelderError) { Melder_clearError (); Melder_warning (L"Audio file too short. Missing samples were set to zero."); } } void MelderFile_writeShortToAudio (MelderFile file, int numberOfChannels, int encoding, const short *buffer, long numberOfSamples) { try { FILE *f = file -> filePointer; if (f == NULL) Melder_throw ("File not open."); long n = numberOfSamples * numberOfChannels, start = 0, step = 1, i; if (numberOfChannels < 0) { n = numberOfSamples * 2; // stereo step = 2; // only one channel will be written if (numberOfChannels == -2) { start = 1; // right channel } numberOfChannels = 1; } switch (encoding) { case Melder_LINEAR_8_SIGNED: for (i = start; i < n; i += step) binputi1 (buffer [i] >> 8, f); break; case Melder_LINEAR_8_UNSIGNED: for (i = start; i < n; i += step) binputu1 ((buffer [i] >> 8) + 128, f); break; case Melder_LINEAR_16_BIG_ENDIAN: for (i = start; i < n; i += step) binputi2 (buffer [i], f); break; case Melder_LINEAR_16_LITTLE_ENDIAN: for (i = start; i < n; i += step) binputi2LE (buffer [i], f); break; case Melder_LINEAR_24_BIG_ENDIAN: for (i = start; i < n; i += step) binputi3 (buffer [i] << 8, f); break; case Melder_LINEAR_24_LITTLE_ENDIAN: for (i = start; i < n; i += step) binputi3LE (buffer [i] << 8, f); break; case Melder_LINEAR_32_BIG_ENDIAN: for (i = start; i < n; i += step) binputi4 (buffer [i] << 16, f); break; case Melder_LINEAR_32_LITTLE_ENDIAN: for (i = start; i < n; i += step) binputi4LE (buffer [i] << 16, f); break; case Melder_IEEE_FLOAT_32_BIG_ENDIAN: for (i = start; i < n; i += step) binputr4 (buffer [i] / 32768.0, f); break; case Melder_IEEE_FLOAT_32_LITTLE_ENDIAN: for (i = start; i < n; i += step) binputr4LE (buffer [i] / 32768.0, f); break; case Melder_FLAC_COMPRESSION_16: case Melder_FLAC_COMPRESSION_24: case Melder_FLAC_COMPRESSION_32: if (! file -> flacEncoder) Melder_throw ("FLAC encoder not initialized."); for (i = start; i < n; i += step * numberOfChannels) { FLAC__int32 samples [FLAC__MAX_CHANNELS]; for (int ichan = 1; ichan <= numberOfChannels; ichan ++) samples [ichan - 1] = buffer [i + ichan - 1]; if (! FLAC__stream_encoder_process_interleaved (file -> flacEncoder, samples, 1)) Melder_throw ("Error encoding FLAC stream."); } break; case Melder_MULAW: case Melder_ALAW: default: Melder_throw ("Unknown encoding %d.", encoding); } } catch (MelderError) { Melder_throw ("Samples not written to audio file."); } } void MelderFile_writeFloatToAudio (MelderFile file, int numberOfChannels, int encoding, double **buffer, long numberOfSamples, int warnIfClipped) { try { FILE *f = file -> filePointer; if (f == NULL) Melder_throw ("File not open."); long nclipped = 0; switch (encoding) { case Melder_LINEAR_8_SIGNED: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { long value = round (buffer [ichan] [isamp] * 128); if (value < -128) { value = -128; nclipped ++; } if (value > 127) { value = 127; nclipped ++; } binputi1 (value, f); } } break; case Melder_LINEAR_8_UNSIGNED: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { long value = floor ((buffer [ichan] [isamp] + 1.0) * 128); if (value < 0) { value = 0; nclipped ++; } if (value > 255) { value = 255; nclipped ++; } binputu1 (value, f); } } break; case Melder_LINEAR_16_BIG_ENDIAN: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { long value = round (buffer [ichan] [isamp] * 32768); if (value < -32768) { value = -32768; nclipped ++; } if (value > 32767) { value = 32767; nclipped ++; } binputi2 (value, f); } } break; case Melder_LINEAR_16_LITTLE_ENDIAN: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { long value = round (buffer [ichan] [isamp] * 32768); if (value < -32768) { value = -32768; nclipped ++; } if (value > 32767) { value = 32767; nclipped ++; } binputi2LE (value, f); } } break; case Melder_LINEAR_24_BIG_ENDIAN: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { long value = round (buffer [ichan] [isamp] * 8388608); if (value < -8388608) { value = -8388608; nclipped ++; } if (value > 8388607) { value = 8388607; nclipped ++; } binputi3 (value, f); } } break; case Melder_LINEAR_24_LITTLE_ENDIAN: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { long value = round (buffer [ichan] [isamp] * 8388608); if (value < -8388608) { value = -8388608; nclipped ++; } if (value > 8388607) { value = 8388607; nclipped ++; } binputi3LE (value, f); } } break; case Melder_LINEAR_32_BIG_ENDIAN: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { double value = round (buffer [ichan] [isamp] * 2147483648.0); if (value < -2147483648.0) { value = -2147483648.0; nclipped ++; } if (value > 2147483647.0) { value = 2147483647.0; nclipped ++; } binputi4 (value, f); } } break; case Melder_LINEAR_32_LITTLE_ENDIAN: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { double value = round (buffer [ichan] [isamp] * 2147483648.0); if (value < -2147483648.0) { value = -2147483648.0; nclipped ++; } if (value > 2147483647.0) { value = 2147483647.0; nclipped ++; } binputi4LE (value, f); } } break; case Melder_IEEE_FLOAT_32_BIG_ENDIAN: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { double value = buffer [ichan] [isamp]; binputr4 (value, f); } } break; case Melder_IEEE_FLOAT_32_LITTLE_ENDIAN: for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { double value = buffer [ichan] [isamp]; binputr4LE (value, f); } } break; case Melder_FLAC_COMPRESSION_16: case Melder_FLAC_COMPRESSION_24: case Melder_FLAC_COMPRESSION_32: if (! file -> flacEncoder) Melder_throw ("FLAC encoder not initialized."); for (long isamp = 1; isamp <= numberOfSamples; isamp ++) { FLAC__int32 samples [FLAC__MAX_CHANNELS]; for (long ichan = 1; ichan <= numberOfChannels; ichan ++) { long value = round (buffer [ichan] [isamp] * 32768); if (value < -32768) { value = -32768; nclipped ++; } if (value > 32767) { value = 32767; nclipped ++; } samples [ichan - 1] = (FLAC__int32) value; } if (! FLAC__stream_encoder_process_interleaved (file -> flacEncoder, samples, 1)) Melder_throw ("Error encoding FLAC stream."); } break; case Melder_MULAW: case Melder_ALAW: default: Melder_throw (L"Unknown format."); } if (nclipped > 0 && warnIfClipped) Melder_warning ("Writing samples to audio file: ", nclipped, " out of ", numberOfSamples, " samples have been clipped.\n" "Advice: you could scale the amplitudes or write to a binary file."); } catch (MelderError) { Melder_throw ("Samples not written to audio file."); } } /* End of file melder_audiofiles.cpp */ sources_5316/sys/Editor.h0000644000176700017670000002431411717711211014143 0ustar paulpaul#ifndef _Editor_h_ #define _Editor_h_ /* Editor.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection.h" #include "Gui.h" #include "Ui.h" #include "Graphics.h" #include "Editor_enums.h" Thing_declare (Editor); Thing_define (EditorMenu, Thing) { // new data: public: Editor d_editor; const wchar *menuTitle; GuiObject menuWidget; Ordered commands; // overridden methods: virtual void v_destroy (); }; Thing_define (EditorCommand, Thing) { // new data: public: Editor d_editor; EditorMenu menu; const wchar *itemTitle; GuiObject itemWidget; void (*commandCallback) (Editor editor_me, EditorCommand cmd, UiForm sendingForm, const wchar *sendingString, Interpreter interpreter); const wchar *script; UiForm d_uiform; // overridden methods: virtual void v_destroy (); }; Thing_define (Editor, Thing) { // new messages: public: void raise () /* * Message: "move your window to the front", i.e. * if you are invisible, then make your window visible at the front; * if you are iconized, then deiconize yourself at the front; * if you are already visible, just move your window to the front." */ { GuiObject_show (d_windowForm); } void dataChanged () /* * Message: "your data has changed by an action from *outside* yourself, * so you may e.g. like to redraw yourself." */ { v_dataChanged (); } void setDataChangedCallback (void (*dataChangedCallback) (Editor me, void *closure), void *dataChangedClosure) /* * Message from boss: "notify me by calling this dataChangedCallback every time your data is changed from *inside* yourself." * * In Praat, the dataChangedCallback is useful if there is more than one editor * with the same data; in this case, the owner of all those editors will * (in the dataChangedCallback it installed) notify the change to the other editors * by sending them a dataChanged () message. */ { d_dataChangedCallback = dataChangedCallback; d_dataChangedClosure = dataChangedClosure; } void broadcastDataChanged () /* * Message to boss: "my data has changed by an action from inside myself." * * The editor has to call this after every menu command, click or key press that causes a change in the data. */ { if (d_dataChangedCallback) d_dataChangedCallback (this, d_dataChangedClosure); } void setDestructionCallback (void (*destructionCallback) (Editor me, void *closure), void *destructionClosure) /* * Message from boss: "notify me by calling this destructionCallback every time you destroy yourself." * * In Praat, "destroying yourself" typically happens when the user closes the editor window * or when an object that is being viewed in an editor window is "Remove"d. * Typically, the boss will (in the destructionCallback it installed) remove all dangling references to this editor. */ { d_destructionCallback = destructionCallback; d_destructionClosure = destructionClosure; } void broadcastDestruction () /* * Message to boss: "I am destroying all my members and will free myself shortly." * * The editor calls this once, namely in Editor::v_destroy(). */ { if (d_destructionCallback) d_destructionCallback (this, d_destructionClosure); } void setPublicationCallback (void (*publicationCallback) (Editor me, void *closure, Data publication), void *publicationClosure) /* * Message from boss: "notify me by calling this publicationCallback every time you have a piece of data to publish." * * In Praat, editors typically "publish" a piece of data when the user chooses * things like "Extract selected sound", "Extract visible pitch curve", or "View spectral slice". * Typically, the boss will (in the publicationCallback it installed) install the published data in Praat's object list, * but the editor doesn't have to know that. */ { d_publicationCallback = publicationCallback; d_publicationClosure = publicationClosure; } void broadcastPublication (Data publication) /* * Message to boss: "I have a piece of data for you to publish." * * The editor has to calls this every time the user wants to "publish" ("Extract") some data from the editor. * * Constraint: "publication" has to be new data, either "extracted" or "copied" from data in the editor. * The boss becomes the owner of this published data, * so the call to broadcastPublication() has to transfer ownership of "publication". */ { if (d_publicationCallback) d_publicationCallback (this, d_publicationClosure, publication); } // new data: public: GuiObject d_windowParent, d_windowShell, d_windowForm; GuiObject menuBar, undoButton, searchButton; Ordered menus; Data data, previousData; // the data that can be displayed and edited bool d_ownData; wchar undoText [100]; Graphics pictureGraphics; void (*d_dataChangedCallback) (Editor me, void *closure); void *d_dataChangedClosure; void (*d_destructionCallback) (Editor me, void *closure); void *d_destructionClosure; void (*d_publicationCallback) (Editor me, void *closure, Data publication); void *d_publicationClosure; // overridden methods: protected: virtual void v_destroy (); virtual void v_info (); virtual void v_nameChanged (); // sets the window and icon titles to reflect the new name // new methods: public: virtual void v_goAway () { forget_nozero (this); } virtual bool v_hasMenuBar () { return true; } virtual bool v_canFullScreen () { return false; } virtual bool v_editable () { return true ; } virtual bool v_scriptable () { return true; } virtual void v_createMenuItems_file (EditorMenu menu); virtual void v_createMenuItems_edit (EditorMenu menu); virtual bool v_hasQueryMenu () { return true; } virtual void v_createMenuItems_query (EditorMenu menu); virtual void v_createMenuItems_query_info (EditorMenu menu); virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu) { (void) menu; } virtual void v_createChildren () { } virtual void v_dataChanged () { } virtual void v_saveData (); virtual void v_restoreData (); virtual void v_form_pictureWindow (EditorCommand cmd); virtual void v_ok_pictureWindow (EditorCommand cmd); virtual void v_do_pictureWindow (EditorCommand cmd); virtual void v_form_pictureMargins (EditorCommand cmd); virtual void v_ok_pictureMargins (EditorCommand cmd); virtual void v_do_pictureMargins (EditorCommand cmd); }; GuiObject EditorMenu_addCommand (EditorMenu me, const wchar *itemTitle, long flags, void (*commandCallback) (Editor me, EditorCommand, UiForm, const wchar *, Interpreter)); GuiObject EditorCommand_getItemWidget (EditorCommand me); EditorMenu Editor_addMenu (Editor me, const wchar *menuTitle, long flags); GuiObject EditorMenu_getMenuWidget (EditorMenu me); #define Editor_HIDDEN (1 << 14) GuiObject Editor_addCommand (Editor me, const wchar *menuTitle, const wchar *itemTitle, long flags, void (*commandCallback) (Editor me, EditorCommand cmd, UiForm sendingForm, const wchar *sendingString, Interpreter interpreter)); GuiObject Editor_addCommandScript (Editor me, const wchar *menuTitle, const wchar *itemTitle, long flags, const wchar *script); void Editor_setMenuSensitive (Editor me, const wchar_t *menu, int sensitive); /***** For inheritors. *****/ void Editor_init (Editor me, GuiObject parent, int x, int y , int width, int height, const wchar *title, Data data); /* This creates my shell and my d_windowForm, calls the v_createMenus and v_createChildren methods, and manages my shell and my d_windowForm. 'width' and 'height' determine the dimensions of the editor: if 'width' < 0, the width of the screen is added to it; if 'height' < 0, the height of the screeen is added to it; if 'width' is 0, the width is based on the children; if 'height' is 0, the height is base on the children. 'x' and 'y' determine the position of the editor: if 'x' > 0, 'x' is the distance to the left edge of the screen; if 'x' < 0, |'x'| is the distance to the right edge of the screen; if 'x' is 0, the editor is horizontally centred on the screen; if 'y' > 0, 'y' is the distance to the top of the screen; if 'y' < 0, |'y'| is the distance to the bottom of the screen; if 'y' is 0, the editor is vertically centred on the screen; This routine does not transfer ownership of 'data' to the Editor, and the Editor will not destroy 'data' when the Editor itself is destroyed. */ void Editor_save (Editor me, const wchar *text); // for Undo UiForm UiForm_createE (EditorCommand cmd, const wchar *title, const wchar *invokingButtonTitle, const wchar *helpTitle); void UiForm_parseStringE (EditorCommand cmd, const wchar *arguments, Interpreter interpreter); UiForm UiOutfile_createE (EditorCommand cmd, const wchar *title, const wchar *invokingButtonTitle, const wchar *helpTitle); UiForm UiInfile_createE (EditorCommand cmd, const wchar_t *title, const wchar_t *invokingButtonTitle, const wchar_t *helpTitle); EditorCommand Editor_getMenuCommand (Editor me, const wchar *menuTitle, const wchar *itemTitle); void Editor_doMenuCommand (Editor me, const wchar *command, const wchar *arguments, Interpreter interpreter); /* * The following two procedures are in praat_picture.cpp. * They allow editors to draw into the Picture window. */ Graphics praat_picture_editor_open (bool eraseFirst); void praat_picture_editor_close (void); void Editor_openPraatPicture (Editor me); void Editor_closePraatPicture (Editor me); void Editor_prefs (void); #endif /* End of file Editor.h */ sources_5316/sys/Editor.cpp0000644000176700017670000004333411753736771014523 0ustar paulpaul/* Editor.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* some GTK stuff added by Stefan de Konink in 2008 and Franz Brausse in 2010 */ #include #include "ScriptEditor.h" #include "machine.h" #include "EditorM.h" #include "praat_script.h" #include "Preferences.h" #include "enums_getText.h" #include "Editor_enums.h" #include "enums_getValue.h" #include "Editor_enums.h" Thing_implement (Editor, Thing, 0); /********** PREFERENCES **********/ static struct { struct { bool eraseFirst; enum kEditor_writeNameAtTop writeNameAtTop; } picture; } preferences; void Editor_prefs (void) { Preferences_addBool (L"Editor.picture.eraseFirst", & preferences.picture.eraseFirst, true); Preferences_addEnum (L"Editor.picture.writeNameAtTop", & preferences.picture.writeNameAtTop, kEditor_writeNameAtTop, DEFAULT); } /********** class EditorCommand **********/ Thing_implement (EditorCommand, Thing, 0); void structEditorCommand :: v_destroy () { Melder_free (itemTitle); Melder_free (script); forget (d_uiform); EditorCommand_Parent :: v_destroy (); } /********** class EditorMenu **********/ Thing_implement (EditorMenu, Thing, 0); void structEditorMenu :: v_destroy () { Melder_free (menuTitle); forget (commands); EditorMenu_Parent :: v_destroy (); } /********** functions **********/ static void commonCallback (GUI_ARGS) { GUI_IAM (EditorCommand); #if gtk if (G_OBJECT_TYPE (w) == GTK_TYPE_RADIO_MENU_ITEM && ! gtk_check_menu_item_get_active (GTK_CHECK_MENU_ITEM (w))) { return; } #endif if (my d_editor && my d_editor -> v_scriptable () && ! wcsstr (my itemTitle, L"...")) { UiHistory_write (L"\n"); UiHistory_write (my itemTitle); } try { my commandCallback (my d_editor, me, NULL, NULL, NULL); therror } catch (MelderError) { Melder_error_ ("Menu command \"", my itemTitle, "\" not completed."); Melder_flushError (NULL); } } GuiObject EditorMenu_addCommand (EditorMenu me, const wchar *itemTitle, long flags, void (*commandCallback) (Editor me, EditorCommand cmd, UiForm sendingForm, const wchar *sendingString, Interpreter interpreter)) { autoEditorCommand thee = Thing_new (EditorCommand); thy d_editor = my d_editor; thy menu = me; thy itemTitle = Melder_wcsdup (itemTitle); thy itemWidget = commandCallback == NULL ? GuiMenu_addSeparator (my menuWidget) : flags & Editor_HIDDEN ? NULL : GuiMenu_addItem (my menuWidget, itemTitle, flags, commonCallback, thee.peek()); // DANGLE BUG: me can be killed by Collection_addItem(), but EditorCommand::destroy doesn't remove the item thy commandCallback = commandCallback; GuiObject result = thy itemWidget; Collection_addItem (my commands, thee.transfer()); return result; } /*GuiObject EditorCommand_getItemWidget (EditorCommand me) { return my itemWidget; }*/ EditorMenu Editor_addMenu (Editor me, const wchar *menuTitle, long flags) { autoEditorMenu thee = Thing_new (EditorMenu); thy d_editor = me; thy menuTitle = Melder_wcsdup (menuTitle); thy menuWidget = GuiMenuBar_addMenu (my menuBar, menuTitle, flags); thy commands = Ordered_create (); EditorMenu result = thee.peek(); Collection_addItem (my menus, thee.transfer()); return result; } /*GuiObject EditorMenu_getMenuWidget (EditorMenu me) { return my menuWidget; }*/ GuiObject Editor_addCommand (Editor me, const wchar *menuTitle, const wchar *itemTitle, long flags, void (*commandCallback) (Editor me, EditorCommand cmd, UiForm sendingForm, const wchar *sendingString, Interpreter interpreter)) { try { long numberOfMenus = my menus -> size; for (long imenu = 1; imenu <= numberOfMenus; imenu ++) { EditorMenu menu = (EditorMenu) my menus -> item [imenu]; if (wcsequ (menuTitle, menu -> menuTitle)) return EditorMenu_addCommand (menu, itemTitle, flags, commandCallback); } Melder_throw ("Menu \"", menuTitle, L"\" does not exist."); } catch (MelderError) { Melder_throw ("Command \"", itemTitle, "\" not inserted in menu \"", menuTitle, "."); } } static void Editor_scriptCallback (Editor me, EditorCommand cmd, UiForm sendingForm, const wchar *sendingString, Interpreter interpreter) { (void) sendingForm; (void) sendingString; (void) interpreter; DO_RunTheScriptFromAnyAddedEditorCommand (me, cmd -> script); } GuiObject Editor_addCommandScript (Editor me, const wchar *menuTitle, const wchar *itemTitle, long flags, const wchar *script) { try { long numberOfMenus = my menus -> size; for (long imenu = 1; imenu <= numberOfMenus; imenu ++) { EditorMenu menu = (EditorMenu) my menus -> item [imenu]; if (wcsequ (menuTitle, menu -> menuTitle)) { autoEditorCommand cmd = Thing_new (EditorCommand); cmd -> d_editor = me; cmd -> menu = menu; cmd -> itemTitle = Melder_wcsdup_f (itemTitle); cmd -> itemWidget = script == NULL ? GuiMenu_addSeparator (menu -> menuWidget) : GuiMenu_addItem (menu -> menuWidget, itemTitle, flags, commonCallback, cmd.peek()); // DANGLE BUG cmd -> commandCallback = Editor_scriptCallback; if (wcslen (script) == 0) { cmd -> script = Melder_wcsdup_f (L""); } else { structMelderFile file = { 0 }; Melder_relativePathToFile (script, & file); cmd -> script = Melder_wcsdup_f (Melder_fileToPath (& file)); } GuiObject result = cmd -> itemWidget; Collection_addItem (menu -> commands, cmd.transfer()); return result; } } Melder_throw ("Menu \"", menuTitle, L"\" does not exist."); } catch (MelderError) { Melder_throw ("Command \"", itemTitle, "\" not inserted in menu \"", menuTitle, "."); } } void Editor_setMenuSensitive (Editor me, const wchar *menuTitle, int sensitive) { int numberOfMenus = my menus -> size; for (int imenu = 1; imenu <= numberOfMenus; imenu ++) { EditorMenu menu = (EditorMenu) my menus -> item [imenu]; if (wcsequ (menuTitle, menu -> menuTitle)) { GuiObject_setSensitive (menu -> menuWidget, sensitive); return; } } } EditorCommand Editor_getMenuCommand (Editor me, const wchar *menuTitle, const wchar *itemTitle) { int numberOfMenus = my menus -> size; for (int imenu = 1; imenu <= numberOfMenus; imenu ++) { EditorMenu menu = (EditorMenu) my menus -> item [imenu]; if (wcsequ (menuTitle, menu -> menuTitle)) { int numberOfCommands = menu -> commands -> size, icommand; for (icommand = 1; icommand <= numberOfCommands; icommand ++) { EditorCommand command = (EditorCommand) menu -> commands -> item [icommand]; if (wcsequ (itemTitle, command -> itemTitle)) return command; } } } Melder_throw ("Command \"", itemTitle, "\" not found in menu \"", menuTitle, "\"."); } void Editor_doMenuCommand (Editor me, const wchar *commandTitle, const wchar *arguments, Interpreter interpreter) { int numberOfMenus = my menus -> size; for (int imenu = 1; imenu <= numberOfMenus; imenu ++) { EditorMenu menu = (EditorMenu) my menus -> item [imenu]; long numberOfCommands = menu -> commands -> size; for (long icommand = 1; icommand <= numberOfCommands; icommand ++) { EditorCommand command = (EditorCommand) menu -> commands -> item [icommand]; if (wcsequ (commandTitle, command -> itemTitle)) { command -> commandCallback (me, command, NULL, arguments, interpreter); therror return; } } } Melder_throw ("Command not available in ", my classInfo -> className, "."); } /********** class Editor **********/ void structEditor :: v_destroy () { MelderAudio_stopPlaying (MelderAudio_IMPLICIT); /* * The following command must be performed before the shell is destroyed. * Otherwise, we would be forgetting dangling command dialogs here. */ forget (menus); if (d_windowShell) { #if gtk Melder_assert (GTK_IS_WIDGET (d_windowShell)); gtk_widget_destroy (GTK_WIDGET (d_windowShell)); #elif motif XtDestroyWidget (d_windowShell); #elif ! useCarbon #endif } broadcastDestruction (); forget (previousData); if (d_ownData) forget (data); Editor_Parent :: v_destroy (); } void structEditor :: v_info () { MelderInfo_writeLine2 (L"Editor type: ", Thing_className (this)); MelderInfo_writeLine2 (L"Editor name: ", name ? name : L""); time_t today = time (NULL); MelderInfo_writeLine2 (L"Date: ", Melder_peekUtf8ToWcs (ctime (& today))); // includes a newline if (data) { MelderInfo_writeLine2 (L"Data type: ", data -> classInfo -> className); MelderInfo_writeLine2 (L"Data name: ", data -> name); } } void structEditor :: v_nameChanged () { if (name) GuiWindow_setTitle (d_windowShell, name); } void structEditor :: v_saveData () { if (! data) return; forget (previousData); previousData = Data_copy (data); } void structEditor :: v_restoreData () { if (data && previousData) Thing_swap (data, previousData); } static void menu_cb_close (EDITOR_ARGS) { EDITOR_IAM (Editor); my v_goAway (); } static void menu_cb_undo (EDITOR_ARGS) { EDITOR_IAM (Editor); my v_restoreData (); if (wcsnequ (my undoText, L"Undo", 4)) my undoText [0] = 'R', my undoText [1] = 'e'; else if (wcsnequ (my undoText, L"Redo", 4)) my undoText [0] = 'U', my undoText [1] = 'n'; else wcscpy (my undoText, L"Undo?"); #if gtk gtk_label_set_label (GTK_LABEL (gtk_bin_get_child (GTK_BIN (my undoButton))), Melder_peekWcsToUtf8 (my undoText)); #elif motif char *text_utf8 = Melder_peekWcsToUtf8 (my undoText); XtVaSetValues (my undoButton, XmNlabelString, text_utf8, NULL); #endif /* * Send a message to myself (e.g., I will redraw myself). */ my v_dataChanged (); /* * Send a message to my boss (e.g., she will notify the others that depend on me). */ my broadcastDataChanged (); } static void menu_cb_searchManual (EDITOR_ARGS) { EDITOR_IAM (Editor); Melder_search (); } static void menu_cb_newScript (EDITOR_ARGS) { EDITOR_IAM (Editor); (void) ScriptEditor_createFromText (my d_windowParent, me, NULL); therror } static void menu_cb_openScript (EDITOR_ARGS) { EDITOR_IAM (Editor); autoScriptEditor scriptEditor = ScriptEditor_createFromText (my d_windowParent, me, NULL); TextEditor_showOpen (scriptEditor.transfer()); } void structEditor :: v_createMenuItems_file (EditorMenu menu) { (void) menu; } void structEditor :: v_createMenuItems_edit (EditorMenu menu) { if (data) undoButton = EditorMenu_addCommand (menu, L"Cannot undo", GuiMenu_INSENSITIVE + 'Z', menu_cb_undo); } static void menu_cb_settingsReport (EDITOR_ARGS) { EDITOR_IAM (Editor); Thing_info (me); } static void menu_cb_info (EDITOR_ARGS) { EDITOR_IAM (Editor); if (my data) Thing_info (my data); } void structEditor :: v_createMenuItems_query (EditorMenu menu) { v_createMenuItems_query_info (menu); } void structEditor :: v_createMenuItems_query_info (EditorMenu menu) { EditorMenu_addCommand (menu, L"Editor info", 0, menu_cb_settingsReport); EditorMenu_addCommand (menu, L"Settings report", Editor_HIDDEN, menu_cb_settingsReport); if (data) { static MelderString title = { 0 }; MelderString_empty (& title); MelderString_append (& title, Thing_className (data), L" info"); EditorMenu_addCommand (menu, title.string, 0, menu_cb_info); } } void structEditor :: v_createMenus () { EditorMenu menu = Editor_addMenu (this, L"File", 0); v_createMenuItems_file (menu); if (v_editable ()) { menu = Editor_addMenu (this, L"Edit", 0); v_createMenuItems_edit (menu); } if (v_hasQueryMenu ()) { menu = Editor_addMenu (this, L"Query", 0); v_createMenuItems_query (menu); } } void structEditor :: v_form_pictureWindow (EditorCommand cmd) { LABEL (L"", L"Picture window:") BOOLEAN (L"Erase first", 1); } void structEditor :: v_ok_pictureWindow (EditorCommand cmd) { SET_INTEGER (L"Erase first", preferences.picture.eraseFirst); } void structEditor :: v_do_pictureWindow (EditorCommand cmd) { preferences.picture.eraseFirst = GET_INTEGER (L"Erase first"); } void structEditor :: v_form_pictureMargins (EditorCommand cmd) { Any radio = 0; LABEL (L"", L"Margins:") OPTIONMENU_ENUM (L"Write name at top", kEditor_writeNameAtTop, DEFAULT); } void structEditor :: v_ok_pictureMargins (EditorCommand cmd) { SET_ENUM (L"Write name at top", kEditor_writeNameAtTop, preferences.picture.writeNameAtTop); } void structEditor :: v_do_pictureMargins (EditorCommand cmd) { preferences.picture.writeNameAtTop = GET_ENUM (kEditor_writeNameAtTop, L"Write name at top"); } static void gui_window_cb_goAway (I) { iam (Editor); my v_goAway (); } void praat_addCommandsToEditor (Editor me); void Editor_init (Editor me, GuiObject parent, int x, int y, int width, int height, const wchar *title, Data data) { double xmin, ymin, widthmax, heightmax; Gui_getWindowPositioningBounds (& xmin, & ymin, & widthmax, & heightmax); /* * Negative widths are relative to the whole screen. */ if (width < 0) width += (int) widthmax; if (height < 0) height += (int) heightmax; /* * Don't start with a maximized window, because then the user doesn't know what a click on the maximize button means. */ if (width > (int) widthmax - 100) width = (int) widthmax - 100; if (height > (int) heightmax - 100) height = (int) heightmax - 100; /* * Make sure that the window has at least a sane size. * Just in case the user made the previous window very small (Praat's FunctionEditor saves the last size), * or the user edited the preferences file (which might save a window size). */ if (width < 200) width = 200; if (height < 150) height = 150; /* * Now that the size is right, establish the position. */ int left, right, top, bottom; if (x > 0) { /* * Positive x: relative to the left edge of the screen. */ left = (int) xmin + x; right = left + width; } else if (x < 0) { /* * Negative x: relative to the right edge of the screen. */ right = (int) xmin + (int) widthmax + x; left = right - width; } else { /* * Zero x: randomize between the left and right edge of the screen. */ left = NUMrandomInteger ((int) xmin + 4, (int) xmin + (int) widthmax - width - 4); right = left + width; } if (y > 0) { /* * Positive y: relative to the top of the screen. */ top = (int) ymin + y; bottom = top + height; } else if (y < 0) { /* * Negative y: relative to the bottom of the screen. */ bottom = (int) ymin + (int) heightmax + y; top = bottom - height; } else { /* * Zero y: randomize between the top and bottom of the screen. */ top = NUMrandomInteger ((int) ymin + 4, (int) ymin + (int) heightmax - height - 4); //Melder_casual ("%d %d %d %d", (int) ymin, (int) heightmax, height, top); bottom = top + height; } #if defined (macintoshXXX) || gtk top += Machine_getTitleBarHeight (); bottom += Machine_getTitleBarHeight (); #endif my d_windowParent = parent; // probably praat.topShell my d_windowForm = GuiWindow_create (parent, left, top, width, height, title, gui_window_cb_goAway, me, my v_canFullScreen () ? GuiWindow_FULLSCREEN : 0); my d_windowShell = GuiObject_parent (my d_windowForm); // note that GuiObject_parent (my shell) will be NULL! //Melder_casual ("my parent %ld my d_windowForm %ld my shell %ld", my parent, my d_windowForm, my shell); Thing_setName (me, title); my data = data; /* Create menus. */ if (my v_hasMenuBar ()) { my menus = Ordered_create (); my menuBar = Gui_addMenuBar (my d_windowForm); my v_createMenus (); EditorMenu helpMenu = Editor_addMenu (me, L"Help", 0); my v_createHelpMenuItems (helpMenu); EditorMenu_addCommand (helpMenu, L"-- search --", 0, NULL); my searchButton = EditorMenu_addCommand (helpMenu, L"Search manual...", 'M', menu_cb_searchManual); if (my v_scriptable ()) { Editor_addCommand (me, L"File", L"New editor script", 0, menu_cb_newScript); Editor_addCommand (me, L"File", L"Open editor script...", 0, menu_cb_openScript); Editor_addCommand (me, L"File", L"-- after script --", 0, 0); } /* * Add the scripted commands. */ praat_addCommandsToEditor (me); Editor_addCommand (me, L"File", L"Close", 'W', menu_cb_close); GuiObject_show (my menuBar); } my v_createChildren (); GuiObject_show (my d_windowForm); } void Editor_save (Editor me, const wchar *text) { my v_saveData (); if (! my undoButton) return; GuiObject_setSensitive (my undoButton, True); swprintf (my undoText, 100, L"Undo %ls", text); #if gtk gtk_label_set_label (GTK_LABEL (gtk_bin_get_child (GTK_BIN (my undoButton))), Melder_peekWcsToUtf8 (my undoText)); #elif motif char *text_utf8 = Melder_peekWcsToUtf8 (my undoText); XtVaSetValues (my undoButton, XmNlabelString, text_utf8, NULL); #endif } void Editor_openPraatPicture (Editor me) { my pictureGraphics = praat_picture_editor_open (preferences.picture.eraseFirst); } void Editor_closePraatPicture (Editor me) { if (my data != NULL && preferences.picture.writeNameAtTop != kEditor_writeNameAtTop_NO) { Graphics_setNumberSignIsBold (my pictureGraphics, false); Graphics_setPercentSignIsItalic (my pictureGraphics, false); Graphics_setCircumflexIsSuperscript (my pictureGraphics, false); Graphics_setUnderscoreIsSubscript (my pictureGraphics, false); Graphics_textTop (my pictureGraphics, preferences.picture.writeNameAtTop == kEditor_writeNameAtTop_FAR, my data -> name); Graphics_setNumberSignIsBold (my pictureGraphics, true); Graphics_setPercentSignIsItalic (my pictureGraphics, true); Graphics_setCircumflexIsSuperscript (my pictureGraphics, true); Graphics_setUnderscoreIsSubscript (my pictureGraphics, true); } praat_picture_editor_close (); } /* End of file Editor.cpp */ sources_5316/sys/Graphics_mouse.cpp0000644000176700017670000000537211641163102016217 0ustar paulpaul/* Graphics_mouse.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "GraphicsP.h" #include "Gui.h" #if cairo static bool theMouseDown = true; #endif /* * Graphics_mouseStillDown () can only be used in a loop * if Graphics_getMouseLocation () is called in that same loop. * This is because the Xwin version requires that. */ bool structGraphicsScreen :: v_mouseStillDown () { #if cairo if (theMouseDown) return true; else { theMouseDown = true; return false; } #elif win return motif_win_mouseStillDown (); #elif mac return StillDown (); #endif } bool Graphics_mouseStillDown (Graphics me) { return my v_mouseStillDown (); } void structGraphicsScreen :: v_getMouseLocation (double *xWC, double *yWC) { #if cairo GdkEvent *gevent = gdk_display_get_event (d_display); if (gevent != NULL) { if (gevent -> type == GDK_BUTTON_RELEASE) { theMouseDown = false; } gdk_event_free (gevent); } gint xDC, yDC; gdk_window_get_pointer (d_window, & xDC, & yDC, NULL); Graphics_DCtoWC (this, xDC, yDC, xWC, yWC); #elif win POINT pos; if (! GetCursorPos (& pos)) { Melder_warning (L"Cannot get cursor position."); return; } ScreenToClient (d_winWindow, & pos); Graphics_DCtoWC (this, pos. x, pos. y, xWC, yWC); #elif mac if (HIGetMousePosition != NULL && false) { // AVAILABLE_MAC_OS_X_VERSION_10_5_AND_LATER //Melder_casual ("HIGetMousePosition exists"); HIPoint mouseLoc; HIGetMousePosition (kHICoordSpaceWindow, GetWindowFromPort (d_macPort), & mouseLoc); Graphics_DCtoWC (this, mouseLoc. x, mouseLoc. y, xWC, yWC); } else { Point mouseLoc; GetMouse (& mouseLoc); // AVAILABLE_MAC_OS_X_VERSION_10_0_AND_LATER_BUT_DEPRECATED_IN_MAC_OS_X_VERSION_10_5 Graphics_DCtoWC (this, mouseLoc. h, mouseLoc. v, xWC, yWC); } #endif } void Graphics_getMouseLocation (Graphics me, double *xWC, double *yWC) { my v_getMouseLocation (xWC, yWC); } void Graphics_waitMouseUp (Graphics me) { while (Graphics_mouseStillDown (me)) { double xWC, yWC; Graphics_getMouseLocation (me, & xWC, & yWC); } } /* End of file Graphics_mouse.cpp */ sources_5316/sys/oo_WRITE_CACHE.h0000644000176700017670000000766711724670615015215 0ustar paulpaul/* oo_WRITE_CACHE.h * * Copyright (C) 1994-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) \ cacput##storage (my x, f); #define oo_ARRAY(type,storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ cacput##storage (my x [i], f); #define oo_SET(type,storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ cacput##storage (my x [i], f); #define oo_VECTOR(type,storage,x,min,max) \ if (my x) \ NUMvector_writeCache_##storage (my x, min, max, f); #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) \ if (my x) \ NUMmatrix_writeCache_##storage (my x, row1, row2, col1, col2, f); #define oo_ENUMx(type,storage,Type,x) \ cacput##storage (my x, f, & enum_##Type); #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) \ for (int i = 0; i < n; i ++) \ cacput##storage (my x [i], f, & enum_##Type); #define oo_ENUMx_SET(type,storage,Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ cacput##storage (my x [i], f, & enum_##Type); #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) \ if (my x) \ NUMvector_writeCache_##storage (my x, min, max, f); #define oo_STRINGx(storage,x) \ cacput##storage (my x, f); #define oo_STRINGx_ARRAY(storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ cacput##storage (my x [i], f); #define oo_STRINGx_SET(storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ cacput##storage (my x [i], f); #define oo_STRINGx_VECTOR(storage,x,min,max) \ if (max >= min) \ for (long i = min; i <= max; i ++) \ cacput##storage (my x [i], f); #define oo_STRUCT(Type,x) \ Type##_writeCache (& my x, f); #define oo_STRUCT_ARRAY(Type,x,cap,n) \ for (int i = 0; i < n; i ++) \ Type##_writeCache (& my x [i], f); #define oo_STRUCT_SET(Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ Type##_writeCache (& my x [i], f); #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ if (max >= min) \ for (long i = min; i <= max; i ++) \ Type##_writeCache (& my x [i], f); #define oo_OBJECT(Class,version,x) \ cacputex (my x != NULL, f); \ if (my x) \ Data_writeCache (my x, f); #define oo_COLLECTION(Class,x,ItemClass,version) \ cacputi4 (my x ? my x -> size : 0, f); \ if (my x) { \ for (long i = 1; i <= my x -> size; i ++) { \ ItemClass data = (ItemClass) my x -> item [i]; \ class##ItemClass -> writeCache (data, f); \ } \ } #define oo_DEFINE_STRUCT(Type) \ static void Type##_writeCache (Type me, CACHE *f) { #define oo_END_STRUCT(Type) \ } #define oo_DEFINE_CLASS(Class,Parent) \ static void class##Class##_writeCache (I, CACHE *f) { \ iam (Class); \ inherited (Class) writeCache (me, f); #define oo_END_CLASS(Class) \ } #define oo_IF(condition) \ if (condition) { #define oo_ENDIF \ } #define oo_FROM(from) #define oo_ENDFROM #define oo_VERSION(version) #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 0 #define oo_READING 0 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 1 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 1 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_WRITE_CACHE.h */ sources_5316/sys/ScriptEditor.cpp0000644000176700017670000003212011633661466015672 0ustar paulpaul/* ScriptEditor.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ScriptEditor.h" #include "longchar.h" #include "praatP.h" #include "EditorM.h" Thing_implement (ScriptEditor, TextEditor, 0); static Collection theScriptEditors; int ScriptEditors_dirty (void) { if (! theScriptEditors) return FALSE; for (long i = 1; i <= theScriptEditors -> size; i ++) { ScriptEditor me = (ScriptEditor) theScriptEditors -> item [i]; if (my dirty) return TRUE; } return FALSE; } void structScriptEditor :: v_destroy () { Melder_free (environmentName); forget (interpreter); forget (argsDialog); if (theScriptEditors) Collection_undangleItem (theScriptEditors, this); ScriptEditor_Parent :: v_destroy (); } void structScriptEditor :: v_nameChanged () { bool dirtinessAlreadyShown = GuiWindow_setDirty (d_windowShell, dirty); static MelderString buffer = { 0 }; MelderString_copy (& buffer, name ? L"Script" : L"untitled script"); if (editorClass) MelderString_append (& buffer, L" [", environmentName, L"]"); if (name) MelderString_append (& buffer, L" ", MelderFile_messageName (& file)); if (dirty && ! dirtinessAlreadyShown) MelderString_append (& buffer, L" (modified)"); GuiWindow_setTitle (d_windowShell, buffer.string); #if motif XtVaSetValues (d_windowShell, XmNiconName, "Script", NULL); #endif } void structScriptEditor :: v_goAway () { if (interpreter -> running) { Melder_error_ ("Cannot close the script window while the script is running or paused. Please close or continue the pause or demo window."); Melder_flushError (NULL); } else { ScriptEditor_Parent :: v_goAway (); } } static void args_ok (UiForm sendingForm, const wchar_t *sendingString_dummy, Interpreter interpreter_dummy, const wchar_t *invokingButtonTitle, bool modified_dummy, I) { iam (ScriptEditor); (void) sendingString_dummy; (void) interpreter_dummy; (void) invokingButtonTitle; (void) modified_dummy; structMelderFile file = { 0 }; wchar *text = GuiText_getString (my textWidget); // BUG: auto if (my name) { Melder_pathToFile (my name, & file); MelderFile_setDefaultDir (& file); } Melder_includeIncludeFiles (& text); therror Interpreter_getArgumentsFromDialog (my interpreter, sendingForm); autoPraatBackground background; if (my name) MelderFile_setDefaultDir (& file); Interpreter_run (my interpreter, text); therror Melder_free (text); } static void run (ScriptEditor me, wchar_t **text) { structMelderFile file = { 0 }; if (my name) { Melder_pathToFile (my name, & file); MelderFile_setDefaultDir (& file); } Melder_includeIncludeFiles (text); therror int npar = Interpreter_readParameters (my interpreter, *text); therror if (npar) { /* * Pop up a dialog box for querying the arguments. */ forget (my argsDialog); my argsDialog = Interpreter_createForm (my interpreter, my d_windowShell, NULL, args_ok, me); UiForm_do (my argsDialog, false); } else { autoPraatBackground background; if (my name) MelderFile_setDefaultDir (& file); Interpreter_run (my interpreter, *text); therror } } static void menu_cb_run (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); if (my interpreter -> running) Melder_throw ("The script is already running (paused). Please close or continue the pause or demo window."); autostring text = GuiText_getString (my textWidget); // not an autostring (the text pointer can be changed by including include files) run (me, & text); } static void menu_cb_runSelection (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); if (my interpreter -> running) Melder_throw (L"The script is already running (paused). Please close or continue the pause or demo window."); autostring text = GuiText_getSelection (my textWidget); if (text.peek() == NULL) Melder_throw ("No text selected."); run (me, & text); } static void menu_cb_addToMenu (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); EDITOR_FORM (L"Add to menu", L"Add to fixed menu...") WORD (L"Window", L"?") SENTENCE (L"Menu", L"File") SENTENCE (L"Command", L"Do it...") SENTENCE (L"After command", L"") INTEGER (L"Depth", L"0") LABEL (L"", L"Script file:") TEXTFIELD (L"Script", L"") EDITOR_OK if (my editorClass) SET_STRING (L"Window", my editorClass -> className) if (my name) SET_STRING (L"Script", my name) else SET_STRING (L"Script", L"(please save your script first)") EDITOR_DO praat_addMenuCommandScript (GET_STRING (L"Window"), GET_STRING (L"Menu"), GET_STRING (L"Command"), GET_STRING (L"After command"), GET_INTEGER (L"Depth"), GET_STRING (L"Script")); praat_show (); EDITOR_END } static void menu_cb_addToFixedMenu (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); EDITOR_FORM (L"Add to fixed menu", L"Add to fixed menu..."); RADIO (L"Window", 1) RADIOBUTTON (L"Objects") RADIOBUTTON (L"Picture") SENTENCE (L"Menu", L"New") SENTENCE (L"Command", L"Do it...") SENTENCE (L"After command", L"") INTEGER (L"Depth", L"0") LABEL (L"", L"Script file:") TEXTFIELD (L"Script", L"") EDITOR_OK if (my name) SET_STRING (L"Script", my name) else SET_STRING (L"Script", L"(please save your script first)") EDITOR_DO praat_addMenuCommandScript (GET_STRING (L"Window"), GET_STRING (L"Menu"), GET_STRING (L"Command"), GET_STRING (L"After command"), GET_INTEGER (L"Depth"), GET_STRING (L"Script")); praat_show (); EDITOR_END } static void menu_cb_addToDynamicMenu (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); EDITOR_FORM (L"Add to dynamic menu", L"Add to dynamic menu...") WORD (L"Class 1", L"Sound") INTEGER (L"Number 1", L"0") WORD (L"Class 2", L"") INTEGER (L"Number 2", L"0") WORD (L"Class 3", L"") INTEGER (L"Number 3", L"0") SENTENCE (L"Command", L"Do it...") SENTENCE (L"After command", L"") INTEGER (L"Depth", L"0") LABEL (L"", L"Script file:") TEXTFIELD (L"Script", L"") EDITOR_OK if (my name) SET_STRING (L"Script", my name) else SET_STRING (L"Script", L"(please save your script first)") EDITOR_DO praat_addActionScript (GET_STRING (L"Class 1"), GET_INTEGER (L"Number 1"), GET_STRING (L"Class 2"), GET_INTEGER (L"Number 2"), GET_STRING (L"Class 3"), GET_INTEGER (L"Number 3"), GET_STRING (L"Command"), GET_STRING (L"After command"), GET_INTEGER (L"Depth"), GET_STRING (L"Script")); praat_show (); EDITOR_END } static void menu_cb_clearHistory (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); UiHistory_clear (); } static void menu_cb_pasteHistory (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); wchar *history = UiHistory_get (); if (history == NULL || history [0] == '\0') Melder_throw ("No history."); long length = wcslen (history); if (history [length - 1] != '\n') { UiHistory_write (L"\n"); history = UiHistory_get (); length = wcslen (history); } if (history [0] == '\n') { history ++; length --; } long first = 0, last = 0; wchar_t *text = GuiText_getStringAndSelectionPosition (my textWidget, & first, & last); Melder_free (text); GuiText_replace (my textWidget, first, last, history); GuiText_setSelection (my textWidget, first, first + length); GuiText_scrollToSelection (my textWidget); } static void menu_cb_expandIncludeFiles (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); structMelderFile file = { 0 }; autostring text = GuiText_getString (my textWidget); if (my name) { Melder_pathToFile (my name, & file); MelderFile_setDefaultDir (& file); } Melder_includeIncludeFiles (& text); therror GuiText_setString (my textWidget, text.peek()); } static void menu_cb_AboutScriptEditor (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"ScriptEditor"); } static void menu_cb_ScriptingTutorial (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"Scripting"); } static void menu_cb_ScriptingExamples (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"Scripting examples"); } static void menu_cb_PraatScript (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"Praat script"); } static void menu_cb_FormulasTutorial (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"Formulas"); } static void menu_cb_DemoWindow (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"Demo window"); } static void menu_cb_TheHistoryMechanism (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"History mechanism"); } static void menu_cb_InitializationScripts (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"Initialization script"); } static void menu_cb_AddingToAFixedMenu (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"Add to fixed menu..."); } static void menu_cb_AddingToADynamicMenu (EDITOR_ARGS) { EDITOR_IAM (ScriptEditor); Melder_help (L"Add to dynamic menu..."); } void structScriptEditor :: v_createMenus () { ScriptEditor_Parent :: v_createMenus (); if (editorClass) { Editor_addCommand (this, L"File", L"Add to menu...", 0, menu_cb_addToMenu); } else { Editor_addCommand (this, L"File", L"Add to fixed menu...", 0, menu_cb_addToFixedMenu); Editor_addCommand (this, L"File", L"Add to dynamic menu...", 0, menu_cb_addToDynamicMenu); } Editor_addCommand (this, L"File", L"-- close --", 0, NULL); Editor_addCommand (this, L"Edit", L"-- history --", 0, 0); Editor_addCommand (this, L"Edit", L"Clear history", 0, menu_cb_clearHistory); Editor_addCommand (this, L"Edit", L"Paste history", 'H', menu_cb_pasteHistory); Editor_addCommand (this, L"Convert", L"-- expand --", 0, 0); Editor_addCommand (this, L"Convert", L"Expand include files", 0, menu_cb_expandIncludeFiles); Editor_addMenu (this, L"Run", 0); Editor_addCommand (this, L"Run", L"Run", 'R', menu_cb_run); Editor_addCommand (this, L"Run", L"Run selection", 'T', menu_cb_runSelection); } void structScriptEditor :: v_createHelpMenuItems (EditorMenu menu) { ScriptEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"About ScriptEditor", '?', menu_cb_AboutScriptEditor); EditorMenu_addCommand (menu, L"Scripting tutorial", 0, menu_cb_ScriptingTutorial); EditorMenu_addCommand (menu, L"Scripting examples", 0, menu_cb_ScriptingExamples); EditorMenu_addCommand (menu, L"Praat script", 0, menu_cb_PraatScript); EditorMenu_addCommand (menu, L"Formulas tutorial", 0, menu_cb_FormulasTutorial); EditorMenu_addCommand (menu, L"Demo window", 0, menu_cb_DemoWindow); EditorMenu_addCommand (menu, L"-- help history --", 0, NULL); EditorMenu_addCommand (menu, L"The History mechanism", 0, menu_cb_TheHistoryMechanism); EditorMenu_addCommand (menu, L"Initialization scripts", 0, menu_cb_InitializationScripts); EditorMenu_addCommand (menu, L"-- help add --", 0, NULL); EditorMenu_addCommand (menu, L"Adding to a fixed menu", 0, menu_cb_AddingToAFixedMenu); EditorMenu_addCommand (menu, L"Adding to a dynamic menu", 0, menu_cb_AddingToADynamicMenu); } void structScriptEditor :: init (GuiObject parent_, Editor environment_, const wchar *initialText_) { if (environment_ != NULL) { environmentName = Melder_wcsdup (environment_ -> name); editorClass = environment_ -> classInfo; } structTextEditor::init (parent_, initialText_); interpreter = Interpreter_createFromEnvironment (environment_); if (theScriptEditors == NULL) { theScriptEditors = Collection_create (NULL, 10); Collection_dontOwnItems (theScriptEditors); } Collection_addItem (theScriptEditors, this); } ScriptEditor ScriptEditor_createFromText (GuiObject parent, Editor environment, const wchar *initialText) { try { autoScriptEditor me = Thing_new (ScriptEditor); me.peek() -> structScriptEditor :: init (parent, environment, initialText); return me.transfer(); } catch (MelderError) { Melder_throw ("Script window not created."); } } ScriptEditor ScriptEditor_createFromScript (GuiObject parent, Editor environment, Script script) { try { if (theScriptEditors) { for (long ieditor = 1; ieditor <= theScriptEditors -> size; ieditor ++) { ScriptEditor editor = (ScriptEditor) theScriptEditors -> item [ieditor]; if (MelderFile_equal (& script -> file, & editor -> file)) { editor -> raise (); Melder_error_ ("The script ", & script -> file, " is already open and has been moved to the front."); if (editor -> dirty) Melder_error_ ("Choose \"Reopen from disk\" if you want to revert to the old version."); Melder_flushError (NULL); return NULL; // safe NULL } } } autostring text = MelderFile_readText (& script -> file); autoScriptEditor me = ScriptEditor_createFromText (parent, environment, text.peek()); MelderFile_copy (& script -> file, & my file); Thing_setName (me.peek(), Melder_fileToPath (& script -> file)); therror return me.transfer(); } catch (MelderError) { Melder_throw ("Script window not created."); } } /* End of file ScriptEditor.cpp */ sources_5316/sys/UiPause.cpp0000644000176700017670000001752411633675046014644 0ustar paulpaul/* UiPause.cpp * * Copyright (C) 2009-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2009/01/20 created * pb 2010/07/13 GTK * pb 2010/07/26 removed UiFile_hide * pb 2011/02/01 cancelContinueButton * pb 2011/05/15 C++ * pb 2011/07/12 C++ */ #include "UiPause.h" #include "praatP.h" static UiForm thePauseForm = NULL; static Any thePauseFormRadio = NULL; static int thePauseForm_clicked = 0; static int theCancelContinueButton = 0; static int theEventLoopDepth = 0; static void thePauseFormOkCallback (UiForm sendingForm, const wchar *sendingString, Interpreter interpreter, const wchar *invokingButtonTitle, bool modified, void *closure) { (void) sendingForm; (void) sendingString; (void) interpreter; (void) invokingButtonTitle; (void) modified; /* BUG: should also restore praatP. editor. */ /* * Get the data from the pause form. */ thePauseForm_clicked = UiForm_getClickedContinueButton (thePauseForm); if (thePauseForm_clicked != theCancelContinueButton) UiForm_Interpreter_addVariables (thePauseForm, (Interpreter) closure); // 'closure', not 'interpreter' or 'theInterpreter'! } static void thePauseFormCancelCallback (Any dia, void *closure) { (void) dia; (void) closure; if (theCancelContinueButton != 0) { thePauseForm_clicked = theCancelContinueButton; } else { thePauseForm_clicked = -1; // STOP button } } void UiPause_begin (GuiObject topShell, const wchar *title, Interpreter interpreter) { if (theEventLoopDepth > 0) Melder_throw ("Praat cannot have more than one pause form at a time."); forget (thePauseForm); // in case an earlier build-up of another pause window was interrupted thePauseForm = UiForm_create (topShell, Melder_wcscat (L"Pause: ", title), thePauseFormOkCallback, interpreter, // pass interpreter as closure! NULL, NULL); } void UiPause_real (const wchar *label, const wchar *defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"real\" has to be between a \"beginPause\" and an \"endPause\"."); UiForm_addReal (thePauseForm, label, defaultValue); } void UiPause_positive (const wchar *label, const wchar *defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"positive\" has to be between a \"beginPause\" and an \"endPause\"."); UiForm_addPositive (thePauseForm, label, defaultValue); } void UiPause_integer (const wchar *label, const wchar *defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"integer\" has to be between a \"beginPause\" and an \"endPause\"."); UiForm_addInteger (thePauseForm, label, defaultValue); } void UiPause_natural (const wchar *label, const wchar *defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"natural\" has to be between a \"beginPause\" and an \"endPause\"."); UiForm_addNatural (thePauseForm, label, defaultValue); } void UiPause_word (const wchar *label, const wchar *defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"word\" has to be between a \"beginPause\" and an \"endPause\"."); UiForm_addWord (thePauseForm, label, defaultValue); } void UiPause_sentence (const wchar *label, const wchar *defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"sentence\" has to be between a \"beginPause\" and an \"endPause\"."); UiForm_addSentence (thePauseForm, label, defaultValue); } void UiPause_text (const wchar *label, const wchar *defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"text\" has to be between a \"beginPause\" and an \"endPause\"."); UiForm_addText (thePauseForm, label, defaultValue); } void UiPause_boolean (const wchar *label, int defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"boolean\" has to be between a \"beginPause\" and an \"endPause\"."); UiForm_addBoolean (thePauseForm, label, defaultValue); } void UiPause_choice (const wchar *label, int defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"choice\" has to be between a \"beginPause\" and an \"endPause\"."); thePauseFormRadio = UiForm_addRadio (thePauseForm, label, defaultValue); } void UiPause_optionMenu (const wchar *label, int defaultValue) { if (thePauseForm == NULL) Melder_throw ("The function \"optionMenu\" has to be between a \"beginPause\" and an \"endPause\"."); thePauseFormRadio = UiForm_addOptionMenu (thePauseForm, label, defaultValue); } void UiPause_option (const wchar *label) { if (thePauseForm == NULL) Melder_throw ("The function \"option\" has to be between a \"beginPause\" and an \"endPause\"."); if (thePauseFormRadio == NULL) { forget (thePauseForm); Melder_throw ("Found the function \"option\" without a preceding \"choice\" or \"optionMenu\"."); } UiOptionMenu_addButton (thePauseFormRadio, label); } void UiPause_comment (const wchar *label) { if (thePauseForm == NULL) Melder_throw ("The function \"comment\" has to be between a \"beginPause\" and an \"endPause\"."); UiForm_addLabel (thePauseForm, L"", label); } int UiPause_end (int numberOfContinueButtons, int defaultContinueButton, int cancelContinueButton, const wchar *continueText1, const wchar *continueText2, const wchar *continueText3, const wchar *continueText4, const wchar *continueText5, const wchar *continueText6, const wchar *continueText7, const wchar *continueText8, const wchar *continueText9, const wchar *continueText10, Interpreter interpreter) { if (thePauseForm == NULL) Melder_throw ("Found the function \"endPause\" without a preceding \"beginPause\"."); UiForm_setPauseForm (thePauseForm, numberOfContinueButtons, defaultContinueButton, cancelContinueButton, continueText1, continueText2, continueText3, continueText4, continueText5, continueText6, continueText7, continueText8, continueText9, continueText10, thePauseFormCancelCallback); theCancelContinueButton = cancelContinueButton; UiForm_finish (thePauseForm); therror bool wasBackgrounding = Melder_backgrounding; //if (theCurrentPraatApplication -> batch) goto end; if (wasBackgrounding) praat_foreground (); /* * Put the pause form on the screen. */ UiForm_destroyWhenUnmanaged (thePauseForm); UiForm_do (thePauseForm, false); /* * Wait for the user to click Stop or Continue. */ #ifndef CONSOLE_APPLICATION { // scope autoMelderSaveDefaultDir saveDir; thePauseForm_clicked = 0; Melder_assert (theEventLoopDepth == 0); theEventLoopDepth ++; try { #if gtk do { gtk_main_iteration (); } while (! thePauseForm_clicked); #else do { XEvent event; GuiNextEvent (& event); XtDispatchEvent (& event); } while (! thePauseForm_clicked); #endif } catch (MelderError) { Melder_flushError ("An error made it to the outer level in a pause window; should not occur! Please write to paul.boersma@uva.nl"); } theEventLoopDepth --; } if (wasBackgrounding) praat_background (); /* BUG: should also restore praatP. editor. */ thePauseForm = NULL; // undangle thePauseFormRadio = NULL; // undangle if (thePauseForm_clicked == -1) { Interpreter_stop (interpreter); Melder_throw ("You interrupted the script."); //Melder_flushError (NULL); //Melder_clearError (); } else { //Melder_casual ("Clicked %d", thePauseForm_clicked); } #endif return thePauseForm_clicked; } /* End of file UiPause.cpp */ sources_5316/sys/oo_CAN_WRITE_AS_ENCODING.h0000644000176700017670000001024711724670170016624 0ustar paulpaul/* oo_CAN_WRITE_AS_ENCODING.h * * Copyright (C) 2007-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "oo_undef.h" #define oo_SIMPLE(type,storage,x) #define oo_ARRAY(type,storage,x,cap,n) #define oo_SET(type,storage,x,setType) #define oo_VECTOR(type,storage,x,min,max) #define oo_MATRIX(type,storage,x,row1,row2,col1,col2) #define oo_ENUMx(type,storage,Type,x) #define oo_ENUMx_ARRAY(type,storage,Type,x,cap,n) #define oo_ENUMx_SET(type,storage,Type,x,setType) #define oo_ENUMx_VECTOR(type,storage,Type,x,min,max) #define oo_STRINGx(storage,x) \ if (x && ! Melder_isEncodable (x, encoding)) return false; #define oo_STRINGx_ARRAY(storage,x,cap,n) \ for (int i = 0; i < n; i ++) \ if (x [i] && ! Melder_isEncodable (x [i], encoding)) return false; #define oo_STRINGx_SET(storage,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ if (x [i] && ! Melder_isEncodable (x [i], encoding)) return false; #define oo_STRINGx_VECTOR(storage,x,min,max) \ if (x) { \ for (long i = min; i <= max; i ++) \ if (x [i] && ! Melder_isEncodable (x [i], encoding)) return false; \ } #define oo_STRUCT(Type,x) \ if (! x. canWriteAsEncoding (encoding)) return false; #define oo_STRUCT_ARRAY(Type,x,cap,n) \ for (int i = 0; i < n; i ++) \ if (! x [i]. canWriteAsEncoding (encoding)) return false; #define oo_STRUCT_SET(Type,x,setType) \ for (int i = 0; i <= setType##_MAX; i ++) \ if (! x [i]. canWriteAsEncoding (encoding)) return false; #define oo_STRUCT_VECTOR_FROM(Type,x,min,max) \ if (x) { \ for (long i = min; i <= max; i ++) \ if (! x [i]. canWriteAsEncoding (encoding)) return false; \ } #define oo_STRUCT_MATRIX_FROM(Type,x,row1,row2,col1,col2) \ if (x) { \ for (long i = row1; i <= row2; i ++) \ for (long j = col1; j <= col2; j ++) \ if (! x [i] [j]. canWriteAsEncoding (encoding)) return false; \ } #define oo_WIDGET(x) \ !!!! Can never write Widgets... !!!! #define oo_WIDGET_ARRAY(x,cap,n) \ !!!! Can never write Widgets... !!!! #define oo_WIDGET_SET(x,setType) \ !!!! Can never write Widgets... !!!! #define oo_WIDGET_VECTOR_FROM(x,cap,min,max) \ !!!! Can never write Widgets... !!!! #define oo_OBJECT(Class,version,x) \ if (x && ! Data_canWriteAsEncoding (x, encoding)) return false; #define oo_COLLECTION(Class,x,ItemClass,version) \ if (x && ! Data_canWriteAsEncoding (x, encoding)) return false; #define oo_FILE(x) \ if (! Melder_isEncodable (x. path, encoding)) return false; #define oo_DIR(x) \ if (! Melder_isEncodable (x. path, encoding)) return false; #define oo_DEFINE_STRUCT(Type) \ bool struct##Type :: canWriteAsEncoding (int encoding) { \ (void) encoding; #define oo_END_STRUCT(Type) \ return true; \ } #define oo_DEFINE_CLASS(Class,Parent) \ bool struct##Class :: v_canWriteAsEncoding (int encoding) { \ if (! Class##_Parent :: v_canWriteAsEncoding (encoding)) return false; #define oo_END_CLASS(Class) \ return true; \ } #define oo_IF(condition) \ if (condition) { #define oo_ENDIF \ } #define oo_FROM(from) #define oo_ENDFROM #define oo_VERSION(version) #define oo_DECLARING 0 #define oo_DESTROYING 0 #define oo_COPYING 0 #define oo_EQUALLING 0 #define oo_COMPARING 0 #define oo_VALIDATING_ENCODING 1 #define oo_READING 0 #define oo_READING_TEXT 0 #define oo_READING_BINARY 0 #define oo_READING_CACHE 0 #define oo_READING_LISP 0 #define oo_WRITING 0 #define oo_WRITING_TEXT 0 #define oo_WRITING_BINARY 0 #define oo_WRITING_CACHE 0 #define oo_WRITING_LISP 0 #define oo_DESCRIBING 0 /* End of file oo_CAN_WRITE_AS_ENCODING.h */ sources_5316/sys/HyperPage.h0000644000176700017670000001065411632117410014600 0ustar paulpaul#ifndef _HyperPage_h_ #define _HyperPage_h_ /* HyperPage.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Editor.h" #include "Collection.h" #include "Graphics.h" Thing_define (HyperLink, Data) { // new data: public: double x1DC, x2DC, y1DC, y2DC; }; HyperLink HyperLink_create (const wchar *name, double x1, double x2, double y1, double y2); Thing_define (HyperPage, Editor) { // data: public: GuiObject drawingArea, verticalScrollBar; Graphics g, ps; double d_x, d_y, rightMargin, previousBottomSpacing; long d_printingPageNumber; Collection links; int printing, top, mirror; wchar *insideHeader, *middleHeader, *outsideHeader; wchar *insideFooter, *middleFooter, *outsideFooter; enum kGraphics_font font; int fontSize; wchar *entryHint; double entryPosition; struct { wchar *page; int top; } history [20]; int historyPointer; wchar *currentPageTitle; GuiObject fontSizeButton_10, fontSizeButton_12, fontSizeButton_14, fontSizeButton_18, fontSizeButton_24; GuiObject holder; void *praatApplication, *praatObjects, *praatPicture; bool scriptErrorHasBeenNotified; structMelderDir rootDirectory; // overridden methods: protected: virtual void v_destroy (); virtual bool v_editable () { return false; } virtual void v_createMenus (); virtual void v_createChildren (); virtual void v_dataChanged (); // new methods: public: virtual void v_draw () { } virtual long v_getNumberOfPages () { return 0; } virtual long v_getCurrentPageNumber () { return 0; } virtual int v_goToPage (const wchar *title) { (void) title; return 0; } virtual void v_goToPage_i (long pageNumber) { (void) pageNumber; } virtual void v_defaultHeaders (EditorCommand cmd) { (void) cmd; } virtual bool v_hasHistory () { return false; } virtual bool v_isOrdered () { return false; } }; void HyperPage_clear (HyperPage me); /* "Methods" */ #define HyperPage_ADD_BORDER 1 #define HyperPage_USE_ENTRY_HINT 2 int HyperPage_any (I, const wchar *text, enum kGraphics_font font, int size, int style, double minFooterDistance, double x, double secondIndent, double topSpacing, double bottomSpacing, unsigned long method); int HyperPage_pageTitle (I, const wchar *title); int HyperPage_intro (I, const wchar *text); int HyperPage_entry (I, const wchar *title); int HyperPage_paragraph (I, const wchar *text); int HyperPage_listItem (I, const wchar *text); int HyperPage_listItem1 (I, const wchar *text); int HyperPage_listItem2 (I, const wchar *text); int HyperPage_listItem3 (I, const wchar *text); int HyperPage_listTag (I, const wchar *text); int HyperPage_listTag1 (I, const wchar *text); int HyperPage_listTag2 (I, const wchar *text); int HyperPage_listTag3 (I, const wchar *text); int HyperPage_definition (I, const wchar *text); int HyperPage_definition1 (I, const wchar *text); int HyperPage_definition2 (I, const wchar *text); int HyperPage_definition3 (I, const wchar *text); int HyperPage_code (I, const wchar *text); int HyperPage_code1 (I, const wchar *text); int HyperPage_code2 (I, const wchar *text); int HyperPage_code3 (I, const wchar *text); int HyperPage_code4 (I, const wchar *text); int HyperPage_code5 (I, const wchar *text); int HyperPage_prototype (I, const wchar *text); int HyperPage_formula (I, const wchar *formula); int HyperPage_picture (I, double width_inches, double height_inches, void (*draw) (Graphics g)); int HyperPage_script (I, double width_inches, double height_inches, const wchar *script); int HyperPage_goToPage (I, const wchar *title); void HyperPage_goToPage_i (I, long i); void HyperPage_init (HyperPage me, GuiObject parent, const wchar *title, Data data); void HyperPage_prefs (void); void HyperPage_setEntryHint (I, const wchar *entry); void HyperPage_initSheetOfPaper (HyperPage me); /* End of file HyperPage.h */ #endif sources_5316/sys/Thing.cpp0000644000176700017670000001733511655767546014355 0ustar paulpaul/* Thing.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include #include "Thing.h" static long theTotalNumberOfThings; void structThing :: v_info () { MelderInfo_writeLine2 (L"Object type: ", Thing_className (this)); MelderInfo_writeLine2 (L"Object name: ", this -> name ? this -> name : L""); time_t today = time (NULL); MelderInfo_writeLine2 (L"Date: ", Melder_peekUtf8ToWcs (ctime (& today))); /* Includes a newline. */ } /* * Instead of the Thing_implement macro. */ struct structClassInfo theClassInfo_Thing = { L"Thing", NULL, // no parent class sizeof (class structThing), NULL, // no _new function (not needed; plus, it would have to be called "_Thing_new", but that name has been given to something else) 0, // version 0, // sequentialUniqueIdOfReadableClass NULL // dummyObject }; ClassInfo classThing = & theClassInfo_Thing; const wchar * Thing_className (Thing me) { return my classInfo -> className; } Any _Thing_new (ClassInfo classInfo_) { Thing me = (Thing) classInfo_ -> _new (); theTotalNumberOfThings += 1; my classInfo = classInfo_; Melder_assert (my name == NULL); // check that _new called calloc if (Melder_debug == 40) Melder_casual ("created %ls (%p, %p)", classInfo_ -> className, classInfo_, me); return me; } static int theNumberOfReadableClasses = 0; static ClassInfo theReadableClasses [1 + 1000]; static void _Thing_addOneReadableClass (ClassInfo readableClass) { if (++ theNumberOfReadableClasses > 1000) Melder_fatal ("(Thing_recognizeClassesByName:) Too many (1001) readable classes."); theReadableClasses [theNumberOfReadableClasses] = readableClass; readableClass -> sequentialUniqueIdOfReadableClass = theNumberOfReadableClasses; } void Thing_recognizeClassesByName (ClassInfo readableClass, ...) { va_list arg; if (readableClass == NULL) return; va_start (arg, readableClass); _Thing_addOneReadableClass (readableClass); ClassInfo klas; while ((klas = va_arg (arg, ClassInfo)) != NULL) { _Thing_addOneReadableClass (klas); } va_end (arg); } long Thing_listReadableClasses (void) { Melder_clearInfo (); MelderInfo_open (); for (long iclass = 1; iclass <= theNumberOfReadableClasses; iclass ++) { ClassInfo klas = theReadableClasses [iclass]; MelderInfo_writeLine3 (Melder_integer (klas -> sequentialUniqueIdOfReadableClass), L"\t", klas -> className); } MelderInfo_close (); return theNumberOfReadableClasses; } static int theNumberOfAliases = 0; static struct { ClassInfo readableClass; const wchar_t *otherName; } theAliases [1 + 100]; void Thing_recognizeClassByOtherName (ClassInfo readableClass, const wchar *otherName) { theAliases [++ theNumberOfAliases]. readableClass = readableClass; theAliases [theNumberOfAliases]. otherName = otherName; } long Thing_version; // global variable! ClassInfo Thing_classFromClassName (const wchar_t *klas) { static wchar buffer [1+100]; wcsncpy (buffer, klas ? klas : L"", 100); wchar *space = wcschr (buffer, ' '); if (space) { *space = '\0'; // strip version number Thing_version = wcstol (space + 1, NULL, 10); } else { Thing_version = 0; } /* * First try the class names that were registered with Thing_recognizeClassesByName. */ for (int i = 1; i <= theNumberOfReadableClasses; i ++) { ClassInfo classInfo = theReadableClasses [i]; if (wcsequ (buffer, classInfo -> className)) { return classInfo; } } /* * Then try the aliases that were registered with Thing_recognizeClassByOtherName. */ for (int i = 1; i <= theNumberOfAliases; i ++) { if (wcsequ (buffer, theAliases [i]. otherName)) { ClassInfo classInfo = theAliases [i]. readableClass; return classInfo; } } Melder_throw ("Class \"", buffer, "\" not recognized."); } Any Thing_newFromClassNameA (const char *className) { try { ClassInfo classInfo = Thing_classFromClassName (Melder_peekUtf8ToWcs (className)); return _Thing_new (classInfo); } catch (MelderError) { Melder_throw (className, " not created."); } } Any Thing_newFromClassName (const wchar *className) { try { ClassInfo classInfo = Thing_classFromClassName (className); return _Thing_new (classInfo); } catch (MelderError) { Melder_throw (className, " not created."); } } Thing _Thing_dummyObject (ClassInfo classInfo) { if (classInfo -> dummyObject == NULL) { classInfo -> dummyObject = (Thing) classInfo -> _new (); } Melder_assert (classInfo -> dummyObject != NULL); return classInfo -> dummyObject; } void _Thing_forget_nozero (Thing me) { if (! me) return; if (Melder_debug == 40) Melder_casual ("destroying %ls", my classInfo -> className); my v_destroy (); theTotalNumberOfThings -= 1; } void _Thing_forget (Thing me) { if (! me) return; if (Melder_debug == 40) Melder_casual ("destroying %ls", my classInfo -> className); my v_destroy (); //Melder_free (me); delete me; theTotalNumberOfThings -= 1; } bool Thing_subclass (ClassInfo klas, ClassInfo ancestor) { while (klas != ancestor && klas != NULL) klas = klas -> parent; return klas != NULL; } bool Thing_member (Thing me, ClassInfo klas) { if (! me) Melder_fatal ("(Thing_member:) Found NULL object."); return Thing_subclass (my classInfo, klas); } void * _Thing_check (Thing me, ClassInfo klas, const char *fileName, int line) { if (! me) Melder_fatal ("(_Thing_check:) NULL object passed to a function\n" "in file %.100s at line %d.", fileName, line); ClassInfo l_classInfo = my classInfo; while (l_classInfo != klas && l_classInfo != NULL) l_classInfo = l_classInfo -> parent; if (! l_classInfo) Melder_fatal ("(_Thing_check:) Object of wrong class (%.50s) passed to a function\n" "in file %.100s at line %d.", Melder_peekWcsToUtf8 (my classInfo -> className), fileName, line); return me; } void Thing_infoWithId (Thing me, unsigned long id) { Melder_clearInfo (); MelderInfo_open (); if (id != 0) MelderInfo_writeLine2 (L"Object id: ", Melder_integer (id)); my v_info (); MelderInfo_close (); } void Thing_info (Thing me) { Thing_infoWithId (me, 0); } wchar * Thing_getName (Thing me) { return my name; } wchar * Thing_messageName (Thing me) { static MelderString buffers [11]; static int ibuffer = 0; if (++ ibuffer == 11) ibuffer = 0; MelderString_empty (& buffers [ibuffer]); if (my name) { MelderString_append (& buffers [ibuffer], my classInfo -> className, L" \"", my name, L"\""); } else { MelderString_append (& buffers [ibuffer], my classInfo -> className); } return buffers [ibuffer]. string; } void Thing_setName (Thing me, const wchar *name) { /* * First check without change. */ autostring newName = Melder_wcsdup_f (name); // BUG: that's no checking /* * Then change without error. */ Melder_free (my name); my name = newName.transfer(); my v_nameChanged (); } long Thing_getTotalNumberOfThings (void) { return theTotalNumberOfThings; } void Thing_swap (Thing me, Thing thee) { Melder_assert (my classInfo == thy classInfo); int n = my classInfo -> size; char *p, *q; int i; for (p = (char *) me, q = (char *) thee, i = n; i > 0; i --, p ++, q ++) { char tmp = *p; *p = *q; *q = tmp; } } /* End of file Thing.cpp */ sources_5316/sys/praat_statistics.cpp0000644000176700017670000001467611735021604016643 0ustar paulpaul/* praat_statistics.c * * Copyright (C) 1992-2008 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2002/03/09 OSX no mention of free memory * pb 2004/10/18 more big integers * pb 2005/03/02 pref string 260 bytes long * pb 2006/10/28 erased MacOS 9 stuff * pb 2006/12/06 MelderString * pb 2006/12/26 theCurrentPraat * pb 2007/07/27 string deallocation size * pb 2007/08/12 wchar * pb 2007/12/09 preferences * pb 2008/11/26 numberOfMotifWidgets */ #include #include "praatP.h" static struct { long batchSessions, interactiveSessions; double memory; wchar dateOfFirstSession [Preferences_STRING_BUFFER_SIZE]; } statistics; void praat_statistics_prefs (void) { Preferences_addLong (L"PraatShell.batchSessions", & statistics.batchSessions, 0); Preferences_addLong (L"PraatShell.interactiveSessions", & statistics.interactiveSessions, 0); Preferences_addDouble (L"PraatShell.memory", & statistics.memory, 0.0); Preferences_addString (L"PraatShell.dateOfFirstSession", & statistics.dateOfFirstSession [0], L""); } void praat_statistics_prefsChanged (void) { if (! statistics.dateOfFirstSession [0]) { time_t today = time (NULL); wchar *newLine; wcscpy (statistics.dateOfFirstSession, Melder_peekUtf8ToWcs (ctime (& today))); newLine = wcschr (statistics.dateOfFirstSession, '\n'); if (newLine) *newLine = '\0'; } if (theCurrentPraatApplication -> batch) statistics.batchSessions += 1; else statistics.interactiveSessions += 1; } void praat_statistics_exit (void) { statistics.memory += Melder_allocationSize (); } void praat_memoryInfo (void) { MelderInfo_open (); MelderInfo_writeLine2 (L"Currently in use:\n" L" Strings: ", Melder_integer (MelderString_allocationCount () - MelderString_deallocationCount ())); MelderInfo_writeLine2 (L" Arrays: ", Melder_integer (NUM_getTotalNumberOfArrays ())); MelderInfo_writeLine5 (L" Things: ", Melder_integer (Thing_getTotalNumberOfThings ()), L" (objects in list: ", Melder_integer (theCurrentPraatObjects -> n), L")"); long numberOfMotifWidgets = #if motif && (defined (_WIN32) || defined (macintosh)) Gui_getNumberOfMotifWidgets (); #else 0; #endif if (numberOfMotifWidgets > 0) { MelderInfo_writeLine2 (L" Motif widgets: ", Melder_integer (numberOfMotifWidgets)); } MelderInfo_writeLine2 (L" Other: ", Melder_bigInteger (Melder_allocationCount () - Melder_deallocationCount () - Thing_getTotalNumberOfThings () - NUM_getTotalNumberOfArrays () - (MelderString_allocationCount () - MelderString_deallocationCount ()) - numberOfMotifWidgets)); MelderInfo_writeLine5 ( L"\nMemory history of this session:\n" L" Total created: ", Melder_bigInteger (Melder_allocationCount ()), L" (", Melder_bigInteger (Melder_allocationSize ()), L" bytes)"); MelderInfo_writeLine2 (L" Total deleted: ", Melder_bigInteger (Melder_deallocationCount ())); MelderInfo_writeLine5 (L" Reallocations: ", Melder_bigInteger (Melder_movingReallocationsCount ()), L" moving, ", Melder_bigInteger (Melder_reallocationsInSituCount ()), L" in situ"); MelderInfo_writeLine5 ( L" Strings created: ", Melder_bigInteger (MelderString_allocationCount ()), L" (", Melder_bigInteger (MelderString_allocationSize ()), L" bytes)"); MelderInfo_writeLine5 ( L" Strings deleted: ", Melder_bigInteger (MelderString_deallocationCount ()), L" (", Melder_bigInteger (MelderString_deallocationSize ()), L" bytes)"); MelderInfo_writeLine3 (L"\nHistory of all sessions from ", statistics.dateOfFirstSession, L" until today:"); MelderInfo_writeLine5 (L" Sessions: ", Melder_integer (statistics.interactiveSessions), L" interactive, ", Melder_integer (statistics.batchSessions), L" batch"); MelderInfo_writeLine3 (L" Total memory use: ", Melder_bigInteger (statistics.memory + Melder_allocationSize ()), L" bytes"); MelderInfo_writeLine9 (L"\nMemory addressing: short ", Melder_integer (sizeof (short) * 8), L" bits, int ", Melder_integer (sizeof (int) * 8), L" bits, long ", Melder_integer (sizeof (long) * 8), L" bits, pointer ", Melder_integer (sizeof (void *) * 8), L" bits"); MelderInfo_writeLine2 (L"\nNumber of actions: ", Melder_integer (praat_getNumberOfActions ())); double x, y, width, height; Gui_getWindowPositioningBounds (& x, & y, & width, & height); MelderInfo_writeLine8 (L"\nWindow positioning area: x = ", Melder_double (x), L", y = ", Melder_double (y), L", width = ", Melder_double (width), L", height = ", Melder_double (height)); #if defined (macintosh) CGDirectDisplayID screen = CGMainDisplayID (); CGSize screenSize_mm = CGDisplayScreenSize (screen); double diagonal_mm = sqrt (screenSize_mm. width * screenSize_mm. width + screenSize_mm. height * screenSize_mm. height); double diagonal_inch = diagonal_mm / 25.4; MelderInfo_writeLine9 (L"\nScreen size: ", Melder_double (screenSize_mm. width), L" x ", Melder_double (screenSize_mm. height), L" mm (diagonal ", Melder_fixed (diagonal_mm, 1), L" mm = ", Melder_fixed (diagonal_inch, 1), L" inch)"); size_t screenWidth_pixels = CGDisplayPixelsWide (screen); size_t screenHeight_pixels = CGDisplayPixelsHigh (screen); MelderInfo_writeLine5 (L"Screen \"resolution\": ", Melder_integer (screenWidth_pixels), L" x ", Melder_integer (screenHeight_pixels), L" pixels"); double resolution = 25.4 * screenWidth_pixels / screenSize_mm. width; MelderInfo_writeLine3 (L"Screen resolution: ", Melder_fixed (resolution, 1), L" pixels/inch"); #elif defined (_WIN32) /*for (int i = 0; i <= 88; i ++) MelderInfo_writeLine4 (L"System metric ", Melder_integer (i), L": ", Melder_integer (GetSystemMetrics (i)));*/ #endif //volatile long i = 0, i2; //do { volatile float r = ++ i; i2 = r; } while (i == i2); //MelderInfo_writeLine2 (L"Highest integer representable in a 32-bit float: ", Melder_integer (i2 - 1)); MelderInfo_close (); } /* End of file praat_statistics.c */ sources_5316/sys/motifEmulator_resources.h0000644000176700017670000001016311522300674017634 0ustar paulpaul/* motifEmulator_resources.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2011/02/02 */ motif_RESOURCE (XmNactivateCallback) /* XmPushButton, XmDrawnButton, XmCascadeButton */ motif_RESOURCE (XmNautoUnmanage) /* XmBulletinBoard */ motif_RESOURCE (XmNbottomAttachment) /* XmForm Constraint */ motif_RESOURCE (XmNbottomOffset) /* XmForm Constraint */ motif_RESOURCE (XmNbottomPosition) /* XmForm Constraint */ motif_RESOURCE (XmNclipWindow) /* XmScrolledWindow */ motif_RESOURCE (XmNcolumns) /* XmText Output */ motif_RESOURCE (XmNdecrementCallback) /* XmScrollBar */ motif_RESOURCE (XmNdeleteResponse) /* VendorShell */ motif_RESOURCE (XmNdestroyCallback) /* Core */ motif_RESOURCE (XmNdialogStyle) /* XmBulletinBoard */ motif_RESOURCE (XmNdialogTitle) /* XmBulletinBoard */ motif_RESOURCE (XmNdragCallback) /* XmScrollBar, XmScale */ motif_RESOURCE (XmNheight) /* Core */ motif_RESOURCE (XmNhelpCallback) /* XmPrimitive, XmManager */ motif_RESOURCE (XmNhorizontalScrollBar) /* XmScrolledWindow */ motif_RESOURCE (XmNiconName) /* TopLevelShell */ motif_RESOURCE (XmNincrement) /* XmScrollBar */ motif_RESOURCE (XmNincrementCallback) /* XmScrollBar */ motif_RESOURCE (XmNlabelString) /* XmLabel, XmRowColumn */ motif_RESOURCE (XmNleftAttachment) /* XmForm Constraint */ motif_RESOURCE (XmNleftOffset) /* XmForm Constraint */ motif_RESOURCE (XmNleftPosition) /* XmForm Constraint */ motif_RESOURCE (XmNmaximum) /* XmScrollBar, XmScale */ motif_RESOURCE (XmNmenuHelpWidget) /* XmRowColumn */ motif_RESOURCE (XmNminimum) /* XmScrollBar, XmScale */ motif_RESOURCE (XmNmoveCallback) /* XmDrawingArea */ /* MACINTOSH ONLY */ motif_RESOURCE (XmNorientation) /* XmRowColumn, XmScale, XmScrollBar */ motif_RESOURCE (XmNpageDecrementCallback) /* XmScrollBar */ motif_RESOURCE (XmNpageIncrement) /* XmScrollBar */ motif_RESOURCE (XmNpageIncrementCallback) /* XmScrollBar */ motif_RESOURCE (XmNradioBehavior) /* XmRowColumn */ motif_RESOURCE (XmNrightAttachment) /* XmForm Constraint */ motif_RESOURCE (XmNrightOffset) /* XmForm Constraint */ motif_RESOURCE (XmNrightPosition) /* XmForm Constraint */ motif_RESOURCE (XmNrowColumnType) /* XmRowColumn */ motif_RESOURCE (XmNrows) /* XmText Output */ motif_RESOURCE (XmNscaleHeight) /* XmScale */ motif_RESOURCE (XmNscaleWidth) /* XmScale */ motif_RESOURCE (XmNscrollingPolicy) /* XmScrolledWindow */ motif_RESOURCE (XmNsensitive) /* Core */ motif_RESOURCE (XmNsliderSize) /* XmScrollBar */ motif_RESOURCE (XmNspacing) /* XmToggleButton, XmRowColumn, XmScrolledWindow */ motif_RESOURCE (XmNsubMenuId) /* XmCascadeButton */ motif_RESOURCE (XmNtitle) /* WMShell */ motif_RESOURCE (XmNtitleString) /* XmScale */ motif_RESOURCE (XmNtopAttachment) /* XmForm Constraint */ motif_RESOURCE (XmNtopItemPosition) /* XmList */ motif_RESOURCE (XmNtopOffset) /* XmForm Constraint */ motif_RESOURCE (XmNtopPosition) /* XmForm Constraint */ motif_RESOURCE (XmNtraversalOn) /* XmPrimitive, XmManager */ motif_RESOURCE (XmNuserData) /* XmPrimitive, XmManager */ motif_RESOURCE (XmNvalue) /* XmScrollBar, XmScale */ motif_RESOURCE (XmNvalueChangedCallback) /* XmToggleButton, XmScrollBar, XmScale */ motif_RESOURCE (XmNverticalScrollBar) /* XmScrolledWindow */ motif_RESOURCE (XmNwidth) /* Core */ motif_RESOURCE (XmNworkWindow) /* XmScrolledWindow */ motif_RESOURCE (XmNx) /* Core */ motif_RESOURCE (XmNy) /* Core */ /* End of file motifEmulator_resources.h */ sources_5316/sys/ScriptEditor.h0000644000176700017670000000352011623752044015331 0ustar paulpaul#ifndef _ScriptEditor_h_ #define _ScriptEditor_h_ /* ScriptEditor.h * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Script.h" #include "TextEditor.h" #include "Interpreter.h" Thing_define (ScriptEditor, TextEditor) { // new data: public: wchar *environmentName; ClassInfo editorClass; Interpreter interpreter; UiForm argsDialog; // functions: void init (GuiObject parent, Editor editor, const wchar_t *initialText); // overridden methods: virtual void v_destroy (); virtual void v_nameChanged (); virtual void v_goAway (); virtual bool v_scriptable () { return false; } virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu); }; ScriptEditor ScriptEditor_createFromText ( GuiObject parent, Editor editor, // the scripting environment; if NULL, the scripting environment consists of the global windows const wchar *initialText // may be NULL ); ScriptEditor ScriptEditor_createFromScript ( GuiObject parent, Editor editor, Script script ); int ScriptEditors_dirty (void); // are there any modified and unsaved scripts? Ask before quitting the program. /* End of file ScriptEditor.h */ #endif sources_5316/sys/Manual.cpp0000644000176700017670000005175711724373301014502 0ustar paulpaul/* Manual.cpp * * Copyright (C) 1996-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2003/03/09 searching: more points for multiple occurrences within a paragraph * pb 2003/10/03 praat_executeFromFile without arguments * pb 2003/11/26 use recording time from file * pb 2003/11/30 removed newline from date * pb 2004/02/08 allow arguments in scripts * pb 2005/05/08 embedded scripts (for pictures) * pb 2005/07/19 moved navigation buttons to the top, removed page label and horizontal scroll bar * pb 2006/10/20 embedded scripts: not on opening page * pb 2007/06/10 wchar_t * pb 2007/08/12 wchar_t * pb 2008/01/19 double * pb 2008/03/20 split off Help menu * pb 2008/03/21 new Editor API * pb 2011/04/06 C++ * pb 2011/07/05 C++ */ #include #include "Manual.h" #include "Printer.h" #include "machine.h" #include "site.h" #include #include "EditorM.h" #include "praat_script.h" #include "praatP.h" Thing_implement (Manual, HyperPage, 0); /* Remaining BUGS: HTML writer does not recognize "\s{". */ #define SEARCH_PAGE 0 static const wchar_t *month [] = { L"", L"January", L"February", L"March", L"April", L"May", L"June", L"July", L"August", L"September", L"October", L"November", L"December" }; static void menu_cb_writeOneToHtmlFile (EDITOR_ARGS) { EDITOR_IAM (Manual); EDITOR_FORM_WRITE (L"Save as HTML file", 0) ManPages manPages = (ManPages) my data; wchar_t *p = defaultName; wcscpy (p, ((ManPage) manPages -> pages -> item [my path]) -> title); while (*p) { if (! isalnum (*p) && *p != '_') *p = '_'; p ++; } wcscat (defaultName, L".html"); EDITOR_DO_WRITE ManPages_writeOneToHtmlFile ((ManPages) my data, my path, file); EDITOR_END } static void menu_cb_writeAllToHtmlDir (EDITOR_ARGS) { EDITOR_IAM (Manual); EDITOR_FORM (L"Save all pages as HTML files", 0) LABEL (L"", L"Type a directory name:") TEXTFIELD (L"directory", L"") EDITOR_OK structMelderDir currentDirectory = { { 0 } }; Melder_getDefaultDir (& currentDirectory); SET_STRING (L"directory", Melder_dirToPath (& currentDirectory)) EDITOR_DO wchar *directory = GET_STRING (L"directory"); ManPages_writeAllToHtmlDir ((ManPages) my data, directory); EDITOR_END } static void menu_cb_searchForPageList (EDITOR_ARGS) { EDITOR_IAM (Manual); EDITOR_FORM (L"Search for page", 0) ManPages manPages = (ManPages) my data; long numberOfPages; const wchar_t **pages = ManPages_getTitles (manPages, & numberOfPages); LIST (L"Page", manPages -> pages -> size, pages, 1) EDITOR_OK EDITOR_DO HyperPage_goToPage_i (me, GET_INTEGER (L"Page")); therror EDITOR_END } void structManual :: v_draw () { ManPages manPages = (ManPages) data; ManPage page; ManPage_Paragraph paragraph; #if motif Graphics_clearWs (g); #endif if (path == SEARCH_PAGE) { HyperPage_pageTitle (this, L"Best matches"); HyperPage_intro (this, L"The best matches to your query seem to be:"); for (int i = 1; i <= numberOfMatches; i ++) { wchar link [300]; page = (ManPage) manPages -> pages -> item [matches [i]]; swprintf (link, 300, L"\\bu @@%ls", page -> title); HyperPage_listItem (this, link); } return; } page = (ManPage) manPages -> pages -> item [path]; if (! paragraphs) return; HyperPage_pageTitle (this, page -> title); for (paragraph = & page -> paragraphs [0]; paragraph -> type != 0; paragraph ++) { switch (paragraph -> type) { case kManPage_type_INTRO: HyperPage_intro (this, paragraph -> text); break; case kManPage_type_ENTRY: HyperPage_entry (this, paragraph -> text); break; case kManPage_type_NORMAL: HyperPage_paragraph (this, paragraph -> text); break; case kManPage_type_LIST_ITEM: HyperPage_listItem (this, paragraph -> text); break; case kManPage_type_TAG: HyperPage_listTag (this, paragraph -> text); break; case kManPage_type_DEFINITION: HyperPage_definition (this, paragraph -> text); break; case kManPage_type_CODE: HyperPage_code (this, paragraph -> text); break; case kManPage_type_PROTOTYPE: HyperPage_prototype (this, paragraph -> text); break; case kManPage_type_FORMULA: HyperPage_formula (this, paragraph -> text); break; case kManPage_type_PICTURE: HyperPage_picture (this, paragraph -> width, paragraph -> height, paragraph -> draw); break; case kManPage_type_SCRIPT: HyperPage_script (this, paragraph -> width, paragraph -> height, paragraph -> text); break; case kManPage_type_LIST_ITEM1: HyperPage_listItem1 (this, paragraph -> text); break; case kManPage_type_LIST_ITEM2: HyperPage_listItem2 (this, paragraph -> text); break; case kManPage_type_LIST_ITEM3: HyperPage_listItem3 (this, paragraph -> text); break; case kManPage_type_TAG1: HyperPage_listTag1 (this, paragraph -> text); break; case kManPage_type_TAG2: HyperPage_listTag2 (this, paragraph -> text); break; case kManPage_type_TAG3: HyperPage_listTag3 (this, paragraph -> text); break; case kManPage_type_DEFINITION1: HyperPage_definition1 (this, paragraph -> text); break; case kManPage_type_DEFINITION2: HyperPage_definition2 (this, paragraph -> text); break; case kManPage_type_DEFINITION3: HyperPage_definition3 (this, paragraph -> text); break; case kManPage_type_CODE1: HyperPage_code1 (this, paragraph -> text); break; case kManPage_type_CODE2: HyperPage_code2 (this, paragraph -> text); break; case kManPage_type_CODE3: HyperPage_code3 (this, paragraph -> text); break; case kManPage_type_CODE4: HyperPage_code4 (this, paragraph -> text); break; case kManPage_type_CODE5: HyperPage_code5 (this, paragraph -> text); break; default: break; } } if (ManPages_uniqueLinksHither (manPages, path)) { long ilink, jlink, lastParagraph = 0; int goAhead = TRUE; while (page -> paragraphs [lastParagraph]. type != 0) lastParagraph ++; if (lastParagraph > 0) { const wchar *text = page -> paragraphs [lastParagraph - 1]. text; if (text == NULL || text [0] == '\0' || text [wcslen (text) - 1] != ':') { if (printing && suppressLinksHither) goAhead = FALSE; else HyperPage_entry (this, L"Links to this page"); } } if (goAhead) for (ilink = 1; ilink <= page -> nlinksHither; ilink ++) { long link = page -> linksHither [ilink]; int alreadyShown = FALSE; for (jlink = 1; jlink <= page -> nlinksThither; jlink ++) if (page -> linksThither [jlink] == link) alreadyShown = TRUE; if (! alreadyShown) { const wchar *title = ((ManPage) manPages -> pages -> item [page -> linksHither [ilink]]) -> title; wchar linkText [304]; swprintf (linkText, 304, L"@@%ls@", title); HyperPage_listItem (this, linkText); } } } if (! printing && page -> date) { wchar signature [100]; long date = page -> date; int imonth = date % 10000 / 100; if (imonth < 0 || imonth > 12) imonth = 0; swprintf (signature, 100, L"\\co %ls, %ld %ls %ld", wcsequ (page -> author, L"ppgb") ? L"Paul Boersma" : wcsequ (page -> author, L"djmw") ? L"David Weenink" : page -> author, date % 100, month [imonth], date / 10000); HyperPage_any (this, L"", font, fontSize, 0, 0.0, 0.0, 0.0, 0.1, 0.1, HyperPage_ADD_BORDER); HyperPage_any (this, signature, font, fontSize, Graphics_ITALIC, 0.0, 0.03, 0.0, 0.1, 0.0, 0); } } /********** PRINTING **********/ static void print (I, Graphics graphics) { iam (Manual); ManPages manPages = (ManPages) my data; long numberOfPages = manPages -> pages -> size, savePage = my path; my ps = graphics; Graphics_setDollarSignIsCode (my ps, TRUE); Graphics_setAtSignIsLink (my ps, TRUE); my printing = TRUE; HyperPage_initSheetOfPaper ((HyperPage) me); for (long ipage = 1; ipage <= numberOfPages; ipage ++) { ManPage page = (ManPage) manPages -> pages -> item [ipage]; if (my printPagesStartingWith == NULL || Melder_stringMatchesCriterion (page -> title, kMelder_string_STARTS_WITH, my printPagesStartingWith)) { ManPage_Paragraph par; my path = ipage; my paragraphs = page -> paragraphs; my numberOfParagraphs = 0; par = my paragraphs; while ((par ++) -> type) my numberOfParagraphs ++; Melder_free (my currentPageTitle); my currentPageTitle = Melder_wcsdup_f (page -> title); my v_goToPage_i (ipage); my v_draw (); my v_goToPage_i (savePage); } } my printing = FALSE; my printPagesStartingWith = NULL; } static void menu_cb_printRange (EDITOR_ARGS) { EDITOR_IAM (Manual); EDITOR_FORM (L"Print range", 0) SENTENCE (L"Left or inside header", L"") SENTENCE (L"Middle header", L"") SENTENCE (L"Right or outside header", L"Manual") SENTENCE (L"Left or inside footer", L"") SENTENCE (L"Middle footer", L"") SENTENCE (L"Right or outside footer", L"") BOOLEAN (L"Mirror even/odd headers", TRUE) LABEL (L"", L"Print all pages whose title starts with:") TEXTFIELD (L"Print pages starting with", L"Intro") INTEGER (L"First page number", L"1") BOOLEAN (L"Suppress \"Links to this page\"", FALSE) EDITOR_OK ManPages manPages = (ManPages) my data; time_t today = time (NULL); char dateA [50]; #ifdef UNIX struct tm *tm = localtime (& today); strftime (dateA, 50, "%B %e, %Y", tm); #else strcpy (dateA, ctime (& today)); #endif wchar_t *date = Melder_peekUtf8ToWcs (dateA), *newline; newline = wcschr (date, '\n'); if (newline) *newline = '\0'; SET_STRING (L"Left or inside header", date) SET_STRING (L"Right or outside header", my name) if (my d_printingPageNumber) SET_INTEGER (L"First page number", my d_printingPageNumber + 1) if (my path >= 1 && my path <= manPages -> pages -> size) { ManPage page = (ManPage) manPages -> pages -> item [my path]; SET_STRING (L"Print pages starting with", page -> title); } EDITOR_DO my insideHeader = GET_STRING (L"Left or inside header"); my middleHeader = GET_STRING (L"Middle header"); my outsideHeader = GET_STRING (L"Right or outside header"); my insideFooter = GET_STRING (L"Left or inside footer"); my middleFooter = GET_STRING (L"Middle footer"); my outsideFooter = GET_STRING (L"Right or outside footer"); my mirror = GET_INTEGER (L"Mirror even/odd headers"); my printPagesStartingWith = GET_STRING (L"Print pages starting with"); my d_printingPageNumber = GET_INTEGER (L"First page number"); my suppressLinksHither = GET_INTEGER (L"Suppress \"Links to this page\""); Printer_print (print, me); EDITOR_END } /********** SEARCHING **********/ static double *goodnessOfMatch; static double searchToken (ManPages me, long ipage, wchar_t *token) { double goodness = 0.0; ManPage page = (ManPage) my pages -> item [ipage]; struct structManPage_Paragraph *par = & page -> paragraphs [0]; if (! token [0]) return 1.0; /* * Try to find a match in the title, case insensitively. */ static MelderString buffer = { 0 }; MelderString_copy (& buffer, page -> title); for (wchar_t *p = & buffer.string [0]; *p != '\0'; p ++) *p = tolower (*p); if (wcsstr (buffer.string, token)) { goodness += 300.0; /* Lots of points for a match in the title! */ if (wcsequ (buffer.string, token)) goodness += 10000.0; /* Even more points for an exact match! */ } /* * Try to find a match in the paragraphs, case-insensitively. */ while (par -> type) { if (par -> text) { wchar_t *ptoken; MelderString_copy (& buffer, par -> text); for (wchar_t *p = & buffer.string [0]; *p != '\0'; p ++) *p = tolower (*p); ptoken = wcsstr (buffer.string, token); if (ptoken) { goodness += 10.0; /* Ten points for every paragraph with a match! */ if (wcsstr (ptoken + wcslen (token), token)) { goodness += 1.0; /* One point for every second occurrence in a paragraph! */ } } } par ++; } return goodness; } static void search (Manual me, const wchar *query) { ManPages manPages = (ManPages) my data; long numberOfPages = manPages -> pages -> size; static MelderString searchText = { 0 }; MelderString_copy (& searchText, query); for (wchar *p = & searchText.string [0]; *p != '\0'; p ++) { if (*p == '\n') *p = ' '; *p = tolower (*p); } if (! goodnessOfMatch) goodnessOfMatch = NUMvector (1, numberOfPages); for (long ipage = 1; ipage <= numberOfPages; ipage ++) { wchar *token = searchText.string; goodnessOfMatch [ipage] = 1.0; for (;;) { wchar *space = wcschr (token, ' '); if (space) *space = '\0'; goodnessOfMatch [ipage] *= searchToken (manPages, ipage, token); if (! space) break; *space = ' '; // restore token = space + 1; } } /* * Find the 20 best matches. */ my numberOfMatches = 0; for (long imatch = 1; imatch <= 20; imatch ++) { long imax = 0; double max = 0.0; for (long ipage = 1; ipage <= numberOfPages; ipage ++) { if (goodnessOfMatch [ipage] > max) { max = goodnessOfMatch [ipage]; imax = ipage; } } if (! imax) break; my matches [++ my numberOfMatches] = imax; goodnessOfMatch [imax] = 0.0; // skip next time } HyperPage_goToPage_i (me, SEARCH_PAGE); } void Manual_search (Manual me, const wchar *query) { GuiText_setString (my searchText, query); search (me, query); } static void gui_button_cb_home (I, GuiButtonEvent event) { (void) event; iam (Manual); ManPages pages = (ManPages) my data; long iHome = ManPages_lookUp (pages, L"Intro"); HyperPage_goToPage_i (me, iHome ? iHome : 1); } static void gui_button_cb_record (I, GuiButtonEvent event) { (void) event; iam (Manual); ManPages manPages = (ManPages) my data; ManPage manPage = (ManPage) (my path < 1 ? NULL : manPages -> pages -> item [my path]); GuiObject_setSensitive (my recordButton, false); GuiObject_setSensitive (my playButton, false); GuiObject_setSensitive (my publishButton, false); #if motif XmUpdateDisplay (my d_windowShell); #endif if (! Melder_record (manPage == NULL ? 1.0 : manPage -> recordingTime)) Melder_flushError (NULL); GuiObject_setSensitive (my recordButton, true); GuiObject_setSensitive (my playButton, true); GuiObject_setSensitive (my publishButton, true); } static void gui_button_cb_play (I, GuiButtonEvent event) { (void) event; iam (Manual); GuiObject_setSensitive (my recordButton, false); GuiObject_setSensitive (my playButton, false); GuiObject_setSensitive (my publishButton, false); #if motif XmUpdateDisplay (my d_windowShell); #endif Melder_play (); GuiObject_setSensitive (my recordButton, true); GuiObject_setSensitive (my playButton, true); GuiObject_setSensitive (my publishButton, true); } static void gui_button_cb_publish (I, GuiButtonEvent event) { (void) event; iam (Manual); (void) me; Melder_publishPlayed (); } static void do_search (Manual me) { wchar_t *query = GuiText_getString (my searchText); search (me, query); Melder_free (query); } static void gui_button_cb_search (I, GuiButtonEvent event) { (void) event; iam (Manual); do_search (me); } static void gui_cb_search (GUI_ARGS) { GUI_IAM (Manual); do_search (me); } void structManual :: v_createChildren () { Manual_Parent :: v_createChildren (); ManPages pages = (ManPages) data; // has been installed here by Editor_init () #if defined (macintosh) #define STRING_SPACING 8 #else #define STRING_SPACING 2 #endif int height = Machine_getTextHeight (), y = Machine_getMenuBarHeight () + 4; homeButton = GuiButton_createShown (holder, 104, 168, y, y + height, L"Home", gui_button_cb_home, this, 0); if (pages -> dynamic) { #if motif XtVaSetValues (drawingArea, XmNtopOffset, y + height * 2 + 16, NULL); XtVaSetValues (verticalScrollBar, XmNtopOffset, y + height * 2 + 16, NULL); #endif recordButton = GuiButton_createShown (d_windowForm, 4, 79, y+height+8, y+height+8 + height, L"Record", gui_button_cb_record, this, 0); playButton = GuiButton_createShown (d_windowForm, 85, 160, y+height+8, y+height+8 + height, L"Play", gui_button_cb_play, this, 0); publishButton = GuiButton_createShown (d_windowForm, 166, 166 + 175, y+height+8, y+height+8 + height, L"Copy last played to list", gui_button_cb_publish, this, 0); } GuiButton_createShown (holder, 274, 274 + 69, y, y + height, L"Search:", gui_button_cb_search, this, GuiButton_DEFAULT); searchText = GuiText_createShown (holder, 274+69 + STRING_SPACING, 452 + STRING_SPACING - 2, y, Gui_AUTOMATIC, 0); #if motif /* TODO */ XtAddCallback (searchText, XmNactivateCallback, gui_cb_search, (XtPointer) this); #endif } static void menu_cb_help (EDITOR_ARGS) { EDITOR_IAM (Manual); HyperPage_goToPage (me, L"Manual"); } void structManual :: v_createMenus () { Manual_Parent :: v_createMenus (); Editor_addCommand (this, L"File", L"Print manual...", 0, menu_cb_printRange); Editor_addCommand (this, L"File", L"Save page as HTML file...", 0, menu_cb_writeOneToHtmlFile); Editor_addCommand (this, L"File", L"Save manual to HTML directory...", 0, menu_cb_writeAllToHtmlDir); Editor_addCommand (this, L"File", L"-- close --", 0, NULL); Editor_addCommand (this, L"Go to", L"Search for page (list)...", 0, menu_cb_searchForPageList); } void structManual :: v_createHelpMenuItems (EditorMenu menu) { Manual_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"Manual help", '?', menu_cb_help); } void structManual :: v_defaultHeaders (EditorCommand cmd) { Manual me = (Manual) cmd -> d_editor; ManPages manPages = (ManPages) my data; if (my path) { wchar_t string [400]; static const wchar_t *shortMonth [] = { L"Jan", L"Feb", L"Mar", L"Apr", L"May", L"Jun", L"Jul", L"Aug", L"Sep", L"Oct", L"Nov", L"Dec" }; ManPage page = (ManPage) manPages -> pages -> item [my path]; long date = page -> date; SET_STRING (L"Right or outside header", page -> title) SET_STRING (L"Left or inside footer", page -> author) if (date) { swprintf (string, 400, L"%ls %ld, %ld", shortMonth [date % 10000 / 100 - 1], date % 100, date / 10000); SET_STRING (L"Left or inside header", string) } } } long structManual :: v_getNumberOfPages () { ManPages manPages = (ManPages) data; return manPages -> pages -> size; } long structManual :: v_getCurrentPageNumber () { return path ? path : 1; } void structManual :: v_goToPage_i (long pageNumber) { ManPages manPages = (ManPages) data; if (pageNumber < 1 || pageNumber > manPages -> pages -> size) { if (pageNumber == SEARCH_PAGE) { path = SEARCH_PAGE; Melder_free (currentPageTitle); return; } else Melder_throw ("Page ", pageNumber, " not found."); } path = pageNumber; ManPage page = (ManPage) manPages -> pages -> item [path]; paragraphs = page -> paragraphs; numberOfParagraphs = 0; ManPage_Paragraph par = paragraphs; while ((par ++) -> type) numberOfParagraphs ++; Melder_free (currentPageTitle); currentPageTitle = Melder_wcsdup_f (page -> title); } int structManual :: v_goToPage (const wchar_t *title) { ManPages manPages = (ManPages) data; if (title [0] == '\\' && title [1] == 'F' && title [2] == 'I') { structMelderFile file = { 0 }; MelderDir_relativePathToFile (& manPages -> rootDirectory, title + 3, & file); Melder_recordFromFile (& file); return -1; } else if (title [0] == '\\' && title [1] == 'S' && title [2] == 'C') { autoMelderSetDefaultDir dir (& manPages -> rootDirectory); autoPraatBackground background; try { praat_executeScriptFromFileNameWithArguments (title + 3); } catch (MelderError) { Melder_flushError (NULL); } return 0; } else { long i = ManPages_lookUp (manPages, title); if (! i) Melder_throw ("Page \"", title, "\" not found."); v_goToPage_i (i); return 1; } } void Manual_init (Manual me, GuiObject parent, const wchar *title, Data data, bool ownData) { ManPages manPages = (ManPages) data; wchar windowTitle [101]; long i; ManPage page; ManPage_Paragraph par; if (! (i = ManPages_lookUp (manPages, title))) Melder_throw ("Page \"", title, "\" not found."); my path = i; page = (ManPage) manPages -> pages -> item [i]; my paragraphs = page -> paragraphs; my numberOfParagraphs = 0; par = my paragraphs; while ((par ++) -> type) my numberOfParagraphs ++; if (((ManPage) manPages -> pages -> item [1]) -> title [0] == '-') { wcscpy (windowTitle, & ((ManPage) manPages -> pages -> item [1]) -> title [1]); if (windowTitle [wcslen (windowTitle) - 1] == '-') windowTitle [wcslen (windowTitle) - 1] = '\0'; } else { wcscpy (windowTitle, L"Manual"); } my d_ownData = ownData; HyperPage_init (me, parent, windowTitle, data); MelderDir_copy (& manPages -> rootDirectory, & my rootDirectory); my history [0]. page = Melder_wcsdup_f (title); /* BAD */ } Manual Manual_create (GuiObject parent, const wchar *title, Data data, bool ownData) { try { autoManual me = Thing_new (Manual); Manual_init (me.peek(), parent, title, data, ownData); return me.transfer(); } catch (MelderError) { Melder_throw ("Manual window not created."); } } /* End of file Manual.cpp */ sources_5316/sys/lispio.cpp0000644000176700017670000001075511614253047014557 0ustar paulpaul/* lispio.cpp * * Copyright (C) 1994-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 1995/07/28 * pb 2002/03/07 GPL * pb 2011/05/15 C++ */ #include "melder.h" #include "lispio.h" #include #define my me -> #define thy thee -> int Lispio_openList (const Lispio *me, LispioSeq *thee) { int ch; if (my length == 0) return 0; /* Empty object. */ if (my string [0] != '(') return 0; /* Not a list. */ Melder_assert (my length >= 2); Melder_assert (my string [my length - 1] == ')'); /* Peel leading '(' and trailing ')'. */ thy length = my length - 2; thy string = my string + 1; /* Forget leading spaces. */ while (thy length != 0 && ((ch = *thy string) == ' ' || ch == '\n' || ch == '\t')) { thy length --; thy string ++; } return 1; } int Lispio_openListFromFile (LispioSeq *seq, FILE *f, char *buffer, long maxLength) { long depth = 0, length = 0; int ch; Lispio list; /* Skip spaces to left parenthesis, checking for normal end-of-file. */ while ((ch = getc (f)) != '(') { if (ch == EOF) return EOF; if (ch != ' ' && ch != '\n' && ch != '\t') Melder_throw ("Lispio_openListFromFile: not a list: expected leading `(' but found character `%c'.", ch); } buffer [0] = ch; depth = 1; length = 1; while (depth != 0) { ch = getc (f); if (ch == EOF) Melder_throw ("Lispio_openListFromFile: early end-of-file detected: no matching `)': depth %ld instead of 0.", depth); if (length >= maxLength) Melder_throw ("Lispio_openListFromFile: buffer too small for list: list longer than %ld bytes.", maxLength); buffer [length ++] = ch; if (ch == '(') depth += 1; else if (ch == ')') depth -= 1; } list.length = length; list.string = buffer; return Lispio_openList (& list, seq); // always 1 } char * Lispio_string (const Lispio *me) { autostring8 result = Melder_malloc (char, my length + 1); memcpy (result.peek(), my string, my length); result [my length] = '\0'; return result.transfer(); } int Lispio_equal (const Lispio *me, const Lispio *thee) { long length = my length; return thy length == length && (length == 0 || ! memcmp (my string, thy string, length)); } int Lispio_strequ (const Lispio *me, const char *string) { long length = my length, thyLength = strlen (string); return thyLength == length && (length == 0 || ! memcmp (my string, string, length)); } int Lispio_read (LispioSeq *me, Lispio *first) { int ch; first -> string = my string; if (my length == 0) { first -> length = 0; return 0; } if ((ch = my string [0]) == '(') { /* First is a list? */ long depth = 1; first -> length = 1; while (depth != 0) { ch = first -> string [first -> length ++]; if (ch == '(') depth += 1; else if (ch == ')') depth -= 1; } } else { /* First is an atom? */ first -> length = 1; while ((ch = first -> string [first -> length ++]) != ' ' && ch != '\n' && ch != '\t' && ch != '(' && ch != ')') { } first -> length -= 1; /* Put back delimiter. */ } my length -= first -> length; Melder_assert (my length >= 0); my string += first -> length; while (my length != 0 && ((ch = *my string) == ' ' || ch == '\n' || ch == '\t')) { my length --; my string ++; } /* Remove leading spaces. */ return 1; } long Lispio_count (const LispioSeq *me) { long result = 0; LispioSeq seq = * (LispioSeq *) me; Lispio obj; while (Lispio_read (& seq, & obj)) result ++; return result; } int Lispio_integer (const Lispio *me, long *value) { char buffer [12]; int ichar = 0, numeric = 1; *value = 0; if (my length < 1 || my length > 11) return 0; if (my string [0] == '+' || my string [0] == '-') { if (my length < 2) return 0; /* Only a sign. */ ichar = 1; } for (; ichar < my length; ichar ++) if (! isdigit (my string [ichar])) numeric = 0; strncpy (buffer, my string, my length); buffer [my length] = '\0'; *value = atol (buffer); return numeric; } /* End of file lispio.cpp */ sources_5316/sys/complex.cpp0000644000176700017670000001224411547120517014722 0ustar paulpaul/* complex.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 1999/06/19 * pb 2002/03/07 GPL * pb 2011/04/06 C++ */ #include #include "complex.h" fcomplex fcomplex_add (fcomplex a, fcomplex b) { fcomplex result; result.re = a.re + b.re; result.im = a.im + b.im; return result; } dcomplex dcomplex_add (dcomplex a, dcomplex b) { dcomplex result; result.re = a.re + b.re; result.im = a.im + b.im; return result; } fcomplex fcomplex_sub (fcomplex a, fcomplex b) { fcomplex result; result.re = a.re - b.re; result.im = a.im - b.im; return result; } dcomplex dcomplex_sub (dcomplex a, dcomplex b) { dcomplex result; result.re = a.re - b.re; result.im = a.im - b.im; return result; } fcomplex fcomplex_mul (fcomplex a, fcomplex b) { fcomplex result; result.re = a.re * b.re - a.im * b.im; result.im = a.im * b.re + a.re * b.im; return result; } dcomplex dcomplex_mul (dcomplex a, dcomplex b) { dcomplex result; result.re = a.re * b.re - a.im * b.im; result.im = a.im * b.re + a.re * b.im; return result; } fcomplex fcomplex_create (float re, float im) { fcomplex result; result.re = re; result.im = im; return result; } dcomplex dcomplex_create (double re, double im) { dcomplex result; result.re = re; result.im = im; return result; } fcomplex fcomplex_conjugate (fcomplex z) { fcomplex result; result.re = z.re; result.im = - z.im; return result; } dcomplex dcomplex_conjugate (dcomplex z) { dcomplex result; result.re = z.re; result.im = - z.im; return result; } fcomplex fcomplex_div (fcomplex a, fcomplex b) { fcomplex result; float r, den; if (fabs (b.re) >= fabs (b.im)) { r = b.im / b.re; den = b.re + r * b.im; result.re = (a.re + r * a.im) / den; result.im = (a.im - r * a.re) / den; } else { r = b.re / b.im; den = b.im + r * b.re; result.re = (a.re * r + a.im) / den; result.im = (a.im * r - a.re) / den; } return result; } dcomplex dcomplex_div (dcomplex a, dcomplex b) { dcomplex result; double r, den; if (fabs (b.re) >= fabs (b.im)) { r = b.im / b.re; den = b.re + r * b.im; result.re = (a.re + r * a.im) / den; result.im = (a.im - r * a.re) / den; } else { r = b.re / b.im; den = b.im + r * b.re; result.re = (a.re * r + a.im) / den; result.im = (a.im * r - a.re) / den; } return result; } float fcomplex_abs (fcomplex z) { float x, y, temp; x = fabs (z.re); y = fabs (z.im); if (x == 0.0) return y; if (y == 0.0) return x; if (x > y) { temp = y / x; return x * sqrt (1.0 + temp * temp); } else { temp = x / y; return y * sqrt (1.0 + temp * temp); } } double dcomplex_abs (dcomplex z) { double x, y, temp; x = fabs (z.re); y = fabs (z.im); if (x == 0.0) return y; if (y == 0.0) return x; if (x > y) { temp = y / x; return x * sqrt (1.0 + temp * temp); } else { temp = x / y; return y * sqrt (1.0 + temp * temp); } } fcomplex fcomplex_sqrt (fcomplex z) { fcomplex result; float x, y, w, r; if (z.re == 0 && z.im == 0) { result.re = 0; result.im = 0; return result; } x = fabs (z.re); y = fabs (z.im); if (x >= y) { r = y / x; w = sqrt (x) * sqrt (0.5 * (1.0 + sqrt (1.0 + r * r))); } else { r = x / y; w = sqrt (y) * sqrt (0.5 * (r + sqrt (1.0 + r * r))); } if (z.re >= 0.0) { result.re = w; result.im = z.im / (2.0 * w); } else { result.im = (z.im >= 0) ? w : -w; result.re = z.im / (2.0 * result.im); } return result; } dcomplex dcomplex_sqrt (dcomplex z) { dcomplex result; double x, y, w, r; if (z.re == 0 && z.im == 0) { result.re = 0; result.im = 0; return result; } x = fabs (z.re); y = fabs (z.im); if (x >= y) { r = y / x; w = sqrt (x) * sqrt (0.5 * (1.0 + sqrt (1.0 + r * r))); } else { r = x / y; w = sqrt (y) * sqrt (0.5 * (r + sqrt (1.0 + r * r))); } if (z.re >= 0.0) { result.re = w; result.im = z.im / (2.0 * w); } else { result.im = (z.im >= 0) ? w : -w; result.re = z.im / (2.0 * result.im); } return result; } fcomplex fcomplex_rmul (float x, fcomplex a) { fcomplex result; result.re = x * a.re; result.im = x * a.im; return result; } dcomplex dcomplex_rmul (double x, dcomplex a) { dcomplex result; result.re = x * a.re; result.im = x * a.im; return result; } fcomplex fcomplex_exp (fcomplex z) { fcomplex result; double size = exp (z.re); result.re = size * cos (z.im); result.im = size * sin (z.im); return result; } dcomplex dcomplex_exp (dcomplex z) { dcomplex result; double size = exp (z.re); result.re = size * cos (z.im); result.im = size * sin (z.im); return result; } /* End of file complex.cpp */ sources_5316/num/0000755000176700017670000000000011724671255012534 5ustar paulpaulsources_5316/num/NUMrandom.cpp0000644000176700017670000002221411633766375015110 0ustar paulpaul/* NUMrandom.c * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/04 GPL * pb 2006/12/18 improved comment * pb 2011/03/29 C++ */ /* Based on: Donald E. Knuth (1998): The art of computer programming. Third edition. Vol. 2: seminumerical algorithms. Boston: Addison-Wesley. */ #include "NUM.h" //#include "melder.h" #include /* The random sequence is based on lagged Fibonacci on real numbers in [0; 1) (Knuth:27,29): X [n] = (X [n - 100] + X [n - 37]) mod 1.0 The routine NUMrandomRestart relies on a 52-bit mantissa, so we will get 10^15 different random numbers. The period is infinitely larger than that. To compute x mod 1, Knuth uses the formula x - (int) x However, we use the following, which is faster: if (x > 1.0) x -= 1.0; */ #define LONG_LAG 100 #define SHORT_LAG 37 #define LAG_DIFF (LONG_LAG - SHORT_LAG) /* Each of the 4 billion possible seeds comes with its own stream of random numbers. These streams must be guaranteed not to overlap within the first 2^70 draws (Knuth:187). That's 30 thousand years if one random number takes 1 nanosecond. */ #define STREAM_SEPARATION 70 /* The following value has to be at least 100, i.e. equal to the long lag. If it is 100, then the entire random sequence will be output by NUMrandomFraction. In that case, however, the resulting numbers will not be completely random (Knuth:72), i.e.: X [n] - X [n - 37] = X [n - 63] - X [n - 163] (modulo 1.0) The following Praat script will show this: echo Birthday spacings test: for i to 200 a'i' = randomUniform (0,1) endfor for i from 164 to 200 xn = a'i' j = i - 37 xn37 = a'j' j = i - 63 xn63 = a'j' j = i - 163 xn163 = a'j' diff1 = xn - xn37 diff2 = xn63 - xn163 printline 'diff1' 'diff2' endfor We see that diff1 and diff2 are equal modulo 1. This is why Knuth advises (p.35,72,188) to throw away 909 numbers after generating 100, i.e. the following value will be 1009. */ #define QUALITY 1009 /* A test for the integrity of NUMrandomRestart and NUMrandomFraction (Knuth:188,603): NUMrandomRestart (310952); for (i = 1; i <= 1009 * 2009 - 100 + 1; i ++) x = NUMrandomFraction (); Melder_information (Melder_double (x)); With QUALITY set to 100, this should give 0.27452626307394156768 (Knuth:603). With QUALITY set to 1009, it should give 0.73203216867254750078. */ static double randomArray [LONG_LAG]; static int randomInited = 0; static long randomArrayPointer1, randomArrayPointer2, iquality; void NUMrandomRestart (unsigned long seed) { /* Based on Knuth, p. 187,602. Knuth had: int s = seed; This is incorrect (even if an int is 32 bit), since a negative value causes a loop in the test if (s != 0) s >>= 1; because the >> operator on negative integers adds a sign bit to the left. */ long t, j; double u [2 * LONG_LAG - 1], ul [2 * LONG_LAG - 1]; double ulp = 1.0 / (1L << 30) / (1L << 22), ss; ss = 2.0 * ulp * (seed + 2); /* QUESTION: does this work if seed exceeds 2^32 - 3? See Knuth p. 187. */ for (j = 0; j < LONG_LAG; j ++) { u [j] = ss; ul [j] = 0.0; ss += ss; if (ss >= 1.0) ss -= 1.0 - 2 * ulp; } for (; j < 2 * LONG_LAG - 1; j ++) u [j] = ul [j] = 0.0; u [1] += ulp; ul [1] = ulp; t = STREAM_SEPARATION - 1; while (t > 0) { for (j = LONG_LAG - 1; j > 0; j --) { ul [j + j] = ul [j]; u [j + j] = u [j]; } for (j = 2 * LONG_LAG - 2; j > LAG_DIFF; j -= 2) { ul [2 * LONG_LAG - 1 - j] = 0.0; u [2 * LONG_LAG - 1 - j] = u [j] - ul [j]; } for (j = 2 * LONG_LAG - 2; j >= LONG_LAG; j --) if (ul [j] != 0) { ul [j - LAG_DIFF] = ulp - ul [j - LAG_DIFF]; u [j - LAG_DIFF] += u [j]; if (u [j - LAG_DIFF] >= 1.0) u [j - LAG_DIFF] -= 1.0; ul [j - LONG_LAG] = ulp - ul [j - LONG_LAG]; u [j - LONG_LAG] += u [j]; if (u [j - LONG_LAG] >= 1.0) u [j - LONG_LAG] -= 1.0; } if ((seed & 1) != 0) { for (j = LONG_LAG; j > 0; j --) { ul [j] = ul [j - 1]; u [j] = u [j - 1]; } ul [0] = ul [LONG_LAG]; u [0] = u [LONG_LAG]; if (ul [LONG_LAG] != 0) { ul [SHORT_LAG] = ulp - ul [SHORT_LAG]; u [SHORT_LAG] += u [LONG_LAG]; if (u [SHORT_LAG] >= 1.0) u [SHORT_LAG] -= 1.0; } } if (seed != 0) { seed >>= 1; } else { t --; } } for (j = 0; j < SHORT_LAG; j ++) randomArray [j + LAG_DIFF] = u [j]; for (; j < LONG_LAG; j ++) randomArray [j - SHORT_LAG] = u [j]; randomArrayPointer1 = 0; randomArrayPointer2 = LAG_DIFF; iquality = 0; randomInited = 1; } double NUMrandomFraction (void) { /* Knuth uses a long random array of length QUALITY to copy values from randomArray. We save 8 kilobytes by using randomArray as a cyclic array (10% speed loss). */ long p1, p2; double newValue; if (! randomInited) NUMrandomRestart (time (NULL)); p1 = randomArrayPointer1, p2 = randomArrayPointer2; if (p1 >= LONG_LAG) p1 = 0; if (p2 >= LONG_LAG) p2 = 0; newValue = randomArray [p1] + randomArray [p2]; if (newValue >= 1.0) newValue -= 1.0; randomArray [p1] = newValue; p1 ++; p2 ++; if (++ iquality == LONG_LAG) { for (; iquality < QUALITY; iquality ++) { double newValue2; /* Possible future minor speed improvement: the cyclic array is walked down instead of up. The following tests will then be for 0. */ if (p1 >= LONG_LAG) p1 = 0; if (p2 >= LONG_LAG) p2 = 0; newValue2 = randomArray [p1] + randomArray [p2]; if (newValue2 >= 1.0) newValue2 -= 1.0; randomArray [p1] = newValue2; p1 ++; p2 ++; } iquality = 0; } randomArrayPointer1 = p1; randomArrayPointer2 = p2; return newValue; } double NUMrandomUniform (double lowest, double highest) { return lowest + (highest - lowest) * NUMrandomFraction (); } long NUMrandomInteger (long lowest, long highest) { return lowest + (long) ((highest - lowest + 1) * NUMrandomFraction ()); } #define repeat do #define until(cond) while (! (cond)) double NUMrandomGauss (double mean, double standardDeviation) { /* Knuth, p. 122. */ static int secondAvailable = 0; static double y; double s, x; if (secondAvailable) { secondAvailable = FALSE; return mean + standardDeviation * y; } else { repeat { x = 2.0 * NUMrandomFraction () - 1.0; /* Inside the square [-1; 1] x [-1; 1]. */ y = 2.0 * NUMrandomFraction () - 1.0; s = x * x + y * y; } until (s < 1.0); /* Inside the unit circle. */ if (s == 0.0) { x = y = 0.0; } else { double factor = sqrt (-2.0 * log (s) / s); x *= factor, y *= factor; } secondAvailable = TRUE; return mean + standardDeviation * x; } } double NUMrandomPoisson (double mean) { /* The Poisson distribution is P(k) = mean^k * exp (- mean) / k! We have to find a function, with known primitive, that is always (a bit) greater than P (k). This function is based on the Lorentzian distribution, with a maximum of P(mean)/0.9 at k=mean: f (k) = mean^mean * exp (- mean) / mean! / (0.9 * (1 + (k - mean)^2 / (2 * mean))) The tangent is computed as the deviate tangent = tan (pi * unif (0, 1)) This must equal the square root of (k - mean)^2 / (2 * mean), so that a trial value for k is given by k = floor (mean + tangent * sqrt (2 * mean)) The probability that this is a good value is proportionate to the ratio of the Poisson distribution and the encapsulating function: probability = P (k) / f (k) = 0.9 * (1 + tangent^2) * mean ^ (k - mean) * mean! / k! The last two factors can be calculated as exp ((k - mean) * ln (mean) + lnGamma (mean + 1) - lnGamma (k + 1)) */ static double previousMean = -1.0; /* This routine may well be called repeatedly with the same mean. Optimize. */ if (mean < 8.0) { static double expMean; double product = 1.0; long result = -1; if (mean != previousMean) { previousMean = mean; expMean = exp (- mean); } repeat { product *= NUMrandomFraction (); result ++; } until (product <= expMean); return result; } else { static double sqrtTwoMean, lnMean, lnMeanFactorial; double result, probability, tangent; if (mean != previousMean) { previousMean = mean; sqrtTwoMean = sqrt (2.0 * mean); lnMean = log (mean); lnMeanFactorial = NUMlnGamma (mean + 1.0); } repeat { repeat { tangent = tan (NUMpi * NUMrandomFraction ()); result = mean + tangent * sqrtTwoMean; } until (result >= 0.0); result = floor (result); probability = 0.9 * (1.0 + tangent * tangent) * exp ((result - mean) * lnMean + lnMeanFactorial - NUMlnGamma (result + 1.0)); } until (NUMrandomFraction () <= probability); return result; } } /* End of file NUMrandom.cpp */ sources_5316/num/Makefile0000644000176700017670000000100411704273347014165 0ustar paulpaul# Makefile of the library "num" # Paul Boersma, 14 January 2012 include ../makefile.defs CPPFLAGS = -I ../external/gsl -I ../external/glpk -I ../sys -I ../dwsys OBJECTS = NUM.o NUMarrays.o NUMrandom.o NUMsort.o NUMear.o NUMlinprog.o .PHONY: all clean all: libnum.a clean: $(RM) $(OBJECTS) $(RM) libnum.a libnum.a: $(OBJECTS) touch libnum.a rm libnum.a ar cq libnum.a $(OBJECTS) $(RANLIB) libnum.a $(OBJECTS): *.h ../external/gsl/*.h ../external/glpk/*.h ../sys/*.h ../dwsys/*.h sources_5316/num/NUMsort.cpp0000644000176700017670000000753611544420737014617 0ustar paulpaul/* NUMsort.c * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/06/24 removed NUMselect * pb 2007/08/10 NUMsort_strW * pb 2008/01/21 double * pb 2011/03/29 C++ */ #include "NUM.h" #include /* NUMsort uses heapsort. J.W.J. Williams (1964). 'xx.' Communications of the Association for Computing Machinery 7: 347-348. R.W. Floyd (1964). 'xx.' Communications of the Association for Computing Machinery 7: 701. Algorithm follows p. 145 of: Donald E. Knuth (1998): The art of computer programming. Third edition. Vol. 3: sorting and searching. Boston: Addison-Wesley. Modification: there is no distinction between record and key. */ #define MACRO_NUMsort(TYPE) { \ long l, r, j, i; \ TYPE k; \ if (n < 2) return; /* Already sorted. */ \ /* This n<2 step is absent from Press et al.'s implementation, */ \ /* which will therefore not terminate on if(--ir==1). */ \ /* Knuth's initial assumption is now fulfilled: n >= 2. */ \ if (n == 2) { \ if (a [1] > a [2]) { TYPE min = a [2]; a [2] = a [1]; a [1] = min; } \ return; \ } \ if (n <= 12) { \ for (i = 1; i < n; i ++) { \ TYPE min = a [i]; \ long pmin = i; \ for (j = i + 1; j <= n; j ++) if (a [j] < min) { \ min = a [j]; \ pmin = j; \ } \ a [pmin] = a [i]; \ a [i] = min; \ } \ return; \ } \ l = (n >> 1) + 1; \ r = n; \ for (;;) { \ if (l > 1) { \ l --; \ k = a [l]; \ } else /* l == 1 */ { \ k = a [r]; \ a [r] = a [1]; \ r --; \ if (r == 1) { a [1] = k; return; } \ } \ j = l; \ for (;;) { \ i = j; \ j = j << 1; \ if (j > r) break; \ if (j < r && a [j] < a [j + 1]) j ++; \ if (k >= a [j]) break; \ a [i] = a [j]; \ } \ a [i] = k; \ } \ } void NUMsort_d (long n, double a []) MACRO_NUMsort (double) void NUMsort_i (long n, int a []) MACRO_NUMsort (int) void NUMsort_l (long n, long a []) MACRO_NUMsort (long) void NUMsort_str (long n, wchar_t *a []) { long l, r, j, i; wchar_t *k; if (n < 2) return; l = (n >> 1) + 1; r = n; for (;;) { if (l > 1) { l --; k = a [l]; } else { k = a [r]; a [r] = a [1]; r --; if (r == 1) { a [1] = k; return; } } j = l; for (;;) { i = j; j = j << 1; if (j > r) break; if (j < r && wcscmp (a [j], a [j + 1]) < 0) j ++; if (wcscmp (k, a [j]) >= 0) break; a [i] = a [j]; } a [i] = k; } } void NUMsort_p (long n, void *a [], int (*compare) (const void *, const void *)) { long l, r, j, i; void *k; if (n < 2) return; l = (n >> 1) + 1; r = n; for (;;) { if (l > 1) { l --; k = a [l]; } else { k = a [r]; a [r] = a [1]; r --; if (r == 1) { a [1] = k; return; } } j = l; for (;;) { i = j; j = j << 1; if (j > r) break; if (j < r && compare (a [j], a [j + 1]) < 0) j ++; if (compare (k, a [j]) >= 0) break; a [i] = a [j]; } a [i] = k; } } double NUMquantile (long n, double a [], double factor) { double place = factor * n + 0.5; long left = floor (place); if (n < 1) return 0.0; if (n == 1) return a [1]; if (left < 1) left = 1; if (left >= n) left = n - 1; if (a [left + 1] == a [left]) return a [left]; return a [left] + (place - left) * (a [left + 1] - a [left]); } /* End of file NUMsort.cpp */ sources_5316/num/NUMlinprog.cpp0000644000176700017670000001200011712573645015264 0ustar paulpaul/* NUMlinprog.cpp * * Copyright (C) 2008-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2008/04/12 created * pb 2011/03/29 C++ */ #include "NUM.h" #include "../external/glpk/glpk.h" #define my me -> struct structNUMlinprog { glp_prob *linearProgram; long numberOfConstraints, ivar, numberOfVariables; int *ind; double *val; int status; }; void NUMlinprog_delete (NUMlinprog me) { if (me == NULL) return; if (my linearProgram != NULL) glp_delete_prob (my linearProgram); NUMvector_free (my ind, 1); NUMvector_free (my val, 1); Melder_free (me); } NUMlinprog NUMlinprog_new (bool maximize) { NUMlinprog me = NULL; try { Melder_calloc (structNUMlinprog, 1); my linearProgram = glp_create_prob (); // TODO: check glp_set_obj_dir (my linearProgram, maximize ? GLP_MAX : GLP_MIN); } catch (MelderError) { if (me) NUMlinprog_delete (me); return NULL; } return me; } void NUMlinprog_addVariable (NUMlinprog me, double lowerBound, double upperBound, double coeff) { glp_add_cols (my linearProgram, 1); glp_set_col_bnds (my linearProgram, ++ my numberOfVariables, lowerBound == NUMundefined ? ( upperBound == NUMundefined ? GLP_FR : GLP_UP ) : upperBound == NUMundefined ? GLP_LO : lowerBound == upperBound ? GLP_FX : GLP_DB, lowerBound, upperBound); glp_set_obj_coef (my linearProgram, my ivar, coeff); } void NUMlinprog_addConstraint (NUMlinprog me, double lowerBound, double upperBound) { try { if (my ind == NULL) { /* * Check without change. */ autoNUMvector ind (1, my numberOfVariables); autoNUMvector val (1, my numberOfVariables); /* * Change without error. */ my ind = ind.transfer(); my val = val.transfer(); } glp_add_rows (my linearProgram, 1); // TODO: check glp_set_row_bnds (my linearProgram, ++ my numberOfConstraints, lowerBound == NUMundefined ? ( upperBound == NUMundefined ? GLP_FR : GLP_UP ) : upperBound == NUMundefined ? GLP_LO : lowerBound == upperBound ? GLP_FX : GLP_DB, lowerBound, upperBound); my ivar = 0; } catch (MelderError) { Melder_throw ("Linear programming: constraint not added."); } } void NUMlinprog_addConstraintCoefficient (NUMlinprog me, double coefficient) { ++ my ivar; my ind [my ivar] = my ivar; my val [my ivar] = coefficient; if (my ivar == my numberOfVariables) { glp_set_mat_row (my linearProgram, my numberOfConstraints, my numberOfVariables, my ind, my val); } } void NUMlinprog_run (NUMlinprog me) { try { glp_smcp parm; glp_init_smcp (& parm); parm. msg_lev = GLP_MSG_OFF; my status = glp_simplex (my linearProgram, & parm); switch (my status) { case GLP_EBADB: Melder_throw ("Unable to start the search, because the initial basis is invalid."); case GLP_ESING: Melder_throw (L"Unable to start the search, because the basis matrix is singular."); case GLP_ECOND: Melder_throw (L"Unable to start the search, because the basis matrix is ill-conditioned."); case GLP_EBOUND: Melder_throw (L"Unable to start the search, because some variables have incorrect bounds."); case GLP_EFAIL: Melder_throw (L"Search prematurely terminated due to solver failure."); case GLP_EOBJLL: Melder_throw (L"Search prematurely terminated: lower limit reached."); case GLP_EOBJUL: Melder_throw (L"Search prematurely terminated: upper limit reached."); case GLP_EITLIM: Melder_throw (L"Search prematurely terminated: iteration limit exceeded."); case GLP_ETMLIM: Melder_throw (L"Search prematurely terminated: time limit exceeded."); case GLP_ENOPFS: Melder_throw (L"The problem has no primal feasible solution."); case GLP_ENODFS: Melder_throw (L"The problem has no dual feasible solution."); default: break; } my status = glp_get_status (my linearProgram); switch (my status) { case GLP_INFEAS: Melder_throw (L"Solution is infeasible."); case GLP_NOFEAS: Melder_throw (L"Problem has no feasible solution."); case GLP_UNBND: Melder_throw (L"Problem has unbounded solution."); case GLP_UNDEF: Melder_throw (L"Solution is undefined."); default: break; } if (my status == GLP_FEAS) { Melder_warning (L"Linear programming solution is feasible but not optimal."); } } catch (MelderError) { Melder_throw ("Linear programming: not run."); } } double NUMlinprog_getPrimalValue (NUMlinprog me, long ivar) { return glp_get_col_prim (my linearProgram, ivar); } /* End of file NUMlinprog.cpp */ sources_5316/num/NUMarrays.cpp0000644000176700017670000003145311724671255015127 0ustar paulpaul/* NUMarrays.cpp * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2007/07/21 readText and writeText API changes * pb 2008/01/19 include storage in I/O names * pb 2009/03/14 NUMvector_add * pb 2011/03/29 C++ * pb 2011/05/14 removed char (because only signed char and unsigned char can be read and written correctly) * pb 2011/07/05 C++ */ #include "NUM.h" #include "melder.h" static long theTotalNumberOfArrays; long NUM_getTotalNumberOfArrays (void) { return theTotalNumberOfArrays; } /*** Generic memory routines for vectors. ***/ void * NUMvector (long elementSize, long lo, long hi) { try { if (hi < lo) return NULL; // not an error char *result; Melder_assert (sizeof (char) == 1); // some say that this is true by definition for (;;) { // not very infinite: 99.999 % of the time once, 0.001 % twice result = reinterpret_cast (_Melder_calloc (hi - lo + 1, elementSize)); if (result -= lo * elementSize) break; // this will normally succeed at the first try (void) Melder_realloc_f (result + lo * elementSize, 1); // make "sure" that the second try will succeed (not *very* sure, because realloc might move memory even if it shrinks) } theTotalNumberOfArrays += 1; return result; } catch (MelderError) { Melder_throw ("Vector of elements not created."); } } void NUMvector_free (long elementSize, void *v, long lo) { if (v == NULL) return; // no error char *dum = (char *) v + lo * elementSize; Melder_free (dum); theTotalNumberOfArrays -= 1; } void * NUMvector_copy (long elementSize, void *v, long lo, long hi) { try { if (v == NULL) return NULL; char *result = reinterpret_cast (NUMvector (elementSize, lo, hi)); long offset = lo * elementSize; memcpy (result + offset, (char *) v + offset, (hi - lo + 1) * elementSize); return result; } catch (MelderError) { Melder_throw ("Vector of elements not copied."); } } void NUMvector_copyElements (long elementSize, void *v, void *to, long lo, long hi) { long offset = lo * elementSize; Melder_assert (v != NULL && to != NULL); if (hi >= lo) memcpy ((char *) to + offset, (char *) v + offset, (hi - lo + 1) * elementSize); } bool NUMvector_equal (long elementSize, void *v1, void *v2, long lo, long hi) { long offset = lo * elementSize; Melder_assert (v1 != NULL && v2 != NULL); return ! memcmp ((char *) v1 + offset, (char *) v2 + offset, (hi - lo + 1) * elementSize); } void NUMvector_append (long elementSize, void **v, long lo, long *hi) { try { char *result; if (*v == NULL) { result = reinterpret_cast (NUMvector (elementSize, lo, lo)); *hi = lo; } else { long offset = lo * elementSize; for (;;) { // not very infinite: 99.999 % of the time once, 0.001 % twice result = reinterpret_cast (Melder_realloc ((char *) *v + offset, (*hi - lo + 2) * elementSize)); if ((result -= offset) != NULL) break; // this will normally succeed at the first try (void) Melder_realloc_f (result + offset, 1); // make "sure" that the second try will succeed } (*hi) ++; memset (result + *hi * elementSize, 0, elementSize); // initialize the new element to zeroes } *v = result; } catch (MelderError) { Melder_throw ("Vector: element not appended."); } } void NUMvector_insert (long elementSize, void **v, long lo, long *hi, long position) { try { char *result; if (*v == NULL) { result = reinterpret_cast (NUMvector (elementSize, lo, lo)); *hi = lo; Melder_assert (position == lo); } else { result = reinterpret_cast (NUMvector (elementSize, lo, *hi + 1)); Melder_assert (position >= lo && position <= *hi + 1); NUMvector_copyElements (elementSize, *v, result, lo, position - 1); NUMvector_copyElements (elementSize, *v, result + elementSize, position, *hi); NUMvector_free (elementSize, *v, lo); (*hi) ++; } *v = result; } catch (MelderError) { Melder_throw ("Vector: element not inserted."); } } /*** Generic memory routines for matrices. ***/ void * NUMmatrix (long elementSize, long row1, long row2, long col1, long col2) { try { /* * Allocate room for the row pointers. */ long numberOfRows = row2 - row1 + 1; char **result; Melder_assert (sizeof (char) == 1); // true by definition for (;;) { result = reinterpret_cast (_Melder_malloc_f (numberOfRows * sizeof (char *))); // assume that all pointers have the same size result -= row1; if (result != NULL) break; // this will normally succeed at the first try (void) Melder_realloc_f (result + row1, 1); // make "sure" that the second try will succeed } /* * Allocate room for the cells. * The first row pointer points to below the first cell. */ long numberOfColumns = col2 - col1 + 1; for (;;) { try { result [row1] = reinterpret_cast (_Melder_calloc (numberOfRows * numberOfColumns, elementSize)); } catch (MelderError) { result += row1; Melder_free (result); // free the row pointers throw MelderError (); } if ((result [row1] -= col1 * elementSize) != NULL) break; // this will normally succeed at the first try (void) Melder_realloc_f (result [row1] + col1 * elementSize, 1); // make "sure" that the second try will succeed } long columnSize = numberOfColumns * elementSize; for (long irow = row1 + 1; irow <= row2; irow ++) result [irow] = result [irow - 1] + columnSize; theTotalNumberOfArrays += 1; return result; } catch (MelderError) { Melder_throw ("Matrix of elements not created."); } } void NUMmatrix_free (long elementSize, void *m, long row1, long col1) { if (m == NULL) return; char *dummy1 = ((char **) m) [row1] + col1 * elementSize; Melder_free (dummy1); char **dummy2 = (char **) m + row1; Melder_free (dummy2); theTotalNumberOfArrays -= 1; } void * NUMmatrix_copy (long elementSize, void * m, long row1, long row2, long col1, long col2) { try { if (m == NULL) return NULL; char **result = reinterpret_cast (NUMmatrix (elementSize, row1, row2, col1, col2)); if (result == NULL) return NULL; long columnOffset = col1 * elementSize; long dataSize = (row2 - row1 + 1) * (col2 - col1 + 1) * elementSize; memcpy (result [row1] + columnOffset, ((char **) m) [row1] + columnOffset, dataSize); return result; } catch (MelderError) { Melder_throw ("Matrix of elements not copied."); } } void NUMmatrix_copyElements (long elementSize, void *m, void *to, long row1, long row2, long col1, long col2) { Melder_assert (m != NULL && to != NULL); long columnOffset = col1 * elementSize; long dataSize = (row2 - row1 + 1) * (col2 - col1 + 1) * elementSize; memcpy (((char **) to) [row1] + columnOffset, ((char **) m) [row1] + columnOffset, dataSize); } bool NUMmatrix_equal (long elementSize, void *m1, void *m2, long row1, long row2, long col1, long col2) { Melder_assert (m1 != NULL && m2 != NULL); long columnOffset = col1 * elementSize; long dataSize = (row2 - row1 + 1) * (col2 - col1 + 1) * elementSize; return ! memcmp (((char **) m1) [row1] + columnOffset, ((char **) m2) [row1] + columnOffset, dataSize); } /*** Typed I/O routines for vectors and matrices. ***/ #define FUNCTION(type,storage) \ void NUMvector_writeText_##storage (const type *v, long lo, long hi, MelderFile file, const wchar *name) { \ texputintro (file, name, L" []: ", hi >= lo ? NULL : L"(empty)", 0,0,0); \ for (long i = lo; i <= hi; i ++) \ texput##storage (file, v [i], name, L" [", Melder_integer (i), L"]", 0,0); \ texexdent (file); \ if (feof (file -> filePointer) || ferror (file -> filePointer)) Melder_throw ("Write error."); \ } \ void NUMvector_writeBinary_##storage (const type *v, long lo, long hi, FILE *f) { \ for (long i = lo; i <= hi; i ++) \ binput##storage (v [i], f); \ if (feof (f) || ferror (f)) Melder_throw ("Write error."); \ } \ void NUMvector_writeCache_##storage (const type *v, long lo, long hi, CACHE *f) { \ for (long i = lo; i <= hi; i ++) \ cacput##storage (v [i], f); \ } \ type * NUMvector_readText_##storage (long lo, long hi, MelderReadText text, const char *name) { \ type *result = NULL; \ try { \ result = NUMvector (lo, hi); \ for (long i = lo; i <= hi; i ++) { \ try { \ result [i] = texget##storage (text); \ } catch (MelderError) { \ Melder_throw ("Could not read ", name, " [", i, "]."); \ } \ } \ return result; \ } catch (MelderError) { \ NUMvector_free (result, lo); \ throw; \ } \ } \ type * NUMvector_readBinary_##storage (long lo, long hi, FILE *f) { \ type *result = NULL; \ try { \ result = NUMvector (lo, hi); \ for (long i = lo; i <= hi; i ++) { \ result [i] = binget##storage (f); \ } \ return result; \ } catch (MelderError) { \ NUMvector_free (result, lo); \ throw; \ } \ } \ type * NUMvector_readCache_##storage (long lo, long hi, CACHE *f) { \ type *result = NULL; \ try { \ result = NUMvector (lo, hi); \ for (long i = lo; i <= hi; i ++) { \ result [i] = cacget##storage (f); \ } \ return result; \ } catch (MelderError) { \ NUMvector_free (result, lo); \ throw; \ } \ } \ void NUMmatrix_writeText_##storage (type **m, long row1, long row2, long col1, long col2, MelderFile file, const wchar_t *name) { \ texputintro (file, name, L" [] []: ", row2 >= row1 ? NULL : L"(empty)", 0,0,0); \ if (row2 >= row1) { \ for (long irow = row1; irow <= row2; irow ++) { \ texputintro (file, name, L" [", Melder_integer (irow), L"]:", 0,0); \ for (long icol = col1; icol <= col2; icol ++) { \ texput##storage (file, m [irow] [icol], name, L" [", Melder_integer (irow), L"] [", Melder_integer (icol), L"]"); \ } \ texexdent (file); \ } \ } \ texexdent (file); \ if (feof (file -> filePointer) || ferror (file -> filePointer)) Melder_throw ("Write error."); \ } \ void NUMmatrix_writeBinary_##storage (type **m, long row1, long row2, long col1, long col2, FILE *f) { \ if (row2 >= row1) { \ for (long irow = row1; irow <= row2; irow ++) { \ for (long icol = col1; icol <= col2; icol ++) \ binput##storage (m [irow] [icol], f); \ } \ } \ if (feof (f) || ferror (f)) Melder_throw ("Write error."); \ } \ void NUMmatrix_writeCache_##storage (type **m, long row1, long row2, long col1, long col2, CACHE *f) { \ if (row2 >= row1) { \ for (long irow = row1; irow <= row2; irow ++) { \ for (long icol = col1; icol <= col2; icol ++) \ cacput##storage (m [irow] [icol], f); \ } \ } \ } \ type ** NUMmatrix_readText_##storage (long row1, long row2, long col1, long col2, MelderReadText text, const char *name) { \ type **result = NULL; \ try { \ result = NUMmatrix (row1, row2, col1, col2); \ for (long irow = row1; irow <= row2; irow ++) for (long icol = col1; icol <= col2; icol ++) { \ try { \ result [irow] [icol] = texget##storage (text); \ } catch (MelderError) { \ Melder_throw ("Could not read ", name, " [", irow, "] [", icol, "]."); \ } \ } \ return result; \ } catch (MelderError) { \ NUMmatrix_free (result, row1, col1); \ throw; \ } \ } \ type ** NUMmatrix_readBinary_##storage (long row1, long row2, long col1, long col2, FILE *f) { \ type **result = NULL; \ try { \ result = NUMmatrix (row1, row2, col1, col2); \ for (long irow = row1; irow <= row2; irow ++) for (long icol = col1; icol <= col2; icol ++) \ result [irow] [icol] = binget##storage (f); \ return result; \ } catch (MelderError) { \ NUMmatrix_free (result, row1, col1); \ throw; \ } \ } \ type ** NUMmatrix_readCache_##storage (long row1, long row2, long col1, long col2, CACHE *f) { \ type **result = NULL; \ try { \ result = NUMmatrix (row1, row2, col1, col2); \ for (long irow = row1; irow <= row2; irow ++) for (long icol = col1; icol <= col2; icol ++) \ result [irow] [icol] = cacget##storage (f); \ return result; \ } catch (MelderError) { \ NUMmatrix_free (result, row1, col1); \ throw; \ } \ } FUNCTION (signed char, i1) FUNCTION (int, i2) FUNCTION (long, i4) FUNCTION (unsigned char, u1) FUNCTION (unsigned int, u2) FUNCTION (unsigned long, u4) FUNCTION (double, r4) FUNCTION (double, r8) FUNCTION (fcomplex, c8) FUNCTION (dcomplex, c16) #undef FUNCTION /* End of file NUMarrays.cpp */ sources_5316/num/NUMear.cpp0000644000176700017670000000545211544420623014364 0ustar paulpaul/* NUMear.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 1999/06/26 * pb 2002/03/07 GPL * pb 2011/03/29 C++ */ #include "NUM.h" double NUMhertzToBark (double hertz) { double r = hertz / 650; return hertz < 0 ? NUMundefined : 7.0 * log (r + sqrt (1 + r * r)); } double NUMbarkToHertz (double bark) { return bark < 0 ? NUMundefined : 650.0 * sinh (bark / 7.0); } double NUMphonToDifferenceLimens (double phon) { return phon < 0 ? NUMundefined : 30 * (pow (61.0 / 60, phon) - 1); } double NUMdifferenceLimensToPhon (double ndli) { return ndli < 0 ? NUMundefined : log (1 + ndli / 30) / log (61.0 / 60); } double NUMsoundPressureToPhon (double soundPressure, double bark) { double result = 0, dum; if (soundPressure <= 0 || bark < 0) return NUMundefined; /* dB = 20 * log10 (soundPressure / threshold) */ if (soundPressure > 0) result = 20 * log10 (soundPressure / 2.0e-5); /* First approximation: phon = dB */ /* Phones from dB */ if (result < 90 && bark < 8.0) { dum = (90 - result) * (8.0 - bark); result -= dum * dum / 2500; } dum = bark / 3.6 - 5; result += 5 * exp (- dum * dum); if (bark > 20.0) { dum = bark - 20; result -= 0.5 * dum * dum; } if (result < 0) result = 0; return result; } double NUMhertzToMel (double hertz) { return hertz < 0 ? NUMundefined : 550.0 * log (1.0 + hertz / 550.0); } double NUMmelToHertz (double mel) { return mel < 0 ? NUMundefined : 550.0 * (exp (mel / 550.0) - 1); } double NUMhertzToSemitones (double hertz) { return hertz <= 0.0 ? NUMundefined : 12.0 * log (hertz / 100.0) / NUMln2; } double NUMsemitonesToHertz (double semitones) { return semitones == NUMundefined ? NUMundefined : 100.0 * exp (semitones * (NUMln2 / 12.0)); } /* Moore & Glasberg 1983 JASA 74: 750 */ double NUMerb (double f) { return 6.23e-6 * f * f + 0.09339 * f + 28.52; } double NUMhertzToErb (double hertz) { return hertz < 0 ? NUMundefined : 11.17 * log ((hertz + 312.0) / (hertz + 14680.0)) + 43.0; } double NUMerbToHertz (double erb) { double dum = exp ((erb - 43.0) / 11.17); return erb < 0 ? NUMundefined : (14680.0 * dum - 312.0) / (1.0 - dum); } /* End of file NUMear.cpp */ sources_5316/num/NUM.h0000644000176700017670000005367111724666750013364 0ustar paulpaul#ifndef _NUM_h_ #define _NUM_h_ /* NUM.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* "NUM" = "NUMerics" */ /* More mathematical and numerical things than there are in . */ /********** Inherit all the ANSI routines from math.h **********/ /* On the sgi, math.h declares some bessel functions. */ /* The following statements suppress these declarations */ /* so that the compiler will give no warnings */ /* when you redeclare y0 etc. in your code. */ #ifdef sgi #define y0 sgi_y0 #define y1 sgi_y1 #define yn sgi_yn #define j0 sgi_j0 #define j1 sgi_j1 #define jn sgi_jn #endif #include #ifdef sgi #undef y0 #undef y1 #undef yn #undef j0 #undef j1 #undef jn #endif #include #include #include "abcio.h" #define NUMlog2(x) (log (x) * NUMlog2e) void NUMinit (void); double NUMpow (double base, double exponent); /* Zero for non-positive base. */ void NUMshift (double *x, double xfrom, double xto); void NUMscale (double *x, double xminfrom, double xmaxfrom, double xminto, double xmaxto); /********** Constants ********** * Forty-digit constants computed by e.g.: * bc -l * scale=42 * print e(1) * Then rounding away the last two digits. */ // print e(1) #define NUMe 2.7182818284590452353602874713526624977572 // print 1/l(2) #define NUMlog2e 1.4426950408889634073599246810018921374266 // print l(10)/l(2) #define NUMlog2_10 3.3219280948873623478703194294893901758648 // print 1/l(10) #define NUMlog10e 0.4342944819032518276511289189166050822944 // print l(2)/l(10) #define NUMlog10_2 0.3010299956639811952137388947244930267682 // print l(2) #define NUMln2 0.6931471805599453094172321214581765680755 // print l(10) #define NUMln10 2.3025850929940456840179914546843642076011 // print a(1)*8 #define NUM2pi 6.2831853071795864769252867665590057683943 // print a(1)*4 #define NUMpi 3.1415926535897932384626433832795028841972 // print a(1)*2 #define NUMpi_2 1.5707963267948966192313216916397514420986 // print a(1) #define NUMpi_4 0.7853981633974483096156608458198757210493 // print 0.25/a(1) #define NUM1_pi 0.3183098861837906715377675267450287240689 // print 0.5/a(1) #define NUM2_pi 0.6366197723675813430755350534900574481378 // print sqrt(a(1)*4) #define NUMsqrtpi 1.7724538509055160272981674833411451827975 // print sqrt(a(1)*8) #define NUMsqrt2pi 2.5066282746310005024157652848110452530070 // print 1/sqrt(a(1)*8) #define NUM1_sqrt2pi 0.3989422804014326779399460599343818684759 // print 1/sqrt(a(1)) #define NUM2_sqrtpi 1.1283791670955125738961589031215451716881 // print l(a(1)*4) #define NUMlnpi 1.1447298858494001741434273513530587116473 // print sqrt(2) #define NUMsqrt2 1.4142135623730950488016887242096980785697 // print sqrt(0.5) #define NUMsqrt1_2 0.7071067811865475244008443621048490392848 // print sqrt(3) #define NUMsqrt3 1.7320508075688772935274463415058723669428 // print sqrt(5) #define NUMsqrt5 2.2360679774997896964091736687312762354406 // print sqrt(6) #define NUMsqrt6 2.4494897427831780981972840747058913919659 // print sqrt(7) #define NUMsqrt7 2.6457513110645905905016157536392604257102 // print sqrt(8) #define NUMsqrt8 2.8284271247461900976033774484193961571393 // print sqrt(10) #define NUMsqrt10 3.1622776601683793319988935444327185337196 // print sqrt(5)/2-0.5 #define NUM_goldenSection 0.6180339887498948482045868343656381177203 // The Euler-Mascheroni constant cannot be computed by bc. // Instead we use the 40 digits computed by Johann von Soldner in 1809. #define NUM_euler 0.5772156649015328606065120900824024310422 #define NUMundefined HUGE_VAL #define NUMdefined(x) ((x) != NUMundefined) /********** Arrays with one index (NUMarrays.c) **********/ void * NUMvector (long elementSize, long lo, long hi); /* Function: create a vector [lo...hi] with all values initialized to 0. Queue an error message and return NULL if anything went wrong. Preconditions: hi >= lo; */ void NUMvector_free (long elementSize, void *v, long lo); /* Function: destroy a vector v that was created with NUMvector. Preconditions: lo must have the same values as with the creation of the vector. */ void * NUMvector_copy (long elementSize, void *v, long lo, long hi); /* Function: copy (part of) a vector v, which need not have been created with NUMvector, to a new one. Queue an error message and return NULL if anything went wrong. Preconditions: if v != NULL, the values v [lo..hi] must exist. */ void NUMvector_copyElements (long elementSize, void *v, void *to, long lo, long hi); /* copy the vector elements v [lo..hi] to those of a vector 'to'. These vectors need not have been created by NUMvector. */ bool NUMvector_equal (long elementSize, void *v1, void *v2, long lo, long hi); /* return 1 if the vector elements v1 [lo..hi] are equal to the corresponding elements of the vector v2; otherwise, return 0. The vectors need not have been created by NUMvector. */ void NUMvector_append (long elementSize, void **v, long lo, long *hi); void NUMvector_insert (long elementSize, void **v, long lo, long *hi, long position); /* add one element to the vector *v. The new element is initialized to zero. On success, *v points to the new vector, and *hi is incremented by 1. On failure, *v and *hi are not changed. */ /********** Arrays with two indices (NUMarrays.c) **********/ void * NUMmatrix (long elementSize, long row1, long row2, long col1, long col2); /* Function: create a matrix [row1...row2] [col1...col2] with all values initialized to 0. Queue an error message and return NULL if anything went wrong. Preconditions: row2 >= row1; col2 >= col1; */ void NUMmatrix_free (long elementSize, void *m, long row1, long col1); /* Function: destroy a matrix m created with NUM...matrix. Preconditions: if m != NULL: row1 and row2 must have the same value as with the creation of the matrix. */ void * NUMmatrix_copy (long elementSize, void *m, long row1, long row2, long col1, long col2); /* Function: copy (part of) a matrix m, wich does not have to be created with NUMmatrix, to a new one. Queue an error message and return NULL if anything went wrong. Preconditions: if m != NULL: the values m [rowmin..rowmax] [colmin..colmax] must exist. */ void NUMmatrix_copyElements (long elementSize, void *m, void *to, long row1, long row2, long col1, long col2); /* copy the matrix elements m [r1..r2] [c1..c2] to those of a matrix 'to'. These matrices need not have been created by NUMmatrix. */ bool NUMmatrix_equal (long elementSize, void *m1, void *m2, long row1, long row2, long col1, long col2); /* return 1 if the matrix elements m1 [r1..r2] [c1..c2] are equal to the corresponding elements of the matrix m2; otherwise, return 0. The matrices need not have been created by NUM...matrix. */ long NUM_getTotalNumberOfArrays (void); /* For debugging. */ /********** Special functions (NUM.c) **********/ double NUMlnGamma (double x); double NUMbeta (double z, double w); double NUMbesselI (long n, double x); /* Precondition: n >= 0 */ double NUMbessel_i0_f (double x); double NUMbessel_i1_f (double x); double NUMbesselK (long n, double x); /* Preconditions: n >= 0 && x > 0.0 */ double NUMbessel_k0_f (double x); double NUMbessel_k1_f (double x); double NUMbesselK_f (long n, double x); double NUMsigmoid (double x); /* Correct also for large positive or negative x. */ double NUMinvSigmoid (double x); double NUMerfcc (double x); double NUMgaussP (double z); double NUMgaussQ (double z); double NUMincompleteGammaP (double a, double x); double NUMincompleteGammaQ (double a, double x); double NUMchiSquareP (double chiSquare, double degreesOfFreedom); double NUMchiSquareQ (double chiSquare, double degreesOfFreedom); double NUMcombinations (long n, long k); double NUMincompleteBeta (double a, double b, double x); // incomplete beta function Ix(a,b). Preconditions: a, b > 0; 0 <= x <= 1 double NUMbinomialP (double p, double k, double n); double NUMbinomialQ (double p, double k, double n); double NUMinvBinomialP (double p, double k, double n); double NUMinvBinomialQ (double p, double k, double n); /********** Auditory modelling (NUMear.c) **********/ double NUMhertzToBark (double hertz); double NUMbarkToHertz (double bark); double NUMphonToDifferenceLimens (double phon); double NUMdifferenceLimensToPhon (double ndli); double NUMsoundPressureToPhon (double soundPressure, double bark); double NUMhertzToMel (double hertz); double NUMmelToHertz (double mel); double NUMhertzToSemitones (double hertz); double NUMsemitonesToHertz (double semitones); double NUMerb (double f); double NUMhertzToErb (double hertz); double NUMerbToHertz (double erb); /********** Sorting (NUMsort.c) **********/ void NUMsort_d (long n, double ra []); /* Heap sort. */ void NUMsort_i (long n, int ra []); void NUMsort_l (long n, long ra []); void NUMsort_str (long n, wchar_t *a []); void NUMsort_p (long n, void *a [], int (*compare) (const void *, const void *)); double NUMquantile (long n, double a [], double factor); /* An estimate of the quantile 'factor' (between 0 and 1) of the distribution from which the set 'a [1..n]' is a sorted array of random samples. For instance, if 'factor' is 0.5, this function returns an estimate of the median of the distribution underlying the sorted set a []. If your array has not been sorted, first sort it with NUMsort (n, a). */ /********** Interpolation and optimization (NUM.c) **********/ // Special values for interpolationDepth: #define NUM_VALUE_INTERPOLATE_NEAREST 0 #define NUM_VALUE_INTERPOLATE_LINEAR 1 #define NUM_VALUE_INTERPOLATE_CUBIC 2 // Higher values than 2 yield a true sinc interpolation. Here are some examples: #define NUM_VALUE_INTERPOLATE_SINC70 70 #define NUM_VALUE_INTERPOLATE_SINC700 700 double NUM_interpolate_sinc (double y [], long nx, double x, long interpolationDepth); #define NUM_PEAK_INTERPOLATE_NONE 0 #define NUM_PEAK_INTERPOLATE_PARABOLIC 1 #define NUM_PEAK_INTERPOLATE_CUBIC 2 #define NUM_PEAK_INTERPOLATE_SINC70 3 #define NUM_PEAK_INTERPOLATE_SINC700 4 double NUMimproveExtremum (double *y, long nx, long ixmid, int interpolation, double *ixmid_real, int isMaximum); double NUMimproveMaximum (double *y, long nx, long ixmid, int interpolation, double *ixmid_real); double NUMimproveMinimum (double *y, long nx, long ixmid, int interpolation, double *ixmid_real); void NUM_viterbi ( long numberOfFrames, long maxnCandidates, long (*getNumberOfCandidates) (long iframe, void *closure), double (*getLocalCost) (long iframe, long icand, void *closure), double (*getTransitionCost) (long iframe, long icand1, long icand2, void *closure), void (*putResult) (long iframe, long place, void *closure), void *closure); void NUM_viterbi_multi ( long nframe, long ncand, int ntrack, double (*getLocalCost) (long iframe, long icand, int itrack, void *closure), double (*getTransitionCost) (long iframe, long icand1, long icand2, int itrack, void *closure), void (*putResult) (long iframe, long place, int itrack, void *closure), void *closure); /********** Metrics (NUM.c) **********/ int NUMrotationsPointInPolygon (double x0, double y0, long n, double x [], double y []); /* Returns the number of times that the closed polygon (x [1], y [1]), (x [2], y [2]),..., (x [n], y [n]), (x [1], y [1]) encloses the point (x0, y0). The result is positive if the polygon encloses the point in the anti-clockwise direction, and negative if the direction is clockwise. The result is 0 if the point is outside the polygon. If the point is on the polygon, the result is unpredictable. */ /********** Random numbers (NUMrandom.c) **********/ void NUMrandomRestart (unsigned long seed); /* Not needed for starting the random generator for the first time; that will be done on the basis of the current time. */ double NUMrandomFraction (void); double NUMrandomUniform (double lowest, double highest); long NUMrandomInteger (long lowest, long highest); double NUMrandomGauss (double mean, double standardDeviation); double NUMrandomPoisson (double mean); void NUMfbtoa (double formant, double bandwidth, double dt, double *a1, double *a2); void NUMfilterSecondOrderSection_a (double x [], long n, double a1, double a2); void NUMfilterSecondOrderSection_fb (double x [], long n, double dt, double formant, double bandwidth); double NUMftopreemphasis (double f, double dt); void NUMpreemphasize_a (double x [], long n, double preemphasis); void NUMdeemphasize_a (double x [], long n, double preemphasis); void NUMpreemphasize_f (double x [], long n, double dt, double frequency); void NUMdeemphasize_f (double x [], long n, double dt, double frequency); void NUMautoscale (double x [], long n, double scale); /* The following ANSI-C power trick generates the declarations of 156 functions. */ #define FUNCTION(type,storage) \ void NUMvector_writeText_##storage (const type *v, long lo, long hi, MelderFile file, const wchar *name); \ void NUMvector_writeBinary_##storage (const type *v, long lo, long hi, FILE *f); \ void NUMvector_writeCache_##storage (const type *v, long lo, long hi, CACHE *f); \ type * NUMvector_readText_##storage (long lo, long hi, MelderReadText text, const char *name); \ type * NUMvector_readBinary_##storage (long lo, long hi, FILE *f); \ type * NUMvector_readCache_##storage (long lo, long hi, CACHE *f); \ void NUMmatrix_writeText_##storage (type **v, long r1, long r2, long c1, long c2, MelderFile file, const wchar *name); \ void NUMmatrix_writeBinary_##storage (type **v, long r1, long r2, long c1, long c2, FILE *f); \ void NUMmatrix_writeCache_##storage (type **v, long r1, long r2, long c1, long c2, CACHE *f); \ type ** NUMmatrix_readText_##storage (long r1, long r2, long c1, long c2, MelderReadText text, const char *name); \ type ** NUMmatrix_readBinary_##storage (long r1, long r2, long c1, long c2, FILE *f); \ type ** NUMmatrix_readCache_##storage (long r1, long r2, long c1, long c2, CACHE *f); FUNCTION (signed char, i1) FUNCTION (int, i2) FUNCTION (long, i4) FUNCTION (unsigned char, u1) FUNCTION (unsigned int, u2) FUNCTION (unsigned long, u4) FUNCTION (double, r4) FUNCTION (double, r8) FUNCTION (fcomplex, c8) FUNCTION (dcomplex, c16) #undef FUNCTION /* void NUMvector_writeBinary_r8 (const double *v, long lo, long hi, FILE *f); // etc write the vector elements v [lo..hi] as machine-independent binary data to the stream f. Throw an error message if anything went wrong. The vectors need not have been created by NUM...vector. double * NUMvector_readText_r8 (long lo, long hi, MelderReadString *text, const char *name); // etc create and read a vector as text. Throw an error message if anything went wrong. Every element is supposed to be on the beginning of a line. double * NUMvector_readBinary_r8 (long lo, long hi, FILE *f); // etc create and read a vector as machine-independent binary data from the stream f. Throw an error message if anything went wrong. void NUMvector_writeText_r8 (const double *v, long lo, long hi, MelderFile file, const wchar *name); // etc write the vector elements v [lo..hi] as text to the open file, each element on its own line, preceded by "name [index]: ". Throw an error message if anything went wrong. The vectors need not have been created by NUMvector. void NUMmatrix_writeText_r8 (double **m, long r1, long r2, long c1, long c2, MelderFile file, const wchar *name); // etc write the matrix elements m [r1..r2] [c1..c2] as text to the open file. Throw an error message if anything went wrong. The matrices need not have been created by NUMmatrix. void NUMmatrix_writeBinary_r8 (double **m, long r1, long r2, long c1, long c2, FILE *f); // etc write the matrix elements m [r1..r2] [c1..c2] as machine-independent binary data to the stream f. Throw an error message if anything went wrong. The matrices need not have been created by NUMmatrix. double ** NUMmatrix_readText_r8 (long r1, long r2, long c1, long c2, MelderReadString *text, const char *name); // etc create and read a matrix as text. Throw an error message if anything went wrong. double ** NUMmatrix_readBinary_r8 (long r1, long r2, long c1, long c2, FILE *f); // etc create and read a matrix as machine-independent binary data from the stream f. Throw an error message if anything went wrong. */ typedef struct structNUMlinprog *NUMlinprog; void NUMlinprog_delete (NUMlinprog me); NUMlinprog NUMlinprog_new (bool maximize); void NUMlinprog_addVariable (NUMlinprog me, double lowerBound, double upperBound, double coeff); void NUMlinprog_addConstraint (NUMlinprog me, double lowerBound, double upperBound); void NUMlinprog_addConstraintCoefficient (NUMlinprog me, double coefficient); void NUMlinprog_run (NUMlinprog me); double NUMlinprog_getPrimalValue (NUMlinprog me, long ivar); template T* NUMvector (long from, long to) { T* result = static_cast (NUMvector (sizeof (T), from, to)); return result; } template void NUMvector_free (T* ptr, long from) { NUMvector_free (sizeof (T), ptr, from); } template T* NUMvector_copy (T* ptr, long lo, long hi) { T* result = static_cast (NUMvector_copy (sizeof (T), ptr, lo, hi)); return result; } template bool NUMvector_equal (T* v1, T* v2, long lo, long hi) { return NUMvector_equal (sizeof (T), v1, v2, lo, hi); } template void NUMvector_copyElements (T* vfrom, T* vto, long lo, long hi) { NUMvector_copyElements (sizeof (T), vfrom, vto, lo, hi); } template void NUMvector_append (T** v, long lo, long *hi) { NUMvector_append (sizeof (T), (void**) v, lo, hi); } template void NUMvector_insert (T** v, long lo, long *hi, long position) { NUMvector_insert (sizeof (T), (void**) v, lo, hi, position); } template class autoNUMvector { T* d_ptr; long d_from; public: autoNUMvector (long from, long to) : d_from (from) { d_ptr = static_cast (NUMvector (sizeof (T), from, to)); } autoNUMvector (T *ptr, long from) : d_ptr (ptr), d_from (from) { therror } autoNUMvector () : d_ptr (NULL), d_from (1) { } ~autoNUMvector () { if (d_ptr) NUMvector_free (sizeof (T), d_ptr, d_from); } T& operator[] (long i) { return d_ptr [i]; } T* peek () const { return d_ptr; } T* transfer () { T* temp = d_ptr; d_ptr = NULL; // make the pointer non-automatic again return temp; } void reset (long from, long to) { if (d_ptr) { NUMvector_free (sizeof (T), d_ptr, d_from); d_ptr = NULL; } d_from = from; d_ptr = static_cast (NUMvector (sizeof (T), from, to)); } }; template T** NUMmatrix (long row1, long row2, long col1, long col2) { T** result = static_cast (NUMmatrix (sizeof (T), row1, row2, col1, col2)); return result; } template void NUMmatrix_free (T** ptr, long row1, long col1) { NUMmatrix_free (sizeof (T), ptr, row1, col1); } template T** NUMmatrix_copy (T** ptr, long row1, long row2, long col1, long col2) { T** result = static_cast (NUMmatrix_copy (sizeof (T), ptr, row1, row2, col1, col2)); return result; } template bool NUMmatrix_equal (T** m1, T** m2, long row1, long row2, long col1, long col2) { return NUMmatrix_equal (sizeof (T), m1, m2, row1, row2, col1, col2); } template void NUMmatrix_copyElements (T** mfrom, T** mto, long row1, long row2, long col1, long col2) { NUMmatrix_copyElements (sizeof (T), mfrom, mto, row1, row2, col1, col2); } template class autoNUMmatrix { T** d_ptr; long d_row1, d_col1; public: autoNUMmatrix (long row1, long row2, long col1, long col2) : d_row1 (row1), d_col1 (col1) { d_ptr = static_cast (NUMmatrix (sizeof (T), row1, row2, col1, col2)); } autoNUMmatrix (T **ptr, long row1, long col1) : d_ptr (ptr), d_row1 (row1), d_col1 (col1) { therror } autoNUMmatrix () : d_ptr (NULL), d_row1 (0), d_col1 (0) { } ~autoNUMmatrix () { if (d_ptr) NUMmatrix_free (sizeof (T), d_ptr, d_row1, d_col1); } T*& operator[] (long row) { return d_ptr [row]; } T** peek () const { return d_ptr; } T** transfer () { T** temp = d_ptr; d_ptr = NULL; return temp; } void reset (long row1, long row2, long col1, long col2) { if (d_ptr) { NUMmatrix_free (sizeof (T), d_ptr, d_row1, d_col1); d_ptr = NULL; } d_row1 = row1; d_col1 = col1; d_ptr = static_cast (NUMmatrix (sizeof (T), row1, row2, col1, col2)); } }; template class autodatavector { T* d_ptr; long d_from, d_to; public: autodatavector (long from, long to) : d_from (from), d_to (to) { d_ptr = static_cast (NUMvector (sizeof (T), from, to)); } autodatavector (T *ptr, long from, long to) : d_ptr (ptr), d_from (from), d_to (to) { therror } autodatavector () : d_ptr (NULL), d_from (1), d_to (0) { } ~autodatavector () { if (d_ptr) { for (long i = d_from; i <= d_to; i ++) Melder_free (d_ptr [i]); NUMvector_free (sizeof (T), d_ptr, d_from); } } T& operator[] (long i) { return d_ptr [i]; } T* peek () const { return d_ptr; } T* transfer () { T* temp = d_ptr; d_ptr = NULL; // make the pointer non-automatic again return temp; } void reset (long from, long to) { if (d_ptr) { for (long i = d_from; i <= d_to; i ++) Melder_free (d_ptr [i]); NUMvector_free (sizeof (T), d_ptr, d_from); d_ptr = NULL; } d_from = from; // this assignment is safe, because d_ptr is NULL d_to = to; d_ptr = static_cast (NUMvector (sizeof (T), from, to)); } }; typedef autodatavector autostringvector; typedef autodatavector autostring8vector; /* End of file NUM.h */ #endif sources_5316/num/NUM.cpp0000644000176700017670000005247511613302421013673 0ustar paulpaul/* NUM.cpp * * Copyright (C) 1992-2008 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/03/07 GPL * pb 2003/06/19 ridders3 replaced with ridders * pb 2003/07/09 gsl * pb 2003/08/27 NUMfisherQ: underflow and iteration excess should not return NUMundefined * pb 2005/07/08 NUMpow * pb 2006/08/02 NUMinvSigmoid * pb 2007/01/27 use #defines for value interpolation * pb 2007/08/20 built a "weird value" check into NUMviterbi (bug report by Adam Jacks) * pb 2008/01/19 double * pb 2008/09/21 NUMshift * pb 2008/09/22 NUMscale * pb 2011/03/29 C++ */ #include "NUM.h" #include "NUM2.h" #include #include "melder.h" #define SIGN(x,s) ((s) < 0 ? -fabs (x) : fabs(x)) #define my me -> double NUMpow (double base, double exponent) { return base <= 0.0 ? 0.0 : pow (base, exponent); } /* GSL is more accurate than the other routines, but makes "Sound: To Intensity..." 10 times slower... */ #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf_gamma.h" #include "gsl_sf_erf.h" void NUMshift (double *x, double xfrom, double xto) { if (*x == xfrom) *x = xto; else *x += xto - xfrom; } void NUMscale (double *x, double xminfrom, double xmaxfrom, double xminto, double xmaxto) { if (*x == xminfrom) *x = xminto; else if (*x == xmaxfrom) *x = xmaxto; else *x = xminto + (xmaxto - xminto) * ((*x - xminfrom) / (xmaxfrom - xminfrom)); } void NUMinit (void) { gsl_set_error_handler_off (); } void NUMfbtoa (double formant, double bandwidth, double dt, double *a1, double *a2) { *a1 = 2 * exp (- NUMpi * bandwidth * dt) * cos (2 * NUMpi * formant * dt); *a2 = exp (- 2 * NUMpi * bandwidth * dt); } void NUMfilterSecondOrderSection_a (double x [], long n, double a1, double a2) { x [2] += a1 * x [1]; for (long i = 3; i <= n; i ++) x [i] += a1 * x [i - 1] - a2 * x [i - 2]; } void NUMfilterSecondOrderSection_fb (double x [], long n, double dt, double formant, double bandwidth) { double a1, a2; NUMfbtoa (formant, bandwidth, dt, & a1, & a2); NUMfilterSecondOrderSection_a (x, n, a1, a2); } double NUMftopreemphasis (double f, double dt) { return exp (- 2.0 * NUMpi * f * dt); } void NUMpreemphasize_a (double x [], long n, double preemphasis) { long i; for (i = n; i >= 2; i --) x [i] -= preemphasis * x [i - 1]; } void NUMdeemphasize_a (double x [], long n, double preemphasis) { long i; for (i = 2; i <= n; i ++) x [i] += preemphasis * x [i - 1]; } void NUMpreemphasize_f (double x [], long n, double dt, double frequency) { NUMpreemphasize_a (x, n, NUMftopreemphasis (frequency, dt)); } void NUMdeemphasize_f (double x [], long n, double dt, double frequency) { NUMdeemphasize_a (x, n, NUMftopreemphasis (frequency, dt)); } void NUMautoscale (double x [], long n, double scale) { long i; double maximum = 0.0; for (i = 1; i <= n; i ++) if (fabs (x [i]) > maximum) maximum = fabs (x [i]); if (maximum > 0.0) { double factor = scale / maximum; for (i = 1; i <= n; i ++) x [i] *= factor; } } double NUMlnGamma (double x) { gsl_sf_result result; int status = gsl_sf_lngamma_e (x, & result); return status == GSL_SUCCESS ? result. val : NUMundefined; } double NUMbeta (double z, double w) { if (z <= 0.0 || w <= 0.0) return NUMundefined; return exp (NUMlnGamma (z) + NUMlnGamma (w) - NUMlnGamma (z + w)); } double NUMincompleteBeta (double a, double b, double x) { gsl_sf_result result; int status = gsl_sf_beta_inc_e (a, b, x, & result); if (status != GSL_SUCCESS && status != GSL_EUNDRFLW && status != GSL_EMAXITER) { Melder_fatal ("NUMincompleteBeta status %d", status); return NUMundefined; } return result. val; } double NUMbinomialP (double p, double k, double n) { double binomialQ; if (p < 0.0 || p > 1.0 || n <= 0.0 || k < 0.0 || k > n) return NUMundefined; if (k == n) return 1.0; binomialQ = NUMincompleteBeta (k + 1, n - k, p); if (binomialQ == NUMundefined) return NUMundefined; return 1.0 - binomialQ; } double NUMbinomialQ (double p, double k, double n) { if (p < 0.0 || p > 1.0 || n <= 0.0 || k < 0.0 || k > n) return NUMundefined; if (k == 0.0) return 1.0; return NUMincompleteBeta (k, n - k + 1, p); } struct binomial { double p, k, n; }; static double binomialP (double p, void *binomial_void) { struct binomial *binomial = (struct binomial *) binomial_void; return NUMbinomialP (p, binomial -> k, binomial -> n) - binomial -> p; } static double binomialQ (double p, void *binomial_void) { struct binomial *binomial = (struct binomial *) binomial_void; return NUMbinomialQ (p, binomial -> k, binomial -> n) - binomial -> p; } double NUMinvBinomialP (double p, double k, double n) { static struct binomial binomial; if (p < 0 || p > 1 || n <= 0 || k < 0 || k > n) return NUMundefined; if (k == n) return 1.0; binomial. p = p; binomial. k = k; binomial. n = n; return NUMridders (binomialP, 0.0, 1.0, & binomial); } double NUMinvBinomialQ (double p, double k, double n) { static struct binomial binomial; if (p < 0 || p > 1 || n <= 0 || k < 0 || k > n) return NUMundefined; if (k == 0) return 0.0; binomial. p = p; binomial. k = k; binomial. n = n; return NUMridders (binomialQ, 0.0, 1.0, & binomial); } /* Modified Bessel function I0. Abramowicz & Stegun, p. 378.*/ double NUMbessel_i0_f (double x) { double t; if (x < 0.0) return NUMbessel_i0_f (- x); if (x < 3.75) { /* Formula 9.8.1. Accuracy 1.6e-7. */ t = x / 3.75; t *= t; return 1.0 + t * (3.5156229 + t * (3.0899424 + t * (1.2067492 + t * (0.2659732 + t * (0.0360768 + t * 0.0045813))))); } /* otherwise: x >= 3.75 */ /* Formula 9.8.2. Accuracy of the polynomial factor 1.9e-7. */ t = 3.75 / x; /* <= 1.0 */ return exp (x) / sqrt (x) * (0.39894228 + t * (0.01328592 + t * (0.00225319 + t * (-0.00157565 + t * (0.00916281 + t * (-0.02057706 + t * (0.02635537 + t * (-0.01647633 + t * 0.00392377)))))))); } /* Modified Bessel function I1. Abramowicz & Stegun, p. 378. */ double NUMbessel_i1_f (double x) { double t; if (x < 0.0) return - NUMbessel_i1_f (- x); if (x < 3.75) { /* Formula 9.8.3. Accuracy of the polynomial factor 8e-9. */ t = x / 3.75; t *= t; return x * (0.5 + t * (0.87890594 + t * (0.51498869 + t * (0.15084934 + t * (0.02658733 + t * (0.00301532 + t * 0.00032411)))))); } /* otherwise: x >= 3.75 */ /* Formula 9.8.4. Accuracy of the polynomial factor 2.2e-7. */ t = 3.75 / x; /* <= 1.0 */ return exp (x) / sqrt (x) * (0.39894228 + t * (-0.03988024 + t * (-0.00362018 + t * (0.00163801 + t * (-0.01031555 + t * (0.02282967 + t * (-0.02895312 + t * (0.01787654 + t * (-0.00420059))))))))); } double NUMbesselI (long n, double x) { gsl_sf_result result; int status = gsl_sf_bessel_In_e (n, x, & result); return status == GSL_SUCCESS ? result. val : NUMundefined; } /* Modified Bessel function K0. Abramowicz & Stegun, p. 379. */ double NUMbessel_k0_f (double x) { double t; if (x <= 0.0) return NUMundefined; /* Positive infinity. */ if (x <= 2.0) { /* Formula 9.8.5. Accuracy 1e-8. */ double x2 = 0.5 * x, t = x2 * x2; return - log (x2) * NUMbessel_i0_f (x) + (-0.57721566 + t * (0.42278420 + t * (0.23069756 + t * (0.03488590 + t * (0.00262698 + t * (0.00010750 + t * 0.00000740)))))); } /* otherwise: 2 < x < positive infinity */ /* Formula 9.8.6. Accuracy of the polynomial factor 1.9e-7. */ t = 2.0 / x; /* < 1.0 */ return exp (- x) / sqrt (x) * (1.25331414 + t * (-0.07832358 + t * (0.02189568 + t * (-0.01062446 + t * (0.00587872 + t * (-0.00251540 + t * 0.00053208)))))); } /* Modified Bessel function K1. Abramowicz & Stegun, p. 379. */ double NUMbessel_k1_f (double x) { double t; if (x <= 0.0) return NUMundefined; /* Positive infinity. */ if (x <= 2.0) { /* Formula 9.8.7. Accuracy of the polynomial factor 8e-9. */ double x2 = 0.5 * x, t = x2 * x2; return log (x2) * NUMbessel_i1_f (x) + (1.0 / x) * (1.0 + t * (0.15443144 + t * (-0.67278579 + t * (-0.18156897 + t * (-0.01919402 + t * (-0.00110404 + t * (-0.00004686))))))); } /* otherwise: 2 < x < positive infinity */ /* Formula 9.8.8. Accuracy of the polynomial factor 2.2e-7. */ t = 2.0 / x; /* < 1.0 */ return exp (- x) / sqrt (x) * (1.25331414 + t * (0.23498619 + t * (-0.03655620 + t * (0.01504268 + t * (-0.00780353 + t * (0.00325614 + t * (-0.00068245))))))); } double NUMbesselK_f (long n, double x) { double twoByX, besselK_min2, besselK_min1, besselK = NUMundefined; long i; Melder_assert (n >= 0 && x > 0); besselK_min2 = NUMbessel_k0_f (x); if (n == 0) return besselK_min2; besselK_min1 = NUMbessel_k1_f (x); if (n == 1) return besselK_min1; Melder_assert (n >= 2); twoByX = 2.0 / x; /* Recursion formula. */ for (i = 1; i < n; i ++) { besselK = besselK_min2 + twoByX * i * besselK_min1; besselK_min2 = besselK_min1; besselK_min1 = besselK; } Melder_assert (NUMdefined (besselK)); return besselK; } double NUMbesselK (long n, double x) { gsl_sf_result result; int status = gsl_sf_bessel_Kn_e (n, x, & result); return status == GSL_SUCCESS ? result. val : NUMundefined; } double NUMsigmoid (double x) { return x > 0.0 ? 1 / (1 + exp (- x)) : 1 - 1 / (1 + exp (x)); } double NUMinvSigmoid (double x) { return x <= 0.0 || x >= 1.0 ? NUMundefined : log (x / (1.0 - x)); } double NUMerfcc (double x) { gsl_sf_result result; int status = gsl_sf_erfc_e (x, & result); return status == GSL_SUCCESS ? result. val : NUMundefined; } double NUMgaussP (double z) { return 1 - 0.5 * NUMerfcc (NUMsqrt1_2 * z); } double NUMgaussQ (double z) { return 0.5 * NUMerfcc (NUMsqrt1_2 * z); } double NUMincompleteGammaP (double a, double x) { gsl_sf_result result; int status = gsl_sf_gamma_inc_P_e (a, x, & result); return status == GSL_SUCCESS ? result. val : NUMundefined; } double NUMincompleteGammaQ (double a, double x) { gsl_sf_result result; int status = gsl_sf_gamma_inc_Q_e (a, x, & result); return status == GSL_SUCCESS ? result. val : NUMundefined; } double NUMchiSquareP (double chiSquare, double degreesOfFreedom) { if (chiSquare < 0 || degreesOfFreedom <= 0) return NUMundefined; return NUMincompleteGammaP (0.5 * degreesOfFreedom, 0.5 * chiSquare); } double NUMchiSquareQ (double chiSquare, double degreesOfFreedom) { if (chiSquare < 0 || degreesOfFreedom <= 0) return NUMundefined; return NUMincompleteGammaQ (0.5 * degreesOfFreedom, 0.5 * chiSquare); } double NUMcombinations (long n, long k) { double result = 1.0; long i; if (k > n / 2) k = n - k; for (i = 1; i <= k; i ++) result *= n - i + 1; for (i = 2; i <= k; i ++) result /= i; return result; } #define NUM_interpolate_simple_cases \ if (nx < 1) return NUMundefined; \ if (x > nx) return y [nx]; \ if (x < 1) return y [1]; \ if (x == midleft) return y [midleft]; \ /* 1 < x < nx && x not integer: interpolate. */ \ if (maxDepth > midright - 1) maxDepth = midright - 1; \ if (maxDepth > nx - midleft) maxDepth = nx - midleft; \ if (maxDepth <= NUM_VALUE_INTERPOLATE_NEAREST) return y [(long) floor (x + 0.5)]; \ if (maxDepth == NUM_VALUE_INTERPOLATE_LINEAR) return y [midleft] + (x - midleft) * (y [midright] - y [midleft]); \ if (maxDepth == NUM_VALUE_INTERPOLATE_CUBIC) { \ double yl = y [midleft], yr = y [midright]; \ double dyl = 0.5 * (yr - y [midleft - 1]), dyr = 0.5 * (y [midright + 1] - yl); \ double fil = x - midleft, fir = midright - x; \ return yl * fir + yr * fil - fil * fir * (0.5 * (dyr - dyl) + (fil - 0.5) * (dyl + dyr - 2 * (yr - yl))); \ } #if defined (__POWERPC__) double NUM_interpolate_sinc (double y [], long nx, double x, long maxDepth) { long ix, midleft = floor (x), midright = midleft + 1, left, right; double result = 0.0, a, halfsina, aa, daa, cosaa, sinaa, cosdaa, sindaa; NUM_interpolate_simple_cases left = midright - maxDepth, right = midleft + maxDepth; a = NUMpi * (x - midleft); halfsina = 0.5 * sin (a); aa = a / (x - left + 1); cosaa = cos (aa); sinaa = sin (aa); daa = NUMpi / (x - left + 1); cosdaa = cos (daa); sindaa = sin (daa); for (ix = midleft; ix >= left; ix --) { double d = halfsina / a * (1.0 + cosaa), help; result += y [ix] * d; a += NUMpi; help = cosaa * cosdaa - sinaa * sindaa; sinaa = cosaa * sindaa + sinaa * cosdaa; cosaa = help; halfsina = - halfsina; } a = NUMpi * (midright - x); halfsina = 0.5 * sin (a); aa = a / (right - x + 1); cosaa = cos (aa); sinaa = sin (aa); daa = NUMpi / (right - x + 1); cosdaa = cos (daa); sindaa = sin (daa); for (ix = midright; ix <= right; ix ++) { double d = halfsina / a * (1.0 + cosaa), help; result += y [ix] * d; a += NUMpi; help = cosaa * cosdaa - sinaa * sindaa; sinaa = cosaa * sindaa + sinaa * cosdaa; cosaa = help; halfsina = - halfsina; } return result; } #else double NUM_interpolate_sinc (double y [], long nx, double x, long maxDepth) { long ix, midleft = floor (x), midright = midleft + 1, left, right; double result = 0.0, a, halfsina, aa, daa; NUM_interpolate_simple_cases left = midright - maxDepth, right = midleft + maxDepth; a = NUMpi * (x - midleft); halfsina = 0.5 * sin (a); aa = a / (x - left + 1); daa = NUMpi / (x - left + 1); for (ix = midleft; ix >= left; ix --) { double d = halfsina / a * (1.0 + cos (aa)); result += y [ix] * d; a += NUMpi; aa += daa; halfsina = - halfsina; } a = NUMpi * (midright - x); halfsina = 0.5 * sin (a); aa = a / (right - x + 1); daa = NUMpi / (right - x + 1); \ for (ix = midright; ix <= right; ix ++) { double d = halfsina / a * (1.0 + cos (aa)); result += y [ix] * d; a += NUMpi; aa += daa; halfsina = - halfsina; } return result; } #endif /********** Improving extrema **********/ #pragma mark Improving extrema struct improve_params { int depth; double *y; long ixmax; int isMaximum; }; static double improve_evaluate (double x, void *closure) { struct improve_params *me = (struct improve_params *) closure; double y = NUM_interpolate_sinc (my y, my ixmax, x, my depth); return my isMaximum ? - y : y; } double NUMimproveExtremum (double *y, long nx, long ixmid, int interpolation, double *ixmid_real, int isMaximum) { struct improve_params params; double result; if (ixmid <= 1) { *ixmid_real = 1; return y [1]; } if (ixmid >= nx) { *ixmid_real = nx; return y [nx]; } if (interpolation <= NUM_PEAK_INTERPOLATE_NONE) { *ixmid_real = ixmid; return y [ixmid]; } if (interpolation == NUM_PEAK_INTERPOLATE_PARABOLIC) { double dy = 0.5 * (y [ixmid + 1] - y [ixmid - 1]); double d2y = 2 * y [ixmid] - y [ixmid - 1] - y [ixmid + 1]; *ixmid_real = ixmid + dy / d2y; return y [ixmid] + 0.5 * dy * dy / d2y; } /* Sinc interpolation. */ params. y = y; params. depth = interpolation == NUM_PEAK_INTERPOLATE_SINC70 ? 70 : 700; params. ixmax = nx; params. isMaximum = isMaximum; /*return isMaximum ? - NUM_minimize (ixmid - 1, ixmid, ixmid + 1, improve_evaluate, & params, 1e-10, 1e-11, ixmid_real) : NUM_minimize (ixmid - 1, ixmid, ixmid + 1, improve_evaluate, & params, 1e-10, 1e-11, ixmid_real);*/ *ixmid_real = NUMminimize_brent (improve_evaluate, ixmid - 1, ixmid + 1, & params, 1e-10, & result); return isMaximum ? - result : result; } double NUMimproveMaximum (double *y, long nx, long ixmid, int interpolation, double *ixmid_real) { return NUMimproveExtremum (y, nx, ixmid, interpolation, ixmid_real, 1); } double NUMimproveMinimum (double *y, long nx, long ixmid, int interpolation, double *ixmid_real) { return NUMimproveExtremum (y, nx, ixmid, interpolation, ixmid_real, 0); } /********** Viterbi **********/ void NUM_viterbi ( long numberOfFrames, long maxnCandidates, long (*getNumberOfCandidates) (long iframe, void *closure), double (*getLocalCost) (long iframe, long icand, void *closure), double (*getTransitionCost) (long iframe, long icand1, long icand2, void *closure), void (*putResult) (long iframe, long place, void *closure), void *closure) { autoNUMmatrix delta (1, numberOfFrames, 1, maxnCandidates); autoNUMmatrix psi (1, numberOfFrames, 1, maxnCandidates); autoNUMvector numberOfCandidates (1, numberOfFrames); for (long iframe = 1; iframe <= numberOfFrames; iframe ++) { numberOfCandidates [iframe] = getNumberOfCandidates (iframe, closure); for (long icand = 1; icand <= numberOfCandidates [iframe]; icand ++) delta [iframe] [icand] = - getLocalCost (iframe, icand, closure); } for (long iframe = 2; iframe <= numberOfFrames; iframe ++) { for (long icand2 = 1; icand2 <= numberOfCandidates [iframe]; icand2 ++) { double maximum = -1e300; double place = 0; for (long icand1 = 1; icand1 <= numberOfCandidates [iframe - 1]; icand1 ++) { double value = delta [iframe - 1] [icand1] + delta [iframe] [icand2] - getTransitionCost (iframe, icand1, icand2, closure); if (value > maximum) { maximum = value; place = icand1; } } if (place == 0) Melder_throw ("Viterbi algorithm cannot compute a track because of weird values."); delta [iframe] [icand2] = maximum; psi [iframe] [icand2] = place; } } /* * Find the end of the most probable path. */ long place; double maximum = delta [numberOfFrames] [place = 1]; for (long icand = 2; icand <= numberOfCandidates [numberOfFrames]; icand ++) if (delta [numberOfFrames] [icand] > maximum) maximum = delta [numberOfFrames] [place = icand]; /* * Backtrack. */ for (long iframe = numberOfFrames; iframe >= 1; iframe --) { putResult (iframe, place, closure); place = psi [iframe] [place]; } } /******************/ struct parm2 { int ntrack; long ncomb; long **indices; double (*getLocalCost) (long iframe, long icand, int itrack, void *closure); double (*getTransitionCost) (long iframe, long icand1, long icand2, int itrack, void *closure); void (*putResult) (long iframe, long place, int itrack, void *closure); void *closure; }; static long getNumberOfCandidates_n (long iframe, void *closure) { struct parm2 *me = (struct parm2 *) closure; (void) iframe; return my ncomb; } static double getLocalCost_n (long iframe, long jcand, void *closure) { struct parm2 *me = (struct parm2 *) closure; double localCost = 0.0; for (int itrack = 1; itrack <= my ntrack; itrack ++) localCost += my getLocalCost (iframe, my indices [jcand] [itrack], itrack, my closure); return localCost; } static double getTransitionCost_n (long iframe, long jcand1, long jcand2, void *closure) { struct parm2 *me = (struct parm2 *) closure; double transitionCost = 0.0; for (int itrack = 1; itrack <= my ntrack; itrack ++) transitionCost += my getTransitionCost (iframe, my indices [jcand1] [itrack], my indices [jcand2] [itrack], itrack, my closure); return transitionCost; } static void putResult_n (long iframe, long jplace, void *closure) { struct parm2 *me = (struct parm2 *) closure; for (int itrack = 1; itrack <= my ntrack; itrack ++) my putResult (iframe, my indices [jplace] [itrack], itrack, my closure); } void NUM_viterbi_multi ( long nframe, long ncand, int ntrack, double (*getLocalCost) (long iframe, long icand, int itrack, void *closure), double (*getTransitionCost) (long iframe, long icand1, long icand2, int itrack, void *closure), void (*putResult) (long iframe, long place, int itrack, void *closure), void *closure) { struct parm2 parm; parm.indices = NULL; if (ntrack > ncand) Melder_throw ("(NUM_viterbi_multi:) " "Number of tracks (", ntrack, ") should not exceed number of candidates (", ncand, ")."); double ncomb = NUMcombinations (ncand, ntrack); if (ncomb > 10000000) Melder_throw ("(NUM_viterbi_multi:) " "Unrealistically high number of combinations (", ncomb, ")."); parm. ntrack = ntrack; parm. ncomb = ncomb; /* * For ncand == 5 and ntrack == 3, parm.indices is going to contain: * 1 2 3 * 1 2 4 * 1 2 5 * 1 3 4 * 1 3 5 * 1 4 5 * 2 3 4 * 2 3 5 * 2 4 5 * 3 4 5 */ autoNUMmatrix indices (1, parm. ncomb, 1, ntrack); parm.indices = indices.peek(); autoNUMvector icand (1, ntrack); for (int itrack = 1; itrack <= ntrack; itrack ++) icand [itrack] = itrack; // start out with "1 2 3" long jcomb = 0; for (;;) { jcomb ++; for (int itrack = 1; itrack <= ntrack; itrack ++) parm. indices [jcomb] [itrack] = icand [itrack]; int itrack = ntrack; for (; itrack >= 1; itrack --) { if (++ icand [itrack] <= ncand - (ntrack - itrack)) { for (int jtrack = itrack + 1; jtrack <= ntrack; jtrack ++) icand [jtrack] = icand [itrack] + jtrack - itrack; break; } } if (itrack == 0) break; } Melder_assert (jcomb == ncomb); parm. getLocalCost = getLocalCost; parm. getTransitionCost = getTransitionCost; parm. putResult = putResult; parm. closure = closure; NUM_viterbi (nframe, ncomb, getNumberOfCandidates_n, getLocalCost_n, getTransitionCost_n, putResult_n, & parm); therror } int NUMrotationsPointInPolygon (double x0, double y0, long n, double x [], double y []) { long nup = 0, i; int upold = y [n] > y0, upnew; for (i = 1; i <= n; i ++) if ((upnew = y [i] > y0) != upold) { long j = i == 1 ? n : i - 1; if (x0 < x [i] + (x [j] - x [i]) * (y0 - y [i]) / (y [j] - y [i])) { if (upnew) nup ++; else nup --; } upold = upnew; } return nup; } /* End of file NUM.cpp */ sources_5316/dwtest/0000755000176700017670000000000011756343546013253 5ustar paulpaulsources_5316/dwtest/test_FilterBank.praat0000644000176700017670000000436111631673132017355 0ustar paulpaul# test_Filterbank.praat # djmw 20110907 eps = 1.6e-16 printline test_FilterBank starttime = 0 endtime = 1 fs = 44100 s = Create Sound from formula... sineWithNoise 1 starttime endtime fs 1/2 * sin(2*pi*377*x) + randomGauss(0,0.1) call test_FormantFilter s call test_BarkFilter s call test_MelFilter s select s Remove printline test_FilterBank OK procedure test_FormantFilter .s printline 'tab$' test FormantFilter bf_first = 100 fdistance = 50 timestep = 0.005 select .s .ff = To FormantFilter... 0.015 timestep bf_first fdistance 0 1.1 75 600 call queries .ff call modifies .ff call commons .ff select .ff Remove endproc procedure test_BarkFilter .s printline 'tab$' test BarkFilter select .s bf_first = 1 fdistance = 1 .bf = To BarkFilter... 0.015 timestep 1 1 0 call queries .bf call modifies .bf call commons .bf select .bf Remove endproc procedure test_MelFilter .s printline 'tab$' test MelFilter select .s bf_first = 100 fdistance = 100 .mf = To MelFilter... 0.015 timestep bf_first fdistance 0 call queries .mf call modifies .mf call commons .mf select .mf .mfcc = To MFCC... 12 Remove select .mf Remove endproc procedure commons .bf select .bf .in = To Intensity Remove select .bf .mat = To Matrix Remove endproc procedure queries .fb select .fb .starttime = Get start time .endtime = Get end time .dur = Get total duration assert abs( .dur -(.endtime-.starttime)) <= eps assert .starttime = starttime assert .endtime = endtime .timestep = Get time step assert .timestep = timestep; '.timestep' 'timestep' .bf_first = Get lowest frequency assert .bf_first >= 0; '.bf_first' 'bf_first' .bf_last = Get highest frequency assert .bf_last <= fs/2 .nf = Get number of frequencies assert .nf >= 1 .fdistance = Get frequency distance assert .fdistance=fdistance; '.fdistance' 'fdistance' .f_from_row[1] = Get frequency from row... 1 for .i from 2 to .nf .f_from_row[.i] = Get frequency from row... .i .fi = .f_from_row[.i] .fim1 = .f_from_row[.i-1] assert .f_from_row[.i] >.f_from_row[.i-1]; '.fi' >.'fim1' endfor for .i to .nf .time = randomUniform (.starttime, endtime) .vali = Get value in cell... .time .i endfor endproc procedure modifies .fb select .fb Equalize intensities... 80 endproc sources_5316/dwtest/KlattGrid_test.praat0000644000176700017670000002412211173361037017215 0ustar paulpaul# KlattGrid_test.praat # djmw 20081208, 20090420 printline =========== KlattGrid test start call test_get_add_remove_extract_replace_old_interface call test_get_add_remove_replace printline =========== KlattGrid test end procedure test_get_add_remove_replace numberOfOralFormants = 6 numberOfNasalFormants = 1 numberOfTrachealFormants = 1 numberOfFricationFormants = 5 numberOfNasalAntiFormants = 1 numberOfTrachealAntiFormants = 1 numberOfDeltaFormants = 1 tmin = 0 tmax = 1 kg = Create KlattGrid... kg tmin tmax numberOfOralFormants numberOfNasalFormants numberOfNasalAntiFormants ... numberOfFricationFormants numberOfTrachealFormants numberOfTrachealAntiFormants numberOfDeltaFormants printline =========== KlattGrid test_get_add_remove_extract_replace start for .itime to 20 call setget_1 "pitch" 130 call setget_1 "voicing amplitude" 90 call setget_1 "flutter" 0.5 call setget_1 "power1" 2 call setget_1 "power2" 3 call setget_1 "open phase" 0.5 call setget_1 "collision phase" 0.035 call setget_1 "double pulsing" 0.4 call setget_1 "spectral tilt" 20 call setget_1 "aspiration amplitude" 90 call setget_1 "breathiness amplitude" 90 call setget_1 "frication bypass" 20 call setget_1 "frication amplitude" 50 call setget_formants Oral call setget_formants Nasal call setget_formants Tracheal call setget_formants Delta call setget_formants Frication call setget_antiformants Nasal call setget_antiformants Tracheal endfor call test_deltaFormants select kg Remove printline =========== KlattGrid test_get_add_remove_extract_replace succesful endproc procedure test_get_add_remove_extract_replace_old_interface numberOfOralFormants = 6 numberOfNormalFormants = numberOfOralFormants numberOfNasalFormants = 1 numberOfTrachealFormants = 1 numberOfFricationFormants = 5 numberOfNasalAntiFormants = 1 numberOfTrachealAntiFormants = 1 numberOfDeltaFormants = 1 tmin = 0 tmax = 1 printline =========== KlattGrid test_get_add_remove_extract_replace_old_interface start kg = Create KlattGrid... kg tmin tmax numberOfOralFormants numberOfNasalFormants numberOfNasalAntiFormants ... numberOfFricationFormants numberOfTrachealFormants numberOfTrachealAntiFormants numberOfDeltaFormants for .itime to 20 call setget_1 "pitch" 130 call setget_1 "voicing amplitude" 90 call setget_1 "flutter" 0.5 call setget_1 "power1" 2 call setget_1 "power2" 3 call setget_1 "open phase" 0.5 call setget_1 "collision phase" 0.035 call setget_1 "double pulsing" 0.4 call setget_1 "spectral tilt" 20 call setget_1 "aspiration amplitude" 90 call setget_1 "breathiness amplitude" 90 call setget_1 "frication bypass" 20 call setget_1 "frication amplitude" 50 call setget_formants_old Normal call setget_formants_old Nasal call setget_formants_old Tracheal call setget_formants_old Frication call setget_antiformants_old Nasal call setget_antiformants_old Tracheal call setget_deltaformants endfor call test_deltaFormants_old select kg Remove printline =========== KlattGrid test_get_add_remove_extract_replace_old_interface succesful endproc procedure setget_1 .var$ .value select kg .time = randomUniform (tmin,tmax) Add '.var$' point... .time .value .val = Get '.var$' at time... .time .vt = Extract '.var$' tier select kg Remove '.var$' points between... tmin tmax .val1 = Get '.var$' at time... .time assert .val1 = undefined; Add '.var$' at time... '.time' '.value' plus .vt Replace '.var$' tier select kg .val1 = Get '.var$' at time... .time assert .val1 =.val; Add '.var$' at time... '.time' '.value' select .vt Remove endproc procedure setget_2p .var$ .ifor .time .value select kg Add delta '.var$' point... .ifor .time .value .val = Get delta '.var$' at time... .ifor .time assert .val = .value; Add delta '.var$' point... .ifor .time .value .fg = Extract delta formant grid select kg Remove delta '.var$' points between... .ifor tmin tmax .val1 = Get delta '.var$' at time... .ifor .time assert .val1 = undefined; Get delta '.var$' at time... .ifor .time plus .fg Replace delta formant grid select kg .val1 = Get delta '.var$' at time... .ifor .time assert .val1 =.val; Get delta '.var$' at time... .ifor .time select .fg Remove endproc procedure setget_3_old .var$ .choice$ .ifor .time .value select kg Add '.var$' point... "'.choice$'" .ifor .time .value .val = Get '.var$' at time... "'.choice$'" .ifor .time assert .val = .value; Add '.var$' point... "'.choice$'" .ifor .time .value .fg = Extract formant grid... '.choice$' select kg Remove '.var$' points between... "'.choice$'" .ifor tmin tmax .val1 = Get '.var$' at time... "'.choice$'" .ifor .time assert .val1 = undefined; Get '.var$' at time... "'.choice$'" .ifor .time plus .fg Replace formant grid... '.choice$' select kg .val1 = Get '.var$' at time... "'.choice$'" .ifor .time assert .val1 =.val; Get '.var$' at time... "'.choice$'" .ifor .time select .fg Remove endproc procedure setget_3a_old .var$ .choice$ .ifor .time .value select kg Add '.var$' point... "'.choice$'" .ifor .time .value .val = Get '.var$' at time... "'.choice$'" .ifor .time assert .val = .value; Add '.var$' point... "'.choice$'" .ifor .time .value .tier = Extract amplitude tier... "'.choice$'" .ifor select kg Remove '.var$' points between... "'.choice$'" .ifor tmin tmax .val1 = Get '.var$' at time... "'.choice$'" .ifor .time assert .val1 = undefined; Get '.var$' at time... "'.choice$'" .ifor .time plus .tier Replace amplitude tier... "'.choice$'" .ifor select kg .val1 = Get '.var$' at time... "'.choice$'" .ifor .time assert .val1 =.val; Get '.var$' at time... "'.choice$'" .ifor .time select .tier Remove endproc procedure setget_formants_old .type$ for .i to numberOf'.type$'Formants .time = randomUniform (tmin, tmax) .f = (2*.i-1) * randomUniform (450, 550) .b = .f /10 .a = randomUniform (70, 90) call setget_3_old "formant" "'.type$' formant" .i .time .f call setget_3_old "bandwidth" "'.type$' formant" .i .time .b call setget_3a_old "amplitude" "'.type$' formant" .i .time .a endfor select kg Formula (frequencies)... "'.type$' formant" self + 100 Formula (bandwidths)... "'.type$' formant" self * 2 endproc procedure setget_3 .type$ .formant$ .var$ .ifor .time .value select kg what$ = "'.type$' '.formant$' '.var$'" Remove 'what$' points... .ifor tmin tmax Add 'what$' point... .ifor .time .value .val = Get 'what$' at time... .ifor .time assert .val = .value; '.val' '.value' (Get 'what$' at time... '.ifor' '.time') .fg = Extract '.type$' '.formant$' grid select kg Remove 'what$' points... .ifor tmin tmax .val1 = Get 'what$' at time... .ifor .time assert .val1 = undefined; '.val1' (Get 'what$' at time... '.ifor' '.time') plus .fg Replace '.type$' '.formant$' grid select kg .val1 = Get 'what$' at time... .ifor .time if .var$ = "amplitude" .val = undefined endif assert .val1 =.val; '.val1' '.val' (Get 'what$' at time... '.ifor' '.time') select .fg Remove endproc procedure setget_formants .tYPE$ .type$ = replace_regex$ (.tYPE$, "(^.)","\L\1", 1) for .i to numberOf'.tYPE$'Formants .time = randomUniform (tmin, tmax) .f = (2*.i-1) * randomUniform (450, 550) .b = .f /10 .a = randomUniform (70, 90) call setget_3 '.type$' "formant" "frequency" .i .time .f call setget_3 '.type$' "formant" "bandwidth" .i .time .b if .tYPE$ <> "Delta" call setget_3 '.type$' "formant" "amplitude" .i .time .a endif endfor select kg Formula ('.type$' formant frequencies)... self + 100 Formula ('.type$' formant bandwidths)... self * 2 endproc procedure setget_antiformants .tYPE$ .type$ = replace_regex$ (.tYPE$, "(^.)","\L\1", 1) for .i to numberOf'.tYPE$'AntiFormants .time = randomUniform (tmin, tmax) .f = (2*.i-1) * randomUniform (450, 550) .b = .f /10 call setget_3 '.type$' "antiformant" "frequency" .i .time .f call setget_3 '.type$' "antiformant" "bandwidth" .i .time .b endfor select kg Formula ('.type$' antiformant frequencies)... self + 100 Formula ('.type$' antiformant bandwidths)... self * 2 endproc procedure setget_deltaformants for .i to numberOfDeltaFormants .time = randomUniform (tmin, tmax) .f = randomUniform (50, 60) .b = .f /10 call setget_2p "formant" .i .time .f call setget_2p "bandwidth" .i .time .b endfor endproc procedure setget_antiformants_old .type$ for .i to numberOf'.type$'AntiFormants .time = randomUniform (tmin, tmax) .f = (2*.i-1) * randomUniform (450, 550) .b = .f /10 call setget_3_old "formant" "'.type$' antiformant" .i .time .f call setget_3_old "bandwidth" "'.type$' antiformant" .i .time .b endfor endproc procedure test_deltaFormants_old .kg = Create KlattGrid... kg 0 1 6 1 1 6 1 1 1 Add pitch point... 0.5 100 Add voicing amplitude point... 0.5 90 Add bandwidth point... "Normal formant" 1 0.5 50 Add delta formant point... 1 0.5 500 Remove formant points between... "Normal formant" 1 0 2 Add formant point... "Normal formant" 1 0 400 Add formant point... "Normal formant" 1 1 600 Add formant point... "Normal formant" 1 0.003553 400 Add formant point... "Normal formant" 1 0.002 300 Add formant point... "Normal formant" 1 0.0112 430 .sound = To Sound Remove select .kg Extract formant grid (open phases)... 0.1 endproc procedure test_deltaFormants .kg = Create KlattGrid... kg 0 1 6 1 1 6 1 1 1 Add pitch point... 0.5 100 Add voicing amplitude point... 0.5 90 Add oral formant bandwidth point... 1 0.5 50 Add delta formant frequency point... 1 0.5 500 Remove oral formant frequency points... 1 0 2 Add oral formant frequency point... 1 0 400 Add oral formant frequency point... 1 1 600 Add oral formant frequency point... 1 0.003553 400 Add oral formant frequency point... 1 0.002 300 Add oral formant frequency point... 1 0.0112 430 .sound = To Sound Remove select .kg Extract oral formant grid (open phases)... 0.1 endproc sources_5316/dwtest/test_henzeZirklerMultivariateNormalityTest.praat0000644000176700017670000000164111567466673025156 0ustar paulpaul# henzeZirklerMultivariateNormalityTest.praat # djmw 20090707,20110526 printline test_henzeZirklerMultivariateNormalityTest ir = Create iris data set ir50 = Extract row ranges... 1:50 report$ = Report multivariate normality... 0 tol = 1e-10 stat = extractNumber (report$, "statistic:") assert abs(stat - 0.958366538697967)= label$ ; i='i' 'lab$' > 'label$' label$ = lab$ endfor select pid Invert pidi = selected ("Permutation") plus testtabp Permute rows testtabpi = selected ("TableOfReal") Formula... self - TableOfReal_test[] stdev = Get column stdev (index)... 1 assert stdev = 0 select pid plus testtabp plus pidi plus testtabpi Remove print . endfor printline o.k. select testtab Remove sources_5316/dwtest/test_MDS.praat0000644000176700017670000000313511564167407015765 0ustar paulpaul# test_MDS.praat printline test MDS dr = Create letter R example... 0 c[1] = To Configuration (monotone mds)... 2 "Primary approach" 1e-05 50 1 select dr c[2] = To Configuration (i-spline mds)... 2 1 1 1e-05 50 1 select dr c[3] = To Configuration (interval mds)... 2 1e-05 50 1 select dr c[4] = To Configuration (ratio mds)... 2 1e-05 50 1 select dr c[5] = To Configuration (absolute mds)... 2 1e-05 50 1 select dr c[6] = To Configuration (kruskal)... 2 2 "Primary approach" Formula1 1e-05 50 1 printline ... comparing configurations for i from 2 to 6 select c[1] plus c[i] p1 = To Procrustes... no plus c[i] ct[i] = To Configuration plus c[1] p2 = To Procrustes... no call check_if_identity_transform p2 plus p1 Remove endfor ct[1] = c[1] printline .... INDSCAL select c[1] for i from 2 to 6 plus ct[i] endfor To Distance for i to 6 dist[i] = selected ("Distance", i) endfor To Configuration (indscal)... 2 yes 1e-5 100 1 ic = selected ("Configuration") is = selected ("Salience") select c[1] plus ic p3 = To Procrustes... no plus ic cp3 = To Configuration plus c[1] p4 = To Procrustes... no call check_if_identity_transform p4 select dr plus ic plus is plus p3 plus p4 plus cp3 for i to 6 plus c[i] plus ct[i] plus dist[i] endfor Remove printline test MDS ok procedure check_if_identity_transform .p select .p .scale = Get scale assert .scale > 1 - 1e-4 for .j to 2 tj = Get translation element... .j assert abs(tj) < 1e-6 for .k to 2 tjk = Get transformation element... .j .k if .j = .k assert tjk > 1 - 1e-4 else assert abs(tjk) < 1e-6 endif endfor endfor endproc sources_5316/dwtest/test_KlattGrid.praat0000644000176700017670000001032111601175507017212 0ustar paulpaul# test_KlattGrid.praat printline test_KlattGrid t = Create Table with column names... t 25 tier min max nf Set string value... 1 tier pitch Set string value... 2 tier voicing amplitude Set string value... 3 tier flutter Set string value... 4 tier power1 Set string value... 5 tier power2 Set string value... 6 tier open phase Set string value... 7 tier collision phase Set string value... 8 tier double pulsing Set string value... 9 tier spectral tilt Set string value... 10 tier aspiration amplitude Set string value... 11 tier breathiness amplitude Set numeric value... 1 min 80 Set numeric value... 2 min 0 Set numeric value... 3 min 0 Set numeric value... 4 min 1 Set numeric value... 5 min 2 Set numeric value... 6 min 0 Set numeric value... 7 min 0 Set numeric value... 8 min 0 Set numeric value... 9 min 0 Set numeric value... 10 min 0 Set numeric value... 11 min 0 Set numeric value... 1 max 400 Set numeric value... 2 max 93 Set numeric value... 3 max 1 Set numeric value... 4 max 4 Set numeric value... 5 max 5 Set numeric value... 6 max 0.9 Set numeric value... 7 max 0.05 Set numeric value... 8 max 1 Set numeric value... 9 max 40 Set numeric value... 10 max 90 Set numeric value... 11 max 90 Set string value... 12 tier oral formant frequency Set string value... 13 tier nasal formant frequency Set string value... 14 tier nasal antiformant frequency Set string value... 15 tier tracheal formant frequency Set string value... 16 tier tracheal antiformant frequency Set string value... 17 tier delta formant frequency Set string value... 18 tier frication formant frequency Set numeric value... 12 min 100 Set numeric value... 13 min 100 Set numeric value... 14 min 0 Set numeric value... 15 min 200 Set numeric value... 16 min 100 Set numeric value... 17 min 0 Set numeric value... 18 min 100 Set numeric value... 12 max 6000 Set numeric value... 13 max 6000 Set numeric value... 14 max 6000 Set numeric value... 15 max 2000 Set numeric value... 16 max 1000 Set numeric value... 17 max 1000 Set numeric value... 18 max 8000 Set string value... 19 tier oral formant bandwidth Set string value... 20 tier nasal formant bandwidth Set string value... 21 tier nasal antiformant bandwidth Set string value... 22 tier tracheal formant bandwidth Set string value... 23 tier tracheal antiformant bandwidth Set string value... 24 tier delta formant bandwidth Set string value... 25 tier frication formant bandwidth nof = 8 nnf = 3 nnaf = 4 ntf = 4 ntaf = 2 ndf = 2 nff = 6 Set numeric value... 12 nf nof Set numeric value... 13 nf nnf Set numeric value... 14 nf nnaf Set numeric value... 15 nf ntf Set numeric value... 16 nf ntaf Set numeric value... 17 nf ndf Set numeric value... 18 nf nff for i from 19 to 25 bwmin = Object_'t'[i-7, "min"] bwmax = Object_'t'[i-7, "max"] nf = Object_'t'[i-7, "nf"] Set numeric value... i min bwmin/10 Set numeric value... i max bwmax/10 Set numeric value... i nf nf endfor nPhonationTiers = 11 tmin = 0 tmax = 1 kg = Create KlattGrid... kg tmin tmax nof nnf nnaf nff ntf ntaf ndf ntimes = 5 dt = 0.0001 for i to nPhonationTiers select kg tier$ = Object_'t'$[i,"tier"] vmin = Object_'t'[i,"min"] vmax = Object_'t'[i,"max"] for itime to ntimes time[itime] = randomUniform (tmin, tmax) val[itime] = randomUniform (vmin, vmax) Add 'tier$' point... time[itime] val[itime] endfor for itime to ntimes val = Get 'tier$' at time... time[itime] assert val = val[itime] endfor Remove 'tier$' points... tmin tmax tier = Extract 'tier$' tier Remove printline ... 'tier$' endfor for i from nPhonationTiers+1 to 25 select kg tier$ = Object_'t'$ [i, "tier"] vmin = Object_'t' [i, "min"] vmax = Object_'t' [i, "max"] nf = Object_'t' [i, "nf"] print ... 'tier$' for ifor from 1 to nf select kg for itime to ntimes time[itime] = randomUniform (tmin, tmax) val[itime] = randomUniform (vmin, vmax) Add 'tier$' point... ifor time[itime] val[itime] endfor for itime to ntimes val = Get 'tier$' at time... ifor time[itime] assert val = val[itime] endfor Remove 'tier$' points... ifor tmin tmax grid$ = replace$ (tier$, " frequency", "", 1) grid$ = replace$ (grid$, " bandwidth", "", 1) grid = Extract 'grid$' grid print 'ifor' Remove endfor print 'newline$' endfor printline test_KlattGrid OKsources_5316/dwtest/test_Polygon_simplify.Matrix0000644000176700017670000000754411577443226021052 0ustar paulpaulFile type = "ooTextFile" Object class = "Matrix 2" 0.5 100.5 100 1 1 0.5 2.5 2 1 1 0.48494076548132437 0.3321202587919751 0.30575672507518403 0.5305516746271928 0.2599470570028398 0.5749720815675041 0.6568742600238754 0.5758106616051097 0.46187961356672635 0.6815312283403661 0.616230423407458 0.6321887679830146 0.6119354592509548 0.619551772114672 0.6747820467027944 0.6053507104944407 0.6744852219347941 0.6521442623629092 0.646942498647082 0.6005431430760269 0.7444762685436419 0.602694678796173 0.7537035926627527 0.7584031538763572 0.6433457606714617 0.6348722288713303 0.7212837441824056 0.7748849145111145 0.6139716959288507 0.7860608322666525 0.2754973056106338 0.2540510068018146 0.44523987620541766 0.07841666575037853 0.4476892768753488 0.11494484316267783 0.6951687272378206 0.583362092525197 0.06631533522833533 0.004101374898366705 0.20261300439857216 0.037034547300827475 0.07402422831306754 0.11109557366596974 0.2191164138565274 0.07546885050441515 0.20483237480364308 0.11615170786986552 0.0381762502754693 0.22263612718720172 0.24336045934786105 0.38598629534869333 0.3204142278104345 0.2601792060240761 0.23247216773041696 0.3757999653852862 0.35928993545506094 0.2509779533453429 0.3643402858148399 0.39632173362710965 0.575687752657507 0.5008732988612786 0.6623919444480774 0.7018043580937466 0.5272871798689759 0.667728311792801 0.6078956020384904 0.4345651922346484 0.5996588130635248 0.7210772003637764 0.42722139243296087 0.35439395239148813 0.7147388704593604 0.4106699658179282 0.3497431011883906 0.5418106542233493 0.560760510938887 0.35225313431311434 0.37402953664800237 0.2297375025660875 0.3577860386183956 0.326537381451767 0.2555420237036465 0.23473207264267626 0.4151883693106389 0.44186282463665766 0.3187782544457513 0.4179154540744977 0.375950547896465 0.44699979421403335 0.4611164668526019 0.4662246206335853 0.4532316308167651 0.4664393408109246 0.464904870758072 0.45197274569258394 0.4762751032293594 0.47350284112275876 0.44706448046952557 0.47657503153322334 0.373882258337215 0.565023074734028 0.5979973624582261 0.316834244300302 0.6552939749607231 0.261275255319136 0.15883580138739917 0.26022639822217686 0.4027260797555509 0.1279960066767012 0.2484533679828127 0.21901575109033694 0.2563760888394433 0.24232663031610985 0.14044590850980773 0.2685226689756044 0.1409934473703218 0.18220477764168244 0.1918002295199586 0.2773909652564597 0.23281209116981214 0.2767245930113652 0.2299542103399049 0.22849866529477975 0.26413416634955944 0.26675858311227507 0.23999526474359578 0.22339394510145336 0.273231882593264 0.2199325471167417 0.1666814158170059 0.16444459392484748 0.18438535164865283 0.1461261538722861 0.1846408210464268 0.14993599666356897 0.210452615303554 0.198791324446648 0.14486400037544028 0.1383751628513299 0.7268245365843252 0.23599918983685594 0.3456479528893672 0.45553879410243736 0.7757457055074936 0.34993025627844104 0.7334034313736815 0.4705267271181671 0.23938354773119475 0.7861792156769964 0.7040039608388684 0.13846996297533598 0.39847358183491394 0.6373149701654086 0.747177759226148 0.17886037238004648 0.2443252523281113 0.6737993923336767 0.22429981437337299 0.0974883155182058 0.20607801190196628 0.16078471238645148 0.2585694587915902 0.2824300654698769 0.17677589808844632 0.2618001404607727 0.22557691478424613 0.12064122698553205 0.22059029346765746 0.2940980062641696 0.18890017166854678 0.16282857878272833 0.29182893904514007 0.1829749042674011 0.1611636143260534 0.2299221351040896 0.23670601971201685 0.16206218444907913 0.16985794791226932 0.11820264920743995 0.2508346492459872 0.21846745453760127 0.14493083645601043 0.1233759986186354 0.3102916814097617 0.3379209419144153 0.21043059160196745 0.3131163814622285 0.2696493524010856 0.3432417879794276 0.5294488406227182 0.5968283346691314 0.4254433064292403 0.5996606176290806 0.5794200727622666 0.4088378856908003 0.7293999958330161 0.6928322599903348 0.34409503699143845 0.7333562231180648 sources_5316/dwtest/test_EditCostTable.praat0000664000176700017670000000370111756711640020026 0ustar paulpaul# test_EditCostTable.praat # djmw 20120522 printline test_EditCostTable numberOfTargets = 4 numberOfSources = 4 table = Create empty EditCostsTable... editCosts numberOfTargets numberOfSources printline 'tab$'Set values... for i to numberOfTargets targetSymbol$[i] = "t'i'" Set target symbol (index)... i t'i' Set insertion costs... t'i' numberOfSources*i endfor for i to numberOfSources sourceSymbol$[i] = "s'i'" Set source symbol (index)... i s'i' Set deletion costs... s'i' numberOfTargets*i endfor cost = 0 for i to numberOfTargets for j to numberOfSources cost += 1 Set substitution costs... t'i' s'j' cost endfor endfor for i to numberOfSources Set substitution costs... nomatch s'i' 20 endfor for i to numberOfTargets Set substitution costs... t'i' nomatch 21 endfor Set costs (others)... 1 2 3 4 costs = Get cost (others)... Insertion assert costs = 1 costs = Get cost (others)... Deletion assert costs = 2 costs = Get cost (others)... Equality assert costs = 3 costs = Get cost (others)... Inequality assert costs = 4 printline 'tab$'Get values... for i to numberOfTargets target$ = targetSymbol$[i] index = Get target index... 'target$' assert index = i cost = Get insertion cost... 'target$' assert cost = numberOfSources*i endfor for i to numberOfSources source$ = sourceSymbol$[i] index = Get source index... 'source$' assert index = i cost = Get deletion cost... 'source$' assert cost = numberOfTargets*i endfor cost = 0 for i to numberOfTargets target$ = targetSymbol$[i] for j to numberOfSources source$ = sourceSymbol$[j] cost += 1 scost = Get substitution cost... 'target$' 'source$' assert scost = cost endfor endfor for i to numberOfSources source$ = sourceSymbol$[i] cost = Get substitution cost... nomatch 'source$' assert cost = 20 endfor for i to numberOfTargets target$ = targetSymbol$[i] cost = Get substitution cost... 'target$' nomatch assert cost = 21 endfor Remove printline test_EditCostTable OKsources_5316/dwtest/test_TextGrid_extensions.praat0000644000176700017670000000112311566423320021335 0ustar paulpaul# test_TextGrid_extensions.praat # djmw 20110523 printline test_TextGrid_extensions s = Read Strings from raw text file... TIMIT_train_dr1_fcjf0_sa1.phn ns = Get number of strings tg = Read from file... TIMIT_train_dr1_fcjf0_sa1.phn ntiers = Get number of tiers assert ntiers = 2 nints = Get number of intervals... 1 assert nints = ns for i to ns select s string$ = Get string... i slabel$ = replace_regex$ (string$, "[0-9\s]", "", 0) select tg tglabel$ = Get label of interval... 1 i assert slabel$ = tglabel$ endfor select s plus tg Remove printline test_TextGrid_extensions OK sources_5316/dwtest/test_Polygon_getLocationOfPoint.praat0000644000176700017670000000355611604654073022622 0ustar paulpaul# test_Polygon_getLocationOfPoint.praat eps = 1e-15 # minimal crossing Polygon px[1] = 0.123 py[1] = 0 px[2] = 0.123 py[2] = 1 px[3] = 1.123 py[3] = 0 px[4] = 1.123 py[4] = 1 np = 4 p = Create simple Polygon... p 'px[1]' 'py[1]' 'px[2]' 'py[2]' 'px[3]' 'py[3]' 'px[4]' 'py[4]' px[5] = px[1] py[5] = py[1] printline ... x left xm = px[1] - 0.1 for i to 100 ym = randomUniform(py[1]-1, py[2]+1) loc$ = Get location of point... xm ym eps assert loc$="O"; 'xm' 'ym' endfor printline ... x right xm = px[3] + 0.1 for i to 100 ym = randomUniform(py[1]-1, py[2]+1) loc$ = Get location of point... xm ym eps assert loc$="O"; 'xm' 'ym' endfor printline ... y top ym = py[2] + 0.1 for i to 100 xm = randomUniform(px[1]-1, px[3]+1) loc$ = Get location of point... xm ym eps assert loc$="O"; 'xm' 'ym' endfor printline ... y bottom ym = py[1] - 0.1 for i to 100 xm = randomUniform(px[1]-1, px[3]+1) loc$ = Get location of point... xm ym eps assert loc$="O"; 'xm' 'ym' endfor printline ... vertices for i to np loc$ = Get location of point... px[i] py[i] eps assert loc$ = "V" endfor printline ... edges for i to np for j to 100 f = randomUniform(0,1) xm = px[i]+f*(px[i+1]-px[i]) ym = py[i] +f*(py[i+1]-py[i]) loc$ = Get location of point... xm ym eps assert loc$ = "E"; 'xm' 'ym' endfor endfor printline ... inside for i to 100 fx = randomUniform (0,0.5) fy = randomUniform (fx, 1-fx) xm = px[1]+fx ym = py[1]+fy loc$ = Get location of point... xm ym eps assert loc$ = "I"; 'xm' 'ym' fx = 1 - fx xm = px[1]+fx loc$ = Get location of point... xm ym eps assert loc$ = "I"; 'xm' 'ym' endfor printline ... outside #could be done better for i to 100 fx = randomUniform (0,0.5) fy = randomUniform (0, fx) xm = px[1] + fx ym = py[1] + fy loc$ = Get location of point... xm ym eps assert loc$ = "O"; 'xm' 'ym' endfor select p Remove # now use epsilon ... sources_5316/dwtest/test_Permutation.praat0000644000176700017670000000373211571432434017645 0ustar paulpaul# test_Permutation.praat # djmw 20050710, 20070820, 20100525, 20100819, 20110418 printline test_Permutation call test_600_12 call rotate call sequence call swap call invertp printline test_Permutation OK procedure rotate printline ..Rotate for .i to 20 .p = Create Permutation... test .i y print '.i' for .k to .i select .p .pk = Rotate... 0 0 .k .pkk = Get value... .k+1 if .pkk > 0 assert .pkk = 1 ; i='.i', k='.k' endif .pki = Rotate... 0 0 -.k for .l to .k .pkil = Get value... .l assert .pkil = .l endfor plus .pk Remove print . endfor printline ..o.k. select .p Remove endfor endproc procedure invertp printline ..Invert for .i to 20 .p = Create Permutation... test .i y .pin = Invert plus .p .pm = Multiply for .k to .i .pmk = Get value... .k assert .pmk = .k ; i='.i', k='.k' endfor print . plus .pin plus .p Remove endfor printline ..o.k. endproc procedure test_600_12 printline ..test_600_12 .p = Create Permutation... 600 600 y .pin = Interleave... 0 0 12 1 .pininv = Invert plus .pin .pm = Multiply for .l to 600 .pkil = Get value... .l assert .pkil = .l; l='.l' endfor plus .pin plus .pininv plus .p Remove printline ..o.k. endproc procedure sequence printline ..Sequences .n = 4 .np = 4*3*2 - 1 Create Permutation... ps .n y for .j to .np for .i to .j Next endfor for .i to .j Previous endfor for .i to .n .val = Get value... .i assert .val = .i endfor print . endfor Remove printline ..o.k. endproc procedure swap print ..Swap positions .p = Create Permutation... id 10 y for .i to 10 for .j to 10 select .p .ps = Copy... swap Swap positions... .i .j for .k to 10 select .p .pk = Get value... .k select .ps .psk = Get value... .k if .k <> .i and .k <> .j assert .pk = .psk endif endfor select .ps Remove print . endfor endfor select .p Remove printline ..o.k. endproc sources_5316/dwtest/test_Procrustes.praat0000644000176700017670000000746611604652224017515 0ustar paulpaul# test_Procrustes.praat # djmw 20040117, 20070820 printline ----- test_Procrustes.praat ----- call test_orthogional_procrustes_gvl_12_4_3 call test_procrustes_bg_19_4 call test_procrustes_random_configurations 12 printline printline ----- succeeded: test_Procrustes.praat (end) ----- procedure test_procrustes_bg_19_4 # example Borg&Groenen section 19.4 printline test example in Borg & Groenen section 19.4 nr = 4 nc = 2 s = 0.5 t1 = 1 t2 = 2 alpha = 30 eps = 2.3e-16 Create Configuration... X nr nc 0 Set value... 1 1 1 Set value... 1 2 2 Set value... 2 1 -1 Set value... 2 2 2 Set value... 3 1 -1 Set value... 3 2 -2 Set value... 4 1 1 Set value... 4 2 -2 for i to 4 Set row label (index)... i x_'i' endfor Copy... Y ! Horizontal reflection Invert dimension... 1 Rotate... 1 2 alpha Formula... 0.5*self + (if col=1 then t1 else t2 fi) plus Configuration X To Procrustes... 0 Rename... X_Y plus Configuration Y To Configuration Rename... Z Formula... self-Configuration_X[] for i to 4 for j to 2 assert Configuration_Z[i,j] < nr*nc*eps; Configuration_Z['i','j'] < 'nr'*'nc'*'eps' endfor endfor select Procrustes X_Y Invert Rename... X_Yi for i to 2 tp = Get translation element... i assert t'i' - tp < nr*nc*eps; translation['i'] endfor sp = Get scale assert s - tp < nr*nc*eps; scale select Configuration X plus Configuration Y plus Configuration Z plus Procrustes X_Y plus Procrustes X_Yi Remove endproc procedure test_procrustes_random_configurations numconf printline 'numconf' randomly generated configurations of dimension 2^1 x 2 .. 2^12 x 2 nr = 2 print Configuration: for k to numconf print 'k' Create Configuration... X nr nc randomUniform(-1,1) Copy... Y Invert dimension... 1 alpha = randomUniform (0,90) Rotate... 1 2 alpha t1 = randomUniform (0,2) t2 = randomUniform (0,2) scale = randomUniform(0.5,2) Formula... scale*self + (if col=1 then t1 else t2 fi) plus Configuration X To Procrustes... 0 Rename... X_Y plus Configuration Y To Configuration Rename... Z Formula... self-Configuration_X[] for i to nr for j to 2 assert Configuration_Z[i,j] < nr*nc*eps; Configuration_Z['i','j'] < 'nr'*'nc'*'eps' endfor endfor select Procrustes X_Y Invert Rename... X_Yi # no need to test the translations, they need not be equal (see BG page 347) sp = Get scale assert abs(scale - sp) < nr*nc*eps; scale # printline o.k.: nr='nr', nc='nc', alpha='alpha' degrees, scale='scale', t=('t1', 't2') nr *= 2 select Configuration X plus Configuration Y plus Configuration Z plus Procrustes X_Y plus Procrustes X_Yi Remove endfor endproc procedure test_orthogional_procrustes_gvl_12_4_3 printline test orthognal Procrustes transform (example 12.4.1 Golub & van Loan) Create Configuration... a 4 2 0 Set value... 1 1 1 Set value... 2 1 3 Set value... 3 1 5 Set value... 4 1 7 Set value... 1 2 2 Set value... 2 2 4 Set value... 3 2 6 Set value... 4 2 8 Create Configuration... b 4 2 0 Set value... 1 1 1.2 Set value... 2 1 2.9 Set value... 3 1 5.2 Set value... 4 1 6.8 Set value... 1 2 2.1 Set value... 2 2 4.3 Set value... 3 2 6.1 Set value... 4 2 8.1 plus Configuration a To Procrustes... y t2 = Get translation element... 2 assert t2 = 0 s = Get scale assert s = 1; eps = 5e-5 r11 = Get transformation element... 1 1 r22 = Get transformation element... 2 2 assert r11-r22 < eps assert r11-0.9999 < eps r12 = Get transformation element... 1 2 r21 = Get transformation element... 2 1 assert r12+0.0126 < eps assert r21-0.0126 < eps plus Configuration a plus Configuration b Remove endproc sources_5316/dwtest/discriminant_tableofreal_mahalanobis.praat0000644000176700017670000000217211321175717023657 0ustar paulpaul# discriminant_tableofreal_mahalanobis.praat # djmw 20100106 # This scripts calculates the amount of overlap between two normal distributions # both distributions have sigma = 1 # mu1 = 0 and mu2 varies from 1 to 5 n = 20000 t0 = Create TableOfReal... t0 n 1 for i to n/2 Set row label (index)... i 1 endfor for i from n/2+1 to n Set row label (index)... i 2 endfor for mu to 5 select t0 Formula... randomGauss ((if row < n/2 then 0 else mu fi), 1) d = To Discriminant for j to 2 select d plus t0 t'j' = To TableOfReal (mahalanobis)... 'j' n endfor tt = Copy... tt for nsigma to 5 Formula... Object_'t1'[row,col] < nsigma and Object_'t2'[row,col] < nsigma nr = 0 for kr to n if Object_'tt'[kr,1] = 1 nr += 1 endif endfor z12 = 0 + nsigma z21 = mu - nsigma expect = 0 if z21 < z12 # we have overlap expect = (gaussQ (z21) - gaussQ (z12)) * n endif diff = nr - expect printline For d='mu' and 'nsigma'-sigma: 'nr' from 'n' overlap; diff = 'diff:1' (expect = 'expect:1') endfor select d plus t1 plus t2 plus tt Remove endforsources_5316/dwtest/test_Sound_draw_where.praat0000644000176700017670000000452411643052627020637 0ustar paulpaul# Sound_drawWhere_test.praat # djmw 20091031,20100912, 20110524 Erase all printline Draw where... Begin tests # maximally steep printline Top: sawtooth in black with parts above 0.5 in blue s = Create Sound from formula... s Mono 0 1 44100 20*((x mod 0.1) - 0.05) ymin = -1.1 ymax = 1.1 Select outer viewport... 0 6 0 3 Blue Draw where... 0 0.4 ymin ymax n Curve self>0.5 Black Draw where... 0 0.4 ymin ymax n Curve self<=0.5 One mark left... 0.5 y y y Draw inner box Text top... n sawtooth in black with parts above 0.5 in blue Remove # corner cases printline Second figure, interpolation between sample points: three sample points, parts above 0.5 in blue s =Create Sound from formula... s Mono 0 0.0003 10000 0 Select outer viewport... 0 6 3 6 Blue Formula... if col=1 then -1 else if col=2 then 1 else -1 fi fi Draw where... 0 0 ymin ymax n Curve self>0.5 Black Draw where... 0 0 ymin ymax n Curve self<=0.5 One mark left... 0.5 y y y Formula... if col=1 then 1 else if col=2 then -1 else 1 fi fi Blue Draw where... 0 0 ymin ymax n Curve self>0.5 Black Draw where... 0 0 ymin ymax n Curve self<=0.5 One mark left... 0.5 y y y # Compatibility with Draw... : only draw in blue Formula... 0.6 Blue Draw where... 0 0 ymin ymax n Curve 1 Black Draw where... 0 0 ymin ymax n Curve 0 Draw inner box Text top... n (2x) three sample points, parts above 0.5 in blue + blue straight Remove # random, selection on amplitudes printline Random amplitudes draw parts > 0.5 in blue Select outer viewport... 0 6 6 9 s = Create Sound from formula... s Mono 0 0.01 10000 randomUniform(-1,1) Blue Draw where... 0 0 ymin ymax n Curve self>0.5 Black Draw where... 0 0 ymin ymax n Curve self<=0.5 One mark left... 0.5 y y y Draw inner box Text top... n Random amplitudes: parts > 0.5 in blue # complementary selections in amplitude and time domain printline Random amplitudes: parts > 0.5 in blue only in the first half of every 0.001 s Select outer viewport... 0 6 9 12 Blue Draw where... 0.001 0.01 ymin ymax n Curve (self>0.5 and x mod 0.001 < 0.0005) Black Draw where... 0.001 0.01 ymin ymax n Curve not (self>0.5 and x mod 0.001 < 0.0005) One mark left... 0.5 y y y Marks bottom every... 1 0.0005 n y y Marks bottom every... 1 0.001 y y y Draw inner box Text top... n Random amplitudes: parts > 0.5 blue only in the first half of every 0.001 s printline Draw where... End tests sources_5316/dwtest/runAllTests.praat0000644000176700017670000000034011603401734016542 0ustar paulpaul# run_all_tests.praat tests = Create Strings as file list... tests test_*.praat ntests = Get number of strings for itest to ntests select tests test$ = Get string... itest printline 'test$' execute 'test$' endif endforsources_5316/dwtest/test_gsl.praat0000664000176700017670000001512711721407131016117 0ustar paulpaul# test_gsl.praat # djmw 20071017, 20080317, 20120223 debug = 0 eps = 2.2204460492503131e-16 tol0 = 2.0*eps tol_2= 4.0*eps tol1 = 16.0*eps tol2 = 256.0*eps tol3 = 2048.0*eps tol4 = 16384.0*eps tol5 = 131072.0*eps tol6 = 1048576.0*eps sqrt_tol0 = sqrt(2.0*eps) call test_besselI call test_besselK call test_erfc call test_erf call test_lnGamma call test_incompleteBeta call test_incompleteGammaP call test_sincpi procedure func_1arg .func$ .arg .r .tol assert$ = "" .res = '.func$' (.arg) .denom = .res+.r if .denom = 0 .denom = 1 endif .z = abs ((.res-.r) / .denom) if .z > .tol assert$ = "!!Assertion failed: " endif if debug <> 0 or assert$ <> "" .neps = .z / eps printline 'assert$' '.func$'('.arg')='.res' ('.r'), n*eps='.neps:2' endif endproc procedure func_1argzero .func$ .arg .tol assert$ = "" .res = '.func$' (.arg) .z = abs (.res) if .z > .tol assert$ = "!!Assertion failed: " endif if debug <> 0 or assert$ <> "" .neps = .z / eps printline 'assert$' '.func$'('.arg')=0, n*eps='.neps:2' endif endproc procedure func_2args .func$ .arg1 .arg2 .r .tol .res = '.func$' (.arg1,.arg2) .denom = .res+.r if .denom <> 0 if debug = 1 .z = abs((.res-.r)/(.res+.r)) .neps = .z/eps printline '.neps:2' '.z' '.func$'('.arg1','.arg2')='.res' ('.r') endif assert abs((.res-.r)/(.res+.r)) < .tol; '.res'='.func$' ('.arg1', '.arg2') ('.r') else if debug = 1 .z = abs(.res-.r) .neps = .z / eps printline '.neps:2' '.z' '.func$'('.arg1','.arg2')='.res' ('.r') endif assert abs(.res-.r) < .tol; '.res'='.func$' ('.arg1', '.arg2') ('.r') endif endproc procedure func_3args .func$ .arg1 .arg2 .arg3 .r .tol .res = '.func$' (.arg1,.arg2, .arg3) .denom = .res+.r if .denom <> 0 if debug = 1 .z = abs((.res-.r)/(.res+.r)) .neps = .z/eps printline '.neps:2' '.z' '.func$'('.arg1','.arg2', '.arg3')='.res' ('.r') endif assert abs((.res-.r)/(.res+.r)) < .tol; '.res'='.func$' ('.arg1', '.arg2', '.arg3') ('.r') else if debug = 1 .z = abs(.res-.r) .neps = .z / eps printline '.neps:2' '.z' '.func$'('.arg1','.arg2', '.arg3')='.res' ('.r') endif assert abs(.res-.r) < .tol; '.res'='.func$' ('.arg1', '.arg2', '.arg3') ('.r') endif endproc procedure test_besselI printline test_besselI: start call func_2args besselI 4 0.1 2.6054690212996573677e-07 tol0 call func_2args besselI 5 2.0 0.009825679323131702321 tol0 call func_2args besselI 100 100.0 4.641534941616199114e+21 tol2 printline test_besselI: success endproc procedure test_besselK printline test_besselK: start call func_2args besselK 4 0.1 479600.2497925682849 tol_2 call func_2args besselK 5 2.0 9.431049100596467443 tol0 call func_2args besselK 100 100.0 7.617129630494085416e-25 tol2 printline test_besselK: success endproc procedure test_erfc printline test_erfc: start call func_1arg erfc -10.0 2.0 tol0 call func_1arg erfc -5.0000002 1.9999999999984625433 tol0 call func_1arg erfc -5.0 1.9999999999984625402 tol0 call func_1arg erfc -1.0 1.8427007929497148693 tol0 call func_1arg erfc -0.5 1.5204998778130465377 tol0 call func_1arg erfc 1.0 0.15729920705028513066 tol0 call func_1arg erfc 3.0 0.000022090496998585441373 tol1 call func_1arg erfc 7.0 4.183825607779414399e-23 tol2 call func_1arg erfc 10.0 2.0884875837625447570e-45 tol2 printline test_erfc: success endproc procedure test_erf printline test_erf: start call func_1arg erf -10.0 -1.0000000000000000000 tol0 call func_1arg erf 0.5 0.5204998778130465377 tol0 call func_1arg erf 1.0 0.8427007929497148693 tol0 call func_1arg erf 10.0 1.0000000000000000000 tol0 printline test_erf: success endproc procedure test_lnGamma printline test_lnGamma: start call func_1arg lnGamma -0.1 2.368961332728788655 tol0 call func_1arg lnGamma -1.0/256.0 5.547444766967471595 tol0 call func_1arg lnGamma 1.0e-08 18.420680738180208905 tol0 call func_1arg lnGamma 0.1 2.252712651734205 tol0 call func_1arg lnGamma 1.0+1.0/256.0 -0.0022422226599611501448 tol0 call func_1arg lnGamma 2.0+1.0/256.0 0.0016564177556961728692 tol0 call func_1arg lnGamma 100.0 359.1342053695753 tol0 call func_1arg lnGamma -1.0-1.0/65536.0 11.090348438090047844 tol0 call func_1arg lnGamma -1.0-1.0/268435456.0 19.408121054103474300 tol0 call func_1arg lnGamma -100.5 -364.9009683094273518 tol0 call func_1arg lnGamma -100-1.0/65536.0 -352.6490910117097874 tol0 call func_1arg lnGamma -1.5 ln(4*sqrt(pi)/3) tol1 call func_1arg lnGamma 0.5 0.5*ln(pi) tol0 call func_1arg lnGamma 1 0 tol0 call func_1arg lnGamma 1.5 ln(sqrt(pi)/2) tol2 call func_1arg lnGamma 2 0 tol0 call func_1arg lnGamma 2.5 ln(3*sqrt(pi)/4) tol1 call func_1arg lnGamma 3 ln(2) tol_2 call func_1arg lnGamma 3.5 ln(15*sqrt(pi)/8) tol_2 call func_1arg lnGamma 4 ln(6) tol_2 printline test_lnGamma: success endproc # incompleteBeta # Limiting values: $I_0(a,b)=0 I_1(a,b)=1$ # Symmetry: $I_x(a,b) = 1 - I_{1-x}(b,a)$ procedure test_incompleteBeta printline test_incompleteBeta: start printline incompleteBeta (a,b,0) = 0 and incompleteBeta (a,b,1) = 1 for .i to 20 .a = randomUniform (0, 50) .b = randomUniform (0, 50) call func_3args incompleteBeta .a .b 0 0 tol0 call func_3args incompleteBeta .a .b 1 1 tol0 endfor printline incompleteBeta(i, 1, 0.1)=10^(-i) & incompleteBeta(a,b,x)=1-incompleteBeta(b,a,1-x) for .i to 310 .a = .i .b = 1 .x = 0.1 call func_3args incompleteBeta .a .b .x 10^(-.i) tol1*.i # if i > 16 then 1-10^(-.i) equals 1! call func_3args incompleteBeta .b .a 1-.x 1-10^(-.i) tol1*.i endfor printline test_incompleteBeta: success endproc procedure test_incompleteGammaP printline test_incompleteGammaP: start printline incompleteGammaP(a,0)=0 &incompleteGammaP(a,inf)=1 for .i to 20 .a = randomUniform (0, 100) call func_2args incompleteGammaP .a 0 0 tol0 call func_2args incompleteGammaP .a 10^200 1 tol0 endfor printline incompleteGammaP(1,x)=1-exp(-x) emax = round(19*ln(10)) for .i to 100 .x = randomUniform (0, emax) call func_2args incompleteGammaP 1 .x 1-exp(-.x) tol1 endfor printline incompleteGammaP(2,x)=(1-(1+x)*exp(-x))/2 for .i to 100 .x = randomUniform (0, emax) call func_2args incompleteGammaP 2 .x 1-(1+.x)*exp(-.x) tol3 endfor printline incompleteGammaP(3,x)=(1-(1+x+0.5*x^2)*exp(-x))/2 for .i to 100 .x = randomUniform (0, emax) call func_2args incompleteGammaP 3 .x 1-(1+.x+0.5*.x^2)*exp(-.x) 2*tol4 endfor printline test_incompleteGammaP: succes endproc procedure test_sincpi printline test_sincpi: start call func_1arg sincpi 0 1 tol0 for .i to 200 .arg = .i call func_1argzero sincpi .arg tol0 .arg = -.arg call func_1argzero sincpi .arg tol0 endfor printline test_sincpi: succes endproc sources_5316/dwtest/test_Polygon_simplify.praat0000644000176700017670000000175311604300707020674 0ustar paulpaul# test_Polygon_simplify.praat printline test_Polygon_simplify p = Create simple Polygon... p 0 0 0 1 0.25 0.75 -0.25 0.75 0.25 0.25 -0.25 0.25 for j to 10 m = Create simple Matrix... ps 2 100 randomUniform (0,1) p1x = Get value in cell... 1 1 p1y = Get value in cell... 2 1 p2x = Get value in cell... 1 10 p2y = Get value in cell... 2 10 for i from 2 to 99 if ( i mod 10) =0 p1x = Get value in cell... 1 i p1y = Get value in cell... 2 i p2x = Get value in cell... 1 i+10 p2y = Get value in cell... 2 i+10 elsif ( i mod 10) >0 # 9 points on the edge from p(i) to point(i+10) af = randomUniform (0,1) xn = p1x +af*(p2x-p1x) yn = p1y + af*(p2y-p1y) Set value... 1 i xn Set value... 2 i yn endif endfor p = To Polygon for k to 10 select p p3 = Circular permutation... randomUniform (1, 100) p4 = Simplify np = Get number of points assert np = 11 plus p3 Remove endfor select m plus p Remove endfor printline test_Polygon_simplify OK sources_5316/dwtest/test_TableOfReal_extensions.praat0000664000176700017670000000160711663202712021732 0ustar paulpaul# test_TableOfReal_extensions.praat eps = 2.3e-16 printline TableOfReal_extensions test call means_by_row_labels printline TableOfReal_extensions test... OK procedure means_by_row_labels printline 'tab$'means_by_row_labels .nrows = 100 .ncols = 3 .tab1 = Create TableOfReal... tab .nrows .ncols for .i to .nrows if (.i mod 2) = 0 Set row label (index)... .i even else Set row label (index)... .i odd endif endfor Formula... if (row mod 2) = 0 then col else 2*col fi .tabm = To TableOfReal (means by row labels)... no .nrowsm = Get number of rows .ncolsm = Get number of columns assert .nrowsm = 2 assert .ncolsm = .ncols for .i to .nrowsm .rowLabel$ = Get row label... .i for .j to .ncols if .rowLabel$ = "even" .dif = abs (Object_'.tabm'[.i,.j] - .j) else .dif = abs(Object_'.tabm'[.i,.j] - .j*2) endif assert .dif <= eps endfor endfor endproc sources_5316/dwtest/test_sigma_ellipse.praat0000644000176700017670000000125510710226217020143 0ustar paulpaul# test_sigma_ellipse.praat # djmw 20070412 Create TableOfReal... table 10000 2 tor = selected ("TableOfReal") Formula... if col = 1 then randomGauss(0,1) else self fi Formula... if col = 2 then randomGauss(0,2) else self fi To SSCP... 0 0 0 0 sscp = selected ("SSCP") Erase all Select outer viewport... 0 6 0 12 select tor Draw scatter plot... 1 2 0 0 -6 6 -12 12 12 no + yes select sscp Red nsigma=3 call get_p 3 call get_p 4 procedure get_p .nsigma select sscp psigma = 1-exp(-.nsigma*.nsigma/2) printline nsigma='.nsigma', p='psigma' Red Draw sigma ellipse... .nsigma 1 2 -6 6 -12 12 no Green Draw confidence ellipse... psigma 1 2 -6 6 -12 12 no Black endproc sources_5316/dwtest/test_FFNet.praat0000644000176700017670000000160711563032622016273 0ustar paulpaul# test_FFNet.praat # djmw 20110512 printline test FFNet Create iris example... 0 0 ffnet = selected ("FFNet") pattern = selected ("Pattern") cat = selected ("Categories") ntries = 10 error1 = Get total costs... Minimum-squared-error tab = Create Table with column names... results ntries costsb costsa fc for i to ntries select ffnet Reset... 0.1 plus pattern plus cat costsb = Get total costs... Minimum-squared-error Learn... 200 1e-7 Minimum-squared-error costsa = Get total costs... Minimum-squared-error select ffnet plus pattern cati = To Categories... Winner-takes-all plus cat fd = Get fraction different fc = 1 -fd select tab Set numeric value... i costsb costsb Set numeric value... i costsa costsa Set numeric value... i fc fc select cati Remove endfor select tab mean = Get mean... fc assert fc > 0.97 plus ffnet plus pattern plus cat Remove printline FFNet ok sources_5316/dwtest/regexp_textgrid_test.praat0000644000176700017670000000042711111067310020523 0ustar paulpaul# regexp_textgrid_test.praat # djmw 20081119 Create Sound from formula... sineWithNoise Mono 0 1 44100 1/2 * sin(2*pi*377*x) + randomGauss(0,0.1) To TextGrid... hhhhh select TextGrid sineWithNoise for i to 5 Insert boundary... 1 0.1*i Set interval text... 1 i+1 'i' endforsources_5316/dwtest/test_regex.praat0000644000176700017670000001423311567530553016454 0ustar paulpaul# test_regex.praat # djmw 20070528, 20070917, 20080122, 20110526 printline test_regex debug = 0 procedure match_index .s$ .match$ .i .il = index_regex (.s$, .match$) if debug = 1 printline '.i' ('.il' = index_regex ("'.s$'", "'.match$'")) endif assert .il = .i; index_regex ("'.s$'", "'.match$'") endproc procedure match_rindex .s$ .match$ .i .ir = rindex_regex (.s$, .match$) if debug = 1 printline '.i' ('.ir' = rindex_regex ("'.s$'", "'.match$'")) endif assert .ir = .i; rindex_regex ("'.s$'", "'.match$'") endproc procedure replace_re .string$ .search$ .replace$ .n .result$ .r$ = replace_regex$ (.string$, .search$, .replace$, .n) if debug = 1 printline '.result$' ("'.r$'" = replace_regex$ ("'.string$'", "'.search$'", "'.replace$'", "'.n'")) endif assert .r$ = .result$; '.result$' ("'.r$'" = replace_regex ("'.string$'", "'.search$'", "'.replace$'", "'.n'")) endproc # ordinary characters printline ---- # match characters alphabet$ = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ" s$ = alphabet$ sl = length (s$) sd$ = s$ + s$ for i to 52 match$ = mid$ (s$, i, 1) call match_index "'s$'" "'match$'" i ir = i + sl call match_rindex "'sd$'" "'match$'" ir endfor printline ---- # special characters # backslash \ call match_index "cscscAaa\n" "aa\\n" 7 call match_rindex "cscscAaa\n" "aa\\n" 7 call match_index "cscscAa+a+" "b\+" 0 call match_index "cscscAa+a+" "a\+" 7 call match_rindex "cscscAa+a+" "b\+" 0 call match_rindex "cscscAa+a+" "a\+" 9 printline ---- # special characters # caret ^ call match_index "cscscAa+a+" "^c" 1 call match_rindex "cscscAa+a+" "^c" 1 printline ---- # special characters # dollar $ call match_index "cscscAa+ac" "c$" 10 call match_rindex "cscscAa+ac" "c$" 10 printline ---- # special characters # quantifier brackets {} call match_index "cscscAaa\n" "a{1}" 7 call match_rindex "cscscAaa\n" "a{1}" 8 call match_index "cscscAaa\n" "a{2}" 7 call match_rindex "cscscAaa\n" "a{2}" 7 call match_index "cscscAaa\n" "a{2,}" 7 call match_rindex "cscscAaa\n" "a{2,}" 7 call match_index "cscscAaa\n" "a{,2}" 1 call match_rindex "cscscAaa\n" "a{,2}" 11 call match_index "cscscAaa\n" "a{1,2}" 7 call match_rindex "cscscAaa\n" "a{1,2}" 8 printline ---- # special characters # open and close brackets [] s$ = alphabet$ sd$ = s$ + s$ for i to 26 # match [a-z], [b-z], ..., [z-z] bl$ = mid$ (s$, i, 1) match$ = "[" + bl$ + "-z]" call match_index "'s$'" "'match$'" i call match_rindex "'sd$'" "'match$'" 78 # now for uppercase bu$ = mid$ (s$, i+26, 1) match$ = "[" + bu$ + "-Z]" il = i+26 call match_index "'s$'" "'match$'" il ir = 104 call match_rindex "'sd$'" "'match$'" ir # match [a-a], [b-b], [z-z] match$ = "[" + bl$ + "-" + bl$ +"]" call match_index "'s$'" "'match$'" i ir = 52+i call match_rindex "'sd$'" "'match$'" ir endfor printline ---- # special characters # grouping characters () match$ = "(ab)" call match_index "c" "(ab)" 0 call match_index "cc" "(ab)" 0 call match_index "ccc" "(ab)" 0 call match_index "ac" "(ab)" 0 call match_index "acc" "(ab)" 0 call match_index "accc" "(ab)" 0 call match_index "aca" "(ab)" 0 call match_index "acca" "(ab)" 0 call match_index "accca" "(ab)" 0 call match_index "ababcccc" "(ab)" 1 call match_rindex "ababcccc" "(ab)" 3 call match_index "cababcccc" "(ab)" 2 call match_rindex "cababcccc" "(ab)" 4 call match_index "cccccccabab" "(ab)" 8 call match_rindex "cccccccabab" "(ab)" 10 call match_index "ababcccc" "(ab)\1" 1 call match_rindex "ababcccc" "(ab)\1" 1 printline ---- # special characters # dot . call match_index "ababcccc" ".d" 0 call match_rindex "ababcccc" ".d" 0 call match_index "ababcccc" ".b" 1 call match_rindex "ababcccc" ".b" 3 call match_index "ababcccc" ".a" 2 call match_rindex "ababcccc" ".a" 2 call match_index "ababcccc" ".c" 4 call match_rindex "ababcccc" ".c" 7 printline ---- # special characters # star * call match_index "ababccccd" "b*" 1 call match_index "ababccccd" "ab*" 1 call match_rindex "ababccccd" "ab*" 3 call match_index "ababccccd" "^.*$" 1 printline ---- # special characters # plus + call match_index "ababccccd" "b+" 2 call match_rindex "ababccccd" "b+" 4 printline ---- # special characters # question mark ? call match_index "ababccccd" "ab?" 1 call match_rindex "ababccccd" "ab?" 3 printline ---- # quantifiers # * call replace_re "ab" "(ab)c*" "x" 0 x call replace_re "abc" "(ab)c*" "x" 0 x call replace_re "abcc" "(ab)c*" "x" 0 x call replace_re "abcccd" "(ab)c*" "x" 0 xd call replace_re "ab" "(ab)c+" "x" 0 ab call replace_re "abc" "(ab)c+" "x" 0 x call replace_re "abcc" "(ab)c+" "x" 0 x call replace_re "abcccd" "(ab)c+" "x" 0 xd call replace_re "yyabcccd" "(ab)c+" "x" 0 yyxd printline ---- # non greedy ? call replace_re "abc" "(ab)c*?" "x" 0 xc call replace_re "abcc" "(ab)c*?" "x" 0 xcc call replace_re "abcccd" "(ab)c*?" "x" 0 xcccd call replace_re "abcc" "(ab)c+?" "x" 0 xc call replace_re "abcccd" "(ab)c+?" "x" 0 xccd printline ---- # anchors call replace_re "ababccccd" "ab" "x" 1 xabccccd call replace_re "ababccccd" "^ab" "x" 1 xabccccd printline --- # empty string call replace_re "" ".*" "aaa" 0 aaa call replace_re "" ".*" "aaa" 1 aaa call replace_re "" ".*" "aaa" 10 aaa # special constructs with parenthesis # special control characters # convenience escapes # octal and hexadecima escapes # sustitution special characters printline ---- # replaced string much longer than original call replace_re "ababababababababababababababababababab" "b" "xxxxx" 1 axxxxxabababababababababababababababababab # The returned value is "xxccccd" instead of "xabccccd". call replace_re "ababccccd" "^ab" "x" 0 xabccccd printline --------- PREVIOUS BUGS < 5.0.4 printline ---- # replace by empty string "" # Bugs in praat versions before 5.0.4 # Returned empty string "" call replace_re "abc " " $" "" 1 abc # Returned "xxccccd" instead of "xabccccd". call replace_re "ababccccd" "^ab" "x" 0 xabccccd printline --------- PREVIOUS BUGS < 5.0.5 call replace_re "hallo" "l" "b" 0 habbo call replace_re "hallo" "." "&&" 0 hhaalllloo printline --------- PREVIOUS BUGS --- END printline --------- BUG in 5.0.40 call replace_re "c " ".*" "aaaa" 0 aaaa printline --------- PREVIOUS BUGS --- END printline test_regex OK sources_5316/dwtest/test_Sound_paint_where.praat0000644000176700017670000000210511571470373021010 0ustar paulpaul# test_Sound_paint_where.praat # djmw 20110524 Erase all s1 = Create Sound from formula... s Mono 0 1 10000 0.5*sin (2*pi*5*x) s2 = Create Sound from formula... 1odx Mono 0 20 100 1/x s3 = Create Sound from formula... line Mono 0 1 10000 x/2 Select outer viewport... 0 6 0 3 select s1 Paint where... Red 0 0 -1 1 -1 y 1 Paint where... Green 0 0 -1 1 1 n 1 Text top... n Paint where: green above, red below the sin of 5 Hz Select outer viewport... 0 6 3 6 Paint where... Red 0 0 -1 1 0 n self>0 Paint where... Green 0 0 -1 1 0 y self<0 Text top... n Paint where: green is positive area , red is negative area of sin of 5 Hz select s2 Select outer viewport... 0 6 6 9 Draw... 0 20 0 1.5 y Curve Paint where... Grey 0 20 0 1.5 0 y (x>=1 and x<2) or (x>=4 and x<8) One mark bottom... 1 y y n One mark bottom... 2 y y n One mark bottom... 4 y y n One mark bottom... 8 y y n Text top... n Paint where: grey intervals (1,2) and (4,8) Remove select s3 plus s1 Select outer viewport... 0 6 9 12 Paint enclosed... Grey 0 0 -1 1 yes Text top... n Paint enclosed: between sine and straight line sources_5316/dwsys/0000755000176700017670000000000011755136571013107 5ustar paulpaulsources_5316/dwsys/FileInMemory.cpp0000664000176700017670000002210211723710247016142 0ustar paulpaul/* FileInMemory.cpp * * Copyright (C) 2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "FileInMemory.h" #include "Strings.h" Thing_implement (FileInMemory, Data, 0); void structFileInMemory :: v_copy (thou) { thouart (FileInMemory); FileInMemory_Parent :: v_copy (thee); therror thy d_path = Melder_wcsdup (d_path); thy d_id = Melder_wcsdup (d_id); thy d_numberOfBytes = d_numberOfBytes; thy d_data = NUMvector (0, d_numberOfBytes); memcpy (thy d_data, d_data, d_numberOfBytes+1); } void structFileInMemory :: v_destroy () { Melder_free (d_path); Melder_free (d_id); NUMvector_free (d_data, 0); FileInMemory_Parent :: v_destroy (); } void structFileInMemory :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"File name: ", d_path); MelderInfo_writeLine2 (L"Id: ", d_id); MelderInfo_writeLine2 (L"Number of bytes: ", Melder_integer (d_numberOfBytes)); } FileInMemory FileInMemory_create (MelderFile file) { try { if (! MelderFile_readable (file)) { Melder_throw ("File not readable."); } long length = MelderFile_length (file); if (length <= 0) { Melder_throw ("File is empty."); } autoFileInMemory me = Thing_new (FileInMemory); my d_path = Melder_wcsdup (file -> path); my d_id = Melder_wcsdup (MelderFile_name (file)); my d_numberOfBytes = length; my d_data = NUMvector (0, my d_numberOfBytes); // one extra for 0-byte at end if text MelderFile_open (file); for (long i = 0; i < my d_numberOfBytes; i++) { unsigned int number = bingetu1 (file -> filePointer); my d_data[i] = number; } my d_data[my d_numberOfBytes] = 0; // one extra MelderFile_close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("FileInMemory not created from \"", Melder_fileToPath (file), "\"."); } } FileInMemory FileInMemory_createWithData (long numberOfBytes, const char *data, const wchar_t *path, const wchar_t *id) { try { autoFileInMemory me = Thing_new (FileInMemory); my d_path = Melder_wcsdup (path); my d_id = Melder_wcsdup (id); my d_numberOfBytes = numberOfBytes; my d_data = const_cast (data); // copy pointer to data only return me.transfer (); } catch (MelderError) { Melder_throw ("FileInMemory not create from data."); } } void FileInMemory_setId (FileInMemory me, const wchar_t *newId) { Melder_free (my d_id); my d_id = Melder_wcsdup (newId); } void FileInMemory_showAsCode (FileInMemory me, const wchar_t *name, long numberOfBytesPerLine) { if (numberOfBytesPerLine <= 0) numberOfBytesPerLine = 20; // autoNUMvector data (0, my d_numberOfBytes); ???? MelderInfo_writeLine5 (L"\t\tstatic unsigned char ", name, L"_data[", Melder_integer (my d_numberOfBytes+1), L"] = {"); for (long i = 0; i < my d_numberOfBytes; i++) { unsigned char number = my d_data[i]; MelderInfo_write4 ((i % numberOfBytesPerLine == 0 ? L"\t\t\t" : L""), Melder_integer (number), L",", ((i % numberOfBytesPerLine == (numberOfBytesPerLine - 1)) ? L"\n" : L" ")); } MelderInfo_writeLine1 ((my d_numberOfBytes - 1) % numberOfBytesPerLine == (numberOfBytesPerLine - 1) ? L"\t\t\t0};" : L"0};"); MelderInfo_write3 (L"\t\tautoFileInMemory ", name, L" = FileInMemory_createWithData ("); MelderInfo_writeLine8 (Melder_integer (my d_numberOfBytes), L", reinterpret_cast (&", name, L"_data), \n\t\t\tL\"", my d_path, L"\", \n\t\t\tL\"", my d_id, L"\");"); } Thing_implement (FilesInMemory, SortedSet, 0); int structFilesInMemory :: s_compare_name (I, thou) { iam (FileInMemory); thouart (FileInMemory); return Melder_wcscmp (my d_path, thy d_path); } int structFilesInMemory :: s_compare_id (I, thou) { iam (FileInMemory); thouart (FileInMemory); return Melder_wcscmp (my d_id, thy d_id); } FilesInMemory FilesInMemory_create () { try { autoFilesInMemory me = Thing_new (FilesInMemory); Collection_init (me.peek(), classFileInMemory, 30); return me.transfer(); } catch (MelderError) { Melder_throw ("FilesInMemory not created."); } } FilesInMemory FilesInMemory_createFromDirectoryContents (const wchar_t *dirpath, const wchar *fileGlobber) { try { structMelderDir parent = { { 0 } }; Melder_pathToDir (dirpath, &parent); autoMelderString path; MelderString_append (&path, dirpath, L"/", fileGlobber); autoStrings thee = Strings_createAsFileList (path.string); if (thy numberOfStrings < 1) { Melder_throw ("No files found."); } autoFilesInMemory me = FilesInMemory_create (); for (long i = 1; i <= thy numberOfStrings; i++) { structMelderFile file = { 0 }; MelderDir_getFile (&parent, thy strings[i], &file); autoFileInMemory fim = FileInMemory_create (&file); Collection_addItem (me.peek(), fim.transfer()); } return me.transfer(); } catch (MelderError) { Melder_throw ("FilesInMemory not created from directory \"", dirpath, "\" for files that match \"", fileGlobber, "\"."); } } void FilesInMemory_showAsCode (FilesInMemory me, const wchar_t *name, long numberOfBytesPerLine) { autoMelderString one_fim; autoMelderString all_fims; MelderInfo_writeLine1 (L"#include \"Collection.h\""); MelderInfo_writeLine1 (L"#include \"FileInMemory.h\""); MelderInfo_writeLine1 (L"#include \"melder.h\"\n"); MelderInfo_writeLine3 (L"FilesInMemory create_", name, L" () {"); MelderInfo_writeLine1 (L"\ttry {"); MelderInfo_writeLine1 (L"\t\tautoFilesInMemory me = FilesInMemory_create ();"); for (long ifile = 1; ifile <= my size; ifile++) { FileInMemory fim = (FileInMemory) my item[ifile]; MelderString_append (&one_fim, name, Melder_integer (ifile)); FileInMemory_showAsCode (fim, one_fim.string, numberOfBytesPerLine); MelderInfo_writeLine3 (L"\t\tCollection_addItem (me.peek(), ", one_fim.string, L".transfer());\n"); MelderString_empty (&one_fim); } MelderInfo_writeLine1 (L"\t\treturn me.transfer();"); MelderInfo_writeLine1 (L"\t} catch (MelderError) {"); MelderInfo_writeLine1 (L"\t\tMelder_throw (L\"FilesInMemory not created.\");"); MelderInfo_writeLine1 (L"\t}"); MelderInfo_writeLine1 (L"}\n\n"); } void FilesInMemory_showOneFileAsCode (FilesInMemory me, long index, const wchar_t *name, long numberOfBytesPerLine) { if (index < 1 || index > my size) return; MelderInfo_writeLine1 (L"#include \"FileInMemory.h\""); MelderInfo_writeLine1 (L"#include \"melder.h\"\n"); MelderInfo_writeLine1 (L"static FileInMemory create_new_object () {"); MelderInfo_writeLine1 (L"\ttry {"); autoMelderString one_fim; FileInMemory fim = (FileInMemory) my item[index]; MelderString_append (&one_fim, name, Melder_integer (index)); FileInMemory_showAsCode (fim, L"me", numberOfBytesPerLine); MelderInfo_writeLine1 (L"\t\treturn me.transfer();"); MelderInfo_writeLine1 (L"\t} catch (MelderError) {"); MelderInfo_writeLine1 (L"\t\tMelder_throw (L\"FileInMemory not created.\");"); MelderInfo_writeLine1 (L"\t}"); MelderInfo_writeLine1 (L"}\n\n"); MelderInfo_writeLine3 (L"FileInMemory ", name, L" = create_new_object ();"); } long FilesInMemory_getIndexFromId (FilesInMemory me, const wchar_t *id) { long index = 0; for (long i = 1; i <= my size; i++) { FileInMemory fim = (FileInMemory) my item[i]; if (Melder_wcscmp (id, fim -> d_id) == 0) { index = i; break; } } return index; } Strings FilesInMemory_to_Strings_id (FilesInMemory me) { try { autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, my size); thy numberOfStrings = 0; for (long ifile = 1; ifile <= my size; ifile++) { FileInMemory fim = (FileInMemory) my item[ifile]; thy strings[ifile] = Melder_wcsdup_f (fim -> d_id); thy numberOfStrings++; } return thee.transfer(); } catch (MelderError) { Melder_throw ("No Strings created from FilesinMemory."); } } char * FilesInMemory_getCopyOfData (FilesInMemory me, const wchar_t *id, long *numberOfBytes) { *numberOfBytes = 0; long index = FilesInMemory_getIndexFromId (me, id); if (index == 0) return 0; FileInMemory fim = (FileInMemory) my item[index]; char *data = (char *) _Melder_malloc (fim -> d_numberOfBytes); if (data == 0 || (memcpy (data, fim -> d_data, fim -> d_numberOfBytes) == NULL)) { //Melder_error_ (L"No memory for dictionary."); return 0; } *numberOfBytes = fim -> d_numberOfBytes; return data; } const char * FilesInMemory_getData (FilesInMemory me, const wchar_t *id, long *numberOfBytes) { *numberOfBytes = 0; long index = FilesInMemory_getIndexFromId (me, id); if (index == 0) return 0; FileInMemory fim = (FileInMemory) my item[index]; *numberOfBytes = fim -> d_numberOfBytes; return fim -> d_data; } /* End of file FileInMemory.cpp */ sources_5316/dwsys/Collection_extensions.h0000644000176700017670000000607311630404722017624 0ustar paulpaul#ifndef _Collection_extensions_h_ #define _Collection_extensions_h_ /* Collection_extensions.h * * Copyright (C) 1994-2002 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20110414 Latest modification. */ #include "Collection.h" #include "Graphics.h" #include "Permutation.h" Collection Collection_and_Permutation_permuteItems (Collection me, Permutation him); Collection Collection_permuteItems(Collection me); /* permute the order of my items */ /****************** class OrderedOfString ******************/ Thing_define (OrderedOfString, Ordered) { // overridden methods: virtual void v_info (); }; OrderedOfString OrderedOfString_create (); int OrderedOfString_init (I, long initialCapacity); int OrderedOfString_append (I, wchar_t *append); OrderedOfString OrderedOfString_joinItems (I, thou); /* Join each item */ OrderedOfString OrderedOfString_selectUniqueItems (I, int sort); /* Postcondition: thy size <= my size */ void OrderedOfString_frequency (I, thou, long *count); /* count how often the items in 'thee' occur in 'me' */ /* Precondition: count[1..thy size] exists */ /* To be removed Praat 4.2.4 2004040427 */ int OrderedOfString_difference (I, thou, long *ndif, double *fraction); double OrderedOfString_getFractionDifferent (I, thou); long OrderedOfString_getNumberOfDifferences (I, thou); const wchar_t *OrderedOfString_itemAtIndex_c (I, long index); long OrderedOfString_indexOfItem_c (I, const wchar_t *str); void OrderedOfString_drawItem (I, Graphics g, long index, double xWC, double yWC); void OrderedOfString_sequentialNumbers (I, long n); void OrderedOfString_removeOccurrences (I, const wchar_t *search, int user_regexp); void OrderedOfString_changeStrings (OrderedOfString me, wchar_t *search, wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp); long OrderedOfString_isSubsetOf (I, thou, long *translation); /* Check whether my items are (a subset of)|(in) thy items. * Preconditions: * if (translation) translation[1..my size] exists. * Postconditions: * Return: the number of my labels that are in thee. * if (translation) the returned translation table has the following property: * if (translation[i] > 0) my label[i] = thy label[ translation[i] ]; * else if (translation[i] == 0) my label[i] not in thy labels. */ long OrderedOfString_getSize (I); /* return my size */ #endif /* _Collection_extensions_h_ */ sources_5316/dwsys/FileInMemory.h0000664000176700017670000000472711723710247015624 0ustar paulpaul#ifndef _FileInMemory_h_ #define _FileInMemory_h_ /* FileInMemory.h * * Copyright (C) 2011-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20120125 */ #include "Collection.h" #include "Strings.h" #include "melder.h" Thing_define (FileInMemory, Data) { public: wchar_t *d_path; wchar_t *d_id; long d_numberOfBytes; char *d_data; // overridden methods: void v_copy (Any data_to); void v_destroy (); void v_info (); }; FileInMemory FileInMemory_create (MelderFile file); FileInMemory FileInMemory_createWithData (long numberOfBytes, const char *data, const wchar_t *path, const wchar_t *id); void FileInMemory_dontOwnData (FileInMemory me); void FileInMemory_setId (FileInMemory me, const wchar_t *newId); void FileInMemory_showAsCode (FileInMemory me, const wchar_t *name, long numberOfBytesPerLine); Thing_define (FilesInMemory, SortedSet) { public: int d_sortKey; // overridden methods: static int s_compare_name (Any data1, Any data2); static int s_compare_id (Any data1, Any data2); virtual Data_CompareFunction v_getCompareFunction () { return d_sortKey == 0 ? s_compare_name : s_compare_id; } }; FilesInMemory FilesInMemory_create (); FilesInMemory FilesInMemory_createFromDirectoryContents (const wchar_t *dirpath, const wchar *file); void FilesInMemory_showAsCode (FilesInMemory me, const wchar_t *name, long numberOfBytesPerLine); void FilesInMemory_showOneFileAsCode (FilesInMemory me, long index, const wchar_t *name, long numberOfBytesPerLine); long FilesInMemory_getIndexFromId (FilesInMemory me, const wchar_t *id); Strings FilesInMemory_to_Strings_id (FilesInMemory me); char * FilesInMemory_getCopyOfData (FilesInMemory me, const wchar_t *id, long *numberOfBytes); const char * FilesInMemory_getData (FilesInMemory me, const wchar_t *id, long *numberOfBytes); #endif // _FileInMemory_h_ sources_5316/dwsys/Command.cpp0000644000176700017670000000546311627152110015162 0ustar paulpaul/* Command.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950710 djmw 20020812 GPL header djmw 20071007 wchar_t djmw 20110304 Thing_new */ #include "Command.h" Thing_implement (Command, Thing, 0); void Command_init (I, const wchar_t *name, Any data, int (*execute) (Any), int (*undo) (Any)) { iam (Command); Melder_assert (execute && undo); Thing_setName (me, name); my data = data; my execute = execute; my undo = undo; } int Command_do (I) { iam (Command); return my execute (me); } int Command_undo (I) { iam (Command); return my undo (me); } Thing_implement (CommandHistory, Ordered, 0); CommandHistory CommandHistory_create (long maximumCapacity) { try { autoCommandHistory me = Thing_new (CommandHistory); Collection_init (me.peek(), classCommand, maximumCapacity); return me.transfer(); } catch (MelderError) { Melder_throw ("Command not created."); } } void CommandHistory_forth (I) { iam (CommandHistory); my current++; } void CommandHistory_back (I) { iam (CommandHistory); my current--; } Any CommandHistory_getItem (I) { iam (CommandHistory); Melder_assert (my current > 0 && my current <= my size); return my item[my current]; } void CommandHistory_insertItem (I, Any data) { iam (CommandHistory); Melder_assert (data && (Thing_member ( (Thing) data, my itemClass) || my itemClass == NULL)); if (my current < my size) { for (long i = my current + 1; i <= my size; i++) { forget ( ( (Command *) my item) [i]); } my size = my current; } if (my size >= my _capacity) { Collection_removeItem (me, 1); } my item[++my size] = data; my current = my size; } int CommandHistory_empty (I) { iam (CommandHistory); return my size == 0; } int CommandHistory_offleft (I) { iam (CommandHistory); return my current == 0; } int CommandHistory_offright (I) { iam (CommandHistory); return my size == 0 || my current == my size + 1; } wchar_t *CommandHistory_commandName (I, long offsetFromCurrent) { iam (CommandHistory); long pos = my current + offsetFromCurrent; return pos >= 1 && pos <= my size ? Thing_getName ( (Thing) my item[pos]) : NULL; } /* End of file Command.cpp */ sources_5316/dwsys/SimpleVector_def.h0000644000176700017670000000227611627165033016512 0ustar paulpaul/* SimpleVector_def.h * * Copyright (C) 1994-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020606 GPL header */ #define ooSTRUCT DoubleVector oo_DEFINE_CLASS (DoubleVector, Data) oo_LONG (min) oo_LONG (max) oo_DOUBLE_VECTOR_FROM (v, min, max) oo_END_CLASS (DoubleVector) #undef ooSTRUCT #define ooSTRUCT ComplexVector oo_DEFINE_CLASS (ComplexVector, Data) oo_LONG (min) oo_LONG (max) oo_DCOMPLEX_VECTOR_FROM (v, min, max) oo_END_CLASS (ComplexVector) #undef ooSTRUCT /* End of file SimpleVector_def.h */ sources_5316/dwsys/Permutation_and_Index.cpp0000644000176700017670000000457111606610736020075 0ustar paulpaul/* Permutation_and_Index.cpp * * Copyright (C) 2005-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * djmw 20050725 * djmw 20110503 Latest modification */ #include "Permutation_and_Index.h" Permutation Index_to_Permutation_permuteRandomly (I, int permuteWithinClasses) { iam (Index); try { long numberOfClasses = my classes -> size; autoPermutation thee = Permutation_create (my numberOfElements); autoPermutation classes = Permutation_create (numberOfClasses); Permutation_permuteRandomly_inline (classes.peek(), 0, 0); autoPermutation classesinv = Permutation_invert (classes.peek()); autoNUMmatrix indices (0, numberOfClasses, 1, 4); for (long i = 1; i <= my numberOfElements; i++) { indices[my classIndex[i]][2]++; /* col 2: number of elements in class */ } /* Get some other indices ready */ for (long i = 1; i <= numberOfClasses; i++) { long klass = classes -> p[i]; indices[i][1] = klass; indices[i][3] = indices[i - 1][3] + indices[i - 1][2]; /* col 3: index at start of class */ } for (long i = 1; i <= my numberOfElements; i++) { long klass = my classIndex[i]; long newindex = classesinv -> p[klass]; indices[newindex][4]++; /* col 4: number of elements processed for class */ long newpos = indices[newindex][3] + indices[newindex][4]; thy p[newpos] = i; } if (permuteWithinClasses) { for (long i = 1; i <= numberOfClasses; i++) { long from = indices[i][3] + 1; long to = from + indices[i][2] - 1; if (to > from) { Permutation_permuteRandomly_inline (thee.peek(), from, to); } } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Permutation not created."); } } /* End of file Permutation_and_Index.cpp */ sources_5316/dwsys/NUMmachar.cpp0000644000176700017670000000434111630130241015404 0ustar paulpaul/* NUMmachar.c * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header */ #include "NUMmachar.h" #include "melder.h" #ifndef _NUMcblas_h_ #include "NUMcblas.h" #endif static struct structmachar_Table machar_table; machar_Table NUMfpp = NULL; /* Floating point properties: NR LAPACK dlamch ibeta base 'B' base of the machine it t 'N' number of (base) digits in the mantissa machep eps prec 'P' eps*base ('quantization step') negep epsneg eps 'E' relative machine precision ('quantization error') iexp minexp emin 'M' minimum exponent before (gradual) underflow xmin rmin 'U' underflow threshold - base**(emin-1) maxexp emax 'U' largest exponent before overflow xmax rmax 'O' overflow threshold - (base**emax)*(1-eps) irnd rnd 'R' 1 when rounding occurs in addition, 0 otherwise ngrd sfmin 'S' safe minimum, such that 1/sfmin does not overflow */ void NUMmachar () { if (NUMfpp) { return; } NUMfpp = & machar_table; NUMfpp -> base = (int) NUMblas_dlamch ("Base"); NUMfpp -> t = (int) NUMblas_dlamch ("Number of digits in mantissa"); NUMfpp -> emin = (int) NUMblas_dlamch ("Minimum exponent"); NUMfpp -> emax = (int) NUMblas_dlamch ("Largest exponent"); NUMfpp -> rnd = (int) NUMblas_dlamch ("Rounding mode"); NUMfpp -> prec = NUMblas_dlamch ("Precision"); NUMfpp -> eps = NUMblas_dlamch ("Epsilon"); NUMfpp -> rmin = NUMblas_dlamch ("Underflow threshold"); NUMfpp -> sfmin = NUMblas_dlamch ("Safe minimum"); NUMfpp -> rmax = NUMblas_dlamch ("Overflow threshold"); } /* End of file NUMmachar.c */ sources_5316/dwsys/Permutation.h0000644000176700017670000000641011627164340015561 0ustar paulpaul#ifndef _Permutation_h_ #define _Permutation_h_ /* Permutation.h * * Copyright (C) 2005-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection.h" #include "Permutation_def.h" oo_CLASS_CREATE (Permutation, Data); /* Class invariant: any permutation equals the identity permutation after all its elements are sorted ascendingly. */ void Permutation_init (Permutation me, long numberOfElements); Permutation Permutation_create (long numberOfElements); /* Create the Permutation data structure and fill with the identical permutation (1,2,..n) */ void Permutation_checkInvariant (Permutation me); /* Check that the elements, if sorted ascendingly, are exactly equal to the identity (1,2,...). */ void Permutation_sort (Permutation me); /* Set p[1..n]=1,..n */ void Permutation_permuteRandomly_inline (Permutation me, long from, long to); Permutation Permutation_permuteRandomly (Permutation me, long from, long to); /* Generate a new sequence by permuting the elements from..to */ Permutation Permutation_rotate (Permutation me, long from, long to, long step); void Permutation_swapOneFromRange (Permutation me, long from, long to, long pos, int forbidsame); /* Swap item at pos with one randomly chosen in interval [from,to]. If pos in [from,to] and forbidsame==true then new position may not be equal to pos. */ void Permutation_swapBlocks (Permutation me, long from, long to, long blocksize); /* Swap two blocks */ void Permutation_swapPositions (Permutation me, long i1, long i2); void Permutation_swapNumbers (Permutation me, long i1, long i2); Permutation Permutation_interleave (Permutation me, long from, long to, long blocksize, long offset); Permutation Permutation_permuteBlocksRandomly (Permutation me, long from, long to, long blocksize, int permuteWithinBlocks, int noDoublets); /* Permute blocks of size blocksize randomly. If permuteWithinBlocks=true and noDoublets=true forbid that the last number in a block and the first number in the following block are 'equal modulo blocksize'. */ long Permutation_getValueAtIndex (Permutation me, long i); /* return i > 0 && i < my n ? my p[i] : -1 */ long Permutation_getIndexAtValue (Permutation me, long value); /* Find i for which p[i] = value */ Permutation Permutation_invert (Permutation me); /* */ Permutation Permutation_reverse (Permutation me, long from, long to); /* (n1,n2,...nn) to (nn,...n2,n1) */ void Permutation_next_inline (Permutation me); void Permutation_previous_inline (Permutation me); Permutation Permutations_multiply2 (Permutation me, Permutation thee); Permutation Permutations_multiply (Collection me); #endif /* _Permutation_h_ */ sources_5316/dwsys/regularExp.cpp0000644000176700017670000041204711725413201015722 0ustar paulpaul/*------------------------------------------------------------------------* * static const char CVSID[] = "$Id: regularExp.c,v 1.30 2006/08/13 21:47:45 yooden Exp $"; * `CompileRE', `ExecRE', and `substituteRE' -- regular expression parsing * * This is a HIGHLY ALTERED VERSION of Henry Spencer's `regcomp' and * `regexec' code adapted for NEdit. * * .-------------------------------------------------------------------. * | ORIGINAL COPYRIGHT NOTICE: | * | | * | Copyright (c) 1986 by University of Toronto. | * | Written by Henry Spencer. Not derived from licensed software. | * | | * | Permission is granted to anyone to use this software for any | * | purpose on any computer system, and to redistribute it freely, | * | subject to the following restrictions: | * | | * | 1. The author is not responsible for the consequences of use of | * | this software, no matter how awful, even if they arise | * | from defects in it. | * | | * | 2. The origin of this software must not be misrepresented, either | * | by explicit claim or by omission. | * | | * | 3. Altered versions must be plainly marked as such, and must not | * | be misrepresented as being the original software. | * `-------------------------------------------------------------------' * * This is free software; you can redistribute it and/or modify it under the * terms of the GNU General Public License as published by the Free Software * Foundation; either version 2 of the License, or (at your option) any later * version. In addition, you may distribute version of this program linked to * Motif or Open Motif. See README for details. * * This software is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. * * You should have received a copy of the GNU General Public License along with * software; if not, write to the Free Software Foundation, Inc., 59 Temple * Place, Suite 330, Boston, MA 02111-1307 USA * * * BEWARE that some of this code is subtly aware of the way operator * precedence is structured in regular expressions. Serious changes in * regular-expression syntax might require a total rethink. * -- Henry Spencer * (Yes, it did!) -- Christopher Conrad, Dec. 1999 * * January, 1994, Mark Edel * Consolidated files, changed names of external functions to avoid * potential conflicts with native regcomp and regexec functions, changed * error reporting to NEdit form, added multi-line and reverse searching, * and added \n \t \u \U \l \L. * * June, 1996, Mark Edel * Bug in NEXT macro, didn't work for expressions which compiled to over * 256 bytes. * * December, 1999, Christopher Conrad * Reformatted code for readability, improved error output, added octal and * hexadecimal escapes, added back-references (\1-\9), added positive look * ahead: (?=...), added negative lookahead: (?!...), added non-capturing * parentheses: (?:...), added case insensitive constructs (?i...) and * (?I...), added newline matching constructs (?n...) and (?N...), added * regex comments: (?#...), added shortcut escapes: \d\D\l\L\s\S\w\W\y\Y. * Added "not a word boundary" anchor \B. * * July, 2002, Eddy De Greef * Added look behind, both positive (?<=...) and negative (? format * djmw 20070614 updated from version 1.25 to 1.30 * djmw 20080110 Extra parameter for SubstituteRE to allow error differentiation (not enough memory can be repaired upstream). * Changed Melder_information in reg_error to Melder_error. * djmw 20101119 Changed NULL to '\0' in makeDelimiterTable */ #include #include #include #include #include #include "regularExp.h" #include "melder.h" /* The first byte of the regexp internal `program' is a magic number to help guard against corrupted data; the compiled regex code really begins in the second byte. */ #define MAGIC 0234 /* The "internal use only" fields in `regexp.h' are present to pass info from * `CompileRE' to `ExecRE' which permits the execute phase to run lots faster on * simple cases. They are: * * match_start Character that must begin a match; '\0' if none obvious. * anchor Is the match anchored (at beginning-of-line only)? * * `match_start' and `anchor' permit very fast decisions on suitable starting * points for a match, considerably reducing the work done by ExecRE. */ /* STRUCTURE FOR A REGULAR EXPRESSION (regex) `PROGRAM'. * * This is essentially a linear encoding of a nondeterministic finite-state * machine or NFA (aka syntax charts or `railroad normal form' in parsing * technology). Each node is an opcode plus a NEXT pointer, possibly * followed by operands. NEXT pointers of all nodes except BRANCH implement * concatenation; a NEXT pointer with a BRANCH on both ends of it is * connecting two alternatives. (Here we have one of the subtle syntax * dependencies: an individual BRANCH (as opposed to a collection of them) is * never concatenated with anything because of operator precedence.) The * operand of some types of nodes is a literal string; for others, it is a node * leading into a sub-FSM. In particular, the operand of a BRANCH node is the * first node of the branch. (NB this is _NOT_ a tree structure: the tail of * the branch connects to the thing following the set of BRANCHes.) * * The opcodes are: */ /* DEFINITION VALUE MEANING */ #define END 1 /* End of program. */ /* Zero width positional assertions. */ #define BOL 2 /* Match position at beginning of line. */ #define EOL 3 /* Match position at end of line. */ #define BOWORD 4 /* Match "" representing word delimiter or BOL */ #define EOWORD 5 /* Match "" representing word delimiter or EOL */ #define NOT_BOUNDARY 6 /* Not word boundary (\B, opposite of < and >) */ /* Op codes with null terminated string operands. */ #define EXACTLY 7 /* Match this string. */ #define SIMILAR 8 /* Match this case insensitive string */ #define ANY_OF 9 /* Match any character in the set. */ #define ANY_BUT 10 /* Match any character not in the set. */ /* Op codes to match any character. */ #define ANY 11 /* Match any one character (implements '.') */ #define EVERY 12 /* Same as ANY but matches newline. */ /* Shortcut escapes, \d, \D, \l, \L, \s, \S, \w, \W, \y, \Y. */ #define DIGIT 13 /* Match any digit, i.e. [0123456789] */ #define NOT_DIGIT 14 /* Match any non-digit, i.e. [^0123456789] */ #define LETTER 15 /* Match any letter character [a-zA-Z] */ #define NOT_LETTER 16 /* Match any non-letter character [^a-zA-Z] */ #define SPACE 17 /* Match any whitespace character EXCEPT \n */ #define SPACE_NL 18 /* Match any whitespace character INCLUDING \n */ #define NOT_SPACE 19 /* Match any non-whitespace character */ #define NOT_SPACE_NL 20 /* Same as NOT_SPACE but matches newline. */ #define WORD_CHAR 21 /* Match any word character [a-zA-Z0-9_] */ #define NOT_WORD_CHAR 22 /* Match any non-word character [^a-zA-Z0-9_] */ #define IS_DELIM 23 /* Match any character that's a word delimiter */ #define NOT_DELIM 24 /* Match any character NOT a word delimiter */ /* Quantifier nodes. (Only applied to SIMPLE nodes. Quantifiers applied to non SIMPLE nodes or larger atoms are implemented using complex constructs.)*/ #define STAR 25 /* Match this (simple) thing 0 or more times. */ #define LAZY_STAR 26 /* Minimal matching STAR */ #define QUESTION 27 /* Match this (simple) thing 0 or 1 times. */ #define LAZY_QUESTION 28 /* Minimal matching QUESTION */ #define PLUS 29 /* Match this (simple) thing 1 or more times. */ #define LAZY_PLUS 30 /* Minimal matching PLUS */ #define BRACE 31 /* Match this (simple) thing m to n times. */ #define LAZY_BRACE 32 /* Minimal matching BRACE */ /* Nodes used to build complex constructs. */ #define NOTHING 33 /* Match empty string (always matches) */ #define BRANCH 34 /* Match this alternative, or the next... */ #define BACK 35 /* Always matches, NEXT ptr points backward. */ #define INIT_COUNT 36 /* Initialize {m,n} counter to zero */ #define INC_COUNT 37 /* Increment {m,n} counter by one */ #define TEST_COUNT 38 /* Test {m,n} counter against operand */ /* Back Reference nodes. */ #define BACK_REF 39 /* Match latest matched parenthesized text */ #define BACK_REF_CI 40 /* Case insensitive version of BACK_REF */ #define X_REGEX_BR 41 /* Cross-Regex Back-Ref for syntax highlighting */ #define X_REGEX_BR_CI 42 /* Case insensitive version of X_REGEX_BR_CI */ /* Various nodes used to implement parenthetical constructs. */ #define POS_AHEAD_OPEN 43 /* Begin positive look ahead */ #define NEG_AHEAD_OPEN 44 /* Begin negative look ahead */ #define LOOK_AHEAD_CLOSE 45 /* End positive or negative look ahead */ #define POS_BEHIND_OPEN 46 /* Begin positive look behind */ #define NEG_BEHIND_OPEN 47 /* Begin negative look behind */ #define LOOK_BEHIND_CLOSE 48 /* Close look behind */ #define OPEN 49 /* Open for capturing parentheses. */ /* OPEN+1 is number 1, etc. */ #define CLOSE (OPEN + NSUBEXP) /* Close for capturing parentheses. */ #define LAST_PAREN (CLOSE + NSUBEXP) #if (LAST_PAREN > UCHAR_MAX) #error "Too many parentheses for storage in an unsigned char (LAST_PAREN too big.)" #endif /* The next_ptr () function can consume up to 30% of the time during matching because it is called an immense number of times (an average of 25 next_ptr() calls per match() call was witnessed for Perl syntax highlighting). Therefore it is well worth removing some of the function call overhead by selectively inlining the next_ptr() calls. Moreover, the inlined code can be simplified for matching because one of the tests, only necessary during compilation, can be left out. The net result of using this inlined version at two critical places is a 25% speedup (again, witnesses on Perl syntax highlighting). */ #define NEXT_PTR(in_ptr, out_ptr)\ next_ptr_offset = GET_OFFSET (in_ptr);\ if (next_ptr_offset == 0)\ out_ptr = NULL;\ else {\ if (GET_OP_CODE (in_ptr) == BACK)\ out_ptr = in_ptr - next_ptr_offset;\ else \ out_ptr = in_ptr + next_ptr_offset;\ } /* OPCODE NOTES: ------------ All nodes consist of an 8 bit op code followed by 2 bytes that make up a 16 bit NEXT pointer. Some nodes have a null terminated character string operand following the NEXT pointer. Other nodes may have an 8 bit index operand. The TEST_COUNT node has an index operand followed by a 16 bit test value. The BRACE and LAZY_BRACE nodes have two 16 bit values for min and max but no index value. SIMILAR Operand(s): null terminated string Implements a case insensitive match of a string. Mostly intended for use in syntax highlighting patterns for keywords of languages like FORTRAN and Ada that are case insensitive. The regex text in this node is converted to lower case during regex compile. DIGIT, NOT_DIGIT, LETTER, NOT_LETTER, SPACE, NOT_SPACE, WORD_CHAR, NOT_WORD_CHAR Operand(s): None Implements shortcut escapes \d, \D, \l, \L, \s, \S, \w, \W. The locale aware ANSI functions isdigit(), isalpha(), isalnun(), and isspace() are used to implement these in the hopes of increasing portability. NOT_BOUNDARY Operand(s): None Implements \B as a zero width assertion that the current character is NOT on a word boundary. Word boundaries are defined to be the position between two characters where one of those characters is one of the dynamically defined word delimiters, and the other character is not. IS_DELIM Operand(s): None Implements \y as any character that is one of the dynamically specified word delimiters. NOT_DELIM Operand(s): None Implements \Y as any character that is NOT one of the dynamically specified word delimiters. STAR, PLUS, QUESTION, and complex '*', '+', and '?' Operand(s): None (Note: NEXT pointer is usually zero. The code that processes this node skips over it.) Complex (parenthesized) versions implemented as circular BRANCH structures using BACK. SIMPLE versions (one character per match) are implemented separately for speed and to minimize recursion. BRACE, LAZY_BRACE Operand(s): minimum value (2 bytes), maximum value (2 bytes) Implements the {m,n} construct for atoms that are SIMPLE. BRANCH Operand(s): None The set of branches constituting a single choice are hooked together with their NEXT pointers, since precedence prevents anything being concatenated to any individual branch. The NEXT pointer of the last BRANCH in a choice points to the thing following the whole choice. This is also where the final NEXT pointer of each individual branch points; each branch starts with the operand node of a BRANCH node. BACK Operand(s): None Normal NEXT pointers all implicitly point forward. Back implicitly points backward. BACK exists to make loop structures possible. INIT_COUNT Operand(s): index (1 byte) Initializes the count array element referenced by the index operand. This node is used to build general (i.e. parenthesized) {m,n} constructs. INC_COUNT Operand(s): index (1 byte) Increments the count array element referenced by the index operand. This node is used to build general (i.e. parenthesized) {m,n} constructs. TEST_COUNT Operand(s): index (1 byte), test value (2 bytes) Tests the current value of the count array element specified by the index operand against the test value. If the current value is less than the test value, control passes to the node after that TEST_COUNT node. Otherwise control passes to the node referenced by the NEXT pointer for the TEST_COUNT node. This node is used to build general (i.e. parenthesized) {m,n} constructs. BACK_REF, BACK_REF_CI Operand(s): index (1 byte, value 1-9) Implements back references. This node will attempt to match whatever text was most recently captured by the index'th set of parentheses. BACK_REF_CI is case insensitive version. X_REGEX_BR, X_REGEX_BR_CI (NOT IMPLEMENTED YET) Operand(s): index (1 byte, value 1-9) Implements back references into a previously matched but separate regular expression. This is used by syntax highlighting patterns. This node will attempt to match whatever text was most captured by the index'th set of parentheses of the separate regex passed to ExecRE. X_REGEX_BR_CI is case insensitive version. POS_AHEAD_OPEN, NEG_AHEAD_OPEN, LOOK_AHEAD_CLOSE Operand(s): None Implements positive and negative look ahead. Look ahead is an assertion that something is either there or not there. Once this is determined the regex engine backtracks to where it was just before the look ahead was encountered, i.e. look ahead is a zero width assertion. POS_BEHIND_OPEN, NEG_BEHIND_OPEN, LOOK_BEHIND_CLOSE Operand(s): 2x2 bytes for OPEN (match boundaries), None for CLOSE Implements positive and negative look behind. Look behind is an assertion that something is either there or not there in front of the current position. Look behind is a zero width assertion, with the additional constraint that it must have a bounded length (for complexity and efficiency reasons; note that most other implementation even impose fixed length). OPEN, CLOSE Operand(s): None OPEN + n = Start of parenthesis 'n', CLOSE + n = Close of parenthesis 'n', and are numbered at compile time. */ /* A node is one char of opcode followed by two chars of NEXT pointer plus * any operands. NEXT pointers are stored as two 8-bit pieces, high order * first. The value is a positive offset from the opcode of the node * containing it. An operand, if any, simply follows the node. (Note that * much of the code generation knows about this implicit relationship.) * * Using two bytes for NEXT_PTR_SIZE is vast overkill for most things, * but allows patterns to get big without disasters. */ #define OP_CODE_SIZE 1 #define NEXT_PTR_SIZE 2 #define INDEX_SIZE 1 #define LENGTH_SIZE 4 #define NODE_SIZE (NEXT_PTR_SIZE + OP_CODE_SIZE) #define GET_OP_CODE(p) (*(regularExp_CHAR *)(p)) #define OPERAND(p) ((p) + NODE_SIZE) #define GET_OFFSET(p) ((( *((p) + 1) & 0377) << 8) + (( *((p) + 2)) & 0377)) #define PUT_OFFSET_L(v) (regularExp_CHAR)(((v) >> 8) & 0377) #define PUT_OFFSET_R(v) (regularExp_CHAR) ((v) & 0377) #define GET_LOWER(p) ((( *((p) + NODE_SIZE) & 0377) << 8) + \ (( *((p) + NODE_SIZE+1)) & 0377)) #define GET_UPPER(p) ((( *((p) + NODE_SIZE+2) & 0377) << 8) + \ (( *((p) + NODE_SIZE+3)) & 0377)) /* Utility definitions. */ #define REG_FAIL(m) {*Error_Ptr = (m); return (NULL);} #define IS_QUANTIFIER(c) ((c) == '*' || (c) == '+' || \ (c) == '?' || (c) == Brace_Char) #define SET_BIT(i,n) ((i) |= (1 << ((n) - 1))) #define TEST_BIT(i,n) ((i) & (1 << ((n) - 1))) #define U_CHAR_AT(p) ((unsigned int) *(regularExp_CHAR *)(p)) /* Flags to be passed up and down via function parameters during compile. */ #define WORST 0 /* Worst case. No assumptions can be made.*/ #define HAS_WIDTH 1 /* Known never to match null string. */ #define SIMPLE 2 /* Simple enough to be STAR/PLUS operand. */ #define NO_PAREN 0 /* Only set by initial call to "chunk". */ #define PAREN 1 /* Used for normal capturing parentheses. */ #define NO_CAPTURE 2 /* Non-capturing parentheses (grouping only). */ #define INSENSITIVE 3 /* Case insensitive parenthetical construct */ #define SENSITIVE 4 /* Case sensitive parenthetical construct */ #define NEWLINE 5 /* Construct to match newlines in most cases */ #define NO_NEWLINE 6 /* Construct to match newlines normally */ #define REG_INFINITY 0UL #define REG_ZERO 0UL #define REG_ONE 1UL /* Flags for function shortcut_escape() */ #define CHECK_ESCAPE 0 /* Check an escape sequence for validity only. */ #define CHECK_CLASS_ESCAPE 1 /* Check the validity of an escape within a character class */ #define EMIT_CLASS_BYTES 2 /* Emit equivalent character class bytes, e.g \d=0123456789 */ #define EMIT_NODE 3 /* Emit the appropriate node. */ /* Array sizes for arrays used by function init_ansi_classes. */ #define WHITE_SPACE_SIZE 16 #define ALNUM_CHAR_SIZE 256 /* Number of bytes to offset from the beginning of the regex program to the start of the actual compiled regex code, i.e. skipping over the MAGIC number and the two counters at the front. */ #define REGEX_START_OFFSET 3 #define MAX_COMPILED_SIZE 32767UL /* Largest size a compiled regex can be. Probably could be 65535UL. */ /* Global work variables for `CompileRE'. */ static regularExp_CHAR *Reg_Parse; /* Input scan ptr (scans user's regex) */ static int Total_Paren; /* Parentheses, (), counter. */ static int Num_Braces; /* Number of general {m,n} constructs. {m,n} quantifiers of SIMPLE atoms are not included in this count. */ static int Closed_Parens; /* Bit flags indicating () closure. */ static int Paren_Has_Width; /* Bit flags indicating ()'s that are known to not match the empty string */ static regularExp_CHAR Compute_Size; /* Address of this used as flag. */ static regularExp_CHAR *Code_Emit_Ptr; /* When Code_Emit_Ptr is set to &Compute_Size no code is emitted. Instead, the size of code that WOULD have been generated is accumulated in Reg_Size. Otherwise, Code_Emit_Ptr points to where compiled regex code is to be written. */ static unsigned long Reg_Size; /* Size of compiled regex code. */ static const wchar **Error_Ptr; /* Place to store error messages so they can be returned by `CompileRE' */ static wchar Error_Text [128];/* Sting to build error messages in. */ static regularExp_CHAR White_Space [WHITE_SPACE_SIZE]; /* Arrays used by */ static regularExp_CHAR Word_Char [ALNUM_CHAR_SIZE]; /* functions */ static regularExp_CHAR Letter_Char [ALNUM_CHAR_SIZE]; /* init_ansi_classes () */ /* and shortcut_escape (). */ static regularExp_CHAR ASCII_Digits [] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' }; /* Same for all */ /* locales. */ static int Is_Case_Insensitive; static int Match_Newline; static int Enable_Counting_Quantifier = 1; static regularExp_CHAR Brace_Char; static regularExp_CHAR Default_Meta_Char [] = { '{', '.', '*', '+', '?', '[', '(', '|', ')', '^', '<', '>', '$' }; static regularExp_CHAR *Meta_Char; typedef struct { long lower; long upper; } len_range; /* Forward declarations for functions used by `CompileRE'. */ static regularExp_CHAR *alternative (int *flag_param, len_range *range_param); static regularExp_CHAR *back_ref (regularExp_CHAR *c, int *flag_param, int emit); static regularExp_CHAR *chunk (int paren, int *flag_param, len_range *range_param); static void emit_byte (regularExp_CHAR c); static void emit_class_byte (regularExp_CHAR c); static regularExp_CHAR *emit_node (int op_code); static regularExp_CHAR *emit_special (regularExp_CHAR op_code, unsigned long test_val, int index); static regularExp_CHAR literal_escape (regularExp_CHAR c); static regularExp_CHAR numeric_escape (regularExp_CHAR c, regularExp_CHAR **parse); static regularExp_CHAR *atom (int *flag_param, len_range *range_param); static void reg_error (const wchar *str); static regularExp_CHAR *insert (regularExp_CHAR op, regularExp_CHAR *opnd, long min, long max, int index); static regularExp_CHAR *next_ptr (regularExp_CHAR *ptr); static void offset_tail (regularExp_CHAR *ptr, int offset, regularExp_CHAR *val); static void branch_tail (regularExp_CHAR *ptr, int offset, regularExp_CHAR *val); static regularExp_CHAR *piece (int *flag_param, len_range *range_param); static void tail (regularExp_CHAR *search_from, regularExp_CHAR *point_t); static regularExp_CHAR *shortcut_escape (regularExp_CHAR c, int *flag_param, int emit); static int init_ansi_classes (void); /*----------------------------------------------------------------------* * CompileRE * * Compiles a regular expression into the internal format used by * `ExecRE'. * * The default behaviour wrt. case sensitivity and newline matching can * be controlled through the defaultFlags argument (Markus Schwarzenberg). * Future extensions are possible by using other flag bits. * Note that currently only the case sensitivity flag is effectively used. * * Beware that the optimization and preparation code in here knows about * some of the structure of the compiled regexp. *----------------------------------------------------------------------*/ regexp *CompileRE (const regularExp_CHAR *exp, const wchar **errorText, int defaultFlags) { register regexp *comp_regex = NULL; register regularExp_CHAR *scan; int flags_local, pass; len_range range_local; if (Enable_Counting_Quantifier) { Brace_Char = '{'; Meta_Char = &Default_Meta_Char [0]; } else { Brace_Char = '*'; /* Bypass the '{' in */ Meta_Char = &Default_Meta_Char [1]; /* Default_Meta_Char */ } /* Set up errorText to receive failure reports. */ Error_Ptr = errorText; *Error_Ptr = L""; if (exp == NULL) { REG_FAIL (L"NULL argument, `CompileRE\'"); } /* Initialize arrays used by function `shortcut_escape'. */ if (!init_ansi_classes ()) { REG_FAIL (L"internal error #1, `CompileRE\'"); } Code_Emit_Ptr = &Compute_Size; Reg_Size = 0UL; /* We can't allocate space until we know how big the compiled form will be, but we can't compile it (and thus know how big it is) until we've got a place to put the code. So we cheat: we compile it twice, once with code generation turned off and size counting turned on, and once "for real". This also means that we don't allocate space until we are sure that the thing really will compile successfully, and we never have to move the code and thus invalidate pointers into it. (Note that it has to be in one piece because free() must be able to free it all.) */ for (pass = 1; pass <= 2; pass++) { /*-------------------------------------------* * FIRST PASS: Determine size and legality. * * SECOND PASS: Emit code. * *-------------------------------------------*/ /* Schwarzenberg: * If defaultFlags = 0 use standard defaults: * Is_Case_Insensitive: Case sensitive is the default * Match_Newline: Newlines are NOT matched by default * in character classes */ Is_Case_Insensitive = ( (defaultFlags & REDFLT_CASE_INSENSITIVE) ? 1 : 0); Match_Newline = 0; /* ((defaultFlags & REDFLT_MATCH_NEWLINE) ? 1 : 0); Currently not used. Uncomment if needed. */ Reg_Parse = (regularExp_CHAR *) exp; Total_Paren = 1; Num_Braces = 0; Closed_Parens = 0; Paren_Has_Width = 0; emit_byte (MAGIC); emit_byte ('%'); /* Placeholder for num of capturing parentheses. */ emit_byte ('%'); /* Placeholder for num of general {m,n} constructs. */ if (chunk (NO_PAREN, &flags_local, &range_local) == NULL) { return (NULL); /* Something went wrong */ } if (pass == 1) { if (Reg_Size >= MAX_COMPILED_SIZE) { /* Too big for NEXT pointers NEXT_PTR_SIZE bytes long to span. This is a real issue since the first BRANCH node usually points to the end of the compiled regex code. */ swprintf ( (wchar *) Error_Text, 128, L"regexp > %lu bytes", MAX_COMPILED_SIZE); REG_FAIL (Error_Text); } /* Allocate memory. */ comp_regex = (regexp *) malloc (sizeof (regexp) + Reg_Size * sizeof (wchar_t)); if (comp_regex == NULL) { REG_FAIL (L"out of memory in `CompileRE\'"); } Code_Emit_Ptr = (regularExp_CHAR *) comp_regex->program; } } comp_regex->program [1] = (regularExp_CHAR) Total_Paren - 1; comp_regex->program [2] = (regularExp_CHAR) Num_Braces; /*----------------------------------------* * Dig out information for optimizations. * *----------------------------------------*/ comp_regex->match_start = '\0'; /* Worst-case defaults. */ comp_regex->anchor = 0; /* First BRANCH. */ scan = (regularExp_CHAR *) (comp_regex->program + REGEX_START_OFFSET); if (GET_OP_CODE (next_ptr (scan)) == END) { /* Only one top-level choice. */ scan = OPERAND (scan); /* Starting-point info. */ if (GET_OP_CODE (scan) == EXACTLY) { comp_regex->match_start = *OPERAND (scan); } else if (PLUS <= GET_OP_CODE (scan) && GET_OP_CODE (scan) <= LAZY_PLUS) { /* Allow x+ or x+? at the start of the regex to be optimized. */ if (GET_OP_CODE (scan + NODE_SIZE) == EXACTLY) { comp_regex->match_start = *OPERAND (scan + NODE_SIZE); } } else if (GET_OP_CODE (scan) == BOL) { comp_regex->anchor++; } } return (comp_regex); } /*----------------------------------------------------------------------* * chunk * * * * Process main body of regex or process a parenthesized "thing". * * * * Caller must absorb opening parenthesis. * * * * Combining parenthesis handling with the base level of regular * * expression is a trifle forced, but the need to tie the tails of the * * branches to what follows makes it hard to avoid. * *----------------------------------------------------------------------*/ static regularExp_CHAR *chunk (int paren, int *flag_param, len_range *range_param) { register regularExp_CHAR *ret_val = NULL; register regularExp_CHAR *this_branch; register regularExp_CHAR *ender = NULL; register int this_paren = 0; int flags_local, first = 1, zero_width, i; int old_sensitive = Is_Case_Insensitive; int old_newline = Match_Newline; len_range range_local; int look_only = 0; regularExp_CHAR *emit_look_behind_bounds = NULL; *flag_param = HAS_WIDTH; /* Tentatively. */ range_param->lower = 0; /* Idem */ range_param->upper = 0; /* Make an OPEN node, if parenthesized. */ if (paren == PAREN) { if (Total_Paren >= NSUBEXP) { swprintf ( (wchar *) Error_Text, 128, L"number of ()'s > %d", (int) NSUBEXP); REG_FAIL (Error_Text); } this_paren = Total_Paren; Total_Paren++; ret_val = emit_node (OPEN + this_paren); } else if (paren == POS_AHEAD_OPEN || paren == NEG_AHEAD_OPEN) { *flag_param = WORST; /* Look ahead is zero width. */ look_only = 1; ret_val = emit_node (paren); } else if (paren == POS_BEHIND_OPEN || paren == NEG_BEHIND_OPEN) { *flag_param = WORST; /* Look behind is zero width. */ look_only = 1; /* We'll overwrite the zero length later on, so we save the ptr */ ret_val = emit_special (paren, 0, 0); emit_look_behind_bounds = ret_val + NODE_SIZE; } else if (paren == INSENSITIVE) { Is_Case_Insensitive = 1; } else if (paren == SENSITIVE) { Is_Case_Insensitive = 0; } else if (paren == NEWLINE) { Match_Newline = 1; } else if (paren == NO_NEWLINE) { Match_Newline = 0; } /* Pick up the branches, linking them together. */ do { this_branch = alternative (&flags_local, &range_local); if (this_branch == NULL) { return (NULL); } if (first) { first = 0; *range_param = range_local; if (ret_val == NULL) { ret_val = this_branch; } } else if (range_param->lower >= 0) { if (range_local.lower >= 0) { if (range_local.lower < range_param->lower) { range_param->lower = range_local.lower; } if (range_local.upper > range_param->upper) { range_param->upper = range_local.upper; } } else { range_param->lower = -1; /* Branches have different lengths */ range_param->upper = -1; } } tail (ret_val, this_branch); /* Connect BRANCH -> BRANCH. */ /* If any alternative could be zero width, consider the whole parenthisized thing to be zero width. */ if (! (flags_local & HAS_WIDTH)) { *flag_param &= ~HAS_WIDTH; } /* Are there more alternatives to process? */ if (*Reg_Parse != '|') { break; } Reg_Parse++; } while (1); /* Make a closing node, and hook it on the end. */ if (paren == PAREN) { ender = emit_node (CLOSE + this_paren); } else if (paren == NO_PAREN) { ender = emit_node (END); } else if (paren == POS_AHEAD_OPEN || paren == NEG_AHEAD_OPEN) { ender = emit_node (LOOK_AHEAD_CLOSE); } else if (paren == POS_BEHIND_OPEN || paren == NEG_BEHIND_OPEN) { ender = emit_node (LOOK_BEHIND_CLOSE); } else { ender = emit_node (NOTHING); } tail (ret_val, ender); /* Hook the tails of the branch alternatives to the closing node. */ for (this_branch = ret_val; this_branch != NULL;) { branch_tail (this_branch, NODE_SIZE, ender); this_branch = next_ptr (this_branch); } /* Check for proper termination. */ if (paren != NO_PAREN && *Reg_Parse++ != ')') { REG_FAIL (L"missing right parenthesis \')\'"); } else if (paren == NO_PAREN && *Reg_Parse != '\0') { if (*Reg_Parse == ')') { REG_FAIL (L"missing left parenthesis \'(\'"); } else { REG_FAIL (L"junk on end"); /* "Can't happen" - NOTREACHED */ } } /* Check whether look behind has a fixed size */ if (emit_look_behind_bounds) { if (range_param->lower < 0) { REG_FAIL (L"look-behind does not have a bounded size"); } if (range_param->upper > 65535L) { REG_FAIL (L"max. look-behind size is too large (>65535)") } if (Code_Emit_Ptr != &Compute_Size) { *emit_look_behind_bounds++ = PUT_OFFSET_L (range_param->lower); *emit_look_behind_bounds++ = PUT_OFFSET_R (range_param->lower); *emit_look_behind_bounds++ = PUT_OFFSET_L (range_param->upper); *emit_look_behind_bounds = PUT_OFFSET_R (range_param->upper); } } /* For look ahead/behind, the length must be set to zero again */ if (look_only) { range_param->lower = 0; range_param->upper = 0; } zero_width = 0; /* Set a bit in Closed_Parens to let future calls to function `back_ref' know that we have closed this set of parentheses. */ if (paren == PAREN && this_paren <= (int) sizeof (Closed_Parens) * CHAR_BIT) { SET_BIT (Closed_Parens, this_paren); /* Determine if a parenthesized expression is modified by a quantifier that can have zero width. */ if (* (Reg_Parse) == '?' || * (Reg_Parse) == '*') { zero_width++; } else if (* (Reg_Parse) == '{' && Brace_Char == '{') { if (* (Reg_Parse + 1) == ',' || * (Reg_Parse + 1) == '}') { zero_width++; } else if (* (Reg_Parse + 1) == '0') { i = 2; while (* (Reg_Parse + i) == '0') { i++; } if (* (Reg_Parse + i) == ',') { zero_width++; } } } } /* If this set of parentheses is known to never match the empty string, set a bit in Paren_Has_Width to let future calls to function back_ref know that this set of parentheses has non-zero width. This will allow star (*) or question (?) quantifiers to be aplied to a back-reference that refers to this set of parentheses. */ if ( (*flag_param & HAS_WIDTH) && paren == PAREN && !zero_width && this_paren <= (int) (sizeof (Paren_Has_Width) * CHAR_BIT)) { SET_BIT (Paren_Has_Width, this_paren); } Is_Case_Insensitive = old_sensitive; Match_Newline = old_newline; return (ret_val); } /*----------------------------------------------------------------------* * alternative * * Processes one alternative of an '|' operator. Connects the NEXT * pointers of each regex atom together sequentialy. *----------------------------------------------------------------------*/ static regularExp_CHAR *alternative (int *flag_param, len_range *range_param) { register regularExp_CHAR *ret_val; register regularExp_CHAR *chain; register regularExp_CHAR *latest; int flags_local; len_range range_local; *flag_param = WORST; /* Tentatively. */ range_param->lower = 0; /* Idem */ range_param->upper = 0; ret_val = emit_node (BRANCH); chain = NULL; /* Loop until we hit the start of the next alternative, the end of this set of alternatives (end of parentheses), or the end of the regex. */ while (*Reg_Parse != '|' && *Reg_Parse != ')' && *Reg_Parse != '\0') { latest = piece (&flags_local, &range_local); if (latest == NULL) { return (NULL); /* Something went wrong. */ } *flag_param |= flags_local & HAS_WIDTH; if (range_local.lower < 0) { /* Not a fixed length */ range_param->lower = -1; range_param->upper = -1; } else if (range_param->lower >= 0) { range_param->lower += range_local.lower; range_param->upper += range_local.upper; } if (chain != NULL) { /* Connect the regex atoms together sequentialy. */ tail (chain, latest); } chain = latest; } if (chain == NULL) { /* Loop ran zero times. */ (void) emit_node (NOTHING); } return (ret_val); } /*----------------------------------------------------------------------* * piece - something followed by possible '*', '+', '?', or "{m,n}" * * Note that the branching code sequences used for the general cases of * *, +. ?, and {m,n} are somewhat optimized: they use the same * NOTHING node as both the endmarker for their branch list and the * body of the last branch. It might seem that this node could be * dispensed with entirely, but the endmarker role is not redundant. *----------------------------------------------------------------------*/ static regularExp_CHAR *piece (int *flag_param, len_range *range_param) { register regularExp_CHAR *ret_val; register regularExp_CHAR *next; register regularExp_CHAR op_code; unsigned long min_max [2] = {REG_ZERO, REG_INFINITY}; int flags_local, i, brace_present = 0; int lazy = 0, comma_present = 0; int digit_present [2] = {0, 0}; len_range range_local; ret_val = atom (&flags_local, &range_local); if (ret_val == NULL) { return (NULL); /* Something went wrong. */ } op_code = *Reg_Parse; if (!IS_QUANTIFIER (op_code)) { *flag_param = flags_local; *range_param = range_local; return (ret_val); } else if (op_code == '{') { /* {n,m} quantifier present */ brace_present++; Reg_Parse++; /* This code will allow specifying a counting range in any of the following forms: {m,n} between m and n. {,n} same as {0,n} or between 0 and infinity. {m,} same as {m,0} or between m and infinity. {m} same as {m,m} or exactly m. {,} same as {0,0} or between 0 and infinity or just '*'. {} same as {0,0} or between 0 and infinity or just '*'. Note that specifying a max of zero, {m,0} is not allowed in the regex itself, but it is implemented internally that way to support '*', '+', and {min,} constructs and signals an unlimited number. */ for (i = 0; i < 2; i++) { /* Look for digits of number and convert as we go. The numeric maximum value for max and min of 65,535 is due to using 2 bytes to store each value in the compiled regex code. */ while (isdigit (*Reg_Parse)) { /* (6553 * 10 + 6) > 65535 (16 bit max) */ if ( (min_max [i] == 6553UL && (*Reg_Parse - '0') <= 5) || (min_max [i] <= 6552UL)) { min_max [i] = (min_max [i] * 10UL) + (unsigned long) (*Reg_Parse - '0'); Reg_Parse++; digit_present [i]++; } else { if (i == 0) { swprintf ( (wchar *) Error_Text, 128, L"min operand of {%lu%c,???} > 65535", min_max [0], *Reg_Parse); } else { swprintf ( (wchar *) Error_Text, 128, L"max operand of {%lu,%lu%c} > 65535", min_max [0], min_max [1], *Reg_Parse); } REG_FAIL (Error_Text); } } if (!comma_present && *Reg_Parse == ',') { comma_present++; Reg_Parse++; } } /* A max of zero cannot be specified directly in the regex since it would signal a max of infinity. This code specifically disallows `{0,0}', `{,0}', and `{0}' which really means nothing to humans but would be interpreted as `{0,infinity}' or `*' if we didn't make this check. */ if (digit_present [0] && (min_max [0] == REG_ZERO) && !comma_present) { REG_FAIL (L"{0} is an invalid range"); } else if (digit_present [0] && (min_max [0] == REG_ZERO) && digit_present [1] && (min_max [1] == REG_ZERO)) { REG_FAIL (L"{0,0} is an invalid range"); } else if (digit_present [1] && (min_max [1] == REG_ZERO)) { if (digit_present [0]) { swprintf ( (wchar *) Error_Text, 128, L"{%lu,0} is an invalid range", min_max [0]); REG_FAIL (Error_Text); } else { REG_FAIL (L"{,0} is an invalid range"); } } if (!comma_present) { min_max [1] = min_max [0]; } /* {x} means {x,x} */ if (*Reg_Parse != '}') { REG_FAIL (L"{m,n} specification missing right \'}\'"); } else if (min_max [1] != REG_INFINITY && min_max [0] > min_max [1]) { /* Disallow a backward range. */ swprintf ( (wchar *) Error_Text, 128, L"{%lu,%lu} is an invalid range", min_max [0], min_max [1]); REG_FAIL (Error_Text); } } Reg_Parse++; /* Check for a minimal matching (non-greedy or "lazy") specification. */ if (*Reg_Parse == '?') { lazy = 1; Reg_Parse++; } /* Avoid overhead of counting if possible */ if (op_code == '{') { if (min_max [0] == REG_ZERO && min_max [1] == REG_INFINITY) { op_code = '*'; } else if (min_max [0] == REG_ONE && min_max [1] == REG_INFINITY) { op_code = '+'; } else if (min_max [0] == REG_ZERO && min_max [1] == REG_ONE) { op_code = '?'; } else if (min_max [0] == REG_ONE && min_max [1] == REG_ONE) { /* "x{1,1}" is the same as "x". No need to pollute the compiled regex with such nonsense. */ *flag_param = flags_local; *range_param = range_local; return (ret_val); } else if (Num_Braces > (int) UCHAR_MAX) { swprintf ( (wchar *) Error_Text, 128, L"number of {m,n} constructs > %d", UCHAR_MAX); REG_FAIL (Error_Text); } } if (op_code == '+') { min_max [0] = REG_ONE; } if (op_code == '?') { min_max [1] = REG_ONE; } /* It is dangerous to apply certain quantifiers to a possibly zero width item. */ if (! (flags_local & HAS_WIDTH)) { if (brace_present) { swprintf ( (wchar *) Error_Text, 128, L"{%lu,%lu} operand could be empty", min_max [0], min_max [1]); } else { swprintf ( (wchar *) Error_Text, 128, L"%c operand could be empty", op_code); } REG_FAIL (Error_Text); } *flag_param = (min_max [0] > REG_ZERO) ? (WORST | HAS_WIDTH) : WORST; if (range_local.lower >= 0) { if (min_max[1] != REG_INFINITY) { range_param->lower = range_local.lower * min_max[0]; range_param->upper = range_local.upper * min_max[1]; } else { range_param->lower = -1; /* Not a fixed-size length */ range_param->upper = -1; } } else { range_param->lower = -1; /* Not a fixed-size length */ range_param->upper = -1; } /*---------------------------------------------------------------------* * Symbol Legend For Node Structure Diagrams *---------------------------------------------------------------------* * (...) = general grouped thing * B = (B)ranch, K = bac(K), N = (N)othing * I = (I)nitialize count, C = Increment (C)ount * T~m = (T)est against mini(m)um- go to NEXT pointer if >= operand * T~x = (T)est against ma(x)imum- go to NEXT pointer if >= operand * '~' = NEXT pointer, \___| = forward pointer, |___/ = Backward pointer *---------------------------------------------------------------------*/ if (op_code == '*' && (flags_local & SIMPLE)) { insert ( (lazy ? LAZY_STAR : STAR), ret_val, 0UL, 0UL, 0); } else if (op_code == '+' && (flags_local & SIMPLE)) { insert (lazy ? LAZY_PLUS : PLUS, ret_val, 0UL, 0UL, 0); } else if (op_code == '?' && (flags_local & SIMPLE)) { insert (lazy ? LAZY_QUESTION : QUESTION, ret_val, 0UL, 0UL, 0); } else if (op_code == '{' && (flags_local & SIMPLE)) { insert (lazy ? LAZY_BRACE : BRACE, ret_val, min_max [0], min_max [1], 0); } else if ( (op_code == '*' || op_code == '+') && lazy) { /* Node structure for (x)*? Node structure for (x)+? construct. * construct. (Same as (x)*? except for initial * forward jump into parenthesis.) * * ___6____ * _______5_______ /________|______ * | _4__ 1_\ /| ____ | _\ * |/ | / |\ / |/ | | / |\ * B~ N~ B~ (...)~ K~ N~ N~ B~ N~ B~ (...)~ K~ N~ * \ \___2_______| \ \___________| * \_____3_______| \_____________| * */ tail (ret_val, emit_node (BACK)); /* 1 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 2,4 */ (void) insert (NOTHING, ret_val, 0UL, 0UL, 0); /* 3 */ next = emit_node (NOTHING); /* 2,3 */ offset_tail (ret_val, NODE_SIZE, next); /* 2 */ tail (ret_val, next); /* 3 */ insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 4,5 */ tail (ret_val, ret_val + (2 * NODE_SIZE)); /* 4 */ offset_tail (ret_val, 3 * NODE_SIZE, ret_val); /* 5 */ if (op_code == '+') { insert (NOTHING, ret_val, 0UL, 0UL, 0); /* 6 */ tail (ret_val, ret_val + (4 * NODE_SIZE)); /* 6 */ } } else if (op_code == '*') { /* Node structure for (x)* construct. * ____1_____ * | \ * B~ (...)~ K~ B~ N~ * \ \_|2 |\_| * \__3_______| 4 */ insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 1,3 */ offset_tail (ret_val, NODE_SIZE, emit_node (BACK)); /* 2 */ offset_tail (ret_val, NODE_SIZE, ret_val); /* 1 */ tail (ret_val, emit_node (BRANCH)); /* 3 */ tail (ret_val, emit_node (NOTHING)); /* 4 */ } else if (op_code == '+') { /* Node structure for (x)+ construct. * * ____2_____ * | \ * (...)~ B~ K~ B~ N~ * \_|\____|\_| * 1 3 4 */ next = emit_node (BRANCH); /* 1 */ tail (ret_val, next); /* 1 */ tail (emit_node (BACK), ret_val); /* 2 */ tail (next, emit_node (BRANCH)); /* 3 */ tail (ret_val, emit_node (NOTHING)); /* 4 */ } else if (op_code == '?' && lazy) { /* Node structure for (x)?? construct. * _4__ 1_ * / | / | * B~ N~ B~ (...)~ N~ * \ \___2____| * \_____3____| */ (void) insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 2,4 */ (void) insert (NOTHING, ret_val, 0UL, 0UL, 0); /* 3 */ next = emit_node (NOTHING); /* 1,2,3 */ offset_tail (ret_val, 2 * NODE_SIZE, next); /* 1 */ offset_tail (ret_val, NODE_SIZE, next); /* 2 */ tail (ret_val, next); /* 3 */ insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 4 */ tail (ret_val, (ret_val + (2 * NODE_SIZE))); /* 4 */ } else if (op_code == '?') { /* Node structure for (x)? construct. * ___1____ _2 * / |/ | * B~ (...)~ B~ N~ * \__3_| */ insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 1 */ tail (ret_val, emit_node (BRANCH)); /* 1 */ next = emit_node (NOTHING); /* 2,3 */ tail (ret_val, next); /* 2 */ offset_tail (ret_val, NODE_SIZE, next); /* 3 */ } else if (op_code == '{' && min_max [0] == min_max [1]) { /* Node structure for (x){m}, (x){m}?, (x){m,m}, or (x){m,m}? constructs. * Note that minimal and maximal matching mean the same thing when we * specify the minimum and maximum to be the same value. * _______3_____ * | 1_ _2 \ * | / |/ | \ * I~ (...)~ C~ T~m K~ N~ * \_| \_____| * 5 4 */ tail (ret_val, emit_special (INC_COUNT, 0UL, Num_Braces)); /* 1 */ tail (ret_val, emit_special (TEST_COUNT, min_max [0], Num_Braces));/* 2 */ tail (emit_node (BACK), ret_val); /* 3 */ tail (ret_val, emit_node (NOTHING)); /* 4 */ next = insert (INIT_COUNT, ret_val, 0UL, 0UL, Num_Braces); /* 5 */ tail (ret_val, next); /* 5 */ Num_Braces++; } else if (op_code == '{' && lazy) { if (min_max [0] == REG_ZERO && min_max [1] != REG_INFINITY) { /* Node structure for (x){0,n}? or {,n}? construct. * _________3____________ * 8_| _4__ 1_ _2 \ * / |/ | / |/ | \ * I~ B~ N~ B~ (...)~ C~ T~x K~ N~ * \ \ \__7__| * \ \_________6_______| * \______5____________| */ tail (ret_val, emit_special (INC_COUNT, 0UL, Num_Braces)); /* 1 */ next = emit_special (TEST_COUNT, min_max [0], Num_Braces); /* 2,7 */ tail (ret_val, next); /* 2 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, Num_Braces); /* 4,6 */ (void) insert (NOTHING, ret_val, 0UL, 0UL, Num_Braces); /* 5 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, Num_Braces); /* 3,4,8 */ tail (emit_node (BACK), ret_val); /* 3 */ tail (ret_val, ret_val + (2 * NODE_SIZE)); /* 4 */ next = emit_node (NOTHING); /* 5,6,7 */ offset_tail (ret_val, NODE_SIZE, next); /* 5 */ offset_tail (ret_val, 2 * NODE_SIZE, next); /* 6 */ offset_tail (ret_val, 3 * NODE_SIZE, next); /* 7 */ next = insert (INIT_COUNT, ret_val, 0UL, 0UL, Num_Braces); /* 8 */ tail (ret_val, next); /* 8 */ } else if (min_max [0] > REG_ZERO && min_max [1] == REG_INFINITY) { /* Node structure for (x){m,}? construct. * ______8_________________ * | _______3_____ \ * | _7__ | 1_ _2 \ \ * |/ | | / |/ | \ \ * I~ B~ N~ B~ (...)~ C~ T~m K~ K~ N~ * \_____\__\_| \_4___| | * 9 \ \_________5__________| * \_______6______________| */ tail (ret_val, emit_special (INC_COUNT, 0UL, Num_Braces)); /* 1 */ next = emit_special (TEST_COUNT, min_max [0], Num_Braces); /* 2,4 */ tail (ret_val, next); /* 2 */ tail (emit_node (BACK), ret_val); /* 3 */ tail (ret_val, emit_node (BACK)); /* 4 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 5,7 */ (void) insert (NOTHING, ret_val, 0UL, 0UL, 0); /* 6 */ next = emit_node (NOTHING); /* 5,6 */ offset_tail (ret_val, NODE_SIZE, next); /* 5 */ tail (ret_val, next); /* 6 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 7,8 */ tail (ret_val, ret_val + (2 * NODE_SIZE)); /* 7 */ offset_tail (ret_val, 3 * NODE_SIZE, ret_val); /* 8 */ (void) insert (INIT_COUNT, ret_val, 0UL, 0UL, Num_Braces); /* 9 */ tail (ret_val, ret_val + INDEX_SIZE + (4 * NODE_SIZE)); /* 9 */ } else { /* Node structure for (x){m,n}? construct. * ______9_____________________ * | _____________3___ \ * | __8_ | 1_ _2 \ \ * |/ | | / |/ | \ \ * I~ B~ N~ B~ (...)~ C~ T~x T~m K~ K~ N~ * \_____\__\_| \ \__4__| | * 10 \ \ \_7_________| * \ \_________6_____________| * \_______5_________________| */ tail (ret_val, emit_special (INC_COUNT, 0UL, Num_Braces)); /* 1 */ next = emit_special (TEST_COUNT, min_max [1], Num_Braces); /* 2,7 */ tail (ret_val, next); /* 2 */ next = emit_special (TEST_COUNT, min_max [0], Num_Braces); /* 4 */ tail (emit_node (BACK), ret_val); /* 3 */ tail (next, emit_node (BACK)); /* 4 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 6,8 */ (void) insert (NOTHING, ret_val, 0UL, 0UL, 0); /* 5 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 8,9 */ next = emit_node (NOTHING); /* 5,6,7 */ offset_tail (ret_val, NODE_SIZE, next); /* 5 */ offset_tail (ret_val, 2 * NODE_SIZE, next); /* 6 */ offset_tail (ret_val, 3 * NODE_SIZE, next); /* 7 */ tail (ret_val, ret_val + (2 * NODE_SIZE)); /* 8 */ offset_tail (next, -NODE_SIZE, ret_val); /* 9 */ insert (INIT_COUNT, ret_val, 0UL, 0UL, Num_Braces); /* 10 */ tail (ret_val, ret_val + INDEX_SIZE + (4 * NODE_SIZE)); /* 10 */ } Num_Braces++; } else if (op_code == '{') { if (min_max [0] == REG_ZERO && min_max [1] != REG_INFINITY) { /* Node structure for (x){0,n} or (x){,n} construct. * * ___3____________ * | 1_ _2 \ 5_ * | / |/ | \ / | * I~ B~ (...)~ C~ T~x K~ B~ N~ * \_|\ \_6___|__| * 7 \________4________| */ tail (ret_val, emit_special (INC_COUNT, 0UL, Num_Braces)); /* 1 */ next = emit_special (TEST_COUNT, min_max [1], Num_Braces); /* 2,6 */ tail (ret_val, next); /* 2 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 3,4,7 */ tail (emit_node (BACK), ret_val); /* 3 */ next = emit_node (BRANCH); /* 4,5 */ tail (ret_val, next); /* 4 */ tail (next, emit_node (NOTHING)); /* 5,6 */ offset_tail (ret_val, NODE_SIZE, next); /* 6 */ next = insert (INIT_COUNT, ret_val, 0UL, 0UL, Num_Braces); /* 7 */ tail (ret_val, next); /* 7 */ } else if (min_max [0] > REG_ZERO && min_max [1] == REG_INFINITY) { /* Node structure for (x){m,} construct. * __________4________ * | __3__________ \ * _|___| 1_ _2 \ \ _7 * / | 8 | / |/ | \ \ / | * I~ B~ (...)~ C~ T~m K~ K~ B~ N~ * \ \_5___| | * \__________6__________| */ tail (ret_val, emit_special (INC_COUNT, 0UL, Num_Braces)); /* 1 */ next = emit_special (TEST_COUNT, min_max [0], Num_Braces); /* 2 */ tail (ret_val, next); /* 2 */ tail (emit_node (BACK), ret_val); /* 3 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 4,6 */ next = emit_node (BACK); /* 4 */ tail (next, ret_val); /* 4 */ offset_tail (ret_val, NODE_SIZE, next); /* 5 */ tail (ret_val, emit_node (BRANCH)); /* 6 */ tail (ret_val, emit_node (NOTHING)); /* 7 */ insert (INIT_COUNT, ret_val, 0UL, 0UL, Num_Braces); /* 8 */ tail (ret_val, ret_val + INDEX_SIZE + (2 * NODE_SIZE)); /* 8 */ } else { /* Node structure for (x){m,n} construct. * _____6________________ * | _____________3___ \ * 9_|__| 1_ _2 \ \ _8 * / | | / |/ | \ \ / | * I~ B~ (...)~ C~ T~x T~m K~ K~ B~ N~ * \ \ \__4__| | | * \ \_7_________|__| * \_________5_____________| */ tail (ret_val, emit_special (INC_COUNT, 0UL, Num_Braces)); /* 1 */ next = emit_special (TEST_COUNT, min_max [1], Num_Braces); /* 2,4 */ tail (ret_val, next); /* 2 */ next = emit_special (TEST_COUNT, min_max [0], Num_Braces); /* 4 */ tail (emit_node (BACK), ret_val); /* 3 */ tail (next, emit_node (BACK)); /* 4 */ (void) insert (BRANCH, ret_val, 0UL, 0UL, 0); /* 5,6 */ next = emit_node (BRANCH); /* 5,8 */ tail (ret_val, next); /* 5 */ offset_tail (next, -NODE_SIZE, ret_val); /* 6 */ next = emit_node (NOTHING); /* 7,8 */ offset_tail (ret_val, NODE_SIZE, next); /* 7 */ offset_tail (next, -NODE_SIZE, next); /* 8 */ (void) insert (INIT_COUNT, ret_val, 0UL, 0UL, Num_Braces); /* 9 */ tail (ret_val, ret_val + INDEX_SIZE + (2 * NODE_SIZE)); /* 9 */ } Num_Braces++; } else { /* We get here if the IS_QUANTIFIER macro is not coordinated properly with this function. */ REG_FAIL (L"internal error #2, `piece\'"); } if (IS_QUANTIFIER (*Reg_Parse)) { if (op_code == '{') { swprintf ( (wchar *) Error_Text, 128, L"nested quantifiers, {m,n}%c", *Reg_Parse); } else { swprintf ( (wchar *) Error_Text, 128, L"nested quantifiers, %c%c", op_code, *Reg_Parse); } REG_FAIL (Error_Text); } return (ret_val); } /*----------------------------------------------------------------------* * atom * * Process one regex item at the lowest level * * OPTIMIZATION: Lumps a continuous sequence of ordinary characters * together so that it can turn them into a single EXACTLY node, which * is smaller to store and faster to run. *----------------------------------------------------------------------*/ static regularExp_CHAR *atom (int *flag_param, len_range *range_param) { register regularExp_CHAR *ret_val; regularExp_CHAR test; int flags_local; len_range range_local; *flag_param = WORST; /* Tentatively. */ range_param->lower = 0; /* Idem */ range_param->upper = 0; /* Process any regex comments, e.g. `(?# match next token->)'. The terminating right parenthesis cannot be escaped. The comment stops at the first right parenthesis encountered (or the end of the regex string)... period. Handles multiple sequential comments, e.g. `(?# one)(?# two)...' */ while (*Reg_Parse == '(' && * (Reg_Parse + 1) == '?' && * (Reg_Parse + 2) == '#') { Reg_Parse += 3; while (*Reg_Parse != ')' && *Reg_Parse != '\0') { Reg_Parse++; } if (*Reg_Parse == ')') { Reg_Parse++; } if (*Reg_Parse == ')' || *Reg_Parse == '|' || *Reg_Parse == '\0') { /* Hit end of regex string or end of parenthesized regex; have to return "something" (i.e. a NOTHING node) to avoid generating an error. */ ret_val = emit_node (NOTHING); return (ret_val); } } switch (*Reg_Parse++) { case '^': ret_val = emit_node (BOL); break; case '$': ret_val = emit_node (EOL); break; case '<': ret_val = emit_node (BOWORD); break; case '>': ret_val = emit_node (EOWORD); break; case '.': if (Match_Newline) { ret_val = emit_node (EVERY); } else { ret_val = emit_node (ANY); } *flag_param |= (HAS_WIDTH | SIMPLE); range_param->lower = 1; range_param->upper = 1; break; case '(': if (*Reg_Parse == '?') { /* Special parenthetical expression */ Reg_Parse++; range_local.lower = 0; /* Make sure it is always used */ range_local.upper = 0; if (*Reg_Parse == ':') { Reg_Parse++; ret_val = chunk (NO_CAPTURE, &flags_local, &range_local); } else if (*Reg_Parse == '=') { Reg_Parse++; ret_val = chunk (POS_AHEAD_OPEN, &flags_local, &range_local); } else if (*Reg_Parse == '!') { Reg_Parse++; ret_val = chunk (NEG_AHEAD_OPEN, &flags_local, &range_local); } else if (*Reg_Parse == 'i') { Reg_Parse++; ret_val = chunk (INSENSITIVE, &flags_local, &range_local); } else if (*Reg_Parse == 'I') { Reg_Parse++; ret_val = chunk (SENSITIVE, &flags_local, &range_local); } else if (*Reg_Parse == 'n') { Reg_Parse++; ret_val = chunk (NEWLINE, &flags_local, &range_local); } else if (*Reg_Parse == 'N') { Reg_Parse++; ret_val = chunk (NO_NEWLINE, &flags_local, &range_local); } else if (*Reg_Parse == '<') { Reg_Parse++; if (*Reg_Parse == '=') { Reg_Parse++; ret_val = chunk (POS_BEHIND_OPEN, &flags_local, &range_local); } else if (*Reg_Parse == '!') { Reg_Parse++; ret_val = chunk (NEG_BEHIND_OPEN, &flags_local, &range_local); } else { swprintf ( (wchar *) Error_Text, 128, L"invalid look-behind syntax, \"(?<%c...)\"", *Reg_Parse); REG_FAIL (Error_Text); } } else { swprintf ( (wchar *) Error_Text, 128, L"invalid grouping syntax, \"(?%c...)\"", *Reg_Parse); REG_FAIL (Error_Text); } } else { /* Normal capturing parentheses */ ret_val = chunk (PAREN, &flags_local, &range_local); } if (ret_val == NULL) { return (NULL); /* Something went wrong. */ } /* Add HAS_WIDTH flag if it was set by call to chunk. */ *flag_param |= flags_local & HAS_WIDTH; *range_param = range_local; break; case '\0': case '|': case ')': REG_FAIL (L"internal error #3, `atom\'"); /* Supposed to be */ /* caught earlier. */ case '?': case '+': case '*': swprintf ( (wchar *) Error_Text, 128, L"%c follows nothing", * (Reg_Parse - 1)); REG_FAIL (Error_Text); case '{': if (Enable_Counting_Quantifier) { REG_FAIL (L"{m,n} follows nothing"); } else { ret_val = emit_node (EXACTLY); /* Treat braces as literals. */ emit_byte ('{'); emit_byte ('\0'); range_param->lower = 1; range_param->upper = 1; } break; case '[': { register unsigned int second_value; register unsigned int last_value; regularExp_CHAR last_emit = 0; /* Handle characters that can only occur at the start of a class. */ if (*Reg_Parse == '^') { /* Complement of range. */ ret_val = emit_node (ANY_BUT); Reg_Parse++; /* All negated classes include newline unless escaped with a "(?n)" switch. */ if (!Match_Newline) { emit_byte ('\n'); } } else { ret_val = emit_node (ANY_OF); } if (*Reg_Parse == ']' || *Reg_Parse == '-') { /* If '-' or ']' is the first character in a class, it is a literal character in the class. */ last_emit = *Reg_Parse; emit_byte (*Reg_Parse); Reg_Parse++; } /* Handle the rest of the class characters. */ while (*Reg_Parse != '\0' && *Reg_Parse != ']') { if (*Reg_Parse == '-') { /* Process a range, e.g [a-z]. */ Reg_Parse++; if (*Reg_Parse == ']' || *Reg_Parse == '\0') { /* If '-' is the last character in a class it is a literal character. If `Reg_Parse' points to the end of the regex string, an error will be generated later. */ emit_byte ('-'); last_emit = '-'; } else { /* We must get the range starting character value from the emitted code since it may have been an escaped character. `second_value' is set one larger than the just emitted character value. This is done since `second_value' is used as the start value for the loop that emits the values in the range. Since we have already emitted the first character of the class, we do not want to emit it again. */ second_value = ( (unsigned int) last_emit) + 1; if (*Reg_Parse == '\\') { /* Handle escaped characters within a class range. Specifically disallow shortcut escapes as the end of a class range. To allow this would be ambiguous since shortcut escapes represent a set of characters, and it would not be clear which character of the class should be treated as the "last" character. */ Reg_Parse++; if ( (test = numeric_escape (*Reg_Parse, &Reg_Parse))) { last_value = (unsigned int) test; } else if ( (test = literal_escape (*Reg_Parse))) { last_value = (unsigned int) test; } else if (shortcut_escape (*Reg_Parse, NULL, CHECK_CLASS_ESCAPE)) { swprintf ( (wchar *) Error_Text, 128, L"\\%c is not allowed as range operand", *Reg_Parse); REG_FAIL (Error_Text); } else { swprintf ( (wchar *) Error_Text, 128, L"\\%c is an invalid char class escape sequence", *Reg_Parse); REG_FAIL (Error_Text); } } else { last_value = U_CHAR_AT (Reg_Parse); } if (Is_Case_Insensitive) { second_value = (unsigned int) tolower ( (int) second_value); last_value = (unsigned int) tolower ( (int) last_value); } /* For case insensitive, something like [A-_] will generate an error here since ranges are converted to lower case. */ if (second_value - 1 > last_value) { REG_FAIL (L"invalid [] range"); } /* If only one character in range (e.g [a-a]) then this loop is not run since the first character of any range was emitted by the previous iteration of while loop. */ for (; second_value <= last_value; second_value++) { emit_class_byte (second_value); } last_emit = (regularExp_CHAR) last_value; Reg_Parse++; } /* End class character range code. */ } else if (*Reg_Parse == '\\') { Reg_Parse++; if ( (test = numeric_escape (*Reg_Parse, &Reg_Parse)) != '\0') { emit_class_byte (test); last_emit = test; } else if ( (test = literal_escape (*Reg_Parse)) != '\0') { emit_byte (test); last_emit = test; } else if (shortcut_escape (*Reg_Parse, NULL, CHECK_CLASS_ESCAPE)) { if (* (Reg_Parse + 1) == '-') { /* Specifically disallow shortcut escapes as the start of a character class range (see comment above.) */ swprintf ( (wchar *) Error_Text, 128, L"\\%c not allowed as range operand", *Reg_Parse); REG_FAIL (Error_Text); } else { /* Emit the bytes that are part of the shortcut escape sequence's range (e.g. \d = 0123456789) */ shortcut_escape (*Reg_Parse, NULL, EMIT_CLASS_BYTES); } } else { swprintf ( (wchar *) Error_Text, 128, L"\\%c is an invalid char class escape sequence", *Reg_Parse); REG_FAIL (Error_Text); } Reg_Parse++; /* End of class escaped sequence code */ } else { emit_class_byte (*Reg_Parse); /* Ordinary class character. */ last_emit = *Reg_Parse; Reg_Parse++; } } /* End of while (*Reg_Parse != '\0' && *Reg_Parse != ']') */ if (*Reg_Parse != ']') { REG_FAIL (L"missing right \']\'"); } emit_byte ('\0'); /* NOTE: it is impossible to specify an empty class. This is because [] would be interpreted as "begin character class" followed by a literal ']' character and no "end character class" delimiter (']'). Because of this, it is always safe to assume that a class HAS_WIDTH. */ Reg_Parse++; *flag_param |= HAS_WIDTH | SIMPLE; range_param->lower = 1; range_param->upper = 1; } break; /* End of character class code. */ case '\\': /* Force Error_Text to have a length of zero. This way we can tell if either of the calls to shortcut_escape() or back_ref() fill Error_Text with an error message. */ Error_Text [0] = '\0'; if ( (ret_val = shortcut_escape (*Reg_Parse, flag_param, EMIT_NODE))) { Reg_Parse++; range_param->lower = 1; range_param->upper = 1; break; } else if ( (ret_val = back_ref (Reg_Parse, flag_param, EMIT_NODE))) { /* Can't make any assumptions about a back-reference as to SIMPLE or HAS_WIDTH. For example (^|<) is neither simple nor has width. So we don't flip bits in flag_param here. */ Reg_Parse++; /* Back-references always have an unknown length */ range_param->lower = -1; range_param->upper = -1; break; } if (wcslen ( (wchar *) Error_Text) > 0) { REG_FAIL (Error_Text); } /* At this point it is apparent that the escaped character is not a shortcut escape or back-reference. Back up one character to allow the default code to include it as an ordinary character. */ /* Fall through to Default case to handle literal escapes and numeric escapes. */ default: Reg_Parse--; /* If we fell through from the above code, we are now pointing at the back slash (\) character. */ { regularExp_CHAR *parse_save; int len = 0; if (Is_Case_Insensitive) { ret_val = emit_node (SIMILAR); } else { ret_val = emit_node (EXACTLY); } /* Loop until we find a meta character, shortcut escape, back reference, or end of regex string. */ for (; *Reg_Parse != '\0' && !wcschr ( (wchar *) Meta_Char, (int) *Reg_Parse); len++) { /* Save where we are in case we have to back this character out. */ parse_save = Reg_Parse; if (*Reg_Parse == '\\') { Reg_Parse++; /* Point to escaped character */ Error_Text [0] = '\0'; /* See comment above. */ if ( (test = numeric_escape (*Reg_Parse, &Reg_Parse))) { if (Is_Case_Insensitive) { emit_byte (tolower (test)); } else { emit_byte (test); } } else if ( (test = literal_escape (*Reg_Parse))) { emit_byte (test); } else if (back_ref (Reg_Parse, NULL, CHECK_ESCAPE)) { /* Leave back reference for next `atom' call */ Reg_Parse--; break; } else if (shortcut_escape (*Reg_Parse, NULL, CHECK_ESCAPE)) { /* Leave shortcut escape for next `atom' call */ Reg_Parse--; break; } else { if (wcslen ( (wchar *) Error_Text) == 0) { /* None of the above calls generated an error message so generate our own here. */ swprintf ( (wchar *) Error_Text, 128, L"\\%c is an invalid escape sequence", *Reg_Parse); } REG_FAIL (Error_Text); } Reg_Parse++; } else { /* Ordinary character */ if (Is_Case_Insensitive) { emit_byte (tolower (*Reg_Parse)); } else { emit_byte (*Reg_Parse); } Reg_Parse++; } /* If next regex token is a quantifier (?, +. *, or {m,n}) and our EXACTLY node so far is more than one character, leave the last character to be made into an EXACTLY node one character wide for the multiplier to act on. For example 'abcd* would have an EXACTLY node with an 'abc' operand followed by a STAR node followed by another EXACTLY node with a 'd' operand. */ if (IS_QUANTIFIER (*Reg_Parse) && len > 0) { Reg_Parse = parse_save; /* Point to previous regex token. */ if (Code_Emit_Ptr == &Compute_Size) { Reg_Size--; } else { Code_Emit_Ptr--; /* Write over previously emitted byte. */ } break; } } if (len <= 0) { REG_FAIL (L"internal error #4, `atom\'"); } *flag_param |= HAS_WIDTH; if (len == 1) { *flag_param |= SIMPLE; } range_param->lower = len; range_param->upper = len; emit_byte ('\0'); } } /* END switch (*Reg_Parse++) */ return (ret_val); } /*----------------------------------------------------------------------* * emit_node * * Emit (if appropriate) the op code for a regex node atom. * * The NEXT pointer is initialized to NULL. * * Returns a pointer to the START of the emitted node. *----------------------------------------------------------------------*/ static regularExp_CHAR *emit_node (int op_code) { register regularExp_CHAR *ret_val; register regularExp_CHAR *ptr; ret_val = Code_Emit_Ptr; /* Return address of start of node */ if (ret_val == &Compute_Size) { Reg_Size += NODE_SIZE; } else { ptr = ret_val; *ptr++ = (regularExp_CHAR) op_code; *ptr++ = '\0'; /* Null "NEXT" pointer. */ *ptr++ = '\0'; Code_Emit_Ptr = ptr; } return (ret_val); } /*----------------------------------------------------------------------* * emit_byte * * Emit (if appropriate) a byte of code (usually part of an operand.) *----------------------------------------------------------------------*/ static void emit_byte (regularExp_CHAR c) { if (Code_Emit_Ptr == &Compute_Size) { Reg_Size++; } else { *Code_Emit_Ptr++ = c; } } /*----------------------------------------------------------------------* * emit_class_byte * * Emit (if appropriate) a byte of code (usually part of a character * class operand.) *----------------------------------------------------------------------*/ static void emit_class_byte (regularExp_CHAR c) { if (Code_Emit_Ptr == &Compute_Size) { Reg_Size++; if (Is_Case_Insensitive && isalpha (c)) { Reg_Size++; } } else if (Is_Case_Insensitive && isalpha (c)) { /* For case insensitive character classes, emit both upper and lower case versions of alphabetical characters. */ *Code_Emit_Ptr++ = tolower (c); *Code_Emit_Ptr++ = toupper (c); } else { *Code_Emit_Ptr++ = c; } } /*----------------------------------------------------------------------* * emit_special * * Emit nodes that need special processing. *----------------------------------------------------------------------*/ static regularExp_CHAR *emit_special ( regularExp_CHAR op_code, unsigned long test_val, int index) { register regularExp_CHAR *ret_val = &Compute_Size; register regularExp_CHAR *ptr; if (Code_Emit_Ptr == &Compute_Size) { switch (op_code) { case POS_BEHIND_OPEN: case NEG_BEHIND_OPEN: Reg_Size += LENGTH_SIZE; /* Length of the look-behind match */ Reg_Size += NODE_SIZE; /* Make room for the node */ break; case TEST_COUNT: Reg_Size += NEXT_PTR_SIZE; /* Make room for a test value. */ case INC_COUNT: Reg_Size += INDEX_SIZE; /* Make room for an index value. */ default: Reg_Size += NODE_SIZE; /* Make room for the node. */ } } else { ret_val = emit_node (op_code); /* Return the address for start of node. */ ptr = Code_Emit_Ptr; if (op_code == INC_COUNT || op_code == TEST_COUNT) { *ptr++ = (regularExp_CHAR) index; if (op_code == TEST_COUNT) { *ptr++ = PUT_OFFSET_L (test_val); *ptr++ = PUT_OFFSET_R (test_val); } } else if (op_code == POS_BEHIND_OPEN || op_code == NEG_BEHIND_OPEN) { *ptr++ = PUT_OFFSET_L (test_val); *ptr++ = PUT_OFFSET_R (test_val); *ptr++ = PUT_OFFSET_L (test_val); *ptr++ = PUT_OFFSET_R (test_val); } Code_Emit_Ptr = ptr; } return (ret_val); } /*----------------------------------------------------------------------* * insert * * Insert a node in front of already emitted node(s). Means relocating * the operand. Code_Emit_Ptr points one byte past the just emitted * node and operand. The parameter `insert_pos' points to the location * where the new node is to be inserted. *----------------------------------------------------------------------*/ static regularExp_CHAR *insert ( regularExp_CHAR op, regularExp_CHAR *insert_pos, long min, long max, int index) { register regularExp_CHAR *src; register regularExp_CHAR *dst; regularExp_CHAR *place; int insert_size = NODE_SIZE; if (op == BRACE || op == LAZY_BRACE) { /* Make room for the min and max values. */ insert_size += (2 * NEXT_PTR_SIZE); } else if (op == INIT_COUNT) { /* Make room for an index value . */ insert_size += INDEX_SIZE; } if (Code_Emit_Ptr == &Compute_Size) { Reg_Size += insert_size; return &Compute_Size; } src = Code_Emit_Ptr; Code_Emit_Ptr += insert_size; dst = Code_Emit_Ptr; /* Relocate the existing emitted code to make room for the new node. */ while (src > insert_pos) { *--dst = *--src; } place = insert_pos; /* Where operand used to be. */ *place++ = op; /* Inserted operand. */ *place++ = '\0'; /* NEXT pointer for inserted operand. */ *place++ = '\0'; if (op == BRACE || op == LAZY_BRACE) { *place++ = PUT_OFFSET_L (min); *place++ = PUT_OFFSET_R (min); *place++ = PUT_OFFSET_L (max); *place++ = PUT_OFFSET_R (max); } else if (op == INIT_COUNT) { *place++ = (regularExp_CHAR) index; } return place; /* Return a pointer to the start of the code moved. */ } /*----------------------------------------------------------------------* * tail - Set the next-pointer at the end of a node chain. *----------------------------------------------------------------------*/ static void tail (regularExp_CHAR *search_from, regularExp_CHAR *point_to) { register regularExp_CHAR *scan; register regularExp_CHAR *next; register int offset; if (search_from == &Compute_Size) { return; } /* Find the last node in the chain (node with a null NEXT pointer) */ scan = search_from; for (;;) { next = next_ptr (scan); if (!next) { break; } scan = next; } if (GET_OP_CODE (scan) == BACK) { offset = scan - point_to; } else { offset = point_to - scan; } /* Set NEXT pointer */ * (scan + 1) = PUT_OFFSET_L (offset); * (scan + 2) = PUT_OFFSET_R (offset); } /*--------------------------------------------------------------------* * offset_tail * * Perform a tail operation on (ptr + offset). *--------------------------------------------------------------------*/ static void offset_tail (regularExp_CHAR *ptr, int offset, regularExp_CHAR *val) { if (ptr == &Compute_Size || ptr == NULL) { return; } tail (ptr + offset, val); } /*--------------------------------------------------------------------* * branch_tail * * Perform a tail operation on (ptr + offset) but only if `ptr' is a * BRANCH node. *--------------------------------------------------------------------*/ static void branch_tail (regularExp_CHAR *ptr, int offset, regularExp_CHAR *val) { if (ptr == &Compute_Size || ptr == NULL || GET_OP_CODE (ptr) != BRANCH) { return; } tail (ptr + offset, val); } /*--------------------------------------------------------------------* * shortcut_escape * * Implements convenient escape sequences that represent entire * character classes or special location assertions (similar to escapes * supported by Perl) * _ * \d Digits [0-9] | * \D NOT a digit [^0-9] | (Examples * \l Letters [a-zA-Z] | at left * \L NOT a Letter [^a-zA-Z] | are * \s Whitespace [ \t\n\r\f\v] | for * \S NOT Whitespace [^ \t\n\r\f\v] | C * \w "Word" character [a-zA-Z0-9_] | Locale) * \W NOT a "Word" character [^a-zA-Z0-9_] _| * * \B Matches any character that is NOT a word-delimiter * * Codes for the "emit" parameter: * * EMIT_NODE * Emit a shortcut node. Shortcut nodes have an implied set of * class characters. This helps keep the compiled regex string * small. * * EMIT_CLASS_BYTES * Emit just the equivalent characters of the class. This makes * the escape usable from within a class, e.g. [a-fA-F\d]. Only * \d, \D, \s, \S, \w, and \W can be used within a class. * * CHECK_ESCAPE * Only verify that this is a valid shortcut escape. * * CHECK_CLASS_ESCAPE * Same as CHECK_ESCAPE but only allows characters valid within * a klas. * *--------------------------------------------------------------------*/ static regularExp_CHAR *shortcut_escape ( regularExp_CHAR c, int *flag_param, int emit) { register regularExp_CHAR *klas = NULL; static regularExp_CHAR *codes = (regularExp_CHAR *) L"ByYdDlLsSwW"; regularExp_CHAR *ret_val = (regularExp_CHAR *) 1; /* Assume success. */ regularExp_CHAR *valid_codes; if (emit == EMIT_CLASS_BYTES || emit == CHECK_CLASS_ESCAPE) { valid_codes = codes + 3; /* \B, \y and \Y are not allowed in classes */ } else { valid_codes = codes; } if (!wcschr ( (wchar *) valid_codes, (int) c)) { return NULL; /* Not a valid shortcut escape sequence */ } else if (emit == CHECK_ESCAPE || emit == CHECK_CLASS_ESCAPE) { return ret_val; /* Just checking if this is a valid shortcut escape. */ } switch (c) { case 'd': case 'D': if (emit == EMIT_CLASS_BYTES) { klas = ASCII_Digits; } else if (emit == EMIT_NODE) { ret_val = (islower (c) ? emit_node (DIGIT) : emit_node (NOT_DIGIT)); } break; case 'l': case 'L': if (emit == EMIT_CLASS_BYTES) { klas = Letter_Char; } else if (emit == EMIT_NODE) { ret_val = (islower (c) ? emit_node (LETTER) : emit_node (NOT_LETTER)); } break; case 's': case 'S': if (emit == EMIT_CLASS_BYTES) { if (Match_Newline) { emit_byte ('\n'); } klas = White_Space; } else if (emit == EMIT_NODE) { if (Match_Newline) { ret_val = (islower (c) ? emit_node (SPACE_NL) : emit_node (NOT_SPACE_NL)); } else { ret_val = (islower (c) ? emit_node (SPACE) : emit_node (NOT_SPACE)); } } break; case 'w': case 'W': if (emit == EMIT_CLASS_BYTES) { klas = Word_Char; } else if (emit == EMIT_NODE) { ret_val = (islower (c) ? emit_node (WORD_CHAR) : emit_node (NOT_WORD_CHAR)); } break; /* Since the delimiter table is not available at regex compile time \B, \Y and \Y can only generate a node. At run time, the delimiter table will be available for these nodes to use. */ case 'y': if (emit == EMIT_NODE) { ret_val = emit_node (IS_DELIM); } else { REG_FAIL (L"internal error #5 `shortcut_escape\'"); } break; case 'Y': if (emit == EMIT_NODE) { ret_val = emit_node (NOT_DELIM); } else { REG_FAIL (L"internal error #6 `shortcut_escape\'"); } break; case 'B': if (emit == EMIT_NODE) { ret_val = emit_node (NOT_BOUNDARY); } else { REG_FAIL (L"internal error #7 `shortcut_escape\'"); } break; default: /* We get here if there isn't a case for every character in the string "codes" */ REG_FAIL (L"internal error #8 `shortcut_escape\'"); } if (emit == EMIT_NODE && c != 'B') { *flag_param |= (HAS_WIDTH | SIMPLE); } if (klas) { /* Emit bytes within a character class operand. */ while (*klas != '\0') { emit_byte (*klas++); } } return ret_val; } /*--------------------------------------------------------------------* * numeric_escape * * Implements hex and octal numeric escape sequence syntax. * * Hexadecimal Escape: \x## Max of two digits Must have leading 'x'. * Octal Escape: \0### Max of three digits and not greater * than 377 octal. Must have leading zero. * * Returns the actual character value or NULL if not a valid hex or * octal escape. REG_FAIL is called if \x0, \x00, \0, \00, \000, or * \0000 is specified. *--------------------------------------------------------------------*/ static regularExp_CHAR numeric_escape ( regularExp_CHAR c, regularExp_CHAR **parse) { static regularExp_CHAR digits [] = { 'f', 'e', 'd', 'c', 'b', 'a', 'F', 'E', 'D', 'C', 'B', 'A', '9', '8', '7', '6', '5', '4', '3', '2', '1', '0' }; static unsigned int digit_val [] = { 15, 14, 13, 12, 11, 10, /* Lower case Hex digits */ 15, 14, 13, 12, 11, 10, /* Upper case Hex digits */ 9, 8, 7, 6, 5, 4, 3, 2, 1, 0 }; /* Decimal Digits */ register regularExp_CHAR *scan; register regularExp_CHAR *pos_ptr; register regularExp_CHAR *digit_str; unsigned int value = 0; unsigned int radix = 8; int width = 3; /* Can not be bigger than \0377 */ int pos_delta = 14; int i, pos; switch (c) { case '0': digit_str = digits + pos_delta; /* Only use Octal digits, i.e. 0-7. */ break; case 'x': case 'X': width = 2; /* Can not be bigger than \0377 */ radix = 16; pos_delta = 0; digit_str = digits; /* Use all of the digit characters. */ break; default: return ('\0'); /* Not a numeric escape */ } scan = *parse; scan++; /* Only change *parse on success. */ pos_ptr = (regularExp_CHAR *) wcschr ( (wchar *) digit_str, (int) * scan); for (i = 0; pos_ptr != NULL && (i < width); i++) { pos = (pos_ptr - digit_str) + pos_delta; value = (value * radix) + digit_val [pos]; /* If this digit makes the value over 255, treat this digit as a literal character instead of part of the numeric escape. For example, \0777 will be processed as \077 (an 'M') and a literal '7' character, NOT 511 decimal which is > 255. */ if (value > 255) { /* Back out calculations for last digit processed. */ value -= digit_val [pos]; value /= radix; break; /* Note that scan will not be incremented and still points to the digit that caused overflow. It will be decremented by the "else" below to point to the last character that is considered to be part of the octal escape. */ } scan++; pos_ptr = (regularExp_CHAR *) wcschr ( (wchar *) digit_str, (int) * scan); } /* Handle the case of "\0" i.e. trying to specify a NULL character. */ if (value == 0) { if (c == '0') { swprintf ( (wchar *) Error_Text, 128, L"\\00 is an invalid octal escape"); } else { swprintf ( (wchar *) Error_Text, 128, L"\\%c0 is an invalid hexadecimal escape", c); } } else { /* Point to the last character of the number on success. */ scan--; *parse = scan; } return (regularExp_CHAR) value; } /*--------------------------------------------------------------------* * literal_escape * * Recognize escaped literal characters (prefixed with backslash), * and translate them into the corresponding character. * * Returns the proper character value or NULL if not a valid literal * escape. *--------------------------------------------------------------------*/ static regularExp_CHAR literal_escape (regularExp_CHAR c) { static regularExp_CHAR valid_escape [] = { 'a', 'b', 'e', 'f', 'n', 'r', 't', 'v', '(', ')', '-', '[', ']', '<', '>', '{', '}', '.', '\\', '|', '^', '$', '*', '+', '?', '&', '\0' }; static regularExp_CHAR value [] = { '\a', '\b', #ifdef EBCDIC_CHARSET 0x27, /* Escape character in IBM's EBCDIC character set. */ #else 0x1B, /* Escape character in ASCII character set. */ #endif '\f', '\n', '\r', '\t', '\v', '(', ')', '-', '[', ']', '<', '>', '{', '}', '.', '\\', '|', '^', '$', '*', '+', '?', '&', '\0' }; int i; for (i = 0; valid_escape [i] != '\0'; i++) { if (c == valid_escape [i]) { return value [i]; } } return '\0'; } /*--------------------------------------------------------------------* * back_ref * * Process a request to match a previous parenthesized thing. * Parenthetical entities are numbered beginning at 1 by counting * opening parentheses from left to to right. \0 would represent * whole match, but would confuse numeric_escape as an octal escape, * so it is forbidden. * * Constructs of the form \~1, \~2, etc. are cross-regex back * references and are used in syntax highlighting patterns to match * text previously matched by another regex. *** IMPLEMENT LATER *** *--------------------------------------------------------------------*/ static regularExp_CHAR *back_ref ( regularExp_CHAR *c, int *flag_param, int emit) { int paren_no, c_offset = 0, is_cross_regex = 0; regularExp_CHAR *ret_val; /* Implement cross regex backreferences later. */ /* if (*c == (regularExp_CHAR) ('~')) { c_offset++; is_cross_regex++; } */ paren_no = (int) (* (c + c_offset) - (regularExp_CHAR) ('0')); if (!isdigit (* (c + c_offset)) || /* Only \1, \2, ... \9 are supported. */ paren_no == 0) { /* Should be caught by numeric_escape. */ return NULL; } /* Make sure parentheses for requested back-reference are complete. */ if (!is_cross_regex && !TEST_BIT (Closed_Parens, paren_no)) { swprintf ( (wchar *) Error_Text, 128, L"\\%d is an illegal back reference", paren_no); return NULL; } if (emit == EMIT_NODE) { if (is_cross_regex) { Reg_Parse++; /* Skip past the '~' in a cross regex back reference. We only do this if we are emitting code. */ if (Is_Case_Insensitive) { ret_val = emit_node (X_REGEX_BR_CI); } else { ret_val = emit_node (X_REGEX_BR); } } else { if (Is_Case_Insensitive) { ret_val = emit_node (BACK_REF_CI); } else { ret_val = emit_node (BACK_REF); } } emit_byte ( (regularExp_CHAR) paren_no); if (is_cross_regex || TEST_BIT (Paren_Has_Width, paren_no)) { *flag_param |= HAS_WIDTH; } } else if (emit == CHECK_ESCAPE) { ret_val = (regularExp_CHAR *) 1; } else { ret_val = NULL; } return ret_val; } /*======================================================================* * Regex execution related code *======================================================================*/ /* Global work variables for `ExecRE'. */ static regularExp_CHAR *Reg_Input; /* String-input pointer. */ static regularExp_CHAR *Start_Of_String; /* Beginning of input, for ^ */ /* and < checks. */ static regularExp_CHAR *End_Of_String; /* Logical end of input (if supplied, till \0 otherwise) */ static regularExp_CHAR *Look_Behind_To; /* Position till were look behind can safely check back */ static regularExp_CHAR **Start_Ptr_Ptr; /* Pointer to `startp' array. */ static regularExp_CHAR **End_Ptr_Ptr; /* Ditto for `endp'. */ static regularExp_CHAR *Extent_Ptr_FW; /* Forward extent pointer */ static regularExp_CHAR *Extent_Ptr_BW; /* Backward extent pointer */ static regularExp_CHAR *Back_Ref_Start [10]; /* Back_Ref_Start [0] and */ static regularExp_CHAR *Back_Ref_End [10]; /* Back_Ref_End [0] are not */ /* used. This simplifies */ /* indexing. */ /* * Measured recursion limits: * Linux: +/- 40 000 (up to 110 000) * Solaris: +/- 85 000 * HP-UX 11: +/- 325 000 * * So 10 000 ought to be safe. */ #define REGEX_RECURSION_LIMIT 10000 static int Recursion_Count; /* Recursion counter */ static int Recursion_Limit_Exceeded; /* Recursion limit exceeded flag */ #define AT_END_OF_STRING(X) (*(X) == (regularExp_CHAR)'\0' ||\ (End_Of_String != NULL && (X) >= End_Of_String)) /* static regexp *Cross_Regex_Backref; */ static int Prev_Is_BOL; static int Succ_Is_EOL; static int Prev_Is_Delim; static int Succ_Is_Delim; /* Define a pointer to an array to hold general (...){m,n} counts. */ typedef struct brace_counts { unsigned long count [1]; /* More unwarranted chumminess with compiler. */ } brace_counts; static struct brace_counts *Brace; /* Default table for determining whether a character is a word delimiter. */ static regularExp_CHAR Default_Delimiters [UCHAR_MAX] = {0}; static regularExp_CHAR *Current_Delimiters; /* Current delimiter table */ /* Forward declarations of functions used by `ExecRE' */ static int attempt (regexp *, regularExp_CHAR *); static int match (regularExp_CHAR *, int *); static unsigned long greedy (regularExp_CHAR *, long); static void adjustcase (regularExp_CHAR *, int, regularExp_CHAR); static regularExp_CHAR *makeDelimiterTable (regularExp_CHAR *, regularExp_CHAR *); /* * ExecRE - match a `regexp' structure against a string * * If `end' is non-NULL, matches may not BEGIN past end, but may extend past * it. If reverse is true, `end' must be specified, and searching begins at * `end'. "isbol" should be set to true if the beginning of the string is the * actual beginning of a line (since `ExecRE' can't look backwards from the * beginning to find whether there was a newline before). Likewise, "isbow" * asks whether the string is preceded by a word delimiter. End of string is * always treated as a word and line boundary (there may be cases where it * shouldn't be, in which case, this should be changed). "delimit" (if * non-null) specifies a null-terminated string of characters to be considered * word delimiters matching "<" and ">". if "delimit" is NULL, the default * delimiters (as set in SetREDefaultWordDelimiters) are used. * Look_behind_to indicates the position till where it is safe to * perform look-behind matches. If set, it should be smaller than or equal * to the start position of the search (pointed at by string). If it is NULL, * it defaults to the start position. * Finally, match_to indicates the logical end of the string, till where * matches are allowed to extend. Note that look-ahead patterns may look * past that boundary. If match_to is set to NULL, the terminating \0 is * assumed to correspond to the logical boundary. Match_to, if set, must be * larger than or equal to end, if set. */ int ExecRE ( regexp *prog, regexp *cross_regex_backref, const regularExp_CHAR *string, const regularExp_CHAR *end, int reverse, regularExp_CHAR prev_char, regularExp_CHAR succ_char, const regularExp_CHAR *delimiters, const regularExp_CHAR *look_behind_to, const regularExp_CHAR *match_to) { register regularExp_CHAR *str; regularExp_CHAR **s_ptr; regularExp_CHAR **e_ptr; int ret_val = 0; regularExp_CHAR tempDelimitTable [256]; int i; (void) cross_regex_backref; s_ptr = (regularExp_CHAR **) prog->startp; e_ptr = (regularExp_CHAR **) prog->endp; /* Check for valid parameters. */ if (prog == NULL || string == NULL) { reg_error (L"NULL parameter to `ExecRE\'"); goto SINGLE_RETURN; } /* Check validity of program. */ if (U_CHAR_AT (prog->program) != MAGIC) { reg_error (L"corrupted program"); goto SINGLE_RETURN; } /* If caller has supplied delimiters, make a delimiter table */ if (delimiters == NULL) { Current_Delimiters = Default_Delimiters; } else { Current_Delimiters = makeDelimiterTable ( (regularExp_CHAR *) delimiters, (regularExp_CHAR *) tempDelimitTable); } /* Remember the logical end of the string. */ End_Of_String = (regularExp_CHAR *) match_to; if (end == NULL && reverse) { for (end = string; !AT_END_OF_STRING ( (regularExp_CHAR *) end); end++) { ; } succ_char = '\n'; } else if (end == NULL) { succ_char = '\n'; } /* Initialize arrays used by shortcut_escape. */ if (!init_ansi_classes ()) { goto SINGLE_RETURN; } /* Remember the beginning of the string for matching BOL */ Start_Of_String = (regularExp_CHAR *) string; Look_Behind_To = (regularExp_CHAR *) (look_behind_to ? look_behind_to : string); Prev_Is_BOL = ( (prev_char == '\n') || (prev_char == '\0') ? 1 : 0); Succ_Is_EOL = ( (succ_char == '\n') || (succ_char == '\0') ? 1 : 0); Prev_Is_Delim = (Current_Delimiters [ (regularExp_CHAR) prev_char] ? 1 : 0); Succ_Is_Delim = (Current_Delimiters [ (regularExp_CHAR) succ_char] ? 1 : 0); Total_Paren = (int) (prog->program [1]); Num_Braces = (int) (prog->program [2]); /* Reset the recursion detection flag */ Recursion_Limit_Exceeded = 0; /* Cross_Regex_Backref = cross_regex_backref; */ /* Allocate memory for {m,n} construct counting variables if need be. */ if (Num_Braces > 0) { Brace = (brace_counts *) malloc (sizeof (brace_counts) * (size_t) Num_Braces); if (Brace == NULL) { reg_error (L"out of memory in `ExecRE\'"); goto SINGLE_RETURN; } } else { Brace = NULL; } /* Initialize the first nine (9) capturing parentheses start and end pointers to point to the start of the search string. This is to prevent crashes when later trying to reference captured parens that do not exist in the compiled regex. We only need to do the first nine since users can only specify \1, \2, ... \9. */ for (i = 9; i > 0; i--) { *s_ptr++ = (regularExp_CHAR *) string; *e_ptr++ = (regularExp_CHAR *) string; } if (!reverse) { /* Forward Search */ if (prog->anchor) { /* Search is anchored at BOL */ if (attempt (prog, (regularExp_CHAR *) string)) { ret_val = 1; goto SINGLE_RETURN; } for (str = (regularExp_CHAR *) string; !AT_END_OF_STRING (str) && str != (regularExp_CHAR *) end && !Recursion_Limit_Exceeded; str++) { if (*str == '\n') { if (attempt (prog, str + 1)) { ret_val = 1; break; } } } goto SINGLE_RETURN; } else if (prog->match_start != '\0') { /* We know what char match must start with. */ for (str = (regularExp_CHAR *) string; !AT_END_OF_STRING (str) && str != (regularExp_CHAR *) end && !Recursion_Limit_Exceeded; str++) { if (*str == (regularExp_CHAR) prog->match_start) { if (attempt (prog, str)) { ret_val = 1; break; } } } goto SINGLE_RETURN; } else { /* General case */ for (str = (regularExp_CHAR *) string; !AT_END_OF_STRING (str) && str != (regularExp_CHAR *) end && !Recursion_Limit_Exceeded; str++) { if (attempt (prog, str)) { ret_val = 1; break; } } /* Beware of a single $ matching \0 */ if (!Recursion_Limit_Exceeded && !ret_val && AT_END_OF_STRING (str) && str != (regularExp_CHAR *) end) { if (attempt (prog, str)) { ret_val = 1; } } goto SINGLE_RETURN; } } else { /* Search reverse, same as forward, but loops run backward */ /* Make sure that we don't start matching beyond the logical end */ if (End_Of_String != NULL && (regularExp_CHAR *) end > End_Of_String) { end = (const regularExp_CHAR *) End_Of_String; } if (prog->anchor) { /* Search is anchored at BOL */ for (str = (regularExp_CHAR *) (end - 1); str >= (regularExp_CHAR *) string && !Recursion_Limit_Exceeded; str--) { if (*str == '\n') { if (attempt (prog, str + 1)) { ret_val = 1; goto SINGLE_RETURN; } } } if (!Recursion_Limit_Exceeded && attempt (prog, (regularExp_CHAR *) string)) { ret_val = 1; goto SINGLE_RETURN; } goto SINGLE_RETURN; } else if (prog->match_start != '\0') { /* We know what char match must start with. */ for (str = (regularExp_CHAR *) end; str >= (regularExp_CHAR *) string && !Recursion_Limit_Exceeded; str--) { if (*str == (regularExp_CHAR) prog->match_start) { if (attempt (prog, str)) { ret_val = 1; break; } } } goto SINGLE_RETURN; } else { /* General case */ for (str = (regularExp_CHAR *) end; str >= (regularExp_CHAR *) string && !Recursion_Limit_Exceeded; str--) { if (attempt (prog, str)) { ret_val = 1; break; } } } } SINGLE_RETURN: if (Brace) { free (Brace); } if (Recursion_Limit_Exceeded) { return (0); } return (ret_val); } /*--------------------------------------------------------------------* * init_ansi_classes * * Generate character class sets using locale aware ANSI C functions. * *--------------------------------------------------------------------*/ static int init_ansi_classes (void) { static int initialized = 0; static int underscore = (int) '_'; int i, word_count, letter_count, space_count; if (!initialized) { initialized = 1; /* Only need to generate character sets once. */ word_count = 0; letter_count = 0; space_count = 0; for (i = 1; i < (int) UCHAR_MAX; i++) { if (isalnum (i) || i == underscore) { Word_Char [word_count++] = (regularExp_CHAR) i; } if (isalpha (i)) { Letter_Char [letter_count++] = (regularExp_CHAR) i; } /* Note: Whether or not newline is considered to be whitespace is handled by switches within the original regex and is thus omitted here. */ if (isspace (i) && (i != (int) '\n')) { White_Space [space_count++] = (regularExp_CHAR) i; } /* Make sure arrays are big enough. ("- 2" because of zero array origin and we need to leave room for the NULL terminator.) */ if (word_count > (ALNUM_CHAR_SIZE - 2) || space_count > (WHITE_SPACE_SIZE - 2) || letter_count > (ALNUM_CHAR_SIZE - 2)) { reg_error (L"internal error #9 `init_ansi_classes\'"); return (0); } } Word_Char [word_count] = '\0'; Letter_Char [word_count] = '\0'; White_Space [space_count] = '\0'; } return (1); } /*----------------------------------------------------------------------* * attempt - try match at specific point, returns: 0 failure, 1 success *----------------------------------------------------------------------*/ static int attempt (regexp *prog, regularExp_CHAR *string) { register int i; register regularExp_CHAR **s_ptr; register regularExp_CHAR **e_ptr; int branch_index = 0; /* Must be set to zero ! */ Reg_Input = string; Start_Ptr_Ptr = (regularExp_CHAR **) prog->startp; End_Ptr_Ptr = (regularExp_CHAR **) prog->endp; s_ptr = (regularExp_CHAR **) prog->startp; e_ptr = (regularExp_CHAR **) prog->endp; /* Reset the recursion counter. */ Recursion_Count = 0; /* Overhead due to capturing parentheses. */ Extent_Ptr_BW = string; Extent_Ptr_FW = NULL; for (i = Total_Paren + 1; i > 0; i--) { *s_ptr++ = NULL; *e_ptr++ = NULL; } if (match ( (regularExp_CHAR *) (prog->program + REGEX_START_OFFSET), &branch_index)) { prog->startp [0] = (regularExp_CHAR *) string; prog->endp [0] = (regularExp_CHAR *) Reg_Input; /* <-- One char AFTER */ prog->extentpBW = (regularExp_CHAR *) Extent_Ptr_BW; /* matched string! */ prog->extentpFW = (regularExp_CHAR *) Extent_Ptr_FW; prog->top_branch = branch_index; return (1); } else { return (0); } } /*----------------------------------------------------------------------* * match - main matching routine * * Conceptually the strategy is simple: check to see whether the * current node matches, call self recursively to see whether the rest * matches, and then act accordingly. In practice we make some effort * to avoid recursion, in particular by going through "ordinary" nodes * (that don't need to know whether the rest of the match failed) by a * loop instead of by recursion. Returns 0 failure, 1 success. *----------------------------------------------------------------------*/ #define MATCH_RETURN(X)\ { --Recursion_Count; return (X); } #define CHECK_RECURSION_LIMIT\ if (Recursion_Limit_Exceeded) MATCH_RETURN (0); static int match (regularExp_CHAR *prog, int *branch_index_param) { register regularExp_CHAR *scan; /* Current node. */ regularExp_CHAR *next; /* Next node. */ register int next_ptr_offset; /* Used by the NEXT_PTR () macro */ if (++Recursion_Count > REGEX_RECURSION_LIMIT) { if (!Recursion_Limit_Exceeded) { /* Prevent duplicate errors */ reg_error (L"recursion limit exceeded, please respecify expression"); } Recursion_Limit_Exceeded = 1; MATCH_RETURN (0); } scan = prog; while (scan != NULL) { NEXT_PTR (scan, next); switch (GET_OP_CODE (scan)) { case BRANCH: { register regularExp_CHAR *save; register int branch_index_local = 0; if (GET_OP_CODE (next) != BRANCH) { /* No choice. */ next = OPERAND (scan); /* Avoid recursion. */ } else { do { save = Reg_Input; if (match (OPERAND (scan), NULL)) { if (branch_index_param) { *branch_index_param = branch_index_local; } MATCH_RETURN (1); } CHECK_RECURSION_LIMIT ++branch_index_local; Reg_Input = save; /* Backtrack. */ NEXT_PTR (scan, scan); } while (scan != NULL && GET_OP_CODE (scan) == BRANCH); MATCH_RETURN (0); /* NOT REACHED */ } } break; case EXACTLY: { register int len; register regularExp_CHAR *opnd; opnd = OPERAND (scan); /* Inline the first character, for speed. */ if (*opnd != *Reg_Input) { MATCH_RETURN (0); } len = wcslen ( (wchar *) opnd); if (End_Of_String != NULL && Reg_Input + len > End_Of_String) { MATCH_RETURN (0); } if (len > 1 && wcsncmp ( (wchar *) opnd, (wchar *) Reg_Input, len) != 0) { MATCH_RETURN (0); } Reg_Input += len; } break; case SIMILAR: { register regularExp_CHAR *opnd; register regularExp_CHAR test; opnd = OPERAND (scan); /* Note: the SIMILAR operand was converted to lower case during regex compile. */ while ( (test = *opnd++) != '\0') { if (AT_END_OF_STRING (Reg_Input) || tolower (*Reg_Input++) != test) { MATCH_RETURN (0); } } } break; case BOL: /* `^' (beginning of line anchor) */ if (Reg_Input == Start_Of_String) { if (Prev_Is_BOL) { break; } } else if (* (Reg_Input - 1) == '\n') { break; } MATCH_RETURN (0); case EOL: /* `$' anchor matches end of line and end of string */ if (*Reg_Input == '\n' || (AT_END_OF_STRING (Reg_Input) && Succ_Is_EOL)) { break; } MATCH_RETURN (0); case BOWORD: /* `<' (beginning of word anchor) */ /* Check to see if the current character is not a delimiter and the preceding character is. */ { int prev_is_delim; if (Reg_Input == Start_Of_String) { prev_is_delim = Prev_Is_Delim; } else { prev_is_delim = Current_Delimiters [ * (Reg_Input - 1) ]; } if (prev_is_delim) { int current_is_delim; if (AT_END_OF_STRING (Reg_Input)) { current_is_delim = Succ_Is_Delim; } else { current_is_delim = Current_Delimiters [ *Reg_Input ]; } if (!current_is_delim) { break; } } } MATCH_RETURN (0); case EOWORD: /* `>' (end of word anchor) */ /* Check to see if the current character is a delimiter and the preceding character is not. */ { int prev_is_delim; if (Reg_Input == Start_Of_String) { prev_is_delim = Prev_Is_Delim; } else { prev_is_delim = Current_Delimiters [ * (Reg_Input - 1) ]; } if (!prev_is_delim) { int current_is_delim; if (AT_END_OF_STRING (Reg_Input)) { current_is_delim = Succ_Is_Delim; } else { current_is_delim = Current_Delimiters [ *Reg_Input ]; } if (current_is_delim) { break; } } } MATCH_RETURN (0); case NOT_BOUNDARY: { /* \B (NOT a word boundary) */ int prev_is_delim; int current_is_delim; if (Reg_Input == Start_Of_String) { prev_is_delim = Prev_Is_Delim; } else { prev_is_delim = Current_Delimiters [ * (Reg_Input - 1) ]; } if (AT_END_OF_STRING (Reg_Input)) { current_is_delim = Succ_Is_Delim; } else { current_is_delim = Current_Delimiters [ *Reg_Input ]; } if (! (prev_is_delim ^ current_is_delim)) { break; } } MATCH_RETURN (0); case IS_DELIM: /* \y (A word delimiter character.) */ if (Current_Delimiters [ *Reg_Input ] && !AT_END_OF_STRING (Reg_Input)) { Reg_Input++; break; } MATCH_RETURN (0); case NOT_DELIM: /* \Y (NOT a word delimiter character.) */ if (!Current_Delimiters [ *Reg_Input ] && !AT_END_OF_STRING (Reg_Input)) { Reg_Input++; break; } MATCH_RETURN (0); case WORD_CHAR: /* \w (word character; alpha-numeric or underscore) */ if ( (isalnum ( (int) *Reg_Input) || *Reg_Input == '_') && !AT_END_OF_STRING (Reg_Input)) { Reg_Input++; break; } MATCH_RETURN (0); case NOT_WORD_CHAR:/* \W (NOT a word character) */ if (isalnum ( (int) *Reg_Input) || *Reg_Input == '_' || *Reg_Input == '\n' || AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case ANY: /* `.' (matches any character EXCEPT newline) */ if (AT_END_OF_STRING (Reg_Input) || *Reg_Input == '\n') { MATCH_RETURN (0); } Reg_Input++; break; case EVERY: /* `.' (matches any character INCLUDING newline) */ if (AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case DIGIT: /* \d, same as [0123456789] */ if (!isdigit ( (int) *Reg_Input) || AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case NOT_DIGIT: /* \D, same as [^0123456789] */ if (isdigit ( (int) *Reg_Input) || *Reg_Input == '\n' || AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case LETTER: /* \l, same as [a-zA-Z] */ if (!isalpha ( (int) *Reg_Input) || AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case NOT_LETTER: /* \L, same as [^0123456789] */ if (isalpha ( (int) *Reg_Input) || *Reg_Input == '\n' || AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case SPACE: /* \s, same as [ \t\r\f\v] */ if (!isspace ( (int) *Reg_Input) || *Reg_Input == '\n' || AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case SPACE_NL: /* \s, same as [\n \t\r\f\v] */ if (!isspace ( (int) *Reg_Input) || AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case NOT_SPACE: /* \S, same as [^\n \t\r\f\v] */ if (isspace ( (int) *Reg_Input) || AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case NOT_SPACE_NL: /* \S, same as [^ \t\r\f\v] */ if ( (isspace ( (int) *Reg_Input) && *Reg_Input != '\n') || AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } Reg_Input++; break; case ANY_OF: /* [...] character class. */ if (AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); } /* Needed because strchr () considers \0 as a member of the character set. */ if (wcschr ( (wchar *) OPERAND (scan), (int) *Reg_Input) == NULL) { MATCH_RETURN (0); } Reg_Input++; break; case ANY_BUT: /* [^...] Negated character class-- does NOT normally match newline (\n added usually to operand at compile time.) */ if (AT_END_OF_STRING (Reg_Input)) { MATCH_RETURN (0); /* See comment for ANY_OF. */ } if (wcschr ( (wchar *) OPERAND (scan), (int) *Reg_Input) != NULL) { MATCH_RETURN (0); } Reg_Input++; break; case NOTHING: case BACK: break; case STAR: case PLUS: case QUESTION: case BRACE: case LAZY_STAR: case LAZY_PLUS: case LAZY_QUESTION: case LAZY_BRACE: { register unsigned long num_matched = REG_ZERO; register unsigned long min = ULONG_MAX, max = REG_ZERO; register regularExp_CHAR *save; register regularExp_CHAR next_char; regularExp_CHAR *next_op; int lazy = 0; /* Lookahead (when possible) to avoid useless match attempts when we know what character comes next. */ if (GET_OP_CODE (next) == EXACTLY) { next_char = *OPERAND (next); } else { next_char = '\0';/* i.e. Don't know what next character is. */ } next_op = OPERAND (scan); switch (GET_OP_CODE (scan)) { case LAZY_STAR: lazy = 1; case STAR: min = REG_ZERO; max = ULONG_MAX; break; case LAZY_PLUS: lazy = 1; case PLUS: min = REG_ONE; max = ULONG_MAX; break; case LAZY_QUESTION: lazy = 1; case QUESTION: min = REG_ZERO; max = REG_ONE; break; case LAZY_BRACE: lazy = 1; case BRACE: min = (unsigned long) GET_OFFSET (scan + NEXT_PTR_SIZE); max = (unsigned long) GET_OFFSET (scan + (2 * NEXT_PTR_SIZE)); if (max <= REG_INFINITY) { max = ULONG_MAX; } next_op = OPERAND (scan + (2 * NEXT_PTR_SIZE)); } save = Reg_Input; if (lazy) { if (min > REG_ZERO) { num_matched = greedy (next_op, min); } } else { num_matched = greedy (next_op, max); } while (min <= num_matched && num_matched <= max) { if (next_char == '\0' || next_char == *Reg_Input) { if (match (next, NULL)) { MATCH_RETURN (1); } CHECK_RECURSION_LIMIT } /* Couldn't or didn't match. */ if (lazy) { if (!greedy (next_op, 1)) { MATCH_RETURN (0); } num_matched++; /* Inch forward. */ } else if (num_matched > REG_ZERO) { num_matched--; /* Back up. */ } else if (min == REG_ZERO && num_matched == REG_ZERO) { break; } Reg_Input = save + num_matched; } MATCH_RETURN (0); } break; case END: if (Extent_Ptr_FW == NULL || (Reg_Input - Extent_Ptr_FW) > 0) { Extent_Ptr_FW = Reg_Input; } MATCH_RETURN (1); /* Success! */ break; case INIT_COUNT: Brace->count [*OPERAND (scan)] = REG_ZERO; break; case INC_COUNT: Brace->count [*OPERAND (scan)]++; break; case TEST_COUNT: if (Brace->count [*OPERAND (scan)] < (unsigned long) GET_OFFSET (scan + NEXT_PTR_SIZE + INDEX_SIZE)) { next = scan + NODE_SIZE + INDEX_SIZE + NEXT_PTR_SIZE; } break; case BACK_REF: case BACK_REF_CI: /* case X_REGEX_BR: */ /* case X_REGEX_BR_CI: *** IMPLEMENT LATER */ { register regularExp_CHAR *captured, *finish; int paren_no; paren_no = (int) * OPERAND (scan); /* if (GET_OP_CODE (scan) == X_REGEX_BR || GET_OP_CODE (scan) == X_REGEX_BR_CI) { if (Cross_Regex_Backref == NULL) MATCH_RETURN (0); captured = (regularExp_CHAR *) Cross_Regex_Backref->startp [paren_no]; finish = (regularExp_CHAR *) Cross_Regex_Backref->endp [paren_no]; } else { */ captured = Back_Ref_Start [paren_no]; finish = Back_Ref_End [paren_no]; /* } */ if ( (captured != NULL) && (finish != NULL)) { if (captured > finish) { MATCH_RETURN (0); } if (GET_OP_CODE (scan) == BACK_REF_CI /* || GET_OP_CODE (scan) == X_REGEX_BR_CI*/) { while (captured < finish) { if (AT_END_OF_STRING (Reg_Input) || tolower (*captured++) != tolower (*Reg_Input++)) { MATCH_RETURN (0); } } } else { while (captured < finish) { if (AT_END_OF_STRING (Reg_Input) || *captured++ != *Reg_Input++) { MATCH_RETURN (0); } } } break; } else { MATCH_RETURN (0); } } case POS_AHEAD_OPEN: case NEG_AHEAD_OPEN: { register regularExp_CHAR *save; register regularExp_CHAR *saved_end; int answer; save = Reg_Input; /* Temporarily ignore the logical end of the string, to allow lookahead past the end. */ saved_end = End_Of_String; End_Of_String = NULL; answer = match (next, NULL); /* Does the look-ahead regex match? */ CHECK_RECURSION_LIMIT if ( (GET_OP_CODE (scan) == POS_AHEAD_OPEN) ? answer : !answer) { /* Remember the last (most to the right) character position that we consume in the input for a successful match. This is info that may be needed should an attempt be made to match the exact same text at the exact same place. Since look-aheads backtrack, a regex with a trailing look-ahead may need more text than it matches to accomplish a re-match. */ if (Extent_Ptr_FW == NULL || (Reg_Input - Extent_Ptr_FW) > 0) { Extent_Ptr_FW = Reg_Input; } Reg_Input = save; /* Backtrack to look-ahead start. */ End_Of_String = saved_end; /* Restore logical end. */ /* Jump to the node just after the (?=...) or (?!...) Construct. */ next = next_ptr (OPERAND (scan)); /* Skip 1st branch */ /* Skip the chain of branches inside the look-ahead */ while (GET_OP_CODE (next) == BRANCH) { next = next_ptr (next); } next = next_ptr (next); /* Skip the LOOK_AHEAD_CLOSE */ } else { Reg_Input = save; /* Backtrack to look-ahead start. */ End_Of_String = saved_end; /* Restore logical end. */ MATCH_RETURN (0); } } break; case POS_BEHIND_OPEN: case NEG_BEHIND_OPEN: { register regularExp_CHAR *save; int answer; register int offset, upper; int lower; int found = 0; regularExp_CHAR *saved_end; save = Reg_Input; saved_end = End_Of_String; /* Prevent overshoot (greedy matching could end past the current position) by tightening the matching boundary. Lookahead inside lookbehind can still cross that boundary. */ End_Of_String = Reg_Input; lower = GET_LOWER (scan); upper = GET_UPPER (scan); /* Start with the shortest match first. This is the most efficient direction in general. Note! Negative look behind is _very_ tricky when the length is not constant: we have to make sure the expression doesn't match for _any_ of the starting positions. */ for (offset = lower; offset <= upper; ++offset) { Reg_Input = save - offset; if (Reg_Input < Look_Behind_To) { /* No need to look any further */ break; } answer = match (next, NULL); /* Does the look-behind regex match? */ CHECK_RECURSION_LIMIT /* The match must have ended at the current position; otherwise it is invalid */ if (answer && Reg_Input == save) { /* It matched, exactly far enough */ found = 1; /* Remember the last (most to the left) character position that we consume in the input for a successful match. This is info that may be needed should an attempt be made to match the exact same text at the exact same place. Since look-behind backtracks, a regex with a leading look-behind may need more text than it matches to accomplish a re-match. */ if (Extent_Ptr_BW == NULL || (Extent_Ptr_BW - (save - offset)) > 0) { Extent_Ptr_BW = save - offset; } break; } } /* Always restore the position and the logical string end. */ Reg_Input = save; End_Of_String = saved_end; if ( (GET_OP_CODE (scan) == POS_BEHIND_OPEN) ? found : !found) { /* The look-behind matches, so we must jump to the next node. The look-behind node is followed by a chain of branches (contents of the look-behind expression), and terminated by a look-behind-close node. */ next = next_ptr (OPERAND (scan) + LENGTH_SIZE); /* 1st branch */ /* Skip the chained branches inside the look-ahead */ while (GET_OP_CODE (next) == BRANCH) { next = next_ptr (next); } next = next_ptr (next); /* Skip LOOK_BEHIND_CLOSE */ } else { /* Not a match */ MATCH_RETURN (0); } } break; case LOOK_AHEAD_CLOSE: case LOOK_BEHIND_CLOSE: MATCH_RETURN (1); /* We have reached the end of the look-ahead or look-behind which implies that we matched it, so return TRUE. */ default: if ( (GET_OP_CODE (scan) > OPEN) && (GET_OP_CODE (scan) < OPEN + NSUBEXP)) { register int no; register regularExp_CHAR *save; no = GET_OP_CODE (scan) - OPEN; save = Reg_Input; if (no < 10) { Back_Ref_Start [no] = save; Back_Ref_End [no] = NULL; } if (match (next, NULL)) { /* Do not set `Start_Ptr_Ptr' if some later invocation (think recursion) of the same parentheses already has. */ if (Start_Ptr_Ptr [no] == NULL) { Start_Ptr_Ptr [no] = save; } MATCH_RETURN (1); } else { MATCH_RETURN (0); } } else if ( (GET_OP_CODE (scan) > CLOSE) && (GET_OP_CODE (scan) < CLOSE + NSUBEXP)) { register int no; register regularExp_CHAR *save; no = GET_OP_CODE (scan) - CLOSE; save = Reg_Input; if (no < 10) { Back_Ref_End [no] = save; } if (match (next, NULL)) { /* Do not set `End_Ptr_Ptr' if some later invocation of the same parentheses already has. */ if (End_Ptr_Ptr [no] == NULL) { End_Ptr_Ptr [no] = save; } MATCH_RETURN (1); } else { MATCH_RETURN (0); } } else { reg_error (L"memory corruption, `match\'"); MATCH_RETURN (0); } break; } scan = next; } /* We get here only if there's trouble -- normally "case END" is the terminating point. */ reg_error (L"corrupted pointers, `match\'"); MATCH_RETURN (0); } /*----------------------------------------------------------------------* * greedy * * Repeatedly match something simple up to "max" times. If max <= 0 * then match as much as possible (max = infinity). Uses unsigned long * variables to maximize the amount of text matchable for unbounded * qualifiers like '*' and '+'. This will allow at least 4,294,967,295 * matches (4 Gig!) for an ANSI C compliant compiler. If you are * applying a regex to something bigger than that, you shouldn't be * using NEdit! * * Returns the actual number of matches. *----------------------------------------------------------------------*/ static unsigned long greedy (regularExp_CHAR *p, long max) { register regularExp_CHAR *input_str; register regularExp_CHAR *operand; register unsigned long count = REG_ZERO; register unsigned long max_cmp; input_str = Reg_Input; operand = OPERAND (p); /* Literal char or start of class characters. */ max_cmp = (max > 0) ? (unsigned long) max : ULONG_MAX; switch (GET_OP_CODE (p)) { case ANY: /* Race to the end of the line or string. Dot DOESN'T match newline. */ while (count < max_cmp && *input_str != '\n' && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case EVERY: /* Race to the end of the line or string. Dot DOES match newline. */ while (count < max_cmp && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case EXACTLY: /* Count occurrences of single character operand. */ while (count < max_cmp && *operand == *input_str && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case SIMILAR: /* Case insensitive version of EXACTLY */ while (count < max_cmp && *operand == tolower (*input_str) && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case ANY_OF: /* [...] character class. */ while (count < max_cmp && wcschr ( (wchar *) operand, (int) *input_str) != NULL && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case ANY_BUT: /* [^...] Negated character class- does NOT normally match newline (\n added usually to operand at compile time.) */ while (count < max_cmp && wcschr ( (wchar *) operand, (int) *input_str) == NULL && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case IS_DELIM: /* \y (not a word delimiter char) NOTE: '\n' and '\0' are always word delimiters. */ while (count < max_cmp && Current_Delimiters [ *input_str ] && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case NOT_DELIM: /* \Y (not a word delimiter char) NOTE: '\n' and '\0' are always word delimiters. */ while (count < max_cmp && !Current_Delimiters [ *input_str ] && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case WORD_CHAR: /* \w (word character, alpha-numeric or underscore) */ while (count < max_cmp && (isalnum ( (int) *input_str) || *input_str == (regularExp_CHAR) '_') && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case NOT_WORD_CHAR:/* \W (NOT a word character) */ while (count < max_cmp && !isalnum ( (int) *input_str) && *input_str != (regularExp_CHAR) '_' && *input_str != (regularExp_CHAR) '\n' && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case DIGIT: /* same as [0123456789] */ while (count < max_cmp && isdigit ( (int) *input_str) && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case NOT_DIGIT: /* same as [^0123456789] */ while (count < max_cmp && !isdigit ( (int) *input_str) && *input_str != '\n' && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case SPACE: /* same as [ \t\r\f\v]-- doesn't match newline. */ while (count < max_cmp && isspace ( (int) *input_str) && *input_str != '\n' && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case SPACE_NL: /* same as [\n \t\r\f\v]-- matches newline. */ while (count < max_cmp && isspace ( (int) *input_str) && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case NOT_SPACE: /* same as [^\n \t\r\f\v]-- doesn't match newline. */ while (count < max_cmp && !isspace ( (int) *input_str) && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case NOT_SPACE_NL: /* same as [^ \t\r\f\v]-- matches newline. */ while (count < max_cmp && (!isspace ( (int) *input_str) || *input_str == '\n') && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case LETTER: /* same as [a-zA-Z] */ while (count < max_cmp && isalpha ( (int) *input_str) && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; case NOT_LETTER: /* same as [^a-zA-Z] */ while (count < max_cmp && !isalpha ( (int) *input_str) && *input_str != '\n' && !AT_END_OF_STRING (input_str)) { count++; input_str++; } break; default: /* Called inappropriately. Only atoms that are SIMPLE should generate a call to greedy. The above cases should cover all the atoms that are SIMPLE. */ reg_error (L"internal error #10 `greedy\'"); count = 0U; /* Best we can do. */ } /* Point to character just after last matched character. */ Reg_Input = input_str; return (count); } /*----------------------------------------------------------------------* * next_ptr - compute the address of a node's "NEXT" pointer. * Note: a simplified inline version is available via the NEXT_PTR() macro, * but that one is only to be used at time-critical places (see the * description of the macro). *----------------------------------------------------------------------*/ static regularExp_CHAR *next_ptr (regularExp_CHAR *ptr) { register int offset; if (ptr == &Compute_Size) { return (NULL); } offset = GET_OFFSET (ptr); if (offset == 0) { return (NULL); } if (GET_OP_CODE (ptr) == BACK) { return (ptr - offset); } else { return (ptr + offset); } } /* ** SubstituteRE - Perform substitutions after a `regexp' match. ** ** This function cleanly shortens results of more than max length to max. ** To give the caller a chance to react to this the function returns False ** on any error. The substitution will still be executed. */ int SubstituteRE (const regexp *prog, const regularExp_CHAR *source, regularExp_CHAR *dest, int max, int *errorType) { register regularExp_CHAR *src; regularExp_CHAR *src_alias; register regularExp_CHAR *dst; register regularExp_CHAR c; register regularExp_CHAR test; register int paren_no; register int len; register regularExp_CHAR chgcase; int anyWarnings = FALSE; *errorType = 0; if (prog == NULL || source == NULL || dest == NULL) { reg_error (L"NULL parm to `SubstituteRE\'"); *errorType = 2; return FALSE; } if (U_CHAR_AT (prog->program) != MAGIC) { *errorType = 3; reg_error (L"damaged regexp passed to `SubstituteRE\'"); return FALSE; } src = (regularExp_CHAR *) source; dst = (regularExp_CHAR *) dest; while ( (c = *src++) != '\0') { chgcase = '\0'; paren_no = -1; if (c == '\\') { /* Process any case altering tokens, i.e \u, \U, \l, \L. */ if (*src == 'u' || *src == 'U' || *src == 'l' || *src == 'L') { chgcase = *src; src++; c = *src++; if (c == '\0') { break; } } } if (c == '&') { paren_no = 0; } else if (c == '\\') { /* Can not pass register variable `&src' to function `numeric_escape' so make a non-register copy that we can take the address of. */ src_alias = src; if ('1' <= *src && *src <= '9') { paren_no = (int) * src++ - (int) '0'; } else if ( (test = literal_escape (*src)) != '\0') { c = test; src++; } else if ( (test = numeric_escape (*src, &src_alias)) != '\0') { c = test; src = src_alias; src++; /* NOTE: if an octal escape for zero is attempted (e.g. \000), it will be treated as a literal string. */ } else if (*src == '\0') { /* If '\' is the last character of the replacement string, it is interpreted as a literal backslash. */ c = '\\'; } else { c = *src++; /* Allow any escape sequence (This is */ } /* INCONSISTENT with the `CompileRE' */ } /* mind set of issuing an error! */ if (paren_no < 0) { /* Ordinary character. */ if ( ( (regularExp_CHAR *) dst - (regularExp_CHAR *) dest) >= (max - 1)) { *errorType = 1; reg_error (L"replacing expression in `SubstituteRE\' too long; truncating"); anyWarnings = TRUE; break; } else { *dst++ = c; } } else if (prog->startp [paren_no] != NULL && prog->endp [paren_no] != NULL) { len = prog->endp [paren_no] - prog->startp [paren_no]; if ( ( (regularExp_CHAR *) dst + len - (regularExp_CHAR *) dest) >= max - 1) { *errorType = 1; reg_error (L"replacing expression in `SubstituteRE\' too long; truncating"); anyWarnings = TRUE; len = max - ( (regularExp_CHAR *) dst - (regularExp_CHAR *) dest) - 1; } (void) wcsncpy ( (wchar *) dst, (wchar *) prog->startp [paren_no], len); if (chgcase != '\0') { adjustcase (dst, len, chgcase); } dst += len; if (len != 0 && * (dst - 1) == '\0') { /* strncpy hit NUL. */ *errorType = 3; reg_error (L"damaged match string in `SubstituteRE\'"); anyWarnings = TRUE; } } } *dst = '\0'; return !anyWarnings; } static void adjustcase (regularExp_CHAR *str, int len, regularExp_CHAR chgcase) { register regularExp_CHAR *string = str; int i; /* The tokens \u and \l only modify the first character while the tokens \U and \L modify the entire string. */ if (islower (chgcase) && len > 0) { len = 1; } switch (chgcase) { case 'u': case 'U': for (i = 0; i < len; i++) { * (string + i) = toupper ( (int) * (string + i)); } break; case 'l': case 'L': for (i = 0; i < len; i++) { * (string + i) = tolower ( (int) * (string + i)); } break; } } /*----------------------------------------------------------------------* * reg_error *----------------------------------------------------------------------*/ static void reg_error (const wchar *str) { Melder_error_ ("Internal error processing regular expression: ", str); } /*----------------------------------------------------------------------* * makeDelimiterTable * * Translate a null-terminated string of delimiters into a 256 byte * lookup table for determining whether a character is a delimiter or * not. * * Table must be allocated by the caller. * * Return value is a pointer to the table. *----------------------------------------------------------------------*/ static regularExp_CHAR *makeDelimiterTable ( regularExp_CHAR *delimiters, regularExp_CHAR *table) { regularExp_CHAR *c; memset (table, 0, 256); for (c = (regularExp_CHAR *) delimiters; *c != '\0'; c++) { table [*c] = 1; } table [ (int) '\0'] = 1; /* These */ table [ (int) '\t'] = 1; /* characters */ table [ (int) '\n'] = 1; /* are always */ table [ (int) ' ' ] = 1; /* delimiters. */ return table; } /*----------------------------------------------------------------------* * SetREDefaultWordDelimiters * * Builds a default delimiter table that persists across `ExecRE' calls. *----------------------------------------------------------------------*/ void SetREDefaultWordDelimiters (regularExp_CHAR *delimiters) { makeDelimiterTable (delimiters, Default_Delimiters); } void EnableCountingQuantifier (int is_enabled) { Enable_Counting_Quantifier = is_enabled; } sources_5316/dwsys/SVD.h0000644000176700017670000000534711627165140013715 0ustar paulpaul/* SVD.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020423 GPL header djmw 20110306 Latest modification. */ #ifndef _SVD_h_ #define _SVD_h_ #include "NUM2.h" #include "Data.h" #include "SVD_def.h" oo_CLASS_CREATE (SVD, Data); #define GSVD__methods(klas) Data__methods(klas) oo_CLASS_CREATE (GSVD, Data); void SVD_init (I, long numberOfRows, long numberOfColumns); SVD SVD_create (long numberOfRows, long numberOfColumns); /* my tolerance = eps * MAX (numberOfRows, numberOfColumns) where eps is the floating point precision, approximately 2.2e-16 */ SVD SVD_create_d (double **m, long numberOfRows, long numberOfColumns); SVD SVD_create_f (float **m, long numberOfRows, long numberOfColumns); /* Copy matrix into svd->u and calculate U D V' */ void SVD_svd_d (SVD me, double **m); void SVD_svd_f (SVD me, float **m); /* Perform SVD analysis on matrix M, i.e., decompose M as M = UDV'. Watch out: dataType contains V, not V' !! */ void SVD_compute (SVD me); void SVD_solve (SVD me, double b[], double x[]); /* Solve Ax = b */ void SVD_sort (SVD me); /* Sort singular values (and corresponding column vectors of U and V) in decreasing order. */ void SVD_setTolerance (SVD me, double tolerance); double SVD_getTolerance (SVD me); long SVD_zeroSmallSingularValues (SVD me, double tolerance); /* Zero singular values smaller than maximum_singular_value * tolerance If tolerance == 0 then then my tolerance will be used. Return the number of s.v.'s zeroed. */ void SVD_synthesize (SVD me, long sv_from, long sv_to, double **m); /* Synthesize matrix as U D(sv_from:sv_to) V'. (The synthesized matrix is an approximation of the svd'ed matrix with only a selected number of sv's). Matrix m is [numberOfRows x numberOfColumns] and must be allocated by caller! */ long SVD_getRank (SVD me); GSVD GSVD_create (long numberOfColumns); GSVD GSVD_create_d (double **m1, long numberOfRows1, long numberOfColumns, double **m2, long numberOfRows2); void GSVD_setTolerance (GSVD me, double tolerance); double GSVD_getTolerance (GSVD me); #endif /* _SVD_h_ */ sources_5316/dwsys/Makefile0000664000176700017670000000140111723710247014536 0ustar paulpaul# makefile for library "dwsys". # David Weenink 20120130 include ../makefile.defs CPPFLAGS = -I ../stat -I ../num -I ../sys -I dwsys -I ../external/gsl -I ../kar all: libdwsys.a OBJECTS = Collection_extensions.o Command.o \ DLL.o Eigen.o FileInMemory.o Index.o \ NUM2.o NUMhuber.o NUMlapack.o NUMmachar.o \ NUMf2c.o NUMcblas.o NUMclapack.o NUMfft_d.o NUMsort2.o \ Permutation.o Permutation_and_Index.o \ regularExp.o SimpleVector.o Simple_extensions.o \ SVD.o .PHONY: all clean all: libdwsys.a clean: $(RM) $(OBJECTS) $(RM) libdwsys.a libdwsys.a: $(OBJECTS) NUMmachar.o touch libdwsys.a rm libdwsys.a ar cq libdwsys.a $(OBJECTS) $(RANLIB) libdwsys.a $(OBJECTS): *.h ../stat/*.h ../num/NUM.h ../sys/*.h ../external/gsl/*.h ../dwsys/*.h ../kar/*.h sources_5316/dwsys/NUMhuber.cpp0000644000176700017670000000556011652257762015310 0ustar paulpaul/* NUMhuber.c * * Copyright (C) 1994-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030814 First version djmw 20080122 float -> double */ #include "NUM2.h" void NUMmad (double *x, long n, double *location, int wantlocation, double *mad, double *work) { double *tmp = work; *mad = NUMundefined; if (n < 1) { Melder_throw ("The dimension must be at least 1"); } if (n == 1) { *location = x[1]; return; } autoNUMvector atmp; if (work == 0) { atmp.reset (1, n); tmp = atmp.peek(); } for (long i = 1; i <= n; i++) { tmp[i] = x[i]; } if (wantlocation) { NUMsort_d (n, tmp); *location = NUMquantile (n, tmp, 0.5); } for (long i = 1; i <= n; i++) { tmp[i] = fabs (tmp[i] - *location); } NUMsort_d (n, tmp); *mad = 1.4826 * NUMquantile (n, tmp, 0.5); } static double NUMgauss (double x) { return NUM1_sqrt2pi * exp (- 0.5 * x * x); } void NUMstatistics_huber (double *x, long n, double *location, int wantlocation, double *scale, int wantscale, double k, double tol, double *work) { double *tmp = work; double theta = 2 * NUMgaussP (k) - 1; double beta = theta + k * k * (1 - theta) - 2 * k * NUMgauss (k); long n1 = n; autoNUMvector atmp; if (work == 0) { atmp.reset (1, n); tmp = atmp.peek(); } double mad; NUMmad (x, n, location, wantlocation, & mad, tmp); if (wantscale) { *scale = mad; } if (*scale == 0) { Melder_throw ("Scale is zero."); } double mu0, mu1 = *location; double s0, s1 = *scale; if (wantlocation) { n1 = n - 1; } do { mu0 = mu1; s0 = s1; double low = mu0 - k * s0; double high = mu0 + k * s0; for (long i = 1; i <= n; i++) { if (x[i] < low) { tmp[i] = low; } else if (x[i] > high) { tmp[i] = high; } else { tmp[i] = x[i]; } } if (wantlocation) { mu1 = 0; for (long i = 1; i <= n; i++) { mu1 += tmp[i]; } mu1 /= n; } if (wantscale) { s1 = 0; for (long i = 1; i <= n; i++) { double dx = tmp[i] - mu1; s1 += dx * dx; } s1 = sqrt (s1 / (n1 * beta)); } } while (fabs (mu0 - mu1) > tol * s0 || fabs (s0 - s1) > tol * s0); //TODO fabs (mu0 - mu1) > tol * s0 ?? if (wantlocation) { *location = mu1; } if (wantscale) { *scale = s1; } } sources_5316/dwsys/NUMmachar.h0000644000176700017670000000323711630130227015060 0ustar paulpaul#ifndef _NUMmachar_h_ #define _NUMmachar_h_ /* NUMmachar.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20110308 Latest modification */ #ifdef __cplusplus extern "C" { #endif struct structmachar_Table { int base; /* Radix in which numbers are presented. */ int t; /* Number of base digits in mantissa*/ int emin; /* Minimum exponent before (gradual) underflow */ int emax; /* Largest exponent before overflow */ int rnd; /* 1 when rounding occurs in addition, 0 otherwise */ double prec; /* Quantization step (eps*base) */ double eps; /* Quantization error (relative machine precision) */ double rmin; /* Underflow threshold - base**(emin-1) */ double sfmin; /* Safe minimum, such that 1/sfmin does not overflow */ double rmax; /* Overflow threshold - (base**emax)*(1-eps)*/ }; typedef struct structmachar_Table *machar_Table; extern machar_Table NUMfpp; void NUMmachar (); #ifdef __cplusplus } #endif #endif /* _NUMmachar_h_ */ sources_5316/dwsys/NUMsort2.cpp0000644000176700017670000001172011725121521015227 0ustar paulpaul/* NUMsort.c * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20030121 Initial version djmw 20030627 Removed bug in MACRO_NUMindex djmw 20120305 Latest modification */ #include "NUM2.h" #include "melder.h" /* NUMsort2 uses heapsort to sort the second array in parallel with the first one. Algorithm follows p. 145 and 642 in: Donald E. Knuth (1998): The art of computer programming. Third edition. Vol. 3: sorting and searching. Boston: Addison-Wesley, printed may 2002. Modification: there is no distinction between record and key and Floyd's optimization (page 642) is used. */ void NUMrankColumns (double **m, long rb, long re, long cb, long ce) { long nr = re - rb + 1; autoNUMvector v (1, nr); autoNUMvector index (1, nr); for (long j = cb; j <= ce; j++) { for (long i = 1; i <= nr; i++) { v[i] = m[rb + i - 1][j]; } for (long i = 1; i <= nr; i++) { index[i] = i; } NUMsort2 (nr, v.peek(), index.peek()); NUMrank (nr, v.peek()); for (long i = 1; i <= nr; i++) { m[rb + index[i] - 1][j] = v[i]; } } } #define MACRO_NUMindex(TYPE) \ { \ long l, r, j, i, ii, k, imin; \ TYPE min; \ for (j = 1; j <= n; j++) index[j] = j; \ if (n < 2) return; /* Already sorted. */ \ if (n == 2) \ { \ if (COMPARELT(a[2], a[1])) \ {\ index[1] = 2; index[2] = 1; \ } \ return; \ } \ if (n <= 12) \ { \ for (i = 1; i < n; i++) \ { \ imin = i; \ min = a[index[imin]]; \ for (j = i + 1; j <= n; j++) \ {\ if (COMPARELT(a[index[j]], min))\ { \ imin = j; \ min = a[index[j]]; \ } \ } \ ii = index[imin]; index[imin] = index[i]; index[i] = ii; \ } \ return; \ } \ /* H1 */\ l = n / 2 + 1; \ r = n; \ for (;;) /* H2 */\ { \ if (l > 1) \ { \ l--; \ k = index[l]; \ } \ else /* l == 1 */ \ { \ k = index[r]; \ index[r] = index[1]; \ r--; \ if (r == 1) \ { \ index[1] = k; break; \ } \ } \ /* H3 */ \ j = l; \ for (;;) \ { \ /* H4 */ \ i = j; \ j *= 2; \ if (j > r) break; \ if (j < r && COMPARELT (a[index[j]], a[index[j + 1]])) j++; /* H5 */\ index[i] = index[j]; /* H7 */\ } \ for (;;) /*H8' */\ {\ j = i; \ i = j >> 1; \ /* H9' */ \ if (j == l || COMPARELT (a[k], a[index[i]])) \ { \ index[j] = k; break; \ } \ index[j] = index[i]; \ }\ } \ } #define COMPARELT(x,y) ((x) < (y)) void NUMindexx_f (const float a[], long n, long index[]) MACRO_NUMindex (float) void NUMindexx (const double a[], long n, long index[]) MACRO_NUMindex (float) #undef COMPARELT #define COMPARELT(x,y) (Melder_wcscmp (x,y) < 0) void NUMindexx_s (wchar_t **a, long n, long index[]) MACRO_NUMindex (wchar_t *) #undef COMPARELT #undef MACRO_INDEXX /* Knuth's heapsort algorithm (vol. 3, page 145), modified with Floyd's optimization (vol. 3, page 642). */ #define MACRO_NUMsortkf(TYPE) { \ long l, r, j, i, imin; \ TYPE k, min; \ if (n < 2) return; /* Already sorted. */ \ /* This n<2 step is absent from Press et al.'s implementation, */ \ /* which will therefore not terminate on if(--ir==1). */ \ /* Knuth's initial assumption is now fulfilled: n >= 2. */ \ if (n == 2) \ { \ if (a[1] > a[2]) \ {\ min = a[2]; a[2] = a[1]; a[1] = min; \ } \ return; \ } \ if (n <= 12) \ { \ for (i = 1; i < n; i++) \ { \ min = a[i]; \ imin = i; \ for (j = i + 1; j <= n; j++) \ {\ if (a[j] < min)\ { \ min = a [j]; \ imin = j; \ } \ } \ a[imin] = a[i]; \ a[i] = min; \ } \ return; \ } \ /* H1 */\ l = (n >> 1) + 1; \ r = n; \ for (;;) /* H2 */\ { \ if (l > 1) \ { \ l--; \ k = a[l]; \ } \ else /* l == 1 */ \ { \ k = a[r]; \ a[r] = a[1]; \ r--; \ if (r == 1) \ { \ a[1] = k; return; \ } \ } \ /* H3 */ \ j = l; \ for (;;) \ { \ /* H4 */ \ i = j; \ j = j << 1; \ if (j > r) break; \ if (j < r && a[j] < a[j + 1]) j++; /* H5 */\ /*if (k >= a[j]) break; */\ a[i] = a[j]; /* H7 */\ } \ /* a[i] = k; H8 */\ for (;;) /*H8' */\ {\ j = i; \ i = j >> 1; \ /* H9' */ \ if (j == l || k <= a[i]) \ { \ a[j] = k; break; \ } \ a[j] = a[i]; \ }\ } \ } void NUMsort1_d (long n, double a[]); void NUMsort1_d (long n, double a[]) MACRO_NUMsortkf (double) #undef MACRO_NUMsortkf /* End of file NUMsort.c */ sources_5316/dwsys/SimpleVector.cpp0000644000176700017670000000441311725072730016222 0ustar paulpaul/* SimpleVector.cpp * * Copyright (C) 1994-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h */ #include "SimpleVector.h" #include "oo_DESTROY.h" #include "SimpleVector_def.h" #include "oo_COPY.h" #include "SimpleVector_def.h" #include "oo_EQUAL.h" #include "SimpleVector_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "SimpleVector_def.h" #include "oo_WRITE_TEXT.h" #include "SimpleVector_def.h" #include "oo_WRITE_BINARY.h" #include "SimpleVector_def.h" #include "oo_READ_TEXT.h" #include "SimpleVector_def.h" #include "oo_READ_BINARY.h" #include "SimpleVector_def.h" #include "oo_DESCRIPTION.h" #include "SimpleVector_def.h" Thing_implement (DoubleVector, Data, 0); void DoubleVector_init (I, long min, long max) { iam (DoubleVector); my min = min; my max = max; my v = NUMvector (min, max); } DoubleVector DoubleVector_create (long min, long max) { try { autoDoubleVector me = Thing_new (DoubleVector); DoubleVector_init (me.peek(), min, max); return me.transfer(); } catch (MelderError) { Melder_throw ("DoubleVector not created."); } } Thing_implement (ComplexVector, Data, 0); void ComplexVector_init (I, long min, long max) { iam (ComplexVector); my min = min; my max = max; my v = NUMvector (min, max); } ComplexVector ComplexVector_create (long min, long max) { try { autoComplexVector me = Thing_new (ComplexVector); ComplexVector_init (me.peek(), min, max); return me.transfer(); } catch (MelderError) { Melder_throw ("ComplexVector not created."); } } /* End of file SimpleVector.cpp */ sources_5316/dwsys/NUMclapack.h0000644000176700017670000073004411607613722015240 0ustar paulpaul#ifndef _NUMclapack_h_ #define _NUMclapack_h_ /* NUMclapack.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020923 GPL header djmw 20030310 Latest modification */ /* The following routines all use FORTRAN column-major storage of matrices. A consequence is that all matrices must have been allocated as a single block of mxn elements. All matrices are passed as a vector of mxn elements. matrix[i][j] => vector[(j-1)*m + i] "Fortran" matrix[i][j] => vector[(i-1)*n + j] "C" The consequence is that you have to transpose C matrices before you pass them to a CLAPACK routine. Sometimes you can avoid transposition by considering the solution of the transposed problem (e.g. See code in SVD_compute). */ #ifdef __cplusplus extern "C" { #endif int NUMlapack_dbdsqr(const char *uplo, long *n, long *ncvt, long *nru, long *ncc, double *d, double *e, double *vt, long *ldvt, double *u, long *ldu, double *c, long *ldc, double *work, long *info); /* Purpose ======= NUMlapack_dbdsqr computes the singular value decomposition (SVD) of a real N-by-N (upper or lower) bidiagonal matrix B: B = Q * S * P' (P' denotes the transpose of P), where S is a diagonal matrix with non-negative diagonal elements (the singular values of B), and Q and P are orthogonal matrices. The routine computes S, and optionally computes U * Q, P' * VT, or Q' * C, for given real input matrices U, VT, and C. See "Computing Small Singular Values of Bidiagonal Matrices With Guaranteed High Relative Accuracy," by J. Demmel and W. Kahan, LAPACK Working Note #3 (or SIAM J. Sci. Statist. Comput. vol. 11, no. 5, pp. 873-912, Sept 1990) and "Accurate singular values and differential qd algorithms," by B. Parlett and V. Fernando, Technical Report CPAM-554, Mathematics Department, University of California at Berkeley, July 1992 for a detailed description of the algorithm. Arguments ========= UPLO (input) char* = 'U': B is upper bidiagonal; = 'L': B is lower bidiagonal. N (input) long The order of the matrix B. N >= 0. NCVT (input) long The number of columns of the matrix VT. NCVT >= 0. NRU (input) long The number of rows of the matrix U. NRU >= 0. NCC (input) long The number of columns of the matrix C. NCC >= 0. D (input/output) double array, dimension (N) On entry, the n diagonal elements of the bidiagonal matrix B. On exit, if INFO=0, the singular values of B in decreasing order. E (input/output) double array, dimension (N) On entry, the elements of E contain the offdiagonal elements of the bidiagonal matrix whose SVD is desired. On normal exit (INFO = 0), E is destroyed. If the algorithm does not converge (INFO > 0), D and E will contain the diagonal and superdiagonal elements of a bidiagonal matrix orthogonally equivalent to the one given as input. E(N) is used for workspace. VT (input/output) double array, dimension (LDVT, NCVT) On entry, an N-by-NCVT matrix VT. On exit, VT is overwritten by P' * VT. VT is not referenced if NCVT = 0. LDVT (input) long The leading dimension of the array VT. LDVT >= max(1,N) if NCVT > 0; LDVT >= 1 if NCVT = 0. U (input/output) double array, dimension (LDU, N) On entry, an NRU-by-N matrix U. On exit, U is overwritten by U * Q. U is not referenced if NRU = 0. LDU (input) long The leading dimension of the array U. LDU >= max(1,NRU). C (input/output) double array, dimension (LDC, NCC) On entry, an N-by-NCC matrix C. On exit, C is overwritten by Q' * C. C is not referenced if NCC = 0. LDC (input) long The leading dimension of the array C. LDC >= max(1,N) if NCC > 0; LDC >=1 if NCC = 0. WORK (workspace) double array, dimension (4*N) INFO (output) long = 0: successful exit < 0: If INFO = -i, the i-th argument had an illegal value > 0: the algorithm did not converge; D and E contain the elements of a bidiagonal matrix which is orthogonally similar to the input matrix B; if INFO = i, i elements of E have not converged to zero. Internal Parameters =================== TOLMUL double, default = max(10,min(100,EPS**(-1/8))) TOLMUL controls the convergence criterion of the QR loop. If it is positive, TOLMUL*EPS is the desired relative precision in the computed singular values. If it is negative, abs(TOLMUL*EPS*sigma_max) is the desired absolute accuracy in the computed singular values (corresponds to relative accuracy abs(TOLMUL*EPS) in the largest singular value. abs(TOLMUL) should be between 1 and 1/EPS, and preferably between 10 (for fast convergence) and .1/EPS (for there to be some accuracy in the results). Default is to lose at either one eighth or 2 of the available decimal digits in each computed singular value (whichever is smaller). MAXITR long, default = 6 MAXITR controls the maximum number of passes of the algorithm through its inner loop. The algorithms stops (and so fails to converge) if the number of passes through the inner loop exceeds MAXITR*N**2. ===================================================================== */ int NUMlapack_dgebd2(long *m, long *n, double *a, long *lda, double *d, double *e, double *tauq, double *taup, double *work, long *info); /* Purpose ======= NUMlapack_dgebd2 reduces a real general m by n matrix A to upper or lower bidiagonal form B by an orthogonal transformation: Q' * A * P = B. If m >= n, B is upper bidiagonal; if m < n, B is lower bidiagonal. Arguments ========= M (input) long The number of rows in the matrix A. M >= 0. N (input) long The number of columns in the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the m by n general matrix to be reduced. On exit, if m >= n, the diagonal and the first superdiagonal are overwritten with the upper bidiagonal matrix B; the elements below the diagonal, with the array TAUQ, represent the orthogonal matrix Q as a product of elementary reflectors, and the elements above the first superdiagonal, with the array TAUP, represent the orthogonal matrix P as a product of elementary reflectors; if m < n, the diagonal and the first subdiagonal are overwritten with the lower bidiagonal matrix B; the elements below the first subdiagonal, with the array TAUQ, represent the orthogonal matrix Q as a product of elementary reflectors, and the elements above the diagonal, with the array TAUP, represent the orthogonal matrix P as a product of elementary reflectors. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). D (output) double array, dimension (min(M,N)) The diagonal elements of the bidiagonal matrix B: D(i) = A(i,i). E (output) double array, dimension (min(M,N)-1) The off-diagonal elements of the bidiagonal matrix B: if m >= n, E(i) = A(i,i+1) for i = 1,2,...,n-1; if m < n, E(i) = A(i+1,i) for i = 1,2,...,m-1. TAUQ (output) double array dimension (min(M,N)) The scalar factors of the elementary reflectors which represent the orthogonal matrix Q. See Further Details. TAUP (output) double array, dimension (min(M,N)) The scalar factors of the elementary reflectors which represent the orthogonal matrix P. See Further Details. WORK (workspace) double array, dimension (max(M,N)) INFO (output) long = 0: successful exit. < 0: if INFO = -i, the i-th argument had an illegal value. Further Details =============== The matrices Q and P are represented as products of elementary reflectors: If m >= n, Q = H(1) H(2) . . . H(n) and P = G(1) G(2) . . . G(n-1) Each H(i) and G(i) has the form: H(i) = I - tauq * v * v' and G(i) = I - taup * u * u' where tauq and taup are real scalars, and v and u are real vectors; v(1:i-1) = 0, v(i) = 1, and v(i+1:m) is stored on exit in A(i+1:m,i); u(1:i) = 0, u(i+1) = 1, and u(i+2:n) is stored on exit in A(i,i+2:n); tauq is stored in TAUQ(i) and taup in TAUP(i). If m < n, Q = H(1) H(2) . . . H(m-1) and P = G(1) G(2) . . . G(m) Each H(i) and G(i) has the form: H(i) = I - tauq * v * v' and G(i) = I - taup * u * u' where tauq and taup are real scalars, and v and u are real vectors; v(1:i) = 0, v(i+1) = 1, and v(i+2:m) is stored on exit in A(i+2:m,i); u(1:i-1) = 0, u(i) = 1, and u(i+1:n) is stored on exit in A(i,i+1:n); tauq is stored in TAUQ(i) and taup in TAUP(i). The contents of A on exit are illustrated by the following examples: m = 6 and n = 5 (m > n): m = 5 and n = 6 (m < n): ( d e u1 u1 u1 ) ( d u1 u1 u1 u1 u1 ) ( v1 d e u2 u2 ) ( e d u2 u2 u2 u2 ) ( v1 v2 d e u3 ) ( v1 e d u3 u3 u3 ) ( v1 v2 v3 d e ) ( v1 v2 e d u4 u4 ) ( v1 v2 v3 v4 d ) ( v1 v2 v3 e d u5 ) ( v1 v2 v3 v4 v5 ) where d and e denote diagonal and off-diagonal elements of B, vi denotes an element of the vector defining H(i), and ui an element of the vector defining G(i). ===================================================================== */ int NUMlapack_dgebrd(long *m, long *n, double *a, long *lda, double *d, double *e, double *tauq, double *taup, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dgebrd reduces a general real M-by-N matrix A to upper or lower bidiagonal form B by an orthogonal transformation: Q**T * A * P = B. If m >= n, B is upper bidiagonal; if m < n, B is lower bidiagonal. Arguments ========= M (input) long The number of rows in the matrix A. M >= 0. N (input) long The number of columns in the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the M-by-N general matrix to be reduced. On exit, if m >= n, the diagonal and the first superdiagonal are overwritten with the upper bidiagonal matrix B; the elements below the diagonal, with the array TAUQ, represent the orthogonal matrix Q as a product of elementary reflectors, and the elements above the first superdiagonal, with the array TAUP, represent the orthogonal matrix P as a product of elementary reflectors; if m < n, the diagonal and the first subdiagonal are overwritten with the lower bidiagonal matrix B; the elements below the first subdiagonal, with the array TAUQ, represent the orthogonal matrix Q as a product of elementary reflectors, and the elements above the diagonal, with the array TAUP, represent the orthogonal matrix P as a product of elementary reflectors. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). D (output) double array, dimension (min(M,N)) The diagonal elements of the bidiagonal matrix B: D(i) = A(i,i). E (output) double array, dimension (min(M,N)-1) The off-diagonal elements of the bidiagonal matrix B: if m >= n, E(i) = A(i,i+1) for i = 1,2,...,n-1; if m < n, E(i) = A(i+1,i) for i = 1,2,...,m-1. TAUQ (output) double array dimension (min(M,N)) The scalar factors of the elementary reflectors which represent the orthogonal matrix Q. See Further Details. TAUP (output) double array, dimension (min(M,N)) The scalar factors of the elementary reflectors which represent the orthogonal matrix P. See Further Details. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The length of the array WORK. LWORK >= max(1,M,N). For optimum performance LWORK >= (M+N)*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value. Further Details =============== The matrices Q and P are represented as products of elementary reflectors: If m >= n, Q = H(1) H(2) . . . H(n) and P = G(1) G(2) . . . G(n-1) Each H(i) and G(i) has the form: H(i) = I - tauq * v * v' and G(i) = I - taup * u * u' where tauq and taup are real scalars, and v and u are real vectors; v(1:i-1) = 0, v(i) = 1, and v(i+1:m) is stored on exit in A(i+1:m,i); u(1:i) = 0, u(i+1) = 1, and u(i+2:n) is stored on exit in A(i,i+2:n); tauq is stored in TAUQ(i) and taup in TAUP(i). If m < n, Q = H(1) H(2) . . . H(m-1) and P = G(1) G(2) . . . G(m) Each H(i) and G(i) has the form: H(i) = I - tauq * v * v' and G(i) = I - taup * u * u' where tauq and taup are real scalars, and v and u are real vectors; v(1:i) = 0, v(i+1) = 1, and v(i+2:m) is stored on exit in A(i+2:m,i); u(1:i-1) = 0, u(i) = 1, and u(i+1:n) is stored on exit in A(i,i+1:n); tauq is stored in TAUQ(i) and taup in TAUP(i). The contents of A on exit are illustrated by the following examples: m = 6 and n = 5 (m > n): m = 5 and n = 6 (m < n): ( d e u1 u1 u1 ) ( d u1 u1 u1 u1 u1 ) ( v1 d e u2 u2 ) ( e d u2 u2 u2 u2 ) ( v1 v2 d e u3 ) ( v1 e d u3 u3 u3 ) ( v1 v2 v3 d e ) ( v1 v2 e d u4 u4 ) ( v1 v2 v3 v4 d ) ( v1 v2 v3 e d u5 ) ( v1 v2 v3 v4 v5 ) where d and e denote diagonal and off-diagonal elements of B, vi denotes an element of the vector defining H(i), and ui an element of the vector defining G(i). ===================================================================== */ int NUMlapack_dgebak (const char *job, const char *side, long *n, long *ilo, long *ihi, double *scale, long *m, double *v, long *ldv, long *info); /* -- LAPACK routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University September 30, 1994 Purpose ======= NUMlapack_dgebak forms the right or left eigenvectors of a real general matrix by backward transformation on the computed eigenvectors of the balanced matrix output by NUMlapack_dgebal. Arguments ========= JOB (input) char* Specifies the type of backward transformation required: = 'N', do nothing, return immediately; = 'P', do backward transformation for permutation only; = 'S', do backward transformation for scaling only; = 'B', do backward transformations for both permutation and scaling. JOB must be the same as the argument JOB supplied to NUMlapack_dgebal. SIDE (input) char* = 'R': V contains right eigenvectors; = 'L': V contains left eigenvectors. N (input) long The number of rows of the matrix V. N >= 0. ILO (input) long IHI (input) long The integers ILO and IHI determined by NUMlapack_dgebal. 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0. SCALE (input) double array, dimension (N) Details of the permutation and scaling factors, as returned by NUMlapack_dgebal. M (input) long The number of columns of the matrix V. M >= 0. V (input/output) double array, dimension (LDV,M) On entry, the matrix of right or left eigenvectors to be transformed, as returned by DHSEIN or NUMlapack_dtrevc. On exit, V is overwritten by the transformed eigenvectors. LDV (input) long The leading dimension of the array V. LDV >= max(1,N). INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value. ===================================================================== */ int NUMlapack_dgebal (const char *job, long *n, double *a, long *lda, long *ilo, long *ihi, double *scale, long *info); /* -- LAPACK routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University June 30, 1999 Purpose ======= NUMlapack_dgebal balances a general real matrix A. This involves, first, permuting A by a similarity transformation to isolate eigenvalues in the first 1 to ILO-1 and last IHI+1 to N elements on the diagonal; and second, applying a diagonal similarity transformation to rows and columns ILO to IHI to make the rows and columns as close in norm as possible. Both steps are optional. Balancing may reduce the 1-norm of the matrix, and improve the accuracy of the computed eigenvalues and/or eigenvectors. Arguments ========= JOB (input) char* Specifies the operations to be performed on A: = 'N': none: simply set ILO = 1, IHI = N, SCALE(I) = 1.0 for i = 1,...,N; = 'P': permute only; = 'S': scale only; = 'B': both permute and scale. N (input) long The order of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the input matrix A. On exit, A is overwritten by the balanced matrix. If JOB = 'N', A is not referenced. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). ILO (output) long IHI (output) long ILO and IHI are set to integers such that on exit A(i,j) = 0 if i > j and j = 1,...,ILO-1 or I = IHI+1,...,N. If JOB = 'N' or 'S', ILO = 1 and IHI = N. SCALE (output) double array, dimension (N) Details of the permutations and scaling factors applied to A. If P(j) is the index of the row and column interchanged with row and column j and D(j) is the scaling factor applied to row and column j, then SCALE(j) = P(j) for j = 1,...,ILO-1 = D(j) for j = ILO,...,IHI = P(j) for j = IHI+1,...,N. The order in which the interchanges are made is N to IHI+1, then 1 to ILO-1. INFO (output) long = 0: successful exit. < 0: if INFO = -i, the i-th argument had an illegal value. Further Details =============== The permutations consist of row and column interchanges which put the matrix in the form ( T1 X Y ) P A P = ( 0 B Z ) ( 0 0 T2 ) where T1 and T2 are upper triangular matrices whose eigenvalues lie along the diagonal. The column indices ILO and IHI mark the starting and ending columns of the submatrix B. Balancing consists of applying a diagonal similarity transformation inv(D) * B * D to make the 1-norms of each row of B and its corresponding column nearly equal. The output matrix is ( T1 X*D Y ) ( 0 inv(D)*B*D inv(D)*Z ). ( 0 0 T2 ) Information about the permutations P and the diagonal matrix D is returned in the vector SCALE. This subroutine is based on the EISPACK routine BALANC. Modified by Tzu-Yi Chen, Computer Science Division, University of California at Berkeley, USA ===================================================================== */ int NUMlapack_dgeev (const char *jobvl, const char *jobvr, long *n, double *a, long *lda, double *wr, double *wi, double *vl, long *ldvl, double *vr, long *ldvr, double *work, long *lwork, long *info); /* -- LAPACK driver routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University December 8, 1999 Purpose ======= NUMlapack_dgeev computes for an N-by-N real nonsymmetric matrix A, the eigenvalues and, optionally, the left and/or right eigenvectors. The right eigenvector v(j) of A satisfies A * v(j) = lambda(j) * v(j) where lambda(j) is its eigenvalue. The left eigenvector u(j) of A satisfies u(j)**H * A = lambda(j) * u(j)**H where u(j)**H denotes the conjugate transpose of u(j). The computed eigenvectors are normalized to have Euclidean norm equal to 1 and largest component real. Arguments ========= JOBVL (input) char* = 'N': left eigenvectors of A are not computed; = 'V': left eigenvectors of A are computed. JOBVR (input) char* = 'N': right eigenvectors of A are not computed; = 'V': right eigenvectors of A are computed. N (input) long The order of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the N-by-N matrix A. On exit, A has been overwritten. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). WR (output) double array, dimension (N) WI (output) double array, dimension (N) WR and WI contain the real and imaginary parts, respectively, of the computed eigenvalues. Complex conjugate pairs of eigenvalues appear consecutively with the eigenvalue having the positive imaginary part first. VL (output) double array, dimension (LDVL,N) If JOBVL = 'V', the left eigenvectors u(j) are stored one after another in the columns of VL, in the same order as their eigenvalues. If JOBVL = 'N', VL is not referenced. If the j-th eigenvalue is real, then u(j) = VL(:,j), the j-th column of VL. If the j-th and (j+1)-st eigenvalues form a complex conjugate pair, then u(j) = VL(:,j) + i*VL(:,j+1) and u(j+1) = VL(:,j) - i*VL(:,j+1). LDVL (input) long The leading dimension of the array VL. LDVL >= 1; if JOBVL = 'V', LDVL >= N. VR (output) double array, dimension (LDVR,N) If JOBVR = 'V', the right eigenvectors v(j) are stored one after another in the columns of VR, in the same order as their eigenvalues. If JOBVR = 'N', VR is not referenced. If the j-th eigenvalue is real, then v(j) = VR(:,j), the j-th column of VR. If the j-th and (j+1)-st eigenvalues form a complex conjugate pair, then v(j) = VR(:,j) + i*VR(:,j+1) and v(j+1) = VR(:,j) - i*VR(:,j+1). LDVR (input) long The leading dimension of the array VR. LDVR >= 1; if JOBVR = 'V', LDVR >= N. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,3*N), and if JOBVL = 'V' or JOBVR = 'V', LWORK >= 4*N. For good performance, LWORK must generally be larger. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value. > 0: if INFO = i, the QR algorithm failed to compute all the eigenvalues, and no eigenvectors have been computed; elements i+1:N of WR and WI contain eigenvalues which have converged. ===================================================================== */ int NUMlapack_dgehd2 (long *n, long *ilo, long *ihi, double *a, long *lda, double *tau, double *work, long *info); /* -- LAPACK routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University October 31, 1992 Purpose ======= NUMlapack_dgehd2 reduces a real general matrix A to upper Hessenberg form H by an orthogonal similarity transformation: Q' * A * Q = H . Arguments ========= N (input) long The order of the matrix A. N >= 0. ILO (input) long IHI (input) long It is assumed that A is already upper triangular in rows and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally set by a previous call to NUMlapack_dgebal; otherwise they should be set to 1 and N respectively. See Further Details. 1 <= ILO <= IHI <= max(1,N). A (input/output) double array, dimension (LDA,N) On entry, the n by n general matrix to be reduced. On exit, the upper triangle and the first subdiagonal of A are overwritten with the upper Hessenberg matrix H, and the elements below the first subdiagonal, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). TAU (output) double array, dimension (N-1) The scalar factors of the elementary reflectors (see Further Details). WORK (workspace) double array, dimension (N) INFO (output) long = 0: successful exit. < 0: if INFO = -i, the i-th argument had an illegal value. Further Details =============== The matrix Q is represented as a product of (ihi-ilo) elementary reflectors Q = H(ilo) H(ilo+1) . . . H(ihi-1). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i) = 0, v(i+1) = 1 and v(ihi+1:n) = 0; v(i+2:ihi) is stored on exit in A(i+2:ihi,i), and tau in TAU(i). The contents of A are illustrated by the following example, with n = 7, ilo = 2 and ihi = 6: on entry, on exit, ( a a a a a a a ) ( a a h h h h a ) ( a a a a a a ) ( a h h h h a ) ( a a a a a a ) ( h h h h h h ) ( a a a a a a ) ( v2 h h h h h ) ( a a a a a a ) ( v2 v3 h h h h ) ( a a a a a a ) ( v2 v3 v4 h h h ) ( a ) ( a ) where a denotes an element of the original matrix A, h denotes a modified element of the upper Hessenberg matrix H, and vi denotes an element of the vector defining H(i). ===================================================================== */ int NUMlapack_dgehrd (long *n, long *ilo, long *ihi, double *a, long *lda, double *tau, double *work, long *lwork, long *info); /* -- LAPACK routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University June 30, 1999 Purpose ======= NUMlapack_dgehrd reduces a real general matrix A to upper Hessenberg form H by an orthogonal similarity transformation: Q' * A * Q = H . Arguments ========= N (input) long The order of the matrix A. N >= 0. ILO (input) long IHI (input) long It is assumed that A is already upper triangular in rows and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally set by a previous call to NUMlapack_dgebal; otherwise they should be set to 1 and N respectively. See Further Details. 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0. A (input/output) double array, dimension (LDA,N) On entry, the N-by-N general matrix to be reduced. On exit, the upper triangle and the first subdiagonal of A are overwritten with the upper Hessenberg matrix H, and the elements below the first subdiagonal, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). TAU (output) double array, dimension (N-1) The scalar factors of the elementary reflectors (see Further Details). Elements 1:ILO-1 and IHI:N-1 of TAU are set to zero. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The length of the array WORK. LWORK >= max(1,N). For optimum performance LWORK >= N*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value. Further Details =============== The matrix Q is represented as a product of (ihi-ilo) elementary reflectors Q = H(ilo) H(ilo+1) . . . H(ihi-1). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i) = 0, v(i+1) = 1 and v(ihi+1:n) = 0; v(i+2:ihi) is stored on exit in A(i+2:ihi,i), and tau in TAU(i). The contents of A are illustrated by the following example, with n = 7, ilo = 2 and ihi = 6: on entry, on exit, ( a a a a a a a ) ( a a h h h h a ) ( a a a a a a ) ( a h h h h a ) ( a a a a a a ) ( h h h h h h ) ( a a a a a a ) ( v2 h h h h h ) ( a a a a a a ) ( v2 v3 h h h h ) ( a a a a a a ) ( v2 v3 v4 h h h ) ( a ) ( a ) where a denotes an element of the original matrix A, h denotes a modified element of the upper Hessenberg matrix H, and vi denotes an element of the vector defining H(i). ===================================================================== */ int NUMlapack_dgelq2 (long *m, long *n, double *a, long *lda, double *tau, double *work, long *info); /* Purpose ======= NUMlapack_dgelq2 computes an LQ factorization of a real m by n matrix A: A = L * Q. Arguments ========= M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the m by n matrix A. On exit, the elements on and below the diagonal of the array contain the m by min(m,n) lower trapezoidal matrix L (L is lower triangular if m <= n); the elements above the diagonal, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors (see Further Details). LDA (input) long The leading dimension of the array A. LDA >= max(1,M). TAU (output) double array, dimension (min(M,N)) The scalar factors of the elementary reflectors (see Further Details). WORK (workspace) double array, dimension (M) INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value Further Details =============== The matrix Q is represented as a product of elementary reflectors Q = H(k) . . . H(2) H(1), where k = min(m,n). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i-1) = 0 and v(i) = 1; v(i+1:n) is stored on exit in A(i,i+1:n), and tau in TAU(i). ===================================================================== */ int NUMlapack_dgelqf (long *m, long *n, double *a, long *lda, double *tau, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dgelqf computes an LQ factorization of a real M-by-N matrix A: A = L * Q. Arguments ========= M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the M-by-N matrix A. On exit, the elements on and below the diagonal of the array contain the m-by-min(m,n) lower trapezoidal matrix L (L is lower triangular if m <= n); the elements above the diagonal, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors (see Further Details). LDA (input) long The leading dimension of the array A. LDA >= max(1,M). TAU (output) double array, dimension (min(M,N)) The scalar factors of the elementary reflectors (see Further Details). WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,M). For optimum performance LWORK >= M*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value Further Details =============== The matrix Q is represented as a product of elementary reflectors Q = H(k) . . . H(2) H(1), where k = min(m,n). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i-1) = 0 and v(i) = 1; v(i+1:n) is stored on exit in A(i,i+1:n), and tau in TAU(i). ===================================================================== */ int NUMlapack_dgelss (long *m, long *n, long *nrhs, double *a, long *lda, double *b, long *ldb, double *s, double *rcond, long *rank, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dgelss computes the minimum norm solution to a real linear least squares problem: Minimize 2-norm(| b - A*x |). using the singular value decomposition (SVD) of A. A is an M-by-N matrix which may be rank-deficient. Several right hand side vectors b and solution vectors x can be handled in a single call; they are stored as the columns of the M-by-NRHS right hand side matrix B and the N-by-NRHS solution matrix X. The effective rank of A is determined by treating as zero those singular values which are less than RCOND times the largest singular value. Arguments ========= M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. NRHS (input) long The number of right hand sides, i.e., the number of columns of the matrices B and X. NRHS >= 0. A (input/output) double array, dimension (LDA,N) On entry, the M-by-N matrix A. On exit, the first min(m,n) rows of A are overwritten with its right singular vectors, stored rowwise. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). B (input/output) double array, dimension (LDB,NRHS) On entry, the M-by-NRHS right hand side matrix B. On exit, B is overwritten by the N-by-NRHS solution matrix X. If m >= n and RANK = n, the residual sum-of-squares for the solution in the i-th column is given by the sum of squares of elements n+1:m in that column. LDB (input) long The leading dimension of the array B. LDB >= max(1,max(M,N)). S (output) double array, dimension (min(M,N)) The singular values of A in decreasing order. The condition number of A in the 2-norm = S(1)/S(min(m,n)). RCOND (input) double RCOND is used to determine the effective rank of A. Singular values S(i) <= RCOND*S(1) are treated as zero. If RCOND < 0, machine precision is used instead. RANK (output) long The effective rank of A, i.e., the number of singular values which are greater than RCOND*S(1). WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= 1, and also: LWORK >= 3*min(M,N) + max( 2*min(M,N), max(M,N), NRHS ) For good performance, LWORK should generally be larger. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value. > 0: the algorithm for computing the SVD failed to converge; if INFO = i, i off-diagonal elements of an intermediate bidiagonal form did not converge to zero. ===================================================================== */ int NUMlapack_dgeqpf (long *m, long *n, double *a, long *lda, long *jpvt, double *tau, double *work, long *info); /* Purpose ======= This routine is deprecated and has been replaced by routine DGEQP3. NUMlapack_dgeqpf computes a QR factorization with column pivoting of a real M-by-N matrix A: A*P = Q*R. Arguments ========= M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0 A (input/output) double array, dimension (LDA,N) On entry, the M-by-N matrix A. On exit, the upper triangle of the array contains the min(M,N)-by-N upper triangular matrix R; the elements below the diagonal, together with the array TAU, represent the orthogonal matrix Q as a product of min(m,n) elementary reflectors. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). JPVT (input/output) long array, dimension (N) On entry, if JPVT(i) .ne. 0, the i-th column of A is permuted to the front of A*P (a leading column); if JPVT(i) = 0, the i-th column of A is a free column. On exit, if JPVT(i) = k, then the i-th column of A*P was the k-th column of A. TAU (output) double array, dimension (min(M,N)) The scalar factors of the elementary reflectors. WORK (workspace) double array, dimension (3*N) INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value Further Details =============== The matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(n) Each H(i) has the form H = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i). The matrix P is represented in jpvt as follows: If jpvt(j) = i then the jth column of P is the ith canonical unit vector. ===================================================================== */ int NUMlapack_dgeqr2 (long *m, long *n, double *a, long *lda, double *tau, double *work, long *info); /* Purpose ======= NUMlapack_dgeqr2 computes a QR factorization of a real m by n matrix A: A = Q * R. Arguments ========= M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the m by n matrix A. On exit, the elements on and above the diagonal of the array contain the min(m,n) by n upper trapezoidal matrix R (R is upper triangular if m >= n); the elements below the diagonal, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors (see Further Details). LDA (input) long The leading dimension of the array A. LDA >= max(1,M). TAU (output) double array, dimension (min(M,N)) The scalar factors of the elementary reflectors (see Further Details). WORK (workspace) double array, dimension (N) INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value Further Details =============== The matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(k), where k = min(m,n). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i), and tau in TAU(i). ===================================================================== */ int NUMlapack_dgeqrf(long *m, long *n, double *a, long *lda, double *tau, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dgeqrf computes a QR factorization of a real M-by-N matrix A: A = Q * R. Arguments ========= M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the M-by-N matrix A. On exit, the elements on and above the diagonal of the array contain the min(M,N)-by-N upper trapezoidal matrix R (R is upper triangular if m >= n); the elements below the diagonal, with the array TAU, represent the orthogonal matrix Q as a product of min(m,n) elementary reflectors (see Further Details). LDA (input) long The leading dimension of the array A. LDA >= max(1,M). TAU (output) double array, dimension (min(M,N)) The scalar factors of the elementary reflectors (see Further Details). WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,N). For optimum performance LWORK >= N*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value Further Details =============== The matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(k), where k = min(m,n). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i), and tau in TAU(i). ===================================================================== */ int NUMlapack_dgerq2(long *m, long *n, double *a, long *lda, double *tau, double *work, long *info); /* Purpose ======= NUMlapack_dgerq2 computes an RQ factorization of a real m by n matrix A: A = R * Q. Arguments ========= M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the m by n matrix A. On exit, if m <= n, the upper triangle of the subarray A(1:m,n-m+1:n) contains the m by m upper triangular matrix R; if m >= n, the elements on and above the (m-n)-th subdiagonal contain the m by n upper trapezoidal matrix R; the remaining elements, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors (see Further Details). LDA (input) long The leading dimension of the array A. LDA >= max(1,M). TAU (output) double array, dimension (min(M,N)) The scalar factors of the elementary reflectors (see Further Details). WORK (workspace) double array, dimension (M) INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value Further Details =============== The matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(k), where k = min(m,n). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(n-k+i+1:n) = 0 and v(n-k+i) = 1; v(1:n-k+i-1) is stored on exit in A(m-k+i,1:n-k+i-1), and tau in TAU(i). ===================================================================== */ int NUMlapack_dgesv (long *n, long *nrhs, double *a, long *lda, long *ipiv, double *b, long *ldb, long *info); /* Purpose ======= NUMlapack_dgesv computes the solution to a real system of linear equations A * X = B, where A is an N-by-N matrix and X and B are N-by-NRHS matrices. The LU decomposition with partial pivoting and row interchanges is used to factor A as A = P * L * U, where P is a permutation matrix, L is unit lower triangular, and U is upper triangular. The factored form of A is then used to solve the system of equations A * X = B. Arguments ========= N (input) long The number of linear equations, i.e., the order of the matrix A. N >= 0. NRHS (input) long The number of right hand sides, i.e., the number of columns of the matrix B. NRHS >= 0. A (input/output) double array, dimension (LDA,N) On entry, the N-by-N coefficient matrix A. On exit, the factors L and U from the factorization A = P*L*U; the unit diagonal elements of L are not stored. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). IPIV (output) long array, dimension (N) The pivot indices that define the permutation matrix P; row i of the matrix was interchanged with row IPIV(i). B (input/output) double array, dimension (LDB,NRHS) On entry, the N-by-NRHS matrix of right hand side matrix B. On exit, if INFO = 0, the N-by-NRHS solution matrix X. LDB (input) long The leading dimension of the array B. LDB >= max(1,N). INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value > 0: if INFO = i, U(i,i) is exactly zero. The factorization has been completed, but the factor U is exactly singular, so the solution could not be computed. ===================================================================== */ int NUMlapack_dgesvd (const char *jobu, const char *jobvt, long *m, long *n, double *a, long *lda, double *s, double *u, long *ldu, double *vt, long *ldvt, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dgesvd computes the singular value decomposition (SVD) of a real M-by-N matrix A, optionally computing the left and/or right singular vectors. The SVD is written A = U * SIGMA * transpose(V) where SIGMA is an M-by-N matrix which is zero except for its min(m,n) diagonal elements, U is an M-by-M orthogonal matrix, and V is an N-by-N orthogonal matrix. The diagonal elements of SIGMA are the singular values of A; they are real and non-negative, and are returned in descending order. The first min(m,n) columns of U and V are the left and right singular vectors of A. Note that the routine returns V**T, not V. Arguments ========= JOBU (input) char* Specifies options for computing all or part of the matrix U: = 'A': all M columns of U are returned in array U: = 'S': the first min(m,n) columns of U (the left singular vectors) are returned in the array U; = 'O': the first min(m,n) columns of U (the left singular vectors) are overwritten on the array A; = 'N': no columns of U (no left singular vectors) are computed. JOBVT (input) char* Specifies options for computing all or part of the matrix V**T: = 'A': all N rows of V**T are returned in the array VT; = 'S': the first min(m,n) rows of V**T (the right singular vectors) are returned in the array VT; = 'O': the first min(m,n) rows of V**T (the right singular vectors) are overwritten on the array A; = 'N': no rows of V**T (no right singular vectors) are computed. JOBVT and JOBU cannot both be 'O'. M (input) long The number of rows of the input matrix A. M >= 0. N (input) long The number of columns of the input matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the M-by-N matrix A. On exit, if JOBU = 'O', A is overwritten with the first min(m,n) columns of U (the left singular vectors, stored columnwise); if JOBVT = 'O', A is overwritten with the first min(m,n) rows of V**T (the right singular vectors, stored rowwise); if JOBU .ne. 'O' and JOBVT .ne. 'O', the contents of A are destroyed. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). S (output) double array, dimension (min(M,N)) The singular values of A, sorted so that S(i) >= S(i+1). U (output) double array, dimension (LDU,UCOL) (LDU,M) if JOBU = 'A' or (LDU,min(M,N)) if JOBU = 'S'. If JOBU = 'A', U contains the M-by-M orthogonal matrix U; if JOBU = 'S', U contains the first min(m,n) columns of U (the left singular vectors, stored columnwise); if JOBU = 'N' or 'O', U is not referenced. LDU (input) long The leading dimension of the array U. LDU >= 1; if JOBU = 'S' or 'A', LDU >= M. VT (output) double array, dimension (LDVT,N) If JOBVT = 'A', VT contains the N-by-N orthogonal matrix V**T; if JOBVT = 'S', VT contains the first min(m,n) rows of V**T (the right singular vectors, stored rowwise); if JOBVT = 'N' or 'O', VT is not referenced. LDVT (input) long The leading dimension of the array VT. LDVT >= 1; if JOBVT = 'A', LDVT >= N; if JOBVT = 'S', LDVT >= min(M,N). WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK; if INFO > 0, WORK(2:MIN(M,N)) contains the unconverged superdiagonal elements of an upper bidiagonal matrix B whose diagonal is in S (not necessarily sorted). B satisfies A = U * B * VT, so it has the same singular values as A, and singular vectors related by U and VT. LWORK (input) long The dimension of the array WORK. LWORK >= 1. LWORK >= MAX(3*MIN(M,N)+MAX(M,N),5*MIN(M,N)). For good performance, LWORK should generally be larger. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit. < 0: if INFO = -i, the i-th argument had an illegal value. > 0: if DBDSQR did not converge, INFO specifies how many superdiagonals of an intermediate bidiagonal form B did not converge to zero. See the description of WORK above for details. ===================================================================== */ int NUMlapack_dgetf2 (long *m, long *n, double *a, long *lda, long *ipiv, long *info); /* Purpose ======= NUMlapack_dgetf2 computes an LU factorization of a general m-by-n matrix A using partial pivoting with row interchanges. The factorization has the form A = P * L * U where P is a permutation matrix, L is lower triangular with unit diagonal elements (lower trapezoidal if m > n), and U is upper triangular (upper trapezoidal if m < n). This is the right-looking Level 2 BLAS version of the algorithm. Arguments ========= M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the m by n matrix to be factored. On exit, the factors L and U from the factorization A = P*L*U; the unit diagonal elements of L are not stored. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). IPIV (output) long array, dimension (min(M,N)) The pivot indices; for 1 <= i <= min(M,N), row i of the matrix was interchanged with row IPIV(i). INFO (output) long = 0: successful exit < 0: if INFO = -k, the k-th argument had an illegal value > 0: if INFO = k, U(k,k) is exactly zero. The factorization has been completed, but the factor U is exactly singular, and division by zero will occur if it is used to solve a system of equations. ===================================================================== */ int NUMlapack_dgetri (long *n, double *a, long *lda, long *ipiv, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dgetri computes the inverse of a matrix using the LU factorization computed by NUMlapack_dgetrf. This method inverts U and then computes inv(A) by solving the system inv(A)*L = inv(U) for inv(A). Arguments ========= N (input) long The order of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the factors L and U from the factorization A = P*L*U as computed by DGETRF. On exit, if INFO = 0, the inverse of the original matrix A. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). IPIV (input) long array, dimension (N) The pivot indices from DGETRF; for 1<=i<=N, row i of the matrix was interchanged with row IPIV(i). WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO=0, then WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,N). For optimal performance LWORK >= N*NB, where NB is the optimal blocksize returned by NUMlapack_ilaenv. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value > 0: if INFO = i, U(i,i) is exactly zero; the matrix is singular and its inverse could not be computed. ===================================================================== */ int NUMlapack_dgetrf (long *m, long *n, double *a, long *lda, long *ipiv, long *info); /* Purpose ======= NUMlapack_dgetrf computes an LU factorization of a general M-by-N matrix A using partial pivoting with row interchanges. The factorization has the form A = P * L * U where P is a permutation matrix, L is lower triangular with unit diagonal elements (lower trapezoidal if m > n), and U is upper triangular (upper trapezoidal if m < n). This is the right-looking Level 3 BLAS version of the algorithm. Arguments ========= M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the M-by-N matrix to be factored. On exit, the factors L and U from the factorization A = P*L*U; the unit diagonal elements of L are not stored. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). IPIV (output) long array, dimension (min(M,N)) The pivot indices; for 1 <= i <= min(M,N), row i of the matrix was interchanged with row IPIV(i). INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value > 0: if INFO = i, U(i,i) is exactly zero. The factorization has been completed, but the factor U is exactly singular, and division by zero will occur if it is used to solve a system of equations. ===================================================================== */ int NUMlapack_dgetrs (const char *trans, long *n, long *nrhs, double *a, long *lda, long *ipiv, double *b, long *ldb, long *info); /* Purpose ======= NUMlapack_dgetrs solves a system of linear equations A * X = B or A' * X = B with a general N-by-N matrix A using the LU factorization computed by DGETRF. Arguments ========= TRANS (input) char* Specifies the form of the system of equations: = 'N': A * X = B (No transpose) = 'T': A'* X = B (Transpose) = 'C': A'* X = B (Conjugate transpose = Transpose) N (input) long The order of the matrix A. N >= 0. NRHS (input) long The number of right hand sides, i.e., the number of columns of the matrix B. NRHS >= 0. A (input) double array, dimension (LDA,N) The factors L and U from the factorization A = P*L*U as computed by DGETRF. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). IPIV (input) long array, dimension (N) The pivot indices from DGETRF; for 1<=i<=N, row i of the matrix was interchanged with row IPIV(i). B (input/output) double array, dimension (LDB,NRHS) On entry, the right hand side matrix B. On exit, the solution matrix X. LDB (input) long The leading dimension of the array B. LDB >= max(1,N). INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dggsvd (const char *jobu, const char *jobv, const char *jobq, long *m, long *n, long *p, long *k, long *l, double *a, long *lda, double *b, long *ldb, double *alpha, double *beta, double *u, long *ldu, double *v, long *ldv, double *q, long *ldq, double *work, long *iwork, long *info); /* Purpose ======= NUMlapack_dggsvd computes the generalized singular value decomposition (GSVD) of an M-by-N real matrix A and P-by-N real matrix B: U'*A*Q = D1*( 0 R ), V'*B*Q = D2*( 0 R ) where U, V and Q are orthogonal matrices, and Z' is the transpose of Z. Let K+L = the effective numerical rank of the matrix (A',B')', then R is a K+L-by-K+L nonsingular upper triangular matrix, D1 and D2 are M-by-(K+L) and P-by-(K+L) "diagonal" matrices and of the following structures, respectively: If M-K-L >= 0, K L D1 = K ( I 0 ) L ( 0 C ) M-K-L ( 0 0 ) K L D2 = L ( 0 S ) P-L ( 0 0 ) N-K-L K L ( 0 R ) = K ( 0 R11 R12 ) L ( 0 0 R22 ) where C = diag( ALPHA(K+1), ... , ALPHA(K+L) ), S = diag( BETA(K+1), ... , BETA(K+L) ), C**2 + S**2 = I. R is stored in A(1:K+L,N-K-L+1:N) on exit. If M-K-L < 0, K M-K K+L-M D1 = K ( I 0 0 ) M-K ( 0 C 0 ) K M-K K+L-M D2 = M-K ( 0 S 0 ) K+L-M ( 0 0 I ) P-L ( 0 0 0 ) N-K-L K M-K K+L-M ( 0 R ) = K ( 0 R11 R12 R13 ) M-K ( 0 0 R22 R23 ) K+L-M ( 0 0 0 R33 ) where C = diag( ALPHA(K+1), ... , ALPHA(M) ), S = diag( BETA(K+1), ... , BETA(M) ), C**2 + S**2 = I. (R11 R12 R13 ) is stored in A(1:M, N-K-L+1:N), and R33 is stored ( 0 R22 R23 ) in B(M-K+1:L,N+M-K-L+1:N) on exit. The routine computes C, S, R, and optionally the orthogonal transformation matrices U, V and Q. In particular, if B is an N-by-N nonsingular matrix, then the GSVD of A and B implicitly gives the SVD of A*inv(B): A*inv(B) = U*(D1*inv(D2))*V'. If ( A',B')' has orthonormal columns, then the GSVD of A and B is also equal to the CS decomposition of A and B. Furthermore, the GSVD can be used to derive the solution of the eigenvalue problem: A'*A x = lambda* B'*B x. In some literature, the GSVD of A and B is presented in the form U'*A*X = ( 0 D1 ), V'*B*X = ( 0 D2 ) where U and V are orthogonal and X is nonsingular, D1 and D2 are ``diagonal''. The former GSVD form can be converted to the latter form by taking the nonsingular matrix X as X = Q*( I 0 ) ( 0 inv(R) ). Arguments ========= JOBU (input) char* = 'U': Orthogonal matrix U is computed; = 'N': U is not computed. JOBV (input) char* = 'V': Orthogonal matrix V is computed; = 'N': V is not computed. JOBQ (input) char* = 'Q': Orthogonal matrix Q is computed; = 'N': Q is not computed. M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrices A and B. N >= 0. P (input) long The number of rows of the matrix B. P >= 0. K (output) long L (output) long On exit, K and L specify the dimension of the subblocks described in the Purpose section. K + L = effective numerical rank of (A',B')'. A (input/output) double array, dimension (LDA,N) On entry, the M-by-N matrix A. On exit, A contains the triangular matrix R, or part of R. See Purpose for details. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). B (input/output) double array, dimension (LDB,N) On entry, the P-by-N matrix B. On exit, B contains the triangular matrix R if M-K-L < 0. See Purpose for details. LDB (input) long The leading dimension of the array B. LDA >= max(1,P). ALPHA (output) double array, dimension (N) BETA (output) double array, dimension (N) On exit, ALPHA and BETA contain the generalized singular value pairs of A and B; ALPHA(1:K) = 1, BETA(1:K) = 0, and if M-K-L >= 0, ALPHA(K+1:K+L) = C, BETA(K+1:K+L) = S, or if M-K-L < 0, ALPHA(K+1:M)=C, ALPHA(M+1:K+L)=0 BETA(K+1:M) =S, BETA(M+1:K+L) =1 and ALPHA(K+L+1:N) = 0 BETA(K+L+1:N) = 0 U (output) double array, dimension (LDU,M) If JOBU = 'U', U contains the M-by-M orthogonal matrix U. If JOBU = 'N', U is not referenced. LDU (input) long The leading dimension of the array U. LDU >= max(1,M) if JOBU = 'U'; LDU >= 1 otherwise. V (output) double array, dimension (LDV,P) If JOBV = 'V', V contains the P-by-P orthogonal matrix V. If JOBV = 'N', V is not referenced. LDV (input) long The leading dimension of the array V. LDV >= max(1,P) if JOBV = 'V'; LDV >= 1 otherwise. Q (output) double array, dimension (LDQ,N) If JOBQ = 'Q', Q contains the N-by-N orthogonal matrix Q. If JOBQ = 'N', Q is not referenced. LDQ (input) long The leading dimension of the array Q. LDQ >= max(1,N) if JOBQ = 'Q'; LDQ >= 1 otherwise. WORK (workspace) double array, dimension (max(3*N,M,P)+N) IWORK (workspace/output) long array, dimension (N) On exit, IWORK stores the sorting information. More precisely, the following loop will sort ALPHA for I = K+1, min(M,K+L) swap ALPHA(I) and ALPHA(IWORK(I)) endfor such that ALPHA(1) >= ALPHA(2) >= ... >= ALPHA(N). INFO (output)long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value. > 0: if INFO = 1, the Jacobi-type procedure failed to converge. For further details, see subroutine NUMlapack_dtgsja. Internal Parameters =================== TOLA double TOLB double TOLA and TOLB are the thresholds to determine the effective rank of (A',B')'. Generally, they are set to TOLA = MAX(M,N)*norm(A)*MAZHEPS, TOLB = MAX(P,N)*norm(B)*MAZHEPS. The size of TOLA and TOLB may affect the size of backward errors of the decomposition. ===================================================================== */ int NUMlapack_dggsvp (const char *jobu, const char *jobv, const char *jobq, long *m, long *p, long *n, double *a, long *lda, double *b, long *ldb, double *tola, double *tolb, long *k, long *l, double *u, long *ldu, double *v, long *ldv, double *q, long *ldq, long *iwork, double *tau, double *work, long *info); /* Purpose ======= NUMlapack_dggsvp computes orthogonal matrices U, V and Q such that N-K-L K L U'*A*Q = K ( 0 A12 A13 ) if M-K-L >= 0; L ( 0 0 A23 ) M-K-L ( 0 0 0 ) N-K-L K L = K ( 0 A12 A13 ) if M-K-L < 0; M-K ( 0 0 A23 ) N-K-L K L V'*B*Q = L ( 0 0 B13 ) P-L ( 0 0 0 ) where the K-by-K matrix A12 and L-by-L matrix B13 are nonsingular upper triangular; A23 is L-by-L upper triangular if M-K-L >= 0, otherwise A23 is (M-K)-by-L upper trapezoidal. K+L = the effective numerical rank of the (M+P)-by-N matrix (A',B')'. Z' denotes the transpose of Z. This decomposition is the preprocessing step for computing the Generalized Singular Value Decomposition (GSVD), see subroutine NUMlapack_dggsvd. Arguments ========= JOBU (input) char* = 'U': Orthogonal matrix U is computed; = 'N': U is not computed. JOBV (input) char* = 'V': Orthogonal matrix V is computed; = 'N': V is not computed. JOBQ (input) char* = 'Q': Orthogonal matrix Q is computed; = 'N': Q is not computed. M (input) long The number of rows of the matrix A. M >= 0. P (input) long The number of rows of the matrix B. P >= 0. N (input) long The number of columns of the matrices A and B. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the M-by-N matrix A. On exit, A contains the triangular (or trapezoidal) matrix described in the Purpose section. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). B (input/output) double array, dimension (LDB,N) On entry, the P-by-N matrix B. On exit, B contains the triangular matrix described in the Purpose section. LDB (input) long The leading dimension of the array B. LDB >= max(1,P). TOLA (input) double TOLB (input) double TOLA and TOLB are the thresholds to determine the effective numerical rank of matrix B and a subblock of A. Generally, they are set to TOLA = MAX(M,N)*norm(A)*MAZHEPS, TOLB = MAX(P,N)*norm(B)*MAZHEPS. The size of TOLA and TOLB may affect the size of backward errors of the decomposition. K (output) long L (output) long On exit, K and L specify the dimension of the subblocks described in Purpose. K + L = effective numerical rank of (A',B')'. U (output) double array, dimension (LDU,M) If JOBU = 'U', U contains the orthogonal matrix U. If JOBU = 'N', U is not referenced. LDU (input) long The leading dimension of the array U. LDU >= max(1,M) if JOBU = 'U'; LDU >= 1 otherwise. V (output) double array, dimension (LDV,M) If JOBV = 'V', V contains the orthogonal matrix V. If JOBV = 'N', V is not referenced. LDV (input) long The leading dimension of the array V. LDV >= max(1,P) if JOBV = 'V'; LDV >= 1 otherwise. Q (output) double array, dimension (LDQ,N) If JOBQ = 'Q', Q contains the orthogonal matrix Q. If JOBQ = 'N', Q is not referenced. LDQ (input) long The leading dimension of the array Q. LDQ >= max(1,N) if JOBQ = 'Q'; LDQ >= 1 otherwise. IWORK (workspace) long array, dimension (N) TAU (workspace) double array, dimension (N) WORK (workspace) double array, dimension (max(3*N,M,P)) INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value. Further Details =============== The subroutine uses LAPACK subroutine DGEQPF for the QR factorization with column pivoting to detect the effective numerical rank of the a matrix. It may be replaced by a better rank determination strategy. ===================================================================== */ int NUMlapack_dhseqr (const char *job, const char *compz, long *n, long *ilo, long *ihi, double *h, long *ldh, double *wr, double *wi, double *z, long *ldz, double *work, long *lwork, long *info); /* -- LAPACK routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University June 30, 1999 Purpose ======= NUMlapack_dhseqr computes the eigenvalues of a real upper Hessenberg matrix H and, optionally, the matrices T and Z from the Schur decomposition H = Z T Z**T, where T is an upper quasi-triangular matrix (the Schur form), and Z is the orthogonal matrix of Schur vectors. Optionally Z may be postmultiplied into an input orthogonal matrix Q, so that this routine can give the Schur factorization of a matrix A which has been reduced to the Hessenberg form H by the orthogonal matrix Q: A = Q*H*Q**T = (QZ)*T*(QZ)**T. Arguments ========= JOB (input) char* = 'E': compute eigenvalues only; = 'S': compute eigenvalues and the Schur form T. COMPZ (input) char* = 'N': no Schur vectors are computed; = 'I': Z is initialized to the unit matrix and the matrix Z of Schur vectors of H is returned; = 'V': Z must contain an orthogonal matrix Q on entry, and the product Q*Z is returned. N (input) long The order of the matrix H. N >= 0. ILO (input) long IHI (input) long It is assumed that H is already upper triangular in rows and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally set by a previous call to NUMlapack_dgebal, and then passed to SGEHRD when the matrix output by NUMlapack_dgebal is reduced to Hessenberg form. Otherwise ILO and IHI should be set to 1 and N respectively. 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0. H (input/output) double array, dimension (LDH,N) On entry, the upper Hessenberg matrix H. On exit, if JOB = 'S', H contains the upper quasi-triangular matrix T from the Schur decomposition (the Schur form); 2-by-2 diagonal blocks (corresponding to complex conjugate pairs of eigenvalues) are returned in standard form, with H(i,i) = H(i+1,i+1) and H(i+1,i)*H(i,i+1) < 0. If JOB = 'E', the contents of H are unspecified on exit. LDH (input) long The leading dimension of the array H. LDH >= max(1,N). WR (output) double array, dimension (N) WI (output) double array, dimension (N) The real and imaginary parts, respectively, of the computed eigenvalues. If two eigenvalues are computed as a complex conjugate pair, they are stored in consecutive elements of WR and WI, say the i-th and (i+1)th, with WI(i) > 0 and WI(i+1) < 0. If JOB = 'S', the eigenvalues are stored in the same order as on the diagonal of the Schur form returned in H, with WR(i) = H(i,i) and, if H(i:i+1,i:i+1) is a 2-by-2 diagonal block, WI(i) = sqrt(H(i+1,i)*H(i,i+1)) and WI(i+1) = -WI(i). Z (input/output) double array, dimension (LDZ,N) If COMPZ = 'N': Z is not referenced. If COMPZ = 'I': on entry, Z need not be set, and on exit, Z contains the orthogonal matrix Z of the Schur vectors of H. If COMPZ = 'V': on entry Z must contain an N-by-N matrix Q, which is assumed to be equal to the unit matrix except for the submatrix Z(ILO:IHI,ILO:IHI); on exit Z contains Q*Z. Normally Q is the orthogonal matrix generated by NUMlapack_dorghr after the call to NUMlapack_dgehrd which formed the Hessenberg matrix H. LDZ (input) long The leading dimension of the array Z. LDZ >= max(1,N) if COMPZ = 'I' or 'V'; LDZ >= 1 otherwise. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,N). If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value > 0: if INFO = i, NUMlapack_dhseqr failed to compute all of the eigenvalues in a total of 30*(IHI-ILO+1) iterations; elements 1:ilo-1 and i+1:n of WR and WI contain those eigenvalues which have been successfully computed. ===================================================================== */ int NUMlapack_dlabad (double *smal, double *large); /* Purpose ======= NUMlapack_dlabad takes as input the values computed by DLAMCH for underflow and overflow, and returns the square root of each of these values if the log of LARGE is sufficiently large. This subroutine is intended to identify machines with a large exponent range, such as the Crays, and redefine the underflow and overflow limits to be the square roots of the values computed by DLAMCH. This subroutine is needed because DLAMCH does not compensate for poor arithmetic in the upper half of the exponent range, as is found on a Cray. Arguments ========= smal (input/output) double On entry, the underflow threshold as computed by DLAMCH. On exit, if LOG10(LARGE) is sufficiently large, the square root of smal, otherwise unchanged. LARGE (input/output) double On entry, the overflow threshold as computed by DLAMCH. On exit, if LOG10(LARGE) is sufficiently large, the square root of LARGE, otherwise unchanged. ===================================================================== If it looks like we're on a Cray, take the square root of smal and LARGE to avoid overflow and underflow problems. */ int NUMlapack_dlabrd (long *m, long *n, long *nb, double *a, long *lda, double *d, double *e, double *tauq, double *taup, double *x, long *ldx, double *y, long *ldy); /* Purpose ======= NUMlapack_dlabrd reduces the first NB rows and columns of a real general m by n matrix A to upper or lower bidiagonal form by an orthogonal transformation Q' * A * P, and returns the matrices X and Y which are needed to apply the transformation to the unreduced part of A. If m >= n, A is reduced to upper bidiagonal form; if m < n, to lower bidiagonal form. This is an auxiliary routine called by DGEBRD Arguments ========= M (input) long The number of rows in the matrix A. N (input) long The number of columns in the matrix A. NB (input) long The number of leading rows and columns of A to be reduced. A (input/output) double array, dimension (LDA,N) On entry, the m by n general matrix to be reduced. On exit, the first NB rows and columns of the matrix are overwritten; the rest of the array is unchanged. If m >= n, elements on and below the diagonal in the first NB columns, with the array TAUQ, represent the orthogonal matrix Q as a product of elementary reflectors; and elements above the diagonal in the first NB rows, with the array TAUP, represent the orthogonal matrix P as a product of elementary reflectors. If m < n, elements below the diagonal in the first NB columns, with the array TAUQ, represent the orthogonal matrix Q as a product of elementary reflectors, and elements on and above the diagonal in the first NB rows, with the array TAUP, represent the orthogonal matrix P as a product of elementary reflectors. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). D (output) double array, dimension (NB) The diagonal elements of the first NB rows and columns of the reduced matrix. D(i) = A(i,i). E (output) double array, dimension (NB) The off-diagonal elements of the first NB rows and columns of the reduced matrix. TAUQ (output) double array dimension (NB) The scalar factors of the elementary reflectors which represent the orthogonal matrix Q. See Further Details. TAUP (output) double array, dimension (NB) The scalar factors of the elementary reflectors which represent the orthogonal matrix P. See Further Details. X (output) double array, dimension (LDX,NB) The m-by-nb matrix X required to update the unreduced part of A. LDX (input) long The leading dimension of the array X. LDX >= M. Y (output) double array, dimension (LDY,NB) The n-by-nb matrix Y required to update the unreduced part of A. LDY (output) long The leading dimension of the array Y. LDY >= N. Further Details =============== The matrices Q and P are represented as products of elementary reflectors: Q = H(1) H(2) . . . H(nb) and P = G(1) G(2) . . . G(nb) Each H(i) and G(i) has the form: H(i) = I - tauq * v * v' and G(i) = I - taup * u * u' where tauq and taup are real scalars, and v and u are real vectors. If m >= n, v(1:i-1) = 0, v(i) = 1, and v(i:m) is stored on exit in A(i:m,i); u(1:i) = 0, u(i+1) = 1, and u(i+1:n) is stored on exit in A(i,i+1:n); tauq is stored in TAUQ(i) and taup in TAUP(i). If m < n, v(1:i) = 0, v(i+1) = 1, and v(i+1:m) is stored on exit in A(i+2:m,i); u(1:i-1) = 0, u(i) = 1, and u(i:n) is stored on exit in A(i,i+1:n); tauq is stored in TAUQ(i) and taup in TAUP(i). The elements of the vectors v and u together form the m-by-nb matrix V and the nb-by-n matrix U' which are needed, with X and Y, to apply the transformation to the unreduced part of the matrix, using a block update of the form: A := A - V*Y' - X*U'. The contents of A on exit are illustrated by the following examples with nb = 2: m = 6 and n = 5 (m > n): m = 5 and n = 6 (m < n): ( 1 1 u1 u1 u1 ) ( 1 u1 u1 u1 u1 u1 ) ( v1 1 1 u2 u2 ) ( 1 1 u2 u2 u2 u2 ) ( v1 v2 a a a ) ( v1 1 a a a a ) ( v1 v2 a a a ) ( v1 v2 a a a a ) ( v1 v2 a a a ) ( v1 v2 a a a a ) ( v1 v2 a a a ) where a denotes an element of the original matrix which is unchanged, vi denotes an element of the vector defining H(i), and ui an element of the vector defining G(i). ===================================================================== */ int NUMlapack_dlacpy (const char *uplo, long *m, long *n, double *a, long *lda, double *b, long *ldb); /* Purpose ======= NUMlapack_dlacpy copies all or part of a two-dimensional matrix A to another matrix B. Arguments ========= UPLO (input) char* Specifies the part of the matrix A to be copied to B. = 'U': Upper triangular part = 'L': Lower triangular part Otherwise: All of the matrix A M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. A (input) double array, dimension (LDA,N) The m by n matrix A. If UPLO = 'U', only the upper triangle or trapezoid is accessed; if UPLO = 'L', only the lower triangle or trapezoid is accessed. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). B (output) double array, dimension (LDB,N) On exit, B = A in the locations specified by UPLO. LDB (input) long The leading dimension of the array B. LDB >= max(1,M). ===================================================================== */ int NUMlapack_dladiv (double *a, double *b, double *c, double *d, double *p, double *q); /* -- LAPACK auxiliary routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University October 31, 1992 Purpose ======= NUMlapack_dladiv performs complex division in real arithmetic a + i*b p + i*q = --------- c + i*d The algorithm is due to Robert L. Smith and can be found in D. Knuth, The art of Computer Programming, Vol.2, p.195 Arguments ========= A (input) double B (input) double C (input) double D (input) double The scalars a, b, c, and d in the above expression. P (output) double Q (output) double The scalars p and q in the above expression. ===================================================================== */ int NUMlapack_dlae2 (double *a, double *b, double *c, double *rt1, double *rt2); /* Purpose ======= NUMlapack_dlae2 computes the eigenvalues of a 2-by-2 symmetric matrix [ A B ] [ B C ]. On return, RT1 is the eigenvalue of larger absolute value, and RT2 is the eigenvalue of smaller absolute value. Arguments ========= A (input) double The (1,1) element of the 2-by-2 matrix. B (input) double The (1,2) and (2,1) elements of the 2-by-2 matrix. C (input) double The (2,2) element of the 2-by-2 matrix. RT1 (output) double The eigenvalue of larger absolute value. RT2 (output) double The eigenvalue of smaller absolute value. Further Details =============== RT1 is accurate to a few ulps barring over/underflow. RT2 may be inaccurate if there is massive cancellation in the determinant A*C-B*B; higher precision or correctly rounded or correctly truncated arithmetic would be needed to compute RT2 accurately in all cases. Overflow is possible only if RT1 is within a factor of 5 of overflow. Underflow is harmless if the input data is 0 or exceeds underflow_threshold / macheps. ===================================================================== */ int NUMlapack_dlaev2 (double *a, double *b, double *c, double *rt1, double *rt2, double *cs1, double *sn1); /* Purpose ======= NUMlapack_dlaev2 computes the eigendecomposition of a 2-by-2 symmetric matrix [ A B ] [ B C ]. On return, RT1 is the eigenvalue of larger absolute value, RT2 is the eigenvalue of smaller absolute value, and (CS1,SN1) is the unit right eigenvector for RT1, giving the decomposition [ CS1 SN1 ] [ A B ] [ CS1 -SN1 ] = [ RT1 0 ] [-SN1 CS1 ] [ B C ] [ SN1 CS1 ] [ 0 RT2 ]. Arguments ========= A (input) double The (1,1) element of the 2-by-2 matrix. B (input) double The (1,2) element and the conjugate of the (2,1) element of the 2-by-2 matrix. C (input) double The (2,2) element of the 2-by-2 matrix. RT1 (output) double The eigenvalue of larger absolute value. RT2 (output) double The eigenvalue of smaller absolute value. CS1 (output) double SN1 (output) double The vector (CS1, SN1) is a unit right eigenvector for RT1. Further Details =============== RT1 is accurate to a few ulps barring over/underflow. RT2 may be inaccurate if there is massive cancellation in the determinant A*C-B*B; higher precision or correctly rounded or correctly truncated arithmetic would be needed to compute RT2 accurately in all cases. CS1 and SN1 are accurate to a few ulps barring over/underflow. Overflow is possible only if RT1 is within a factor of 5 of overflow. Underflow is harmless if the input data is 0 or exceeds underflow_threshold / macheps. ===================================================================== */ int NUMlapack_dlags2 (long *upper, double *a1, double *a2, double *a3, double *b1, double *b2, double *b3, double *csu, double *snu, double *csv, double *snv, double *csq, double *snq); /* Purpose ======= NUMlapack_dlags2 computes 2-by-2 orthogonal matrices U, V and Q, such that if ( UPPER ) then U'*A*Q = U'*( A1 A2 )*Q = ( x 0 ) ( 0 A3 ) ( x x ) and V'*B*Q = V'*( B1 B2 )*Q = ( x 0 ) ( 0 B3 ) ( x x ) or if ( .NOT.UPPER ) then U'*A*Q = U'*( A1 0 )*Q = ( x x ) ( A2 A3 ) ( 0 x ) and V'*B*Q = V'*( B1 0 )*Q = ( x x ) ( B2 B3 ) ( 0 x ) The rows of the transformed A and B are parallel, where U = ( CSU SNU ), V = ( CSV SNV ), Q = ( CSQ SNQ ) ( -SNU CSU ) ( -SNV CSV ) ( -SNQ CSQ ) Z' denotes the transpose of Z. Arguments ========= UPPER (input) long* (boolean) = TRUE: the input matrices A and B are upper triangular. = FALSE: the input matrices A and B are lower triangular. A1 (input) double A2 (input) double A3 (input) double On entry, A1, A2 and A3 are elements of the input 2-by-2 upper (lower) triangular matrix A. B1 (input) double B2 (input) double B3 (input) double On entry, B1, B2 and B3 are elements of the input 2-by-2 upper (lower) triangular matrix B. CSU (output) double SNU (output) double The desired orthogonal matrix U. CSV (output) double SNV (output) double The desired orthogonal matrix V. CSQ (output) double SNQ (output) double The desired orthogonal matrix Q. ===================================================================== */ int NUMlapack_dlahqr (int * wantt, int * wantz, long *n, long *ilo, long *ihi, double *h, long *ldh, double *wr, double *wi, long *iloz, long *ihiz, double *z, long *ldz, long *info); /* -- LAPACK auxiliary routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University June 30, 1999 Purpose ======= NUMlapack_dlahqr is an auxiliary routine called by NUMlapack_dhseqr to update the eigenvalues and Schur decomposition already computed by NUMlapack_dhseqr, by dealing with the Hessenberg submatrix in rows and columns ILO to IHI. Arguments ========= WANTT (input) int = .TRUE. : the full Schur form T is required; = .FALSE.: only eigenvalues are required. WANTZ (input) int = .TRUE. : the matrix of Schur vectors Z is required; = .FALSE.: Schur vectors are not required. N (input) long The order of the matrix H. N >= 0. ILO (input) long IHI (input) long It is assumed that H is already upper quasi-triangular in rows and columns IHI+1:N, and that H(ILO,ILO-1) = 0 (unless ILO = 1). NUMlapack_dlahqr works primarily with the Hessenberg submatrix in rows and columns ILO to IHI, but applies transformations to all of H if WANTT is .TRUE.. 1 <= ILO <= max(1,IHI); IHI <= N. H (input/output) double array, dimension (LDH,N) On entry, the upper Hessenberg matrix H. On exit, if WANTT is .TRUE., H is upper quasi-triangular in rows and columns ILO:IHI, with any 2-by-2 diagonal blocks in standard form. If WANTT is .FALSE., the contents of H are unspecified on exit. LDH (input) long The leading dimension of the array H. LDH >= max(1,N). WR (output) double array, dimension (N) WI (output) double array, dimension (N) The real and imaginary parts, respectively, of the computed eigenvalues ILO to IHI are stored in the corresponding elements of WR and WI. If two eigenvalues are computed as a complex conjugate pair, they are stored in consecutive elements of WR and WI, say the i-th and (i+1)th, with WI(i) > 0 and WI(i+1) < 0. If WANTT is .TRUE., the eigenvalues are stored in the same order as on the diagonal of the Schur form returned in H, with WR(i) = H(i,i), and, if H(i:i+1,i:i+1) is a 2-by-2 diagonal block, WI(i) = sqrt(H(i+1,i)*H(i,i+1)) and WI(i+1) = -WI(i). ILOZ (input) long IHIZ (input) long Specify the rows of Z to which transformations must be applied if WANTZ is .TRUE.. 1 <= ILOZ <= ILO; IHI <= IHIZ <= N. Z (input/output) double array, dimension (LDZ,N) If WANTZ is .TRUE., on entry Z must contain the current matrix Z of transformations accumulated by NUMlapack_dhseqr, and on exit Z has been updated; transformations are applied only to the submatrix Z(ILOZ:IHIZ,ILO:IHI). If WANTZ is .FALSE., Z is not referenced. LDZ (input) long The leading dimension of the array Z. LDZ >= max(1,N). INFO (output) long = 0: successful exit > 0: NUMlapack_dlahqr failed to compute all the eigenvalues ILO to IHI in a total of 30*(IHI-ILO+1) iterations; if INFO = i, elements i+1:ihi of WR and WI contain those eigenvalues which have been successfully computed. Further Details =============== 2-96 Based on modifications by David Day, Sandia National Laboratory, USA ===================================================================== */ int NUMlapack_dlahrd (long *n, long *k, long *nb, double *a, long *lda, double *tau, double *t, long *ldt, double *y, long *ldy); /* -- LAPACK auxiliary routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University June 30, 1999 Purpose ======= NUMlapack_dlahrd reduces the first NB columns of a real general n-by-(n-k+1) matrix A so that elements below the k-th subdiagonal are zero. The reduction is performed by an orthogonal similarity transformation Q' * A * Q. The routine returns the matrices V and T which determine Q as a block reflector I - V*T*V', and also the matrix Y = A * V * T. This is an auxiliary routine called by NUMlapack_dgehrd. Arguments ========= N (input) long The order of the matrix A. K (input) long The offset for the reduction. Elements below the k-th subdiagonal in the first NB columns are reduced to zero. NB (input) long The number of columns to be reduced. A (input/output) double array, dimension (LDA,N-K+1) On entry, the n-by-(n-k+1) general matrix A. On exit, the elements on and above the k-th subdiagonal in the first NB columns are overwritten with the corresponding elements of the reduced matrix; the elements below the k-th subdiagonal, with the array TAU, represent the matrix Q as a product of elementary reflectors. The other columns of A are unchanged. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). TAU (output) double array, dimension (NB) The scalar factors of the elementary reflectors. See Further Details. T (output) double array, dimension (LDT,NB) The upper triangular matrix T. LDT (input) long The leading dimension of the array T. LDT >= NB. Y (output) double array, dimension (LDY,NB) The n-by-nb matrix Y. LDY (input) long The leading dimension of the array Y. LDY >= N. Further Details =============== The matrix Q is represented as a product of nb elementary reflectors Q = H(1) H(2) . . . H(nb). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i+k-1) = 0, v(i+k) = 1; v(i+k+1:n) is stored on exit in A(i+k+1:n,i), and tau in TAU(i). The elements of the vectors v together form the (n-k+1)-by-nb matrix V which is needed, with T and Y, to apply the transformation to the unreduced part of the matrix, using an update of the form: A := (I - V*T*V') * (A - Y*V'). The contents of A on exit are illustrated by the following example with n = 7, k = 3 and nb = 2: ( a h a a a ) ( a h a a a ) ( a h a a a ) ( h h a a a ) ( v1 h a a a ) ( v1 v2 a a a ) ( v1 v2 a a a ) where a denotes an element of the original matrix A, h denotes a modified element of the upper Hessenberg matrix H, and vi denotes an element of the vector defining H(i). ===================================================================== */ int NUMlapack_dlaln2 (int * ltrans, long *na, long *nw, double *smin, double *ca, double *a, long *lda, double *d1, double *d2, double *b, long *ldb, double *wr, double *wi, double *x, long *ldx, double *scale, double *xnorm, long *info); /* -- LAPACK auxiliary routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University October 31, 1992 Purpose ======= NUMlapack_dlaln2 solves a system of the form (ca A - w D ) X = s B or (ca A' - w D) X = s B with possible scaling ("s") and perturbation of A. (A' means A-transpose.) A is an NA x NA real matrix, ca is a real scalar, D is an NA x NA real diagonal matrix, w is a real or complex value, and X and B are NA x 1 matrices -- real if w is real, complex if w is complex. NA may be 1 or 2. If w is complex, X and B are represented as NA x 2 matrices, the first column of each being the real part and the second being the imaginary part. "s" is a scaling factor (.LE. 1), computed by NUMlapack_dlaln2, which is so chosen that X can be computed without overflow. X is further scaled if necessary to assure that norm(ca A - w D)*norm(X) is less than overflow. If both singular values of (ca A - w D) are less than SMIN, SMIN*identity will be used instead of (ca A - w D). If only one singular value is less than SMIN, one element of (ca A - w D) will be perturbed enough to make the smallest singular value roughly SMIN. If both singular values are at least SMIN, (ca A - w D) will not be perturbed. In any case, the perturbation will be at most some small multiple of max( SMIN, ulp*norm(ca A - w D) ). The singular values are computed by infinity-norm approximations, and thus will only be correct to a factor of 2 or so. Note: all input quantities are assumed to be smaller than overflow by a reasonable factor. (See BIGNUM.) Arguments ========== LTRANS (input) int =.TRUE.: A-transpose will be used. =.FALSE.: A will be used (not transposed.) NA (input) long The size of the matrix A. It may (only) be 1 or 2. NW (input) long 1 if "w" is real, 2 if "w" is complex. It may only be 1 or 2. SMIN (input) double The desired lower bound on the singular values of A. This should be a safe distance away from underflow or overflow, say, between (underflow/machine precision) and (machine precision * overflow ). (See BIGNUM and ULP.) CA (input) double The coefficient c, which A is multiplied by. A (input) double array, dimension (LDA,NA) The NA x NA matrix A. LDA (input) long The leading dimension of A. It must be at least NA. D1 (input) double The 1,1 element in the diagonal matrix D. D2 (input) double The 2,2 element in the diagonal matrix D. Not used if NW=1. B (input) double array, dimension (LDB,NW) The NA x NW matrix B (right-hand side). If NW=2 ("w" is complex), column 1 contains the real part of B and column 2 contains the imaginary part. LDB (input) long The leading dimension of B. It must be at least NA. WR (input) double The real part of the scalar "w". WI (input) double The imaginary part of the scalar "w". Not used if NW=1. X (output) double array, dimension (LDX,NW) The NA x NW matrix X (unknowns), as computed by NUMlapack_dlaln2. If NW=2 ("w" is complex), on exit, column 1 will contain the real part of X and column 2 will contain the imaginary part. LDX (input) long The leading dimension of X. It must be at least NA. SCALE (output) double The scale factor that B must be multiplied by to insure that overflow does not occur when computing X. Thus, (ca A - w D) X will be SCALE*B, not B (ignoring perturbations of A.) It will be at most 1. XNORM (output) double The infinity-norm of X, when X is regarded as an NA x NW real matrix. INFO (output) long An error flag. It will be set to zero if no error occurs, a negative number if an argument is in error, or a positive number if ca A - w D had to be perturbed. The possible values are: = 0: No error occurred, and (ca A - w D) did not have to be perturbed. = 1: (ca A - w D) had to be perturbed to make its smallest (or only) singular value greater than SMIN. NOTE: In the interests of speed, this routine does not check the inputs for errors. ===================================================================== */ double NUMlapack_dlange (const char *norm, long *m, long *n, double *a, long *lda, double *work); /* Purpose ======= NUMlapack_dlange returns the value of the one norm, or the Frobenius norm, or the infinity norm, or the element of largest absolute value of a real matrix A. Description =========== DLANGE returns the value DLANGE = ( max(abs(A(i,j))), NORM = 'M' or 'm' ( ( norm1(A), NORM = '1', 'O' or 'o' ( ( normI(A), NORM = 'I' or 'i' ( ( normF(A), NORM = 'F', 'f', 'E' or 'e' where norm1 denotes the one norm of a matrix (maximum column sum), normI denotes the infinity norm of a matrix (maximum row sum) and normF denotes the Frobenius norm of a matrix (square root of sum of squares). Note that max(abs(A(i,j))) is not a matrix norm. Arguments ========= NORM (input) char* Specifies the value to be returned in DLANGE as described above. M (input) long The number of rows of the matrix A. M >= 0. When M = 0, DLANGE is set to zero. N (input) long The number of columns of the matrix A. N >= 0. When N = 0, DLANGE is set to zero. A (input) double array, dimension (LDA,N) The m by n matrix A. LDA (input) long The leading dimension of the array A. LDA >= max(M,1). WORK (workspace) double array, dimension (LWORK), where LWORK >= M when NORM = 'I'; otherwise, WORK is not referenced. ===================================================================== */ double NUMlapack_dlanhs (const char *norm, long *n, double *a, long *lda, double *work); /* -- LAPACK auxiliary routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University October 31, 1992 Purpose ======= NUMlapack_dlanhs returns the value of the one norm, or the Frobenius norm, or the infinity norm, or the element of largest absolute value of a Hessenberg matrix A. Description =========== NUMlapack_dlanhs returns the value NUMlapack_dlanhs = ( max(abs(A(i,j))), NORM = 'M' or 'm' ( ( norm1(A), NORM = '1', 'O' or 'o' ( ( normI(A), NORM = 'I' or 'i' ( ( normF(A), NORM = 'F', 'f', 'E' or 'e' where norm1 denotes the one norm of a matrix (maximum column sum), normI denotes the infinity norm of a matrix (maximum row sum) and normF denotes the Frobenius norm of a matrix (square root of sum of squares). Note that max(abs(A(i,j))) is not a matrix norm. Arguments ========= NORM (input) char* Specifies the value to be returned in NUMlapack_dlanhs as described above. N (input) long The order of the matrix A. N >= 0. When N = 0, NUMlapack_dlanhs is set to zero. A (input) double array, dimension (LDA,N) The n by n upper Hessenberg matrix A; the part of A below the first sub-diagonal is not referenced. LDA (input) long The leading dimension of the array A. LDA >= max(N,1). WORK (workspace) double array, dimension (LWORK), where LWORK >= N when NORM = 'I'; otherwise, WORK is not referenced. ===================================================================== */ double NUMlapack_dlanst (const char *norm, long *n, double *d, double *e); /* Purpose ======= NUMlapack_dlanst returns the value of the one norm, or the Frobenius norm, or the infinity norm, or the element of largest absolute value of a real symmetric tridiagonal matrix A. Description =========== NUMlapack_dlanst returns the value NUMlapack_dlanst = ( max(abs(A(i,j))), NORM = 'M' or 'm' ( ( norm1(A), NORM = '1', 'O' or 'o' ( ( normI(A), NORM = 'I' or 'i' ( ( normF(A), NORM = 'F', 'f', 'E' or 'e' where norm1 denotes the one norm of a matrix (maximum column sum), normI denotes the infinity norm of a matrix (maximum row sum) and normF denotes the Frobenius norm of a matrix (square root of sum of squares). Note that max(abs(A(i,j))) is not a matrix norm. Arguments ========= NORM (input) char* Specifies the value to be returned in DLANST as described above. N (input) long The order of the matrix A. N >= 0. When N = 0, DLANST is set to zero. D (input) double array, dimension (N) The diagonal elements of A. E (input) double array, dimension (N-1) The (n-1) sub-diagonal or super-diagonal elements of A. ===================================================================== */ double NUMlapack_dlansy (const char *norm, const char *uplo, long *n, double *a, long *lda, double *work); /* Purpose ======= NUMlapack_dlansy returns the value of the one norm, or the Frobenius norm, or the infinity norm, or the element of largest absolute value of a real symmetric matrix A. Description =========== NUMlapack_dlansy returns the value ( max(abs(A(i,j))), NORM = 'M' or 'm' ( ( norm1(A), NORM = '1', 'O' or 'o' ( ( normI(A), NORM = 'I' or 'i' ( ( normF(A), NORM = 'F', 'f', 'E' or 'e' where norm1 denotes the one norm of a matrix (maximum column sum), normI denotes the infinity norm of a matrix (maximum row sum) and normF denotes the Frobenius norm of a matrix (square root of sum of squares). Note that max(abs(A(i,j))) is not a matrix norm. Arguments ========= NORM (input) char* Specifies the value to be returned in DLANSY as described above. UPLO (input) char* Specifies whether the upper or lower triangular part of the symmetric matrix A is to be referenced. = 'U': Upper triangular part of A is referenced = 'L': Lower triangular part of A is referenced N (input) long The order of the matrix A. N >= 0. When N = 0, DLANSY is set to zero. A (input) double array, dimension (LDA,N) The symmetric matrix A. If UPLO = 'U', the leading n by n upper triangular part of A contains the upper triangular part of the matrix A, and the strictly lower triangular part of A is not referenced. If UPLO = 'L', the leading n by n lower triangular part of A contains the lower triangular part of the matrix A, and the strictly upper triangular part of A is not referenced. LDA (input) long The leading dimension of the array A. LDA >= max(N,1). WORK (workspace) double array, dimension (LWORK), where LWORK >= N when NORM = 'I' or '1' or 'O'; otherwise, WORK is not referenced. ===================================================================== */ int NUMlapack_dlanv2 (double *a, double *b, double *c, double *d, double *rt1r, double *rt1i, double *rt2r, double *rt2i, double *cs, double *sn); /* -- LAPACK driver routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University June 30, 1999 Purpose ======= NUMlapack_dlanv2 computes the Schur factorization of a real 2-by-2 nonsymmetric matrix in standard form: [ A B ] = [ CS -SN ] [ AA BB ] [ CS SN ] [ C D ] [ SN CS ] [ CC DD ] [-SN CS ] where either 1) CC = 0 so that AA and DD are real eigenvalues of the matrix, or 2) AA = DD and BB*CC < 0, so that AA + or - sqrt(BB*CC) are complex conjugate eigenvalues. Arguments ========= A (input/output) double B (input/output) double C (input/output) double D (input/output) double On entry, the elements of the input matrix. On exit, they are overwritten by the elements of the standardised Schur form. RT1R (output) double RT1I (output) double RT2R (output) double RT2I (output) double The real and imaginary parts of the eigenvalues. If the eigenvalues are a complex conjugate pair, RT1I > 0. CS (output) double SN (output) double Parameters of the rotation matrix. Further Details =============== Modified by V. Sima, Research Institute for Informatics, Bucharest, Romania, to reduce the risk of cancellation errors, when computing real eigenvalues, and to ensure, if possible, that abs(RT1R) >= abs(RT2R). ===================================================================== */ int NUMlapack_dlapll(long *n, double *x, long *incx, double *y, long *incy, double *ssmin); /* Purpose ======= Given two column vectors X and Y, let A = ( X Y ). The subroutine first computes the QR factorization of A = Q*R, and then computes the SVD of the 2-by-2 upper triangular matrix R. The smaller singular value of R is returned in SSMIN, which is used as the measurement of the linear dependency of the vectors X and Y. Arguments ========= N (input) long The length of the vectors X and Y. X (input/output) double array, dimension (1+(N-1)*INCX) On entry, X contains the N-vector X. On exit, X is overwritten. INCX (input) long The increment between successive elements of X. INCX > 0. Y (input/output) double array, dimension (1+(N-1)*INCY) On entry, Y contains the N-vector Y. On exit, Y is overwritten. INCY (input) long The increment between successive elements of Y. INCY > 0. SSMIN (output) double The smallest singular value of the N-by-2 matrix A = ( X Y ). ===================================================================== */ double NUMlapack_dlapy2 (double *x, double *y); /* Purpose ======= NUMlapack_dlapy2 returns sqrt(x**2+y**2), taking care not to cause unnecessary overflow. Arguments ========= X (input) double Y (input) double X and Y specify the values x and y. ===================================================================== */ int NUMlapack_dlapmt (long *forwrd, long *m, long *n, double *x, long *ldx, long *k); /* Purpose ======= NUMlapack_dlapmt rearranges the columns of the M by N matrix X as specified by the permutation K(1),K(2),...,K(N) of the integers 1,...,N. If FORWRD = TRUE, forward permutation: X(*,K(J)) is moved X(*,J) for J = 1,2,...,N. If FORWRD = FALSE, backward permutation: X(*,J) is moved to X(*,K(J)) for J = 1,2,...,N. Arguments ========= FORWRD (input) long* (boolean) = TRUE, forward permutation = FALSE, backward permutation M (input) long The number of rows of the matrix X. M >= 0. N (input) long The number of columns of the matrix X. N >= 0. X (input/output) double array, dimension (LDX,N) On entry, the M by N matrix X. On exit, X contains the permuted matrix X. LDX (input) long The leading dimension of the array X, LDX >= MAX(1,M). K (input) long array, dimension (N) On entry, K contains the permutation vector. ===================================================================== */ int NUMlapack_dlarf (const char *side, long *m, long *n, double *v, long *incv, double *tau, double *c, long *ldc, double *work); /* Purpose ======= NUMlapack_dlarf applies a real elementary reflector H to a real m by n matrix C, from either the left or the right. H is represented in the form H = I - tau * v * v' where tau is a real scalar and v is a real vector. If tau = 0, then H is taken to be the unit matrix. Arguments ========= SIDE (input) char* = 'L': form H * C = 'R': form C * H M (input) long The number of rows of the matrix C. N (input) long The number of columns of the matrix C. V (input) double array, dimension (1 + (M-1)*abs(INCV)) if SIDE = 'L' or (1 + (N-1)*abs(INCV)) if SIDE = 'R' The vector v in the representation of H. V is not used if TAU = 0. INCV (input) long The increment between elements of v. INCV <> 0. TAU (input) double The value tau in the representation of H. C (input/output) double array, dimension (LDC,N) On entry, the m by n matrix C. On exit, C is overwritten by the matrix H * C if SIDE = 'L', or C * H if SIDE = 'R'. LDC (input) long The leading dimension of the array C. LDC >= max(1,M). WORK (workspace) double array, dimension (N) if SIDE = 'L' or (M) if SIDE = 'R' ===================================================================== */ int NUMlapack_dlarfb (const char *side, const char *trans, const char *direct, const char *storev, long *m, long *n, long *k, double *v, long *ldv, double *t, long *ldt, double *c, long *ldc, double *work, long *ldwork); /* Purpose ======= NUMlapack_dlarfb applies a real block reflector H or its transpose H' to a real m by n matrix C, from either the left or the right. Arguments ========= SIDE (input) char* = 'L': apply H or H' from the Left = 'R': apply H or H' from the Right TRANS (input) char* = 'N': apply H (No transpose) = 'T': apply H' (Transpose) DIRECT (input) char* Indicates how H is formed from a product of elementary reflectors = 'F': H = H(1) H(2) . . . H(k) (Forward) = 'B': H = H(k) . . . H(2) H(1) (Backward) STOREV (input) char* Indicates how the vectors which define the elementary reflectors are stored: = 'C': Columnwise = 'R': Rowwise M (input) long The number of rows of the matrix C. N (input) long The number of columns of the matrix C. K (input) long The order of the matrix T (= the number of elementary reflectors whose product defines the block reflector). V (input) double array, dimension (LDV,K) if STOREV = 'C' (LDV,M) if STOREV = 'R' and SIDE = 'L' (LDV,N) if STOREV = 'R' and SIDE = 'R' The matrix V. See further details. LDV (input) long The leading dimension of the array V. If STOREV = 'C' and SIDE = 'L', LDV >= max(1,M); if STOREV = 'C' and SIDE = 'R', LDV >= max(1,N); if STOREV = 'R', LDV >= K. T (input) double array, dimension (LDT,K) The triangular k by k matrix T in the representation of the block reflector. LDT (input) long The leading dimension of the array T. LDT >= K. C (input/output) double array, dimension (LDC,N) On entry, the m by n matrix C. On exit, C is overwritten by H*C or H'*C or C*H or C*H'. LDC (input) long The leading dimension of the array C. LDA >= max(1,M). WORK (workspace) double array, dimension (LDWORK,K) LDWORK (input) long The leading dimension of the array WORK. If SIDE = 'L', LDWORK >= max(1,N); if SIDE = 'R', LDWORK >= max(1,M). ===================================================================== */ int NUMlapack_dlarfg (long *n, double *alpha, double *x, long *incx, double *tau); /* Purpose ======= NUMlapack_dlarfg generates a real elementary reflector H of order n, such that H * ( alpha ) = ( beta ), H' * H = I. ( x ) ( 0 ) where alpha and beta are scalars, and x is an (n-1)-element real vector. H is represented in the form H = I - tau * ( 1 ) * ( 1 v' ) , ( v ) where tau is a real scalar and v is a real (n-1)-element vector. If the elements of x are all zero, then tau = 0 and H is taken to be the unit matrix. Otherwise 1 <= tau <= 2. Arguments ========= N (input) long The order of the elementary reflector. ALPHA (input/output) double On entry, the value alpha. On exit, it is overwritten with the value beta. X (input/output) double array, dimension (1+(N-2)*abs(INCX)) On entry, the vector x. On exit, it is overwritten with the vector v. INCX (input) long The increment between elements of X. INCX > 0. TAU (output) double The value tau. ===================================================================== */ int NUMlapack_dlarft (const char *direct, const char *storev, long *n, long *k, double *v, long *ldv, double *tau, double *t, long *ldt); /* Purpose ======= NUMlapack_dlarft forms the triangular factor T of a real block reflector H of order n, which is defined as a product of k elementary reflectors. If DIRECT = 'F', H = H(1) H(2) . . . H(k) and T is upper triangular; If DIRECT = 'B', H = H(k) . . . H(2) H(1) and T is lower triangular. If STOREV = 'C', the vector which defines the elementary reflector H(i) is stored in the i-th column of the array V, and H = I - V * T * V' If STOREV = 'R', the vector which defines the elementary reflector H(i) is stored in the i-th row of the array V, and H = I - V' * T * V Arguments ========= DIRECT (input) char* Specifies the order in which the elementary reflectors are multiplied to form the block reflector: = 'F': H = H(1) H(2) . . . H(k) (Forward) = 'B': H = H(k) . . . H(2) H(1) (Backward) STOREV (input) char* Specifies how the vectors which define the elementary reflectors are stored (see also Further Details): = 'C': columnwise = 'R': rowwise N (input) long The order of the block reflector H. N >= 0. K (input) long The order of the triangular factor T (= the number of elementary reflectors). K >= 1. V (input/output) double array, dimension (LDV,K) if STOREV = 'C' (LDV,N) if STOREV = 'R' The matrix V. See further details. LDV (input) long The leading dimension of the array V. If STOREV = 'C', LDV >= max(1,N); if STOREV = 'R', LDV >= K. TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i). T (output) double array, dimension (LDT,K) The k by k triangular factor T of the block reflector. If DIRECT = 'F', T is upper triangular; if DIRECT = 'B', T is lower triangular. The rest of the array is not used. LDT (input) long The leading dimension of the array T. LDT >= K. Further Details =============== The shape of the matrix V and the storage of the vectors which define the H(i) is best illustrated by the following example with n = 5 and k = 3. The elements equal to 1 are not stored; the corresponding array elements are modified but restored on exit. The rest of the array is not used. DIRECT = 'F' and STOREV = 'C': DIRECT = 'F' and STOREV = 'R': V = ( 1 ) V = ( 1 v1 v1 v1 v1 ) ( v1 1 ) ( 1 v2 v2 v2 ) ( v1 v2 1 ) ( 1 v3 v3 ) ( v1 v2 v3 ) ( v1 v2 v3 ) DIRECT = 'B' and STOREV = 'C': DIRECT = 'B' and STOREV = 'R': V = ( v1 v2 v3 ) V = ( v1 v1 1 ) ( v1 v2 v3 ) ( v2 v2 v2 1 ) ( 1 v2 v3 ) ( v3 v3 v3 v3 1 ) ( 1 v3 ) ( 1 ) ===================================================================== */ int NUMlapack_dlarfx (const char *side, long *m, long *n, double *v, double *tau, double *c, long *ldc, double *work); /* -- LAPACK auxiliary routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University February 29, 1992 Purpose ======= NUMlapack_dlarfx applies a real elementary reflector H to a real m by n matrix C, from either the left or the right. H is represented in the form H = I - tau * v * v' where tau is a real scalar and v is a real vector. If tau = 0, then H is taken to be the unit matrix This version uses inline code if H has order < 11. Arguments ========= SIDE (input) char* = 'L': form H * C = 'R': form C * H M (input) long The number of rows of the matrix C. N (input) long The number of columns of the matrix C. V (input) double array, dimension (M) if SIDE = 'L' or (N) if SIDE = 'R' The vector v in the representation of H. TAU (input) double The value tau in the representation of H. C (input/output) double array, dimension (LDC,N) On entry, the m by n matrix C. On exit, C is overwritten by the matrix H * C if SIDE = 'L', or C * H if SIDE = 'R'. LDC (input) long The leading dimension of the array C. LDA >= (1,M). WORK (workspace) double array, dimension (N) if SIDE = 'L' or (M) if SIDE = 'R' WORK is not referenced if H has order < 11. ===================================================================== */ int NUMlapack_dlartg (double *f, double *g, double *cs, double *sn, double *r); /* Purpose ======= NUMlapack_dlartg generate a plane rotation so that [ CS SN ] . [ F ] = [ R ] where CS**2 + SN**2 = 1. [ -SN CS ] [ G ] [ 0 ] This is a slower, more accurate version of the BLAS1 routine DROTG, with the following other differences: F and G are unchanged on return. If G=0, then CS=1 and SN=0. If F=0 and (G .ne. 0), then CS=0 and SN=1 without doing any floating point operations (saves work in DBDSQR when there are zeros on the diagonal). If F exceeds G in magnitude, CS will be positive. Arguments ========= F (input) double The first component of vector to be rotated. G (input) double The second component of vector to be rotated. CS (output) double The cosine of the rotation. SN (output) double The sine of the rotation. R (output) double The nonzero component of the rotated vector. ===================================================================== */ int NUMlapack_dlas2 (double *f, double *g, double *h, double *ssmin, double *ssmax); /* Purpose ======= NUMlapack_dlas2 computes the singular values of the 2-by-2 matrix [ F G ] [ 0 H ]. On return, SSMIN is the smaller singular value and SSMAX is the larger singular value. Arguments ========= F (input) double The (1,1) element of the 2-by-2 matrix. G (input) double The (1,2) element of the 2-by-2 matrix. H (input) double The (2,2) element of the 2-by-2 matrix. SSMIN (output) double The smaller singular value. SSMAX (output) double The larger singular value. Further Details =============== Barring over/underflow, all output quantities are correct to within a few units in the last place (ulps), even in the absence of a guard digit in addition/subtraction. In IEEE arithmetic, the code works correctly if one matrix element is infinite. Overflow will not occur unless the largest singular value itself overflows, or is within a few ulps of overflow. (On machines with partial overflow, like the Cray, overflow may occur if the largest singular value is within a factor of 2 of overflow.) Underflow is harmless if underflow is gradual. Otherwise, results may correspond to a matrix modified by perturbations of size near the underflow threshold. ==================================================================== */ int NUMlapack_dlascl (const char *type, long *kl, long *ku, double *cfrom, double *cto, long *m, long *n, double *a, long *lda, long *info); /* Purpose ======= NUMlapack_dlascl multiplies the M by N real matrix A by the real scalar CTO/CFROM. This is done without over/underflow as long as the final result CTO*A(I,J)/CFROM does not over/underflow. TYPE specifies that A may be full, upper triangular, lower triangular, upper Hessenberg, or banded. Arguments ========= TYPE (input) char* TYPE indices the storage type of the input matrix. = 'G': A is a full matrix. = 'L': A is a lower triangular matrix. = 'U': A is an upper triangular matrix. = 'H': A is an upper Hessenberg matrix. = 'B': A is a symmetric band matrix with lower bandwidth KL and upper bandwidth KU and with the only the lower half stored. = 'Q': A is a symmetric band matrix with lower bandwidth KL and upper bandwidth KU and with the only the upper half stored. = 'Z': A is a band matrix with lower bandwidth KL and upper bandwidth KU. KL (input) long The lower bandwidth of A. Referenced only if TYPE = 'B', 'Q' or 'Z'. KU (input) long The upper bandwidth of A. Referenced only if TYPE = 'B', 'Q' or 'Z'. CFROM (input) double CTO (input) double The matrix A is multiplied by CTO/CFROM. A(I,J) is computed without over/underflow if the final result CTO*A(I,J)/CFROM can be represented without over/underflow. CFROM must be nonzero. M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,M) The matrix to be multiplied by CTO/CFROM. See TYPE for the storage type. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). INFO (output) long 0 - successful exit <0 - if INFO = -i, the i-th argument had an illegal value. ===================================================================== */ int NUMlapack_dlaset (const char *uplo, long *m, long *n, double *alpha, double *beta, double *a, long *lda); /* Purpose ======= NUMlapack_dlaset initializes an m-by-n matrix A to BETA on the diagonal and ALPHA on the offdiagonals. Arguments ========= UPLO (input) char* Specifies the part of the matrix A to be set. = 'U': Upper triangular part is set; the strictly lower triangular part of A is not changed. = 'L': Lower triangular part is set; the strictly upper triangular part of A is not changed. Otherwise: All of the matrix A is set. M (input) long The number of rows of the matrix A. M >= 0. N (input) long The number of columns of the matrix A. N >= 0. ALPHA (input) double The constant to which the offdiagonal elements are to be set. BETA (input) double The constant to which the diagonal elements are to be set. A (input/output) double array, dimension (LDA,N) On exit, the leading m-by-n submatrix of A is set as follows: if UPLO = 'U', A(i,j) = ALPHA, 1<=i<=j-1, 1<=j<=n, if UPLO = 'L', A(i,j) = ALPHA, j+1<=i<=m, 1<=j<=n, otherwise, A(i,j) = ALPHA, 1<=i<=m, 1<=j<=n, i.ne.j, and, for all UPLO, A(i,i) = BETA, 1<=i<=min(m,n). LDA (input) long The leading dimension of the array A. LDA >= max(1,M). ===================================================================== */ int NUMlapack_dlasq1 (long *n, double *d, double *e, double *work, long *info); /* Purpose ======= NUMlapack_dlasq1 computes the singular values of a real N-by-N bidiagonal matrix with diagonal D and off-diagonal E. The singular values are computed to high relative accuracy, in the absence of denormalization, underflow and overflow. The algorithm was first presented in "Accurate singular values and differential qd algorithms" by K. V. Fernando and B. N. Parlett, Numer. Math., Vol-67, No. 2, pp. 191-230, 1994, and the present implementation is described in "An implementation of the dqds Algorithm (Positive Case)", LAPACK Working Note. Arguments ========= N (input) long The number of rows and columns in the matrix. N >= 0. D (input/output) double array, dimension (N) On entry, D contains the diagonal elements of the bidiagonal matrix whose SVD is desired. On normal exit, D contains the singular values in decreasing order. E (input/output) double array, dimension (N) On entry, elements E(1:N-1) contain the off-diagonal elements of the bidiagonal matrix whose SVD is desired. On exit, E is overwritten. WORK (workspace) double array, dimension (4*N) INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value > 0: the algorithm failed = 1, a split was marked by a positive value in E = 2, current block of Z not diagonalized after 30*N iterations (in inner while loop) = 3, termination criterion of outer while loop not met (program created more than N unreduced blocks) ===================================================================== */ int NUMlapack_dlasq2 (long *n, double *z, long *info); /* Purpose ======= NUMlapack_dlasq2 computes all the eigenvalues of the symmetric positive definite tridiagonal matrix associated with the qd array Z to high relative accuracy are computed to high relative accuracy, in the absence of denormalization, underflow and overflow. To see the relation of Z to the tridiagonal matrix, let L be a unit lower bidiagonal matrix with subdiagonals Z(2,4,6,,..) and let U be an upper bidiagonal matrix with 1's above and diagonal Z(1,3,5,,..). The tridiagonal is L*U or, if you prefer, the symmetric tridiagonal to which it is similar. Note : NUMlapack_dlasq2 defines a long* (boolean) variable, IEEE, which is true on machines which follow ieee-754 floating-point standard in their handling of infinities and NaNs, and false otherwise. This variable is passed to NUMlapack_dlasq3. Arguments ========= N (input) long The number of rows and columns in the matrix. N >= 0. Z (workspace) double array, dimension ( 4*N ) On entry Z holds the qd array. On exit, entries 1 to N hold the eigenvalues in decreasing order, Z( 2*N+1 ) holds the trace, and Z( 2*N+2 ) holds the sum of the eigenvalues. If N > 2, then Z( 2*N+3 ) holds the iteration count, Z( 2*N+4 ) holds NDIVS/NIN^2, and Z( 2*N+5 ) holds the percentage of shifts that failed. INFO (output) long = 0: successful exit < 0: if the i-th argument is a scalar and had an illegal value, then INFO = -i, if the i-th argument is an array and the j-entry had an illegal value, then INFO = -(i*100+j) > 0: the algorithm failed = 1, a split was marked by a positive value in E = 2, current block of Z not diagonalized after 30*N iterations (in inner while loop) = 3, termination criterion of outer while loop not met (program created more than N unreduced blocks) Further Details =============== Local Variables: I0:N0 defines a current unreduced segment of Z. The shifts are accumulated in SIGMA. Iteration count is in ITER. Ping-pong is controlled by PP (alternates between 0 and 1). ===================================================================== */ int NUMlapack_dlasq3 (long *i0, long *n0, double *z, long *pp, double *dmin, double *sigma, double *desig, double *qmax, long *nfail, long *iter, long *ndiv, long *ieee); /* Purpose ======= NUMlapack_dlasq3 checks for deflation, computes a shift (TAU) and calls dqds. In case of failure it changes shifts, and tries again until output is positive. Arguments ========= I0 (input) long First index. N0 (input) long Last index. Z (input) double array, dimension ( 4*N ) Z holds the qd array. PP (input) long PP=0 for ping, PP=1 for pong. DMIN (output) double Minimum value of d. SIGMA (output) double Sum of shifts used in current segment. DESIG (input/output) double Lower order part of SIGMA QMAX (input) double Maximum value of q. NFAIL (output) long Number of times shift was too big. ITER (output) long Number of iterations. NDIV (output) long Number of divisions. TTYPE (output) long Shift type. IEEE (input) long* (boolean) Flag for IEEE or non IEEE arithmetic (passed to DLASQ5). ===================================================================== */ int NUMlapack_dlasq4 (long *i0, long *n0, double *z, long *pp, long *n0in, double *dmin, double *dmin1, double *dmin2, double *dn, double *dn1, double *dn2, double *tau, long *ttype); /* Purpose ======= NUMlapack_dlasq4 computes an approximation TAU to the smallest eigenvalue using values of d from the previous transform. I0 (input) long First index. N0 (input) long Last index. Z (input) double array, dimension ( 4*N ) Z holds the qd array. PP (input) long PP=0 for ping, PP=1 for pong. NOIN (input) long The value of N0 at start of EIGTEST. DMIN (input) double Minimum value of d. DMIN1 (input) double Minimum value of d, excluding D( N0 ). DMIN2 (input) double Minimum value of d, excluding D( N0 ) and D( N0-1 ). DN (input) double d(N) DN1 (input) double d(N-1) DN2 (input) double d(N-2) TAU (output) double This is the shift. TTYPE (output) long Shift type. Further Details =============== CNST1 = 9/16 ===================================================================== */ int NUMlapack_dlasq5 (long *i0, long *n0, double *z, long *pp, double *tau, double *dmin, double *dmin1, double *dmin2, double *dn, double *dnm1, double *dnm2, long *ieee); /* Purpose ======= NUMlapack_dlasq5 computes one dqds transform in ping-pong form, one version for IEEE machines another for non IEEE machines. Arguments ========= I0 (input) long First index. N0 (input) long Last index. Z (input) double array, dimension ( 4*N ) Z holds the qd array. EMIN is stored in Z(4*N0) to avoid an extra argument. PP (input) long PP=0 for ping, PP=1 for pong. TAU (input) double This is the shift. DMIN (output) double Minimum value of d. DMIN1 (output) double Minimum value of d, excluding D( N0 ). DMIN2 (output) double Minimum value of d, excluding D( N0 ) and D( N0-1 ). DN (output) double d(N0), the last value of d. DNM1 (output) double d(N0-1). DNM2 (output) double d(N0-2). IEEE (input) long* (boolean) Flag for IEEE or non IEEE arithmetic. ===================================================================== */ int NUMlapack_dlasq6 (long *i0, long *n0, double *z, long *pp, double *dmin, double *dmin1, double *dmin2, double *dn, double *dnm1, double *dnm2); /* Purpose ======= NUMlapack_dlasq6 computes one dqd (shift equal to zero) transform in ping-pong form, with protection against underflow and overflow. Arguments ========= I0 (input) long First index. N0 (input) long Last index. Z (input) double array, dimension ( 4*N ) Z holds the qd array. EMIN is stored in Z(4*N0) to avoid an extra argument. PP (input) long PP=0 for ping, PP=1 for pong. DMIN (output) double Minimum value of d. DMIN1 (output) double Minimum value of d, excluding D( N0 ). DMIN2 (output) double Minimum value of d, excluding D( N0 ) and D( N0-1 ). DN (output) double d(N0), the last value of d. DNM1 (output) double d(N0-1). DNM2 (output) double d(N0-2). ===================================================================== */ int NUMlapack_dlasr (const char *side, const char *pivot, const char *direct, long *m, long *n, double *c, double *s, double *a, long *lda); /* Purpose ======= NUMlapack_dlasr performs the transformation A := P*A, when SIDE = 'L' or 'l' ( Left-hand side ) A := A*P', when SIDE = 'R' or 'r' ( Right-hand side ) where A is an m by n real matrix and P is an orthogonal matrix, consisting of a sequence of plane rotations determined by the parameters PIVOT and DIRECT as follows ( z = m when SIDE = 'L' or 'l' and z = n when SIDE = 'R' or 'r' ): When DIRECT = 'F' or 'f' ( Forward sequence ) then P = P( z - 1 )*...*P( 2 )*P( 1 ), and when DIRECT = 'B' or 'b' ( Backward sequence ) then P = P( 1 )*P( 2 )*...*P( z - 1 ), where P( k ) is a plane rotation matrix for the following planes: when PIVOT = 'V' or 'v' ( Variable pivot ), the plane ( k, k + 1 ) when PIVOT = 'T' or 't' ( Top pivot ), the plane ( 1, k + 1 ) when PIVOT = 'B' or 'b' ( Bottom pivot ), the plane ( k, z ) c( k ) and s( k ) must contain the cosine and sine that define the matrix P( k ). The two by two plane rotation part of the matrix P( k ), R( k ), is assumed to be of the form R( k ) = ( c( k ) s( k ) ). ( -s( k ) c( k ) ) This version vectorises across rows of the array A when SIDE = 'L'. Arguments ========= SIDE (input) char* Specifies whether the plane rotation matrix P is applied to A on the left or the right. = 'L': Left, compute A := P*A = 'R': Right, compute A:= A*P' DIRECT (input) char* Specifies whether P is a forward or backward sequence of plane rotations. = 'F': Forward, P = P( z - 1 )*...*P( 2 )*P( 1 ) = 'B': Backward, P = P( 1 )*P( 2 )*...*P( z - 1 ) PIVOT (input) char* Specifies the plane for which P(k) is a plane rotation matrix. = 'V': Variable pivot, the plane (k,k+1) = 'T': Top pivot, the plane (1,k+1) = 'B': Bottom pivot, the plane (k,z) M (input) long The number of rows of the matrix A. If m <= 1, an immediate return is effected. N (input) long The number of columns of the matrix A. If n <= 1, an immediate return is effected. C, S (input) double arrays, dimension (M-1) if SIDE = 'L' (N-1) if SIDE = 'R' c(k) and s(k) contain the cosine and sine that define the matrix P(k). The two by two plane rotation part of the matrix P(k), R(k), is assumed to be of the form R( k ) = ( c( k ) s( k ) ). ( -s( k ) c( k ) ) A (input/output) double array, dimension (LDA,N) The m by n matrix A. On exit, A is overwritten by P*A if SIDE = 'R' or by A*P' if SIDE = 'L'. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). ===================================================================== */ int NUMlapack_dlasrt (const char *id, long *n, double *d, long *info); /* Purpose ======= Sort the numbers in D in increasing order (if ID = 'I') or in decreasing order (if ID = 'D' ). Use Quick Sort, reverting to Insertion sort on arrays of size <= 20. Dimension of STACK limits N to about 2**32. Arguments ========= ID (input) char* = 'I': sort D in increasing order; = 'D': sort D in decreasing order. N (input) long The length of the array D. D (input/output) double array, dimension (N) On entry, the array to be sorted. On exit, D has been sorted into increasing order (D(1) <= ... <= D(N) ) or into decreasing order (D(1) >= ... >= D(N) ), depending on ID. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dlassq (long *n, double *x, long *incx, double *scale, double *sumsq); /* Purpose ======= NUMlapack_dlassq returns the values scl and smsq such that ( scl**2 )*smsq = x( 1 )**2 +...+ x( n )**2 + ( scale**2 )*sumsq, where x( i ) = X( 1 + ( i - 1 )*INCX ). The value of sumsq is assumed to be non-negative and scl returns the value scl = max( scale, abs( x( i ) ) ). scale and sumsq must be supplied in SCALE and SUMSQ and scl and smsq are overwritten on SCALE and SUMSQ respectively. The routine makes only one pass through the vector x. Arguments ========= N (input) long The number of elements to be used from the vector X. X (input) double array, dimension (N) The vector for which a scaled sum of squares is computed. x( i ) = X( 1 + ( i - 1 )*INCX ), 1 <= i <= n. INCX (input) long The increment between successive values of the vector X. INCX > 0. SCALE (input/output) double On entry, the value scale in the equation above. On exit, SCALE is overwritten with scl , the scaling factor for the sum of squares. SUMSQ (input/output) double On entry, the value sumsq in the equation above. On exit, SUMSQ is overwritten with smsq , the basic sum of squares from which scl has been factored out. ===================================================================== */ int NUMlapack_dlasv2 (double *f, double *g, double *h, double *ssmin, double *ssmax, double *snr, double *csr, double *snl, double *csl); /* Purpose ======= NUMlapack_dlasv2 computes the singular value decomposition of a 2-by-2 triangular matrix [ F G ] [ 0 H ]. On return, abs(SSMAX) is the larger singular value, abs(SSMIN) is the smaller singular value, and (CSL,SNL) and (CSR,SNR) are the left and right singular vectors for abs(SSMAX), giving the decomposition [ CSL SNL ] [ F G ] [ CSR -SNR ] = [ SSMAX 0 ] [-SNL CSL ] [ 0 H ] [ SNR CSR ] [ 0 SSMIN ]. Arguments ========= F (input) double The (1,1) element of the 2-by-2 matrix. G (input) double The (1,2) element of the 2-by-2 matrix. H (input) double The (2,2) element of the 2-by-2 matrix. SSMIN (output) double abs(SSMIN) is the smaller singular value. SSMAX (output) double abs(SSMAX) is the larger singular value. SNL (output) double CSL (output) double The vector (CSL, SNL) is a unit left singular vector for the singular value abs(SSMAX). SNR (output) double CSR (output) double The vector (CSR, SNR) is a unit right singular vector for the singular value abs(SSMAX). Further Details =============== Any input parameter may be aliased with any output parameter. Barring over/underflow and assuming a guard digit in subtraction, all output quantities are correct to within a few units in the last place (ulps). In IEEE arithmetic, the code works correctly if one matrix element is infinite. Overflow will not occur unless the largest singular value itself overflows or is within a few ulps of overflow. (On machines with partial overflow, like the Cray, overflow may occur if the largest singular value is within a factor of 2 of overflow.) Underflow is harmless if underflow is gradual. Otherwise, results may correspond to a matrix modified by perturbations of size near the underflow threshold. ===================================================================== */ int NUMlapack_dlaswp (long *n, double *a, long *lda, long *k1, long *k2, long *ipiv, long *incx); /* Purpose ======= NUMlapack_dlaswp performs a series of row interchanges on the matrix A. One row interchange is initiated for each of rows K1 through K2 of A. Arguments ========= N (input) long The number of columns of the matrix A. A (input/output) double array, dimension (LDA,N) On entry, the matrix of column dimension N to which the row interchanges will be applied. On exit, the permuted matrix. LDA (input) long The leading dimension of the array A. K1 (input) long The first element of IPIV for which a row interchange will be done. K2 (input) long The last element of IPIV for which a row interchange will be done. IPIV (input) long array, dimension (M*abs(INCX)) The vector of pivot indices. Only the elements in positions K1 through K2 of IPIV are accessed. IPIV(K) = L implies rows K and L are to be interchanged. INCX (input) long The increment between successive values of IPIV. If IPIV is negative, the pivots are applied in reverse order. ===================================================================== */ int NUMlapack_dlatrd (const char *uplo, long *n, long *nb, double *a, long *lda, double *e, double *tau, double *w, long *ldw); /* Purpose ======= NUMlapack_dlatrd reduces NB rows and columns of a real symmetric matrix A to symmetric tridiagonal form by an orthogonal similarity transformation Q' * A * Q, and returns the matrices V and W which are needed to apply the transformation to the unreduced part of A. If UPLO = 'U', DLATRD reduces the last NB rows and columns of a matrix, of which the upper triangle is supplied; if UPLO = 'L', DLATRD reduces the first NB rows and columns of a matrix, of which the lower triangle is supplied. This is an auxiliary routine called by NUMlapack_dsytrd. Arguments ========= UPLO (input) CHARACTER Specifies whether the upper or lower triangular part of the symmetric matrix A is stored: = 'U': Upper triangular = 'L': Lower triangular N (input) long The order of the matrix A. NB (input) long The number of rows and columns to be reduced. A (input/output) double array, dimension (LDA,N) On entry, the symmetric matrix A. If UPLO = 'U', the leading n-by-n upper triangular part of A contains the upper triangular part of the matrix A, and the strictly lower triangular part of A is not referenced. If UPLO = 'L', the leading n-by-n lower triangular part of A contains the lower triangular part of the matrix A, and the strictly upper triangular part of A is not referenced. On exit: if UPLO = 'U', the last NB columns have been reduced to tridiagonal form, with the diagonal elements overwriting the diagonal elements of A; the elements above the diagonal with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors; if UPLO = 'L', the first NB columns have been reduced to tridiagonal form, with the diagonal elements overwriting the diagonal elements of A; the elements below the diagonal with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= (1,N). E (output) double array, dimension (N-1) If UPLO = 'U', E(n-nb:n-1) contains the superdiagonal elements of the last NB columns of the reduced matrix; if UPLO = 'L', E(1:nb) contains the subdiagonal elements of the first NB columns of the reduced matrix. TAU (output) double array, dimension (N-1) The scalar factors of the elementary reflectors, stored in TAU(n-nb:n-1) if UPLO = 'U', and in TAU(1:nb) if UPLO = 'L'. See Further Details. W (output) double array, dimension (LDW,NB) The n-by-nb matrix W required to update the unreduced part of A. LDW (input) long The leading dimension of the array W. LDW >= max(1,N). Further Details =============== If UPLO = 'U', the matrix Q is represented as a product of elementary reflectors Q = H(n) H(n-1) . . . H(n-nb+1). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(i:n) = 0 and v(i-1) = 1; v(1:i-1) is stored on exit in A(1:i-1,i), and tau in TAU(i-1). If UPLO = 'L', the matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(nb). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i) = 0 and v(i+1) = 1; v(i+1:n) is stored on exit in A(i+1:n,i), and tau in TAU(i). The elements of the vectors v together form the n-by-nb matrix V which is needed, with W, to apply the transformation to the unreduced part of the matrix, using a symmetric rank-2k update of the form: A := A - V*W' - W*V'. The contents of A on exit are illustrated by the following examples with n = 5 and nb = 2: if UPLO = 'U': if UPLO = 'L': ( a a a v4 v5 ) ( d ) ( a a v4 v5 ) ( 1 d ) ( a 1 v5 ) ( v1 1 a ) ( d 1 ) ( v1 v2 a a ) ( d ) ( v1 v2 a a a ) where d denotes a diagonal element of the reduced matrix, a denotes an element of the original matrix that is unchanged, and vi denotes an element of the vector defining H(i). ===================================================================== */ int NUMlapack_dorg2l (long *m, long *n, long *k, double * a, long *lda, double *tau, double *work, long *info); /* Purpose ======= NUMlapack_dorg2l generates an m by n real matrix Q with orthonormal columns, which is defined as the last n columns of a product of k elementary reflectors of order m Q = H(k) . . . H(2) H(1) as returned by NUMlapack_dgeqlf. Arguments ========= M (input) long The number of rows of the matrix Q. M >= 0. N (input) long The number of columns of the matrix Q. M >= N >= 0. K (input) long The number of elementary reflectors whose product defines the matrix Q. N >= K >= 0. A (input/output) double array, dimension (LDA,N) On entry, the (n-k+i)-th column must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by DGEQLF in the last k columns of its array argument A. On exit, the m by n matrix Q. LDA (input) long The first dimension of the array A. LDA >= max(1,M). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by DGEQLF. WORK (workspace) double array, dimension (N) INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument has an illegal value ===================================================================== */ int NUMlapack_dorg2r (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *info); /* Purpose ======= NUMlapack_dorg2r generates an m by n real matrix Q with orthonormal columns, which is defined as the first n columns of a product of k elementary reflectors of order m Q = H(1) H(2) . . . H(k) as returned by NUMlapack_dgeqrf. Arguments ========= M (input) long The number of rows of the matrix Q. M >= 0. N (input) long The number of columns of the matrix Q. M >= N >= 0. K (input) long The number of elementary reflectors whose product defines the matrix Q. N >= K >= 0. A (input/output) double array, dimension (LDA,N) On entry, the i-th column must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by DGEQRF in the first k columns of its array argument A. On exit, the m-by-n matrix Q. LDA (input) long The first dimension of the array A. LDA >= max(1,M). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by DGEQRF. WORK (workspace) double array, dimension (N) INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument has an illegal value ===================================================================== */ int NUMlapack_dorgbr (const char *vect, long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dorgbr generates one of the real orthogonal matrices Q or P**T determined by DGEBRD when reducing a real matrix A to bidiagonal form: A = Q * B * P**T. Q and P**T are defined as products of elementary reflectors H(i) or G(i) respectively. If VECT = 'Q', A is assumed to have been an M-by-K matrix, and Q is of order M: if m >= k, Q = H(1) H(2) . . . H(k) and NUMlapack_dorgbr returns the first n columns of Q, where m >= n >= k; if m < k, Q = H(1) H(2) . . . H(m-1) and NUMlapack_dorgbr returns Q as an M-by-M matrix. If VECT = 'P', A is assumed to have been a K-by-N matrix, and P**T is of order N: if k < n, P**T = G(k) . . . G(2) G(1) and NUMlapack_dorgbr returns the first m rows of P**T, where n >= m >= k; if k >= n, P**T = G(n-1) . . . G(2) G(1) and NUMlapack_dorgbr returns P**T as an N-by-N matrix. Arguments ========= VECT (input) char* Specifies whether the matrix Q or the matrix P**T is required, as defined in the transformation applied by DGEBRD: = 'Q': generate Q; = 'P': generate P**T. M (input) long The number of rows of the matrix Q or P**T to be returned. M >= 0. N (input) long The number of columns of the matrix Q or P**T to be returned. N >= 0. If VECT = 'Q', M >= N >= min(M,K); if VECT = 'P', N >= M >= min(N,K). K (input) long If VECT = 'Q', the number of columns in the original M-by-K matrix reduced by DGEBRD. If VECT = 'P', the number of rows in the original K-by-N matrix reduced by DGEBRD. K >= 0. A (input/output) double array, dimension (LDA,N) On entry, the vectors which define the elementary reflectors, as returned by DGEBRD. On exit, the M-by-N matrix Q or P**T. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). TAU (input) double array, dimension (min(M,K)) if VECT = 'Q' (min(N,K)) if VECT = 'P' TAU(i) must contain the scalar factor of the elementary reflector H(i) or G(i), which determines Q or P**T, as returned by DGEBRD in its array argument TAUQ or TAUP. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,min(M,N)). For optimum performance LWORK >= min(M,N)*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dorghr (long *n, long *ilo, long *ihi, double *a, long *lda, double *tau, double *work, long *lwork, long *info); /* -- LAPACK routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University June 30, 1999 Purpose ======= NUMlapack_dorghr generates a real orthogonal matrix Q which is defined as the product of IHI-ILO elementary reflectors of order N, as returned by NUMlapack_dgehrd: Q = H(ilo) H(ilo+1) . . . H(ihi-1). Arguments ========= N (input) long The order of the matrix Q. N >= 0. ILO (input) long IHI (input) long ILO and IHI must have the same values as in the previous call of NUMlapack_dgehrd. Q is equal to the unit matrix except in the submatrix Q(ilo+1:ihi,ilo+1:ihi). 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0. A (input/output) double array, dimension (LDA,N) On entry, the vectors which define the elementary reflectors, as returned by NUMlapack_dgehrd. On exit, the N-by-N orthogonal matrix Q. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). TAU (input) double array, dimension (N-1) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by NUMlapack_dgehrd. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= IHI-ILO. For optimum performance LWORK >= (IHI-ILO)*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dorgl2 (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *info); /* Purpose ======= NUMlapack_dorgl2 generates an m by n real matrix Q with orthonormal rows, which is defined as the first m rows of a product of k elementary reflectors of order n Q = H(k) . . . H(2) H(1) as returned by NUMlapack_dgelqf. Arguments ========= M (input) long The number of rows of the matrix Q. M >= 0. N (input) long The number of columns of the matrix Q. N >= M. K (input) long The number of elementary reflectors whose product defines the matrix Q. M >= K >= 0. A (input/output) double array, dimension (LDA,N) On entry, the i-th row must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by NUMlapack_dgelqf in the first k rows of its array argument A. On exit, the m-by-n matrix Q. LDA (input) long The first dimension of the array A. LDA >= max(1,M). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by NUMlapack_dgelqf. WORK (workspace) double array, dimension (M) INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument has an illegal value ===================================================================== */ int NUMlapack_dorglq (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dorglq generates an M-by-N real matrix Q with orthonormal rows, which is defined as the first M rows of a product of K elementary reflectors of order N Q = H(k) . . . H(2) H(1) as returned by DGELQf. Arguments ========= M (input) long The number of rows of the matrix Q. M >= 0. N (input) long The number of columns of the matrix Q. N >= M. K (input) long The number of elementary reflectors whose product defines the matrix Q. M >= K >= 0. A (input/output) double array, dimension (LDA,N) On entry, the i-th row must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by NUMlapack_dgelqf in the first k rows of its array argument A. On exit, the M-by-N matrix Q. LDA (input) long The first dimension of the array A. LDA >= max(1,M). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by NUMlapack_dgelqf. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,M). For optimum performance LWORK >= M*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument has an illegal value ===================================================================== */ int NUMlapack_dorgql (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dorgql generates an M-by-N real matrix Q with orthonormal columns, which is defined as the last N columns of a product of K elementary reflectors of order M Q = H(k) . . . H(2) H(1) as returned by DGEQLF. Arguments ========= M (input) long The number of rows of the matrix Q. M >= 0. N (input) long The number of columns of the matrix Q. M >= N >= 0. K (input) long The number of elementary reflectors whose product defines the matrix Q. N >= K >= 0. A (input/output) double array, dimension (LDA,N) On entry, the (n-k+i)-th column must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by DGEQLF in the last k columns of its array argument A. On exit, the M-by-N matrix Q. LDA (input) long The first dimension of the array A. LDA >= max(1,M). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by DGEQLF. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,N). For optimum performance LWORK >= N*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument has an illegal value ===================================================================== */ int NUMlapack_dorgqr (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dorgqr generates an M-by-N real matrix Q with orthonormal columns, which is defined as the first N columns of a product of K elementary reflectors of order M Q = H(1) H(2) . . . H(k) as returned by DGEQRF. Arguments ========= M (input) long The number of rows of the matrix Q. M >= 0. N (input) long The number of columns of the matrix Q. M >= N >= 0. K (input) long The number of elementary reflectors whose product defines the matrix Q. N >= K >= 0. A (input/output) double array, dimension (LDA,N) On entry, the i-th column must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by DGEQRF in the first k columns of its array argument A. On exit, the M-by-N matrix Q. LDA (input) long The first dimension of the array A. LDA >= max(1,M). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by DGEQRF. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,N). For optimum performance LWORK >= N*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument has an illegal value ===================================================================== */ int NUMlapack_dorgtr (const char *uplo, long *n, double *a, long *lda, double *tau, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dorgtr generates a real orthogonal matrix Q which is defined as the product of n-1 elementary reflectors of order N, as returned by NUMlapack_dsytrd: if UPLO = 'U', Q = H(n-1) . . . H(2) H(1), if UPLO = 'L', Q = H(1) H(2) . . . H(n-1). Arguments ========= UPLO (input) char* = 'U': Upper triangle of A contains elementary reflectors from NUMlapack_dsytrd; = 'L': Lower triangle of A contains elementary reflectors from NUMlapack_dsytrd. N (input) long The order of the matrix Q. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the vectors which define the elementary reflectors, as returned by NUMlapack_dsytrd. On exit, the N-by-N orthogonal matrix Q. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). TAU (input) double array, dimension (N-1) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by NUMlapack_dsytrd. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= max(1,N-1). For optimum performance LWORK >= (N-1)*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dorm2r (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c, long *ldc, double *work, long *info); /* Purpose ======= NUMlapack_dorm2r overwrites the general real m by n matrix C with Q * C if SIDE = 'L' and TRANS = 'N', or Q'* C if SIDE = 'L' and TRANS = 'T', or C * Q if SIDE = 'R' and TRANS = 'N', or C * Q' if SIDE = 'R' and TRANS = 'T', where Q is a real orthogonal matrix defined as the product of k elementary reflectors Q = H(1) H(2) . . . H(k) as returned by DGEQRF. Q is of order m if SIDE = 'L' and of order n if SIDE = 'R'. Arguments ========= SIDE (input) char* = 'L': apply Q or Q' from the Left = 'R': apply Q or Q' from the Right TRANS (input) char* = 'N': apply Q (No transpose) = 'T': apply Q' (Transpose) M (input) long The number of rows of the matrix C. M >= 0. N (input) long The number of columns of the matrix C. N >= 0. K (input) long The number of elementary reflectors whose product defines the matrix Q. If SIDE = 'L', M >= K >= 0; if SIDE = 'R', N >= K >= 0. A (input) double array, dimension (LDA,K) The i-th column must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by DGEQRF in the first k columns of its array argument A. A is modified by the routine but restored on exit. LDA (input) long The leading dimension of the array A. If SIDE = 'L', LDA >= max(1,M); if SIDE = 'R', LDA >= max(1,N). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by DGEQRF. C (input/output) double array, dimension (LDC,N) On entry, the m by n matrix C. On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q. LDC (input) long The leading dimension of the array C. LDC >= max(1,M). WORK (workspace) double array, dimension (N) if SIDE = 'L', (M) if SIDE = 'R' INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dormbr (const char *vect, const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c, long *ldc, double *work, long *lwork, long *info); /* Purpose ======= If VECT = 'Q', NUMlapack_dormbr overwrites the general real M-by-N matrix C with SIDE = 'L' SIDE = 'R' TRANS = 'N': Q * C C * Q TRANS = 'T': Q**T * C C * Q**T If VECT = 'P', NUMlapack_dormbr overwrites the general real M-by-N matrix C with SIDE = 'L' SIDE = 'R' TRANS = 'N': P * C C * P TRANS = 'T': P**T * C C * P**T Here Q and P**T are the orthogonal matrices determined by DGEBRD when reducing a real matrix A to bidiagonal form: A = Q * B * P**T. Q and P**T are defined as products of elementary reflectors H(i) and G(i) respectively. Let nq = m if SIDE = 'L' and nq = n if SIDE = 'R'. Thus nq is the order of the orthogonal matrix Q or P**T that is applied. If VECT = 'Q', A is assumed to have been an NQ-by-K matrix: if nq >= k, Q = H(1) H(2) . . . H(k); if nq < k, Q = H(1) H(2) . . . H(nq-1). If VECT = 'P', A is assumed to have been a K-by-NQ matrix: if k < nq, P = G(1) G(2) . . . G(k); if k >= nq, P = G(1) G(2) . . . G(nq-1). Arguments ========= VECT (input) char* = 'Q': apply Q or Q**T; = 'P': apply P or P**T. SIDE (input) char* = 'L': apply Q, Q**T, P or P**T from the Left; = 'R': apply Q, Q**T, P or P**T from the Right. TRANS (input) char* = 'N': No transpose, apply Q or P; = 'T': Transpose, apply Q**T or P**T. M (input) long The number of rows of the matrix C. M >= 0. N (input) long The number of columns of the matrix C. N >= 0. K (input) long If VECT = 'Q', the number of columns in the original matrix reduced by DGEBRD. If VECT = 'P', the number of rows in the original matrix reduced by DGEBRD. K >= 0. A (input) double array, dimension (LDA,min(nq,K)) if VECT = 'Q' (LDA,nq) if VECT = 'P' The vectors which define the elementary reflectors H(i) and G(i), whose products determine the matrices Q and P, as returned by DGEBRD. LDA (input) long The leading dimension of the array A. If VECT = 'Q', LDA >= max(1,nq); if VECT = 'P', LDA >= max(1,min(nq,K)). TAU (input) double array, dimension (min(nq,K)) TAU(i) must contain the scalar factor of the elementary reflector H(i) or G(i) which determines Q or P, as returned by DGEBRD in the array argument TAUQ or TAUP. C (input/output) double array, dimension (LDC,N) On entry, the M-by-N matrix C. On exit, C is overwritten by Q*C or Q**T*C or C*Q**T or C*Q or P*C or P**T*C or C*P or C*P**T. LDC (input) long The leading dimension of the array C. LDC >= max(1,M). WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. If SIDE = 'L', LWORK >= max(1,N); if SIDE = 'R', LWORK >= max(1,M). For optimum performance LWORK >= N*NB if SIDE = 'L', and LWORK >= M*NB if SIDE = 'R', where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dorml2 (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c, long *ldc, double *work, long *info); /* Purpose ======= NUMlapack_dorml2 overwrites the general real m by n matrix C with Q * C if SIDE = 'L' and TRANS = 'N', or Q'* C if SIDE = 'L' and TRANS = 'T', or C * Q if SIDE = 'R' and TRANS = 'N', or C * Q' if SIDE = 'R' and TRANS = 'T', where Q is a real orthogonal matrix defined as the product of k elementary reflectors Q = H(k) . . . H(2) H(1) as returned by NUMlapack_dgelqf. Q is of order m if SIDE = 'L' and of order n if SIDE = 'R'. Arguments ========= SIDE (input) char* = 'L': apply Q or Q' from the Left = 'R': apply Q or Q' from the Right TRANS (input) char* = 'N': apply Q (No transpose) = 'T': apply Q' (Transpose) M (input) long The number of rows of the matrix C. M >= 0. N (input) long The number of columns of the matrix C. N >= 0. K (input) long The number of elementary reflectors whose product defines the matrix Q. If SIDE = 'L', M >= K >= 0; if SIDE = 'R', N >= K >= 0. A (input) double array, dimension (LDA,M) if SIDE = 'L', (LDA,N) if SIDE = 'R' The i-th row must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by NUMlapack_dgelqf in the first k rows of its array argument A. A is modified by the routine but restored on exit. LDA (input) long The leading dimension of the array A. LDA >= max(1,K). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by NUMlapack_dgelqf. C (input/output) double array, dimension (LDC,N) On entry, the m by n matrix C. On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q. LDC (input) long The leading dimension of the array C. LDC >= max(1,M). WORK (workspace) double array, dimension (N) if SIDE = 'L', (M) if SIDE = 'R' INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dormlq (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c, long *ldc, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dormlq overwrites the general real M-by-N matrix C with SIDE = 'L' SIDE = 'R' TRANS = 'N': Q * C C * Q TRANS = 'T': Q**T * C C * Q**T where Q is a real orthogonal matrix defined as the product of k elementary reflectors Q = H(k) . . . H(2) H(1) as returned by NUMlapack_dgelqf. Q is of order M if SIDE = 'L' and of order N if SIDE = 'R'. Arguments ========= SIDE (input) char* = 'L': apply Q or Q**T from the Left; = 'R': apply Q or Q**T from the Right. TRANS (input) char* = 'N': No transpose, apply Q; = 'T': Transpose, apply Q**T. M (input) long The number of rows of the matrix C. M >= 0. N (input) long The number of columns of the matrix C. N >= 0. K (input) long The number of elementary reflectors whose product defines the matrix Q. If SIDE = 'L', M >= K >= 0; if SIDE = 'R', N >= K >= 0. A (input) double array, dimension (LDA,M) if SIDE = 'L', (LDA,N) if SIDE = 'R' The i-th row must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by NUMlapack_dgelqf in the first k rows of its array argument A. A is modified by the routine but restored on exit. LDA (input) long The leading dimension of the array A. LDA >= max(1,K). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by NUMlapack_dgelqf. C (input/output) double array, dimension (LDC,N) On entry, the M-by-N matrix C. On exit, C is overwritten by Q*C or Q**T*C or C*Q**T or C*Q. LDC (input) long The leading dimension of the array C. LDC >= max(1,M). WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. If SIDE = 'L', LWORK >= max(1,N); if SIDE = 'R', LWORK >= max(1,M). For optimum performance LWORK >= N*NB if SIDE = 'L', and LWORK >= M*NB if SIDE = 'R', where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dormqr (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c, long *ldc, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dormqr overwrites the general real M-by-N matrix C with SIDE = 'L' SIDE = 'R' TRANS = 'N': Q * C C * Q TRANS = 'T': Q**T * C C * Q**T where Q is a real orthogonal matrix defined as the product of k elementary reflectors Q = H(1) H(2) . . . H(k) as returned by DGEQRF. Q is of order M if SIDE = 'L' and of order N if SIDE = 'R'. Arguments ========= SIDE (input) char* = 'L': apply Q or Q**T from the Left; = 'R': apply Q or Q**T from the Right. TRANS (input) char* = 'N': No transpose, apply Q; = 'T': Transpose, apply Q**T. M (input) long The number of rows of the matrix C. M >= 0. N (input) long The number of columns of the matrix C. N >= 0. K (input) long The number of elementary reflectors whose product defines the matrix Q. If SIDE = 'L', M >= K >= 0; if SIDE = 'R', N >= K >= 0. A (input) double array, dimension (LDA,K) The i-th column must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by DGEQRF in the first k columns of its array argument A. A is modified by the routine but restored on exit. LDA (input) long The leading dimension of the array A. If SIDE = 'L', LDA >= max(1,M); if SIDE = 'R', LDA >= max(1,N). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by DGEQRF. C (input/output) double array, dimension (LDC,N) On entry, the M-by-N matrix C. On exit, C is overwritten by Q*C or Q**T*C or C*Q**T or C*Q. LDC (input) long The leading dimension of the array C. LDC >= max(1,M). WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. If SIDE = 'L', LWORK >= max(1,N); if SIDE = 'R', LWORK >= max(1,M). For optimum performance LWORK >= N*NB if SIDE = 'L', and LWORK >= M*NB if SIDE = 'R', where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dormr2 (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c, long *ldc, double *work, long *info); /* Purpose ======= NUMlapack_dormr2 overwrites the general real m by n matrix C with Q * C if SIDE = 'L' and TRANS = 'N', or Q'* C if SIDE = 'L' and TRANS = 'T', or C * Q if SIDE = 'R' and TRANS = 'N', or C * Q' if SIDE = 'R' and TRANS = 'T', where Q is a real orthogonal matrix defined as the product of k elementary reflectors Q = H(1) H(2) . . . H(k) as returned by DGERQF. Q is of order m if SIDE = 'L' and of order n if SIDE = 'R'. Arguments ========= SIDE (input) char* = 'L': apply Q or Q' from the Left = 'R': apply Q or Q' from the Right TRANS (input) char* = 'N': apply Q (No transpose) = 'T': apply Q' (Transpose) M (input) long The number of rows of the matrix C. M >= 0. N (input) long The number of columns of the matrix C. N >= 0. K (input) long The number of elementary reflectors whose product defines the matrix Q. If SIDE = 'L', M >= K >= 0; if SIDE = 'R', N >= K >= 0. A (input) double array, dimension (LDA,M) if SIDE = 'L', (LDA,N) if SIDE = 'R' The i-th row must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k, as returned by DGERQF in the last k rows of its array argument A. A is modified by the routine but restored on exit. LDA (input) long The leading dimension of the array A. LDA >= max(1,K). TAU (input) double array, dimension (K) TAU(i) must contain the scalar factor of the elementary reflector H(i), as returned by DGERQF. C (input/output) double array, dimension (LDC,N) On entry, the m by n matrix C. On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q. LDC (input) long The leading dimension of the array C. LDC >= max(1,M). WORK (workspace) double array, dimension (N) if SIDE = 'L', (M) if SIDE = 'R' INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value ===================================================================== */ int NUMlapack_dpotf2 (const char *uplo, long *n, double *a, long *lda, long *info); /* -- LAPACK routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University February 29, 1992 Purpose ======= NUMlapack_dpotf2 computes the Cholesky factorization of a real symmetric positive definite matrix A. The factorization has the form A = U' * U , if UPLO = 'U', or A = L * L', if UPLO = 'L', where U is an upper triangular matrix and L is lower triangular. This is the unblocked version of the algorithm, calling Level 2 BLAS. Arguments ========= UPLO (input) char * Specifies whether the upper or lower triangular part of the symmetric matrix A is stored. = 'U': Upper triangular = 'L': Lower triangular N (input) long The order of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the symmetric matrix A. If UPLO = 'U', the leading n by n upper triangular part of A contains the upper triangular part of the matrix A, and the strictly lower triangular part of A is not referenced. If UPLO = 'L', the leading n by n lower triangular part of A contains the lower triangular part of the matrix A, and the strictly upper triangular part of A is not referenced. On exit, if INFO = 0, the factor U or L from the Cholesky factorization A = U'*U or A = L*L'. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). INFO (output) long = 0: successful exit < 0: if INFO = -k, the k-th argument had an illegal value > 0: if INFO = k, the leading minor of order k is not positive definite, and the factorization could not be completed. */ int NUMlapack_drscl (long *n, double *sa, double *sx, long *incx); /* Purpose ======= NUMlapack_drscl multiplies an n-element real vector x by the real scalar 1/a. This is done without overflow or underflow as long as the final result x/a does not overflow or underflow. Arguments ========= N (input) long The number of components of the vector x. SA (input) double The scalar a which is used to divide each component of x. SA must be >= 0, or the subroutine will divide by zero. SX (input/output) double array, dimension (1+(N-1)*abs(INCX)) The n-element vector x. INCX (input) long The increment between successive values of the vector SX. > 0: SX(1) = X(1) and SX(1+(i-1)*INCX) = x(i), 1< i<= n ===================================================================== */ int NUMlapack_dsteqr (const char *compz, long *n, double *d, double *e, double *z, long *ldz, double *work, long *info); /* Purpose ======= NUMlapack_dsteqr computes all eigenvalues and, optionally, eigenvectors of a symmetric tridiagonal matrix using the implicit QL or QR method. The eigenvectors of a full or band symmetric matrix can also be found if NUMlapack_dsytrd or DSPTRD or DSBTRD has been used to reduce this matrix to tridiagonal form. Arguments ========= COMPZ (input) char* = 'N': Compute eigenvalues only. = 'V': Compute eigenvalues and eigenvectors of the original symmetric matrix. On entry, Z must contain the orthogonal matrix used to reduce the original matrix to tridiagonal form. = 'I': Compute eigenvalues and eigenvectors of the tridiagonal matrix. Z is initialized to the identity matrix. N (input) long The order of the matrix. N >= 0. D (input/output) double array, dimension (N) On entry, the diagonal elements of the tridiagonal matrix. On exit, if INFO = 0, the eigenvalues in ascending order. E (input/output) double array, dimension (N-1) On entry, the (n-1) subdiagonal elements of the tridiagonal matrix. On exit, E has been destroyed. Z (input/output) double array, dimension (LDZ, N) On entry, if COMPZ = 'V', then Z contains the orthogonal matrix used in the reduction to tridiagonal form. On exit, if INFO = 0, then if COMPZ = 'V', Z contains the orthonormal eigenvectors of the original symmetric matrix, and if COMPZ = 'I', Z contains the orthonormal eigenvectors of the symmetric tridiagonal matrix. If COMPZ = 'N', then Z is not referenced. LDZ (input) long The leading dimension of the array Z. LDZ >= 1, and if eigenvectors are desired, then LDZ >= max(1,N). WORK (workspace) double array, dimension (max(1,2*N-2)) If COMPZ = 'N', then WORK is not referenced. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value > 0: the algorithm has failed to find all the eigenvalues in a total of 30*N iterations; if INFO = i, then i elements of E have not converged to zero; on exit, D and E contain the elements of a symmetric tridiagonal matrix which is orthogonally similar to the original matrix. ===================================================================== */ int NUMlapack_dsterf (long *n, double *d, double *e, long *info); /* Purpose ======= NUMlapack_dsterf computes all eigenvalues of a symmetric tridiagonal matrix using the Pal-Walker-Kahan variant of the QL or QR algorithm. Arguments ========= N (input) long The order of the matrix. N >= 0. D (input/output) double array, dimension (N) On entry, the n diagonal elements of the tridiagonal matrix. On exit, if INFO = 0, the eigenvalues in ascending order. E (input/output) double array, dimension (N-1) On entry, the (n-1) subdiagonal elements of the tridiagonal matrix. On exit, E has been destroyed. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value > 0: the algorithm failed to find all of the eigenvalues in a total of 30*N iterations; if INFO = i, then i elements of E have not converged to zero. ===================================================================== */ int NUMlapack_dsyev (const char *jobz, const char *uplo, long *n, double *a, long *lda, double *w, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dsyev computes all eigenvalues and, optionally, eigenvectors of a real symmetric matrix A. Arguments ========= JOBZ (input) char* = 'N': Compute eigenvalues only; = 'V': Compute eigenvalues and eigenvectors. UPLO (input) char* = 'U': Upper triangle of A is stored; = 'L': Lower triangle of A is stored. N (input) long The order of the matrix A. N >= 0. A (input/output) double array, dimension (LDA, N) On entry, the symmetric matrix A. If UPLO = 'U', the leading N-by-N upper triangular part of A contains the upper triangular part of the matrix A. If UPLO = 'L', the leading N-by-N lower triangular part of A contains the lower triangular part of the matrix A. On exit, if JOBZ = 'V', then if INFO = 0, A contains the orthonormal eigenvectors of the matrix A. If JOBZ = 'N', then on exit the lower triangle (if UPLO='L') or the upper triangle (if UPLO='U') of A, including the diagonal, is destroyed. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). W (output) double array, dimension (N) If INFO = 0, the eigenvalues in ascending order. WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The length of the array WORK. LWORK >= max(1,3*N-1). For optimal efficiency, LWORK >= (NB+2)*N, where NB is the blocksize for NUMlapack_dsytrd returned by NUMlapack_ilaenv. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value > 0: if INFO = i, the algorithm failed to converge; i off-diagonal elements of an intermediate tridiagonal form did not converge to zero. ===================================================================== */ int NUMlapack_dsytd2 (const char *uplo, long *n, double *a, long *lda, double *d, double *e, double *tau, long *info); /* Purpose ======= NUMlapack_dsytd2 reduces a real symmetric matrix A to symmetric tridiagonal form T by an orthogonal similarity transformation: Q' * A * Q = T. Arguments ========= UPLO (input) char* Specifies whether the upper or lower triangular part of the symmetric matrix A is stored: = 'U': Upper triangular = 'L': Lower triangular N (input) long The order of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the symmetric matrix A. If UPLO = 'U', the leading n-by-n upper triangular part of A contains the upper triangular part of the matrix A, and the strictly lower triangular part of A is not referenced. If UPLO = 'L', the leading n-by-n lower triangular part of A contains the lower triangular part of the matrix A, and the strictly upper triangular part of A is not referenced. On exit, if UPLO = 'U', the diagonal and first superdiagonal of A are overwritten by the corresponding elements of the tridiagonal matrix T, and the elements above the first superdiagonal, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors; if UPLO = 'L', the diagonal and first subdiagonal of A are over- written by the corresponding elements of the tridiagonal matrix T, and the elements below the first subdiagonal, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). D (output) double array, dimension (N) The diagonal elements of the tridiagonal matrix T: D(i) = A(i,i). E (output) double array, dimension (N-1) The off-diagonal elements of the tridiagonal matrix T: E(i) = A(i,i+1) if UPLO = 'U', E(i) = A(i+1,i) if UPLO = 'L'. TAU (output) double array, dimension (N-1) The scalar factors of the elementary reflectors (see Further Details). INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value. Further Details =============== If UPLO = 'U', the matrix Q is represented as a product of elementary reflectors Q = H(n-1) . . . H(2) H(1). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(i+1:n) = 0 and v(i) = 1; v(1:i-1) is stored on exit in A(1:i-1,i+1), and tau in TAU(i). If UPLO = 'L', the matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(n-1). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i) = 0 and v(i+1) = 1; v(i+2:n) is stored on exit in A(i+2:n,i), and tau in TAU(i). The contents of A on exit are illustrated by the following examples with n = 5: if UPLO = 'U': if UPLO = 'L': ( d e v2 v3 v4 ) ( d ) ( d e v3 v4 ) ( e d ) ( d e v4 ) ( v1 e d ) ( d e ) ( v1 v2 e d ) ( d ) ( v1 v2 v3 e d ) where d and e denote diagonal and off-diagonal elements of T, and vi denotes an element of the vector defining H(i). ===================================================================== */ int NUMlapack_dsytrd (const char *uplo, long *n, double *a, long *lda, double *d, double *e, double *tau, double *work, long *lwork, long *info); /* Purpose ======= NUMlapack_dsytrd reduces a real symmetric matrix A to real symmetric tridiagonal form T by an orthogonal similarity transformation: Q**T * A * Q = T. Arguments ========= UPLO (input) char* = 'U': Upper triangle of A is stored; = 'L': Lower triangle of A is stored. N (input) long The order of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the symmetric matrix A. If UPLO = 'U', the leading N-by-N upper triangular part of A contains the upper triangular part of the matrix A, and the strictly lower triangular part of A is not referenced. If UPLO = 'L', the leading N-by-N lower triangular part of A contains the lower triangular part of the matrix A, and the strictly upper triangular part of A is not referenced. On exit, if UPLO = 'U', the diagonal and first superdiagonal of A are overwritten by the corresponding elements of the tridiagonal matrix T, and the elements above the first superdiagonal, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors; if UPLO = 'L', the diagonal and first subdiagonal of A are over- written by the corresponding elements of the tridiagonal matrix T, and the elements below the first subdiagonal, with the array TAU, represent the orthogonal matrix Q as a product of elementary reflectors. See Further Details. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). D (output) double array, dimension (N) The diagonal elements of the tridiagonal matrix T: D(i) = A(i,i). E (output) double array, dimension (N-1) The off-diagonal elements of the tridiagonal matrix T: E(i) = A(i,i+1) if UPLO = 'U', E(i) = A(i+1,i) if UPLO = 'L'. TAU (output) double array, dimension (N-1) The scalar factors of the elementary reflectors (see Further Details). WORK (workspace/output) double array, dimension (LWORK) On exit, if INFO = 0, WORK(1) returns the optimal LWORK. LWORK (input) long The dimension of the array WORK. LWORK >= 1. For optimum performance LWORK >= N*NB, where NB is the optimal blocksize. If LWORK = -1, then a workspace query is assumed; the routine only calculates the optimal size of the WORK array, returns this value as the first entry of the WORK array, and no error message related to LWORK is issued by XERBLA. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value Further Details =============== If UPLO = 'U', the matrix Q is represented as a product of elementary reflectors Q = H(n-1) . . . H(2) H(1). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(i+1:n) = 0 and v(i) = 1; v(1:i-1) is stored on exit in A(1:i-1,i+1), and tau in TAU(i). If UPLO = 'L', the matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(n-1). Each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i) = 0 and v(i+1) = 1; v(i+2:n) is stored on exit in A(i+2:n,i), and tau in TAU(i). The contents of A on exit are illustrated by the following examples with n = 5: if UPLO = 'U': if UPLO = 'L': ( d e v2 v3 v4 ) ( d ) ( d e v3 v4 ) ( e d ) ( d e v4 ) ( v1 e d ) ( d e ) ( v1 v2 e d ) ( d ) ( v1 v2 v3 e d ) where d and e denote diagonal and off-diagonal elements of T, and vi denotes an element of the vector defining H(i). ===================================================================== */ int NUMlapack_dtgsja(const char *jobu, const char *jobv, const char *jobq, long *m, long *p, long *n, long *k, long *l, double *a, long *lda, double *b, long *ldb, double *tola, double *tolb, double *alpha, double *beta, double *u, long *ldu, double *v, long *ldv, double *q, long *ldq, double *work, long *ncycle, long *info); /* Purpose ======= NUMlapack_dtgsja computes the generalized singular value decomposition (GSVD) of two real upper triangular (or trapezoidal) matrices A and B. On entry, it is assumed that matrices A and B have the following forms, which may be obtained by the preprocessing subroutine NUMlapack_dggsvp from a general M-by-N matrix A and P-by-N matrix B: N-K-L K L A = K ( 0 A12 A13 ) if M-K-L >= 0; L ( 0 0 A23 ) M-K-L ( 0 0 0 ) N-K-L K L A = K ( 0 A12 A13 ) if M-K-L < 0; M-K ( 0 0 A23 ) N-K-L K L B = L ( 0 0 B13 ) P-L ( 0 0 0 ) where the K-by-K matrix A12 and L-by-L matrix B13 are nonsingular upper triangular; A23 is L-by-L upper triangular if M-K-L >= 0, otherwise A23 is (M-K)-by-L upper trapezoidal. On exit, U'*A*Q = D1*( 0 R ), V'*B*Q = D2*( 0 R ), where U, V and Q are orthogonal matrices, Z' denotes the transpose of Z, R is a nonsingular upper triangular matrix, and D1 and D2 are ``diagonal'' matrices, which are of the following structures: If M-K-L >= 0, K L D1 = K ( I 0 ) L ( 0 C ) M-K-L ( 0 0 ) K L D2 = L ( 0 S ) P-L ( 0 0 ) N-K-L K L ( 0 R ) = K ( 0 R11 R12 ) K L ( 0 0 R22 ) L where C = diag( ALPHA(K+1), ... , ALPHA(K+L) ), S = diag( BETA(K+1), ... , BETA(K+L) ), C**2 + S**2 = I. R is stored in A(1:K+L,N-K-L+1:N) on exit. If M-K-L < 0, K M-K K+L-M D1 = K ( I 0 0 ) M-K ( 0 C 0 ) K M-K K+L-M D2 = M-K ( 0 S 0 ) K+L-M ( 0 0 I ) P-L ( 0 0 0 ) N-K-L K M-K K+L-M ( 0 R ) = K ( 0 R11 R12 R13 ) M-K ( 0 0 R22 R23 ) K+L-M ( 0 0 0 R33 ) where C = diag( ALPHA(K+1), ... , ALPHA(M) ), S = diag( BETA(K+1), ... , BETA(M) ), C**2 + S**2 = I. R = ( R11 R12 R13 ) is stored in A(1:M, N-K-L+1:N) and R33 is stored ( 0 R22 R23 ) in B(M-K+1:L,N+M-K-L+1:N) on exit. The computation of the orthogonal transformation matrices U, V or Q is optional. These matrices may either be formed explicitly, or they may be postmultiplied into input matrices U1, V1, or Q1. Arguments ========= JOBU (input) char* = 'U': U must contain an orthogonal matrix U1 on entry, and the product U1*U is returned; = 'I': U is initialized to the unit matrix, and the orthogonal matrix U is returned; = 'N': U is not computed. JOBV (input) char* = 'V': V must contain an orthogonal matrix V1 on entry, and the product V1*V is returned; = 'I': V is initialized to the unit matrix, and the orthogonal matrix V is returned; = 'N': V is not computed. JOBQ (input) char* = 'Q': Q must contain an orthogonal matrix Q1 on entry, and the product Q1*Q is returned; = 'I': Q is initialized to the unit matrix, and the orthogonal matrix Q is returned; = 'N': Q is not computed. M (input) long The number of rows of the matrix A. M >= 0. P (input) long The number of rows of the matrix B. P >= 0. N (input) long The number of columns of the matrices A and B. N >= 0. K (input) long L (input) long K and L specify the subblocks in the input matrices A and B: A23 = A(K+1:MIN(K+L,M),N-L+1:N) and B13 = B(1:L,N-L+1:N) of A and B, whose GSVD is going to be computed by NUMlapack_dtgsja. See Further details. A (input/output) double array, dimension (LDA,N) On entry, the M-by-N matrix A. On exit, A(N-K+1:N,1:MIN(K+L,M) ) contains the triangular matrix R or part of R. See Purpose for details. LDA (input) long The leading dimension of the array A. LDA >= max(1,M). B (input/output) double array, dimension (LDB,N) On entry, the P-by-N matrix B. On exit, if necessary, B(M-K+1:L,N+M-K-L+1:N) contains a part of R. See Purpose for details. LDB (input) long The leading dimension of the array B. LDB >= max(1,P). TOLA (input) double TOLB (input) double TOLA and TOLB are the convergence criteria for the Jacobi- Kogbetliantz iteration procedure. Generally, they are the same as used in the preprocessing step, say TOLA = max(M,N)*norm(A)*MAZHEPS, TOLB = max(P,N)*norm(B)*MAZHEPS. ALPHA (output) double array, dimension (N) BETA (output) double array, dimension (N) On exit, ALPHA and BETA contain the generalized singular value pairs of A and B; ALPHA(1:K) = 1, BETA(1:K) = 0, and if M-K-L >= 0, ALPHA(K+1:K+L) = diag(C), BETA(K+1:K+L) = diag(S), or if M-K-L < 0, ALPHA(K+1:M)= C, ALPHA(M+1:K+L)= 0 BETA(K+1:M) = S, BETA(M+1:K+L) = 1. Furthermore, if K+L < N, ALPHA(K+L+1:N) = 0 and BETA(K+L+1:N) = 0. U (input/output) double array, dimension (LDU,M) On entry, if JOBU = 'U', U must contain a matrix U1 (usually the orthogonal matrix returned by NUMlapack_dggsvp). On exit, if JOBU = 'I', U contains the orthogonal matrix U; if JOBU = 'U', U contains the product U1*U. If JOBU = 'N', U is not referenced. LDU (input) long The leading dimension of the array U. LDU >= max(1,M) if JOBU = 'U'; LDU >= 1 otherwise. V (input/output) double array, dimension (LDV,P) On entry, if JOBV = 'V', V must contain a matrix V1 (usually the orthogonal matrix returned by NUMlapack_dggsvp). On exit, if JOBV = 'I', V contains the orthogonal matrix V; if JOBV = 'V', V contains the product V1*V. If JOBV = 'N', V is not referenced. LDV (input) long The leading dimension of the array V. LDV >= max(1,P) if JOBV = 'V'; LDV >= 1 otherwise. Q (input/output) double array, dimension (LDQ,N) On entry, if JOBQ = 'Q', Q must contain a matrix Q1 (usually the orthogonal matrix returned by NUMlapack_dggsvp). On exit, if JOBQ = 'I', Q contains the orthogonal matrix Q; if JOBQ = 'Q', Q contains the product Q1*Q. If JOBQ = 'N', Q is not referenced. LDQ (input) long The leading dimension of the array Q. LDQ >= max(1,N) if JOBQ = 'Q'; LDQ >= 1 otherwise. WORK (workspace) double array, dimension (2*N) NCYCLE (output) long The number of cycles required for convergence. INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value. = 1: the procedure does not converge after MAXIT cycles. Internal Parameters =================== MAXIT long MAXIT specifies the total loops that the iterative procedure may take. If after MAXIT cycles, the routine fails to converge, we return INFO = 1. Further Details =============== NUMlapack_dtgsja essentially uses a variant of Kogbetliantz algorithm to reduce min(L,M-K)-by-L triangular (or trapezoidal) matrix A23 and L-by-L matrix B13 to the form: U1'*A13*Q1 = C1*R1; V1'*B13*Q1 = S1*R1, where U1, V1 and Q1 are orthogonal matrix, and Z' is the transpose of Z. C1 and S1 are diagonal matrices satisfying C1**2 + S1**2 = I, and R1 is an L-by-L nonsingular upper triangular matrix. ===================================================================== */ int NUMlapack_dtrevc (const char *side, const char *howmny, int * select, long *n, double *t, long *ldt, double *vl, long *ldvl, double *vr, long *ldvr, long *mm, long *m, double *work, long *info); /* -- LAPACK routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University June 30, 1999 Purpose ======= NUMlapack_dtrevc computes some or all of the right and/or left eigenvectors of a real upper quasi-triangular matrix T. The right eigenvector x and the left eigenvector y of T corresponding to an eigenvalue w are defined by: T*x = w*x, y'*T = w*y' where y' denotes the conjugate transpose of the vector y. If all eigenvectors are requested, the routine may either return the matrices X and/or Y of right or left eigenvectors of T, or the products Q*X and/or Q*Y, where Q is an input orthogonal matrix. If T was obtained from the real-Schur factorization of an original matrix A = Q*T*Q', then Q*X and Q*Y are the matrices of right or left eigenvectors of A. T must be in Schur canonical form (as returned by NUMlapack_dhseqr), that is, block upper triangular with 1-by-1 and 2-by-2 diagonal blocks; each 2-by-2 diagonal block has its diagonal elements equal and its off-diagonal elements of opposite sign. Corresponding to each 2-by-2 diagonal block is a complex conjugate pair of eigenvalues and eigenvectors; only one eigenvector of the pair is computed, namely the one corresponding to the eigenvalue with positive imaginary part. Arguments ========= SIDE (input) char* = 'R': compute right eigenvectors only; = 'L': compute left eigenvectors only; = 'B': compute both right and left eigenvectors. HOWMNY (input) char* = 'A': compute all right and/or left eigenvectors; = 'B': compute all right and/or left eigenvectors, and backtransform them using the input matrices supplied in VR and/or VL; = 'S': compute selected right and/or left eigenvectors, specified by the int array SELECT. SELECT (input/output) int array, dimension (N) If HOWMNY = 'S', SELECT specifies the eigenvectors to be computed. If HOWMNY = 'A' or 'B', SELECT is not referenced. To select the real eigenvector corresponding to a real eigenvalue w(j), SELECT(j) must be set to .TRUE.. To select the complex eigenvector corresponding to a complex conjugate pair w(j) and w(j+1), either SELECT(j) or SELECT(j+1) must be set to .TRUE.; then on exit SELECT(j) is .TRUE. and SELECT(j+1) is .FALSE.. N (input) long The order of the matrix T. N >= 0. T (input) double array, dimension (LDT,N) The upper quasi-triangular matrix T in Schur canonical form. LDT (input) long The leading dimension of the array T. LDT >= max(1,N). VL (input/output) double array, dimension (LDVL,MM) On entry, if SIDE = 'L' or 'B' and HOWMNY = 'B', VL must contain an N-by-N matrix Q (usually the orthogonal matrix Q of Schur vectors returned by NUMlapack_dhseqr). On exit, if SIDE = 'L' or 'B', VL contains: if HOWMNY = 'A', the matrix Y of left eigenvectors of T; VL has the same quasi-lower triangular form as T'. If T(i,i) is a real eigenvalue, then the i-th column VL(i) of VL is its corresponding eigenvector. If T(i:i+1,i:i+1) is a 2-by-2 block whose eigenvalues are complex-conjugate eigenvalues of T, then VL(i)+sqrt(-1)*VL(i+1) is the complex eigenvector corresponding to the eigenvalue with positive real part. if HOWMNY = 'B', the matrix Q*Y; if HOWMNY = 'S', the left eigenvectors of T specified by SELECT, stored consecutively in the columns of VL, in the same order as their eigenvalues. A complex eigenvector corresponding to a complex eigenvalue is stored in two consecutive columns, the first holding the real part, and the second the imaginary part. If SIDE = 'R', VL is not referenced. LDVL (input) long The leading dimension of the array VL. LDVL >= max(1,N) if SIDE = 'L' or 'B'; LDVL >= 1 otherwise. VR (input/output) double array, dimension (LDVR,MM) On entry, if SIDE = 'R' or 'B' and HOWMNY = 'B', VR must contain an N-by-N matrix Q (usually the orthogonal matrix Q of Schur vectors returned by NUMlapack_dhseqr). On exit, if SIDE = 'R' or 'B', VR contains: if HOWMNY = 'A', the matrix X of right eigenvectors of T; VR has the same quasi-upper triangular form as T. If T(i,i) is a real eigenvalue, then the i-th column VR(i) of VR is its corresponding eigenvector. If T(i:i+1,i:i+1) is a 2-by-2 block whose eigenvalues are complex-conjugate eigenvalues of T, then VR(i)+sqrt(-1)*VR(i+1) is the complex eigenvector corresponding to the eigenvalue with positive real part. if HOWMNY = 'B', the matrix Q*X; if HOWMNY = 'S', the right eigenvectors of T specified by SELECT, stored consecutively in the columns of VR, in the same order as their eigenvalues. A complex eigenvector corresponding to a complex eigenvalue is stored in two consecutive columns, the first holding the real part and the second the imaginary part. If SIDE = 'L', VR is not referenced. LDVR (input) long The leading dimension of the array VR. LDVR >= max(1,N) if SIDE = 'R' or 'B'; LDVR >= 1 otherwise. MM (input) long The number of columns in the arrays VL and/or VR. MM >= M. M (output) long The number of columns in the arrays VL and/or VR actually used to store the eigenvectors. If HOWMNY = 'A' or 'B', M is set to N. Each selected real eigenvector occupies one column and each selected complex eigenvector occupies two columns. WORK (workspace) double array, dimension (3*N) INFO (output) INTEGER = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value Further Details =============== The algorithm used in this program is basically backward (forward) substitution, with scaling to make the the code robust against possible overflow. Each eigenvector is normalized so that the element of largest magnitude has magnitude 1; here the magnitude of a complex number (x,y) is taken to be |x| + |y|. ===================================================================== */ int NUMlapack_dtrti2 (const char *uplo, const char *diag, long *n, double *a, long *lda, long *info); /* Purpose ======= NUMlapack_dtrti2 computes the inverse of a real upper or lower triangular matrix. This is the Level 2 BLAS version of the algorithm. Arguments ========= UPLO (input) char* Specifies whether the matrix A is upper or lower triangular. = 'U': Upper triangular = 'L': Lower triangular DIAG (input) char* Specifies whether or not the matrix A is unit triangular. = 'N': Non-unit triangular = 'U': Unit triangular N (input) long The order of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the triangular matrix A. If UPLO = 'U', the leading n by n upper triangular part of the array A contains the upper triangular matrix, and the strictly lower triangular part of A is not referenced. If UPLO = 'L', the leading n by n lower triangular part of the array A contains the lower triangular matrix, and the strictly upper triangular part of A is not referenced. If DIAG = 'U', the diagonal elements of A are also not referenced and are assumed to be 1. On exit, the (triangular) inverse of the original matrix, in the same storage format. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). INFO (output) long = 0: successful exit < 0: if INFO = -k, the k-th argument had an illegal value ===================================================================== */ int NUMlapack_dtrtri (const char *uplo, const char *diag, long *n, double * a, long *lda, long *info); /* Purpose ======= NUMlapack_dtrtri computes the inverse of a real upper or lower triangular matrix A. This is the Level 3 BLAS version of the algorithm. Arguments ========= UPLO (input) char* = 'U': A is upper triangular; = 'L': A is lower triangular. DIAG (input) char* = 'N': A is non-unit triangular; = 'U': A is unit triangular. N (input) long The order of the matrix A. N >= 0. A (input/output) double array, dimension (LDA,N) On entry, the triangular matrix A. If UPLO = 'U', the leading N-by-N upper triangular part of the array A contains the upper triangular matrix, and the strictly lower triangular part of A is not referenced. If UPLO = 'L', the leading N-by-N lower triangular part of the array A contains the lower triangular matrix, and the strictly upper triangular part of A is not referenced. If DIAG = 'U', the diagonal elements of A are also not referenced and are assumed to be 1. On exit, the (triangular) inverse of the original matrix, in the same storage format. LDA (input) long The leading dimension of the array A. LDA >= max(1,N). INFO (output) long = 0: successful exit < 0: if INFO = -i, the i-th argument had an illegal value > 0: if INFO = i, A(i,i) is exactly zero. The triangular matrix is singular and its inverse can not be computed. ===================================================================== */ long NUMlapack_ieeeck (long *ispec, float *zero, float *one); /* Purpose ======= NUMlapack_ieeeck is called from the NUMlapack_ilaenv to verify that Infinity and possibly NaN arithmetic is safe (i.e. will not trap). Arguments ========= ISPEC (input) long Specifies whether to test just for inifinity arithmetic or whether to test for infinity and NaN arithmetic. = 0: Verify infinity arithmetic only. = 1: Verify infinity and NaN arithmetic. ZERO (input) REAL Must contain the value 0.0 This is passed to prevent the compiler from optimizing away this code. ONE (input) REAL Must contain the value 1.0 This is passed to prevent the compiler from optimizing away this code. RETURN VALUE: long = 0: Arithmetic failed to produce the correct answers = 1: Arithmetic produced the correct answers */ long NUMlapack_ilaenv (long *ispec, const char *name, const char *opts, long *n1, long *n2, long *n3, long *n4, long name_len, long opts_len); /* Purpose ======= NUMlapack_ilaenv is called from the LAPACK routines to choose problem-dependent parameters for the local environment. See ISPEC for a description of the parameters. This version provides a set of parameters which should give good, but not optimal, performance on many of the currently available computers. Users are encouraged to modify this subroutine to set the tuning parameters for their particular machine using the option and problem size information in the arguments. This routine will not function correctly if it is converted to all lower case. Converting it to all upper case is allowed. Arguments ========= ISPEC (input) long Specifies the parameter to be returned as the value of NUMlapack_ilaenv. = 1: the optimal blocksize; if this value is 1, an unblocked algorithm will give the best performance. = 2: the minimum block size for which the block routine should be used; if the usable block size is less than this value, an unblocked routine should be used. = 3: the crossover point (in a block routine, for N less than this value, an unblocked routine should be used) = 4: the number of shifts, used in the nonsymmetric eigenvalue routines = 5: the minimum column dimension for blocking to be used; rectangular blocks must have dimension at least k by m, where k is given by NUMlapack_ilaenv(2,...) and m by NUMlapack_ilaenv(5,...) = 6: the crossover point for the SVD (when reducing an m by n matrix to bidiagonal form, if max(m,n)/min(m,n) exceeds this value, a QR factorization is used first to reduce the matrix to a triangular form.) = 7: the number of processors = 8: the crossover point for the multishift QR and QZ methods for nonsymmetric eigenvalue problems. = 9: maximum size of the subproblems at the bottom of the computation tree in the divide-and-conquer algorithm (used by xGELSD and xGESDD) =10: ieee NaN arithmetic can be trusted not to trap =11: infinity arithmetic can be trusted not to trap NAME (input) CHARACTER*(*) The name of the calling subroutine, in either upper case or lower case. OPTS (input) CHARACTER*(*) The character options to the subroutine NAME, concatenated into a single character string. For example, UPLO = 'U', TRANS = 'T', and DIAG = 'N' for a triangular routine would be specified as OPTS = 'UTN'. N1 (input) long N2 (input) long N3 (input) long N4 (input) long Problem dimensions for the subroutine NAME; these may not all be required. (NUMlapack_ilaenv) (output) long >= 0: the value of the parameter specified by ISPEC < 0: if NUMlapack_ilaenv = -k, the k-th argument had an illegal value. Further Details =============== The following conventions have been used when calling NUMlapack_ilaenv from the LAPACK routines: 1) OPTS is a concatenation of all of the character options to subroutine NAME, in the same order that they appear in the argument list for NAME, even if they are not used in determining the value of the parameter specified by ISPEC. 2) The problem dimensions N1, N2, N3, N4 are specified in the order that they appear in the argument list for NAME. N1 is used first, N2 second, and so on, and unused problem dimensions are passed a value of -1. 3) The parameter value returned by NUMlapack_ilaenv is checked for validity in the calling subroutine. For example, NUMlapack_ilaenv is used to retrieve the optimal blocksize for STRTRI as follows: NB = NUMlapack_ilaenv( 1, 'STRTRI', UPLO // DIAG, N, -1, -1, -1 ) IF( NB.LE.1 ) NB = MAX( 1, N ) ===================================================================== */ #ifdef __cplusplus } #endif #endif /* _NUMclapack_h_ */ sources_5316/dwsys/Collection_extensions.cpp0000644000176700017670000002351411631152107020154 0ustar paulpaul/* Collection_extensions.c * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20040420 Fraction in OrderedOfString_difference must be double. djmw 20050511 Skip printing unique labels in OrderedOfString djmw 20061214 djmw 20061214 Changed info to Melder_writeLine format. djmw 20110304 Thing_new */ #include "Collection_extensions.h" #include "Simple_extensions.h" #include "NUM2.h" Collection Collection_and_Permutation_permuteItems (Collection me, Permutation him) { try { if (my size != his numberOfElements) { Melder_throw (me, "The number of elements are not equal."); } autoNUMvector pos (1, my size); autoCollection thee = static_cast (Data_copy (me)); for (long i = 1; i <= my size; i++) { pos[i] = i; } /* Dual meaning of array pos: */ /* k < i : position of item 'k' */ /* k >= i : the item at position 'k' */ for (long i = 1; i <= my size; i++) { long ti = pos[i], which = Permutation_getValueAtIndex (him, i); long where = pos[which]; /* where >= i */ Data tmp = static_cast (thy item[i]); if (i == where) { continue; } thy item[i] = thy item[ where ]; thy item[where] = tmp; /* order is important !! */ pos[ti] = where; pos[where] = ti; pos[which] = which <= i ? i : ti; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not permuted."); } } Collection Collection_permuteItems (Collection me) { try { autoPermutation p = Permutation_create (my size); Permutation_permuteRandomly_inline (p.peek(), 0, 0); autoCollection thee = Collection_and_Permutation_permuteItems (me, p.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": items not permuted."); } } /****************** class OrderedOfString ******************/ void structOrderedOfString :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of strings: ", Melder_integer (size)); autoOrderedOfString uStrings = OrderedOfString_selectUniqueItems (this, 1); MelderInfo_writeLine2 (L"Number of unique categories: ", Melder_integer (uStrings -> size)); } Thing_implement (OrderedOfString, Ordered, 0); int OrderedOfString_init (I, long initialCapacity) { iam (OrderedOfString); Ordered_init (me, classSimpleString, initialCapacity); return 1; } OrderedOfString OrderedOfString_create () { try { autoOrderedOfString me = Thing_new (OrderedOfString); OrderedOfString_init (me.peek(), 10); return me.transfer(); } catch (MelderError) { Melder_throw ("OrderedOfString not created."); } } int OrderedOfString_append (I, wchar_t *append) { iam (OrderedOfString); try { if (append == 0) { return 1; // BUG: lege string appenden?? } autoSimpleString item = SimpleString_create (append); Collection_addItem (me, item.transfer()); return 1; } catch (MelderError) { Melder_throw (me, ": text not appended."); } } OrderedOfString OrderedOfString_joinItems (I, thou) { iam (OrderedOfString); thouart (OrderedOfString); try { if (my size != thy size) { Melder_throw ("sizes must be equal."); } autoOrderedOfString him = Data_copy (me); for (long i = 1; i <= my size; i++) { SimpleString_append ( (SimpleString) his item[i], (SimpleString) thy item[i]); } return him.transfer(); } catch (MelderError) { Melder_throw ("Items not joinmed."); } } OrderedOfString OrderedOfString_selectUniqueItems (I, int sort) { iam (OrderedOfString); try { if (! sort) { autoOrderedOfString him = OrderedOfString_create (); for (long i = 1; i <= my size; i++) { SimpleString ss = (SimpleString) my item[i]; if (! OrderedOfString_indexOfItem_c (him.peek(), ss -> string)) { autoSimpleString item = Data_copy (ss); Collection_addItem (him.peek(), item.transfer()); } } Collection_shrinkToFit (him.peek()); return him.transfer(); } autoSortedSetOfString thee = SortedSetOfString_create (); /* Collection_to_SortedSet (I, int (*compare)(I, thou)) */ for (long i = 1; i <= my size; i++) { if (! thy hasItem (my item[i])) { autoSimpleString item = Data_copy ( (SimpleString) my item[i]); Collection_addItem (thee.peek(), item.transfer()); } } autoOrderedOfString him = OrderedOfString_create (); for (long i = 1; i <= thy size; i++) { autoSimpleString item = Data_copy ( (SimpleString) thy item[i]); Collection_addItem (him.peek(), item.transfer()); } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": unique items not selected."); } } void OrderedOfString_frequency (I, thou, long *count) { iam (OrderedOfString); thouart (OrderedOfString); for (long i = 1; i <= my size; i++) { for (long j = 1; j <= thy size; j++) { if (Data_equal ( (Data) my item[i], (Data) thy item[j])) { count[j]++; break; } } } } long OrderedOfString_getNumberOfDifferences (I, thou) { iam (OrderedOfString); thouart (OrderedOfString); long numberOfDifferences = 0; if (my size != thy size) { return -1; } for (long i = 1; i <= my size; i++) { if (! Data_equal ( (SimpleString) my item[i], (SimpleString) thy item[i])) { numberOfDifferences++; } } return numberOfDifferences; } double OrderedOfString_getFractionDifferent (I, thou) { iam (OrderedOfString); thouart (OrderedOfString); long numberOfDifferences = OrderedOfString_getNumberOfDifferences (me, thee); if (numberOfDifferences < 0) { return NUMundefined; } return my size == 0 ? 0 : (0.0 + numberOfDifferences) / my size; } int OrderedOfString_difference (I, thou, long *ndif, double *fraction) { iam (OrderedOfString); thouart (OrderedOfString); *ndif = 0; *fraction = 1; if (my size != thy size) { Melder_flushError ("OrderedOfString_difference: the number of items differ"); return 0; } for (long i = 1; i <= my size; i++) { if (! Data_equal ( (SimpleString) my item[i], (SimpleString) thy item[i])) { (*ndif) ++; } } *fraction = *ndif; *fraction /= my size; return 1; } long OrderedOfString_indexOfItem_c (I, const wchar_t *str) { iam (OrderedOfString); long index = 0; autoSimpleString s = SimpleString_create (str); for (long i = 1; i <= my size; i++) { if (Data_equal ( (Data) my item[i], s.peek())) { index = i; break; } } return index; } const wchar_t *OrderedOfString_itemAtIndex_c (I, long index) { iam (OrderedOfString); return index > 0 && index <= my size ? SimpleString_c ( (SimpleString) my item[index]) : NULL; } void OrderedOfString_sequentialNumbers (I, long n) { iam (OrderedOfString); Collection_removeAllItems (me); for (long i = 1; i <= n; i++) { wchar_t s[20]; swprintf (s, 20, L"%ld", i); autoSimpleString str = SimpleString_create (s); Collection_addItem (me, str.transfer()); } } void OrderedOfString_changeStrings (OrderedOfString me, wchar_t *search, wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp) { regexp *compiled_search = NULL; try { const wchar_t *compileMsg; wchar_t *r; if (search == NULL) { Melder_throw ("Missing search string."); } if (replace == NULL) { Melder_throw ("Missing replace string."); } if (use_regexp) { compiled_search = CompileRE ( (regularExp_CHAR *) search, &compileMsg, 0); if (compiled_search == NULL) { Melder_throw (compileMsg); } } for (long i = 1; i <= my size; i++) { SimpleString ss = (SimpleString) my item[i]; long nmatches_sub; if (use_regexp) { r = str_replace_regexp (ss -> string, compiled_search, replace, maximumNumberOfReplaces, &nmatches_sub); } else r = str_replace_literal (ss -> string, search, replace, maximumNumberOfReplaces, &nmatches_sub); // Change without error: Melder_free (ss -> string); ss -> string = r; if (nmatches_sub > 0) { *nmatches += nmatches_sub; (*nstringmatches) ++; } } if (use_regexp) { free (compiled_search); } } catch (MelderError) { if (use_regexp) { free (compiled_search); } Melder_throw ("Replace not completed."); } } long OrderedOfString_isSubsetOf (I, thou, long *translation) { // ?? test and give number iam (OrderedOfString); thouart (OrderedOfString); long nStrings = 0; for (long i = 1; i <= my size; i++) { if (translation) { translation[i] = 0; } for (long j = 1; j <= thy size; j++) if (Data_equal ( (SimpleString) my item[i], (SimpleString) thy item[j])) { if (translation) { translation[i] = j; } nStrings++; break; } } return nStrings; } void OrderedOfString_drawItem (I, Graphics g, long index, double xWC, double yWC) { iam (OrderedOfString); if (index > 0 && index <= my size) { SimpleString_draw ( (SimpleString) my item[index], g, xWC, yWC); } } long OrderedOfString_getSize (I) { iam (OrderedOfString); return my size; } void OrderedOfString_removeOccurrences (I, const wchar_t *search, int use_regexp) { iam (OrderedOfString); if (search == NULL) { return; } for (long i = my size; i >= 1; i--) { SimpleString ss = (SimpleString) my item[i]; if ( (use_regexp && strstr_regexp (ss -> string, search)) || (!use_regexp && wcsstr (ss -> string, search))) { Collection_removeItem (me, i); } } } /* End of file Collection_extensions.c */ sources_5316/dwsys/Permutation_and_Index.h0000644000176700017670000000214311607123041017520 0ustar paulpaul#ifndef _Permutation_and_Index_h_ #define _Permutation_and_Index_h_ /* Permutation_and_Index.h * * Copyright (C) 2005-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * djmw 20110307 Latest modification */ #include "Permutation.h" #include "Index.h" #ifdef __cplusplus extern "C" { #endif Permutation Index_to_Permutation_permuteRandomly (I, int permuteWithinClass); #ifdef __cplusplus } #endif #endif /* _Permutation_and_Index_h_ */ sources_5316/dwsys/Simple_extensions.cpp0000644000176700017670000000534411627164673017333 0ustar paulpaul/* Simple_extensions.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw & pb wchar_t */ #include "Simple_extensions.h" #include "longchar.h" void SimpleString_init (SimpleString me, const wchar_t *string) { my string = Melder_wcsdup (string); } int SimpleString_compare (SimpleString me, SimpleString thee) { return wcscmp (my string, thy string); } const wchar_t *SimpleString_c (SimpleString me) { return my string; } void SimpleString_append (SimpleString me, SimpleString thee) { SimpleString_append_c (me, thy string); } void SimpleString_append_c (SimpleString me, const wchar_t *str) { if (str == 0) { return; } long myLength = wcslen (my string); my string = (wchar_t *) Melder_realloc (my string, (myLength + wcslen (str) + 1) * sizeof (wchar_t)); wcscpy (& my string[myLength], str); } SimpleString SimpleString_concat (SimpleString me, SimpleString thee) { autoSimpleString him = Data_copy (me); SimpleString_append_c (him.peek(), thy string); return him.transfer(); } SimpleString SimpleString_concat_c (SimpleString me, const wchar_t *str) { autoSimpleString him = Data_copy (me); SimpleString_append_c (him.peek(), str); return him.transfer(); } void SimpleString_replace_c (SimpleString me, const wchar_t *str) { wchar_t *ptr = Melder_wcsdup (str); Melder_free (my string); my string = ptr; } long SimpleString_length (SimpleString me) { return wcslen (my string); } void SimpleString_draw (SimpleString me, Graphics g, double xWC, double yWC) { Graphics_text (g, xWC, yWC, my string); } const wchar_t *SimpleString_nativize_c (SimpleString me, int educateQuotes) { autoSimpleString thee = Data_copy (me); Longchar_nativizeW (thy string, my string, educateQuotes); return my string; } const wchar_t *SimpleString_genericize_c (SimpleString me) { autoSimpleString thee = Data_copy (me); my string = (wchar_t *) Melder_realloc (my string, (3 * wcslen (my string) + 1) * sizeof (wchar_t)); Longchar_genericizeW (thy string, my string); return my string; } /* End of file Simple_extensions.cpp */ sources_5316/dwsys/Permutation_def.h0000644000176700017670000000205411627164413016400 0ustar paulpaul/* Permutation_def.h * * Copyright (C) 2005-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Permutation oo_DEFINE_CLASS (Permutation, Data) oo_LONG (numberOfElements) oo_LONG_VECTOR (p, numberOfElements) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS(Permutation) #undef ooSTRUCT /* End of file Permutation_def.h */ sources_5316/dwsys/regularExp.h0000644000176700017670000001446411631104425015371 0ustar paulpaul#ifndef _regularExp_h_ #define _regularExp_h_ /******************************************************************************* * * * regularExp.h -- Nirvana Editor Regular Expression Package Header File * * * * Copyright 2002 The NEdit Developers * * * * This is free software; you can redistribute it and/or modify it under the * * terms of the GNU General Public License as published by the Free Software * * Foundation; either version 2 of the License, or (at your option) any later * * version. In addition, you may distribute version of this program linked to * * Motif or Open Motif. See README for details. * * * * This software is distributed in the hope that it will be useful, but WITHOUT * * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License * * for more details. * * * * You should have received a copy of the GNU General Public License along with * * software; if not, write to the Free Software Foundation, Inc., 59 Temple * * Place, Suite 330, Boston, MA 02111-1307 USA * * * * Nirvana Text Editor * * July 31, 2001 * * * * * *******************************************************************************/ /* djmw 20080110 Extra parameter for SubstituteRE to allow error differentiation */ /* Number of text capturing parentheses allowed. */ #include #if defined (macintosh) || defined (linux) #define regularExp_CHAR wchar_t #else #define regularExp_CHAR unsigned short #endif #define NSUBEXP 50 /* Structure to contain the compiled form of a regular expression plus pointers to matched text. `program' is the actual compiled regex code. */ #ifdef __cplusplus extern "C" { #endif typedef struct regexp { regularExp_CHAR *startp [NSUBEXP]; /* Captured text starting locations. */ regularExp_CHAR *endp [NSUBEXP]; /* Captured text ending locations. */ regularExp_CHAR *extentpBW; /* Points to the maximum extent of text scanned by ExecRE in front of the string to achieve a match (needed because of positive look-behind.) */ regularExp_CHAR *extentpFW; /* Points to the maximum extent of text scanned by ExecRE to achieve a match (needed because of positive look-ahead.) */ int top_branch; /* Zero-based index of the top branch that matches. Used by syntax highlighting only. */ regularExp_CHAR match_start; /* Internal use only. */ regularExp_CHAR anchor; /* Internal use only. */ regularExp_CHAR program [1]; /* Unwarranted chumminess with compiler. */ } regexp; /* Flags for CompileRE default settings (Markus Schwarzenberg) */ typedef enum { REDFLT_STANDARD = 0, REDFLT_CASE_INSENSITIVE = 1 /* REDFLT_MATCH_NEWLINE = 2 Currently not used. */ } RE_DEFAULT_FLAG; /* Compiles a regular expression into the internal format used by `ExecRE'. */ regexp * CompileRE ( const regularExp_CHAR *exp, /* String containing the regex specification. */ const wchar_t **errorText, /* Text of any error message produced. */ int defaultFlags); /* Flags for default RE-operation */ /* Match a `regexp' structure against a string. */ int ExecRE ( regexp *prog, /* Compiled regex. */ regexp *cross_regex_backref, /* Pointer to a `regexp' that was used in a previous execution of ExecRE. Used to implement back references across regular expressions for use in syntax highlighting.*/ const regularExp_CHAR *string, /* Text to search within. */ const regularExp_CHAR *end, /* Pointer to the end of `string'. If NULL will scan from `string' until '\0' is found. */ int reverse, /* Backward search. */ regularExp_CHAR prev_char, /* Character immediately prior to `string'. Set to '\n' or '\0' if true beginning of text. */ regularExp_CHAR succ_char, /* Character immediately after `end'. Set to '\n' or '\0' if true beginning of text. */ const regularExp_CHAR *delimiters, /* Word delimiters to use (NULL for default) */ const regularExp_CHAR *look_behind_to,/* Boundary for look-behind; defaults to "string" if NULL */ const regularExp_CHAR *match_till); /* Boundary to where match can extend. \0 is assumed to be the boundary if not set. Lookahead can cross the boundary. */ /* Perform substitutions after a `regexp' match. */ int SubstituteRE ( const regexp *prog, const regularExp_CHAR *source, regularExp_CHAR *dest, int max, int *errorType); // djmw 20080110 0: ok; 1: is not enough memory /* Builds a default delimiter table that persists across `ExecRE' calls that is identical to `delimiters'. Pass NULL for "default default" set of delimiters. */ void SetREDefaultWordDelimiters ( regularExp_CHAR *delimiters); /* Enable (or disable) brace counting quantifiers, e.g. `(foo){0,3}'. */ void EnableCountingQuantifier (int is_enabled); #ifdef __cplusplus } #endif #endif /* _regularExp_h_ */ sources_5316/dwsys/NUMlapack.cpp0000644000176700017670000011036611627164153015430 0ustar paulpaul/* NUMlapack.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020812 GPL header djmw 20030205 Latest modification (NUMmacros) djmw 20071022 NUMmatricesToUpperTriangularForms now inializes l=0 */ #include "NUM.h" #include "NUMlapack.h" #include "NUMmachar.h" #include "melder.h" #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) #define SIGN(x,s) ((s) < 0 ? -fabs (x) : fabs(x)) #define TOVEC(x) (&(x) - 1) void NUMidentity (double **a, long rb, long re, long cb) { for (long i = rb; i <= re; i++) { for (long j = cb; j <= cb + (re - rb); j++) { a[i][j] = 0; } a[i][i] = 1; } } double NUMpythagoras (double a, double b) { double absa = fabs (a), absb = fabs (b); double w = MAX (absa, absb); double z = MIN (absa, absb); if (z == 0) { return w; } double t = z / w; return w * sqrt (1 + t * t); } double NUMnorm2 (long n, double *x, long incx) { if (n < 1 || incx < 1) { return 0; } if (n == 1) { return fabs (x[1]); } double scale = 0, ssq = 1; for (long i = 1; i <= 1 + (n - 1) * incx; i += incx) { if (x[i] != 0) { double absxi = fabs (x[i]); if (scale < absxi) { double tmp = scale / absxi; ssq = 1 + ssq * tmp * tmp; scale = absxi; } else { double tmp = absxi / scale; ssq += tmp * tmp; } } } return scale * sqrt (ssq); } double NUMfrobeniusnorm (long m, long n, double **x) { if (n < 1 || m < 1) { return 0; } double scale = 0, ssq = 1; for (long i = 1; i <= m; i++) { for (long j = 1; j <= n; j++) { if (x[i][j] != 0) { double absxi = fabs (x[i][j]); if (scale < absxi) { double t = scale / absxi; ssq = 1 + ssq * t * t; scale = absxi; } else { double t = absxi / scale; ssq += t * t; } } } } return scale * sqrt (ssq); } double NUMdotproduct (long n, double x[], long incx, double y[], long incy) { long ix = 1, iy = 1; if (n <= 0) { return 0; } if (incx < 0) { ix = (-n + 1) * incx + 1; } if (incy < 0) { iy = (-n + 1) * incy + 1; } double dot = 0; for (long i = 1; i <= n; i++, ix += incx, iy += incy) { dot += x[ix] * y[iy]; } return dot; } void NUMdaxpy (long n, double da, double x[], long incx, double y[], long incy) { long ix = 1, iy = 1; if (n <= 0) { return; } if (incx < 0) { ix = (-n + 1) * incx + 1; } if (incy < 0) { iy = (-n + 1) * incy + 1; } for (long i = 1; i <= n; i++, ix += incx, iy += incy) { y[iy] += da * x[ix]; } } void NUMvector_scale (long n, double da, double dx[], long incx) { if (n < 1 || incx < 1) { return; } for (long i = 1; i <= n * incx; i += incx) { dx[i] *= da; } } void NUMcopyElements (long n, double x[], long incx, double y[], long incy) { if (n <= 0) { return; } if (incx == 1 && incy == 1) { for (long i = 1; i <= n; i++) { y[i] = x[i]; } } else { long ix = 1, iy = 1; if (incx < 0) { ix = (-n + 1) * incx + 1; } if (incy < 0) { iy = (-n + 1) * incy + 1; } for (long i = 1; i <= n; i++, ix += incx, iy += incy) { y[iy] = x[ix]; } } } void NUMplaneRotation (long n, double x[], long incx, double y[], long incy, double c, double s) { if (n < 1) { return; } if (incx == 1 && incy == 1) { for (long i = 1; i <= n; i++) { double xt = c * x[i] + s * y[i]; y[i] = c * y[i] - s * x[i]; x[i] = xt; } } else { long ix = 1, iy = 1; if (incx < 0) { ix = (-n + 1) * incx + 1; } if (incy < 0) { iy = (-n + 1) * incy + 1; } for (long i = 1; i <= n; i++, ix += incx, iy += incy) { double xt = c * x[ix] + s * y[iy]; y[iy] = c * y[iy] - s * x[ix]; x[ix] = xt; } } } void NUMpermuteColumns (int forward, long m, long n, double **x, long *perm) { if (n <= 1) { return; } for (long i = 1; i <= n; i++) { perm[i] = - perm[i]; } if (forward) { for (long i = 1; i <= n; i++) { if (perm[i] > 0) { continue; } long j = i; perm[j] = -perm[j]; long in = perm[j]; for (;;) { if (perm[in] > 0) { break; } for (long ii = 1; ii <= m; ii++) { double tmp = x[ii][j]; x[ii][j] = x[ii][in]; x[ii][in] = tmp; } perm[in] = -perm[in]; j = in; in = perm[in]; } } } else { for (long i = 1; i <= n; i++) { if (perm[i] > 0) { continue; } long j = perm[i] = - perm[i]; for (;;) { if (j == i) { break; } for (long ii = 1; ii <= m; ii++) { double tmp = x[ii][i]; x[ii][i] = x[ii][j]; x[ii][j] = tmp; } perm[j] = -perm[j]; j = perm[j]; } } } } void NUMfindHouseholder (long n, double *alpha, double x[], long incx, double *tau) { double xnorm; if (n < 2 || (xnorm = NUMnorm2 (n - 1, x, incx)) == 0) { *tau = 0; return; } double beta = NUMpythagoras (*alpha, xnorm); if (*alpha > 0) { beta = - beta; } if (! NUMfpp) { NUMmachar (); } double safmin = NUMfpp -> sfmin / NUMfpp -> eps; if (fabs (beta) >= safmin) { *tau = (beta - *alpha) / beta; NUMvector_scale (n - 1, 1 / (*alpha - beta), x, incx); *alpha = beta; } else { // xnorm, beta may be inaccurate; scale x and recompute them double rsafmn = 1 / safmin; long knt = 0; do { knt++; NUMvector_scale (n - 1, rsafmn, x, incx); beta *= rsafmn; *alpha *= rsafmn; } while (fabs (beta) < safmin); /* New beta is at most 1, at least safmin */ xnorm = NUMnorm2 (n - 1, x, incx); beta = NUMpythagoras (*alpha, xnorm); if (*alpha > 0) { beta = - beta; } *tau = (beta - *alpha) / beta; NUMvector_scale (n - 1, 1 / (*alpha - beta), x, incx); /* If alpha is subnormal, it may lose relative accuracy */ *alpha = beta; for (long i = 1; i <= knt; i++) { *alpha *= safmin; } } } void NUMfindGivens (double f, double g, double *cs, double *sn, double *r) { long count; if (! NUMfpp) { NUMmachar (); } double safmn2 = pow (NUMfpp -> base, (long) (log (NUMfpp -> sfmin / NUMfpp -> eps) / log (NUMfpp -> base) / 2.)); double safmx2 = 1 / safmn2; if (g == 0) { *cs = 1; *sn = 0; *r = f; return; } if (f == 0) { *cs = 0; *sn = 1; *r = g; return; } double f1 = f, g1 = g; double scale = MAX (fabs (f1), fabs (g1)); if (scale >= safmx2) { count = 0; do { count++; f1 *= safmn2; g1 *= safmn2; scale = MAX (fabs (f1), fabs (g1)); } while (scale >= safmx2); *r = sqrt (f1 * f1 + g1 * g1); *cs = f1 / *r; *sn = g1 / *r; for (long i = 1; i <= count; i++) { *r *= safmx2; } } else if (scale <= safmn2) { count = 0; do { count++; f1 *= safmx2; g1 *= safmx2; scale = MAX (fabs (f1), fabs (g1)); } while (scale <= safmn2); *r = sqrt (f1 * f1 + g1 * g1); *cs = f1 / *r; *sn = g1 / *r; for (long i = 1; i <= count; i++) { *r *= safmn2; } } else { *r = sqrt (f1 * f1 + g1 * g1); *cs = f1 / *r; *sn = g1 / *r; } if (fabs (f) > fabs (g) && *cs < 0) { *cs = -*cs; *sn = -*sn; *r = -*r; } } void NUMapplyFactoredHouseholder (double **c, long rb, long re, long cb, long ce, double v[], long incv, double tau, int side) { long i, j, iv; double sum; Melder_assert ( (re - rb) >= 0 && (ce - cb) >= 0 && incv != 0); if (tau == 0) { return; } if (side == NUM_LEFT) { /* Form Q * C: 1. w := C' * v 2. C := C - v * w' */ for (j = cb; j <= ce; j++) { for (sum = 0, iv = 1, i = rb; i <= re; i++, iv += incv) { sum += c[i][j] * v[iv]; } sum *= tau; for (iv = 1, i = rb; i <= re; i++, iv += incv) { c[i][j] -= v[iv] * sum; } } } else { /* side == NUM_RIGHT */ /* Form C * Q 1. w := C * v 2. C := C - w * v' */ for (i = rb; i <= re; i++) { for (sum = 0, iv = 1, j = cb; j <= ce; j++, iv += incv) { sum += c[i][j] * v[iv]; } sum *= tau; for (iv = 1, j = cb; j <= ce; j++, iv += incv) { c[i][j] -= sum * v[iv]; } } } } void NUMapplyFactoredHouseholders (double **c, long rb, long re, long cb, long ce, double **v, long rbv, long rev, long cbv, long cev, long incv, double tau[], int side, int trans) { int left = side == NUM_LEFT, transpose = trans != NUM_NOTRANSPOSE; long mv = rev - rbv + 1, nv = cev - cbv + 1; long i_begin, i_end, i_inc, numberOfHouseholders, order_v; long m = re - rb + 1, n = ce - cb + 1; long rbc = rb, rec = re, cbc = cb, cec = ce; if (incv != 1) { /* by column (QR) */ numberOfHouseholders = mv > nv ? nv : mv - 1; order_v = mv; } else { /* by row (RQ) */ numberOfHouseholders = nv > mv ? mv : nv - 1; order_v = nv; } Melder_assert (m > 0 && n > 0 && mv > 0 && nv > 0); Melder_assert (numberOfHouseholders <= MAX (m, n)); Melder_assert ( (left && m == order_v) || (! left && n == order_v)); if ( (left && ! transpose) || (! left && transpose)) { i_begin = numberOfHouseholders; i_end = 0; i_inc = -1; } else { i_begin = 1; i_end = numberOfHouseholders + 1; i_inc = 1; } long i = i_begin; while (i != i_end) { double save, *v1; long vr, vc; if (incv == 1) { vr = rev - i + 1; vc = cev - i + 1; if (left) { rec = re - i + 1; } else { cec = ce - i + 1; } v1 = v[vr]; } else { vr = rbv + i - 1; vc = cbv + i - 1; if (left) { rbc = rb + i - 1; } else { cbc = cb + i - 1; } v1 = TOVEC (v[vr][vc]); } save = v[vr][vc]; v[vr][vc] = 1; NUMapplyFactoredHouseholder (c, rbc, rec, cbc, cec, v1, incv, tau[i], side); v[vr][vc] = save; i += i_inc; } } void NUMhouseholderQR (double **a, long rb, long re, long cb, long ce, long lda, double tau[]) { long m = re - rb + 1, n = ce - cb + 1; long numberOfHouseholders = MIN (m, n); Melder_assert (numberOfHouseholders > 0); if (numberOfHouseholders == m) { tau[m] = 0; numberOfHouseholders--; } for (long i = 1; i <= numberOfHouseholders; i++) { long ri = rb + i - 1, ci = cb + i - 1; // Generate elementary reflector H(i) to annihilate "A(i+1:m,i)" NUMfindHouseholder (m - i + 1, &a[ri][ci], TOVEC (a[ri + 1][ci]), lda, &tau[i]); if (i < n) { // Apply H(i) to "A(i:m, i+1:n)" from the left double save = a[ri][ci]; a[ri][ci] = 1; NUMapplyFactoredHouseholder (a, ri, re, cb + i, ce, TOVEC (a[ri][ci]), lda, tau[i], NUM_LEFT); a[ri][ci] = save; } } } void NUMhouseholderQRwithColumnPivoting (long m, long n, double **a, long lda, long pivot[], double tau[]) { long numberOfHouseholders = MIN (m, n); Melder_assert (numberOfHouseholders > 0); if (! pivot) { NUMhouseholderQR (a, 1, m, 1, n, lda, tau); return; } if (numberOfHouseholders == m) { tau[m] = 0; numberOfHouseholders--; } autoNUMvector colnorm (1, 2 * n); long itmp = 1; for (long i = 1; i <= n; i++) { if (pivot[i] != 0) { if (i != itmp) { for (long j = 1; j <= m; j++) { double tmp = a[j][i]; a[j][i] = a[j][itmp]; a[j][itmp] = tmp; } pivot[i] = pivot[itmp]; pivot[itmp] = i; } else { pivot[i] = i; } itmp++; } else { pivot[i] = i; } } itmp--; // Compute the QR factorization and update remaining columns if (itmp > 0) { long ma = MIN (itmp, m); NUMhouseholderQR (a, 1, m, 1, ma, lda, tau); if (ma < n) NUMapplyFactoredHouseholders (a, 1, m, ma + 1, n, a, 1, m, 1, ma, lda, tau, NUM_LEFT, NUM_TRANSPOSE); } if (itmp >= numberOfHouseholders) { return; // goto end; } // Initialize partial column norms. the first n elements of // colnorm store the exact column norms. for (long i = itmp + 1; i <= n; i++) { colnorm[n + i] = colnorm[i] = NUMnorm2 (m - itmp, TOVEC (a[itmp + 1][i]), lda); } // Compute factorization for (long i = itmp + 1; i <= numberOfHouseholders; i++) { // Determine ith pivot column and swap if necessary double max = colnorm[i]; long pvt = i; for (long j = i + 1; j <= n; j++) { if (fabs (colnorm[j]) > max) { max = fabs (colnorm[j]); pvt = j; } } if (pvt != i) { for (long j = 1; j <= m; j++) { double tmp = a[j][i]; a[j][i] = a[j][pvt]; a[j][pvt] = tmp; } itmp = pivot[pvt]; pivot[pvt] = pivot[i]; pivot[i] = itmp; colnorm[pvt] = colnorm[i]; colnorm[n + pvt] = colnorm[n + i]; } // Generate elementary reflector H(i) NUMfindHouseholder (m - i + 1, &a[i][i], TOVEC (a[i + 1][i]), lda, &tau[i]); if (i < n) { // Apply H(i) to A(i:m,i+1:n) from the left double save = a[i][i]; a[i][i] = 1; NUMapplyFactoredHouseholder (a, i, m, i + 1, n, TOVEC (a[i][i]), lda, tau[i], NUM_LEFT); a[i][i] = save; } // Update partial column norms. for (long j = i + 1; j <= n; j++) { if (colnorm[j] == 0) { continue; } double t = a[i][j] / colnorm[j]; double tmp = 1 - t * t; if (tmp < 0) { tmp = 0; } t = colnorm[j] / colnorm[n + j]; if ( (1 + 0.05 * tmp * t * t) == 1) { if (m - i > 0) { colnorm[n + j] = colnorm[j] = NUMnorm2 (m - i, TOVEC (a[i + 1][j]), lda); } else { colnorm[j] = colnorm[n + j] = 0; } } else { colnorm[j] *= sqrt (tmp); } } } } void NUMhouseholderRQ (double **a, long rb, long re, long cb, long ce, double tau[]) { long m = re - rb + 1, n = ce - cb + 1; long numberOfHouseholders = MIN (m, n); Melder_assert (numberOfHouseholders > 0); if (numberOfHouseholders == n) { tau[n] = 0; numberOfHouseholders--; } for (long i = 1; i <= numberOfHouseholders; i++) { // Generate elementary reflector H(i) to annihilate "A(m-i+1,1:n-i)" long ri = re - i + 1, ci = ce - i + 1, order = n - i + 1; NUMfindHouseholder (order, &a[ri][ci], a[ri], 1, &tau[i]); if (i < m) { // Apply H(i) to "A(1:m-i,1:n-i+1)" from the right double save = a[ri][ci]; a[ri][ci] = 1; NUMapplyFactoredHouseholder (a, rb, re - i, cb, ci, a[ri], 1, tau[i], NUM_RIGHT); a[ri][ci] = save; } } } void NUMparallelVectors (long n, double x[], long incx, double y[], long incy, double *svmin) { double a11, c, svmax, tau; if (n <= 1) { *svmin = 0; return; } // Compute the QR factorization of the n-by-2 matrix ( x y ) NUMfindHouseholder (n, &x[1], TOVEC (x[1 + incx]), incx, &tau); a11 = x[1]; x[1] = 1; c = - tau * NUMdotproduct (n, x, incx, y, incy); NUMdaxpy (n, c, x, incx, y, incy); NUMfindHouseholder (n - 1, &y[1 + incy], TOVEC (y[1 + 2 * incy]), incy, &tau); // Compute the svd of 2-by-2 upper triangular matrix. NUMsvcmp22 (a11, y[1], y[1 + incy], svmin, &svmax); } void NUMsvdcmp22 (double f, double g, double h, double *svmin, double *svmax, double *snr, double *csr, double *snl, double *csl) { double a, clt, crt, slt, srt, tsign; double ft = f, fa = fabs (f); double ht = h, ha = fabs (h); double gt = g, ga = fabs (g); long pmax = 1; // pmax: maximum absolute entry of matrix (f=1, g=2, h=3). bool swap = ha > fa; if (swap) { double tmp = ft; ft = ht; ht = tmp; tmp = fa; fa = ha; ha = tmp; pmax = 3; } if (ga == 0) { // diagonal matrix *svmin = ha; *svmax = fa; clt = crt = 1; slt = srt = 0; } else { int gasmal = 1; if (ga > fa) { pmax = 2; if (! NUMfpp) { NUMmachar (); } if (fa / ga <= NUMfpp -> eps) { /* very large ga */ gasmal = 0; *svmax = ga; *svmin = ha > 1 ? fa / (ga / ha) : (fa / ga) * ha; clt = 1; slt = ht / gt; srt = 1; crt = ft / gt; } } if (gasmal) { // normal case double m, mm, l, t, tt, r, s, d = fa - ha; l = d == fa ? 1 : d / fa; /* copes with infinite f or h. */ m = gt / ft; mm = m * m; t = 2 - l; tt = t * t; s = sqrt (tt + mm); r = l == 0 ? fabs (m) : sqrt (l * l + mm); a = 0.5 * (s + r); *svmin = ha / a; *svmax = fa * a; t = mm == 0 ? (l == 0 ? SIGN (2, ft) * SIGN (1, gt) : gt / SIGN (d, ft) + m / t) : (m / (s + t) + m / (r + l)) * (1 + a); l = sqrt (t * t + 4); crt = 2 / l; srt = t / l; clt = (crt + srt * m) / a; slt = (ht / ft) * srt / a; } } if (swap) { *csl = srt; *snl = crt; *csr = slt; *snr = clt; } else { *csl = clt; *snl = slt; *csr = crt; *snr = srt; } // Correct the signs of svmin and svmax if (pmax == 1) { tsign = SIGN (1, *csr) * SIGN (1, *csl) * SIGN (1, f); } else if (pmax == 2) { tsign = SIGN (1, *snr) * SIGN (1, *csl) * SIGN (1, g); } else { /* pmax == 3 */ tsign = SIGN (1, *snr) * SIGN (1, *snl) * SIGN (1, h); } *svmax = SIGN (*svmax, tsign); *svmin = SIGN (*svmin, tsign * SIGN (1, f) * SIGN (1, h)); } /* Bai & Demmel, page 1472 */ void NUMgsvdcmp22 (int upper, int productsvd, double a1, double a2, double a3, double b1, double b2, double b3, double *csu, double *snu, double *csv, double *snv, double *csq, double *snq) { double a, aua11, aua12, aua21, aua22, avb12, avb11; double avb21, avb22, b, c, csl, csr, d, g, r, s1, s2; double snl, snr, ua11, ua11r, ua12, ua21, ua22; double ua22r, vb11, vb11r, vb12, vb21, vb22, vb22r; if (upper) { // Input matrices A and B are upper triangular matrices // Form matrix C = A * adj(B) = ( a b ) // ( 0 d ) if (productsvd) { /* This is to simplistic, will not work. Form: C = A.B: a = a1 * b1; d = a3 * b3; b = a1 * b2 + a2 * b3; Form C = B.A */ a = a1 * b1; d = a3 * b3; b = a2 * b2 + a3 * b2; } else { a = a1 * b3; d = a3 * b1; b = a2 * b1 - a1 * b2; } /* the svd of real 2-by-2 triangular C ( csl -snl )*( a b )*( csr snr ) = ( r 0 ) ( snl csl ) ( 0 d ) ( -snr csr ) ( 0 t ) */ NUMsvdcmp22 (a, b, d, &s1, &s2, &snr, &csr, &snl, &csl); if (fabs (csl) >= fabs (snl) || fabs (csr) >= fabs (snr)) { // Compute the (1,1) and (1,2) elements of U' * A and V' * B, // and (1,2) element of |U|' * |A| and |V|' * |B|. ua11r = csl * a1; ua12 = csl * a2 + snl * a3; vb11r = csr * b1; vb12 = csr * b2 + snr * b3; aua12 = fabs (csl) * fabs (a2) + fabs (snl) * fabs (a3); avb12 = fabs (csr) * fabs (b2) + fabs (snr) * fabs (b3); g = fabs (ua11r) + fabs (ua12); // Zero (1,2) elements of U'*A and V' * B if (g != 0 && aua12 / g <= avb12 / (fabs (vb11r) + fabs (vb12))) { NUMfindGivens (-ua11r, ua12, csq, snq, &r); } else { NUMfindGivens (-vb11r, vb12, csq, snq, &r); } *csu = csl; *snu = -snl; *csv = csr; *snv = -snr; } else { /* Compute the (2,1) and (2,2) elements of U' * A and V' * B, and (2,2) element of |U|' * |A| and |V|' * |B|. */ ua21 = -snl * a1; ua22 = -snl * a2 + csl * a3; vb21 = -snr * b1; vb22 = -snr * b2 + csr * b3; aua22 = fabs (snl) * fabs (a2) + fabs (csl) * fabs (a3); avb22 = fabs (snr) * fabs (b2) + fabs (csr) * fabs (b3); g = fabs (ua21) + fabs (ua22); // Zero (2,2) elements of U' * A and V' * B, and then swap. if (g != 0 && aua22 / g <= avb22 / (fabs (vb21) + fabs (vb22))) { NUMfindGivens (-ua21, ua22, csq, snq, &r); } else { NUMfindGivens (-vb21, vb22, csq, snq, &r); } *csu = snl; *snu = csl; *csv = snr; *snv = csr; } } else { // Input matrices A and B are lower triangular matrices // Form matrix C = A * adj(B) = ( a 0 ) // ( c d ) if (productsvd) { a = a1 * b1; d = a3 * b3; c = a2 * b1 + a3 * b2; } else { a = a1 * b3; d = a3 * b1; c = a2 * b3 - a3 * b2; } // The svd of real 2-by-2 triangular C // ( csl -snl ) * ( a 0 ) * ( csr snr ) = ( r 0 ) // ( snl csl ) ( c d ) ( -snr csr ) ( 0 t ) NUMsvdcmp22 (a, c, d, &s1, &s2, &snr, &csr, &snl, &csl); if (fabs (csr) >= fabs (snr) || fabs (csl) >= fabs (snl)) { // Compute the (2,1) and (2,2) elements of U' * A and V' * B, // and (2,1) element of |U|' * |A| and |V|' * |B|. ua21 = -snr * a1 + csr * a2; ua22r = csr * a3; vb21 = -snl * b1 + csl * b2; vb22r = csl * b3; aua21 = fabs (snr) * fabs (a1) + fabs (csr) * fabs (a2); avb21 = fabs (snl) * fabs (b1) + fabs (csl) * fabs (b2); g = fabs (ua21) + fabs (ua22r); // Zero (2,1) elements of U' * A and V' * B. if (g != 0 && aua21 / g <= avb21 / (fabs (vb21) + fabs (vb22r))) { NUMfindGivens (ua22r, ua21, csq, snq, &r); } else { NUMfindGivens (vb22r, vb21, csq, snq, &r); } *csu = csr; *snu = -snr; *csv = csl; *snv = -snl; } else { // Compute the (1,1) and (1,2) elements of U' * A and V' * B, // and (1,1) element of |U|' * |A| and |V|' * |B|. ua11 = csr * a1 + snr * a2; ua12 = snr * a3; vb11 = csl * b1 + snl * b2; vb12 = snl * b3; aua11 = fabs (csr) * fabs (a1) + fabs (snr) * fabs (a2); avb11 = fabs (csl) * fabs (b1) + fabs (snl) * fabs (b2); g = fabs (ua11) + fabs (ua12); // Zero (1,1) elements of U' * A and V' * B, and then swap. if (g != 0 && aua11 / g <= avb11 / (fabs (vb11) + fabs (vb12))) { NUMfindGivens (ua12, ua11, csq, snq, &r); } else { NUMfindGivens (vb12, vb11, csq, snq, &r); } *csu = snr; *snu = csr; *csv = snl; *snv = csl; } } } void NUMsvcmp22 (double f, double g, double h, double *svmin, double *svmax) { double as, at, au, c; double fa = fabs (f), ga = fabs (g), ha = fabs (h); double fhmn = MIN (fa, ha), fhmx = MAX (fa, ha); if (fhmn == 0) { *svmin = 0; if (fhmx == 0) { *svmax = ga; } else { double tmp = MIN (fhmx, ga) / MAX (fhmx, ga); *svmax = MAX (fhmx, ga) * sqrt (1 + tmp * tmp); } } else { if (ga < fhmx) { as = 1 + fhmn / fhmx; at = (fhmx - fhmn) / fhmx; au = ga / fhmx; au *= au; c = 2 / (sqrt (as * as + au) + sqrt (at * at + au)); *svmin = fhmn * c; *svmax = fhmx / c; } else { au = fhmx / ga; if (au == 0) { // Avoid possible harmful underflow if exponent range // asymmetric (true svmin may not underflow even if au underflows) *svmin = (fhmn * fhmx) / ga; *svmax = ga; } else { double t1, t2; as = 1 + fhmn / fhmx; at = (fhmx - fhmn) / fhmx; t1 = as * au; t2 = at * au; c = 1 / (sqrt (1 + t1 * t1) + sqrt (1 + t2 * t2)); *svmin = (fhmn * c) * au; *svmin += *svmin; *svmax = ga / (c + c); } } } } #define MAXIT 50 void NUMgsvdFromUpperTriangulars (double **a, long m, long n, double **b, long p, int product, long k, long l, double tola, double tolb, double *alpha, double *beta, double **u, double **v, double **q, long *ncycle) { int upper = 0; long iter, maxmn = MAX (m, n); double a1, a2, a3, b1, b2, b3, csq, csu, csv; double snq, snu, snv; Melder_assert (m > 0 && p > 0 && n > 0 && k <= maxmn && l <= maxmn); autoNUMvector work (1, 2 * n); for (iter = 1; iter <= MAXIT; iter++) { upper = ! upper; for (long i = 1; i <= l - 1; i++) { for (long j = i + 1; j <= l; j++) { a1 = a2 = a3 = 0; if (k + i <= m) { a1 = a[k + i][n - l + i]; } if (k + j <= m) { a3 = a[k + j][n - l + j]; } b1 = b[i][n - l + i]; b3 = b[j][n - l + j]; if (upper) { if (k + i <= m) { a2 = a[k + i][n - l + j]; } b2 = b[i][n - l + j]; } else { if (k + j <= m) { a2 = a[k + j][n - l + i]; } b2 = b[j][n - l + i]; } NUMgsvdcmp22 (upper, product, a1, a2, a3, b1, b2, b3, &csu, &snu, &csv, &snv, &csq, &snq); // Update (k+i)-th and (k+j)-th rows of matrix A: U'*A if (k + j <= m) NUMplaneRotation (l, TOVEC (a[k + j][n - l + 1]), 1, TOVEC (a[k + i][n - l + 1]), 1, csu, snu); // Update i-th and j-th rows of matrix B: V' * B NUMplaneRotation (l, TOVEC (b[j][n - l + 1]), 1, TOVEC (b[i][n - l + 1]), 1, csv, snv); // Update (n-l+i)-th and (n-l+j)-th columns of matrices A and B: A * Q and B * Q NUMplaneRotation (MIN (k + l, m), TOVEC (a[1][n - l + j]), n, TOVEC (a[1][n - l + i]), n, csq, snq); NUMplaneRotation (l, TOVEC (b[1][n - l + j]), n, TOVEC (b[1][n - l + i]), n, csq, snq); if (upper) { if (k + i <= m) { a[k + i][n - l + j] = 0; } b[i][n - l + j] = 0; } else { if (k + j <= m) { a[k + j][n - l + i] = 0; } b[j][n - l + i] = 0; } // Update columns of orthogonal matrices U, V, Q, if desired. if (u && k + j <= m) { NUMplaneRotation (m, TOVEC (u[1][k + j]), m, TOVEC (u[1][k + i]), m, csu, snu); } if (v) { NUMplaneRotation (p, TOVEC (v[1][j]), p, TOVEC (v[1][i]), p, csv, snv); } if (q) { NUMplaneRotation (n, TOVEC (q[1][n - l + j]), n, TOVEC (q[1][n - l + i]), n, csq, snq); } } } if (! upper) { // The matrices A13 and B13 were lower triangular at the start // of the cycle, and are now upper triangular. // Convergence test: test the parallelism of the corresponding rows of A and B. double error = 0, svmin; for (long i = 1; i <= MIN (l, m - k); i++) { long jj = n - l + i; for (long j = 1; j <= l - i + 1; j++, jj++) { work[j] = a[k + i][jj]; work[l + j] = b[i][jj]; } NUMparallelVectors (l - i + 1, work.peek(), 1, TOVEC (work[l + 1]), 1, &svmin); if (svmin > error) { error = svmin; } } if (fabs (error) <= MIN (tola, tolb) * n) { break; } } } // Has the algorithm converged after maxit cycles? if (iter == MAXIT + 1) { *ncycle = MAXIT; Melder_throw ("No convergence after ", MAXIT, " iterations."); } *ncycle = iter; // Compute the generalized singular value pairs (alpha, beta), and // set the triangular matrix R to matrix a. for (long i = 1; i <= k; i++) { alpha[i] = 1; beta[i] = 0; } for (long i = 1; i <= MIN (l, m - k); i++) { a1 = a[k + i][n - l + i]; b1 = b[i][n - l + i]; if (a1 != 0) { double gamma = b1 / a1, rwk; if (gamma < 0) { /* Change sign of i-th row of B and i-th column of V: B(i, n-l+i:n) := - B(i, n-l+i:n) V(1:p, i) := - V(1:p, i) */ for (long j = n - l + i; j <= n; j++) { b[i][j] = -b[i][j]; } if (v) for (long j = 1; j <= p; j++) { v[j][i] = - v[j][i]; } } NUMfindGivens (fabs (gamma), 1, &beta[k + i], &alpha[k + i], &rwk); if (alpha[k + i] >= beta[k + i]) { for (long j = n - l + i; j <= n; j++) { a[k + i][j] /= alpha[k + i]; } } else { for (long j = n - l + i; j <= n; j++) { b[i][j] /= beta[k + i]; a[k + i][j] = b[i][j]; } } } else { alpha[k + i] = 0; beta[k + i] = 1; for (long j = n - l + i; j <= n; j++) { a[k + i][j] = b[i][j]; } } } // Post-assignment for (long i = m + 1; i <= k + l; i++) { alpha[i] = 0; beta[i] = 1; } if (k + l < n) { for (long i = k + l + 1; i <= n; i++) { alpha[i] = beta[i] = 0; } } } void NUMmatricesToUpperTriangularForms (double **a, long m, long n, double **b, long p, double tola, double tolb, long *kk, long *ll, double **u, double **v, double **q) { int forward = 1; long i, j, k = 0, l = 0, lda = n, ldb = n; Melder_assert (m > 0 && p > 0 && n > 0); *kk = *ll = 0; autoNUMvector pivot (1, n); autoNUMvector tau (1, n); if (v) { NUMidentity (v, 1, p, 1); } if (u) { NUMidentity (u, 1, m, 1); } if (q) { NUMidentity (q, 1, n, 1); } /* QR with column pivoting of B: B * P = V * ( B11 B12 ) ( 0 0 ), where V = H(1)H(2)...H(min(p,n)) */ NUMhouseholderQRwithColumnPivoting (p, n, b, ldb, pivot.peek(), tau.peek()); if (v) NUMapplyFactoredHouseholders (v, 1, p, 1, p, b, 1, p, 1, n, ldb, tau.peek(), NUM_RIGHT, NUM_NOTRANSPOSE); if (q) { NUMpermuteColumns (forward, n, n, q, pivot.peek()); } // Update A := A * P NUMpermuteColumns (forward, m, n, a, pivot.peek()); // Determine the effective rank of matrix B and clean up B. for (l = 0, i = 1; i <= MIN (p, n); i++) { if (fabs (b[i][i]) > tolb) { l++; } } for (i = 2; i <= p; i++) { for (j = 1; j <= (i <= l ? i - 1 : n); j++) { b[i][j] = 0; } } if (p >= l && n != l) { // RQ factorization of (B11 B12): ( B11 B12 ) = ( 0 B12 ) * Z NUMhouseholderRQ (b, 1, l, 1, n, tau.peek()); // Update A := A * Z' and Q := Q * Z' // Householder vectors are stored in rows of B. NUMapplyFactoredHouseholders (a, 1, m, 1, n, b, 1, l, 1, n, 1, tau.peek(), NUM_RIGHT, NUM_NOTRANSPOSE); if (q) NUMapplyFactoredHouseholders (q, 1, n, 1, n, b, 1, l, 1, n, 1, tau.peek(), NUM_RIGHT, NUM_NOTRANSPOSE); // Clean up B for (i = 1; i <= l; i++) { for (j = 1; j <= n - l + i - 1; j++) { b[i][j] = 0; } } } /* We are done with B, now proceed with A. Let n-l l A = ( A11 A12 ) m, then the following does the complete QR decomposition of A11: A11 = U * ( 0 T12 ) * P1' ( 0 0 ) */ if (n - l > 0) { for (i = 1; i <= n - l; i++) { pivot[i] = 0; } NUMhouseholderQRwithColumnPivoting (m, n - l, a, lda, pivot.peek(), tau.peek()); // Determine the effective rank of A11 for (k = 0, i = 1; i <= MIN (m, n - l); i++) { if (fabs (a[i][i]) > tola) { k++; } } // Update A12 := U' * A12, where A12 = A (1:m, n-l+1:n) NUMapplyFactoredHouseholders (a, 1, m, n - l + 1, n, a, 1, m, 1, n - l, lda, tau.peek(), NUM_LEFT, NUM_TRANSPOSE); if (u) NUMapplyFactoredHouseholders (u, 1, m, 1, m, a, 1, m, 1, n - l, lda, tau.peek(), NUM_RIGHT, NUM_NOTRANSPOSE); // Update Q(1:n, 1:n-l) = Q(1:n, 1:n-l) * P1 if (q) { NUMpermuteColumns (forward, n, n - l, q, pivot.peek()); } // Clean up A: set the strictly lower triangular part of // A(1:k, 1:k) = 0, and A(k+1:m, 1:n-l) = 0. for (i = 2; i <= k; i++) { for (j = 1; j <= i - 1; j++) { a[i][j] = 0; } } for (i = k + 1; i <= m; i++) { for (j = 1; j <= n - l; j++) { a[i][j] = 0; } } } if (n - l > k) { // RQ factorization of ( T11 T12 ) = ( 0 T12 ) * Z1 NUMhouseholderRQ (a, 1, k, 1, n - l, tau.peek()); // Update Q(1:n,1:n-l) = Q(1:n,1:n-l ) * Z1' // djmw: was transpose instead of no_transpose if (q) NUMapplyFactoredHouseholders (q, 1, n, 1, n - l, a, 1, k, 1, n - l, 1, tau.peek(), NUM_RIGHT, NUM_NOTRANSPOSE); // Clean up A for (i = 1; i <= k; i++) { for (j = 1; j <= n - l - k + i - 1; j++) { a[i][j] = 0; } } } if (m > k) { // QR factorization of A (k+1:m, n-l+1:n) NUMhouseholderQR (a, k + 1, m, n - l + 1, n, lda, tau.peek()); // Update U(:,k+1:m) := U(:,k+1:m)*U1 if (u) NUMapplyFactoredHouseholders (u, 1, m, k + 1, m, a, k + 1, m, n - l + 1, n, lda, tau.peek(), NUM_RIGHT, NUM_NOTRANSPOSE); // Clean up for (j = n - l + 1; j <= n; j++) { for (i = j - n + k + l + 1; i <= m; i++) { a[i][j] = 0; } } } *kk = k; *ll = l; } void NUMgsvdcmp (double **a, long m, long n, double **b, long p, int productsvd, long *k, long *l, double *alpha, double *beta, double **u, double **v, double **q, int invertR) { long ncycle; Melder_assert (m > 0 && n > 0 && p > 0); /* Get machine precision and set up threshold for determining the effective numerical rank of the matrices a and b. */ if (! NUMfpp) { NUMmachar (); } double anorm = NUMfrobeniusnorm (m, n, a); double bnorm = NUMfrobeniusnorm (p, n, b); if (anorm == 0 || bnorm == 0) { Melder_throw ("NUMgsvdcmp: empty matrix."); } double tola = MAX (m, n) * MAX (anorm, NUMfpp -> sfmin) * NUMfpp -> prec; double tolb = MAX (p, n) * MAX (bnorm, NUMfpp -> sfmin) * NUMfpp -> prec; NUMmatricesToUpperTriangularForms (a, m, n, b, p, tola, tolb, k, l, u, v, q); NUMgsvdFromUpperTriangulars (a, m, n, b, p, productsvd, *k, *l, tola, tolb, alpha, beta, u, v, q, &ncycle); if (q && invertR) { long i, j, ki, nr = *k + *l; int upper, unitDiagonal; autoNUMmatrix r (1, nr, 1, nr); autoNUMvector norms (1, *l); autoNUMvector xrow (n - *k - *l + 1, n); if (m - *k - *l >= 0) { /* n-k-l k l ( 0 R ) = k ( 0 R11 R12 ) l ( 0 0 R22 ) R is stored in A (1:k+l, n-k-l+1:n). */ for (i = 1; i <= nr; i++) { for (j = i; j <= nr; j++) { r[i][j] = a[i][n - *k - *l + j]; } } } else { /* n-k-l k m-k k+l-m ( 0 R ) = k ( 0 R11 R12 R13 ) m-k ( 0 0 R22 R23 ) k+l-m ( 0 0 0 R33 ) (R11 R12 R13 ) is stored in A (1:m, n-k-l+1:n), and R33 is stored ( 0 R22 R23 ) in B (m-k+1:l, n+m-k-l+1:n). */ for (i = 1; i <= m; i++) { for (j = i; j <= nr; j++) { r[i][j] = a[i][n - *k - *l + j]; } } for (i = m + 1; i <= nr; i++) { for (j = i; j <= nr; j++) { r[i][j] = b[i - *k][n - *k - *l + j]; } } } /* Form X = Q * ( I 0 ) ( 0 inv(R) ) and store result in Q. */ NUMtriangularInverse ( (upper = 1), (unitDiagonal = 0), nr, r.peek()); for (i = 1; i <= n; i++) { for (j = n - *k - *l + 1; j <= n; j++) { xrow[j] = 0; for (ki = n - *k - *l + 1; ki <= j; ki++) { xrow[j] += q[i][ki] * r[ki][j]; } } for (j = n - *k - *l + 1; j <= n; j++) { q[i][j] = xrow[j]; } } /* Get norms of eigenvectors. */ for (i = 1; i <= *l; i++) { norms[i] = NUMnorm2 (n, TOVEC (q[1][*k + i]), n); printf ("%f ", norms[i]); } } } void NUMtriangularInverse (int upper, int unitDiagonal, long n, double **a) { long j, i, k; double ajj, tmp; Melder_assert (n > 0); if (upper) { for (j = 1; j <= n; j++) { if (! unitDiagonal) { a[j][j] = 1 / a[j][j]; ajj = -a[j][j]; } else { ajj = -1; } /* Compute elements 1:j-1 of j-th column. */ for (k = 1; k <= j - 1; k++) { if (a[k][j] == 0) { continue; } tmp = a[k][j]; for (i = 1; i <= k - 1; i++) { a[i][j] += tmp * a[i][k]; } if (! unitDiagonal) { a[k][j] *= a[k][k]; } } for (k = 1; k <= j - 1; k++) { a[k][j] *= ajj; } } } else { for (j = n; j >= 1; j--) { if (! unitDiagonal) { a[j][j] = 1 / a[j][j]; ajj = -a[j][j]; } else { ajj = -1; } if (j < n) { /* Compute elements j+1:n of j-th column. */ for (k = n; k >= j + 1; k--) { if (a[k][j] == 0) { continue; } tmp = a[k][j]; for (i = n; i >= k + 1; i--) { a[i][j] += tmp * a[i][k]; } if (! unitDiagonal) { a[k][j] *= a[k][k]; } } for (k = 1; k <= n - j; k++) { a[j + k][j] *= ajj; } } } } } void NUMeigencmp22 (double a, double b, double c, double *rt1, double *rt2, double *cs1, double *sn1) { long sgn1, sgn2; double ab, acmn, acmx, acs, adf, cs, ct, df, rt, sm, tb, tn; sm = a + c; df = a - c; adf = fabs (df); tb = b + b; ab = fabs (tb); if (fabs (a) > fabs (c)) { acmx = a; acmn = c; } else { acmx = c; acmn = a; } if (adf > ab) { tn = ab / adf; rt = adf * sqrt (1 + tn * tn); } else if (adf < ab) { tn = adf / ab; rt = ab * sqrt (1 + tn * tn); } else { rt = ab * sqrt (2); } if (sm < 0) { *rt1 = 0.5 * (sm - rt); sgn1 = -1; /* Order of execution important. To get fully accurate smaller eigenvalue, next line needs to be executed in higher precision. */ *rt2 = (acmx / *rt1) * acmn - (b / *rt1) * b; } else if (sm > 0) { *rt1 = 0.5 * (sm + rt); sgn1 = 1; /* Order of execution important. To get fully accurate smaller eigenvalue, next line needs to be executed in higher precision. */ *rt2 = (acmx / *rt1) * acmn - (b / *rt1) * b; } else { *rt1 = 0.5 * rt; *rt2 = -0.5 * rt; sgn1 = 1; } /* Compute the eigenvector */ if (df >= 0) { cs = df + rt; sgn2 = 1; } else { cs = df - rt; sgn2 = -1; } acs = fabs (cs); if (acs > ab) { ct = -tb / cs; *sn1 = 1 / sqrt (1 + ct * ct); *cs1 = ct * *sn1; } else { if (ab == 0) { *cs1 = 1; *sn1 = 0; } else { tn = -cs / tb; *cs1 = 1 / sqrt (1 + tn * tn); *sn1 = tn * *cs1; } } if (sgn1 == sgn2) { tn = *cs1; *cs1 = -*sn1; *sn1 = tn; } } /* End of file NUMlapack.cpp */ sources_5316/dwsys/Simple_extensions.h0000644000176700017670000000373211627164711016770 0ustar paulpaul#ifndef _Simple_extensions_h_ #define _Simple_extensions_h_ /* Simple_extensions.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950616 djmw 20020812 GPL header */ #include "Data.h" #include "Graphics.h" #include "Simple.h" void SimpleString_init (SimpleString me, const wchar_t *value); /* return 0 when value == NULL */ const wchar_t *SimpleString_c (SimpleString me); /* return pointer to the string */ int SimpleString_compare (SimpleString me, SimpleString thee); void SimpleString_append (SimpleString me, SimpleString thee); void SimpleString_append_c (SimpleString me, const wchar_t *str); /* append string to me */ SimpleString SimpleString_concat (SimpleString me, SimpleString thee); SimpleString SimpleString_concat_c (SimpleString me, const wchar_t *str); /* concatenate two strings */ void SimpleString_replace_c (SimpleString me, const wchar_t *replacement); /* replace my value with new string */ long SimpleString_length (SimpleString me); /* return my length */ void SimpleString_draw (SimpleString me, Graphics g, double xWC, double yWC); /* draw the string */ const wchar_t * SimpleString_nativize_c (SimpleString me, int educateQuotes); const wchar_t * SimpleString_genericize_c (SimpleString me); /* see longchar.h for info */ #endif /* _Simple_extensions_h_ */ sources_5316/dwsys/Eigen.h0000644000176700017670000000600311737004130014267 0ustar paulpaul#ifndef _Eigen_h_ #define _Eigen_h_ /* Eigen.h * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20110306 Latest modification */ #include "Collection.h" #include "Graphics.h" #include "Strings.h" #include "Eigen_def.h" oo_CLASS_CREATE (Eigen, Data); Eigen Eigen_create (long numberOfEigenvalues, long dimension); void Eigen_init (I, long numberOfEigenvalues, long dimension); void Eigen_initFromSymmetricMatrix_f (I, float **a, long n); void Eigen_initFromSymmetricMatrix (I, double **a, long n); void Eigen_initFromSquareRoot (I, double **a, long numberOfRows, long numberOfColumns); /* Calculate eigenstructure for symmetric matrix A'A (e.g. covariance matrix), when only A is given. Precondition: numberOfRows > 1 Method: SVD. */ void Eigen_initFromSquareRootPair (I, double **a, long numberOfRows, long numberOfColumns, double **b, long numberOfRows_b); /* Calculate eigenstructure for A'Ax - lambda B'Bx = 0 Preconditions: numberOfRows >= numberOfColumns && numberOfRows_b >= numberOfColumns Method: Generalized SVD. */ long Eigen_getNumberOfEigenvectors (I); long Eigen_getDimensionOfComponents (I); double Eigen_getCumulativeContributionOfComponents (I, long from, long to); long Eigen_getDimensionOfFraction (I, double fraction); double Eigen_getEigenvectorElement (I, long ivec, long element); double Eigen_getSumOfEigenvalues (I, long from, long to); void Eigen_sort (I); /* Sort eigenvalues and corresponding eigenvectors in decreasing order. */ void Eigen_invertEigenvector (I, long ivec); void Eigen_drawEigenvalues (I, Graphics g, long first, long last, double ymin, double ymax, int fractionOfTotal, int cumulative, double size_mm, const wchar_t *mark, int garnish); void Eigen_drawEigenvector (I, Graphics g, long ivec, long first, long last, double minimum, double maximum, int weigh, double size_mm, const wchar_t *mark, int connect, wchar_t **rowLabels, int garnish); /* Draw eigenvector. When rowLabels != NULL, draw row text labels on bottom axis. */ void Eigens_alignEigenvectors (Collection me); /* Correlate all eigenvectors with the eigenvectors of the first Eigen. If r < 0 then mirror the eigenvectors of */ double Eigens_getAngleBetweenEigenplanes_degrees (I, thou); /* Get angle between the eigenplanes, spanned by the first two eigenvectors, . */ #endif /* _Eigen_h_ */ sources_5316/dwsys/NUM2.cpp0000664000176700017670000022622311747467563014356 0ustar paulpaul/* NUM2.cpp * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020819 GPL header djmw 20020819 Split nonGLP part off. djmw 20001109 Changed stop criteria in NUMsvdcmp and NUMtqli. djmw 20020819 Split into GPL and nonGPL part. djmw 20021008 Removed SVD_sort. djmw 20030619 Removed calls to NRC svd-routines. djmw 20030623 Removed tqli en tred calls. djmw 20030703 Replaced NUMincompleteBeta with gsl_sf_beta_inc. djmw 20030710 NUMminimize_brent now also returns the minimum function value. djmw 20030731 NUMridders: better approximation for small d. NUMinvFisherQ better approximation for p < 0.5 djmw 20030813 Added NUMmad and NUMstatistics_huber. djmw 20030825 Replaced gsl_sf_beta_inc with NUMincompleteBeta pb 20030828 Improvements for invFisherQ, ridders, studentP, studentQ, invStudentQ, invChiSquareQ: modifications for 'undefined' return values. djmw 20030830 Corrected a bug in NUMtriangularfilter_amplitude djmw 20031111 Added NUMdmatrix_transpose, NUMdmatrix_printMatlabForm djmw 20040105 Added NUMmahalanobisDistance_chi djmw 20040211 Modified NUMstrings_copyElements: if (form[i]==NULL) then {to[i]= NULL}. djmw 20040303 Added NUMstring_containsPrintableCharacter. djmw 20050406 NUMprocrutus->NUMprocrustes djmw 20060319 NUMinverse_cholesky: calculation of determinant is made optional djmw 20060517 Added NUMregexp_compile djmw 20060518 Treat NULL string as empty string in strs_replace_regexp/literal. Don't accept empty search in str_replace_regexp djmw 20060626 Extra NULL argument for ExecRE. djmw 20061021 printf expects %ld for 'long int' for 64-bit systems djmw 20070302 NUMclipLineWithinRectangle djmw 20070614 updated to version 1.30 of regular expressions. djmw 20071022 Removed function NUMfvector_moment2. djmw 20071201 Melder_warning djmw 20080107 Changed assertion to "npoints > 0" in NUMcosinesTable djmw 20080110 Corrected some bugs in str_replace_regexp djmw 20080122 Bug in str_replace_regexp djmw 20080317 +NUMsinc pb 20080410 FisherQ from gsl djmw 20090630 NUMlogNormalP/Q from gsl djmw 20090707 Rename NUMinverse_cholesky to NUMlowerCholeskyInverse, +NUMcovarianceFromColumnCentredMatrix, +NUMmultivariateKurtosis djmw 20100311 +NUMsolveQuadraticEquation djmw 20100426 replace wcstok by Melder_wcstok djmw 20101209 removed NUMwcscmp is Melder_wcscmp now djmw 20110304 Thing_new djmw 20111110 use autostringvector */ #include #include "Interpreter.h" #include "SVD.h" #include "Eigen.h" #include "NUMclapack.h" #ifndef _NUM_h_ #include "NUM.h" #endif #include "NUM2.h" #include "NUMmachar.h" #include "melder.h" #include #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf_gamma.h" #include "gsl_sf_erf.h" #include "gsl_sf_trig.h" #include "gsl_poly.h" #include "gsl_cdf.h" #define my me -> #undef MAX #undef MIN #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) #define SIGN(a,b) ((b < 0) ? -fabs(a) : fabs(a)) using namespace std; struct pdf1_struct { double p; double df; }; struct pdf2_struct { double p; double df1; double df2; }; int NUMdmatrix_hasInfinities (double **m, long rb, long re, long cb, long ce) { double min = m[rb][cb]; double max = min; for (long i = rb; i <= re; i++) { for (long j = cb; j <= ce; j++) { if (m[i][j] > max) { max = m[i][j]; } else if (m[i][j] < min) { min = m[i][j]; } } } if (! NUMfpp) { NUMmachar (); } return max >= NUMfpp -> rmax || min <= - NUMfpp -> rmax; } int NUMstring_containsPrintableCharacter (const wchar_t *s) { long len; if (s == NULL || ( (len = wcslen (s)) == 0)) { return 0; } for (long i = 0; i < len; i++) { int c = s[i]; if (isgraph (c)) { return 1; } } return 0; } double *NUMstring_to_numbers (const wchar_t *s, long *numbers_found) { *numbers_found = Melder_countTokens (s); if (*numbers_found < 1) { Melder_throw ("Empty string."); } autoNUMvector numbers (1, *numbers_found); long inum = 1; for (wchar_t *token = Melder_firstToken (s); token != 0; token = Melder_nextToken (), inum++) { Interpreter_numericExpression (0, token, &numbers[inum]); } return numbers.transfer(); } #if 0 int NUMstrings_equal (wchar_t **s1, wchar_t **s2, long lo, long hi) { for (long i = lo; i <= hi; i++) { if (Melder_wcscmp (s1[i], s2[i])) { return 0; } } return 1; } #endif void NUMstrings_copyElements (wchar_t **from, wchar_t **to, long lo, long hi) { for (long i = lo; i <= hi; i++) { Melder_free (to[i]); if (from[i]) { to[i] = Melder_wcsdup (from[i]); } } } void NUMstrings_free (wchar_t **s, long lo, long hi) { if (s == NULL) { return; } for (long i = lo; i <= hi; i++) { Melder_free (s[i]); } NUMvector_free (s, lo); } wchar_t **NUMstrings_copy (wchar_t **from, long lo, long hi) { autoNUMvector to (lo, hi); NUMstrings_copyElements (from, to.peek(), lo, hi); return to.transfer(); } static wchar_t *appendNumberToString (const wchar_t *s, long number) { wchar_t buf[12]; long ncharb, nchars = 0; ncharb = swprintf (buf, 12, L"%ld", number); if (s != NULL) { nchars = wcslen (s); } wchar_t *newc = Melder_calloc (wchar_t, nchars + ncharb + 1); if (nchars > 0) { wcsncpy (newc, s, nchars); } wcsncpy (newc + nchars, buf, ncharb + 1); return newc; } int NUMstrings_setSequentialNumbering (wchar_t **s, long lo, long hi, const wchar_t *pre, long number, long increment) { for (long i = lo; i <= hi; i++, number += increment) { wchar_t *newc = appendNumberToString (pre, number); if (newc == NULL) { return 0; } Melder_free (s[i]); s[i] = newc; } return 1; } #define HIGHBYTE(x) ((unsigned char) ((x) & 0xFF)) #define LOWBYTE(x) ((unsigned char) ((x) >> 8 & 0xFF)) /* a+b=c in radix 256 */ void NUMstring_add (unsigned char *a, unsigned char *b, unsigned char *c, long n); void NUMstring_add (unsigned char *a, unsigned char *b, unsigned char *c, long n) { int j; unsigned short reg = 0; for (j = n; j > 1; j--) { reg = a[j] + b[j] + HIGHBYTE (reg); c[j + 1] = LOWBYTE (reg); } } wchar_t *strstr_regexp (const wchar_t *string, const wchar_t *search_regexp) { wchar_t *charp = 0; const wchar_t *compileMsg; regexp *compiled_regexp = CompileRE ( (regularExp_CHAR *) search_regexp, &compileMsg, 0); if (compiled_regexp == 0) { Melder_throw ("No regexp"); } if (ExecRE (compiled_regexp, NULL, (regularExp_CHAR *) string, NULL, 0, '\0', '\0', NULL, NULL, NULL)) { charp = (wchar *) compiled_regexp -> startp[0]; } free (compiled_regexp); return charp; } wchar_t *str_replace_literal (const wchar_t *string, const wchar_t *search, const wchar_t *replace, long maximumNumberOfReplaces, long *nmatches) { if (string == 0 || search == 0 || replace == 0) { return NULL; } int len_string = wcslen (string); if (len_string == 0) { maximumNumberOfReplaces = 1; } int len_search = wcslen (search); if (len_search == 0) { maximumNumberOfReplaces = 1; } /* To allocate memory for 'result' only once, we have to know how many matches will occur. */ const wchar_t *pos = string; //current position / start of current match *nmatches = 0; if (maximumNumberOfReplaces <= 0) { maximumNumberOfReplaces = LONG_MAX; } if (len_search == 0) { /* Search is empty string... */ if (len_string == 0) { *nmatches = 1; /* ...only matches empty string */ } } else { if (len_string != 0) { /* Because empty string always matches */ while ( (pos = wcsstr (pos, search)) && *nmatches < maximumNumberOfReplaces) { pos += len_search; (*nmatches) ++; } } } int len_replace = wcslen (replace); int len_result = len_string + *nmatches * (len_replace - len_search); wchar_t *result = Melder_malloc (wchar_t, (len_result + 1) * sizeof (wchar_t)); result[len_result] = '\0'; const wchar_t *posp = pos = string; int nchar = 0, result_nchar = 0; for (long i = 1; i <= *nmatches; i++) { pos = wcsstr (pos, search); /* Copy gap between end of previous match and start of current. */ nchar = (pos - posp); if (nchar > 0) { wcsncpy (result + result_nchar, posp, nchar); result_nchar += nchar; } /* Insert the replace string in result. */ wcsncpy (result + result_nchar, replace, len_replace); result_nchar += len_replace; /* Next search starts after the match. */ pos += len_search; posp = pos; } /* Copy gap between end of match and end of string. */ pos = string + len_string; nchar = pos - posp; if (nchar > 0) { wcsncpy (result + result_nchar, posp, nchar); } return result; } wchar_t *str_replace_regexp (const wchar_t *string, regexp *compiledSearchRE, const wchar_t *replaceRE, long maximumNumberOfReplaces, long *nmatches) { int buf_nchar = 0; /* # characters in 'buf' */ int gap_copied = 0; int nchar, reverse = 0; int errorType; wchar_t prev_char = '\0'; const wchar_t *pos; /* current position in 'string' / start of current match */ const wchar_t *posp; /* end of previous match */ autostring buf; *nmatches = 0; if (string == 0 || compiledSearchRE == 0 || replaceRE == 0) { return 0; } int string_length = wcslen (string); //int replace_length = wcslen (replaceRE); if (string_length == 0) { maximumNumberOfReplaces = 1; } long i = maximumNumberOfReplaces > 0 ? 0 : - string_length; /* We do not know the size of the replaced string in advance, therefor, we allocate a replace buffer twice the size of the original string. After all replaces have taken place we do a final realloc to the then exactly known size. If during the replace, the size of the buffer happens to be too small (this is signalled by the replaceRE function), we double its size and restart the replace. */ int buf_size = MAX (2 * string_length, 100); buf.resize (buf_size); pos = posp = string; while (ExecRE (compiledSearchRE, 0, (regularExp_CHAR *) pos, 0, reverse, prev_char, '\0', 0, 0, 0) && i++ < maximumNumberOfReplaces) { /* Copy gap between the end of the previous match and the start of the current match. Check buffer overflow. pos == posp ? '\0' : pos[-1], */ pos = (wchar_t *) compiledSearchRE -> startp[0]; nchar = pos - posp; if (nchar > 0 && ! gap_copied) { if (buf_nchar + nchar + 1 > buf_size) { buf_size *= 2; buf.resize (buf_size); } wcsncpy (buf.peek() + buf_nchar, posp, nchar); buf_nchar += nchar; } gap_copied = 1; /* Do the substitution. We can only check afterwards for buffer overflow. SubstituteRE puts null byte at last replaced position and signals when overflow. */ if ( (SubstituteRE (compiledSearchRE, (regularExp_CHAR *) replaceRE, (regularExp_CHAR *) buf.peek() + buf_nchar, buf_size - buf_nchar, &errorType)) == false) { if (errorType == 1) { // not enough memory buf_size *= 2; buf.resize (buf_size); Melder_clearError (); i--; // retry continue; } Melder_throw ("Error during substitution."); } // Buffer is not full, get number of characters added; nchar = wcslen (buf.peek() + buf_nchar); buf_nchar += nchar; // Update next start position in search string. posp = pos; pos = (wchar_t *) compiledSearchRE -> endp[0]; if (pos != posp) { prev_char = pos[-1]; } gap_copied = 0; posp = pos; //pb 20080121 (*nmatches) ++; // at end of string? // we need this because .* matches at end of a string if (pos - string == string_length) { break; } } // Copy last part of string to destination string nchar = (string + string_length) - pos; buf_size = buf_nchar + nchar + 1; buf.resize (buf_size); wcsncpy (buf.peek() + buf_nchar, pos, nchar); buf[buf_size - 1] = '\0'; return buf.transfer(); } static wchar_t **strs_replace_literal (wchar_t **from, long lo, long hi, const wchar_t *search, const wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches) { if (search == NULL || replace == NULL) { return NULL; } autostringvector result (lo, hi); try { long nmatches_sub = 0; *nmatches = 0; *nstringmatches = 0; for (long i = lo; i <= hi; i++) { /* Treat a NULL as an empty string */ const wchar_t *string = from[i] == NULL ? L"" : from[i]; result[i] = str_replace_literal (string, search, replace, maximumNumberOfReplaces, &nmatches_sub); if (nmatches_sub > 0) { *nmatches += nmatches_sub; (*nstringmatches) ++; } } return result.transfer(); } catch (MelderError) { return 0; } } static wchar_t **strs_replace_regexp (wchar_t **from, long lo, long hi, const wchar_t *searchRE, const wchar_t *replaceRE, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches) { if (searchRE == NULL || replaceRE == NULL) { return NULL; } autostringvector result; try { regexp *compiledRE; const wchar_t *compileMsg; long nmatches_sub = 0; compiledRE = CompileRE ( (regularExp_CHAR *) searchRE, &compileMsg, 0); if (compiledRE == NULL) { Melder_throw ("No regexp "); } result.reset (lo, hi); *nmatches = 0; *nstringmatches = 0; for (long i = lo; i <= hi; i++) { /* Treat a NULL as an empty string */ const wchar_t *string = from[i] == NULL ? L"" : from[i]; result [i] = str_replace_regexp (string, compiledRE, replaceRE, maximumNumberOfReplaces, &nmatches_sub); if (nmatches_sub > 0) { *nmatches += nmatches_sub; (*nstringmatches) ++; } } return result.transfer(); } catch (MelderError) { return 0; } } wchar_t **strs_replace (wchar_t **from, long lo, long hi, const wchar_t *search, const wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp) { if (use_regexp) return strs_replace_regexp (from, lo, hi, search, replace, maximumNumberOfReplaces, nmatches, nstringmatches); else return strs_replace_literal (from, lo, hi, search, replace, maximumNumberOfReplaces, nmatches, nstringmatches); } void NUMdmatrix_printMatlabForm (double **m, long nr, long nc, const wchar_t *name) { long i, j, k, npc = 5; ldiv_t n = ldiv (nc, npc); MelderInfo_open (); MelderInfo_write2 (name, L"=["); for (i = 1; i <= nr; i++) { for (j = 1; j <= n.quot; j++) { for (k = 1; k <= npc; k++) { MelderInfo_write2 (Melder_double (m[i][ (j - 1) *npc + k]), (k < npc ? L", " : L"")); } MelderInfo_write1 (j < n.quot ? L",\n" : L""); } for (k = 1; k <= n.rem; k++) { MelderInfo_write2 (Melder_double (m[i][n.quot * npc + k]), (k < n.rem ? L", " : L"")); } MelderInfo_write1 (i < nr ? L";\n" : L"];\n"); } MelderInfo_close (); } void NUMcentreRows (double **a, long rb, long re, long cb, long ce) { long i, j; for (i = rb; i <= re; i++) { double rowmean = 0; for (j = cb; j <= ce; j++) { rowmean += a[i][j]; } rowmean /= (ce - cb + 1); for (j = cb; j <= ce; j++) { a[i][j] -= rowmean; } } } void NUMcentreColumns (double **a, long rb, long re, long cb, long ce, double *centres) { for (long j = cb; j <= ce; j++) { double colmean = 0; for (long i = rb; i <= re; i++) { colmean += a[i][j]; } colmean /= (re - rb + 1); for (long i = rb; i <= re; i++) { a[i][j] -= colmean; } if (centres != NULL) { centres[j - cb + 1] = colmean; } } } void NUMdoubleCentre (double **a, long rb, long re, long cb, long ce) { NUMcentreRows (a, rb, re, cb, ce); NUMcentreColumns (a, rb, re, cb, ce, NULL); } void NUMnormalizeColumns (double **a, long nr, long nc, double norm) { long i, j; double s; Melder_assert (norm > 0); for (j = 1; j <= nc; j++) { for (s = 0, i = 1; i <= nr; i++) { s += a[i][j] * a[i][j]; } if (s <= 0) { continue; } s = sqrt (norm / s); for (i = 1; i <= nr; i++) { a[i][j] *= s; } } } void NUMnormalizeRows (double **a, long nr, long nc, double norm) { long i, j; double s; Melder_assert (norm > 0); for (i = 1; i <= nr; i++) { for (s = 0, j = 1; j <= nc; j++) { s += a[i][j] * a[i][j]; } if (s <= 0) { continue; } s = sqrt (norm / s); for (j = 1; j <= nc; j++) { a[i][j] *= s; } } } void NUMnormalize (double **a, long nr, long nc, double norm) { double sq; long i, j; Melder_assert (norm > 0); for (sq = 0, i = 1; i <= nr; i++) { for (j = 1; j <= nc; j++) { sq += a[i][j] * a[i][j]; } } if (sq <= 0) { return; } norm = sqrt (norm / sq); for (i = 1; i <= nr; i++) { for (j = 1; j <= nc; j++) { a[i][j] *= norm; } } } void NUMstandardizeColumns (double **a, long rb, long re, long cb, long ce) { long i, j, n = re - rb + 1; if (n < 2) { return; } for (j = cb; j <= ce; j++) { double ep = 0, s = 0, ave, sdev, var = 0; for (i = rb; i <= re; i++) { s += a[i][j]; } ave = s / n; for (i = rb; i <= re; i++) { s = a[i][j] - ave; ep += s; var += s * s; } if (ave != 0) for (i = rb; i <= re; i++) { a[i][j] -= ave; } if (var > 0) { var = (var - ep * ep / n) / (n - 1); sdev = sqrt (var); for (i = rb; i <= re; i++) { a[i][j] /= sdev; } } } } void NUMstandardizeRows (double **a, long rb, long re, long cb, long ce) { long i, j, n = ce - cb + 1; if (n < 2) { return; } for (i = rb; i <= re; i++) { double ep = 0, s = 0, ave, sdev, var = 0; for (j = cb; j <= ce; j++) { s += a[i][j]; } ave = s / n; for (j = cb; j <= ce; j++) { s = a[i][j] - ave; ep += s; var += s * s; } if (ave != 0) for (j = cb; j <= ce; j++) { a[i][j] -= ave; } if (var > 0) { var = (var - ep * ep / n) / (n - 1); sdev = sqrt (var); for (j = cb; j <= ce; j++) { a[i][j] /= sdev; } } } } void NUMaverageColumns (double **a, long rb, long re, long cb, long ce) { long i, j, n = re - rb + 1; if (n < 2) { return; } for (j = cb; j <= ce; j++) { double ave = 0; for (i = rb; i <= re; i++) { ave += a[i][j]; } ave /= n; for (i = rb; i <= re; i++) { a[i][j] = ave; } } } void NUMcolumn_avevar (double **a, long nr, long nc, long icol, double *average, double *variance) { long i; double eps = 0, mean = 0, var = 0; Melder_assert (nr > 0 && nc > 0 && icol > 0 && icol <= nc); for (i = 1; i <= nr; i++) { mean += a[i][icol]; } mean /= nr; if (average != NULL) { *average = mean; } if (variance == NULL) { return; } if (nr > 1) { for (i = 1; i <= nr; i++) { double s = a[i][icol] - mean; eps += s; var += s * s; } var = (var - eps * eps / nr) / (nr - 1); } else { var = NUMundefined; } *variance = var; } void NUMcolumn2_avevar (double **a, long nr, long nc, long icol1, long icol2, double *average1, double *variance1, double *average2, double *variance2, double *covariance) { long i, ndf = nr - 1; double eps1 = 0, eps2 = 0, mean1 = 0, mean2 = 0; double var1 = 0, var2 = 0, covar = 0; Melder_assert (icol1 > 0 && icol1 <= nc && icol2 > 0 && icol2 <= nc); for (i = 1; i <= nr; i++) { mean1 += a[i][icol1]; mean2 += a[i][icol2]; } mean1 /= nr; mean2 /= nr; if (average1 != NULL) { *average1 = mean1; } if (average2 != NULL) { *average2 = mean2; } if (variance1 == NULL && variance2 == NULL && covariance == NULL) { return; } if (nr > 1) { for (i = 1; i <= nr; i++) { double s1 = a[i][icol1] - mean1; double s2 = a[i][icol2] - mean2; eps1 += s1; eps2 += s2; var1 += s1 * s1; var2 += s2 * s2; covar += s1 * s2; } var1 = (var1 - eps1 * eps1 / nr) / ndf; var2 = (var2 - eps2 * eps2 / nr) / ndf; covar /= ndf; } else { var1 = NUMundefined; var2 = NUMundefined; covar = NUMundefined; } if (variance1 != NULL) { *variance1 = var1; } if (variance2 != NULL) { *variance2 = var2; } if (covariance != NULL) { *covariance = covar; } if (icol1 == icol2) { *covariance = *variance1; } } void NUMcovarianceFromColumnCentredMatrix (double **x, long nrows, long ncols, long ndf, double **covar) { if (ndf < 0 || nrows - ndf < 1 || covar == 0) { Melder_throw ("Invalid arguments."); } for (long i = 1; i <= ncols; i++) { for (long j = i; j <= ncols; j++) { double sum = 0; for (long k = 1; k <= nrows; k++) { sum += x[k][i] * x[k][j]; } covar[i][j] = covar[j][i] = sum / (nrows - ndf); } } } double NUMmultivariateKurtosis (double **x, long nrows, long ncols, int method) { double kurt = NUMundefined; if (nrows < 5) { return kurt; } autoNUMvector mean (1, ncols); autoNUMmatrix covar (1, ncols, 1, ncols); NUMcentreColumns (x, 1, nrows, 1, ncols, mean.peek()); NUMcovarianceFromColumnCentredMatrix (x, nrows, ncols, 1, covar.peek()); if (method == 1) { // Schott (2001, page 33) kurt = 0; for (long l = 1; l <= ncols; l++) { double zl = 0, wl, sll2 = covar[l][l] * covar[l][l]; for (long j = 1; j <= nrows; j++) { double d = x[j][l] - mean[l], d2 = d * d; zl += d2 * d2; } zl = (zl - 6 * sll2) / (nrows - 4); wl = (sll2 - zl / nrows) * nrows / (nrows - 1); kurt += zl / wl; } kurt = kurt / (3 * ncols) - 1; } return kurt; } void eigenSort (double d[], double **v, long n, int sort) { long i, j, k; if (sort == 0) { return; } for (i = 1; i < n; i++) { double temp = d[k = i]; if (sort > 0) { for (j = i + 1; j <= n; j++) { if (d[j] > temp) { temp = d[k = j]; } } } else { for (j = i + 1; j <= n; j++) { if (d[j] < temp) { temp = d[k = j]; } } } if (k != i) { d[k] = d[i]; d[i] = temp; if (v) { for (j = 1; j <= n; j++) { temp = v[j][i]; v[j][i] = v[j][k]; v[j][k] = temp; } } } } } int NUMstrcmp (const char *s1, const char *s2) { if (s1 == NULL || s1[0] == '\0') { if (s2 != NULL && s2[0] != '\0') { return -1; } else { return 0; } } else { if (s2 == NULL) { return +1; } else { return strcmp (s1, s2); } } } void NUMlocate_f (float *xx, long n, float x, long *index) { long ju = n + 1, jm, jl = 0; int ascend = xx[n] >= xx[1]; while (ju - jl > 1) { jm = (ju + jl) / 2; if ( (x >= xx[jm]) == ascend) { jl = jm; } else { ju = jm; } } if (x == xx[1]) { *index = 1; } else if (x == xx[n]) { *index = n - 1; } else { *index = jl; } } void NUMlocate (double *xx, long n, double x, long *index) { long ju = n + 1, jm, jl = 0; int ascend = xx[n] >= xx[1]; while (ju - jl > 1) { jm = (ju + jl) / 2; if ( (x >= xx[jm]) == ascend) { jl = jm; } else { ju = jm; } } if (x == xx[1]) { *index = 1; } else if (x == xx[n]) { *index = n - 1; } else { *index = jl; } } /* The following algorithm for monotone regession is on the average 3.5 times faster than Kruskal's algorithm for monotone regression (and much simpler). Regression is ascending */ void NUMmonotoneRegression (const double x[], long n, double xs[]) { double xt = NUMundefined; // Only to stop gcc complaining "may be used unitialized" for (long i = 1; i <= n; i++) { xs[i] = x[i]; } for (long i = 2; i <= n; i++) { if (xs[i] >= xs[i - 1]) { continue; } double sum = xs[i]; long nt = 1; for (long j = 1; j <= i - 1; j++) { sum += xs[i - j]; nt++; xt = sum / nt; // i >= 2 -> xt always gets a value if (j < i - 1 && xt >= xs[i - j - 1]) { break; } } for (long j = i - nt + 1; j <= i; j++) { xs[j] = xt; } } } float NUMfvector_getNorm1 (const float v[], long n); float NUMfvector_getNorm1 (const float v[], long n) { float norm = 0; long i; for (i = 1; i <= n; i++) { norm += fabs (v[i]); } return norm; } float NUMfvector_getNorm2 (const float v[], long n); float NUMfvector_getNorm2 (const float v[], long n) { float norm = 0; long i; for (i = 1; i <= n; i++) { norm += v[i] * v[i]; } return sqrt (norm); } double NUMvector_getNorm2 (const double v[], long n) { double norm = 0; long i; for (i = 1; i <= n; i++) { norm += v[i] * v[i]; } return sqrt (norm); } double NUMvector_normalize1 (double v[], long n) { double norm = 0; long i; for (i = 1; i <= n; i++) { norm += fabs (v[i]); } if (norm > 0) for (i = 1; i <= n; i++) { v[i] /= norm; } return norm; } double NUMvector_normalize2 (double v[], long n) { double norm = 0; long i; for (i = 1; i <= n; i++) { norm += v[i] * v[i]; } norm = sqrt (norm); if (norm > 0) for (i = 1; i <= n; i++) { v[i] /= norm; } return norm; } #undef TINY void NUMcholeskySolve (double **a, long n, double d[], double b[], double x[]) { long i, k; double sum; for (i = 1; i <= n; i++) { /* Solve L.y=b */ for (sum = b[i], k = i - 1; k >= 1; k--) { sum -= a[i][k] * x[k]; } x[i] = sum / d[i]; } for (i = n; i >= 1; i--) { /* Solve L^T.x=y */ for (sum = x[i], k = i + 1; k <= n; k++) { sum -= a[k][i] * x[k]; } x[i] = sum / d[i]; } } void NUMdeterminant_cholesky (double **a, long n, double *lnd) { // Save the diagonal autoNUMvector d (1, n); for (long i = 1; i <= n; i++) { d[i] = a[i][i]; } // Cholesky decomposition in lower, leave upper intact char uplo = 'U'; long lda = n, info; NUMlapack_dpotf2 (&uplo, &n, &a[1][1], &lda, &info); if (info != 0) { Melder_throw ("Cannot determine Cholesky decomposition."); } // Determinant from diagonal, restore diagonal *lnd = 0; for (long i = 1; i <= n; i++) { *lnd += log (a[i][i]); a[i][i] = d[i]; } *lnd *= 2; // because A = L . L' // Restore lower from upper */ for (long i = 1; i < n; i++) { for (long j = i + 1; j <= n; j++) { a[j][i] = a[i][j]; } } } void NUMlowerCholeskyInverse (double **a, long n, double *lnd) { char uplo = 'U', diag = 'N'; long info; // Cholesky decomposition in lower, leave upper intact // Fortran storage -> use uplo='U' to get 'L'. (void) NUMlapack_dpotf2 (&uplo, &n, &a[1][1], &n, &info); if (info != 0) { Melder_throw ("dpotf2 fails."); } // Determinant from diagonal, diagonal is now sqrt (a[i][i]) ! if (lnd != NULL) { *lnd = 0; for (long i = 1; i <= n; i++) { *lnd += log (a[i][i]); } *lnd *= 2; /* because A = L . L' */ } // Get the inverse */ (void) NUMlapack_dtrtri (&uplo, &diag, &n, &a[1][1], &n, &info); if (info != 0) { Melder_throw ("dtrtri fails."); } } double **NUMinverseFromLowerCholesky (double **m, long n) { autoNUMmatrix r (1, n, 1, n); for (long i = 1; i <= n; i++) { for (long j = 1; j <= i; j++) { double sum = 0; for (long k = i; k <= n; k++) { sum += m[k][i] * m[k][j]; } r[i][j] = r[j][i] = sum; } } return r.transfer(); } double NUMmahalanobisDistance_chi (double **linv, double *v, double *m, long nr, long n) { double chisq = 0; if (nr == 1) { // 1xn matrix for (long j = 1; j <= n; j++) { double t = linv[1][j] * (v[j] - m[j]); chisq += t * t; } } else { // nxn matrix for (long i = n; i > 0; i--) { double t = 0; for (long j = 1; j <= i; j++) { t += linv[i][j] * (v[j] - m[j]); } chisq += t * t; } } return chisq; } double NUMtrace (double **a, long n) { double trace = 0; for (long i = 1; i <= n; i++) { trace += a[i][i]; } return trace; } double NUMtrace2 (double **a1, double **a2, long n) { double trace = 0; for (long i = 1; i <= n; i++) for (long k = 1; k <= n; k++) { trace += a1[i][k] * a2[k][i]; } return trace; } void NUMeigensystem (double **a, long n, double **evec, double eval[]) { autoEigen me = Thing_new (Eigen); Eigen_initFromSymmetricMatrix (me.peek(), a, n); if (evec) { NUMmatrix_copyElements (my eigenvectors, evec, 1, n, 1, n); } if (eval) { NUMvector_copyElements (my eigenvalues, eval, 1, n); } } void NUMdominantEigenvector (double **mns, long n, double *q, double *lambda, double tolerance) { autoNUMvector z (1, n); double val, cval = 0; for (long k = 1; k <= n; k++) { for (long l = 1; l <= n; l++) { cval += q[k] * mns[k][l] * q[l]; } } if (cval == 0) { Melder_throw ("Zero matrices ??"); } long iter = 0; do { double znorm2 = 0; for (long l = 1; l <= n; l++) { z[l] = 0; for (long k = 1; k <= n; k++) { z[l] += mns[l][k] * q[k]; } } for (long k = 1; k <= n; k++) { znorm2 += z[k] * z[k]; } znorm2 = sqrt (znorm2); for (long k = 1; k <= n; k++) { q[k] = z[k] / znorm2; } val = cval; cval = 0; for (long k = 1; k <= n; k++) { for (long l = 1; l <= n; l++) { cval += q[k] * mns[k][l] * q[l]; } } } while (fabs (cval - val) > tolerance || ++iter < 30); *lambda = cval; } void NUMprincipalComponents (double **a, long n, long nComponents, double **pc) { autoNUMmatrix evec (1, n, 1, n); NUMeigensystem (a, n, evec.peek(), NULL); for (long i = 1; i <= n; i++) { for (long j = 1; j <= nComponents; j++) { double s = 0; for (long k = 1; k <= n; k++) { s += a[k][i] * evec[k][j]; /* times sqrt(eigenvalue) ?? */ } pc[i][j] = s; } } } void NUMdmatrix_into_principalComponents (double **m, long nrows, long ncols, long numberOfComponents, double **pc) { Melder_assert (numberOfComponents > 0 && numberOfComponents <= ncols); autoNUMmatrix mc (NUMmatrix_copy (m, 1, nrows, 1, ncols), 1, 1); /*NUMcentreColumns (mc, nrows, ncols);*/ autoSVD svd = SVD_create_d (mc.peek(), nrows, ncols); for (long i = 1; i <= nrows; i++) { for (long j = 1; j <= numberOfComponents; j++) { pc[i][j] = 0; for (long k = 1; k <= ncols; k++) { pc[i][j] += svd -> v[k][j] * m[i][k]; } } } } void NUMpseudoInverse (double **y, long nr, long nc, double **yinv, double tolerance) { autoSVD me = SVD_create_d (y, nr, nc); (void) SVD_zeroSmallSingularValues (me.peek(), tolerance); for (long i = 1; i <= nc; i++) { for (long j = 1; j <= nr; j++) { double s = 0; for (long k = 1; k <= nc; k++) { if (my d[k] != 0) { s += my v[i][k] * my u[j][k] / my d[k]; } } yinv[i][j] = s; } } } long NUMsolveQuadraticEquation (double a, double b, double c, double *x1, double *x2) { return gsl_poly_solve_quadratic (a, b, c, x1, x2); } void NUMsolveEquation (double **a, long nr, long nc, double *b, double tolerance, double *result) { double tol = tolerance > 0 ? tolerance : NUMfpp -> eps * nr; if (nr <= 0 || nc <= 0) { Melder_throw ("Negative dimensions"); } autoSVD me = SVD_create_d (a, nr, nc); SVD_zeroSmallSingularValues (me.peek(), tol); SVD_solve (me.peek(), b, result); } void NUMsolveEquations (double **a, long nr, long nc, double **b, long ncb, double tolerance, double **x) { double tol = tolerance > 0 ? tolerance : NUMfpp -> eps * nr; if (nr <= 0 || nc <= 0) { Melder_throw ("Negative dimensions"); } autoSVD me = SVD_create_d (a, nr, nc); autoNUMvector bt (1, nr + nc); double *xt = & bt[nr]; SVD_zeroSmallSingularValues (me.peek(), tol); for (long k = 1; k <= ncb; k++) { for (long j = 1; j <= nr; j++) { bt[j] = b[j][k]; } SVD_solve (me.peek(), bt.peek(), xt); for (long j = 1; j <= nc; j++) { x[j][k] = xt[j]; } } } void NUMsolveNonNegativeLeastSquaresRegression (double **m, long nr, long nc, double *d, double tol, long itermax, double *b) { double difsq, difsqp = 0; for (long iter = 1; iter <= itermax; iter++) { /* Fix all weights except b[j] */ for (long j = 1; j <= nc; j++) { double mjr = 0, mjmj = 0; for (long i = 1; i <= nr; i++) { double ri = d[i], mij = m[i][j]; for (long l = 1; l <= nc; l++) { if (l != j) { ri -= b[l] * m[i][l]; } } mjr += mij * ri; mjmj += mij * mij; } b[j] = mjr / mjmj; if (b[j] < 0) { b[j] = 0; } } /* Calculate t(b) and compare with previous result. */ difsq = 0; for (long i = 1; i <= nr; i++) { double dmb = d[i]; for (long j = 1; j <= nc; j++) { dmb -= m[i][j] * b[j]; } difsq += dmb * dmb; } if (fabs (difsq - difsqp) / difsq < tol) { break; } difsqp = difsq; } } struct nr_struct { double *y, *delta; }; /* f (lambda) = sum (y[i]^2 delta[i] / (delta[i]-lambda)^2, i=1..3) f'(lambda) = 2 * sum (y[i]^2 delta[i] / (delta[i]-lambda)^3, i=1..3) */ static void nr_func (double x, double *f, double *df, void *data) { struct nr_struct *me = (struct nr_struct *) data; *f = *df = 0; for (long i = 1; i <= 3; i++) { double t1 = (my delta[i] - x); double t2 = my y[i] / t1; double t3 = t2 * t2 * my delta[i]; *f += t3; *df += t3 * 2 / t1; } } void NUMsolveConstrainedLSQuadraticRegression (double **o, const double d[], long n, double *alpha, double *gamma) { long n3 = 3, info; double eps = 1e-5, t1, t2, t3; autoNUMmatrix ftinv (1, n3, 1, n3); autoNUMmatrix b (1, n3, 1, n3); autoNUMmatrix g (1, n3, 1, n3); autoNUMmatrix p (1, n3, 1, n3); autoNUMvector delta (1, n3); autoNUMmatrix ftinvp (1, n3, 1, n3); autoNUMmatrix ptfinv (1, n3, 1, n3); autoNUMvector otd (1, n3); autoNUMmatrix ptfinvc (1, n3, 1, n3); autoNUMvector y (1, n3); autoNUMvector w (1, n3); autoNUMvector chi (1, n3); autoNUMvector diag (1, n3); // Construct O'.O [1..3][1..3]. for (long i = 1; i <= n3; i++) { for (long j = 1; j <= n3; j++) { for (long k = 1; k <= n; k++) { ftinv[i][j] += o[k][i] * o[k][j]; } } } // Get lower triangular decomposition from O'.O and // get F'^-1 from it (eq. (2)) (F^-1 not done ????) char uplo = 'U'; (void) NUMlapack_dpotf2 (&uplo, &n3, &ftinv[1][1], &n3, &info); if (info != 0) { Melder_throw ("dpotf2 fails."); } ftinv[1][2] = ftinv[1][3] = ftinv[2][3] = 0; // Construct G and its eigen-decomposition (eq. (4,5)) // Sort eigenvalues (& eigenvectors) ascending. b[3][1] = b[1][3] = -0.5; b[2][2] = 1; // G = F^-1 B (F')^-1 (eq. 4) for (long i = 1; i <= 3; i++) { for (long j = 1; j <= 3; j++) { for (long k = 1; k <= 3; k++) { if (ftinv[k][i] != 0) { for (long l = 1; l <= 3; l++) { g[i][j] += ftinv[k][i] * b[k][l] * ftinv[l][j]; } } } } } // G's eigen-decomposition with eigenvalues (assumed ascending). (eq. 5) NUMeigensystem (g.peek(), 3, p.peek(), delta.peek()); NUMsort_d (3, delta.peek()); /* ascending */ // Construct y = P'.F'.O'.d ==> Solve (F')^-1 . P .y = (O'.d) (page 632) // Get P'F^-1 from the transpose of (F')^-1 . P for (long i = 1; i <= 3; i++) { for (long j = 1; j <= 3; j++) { if (ftinv[i][j] != 0) { for (long k = 1; k <= 3; k++) { ftinvp[i][k] += ftinv[i][j] * p[3 + 1 - j][k]; /* is sorted desc. */ } } } for (long k = 1; k <= n; k++) { otd[i] += o[k][i] * d[k]; } } for (long i = 1; i <= 3; i++) { for (long j = 1; j <= 3; j++) { ptfinvc[j][i] = ptfinv[j][i] = ftinvp[i][j]; } } NUMsolveEquation (ftinvp.peek(), 3, 3, otd.peek(), 1e-6, y.peek()); // The solution (3 cases) if (fabs (y[1]) < eps) { // Case 1: page 633 t2 = y[2] / (delta[2] - delta[1]); t3 = y[3] / (delta[3] - delta[1]); /* +- */ w[1] = sqrt (- delta[1] * (t2 * t2 * delta[2] + t3 * t3 * delta[3])); w[2] = t2 * delta[2]; w[3] = t3 * delta[3]; NUMsolveEquation (ptfinv.peek(), 3, 3, w.peek(), 1e-6, chi.peek()); w[1] = -w[1]; if (fabs (chi[3] / chi[1]) < eps) { NUMsolveEquation (ptfinvc.peek(), 3, 3, w.peek(), 1e-6, chi.peek()); } } else if (fabs (y[2]) < eps) { // Case 2: page 633 t1 = y[1] / (delta[1] - delta[2]); t3 = y[3] / (delta[3] - delta[2]); w[1] = t1 * delta[1]; if ( (delta[2] < delta[3] && (t2 = (t1 * t1 * delta[1] + t3 * t3 * delta[3])) < eps)) { w[2] = sqrt (- delta[2] * t2); /* +- */ w[3] = t3 * delta[3]; NUMsolveEquation (ptfinv.peek(), 3, 3, w.peek(), 1e-6, chi.peek()); w[2] = -w[2]; if (fabs (chi[3] / chi[1]) < eps) { NUMsolveEquation (ptfinvc.peek(), 3, 3, w.peek(), 1e-6, chi.peek()); } } else if ( ( (delta[2] < delta[3] + eps) || (delta[2] > delta[3] - eps)) && fabs (y[3]) < eps) { // choose one value for w[2] from an infinite number w[2] = w[1]; w[3] = sqrt (- t1 * t1 * delta[1] * delta[2] - w[2] * w[2]); NUMsolveEquation (ptfinv.peek(), 3, 3, w.peek(), 1e-6, chi.peek()); } } else { // Case 3: page 634 use Newton-Raphson root finder struct nr_struct me; double xlambda, eps2 = (delta[2] - delta[1]) * 1e-6; me.y = y.peek(); me.delta = delta.peek(); NUMnrbis (nr_func, delta[1] + eps, delta[2] - eps2, & me, & xlambda); for (long i = 1; i <= 3; i++) { w[i] = y[i] / (1 - xlambda / delta[i]); } NUMsolveEquation (ptfinv.peek(), 3, 3, w.peek(), 1e-6, chi.peek()); } *alpha = chi[1]; *gamma = chi[3]; } /* f (b) = delta - b / (2 alpha) - sum (x[i]^2 / (c[i] - b)^2, i=1..n) f'(b) = - 1 / (2 alpha) + 2 * sum (x[i]^2 / (c[i] - b)^3, i=1..n) */ struct nr2_struct { long m; double delta, alpha, *x, *c; }; static void nr2_func (double b, double *f, double *df, void *data) { struct nr2_struct *me = (struct nr2_struct *) data; *df = - 0.5 / my alpha; *f = my delta + *df * b; for (long i = 1; i <= my m; i++) { double c1 = (my c[i] - b); double c2 = my x[i] / c1; double c2sq = c2 * c2; *f -= c2sq; *df += 2 * c2sq / c1; } } void NUMsolveWeaklyConstrainedLinearRegression (double **f, long n, long m, double phi[], double alpha, double delta, double t[]) { autoNUMmatrix u (1, m, 1, m); autoNUMvector c (1, m); autoNUMvector x (1, n); autoNUMvector indx (1, m); for (long j = 1; j <= m; j++) { t[j] = 0; } autoSVD svd = SVD_create_d (f, n, m); if (alpha == 0) { SVD_solve (svd.peek(), phi, t); // standard least squares } // Step 1: Compute U and C from the eigendecomposition F'F = UCU' // Evaluate q, the multiplicity of the smallest eigenvalue in C double *sqrtc = svd -> d; double **ut = svd -> v; NUMindexx (sqrtc, m, indx.peek()); for (long j = m; j > 0; j--) { double tmp = sqrtc [indx[j]]; c[m - j + 1] = tmp * tmp; for (long k = 1; k <= m; k++) { u[m - j + 1][k] = ut [indx[j]] [k]; } } long q = 1; double tol = 1e-6; while (q < m && (c[m - q] - c[m]) < tol) { q++; } // step 2: x = U'F'phi for (long i = 1; i <= m; i++) { for (long j = 1; j <= m; j++) { for (long k = 1; k <= n; k++) { x[i] += u[j][i] * f[k][j] * phi[k]; } } } // step 3: struct nr2_struct me; me.m = m; me.delta = delta; me.alpha = alpha; me.x = x.peek(); me.c = c.peek(); double xqsq = 0; for (long j = m - q + 1; j <= m; j++) { xqsq += x[j] * x[j]; } long r = m; if (xqsq < tol) { /* xqsq == 0 */ double fm, df; r = m - q; me.m = r; nr2_func (c[m], &fm, &df, & me); if (fm >= 0) { /* step 3.b1 */ x[r + 1] = sqrt (fm); for (long j = 1; j <= r; j++) { x[j] /= c[j] - c[m]; } for (long j = 1; j <= r + 1; j++) { for (long k = 1; k <= r + 1; k++) { t[j] += u[j][k] * x[k]; } } return; } /* else continue with r = m - q */ } // step 3a & 3b2, determine interval lower bound for Newton-Raphson root finder double xCx = 0; for (long j = 1; j <= r; j++) { xCx += x[j] * x[j] / c[j]; } double b0, bmin = delta > 0 ? - xCx / delta : -2 * sqrt (alpha * xCx); double eps = (c[m] - bmin) * tol; // find the root of d(psi(b)/db in interval (bmin, c[m]) NUMnrbis (nr2_func, bmin + eps, c[m] - eps, & me, & b0); for (long j = 1; j <= r; j++) { for (long k = 1; k <= r; k++) { t[j] += u[j][k] * x[k] / (c[k] - b0); } } } void NUMProcrustes (double **x, double **y, long nPoints, long nDimensions, double **t, double *v, double *s) { int orthogonal = v == 0 || s == 0; /* else similarity transform */ autoNUMmatrix c (1, nDimensions, 1, nDimensions); autoNUMmatrix yc (1, nPoints, 1, nDimensions); NUMmatrix_copyElements (y, yc.peek(), 1, nPoints, 1, nDimensions); /* Reference: Borg & Groenen (1997), Modern multidimensional scaling, Springer 1. Calculate C = X'JY (page 346) for similarity transform else X'Y for othogonal (page 341) JY amounts to centering the columns of Y. */ if (! orthogonal) { NUMcentreColumns (yc.peek(), 1, nPoints, 1, nDimensions, NULL); } for (long i = 1; i <= nDimensions; i++) { for (long j = 1; j <= nDimensions; j++) { for (long k = 1; k <= nPoints; k++) { c[i][j] += x[k][i] * yc[k][j]; } } } // 2. Decompose C by SVD: C = PDQ' (SVD attribute is Q instead of Q'!) autoSVD svd = SVD_create_d (c.peek(), nDimensions, nDimensions); double trace = 0; for (long i = 1; i <= nDimensions; i++) { trace += svd -> d[i]; } if (trace == 0) { Melder_throw ("NUMProcrustes: degenerate configuration(s)."); } // 3. T = QP' for (long i = 1; i <= nDimensions; i++) { for (long j = 1; j <= nDimensions; j++) { t[i][j] = 0; for (long k = 1; k <= nDimensions; k++) { t[i][j] += svd -> v[i][k] * svd -> u[j][k]; } } } if (! orthogonal) { autoNUMmatrix xc (1, nPoints, 1, nDimensions); NUMmatrix_copyElements (x, xc.peek(), 1, nPoints, 1, nDimensions); autoNUMmatrix yt (1, nPoints, 1, nDimensions); // 4. Dilation factor s = (tr X'JYT) / (tr Y'JY) // First we need YT. for (long i = 1; i <= nPoints; i++) { for (long j = 1; j <= nDimensions; j++) { for (long k = 1; k <= nDimensions; k++) { yt[i][j] += y[i][k] * t[k][j]; } } } // X'J amount to centering the columns of X NUMcentreColumns (xc.peek(), 1, nPoints, 1, nDimensions, NULL); // tr X'J YT == tr xc' yt double traceXtJYT = 0; for (long i = 1; i <= nDimensions; i++) { for (long j = 1; j <= nPoints; j++) { traceXtJYT += xc[j][i] * yt[j][i]; } } double traceYtJY = 0; for (long i = 1; i <= nDimensions; i++) { for (long j = 1; j <= nPoints; j++) { traceYtJY += y[j][i] * yc[j][i]; } } *s = traceXtJYT / traceYtJY; // 5. Translation vector tr = (X - sYT)'1 / nPoints for (long i = 1; i <= nDimensions; i++) { for (long j = 1; j <= nPoints; j++) { v[i] += x[j][i] - *s * yt[j][i]; } v[i] /= nPoints; } } } void NUMmspline (double knot[], long nKnots, long order, long i, double x, double *y) { long jj, nSplines = nKnots - order; if (nSplines <= 0) { Melder_throw ("No splines."); } // Find the interval where x is located. // M-splines of order k have degree k-1. // M-splines are zero outside interval [ knot[i], knot[i+order] ). // First and last 'order' knots are equal, i.e., // knot[1] = ... = knot[order] && knot[nKnots-order+1] = ... knot[nKnots]. *y = 0; if (i > nSplines || order < 1) { Melder_throw ("Combination of order and index not correct."); } for (jj = order; jj <= nKnots - order + 1; jj++) { if (x < knot[jj]) { break; } } if (jj < i || (jj > i + order) || jj == order || jj > (nKnots - order + 1)) { return; } // Calculate M[i](x|1,t) according to eq.2. long ito = i + order - 1; autoNUMvector m (i, ito); for (long j = i; j <= ito; j++) { if (x >= knot[j] && x < knot[j + 1]) { m[j] = 1 / (knot[j + 1] - knot[j]); } } // Iterate to get M[i](x|k,t) for (long k = 2; k <= order; k++) { for (long j = i; j <= i + order - k; j++) { double kj = knot[j], kjpk = knot[j + k]; if (kjpk > kj) { m[j] = k * ( (x - kj) * m[j] + (kjpk - x) * m[j + 1]) / ( (k - 1) * (kjpk - kj)); } } } *y = m[i]; } void NUMispline (double aknot[], long nKnots, long order, long i, double x, double *y) { long j, orderp1 = order + 1; *y = 0; for (j = orderp1; j <= nKnots - order; j++) { if (x < aknot[j]) { break; } } j--; if (j < i) { return; } if (j > i + order || (j == nKnots - order && x == aknot[j])) { *y = 1; return; } // Equation 5 in Ramsay's article contains some errors!!! // 1. the interval selection must be 'j-k <= i <= j' instead of // 'j-k+1 <= i <= j' // 2. the summation index m starts at 'i+1' instead of 'i' for (long m = i + 1; m <= j; m++) { double r; NUMmspline (aknot, nKnots, orderp1, m, x, &r); *y += (aknot[m + orderp1] - aknot[m]) * r; } *y /= orderp1; } double NUMwilksLambda (double *lambda, long from, long to) { double result = 1; for (long i = from; i <= to; i++) { result /= (1 + lambda[i]); } return result; } double NUMfactln (int n) { static double table[101]; if (n < 0) { return NUMundefined; } if (n <= 1) { return 0; } return n > 100 ? NUMlnGamma (n + 1.0) : table[n] ? table[n] : (table[n] = NUMlnGamma (n + 1.0)); } void NUMnrbis (void (*f) (double x, double *fx, double *dfx, void *closure), double x1, double x2, void *closure, double *root) { double df, dx, dxold, fx, fh, fl, tmp, xh, xl, tol; long itermax = 60; (*f) (x1, &fl, &df, closure); if (fl == 0.0) { *root = x1; return; } (*f) (x2, &fh, &df, closure); if (fh == 0.0) { *root = x2; return; } if ( (fl > 0.0 && fh > 0.0) || (fl < 0.0 && fh < 0.0)) { *root = NUMundefined; Melder_throw (L"Root must be bracketed."); } if (fl < 0.0) { xl = x1; xh = x2; } else { xh = x1; xl = x2; } dxold = fabs (x2 - x1); dx = dxold; *root = 0.5 * (x1 + x2); (*f) (*root, &fx, &df, closure); for (long iter = 1; iter <= itermax; iter++) { if ( ( ( (*root - xh) * df - fx) * ( (*root - xl) * df - fx) >= 0.0) || (fabs (2.0 * fx) > fabs (dxold * df))) { dxold = dx; dx = 0.5 * (xh - xl); *root = xl + dx; if (xl == *root) { return; } } else { dxold = dx; dx = fx / df; tmp = *root; *root -= dx; if (tmp == *root) { return; } } tol = NUMfpp -> eps * (*root == 0 ? 1 : fabs (*root)); if (fabs (dx) < tol) { return; } (*f) (*root, &fx, &df, closure); if (fx < 0.0) { xl = *root; } else { xh = *root; } } Melder_warning (L"NUMnrbis: maximum number of iterations (", Melder_integer (itermax), L") exceeded."); } double NUMridders (double (*f) (double x, void *closure), double x1, double x2, void *closure) { /* There is still a problem with this implementation: tol may be zero; */ double x3, x4, d, root = NUMundefined; double f1, f2, f3, f4, tol; long itermax = 100; f1 = f (x1, closure); if (f1 == 0.0) { return x1; } if (f1 == NUMundefined) { return NUMundefined; } f2 = f (x2, closure); if (f2 == 0.0) { return x2; } if (f2 == NUMundefined) { return NUMundefined; } if ( (f1 < 0 && f2 < 0) || (f1 > 0 && f2 > 0)) { Melder_warning (L"NUMridders: root must be bracketed."); return NUMundefined; } for (long iter = 1; iter <= itermax; iter++) { x3 = 0.5 * (x1 + x2); f3 = f (x3, closure); if (f3 == 0.0) { return x3; } if (f3 == NUMundefined) { return NUMundefined; } /* New guess: x4 = x3 + (x3 - x1) * sign(f1 - f2) * f3 / sqrt(f3^2 - f1*f2) */ d = f3 * f3 - f1 * f2; if (d < 0.0) { Melder_warning (L"d < 0 in ridders (iter = ", Melder_integer (iter), L")."); return NUMundefined; } if (d == 0.0) { /* pb test added because f1 f2 f3 may be 1e-170 or so */ tol = NUMfpp -> eps * fabs (x3); if (iter > 1 && fabs (x3 - root) < tol) { return root; } root = x3; /* * Perform bisection. */ if (f1 > 0.0) { /* falling curve: f1 > 0, f2 < 0 */ if (f3 > 0.0) { x1 = x3; f1 = f3; /* retain invariant: f1 > 0, f2 < 0 */ } else { /* f3 < 0.0 */ x2 = x3; f2 = f3; /* retain invariant: f1 > 0, f2 < 0 */ } } else { /* rising curve: f1 < 0, f2 > 0 */ if (f3 > 0.0) { x2 = x3; f2 = f3; /* retain invariant: f1 < 0, f2 > 0 */ } else { /* f3 < 0.0 */ x1 = x3; f1 = f3; /* retain invariant: f1 < 0, f2 > 0 */ } } } else { d = sqrt (d); if (isnan (d)) { /* pb: square root of denormalized small number fails on some computers */ tol = NUMfpp -> eps * fabs (x3); if (iter > 1 && fabs (x3 - root) < tol) { return root; } root = x3; /* * Perform bisection. */ if (f1 > 0.0) { /* falling curve: f1 > 0, f2 < 0 */ if (f3 > 0.0) { x1 = x3; f1 = f3; /* retain invariant: f1 > 0, f2 < 0 */ } else { /* f3 < 0.0 */ x2 = x3; f2 = f3; /* retain invariant: f1 > 0, f2 < 0 */ } } else { /* rising curve: f1 < 0, f2 > 0 */ if (f3 > 0.0) { x2 = x3; f2 = f3; /* retain invariant: f1 < 0, f2 > 0 */ } else { /* f3 < 0.0 */ x1 = x3; f1 = f3; /* retain invariant: f1 < 0, f2 > 0 */ } } } else { d = (x3 - x1) * f3 / d; x4 = f1 - f2 < 0 ? x3 - d : x3 + d; tol = NUMfpp -> eps * fabs (x4); if (iter > 1 && fabs (x4 - root) < tol) { return root; } root = x4; f4 = f (x4, closure); if (f4 == 0.0) { return root; } if (f4 == NUMundefined) { return NUMundefined; } if ( (f1 > f2) == (d > 0.0) /* pb: instead of x3 < x4 */) { if (SIGN (f3, f4) != f3) { x1 = x3; f1 = f3; x2 = x4; f2 = f4; } else { x1 = x4; f1 = f4; } } else { if (SIGN (f3, f4) != f3) { x1 = x4; f1 = f4; x2 = x3; f2 = f3; } else { x2 = x4; f2 = f4; } } } } if (fabs (x1 - x2) < tol) { return root; } } { static long nwarnings = 0; nwarnings++; Melder_warning (L"NUMridders: maximum number of iterations (", Melder_integer (itermax), L") exceeded."); } return root; } double NUMlogNormalP (double x, double zeta, double sigma) { return gsl_cdf_lognormal_P (x, zeta, sigma); } double NUMlogNormalQ (double x, double zeta, double sigma) { return gsl_cdf_lognormal_Q (x, zeta, sigma); } double NUMstudentP (double t, double df) { if (df < 1) { return NUMundefined; } double ib = NUMincompleteBeta (0.5 * df, 0.5, df / (df + t * t)); if (ib == NUMundefined) { return NUMundefined; } ib *= 0.5; return t < 0 ? ib : 1 - ib; } double NUMstudentQ (double t, double df) { if (df < 1) { return NUMundefined; } double ib = NUMincompleteBeta (0.5 * df, 0.5, df / (df + t * t)); if (ib == NUMundefined) { return NUMundefined; } ib *= 0.5; return t > 0 ? ib : 1 - ib; } double NUMfisherP (double f, double df1, double df2) { if (f < 0 || df1 < 1 || df2 < 1) { return NUMundefined; } double ib = NUMincompleteBeta (0.5 * df2, 0.5 * df1, df2 / (df2 + f * df1)); if (ib == NUMundefined) { return NUMundefined; } return 1 - ib; } double NUMfisherQ (double f, double df1, double df2) { if (f < 0 || df1 < 1 || df2 < 1) { return NUMundefined; } if (Melder_debug == 28) { return NUMincompleteBeta (0.5 * df2, 0.5 * df1, df2 / (df2 + f * df1)); } else { double result = gsl_cdf_fdist_Q (f, df1, df2); if (isnan (result)) { return NUMundefined; } return result; } } double NUMinvGaussQ (double p) { double pc = p; if (p <= 0 || p >= 1.0) { return NUMundefined; } if (p > 0.5) { pc = 1 - p; } double t = sqrt (- 2.0 * log (pc)); t -= (2.515517 + (0.802853 + 0.010328 * t) * t) / (1.0 + (1.432788 + (0.189269 + 0.001308 * t) * t) * t); return p > 0.5 ? -t : t; } static double studentQ_func (double x, void *voidParams) { struct pdf1_struct *params = (struct pdf1_struct *) voidParams; double q = NUMstudentQ (x, params -> df); return q == NUMundefined ? NUMundefined : q - params -> p; } double NUMinvStudentQ (double p, double df) { struct pdf1_struct params; double pc = p > 0.5 ? 1 - p : p, xmin, xmax = 1, x; if (p < 0 || p >= 1) { return NUMundefined; } /* Bracket the function f(x) = NUMstudentQ (x, df) - p. */ for (;;) { double q = NUMstudentQ (xmax, df); if (q == NUMundefined) { return NUMundefined; } if (q < pc) { break; } xmax *= 2; } xmin = xmax > 1 ? xmax / 2 : 0; /* Find zero of f(x) with Ridders' method. */ params. df = df; params. p = pc; x = NUMridders (studentQ_func, xmin, xmax, & params); if (x == NUMundefined) { return NUMundefined; } return p > 0.5 ? -x : x; } static double chiSquareQ_func (double x, void *voidParams) { struct pdf1_struct *params = (struct pdf1_struct *) voidParams; double q = NUMchiSquareQ (x, params -> df); return q == NUMundefined ? NUMundefined : q - params -> p; } double NUMinvChiSquareQ (double p, double df) { struct pdf1_struct params; double xmin, xmax = 1; if (p < 0 || p >= 1) { return NUMundefined; } /* Bracket the function f(x) = NUMchiSquareQ (x, df) - p. */ for (;;) { double q = NUMchiSquareQ (xmax, df); if (q == NUMundefined) { return NUMundefined; } if (q < p) { break; } xmax *= 2; } xmin = xmax > 1 ? xmax / 2 : 0; /* Find zero of f(x) with Ridders' method. */ params. df = df; params. p = p; return NUMridders (chiSquareQ_func, xmin, xmax, & params); } static double fisherQ_func (double x, void *voidParams) { struct pdf2_struct *params = (struct pdf2_struct *) voidParams; double q = NUMfisherQ (x, params -> df1, params -> df2); return q == NUMundefined ? NUMundefined : q - params -> p; } double NUMinvFisherQ (double p, double df1, double df2) { if (p <= 0.0 || p > 1.0 || df1 < 1 || df2 < 1) { return NUMundefined; } if (Melder_debug == 29) { //if (p == 1.0) return 0.0; return gsl_cdf_fdist_Qinv (p, df1, df2); } else { struct pdf2_struct params; double top = 1000.0; if (p == 1.0) { return 0.0; } params. p = p; params. df1 = df1; params. df2 = df2; for (;;) { double q = NUMfisherQ (top, df1, df2); if (q == NUMundefined) { return NUMundefined; } if (q < p) { break; } if (top > 0.9e300) { return NUMundefined; } top *= 1e9; } return NUMridders (fisherQ_func, 0.0, p > 0.5 ? 2.2 : top, & params); } } double NUMbeta2 (double z, double w) { gsl_sf_result result; int status = gsl_sf_beta_e (z, w, &result); return status == GSL_SUCCESS ? result.val : NUMundefined; } double NUMlnBeta (double a, double b) { gsl_sf_result result; int status = gsl_sf_lnbeta_e (a, b, &result); return status == GSL_SUCCESS ? result.val : NUMundefined; } double NUMnormalityTest_HenzeZirkler (double **data, long n, long p, double *beta, double *tnb, double *lnmu, double *lnvar) { if (*beta <= 0) { *beta = (1.0 / sqrt (2)) * pow ( (1.0 + 2 * p) / 4, 1.0 / (p + 4)) * pow (n, 1.0 / (p + 4)); } double p2 = p / 2.0; double beta2 = *beta * *beta, beta4 = beta2 * beta2, beta8 = beta4 * beta4; double gamma = 1 + 2 * beta2, gamma2 = gamma * gamma, gamma4 = gamma2 * gamma2; double delta = 1.0 + beta2 * (4 + 3 * beta2), delta2 = delta * delta; double prob = NUMundefined; *tnb = *lnmu = *lnvar = NUMundefined; if (n < 2 || p < 1) { return prob; } autoNUMvector zero (1, p); autoNUMmatrix covar (1, p, 1, p); autoNUMmatrix x (NUMmatrix_copy (data, 1, n, 1, p), 1, 1); NUMcentreColumns (x.peek(), 1, n, 1, p, NULL); // x - xmean NUMcovarianceFromColumnCentredMatrix (x.peek(), n, p, 0, covar.peek()); try { NUMlowerCholeskyInverse (covar.peek(), p, NULL); double djk, djj, sumjk = 0, sumj = 0; double b1 = beta2 / 2, b2 = b1 / (1.0 + beta2); /* Heinze & Wagner (1997), page 3 We use d[j][k] = ||Y[j]-Y[k]||^2 = (Y[j]-Y[k])'S^(-1)(Y[j]-Y[k]) So d[j][k]= d[k][j] and d[j][j] = 0 */ for (long j = 1; j <= n; j++) { for (long k = 1; k < j; k++) { djk = NUMmahalanobisDistance_chi (covar.peek(), x[j], x[k], p, p); sumjk += 2 * exp (-b1 * djk); // factor 2 because d[j][k] == d[k][j] } sumjk += 1; // for k == j djj = NUMmahalanobisDistance_chi (covar.peek(), x[j], zero.peek(), p, p); sumj += exp (-b2 * djj); } *tnb = (1.0 / n) * sumjk - 2.0 * pow (1.0 + beta2, - p2) * sumj + n * pow (gamma, - p2); // n * } catch (MelderError) { Melder_clearError (); *tnb = 4 * n; } double mu = 1.0 - pow (gamma, -p2) * (1.0 + p * beta2 / gamma + p * (p + 2) * beta4 / (2 * gamma2)); double var = 2.0 * pow (1 + 4 * beta2, -p2) + 2.0 * pow (gamma, -p) * (1.0 + 2 * p * beta4 / gamma2 + 3 * p * (p + 2) * beta8 / (4 * gamma4)) - 4.0 * pow (delta, -p2) * (1.0 + 3 * p * beta4 / (2 * delta) + p * (p + 2) * beta8 / (2 * delta2)); double mu2 = mu * mu; *lnmu = log (sqrt (mu2 * mu2 / (mu2 + var))); *lnvar = sqrt (log ( (mu2 + var) / mu2)); prob = NUMlogNormalQ (*tnb, *lnmu, *lnvar); return prob; } /*************** Hz <--> other freq reps *********************/ double NUMmelToHertz3 (double mel) { if (mel < 0) { return NUMundefined; } return mel < 1000 ? mel : 1000 * (exp (mel * log10 (2) / 1000) - 1); } double NUMhertzToMel3 (double hz) { if (hz < 0) { return NUMundefined; } return hz < 1000 ? hz : 1000 * log10 (1 + hz / 1000) / log10 (2); } double NUMmelToHertz2 (double mel) { if (mel < 0) { return NUMundefined; } return 700 * (pow (10.0, mel / 2595.0) - 1); } double NUMhertzToMel2 (double hz) { if (hz < 0) { return NUMundefined; } return 2595 * log10 (1 + hz / 700); } double NUMhertzToBark_traunmueller (double hz) { if (hz < 0) { return NUMundefined; } return 26.81 * hz / (1960 + hz) - 0.53; } double NUMbarkToHertz_traunmueller (double bark) { if (bark < 0 || bark > 26.28) { return NUMundefined; } return 1960 * (bark + 0.53) / (26.28 - bark); } double NUMbarkToHertz_schroeder (double bark) { return 650.0 * sinh (bark / 7.0); } double NUMbarkToHertz_zwickerterhardt (double hz) { if (hz < 0) { return NUMundefined; } return 13 * atan (0.00076 * hz) + 3.5 * atan (hz / 7500); } double NUMhertzToBark_schroeder (double hz) { double h650; if (hz < 0) { return NUMundefined; } h650 = hz / 650; return 7.0 * log (h650 + sqrt (1 + h650 * h650)); } double NUMbarkToHertz2 (double bark) { if (bark < 0) { return NUMundefined; } return 650.0 * sinh (bark / 7.0); } double NUMhertzToBark2 (double hz) { if (hz < 0) { return NUMundefined; } double h650 = hz / 650; return 7.0 * log (h650 + sqrt (1 + h650 * h650)); } double NUMbladonlindblomfilter_amplitude (double zc, double z) { double dz = zc - z + 0.474; return pow (10, 1.581 + 0.75 * dz - 1.75 * sqrt (1 + dz * dz)); } double NUMsekeyhansonfilter_amplitude (double zc, double z) { double dz = zc - z - 0.215; return pow (10, 0.7 - 0.75 * dz - 1.75 * sqrt (0.196 + dz * dz)); } double NUMtriangularfilter_amplitude (double fl, double fc, double fh, double f) { double a = 0; if (f > fl && f < fh) { a = f < fc ? (f - fl) / (fc - fl) : (fh - f) / (fh - fc); /* Normalize such that area under the filter is always 1. ??? a /= 2 * (fh - fl);*/ } return a; } double NUMformantfilter_amplitude (double fc, double bw, double f) { double dq = (fc * fc - f * f) / (bw * f); return 1.0 / (dq * dq + 1.0); } /* Childers (1978), Modern Spectrum analysis, IEEE Press, 252-255) */ /* work[1..n+n+n]; b1 = & work[1]; b2 = & work[n+1]; aa = & work[n+n+1]; for (i=1; i<=n+n+n; i++) work[i]=0; */ int NUMburg (double x[], long n, double a[], int m, double *xms) { for (long j = 1; j <= m; j++) { a[j] = 0; } autoNUMvector b1 (1, n); autoNUMvector b2 (1, n); autoNUMvector aa (1, m); // (3) double p = 0.0; for (long j = 1; j <= n; j++) { p += x[j] * x[j]; } *xms = p / n; if (*xms <= 0) { return 0; // warning empty } // (9) b1[1] = x[1]; b2[n - 1] = x[n]; for (long j = 2; j <= n - 1; j++) { b1[j] = b2[j - 1] = x[j]; } for (long i = 1; i <= m; i++) { // (7) double num = 0.0, denum = 0.0; for (long j = 1; j <= n - i; j++) { num += b1[j] * b2[j]; denum += b1[j] * b1[j] + b2[j] * b2[j]; } if (denum <= 0) { return 0; // warning ill-conditioned } a[i] = 2.0 * num / denum; // (10) *xms *= 1.0 - a[i] * a[i]; // (5) for (long j = 1; j <= i - 1; j++) { a[j] = aa[j] - a[i] * aa[i - j]; } if (i < m) { // (8) Watch out: i -> i+1 for (long j = 1; j <= i; j++) { aa[j] = a[j]; } for (long j = 1; j <= n - i - 1; j++) { b1[j] -= aa[i] * b2[j]; b2[j] = b2[j + 1] - aa[i] * b1[j + 1]; } } } return 1; } void NUMdmatrix_to_dBs (double **m, long rb, long re, long cb, long ce, double ref, double factor, double floor) { double ref_db, factor10 = factor * 10; double max = m[rb][cb], min = max; Melder_assert (ref > 0 && factor > 0 && rb <= re && cb <= ce); for (long i = rb; i <= re; i++) { for (long j = cb; j <= ce; j++) { if (m[i][j] > max) { max = m[i][j]; } else if (m[i][j] < min) { min = m[i][j]; } } } if (max < 0 || min < 0) Melder_throw ("NUMdmatrix_to_dBs: all " "matrix elements must be positive."); ref_db = factor10 * log10 (ref); for (long i = rb; i <= re; i++) { for (long j = cb; j <= ce; j++) { double mij = floor; if (m[i][j] > 0) { mij = factor10 * log10 (m[i][j]) - ref_db; if (mij < floor) { mij = floor; } } m[i][j] = mij; } } } double **NUMcosinesTable (long first, long last, long npoints) { Melder_assert (0 < first && first <= last && npoints > 0); autoNUMmatrix m (first, last, 1, npoints); for (long i = first; i <= last; i++) { double f = i * NUMpi / npoints; for (long j = 1; j <= npoints; j++) { m[i][j] = cos (f * (j - 0.5)); } } return m.transfer(); } void NUMspline (double x[], double y[], long n, double yp1, double ypn, double y2[]) { autoNUMvector u (1, n - 1); if (yp1 > 0.99e30) { y2[1] = u[1] = 0.0; } else { y2[1] = -0.5; u[1] = (3.0 / (x[2] - x[1])) * ( (y[2] - y[1]) / (x[2] - x[1]) - yp1); } for (long i = 2; i <= n - 1; i++) { double sig = (x[i] - x[i - 1]) / (x[i + 1] - x[i - 1]); double p = sig * y2[i - 1] + 2.0; y2[i] = (sig - 1.0) / p; u[i] = (y[i + 1] - y[i]) / (x[i + 1] - x[i]) - (y[i] - y[i - 1]) / (x[i] - x[i - 1]); u[i] = (6.0 * u[i] / (x[i + 1] - x[i - 1]) - sig * u[i - 1]) / p; } double qn, un; if (ypn > 0.99e30) { qn = un = 0.0; } else { qn = 0.5; un = (3.0 / (x[n] - x[n - 1])) * (ypn - (y[n] - y[n - 1]) / (x[n] - x[n - 1])); } y2[n] = (un - qn * u[n - 1]) / (qn * y2[n - 1] + 1.0); for (long k = n - 1; k >= 1; k--) { y2[k] = y2[k] * y2[k + 1] + u[k]; } } void NUMsplint (double xa[], double ya[], double y2a[], long n, double x, double *y) { long klo = 1, khi = n; while (khi - klo > 1) { long k = (khi + klo) >> 1; if (xa[k] > x) { khi = k; } else { klo = k; } } double h = xa[khi] - xa[klo]; if (h == 0.0) { Melder_throw ("NUMsplint: bad input value."); } double a = (xa[khi] - x) / h; double b = (x - xa[klo]) / h; *y = a * ya[klo] + b * ya[khi] + ( (a * a * a - a) * y2a[klo] + (b * b * b - b) * y2a[khi]) * (h * h) / 6.0; } double NUMsinc (const double x) { struct gsl_sf_result_struct result; int status = gsl_sf_sinc_e (x / NUMpi, &result); return status == GSL_SUCCESS ? result. val : NUMundefined; } double NUMsincpi (const double x) { struct gsl_sf_result_struct result; int status = gsl_sf_sinc_e (x, &result); return status == GSL_SUCCESS ? result. val : NUMundefined; } /* Does the line segment from (x1,y1) to (x2,y2) intersect with the line segment from (x3,y3) to (x4,y4)? */ int NUMdoLineSegmentsIntersect (double x1, double y1, double x2, double y2, double x3, double y3, double x4, double y4) { int o11 = NUMgetOrientationOfPoints (x1, y1, x2, y2, x3, y3); int o12 = NUMgetOrientationOfPoints (x1, y1, x2, y2, x4, y4); int o21 = NUMgetOrientationOfPoints (x3, y3, x4, y4, x1, y1); int o22 = NUMgetOrientationOfPoints (x3, y3, x4, y4, x2, y2); return ( (o11 * o12 < 0) && (o21 * o22 < 0)) || (o11 *o12 *o21 *o22 == 0); } int NUMgetOrientationOfPoints (double x1, double y1, double x2, double y2, double x3, double y3) { int orientation; double dx2 = x2 - x1, dy2 = y2 - y1; double dx3 = x3 - x1, dy3 = y3 - y1; if (dx2 * dy3 > dy2 * dx3) { orientation = 1; } else if (dx2 * dy3 < dy2 * dx3) { orientation = -1; } else { if ( (dx2 * dx3 < 0) || (dy2 * dy3 < 0)) { orientation = -1; } else if ( (dx2 * dx2 + dy2 * dy2) >= (dx3 * dx3 + dy3 * dy3)) { orientation = 0; } else { orientation = 1; } } return orientation; } int NUMgetIntersectionsWithRectangle (double x1, double y1, double x2, double y2, double xmin, double ymin, double xmax, double ymax, double *xi, double *yi) { double x[6], y[6], t; long ni = 0; x[1] = x[4] = x[5] = xmin; x[2] = x[3] = xmax; y[1] = y[2] = y[5] = ymin; y[3] = y[4] = ymax; /* Calculate intersection of line segment through p1=(x1,y1) to p2(x2,y2) with line segment through p3=(x3,y3) to p4=(x4,y4). Parametrisation of the lines: l1 = p1 + s (p2 - p1), s in (-inf,+inf) l2 = p3 + t (p4 - p3), t in (-inf,+inf). When s and t are in [0,1] we have line segments between the points. At the intersection l1 == l2. We get for the x and y coordinates: x1 + s (x2 - x1) = x3 + t (x4 - x3).............(1) y1 + s (y2 - y1) = y3 + t (y4 - y3).............(2) Multiply (1)*(y2 - y1) and (2)*(x2 - x1): x1 (y2 - y1) + s (x2 - x1)(y2 - y1) = x3 (y2 - y1) + t (x4 - x3)(y2 - y1).......(3) y1 (x2 - x1) + s (y2 - y1)(x2 - x1) = y3 (x2 - x1) + t (y4 - y3)(x2 - x1).......(4) (3)-(4) with y21 = y2 -y1, x21 = x2 - x1, x43 = x4 - x3, ... x1 y21 - y1 x21 = x3 y21 - y3 x21 +t (x43 y21 - y43 x21) Combining: y31 x21 - x31 y21 = t (x43 y21 - y43 x21) Therefor at the intersection we have: t = (y31 x21 - x31 y21) / (x43 y21 - y43 x21) If (x43 y21 - y43 x21) == 0 There is no intersection. If (t < 0 || t >= 1) No intersection in the segment l2 To count intersections in a corner only once we have t < 0 instead of t <= 0! */ for (long i = 1; i <= 4; i++) { double denom = (x[i + 1] - x[i]) * (y2 - y1) - (y[i + 1] - y[i]) * (x2 - x1); if (denom == 0) { continue; } /* We have an intersection. */ t = ( (y[i] - y1) * (x2 - x1) - (x[i] - x1) * (y2 - y1)) / denom; if (t < 0 || t >= 1) { continue; } /* Intersection is within rectangle side. */ ni++; if (ni > 2) { Melder_throw ("Too many intersections."); } xi[ni] = x[i] + t * (x[i + 1] - x[i]); yi[ni] = y[i] + t * (y[i + 1] - y[i]); } return ni; } int NUMclipLineWithinRectangle (double xl1, double yl1, double xl2, double yl2, double xr1, double yr1, double xr2, double yr2, double *xo1, double *yo1, double *xo2, double *yo2) { int ncrossings = 0; bool xswap, yswap; double a, b, x, y, t, xc[5], yc[5], xmin, xmax, ymin, ymax; *xo1 = xl1; *yo1 = yl1; *xo2 = xl2; *yo2 = yl2; // This test first because we expect the majority of the tested segments to be // within the rectangle if (xl1 >= xr1 && xl1 <= xr2 && yl1 >= yr1 && yl1 <= yr2 && xl2 >= xr1 && xl2 <= xr2 && yl2 >= yr1 && yl2 <= yr2) { return 1; } // All lines that are completely outside the rectangle if ( (xl1 <= xr1 && xl2 <= xr1) || (xl1 >= xr2 && xl2 >= xr2) || (yl1 <= yr1 && yl2 <= yr1) || (yl1 >= yr2 && yl2 >= yr2)) { return 0; } // At least line spans (part of) the rectangle. // Get extremes in x and y of the line for easy testing further on. if (xl1 < xl2) { xmin = xl1; xmax = xl2; xswap = false; } else { xmin = xl2; xmax = xl1; xswap = true; } if (yl1 < yl2) { ymin = yl1; ymax = yl2; yswap = false; } else { ymin = yl2; ymax = yl1; yswap = true; } bool hline = yl1 == yl2, vline = xl1 == xl2; if (hline) { if (xmin < xr1) { *xo1 = xr1; } if (xmax > xr2) { *xo2 = xr2; } if (xswap) { t = *xo1; *xo1 = *xo2; *xo2 = t; } return 1; } if (vline) { if (ymin < yr1) { *yo1 = yr1; } if (ymax > yr2) { *yo2 = yr2; } if (yswap) { t = *yo1; *yo1 = *yo2; *yo2 = t; } return 1; } // Now we know that the line from (x1,y1) to (x2,y2) is neither horizontal nor vertical. // Parametrize it as y = ax + b a = (yl1 - yl2) / (xl1 - xl2); b = yl1 - a * xl1; // To determine the crossings we have to avoid counting the crossings in a corner twice. // Therefore we test the corners inclusive (..<=..<=..) on the vertical borders of the rectangle // and exclusive (..<..<) at the horizontal borders. y = a * xr1 + b; // Crossing at y with left border: x = xr1 if (y >= yr1 && y <= yr2 && xmin < xr1) { // Within vertical range? ncrossings++; xc[ncrossings] = xr1; yc[ncrossings] = y; xc[2] = xmax; yc[2] = xl1 > xl2 ? yl1 : yl2; } x = (yr2 - b) / a; // Crossing at x with top border: y = yr2 if (x > xr1 && x < xr2 && ymax > yr2) { // Within horizontal range? ncrossings++; xc[ncrossings] = x; yc[ncrossings] = yr2; if (ncrossings == 1) { yc[2] = ymin; xc[2] = yl1 < yl2 ? xl1 : xl2; } } y = a * xr2 + b; // Crossing at y with right border: x = xr2 if (y >= yr1 && y <= yr2 && xmax > xr2) { // Within vertical range? ncrossings++; xc[ncrossings] = xr2; yc[ncrossings] = y; if (ncrossings == 1) { xc[2] = xmin; yc[2] = xl1 < xl2 ? yl1 : yl2; } } x = (yr1 - b) / a; // Crossing at x with bottom border: y = yr1 if (x > xr1 && x < xr2 && ymin < yr1) { ncrossings++; xc[ncrossings] = x; yc[ncrossings] = yr1; if (ncrossings == 1) { yc[2] = ymax; xc[2] = yl1 > yl2 ? xl1 : xl2; } } if (ncrossings == 0) { return 0; } if (ncrossings == 1 || ncrossings == 2) { // if start and endpoint of line are outside rectangle and ncrossings == 1, // than the line only touches. if (ncrossings == 1 && (xl1 < xr1 || xl1 > xr2 || yl1 < yr1 || yl1 > yr2) && (xl2 < xr1 || xl2 > xr2 || yl2 < yr1 || yl2 > yr2)) { return 0; } if ( (xc[1] > xc[2] && ! xswap) || (xc[1] < xc[2] && xswap)) { t = xc[1]; xc[1] = xc[2]; xc[2] = t; t = yc[1]; yc[1] = yc[2]; yc[2] = t; } *xo1 = xc[1]; *yo1 = yc[1]; *xo2 = xc[2]; *yo2 = yc[2]; } else { Melder_throw ("Too many crossings found."); } return 1; } void NUMgetEllipseBoundingBox (double a, double b, double cospsi, double *width, double *height) { Melder_assert (cospsi >= -1 && cospsi <= 1); if (cospsi == 1) { /* a-axis along x-axis */ *width = a; *height = b; } else if (cospsi == 0) { /* a-axis along y-axis */ *width = b; *height = a; } else { double psi = acos (cospsi), sn = sin (psi); double phi = atan2 (-b * sn, a * cospsi); *width = fabs (a * cospsi * cos (phi) - b * sn * sin (phi)); phi = atan2 (b * cospsi , a * sn); *height = fabs (a * sn * cos (phi) + b * cospsi * sin (phi)); } } /* Closely modelled after the netlib code by Oleg Keselyov. */ double NUMminimize_brent (double (*f) (double x, void *closure), double a, double b, void *closure, double tol, double *fx) { double x, v, fv, w, fw; const double golden = 1 - NUM_goldenSection; const double sqrt_epsilon = sqrt (NUMfpp -> eps); long itermax = 60; Melder_assert (tol > 0 && a < b); /* First step - golden section */ v = a + golden * (b - a); fv = (*f) (v, closure); x = v; w = v; *fx = fv; fw = fv; for (long iter = 1; iter <= itermax; iter++) { double range = b - a; double middle_range = (a + b) / 2; double tol_act = sqrt_epsilon * fabs (x) + tol / 3; double new_step; /* Step at this iteration */ if (fabs (x - middle_range) + range / 2 <= 2 * tol_act) { return x; } /* Obtain the golden section step */ new_step = golden * (x < middle_range ? b - x : a - x); /* Decide if the parabolic interpolation can be tried */ if (fabs (x - w) >= tol_act) { /* Interpolation step is calculated as p/q; division operation is delayed until last moment. */ double p, q, t; t = (x - w) * (*fx - fv); q = (x - v) * (*fx - fw); p = (x - v) * q - (x - w) * t; q = 2 * (q - t); if (q > 0) { p = -p; } else { q = -q; } /* If x+p/q falls in [a,b], not too close to a and b, and isn't too large, it is accepted. If p/q is too large then the golden section procedure can reduce [a,b] range. */ if (fabs (p) < fabs (new_step * q) && p > q * (a - x + 2 * tol_act) && p < q * (b - x - 2 * tol_act)) { new_step = p / q; } } /* Adjust the step to be not less than tolerance. */ if (fabs (new_step) < tol_act) { new_step = new_step > 0 ? tol_act : - tol_act; } /* Obtain the next approximation to min and reduce the enveloping range */ { double t = x + new_step; /* Tentative point for the min */ double ft = (*f) (t, closure); /* If t is a better approximation, reduce the range so that t would fall within it. If x remains the best, reduce the range so that x falls within it. */ if (ft <= *fx) { if (t < x) { b = x; } else { a = x; } v = w; w = x; x = t; fv = fw; fw = *fx; *fx = ft; } else { if (t < x) { a = t; } else { b = t; } if (ft <= fw || w == x) { v = w; w = t; fv = fw; fw = ft; } else if (ft <= fv || v == x || v == w) { v = t; fv = ft; } } } } Melder_warning (L"NUMminimize_brent: maximum number of iterations (", Melder_integer (itermax), L") exceeded."); return x; } /* probs is probability vector, i.e. all 0 <= probs[i] <= 1 and sum(i=1;i=nprobs, probs[i])= 1 p is a probability */ long NUMgetIndexFromProbability (double *probs, long nprobs, double p) { long index = 1; double psum = probs[index]; while (p > psum && index < nprobs) { psum += probs[++index]; } return index; } // IEEE: Programs for digital signal processing section 4.3 LPTRN // lpc[1..n] to rc[1..n] void NUMlpc_lpc_to_rc (double *lpc, long p, double *rc) { autoNUMvector b (1, p); autoNUMvector a (NUMvector_copy (lpc, 1, p), 1); for (long m = p; m > 0; m--) { rc[m] = a[m]; if (fabs (rc[m]) > 1) { Melder_throw ("Relection coefficient [", Melder_integer(m), "] larger 1."); } for (long i = 1; i < m; i++) { b[i] = a[i]; } for (long i = 1; i < m; i++) { a[i] = (b[i] - rc[m] * b[m - i]) / (1.0 - rc[m] * rc[m]); } } } void NUMlpc_rc_to_area2 (double *rc, long n, double *area); void NUMlpc_rc_to_area2 (double *rc, long n, double *area) { double s = 0.0001; /* 1.0 cm^2 at glottis */ for (long i = n; i > 0; i--) { s *= (1.0 + rc[i]) / (1.0 - rc[i]); area[i] = s; } } void NUMlpc_area_to_lpc2 (double *area, long n, double *lpc); void NUMlpc_area_to_lpc2 (double *area, long n, double *lpc) { // from area to reflection coefficients autoNUMvector rc (1, n); // normalisation: area[n+1] = 0.0001 for (long j = n; j > 0; j--) { double ar = area[j+1] / area[j]; rc[j] = (1 - ar) / (1 + ar); } // LPTRAN works from mouth to lips: for (long j = 1; j <= n; j++) { lpc[j] = rc[n - j + 1]; } for (long j = 2; j <= n; j++) { long nh = j / 2; double q = rc[j]; for (long k = 1; k <= nh; k++) { double at = lpc[k] + q * lpc[j - k]; lpc[j - k] += q * lpc[k]; lpc[k] = at; } } } void NUMlpc_lpc_to_rc2 (double *lpc, long m, double *rc); void NUMlpc_lpc_to_rc2 (double *lpc, long m, double *rc) { // klopt nog niet NUMvector_copyElements (lpc, rc, 1, m); for (long j = 2; j <= m; j++) { long jb = m + 1 - j; long mh = (jb + 1) / 2; double rct = rc[jb+1]; double d = 1 - rct * rct; for (long k = 1; k <= mh; k++) { rc[k] *= (1 - rct) / d; } } } // area[1] at lips generates n+1 areas from n rc's void NUMlpc_rc_to_area (double *rc, long m, double *area) { area[m+1] = 0.0001; /* 1.0 cm^2 */ for (long j = 1; j <= m; j++) { double ar = (1 - rc[m+1-j]) / (1 + rc[m+1-j]); area[m+1-j] = area[m+2-j] / ar; } } // returns m-1 reflection coefficients from m areas void NUMlpc_area_to_rc (double *area, long m, double *rc) { for (long j = 1; j <= m - 1; j++) { double ar = area[j+1] / area[j]; rc[j] = (1 - ar) / (1 + ar); } } void NUMlpc_rc_to_lpc (double *rc, long m, double *lpc); void NUMlpc_rc_to_lpc (double *rc, long m, double *lpc) { NUMvector_copyElements (rc, lpc, 1, m); for (long j = 2; j <= m; j++) { for (long k = 1; k <= j / 2; k++) { double at = lpc[k] + rc[j] * lpc[j - k]; lpc[j - k] += rc[j] * lpc[k]; lpc[k] = at; } } } void NUMlpc_area_to_lpc (double *area, long m, double *lpc) { // from area to reflection coefficients autoNUMvector rc (1, m); // normalisation: area[n+1] = 0.0001 NUMlpc_area_to_rc (area, m, rc.peek()); NUMlpc_rc_to_lpc (rc.peek(), m - 1, lpc); } void NUMlpc_lpc_to_area (double *lpc, long m, double *area) { autoNUMvector rc (1, m); NUMlpc_lpc_to_rc (lpc, m, rc.peek()); NUMlpc_rc_to_area (rc.peek(), m, area); } #undef MAX #undef MIN #undef SIGN /* End of file NUM2.c */ sources_5316/dwsys/Eigen.cpp0000644000176700017670000003744511725125743014653 0ustar paulpaul/* Eigen.c * * Copyright (C) 1993-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010719 djmw 20020402 GPL header. djmw 20030701 Modified sorting in Eigen_initFromSquareRootPair. djmw 20030703 Added Eigens_alignEigenvectors. djmw 20030708 Corrected syntax error in Eigens_alignEigenvectors. djmw 20030812 Corrected memory bug in Eigen_initFromSymmetricMatrix. djmw 20030825 Removed praat_USE_LAPACK external variable. djmw 20031101 Documentation djmw 20031107 Moved NUMdmatrix_transpose to NUM2.c djmw 20031210 Added rowLabels to Eigen_drawEigenvector and Eigen_and_Strings_drawEigenvector djmw 20030322 Extra test in Eigen_initFromSquareRootPair. djmw 20040329 Added fractionOfTotal and cumulative parameters in Eigen_drawEigenvalues_scree. djmw 20040622 Less horizontal labels in Eigen_drawEigenvector. djmw 20050706 Shortened horizontal offsets in Eigen_drawEigenvalues from 1 to 0.5 djmw 20051204 Eigen_initFromSquareRoot adapted for nrows < ncols djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20110304 Thing_new */ #include "Eigen.h" #include "NUMmachar.h" #include "NUMlapack.h" #include "NUMclapack.h" #include "NUM2.h" #include "SVD.h" #include "oo_DESTROY.h" #include "Eigen_def.h" #include "oo_COPY.h" #include "Eigen_def.h" #include "oo_EQUAL.h" #include "Eigen_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Eigen_def.h" #include "oo_WRITE_TEXT.h" #include "Eigen_def.h" #include "oo_READ_TEXT.h" #include "Eigen_def.h" #include "oo_WRITE_BINARY.h" #include "Eigen_def.h" #include "oo_READ_BINARY.h" #include "Eigen_def.h" #include "oo_DESCRIPTION.h" #include "Eigen_def.h" Thing_implement (Eigen, Data, 0); #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) #define SWAP(a,b) {temp=(a);(a)=(b);(b)=temp;} static void Graphics_ticks (Graphics g, double min, double max, int hasNumber, int hasTick, int hasDottedLine, int integers) { double range = max - min, scale = 1, tick = min, dtick = 1; if (range == 0) { return; } else if (range > 1) { while (range / scale > 10) { scale *= 10; } range /= scale; } else { while (range / scale < 10) { scale /= 10; } range *= scale; } if (range < 3) { dtick = 0.5; } dtick *= scale; tick = dtick * floor (min / dtick); if (tick < min) { tick += dtick; } while (tick <= max) { double num = integers ? floor (tick + 0.5) : tick; Graphics_markBottom (g, num, hasNumber, hasTick, hasDottedLine, NULL); tick += dtick; } } void Eigen_init (I, long numberOfEigenvalues, long dimension) { iam (Eigen); my numberOfEigenvalues = numberOfEigenvalues; my dimension = dimension; my eigenvalues = NUMvector (1, numberOfEigenvalues); my eigenvectors = NUMmatrix (1, numberOfEigenvalues, 1, dimension); } /* Solve: (A'A - lambda)x = 0 for eigenvalues lambda and eigenvectors x. svd(A) = UDV' => A'A = (UDV')'(UDV') = VD^2V' (VD^2V'-lambda)x = 0 => (D^2 - lambda)V'x = 0 => solution V'x = I => x = V Eigenvectors: the columns of the matrix V Eigenvalues: D_i^2 */ void Eigen_initFromSquareRoot (I, double **a, long numberOfRows, long numberOfColumns) { iam (Eigen); long numberOfZeroed, numberOfEigenvalues; long nsv = MIN (numberOfRows, numberOfColumns); my dimension = numberOfColumns; autoSVD svd = SVD_create_d (a, numberOfRows, numberOfColumns); /* Make sv's that are too small zero. These values occur automatically when the rank of A'A < numberOfColumns. This could occur when for example numberOfRows <= numberOfColumns. (n points in an n-dimensional space define maximally an n-1 dimensional surface for which we maximally need an n-1 dimensional basis.) */ numberOfZeroed = SVD_zeroSmallSingularValues (svd.peek(), 0); numberOfEigenvalues = nsv - numberOfZeroed; Eigen_init (me, numberOfEigenvalues, numberOfColumns); long k = 0; for (long i = 1; i <= nsv; i++) { double t = svd -> d[i]; if (t > 0) { my eigenvalues[++k] = t * t; for (long j = 1; j <= numberOfColumns; j++) { my eigenvectors[k][j] = svd -> v[j][i]; } } } Eigen_sort (me); } void Eigen_initFromSquareRootPair (I, double **a, long numberOfRows, long numberOfColumns, double **b, long numberOfRows_b) { iam (Eigen); double *u = NULL, *v = NULL, maxsv2 = -10; char jobu = 'N', jobv = 'N', jobq = 'Q'; long k, ll, m = numberOfRows, n = numberOfColumns, p = numberOfRows_b; long lda = m, ldb = p, ldu = lda, ldv = ldb, ldq = n; long lwork = MAX (MAX (3 * n, m), p) + n, info; /* Melder_assert (numberOfRows >= numberOfColumns || numberOfRows_b >= numberOfColumns);*/ my dimension = numberOfColumns; autoNUMvector alpha (1, n); autoNUMvector beta (1, n); autoNUMvector work (1, lwork); autoNUMvector iwork (1, n); autoNUMmatrix q (1, n, 1, n); autoNUMmatrix ac (NUMmatrix_transpose (a, numberOfRows, numberOfColumns), 1, 1); autoNUMmatrix bc (NUMmatrix_transpose (b, numberOfRows_b, numberOfColumns), 1, 1); (void) NUMlapack_dggsvd (&jobu, &jobv, &jobq, &m, &n, &p, &k, &ll, &ac[1][1], &lda, &bc[1][1], &ldb, &alpha[1], &beta[1], u, &ldu, v, &ldv, &q[1][1], &ldq, &work[1], &iwork[1], &info); if (info != 0) { Melder_throw ("dggsvd fails."); } /* Calculate the eigenvalues (alpha[i]/beta[i])^2 and store in alpha[i]. */ maxsv2 = -1; for (long i = k + 1; i <= k + ll; i++) { double t = alpha[i] / beta[i]; alpha[i] = t * t; if (alpha[i] > maxsv2) { maxsv2 = alpha[i]; } } /* Deselect the eigenvalues < eps * max_eigenvalue. */ n = 0; for (long i = k + 1; i <= k + ll; i++) { if (alpha[i] < NUMfpp -> eps * maxsv2) { n++; alpha[i] = -1; } } if (ll - n < 1) { Melder_throw ("No eigenvectors can be found. Matrix too singular."); } Eigen_init (me, ll - n, numberOfColumns); long ii = 0; for (long i = k + 1; i <= k + ll; i++) { if (alpha[i] == -1) { continue; } my eigenvalues[++ii] = alpha[i]; for (long j = 1; j <= numberOfColumns; j++) { my eigenvectors[ii][j] = q[i][j]; } } Eigen_sort (me); NUMnormalizeRows (my eigenvectors, my numberOfEigenvalues, numberOfColumns, 1); } void Eigen_initFromSymmetricMatrix_f (I, float **a, long n) { iam (Eigen); autoNUMmatrix m (1, n, 1, n); for (long i = 1; i <= n; i++) { for (long j = 1; j <= n; j++) { m[i][j] = a[i][j]; } } Eigen_initFromSymmetricMatrix (me, m.peek(), n); } void Eigen_initFromSymmetricMatrix (I, double **a, long n) { iam (Eigen); double wt[1], temp; char jobz = 'V', uplo = 'U'; long lwork = -1, info; my dimension = my numberOfEigenvalues = n; if (my eigenvectors == NULL) { Eigen_init (me, n, n); } NUMmatrix_copyElements (a, my eigenvectors, 1, n, 1, n); /* Get size of work array */ (void) NUMlapack_dsyev (&jobz, &uplo, &n, &my eigenvectors[1][1], &n, &my eigenvalues[1], wt, &lwork, &info); if (info != 0) { Melder_throw ("dsyev fails"); } lwork = wt[0]; autoNUMvector work (0L, lwork); (void) NUMlapack_dsyev (&jobz, &uplo, &n, &my eigenvectors[1][1], &n, &my eigenvalues[1], work.peek(), &lwork, &info); if (info != 0) { Melder_throw ("dsyev fails"); } /* We want descending order instead of ascending. */ for (long i = 1; i <= n / 2; i++) { long ilast = n - i + 1; SWAP (my eigenvalues[i], my eigenvalues[ilast]) for (long j = 1; j <= n; j++) { SWAP (my eigenvectors[i][j], my eigenvectors[ilast][j]) } } } Eigen Eigen_create (long numberOfEigenvalues, long dimension) { try { autoEigen me = Thing_new (Eigen); Eigen_init (me.peek(), numberOfEigenvalues, dimension); return me.transfer(); } catch (MelderError) { Melder_throw ("Eigen not created."); } } long Eigen_getNumberOfEigenvectors (I) { iam (Eigen); return my numberOfEigenvalues; } double Eigen_getEigenvectorElement (I, long ivec, long element) { iam (Eigen); if (ivec > my numberOfEigenvalues || element < 1 || element > my dimension) { return NUMundefined; } return my eigenvectors[ivec][element]; } long Eigen_getDimensionOfComponents (I) { iam (Eigen); return my dimension; } double Eigen_getSumOfEigenvalues (I, long from, long to) { iam (Eigen); if (from < 1) { from = 1; } if (to < 1) { to = my numberOfEigenvalues; } if (to > my numberOfEigenvalues || from > to) { return NUMundefined; } double sum = 0; for (long i = from; i <= to; i++) { sum += my eigenvalues[i]; } return sum; } double Eigen_getCumulativeContributionOfComponents (I, long from, long to) { iam (Eigen); double partial = 0, sum = 0; if (to == 0) { to = my numberOfEigenvalues; } if (from > 0 && to <= my numberOfEigenvalues && from <= to) { for (long i = 1; i <= my numberOfEigenvalues; i++) { sum += my eigenvalues[i]; if (i >= from && i <= to) { partial += my eigenvalues[i]; } } } return sum > 0 ? partial / sum : 0; } long Eigen_getDimensionOfFraction (I, double fraction) { iam (Eigen); double sum = Eigen_getSumOfEigenvalues (me, 0, 0); if (sum == 0) { return 1; } long n = 1; double p = my eigenvalues[1]; while (p / sum < fraction && n < my numberOfEigenvalues) { p += my eigenvalues[++n]; } return n; } void Eigen_sort (I) { iam (Eigen); double temp, *e = my eigenvalues, **v = my eigenvectors; for (long i = 1; i < my numberOfEigenvalues; i++) { long k; double emax = e[k = i]; for (long j = i + 1; j <= my numberOfEigenvalues; j++) { if (e[j] > emax) { emax = e[k = j]; } } if (k != i) { /* Swap eigenvalues and eigenvectors */ SWAP (e[i], e[k]) for (long j = 1; j <= my dimension; j++) { SWAP (v[i][j], v[k][j]) } } } } void Eigen_invertEigenvector (I, long ivec) { iam (Eigen); if (ivec < 1 || ivec > my numberOfEigenvalues) { return; } for (long j = 1; j <= my dimension; j++) { my eigenvectors[ivec][j] = - my eigenvectors[ivec][j]; } } void Eigen_drawEigenvalues (I, Graphics g, long first, long last, double ymin, double ymax, int fractionOfTotal, int cumulative, double size_mm, const wchar_t *mark, int garnish) { iam (Eigen); double xmin = first, xmax = last, scale = 1, sumOfEigenvalues = 0; long i; if (first < 1) { first = 1; } if (last < 1 || last > my numberOfEigenvalues) { last = my numberOfEigenvalues; } if (last <= first) { first = 1; last = my numberOfEigenvalues; } xmin = first - 0.5; xmax = last + 0.5; if (fractionOfTotal || cumulative) { sumOfEigenvalues = Eigen_getSumOfEigenvalues (me, 0, 0); if (sumOfEigenvalues <= 0) { sumOfEigenvalues = 1; } scale = sumOfEigenvalues; } if (ymax <= ymin) { ymax = Eigen_getSumOfEigenvalues (me, (cumulative ? 1 : first), first) / scale; ymin = Eigen_getSumOfEigenvalues (me, (cumulative ? 1 : last), last) / scale; if (ymin > ymax) { double tmp = ymin; ymin = ymax; ymax = tmp; } } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); for (i = first; i <= last; i++) { double accu = Eigen_getSumOfEigenvalues (me, (cumulative ? 1 : i), i); Graphics_mark (g, i, accu / scale, size_mm, mark); } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textLeft (g, 1, fractionOfTotal ? (cumulative ? L"Cumulative fractional eigenvalue" : L"Fractional eigenvalue") : (cumulative ? L"Cumulative eigenvalue" : L"Eigenvalue")); Graphics_ticks (g, first, last, 1, 1, 0, 1); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_textBottom (g, 1, L"Index"); } } void Eigen_drawEigenvector (I, Graphics g, long ivec, long first, long last, double ymin, double ymax, int weigh, double size_mm, const wchar_t *mark, int connect, wchar_t **rowLabels, int garnish) { iam (Eigen); double xmin = first, xmax = last, *vec, w; if (ivec < 1 || ivec > my numberOfEigenvalues) { return; } if (last <= first) { first = 1; last = my dimension; xmin = 0.5; xmax = last + 0.5; } vec = my eigenvectors[ivec]; w = weigh ? sqrt (my eigenvalues[ivec]) : 1; /* If ymax < ymin the eigenvector will automatically be drawn inverted. */ if (ymax == ymin) { NUMvector_extrema (vec, first, last, &ymin, &ymax); ymax *= w; ymin *= w; } Graphics_setInner (g); Graphics_setWindow (g, xmin, xmax, ymin, ymax); for (long i = first; i <= last; i++) { Graphics_mark (g, i, w * vec[i], size_mm, mark); if (connect && i > first) { Graphics_line (g, i - 1, w * vec[i - 1], i, w * vec[i]); } } Graphics_unsetInner (g); if (garnish) { Graphics_markBottom (g, first, 0, 1, 0, rowLabels ? rowLabels[first] : Melder_integer (first)); Graphics_markBottom (g, last, 0, 1, 0, rowLabels ? rowLabels[last] : Melder_integer (last)); Graphics_drawInnerBox (g); if (ymin * ymax < 0) { Graphics_markLeft (g, 0.0, 1, 1, 1, NULL); } Graphics_marksLeft (g, 2, 1, 1, 0); if (rowLabels == NULL) { Graphics_textBottom (g, 1, L"Element number"); } } } void Eigens_alignEigenvectors (Collection me) { if (my size < 2) { return; } Eigen e1 = (Eigen) my item[1]; double **evec1 = e1 -> eigenvectors; long nev1 = e1 -> numberOfEigenvalues; long dimension = e1 -> dimension; for (long i = 2; i <= my size; i++) { Eigen e2 = (Eigen) my item[i]; if (e2 -> dimension != dimension) { Melder_throw ("The dimension of the eigenvectors must be equal (offending object is ", i, ")."); } } /* Correlate eigenvectors. If r < 0 then mirror the eigenvector. */ for (long i = 2; i <= my size; i++) { Eigen e2 = (Eigen) my item[i]; double **evec2 = e2 -> eigenvectors; for (long j = 1; j <= MIN (nev1, e2 -> numberOfEigenvalues); j++) { double ip = 0; for (long k = 1; k <= dimension; k++) { ip += evec1[j][k] * evec2[j][k]; } if (ip < 0) { for (long k = 1; k <= dimension; k++) { evec2[j][k] = - evec2[j][k]; } } } } } static void Eigens_getAnglesBetweenSubspaces (I, thou, long ivec_from, long ivec_to, double *angles_degrees) { iam (Eigen); thouart (Eigen); long nvectors = ivec_to - ivec_from + 1; for (long i = 1; i <= nvectors; i++) { angles_degrees[i] = NUMundefined; } long nmin = my numberOfEigenvalues < thy numberOfEigenvalues ? my numberOfEigenvalues : thy numberOfEigenvalues; if (my dimension != thy dimension) { Melder_throw ("The eigenvectors must have the same dimension."); } if (ivec_from > ivec_to || ivec_from < 1 || ivec_to > nmin) { Melder_throw ("Eigenvector range too large."); } autoNUMmatrix c (1, nvectors, 1, nvectors); /* Algorithm 12.4.3 Golub & van Loan Because we deal with eigenvectors we don't have to do the QR-decomposition, the columns in the Q's are the eigenvectors. Compute C. */ for (long i = 1; i <= nvectors; i++) { for (long j = 1; j <= nvectors; j++) { for (long k = 1; k <= my dimension; k++) { c[i][j] += my eigenvectors[ivec_from + i - 1][k] * thy eigenvectors[ivec_from + j - 1][k]; } } } autoSVD svd = SVD_create_d (c.peek(), nvectors, nvectors); for (long i = 1; i <= nvectors; i++) { angles_degrees[i] = acos (svd -> d[i]) * 180 / NUMpi; } } double Eigens_getAngleBetweenEigenplanes_degrees (I, thou) { iam (Eigen); thouart (Eigen); double angles_degrees[3]; Eigens_getAnglesBetweenSubspaces (me, thee, 1, 2, angles_degrees); return angles_degrees[2]; } #undef MAX #undef MIN #undef SWAP /* End of file Eigen.c */ sources_5316/dwsys/SVD.cpp0000644000176700017670000002773411725125743014260 0ustar paulpaul/* SVD.cpp * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20010719 djmw 20020408 GPL + cosmetic changes. djmw 20020415 +SVD_synthesize. djmw 20030624 Removed NRC svd calls. djmw 20030825 Removed praat_USE_LAPACK external variable. djmw 20031018 Removed bug in SVD_solve that caused incorrect output when nrow > ncol djmw 20031101 Changed documentation in SVD_compute + bug correction in SVD_synthesize. djmw 20031111 Added GSVD_create_d. djmw 20051201 Adapt for numberOfRows < numberOfColumns djmw 20060810 Removed #include praat.h djmw 20061212 Changed info to Melder_writeLine format. djmw 20070102 Removed the #include "TableOfReal.h" djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20110304 Thing_new */ #include "SVD.h" #include "NUMlapack.h" #include "NUMmachar.h" #include "Collection.h" #include "NUMclapack.h" #include "NUMcblas.h" #include "oo_DESTROY.h" #include "SVD_def.h" #include "oo_COPY.h" #include "SVD_def.h" #include "oo_EQUAL.h" #include "SVD_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "SVD_def.h" #include "oo_WRITE_TEXT.h" #include "SVD_def.h" #include "oo_WRITE_BINARY.h" #include "SVD_def.h" #include "oo_READ_TEXT.h" #include "SVD_def.h" #include "oo_READ_BINARY.h" #include "SVD_def.h" #include "oo_DESCRIPTION.h" #include "SVD_def.h" Thing_implement (SVD, Data, 0); #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) static void NUMtranspose_d (double **m, long n); /* if A=UDV' then A' = (UDV')'=VDU' */ static void SVD_transpose (SVD me) { long tmpl = my numberOfRows; double **tmpd = my u; my u = my v; my v = tmpd; my numberOfRows = my numberOfColumns; my numberOfColumns = tmpl; } void structSVD :: v_info () { MelderInfo_writeLine2 (L"Number of rows: ", Melder_integer (numberOfRows)); MelderInfo_writeLine2 (L"Number of columns: ", Melder_integer (numberOfColumns)); } /* m >=n, mxn matrix A has svd UDV', where u is mxn, D is n and V is nxn. m < n, mxn matrix A. Consider A' with svd (UDV')'= VDU', where v is mxm, D is m and U' is mxn */ void SVD_init (I, long numberOfRows, long numberOfColumns) { iam (SVD); long mn_min = MIN (numberOfRows, numberOfColumns); my numberOfRows = numberOfRows; my numberOfColumns = numberOfColumns; if (! NUMfpp) { NUMmachar (); } my tolerance = NUMfpp -> eps * MAX (numberOfRows, numberOfColumns); my u = NUMmatrix (1, numberOfRows, 1, mn_min); my v = NUMmatrix (1, numberOfColumns, 1, mn_min); my d = NUMvector (1, mn_min); } SVD SVD_create (long numberOfRows, long numberOfColumns) { try { autoSVD me = Thing_new (SVD); SVD_init (me.peek(), numberOfRows, numberOfColumns); return me.transfer(); } catch (MelderError) { Melder_throw ("SVD not created."); } } SVD SVD_create_d (double **m, long numberOfRows, long numberOfColumns) { try { autoSVD me = SVD_create (numberOfRows, numberOfColumns); SVD_svd_d (me.peek(), m); return me.transfer(); } catch (MelderError) { Melder_throw ("SVD not created from vector."); } } SVD SVD_create_f (float **m, long numberOfRows, long numberOfColumns) { try { autoSVD me = SVD_create (numberOfRows, numberOfColumns); SVD_svd_f (me.peek(), m); return me.transfer(); } catch (MelderError) { Melder_throw ("SVD not created from vector."); } } void SVD_svd_d (SVD me, double **m) { if (my numberOfRows >= my numberOfColumns) { /* Store m in u */ for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { my u[i][j] = m[i][j]; } } } else { /* Store m transposed in v */ for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { my v[j][i] = m[i][j]; } } } SVD_compute (me); } void SVD_svd_f (SVD me, float **m) { if (my numberOfRows >= my numberOfColumns) { /* Store in u */ for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { my u[j][i] = m[i][j]; } } } else { /* Store transposed in v */ for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { my v[i][j] = m[j][i]; } } } SVD_compute (me); } void SVD_setTolerance (SVD me, double tolerance) { my tolerance = tolerance; } double SVD_getTolerance (SVD me) { return my tolerance; } static void NUMtranspose_d (double **m, long n) { for (long i = 1; i <= n - 1; i++) { for (long j = i + 1; j <= n; j++) { double t = m[i][j]; m[i][j] = m[j][i]; m[j][i] = t; } } } /* Compute svd(A) = U D Vt. The svd routine from CLAPACK uses (fortran) column major storage, while C uses row major storage. To solve the problem above we have to transpose the matrix A, calculate the solution and transpose the U and Vt matrices of the solution. However, if we solve the transposed problem svd(A') = V D U', we have less work to do: We may call the algorithm with reverted row/column dimensions, and we switch the U and V' output arguments. The only thing that we have to do afterwards is transposing the (small) V matrix because the SVD-object has row vectors in v. The sv's are already sorted. int NUMlapack_dgesvd (char *jobu, char *jobvt, long *m, long *n, double *a, long *lda, double *s, double *u, long *ldu, double *vt, long *ldvt, double *work, long *lwork, long *info); */ void SVD_compute (SVD me) { try { char jobu = 'S', jobvt = 'O'; long m, lda, ldu, ldvt, info, lwork = -1; double wt[2]; int transpose = my numberOfRows < my numberOfColumns; /* transpose: if rows < cols then data in v */ if (transpose) { SVD_transpose (me); } lda = ldu = ldvt = m = my numberOfColumns; long n = my numberOfRows; (void) NUMlapack_dgesvd (&jobu, &jobvt, &m, &n, &my u[1][1], &lda, &my d[1], &my v[1][1], &ldu, NULL, &ldvt, wt, &lwork, &info); if (info != 0) { Melder_throw ("SVD not precomputed."); } lwork = wt[0]; autoNUMvector work (0L, lwork); (void) NUMlapack_dgesvd (&jobu, &jobvt, &m, &n, &my u[1][1], &lda, &my d[1], &my v[1][1], &ldu, NULL, &ldvt, work.peek(), &lwork, &info); if (info != 0) { Melder_throw ("SVD not computed."); } NUMtranspose_d (my v, MIN (m, n)); if (transpose) { SVD_transpose (me); } } catch (MelderError) { Melder_throw (me, ": SVD could not be computed."); } } void SVD_solve (SVD me, double b[], double x[]) { try { long mn_min = MIN (my numberOfRows, my numberOfColumns); autoNUMvector t (1, mn_min); /* Solve UDV' x = b. Solution: x = V D^-1 U' b */ for (long j = 1; j <= mn_min; j++) { double tmp = 0; if (my d[j] > 0) { for (long i = 1; i <= my numberOfRows; i++) { tmp += my u[i][j] * b[i]; } tmp /= my d[j]; } t[j] = tmp; } for (long j = 1; j <= my numberOfColumns; j++) { double tmp = 0; for (long i = 1; i <= mn_min; i++) { tmp += my v[j][i] * t[i]; } x[j] = tmp; } } catch (MelderError) { Melder_throw (me, ": not solved."); } } void SVD_sort (SVD me) { try { long mn_min = MIN (my numberOfRows, my numberOfColumns); autoSVD thee = Data_copy (me); autoNUMvector index (1, mn_min); NUMindexx (my d, mn_min, index.peek()); for (long j = 1; j <= mn_min; j++) { long from = index[mn_min - j + 1]; my d[j] = thy d[from]; for (long i = 1; i <= my numberOfRows; i++) { my u[i][j] = thy u[i][from]; } for (long i = 1; i <= my numberOfColumns; i++) { my v[i][j] = thy v[i][from]; } } } catch (MelderError) { Melder_throw (me, ": not sorted."); } } long SVD_zeroSmallSingularValues (SVD me, double tolerance) { long numberOfZeroed = 0, mn_min = MIN (my numberOfRows, my numberOfColumns); double dmax = my d[1]; if (tolerance == 0) { tolerance = my tolerance; } for (long i = 2; i <= mn_min; i++) { if (my d[i] > dmax) { dmax = my d[i]; } } for (long i = 1; i <= mn_min; i++) { if (my d[i] < dmax * tolerance) { my d[i] = 0; numberOfZeroed++; } } return numberOfZeroed; } long SVD_getRank (SVD me) { long rank = 0, mn_min = MIN (my numberOfRows, my numberOfColumns); for (long i = 1; i <= mn_min; i++) { if (my d[i] > 0) { rank++; } } return rank; } /* SVD of A = U D V'. If u[i] is the i-th column vector of U and v[i] the i-th column vector of V and s[i] the i-th singular value, we can write the svd expansion A = sum_{i=1}^n {d[i] u[i] v[i]'}. Golub & van Loan, 3rd ed, p 71. */ void SVD_synthesize (SVD me, long sv_from, long sv_to, double **m) { try { long mn_min = MIN (my numberOfRows, my numberOfColumns); if (sv_to == 0) { sv_to = mn_min; } if (sv_from > sv_to || sv_from < 1 || sv_to > mn_min) { Melder_throw ("Indices must be in range [1, ", mn_min, "]."); } for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { m[i][j] = 0; } } for (long k = sv_from; k <= sv_to; k++) { for (long i = 1; i <= my numberOfRows; i++) { for (long j = 1; j <= my numberOfColumns; j++) { m[i][j] += my d[k] * my u[i][k] * my v[j][k]; } } } } catch (MelderError) { Melder_throw (me, ": no synthesis."); } } Thing_implement (GSVD, Data, 0); void structGSVD :: v_info () { MelderInfo_writeLine2 (L"Number of columns: ", Melder_integer (numberOfColumns)); } GSVD GSVD_create (long numberOfColumns) { try { autoGSVD me = Thing_new (GSVD); my numberOfColumns = numberOfColumns; my q = NUMmatrix (1, numberOfColumns, 1, numberOfColumns); my r = NUMmatrix (1, numberOfColumns, 1, numberOfColumns); my d1 = NUMvector (1, numberOfColumns); my d2 = NUMvector (1, numberOfColumns); return me.transfer(); } catch (MelderError) { Melder_throw ("GSVD not created."); } } GSVD GSVD_create_d (double **m1, long numberOfRows1, long numberOfColumns, double **m2, long numberOfRows2) { try { long m = numberOfRows1, n = numberOfColumns, p = numberOfRows2; long lwork = MAX (MAX (3 * n, m), p) + n; // Store the matrices a and b as column major! autoNUMmatrix a (NUMmatrix_transpose (m1, m, n), 1, 1); autoNUMmatrix b (NUMmatrix_transpose (m2, p, n), 1, 1); autoNUMmatrix q (1, n, 1, n); autoNUMvector alpha (1, n); autoNUMvector beta (1, n); autoNUMvector work (1, lwork); autoNUMvector iwork (1, n); char jobu1 = 'N', jobu2 = 'N', jobq = 'Q'; long k, l, info; NUMlapack_dggsvd (&jobu1, &jobu2, &jobq, &m, &n, &p, &k, &l, &a[1][1], &m, &b[1][1], &p, &alpha[1], &beta[1], NULL, &m, NULL, &p, &q[1][1], &n, &work[1], &iwork[1], &info); if (info != 0) { Melder_throw ("dggsvd failed, error = ", info); } long kl = k + l; autoGSVD me = GSVD_create (kl); for (long i = 1; i <= kl; i++) { my d1[i] = alpha[i]; my d2[i] = beta[i]; } // Transpose q for (long i = 1; i <= n; i++) { for (long j = i + 1; j <= n; j++) { my q[i][j] = q[j][i]; my q[j][i] = q[i][j]; } my q[i][i] = q[i][i]; } // Get R from a(1:k+l,n-k-l+1:n) double *pr = &a[1][1]; for (long i = 1; i <= kl; i++) { for (long j = i; j <= kl; j++) { my r[i][j] = pr[i - 1 + (n - kl + j - 1) * m]; /* from col-major */ } } return me.transfer(); } catch (MelderError) { Melder_throw ("GSVD not created."); } } void GSVD_setTolerance (GSVD me, double tolerance) { my tolerance = tolerance; } double GSVD_getTolerance (GSVD me) { return my tolerance; } #undef MAX #undef MIN /* End of file SVD.c */ sources_5316/dwsys/NUM2.h0000644000176700017670000012231311745535046014002 0ustar paulpaul#ifndef _NUM2_h_ #define _NUM2_h_ /* NUM2.h * * Copyright (C) 1997-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020815 GPL header djmw 20110428 Latest modification. */ #include #include "../num/NUM.h" #include "regularExp.h" /* machine precision */ #define NUMeps 2.2e-16 int NUMstrcmp (const char *s1, const char *s2); /* Compares strings, accepts NUL-strings (NULL < 'a') return s1 == NULL ? (s2 == NULL ? 0 : - 1) : (s2 == NULL ? 1 : strcmp (s1, s2)); */ int NUMstring_containsPrintableCharacter (const wchar_t *s); double *NUMstring_to_numbers (const wchar_t *s, long *numbers_found); /* return array with the number of numbers found */ int NUMstrings_equal (const wchar_t **s1, const wchar_t **s2, long lo, long hi); void NUMstrings_copyElements (wchar_t **from, wchar_t**to, long lo, long hi); void NUMstrings_free (wchar_t **s, long lo, long hi); int NUMstrings_setSequentialNumbering (wchar_t **s, long lo, long hi, const wchar_t *precursor, long number, long increment); /* Set s[lo] = precursor s[lo+1] = precursor ... s[hi] = precursor */ wchar_t **NUMstrings_copy (wchar_t **from, long lo, long hi); regexp *NUMregexp_compile (const wchar_t *regexp); /* Compiles a regular expression to a datastructure used by the regexp engine */ wchar_t *strstr_regexp (const wchar_t *string, const wchar_t *search_regexp); /* Returns a pointer to the first occurrence in 'string' of the regular expression 'searchRE'. It returns a null pointer if no match is found. */ wchar_t **strs_replace (wchar_t **from, long lo, long hi, const wchar_t *search, const wchar_t *replace, int maximumNumberOfReplaces, long *nmatches, long *nstringmatches, int use_regexp); /* Searches and replaces in string array of strings. If use_regexp != 0, 'search' and 'replace' will be interpreted as regular expressions. Else these strings are taken literally. 'maximumNumberOfReplaces' is the maximum number of replaces in EACH string in the array of strings (you can replace ALL occurrences by making this number <= 0). The totalnumber of matches found is returned in 'nmatches'. The number of strings with at least one match is returned in 'nstringmatches'. */ wchar_t *str_replace_literal (const wchar_t *string, const wchar_t *search, const wchar_t *replace, long maximumNumberOfReplaces, long *nmatches); /* Search and replace in 'string'. The maximum number of replaces is limited by 'maximumNumberOfReplaces'. */ wchar_t *str_replace_regexp (const wchar_t *string, regexp *search_compiled, const wchar_t *replace_regexp, long maximumNumberOfReplaces, long *nmatches); /* Searches and replaces 'maximumNumberOfReplaces' times in 'string' on the basis of regular expressions (RE). If maximumNumberOfReplaces <= 0 the interpreted 'replaceRE' replaces ALL occurrences. 'search_regexp' is an efficient representation of the search RE and is the result of the compileRE-function which must be called first before calling this routine. The number of matches found is returned in 'nmatches'. */ void NUMdmatrix_printMatlabForm (double **m, long nr, long nc, const wchar_t *name); /* Print a matrix in a form that can be used as input for octave/matlab. 1 2 3 Let A be the matrix: 4 5 6 7 8 9 The output from NUMdmatrix_printAsOctaveForm (A, 3, 3, "M") will be M=[1, 2, 3; 4, 5, 6; 7, 8, 9]; */ double **NUMdmatrix_transpose (double **m, long nr, long nc); /* Transpose a nr x nc matrix. */ /* NUMvector_extrema * Function: * compute minimum and maximum values of array v[lo..hi]. * Precondition: * lo and hi must be valid indices in the array. */ template void NUMvector_extrema (T *v, long lo, long hi, double *min, double *max) { T tmin = v[lo]; T tmax = tmin; for (long i = lo + 1; i <= hi; i++) { if (v[i] < tmin) tmin = v[i]; else if (v[i] > tmax) tmax = v[i]; } *min = tmin; *max = tmax; } template void NUMmatrix_extrema (T **x, long rb, long re, long cb, long ce, double *min, double *max) { T xmin, xmax; xmax = xmin = x[rb][cb]; for (long i = rb; i <= re; i++) { for (long j = cb; j <= ce; j++) { T t = x[i][j]; if (t < xmin) xmin = t; else if (t > xmax) xmax = t; } } *min = xmin; *max = xmax; } /* NUMvector_clip Clip array values. c[i] = c[i] < min ? min : (c[i] > max ? max : c[i]) */ template void NUMvector_clip (T *v, long lo, long hi, double min, double max) { T tmin = min, tmax = max; for (long i = lo; i <= hi; i++) { if (v[i] < tmin) v[i] = tmin; else if (v[i] > tmax) v[i] = tmax; } } template T ** NUMmatrix_transpose (T **m, long nr, long nc) { autoNUMmatrix to (1, nc, 1, nr); for (long i = 1; i <= nr; i++) { for (long j = 1; j <= nc; j++) { to[j][i] = m[i][j]; } } return to.transfer(); } int NUMdmatrix_hasInfinities (double **m, long rb, long re, long cb, long ce); double NUMvector_normalize1 (double v[], long n); double NUMvector_normalize2 (double v[], long n); double NUMvector_getNorm1 (const double v[], long n); double NUMvector_getNorm2 (const double v[], long n); void NUMcentreRows (double **a, long rb, long re, long cb, long ce); /* a[i][j] -= a[i][.] */ void NUMcentreColumns (double **a, long rb, long re, long cb, long ce, double *centres); /* a[i][j] -= a[.][j] if centres != NULL the means are returned in centres[1..re-rb+1] */ void NUMdoubleCentre (double **a, long rb, long re, long cb, long ce); /* Function: Make the average value of each column and each row zero. a[i][j] += - a[i][.] - a[.][j] + a[.][.] */ void NUMnormalizeRows (double **a, long nr, long nc, double norm); void NUMnormalizeColumns (double **a, long nr, long nc, double norm); /* Scale a[.][j] such that sqrt (Sum(a[i][j]^2, i=1..nPoints)) = norm. */ void NUMnormalize (double **a, long nr, long nc, double norm); /* Scale all elements of the matrix [1..nr][1..nc] such that (sqrt(Sum( a[i][j]^2, i=1..nr, j=1..nc)) becomes equal to norm. */ void NUMstandardizeColumns (double **a, long rb, long re, long cb, long ce); /* a[i][j] = (a[i][j] - average[j]) / sigma[j] */ void NUMstandardizeRows (double **a, long rb, long re, long cb, long ce); /* a[i][j] = (a[i][j] - average[i]) / sigma[i] */ void NUMaverageColumns (double **a, long rb, long re, long cb, long ce); /* a[i][j] = average[j]) */ void NUMcolumn_avevar (double **a, long nr, long nc, long icol, double *average, double *variance); /* Get mean and variance of a column. When average and/or variance are NULL, the corresponding output is NOT given. */ void NUMcolumn2_avevar (double **a, long nr, long nc, long icol1, long icol2, double *average1, double *variance1, double *average2, double *variance2, double *covariance); /* Get mean and variance of two columns. When average and/or variance are NULL, the corresponding output is NOT given. */ void NUMcovarianceFromColumnCentredMatrix (double **x, long nrows, long ncols, long ndf, double **covar); /* Calculate covariance matrix(ncols x ncols) from data matrix (nrows x ncols); The matrix covar must already have been allocated and centered. covar[i][j] = sum (k=1..nrows, x[i]k]*x[k][j])/(nrows - ndf) */ double NUMmultivariateKurtosis (double **x, long nrows, long ncols, int method); /* calculate multivariate kurtosis. method = 1 : Schott (2001), J. of Statistical planning and Inference 94, 25-36. */ void NUMmad (double *x, long n, double *location, int wantlocation, double *mad, double *work); /* Computes the median absolute deviation, i.e., the median of the absolute deviations from the median, and adjust by a factor for asymptotically normal consistency, i.e. the returned value is 1.4826*mad which makes the returned value "equal" to the standard deviation if the data is normally distributed. You either GIVE the median location (if wantlocation = 0) or it will be calculated (if wantlocation = 1); work is a working array (1..n) that can be used for efficiency reasons. If work == NULL, the routine allocates (and destroys) its own memory. */ void NUMstatistics_huber (double *x, long n, double *location, int wantlocation, double *scale, int wantscale, double k, double tol, double *work); /* Finds the Huber M-estimator for location with scale specified, scale with location specified, or both if neither is specified. k Winsorizes at `k' standard deviations. work is a working array (1..n) that can be used for efficiency reasons. If work == NULL, the routine allocates (and destroys) its own memory. */ void NUMmonotoneRegression (const double x[], long n, double xs[]); /* Find numbers xs[1..n] that have a monotone relationship with the numbers in x[1..n]. The xs[i] will be ascending. */ /* NUMsort2: NUMsort2 uses heapsort to sort the second array in parallel with the first one. Algorithm follows p. 145 and 642 in: Donald E. Knuth (1998): The art of computer programming. Third edition. Vol. 3: sorting and searching. Boston: Addison-Wesley, printed may 2002. Modification: there is no distinction between record and key and Floyd's optimization (page 642) is used. Sorts (inplace) an array a[1..n] into ascending order using the Heapsort algorithm, while making the corresponding rearrangement of the companion array b[1..n]. A characteristic of heapsort is that it does not conserve the order of equals: e.g., the array 3,1,1,2 will be sorted as 1,1,2,3. It may occur that a_sorted[1] = a_presorted[2] and a_sorted[2] = a_presorted[1] no g */ template void NUMsort2 (long n, T1 *a, T2 *b) { long l, r, j, i, imin; T1 k, min; T2 kb, min2; if (n < 2) { return; /* Already sorted. */ } if (n == 2) { if (a[1] > a[2]) { min = a[2]; a[2] = a[1]; a[1] = min; min2 = b[2]; b[2] = b[1]; b[1] = min2; } return; } if (n <= 12) { for (i = 1; i < n; i++) { min = a[i]; imin = i; for (j = i + 1; j <= n; j++) { if (a[j] < min) { min = a [j]; imin = j; } } a[imin] = a[i]; a[i] = min; min2 = b[imin]; b[imin] = b[i]; b[i] = min2; } return; } /* H1 */ l = (n >> 1) + 1; r = n; for (;;) { if (l > 1) { l--; k = a[l]; kb = b[l]; } else /* l == 1 */ { k = a[r]; kb = b[r]; a[r] = a[1]; b[r] = b[1]; r--; if (r == 1) { a[1] = k; b[1] = kb; return; } } /* H3 */ j = l; for (;;) { /* H4 */ i = j; j = j << 1; if (j > r) break; if (j < r && a[j] < a[j + 1]) j++; /* H5 */ /* if (k >= a[j]) break; H6 */ a[i] = a[j]; b[i] = b[j]; /* H7 */ } /* a[i] = k; b[i] = kb; H8 */ for (;;) { /*H8' */ j = i; i = j >> 1; /* H9' */ if (j == l || k <= a[i]) { a[j] = k; b[j] = kb; break; } a[j] = a[i]; b[j] = b[i]; } } } void NUMindexx_f (const float a[], long n, long indx[]); void NUMindexx (const double a[], long n, long indx[]); void NUMindexx_s (wchar_t *a[], long n, long indx[]); /* Indexes the array a[1..n], i.e., outputs the array indx[1..n] such that a[ indx[i] ] is in ascending order for i=1..n; No preservation of order amoung equals (see NUMsort2_...) */ /* NUMrank: * Replace content of array by rank number, including midranking of ties. * E.g. The elements {10, 20.1, 20.1, 20.1, 20.1, 30} in array a will be replaced * by {1, 3.5, 3.5, 3.5, 3.5, 4}, respectively. * */ template void NUMrank (long n, T *a) { long jt, j = 1; while (j < n) { for (jt = j + 1; jt <= n && a[jt] == a[j]; jt++) {} T rank = (j + jt - 1) * 0.5; for (long i = j; i <= jt - 1; i++) { a[i] = rank; } j = jt; } if (j == n) a[n] = n; } void NUMrankColumns (double **m, long rb, long re, long cb, long ce); void NUMlocate_f (float *xx, long n, float x, long *index); void NUMlocate (double *xx, long n, double x, long *index); /* Given an array xx[1..n], and given a value x, returns a value index such that xx[index] < x <= xx[index+1]. Preconditions: xx must be monotonic Error: index = 0 or index = n (out of range) */ int NUMjacobi (float **a, long n, float d[], float **v, long *nrot); /* This version deviates from the NR version. HERE: v[1..n][1..n] is a matrix whose ROWS (and not the columns) contain, on output, the normalized eigenvectors of `a'. Computes all eigenvalues and eigenvectors of a real symmetric matrix a[1..n][1..n]. On output, elements of `a' above the diagonal are destroyed. d[1..n] returns the eigenvalues of `a'. `nrot' returns the number of Jacobi rotations that were required. */ void NUMtred2_f (float **a, long n, float d[], float e[]); void NUMtred2 (double **a, long n, double d[], double e[]); /* Householder reduction of a real, symmetric matrix a[1..n][1..n]. On output, a is replaced by the orthogonal matrix Q effecting the transformation. d[1..n] returns the diagonal elements of the tridiagonal matrix, and e[1..n] the off-diagonal elements, with e[1] = 0. */ int NUMtqli_f (float d[], float e[], long n, float **z); int NUMtqli (double d[], double e[], long n, double **z); /* QL algorithm with implicit shifts, to determine the (sorted) eigenvalues and eigenvectors of a real, symmetric, tridiagonal matrix, or of a real, symmetric matrix previously reduced by NUMtred2 . On input d[1..n] contains the diagonal elements of the tridiagonal matrix. On output, it returns the eigenvalues. The vector e[1..n] inputs the subdiagonal elements of the tridiagonal matrix, with e[1] arbitrary. On output e is destroyed. If the eigenvectors of a tridiagonal matrix are desired, the matrix z[1..n][1..n] is input as the identity matrix. If the eigenvectors of a matrix that has been reduced by NUMtred2 are required, then z is input as the matrix output by NUMtred2. The k-th column of z returns the normalized eigenvector corresponding to d[k]. Returns 0 in case of too many rotations. */ int NUMgaussj (double **a, long n, double **b, long m); int NUMgaussj_f (float **a, long n); /* Calculate inverse of square matrix a[1..n][1..n] (in-place). Method: Gauss-Jordan elimination with full pivoting. Error message in case of singular matrix. */ int NUMsvdcmp (double **a, long m, long n, double w[], double **v); /* Given a matrix a[1..m][1..n], this routine computes its singular value decomposition, A = U.W.V'. The matrix U replaces a on output. The diagonal matrix of singular values W is output as vector w[1..n]. The matrix V (not the transpose V') is output as v[1..n][1..n]. Possible errors: no memory or more than 30 iterations. */ int NUMsvbksb (double **u, double w[], double **v, long m, long n, double b[], double x[]); /* Solves A.X=B for a vector X, where A is specified by the arrays u[1..m][1..n], w[1..n], v[1..n][1..n] as returned by NUMsvdcmp. m and n are the dimensions of a, and will be equal for square matrices. b[1..m] is the input right-hand side. x[1..n] is the output solution vector. Possible errors: no memory. */ int NUMludcmp (double **a, long n, long *indx, double *d); int NUMludcmp_f (float **a, long n, long *indx, float *d); /* Given a matrix a[1..n][1..n], this routine replaces it by the LU decomposition of a rowwise permutation of itself. a : matrix [1..n][1..n] n : dimension of matrix indx : output vector[1..n] that records the row permutation effected by partial pivoting. d : output +/-1 depending on whether the number of ro interchanges was even/odd. */ int NUMcholeskyDecomposition(double **a, long n, double d[]); /* Cholesky decomposition of a symmetric positive definite matrix. */ void NUMcholeskySolve (double **a, long n, double d[], double b[], double x[]); /* Solves A.x=b for x. A[][] and d[] are output from NUMcholeskyDecomposition. */ void NUMlowerCholeskyInverse (double **a, long n, double *lnd); /* Calculates L^-1, where A = L.L' is a symmetric positive definite matrix and ln(determinant). L^-1 in lower, leave upper part intact. */ double **NUMinverseFromLowerCholesky (double **m, long n); /* Return the complete matrix inverse (m x m). Input is the lower Cholesky decomposition of the inverse as calculated by NUMlowerCholeskyInverse. */ void NUMdeterminant_cholesky (double **a, long n, double *lnd); /* ln(determinant) of a symmetric p.s.d. matrix */ double NUMmahalanobisDistance_chi (double **l, double *v, double *m, long nr, long nc); /* Calculates squared Mahalanobis distance: (v-m)'S^-1(v-m). Input matrix (li) is the inverse L^-1 of the Cholesky decomposition S = L.L' as calculated by NUMlowerCholeskyInverse or 1-row for a diagonal matrix (nr =1) Mahalanobis distance calculation. S = L.L' -> S**-1 = L**-1' . L**-1 (x-m)'S**-1 (x-m) = (x-m)'L**-1' . L**-1. (x-m) = (L**-1.(x-m))' . (L**-1.(x-m)) */ double NUMtrace (double **a, long n); double NUMtrace2 (double **a1, double **a2, long n); /* Calculates the trace from the product matrix a1 * a2. a1 and a2 are [1..n][1..n] square matrices. */ void eigenSort (double d[], double **v, long n, int sort); void NUMeigensystem (double **a, long n, double **evec, double eval[]); /* Determines the eigensystem of a real, symmetric matrix[1..][1..n]. Returned are: evec[1..n][1..n] with eigenvectors (columnwise) and eval[1..n], the eigenvalues. No eigenvectors or eigenvalues are returned when the function is called with the corresponding parameter NULL. Eigenvalues (with corresponding eigenvectors) are sorted in descending order. */ void NUMdominantEigenvector (double **mns, long n, double *q, double *lambda, double tolerance); /* Determines the first dominant eigenvector from a GENERAL matrix mns[1..n][1..]. Besides the matrix mns, a first guess for the eigenvector q must be supplied (e.g. 1,0,...,0) and a value for tolerance (iteration stops when fabs(lamda[k] - lambda[k-1]) <= tolerance, where lamda[k] is the eigenvalue at the k-th iteration step. The methos is described in: G. Golub & C. van Loan (1996), Matrix computations, third edition, The Johns Hopkins University Press Ltd., London, (Par. 7.3.1 The Power Method) */ void NUMdmatrix_into_principalComponents (double **m, long nrows, long ncols, long numberOfComponents, double **pc); /* Precondition: numberOfComponents > 0 && numberOfComponents <= ncols pc[1..nrows][1..numberOfComponents] exists Function: Calculates the first 'numberOfComponents' principal components for the matrix m[1..nrows][1..ncols]. Postcondition: Matrix pc contains the principal components Algorithm: Singular Value Decomposition: 1. Centre the columns of m, this results in a new matrix mc 2. SVD the mc matrix -> U.d.V' (Covariance matrix from mc is mc'.mc = (U.d.V')'.(U.d.V') = V.d^2.V') 3. Sort singular values d (descending) and corresponding vectors in V 4. The principal components are now: pc[i][j] = sum (k=1..ncols, v[k][j] * m[i][k]) Remark: The resulting configuration is unique up to reflections along the new principal directions. */ void NUMprincipalComponents (double **a, long n, long nComponents, double **pc); /* Determines the principal components of a real symmetric matrix a[1..n][1..n] as a pc[1..n][1..nComponents] column matrix. */ void NUMpseudoInverse (double **y, long nr, long nc, double **yinv, double tolerance); /* Determines the pseudo-inverse Y^-1 of Y[1..nr][1..nc] via s.v.d. Alternative notation for pseudo-inverse: (Y'.Y)^-1.Y' Returns a [1..nc][1..nr] matrix */ long NUMsolveQuadraticEquation (double a, double b, double c, double *x1, double *x2); /* Finds the real roots of ax^2 + bx + c = 0. The number of real roots is returned and their locations in x1 and x2. If only one root found it is stored in x1. If no roots found then x1 and x2 will not be changed. */ void NUMsolveEquation (double **a, long nr, long nc, double *b, double tol, double *x); /* Solve the equation: a.x = b; a[1..nr][1..nc], b[1..nr] and the unknown x[1..nc] a & b are destroyed during the computation. Algorithm: s.v.d. */ void NUMsolveEquations (double **a, long nr, long nc, double **b, long ncb, double tol, double **x); /* Solve the equation: a.x = b; a[1..nr][1..nc], b[1..nr][1..nc2] and the unknown x[1..nc][1..nc2] a & b are destroyed during the computation. Algorithm: s.v.d. */ void NUMsolveNonNegativeLeastSquaresRegression (double **a, long nr, long nc, double *b, double tol, long itermax, double *x); /* Solve the equation: a.x = b for x under the constraint: all x[i] >= 0; a[1..nr][1..nc], b[1..nr] and x[1..nc]. Algorithm: Alternating least squares. Borg & Groenen (1997), Modern multidimensional scaling, Springer, page 180. */ void NUMsolveConstrainedLSQuadraticRegression (double **o, const double y[], long n, double *alpha, double *gamma); /* Solve y[i] = alpha + beta * x[i] + gamma * x[i]^2, with i = 1..n, subject to the constraint beta^2 = 4 * alpha * gamma, for alpha and gamma (Least Squares). The input Vandermonde-matrix o[1..n,1..3] has columns with 1, x[i] and x[i]^2, respectively. The algorithm is according to: Jos M.F. Ten Berge (1983), A generalization of Verhelst's solution for a constrained regression problem in ALSCAL and related MDS-algorithms, Psychometrika 48, 631-638. */ void NUMsolveWeaklyConstrainedLinearRegression (double **f, long n, long m, double phi[], double alpha, double delta, double t[]); /* Solve g(t) = ||Ft - phi||^2 + alpha (t't - delta)^2 for t[1..m], where F[1..n][1..m] is a matrix, phi[1..n] a given vector, and alpha and delta are fixed numbers. This class of functions is composed of a linear regression function and a penalty function for the sum of squared regression weights. It is weakly constrained because the penalty function prohibits a relatively large departure of t't from delta. The solution is due to: Jos M.F. ten Berge (1991), A general solution for a class of weakly constrained linear regression problems, Psychometrika 56, 601-609. Preconditions: n >= m alpha >= 0 */ void NUMProcrustes (double **x, double **y, long nPoints, long nDimensions, double **t, double *v, double *s); /* Given two configurations x and y (nPoints x nDimensions), find the the Procrustes rotation/reflection matrix T, the translation vector v and the scaling factor s such that Y = sXT+1v' (1 is the nPoints vector with ones). Solution: see Borg and Groenen (1997), Modern Multidimensional Scaling, pp 340-346. When on input v == NULL or s == NULL, only the matrix T will be solved for: the orthogonal Procrustes transform. */ void NUMnrbis (void (*f)(double x, double *fx, double *dfx, void *closure), double x1, double x2, void *closure, double *root); /* Find the root of a function between x1 and x2. Method: Newton-Raphson with bisection (i.e., derivative is known!). Error condition: root not bracketed. */ double NUMridders (double (*f) (double x, void *closure), double x1, double x2, void *closure); /* Return the root of a function f bracketed in [xlow, xhigh]. Error condition: root not bracketed. */ void NUMmspline (double knot[], long nKnots, long order, long i, double x, double *y); /* Calculates an M-spline for a knot sequence. After Ramsay (1988), Monotone splines in action, Statistical Science 4. M-splines of order k have degree k-1. M-splines are zero outside interval [ knot[i], knot[i+order] ). First and last 'order' knots are equal, i.e., knot[1] = ... = knot[order] && knot[nKnots-order+1] = ... knot[nKnots]. Error condition: no memory. */ void NUMispline (double aknot[], long nKnots, long order, long i, double x, double *y); /* Calculates an I-spline for simple knot sequences: only one knot at each interior boundary. After Ramsay (1988), Monotone splines in action, Statistical Science 4. I-splines of order k have degree k (because they Integrate an M-spline of degree k-1). In the calculation of the integral of M(x|k,t), M-splines are used that have two more knots, i.e., M(x|k+1,t). For reasons of efficiency we demand that these extra knots are given, i.e., the 'aknot[]' argument contains the knot positions as if the spline to be integrated were an M(x|k+1,t) spline. knot[1] = ... = knot[order+1] && knot[nKnots-order] = ... knot[nKnots] Error condition: no memory. */ double NUMwilksLambda (double *lambda, long from, long to); /* Calculate: Product (i=from..to; 1/(1+lambda[i])) Preconditions: to >= from */ double NUMlnBeta (double a, double b); /* Computes the logarithm of the beta function log(B(a,b) subject to a and b not being negative integers. */ double NUMbeta2 (double z, double w);//temporarily double NUMbetaContinuedFraction(double a, double b, double x); double NUMfactln (int n); /* Returns ln (n!) */ /***** STATISTICS: PROBABILITY DENSITY FUNCTIONS ********************/ double NUMlogNormalP (double x, double zeta, double sigma); /* Area under log normal from 0 to x */ double NUMlogNormalQ (double x, double zeta, double sigma); /* Area under log normal from x to +infinity */ double NUMstudentP (double t, double df); /* The area under the student T-distribution from -infinity to t. Precondition: df > 0 */ double NUMstudentQ (double t, double df); /* The area under the student T distribution from t to +infinity. Precondition: df > 0 */ double NUMfisherP (double f, double df1, double df2); /* The area under Fisher's F-distribution from 0 to f Preconditions: f >= 0, df1 > 0, df2 > 0 */ double NUMfisherQ (double f, double df1, double df2); /* The area under Fisher's F-distribution from f to +infinity Preconditions: f >= 0, df1 > 0, df2 > 0 */ double NUMinvGaussQ (double p); /* Solves NUMgaussQ (x) == p for x, given p. Precondition: 0 < p < 1 Method: Abramovitz & Stegun 26.2.23 Precision: |eps(p)| < 4.5 10^-4 */ double NUMinvChiSquareQ (double p, double df); /* Solves NUMchiSquareQ (chiSquare, df) == p for chiSquare, given p, df. Preconditions: 0 < p < 1, df > 0 */ double NUMinvStudentQ (double p, double df); /* Solves NUMstudentQ (t, df) == p for t, given p, df. Preconditions: 0 < p < 1, df > 0 */ double NUMinvFisherQ (double p, double df1, double df2); /* Solves NUMfisherQ (f, df1, df2) == p for f, given p, df1, df2 Precondition: 0 < p < 1 */ double NUMnormalityTest_HenzeZirkler (double **data, long n, long p, double *beta, double *tnb, double *lnmu, double *lnvar); /* Multivariate normality test of nxp data matrix according to the method described in Henze & Wagner (1997). The test statistic is returned in tnb, together with the lognormal mean 'lnmu' and the lognormal variance 'lnvar'. */ /****** Frequency in Hz to other frequency reps ****/ double NUMmelToHertz2 (double mel); /* Return 700 * (pow (10.0, mel / 2595.0) - 1) */ double NUMhertzToMel2 (double f); /* Return 2595 * log10 (1 + f/700) */ double NUMmelToHertz3 (double mel); /* Return mel < 1000 ? mel : 1000 * (exp (mel * log10(2) / 1000) - 1) */ double NUMhertzToMel3 (double hz); /* Return hz < 1000 ? hz : 1000 * log10 (1 + hz / 1000) / log10 (2) */ double NUMbarkToHertz2 (double bark); /* Return 650 * sinh (bark / 7) */ double NUMhertzToBark2 (double hz); /* Return 7 * ln (hz / 650 + sqrt(1 + (hz / 650)^2)) */ double NUMhertzToBark_traunmueller (double hz); /* return 26.81 * hz /(1960 + hz) -0.53; */ double NUMbarkToHertz_traunmueller (double bark); /* return 1960* (bark + 0.53) / (26.28 - bark); */ double NUMbarkToHertz_schroeder (double bark); /* return 650.0 * sinh (bark / 7.0); */ double NUMbarkToHertz_zwickerterhardt (double hz); /* return 13 * atan (0.00076 * hz) + 3.5 * atan (hz / 7500); */ double NUMhertzToBark_schroeder (double hz); /* return 7.0 * log (hz / 650 + sqrt (1 + (hz / 650)^2)); */ double NUMbladonlindblomfilter_amplitude (double zc, double z); /* Amplitude of filter at dz (barks) from centre frequency. dz may be positive and negative. The bladonlindblomfilter function is: z' = zc - z + 0.474 10 log10 F(z') = 15.81 + 7.5 z' - 17.5 sqrt( 1 + z'^2 ) Reference: Bladon, R.A.W & Lindblom, B., (1980), "Modeling the judgment of vowel quality differences", JASA 69, 1414-1422. The filter has a bandwidth of 1.43 Bark, the maximum occurs at z = zc, and the slopes are -10 dB/Bark and +25 dB/Bark. */ double NUMsekeyhansonfilter_amplitude (double zc, double z); /* Amplitude of filter at dz (barks) from centre frequency. dz may be positive and negative. The sekeyhansonfilter function is: z' = zc - z - 0.215 10 log10 F(z') = 7 - 7.5 * z' - 17.5 * sqrt( 0.196 + z'^2 ) Reference: Sekey, A. & Hanson, B.A. (1984), "Improved 1-Bark bandwidth auditory filter", JASA 75, 1902-1904. The filter function has a bandwidth of 1 Bark, the maximum response occurs at z=zc, and the slopes are +10 dB/Bark and -25 dB/Bark. It is an improved version of bladonlindblomfilter. */ double NUMtriangularfilter_amplitude (double fl, double fc, double fh, double f); /* Filterfunction that intermediates in Mel frequency cepstral coefficients calculation. The filter function is (f-fl)/(fc-fl) fl < f < fc H(z) = (fh-f)/(fh-fc) fc < f < fh 0 otherwise Preconditions: 0 < fl < fh */ double NUMformantfilter_amplitude (double fc, double bw, double f); /* Filterfunction with a formant-like shape on a linear freq. scale. H(f) = 1.0 / (dq * dq + 1.0), where dq = (fc * fc - f * f) / (bw * f) */ int NUMburg (double x[], long n, double a[], int m, double *xms); /* Calculates linear prediction coefficients according to the algorithm from J.P. Burg as described by N.Anderson in Childers, D. (ed), Modern Spectrum Analysis, IEEE Press, 1978, 252-255. */ void NUMdmatrix_to_dBs (double **m, long rb, long re, long cb, long ce, double ref, double factor, double floor); /* Transforms the values in the matrix m[rb..re][cb..ce] to dB's m[i][j] = factor * 10 * log10 (m[i][j] / ref) if (m[i][j] < floor) m[i][j] = floor; Preconditions: rb <= re cb <= ce ref > 0 factor > 0 Errors: Matrix elements < 0; */ double **NUMcosinesTable (long first, long last, long npoints); /* Generate table with cosines. result[i][j] = cos (i * pi * (j - 1/2) / npoints) i=first..last; j=1..npoints Preconditions: 1 <= first <= last npoints > 1 */ /****** Interpolation ****/ void NUMspline (double x[], double y[], long n, double yp1, double ypn, double y2[]); /* Given arrays a[1..n] and y[1..n] containing a tabulated function, i.e., y[i] = f(x[i]), with x[1] < x[2] < ... < x[n], and given values yp1 and ypn for the first derivative of the interpolating function at point 1 and n, respectively, this routine returns an array y2[1..n] that contains the second derivative of the interpolating function at the tabulated point x. If yp1 and/or ypn are greaterequal 10^30, the routine is signaled to set the corresponding boundary condition for a natuarl spline, with zero second derivative on that boundary. */ void NUMsplint (double xa[], double ya[], double y2a[], long n, double x, double *y); /* Given arrays xa[1..n] and ya[1..n] containing a tabulated function, i.e., y[i] = f(x[i]), with x[1] < x[2] < ... < x[n], and given the array y2a[1..n] which is the output of NUMspline above, and given a value of x, this routine returns an interpolated value y. */ double NUMsincpi (const double x); /* Calculates sin(pi*x)/(pi*x) */ double NUMsinc (const double x); /* Calculates sin(x)/(x) */ /*********************** Geometry *************************************/ int NUMgetOrientationOfPoints (double x1, double y1, double x2, double y2, double x3, double y3); /* Traverse points 1, 2 and 3. If we travel counter-clockwise the result will be 1, if we travel clockwise the result will be -1 and the result will be 0 if 3 is on the line segment between 1 and 2. */ int NUMdoLineSegmentsIntersect (double x1, double y1, double x2, double y2, double x3, double y3, double x4, double y4); /* Does the line segment from (x1,y1) to (x2,y2) intersect with the line segment from (x3,y3) to (x4,y4)? */ int NUMgetIntersectionsWithRectangle (double x1, double y1, double x2, double y2, double xmin, double ymin, double xmax, double ymax, double *xi, double *yi); /* Get the intersection points of the line through the points (x1,y1) and (x2,y2) with the rectangle with corners (xmin, ymin) and (xmax,ymax). The returned value is the number of intersections found and is either 0 or 1 or 2. */ int NUMclipLineWithinRectangle (double xl1, double yl1, double xl2, double yl2, double xr1, double yr1, double xr2, double yr2, double *xo1, double *yo1, double *xo2, double *yo2); /* Returns in (xo1, yo1) and (xo2, yo2) the coordinates of that piece of the line (xl1, yl1)..(xl2, yl2) that can be drawn within the rectangle with lowerleft corner (xr1, yr1) and upperright (xr2, yr2). Returns 0 if there is nothing to be drawn inside. */ void NUMgetEllipseBoundingBox (double a, double b, double cospsi, double *width, double *height); /* Get the width and the height of the bonding box around an ellipse. a and b are the lengths of the long axes. cospsi is the cosine of the angle between the a-axis and the horizontal x-axis (cs == 0 when a-axis and x-axis are perpendicular). Parametrisation of the ellipse: x(phi) = a cos(psi) cos(phi) - b sin (psi) sin(phi) y(phi) = a sin(psi) cos(phi) + b cos(psi) sin(phi) 0 <= phi <= 2 pi Extrema: d x(phi) / dphi == 0 and d y(phi) / dphi == 0 Solution: x(phi1) = a cos(psi) cos(phi1) - b sin (psi) sin(phi1) y(phi2) = a sin(psi) cos(phi2) + b cos(psi) sin(phi2), where phi1 = arctg ( -b/a tg(psi)) phi2 = arctg ( b/a cotg(psi)) Special cases are psi = 0 and pi /2 */ double NUMminimize_brent (double (*f) (double x, void *closure), double a, double b, void *closure, double tol, double *fx); /* The function returns an estimate for the minimum location with accuracy 3 * SQRT_EPSILON * abs(x) + tol. The function always obtains a local minimum which coincides with the global one only if a function under investigation being unimodular. If a function being examined possesses no local minimum within the given range, the function returns 'a' (if f(a) < f(b)), otherwise it returns the right range boundary value b. Algorithm The function makes use of the golden section procedure combined with parabolic interpolation. At every step, the program operates at three abscissae - x, v, and w. x - the last and the best approximation to the minimum location, i.e. f(x) <= f(a) or/and f(x) <= f(b) (if the function f has a local minimum in (a,b), then both conditions are fulfiled after one or two steps). v, w are previous approximations to the minimum location. They may coincide with a, b, or x (although the algorithm tries to make all u, v, and w distinct). Points x, v, and w are used to construct interpolating parabola whose minimum will be treated as a new approximation to the minimum location if the former falls within [a,b] and reduces the range enveloping minimum more efficient than the golden section procedure. When f(x) has a second derivative positive at the minimum location (not coinciding with a or b) the procedure converges superlinearly at a rate order about 1.324 */ /********************** fft ******************************************/ struct structNUMfft_Table_f { long n; /* Data length */ float *trigcache; long *splitcache; }; struct structNUMfft_Table { long n; double *trigcache; long *splitcache; }; typedef struct structNUMfft_Table_f *NUMfft_Table_f; typedef struct structNUMfft_Table *NUMfft_Table; void NUMfft_Table_init_f (NUMfft_Table_f table, long n); void NUMfft_Table_init (NUMfft_Table table, long n); /* n : data size */ #ifdef __cplusplus struct autoNUMfft_Table : public structNUMfft_Table { autoNUMfft_Table () throw () { n = 0; trigcache = 0; splitcache = 0; } ~autoNUMfft_Table () { NUMvector_free (trigcache, 0); NUMvector_free (splitcache, 0); } }; #endif void NUMfft_forward_f (NUMfft_Table_f table, float *data); void NUMfft_forward (NUMfft_Table table, double *data); /* Function: Calculates the Fourier Transform of a set of n real-valued data points. Replaces this data in array data [1...n] by the positive frequency half of its complex Fourier Transform, with a minus sign in the exponent. Preconditions: data != NULL; table must have been initialised with NUMfft_Table_init_f/d Postconditions: data[1] contains real valued first component (Direct Current) data[2..n-1] even index : real part; odd index: imaginary part of DFT. data[n] contains real valued last component (Nyquist frequency) Output parameters: data r(1) = the sum from i=1 to i=n of r(i) If l =(int) (n+1)/2 then for k = 2,...,l r(2*k-2) = the sum from i = 1 to i = n of r(i)*cos((k-1)*(i-1)*2*pi/n) r(2*k-1) = the sum from i = 1 to i = n of -r(i)*sin((k-1)*(i-1)*2*pi/n) if n is even r(n) = the sum from i = 1 to i = n of (-1)**(i-1)*r(i) i.e., the ordering of the output array will be for n even r(1),(r(2),i(2)),(r(3),i(3)),...,(r(l-1),i(l-1)),r(l). Or ...., (r(l),i(l)) for n uneven. ***** note this transform is unnormalized since a call of NUMfft_forward followed by a call of NUMfft_backward will multiply the input sequence by n. */ void NUMfft_backward_f (NUMfft_Table_f table, float *data); void NUMfft_backward (NUMfft_Table table, double *data); /* Function: Calculates the inverse transform of a complex array if it is the transform of real data. (Result in this case must be multiplied by 1/n.) Preconditions: n is an integer power of 2. data != NULL; data [1] contains real valued first component (Direct Current) data [2..n-1] even index : real part; odd index: imaginary part of DFT. data [n] contains real valued last component (Nyquist frequency) table must have been initialised with NUMfft_Table_init_f/d Output parameters data for n even and for i = 1,...,n r(i) = r(1)+(-1)**(i-1)*r(n) plus the sum from k=2 to k=n/2 of 2.*r(2*k-2)*cos((k-1)*(i-1)*2*pi/n) -2.*r(2*k-1)*sin((k-1)*(i-1)*2*pi/n) for n odd and for i = 1,...,n r(i) = r(1) plus the sum from k=2 to k=(n+1)/2 of 2.*r(2*k-2)*cos((k-1)*(i-1)*2*pi/n) -2.*r(2*k-1)*sin((k-1)*(i-1)*2*pi/n) ***** note this transform is unnormalized since a call of NUMfft_forward followed by a call of NUMfft_backward will multiply the input sequence by n. */ /**** Compatibility with NR fft's */ void NUMforwardRealFastFourierTransform_f (float *data, long n); void NUMforwardRealFastFourierTransform (double *data, long n); /* Function: Calculates the Fourier Transform of a set of n real-valued data points. Replaces this data in array data [1...n] by the positive frequency half of its complex Fourier Transform, with a minus sign in the exponent. Preconditions: n is an integer power of 2. data != NULL; Postconditions: data [1] contains real valued first component (Direct Current) data [2] contains real valued last component (Nyquist frequency) data [3..n] odd index : real part; even index: imaginary part of DFT. */ void NUMreverseRealFastFourierTransform_f (float *data, long n); void NUMreverseRealFastFourierTransform (double *data, long n); /* Function: Calculates the inverse transform of a complex array if it is the transform of real data. (Result in this case must be multiplied by 1/n.) Preconditions: n is an integer power of 2. data != NULL; data [1] contains real valued first component (Direct Current) data [2] contains real valued last component (Nyquist frequency) data [3..n] odd index : real part; even index: imaginary part of DFT. */ void NUMrealft_f (float *data, long n, int direction); /* Please stop using. */ void NUMrealft (double *data, long n, int direction); long NUMgetIndexFromProbability (double *probs, long nprobs, double p); // IEEE: Programs for digital signal processing section 4.3 LPTRN (modfied) // lpc[1..n] to rc[1..n] void NUMlpc_lpc_to_rc (double *lpc, long p, double *rc); // rc[1..n] to area[1..n+1], area[m+1] = 0.0001; (1 cm^2) void NUMlpc_rc_to_area (double *rc, long n, double *area); // area[1..n] to rc[1..n-1] (modification: LPTRN assumes area[n+1]) void NUMlpc_area_to_rc (double *area, long n, double *rc); // area[1..n] to lpc[1..n-1]! (modification: lptrn gives lpc[1] = 1 we don't) void NUMlpc_area_to_lpc (double *area, long n, double *lpc); // lpc[1..n] to area[1..n+1], area[m+1] = 0.0001; (1 cm^2) void NUMlpc_lpc_to_area (double *lpc, long m, double *area); #endif // _NUM2_h_ sources_5316/dwsys/NUMcblas.cpp0000644000176700017670000020575311634065544015270 0ustar paulpaul/* NUMcblas.c -- LAPACK helper routines -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University October 31, 1999 -- translated by f2c (version 19990503) Adapted by David Weenink 20021201 */ /* djmw 20020813 GPL header djmw 20071201 Latest modification pb 20100120 dlamc3_: declare volatile double ret_val to prevent optimization! */ /* #include "blaswrap.h" */ #include "melder.h" #include "NUMcblas.h" #include "NUMf2c.h" #include "NUM2.h" #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) static int dlamc1_ (long *beta, long *t, long *rnd, long *ieee1); static int dlamc2_ (long *beta, long *t, long *rnd, double *eps, long *emin, double *rmin, long *emax, double *rmax); static double dlamc3_ (double *, double *); static int dlamc4_ (long *emin, double *start, long *base); static int dlamc5_ (long *beta, long *p, long *emin, long *ieee, long *emax, double *rmax); int NUMblas_daxpy (long *n, double *da, double *dx, long *incx, double *dy, long *incy) { /* System generated locals */ long i__1; /* Local variables */ static long i__, m, ix, iy, mp1; --dy; --dx; /* Function Body */ if (*n <= 0) { return 0; } if (*da == 0.) { return 0; } if (*incx == 1 && *incy == 1) { goto L20; } /* code for unequal increments or equal increments not equal to 1 */ ix = 1; iy = 1; if (*incx < 0) { ix = (- (*n) + 1) * *incx + 1; } if (*incy < 0) { iy = (- (*n) + 1) * *incy + 1; } i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { dy[iy] += *da * dx[ix]; ix += *incx; iy += *incy; /* L10: */ } return 0; /* code for both increments equal to 1 clean-up loop */ L20: m = *n % 4; if (m == 0) { goto L40; } i__1 = m; for (i__ = 1; i__ <= i__1; ++i__) { dy[i__] += *da * dx[i__]; /* L30: */ } if (*n < 4) { return 0; } L40: mp1 = m + 1; i__1 = *n; for (i__ = mp1; i__ <= i__1; i__ += 4) { dy[i__] += *da * dx[i__]; dy[i__ + 1] += *da * dx[i__ + 1]; dy[i__ + 2] += *da * dx[i__ + 2]; dy[i__ + 3] += *da * dx[i__ + 3]; /* L50: */ } return 0; } /* NUMblas_daxpy */ int NUMblas_dcopy (long *n, double *dx, long *incx, double *dy, long *incy) { /* System generated locals */ long i__1; /* Local variables */ static long i__, m, ix, iy, mp1; --dy; --dx; /* Function Body */ if (*n <= 0) { return 0; } if (*incx == 1 && *incy == 1) { goto L20; } /* code for unequal increments or equal increments not equal to 1 */ ix = 1; iy = 1; if (*incx < 0) { ix = (- (*n) + 1) * *incx + 1; } if (*incy < 0) { iy = (- (*n) + 1) * *incy + 1; } i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { dy[iy] = dx[ix]; ix += *incx; iy += *incy; /* L10: */ } return 0; /* code for both increments equal to 1 clean-up loop */ L20: m = *n % 7; if (m == 0) { goto L40; } i__1 = m; for (i__ = 1; i__ <= i__1; ++i__) { dy[i__] = dx[i__]; /* L30: */ } if (*n < 7) { return 0; } L40: mp1 = m + 1; i__1 = *n; for (i__ = mp1; i__ <= i__1; i__ += 7) { dy[i__] = dx[i__]; dy[i__ + 1] = dx[i__ + 1]; dy[i__ + 2] = dx[i__ + 2]; dy[i__ + 3] = dx[i__ + 3]; dy[i__ + 4] = dx[i__ + 4]; dy[i__ + 5] = dx[i__ + 5]; dy[i__ + 6] = dx[i__ + 6]; /* L50: */ } return 0; } /* NUMblas_dcopy */ double NUMblas_ddot (long *n, double *dx, long *incx, double *dy, long *incy) { /* System generated locals */ long i__1; double ret_val; /* Local variables */ static long i__, m; static double dtemp; static long ix, iy, mp1; /* Parameter adjustments */ --dy; --dx; /* Function Body */ ret_val = 0.; dtemp = 0.; if (*n <= 0) { return ret_val; } if (*incx == 1 && *incy == 1) { goto L20; } /* code for unequal increments or equal increments not equal to 1 */ ix = 1; iy = 1; if (*incx < 0) { ix = (- (*n) + 1) * *incx + 1; } if (*incy < 0) { iy = (- (*n) + 1) * *incy + 1; } i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { dtemp += dx[ix] * dy[iy]; ix += *incx; iy += *incy; /* L10: */ } ret_val = dtemp; return ret_val; /* code for both increments equal to 1 clean-up loop */ L20: m = *n % 5; if (m == 0) { goto L40; } i__1 = m; for (i__ = 1; i__ <= i__1; ++i__) { dtemp += dx[i__] * dy[i__]; /* L30: */ } if (*n < 5) { goto L60; } L40: mp1 = m + 1; i__1 = *n; for (i__ = mp1; i__ <= i__1; i__ += 5) { dtemp = dtemp + dx[i__] * dy[i__] + dx[i__ + 1] * dy[i__ + 1] + dx[i__ + 2] * dy[i__ + 2] + dx[i__ + 3] * dy[i__ + 3] + dx[i__ + 4] * dy[i__ + 4]; /* L50: */ } L60: ret_val = dtemp; return ret_val; } /* NUMblas_ddot */ int NUMblas_dgemm (const char *transa, const char *transb, long *m, long *n, long *k, double *alpha, double *a, long *lda, double *b, long *ldb, double *beta, double *c__, long *ldc) { /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, c_dim1, c_offset, i__1, i__2, i__3; /* Local variables */ static long info; static long nota, notb; static double temp; static long i__, j, l, ncola; static long nrowa, nrowb; #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] #define b_ref(a_1,a_2) b[(a_2)*b_dim1 + a_1] #define c___ref(a_1,a_2) c__[(a_2)*c_dim1 + a_1] /* Set NOTA and NOTB as true if A and B respectively are not transposed and set NROWA, NCOLA and NROWB as the number of rows and columns of A and the number of rows of B respectively. Parameter adjustments */ a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; /* Function Body */ nota = lsame_ (transa, "N"); notb = lsame_ (transb, "N"); if (nota) { nrowa = *m; ncola = *k; } else { nrowa = *k; ncola = *m; } if (notb) { nrowb = *k; } else { nrowb = *n; } /* Test the input parameters. */ info = 0; if (!nota && !lsame_ (transa, "C") && !lsame_ (transa, "T")) { info = 1; } else if (!notb && !lsame_ (transb, "C") && !lsame_ (transb, "T")) { info = 2; } else if (*m < 0) { info = 3; } else if (*n < 0) { info = 4; } else if (*k < 0) { info = 5; } else if (*lda < MAX (1, nrowa)) { info = 8; } else if (*ldb < MAX (1, nrowb)) { info = 10; } else if (*ldc < MAX (1, *m)) { info = 13; } if (info != 0) { xerbla_ ("DGEMM ", &info); return 0; } /* Quick return if possible. */ if (*m == 0 || *n == 0 || (*alpha == 0. || *k == 0) && *beta == 1.) { return 0; } /* And if alpha.eq.zero. */ if (*alpha == 0.) { if (*beta == 0.) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = 0.; /* L10: */ } /* L20: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = *beta * c___ref (i__, j); /* L30: */ } /* L40: */ } } return 0; } /* Start the operations. */ if (notb) { if (nota) { /* Form C := alpha*A*B + beta*C. */ i__1 = *n; for (j = 1; j <= i__1; ++j) { if (*beta == 0.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = 0.; /* L50: */ } } else if (*beta != 1.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = *beta * c___ref (i__, j); /* L60: */ } } i__2 = *k; for (l = 1; l <= i__2; ++l) { if (b_ref (l, j) != 0.) { temp = *alpha * b_ref (l, j); i__3 = *m; for (i__ = 1; i__ <= i__3; ++i__) { c___ref (i__, j) = c___ref (i__, j) + temp * a_ref (i__, l); /* L70: */ } } /* L80: */ } /* L90: */ } } else { /* Form C := alpha*A'*B + beta*C */ i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { temp = 0.; i__3 = *k; for (l = 1; l <= i__3; ++l) { temp += a_ref (l, i__) * b_ref (l, j); /* L100: */ } if (*beta == 0.) { c___ref (i__, j) = *alpha * temp; } else { c___ref (i__, j) = *alpha * temp + *beta * c___ref (i__, j); } /* L110: */ } /* L120: */ } } } else { if (nota) { /* Form C := alpha*A*B' + beta*C */ i__1 = *n; for (j = 1; j <= i__1; ++j) { if (*beta == 0.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = 0.; /* L130: */ } } else if (*beta != 1.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = *beta * c___ref (i__, j); /* L140: */ } } i__2 = *k; for (l = 1; l <= i__2; ++l) { if (b_ref (j, l) != 0.) { temp = *alpha * b_ref (j, l); i__3 = *m; for (i__ = 1; i__ <= i__3; ++i__) { c___ref (i__, j) = c___ref (i__, j) + temp * a_ref (i__, l); /* L150: */ } } /* L160: */ } /* L170: */ } } else { /* Form C := alpha*A'*B' + beta*C */ i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { temp = 0.; i__3 = *k; for (l = 1; l <= i__3; ++l) { temp += a_ref (l, i__) * b_ref (j, l); /* L180: */ } if (*beta == 0.) { c___ref (i__, j) = *alpha * temp; } else { c___ref (i__, j) = *alpha * temp + *beta * c___ref (i__, j); } /* L190: */ } /* L200: */ } } } return 0; /* End of DGEMM . */ } /* NUMblas_dgemm */ #undef c___ref #undef b_ref #undef a_ref int NUMblas_dger (long *m, long *n, double *alpha, double *x, long *incx, double *y, long *incy, double *a, long *lda) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2; /* Local variables */ static long info; static double temp; static long i__, j, ix, jy, kx; #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] /* Test the input parameters. Parameter adjustments */ --x; --y; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; /* Function Body */ info = 0; if (*m < 0) { info = 1; } else if (*n < 0) { info = 2; } else if (*incx == 0) { info = 5; } else if (*incy == 0) { info = 7; } else if (*lda < MAX (1, *m)) { info = 9; } if (info != 0) { xerbla_ ("DGER ", &info); return 0; } /* Quick return if possible. */ if (*m == 0 || *n == 0 || *alpha == 0.) { return 0; } /* Start the operations. In this version the elements of A are accessed sequentially with one pass through A. */ if (*incy > 0) { jy = 1; } else { jy = 1 - (*n - 1) * *incy; } if (*incx == 1) { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (y[jy] != 0.) { temp = *alpha * y[jy]; i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) + x[i__] * temp; /* L10: */ } } jy += *incy; /* L20: */ } } else { if (*incx > 0) { kx = 1; } else { kx = 1 - (*m - 1) * *incx; } i__1 = *n; for (j = 1; j <= i__1; ++j) { if (y[jy] != 0.) { temp = *alpha * y[jy]; ix = kx; i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) + x[ix] * temp; ix += *incx; /* L30: */ } } jy += *incy; /* L40: */ } } return 0; } /* NUMblas_dger */ #undef a_ref int NUMblas_dgemv (const char *trans, long *m, long *n, double *alpha, double *a, long *lda, double *x, long *incx, double *beta, double *y, long *incy) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2; /* Local variables */ static long info; static double temp; static long lenx, leny, i__, j; static long ix, iy, jx, jy, kx, ky; #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] /* Parameter adjustments */ a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --x; --y; /* Function Body */ info = 0; if (!lsame_ (trans, "N") && !lsame_ (trans, "T") && !lsame_ (trans, "C")) { info = 1; } else if (*m < 0) { info = 2; } else if (*n < 0) { info = 3; } else if (*lda < MAX (1, *m)) { info = 6; } else if (*incx == 0) { info = 8; } else if (*incy == 0) { info = 11; } if (info != 0) { xerbla_ ("DGEMV ", &info); return 0; } /* Quick return if possible. */ if (*m == 0 || *n == 0 || *alpha == 0. && *beta == 1.) { return 0; } /* Set LENX and LENY, the lengths of the vectors x and y, and set up the start points in X and Y. */ if (lsame_ (trans, "N")) { lenx = *n; leny = *m; } else { lenx = *m; leny = *n; } if (*incx > 0) { kx = 1; } else { kx = 1 - (lenx - 1) * *incx; } if (*incy > 0) { ky = 1; } else { ky = 1 - (leny - 1) * *incy; } /* Start the operations. In this version the elements of A are accessed sequentially with one pass through A. First form y := beta*y. */ if (*beta != 1.) { if (*incy == 1) { if (*beta == 0.) { i__1 = leny; for (i__ = 1; i__ <= i__1; ++i__) { y[i__] = 0.; /* L10: */ } } else { i__1 = leny; for (i__ = 1; i__ <= i__1; ++i__) { y[i__] = *beta * y[i__]; /* L20: */ } } } else { iy = ky; if (*beta == 0.) { i__1 = leny; for (i__ = 1; i__ <= i__1; ++i__) { y[iy] = 0.; iy += *incy; /* L30: */ } } else { i__1 = leny; for (i__ = 1; i__ <= i__1; ++i__) { y[iy] = *beta * y[iy]; iy += *incy; /* L40: */ } } } } if (*alpha == 0.) { return 0; } if (lsame_ (trans, "N")) { /* Form y := alpha*A*x + y. */ jx = kx; if (*incy == 1) { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (x[jx] != 0.) { temp = *alpha * x[jx]; i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { y[i__] += temp * a_ref (i__, j); /* L50: */ } } jx += *incx; /* L60: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (x[jx] != 0.) { temp = *alpha * x[jx]; iy = ky; i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { y[iy] += temp * a_ref (i__, j); iy += *incy; /* L70: */ } } jx += *incx; /* L80: */ } } } else { /* Form y := alpha*A'*x + y. */ jy = ky; if (*incx == 1) { i__1 = *n; for (j = 1; j <= i__1; ++j) { temp = 0.; i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { temp += a_ref (i__, j) * x[i__]; /* L90: */ } y[jy] += *alpha * temp; jy += *incy; /* L100: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { temp = 0.; ix = kx; i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { temp += a_ref (i__, j) * x[ix]; ix += *incx; /* L110: */ } y[jy] += *alpha * temp; jy += *incy; /* L120: */ } } } return 0; } /* NUMblas_dgemv */ #undef a_ref double NUMblas_dlamch (const char *cmach) { /* Initialized data */ static long first = TRUE; /* System generated locals */ long i__1; double ret_val; /* Builtin functions */ /* Local variables */ static double base; static long beta; static double emin, prec, emax; static long imin, imax; static long lrnd; static double rmin, rmax, t, rmach; static double smal, sfmin; static long it; static double rnd, eps; if (first) { first = FALSE; dlamc2_ (&beta, &it, &lrnd, &eps, &imin, &rmin, &imax, &rmax); base = (double) beta; t = (double) it; if (lrnd) { rnd = 1.; i__1 = 1 - it; eps = pow_di (&base, &i__1) / 2; } else { rnd = 0.; i__1 = 1 - it; eps = pow_di (&base, &i__1); } prec = eps * base; emin = (double) imin; emax = (double) imax; sfmin = rmin; smal = 1. / rmax; if (smal >= sfmin) { /* Use smal plus a bit, to avoid the possibility of rounding causing overflow when computing 1/sfmin. */ sfmin = smal * (eps + 1.); } } if (lsame_ (cmach, "E")) { rmach = eps; } else if (lsame_ (cmach, "S")) { rmach = sfmin; } else if (lsame_ (cmach, "B")) { rmach = base; } else if (lsame_ (cmach, "P")) { rmach = prec; } else if (lsame_ (cmach, "N")) { rmach = t; } else if (lsame_ (cmach, "R")) { rmach = rnd; } else if (lsame_ (cmach, "M")) { rmach = emin; } else if (lsame_ (cmach, "U")) { rmach = rmin; } else if (lsame_ (cmach, "L")) { rmach = emax; } else if (lsame_ (cmach, "O")) { rmach = rmax; } ret_val = rmach; return ret_val; } /* NUMblas_dlamch */ static int dlamc1_ (long *beta, long *t, long *rnd, long *ieee1) { /* -- LAPACK auxiliary routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University October 31, 1992 Purpose ======= DLAMC1 determines the machine parameters given by BETA, T, RND, and IEEE1. Arguments ========= BETA (output) INTEGER The base of the machine. T (output) INTEGER The number of ( BETA ) digits in the mantissa. RND (output) LOGICAL Specifies whether proper rounding ( RND = .TRUE. ) or chopping ( RND = .FALSE. ) occurs in addition. This may not be a reliable guide to the way in which the machine performs its arithmetic. IEEE1 (output) LOGICAL Specifies whether rounding appears to be done in the IEEE 'round to nearest' style. Further Details =============== The routine is based on the routine ENVRON by Malcolm and incorporates suggestions by Gentleman and Marovich. See Malcolm M. A. (1972) Algorithms to reveal properties of floating-point arithmetic. Comms. of the ACM, 15, 949-951. Gentleman W. M. and Marovich S. B. (1974) More on algorithms that reveal properties of floating point arithmetic units. Comms. of the ACM, 17, 276-277. ===================================================================== */ /* Initialized data */ static long first = TRUE; /* System generated locals */ double d__1, d__2; /* Local variables */ static long lrnd; static double a, b, c, f; static long lbeta; static double savec; static long lieee1; static double t1, t2; static long lt; static double one, qtr; if (first) { first = FALSE; one = 1.; /* LBETA, LIEEE1, LT and LRND are the local values of BETA, IEEE1, T and RND. Throughout this routine we use the function DLAMC3 to ensure that relevant values are stored and not held in registers, or are not affected by optimizers. Compute a = 2.0**m with the smallest positive integer m such that fl( a + 1.0 ) = a. */ a = 1.; c = 1.; /* + WHILE( C.EQ.ONE )LOOP */ L10: if (c == one) { a *= 2; c = dlamc3_ (&a, &one); d__1 = -a; c = dlamc3_ (&c, &d__1); goto L10; } /* + END WHILE Now compute b = 2.0**m with the smallest positive integer m such that fl( a + b ) .gt. a. */ b = 1.; c = dlamc3_ (&a, &b); /* + WHILE( C.EQ.A )LOOP */ L20: if (c == a) { b *= 2; c = dlamc3_ (&a, &b); goto L20; } /* + END WHILE Now compute the base. a and c are neighbouring floating point numbers in the interval ( beta**t, beta**( t + 1 ) ) and so their difference is beta. Adding 0.25 to c is to ensure that it is truncated to beta and not ( beta - 1 ). */ qtr = one / 4; savec = c; d__1 = -a; c = dlamc3_ (&c, &d__1); lbeta = (long) (c + qtr); /* Now determine whether rounding or chopping occurs, by adding a bit less than beta/2 and a bit more than beta/2 to a. */ b = (double) lbeta; d__1 = b / 2; d__2 = -b / 100; f = dlamc3_ (&d__1, &d__2); c = dlamc3_ (&f, &a); if (c == a) { lrnd = TRUE; } else { lrnd = FALSE; } d__1 = b / 2; d__2 = b / 100; f = dlamc3_ (&d__1, &d__2); c = dlamc3_ (&f, &a); if (lrnd && c == a) { lrnd = FALSE; } /* Try and decide whether rounding is done in the IEEE 'round to nearest' style. B/2 is half a unit in the last place of the two numbers A and SAVEC. Furthermore, A is even, i.e. has last bit zero, and SAVEC is odd. Thus adding B/2 to A should not change A, but adding B/2 to SAVEC should change SAVEC. */ d__1 = b / 2; t1 = dlamc3_ (&d__1, &a); d__1 = b / 2; t2 = dlamc3_ (&d__1, &savec); lieee1 = t1 == a && t2 > savec && lrnd; /* Now find the mantissa, t. It should be the integer part of log to the base beta of a, however it is safer to determine t by powering. So we find t as the smallest positive integer for which fl( beta**t + 1.0 ) = 1.0. */ lt = 0; a = 1.; c = 1.; /* + WHILE( C.EQ.ONE )LOOP */ L30: if (c == one) { ++lt; a *= lbeta; c = dlamc3_ (&a, &one); d__1 = -a; c = dlamc3_ (&c, &d__1); goto L30; } /* + END WHILE */ } *beta = lbeta; *t = lt; *rnd = lrnd; *ieee1 = lieee1; return 0; } /* dlamc1_ */ static int dlamc2_ (long *beta, long *t, long *rnd, double *eps, long *emin, double *rmin, long *emax, double *rmax) { /* -- LAPACK auxiliary routine (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University October 31, 1992 Purpose ======= DLAMC2 determines the machine parameters specified in its argument list. Arguments ========= BETA (output) INTEGER The base of the machine. T (output) INTEGER The number of ( BETA ) digits in the mantissa. RND (output) LOGICAL Specifies whether proper rounding ( RND = .TRUE. ) or chopping ( RND = .FALSE. ) occurs in addition. This may not be a reliable guide to the way in which the machine performs its arithmetic. EPS (output) DOUBLE PRECISION The smallest positive number such that fl( 1.0 - EPS ) .LT. 1.0, where fl denotes the computed value. EMIN (output) INTEGER The minimum exponent before (gradual) underflow occurs. RMIN (output) DOUBLE PRECISION The smallest normalized number for the machine, given by BASE**( EMIN - 1 ), where BASE is the floating point value of BETA. EMAX (output) INTEGER The maximum exponent before overflow occurs. RMAX (output) DOUBLE PRECISION The largest positive number for the machine, given by BASE**EMAX * ( 1 - EPS ), where BASE is the floating point value of BETA. Further Details =============== The computation of EPS is based on a routine PARANOIA by W. Kahan of the University of California at Berkeley. ===================================================================== */ /* Table of constant values */ /* Initialized data */ static long first = TRUE; static long iwarn = FALSE; /* System generated locals */ long i__1; double d__1, d__2, d__3, d__4, d__5; /* Builtin functions */ /* Local variables */ static long ieee; static double half; static long lrnd; static double leps, zero, a, b, c; static long i, lbeta; static double rbase; static long lemin, lemax, gnmin; static double smal; static long gpmin; static double third, lrmin, lrmax, sixth; static long lieee1; static long lt, ngnmin, ngpmin; static double one, two; if (first) { first = FALSE; zero = 0.; one = 1.; two = 2.; /* LBETA, LT, LRND, LEPS, LEMIN and LRMIN are the local values of BETA, T, RND, EPS, EMIN and RMIN. Throughout this routine we use the function DLAMC3 to ensure that relevant values are stored and not held in registers, or are not affected by optimizers. DLAMC1 returns the parameters LBETA, LT, LRND and LIEEE1. */ dlamc1_ (&lbeta, <, &lrnd, &lieee1); /* Start to find EPS. */ b = (double) lbeta; i__1 = -lt; a = pow_di (&b, &i__1); leps = a; /* Try some tricks to see whether or not this is the correct EPS. */ b = two / 3; half = one / 2; d__1 = -half; sixth = dlamc3_ (&b, &d__1); third = dlamc3_ (&sixth, &sixth); d__1 = -half; b = dlamc3_ (&third, &d__1); b = dlamc3_ (&b, &sixth); b = fabs (b); if (b < leps) { b = leps; } leps = 1.; /* + WHILE( ( LEPS.GT.B ).AND.( B.GT.ZERO ) )LOOP */ L10: if (leps > b && b > zero) { leps = b; d__1 = half * leps; /* Computing 5th power */ d__3 = two, d__4 = d__3, d__3 *= d__3; /* Computing 2nd power */ d__5 = leps; d__2 = d__4 * (d__3 * d__3) * (d__5 * d__5); c = dlamc3_ (&d__1, &d__2); d__1 = -c; c = dlamc3_ (&half, &d__1); b = dlamc3_ (&half, &c); d__1 = -b; c = dlamc3_ (&half, &d__1); b = dlamc3_ (&half, &c); goto L10; } /* + END WHILE */ if (a < leps) { leps = a; } /* Computation of EPS complete. Now find EMIN. Let A = + or - 1, and + or - (1 + BASE**(-3)). Keep dividing A by BETA until (gradual) underflow occurs. This is detected when we cannot recover the previous A. */ rbase = one / lbeta; smal = one; for (i = 1; i <= 3; ++i) { d__1 = smal * rbase; smal = dlamc3_ (&d__1, &zero); /* L20: */ } a = dlamc3_ (&one, &smal); dlamc4_ (&ngpmin, &one, &lbeta); d__1 = -one; dlamc4_ (&ngnmin, &d__1, &lbeta); dlamc4_ (&gpmin, &a, &lbeta); d__1 = -a; dlamc4_ (&gnmin, &d__1, &lbeta); ieee = FALSE; if (ngpmin == ngnmin && gpmin == gnmin) { if (ngpmin == gpmin) { lemin = ngpmin; /* ( Non twos-complement machines, no gradual underflow; e.g., VAX ) */ } else if (gpmin - ngpmin == 3) { lemin = ngpmin - 1 + lt; ieee = TRUE; /* ( Non twos-complement machines, with gradual underflow; e.g., IEEE standard followers ) */ } else { lemin = MIN (ngpmin, gpmin); /* ( A guess; no known machine ) */ iwarn = TRUE; } } else if (ngpmin == gpmin && ngnmin == gnmin) { if ( (i__1 = ngpmin - ngnmin, abs (i__1)) == 1) { lemin = MAX (ngpmin, ngnmin); /* ( Twos-complement machines, no gradual underflow; e.g., CYBER 205 ) */ } else { lemin = MIN (ngpmin, ngnmin); /* ( A guess; no known machine ) */ iwarn = TRUE; } } else if ( (i__1 = ngpmin - ngnmin, abs (i__1)) == 1 && gpmin == gnmin) { if (gpmin - MIN (ngpmin, ngnmin) == 3) { lemin = MAX (ngpmin, ngnmin) - 1 + lt; /* ( Twos-complement machines with gradual underflow; no known machine ) */ } else { lemin = MIN (ngpmin, ngnmin); /* ( A guess; no known machine ) */ iwarn = TRUE; } } else { /* Computing MIN */ i__1 = MIN (ngpmin, ngnmin), i__1 = MIN (i__1, gpmin); lemin = MIN (i__1, gnmin); /* ( A guess; no known machine ) */ iwarn = TRUE; } /* Comment out this if block if EMIN is ok */ if (iwarn) { first = TRUE; Melder_warning (L"\n\n WARNING. The value EMIN may be incorrect:- " "EMIN = ", Melder_integer (lemin), L"\nIf, after inspection, the value EMIN looks acceptable" "please comment out \n the IF block as marked within the" "code of routine DLAMC2, \n otherwise supply EMIN" "explicitly.\n"); } /* ** Assume IEEE arithmetic if we found denormalised numbers above, or if arithmetic seems to round in the IEEE style, determined in routine DLAMC1. A true IEEE machine should have both things true; however, faulty machines may have one or the other. */ ieee = ieee || lieee1; /* Compute RMIN by successive division by BETA. We could compute RMIN as BASE**( EMIN - 1 ), but some machines underflow during this computation. */ lrmin = 1.; i__1 = 1 - lemin; for (i = 1; i <= 1 - lemin; ++i) { d__1 = lrmin * rbase; lrmin = dlamc3_ (&d__1, &zero); /* L30: */ } /* Finally, call DLAMC5 to compute EMAX and RMAX. */ dlamc5_ (&lbeta, <, &lemin, &ieee, &lemax, &lrmax); } *beta = lbeta; *t = lt; *rnd = lrnd; *eps = leps; *emin = lemin; *rmin = lrmin; *emax = lemax; *rmax = lrmax; return 0; } /* dlamc2_ */ static double dlamc3_ (double *a, double *b) /* Purpose ======= dlamc3_ is intended to force A and B to be stored prior to doing the addition of A and B , for use in situations where optimizers might hold one of these in a register. Arguments ========= A, B (input) DOUBLE PRECISION The values A and B. ===================================================================== */ { volatile double ret_val; ret_val = *a + *b; return ret_val; } /* dlamc3_ */ static int dlamc4_ (long *emin, double *start, long *base) { /* -- LAPACK auxiliary routine (version 2.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University October 31, 1992 Purpose ======= DLAMC4 is a service routine for DLAMC2. Arguments ========= EMIN (output) EMIN The minimum exponent before (gradual) underflow, computed by setting A = START and dividing by BASE until the previous A can not be recovered. START (input) DOUBLE PRECISION The starting point for determining EMIN. BASE (input) INTEGER The base of the machine. ===================================================================== */ /* System generated locals */ long i__1; double d__1; /* Local variables */ static double zero, a; static long i; static double rbase, b1, b2, c1, c2, d1, d2; static double one; a = *start; one = 1.; rbase = one / *base; zero = 0.; *emin = 1; d__1 = a * rbase; b1 = dlamc3_ (&d__1, &zero); c1 = a; c2 = a; d1 = a; d2 = a; /* + WHILE( ( C1.EQ.A ).AND.( C2.EQ.A ).AND. $ ( D1.EQ.A ).AND.( D2.EQ.A ) )LOOP */ L10: if (c1 == a && c2 == a && d1 == a && d2 == a) { -- (*emin); a = b1; d__1 = a / *base; b1 = dlamc3_ (&d__1, &zero); d__1 = b1 * *base; c1 = dlamc3_ (&d__1, &zero); d1 = zero; i__1 = *base; for (i = 1; i <= *base; ++i) { d1 += b1; /* L20: */ } d__1 = a * rbase; b2 = dlamc3_ (&d__1, &zero); d__1 = b2 / rbase; c2 = dlamc3_ (&d__1, &zero); d2 = zero; i__1 = *base; for (i = 1; i <= *base; ++i) { d2 += b2; /* L30: */ } goto L10; } /* + END WHILE */ return 0; } /* dlamc4_ */ static int dlamc5_ (long *beta, long *p, long *emin, long *ieee, long *emax, double *rmax) { /* First compute LEXP and UEXP, two powers of 2 that bound abs(EMIN). We then assume that EMAX + abs(EMIN) will sum approximately to the bound that is closest to abs(EMIN). (EMAX is the exponent of the required number RMAX). */ /* Table of constant values */ static double c_b5 = 0.; /* System generated locals */ long i__1; double d__1; /* Local variables */ static long lexp; static double oldy; static long uexp, i; static double y, z; static long nbits; static double recbas; static long exbits, expsum, try__; lexp = 1; exbits = 1; L10: try__ = lexp << 1; if (try__ <= - (*emin)) { lexp = try__; ++exbits; goto L10; } if (lexp == - (*emin)) { uexp = lexp; } else { uexp = try__; ++exbits; } /* Now -LEXP is less than or equal to EMIN, and -UEXP is greater than or equal to EMIN. EXBITS is the number of bits needed to store the exponent. */ if (uexp + *emin > -lexp - *emin) { expsum = lexp << 1; } else { expsum = uexp << 1; } /* EXPSUM is the exponent range, approximately equal to EMAX - EMIN + 1 . */ *emax = expsum + *emin - 1; nbits = exbits + 1 + *p; /* NBITS is the total number of bits needed to store a floating-point number. */ if (nbits % 2 == 1 && *beta == 2) { /* Either there are an odd number of bits used to store a floating-point number, which is unlikely, or some bits are not used in the representation of numbers, which is possible, (e.g. Cray machines) or the mantissa has an implicit bit, (e.g. IEEE machines, Dec Vax machines), which is perhaps the most likely. We have to assume the last alternative. If this is true, then we need to reduce EMAX by one because there must be some way of representing zero in an implicit-bit system. On machines like Cray, we are reducing EMAX by one unnecessarily. */ -- (*emax); } if (*ieee) { /* Assume we are on an IEEE machine which reserves one exponent for infinity and NaN. */ -- (*emax); } /* Now create RMAX, the largest machine number, which should be equal to (1.0 - BETA**(-P)) * BETA**EMAX . First compute 1.0 - BETA**(-P), being careful that the result is less than 1.0 . */ recbas = 1. / *beta; z = *beta - 1.; y = 0.; i__1 = *p; for (i = 1; i <= *p; ++i) { z *= recbas; if (y < 1.) { oldy = y; } y = dlamc3_ (&y, &z); /* L20: */ } if (y >= 1.) { y = oldy; } /* Now multiply by BETA**EMAX to get RMAX. */ i__1 = *emax; for (i = 1; i <= *emax; ++i) { d__1 = y * *beta; y = dlamc3_ (&d__1, &c_b5); /* L30: */ } *rmax = y; return 0; } /* dlamc5_ */ double NUMblas_dnrm2 (long *n, double *x, long *incx) { /* The following loop is equivalent to this call to the LAPACK auxiliary routine: CALL DLASSQ( N, X, INCX, SCALE, SSQ ) */ /* System generated locals */ long i__1, i__2; double ret_val, d__1; /* Local variables */ static double norm, scale, absxi; static long ix; static double ssq; --x; /* Function Body */ if (*n < 1 || *incx < 1) { norm = 0.; } else if (*n == 1) { norm = fabs (x[1]); } else { scale = 0.; ssq = 1.; i__1 = (*n - 1) * *incx + 1; i__2 = *incx; for (ix = 1; i__2 < 0 ? ix >= i__1 : ix <= i__1; ix += i__2) { if (x[ix] != 0.) { absxi = (d__1 = x[ix], fabs (d__1)); if (scale < absxi) { /* Computing 2nd power */ d__1 = scale / absxi; ssq = ssq * (d__1 * d__1) + 1.; scale = absxi; } else { /* Computing 2nd power */ d__1 = absxi / scale; ssq += d__1 * d__1; } } /* L10: */ } norm = scale * sqrt (ssq); } ret_val = norm; return ret_val; } /* NUMblas_dnrm2 */ int NUMblas_drot (long *n, double *dx, long *incx, double *dy, long *incy, double *c__, double *s) { /* System generated locals */ long i__1; /* Local variables */ static long i__; static double dtemp; static long ix, iy; /* applies a plane rotation. jack dongarra, linpack, 3/11/78. modified 12/3/93, array(1) declarations changed to array(*) Parameter adjustments */ --dy; --dx; /* Function Body */ if (*n <= 0) { return 0; } if (*incx == 1 && *incy == 1) { goto L20; } /* code for unequal increments or equal increments not equal to 1 */ ix = 1; iy = 1; if (*incx < 0) { ix = (- (*n) + 1) * *incx + 1; } if (*incy < 0) { iy = (- (*n) + 1) * *incy + 1; } i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { dtemp = *c__ * dx[ix] + *s * dy[iy]; dy[iy] = *c__ * dy[iy] - *s * dx[ix]; dx[ix] = dtemp; ix += *incx; iy += *incy; /* L10: */ } return 0; /* code for both increments equal to 1 */ L20: i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { dtemp = *c__ * dx[i__] + *s * dy[i__]; dy[i__] = *c__ * dy[i__] - *s * dx[i__]; dx[i__] = dtemp; /* L30: */ } return 0; } /* NUMblas_drot */ int NUMblas_dscal (long *n, double *da, double *dx, long *incx) { /* System generated locals */ long i__1, i__2; /* Local variables */ static long i__, m, nincx, mp1; /* Parameter adjustments */ --dx; /* Function Body */ if (*n <= 0 || *incx <= 0) { return 0; } if (*incx == 1) { goto L20; } /* code for increment not equal to 1 */ nincx = *n * *incx; i__1 = nincx; i__2 = *incx; for (i__ = 1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { dx[i__] = *da * dx[i__]; /* L10: */ } return 0; /* code for increment equal to 1 clean-up loop */ L20: m = *n % 5; if (m == 0) { goto L40; } i__2 = m; for (i__ = 1; i__ <= i__2; ++i__) { dx[i__] = *da * dx[i__]; /* L30: */ } if (*n < 5) { return 0; } L40: mp1 = m + 1; i__2 = *n; for (i__ = mp1; i__ <= i__2; i__ += 5) { dx[i__] = *da * dx[i__]; dx[i__ + 1] = *da * dx[i__ + 1]; dx[i__ + 2] = *da * dx[i__ + 2]; dx[i__ + 3] = *da * dx[i__ + 3]; dx[i__ + 4] = *da * dx[i__ + 4]; /* L50: */ } return 0; } /* dscal_ */ int NUMblas_dswap (long *n, double *dx, long *incx, double *dy, long *incy) { /* System generated locals */ long i__1; /* Local variables */ static long i__, m; static double dtemp; static long ix, iy, mp1; /* interchanges two vectors. uses unrolled loops for increments equal one. jack dongarra, linpack, 3/11/78. modified 12/3/93, array(1) declarations changed to array(*) Parameter adjustments */ --dy; --dx; /* Function Body */ if (*n <= 0) { return 0; } if (*incx == 1 && *incy == 1) { goto L20; } /* code for unequal increments or equal increments not equal to 1 */ ix = 1; iy = 1; if (*incx < 0) { ix = (- (*n) + 1) * *incx + 1; } if (*incy < 0) { iy = (- (*n) + 1) * *incy + 1; } i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { dtemp = dx[ix]; dx[ix] = dy[iy]; dy[iy] = dtemp; ix += *incx; iy += *incy; /* L10: */ } return 0; /* code for both increments equal to 1 clean-up loop */ L20: m = *n % 3; if (m == 0) { goto L40; } i__1 = m; for (i__ = 1; i__ <= i__1; ++i__) { dtemp = dx[i__]; dx[i__] = dy[i__]; dy[i__] = dtemp; /* L30: */ } if (*n < 3) { return 0; } L40: mp1 = m + 1; i__1 = *n; for (i__ = mp1; i__ <= i__1; i__ += 3) { dtemp = dx[i__]; dx[i__] = dy[i__]; dy[i__] = dtemp; dtemp = dx[i__ + 1]; dx[i__ + 1] = dy[i__ + 1]; dy[i__ + 1] = dtemp; dtemp = dx[i__ + 2]; dx[i__ + 2] = dy[i__ + 2]; dy[i__ + 2] = dtemp; /* L50: */ } return 0; } /* NUMblas_dswap */ int NUMblas_dsymv (const char *uplo, long *n, double *alpha, double *a, long *lda, double *x, long *incx, double *beta, double *y, long *incy) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2; /* Local variables */ static long info; static double temp1, temp2; static long i__, j; static long ix, iy, jx, jy, kx, ky; #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --x; --y; /* Function Body */ info = 0; if (!lsame_ (uplo, "U") && !lsame_ (uplo, "L")) { info = 1; } else if (*n < 0) { info = 2; } else if (*lda < MAX (1, *n)) { info = 5; } else if (*incx == 0) { info = 7; } else if (*incy == 0) { info = 10; } if (info != 0) { xerbla_ ("DSYMV ", &info); return 0; } /* Quick return if possible. */ if (*n == 0 || *alpha == 0. && *beta == 1.) { return 0; } /* Set up the start points in X and Y. */ if (*incx > 0) { kx = 1; } else { kx = 1 - (*n - 1) * *incx; } if (*incy > 0) { ky = 1; } else { ky = 1 - (*n - 1) * *incy; } /* Start the operations. In this version the elements of A are accessed sequentially with one pass through the triangular part of A. First form y := beta*y. */ if (*beta != 1.) { if (*incy == 1) { if (*beta == 0.) { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { y[i__] = 0.; /* L10: */ } } else { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { y[i__] = *beta * y[i__]; /* L20: */ } } } else { iy = ky; if (*beta == 0.) { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { y[iy] = 0.; iy += *incy; /* L30: */ } } else { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { y[iy] = *beta * y[iy]; iy += *incy; /* L40: */ } } } } if (*alpha == 0.) { return 0; } if (lsame_ (uplo, "U")) { /* Form y when A is stored in upper triangle. */ if (*incx == 1 && *incy == 1) { i__1 = *n; for (j = 1; j <= i__1; ++j) { temp1 = *alpha * x[j]; temp2 = 0.; i__2 = j - 1; for (i__ = 1; i__ <= i__2; ++i__) { y[i__] += temp1 * a_ref (i__, j); temp2 += a_ref (i__, j) * x[i__]; /* L50: */ } y[j] = y[j] + temp1 * a_ref (j, j) + *alpha * temp2; /* L60: */ } } else { jx = kx; jy = ky; i__1 = *n; for (j = 1; j <= i__1; ++j) { temp1 = *alpha * x[jx]; temp2 = 0.; ix = kx; iy = ky; i__2 = j - 1; for (i__ = 1; i__ <= i__2; ++i__) { y[iy] += temp1 * a_ref (i__, j); temp2 += a_ref (i__, j) * x[ix]; ix += *incx; iy += *incy; /* L70: */ } y[jy] = y[jy] + temp1 * a_ref (j, j) + *alpha * temp2; jx += *incx; jy += *incy; /* L80: */ } } } else { /* Form y when A is stored in lower triangle. */ if (*incx == 1 && *incy == 1) { i__1 = *n; for (j = 1; j <= i__1; ++j) { temp1 = *alpha * x[j]; temp2 = 0.; y[j] += temp1 * a_ref (j, j); i__2 = *n; for (i__ = j + 1; i__ <= i__2; ++i__) { y[i__] += temp1 * a_ref (i__, j); temp2 += a_ref (i__, j) * x[i__]; /* L90: */ } y[j] += *alpha * temp2; /* L100: */ } } else { jx = kx; jy = ky; i__1 = *n; for (j = 1; j <= i__1; ++j) { temp1 = *alpha * x[jx]; temp2 = 0.; y[jy] += temp1 * a_ref (j, j); ix = jx; iy = jy; i__2 = *n; for (i__ = j + 1; i__ <= i__2; ++i__) { ix += *incx; iy += *incy; y[iy] += temp1 * a_ref (i__, j); temp2 += a_ref (i__, j) * x[ix]; /* L110: */ } y[jy] += *alpha * temp2; jx += *incx; jy += *incy; /* L120: */ } } } return 0; } /* NUMblas_dsymv */ #undef a_ref int NUMblas_dsyr2 (const char *uplo, long *n, double *alpha, double *x, long *incx, double *y, long *incy, double *a, long *lda) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2; /* Local variables */ static long info; static double temp1, temp2; static long i__, j; static long ix, iy, jx, jy, kx, ky; #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] --x; --y; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; /* Function Body */ info = 0; if (!lsame_ (uplo, "U") && !lsame_ (uplo, "L")) { info = 1; } else if (*n < 0) { info = 2; } else if (*incx == 0) { info = 5; } else if (*incy == 0) { info = 7; } else if (*lda < MAX (1, *n)) { info = 9; } if (info != 0) { xerbla_ ("DSYR2 ", &info); return 0; } /* Quick return if possible. */ if (*n == 0 || *alpha == 0.) { return 0; } /* Set up the start points in X and Y if the increments are not both unity. */ if (*incx != 1 || *incy != 1) { if (*incx > 0) { kx = 1; } else { kx = 1 - (*n - 1) * *incx; } if (*incy > 0) { ky = 1; } else { ky = 1 - (*n - 1) * *incy; } jx = kx; jy = ky; } /* Start the operations. In this version the elements of A are accessed sequentially with one pass through the triangular part of A. */ if (lsame_ (uplo, "U")) { /* Form A when A is stored in the upper triangle. */ if (*incx == 1 && *incy == 1) { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (x[j] != 0. || y[j] != 0.) { temp1 = *alpha * y[j]; temp2 = *alpha * x[j]; i__2 = j; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) + x[i__] * temp1 + y[i__] * temp2; /* L10: */ } } /* L20: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (x[jx] != 0. || y[jy] != 0.) { temp1 = *alpha * y[jy]; temp2 = *alpha * x[jx]; ix = kx; iy = ky; i__2 = j; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) + x[ix] * temp1 + y[iy] * temp2; ix += *incx; iy += *incy; /* L30: */ } } jx += *incx; jy += *incy; /* L40: */ } } } else { /* Form A when A is stored in the lower triangle. */ if (*incx == 1 && *incy == 1) { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (x[j] != 0. || y[j] != 0.) { temp1 = *alpha * y[j]; temp2 = *alpha * x[j]; i__2 = *n; for (i__ = j; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) + x[i__] * temp1 + y[i__] * temp2; /* L50: */ } } /* L60: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (x[jx] != 0. || y[jy] != 0.) { temp1 = *alpha * y[jy]; temp2 = *alpha * x[jx]; ix = jx; iy = jy; i__2 = *n; for (i__ = j; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) + x[ix] * temp1 + y[iy] * temp2; ix += *incx; iy += *incy; /* L70: */ } } jx += *incx; jy += *incy; /* L80: */ } } } return 0; } /* NUMblas_dsyr2 */ #undef a_ref int NUMblas_dsyr2k (const char *uplo, const char *trans, long *n, long *k, double *alpha, double *a, long *lda, double *b, long *ldb, double *beta, double *c__, long *ldc) { /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, c_dim1, c_offset, i__1, i__2, i__3; /* Local variables */ static long info; static double temp1, temp2; static long i__, j, l; static long nrowa; static long upper; #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] #define b_ref(a_1,a_2) b[(a_2)*b_dim1 + a_1] #define c___ref(a_1,a_2) c__[(a_2)*c_dim1 + a_1] a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; /* Function Body */ if (lsame_ (trans, "N")) { nrowa = *n; } else { nrowa = *k; } upper = lsame_ (uplo, "U"); info = 0; if (!upper && !lsame_ (uplo, "L")) { info = 1; } else if (!lsame_ (trans, "N") && !lsame_ (trans, "T") && !lsame_ (trans, "C")) { info = 2; } else if (*n < 0) { info = 3; } else if (*k < 0) { info = 4; } else if (*lda < MAX (1, nrowa)) { info = 7; } else if (*ldb < MAX (1, nrowa)) { info = 9; } else if (*ldc < MAX (1, *n)) { info = 12; } if (info != 0) { xerbla_ ("DSYR2K", &info); return 0; } /* Quick return if possible. */ if (*n == 0 || (*alpha == 0. || *k == 0) && *beta == 1.) { return 0; } /* And when alpha.eq.zero. */ if (*alpha == 0.) { if (upper) { if (*beta == 0.) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = j; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = 0.; /* L10: */ } /* L20: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = j; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = *beta * c___ref (i__, j); /* L30: */ } /* L40: */ } } } else { if (*beta == 0.) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *n; for (i__ = j; i__ <= i__2; ++i__) { c___ref (i__, j) = 0.; /* L50: */ } /* L60: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *n; for (i__ = j; i__ <= i__2; ++i__) { c___ref (i__, j) = *beta * c___ref (i__, j); /* L70: */ } /* L80: */ } } } return 0; } /* Start the operations. */ if (lsame_ (trans, "N")) { /* Form C := alpha*A*B' + alpha*B*A' + C. */ if (upper) { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (*beta == 0.) { i__2 = j; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = 0.; /* L90: */ } } else if (*beta != 1.) { i__2 = j; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = *beta * c___ref (i__, j); /* L100: */ } } i__2 = *k; for (l = 1; l <= i__2; ++l) { if (a_ref (j, l) != 0. || b_ref (j, l) != 0.) { temp1 = *alpha * b_ref (j, l); temp2 = *alpha * a_ref (j, l); i__3 = j; for (i__ = 1; i__ <= i__3; ++i__) { c___ref (i__, j) = c___ref (i__, j) + a_ref (i__, l) * temp1 + b_ref (i__, l) * temp2; /* L110: */ } } /* L120: */ } /* L130: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (*beta == 0.) { i__2 = *n; for (i__ = j; i__ <= i__2; ++i__) { c___ref (i__, j) = 0.; /* L140: */ } } else if (*beta != 1.) { i__2 = *n; for (i__ = j; i__ <= i__2; ++i__) { c___ref (i__, j) = *beta * c___ref (i__, j); /* L150: */ } } i__2 = *k; for (l = 1; l <= i__2; ++l) { if (a_ref (j, l) != 0. || b_ref (j, l) != 0.) { temp1 = *alpha * b_ref (j, l); temp2 = *alpha * a_ref (j, l); i__3 = *n; for (i__ = j; i__ <= i__3; ++i__) { c___ref (i__, j) = c___ref (i__, j) + a_ref (i__, l) * temp1 + b_ref (i__, l) * temp2; /* L160: */ } } /* L170: */ } /* L180: */ } } } else { /* Form C := alpha*A'*B + alpha*B'*A + C. */ if (upper) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = j; for (i__ = 1; i__ <= i__2; ++i__) { temp1 = 0.; temp2 = 0.; i__3 = *k; for (l = 1; l <= i__3; ++l) { temp1 += a_ref (l, i__) * b_ref (l, j); temp2 += b_ref (l, i__) * a_ref (l, j); /* L190: */ } if (*beta == 0.) { c___ref (i__, j) = *alpha * temp1 + *alpha * temp2; } else { c___ref (i__, j) = *beta * c___ref (i__, j) + *alpha * temp1 + *alpha * temp2; } /* L200: */ } /* L210: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *n; for (i__ = j; i__ <= i__2; ++i__) { temp1 = 0.; temp2 = 0.; i__3 = *k; for (l = 1; l <= i__3; ++l) { temp1 += a_ref (l, i__) * b_ref (l, j); temp2 += b_ref (l, i__) * a_ref (l, j); /* L220: */ } if (*beta == 0.) { c___ref (i__, j) = *alpha * temp1 + *alpha * temp2; } else { c___ref (i__, j) = *beta * c___ref (i__, j) + *alpha * temp1 + *alpha * temp2; } /* L230: */ } /* L240: */ } } } return 0; } /* NUMblas_dsyr2k */ #undef c___ref #undef b_ref #undef a_ref int NUMblas_dtrmm (const char *side, const char *uplo, const char *transa, const char *diag, long *m, long *n, double *alpha, double *a, long *lda, double *b, long *ldb) { /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, i__1, i__2, i__3; /* Local variables */ static long info; static double temp; static long i__, j, k; static long lside; static long nrowa; static long upper; static long nounit; #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] #define b_ref(a_1,a_2) b[(a_2)*b_dim1 + a_1] /* Level 3 Blas routine. -- Written on 8-February-1989. Jack Dongarra, Argonne National Laboratory. Iain Duff, AERE Harwell. Jeremy Du Croz, Numerical Algorithms Group Ltd. Sven Hammarling, Numerical Algorithms Group Ltd. Test the input parameters. Parameter adjustments */ a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; /* Function Body */ lside = lsame_ (side, "L"); if (lside) { nrowa = *m; } else { nrowa = *n; } nounit = lsame_ (diag, "N"); upper = lsame_ (uplo, "U"); info = 0; if (!lside && !lsame_ (side, "R")) { info = 1; } else if (!upper && !lsame_ (uplo, "L")) { info = 2; } else if (!lsame_ (transa, "N") && !lsame_ (transa, "T") && !lsame_ (transa, "C")) { info = 3; } else if (!lsame_ (diag, "U") && !lsame_ (diag, "N")) { info = 4; } else if (*m < 0) { info = 5; } else if (*n < 0) { info = 6; } else if (*lda < MAX (1, nrowa)) { info = 9; } else if (*ldb < MAX (1, *m)) { info = 11; } if (info != 0) { xerbla_ ("DTRMM ", &info); return 0; } /* Quick return if possible. */ if (*n == 0) { return 0; } /* And when alpha.eq.zero. */ if (*alpha == 0.) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = 0.; /* L10: */ } /* L20: */ } return 0; } /* Start the operations. */ if (lside) { if (lsame_ (transa, "N")) { /* Form B := alpha*A*B. */ if (upper) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (k = 1; k <= i__2; ++k) { if (b_ref (k, j) != 0.) { temp = *alpha * b_ref (k, j); i__3 = k - 1; for (i__ = 1; i__ <= i__3; ++i__) { b_ref (i__, j) = b_ref (i__, j) + temp * a_ref (i__, k); /* L30: */ } if (nounit) { temp *= a_ref (k, k); } b_ref (k, j) = temp; } /* L40: */ } /* L50: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { for (k = *m; k >= 1; --k) { if (b_ref (k, j) != 0.) { temp = *alpha * b_ref (k, j); b_ref (k, j) = temp; if (nounit) { b_ref (k, j) = b_ref (k, j) * a_ref (k, k); } i__2 = *m; for (i__ = k + 1; i__ <= i__2; ++i__) { b_ref (i__, j) = b_ref (i__, j) + temp * a_ref (i__, k); /* L60: */ } } /* L70: */ } /* L80: */ } } } else { /* Form B := alpha*A'*B. */ if (upper) { i__1 = *n; for (j = 1; j <= i__1; ++j) { for (i__ = *m; i__ >= 1; --i__) { temp = b_ref (i__, j); if (nounit) { temp *= a_ref (i__, i__); } i__2 = i__ - 1; for (k = 1; k <= i__2; ++k) { temp += a_ref (k, i__) * b_ref (k, j); /* L90: */ } b_ref (i__, j) = *alpha * temp; /* L100: */ } /* L110: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { temp = b_ref (i__, j); if (nounit) { temp *= a_ref (i__, i__); } i__3 = *m; for (k = i__ + 1; k <= i__3; ++k) { temp += a_ref (k, i__) * b_ref (k, j); /* L120: */ } b_ref (i__, j) = *alpha * temp; /* L130: */ } /* L140: */ } } } } else { if (lsame_ (transa, "N")) { /* Form B := alpha*B*A. */ if (upper) { for (j = *n; j >= 1; --j) { temp = *alpha; if (nounit) { temp *= a_ref (j, j); } i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { b_ref (i__, j) = temp * b_ref (i__, j); /* L150: */ } i__1 = j - 1; for (k = 1; k <= i__1; ++k) { if (a_ref (k, j) != 0.) { temp = *alpha * a_ref (k, j); i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = b_ref (i__, j) + temp * b_ref (i__, k); /* L160: */ } } /* L170: */ } /* L180: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { temp = *alpha; if (nounit) { temp *= a_ref (j, j); } i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = temp * b_ref (i__, j); /* L190: */ } i__2 = *n; for (k = j + 1; k <= i__2; ++k) { if (a_ref (k, j) != 0.) { temp = *alpha * a_ref (k, j); i__3 = *m; for (i__ = 1; i__ <= i__3; ++i__) { b_ref (i__, j) = b_ref (i__, j) + temp * b_ref (i__, k); /* L200: */ } } /* L210: */ } /* L220: */ } } } else { /* Form B := alpha*B*A'. */ if (upper) { i__1 = *n; for (k = 1; k <= i__1; ++k) { i__2 = k - 1; for (j = 1; j <= i__2; ++j) { if (a_ref (j, k) != 0.) { temp = *alpha * a_ref (j, k); i__3 = *m; for (i__ = 1; i__ <= i__3; ++i__) { b_ref (i__, j) = b_ref (i__, j) + temp * b_ref (i__, k); /* L230: */ } } /* L240: */ } temp = *alpha; if (nounit) { temp *= a_ref (k, k); } if (temp != 1.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, k) = temp * b_ref (i__, k); /* L250: */ } } /* L260: */ } } else { for (k = *n; k >= 1; --k) { i__1 = *n; for (j = k + 1; j <= i__1; ++j) { if (a_ref (j, k) != 0.) { temp = *alpha * a_ref (j, k); i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = b_ref (i__, j) + temp * b_ref (i__, k); /* L270: */ } } /* L280: */ } temp = *alpha; if (nounit) { temp *= a_ref (k, k); } if (temp != 1.) { i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { b_ref (i__, k) = temp * b_ref (i__, k); /* L290: */ } } /* L300: */ } } } } return 0; } /* NUMblas_dtrmm */ #undef b_ref #undef a_ref int NUMblas_dtrmv (const char *uplo, const char *trans, const char *diag, long *n, double *a, long *lda, double *x, long *incx) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2; /* Local variables */ static long info; static double temp; static long i__, j; static long ix, jx, kx; static long nounit; #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] /* -- Written on 22-October-1986. Jack Dongarra, Argonne National Lab. Jeremy Du Croz, Nag Central Office. Sven Hammarling, Nag Central Office. Richard Hanson, Sandia National Labs. Test the input parameters. Parameter adjustments */ a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --x; /* Function Body */ info = 0; if (!lsame_ (uplo, "U") && !lsame_ (uplo, "L")) { info = 1; } else if (!lsame_ (trans, "N") && !lsame_ (trans, "T") && !lsame_ (trans, "C")) { info = 2; } else if (!lsame_ (diag, "U") && !lsame_ (diag, "N")) { info = 3; } else if (*n < 0) { info = 4; } else if (*lda < MAX (1, *n)) { info = 6; } else if (*incx == 0) { info = 8; } if (info != 0) { xerbla_ ("DTRMV ", &info); return 0; } /* Quick return if possible. */ if (*n == 0) { return 0; } nounit = lsame_ (diag, "N"); /* Set up the start point in X if the increment is not unity. This will be ( N - 1 )*INCX too small for descending loops. */ if (*incx <= 0) { kx = 1 - (*n - 1) * *incx; } else if (*incx != 1) { kx = 1; } /* Start the operations. In this version the elements of A are accessed sequentially with one pass through A. */ if (lsame_ (trans, "N")) { /* Form x := A*x. */ if (lsame_ (uplo, "U")) { if (*incx == 1) { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (x[j] != 0.) { temp = x[j]; i__2 = j - 1; for (i__ = 1; i__ <= i__2; ++i__) { x[i__] += temp * a_ref (i__, j); /* L10: */ } if (nounit) { x[j] *= a_ref (j, j); } } /* L20: */ } } else { jx = kx; i__1 = *n; for (j = 1; j <= i__1; ++j) { if (x[jx] != 0.) { temp = x[jx]; ix = kx; i__2 = j - 1; for (i__ = 1; i__ <= i__2; ++i__) { x[ix] += temp * a_ref (i__, j); ix += *incx; /* L30: */ } if (nounit) { x[jx] *= a_ref (j, j); } } jx += *incx; /* L40: */ } } } else { if (*incx == 1) { for (j = *n; j >= 1; --j) { if (x[j] != 0.) { temp = x[j]; i__1 = j + 1; for (i__ = *n; i__ >= i__1; --i__) { x[i__] += temp * a_ref (i__, j); /* L50: */ } if (nounit) { x[j] *= a_ref (j, j); } } /* L60: */ } } else { kx += (*n - 1) * *incx; jx = kx; for (j = *n; j >= 1; --j) { if (x[jx] != 0.) { temp = x[jx]; ix = kx; i__1 = j + 1; for (i__ = *n; i__ >= i__1; --i__) { x[ix] += temp * a_ref (i__, j); ix -= *incx; /* L70: */ } if (nounit) { x[jx] *= a_ref (j, j); } } jx -= *incx; /* L80: */ } } } } else { /* Form x := A'*x. */ if (lsame_ (uplo, "U")) { if (*incx == 1) { for (j = *n; j >= 1; --j) { temp = x[j]; if (nounit) { temp *= a_ref (j, j); } for (i__ = j - 1; i__ >= 1; --i__) { temp += a_ref (i__, j) * x[i__]; /* L90: */ } x[j] = temp; /* L100: */ } } else { jx = kx + (*n - 1) * *incx; for (j = *n; j >= 1; --j) { temp = x[jx]; ix = jx; if (nounit) { temp *= a_ref (j, j); } for (i__ = j - 1; i__ >= 1; --i__) { ix -= *incx; temp += a_ref (i__, j) * x[ix]; /* L110: */ } x[jx] = temp; jx -= *incx; /* L120: */ } } } else { if (*incx == 1) { i__1 = *n; for (j = 1; j <= i__1; ++j) { temp = x[j]; if (nounit) { temp *= a_ref (j, j); } i__2 = *n; for (i__ = j + 1; i__ <= i__2; ++i__) { temp += a_ref (i__, j) * x[i__]; /* L130: */ } x[j] = temp; /* L140: */ } } else { jx = kx; i__1 = *n; for (j = 1; j <= i__1; ++j) { temp = x[jx]; ix = jx; if (nounit) { temp *= a_ref (j, j); } i__2 = *n; for (i__ = j + 1; i__ <= i__2; ++i__) { ix += *incx; temp += a_ref (i__, j) * x[ix]; /* L150: */ } x[jx] = temp; jx += *incx; /* L160: */ } } } } return 0; } /* NUMblas_dtrmv */ #undef a_ref int NUMblas_dtrsm (const char *side, const char *uplo, const char *transa, const char *diag, long *m, long *n, double *alpha, double *a, long *lda, double *b, long *ldb) { /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, i__1, i__2, i__3; /* Local variables */ static long info; static double temp; static long i__, j, k; static long lside; static long nrowa; static long upper; static long nounit; #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] #define b_ref(a_1,a_2) b[(a_2)*b_dim1 + a_1] a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; /* Function Body */ lside = lsame_ (side, "L"); if (lside) { nrowa = *m; } else { nrowa = *n; } nounit = lsame_ (diag, "N"); upper = lsame_ (uplo, "U"); info = 0; if (!lside && !lsame_ (side, "R")) { info = 1; } else if (!upper && !lsame_ (uplo, "L")) { info = 2; } else if (!lsame_ (transa, "N") && !lsame_ (transa, "T") && !lsame_ (transa, "C")) { info = 3; } else if (!lsame_ (diag, "U") && !lsame_ (diag, "N")) { info = 4; } else if (*m < 0) { info = 5; } else if (*n < 0) { info = 6; } else if (*lda < MAX (1, nrowa)) { info = 9; } else if (*ldb < MAX (1, *m)) { info = 11; } if (info != 0) { xerbla_ ("DTRSM ", &info); return 0; } /* Quick return if possible. */ if (*n == 0) { return 0; } /* And when alpha.eq.zero. */ if (*alpha == 0.) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = 0.; /* L10: */ } /* L20: */ } return 0; } /* Start the operations. */ if (lside) { if (lsame_ (transa, "N")) { /* Form B := alpha*inv( A )*B. */ if (upper) { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (*alpha != 1.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = *alpha * b_ref (i__, j); /* L30: */ } } for (k = *m; k >= 1; --k) { if (b_ref (k, j) != 0.) { if (nounit) { b_ref (k, j) = b_ref (k, j) / a_ref (k, k); } i__2 = k - 1; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = b_ref (i__, j) - b_ref (k, j) * a_ref (i__, k); /* L40: */ } } /* L50: */ } /* L60: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (*alpha != 1.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = *alpha * b_ref (i__, j); /* L70: */ } } i__2 = *m; for (k = 1; k <= i__2; ++k) { if (b_ref (k, j) != 0.) { if (nounit) { b_ref (k, j) = b_ref (k, j) / a_ref (k, k); } i__3 = *m; for (i__ = k + 1; i__ <= i__3; ++i__) { b_ref (i__, j) = b_ref (i__, j) - b_ref (k, j) * a_ref (i__, k); /* L80: */ } } /* L90: */ } /* L100: */ } } } else { /* Form B := alpha*inv( A' )*B. */ if (upper) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { temp = *alpha * b_ref (i__, j); i__3 = i__ - 1; for (k = 1; k <= i__3; ++k) { temp -= a_ref (k, i__) * b_ref (k, j); /* L110: */ } if (nounit) { temp /= a_ref (i__, i__); } b_ref (i__, j) = temp; /* L120: */ } /* L130: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { for (i__ = *m; i__ >= 1; --i__) { temp = *alpha * b_ref (i__, j); i__2 = *m; for (k = i__ + 1; k <= i__2; ++k) { temp -= a_ref (k, i__) * b_ref (k, j); /* L140: */ } if (nounit) { temp /= a_ref (i__, i__); } b_ref (i__, j) = temp; /* L150: */ } /* L160: */ } } } } else { if (lsame_ (transa, "N")) { /* Form B := alpha*B*inv( A ). */ if (upper) { i__1 = *n; for (j = 1; j <= i__1; ++j) { if (*alpha != 1.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = *alpha * b_ref (i__, j); /* L170: */ } } i__2 = j - 1; for (k = 1; k <= i__2; ++k) { if (a_ref (k, j) != 0.) { i__3 = *m; for (i__ = 1; i__ <= i__3; ++i__) { b_ref (i__, j) = b_ref (i__, j) - a_ref (k, j) * b_ref (i__, k); /* L180: */ } } /* L190: */ } if (nounit) { temp = 1. / a_ref (j, j); i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = temp * b_ref (i__, j); /* L200: */ } } /* L210: */ } } else { for (j = *n; j >= 1; --j) { if (*alpha != 1.) { i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { b_ref (i__, j) = *alpha * b_ref (i__, j); /* L220: */ } } i__1 = *n; for (k = j + 1; k <= i__1; ++k) { if (a_ref (k, j) != 0.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = b_ref (i__, j) - a_ref (k, j) * b_ref (i__, k); /* L230: */ } } /* L240: */ } if (nounit) { temp = 1. / a_ref (j, j); i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { b_ref (i__, j) = temp * b_ref (i__, j); /* L250: */ } } /* L260: */ } } } else { /* Form B := alpha*B*inv( A' ). */ if (upper) { for (k = *n; k >= 1; --k) { if (nounit) { temp = 1. / a_ref (k, k); i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { b_ref (i__, k) = temp * b_ref (i__, k); /* L270: */ } } i__1 = k - 1; for (j = 1; j <= i__1; ++j) { if (a_ref (j, k) != 0.) { temp = a_ref (j, k); i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = b_ref (i__, j) - temp * b_ref (i__, k); /* L280: */ } } /* L290: */ } if (*alpha != 1.) { i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { b_ref (i__, k) = *alpha * b_ref (i__, k); /* L300: */ } } /* L310: */ } } else { i__1 = *n; for (k = 1; k <= i__1; ++k) { if (nounit) { temp = 1. / a_ref (k, k); i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, k) = temp * b_ref (i__, k); /* L320: */ } } i__2 = *n; for (j = k + 1; j <= i__2; ++j) { if (a_ref (j, k) != 0.) { temp = a_ref (j, k); i__3 = *m; for (i__ = 1; i__ <= i__3; ++i__) { b_ref (i__, j) = b_ref (i__, j) - temp * b_ref (i__, k); /* L330: */ } } /* L340: */ } if (*alpha != 1.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, k) = *alpha * b_ref (i__, k); /* L350: */ } } /* L360: */ } } } } return 0; } /* NUMblas_dtrsm */ #undef b_ref #undef a_ref long NUMblas_idamax (long *n, double *dx, long *incx) { /* System generated locals */ long ret_val, i__1; double d__1; /* Local variables */ static double dmax__; static long i__, ix; /* finds the index of element having max. absolute value. jack dongarra, linpack, 3/11/78. modified 3/93 to return if incx .le. 0. modified 12/3/93, array(1) declarations changed to array(*) Parameter adjustments */ --dx; /* Function Body */ ret_val = 0; if (*n < 1 || *incx <= 0) { return ret_val; } ret_val = 1; if (*n == 1) { return ret_val; } if (*incx == 1) { goto L20; } /* code for increment not equal to 1 */ ix = 1; dmax__ = fabs (dx[1]); ix += *incx; i__1 = *n; for (i__ = 2; i__ <= i__1; ++i__) { if ( (d__1 = dx[ix], fabs (d__1)) <= dmax__) { goto L5; } ret_val = i__; dmax__ = (d__1 = dx[ix], fabs (d__1)); L5: ix += *incx; /* L10: */ } return ret_val; /* code for increment equal to 1 */ L20: dmax__ = fabs (dx[1]); i__1 = *n; for (i__ = 2; i__ <= i__1; ++i__) { if ( (d__1 = dx[i__], fabs (d__1)) <= dmax__) { goto L30; } ret_val = i__; dmax__ = (d__1 = dx[i__], fabs (d__1)); L30: ; } return ret_val; } /* NUMblas_idamax */ #undef MAX #undef MIN /* End of file NUMcblas.c */ sources_5316/dwsys/NUMfft_f.cpp0000644000176700017670000000514011606610736015252 0ustar paulpaul/* NUMfft_f.c * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020701 GPL header djmw 20040511 Added n>1 test for compatibility with old behaviour. */ #include "NUM2.h" #include "melder.h" #define my me -> #define FFT_DATA_TYPE float #include "NUMfft_core.h" void NUMforwardRealFastFourierTransform_f (float *data, long n) { struct NUMfft_Table_f table_struct; NUMfft_Table_f table = &table_struct; NUMfft_Table_init_f (table, n); NUMfft_forward_f (table, data); if (n > 1) { // To be compatible with old behaviour float tmp = data[n]; for (long i = n; i > 2; i--) { data[i] = data[i - 1]; } data[2] = tmp; } NUMfft_Table_free_f (table); } void NUMreverseRealFastFourierTransform_f (float *data, long n) { struct NUMfft_Table_f table_struct; NUMfft_Table_f table = &table_struct; if (n > 1) { // To be compatible with old behaviour float tmp = data[2]; for (long i = 2; i < n; i++) { data[i] = data[i + 1]; } data[n] = tmp; } NUMfft_Table_init_f (table, n); NUMfft_backward_f (table, data); NUMfft_Table_free_f (table); } void NUMfft_forward_f (NUMfft_Table_f me, float *data) { if (my n == 1) { return; } drftf1 (my n, &data[1], my trigcache, my trigcache + my n, my splitcache); } void NUMfft_backward_f (NUMfft_Table_f me, float *data) { if (my n == 1) { return; } drftb1 (my n, &data[1], my trigcache, my trigcache + my n, my splitcache); } void NUMfft_Table_init_f (NUMfft_Table_f me, long n) { my n = n; my trigcache = NUMvector (0, 3 * n - 1); my splitcache = NUMvector (0, 31); NUMrffti (n, my trigcache, my splitcache); } void NUMfft_Table_free_f (NUMfft_Table_f me) { if (me) { NUMvector_free (my trigcache, 0); NUMvector_free (my splitcache, 0); } } void NUMrealft_f (float *data, long n, int isign) { isign == 1 ? NUMforwardRealFastFourierTransform_f (data, n) : NUMreverseRealFastFourierTransform_f (data, n); } /* End of file NUMfft.cpp */ sources_5316/dwsys/SimpleVector.h0000644000176700017670000000224111627165002015660 0ustar paulpaul#ifndef _SimpleVector_h_ #define _SimpleVector_h_ /* SimpleVector.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" #include "SimpleVector_def.h" oo_CLASS_CREATE (DoubleVector, Data); oo_CLASS_CREATE (ComplexVector, Data); void DoubleVector_init (I, long min, long max); DoubleVector DoubleVector_create (long min, long max); void ComplexVector_init (I, long min, long max); ComplexVector ComplexVector_create (long min, long max); #endif /* _SimpleVector_h_ */ sources_5316/dwsys/NUMfft_d.cpp0000644000176700017670000000450611606610736015255 0ustar paulpaul/* NUMfft_d.c * * Copyright (C) 1997-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header djmw 20040511 Added n>1 test for compatibility with old behaviour. djmw 20110308 struct renaming */ #include "NUM2.h" #include "melder.h" #define my me -> #define FFT_DATA_TYPE double #include "NUMfft_core.h" void NUMforwardRealFastFourierTransform (double *data, long n) { autoNUMfft_Table table; NUMfft_Table_init (& table, n); NUMfft_forward (& table, data); if (n > 1) { // To be compatible with old behaviour double tmp = data[n]; for (long i = n; i > 2; i--) { data[i] = data[i - 1]; } data[2] = tmp; } } void NUMreverseRealFastFourierTransform (double *data, long n) { autoNUMfft_Table table; if (n > 1) { // To be compatible with old behaviour double tmp = data[2]; for (long i = 2; i < n; i++) { data[i] = data[i + 1]; } data[n] = tmp; } NUMfft_Table_init (& table, n); NUMfft_backward (& table, data); } void NUMfft_forward (NUMfft_Table me, double *data) { if (my n == 1) { return; } drftf1 (my n, &data[1], my trigcache, my trigcache + my n, my splitcache); } void NUMfft_backward (NUMfft_Table me, double *data) { if (my n == 1) { return; } drftb1 (my n, &data[1], my trigcache, my trigcache + my n, my splitcache); } void NUMfft_Table_init (NUMfft_Table me, long n) { my n = n; my trigcache = NUMvector (0, 3 * n - 1); my splitcache = NUMvector (0, 31); NUMrffti (n, my trigcache, my splitcache); } void NUMrealft (double *data, long n, int isign) { isign == 1 ? NUMforwardRealFastFourierTransform (data, n) : NUMreverseRealFastFourierTransform (data, n); } /* End of file NUMfft.c */ sources_5316/dwsys/NUMclapack.cpp0000644000176700017670000175471311612037447015605 0ustar paulpaul/* NUMclapack.c */ /* -- LAPACK driver routines (version 3.0) -- Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., Courant Institute, Argonne National Lab, and Rice University October 31, 1999 -- translated by f2c (version 19990503). Adapted by David Weenink 20021201 djmw 20030205 Latest modification */ /* #include "blaswrap.h" */ #include "NUMf2c.h" #include "NUMclapack.h" #include "NUMcblas.h" #include "NUM2.h" #include "melder.h" /* Table of constant values */ static long c__0 = 0; static long c__1 = 1; static long c_n1 = -1; static long c__2 = 2; static long c__3 = 3; static long c__4 = 4; static long c__6 = 6; static long c__10 = 10; static long c__11 = 11; static double c_b15 = -.125; static double c_b49 = 1.; static double c_b72 = -1.; static double c_b74 = 0.; static double c_b108 = 1.; static double c_b416 = 0.; static double c_b438 = 1.; #define MAX(m,n) ((m) > (n) ? (m) : (n)) #define MIN(m,n) ((m) < (n) ? (m) : (n)) #define a_ref(a_1,a_2) a[(a_2)*a_dim1 + a_1] #define c___ref(a_1,a_2) c__[(a_2)*c_dim1 + a_1] /* --------------------------------------------------- */ #define u_ref(a_1,a_2) u[(a_2)*u_dim1 + a_1] #define vt_ref(a_1,a_2) vt[(a_2)*vt_dim1 + a_1] int NUMlapack_dbdsqr (const char *uplo, long *n, long *ncvt, long *nru, long *ncc, double *d__, double *e, double *vt, long *ldvt, double *u, long *ldu, double *c__, long *ldc, double *work, long *info) { /* System generated locals */ long c_dim1, c_offset, u_dim1, u_offset, vt_dim1, vt_offset, i__1, i__2; double d__1, d__2, d__3, d__4; /* Local variables */ static double abse; static long idir; static double abss; static long oldm; static double cosl; static long isub, iter; static double unfl, sinl, cosr, smin, smax, sinr; static double f, g, h__; static long i__, j, m; static double r__; static double oldcs; static long oldll; static double shift, sigmn, oldsn; static long maxit; static double sminl, sigmx; static long lower; static double cs; static long ll; static double sn, mu; static double sminoa, thresh; static long rotate; static double sminlo; static long nm1; static double tolmul; static long nm12, nm13, lll; static double eps, sll, tol; /* Parameter adjustments */ --d__; --e; vt_dim1 = *ldvt; vt_offset = 1 + vt_dim1 * 1; vt -= vt_offset; u_dim1 = *ldu; u_offset = 1 + u_dim1 * 1; u -= u_offset; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; --work; /* Function Body */ *info = 0; lower = lsame_ (uplo, "L"); if (!lsame_ (uplo, "U") && !lower) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*ncvt < 0) { *info = -3; } else if (*nru < 0) { *info = -4; } else if (*ncc < 0) { *info = -5; } else if (*ncvt == 0 && *ldvt < 1 || *ncvt > 0 && *ldvt < MAX (1, *n)) { *info = -9; } else if (*ldu < MAX (1, *nru)) { *info = -11; } else if (*ncc == 0 && *ldc < 1 || *ncc > 0 && *ldc < MAX (1, *n)) { *info = -13; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DBDSQR", &i__1); return 0; } if (*n == 0) { return 0; } if (*n == 1) { goto L160; } /* ROTATE is true if any singular vectors desired, false otherwise */ rotate = *ncvt > 0 || *nru > 0 || *ncc > 0; /* If no singular vectors desired, use qd algorithm */ if (!rotate) { NUMlapack_dlasq1 (n, &d__[1], &e[1], &work[1], info); return 0; } nm1 = *n - 1; nm12 = nm1 + nm1; nm13 = nm12 + nm1; idir = 0; /* Get machine constants */ eps = NUMblas_dlamch ("Epsilon"); unfl = NUMblas_dlamch ("Safe minimum"); /* If matrix lower bidiagonal, rotate to be upper bidiagonal by applying Givens rotations on the left */ if (lower) { i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { NUMlapack_dlartg (&d__[i__], &e[i__], &cs, &sn, &r__); d__[i__] = r__; e[i__] = sn * d__[i__ + 1]; d__[i__ + 1] = cs * d__[i__ + 1]; work[i__] = cs; work[nm1 + i__] = sn; /* L10: */ } /* Update singular vectors if desired */ if (*nru > 0) { NUMlapack_dlasr ("R", "V", "F", nru, n, &work[1], &work[*n], &u[u_offset], ldu); } if (*ncc > 0) { NUMlapack_dlasr ("L", "V", "F", n, ncc, &work[1], &work[*n], &c__[c_offset], ldc); } } /* Compute singular values to relative accuracy TOL (By setting TOL to be negative, algorithm will compute singular values to absolute accuracy ABS(TOL)*norm(input matrix)) Computing MAX Computing MIN */ d__3 = 100., d__4 = pow (eps, c_b15); d__1 = 10., d__2 = MIN (d__3, d__4); tolmul = MAX (d__1, d__2); tol = tolmul * eps; /* Compute approximate maximum, minimum singular values */ smax = 0.; i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { /* Computing MAX */ d__2 = smax, d__3 = (d__1 = d__[i__], fabs (d__1)); smax = MAX (d__2, d__3); /* L20: */ } i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { /* Computing MAX */ d__2 = smax, d__3 = (d__1 = e[i__], fabs (d__1)); smax = MAX (d__2, d__3); /* L30: */ } sminl = 0.; if (tol >= 0.) { /* Relative accuracy desired */ sminoa = fabs (d__[1]); if (sminoa == 0.) { goto L50; } mu = sminoa; i__1 = *n; for (i__ = 2; i__ <= i__1; ++i__) { mu = (d__2 = d__[i__], fabs (d__2)) * (mu / (mu + (d__1 = e[i__ - 1], fabs (d__1)))); sminoa = MIN (sminoa, mu); if (sminoa == 0.) { goto L50; } /* L40: */ } L50: sminoa /= sqrt ( (double) (*n)); /* Computing MAX */ d__1 = tol * sminoa, d__2 = *n * 6 * *n * unfl; thresh = MAX (d__1, d__2); } else { /* Absolute accuracy desired Computing MAX */ d__1 = fabs (tol) * smax, d__2 = *n * 6 * *n * unfl; thresh = MAX (d__1, d__2); } /* Prepare for main iteration loop for the singular values (MAXIT is the maximum number of passes through the inner loop permitted before nonconvergence signalled.) */ maxit = *n * 6 * *n; iter = 0; oldll = -1; oldm = -1; /* M points to last element of unconverged part of matrix */ m = *n; /* Begin main iteration loop */ L60: /* Check for convergence or exceeding iteration count */ if (m <= 1) { goto L160; } if (iter > maxit) { goto L200; } /* Find diagonal block of matrix to work on */ if (tol < 0. && (d__1 = d__[m], fabs (d__1)) <= thresh) { d__[m] = 0.; } smax = (d__1 = d__[m], fabs (d__1)); smin = smax; i__1 = m - 1; for (lll = 1; lll <= i__1; ++lll) { ll = m - lll; abss = (d__1 = d__[ll], fabs (d__1)); abse = (d__1 = e[ll], fabs (d__1)); if (tol < 0. && abss <= thresh) { d__[ll] = 0.; } if (abse <= thresh) { goto L80; } smin = MIN (smin, abss); /* Computing MAX */ d__1 = MAX (smax, abss); smax = MAX (d__1, abse); /* L70: */ } ll = 0; goto L90; L80: e[ll] = 0.; /* Matrix splits since E(LL) = 0 */ if (ll == m - 1) { /* Convergence of bottom singular value, return to top of loop */ --m; goto L60; } L90: ++ll; /* E(LL) through E(M-1) are nonzero, E(LL-1) is zero */ if (ll == m - 1) { /* 2 by 2 block, handle separately */ NUMlapack_dlasv2 (&d__[m - 1], &e[m - 1], &d__[m], &sigmn, &sigmx, &sinr, &cosr, &sinl, &cosl); d__[m - 1] = sigmx; e[m - 1] = 0.; d__[m] = sigmn; /* Compute singular vectors, if desired */ if (*ncvt > 0) { NUMblas_drot (ncvt, &vt_ref (m - 1, 1), ldvt, &vt_ref (m, 1), ldvt, &cosr, &sinr); } if (*nru > 0) { NUMblas_drot (nru, &u_ref (1, m - 1), &c__1, &u_ref (1, m), &c__1, &cosl, &sinl); } if (*ncc > 0) { NUMblas_drot (ncc, &c___ref (m - 1, 1), ldc, &c___ref (m, 1), ldc, &cosl, &sinl); } m += -2; goto L60; } /* If working on new submatrix, choose shift direction (from larger end diagonal element towards smaller) */ if (ll > oldm || m < oldll) { if ( (d__1 = d__[ll], fabs (d__1)) >= (d__2 = d__[m], fabs (d__2))) { /* Chase bulge from top (big end) to bottom (small end) */ idir = 1; } else { /* Chase bulge from bottom (big end) to top (small end) */ idir = 2; } } /* Apply convergence tests */ if (idir == 1) { /* Run convergence test in forward direction First apply standard test to bottom of matrix */ if ( (d__2 = e[m - 1], fabs (d__2)) <= fabs (tol) * (d__1 = d__[m], fabs (d__1)) || tol < 0. && (d__3 = e[m - 1], fabs (d__3)) <= thresh) { e[m - 1] = 0.; goto L60; } if (tol >= 0.) { /* If relative accuracy desired, apply convergence criterion forward */ mu = (d__1 = d__[ll], fabs (d__1)); sminl = mu; i__1 = m - 1; for (lll = ll; lll <= i__1; ++lll) { if ( (d__1 = e[lll], fabs (d__1)) <= tol * mu) { e[lll] = 0.; goto L60; } sminlo = sminl; mu = (d__2 = d__[lll + 1], fabs (d__2)) * (mu / (mu + (d__1 = e[lll], fabs (d__1)))); sminl = MIN (sminl, mu); /* L100: */ } } } else { /* Run convergence test in backward direction First apply standard test to top of matrix */ if ( (d__2 = e[ll], fabs (d__2)) <= fabs (tol) * (d__1 = d__[ll], fabs (d__1)) || tol < 0. && (d__3 = e[ll], fabs (d__3)) <= thresh) { e[ll] = 0.; goto L60; } if (tol >= 0.) { /* If relative accuracy desired, apply convergence criterion backward */ mu = (d__1 = d__[m], fabs (d__1)); sminl = mu; i__1 = ll; for (lll = m - 1; lll >= i__1; --lll) { if ( (d__1 = e[lll], fabs (d__1)) <= tol * mu) { e[lll] = 0.; goto L60; } sminlo = sminl; mu = (d__2 = d__[lll], fabs (d__2)) * (mu / (mu + (d__1 = e[lll], fabs (d__1)))); sminl = MIN (sminl, mu); /* L110: */ } } } oldll = ll; oldm = m; /* Compute shift. First, test if shifting would ruin relative accuracy, and if so set the shift to zero. Computing MAX */ d__1 = eps, d__2 = tol * .01; if (tol >= 0. && *n * tol * (sminl / smax) <= MAX (d__1, d__2)) { /* Use a zero shift to avoid loss of relative accuracy */ shift = 0.; } else { /* Compute the shift from 2-by-2 block at end of matrix */ if (idir == 1) { sll = (d__1 = d__[ll], fabs (d__1)); NUMlapack_dlas2 (&d__[m - 1], &e[m - 1], &d__[m], &shift, &r__); } else { sll = (d__1 = d__[m], fabs (d__1)); NUMlapack_dlas2 (&d__[ll], &e[ll], &d__[ll + 1], &shift, &r__); } /* Test if shift negligible, and if so set to zero */ if (sll > 0.) { /* Computing 2nd power */ d__1 = shift / sll; if (d__1 * d__1 < eps) { shift = 0.; } } } /* Increment iteration count */ iter = iter + m - ll; /* If SHIFT = 0, do simplified QR iteration */ if (shift == 0.) { if (idir == 1) { /* Chase bulge from top to bottom Save cosines and sines for later singular vector updates */ cs = 1.; oldcs = 1.; i__1 = m - 1; for (i__ = ll; i__ <= i__1; ++i__) { d__1 = d__[i__] * cs; NUMlapack_dlartg (&d__1, &e[i__], &cs, &sn, &r__); if (i__ > ll) { e[i__ - 1] = oldsn * r__; } d__1 = oldcs * r__; d__2 = d__[i__ + 1] * sn; NUMlapack_dlartg (&d__1, &d__2, &oldcs, &oldsn, &d__[i__]); work[i__ - ll + 1] = cs; work[i__ - ll + 1 + nm1] = sn; work[i__ - ll + 1 + nm12] = oldcs; work[i__ - ll + 1 + nm13] = oldsn; /* L120: */ } h__ = d__[m] * cs; d__[m] = h__ * oldcs; e[m - 1] = h__ * oldsn; /* Update singular vectors */ if (*ncvt > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("L", "V", "F", &i__1, ncvt, &work[1], &work[*n], &vt_ref (ll, 1), ldvt); } if (*nru > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("R", "V", "F", nru, &i__1, &work[nm12 + 1], &work[nm13 + 1], &u_ref (1, ll), ldu); } if (*ncc > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("L", "V", "F", &i__1, ncc, &work[nm12 + 1], &work[nm13 + 1], &c___ref (ll, 1), ldc); } /* Test convergence */ if ( (d__1 = e[m - 1], fabs (d__1)) <= thresh) { e[m - 1] = 0.; } } else { /* Chase bulge from bottom to top Save cosines and sines for later singular vector updates */ cs = 1.; oldcs = 1.; i__1 = ll + 1; for (i__ = m; i__ >= i__1; --i__) { d__1 = d__[i__] * cs; NUMlapack_dlartg (&d__1, &e[i__ - 1], &cs, &sn, &r__); if (i__ < m) { e[i__] = oldsn * r__; } d__1 = oldcs * r__; d__2 = d__[i__ - 1] * sn; NUMlapack_dlartg (&d__1, &d__2, &oldcs, &oldsn, &d__[i__]); work[i__ - ll] = cs; work[i__ - ll + nm1] = -sn; work[i__ - ll + nm12] = oldcs; work[i__ - ll + nm13] = -oldsn; /* L130: */ } h__ = d__[ll] * cs; d__[ll] = h__ * oldcs; e[ll] = h__ * oldsn; /* Update singular vectors */ if (*ncvt > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("L", "V", "B", &i__1, ncvt, &work[nm12 + 1], &work[nm13 + 1], &vt_ref (ll, 1), ldvt); } if (*nru > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("R", "V", "B", nru, &i__1, &work[1], &work[*n], &u_ref (1, ll), ldu); } if (*ncc > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("L", "V", "B", &i__1, ncc, &work[1], &work[*n], &c___ref (ll, 1), ldc); } /* Test convergence */ if ( (d__1 = e[ll], fabs (d__1)) <= thresh) { e[ll] = 0.; } } } else { /* Use nonzero shift */ if (idir == 1) { /* Chase bulge from top to bottom Save cosines and sines for later singular vector updates */ f = ( (d__1 = d__[ll], fabs (d__1)) - shift) * (d_sign (&c_b49, &d__[ll]) + shift / d__[ll]); g = e[ll]; i__1 = m - 1; for (i__ = ll; i__ <= i__1; ++i__) { NUMlapack_dlartg (&f, &g, &cosr, &sinr, &r__); if (i__ > ll) { e[i__ - 1] = r__; } f = cosr * d__[i__] + sinr * e[i__]; e[i__] = cosr * e[i__] - sinr * d__[i__]; g = sinr * d__[i__ + 1]; d__[i__ + 1] = cosr * d__[i__ + 1]; NUMlapack_dlartg (&f, &g, &cosl, &sinl, &r__); d__[i__] = r__; f = cosl * e[i__] + sinl * d__[i__ + 1]; d__[i__ + 1] = cosl * d__[i__ + 1] - sinl * e[i__]; if (i__ < m - 1) { g = sinl * e[i__ + 1]; e[i__ + 1] = cosl * e[i__ + 1]; } work[i__ - ll + 1] = cosr; work[i__ - ll + 1 + nm1] = sinr; work[i__ - ll + 1 + nm12] = cosl; work[i__ - ll + 1 + nm13] = sinl; /* L140: */ } e[m - 1] = f; /* Update singular vectors */ if (*ncvt > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("L", "V", "F", &i__1, ncvt, &work[1], &work[*n], &vt_ref (ll, 1), ldvt); } if (*nru > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("R", "V", "F", nru, &i__1, &work[nm12 + 1], &work[nm13 + 1], &u_ref (1, ll), ldu); } if (*ncc > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("L", "V", "F", &i__1, ncc, &work[nm12 + 1], &work[nm13 + 1], &c___ref (ll, 1), ldc); } /* Test convergence */ if ( (d__1 = e[m - 1], fabs (d__1)) <= thresh) { e[m - 1] = 0.; } } else { /* Chase bulge from bottom to top Save cosines and sines for later singular vector updates */ f = ( (d__1 = d__[m], fabs (d__1)) - shift) * (d_sign (&c_b49, &d__[m]) + shift / d__[m]); g = e[m - 1]; i__1 = ll + 1; for (i__ = m; i__ >= i__1; --i__) { NUMlapack_dlartg (&f, &g, &cosr, &sinr, &r__); if (i__ < m) { e[i__] = r__; } f = cosr * d__[i__] + sinr * e[i__ - 1]; e[i__ - 1] = cosr * e[i__ - 1] - sinr * d__[i__]; g = sinr * d__[i__ - 1]; d__[i__ - 1] = cosr * d__[i__ - 1]; NUMlapack_dlartg (&f, &g, &cosl, &sinl, &r__); d__[i__] = r__; f = cosl * e[i__ - 1] + sinl * d__[i__ - 1]; d__[i__ - 1] = cosl * d__[i__ - 1] - sinl * e[i__ - 1]; if (i__ > ll + 1) { g = sinl * e[i__ - 2]; e[i__ - 2] = cosl * e[i__ - 2]; } work[i__ - ll] = cosr; work[i__ - ll + nm1] = -sinr; work[i__ - ll + nm12] = cosl; work[i__ - ll + nm13] = -sinl; /* L150: */ } e[ll] = f; /* Test convergence */ if ( (d__1 = e[ll], fabs (d__1)) <= thresh) { e[ll] = 0.; } /* Update singular vectors if desired */ if (*ncvt > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("L", "V", "B", &i__1, ncvt, &work[nm12 + 1], &work[nm13 + 1], &vt_ref (ll, 1), ldvt); } if (*nru > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("R", "V", "B", nru, &i__1, &work[1], &work[*n], &u_ref (1, ll), ldu); } if (*ncc > 0) { i__1 = m - ll + 1; NUMlapack_dlasr ("L", "V", "B", &i__1, ncc, &work[1], &work[*n], &c___ref (ll, 1), ldc); } } } /* QR iteration finished, go back and check convergence */ goto L60; /* All singular values converged, so make them positive */ L160: i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { if (d__[i__] < 0.) { d__[i__] = -d__[i__]; /* Change sign of singular vectors, if desired */ if (*ncvt > 0) { NUMblas_dscal (ncvt, &c_b72, &vt_ref (i__, 1), ldvt); } } /* L170: */ } /* Sort the singular values into decreasing order (insertion sort on singular values, but only one transposition per singular vector) */ i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { /* Scan for smallest D(I) */ isub = 1; smin = d__[1]; i__2 = *n + 1 - i__; for (j = 2; j <= i__2; ++j) { if (d__[j] <= smin) { isub = j; smin = d__[j]; } /* L180: */ } if (isub != *n + 1 - i__) { /* Swap singular values and vectors */ d__[isub] = d__[*n + 1 - i__]; d__[*n + 1 - i__] = smin; if (*ncvt > 0) { NUMblas_dswap (ncvt, &vt_ref (isub, 1), ldvt, &vt_ref (*n + 1 - i__, 1), ldvt); } if (*nru > 0) { NUMblas_dswap (nru, &u_ref (1, isub), &c__1, &u_ref (1, *n + 1 - i__), &c__1); } if (*ncc > 0) { NUMblas_dswap (ncc, &c___ref (isub, 1), ldc, &c___ref (*n + 1 - i__, 1), ldc); } } /* L190: */ } goto L220; /* Maximum number of iterations exceeded, failure to converge */ L200: *info = 0; i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { if (e[i__] != 0.) { ++ (*info); } /* L210: */ } L220: return 0; } /* NUMlapack_dbdsqr */ #undef vt_ref #undef u_ref int NUMlapack_dgebd2 (long *m, long *n, double *a, long *lda, double *d__, double *e, double *tauq, double *taup, double *work, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4; /* Local variables */ static long i__; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --d__; --e; --tauq; --taup; --work; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } if (*info < 0) { i__1 = - (*info); xerbla_ ("DGEBD2", &i__1); return 0; } if (*m >= *n) { /* Reduce to upper bidiagonal form */ i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { /* Generate elementary reflector H(i) to annihilate A(i+1:m,i) Computing MIN */ i__2 = i__ + 1; i__3 = *m - i__ + 1; NUMlapack_dlarfg (&i__3, &a_ref (i__, i__), &a_ref (MIN (i__2, *m), i__), &c__1, &tauq[i__]); d__[i__] = a_ref (i__, i__); a_ref (i__, i__) = 1.; /* Apply H(i) to A(i:m,i+1:n) from the left */ i__2 = *m - i__ + 1; i__3 = *n - i__; NUMlapack_dlarf ("Left", &i__2, &i__3, &a_ref (i__, i__), &c__1, &tauq[i__], &a_ref (i__, i__ + 1), lda, &work[1]); a_ref (i__, i__) = d__[i__]; if (i__ < *n) { /* Generate elementary reflector G(i) to annihilate A(i,i+2:n) Computing MIN */ i__2 = i__ + 2; i__3 = *n - i__; NUMlapack_dlarfg (&i__3, &a_ref (i__, i__ + 1), &a_ref (i__, MIN (i__2, *n)), lda, &taup[i__]); e[i__] = a_ref (i__, i__ + 1); a_ref (i__, i__ + 1) = 1.; /* Apply G(i) to A(i+1:m,i+1:n) from the right */ i__2 = *m - i__; i__3 = *n - i__; NUMlapack_dlarf ("Right", &i__2, &i__3, &a_ref (i__, i__ + 1), lda, &taup[i__], &a_ref (i__ + 1, i__ + 1), lda, &work[1]); a_ref (i__, i__ + 1) = e[i__]; } else { taup[i__] = 0.; } /* L10: */ } } else { /* Reduce to lower bidiagonal form */ i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { /* Generate elementary reflector G(i) to annihilate A(i,i+1:n) Computing MIN */ i__2 = i__ + 1; i__3 = *n - i__ + 1; NUMlapack_dlarfg (&i__3, &a_ref (i__, i__), &a_ref (i__, MIN (i__2, *n)), lda, &taup[i__]); d__[i__] = a_ref (i__, i__); a_ref (i__, i__) = 1.; /* Apply G(i) to A(i+1:m,i:n) from the right Computing MIN */ i__2 = i__ + 1; i__3 = *m - i__; i__4 = *n - i__ + 1; NUMlapack_dlarf ("Right", &i__3, &i__4, &a_ref (i__, i__), lda, &taup[i__], &a_ref (MIN (i__2, *m), i__), lda, &work[1]); a_ref (i__, i__) = d__[i__]; if (i__ < *m) { /* Generate elementary reflector H(i) to annihilate A(i+2:m,i) Computing MIN */ i__2 = i__ + 2; i__3 = *m - i__; NUMlapack_dlarfg (&i__3, &a_ref (i__ + 1, i__), &a_ref (MIN (i__2, *m), i__), &c__1, &tauq[i__]); e[i__] = a_ref (i__ + 1, i__); a_ref (i__ + 1, i__) = 1.; /* Apply H(i) to A(i+1:m,i+1:n) from the left */ i__2 = *m - i__; i__3 = *n - i__; NUMlapack_dlarf ("Left", &i__2, &i__3, &a_ref (i__ + 1, i__), &c__1, &tauq[i__], &a_ref (i__ + 1, i__ + 1), lda, &work[1]); a_ref (i__ + 1, i__) = e[i__]; } else { tauq[i__] = 0.; } /* L20: */ } } return 0; } /* NUMlapack_dgebd2 */ int NUMlapack_dgebak (const char *job, const char *side, long *n, long *ilo, long *ihi, double *scale, long *m, double *v, long *ldv, long *info) { /* System generated locals */ long v_dim1, v_offset, i__1; /* Local variables */ static long i__, k; static double s; static int leftv; static long ii; static int rightv; #define v_ref(a_1,a_2) v[(a_2)*v_dim1 + a_1] --scale; v_dim1 = *ldv; v_offset = 1 + v_dim1 * 1; v -= v_offset; /* Function Body */ rightv = lsame_ (side, "R"); leftv = lsame_ (side, "L"); *info = 0; if (!lsame_ (job, "N") && !lsame_ (job, "P") && !lsame_ (job, "S") && !lsame_ (job, "B")) { *info = -1; } else if (!rightv && !leftv) { *info = -2; } else if (*n < 0) { *info = -3; } else if (*ilo < 1 || *ilo > MAX (1, *n)) { *info = -4; } else if (*ihi < MIN (*ilo, *n) || *ihi > *n) { *info = -5; } else if (*m < 0) { *info = -7; } else if (*ldv < MAX (1, *n)) { *info = -9; } if (*info != 0) { i__1 = - (*info); xerbla_ ("NUMlapack_dgebak ", &i__1); return 0; } /* Quick return if possible */ if (*n == 0) { return 0; } if (*m == 0) { return 0; } if (lsame_ (job, "N")) { return 0; } if (*ilo == *ihi) { goto L30; } /* Backward balance */ if (lsame_ (job, "S") || lsame_ (job, "B")) { if (rightv) { i__1 = *ihi; for (i__ = *ilo; i__ <= i__1; ++i__) { s = scale[i__]; NUMblas_dscal (m, &s, &v_ref (i__, 1), ldv); /* L10: */ } } if (leftv) { i__1 = *ihi; for (i__ = *ilo; i__ <= i__1; ++i__) { s = 1. / scale[i__]; NUMblas_dscal (m, &s, &v_ref (i__, 1), ldv); /* L20: */ } } } /* Backward permutation For I = ILO-1 step -1 until 1, IHI+1 step 1 until N do -- */ L30: if (lsame_ (job, "P") || lsame_ (job, "B")) { if (rightv) { i__1 = *n; for (ii = 1; ii <= i__1; ++ii) { i__ = ii; if (i__ >= *ilo && i__ <= *ihi) { goto L40; } if (i__ < *ilo) { i__ = *ilo - ii; } k = (long) scale[i__]; if (k == i__) { goto L40; } NUMblas_dswap (m, &v_ref (i__, 1), ldv, &v_ref (k, 1), ldv); L40: ; } } if (leftv) { i__1 = *n; for (ii = 1; ii <= i__1; ++ii) { i__ = ii; if (i__ >= *ilo && i__ <= *ihi) { goto L50; } if (i__ < *ilo) { i__ = *ilo - ii; } k = (long) scale[i__]; if (k == i__) { goto L50; } NUMblas_dswap (m, &v_ref (i__, 1), ldv, &v_ref (k, 1), ldv); L50: ; } } } return 0; } /* NUMlapack_dgebak */ #undef v_ref int NUMlapack_dgebal (const char *job, long *n, double *a, long *lda, long *ilo, long *ihi, double *scale, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2; double d__1, d__2; /* Local variables */ static long iexc; static double c__, f, g; static long i__, j, k, l, m; static double r__, s; static double sfmin1, sfmin2, sfmax1, sfmax2, ca, ra; static int noconv; static long ica, ira; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --scale; /* Function Body */ *info = 0; if (!lsame_ (job, "N") && !lsame_ (job, "P") && !lsame_ (job, "S") && !lsame_ (job, "B")) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *n)) { *info = -4; } if (*info != 0) { i__1 = - (*info); xerbla_ ("NUMlapack_dgebal ", &i__1); return 0; } k = 1; l = *n; if (*n == 0) { goto L210; } if (lsame_ (job, "N")) { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { scale[i__] = 1.; /* L10: */ } goto L210; } if (lsame_ (job, "S")) { goto L120; } /* Permutation to isolate eigenvalues if possible */ goto L50; /* Row and column exchange. */ L20: scale[m] = (double) j; if (j == m) { goto L30; } NUMblas_dswap (&l, &a_ref (1, j), &c__1, &a_ref (1, m), &c__1); i__1 = *n - k + 1; NUMblas_dswap (&i__1, &a_ref (j, k), lda, &a_ref (m, k), lda); L30: switch (iexc) { case 1: goto L40; case 2: goto L80; } /* Search for rows isolating an eigenvalue and push them down. */ L40: if (l == 1) { goto L210; } --l; L50: for (j = l; j >= 1; --j) { i__1 = l; for (i__ = 1; i__ <= i__1; ++i__) { if (i__ == j) { goto L60; } if (a_ref (j, i__) != 0.) { goto L70; } L60: ; } m = l; iexc = 1; goto L20; L70: ; } goto L90; /* Search for columns isolating an eigenvalue and push them left. */ L80: ++k; L90: i__1 = l; for (j = k; j <= i__1; ++j) { i__2 = l; for (i__ = k; i__ <= i__2; ++i__) { if (i__ == j) { goto L100; } if (a_ref (i__, j) != 0.) { goto L110; } L100: ; } m = k; iexc = 2; goto L20; L110: ; } L120: i__1 = l; for (i__ = k; i__ <= i__1; ++i__) { scale[i__] = 1.; /* L130: */ } if (lsame_ (job, "P")) { goto L210; } /* Balance the submatrix in rows K to L. Iterative loop for norm reduction */ sfmin1 = NUMblas_dlamch ("S") / NUMblas_dlamch ("P"); sfmax1 = 1. / sfmin1; sfmin2 = sfmin1 * 8.; sfmax2 = 1. / sfmin2; L140: noconv = FALSE; i__1 = l; for (i__ = k; i__ <= i__1; ++i__) { c__ = 0.; r__ = 0.; i__2 = l; for (j = k; j <= i__2; ++j) { if (j == i__) { goto L150; } c__ += (d__1 = a_ref (j, i__), fabs (d__1)); r__ += (d__1 = a_ref (i__, j), fabs (d__1)); L150: ; } ica = NUMblas_idamax (&l, &a_ref (1, i__), &c__1); ca = (d__1 = a_ref (ica, i__), fabs (d__1)); i__2 = *n - k + 1; ira = NUMblas_idamax (&i__2, &a_ref (i__, k), lda); ra = (d__1 = a_ref (i__, ira + k - 1), fabs (d__1)); /* Guard against zero C or R due to underflow. */ if (c__ == 0. || r__ == 0.) { goto L200; } g = r__ / 8.; f = 1.; s = c__ + r__; L160: /* Computing MAX */ d__1 = MAX (f, c__); /* Computing MIN */ d__2 = MIN (r__, g); if (c__ >= g || MAX (d__1, ca) >= sfmax2 || MIN (d__2, ra) <= sfmin2) { goto L170; } f *= 8.; c__ *= 8.; ca *= 8.; r__ /= 8.; g /= 8.; ra /= 8.; goto L160; L170: g = c__ / 8.; L180: /* Computing MIN */ d__1 = MIN (f, c__), d__1 = MIN (d__1, g); if (g < r__ || MAX (r__, ra) >= sfmax2 || MIN (d__1, ca) <= sfmin2) { goto L190; } f /= 8.; c__ /= 8.; g /= 8.; ca /= 8.; r__ *= 8.; ra *= 8.; goto L180; /* Now balance. */ L190: if (c__ + r__ >= s * .95) { goto L200; } if (f < 1. && scale[i__] < 1.) { if (f * scale[i__] <= sfmin1) { goto L200; } } if (f > 1. && scale[i__] > 1.) { if (scale[i__] >= sfmax1 / f) { goto L200; } } g = 1. / f; scale[i__] *= f; noconv = TRUE; i__2 = *n - k + 1; NUMblas_dscal (&i__2, &g, &a_ref (i__, k), lda); NUMblas_dscal (&l, &f, &a_ref (1, i__), &c__1); L200: ; } if (noconv) { goto L140; } L210: *ilo = k; *ihi = l; return 0; } /* NUMlapack_dgebal */ int NUMlapack_dgebrd (long *m, long *n, double *a, long *lda, double *d__, double *e, double *tauq, double *taup, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__3 = 3; static long c__2 = 2; static double c_b21 = -1.; static double c_b22 = 1.; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4; /* Local variables */ static long i__, j; static long nbmin, iinfo, minmn; static long nb; static long nx; static double ws; static long ldwrkx, ldwrky, lwkopt; static long lquery; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --d__; --e; --tauq; --taup; --work; /* Function Body */ *info = 0; /* Computing MAX */ i__1 = 1, i__2 = NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, n, &c_n1, &c_n1, 6, 1); nb = MAX (i__1, i__2); lwkopt = (*m + *n) * nb; work[1] = (double) lwkopt; lquery = *lwork == -1; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } else { /* if(complicated condition) */ /* Computing MAX */ i__1 = MAX (1, *m); if (*lwork < MAX (i__1, *n) && !lquery) { *info = -10; } } if (*info < 0) { i__1 = - (*info); xerbla_ ("DGEBRD", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ minmn = MIN (*m, *n); if (minmn == 0) { work[1] = 1.; return 0; } ws = (double) MAX (*m, *n); ldwrkx = *m; ldwrky = *n; if (nb > 1 && nb < minmn) { /* Set the crossover point NX. Computing MAX */ i__1 = nb, i__2 = NUMlapack_ilaenv (&c__3, "DGEBRD", " ", m, n, &c_n1, &c_n1, 6, 1); nx = MAX (i__1, i__2); /* Determine when to switch from blocked to unblocked code. */ if (nx < minmn) { ws = (double) ( (*m + *n) * nb); if ( (double) (*lwork) < ws) { /* Not enough work space for the optimal NB, consider using a smaller block size. */ nbmin = NUMlapack_ilaenv (&c__2, "DGEBRD", " ", m, n, &c_n1, &c_n1, 6, 1); if (*lwork >= (*m + *n) * nbmin) { nb = *lwork / (*m + *n); } else { nb = 1; nx = minmn; } } } } else { nx = minmn; } i__1 = minmn - nx; i__2 = nb; for (i__ = 1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Reduce rows and columns i:i+nb-1 to bidiagonal form and return the matrices X and Y which are needed to update the unreduced part of the matrix */ i__3 = *m - i__ + 1; i__4 = *n - i__ + 1; NUMlapack_dlabrd (&i__3, &i__4, &nb, &a_ref (i__, i__), lda, &d__[i__], &e[i__], &tauq[i__], &taup[i__], &work[1], &ldwrkx, &work[ldwrkx * nb + 1], &ldwrky); /* Update the trailing submatrix A(i+nb:m,i+nb:n), using an update of the form A := A - V*Y' - X*U' */ i__3 = *m - i__ - nb + 1; i__4 = *n - i__ - nb + 1; NUMblas_dgemm ("No transpose", "Transpose", &i__3, &i__4, &nb, &c_b21, &a_ref (i__ + nb, i__), lda, &work[ldwrkx * nb + nb + 1], &ldwrky, &c_b22, &a_ref (i__ + nb, i__ + nb), lda); i__3 = *m - i__ - nb + 1; i__4 = *n - i__ - nb + 1; NUMblas_dgemm ("No transpose", "No transpose", &i__3, &i__4, &nb, &c_b21, &work[nb + 1], &ldwrkx, &a_ref (i__, i__ + nb), lda, &c_b22, &a_ref (i__ + nb, i__ + nb), lda); /* Copy diagonal and off-diagonal elements of B back into A */ if (*m >= *n) { i__3 = i__ + nb - 1; for (j = i__; j <= i__3; ++j) { a_ref (j, j) = d__[j]; a_ref (j, j + 1) = e[j]; /* L10: */ } } else { i__3 = i__ + nb - 1; for (j = i__; j <= i__3; ++j) { a_ref (j, j) = d__[j]; a_ref (j + 1, j) = e[j]; /* L20: */ } } /* L30: */ } /* Use unblocked code to reduce the remainder of the matrix */ i__2 = *m - i__ + 1; i__1 = *n - i__ + 1; NUMlapack_dgebd2 (&i__2, &i__1, &a_ref (i__, i__), lda, &d__[i__], &e[i__], &tauq[i__], &taup[i__], &work[1], &iinfo); work[1] = ws; return 0; } /* NUMlapack_dgebrd */ int NUMlapack_dgeev (const char *jobvl, const char *jobvr, long *n, double *a, long *lda, double *wr, double *wi, double *vl, long *ldvl, double *vr, long *ldvr, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__8 = 8; static long c_n1 = -1; /* System generated locals */ long a_dim1, a_offset, vl_dim1, vl_offset, vr_dim1, vr_offset, i__1, i__2, i__3, i__4; double d__1, d__2; /* Local variables */ static long ibal; static char side[1]; static long maxb; static double anrm; static long ierr, itau; static long iwrk, nout; static long i__, k; static double r__; static double cs; static int scalea; static double cscale; static double sn; static int select[1]; static double bignum; static long minwrk, maxwrk; static int wantvl; static double smlnum; static long hswork; static int lquery, wantvr; static long ihi; static double scl; static long ilo; static double dum[1], eps; #define vl_ref(a_1,a_2) vl[(a_2)*vl_dim1 + a_1] #define vr_ref(a_1,a_2) vr[(a_2)*vr_dim1 + a_1] a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --wr; --wi; vl_dim1 = *ldvl; vl_offset = 1 + vl_dim1 * 1; vl -= vl_offset; vr_dim1 = *ldvr; vr_offset = 1 + vr_dim1 * 1; vr -= vr_offset; --work; /* Function Body */ *info = 0; lquery = *lwork == -1; wantvl = lsame_ (jobvl, "V"); wantvr = lsame_ (jobvr, "V"); if (!wantvl && !lsame_ (jobvl, "N")) { *info = -1; } else if (!wantvr && !lsame_ (jobvr, "N")) { *info = -2; } else if (*n < 0) { *info = -3; } else if (*lda < MAX (1, *n)) { *info = -5; } else if (*ldvl < 1 || wantvl && *ldvl < *n) { *info = -9; } else if (*ldvr < 1 || wantvr && *ldvr < *n) { *info = -11; } /* Compute workspace (Note: Comments in the code beginning "Workspace:" describe the minimal amount of workspace needed at that point in the code, as well as the preferred amount for good performance. NB refers to the optimal block size for the immediately following subroutine, as returned by ILAENV. HSWORK refers to the workspace preferred by NUMlapack_dhseqr , as calculated below. HSWORK is computed assuming ILO=1 and IHI=N, the worst case.) */ minwrk = 1; if (*info == 0 && (*lwork >= 1 || lquery)) { maxwrk = (*n << 1) + *n * NUMlapack_ilaenv (&c__1, "NUMlapack_dgehrd ", " ", n, &c__1, n, &c__0, 6, 1); if (!wantvl && !wantvr) { /* Computing MAX */ i__1 = 1, i__2 = *n * 3; minwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = NUMlapack_ilaenv (&c__8, "NUMlapack_dhseqr ", "EN", n, &c__1, n, &c_n1, 6, 2); maxb = MAX (i__1, 2); /* Computing MIN Computing MAX */ i__3 = 2, i__4 = NUMlapack_ilaenv (&c__4, "NUMlapack_dhseqr ", "EN", n, &c__1, n, &c_n1, 6, 2); i__1 = MIN (maxb, *n), i__2 = MAX (i__3, i__4); k = MIN (i__1, i__2); /* Computing MAX */ i__1 = k * (k + 2), i__2 = *n << 1; hswork = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *n + 1, i__1 = MAX (i__1, i__2), i__2 = *n + hswork; maxwrk = MAX (i__1, i__2); } else { /* Computing MAX */ i__1 = 1, i__2 = *n << 2; minwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = (*n << 1) + (*n - 1) * NUMlapack_ilaenv (&c__1, "DOR" "GHR", " ", n, &c__1, n, &c_n1, 6, 1); maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = NUMlapack_ilaenv (&c__8, "NUMlapack_dhseqr ", "SV", n, &c__1, n, &c_n1, 6, 2); maxb = MAX (i__1, 2); /* Computing MIN Computing MAX */ i__3 = 2, i__4 = NUMlapack_ilaenv (&c__4, "NUMlapack_dhseqr ", "SV", n, &c__1, n, &c_n1, 6, 2); i__1 = MIN (maxb, *n), i__2 = MAX (i__3, i__4); k = MIN (i__1, i__2); /* Computing MAX */ i__1 = k * (k + 2), i__2 = *n << 1; hswork = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *n + 1, i__1 = MAX (i__1, i__2), i__2 = *n + hswork; maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *n << 2; maxwrk = MAX (i__1, i__2); } work[1] = (double) maxwrk; } if (*lwork < minwrk && !lquery) { *info = -13; } if (*info != 0) { i__1 = - (*info); xerbla_ ("NUMlapack_dgeev ", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*n == 0) { return 0; } /* Get machine constants */ eps = NUMblas_dlamch ("P"); smlnum = NUMblas_dlamch ("S"); bignum = 1. / smlnum; NUMlapack_dlabad (&smlnum, &bignum); smlnum = sqrt (smlnum) / eps; bignum = 1. / smlnum; /* Scale A if max element outside range [SMLNUM,BIGNUM] */ anrm = NUMlapack_dlange ("M", n, n, &a[a_offset], lda, dum); scalea = FALSE; if (anrm > 0. && anrm < smlnum) { scalea = TRUE; cscale = smlnum; } else if (anrm > bignum) { scalea = TRUE; cscale = bignum; } if (scalea) { NUMlapack_dlascl ("G", &c__0, &c__0, &anrm, &cscale, n, n, &a[a_offset], lda, &ierr); } /* Balance the matrix (Workspace: need N) */ ibal = 1; NUMlapack_dgebal ("B", n, &a[a_offset], lda, &ilo, &ihi, &work[ibal], &ierr); /* Reduce to upper Hessenberg form (Workspace: need 3*N, prefer 2*N+N*NB) */ itau = ibal + *n; iwrk = itau + *n; i__1 = *lwork - iwrk + 1; NUMlapack_dgehrd (n, &ilo, &ihi, &a[a_offset], lda, &work[itau], &work[iwrk], &i__1, &ierr); if (wantvl) { /* Want left eigenvectors Copy Householder vectors to VL */ * (unsigned char *) side = 'L'; NUMlapack_dlacpy ("L", n, n, &a[a_offset], lda, &vl[vl_offset], ldvl); /* Generate orthogonal matrix in VL (Workspace: need 3*N-1, prefer 2*N+(N-1)*NB) */ i__1 = *lwork - iwrk + 1; NUMlapack_dorghr (n, &ilo, &ihi, &vl[vl_offset], ldvl, &work[itau], &work[iwrk], &i__1, &ierr); /* Perform QR iteration, accumulating Schur vectors in VL (Workspace: need N+1, prefer N+HSWORK (see comments) ) */ iwrk = itau; i__1 = *lwork - iwrk + 1; NUMlapack_dhseqr ("S", "V", n, &ilo, &ihi, &a[a_offset], lda, &wr[1], &wi[1], &vl[vl_offset], ldvl, &work[iwrk], &i__1, info); if (wantvr) { /* Want left and right eigenvectors Copy Schur vectors to VR */ * (unsigned char *) side = 'B'; NUMlapack_dlacpy ("F", n, n, &vl[vl_offset], ldvl, &vr[vr_offset], ldvr); } } else if (wantvr) { /* Want right eigenvectors Copy Householder vectors to VR */ * (unsigned char *) side = 'R'; NUMlapack_dlacpy ("L", n, n, &a[a_offset], lda, &vr[vr_offset], ldvr); /* Generate orthogonal matrix in VR (Workspace: need 3*N-1, prefer 2*N+(N-1)*NB) */ i__1 = *lwork - iwrk + 1; NUMlapack_dorghr (n, &ilo, &ihi, &vr[vr_offset], ldvr, &work[itau], &work[iwrk], &i__1, &ierr); /* Perform QR iteration, accumulating Schur vectors in VR (Workspace: need N+1, prefer N+HSWORK (see comments) ) */ iwrk = itau; i__1 = *lwork - iwrk + 1; NUMlapack_dhseqr ("S", "V", n, &ilo, &ihi, &a[a_offset], lda, &wr[1], &wi[1], &vr[vr_offset], ldvr, &work[iwrk], &i__1, info); } else { /* Compute eigenvalues only (Workspace: need N+1, prefer N+HSWORK (see comments) ) */ iwrk = itau; i__1 = *lwork - iwrk + 1; NUMlapack_dhseqr ("E", "N", n, &ilo, &ihi, &a[a_offset], lda, &wr[1], &wi[1], &vr[vr_offset], ldvr, &work[iwrk], &i__1, info); } /* If INFO > 0 from NUMlapack_dhseqr , then quit */ if (*info > 0) { goto L50; } if (wantvl || wantvr) { /* Compute left and/or right eigenvectors (Workspace: need 4*N) */ NUMlapack_dtrevc (side, "B", select, n, &a[a_offset], lda, &vl[vl_offset], ldvl, &vr[vr_offset], ldvr, n, &nout, &work[iwrk], &ierr); } if (wantvl) { /* Undo balancing of left eigenvectors (Workspace: need N) */ NUMlapack_dgebak ("B", "L", n, &ilo, &ihi, &work[ibal], n, &vl[vl_offset], ldvl, &ierr); /* Normalize left eigenvectors and make largest component real */ i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { if (wi[i__] == 0.) { scl = 1. / NUMblas_dnrm2 (n, &vl_ref (1, i__), &c__1); NUMblas_dscal (n, &scl, &vl_ref (1, i__), &c__1); } else if (wi[i__] > 0.) { d__1 = NUMblas_dnrm2 (n, &vl_ref (1, i__), &c__1); d__2 = NUMblas_dnrm2 (n, &vl_ref (1, i__ + 1), &c__1); scl = 1. / NUMlapack_dlapy2 (&d__1, &d__2); NUMblas_dscal (n, &scl, &vl_ref (1, i__), &c__1); NUMblas_dscal (n, &scl, &vl_ref (1, i__ + 1), &c__1); i__2 = *n; for (k = 1; k <= i__2; ++k) { /* Computing 2nd power */ d__1 = vl_ref (k, i__); /* Computing 2nd power */ d__2 = vl_ref (k, i__ + 1); work[iwrk + k - 1] = d__1 * d__1 + d__2 * d__2; /* L10: */ } k = NUMblas_idamax (n, &work[iwrk], &c__1); NUMlapack_dlartg (&vl_ref (k, i__), &vl_ref (k, i__ + 1), &cs, &sn, &r__); NUMblas_drot (n, &vl_ref (1, i__), &c__1, &vl_ref (1, i__ + 1), &c__1, &cs, &sn); vl_ref (k, i__ + 1) = 0.; } /* L20: */ } } if (wantvr) { /* Undo balancing of right eigenvectors (Workspace: need N) */ NUMlapack_dgebak ("B", "R", n, &ilo, &ihi, &work[ibal], n, &vr[vr_offset], ldvr, &ierr); /* Normalize right eigenvectors and make largest component real */ i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { if (wi[i__] == 0.) { scl = 1. / NUMblas_dnrm2 (n, &vr_ref (1, i__), &c__1); NUMblas_dscal (n, &scl, &vr_ref (1, i__), &c__1); } else if (wi[i__] > 0.) { d__1 = NUMblas_dnrm2 (n, &vr_ref (1, i__), &c__1); d__2 = NUMblas_dnrm2 (n, &vr_ref (1, i__ + 1), &c__1); scl = 1. / NUMlapack_dlapy2 (&d__1, &d__2); NUMblas_dscal (n, &scl, &vr_ref (1, i__), &c__1); NUMblas_dscal (n, &scl, &vr_ref (1, i__ + 1), &c__1); i__2 = *n; for (k = 1; k <= i__2; ++k) { /* Computing 2nd power */ d__1 = vr_ref (k, i__); /* Computing 2nd power */ d__2 = vr_ref (k, i__ + 1); work[iwrk + k - 1] = d__1 * d__1 + d__2 * d__2; /* L30: */ } k = NUMblas_idamax (n, &work[iwrk], &c__1); NUMlapack_dlartg (&vr_ref (k, i__), &vr_ref (k, i__ + 1), &cs, &sn, &r__); NUMblas_drot (n, &vr_ref (1, i__), &c__1, &vr_ref (1, i__ + 1), &c__1, &cs, &sn); vr_ref (k, i__ + 1) = 0.; } /* L40: */ } } /* Undo scaling if necessary */ L50: if (scalea) { i__1 = *n - *info; /* Computing MAX */ i__3 = *n - *info; i__2 = MAX (i__3, 1); NUMlapack_dlascl ("G", &c__0, &c__0, &cscale, &anrm, &i__1, &c__1, &wr[*info + 1], &i__2, &ierr); i__1 = *n - *info; /* Computing MAX */ i__3 = *n - *info; i__2 = MAX (i__3, 1); NUMlapack_dlascl ("G", &c__0, &c__0, &cscale, &anrm, &i__1, &c__1, &wi[*info + 1], &i__2, &ierr); if (*info > 0) { i__1 = ilo - 1; NUMlapack_dlascl ("G", &c__0, &c__0, &cscale, &anrm, &i__1, &c__1, &wr[1], n, &ierr); i__1 = ilo - 1; NUMlapack_dlascl ("G", &c__0, &c__0, &cscale, &anrm, &i__1, &c__1, &wi[1], n, &ierr); } } work[1] = (double) maxwrk; return 0; } /* NUMlapack_dgeev */ #undef vr_ref #undef vl_ref int NUMlapack_dgehd2 (long *n, long *ilo, long *ihi, double *a, long *lda, double *tau, double *work, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__; static double aii; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; if (*n < 0) { *info = -1; } else if (*ilo < 1 || *ilo > MAX (1, *n)) { *info = -2; } else if (*ihi < MIN (*ilo, *n) || *ihi > *n) { *info = -3; } else if (*lda < MAX (1, *n)) { *info = -5; } if (*info != 0) { i__1 = - (*info); xerbla_ ("NUMlapack_dgehd2 ", &i__1); return 0; } i__1 = *ihi - 1; for (i__ = *ilo; i__ <= i__1; ++i__) { /* Compute elementary reflector H(i) to annihilate A(i+2:ihi,i) Computing MIN */ i__2 = i__ + 2; i__3 = *ihi - i__; NUMlapack_dlarfg (&i__3, &a_ref (i__ + 1, i__), &a_ref (MIN (i__2, *n), i__), &c__1, &tau[i__]); aii = a_ref (i__ + 1, i__); a_ref (i__ + 1, i__) = 1.; /* Apply H(i) to A(1:ihi,i+1:ihi) from the right */ i__2 = *ihi - i__; NUMlapack_dlarf ("Right", ihi, &i__2, &a_ref (i__ + 1, i__), &c__1, &tau[i__], &a_ref (1, i__ + 1), lda, &work[1]); /* Apply H(i) to A(i+1:ihi,i+1:n) from the left */ i__2 = *ihi - i__; i__3 = *n - i__; NUMlapack_dlarf ("Left", &i__2, &i__3, &a_ref (i__ + 1, i__), &c__1, &tau[i__], &a_ref (i__ + 1, i__ + 1), lda, &work[1]); a_ref (i__ + 1, i__) = aii; /* L10: */ } return 0; } /* NUMlapack_dgehd2 */ int NUMlapack_dgehrd (long *n, long *ilo, long *ihi, double *a, long *lda, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__3 = 3; static long c__2 = 2; static long c__65 = 65; static double c_b25 = -1.; static double c_b26 = 1.; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4; /* Local variables */ static long i__; static double t[4160] /* was [65][64] */ ; static long nbmin, iinfo; static long ib; static double ei; static long nb, nh; static long nx; static long ldwork, lwkopt; static int lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; /* Computing MIN */ i__1 = 64, i__2 = NUMlapack_ilaenv (&c__1, "NUMlapack_dgehrd ", " ", n, ilo, ihi, &c_n1, 6, 1); nb = MIN (i__1, i__2); lwkopt = *n * nb; work[1] = (double) lwkopt; lquery = *lwork == -1; if (*n < 0) { *info = -1; } else if (*ilo < 1 || *ilo > MAX (1, *n)) { *info = -2; } else if (*ihi < MIN (*ilo, *n) || *ihi > *n) { *info = -3; } else if (*lda < MAX (1, *n)) { *info = -5; } else if (*lwork < MAX (1, *n) && !lquery) { *info = -8; } if (*info != 0) { i__1 = - (*info); xerbla_ ("NUMlapack_dgehrd ", &i__1); return 0; } else if (lquery) { return 0; } /* Set elements 1:ILO-1 and IHI:N-1 of TAU to zero */ i__1 = *ilo - 1; for (i__ = 1; i__ <= i__1; ++i__) { tau[i__] = 0.; /* L10: */ } i__1 = *n - 1; for (i__ = MAX (1, *ihi); i__ <= i__1; ++i__) { tau[i__] = 0.; /* L20: */ } /* Quick return if possible */ nh = *ihi - *ilo + 1; if (nh <= 1) { work[1] = 1.; return 0; } /* Determine the block size. Computing MIN */ i__1 = 64, i__2 = NUMlapack_ilaenv (&c__1, "NUMlapack_dgehrd ", " ", n, ilo, ihi, &c_n1, 6, 1); nb = MIN (i__1, i__2); nbmin = 2; iws = 1; if (nb > 1 && nb < nh) { /* Determine when to cross over from blocked to unblocked code (last block is always handled by unblocked code). Computing MAX */ i__1 = nb, i__2 = NUMlapack_ilaenv (&c__3, "NUMlapack_dgehrd ", " ", n, ilo, ihi, &c_n1, 6, 1); nx = MAX (i__1, i__2); if (nx < nh) { /* Determine if workspace is large enough for blocked code. */ iws = *n * nb; if (*lwork < iws) { /* Not enough workspace to use optimal NB: determine the minimum value of NB, and reduce NB or force use of unblocked code. Computing MAX */ i__1 = 2, i__2 = NUMlapack_ilaenv (&c__2, "NUMlapack_dgehrd ", " ", n, ilo, ihi, &c_n1, 6, 1); nbmin = MAX (i__1, i__2); if (*lwork >= *n * nbmin) { nb = *lwork / *n; } else { nb = 1; } } } } ldwork = *n; if (nb < nbmin || nb >= nh) { /* Use unblocked code below */ i__ = *ilo; } else { /* Use blocked code */ i__1 = *ihi - 1 - nx; i__2 = nb; for (i__ = *ilo; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Computing MIN */ i__3 = nb, i__4 = *ihi - i__; ib = MIN (i__3, i__4); /* Reduce columns i:i+ib-1 to Hessenberg form, returning the matrices V and T of the block reflector H = I - V*T*V' which performs the reduction, and also the matrix Y = A*V*T */ NUMlapack_dlahrd (ihi, &i__, &ib, &a_ref (1, i__), lda, &tau[i__], t, &c__65, &work[1], &ldwork); /* Apply the block reflector H to A(1:ihi,i+ib:ihi) from the right, computing A := A - Y * V'. V(i+ib,ib-1) must be set to 1. */ ei = a_ref (i__ + ib, i__ + ib - 1); a_ref (i__ + ib, i__ + ib - 1) = 1.; i__3 = *ihi - i__ - ib + 1; NUMblas_dgemm ("No transpose", "Transpose", ihi, &i__3, &ib, &c_b25, &work[1], &ldwork, &a_ref (i__ + ib, i__), lda, &c_b26, &a_ref (1, i__ + ib), lda); a_ref (i__ + ib, i__ + ib - 1) = ei; /* Apply the block reflector H to A(i+1:ihi,i+ib:n) from the left */ i__3 = *ihi - i__; i__4 = *n - i__ - ib + 1; NUMlapack_dlarfb ("Left", "Transpose", "Forward", "Columnwise", &i__3, &i__4, &ib, &a_ref (i__ + 1, i__), lda, t, &c__65, &a_ref (i__ + 1, i__ + ib), lda, &work[1], &ldwork); /* L30: */ } } /* Use unblocked code to reduce the rest of the matrix */ NUMlapack_dgehd2 (n, &i__, ihi, &a[a_offset], lda, &tau[1], &work[1], &iinfo); work[1] = (double) iws; return 0; } /* NUMlapack_dgehrd */ int NUMlapack_dgelq2 (long *m, long *n, double *a, long *lda, double *tau, double *work, long *info) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__, k; static double aii; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGELQ2", &i__1); return 0; } k = MIN (*m, *n); i__1 = k; for (i__ = 1; i__ <= i__1; ++i__) { /* Generate elementary reflector H(i) to annihilate A(i,i+1:n) Computing MIN */ i__2 = i__ + 1; i__3 = *n - i__ + 1; NUMlapack_dlarfg (&i__3, &a_ref (i__, i__), &a_ref (i__, MIN (i__2, *n)), lda, &tau[i__]); if (i__ < *m) { /* Apply H(i) to A(i+1:m,i:n) from the right */ aii = a_ref (i__, i__); a_ref (i__, i__) = 1.; i__2 = *m - i__; i__3 = *n - i__ + 1; NUMlapack_dlarf ("Right", &i__2, &i__3, &a_ref (i__, i__), lda, &tau[i__], &a_ref (i__ + 1, i__), lda, &work[1]); a_ref (i__, i__) = aii; } /* L10: */ } return 0; } /* NUMlapack_dgelq2 */ int NUMlapack_dgelqf (long *m, long *n, double *a, long *lda, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__3 = 3; static long c__2 = 2; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4; /* Local variables */ static long i__, k, nbmin, iinfo; static long ib, nb; static long nx; static long ldwork, lwkopt; static long lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; nb = NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); lwkopt = *m * nb; work[1] = (double) lwkopt; lquery = *lwork == -1; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } else if (*lwork < MAX (1, *m) && !lquery) { *info = -7; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGELQF", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ k = MIN (*m, *n); if (k == 0) { work[1] = 1.; return 0; } nbmin = 2; nx = 0; iws = *m; if (nb > 1 && nb < k) { /* Determine when to cross over from blocked to unblocked code. Computing MAX */ i__1 = 0, i__2 = NUMlapack_ilaenv (&c__3, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); nx = MAX (i__1, i__2); if (nx < k) { /* Determine if workspace is large enough for blocked code. */ ldwork = *m; iws = ldwork * nb; if (*lwork < iws) { /* Not enough workspace to use optimal NB: reduce NB and determine the minimum value of NB. */ nb = *lwork / ldwork; /* Computing MAX */ i__1 = 2, i__2 = NUMlapack_ilaenv (&c__2, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); nbmin = MAX (i__1, i__2); } } } if (nb >= nbmin && nb < k && nx < k) { /* Use blocked code initially */ i__1 = k - nx; i__2 = nb; for (i__ = 1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Computing MIN */ i__3 = k - i__ + 1; ib = MIN (i__3, nb); /* Compute the LQ factorization of the current block A(i:i+ib-1,i:n) */ i__3 = *n - i__ + 1; NUMlapack_dgelq2 (&ib, &i__3, &a_ref (i__, i__), lda, &tau[i__], &work[1], &iinfo); if (i__ + ib <= *m) { /* Form the triangular factor of the block reflector H = H(i) H(i+1) . . . H(i+ib-1) */ i__3 = *n - i__ + 1; NUMlapack_dlarft ("Forward", "Rowwise", &i__3, &ib, &a_ref (i__, i__), lda, &tau[i__], &work[1], &ldwork); /* Apply H to A(i+ib:m,i:n) from the right */ i__3 = *m - i__ - ib + 1; i__4 = *n - i__ + 1; NUMlapack_dlarfb ("Right", "No transpose", "Forward", "Rowwise", &i__3, &i__4, &ib, &a_ref (i__, i__), lda, &work[1], &ldwork, &a_ref (i__ + ib, i__), lda, &work[ib + 1], &ldwork); } /* L10: */ } } else { i__ = 1; } /* Use unblocked code to factor the last or only block. */ if (i__ <= k) { i__2 = *m - i__ + 1; i__1 = *n - i__ + 1; NUMlapack_dgelq2 (&i__2, &i__1, &a_ref (i__, i__), lda, &tau[i__], &work[1], &iinfo); } work[1] = (double) iws; return 0; } /* NUMlapack_dgelqf */ #define b_ref(a_1,a_2) b[(a_2)*b_dim1 + a_1] int NUMlapack_dgelss (long *m, long *n, long *nrhs, double *a, long *lda, double *b, long *ldb, double *s, double *rcond, long *rank, double *work, long *lwork, long *info) { /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, i__1, i__2, i__3, i__4; double d__1; /* Local variables */ static double anrm, bnrm; static long itau; static double vdum[1]; static long i__; static long iascl, ibscl; static long chunk; static double sfmin; static long minmn; static long maxmn, itaup, itauq, mnthr, iwork; static long bl, ie, il; static long mm; static long bdspac; static double bignum; static long ldwork; static long minwrk, maxwrk; static double smlnum; static long lquery; static double eps, thr; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; --s; --work; /* Function Body */ *info = 0; minmn = MIN (*m, *n); maxmn = MAX (*m, *n); mnthr = NUMlapack_ilaenv (&c__6, "DGELSS", " ", m, n, nrhs, &c_n1, 6, 1); lquery = *lwork == -1; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*nrhs < 0) { *info = -3; } else if (*lda < MAX (1, *m)) { *info = -5; } else if (*ldb < MAX (1, maxmn)) { *info = -7; } /* Compute workspace (Note: Comments in the code beginning "Workspace:" describe the minimal amount of workspace needed at that point in the code, as well as the preferred amount for good performance. NB refers to the optimal block size for the immediately following subroutine, as returned by ILAENV.) */ minwrk = 1; if (*info == 0 && (*lwork >= 1 || lquery)) { maxwrk = 0; mm = *m; if (*m >= *n && *m >= mnthr) { /* Path 1a - overdetermined, with many more rows than columns */ mm = *n; /* Computing MAX */ i__1 = maxwrk, i__2 = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *n + *nrhs * NUMlapack_ilaenv (&c__1, "DORMQR", "LT", m, nrhs, n, &c_n1, 6, 2); maxwrk = MAX (i__1, i__2); } if (*m >= *n) { /* Path 1 - overdetermined or exactly determined Compute workspace needed for DBDSQR Computing MAX */ i__1 = 1, i__2 = *n * 5; bdspac = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *n * 3 + (mm + *n) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", &mm, n, &c_n1, &c_n1, 6, 1); maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *n * 3 + *nrhs * NUMlapack_ilaenv (&c__1, "DORMBR", "QLT", &mm, nrhs, n, &c_n1, 6, 3); maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *n * 3 + (*n - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", n, n, n, &c_n1, 6, 1); maxwrk = MAX (i__1, i__2); maxwrk = MAX (maxwrk, bdspac); /* Computing MAX */ i__1 = maxwrk, i__2 = *n * *nrhs; maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = *n * 3 + mm, i__2 = *n * 3 + *nrhs, i__1 = MAX (i__1, i__2); minwrk = MAX (i__1, bdspac); maxwrk = MAX (minwrk, maxwrk); } if (*n > *m) { /* Compute workspace needed for DBDSQR Computing MAX */ i__1 = 1, i__2 = *m * 5; bdspac = MAX (i__1, i__2); /* Computing MAX */ i__1 = *m * 3 + *nrhs, i__2 = *m * 3 + *n, i__1 = MAX (i__1, i__2); minwrk = MAX (i__1, bdspac); if (*n >= mnthr) { /* Path 2a - underdetermined, with many more columns than rows */ maxwrk = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__1 = maxwrk, i__2 = *m * *m + (*m << 2) + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *m * *m + (*m << 2) + *nrhs * NUMlapack_ilaenv (&c__1, "DORMBR", "QLT", m, nrhs, m, &c_n1, 6, 3); maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *m * *m + (*m << 2) + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, m, m, &c_n1, 6, 1); maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *m * *m + *m + bdspac; maxwrk = MAX (i__1, i__2); if (*nrhs > 1) { /* Computing MAX */ i__1 = maxwrk, i__2 = *m * *m + *m + *m * *nrhs; maxwrk = MAX (i__1, i__2); } else { /* Computing MAX */ i__1 = maxwrk, i__2 = *m * *m + (*m << 1); maxwrk = MAX (i__1, i__2); } /* Computing MAX */ i__1 = maxwrk, i__2 = *m + *nrhs * NUMlapack_ilaenv (&c__1, "DORMLQ", "LT", n, nrhs, m, &c_n1, 6, 2); maxwrk = MAX (i__1, i__2); } else { /* Path 2 - underdetermined */ maxwrk = *m * 3 + (*n + *m) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__1 = maxwrk, i__2 = *m * 3 + *nrhs * NUMlapack_ilaenv (&c__1, "DORMBR", "QLT", m, nrhs, m, &c_n1, 6, 3); maxwrk = MAX (i__1, i__2); /* Computing MAX */ i__1 = maxwrk, i__2 = *m * 3 + *m * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, n, m, &c_n1, 6, 1); maxwrk = MAX (i__1, i__2); maxwrk = MAX (maxwrk, bdspac); /* Computing MAX */ i__1 = maxwrk, i__2 = *n * *nrhs; maxwrk = MAX (i__1, i__2); } } maxwrk = MAX (minwrk, maxwrk); work[1] = (double) maxwrk; } minwrk = MAX (minwrk, 1); if (*lwork < minwrk && !lquery) { *info = -12; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGELSS", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0) { *rank = 0; return 0; } /* Get machine parameters */ eps = NUMblas_dlamch ("P"); sfmin = NUMblas_dlamch ("S"); smlnum = sfmin / eps; bignum = 1. / smlnum; NUMlapack_dlabad (&smlnum, &bignum); /* Scale A if max element outside range [SMLNUM,BIGNUM] */ anrm = NUMlapack_dlange ("M", m, n, &a[a_offset], lda, &work[1]); iascl = 0; if (anrm > 0. && anrm < smlnum) { /* Scale matrix norm up to SMLNUM */ NUMlapack_dlascl ("G", &c__0, &c__0, &anrm, &smlnum, m, n, &a[a_offset], lda, info); iascl = 1; } else if (anrm > bignum) { /* Scale matrix norm down to BIGNUM */ NUMlapack_dlascl ("G", &c__0, &c__0, &anrm, &bignum, m, n, &a[a_offset], lda, info); iascl = 2; } else if (anrm == 0.) { /* Matrix all zero. Return zero solution. */ i__1 = MAX (*m, *n); NUMlapack_dlaset ("F", &i__1, nrhs, &c_b74, &c_b74, &b[b_offset], ldb); NUMlapack_dlaset ("F", &minmn, &c__1, &c_b74, &c_b74, &s[1], &c__1); *rank = 0; goto L70; } /* Scale B if max element outside range [SMLNUM,BIGNUM] */ bnrm = NUMlapack_dlange ("M", m, nrhs, &b[b_offset], ldb, &work[1]); ibscl = 0; if (bnrm > 0. && bnrm < smlnum) { /* Scale matrix norm up to SMLNUM */ NUMlapack_dlascl ("G", &c__0, &c__0, &bnrm, &smlnum, m, nrhs, &b[b_offset], ldb, info); ibscl = 1; } else if (bnrm > bignum) { /* Scale matrix norm down to BIGNUM */ NUMlapack_dlascl ("G", &c__0, &c__0, &bnrm, &bignum, m, nrhs, &b[b_offset], ldb, info); ibscl = 2; } /* Overdetermined case */ if (*m >= *n) { /* Path 1 - overdetermined or exactly determined */ mm = *m; if (*m >= mnthr) { /* Path 1a - overdetermined, with many more rows than columns */ mm = *n; itau = 1; iwork = itau + *n; /* Compute A=Q*R (Workspace: need 2*N, prefer N+N*NB) */ i__1 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__1, info); /* Multiply B by transpose(Q) (Workspace: need N+NRHS, prefer N+NRHS*NB) */ i__1 = *lwork - iwork + 1; NUMlapack_dormqr ("L", "T", m, nrhs, n, &a[a_offset], lda, &work[itau], &b[b_offset], ldb, &work[iwork], &i__1, info); /* Zero out below R */ if (*n > 1) { i__1 = *n - 1; i__2 = *n - 1; NUMlapack_dlaset ("L", &i__1, &i__2, &c_b74, &c_b74, &a_ref (2, 1), lda); } } ie = 1; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in A (Workspace: need 3*N+MM, prefer 3*N+(MM+N)*NB) */ i__1 = *lwork - iwork + 1; NUMlapack_dgebrd (&mm, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__1, info); /* Multiply B by transpose of left bidiagonalizing vectors of R (Workspace: need 3*N+NRHS, prefer 3*N+NRHS*NB) */ i__1 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "L", "T", &mm, nrhs, n, &a[a_offset], lda, &work[itauq], &b[b_offset], ldb, &work[iwork], &i__1, info); /* Generate right bidiagonalizing vectors of R in A (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB) */ i__1 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &a[a_offset], lda, &work[itaup], &work[iwork], &i__1, info); iwork = ie + *n; /* Perform bidiagonal QR iteration multiply B by transpose of left singular vectors compute right singular vectors in A (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, &c__0, nrhs, &s[1], &work[ie], &a[a_offset], lda, vdum, &c__1, &b[b_offset], ldb, &work[iwork], info); if (*info != 0) { goto L70; } /* Multiply B by reciprocals of singular values Computing MAX */ d__1 = *rcond * s[1]; thr = MAX (d__1, sfmin); if (*rcond < 0.) { /* Computing MAX */ d__1 = eps * s[1]; thr = MAX (d__1, sfmin); } *rank = 0; i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { if (s[i__] > thr) { NUMlapack_drscl (nrhs, &s[i__], &b_ref (i__, 1), ldb); ++ (*rank); } else { NUMlapack_dlaset ("F", &c__1, nrhs, &c_b74, &c_b74, &b_ref (i__, 1), ldb); } /* L10: */ } /* Multiply B by right singular vectors (Workspace: need N, prefer N*NRHS) */ if (*lwork >= *ldb * *nrhs && *nrhs > 1) { NUMblas_dgemm ("T", "N", n, nrhs, n, &c_b108, &a[a_offset], lda, &b[b_offset], ldb, &c_b74, &work[1], ldb); NUMlapack_dlacpy ("G", n, nrhs, &work[1], ldb, &b[b_offset], ldb); } else if (*nrhs > 1) { chunk = *lwork / *n; i__1 = *nrhs; i__2 = chunk; for (i__ = 1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Computing MIN */ i__3 = *nrhs - i__ + 1; bl = MIN (i__3, chunk); NUMblas_dgemm ("T", "N", n, &bl, n, &c_b108, &a[a_offset], lda, &b_ref (1, i__), ldb, &c_b74, &work[1], n); NUMlapack_dlacpy ("G", n, &bl, &work[1], n, &b_ref (1, i__), ldb); /* L20: */ } } else { NUMblas_dgemv ("T", n, n, &c_b108, &a[a_offset], lda, &b[b_offset], &c__1, &c_b74, &work[1], &c__1); NUMblas_dcopy (n, &work[1], &c__1, &b[b_offset], &c__1); } } else { /* if(complicated condition) */ /* Computing MAX */ i__2 = *m, i__1 = (*m << 1) - 4, i__2 = MAX (i__2, i__1), i__2 = MAX (i__2, *nrhs), i__1 = *n - *m * 3; if (*n >= mnthr && *lwork >= (*m << 2) + *m * *m + MAX (i__2, i__1)) { /* Path 2a - underdetermined, with many more columns than rows and sufficient workspace for an efficient algorithm */ ldwork = *m; /* Computing MAX Computing MAX */ i__3 = *m, i__4 = (*m << 1) - 4, i__3 = MAX (i__3, i__4), i__3 = MAX (i__3, *nrhs), i__4 = *n - *m * 3; i__2 = (*m << 2) + *m * *lda + MAX (i__3, i__4), i__1 = *m * *lda + *m + *m * *nrhs; if (*lwork >= MAX (i__2, i__1)) { ldwork = *lda; } itau = 1; iwork = *m + 1; /* Compute A=L*Q (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, info); il = iwork; /* Copy L to WORK(IL), zeroing out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &work[il], &ldwork); i__2 = *m - 1; i__1 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__1, &c_b74, &c_b74, &work[il + ldwork], &ldwork); ie = il + ldwork * *m; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in WORK(IL) (Workspace: need M*M+5*M, prefer M*M+4*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &work[il], &ldwork, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, info); /* Multiply B by transpose of left bidiagonalizing vectors of L (Workspace: need M*M+4*M+NRHS, prefer M*M+4*M+NRHS*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "L", "T", m, nrhs, m, &work[il], &ldwork, &work[itauq], &b[b_offset], ldb, &work[iwork], &i__2, info); /* Generate right bidiagonalizing vectors of R in WORK(IL) (Workspace: need M*M+5*M-1, prefer M*M+4*M+(M-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, m, m, &work[il], &ldwork, &work[itaup], &work[iwork], &i__2, info); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing right singular vectors of L in WORK(IL) and multiplying B by transpose of left singular vectors (Workspace: need M*M+M+BDSPAC) */ NUMlapack_dbdsqr ("U", m, m, &c__0, nrhs, &s[1], &work[ie], &work[il], &ldwork, &a[a_offset], lda, &b[b_offset], ldb, &work[iwork], info); if (*info != 0) { goto L70; } /* Multiply B by reciprocals of singular values Computing MAX */ d__1 = *rcond * s[1]; thr = MAX (d__1, sfmin); if (*rcond < 0.) { /* Computing MAX */ d__1 = eps * s[1]; thr = MAX (d__1, sfmin); } *rank = 0; i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { if (s[i__] > thr) { NUMlapack_drscl (nrhs, &s[i__], &b_ref (i__, 1), ldb); ++ (*rank); } else { NUMlapack_dlaset ("F", &c__1, nrhs, &c_b74, &c_b74, &b_ref (i__, 1), ldb); } /* L30: */ } iwork = ie; /* Multiply B by right singular vectors of L in WORK(IL) (Workspace: need M*M+2*M, prefer M*M+M+M*NRHS) */ if (*lwork >= *ldb * *nrhs + iwork - 1 && *nrhs > 1) { NUMblas_dgemm ("T", "N", m, nrhs, m, &c_b108, &work[il], &ldwork, &b[b_offset], ldb, &c_b74, &work[iwork], ldb); NUMlapack_dlacpy ("G", m, nrhs, &work[iwork], ldb, &b[b_offset], ldb); } else if (*nrhs > 1) { chunk = (*lwork - iwork + 1) / *m; i__2 = *nrhs; i__1 = chunk; for (i__ = 1; i__1 < 0 ? i__ >= i__2 : i__ <= i__2; i__ += i__1) { /* Computing MIN */ i__3 = *nrhs - i__ + 1; bl = MIN (i__3, chunk); NUMblas_dgemm ("T", "N", m, &bl, m, &c_b108, &work[il], &ldwork, &b_ref (1, i__), ldb, &c_b74, &work[iwork], n); NUMlapack_dlacpy ("G", m, &bl, &work[iwork], n, &b_ref (1, i__), ldb); /* L40: */ } } else { NUMblas_dgemv ("T", m, m, &c_b108, &work[il], &ldwork, &b_ref (1, 1), &c__1, &c_b74, &work[iwork], &c__1); NUMblas_dcopy (m, &work[iwork], &c__1, &b_ref (1, 1), &c__1); } /* Zero out below first M rows of B */ i__1 = *n - *m; NUMlapack_dlaset ("F", &i__1, nrhs, &c_b74, &c_b74, &b_ref (*m + 1, 1), ldb); iwork = itau + *m; /* Multiply transpose(Q) by B (Workspace: need M+NRHS, prefer M+NRHS*NB) */ i__1 = *lwork - iwork + 1; NUMlapack_dormlq ("L", "T", n, nrhs, m, &a[a_offset], lda, &work[itau], &b[b_offset], ldb, &work[iwork], &i__1, info); } else { /* Path 2 - remaining underdetermined cases */ ie = 1; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize A (Workspace: need 3*M+N, prefer 3*M+(M+N)*NB) */ i__1 = *lwork - iwork + 1; NUMlapack_dgebrd (m, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__1, info); /* Multiply B by transpose of left bidiagonalizing vectors (Workspace: need 3*M+NRHS, prefer 3*M+NRHS*NB) */ i__1 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "L", "T", m, nrhs, n, &a[a_offset], lda, &work[itauq], &b[b_offset], ldb, &work[iwork], &i__1, info); /* Generate right bidiagonalizing vectors in A (Workspace: need 4*M, prefer 3*M+M*NB) */ i__1 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, n, m, &a[a_offset], lda, &work[itaup], &work[iwork], &i__1, info); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing right singular vectors of A in A and multiplying B by transpose of left singular vectors (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("L", m, n, &c__0, nrhs, &s[1], &work[ie], &a[a_offset], lda, vdum, &c__1, &b[b_offset], ldb, &work[iwork], info); if (*info != 0) { goto L70; } /* Multiply B by reciprocals of singular values Computing MAX */ d__1 = *rcond * s[1]; thr = MAX (d__1, sfmin); if (*rcond < 0.) { /* Computing MAX */ d__1 = eps * s[1]; thr = MAX (d__1, sfmin); } *rank = 0; i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { if (s[i__] > thr) { NUMlapack_drscl (nrhs, &s[i__], &b_ref (i__, 1), ldb); ++ (*rank); } else { NUMlapack_dlaset ("F", &c__1, nrhs, &c_b74, &c_b74, &b_ref (i__, 1), ldb); } /* L50: */ } /* Multiply B by right singular vectors of A (Workspace: need N, prefer N*NRHS) */ if (*lwork >= *ldb * *nrhs && *nrhs > 1) { NUMblas_dgemm ("T", "N", n, nrhs, m, &c_b108, &a[a_offset], lda, &b[b_offset], ldb, &c_b74, &work[1], ldb); NUMlapack_dlacpy ("F", n, nrhs, &work[1], ldb, &b[b_offset], ldb); } else if (*nrhs > 1) { chunk = *lwork / *n; i__1 = *nrhs; i__2 = chunk; for (i__ = 1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Computing MIN */ i__3 = *nrhs - i__ + 1; bl = MIN (i__3, chunk); NUMblas_dgemm ("T", "N", n, &bl, m, &c_b108, &a[a_offset], lda, &b_ref (1, i__), ldb, &c_b74, &work[1], n); NUMlapack_dlacpy ("F", n, &bl, &work[1], n, &b_ref (1, i__), ldb); /* L60: */ } } else { NUMblas_dgemv ("T", m, n, &c_b108, &a[a_offset], lda, &b[b_offset], &c__1, &c_b74, &work[1], &c__1); NUMblas_dcopy (n, &work[1], &c__1, &b[b_offset], &c__1); } } } /* Undo scaling */ if (iascl == 1) { NUMlapack_dlascl ("G", &c__0, &c__0, &anrm, &smlnum, n, nrhs, &b[b_offset], ldb, info); NUMlapack_dlascl ("G", &c__0, &c__0, &smlnum, &anrm, &minmn, &c__1, &s[1], &minmn, info); } else if (iascl == 2) { NUMlapack_dlascl ("G", &c__0, &c__0, &anrm, &bignum, n, nrhs, &b[b_offset], ldb, info); NUMlapack_dlascl ("G", &c__0, &c__0, &bignum, &anrm, &minmn, &c__1, &s[1], &minmn, info); } if (ibscl == 1) { NUMlapack_dlascl ("G", &c__0, &c__0, &smlnum, &bnrm, n, nrhs, &b[b_offset], ldb, info); } else if (ibscl == 2) { NUMlapack_dlascl ("G", &c__0, &c__0, &bignum, &bnrm, n, nrhs, &b[b_offset], ldb, info); } L70: work[1] = (double) maxwrk; return 0; } /* NUMlapack_dgelss */ #undef b_ref int NUMlapack_dgeqpf (long *m, long *n, double *a, long *lda, long *jpvt, double *tau, double *work, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; double d__1, d__2; /* Local variables */ static double temp; static double temp2; static long i__, j; static long itemp; static long ma, mn; static double aii; static long pvt; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --jpvt; --tau; --work; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGEQPF", &i__1); return 0; } mn = MIN (*m, *n); /* Move initial columns up front */ itemp = 1; i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { if (jpvt[i__] != 0) { if (i__ != itemp) { NUMblas_dswap (m, &a_ref (1, i__), &c__1, &a_ref (1, itemp), &c__1); jpvt[i__] = jpvt[itemp]; jpvt[itemp] = i__; } else { jpvt[i__] = i__; } ++itemp; } else { jpvt[i__] = i__; } /* L10: */ } --itemp; /* Compute the QR factorization and update remaining columns */ if (itemp > 0) { ma = MIN (itemp, *m); NUMlapack_dgeqr2 (m, &ma, &a[a_offset], lda, &tau[1], &work[1], info); if (ma < *n) { i__1 = *n - ma; NUMlapack_dorm2r ("Left", "Transpose", m, &i__1, &ma, &a[a_offset], lda, &tau[1], &a_ref (1, ma + 1), lda, &work[1], info); } } if (itemp < mn) { /* Initialize partial column norms. The first n elements of work store the exact column norms. */ i__1 = *n; for (i__ = itemp + 1; i__ <= i__1; ++i__) { i__2 = *m - itemp; work[i__] = NUMblas_dnrm2 (&i__2, &a_ref (itemp + 1, i__), &c__1); work[*n + i__] = work[i__]; /* L20: */ } /* Compute factorization */ i__1 = mn; for (i__ = itemp + 1; i__ <= i__1; ++i__) { /* Determine ith pivot column and swap if necessary */ i__2 = *n - i__ + 1; pvt = i__ - 1 + NUMblas_idamax (&i__2, &work[i__], &c__1); if (pvt != i__) { NUMblas_dswap (m, &a_ref (1, pvt), &c__1, &a_ref (1, i__), &c__1); itemp = jpvt[pvt]; jpvt[pvt] = jpvt[i__]; jpvt[i__] = itemp; work[pvt] = work[i__]; work[*n + pvt] = work[*n + i__]; } /* Generate elementary reflector H(i) */ if (i__ < *m) { i__2 = *m - i__ + 1; NUMlapack_dlarfg (&i__2, &a_ref (i__, i__), &a_ref (i__ + 1, i__), &c__1, &tau[i__]); } else { NUMlapack_dlarfg (&c__1, &a_ref (*m, *m), &a_ref (*m, *m), &c__1, &tau[*m]); } if (i__ < *n) { /* Apply H(i) to A(i:m,i+1:n) from the left */ aii = a_ref (i__, i__); a_ref (i__, i__) = 1.; i__2 = *m - i__ + 1; i__3 = *n - i__; NUMlapack_dlarf ("LEFT", &i__2, &i__3, &a_ref (i__, i__), &c__1, &tau[i__], &a_ref (i__, i__ + 1), lda, &work[ (*n << 1) + 1]); a_ref (i__, i__) = aii; } /* Update partial column norms */ i__2 = *n; for (j = i__ + 1; j <= i__2; ++j) { if (work[j] != 0.) { /* Computing 2nd power */ d__2 = (d__1 = a_ref (i__, j), fabs (d__1)) / work[j]; temp = 1. - d__2 * d__2; temp = MAX (temp, 0.); /* Computing 2nd power */ d__1 = work[j] / work[*n + j]; temp2 = temp * .05 * (d__1 * d__1) + 1.; if (temp2 == 1.) { if (*m - i__ > 0) { i__3 = *m - i__; work[j] = NUMblas_dnrm2 (&i__3, &a_ref (i__ + 1, j), &c__1); work[*n + j] = work[j]; } else { work[j] = 0.; work[*n + j] = 0.; } } else { work[j] *= sqrt (temp); } } /* L30: */ } /* L40: */ } } return 0; } /* NUMlapack_dgeqpf */ int NUMlapack_dgeqr2 (long *m, long *n, double *a, long *lda, double *tau, double *work, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__, k; static double aii; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGEQR2", &i__1); return 0; } k = MIN (*m, *n); i__1 = k; for (i__ = 1; i__ <= i__1; ++i__) { /* Generate elementary reflector H(i) to annihilate A(i+1:m,i) Computing MIN */ i__2 = i__ + 1; i__3 = *m - i__ + 1; NUMlapack_dlarfg (&i__3, &a_ref (i__, i__), &a_ref (MIN (i__2, *m), i__), &c__1, &tau[i__]); if (i__ < *n) { /* Apply H(i) to A(i:m,i+1:n) from the left */ aii = a_ref (i__, i__); a_ref (i__, i__) = 1.; i__2 = *m - i__ + 1; i__3 = *n - i__; NUMlapack_dlarf ("Left", &i__2, &i__3, &a_ref (i__, i__), &c__1, &tau[i__], &a_ref (i__, i__ + 1), lda, &work[1]); a_ref (i__, i__) = aii; } /* L10: */ } return 0; } /* NUMlapack_dgeqr2 */ int NUMlapack_dgeqrf (long *m, long *n, double *a, long *lda, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__3 = 3; static long c__2 = 2; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4; /* Local variables */ static long i__, k, nbmin, iinfo; static long ib, nb; static long nx; static long ldwork, lwkopt; static long lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; nb = NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); lwkopt = *n * nb; work[1] = (double) lwkopt; lquery = *lwork == -1; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } else if (*lwork < MAX (1, *n) && !lquery) { *info = -7; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGEQRF", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ k = MIN (*m, *n); if (k == 0) { work[1] = 1.; return 0; } nbmin = 2; nx = 0; iws = *n; if (nb > 1 && nb < k) { /* Determine when to cross over from blocked to unblocked code. Computing MAX */ i__1 = 0, i__2 = NUMlapack_ilaenv (&c__3, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); nx = MAX (i__1, i__2); if (nx < k) { /* Determine if workspace is large enough for blocked code. */ ldwork = *n; iws = ldwork * nb; if (*lwork < iws) { /* Not enough workspace to use optimal NB: reduce NB and determine the minimum value of NB. */ nb = *lwork / ldwork; /* Computing MAX */ i__1 = 2, i__2 = NUMlapack_ilaenv (&c__2, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); nbmin = MAX (i__1, i__2); } } } if (nb >= nbmin && nb < k && nx < k) { /* Use blocked code initially */ i__1 = k - nx; i__2 = nb; for (i__ = 1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Computing MIN */ i__3 = k - i__ + 1; ib = MIN (i__3, nb); /* Compute the QR factorization of the current block A(i:m,i:i+ib-1) */ i__3 = *m - i__ + 1; NUMlapack_dgeqr2 (&i__3, &ib, &a_ref (i__, i__), lda, &tau[i__], &work[1], &iinfo); if (i__ + ib <= *n) { /* Form the triangular factor of the block reflector H = H(i) H(i+1) . . . H(i+ib-1) */ i__3 = *m - i__ + 1; NUMlapack_dlarft ("Forward", "Columnwise", &i__3, &ib, &a_ref (i__, i__), lda, &tau[i__], &work[1], &ldwork); /* Apply H' to A(i:m,i+ib:n) from the left */ i__3 = *m - i__ + 1; i__4 = *n - i__ - ib + 1; NUMlapack_dlarfb ("Left", "Transpose", "Forward", "Columnwise", &i__3, &i__4, &ib, &a_ref (i__, i__), lda, &work[1], &ldwork, &a_ref (i__, i__ + ib), lda, &work[ib + 1], &ldwork); } /* L10: */ } } else { i__ = 1; } /* Use unblocked code to factor the last or only block. */ if (i__ <= k) { i__2 = *m - i__ + 1; i__1 = *n - i__ + 1; NUMlapack_dgeqr2 (&i__2, &i__1, &a_ref (i__, i__), lda, &tau[i__], &work[1], &iinfo); } work[1] = (double) iws; return 0; } /* NUMlapack_dgeqrf */ int NUMlapack_dgerq2 (long *m, long *n, double *a, long *lda, double *tau, double *work, long *info) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2; /* Local variables */ static long i__, k; static double aii; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGERQ2", &i__1); return 0; } k = MIN (*m, *n); for (i__ = k; i__ >= 1; --i__) { /* Generate elementary reflector H(i) to annihilate A(m-k+i,1:n-k+i-1) */ i__1 = *n - k + i__; NUMlapack_dlarfg (&i__1, &a_ref (*m - k + i__, *n - k + i__), &a_ref (*m - k + i__, 1), lda, &tau[i__]); /* Apply H(i) to A(1:m-k+i-1,1:n-k+i) from the right */ aii = a_ref (*m - k + i__, *n - k + i__); a_ref (*m - k + i__, *n - k + i__) = 1.; i__1 = *m - k + i__ - 1; i__2 = *n - k + i__; NUMlapack_dlarf ("Right", &i__1, &i__2, &a_ref (*m - k + i__, 1), lda, &tau[i__], &a[a_offset], lda, &work[1]); a_ref (*m - k + i__, *n - k + i__) = aii; /* L10: */ } return 0; } /* NUMlapack_dgerq2 */ int NUMlapack_dgesv (long *n, long *nrhs, double *a, long *lda, long *ipiv, double *b, long *ldb, long *info) { /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, i__1; /* Local variables */ a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --ipiv; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; /* Function Body */ *info = 0; if (*n < 0) { *info = -1; } else if (*nrhs < 0) { *info = -2; } else if (*lda < MAX (1, *n)) { *info = -4; } else if (*ldb < MAX (1, *n)) { *info = -7; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGESV ", &i__1); return 0; } /* Compute the LU factorization of A. */ NUMlapack_dgetrf (n, n, &a[a_offset], lda, &ipiv[1], info); if (*info == 0) { /* Solve the system A*X = B, overwriting B with X. */ NUMlapack_dgetrs ("No transpose", n, nrhs, &a[a_offset], lda, &ipiv[1], &b[b_offset], ldb, info); } return 0; } /* NUMlapack_dgesv */ #define u_ref(a_1,a_2) u[(a_2)*u_dim1 + a_1] #define vt_ref(a_1,a_2) vt[(a_2)*vt_dim1 + a_1] int NUMlapack_dgesvd (const char *jobu, const char *jobvt, long *m, long *n, double *a, long *lda, double *s, double *u, long *ldu, double *vt, long *ldvt, double *work, long *lwork, long *info) { /* System generated locals */ const char *a__1[2]; long a_dim1, a_offset, u_dim1, u_offset, vt_dim1, vt_offset, i__1[2], i__2, i__3, i__4; char ch__1[2]; /* Local variables */ static long iscl; static double anrm; static long ierr, itau, ncvt, nrvt, i__; static long chunk, minmn, wrkbl, itaup, itauq, mnthr, iwork; static long wntua, wntva, wntun, wntuo, wntvn, wntvo, wntus, wntvs; static long ie; static long ir, bdspac, iu; static double bignum; static long ldwrkr, minwrk, ldwrku, maxwrk; static double smlnum; static long lquery, wntuas, wntvas; static long blk, ncu; static double dum[1], eps; static long nru; /* Parameter adjustments */ a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --s; u_dim1 = *ldu; u_offset = 1 + u_dim1 * 1; u -= u_offset; vt_dim1 = *ldvt; vt_offset = 1 + vt_dim1 * 1; vt -= vt_offset; --work; /* Function Body */ *info = 0; minmn = MIN (*m, *n); /* Writing concatenation */ i__1[0] = 1, a__1[0] = jobu; i__1[1] = 1, a__1[1] = jobvt; s_cat (ch__1, a__1, i__1, &c__2, 2); mnthr = NUMlapack_ilaenv (&c__6, "DGESVD", ch__1, m, n, &c__0, &c__0, 6, 2); wntua = lsame_ (jobu, "A"); wntus = lsame_ (jobu, "S"); wntuas = wntua || wntus; wntuo = lsame_ (jobu, "O"); wntun = lsame_ (jobu, "N"); wntva = lsame_ (jobvt, "A"); wntvs = lsame_ (jobvt, "S"); wntvas = wntva || wntvs; wntvo = lsame_ (jobvt, "O"); wntvn = lsame_ (jobvt, "N"); minwrk = 1; lquery = *lwork == -1; if (! (wntua || wntus || wntuo || wntun)) { *info = -1; } else if (! (wntva || wntvs || wntvo || wntvn) || wntvo && wntuo) { *info = -2; } else if (*m < 0) { *info = -3; } else if (*n < 0) { *info = -4; } else if (*lda < MAX (1, *m)) { *info = -6; } else if (*ldu < 1 || wntuas && *ldu < *m) { *info = -9; } else if (*ldvt < 1 || wntva && *ldvt < *n || wntvs && *ldvt < minmn) { *info = -11; } /* Compute workspace (Note: Comments in the code beginning "Workspace:" describe the minimal amount of workspace needed at that point in the code, as well as the preferred amount for good performance. NB refers to the optimal block size for the immediately following subroutine, as returned by ILAENV.) */ if (*info == 0 && (*lwork >= 1 || lquery) && *m > 0 && *n > 0) { if (*m >= *n) { /* Compute space needed for DBDSQR */ bdspac = *n * 5; if (*m >= mnthr) { if (wntun) { /* Path 1 (M much larger than N, JOBU='N') */ maxwrk = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = maxwrk, i__3 = *n * 3 + (*n << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", n, n, &c_n1, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); if (wntvo || wntvas) { /* Computing MAX */ i__2 = maxwrk, i__3 = *n * 3 + (*n - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", n, n, n, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); } maxwrk = MAX (maxwrk, bdspac); /* Computing MAX */ i__2 = *n << 2; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntuo && wntvn) { /* Path 2 (M much larger than N, JOBU='O', JOBVT='N') */ wrkbl = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *n + *n * NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", n, n, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + *n * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); /* Computing MAX */ i__2 = *n * *n + wrkbl, i__3 = *n * *n + *m * *n + *n; maxwrk = MAX (i__2, i__3); /* Computing MAX */ i__2 = *n * 3 + *m; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntuo && wntvas) { /* Path 3 (M much larger than N, JOBU='O', JOBVT='S' or 'A') */ wrkbl = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *n + *n * NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", n, n, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + *n * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); /* Computing MAX */ i__2 = *n * *n + wrkbl, i__3 = *n * *n + *m * *n + *n; maxwrk = MAX (i__2, i__3); /* Computing MAX */ i__2 = *n * 3 + *m; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntus && wntvn) { /* Path 4 (M much larger than N, JOBU='S', JOBVT='N') */ wrkbl = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *n + *n * NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", n, n, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + *n * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = *n * *n + wrkbl; /* Computing MAX */ i__2 = *n * 3 + *m; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntus && wntvo) { /* Path 5 (M much larger than N, JOBU='S', JOBVT='O') */ wrkbl = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *n + *n * NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", n, n, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + *n * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = (*n << 1) * *n + wrkbl; /* Computing MAX */ i__2 = *n * 3 + *m; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntus && wntvas) { /* Path 6 (M much larger than N, JOBU='S', JOBVT='S' or 'A') */ wrkbl = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *n + *n * NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", n, n, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + *n * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = *n * *n + wrkbl; /* Computing MAX */ i__2 = *n * 3 + *m; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntua && wntvn) { /* Path 7 (M much larger than N, JOBU='A', JOBVT='N') */ wrkbl = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *n + *m * NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, m, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", n, n, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + *n * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = *n * *n + wrkbl; /* Computing MAX */ i__2 = *n * 3 + *m; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntua && wntvo) { /* Path 8 (M much larger than N, JOBU='A', JOBVT='O') */ wrkbl = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *n + *m * NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, m, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", n, n, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + *n * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = (*n << 1) * *n + wrkbl; /* Computing MAX */ i__2 = *n * 3 + *m; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntua && wntvas) { /* Path 9 (M much larger than N, JOBU='A', JOBVT='S' or 'A') */ wrkbl = *n + *n * NUMlapack_ilaenv (&c__1, "DGEQRF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *n + *m * NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, m, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", n, n, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + *n * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *n * 3 + (*n - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", n, n, n, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = *n * *n + wrkbl; /* Computing MAX */ i__2 = *n * 3 + *m; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } } else { /* Path 10 (M at least N, but not much larger) */ maxwrk = *n * 3 + (*m + *n) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, n, &c_n1, &c_n1, 6, 1); if (wntus || wntuo) { /* Computing MAX */ i__2 = maxwrk, i__3 = *n * 3 + *n * NUMlapack_ilaenv (&c__1, "DORG" "BR", "Q", m, n, n, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); } if (wntua) { /* Computing MAX */ i__2 = maxwrk, i__3 = *n * 3 + *m * NUMlapack_ilaenv (&c__1, "DORG" "BR", "Q", m, m, n, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); } if (!wntvn) { /* Computing MAX */ i__2 = maxwrk, i__3 = *n * 3 + (*n - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", n, n, n, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); } maxwrk = MAX (maxwrk, bdspac); /* Computing MAX */ i__2 = *n * 3 + *m; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } } else { /* Compute space needed for DBDSQR */ bdspac = *m * 5; if (*n >= mnthr) { if (wntvn) { /* Path 1t(N much larger than M, JOBVT='N') */ maxwrk = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = maxwrk, i__3 = *m * 3 + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); if (wntuo || wntuas) { /* Computing MAX */ i__2 = maxwrk, i__3 = *m * 3 + *m * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", m, m, m, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); } maxwrk = MAX (maxwrk, bdspac); /* Computing MAX */ i__2 = *m << 2; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntvo && wntun) { /* Path 2t(N much larger than M, JOBU='N', JOBVT='O') */ wrkbl = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *m + *m * NUMlapack_ilaenv (&c__1, "DORGLQ", " ", m, n, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); /* Computing MAX */ i__2 = *m * *m + wrkbl, i__3 = *m * *m + *m * *n + *m; maxwrk = MAX (i__2, i__3); /* Computing MAX */ i__2 = *m * 3 + *n; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntvo && wntuas) { /* Path 3t(N much larger than M, JOBU='S' or 'A', JOBVT='O') */ wrkbl = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *m + *m * NUMlapack_ilaenv (&c__1, "DORGLQ", " ", m, n, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + *m * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); /* Computing MAX */ i__2 = *m * *m + wrkbl, i__3 = *m * *m + *m * *n + *m; maxwrk = MAX (i__2, i__3); /* Computing MAX */ i__2 = *m * 3 + *n; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntvs && wntun) { /* Path 4t(N much larger than M, JOBU='N', JOBVT='S') */ wrkbl = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *m + *m * NUMlapack_ilaenv (&c__1, "DORGLQ", " ", m, n, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = *m * *m + wrkbl; /* Computing MAX */ i__2 = *m * 3 + *n; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntvs && wntuo) { /* Path 5t(N much larger than M, JOBU='O', JOBVT='S') */ wrkbl = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *m + *m * NUMlapack_ilaenv (&c__1, "DORGLQ", " ", m, n, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + *m * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = (*m << 1) * *m + wrkbl; /* Computing MAX */ i__2 = *m * 3 + *n; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntvs && wntuas) { /* Path 6t(N much larger than M, JOBU='S' or 'A', JOBVT='S') */ wrkbl = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *m + *m * NUMlapack_ilaenv (&c__1, "DORGLQ", " ", m, n, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + *m * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = *m * *m + wrkbl; /* Computing MAX */ i__2 = *m * 3 + *n; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntva && wntun) { /* Path 7t(N much larger than M, JOBU='N', JOBVT='A') */ wrkbl = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *m + *n * NUMlapack_ilaenv (&c__1, "DORGLQ", " ", n, n, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = *m * *m + wrkbl; /* Computing MAX */ i__2 = *m * 3 + *n; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntva && wntuo) { /* Path 8t(N much larger than M, JOBU='O', JOBVT='A') */ wrkbl = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *m + *n * NUMlapack_ilaenv (&c__1, "DORGLQ", " ", n, n, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + *m * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = (*m << 1) * *m + wrkbl; /* Computing MAX */ i__2 = *m * 3 + *n; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } else if (wntva && wntuas) { /* Path 9t(N much larger than M, JOBU='S' or 'A', JOBVT='A') */ wrkbl = *m + *m * NUMlapack_ilaenv (&c__1, "DGELQF", " ", m, n, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__2 = wrkbl, i__3 = *m + *n * NUMlapack_ilaenv (&c__1, "DORGLQ", " ", n, n, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m << 1) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, m, &c_n1, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "P", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); /* Computing MAX */ i__2 = wrkbl, i__3 = *m * 3 + *m * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", m, m, m, &c_n1, 6, 1); wrkbl = MAX (i__2, i__3); wrkbl = MAX (wrkbl, bdspac); maxwrk = *m * *m + wrkbl; /* Computing MAX */ i__2 = *m * 3 + *n; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } } else { /* Path 10t(N greater than M, but not much larger) */ maxwrk = *m * 3 + (*m + *n) * NUMlapack_ilaenv (&c__1, "DGEBRD", " ", m, n, &c_n1, &c_n1, 6, 1); if (wntvs || wntvo) { /* Computing MAX */ i__2 = maxwrk, i__3 = *m * 3 + *m * NUMlapack_ilaenv (&c__1, "DORG" "BR", "P", m, n, m, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); } if (wntva) { /* Computing MAX */ i__2 = maxwrk, i__3 = *m * 3 + *n * NUMlapack_ilaenv (&c__1, "DORG" "BR", "P", n, n, m, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); } if (!wntun) { /* Computing MAX */ i__2 = maxwrk, i__3 = *m * 3 + (*m - 1) * NUMlapack_ilaenv (&c__1, "DORGBR", "Q", m, m, m, &c_n1, 6, 1); maxwrk = MAX (i__2, i__3); } maxwrk = MAX (maxwrk, bdspac); /* Computing MAX */ i__2 = *m * 3 + *n; minwrk = MAX (i__2, bdspac); maxwrk = MAX (maxwrk, minwrk); } } work[1] = (double) maxwrk; } if (*lwork < minwrk && !lquery) { *info = -13; } if (*info != 0) { i__2 = - (*info); xerbla_ ("DGESVD", &i__2); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0) { if (*lwork >= 1) { work[1] = 1.; } return 0; } /* Get machine constants */ eps = NUMblas_dlamch ("P"); smlnum = sqrt (NUMblas_dlamch ("S")) / eps; bignum = 1. / smlnum; /* Scale A if max element outside range [SMLNUM,BIGNUM] */ anrm = NUMlapack_dlange ("M", m, n, &a[a_offset], lda, dum); iscl = 0; if (anrm > 0. && anrm < smlnum) { iscl = 1; NUMlapack_dlascl ("G", &c__0, &c__0, &anrm, &smlnum, m, n, &a[a_offset], lda, &ierr); } else if (anrm > bignum) { iscl = 1; NUMlapack_dlascl ("G", &c__0, &c__0, &anrm, &bignum, m, n, &a[a_offset], lda, &ierr); } if (*m >= *n) { /* A has at least as many rows as columns. If A has sufficiently more rows than columns, first reduce using the QR decomposition (if sufficient workspace available) */ if (*m >= mnthr) { if (wntun) { /* Path 1 (M much larger than N, JOBU='N') No left singular vectors to be computed */ itau = 1; iwork = itau + *n; /* Compute A=Q*R (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Zero out below R */ i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &a_ref (2, 1), lda); ie = 1; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in A (Workspace: need 4*N, prefer 3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); ncvt = 0; if (wntvo || wntvas) { /* If right singular vectors desired, generate P'. (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &a[a_offset], lda, &work[itaup], &work[iwork], &i__2, &ierr); ncvt = *n; } iwork = ie + *n; /* Perform bidiagonal QR iteration, computing right singular vectors of A in A if desired (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, &ncvt, &c__0, &c__0, &s[1], &work[ie], &a[a_offset], lda, dum, &c__1, dum, &c__1, &work[iwork], info); /* If right singular vectors desired in VT, copy them there */ if (wntvas) { NUMlapack_dlacpy ("F", n, n, &a[a_offset], lda, &vt[vt_offset], ldvt); } } else if (wntuo && wntvn) { /* Path 2 (M much larger than N, JOBU='O', JOBVT='N') N left singular vectors to be overwritten on A and no right singular vectors to be computed Computing MAX */ i__2 = *n << 2; if (*lwork >= *n * *n + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ ir = 1; /* Computing MAX */ i__2 = wrkbl, i__3 = *lda * *n + *n; if (*lwork >= MAX (i__2, i__3) + *lda * *n) { /* WORK(IU) is LDA by N, WORK(IR) is LDA by N */ ldwrku = *lda; ldwrkr = *lda; } else { /* if(complicated condition) */ /* Computing MAX */ i__2 = wrkbl, i__3 = *lda * *n + *n; if (*lwork >= MAX (i__2, i__3) + *n * *n) { /* WORK(IU) is LDA by N, WORK(IR) is N by N */ ldwrku = *lda; ldwrkr = *n; } else { /* WORK(IU) is LDWRKU by N, WORK(IR) is N by N */ ldwrku = (*lwork - *n * *n - *n) / *n; ldwrkr = *n; } } itau = ir + ldwrkr * *n; iwork = itau + *n; /* Compute A=Q*R (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy R to WORK(IR) and zero out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &work[ir], &ldwrkr); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &work[ir + 1], &ldwrkr); /* Generate Q in A (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, n, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in WORK(IR) (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &work[ir], &ldwrkr, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Generate left vectors bidiagonalizing R (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", n, n, n, &work[ir], &ldwrkr, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of R in WORK(IR) (Workspace: need N*N+BDSPAC) */ NUMlapack_dbdsqr ("U", n, &c__0, n, &c__0, &s[1], &work[ie], dum, &c__1, &work[ir], &ldwrkr, dum, &c__1, &work[iwork], info); iu = ie + *n; /* Multiply Q in A by left singular vectors of R in WORK(IR), storing result in WORK(IU) and copying to A (Workspace: need N*N+2*N, prefer N*N+M*N+N) */ i__2 = *m; i__3 = ldwrku; for (i__ = 1; i__3 < 0 ? i__ >= i__2 : i__ <= i__2; i__ += i__3) { /* Computing MIN */ i__4 = *m - i__ + 1; chunk = MIN (i__4, ldwrku); NUMblas_dgemm ("N", "N", &chunk, n, n, &c_b438, &a_ref (i__, 1), lda, &work[ir], &ldwrkr, &c_b416, &work[iu], &ldwrku); NUMlapack_dlacpy ("F", &chunk, n, &work[iu], &ldwrku, &a_ref (i__, 1), lda); /* L10: */ } } else { /* Insufficient workspace for a fast algorithm */ ie = 1; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize A (Workspace: need 3*N+M, prefer 3*N+(M+N)*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dgebrd (m, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__3, &ierr); /* Generate left vectors bidiagonalizing A (Workspace: need 4*N, prefer 3*N+N*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, n, n, &a[a_offset], lda, &work[itauq], &work[iwork], &i__3, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of A in A (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, &c__0, m, &c__0, &s[1], &work[ie], dum, &c__1, &a[a_offset], lda, dum, &c__1, &work[iwork], info); } } else if (wntuo && wntvas) { /* Path 3 (M much larger than N, JOBU='O', JOBVT='S' or 'A') N left singular vectors to be overwritten on A and N right singular vectors to be computed in VT Computing MAX */ i__3 = *n << 2; if (*lwork >= *n * *n + MAX (i__3, bdspac)) { /* Sufficient workspace for a fast algorithm */ ir = 1; /* Computing MAX */ i__3 = wrkbl, i__2 = *lda * *n + *n; if (*lwork >= MAX (i__3, i__2) + *lda * *n) { /* WORK(IU) is LDA by N and WORK(IR) is LDA by N */ ldwrku = *lda; ldwrkr = *lda; } else { /* if(complicated condition) */ /* Computing MAX */ i__3 = wrkbl, i__2 = *lda * *n + *n; if (*lwork >= MAX (i__3, i__2) + *n * *n) { /* WORK(IU) is LDA by N and WORK(IR) is N by N */ ldwrku = *lda; ldwrkr = *n; } else { /* WORK(IU) is LDWRKU by N and WORK(IR) is N by N */ ldwrku = (*lwork - *n * *n - *n) / *n; ldwrkr = *n; } } itau = ir + ldwrkr * *n; iwork = itau + *n; /* Compute A=Q*R (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__3, &ierr); /* Copy R to VT, zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &vt[vt_offset], ldvt); i__3 = *n - 1; i__2 = *n - 1; NUMlapack_dlaset ("L", &i__3, &i__2, &c_b416, &c_b416, &vt_ref (2, 1), ldvt); /* Generate Q in A (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dorgqr (m, n, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__3, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in VT, copying result to WORK(IR) (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &vt[vt_offset], ldvt, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__3, &ierr); NUMlapack_dlacpy ("L", n, n, &vt[vt_offset], ldvt, &work[ir], &ldwrkr); /* Generate left vectors bidiagonalizing R in WORK(IR) (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", n, n, n, &work[ir], &ldwrkr, &work[itauq], &work[iwork], &i__3, &ierr); /* Generate right vectors bidiagonalizing R in VT (Workspace: need N*N+4*N-1, prefer N*N+3*N+(N-1)*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &vt[vt_offset], ldvt, &work[itaup], &work[iwork], &i__3, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of R in WORK(IR) and computing right singular vectors of R in VT (Workspace: need N*N+BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, n, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &work[ir], &ldwrkr, dum, &c__1, &work[iwork], info); iu = ie + *n; /* Multiply Q in A by left singular vectors of R in WORK(IR), storing result in WORK(IU) and copying to A (Workspace: need N*N+2*N, prefer N*N+M*N+N) */ i__3 = *m; i__2 = ldwrku; for (i__ = 1; i__2 < 0 ? i__ >= i__3 : i__ <= i__3; i__ += i__2) { /* Computing MIN */ i__4 = *m - i__ + 1; chunk = MIN (i__4, ldwrku); NUMblas_dgemm ("N", "N", &chunk, n, n, &c_b438, &a_ref (i__, 1), lda, &work[ir], &ldwrkr, &c_b416, &work[iu], &ldwrku); NUMlapack_dlacpy ("F", &chunk, n, &work[iu], &ldwrku, &a_ref (i__, 1), lda); /* L20: */ } } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *n; /* Compute A=Q*R (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy R to VT, zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &vt[vt_offset], ldvt); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &vt_ref (2, 1), ldvt); /* Generate Q in A (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, n, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in VT (Workspace: need 4*N, prefer 3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &vt[vt_offset], ldvt, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply Q in A by left vectors bidiagonalizing R (Workspace: need 3*N+M, prefer 3*N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "R", "N", m, n, n, &vt[vt_offset], ldvt, &work[itauq], &a[a_offset], lda, &work[iwork], &i__2, &ierr); /* Generate right vectors bidiagonalizing R in VT (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &vt[vt_offset], ldvt, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of A in A and computing right singular vectors of A in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, m, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &a[a_offset], lda, dum, &c__1, &work[iwork], info); } } else if (wntus) { if (wntvn) { /* Path 4 (M much larger than N, JOBU='S', JOBVT='N') N left singular vectors to be computed in U and no right singular vectors to be computed Computing MAX */ i__2 = *n << 2; if (*lwork >= *n * *n + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ ir = 1; if (*lwork >= wrkbl + *lda * *n) { /* WORK(IR) is LDA by N */ ldwrkr = *lda; } else { /* WORK(IR) is N by N */ ldwrkr = *n; } itau = ir + ldwrkr * *n; iwork = itau + *n; /* Compute A=Q*R (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy R to WORK(IR), zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &work[ir], &ldwrkr); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &work[ir + 1], &ldwrkr); /* Generate Q in A (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, n, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in WORK(IR) (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &work[ir], &ldwrkr, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Generate left vectors bidiagonalizing R in WORK(IR) (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", n, n, n, &work[ir], &ldwrkr, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of R in WORK(IR) (Workspace: need N*N+BDSPAC) */ NUMlapack_dbdsqr ("U", n, &c__0, n, &c__0, &s[1], &work[ie], dum, &c__1, &work[ir], &ldwrkr, dum, &c__1, &work[iwork], info); /* Multiply Q in A by left singular vectors of R in WORK(IR), storing result in U (Workspace: need N*N) */ NUMblas_dgemm ("N", "N", m, n, n, &c_b438, &a[a_offset], lda, &work[ir], &ldwrkr, &c_b416, &u[u_offset], ldu); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *n; /* Compute A=Q*R, copying result to U (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Generate Q in U (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, n, n, &u[u_offset], ldu, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Zero out below R in A */ i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &a_ref (2, 1), lda); /* Bidiagonalize R in A (Workspace: need 4*N, prefer 3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply Q in U by left vectors bidiagonalizing R (Workspace: need 3*N+M, prefer 3*N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "R", "N", m, n, n, &a[a_offset], lda, &work[itauq], &u[u_offset], ldu, &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of A in U (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, &c__0, m, &c__0, &s[1], &work[ie], dum, &c__1, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } } else if (wntvo) { /* Path 5 (M much larger than N, JOBU='S', JOBVT='O') N left singular vectors to be computed in U and N right singular vectors to be overwritten on A Computing MAX */ i__2 = *n << 2; if (*lwork >= (*n << 1) * *n + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ iu = 1; if (*lwork >= wrkbl + (*lda << 1) * *n) { /* WORK(IU) is LDA by N and WORK(IR) is LDA by N */ ldwrku = *lda; ir = iu + ldwrku * *n; ldwrkr = *lda; } else if (*lwork >= wrkbl + (*lda + *n) * *n) { /* WORK(IU) is LDA by N and WORK(IR) is N by N */ ldwrku = *lda; ir = iu + ldwrku * *n; ldwrkr = *n; } else { /* WORK(IU) is N by N and WORK(IR) is N by N */ ldwrku = *n; ir = iu + ldwrku * *n; ldwrkr = *n; } itau = ir + ldwrkr * *n; iwork = itau + *n; /* Compute A=Q*R (Workspace: need 2*N*N+2*N, prefer 2*N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy R to WORK(IU), zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &work[iu], &ldwrku); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &work[iu + 1], &ldwrku); /* Generate Q in A (Workspace: need 2*N*N+2*N, prefer 2*N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, n, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in WORK(IU), copying result to WORK(IR) (Workspace: need 2*N*N+4*N, prefer 2*N*N+3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &work[iu], &ldwrku, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", n, n, &work[iu], &ldwrku, &work[ir], &ldwrkr); /* Generate left bidiagonalizing vectors in WORK(IU) (Workspace: need 2*N*N+4*N, prefer 2*N*N+3*N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", n, n, n, &work[iu], &ldwrku, &work[itauq], &work[iwork], &i__2, &ierr); /* Generate right bidiagonalizing vectors in WORK(IR) (Workspace: need 2*N*N+4*N-1, prefer 2*N*N+3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &work[ir], &ldwrkr, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of R in WORK(IU) and computing right singular vectors of R in WORK(IR) (Workspace: need 2*N*N+BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, n, &c__0, &s[1], &work[ie], &work[ir], &ldwrkr, &work[iu], &ldwrku, dum, &c__1, &work[iwork], info); /* Multiply Q in A by left singular vectors of R in WORK(IU), storing result in U (Workspace: need N*N) */ NUMblas_dgemm ("N", "N", m, n, n, &c_b438, &a[a_offset], lda, &work[iu], &ldwrku, &c_b416, &u[u_offset], ldu); /* Copy right singular vectors of R to A (Workspace: need N*N) */ NUMlapack_dlacpy ("F", n, n, &work[ir], &ldwrkr, &a[a_offset], lda); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *n; /* Compute A=Q*R, copying result to U (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Generate Q in U (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, n, n, &u[u_offset], ldu, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Zero out below R in A */ i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &a_ref (2, 1), lda); /* Bidiagonalize R in A (Workspace: need 4*N, prefer 3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply Q in U by left vectors bidiagonalizing R (Workspace: need 3*N+M, prefer 3*N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "R", "N", m, n, n, &a[a_offset], lda, &work[itauq], &u[u_offset], ldu, &work[iwork], &i__2, &ierr); /* Generate right vectors bidiagonalizing R in A (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &a[a_offset], lda, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of A in U and computing right singular vectors of A in A (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, m, &c__0, &s[1], &work[ie], &a[a_offset], lda, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } } else if (wntvas) { /* Path 6 (M much larger than N, JOBU='S', JOBVT='S' or 'A') N left singular vectors to be computed in U and N right singular vectors to be computed in VT Computing MAX */ i__2 = *n << 2; if (*lwork >= *n * *n + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ iu = 1; if (*lwork >= wrkbl + *lda * *n) { /* WORK(IU) is LDA by N */ ldwrku = *lda; } else { /* WORK(IU) is N by N */ ldwrku = *n; } itau = iu + ldwrku * *n; iwork = itau + *n; /* Compute A=Q*R (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy R to WORK(IU), zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &work[iu], &ldwrku); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &work[iu + 1], &ldwrku); /* Generate Q in A (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, n, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in WORK(IU), copying result to VT (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &work[iu], &ldwrku, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", n, n, &work[iu], &ldwrku, &vt[vt_offset], ldvt); /* Generate left bidiagonalizing vectors in WORK(IU) (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", n, n, n, &work[iu], &ldwrku, &work[itauq], &work[iwork], &i__2, &ierr); /* Generate right bidiagonalizing vectors in VT (Workspace: need N*N+4*N-1, prefer N*N+3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &vt[vt_offset], ldvt, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of R in WORK(IU) and computing right singular vectors of R in VT (Workspace: need N*N+BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, n, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &work[iu], &ldwrku, dum, &c__1, &work[iwork], info); /* Multiply Q in A by left singular vectors of R in WORK(IU), storing result in U (Workspace: need N*N) */ NUMblas_dgemm ("N", "N", m, n, n, &c_b438, &a[a_offset], lda, &work[iu], &ldwrku, &c_b416, &u[u_offset], ldu); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *n; /* Compute A=Q*R, copying result to U (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Generate Q in U (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, n, n, &u[u_offset], ldu, &work[itau], &work[iwork], &i__2, &ierr); /* Copy R to VT, zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &vt[vt_offset], ldvt); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &vt_ref (2, 1), ldvt); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in VT (Workspace: need 4*N, prefer 3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &vt[vt_offset], ldvt, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply Q in U by left bidiagonalizing vectors in VT (Workspace: need 3*N+M, prefer 3*N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "R", "N", m, n, n, &vt[vt_offset], ldvt, &work[itauq], &u[u_offset], ldu, &work[iwork], &i__2, &ierr); /* Generate right bidiagonalizing vectors in VT (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &vt[vt_offset], ldvt, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of A in U and computing right singular vectors of A in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, m, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } } } else if (wntua) { if (wntvn) { /* Path 7 (M much larger than N, JOBU='A', JOBVT='N') M left singular vectors to be computed in U and no right singular vectors to be computed Computing MAX */ i__2 = *n + *m, i__3 = *n << 2, i__2 = MAX (i__2, i__3); if (*lwork >= *n * *n + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ ir = 1; if (*lwork >= wrkbl + *lda * *n) { /* WORK(IR) is LDA by N */ ldwrkr = *lda; } else { /* WORK(IR) is N by N */ ldwrkr = *n; } itau = ir + ldwrkr * *n; iwork = itau + *n; /* Compute A=Q*R, copying result to U (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Copy R to WORK(IR), zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &work[ir], &ldwrkr); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &work[ir + 1], &ldwrkr); /* Generate Q in U (Workspace: need N*N+N+M, prefer N*N+N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, m, n, &u[u_offset], ldu, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in WORK(IR) (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &work[ir], &ldwrkr, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Generate left bidiagonalizing vectors in WORK(IR) (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", n, n, n, &work[ir], &ldwrkr, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of R in WORK(IR) (Workspace: need N*N+BDSPAC) */ NUMlapack_dbdsqr ("U", n, &c__0, n, &c__0, &s[1], &work[ie], dum, &c__1, &work[ir], &ldwrkr, dum, &c__1, &work[iwork], info); /* Multiply Q in U by left singular vectors of R in WORK(IR), storing result in A (Workspace: need N*N) */ NUMblas_dgemm ("N", "N", m, n, n, &c_b438, &u[u_offset], ldu, &work[ir], &ldwrkr, &c_b416, &a[a_offset], lda); /* Copy left singular vectors of A from A to U */ NUMlapack_dlacpy ("F", m, n, &a[a_offset], lda, &u[u_offset], ldu); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *n; /* Compute A=Q*R, copying result to U (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Generate Q in U (Workspace: need N+M, prefer N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, m, n, &u[u_offset], ldu, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Zero out below R in A */ i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &a_ref (2, 1), lda); /* Bidiagonalize R in A (Workspace: need 4*N, prefer 3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply Q in U by left bidiagonalizing vectors in A (Workspace: need 3*N+M, prefer 3*N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "R", "N", m, n, n, &a[a_offset], lda, &work[itauq], &u[u_offset], ldu, &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of A in U (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, &c__0, m, &c__0, &s[1], &work[ie], dum, &c__1, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } } else if (wntvo) { /* Path 8 (M much larger than N, JOBU='A', JOBVT='O') M left singular vectors to be computed in U and N right singular vectors to be overwritten on A Computing MAX */ i__2 = *n + *m, i__3 = *n << 2, i__2 = MAX (i__2, i__3); if (*lwork >= (*n << 1) * *n + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ iu = 1; if (*lwork >= wrkbl + (*lda << 1) * *n) { /* WORK(IU) is LDA by N and WORK(IR) is LDA by N */ ldwrku = *lda; ir = iu + ldwrku * *n; ldwrkr = *lda; } else if (*lwork >= wrkbl + (*lda + *n) * *n) { /* WORK(IU) is LDA by N and WORK(IR) is N by N */ ldwrku = *lda; ir = iu + ldwrku * *n; ldwrkr = *n; } else { /* WORK(IU) is N by N and WORK(IR) is N by N */ ldwrku = *n; ir = iu + ldwrku * *n; ldwrkr = *n; } itau = ir + ldwrkr * *n; iwork = itau + *n; /* Compute A=Q*R, copying result to U (Workspace: need 2*N*N+2*N, prefer 2*N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Generate Q in U (Workspace: need 2*N*N+N+M, prefer 2*N*N+N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, m, n, &u[u_offset], ldu, &work[itau], &work[iwork], &i__2, &ierr); /* Copy R to WORK(IU), zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &work[iu], &ldwrku); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &work[iu + 1], &ldwrku); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in WORK(IU), copying result to WORK(IR) (Workspace: need 2*N*N+4*N, prefer 2*N*N+3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &work[iu], &ldwrku, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", n, n, &work[iu], &ldwrku, &work[ir], &ldwrkr); /* Generate left bidiagonalizing vectors in WORK(IU) (Workspace: need 2*N*N+4*N, prefer 2*N*N+3*N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", n, n, n, &work[iu], &ldwrku, &work[itauq], &work[iwork], &i__2, &ierr); /* Generate right bidiagonalizing vectors in WORK(IR) (Workspace: need 2*N*N+4*N-1, prefer 2*N*N+3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &work[ir], &ldwrkr, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of R in WORK(IU) and computing right singular vectors of R in WORK(IR) (Workspace: need 2*N*N+BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, n, &c__0, &s[1], &work[ie], &work[ir], &ldwrkr, &work[iu], &ldwrku, dum, &c__1, &work[iwork], info); /* Multiply Q in U by left singular vectors of R in WORK(IU), storing result in A (Workspace: need N*N) */ NUMblas_dgemm ("N", "N", m, n, n, &c_b438, &u[u_offset], ldu, &work[iu], &ldwrku, &c_b416, &a[a_offset], lda); /* Copy left singular vectors of A from A to U */ NUMlapack_dlacpy ("F", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Copy right singular vectors of R from WORK(IR) to A */ NUMlapack_dlacpy ("F", n, n, &work[ir], &ldwrkr, &a[a_offset], lda); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *n; /* Compute A=Q*R, copying result to U (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Generate Q in U (Workspace: need N+M, prefer N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, m, n, &u[u_offset], ldu, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Zero out below R in A */ i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &a_ref (2, 1), lda); /* Bidiagonalize R in A (Workspace: need 4*N, prefer 3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply Q in U by left bidiagonalizing vectors in A (Workspace: need 3*N+M, prefer 3*N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "R", "N", m, n, n, &a[a_offset], lda, &work[itauq], &u[u_offset], ldu, &work[iwork], &i__2, &ierr); /* Generate right bidiagonalizing vectors in A (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &a[a_offset], lda, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of A in U and computing right singular vectors of A in A (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, m, &c__0, &s[1], &work[ie], &a[a_offset], lda, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } } else if (wntvas) { /* Path 9 (M much larger than N, JOBU='A', JOBVT='S' or 'A') M left singular vectors to be computed in U and N right singular vectors to be computed in VT Computing MAX */ i__2 = *n + *m, i__3 = *n << 2, i__2 = MAX (i__2, i__3); if (*lwork >= *n * *n + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ iu = 1; if (*lwork >= wrkbl + *lda * *n) { /* WORK(IU) is LDA by N */ ldwrku = *lda; } else { /* WORK(IU) is N by N */ ldwrku = *n; } itau = iu + ldwrku * *n; iwork = itau + *n; /* Compute A=Q*R, copying result to U (Workspace: need N*N+2*N, prefer N*N+N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Generate Q in U (Workspace: need N*N+N+M, prefer N*N+N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, m, n, &u[u_offset], ldu, &work[itau], &work[iwork], &i__2, &ierr); /* Copy R to WORK(IU), zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &work[iu], &ldwrku); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &work[iu + 1], &ldwrku); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in WORK(IU), copying result to VT (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &work[iu], &ldwrku, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", n, n, &work[iu], &ldwrku, &vt[vt_offset], ldvt); /* Generate left bidiagonalizing vectors in WORK(IU) (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", n, n, n, &work[iu], &ldwrku, &work[itauq], &work[iwork], &i__2, &ierr); /* Generate right bidiagonalizing vectors in VT (Workspace: need N*N+4*N-1, prefer N*N+3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &vt[vt_offset], ldvt, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of R in WORK(IU) and computing right singular vectors of R in VT (Workspace: need N*N+BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, n, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &work[iu], &ldwrku, dum, &c__1, &work[iwork], info); /* Multiply Q in U by left singular vectors of R in WORK(IU), storing result in A (Workspace: need N*N) */ NUMblas_dgemm ("N", "N", m, n, n, &c_b438, &u[u_offset], ldu, &work[iu], &ldwrku, &c_b416, &a[a_offset], lda); /* Copy left singular vectors of A from A to U */ NUMlapack_dlacpy ("F", m, n, &a[a_offset], lda, &u[u_offset], ldu); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *n; /* Compute A=Q*R, copying result to U (Workspace: need 2*N, prefer N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgeqrf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); /* Generate Q in U (Workspace: need N+M, prefer N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgqr (m, m, n, &u[u_offset], ldu, &work[itau], &work[iwork], &i__2, &ierr); /* Copy R from A to VT, zeroing out below it */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &vt[vt_offset], ldvt); i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dlaset ("L", &i__2, &i__3, &c_b416, &c_b416, &vt_ref (2, 1), ldvt); ie = itau; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize R in VT (Workspace: need 4*N, prefer 3*N+2*N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (n, n, &vt[vt_offset], ldvt, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply Q in U by left bidiagonalizing vectors in VT (Workspace: need 3*N+M, prefer 3*N+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("Q", "R", "N", m, n, n, &vt[vt_offset], ldvt, &work[itauq], &u[u_offset], ldu, &work[iwork], &i__2, &ierr); /* Generate right bidiagonalizing vectors in VT (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &vt[vt_offset], ldvt, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *n; /* Perform bidiagonal QR iteration, computing left singular vectors of A in U and computing right singular vectors of A in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, n, m, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } } } } else { /* M .LT. MNTHR Path 10 (M at least N, but not much larger) Reduce to bidiagonal form without QR decomposition */ ie = 1; itauq = ie + *n; itaup = itauq + *n; iwork = itaup + *n; /* Bidiagonalize A (Workspace: need 3*N+M, prefer 3*N+(M+N)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); if (wntuas) { /* If left singular vectors desired in U, copy result to U and generate left bidiagonalizing vectors in U (Workspace: need 3*N+NCU, prefer 3*N+NCU*NB) */ NUMlapack_dlacpy ("L", m, n, &a[a_offset], lda, &u[u_offset], ldu); if (wntus) { ncu = *n; } if (wntua) { ncu = *m; } i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, &ncu, n, &u[u_offset], ldu, &work[itauq], &work[iwork], &i__2, &ierr); } if (wntvas) { /* If right singular vectors desired in VT, copy result to VT and generate right bidiagonalizing vectors in VT (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB) */ NUMlapack_dlacpy ("U", n, n, &a[a_offset], lda, &vt[vt_offset], ldvt); i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &vt[vt_offset], ldvt, &work[itaup], &work[iwork], &i__2, &ierr); } if (wntuo) { /* If left singular vectors desired in A, generate left bidiagonalizing vectors in A (Workspace: need 4*N, prefer 3*N+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, n, n, &a[a_offset], lda, &work[itauq], &work[iwork], &i__2, &ierr); } if (wntvo) { /* If right singular vectors desired in A, generate right bidiagonalizing vectors in A (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", n, n, n, &a[a_offset], lda, &work[itaup], &work[iwork], &i__2, &ierr); } iwork = ie + *n; if (wntuas || wntuo) { nru = *m; } if (wntun) { nru = 0; } if (wntvas || wntvo) { ncvt = *n; } if (wntvn) { ncvt = 0; } if (!wntuo && !wntvo) { /* Perform bidiagonal QR iteration, if desired, computing left singular vectors in U and computing right singular vectors in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, &ncvt, &nru, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } else if (!wntuo && wntvo) { /* Perform bidiagonal QR iteration, if desired, computing left singular vectors in U and computing right singular vectors in A (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, &ncvt, &nru, &c__0, &s[1], &work[ie], &a[a_offset], lda, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } else { /* Perform bidiagonal QR iteration, if desired, computing left singular vectors in A and computing right singular vectors in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", n, &ncvt, &nru, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &a[a_offset], lda, dum, &c__1, &work[iwork], info); } } } else { /* A has more columns than rows. If A has sufficiently more columns than rows, first reduce using the LQ decomposition (if sufficient workspace available) */ if (*n >= mnthr) { if (wntvn) { /* Path 1t(N much larger than M, JOBVT='N') No right singular vectors to be computed */ itau = 1; iwork = itau + *m; /* Compute A=L*Q (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Zero out above L */ i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &a_ref (1, 2), lda); ie = 1; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in A (Workspace: need 4*M, prefer 3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); if (wntuo || wntuas) { /* If left singular vectors desired, generate Q (Workspace: need 4*M, prefer 3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &a[a_offset], lda, &work[itauq], &work[iwork], &i__2, &ierr); } iwork = ie + *m; nru = 0; if (wntuo || wntuas) { nru = *m; } /* Perform bidiagonal QR iteration, computing left singular vectors of A in A if desired (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", m, &c__0, &nru, &c__0, &s[1], &work[ie], dum, &c__1, &a[a_offset], lda, dum, &c__1, &work[iwork], info); /* If left singular vectors desired in U, copy them there */ if (wntuas) { NUMlapack_dlacpy ("F", m, m, &a[a_offset], lda, &u[u_offset], ldu); } } else if (wntvo && wntun) { /* Path 2t(N much larger than M, JOBU='N', JOBVT='O') M right singular vectors to be overwritten on A and no left singular vectors to be computed Computing MAX */ i__2 = *m << 2; if (*lwork >= *m * *m + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ ir = 1; /* Computing MAX */ i__2 = wrkbl, i__3 = *lda * *n + *m; if (*lwork >= MAX (i__2, i__3) + *lda * *m) { /* WORK(IU) is LDA by N and WORK(IR) is LDA by M */ ldwrku = *lda; chunk = *n; ldwrkr = *lda; } else { /* if(complicated condition) */ /* Computing MAX */ i__2 = wrkbl, i__3 = *lda * *n + *m; if (*lwork >= MAX (i__2, i__3) + *m * *m) { /* WORK(IU) is LDA by N and WORK(IR) is M by M */ ldwrku = *lda; chunk = *n; ldwrkr = *m; } else { /* WORK(IU) is M by CHUNK and WORK(IR) is M by M */ ldwrku = *m; chunk = (*lwork - *m * *m - *m) / *m; ldwrkr = *m; } } itau = ir + ldwrkr * *m; iwork = itau + *m; /* Compute A=L*Q (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy L to WORK(IR) and zero out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &work[ir], &ldwrkr); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &work[ir + ldwrkr], &ldwrkr); /* Generate Q in A (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (m, n, m, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in WORK(IR) (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &work[ir], &ldwrkr, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Generate right vectors bidiagonalizing L (Workspace: need M*M+4*M-1, prefer M*M+3*M+(M-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, m, m, &work[ir], &ldwrkr, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing right singular vectors of L in WORK(IR) (Workspace: need M*M+BDSPAC) */ NUMlapack_dbdsqr ("U", m, m, &c__0, &c__0, &s[1], &work[ie], &work[ir], &ldwrkr, dum, &c__1, dum, &c__1, &work[iwork], info); iu = ie + *m; /* Multiply right singular vectors of L in WORK(IR) by Q in A, storing result in WORK(IU) and copying to A (Workspace: need M*M+2*M, prefer M*M+M*N+M) */ i__2 = *n; i__3 = chunk; for (i__ = 1; i__3 < 0 ? i__ >= i__2 : i__ <= i__2; i__ += i__3) { /* Computing MIN */ i__4 = *n - i__ + 1; blk = MIN (i__4, chunk); NUMblas_dgemm ("N", "N", m, &blk, m, &c_b438, &work[ir], &ldwrkr, &a_ref (1, i__), lda, &c_b416, &work[iu], &ldwrku); NUMlapack_dlacpy ("F", m, &blk, &work[iu], &ldwrku, &a_ref (1, i__), lda); /* L30: */ } } else { /* Insufficient workspace for a fast algorithm */ ie = 1; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize A (Workspace: need 3*M+N, prefer 3*M+(M+N)*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dgebrd (m, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__3, &ierr); /* Generate right vectors bidiagonalizing A (Workspace: need 4*M, prefer 3*M+M*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, n, m, &a[a_offset], lda, &work[itaup], &work[iwork], &i__3, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing right singular vectors of A in A (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("L", m, n, &c__0, &c__0, &s[1], &work[ie], &a[a_offset], lda, dum, &c__1, dum, &c__1, &work[iwork], info); } } else if (wntvo && wntuas) { /* Path 3t(N much larger than M, JOBU='S' or 'A', JOBVT='O') M right singular vectors to be overwritten on A and M left singular vectors to be computed in U Computing MAX */ i__3 = *m << 2; if (*lwork >= *m * *m + MAX (i__3, bdspac)) { /* Sufficient workspace for a fast algorithm */ ir = 1; /* Computing MAX */ i__3 = wrkbl, i__2 = *lda * *n + *m; if (*lwork >= MAX (i__3, i__2) + *lda * *m) { /* WORK(IU) is LDA by N and WORK(IR) is LDA by M */ ldwrku = *lda; chunk = *n; ldwrkr = *lda; } else { /* if(complicated condition) */ /* Computing MAX */ i__3 = wrkbl, i__2 = *lda * *n + *m; if (*lwork >= MAX (i__3, i__2) + *m * *m) { /* WORK(IU) is LDA by N and WORK(IR) is M by M */ ldwrku = *lda; chunk = *n; ldwrkr = *m; } else { /* WORK(IU) is M by CHUNK and WORK(IR) is M by M */ ldwrku = *m; chunk = (*lwork - *m * *m - *m) / *m; ldwrkr = *m; } } itau = ir + ldwrkr * *m; iwork = itau + *m; /* Compute A=L*Q (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__3, &ierr); /* Copy L to U, zeroing about above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &u[u_offset], ldu); i__3 = *m - 1; i__2 = *m - 1; NUMlapack_dlaset ("U", &i__3, &i__2, &c_b416, &c_b416, &u_ref (1, 2), ldu); /* Generate Q in A (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dorglq (m, n, m, &a[a_offset], lda, &work[itau], &work[iwork], &i__3, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in U, copying result to WORK(IR) (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &u[u_offset], ldu, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__3, &ierr); NUMlapack_dlacpy ("U", m, m, &u[u_offset], ldu, &work[ir], &ldwrkr); /* Generate right vectors bidiagonalizing L in WORK(IR) (Workspace: need M*M+4*M-1, prefer M*M+3*M+(M-1)*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, m, m, &work[ir], &ldwrkr, &work[itaup], &work[iwork], &i__3, &ierr); /* Generate left vectors bidiagonalizing L in U (Workspace: need M*M+4*M, prefer M*M+3*M+M*NB) */ i__3 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &u[u_offset], ldu, &work[itauq], &work[iwork], &i__3, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing left singular vectors of L in U, and computing right singular vectors of L in WORK(IR) (Workspace: need M*M+BDSPAC) */ NUMlapack_dbdsqr ("U", m, m, m, &c__0, &s[1], &work[ie], &work[ir], &ldwrkr, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); iu = ie + *m; /* Multiply right singular vectors of L in WORK(IR) by Q in A, storing result in WORK(IU) and copying to A (Workspace: need M*M+2*M, prefer M*M+M*N+M)) */ i__3 = *n; i__2 = chunk; for (i__ = 1; i__2 < 0 ? i__ >= i__3 : i__ <= i__3; i__ += i__2) { /* Computing MIN */ i__4 = *n - i__ + 1; blk = MIN (i__4, chunk); NUMblas_dgemm ("N", "N", m, &blk, m, &c_b438, &work[ir], &ldwrkr, &a_ref (1, i__), lda, &c_b416, &work[iu], &ldwrku); NUMlapack_dlacpy ("F", m, &blk, &work[iu], &ldwrku, &a_ref (1, i__), lda); /* L40: */ } } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *m; /* Compute A=L*Q (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy L to U, zeroing out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &u[u_offset], ldu); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &u_ref (1, 2), ldu); /* Generate Q in A (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (m, n, m, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in U (Workspace: need 4*M, prefer 3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &u[u_offset], ldu, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply right vectors bidiagonalizing L by Q in A (Workspace: need 3*M+N, prefer 3*M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("P", "L", "T", m, n, m, &u[u_offset], ldu, &work[itaup], &a[a_offset], lda, &work[iwork], &i__2, &ierr); /* Generate left vectors bidiagonalizing L in U (Workspace: need 4*M, prefer 3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &u[u_offset], ldu, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing left singular vectors of A in U and computing right singular vectors of A in A (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", m, n, m, &c__0, &s[1], &work[ie], &a[a_offset], lda, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } } else if (wntvs) { if (wntun) { /* Path 4t(N much larger than M, JOBU='N', JOBVT='S') M right singular vectors to be computed in VT and no left singular vectors to be computed Computing MAX */ i__2 = *m << 2; if (*lwork >= *m * *m + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ ir = 1; if (*lwork >= wrkbl + *lda * *m) { /* WORK(IR) is LDA by M */ ldwrkr = *lda; } else { /* WORK(IR) is M by M */ ldwrkr = *m; } itau = ir + ldwrkr * *m; iwork = itau + *m; /* Compute A=L*Q (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy L to WORK(IR), zeroing out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &work[ir], &ldwrkr); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &work[ir + ldwrkr], &ldwrkr); /* Generate Q in A (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (m, n, m, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in WORK(IR) (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &work[ir], &ldwrkr, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Generate right vectors bidiagonalizing L in WORK(IR) (Workspace: need M*M+4*M, prefer M*M+3*M+(M-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, m, m, &work[ir], &ldwrkr, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing right singular vectors of L in WORK(IR) (Workspace: need M*M+BDSPAC) */ NUMlapack_dbdsqr ("U", m, m, &c__0, &c__0, &s[1], &work[ie], &work[ir], &ldwrkr, dum, &c__1, dum, &c__1, &work[iwork], info); /* Multiply right singular vectors of L in WORK(IR) by Q in A, storing result in VT (Workspace: need M*M) */ NUMblas_dgemm ("N", "N", m, n, m, &c_b438, &work[ir], &ldwrkr, &a[a_offset], lda, &c_b416, &vt[vt_offset], ldvt); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *m; /* Compute A=L*Q (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy result to VT */ NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Generate Q in VT (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (m, n, m, &vt[vt_offset], ldvt, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Zero out above L in A */ i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &a_ref (1, 2), lda); /* Bidiagonalize L in A (Workspace: need 4*M, prefer 3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply right vectors bidiagonalizing L by Q in VT (Workspace: need 3*M+N, prefer 3*M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("P", "L", "T", m, n, m, &a[a_offset], lda, &work[itaup], &vt[vt_offset], ldvt, &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing right singular vectors of A in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", m, n, &c__0, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, dum, &c__1, dum, &c__1, &work[iwork], info); } } else if (wntuo) { /* Path 5t(N much larger than M, JOBU='O', JOBVT='S') M right singular vectors to be computed in VT and M left singular vectors to be overwritten on A Computing MAX */ i__2 = *m << 2; if (*lwork >= (*m << 1) * *m + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ iu = 1; if (*lwork >= wrkbl + (*lda << 1) * *m) { /* WORK(IU) is LDA by M and WORK(IR) is LDA by M */ ldwrku = *lda; ir = iu + ldwrku * *m; ldwrkr = *lda; } else if (*lwork >= wrkbl + (*lda + *m) * *m) { /* WORK(IU) is LDA by M and WORK(IR) is M by M */ ldwrku = *lda; ir = iu + ldwrku * *m; ldwrkr = *m; } else { /* WORK(IU) is M by M and WORK(IR) is M by M */ ldwrku = *m; ir = iu + ldwrku * *m; ldwrkr = *m; } itau = ir + ldwrkr * *m; iwork = itau + *m; /* Compute A=L*Q (Workspace: need 2*M*M+2*M, prefer 2*M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy L to WORK(IU), zeroing out below it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &work[iu], &ldwrku); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &work[iu + ldwrku], &ldwrku); /* Generate Q in A (Workspace: need 2*M*M+2*M, prefer 2*M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (m, n, m, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in WORK(IU), copying result to WORK(IR) (Workspace: need 2*M*M+4*M, prefer 2*M*M+3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &work[iu], &ldwrku, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, m, &work[iu], &ldwrku, &work[ir], &ldwrkr); /* Generate right bidiagonalizing vectors in WORK(IU) (Workspace: need 2*M*M+4*M-1, prefer 2*M*M+3*M+(M-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, m, m, &work[iu], &ldwrku, &work[itaup], &work[iwork], &i__2, &ierr); /* Generate left bidiagonalizing vectors in WORK(IR) (Workspace: need 2*M*M+4*M, prefer 2*M*M+3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &work[ir], &ldwrkr, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing left singular vectors of L in WORK(IR) and computing right singular vectors of L in WORK(IU) (Workspace: need 2*M*M+BDSPAC) */ NUMlapack_dbdsqr ("U", m, m, m, &c__0, &s[1], &work[ie], &work[iu], &ldwrku, &work[ir], &ldwrkr, dum, &c__1, &work[iwork], info); /* Multiply right singular vectors of L in WORK(IU) by Q in A, storing result in VT (Workspace: need M*M) */ NUMblas_dgemm ("N", "N", m, n, m, &c_b438, &work[iu], &ldwrku, &a[a_offset], lda, &c_b416, &vt[vt_offset], ldvt); /* Copy left singular vectors of L to A (Workspace: need M*M) */ NUMlapack_dlacpy ("F", m, m, &work[ir], &ldwrkr, &a[a_offset], lda); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *m; /* Compute A=L*Q, copying result to VT (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Generate Q in VT (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (m, n, m, &vt[vt_offset], ldvt, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Zero out above L in A */ i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &a_ref (1, 2), lda); /* Bidiagonalize L in A (Workspace: need 4*M, prefer 3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply right vectors bidiagonalizing L by Q in VT (Workspace: need 3*M+N, prefer 3*M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("P", "L", "T", m, n, m, &a[a_offset], lda, &work[itaup], &vt[vt_offset], ldvt, &work[iwork], &i__2, &ierr); /* Generate left bidiagonalizing vectors of L in A (Workspace: need 4*M, prefer 3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &a[a_offset], lda, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, compute left singular vectors of A in A and compute right singular vectors of A in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", m, n, m, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &a[a_offset], lda, dum, &c__1, &work[iwork], info); } } else if (wntuas) { /* Path 6t(N much larger than M, JOBU='S' or 'A', JOBVT='S') M right singular vectors to be computed in VT and M left singular vectors to be computed in U Computing MAX */ i__2 = *m << 2; if (*lwork >= *m * *m + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ iu = 1; if (*lwork >= wrkbl + *lda * *m) { /* WORK(IU) is LDA by N */ ldwrku = *lda; } else { /* WORK(IU) is LDA by M */ ldwrku = *m; } itau = iu + ldwrku * *m; iwork = itau + *m; /* Compute A=L*Q (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); /* Copy L to WORK(IU), zeroing out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &work[iu], &ldwrku); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &work[iu + ldwrku], &ldwrku); /* Generate Q in A (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (m, n, m, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in WORK(IU), copying result to U (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &work[iu], &ldwrku, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, m, &work[iu], &ldwrku, &u[u_offset], ldu); /* Generate right bidiagonalizing vectors in WORK(IU) (Workspace: need M*M+4*M-1, prefer M*M+3*M+(M-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, m, m, &work[iu], &ldwrku, &work[itaup], &work[iwork], &i__2, &ierr); /* Generate left bidiagonalizing vectors in U (Workspace: need M*M+4*M, prefer M*M+3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &u[u_offset], ldu, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing left singular vectors of L in U and computing right singular vectors of L in WORK(IU) (Workspace: need M*M+BDSPAC) */ NUMlapack_dbdsqr ("U", m, m, m, &c__0, &s[1], &work[ie], &work[iu], &ldwrku, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); /* Multiply right singular vectors of L in WORK(IU) by Q in A, storing result in VT (Workspace: need M*M) */ NUMblas_dgemm ("N", "N", m, n, m, &c_b438, &work[iu], &ldwrku, &a[a_offset], lda, &c_b416, &vt[vt_offset], ldvt); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *m; /* Compute A=L*Q, copying result to VT (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Generate Q in VT (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (m, n, m, &vt[vt_offset], ldvt, &work[itau], &work[iwork], &i__2, &ierr); /* Copy L to U, zeroing out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &u[u_offset], ldu); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &u_ref (1, 2), ldu); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in U (Workspace: need 4*M, prefer 3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &u[u_offset], ldu, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply right bidiagonalizing vectors in U by Q in VT (Workspace: need 3*M+N, prefer 3*M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("P", "L", "T", m, n, m, &u[u_offset], ldu, &work[itaup], &vt[vt_offset], ldvt, &work[iwork], &i__2, &ierr); /* Generate left bidiagonalizing vectors in U (Workspace: need 4*M, prefer 3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &u[u_offset], ldu, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing left singular vectors of A in U and computing right singular vectors of A in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", m, n, m, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } } } else if (wntva) { if (wntun) { /* Path 7t(N much larger than M, JOBU='N', JOBVT='A') N right singular vectors to be computed in VT and no left singular vectors to be computed Computing MAX */ i__2 = *n + *m, i__3 = *m << 2, i__2 = MAX (i__2, i__3); if (*lwork >= *m * *m + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ ir = 1; if (*lwork >= wrkbl + *lda * *m) { /* WORK(IR) is LDA by M */ ldwrkr = *lda; } else { /* WORK(IR) is M by M */ ldwrkr = *m; } itau = ir + ldwrkr * *m; iwork = itau + *m; /* Compute A=L*Q, copying result to VT (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Copy L to WORK(IR), zeroing out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &work[ir], &ldwrkr); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &work[ir + ldwrkr], &ldwrkr); /* Generate Q in VT (Workspace: need M*M+M+N, prefer M*M+M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (n, n, m, &vt[vt_offset], ldvt, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in WORK(IR) (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &work[ir], &ldwrkr, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Generate right bidiagonalizing vectors in WORK(IR) (Workspace: need M*M+4*M-1, prefer M*M+3*M+(M-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, m, m, &work[ir], &ldwrkr, &work[itaup], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing right singular vectors of L in WORK(IR) (Workspace: need M*M+BDSPAC) */ NUMlapack_dbdsqr ("U", m, m, &c__0, &c__0, &s[1], &work[ie], &work[ir], &ldwrkr, dum, &c__1, dum, &c__1, &work[iwork], info); /* Multiply right singular vectors of L in WORK(IR) by Q in VT, storing result in A (Workspace: need M*M) */ NUMblas_dgemm ("N", "N", m, n, m, &c_b438, &work[ir], &ldwrkr, &vt[vt_offset], ldvt, &c_b416, &a[a_offset], lda); /* Copy right singular vectors of A from A to VT */ NUMlapack_dlacpy ("F", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *m; /* Compute A=L*Q, copying result to VT (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Generate Q in VT (Workspace: need M+N, prefer M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (n, n, m, &vt[vt_offset], ldvt, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Zero out above L in A */ i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &a_ref (1, 2), lda); /* Bidiagonalize L in A (Workspace: need 4*M, prefer 3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply right bidiagonalizing vectors in A by Q in VT (Workspace: need 3*M+N, prefer 3*M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("P", "L", "T", m, n, m, &a[a_offset], lda, &work[itaup], &vt[vt_offset], ldvt, &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing right singular vectors of A in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", m, n, &c__0, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, dum, &c__1, dum, &c__1, &work[iwork], info); } } else if (wntuo) { /* Path 8t(N much larger than M, JOBU='O', JOBVT='A') N right singular vectors to be computed in VT and M left singular vectors to be overwritten on A Computing MAX */ i__2 = *n + *m, i__3 = *m << 2, i__2 = MAX (i__2, i__3); if (*lwork >= (*m << 1) * *m + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ iu = 1; if (*lwork >= wrkbl + (*lda << 1) * *m) { /* WORK(IU) is LDA by M and WORK(IR) is LDA by M */ ldwrku = *lda; ir = iu + ldwrku * *m; ldwrkr = *lda; } else if (*lwork >= wrkbl + (*lda + *m) * *m) { /* WORK(IU) is LDA by M and WORK(IR) is M by M */ ldwrku = *lda; ir = iu + ldwrku * *m; ldwrkr = *m; } else { /* WORK(IU) is M by M and WORK(IR) is M by M */ ldwrku = *m; ir = iu + ldwrku * *m; ldwrkr = *m; } itau = ir + ldwrkr * *m; iwork = itau + *m; /* Compute A=L*Q, copying result to VT (Workspace: need 2*M*M+2*M, prefer 2*M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Generate Q in VT (Workspace: need 2*M*M+M+N, prefer 2*M*M+M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (n, n, m, &vt[vt_offset], ldvt, &work[itau], &work[iwork], &i__2, &ierr); /* Copy L to WORK(IU), zeroing out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &work[iu], &ldwrku); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &work[iu + ldwrku], &ldwrku); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in WORK(IU), copying result to WORK(IR) (Workspace: need 2*M*M+4*M, prefer 2*M*M+3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &work[iu], &ldwrku, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, m, &work[iu], &ldwrku, &work[ir], &ldwrkr); /* Generate right bidiagonalizing vectors in WORK(IU) (Workspace: need 2*M*M+4*M-1, prefer 2*M*M+3*M+(M-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, m, m, &work[iu], &ldwrku, &work[itaup], &work[iwork], &i__2, &ierr); /* Generate left bidiagonalizing vectors in WORK(IR) (Workspace: need 2*M*M+4*M, prefer 2*M*M+3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &work[ir], &ldwrkr, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing left singular vectors of L in WORK(IR) and computing right singular vectors of L in WORK(IU) (Workspace: need 2*M*M+BDSPAC) */ NUMlapack_dbdsqr ("U", m, m, m, &c__0, &s[1], &work[ie], &work[iu], &ldwrku, &work[ir], &ldwrkr, dum, &c__1, &work[iwork], info); /* Multiply right singular vectors of L in WORK(IU) by Q in VT, storing result in A (Workspace: need M*M) */ NUMblas_dgemm ("N", "N", m, n, m, &c_b438, &work[iu], &ldwrku, &vt[vt_offset], ldvt, &c_b416, &a[a_offset], lda); /* Copy right singular vectors of A from A to VT */ NUMlapack_dlacpy ("F", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Copy left singular vectors of A from WORK(IR) to A */ NUMlapack_dlacpy ("F", m, m, &work[ir], &ldwrkr, &a[a_offset], lda); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *m; /* Compute A=L*Q, copying result to VT (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Generate Q in VT (Workspace: need M+N, prefer M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (n, n, m, &vt[vt_offset], ldvt, &work[itau], &work[iwork], &i__2, &ierr); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Zero out above L in A */ i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &a_ref (1, 2), lda); /* Bidiagonalize L in A (Workspace: need 4*M, prefer 3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply right bidiagonalizing vectors in A by Q in VT (Workspace: need 3*M+N, prefer 3*M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("P", "L", "T", m, n, m, &a[a_offset], lda, &work[itaup], &vt[vt_offset], ldvt, &work[iwork], &i__2, &ierr); /* Generate left bidiagonalizing vectors in A (Workspace: need 4*M, prefer 3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &a[a_offset], lda, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing left singular vectors of A in A and computing right singular vectors of A in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", m, n, m, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &a[a_offset], lda, dum, &c__1, &work[iwork], info); } } else if (wntuas) { /* Path 9t(N much larger than M, JOBU='S' or 'A', JOBVT='A') N right singular vectors to be computed in VT and M left singular vectors to be computed in U Computing MAX */ i__2 = *n + *m, i__3 = *m << 2, i__2 = MAX (i__2, i__3); if (*lwork >= *m * *m + MAX (i__2, bdspac)) { /* Sufficient workspace for a fast algorithm */ iu = 1; if (*lwork >= wrkbl + *lda * *m) { /* WORK(IU) is LDA by M */ ldwrku = *lda; } else { /* WORK(IU) is M by M */ ldwrku = *m; } itau = iu + ldwrku * *m; iwork = itau + *m; /* Compute A=L*Q, copying result to VT (Workspace: need M*M+2*M, prefer M*M+M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Generate Q in VT (Workspace: need M*M+M+N, prefer M*M+M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (n, n, m, &vt[vt_offset], ldvt, &work[itau], &work[iwork], &i__2, &ierr); /* Copy L to WORK(IU), zeroing out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &work[iu], &ldwrku); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &work[iu + ldwrku], &ldwrku); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in WORK(IU), copying result to U (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &work[iu], &ldwrku, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("L", m, m, &work[iu], &ldwrku, &u[u_offset], ldu); /* Generate right bidiagonalizing vectors in WORK(IU) (Workspace: need M*M+4*M, prefer M*M+3*M+(M-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, m, m, &work[iu], &ldwrku, &work[itaup], &work[iwork], &i__2, &ierr); /* Generate left bidiagonalizing vectors in U (Workspace: need M*M+4*M, prefer M*M+3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &u[u_offset], ldu, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing left singular vectors of L in U and computing right singular vectors of L in WORK(IU) (Workspace: need M*M+BDSPAC) */ NUMlapack_dbdsqr ("U", m, m, m, &c__0, &s[1], &work[ie], &work[iu], &ldwrku, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); /* Multiply right singular vectors of L in WORK(IU) by Q in VT, storing result in A (Workspace: need M*M) */ NUMblas_dgemm ("N", "N", m, n, m, &c_b438, &work[iu], &ldwrku, &vt[vt_offset], ldvt, &c_b416, &a[a_offset], lda); /* Copy right singular vectors of A from A to VT */ NUMlapack_dlacpy ("F", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); } else { /* Insufficient workspace for a fast algorithm */ itau = 1; iwork = itau + *m; /* Compute A=L*Q, copying result to VT (Workspace: need 2*M, prefer M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgelqf (m, n, &a[a_offset], lda, &work[itau], &work[iwork], &i__2, &ierr); NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); /* Generate Q in VT (Workspace: need M+N, prefer M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorglq (n, n, m, &vt[vt_offset], ldvt, &work[itau], &work[iwork], &i__2, &ierr); /* Copy L to U, zeroing out above it */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &u[u_offset], ldu); i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dlaset ("U", &i__2, &i__3, &c_b416, &c_b416, &u_ref (1, 2), ldu); ie = itau; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize L in U (Workspace: need 4*M, prefer 3*M+2*M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, m, &u[u_offset], ldu, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); /* Multiply right bidiagonalizing vectors in U by Q in VT (Workspace: need 3*M+N, prefer 3*M+N*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dormbr ("P", "L", "T", m, n, m, &u[u_offset], ldu, &work[itaup], &vt[vt_offset], ldvt, &work[iwork], &i__2, &ierr); /* Generate left bidiagonalizing vectors in U (Workspace: need 4*M, prefer 3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, m, &u[u_offset], ldu, &work[itauq], &work[iwork], &i__2, &ierr); iwork = ie + *m; /* Perform bidiagonal QR iteration, computing left singular vectors of A in U and computing right singular vectors of A in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("U", m, n, m, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } } } } else { /* N .LT. MNTHR Path 10t(N greater than M, but not much larger) Reduce to bidiagonal form without LQ decomposition */ ie = 1; itauq = ie + *m; itaup = itauq + *m; iwork = itaup + *m; /* Bidiagonalize A (Workspace: need 3*M+N, prefer 3*M+(M+N)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dgebrd (m, n, &a[a_offset], lda, &s[1], &work[ie], &work[itauq], &work[itaup], &work[iwork], &i__2, &ierr); if (wntuas) { /* If left singular vectors desired in U, copy result to U and generate left bidiagonalizing vectors in U (Workspace: need 4*M-1, prefer 3*M+(M-1)*NB) */ NUMlapack_dlacpy ("L", m, m, &a[a_offset], lda, &u[u_offset], ldu); i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, n, &u[u_offset], ldu, &work[itauq], &work[iwork], &i__2, &ierr); } if (wntvas) { /* If right singular vectors desired in VT, copy result to VT and generate right bidiagonalizing vectors in VT (Workspace: need 3*M+NRVT, prefer 3*M+NRVT*NB) */ NUMlapack_dlacpy ("U", m, n, &a[a_offset], lda, &vt[vt_offset], ldvt); if (wntva) { nrvt = *n; } if (wntvs) { nrvt = *m; } i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", &nrvt, n, m, &vt[vt_offset], ldvt, &work[itaup], &work[iwork], &i__2, &ierr); } if (wntuo) { /* If left singular vectors desired in A, generate left bidiagonalizing vectors in A (Workspace: need 4*M-1, prefer 3*M+(M-1)*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("Q", m, m, n, &a[a_offset], lda, &work[itauq], &work[iwork], &i__2, &ierr); } if (wntvo) { /* If right singular vectors desired in A, generate right bidiagonalizing vectors in A (Workspace: need 4*M, prefer 3*M+M*NB) */ i__2 = *lwork - iwork + 1; NUMlapack_dorgbr ("P", m, n, m, &a[a_offset], lda, &work[itaup], &work[iwork], &i__2, &ierr); } iwork = ie + *m; if (wntuas || wntuo) { nru = *m; } if (wntun) { nru = 0; } if (wntvas || wntvo) { ncvt = *n; } if (wntvn) { ncvt = 0; } if (!wntuo && !wntvo) { /* Perform bidiagonal QR iteration, if desired, computing left singular vectors in U and computing right singular vectors in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("L", m, &ncvt, &nru, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } else if (!wntuo && wntvo) { /* Perform bidiagonal QR iteration, if desired, computing left singular vectors in U and computing right singular vectors in A (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("L", m, &ncvt, &nru, &c__0, &s[1], &work[ie], &a[a_offset], lda, &u[u_offset], ldu, dum, &c__1, &work[iwork], info); } else { /* Perform bidiagonal QR iteration, if desired, computing left singular vectors in A and computing right singular vectors in VT (Workspace: need BDSPAC) */ NUMlapack_dbdsqr ("L", m, &ncvt, &nru, &c__0, &s[1], &work[ie], &vt[vt_offset], ldvt, &a[a_offset], lda, dum, &c__1, &work[iwork], info); } } } /* If DBDSQR failed to converge, copy unconverged superdiagonals to WORK( 2:MINMN ) */ if (*info != 0) { if (ie > 2) { i__2 = minmn - 1; for (i__ = 1; i__ <= i__2; ++i__) { work[i__ + 1] = work[i__ + ie - 1]; /* L50: */ } } if (ie < 2) { for (i__ = minmn - 1; i__ >= 1; --i__) { work[i__ + 1] = work[i__ + ie - 1]; /* L60: */ } } } /* Undo scaling if necessary */ if (iscl == 1) { if (anrm > bignum) { NUMlapack_dlascl ("G", &c__0, &c__0, &bignum, &anrm, &minmn, &c__1, &s[1], &minmn, &ierr); } if (*info != 0 && anrm > bignum) { i__2 = minmn - 1; NUMlapack_dlascl ("G", &c__0, &c__0, &bignum, &anrm, &i__2, &c__1, &work[2], &minmn, &ierr); } if (anrm < smlnum) { NUMlapack_dlascl ("G", &c__0, &c__0, &smlnum, &anrm, &minmn, &c__1, &s[1], &minmn, &ierr); } if (*info != 0 && anrm < smlnum) { i__2 = minmn - 1; NUMlapack_dlascl ("G", &c__0, &c__0, &smlnum, &anrm, &i__2, &c__1, &work[2], &minmn, &ierr); } } /* Return optimal workspace in WORK(1) */ work[1] = (double) maxwrk; return 0; } /* NUMlapack_dgesvd */ #undef vt_ref #undef u_ref int NUMlapack_dgetf2 (long *m, long *n, double *a, long *lda, long *ipiv, long *info) { /* Table of constant values */ static long c__1 = 1; static double c_b6 = -1.; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; double d__1; /* Local variables */ static long j; static long jp; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --ipiv; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGETF2", &i__1); return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0) { return 0; } i__1 = MIN (*m, *n); for (j = 1; j <= i__1; ++j) { /* Find pivot and test for singularity. */ i__2 = *m - j + 1; jp = j - 1 + NUMblas_idamax (&i__2, &a_ref (j, j), &c__1); ipiv[j] = jp; if (a_ref (jp, j) != 0.) { /* Apply the interchange to columns 1:N. */ if (jp != j) { NUMblas_dswap (n, &a_ref (j, 1), lda, &a_ref (jp, 1), lda); } /* Compute elements J+1:M of J-th column. */ if (j < *m) { i__2 = *m - j; d__1 = 1. / a_ref (j, j); NUMblas_dscal (&i__2, &d__1, &a_ref (j + 1, j), &c__1); } } else if (*info == 0) { *info = j; } if (j < MIN (*m, *n)) { /* Update trailing submatrix. */ i__2 = *m - j; i__3 = *n - j; NUMblas_dger (&i__2, &i__3, &c_b6, &a_ref (j + 1, j), &c__1, &a_ref (j, j + 1), lda, &a_ref (j + 1, j + 1), lda); } /* L10: */ } return 0; } /* NUMlapack_dgetf2 */ int NUMlapack_dgetri (long *n, double *a, long *lda, long *ipiv, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__2 = 2; static double c_b20 = -1.; static double c_b22 = 1.; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__, j; static long nbmin; static long jb, nb, jj, jp, nn; static long ldwork; static long lwkopt; static long lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --ipiv; --work; /* Function Body */ *info = 0; nb = NUMlapack_ilaenv (&c__1, "DGETRI", " ", n, &c_n1, &c_n1, &c_n1, 6, 1); lwkopt = *n * nb; work[1] = (double) lwkopt; lquery = *lwork == -1; if (*n < 0) { *info = -1; } else if (*lda < MAX (1, *n)) { *info = -3; } else if (*lwork < MAX (1, *n) && !lquery) { *info = -6; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGETRI", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*n == 0) { return 0; } /* Form inv(U). If INFO > 0 from DTRTRI, then U is singular, and the inverse is not computed. */ NUMlapack_dtrtri ("Upper", "Non-unit", n, &a[a_offset], lda, info); if (*info > 0) { return 0; } nbmin = 2; ldwork = *n; if (nb > 1 && nb < *n) { /* Computing MAX */ i__1 = ldwork * nb; iws = MAX (i__1, 1); if (*lwork < iws) { nb = *lwork / ldwork; /* Computing MAX */ i__1 = 2, i__2 = NUMlapack_ilaenv (&c__2, "DGETRI", " ", n, &c_n1, &c_n1, &c_n1, 6, 1); nbmin = MAX (i__1, i__2); } } else { iws = *n; } /* Solve the equation inv(A)*L = inv(U) for inv(A). */ if (nb < nbmin || nb >= *n) { /* Use unblocked code. */ for (j = *n; j >= 1; --j) { /* Copy current column of L to WORK and replace with zeros. */ i__1 = *n; for (i__ = j + 1; i__ <= i__1; ++i__) { work[i__] = a_ref (i__, j); a_ref (i__, j) = 0.; /* L10: */ } /* Compute current column of inv(A). */ if (j < *n) { i__1 = *n - j; NUMblas_dgemv ("No transpose", n, &i__1, &c_b20, &a_ref (1, j + 1), lda, &work[j + 1], &c__1, &c_b22, &a_ref (1, j), &c__1); } /* L20: */ } } else { /* Use blocked code. */ nn = (*n - 1) / nb * nb + 1; i__1 = -nb; for (j = nn; i__1 < 0 ? j >= 1 : j <= 1; j += i__1) { /* Computing MIN */ i__2 = nb, i__3 = *n - j + 1; jb = MIN (i__2, i__3); /* Copy current block column of L to WORK and replace with zeros. */ i__2 = j + jb - 1; for (jj = j; jj <= i__2; ++jj) { i__3 = *n; for (i__ = jj + 1; i__ <= i__3; ++i__) { work[i__ + (jj - j) * ldwork] = a_ref (i__, jj); a_ref (i__, jj) = 0.; /* L30: */ } /* L40: */ } /* Compute current block column of inv(A). */ if (j + jb <= *n) { i__2 = *n - j - jb + 1; NUMblas_dgemm ("No transpose", "No transpose", n, &jb, &i__2, &c_b20, &a_ref (1, j + jb), lda, &work[j + jb], &ldwork, &c_b22, &a_ref (1, j), lda); } NUMblas_dtrsm ("Right", "Lower", "No transpose", "Unit", n, &jb, &c_b22, &work[j], &ldwork, &a_ref (1, j), lda); /* L50: */ } } /* Apply column interchanges. */ for (j = *n - 1; j >= 1; --j) { jp = ipiv[j]; if (jp != j) { NUMblas_dswap (n, &a_ref (1, j), &c__1, &a_ref (1, jp), &c__1); } /* L60: */ } work[1] = (double) iws; return 0; } /* NUMlapack_dgetri */ int NUMlapack_dgetrf (long *m, long *n, double *a, long *lda, long *ipiv, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static double c_b16 = 1.; static double c_b19 = -1.; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4, i__5; /* Local variables */ static long i__, j; static long iinfo; static long jb, nb; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --ipiv; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *m)) { *info = -4; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGETRF", &i__1); return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0) { return 0; } /* Determine the block size for this environment. */ nb = NUMlapack_ilaenv (&c__1, "DGETRF", " ", m, n, &c_n1, &c_n1, 6, 1); if (nb <= 1 || nb >= MIN (*m, *n)) { /* Use unblocked code. */ NUMlapack_dgetf2 (m, n, &a[a_offset], lda, &ipiv[1], info); } else { /* Use blocked code. */ i__1 = MIN (*m, *n); i__2 = nb; for (j = 1; i__2 < 0 ? j >= i__1 : j <= i__1; j += i__2) { /* Computing MIN */ i__3 = MIN (*m, *n) - j + 1; jb = MIN (i__3, nb); /* Factor diagonal and subdiagonal blocks and test for exact singularity. */ i__3 = *m - j + 1; NUMlapack_dgetf2 (&i__3, &jb, &a_ref (j, j), lda, &ipiv[j], &iinfo); /* Adjust INFO and the pivot indices. */ if (*info == 0 && iinfo > 0) { *info = iinfo + j - 1; } /* Computing MIN */ i__4 = *m, i__5 = j + jb - 1; i__3 = MIN (i__4, i__5); for (i__ = j; i__ <= i__3; ++i__) { ipiv[i__] = j - 1 + ipiv[i__]; /* L10: */ } /* Apply interchanges to columns 1:J-1. */ i__3 = j - 1; i__4 = j + jb - 1; NUMlapack_dlaswp (&i__3, &a[a_offset], lda, &j, &i__4, &ipiv[1], &c__1); if (j + jb <= *n) { /* Apply interchanges to columns J+JB:N. */ i__3 = *n - j - jb + 1; i__4 = j + jb - 1; NUMlapack_dlaswp (&i__3, &a_ref (1, j + jb), lda, &j, &i__4, &ipiv[1], &c__1); /* Compute block row of U. */ i__3 = *n - j - jb + 1; NUMblas_dtrsm ("Left", "Lower", "No transpose", "Unit", &jb, &i__3, &c_b16, &a_ref (j, j), lda, &a_ref (j, j + jb), lda); if (j + jb <= *m) { /* Update trailing submatrix. */ i__3 = *m - j - jb + 1; i__4 = *n - j - jb + 1; NUMblas_dgemm ("No transpose", "No transpose", &i__3, &i__4, &jb, &c_b19, &a_ref (j + jb, j), lda, &a_ref (j, j + jb), lda, &c_b16, &a_ref (j + jb, j + jb), lda); } } /* L20: */ } } return 0; } /* NUMlapack_dgetrf */ int NUMlapack_dgetrs (const char *trans, long *n, long *nrhs, double *a, long *lda, long *ipiv, double *b, long *ldb, long *info) { /* Table of constant values */ static long c__1 = 1; static double c_b12 = 1.; static long c_n1 = -1; /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, i__1; /* Local variables */ static long notran; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --ipiv; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; /* Function Body */ *info = 0; notran = lsame_ (trans, "N"); if (!notran && !lsame_ (trans, "T") && !lsame_ (trans, "C")) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*nrhs < 0) { *info = -3; } else if (*lda < MAX (1, *n)) { *info = -5; } else if (*ldb < MAX (1, *n)) { *info = -8; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGETRS", &i__1); return 0; } /* Quick return if possible */ if (*n == 0 || *nrhs == 0) { return 0; } if (notran) { /* Solve A * X = B. Apply row interchanges to the right hand sides. */ NUMlapack_dlaswp (nrhs, &b[b_offset], ldb, &c__1, n, &ipiv[1], &c__1); /* Solve L*X = B, overwriting B with X. */ NUMblas_dtrsm ("Left", "Lower", "No transpose", "Unit", n, nrhs, &c_b12, &a[a_offset], lda, &b[b_offset], ldb); /* Solve U*X = B, overwriting B with X. */ NUMblas_dtrsm ("Left", "Upper", "No transpose", "Non-unit", n, nrhs, &c_b12, &a[a_offset], lda, &b[b_offset], ldb); } else { /* Solve A' * X = B. Solve U'*X = B, overwriting B with X. */ NUMblas_dtrsm ("Left", "Upper", "Transpose", "Non-unit", n, nrhs, &c_b12, &a[a_offset], lda, &b[b_offset], ldb); /* Solve L'*X = B, overwriting B with X. */ NUMblas_dtrsm ("Left", "Lower", "Transpose", "Unit", n, nrhs, &c_b12, &a[a_offset], lda, &b[b_offset], ldb); /* Apply row interchanges to the solution vectors. */ NUMlapack_dlaswp (nrhs, &b[b_offset], ldb, &c__1, n, &ipiv[1], &c_n1); } return 0; } /* NUMlapack_dgetrs */ int NUMlapack_dggsvd (const char *jobu, const char *jobv, const char *jobq, long *m, long *n, long *p, long *k, long *l, double *a, long *lda, double *b, long *ldb, double *alpha, double *beta, double *u, long *ldu, double *v, long *ldv, double *q, long *ldq, double *work, long *iwork, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, q_dim1, q_offset, u_dim1, u_offset, v_dim1, v_offset, i__1, i__2; /* Local variables */ static long ibnd; static double tola; static long isub; static double tolb, unfl, temp, smax; static long i__, j; static double anorm, bnorm; static long wantq, wantu, wantv; static long ncycle; static double ulp; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; --alpha; --beta; u_dim1 = *ldu; u_offset = 1 + u_dim1 * 1; u -= u_offset; v_dim1 = *ldv; v_offset = 1 + v_dim1 * 1; v -= v_offset; q_dim1 = *ldq; q_offset = 1 + q_dim1 * 1; q -= q_offset; --work; --iwork; /* Function Body */ wantu = lsame_ (jobu, "U"); wantv = lsame_ (jobv, "V"); wantq = lsame_ (jobq, "Q"); *info = 0; if (! (wantu || lsame_ (jobu, "N"))) { *info = -1; } else if (! (wantv || lsame_ (jobv, "N"))) { *info = -2; } else if (! (wantq || lsame_ (jobq, "N"))) { *info = -3; } else if (*m < 0) { *info = -4; } else if (*n < 0) { *info = -5; } else if (*p < 0) { *info = -6; } else if (*lda < MAX (1, *m)) { *info = -10; } else if (*ldb < MAX (1, *p)) { *info = -12; } else if (*ldu < 1 || wantu && *ldu < *m) { *info = -16; } else if (*ldv < 1 || wantv && *ldv < *p) { *info = -18; } else if (*ldq < 1 || wantq && *ldq < *n) { *info = -20; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGGSVD", &i__1); return 0; } /* Compute the Frobenius norm of matrices A and B */ anorm = NUMlapack_dlange ("1", m, n, &a[a_offset], lda, &work[1]); bnorm = NUMlapack_dlange ("1", p, n, &b[b_offset], ldb, &work[1]); /* Get machine precision and set up threshold for determining the effective numerical rank of the matrices A and B. */ ulp = NUMblas_dlamch ("Precision"); unfl = NUMblas_dlamch ("Safe Minimum"); tola = MAX (*m, *n) * MAX (anorm, unfl) * ulp; tolb = MAX (*p, *n) * MAX (bnorm, unfl) * ulp; /* Preprocessing */ NUMlapack_dggsvp (jobu, jobv, jobq, m, p, n, &a[a_offset], lda, &b[b_offset], ldb, &tola, &tolb, k, l, &u[u_offset], ldu, &v[v_offset], ldv, &q[q_offset], ldq, &iwork[1], &work[1], &work[*n + 1], info); /* Compute the GSVD of two upper "triangular" matrices */ NUMlapack_dtgsja (jobu, jobv, jobq, m, p, n, k, l, &a[a_offset], lda, &b[b_offset], ldb, &tola, &tolb, &alpha[1], &beta[1], &u[u_offset], ldu, &v[v_offset], ldv, &q[q_offset], ldq, &work[1], &ncycle, info); /* Sort the singular values and store the pivot indices in IWORK Copy ALPHA to WORK, then sort ALPHA in WORK */ NUMblas_dcopy (n, &alpha[1], &c__1, &work[1], &c__1); /* Computing MIN */ i__1 = *l, i__2 = *m - *k; ibnd = MIN (i__1, i__2); i__1 = ibnd; for (i__ = 1; i__ <= i__1; ++i__) { /* Scan for largest ALPHA(K+I) */ isub = i__; smax = work[*k + i__]; i__2 = ibnd; for (j = i__ + 1; j <= i__2; ++j) { temp = work[*k + j]; if (temp > smax) { isub = j; smax = temp; } /* L10: */ } if (isub != i__) { work[*k + isub] = work[*k + i__]; work[*k + i__] = smax; iwork[*k + i__] = *k + isub; } else { iwork[*k + i__] = *k + i__; } /* L20: */ } return 0; } /* NUMlapack_dggsvd */ #define b_ref(a_1,a_2) b[(a_2)*b_dim1 + a_1] #define u_ref(a_1,a_2) u[(a_2)*u_dim1 + a_1] #define v_ref(a_1,a_2) v[(a_2)*v_dim1 + a_1] int NUMlapack_dggsvp (const char *jobu, const char *jobv, const char *jobq, long *m, long *p, long *n, double *a, long *lda, double *b, long *ldb, double *tola, double *tolb, long *k, long *l, double *u, long *ldu, double *v, long *ldv, double *q, long *ldq, long *iwork, double *tau, double *work, long *info) { /* Table of constant values */ static double c_b12 = 0.; static double c_b22 = 1.; /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, q_dim1, q_offset, u_dim1, u_offset, v_dim1, v_offset, i__1, i__2, i__3; double d__1; /* Local variables */ static long i__, j; static long wantq, wantu, wantv; static long forwrd; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; u_dim1 = *ldu; u_offset = 1 + u_dim1 * 1; u -= u_offset; v_dim1 = *ldv; v_offset = 1 + v_dim1 * 1; v -= v_offset; q_dim1 = *ldq; q_offset = 1 + q_dim1 * 1; q -= q_offset; --iwork; --tau; --work; /* Function Body */ wantu = lsame_ (jobu, "U"); wantv = lsame_ (jobv, "V"); wantq = lsame_ (jobq, "Q"); forwrd = TRUE; *info = 0; if (! (wantu || lsame_ (jobu, "N"))) { *info = -1; } else if (! (wantv || lsame_ (jobv, "N"))) { *info = -2; } else if (! (wantq || lsame_ (jobq, "N"))) { *info = -3; } else if (*m < 0) { *info = -4; } else if (*p < 0) { *info = -5; } else if (*n < 0) { *info = -6; } else if (*lda < MAX (1, *m)) { *info = -8; } else if (*ldb < MAX (1, *p)) { *info = -10; } else if (*ldu < 1 || wantu && *ldu < *m) { *info = -16; } else if (*ldv < 1 || wantv && *ldv < *p) { *info = -18; } else if (*ldq < 1 || wantq && *ldq < *n) { *info = -20; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DGGSVP", &i__1); return 0; } /* QR with column pivoting of B: B*P = V*( S11 S12 ) ( 0 0 ) */ i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { iwork[i__] = 0; /* L10: */ } NUMlapack_dgeqpf (p, n, &b[b_offset], ldb, &iwork[1], &tau[1], &work[1], info); /* Update A := A*P */ NUMlapack_dlapmt (&forwrd, m, n, &a[a_offset], lda, &iwork[1]); /* Determine the effective rank of matrix B. */ *l = 0; i__1 = MIN (*p, *n); for (i__ = 1; i__ <= i__1; ++i__) { if ( (d__1 = b_ref (i__, i__), fabs (d__1)) > *tolb) { ++ (*l); } /* L20: */ } if (wantv) { /* Copy the details of V, and form V. */ NUMlapack_dlaset ("Full", p, p, &c_b12, &c_b12, &v[v_offset], ldv); if (*p > 1) { i__1 = *p - 1; NUMlapack_dlacpy ("Lower", &i__1, n, &b_ref (2, 1), ldb, &v_ref (2, 1), ldv); } i__1 = MIN (*p, *n); NUMlapack_dorg2r (p, p, &i__1, &v[v_offset], ldv, &tau[1], &work[1], info); } /* Clean up B */ i__1 = *l - 1; for (j = 1; j <= i__1; ++j) { i__2 = *l; for (i__ = j + 1; i__ <= i__2; ++i__) { b_ref (i__, j) = 0.; /* L30: */ } /* L40: */ } if (*p > *l) { i__1 = *p - *l; NUMlapack_dlaset ("Full", &i__1, n, &c_b12, &c_b12, &b_ref (*l + 1, 1), ldb); } if (wantq) { /* Set Q = I and Update Q := Q*P */ NUMlapack_dlaset ("Full", n, n, &c_b12, &c_b22, &q[q_offset], ldq); NUMlapack_dlapmt (&forwrd, n, n, &q[q_offset], ldq, &iwork[1]); } if (*p >= *l && *n != *l) { /* RQ factorization of (S11 S12): ( S11 S12 ) = ( 0 S12 )*Z */ NUMlapack_dgerq2 (l, n, &b[b_offset], ldb, &tau[1], &work[1], info); /* Update A := A*Z' */ NUMlapack_dormr2 ("Right", "Transpose", m, n, l, &b[b_offset], ldb, &tau[1], &a[a_offset], lda, &work[1], info); if (wantq) { /* Update Q := Q*Z' */ NUMlapack_dormr2 ("Right", "Transpose", n, n, l, &b[b_offset], ldb, &tau[1], &q[q_offset], ldq, &work[1], info); } /* Clean up B */ i__1 = *n - *l; NUMlapack_dlaset ("Full", l, &i__1, &c_b12, &c_b12, &b[b_offset], ldb); i__1 = *n; for (j = *n - *l + 1; j <= i__1; ++j) { i__2 = *l; for (i__ = j - *n + *l + 1; i__ <= i__2; ++i__) { b_ref (i__, j) = 0.; /* L50: */ } /* L60: */ } } /* Let N-L L A = ( A11 A12 ) M, then the following does the complete QR decomposition of A11: A11 = U*( 0 T12 )*P1' ( 0 0 ) */ i__1 = *n - *l; for (i__ = 1; i__ <= i__1; ++i__) { iwork[i__] = 0; /* L70: */ } i__1 = *n - *l; NUMlapack_dgeqpf (m, &i__1, &a[a_offset], lda, &iwork[1], &tau[1], &work[1], info); /* Determine the effective rank of A11 */ *k = 0; /* Computing MIN */ i__2 = *m, i__3 = *n - *l; i__1 = MIN (i__2, i__3); for (i__ = 1; i__ <= i__1; ++i__) { if ( (d__1 = a_ref (i__, i__), fabs (d__1)) > *tola) { ++ (*k); } /* L80: */ } /* Update A12 := U'*A12, where A12 = A( 1:M, N-L+1:N ) Computing MIN */ i__2 = *m, i__3 = *n - *l; i__1 = MIN (i__2, i__3); NUMlapack_dorm2r ("Left", "Transpose", m, l, &i__1, &a[a_offset], lda, &tau[1], &a_ref (1, *n - *l + 1), lda, &work[1], info); if (wantu) { /* Copy the details of U, and form U */ NUMlapack_dlaset ("Full", m, m, &c_b12, &c_b12, &u[u_offset], ldu); if (*m > 1) { i__1 = *m - 1; i__2 = *n - *l; NUMlapack_dlacpy ("Lower", &i__1, &i__2, &a_ref (2, 1), lda, &u_ref (2, 1), ldu); } /* Computing MIN */ i__2 = *m, i__3 = *n - *l; i__1 = MIN (i__2, i__3); NUMlapack_dorg2r (m, m, &i__1, &u[u_offset], ldu, &tau[1], &work[1], info); } if (wantq) { /* Update Q( 1:N, 1:N-L ) = Q( 1:N, 1:N-L )*P1 */ i__1 = *n - *l; NUMlapack_dlapmt (&forwrd, n, &i__1, &q[q_offset], ldq, &iwork[1]); } /* Clean up A: set the strictly lower triangular part of A(1:K, 1:K) = 0, and A( K+1:M, 1:N-L ) = 0. */ i__1 = *k - 1; for (j = 1; j <= i__1; ++j) { i__2 = *k; for (i__ = j + 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L90: */ } /* L100: */ } if (*m > *k) { i__1 = *m - *k; i__2 = *n - *l; NUMlapack_dlaset ("Full", &i__1, &i__2, &c_b12, &c_b12, &a_ref (*k + 1, 1), lda); } if (*n - *l > *k) { /* RQ factorization of ( T11 T12 ) = ( 0 T12 )*Z1 */ i__1 = *n - *l; NUMlapack_dgerq2 (k, &i__1, &a[a_offset], lda, &tau[1], &work[1], info); if (wantq) { /* Update Q( 1:N,1:N-L ) = Q( 1:N,1:N-L )*Z1' */ i__1 = *n - *l; NUMlapack_dormr2 ("Right", "Transpose", n, &i__1, k, &a[a_offset], lda, &tau[1], &q[q_offset], ldq, &work[1], info); } /* Clean up A */ i__1 = *n - *l - *k; NUMlapack_dlaset ("Full", k, &i__1, &c_b12, &c_b12, &a[a_offset], lda); i__1 = *n - *l; for (j = *n - *l - *k + 1; j <= i__1; ++j) { i__2 = *k; for (i__ = j - *n + *l + *k + 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L110: */ } /* L120: */ } } if (*m > *k) { /* QR factorization of A( K+1:M,N-L+1:N ) */ i__1 = *m - *k; NUMlapack_dgeqr2 (&i__1, l, &a_ref (*k + 1, *n - *l + 1), lda, &tau[1], &work[1], info); if (wantu) { /* Update U(:,K+1:M) := U(:,K+1:M)*U1 */ i__1 = *m - *k; /* Computing MIN */ i__3 = *m - *k; i__2 = MIN (i__3, *l); NUMlapack_dorm2r ("Right", "No transpose", m, &i__1, &i__2, &a_ref (*k + 1, *n - *l + 1), lda, &tau[1], &u_ref (1, *k + 1), ldu, &work[1], info); } /* Clean up */ i__1 = *n; for (j = *n - *l + 1; j <= i__1; ++j) { i__2 = *m; for (i__ = j - *n + *k + *l + 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L130: */ } /* L140: */ } } return 0; } /* NUMlapack_dggsvp */ #undef v_ref #undef u_ref #undef b_ref int NUMlapack_dhseqr (const char *job, const char *compz, long *n, long *ilo, long *ihi, double *h__, long *ldh, double *wr, double *wi, double *z__, long *ldz, double *work, long *lwork, long *info) { /* Table of constant values */ static double c_b9 = 0.; static double c_b10 = 1.; static long c__4 = 4; static long c_n1 = -1; static long c__2 = 2; static long c__8 = 8; static long c__15 = 15; static int c_false = FALSE; static long c__1 = 1; /* System generated locals */ const char *a__1[2]; long h_dim1, h_offset, z_dim1, z_offset, i__1, i__2, i__3[2], i__4, i__5; double d__1, d__2; char ch__1[2]; /* Local variables */ static long maxb; static double absw; static long ierr; static double unfl, temp, ovfl; static long i__, j, k, l; static double s[225] /* was [15][15] */ , v[16]; static long itemp; static long i1, i2; static int initz, wantt, wantz; static long ii, nh; static long nr, ns; static long nv; static double vv[16]; static double smlnum; static int lquery; static long itn; static double tau; static long its; static double ulp, tst1; #define h___ref(a_1,a_2) h__[(a_2)*h_dim1 + a_1] #define s_ref(a_1,a_2) s[(a_2)*15 + a_1 - 16] #define z___ref(a_1,a_2) z__[(a_2)*z_dim1 + a_1] h_dim1 = *ldh; h_offset = 1 + h_dim1 * 1; h__ -= h_offset; --wr; --wi; z_dim1 = *ldz; z_offset = 1 + z_dim1 * 1; z__ -= z_offset; --work; /* Function Body */ wantt = lsame_ (job, "S"); initz = lsame_ (compz, "I"); wantz = initz || lsame_ (compz, "V"); *info = 0; work[1] = (double) MAX (1, *n); lquery = *lwork == -1; if (!lsame_ (job, "E") && !wantt) { *info = -1; } else if (!lsame_ (compz, "N") && !wantz) { *info = -2; } else if (*n < 0) { *info = -3; } else if (*ilo < 1 || *ilo > MAX (1, *n)) { *info = -4; } else if (*ihi < MIN (*ilo, *n) || *ihi > *n) { *info = -5; } else if (*ldh < MAX (1, *n)) { *info = -7; } else if (*ldz < 1 || wantz && *ldz < MAX (1, *n)) { *info = -11; } else if (*lwork < MAX (1, *n) && !lquery) { *info = -13; } if (*info != 0) { i__1 = - (*info); xerbla_ ("NUMlapack_dhseqr ", &i__1); return 0; } else if (lquery) { return 0; } /* Initialize Z, if necessary */ if (initz) { NUMlapack_dlaset ("Full", n, n, &c_b9, &c_b10, &z__[z_offset], ldz); } /* Store the eigenvalues isolated by NUMlapack_dgebal. */ i__1 = *ilo - 1; for (i__ = 1; i__ <= i__1; ++i__) { wr[i__] = h___ref (i__, i__); wi[i__] = 0.; /* L10: */ } i__1 = *n; for (i__ = *ihi + 1; i__ <= i__1; ++i__) { wr[i__] = h___ref (i__, i__); wi[i__] = 0.; /* L20: */ } /* Quick return if possible. */ if (*n == 0) { return 0; } if (*ilo == *ihi) { wr[*ilo] = h___ref (*ilo, *ilo); wi[*ilo] = 0.; return 0; } /* Set rows and columns ILO to IHI to zero below the first subdiagonal. */ i__1 = *ihi - 2; for (j = *ilo; j <= i__1; ++j) { i__2 = *n; for (i__ = j + 2; i__ <= i__2; ++i__) { h___ref (i__, j) = 0.; /* L30: */ } /* L40: */ } nh = *ihi - *ilo + 1; /* Determine the order of the multi-shift QR algorithm to be used. Writing concatenation */ i__3[0] = 1, a__1[0] = job; i__3[1] = 1, a__1[1] = compz; s_cat ( (char *) ch__1, a__1, i__3, &c__2, 2); ns = NUMlapack_ilaenv (&c__4, "NUMlapack_dhseqr ", ch__1, n, ilo, ihi, &c_n1, 6, 2); /* Writing concatenation */ i__3[0] = 1, a__1[0] = job; i__3[1] = 1, a__1[1] = compz; s_cat (ch__1, a__1, i__3, &c__2, 2); maxb = NUMlapack_ilaenv (&c__8, "NUMlapack_dhseqr ", ch__1, n, ilo, ihi, &c_n1, 6, 2); if (ns <= 2 || ns > nh || maxb >= nh) { /* Use the standard double-shift algorithm */ NUMlapack_dlahqr (&wantt, &wantz, n, ilo, ihi, &h__[h_offset], ldh, &wr[1], &wi[1], ilo, ihi, &z__[z_offset], ldz, info); return 0; } maxb = MAX (3, maxb); /* Computing MIN */ i__1 = MIN (ns, maxb); ns = MIN (i__1, 15); /* Now 2 < NS <= MAXB < NH. Set machine-dependent constants for the stopping criterion. If norm(H) <= sqrt(OVFL), overflow should not occur. */ unfl = NUMblas_dlamch ("Safe minimum"); ovfl = 1. / unfl; NUMlapack_dlabad (&unfl, &ovfl); ulp = NUMblas_dlamch ("Precision"); smlnum = unfl * (nh / ulp); /* I1 and I2 are the indices of the first row and last column of H to which transformations must be applied. If eigenvalues only are being computed, I1 and I2 are set inside the main loop. */ if (wantt) { i1 = 1; i2 = *n; } /* ITN is the total number of multiple-shift QR iterations allowed. */ itn = nh * 30; /* The main loop begins here. I is the loop index and decreases from IHI to ILO in steps of at most MAXB. Each iteration of the loop works with the active submatrix in rows and columns L to I. Eigenvalues I+1 to IHI have already converged. Either L = ILO or H(L,L-1) is negligible so that the matrix splits. */ i__ = *ihi; L50: l = *ilo; if (i__ < *ilo) { goto L170; } /* Perform multiple-shift QR iterations on rows and columns ILO to I until a submatrix of order at most MAXB splits off at the bottom because a subdiagonal element has become negligible. */ i__1 = itn; for (its = 0; its <= i__1; ++its) { /* Look for a single small subdiagonal element. */ i__2 = l + 1; for (k = i__; k >= i__2; --k) { tst1 = (d__1 = h___ref (k - 1, k - 1), fabs (d__1)) + (d__2 = h___ref (k, k), fabs (d__2)); if (tst1 == 0.) { i__4 = i__ - l + 1; tst1 = NUMlapack_dlanhs ("1", &i__4, &h___ref (l, l), ldh, &work[1]); } /* Computing MAX */ d__2 = ulp * tst1; if ( (d__1 = h___ref (k, k - 1), fabs (d__1)) <= MAX (d__2, smlnum)) { goto L70; } /* L60: */ } L70: l = k; if (l > *ilo) { /* H(L,L-1) is negligible. */ h___ref (l, l - 1) = 0.; } /* Exit from loop if a submatrix of order <= MAXB has split off. */ if (l >= i__ - maxb + 1) { goto L160; } /* Now the active submatrix is in rows and columns L to I. If eigenvalues only are being computed, only the active submatrix need be transformed. */ if (!wantt) { i1 = l; i2 = i__; } if (its == 20 || its == 30) { /* Exceptional shifts. */ i__2 = i__; for (ii = i__ - ns + 1; ii <= i__2; ++ii) { wr[ii] = ( (d__1 = h___ref (ii, ii - 1), fabs (d__1)) + (d__2 = h___ref (ii, ii), fabs (d__2))) * 1.5; wi[ii] = 0.; /* L80: */ } } else { /* Use eigenvalues of trailing submatrix of order NS as shifts. */ NUMlapack_dlacpy ("Full", &ns, &ns, &h___ref (i__ - ns + 1, i__ - ns + 1), ldh, s, &c__15); NUMlapack_dlahqr (&c_false, &c_false, &ns, &c__1, &ns, s, &c__15, &wr[i__ - ns + 1], &wi[i__ - ns + 1], &c__1, &ns, &z__[z_offset], ldz, &ierr); if (ierr > 0) { /* If NUMlapack_dlahqr failed to compute all NS eigenvalues, use the unconverged diagonal elements as the remaining shifts. */ i__2 = ierr; for (ii = 1; ii <= i__2; ++ii) { wr[i__ - ns + ii] = s_ref (ii, ii); wi[i__ - ns + ii] = 0.; /* L90: */ } } } /* Form the first column of (G-w(1)) (G-w(2)) . . . (G-w(ns)) where G is the Hessenberg submatrix H(L:I,L:I) and w is the vector of shifts (stored in WR and WI). The result is stored in the local array V. */ v[0] = 1.; i__2 = ns + 1; for (ii = 2; ii <= i__2; ++ii) { v[ii - 1] = 0.; /* L100: */ } nv = 1; i__2 = i__; for (j = i__ - ns + 1; j <= i__2; ++j) { if (wi[j] >= 0.) { if (wi[j] == 0.) { /* real shift */ i__4 = nv + 1; NUMblas_dcopy (&i__4, v, &c__1, vv, &c__1); i__4 = nv + 1; d__1 = -wr[j]; NUMblas_dgemv ("No transpose", &i__4, &nv, &c_b10, &h___ref (l, l), ldh, vv, &c__1, &d__1, v, &c__1); ++nv; } else if (wi[j] > 0.) { /* complex conjugate pair of shifts */ i__4 = nv + 1; NUMblas_dcopy (&i__4, v, &c__1, vv, &c__1); i__4 = nv + 1; d__1 = wr[j] * -2.; NUMblas_dgemv ("No transpose", &i__4, &nv, &c_b10, &h___ref (l, l), ldh, v, &c__1, &d__1, vv, &c__1); i__4 = nv + 1; itemp = NUMblas_idamax (&i__4, vv, &c__1); /* Computing MAX */ d__2 = (d__1 = vv[itemp - 1], fabs (d__1)); temp = 1. / MAX (d__2, smlnum); i__4 = nv + 1; NUMblas_dscal (&i__4, &temp, vv, &c__1); absw = NUMlapack_dlapy2 (&wr[j], &wi[j]); temp = temp * absw * absw; i__4 = nv + 2; i__5 = nv + 1; NUMblas_dgemv ("No transpose", &i__4, &i__5, &c_b10, &h___ref (l, l), ldh, vv, &c__1, &temp, v, &c__1); nv += 2; } /* Scale V(1:NV) so that MAX (fabs (V(i))) = 1. If V is zero, reset it to the unit vector. */ itemp = NUMblas_idamax (&nv, v, &c__1); temp = (d__1 = v[itemp - 1], fabs (d__1)); if (temp == 0.) { v[0] = 1.; i__4 = nv; for (ii = 2; ii <= i__4; ++ii) { v[ii - 1] = 0.; /* L110: */ } } else { temp = MAX (temp, smlnum); d__1 = 1. / temp; NUMblas_dscal (&nv, &d__1, v, &c__1); } } /* L120: */ } /* Multiple-shift QR step */ i__2 = i__ - 1; for (k = l; k <= i__2; ++k) { /* The first iteration of this loop determines a reflection G from the vector V and applies it from left and right to H, thus creating a nonzero bulge below the subdiagonal. Each subsequent iteration determines a reflection G to restore the Hessenberg form in the (K-1)th column, and thus chases the bulge one step toward the bottom of the active submatrix. NR is the order of G. Computing MIN */ i__4 = ns + 1, i__5 = i__ - k + 1; nr = MIN (i__4, i__5); if (k > l) { NUMblas_dcopy (&nr, &h___ref (k, k - 1), &c__1, v, &c__1); } NUMlapack_dlarfg (&nr, v, &v[1], &c__1, &tau); if (k > l) { h___ref (k, k - 1) = v[0]; i__4 = i__; for (ii = k + 1; ii <= i__4; ++ii) { h___ref (ii, k - 1) = 0.; /* L130: */ } } v[0] = 1.; /* Apply G from the left to transform the rows of the matrix in columns K to I2. */ i__4 = i2 - k + 1; NUMlapack_dlarfx ("Left", &nr, &i__4, v, &tau, &h___ref (k, k), ldh, &work[1]); /* Apply G from the right to transform the columns of the matrix in rows I1 to MIN (K+NR,I). Computing MIN */ i__5 = k + nr; i__4 = MIN (i__5, i__) - i1 + 1; NUMlapack_dlarfx ("Right", &i__4, &nr, v, &tau, &h___ref (i1, k), ldh, &work[1]); if (wantz) { /* Accumulate transformations in the matrix Z */ NUMlapack_dlarfx ("Right", &nh, &nr, v, &tau, &z___ref (*ilo, k), ldz, &work[1]); } /* L140: */ } /* L150: */ } /* Failure to converge in remaining number of iterations */ *info = i__; return 0; L160: /* A submatrix of order <= MAXB in rows and columns L to I has split off. Use the double-shift QR algorithm to handle it. */ NUMlapack_dlahqr (&wantt, &wantz, n, &l, &i__, &h__[h_offset], ldh, &wr[1], &wi[1], ilo, ihi, &z__[z_offset], ldz, info); if (*info > 0) { return 0; } /* Decrement number of remaining iterations, and return to start of the main loop with a new value of I. */ itn -= its; i__ = l - 1; goto L50; L170: work[1] = (double) MAX (1, *n); return 0; } /* NUMlapack_dhseqr */ #undef z___ref #undef s_ref #undef h___ref int NUMlapack_dlabad (double *smal, double *large) { if (log10 (*large) > 2e3) { *smal = sqrt (*smal); *large = sqrt (*large); } return 0; } /* NUMlapack_dlabad */ #define x_ref(a_1,a_2) x[(a_2)*x_dim1 + a_1] #define y_ref(a_1,a_2) y[(a_2)*y_dim1 + a_1] int NUMlapack_dlabrd (long *m, long *n, long *nb, double *a, long *lda, double *d__, double *e, double *tauq, double *taup, double *x, long *ldx, double *y, long *ldy) { /* Table of constant values */ static double c_b4 = -1.; static double c_b5 = 1.; static long c__1 = 1; static double c_b16 = 0.; /* System generated locals */ long a_dim1, a_offset, x_dim1, x_offset, y_dim1, y_offset, i__1, i__2, i__3; /* Local variables */ static long i__; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --d__; --e; --tauq; --taup; x_dim1 = *ldx; x_offset = 1 + x_dim1 * 1; x -= x_offset; y_dim1 = *ldy; y_offset = 1 + y_dim1 * 1; y -= y_offset; /* Function Body */ if (*m <= 0 || *n <= 0) { return 0; } if (*m >= *n) { /* Reduce to upper bidiagonal form */ i__1 = *nb; for (i__ = 1; i__ <= i__1; ++i__) { /* Update A(i:m,i) */ i__2 = *m - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &a_ref (i__, 1), lda, &y_ref (i__, 1), ldy, &c_b5, &a_ref (i__, i__), &c__1); i__2 = *m - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &x_ref (i__, 1), ldx, &a_ref (1, i__), &c__1, &c_b5, &a_ref (i__, i__), &c__1); /* Generate reflection Q(i) to annihilate A(i+1:m,i) Computing MIN */ i__2 = i__ + 1; i__3 = *m - i__ + 1; NUMlapack_dlarfg (&i__3, &a_ref (i__, i__), &a_ref (MIN (i__2, *m), i__), &c__1, &tauq[i__]); d__[i__] = a_ref (i__, i__); if (i__ < *n) { a_ref (i__, i__) = 1.; /* Compute Y(i+1:n,i) */ i__2 = *m - i__ + 1; i__3 = *n - i__; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b5, &a_ref (i__, i__ + 1), lda, &a_ref (i__, i__), &c__1, &c_b16, &y_ref (i__ + 1, i__), &c__1); i__2 = *m - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b5, &a_ref (i__, 1), lda, &a_ref (i__, i__), &c__1, &c_b16, &y_ref (1, i__), &c__1); i__2 = *n - i__; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &y_ref (i__ + 1, 1), ldy, &y_ref (1, i__), &c__1, &c_b5, &y_ref (i__ + 1, i__), &c__1); i__2 = *m - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b5, &x_ref (i__, 1), ldx, &a_ref (i__, i__), &c__1, &c_b16, &y_ref (1, i__), &c__1); i__2 = i__ - 1; i__3 = *n - i__; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b4, &a_ref (1, i__ + 1), lda, &y_ref (1, i__), &c__1, &c_b5, &y_ref (i__ + 1, i__), &c__1); i__2 = *n - i__; NUMblas_dscal (&i__2, &tauq[i__], &y_ref (i__ + 1, i__), &c__1); /* Update A(i,i+1:n) */ i__2 = *n - i__; NUMblas_dgemv ("No transpose", &i__2, &i__, &c_b4, &y_ref (i__ + 1, 1), ldy, &a_ref (i__, 1), lda, &c_b5, &a_ref (i__, i__ + 1), lda); i__2 = i__ - 1; i__3 = *n - i__; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b4, &a_ref (1, i__ + 1), lda, &x_ref (i__, 1), ldx, &c_b5, &a_ref (i__, i__ + 1), lda); /* Generate reflection P(i) to annihilate A(i,i+2:n) Computing MIN */ i__2 = i__ + 2; i__3 = *n - i__; NUMlapack_dlarfg (&i__3, &a_ref (i__, i__ + 1), &a_ref (i__, MIN (i__2, *n)), lda, &taup[i__]); e[i__] = a_ref (i__, i__ + 1); a_ref (i__, i__ + 1) = 1.; /* Compute X(i+1:m,i) */ i__2 = *m - i__; i__3 = *n - i__; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &a_ref (i__ + 1, i__ + 1), lda, &a_ref (i__, i__ + 1), lda, &c_b16, &x_ref (i__ + 1, i__), &c__1); i__2 = *n - i__; NUMblas_dgemv ("Transpose", &i__2, &i__, &c_b5, &y_ref (i__ + 1, 1), ldy, &a_ref (i__, i__ + 1), lda, &c_b16, &x_ref (1, i__), &c__1); i__2 = *m - i__; NUMblas_dgemv ("No transpose", &i__2, &i__, &c_b4, &a_ref (i__ + 1, 1), lda, &x_ref (1, i__), &c__1, &c_b5, &x_ref (i__ + 1, i__), &c__1); i__2 = i__ - 1; i__3 = *n - i__; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &a_ref (1, i__ + 1), lda, &a_ref (i__, i__ + 1), lda, &c_b16, &x_ref (1, i__), &c__1); i__2 = *m - i__; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &x_ref (i__ + 1, 1), ldx, &x_ref (1, i__), &c__1, &c_b5, &x_ref (i__ + 1, i__), &c__1); i__2 = *m - i__; NUMblas_dscal (&i__2, &taup[i__], &x_ref (i__ + 1, i__), &c__1); } /* L10: */ } } else { /* Reduce to lower bidiagonal form */ i__1 = *nb; for (i__ = 1; i__ <= i__1; ++i__) { /* Update A(i,i:n) */ i__2 = *n - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &y_ref (i__, 1), ldy, &a_ref (i__, 1), lda, &c_b5, &a_ref (i__, i__), lda); i__2 = i__ - 1; i__3 = *n - i__ + 1; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b4, &a_ref (1, i__), lda, &x_ref (i__, 1), ldx, &c_b5, &a_ref (i__, i__), lda); /* Generate reflection P(i) to annihilate A(i,i+1:n) Computing MIN */ i__2 = i__ + 1; i__3 = *n - i__ + 1; NUMlapack_dlarfg (&i__3, &a_ref (i__, i__), &a_ref (i__, MIN (i__2, *n)), lda, &taup[i__]); d__[i__] = a_ref (i__, i__); if (i__ < *m) { a_ref (i__, i__) = 1.; /* Compute X(i+1:m,i) */ i__2 = *m - i__; i__3 = *n - i__ + 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &a_ref (i__ + 1, i__), lda, &a_ref (i__, i__), lda, &c_b16, &x_ref (i__ + 1, i__), &c__1); i__2 = *n - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b5, &y_ref (i__, 1), ldy, &a_ref (i__, i__), lda, &c_b16, &x_ref (1, i__), &c__1); i__2 = *m - i__; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &a_ref (i__ + 1, 1), lda, &x_ref (1, i__), &c__1, &c_b5, &x_ref (i__ + 1, i__), &c__1); i__2 = i__ - 1; i__3 = *n - i__ + 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &a_ref (1, i__), lda, &a_ref (i__, i__), lda, &c_b16, &x_ref (1, i__), &c__1); i__2 = *m - i__; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &x_ref (i__ + 1, 1), ldx, &x_ref (1, i__), &c__1, &c_b5, &x_ref (i__ + 1, i__), &c__1); i__2 = *m - i__; NUMblas_dscal (&i__2, &taup[i__], &x_ref (i__ + 1, i__), &c__1); /* Update A(i+1:m,i) */ i__2 = *m - i__; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &a_ref (i__ + 1, 1), lda, &y_ref (i__, 1), ldy, &c_b5, &a_ref (i__ + 1, i__), &c__1); i__2 = *m - i__; NUMblas_dgemv ("No transpose", &i__2, &i__, &c_b4, &x_ref (i__ + 1, 1), ldx, &a_ref (1, i__), &c__1, &c_b5, &a_ref (i__ + 1, i__), &c__1); /* Generate reflection Q(i) to annihilate A(i+2:m,i) Computing MIN */ i__2 = i__ + 2; i__3 = *m - i__; NUMlapack_dlarfg (&i__3, &a_ref (i__ + 1, i__), &a_ref (MIN (i__2, *m), i__), &c__1, &tauq[i__]); e[i__] = a_ref (i__ + 1, i__); a_ref (i__ + 1, i__) = 1.; /* Compute Y(i+1:n,i) */ i__2 = *m - i__; i__3 = *n - i__; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b5, &a_ref (i__ + 1, i__ + 1), lda, &a_ref (i__ + 1, i__), &c__1, &c_b16, &y_ref (i__ + 1, i__), &c__1); i__2 = *m - i__; i__3 = i__ - 1; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b5, &a_ref (i__ + 1, 1), lda, &a_ref (i__ + 1, i__), &c__1, &c_b16, &y_ref (1, i__), &c__1); i__2 = *n - i__; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &y_ref (i__ + 1, 1), ldy, &y_ref (1, i__), &c__1, &c_b5, &y_ref (i__ + 1, i__), &c__1); i__2 = *m - i__; NUMblas_dgemv ("Transpose", &i__2, &i__, &c_b5, &x_ref (i__ + 1, 1), ldx, &a_ref (i__ + 1, i__), &c__1, &c_b16, &y_ref (1, i__), &c__1); i__2 = *n - i__; NUMblas_dgemv ("Transpose", &i__, &i__2, &c_b4, &a_ref (1, i__ + 1), lda, &y_ref (1, i__), &c__1, &c_b5, &y_ref (i__ + 1, i__), &c__1); i__2 = *n - i__; NUMblas_dscal (&i__2, &tauq[i__], &y_ref (i__ + 1, i__), &c__1); } /* L20: */ } } return 0; } /* NUMlapack_dlabrd */ #undef y_ref #undef x_ref #define b_ref(a_1,a_2) b[(a_2)*b_dim1 + a_1] int NUMlapack_dlacpy (const char *uplo, long *m, long *n, double *a, long *lda, double *b, long *ldb) { /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, i__1, i__2; /* Local variables */ static long i__, j; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; /* Function Body */ if (lsame_ (uplo, "U")) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = MIN (j, *m); for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = a_ref (i__, j); /* L10: */ } /* L20: */ } } else if (lsame_ (uplo, "L")) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = j; i__ <= i__2; ++i__) { b_ref (i__, j) = a_ref (i__, j); /* L30: */ } /* L40: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { b_ref (i__, j) = a_ref (i__, j); /* L50: */ } /* L60: */ } } return 0; } /* NUMlapack_dlacpy */ #undef b_ref int NUMlapack_dladiv (double *a, double *b, double *c, double *d, double *p, double *q) { static double e, f; if (fabs (*d) < fabs (*c)) { e = *d / *c; f = *c + *d * e; *p = (*a + *b * e) / f; *q = (*b - *a * e) / f; } else { e = *c / *d; f = *d + *c * e; *p = (*b + *a * e) / f; *q = (- (*a) + *b * e) / f; } return 0; } /* NUMlapack_dladiv */ int NUMlapack_dlae2 (double *a, double *b, double *c__, double *rt1, double *rt2) { /* System generated locals */ double d__1; /* Local variables */ static double acmn, acmx, ab, df, tb, sm, rt, adf; sm = *a + *c__; df = *a - *c__; adf = fabs (df); tb = *b + *b; ab = fabs (tb); // djmw 20110721 changed abs(*a) to fabs(*a) if (fabs (*a) > fabs (*c__)) { acmx = *a; acmn = *c__; } else { acmx = *c__; acmn = *a; } if (adf > ab) { /* Computing 2nd power */ d__1 = ab / adf; rt = adf * sqrt (d__1 * d__1 + 1.); } else if (adf < ab) { /* Computing 2nd power */ d__1 = adf / ab; rt = ab * sqrt (d__1 * d__1 + 1.); } else { /* Includes case AB=ADF=0 */ rt = ab * sqrt (2.); } if (sm < 0.) { *rt1 = (sm - rt) * .5; /* Order of execution important. To get fully accurate smaller eigenvalue, next line needs to be executed in higher precision. */ *rt2 = acmx / *rt1 * acmn - *b / *rt1 * *b; } else if (sm > 0.) { *rt1 = (sm + rt) * .5; /* Order of execution important. To get fully accurate smaller eigenvalue, next line needs to be executed in higher precision. */ *rt2 = acmx / *rt1 * acmn - *b / *rt1 * *b; } else { /* Includes case RT1 = RT2 = 0 */ *rt1 = rt * .5; *rt2 = rt * -.5; } return 0; } /* NUMlapack_dlae2 */ int NUMlapack_dlaev2 (double *a, double *b, double *c__, double *rt1, double *rt2, double *cs1, double *sn1) { /* System generated locals */ double d__1; /* Local variables */ static double acmn, acmx, ab, df, cs, ct, tb, sm, tn, rt, adf, acs; static long sgn1, sgn2; sm = *a + *c__; df = *a - *c__; adf = fabs (df); tb = *b + *b; ab = fabs (tb); if (fabs (*a) > fabs (*c__)) { acmx = *a; acmn = *c__; } else { acmx = *c__; acmn = *a; } if (adf > ab) { /* Computing 2nd power */ d__1 = ab / adf; rt = adf * sqrt (d__1 * d__1 + 1.); } else if (adf < ab) { /* Computing 2nd power */ d__1 = adf / ab; rt = ab * sqrt (d__1 * d__1 + 1.); } else { /* Includes case AB=ADF=0 */ rt = ab * sqrt (2.); } if (sm < 0.) { *rt1 = (sm - rt) * .5; sgn1 = -1; /* Order of execution important. To get fully accurate smaller eigenvalue, next line needs to be executed in higher precision. */ *rt2 = acmx / *rt1 * acmn - *b / *rt1 * *b; } else if (sm > 0.) { *rt1 = (sm + rt) * .5; sgn1 = 1; /* Order of execution important. To get fully accurate smaller eigenvalue, next line needs to be executed in higher precision. */ *rt2 = acmx / *rt1 * acmn - *b / *rt1 * *b; } else { /* Includes case RT1 = RT2 = 0 */ *rt1 = rt * .5; *rt2 = rt * -.5; sgn1 = 1; } /* Compute the eigenvector */ if (df >= 0.) { cs = df + rt; sgn2 = 1; } else { cs = df - rt; sgn2 = -1; } acs = fabs (cs); if (acs > ab) { ct = -tb / cs; *sn1 = 1. / sqrt (ct * ct + 1.); *cs1 = ct * *sn1; } else { if (ab == 0.) { *cs1 = 1.; *sn1 = 0.; } else { tn = -cs / tb; *cs1 = 1. / sqrt (tn * tn + 1.); *sn1 = tn * *cs1; } } if (sgn1 == sgn2) { tn = *cs1; *cs1 = - (*sn1); *sn1 = tn; } return 0; } /* NUMlapack_dlaev2 */ int NUMlapack_dlags2 (long *upper, double *a1, double *a2, double *a3, double *b1, double *b2, double *b3, double *csu, double *snu, double *csv, double *snv, double *csq, double *snq) { /* System generated locals */ double d__1; /* Local variables */ static double aua11, aua12, aua21, aua22, avb11, avb12, avb21, avb22; double ua11r, ua22r, vb11r, vb22r, a, b, c__, d__, r__, s1, s2; static double ua11, ua12, ua21, ua22, vb11, vb12, vb21, vb22, csl, csr, snl, snr; if (*upper) { /* Input matrices A and B are upper triangular matrices Form matrix C = A*adj(B) = ( a b ) ( 0 d ) */ a = *a1 * *b3; d__ = *a3 * *b1; b = *a2 * *b1 - *a1 * *b2; /* The SVD of real 2-by-2 triangular C ( CSL -SNL )*( A B )*( CSR SNR ) = ( R 0 ) ( SNL CSL ) ( 0 D ) ( -SNR CSR ) ( 0 T ) */ NUMlapack_dlasv2 (&a, &b, &d__, &s1, &s2, &snr, &csr, &snl, &csl); if (fabs (csl) >= fabs (snl) || fabs (csr) >= fabs (snr)) { /* Compute the (1,1) and (1,2) elements of U'*A and V'*B, and (1,2) element of |U|'*|A| and |V|'*|B|. */ ua11r = csl * *a1; ua12 = csl * *a2 + snl * *a3; vb11r = csr * *b1; vb12 = csr * *b2 + snr * *b3; aua12 = fabs (csl) * fabs (*a2) + fabs (snl) * fabs (*a3); avb12 = fabs (csr) * fabs (*b2) + fabs (snr) * fabs (*b3); /* zero (1,2) elements of U'*A and V'*B */ if (fabs (ua11r) + fabs (ua12) != 0.) { if (aua12 / (fabs (ua11r) + fabs (ua12)) <= avb12 / (fabs (vb11r) + fabs (vb12))) { d__1 = -ua11r; NUMlapack_dlartg (&d__1, &ua12, csq, snq, &r__); } else { d__1 = -vb11r; NUMlapack_dlartg (&d__1, &vb12, csq, snq, &r__); } } else { d__1 = -vb11r; NUMlapack_dlartg (&d__1, &vb12, csq, snq, &r__); } *csu = csl; *snu = -snl; *csv = csr; *snv = -snr; } else { /* Compute the (2,1) and (2,2) elements of U'*A and V'*B, and (2,2) element of |U|'*|A| and |V|'*|B|. */ ua21 = -snl * *a1; ua22 = -snl * *a2 + csl * *a3; vb21 = -snr * *b1; vb22 = -snr * *b2 + csr * *b3; aua22 = fabs (snl) * fabs (*a2) + fabs (csl) * fabs (*a3); avb22 = fabs (snr) * fabs (*b2) + fabs (csr) * fabs (*b3); /* zero (2,2) elements of U'*A and V'*B, and then swap. */ if (fabs (ua21) + fabs (ua22) != 0.) { if (aua22 / (fabs (ua21) + fabs (ua22)) <= avb22 / (fabs (vb21) + fabs (vb22))) { d__1 = -ua21; NUMlapack_dlartg (&d__1, &ua22, csq, snq, &r__); } else { d__1 = -vb21; NUMlapack_dlartg (&d__1, &vb22, csq, snq, &r__); } } else { d__1 = -vb21; NUMlapack_dlartg (&d__1, &vb22, csq, snq, &r__); } *csu = snl; *snu = csl; *csv = snr; *snv = csr; } } else { /* Input matrices A and B are lower triangular matrices Form matrix C = A*adj(B) = ( a 0 ) ( c d ) */ a = *a1 * *b3; d__ = *a3 * *b1; c__ = *a2 * *b3 - *a3 * *b2; /* The SVD of real 2-by-2 triangular C ( CSL -SNL )*( A 0 )*( CSR SNR ) = ( R 0 ) ( SNL CSL ) ( C D ) ( -SNR CSR ) ( 0 T ) */ NUMlapack_dlasv2 (&a, &c__, &d__, &s1, &s2, &snr, &csr, &snl, &csl); if (fabs (csr) >= fabs (snr) || fabs (csl) >= fabs (snl)) { /* Compute the (2,1) and (2,2) elements of U'*A and V'*B, and (2,1) element of |U|'*|A| and |V|'*|B|. */ ua21 = -snr * *a1 + csr * *a2; ua22r = csr * *a3; vb21 = -snl * *b1 + csl * *b2; vb22r = csl * *b3; aua21 = fabs (snr) * fabs (*a1) + fabs (csr) * fabs (*a2); avb21 = fabs (snl) * fabs (*b1) + fabs (csl) * fabs (*b2); /* zero (2,1) elements of U'*A and V'*B. */ if (fabs (ua21) + fabs (ua22r) != 0.) { if (aua21 / (fabs (ua21) + fabs (ua22r)) <= avb21 / (fabs (vb21) + fabs (vb22r))) { NUMlapack_dlartg (&ua22r, &ua21, csq, snq, &r__); } else { NUMlapack_dlartg (&vb22r, &vb21, csq, snq, &r__); } } else { NUMlapack_dlartg (&vb22r, &vb21, csq, snq, &r__); } *csu = csr; *snu = -snr; *csv = csl; *snv = -snl; } else { /* Compute the (1,1) and (1,2) elements of U'*A and V'*B, and (1,1) element of |U|'*|A| and |V|'*|B|. */ ua11 = csr * *a1 + snr * *a2; ua12 = snr * *a3; vb11 = csl * *b1 + snl * *b2; vb12 = snl * *b3; aua11 = fabs (csr) * fabs (*a1) + fabs (snr) * fabs (*a2); avb11 = fabs (csl) * fabs (*b1) + fabs (snl) * fabs (*b2); /* zero (1,1) elements of U'*A and V'*B, and then swap. */ if (fabs (ua11) + fabs (ua12) != 0.) { if (aua11 / (fabs (ua11) + fabs (ua12)) <= avb11 / (fabs (vb11) + fabs (vb12))) { NUMlapack_dlartg (&ua12, &ua11, csq, snq, &r__); } else { NUMlapack_dlartg (&vb12, &vb11, csq, snq, &r__); } } else { NUMlapack_dlartg (&vb12, &vb11, csq, snq, &r__); } *csu = snr; *snu = csr; *csv = snl; *snv = csl; } } return 0; } /* NUMlapack_dlags2 */ int NUMlapack_dlahqr (int *wantt, int *wantz, long *n, long *ilo, long *ihi, double *h__, long *ldh, double *wr, double *wi, long *iloz, long *ihiz, double *z__, long *ldz, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long h_dim1, h_offset, z_dim1, z_offset, i__1, i__2, i__3, i__4; double d__1, d__2; /* Local variables */ static double h43h34, disc, unfl, ovfl; static double work[1]; static long i__, j, k, l, m; static double s, v[3]; static long i1, i2; static double t1, t2, t3, v1, v2, v3; static double h00, h10, h11, h12, h21, h22, h33, h44; static long nh; static double cs; static long nr; static double sn; static long nz; static double smlnum, ave, h33s, h44s; static long itn, its; static double ulp, sum, tst1; #define h___ref(a_1,a_2) h__[(a_2)*h_dim1 + a_1] #define z___ref(a_1,a_2) z__[(a_2)*z_dim1 + a_1] h_dim1 = *ldh; h_offset = 1 + h_dim1 * 1; h__ -= h_offset; --wr; --wi; z_dim1 = *ldz; z_offset = 1 + z_dim1 * 1; z__ -= z_offset; /* Function Body */ *info = 0; /* Quick return if possible */ if (*n == 0) { return 0; } if (*ilo == *ihi) { wr[*ilo] = h___ref (*ilo, *ilo); wi[*ilo] = 0.; return 0; } nh = *ihi - *ilo + 1; nz = *ihiz - *iloz + 1; /* Set machine-dependent constants for the stopping criterion. If norm(H) <= sqrt(OVFL), overflow should not occur. */ unfl = NUMblas_dlamch ("Safe minimum"); ovfl = 1. / unfl; NUMlapack_dlabad (&unfl, &ovfl); ulp = NUMblas_dlamch ("Precision"); smlnum = unfl * (nh / ulp); /* I1 and I2 are the indices of the first row and last column of H to which transformations must be applied. If eigenvalues only are being computed, I1 and I2 are set inside the main loop. */ if (*wantt) { i1 = 1; i2 = *n; } /* ITN is the total number of QR iterations allowed. */ itn = nh * 30; /* The main loop begins here. I is the loop index and decreases from IHI to ILO in steps of 1 or 2. Each iteration of the loop works with the active submatrix in rows and columns L to I. Eigenvalues I+1 to IHI have already converged. Either L = ILO or H(L,L-1) is negligible so that the matrix splits. */ i__ = *ihi; L10: l = *ilo; if (i__ < *ilo) { goto L150; } /* Perform QR iterations on rows and columns ILO to I until a submatrix of order 1 or 2 splits off at the bottom because a subdiagonal element has become negligible. */ i__1 = itn; for (its = 0; its <= i__1; ++its) { /* Look for a single small subdiagonal element. */ i__2 = l + 1; for (k = i__; k >= i__2; --k) { tst1 = (d__1 = h___ref (k - 1, k - 1), fabs (d__1)) + (d__2 = h___ref (k, k), fabs (d__2)); if (tst1 == 0.) { i__3 = i__ - l + 1; tst1 = NUMlapack_dlanhs ("1", &i__3, &h___ref (l, l), ldh, work); } /* Computing MAX */ d__2 = ulp * tst1; if ( (d__1 = h___ref (k, k - 1), fabs (d__1)) <= MAX (d__2, smlnum)) { goto L30; } /* L20: */ } L30: l = k; if (l > *ilo) { /* H(L,L-1) is negligible */ h___ref (l, l - 1) = 0.; } /* Exit from loop if a submatrix of order 1 or 2 has split off. */ if (l >= i__ - 1) { goto L140; } /* Now the active submatrix is in rows and columns L to I. If eigenvalues only are being computed, only the active submatrix need be transformed. */ if (! (*wantt)) { i1 = l; i2 = i__; } if (its == 10 || its == 20) { /* Exceptional shift. */ s = (d__1 = h___ref (i__, i__ - 1), fabs (d__1)) + (d__2 = h___ref (i__ - 1, i__ - 2), fabs (d__2)); h44 = s * .75 + h___ref (i__, i__); h33 = h44; h43h34 = s * -.4375 * s; } else { /* Prepare to use Francis' double shift (i.e. 2nd degree generalized Rayleigh quotient) */ h44 = h___ref (i__, i__); h33 = h___ref (i__ - 1, i__ - 1); h43h34 = h___ref (i__, i__ - 1) * h___ref (i__ - 1, i__); s = h___ref (i__ - 1, i__ - 2) * h___ref (i__ - 1, i__ - 2); disc = (h33 - h44) * .5; disc = disc * disc + h43h34; if (disc > 0.) { /* Real roots: use Wilkinson's shift twice */ disc = sqrt (disc); ave = (h33 + h44) * .5; if (fabs (h33) - fabs (h44) > 0.) { h33 = h33 * h44 - h43h34; h44 = h33 / (d_sign (&disc, &ave) + ave); } else { h44 = d_sign (&disc, &ave) + ave; } h33 = h44; h43h34 = 0.; } } /* Look for two consecutive small subdiagonal elements. */ i__2 = l; for (m = i__ - 2; m >= i__2; --m) { /* Determine the effect of starting the double-shift QR iteration at row M, and see if this would make H(M,M-1) negligible. */ h11 = h___ref (m, m); h22 = h___ref (m + 1, m + 1); h21 = h___ref (m + 1, m); h12 = h___ref (m, m + 1); h44s = h44 - h11; h33s = h33 - h11; v1 = (h33s * h44s - h43h34) / h21 + h12; v2 = h22 - h11 - h33s - h44s; v3 = h___ref (m + 2, m + 1); s = fabs (v1) + fabs (v2) + fabs (v3); v1 /= s; v2 /= s; v3 /= s; v[0] = v1; v[1] = v2; v[2] = v3; if (m == l) { goto L50; } h00 = h___ref (m - 1, m - 1); h10 = h___ref (m, m - 1); tst1 = fabs (v1) * (fabs (h00) + fabs (h11) + fabs (h22)); if (fabs (h10) * (fabs (v2) + fabs (v3)) <= ulp * tst1) { goto L50; } /* L40: */ } L50: /* Double-shift QR step */ i__2 = i__ - 1; for (k = m; k <= i__2; ++k) { /* The first iteration of this loop determines a reflection G from the vector V and applies it from left and right to H, thus creating a nonzero bulge below the subdiagonal. Each subsequent iteration determines a reflection G to restore the Hessenberg form in the (K-1)th column, and thus chases the bulge one step toward the bottom of the active submatrix. NR is the order of G. Computing MIN */ i__3 = 3, i__4 = i__ - k + 1; nr = MIN (i__3, i__4); if (k > m) { NUMblas_dcopy (&nr, &h___ref (k, k - 1), &c__1, v, &c__1); } NUMlapack_dlarfg (&nr, v, &v[1], &c__1, &t1); if (k > m) { h___ref (k, k - 1) = v[0]; h___ref (k + 1, k - 1) = 0.; if (k < i__ - 1) { h___ref (k + 2, k - 1) = 0.; } } else if (m > l) { h___ref (k, k - 1) = -h___ref (k, k - 1); } v2 = v[1]; t2 = t1 * v2; if (nr == 3) { v3 = v[2]; t3 = t1 * v3; /* Apply G from the left to transform the rows of the matrix in columns K to I2. */ i__3 = i2; for (j = k; j <= i__3; ++j) { sum = h___ref (k, j) + v2 * h___ref (k + 1, j) + v3 * h___ref (k + 2, j); h___ref (k, j) = h___ref (k, j) - sum * t1; h___ref (k + 1, j) = h___ref (k + 1, j) - sum * t2; h___ref (k + 2, j) = h___ref (k + 2, j) - sum * t3; /* L60: */ } /* Apply G from the right to transform the columns of the matrix in rows I1 to MIN (K+3,I). Computing MIN */ i__4 = k + 3; i__3 = MIN (i__4, i__); for (j = i1; j <= i__3; ++j) { sum = h___ref (j, k) + v2 * h___ref (j, k + 1) + v3 * h___ref (j, k + 2); h___ref (j, k) = h___ref (j, k) - sum * t1; h___ref (j, k + 1) = h___ref (j, k + 1) - sum * t2; h___ref (j, k + 2) = h___ref (j, k + 2) - sum * t3; /* L70: */ } if (*wantz) { /* Accumulate transformations in the matrix Z */ i__3 = *ihiz; for (j = *iloz; j <= i__3; ++j) { sum = z___ref (j, k) + v2 * z___ref (j, k + 1) + v3 * z___ref (j, k + 2); z___ref (j, k) = z___ref (j, k) - sum * t1; z___ref (j, k + 1) = z___ref (j, k + 1) - sum * t2; z___ref (j, k + 2) = z___ref (j, k + 2) - sum * t3; /* L80: */ } } } else if (nr == 2) { /* Apply G from the left to transform the rows of the matrix in columns K to I2. */ i__3 = i2; for (j = k; j <= i__3; ++j) { sum = h___ref (k, j) + v2 * h___ref (k + 1, j); h___ref (k, j) = h___ref (k, j) - sum * t1; h___ref (k + 1, j) = h___ref (k + 1, j) - sum * t2; /* L90: */ } /* Apply G from the right to transform the columns of the matrix in rows I1 to MIN (K+3,I). */ i__3 = i__; for (j = i1; j <= i__3; ++j) { sum = h___ref (j, k) + v2 * h___ref (j, k + 1); h___ref (j, k) = h___ref (j, k) - sum * t1; h___ref (j, k + 1) = h___ref (j, k + 1) - sum * t2; /* L100: */ } if (*wantz) { /* Accumulate transformations in the matrix Z */ i__3 = *ihiz; for (j = *iloz; j <= i__3; ++j) { sum = z___ref (j, k) + v2 * z___ref (j, k + 1); z___ref (j, k) = z___ref (j, k) - sum * t1; z___ref (j, k + 1) = z___ref (j, k + 1) - sum * t2; /* L110: */ } } } /* L120: */ } /* L130: */ } /* Failure to converge in remaining number of iterations */ *info = i__; return 0; L140: if (l == i__) { /* H(I,I-1) is negligible: one eigenvalue has converged. */ wr[i__] = h___ref (i__, i__); wi[i__] = 0.; } else if (l == i__ - 1) { /* H(I-1,I-2) is negligible: a pair of eigenvalues have converged. Transform the 2-by-2 submatrix to standard Schur form, and compute and store the eigenvalues. */ NUMlapack_dlanv2 (&h___ref (i__ - 1, i__ - 1), &h___ref (i__ - 1, i__), &h___ref (i__, i__ - 1), &h___ref (i__, i__), &wr[i__ - 1], &wi[i__ - 1], &wr[i__], &wi[i__], &cs, &sn); if (*wantt) { /* Apply the transformation to the rest of H. */ if (i2 > i__) { i__1 = i2 - i__; NUMblas_drot (&i__1, &h___ref (i__ - 1, i__ + 1), ldh, &h___ref (i__, i__ + 1), ldh, &cs, &sn); } i__1 = i__ - i1 - 1; NUMblas_drot (&i__1, &h___ref (i1, i__ - 1), &c__1, &h___ref (i1, i__), &c__1, &cs, &sn); } if (*wantz) { /* Apply the transformation to Z. */ NUMblas_drot (&nz, &z___ref (*iloz, i__ - 1), &c__1, &z___ref (*iloz, i__), &c__1, &cs, &sn); } } /* Decrement number of remaining iterations, and return to start of the main loop with new value of I. */ itn -= its; i__ = l - 1; goto L10; L150: return 0; } /* NUMlapack_dlahqr */ #undef z___ref #undef h___ref int NUMlapack_dlahrd (long *n, long *k, long *nb, double *a, long *lda, double *tau, double *t, long *ldt, double *y, long *ldy) { /* Table of constant values */ static double c_b4 = -1.; static double c_b5 = 1.; static long c__1 = 1; static double c_b38 = 0.; /* System generated locals */ long a_dim1, a_offset, t_dim1, t_offset, y_dim1, y_offset, i__1, i__2, i__3; double d__1; /* Local variables */ static long i__; static double ei; #define t_ref(a_1,a_2) t[(a_2)*t_dim1 + a_1] #define y_ref(a_1,a_2) y[(a_2)*y_dim1 + a_1] --tau; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; t_dim1 = *ldt; t_offset = 1 + t_dim1 * 1; t -= t_offset; y_dim1 = *ldy; y_offset = 1 + y_dim1 * 1; y -= y_offset; /* Function Body */ if (*n <= 1) { return 0; } i__1 = *nb; for (i__ = 1; i__ <= i__1; ++i__) { if (i__ > 1) { /* Update A(1:n,i) Compute i-th column of A - Y * V' */ i__2 = i__ - 1; NUMblas_dgemv ("No transpose", n, &i__2, &c_b4, &y[y_offset], ldy, &a_ref (*k + i__ - 1, 1), lda, &c_b5, &a_ref (1, i__), &c__1); /* Apply I - V * T' * V' to this column (call it b) from the left, using the last column of T as workspace Let V = ( V1 ) and b = ( b1 ) (first I-1 rows) ( V2 ) ( b2 ) where V1 is unit lower triangular w := V1' * b1 */ i__2 = i__ - 1; NUMblas_dcopy (&i__2, &a_ref (*k + 1, i__), &c__1, &t_ref (1, *nb), &c__1); i__2 = i__ - 1; NUMblas_dtrmv ("Lower", "Transpose", "Unit", &i__2, &a_ref (*k + 1, 1), lda, &t_ref (1, *nb), &c__1); /* w := w + V2'*b2 */ i__2 = *n - *k - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b5, &a_ref (*k + i__, 1), lda, &a_ref (*k + i__, i__), &c__1, &c_b5, &t_ref (1, *nb), &c__1); /* w := T'*w */ i__2 = i__ - 1; NUMblas_dtrmv ("Upper", "Transpose", "Non-unit", &i__2, &t[t_offset], ldt, &t_ref (1, *nb), &c__1); /* b2 := b2 - V2*w */ i__2 = *n - *k - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b4, &a_ref (*k + i__, 1), lda, &t_ref (1, *nb), &c__1, &c_b5, &a_ref (*k + i__, i__), &c__1); /* b1 := b1 - V1*w */ i__2 = i__ - 1; NUMblas_dtrmv ("Lower", "No transpose", "Unit", &i__2, &a_ref (*k + 1, 1), lda, &t_ref (1, *nb), &c__1); i__2 = i__ - 1; NUMblas_daxpy (&i__2, &c_b4, &t_ref (1, *nb), &c__1, &a_ref (*k + 1, i__), &c__1); a_ref (*k + i__ - 1, i__ - 1) = ei; } /* Generate the elementary reflector H(i) to annihilate A(k+i+1:n,i) Computing MIN */ i__2 = *k + i__ + 1; i__3 = *n - *k - i__ + 1; NUMlapack_dlarfg (&i__3, &a_ref (*k + i__, i__), &a_ref (MIN (i__2, *n), i__), &c__1, &tau[i__]); ei = a_ref (*k + i__, i__); a_ref (*k + i__, i__) = 1.; /* Compute Y(1:n,i) */ i__2 = *n - *k - i__ + 1; NUMblas_dgemv ("No transpose", n, &i__2, &c_b5, &a_ref (1, i__ + 1), lda, &a_ref (*k + i__, i__), &c__1, &c_b38, &y_ref (1, i__), &c__1); i__2 = *n - *k - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b5, &a_ref (*k + i__, 1), lda, &a_ref (*k + i__, i__), &c__1, &c_b38, &t_ref (1, i__), &c__1); i__2 = i__ - 1; NUMblas_dgemv ("No transpose", n, &i__2, &c_b4, &y[y_offset], ldy, &t_ref (1, i__), &c__1, &c_b5, &y_ref (1, i__), &c__1); NUMblas_dscal (n, &tau[i__], &y_ref (1, i__), &c__1); /* Compute T(1:i,i) */ i__2 = i__ - 1; d__1 = -tau[i__]; NUMblas_dscal (&i__2, &d__1, &t_ref (1, i__), &c__1); i__2 = i__ - 1; NUMblas_dtrmv ("Upper", "No transpose", "Non-unit", &i__2, &t[t_offset], ldt, &t_ref (1, i__), &c__1); t_ref (i__, i__) = tau[i__]; /* L10: */ } a_ref (*k + *nb, *nb) = ei; return 0; } /* NUMlapack_dlahrd */ #undef y_ref #undef t_ref int NUMlapack_dlaln2 (int *ltrans, long *na, long *nw, double *smin, double *ca, double *a, long *lda, double *d1, double *d2, double *b, long *ldb, double *wr, double *wi, double *x, long *ldx, double *scale, double *xnorm, long *info) { /* Initialized data */ static int zswap[4] = { FALSE, FALSE, TRUE, TRUE }; static int rswap[4] = { FALSE, TRUE, FALSE, TRUE }; static long ipivot[16] /* was [4][4] */ = { 1, 2, 3, 4, 2, 1, 4, 3, 3, 4, 1, 2, 4, 3, 2, 1 }; /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, x_dim1, x_offset; double d__1, d__2, d__3, d__4, d__5, d__6; static double equiv_0[4], equiv_1[4]; /* Local variables */ static double bbnd, cmax, ui11r, ui12s, temp, ur11r, ur12s; static long j; static double u22abs; static long icmax; static double bnorm, cnorm, smini; #define ci (equiv_0) #define cr (equiv_1) static double bignum, bi1, bi2, br1, br2, smlnum, xi1, xi2, xr1, xr2, ci21, ci22, cr21, cr22, li21, csi, ui11, lr21, ui12, ui22; #define civ (equiv_0) static double csr, ur11, ur12, ur22; #define crv (equiv_1) #define b_ref(a_1,a_2) b[(a_2)*b_dim1 + a_1] #define x_ref(a_1,a_2) x[(a_2)*x_dim1 + a_1] #define ci_ref(a_1,a_2) ci[(a_2)*2 + a_1 - 3] #define cr_ref(a_1,a_2) cr[(a_2)*2 + a_1 - 3] #define ipivot_ref(a_1,a_2) ipivot[(a_2)*4 + a_1 - 5] a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; x_dim1 = *ldx; x_offset = 1 + x_dim1 * 1; x -= x_offset; /* Function Body Compute BIGNUM */ smlnum = 2. * NUMblas_dlamch ("Safe minimum"); bignum = 1. / smlnum; smini = MAX (*smin, smlnum); /* Don't check for input errors */ *info = 0; /* Standard Initializations */ *scale = 1.; if (*na == 1) { /* 1 x 1 (i.e., scalar) system C X = B */ if (*nw == 1) { /* Real 1x1 system. C = ca A - w D */ csr = *ca * a_ref (1, 1) - *wr * *d1; cnorm = fabs (csr); /* If | C | < SMINI, use C = SMINI */ if (cnorm < smini) { csr = smini; cnorm = smini; *info = 1; } /* Check scaling for X = B / C */ bnorm = (d__1 = b_ref (1, 1), fabs (d__1)); if (cnorm < 1. && bnorm > 1.) { if (bnorm > bignum * cnorm) { *scale = 1. / bnorm; } } /* Compute X */ x_ref (1, 1) = b_ref (1, 1) * *scale / csr; *xnorm = (d__1 = x_ref (1, 1), fabs (d__1)); } else { /* Complex 1x1 system (w is complex) C = ca A - w D */ csr = *ca * a_ref (1, 1) - *wr * *d1; csi = - (*wi) * *d1; cnorm = fabs (csr) + fabs (csi); /* If | C | < SMINI, use C = SMINI */ if (cnorm < smini) { csr = smini; csi = 0.; cnorm = smini; *info = 1; } /* Check scaling for X = B / C */ bnorm = (d__1 = b_ref (1, 1), fabs (d__1)) + (d__2 = b_ref (1, 2), fabs (d__2)); if (cnorm < 1. && bnorm > 1.) { if (bnorm > bignum * cnorm) { *scale = 1. / bnorm; } } /* Compute X */ d__1 = *scale * b_ref (1, 1); d__2 = *scale * b_ref (1, 2); NUMlapack_dladiv (&d__1, &d__2, &csr, &csi, &x_ref (1, 1), &x_ref (1, 2)); *xnorm = (d__1 = x_ref (1, 1), fabs (d__1)) + (d__2 = x_ref (1, 2), fabs (d__2)); } } else { /* 2x2 System Compute the real part of C = ca A - w D (or ca A' - w D ) */ cr_ref (1, 1) = *ca * a_ref (1, 1) - *wr * *d1; cr_ref (2, 2) = *ca * a_ref (2, 2) - *wr * *d2; if (*ltrans) { cr_ref (1, 2) = *ca * a_ref (2, 1); cr_ref (2, 1) = *ca * a_ref (1, 2); } else { cr_ref (2, 1) = *ca * a_ref (2, 1); cr_ref (1, 2) = *ca * a_ref (1, 2); } if (*nw == 1) { /* Real 2x2 system (w is real) Find the largest element in C */ cmax = 0.; icmax = 0; for (j = 1; j <= 4; ++j) { if ( (d__1 = crv[j - 1], fabs (d__1)) > cmax) { cmax = (d__1 = crv[j - 1], fabs (d__1)); icmax = j; } /* L10: */ } /* If norm(C) < SMINI, use SMINI*identity. */ if (cmax < smini) { /* Computing MAX */ d__3 = (d__1 = b_ref (1, 1), fabs (d__1)), d__4 = (d__2 = b_ref (2, 1), fabs (d__2)); bnorm = MAX (d__3, d__4); if (smini < 1. && bnorm > 1.) { if (bnorm > bignum * smini) { *scale = 1. / bnorm; } } temp = *scale / smini; x_ref (1, 1) = temp * b_ref (1, 1); x_ref (2, 1) = temp * b_ref (2, 1); *xnorm = temp * bnorm; *info = 1; return 0; } /* Gaussian elimination with complete pivoting. */ ur11 = crv[icmax - 1]; cr21 = crv[ipivot_ref (2, icmax) - 1]; ur12 = crv[ipivot_ref (3, icmax) - 1]; cr22 = crv[ipivot_ref (4, icmax) - 1]; ur11r = 1. / ur11; lr21 = ur11r * cr21; ur22 = cr22 - ur12 * lr21; /* If smaller pivot < SMINI, use SMINI */ if (fabs (ur22) < smini) { ur22 = smini; *info = 1; } if (rswap[icmax - 1]) { br1 = b_ref (2, 1); br2 = b_ref (1, 1); } else { br1 = b_ref (1, 1); br2 = b_ref (2, 1); } br2 -= lr21 * br1; /* Computing MAX */ d__2 = (d__1 = br1 * (ur22 * ur11r), fabs (d__1)), d__3 = fabs (br2); bbnd = MAX (d__2, d__3); if (bbnd > 1. && fabs (ur22) < 1.) { if (bbnd >= bignum * fabs (ur22)) { *scale = 1. / bbnd; } } xr2 = br2 * *scale / ur22; xr1 = *scale * br1 * ur11r - xr2 * (ur11r * ur12); if (zswap[icmax - 1]) { x_ref (1, 1) = xr2; x_ref (2, 1) = xr1; } else { x_ref (1, 1) = xr1; x_ref (2, 1) = xr2; } /* Computing MAX */ d__1 = fabs (xr1), d__2 = fabs (xr2); *xnorm = MAX (d__1, d__2); /* Further scaling if norm(A) norm(X) > overflow */ if (*xnorm > 1. && cmax > 1.) { if (*xnorm > bignum / cmax) { temp = cmax / bignum; x_ref (1, 1) = temp * x_ref (1, 1); x_ref (2, 1) = temp * x_ref (2, 1); *xnorm = temp * *xnorm; *scale = temp * *scale; } } } else { /* Complex 2x2 system (w is complex) Find the largest element in C */ ci_ref (1, 1) = - (*wi) * *d1; ci_ref (2, 1) = 0.; ci_ref (1, 2) = 0.; ci_ref (2, 2) = - (*wi) * *d2; cmax = 0.; icmax = 0; for (j = 1; j <= 4; ++j) { if ( (d__1 = crv[j - 1], fabs (d__1)) + (d__2 = civ[j - 1], fabs (d__2)) > cmax) { cmax = (d__1 = crv[j - 1], fabs (d__1)) + (d__2 = civ[j - 1], fabs (d__2)); icmax = j; } /* L20: */ } /* If norm(C) < SMINI, use SMINI*identity. */ if (cmax < smini) { /* Computing MAX */ d__5 = (d__1 = b_ref (1, 1), fabs (d__1)) + (d__2 = b_ref (1, 2), fabs (d__2)), d__6 = (d__3 = b_ref (2, 1), fabs (d__3)) + (d__4 = b_ref (2, 2), fabs (d__4)); bnorm = MAX (d__5, d__6); if (smini < 1. && bnorm > 1.) { if (bnorm > bignum * smini) { *scale = 1. / bnorm; } } temp = *scale / smini; x_ref (1, 1) = temp * b_ref (1, 1); x_ref (2, 1) = temp * b_ref (2, 1); x_ref (1, 2) = temp * b_ref (1, 2); x_ref (2, 2) = temp * b_ref (2, 2); *xnorm = temp * bnorm; *info = 1; return 0; } /* Gaussian elimination with complete pivoting. */ ur11 = crv[icmax - 1]; ui11 = civ[icmax - 1]; cr21 = crv[ipivot_ref (2, icmax) - 1]; ci21 = civ[ipivot_ref (2, icmax) - 1]; ur12 = crv[ipivot_ref (3, icmax) - 1]; ui12 = civ[ipivot_ref (3, icmax) - 1]; cr22 = crv[ipivot_ref (4, icmax) - 1]; ci22 = civ[ipivot_ref (4, icmax) - 1]; if (icmax == 1 || icmax == 4) { /* Code when off-diagonals of pivoted C are real */ if (fabs (ur11) > fabs (ui11)) { temp = ui11 / ur11; /* Computing 2nd power */ d__1 = temp; ur11r = 1. / (ur11 * (d__1 * d__1 + 1.)); ui11r = -temp * ur11r; } else { temp = ur11 / ui11; /* Computing 2nd power */ d__1 = temp; ui11r = -1. / (ui11 * (d__1 * d__1 + 1.)); ur11r = -temp * ui11r; } lr21 = cr21 * ur11r; li21 = cr21 * ui11r; ur12s = ur12 * ur11r; ui12s = ur12 * ui11r; ur22 = cr22 - ur12 * lr21; ui22 = ci22 - ur12 * li21; } else { /* Code when diagonals of pivoted C are real */ ur11r = 1. / ur11; ui11r = 0.; lr21 = cr21 * ur11r; li21 = ci21 * ur11r; ur12s = ur12 * ur11r; ui12s = ui12 * ur11r; ur22 = cr22 - ur12 * lr21 + ui12 * li21; ui22 = -ur12 * li21 - ui12 * lr21; } u22abs = fabs (ur22) + fabs (ui22); /* If smaller pivot < SMINI, use SMINI */ if (u22abs < smini) { ur22 = smini; ui22 = 0.; *info = 1; } if (rswap[icmax - 1]) { br2 = b_ref (1, 1); br1 = b_ref (2, 1); bi2 = b_ref (1, 2); bi1 = b_ref (2, 2); } else { br1 = b_ref (1, 1); br2 = b_ref (2, 1); bi1 = b_ref (1, 2); bi2 = b_ref (2, 2); } br2 = br2 - lr21 * br1 + li21 * bi1; bi2 = bi2 - li21 * br1 - lr21 * bi1; /* Computing MAX */ // djmw 20110721 changed abs(br2) to fabs(br2) d__1 = (fabs (br1) + fabs (bi1)) * (u22abs * (fabs (ur11r) + fabs (ui11r))), d__2 = fabs (br2) + fabs (bi2); bbnd = MAX (d__1, d__2); if (bbnd > 1. && u22abs < 1.) { if (bbnd >= bignum * u22abs) { *scale = 1. / bbnd; br1 = *scale * br1; bi1 = *scale * bi1; br2 = *scale * br2; bi2 = *scale * bi2; } } NUMlapack_dladiv (&br2, &bi2, &ur22, &ui22, &xr2, &xi2); xr1 = ur11r * br1 - ui11r * bi1 - ur12s * xr2 + ui12s * xi2; xi1 = ui11r * br1 + ur11r * bi1 - ui12s * xr2 - ur12s * xi2; if (zswap[icmax - 1]) { x_ref (1, 1) = xr2; x_ref (2, 1) = xr1; x_ref (1, 2) = xi2; x_ref (2, 2) = xi1; } else { x_ref (1, 1) = xr1; x_ref (2, 1) = xr2; x_ref (1, 2) = xi1; x_ref (2, 2) = xi2; } /* Computing MAX */ d__1 = fabs (xr1) + fabs (xi1), d__2 = fabs (xr2) + fabs (xi2); *xnorm = MAX (d__1, d__2); /* Further scaling if norm(A) norm(X) > overflow */ if (*xnorm > 1. && cmax > 1.) { if (*xnorm > bignum / cmax) { temp = cmax / bignum; x_ref (1, 1) = temp * x_ref (1, 1); x_ref (2, 1) = temp * x_ref (2, 1); x_ref (1, 2) = temp * x_ref (1, 2); x_ref (2, 2) = temp * x_ref (2, 2); *xnorm = temp * *xnorm; *scale = temp * *scale; } } } } return 0; } /* NUMlapack_NUMlapack_dlaln2 */ #undef ipivot_ref #undef cr_ref #undef ci_ref #undef x_ref #undef b_ref #undef crv #undef civ #undef cr #undef ci double NUMlapack_dlange (const char *norm, long *m, long *n, double *a, long *lda, double *work) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2; double ret_val, d__1, d__2, d__3; /* Local variables */ static long i__, j; static double scale; static double value; static double sum; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --work; /* Function Body */ if (MIN (*m, *n) == 0) { value = 0.; } else if (lsame_ (norm, "M")) { /* Find MAX(abs(A(i,j))). */ value = 0.; i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { /* Computing MAX */ d__2 = value, d__3 = (d__1 = a_ref (i__, j), fabs (d__1)); value = MAX (d__2, d__3); /* L10: */ } /* L20: */ } } else if (lsame_ (norm, "O") || * (unsigned char *) norm == '1') { /* Find norm1(A). */ value = 0.; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = 0.; i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { sum += (d__1 = a_ref (i__, j), fabs (d__1)); /* L30: */ } value = MAX (value, sum); /* L40: */ } } else if (lsame_ (norm, "I")) { /* Find normI(A). */ i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { work[i__] = 0.; /* L50: */ } i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { work[i__] += (d__1 = a_ref (i__, j), fabs (d__1)); /* L60: */ } /* L70: */ } value = 0.; i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { /* Computing MAX */ d__1 = value, d__2 = work[i__]; value = MAX (d__1, d__2); /* L80: */ } } else if (lsame_ (norm, "F") || lsame_ (norm, "E")) { /* Find normF(A). */ scale = 0.; sum = 1.; i__1 = *n; for (j = 1; j <= i__1; ++j) { NUMlapack_dlassq (m, &a_ref (1, j), &c__1, &scale, &sum); /* L90: */ } value = scale * sqrt (sum); } ret_val = value; return ret_val; } /* NUMlapack_dlange */ double NUMlapack_dlanhs (const char *norm, long *n, double *a, long *lda, double *work) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4; double ret_val, d__1, d__2, d__3; /* Local variables */ static long i__, j; static double scale; static double value; static double sum; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --work; /* Function Body */ if (*n == 0) { value = 0.; } else if (lsame_ (norm, "M")) { /* Find MAX (fabs (A(i,j))). */ value = 0.; i__1 = *n; for (j = 1; j <= i__1; ++j) { /* Computing MIN */ i__3 = *n, i__4 = j + 1; i__2 = MIN (i__3, i__4); for (i__ = 1; i__ <= i__2; ++i__) { /* Computing MAX */ d__2 = value, d__3 = (d__1 = a_ref (i__, j), fabs (d__1)); value = MAX (d__2, d__3); /* L10: */ } /* L20: */ } } else if (lsame_ (norm, "O") || * (unsigned char *) norm == '1') { /* Find norm1(A). */ value = 0.; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = 0.; /* Computing MIN */ i__3 = *n, i__4 = j + 1; i__2 = MIN (i__3, i__4); for (i__ = 1; i__ <= i__2; ++i__) { sum += (d__1 = a_ref (i__, j), fabs (d__1)); /* L30: */ } value = MAX (value, sum); /* L40: */ } } else if (lsame_ (norm, "I")) { /* Find normI(A). */ i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { work[i__] = 0.; /* L50: */ } i__1 = *n; for (j = 1; j <= i__1; ++j) { /* Computing MIN */ i__3 = *n, i__4 = j + 1; i__2 = MIN (i__3, i__4); for (i__ = 1; i__ <= i__2; ++i__) { work[i__] += (d__1 = a_ref (i__, j), fabs (d__1)); /* L60: */ } /* L70: */ } value = 0.; i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { /* Computing MAX */ d__1 = value, d__2 = work[i__]; value = MAX (d__1, d__2); /* L80: */ } } else if (lsame_ (norm, "F") || lsame_ (norm, "E")) { /* Find normF(A). */ scale = 0.; sum = 1.; i__1 = *n; for (j = 1; j <= i__1; ++j) { /* Computing MIN */ i__3 = *n, i__4 = j + 1; i__2 = MIN (i__3, i__4); NUMlapack_dlassq (&i__2, &a_ref (1, j), &c__1, &scale, &sum); /* L90: */ } value = scale * sqrt (sum); } ret_val = value; return ret_val; } /* NUMlapack_dlanhs */ double NUMlapack_dlanst (const char *norm, long *n, double *d__, double *e) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long i__1; double ret_val, d__1, d__2, d__3, d__4, d__5; static long i__; static double scale; static double anorm; static double sum; --e; --d__; /* Function Body */ if (*n <= 0) { anorm = 0.; } else if (lsame_ (norm, "M")) { /* Find max(abs(A(i,j))). */ anorm = (d__1 = d__[*n], fabs (d__1)); i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { /* Computing MAX */ d__2 = anorm, d__3 = (d__1 = d__[i__], fabs (d__1)); anorm = MAX (d__2, d__3); /* Computing MAX */ d__2 = anorm, d__3 = (d__1 = e[i__], fabs (d__1)); anorm = MAX (d__2, d__3); /* L10: */ } } else if (lsame_ (norm, "O") || * (unsigned char *) norm == '1' || lsame_ (norm, "I")) { /* Find norm1(A). */ if (*n == 1) { anorm = fabs (d__[1]); } else { /* Computing MAX */ d__3 = fabs (d__[1]) + fabs (e[1]), d__4 = (d__1 = e[*n - 1], fabs (d__1)) + (d__2 = d__[*n], fabs (d__2)); anorm = MAX (d__3, d__4); i__1 = *n - 1; for (i__ = 2; i__ <= i__1; ++i__) { /* Computing MAX */ d__4 = anorm, d__5 = (d__1 = d__[i__], fabs (d__1)) + (d__2 = e[i__], fabs (d__2)) + (d__3 = e[i__ - 1], fabs (d__3)); anorm = MAX (d__4, d__5); /* L20: */ } } } else if (lsame_ (norm, "F") || lsame_ (norm, "E")) { /* Find normF(A). */ scale = 0.; sum = 1.; if (*n > 1) { i__1 = *n - 1; NUMlapack_dlassq (&i__1, &e[1], &c__1, &scale, &sum); sum *= 2; } NUMlapack_dlassq (n, &d__[1], &c__1, &scale, &sum); anorm = scale * sqrt (sum); } ret_val = anorm; return ret_val; } /* NUMlapack_dlanst */ double NUMlapack_dlansy (const char *norm, const char *uplo, long *n, double *a, long *lda, double *work) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2; double ret_val, d__1, d__2, d__3; /* Local variables */ static double absa; static long i__, j; static double scale; static double value; static double sum; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --work; /* Function Body */ if (*n == 0) { value = 0.; } else if (lsame_ (norm, "M")) { /* Find max(abs(A(i,j))). */ value = 0.; if (lsame_ (uplo, "U")) { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = j; for (i__ = 1; i__ <= i__2; ++i__) { /* Computing MAX */ d__2 = value, d__3 = (d__1 = a_ref (i__, j), fabs (d__1)); value = MAX (d__2, d__3); /* L10: */ } /* L20: */ } } else { i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *n; for (i__ = j; i__ <= i__2; ++i__) { /* Computing MAX */ d__2 = value, d__3 = (d__1 = a_ref (i__, j), fabs (d__1)); value = MAX (d__2, d__3); /* L30: */ } /* L40: */ } } } else if (lsame_ (norm, "I") || lsame_ (norm, "O") || * (unsigned char *) norm == '1') { /* Find normI(A) ( = norm1(A), since A is symmetric). */ value = 0.; if (lsame_ (uplo, "U")) { i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = 0.; i__2 = j - 1; for (i__ = 1; i__ <= i__2; ++i__) { absa = (d__1 = a_ref (i__, j), fabs (d__1)); sum += absa; work[i__] += absa; /* L50: */ } work[j] = sum + (d__1 = a_ref (j, j), fabs (d__1)); /* L60: */ } i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { /* Computing MAX */ d__1 = value, d__2 = work[i__]; value = MAX (d__1, d__2); /* L70: */ } } else { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { work[i__] = 0.; /* L80: */ } i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = work[j] + (d__1 = a_ref (j, j), fabs (d__1)); i__2 = *n; for (i__ = j + 1; i__ <= i__2; ++i__) { absa = (d__1 = a_ref (i__, j), fabs (d__1)); sum += absa; work[i__] += absa; /* L90: */ } value = MAX (value, sum); /* L100: */ } } } else if (lsame_ (norm, "F") || lsame_ (norm, "E")) { /* Find normF(A). */ scale = 0.; sum = 1.; if (lsame_ (uplo, "U")) { i__1 = *n; for (j = 2; j <= i__1; ++j) { i__2 = j - 1; NUMlapack_dlassq (&i__2, &a_ref (1, j), &c__1, &scale, &sum); /* L110: */ } } else { i__1 = *n - 1; for (j = 1; j <= i__1; ++j) { i__2 = *n - j; NUMlapack_dlassq (&i__2, &a_ref (j + 1, j), &c__1, &scale, &sum); /* L120: */ } } sum *= 2; i__1 = *lda + 1; NUMlapack_dlassq (n, &a[a_offset], &i__1, &scale, &sum); value = scale * sqrt (sum); } ret_val = value; return ret_val; } /* NUMlapack_dlansy */ int NUMlapack_dlanv2 (double *a, double *b, double *c__, double *d__, double *rt1r, double *rt1i, double *rt2r, double *rt2i, double *cs, double *sn) { /* Table of constant values */ static double c_b4 = 1.; /* System generated locals */ double d__1, d__2; /* Local variables */ static double temp, p, scale, bcmax, z__, bcmis, sigma; static double aa, bb, cc, dd; static double cs1, sn1, sab, sac, eps, tau; eps = NUMblas_dlamch ("P"); if (*c__ == 0.) { *cs = 1.; *sn = 0.; goto L10; } else if (*b == 0.) { /* Swap rows and columns */ *cs = 0.; *sn = 1.; temp = *d__; *d__ = *a; *a = temp; *b = - (*c__); *c__ = 0.; goto L10; } else if (*a - *d__ == 0. && d_sign (&c_b4, b) != d_sign (&c_b4, c__)) { *cs = 1.; *sn = 0.; goto L10; } else { temp = *a - *d__; p = temp * .5; /* Computing MAX */ d__1 = fabs (*b), d__2 = fabs (*c__); bcmax = MAX (d__1, d__2); /* Computing MIN */ d__1 = fabs (*b), d__2 = fabs (*c__); bcmis = MIN (d__1, d__2) * d_sign (&c_b4, b) * d_sign (&c_b4, c__); /* Computing MAX */ d__1 = fabs (p); scale = MAX (d__1, bcmax); z__ = p / scale * p + bcmax / scale * bcmis; /* If Z is of the order of the machine accuracy, postpone the decision on the nature of eigenvalues */ if (z__ >= eps * 4.) { /* Real eigenvalues. Compute A and D. */ d__1 = sqrt (scale) * sqrt (z__); z__ = p + d_sign (&d__1, &p); *a = *d__ + z__; *d__ -= bcmax / z__ * bcmis; /* Compute B and the rotation matrix */ tau = NUMlapack_dlapy2 (c__, &z__); *cs = z__ / tau; *sn = *c__ / tau; *b -= *c__; *c__ = 0.; } else { /* Complex eigenvalues, or real (almost) equal eigenvalues. Make diagonal elements equal. */ sigma = *b + *c__; tau = NUMlapack_dlapy2 (&sigma, &temp); *cs = sqrt ( (fabs (sigma) / tau + 1.) * .5); *sn = - (p / (tau * *cs)) * d_sign (&c_b4, &sigma); /* Compute [ AA BB ] = [ A B ] [ CS -SN ] [ CC DD ] [ C D ] [ SN CS ] */ aa = *a * *cs + *b * *sn; bb = - (*a) * *sn + *b * *cs; cc = *c__ * *cs + *d__ * *sn; dd = - (*c__) * *sn + *d__ * *cs; /* Compute [ A B ] = [ CS SN ] [ AA BB ] [ C D ] [-SN CS ] [ CC DD ] */ *a = aa * *cs + cc * *sn; *b = bb * *cs + dd * *sn; *c__ = -aa * *sn + cc * *cs; *d__ = -bb * *sn + dd * *cs; temp = (*a + *d__) * .5; *a = temp; *d__ = temp; if (*c__ != 0.) { if (*b != 0.) { if (d_sign (&c_b4, b) == d_sign (&c_b4, c__)) { /* Real eigenvalues: reduce to upper triangular form */ sab = sqrt ( (fabs (*b))); sac = sqrt ( (fabs (*c__))); d__1 = sab * sac; p = d_sign (&d__1, c__); tau = 1. / sqrt ( (d__1 = *b + *c__, fabs (d__1))); *a = temp + p; *d__ = temp - p; *b -= *c__; *c__ = 0.; cs1 = sab * tau; sn1 = sac * tau; temp = *cs * cs1 - *sn * sn1; *sn = *cs * sn1 + *sn * cs1; *cs = temp; } } else { *b = - (*c__); *c__ = 0.; temp = *cs; *cs = - (*sn); *sn = temp; } } } } L10: /* Store eigenvalues in (RT1R,RT1I) and (RT2R,RT2I). */ *rt1r = *a; *rt2r = *d__; if (*c__ == 0.) { *rt1i = 0.; *rt2i = 0.; } else { *rt1i = sqrt ( (fabs (*b))) * sqrt ( (fabs (*c__))); *rt2i = - (*rt1i); } return 0; } /* NUMlapack_dlanv2 */ int NUMlapack_dlapll (long *n, double *x, long *incx, double *y, long *incy, double *ssmin) { /* System generated locals */ long i__1; /* Local variables */ static double c__; static double ssmax, a11, a12, a22; static double tau; --y; --x; /* Function Body */ if (*n <= 1) { *ssmin = 0.; return 0; } /* Compute the QR factorization of the N-by-2 matrix ( X Y ) */ NUMlapack_dlarfg (n, &x[1], &x[*incx + 1], incx, &tau); a11 = x[1]; x[1] = 1.; c__ = -tau * NUMblas_ddot (n, &x[1], incx, &y[1], incy); NUMblas_daxpy (n, &c__, &x[1], incx, &y[1], incy); i__1 = *n - 1; NUMlapack_dlarfg (&i__1, &y[*incy + 1], &y[ (*incy << 1) + 1], incy, &tau); a12 = y[1]; a22 = y[*incy + 1]; /* Compute the SVD of 2-by-2 Upper triangular matrix. */ NUMlapack_dlas2 (&a11, &a12, &a22, ssmin, &ssmax); return 0; } /* NUMlapack_dlapll */ #define x_ref(a_1,a_2) x[(a_2)*x_dim1 + a_1] int NUMlapack_dlapmt (long *forwrd, long *m, long *n, double *x, long *ldx, long *k) { /* System generated locals */ long x_dim1, x_offset, i__1, i__2; /* Local variables */ static double temp; static long i__, j, ii, in; x_dim1 = *ldx; x_offset = 1 + x_dim1 * 1; x -= x_offset; --k; /* Function Body */ if (*n <= 1) { return 0; } i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { k[i__] = -k[i__]; /* L10: */ } if (*forwrd) { /* Forward permutation */ i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { if (k[i__] > 0) { goto L40; } j = i__; k[j] = -k[j]; in = k[j]; L20: if (k[in] > 0) { goto L40; } i__2 = *m; for (ii = 1; ii <= i__2; ++ii) { temp = x_ref (ii, j); x_ref (ii, j) = x_ref (ii, in); x_ref (ii, in) = temp; /* L30: */ } k[in] = -k[in]; j = in; in = k[in]; goto L20; L40: /* L50: */ ; } } else { /* Backward permutation */ i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { if (k[i__] > 0) { goto L80; } k[i__] = -k[i__]; j = k[i__]; L60: if (j == i__) { goto L80; } i__2 = *m; for (ii = 1; ii <= i__2; ++ii) { temp = x_ref (ii, i__); x_ref (ii, i__) = x_ref (ii, j); x_ref (ii, j) = temp; /* L70: */ } k[j] = -k[j]; j = k[j]; goto L60; L80: /* L90: */ ; } } return 0; } /* NUMlapack_dlapmt */ #undef x_ref double NUMlapack_dlapy2 (double *x, double *y) { /* System generated locals */ double ret_val, d__1; /* Local variables */ static double xabs, yabs, w, z__; xabs = fabs (*x); yabs = fabs (*y); w = MAX (xabs, yabs); z__ = MIN (xabs, yabs); if (z__ == 0.) { ret_val = w; } else { /* Computing 2nd power */ d__1 = z__ / w; ret_val = w * sqrt (d__1 * d__1 + 1.); } return ret_val; } /* NUMlapack_dlapy2 */ #define work_ref(a_1,a_2) work[(a_2)*work_dim1 + a_1] #define v_ref(a_1,a_2) v[(a_2)*v_dim1 + a_1] int NUMlapack_dlarfb (const char *side, const char *trans, const char *direct, const char *storev, long *m, long *n, long *k, double *v, long *ldv, double *t, long *ldt, double *c__, long *ldc, double *work, long *ldwork) { /* Table of constant values */ static long c__1 = 1; static double c_b14 = 1.; static double c_b25 = -1.; /* System generated locals */ long c_dim1, c_offset, t_dim1, t_offset, v_dim1, v_offset; long work_dim1, work_offset, i__1, i__2; /* Local variables */ static long i__, j; static char transt[1]; v_dim1 = *ldv; v_offset = 1 + v_dim1 * 1; v -= v_offset; t_dim1 = *ldt; t_offset = 1 + t_dim1 * 1; t -= t_offset; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; work_dim1 = *ldwork; work_offset = 1 + work_dim1 * 1; work -= work_offset; /* Function Body */ if (*m <= 0 || *n <= 0) { return 0; } if (lsame_ (trans, "N")) { * (unsigned char *) transt = 'T'; } else { * (unsigned char *) transt = 'N'; } if (lsame_ (storev, "C")) { if (lsame_ (direct, "F")) { /* Let V = ( V1 ) (first K rows) ( V2 ) where V1 is unit lower triangular. */ if (lsame_ (side, "L")) { /* Form H * C or H' * C where C = ( C1 ) ( C2 ) W := C' * V = (C1'*V1 + C2'*V2) (stored in WORK) W := C1' */ i__1 = *k; for (j = 1; j <= i__1; ++j) { NUMblas_dcopy (n, &c___ref (j, 1), ldc, &work_ref (1, j), &c__1); /* L10: */ } /* W := W * V1 */ NUMblas_dtrmm ("Right", "Lower", "No transpose", "Unit", n, k, &c_b14, &v[v_offset], ldv, &work[work_offset], ldwork); if (*m > *k) { /* W := W + C2'*V2 */ i__1 = *m - *k; NUMblas_dgemm ("Transpose", "No transpose", n, k, &i__1, &c_b14, &c___ref (*k + 1, 1), ldc, &v_ref (*k + 1, 1), ldv, &c_b14, &work[work_offset], ldwork); } /* W := W * T' or W * T */ NUMblas_dtrmm ("Right", "Upper", transt, "Non-unit", n, k, &c_b14, &t[t_offset], ldt, &work[work_offset], ldwork); /* C := C - V * W' */ if (*m > *k) { /* C2 := C2 - V2 * W' */ i__1 = *m - *k; NUMblas_dgemm ("No transpose", "Transpose", &i__1, n, k, &c_b25, &v_ref (*k + 1, 1), ldv, &work[work_offset], ldwork, &c_b14, &c___ref (*k + 1, 1), ldc); } /* W := W * V1' */ NUMblas_dtrmm ("Right", "Lower", "Transpose", "Unit", n, k, &c_b14, &v[v_offset], ldv, &work[work_offset], ldwork); /* C1 := C1 - W' */ i__1 = *k; for (j = 1; j <= i__1; ++j) { i__2 = *n; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (j, i__) = c___ref (j, i__) - work_ref (i__, j); /* L20: */ } /* L30: */ } } else if (lsame_ (side, "R")) { /* Form C * H or C * H' where C = ( C1 C2 ) W := C * V = (C1*V1 + C2*V2) (stored in WORK) W := C1 */ i__1 = *k; for (j = 1; j <= i__1; ++j) { NUMblas_dcopy (m, &c___ref (1, j), &c__1, &work_ref (1, j), &c__1); /* L40: */ } /* W := W * V1 */ NUMblas_dtrmm ("Right", "Lower", "No transpose", "Unit", m, k, &c_b14, &v[v_offset], ldv, &work[work_offset], ldwork); if (*n > *k) { /* W := W + C2 * V2 */ i__1 = *n - *k; NUMblas_dgemm ("No transpose", "No transpose", m, k, &i__1, &c_b14, &c___ref (1, *k + 1), ldc, &v_ref (*k + 1, 1), ldv, &c_b14, &work[work_offset], ldwork); } /* W := W * T or W * T' */ NUMblas_dtrmm ("Right", "Upper", trans, "Non-unit", m, k, &c_b14, &t[t_offset], ldt, &work[work_offset], ldwork); /* C := C - W * V' */ if (*n > *k) { /* C2 := C2 - W * V2' */ i__1 = *n - *k; NUMblas_dgemm ("No transpose", "Transpose", m, &i__1, k, &c_b25, &work[work_offset], ldwork, &v_ref (*k + 1, 1), ldv, &c_b14, &c___ref (1, *k + 1), ldc); } /* W := W * V1' */ NUMblas_dtrmm ("Right", "Lower", "Transpose", "Unit", m, k, &c_b14, &v[v_offset], ldv, &work[work_offset], ldwork); /* C1 := C1 - W */ i__1 = *k; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = c___ref (i__, j) - work_ref (i__, j); /* L50: */ } /* L60: */ } } } else { /* Let V = ( V1 ) ( V2 ) (last K rows) where V2 is unit upper triangular. */ if (lsame_ (side, "L")) { /* Form H * C or H' * C where C = ( C1 ) ( C2 ) W := C' * V = (C1'*V1 + C2'*V2) (stored in WORK) W := C2' */ i__1 = *k; for (j = 1; j <= i__1; ++j) { NUMblas_dcopy (n, &c___ref (*m - *k + j, 1), ldc, &work_ref (1, j), &c__1); /* L70: */ } /* W := W * V2 */ NUMblas_dtrmm ("Right", "Upper", "No transpose", "Unit", n, k, &c_b14, &v_ref (*m - *k + 1, 1), ldv, &work[work_offset], ldwork); if (*m > *k) { /* W := W + C1'*V1 */ i__1 = *m - *k; NUMblas_dgemm ("Transpose", "No transpose", n, k, &i__1, &c_b14, &c__[c_offset], ldc, &v[v_offset], ldv, &c_b14, &work[work_offset], ldwork); } /* W := W * T' or W * T */ NUMblas_dtrmm ("Right", "Lower", transt, "Non-unit", n, k, &c_b14, &t[t_offset], ldt, &work[work_offset], ldwork); /* C := C - V * W' */ if (*m > *k) { /* C1 := C1 - V1 * W' */ i__1 = *m - *k; NUMblas_dgemm ("No transpose", "Transpose", &i__1, n, k, &c_b25, &v[v_offset], ldv, &work[work_offset], ldwork, &c_b14, &c__[c_offset], ldc); } /* W := W * V2' */ NUMblas_dtrmm ("Right", "Upper", "Transpose", "Unit", n, k, &c_b14, &v_ref (*m - *k + 1, 1), ldv, &work[work_offset], ldwork); /* C2 := C2 - W' */ i__1 = *k; for (j = 1; j <= i__1; ++j) { i__2 = *n; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (*m - *k + j, i__) = c___ref (*m - *k + j, i__) - work_ref (i__, j); /* L80: */ } /* L90: */ } } else if (lsame_ (side, "R")) { /* Form C * H or C * H' where C = ( C1 C2 ) W := C * V = (C1*V1 + C2*V2) (stored in WORK) W := C2 */ i__1 = *k; for (j = 1; j <= i__1; ++j) { NUMblas_dcopy (m, &c___ref (1, *n - *k + j), &c__1, &work_ref (1, j), &c__1); /* L100: */ } /* W := W * V2 */ NUMblas_dtrmm ("Right", "Upper", "No transpose", "Unit", m, k, &c_b14, &v_ref (*n - *k + 1, 1), ldv, &work[work_offset], ldwork); if (*n > *k) { /* W := W + C1 * V1 */ i__1 = *n - *k; NUMblas_dgemm ("No transpose", "No transpose", m, k, &i__1, &c_b14, &c__[c_offset], ldc, &v[v_offset], ldv, &c_b14, &work[work_offset], ldwork); } /* W := W * T or W * T' */ NUMblas_dtrmm ("Right", "Lower", trans, "Non-unit", m, k, &c_b14, &t[t_offset], ldt, &work[work_offset], ldwork); /* C := C - W * V' */ if (*n > *k) { /* C1 := C1 - W * V1' */ i__1 = *n - *k; NUMblas_dgemm ("No transpose", "Transpose", m, &i__1, k, &c_b25, &work[work_offset], ldwork, &v[v_offset], ldv, &c_b14, &c__[c_offset], ldc); } /* W := W * V2' */ NUMblas_dtrmm ("Right", "Upper", "Transpose", "Unit", m, k, &c_b14, &v_ref (*n - *k + 1, 1), ldv, &work[work_offset], ldwork); /* C2 := C2 - W */ i__1 = *k; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, *n - *k + j) = c___ref (i__, *n - *k + j) - work_ref (i__, j); /* L110: */ } /* L120: */ } } } } else if (lsame_ (storev, "R")) { if (lsame_ (direct, "F")) { /* Let V = ( V1 V2 ) (V1: first K columns) where V1 is unit upper triangular. */ if (lsame_ (side, "L")) { /* Form H * C or H' * C where C = ( C1 ) ( C2 ) W := C' * V' = (C1'*V1' + C2'*V2') (stored in WORK) W := C1' */ i__1 = *k; for (j = 1; j <= i__1; ++j) { NUMblas_dcopy (n, &c___ref (j, 1), ldc, &work_ref (1, j), &c__1); /* L130: */ } /* W := W * V1' */ NUMblas_dtrmm ("Right", "Upper", "Transpose", "Unit", n, k, &c_b14, &v[v_offset], ldv, &work[work_offset], ldwork); if (*m > *k) { /* W := W + C2'*V2' */ i__1 = *m - *k; NUMblas_dgemm ("Transpose", "Transpose", n, k, &i__1, &c_b14, &c___ref (*k + 1, 1), ldc, &v_ref (1, *k + 1), ldv, &c_b14, &work[work_offset], ldwork); } /* W := W * T' or W * T */ NUMblas_dtrmm ("Right", "Upper", transt, "Non-unit", n, k, &c_b14, &t[t_offset], ldt, &work[work_offset], ldwork); /* C := C - V' * W' */ if (*m > *k) { /* C2 := C2 - V2' * W' */ i__1 = *m - *k; NUMblas_dgemm ("Transpose", "Transpose", &i__1, n, k, &c_b25, &v_ref (1, *k + 1), ldv, &work[work_offset], ldwork, &c_b14, &c___ref (*k + 1, 1), ldc); } /* W := W * V1 */ NUMblas_dtrmm ("Right", "Upper", "No transpose", "Unit", n, k, &c_b14, &v[v_offset], ldv, &work[work_offset], ldwork); /* C1 := C1 - W' */ i__1 = *k; for (j = 1; j <= i__1; ++j) { i__2 = *n; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (j, i__) = c___ref (j, i__) - work_ref (i__, j); /* L140: */ } /* L150: */ } } else if (lsame_ (side, "R")) { /* Form C * H or C * H' where C = ( C1 C2 ) W := C * V' = (C1*V1' + C2*V2') (stored in WORK) W := C1 */ i__1 = *k; for (j = 1; j <= i__1; ++j) { NUMblas_dcopy (m, &c___ref (1, j), &c__1, &work_ref (1, j), &c__1); /* L160: */ } /* W := W * V1' */ NUMblas_dtrmm ("Right", "Upper", "Transpose", "Unit", m, k, &c_b14, &v[v_offset], ldv, &work[work_offset], ldwork); if (*n > *k) { /* W := W + C2 * V2' */ i__1 = *n - *k; NUMblas_dgemm ("No transpose", "Transpose", m, k, &i__1, &c_b14, &c___ref (1, *k + 1), ldc, &v_ref (1, *k + 1), ldv, &c_b14, &work[work_offset], ldwork); } /* W := W * T or W * T' */ NUMblas_dtrmm ("Right", "Upper", trans, "Non-unit", m, k, &c_b14, &t[t_offset], ldt, &work[work_offset], ldwork); /* C := C - W * V */ if (*n > *k) { /* C2 := C2 - W * V2 */ i__1 = *n - *k; NUMblas_dgemm ("No transpose", "No transpose", m, &i__1, k, &c_b25, &work[work_offset], ldwork, &v_ref (1, *k + 1), ldv, &c_b14, &c___ref (1, *k + 1), ldc); } /* W := W * V1 */ NUMblas_dtrmm ("Right", "Upper", "No transpose", "Unit", m, k, &c_b14, &v[v_offset], ldv, &work[work_offset], ldwork); /* C1 := C1 - W */ i__1 = *k; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, j) = c___ref (i__, j) - work_ref (i__, j); /* L170: */ } /* L180: */ } } } else { /* Let V = ( V1 V2 ) (V2: last K columns) where V2 is unit lower triangular. */ if (lsame_ (side, "L")) { /* Form H * C or H' * C where C = ( C1 ) ( C2 ) W := C' * V' = (C1'*V1' + C2'*V2') (stored in WORK) W := C2' */ i__1 = *k; for (j = 1; j <= i__1; ++j) { NUMblas_dcopy (n, &c___ref (*m - *k + j, 1), ldc, &work_ref (1, j), &c__1); /* L190: */ } /* W := W * V2' */ NUMblas_dtrmm ("Right", "Lower", "Transpose", "Unit", n, k, &c_b14, &v_ref (1, *m - *k + 1), ldv, &work[work_offset], ldwork); if (*m > *k) { /* W := W + C1'*V1' */ i__1 = *m - *k; NUMblas_dgemm ("Transpose", "Transpose", n, k, &i__1, &c_b14, &c__[c_offset], ldc, &v[v_offset], ldv, &c_b14, &work[work_offset], ldwork); } /* W := W * T' or W * T */ NUMblas_dtrmm ("Right", "Lower", transt, "Non-unit", n, k, &c_b14, &t[t_offset], ldt, &work[work_offset], ldwork); /* C := C - V' * W' */ if (*m > *k) { /* C1 := C1 - V1' * W' */ i__1 = *m - *k; NUMblas_dgemm ("Transpose", "Transpose", &i__1, n, k, &c_b25, &v[v_offset], ldv, &work[work_offset], ldwork, &c_b14, &c__[c_offset], ldc); } /* W := W * V2 */ NUMblas_dtrmm ("Right", "Lower", "No transpose", "Unit", n, k, &c_b14, &v_ref (1, *m - *k + 1), ldv, &work[work_offset], ldwork); /* C2 := C2 - W' */ i__1 = *k; for (j = 1; j <= i__1; ++j) { i__2 = *n; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (*m - *k + j, i__) = c___ref (*m - *k + j, i__) - work_ref (i__, j); /* L200: */ } /* L210: */ } } else if (lsame_ (side, "R")) { /* Form C * H or C * H' where C = ( C1 C2 ) W := C * V' = (C1*V1' + C2*V2') (stored in WORK) W := C2 */ i__1 = *k; for (j = 1; j <= i__1; ++j) { NUMblas_dcopy (m, &c___ref (1, *n - *k + j), &c__1, &work_ref (1, j), &c__1); /* L220: */ } /* W := W * V2' */ NUMblas_dtrmm ("Right", "Lower", "Transpose", "Unit", m, k, &c_b14, &v_ref (1, *n - *k + 1), ldv, &work[work_offset], ldwork); if (*n > *k) { /* W := W + C1 * V1' */ i__1 = *n - *k; NUMblas_dgemm ("No transpose", "Transpose", m, k, &i__1, &c_b14, &c__[c_offset], ldc, &v[v_offset], ldv, &c_b14, &work[work_offset], ldwork); } /* W := W * T or W * T' */ NUMblas_dtrmm ("Right", "Lower", trans, "Non-unit", m, k, &c_b14, &t[t_offset], ldt, &work[work_offset], ldwork); /* C := C - W * V */ if (*n > *k) { /* C1 := C1 - W * V1 */ i__1 = *n - *k; NUMblas_dgemm ("No transpose", "No transpose", m, &i__1, k, &c_b25, &work[work_offset], ldwork, &v[v_offset], ldv, &c_b14, &c__[c_offset], ldc); } /* W := W * V2 */ NUMblas_dtrmm ("Right", "Lower", "No transpose", "Unit", m, k, &c_b14, &v_ref (1, *n - *k + 1), ldv, &work[work_offset], ldwork); /* C1 := C1 - W */ i__1 = *k; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { c___ref (i__, *n - *k + j) = c___ref (i__, *n - *k + j) - work_ref (i__, j); /* L230: */ } /* L240: */ } } } } return 0; } /* NUMlapack_dlarfb */ #undef v_ref #undef work_ref int NUMlapack_dlarf (const char *side, long *m, long *n, double *v, long *incv, double *tau, double *c__, long *ldc, double *work) { /* Table of constant values */ static double c_b4 = 1.; static double c_b5 = 0.; static long c__1 = 1; /* System generated locals */ long c_dim1, c_offset; double d__1; /* Local variables */ --v; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; --work; /* Function Body */ if (lsame_ (side, "L")) { /* Form H * C */ if (*tau != 0.) { /* w := C' * v */ NUMblas_dgemv ("Transpose", m, n, &c_b4, &c__[c_offset], ldc, &v[1], incv, &c_b5, &work[1], &c__1); /* C := C - v * w' */ d__1 = - (*tau); NUMblas_dger (m, n, &d__1, &v[1], incv, &work[1], &c__1, &c__[c_offset], ldc); } } else { /* Form C * H */ if (*tau != 0.) { /* w := C * v */ NUMblas_dgemv ("No transpose", m, n, &c_b4, &c__[c_offset], ldc, &v[1], incv, &c_b5, &work[1], &c__1); /* C := C - w * v' */ d__1 = - (*tau); NUMblas_dger (m, n, &d__1, &work[1], &c__1, &v[1], incv, &c__[c_offset], ldc); } } return 0; } /* NUMlapack_dlarf */ int NUMlapack_dlarfg (long *n, double *alpha, double *x, long *incx, double *tau) { /* System generated locals */ long i__1; double d__1; /* Local variables */ static double beta; static long j; static double xnorm; static double safmin, rsafmn; static long knt; --x; /* Function Body */ if (*n <= 1) { *tau = 0.; return 0; } i__1 = *n - 1; xnorm = NUMblas_dnrm2 (&i__1, &x[1], incx); if (xnorm == 0.) { /* H = I */ *tau = 0.; } else { /* general case */ d__1 = NUMlapack_dlapy2 (alpha, &xnorm); beta = -d_sign (&d__1, alpha); safmin = NUMblas_dlamch ("S") / NUMblas_dlamch ("E"); if (fabs (beta) < safmin) { /* XNORM, BETA may be inaccurate; scale X and recompute them */ rsafmn = 1. / safmin; knt = 0; L10: ++knt; i__1 = *n - 1; NUMblas_dscal (&i__1, &rsafmn, &x[1], incx); beta *= rsafmn; *alpha *= rsafmn; if (fabs (beta) < safmin) { goto L10; } /* New BETA is at most 1, at least SAFMIN */ i__1 = *n - 1; xnorm = NUMblas_dnrm2 (&i__1, &x[1], incx); d__1 = NUMlapack_dlapy2 (alpha, &xnorm); beta = -d_sign (&d__1, alpha); *tau = (beta - *alpha) / beta; i__1 = *n - 1; d__1 = 1. / (*alpha - beta); NUMblas_dscal (&i__1, &d__1, &x[1], incx); /* If ALPHA is subnormal, it may lose relative accuracy */ *alpha = beta; i__1 = knt; for (j = 1; j <= i__1; ++j) { *alpha *= safmin; /* L20: */ } } else { *tau = (beta - *alpha) / beta; i__1 = *n - 1; d__1 = 1. / (*alpha - beta); NUMblas_dscal (&i__1, &d__1, &x[1], incx); *alpha = beta; } } return 0; } /* NUMlapack_dlarfg */ #define t_ref(a_1,a_2) t[(a_2)*t_dim1 + a_1] #define v_ref(a_1,a_2) v[(a_2)*v_dim1 + a_1] int NUMlapack_dlarft (const char *direct, const char *storev, long *n, long *k, double *v, long *ldv, double *tau, double *t, long *ldt) { /* Table of constant values */ static long c__1 = 1; static double c_b8 = 0.; /* System generated locals */ long t_dim1, t_offset, v_dim1, v_offset, i__1, i__2, i__3; double d__1; /* Local variables */ static long i__, j; static double vii; v_dim1 = *ldv; v_offset = 1 + v_dim1 * 1; v -= v_offset; --tau; t_dim1 = *ldt; t_offset = 1 + t_dim1 * 1; t -= t_offset; /* Function Body */ if (*n == 0) { return 0; } if (lsame_ (direct, "F")) { i__1 = *k; for (i__ = 1; i__ <= i__1; ++i__) { if (tau[i__] == 0.) { /* H(i) = I */ i__2 = i__; for (j = 1; j <= i__2; ++j) { t_ref (j, i__) = 0.; /* L10: */ } } else { /* general case */ vii = v_ref (i__, i__); v_ref (i__, i__) = 1.; if (lsame_ (storev, "C")) { /* T(1:i-1,i) := - tau(i) * V(i:n,1:i-1)' * V(i:n,i) */ i__2 = *n - i__ + 1; i__3 = i__ - 1; d__1 = -tau[i__]; NUMblas_dgemv ("Transpose", &i__2, &i__3, &d__1, &v_ref (i__, 1), ldv, &v_ref (i__, i__), &c__1, &c_b8, &t_ref (1, i__), &c__1); } else { /* T(1:i-1,i) := - tau(i) * V(1:i-1,i:n) * V(i,i:n)' */ i__2 = i__ - 1; i__3 = *n - i__ + 1; d__1 = -tau[i__]; NUMblas_dgemv ("No transpose", &i__2, &i__3, &d__1, &v_ref (1, i__), ldv, &v_ref (i__, i__), ldv, &c_b8, &t_ref (1, i__), &c__1); } v_ref (i__, i__) = vii; /* T(1:i-1,i) := T(1:i-1,1:i-1) * T(1:i-1,i) */ i__2 = i__ - 1; NUMblas_dtrmv ("Upper", "No transpose", "Non-unit", &i__2, &t[t_offset], ldt, &t_ref (1, i__), &c__1); t_ref (i__, i__) = tau[i__]; } /* L20: */ } } else { for (i__ = *k; i__ >= 1; --i__) { if (tau[i__] == 0.) { /* H(i) = I */ i__1 = *k; for (j = i__; j <= i__1; ++j) { t_ref (j, i__) = 0.; /* L30: */ } } else { /* general case */ if (i__ < *k) { if (lsame_ (storev, "C")) { vii = v_ref (*n - *k + i__, i__); v_ref (*n - *k + i__, i__) = 1.; /* T(i+1:k,i) := - tau(i) * V(1:n-k+i,i+1:k)' * V(1:n-k+i,i) */ i__1 = *n - *k + i__; i__2 = *k - i__; d__1 = -tau[i__]; NUMblas_dgemv ("Transpose", &i__1, &i__2, &d__1, &v_ref (1, i__ + 1), ldv, &v_ref (1, i__), &c__1, &c_b8, &t_ref (i__ + 1, i__), &c__1); v_ref (*n - *k + i__, i__) = vii; } else { vii = v_ref (i__, *n - *k + i__); v_ref (i__, *n - *k + i__) = 1.; /* T(i+1:k,i) := - tau(i) * V(i+1:k,1:n-k+i) * V(i,1:n-k+i)' */ i__1 = *k - i__; i__2 = *n - *k + i__; d__1 = -tau[i__]; NUMblas_dgemv ("No transpose", &i__1, &i__2, &d__1, &v_ref (i__ + 1, 1), ldv, &v_ref (i__, 1), ldv, &c_b8, &t_ref (i__ + 1, i__), &c__1); v_ref (i__, *n - *k + i__) = vii; } /* T(i+1:k,i) := T(i+1:k,i+1:k) * T(i+1:k,i) */ i__1 = *k - i__; NUMblas_dtrmv ("Lower", "No transpose", "Non-unit", &i__1, &t_ref (i__ + 1, i__ + 1), ldt, &t_ref (i__ + 1, i__), &c__1); } t_ref (i__, i__) = tau[i__]; } /* L40: */ } } return 0; } /* NUMlapack_dlarft */ #undef v_ref #undef t_ref int NUMlapack_dlartg (double *f, double *g, double *cs, double *sn, double *r__) { /* Initialized data */ static long first = TRUE; /* System generated locals */ long i__1; double d__1, d__2; /* Local variables */ static long i__; static double scale; static long count; static double f1, g1, safmn2, safmx2; static double safmin, eps; if (first) { first = FALSE; safmin = NUMblas_dlamch ("S"); eps = NUMblas_dlamch ("E"); d__1 = NUMblas_dlamch ("B"); i__1 = (long) (log (safmin / eps) / log (NUMblas_dlamch ("B")) / 2.); safmn2 = pow_di (&d__1, &i__1); safmx2 = 1. / safmn2; } if (*g == 0.) { *cs = 1.; *sn = 0.; *r__ = *f; } else if (*f == 0.) { *cs = 0.; *sn = 1.; *r__ = *g; } else { f1 = *f; g1 = *g; /* Computing MAX */ d__1 = fabs (f1), d__2 = fabs (g1); scale = MAX (d__1, d__2); if (scale >= safmx2) { count = 0; L10: ++count; f1 *= safmn2; g1 *= safmn2; /* Computing MAX */ d__1 = fabs (f1), d__2 = fabs (g1); scale = MAX (d__1, d__2); if (scale >= safmx2) { goto L10; } /* Computing 2nd power */ d__1 = f1; /* Computing 2nd power */ d__2 = g1; *r__ = sqrt (d__1 * d__1 + d__2 * d__2); *cs = f1 / *r__; *sn = g1 / *r__; i__1 = count; for (i__ = 1; i__ <= i__1; ++i__) { *r__ *= safmx2; /* L20: */ } } else if (scale <= safmn2) { count = 0; L30: ++count; f1 *= safmx2; g1 *= safmx2; /* Computing MAX */ d__1 = fabs (f1), d__2 = fabs (g1); scale = MAX (d__1, d__2); if (scale <= safmn2) { goto L30; } /* Computing 2nd power */ d__1 = f1; /* Computing 2nd power */ d__2 = g1; *r__ = sqrt (d__1 * d__1 + d__2 * d__2); *cs = f1 / *r__; *sn = g1 / *r__; i__1 = count; for (i__ = 1; i__ <= i__1; ++i__) { *r__ *= safmn2; /* L40: */ } } else { /* Computing 2nd power */ d__1 = f1; /* Computing 2nd power */ d__2 = g1; *r__ = sqrt (d__1 * d__1 + d__2 * d__2); *cs = f1 / *r__; *sn = g1 / *r__; } if (fabs (*f) > fabs (*g) && *cs < 0.) { *cs = - (*cs); *sn = - (*sn); *r__ = - (*r__); } } return 0; } /* NUMlapack_dlartg */ int NUMlapack_dlarfx (const char *side, long *m, long *n, double *v, double *tau, double *c__, long *ldc, double *work) { /* Table of constant values */ static double c_b14 = 1.; static long c__1 = 1; static double c_b16 = 0.; /* System generated locals */ long c_dim1, c_offset, i__1; double d__1; /* Local variables */ static long j; static double t1, t2, t3, t4, t5, t6, t7, t8, t9, v1, v2, v3, v4, v5, v6, v7, v8, v9, t10, v10, sum; --v; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; --work; /* Function Body */ if (*tau == 0.) { return 0; } if (lsame_ (side, "L")) { /* Form H * C, where H has order m. */ switch (*m) { case 1: goto L10; case 2: goto L30; case 3: goto L50; case 4: goto L70; case 5: goto L90; case 6: goto L110; case 7: goto L130; case 8: goto L150; case 9: goto L170; case 10: goto L190; } /* Code for general M w := C'*v */ NUMblas_dgemv ("Transpose", m, n, &c_b14, &c__[c_offset], ldc, &v[1], &c__1, &c_b16, &work[1], &c__1); /* C := C - tau * v * w' */ d__1 = - (*tau); NUMblas_dger (m, n, &d__1, &v[1], &c__1, &work[1], &c__1, &c__[c_offset], ldc); goto L410; L10: /* Special code for 1 x 1 Householder */ t1 = 1. - *tau * v[1] * v[1]; i__1 = *n; for (j = 1; j <= i__1; ++j) { c___ref (1, j) = t1 * c___ref (1, j); /* L20: */ } goto L410; L30: /* Special code for 2 x 2 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (1, j) + v2 * c___ref (2, j); c___ref (1, j) = c___ref (1, j) - sum * t1; c___ref (2, j) = c___ref (2, j) - sum * t2; /* L40: */ } goto L410; L50: /* Special code for 3 x 3 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (1, j) + v2 * c___ref (2, j) + v3 * c___ref (3, j); c___ref (1, j) = c___ref (1, j) - sum * t1; c___ref (2, j) = c___ref (2, j) - sum * t2; c___ref (3, j) = c___ref (3, j) - sum * t3; /* L60: */ } goto L410; L70: /* Special code for 4 x 4 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (1, j) + v2 * c___ref (2, j) + v3 * c___ref (3, j) + v4 * c___ref (4, j); c___ref (1, j) = c___ref (1, j) - sum * t1; c___ref (2, j) = c___ref (2, j) - sum * t2; c___ref (3, j) = c___ref (3, j) - sum * t3; c___ref (4, j) = c___ref (4, j) - sum * t4; /* L80: */ } goto L410; L90: /* Special code for 5 x 5 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (1, j) + v2 * c___ref (2, j) + v3 * c___ref (3, j) + v4 * c___ref (4, j) + v5 * c___ref (5, j); c___ref (1, j) = c___ref (1, j) - sum * t1; c___ref (2, j) = c___ref (2, j) - sum * t2; c___ref (3, j) = c___ref (3, j) - sum * t3; c___ref (4, j) = c___ref (4, j) - sum * t4; c___ref (5, j) = c___ref (5, j) - sum * t5; /* L100: */ } goto L410; L110: /* Special code for 6 x 6 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (1, j) + v2 * c___ref (2, j) + v3 * c___ref (3, j) + v4 * c___ref (4, j) + v5 * c___ref (5, j) + v6 * c___ref (6, j); c___ref (1, j) = c___ref (1, j) - sum * t1; c___ref (2, j) = c___ref (2, j) - sum * t2; c___ref (3, j) = c___ref (3, j) - sum * t3; c___ref (4, j) = c___ref (4, j) - sum * t4; c___ref (5, j) = c___ref (5, j) - sum * t5; c___ref (6, j) = c___ref (6, j) - sum * t6; /* L120: */ } goto L410; L130: /* Special code for 7 x 7 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; v7 = v[7]; t7 = *tau * v7; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (1, j) + v2 * c___ref (2, j) + v3 * c___ref (3, j) + v4 * c___ref (4, j) + v5 * c___ref (5, j) + v6 * c___ref (6, j) + v7 * c___ref (7, j); c___ref (1, j) = c___ref (1, j) - sum * t1; c___ref (2, j) = c___ref (2, j) - sum * t2; c___ref (3, j) = c___ref (3, j) - sum * t3; c___ref (4, j) = c___ref (4, j) - sum * t4; c___ref (5, j) = c___ref (5, j) - sum * t5; c___ref (6, j) = c___ref (6, j) - sum * t6; c___ref (7, j) = c___ref (7, j) - sum * t7; /* L140: */ } goto L410; L150: /* Special code for 8 x 8 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; v7 = v[7]; t7 = *tau * v7; v8 = v[8]; t8 = *tau * v8; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (1, j) + v2 * c___ref (2, j) + v3 * c___ref (3, j) + v4 * c___ref (4, j) + v5 * c___ref (5, j) + v6 * c___ref (6, j) + v7 * c___ref (7, j) + v8 * c___ref (8, j); c___ref (1, j) = c___ref (1, j) - sum * t1; c___ref (2, j) = c___ref (2, j) - sum * t2; c___ref (3, j) = c___ref (3, j) - sum * t3; c___ref (4, j) = c___ref (4, j) - sum * t4; c___ref (5, j) = c___ref (5, j) - sum * t5; c___ref (6, j) = c___ref (6, j) - sum * t6; c___ref (7, j) = c___ref (7, j) - sum * t7; c___ref (8, j) = c___ref (8, j) - sum * t8; /* L160: */ } goto L410; L170: /* Special code for 9 x 9 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; v7 = v[7]; t7 = *tau * v7; v8 = v[8]; t8 = *tau * v8; v9 = v[9]; t9 = *tau * v9; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (1, j) + v2 * c___ref (2, j) + v3 * c___ref (3, j) + v4 * c___ref (4, j) + v5 * c___ref (5, j) + v6 * c___ref (6, j) + v7 * c___ref (7, j) + v8 * c___ref (8, j) + v9 * c___ref (9, j); c___ref (1, j) = c___ref (1, j) - sum * t1; c___ref (2, j) = c___ref (2, j) - sum * t2; c___ref (3, j) = c___ref (3, j) - sum * t3; c___ref (4, j) = c___ref (4, j) - sum * t4; c___ref (5, j) = c___ref (5, j) - sum * t5; c___ref (6, j) = c___ref (6, j) - sum * t6; c___ref (7, j) = c___ref (7, j) - sum * t7; c___ref (8, j) = c___ref (8, j) - sum * t8; c___ref (9, j) = c___ref (9, j) - sum * t9; /* L180: */ } goto L410; L190: /* Special code for 10 x 10 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; v7 = v[7]; t7 = *tau * v7; v8 = v[8]; t8 = *tau * v8; v9 = v[9]; t9 = *tau * v9; v10 = v[10]; t10 = *tau * v10; i__1 = *n; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (1, j) + v2 * c___ref (2, j) + v3 * c___ref (3, j) + v4 * c___ref (4, j) + v5 * c___ref (5, j) + v6 * c___ref (6, j) + v7 * c___ref (7, j) + v8 * c___ref (8, j) + v9 * c___ref (9, j) + v10 * c___ref (10, j); c___ref (1, j) = c___ref (1, j) - sum * t1; c___ref (2, j) = c___ref (2, j) - sum * t2; c___ref (3, j) = c___ref (3, j) - sum * t3; c___ref (4, j) = c___ref (4, j) - sum * t4; c___ref (5, j) = c___ref (5, j) - sum * t5; c___ref (6, j) = c___ref (6, j) - sum * t6; c___ref (7, j) = c___ref (7, j) - sum * t7; c___ref (8, j) = c___ref (8, j) - sum * t8; c___ref (9, j) = c___ref (9, j) - sum * t9; c___ref (10, j) = c___ref (10, j) - sum * t10; /* L200: */ } goto L410; } else { /* Form C * H, where H has order n. */ switch (*n) { case 1: goto L210; case 2: goto L230; case 3: goto L250; case 4: goto L270; case 5: goto L290; case 6: goto L310; case 7: goto L330; case 8: goto L350; case 9: goto L370; case 10: goto L390; } /* Code for general N w := C * v */ NUMblas_dgemv ("No transpose", m, n, &c_b14, &c__[c_offset], ldc, &v[1], &c__1, &c_b16, &work[1], &c__1); /* C := C - tau * w * v' */ d__1 = - (*tau); NUMblas_dger (m, n, &d__1, &work[1], &c__1, &v[1], &c__1, &c__[c_offset], ldc); goto L410; L210: /* Special code for 1 x 1 Householder */ t1 = 1. - *tau * v[1] * v[1]; i__1 = *m; for (j = 1; j <= i__1; ++j) { c___ref (j, 1) = t1 * c___ref (j, 1); /* L220: */ } goto L410; L230: /* Special code for 2 x 2 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; i__1 = *m; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (j, 1) + v2 * c___ref (j, 2); c___ref (j, 1) = c___ref (j, 1) - sum * t1; c___ref (j, 2) = c___ref (j, 2) - sum * t2; /* L240: */ } goto L410; L250: /* Special code for 3 x 3 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; i__1 = *m; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (j, 1) + v2 * c___ref (j, 2) + v3 * c___ref (j, 3); c___ref (j, 1) = c___ref (j, 1) - sum * t1; c___ref (j, 2) = c___ref (j, 2) - sum * t2; c___ref (j, 3) = c___ref (j, 3) - sum * t3; /* L260: */ } goto L410; L270: /* Special code for 4 x 4 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; i__1 = *m; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (j, 1) + v2 * c___ref (j, 2) + v3 * c___ref (j, 3) + v4 * c___ref (j, 4); c___ref (j, 1) = c___ref (j, 1) - sum * t1; c___ref (j, 2) = c___ref (j, 2) - sum * t2; c___ref (j, 3) = c___ref (j, 3) - sum * t3; c___ref (j, 4) = c___ref (j, 4) - sum * t4; /* L280: */ } goto L410; L290: /* Special code for 5 x 5 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; i__1 = *m; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (j, 1) + v2 * c___ref (j, 2) + v3 * c___ref (j, 3) + v4 * c___ref (j, 4) + v5 * c___ref (j, 5); c___ref (j, 1) = c___ref (j, 1) - sum * t1; c___ref (j, 2) = c___ref (j, 2) - sum * t2; c___ref (j, 3) = c___ref (j, 3) - sum * t3; c___ref (j, 4) = c___ref (j, 4) - sum * t4; c___ref (j, 5) = c___ref (j, 5) - sum * t5; /* L300: */ } goto L410; L310: /* Special code for 6 x 6 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; i__1 = *m; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (j, 1) + v2 * c___ref (j, 2) + v3 * c___ref (j, 3) + v4 * c___ref (j, 4) + v5 * c___ref (j, 5) + v6 * c___ref (j, 6); c___ref (j, 1) = c___ref (j, 1) - sum * t1; c___ref (j, 2) = c___ref (j, 2) - sum * t2; c___ref (j, 3) = c___ref (j, 3) - sum * t3; c___ref (j, 4) = c___ref (j, 4) - sum * t4; c___ref (j, 5) = c___ref (j, 5) - sum * t5; c___ref (j, 6) = c___ref (j, 6) - sum * t6; /* L320: */ } goto L410; L330: /* Special code for 7 x 7 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; v7 = v[7]; t7 = *tau * v7; i__1 = *m; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (j, 1) + v2 * c___ref (j, 2) + v3 * c___ref (j, 3) + v4 * c___ref (j, 4) + v5 * c___ref (j, 5) + v6 * c___ref (j, 6) + v7 * c___ref (j, 7); c___ref (j, 1) = c___ref (j, 1) - sum * t1; c___ref (j, 2) = c___ref (j, 2) - sum * t2; c___ref (j, 3) = c___ref (j, 3) - sum * t3; c___ref (j, 4) = c___ref (j, 4) - sum * t4; c___ref (j, 5) = c___ref (j, 5) - sum * t5; c___ref (j, 6) = c___ref (j, 6) - sum * t6; c___ref (j, 7) = c___ref (j, 7) - sum * t7; /* L340: */ } goto L410; L350: /* Special code for 8 x 8 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; v7 = v[7]; t7 = *tau * v7; v8 = v[8]; t8 = *tau * v8; i__1 = *m; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (j, 1) + v2 * c___ref (j, 2) + v3 * c___ref (j, 3) + v4 * c___ref (j, 4) + v5 * c___ref (j, 5) + v6 * c___ref (j, 6) + v7 * c___ref (j, 7) + v8 * c___ref (j, 8); c___ref (j, 1) = c___ref (j, 1) - sum * t1; c___ref (j, 2) = c___ref (j, 2) - sum * t2; c___ref (j, 3) = c___ref (j, 3) - sum * t3; c___ref (j, 4) = c___ref (j, 4) - sum * t4; c___ref (j, 5) = c___ref (j, 5) - sum * t5; c___ref (j, 6) = c___ref (j, 6) - sum * t6; c___ref (j, 7) = c___ref (j, 7) - sum * t7; c___ref (j, 8) = c___ref (j, 8) - sum * t8; /* L360: */ } goto L410; L370: /* Special code for 9 x 9 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; v7 = v[7]; t7 = *tau * v7; v8 = v[8]; t8 = *tau * v8; v9 = v[9]; t9 = *tau * v9; i__1 = *m; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (j, 1) + v2 * c___ref (j, 2) + v3 * c___ref (j, 3) + v4 * c___ref (j, 4) + v5 * c___ref (j, 5) + v6 * c___ref (j, 6) + v7 * c___ref (j, 7) + v8 * c___ref (j, 8) + v9 * c___ref (j, 9); c___ref (j, 1) = c___ref (j, 1) - sum * t1; c___ref (j, 2) = c___ref (j, 2) - sum * t2; c___ref (j, 3) = c___ref (j, 3) - sum * t3; c___ref (j, 4) = c___ref (j, 4) - sum * t4; c___ref (j, 5) = c___ref (j, 5) - sum * t5; c___ref (j, 6) = c___ref (j, 6) - sum * t6; c___ref (j, 7) = c___ref (j, 7) - sum * t7; c___ref (j, 8) = c___ref (j, 8) - sum * t8; c___ref (j, 9) = c___ref (j, 9) - sum * t9; /* L380: */ } goto L410; L390: /* Special code for 10 x 10 Householder */ v1 = v[1]; t1 = *tau * v1; v2 = v[2]; t2 = *tau * v2; v3 = v[3]; t3 = *tau * v3; v4 = v[4]; t4 = *tau * v4; v5 = v[5]; t5 = *tau * v5; v6 = v[6]; t6 = *tau * v6; v7 = v[7]; t7 = *tau * v7; v8 = v[8]; t8 = *tau * v8; v9 = v[9]; t9 = *tau * v9; v10 = v[10]; t10 = *tau * v10; i__1 = *m; for (j = 1; j <= i__1; ++j) { sum = v1 * c___ref (j, 1) + v2 * c___ref (j, 2) + v3 * c___ref (j, 3) + v4 * c___ref (j, 4) + v5 * c___ref (j, 5) + v6 * c___ref (j, 6) + v7 * c___ref (j, 7) + v8 * c___ref (j, 8) + v9 * c___ref (j, 9) + v10 * c___ref (j, 10); c___ref (j, 1) = c___ref (j, 1) - sum * t1; c___ref (j, 2) = c___ref (j, 2) - sum * t2; c___ref (j, 3) = c___ref (j, 3) - sum * t3; c___ref (j, 4) = c___ref (j, 4) - sum * t4; c___ref (j, 5) = c___ref (j, 5) - sum * t5; c___ref (j, 6) = c___ref (j, 6) - sum * t6; c___ref (j, 7) = c___ref (j, 7) - sum * t7; c___ref (j, 8) = c___ref (j, 8) - sum * t8; c___ref (j, 9) = c___ref (j, 9) - sum * t9; c___ref (j, 10) = c___ref (j, 10) - sum * t10; /* L400: */ } goto L410; } L410: return 0; } /* NUMlapack_dlarfx */ int NUMlapack_dlas2 (double *f, double *g, double *h__, double *ssmin, double *ssmax) { /* System generated locals */ double d__1, d__2; /* Local variables */ static double fhmn, fhmx, c__, fa, ga, ha, as, at, au; fa = fabs (*f); ga = fabs (*g); ha = fabs (*h__); fhmn = MIN (fa, ha); fhmx = MAX (fa, ha); if (fhmn == 0.) { *ssmin = 0.; if (fhmx == 0.) { *ssmax = ga; } else { /* Computing 2nd power */ d__1 = MIN (fhmx, ga) / MAX (fhmx, ga); *ssmax = MAX (fhmx, ga) * sqrt (d__1 * d__1 + 1.); } } else { if (ga < fhmx) { as = fhmn / fhmx + 1.; at = (fhmx - fhmn) / fhmx; /* Computing 2nd power */ d__1 = ga / fhmx; au = d__1 * d__1; c__ = 2. / (sqrt (as * as + au) + sqrt (at * at + au)); *ssmin = fhmn * c__; *ssmax = fhmx / c__; } else { au = fhmx / ga; if (au == 0.) { /* Avoid possible harmful underflow if exponent range asymmetric (true SSMIN may not underflow even if AU underflows) */ *ssmin = fhmn * fhmx / ga; *ssmax = ga; } else { as = fhmn / fhmx + 1.; at = (fhmx - fhmn) / fhmx; /* Computing 2nd power */ d__1 = as * au; /* Computing 2nd power */ d__2 = at * au; c__ = 1. / (sqrt (d__1 * d__1 + 1.) + sqrt (d__2 * d__2 + 1.)); *ssmin = fhmn * c__ * au; *ssmin += *ssmin; *ssmax = ga / (c__ + c__); } } } return 0; } /* NUMlapack_dlas2 */ int NUMlapack_dlascl (const char *type__, long *kl, long *ku, double *cfrom, double *cto, long *m, long *n, double *a, long *lda, long *info) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4, i__5; /* Local variables */ static long done; static double ctoc; static long i__, j; static long itype, k1, k2, k3, k4; static double cfrom1; static double cfromc; static double bignum, smlnum, mul, cto1; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; /* Function Body */ *info = 0; if (lsame_ (type__, "G")) { itype = 0; } else if (lsame_ (type__, "L")) { itype = 1; } else if (lsame_ (type__, "U")) { itype = 2; } else if (lsame_ (type__, "H")) { itype = 3; } else if (lsame_ (type__, "B")) { itype = 4; } else if (lsame_ (type__, "Q")) { itype = 5; } else if (lsame_ (type__, "Z")) { itype = 6; } else { itype = -1; } if (itype == -1) { *info = -1; } else if (*cfrom == 0.) { *info = -4; } else if (*m < 0) { *info = -6; } else if (*n < 0 || itype == 4 && *n != *m || itype == 5 && *n != *m) { *info = -7; } else if (itype <= 3 && *lda < MAX (1, *m)) { *info = -9; } else if (itype >= 4) { /* Computing MAX */ i__1 = *m - 1; if (*kl < 0 || *kl > MAX (i__1, 0)) { *info = -2; } else { /* if(complicated condition) */ /* Computing MAX */ i__1 = *n - 1; if (*ku < 0 || *ku > MAX (i__1, 0) || (itype == 4 || itype == 5) && *kl != *ku) { *info = -3; } else if (itype == 4 && *lda < *kl + 1 || itype == 5 && *lda < *ku + 1 || itype == 6 && *lda < (*kl << 1) + *ku + 1) { *info = -9; } } } if (*info != 0) { i__1 = - (*info); xerbla_ ("DLASCL", &i__1); return 0; } /* Quick return if possible */ if (*n == 0 || *m == 0) { return 0; } /* Get machine parameters */ smlnum = NUMblas_dlamch ("S"); bignum = 1. / smlnum; cfromc = *cfrom; ctoc = *cto; L10: cfrom1 = cfromc * smlnum; cto1 = ctoc / bignum; if (fabs (cfrom1) > fabs (ctoc) && ctoc != 0.) { mul = smlnum; done = FALSE; cfromc = cfrom1; } else if (fabs (cto1) > fabs (cfromc)) { mul = bignum; done = FALSE; ctoc = cto1; } else { mul = ctoc / cfromc; done = TRUE; } if (itype == 0) { /* Full matrix */ i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) * mul; /* L20: */ } /* L30: */ } } else if (itype == 1) { /* Lower triangular matrix */ i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = j; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) * mul; /* L40: */ } /* L50: */ } } else if (itype == 2) { /* Upper triangular matrix */ i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = MIN (j, *m); for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) * mul; /* L60: */ } /* L70: */ } } else if (itype == 3) { /* Upper Hessenberg matrix */ i__1 = *n; for (j = 1; j <= i__1; ++j) { /* Computing MIN */ i__3 = j + 1; i__2 = MIN (i__3, *m); for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) * mul; /* L80: */ } /* L90: */ } } else if (itype == 4) { /* Lower half of a symmetric band matrix */ k3 = *kl + 1; k4 = *n + 1; i__1 = *n; for (j = 1; j <= i__1; ++j) { /* Computing MIN */ i__3 = k3, i__4 = k4 - j; i__2 = MIN (i__3, i__4); for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) * mul; /* L100: */ } /* L110: */ } } else if (itype == 5) { /* Upper half of a symmetric band matrix */ k1 = *ku + 2; k3 = *ku + 1; i__1 = *n; for (j = 1; j <= i__1; ++j) { /* Computing MAX */ i__2 = k1 - j; i__3 = k3; for (i__ = MAX (i__2, 1); i__ <= i__3; ++i__) { a_ref (i__, j) = a_ref (i__, j) * mul; /* L120: */ } /* L130: */ } } else if (itype == 6) { /* Band matrix */ k1 = *kl + *ku + 2; k2 = *kl + 1; k3 = (*kl << 1) + *ku + 1; k4 = *kl + *ku + 1 + *m; i__1 = *n; for (j = 1; j <= i__1; ++j) { /* Computing MAX */ i__3 = k1 - j; /* Computing MIN */ i__4 = k3, i__5 = k4 - j; i__2 = MIN (i__4, i__5); for (i__ = MAX (i__3, k2); i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j) * mul; /* L140: */ } /* L150: */ } } if (!done) { goto L10; } return 0; } /* NUMlapack_dlascl */ int NUMlapack_dlaset (const char *uplo, long *m, long *n, double *alpha, double *beta, double *a, long *lda) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__, j; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; /* Function Body */ if (lsame_ (uplo, "U")) { /* Set the strictly upper triangular or trapezoidal part of the array to ALPHA. */ i__1 = *n; for (j = 2; j <= i__1; ++j) { /* Computing MIN */ i__3 = j - 1; i__2 = MIN (i__3, *m); for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = *alpha; /* L10: */ } /* L20: */ } } else if (lsame_ (uplo, "L")) { /* Set the strictly lower triangular or trapezoidal part of the array to ALPHA. */ i__1 = MIN (*m, *n); for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = j + 1; i__ <= i__2; ++i__) { a_ref (i__, j) = *alpha; /* L30: */ } /* L40: */ } } else { /* Set the leading m-by-n submatrix to ALPHA. */ i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = *alpha; /* L50: */ } /* L60: */ } } /* Set the first MIN(M,N) diagonal elements to BETA. */ i__1 = MIN (*m, *n); for (i__ = 1; i__ <= i__1; ++i__) { a_ref (i__, i__) = *beta; /* L70: */ } return 0; } /* NUMlapack_dlaset */ int NUMlapack_dlasq1 (long *n, double *d__, double *e, double *work, long *info) { /* System generated locals */ long i__1, i__2; double d__1, d__2, d__3; /* Local variables */ static long i__; static double scale; static long iinfo; static double sigmn; static double sigmx; static double safmin; static double eps; /* Parameter adjustments */ --work; --e; --d__; /* Function Body */ *info = 0; if (*n < 0) { *info = -2; i__1 = - (*info); xerbla_ ("DLASQ1", &i__1); return 0; } else if (*n == 0) { return 0; } else if (*n == 1) { d__[1] = fabs (d__[1]); return 0; } else if (*n == 2) { NUMlapack_dlas2 (&d__[1], &e[1], &d__[2], &sigmn, &sigmx); d__[1] = sigmx; d__[2] = sigmn; return 0; } /* Estimate the largest singular value. */ sigmx = 0.; i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { d__[i__] = (d__1 = d__[i__], fabs (d__1)); /* Computing MAX */ d__2 = sigmx, d__3 = (d__1 = e[i__], fabs (d__1)); sigmx = MAX (d__2, d__3); /* L10: */ } d__[*n] = (d__1 = d__[*n], fabs (d__1)); /* Early return if SIGMX is zero (matrix is already diagonal). */ if (sigmx == 0.) { NUMlapack_dlasrt ("D", n, &d__[1], &iinfo); return 0; } i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { /* Computing MAX */ d__1 = sigmx, d__2 = d__[i__]; sigmx = MAX (d__1, d__2); /* L20: */ } /* Copy D and E into WORK (in the Z format) and scale (squaring the input data makes scaling by a power of the radix pointless). */ eps = NUMblas_dlamch ("Precision"); safmin = NUMblas_dlamch ("Safe minimum"); scale = sqrt (eps / safmin); NUMblas_dcopy (n, &d__[1], &c__1, &work[1], &c__2); i__1 = *n - 1; NUMblas_dcopy (&i__1, &e[1], &c__1, &work[2], &c__2); i__1 = (*n << 1) - 1; i__2 = (*n << 1) - 1; NUMlapack_dlascl ("G", &c__0, &c__0, &sigmx, &scale, &i__1, &c__1, &work[1], &i__2, &iinfo); /* Compute the q's and e's. */ i__1 = (*n << 1) - 1; for (i__ = 1; i__ <= i__1; ++i__) { /* Computing 2nd power */ d__1 = work[i__]; work[i__] = d__1 * d__1; /* L30: */ } work[*n * 2] = 0.; NUMlapack_dlasq2 (n, &work[1], info); if (*info == 0) { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { d__[i__] = sqrt (work[i__]); /* L40: */ } NUMlapack_dlascl ("G", &c__0, &c__0, &scale, &sigmx, n, &c__1, &d__[1], n, &iinfo); } return 0; } /* NUMlapack_dlasq1 */ int NUMlapack_dlasq2 (long *n, double *z__, long *info) { /* System generated locals */ long i__1, i__2, i__3; double d__1, d__2; /* Local variables */ static long ieee; static long nbig; static double dmin__, emin, emax; static long ndiv, iter; static double qmin, temp, qmax, zmax; static long splt; static double d__, e; static long k; static double s, t; static long nfail; static double desig, trace, sigma; static long iinfo, i0, i4, n0; static long pp, iwhila, iwhilb; static double oldemn, safmin; static double eps, tol; static long ipn4; static double tol2; /* Parameter adjustments */ --z__; /* Function Body */ *info = 0; eps = NUMblas_dlamch ("Precision"); safmin = NUMblas_dlamch ("Safe minimum"); tol = eps * 100.; /* Computing 2nd power */ d__1 = tol; tol2 = d__1 * d__1; if (*n < 0) { *info = -1; xerbla_ ("DLASQ2", &c__1); return 0; } else if (*n == 0) { return 0; } else if (*n == 1) { /* 1-by-1 case. */ if (z__[1] < 0.) { *info = -201; xerbla_ ("DLASQ2", &c__2); } return 0; } else if (*n == 2) { /* 2-by-2 case. */ if (z__[2] < 0. || z__[3] < 0.) { *info = -2; xerbla_ ("DLASQ2", &c__2); return 0; } else if (z__[3] > z__[1]) { d__ = z__[3]; z__[3] = z__[1]; z__[1] = d__; } z__[5] = z__[1] + z__[2] + z__[3]; if (z__[2] > z__[3] * tol2) { t = (z__[1] - z__[3] + z__[2]) * .5; s = z__[3] * (z__[2] / t); if (s <= t) { s = z__[3] * (z__[2] / (t * (sqrt (s / t + 1.) + 1.))); } else { s = z__[3] * (z__[2] / (t + sqrt (t) * sqrt (t + s))); } t = z__[1] + (s + z__[2]); z__[3] *= z__[1] / t; z__[1] = t; } z__[2] = z__[3]; z__[6] = z__[2] + z__[1]; return 0; } /* Check for negative data and compute sums of q's and e's. */ z__[*n * 2] = 0.; emin = z__[2]; qmax = 0.; zmax = 0.; d__ = 0.; e = 0.; i__1 = *n - 1 << 1; for (k = 1; k <= i__1; k += 2) { if (z__[k] < 0.) { *info = - (k + 200); xerbla_ ("DLASQ2", &c__2); return 0; } else if (z__[k + 1] < 0.) { *info = - (k + 201); xerbla_ ("DLASQ2", &c__2); return 0; } d__ += z__[k]; e += z__[k + 1]; /* Computing MAX */ d__1 = qmax, d__2 = z__[k]; qmax = MAX (d__1, d__2); /* Computing MIN */ d__1 = emin, d__2 = z__[k + 1]; emin = MIN (d__1, d__2); /* Computing MAX */ d__1 = MAX (qmax, zmax), d__2 = z__[k + 1]; zmax = MAX (d__1, d__2); /* L10: */ } if (z__[ (*n << 1) - 1] < 0.) { *info = - ( (*n << 1) + 199); xerbla_ ("DLASQ2", &c__2); return 0; } d__ += z__[ (*n << 1) - 1]; /* Computing MAX */ d__1 = qmax, d__2 = z__[ (*n << 1) - 1]; qmax = MAX (d__1, d__2); zmax = MAX (qmax, zmax); /* Check for diagonality. */ if (e == 0.) { i__1 = *n; for (k = 2; k <= i__1; ++k) { z__[k] = z__[ (k << 1) - 1]; /* L20: */ } NUMlapack_dlasrt ("D", n, &z__[1], &iinfo); z__[ (*n << 1) - 1] = d__; return 0; } trace = d__ + e; /* Check for zero data. */ if (trace == 0.) { z__[ (*n << 1) - 1] = 0.; return 0; } /* Check whether the machine is IEEE conformable. */ ieee = NUMlapack_ilaenv (&c__10, "DLASQ2", "N", &c__1, &c__2, &c__3, &c__4, 6, 1) == 1 && NUMlapack_ilaenv (&c__11, "DLASQ2", "N", &c__1, &c__2, &c__3, &c__4, 6, 1) == 1; /* Rearrange data for locality: Z=(q1,qq1,e1,ee1,q2,qq2,e2,ee2,...). */ for (k = *n << 1; k >= 2; k += -2) { z__[k * 2] = 0.; z__[ (k << 1) - 1] = z__[k]; z__[ (k << 1) - 2] = 0.; z__[ (k << 1) - 3] = z__[k - 1]; /* L30: */ } i0 = 1; n0 = *n; /* Reverse the qd-array, if warranted. */ if (z__[ (i0 << 2) - 3] * 1.5 < z__[ (n0 << 2) - 3]) { ipn4 = i0 + n0 << 2; i__1 = i0 + n0 - 1 << 1; for (i4 = i0 << 2; i4 <= i__1; i4 += 4) { temp = z__[i4 - 3]; z__[i4 - 3] = z__[ipn4 - i4 - 3]; z__[ipn4 - i4 - 3] = temp; temp = z__[i4 - 1]; z__[i4 - 1] = z__[ipn4 - i4 - 5]; z__[ipn4 - i4 - 5] = temp; /* L40: */ } } /* Initial split checking via dqd and Li's test. */ pp = 0; for (k = 1; k <= 2; ++k) { d__ = z__[ (n0 << 2) + pp - 3]; i__1 = (i0 << 2) + pp; for (i4 = (n0 - 1 << 2) + pp; i4 >= i__1; i4 += -4) { if (z__[i4 - 1] <= tol2 * d__) { z__[i4 - 1] = 0.; d__ = z__[i4 - 3]; } else { d__ = z__[i4 - 3] * (d__ / (d__ + z__[i4 - 1])); } /* L50: */ } /* dqd maps Z to ZZ plus Li's test. */ emin = z__[ (i0 << 2) + pp + 1]; d__ = z__[ (i0 << 2) + pp - 3]; i__1 = (n0 - 1 << 2) + pp; for (i4 = (i0 << 2) + pp; i4 <= i__1; i4 += 4) { z__[i4 - (pp << 1) - 2] = d__ + z__[i4 - 1]; if (z__[i4 - 1] <= tol2 * d__) { z__[i4 - 1] = 0.; z__[i4 - (pp << 1) - 2] = d__; z__[i4 - (pp << 1)] = 0.; d__ = z__[i4 + 1]; } else if (safmin * z__[i4 + 1] < z__[i4 - (pp << 1) - 2] && safmin * z__[i4 - (pp << 1) - 2] < z__[i4 + 1]) { temp = z__[i4 + 1] / z__[i4 - (pp << 1) - 2]; z__[i4 - (pp << 1)] = z__[i4 - 1] * temp; d__ *= temp; } else { z__[i4 - (pp << 1)] = z__[i4 + 1] * (z__[i4 - 1] / z__[i4 - (pp << 1) - 2]); d__ = z__[i4 + 1] * (d__ / z__[i4 - (pp << 1) - 2]); } /* Computing MIN */ d__1 = emin, d__2 = z__[i4 - (pp << 1)]; emin = MIN (d__1, d__2); /* L60: */ } z__[ (n0 << 2) - pp - 2] = d__; /* Now find qmax. */ qmax = z__[ (i0 << 2) - pp - 2]; i__1 = (n0 << 2) - pp - 2; for (i4 = (i0 << 2) - pp + 2; i4 <= i__1; i4 += 4) { /* Computing MAX */ d__1 = qmax, d__2 = z__[i4]; qmax = MAX (d__1, d__2); /* L70: */ } /* Prepare for the next iteration on K. */ pp = 1 - pp; /* L80: */ } iter = 2; nfail = 0; ndiv = n0 - i0 << 1; i__1 = *n + 1; for (iwhila = 1; iwhila <= i__1; ++iwhila) { if (n0 < 1) { goto L150; } /* While array unfinished do E(N0) holds the value of SIGMA when submatrix in I0:N0 splits from the rest of the array, but is negated. */ desig = 0.; if (n0 == *n) { sigma = 0.; } else { sigma = -z__[ (n0 << 2) - 1]; } if (sigma < 0.) { *info = 1; return 0; } /* Find last unreduced submatrix's top index I0, find QMAX and EMIN. Find Gershgorin-type bound if Q's much greater than E's. */ emax = 0.; if (n0 > i0) { emin = (d__1 = z__[ (n0 << 2) - 5], fabs (d__1)); } else { emin = 0.; } qmin = z__[ (n0 << 2) - 3]; qmax = qmin; for (i4 = n0 << 2; i4 >= 8; i4 += -4) { if (z__[i4 - 5] <= 0.) { goto L100; } if (qmin >= emax * 4.) { /* Computing MIN */ d__1 = qmin, d__2 = z__[i4 - 3]; qmin = MIN (d__1, d__2); /* Computing MAX */ d__1 = emax, d__2 = z__[i4 - 5]; emax = MAX (d__1, d__2); } /* Computing MAX */ d__1 = qmax, d__2 = z__[i4 - 7] + z__[i4 - 5]; qmax = MAX (d__1, d__2); /* Computing MIN */ d__1 = emin, d__2 = z__[i4 - 5]; emin = MIN (d__1, d__2); /* L90: */ } i4 = 4; L100: i0 = i4 / 4; /* Store EMIN for passing to DLASQ3. */ z__[ (n0 << 2) - 1] = emin; /* Put -(initial shift) into DMIN. Computing MAX */ d__1 = 0., d__2 = qmin - sqrt (qmin) * 2. * sqrt (emax); dmin__ = -MAX (d__1, d__2); /* Now I0:N0 is unreduced. PP = 0 for ping, PP = 1 for pong. */ pp = 0; nbig = (n0 - i0 + 1) * 30; i__2 = nbig; for (iwhilb = 1; iwhilb <= i__2; ++iwhilb) { if (i0 > n0) { goto L130; } /* While submatrix unfinished take a good dqds step. */ NUMlapack_dlasq3 (&i0, &n0, &z__[1], &pp, &dmin__, &sigma, &desig, &qmax, &nfail, &iter, &ndiv, &ieee); pp = 1 - pp; /* When EMIN is very small check for splits. */ if (pp == 0 && n0 - i0 >= 3) { if (z__[n0 * 4] <= tol2 * qmax || z__[ (n0 << 2) - 1] <= tol2 * sigma) { splt = i0 - 1; qmax = z__[ (i0 << 2) - 3]; emin = z__[ (i0 << 2) - 1]; oldemn = z__[i0 * 4]; i__3 = n0 - 3 << 2; for (i4 = i0 << 2; i4 <= i__3; i4 += 4) { if (z__[i4] <= tol2 * z__[i4 - 3] || z__[i4 - 1] <= tol2 * sigma) { z__[i4 - 1] = -sigma; splt = i4 / 4; qmax = 0.; emin = z__[i4 + 3]; oldemn = z__[i4 + 4]; } else { /* Computing MAX */ d__1 = qmax, d__2 = z__[i4 + 1]; qmax = MAX (d__1, d__2); /* Computing MIN */ d__1 = emin, d__2 = z__[i4 - 1]; emin = MIN (d__1, d__2); /* Computing MIN */ d__1 = oldemn, d__2 = z__[i4]; oldemn = MIN (d__1, d__2); } /* L110: */ } z__[ (n0 << 2) - 1] = emin; z__[n0 * 4] = oldemn; i0 = splt + 1; } } /* L120: */ } *info = 2; return 0; /* end IWHILB */ L130: /* L140: */ ; } *info = 3; return 0; /* end IWHILA */ L150: /* Move q's to the front. */ i__1 = *n; for (k = 2; k <= i__1; ++k) { z__[k] = z__[ (k << 2) - 3]; /* L160: */ } /* Sort and compute sum of eigenvalues. */ NUMlapack_dlasrt ("D", n, &z__[1], &iinfo); e = 0.; for (k = *n; k >= 1; --k) { e += z__[k]; /* L170: */ } /* Store trace, sum(eigenvalues) and information on performance. */ z__[ (*n << 1) + 1] = trace; z__[ (*n << 1) + 2] = e; z__[ (*n << 1) + 3] = (double) iter; /* Computing 2nd power */ i__1 = *n; z__[ (*n << 1) + 4] = (double) ndiv / (double) (i__1 * i__1); z__[ (*n << 1) + 5] = nfail * 100. / (double) iter; return 0; } /* NUMlapack_dlasq2 */ int NUMlapack_dlasq3 (long *i0, long *n0, double *z__, long *pp, double *dmin__, double *sigma, double *desig, double *qmax, long *nfail, long *iter, long *ndiv, long *ieee) { /* Initialized data */ static long ttype = 0; static double dmin1 = 0.; static double dmin2 = 0.; static double dn = 0.; static double dn1 = 0.; static double dn2 = 0.; static double tau = 0.; /* System generated locals */ long i__1; double d__1, d__2; /* Local variables */ static double temp, s, t; static long j4; static long nn; static double safmin, eps, tol; static long n0in, ipn4; static double tol2; --z__; /* Function Body */ n0in = *n0; eps = NUMblas_dlamch ("Precision"); safmin = NUMblas_dlamch ("Safe minimum"); tol = eps * 100.; /* Computing 2nd power */ d__1 = tol; tol2 = d__1 * d__1; /* Check for deflation. */ L10: if (*n0 < *i0) { return 0; } if (*n0 == *i0) { goto L20; } nn = (*n0 << 2) + *pp; if (*n0 == *i0 + 1) { goto L40; } /* Check whether E(N0-1) is negligible, 1 eigenvalue. */ if (z__[nn - 5] > tol2 * (*sigma + z__[nn - 3]) && z__[nn - (*pp << 1) - 4] > tol2 * z__[nn - 7]) { goto L30; } L20: z__[ (*n0 << 2) - 3] = z__[ (*n0 << 2) + *pp - 3] + *sigma; -- (*n0); goto L10; /* Check whether E(N0-2) is negligible, 2 eigenvalues. */ L30: if (z__[nn - 9] > tol2 * *sigma && z__[nn - (*pp << 1) - 8] > tol2 * z__[nn - 11]) { goto L50; } L40: if (z__[nn - 3] > z__[nn - 7]) { s = z__[nn - 3]; z__[nn - 3] = z__[nn - 7]; z__[nn - 7] = s; } if (z__[nn - 5] > z__[nn - 3] * tol2) { t = (z__[nn - 7] - z__[nn - 3] + z__[nn - 5]) * .5; s = z__[nn - 3] * (z__[nn - 5] / t); if (s <= t) { s = z__[nn - 3] * (z__[nn - 5] / (t * (sqrt (s / t + 1.) + 1.))); } else { s = z__[nn - 3] * (z__[nn - 5] / (t + sqrt (t) * sqrt (t + s))); } t = z__[nn - 7] + (s + z__[nn - 5]); z__[nn - 3] *= z__[nn - 7] / t; z__[nn - 7] = t; } z__[ (*n0 << 2) - 7] = z__[nn - 7] + *sigma; z__[ (*n0 << 2) - 3] = z__[nn - 3] + *sigma; *n0 += -2; goto L10; L50: /* Reverse the qd-array, if warranted. */ if (*dmin__ <= 0. || *n0 < n0in) { if (z__[ (*i0 << 2) + *pp - 3] * 1.5 < z__[ (*n0 << 2) + *pp - 3]) { ipn4 = *i0 + *n0 << 2; i__1 = *i0 + *n0 - 1 << 1; for (j4 = *i0 << 2; j4 <= i__1; j4 += 4) { temp = z__[j4 - 3]; z__[j4 - 3] = z__[ipn4 - j4 - 3]; z__[ipn4 - j4 - 3] = temp; temp = z__[j4 - 2]; z__[j4 - 2] = z__[ipn4 - j4 - 2]; z__[ipn4 - j4 - 2] = temp; temp = z__[j4 - 1]; z__[j4 - 1] = z__[ipn4 - j4 - 5]; z__[ipn4 - j4 - 5] = temp; temp = z__[j4]; z__[j4] = z__[ipn4 - j4 - 4]; z__[ipn4 - j4 - 4] = temp; /* L60: */ } if (*n0 - *i0 <= 4) { z__[ (*n0 << 2) + *pp - 1] = z__[ (*i0 << 2) + *pp - 1]; z__[ (*n0 << 2) - *pp] = z__[ (*i0 << 2) - *pp]; } /* Computing MIN */ d__1 = dmin2, d__2 = z__[ (*n0 << 2) + *pp - 1]; dmin2 = MIN (d__1, d__2); /* Computing MIN */ d__1 = z__[ (*n0 << 2) + *pp - 1], d__2 = z__[ (*i0 << 2) + *pp - 1], d__1 = MIN (d__1, d__2), d__2 = z__[ (*i0 << 2) + *pp + 3]; z__[ (*n0 << 2) + *pp - 1] = MIN (d__1, d__2); /* Computing MIN */ d__1 = z__[ (*n0 << 2) - *pp], d__2 = z__[ (*i0 << 2) - *pp], d__1 = MIN (d__1, d__2), d__2 = z__[ (*i0 << 2) - *pp + 4]; z__[ (*n0 << 2) - *pp] = MIN (d__1, d__2); /* Computing MAX */ d__1 = *qmax, d__2 = z__[ (*i0 << 2) + *pp - 3], d__1 = MAX (d__1, d__2), d__2 = z__[ (*i0 << 2) + *pp + 1]; *qmax = MAX (d__1, d__2); *dmin__ = 0.; } } /* L70: Computing MIN */ d__1 = z__[ (*n0 << 2) + *pp - 1], d__2 = z__[ (*n0 << 2) + *pp - 9], d__1 = MIN (d__1, d__2), d__2 = dmin2 + z__[ (*n0 << 2) - *pp]; if (*dmin__ < 0. || safmin * *qmax < MIN (d__1, d__2)) { /* Choose a shift. */ NUMlapack_dlasq4 (i0, n0, &z__[1], pp, &n0in, dmin__, &dmin1, &dmin2, &dn, &dn1, &dn2, &tau, &ttype); /* Call dqds until DMIN > 0. */ L80: NUMlapack_dlasq5 (i0, n0, &z__[1], pp, &tau, dmin__, &dmin1, &dmin2, &dn, &dn1, &dn2, ieee); *ndiv += *n0 - *i0 + 2; ++ (*iter); /* Check status. */ if (*dmin__ >= 0. && dmin1 > 0.) { /* Success. */ goto L100; } else if (*dmin__ < 0. && dmin1 > 0. && z__[ (*n0 - 1 << 2) - *pp] < tol * (*sigma + dn1) && fabs (dn) < tol * *sigma) { /* Convergence hidden by negative DN. */ z__[ (*n0 - 1 << 2) - *pp + 2] = 0.; *dmin__ = 0.; goto L100; } else if (*dmin__ < 0.) { /* TAU too big. Select new TAU and try again. */ ++ (*nfail); if (ttype < -22) { /* Failed twice. Play it safe. */ tau = 0.; } else if (dmin1 > 0.) { /* Late failure. Gives excellent shift. */ tau = (tau + *dmin__) * (1. - eps * 2.); ttype += -11; } else { /* Early failure. Divide by 4. */ tau *= .25; ttype += -12; } goto L80; } else if (*dmin__ != *dmin__) { /* NaN. */ tau = 0.; goto L80; } else { /* Possible underflow. Play it safe. */ goto L90; } } /* Risk of underflow. */ L90: NUMlapack_dlasq6 (i0, n0, &z__[1], pp, dmin__, &dmin1, &dmin2, &dn, &dn1, &dn2); *ndiv += *n0 - *i0 + 2; ++ (*iter); tau = 0.; L100: if (tau < *sigma) { *desig += tau; t = *sigma + *desig; *desig -= t - *sigma; } else { t = *sigma + tau; *desig = *sigma - (t - tau) + *desig; } *sigma = t; return 0; } /* NUMlapack_dlasq3 */ int NUMlapack_dlasq4 (long *i0, long *n0, double *z__, long *pp, long *n0in, double *dmin__, double *dmin1, double *dmin2, double *dn, double *dn1, double *dn2, double *tau, long *ttype) { /* Initialized data */ static double g = 0.; /* System generated locals */ long i__1; double d__1, d__2; /* Local variables */ static double s, a2, b1, b2; static long i4, nn, np; static double gam, gap1, gap2; /* Parameter adjustments */ --z__; /* Function Body A negative DMIN forces the shift to take that absolute value TTYPE records the type of shift. */ if (*dmin__ <= 0.) { *tau = - (*dmin__); *ttype = -1; return 0; } nn = (*n0 << 2) + *pp; if (*n0in == *n0) { /* No eigenvalues deflated. */ if (*dmin__ == *dn || *dmin__ == *dn1) { b1 = sqrt (z__[nn - 3]) * sqrt (z__[nn - 5]); b2 = sqrt (z__[nn - 7]) * sqrt (z__[nn - 9]); a2 = z__[nn - 7] + z__[nn - 5]; /* Cases 2 and 3. */ if (*dmin__ == *dn && *dmin1 == *dn1) { gap2 = *dmin2 - a2 - *dmin2 * .25; if (gap2 > 0. && gap2 > b2) { gap1 = a2 - *dn - b2 / gap2 * b2; } else { gap1 = a2 - *dn - (b1 + b2); } if (gap1 > 0. && gap1 > b1) { /* Computing MAX */ d__1 = *dn - b1 / gap1 * b1, d__2 = *dmin__ * .5; s = MAX (d__1, d__2); *ttype = -2; } else { s = 0.; if (*dn > b1) { s = *dn - b1; } if (a2 > b1 + b2) { /* Computing MIN */ d__1 = s, d__2 = a2 - (b1 + b2); s = MIN (d__1, d__2); } /* Computing MAX */ d__1 = s, d__2 = *dmin__ * .333; s = MAX (d__1, d__2); *ttype = -3; } } else { /* Case 4. */ *ttype = -4; s = *dmin__ * .25; if (*dmin__ == *dn) { gam = *dn; a2 = 0.; if (z__[nn - 5] > z__[nn - 7]) { return 0; } b2 = z__[nn - 5] / z__[nn - 7]; np = nn - 9; } else { np = nn - (*pp << 1); b2 = z__[np - 2]; gam = *dn1; if (z__[np - 4] > z__[np - 2]) { return 0; } a2 = z__[np - 4] / z__[np - 2]; if (z__[nn - 9] > z__[nn - 11]) { return 0; } b2 = z__[nn - 9] / z__[nn - 11]; np = nn - 13; } /* Approximate contribution to norm squared from I < NN-1. */ a2 += b2; i__1 = (*i0 << 2) - 1 + *pp; for (i4 = np; i4 >= i__1; i4 += -4) { if (b2 == 0.) { goto L20; } b1 = b2; if (z__[i4] > z__[i4 - 2]) { return 0; } b2 *= z__[i4] / z__[i4 - 2]; a2 += b2; if (MAX (b2, b1) * 100. < a2 || .563 < a2) { goto L20; } /* L10: */ } L20: a2 *= 1.05; /* Rayleigh quotient residual bound. */ if (a2 < .563) { s = gam * (1. - sqrt (a2)) / (a2 + 1.); } } } else if (*dmin__ == *dn2) { /* Case 5. */ *ttype = -5; s = *dmin__ * .25; /* Compute contribution to norm squared from I > NN-2. */ np = nn - (*pp << 1); b1 = z__[np - 2]; b2 = z__[np - 6]; gam = *dn2; if (z__[np - 8] > b2 || z__[np - 4] > b1) { return 0; } a2 = z__[np - 8] / b2 * (z__[np - 4] / b1 + 1.); /* Approximate contribution to norm squared from I < NN-2. */ if (*n0 - *i0 > 2) { b2 = z__[nn - 13] / z__[nn - 15]; a2 += b2; i__1 = (*i0 << 2) - 1 + *pp; for (i4 = nn - 17; i4 >= i__1; i4 += -4) { if (b2 == 0.) { goto L40; } b1 = b2; if (z__[i4] > z__[i4 - 2]) { return 0; } b2 *= z__[i4] / z__[i4 - 2]; a2 += b2; if (MAX (b2, b1) * 100. < a2 || .563 < a2) { goto L40; } /* L30: */ } L40: a2 *= 1.05; } if (a2 < .563) { s = gam * (1. - sqrt (a2)) / (a2 + 1.); } } else { /* Case 6, no information to guide us. */ if (*ttype == -6) { g += (1. - g) * .333; } else if (*ttype == -18) { g = .083250000000000005; } else { g = .25; } s = g * *dmin__; *ttype = -6; } } else if (*n0in == *n0 + 1) { /* One eigenvalue just deflated. Use DMIN1, DN1 for DMIN and DN. */ if (*dmin1 == *dn1 && *dmin2 == *dn2) { /* Cases 7 and 8. */ *ttype = -7; s = *dmin1 * .333; if (z__[nn - 5] > z__[nn - 7]) { return 0; } b1 = z__[nn - 5] / z__[nn - 7]; b2 = b1; if (b2 == 0.) { goto L60; } i__1 = (*i0 << 2) - 1 + *pp; for (i4 = (*n0 << 2) - 9 + *pp; i4 >= i__1; i4 += -4) { a2 = b1; if (z__[i4] > z__[i4 - 2]) { return 0; } b1 *= z__[i4] / z__[i4 - 2]; b2 += b1; if (MAX (b1, a2) * 100. < b2) { goto L60; } /* L50: */ } L60: b2 = sqrt (b2 * 1.05); /* Computing 2nd power */ d__1 = b2; a2 = *dmin1 / (d__1 * d__1 + 1.); gap2 = *dmin2 * .5 - a2; if (gap2 > 0. && gap2 > b2 * a2) { /* Computing MAX */ d__1 = s, d__2 = a2 * (1. - a2 * 1.01 * (b2 / gap2) * b2); s = MAX (d__1, d__2); } else { /* Computing MAX */ d__1 = s, d__2 = a2 * (1. - b2 * 1.01); s = MAX (d__1, d__2); *ttype = -8; } } else { /* Case 9. */ s = *dmin1 * .25; if (*dmin1 == *dn1) { s = *dmin1 * .5; } *ttype = -9; } } else if (*n0in == *n0 + 2) { /* Two eigenvalues deflated. Use DMIN2, DN2 for DMIN and DN. Cases 10 and 11. */ if (*dmin2 == *dn2 && z__[nn - 5] * 2. < z__[nn - 7]) { *ttype = -10; s = *dmin2 * .333; if (z__[nn - 5] > z__[nn - 7]) { return 0; } b1 = z__[nn - 5] / z__[nn - 7]; b2 = b1; if (b2 == 0.) { goto L80; } i__1 = (*i0 << 2) - 1 + *pp; for (i4 = (*n0 << 2) - 9 + *pp; i4 >= i__1; i4 += -4) { if (z__[i4] > z__[i4 - 2]) { return 0; } b1 *= z__[i4] / z__[i4 - 2]; b2 += b1; if (b1 * 100. < b2) { goto L80; } /* L70: */ } L80: b2 = sqrt (b2 * 1.05); /* Computing 2nd power */ d__1 = b2; a2 = *dmin2 / (d__1 * d__1 + 1.); gap2 = z__[nn - 7] + z__[nn - 9] - sqrt (z__[nn - 11]) * sqrt (z__[nn - 9]) - a2; if (gap2 > 0. && gap2 > b2 * a2) { /* Computing MAX */ d__1 = s, d__2 = a2 * (1. - a2 * 1.01 * (b2 / gap2) * b2); s = MAX (d__1, d__2); } else { /* Computing MAX */ d__1 = s, d__2 = a2 * (1. - b2 * 1.01); s = MAX (d__1, d__2); } } else { s = *dmin2 * .25; *ttype = -11; } } else if (*n0in > *n0 + 2) { /* Case 12, more than two eigenvalues deflated. No information. */ s = 0.; *ttype = -12; } *tau = s; return 0; } /* NUMlapack_dlasq4 */ int NUMlapack_dlasq5 (long *i0, long *n0, double *z__, long *pp, double *tau, double *dmin__, double *dmin1, double *dmin2, double *dn, double *dnm1, double *dnm2, long *ieee) { /* System generated locals */ long i__1; double d__1, d__2; /* Local variables */ static double emin, temp, d__; static long j4, j4p2; --z__; /* Function Body */ if (*n0 - *i0 - 1 <= 0) { return 0; } j4 = (*i0 << 2) + *pp - 3; emin = z__[j4 + 4]; d__ = z__[j4] - *tau; *dmin__ = d__; *dmin1 = -z__[j4]; if (*ieee) { /* Code for IEEE arithmetic. */ if (*pp == 0) { i__1 = *n0 - 3 << 2; for (j4 = *i0 << 2; j4 <= i__1; j4 += 4) { z__[j4 - 2] = d__ + z__[j4 - 1]; temp = z__[j4 + 1] / z__[j4 - 2]; d__ = d__ * temp - *tau; *dmin__ = MIN (*dmin__, d__); z__[j4] = z__[j4 - 1] * temp; /* Computing MIN */ d__1 = z__[j4]; emin = MIN (d__1, emin); /* L10: */ } } else { i__1 = *n0 - 3 << 2; for (j4 = *i0 << 2; j4 <= i__1; j4 += 4) { z__[j4 - 3] = d__ + z__[j4]; temp = z__[j4 + 2] / z__[j4 - 3]; d__ = d__ * temp - *tau; *dmin__ = MIN (*dmin__, d__); z__[j4 - 1] = z__[j4] * temp; /* Computing MIN */ d__1 = z__[j4 - 1]; emin = MIN (d__1, emin); /* L20: */ } } /* Unroll last two steps. */ *dnm2 = d__; *dmin2 = *dmin__; j4 = (*n0 - 2 << 2) - *pp; j4p2 = j4 + (*pp << 1) - 1; z__[j4 - 2] = *dnm2 + z__[j4p2]; z__[j4] = z__[j4p2 + 2] * (z__[j4p2] / z__[j4 - 2]); *dnm1 = z__[j4p2 + 2] * (*dnm2 / z__[j4 - 2]) - *tau; *dmin__ = MIN (*dmin__, *dnm1); *dmin1 = *dmin__; j4 += 4; j4p2 = j4 + (*pp << 1) - 1; z__[j4 - 2] = *dnm1 + z__[j4p2]; z__[j4] = z__[j4p2 + 2] * (z__[j4p2] / z__[j4 - 2]); *dn = z__[j4p2 + 2] * (*dnm1 / z__[j4 - 2]) - *tau; *dmin__ = MIN (*dmin__, *dn); } else { /* Code for non IEEE arithmetic. */ if (*pp == 0) { i__1 = *n0 - 3 << 2; for (j4 = *i0 << 2; j4 <= i__1; j4 += 4) { z__[j4 - 2] = d__ + z__[j4 - 1]; if (d__ < 0.) { return 0; } else { z__[j4] = z__[j4 + 1] * (z__[j4 - 1] / z__[j4 - 2]); d__ = z__[j4 + 1] * (d__ / z__[j4 - 2]) - *tau; } *dmin__ = MIN (*dmin__, d__); /* Computing MIN */ d__1 = emin, d__2 = z__[j4]; emin = MIN (d__1, d__2); /* L30: */ } } else { i__1 = *n0 - 3 << 2; for (j4 = *i0 << 2; j4 <= i__1; j4 += 4) { z__[j4 - 3] = d__ + z__[j4]; if (d__ < 0.) { return 0; } else { z__[j4 - 1] = z__[j4 + 2] * (z__[j4] / z__[j4 - 3]); d__ = z__[j4 + 2] * (d__ / z__[j4 - 3]) - *tau; } *dmin__ = MIN (*dmin__, d__); /* Computing MIN */ d__1 = emin, d__2 = z__[j4 - 1]; emin = MIN (d__1, d__2); /* L40: */ } } /* Unroll last two steps. */ *dnm2 = d__; *dmin2 = *dmin__; j4 = (*n0 - 2 << 2) - *pp; j4p2 = j4 + (*pp << 1) - 1; z__[j4 - 2] = *dnm2 + z__[j4p2]; if (*dnm2 < 0.) { return 0; } else { z__[j4] = z__[j4p2 + 2] * (z__[j4p2] / z__[j4 - 2]); *dnm1 = z__[j4p2 + 2] * (*dnm2 / z__[j4 - 2]) - *tau; } *dmin__ = MIN (*dmin__, *dnm1); *dmin1 = *dmin__; j4 += 4; j4p2 = j4 + (*pp << 1) - 1; z__[j4 - 2] = *dnm1 + z__[j4p2]; if (*dnm1 < 0.) { return 0; } else { z__[j4] = z__[j4p2 + 2] * (z__[j4p2] / z__[j4 - 2]); *dn = z__[j4p2 + 2] * (*dnm1 / z__[j4 - 2]) - *tau; } *dmin__ = MIN (*dmin__, *dn); } z__[j4 + 2] = *dn; z__[ (*n0 << 2) - *pp] = emin; return 0; } /* NUMlapack_dlasq5 */ int NUMlapack_dlasq6 (long *i0, long *n0, double *z__, long *pp, double *dmin__, double *dmin1, double *dmin2, double *dn, double *dnm1, double *dnm2) { /* System generated locals */ long i__1; double d__1, d__2; /* Local variables */ static double emin, temp, d__; static long j4; static double safmin; static long j4p2; /* Parameter adjustments */ --z__; /* Function Body */ if (*n0 - *i0 - 1 <= 0) { return 0; } safmin = NUMblas_dlamch ("Safe minimum"); j4 = (*i0 << 2) + *pp - 3; emin = z__[j4 + 4]; d__ = z__[j4]; *dmin__ = d__; if (*pp == 0) { i__1 = *n0 - 3 << 2; for (j4 = *i0 << 2; j4 <= i__1; j4 += 4) { z__[j4 - 2] = d__ + z__[j4 - 1]; if (z__[j4 - 2] == 0.) { z__[j4] = 0.; d__ = z__[j4 + 1]; *dmin__ = d__; emin = 0.; } else if (safmin * z__[j4 + 1] < z__[j4 - 2] && safmin * z__[j4 - 2] < z__[j4 + 1]) { temp = z__[j4 + 1] / z__[j4 - 2]; z__[j4] = z__[j4 - 1] * temp; d__ *= temp; } else { z__[j4] = z__[j4 + 1] * (z__[j4 - 1] / z__[j4 - 2]); d__ = z__[j4 + 1] * (d__ / z__[j4 - 2]); } *dmin__ = MIN (*dmin__, d__); /* Computing MIN */ d__1 = emin, d__2 = z__[j4]; emin = MIN (d__1, d__2); /* L10: */ } } else { i__1 = *n0 - 3 << 2; for (j4 = *i0 << 2; j4 <= i__1; j4 += 4) { z__[j4 - 3] = d__ + z__[j4]; if (z__[j4 - 3] == 0.) { z__[j4 - 1] = 0.; d__ = z__[j4 + 2]; *dmin__ = d__; emin = 0.; } else if (safmin * z__[j4 + 2] < z__[j4 - 3] && safmin * z__[j4 - 3] < z__[j4 + 2]) { temp = z__[j4 + 2] / z__[j4 - 3]; z__[j4 - 1] = z__[j4] * temp; d__ *= temp; } else { z__[j4 - 1] = z__[j4 + 2] * (z__[j4] / z__[j4 - 3]); d__ = z__[j4 + 2] * (d__ / z__[j4 - 3]); } *dmin__ = MIN (*dmin__, d__); /* Computing MIN */ d__1 = emin, d__2 = z__[j4 - 1]; emin = MIN (d__1, d__2); /* L20: */ } } /* Unroll last two steps. */ *dnm2 = d__; *dmin2 = *dmin__; j4 = (*n0 - 2 << 2) - *pp; j4p2 = j4 + (*pp << 1) - 1; z__[j4 - 2] = *dnm2 + z__[j4p2]; if (z__[j4 - 2] == 0.) { z__[j4] = 0.; *dnm1 = z__[j4p2 + 2]; *dmin__ = *dnm1; emin = 0.; } else if (safmin * z__[j4p2 + 2] < z__[j4 - 2] && safmin * z__[j4 - 2] < z__[j4p2 + 2]) { temp = z__[j4p2 + 2] / z__[j4 - 2]; z__[j4] = z__[j4p2] * temp; *dnm1 = *dnm2 * temp; } else { z__[j4] = z__[j4p2 + 2] * (z__[j4p2] / z__[j4 - 2]); *dnm1 = z__[j4p2 + 2] * (*dnm2 / z__[j4 - 2]); } *dmin__ = MIN (*dmin__, *dnm1); *dmin1 = *dmin__; j4 += 4; j4p2 = j4 + (*pp << 1) - 1; z__[j4 - 2] = *dnm1 + z__[j4p2]; if (z__[j4 - 2] == 0.) { z__[j4] = 0.; *dn = z__[j4p2 + 2]; *dmin__ = *dn; emin = 0.; } else if (safmin * z__[j4p2 + 2] < z__[j4 - 2] && safmin * z__[j4 - 2] < z__[j4p2 + 2]) { temp = z__[j4p2 + 2] / z__[j4 - 2]; z__[j4] = z__[j4p2] * temp; *dn = *dnm1 * temp; } else { z__[j4] = z__[j4p2 + 2] * (z__[j4p2] / z__[j4 - 2]); *dn = z__[j4p2 + 2] * (*dnm1 / z__[j4 - 2]); } *dmin__ = MIN (*dmin__, *dn); z__[j4 + 2] = *dn; z__[ (*n0 << 2) - *pp] = emin; return 0; } /* NUMlapack_dlasq6 */ int NUMlapack_dlasr (const char *side, const char *pivot, const char *direct, long *m, long *n, double *c__, double *s, double *a, long *lda) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2; /* Local variables */ static long info; static double temp; static long i__, j; static double ctemp, stemp; --c__; --s; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; /* Function Body */ info = 0; if (! (lsame_ (side, "L") || lsame_ (side, "R"))) { info = 1; } else if (! (lsame_ (pivot, "V") || lsame_ (pivot, "T") || lsame_ (pivot, "B"))) { info = 2; } else if (! (lsame_ (direct, "F") || lsame_ (direct, "B"))) { info = 3; } else if (*m < 0) { info = 4; } else if (*n < 0) { info = 5; } else if (*lda < MAX (1, *m)) { info = 9; } if (info != 0) { xerbla_ ("DLASR ", &info); return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0) { return 0; } if (lsame_ (side, "L")) { /* Form P * A */ if (lsame_ (pivot, "V")) { if (lsame_ (direct, "F")) { i__1 = *m - 1; for (j = 1; j <= i__1; ++j) { ctemp = c__[j]; stemp = s[j]; if (ctemp != 1. || stemp != 0.) { i__2 = *n; for (i__ = 1; i__ <= i__2; ++i__) { temp = a_ref (j + 1, i__); a_ref (j + 1, i__) = ctemp * temp - stemp * a_ref (j, i__); a_ref (j, i__) = stemp * temp + ctemp * a_ref (j, i__); /* L10: */ } } /* L20: */ } } else if (lsame_ (direct, "B")) { for (j = *m - 1; j >= 1; --j) { ctemp = c__[j]; stemp = s[j]; if (ctemp != 1. || stemp != 0.) { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { temp = a_ref (j + 1, i__); a_ref (j + 1, i__) = ctemp * temp - stemp * a_ref (j, i__); a_ref (j, i__) = stemp * temp + ctemp * a_ref (j, i__); /* L30: */ } } /* L40: */ } } } else if (lsame_ (pivot, "T")) { if (lsame_ (direct, "F")) { i__1 = *m; for (j = 2; j <= i__1; ++j) { ctemp = c__[j - 1]; stemp = s[j - 1]; if (ctemp != 1. || stemp != 0.) { i__2 = *n; for (i__ = 1; i__ <= i__2; ++i__) { temp = a_ref (j, i__); a_ref (j, i__) = ctemp * temp - stemp * a_ref (1, i__); a_ref (1, i__) = stemp * temp + ctemp * a_ref (1, i__); /* L50: */ } } /* L60: */ } } else if (lsame_ (direct, "B")) { for (j = *m; j >= 2; --j) { ctemp = c__[j - 1]; stemp = s[j - 1]; if (ctemp != 1. || stemp != 0.) { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { temp = a_ref (j, i__); a_ref (j, i__) = ctemp * temp - stemp * a_ref (1, i__); a_ref (1, i__) = stemp * temp + ctemp * a_ref (1, i__); /* L70: */ } } /* L80: */ } } } else if (lsame_ (pivot, "B")) { if (lsame_ (direct, "F")) { i__1 = *m - 1; for (j = 1; j <= i__1; ++j) { ctemp = c__[j]; stemp = s[j]; if (ctemp != 1. || stemp != 0.) { i__2 = *n; for (i__ = 1; i__ <= i__2; ++i__) { temp = a_ref (j, i__); a_ref (j, i__) = stemp * a_ref (*m, i__) + ctemp * temp; a_ref (*m, i__) = ctemp * a_ref (*m, i__) - stemp * temp; /* L90: */ } } /* L100: */ } } else if (lsame_ (direct, "B")) { for (j = *m - 1; j >= 1; --j) { ctemp = c__[j]; stemp = s[j]; if (ctemp != 1. || stemp != 0.) { i__1 = *n; for (i__ = 1; i__ <= i__1; ++i__) { temp = a_ref (j, i__); a_ref (j, i__) = stemp * a_ref (*m, i__) + ctemp * temp; a_ref (*m, i__) = ctemp * a_ref (*m, i__) - stemp * temp; /* L110: */ } } /* L120: */ } } } } else if (lsame_ (side, "R")) { /* Form A * P' */ if (lsame_ (pivot, "V")) { if (lsame_ (direct, "F")) { i__1 = *n - 1; for (j = 1; j <= i__1; ++j) { ctemp = c__[j]; stemp = s[j]; if (ctemp != 1. || stemp != 0.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { temp = a_ref (i__, j + 1); a_ref (i__, j + 1) = ctemp * temp - stemp * a_ref (i__, j); a_ref (i__, j) = stemp * temp + ctemp * a_ref (i__, j); /* L130: */ } } /* L140: */ } } else if (lsame_ (direct, "B")) { for (j = *n - 1; j >= 1; --j) { ctemp = c__[j]; stemp = s[j]; if (ctemp != 1. || stemp != 0.) { i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { temp = a_ref (i__, j + 1); a_ref (i__, j + 1) = ctemp * temp - stemp * a_ref (i__, j); a_ref (i__, j) = stemp * temp + ctemp * a_ref (i__, j); /* L150: */ } } /* L160: */ } } } else if (lsame_ (pivot, "T")) { if (lsame_ (direct, "F")) { i__1 = *n; for (j = 2; j <= i__1; ++j) { ctemp = c__[j - 1]; stemp = s[j - 1]; if (ctemp != 1. || stemp != 0.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { temp = a_ref (i__, j); a_ref (i__, j) = ctemp * temp - stemp * a_ref (i__, 1); a_ref (i__, 1) = stemp * temp + ctemp * a_ref (i__, 1); /* L170: */ } } /* L180: */ } } else if (lsame_ (direct, "B")) { for (j = *n; j >= 2; --j) { ctemp = c__[j - 1]; stemp = s[j - 1]; if (ctemp != 1. || stemp != 0.) { i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { temp = a_ref (i__, j); a_ref (i__, j) = ctemp * temp - stemp * a_ref (i__, 1); a_ref (i__, 1) = stemp * temp + ctemp * a_ref (i__, 1); /* L190: */ } } /* L200: */ } } } else if (lsame_ (pivot, "B")) { if (lsame_ (direct, "F")) { i__1 = *n - 1; for (j = 1; j <= i__1; ++j) { ctemp = c__[j]; stemp = s[j]; if (ctemp != 1. || stemp != 0.) { i__2 = *m; for (i__ = 1; i__ <= i__2; ++i__) { temp = a_ref (i__, j); a_ref (i__, j) = stemp * a_ref (i__, *n) + ctemp * temp; a_ref (i__, *n) = ctemp * a_ref (i__, *n) - stemp * temp; /* L210: */ } } /* L220: */ } } else if (lsame_ (direct, "B")) { for (j = *n - 1; j >= 1; --j) { ctemp = c__[j]; stemp = s[j]; if (ctemp != 1. || stemp != 0.) { i__1 = *m; for (i__ = 1; i__ <= i__1; ++i__) { temp = a_ref (i__, j); a_ref (i__, j) = stemp * a_ref (i__, *n) + ctemp * temp; a_ref (i__, *n) = ctemp * a_ref (i__, *n) - stemp * temp; /* L230: */ } } /* L240: */ } } } } return 0; } /* NUMlapack_dlasr */ #define stack_ref(a_1,a_2) stack[(a_2)*2 + a_1 - 3] int NUMlapack_dlasrt (const char *id, long *n, double *d__, long *info) { /* System generated locals */ long i__1, i__2; /* Local variables */ static long endd, i__, j; static long stack[64] /* was [2][32] */ ; static double dmnmx, d1, d2, d3; static long start; static long stkpnt, dir; static double tmp; --d__; /* Function Body */ *info = 0; dir = -1; if (lsame_ (id, "D")) { dir = 0; } else if (lsame_ (id, "I")) { dir = 1; } if (dir == -1) { *info = -1; } else if (*n < 0) { *info = -2; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DLASRT", &i__1); return 0; } /* Quick return if possible */ if (*n <= 1) { return 0; } stkpnt = 1; stack_ref (1, 1) = 1; stack_ref (2, 1) = *n; L10: start = stack_ref (1, stkpnt); endd = stack_ref (2, stkpnt); --stkpnt; if (endd - start <= 20 && endd - start > 0) { /* Do Insertion sort on D( START:ENDD ) */ if (dir == 0) { /* Sort into decreasing order */ i__1 = endd; for (i__ = start + 1; i__ <= i__1; ++i__) { i__2 = start + 1; for (j = i__; j >= i__2; --j) { if (d__[j] > d__[j - 1]) { dmnmx = d__[j]; d__[j] = d__[j - 1]; d__[j - 1] = dmnmx; } else { goto L30; } /* L20: */ } L30: ; } } else { /* Sort into increasing order */ i__1 = endd; for (i__ = start + 1; i__ <= i__1; ++i__) { i__2 = start + 1; for (j = i__; j >= i__2; --j) { if (d__[j] < d__[j - 1]) { dmnmx = d__[j]; d__[j] = d__[j - 1]; d__[j - 1] = dmnmx; } else { goto L50; } /* L40: */ } L50: ; } } } else if (endd - start > 20) { /* Partition D( START:ENDD ) and stack parts, largest one first Choose partition entry as median of 3 */ d1 = d__[start]; d2 = d__[endd]; i__ = (start + endd) / 2; d3 = d__[i__]; if (d1 < d2) { if (d3 < d1) { dmnmx = d1; } else if (d3 < d2) { dmnmx = d3; } else { dmnmx = d2; } } else { if (d3 < d2) { dmnmx = d2; } else if (d3 < d1) { dmnmx = d3; } else { dmnmx = d1; } } if (dir == 0) { /* Sort into decreasing order */ i__ = start - 1; j = endd + 1; L60: L70: --j; if (d__[j] < dmnmx) { goto L70; } L80: ++i__; if (d__[i__] > dmnmx) { goto L80; } if (i__ < j) { tmp = d__[i__]; d__[i__] = d__[j]; d__[j] = tmp; goto L60; } if (j - start > endd - j - 1) { ++stkpnt; stack_ref (1, stkpnt) = start; stack_ref (2, stkpnt) = j; ++stkpnt; stack_ref (1, stkpnt) = j + 1; stack_ref (2, stkpnt) = endd; } else { ++stkpnt; stack_ref (1, stkpnt) = j + 1; stack_ref (2, stkpnt) = endd; ++stkpnt; stack_ref (1, stkpnt) = start; stack_ref (2, stkpnt) = j; } } else { /* Sort into increasing order */ i__ = start - 1; j = endd + 1; L90: L100: --j; if (d__[j] > dmnmx) { goto L100; } L110: ++i__; if (d__[i__] < dmnmx) { goto L110; } if (i__ < j) { tmp = d__[i__]; d__[i__] = d__[j]; d__[j] = tmp; goto L90; } if (j - start > endd - j - 1) { ++stkpnt; stack_ref (1, stkpnt) = start; stack_ref (2, stkpnt) = j; ++stkpnt; stack_ref (1, stkpnt) = j + 1; stack_ref (2, stkpnt) = endd; } else { ++stkpnt; stack_ref (1, stkpnt) = j + 1; stack_ref (2, stkpnt) = endd; ++stkpnt; stack_ref (1, stkpnt) = start; stack_ref (2, stkpnt) = j; } } } if (stkpnt > 0) { goto L10; } return 0; } /* NUMlapack_dlasrt */ #undef stack_ref int NUMlapack_dlassq (long *n, double *x, long *incx, double *scale, double *sumsq) { /* System generated locals */ long i__1, i__2; double d__1; /* Local variables */ static double absxi; static long ix; --x; /* Function Body */ if (*n > 0) { i__1 = (*n - 1) * *incx + 1; i__2 = *incx; for (ix = 1; i__2 < 0 ? ix >= i__1 : ix <= i__1; ix += i__2) { if (x[ix] != 0.) { absxi = (d__1 = x[ix], fabs (d__1)); if (*scale < absxi) { /* Computing 2nd power */ d__1 = *scale / absxi; *sumsq = *sumsq * (d__1 * d__1) + 1; *scale = absxi; } else { /* Computing 2nd power */ d__1 = absxi / *scale; *sumsq += d__1 * d__1; } } /* L10: */ } } return 0; } /* NUMlapack_dlassq */ int NUMlapack_dlasv2 (double *f, double *g, double *h__, double *ssmin, double *ssmax, double *snr, double *csr, double *snl, double *csl) { /* Table of constant values */ static double c_b3 = 2.; static double c_b4 = 1.; /* System generated locals */ double d__1; /* Local variables */ static long pmax; static double temp; static long swap; static double a, d__, l, m, r__, s, t, tsign, fa, ga, ha; static double ft, gt, ht, mm; static long gasmal; static double tt, clt, crt, slt, srt; ft = *f; fa = fabs (ft); ht = *h__; ha = fabs (*h__); /* PMAX points to the maximum absolute element of matrix PMAX = 1 if F largest in absolute values PMAX = 2 if G largest in absolute values PMAX = 3 if H largest in absolute values */ pmax = 1; swap = ha > fa; if (swap) { pmax = 3; temp = ft; ft = ht; ht = temp; temp = fa; fa = ha; ha = temp; /* Now FA .ge. HA */ } gt = *g; ga = fabs (gt); if (ga == 0.) { /* Diagonal matrix */ *ssmin = ha; *ssmax = fa; clt = 1.; crt = 1.; slt = 0.; srt = 0.; } else { gasmal = TRUE; if (ga > fa) { pmax = 2; if (fa / ga < NUMblas_dlamch ("EPS")) { /* Case of very large GA */ gasmal = FALSE; *ssmax = ga; if (ha > 1.) { *ssmin = fa / (ga / ha); } else { *ssmin = fa / ga * ha; } clt = 1.; slt = ht / gt; srt = 1.; crt = ft / gt; } } if (gasmal) { /* Normal case */ d__ = fa - ha; if (d__ == fa) { /* Copes with infinite F or H */ l = 1.; } else { l = d__ / fa; } /* Note that 0 .le. L .le. 1 */ m = gt / ft; /* Note that abs(M) .le. 1/macheps */ t = 2. - l; /* Note that T .ge. 1 */ mm = m * m; tt = t * t; s = sqrt (tt + mm); /* Note that 1 .le. S .le. 1 + 1/macheps */ if (l == 0.) { r__ = fabs (m); } else { r__ = sqrt (l * l + mm); } /* Note that 0 .le. R .le. 1 + 1/macheps */ a = (s + r__) * .5; /* Note that 1 .le. A .le. 1 + abs(M) */ *ssmin = ha / a; *ssmax = fa * a; if (mm == 0.) { /* Note that M is very tiny */ if (l == 0.) { t = d_sign (&c_b3, &ft) * d_sign (&c_b4, >); } else { t = gt / d_sign (&d__, &ft) + m / t; } } else { t = (m / (s + t) + m / (r__ + l)) * (a + 1.); } l = sqrt (t * t + 4.); crt = 2. / l; srt = t / l; clt = (crt + srt * m) / a; slt = ht / ft * srt / a; } } if (swap) { *csl = srt; *snl = crt; *csr = slt; *snr = clt; } else { *csl = clt; *snl = slt; *csr = crt; *snr = srt; } /* Correct signs of SSMAX and SSMIN */ if (pmax == 1) { tsign = d_sign (&c_b4, csr) * d_sign (&c_b4, csl) * d_sign (&c_b4, f); } if (pmax == 2) { tsign = d_sign (&c_b4, snr) * d_sign (&c_b4, csl) * d_sign (&c_b4, g); } if (pmax == 3) { tsign = d_sign (&c_b4, snr) * d_sign (&c_b4, snl) * d_sign (&c_b4, h__); } *ssmax = d_sign (ssmax, &tsign); d__1 = tsign * d_sign (&c_b4, f) * d_sign (&c_b4, h__); *ssmin = d_sign (ssmin, &d__1); return 0; } /* NUMlapack_dlasv2 */ int NUMlapack_dlaswp (long *n, double *a, long *lda, long *k1, long *k2, long *ipiv, long *incx) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4; /* Local variables */ static double temp; static long i__, j, k, i1, i2, n32, ip, ix, ix0, inc; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --ipiv; /* Function Body */ if (*incx > 0) { ix0 = *k1; i1 = *k1; i2 = *k2; inc = 1; } else if (*incx < 0) { ix0 = (1 - *k2) * *incx + 1; i1 = *k2; i2 = *k1; inc = -1; } else { return 0; } n32 = *n / 32 << 5; if (n32 != 0) { i__1 = n32; for (j = 1; j <= i__1; j += 32) { ix = ix0; i__2 = i2; i__3 = inc; for (i__ = i1; i__3 < 0 ? i__ >= i__2 : i__ <= i__2; i__ += i__3) { ip = ipiv[ix]; if (ip != i__) { i__4 = j + 31; for (k = j; k <= i__4; ++k) { temp = a_ref (i__, k); a_ref (i__, k) = a_ref (ip, k); a_ref (ip, k) = temp; /* L10: */ } } ix += *incx; /* L20: */ } /* L30: */ } } if (n32 != *n) { ++n32; ix = ix0; i__1 = i2; i__3 = inc; for (i__ = i1; i__3 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__3) { ip = ipiv[ix]; if (ip != i__) { i__2 = *n; for (k = n32; k <= i__2; ++k) { temp = a_ref (i__, k); a_ref (i__, k) = a_ref (ip, k); a_ref (ip, k) = temp; /* L40: */ } } ix += *incx; /* L50: */ } } return 0; } /* NUMlapack_dlaswp */ #define w_ref(a_1,a_2) w[(a_2)*w_dim1 + a_1] int NUMlapack_dlatrd (const char *uplo, long *n, long *nb, double *a, long *lda, double *e, double *tau, double *w, long *ldw) { /* Table of constant values */ static double c_b5 = -1.; static double c_b6 = 1.; static long c__1 = 1; static double c_b16 = 0.; /* System generated locals */ long a_dim1, a_offset, w_dim1, w_offset, i__1, i__2, i__3; /* Local variables */ static long i__; static double alpha; static long iw; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --e; --tau; w_dim1 = *ldw; w_offset = 1 + w_dim1 * 1; w -= w_offset; /* Function Body */ if (*n <= 0) { return 0; } if (lsame_ (uplo, "U")) { /* Reduce last NB columns of upper triangle */ i__1 = *n - *nb + 1; for (i__ = *n; i__ >= i__1; --i__) { iw = i__ - *n + *nb; if (i__ < *n) { /* Update A(1:i,i) */ i__2 = *n - i__; NUMblas_dgemv ("No transpose", &i__, &i__2, &c_b5, &a_ref (1, i__ + 1), lda, &w_ref (i__, iw + 1), ldw, &c_b6, &a_ref (1, i__), &c__1); i__2 = *n - i__; NUMblas_dgemv ("No transpose", &i__, &i__2, &c_b5, &w_ref (1, iw + 1), ldw, &a_ref (i__, i__ + 1), lda, &c_b6, &a_ref (1, i__), &c__1); } if (i__ > 1) { /* Generate elementary reflector H(i) to annihilate A(1:i-2,i) */ i__2 = i__ - 1; NUMlapack_dlarfg (&i__2, &a_ref (i__ - 1, i__), &a_ref (1, i__), &c__1, &tau[i__ - 1]); e[i__ - 1] = a_ref (i__ - 1, i__); a_ref (i__ - 1, i__) = 1.; /* Compute W(1:i-1,i) */ i__2 = i__ - 1; NUMblas_dsymv ("Upper", &i__2, &c_b6, &a[a_offset], lda, &a_ref (1, i__), &c__1, &c_b16, &w_ref (1, iw), &c__1); if (i__ < *n) { i__2 = i__ - 1; i__3 = *n - i__; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b6, &w_ref (1, iw + 1), ldw, &a_ref (1, i__), &c__1, &c_b16, &w_ref (i__ + 1, iw), &c__1); i__2 = i__ - 1; i__3 = *n - i__; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &a_ref (1, i__ + 1), lda, &w_ref (i__ + 1, iw), &c__1, &c_b6, &w_ref (1, iw), &c__1); i__2 = i__ - 1; i__3 = *n - i__; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b6, &a_ref (1, i__ + 1), lda, &a_ref (1, i__), &c__1, &c_b16, &w_ref (i__ + 1, iw), &c__1); i__2 = i__ - 1; i__3 = *n - i__; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &w_ref (1, iw + 1), ldw, &w_ref (i__ + 1, iw), &c__1, &c_b6, &w_ref (1, iw), &c__1); } i__2 = i__ - 1; NUMblas_dscal (&i__2, &tau[i__ - 1], &w_ref (1, iw), &c__1); i__2 = i__ - 1; alpha = tau[i__ - 1] * -.5 * NUMblas_ddot (&i__2, &w_ref (1, iw), &c__1, &a_ref (1, i__), &c__1); i__2 = i__ - 1; NUMblas_daxpy (&i__2, &alpha, &a_ref (1, i__), &c__1, &w_ref (1, iw), &c__1); } /* L10: */ } } else { /* Reduce first NB columns of lower triangle */ i__1 = *nb; for (i__ = 1; i__ <= i__1; ++i__) { /* Update A(i:n,i) */ i__2 = *n - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &a_ref (i__, 1), lda, &w_ref (i__, 1), ldw, &c_b6, &a_ref (i__, i__), &c__1); i__2 = *n - i__ + 1; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &w_ref (i__, 1), ldw, &a_ref (i__, 1), lda, &c_b6, &a_ref (i__, i__), &c__1); if (i__ < *n) { /* Generate elementary reflector H(i) to annihilate A(i+2:n,i) Computing MIN */ i__2 = i__ + 2; i__3 = *n - i__; NUMlapack_dlarfg (&i__3, &a_ref (i__ + 1, i__), &a_ref (MIN (i__2, *n), i__), &c__1, &tau[i__]); e[i__] = a_ref (i__ + 1, i__); a_ref (i__ + 1, i__) = 1.; /* Compute W(i+1:n,i) */ i__2 = *n - i__; NUMblas_dsymv ("Lower", &i__2, &c_b6, &a_ref (i__ + 1, i__ + 1), lda, &a_ref (i__ + 1, i__), &c__1, &c_b16, &w_ref (i__ + 1, i__), &c__1); i__2 = *n - i__; i__3 = i__ - 1; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b6, &w_ref (i__ + 1, 1), ldw, &a_ref (i__ + 1, i__), &c__1, &c_b16, &w_ref (1, i__), &c__1); i__2 = *n - i__; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &a_ref (i__ + 1, 1), lda, &w_ref (1, i__), &c__1, &c_b6, &w_ref (i__ + 1, i__), &c__1); i__2 = *n - i__; i__3 = i__ - 1; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b6, &a_ref (i__ + 1, 1), lda, &a_ref (i__ + 1, i__), &c__1, &c_b16, &w_ref (1, i__), &c__1); i__2 = *n - i__; i__3 = i__ - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b5, &w_ref (i__ + 1, 1), ldw, &w_ref (1, i__), &c__1, &c_b6, &w_ref (i__ + 1, i__), &c__1); i__2 = *n - i__; NUMblas_dscal (&i__2, &tau[i__], &w_ref (i__ + 1, i__), &c__1); i__2 = *n - i__; alpha = tau[i__] * -.5 * NUMblas_ddot (&i__2, &w_ref (i__ + 1, i__), &c__1, &a_ref (i__ + 1, i__), &c__1); i__2 = *n - i__; NUMblas_daxpy (&i__2, &alpha, &a_ref (i__ + 1, i__), &c__1, &w_ref (i__ + 1, i__), &c__1); } /* L20: */ } } return 0; } /* NUMlapack_dlatrd */ #undef w_ref int NUMlapack_dorg2l (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; double d__1; /* Local variables */ static long i__, j, l; static long ii; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < 0 || *n > *m) { *info = -2; } else if (*k < 0 || *k > *n) { *info = -3; } else if (*lda < MAX (1, *m)) { *info = -5; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORG2L", &i__1); return 0; } /* Quick return if possible */ if (*n <= 0) { return 0; } /* Initialise columns 1:n-k to columns of the unit matrix */ i__1 = *n - *k; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (l = 1; l <= i__2; ++l) { a_ref (l, j) = 0.; /* L10: */ } a_ref (*m - *n + j, j) = 1.; /* L20: */ } i__1 = *k; for (i__ = 1; i__ <= i__1; ++i__) { ii = *n - *k + i__; /* Apply H(i) to A(1:m-k+i,1:n-k+i) from the left */ a_ref (*m - *n + ii, ii) = 1.; i__2 = *m - *n + ii; i__3 = ii - 1; NUMlapack_dlarf ("Left", &i__2, &i__3, &a_ref (1, ii), &c__1, &tau[i__], &a[a_offset], lda, &work[1]); i__2 = *m - *n + ii - 1; d__1 = -tau[i__]; NUMblas_dscal (&i__2, &d__1, &a_ref (1, ii), &c__1); a_ref (*m - *n + ii, ii) = 1. - tau[i__]; /* Set A(m-k+i+1:m,n-k+i) to zero */ i__2 = *m; for (l = *m - *n + ii + 1; l <= i__2; ++l) { a_ref (l, ii) = 0.; /* L30: */ } /* L40: */ } return 0; } /* NUMlapack_dorg2l */ int NUMlapack_dorg2r (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2; double d__1; /* Local variables */ static long i__, j, l; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < 0 || *n > *m) { *info = -2; } else if (*k < 0 || *k > *n) { *info = -3; } else if (*lda < MAX (1, *m)) { *info = -5; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORG2R", &i__1); return 0; } /* Quick return if possible */ if (*n <= 0) { return 0; } /* Initialise columns k+1:n to columns of the unit matrix */ i__1 = *n; for (j = *k + 1; j <= i__1; ++j) { i__2 = *m; for (l = 1; l <= i__2; ++l) { a_ref (l, j) = 0.; /* L10: */ } a_ref (j, j) = 1.; /* L20: */ } for (i__ = *k; i__ >= 1; --i__) { /* Apply H(i) to A(i:m,i:n) from the left */ if (i__ < *n) { a_ref (i__, i__) = 1.; i__1 = *m - i__ + 1; i__2 = *n - i__; NUMlapack_dlarf ("Left", &i__1, &i__2, &a_ref (i__, i__), &c__1, &tau[i__], &a_ref (i__, i__ + 1), lda, &work[1]); } if (i__ < *m) { i__1 = *m - i__; d__1 = -tau[i__]; NUMblas_dscal (&i__1, &d__1, &a_ref (i__ + 1, i__), &c__1); } a_ref (i__, i__) = 1. - tau[i__]; /* Set A(1:i-1,i) to zero */ i__1 = i__ - 1; for (l = 1; l <= i__1; ++l) { a_ref (l, i__) = 0.; /* L30: */ } /* L40: */ } return 0; } /* NUMlapack_dorg2r */ int NUMlapack_dorgbr (const char *vect, long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__, j; static long iinfo; static long wantq; static long nb, mn; static long lwkopt; static long lquery; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; wantq = lsame_ (vect, "Q"); mn = MIN (*m, *n); lquery = *lwork == -1; if (!wantq && !lsame_ (vect, "P")) { *info = -1; } else if (*m < 0) { *info = -2; } else if (*n < 0 || wantq && (*n > *m || *n < MIN (*m, *k)) || !wantq && (*m > *n || *m < MIN (*n, *k))) { *info = -3; } else if (*k < 0) { *info = -4; } else if (*lda < MAX (1, *m)) { *info = -6; } else if (*lwork < MAX (1, mn) && !lquery) { *info = -9; } if (*info == 0) { if (wantq) { nb = NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, n, k, &c_n1, 6, 1); } else { nb = NUMlapack_ilaenv (&c__1, "DORGLQ", " ", m, n, k, &c_n1, 6, 1); } lwkopt = MAX (1, mn) * nb; work[1] = (double) lwkopt; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORGBR", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0) { work[1] = 1.; return 0; } if (wantq) { /* Form Q, determined by a call to DGEBRD to reduce an m-by-k matrix */ if (*m >= *k) { /* If m >= k, assume m >= n >= k */ NUMlapack_dorgqr (m, n, k, &a[a_offset], lda, &tau[1], &work[1], lwork, &iinfo); } else { /* If m < k, assume m = n Shift the vectors which define the elementary reflectors one column to the right, and set the first row and column of Q to those of the unit matrix */ for (j = *m; j >= 2; --j) { a_ref (1, j) = 0.; i__1 = *m; for (i__ = j + 1; i__ <= i__1; ++i__) { a_ref (i__, j) = a_ref (i__, j - 1); /* L10: */ } /* L20: */ } a_ref (1, 1) = 1.; i__1 = *m; for (i__ = 2; i__ <= i__1; ++i__) { a_ref (i__, 1) = 0.; /* L30: */ } if (*m > 1) { /* Form Q(2:m,2:m) */ i__1 = *m - 1; i__2 = *m - 1; i__3 = *m - 1; NUMlapack_dorgqr (&i__1, &i__2, &i__3, &a_ref (2, 2), lda, &tau[1], &work[1], lwork, &iinfo); } } } else { /* Form P', determined by a call to DGEBRD to reduce a k-by-n matrix */ if (*k < *n) { /* If k < n, assume k <= m <= n */ NUMlapack_dorglq (m, n, k, &a[a_offset], lda, &tau[1], &work[1], lwork, &iinfo); } else { /* If k >= n, assume m = n Shift the vectors which define the elementary reflectors one row downward, and set the first row and column of P' to those of the unit matrix */ a_ref (1, 1) = 1.; i__1 = *n; for (i__ = 2; i__ <= i__1; ++i__) { a_ref (i__, 1) = 0.; /* L40: */ } i__1 = *n; for (j = 2; j <= i__1; ++j) { for (i__ = j - 1; i__ >= 2; --i__) { a_ref (i__, j) = a_ref (i__ - 1, j); /* L50: */ } a_ref (1, j) = 0.; /* L60: */ } if (*n > 1) { /* Form P'(2:n,2:n) */ i__1 = *n - 1; i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dorglq (&i__1, &i__2, &i__3, &a_ref (2, 2), lda, &tau[1], &work[1], lwork, &iinfo); } } } work[1] = (double) lwkopt; return 0; } /* NUMlapack_dorgbr */ int NUMlapack_dorghr (long *n, long *ilo, long *ihi, double *a, long *lda, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2; /* Local variables */ static long i__, j, iinfo, nb, nh; static long lwkopt; static int lquery; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; nh = *ihi - *ilo; lquery = *lwork == -1; if (*n < 0) { *info = -1; } else if (*ilo < 1 || *ilo > MAX (1, *n)) { *info = -2; } else if (*ihi < MIN (*ilo, *n) || *ihi > *n) { *info = -3; } else if (*lda < MAX (1, *n)) { *info = -5; } else if (*lwork < MAX (1, nh) && !lquery) { *info = -8; } if (*info == 0) { nb = NUMlapack_ilaenv (&c__1, "DORGQR", " ", &nh, &nh, &nh, &c_n1, 6, 1); lwkopt = MAX (1, nh) * nb; work[1] = (double) lwkopt; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORGHR", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*n == 0) { work[1] = 1.; return 0; } /* Shift the vectors which define the elementary reflectors one column to the right, and set the first ilo and the last n-ihi rows and columns to those of the unit matrix */ i__1 = *ilo + 1; for (j = *ihi; j >= i__1; --j) { i__2 = j - 1; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L10: */ } i__2 = *ihi; for (i__ = j + 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j - 1); /* L20: */ } i__2 = *n; for (i__ = *ihi + 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L30: */ } /* L40: */ } i__1 = *ilo; for (j = 1; j <= i__1; ++j) { i__2 = *n; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L50: */ } a_ref (j, j) = 1.; /* L60: */ } i__1 = *n; for (j = *ihi + 1; j <= i__1; ++j) { i__2 = *n; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L70: */ } a_ref (j, j) = 1.; /* L80: */ } if (nh > 0) { /* Generate Q(ilo+1:ihi,ilo+1:ihi) */ NUMlapack_dorgqr (&nh, &nh, &nh, &a_ref (*ilo + 1, *ilo + 1), lda, &tau[*ilo], &work[1], lwork, &iinfo); } work[1] = (double) lwkopt; return 0; } /* NUMlapack_dorghr */ int NUMlapack_dorgl2 (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *info) { /* System generated locals */ long a_dim1, a_offset, i__1, i__2; double d__1; /* Local variables */ static long i__, j, l; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; if (*m < 0) { *info = -1; } else if (*n < *m) { *info = -2; } else if (*k < 0 || *k > *m) { *info = -3; } else if (*lda < MAX (1, *m)) { *info = -5; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORGL2", &i__1); return 0; } /* Quick return if possible */ if (*m <= 0) { return 0; } if (*k < *m) { /* Initialise rows k+1:m to rows of the unit matrix */ i__1 = *n; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (l = *k + 1; l <= i__2; ++l) { a_ref (l, j) = 0.; /* L10: */ } if (j > *k && j <= *m) { a_ref (j, j) = 1.; } /* L20: */ } } for (i__ = *k; i__ >= 1; --i__) { /* Apply H(i) to A(i:m,i:n) from the right */ if (i__ < *n) { if (i__ < *m) { a_ref (i__, i__) = 1.; i__1 = *m - i__; i__2 = *n - i__ + 1; NUMlapack_dlarf ("Right", &i__1, &i__2, &a_ref (i__, i__), lda, &tau[i__], &a_ref (i__ + 1, i__), lda, &work[1]); } i__1 = *n - i__; d__1 = -tau[i__]; NUMblas_dscal (&i__1, &d__1, &a_ref (i__, i__ + 1), lda); } a_ref (i__, i__) = 1. - tau[i__]; /* Set A(i,1:i-1) to zero */ i__1 = i__ - 1; for (l = 1; l <= i__1; ++l) { a_ref (i__, l) = 0.; /* L30: */ } /* L40: */ } return 0; } /* NUMlapack_dorgl2 */ int NUMlapack_dorglq (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__3 = 3; static long c__2 = 2; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__, j, l, nbmin, iinfo; static long ib, nb, ki, kk; static long nx; static long ldwork, lwkopt; static long lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; nb = NUMlapack_ilaenv (&c__1, "DORGLQ", " ", m, n, k, &c_n1, 6, 1); lwkopt = MAX (1, *m) * nb; work[1] = (double) lwkopt; lquery = *lwork == -1; if (*m < 0) { *info = -1; } else if (*n < *m) { *info = -2; } else if (*k < 0 || *k > *m) { *info = -3; } else if (*lda < MAX (1, *m)) { *info = -5; } else if (*lwork < MAX (1, *m) && !lquery) { *info = -8; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORGLQ", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*m <= 0) { work[1] = 1.; return 0; } nbmin = 2; nx = 0; iws = *m; if (nb > 1 && nb < *k) { /* Determine when to cross over from blocked to unblocked code. Computing MAX */ i__1 = 0, i__2 = NUMlapack_ilaenv (&c__3, "DORGLQ", " ", m, n, k, &c_n1, 6, 1); nx = MAX (i__1, i__2); if (nx < *k) { /* Determine if workspace is large enough for blocked code. */ ldwork = *m; iws = ldwork * nb; if (*lwork < iws) { /* Not enough workspace to use optimal NB: reduce NB and determine the minimum value of NB. */ nb = *lwork / ldwork; /* Computing MAX */ i__1 = 2, i__2 = NUMlapack_ilaenv (&c__2, "DORGLQ", " ", m, n, k, &c_n1, 6, 1); nbmin = MAX (i__1, i__2); } } } if (nb >= nbmin && nb < *k && nx < *k) { /* Use blocked code after the last block. The first kk rows are handled by the block method. */ ki = (*k - nx - 1) / nb * nb; /* Computing MIN */ i__1 = *k, i__2 = ki + nb; kk = MIN (i__1, i__2); /* Set A(kk+1:m,1:kk) to zero. */ i__1 = kk; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = kk + 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L10: */ } /* L20: */ } } else { kk = 0; } /* Use unblocked code for the last or only block. */ if (kk < *m) { i__1 = *m - kk; i__2 = *n - kk; i__3 = *k - kk; NUMlapack_dorgl2 (&i__1, &i__2, &i__3, &a_ref (kk + 1, kk + 1), lda, &tau[kk + 1], &work[1], &iinfo); } if (kk > 0) { /* Use blocked code */ i__1 = -nb; for (i__ = ki + 1; i__1 < 0 ? i__ >= 1 : i__ <= 1; i__ += i__1) { /* Computing MIN */ i__2 = nb, i__3 = *k - i__ + 1; ib = MIN (i__2, i__3); if (i__ + ib <= *m) { /* Form the triangular factor of the block reflector H = H(i) H(i+1) . . . H(i+ib-1) */ i__2 = *n - i__ + 1; NUMlapack_dlarft ("Forward", "Rowwise", &i__2, &ib, &a_ref (i__, i__), lda, &tau[i__], &work[1], &ldwork); /* Apply H' to A(i+ib:m,i:n) from the right */ i__2 = *m - i__ - ib + 1; i__3 = *n - i__ + 1; NUMlapack_dlarfb ("Right", "Transpose", "Forward", "Rowwise", &i__2, &i__3, &ib, &a_ref (i__, i__), lda, &work[1], &ldwork, &a_ref (i__ + ib, i__), lda, &work[ib + 1], &ldwork); } /* Apply H' to columns i:n of current block */ i__2 = *n - i__ + 1; NUMlapack_dorgl2 (&ib, &i__2, &ib, &a_ref (i__, i__), lda, &tau[i__], &work[1], &iinfo); /* Set columns 1:i-1 of current block to zero */ i__2 = i__ - 1; for (j = 1; j <= i__2; ++j) { i__3 = i__ + ib - 1; for (l = i__; l <= i__3; ++l) { a_ref (l, j) = 0.; /* L30: */ } /* L40: */ } /* L50: */ } } work[1] = (double) iws; return 0; } /* NUMlapack_dorglq */ int NUMlapack_dorgql (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__3 = 3; static long c__2 = 2; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3, i__4; /* Local variables */ static long i__, j, l, nbmin, iinfo; static long ib, nb, kk; static long nx; static long ldwork, lwkopt; static long lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; nb = NUMlapack_ilaenv (&c__1, "DORGQL", " ", m, n, k, &c_n1, 6, 1); lwkopt = MAX (1, *n) * nb; work[1] = (double) lwkopt; lquery = *lwork == -1; if (*m < 0) { *info = -1; } else if (*n < 0 || *n > *m) { *info = -2; } else if (*k < 0 || *k > *n) { *info = -3; } else if (*lda < MAX (1, *m)) { *info = -5; } else if (*lwork < MAX (1, *n) && !lquery) { *info = -8; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORGQL", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*n <= 0) { work[1] = 1.; return 0; } nbmin = 2; nx = 0; iws = *n; if (nb > 1 && nb < *k) { /* Determine when to cross over from blocked to unblocked code. Computing MAX */ i__1 = 0, i__2 = NUMlapack_ilaenv (&c__3, "DORGQL", " ", m, n, k, &c_n1, 6, 1); nx = MAX (i__1, i__2); if (nx < *k) { /* Determine if workspace is large enough for blocked code. */ ldwork = *n; iws = ldwork * nb; if (*lwork < iws) { /* Not enough workspace to use optimal NB: reduce NB and determine the minimum value of NB. */ nb = *lwork / ldwork; /* Computing MAX */ i__1 = 2, i__2 = NUMlapack_ilaenv (&c__2, "DORGQL", " ", m, n, k, &c_n1, 6, 1); nbmin = MAX (i__1, i__2); } } } if (nb >= nbmin && nb < *k && nx < *k) { /* Use blocked code after the first block. The last kk columns are handled by the block method. Computing MIN */ i__1 = *k, i__2 = (*k - nx + nb - 1) / nb * nb; kk = MIN (i__1, i__2); /* Set A(m-kk+1:m,1:n-kk) to zero. */ i__1 = *n - kk; for (j = 1; j <= i__1; ++j) { i__2 = *m; for (i__ = *m - kk + 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L10: */ } /* L20: */ } } else { kk = 0; } /* Use unblocked code for the first or only block. */ i__1 = *m - kk; i__2 = *n - kk; i__3 = *k - kk; NUMlapack_dorg2l (&i__1, &i__2, &i__3, &a[a_offset], lda, &tau[1], &work[1], &iinfo); if (kk > 0) { /* Use blocked code */ i__1 = *k; i__2 = nb; for (i__ = *k - kk + 1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Computing MIN */ i__3 = nb, i__4 = *k - i__ + 1; ib = MIN (i__3, i__4); if (*n - *k + i__ > 1) { /* Form the triangular factor of the block reflector H = H(i+ib-1) . . . H(i+1) H(i) */ i__3 = *m - *k + i__ + ib - 1; NUMlapack_dlarft ("Backward", "Columnwise", &i__3, &ib, &a_ref (1, *n - *k + i__), lda, &tau[i__], &work[1], &ldwork); /* Apply H to A(1:m-k+i+ib-1,1:n-k+i-1) from the left */ i__3 = *m - *k + i__ + ib - 1; i__4 = *n - *k + i__ - 1; NUMlapack_dlarfb ("Left", "No transpose", "Backward", "Columnwise", &i__3, &i__4, &ib, &a_ref (1, *n - *k + i__), lda, &work[1], &ldwork, &a[a_offset], lda, &work[ib + 1], &ldwork); } /* Apply H to rows 1:m-k+i+ib-1 of current block */ i__3 = *m - *k + i__ + ib - 1; NUMlapack_dorg2l (&i__3, &ib, &ib, &a_ref (1, *n - *k + i__), lda, &tau[i__], &work[1], &iinfo); /* Set rows m-k+i+ib:m of current block to zero */ i__3 = *n - *k + i__ + ib - 1; for (j = *n - *k + i__; j <= i__3; ++j) { i__4 = *m; for (l = *m - *k + i__ + ib; l <= i__4; ++l) { a_ref (l, j) = 0.; /* L30: */ } /* L40: */ } /* L50: */ } } work[1] = (double) iws; return 0; } /* NUMlapack_dorgql */ int NUMlapack_dorgqr (long *m, long *n, long *k, double *a, long *lda, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__3 = 3; static long c__2 = 2; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__, j, l, nbmin, iinfo; static long ib, nb, ki, kk; static long nx; static long ldwork, lwkopt; static long lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; nb = NUMlapack_ilaenv (&c__1, "DORGQR", " ", m, n, k, &c_n1, 6, 1); lwkopt = MAX (1, *n) * nb; work[1] = (double) lwkopt; lquery = *lwork == -1; if (*m < 0) { *info = -1; } else if (*n < 0 || *n > *m) { *info = -2; } else if (*k < 0 || *k > *n) { *info = -3; } else if (*lda < MAX (1, *m)) { *info = -5; } else if (*lwork < MAX (1, *n) && !lquery) { *info = -8; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORGQR", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*n <= 0) { work[1] = 1.; return 0; } nbmin = 2; nx = 0; iws = *n; if (nb > 1 && nb < *k) { /* Determine when to cross over from blocked to unblocked code. Computing MAX */ i__1 = 0, i__2 = NUMlapack_ilaenv (&c__3, "DORGQR", " ", m, n, k, &c_n1, 6, 1); nx = MAX (i__1, i__2); if (nx < *k) { /* Determine if workspace is large enough for blocked code. */ ldwork = *n; iws = ldwork * nb; if (*lwork < iws) { /* Not enough workspace to use optimal NB: reduce NB and determine the minimum value of NB. */ nb = *lwork / ldwork; /* Computing MAX */ i__1 = 2, i__2 = NUMlapack_ilaenv (&c__2, "DORGQR", " ", m, n, k, &c_n1, 6, 1); nbmin = MAX (i__1, i__2); } } } if (nb >= nbmin && nb < *k && nx < *k) { /* Use blocked code after the last block. The first kk columns are handled by the block method. */ ki = (*k - nx - 1) / nb * nb; /* Computing MIN */ i__1 = *k, i__2 = ki + nb; kk = MIN (i__1, i__2); /* Set A(1:kk,kk+1:n) to zero. */ i__1 = *n; for (j = kk + 1; j <= i__1; ++j) { i__2 = kk; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = 0.; /* L10: */ } /* L20: */ } } else { kk = 0; } /* Use unblocked code for the last or only block. */ if (kk < *n) { i__1 = *m - kk; i__2 = *n - kk; i__3 = *k - kk; NUMlapack_dorg2r (&i__1, &i__2, &i__3, &a_ref (kk + 1, kk + 1), lda, &tau[kk + 1], &work[1], &iinfo); } if (kk > 0) { /* Use blocked code */ i__1 = -nb; for (i__ = ki + 1; i__1 < 0 ? i__ >= 1 : i__ <= 1; i__ += i__1) { /* Computing MIN */ i__2 = nb, i__3 = *k - i__ + 1; ib = MIN (i__2, i__3); if (i__ + ib <= *n) { /* Form the triangular factor of the block reflector H = H(i) H(i+1) . . . H(i+ib-1) */ i__2 = *m - i__ + 1; NUMlapack_dlarft ("Forward", "Columnwise", &i__2, &ib, &a_ref (i__, i__), lda, &tau[i__], &work[1], &ldwork); /* Apply H to A(i:m,i+ib:n) from the left */ i__2 = *m - i__ + 1; i__3 = *n - i__ - ib + 1; NUMlapack_dlarfb ("Left", "No transpose", "Forward", "Columnwise", &i__2, &i__3, &ib, &a_ref (i__, i__), lda, &work[1], &ldwork, &a_ref (i__, i__ + ib), lda, &work[ib + 1], &ldwork); } /* Apply H to rows i:m of current block */ i__2 = *m - i__ + 1; NUMlapack_dorg2r (&i__2, &ib, &ib, &a_ref (i__, i__), lda, &tau[i__], &work[1], &iinfo); /* Set rows 1:i-1 of current block to zero */ i__2 = i__ + ib - 1; for (j = i__; j <= i__2; ++j) { i__3 = i__ - 1; for (l = 1; l <= i__3; ++l) { a_ref (l, j) = 0.; /* L30: */ } /* L40: */ } /* L50: */ } } work[1] = (double) iws; return 0; } /* NUMlapack_dorgqr */ int NUMlapack_dorgtr (const char *uplo, long *n, double *a, long *lda, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__, j; static long iinfo; static long upper; static long nb; static long lwkopt; static long lquery; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; --work; /* Function Body */ *info = 0; lquery = *lwork == -1; upper = lsame_ (uplo, "U"); if (!upper && !lsame_ (uplo, "L")) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *n)) { *info = -4; } else { /* if(complicated condition) */ /* Computing MAX */ i__1 = 1, i__2 = *n - 1; if (*lwork < MAX (i__1, i__2) && !lquery) { *info = -7; } } if (*info == 0) { if (upper) { i__1 = *n - 1; i__2 = *n - 1; i__3 = *n - 1; nb = NUMlapack_ilaenv (&c__1, "DORGQL", " ", &i__1, &i__2, &i__3, &c_n1, 6, 1); } else { i__1 = *n - 1; i__2 = *n - 1; i__3 = *n - 1; nb = NUMlapack_ilaenv (&c__1, "DORGQR", " ", &i__1, &i__2, &i__3, &c_n1, 6, 1); } /* Computing MAX */ i__1 = 1, i__2 = *n - 1; lwkopt = MAX (i__1, i__2) * nb; work[1] = (double) lwkopt; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORGTR", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*n == 0) { work[1] = 1.; return 0; } if (upper) { /* Q was determined by a call to DSYTRD with UPLO = 'U' Shift the vectors which define the elementary reflectors one column to the left, and set the last row and column of Q to those of the unit matrix */ i__1 = *n - 1; for (j = 1; j <= i__1; ++j) { i__2 = j - 1; for (i__ = 1; i__ <= i__2; ++i__) { a_ref (i__, j) = a_ref (i__, j + 1); /* L10: */ } a_ref (*n, j) = 0.; /* L20: */ } i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { a_ref (i__, *n) = 0.; /* L30: */ } a_ref (*n, *n) = 1.; /* Generate Q(1:n-1,1:n-1) */ i__1 = *n - 1; i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dorgql (&i__1, &i__2, &i__3, &a[a_offset], lda, &tau[1], &work[1], lwork, &iinfo); } else { /* Q was determined by a call to DSYTRD with UPLO = 'L'. Shift the vectors which define the elementary reflectors one column to the right, and set the first row and column of Q to those of the unit matrix */ for (j = *n; j >= 2; --j) { a_ref (1, j) = 0.; i__1 = *n; for (i__ = j + 1; i__ <= i__1; ++i__) { a_ref (i__, j) = a_ref (i__, j - 1); /* L40: */ } /* L50: */ } a_ref (1, 1) = 1.; i__1 = *n; for (i__ = 2; i__ <= i__1; ++i__) { a_ref (i__, 1) = 0.; /* L60: */ } if (*n > 1) { /* Generate Q(2:n,2:n) */ i__1 = *n - 1; i__2 = *n - 1; i__3 = *n - 1; NUMlapack_dorgqr (&i__1, &i__2, &i__3, &a_ref (2, 2), lda, &tau[1], &work[1], lwork, &iinfo); } } work[1] = (double) lwkopt; return 0; } /* NUMlapack_dorgtr */ int NUMlapack_dorm2r (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c__, long *ldc, double *work, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, c_dim1, c_offset, i__1, i__2; /* Local variables */ static long left; static long i__; static long i1, i2, i3, ic, jc, mi, ni, nq; static long notran; static double aii; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; --work; /* Function Body */ *info = 0; left = lsame_ (side, "L"); notran = lsame_ (trans, "N"); /* NQ is the order of Q */ if (left) { nq = *m; } else { nq = *n; } if (!left && !lsame_ (side, "R")) { *info = -1; } else if (!notran && !lsame_ (trans, "T")) { *info = -2; } else if (*m < 0) { *info = -3; } else if (*n < 0) { *info = -4; } else if (*k < 0 || *k > nq) { *info = -5; } else if (*lda < MAX (1, nq)) { *info = -7; } else if (*ldc < MAX (1, *m)) { *info = -10; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORM2R", &i__1); return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0 || *k == 0) { return 0; } if (left && !notran || !left && notran) { i1 = 1; i2 = *k; i3 = 1; } else { i1 = *k; i2 = 1; i3 = -1; } if (left) { ni = *n; jc = 1; } else { mi = *m; ic = 1; } i__1 = i2; i__2 = i3; for (i__ = i1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { if (left) { /* H(i) is applied to C(i:m,1:n) */ mi = *m - i__ + 1; ic = i__; } else { /* H(i) is applied to C(1:m,i:n) */ ni = *n - i__ + 1; jc = i__; } /* Apply H(i) */ aii = a_ref (i__, i__); a_ref (i__, i__) = 1.; NUMlapack_dlarf (side, &mi, &ni, &a_ref (i__, i__), &c__1, &tau[i__], &c___ref (ic, jc), ldc, &work[1]); a_ref (i__, i__) = aii; /* L10: */ } return 0; } /* NUMlapack_dorm2r */ int NUMlapack_dormbr (const char *vect, const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c__, long *ldc, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__2 = 2; /* System generated locals */ const char *a__1[2]; long a_dim1, a_offset, c_dim1, c_offset, i__1, i__2, i__3[2]; char ch__1[2]; /* Local variables */ static long left; static long iinfo, i1, i2, nb, mi, ni, nq, nw; static long notran; static long applyq; static char transt[1]; static long lwkopt; static long lquery; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; --work; /* Function Body */ *info = 0; applyq = lsame_ (vect, "Q"); left = lsame_ (side, "L"); notran = lsame_ (trans, "N"); lquery = *lwork == -1; /* NQ is the order of Q or P and NW is the minimum dimension of WORK */ if (left) { nq = *m; nw = *n; } else { nq = *n; nw = *m; } if (!applyq && !lsame_ (vect, "P")) { *info = -1; } else if (!left && !lsame_ (side, "R")) { *info = -2; } else if (!notran && !lsame_ (trans, "T")) { *info = -3; } else if (*m < 0) { *info = -4; } else if (*n < 0) { *info = -5; } else if (*k < 0) { *info = -6; } else { /* if(complicated condition) */ /* Computing MAX */ i__1 = 1, i__2 = MIN (nq, *k); if (applyq && *lda < MAX (1, nq) || !applyq && *lda < MAX (i__1, i__2)) { *info = -8; } else if (*ldc < MAX (1, *m)) { *info = -11; } else if (*lwork < MAX (1, nw) && !lquery) { *info = -13; } } if (*info == 0) { if (applyq) { if (left) { /* Writing concatenation */ i__3[0] = 1, a__1[0] = side; i__3[1] = 1, a__1[1] = trans; s_cat (ch__1, a__1, i__3, &c__2, 2); i__1 = *m - 1; i__2 = *m - 1; nb = NUMlapack_ilaenv (&c__1, "DORMQR", ch__1, &i__1, n, &i__2, &c_n1, 6, 2); } else { /* Writing concatenation */ i__3[0] = 1, a__1[0] = side; i__3[1] = 1, a__1[1] = trans; s_cat (ch__1, a__1, i__3, &c__2, 2); i__1 = *n - 1; i__2 = *n - 1; nb = NUMlapack_ilaenv (&c__1, "DORMQR", ch__1, m, &i__1, &i__2, &c_n1, 6, 2); } } else { if (left) { /* Writing concatenation */ i__3[0] = 1, a__1[0] = side; i__3[1] = 1, a__1[1] = trans; s_cat (ch__1, a__1, i__3, &c__2, 2); i__1 = *m - 1; i__2 = *m - 1; nb = NUMlapack_ilaenv (&c__1, "DORMLQ", ch__1, &i__1, n, &i__2, &c_n1, 6, 2); } else { /* Writing concatenation */ i__3[0] = 1, a__1[0] = side; i__3[1] = 1, a__1[1] = trans; s_cat (ch__1, a__1, i__3, &c__2, 2); i__1 = *n - 1; i__2 = *n - 1; nb = NUMlapack_ilaenv (&c__1, "DORMLQ", ch__1, m, &i__1, &i__2, &c_n1, 6, 2); } } lwkopt = MAX (1, nw) * nb; work[1] = (double) lwkopt; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORMBR", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ work[1] = 1.; if (*m == 0 || *n == 0) { return 0; } if (applyq) { /* Apply Q */ if (nq >= *k) { /* Q was determined by a call to DGEBRD with nq >= k */ NUMlapack_dormqr (side, trans, m, n, k, &a[a_offset], lda, &tau[1], &c__[c_offset], ldc, &work[1], lwork, &iinfo); } else if (nq > 1) { /* Q was determined by a call to DGEBRD with nq < k */ if (left) { mi = *m - 1; ni = *n; i1 = 2; i2 = 1; } else { mi = *m; ni = *n - 1; i1 = 1; i2 = 2; } i__1 = nq - 1; NUMlapack_dormqr (side, trans, &mi, &ni, &i__1, &a_ref (2, 1), lda, &tau[1], &c___ref (i1, i2), ldc, &work[1], lwork, &iinfo); } } else { /* Apply P */ if (notran) { * (unsigned char *) transt = 'T'; } else { * (unsigned char *) transt = 'N'; } if (nq > *k) { /* P was determined by a call to DGEBRD with nq > k */ NUMlapack_dormlq (side, transt, m, n, k, &a[a_offset], lda, &tau[1], &c__[c_offset], ldc, &work[1], lwork, &iinfo); } else if (nq > 1) { /* P was determined by a call to DGEBRD with nq <= k */ if (left) { mi = *m - 1; ni = *n; i1 = 2; i2 = 1; } else { mi = *m; ni = *n - 1; i1 = 1; i2 = 2; } i__1 = nq - 1; NUMlapack_dormlq (side, transt, &mi, &ni, &i__1, &a_ref (1, 2), lda, &tau[1], &c___ref (i1, i2), ldc, &work[1], lwork, &iinfo); } } work[1] = (double) lwkopt; return 0; } /* NUMlapack_dormbr */ int NUMlapack_dorml2 (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c__, long *ldc, double *work, long *info) { /* System generated locals */ long a_dim1, a_offset, c_dim1, c_offset, i__1, i__2; /* Local variables */ static long left; static long i__; static long i1, i2, i3, ic, jc, mi, ni, nq; static long notran; static double aii; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; --work; /* Function Body */ *info = 0; left = lsame_ (side, "L"); notran = lsame_ (trans, "N"); /* NQ is the order of Q */ if (left) { nq = *m; } else { nq = *n; } if (!left && !lsame_ (side, "R")) { *info = -1; } else if (!notran && !lsame_ (trans, "T")) { *info = -2; } else if (*m < 0) { *info = -3; } else if (*n < 0) { *info = -4; } else if (*k < 0 || *k > nq) { *info = -5; } else if (*lda < MAX (1, *k)) { *info = -7; } else if (*ldc < MAX (1, *m)) { *info = -10; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORML2", &i__1); return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0 || *k == 0) { return 0; } if (left && notran || !left && !notran) { i1 = 1; i2 = *k; i3 = 1; } else { i1 = *k; i2 = 1; i3 = -1; } if (left) { ni = *n; jc = 1; } else { mi = *m; ic = 1; } i__1 = i2; i__2 = i3; for (i__ = i1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { if (left) { /* H(i) is applied to C(i:m,1:n) */ mi = *m - i__ + 1; ic = i__; } else { /* H(i) is applied to C(1:m,i:n) */ ni = *n - i__ + 1; jc = i__; } /* Apply H(i) */ aii = a_ref (i__, i__); a_ref (i__, i__) = 1.; NUMlapack_dlarf (side, &mi, &ni, &a_ref (i__, i__), lda, &tau[i__], &c___ref (ic, jc), ldc, &work[1]); a_ref (i__, i__) = aii; /* L10: */ } return 0; } /* NUMlapack_dorml2 */ int NUMlapack_dormlq (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c__, long *ldc, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__2 = 2; static long c__65 = 65; /* System generated locals */ char *a__1[2]; long a_dim1, a_offset, c_dim1, c_offset, i__1, i__2, i__3[2], i__4, i__5; char ch__1[2]; /* Local variables */ static long left; static long i__; static double t[4160] /* was [65][64] */ ; static long nbmin, iinfo, i1, i2, i3; static long ib, ic, jc, nb, mi, ni; static long nq, nw; static long notran; static long ldwork; static char transt[1]; static long lwkopt; static long lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; --work; /* Function Body */ *info = 0; left = lsame_ (side, "L"); notran = lsame_ (trans, "N"); lquery = *lwork == -1; /* NQ is the order of Q and NW is the minimum dimension of WORK */ if (left) { nq = *m; nw = *n; } else { nq = *n; nw = *m; } if (!left && !lsame_ (side, "R")) { *info = -1; } else if (!notran && !lsame_ (trans, "T")) { *info = -2; } else if (*m < 0) { *info = -3; } else if (*n < 0) { *info = -4; } else if (*k < 0 || *k > nq) { *info = -5; } else if (*lda < MAX (1, *k)) { *info = -7; } else if (*ldc < MAX (1, *m)) { *info = -10; } else if (*lwork < MAX (1, nw) && !lquery) { *info = -12; } if (*info == 0) { /* Determine the block size. NB may be at most NBMAX, where NBMAX is used to define the local array T. Computing MIN Writing concatenation */ i__3[0] = 1, a__1[0] = (char *) side; i__3[1] = 1, a__1[1] = (char *) trans; s_cat (ch__1, (const char **) a__1, i__3, &c__2, 2); i__1 = 64, i__2 = NUMlapack_ilaenv (&c__1, "DORMLQ", ch__1, m, n, k, &c_n1, 6, 2); nb = MIN (i__1, i__2); lwkopt = MAX (1, nw) * nb; work[1] = (double) lwkopt; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORMLQ", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0 || *k == 0) { work[1] = 1.; return 0; } nbmin = 2; ldwork = nw; if (nb > 1 && nb < *k) { iws = nw * nb; if (*lwork < iws) { nb = *lwork / ldwork; /* Computing MAX Writing concatenation */ i__3[0] = 1, a__1[0] = (char *) side; i__3[1] = 1, a__1[1] = (char *) trans; s_cat (ch__1, (const char **) a__1, i__3, &c__2, 2); i__1 = 2, i__2 = NUMlapack_ilaenv (&c__2, "DORMLQ", ch__1, m, n, k, &c_n1, 6, 2); nbmin = MAX (i__1, i__2); } } else { iws = nw; } if (nb < nbmin || nb >= *k) { /* Use unblocked code */ NUMlapack_dorml2 (side, trans, m, n, k, &a[a_offset], lda, &tau[1], &c__[c_offset], ldc, &work[1], &iinfo); } else { /* Use blocked code */ if (left && notran || !left && !notran) { i1 = 1; i2 = *k; i3 = nb; } else { i1 = (*k - 1) / nb * nb + 1; i2 = 1; i3 = -nb; } if (left) { ni = *n; jc = 1; } else { mi = *m; ic = 1; } if (notran) { * (unsigned char *) transt = 'T'; } else { * (unsigned char *) transt = 'N'; } i__1 = i2; i__2 = i3; for (i__ = i1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Computing MIN */ i__4 = nb, i__5 = *k - i__ + 1; ib = MIN (i__4, i__5); /* Form the triangular factor of the block reflector H = H(i) H(i+1) . . . H(i+ib-1) */ i__4 = nq - i__ + 1; NUMlapack_dlarft ("Forward", "Rowwise", &i__4, &ib, &a_ref (i__, i__), lda, &tau[i__], t, &c__65); if (left) { /* H or H' is applied to C(i:m,1:n) */ mi = *m - i__ + 1; ic = i__; } else { /* H or H' is applied to C(1:m,i:n) */ ni = *n - i__ + 1; jc = i__; } /* Apply H or H' */ NUMlapack_dlarfb (side, transt, "Forward", "Rowwise", &mi, &ni, &ib, &a_ref (i__, i__), lda, t, &c__65, &c___ref (ic, jc), ldc, &work[1], &ldwork); /* L10: */ } } work[1] = (double) lwkopt; return 0; } /* NUMlapack_dormlq */ int NUMlapack_dormqr (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c__, long *ldc, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__2 = 2; static long c__65 = 65; /* System generated locals */ char *a__1[2]; long a_dim1, a_offset, c_dim1, c_offset, i__1, i__2, i__3[2], i__4, i__5; char ch__1[2]; /* Local variables */ static long left; static long i__; static double t[4160] /* was [65][64] */ ; static long nbmin, iinfo, i1, i2, i3; static long ib, ic, jc, nb, mi, ni; static long nq, nw; static long notran; static long ldwork, lwkopt; static long lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; --work; /* Function Body */ *info = 0; left = lsame_ (side, "L"); notran = lsame_ (trans, "N"); lquery = *lwork == -1; /* NQ is the order of Q and NW is the minimum dimension of WORK */ if (left) { nq = *m; nw = *n; } else { nq = *n; nw = *m; } if (!left && !lsame_ (side, "R")) { *info = -1; } else if (!notran && !lsame_ (trans, "T")) { *info = -2; } else if (*m < 0) { *info = -3; } else if (*n < 0) { *info = -4; } else if (*k < 0 || *k > nq) { *info = -5; } else if (*lda < MAX (1, nq)) { *info = -7; } else if (*ldc < MAX (1, *m)) { *info = -10; } else if (*lwork < MAX (1, nw) && !lquery) { *info = -12; } if (*info == 0) { /* Determine the block size. NB may be at most NBMAX, where NBMAX is used to define the local array T. Computing MIN Writing concatenation */ i__3[0] = 1, a__1[0] = (char *) side; i__3[1] = 1, a__1[1] = (char *) trans; s_cat (ch__1, (const char **) a__1, i__3, &c__2, 2); i__1 = 64, i__2 = NUMlapack_ilaenv (&c__1, "DORMQR", ch__1, m, n, k, &c_n1, 6, 2); nb = MIN (i__1, i__2); lwkopt = MAX (1, nw) * nb; work[1] = (double) lwkopt; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORMQR", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0 || *k == 0) { work[1] = 1.; return 0; } nbmin = 2; ldwork = nw; if (nb > 1 && nb < *k) { iws = nw * nb; if (*lwork < iws) { nb = *lwork / ldwork; /* Computing MAX Writing concatenation */ i__3[0] = 1, a__1[0] = (char *) side; i__3[1] = 1, a__1[1] = (char *) trans; s_cat (ch__1, (const char **) a__1, i__3, &c__2, 2); i__1 = 2, i__2 = NUMlapack_ilaenv (&c__2, "DORMQR", ch__1, m, n, k, &c_n1, 6, 2); nbmin = MAX (i__1, i__2); } } else { iws = nw; } if (nb < nbmin || nb >= *k) { /* Use unblocked code */ NUMlapack_dorm2r (side, trans, m, n, k, &a[a_offset], lda, &tau[1], &c__[c_offset], ldc, &work[1], &iinfo); } else { /* Use blocked code */ if (left && !notran || !left && notran) { i1 = 1; i2 = *k; i3 = nb; } else { i1 = (*k - 1) / nb * nb + 1; i2 = 1; i3 = -nb; } if (left) { ni = *n; jc = 1; } else { mi = *m; ic = 1; } i__1 = i2; i__2 = i3; for (i__ = i1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Computing MIN */ i__4 = nb, i__5 = *k - i__ + 1; ib = MIN (i__4, i__5); /* Form the triangular factor of the block reflector H = H(i) H(i+1) . . . H(i+ib-1) */ i__4 = nq - i__ + 1; NUMlapack_dlarft ("Forward", "Columnwise", &i__4, &ib, &a_ref (i__, i__), lda, &tau[i__], t, &c__65); if (left) { /* H or H' is applied to C(i:m,1:n) */ mi = *m - i__ + 1; ic = i__; } else { /* H or H' is applied to C(1:m,i:n) */ ni = *n - i__ + 1; jc = i__; } /* Apply H or H' */ NUMlapack_dlarfb (side, trans, "Forward", "Columnwise", &mi, &ni, &ib, &a_ref (i__, i__), lda, t, &c__65, &c___ref (ic, jc), ldc, &work[1], &ldwork); /* L10: */ } } work[1] = (double) lwkopt; return 0; } /* NUMlapack_dormqr */ int NUMlapack_dormr2 (const char *side, const char *trans, long *m, long *n, long *k, double *a, long *lda, double *tau, double *c__, long *ldc, double *work, long *info) { /* System generated locals */ long a_dim1, a_offset, c_dim1, c_offset, i__1, i__2; /* Local variables */ static long left; static long i__; static long i1, i2, i3, mi, ni, nq; static long notran; static double aii; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --tau; c_dim1 = *ldc; c_offset = 1 + c_dim1 * 1; c__ -= c_offset; --work; /* Function Body */ *info = 0; left = lsame_ (side, "L"); notran = lsame_ (trans, "N"); /* NQ is the order of Q */ if (left) { nq = *m; } else { nq = *n; } if (!left && !lsame_ (side, "R")) { *info = -1; } else if (!notran && !lsame_ (trans, "T")) { *info = -2; } else if (*m < 0) { *info = -3; } else if (*n < 0) { *info = -4; } else if (*k < 0 || *k > nq) { *info = -5; } else if (*lda < MAX (1, *k)) { *info = -7; } else if (*ldc < MAX (1, *m)) { *info = -10; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DORMR2", &i__1); return 0; } /* Quick return if possible */ if (*m == 0 || *n == 0 || *k == 0) { return 0; } if (left && !notran || !left && notran) { i1 = 1; i2 = *k; i3 = 1; } else { i1 = *k; i2 = 1; i3 = -1; } if (left) { ni = *n; } else { mi = *m; } i__1 = i2; i__2 = i3; for (i__ = i1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { if (left) { /* H(i) is applied to C(1:m-k+i,1:n) */ mi = *m - *k + i__; } else { /* H(i) is applied to C(1:m,1:n-k+i) */ ni = *n - *k + i__; } /* Apply H(i) */ aii = a_ref (i__, nq - *k + i__); a_ref (i__, nq - *k + i__) = 1.; NUMlapack_dlarf (side, &mi, &ni, &a_ref (i__, 1), lda, &tau[i__], &c__[c_offset], ldc, &work[1]); a_ref (i__, nq - *k + i__) = aii; /* L10: */ } return 0; } /* NUMlapack_dormr2 */ int NUMlapack_dpotf2 (const char *uplo, long *n, double *a, long *lda, long *info) { /* Table of constant values */ static double c_b10 = -1.; static double c_b12 = 1.; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; double d__1; /* Local variables */ static long j; static int upper; static double ajj; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; /* Function Body */ *info = 0; upper = lsame_ (uplo, "U"); if (!upper && !lsame_ (uplo, "L")) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *n)) { *info = -4; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DPOTF2", &i__1); return 0; } /* Quick return if possible */ if (*n == 0) { return 0; } if (upper) { /* Compute the Cholesky factorization A = U'*U. */ i__1 = *n; for (j = 1; j <= i__1; ++j) { /* Compute U(J,J) and test for non-positive-definiteness. */ i__2 = j - 1; ajj = a_ref (j, j) - NUMblas_ddot (&i__2, &a_ref (1, j), &c__1, &a_ref (1, j), &c__1); if (ajj <= 0.) { a_ref (j, j) = ajj; goto L30; } ajj = sqrt (ajj); a_ref (j, j) = ajj; /* Compute elements J+1:N of row J. */ if (j < *n) { i__2 = j - 1; i__3 = *n - j; NUMblas_dgemv ("Transpose", &i__2, &i__3, &c_b10, &a_ref (1, j + 1), lda, &a_ref (1, j), &c__1, &c_b12, &a_ref (j, j + 1), lda); i__2 = *n - j; d__1 = 1. / ajj; NUMblas_dscal (&i__2, &d__1, &a_ref (j, j + 1), lda); } /* L10: */ } } else { /* Compute the Cholesky factorization A = L*L'. */ i__1 = *n; for (j = 1; j <= i__1; ++j) { /* Compute L(J,J) and test for non-positive-definiteness. */ i__2 = j - 1; ajj = a_ref (j, j) - NUMblas_ddot (&i__2, &a_ref (j, 1), lda, &a_ref (j, 1), lda); if (ajj <= 0.) { a_ref (j, j) = ajj; goto L30; } ajj = sqrt (ajj); a_ref (j, j) = ajj; /* Compute elements J+1:N of column J. */ if (j < *n) { i__2 = *n - j; i__3 = j - 1; NUMblas_dgemv ("No transpose", &i__2, &i__3, &c_b10, &a_ref (j + 1, 1), lda, &a_ref (j, 1), lda, &c_b12, &a_ref (j + 1, j), &c__1); i__2 = *n - j; d__1 = 1. / ajj; NUMblas_dscal (&i__2, &d__1, &a_ref (j + 1, j), &c__1); } /* L20: */ } } goto L40; L30: *info = j; L40: return 0; } /* NUMlapack_dpotf2_ */ int NUMlapack_drscl (long *n, double *sa, double *sx, long *incx) { static double cden; static long done; static double cnum, cden1, cnum1; static double bignum, smlnum, mul; --sx; /* Function Body */ if (*n <= 0) { return 0; } /* Get machine parameters */ smlnum = NUMblas_dlamch ("S"); bignum = 1. / smlnum; NUMlapack_dlabad (&smlnum, &bignum); /* Initialize the denominator to SA and the numerator to 1. */ cden = *sa; cnum = 1.; L10: cden1 = cden * smlnum; cnum1 = cnum / bignum; if (fabs (cden1) > fabs (cnum) && cnum != 0.) { /* Pre-multiply X by SMLNUM if CDEN is large compared to CNUM. */ mul = smlnum; done = FALSE; cden = cden1; } else if (fabs (cnum1) > fabs (cden)) { /* Pre-multiply X by BIGNUM if CDEN is small compared to CNUM. */ mul = bignum; done = FALSE; cnum = cnum1; } else { /* Multiply X by CNUM / CDEN and return. */ mul = cnum / cden; done = TRUE; } /* Scale the vector X by MUL */ NUMblas_dscal (n, &mul, &sx[1], incx); if (!done) { goto L10; } return 0; } /* NUMlapack_drscl */ #define z___ref(a_1,a_2) z__[(a_2)*z_dim1 + a_1] int NUMlapack_dsteqr (const char *compz, long *n, double *d__, double *e, double *z__, long *ldz, double *work, long *info) { /* Table of constant values */ static double c_b9 = 0.; static double c_b10 = 1.; static long c__0 = 0; static long c__1 = 1; static long c__2 = 2; /* System generated locals */ long z_dim1, z_offset, i__1, i__2; double d__1, d__2; /* Local variables */ static long lend, jtot; static double b, c__, f, g; static long i__, j, k, l, m; static double p, r__, s; static double anorm; static long l1; static long lendm1, lendp1; static long ii; static long mm, iscale; static double safmin; static double safmax; static long lendsv; static double ssfmin; static long nmaxit, icompz; static double ssfmax; static long lm1, mm1, nm1; static double rt1, rt2, eps; static long lsv; static double tst, eps2; --d__; --e; z_dim1 = *ldz; z_offset = 1 + z_dim1 * 1; z__ -= z_offset; --work; /* Function Body */ *info = 0; if (lsame_ (compz, "N")) { icompz = 0; } else if (lsame_ (compz, "V")) { icompz = 1; } else if (lsame_ (compz, "I")) { icompz = 2; } else { icompz = -1; } if (icompz < 0) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*ldz < 1 || icompz > 0 && *ldz < MAX (1, *n)) { *info = -6; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DSTEQR", &i__1); return 0; } /* Quick return if possible */ if (*n == 0) { return 0; } if (*n == 1) { if (icompz == 2) { z___ref (1, 1) = 1.; } return 0; } /* Determine the unit roundoff and over/underflow thresholds. */ eps = NUMblas_dlamch ("E"); /* Computing 2nd power */ d__1 = eps; eps2 = d__1 * d__1; safmin = NUMblas_dlamch ("S"); safmax = 1. / safmin; ssfmax = sqrt (safmax) / 3.; ssfmin = sqrt (safmin) / eps2; /* Compute the eigenvalues and eigenvectors of the tridiagonal matrix. */ if (icompz == 2) { NUMlapack_dlaset ("Full", n, n, &c_b9, &c_b10, &z__[z_offset], ldz); } nmaxit = *n * 30; jtot = 0; /* Determine where the matrix splits and choose QL or QR iteration for each block, according to whether top or bottom diagonal element is smaller. */ l1 = 1; nm1 = *n - 1; L10: if (l1 > *n) { goto L160; } if (l1 > 1) { e[l1 - 1] = 0.; } if (l1 <= nm1) { i__1 = nm1; for (m = l1; m <= i__1; ++m) { tst = (d__1 = e[m], fabs (d__1)); if (tst == 0.) { goto L30; } if (tst <= sqrt ( (d__1 = d__[m], fabs (d__1))) * sqrt ( (d__2 = d__[m + 1], fabs (d__2))) * eps) { e[m] = 0.; goto L30; } /* L20: */ } } m = *n; L30: l = l1; lsv = l; lend = m; lendsv = lend; l1 = m + 1; if (lend == l) { goto L10; } /* Scale submatrix in rows and columns L to LEND */ i__1 = lend - l + 1; anorm = NUMlapack_dlanst ("I", &i__1, &d__[l], &e[l]); iscale = 0; if (anorm == 0.) { goto L10; } if (anorm > ssfmax) { iscale = 1; i__1 = lend - l + 1; NUMlapack_dlascl ("G", &c__0, &c__0, &anorm, &ssfmax, &i__1, &c__1, &d__[l], n, info); i__1 = lend - l; NUMlapack_dlascl ("G", &c__0, &c__0, &anorm, &ssfmax, &i__1, &c__1, &e[l], n, info); } else if (anorm < ssfmin) { iscale = 2; i__1 = lend - l + 1; NUMlapack_dlascl ("G", &c__0, &c__0, &anorm, &ssfmin, &i__1, &c__1, &d__[l], n, info); i__1 = lend - l; NUMlapack_dlascl ("G", &c__0, &c__0, &anorm, &ssfmin, &i__1, &c__1, &e[l], n, info); } /* Choose between QL and QR iteration */ if ( (d__1 = d__[lend], fabs (d__1)) < (d__2 = d__[l], fabs (d__2))) { lend = lsv; l = lendsv; } if (lend > l) { /* QL Iteration Look for small subdiagonal element. */ L40: if (l != lend) { lendm1 = lend - 1; i__1 = lendm1; for (m = l; m <= i__1; ++m) { /* Computing 2nd power */ d__2 = (d__1 = e[m], fabs (d__1)); tst = d__2 * d__2; if (tst <= eps2 * (d__1 = d__[m], fabs (d__1)) * (d__2 = d__[m + 1], fabs (d__2)) + safmin) { goto L60; } /* L50: */ } } m = lend; L60: if (m < lend) { e[m] = 0.; } p = d__[l]; if (m == l) { goto L80; } /* If remaining matrix is 2-by-2, use DLAE2 or SLAEV2 to compute its eigensystem. */ if (m == l + 1) { if (icompz > 0) { NUMlapack_dlaev2 (&d__[l], &e[l], &d__[l + 1], &rt1, &rt2, &c__, &s); work[l] = c__; work[*n - 1 + l] = s; NUMlapack_dlasr ("R", "V", "B", n, &c__2, &work[l], &work[*n - 1 + l], &z___ref (1, l), ldz); } else { NUMlapack_dlae2 (&d__[l], &e[l], &d__[l + 1], &rt1, &rt2); } d__[l] = rt1; d__[l + 1] = rt2; e[l] = 0.; l += 2; if (l <= lend) { goto L40; } goto L140; } if (jtot == nmaxit) { goto L140; } ++jtot; /* Form shift. */ g = (d__[l + 1] - p) / (e[l] * 2.); r__ = NUMlapack_dlapy2 (&g, &c_b10); g = d__[m] - p + e[l] / (g + d_sign (&r__, &g)); s = 1.; c__ = 1.; p = 0.; /* Inner loop */ mm1 = m - 1; i__1 = l; for (i__ = mm1; i__ >= i__1; --i__) { f = s * e[i__]; b = c__ * e[i__]; NUMlapack_dlartg (&g, &f, &c__, &s, &r__); if (i__ != m - 1) { e[i__ + 1] = r__; } g = d__[i__ + 1] - p; r__ = (d__[i__] - g) * s + c__ * 2. * b; p = s * r__; d__[i__ + 1] = g + p; g = c__ * r__ - b; /* If eigenvectors are desired, then save rotations. */ if (icompz > 0) { work[i__] = c__; work[*n - 1 + i__] = -s; } /* L70: */ } /* If eigenvectors are desired, then apply saved rotations. */ if (icompz > 0) { mm = m - l + 1; NUMlapack_dlasr ("R", "V", "B", n, &mm, &work[l], &work[*n - 1 + l], &z___ref (1, l), ldz); } d__[l] -= p; e[l] = g; goto L40; /* Eigenvalue found. */ L80: d__[l] = p; ++l; if (l <= lend) { goto L40; } goto L140; } else { /* QR Iteration Look for small superdiagonal element. */ L90: if (l != lend) { lendp1 = lend + 1; i__1 = lendp1; for (m = l; m >= i__1; --m) { /* Computing 2nd power */ d__2 = (d__1 = e[m - 1], fabs (d__1)); tst = d__2 * d__2; if (tst <= eps2 * (d__1 = d__[m], fabs (d__1)) * (d__2 = d__[m - 1], fabs (d__2)) + safmin) { goto L110; } /* L100: */ } } m = lend; L110: if (m > lend) { e[m - 1] = 0.; } p = d__[l]; if (m == l) { goto L130; } /* If remaining matrix is 2-by-2, use DLAE2 or SLAEV2 to compute its eigensystem. */ if (m == l - 1) { if (icompz > 0) { NUMlapack_dlaev2 (&d__[l - 1], &e[l - 1], &d__[l], &rt1, &rt2, &c__, &s); work[m] = c__; work[*n - 1 + m] = s; NUMlapack_dlasr ("R", "V", "F", n, &c__2, &work[m], &work[*n - 1 + m], &z___ref (1, l - 1), ldz); } else { NUMlapack_dlae2 (&d__[l - 1], &e[l - 1], &d__[l], &rt1, &rt2); } d__[l - 1] = rt1; d__[l] = rt2; e[l - 1] = 0.; l += -2; if (l >= lend) { goto L90; } goto L140; } if (jtot == nmaxit) { goto L140; } ++jtot; /* Form shift. */ g = (d__[l - 1] - p) / (e[l - 1] * 2.); r__ = NUMlapack_dlapy2 (&g, &c_b10); g = d__[m] - p + e[l - 1] / (g + d_sign (&r__, &g)); s = 1.; c__ = 1.; p = 0.; /* Inner loop */ lm1 = l - 1; i__1 = lm1; for (i__ = m; i__ <= i__1; ++i__) { f = s * e[i__]; b = c__ * e[i__]; NUMlapack_dlartg (&g, &f, &c__, &s, &r__); if (i__ != m) { e[i__ - 1] = r__; } g = d__[i__] - p; r__ = (d__[i__ + 1] - g) * s + c__ * 2. * b; p = s * r__; d__[i__] = g + p; g = c__ * r__ - b; /* If eigenvectors are desired, then save rotations. */ if (icompz > 0) { work[i__] = c__; work[*n - 1 + i__] = s; } /* L120: */ } /* If eigenvectors are desired, then apply saved rotations. */ if (icompz > 0) { mm = l - m + 1; NUMlapack_dlasr ("R", "V", "F", n, &mm, &work[m], &work[*n - 1 + m], &z___ref (1, m), ldz); } d__[l] -= p; e[lm1] = g; goto L90; /* Eigenvalue found. */ L130: d__[l] = p; --l; if (l >= lend) { goto L90; } goto L140; } /* Undo scaling if necessary */ L140: if (iscale == 1) { i__1 = lendsv - lsv + 1; NUMlapack_dlascl ("G", &c__0, &c__0, &ssfmax, &anorm, &i__1, &c__1, &d__[lsv], n, info); i__1 = lendsv - lsv; NUMlapack_dlascl ("G", &c__0, &c__0, &ssfmax, &anorm, &i__1, &c__1, &e[lsv], n, info); } else if (iscale == 2) { i__1 = lendsv - lsv + 1; NUMlapack_dlascl ("G", &c__0, &c__0, &ssfmin, &anorm, &i__1, &c__1, &d__[lsv], n, info); i__1 = lendsv - lsv; NUMlapack_dlascl ("G", &c__0, &c__0, &ssfmin, &anorm, &i__1, &c__1, &e[lsv], n, info); } /* Check for no convergence to an eigenvalue after a total of N*MAXIT iterations. */ if (jtot < nmaxit) { goto L10; } i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { if (e[i__] != 0.) { ++ (*info); } /* L150: */ } goto L190; /* Order eigenvalues and eigenvectors. */ L160: if (icompz == 0) { /* Use Quick Sort */ NUMlapack_dlasrt ("I", n, &d__[1], info); } else { /* Use Selection Sort to minimize swaps of eigenvectors */ i__1 = *n; for (ii = 2; ii <= i__1; ++ii) { i__ = ii - 1; k = i__; p = d__[i__]; i__2 = *n; for (j = ii; j <= i__2; ++j) { if (d__[j] < p) { k = j; p = d__[j]; } /* L170: */ } if (k != i__) { d__[k] = d__[i__]; d__[i__] = p; NUMblas_dswap (n, &z___ref (1, i__), &c__1, &z___ref (1, k), &c__1); } /* L180: */ } } L190: return 0; } /* NUMlapack_dsteqr */ #undef z___ref int NUMlapack_dsterf (long *n, double *d__, double *e, long *info) { /* Table of constant values */ static long c__0 = 0; static long c__1 = 1; static double c_b32 = 1.; /* System generated locals */ long i__1; double d__1, d__2, d__3; /* Local variables */ static double oldc; static long lend, jtot; static double c__; static long i__, l, m; static double p, gamma, r__, s, alpha, sigma, anorm; static long l1; static double bb; static long iscale; static double oldgam, safmin; static double safmax; static long lendsv; static double ssfmin; static long nmaxit; static double ssfmax, rt1, rt2, eps, rte; static long lsv; static double eps2; --e; --d__; /* Function Body */ *info = 0; /* Quick return if possible */ if (*n < 0) { *info = -1; i__1 = - (*info); xerbla_ ("DSTERF", &i__1); return 0; } if (*n <= 1) { return 0; } /* Determine the unit roundoff for this environment. */ eps = NUMblas_dlamch ("E"); /* Computing 2nd power */ d__1 = eps; eps2 = d__1 * d__1; safmin = NUMblas_dlamch ("S"); safmax = 1. / safmin; ssfmax = sqrt (safmax) / 3.; ssfmin = sqrt (safmin) / eps2; /* Compute the eigenvalues of the tridiagonal matrix. */ nmaxit = *n * 30; sigma = 0.; jtot = 0; /* Determine where the matrix splits and choose QL or QR iteration for each block, according to whether top or bottom diagonal element is smaller. */ l1 = 1; L10: if (l1 > *n) { goto L170; } if (l1 > 1) { e[l1 - 1] = 0.; } i__1 = *n - 1; for (m = l1; m <= i__1; ++m) { if ( (d__3 = e[m], fabs (d__3)) <= sqrt ( (d__1 = d__[m], fabs (d__1))) * sqrt ( (d__2 = d__[m + 1], fabs (d__2))) * eps) { e[m] = 0.; goto L30; } /* L20: */ } m = *n; L30: l = l1; lsv = l; lend = m; lendsv = lend; l1 = m + 1; if (lend == l) { goto L10; } /* Scale submatrix in rows and columns L to LEND */ i__1 = lend - l + 1; anorm = NUMlapack_dlanst ("I", &i__1, &d__[l], &e[l]); iscale = 0; if (anorm > ssfmax) { iscale = 1; i__1 = lend - l + 1; NUMlapack_dlascl ("G", &c__0, &c__0, &anorm, &ssfmax, &i__1, &c__1, &d__[l], n, info); i__1 = lend - l; NUMlapack_dlascl ("G", &c__0, &c__0, &anorm, &ssfmax, &i__1, &c__1, &e[l], n, info); } else if (anorm < ssfmin) { iscale = 2; i__1 = lend - l + 1; NUMlapack_dlascl ("G", &c__0, &c__0, &anorm, &ssfmin, &i__1, &c__1, &d__[l], n, info); i__1 = lend - l; NUMlapack_dlascl ("G", &c__0, &c__0, &anorm, &ssfmin, &i__1, &c__1, &e[l], n, info); } i__1 = lend - 1; for (i__ = l; i__ <= i__1; ++i__) { /* Computing 2nd power */ d__1 = e[i__]; e[i__] = d__1 * d__1; /* L40: */ } /* Choose between QL and QR iteration */ if ( (d__1 = d__[lend], fabs (d__1)) < (d__2 = d__[l], fabs (d__2))) { lend = lsv; l = lendsv; } if (lend >= l) { /* QL Iteration Look for small subdiagonal element. */ L50: if (l != lend) { i__1 = lend - 1; for (m = l; m <= i__1; ++m) { if ( (d__2 = e[m], fabs (d__2)) <= eps2 * (d__1 = d__[m] * d__[m + 1], fabs (d__1))) { goto L70; } /* L60: */ } } m = lend; L70: if (m < lend) { e[m] = 0.; } p = d__[l]; if (m == l) { goto L90; } /* If remaining matrix is 2 by 2, use DLAE2 to compute its eigenvalues. */ if (m == l + 1) { rte = sqrt (e[l]); NUMlapack_dlae2 (&d__[l], &rte, &d__[l + 1], &rt1, &rt2); d__[l] = rt1; d__[l + 1] = rt2; e[l] = 0.; l += 2; if (l <= lend) { goto L50; } goto L150; } if (jtot == nmaxit) { goto L150; } ++jtot; /* Form shift. */ rte = sqrt (e[l]); sigma = (d__[l + 1] - p) / (rte * 2.); r__ = NUMlapack_dlapy2 (&sigma, &c_b32); sigma = p - rte / (sigma + d_sign (&r__, &sigma)); c__ = 1.; s = 0.; gamma = d__[m] - sigma; p = gamma * gamma; /* Inner loop */ i__1 = l; for (i__ = m - 1; i__ >= i__1; --i__) { bb = e[i__]; r__ = p + bb; if (i__ != m - 1) { e[i__ + 1] = s * r__; } oldc = c__; c__ = p / r__; s = bb / r__; oldgam = gamma; alpha = d__[i__]; gamma = c__ * (alpha - sigma) - s * oldgam; d__[i__ + 1] = oldgam + (alpha - gamma); if (c__ != 0.) { p = gamma * gamma / c__; } else { p = oldc * bb; } /* L80: */ } e[l] = s * p; d__[l] = sigma + gamma; goto L50; /* Eigenvalue found. */ L90: d__[l] = p; ++l; if (l <= lend) { goto L50; } goto L150; } else { /* QR Iteration Look for small superdiagonal element. */ L100: i__1 = lend + 1; for (m = l; m >= i__1; --m) { if ( (d__2 = e[m - 1], fabs (d__2)) <= eps2 * (d__1 = d__[m] * d__[m - 1], fabs (d__1))) { goto L120; } /* L110: */ } m = lend; L120: if (m > lend) { e[m - 1] = 0.; } p = d__[l]; if (m == l) { goto L140; } /* If remaining matrix is 2 by 2, use DLAE2 to compute its eigenvalues. */ if (m == l - 1) { rte = sqrt (e[l - 1]); NUMlapack_dlae2 (&d__[l], &rte, &d__[l - 1], &rt1, &rt2); d__[l] = rt1; d__[l - 1] = rt2; e[l - 1] = 0.; l += -2; if (l >= lend) { goto L100; } goto L150; } if (jtot == nmaxit) { goto L150; } ++jtot; /* Form shift. */ rte = sqrt (e[l - 1]); sigma = (d__[l - 1] - p) / (rte * 2.); r__ = NUMlapack_dlapy2 (&sigma, &c_b32); sigma = p - rte / (sigma + d_sign (&r__, &sigma)); c__ = 1.; s = 0.; gamma = d__[m] - sigma; p = gamma * gamma; /* Inner loop */ i__1 = l - 1; for (i__ = m; i__ <= i__1; ++i__) { bb = e[i__]; r__ = p + bb; if (i__ != m) { e[i__ - 1] = s * r__; } oldc = c__; c__ = p / r__; s = bb / r__; oldgam = gamma; alpha = d__[i__ + 1]; gamma = c__ * (alpha - sigma) - s * oldgam; d__[i__] = oldgam + (alpha - gamma); if (c__ != 0.) { p = gamma * gamma / c__; } else { p = oldc * bb; } /* L130: */ } e[l - 1] = s * p; d__[l] = sigma + gamma; goto L100; /* Eigenvalue found. */ L140: d__[l] = p; --l; if (l >= lend) { goto L100; } goto L150; } /* Undo scaling if necessary */ L150: if (iscale == 1) { i__1 = lendsv - lsv + 1; NUMlapack_dlascl ("G", &c__0, &c__0, &ssfmax, &anorm, &i__1, &c__1, &d__[lsv], n, info); } if (iscale == 2) { i__1 = lendsv - lsv + 1; NUMlapack_dlascl ("G", &c__0, &c__0, &ssfmin, &anorm, &i__1, &c__1, &d__[lsv], n, info); } /* Check for no convergence to an eigenvalue after a total of N*MAXIT iterations. */ if (jtot < nmaxit) { goto L10; } i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { if (e[i__] != 0.) { ++ (*info); } /* L160: */ } goto L180; /* Sort eigenvalues in increasing order. */ L170: NUMlapack_dlasrt ("I", n, &d__[1], info); L180: return 0; } /* NUMlapack_dsterf */ int NUMlapack_dsyev (const char *jobz, const char *uplo, long *n, double *a, long *lda, double *w, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__0 = 0; static double c_b17 = 1.; /* System generated locals */ long a_dim1, a_offset, i__1, i__2; double d__1; /* Local variables */ static long inde; static double anrm; static long imax; static double rmin, rmax; static long lopt; static double sigma; static long iinfo; static long lower, wantz; static long nb; static long iscale; static double safmin; static double bignum; static long indtau; static long indwrk; static long llwork; static double smlnum; static long lwkopt; static long lquery; static double eps; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --w; --work; /* Function Body */ wantz = lsame_ (jobz, "V"); lower = lsame_ (uplo, "L"); lquery = *lwork == -1; *info = 0; if (! (wantz || lsame_ (jobz, "N"))) { *info = -1; } else if (! (lower || lsame_ (uplo, "U"))) { *info = -2; } else if (*n < 0) { *info = -3; } else if (*lda < MAX (1, *n)) { *info = -5; } else { /* if(complicated condition) */ /* Computing MAX */ i__1 = 1, i__2 = *n * 3 - 1; if (*lwork < MAX (i__1, i__2) && !lquery) { *info = -8; } } if (*info == 0) { nb = NUMlapack_ilaenv (&c__1, "DSYTRD", uplo, n, &c_n1, &c_n1, &c_n1, 6, 1); /* Computing MAX */ i__1 = 1, i__2 = (nb + 2) * *n; lwkopt = MAX (i__1, i__2); work[1] = (double) lwkopt; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DSYEV ", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*n == 0) { work[1] = 1.; return 0; } if (*n == 1) { w[1] = a_ref (1, 1); work[1] = 3.; if (wantz) { a_ref (1, 1) = 1.; } return 0; } /* Get machine constants. */ safmin = NUMblas_dlamch ("Safe minimum"); eps = NUMblas_dlamch ("Precision"); smlnum = safmin / eps; bignum = 1. / smlnum; rmin = sqrt (smlnum); rmax = sqrt (bignum); /* Scale matrix to allowable range, if necessary. */ anrm = NUMlapack_dlansy ("M", uplo, n, &a[a_offset], lda, &work[1]); iscale = 0; if (anrm > 0. && anrm < rmin) { iscale = 1; sigma = rmin / anrm; } else if (anrm > rmax) { iscale = 1; sigma = rmax / anrm; } if (iscale == 1) { NUMlapack_dlascl (uplo, &c__0, &c__0, &c_b17, &sigma, n, n, &a[a_offset], lda, info); } /* Call DSYTRD to reduce symmetric matrix to tridiagonal form. */ inde = 1; indtau = inde + *n; indwrk = indtau + *n; llwork = *lwork - indwrk + 1; NUMlapack_dsytrd (uplo, n, &a[a_offset], lda, &w[1], &work[inde], &work[indtau], &work[indwrk], &llwork, &iinfo); lopt = (long) ( (*n << 1) + work[indwrk]); /* For eigenvalues only, call DSTERF. For eigenvectors, first call DORGTR to generate the orthogonal matrix, then call DSTEQR. */ if (!wantz) { NUMlapack_dsterf (n, &w[1], &work[inde], info); } else { NUMlapack_dorgtr (uplo, n, &a[a_offset], lda, &work[indtau], &work[indwrk], &llwork, &iinfo); NUMlapack_dsteqr (jobz, n, &w[1], &work[inde], &a[a_offset], lda, &work[indtau], info); } /* If matrix was scaled, then rescale eigenvalues appropriately. */ if (iscale == 1) { if (*info == 0) { imax = *n; } else { imax = *info - 1; } d__1 = 1. / sigma; NUMblas_dscal (&imax, &d__1, &w[1], &c__1); } /* Set WORK(1) to optimal workspace size. */ work[1] = (double) lwkopt; return 0; } /* NUMlapack_dsyev */ int NUMlapack_dsytd2 (const char *uplo, long *n, double *a, long *lda, double *d__, double *e, double *tau, long *info) { /* Table of constant values */ static long c__1 = 1; static double c_b8 = 0.; static double c_b14 = -1.; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static double taui; static long i__; static double alpha; static long upper; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --d__; --e; --tau; /* Function Body */ *info = 0; upper = lsame_ (uplo, "U"); if (!upper && !lsame_ (uplo, "L")) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *n)) { *info = -4; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DSYTD2", &i__1); return 0; } /* Quick return if possible */ if (*n <= 0) { return 0; } if (upper) { /* Reduce the upper triangle of A */ for (i__ = *n - 1; i__ >= 1; --i__) { /* Generate elementary reflector H(i) = I - tau * v * v' to annihilate A(1:i-1,i+1) */ NUMlapack_dlarfg (&i__, &a_ref (i__, i__ + 1), &a_ref (1, i__ + 1), &c__1, &taui); e[i__] = a_ref (i__, i__ + 1); if (taui != 0.) { /* Apply H(i) from both sides to A(1:i,1:i) */ a_ref (i__, i__ + 1) = 1.; /* Compute x := tau * A * v storing x in TAU(1:i) */ NUMblas_dsymv (uplo, &i__, &taui, &a[a_offset], lda, &a_ref (1, i__ + 1), &c__1, &c_b8, &tau[1], &c__1); /* Compute w := x - 1/2 * tau * (x'*v) * v */ alpha = taui * -.5 * NUMblas_ddot (&i__, &tau[1], &c__1, &a_ref (1, i__ + 1), &c__1); NUMblas_daxpy (&i__, &alpha, &a_ref (1, i__ + 1), &c__1, &tau[1], &c__1); /* Apply the transformation as a rank-2 update: A := A - v * w' - w * v' */ NUMblas_dsyr2 (uplo, &i__, &c_b14, &a_ref (1, i__ + 1), &c__1, &tau[1], &c__1, &a[a_offset], lda); a_ref (i__, i__ + 1) = e[i__]; } d__[i__ + 1] = a_ref (i__ + 1, i__ + 1); tau[i__] = taui; /* L10: */ } d__[1] = a_ref (1, 1); } else { /* Reduce the lower triangle of A */ i__1 = *n - 1; for (i__ = 1; i__ <= i__1; ++i__) { /* Generate elementary reflector H(i) = I - tau * v * v' to annihilate A(i+2:n,i) Computing MIN */ i__2 = i__ + 2; i__3 = *n - i__; NUMlapack_dlarfg (&i__3, &a_ref (i__ + 1, i__), &a_ref (MIN (i__2, *n), i__), &c__1, &taui); e[i__] = a_ref (i__ + 1, i__); if (taui != 0.) { /* Apply H(i) from both sides to A(i+1:n,i+1:n) */ a_ref (i__ + 1, i__) = 1.; /* Compute x := tau * A * v storing y in TAU(i:n-1) */ i__2 = *n - i__; NUMblas_dsymv (uplo, &i__2, &taui, &a_ref (i__ + 1, i__ + 1), lda, &a_ref (i__ + 1, i__), &c__1, &c_b8, &tau[i__], &c__1); /* Compute w := x - 1/2 * tau * (x'*v) * v */ i__2 = *n - i__; alpha = taui * -.5 * NUMblas_ddot (&i__2, &tau[i__], &c__1, &a_ref (i__ + 1, i__), &c__1); i__2 = *n - i__; NUMblas_daxpy (&i__2, &alpha, &a_ref (i__ + 1, i__), &c__1, &tau[i__], &c__1); /* Apply the transformation as a rank-2 update: A := A - v * w' - w * v' */ i__2 = *n - i__; NUMblas_dsyr2 (uplo, &i__2, &c_b14, &a_ref (i__ + 1, i__), &c__1, &tau[i__], &c__1, &a_ref (i__ + 1, i__ + 1), lda); a_ref (i__ + 1, i__) = e[i__]; } d__[i__] = a_ref (i__, i__); tau[i__] = taui; /* L20: */ } d__[*n] = a_ref (*n, *n); } return 0; } /* NUMlapack_dsytd2 */ int NUMlapack_dsytrd (const char *uplo, long *n, double *a, long *lda, double *d__, double *e, double *tau, double *work, long *lwork, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__3 = 3; static long c__2 = 2; static double c_b22 = -1.; static double c_b23 = 1.; /* System generated locals */ long a_dim1, a_offset, i__1, i__2, i__3; /* Local variables */ static long i__, j; static long nbmin, iinfo; static long upper; static long nb, kk, nx; static long ldwork, lwkopt; static long lquery; static long iws; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; --d__; --e; --tau; --work; /* Function Body */ *info = 0; upper = lsame_ (uplo, "U"); lquery = *lwork == -1; if (!upper && !lsame_ (uplo, "L")) { *info = -1; } else if (*n < 0) { *info = -2; } else if (*lda < MAX (1, *n)) { *info = -4; } else if (*lwork < 1 && !lquery) { *info = -9; } if (*info == 0) { /* Determine the block size. */ nb = NUMlapack_ilaenv (&c__1, "DSYTRD", uplo, n, &c_n1, &c_n1, &c_n1, 6, 1); lwkopt = *n * nb; work[1] = (double) lwkopt; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DSYTRD", &i__1); return 0; } else if (lquery) { return 0; } /* Quick return if possible */ if (*n == 0) { work[1] = 1.; return 0; } nx = *n; iws = 1; if (nb > 1 && nb < *n) { /* Determine when to cross over from blocked to unblocked code (last block is always handled by unblocked code). Computing MAX */ i__1 = nb, i__2 = NUMlapack_ilaenv (&c__3, "DSYTRD", uplo, n, &c_n1, &c_n1, &c_n1, 6, 1); nx = MAX (i__1, i__2); if (nx < *n) { /* Determine if workspace is large enough for blocked code. */ ldwork = *n; iws = ldwork * nb; if (*lwork < iws) { /* Not enough workspace to use optimal NB: determine the minimum value of NB, and reduce NB or force use of unblocked code by setting NX = N. Computing MAX */ i__1 = *lwork / ldwork; nb = MAX (i__1, 1); nbmin = NUMlapack_ilaenv (&c__2, "DSYTRD", uplo, n, &c_n1, &c_n1, &c_n1, 6, 1); if (nb < nbmin) { nx = *n; } } } else { nx = *n; } } else { nb = 1; } if (upper) { /* Reduce the upper triangle of A. Columns 1:kk are handled by the unblocked method. */ kk = *n - (*n - nx + nb - 1) / nb * nb; i__1 = kk + 1; i__2 = -nb; for (i__ = *n - nb + 1; i__2 < 0 ? i__ >= i__1 : i__ <= i__1; i__ += i__2) { /* Reduce columns i:i+nb-1 to tridiagonal form and form the matrix W which is needed to update the unreduced part of the matrix */ i__3 = i__ + nb - 1; NUMlapack_dlatrd (uplo, &i__3, &nb, &a[a_offset], lda, &e[1], &tau[1], &work[1], &ldwork); /* Update the unreduced submatrix A(1:i-1,1:i-1), using an update of the form: A := A - V*W' - W*V' */ i__3 = i__ - 1; NUMblas_dsyr2k (uplo, "No transpose", &i__3, &nb, &c_b22, &a_ref (1, i__), lda, &work[1], &ldwork, &c_b23, &a[a_offset], lda); /* Copy superdiagonal elements back into A, and diagonal elements into D */ i__3 = i__ + nb - 1; for (j = i__; j <= i__3; ++j) { a_ref (j - 1, j) = e[j - 1]; d__[j] = a_ref (j, j); /* L10: */ } /* L20: */ } /* Use unblocked code to reduce the last or only block */ NUMlapack_dsytd2 (uplo, &kk, &a[a_offset], lda, &d__[1], &e[1], &tau[1], &iinfo); } else { /* Reduce the lower triangle of A */ i__2 = *n - nx; i__1 = nb; for (i__ = 1; i__1 < 0 ? i__ >= i__2 : i__ <= i__2; i__ += i__1) { /* Reduce columns i:i+nb-1 to tridiagonal form and form the matrix W which is needed to update the unreduced part of the matrix */ i__3 = *n - i__ + 1; NUMlapack_dlatrd (uplo, &i__3, &nb, &a_ref (i__, i__), lda, &e[i__], &tau[i__], &work[1], &ldwork); /* Update the unreduced submatrix A(i+ib:n,i+ib:n), using an update of the form: A := A - V*W' - W*V' */ i__3 = *n - i__ - nb + 1; NUMblas_dsyr2k (uplo, "No transpose", &i__3, &nb, &c_b22, &a_ref (i__ + nb, i__), lda, &work[nb + 1], &ldwork, &c_b23, &a_ref (i__ + nb, i__ + nb), lda); /* Copy subdiagonal elements back into A, and diagonal elements into D */ i__3 = i__ + nb - 1; for (j = i__; j <= i__3; ++j) { a_ref (j + 1, j) = e[j]; d__[j] = a_ref (j, j); /* L30: */ } /* L40: */ } /* Use unblocked code to reduce the last or only block */ i__1 = *n - i__ + 1; NUMlapack_dsytd2 (uplo, &i__1, &a_ref (i__, i__), lda, &d__[i__], &e[i__], &tau[i__], &iinfo); } work[1] = (double) lwkopt; return 0; } /* NUMlapack_dsytrd */ #define b_ref(a_1,a_2) b[(a_2)*b_dim1 + a_1] #define q_ref(a_1,a_2) q[(a_2)*q_dim1 + a_1] #define u_ref(a_1,a_2) u[(a_2)*u_dim1 + a_1] #define v_ref(a_1,a_2) v[(a_2)*v_dim1 + a_1] int NUMlapack_dtgsja (const char *jobu, const char *jobv, const char *jobq, long *m, long *p, long *n, long *k, long *l, double *a, long *lda, double *b, long *ldb, double *tola, double *tolb, double *alpha, double *beta, double *u, long *ldu, double *v, long *ldv, double *q, long *ldq, double *work, long *ncycle, long *info) { /* Table of constant values */ static double c_b13 = 0.; static double c_b14 = 1.; static long c__1 = 1; static double c_b43 = -1.; /* System generated locals */ long a_dim1, a_offset, b_dim1, b_offset, q_dim1, q_offset, u_dim1, u_offset, v_dim1, v_offset, i__1, i__2, i__3, i__4; double d__1; /* Local variables */ static long i__, j; static double gamma; static double a1; static long initq; static double a2, a3, b1; static long initu, initv, wantq, upper; static double b2, b3; static long wantu, wantv; static double error, ssmin; static long kcycle; static double csq, csu, csv, snq, rwk, snu, snv; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; b_dim1 = *ldb; b_offset = 1 + b_dim1 * 1; b -= b_offset; --alpha; --beta; u_dim1 = *ldu; u_offset = 1 + u_dim1 * 1; u -= u_offset; v_dim1 = *ldv; v_offset = 1 + v_dim1 * 1; v -= v_offset; q_dim1 = *ldq; q_offset = 1 + q_dim1 * 1; q -= q_offset; --work; /* Function Body */ initu = lsame_ (jobu, "I"); wantu = initu || lsame_ (jobu, "U"); initv = lsame_ (jobv, "I"); wantv = initv || lsame_ (jobv, "V"); initq = lsame_ (jobq, "I"); wantq = initq || lsame_ (jobq, "Q"); *info = 0; if (! (initu || wantu || lsame_ (jobu, "N"))) { *info = -1; } else if (! (initv || wantv || lsame_ (jobv, "N"))) { *info = -2; } else if (! (initq || wantq || lsame_ (jobq, "N"))) { *info = -3; } else if (*m < 0) { *info = -4; } else if (*p < 0) { *info = -5; } else if (*n < 0) { *info = -6; } else if (*lda < MAX (1, *m)) { *info = -10; } else if (*ldb < MAX (1, *p)) { *info = -12; } else if (*ldu < 1 || wantu && *ldu < *m) { *info = -18; } else if (*ldv < 1 || wantv && *ldv < *p) { *info = -20; } else if (*ldq < 1 || wantq && *ldq < *n) { *info = -22; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DTGSJA", &i__1); return 0; } /* Initialize U, V and Q, if necessary */ if (initu) { NUMlapack_dlaset ("Full", m, m, &c_b13, &c_b14, &u[u_offset], ldu); } if (initv) { NUMlapack_dlaset ("Full", p, p, &c_b13, &c_b14, &v[v_offset], ldv); } if (initq) { NUMlapack_dlaset ("Full", n, n, &c_b13, &c_b14, &q[q_offset], ldq); } /* Loop until convergence */ upper = FALSE; for (kcycle = 1; kcycle <= 40; ++kcycle) { upper = !upper; i__1 = *l - 1; for (i__ = 1; i__ <= i__1; ++i__) { i__2 = *l; for (j = i__ + 1; j <= i__2; ++j) { a1 = 0.; a2 = 0.; a3 = 0.; if (*k + i__ <= *m) { a1 = a_ref (*k + i__, *n - *l + i__); } if (*k + j <= *m) { a3 = a_ref (*k + j, *n - *l + j); } b1 = b_ref (i__, *n - *l + i__); b3 = b_ref (j, *n - *l + j); if (upper) { if (*k + i__ <= *m) { a2 = a_ref (*k + i__, *n - *l + j); } b2 = b_ref (i__, *n - *l + j); } else { if (*k + j <= *m) { a2 = a_ref (*k + j, *n - *l + i__); } b2 = b_ref (j, *n - *l + i__); } NUMlapack_dlags2 (&upper, &a1, &a2, &a3, &b1, &b2, &b3, &csu, &snu, &csv, &snv, &csq, &snq); /* Update (K+I)-th and (K+J)-th rows of matrix A: U'*A */ if (*k + j <= *m) { NUMblas_drot (l, &a_ref (*k + j, *n - *l + 1), lda, &a_ref (*k + i__, *n - *l + 1), lda, &csu, &snu); } /* Update I-th and J-th rows of matrix B: V'*B */ NUMblas_drot (l, &b_ref (j, *n - *l + 1), ldb, &b_ref (i__, *n - *l + 1), ldb, &csv, &snv); /* Update (N-L+I)-th and (N-L+J)-th columns of matrices A and B: A*Q and B*Q Computing MIN */ i__4 = *k + *l; i__3 = MIN (i__4, *m); NUMblas_drot (&i__3, &a_ref (1, *n - *l + j), &c__1, &a_ref (1, *n - *l + i__), &c__1, &csq, &snq); NUMblas_drot (l, &b_ref (1, *n - *l + j), &c__1, &b_ref (1, *n - *l + i__), &c__1, &csq, &snq); if (upper) { if (*k + i__ <= *m) { a_ref (*k + i__, *n - *l + j) = 0.; } b_ref (i__, *n - *l + j) = 0.; } else { if (*k + j <= *m) { a_ref (*k + j, *n - *l + i__) = 0.; } b_ref (j, *n - *l + i__) = 0.; } /* Update orthogonal matrices U, V, Q, if desired. */ if (wantu && *k + j <= *m) { NUMblas_drot (m, &u_ref (1, *k + j), &c__1, &u_ref (1, *k + i__), &c__1, &csu, &snu); } if (wantv) { NUMblas_drot (p, &v_ref (1, j), &c__1, &v_ref (1, i__), &c__1, &csv, &snv); } if (wantq) { NUMblas_drot (n, &q_ref (1, *n - *l + j), &c__1, &q_ref (1, *n - *l + i__), &c__1, &csq, &snq); } /* L10: */ } /* L20: */ } if (!upper) { /* The matrices A13 and B13 were lower triangular at the start of the cycle, and are now upper triangular. Convergence test: test the parallelism of the corresponding rows of A and B. */ error = 0.; /* Computing MIN */ i__2 = *l, i__3 = *m - *k; i__1 = MIN (i__2, i__3); for (i__ = 1; i__ <= i__1; ++i__) { i__2 = *l - i__ + 1; NUMblas_dcopy (&i__2, &a_ref (*k + i__, *n - *l + i__), lda, &work[1], &c__1); i__2 = *l - i__ + 1; NUMblas_dcopy (&i__2, &b_ref (i__, *n - *l + i__), ldb, &work[*l + 1], &c__1); i__2 = *l - i__ + 1; NUMlapack_dlapll (&i__2, &work[1], &c__1, &work[*l + 1], &c__1, &ssmin); error = MAX (error, ssmin); /* L30: */ } if (fabs (error) <= MIN (*tola, *tolb)) { goto L50; } } /* End of cycle loop L40: */ } /* The algorithm has not converged after MAXIT cycles. */ *info = 1; goto L100; L50: /* If ERROR <= MIN(TOLA,TOLB), then the algorithm has converged. Compute the generalized singular value pairs (ALPHA, BETA), and set the triangular matrix R to array A. */ i__1 = *k; for (i__ = 1; i__ <= i__1; ++i__) { alpha[i__] = 1.; beta[i__] = 0.; /* L60: */ } /* Computing MIN */ i__2 = *l, i__3 = *m - *k; i__1 = MIN (i__2, i__3); for (i__ = 1; i__ <= i__1; ++i__) { a1 = a_ref (*k + i__, *n - *l + i__); b1 = b_ref (i__, *n - *l + i__); if (a1 != 0.) { gamma = b1 / a1; /* change sign if necessary */ if (gamma < 0.) { i__2 = *l - i__ + 1; NUMblas_dscal (&i__2, &c_b43, &b_ref (i__, *n - *l + i__), ldb); if (wantv) { NUMblas_dscal (p, &c_b43, &v_ref (1, i__), &c__1); } } d__1 = fabs (gamma); NUMlapack_dlartg (&d__1, &c_b14, &beta[*k + i__], &alpha[*k + i__], &rwk); if (alpha[*k + i__] >= beta[*k + i__]) { i__2 = *l - i__ + 1; d__1 = 1. / alpha[*k + i__]; NUMblas_dscal (&i__2, &d__1, &a_ref (*k + i__, *n - *l + i__), lda); } else { i__2 = *l - i__ + 1; d__1 = 1. / beta[*k + i__]; NUMblas_dscal (&i__2, &d__1, &b_ref (i__, *n - *l + i__), ldb); i__2 = *l - i__ + 1; NUMblas_dcopy (&i__2, &b_ref (i__, *n - *l + i__), ldb, &a_ref (*k + i__, *n - *l + i__), lda); } } else { alpha[*k + i__] = 0.; beta[*k + i__] = 1.; i__2 = *l - i__ + 1; NUMblas_dcopy (&i__2, &b_ref (i__, *n - *l + i__), ldb, &a_ref (*k + i__, *n - *l + i__), lda); } /* L70: */ } /* Post-assignment */ i__1 = *k + *l; for (i__ = *m + 1; i__ <= i__1; ++i__) { alpha[i__] = 0.; beta[i__] = 1.; /* L80: */ } if (*k + *l < *n) { i__1 = *n; for (i__ = *k + *l + 1; i__ <= i__1; ++i__) { alpha[i__] = 0.; beta[i__] = 0.; /* L90: */ } } L100: *ncycle = kcycle; return 0; } /* NUMlapack_dtgsja */ #undef v_ref #undef u_ref #undef q_ref #undef b_ref int NUMlapack_dtrevc (const char *side, const char *howmny, int *select, long *n, double *t, long *ldt, double *vl, long *ldvl, double *vr, long *ldvr, long *mm, long *m, double *work, long *info) { /* Table of constant values */ static int c_false = FALSE; static long c__1 = 1; static double c_b22 = 1.; static double c_b25 = 0.; static long c__2 = 2; static int c_true = TRUE; /* System generated locals */ long t_dim1, t_offset, vl_dim1, vl_offset, vr_dim1, vr_offset, i__1, i__2, i__3; double d__1, d__2, d__3, d__4, d__5, d__6; /* Local variables */ static double beta, emax; static int pair; static int allv; static long ierr; static double unfl, ovfl, smin; static int over; static double vmax; static long jnxt, i__, j, k; static double scale, x[4] /* was [2][2] */ ; static double remax; static int leftv, bothv; static double vcrit; static int somev; static long j1, j2, n2; static double xnorm; static long ii, ki; static long ip, is; static double wi; static double wr; static double bignum; static int rightv; static double smlnum, rec, ulp; #define t_ref(a_1,a_2) t[(a_2)*t_dim1 + a_1] #define x_ref(a_1,a_2) x[(a_2)*2 + a_1 - 3] #define vl_ref(a_1,a_2) vl[(a_2)*vl_dim1 + a_1] #define vr_ref(a_1,a_2) vr[(a_2)*vr_dim1 + a_1] --select; t_dim1 = *ldt; t_offset = 1 + t_dim1 * 1; t -= t_offset; vl_dim1 = *ldvl; vl_offset = 1 + vl_dim1 * 1; vl -= vl_offset; vr_dim1 = *ldvr; vr_offset = 1 + vr_dim1 * 1; vr -= vr_offset; --work; /* Function Body */ bothv = lsame_ (side, "B"); rightv = lsame_ (side, "R") || bothv; leftv = lsame_ (side, "L") || bothv; allv = lsame_ (howmny, "A"); over = lsame_ (howmny, "B"); somev = lsame_ (howmny, "S"); *info = 0; if (!rightv && !leftv) { *info = -1; } else if (!allv && !over && !somev) { *info = -2; } else if (*n < 0) { *info = -4; } else if (*ldt < MAX (1, *n)) { *info = -6; } else if (*ldvl < 1 || leftv && *ldvl < *n) { *info = -8; } else if (*ldvr < 1 || rightv && *ldvr < *n) { *info = -10; } else { /* Set M to the number of columns required to store the selected eigenvectors, standardize the array SELECT if necessary, and test MM. */ if (somev) { *m = 0; pair = FALSE; i__1 = *n; for (j = 1; j <= i__1; ++j) { if (pair) { pair = FALSE; select[j] = FALSE; } else { if (j < *n) { if (t_ref (j + 1, j) == 0.) { if (select[j]) { ++ (*m); } } else { pair = TRUE; if (select[j] || select[j + 1]) { select[j] = TRUE; *m += 2; } } } else { if (select[*n]) { ++ (*m); } } } /* L10: */ } } else { *m = *n; } if (*mm < *m) { *info = -11; } } if (*info != 0) { i__1 = - (*info); xerbla_ ("NUMlapack_dtrevc", &i__1); return 0; } /* Quick return if possible. */ if (*n == 0) { return 0; } /* Set the constants to control overflow. */ unfl = NUMblas_dlamch ("Safe minimum"); ovfl = 1. / unfl; NUMlapack_dlabad (&unfl, &ovfl); ulp = NUMblas_dlamch ("Precision"); smlnum = unfl * (*n / ulp); bignum = (1. - ulp) / smlnum; /* Compute 1-norm of each column of strictly upper triangular part of T to control overflow in triangular solver. */ work[1] = 0.; i__1 = *n; for (j = 2; j <= i__1; ++j) { work[j] = 0.; i__2 = j - 1; for (i__ = 1; i__ <= i__2; ++i__) { work[j] += (d__1 = t_ref (i__, j), fabs (d__1)); /* L20: */ } /* L30: */ } /* Index IP is used to specify the real or complex eigenvalue: IP = 0, real eigenvalue, 1, first of conjugate complex pair: (wr,wi) -1, second of conjugate complex pair: (wr,wi) */ n2 = *n << 1; if (rightv) { /* Compute right eigenvectors. */ ip = 0; is = *m; for (ki = *n; ki >= 1; --ki) { if (ip == 1) { goto L130; } if (ki == 1) { goto L40; } if (t_ref (ki, ki - 1) == 0.) { goto L40; } ip = -1; L40: if (somev) { if (ip == 0) { if (!select[ki]) { goto L130; } } else { if (!select[ki - 1]) { goto L130; } } } /* Compute the KI-th eigenvalue (WR,WI). */ wr = t_ref (ki, ki); wi = 0.; if (ip != 0) { wi = sqrt ( (d__1 = t_ref (ki, ki - 1), fabs (d__1))) * sqrt ( (d__2 = t_ref (ki - 1, ki), fabs (d__2))); } /* Computing MAX */ d__1 = ulp * (fabs (wr) + fabs (wi)); smin = MAX (d__1, smlnum); if (ip == 0) { /* Real right eigenvector */ work[ki + *n] = 1.; /* Form right-hand side */ i__1 = ki - 1; for (k = 1; k <= i__1; ++k) { work[k + *n] = -t_ref (k, ki); /* L50: */ } /* Solve the upper quasi-triangular system: (T(1:KI-1,1:KI-1) - WR)*X = SCALE*WORK. */ jnxt = ki - 1; for (j = ki - 1; j >= 1; --j) { if (j > jnxt) { goto L60; } j1 = j; j2 = j; jnxt = j - 1; if (j > 1) { if (t_ref (j, j - 1) != 0.) { j1 = j - 1; jnxt = j - 2; } } if (j1 == j2) { /* 1-by-1 diagonal block */ NUMlapack_dlaln2 (&c_false, &c__1, &c__1, &smin, &c_b22, &t_ref (j, j), ldt, &c_b22, &c_b22, &work[j + *n], n, &wr, &c_b25, x, &c__2, &scale, &xnorm, &ierr); /* Scale X(1,1) to avoid overflow when updating the right-hand side. */ if (xnorm > 1.) { if (work[j] > bignum / xnorm) { x_ref (1, 1) = x_ref (1, 1) / xnorm; scale /= xnorm; } } /* Scale if necessary */ if (scale != 1.) { NUMblas_dscal (&ki, &scale, &work[*n + 1], &c__1); } work[j + *n] = x_ref (1, 1); /* Update right-hand side */ i__1 = j - 1; d__1 = -x_ref (1, 1); NUMblas_daxpy (&i__1, &d__1, &t_ref (1, j), &c__1, &work[*n + 1], &c__1); } else { /* 2-by-2 diagonal block */ NUMlapack_dlaln2 (&c_false, &c__2, &c__1, &smin, &c_b22, &t_ref (j - 1, j - 1), ldt, &c_b22, &c_b22, &work[j - 1 + *n], n, &wr, &c_b25, x, &c__2, &scale, &xnorm, &ierr); /* Scale X(1,1) and X(2,1) to avoid overflow when updating the right-hand side. */ if (xnorm > 1.) { /* Computing MAX */ d__1 = work[j - 1], d__2 = work[j]; beta = MAX (d__1, d__2); if (beta > bignum / xnorm) { x_ref (1, 1) = x_ref (1, 1) / xnorm; x_ref (2, 1) = x_ref (2, 1) / xnorm; scale /= xnorm; } } /* Scale if necessary */ if (scale != 1.) { NUMblas_dscal (&ki, &scale, &work[*n + 1], &c__1); } work[j - 1 + *n] = x_ref (1, 1); work[j + *n] = x_ref (2, 1); /* Update right-hand side */ i__1 = j - 2; d__1 = -x_ref (1, 1); NUMblas_daxpy (&i__1, &d__1, &t_ref (1, j - 1), &c__1, &work[*n + 1], &c__1); i__1 = j - 2; d__1 = -x_ref (2, 1); NUMblas_daxpy (&i__1, &d__1, &t_ref (1, j), &c__1, &work[*n + 1], &c__1); } L60: ; } /* Copy the vector x or Q*x to VR and normalize. */ if (!over) { NUMblas_dcopy (&ki, &work[*n + 1], &c__1, &vr_ref (1, is), &c__1); ii = NUMblas_idamax (&ki, &vr_ref (1, is), &c__1); remax = 1. / (d__1 = vr_ref (ii, is), fabs (d__1)); NUMblas_dscal (&ki, &remax, &vr_ref (1, is), &c__1); i__1 = *n; for (k = ki + 1; k <= i__1; ++k) { vr_ref (k, is) = 0.; /* L70: */ } } else { if (ki > 1) { i__1 = ki - 1; NUMblas_dgemv ("N", n, &i__1, &c_b22, &vr[vr_offset], ldvr, &work[*n + 1], &c__1, &work[ki + *n], &vr_ref (1, ki), &c__1); } ii = NUMblas_idamax (n, &vr_ref (1, ki), &c__1); remax = 1. / (d__1 = vr_ref (ii, ki), fabs (d__1)); NUMblas_dscal (n, &remax, &vr_ref (1, ki), &c__1); } } else { /* Complex right eigenvector. Initial solve [ (T(KI-1,KI-1) T(KI-1,KI) ) - (WR + I* WI)]*X = 0. [ (T(KI,KI-1) T(KI,KI) ) ] */ if ( (d__1 = t_ref (ki - 1, ki), fabs (d__1)) >= (d__2 = t_ref (ki, ki - 1), fabs (d__2))) { work[ki - 1 + *n] = 1.; work[ki + n2] = wi / t_ref (ki - 1, ki); } else { work[ki - 1 + *n] = -wi / t_ref (ki, ki - 1); work[ki + n2] = 1.; } work[ki + *n] = 0.; work[ki - 1 + n2] = 0.; /* Form right-hand side */ i__1 = ki - 2; for (k = 1; k <= i__1; ++k) { work[k + *n] = -work[ki - 1 + *n] * t_ref (k, ki - 1); work[k + n2] = -work[ki + n2] * t_ref (k, ki); /* L80: */ } /* Solve upper quasi-triangular system: (T(1:KI-2,1:KI-2) - (WR+i*WI))*X = SCALE*(WORK+i*WORK2) */ jnxt = ki - 2; for (j = ki - 2; j >= 1; --j) { if (j > jnxt) { goto L90; } j1 = j; j2 = j; jnxt = j - 1; if (j > 1) { if (t_ref (j, j - 1) != 0.) { j1 = j - 1; jnxt = j - 2; } } if (j1 == j2) { /* 1-by-1 diagonal block */ NUMlapack_dlaln2 (&c_false, &c__1, &c__2, &smin, &c_b22, &t_ref (j, j), ldt, &c_b22, &c_b22, &work[j + *n], n, &wr, &wi, x, &c__2, &scale, &xnorm, &ierr); /* Scale X(1,1) and X(1,2) to avoid overflow when updating the right-hand side. */ if (xnorm > 1.) { if (work[j] > bignum / xnorm) { x_ref (1, 1) = x_ref (1, 1) / xnorm; x_ref (1, 2) = x_ref (1, 2) / xnorm; scale /= xnorm; } } /* Scale if necessary */ if (scale != 1.) { NUMblas_dscal (&ki, &scale, &work[*n + 1], &c__1); NUMblas_dscal (&ki, &scale, &work[n2 + 1], &c__1); } work[j + *n] = x_ref (1, 1); work[j + n2] = x_ref (1, 2); /* Update the right-hand side */ i__1 = j - 1; d__1 = -x_ref (1, 1); NUMblas_daxpy (&i__1, &d__1, &t_ref (1, j), &c__1, &work[*n + 1], &c__1); i__1 = j - 1; d__1 = -x_ref (1, 2); NUMblas_daxpy (&i__1, &d__1, &t_ref (1, j), &c__1, &work[n2 + 1], &c__1); } else { /* 2-by-2 diagonal block */ NUMlapack_dlaln2 (&c_false, &c__2, &c__2, &smin, &c_b22, &t_ref (j - 1, j - 1), ldt, &c_b22, &c_b22, &work[j - 1 + *n], n, &wr, &wi, x, &c__2, &scale, &xnorm, &ierr); /* Scale X to avoid overflow when updating the right-hand side. */ if (xnorm > 1.) { /* Computing MAX */ d__1 = work[j - 1], d__2 = work[j]; beta = MAX (d__1, d__2); if (beta > bignum / xnorm) { rec = 1. / xnorm; x_ref (1, 1) = x_ref (1, 1) * rec; x_ref (1, 2) = x_ref (1, 2) * rec; x_ref (2, 1) = x_ref (2, 1) * rec; x_ref (2, 2) = x_ref (2, 2) * rec; scale *= rec; } } /* Scale if necessary */ if (scale != 1.) { NUMblas_dscal (&ki, &scale, &work[*n + 1], &c__1); NUMblas_dscal (&ki, &scale, &work[n2 + 1], &c__1); } work[j - 1 + *n] = x_ref (1, 1); work[j + *n] = x_ref (2, 1); work[j - 1 + n2] = x_ref (1, 2); work[j + n2] = x_ref (2, 2); /* Update the right-hand side */ i__1 = j - 2; d__1 = -x_ref (1, 1); NUMblas_daxpy (&i__1, &d__1, &t_ref (1, j - 1), &c__1, &work[*n + 1], &c__1); i__1 = j - 2; d__1 = -x_ref (2, 1); NUMblas_daxpy (&i__1, &d__1, &t_ref (1, j), &c__1, &work[*n + 1], &c__1); i__1 = j - 2; d__1 = -x_ref (1, 2); NUMblas_daxpy (&i__1, &d__1, &t_ref (1, j - 1), &c__1, &work[n2 + 1], &c__1); i__1 = j - 2; d__1 = -x_ref (2, 2); NUMblas_daxpy (&i__1, &d__1, &t_ref (1, j), &c__1, &work[n2 + 1], &c__1); } L90: ; } /* Copy the vector x or Q*x to VR and normalize. */ if (!over) { NUMblas_dcopy (&ki, &work[*n + 1], &c__1, &vr_ref (1, is - 1), &c__1); NUMblas_dcopy (&ki, &work[n2 + 1], &c__1, &vr_ref (1, is), &c__1); emax = 0.; i__1 = ki; for (k = 1; k <= i__1; ++k) { /* Computing MAX */ d__3 = emax, d__4 = (d__1 = vr_ref (k, is - 1), fabs (d__1)) + (d__2 = vr_ref (k, is), fabs (d__2)); emax = MAX (d__3, d__4); /* L100: */ } remax = 1. / emax; NUMblas_dscal (&ki, &remax, &vr_ref (1, is - 1), &c__1); NUMblas_dscal (&ki, &remax, &vr_ref (1, is), &c__1); i__1 = *n; for (k = ki + 1; k <= i__1; ++k) { vr_ref (k, is - 1) = 0.; vr_ref (k, is) = 0.; /* L110: */ } } else { if (ki > 2) { i__1 = ki - 2; NUMblas_dgemv ("N", n, &i__1, &c_b22, &vr[vr_offset], ldvr, &work[*n + 1], &c__1, &work[ki - 1 + *n], &vr_ref (1, ki - 1), &c__1); i__1 = ki - 2; NUMblas_dgemv ("N", n, &i__1, &c_b22, &vr[vr_offset], ldvr, &work[n2 + 1], &c__1, &work[ki + n2], &vr_ref (1, ki), &c__1); } else { NUMblas_dscal (n, &work[ki - 1 + *n], &vr_ref (1, ki - 1), &c__1); NUMblas_dscal (n, &work[ki + n2], &vr_ref (1, ki), &c__1); } emax = 0.; i__1 = *n; for (k = 1; k <= i__1; ++k) { /* Computing MAX */ d__3 = emax, d__4 = (d__1 = vr_ref (k, ki - 1), fabs (d__1)) + (d__2 = vr_ref (k, ki), fabs (d__2)); emax = MAX (d__3, d__4); /* L120: */ } remax = 1. / emax; NUMblas_dscal (n, &remax, &vr_ref (1, ki - 1), &c__1); NUMblas_dscal (n, &remax, &vr_ref (1, ki), &c__1); } } --is; if (ip != 0) { --is; } L130: if (ip == 1) { ip = 0; } if (ip == -1) { ip = 1; } /* L140: */ } } if (leftv) { /* Compute left eigenvectors. */ ip = 0; is = 1; i__1 = *n; for (ki = 1; ki <= i__1; ++ki) { if (ip == -1) { goto L250; } if (ki == *n) { goto L150; } if (t_ref (ki + 1, ki) == 0.) { goto L150; } ip = 1; L150: if (somev) { if (!select[ki]) { goto L250; } } /* Compute the KI-th eigenvalue (WR,WI). */ wr = t_ref (ki, ki); wi = 0.; if (ip != 0) { wi = sqrt ( (d__1 = t_ref (ki, ki + 1), fabs (d__1))) * sqrt ( (d__2 = t_ref (ki + 1, ki), fabs (d__2))); } /* Computing MAX */ d__1 = ulp * (fabs (wr) + fabs (wi)); smin = MAX (d__1, smlnum); if (ip == 0) { /* Real left eigenvector. */ work[ki + *n] = 1.; /* Form right-hand side */ i__2 = *n; for (k = ki + 1; k <= i__2; ++k) { work[k + *n] = -t_ref (ki, k); /* L160: */ } /* Solve the quasi-triangular system: (T(KI+1:N,KI+1:N) - WR)'*X = SCALE*WORK */ vmax = 1.; vcrit = bignum; jnxt = ki + 1; i__2 = *n; for (j = ki + 1; j <= i__2; ++j) { if (j < jnxt) { goto L170; } j1 = j; j2 = j; jnxt = j + 1; if (j < *n) { if (t_ref (j + 1, j) != 0.) { j2 = j + 1; jnxt = j + 2; } } if (j1 == j2) { /* 1-by-1 diagonal block Scale if necessary to avoid overflow when forming the right-hand side. */ if (work[j] > vcrit) { rec = 1. / vmax; i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &rec, &work[ki + *n], &c__1); vmax = 1.; vcrit = bignum; } i__3 = j - ki - 1; work[j + *n] -= NUMblas_ddot (&i__3, &t_ref (ki + 1, j), &c__1, &work[ki + 1 + *n], &c__1); /* Solve (T(J,J)-WR)'*X = WORK */ NUMlapack_dlaln2 (&c_false, &c__1, &c__1, &smin, &c_b22, &t_ref (j, j), ldt, &c_b22, &c_b22, &work[j + *n], n, &wr, &c_b25, x, &c__2, &scale, &xnorm, &ierr); /* Scale if necessary */ if (scale != 1.) { i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &scale, &work[ki + *n], &c__1); } work[j + *n] = x_ref (1, 1); /* Computing MAX */ d__2 = (d__1 = work[j + *n], fabs (d__1)); vmax = MAX (d__2, vmax); vcrit = bignum / vmax; } else { /* 2-by-2 diagonal block Scale if necessary to avoid overflow when forming the right-hand side. Computing MAX */ d__1 = work[j], d__2 = work[j + 1]; beta = MAX (d__1, d__2); if (beta > vcrit) { rec = 1. / vmax; i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &rec, &work[ki + *n], &c__1); vmax = 1.; vcrit = bignum; } i__3 = j - ki - 1; work[j + *n] -= NUMblas_ddot (&i__3, &t_ref (ki + 1, j), &c__1, &work[ki + 1 + *n], &c__1); i__3 = j - ki - 1; work[j + 1 + *n] -= NUMblas_ddot (&i__3, &t_ref (ki + 1, j + 1), &c__1, &work[ki + 1 + *n], &c__1); /* Solve [T(J,J)-WR T(J,J+1) ]'* X = SCALE*( WORK1 ) [T(J+1,J) T(J+1,J+1)-WR] ( WORK2 ) */ NUMlapack_dlaln2 (&c_true, &c__2, &c__1, &smin, &c_b22, &t_ref (j, j), ldt, &c_b22, &c_b22, &work[j + *n], n, &wr, &c_b25, x, &c__2, &scale, &xnorm, &ierr); /* Scale if necessary */ if (scale != 1.) { i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &scale, &work[ki + *n], &c__1); } work[j + *n] = x_ref (1, 1); work[j + 1 + *n] = x_ref (2, 1); /* Computing MAX */ d__3 = (d__1 = work[j + *n], fabs (d__1)), d__4 = (d__2 = work[j + 1 + *n], fabs (d__2)), d__3 = MAX (d__3, d__4); vmax = MAX (d__3, vmax); vcrit = bignum / vmax; } L170: ; } /* Copy the vector x or Q*x to VL and normalize. */ if (!over) { i__2 = *n - ki + 1; NUMblas_dcopy (&i__2, &work[ki + *n], &c__1, &vl_ref (ki, is), &c__1); i__2 = *n - ki + 1; ii = NUMblas_idamax (&i__2, &vl_ref (ki, is), &c__1) + ki - 1; remax = 1. / (d__1 = vl_ref (ii, is), fabs (d__1)); i__2 = *n - ki + 1; NUMblas_dscal (&i__2, &remax, &vl_ref (ki, is), &c__1); i__2 = ki - 1; for (k = 1; k <= i__2; ++k) { vl_ref (k, is) = 0.; /* L180: */ } } else { if (ki < *n) { i__2 = *n - ki; NUMblas_dgemv ("N", n, &i__2, &c_b22, &vl_ref (1, ki + 1), ldvl, &work[ki + 1 + *n], &c__1, &work[ki + *n], &vl_ref (1, ki), &c__1); } ii = NUMblas_idamax (n, &vl_ref (1, ki), &c__1); remax = 1. / (d__1 = vl_ref (ii, ki), fabs (d__1)); NUMblas_dscal (n, &remax, &vl_ref (1, ki), &c__1); } } else { /* Complex left eigenvector. Initial solve: ((T(KI,KI) T(KI,KI+1) )' - (WR - I* WI))*X = 0. ((T(KI+1,KI) T(KI+1,KI+1)) ) */ if ( (d__1 = t_ref (ki, ki + 1), fabs (d__1)) >= (d__2 = t_ref (ki + 1, ki), fabs (d__2))) { work[ki + *n] = wi / t_ref (ki, ki + 1); work[ki + 1 + n2] = 1.; } else { work[ki + *n] = 1.; work[ki + 1 + n2] = -wi / t_ref (ki + 1, ki); } work[ki + 1 + *n] = 0.; work[ki + n2] = 0.; /* Form right-hand side */ i__2 = *n; for (k = ki + 2; k <= i__2; ++k) { work[k + *n] = -work[ki + *n] * t_ref (ki, k); work[k + n2] = -work[ki + 1 + n2] * t_ref (ki + 1, k); /* L190: */ } /* Solve complex quasi-triangular system: ( T(KI+2,N:KI+2,N) - (WR-i*WI) )*X = WORK1+i*WORK2 */ vmax = 1.; vcrit = bignum; jnxt = ki + 2; i__2 = *n; for (j = ki + 2; j <= i__2; ++j) { if (j < jnxt) { goto L200; } j1 = j; j2 = j; jnxt = j + 1; if (j < *n) { if (t_ref (j + 1, j) != 0.) { j2 = j + 1; jnxt = j + 2; } } if (j1 == j2) { /* 1-by-1 diagonal block Scale if necessary to avoid overflow when forming the right-hand side elements. */ if (work[j] > vcrit) { rec = 1. / vmax; i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &rec, &work[ki + *n], &c__1); i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &rec, &work[ki + n2], &c__1); vmax = 1.; vcrit = bignum; } i__3 = j - ki - 2; work[j + *n] -= NUMblas_ddot (&i__3, &t_ref (ki + 2, j), &c__1, &work[ki + 2 + *n], &c__1); i__3 = j - ki - 2; work[j + n2] -= NUMblas_ddot (&i__3, &t_ref (ki + 2, j), &c__1, &work[ki + 2 + n2], &c__1); /* Solve (T(J,J)-(WR-i*WI))*(X11+i*X12)= WK+I*WK2 */ d__1 = -wi; NUMlapack_dlaln2 (&c_false, &c__1, &c__2, &smin, &c_b22, &t_ref (j, j), ldt, &c_b22, &c_b22, &work[j + *n], n, &wr, &d__1, x, &c__2, &scale, &xnorm, &ierr); /* Scale if necessary */ if (scale != 1.) { i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &scale, &work[ki + *n], &c__1); i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &scale, &work[ki + n2], &c__1); } work[j + *n] = x_ref (1, 1); work[j + n2] = x_ref (1, 2); /* Computing MAX */ d__3 = (d__1 = work[j + *n], fabs (d__1)), d__4 = (d__2 = work[j + n2], fabs (d__2)), d__3 = MAX (d__3, d__4); vmax = MAX (d__3, vmax); vcrit = bignum / vmax; } else { /* 2-by-2 diagonal block Scale if necessary to avoid overflow when forming the right-hand side elements. Computing MAX */ d__1 = work[j], d__2 = work[j + 1]; beta = MAX (d__1, d__2); if (beta > vcrit) { rec = 1. / vmax; i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &rec, &work[ki + *n], &c__1); i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &rec, &work[ki + n2], &c__1); vmax = 1.; vcrit = bignum; } i__3 = j - ki - 2; work[j + *n] -= NUMblas_ddot (&i__3, &t_ref (ki + 2, j), &c__1, &work[ki + 2 + *n], &c__1); i__3 = j - ki - 2; work[j + n2] -= NUMblas_ddot (&i__3, &t_ref (ki + 2, j), &c__1, &work[ki + 2 + n2], &c__1); i__3 = j - ki - 2; work[j + 1 + *n] -= NUMblas_ddot (&i__3, &t_ref (ki + 2, j + 1), &c__1, &work[ki + 2 + *n], &c__1); i__3 = j - ki - 2; work[j + 1 + n2] -= NUMblas_ddot (&i__3, &t_ref (ki + 2, j + 1), &c__1, &work[ki + 2 + n2], &c__1); /* Solve 2-by-2 complex linear equation ([T(j,j) T(j,j+1) ]'-(wr-i*wi)*I)*X = SCALE*B ([T(j+1,j) T(j+1,j+1)] ) */ d__1 = -wi; NUMlapack_dlaln2 (&c_true, &c__2, &c__2, &smin, &c_b22, &t_ref (j, j), ldt, &c_b22, &c_b22, &work[j + *n], n, &wr, &d__1, x, &c__2, &scale, &xnorm, &ierr); /* Scale if necessary */ if (scale != 1.) { i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &scale, &work[ki + *n], &c__1); i__3 = *n - ki + 1; NUMblas_dscal (&i__3, &scale, &work[ki + n2], &c__1); } work[j + *n] = x_ref (1, 1); work[j + n2] = x_ref (1, 2); work[j + 1 + *n] = x_ref (2, 1); work[j + 1 + n2] = x_ref (2, 2); /* Computing MAX */ d__5 = (d__1 = x_ref (1, 1), fabs (d__1)), d__6 = (d__2 = x_ref (1, 2), fabs (d__2)), d__5 = MAX (d__5, d__6), d__6 = (d__3 = x_ref (2, 1), fabs (d__3)), d__5 = MAX (d__5, d__6), d__6 = (d__4 = x_ref (2, 2), fabs (d__4)), d__5 = MAX (d__5, d__6); vmax = MAX (d__5, vmax); vcrit = bignum / vmax; } L200: ; } /* Copy the vector x or Q*x to VL and normalize. L210: */ if (!over) { i__2 = *n - ki + 1; NUMblas_dcopy (&i__2, &work[ki + *n], &c__1, &vl_ref (ki, is), &c__1); i__2 = *n - ki + 1; NUMblas_dcopy (&i__2, &work[ki + n2], &c__1, &vl_ref (ki, is + 1), &c__1); emax = 0.; i__2 = *n; for (k = ki; k <= i__2; ++k) { /* Computing MAX */ d__3 = emax, d__4 = (d__1 = vl_ref (k, is), fabs (d__1)) + (d__2 = vl_ref (k, is + 1), fabs (d__2)); emax = MAX (d__3, d__4); /* L220: */ } remax = 1. / emax; i__2 = *n - ki + 1; NUMblas_dscal (&i__2, &remax, &vl_ref (ki, is), &c__1); i__2 = *n - ki + 1; NUMblas_dscal (&i__2, &remax, &vl_ref (ki, is + 1), &c__1); i__2 = ki - 1; for (k = 1; k <= i__2; ++k) { vl_ref (k, is) = 0.; vl_ref (k, is + 1) = 0.; /* L230: */ } } else { if (ki < *n - 1) { i__2 = *n - ki - 1; NUMblas_dgemv ("N", n, &i__2, &c_b22, &vl_ref (1, ki + 2), ldvl, &work[ki + 2 + *n], &c__1, &work[ki + *n], &vl_ref (1, ki), &c__1); i__2 = *n - ki - 1; NUMblas_dgemv ("N", n, &i__2, &c_b22, &vl_ref (1, ki + 2), ldvl, &work[ki + 2 + n2], &c__1, &work[ki + 1 + n2], &vl_ref (1, ki + 1), &c__1); } else { NUMblas_dscal (n, &work[ki + *n], &vl_ref (1, ki), &c__1); NUMblas_dscal (n, &work[ki + 1 + n2], &vl_ref (1, ki + 1), &c__1); } emax = 0.; i__2 = *n; for (k = 1; k <= i__2; ++k) { /* Computing MAX */ d__3 = emax, d__4 = (d__1 = vl_ref (k, ki), fabs (d__1)) + (d__2 = vl_ref (k, ki + 1), fabs (d__2)); emax = MAX (d__3, d__4); /* L240: */ } remax = 1. / emax; NUMblas_dscal (n, &remax, &vl_ref (1, ki), &c__1); NUMblas_dscal (n, &remax, &vl_ref (1, ki + 1), &c__1); } } ++is; if (ip != 0) { ++is; } L250: if (ip == -1) { ip = 0; } if (ip == 1) { ip = -1; } /* L260: */ } } return 0; } /* NUMlapack_dtrevc */ #undef vr_ref #undef vl_ref #undef x_ref #undef t_ref int NUMlapack_dtrti2 (const char *uplo, const char *diag, long *n, double *a, long *lda, long *info) { /* Table of constant values */ static long c__1 = 1; /* System generated locals */ long a_dim1, a_offset, i__1, i__2; /* Local variables */ static long j; static long upper; static long nounit; static double ajj; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; /* Function Body */ *info = 0; upper = lsame_ (uplo, "U"); nounit = lsame_ (diag, "N"); if (!upper && !lsame_ (uplo, "L")) { *info = -1; } else if (!nounit && !lsame_ (diag, "U")) { *info = -2; } else if (*n < 0) { *info = -3; } else if (*lda < MAX (1, *n)) { *info = -5; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DTRTI2", &i__1); return 0; } if (upper) { /* Compute inverse of upper triangular matrix. */ i__1 = *n; for (j = 1; j <= i__1; ++j) { if (nounit) { a_ref (j, j) = 1. / a_ref (j, j); ajj = -a_ref (j, j); } else { ajj = -1.; } /* Compute elements 1:j-1 of j-th column. */ i__2 = j - 1; NUMblas_dtrmv ("Upper", "No transpose", diag, &i__2, &a[a_offset], lda, &a_ref (1, j), &c__1); i__2 = j - 1; NUMblas_dscal (&i__2, &ajj, &a_ref (1, j), &c__1); /* L10: */ } } else { /* Compute inverse of lower triangular matrix. */ for (j = *n; j >= 1; --j) { if (nounit) { a_ref (j, j) = 1. / a_ref (j, j); ajj = -a_ref (j, j); } else { ajj = -1.; } if (j < *n) { /* Compute elements j+1:n of j-th column. */ i__1 = *n - j; NUMblas_dtrmv ("Lower", "No transpose", diag, &i__1, &a_ref (j + 1, j + 1), lda, &a_ref (j + 1, j), &c__1); i__1 = *n - j; NUMblas_dscal (&i__1, &ajj, &a_ref (j + 1, j), &c__1); } /* L20: */ } } return 0; } /* NUMlapack_dtrti2 */ int NUMlapack_dtrtri (const char *uplo, const char *diag, long *n, double *a, long *lda, long *info) { /* Table of constant values */ static long c__1 = 1; static long c_n1 = -1; static long c__2 = 2; static double c_b18 = 1.; static double c_b22 = -1.; /* System generated locals */ char *a__1[2]; long a_dim1, a_offset, i__1, i__2[2], i__3, i__4, i__5; char ch__1[2]; /* Local variables */ static long j; static long upper; static long jb, nb, nn; static long nounit; a_dim1 = *lda; a_offset = 1 + a_dim1 * 1; a -= a_offset; /* Function Body */ *info = 0; upper = lsame_ (uplo, "U"); nounit = lsame_ (diag, "N"); if (!upper && !lsame_ (uplo, "L")) { *info = -1; } else if (!nounit && !lsame_ (diag, "U")) { *info = -2; } else if (*n < 0) { *info = -3; } else if (*lda < MAX (1, *n)) { *info = -5; } if (*info != 0) { i__1 = - (*info); xerbla_ ("DTRTRI", &i__1); return 0; } /* Quick return if possible */ if (*n == 0) { return 0; } /* Check for singularity if non-unit. */ if (nounit) { i__1 = *n; for (*info = 1; *info <= i__1; ++ (*info)) { if (a_ref (*info, *info) == 0.) { return 0; } /* L10: */ } *info = 0; } /* Determine the block size for this environment. Writing concatenation */ i__2[0] = 1, a__1[0] = (char *) uplo; i__2[1] = 1, a__1[1] = (char *) diag; s_cat (ch__1, (const char **) a__1, i__2, &c__2, 2); nb = NUMlapack_ilaenv (&c__1, "DTRTRI", ch__1, n, &c_n1, &c_n1, &c_n1, 6, 2); if (nb <= 1 || nb >= *n) { /* Use unblocked code */ NUMlapack_dtrti2 (uplo, diag, n, &a[a_offset], lda, info); } else { /* Use blocked code */ if (upper) { /* Compute inverse of upper triangular matrix */ i__1 = *n; i__3 = nb; for (j = 1; i__3 < 0 ? j >= i__1 : j <= i__1; j += i__3) { /* Computing MIN */ i__4 = nb, i__5 = *n - j + 1; jb = MIN (i__4, i__5); /* Compute rows 1:j-1 of current block column */ i__4 = j - 1; NUMblas_dtrmm ("Left", "Upper", "No transpose", diag, &i__4, &jb, &c_b18, &a[a_offset], lda, &a_ref (1, j), lda); i__4 = j - 1; NUMblas_dtrsm ("Right", "Upper", "No transpose", diag, &i__4, &jb, &c_b22, &a_ref (j, j), lda, &a_ref (1, j), lda); /* Compute inverse of current diagonal block */ NUMlapack_dtrti2 ("Upper", diag, &jb, &a_ref (j, j), lda, info); /* L20: */ } } else { /* Compute inverse of lower triangular matrix */ nn = (*n - 1) / nb * nb + 1; i__3 = -nb; for (j = nn; i__3 < 0 ? j >= 1 : j <= 1; j += i__3) { /* Computing MIN */ i__1 = nb, i__4 = *n - j + 1; jb = MIN (i__1, i__4); if (j + jb <= *n) { /* Compute rows j+jb:n of current block column */ i__1 = *n - j - jb + 1; NUMblas_dtrmm ("Left", "Lower", "No transpose", diag, &i__1, &jb, &c_b18, &a_ref (j + jb, j + jb), lda, &a_ref (j + jb, j), lda); i__1 = *n - j - jb + 1; NUMblas_dtrsm ("Right", "Lower", "No transpose", diag, &i__1, &jb, &c_b22, &a_ref (j, j), lda, &a_ref (j + jb, j), lda); } /* Compute inverse of current diagonal block */ NUMlapack_dtrti2 ("Lower", diag, &jb, &a_ref (j, j), lda, info); /* L30: */ } } } return 0; } /* NUMlapack_dtrtri */ long NUMlapack_ieeeck (long *ispec, float *zero, float *one) { /* System generated locals */ long ret_val; /* Local variables */ static float neginf, posinf, negzro, newzro, nan1, nan2, nan3, nan4, nan5, nan6; ret_val = 1; posinf = *one / *zero; if (posinf <= *one) { ret_val = 0; return ret_val; } neginf = - (*one) / *zero; if (neginf >= *zero) { ret_val = 0; return ret_val; } negzro = *one / (neginf + *one); if (negzro != *zero) { ret_val = 0; return ret_val; } neginf = *one / negzro; if (neginf >= *zero) { ret_val = 0; return ret_val; } newzro = negzro + *zero; if (newzro != *zero) { ret_val = 0; return ret_val; } posinf = *one / newzro; if (posinf <= *one) { ret_val = 0; return ret_val; } neginf *= posinf; if (neginf >= *zero) { ret_val = 0; return ret_val; } posinf *= posinf; if (posinf <= *one) { ret_val = 0; return ret_val; } /* Return if we were only asked to check infinity arithmetic */ if (*ispec == 0) { return ret_val; } nan1 = posinf + neginf; nan2 = posinf / neginf; nan3 = posinf / posinf; nan4 = posinf * *zero; nan5 = neginf * negzro; nan6 = nan5 * 0.f; if (nan1 == nan1) { ret_val = 0; return ret_val; } if (nan2 == nan2) { ret_val = 0; return ret_val; } if (nan3 == nan3) { ret_val = 0; return ret_val; } if (nan4 == nan4) { ret_val = 0; return ret_val; } if (nan5 == nan5) { ret_val = 0; return ret_val; } if (nan6 == nan6) { ret_val = 0; return ret_val; } return ret_val; } /* NUMlapack_ieeeck */ long NUMlapack_ilaenv (long *ispec, const char *name__, const char *opts, long *n1, long *n2, long *n3, long *n4, long name_len, long opts_len) { /* Table of constant values */ static long c__0 = 0; static float c_b162 = 0.f; static float c_b163 = 1.f; static long c__1 = 1; /* System generated locals */ long ret_val; /* Local variables */ static long i__; static long cname, sname; static long nbmin; static char c1[1], c2[2], c3[3], c4[2]; static long ic, nb; static long iz, nx; static char subnam[6]; (void) opts; (void) n3; (void) opts_len; switch (*ispec) { case 1: goto L100; case 2: goto L100; case 3: goto L100; case 4: goto L400; case 5: goto L500; case 6: goto L600; case 7: goto L700; case 8: goto L800; case 9: goto L900; case 10: goto L1000; case 11: goto L1100; } /* Invalid value for ISPEC */ ret_val = -1; return ret_val; L100: /* Convert NAME to upper case if the first character is lower case. */ ret_val = 1; s_copy (subnam, (char *) name__, 6, name_len); ic = * (unsigned char *) subnam; iz = 'Z'; if (iz == 90 || iz == 122) { /* ASCII character set */ if (ic >= 97 && ic <= 122) { * (unsigned char *) subnam = (char) (ic - 32); for (i__ = 2; i__ <= 6; ++i__) { ic = * (unsigned char *) &subnam[i__ - 1]; if (ic >= 97 && ic <= 122) { * (unsigned char *) &subnam[i__ - 1] = (char) (ic - 32); } /* L10: */ } } } else if (iz == 233 || iz == 169) { /* EBCDIC character set */ if (ic >= 129 && ic <= 137 || ic >= 145 && ic <= 153 || ic >= 162 && ic <= 169) { * (unsigned char *) subnam = (char) (ic + 64); for (i__ = 2; i__ <= 6; ++i__) { ic = * (unsigned char *) &subnam[i__ - 1]; if (ic >= 129 && ic <= 137 || ic >= 145 && ic <= 153 || ic >= 162 && ic <= 169) { * (unsigned char *) &subnam[i__ - 1] = (char) (ic + 64); } /* L20: */ } } } else if (iz == 218 || iz == 250) { /* Prime machines: ASCII+128 */ if (ic >= 225 && ic <= 250) { * (unsigned char *) subnam = (char) (ic - 32); for (i__ = 2; i__ <= 6; ++i__) { ic = * (unsigned char *) &subnam[i__ - 1]; if (ic >= 225 && ic <= 250) { * (unsigned char *) &subnam[i__ - 1] = (char) (ic - 32); } /* L30: */ } } } * (unsigned char *) c1 = * (unsigned char *) subnam; sname = * (unsigned char *) c1 == 'S' || * (unsigned char *) c1 == 'D'; cname = * (unsigned char *) c1 == 'C' || * (unsigned char *) c1 == 'Z'; if (! (cname || sname)) { return ret_val; } s_copy (c2, subnam + 1, 2, 2); s_copy (c3, subnam + 3, 3, 3); s_copy (c4, c3 + 1, 2, 2); switch (*ispec) { case 1: goto L110; case 2: goto L200; case 3: goto L300; } L110: /* ISPEC = 1: block size In these examples, separate code is provided for setting NB for real and complex. We assume that NB will take the same value in single or double precision. */ nb = 1; if (s_cmp (c2, "GE", 2, 2) == 0) { if (s_cmp (c3, "TRF", 3, 3) == 0) { if (sname) { nb = 64; } else { nb = 64; } } else if (s_cmp (c3, "QRF", 3, 3) == 0 || s_cmp (c3, "RQF", 3, 3) == 0 || s_cmp (c3, "LQF", 3, 3) == 0 || s_cmp (c3, "QLF", 3, 3) == 0) { if (sname) { nb = 32; } else { nb = 32; } } else if (s_cmp (c3, "HRD", 3, 3) == 0) { if (sname) { nb = 32; } else { nb = 32; } } else if (s_cmp (c3, "BRD", 3, 3) == 0) { if (sname) { nb = 32; } else { nb = 32; } } else if (s_cmp (c3, "TRI", 3, 3) == 0) { if (sname) { nb = 64; } else { nb = 64; } } } else if (s_cmp (c2, "PO", 2, 2) == 0) { if (s_cmp (c3, "TRF", 3, 3) == 0) { if (sname) { nb = 64; } else { nb = 64; } } } else if (s_cmp (c2, "SY", 2, 2) == 0) { if (s_cmp (c3, "TRF", 3, 3) == 0) { if (sname) { nb = 64; } else { nb = 64; } } else if (sname && s_cmp (c3, "TRD", 3, 3) == 0) { nb = 32; } else if (sname && s_cmp (c3, "GST", 3, 3) == 0) { nb = 64; } } else if (cname && s_cmp (c2, "HE", 2, 2) == 0) { if (s_cmp (c3, "TRF", 3, 3) == 0) { nb = 64; } else if (s_cmp (c3, "TRD", 3, 3) == 0) { nb = 32; } else if (s_cmp (c3, "GST", 3, 3) == 0) { nb = 64; } } else if (sname && s_cmp (c2, "OR", 2, 2) == 0) { if (* (unsigned char *) c3 == 'G') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nb = 32; } } else if (* (unsigned char *) c3 == 'M') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nb = 32; } } } else if (cname && s_cmp (c2, "UN", 2, 2) == 0) { if (* (unsigned char *) c3 == 'G') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nb = 32; } } else if (* (unsigned char *) c3 == 'M') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nb = 32; } } } else if (s_cmp (c2, "GB", 2, 2) == 0) { if (s_cmp (c3, "TRF", 3, 3) == 0) { if (sname) { if (*n4 <= 64) { nb = 1; } else { nb = 32; } } else { if (*n4 <= 64) { nb = 1; } else { nb = 32; } } } } else if (s_cmp (c2, "PB", 2, 2) == 0) { if (s_cmp (c3, "TRF", 3, 3) == 0) { if (sname) { if (*n2 <= 64) { nb = 1; } else { nb = 32; } } else { if (*n2 <= 64) { nb = 1; } else { nb = 32; } } } } else if (s_cmp (c2, "TR", 2, 2) == 0) { if (s_cmp (c3, "TRI", 3, 3) == 0) { if (sname) { nb = 64; } else { nb = 64; } } } else if (s_cmp (c2, "LA", 2, 2) == 0) { if (s_cmp (c3, "UUM", 3, 3) == 0) { if (sname) { nb = 64; } else { nb = 64; } } } else if (sname && s_cmp (c2, "ST", 2, 2) == 0) { if (s_cmp (c3, "EBZ", 3, 3) == 0) { nb = 1; } } ret_val = nb; return ret_val; L200: /* ISPEC = 2: minimum block size */ nbmin = 2; if (s_cmp (c2, "GE", 2, 2) == 0) { if (s_cmp (c3, "QRF", 3, 3) == 0 || s_cmp (c3, "RQF", 3, 3) == 0 || s_cmp (c3, "LQF", 3, 3) == 0 || s_cmp (c3, "QLF", 3, 3) == 0) { if (sname) { nbmin = 2; } else { nbmin = 2; } } else if (s_cmp (c3, "HRD", 3, 3) == 0) { if (sname) { nbmin = 2; } else { nbmin = 2; } } else if (s_cmp (c3, "BRD", 3, 3) == 0) { if (sname) { nbmin = 2; } else { nbmin = 2; } } else if (s_cmp (c3, "TRI", 3, 3) == 0) { if (sname) { nbmin = 2; } else { nbmin = 2; } } } else if (s_cmp (c2, "SY", 2, 2) == 0) { if (s_cmp (c3, "TRF", 3, 3) == 0) { if (sname) { nbmin = 8; } else { nbmin = 8; } } else if (sname && s_cmp (c3, "TRD", 3, 3) == 0) { nbmin = 2; } } else if (cname && s_cmp (c2, "HE", 2, 2) == 0) { if (s_cmp (c3, "TRD", 3, 3) == 0) { nbmin = 2; } } else if (sname && s_cmp (c2, "OR", 2, 2) == 0) { if (* (unsigned char *) c3 == 'G') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nbmin = 2; } } else if (* (unsigned char *) c3 == 'M') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nbmin = 2; } } } else if (cname && s_cmp (c2, "UN", 2, 2) == 0) { if (* (unsigned char *) c3 == 'G') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nbmin = 2; } } else if (* (unsigned char *) c3 == 'M') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nbmin = 2; } } } ret_val = nbmin; return ret_val; L300: /* ISPEC = 3: crossover point */ nx = 0; if (s_cmp (c2, "GE", 2, 2) == 0) { if (s_cmp (c3, "QRF", 3, 3) == 0 || s_cmp (c3, "RQF", 3, 3) == 0 || s_cmp (c3, "LQF", 3, 3) == 0 || s_cmp (c3, "QLF", 3, 3) == 0) { if (sname) { nx = 128; } else { nx = 128; } } else if (s_cmp (c3, "HRD", 3, 3) == 0) { if (sname) { nx = 128; } else { nx = 128; } } else if (s_cmp (c3, "BRD", 3, 3) == 0) { if (sname) { nx = 128; } else { nx = 128; } } } else if (s_cmp (c2, "SY", 2, 2) == 0) { if (sname && s_cmp (c3, "TRD", 3, 3) == 0) { nx = 32; } } else if (cname && s_cmp (c2, "HE", 2, 2) == 0) { if (s_cmp (c3, "TRD", 3, 3) == 0) { nx = 32; } } else if (sname && s_cmp (c2, "OR", 2, 2) == 0) { if (* (unsigned char *) c3 == 'G') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nx = 128; } } } else if (cname && s_cmp (c2, "UN", 2, 2) == 0) { if (* (unsigned char *) c3 == 'G') { if (s_cmp (c4, "QR", 2, 2) == 0 || s_cmp (c4, "RQ", 2, 2) == 0 || s_cmp (c4, "LQ", 2, 2) == 0 || s_cmp (c4, "QL", 2, 2) == 0 || s_cmp (c4, "HR", 2, 2) == 0 || s_cmp (c4, "TR", 2, 2) == 0 || s_cmp (c4, "BR", 2, 2) == 0) { nx = 128; } } } ret_val = nx; return ret_val; L400: /* ISPEC = 4: number of shifts (used by xHSEQR) */ ret_val = 6; return ret_val; L500: /* ISPEC = 5: minimum column dimension (not used) */ ret_val = 2; return ret_val; L600: /* ISPEC = 6: crossover point for SVD (used by xGELSS and xGESVD) */ ret_val = (long) ( (float) MIN (*n1, *n2) * 1.6f); return ret_val; L700: /* ISPEC = 7: number of processors (not used) */ ret_val = 1; return ret_val; L800: /* ISPEC = 8: crossover point for multishift (used by xHSEQR) */ ret_val = 50; return ret_val; L900: /* ISPEC = 9: maximum size of the subproblems at the bottom of the computation tree in the divide-and-conquer algorithm (used by xGELSD and xGESDD) */ ret_val = 25; return ret_val; L1000: /* ISPEC = 10: ieee NaN arithmetic can be trusted not to trap ILAENV = 0 */ ret_val = 1; if (ret_val == 1) { ret_val = NUMlapack_ieeeck (&c__0, &c_b162, &c_b163); } return ret_val; L1100: /* ISPEC = 11: infinity arithmetic can be trusted not to trap ILAENV = 0 */ ret_val = 1; if (ret_val == 1) { ret_val = NUMlapack_ieeeck (&c__1, &c_b162, &c_b163); } return ret_val; } /* NUMlapack_ilaenv */ #undef a_ref #undef c___ref #undef MAX #undef MIN /* End of file NUMclapack.c */ sources_5316/dwsys/NUMlapack.h0000644000176700017670000010151011616314414015057 0ustar paulpaul/* NUMlapack.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020418 Notify that product svd does not work. djmw 20110308 Latest modification */ #ifndef _NUMlapack_h_ #define _NUMlapack_h_ #ifndef _NUM2_h_ #include "NUM2.h" #endif #define NUM_NOTRANSPOSE 0 #define NUM_TRANSPOSE 1 #define NUM_LEFT 0 #define NUM_RIGHT 1 #define NUM_BYROW 1 #define NUM_BYCOLUMN 0 /* From: http://www.netlib.org/lapack/faq.html LAPACK is a freely-available software package. It is available from netlib via anonymous ftp and the World Wide Web. Thus, it can be included in commercial software packages (and has been). We only ask that proper credit be given to the authors. Like all software, it is copyrighted. It is not trademarked, but we do ask the following: If you modify the source for these routines we ask that you change the name of the routine and comment the changes made to the original. We will gladly answer any questions regarding the software. If a modification is done, however, it is the responsibility of the person who modified the outine to provide support. */ /* The following routines are modified C versions of LAPACK fortran sources. Although there also is an official C-version of these fortran routines the latter have severe drawbacks. They all imply call-by-reference and a fortran like array structure (column-wise storage). We have changed the following things: 1. Our matrices are all dimensioned a[1:m, 1:n] (contrary to standard C where numbering starts at 0). 2. All the matrices should be allocated as one contiguous block of storage (in C only the rows need to be contiguously allocated). A number of procedures depend critically on this fact: all procedures that approach the columns of a matrix as a vector by indexing its first element and then using an 'increment' of size 'number of columns' to approach the next elements of the vector. 3. In C, array storage is row wise. The leading dimension hack in many routines therefor works opposite to the fortran implementation: it must be used for indexing COLUMNS instead of rows (lda =1 to index by row, lda=n to index by column). This also implies that the leading dimension of a matrix equals the number of columns. With this trick we can also address vectors from a matrix by column and by row, however we have to use a little trick. In the fortran routines it often happens that a sub-row or a sub-column is passed to a subroutine in which it is referenced as a VECTOR, i.e. someArgument(i). To copy this in C we have to translate call sub (.., A(I,J), ..) into: sub (.., &A[i][j] - 1, ..) We do this with a macro: #define TOVEC(x) &(x) - 1, because our matrices are dimensioned as A[1:m,1:n] For addressing submatrices in C we can not imitate the fortran trick call somesub (..., A(I,J), lda,...), however. We therefor use explicit indexing, i.e., we address the part to be updated: as in NUMapplyFactoredHouseholder (c, rb, re, cb, ce,...) where rb/re and cb/ce refer to the start/end rows and columns, respectively. 3. We changed routine names: dnrm2 NUMnorm2 dlapy2 NUMpythagoras dcopy NUMcopyElements ddot NUMdotproduct daxpy NUMdaxpy dscal NUMvector_scale drot NUMplaneRotation dlas2 NUMsvcmp22 dlartg NUMfindGivens dgeqr2 NUMhouseholderQR dgerq2 NUMhouseholderRQ dgeqpf NUMhouseholderQRwithColumnPivoting dlarfg NUMfindHouseholder dlarf NUMapplyFactoredHouseholder dorm2r NUMapplyFactoredHouseholders dlapll NUMparallelVectors dlapmt NUMpermuteColumns dlasv2 NUMsvdcmp22 dlags2 NUMgsvdcmp22 dtgsja NUMgsvdFromUpperTriangulars dggsvp NUMmatricesToUpperTriangularForms */ #ifdef __cplusplus extern "C" { #endif void NUMidentity (double **a, long rb, long re, long cb); /* Set a[rb:re, cb:cb+re-rb] to identity matrix. */ double NUMpythagoras (double a, double b); /* Returns sqrt (a^2 + b^2), taking care not to cause unnecessary overflow. */ double NUMnorm2 (long n, double *x, long incx); /* Returns the euclidean norm of a vector so that NUMvector_norm2 := sqrt (x'*x) */ double NUMfrobeniusnorm (long m, long n, double **x); /* Returns frobenius norm of matrix sqrt (sum (i=1:m, j=1:n, x[i][j]^2)) */ double NUMdotproduct (long n, double x[], long incx, double y[], long incy); /* Returns the dot product of two vectors. */ void NUMcopyElements (long n, double x[], long incx, double y[], long incy); /* Copies a vector, x, to a vector, y. */ void NUMdaxpy (long n, double da, double x[], long incx, double y[], long incy); /* Constant times a vector plus a vector y[] += da*x[]. */ void NUMvector_scale (long n, double da, double dx[], long incx); /* Scales a vector by a constant. */ void NUMplaneRotation (long n, double x[], long incx, double y[], long incy, double c, double s); /* Rotates vector's x and y. */ void NUMpermuteColumns (int forward, long m, long n, double **x, long *perm); /* Rearranges the columns of the m by n matrix X as specified by the permutation perm[1], perm[2], ..., perm[n] of the integers 1, ..., n. if forward != 0, forward permutation: x[*,perm[j]] is moved to x[*,j] for j = 1, 2, ..., n. if forward == 0, backward permutation: x[*,j] is moved to x[*,perm[j]] for j = 1, 2, ..., n. arguments ========= forward != 0 forward permutation == 0 backward permutation m the number of rows of the matrix X. m > 0. n the number of columns of the matrix X. n > 0. x on entry, the matrix x[1:m, 1:n]. on exit, x contains the permuted matrix X. perm the permutation vector [1..n]. */ void NUMfindHouseholder (long n, double *alpha, double x[], long incx, double *tau); /* Find a real elementary reflector H of order n, such that H * ( alpha ) = ( beta ), H' * H = i. ( x ) ( 0 ) where alpha and beta are scalars, and x is an (n-1)-element real vector. H is represented in the form H = I - tau * ( 1 ) * ( 1 v' ) , ( v ) where tau is a real scalar and v is a real (n-1)-element vector. If the elements of x are all zero, then tau = 0 and H is taken to be the unit matrix. otherwise 1 <= tau <= 2. arguments ========= n the order of the elementary reflector. alpha (input/output) double on entry, the value alpha. on exit, it is overwritten with the value beta. x (input/output) double array, dimension (1+(n-2)*abs(incx)) on entry, the vector x. on exit, it is overwritten with the vector v. incx the increment between elements of x. incx > 0. tau (output) the value tau. */ void NUMfindGivens (double f, double g, double *cs, double *sn, double *r); /* Generate a 2 dimensional rotation so that [ cs sn ] . [ f ] = [ r ] where cs**2 + sn**2 = 1. [ -sn cs ] [ g ] [ 0 ] if g=0, then cs=1 and sn=0. if f=0 and (g != 0), then cs=0 and sn=1 if f exceeds g in magnitude, cs will be positive. Arguments ========= f the first component of vector to be rotated. g the second component of vector to be rotated. cs the cosine of the rotation. sn the sine of the rotation. r the nonzero component of the rotated vector. */ void NUMapplyFactoredHouseholder (double **c, long rb, long re, long cb, long ce, double v[], long incv, double tau, int side); /* Applies a real elementary reflector H to the (rb:re, cb:ce) part of a real matrix C (1:,1;), from either the left or the right. H is represented in the form H = i - tau * v * v' where tau is a real scalar and v is a real vector. if tau = 0, then H is taken to be the unit matrix. arguments ========= side (input) int = NUM_LEFTSIDE: form H * C = NUM_RIGHTSIDE: form C * H rb, re begin/end row of the (sub) matrix. cb, ce begin/end columns of the (sub) matrix. v double array, dimension (1 + (m-1)*abs(incv)) if side = NUM_LEFTSIDE or (1 + (n-1)*abs(incv)) if side = NUM_RIGHTSIDE the vector v in the representation of H. v is not used if tau = 0. incv integer the increment between elements of v. incv <> 0. tau (input) double the value tau in the representation of H. c (input/output) double array, dimension (m,n) on entry, the m by n matrix C. on exit, C is overwritten by the matrix H * C or C * H. */ void NUMapplyFactoredHouseholders (double **c, long rb, long re, long cb, long ce, double **v, long rbv, long rev, long cbv, long cev, long incv, double tau[], int side, int trans); /* Overwrites the general real m by n matrix C with Q * C if side = NUM_LEFTSIDE and trans = NUM_NOTRANSPOSE, or Q'* C if side = NUM_LEFTSIDE and trans = NUM_TRANSPOSE, or C * Q if side = NUM_RIGHTSIDE and trans = NUM_NOTRANSPOSE, or C * Q' if side = NUM_RIGHTSIDE and trans = NUM_TRANSPOSE, where Q is a real orthogonal matrix defined as the product of k elementary reflectors Q = H(1) H(2) . . . H(k) Q is of order m if side = NUM_LEFTSIDE and of order n if side = NUM_RIGHTSIDE. arguments ========= c on entry, the matrix c[rb:re, cb:ce]. on exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q. rb, re begin/end rows of the matrix C. (m = (re-rb+1)) >= 0. cb, ce begin/end columns of the matrix C. (n = (ce-cb+1)) >= 0. k (input) integer the number of elementary reflectors whose product defines the matrix Q. if side = NUM_LEFTSIDE, m >= k >= 0; if side = NUM_RIGHTSIDE, n >= k >= 0. v (input) double array [rbv:rev, cbv:cev]. the i-th row or column must contain the vector which defines the elementary reflector H(i), for i = 1,2,...,k. v is modified by the routine but restored on exit. rbv, rev begin/end rows of the matrix V. cbv, cev begin/end columns of the matrix V. incv the increment between elements of v. incv <> 0. if incv = 1 the H(i) are row vectors if incv > 1 the H(i) are columnvectors tau (input) double array[1:n] tau[i] must contain the scalar factor of the elementary reflector H(i), as returned by one of the QR or RQ factorizations. side (input) int = NUM_LEFTSIDE: apply Q or Q' from the left = NUM_RIGHTSIDE: apply Q or Q' from the right trans (input) int = NUM_NOTRANSPOSE: apply Q (no transpose) = NUM_TRANSPOSE: apply Q' (transpose) */ void NUMeigencmp22 (double a, double b, double c, double *rt1, double *rt2, double *cs1, double *sn1 ); /* NUMeigencmp22 computes the eigendecomposition of a 2-by-2 symmetric matrix [ a b ] [ b c ]. on return, rt1 is the eigenvalue of larger absolute value, rt2 is the eigenvalue of smaller absolute value, and (cs1,sn1) is the unit right eigenvector for rt1, giving the decomposition [ cs1 sn1 ] [ a b ] [ cs1 -sn1 ] = [ rt1 0 ] [-sn1 cs1 ] [ b c ] [ sn1 cs1 ] [ 0 rt2 ]. rt1 is accurate to a few ulps barring over/underflow. rt2 may be inaccurate if there is massive cancellation in the determinant a*c-b*b; higher precision or correctly rounded or correctly truncated arithmetic would be needed to compute rt2 accurately in all cases. cs1 and sn1 are accurate to a few ulps barring over/underflow. overflow is possible only if rt1 is within a factor of 5 of overflow. underflow is harmless if the input data is 0 or exceeds underflow_threshold / macheps. */ void NUMhouseholderQR (double **a, long rb, long re, long cb, long ce, long ncol, double tau[]); /* Computes a QR factorization of a real (sub) matrix (rb:re, cb:ce) of A (:, :lda) A = Q * R. arguments ========= a (input/output) double precision array, dimension (m,n) on entry, the m by n matrix A. on exit, the elements on and above the diagonal of the array contain the min(m,n) by n upper trapezoidal matrix R (R is upper triangular if m >= n); the elements below the diagonal, with the array tau, represent the orthogonal matrix Q as a product of elementary reflectors (see further details). rb, re (input) begin/end rows of the matrix A. (re - rb) >= 0. cb, ce (input) begin/end columns of the matrix A. (ce - cb) >= 0 lda (input) the leading dimension of the array a, i.e., the number of rows. tau (output) double array, dimension (min(m,n)) the scalar factors of the elementary reflectors (see further details). Further details =============== The matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(k), where k = min(m,n). each H(i) has the form H(i) = i - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in a(rb+i-1:ce, cb+i-1), and tau in tau(i). */ void NUMhouseholderQRwithColumnPivoting (long m, long n, double **a, long ncol, long *pivot, double tau[]); /* Computes a QR factorization with column pivoting of a real m-by-n matrix A: A*P = Q*R. arguments ========= m the number of rows of the matrix A. m >= 0. n the number of columns of the matrix A. n >= 0 a on entry, the m-by-n matrix A. on exit, the upper triangle of the array contains the min(m,n)-by-n upper triangular matrix R; the elements below the diagonal, together with the array tau, represent the orthogonal matrix Q as a product of min(m,n) elementary reflectors. ncol the leading dimension of the array A, number of columns pivot on entry, if pivot[i] != 0, the i-th column of A is permuted to the front of A*P (A leading column); if pivot[i] = 0, the i-th column of A is a free column. on exit, if pivot[i] = k, then the i-th column of A*P was the k-th column of A. tau (output) double array, dimension (min(m,n)) the scalar factors of the elementary reflectors. Further details =============== The matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(n) Each H(i) has the form H = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i). The matrix P is represented in pivot as follows: If pivot[j] = i then the jth column of P is the ith canonical unit vector. */ void NUMhouseholderRQ (double **a, long rb, long re, long cb, long ce, double tau[]); /* Computes an RQ factorization of a real m by n matrix A: A = R * Q. arguments ========= rb, re begin/end rows of the matrix A ==> m = re - rb + 1. cb, ce begin/end columns of the matrix A ==> n = ce -cb + 1. a (input/output) double array, dimension (rb:re, cb:ce) on entry, the m by n matrix A. on exit, if m <= n, the upper triangle of the subarray a(1:m,n-m+1:n) contains the m by m upper triangular matrix R; if m >= n, the elements on and above the (m-n)-th subdiagonal contain the m by n upper trapezoidal matrix R; the remaining elements, with the array tau, represent the orthogonal matrix Q as a product of elementary reflectors (see further details). tau (output) double array [1: (min(m,n)]. the scalar factors of the elementary reflectors (see further details). Further details =============== The matrix Q is represented as a product of elementary reflectors Q = H(1) H(2) . . . H(k), where k = min (m,n). each H(i) has the form H(i) = I - tau * v * v' where tau is a real scalar, and v is a real vector with v(n-k+i+1:n) = 0 and v(n-k+i) = 1; v(1:n-k+i-1) is stored on exit in A(m-k+i,1:n-k+i-1), and tau in tau(i). */ void NUMparallelVectors (long n, double x[], long incx, double y[], long incy, double *svmin); /* Given two column vectors x and y, let A = ( x y ). the subroutine first computes the QR factorization of A = Q*R, and then computes the svd of the 2-by-2 upper triangular matrix R. The smaller singular value of R is returned in svmin, which is used as the measurement of the linear dependency of the vectors x and y. arguments ========= n the length of the vectors x and y. x (input/output) double array [1: (1+(n-1)*incx]. on entry, x contains the n-vector x. on exit, x is overwritten. incx the increment between successive elements of x. incx > 0. y (input/output) double array [1: (1+(n-1)*incy]. on entry, y contains the n-vector y. on exit, y is overwritten. incy the increment between successive elements of y. incy > 0. svmin the smallest singular value of the n-by-2 matrix A = ( x y ). */ void NUMsvdcmp22 (double f, double g, double h, double *svmin, double *svmax, double *snr, double *csr, double *snl, double *csl); /* Computes the SVD of a 2x2 triangular matrix: [ csl snl ] . [ f g ] . [ csr -snr ] = [ svmax 0 ] [-snl csl ] [ 0 h ] [ snr csr] [ 0 svmin ] The absolute value of svmax is larger singular value, absolute value of svmin is smaller singular value. Both csr^2 + snr^2 = 1 and csl^2 + snl^2 = 1. Arguments ========= f, g, h the (1,1), (1,2) and (2,2) element of the 2-by-2 matrix. svmin abs(svmin) is the smaller singular value. svmax abs(svmax) is the larger singular value. csl, the vector (csl, snl) is a unit left singular vector for the snl singular value abs(svmax). csr, the vector (csr, snr) is a unit right singular vector for the snr singular value abs(svmax). Further Details =============== Any input parameter may be aliased with any output parameter. Barring over/underflow and assuming a guard digit in subtraction, all output quantities are correct to within a few units in the last place (ulps). In IEEE arithmetic, the code works correctly if one matrix element is infinite. Overflow will not occur unless the largest singular value itself overflows or is within a few ulps of overflow. (On machines with partial overflow, like the Cray, overflow may occur if the largest singular value is within a factor of 2 of overflow.) Underflow is harmless if underflow is gradual. Otherwise, results may correspond to a matrix modified by perturbations of size near the underflow threshold. Z. Bai & J. Demmel (1993), "Computing the generalized singular value decomposition", SIAM J. Sci. Comput. 14, 1464 - 1486. */ void NUMgsvdcmp22 (int upper, int product, double a1, double a2, double a3, double b1, double b2, double b3, double *csu, double *snu, double *csv, double *snv, double *csq, double *snq); /* Compute 2-by-2 orthogonal matrices U, V and Q, such that if (upper) then U'*A*Q = U'*( a1 a2 )*Q = ( x 0 ) ( 0 a3 ) ( x x ) and V'*B*Q = V'*( b1 b2 )*Q = ( x 0 ) ( 0 b3 ) ( x x ) or if (! upper ) then U'*A*Q = U'*( a1 0 )*Q = ( x x ) ( a2 a3 ) ( 0 x ) and V'*B*Q = V'*( b1 0 )*Q = ( x x ) ( b2 b3 ) ( 0 x ) the rows of the transformed A and B are parallel, where U = ( csu snu ), V = ( csv snv ), Q = ( csq snq ) ( -snu csu ) ( -snv csv ) ( -snq csq ) Z' denotes the transpose of Z. Arguments ========= upper != 0: the input matrices A and B are upper triangular. = 0: the input matrices A and B are lower triangular. product if true the product svd is calculated intead of the quotient svd. a1, a2, a3 elements of the input 2-by-2 upper (lower) triangular matrix A. b1, b2, b3 elements of the input 2-by-2 upper (lower) triangular matrix B. csu, snu the desired orthogonal matrix U. csv, snv the desired orthogonal matrix V. csq, snq the desired orthogonal matrix Q. */ void NUMsvcmp22 (double f, double g, double h, double *svmin, double *svmax ); /* Compute the singular values of the 2-by-2 triangular matrix [ f g ] [ 0 h ]. On return, svmin is the smaller singular value and svmax is the larger singular value. Arguments ========= f, g, h the [1,1] [1,2] and [2,1] elements of the 2-by-2 matrix. svmin the smaller singular value. svmax the larger singular value. Further details =============== Barring over/underflow, all output quantities are correct to within a few units in the last place (ulps), even in the absence of a guard digit in addition/subtraction. In ieee arithmetic, the code works correctly if one matrix element is infinite. Overflow will not occur unless the largest singular value itself overflows, or is within a few ulps of overflow (on machines with partial overflow, like the cray, overflow may occur if the largest singular value is within a factor of 2 of overflow). Underflow is harmless if underflow is gradual. Otherwise, results may correspond to a matrix modified by perturbations of size near the underflow threshold. */ void NUMgsvdFromUpperTriangulars (double **a, long m, long n, double **b, long p, int product, long k, long l, double tola, double tolb, double *alpha, double *beta, double **u, double **v, double **q, long *ncycle); /* Computes the generalized singular value decomposition (gsvd) of two real upper triangular (or trapezoidal) matrices A and B. On entry, it is assumed that matrices A and B have the following forms, which may be obtained by the preprocessing subroutine dggsvp from a general m-by-n matrix A and p-by-n matrix B: n-k-l k l A = k ( 0 A12 A13 ) if m-k-l >= 0; l ( 0 0 A23 ) m-k-l ( 0 0 0 ) n-k-l k l A = k ( 0 A12 A13 ) if m-k-l < 0; m-k ( 0 0 A23 ) n-k-l k l B = l ( 0 0 B13 ) p-l ( 0 0 0 ) where the k-by-k matrix A12 and l-by-l matrix B13 are nonsingular upper triangular; A23 is l-by-l upper triangular if m-k-l >= 0, otherwise A23 is (m-k)-by-l upper trapezoidal. On exit, U'*A*Q = D1*( 0 R ), V'*B*Q = D2*( 0 R ), where U, V and Q are orthogonal matrices, Z' denotes the transpose of Z, R is a nonsingular upper triangular matrix, and D1 and D2 are ``diagonal'' matrices, which are of the following structures: if m-k-l >= 0, k l D1 = k ( I 0 ) l ( 0 C ) m-k-l ( 0 0 ) k l D2 = l ( 0 S ) p-l ( 0 0 ) n-k-l k l ( 0 R ) = k ( 0 R11 R12 ) k l ( 0 0 R22 ) l where C = Diag (alpha(k+1), ... , alpha(k+l)), S = Diag (beta(k+1), ... , beta(k+l)), C**2 + S**2 = i. R is stored in A(1:k+l,n-k-l+1:n) on exit. if m-k-l < 0, k m-k k+l-m D1 = k ( I 0 0 ) m-k ( 0 C 0 ) k m-k k+l-m D2 = m-k ( 0 S 0 ) k+l-m ( 0 0 I ) p-l ( 0 0 0 ) n-k-l k m-k k+l-m ( 0 R ) = k ( 0 R11 R12 R13 ) m-k ( 0 0 R22 R23 ) k+l-m ( 0 0 0 R33 ) where C = Diag (alpha(k+1), ... , alpha(m)), S = Diag (beta(k+1), ... , beta(m)), C**2 + S**2 = i. R = ( R11 R12 R13 ) is stored in A(1:m, n-k-l+1:n) and R33 is stored ( 0 R22 R23 ) in B(m-k+1:l,n+m-k-l+1:n) on exit. the computation of the orthogonal transformation matrices U, V or Q is optional. these matrices may either be formed explicitly, or they may be postmultiplied into input matrices U1, V1, or Q1. arguments ========= m the number of rows of the matrix A. m >= 0. p the number of rows of the matrix B. p >= 0. n the number of columns of the matrices A and B. n >= 0. k, l k and l specify the subblocks in the input matrices A and B: A23 = A(k+1:min(k+l,m), n-l+1:n) and B13 = B(1:l, n-l+1:n) of A and B, whose gsvd is going to be computed. see further details. a on entry, the m-by-n matrix A. on exit, A(n-k+1:n, 1:min(k+l,m) ) contains the triangular matrix R or part of R. see purpose for details. b on entry, the p-by-n matrix B. on exit, if necessary, B(m-k+1:l, n+m-k-l+1:n) contains a part of R. see purpose for details. product if true the product svd is calculated instead of the quotient svd tola, the convergence criteria for the Jacobi- Kogbetliantz tolb iteration procedure. Generally, they are the same as used in the preprocessing step, say tola = max(m,n) * norm(a) * macheps, tolb = max(p,n) * norm(b) * macheps. alpha, array[1:n] beta on exit, alpha and beta contain the generalized singular value pairs of A and B; alpha(1:k) = 1, beta(1:k) = 0, and if m-k-l >= 0, alpha(k+1:k+l) = diag(C), beta(k+1:k+l) = diag(S), or if m-k-l < 0, alpha(k+1:m)= C, alpha(m+1:k+l)= 0 beta(k+1:m) = S, beta(m+1:k+l) = 1. furthermore, if k+l < n, alpha(k+l+1:n) = 0 and beta(k+l+1:n) = 0. u on entry, if u != NULL, u must contain a matrix U1 (usually the orthogonal matrix returned by NUMmatricesToUpperTriangularForms). on exit, if u != NULL, u contains the product U1*U. if u == NULL, u is not referenced. v on entry, if v != NULL, v must contain a matrix V1 (usually the orthogonal matrix returned by NUMmatricesToUpperTriangularForms). on exit, if u != NULL, v contains the product V1*V. if u == NULL, v is not referenced. q on entry, if u != NULL, q must contain a matrix Q1 (usually the orthogonal matrix returned by NUMmatricesToUpperTriangularForms). on exit, if u != NULL, q contains the product Q1*Q. if u == NULL, q is not referenced. ncycle the number of cycles required for convergence. internal parameters =================== maxit specifies the total loops that the iterative procedure may take. if after maxit cycles, the routine fails to converge, we return with an error message. Further details =============== NUMgsvdFromUpperTriangulars essentially uses a variant of Kogbetliantz algorithm to reduce min(l,m-k)-by-l triangular (or trapezoidal) matrix A23 and l-by-l matrix B13 to the form: U1'*A13*Q1 = C1*R1; V1'*B13*Q1 = S1*R1, where U1, V1 and Q1 are orthogonal matrix, and Z' is the transpose of Z. C1 and S1 are diagonal matrices satisfying C1**2 + S1**2 = I, and R1 is an l-by-l nonsingular upper triangular matrix. */ void NUMmatricesToUpperTriangularForms (double **a, long m, long n, double **b, long p, double tola, double tolb, long *kk, long *ll, double **u, double **v, double **q); /* Computes orthogonal matrices U, V and Q such that n-k-l k l U'*A*Q = k ( 0 A12 A13 ) if m-k-l >= 0; l ( 0 0 A23 ) m-k-l ( 0 0 0 ) n-k-l k l = k ( 0 A12 A13 ) if m-k-l < 0; m-k ( 0 0 A23 ) n-k-l k l V'*B*Q = l ( 0 0 B13 ) p-l ( 0 0 0 ) where the k-by-k matrix A12 and l-by-l matrix B13 are nonsingular upper triangular; A23 is l-by-l upper triangular if m-k-l >= 0, otherwise A23 is (m-k)-by-l upper trapezoidal. k+l = the effective numerical rank of the (m+p)-by-n matrix (A',B')'. Z' denotes the transpose of Z. This decomposition is the preprocessing step for computing the generalized singular value decomposition (gsvd), see subroutine NUMgsvdFromUpperTriangulars. arguments ========= m the number of rows of the matrix A. m > 0. p the number of rows of the matrix B. p > 0. n the number of columns of the matrices A and B. n > 0. a on entry, the m-by-n matrix A. on exit, A contains the triangular (or trapezoidal) matrix described in the purpose section. b on entry, the p-by-n matrix B. on exit, B contains the triangular matrix described in the purpose section. tola, the thresholds to determine the effective numerical rank of matrix B tolb and a subblock of A. Generally, they are set to tola = max(m,n)*norm(A)*macheps, tolb = max(p,n)*norm(B)*macheps. the size of tola and tolb may affect the size of backward errors of the decomposition. k, l on exit, k and l specify the dimension of the subblocks described in purpose. k + l = effective numerical rank of (A',B')'. u if u != NULL, u contains the orthogonal matrix U. if u == NULL, u is not referenced. v if v != NULL, v contains the orthogonal matrix V. if v == NULL, v is not referenced. q if q != NULL, q contains the orthogonal matrix Q. if q == NULL, q is not referenced. Further details =============== The program uses NUMhouseholderQRwithColumnPivoting for the QR factorization to detect the effective numerical rank of the A matrix. It may be replaced by a better rank determination strategy. */ void NUMgsvdcmp (double **a, long m, long n, double **b, long p, int product, long *k, long *l, double *alpha, double *beta, double **u, double **v, double **q, int invertR); /* Computes the generalized singular value decomposition (gsvd) of an m-by-n real matrix A and p-by-n real matrix B: U'*A*Q = D1*( 0 R ), V'*B*Q = D2*( 0 R ) where U, V and Q are orthogonal matrices, and Z' is the transpose of Z. Let k+l = the effective numerical rank of the matrix (A',B')', then R is a k+l-by-k+l nonsingular upper triangular matrix, D1 and D2 are m-by-(k+l) and p-by-(k+l) "diagonal" matrices and of the following structures, respectively: if m-k-l >= 0, k l D1 = k ( I 0 ) l ( 0 C ) m-k-l ( 0 0 ) k l D2 = l ( 0 S ) p-l ( 0 0 ) n-k-l k l ( 0 R ) = k ( 0 R11 R12 ) l ( 0 0 R22 ) where C = Diag( alpha(k+1), ... , alpha(k+l) ), S = Diag( beta(k+1), ... , beta(k+l) ), C**2 + S**2 = I. R is stored in A(1:k+l,n-k-l+1:n) on exit. if m-k-l < 0, k m-k k+l-m D1 = k ( I 0 0 ) m-k ( 0 C 0 ) k m-k k+l-m D2 = m-k ( 0 S 0 ) k+l-m ( 0 0 I ) p-l ( 0 0 0 ) n-k-l k m-k k+l-m ( 0 R ) = k ( 0 R11 R12 R13 ) m-k ( 0 0 R22 R23 ) k+l-m ( 0 0 0 R33 ) where C = diag( alpha(k+1), ... , alpha(m) ), S = diag( beta(k+1), ... , beta(m) ), C**2 + S**2 = I. (R11 R12 R13 ) is stored in A(1:m, n-k-l+1:n), and R33 is stored ( 0 R22 R23 ) in B(m-k+1:l,n+m-k-l+1:n) on exit. The routine computes C, S, R, and optionally the orthogonal transformation matrices U, V and Q. In particular, if B is an n-by-n nonsingular matrix and product == 0, then the gsvd of A and B implicitly gives the (quotient) svd of A * inv(B): A * inv(B) = U*(D1*inv(D2))*V', If product != 0 then the gsvd of A and B implicitly gives the product svd of A * B: A * B = U * (D1 * D2) * V'. If ( A',B')' has orthonormal columns, then the gsvd of A and B is also equal to the CS decomposition of A and B. Furthermore, the gsvd can be used to derive the solution of the eigenvalue problem: A'*A x = lambda* B'*B x. In some literature, the gsvd of A and B is presented in the form U'*A*X = ( 0 D1 ), V'*B*X = ( 0 D2 ) where U and V are orthogonal and X is nonsingular, D1 and D2 are ``diagonal''. The former gsvd form can be converted to the latter form by taking the nonsingular matrix X as X = Q*( I 0 ) ( 0 inv(R) ). arguments ========= a on entry, the m-by-n matrix A. on exit, a contains the triangular matrix R, or part of R. see purpose for details. m the number of rows of the matrix A. m > 0. n the number of columns of the matrices A and B. n > 0. b on entry, the p-by-n matrix B. on exit, b contains the triangular matrix R if m-k-l < 0. see purpose for details. p the number of rows of the matrix B. p > 0. k, l on exit, k and l specify the dimension of the subblocks described in the purpose section. k + l = effective numerical rank of (A',B')'. product svd of A * B instead of A * inv (B). Watch out: you can only use product=0 (i.e. QSVD). alpha, on exit, alpha and beta contain the generalized singular beta value pairs of A and B; alpha(1:k) = 1, beta(1:k) = 0, and if m-k-l >= 0, alpha(k+1:k+l) = C, beta(k+1:k+l) = S, or if m-k-l < 0, alpha(k+1:m)=C, alpha(m+1:k+l)=0 beta(k+1:m) =S, beta(m+1:k+l) =1 and alpha(k+l+1:n) = 0 beta(k+l+1:n) = 0 u if u != NULL, u contains the m-by-m orthogonal matrix U. if u == NULL, u is not referenced. v if v != NULL, v contains the p-by-p orthogonal matrix V. if v == NULL, v is not referenced. q if q != NULL, q contains the n-by-n orthogonal matrix Q. if q == NULL, q is not referenced. Internal parameters =================== tola double tolb double tola and tolb are the thresholds to determine the effective rank of (A',B')'. Generally, they are set to tola = max(m,n) * norm(A) * macheps, tolb = max(p,n) * norm(B) * macheps. the size of tola and tolb may affect the size of backward errors of the decomposition. */ void NUMtriangularInverse (int upper, int unitDiagonal, long n, double **a); /* Computes inverse of triangular matrix. */ #ifdef __cplusplus } #endif #endif /* _NUMlapack_h_ */ sources_5316/dwsys/Eigen_def.h0000644000176700017670000000210411627163123015111 0ustar paulpaul/* Eigen_def.h * * Copyright (C) 1993-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020813 GPL header */ #define ooSTRUCT Eigen oo_DEFINE_CLASS (Eigen, Data) oo_LONG (numberOfEigenvalues) oo_LONG (dimension) oo_DOUBLE_VECTOR (eigenvalues, numberOfEigenvalues) oo_DOUBLE_MATRIX (eigenvectors, numberOfEigenvalues, dimension) oo_END_CLASS (Eigen) #undef ooSTRUCT /* End of file Eigen_def.h */ sources_5316/dwsys/NUMf2c.h0000644000176700017670000000334611607762412014313 0ustar paulpaul#ifndef _NUMf2c_h_ #define _NUMf2c_h_ /* NUMf2c.h -- Standard Fortran to C header file * Auxiliary f2c routines. * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020923 GPL header djmw 20110308 Latest modification */ #ifdef __cplusplus extern "C" { #endif double d_sign(double *a, double *b); /* returns sign(b)*fabs(a) */ long int lsame_(const char *ca, const char *cb); /* Returns true if ca[0] is the same letter as cb[0] regardless of case. */ double pow_di(double *ap, long *bp); void s_cat(char *lp, const char *rpp[], long rnp[], long *np, long ll); /* Unless compiled with -DNO_OVERWRITE, this variant of s_cat allows the * target of a concatenation to appear on its right-hand side (contrary * to the Fortran 77 Standard, but in accordance with Fortran 90). */ long s_cmp(const char *a0, const char *b0, long la, long lb); void s_copy(register char *a, register char *b, long la, long lb); /* assign strings: a = b (when no null byte at end of string)*/ #ifdef __cplusplus } #endif #endif /* _NUMf2c_h_ */ sources_5316/dwsys/Index.cpp0000644000176700017670000000632211627355523014663 0ustar paulpaul/* Index.c * * Copyright (C) 2005-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20050724 djmw 20061212 Changed info to Melder_writeLine format. djmw 20070102 djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20110304 Thing_new */ #include #include "Index.h" #include "NUM2.h" #include "oo_DESTROY.h" #include "Index_def.h" #include "oo_COPY.h" #include "Index_def.h" #include "oo_EQUAL.h" #include "Index_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Index_def.h" #include "oo_WRITE_TEXT.h" #include "Index_def.h" #include "oo_WRITE_BINARY.h" #include "Index_def.h" #include "oo_READ_TEXT.h" #include "Index_def.h" #include "oo_READ_BINARY.h" #include "Index_def.h" #include "oo_DESCRIPTION.h" #include "Index_def.h" Thing_implement (Index, Data, 0); void structIndex :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of elements: ", Melder_integer (numberOfElements)); } void Index_init (I, long numberOfElements) { iam (Index); if (numberOfElements < 1) { Melder_throw ("Cannot create index without elements."); } my classes = Ordered_create (); my numberOfElements = numberOfElements; my classIndex = NUMvector (1, numberOfElements); } Index Index_extractPart (I, long from, long to) { iam (Index); try { if (from == 0) { from = 1; } if (to == 0) { to = my numberOfElements; } if (to < from || from < 1 || to > my numberOfElements) Melder_throw ("Range should be in interval [1,", my numberOfElements, "]."); autoIndex thee = Data_copy (me); thy numberOfElements = to - from + 1; /* */ for (long i = 1; i <= thy numberOfElements; i++) { thy classIndex[i] = my classIndex[from + i - 1]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": part not extracted."); } } Thing_implement (StringsIndex, Index, 0); StringsIndex StringsIndex_create (long numberOfElements) { try { autoStringsIndex me = (StringsIndex) Thing_new (StringsIndex); Index_init (me.peek(), numberOfElements); return me.transfer(); } catch (MelderError) { Melder_throw ("StringsIndex not created."); } } int StringsIndex_getClass (StringsIndex me, wchar_t *classLabel) { for (long i = 1; i <= my classes -> size; i++) { SimpleString ss = (SimpleString) my classes -> item[i]; if (Melder_wcscmp (ss -> string, classLabel) == 0) { return i; } } return 0; } long StringsIndex_countItems (StringsIndex me, int iclass) { long sum = 0; for (long i = 1; i <= my numberOfElements; i++) if (my classIndex[i] == iclass) { sum++; } return sum; } /* End of Index.c */ sources_5316/dwsys/Permutation.cpp0000644000176700017670000003107311725072313016114 0ustar paulpaul/* Permutation.cpp * * Copyright (C) 2005-2012 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20050706 djmw 20050722 Latest modification. djmw 20061212 Changed info to Melder_writeLine format. djmw 20071012 Added: o_CAN_WRITE_AS_ENCODING.h djmw 20100521 Next and Previous djmw 20100818 Permutation_permuteTwoItems/Numbers djmw 20110304 Thing_new */ #include #include "Permutation.h" #include "oo_DESTROY.h" #include "Permutation_def.h" #include "oo_COPY.h" #include "Permutation_def.h" #include "oo_EQUAL.h" #include "Permutation_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Permutation_def.h" #include "oo_WRITE_TEXT.h" #include "Permutation_def.h" #include "oo_WRITE_BINARY.h" #include "Permutation_def.h" #include "oo_READ_BINARY.h" #include "Permutation_def.h" #include "oo_DESCRIPTION.h" #include "Permutation_def.h" Thing_implement (Permutation, Data, 0); static long Permutation_checkRange (Permutation me, long *from, long *to) { if ( (*from < 0 || *from > my numberOfElements) || (*to < 0 || *to > my numberOfElements)) { Melder_throw (L"Range must be in [1, ", my numberOfElements, "]."); } if (*from == 0) { *from = 1; } if (*to == 0) { *to = my numberOfElements; } return *to - *from + 1; } void Permutation_checkInvariant (Permutation me) { autoPermutation thee = Data_copy (me); NUMsort_l (thy numberOfElements, thy p); for (long i = 1; i <= my numberOfElements; i++) { if (thy p[i] != i) { Melder_throw (me, ":not a valid permutation."); } } } void structPermutation :: v_info () { structData :: v_info (); MelderInfo_writeLine2 (L"Number of elements: ", Melder_integer (numberOfElements)); } void structPermutation :: v_readText (MelderReadText text) { numberOfElements = texgeti4 (text); if (numberOfElements < 1) { Melder_throw (L"Found a negative mumber of elements during reading."); } p = NUMvector_readText_i4 (1, numberOfElements, text, "p"); Permutation_checkInvariant (this); } void Permutation_init (Permutation me, long numberOfElements) { my numberOfElements = numberOfElements; my p = NUMvector (1, numberOfElements); Permutation_sort (me); } Permutation Permutation_create (long numberOfElements) { try { autoPermutation me = Thing_new (Permutation); Permutation_init (me.peek(), numberOfElements); return me.transfer(); } catch (MelderError) { Melder_throw ("Permulation not created."); } } void Permutation_sort (Permutation me) { for (long i = 1; i <= my numberOfElements; i++) { my p[i] = i; } } void Permutation_swapPositions (Permutation me, long i1, long i2) { try { if (i1 < 1 || i1 > my numberOfElements || i2 < 1 || i2 > my numberOfElements) { Melder_throw ("Invalid positions."); } long tmp = my p[i1]; my p[i1] = my p[i2]; my p[i2] = tmp; } catch (MelderError) { Melder_throw (me, ":positions not swapped."); } } void Permutation_swapNumbers (Permutation me, long i1, long i2) { try { long ip = 0; if (i1 < 1 || i1 > my numberOfElements || i2 < 1 || i2 > my numberOfElements) { Melder_throw (""); } if (i1 == i2) { return; } for (long i = 1; i <= my numberOfElements; i++) { if (my p[i] == i1) { my p[i] = i2; ip++; } else if (my p[i] == i2) { my p[i] = i1; ip++; } if (ip == 2) { break; } } Melder_assert (ip == 2); } catch (MelderError) { Melder_throw (me, ": numbers not swapped."); } } void Permutation_swapBlocks (Permutation me, long from, long to, long blocksize) { try { if (blocksize < 1 || blocksize > my numberOfElements) Melder_throw ("Blocksize must be in [1, %d] range.", my numberOfElements / 2); if (from < 0 || from + blocksize - 1 > my numberOfElements || to < 0 || to + blocksize - 1 > my numberOfElements) { Melder_throw (L"Start and finish positions of the two blocks must be in [1,", my numberOfElements, "] range."); } if (from == to) { return; } for (long i = 1; i <= blocksize; i++) { long tmp = my p[from + i - 1]; my p[from + i - 1] = my p[to + i - 1]; my p[to + i - 1] = tmp; } } catch (MelderError) { Melder_throw (me, ": blocks not swapped."); } } void Permutation_permuteRandomly_inline (Permutation me, long from, long to) { try { long n = Permutation_checkRange (me, &from, &to); if (n == 1) { return; } for (long i = from; i < to; i++) { long newpos = NUMrandomInteger (from, to); long pi = my p[i]; my p[i] = my p[newpos]; my p[newpos] = pi; } } catch (MelderError) { Melder_throw (me, ": not permuted randomly."); } } Permutation Permutation_permuteRandomly (Permutation me, long from, long to) { try { autoPermutation thee = Data_copy (me); Permutation_permuteRandomly_inline (thee.peek(), from, to); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not permuted."); } } Permutation Permutation_rotate (Permutation me, long from, long to, long step) { try { long n = Permutation_checkRange (me, &from, &to); step = (step - 1) % n + 1; autoPermutation thee = Data_copy (me); for (long i = from; i <= to; i++) { long ifrom = i + step; if (ifrom > to) { ifrom -= n; } if (ifrom < from) { ifrom += n; } thy p[ifrom] = my p[i]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not rotated."); } } void Permutation_swapOneFromRange (Permutation me, long from, long to, long pos, int forbidsame) { try { long n = Permutation_checkRange (me, &from, &to); long newpos = NUMrandomInteger (from, to); if (newpos == pos && forbidsame) { if (n == 1) { Melder_throw (L"Impossible to satisfy \"forbid same\" constraint within the chosen range."); } while ( (newpos = NUMrandomInteger (from, to)) == pos) { ; } } long tmp = my p[pos]; my p[pos] = my p[newpos]; my p[newpos] = tmp; } catch (MelderError) { Melder_throw (me, ": one from range not swapped."); } } Permutation Permutation_permuteBlocksRandomly (Permutation me, long from, long to, long blocksize, int permuteWithinBlocks, int noDoublets) { try { long n = Permutation_checkRange (me, &from, &to); if (blocksize == 1 || (blocksize >= n && permuteWithinBlocks)) { autoPermutation thee = Permutation_permuteRandomly (me, from, to); return thee.transfer(); } autoPermutation thee = Data_copy (me); if (blocksize >= n) { return thee.transfer(); } long nblocks = n / blocksize, nrest = n % blocksize; if (nrest != 0) Melder_throw ("It is not possible to fit an integer number of blocks " "in the range.\n(The last block is only of size ", nrest, ")."); autoPermutation pblocks = Permutation_create (nblocks); Permutation_permuteRandomly_inline (pblocks.peek(), 1, nblocks); long first = from; for (long iblock = 1; iblock <= nblocks; iblock++, first += blocksize) { /* (n1,n2,n3,...) means: move block n1 to position 1 etc... */ long blocktomove = Permutation_getValueAtIndex (pblocks.peek(), iblock); for (long j = 1; j <= blocksize; j++) { thy p[first - 1 + j] = my p[from - 1 + (blocktomove - 1) * blocksize + j]; } if (permuteWithinBlocks) { long last = first + blocksize - 1; Permutation_permuteRandomly_inline (thee.peek(), first, last); if (noDoublets && iblock > 0 && (thy p[first - 1] % blocksize) == (thy p[first] % blocksize)) { Permutation_swapOneFromRange (thee.peek(), first + 1, last, first, 0); } } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not permuted block randomly."); } } Permutation Permutation_interleave (Permutation me, long from, long to, long blocksize, long offset) { try { long n = Permutation_checkRange (me, &from, &to); long nblocks = n / blocksize; long nrest = n % blocksize; if (nrest != 0) Melder_throw ("There is not an integer number of blocks in the range.\n" "(The last block is only of size ", nrest, L" instead of ", blocksize, ")."); if (offset >= blocksize) { Melder_throw (L"Offset must be smaller than blocksize."); } autoPermutation thee = Data_copy (me); if (nblocks == 1) { return thee.transfer(); } autoNUMvector occupied (1, blocksize); long posinblock = 1 - offset; for (long i = 1; i <= n; i++) { long index, rblock = (i - 1) % nblocks + 1; posinblock += offset; if (posinblock > blocksize) { posinblock -= blocksize; } if (i % nblocks == 1) { long count = blocksize; while (occupied[posinblock] == 1 && count > 0) { posinblock++; count--; if (posinblock > blocksize) { posinblock -= blocksize; } } occupied[posinblock] = 1; } index = from - 1 + (rblock - 1) * blocksize + posinblock; thy p[from - 1 + i] = my p[index]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not interleaved."); } } long Permutation_getValueAtIndex (Permutation me, long i) { return i > 0 && i <= my numberOfElements ? my p[i] : -1; } long Permutation_getIndexAtValue (Permutation me, long value) { for (long i = 1; i <= my numberOfElements; i++) { if (my p[i] == value) { return i; } } return -1; } Permutation Permutation_invert (Permutation me) { try { autoPermutation thee = Data_copy (me); for (long i = 1; i <= my numberOfElements; i++) { thy p[my p[i]] = i; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not inverted."); } } Permutation Permutation_reverse (Permutation me, long from, long to) { try { long n = Permutation_checkRange (me, &from, &to); autoPermutation thee = Data_copy (me); for (long i = 1; i <= n; i++) { thy p[from + i - 1] = my p[to - i + 1]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not reversed."); } } /* Replaces p with the next permutation (in the standard lexicographical ordering. Adapted from the GSL library */ void Permutation_next_inline (Permutation me) { long size = my numberOfElements; long *p = & my p[1]; if (size < 2) { Melder_throw ("Only one element."); } long i = size - 2; while ( (p[i] > p[i + 1]) && (i != 0)) { i--; } if ( (i == 0) && (p[0] > p[1])) { Melder_throw ("No next."); } long k = i + 1; for (long j = i + 2; j < size; j++) { if ( (p[j] > p[i]) && (p[j] < p[k])) { k = j; } } long tmp = p[i]; p[i] = p[k]; p[k] = tmp; for (long j = i + 1; j <= ( (size + i) / 2); j++) { tmp = p[j]; p[j] = p[size + i - j]; p[size + i - j] = tmp; } } /* Replaces p with the previous permutation (in the standard lexicographical ordering. Adapted from the GSL library */ void Permutation_previous_inline (Permutation me) { long size = my numberOfElements; long *p = & my p[1]; if (size < 2) { Melder_throw ("Only one element."); } long i = size - 2; while ( (p[i] < p[i + 1]) && (i != 0)) { i--; } if ( (i == 0) && (p[0] < p[1])) { Melder_throw ("No previous"); } long k = i + 1; for (long j = i + 2; j < size; j++) { if ( (p[j] < p[i]) && (p[j] > p[k])) { k = j; } } long tmp = p[i]; p[i] = p[k]; p[k] = tmp; for (long j = i + 1; j <= ( (size + i) / 2); j++) { tmp = p[j]; p[j] = p[size + i - j]; p[size + i - j] = tmp; } } Permutation Permutations_multiply2 (Permutation me, Permutation thee) { try { if (my numberOfElements != thy numberOfElements) { Melder_throw ("Number of elements must be equal."); } autoPermutation him = Data_copy (me); for (long i = 1; i <= my numberOfElements; i++) { his p[i] = my p[thy p[i]]; } return him.transfer(); } catch (MelderError) { Melder_throw (me, " & ", thee, " not multiplied."); } } Permutation Permutations_multiply (Collection me) { try { if (my size < 2) { Melder_throw ("There must be at least 2 Permutations in the set."); } autoPermutation thee = Permutations_multiply2 ( (Permutation) my item[1], (Permutation) my item[2]); for (long i = 3; i <= my size; i++) { thee.reset (Permutations_multiply2 (thee.peek(), (Permutation) my item[i])); } return thee.transfer(); } catch (MelderError) { Melder_throw ("Permutations not multiplied."); } } /* End of Permutation.c */ sources_5316/dwsys/NUMfft_core.h0000644000176700017670000005774410567037070015442 0ustar paulpaul/******************************************************************** * * * THIS FILE IS PART OF THE OggSQUISH SOFTWARE CODEC SOURCE CODE. * * * ******************************************************************** function: Fast discrete Fourier and cosine transforms and inverses author: Monty modifications by: Monty last modification date: Jul 1 1996 djmw 20030630 Adapted for praat (replaced 'int' declarations with 'long'). djmw 20040511 Made all local variables type double to increase numerical precision. ********************************************************************/ /* These Fourier routines were originally based on the Fourier routines of the same names from the NETLIB bihar and fftpack fortran libraries developed by Paul N. Swarztrauber at the National Center for Atmospheric Research in Boulder, CO USA. They have been reimplemented in C and optimized in a few ways for OggSquish. */ /* As the original fortran libraries are public domain, the C Fourier routines in this file are hereby released to the public domain as well. The C routines here produce output exactly equivalent to the original fortran routines. Of particular interest are the facts that (like the original fortran), these routines can work on arbitrary length vectors that need not be powers of two in length. */ static void drfti1 (long n, FFT_DATA_TYPE * wa, long *ifac) { static long ntryh[4] = { 4, 2, 3, 5 }; static double tpi = 6.28318530717958647692528676655900577; double arg, argh, argld, fi; long ntry = 0, i, j = -1; long k1, l1, l2, ib; long ld, ii, ip, is, nq, nr; long ido, ipm, nfm1; long nl = n; long nf = 0; L101: j++; if (j < 4) ntry = ntryh[j]; else ntry += 2; L104: nq = nl / ntry; nr = nl - ntry * nq; if (nr != 0) goto L101; nf++; ifac[nf + 1] = ntry; nl = nq; if (ntry != 2) goto L107; if (nf == 1) goto L107; for (i = 1; i < nf; i++) { ib = nf - i + 1; ifac[ib + 1] = ifac[ib]; } ifac[2] = 2; L107: if (nl != 1) goto L104; ifac[0] = n; ifac[1] = nf; argh = tpi / n; is = 0; nfm1 = nf - 1; l1 = 1; if (nfm1 == 0) return; for (k1 = 0; k1 < nfm1; k1++) { ip = ifac[k1 + 2]; ld = 0; l2 = l1 * ip; ido = n / l2; ipm = ip - 1; for (j = 0; j < ipm; j++) { ld += l1; i = is; argld = (double) ld *argh; fi = 0.; for (ii = 2; ii < ido; ii += 2) { fi += 1.; arg = fi * argld; wa[i++] = cos (arg); wa[i++] = sin (arg); } is += ido; } l1 = l2; } } static void NUMrffti (long n, FFT_DATA_TYPE * wsave, long *ifac) { if (n == 1) return; drfti1 (n, wsave + n, ifac); } /* void NUMcosqi(long n, FFT_DATA_TYPE *wsave, long *ifac){ static double pih = 1.57079632679489661923132169163975; static long k; static double fk, dt; dt=pih/n; fk=0.; for(k=0;k> 1; ipp2 = ip; idp2 = ido; nbd = (ido - 1) >> 1; t0 = l1 * ido; t10 = ip * ido; if (ido == 1) goto L119; for (ik = 0; ik < idl1; ik++) ch2[ik] = c2[ik]; t1 = 0; for (j = 1; j < ip; j++) { t1 += t0; t2 = t1; for (k = 0; k < l1; k++) { ch[t2] = c1[t2]; t2 += ido; } } is = -ido; t1 = 0; if (nbd > l1) { for (j = 1; j < ip; j++) { t1 += t0; is += ido; t2 = -ido + t1; for (k = 0; k < l1; k++) { idij = is - 1; t2 += ido; t3 = t2; for (i = 2; i < ido; i += 2) { idij += 2; t3 += 2; ch[t3 - 1] = wa[idij - 1] * c1[t3 - 1] + wa[idij] * c1[t3]; ch[t3] = wa[idij - 1] * c1[t3] - wa[idij] * c1[t3 - 1]; } } } } else { for (j = 1; j < ip; j++) { is += ido; idij = is - 1; t1 += t0; t2 = t1; for (i = 2; i < ido; i += 2) { idij += 2; t2 += 2; t3 = t2; for (k = 0; k < l1; k++) { ch[t3 - 1] = wa[idij - 1] * c1[t3 - 1] + wa[idij] * c1[t3]; ch[t3] = wa[idij - 1] * c1[t3] - wa[idij] * c1[t3 - 1]; t3 += ido; } } } } t1 = 0; t2 = ipp2 * t0; if (nbd < l1) { for (j = 1; j < ipph; j++) { t1 += t0; t2 -= t0; t3 = t1; t4 = t2; for (i = 2; i < ido; i += 2) { t3 += 2; t4 += 2; t5 = t3 - ido; t6 = t4 - ido; for (k = 0; k < l1; k++) { t5 += ido; t6 += ido; c1[t5 - 1] = ch[t5 - 1] + ch[t6 - 1]; c1[t6 - 1] = ch[t5] - ch[t6]; c1[t5] = ch[t5] + ch[t6]; c1[t6] = ch[t6 - 1] - ch[t5 - 1]; } } } } else { for (j = 1; j < ipph; j++) { t1 += t0; t2 -= t0; t3 = t1; t4 = t2; for (k = 0; k < l1; k++) { t5 = t3; t6 = t4; for (i = 2; i < ido; i += 2) { t5 += 2; t6 += 2; c1[t5 - 1] = ch[t5 - 1] + ch[t6 - 1]; c1[t6 - 1] = ch[t5] - ch[t6]; c1[t5] = ch[t5] + ch[t6]; c1[t6] = ch[t6 - 1] - ch[t5 - 1]; } t3 += ido; t4 += ido; } } } L119: for (ik = 0; ik < idl1; ik++) c2[ik] = ch2[ik]; t1 = 0; t2 = ipp2 * idl1; for (j = 1; j < ipph; j++) { t1 += t0; t2 -= t0; t3 = t1 - ido; t4 = t2 - ido; for (k = 0; k < l1; k++) { t3 += ido; t4 += ido; c1[t3] = ch[t3] + ch[t4]; c1[t4] = ch[t4] - ch[t3]; } } ar1 = 1.; ai1 = 0.; t1 = 0; t2 = ipp2 * idl1; t3 = (ip - 1) * idl1; for (l = 1; l < ipph; l++) { t1 += idl1; t2 -= idl1; ar1h = dcp * ar1 - dsp * ai1; ai1 = dcp * ai1 + dsp * ar1; ar1 = ar1h; t4 = t1; t5 = t2; t6 = t3; t7 = idl1; for (ik = 0; ik < idl1; ik++) { ch2[t4++] = c2[ik] + ar1 * c2[t7++]; ch2[t5++] = ai1 * c2[t6++]; } dc2 = ar1; ds2 = ai1; ar2 = ar1; ai2 = ai1; t4 = idl1; t5 = (ipp2 - 1) * idl1; for (j = 2; j < ipph; j++) { t4 += idl1; t5 -= idl1; ar2h = dc2 * ar2 - ds2 * ai2; ai2 = dc2 * ai2 + ds2 * ar2; ar2 = ar2h; t6 = t1; t7 = t2; t8 = t4; t9 = t5; for (ik = 0; ik < idl1; ik++) { ch2[t6++] += ar2 * c2[t8++]; ch2[t7++] += ai2 * c2[t9++]; } } } t1 = 0; for (j = 1; j < ipph; j++) { t1 += idl1; t2 = t1; for (ik = 0; ik < idl1; ik++) ch2[ik] += c2[t2++]; } if (ido < l1) goto L132; t1 = 0; t2 = 0; for (k = 0; k < l1; k++) { t3 = t1; t4 = t2; for (i = 0; i < ido; i++) cc[t4++] = ch[t3++]; t1 += ido; t2 += t10; } goto L135; L132: for (i = 0; i < ido; i++) { t1 = i; t2 = i; for (k = 0; k < l1; k++) { cc[t2] = ch[t1]; t1 += ido; t2 += t10; } } L135: t1 = 0; t2 = ido << 1; t3 = 0; t4 = ipp2 * t0; for (j = 1; j < ipph; j++) { t1 += t2; t3 += t0; t4 -= t0; t5 = t1; t6 = t3; t7 = t4; for (k = 0; k < l1; k++) { cc[t5 - 1] = ch[t6]; cc[t5] = ch[t7]; t5 += t10; t6 += ido; t7 += ido; } } if (ido == 1) return; if (nbd < l1) goto L141; t1 = -ido; t3 = 0; t4 = 0; t5 = ipp2 * t0; for (j = 1; j < ipph; j++) { t1 += t2; t3 += t2; t4 += t0; t5 -= t0; t6 = t1; t7 = t3; t8 = t4; t9 = t5; for (k = 0; k < l1; k++) { for (i = 2; i < ido; i += 2) { ic = idp2 - i; cc[i + t7 - 1] = ch[i + t8 - 1] + ch[i + t9 - 1]; cc[ic + t6 - 1] = ch[i + t8 - 1] - ch[i + t9 - 1]; cc[i + t7] = ch[i + t8] + ch[i + t9]; cc[ic + t6] = ch[i + t9] - ch[i + t8]; } t6 += t10; t7 += t10; t8 += ido; t9 += ido; } } return; L141: t1 = -ido; t3 = 0; t4 = 0; t5 = ipp2 * t0; for (j = 1; j < ipph; j++) { t1 += t2; t3 += t2; t4 += t0; t5 -= t0; for (i = 2; i < ido; i += 2) { t6 = idp2 + t1 - i; t7 = i + t3; t8 = i + t4; t9 = i + t5; for (k = 0; k < l1; k++) { cc[t7 - 1] = ch[t8 - 1] + ch[t9 - 1]; cc[t6 - 1] = ch[t8 - 1] - ch[t9 - 1]; cc[t7] = ch[t8] + ch[t9]; cc[t6] = ch[t9] - ch[t8]; t6 += t10; t7 += t10; t8 += ido; t9 += ido; } } } } static void drftf1 (long n, FFT_DATA_TYPE * c, FFT_DATA_TYPE * ch, FFT_DATA_TYPE * wa, long *ifac) { long i, k1, l1, l2; long na, kh, nf; long ip, iw, ido, idl1, ix2, ix3; nf = ifac[1]; na = 1; l2 = n; iw = n; for (k1 = 0; k1 < nf; k1++) { kh = nf - k1; ip = ifac[kh + 1]; l1 = l2 / ip; ido = n / l2; idl1 = ido * l1; iw -= (ip - 1) * ido; na = 1 - na; if (ip != 4) goto L102; ix2 = iw + ido; ix3 = ix2 + ido; if (na != 0) dradf4 (ido, l1, ch, c, wa + iw - 1, wa + ix2 - 1, wa + ix3 - 1); else dradf4 (ido, l1, c, ch, wa + iw - 1, wa + ix2 - 1, wa + ix3 - 1); goto L110; L102: if (ip != 2) goto L104; if (na != 0) goto L103; dradf2 (ido, l1, c, ch, wa + iw - 1); goto L110; L103: dradf2 (ido, l1, ch, c, wa + iw - 1); goto L110; L104: if (ido == 1) na = 1 - na; if (na != 0) goto L109; dradfg (ido, ip, l1, idl1, c, c, c, ch, ch, wa + iw - 1); na = 1; goto L110; L109: dradfg (ido, ip, l1, idl1, ch, ch, ch, c, c, wa + iw - 1); na = 0; L110: l2 = l1; } if (na == 1) return; for (i = 0; i < n; i++) c[i] = ch[i]; } static void dradb2 (long ido, long l1, FFT_DATA_TYPE * cc, FFT_DATA_TYPE * ch, FFT_DATA_TYPE * wa1) { long i, k, t0, t1, t2, t3, t4, t5, t6; double ti2, tr2; t0 = l1 * ido; t1 = 0; t2 = 0; t3 = (ido << 1) - 1; for (k = 0; k < l1; k++) { ch[t1] = cc[t2] + cc[t3 + t2]; ch[t1 + t0] = cc[t2] - cc[t3 + t2]; t2 = (t1 += ido) << 1; } if (ido < 2) return; if (ido == 2) goto L105; t1 = 0; t2 = 0; for (k = 0; k < l1; k++) { t3 = t1; t5 = (t4 = t2) + (ido << 1); t6 = t0 + t1; for (i = 2; i < ido; i += 2) { t3 += 2; t4 += 2; t5 -= 2; t6 += 2; ch[t3 - 1] = cc[t4 - 1] + cc[t5 - 1]; tr2 = cc[t4 - 1] - cc[t5 - 1]; ch[t3] = cc[t4] - cc[t5]; ti2 = cc[t4] + cc[t5]; ch[t6 - 1] = wa1[i - 2] * tr2 - wa1[i - 1] * ti2; ch[t6] = wa1[i - 2] * ti2 + wa1[i - 1] * tr2; } t2 = (t1 += ido) << 1; } if (ido % 2 == 1) return; L105: t1 = ido - 1; t2 = ido - 1; for (k = 0; k < l1; k++) { ch[t1] = cc[t2] + cc[t2]; ch[t1 + t0] = -(cc[t2 + 1] + cc[t2 + 1]); t1 += ido; t2 += ido << 1; } } static void dradb3 (long ido, long l1, FFT_DATA_TYPE * cc, FFT_DATA_TYPE * ch, FFT_DATA_TYPE * wa1, FFT_DATA_TYPE * wa2) { static double taur = -.5; static double taui = .86602540378443864676372317075293618; long i, k, t0, t1, t2, t3, t4, t5, t6, t7, t8, t9, t10; double ci2, ci3, di2, di3, cr2, cr3, dr2, dr3, ti2, tr2; t0 = l1 * ido; t1 = 0; t2 = t0 << 1; t3 = ido << 1; t4 = ido + (ido << 1); t5 = 0; for (k = 0; k < l1; k++) { tr2 = cc[t3 - 1] + cc[t3 - 1]; cr2 = cc[t5] + (taur * tr2); ch[t1] = cc[t5] + tr2; ci3 = taui * (cc[t3] + cc[t3]); ch[t1 + t0] = cr2 - ci3; ch[t1 + t2] = cr2 + ci3; t1 += ido; t3 += t4; t5 += t4; } if (ido == 1) return; t1 = 0; t3 = ido << 1; for (k = 0; k < l1; k++) { t7 = t1 + (t1 << 1); t6 = (t5 = t7 + t3); t8 = t1; t10 = (t9 = t1 + t0) + t0; for (i = 2; i < ido; i += 2) { t5 += 2; t6 -= 2; t7 += 2; t8 += 2; t9 += 2; t10 += 2; tr2 = cc[t5 - 1] + cc[t6 - 1]; cr2 = cc[t7 - 1] + (taur * tr2); ch[t8 - 1] = cc[t7 - 1] + tr2; ti2 = cc[t5] - cc[t6]; ci2 = cc[t7] + (taur * ti2); ch[t8] = cc[t7] + ti2; cr3 = taui * (cc[t5 - 1] - cc[t6 - 1]); ci3 = taui * (cc[t5] + cc[t6]); dr2 = cr2 - ci3; dr3 = cr2 + ci3; di2 = ci2 + cr3; di3 = ci2 - cr3; ch[t9 - 1] = wa1[i - 2] * dr2 - wa1[i - 1] * di2; ch[t9] = wa1[i - 2] * di2 + wa1[i - 1] * dr2; ch[t10 - 1] = wa2[i - 2] * dr3 - wa2[i - 1] * di3; ch[t10] = wa2[i - 2] * di3 + wa2[i - 1] * dr3; } t1 += ido; } } static void dradb4 (long ido, long l1, FFT_DATA_TYPE * cc, FFT_DATA_TYPE * ch, FFT_DATA_TYPE * wa1, FFT_DATA_TYPE * wa2, FFT_DATA_TYPE * wa3) { static double sqrt2 = 1.4142135623730950488016887242097; long i, k, t0, t1, t2, t3, t4, t5, t6, t7, t8; double ci2, ci3, ci4, cr2, cr3, cr4, ti1, ti2, ti3, ti4, tr1, tr2, tr3, tr4; t0 = l1 * ido; t1 = 0; t2 = ido << 2; t3 = 0; t6 = ido << 1; for (k = 0; k < l1; k++) { t4 = t3 + t6; t5 = t1; tr3 = cc[t4 - 1] + cc[t4 - 1]; tr4 = cc[t4] + cc[t4]; tr1 = cc[t3] - cc[(t4 += t6) - 1]; tr2 = cc[t3] + cc[t4 - 1]; ch[t5] = tr2 + tr3; ch[t5 += t0] = tr1 - tr4; ch[t5 += t0] = tr2 - tr3; ch[t5 += t0] = tr1 + tr4; t1 += ido; t3 += t2; } if (ido < 2) return; if (ido == 2) goto L105; t1 = 0; for (k = 0; k < l1; k++) { t5 = (t4 = (t3 = (t2 = t1 << 2) + t6)) + t6; t7 = t1; for (i = 2; i < ido; i += 2) { t2 += 2; t3 += 2; t4 -= 2; t5 -= 2; t7 += 2; ti1 = cc[t2] + cc[t5]; ti2 = cc[t2] - cc[t5]; ti3 = cc[t3] - cc[t4]; tr4 = cc[t3] + cc[t4]; tr1 = cc[t2 - 1] - cc[t5 - 1]; tr2 = cc[t2 - 1] + cc[t5 - 1]; ti4 = cc[t3 - 1] - cc[t4 - 1]; tr3 = cc[t3 - 1] + cc[t4 - 1]; ch[t7 - 1] = tr2 + tr3; cr3 = tr2 - tr3; ch[t7] = ti2 + ti3; ci3 = ti2 - ti3; cr2 = tr1 - tr4; cr4 = tr1 + tr4; ci2 = ti1 + ti4; ci4 = ti1 - ti4; ch[(t8 = t7 + t0) - 1] = wa1[i - 2] * cr2 - wa1[i - 1] * ci2; ch[t8] = wa1[i - 2] * ci2 + wa1[i - 1] * cr2; ch[(t8 += t0) - 1] = wa2[i - 2] * cr3 - wa2[i - 1] * ci3; ch[t8] = wa2[i - 2] * ci3 + wa2[i - 1] * cr3; ch[(t8 += t0) - 1] = wa3[i - 2] * cr4 - wa3[i - 1] * ci4; ch[t8] = wa3[i - 2] * ci4 + wa3[i - 1] * cr4; } t1 += ido; } if (ido % 2 == 1) return; L105: t1 = ido; t2 = ido << 2; t3 = ido - 1; t4 = ido + (ido << 1); for (k = 0; k < l1; k++) { t5 = t3; ti1 = cc[t1] + cc[t4]; ti2 = cc[t4] - cc[t1]; tr1 = cc[t1 - 1] - cc[t4 - 1]; tr2 = cc[t1 - 1] + cc[t4 - 1]; ch[t5] = tr2 + tr2; ch[t5 += t0] = sqrt2 * (tr1 - ti1); ch[t5 += t0] = ti2 + ti2; ch[t5 += t0] = -sqrt2 * (tr1 + ti1); t3 += ido; t1 += t2; t4 += t2; } } static void dradbg (long ido, long ip, long l1, long idl1, FFT_DATA_TYPE * cc, FFT_DATA_TYPE * c1, FFT_DATA_TYPE * c2, FFT_DATA_TYPE * ch, FFT_DATA_TYPE * ch2, FFT_DATA_TYPE * wa) { static double tpi = 6.28318530717958647692528676655900577; long idij, ipph, i, j, k, l, ik, is, t0, t1, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12; double dc2, ai1, ai2, ar1, ar2, ds2; long nbd; double dcp, arg, dsp, ar1h, ar2h; long ipp2; t10 = ip * ido; t0 = l1 * ido; arg = tpi / (double) ip; dcp = cos (arg); dsp = sin (arg); nbd = (ido - 1) >> 1; ipp2 = ip; ipph = (ip + 1) >> 1; if (ido < l1) goto L103; t1 = 0; t2 = 0; for (k = 0; k < l1; k++) { t3 = t1; t4 = t2; for (i = 0; i < ido; i++) { ch[t3] = cc[t4]; t3++; t4++; } t1 += ido; t2 += t10; } goto L106; L103: t1 = 0; for (i = 0; i < ido; i++) { t2 = t1; t3 = t1; for (k = 0; k < l1; k++) { ch[t2] = cc[t3]; t2 += ido; t3 += t10; } t1++; } L106: t1 = 0; t2 = ipp2 * t0; t7 = (t5 = ido << 1); for (j = 1; j < ipph; j++) { t1 += t0; t2 -= t0; t3 = t1; t4 = t2; t6 = t5; for (k = 0; k < l1; k++) { ch[t3] = cc[t6 - 1] + cc[t6 - 1]; ch[t4] = cc[t6] + cc[t6]; t3 += ido; t4 += ido; t6 += t10; } t5 += t7; } if (ido == 1) goto L116; if (nbd < l1) goto L112; t1 = 0; t2 = ipp2 * t0; t7 = 0; for (j = 1; j < ipph; j++) { t1 += t0; t2 -= t0; t3 = t1; t4 = t2; t7 += (ido << 1); t8 = t7; for (k = 0; k < l1; k++) { t5 = t3; t6 = t4; t9 = t8; t11 = t8; for (i = 2; i < ido; i += 2) { t5 += 2; t6 += 2; t9 += 2; t11 -= 2; ch[t5 - 1] = cc[t9 - 1] + cc[t11 - 1]; ch[t6 - 1] = cc[t9 - 1] - cc[t11 - 1]; ch[t5] = cc[t9] - cc[t11]; ch[t6] = cc[t9] + cc[t11]; } t3 += ido; t4 += ido; t8 += t10; } } goto L116; L112: t1 = 0; t2 = ipp2 * t0; t7 = 0; for (j = 1; j < ipph; j++) { t1 += t0; t2 -= t0; t3 = t1; t4 = t2; t7 += (ido << 1); t8 = t7; t9 = t7; for (i = 2; i < ido; i += 2) { t3 += 2; t4 += 2; t8 += 2; t9 -= 2; t5 = t3; t6 = t4; t11 = t8; t12 = t9; for (k = 0; k < l1; k++) { ch[t5 - 1] = cc[t11 - 1] + cc[t12 - 1]; ch[t6 - 1] = cc[t11 - 1] - cc[t12 - 1]; ch[t5] = cc[t11] - cc[t12]; ch[t6] = cc[t11] + cc[t12]; t5 += ido; t6 += ido; t11 += t10; t12 += t10; } } } L116: ar1 = 1.; ai1 = 0.; t1 = 0; t9 = (t2 = ipp2 * idl1); t3 = (ip - 1) * idl1; for (l = 1; l < ipph; l++) { t1 += idl1; t2 -= idl1; ar1h = dcp * ar1 - dsp * ai1; ai1 = dcp * ai1 + dsp * ar1; ar1 = ar1h; t4 = t1; t5 = t2; t6 = 0; t7 = idl1; t8 = t3; for (ik = 0; ik < idl1; ik++) { c2[t4++] = ch2[t6++] + ar1 * ch2[t7++]; c2[t5++] = ai1 * ch2[t8++]; } dc2 = ar1; ds2 = ai1; ar2 = ar1; ai2 = ai1; t6 = idl1; t7 = t9 - idl1; for (j = 2; j < ipph; j++) { t6 += idl1; t7 -= idl1; ar2h = dc2 * ar2 - ds2 * ai2; ai2 = dc2 * ai2 + ds2 * ar2; ar2 = ar2h; t4 = t1; t5 = t2; t11 = t6; t12 = t7; for (ik = 0; ik < idl1; ik++) { c2[t4++] += ar2 * ch2[t11++]; c2[t5++] += ai2 * ch2[t12++]; } } } t1 = 0; for (j = 1; j < ipph; j++) { t1 += idl1; t2 = t1; for (ik = 0; ik < idl1; ik++) ch2[ik] += ch2[t2++]; } t1 = 0; t2 = ipp2 * t0; for (j = 1; j < ipph; j++) { t1 += t0; t2 -= t0; t3 = t1; t4 = t2; for (k = 0; k < l1; k++) { ch[t3] = c1[t3] - c1[t4]; ch[t4] = c1[t3] + c1[t4]; t3 += ido; t4 += ido; } } if (ido == 1) goto L132; if (nbd < l1) goto L128; t1 = 0; t2 = ipp2 * t0; for (j = 1; j < ipph; j++) { t1 += t0; t2 -= t0; t3 = t1; t4 = t2; for (k = 0; k < l1; k++) { t5 = t3; t6 = t4; for (i = 2; i < ido; i += 2) { t5 += 2; t6 += 2; ch[t5 - 1] = c1[t5 - 1] - c1[t6]; ch[t6 - 1] = c1[t5 - 1] + c1[t6]; ch[t5] = c1[t5] + c1[t6 - 1]; ch[t6] = c1[t5] - c1[t6 - 1]; } t3 += ido; t4 += ido; } } goto L132; L128: t1 = 0; t2 = ipp2 * t0; for (j = 1; j < ipph; j++) { t1 += t0; t2 -= t0; t3 = t1; t4 = t2; for (i = 2; i < ido; i += 2) { t3 += 2; t4 += 2; t5 = t3; t6 = t4; for (k = 0; k < l1; k++) { ch[t5 - 1] = c1[t5 - 1] - c1[t6]; ch[t6 - 1] = c1[t5 - 1] + c1[t6]; ch[t5] = c1[t5] + c1[t6 - 1]; ch[t6] = c1[t5] - c1[t6 - 1]; t5 += ido; t6 += ido; } } } L132: if (ido == 1) return; for (ik = 0; ik < idl1; ik++) c2[ik] = ch2[ik]; t1 = 0; for (j = 1; j < ip; j++) { t2 = (t1 += t0); for (k = 0; k < l1; k++) { c1[t2] = ch[t2]; t2 += ido; } } if (nbd > l1) goto L139; is = -ido - 1; t1 = 0; for (j = 1; j < ip; j++) { is += ido; t1 += t0; idij = is; t2 = t1; for (i = 2; i < ido; i += 2) { t2 += 2; idij += 2; t3 = t2; for (k = 0; k < l1; k++) { c1[t3 - 1] = wa[idij - 1] * ch[t3 - 1] - wa[idij] * ch[t3]; c1[t3] = wa[idij - 1] * ch[t3] + wa[idij] * ch[t3 - 1]; t3 += ido; } } } return; L139: is = -ido - 1; t1 = 0; for (j = 1; j < ip; j++) { is += ido; t1 += t0; t2 = t1; for (k = 0; k < l1; k++) { idij = is; t3 = t2; for (i = 2; i < ido; i += 2) { idij += 2; t3 += 2; c1[t3 - 1] = wa[idij - 1] * ch[t3 - 1] - wa[idij] * ch[t3]; c1[t3] = wa[idij - 1] * ch[t3] + wa[idij] * ch[t3 - 1]; } t2 += ido; } } } static void drftb1 (long n, FFT_DATA_TYPE * c, FFT_DATA_TYPE * ch, FFT_DATA_TYPE * wa, long *ifac) { long i, k1, l1, l2; long na; long nf, ip, iw, ix2, ix3, ido, idl1; nf = ifac[1]; na = 0; l1 = 1; iw = 1; for (k1 = 0; k1 < nf; k1++) { ip = ifac[k1 + 2]; l2 = ip * l1; ido = n / l2; idl1 = ido * l1; if (ip != 4) goto L103; ix2 = iw + ido; ix3 = ix2 + ido; if (na != 0) dradb4 (ido, l1, ch, c, wa + iw - 1, wa + ix2 - 1, wa + ix3 - 1); else dradb4 (ido, l1, c, ch, wa + iw - 1, wa + ix2 - 1, wa + ix3 - 1); na = 1 - na; goto L115; L103: if (ip != 2) goto L106; if (na != 0) dradb2 (ido, l1, ch, c, wa + iw - 1); else dradb2 (ido, l1, c, ch, wa + iw - 1); na = 1 - na; goto L115; L106: if (ip != 3) goto L109; ix2 = iw + ido; if (na != 0) dradb3 (ido, l1, ch, c, wa + iw - 1, wa + ix2 - 1); else dradb3 (ido, l1, c, ch, wa + iw - 1, wa + ix2 - 1); na = 1 - na; goto L115; L109: /* The radix five case can be translated later..... */ /* if(ip!=5)goto L112; ix2=iw+ido; ix3=ix2+ido; ix4=ix3+ido; if(na!=0) dradb5(ido,l1,ch,c,wa+iw-1,wa+ix2-1,wa+ix3-1,wa+ix4-1); else dradb5(ido,l1,c,ch,wa+iw-1,wa+ix2-1,wa+ix3-1,wa+ix4-1); na=1-na; goto L115; L112: */ if (na != 0) dradbg (ido, ip, l1, idl1, ch, ch, ch, c, c, wa + iw - 1); else dradbg (ido, ip, l1, idl1, c, c, c, ch, ch, wa + iw - 1); if (ido == 1) na = 1 - na; L115: l1 = l2; iw += (ip - 1) * ido; } if (na == 0) return; for (i = 0; i < n; i++) c[i] = ch[i]; } /* End of file NUMfft_core.h */ sources_5316/dwsys/Index.h0000644000176700017670000000230311627163273014322 0ustar paulpaul#ifndef _Index_h_ #define _Index_h_ /* Index.h * * Copyright (C) 2005-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection.h" #include "Index_def.h" oo_CLASS_CREATE (Index, Data); oo_CLASS_CREATE (StringsIndex, Index); void Index_init (I, long numberOfElements); Index Index_extractPart (I, long from, long to); StringsIndex StringsIndex_create (long numberOfElements); int StringsIndex_getClass (StringsIndex me, wchar_t *classLabel); long StringsIndex_countItems (StringsIndex me, int iclas); #endif /* _Index_h_ */ sources_5316/dwsys/Command.h0000644000176700017670000000442111627152157014633 0ustar paulpaul#ifndef _Command_h_ #define _Command_h_ /* Command.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 19950711 djmw 20020812 GPL header djmw 20110306 Latest modification */ #include "Thing.h" #include "Collection.h" Thing_define (Command, Thing) { // new data: public: Any data; int (*execute) (I); int (*undo) (I); }; void Command_init (I, const wchar_t *name, Any data, int (*execute)(Any), int (*undo)(Any)); int Command_do (I); int Command_undo (I); Thing_define (CommandHistory, Ordered) { // new data: public: long current; }; /* Active data structure. 'current' is position of the cursor in the list */ /* Queries and insertions are at the current position */ /* Invariants: */ /* 0 <= current <= size + 1; */ CommandHistory CommandHistory_create (long maximumCapacity); void CommandHistory_forth (I); /* Precondition: ! offright */ /* my current++; */ void CommandHistory_back (I); /* Precondition: ! offleft */ /* my current--; */ Any CommandHistory_getItem (I); /* return (pointer to) my item[my current]; */ void CommandHistory_insertItem (I, Any item); /* 1. forget about item[ current+1..size ] */ /* 2. insert item after current. */ /* 3. current = size */ int CommandHistory_empty (I); /* return my size == 0; */ int CommandHistory_offleft (I); /* return my current == 0; */ int CommandHistory_offright (I); /* return my size == 0 || my current == my size + 1; */ wchar_t *CommandHistory_commandName (I, long offsetFromCurrent); /* offsetFromCurrent may be zero, positive or negative. */ /* References outside the list will return NULL. */ #endif /* _Command_h_ */ sources_5316/dwsys/NUMf2c.cpp0000644000176700017670000000520511607763164014647 0ustar paulpaul/* NUMf2c.c */ #include #include "NUMf2c.h" #include "melder.h" double d_sign (double *a, double *b) { double x; x = (*a >= 0 ? *a : - *a); return (*b >= 0 ? x : -x); } long int lsame_ (const char *ca, const char *cb) { int a = * (unsigned char *) ca; int b = * (unsigned char *) cb; return tolower (a) == tolower (b); } double pow_di (double *ap, long *bp) { double pow, x; long n; unsigned long u; pow = 1; x = *ap; n = *bp; if (n != 0) { if (n < 0) { n = -n; x = 1 / x; } for (u = n; ;) { if (u & 01) { pow *= x; } if (u >>= 1) { x *= x; } else { break; } } } return (pow); } void s_cat (char *lp, const char *rpp[], long rnp[], long *np, long ll) { long i, nc; char *rp; long n = *np; #ifndef NO_OVERWRITE long L, m; char *lp0, *lp1; lp0 = 0; lp1 = lp; L = ll; i = 0; while (i < n) { rp = (char *) rpp[i]; m = rnp[i++]; if (rp >= lp1 || rp + m <= lp) { if ( (L -= m) <= 0) { n = i; break; } lp1 += m; continue; } lp0 = lp; lp = lp1 = Melder_malloc_f (char, L = ll); break; } lp1 = lp; #endif /* NO_OVERWRITE */ for (i = 0 ; i < n ; ++i) { nc = ll; if (rnp[i] < nc) { nc = rnp[i]; } ll -= nc; rp = (char *) rpp[i]; while (--nc >= 0) { *lp++ = *rp++; } } while (--ll >= 0) { *lp++ = ' '; } #ifndef NO_OVERWRITE if (lp0) { memcpy (lp0, lp1, L); free (lp1); } #endif } /* compare two strings */ long s_cmp (const char *a0, const char *b0, long la, long lb) { register unsigned char *a, *aend, *b, *bend; a = (unsigned char *) a0; b = (unsigned char *) b0; aend = a + la; bend = b + lb; if (la <= lb) { while (a < aend) if (*a != *b) { return (*a - *b); } else { ++a; ++b; } while (b < bend) if (*b != ' ') { return (' ' - *b); } else { ++b; } } else { while (b < bend) if (*a == *b) { ++a; ++b; } else { return (*a - *b); } while (a < aend) if (*a != ' ') { return (*a - ' '); } else { ++a; } } return (0); } void s_copy (register char *a, register char *b, long la, long lb) { register char *aend, *bend; aend = a + la; if (la <= lb) #ifndef NO_OVERWRITE if (a <= b || a >= b + la) #endif while (a < aend) { *a++ = *b++; } #ifndef NO_OVERWRITE else for (b += la; a < aend;) { *--aend = *--b; } #endif else { bend = b + lb; #ifndef NO_OVERWRITE if (a <= b || a >= bend) #endif while (b < bend) { *a++ = *b++; } #ifndef NO_OVERWRITE else { a += lb; while (b < bend) { *--a = *--bend; } a += lb; } #endif while (a < aend) { *a++ = ' '; } } } /* End of file NUMf2c.c */ sources_5316/dwsys/Index_def.h0000644000176700017670000000234511627163344015145 0ustar paulpaul/* Index_def.h * * Copyright (C) 2005-2006 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20050724 djmw 20060529 Added object version numbers. */ #define ooSTRUCT Index oo_DEFINE_CLASS (Index, Data) oo_OBJECT (Ordered, 0, classes) oo_LONG (numberOfElements) oo_LONG_VECTOR (classIndex, numberOfElements) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS(Index) #undef ooSTRUCT #define ooSTRUCT StringsIndex oo_DEFINE_CLASS (StringsIndex, Index) oo_END_CLASS(StringsIndex) #undef ooSTRUCT /* End of file Index_def.h */ sources_5316/dwsys/SVD_def.h0000644000176700017670000000331711631153125014521 0ustar paulpaul/* SVD_def.h * * Copyright (C) 1994-2008 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT SVD oo_DEFINE_CLASS (SVD, Data) oo_DOUBLE (tolerance) oo_LONG (numberOfRows) oo_LONG (numberOfColumns) oo_DOUBLE_MATRIX (u, numberOfRows, (numberOfColumns < numberOfRows ? numberOfColumns : numberOfRows)) oo_DOUBLE_MATRIX (v, numberOfColumns, (numberOfColumns < numberOfRows ? numberOfColumns : numberOfRows)) oo_DOUBLE_VECTOR (d, (numberOfColumns < numberOfRows ? numberOfColumns : numberOfRows)) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (SVD) #undef ooSTRUCT #define ooSTRUCT GSVD oo_DEFINE_CLASS (GSVD, Data) oo_DOUBLE (tolerance) oo_LONG (numberOfColumns) oo_DOUBLE_MATRIX ( q, numberOfColumns, numberOfColumns) oo_DOUBLE_MATRIX ( r, numberOfColumns, numberOfColumns) oo_DOUBLE_VECTOR (d1, numberOfColumns) oo_DOUBLE_VECTOR (d2, numberOfColumns) #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (GSVD) #undef ooSTRUCT /* End of file SVD_def.h */ sources_5316/dwsys/NUMcblas.h0000644000176700017670000010474011627163665014734 0ustar paulpaul #ifndef _NUMcblas_h_ #define _NUMcblas_h_ /* NUMcblas.h * * Copyright (C) 1994-2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* djmw 20020923 GPL header djmw 20110308 Latest modification */ #ifdef __cplusplus extern "C" { #endif #define xerbla_(src,info) Melder_throw (Melder_peekUtf8ToWcs (src), ": parameter ", *info, "not correct!") int NUMblas_daxpy (long *n, double *da, double *dx, long *incx, double *dy, long *incy); /* constant times a vector plus a vector. uses unrolled loops for increments equal to one. */ int NUMblas_dcopy (long *n, double *dx, long *incx, double *dy, long *incy); /* copies a vector, x, to a vector, y. uses unrolled loops for increments equal to one. */ double NUMblas_ddot (long *n, double *dx, long *incx, double *dy, long *incy); /* forms the dot product of two vectors. uses unrolled loops for increments equal to one. */ int NUMblas_dgemm (const char *transa, const char *transb, long *m, long *n, long *k, double *alpha, double *a, long *lda, double *b, long *ldb, double *beta, double *c, long *ldc); /* Purpose ======= NUMblas_dgemm performs one of the matrix-matrix operations C := alpha*op( A )*op( B ) + beta*C, where op( X ) is one of op( X ) = X or op( X ) = X', alpha and beta are scalars, and A, B and C are matrices, with op( A ) an m by k matrix, op( B ) a k by n matrix and C an m by n matrix. Parameters ========== TRANSA - char*. On entry, TRANSA specifies the form of op( A ) to be used in the matrix multiplication as follows: TRANSA = 'N' or 'n', op( A ) = A. TRANSA = 'T' or 't', op( A ) = A'. TRANSA = 'C' or 'c', op( A ) = A'. Unchanged on exit. TRANSB - char*. On entry, TRANSB specifies the form of op( B ) to be used in the matrix multiplication as follows: TRANSB = 'N' or 'n', op( B ) = B. TRANSB = 'T' or 't', op( B ) = B'. TRANSB = 'C' or 'c', op( B ) = B'. Unchanged on exit. M - long. On entry, M specifies the number of rows of the matrix op( A ) and of the matrix C. M must be at least zero. Unchanged on exit. N - long. On entry, N specifies the number of columns of the matrix op( B ) and the number of columns of the matrix C. N must be at least zero. Unchanged on exit. K - long. On entry, K specifies the number of columns of the matrix op( A ) and the number of rows of the matrix op( B ). K must be at least zero. Unchanged on exit. ALPHA - double. On entry, ALPHA specifies the scalar alpha. Unchanged on exit. A - double array of DIMENSION ( LDA, ka ), where ka is k when TRANSA = 'N' or 'n', and is m otherwise. Before entry with TRANSA = 'N' or 'n', the leading m by k part of the array A must contain the matrix A, otherwise the leading k by m part of the array A must contain the matrix A. Unchanged on exit. LDA - long. On entry, LDA specifies the first dimension of A as declared in the calling (sub) program. When TRANSA = 'N' or 'n' then LDA must be at least max( 1, m ), otherwise LDA must be at least max( 1, k ). Unchanged on exit. B - double array of DIMENSION ( LDB, kb ), where kb is n when TRANSB = 'N' or 'n', and is k otherwise. Before entry with TRANSB = 'N' or 'n', the leading k by n part of the array B must contain the matrix B, otherwise the leading n by k part of the array B must contain the matrix B. Unchanged on exit. LDB - long. On entry, LDB specifies the first dimension of B as declared in the calling (sub) program. When TRANSB = 'N' or 'n' then LDB must be at least max( 1, k ), otherwise LDB must be at least max( 1, n ). Unchanged on exit. BETA - double. On entry, BETA specifies the scalar beta. When BETA is supplied as zero then C need not be set on input. Unchanged on exit. C - double array of DIMENSION ( LDC, n ). Before entry, the leading m by n part of the array C must contain the matrix C, except when beta is zero, in which case C need not be set on entry. On exit, the array C is overwritten by the m by n matrix ( alpha*op( A )*op( B ) + beta*C ). LDC - long. On entry, LDC specifies the first dimension of C as declared in the calling (sub) program. LDC must be at least max( 1, m ). Unchanged on exit. Level 3 Blas routine. -- Written on 8-February-1989. Jack Dongarra, Argonne National Laboratory. Iain Duff, AERE Harwell. Jeremy Du Croz, Numerical Algorithms Group Ltd. Sven Hammarling, Numerical Algorithms Group Ltd. */ int NUMblas_dger (long *m, long *n, double *alpha, double *x, long *incx, double *y, long *incy, double *a, long *lda); /* Purpose ======= NUMblas_dger performs the rank 1 operation A := alpha*x*y' + A, where alpha is a scalar, x is an m element vector, y is an n element vector and A is an m by n matrix. Parameters ========== M - long. On entry, M specifies the number of rows of the matrix A. M must be at least zero. Unchanged on exit. N - long. On entry, N specifies the number of columns of the matrix A. N must be at least zero. Unchanged on exit. ALPHA - double. On entry, ALPHA specifies the scalar alpha. Unchanged on exit. X - double array of dimension at least ( 1 + ( m - 1 )*abs( INCX ) ). Before entry, the incremented array X must contain the m element vector x. Unchanged on exit. INCX - long. On entry, INCX specifies the increment for the elements of X. INCX must not be zero. Unchanged on exit. Y - double array of dimension at least ( 1 + ( n - 1 )*abs( INCY ) ). Before entry, the incremented array Y must contain the n element vector y. Unchanged on exit. INCY - long. On entry, INCY specifies the increment for the elements of Y. INCY must not be zero. Unchanged on exit. A - double array of DIMENSION ( LDA, n ). Before entry, the leading m by n part of the array A must contain the matrix of coefficients. On exit, A is overwritten by the updated matrix. LDA - long. On entry, LDA specifies the first dimension of A as declared in the calling (sub) program. LDA must be at least max( 1, m ). Unchanged on exit. Level 2 Blas routine. -- Written on 22-October-1986. Jack Dongarra, Argonne National Lab. Jeremy Du Croz, Nag Central Office. Sven Hammarling, Nag Central Office. Richard Hanson, Sandia National Labs. */ int NUMblas_dgemv (const char *trans, long *m, long *n, double *alpha, double *a, long *lda, double *x, long *incx, double *beta, double *y, long *incy); /* Purpose ======= NUMblas_dgemv performs one of the matrix-vector operations y := alpha*A*x + beta*y, or y := alpha*A'*x + beta*y, where alpha and beta are scalars, x and y are vectors and A is an m by n matrix. Parameters ========== TRANS - char*. On entry, TRANS specifies the operation to be performed as follows: TRANS = 'N' or 'n' y := alpha*A*x + beta*y. TRANS = 'T' or 't' y := alpha*A'*x + beta*y. TRANS = 'C' or 'c' y := alpha*A'*x + beta*y. Unchanged on exit. M - long. On entry, M specifies the number of rows of the matrix A. M must be at least zero. Unchanged on exit. N - long. On entry, N specifies the number of columns of the matrix A. N must be at least zero. Unchanged on exit. ALPHA - double. On entry, ALPHA specifies the scalar alpha. Unchanged on exit. A - double array of DIMENSION ( LDA, n ). Before entry, the leading m by n part of the array A must contain the matrix of coefficients. Unchanged on exit. LDA - long. On entry, LDA specifies the first dimension of A as declared in the calling (sub) program. LDA must be at least max( 1, m ). Unchanged on exit. X - double array of DIMENSION at least ( 1 + ( n - 1 )*abs( INCX ) ) when TRANS = 'N' or 'n' and at least ( 1 + ( m - 1 )*abs( INCX ) ) otherwise. Before entry, the incremented array X must contain the vector x. Unchanged on exit. INCX - long. On entry, INCX specifies the increment for the elements of X. INCX must not be zero. Unchanged on exit. BETA - double. On entry, BETA specifies the scalar beta. When BETA is supplied as zero then Y need not be set on input. Unchanged on exit. Y - double array of DIMENSION at least ( 1 + ( m - 1 )*abs( INCY ) ) when TRANS = 'N' or 'n' and at least ( 1 + ( n - 1 )*abs( INCY ) ) otherwise. Before entry with BETA non-zero, the incremented array Y must contain the vector y. On exit, Y is overwritten by the updated vector y. INCY - long. On entry, INCY specifies the increment for the elements of Y. INCY must not be zero. Unchanged on exit. Level 2 Blas routine. -- Written on 22-October-1986. Jack Dongarra, Argonne National Lab. Jeremy Du Croz, Nag Central Office. Sven Hammarling, Nag Central Office. Richard Hanson, Sandia National Labs. */ double NUMblas_dlamch (const char *cmach); /* Purpose ======= NUMblas_dlamch determines double machine parameters. Arguments ========= CMACH (input) char* Specifies the value to be returned by DLAMCH: = 'E' or 'e', DLAMCH := eps = 'S' or 's , DLAMCH := sfmin = 'B' or 'b', DLAMCH := base = 'P' or 'p', DLAMCH := eps*base = 'N' or 'n', DLAMCH := t = 'R' or 'r', DLAMCH := rnd = 'M' or 'm', DLAMCH := emin = 'U' or 'u', DLAMCH := rmin = 'L' or 'l', DLAMCH := emax = 'O' or 'o', DLAMCH := rmax where eps = relative machine precision sfmin = safe minimum, such that 1/sfmin does not overflow base = base of the machine prec = eps*base t = number of (base) digits in the mantissa rnd = 1.0 when rounding occurs in addition, 0.0 otherwise emin = minimum exponent before (gradual) underflow rmin = underflow threshold - base**(emin-1) emax = largest exponent before overflow rmax = overflow threshold - (base**emax)*(1-eps) ===================================================================== */ double NUMblas_dnrm2 (long *n, double *x, long *incx); /* NUMblas_dnrm2 returns the euclidean norm of a vector via the function name, so that DNRM2 := sqrt( x'*x ) -- This version written on 25-October-1982. Modified on 14-October-1993 to inline the call to DLASSQ. Sven Hammarling, Nag Ltd. Parameter adjustments */ int NUMblas_drot (long *n, double *dx, long *incx, double *dy, long *incy, double *c__, double *s); /* applies a plane rotation. */ int NUMblas_dscal (long *n, double *da, double *dx, long *incx); /* scales a vector by a constant. uses unrolled loops for increment equal to one. */ int NUMblas_dswap (long *n, double *dx, long *incx, double *dy, long *incy); /* interchanges two vectors. uses unrolled loops for increments equal one. */ int NUMblas_dsymv (const char *uplo, long *n, double *alpha, double *a, long *lda, double *x, long *incx, double *beta, double *y, long *incy); /* Purpose ======= NUMblas_dsymv performs the matrix-vector operation y := alpha*A*x + beta*y, where alpha and beta are scalars, x and y are n element vectors and A is an n by n symmetric matrix. Parameters ========== UPLO - char*. On entry, UPLO specifies whether the upper or lower triangular part of the array A is to be referenced as follows: UPLO = 'U' or 'u' Only the upper triangular part of A is to be referenced. UPLO = 'L' or 'l' Only the lower triangular part of A is to be referenced. Unchanged on exit. N - long. On entry, N specifies the order of the matrix A. N must be at least zero. Unchanged on exit. ALPHA - double. On entry, ALPHA specifies the scalar alpha. Unchanged on exit. A - double array of DIMENSION ( LDA, n ). Before entry with UPLO = 'U' or 'u', the leading n by n upper triangular part of the array A must contain the upper triangular part of the symmetric matrix and the strictly lower triangular part of A is not referenced. Before entry with UPLO = 'L' or 'l', the leading n by n lower triangular part of the array A must contain the lower triangular part of the symmetric matrix and the strictly upper triangular part of A is not referenced. Unchanged on exit. LDA - long. On entry, LDA specifies the first dimension of A as declared in the calling (sub) program. LDA must be at least max( 1, n ). Unchanged on exit. X - double array of dimension at least ( 1 + ( n - 1 )*abs( INCX ) ). Before entry, the incremented array X must contain the n element vector x. Unchanged on exit. INCX - long. On entry, INCX specifies the increment for the elements of X. INCX must not be zero. Unchanged on exit. BETA - double. On entry, BETA specifies the scalar beta. When BETA is supplied as zero then Y need not be set on input. Unchanged on exit. Y - double array of dimension at least ( 1 + ( n - 1 )*abs( INCY ) ). Before entry, the incremented array Y must contain the n element vector y. On exit, Y is overwritten by the updated vector y. INCY - long. On entry, INCY specifies the increment for the elements of Y. INCY must not be zero. Unchanged on exit. */ int NUMblas_dsyr2 (const char *uplo, long *n, double *alpha, double *x, long *incx, double *y, long *incy, double *a, long *lda); /* Purpose ======= NUMblas_dsyr2 performs the symmetric rank 2 operation A := alpha*x*y' + alpha*y*x' + A, where alpha is a scalar, x and y are n element vectors and A is an n by n symmetric matrix. Parameters ========== UPLO - char*. On entry, UPLO specifies whether the upper or lower triangular part of the array A is to be referenced as follows: UPLO = 'U' or 'u' Only the upper triangular part of A is to be referenced. UPLO = 'L' or 'l' Only the lower triangular part of A is to be referenced. Unchanged on exit. N - long. On entry, N specifies the order of the matrix A. N must be at least zero. Unchanged on exit. ALPHA - double. On entry, ALPHA specifies the scalar alpha. Unchanged on exit. X - double array of dimension at least ( 1 + ( n - 1 )*abs( INCX ) ). Before entry, the incremented array X must contain the n element vector x. Unchanged on exit. INCX - long. On entry, INCX specifies the increment for the elements of X. INCX must not be zero. Unchanged on exit. Y - double array of dimension at least ( 1 + ( n - 1 )*abs( INCY ) ). Before entry, the incremented array Y must contain the n element vector y. Unchanged on exit. INCY - long. On entry, INCY specifies the increment for the elements of Y. INCY must not be zero. Unchanged on exit. A - double array of DIMENSION ( LDA, n ). Before entry with UPLO = 'U' or 'u', the leading n by n upper triangular part of the array A must contain the upper triangular part of the symmetric matrix and the strictly lower triangular part of A is not referenced. On exit, the upper triangular part of the array A is overwritten by the upper triangular part of the updated matrix. Before entry with UPLO = 'L' or 'l', the leading n by n lower triangular part of the array A must contain the lower triangular part of the symmetric matrix and the strictly upper triangular part of A is not referenced. On exit, the lower triangular part of the array A is overwritten by the lower triangular part of the updated matrix. LDA - long. On entry, LDA specifies the first dimension of A as declared in the calling (sub) program. LDA must be at least max( 1, n ). Unchanged on exit. */ int NUMblas_dsyr2k (const char *uplo, const char *trans, long *n, long *k, double *alpha, double *a, long *lda, double *b, long *ldb, double *beta, double *c, long *ldc); /* Purpose ======= NUMblas_dsyr2k performs one of the symmetric rank 2k operations C := alpha*A*B' + alpha*B*A' + beta*C, or C := alpha*A'*B + alpha*B'*A + beta*C, where alpha and beta are scalars, C is an n by n symmetric matrix and A and B are n by k matrices in the first case and k by n matrices in the second case. Parameters ========== UPLO - char*. On entry, UPLO specifies whether the upper or lower triangular part of the array C is to be referenced as follows: UPLO = 'U' or 'u' Only the upper triangular part of C is to be referenced. UPLO = 'L' or 'l' Only the lower triangular part of C is to be referenced. Unchanged on exit. TRANS - char*. On entry, TRANS specifies the operation to be performed as follows: TRANS = 'N' or 'n' C := alpha*A*B' + alpha*B*A' + beta*C. TRANS = 'T' or 't' C := alpha*A'*B + alpha*B'*A + beta*C. TRANS = 'C' or 'c' C := alpha*A'*B + alpha*B'*A + beta*C. Unchanged on exit. N - long. On entry, N specifies the order of the matrix C. N must be at least zero. Unchanged on exit. K - long. On entry with TRANS = 'N' or 'n', K specifies the number of columns of the matrices A and B, and on entry with TRANS = 'T' or 't' or 'C' or 'c', K specifies the number of rows of the matrices A and B. K must be at least zero. Unchanged on exit. ALPHA - double. On entry, ALPHA specifies the scalar alpha. Unchanged on exit. A - double array of DIMENSION ( LDA, ka ), where ka is k when TRANS = 'N' or 'n', and is n otherwise. Before entry with TRANS = 'N' or 'n', the leading n by k part of the array A must contain the matrix A, otherwise the leading k by n part of the array A must contain the matrix A. Unchanged on exit. LDA - long. On entry, LDA specifies the first dimension of A as declared in the calling (sub) program. When TRANS = 'N' or 'n' then LDA must be at least max( 1, n ), otherwise LDA must be at least max( 1, k ). Unchanged on exit. B - double array of DIMENSION ( LDB, kb ), where kb is k when TRANS = 'N' or 'n', and is n otherwise. Before entry with TRANS = 'N' or 'n', the leading n by k part of the array B must contain the matrix B, otherwise the leading k by n part of the array B must contain the matrix B. Unchanged on exit. LDB - long. On entry, LDB specifies the first dimension of B as declared in the calling (sub) program. When TRANS = 'N' or 'n' then LDB must be at least max( 1, n ), otherwise LDB must be at least max( 1, k ). Unchanged on exit. BETA - double. On entry, BETA specifies the scalar beta. Unchanged on exit. C - double array of DIMENSION ( LDC, n ). Before entry with UPLO = 'U' or 'u', the leading n by n upper triangular part of the array C must contain the upper triangular part of the symmetric matrix and the strictly lower triangular part of C is not referenced. On exit, the upper triangular part of the array C is overwritten by the upper triangular part of the updated matrix. Before entry with UPLO = 'L' or 'l', the leading n by n lower triangular part of the array C must contain the lower triangular part of the symmetric matrix and the strictly upper triangular part of C is not referenced. On exit, the lower triangular part of the array C is overwritten by the lower triangular part of the updated matrix. LDC - long. On entry, LDC specifies the first dimension of C as declared in the calling (sub) program. LDC must be at least max( 1, n ). Unchanged on exit. Level 3 Blas routine. */ int NUMblas_dtrmm (const char *side, const char *uplo, const char *transa, const char *diag, long *m, long *n, double *alpha, double *a, long *lda, double *b, long *ldb); /* Purpose ======= NUMblas_dtrmm performs one of the matrix-matrix operations B := alpha*op( A )*B, or B := alpha*B*op( A ), where alpha is a scalar, B is an m by n matrix, A is a unit, or non-unit, upper or lower triangular matrix and op( A ) is one of op( A ) = A or op( A ) = A'. Parameters ========== SIDE - char*. On entry, SIDE specifies whether op( A ) multiplies B from the left or right as follows: SIDE = 'L' or 'l' B := alpha*op( A )*B. SIDE = 'R' or 'r' B := alpha*B*op( A ). Unchanged on exit. UPLO - char*. On entry, UPLO specifies whether the matrix A is an upper or lower triangular matrix as follows: UPLO = 'U' or 'u' A is an upper triangular matrix. UPLO = 'L' or 'l' A is a lower triangular matrix. Unchanged on exit. TRANSA - char*. On entry, TRANSA specifies the form of op( A ) to be used in the matrix multiplication as follows: TRANSA = 'N' or 'n' op( A ) = A. TRANSA = 'T' or 't' op( A ) = A'. TRANSA = 'C' or 'c' op( A ) = A'. Unchanged on exit. DIAG - char*. On entry, DIAG specifies whether or not A is unit triangular as follows: DIAG = 'U' or 'u' A is assumed to be unit triangular. DIAG = 'N' or 'n' A is not assumed to be unit triangular. Unchanged on exit. M - long. On entry, M specifies the number of rows of B. M must be at least zero. Unchanged on exit. N - long. On entry, N specifies the number of columns of B. N must be at least zero. Unchanged on exit. ALPHA - double. On entry, ALPHA specifies the scalar alpha. When alpha is zero then A is not referenced and B need not be set before entry. Unchanged on exit. A - double array of DIMENSION ( LDA, k ), where k is m when SIDE = 'L' or 'l' and is n when SIDE = 'R' or 'r'. Before entry with UPLO = 'U' or 'u', the leading k by k upper triangular part of the array A must contain the upper triangular matrix and the strictly lower triangular part of A is not referenced. Before entry with UPLO = 'L' or 'l', the leading k by k lower triangular part of the array A must contain the lower triangular matrix and the strictly upper triangular part of A is not referenced. Note that when DIAG = 'U' or 'u', the diagonal elements of A are not referenced either, but are assumed to be unity. Unchanged on exit. LDA - long. On entry, LDA specifies the first dimension of A as declared in the calling (sub) program. When SIDE = 'L' or 'l' then LDA must be at least max( 1, m ), when SIDE = 'R' or 'r' then LDA must be at least max( 1, n ). Unchanged on exit. B - double array of DIMENSION ( LDB, n ). Before entry, the leading m by n part of the array B must contain the matrix B, and on exit is overwritten by the transformed matrix. LDB - long. On entry, LDB specifies the first dimension of B as declared in the calling (sub) program. LDB must be at least max( 1, m ). Unchanged on exit. Level 3 Blas routine. */ int NUMblas_dtrmv (const char *uplo, const char *trans, const char *diag, long *n, double *a, long *lda, double *x, long *incx); /* Purpose ======= NUMblas_dtrmv performs one of the matrix-vector operations x := A*x, or x := A'*x, where x is an n element vector and A is an n by n unit, or non-unit, upper or lower triangular matrix. Parameters ========== UPLO - char*. On entry, UPLO specifies whether the matrix is an upper or lower triangular matrix as follows: UPLO = 'U' or 'u' A is an upper triangular matrix. UPLO = 'L' or 'l' A is a lower triangular matrix. Unchanged on exit. TRANS - char*. On entry, TRANS specifies the operation to be performed as follows: TRANS = 'N' or 'n' x := A*x. TRANS = 'T' or 't' x := A'*x. TRANS = 'C' or 'c' x := A'*x. Unchanged on exit. DIAG - char*. On entry, DIAG specifies whether or not A is unit triangular as follows: DIAG = 'U' or 'u' A is assumed to be unit triangular. DIAG = 'N' or 'n' A is not assumed to be unit triangular. Unchanged on exit. N - long. On entry, N specifies the order of the matrix A. N must be at least zero. Unchanged on exit. A - double array of DIMENSION ( LDA, n ). Before entry with UPLO = 'U' or 'u', the leading n by n upper triangular part of the array A must contain the upper triangular matrix and the strictly lower triangular part of A is not referenced. Before entry with UPLO = 'L' or 'l', the leading n by n lower triangular part of the array A must contain the lower triangular matrix and the strictly upper triangular part of A is not referenced. Note that when DIAG = 'U' or 'u', the diagonal elements of A are not referenced either, but are assumed to be unity. Unchanged on exit. LDA - long. On entry, LDA specifies the first dimension of A as declared in the calling (sub) program. LDA must be at least max( 1, n ). Unchanged on exit. X - double array of dimension at least ( 1 + ( n - 1 )*abs( INCX ) ). Before entry, the incremented array X must contain the n element vector x. On exit, X is overwritten with the tranformed vector x. INCX - long. On entry, INCX specifies the increment for the elements of X. INCX must not be zero. Unchanged on exit. Level 2 Blas routine. */ int NUMblas_dtrsm (const char *side, const char *uplo, const char *transa, const char *diag, long *m, long *n, double *alpha, double *a, long *lda, double *b, long *ldb); /* Purpose ======= NUMblas_dtrsm solves one of the matrix equations op( A )*X = alpha*B, or X*op( A ) = alpha*B, where alpha is a scalar, X and B are m by n matrices, A is a unit, or non-unit, upper or lower triangular matrix and op( A ) is one of op( A ) = A or op( A ) = A'. The matrix X is overwritten on B. Parameters ========== SIDE - char*. On entry, SIDE specifies whether op( A ) appears on the left or right of X as follows: SIDE = 'L' or 'l' op( A )*X = alpha*B. SIDE = 'R' or 'r' X*op( A ) = alpha*B. Unchanged on exit. UPLO - char*. On entry, UPLO specifies whether the matrix A is an upper or lower triangular matrix as follows: UPLO = 'U' or 'u' A is an upper triangular matrix. UPLO = 'L' or 'l' A is a lower triangular matrix. Unchanged on exit. TRANSA - char*. On entry, TRANSA specifies the form of op( A ) to be used in the matrix multiplication as follows: TRANSA = 'N' or 'n' op( A ) = A. TRANSA = 'T' or 't' op( A ) = A'. TRANSA = 'C' or 'c' op( A ) = A'. Unchanged on exit. DIAG - char*. On entry, DIAG specifies whether or not A is unit triangular as follows: DIAG = 'U' or 'u' A is assumed to be unit triangular. DIAG = 'N' or 'n' A is not assumed to be unit triangular. Unchanged on exit. M - long. On entry, M specifies the number of rows of B. M must be at least zero. Unchanged on exit. N - long. On entry, N specifies the number of columns of B. N must be at least zero. Unchanged on exit. ALPHA - double. On entry, ALPHA specifies the scalar alpha. When alpha is zero then A is not referenced and B need not be set before entry. Unchanged on exit. A - double array of DIMENSION ( LDA, k ), where k is m when SIDE = 'L' or 'l' and is n when SIDE = 'R' or 'r'. Before entry with UPLO = 'U' or 'u', the leading k by k upper triangular part of the array A must contain the upper triangular matrix and the strictly lower triangular part of A is not referenced. Before entry with UPLO = 'L' or 'l', the leading k by k lower triangular part of the array A must contain the lower triangular matrix and the strictly upper triangular part of A is not referenced. Note that when DIAG = 'U' or 'u', the diagonal elements of A are not referenced either, but are assumed to be unity. Unchanged on exit. LDA - long. On entry, LDA specifies the first dimension of A as declared in the calling (sub) program. When SIDE = 'L' or 'l' then LDA must be at least max( 1, m ), when SIDE = 'R' or 'r' then LDA must be at least max( 1, n ). Unchanged on exit. B - double array of DIMENSION ( LDB, n ). Before entry, the leading m by n part of the array B must contain the right-hand side matrix B, and on exit is overwritten by the solution matrix X. LDB - long. On entry, LDB specifies the first dimension of B as declared in the calling (sub) program. LDB must be at least max( 1, m ). Unchanged on exit. */ long NUMblas_idamax (long *n, double *dx, long *incx); /* finds the index of element having max. absolute value.*/ #ifdef __cplusplus } #endif #endif /* _NUMcblas_h_ */ sources_5316/dwsys/DLL.h0000644000176700017670000000330311627152541013663 0ustar paulpaul#ifndef _DLL_h_ #define _DLL_h_ /* DLL.h * * Copyright (C) 2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" Thing_define (DLLNode, Data) { // new data: public: DLLNode next, prev; Data data; // overridden methods: protected: virtual void v_destroy (); virtual void v_copy (Any data_to); }; Thing_define (DLL, Thing) { // new data: public: long numberOfNodes; DLLNode front, back; // overridden methods: protected: virtual void v_destroy (); // new methods: public: static int s_compare (Any data1, Any data2); virtual Data_CompareFunction v_getCompareFunction () { return s_compare; } }; DLLNode DLLNode_create (Data data); // DLLNode owns the data void DLL_init (I); DLL DLL_create(); void DLL_addFront (DLL me, DLLNode n); void DLL_addBack (DLL me, DLLNode n); void DLL_addBefore (DLL me, DLLNode pos, DLLNode n); void DLL_addAfter (DLL me, DLLNode pos, DLLNode n); void DLL_remove (DLL me, DLLNode n); void DLL_sort (DLL me); void DLL_sortPart (DLL me, DLLNode from, DLLNode to); #endif // _DLL_h_ sources_5316/dwsys/DLL.cpp0000644000176700017670000001066211627162721014225 0ustar paulpaul/* DLL.cpp * * Copyright (C) 2011 David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "DLL.h" Thing_implement (DLLNode, Data, 0); void structDLLNode :: v_destroy () { forget (data); DLLNode_Parent :: v_destroy (); } void structDLLNode :: v_copy (thou) { thouart (DLLNode); thy data = Data_copy (data); therror } Thing_implement (DLL, Thing, 0); void structDLL :: v_destroy () { DLLNode v = front; while (v != 0) { DLLNode cur = v; v = v -> next; forget (cur); } DLL_Parent :: v_destroy (); } int structDLL :: s_compare (Any node1, Any node2) { (void) node1; (void) node2; return 0; } DLLNode DLLNode_create (Data data) { DLLNode me = Thing_new (DLLNode); my data = data; return me; } void DLL_init (I) { iam (DLL); } DLL DLL_create() { try { DLL me = Thing_new (DLL); return me; } catch (MelderError) { Melder_throw ("DLL not created."); } } void DLL_addFront (DLL me, DLLNode n) { if (my front == 0) { // empty list my front = n; my back = n; n -> next = 0; n -> prev = 0; my numberOfNodes++; } else { DLL_addBefore (me, my front, n); } } void DLL_addBack (DLL me, DLLNode n) { if (my back == 0) { DLL_addFront (me, n); // empty list } else { DLL_addAfter (me, my back, n); } } void DLL_addBefore (DLL me, DLLNode pos, DLLNode n) { n -> prev = pos -> prev; n -> next = pos; if (pos -> prev == 0) { my front = n; } else { pos -> prev -> next = n; } pos -> prev = n; my numberOfNodes++; } void DLL_addAfter (DLL me, DLLNode pos, DLLNode n) { n -> prev = pos; n -> next = pos -> next; if (pos -> next == 0) { my back = n; } else { pos -> next -> prev = n; } pos -> next = n; my numberOfNodes++; } void DLL_remove (DLL me, DLLNode n) { if (my numberOfNodes == 0) { return; } if (n == my front) { my front = my front -> next; my front -> prev = 0; } else if (n == my back) { my back = my back -> prev; my back -> next = 0; } else { n -> prev -> next = n -> next; n -> next -> prev = n -> prev; } forget (n); my numberOfNodes++; } // Preconditions: // from and to must be part of the list // from must occur before to void DLL_sortPart (DLL me, DLLNode from, DLLNode to) { // Save data if (from == to) { return; // nothing to do } DLLNode from_prev = from -> prev; DLLNode to_next = to -> next; DLLNode my_front = my front; DLLNode my_back = my back; from -> prev = to -> next = 0; my front = from; my back = to; DLL_sort (me); // restore complete list my front -> prev = from_prev; if (from_prev != 0) { from_prev -> next = my front; } my back -> next = to_next; if (to_next != 0) { to_next -> prev = my back; } if (my_front != from) { my front = my_front; } if (my_back != to) { my back = my_back; } } void DLL_sort (DLL me) { Data_CompareFunction compare = my v_getCompareFunction (); long increment = 1; DLLNode front = my front, back; for (;;) { DLLNode n1 = front; front = 0; back = 0; long numberOfMerges = 0; while (n1 != 0) { DLLNode n2 = n1, n; long n1size = 0; numberOfMerges++; for (long i = 1; i <= increment; i++) { n1size++; n2 = n2 -> next; if (n2 == 0) { break; } } long n2size = increment; while (n1size > 0 || (n2size > 0 && n2 != 0)) { // merge n1 and n2 if (n1size == 0) { n2size--; n = n2; n2 = n2 -> next; } else if (n2size == 0 || n2 == 0) { n1size--; n = n1; n1 = n1 -> next; } else if (compare (n1, n2) <= 0) { n1size--; n = n1; n1 = n1 -> next; } else { n2size--; n = n2; n2 = n2 -> next; } if (back != 0) { back -> next = n; } else { front = n; } n -> prev = back; back = n; } n1 = n2; } back -> next = 0; if (numberOfMerges <= 1) { break; } increment *= 2; } // my front = front; my back = back; } // end of file DLL.cpp sources_5316/external/0000775000176700017670000000000011704542243013551 5ustar paulpaulsources_5316/external/glpk/0000755000176700017670000000000011704065313014502 5ustar paulpaulsources_5316/external/glpk/glpmpl02.c0000644000176700017670000013124211411455407016310 0ustar paulpaul/* glpmpl02.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_STDIO #include "glpenv.h" #include "glpmpl.h" /**********************************************************************/ /* * * PROCESSING DATA SECTION * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- create_slice - create slice. -- -- This routine creates a slice, which initially has no components. */ SLICE *create_slice(MPL *mpl) { SLICE *slice; xassert(mpl == mpl); slice = NULL; return slice; } /*---------------------------------------------------------------------- -- expand_slice - append new component to slice. -- -- This routine expands slice appending to it either a given symbol or -- null component, which becomes the last component of the slice. */ SLICE *expand_slice ( MPL *mpl, SLICE *slice, /* destroyed */ SYMBOL *sym /* destroyed */ ) { SLICE *tail, *temp; /* create a new component */ tail = dmp_get_atom(mpl->tuples, sizeof(SLICE)); tail->sym = sym; tail->next = NULL; /* and append it to the component list */ if (slice == NULL) slice = tail; else { for (temp = slice; temp->next != NULL; temp = temp->next); temp->next = tail; } return slice; } /*---------------------------------------------------------------------- -- slice_dimen - determine dimension of slice. -- -- This routine returns dimension of slice, which is number of all its -- components including null ones. */ int slice_dimen ( MPL *mpl, SLICE *slice /* not changed */ ) { SLICE *temp; int dim; xassert(mpl == mpl); dim = 0; for (temp = slice; temp != NULL; temp = temp->next) dim++; return dim; } /*---------------------------------------------------------------------- -- slice_arity - determine arity of slice. -- -- This routine returns arity of slice, i.e. number of null components -- (indicated by asterisks) in the slice. */ int slice_arity ( MPL *mpl, SLICE *slice /* not changed */ ) { SLICE *temp; int arity; xassert(mpl == mpl); arity = 0; for (temp = slice; temp != NULL; temp = temp->next) if (temp->sym == NULL) arity++; return arity; } /*---------------------------------------------------------------------- -- fake_slice - create fake slice of all asterisks. -- -- This routine creates a fake slice of given dimension, which contains -- asterisks in all components. Zero dimension is allowed. */ SLICE *fake_slice(MPL *mpl, int dim) { SLICE *slice; slice = create_slice(mpl); while (dim-- > 0) slice = expand_slice(mpl, slice, NULL); return slice; } /*---------------------------------------------------------------------- -- delete_slice - delete slice. -- -- This routine deletes specified slice. */ void delete_slice ( MPL *mpl, SLICE *slice /* destroyed */ ) { SLICE *temp; while (slice != NULL) { temp = slice; slice = temp->next; if (temp->sym != NULL) delete_symbol(mpl, temp->sym); xassert(sizeof(SLICE) == sizeof(TUPLE)); dmp_free_atom(mpl->tuples, temp, sizeof(TUPLE)); } return; } /*---------------------------------------------------------------------- -- is_number - check if current token is number. -- -- If the current token is a number, this routine returns non-zero. -- Otherwise zero is returned. */ int is_number(MPL *mpl) { return mpl->token == T_NUMBER; } /*---------------------------------------------------------------------- -- is_symbol - check if current token is symbol. -- -- If the current token is suitable to be a symbol, the routine returns -- non-zero. Otherwise zero is returned. */ int is_symbol(MPL *mpl) { return mpl->token == T_NUMBER || mpl->token == T_SYMBOL || mpl->token == T_STRING; } /*---------------------------------------------------------------------- -- is_literal - check if current token is given symbolic literal. -- -- If the current token is given symbolic literal, this routine returns -- non-zero. Otherwise zero is returned. -- -- This routine is used on processing the data section in the same way -- as the routine is_keyword on processing the model section. */ int is_literal(MPL *mpl, char *literal) { return is_symbol(mpl) && strcmp(mpl->image, literal) == 0; } /*---------------------------------------------------------------------- -- read_number - read number. -- -- This routine reads the current token, which must be a number, and -- returns its numeric value. */ double read_number(MPL *mpl) { double num; xassert(is_number(mpl)); num = mpl->value; get_token(mpl /* */); return num; } /*---------------------------------------------------------------------- -- read_symbol - read symbol. -- -- This routine reads the current token, which must be a symbol, and -- returns its symbolic value. */ SYMBOL *read_symbol(MPL *mpl) { SYMBOL *sym; xassert(is_symbol(mpl)); if (is_number(mpl)) sym = create_symbol_num(mpl, mpl->value); else sym = create_symbol_str(mpl, create_string(mpl, mpl->image)); get_token(mpl /* */); return sym; } /*---------------------------------------------------------------------- -- read_slice - read slice. -- -- This routine reads slice using the syntax: -- -- ::= [ ] -- ::= ( ) -- ::= -- ::= , -- ::= -- ::= * -- -- The bracketed form of slice is used for members of multi-dimensional -- objects while the parenthesized form is used for elemental sets. */ SLICE *read_slice ( MPL *mpl, char *name, /* not changed */ int dim ) { SLICE *slice; int close; xassert(name != NULL); switch (mpl->token) { case T_LBRACKET: close = T_RBRACKET; break; case T_LEFT: xassert(dim > 0); close = T_RIGHT; break; default: xassert(mpl != mpl); } if (dim == 0) mpl_error(mpl, "%s cannot be subscripted", name); get_token(mpl /* ( | [ */); /* read slice components */ slice = create_slice(mpl); for (;;) { /* the current token must be a symbol or asterisk */ if (is_symbol(mpl)) slice = expand_slice(mpl, slice, read_symbol(mpl)); else if (mpl->token == T_ASTERISK) { slice = expand_slice(mpl, slice, NULL); get_token(mpl /* * */); } else mpl_error(mpl, "number, symbol, or asterisk missing where expec" "ted"); /* check a token that follows the symbol */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == close) break; else mpl_error(mpl, "syntax error in slice"); } /* number of slice components must be the same as the appropriate dimension */ if (slice_dimen(mpl, slice) != dim) { switch (close) { case T_RBRACKET: mpl_error(mpl, "%s must have %d subscript%s, not %d", name, dim, dim == 1 ? "" : "s", slice_dimen(mpl, slice)); break; case T_RIGHT: mpl_error(mpl, "%s has dimension %d, not %d", name, dim, slice_dimen(mpl, slice)); break; default: xassert(close != close); } } get_token(mpl /* ) | ] */); return slice; } /*---------------------------------------------------------------------- -- select_set - select set to saturate it with elemental sets. -- -- This routine selects set to saturate it with elemental sets provided -- in the data section. */ SET *select_set ( MPL *mpl, char *name /* not changed */ ) { SET *set; AVLNODE *node; xassert(name != NULL); node = avl_find_node(mpl->tree, name); if (node == NULL || avl_get_node_type(node) != A_SET) mpl_error(mpl, "%s not a set", name); set = (SET *)avl_get_node_link(node); if (set->assign != NULL || set->gadget != NULL) mpl_error(mpl, "%s needs no data", name); set->data = 1; return set; } /*---------------------------------------------------------------------- -- simple_format - read set data block in simple format. -- -- This routine reads set data block using the syntax: -- -- ::= , , ... , -- -- where are used to construct a complete n-tuple, which is -- included in elemental set assigned to the set member. Commae between -- symbols are optional and may be omitted anywhere. -- -- Number of components in the slice must be the same as dimension of -- n-tuples in elemental sets assigned to the set members. To construct -- complete n-tuple the routine replaces null positions in the slice by -- corresponding . -- -- If the slice contains at least one null position, the current token -- must be symbol. Otherwise, the routine reads no symbols to construct -- the n-tuple, so the current token is not checked. */ void simple_format ( MPL *mpl, SET *set, /* not changed */ MEMBER *memb, /* modified */ SLICE *slice /* not changed */ ) { TUPLE *tuple; SLICE *temp; SYMBOL *sym, *with = NULL; xassert(set != NULL); xassert(memb != NULL); xassert(slice != NULL); xassert(set->dimen == slice_dimen(mpl, slice)); xassert(memb->value.set->dim == set->dimen); if (slice_arity(mpl, slice) > 0) xassert(is_symbol(mpl)); /* read symbols and construct complete n-tuple */ tuple = create_tuple(mpl); for (temp = slice; temp != NULL; temp = temp->next) { if (temp->sym == NULL) { /* substitution is needed; read symbol */ if (!is_symbol(mpl)) { int lack = slice_arity(mpl, temp); /* with cannot be null due to assertion above */ xassert(with != NULL); if (lack == 1) mpl_error(mpl, "one item missing in data group beginning " "with %s", format_symbol(mpl, with)); else mpl_error(mpl, "%d items missing in data group beginning " "with %s", lack, format_symbol(mpl, with)); } sym = read_symbol(mpl); if (with == NULL) with = sym; } else { /* copy symbol from the slice */ sym = copy_symbol(mpl, temp->sym); } /* append the symbol to the n-tuple */ tuple = expand_tuple(mpl, tuple, sym); /* skip optional comma *between* */ if (temp->next != NULL && mpl->token == T_COMMA) get_token(mpl /* , */); } /* add constructed n-tuple to elemental set */ check_then_add(mpl, memb->value.set, tuple); return; } /*---------------------------------------------------------------------- -- matrix_format - read set data block in matrix format. -- -- This routine reads set data block using the syntax: -- -- ::= ... := -- +/- +/- ... +/- -- +/- +/- ... +/- -- . . . . . . . . . . . -- +/- +/- ... +/- -- -- where are symbols that denote rows of the matrix, -- are symbols that denote columns of the matrix, "+" and "-" indicate -- whether corresponding n-tuple needs to be included in the elemental -- set or not, respectively. -- -- Number of the slice components must be the same as dimension of the -- elemental set. The slice must have two null positions. To construct -- complete n-tuple for particular element of the matrix the routine -- replaces first null position of the slice by the corresponding -- (or , if the flag tr is on) and second null position by the -- corresponding (or by , if the flag tr is on). */ void matrix_format ( MPL *mpl, SET *set, /* not changed */ MEMBER *memb, /* modified */ SLICE *slice, /* not changed */ int tr ) { SLICE *list, *col, *temp; TUPLE *tuple; SYMBOL *row; xassert(set != NULL); xassert(memb != NULL); xassert(slice != NULL); xassert(set->dimen == slice_dimen(mpl, slice)); xassert(memb->value.set->dim == set->dimen); xassert(slice_arity(mpl, slice) == 2); /* read the matrix heading that contains column symbols (there may be no columns at all) */ list = create_slice(mpl); while (mpl->token != T_ASSIGN) { /* read column symbol and append it to the column list */ if (!is_symbol(mpl)) mpl_error(mpl, "number, symbol, or := missing where expected"); list = expand_slice(mpl, list, read_symbol(mpl)); } get_token(mpl /* := */); /* read zero or more rows that contain matrix data */ while (is_symbol(mpl)) { /* read row symbol (if the matrix has no columns, row symbols are just ignored) */ row = read_symbol(mpl); /* read the matrix row accordingly to the column list */ for (col = list; col != NULL; col = col->next) { int which = 0; /* check indicator */ if (is_literal(mpl, "+")) ; else if (is_literal(mpl, "-")) { get_token(mpl /* - */); continue; } else { int lack = slice_dimen(mpl, col); if (lack == 1) mpl_error(mpl, "one item missing in data group beginning " "with %s", format_symbol(mpl, row)); else mpl_error(mpl, "%d items missing in data group beginning " "with %s", lack, format_symbol(mpl, row)); } /* construct complete n-tuple */ tuple = create_tuple(mpl); for (temp = slice; temp != NULL; temp = temp->next) { if (temp->sym == NULL) { /* substitution is needed */ switch (++which) { case 1: /* substitute in the first null position */ tuple = expand_tuple(mpl, tuple, copy_symbol(mpl, tr ? col->sym : row)); break; case 2: /* substitute in the second null position */ tuple = expand_tuple(mpl, tuple, copy_symbol(mpl, tr ? row : col->sym)); break; default: xassert(which != which); } } else { /* copy symbol from the slice */ tuple = expand_tuple(mpl, tuple, copy_symbol(mpl, temp->sym)); } } xassert(which == 2); /* add constructed n-tuple to elemental set */ check_then_add(mpl, memb->value.set, tuple); get_token(mpl /* + */); } /* delete the row symbol */ delete_symbol(mpl, row); } /* delete the column list */ delete_slice(mpl, list); return; } /*---------------------------------------------------------------------- -- set_data - read set data. -- -- This routine reads set data using the syntax: -- -- ::= set ; -- ::= set [ ] ; -- ::= -- ::= -- ::= , := -- ::= , ( ) -- ::= , -- ::= , : -- ::= , (tr) -- ::= , (tr) : -- -- Commae in are optional and may be omitted anywhere. */ void set_data(MPL *mpl) { SET *set; TUPLE *tuple; MEMBER *memb; SLICE *slice; int tr = 0; xassert(is_literal(mpl, "set")); get_token(mpl /* set */); /* symbolic name of set must follows the keyword 'set' */ if (!is_symbol(mpl)) mpl_error(mpl, "set name missing where expected"); /* select the set to saturate it with data */ set = select_set(mpl, mpl->image); get_token(mpl /* */); /* read optional subscript list, which identifies member of the set to be read */ tuple = create_tuple(mpl); if (mpl->token == T_LBRACKET) { /* subscript list is specified */ if (set->dim == 0) mpl_error(mpl, "%s cannot be subscripted", set->name); get_token(mpl /* [ */); /* read symbols and construct subscript list */ for (;;) { if (!is_symbol(mpl)) mpl_error(mpl, "number or symbol missing where expected"); tuple = expand_tuple(mpl, tuple, read_symbol(mpl)); if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_RBRACKET) break; else mpl_error(mpl, "syntax error in subscript list"); } if (set->dim != tuple_dimen(mpl, tuple)) mpl_error(mpl, "%s must have %d subscript%s rather than %d", set->name, set->dim, set->dim == 1 ? "" : "s", tuple_dimen(mpl, tuple)); get_token(mpl /* ] */); } else { /* subscript list is not specified */ if (set->dim != 0) mpl_error(mpl, "%s must be subscripted", set->name); } /* there must be no member with the same subscript list */ if (find_member(mpl, set->array, tuple) != NULL) mpl_error(mpl, "%s%s already defined", set->name, format_tuple(mpl, '[', tuple)); /* add new member to the set and assign it empty elemental set */ memb = add_member(mpl, set->array, tuple); memb->value.set = create_elemset(mpl, set->dimen); /* create an initial fake slice of all asterisks */ slice = fake_slice(mpl, set->dimen); /* read zero or more data assignments */ for (;;) { /* skip optional comma */ if (mpl->token == T_COMMA) get_token(mpl /* , */); /* process assignment element */ if (mpl->token == T_ASSIGN) { /* assignment ligature is non-significant element */ get_token(mpl /* := */); } else if (mpl->token == T_LEFT) { /* left parenthesis begins either new slice or "transpose" indicator */ int is_tr; get_token(mpl /* ( */); is_tr = is_literal(mpl, "tr"); unget_token(mpl /* ( */); if (is_tr) goto left; /* delete the current slice and read new one */ delete_slice(mpl, slice); slice = read_slice(mpl, set->name, set->dimen); /* each new slice resets the "transpose" indicator */ tr = 0; /* if the new slice is 0-ary, formally there is one 0-tuple (in the simple format) that follows it */ if (slice_arity(mpl, slice) == 0) simple_format(mpl, set, memb, slice); } else if (is_symbol(mpl)) { /* number or symbol begins data in the simple format */ simple_format(mpl, set, memb, slice); } else if (mpl->token == T_COLON) { /* colon begins data in the matrix format */ if (slice_arity(mpl, slice) != 2) err1: mpl_error(mpl, "slice currently used must specify 2 asterisk" "s, not %d", slice_arity(mpl, slice)); get_token(mpl /* : */); /* read elemental set data in the matrix format */ matrix_format(mpl, set, memb, slice, tr); } else if (mpl->token == T_LEFT) left: { /* left parenthesis begins the "transpose" indicator, which is followed by data in the matrix format */ get_token(mpl /* ( */); if (!is_literal(mpl, "tr")) err2: mpl_error(mpl, "transpose indicator (tr) incomplete"); if (slice_arity(mpl, slice) != 2) goto err1; get_token(mpl /* tr */); if (mpl->token != T_RIGHT) goto err2; get_token(mpl /* ) */); /* in this case the colon is optional */ if (mpl->token == T_COLON) get_token(mpl /* : */); /* set the "transpose" indicator */ tr = 1; /* read elemental set data in the matrix format */ matrix_format(mpl, set, memb, slice, tr); } else if (mpl->token == T_SEMICOLON) { /* semicolon terminates the data block */ get_token(mpl /* ; */); break; } else mpl_error(mpl, "syntax error in set data block"); } /* delete the current slice */ delete_slice(mpl, slice); return; } /*---------------------------------------------------------------------- -- select_parameter - select parameter to saturate it with data. -- -- This routine selects parameter to saturate it with data provided in -- the data section. */ PARAMETER *select_parameter ( MPL *mpl, char *name /* not changed */ ) { PARAMETER *par; AVLNODE *node; xassert(name != NULL); node = avl_find_node(mpl->tree, name); if (node == NULL || avl_get_node_type(node) != A_PARAMETER) mpl_error(mpl, "%s not a parameter", name); par = (PARAMETER *)avl_get_node_link(node); if (par->assign != NULL) mpl_error(mpl, "%s needs no data", name); if (par->data) mpl_error(mpl, "%s already provided with data", name); par->data = 1; return par; } /*---------------------------------------------------------------------- -- set_default - set default parameter value. -- -- This routine sets default value for specified parameter. */ void set_default ( MPL *mpl, PARAMETER *par, /* not changed */ SYMBOL *altval /* destroyed */ ) { xassert(par != NULL); xassert(altval != NULL); if (par->option != NULL) mpl_error(mpl, "default value for %s already specified in model se" "ction", par->name); xassert(par->defval == NULL); par->defval = altval; return; } /*---------------------------------------------------------------------- -- read_value - read value and assign it to parameter member. -- -- This routine reads numeric or symbolic value from the input stream -- and assigns to new parameter member specified by its n-tuple, which -- (the member) is created and added to the parameter array. */ MEMBER *read_value ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* destroyed */ ) { MEMBER *memb; xassert(par != NULL); xassert(is_symbol(mpl)); /* there must be no member with the same n-tuple */ if (find_member(mpl, par->array, tuple) != NULL) mpl_error(mpl, "%s%s already defined", par->name, format_tuple(mpl, '[', tuple)); /* create new parameter member with given n-tuple */ memb = add_member(mpl, par->array, tuple); /* read value and assigns it to the new parameter member */ switch (par->type) { case A_NUMERIC: case A_INTEGER: case A_BINARY: if (!is_number(mpl)) mpl_error(mpl, "%s requires numeric data", par->name); memb->value.num = read_number(mpl); break; case A_SYMBOLIC: memb->value.sym = read_symbol(mpl); break; default: xassert(par != par); } return memb; } /*---------------------------------------------------------------------- -- plain_format - read parameter data block in plain format. -- -- This routine reads parameter data block using the syntax: -- -- ::= , , ... , , -- -- where are used to determine a complete subscript list for -- parameter member, is a numeric or symbolic value assigned to -- the parameter member. Commae between data items are optional and may -- be omitted anywhere. -- -- Number of components in the slice must be the same as dimension of -- the parameter. To construct the complete subscript list the routine -- replaces null positions in the slice by corresponding . */ void plain_format ( MPL *mpl, PARAMETER *par, /* not changed */ SLICE *slice /* not changed */ ) { TUPLE *tuple; SLICE *temp; SYMBOL *sym, *with = NULL; xassert(par != NULL); xassert(par->dim == slice_dimen(mpl, slice)); xassert(is_symbol(mpl)); /* read symbols and construct complete subscript list */ tuple = create_tuple(mpl); for (temp = slice; temp != NULL; temp = temp->next) { if (temp->sym == NULL) { /* substitution is needed; read symbol */ if (!is_symbol(mpl)) { int lack = slice_arity(mpl, temp) + 1; xassert(with != NULL); xassert(lack > 1); mpl_error(mpl, "%d items missing in data group beginning wit" "h %s", lack, format_symbol(mpl, with)); } sym = read_symbol(mpl); if (with == NULL) with = sym; } else { /* copy symbol from the slice */ sym = copy_symbol(mpl, temp->sym); } /* append the symbol to the subscript list */ tuple = expand_tuple(mpl, tuple, sym); /* skip optional comma */ if (mpl->token == T_COMMA) get_token(mpl /* , */); } /* read value and assign it to new parameter member */ if (!is_symbol(mpl)) { xassert(with != NULL); mpl_error(mpl, "one item missing in data group beginning with %s", format_symbol(mpl, with)); } read_value(mpl, par, tuple); return; } /*---------------------------------------------------------------------- -- tabular_format - read parameter data block in tabular format. -- -- This routine reads parameter data block using the syntax: -- -- ::= ... := -- ... -- ... -- . . . . . . . . . . . -- ... -- -- where are symbols that denote rows of the table, -- are symbols that denote columns of the table, are numeric -- or symbolic values assigned to the corresponding parameter members. -- If is specified as single point, no value is provided. -- -- Number of components in the slice must be the same as dimension of -- the parameter. The slice must have two null positions. To construct -- complete subscript list for particular the routine replaces -- the first null position of the slice by the corresponding (or -- , if the flag tr is on) and the second null position by the -- corresponding (or by , if the flag tr is on). */ void tabular_format ( MPL *mpl, PARAMETER *par, /* not changed */ SLICE *slice, /* not changed */ int tr ) { SLICE *list, *col, *temp; TUPLE *tuple; SYMBOL *row; xassert(par != NULL); xassert(par->dim == slice_dimen(mpl, slice)); xassert(slice_arity(mpl, slice) == 2); /* read the table heading that contains column symbols (the table may have no columns) */ list = create_slice(mpl); while (mpl->token != T_ASSIGN) { /* read column symbol and append it to the column list */ if (!is_symbol(mpl)) mpl_error(mpl, "number, symbol, or := missing where expected"); list = expand_slice(mpl, list, read_symbol(mpl)); } get_token(mpl /* := */); /* read zero or more rows that contain tabular data */ while (is_symbol(mpl)) { /* read row symbol (if the table has no columns, these symbols are just ignored) */ row = read_symbol(mpl); /* read values accordingly to the column list */ for (col = list; col != NULL; col = col->next) { int which = 0; /* if the token is single point, no value is provided */ if (is_literal(mpl, ".")) { get_token(mpl /* . */); continue; } /* construct complete subscript list */ tuple = create_tuple(mpl); for (temp = slice; temp != NULL; temp = temp->next) { if (temp->sym == NULL) { /* substitution is needed */ switch (++which) { case 1: /* substitute in the first null position */ tuple = expand_tuple(mpl, tuple, copy_symbol(mpl, tr ? col->sym : row)); break; case 2: /* substitute in the second null position */ tuple = expand_tuple(mpl, tuple, copy_symbol(mpl, tr ? row : col->sym)); break; default: xassert(which != which); } } else { /* copy symbol from the slice */ tuple = expand_tuple(mpl, tuple, copy_symbol(mpl, temp->sym)); } } xassert(which == 2); /* read value and assign it to new parameter member */ if (!is_symbol(mpl)) { int lack = slice_dimen(mpl, col); if (lack == 1) mpl_error(mpl, "one item missing in data group beginning " "with %s", format_symbol(mpl, row)); else mpl_error(mpl, "%d items missing in data group beginning " "with %s", lack, format_symbol(mpl, row)); } read_value(mpl, par, tuple); } /* delete the row symbol */ delete_symbol(mpl, row); } /* delete the column list */ delete_slice(mpl, list); return; } /*---------------------------------------------------------------------- -- tabbing_format - read parameter data block in tabbing format. -- -- This routine reads parameter data block using the syntax: -- -- ::= , ... , , := , -- , ... , , , ... , , -- , ... , , , ... , , -- . . . . . . . . . . . . . . . . . -- , ... , , , ... , -- ::= -- ::= : -- -- where are names of parameters (all the parameters must be -- subscripted and have identical dimensions), are symbols -- used to define subscripts of parameter members, are numeric -- or symbolic values assigned to the corresponding parameter members. -- Optional may specify a simple set, in which case n-tuples -- built of for each row of the data table (i.e. subscripts -- of parameter members) are added to the specified set. Commae between -- data items are optional and may be omitted anywhere. -- -- If the parameter altval is not NULL, it specifies a default value -- provided for all the parameters specified in the data block. */ void tabbing_format ( MPL *mpl, SYMBOL *altval /* not changed */ ) { SET *set = NULL; PARAMETER *par; SLICE *list, *col; TUPLE *tuple; int next_token, j, dim = 0; char *last_name = NULL; /* read the optional */ if (is_symbol(mpl)) { get_token(mpl /* */); next_token = mpl->token; unget_token(mpl /* */); if (next_token == T_COLON) { /* select the set to saturate it with data */ set = select_set(mpl, mpl->image); /* the set must be simple (i.e. not set of sets) */ if (set->dim != 0) mpl_error(mpl, "%s must be a simple set", set->name); /* and must not be defined yet */ if (set->array->head != NULL) mpl_error(mpl, "%s already defined", set->name); /* add new (the only) member to the set and assign it empty elemental set */ add_member(mpl, set->array, NULL)->value.set = create_elemset(mpl, set->dimen); last_name = set->name, dim = set->dimen; get_token(mpl /* */); xassert(mpl->token == T_COLON); get_token(mpl /* : */); } } /* read the table heading that contains parameter names */ list = create_slice(mpl); while (mpl->token != T_ASSIGN) { /* there must be symbolic name of parameter */ if (!is_symbol(mpl)) mpl_error(mpl, "parameter name or := missing where expected"); /* select the parameter to saturate it with data */ par = select_parameter(mpl, mpl->image); /* the parameter must be subscripted */ if (par->dim == 0) mpl_error(mpl, "%s not a subscripted parameter", mpl->image); /* the set (if specified) and all the parameters in the data block must have identical dimension */ if (dim != 0 && par->dim != dim) { xassert(last_name != NULL); mpl_error(mpl, "%s has dimension %d while %s has dimension %d", last_name, dim, par->name, par->dim); } /* set default value for the parameter (if specified) */ if (altval != NULL) set_default(mpl, par, copy_symbol(mpl, altval)); /* append the parameter to the column list */ list = expand_slice(mpl, list, (SYMBOL *)par); last_name = par->name, dim = par->dim; get_token(mpl /* */); /* skip optional comma */ if (mpl->token == T_COMMA) get_token(mpl /* , */); } if (slice_dimen(mpl, list) == 0) mpl_error(mpl, "at least one parameter name required"); get_token(mpl /* := */); /* skip optional comma */ if (mpl->token == T_COMMA) get_token(mpl /* , */); /* read rows that contain tabbing data */ while (is_symbol(mpl)) { /* read subscript list */ tuple = create_tuple(mpl); for (j = 1; j <= dim; j++) { /* read j-th subscript */ if (!is_symbol(mpl)) { int lack = slice_dimen(mpl, list) + dim - j + 1; xassert(tuple != NULL); xassert(lack > 1); mpl_error(mpl, "%d items missing in data group beginning wit" "h %s", lack, format_symbol(mpl, tuple->sym)); } /* read and append j-th subscript to the n-tuple */ tuple = expand_tuple(mpl, tuple, read_symbol(mpl)); /* skip optional comma *between* */ if (j < dim && mpl->token == T_COMMA) get_token(mpl /* , */); } /* if the set is specified, add to it new n-tuple, which is a copy of the subscript list just read */ if (set != NULL) check_then_add(mpl, set->array->head->value.set, copy_tuple(mpl, tuple)); /* skip optional comma between and */ if (mpl->token == T_COMMA) get_token(mpl /* , */); /* read values accordingly to the column list */ for (col = list; col != NULL; col = col->next) { /* if the token is single point, no value is provided */ if (is_literal(mpl, ".")) { get_token(mpl /* . */); continue; } /* read value and assign it to new parameter member */ if (!is_symbol(mpl)) { int lack = slice_dimen(mpl, col); xassert(tuple != NULL); if (lack == 1) mpl_error(mpl, "one item missing in data group beginning " "with %s", format_symbol(mpl, tuple->sym)); else mpl_error(mpl, "%d items missing in data group beginning " "with %s", lack, format_symbol(mpl, tuple->sym)); } read_value(mpl, (PARAMETER *)col->sym, copy_tuple(mpl, tuple)); /* skip optional comma preceding the next value */ if (col->next != NULL && mpl->token == T_COMMA) get_token(mpl /* , */); } /* delete the original subscript list */ delete_tuple(mpl, tuple); /* skip optional comma (only if there is next data group) */ if (mpl->token == T_COMMA) { get_token(mpl /* , */); if (!is_symbol(mpl)) unget_token(mpl /* , */); } } /* delete the column list (it contains parameters, not symbols, so nullify it before) */ for (col = list; col != NULL; col = col->next) col->sym = NULL; delete_slice(mpl, list); return; } /*---------------------------------------------------------------------- -- parameter_data - read parameter data. -- -- This routine reads parameter data using the syntax: -- -- ::= param : ; -- ::= param -- ; -- ::= -- ::= -- ::= default -- ::= -- ::= , := -- ::= , [ ] -- ::= , -- ::= , : -- ::= , (tr) -- ::= , (tr) : -- -- Commae in are optional and may be omitted anywhere. */ void parameter_data(MPL *mpl) { PARAMETER *par; SYMBOL *altval = NULL; SLICE *slice; int tr = 0; xassert(is_literal(mpl, "param")); get_token(mpl /* param */); /* read optional default value */ if (is_literal(mpl, "default")) { get_token(mpl /* default */); if (!is_symbol(mpl)) mpl_error(mpl, "default value missing where expected"); altval = read_symbol(mpl); /* if the default value follows the keyword 'param', the next token must be only the colon */ if (mpl->token != T_COLON) mpl_error(mpl, "colon missing where expected"); } /* being used after the keyword 'param' or the optional default value the colon begins data in the tabbing format */ if (mpl->token == T_COLON) { get_token(mpl /* : */); /* skip optional comma */ if (mpl->token == T_COMMA) get_token(mpl /* , */); /* read parameter data in the tabbing format */ tabbing_format(mpl, altval); /* on reading data in the tabbing format the default value is always copied, so delete the original symbol */ if (altval != NULL) delete_symbol(mpl, altval); /* the next token must be only semicolon */ if (mpl->token != T_SEMICOLON) mpl_error(mpl, "symbol, number, or semicolon missing where expe" "cted"); get_token(mpl /* ; */); goto done; } /* in other cases there must be symbolic name of parameter, which follows the keyword 'param' */ if (!is_symbol(mpl)) mpl_error(mpl, "parameter name missing where expected"); /* select the parameter to saturate it with data */ par = select_parameter(mpl, mpl->image); get_token(mpl /* */); /* read optional default value */ if (is_literal(mpl, "default")) { get_token(mpl /* default */); if (!is_symbol(mpl)) mpl_error(mpl, "default value missing where expected"); altval = read_symbol(mpl); /* set default value for the parameter */ set_default(mpl, par, altval); } /* create initial fake slice of all asterisks */ slice = fake_slice(mpl, par->dim); /* read zero or more data assignments */ for (;;) { /* skip optional comma */ if (mpl->token == T_COMMA) get_token(mpl /* , */); /* process current assignment */ if (mpl->token == T_ASSIGN) { /* assignment ligature is non-significant element */ get_token(mpl /* := */); } else if (mpl->token == T_LBRACKET) { /* left bracket begins new slice; delete the current slice and read new one */ delete_slice(mpl, slice); slice = read_slice(mpl, par->name, par->dim); /* each new slice resets the "transpose" indicator */ tr = 0; } else if (is_symbol(mpl)) { /* number or symbol begins data in the plain format */ plain_format(mpl, par, slice); } else if (mpl->token == T_COLON) { /* colon begins data in the tabular format */ if (par->dim == 0) err1: mpl_error(mpl, "%s not a subscripted parameter", par->name); if (slice_arity(mpl, slice) != 2) err2: mpl_error(mpl, "slice currently used must specify 2 asterisk" "s, not %d", slice_arity(mpl, slice)); get_token(mpl /* : */); /* read parameter data in the tabular format */ tabular_format(mpl, par, slice, tr); } else if (mpl->token == T_LEFT) { /* left parenthesis begins the "transpose" indicator, which is followed by data in the tabular format */ get_token(mpl /* ( */); if (!is_literal(mpl, "tr")) err3: mpl_error(mpl, "transpose indicator (tr) incomplete"); if (par->dim == 0) goto err1; if (slice_arity(mpl, slice) != 2) goto err2; get_token(mpl /* tr */); if (mpl->token != T_RIGHT) goto err3; get_token(mpl /* ) */); /* in this case the colon is optional */ if (mpl->token == T_COLON) get_token(mpl /* : */); /* set the "transpose" indicator */ tr = 1; /* read parameter data in the tabular format */ tabular_format(mpl, par, slice, tr); } else if (mpl->token == T_SEMICOLON) { /* semicolon terminates the data block */ get_token(mpl /* ; */); break; } else mpl_error(mpl, "syntax error in parameter data block"); } /* delete the current slice */ delete_slice(mpl, slice); done: return; } /*---------------------------------------------------------------------- -- data_section - read data section. -- -- This routine reads data section using the syntax: -- -- ::= -- ::= ; -- ::= -- ::= -- -- Reading data section is terminated by either the keyword 'end' or -- the end of file. */ void data_section(MPL *mpl) { while (!(mpl->token == T_EOF || is_literal(mpl, "end"))) { if (is_literal(mpl, "set")) set_data(mpl); else if (is_literal(mpl, "param")) parameter_data(mpl); else mpl_error(mpl, "syntax error in data section"); } return; } /* eof */ sources_5316/external/glpk/glpfhv.h0000644000176700017670000001522311401660400016134 0ustar paulpaul/* glpfhv.h (LP basis factorization, FHV eta file version) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPFHV_H #define GLPFHV_H #include "glpluf.h" /*********************************************************************** * The structure FHV defines the factorization of the basis mxm-matrix * B, where m is the number of rows in corresponding problem instance. * * This factorization is the following sextet: * * [B] = (F, H, V, P0, P, Q), (1) * * where F, H, and V are such matrices that * * B = F * H * V, (2) * * and P0, P, and Q are such permutation matrices that the matrix * * L = P0 * F * inv(P0) (3) * * is lower triangular with unity diagonal, and the matrix * * U = P * V * Q (4) * * is upper triangular. All the matrices have the same order m, which * is the order of the basis matrix B. * * The matrices F, V, P, and Q are stored in the structure LUF (see the * module GLPLUF), which is a member of the structure FHV. * * The matrix H is stored in the form of eta file using row-like format * as follows: * * H = H[1] * H[2] * ... * H[nfs], (5) * * where H[k], k = 1, 2, ..., nfs, is a row-like factor, which differs * from the unity matrix only by one row, nfs is current number of row- * like factors. After the factorization has been built for some given * basis matrix B the matrix H has no factors and thus it is the unity * matrix. Then each time when the factorization is recomputed for an * adjacent basis matrix, the next factor H[k], k = 1, 2, ... is built * and added to the end of the eta file H. * * Being sparse vectors non-trivial rows of the factors H[k] are stored * in the right part of the sparse vector area (SVA) in the same manner * as rows and columns of the matrix F. * * For more details see the program documentation. */ typedef struct FHV FHV; struct FHV { /* LP basis factorization */ int m_max; /* maximal value of m (increased automatically, if necessary) */ int m; /* the order of matrices B, F, H, V, P0, P, Q */ int valid; /* the factorization is valid only if this flag is set */ LUF *luf; /* LU-factorization (contains the matrices F, V, P, Q) */ /*--------------------------------------------------------------*/ /* matrix H in the form of eta file */ int hh_max; /* maximal number of row-like factors (which limits the number of updates of the factorization) */ int hh_nfs; /* current number of row-like factors (0 <= hh_nfs <= hh_max) */ int *hh_ind; /* int hh_ind[1+hh_max]; */ /* hh_ind[k], k = 1, ..., nfs, is the number of a non-trivial row of factor H[k] */ int *hh_ptr; /* int hh_ptr[1+hh_max]; */ /* hh_ptr[k], k = 1, ..., nfs, is a pointer to the first element of the non-trivial row of factor H[k] in the SVA */ int *hh_len; /* int hh_len[1+hh_max]; */ /* hh_len[k], k = 1, ..., nfs, is the number of non-zero elements in the non-trivial row of factor H[k] */ /*--------------------------------------------------------------*/ /* matrix P0 */ int *p0_row; /* int p0_row[1+m_max]; */ /* p0_row[i] = j means that p0[i,j] = 1 */ int *p0_col; /* int p0_col[1+m_max]; */ /* p0_col[j] = i means that p0[i,j] = 1 */ /* if i-th row or column of the matrix F corresponds to i'-th row or column of the matrix L = P0*F*inv(P0), then p0_row[i'] = i and p0_col[i] = i' */ /*--------------------------------------------------------------*/ /* working arrays */ int *cc_ind; /* int cc_ind[1+m_max]; */ /* integer working array */ double *cc_val; /* double cc_val[1+m_max]; */ /* floating-point working array */ /*--------------------------------------------------------------*/ /* control parameters */ double upd_tol; /* update tolerance; if after updating the factorization absolute value of some diagonal element u[k,k] of matrix U = P*V*Q is less than upd_tol * max(|u[k,*]|, |u[*,k]|), the factorization is considered as inaccurate */ /*--------------------------------------------------------------*/ /* some statistics */ int nnz_h; /* current number of non-zeros in all factors of matrix H */ }; /* return codes: */ #define FHV_ESING 1 /* singular matrix */ #define FHV_ECOND 2 /* ill-conditioned matrix */ #define FHV_ECHECK 3 /* insufficient accuracy */ #define FHV_ELIMIT 4 /* update limit reached */ #define FHV_EROOM 5 /* SVA overflow */ #define fhv_create_it _glp_fhv_create_it FHV *fhv_create_it(void); /* create LP basis factorization */ #define fhv_factorize _glp_fhv_factorize int fhv_factorize(FHV *fhv, int m, int (*col)(void *info, int j, int ind[], double val[]), void *info); /* compute LP basis factorization */ #define fhv_h_solve _glp_fhv_h_solve void fhv_h_solve(FHV *fhv, int tr, double x[]); /* solve system H*x = b or H'*x = b */ #define fhv_ftran _glp_fhv_ftran void fhv_ftran(FHV *fhv, double x[]); /* perform forward transformation (solve system B*x = b) */ #define fhv_btran _glp_fhv_btran void fhv_btran(FHV *fhv, double x[]); /* perform backward transformation (solve system B'*x = b) */ #define fhv_update_it _glp_fhv_update_it int fhv_update_it(FHV *fhv, int j, int len, const int ind[], const double val[]); /* update LP basis factorization */ #define fhv_delete_it _glp_fhv_delete_it void fhv_delete_it(FHV *fhv); /* delete LP basis factorization */ #endif /* eof */ sources_5316/external/glpk/glplib03.c0000644000176700017670000004335611401660400016265 0ustar paulpaul/* glplib03.c (miscellaneous library routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glplib.h" /*********************************************************************** * NAME * * str2int - convert character string to value of int type * * SYNOPSIS * * #include "glplib.h" * int str2int(const char *str, int *val); * * DESCRIPTION * * The routine str2int converts the character string str to a value of * integer type and stores the value into location, which the parameter * val points to (in the case of error content of this location is not * changed). * * RETURNS * * The routine returns one of the following error codes: * * 0 - no error; * 1 - value out of range; * 2 - character string is syntactically incorrect. */ int str2int(const char *str, int *_val) { int d, k, s, val = 0; /* scan optional sign */ if (str[0] == '+') s = +1, k = 1; else if (str[0] == '-') s = -1, k = 1; else s = +1, k = 0; /* check for the first digit */ if (!isdigit((unsigned char)str[k])) return 2; /* scan digits */ while (isdigit((unsigned char)str[k])) { d = str[k++] - '0'; if (s > 0) { if (val > INT_MAX / 10) return 1; val *= 10; if (val > INT_MAX - d) return 1; val += d; } else { if (val < INT_MIN / 10) return 1; val *= 10; if (val < INT_MIN + d) return 1; val -= d; } } /* check for terminator */ if (str[k] != '\0') return 2; /* conversion has been done */ *_val = val; return 0; } /*********************************************************************** * NAME * * str2num - convert character string to value of double type * * SYNOPSIS * * #include "glplib.h" * int str2num(const char *str, double *val); * * DESCRIPTION * * The routine str2num converts the character string str to a value of * double type and stores the value into location, which the parameter * val points to (in the case of error content of this location is not * changed). * * RETURNS * * The routine returns one of the following error codes: * * 0 - no error; * 1 - value out of range; * 2 - character string is syntactically incorrect. */ int str2num(const char *str, double *_val) { int k; double val; /* scan optional sign */ k = (str[0] == '+' || str[0] == '-' ? 1 : 0); /* check for decimal point */ if (str[k] == '.') { k++; /* a digit should follow it */ if (!isdigit((unsigned char)str[k])) return 2; k++; goto frac; } /* integer part should start with a digit */ if (!isdigit((unsigned char)str[k])) return 2; /* scan integer part */ while (isdigit((unsigned char)str[k])) k++; /* check for decimal point */ if (str[k] == '.') k++; frac: /* scan optional fraction part */ while (isdigit((unsigned char)str[k])) k++; /* check for decimal exponent */ if (str[k] == 'E' || str[k] == 'e') { k++; /* scan optional sign */ if (str[k] == '+' || str[k] == '-') k++; /* a digit should follow E, E+ or E- */ if (!isdigit((unsigned char)str[k])) return 2; } /* scan optional exponent part */ while (isdigit((unsigned char)str[k])) k++; /* check for terminator */ if (str[k] != '\0') return 2; /* perform conversion */ { char *endptr; val = strtod(str, &endptr); if (*endptr != '\0') return 2; } /* check for overflow */ if (!(-DBL_MAX <= val && val <= +DBL_MAX)) return 1; /* check for underflow */ if (-DBL_MIN < val && val < +DBL_MIN) val = 0.0; /* conversion has been done */ *_val = val; return 0; } /*********************************************************************** * NAME * * strspx - remove all spaces from character string * * SYNOPSIS * * #include "glplib.h" * char *strspx(char *str); * * DESCRIPTION * * The routine strspx removes all spaces from the character string str. * * RETURNS * * The routine returns a pointer to the character string. * * EXAMPLES * * strspx(" Errare humanum est ") => "Errarehumanumest" * * strspx(" ") => "" */ char *strspx(char *str) { char *s, *t; for (s = t = str; *s; s++) if (*s != ' ') *t++ = *s; *t = '\0'; return str; } /*********************************************************************** * NAME * * strtrim - remove trailing spaces from character string * * SYNOPSIS * * #include "glplib.h" * char *strtrim(char *str); * * DESCRIPTION * * The routine strtrim removes trailing spaces from the character * string str. * * RETURNS * * The routine returns a pointer to the character string. * * EXAMPLES * * strtrim("Errare humanum est ") => "Errare humanum est" * * strtrim(" ") => "" */ char *strtrim(char *str) { char *t; for (t = strrchr(str, '\0') - 1; t >= str; t--) { if (*t != ' ') break; *t = '\0'; } return str; } /*********************************************************************** * NAME * * strrev - reverse character string * * SYNOPSIS * * #include "glplib.h" * char *strrev(char *s); * * DESCRIPTION * * The routine strrev changes characters in a character string s to the * reverse order, except the terminating null character. * * RETURNS * * The routine returns the pointer s. * * EXAMPLES * * strrev("") => "" * * strrev("Today is Monday") => "yadnoM si yadoT" */ char *strrev(char *s) { int i, j; char t; for (i = 0, j = strlen(s)-1; i < j; i++, j--) t = s[i], s[i] = s[j], s[j] = t; return s; } /*********************************************************************** * NAME * * gcd - find greatest common divisor of two integers * * SYNOPSIS * * #include "glplib.h" * int gcd(int x, int y); * * RETURNS * * The routine gcd returns gcd(x, y), the greatest common divisor of * the two positive integers given. * * ALGORITHM * * The routine gcd is based on Euclid's algorithm. * * REFERENCES * * Don Knuth, The Art of Computer Programming, Vol.2: Seminumerical * Algorithms, 3rd Edition, Addison-Wesley, 1997. Section 4.5.2: The * Greatest Common Divisor, pp. 333-56. */ int gcd(int x, int y) { int r; xassert(x > 0 && y > 0); while (y > 0) r = x % y, x = y, y = r; return x; } /*********************************************************************** * NAME * * gcdn - find greatest common divisor of n integers * * SYNOPSIS * * #include "glplib.h" * int gcdn(int n, int x[]); * * RETURNS * * The routine gcdn returns gcd(x[1], x[2], ..., x[n]), the greatest * common divisor of n positive integers given, n > 0. * * BACKGROUND * * The routine gcdn is based on the following identity: * * gcd(x, y, z) = gcd(gcd(x, y), z). * * REFERENCES * * Don Knuth, The Art of Computer Programming, Vol.2: Seminumerical * Algorithms, 3rd Edition, Addison-Wesley, 1997. Section 4.5.2: The * Greatest Common Divisor, pp. 333-56. */ int gcdn(int n, int x[]) { int d, j; xassert(n > 0); for (j = 1; j <= n; j++) { xassert(x[j] > 0); if (j == 1) d = x[1]; else d = gcd(d, x[j]); if (d == 1) break; } return d; } /*********************************************************************** * NAME * * lcm - find least common multiple of two integers * * SYNOPSIS * * #include "glplib.h" * int lcm(int x, int y); * * RETURNS * * The routine lcm returns lcm(x, y), the least common multiple of the * two positive integers given. In case of integer overflow the routine * returns zero. * * BACKGROUND * * The routine lcm is based on the following identity: * * lcm(x, y) = (x * y) / gcd(x, y) = x * [y / gcd(x, y)], * * where gcd(x, y) is the greatest common divisor of x and y. */ int lcm(int x, int y) { xassert(x > 0); xassert(y > 0); y /= gcd(x, y); if (x > INT_MAX / y) return 0; return x * y; } /*********************************************************************** * NAME * * lcmn - find least common multiple of n integers * * SYNOPSIS * * #include "glplib.h" * int lcmn(int n, int x[]); * * RETURNS * * The routine lcmn returns lcm(x[1], x[2], ..., x[n]), the least * common multiple of n positive integers given, n > 0. In case of * integer overflow the routine returns zero. * * BACKGROUND * * The routine lcmn is based on the following identity: * * lcmn(x, y, z) = lcm(lcm(x, y), z), * * where lcm(x, y) is the least common multiple of x and y. */ int lcmn(int n, int x[]) { int m, j; xassert(n > 0); for (j = 1; j <= n; j++) { xassert(x[j] > 0); if (j == 1) m = x[1]; else m = lcm(m, x[j]); if (m == 0) break; } return m; } /*********************************************************************** * NAME * * round2n - round floating-point number to nearest power of two * * SYNOPSIS * * #include "glplib.h" * double round2n(double x); * * RETURNS * * Given a positive floating-point value x the routine round2n returns * 2^n such that |x - 2^n| is minimal. * * EXAMPLES * * round2n(10.1) = 2^3 = 8 * round2n(15.3) = 2^4 = 16 * round2n(0.01) = 2^(-7) = 0.0078125 * * BACKGROUND * * Let x = f * 2^e, where 0.5 <= f < 1 is a normalized fractional part, * e is an integer exponent. Then, obviously, 0.5 * 2^e <= x < 2^e, so * if x - 0.5 * 2^e <= 2^e - x, we choose 0.5 * 2^e = 2^(e-1), and 2^e * otherwise. The latter condition can be written as 2 * x <= 1.5 * 2^e * or 2 * f * 2^e <= 1.5 * 2^e or, finally, f <= 0.75. */ double round2n(double x) { int e; double f; xassert(x > 0.0); f = frexp(x, &e); return ldexp(1.0, f <= 0.75 ? e-1 : e); } /*********************************************************************** * NAME * * fp2rat - convert floating-point number to rational number * * SYNOPSIS * * #include "glplib.h" * int fp2rat(double x, double eps, double *p, double *q); * * DESCRIPTION * * Given a floating-point number 0 <= x < 1 the routine fp2rat finds * its "best" rational approximation p / q, where p >= 0 and q > 0 are * integer numbers, such that |x - p / q| <= eps. * * RETURNS * * The routine fp2rat returns the number of iterations used to achieve * the specified precision eps. * * EXAMPLES * * For x = sqrt(2) - 1 = 0.414213562373095 and eps = 1e-6 the routine * gives p = 408 and q = 985, where 408 / 985 = 0.414213197969543. * * BACKGROUND * * It is well known that every positive real number x can be expressed * as the following continued fraction: * * x = b[0] + a[1] * ------------------------ * b[1] + a[2] * ----------------- * b[2] + a[3] * ---------- * b[3] + ... * * where: * * a[k] = 1, k = 0, 1, 2, ... * * b[k] = floor(x[k]), k = 0, 1, 2, ... * * x[0] = x, * * x[k] = 1 / frac(x[k-1]), k = 1, 2, 3, ... * * To find the "best" rational approximation of x the routine computes * partial fractions f[k] by dropping after k terms as follows: * * f[k] = A[k] / B[k], * * where: * * A[-1] = 1, A[0] = b[0], B[-1] = 0, B[0] = 1, * * A[k] = b[k] * A[k-1] + a[k] * A[k-2], * * B[k] = b[k] * B[k-1] + a[k] * B[k-2]. * * Once the condition * * |x - f[k]| <= eps * * has been satisfied, the routine reports p = A[k] and q = B[k] as the * final answer. * * In the table below here is some statistics obtained for one million * random numbers uniformly distributed in the range [0, 1). * * eps max p mean p max q mean q max k mean k * ------------------------------------------------------------- * 1e-1 8 1.6 9 3.2 3 1.4 * 1e-2 98 6.2 99 12.4 5 2.4 * 1e-3 997 20.7 998 41.5 8 3.4 * 1e-4 9959 66.6 9960 133.5 10 4.4 * 1e-5 97403 211.7 97404 424.2 13 5.3 * 1e-6 479669 669.9 479670 1342.9 15 6.3 * 1e-7 1579030 2127.3 3962146 4257.8 16 7.3 * 1e-8 26188823 6749.4 26188824 13503.4 19 8.2 * * REFERENCES * * W. B. Jones and W. J. Thron, "Continued Fractions: Analytic Theory * and Applications," Encyclopedia on Mathematics and Its Applications, * Addison-Wesley, 1980. */ int fp2rat(double x, double eps, double *p, double *q) { int k; double xk, Akm1, Ak, Bkm1, Bk, ak, bk, fk, temp; if (!(0.0 <= x && x < 1.0)) xerror("fp2rat: x = %g; number out of range\n", x); for (k = 0; ; k++) { xassert(k <= 100); if (k == 0) { /* x[0] = x */ xk = x; /* A[-1] = 1 */ Akm1 = 1.0; /* A[0] = b[0] = floor(x[0]) = 0 */ Ak = 0.0; /* B[-1] = 0 */ Bkm1 = 0.0; /* B[0] = 1 */ Bk = 1.0; } else { /* x[k] = 1 / frac(x[k-1]) */ temp = xk - floor(xk); xassert(temp != 0.0); xk = 1.0 / temp; /* a[k] = 1 */ ak = 1.0; /* b[k] = floor(x[k]) */ bk = floor(xk); /* A[k] = b[k] * A[k-1] + a[k] * A[k-2] */ temp = bk * Ak + ak * Akm1; Akm1 = Ak, Ak = temp; /* B[k] = b[k] * B[k-1] + a[k] * B[k-2] */ temp = bk * Bk + ak * Bkm1; Bkm1 = Bk, Bk = temp; } /* f[k] = A[k] / B[k] */ fk = Ak / Bk; #if 0 print("%.*g / %.*g = %.*g", DBL_DIG, Ak, DBL_DIG, Bk, DBL_DIG, fk); #endif if (fabs(x - fk) <= eps) break; } *p = Ak; *q = Bk; return k; } /*********************************************************************** * NAME * * jday - convert calendar date to Julian day number * * SYNOPSIS * * #include "glplib.h" * int jday(int d, int m, int y); * * DESCRIPTION * * The routine jday converts a calendar date, Gregorian calendar, to * corresponding Julian day number j. * * From the given day d, month m, and year y, the Julian day number j * is computed without using tables. * * The routine is valid for 1 <= y <= 4000. * * RETURNS * * The routine jday returns the Julian day number, or negative value if * the specified date is incorrect. * * REFERENCES * * R. G. Tantzen, Algorithm 199: conversions between calendar date and * Julian day number, Communications of the ACM, vol. 6, no. 8, p. 444, * Aug. 1963. */ int jday(int d, int m, int y) { int c, ya, j, dd; if (!(1 <= d && d <= 31 && 1 <= m && m <= 12 && 1 <= y && y <= 4000)) { j = -1; goto done; } if (m >= 3) m -= 3; else m += 9, y--; c = y / 100; ya = y - 100 * c; j = (146097 * c) / 4 + (1461 * ya) / 4 + (153 * m + 2) / 5 + d + 1721119; jdate(j, &dd, NULL, NULL); if (d != dd) j = -1; done: return j; } /*********************************************************************** * NAME * * jdate - convert Julian day number to calendar date * * SYNOPSIS * * #include "glplib.h" * void jdate(int j, int *d, int *m, int *y); * * DESCRIPTION * * The routine jdate converts a Julian day number j to corresponding * calendar date, Gregorian calendar. * * The day d, month m, and year y are computed without using tables and * stored in corresponding locations. * * The routine is valid for 1721426 <= j <= 3182395. * * RETURNS * * If the conversion is successful, the routine returns zero, otherwise * non-zero. * * REFERENCES * * R. G. Tantzen, Algorithm 199: conversions between calendar date and * Julian day number, Communications of the ACM, vol. 6, no. 8, p. 444, * Aug. 1963. */ int jdate(int j, int *_d, int *_m, int *_y) { int d, m, y, ret = 0; if (!(1721426 <= j && j <= 3182395)) { ret = 1; goto done; } j -= 1721119; y = (4 * j - 1) / 146097; j = (4 * j - 1) % 146097; d = j / 4; j = (4 * d + 3) / 1461; d = (4 * d + 3) % 1461; d = (d + 4) / 4; m = (5 * d - 3) / 153; d = (5 * d - 3) % 153; d = (d + 5) / 5; y = 100 * y + j; if (m <= 9) m += 3; else m -= 9, y++; if (_d != NULL) *_d = d; if (_m != NULL) *_m = m; if (_y != NULL) *_y = y; done: return ret; } #if 0 int main(void) { int jbeg, jend, j, d, m, y; jbeg = jday(1, 1, 1); jend = jday(31, 12, 4000); for (j = jbeg; j <= jend; j++) { xassert(jdate(j, &d, &m, &y) == 0); xassert(jday(d, m, y) == j); } xprintf("Routines jday and jdate work correctly.\n"); return 0; } #endif /* eof */ sources_5316/external/glpk/glpapi07.c0000644000176700017670000003504211401660400016265 0ustar paulpaul/* glpapi07.c (exact simplex solver) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" #include "glpssx.h" /*********************************************************************** * NAME * * glp_exact - solve LP problem in exact arithmetic * * SYNOPSIS * * int glp_exact(glp_prob *lp, const glp_smcp *parm); * * DESCRIPTION * * The routine glp_exact is a tentative implementation of the primal * two-phase simplex method based on exact (rational) arithmetic. It is * similar to the routine glp_simplex, however, for all internal * computations it uses arithmetic of rational numbers, which is exact * in mathematical sense, i.e. free of round-off errors unlike floating * point arithmetic. * * Note that the routine glp_exact uses inly two control parameters * passed in the structure glp_smcp, namely, it_lim and tm_lim. * * RETURNS * * 0 The LP problem instance has been successfully solved. This code * does not necessarily mean that the solver has found optimal * solution. It only means that the solution process was successful. * * GLP_EBADB * Unable to start the search, because the initial basis specified * in the problem object is invalid--the number of basic (auxiliary * and structural) variables is not the same as the number of rows in * the problem object. * * GLP_ESING * Unable to start the search, because the basis matrix correspodning * to the initial basis is exactly singular. * * GLP_EBOUND * Unable to start the search, because some double-bounded variables * have incorrect bounds. * * GLP_EFAIL * The problem has no rows/columns. * * GLP_EITLIM * The search was prematurely terminated, because the simplex * iteration limit has been exceeded. * * GLP_ETMLIM * The search was prematurely terminated, because the time limit has * been exceeded. */ static void set_d_eps(mpq_t x, double val) { /* convert double val to rational x obtaining a more adequate fraction than provided by mpq_set_d due to allowing a small approximation error specified by a given relative tolerance; for example, mpq_set_d would give the following 1/3 ~= 0.333333333333333314829616256247391... -> -> 6004799503160661/18014398509481984 while this routine gives exactly 1/3 */ int s, n, j; double f, p, q, eps = 1e-9; mpq_t temp; xassert(-DBL_MAX <= val && val <= +DBL_MAX); #if 1 /* 30/VII-2008 */ if (val == floor(val)) { /* if val is integral, do not approximate */ mpq_set_d(x, val); goto done; } #endif if (val > 0.0) s = +1; else if (val < 0.0) s = -1; else { mpq_set_si(x, 0, 1); goto done; } f = frexp(fabs(val), &n); /* |val| = f * 2^n, where 0.5 <= f < 1.0 */ fp2rat(f, 0.1 * eps, &p, &q); /* f ~= p / q, where p and q are integers */ mpq_init(temp); mpq_set_d(x, p); mpq_set_d(temp, q); mpq_div(x, x, temp); mpq_set_si(temp, 1, 1); for (j = 1; j <= abs(n); j++) mpq_add(temp, temp, temp); if (n > 0) mpq_mul(x, x, temp); else if (n < 0) mpq_div(x, x, temp); mpq_clear(temp); if (s < 0) mpq_neg(x, x); /* check that the desired tolerance has been attained */ xassert(fabs(val - mpq_get_d(x)) <= eps * (1.0 + fabs(val))); done: return; } static void load_data(SSX *ssx, LPX *lp) { /* load LP problem data into simplex solver workspace */ int m = ssx->m; int n = ssx->n; int nnz = ssx->A_ptr[n+1]-1; int j, k, type, loc, len, *ind; double lb, ub, coef, *val; xassert(lpx_get_num_rows(lp) == m); xassert(lpx_get_num_cols(lp) == n); xassert(lpx_get_num_nz(lp) == nnz); /* types and bounds of rows and columns */ for (k = 1; k <= m+n; k++) { if (k <= m) { type = lpx_get_row_type(lp, k); lb = lpx_get_row_lb(lp, k); ub = lpx_get_row_ub(lp, k); } else { type = lpx_get_col_type(lp, k-m); lb = lpx_get_col_lb(lp, k-m); ub = lpx_get_col_ub(lp, k-m); } switch (type) { case LPX_FR: type = SSX_FR; break; case LPX_LO: type = SSX_LO; break; case LPX_UP: type = SSX_UP; break; case LPX_DB: type = SSX_DB; break; case LPX_FX: type = SSX_FX; break; default: xassert(type != type); } ssx->type[k] = type; set_d_eps(ssx->lb[k], lb); set_d_eps(ssx->ub[k], ub); } /* optimization direction */ switch (lpx_get_obj_dir(lp)) { case LPX_MIN: ssx->dir = SSX_MIN; break; case LPX_MAX: ssx->dir = SSX_MAX; break; default: xassert(lp != lp); } /* objective coefficients */ for (k = 0; k <= m+n; k++) { if (k == 0) coef = lpx_get_obj_coef(lp, 0); else if (k <= m) coef = 0.0; else coef = lpx_get_obj_coef(lp, k-m); set_d_eps(ssx->coef[k], coef); } /* constraint coefficients */ ind = xcalloc(1+m, sizeof(int)); val = xcalloc(1+m, sizeof(double)); loc = 0; for (j = 1; j <= n; j++) { ssx->A_ptr[j] = loc+1; len = lpx_get_mat_col(lp, j, ind, val); for (k = 1; k <= len; k++) { loc++; ssx->A_ind[loc] = ind[k]; set_d_eps(ssx->A_val[loc], val[k]); } } xassert(loc == nnz); xfree(ind); xfree(val); return; } static int load_basis(SSX *ssx, LPX *lp) { /* load current LP basis into simplex solver workspace */ int m = ssx->m; int n = ssx->n; int *type = ssx->type; int *stat = ssx->stat; int *Q_row = ssx->Q_row; int *Q_col = ssx->Q_col; int i, j, k; xassert(lpx_get_num_rows(lp) == m); xassert(lpx_get_num_cols(lp) == n); /* statuses of rows and columns */ for (k = 1; k <= m+n; k++) { if (k <= m) stat[k] = lpx_get_row_stat(lp, k); else stat[k] = lpx_get_col_stat(lp, k-m); switch (stat[k]) { case LPX_BS: stat[k] = SSX_BS; break; case LPX_NL: stat[k] = SSX_NL; xassert(type[k] == SSX_LO || type[k] == SSX_DB); break; case LPX_NU: stat[k] = SSX_NU; xassert(type[k] == SSX_UP || type[k] == SSX_DB); break; case LPX_NF: stat[k] = SSX_NF; xassert(type[k] == SSX_FR); break; case LPX_NS: stat[k] = SSX_NS; xassert(type[k] == SSX_FX); break; default: xassert(stat != stat); } } /* build permutation matix Q */ i = j = 0; for (k = 1; k <= m+n; k++) { if (stat[k] == SSX_BS) { i++; if (i > m) return 1; Q_row[k] = i, Q_col[i] = k; } else { j++; if (j > n) return 1; Q_row[k] = m+j, Q_col[m+j] = k; } } xassert(i == m && j == n); return 0; } int glp_exact(glp_prob *lp, const glp_smcp *parm) { glp_smcp _parm; SSX *ssx; int m = lpx_get_num_rows(lp); int n = lpx_get_num_cols(lp); int nnz = lpx_get_num_nz(lp); int i, j, k, type, pst, dst, ret, *stat; double lb, ub, *prim, *dual, sum; if (parm == NULL) parm = &_parm, glp_init_smcp((glp_smcp *)parm); /* check control parameters */ if (parm->it_lim < 0) xerror("glp_exact: it_lim = %d; invalid parameter\n", parm->it_lim); if (parm->tm_lim < 0) xerror("glp_exact: tm_lim = %d; invalid parameter\n", parm->tm_lim); /* the problem must have at least one row and one column */ if (!(m > 0 && n > 0)) { xprintf("glp_exact: problem has no rows/columns\n"); return GLP_EFAIL; } #if 1 /* basic solution is currently undefined */ lp->pbs_stat = lp->dbs_stat = GLP_UNDEF; lp->obj_val = 0.0; lp->some = 0; #endif /* check that all double-bounded variables have correct bounds */ for (k = 1; k <= m+n; k++) { if (k <= m) { type = lpx_get_row_type(lp, k); lb = lpx_get_row_lb(lp, k); ub = lpx_get_row_ub(lp, k); } else { type = lpx_get_col_type(lp, k-m); lb = lpx_get_col_lb(lp, k-m); ub = lpx_get_col_ub(lp, k-m); } if (type == LPX_DB && lb >= ub) { xprintf("glp_exact: %s %d has invalid bounds\n", k <= m ? "row" : "column", k <= m ? k : k-m); return GLP_EBOUND; } } /* create the simplex solver workspace */ xprintf("glp_exact: %d rows, %d columns, %d non-zeros\n", m, n, nnz); #ifdef HAVE_GMP xprintf("GNU MP bignum library is being used\n"); #else xprintf("GLPK bignum module is being used\n"); xprintf("(Consider installing GNU MP to attain a much better perf" "ormance.)\n"); #endif ssx = ssx_create(m, n, nnz); /* load LP problem data into the workspace */ load_data(ssx, lp); /* load current LP basis into the workspace */ if (load_basis(ssx, lp)) { xprintf("glp_exact: initial LP basis is invalid\n"); ret = GLP_EBADB; goto done; } /* inherit some control parameters from the LP object */ #if 0 ssx->it_lim = lpx_get_int_parm(lp, LPX_K_ITLIM); ssx->it_cnt = lpx_get_int_parm(lp, LPX_K_ITCNT); ssx->tm_lim = lpx_get_real_parm(lp, LPX_K_TMLIM); #else ssx->it_lim = parm->it_lim; ssx->it_cnt = lp->it_cnt; ssx->tm_lim = (double)parm->tm_lim / 1000.0; #endif ssx->out_frq = 5.0; ssx->tm_beg = xtime(); ssx->tm_lag = xlset(0); /* solve LP */ ret = ssx_driver(ssx); /* copy back some statistics to the LP object */ #if 0 lpx_set_int_parm(lp, LPX_K_ITLIM, ssx->it_lim); lpx_set_int_parm(lp, LPX_K_ITCNT, ssx->it_cnt); lpx_set_real_parm(lp, LPX_K_TMLIM, ssx->tm_lim); #else lp->it_cnt = ssx->it_cnt; #endif /* analyze the return code */ switch (ret) { case 0: /* optimal solution found */ ret = 0; pst = LPX_P_FEAS, dst = LPX_D_FEAS; break; case 1: /* problem has no feasible solution */ ret = 0; pst = LPX_P_NOFEAS, dst = LPX_D_INFEAS; break; case 2: /* problem has unbounded solution */ ret = 0; pst = LPX_P_FEAS, dst = LPX_D_NOFEAS; #if 1 xassert(1 <= ssx->q && ssx->q <= n); lp->some = ssx->Q_col[m + ssx->q]; xassert(1 <= lp->some && lp->some <= m+n); #endif break; case 3: /* iteration limit exceeded (phase I) */ ret = GLP_EITLIM; pst = LPX_P_INFEAS, dst = LPX_D_INFEAS; break; case 4: /* iteration limit exceeded (phase II) */ ret = GLP_EITLIM; pst = LPX_P_FEAS, dst = LPX_D_INFEAS; break; case 5: /* time limit exceeded (phase I) */ ret = GLP_ETMLIM; pst = LPX_P_INFEAS, dst = LPX_D_INFEAS; break; case 6: /* time limit exceeded (phase II) */ ret = GLP_ETMLIM; pst = LPX_P_FEAS, dst = LPX_D_INFEAS; break; case 7: /* initial basis matrix is singular */ ret = GLP_ESING; goto done; default: xassert(ret != ret); } /* obtain final basic solution components */ stat = xcalloc(1+m+n, sizeof(int)); prim = xcalloc(1+m+n, sizeof(double)); dual = xcalloc(1+m+n, sizeof(double)); for (k = 1; k <= m+n; k++) { if (ssx->stat[k] == SSX_BS) { i = ssx->Q_row[k]; /* x[k] = xB[i] */ xassert(1 <= i && i <= m); stat[k] = LPX_BS; prim[k] = mpq_get_d(ssx->bbar[i]); dual[k] = 0.0; } else { j = ssx->Q_row[k] - m; /* x[k] = xN[j] */ xassert(1 <= j && j <= n); switch (ssx->stat[k]) { case SSX_NF: stat[k] = LPX_NF; prim[k] = 0.0; break; case SSX_NL: stat[k] = LPX_NL; prim[k] = mpq_get_d(ssx->lb[k]); break; case SSX_NU: stat[k] = LPX_NU; prim[k] = mpq_get_d(ssx->ub[k]); break; case SSX_NS: stat[k] = LPX_NS; prim[k] = mpq_get_d(ssx->lb[k]); break; default: xassert(ssx != ssx); } dual[k] = mpq_get_d(ssx->cbar[j]); } } /* and store them into the LP object */ pst = pst - LPX_P_UNDEF + GLP_UNDEF; dst = dst - LPX_D_UNDEF + GLP_UNDEF; for (k = 1; k <= m+n; k++) stat[k] = stat[k] - LPX_BS + GLP_BS; sum = lpx_get_obj_coef(lp, 0); for (j = 1; j <= n; j++) sum += lpx_get_obj_coef(lp, j) * prim[m+j]; lpx_put_solution(lp, 1, &pst, &dst, &sum, &stat[0], &prim[0], &dual[0], &stat[m], &prim[m], &dual[m]); xfree(stat); xfree(prim); xfree(dual); done: /* delete the simplex solver workspace */ ssx_delete(ssx); /* return to the application program */ return ret; } /* eof */ sources_5316/external/glpk/glprgr.h0000644000176700017670000000244511401660400016145 0ustar paulpaul/* glprgr.h (raster graphics) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPRGR_H #define GLPRGR_H #define rgr_write_bmp16 _glp_rgr_write_bmp16 int rgr_write_bmp16(const char *fname, int m, int n, const char map[]); /* write 16-color raster image in BMP file format */ #endif /* eof */ sources_5316/external/glpk/glpssx01.c0000644000176700017670000006615411401660400016333 0ustar paulpaul/* glpssx01.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glpssx.h" #define xfault xerror /*---------------------------------------------------------------------- // ssx_create - create simplex solver workspace. // // This routine creates the workspace used by simplex solver routines, // and returns a pointer to it. // // Parameters m, n, and nnz specify, respectively, the number of rows, // columns, and non-zero constraint coefficients. // // This routine only allocates the memory for the workspace components, // so the workspace needs to be saturated by data. */ SSX *ssx_create(int m, int n, int nnz) { SSX *ssx; int i, j, k; if (m < 1) xfault("ssx_create: m = %d; invalid number of rows\n", m); if (n < 1) xfault("ssx_create: n = %d; invalid number of columns\n", n); if (nnz < 0) xfault("ssx_create: nnz = %d; invalid number of non-zero const" "raint coefficients\n", nnz); ssx = xmalloc(sizeof(SSX)); ssx->m = m; ssx->n = n; ssx->type = xcalloc(1+m+n, sizeof(int)); ssx->lb = xcalloc(1+m+n, sizeof(mpq_t)); for (k = 1; k <= m+n; k++) mpq_init(ssx->lb[k]); ssx->ub = xcalloc(1+m+n, sizeof(mpq_t)); for (k = 1; k <= m+n; k++) mpq_init(ssx->ub[k]); ssx->coef = xcalloc(1+m+n, sizeof(mpq_t)); for (k = 0; k <= m+n; k++) mpq_init(ssx->coef[k]); ssx->A_ptr = xcalloc(1+n+1, sizeof(int)); ssx->A_ptr[n+1] = nnz+1; ssx->A_ind = xcalloc(1+nnz, sizeof(int)); ssx->A_val = xcalloc(1+nnz, sizeof(mpq_t)); for (k = 1; k <= nnz; k++) mpq_init(ssx->A_val[k]); ssx->stat = xcalloc(1+m+n, sizeof(int)); ssx->Q_row = xcalloc(1+m+n, sizeof(int)); ssx->Q_col = xcalloc(1+m+n, sizeof(int)); ssx->binv = bfx_create_binv(); ssx->bbar = xcalloc(1+m, sizeof(mpq_t)); for (i = 0; i <= m; i++) mpq_init(ssx->bbar[i]); ssx->pi = xcalloc(1+m, sizeof(mpq_t)); for (i = 1; i <= m; i++) mpq_init(ssx->pi[i]); ssx->cbar = xcalloc(1+n, sizeof(mpq_t)); for (j = 1; j <= n; j++) mpq_init(ssx->cbar[j]); ssx->rho = xcalloc(1+m, sizeof(mpq_t)); for (i = 1; i <= m; i++) mpq_init(ssx->rho[i]); ssx->ap = xcalloc(1+n, sizeof(mpq_t)); for (j = 1; j <= n; j++) mpq_init(ssx->ap[j]); ssx->aq = xcalloc(1+m, sizeof(mpq_t)); for (i = 1; i <= m; i++) mpq_init(ssx->aq[i]); mpq_init(ssx->delta); return ssx; } /*---------------------------------------------------------------------- // ssx_factorize - factorize the current basis matrix. // // This routine computes factorization of the current basis matrix B // and returns the singularity flag. If the matrix B is non-singular, // the flag is zero, otherwise non-zero. */ static int basis_col(void *info, int j, int ind[], mpq_t val[]) { /* this auxiliary routine provides row indices and numeric values of non-zero elements in j-th column of the matrix B */ SSX *ssx = info; int m = ssx->m; int n = ssx->n; int *A_ptr = ssx->A_ptr; int *A_ind = ssx->A_ind; mpq_t *A_val = ssx->A_val; int *Q_col = ssx->Q_col; int k, len, ptr; xassert(1 <= j && j <= m); k = Q_col[j]; /* x[k] = xB[j] */ xassert(1 <= k && k <= m+n); /* j-th column of the matrix B is k-th column of the augmented constraint matrix (I | -A) */ if (k <= m) { /* it is a column of the unity matrix I */ len = 1, ind[1] = k, mpq_set_si(val[1], 1, 1); } else { /* it is a column of the original constraint matrix -A */ len = 0; for (ptr = A_ptr[k-m]; ptr < A_ptr[k-m+1]; ptr++) { len++; ind[len] = A_ind[ptr]; mpq_neg(val[len], A_val[ptr]); } } return len; } int ssx_factorize(SSX *ssx) { int ret; ret = bfx_factorize(ssx->binv, ssx->m, basis_col, ssx); return ret; } /*---------------------------------------------------------------------- // ssx_get_xNj - determine value of non-basic variable. // // This routine determines the value of non-basic variable xN[j] in the // current basic solution defined as follows: // // 0, if xN[j] is free variable // lN[j], if xN[j] is on its lower bound // uN[j], if xN[j] is on its upper bound // lN[j] = uN[j], if xN[j] is fixed variable // // where lN[j] and uN[j] are lower and upper bounds of xN[j]. */ void ssx_get_xNj(SSX *ssx, int j, mpq_t x) { int m = ssx->m; int n = ssx->n; mpq_t *lb = ssx->lb; mpq_t *ub = ssx->ub; int *stat = ssx->stat; int *Q_col = ssx->Q_col; int k; xassert(1 <= j && j <= n); k = Q_col[m+j]; /* x[k] = xN[j] */ xassert(1 <= k && k <= m+n); switch (stat[k]) { case SSX_NL: /* xN[j] is on its lower bound */ mpq_set(x, lb[k]); break; case SSX_NU: /* xN[j] is on its upper bound */ mpq_set(x, ub[k]); break; case SSX_NF: /* xN[j] is free variable */ mpq_set_si(x, 0, 1); break; case SSX_NS: /* xN[j] is fixed variable */ mpq_set(x, lb[k]); break; default: xassert(stat != stat); } return; } /*---------------------------------------------------------------------- // ssx_eval_bbar - compute values of basic variables. // // This routine computes values of basic variables xB in the current // basic solution as follows: // // beta = - inv(B) * N * xN, // // where B is the basis matrix, N is the matrix of non-basic columns, // xN is a vector of current values of non-basic variables. */ void ssx_eval_bbar(SSX *ssx) { int m = ssx->m; int n = ssx->n; mpq_t *coef = ssx->coef; int *A_ptr = ssx->A_ptr; int *A_ind = ssx->A_ind; mpq_t *A_val = ssx->A_val; int *Q_col = ssx->Q_col; mpq_t *bbar = ssx->bbar; int i, j, k, ptr; mpq_t x, temp; mpq_init(x); mpq_init(temp); /* bbar := 0 */ for (i = 1; i <= m; i++) mpq_set_si(bbar[i], 0, 1); /* bbar := - N * xN = - N[1] * xN[1] - ... - N[n] * xN[n] */ for (j = 1; j <= n; j++) { ssx_get_xNj(ssx, j, x); if (mpq_sgn(x) == 0) continue; k = Q_col[m+j]; /* x[k] = xN[j] */ if (k <= m) { /* N[j] is a column of the unity matrix I */ mpq_sub(bbar[k], bbar[k], x); } else { /* N[j] is a column of the original constraint matrix -A */ for (ptr = A_ptr[k-m]; ptr < A_ptr[k-m+1]; ptr++) { mpq_mul(temp, A_val[ptr], x); mpq_add(bbar[A_ind[ptr]], bbar[A_ind[ptr]], temp); } } } /* bbar := inv(B) * bbar */ bfx_ftran(ssx->binv, bbar, 0); #if 1 /* compute value of the objective function */ /* bbar[0] := c[0] */ mpq_set(bbar[0], coef[0]); /* bbar[0] := bbar[0] + sum{i in B} cB[i] * xB[i] */ for (i = 1; i <= m; i++) { k = Q_col[i]; /* x[k] = xB[i] */ if (mpq_sgn(coef[k]) == 0) continue; mpq_mul(temp, coef[k], bbar[i]); mpq_add(bbar[0], bbar[0], temp); } /* bbar[0] := bbar[0] + sum{j in N} cN[j] * xN[j] */ for (j = 1; j <= n; j++) { k = Q_col[m+j]; /* x[k] = xN[j] */ if (mpq_sgn(coef[k]) == 0) continue; ssx_get_xNj(ssx, j, x); mpq_mul(temp, coef[k], x); mpq_add(bbar[0], bbar[0], temp); } #endif mpq_clear(x); mpq_clear(temp); return; } /*---------------------------------------------------------------------- // ssx_eval_pi - compute values of simplex multipliers. // // This routine computes values of simplex multipliers (shadow prices) // pi in the current basic solution as follows: // // pi = inv(B') * cB, // // where B' is a matrix transposed to the basis matrix B, cB is a vector // of objective coefficients at basic variables xB. */ void ssx_eval_pi(SSX *ssx) { int m = ssx->m; mpq_t *coef = ssx->coef; int *Q_col = ssx->Q_col; mpq_t *pi = ssx->pi; int i; /* pi := cB */ for (i = 1; i <= m; i++) mpq_set(pi[i], coef[Q_col[i]]); /* pi := inv(B') * cB */ bfx_btran(ssx->binv, pi); return; } /*---------------------------------------------------------------------- // ssx_eval_dj - compute reduced cost of non-basic variable. // // This routine computes reduced cost d[j] of non-basic variable xN[j] // in the current basic solution as follows: // // d[j] = cN[j] - N[j] * pi, // // where cN[j] is an objective coefficient at xN[j], N[j] is a column // of the augmented constraint matrix (I | -A) corresponding to xN[j], // pi is the vector of simplex multipliers (shadow prices). */ void ssx_eval_dj(SSX *ssx, int j, mpq_t dj) { int m = ssx->m; int n = ssx->n; mpq_t *coef = ssx->coef; int *A_ptr = ssx->A_ptr; int *A_ind = ssx->A_ind; mpq_t *A_val = ssx->A_val; int *Q_col = ssx->Q_col; mpq_t *pi = ssx->pi; int k, ptr, end; mpq_t temp; mpq_init(temp); xassert(1 <= j && j <= n); k = Q_col[m+j]; /* x[k] = xN[j] */ xassert(1 <= k && k <= m+n); /* j-th column of the matrix N is k-th column of the augmented constraint matrix (I | -A) */ if (k <= m) { /* it is a column of the unity matrix I */ mpq_sub(dj, coef[k], pi[k]); } else { /* it is a column of the original constraint matrix -A */ mpq_set(dj, coef[k]); for (ptr = A_ptr[k-m], end = A_ptr[k-m+1]; ptr < end; ptr++) { mpq_mul(temp, A_val[ptr], pi[A_ind[ptr]]); mpq_add(dj, dj, temp); } } mpq_clear(temp); return; } /*---------------------------------------------------------------------- // ssx_eval_cbar - compute reduced costs of all non-basic variables. // // This routine computes the vector of reduced costs pi in the current // basic solution for all non-basic variables, including fixed ones. */ void ssx_eval_cbar(SSX *ssx) { int n = ssx->n; mpq_t *cbar = ssx->cbar; int j; for (j = 1; j <= n; j++) ssx_eval_dj(ssx, j, cbar[j]); return; } /*---------------------------------------------------------------------- // ssx_eval_rho - compute p-th row of the inverse. // // This routine computes p-th row of the matrix inv(B), where B is the // current basis matrix. // // p-th row of the inverse is computed using the following formula: // // rho = inv(B') * e[p], // // where B' is a matrix transposed to B, e[p] is a unity vector, which // contains one in p-th position. */ void ssx_eval_rho(SSX *ssx) { int m = ssx->m; int p = ssx->p; mpq_t *rho = ssx->rho; int i; xassert(1 <= p && p <= m); /* rho := 0 */ for (i = 1; i <= m; i++) mpq_set_si(rho[i], 0, 1); /* rho := e[p] */ mpq_set_si(rho[p], 1, 1); /* rho := inv(B') * rho */ bfx_btran(ssx->binv, rho); return; } /*---------------------------------------------------------------------- // ssx_eval_row - compute pivot row of the simplex table. // // This routine computes p-th (pivot) row of the current simplex table // A~ = - inv(B) * N using the following formula: // // A~[p] = - N' * inv(B') * e[p] = - N' * rho[p], // // where N' is a matrix transposed to the matrix N, rho[p] is p-th row // of the inverse inv(B). */ void ssx_eval_row(SSX *ssx) { int m = ssx->m; int n = ssx->n; int *A_ptr = ssx->A_ptr; int *A_ind = ssx->A_ind; mpq_t *A_val = ssx->A_val; int *Q_col = ssx->Q_col; mpq_t *rho = ssx->rho; mpq_t *ap = ssx->ap; int j, k, ptr; mpq_t temp; mpq_init(temp); for (j = 1; j <= n; j++) { /* ap[j] := - N'[j] * rho (inner product) */ k = Q_col[m+j]; /* x[k] = xN[j] */ if (k <= m) mpq_neg(ap[j], rho[k]); else { mpq_set_si(ap[j], 0, 1); for (ptr = A_ptr[k-m]; ptr < A_ptr[k-m+1]; ptr++) { mpq_mul(temp, A_val[ptr], rho[A_ind[ptr]]); mpq_add(ap[j], ap[j], temp); } } } mpq_clear(temp); return; } /*---------------------------------------------------------------------- // ssx_eval_col - compute pivot column of the simplex table. // // This routine computes q-th (pivot) column of the current simplex // table A~ = - inv(B) * N using the following formula: // // A~[q] = - inv(B) * N[q], // // where N[q] is q-th column of the matrix N corresponding to chosen // non-basic variable xN[q]. */ void ssx_eval_col(SSX *ssx) { int m = ssx->m; int n = ssx->n; int *A_ptr = ssx->A_ptr; int *A_ind = ssx->A_ind; mpq_t *A_val = ssx->A_val; int *Q_col = ssx->Q_col; int q = ssx->q; mpq_t *aq = ssx->aq; int i, k, ptr; xassert(1 <= q && q <= n); /* aq := 0 */ for (i = 1; i <= m; i++) mpq_set_si(aq[i], 0, 1); /* aq := N[q] */ k = Q_col[m+q]; /* x[k] = xN[q] */ if (k <= m) { /* N[q] is a column of the unity matrix I */ mpq_set_si(aq[k], 1, 1); } else { /* N[q] is a column of the original constraint matrix -A */ for (ptr = A_ptr[k-m]; ptr < A_ptr[k-m+1]; ptr++) mpq_neg(aq[A_ind[ptr]], A_val[ptr]); } /* aq := inv(B) * aq */ bfx_ftran(ssx->binv, aq, 1); /* aq := - aq */ for (i = 1; i <= m; i++) mpq_neg(aq[i], aq[i]); return; } /*---------------------------------------------------------------------- // ssx_chuzc - choose pivot column. // // This routine chooses non-basic variable xN[q] whose reduced cost // indicates possible improving of the objective function to enter it // in the basis. // // Currently the standard (textbook) pricing is used, i.e. that // non-basic variable is preferred which has greatest reduced cost (in // magnitude). // // If xN[q] has been chosen, the routine stores its number q and also // sets the flag q_dir that indicates direction in which xN[q] has to // change (+1 means increasing, -1 means decreasing). // // If the choice cannot be made, because the current basic solution is // dual feasible, the routine sets the number q to 0. */ void ssx_chuzc(SSX *ssx) { int m = ssx->m; int n = ssx->n; int dir = (ssx->dir == SSX_MIN ? +1 : -1); int *Q_col = ssx->Q_col; int *stat = ssx->stat; mpq_t *cbar = ssx->cbar; int j, k, s, q, q_dir; double best, temp; /* nothing is chosen so far */ q = 0, q_dir = 0, best = 0.0; /* look through the list of non-basic variables */ for (j = 1; j <= n; j++) { k = Q_col[m+j]; /* x[k] = xN[j] */ s = dir * mpq_sgn(cbar[j]); if ((stat[k] == SSX_NF || stat[k] == SSX_NL) && s < 0 || (stat[k] == SSX_NF || stat[k] == SSX_NU) && s > 0) { /* reduced cost of xN[j] indicates possible improving of the objective function */ temp = fabs(mpq_get_d(cbar[j])); xassert(temp != 0.0); if (q == 0 || best < temp) q = j, q_dir = - s, best = temp; } } ssx->q = q, ssx->q_dir = q_dir; return; } /*---------------------------------------------------------------------- // ssx_chuzr - choose pivot row. // // This routine looks through elements of q-th column of the simplex // table and chooses basic variable xB[p] which should leave the basis. // // The choice is based on the standard (textbook) ratio test. // // If xB[p] has been chosen, the routine stores its number p and also // sets its non-basic status p_stat which should be assigned to xB[p] // when it has left the basis and become xN[q]. // // Special case p < 0 means that xN[q] is double-bounded variable and // it reaches its opposite bound before any basic variable does that, // so the current basis remains unchanged. // // If the choice cannot be made, because xN[q] can infinitely change in // the feasible direction, the routine sets the number p to 0. */ void ssx_chuzr(SSX *ssx) { int m = ssx->m; int n = ssx->n; int *type = ssx->type; mpq_t *lb = ssx->lb; mpq_t *ub = ssx->ub; int *Q_col = ssx->Q_col; mpq_t *bbar = ssx->bbar; int q = ssx->q; mpq_t *aq = ssx->aq; int q_dir = ssx->q_dir; int i, k, s, t, p, p_stat; mpq_t teta, temp; mpq_init(teta); mpq_init(temp); xassert(1 <= q && q <= n); xassert(q_dir == +1 || q_dir == -1); /* nothing is chosen so far */ p = 0, p_stat = 0; /* look through the list of basic variables */ for (i = 1; i <= m; i++) { s = q_dir * mpq_sgn(aq[i]); if (s < 0) { /* xB[i] decreases */ k = Q_col[i]; /* x[k] = xB[i] */ t = type[k]; if (t == SSX_LO || t == SSX_DB || t == SSX_FX) { /* xB[i] has finite lower bound */ mpq_sub(temp, bbar[i], lb[k]); mpq_div(temp, temp, aq[i]); mpq_abs(temp, temp); if (p == 0 || mpq_cmp(teta, temp) > 0) { p = i; p_stat = (t == SSX_FX ? SSX_NS : SSX_NL); mpq_set(teta, temp); } } } else if (s > 0) { /* xB[i] increases */ k = Q_col[i]; /* x[k] = xB[i] */ t = type[k]; if (t == SSX_UP || t == SSX_DB || t == SSX_FX) { /* xB[i] has finite upper bound */ mpq_sub(temp, bbar[i], ub[k]); mpq_div(temp, temp, aq[i]); mpq_abs(temp, temp); if (p == 0 || mpq_cmp(teta, temp) > 0) { p = i; p_stat = (t == SSX_FX ? SSX_NS : SSX_NU); mpq_set(teta, temp); } } } /* if something has been chosen and the ratio test indicates exact degeneracy, the search can be finished */ if (p != 0 && mpq_sgn(teta) == 0) break; } /* if xN[q] is double-bounded, check if it can reach its opposite bound before any basic variable */ k = Q_col[m+q]; /* x[k] = xN[q] */ if (type[k] == SSX_DB) { mpq_sub(temp, ub[k], lb[k]); if (p == 0 || mpq_cmp(teta, temp) > 0) { p = -1; p_stat = -1; mpq_set(teta, temp); } } ssx->p = p; ssx->p_stat = p_stat; /* if xB[p] has been chosen, determine its actual change in the adjacent basis (it has the same sign as q_dir) */ if (p != 0) { xassert(mpq_sgn(teta) >= 0); if (q_dir > 0) mpq_set(ssx->delta, teta); else mpq_neg(ssx->delta, teta); } mpq_clear(teta); mpq_clear(temp); return; } /*---------------------------------------------------------------------- // ssx_update_bbar - update values of basic variables. // // This routine recomputes the current values of basic variables for // the adjacent basis. // // The simplex table for the current basis is the following: // // xB[i] = sum{j in 1..n} alfa[i,j] * xN[q], i = 1,...,m // // therefore // // delta xB[i] = alfa[i,q] * delta xN[q], i = 1,...,m // // where delta xN[q] = xN.new[q] - xN[q] is the change of xN[q] in the // adjacent basis, and delta xB[i] = xB.new[i] - xB[i] is the change of // xB[i]. This gives formulae for recomputing values of xB[i]: // // xB.new[p] = xN[q] + delta xN[q] // // (because xN[q] becomes xB[p] in the adjacent basis), and // // xB.new[i] = xB[i] + alfa[i,q] * delta xN[q], i != p // // for other basic variables. */ void ssx_update_bbar(SSX *ssx) { int m = ssx->m; int n = ssx->n; mpq_t *bbar = ssx->bbar; mpq_t *cbar = ssx->cbar; int p = ssx->p; int q = ssx->q; mpq_t *aq = ssx->aq; int i; mpq_t temp; mpq_init(temp); xassert(1 <= q && q <= n); if (p < 0) { /* xN[q] is double-bounded and goes to its opposite bound */ /* nop */; } else { /* xN[q] becomes xB[p] in the adjacent basis */ /* xB.new[p] = xN[q] + delta xN[q] */ xassert(1 <= p && p <= m); ssx_get_xNj(ssx, q, temp); mpq_add(bbar[p], temp, ssx->delta); } /* update values of other basic variables depending on xN[q] */ for (i = 1; i <= m; i++) { if (i == p) continue; /* xB.new[i] = xB[i] + alfa[i,q] * delta xN[q] */ if (mpq_sgn(aq[i]) == 0) continue; mpq_mul(temp, aq[i], ssx->delta); mpq_add(bbar[i], bbar[i], temp); } #if 1 /* update value of the objective function */ /* z.new = z + d[q] * delta xN[q] */ mpq_mul(temp, cbar[q], ssx->delta); mpq_add(bbar[0], bbar[0], temp); #endif mpq_clear(temp); return; } /*---------------------------------------------------------------------- -- ssx_update_pi - update simplex multipliers. -- -- This routine recomputes the vector of simplex multipliers for the -- adjacent basis. */ void ssx_update_pi(SSX *ssx) { int m = ssx->m; int n = ssx->n; mpq_t *pi = ssx->pi; mpq_t *cbar = ssx->cbar; int p = ssx->p; int q = ssx->q; mpq_t *aq = ssx->aq; mpq_t *rho = ssx->rho; int i; mpq_t new_dq, temp; mpq_init(new_dq); mpq_init(temp); xassert(1 <= p && p <= m); xassert(1 <= q && q <= n); /* compute d[q] in the adjacent basis */ mpq_div(new_dq, cbar[q], aq[p]); /* update the vector of simplex multipliers */ for (i = 1; i <= m; i++) { if (mpq_sgn(rho[i]) == 0) continue; mpq_mul(temp, new_dq, rho[i]); mpq_sub(pi[i], pi[i], temp); } mpq_clear(new_dq); mpq_clear(temp); return; } /*---------------------------------------------------------------------- // ssx_update_cbar - update reduced costs of non-basic variables. // // This routine recomputes the vector of reduced costs of non-basic // variables for the adjacent basis. */ void ssx_update_cbar(SSX *ssx) { int m = ssx->m; int n = ssx->n; mpq_t *cbar = ssx->cbar; int p = ssx->p; int q = ssx->q; mpq_t *ap = ssx->ap; int j; mpq_t temp; mpq_init(temp); xassert(1 <= p && p <= m); xassert(1 <= q && q <= n); /* compute d[q] in the adjacent basis */ /* d.new[q] = d[q] / alfa[p,q] */ mpq_div(cbar[q], cbar[q], ap[q]); /* update reduced costs of other non-basic variables */ for (j = 1; j <= n; j++) { if (j == q) continue; /* d.new[j] = d[j] - (alfa[p,j] / alfa[p,q]) * d[q] */ if (mpq_sgn(ap[j]) == 0) continue; mpq_mul(temp, ap[j], cbar[q]); mpq_sub(cbar[j], cbar[j], temp); } mpq_clear(temp); return; } /*---------------------------------------------------------------------- // ssx_change_basis - change current basis to adjacent one. // // This routine changes the current basis to the adjacent one swapping // basic variable xB[p] and non-basic variable xN[q]. */ void ssx_change_basis(SSX *ssx) { int m = ssx->m; int n = ssx->n; int *type = ssx->type; int *stat = ssx->stat; int *Q_row = ssx->Q_row; int *Q_col = ssx->Q_col; int p = ssx->p; int q = ssx->q; int p_stat = ssx->p_stat; int k, kp, kq; if (p < 0) { /* special case: xN[q] goes to its opposite bound */ xassert(1 <= q && q <= n); k = Q_col[m+q]; /* x[k] = xN[q] */ xassert(type[k] == SSX_DB); switch (stat[k]) { case SSX_NL: stat[k] = SSX_NU; break; case SSX_NU: stat[k] = SSX_NL; break; default: xassert(stat != stat); } } else { /* xB[p] leaves the basis, xN[q] enters the basis */ xassert(1 <= p && p <= m); xassert(1 <= q && q <= n); kp = Q_col[p]; /* x[kp] = xB[p] */ kq = Q_col[m+q]; /* x[kq] = xN[q] */ /* check non-basic status of xB[p] which becomes xN[q] */ switch (type[kp]) { case SSX_FR: xassert(p_stat == SSX_NF); break; case SSX_LO: xassert(p_stat == SSX_NL); break; case SSX_UP: xassert(p_stat == SSX_NU); break; case SSX_DB: xassert(p_stat == SSX_NL || p_stat == SSX_NU); break; case SSX_FX: xassert(p_stat == SSX_NS); break; default: xassert(type != type); } /* swap xB[p] and xN[q] */ stat[kp] = (char)p_stat, stat[kq] = SSX_BS; Q_row[kp] = m+q, Q_row[kq] = p; Q_col[p] = kq, Q_col[m+q] = kp; /* update factorization of the basis matrix */ if (bfx_update(ssx->binv, p)) { if (ssx_factorize(ssx)) xassert(("Internal error: basis matrix is singular", 0)); } } return; } /*---------------------------------------------------------------------- // ssx_delete - delete simplex solver workspace. // // This routine deletes the simplex solver workspace freeing all the // memory allocated to this object. */ void ssx_delete(SSX *ssx) { int m = ssx->m; int n = ssx->n; int nnz = ssx->A_ptr[n+1]-1; int i, j, k; xfree(ssx->type); for (k = 1; k <= m+n; k++) mpq_clear(ssx->lb[k]); xfree(ssx->lb); for (k = 1; k <= m+n; k++) mpq_clear(ssx->ub[k]); xfree(ssx->ub); for (k = 0; k <= m+n; k++) mpq_clear(ssx->coef[k]); xfree(ssx->coef); xfree(ssx->A_ptr); xfree(ssx->A_ind); for (k = 1; k <= nnz; k++) mpq_clear(ssx->A_val[k]); xfree(ssx->A_val); xfree(ssx->stat); xfree(ssx->Q_row); xfree(ssx->Q_col); bfx_delete_binv(ssx->binv); for (i = 0; i <= m; i++) mpq_clear(ssx->bbar[i]); xfree(ssx->bbar); for (i = 1; i <= m; i++) mpq_clear(ssx->pi[i]); xfree(ssx->pi); for (j = 1; j <= n; j++) mpq_clear(ssx->cbar[j]); xfree(ssx->cbar); for (i = 1; i <= m; i++) mpq_clear(ssx->rho[i]); xfree(ssx->rho); for (j = 1; j <= n; j++) mpq_clear(ssx->ap[j]); xfree(ssx->ap); for (i = 1; i <= m; i++) mpq_clear(ssx->aq[i]); xfree(ssx->aq); mpq_clear(ssx->delta); xfree(ssx); return; } /* eof */ sources_5316/external/glpk/glpapi16.c0000644000176700017670000002562111401660400016267 0ustar paulpaul/* glpapi16.c (graph and network analysis routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" #include "glpnet.h" /*********************************************************************** * NAME * * glp_weak_comp - find all weakly connected components of graph * * SYNOPSIS * * int glp_weak_comp(glp_graph *G, int v_num); * * DESCRIPTION * * The routine glp_weak_comp finds all weakly connected components of * the specified graph. * * The parameter v_num specifies an offset of the field of type int * in the vertex data block, to which the routine stores the number of * a (weakly) connected component containing that vertex. If v_num < 0, * no component numbers are stored. * * The components are numbered in arbitrary order from 1 to nc, where * nc is the total number of components found, 0 <= nc <= |V|. * * RETURNS * * The routine returns nc, the total number of components found. */ int glp_weak_comp(glp_graph *G, int v_num) { glp_vertex *v; glp_arc *a; int f, i, j, nc, nv, pos1, pos2, *prev, *next, *list; if (v_num >= 0 && v_num > G->v_size - (int)sizeof(int)) xerror("glp_weak_comp: v_num = %d; invalid offset\n", v_num); nv = G->nv; if (nv == 0) { nc = 0; goto done; } /* allocate working arrays */ prev = xcalloc(1+nv, sizeof(int)); next = xcalloc(1+nv, sizeof(int)); list = xcalloc(1+nv, sizeof(int)); /* if vertex i is unlabelled, prev[i] is the index of previous unlabelled vertex, and next[i] is the index of next unlabelled vertex; if vertex i is labelled, then prev[i] < 0, and next[i] is the connected component number */ /* initially all vertices are unlabelled */ f = 1; for (i = 1; i <= nv; i++) prev[i] = i - 1, next[i] = i + 1; next[nv] = 0; /* main loop (until all vertices have been labelled) */ nc = 0; while (f != 0) { /* take an unlabelled vertex */ i = f; /* and remove it from the list of unlabelled vertices */ f = next[i]; if (f != 0) prev[f] = 0; /* label the vertex; it begins a new component */ prev[i] = -1, next[i] = ++nc; /* breadth first search */ list[1] = i, pos1 = pos2 = 1; while (pos1 <= pos2) { /* dequeue vertex i */ i = list[pos1++]; /* consider all arcs incoming to vertex i */ for (a = G->v[i]->in; a != NULL; a = a->h_next) { /* vertex j is adjacent to vertex i */ j = a->tail->i; if (prev[j] >= 0) { /* vertex j is unlabelled */ /* remove it from the list of unlabelled vertices */ if (prev[j] == 0) f = next[j]; else next[prev[j]] = next[j]; if (next[j] == 0) ; else prev[next[j]] = prev[j]; /* label the vertex */ prev[j] = -1, next[j] = nc; /* and enqueue it for further consideration */ list[++pos2] = j; } } /* consider all arcs outgoing from vertex i */ for (a = G->v[i]->out; a != NULL; a = a->t_next) { /* vertex j is adjacent to vertex i */ j = a->head->i; if (prev[j] >= 0) { /* vertex j is unlabelled */ /* remove it from the list of unlabelled vertices */ if (prev[j] == 0) f = next[j]; else next[prev[j]] = next[j]; if (next[j] == 0) ; else prev[next[j]] = prev[j]; /* label the vertex */ prev[j] = -1, next[j] = nc; /* and enqueue it for further consideration */ list[++pos2] = j; } } } } /* store component numbers */ if (v_num >= 0) { for (i = 1; i <= nv; i++) { v = G->v[i]; memcpy((char *)v->data + v_num, &next[i], sizeof(int)); } } /* free working arrays */ xfree(prev); xfree(next); xfree(list); done: return nc; } /*********************************************************************** * NAME * * glp_strong_comp - find all strongly connected components of graph * * SYNOPSIS * * int glp_strong_comp(glp_graph *G, int v_num); * * DESCRIPTION * * The routine glp_strong_comp finds all strongly connected components * of the specified graph. * * The parameter v_num specifies an offset of the field of type int * in the vertex data block, to which the routine stores the number of * a strongly connected component containing that vertex. If v_num < 0, * no component numbers are stored. * * The components are numbered in arbitrary order from 1 to nc, where * nc is the total number of components found, 0 <= nc <= |V|. However, * the component numbering has the property that for every arc (i->j) * in the graph the condition num(i) >= num(j) holds. * * RETURNS * * The routine returns nc, the total number of components found. */ int glp_strong_comp(glp_graph *G, int v_num) { glp_vertex *v; glp_arc *a; int i, k, last, n, na, nc, *icn, *ip, *lenr, *ior, *ib, *lowl, *numb, *prev; if (v_num >= 0 && v_num > G->v_size - (int)sizeof(int)) xerror("glp_strong_comp: v_num = %d; invalid offset\n", v_num); n = G->nv; if (n == 0) { nc = 0; goto done; } na = G->na; icn = xcalloc(1+na, sizeof(int)); ip = xcalloc(1+n, sizeof(int)); lenr = xcalloc(1+n, sizeof(int)); ior = xcalloc(1+n, sizeof(int)); ib = xcalloc(1+n, sizeof(int)); lowl = xcalloc(1+n, sizeof(int)); numb = xcalloc(1+n, sizeof(int)); prev = xcalloc(1+n, sizeof(int)); k = 1; for (i = 1; i <= n; i++) { v = G->v[i]; ip[i] = k; for (a = v->out; a != NULL; a = a->t_next) icn[k++] = a->head->i; lenr[i] = k - ip[i]; } xassert(na == k-1); nc = mc13d(n, icn, ip, lenr, ior, ib, lowl, numb, prev); if (v_num >= 0) { xassert(ib[1] == 1); for (k = 1; k <= nc; k++) { last = (k < nc ? ib[k+1] : n+1); xassert(ib[k] < last); for (i = ib[k]; i < last; i++) { v = G->v[ior[i]]; memcpy((char *)v->data + v_num, &k, sizeof(int)); } } } xfree(icn); xfree(ip); xfree(lenr); xfree(ior); xfree(ib); xfree(lowl); xfree(numb); xfree(prev); done: return nc; } /*********************************************************************** * NAME * * glp_top_sort - topological sorting of acyclic digraph * * SYNOPSIS * * int glp_top_sort(glp_graph *G, int v_num); * * DESCRIPTION * * The routine glp_top_sort performs topological sorting of vertices of * the specified acyclic digraph. * * The parameter v_num specifies an offset of the field of type int in * the vertex data block, to which the routine stores the vertex number * assigned. If v_num < 0, vertex numbers are not stored. * * The vertices are numbered from 1 to n, where n is the total number * of vertices in the graph. The vertex numbering has the property that * for every arc (i->j) in the graph the condition num(i) < num(j) * holds. Special case num(i) = 0 means that vertex i is not assigned a * number, because the graph is *not* acyclic. * * RETURNS * * If the graph is acyclic and therefore all the vertices have been * assigned numbers, the routine glp_top_sort returns zero. Otherwise, * if the graph is not acyclic, the routine returns the number of * vertices which have not been numbered, i.e. for which num(i) = 0. */ static int top_sort(glp_graph *G, int num[]) { glp_arc *a; int i, j, cnt, top, *stack, *indeg; /* allocate working arrays */ indeg = xcalloc(1+G->nv, sizeof(int)); stack = xcalloc(1+G->nv, sizeof(int)); /* determine initial indegree of each vertex; push into the stack the vertices having zero indegree */ top = 0; for (i = 1; i <= G->nv; i++) { num[i] = indeg[i] = 0; for (a = G->v[i]->in; a != NULL; a = a->h_next) indeg[i]++; if (indeg[i] == 0) stack[++top] = i; } /* assign numbers to vertices in the sorted order */ cnt = 0; while (top > 0) { /* pull vertex i from the stack */ i = stack[top--]; /* it has zero indegree in the current graph */ xassert(indeg[i] == 0); /* so assign it a next number */ xassert(num[i] == 0); num[i] = ++cnt; /* remove vertex i from the current graph, update indegree of its adjacent vertices, and push into the stack new vertices whose indegree becomes zero */ for (a = G->v[i]->out; a != NULL; a = a->t_next) { j = a->head->i; /* there exists arc (i->j) in the graph */ xassert(indeg[j] > 0); indeg[j]--; if (indeg[j] == 0) stack[++top] = j; } } /* free working arrays */ xfree(indeg); xfree(stack); return G->nv - cnt; } int glp_top_sort(glp_graph *G, int v_num) { glp_vertex *v; int i, cnt, *num; if (v_num >= 0 && v_num > G->v_size - (int)sizeof(int)) xerror("glp_top_sort: v_num = %d; invalid offset\n", v_num); if (G->nv == 0) { cnt = 0; goto done; } num = xcalloc(1+G->nv, sizeof(int)); cnt = top_sort(G, num); if (v_num >= 0) { for (i = 1; i <= G->nv; i++) { v = G->v[i]; memcpy((char *)v->data + v_num, &num[i], sizeof(int)); } } xfree(num); done: return cnt; } /* eof */ sources_5316/external/glpk/glpapi19.c0000644000176700017670000013232711401660400016274 0ustar paulpaul/* glpapi19.c (stand-alone LP/MIP solver) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" #include "glpgmp.h" struct csa { /* common storage area */ glp_prob *prob; /* LP/MIP problem object */ glp_bfcp bfcp; /* basis factorization control parameters */ glp_smcp smcp; /* simplex method control parameters */ glp_iptcp iptcp; /* interior-point method control parameters */ glp_iocp iocp; /* integer optimizer control parameters */ glp_tran *tran; /* model translator workspace */ glp_graph *graph; /* network problem object */ int format; /* problem file format: */ #define FMT_MPS_DECK 1 /* fixed MPS */ #define FMT_MPS_FILE 2 /* free MPS */ #define FMT_LP 3 /* CPLEX LP */ #define FMT_GLP 4 /* GLPK LP/MIP */ #define FMT_MATHPROG 5 /* MathProg */ #define FMT_MIN_COST 6 /* DIMACS min-cost flow */ #define FMT_MAX_FLOW 7 /* DIMACS maximum flow */ const char *in_file; /* name of input problem file */ #define DATA_MAX 10 /* maximal number of input data files */ int ndf; /* number of input data files specified */ const char *in_data[1+DATA_MAX]; /* name(s) of input data file(s) */ const char *out_dpy; /* name of output file to send display output; NULL means the display output is sent to the terminal */ int seed; /* seed value to be passed to the MathProg translator; initially set to 1; 0x80000000 means the value is omitted */ int solution; /* solution type flag: */ #define SOL_BASIC 1 /* basic */ #define SOL_INTERIOR 2 /* interior-point */ #define SOL_INTEGER 3 /* mixed integer */ const char *in_res; /* name of input solution file in raw format */ int dir; /* optimization direction flag: 0 - not specified GLP_MIN - minimization GLP_MAX - maximization */ int scale; /* automatic problem scaling flag */ const char *out_sol; /* name of output solution file in printable format */ const char *out_res; /* name of output solution file in raw format */ const char *out_ranges; /* name of output file to write sensitivity analysis report */ int check; /* input data checking flag; no solution is performed */ const char *new_name; /* new name to be assigned to the problem */ const char *out_mps; /* name of output problem file in fixed MPS format */ const char *out_freemps; /* name of output problem file in free MPS format */ const char *out_cpxlp; /* name of output problem file in CPLEX LP format */ const char *out_glp; /* name of output problem file in GLPK format */ const char *out_pb; /* name of output problem file in OPB format */ const char *out_npb; /* name of output problem file in normalized OPB format */ const char *log_file; /* name of output file to hardcopy terminal output */ int crash; /* initial basis option: */ #define USE_STD_BASIS 1 /* use standard basis */ #define USE_ADV_BASIS 2 /* use advanced basis */ #define USE_CPX_BASIS 3 /* use Bixby's basis */ #define USE_INI_BASIS 4 /* use initial basis from ini_file */ const char *ini_file; /* name of input file containing initial basis */ int exact; /* flag to use glp_exact rather than glp_simplex */ int xcheck; /* flag to check final basis with glp_exact */ int nomip; /* flag to consider MIP as pure LP */ }; static void print_help(const char *my_name) { /* print help information */ xprintf("Usage: %s [options...] filename\n", my_name); xprintf("\n"); xprintf("General options:\n"); xprintf(" --mps read LP/MIP problem in fixed MPS fo" "rmat\n"); xprintf(" --freemps read LP/MIP problem in free MPS for" "mat (default)\n"); xprintf(" --lp read LP/MIP problem in CPLEX LP for" "mat\n"); xprintf(" --glp read LP/MIP problem in GLPK format " "\n"); xprintf(" --math read LP/MIP model written in GNU Ma" "thProg modeling\n"); xprintf(" language\n"); xprintf(" -m filename, --model filename\n"); xprintf(" read model section and optional dat" "a section from\n"); xprintf(" filename (same as --math)\n"); xprintf(" -d filename, --data filename\n"); xprintf(" read data section from filename (fo" "r --math only);\n"); xprintf(" if model file also has data section" ", it is ignored\n"); xprintf(" -y filename, --display filename\n"); xprintf(" send display output to filename (fo" "r --math only);\n"); xprintf(" by default the output is sent to te" "rminal\n"); xprintf(" --seed value initialize pseudo-random number gen" "erator used in\n"); xprintf(" MathProg model with specified seed " "(any integer);\n"); xprintf(" if seed value is ?, some random see" "d will be used\n"); xprintf(" --mincost read min-cost flow problem in DIMAC" "S format\n"); xprintf(" --maxflow read maximum flow problem in DIMACS" " format\n"); xprintf(" --simplex use simplex method (default)\n"); xprintf(" --interior use interior point method (LP only)" "\n"); xprintf(" -r filename, --read filename\n"); xprintf(" read solution from filename rather " "to find it with\n"); xprintf(" the solver\n"); xprintf(" --min minimization\n"); xprintf(" --max maximization\n"); xprintf(" --scale scale problem (default)\n"); xprintf(" --noscale do not scale problem\n"); xprintf(" -o filename, --output filename\n"); xprintf(" write solution to filename in print" "able format\n"); xprintf(" -w filename, --write filename\n"); xprintf(" write solution to filename in plain" " text format\n"); xprintf(" --ranges filename\n"); xprintf(" write sensitivity analysis report t" "o filename in\n"); xprintf(" printable format (simplex only)\n"); xprintf(" --tmlim nnn limit solution time to nnn seconds " "\n"); xprintf(" --memlim nnn limit available memory to nnn megab" "ytes\n"); xprintf(" --check do not solve problem, check input d" "ata only\n"); xprintf(" --name probname change problem name to probname\n"); xprintf(" --wmps filename write problem to filename in fixed " "MPS format\n"); xprintf(" --wfreemps filename\n"); xprintf(" write problem to filename in free M" "PS format\n"); xprintf(" --wlp filename write problem to filename in CPLEX " "LP format\n"); xprintf(" --wglp filename write problem to filename in GLPK f" "ormat\n"); #if 0 xprintf(" --wpb filename write problem to filename in OPB fo" "rmat\n"); xprintf(" --wnpb filename write problem to filename in normal" "ized OPB format\n"); #endif xprintf(" --log filename write copy of terminal output to fi" "lename\n"); xprintf(" -h, --help display this help information and e" "xit\n"); xprintf(" -v, --version display program version and exit\n") ; xprintf("\n"); xprintf("LP basis factorization options:\n"); xprintf(" --luf LU + Forrest-Tomlin update\n"); xprintf(" (faster, less stable; default)\n"); xprintf(" --cbg LU + Schur complement + Bartels-Gol" "ub update\n"); xprintf(" (slower, more stable)\n"); xprintf(" --cgr LU + Schur complement + Givens rota" "tion update\n"); xprintf(" (slower, more stable)\n"); xprintf("\n"); xprintf("Options specific to simplex solver:\n"); xprintf(" --primal use primal simplex (default)\n"); xprintf(" --dual use dual simplex\n"); xprintf(" --std use standard initial basis of all s" "lacks\n"); xprintf(" --adv use advanced initial basis (default" ")\n"); xprintf(" --bib use Bixby's initial basis\n"); xprintf(" --ini filename use as initial basis previously sav" "ed with -w\n"); xprintf(" (disables LP presolver)\n"); xprintf(" --steep use steepest edge technique (defaul" "t)\n"); xprintf(" --nosteep use standard \"textbook\" pricing\n" ); xprintf(" --relax use Harris' two-pass ratio test (de" "fault)\n"); xprintf(" --norelax use standard \"textbook\" ratio tes" "t\n"); xprintf(" --presol use presolver (default; assumes --s" "cale and --adv)\n"); xprintf(" --nopresol do not use presolver\n"); xprintf(" --exact use simplex method based on exact a" "rithmetic\n"); xprintf(" --xcheck check final basis using exact arith" "metic\n"); xprintf("\n"); xprintf("Options specific to interior-point solver:\n"); xprintf(" --nord use natural (original) ordering\n"); xprintf(" --qmd use quotient minimum degree orderin" "g\n"); xprintf(" --amd use approximate minimum degree orde" "ring (default)\n"); xprintf(" --symamd use approximate minimum degree orde" "ring\n"); xprintf("\n"); xprintf("Options specific to MIP solver:\n"); xprintf(" --nomip consider all integer variables as c" "ontinuous\n"); xprintf(" (allows solving MIP as pure LP)\n"); xprintf(" --first branch on first integer variable\n") ; xprintf(" --last branch on last integer variable\n"); xprintf(" --mostf branch on most fractional variable " "\n"); xprintf(" --drtom branch using heuristic by Driebeck " "and Tomlin\n"); xprintf(" (default)\n"); xprintf(" --pcost branch using hybrid pseudocost heur" "istic (may be\n"); xprintf(" useful for hard instances)\n"); xprintf(" --dfs backtrack using depth first search " "\n"); xprintf(" --bfs backtrack using breadth first searc" "h\n"); xprintf(" --bestp backtrack using the best projection" " heuristic\n"); xprintf(" --bestb backtrack using node with best loca" "l bound\n"); xprintf(" (default)\n"); xprintf(" --intopt use MIP presolver (default)\n"); xprintf(" --nointopt do not use MIP presolver\n"); xprintf(" --binarize replace general integer variables b" "y binary ones\n"); xprintf(" (assumes --intopt)\n"); xprintf(" --fpump apply feasibility pump heuristic\n") ; xprintf(" --gomory generate Gomory's mixed integer cut" "s\n"); xprintf(" --mir generate MIR (mixed integer roundin" "g) cuts\n"); xprintf(" --cover generate mixed cover cuts\n"); xprintf(" --clique generate clique cuts\n"); xprintf(" --cuts generate all cuts above\n"); xprintf(" --mipgap tol set relative mip gap tolerance to t" "ol\n"); xprintf("\n"); xprintf("For description of the MPS and CPLEX LP formats see Refe" "rence Manual.\n"); xprintf("For description of the modeling language see \"GLPK: Mod" "eling Language\n"); xprintf("GNU MathProg\". Both documents are included in the GLPK " "distribution.\n"); xprintf("\n"); xprintf("See GLPK web page at .\n"); xprintf("\n"); xprintf("Please report bugs to .\n"); return; } static void print_version(int briefly) { /* print version information */ xprintf("GLPSOL: GLPK LP/MIP Solver, v%s\n", glp_version()); if (briefly) goto done; xprintf("\n"); xprintf("Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, " "2007, 2008,\n"); xprintf("2009, 2010 Andrew Makhorin, Department for Applied Infor" "matics, Moscow\n"); xprintf("Aviation Institute, Moscow, Russia. All rights reserved." "\n"); xprintf("\n"); xprintf("This program has ABSOLUTELY NO WARRANTY.\n"); xprintf("\n"); xprintf("This program is free software; you may re-distribute it " "under the terms\n"); xprintf("of the GNU General Public License version 3 or later.\n") ; done: return; } static int parse_cmdline(struct csa *csa, int argc, const char *argv[]) { /* parse command-line parameters */ int k; #define p(str) (strcmp(argv[k], str) == 0) for (k = 1; k < argc; k++) { if (p("--mps")) csa->format = FMT_MPS_DECK; else if (p("--freemps")) csa->format = FMT_MPS_FILE; else if (p("--lp") || p("--cpxlp")) csa->format = FMT_LP; else if (p("--glp")) csa->format = FMT_GLP; else if (p("--math") || p("-m") || p("--model")) csa->format = FMT_MATHPROG; else if (p("-d") || p("--data")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No input data file specified\n"); return 1; } if (csa->ndf == DATA_MAX) { xprintf("Too many input data files\n"); return 1; } csa->in_data[++(csa->ndf)] = argv[k]; } else if (p("-y") || p("--display")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No display output file specified\n"); return 1; } if (csa->out_dpy != NULL) { xprintf("Only one display output file allowed\n"); return 1; } csa->out_dpy = argv[k]; } else if (p("--seed")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-' && !isdigit((unsigned char)argv[k][1])) { xprintf("No seed value specified\n"); return 1; } if (strcmp(argv[k], "?") == 0) csa->seed = 0x80000000; else if (str2int(argv[k], &csa->seed)) { xprintf("Invalid seed value `%s'\n", argv[k]); return 1; } } else if (p("--mincost")) csa->format = FMT_MIN_COST; else if (p("--maxflow")) csa->format = FMT_MAX_FLOW; else if (p("--simplex")) csa->solution = SOL_BASIC; else if (p("--interior")) csa->solution = SOL_INTERIOR; #if 1 /* 28/V-2010 */ else if (p("--alien")) csa->iocp.alien = GLP_ON; #endif else if (p("-r") || p("--read")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No input solution file specified\n"); return 1; } if (csa->in_res != NULL) { xprintf("Only one input solution file allowed\n"); return 1; } csa->in_res = argv[k]; } else if (p("--min")) csa->dir = GLP_MIN; else if (p("--max")) csa->dir = GLP_MAX; else if (p("--scale")) csa->scale = 1; else if (p("--noscale")) csa->scale = 0; else if (p("-o") || p("--output")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No output solution file specified\n"); return 1; } if (csa->out_sol != NULL) { xprintf("Only one output solution file allowed\n"); return 1; } csa->out_sol = argv[k]; } else if (p("-w") || p("--write")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No output solution file specified\n"); return 1; } if (csa->out_res != NULL) { xprintf("Only one output solution file allowed\n"); return 1; } csa->out_res = argv[k]; } else if (p("--ranges") || p("--bounds")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No output file specified to write sensitivity a" "nalysis report\n"); return 1; } if (csa->out_ranges != NULL) { xprintf("Only one output file allowed to write sensitivi" "ty analysis report\n"); return 1; } csa->out_ranges = argv[k]; } else if (p("--tmlim")) { int tm_lim; k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No time limit specified\n"); return 1; } if (str2int(argv[k], &tm_lim) || tm_lim < 0) { xprintf("Invalid time limit `%s'\n", argv[k]); return 1; } if (tm_lim <= INT_MAX / 1000) csa->smcp.tm_lim = csa->iocp.tm_lim = 1000 * tm_lim; else csa->smcp.tm_lim = csa->iocp.tm_lim = INT_MAX; } else if (p("--memlim")) { int mem_lim; k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No memory limit specified\n"); return 1; } if (str2int(argv[k], &mem_lim) || mem_lim < 1) { xprintf("Invalid memory limit `%s'\n", argv[k]); return 1; } glp_mem_limit(mem_lim); } else if (p("--check")) csa->check = 1; else if (p("--name")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No problem name specified\n"); return 1; } if (csa->new_name != NULL) { xprintf("Only one problem name allowed\n"); return 1; } csa->new_name = argv[k]; } else if (p("--wmps")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No fixed MPS output file specified\n"); return 1; } if (csa->out_mps != NULL) { xprintf("Only one fixed MPS output file allowed\n"); return 1; } csa->out_mps = argv[k]; } else if (p("--wfreemps")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No free MPS output file specified\n"); return 1; } if (csa->out_freemps != NULL) { xprintf("Only one free MPS output file allowed\n"); return 1; } csa->out_freemps = argv[k]; } else if (p("--wlp") || p("--wcpxlp") || p("--wlpt")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No CPLEX LP output file specified\n"); return 1; } if (csa->out_cpxlp != NULL) { xprintf("Only one CPLEX LP output file allowed\n"); return 1; } csa->out_cpxlp = argv[k]; } else if (p("--wglp")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No GLPK LP/MIP output file specified\n"); return 1; } if (csa->out_glp != NULL) { xprintf("Only one GLPK LP/MIP output file allowed\n"); return 1; } csa->out_glp = argv[k]; } else if (p("--wpb")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No problem output file specified\n"); return 1; } if (csa->out_pb != NULL) { xprintf("Only one OPB output file allowed\n"); return 1; } csa->out_pb = argv[k]; } else if (p("--wnpb")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No problem output file specified\n"); return 1; } if (csa->out_npb != NULL) { xprintf("Only one normalized OPB output file allowed\n"); return 1; } csa->out_npb = argv[k]; } else if (p("--log")) { k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No log file specified\n"); return 1; } if (csa->log_file != NULL) { xprintf("Only one log file allowed\n"); return 1; } csa->log_file = argv[k]; } else if (p("-h") || p("--help")) { print_help(argv[0]); return -1; } else if (p("-v") || p("--version")) { print_version(0); return -1; } else if (p("--luf")) csa->bfcp.type = GLP_BF_FT; else if (p("--cbg")) csa->bfcp.type = GLP_BF_BG; else if (p("--cgr")) csa->bfcp.type = GLP_BF_GR; else if (p("--primal")) csa->smcp.meth = GLP_PRIMAL; else if (p("--dual")) csa->smcp.meth = GLP_DUAL; else if (p("--std")) csa->crash = USE_STD_BASIS; else if (p("--adv")) csa->crash = USE_ADV_BASIS; else if (p("--bib")) csa->crash = USE_CPX_BASIS; else if (p("--ini")) { csa->crash = USE_INI_BASIS; csa->smcp.presolve = GLP_OFF; k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No initial basis file specified\n"); return 1; } if (csa->ini_file != NULL) { xprintf("Only one initial basis file allowed\n"); return 1; } csa->ini_file = argv[k]; } else if (p("--steep")) csa->smcp.pricing = GLP_PT_PSE; else if (p("--nosteep")) csa->smcp.pricing = GLP_PT_STD; else if (p("--relax")) csa->smcp.r_test = GLP_RT_HAR; else if (p("--norelax")) csa->smcp.r_test = GLP_RT_STD; else if (p("--presol")) csa->smcp.presolve = GLP_ON; else if (p("--nopresol")) csa->smcp.presolve = GLP_OFF; else if (p("--exact")) csa->exact = 1; else if (p("--xcheck")) csa->xcheck = 1; else if (p("--nord")) csa->iptcp.ord_alg = GLP_ORD_NONE; else if (p("--qmd")) csa->iptcp.ord_alg = GLP_ORD_QMD; else if (p("--amd")) csa->iptcp.ord_alg = GLP_ORD_AMD; else if (p("--symamd")) csa->iptcp.ord_alg = GLP_ORD_SYMAMD; else if (p("--nomip")) csa->nomip = 1; else if (p("--first")) csa->iocp.br_tech = GLP_BR_FFV; else if (p("--last")) csa->iocp.br_tech = GLP_BR_LFV; else if (p("--drtom")) csa->iocp.br_tech = GLP_BR_DTH; else if (p("--mostf")) csa->iocp.br_tech = GLP_BR_MFV; else if (p("--pcost")) csa->iocp.br_tech = GLP_BR_PCH; else if (p("--dfs")) csa->iocp.bt_tech = GLP_BT_DFS; else if (p("--bfs")) csa->iocp.bt_tech = GLP_BT_BFS; else if (p("--bestp")) csa->iocp.bt_tech = GLP_BT_BPH; else if (p("--bestb")) csa->iocp.bt_tech = GLP_BT_BLB; else if (p("--intopt")) csa->iocp.presolve = GLP_ON; else if (p("--nointopt")) csa->iocp.presolve = GLP_OFF; else if (p("--binarize")) csa->iocp.presolve = csa->iocp.binarize = GLP_ON; else if (p("--fpump")) csa->iocp.fp_heur = GLP_ON; else if (p("--gomory")) csa->iocp.gmi_cuts = GLP_ON; else if (p("--mir")) csa->iocp.mir_cuts = GLP_ON; else if (p("--cover")) csa->iocp.cov_cuts = GLP_ON; else if (p("--clique")) csa->iocp.clq_cuts = GLP_ON; else if (p("--cuts")) csa->iocp.gmi_cuts = csa->iocp.mir_cuts = csa->iocp.cov_cuts = csa->iocp.clq_cuts = GLP_ON; else if (p("--mipgap")) { double mip_gap; k++; if (k == argc || argv[k][0] == '\0' || argv[k][0] == '-') { xprintf("No relative gap tolerance specified\n"); return 1; } if (str2num(argv[k], &mip_gap) || mip_gap < 0.0) { xprintf("Invalid relative mip gap tolerance `%s'\n", argv[k]); return 1; } csa->iocp.mip_gap = mip_gap; } else if (argv[k][0] == '-' || (argv[k][0] == '-' && argv[k][1] == '-')) { xprintf("Invalid option `%s'; try %s --help\n", argv[k], argv[0]); return 1; } else { if (csa->in_file != NULL) { xprintf("Only one input problem file allowed\n"); return 1; } csa->in_file = argv[k]; } } #undef p return 0; } typedef struct { double rhs, pi; } v_data; typedef struct { double low, cap, cost, x; } a_data; int glp_main(int argc, const char *argv[]) { /* stand-alone LP/MIP solver */ struct csa _csa, *csa = &_csa; int ret; glp_long start; /* perform initialization */ csa->prob = glp_create_prob(); glp_get_bfcp(csa->prob, &csa->bfcp); glp_init_smcp(&csa->smcp); csa->smcp.presolve = GLP_ON; glp_init_iptcp(&csa->iptcp); glp_init_iocp(&csa->iocp); csa->iocp.presolve = GLP_ON; csa->tran = NULL; csa->graph = NULL; csa->format = FMT_MPS_FILE; csa->in_file = NULL; csa->ndf = 0; csa->out_dpy = NULL; csa->seed = 1; csa->solution = SOL_BASIC; csa->in_res = NULL; csa->dir = 0; csa->scale = 1; csa->out_sol = NULL; csa->out_res = NULL; csa->out_ranges = NULL; csa->check = 0; csa->new_name = NULL; csa->out_mps = NULL; csa->out_freemps = NULL; csa->out_cpxlp = NULL; csa->out_glp = NULL; csa->out_pb = NULL; csa->out_npb = NULL; csa->log_file = NULL; csa->crash = USE_ADV_BASIS; csa->ini_file = NULL; csa->exact = 0; csa->xcheck = 0; csa->nomip = 0; /* parse command-line parameters */ ret = parse_cmdline(csa, argc, argv); if (ret < 0) { ret = EXIT_SUCCESS; goto done; } if (ret > 0) { ret = EXIT_FAILURE; goto done; } /*--------------------------------------------------------------*/ /* remove all output files specified in the command line */ if (csa->out_dpy != NULL) remove(csa->out_dpy); if (csa->out_sol != NULL) remove(csa->out_sol); if (csa->out_res != NULL) remove(csa->out_res); if (csa->out_ranges != NULL) remove(csa->out_ranges); if (csa->out_mps != NULL) remove(csa->out_mps); if (csa->out_freemps != NULL) remove(csa->out_freemps); if (csa->out_cpxlp != NULL) remove(csa->out_cpxlp); if (csa->out_glp != NULL) remove(csa->out_glp); if (csa->out_pb != NULL) remove(csa->out_pb); if (csa->out_npb != NULL) remove(csa->out_npb); if (csa->log_file != NULL) remove(csa->log_file); /*--------------------------------------------------------------*/ /* open log file, if required */ if (csa->log_file != NULL) { if (glp_open_tee(csa->log_file)) { xprintf("Unable to create log file\n"); ret = EXIT_FAILURE; goto done; } } /*--------------------------------------------------------------*/ /* print version information */ print_version(1); /*--------------------------------------------------------------*/ /* print parameters specified in the command line */ if (argc > 1) { int k, len = INT_MAX; xprintf("Parameter(s) specified in the command line:"); for (k = 1; k < argc; k++) { if (len > 72) xprintf("\n"), len = 0; xprintf(" %s", argv[k]); len += 1 + strlen(argv[k]); } xprintf("\n"); } /*--------------------------------------------------------------*/ /* read problem data from the input file */ if (csa->in_file == NULL) { xprintf("No input problem file specified; try %s --help\n", argv[0]); ret = EXIT_FAILURE; goto done; } if (csa->format == FMT_MPS_DECK) { ret = glp_read_mps(csa->prob, GLP_MPS_DECK, NULL, csa->in_file); if (ret != 0) err1: { xprintf("MPS file processing error\n"); ret = EXIT_FAILURE; goto done; } } else if (csa->format == FMT_MPS_FILE) { ret = glp_read_mps(csa->prob, GLP_MPS_FILE, NULL, csa->in_file); if (ret != 0) goto err1; } else if (csa->format == FMT_LP) { ret = glp_read_lp(csa->prob, NULL, csa->in_file); if (ret != 0) { xprintf("CPLEX LP file processing error\n"); ret = EXIT_FAILURE; goto done; } } else if (csa->format == FMT_GLP) { ret = glp_read_prob(csa->prob, 0, csa->in_file); if (ret != 0) { xprintf("GLPK LP/MIP file processing error\n"); ret = EXIT_FAILURE; goto done; } } else if (csa->format == FMT_MATHPROG) { int k; /* allocate the translator workspace */ csa->tran = glp_mpl_alloc_wksp(); /* set seed value */ if (csa->seed == 0x80000000) { csa->seed = glp_time().lo; xprintf("Seed value %d will be used\n", csa->seed); } _glp_mpl_init_rand(csa->tran, csa->seed); /* read model section and optional data section */ if (glp_mpl_read_model(csa->tran, csa->in_file, csa->ndf > 0)) err2: { xprintf("MathProg model processing error\n"); ret = EXIT_FAILURE; goto done; } /* read optional data section(s), if necessary */ for (k = 1; k <= csa->ndf; k++) { if (glp_mpl_read_data(csa->tran, csa->in_data[k])) goto err2; } /* generate the model */ if (glp_mpl_generate(csa->tran, csa->out_dpy)) goto err2; /* build the problem instance from the model */ glp_mpl_build_prob(csa->tran, csa->prob); } else if (csa->format == FMT_MIN_COST) { csa->graph = glp_create_graph(sizeof(v_data), sizeof(a_data)); ret = glp_read_mincost(csa->graph, offsetof(v_data, rhs), offsetof(a_data, low), offsetof(a_data, cap), offsetof(a_data, cost), csa->in_file); if (ret != 0) { xprintf("DIMACS file processing error\n"); ret = EXIT_FAILURE; goto done; } glp_mincost_lp(csa->prob, csa->graph, GLP_ON, offsetof(v_data, rhs), offsetof(a_data, low), offsetof(a_data, cap), offsetof(a_data, cost)); glp_set_prob_name(csa->prob, csa->in_file); } else if (csa->format == FMT_MAX_FLOW) { int s, t; csa->graph = glp_create_graph(sizeof(v_data), sizeof(a_data)); ret = glp_read_maxflow(csa->graph, &s, &t, offsetof(a_data, cap), csa->in_file); if (ret != 0) { xprintf("DIMACS file processing error\n"); ret = EXIT_FAILURE; goto done; } glp_maxflow_lp(csa->prob, csa->graph, GLP_ON, s, t, offsetof(a_data, cap)); glp_set_prob_name(csa->prob, csa->in_file); } else xassert(csa != csa); /*--------------------------------------------------------------*/ /* change problem name, if required */ if (csa->new_name != NULL) glp_set_prob_name(csa->prob, csa->new_name); /* change optimization direction, if required */ if (csa->dir != 0) glp_set_obj_dir(csa->prob, csa->dir); /* sort elements of the constraint matrix */ glp_sort_matrix(csa->prob); /*--------------------------------------------------------------*/ /* write problem data in fixed MPS format, if required */ if (csa->out_mps != NULL) { ret = glp_write_mps(csa->prob, GLP_MPS_DECK, NULL, csa->out_mps); if (ret != 0) { xprintf("Unable to write problem in fixed MPS format\n"); ret = EXIT_FAILURE; goto done; } } /* write problem data in free MPS format, if required */ if (csa->out_freemps != NULL) { ret = glp_write_mps(csa->prob, GLP_MPS_FILE, NULL, csa->out_freemps); if (ret != 0) { xprintf("Unable to write problem in free MPS format\n"); ret = EXIT_FAILURE; goto done; } } /* write problem data in CPLEX LP format, if required */ if (csa->out_cpxlp != NULL) { ret = glp_write_lp(csa->prob, NULL, csa->out_cpxlp); if (ret != 0) { xprintf("Unable to write problem in CPLEX LP format\n"); ret = EXIT_FAILURE; goto done; } } /* write problem data in GLPK format, if required */ if (csa->out_glp != NULL) { ret = glp_write_prob(csa->prob, 0, csa->out_glp); if (ret != 0) { xprintf("Unable to write problem in GLPK format\n"); ret = EXIT_FAILURE; goto done; } } /* write problem data in OPB format, if required */ if (csa->out_pb != NULL) { ret = lpx_write_pb(csa->prob, csa->out_pb, 0, 0); if (ret != 0) { xprintf("Unable to write problem in OPB format\n"); ret = EXIT_FAILURE; goto done; } } /* write problem data in normalized OPB format, if required */ if (csa->out_npb != NULL) { ret = lpx_write_pb(csa->prob, csa->out_npb, 1, 1); if (ret != 0) { xprintf( "Unable to write problem in normalized OPB format\n"); ret = EXIT_FAILURE; goto done; } } /*--------------------------------------------------------------*/ /* if only problem data check is required, skip computations */ if (csa->check) { ret = EXIT_SUCCESS; goto done; } /*--------------------------------------------------------------*/ /* determine the solution type */ if (!csa->nomip && glp_get_num_int(csa->prob) + glp_get_num_bin(csa->prob) > 0) { if (csa->solution == SOL_INTERIOR) { xprintf("Interior-point method is not able to solve MIP pro" "blem; use --simplex\n"); ret = EXIT_FAILURE; goto done; } csa->solution = SOL_INTEGER; } /*--------------------------------------------------------------*/ /* if solution is provided, read it and skip computations */ if (csa->in_res != NULL) { if (csa->solution == SOL_BASIC) ret = glp_read_sol(csa->prob, csa->in_res); else if (csa->solution == SOL_INTERIOR) ret = glp_read_ipt(csa->prob, csa->in_res); else if (csa->solution == SOL_INTEGER) ret = glp_read_mip(csa->prob, csa->in_res); else xassert(csa != csa); if (ret != 0) { xprintf("Unable to read problem solution\n"); ret = EXIT_FAILURE; goto done; } goto skip; } /*--------------------------------------------------------------*/ /* scale the problem data, if required */ if (csa->scale) { if (csa->solution == SOL_BASIC && !csa->smcp.presolve || csa->solution == SOL_INTERIOR || csa->solution == SOL_INTEGER && !csa->iocp.presolve) glp_scale_prob(csa->prob, GLP_SF_AUTO); } /*--------------------------------------------------------------*/ /* construct starting LP basis */ if (csa->solution == SOL_BASIC && !csa->smcp.presolve || csa->solution == SOL_INTEGER && !csa->iocp.presolve) { if (csa->crash == USE_STD_BASIS) glp_std_basis(csa->prob); else if (csa->crash == USE_ADV_BASIS) glp_adv_basis(csa->prob, 0); else if (csa->crash == USE_CPX_BASIS) glp_cpx_basis(csa->prob); else if (csa->crash == USE_INI_BASIS) { ret = glp_read_sol(csa->prob, csa->ini_file); if (ret != 0) { xprintf("Unable to read initial basis\n"); ret = EXIT_FAILURE; goto done; } } else xassert(csa != csa); } /*--------------------------------------------------------------*/ /* solve the problem */ start = xtime(); if (csa->solution == SOL_BASIC) { if (!csa->exact) { glp_set_bfcp(csa->prob, &csa->bfcp); glp_simplex(csa->prob, &csa->smcp); if (csa->xcheck) { if (csa->smcp.presolve && glp_get_status(csa->prob) != GLP_OPT) xprintf("If you need to check final basis for non-opt" "imal solution, use --nopresol\n"); else glp_exact(csa->prob, &csa->smcp); } if (csa->out_sol != NULL || csa->out_res != NULL) { if (csa->smcp.presolve && glp_get_status(csa->prob) != GLP_OPT) xprintf("If you need actual output for non-optimal solut" "ion, use --nopresol\n"); } } else glp_exact(csa->prob, &csa->smcp); } else if (csa->solution == SOL_INTERIOR) glp_interior(csa->prob, &csa->iptcp); else if (csa->solution == SOL_INTEGER) { if (!csa->iocp.presolve) { glp_set_bfcp(csa->prob, &csa->bfcp); glp_simplex(csa->prob, &csa->smcp); } #if 0 csa->iocp.msg_lev = GLP_MSG_DBG; csa->iocp.pp_tech = GLP_PP_NONE; #endif glp_intopt(csa->prob, &csa->iocp); } else xassert(csa != csa); /*--------------------------------------------------------------*/ /* display statistics */ xprintf("Time used: %.1f secs\n", xdifftime(xtime(), start)); { glp_long tpeak; char buf[50]; glp_mem_usage(NULL, NULL, NULL, &tpeak); xprintf("Memory used: %.1f Mb (%s bytes)\n", xltod(tpeak) / 1048576.0, xltoa(tpeak, buf)); } /*--------------------------------------------------------------*/ skip: /* postsolve the model, if necessary */ if (csa->tran != NULL) { if (csa->solution == SOL_BASIC) ret = glp_mpl_postsolve(csa->tran, csa->prob, GLP_SOL); else if (csa->solution == SOL_INTERIOR) ret = glp_mpl_postsolve(csa->tran, csa->prob, GLP_IPT); else if (csa->solution == SOL_INTEGER) ret = glp_mpl_postsolve(csa->tran, csa->prob, GLP_MIP); else xassert(csa != csa); if (ret != 0) { xprintf("Model postsolving error\n"); ret = EXIT_FAILURE; goto done; } } /*--------------------------------------------------------------*/ /* write problem solution in printable format, if required */ if (csa->out_sol != NULL) { if (csa->solution == SOL_BASIC) ret = lpx_print_sol(csa->prob, csa->out_sol); else if (csa->solution == SOL_INTERIOR) ret = lpx_print_ips(csa->prob, csa->out_sol); else if (csa->solution == SOL_INTEGER) ret = lpx_print_mip(csa->prob, csa->out_sol); else xassert(csa != csa); if (ret != 0) { xprintf("Unable to write problem solution\n"); ret = EXIT_FAILURE; goto done; } } /* write problem solution in printable format, if required */ if (csa->out_res != NULL) { if (csa->solution == SOL_BASIC) ret = glp_write_sol(csa->prob, csa->out_res); else if (csa->solution == SOL_INTERIOR) ret = glp_write_ipt(csa->prob, csa->out_res); else if (csa->solution == SOL_INTEGER) ret = glp_write_mip(csa->prob, csa->out_res); else xassert(csa != csa); if (ret != 0) { xprintf("Unable to write problem solution\n"); ret = EXIT_FAILURE; goto done; } } /* write sensitivity analysis report, if required */ if (csa->out_ranges != NULL) { if (csa->solution == SOL_BASIC) { if (glp_get_status(csa->prob) == GLP_OPT) { if (glp_bf_exists(csa->prob)) ranges: { ret = glp_print_ranges(csa->prob, 0, NULL, 0, csa->out_ranges); if (ret != 0) { xprintf("Unable to write sensitivity analysis repo" "rt\n"); ret = EXIT_FAILURE; goto done; } } else { ret = glp_factorize(csa->prob); if (ret == 0) goto ranges; xprintf("Cannot produce sensitivity analysis report d" "ue to error in basis factorization (glp_factorize" " returned %d); try --nopresol\n", ret); } } else xprintf("Cannot produce sensitivity analysis report for " "non-optimal basic solution\n"); } else xprintf("Cannot produce sensitivity analysis report for int" "erior-point or MIP solution\n"); } /*--------------------------------------------------------------*/ /* all seems to be ok */ ret = EXIT_SUCCESS; /*--------------------------------------------------------------*/ done: /* delete the LP/MIP problem object */ if (csa->prob != NULL) glp_delete_prob(csa->prob); /* free the translator workspace, if necessary */ if (csa->tran != NULL) glp_mpl_free_wksp(csa->tran); /* delete the network problem object, if necessary */ if (csa->graph != NULL) glp_delete_graph(csa->graph); xassert(gmp_pool_count() == 0); gmp_free_mem(); /* close log file, if necessary */ if (csa->log_file != NULL) glp_close_tee(); /* check that no memory blocks are still allocated */ { int count; glp_long total; glp_mem_usage(&count, NULL, &total, NULL); if (count != 0) xerror("Error: %d memory block(s) were lost\n", count); xassert(count == 0); xassert(total.lo == 0 && total.hi == 0); } /* free the GLPK environment */ glp_free_env(); /* return to the control program */ return ret; } /* eof */ sources_5316/external/glpk/amd_info.c0000644000176700017670000001065611401660400016422 0ustar paulpaul/* ========================================================================= */ /* === AMD_info ============================================================ */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* User-callable. Prints the output statistics for AMD. See amd.h * for details. If the Info array is not present, nothing is printed. */ #include "amd_internal.h" #define PRI(format,x) { if (x >= 0) { PRINTF ((format, x)) ; }} GLOBAL void AMD_info ( double Info [ ] ) { double n, ndiv, nmultsubs_ldl, nmultsubs_lu, lnz, lnzd ; PRINTF (("\nAMD version %d.%d.%d, %s, results:\n", AMD_MAIN_VERSION, AMD_SUB_VERSION, AMD_SUBSUB_VERSION, AMD_DATE)) ; if (!Info) { return ; } n = Info [AMD_N] ; ndiv = Info [AMD_NDIV] ; nmultsubs_ldl = Info [AMD_NMULTSUBS_LDL] ; nmultsubs_lu = Info [AMD_NMULTSUBS_LU] ; lnz = Info [AMD_LNZ] ; lnzd = (n >= 0 && lnz >= 0) ? (n + lnz) : (-1) ; /* AMD return status */ PRINTF ((" status: ")) ; if (Info [AMD_STATUS] == AMD_OK) { PRINTF (("OK\n")) ; } else if (Info [AMD_STATUS] == AMD_OUT_OF_MEMORY) { PRINTF (("out of memory\n")) ; } else if (Info [AMD_STATUS] == AMD_INVALID) { PRINTF (("invalid matrix\n")) ; } else if (Info [AMD_STATUS] == AMD_OK_BUT_JUMBLED) { PRINTF (("OK, but jumbled\n")) ; } else { PRINTF (("unknown\n")) ; } /* statistics about the input matrix */ PRI (" n, dimension of A: %.20g\n", n); PRI (" nz, number of nonzeros in A: %.20g\n", Info [AMD_NZ]) ; PRI (" symmetry of A: %.4f\n", Info [AMD_SYMMETRY]) ; PRI (" number of nonzeros on diagonal: %.20g\n", Info [AMD_NZDIAG]) ; PRI (" nonzeros in pattern of A+A' (excl. diagonal): %.20g\n", Info [AMD_NZ_A_PLUS_AT]) ; PRI (" # dense rows/columns of A+A': %.20g\n", Info [AMD_NDENSE]) ; /* statistics about AMD's behavior */ PRI (" memory used, in bytes: %.20g\n", Info [AMD_MEMORY]) ; PRI (" # of memory compactions: %.20g\n", Info [AMD_NCMPA]) ; /* statistics about the ordering quality */ PRINTF (("\n" " The following approximate statistics are for a subsequent\n" " factorization of A(P,P) + A(P,P)'. They are slight upper\n" " bounds if there are no dense rows/columns in A+A', and become\n" " looser if dense rows/columns exist.\n\n")) ; PRI (" nonzeros in L (excluding diagonal): %.20g\n", lnz) ; PRI (" nonzeros in L (including diagonal): %.20g\n", lnzd) ; PRI (" # divide operations for LDL' or LU: %.20g\n", ndiv) ; PRI (" # multiply-subtract operations for LDL': %.20g\n", nmultsubs_ldl) ; PRI (" # multiply-subtract operations for LU: %.20g\n", nmultsubs_lu) ; PRI (" max nz. in any column of L (incl. diagonal): %.20g\n", Info [AMD_DMAX]) ; /* total flop counts for various factorizations */ if (n >= 0 && ndiv >= 0 && nmultsubs_ldl >= 0 && nmultsubs_lu >= 0) { PRINTF (("\n" " chol flop count for real A, sqrt counted as 1 flop: %.20g\n" " LDL' flop count for real A: %.20g\n" " LDL' flop count for complex A: %.20g\n" " LU flop count for real A (with no pivoting): %.20g\n" " LU flop count for complex A (with no pivoting): %.20g\n\n", n + ndiv + 2*nmultsubs_ldl, ndiv + 2*nmultsubs_ldl, 9*ndiv + 8*nmultsubs_ldl, ndiv + 2*nmultsubs_lu, 9*ndiv + 8*nmultsubs_lu)) ; } } sources_5316/external/glpk/glpgmp.c0000644000176700017670000007560311401660400016137 0ustar paulpaul/* glpgmp.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_STDIO #include "glpdmp.h" #include "glpgmp.h" #define xfault xerror #ifdef HAVE_GMP /* use GNU MP bignum library */ int gmp_pool_count(void) { return 0; } void gmp_free_mem(void) { return; } #else /* use GLPK bignum module */ static DMP *gmp_pool = NULL; static int gmp_size = 0; static unsigned short *gmp_work = NULL; void *gmp_get_atom(int size) { if (gmp_pool == NULL) gmp_pool = dmp_create_pool(); return dmp_get_atom(gmp_pool, size); } void gmp_free_atom(void *ptr, int size) { xassert(gmp_pool != NULL); dmp_free_atom(gmp_pool, ptr, size); return; } int gmp_pool_count(void) { if (gmp_pool == NULL) return 0; else return dmp_in_use(gmp_pool).lo; } unsigned short *gmp_get_work(int size) { xassert(size > 0); if (gmp_size < size) { if (gmp_size == 0) { xassert(gmp_work == NULL); gmp_size = 100; } else { xassert(gmp_work != NULL); xfree(gmp_work); } while (gmp_size < size) gmp_size += gmp_size; gmp_work = xcalloc(gmp_size, sizeof(unsigned short)); } return gmp_work; } void gmp_free_mem(void) { if (gmp_pool != NULL) dmp_delete_pool(gmp_pool); if (gmp_work != NULL) xfree(gmp_work); gmp_pool = NULL; gmp_size = 0; gmp_work = NULL; return; } /*====================================================================*/ mpz_t _mpz_init(void) { /* initialize x, and set its value to 0 */ mpz_t x; x = gmp_get_atom(sizeof(struct mpz)); x->val = 0; x->ptr = NULL; return x; } void mpz_clear(mpz_t x) { /* free the space occupied by x */ mpz_set_si(x, 0); xassert(x->ptr == NULL); /* free the number descriptor */ gmp_free_atom(x, sizeof(struct mpz)); return; } void mpz_set(mpz_t z, mpz_t x) { /* set the value of z from x */ struct mpz_seg *e, *ee, *es; if (z != x) { mpz_set_si(z, 0); z->val = x->val; xassert(z->ptr == NULL); for (e = x->ptr, es = NULL; e != NULL; e = e->next) { ee = gmp_get_atom(sizeof(struct mpz_seg)); memcpy(ee->d, e->d, 12); ee->next = NULL; if (z->ptr == NULL) z->ptr = ee; else es->next = ee; es = ee; } } return; } void mpz_set_si(mpz_t x, int val) { /* set the value of x to val */ struct mpz_seg *e; /* free existing segments, if any */ while (x->ptr != NULL) { e = x->ptr; x->ptr = e->next; gmp_free_atom(e, sizeof(struct mpz_seg)); } /* assign new value */ if (val == 0x80000000) { /* long format is needed */ x->val = -1; x->ptr = e = gmp_get_atom(sizeof(struct mpz_seg)); memset(e->d, 0, 12); e->d[1] = 0x8000; e->next = NULL; } else { /* short format is enough */ x->val = val; } return; } double mpz_get_d(mpz_t x) { /* convert x to a double, truncating if necessary */ struct mpz_seg *e; int j; double val, deg; if (x->ptr == NULL) val = (double)x->val; else { xassert(x->val != 0); val = 0.0; deg = 1.0; for (e = x->ptr; e != NULL; e = e->next) { for (j = 0; j <= 5; j++) { val += deg * (double)((int)e->d[j]); deg *= 65536.0; } } if (x->val < 0) val = - val; } return val; } double mpz_get_d_2exp(int *exp, mpz_t x) { /* convert x to a double, truncating if necessary (i.e. rounding towards zero), and returning the exponent separately; the return value is in the range 0.5 <= |d| < 1 and the exponent is stored to *exp; d*2^exp is the (truncated) x value; if x is zero, the return is 0.0 and 0 is stored to *exp; this is similar to the standard C frexp function */ struct mpz_seg *e; int j, n, n1; double val; if (x->ptr == NULL) val = (double)x->val, n = 0; else { xassert(x->val != 0); val = 0.0, n = 0; for (e = x->ptr; e != NULL; e = e->next) { for (j = 0; j <= 5; j++) { val += (double)((int)e->d[j]); val /= 65536.0, n += 16; } } if (x->val < 0) val = - val; } val = frexp(val, &n1); *exp = n + n1; return val; } void mpz_swap(mpz_t x, mpz_t y) { /* swap the values x and y efficiently */ int val; void *ptr; val = x->val, ptr = x->ptr; x->val = y->val, x->ptr = y->ptr; y->val = val, y->ptr = ptr; return; } static void normalize(mpz_t x) { /* normalize integer x that includes removing non-significant (leading) zeros and converting to short format, if possible */ struct mpz_seg *es, *e; /* if the integer is in short format, it remains unchanged */ if (x->ptr == NULL) { xassert(x->val != 0x80000000); goto done; } xassert(x->val == +1 || x->val == -1); /* find the last (most significant) non-zero segment */ es = NULL; for (e = x->ptr; e != NULL; e = e->next) { if (e->d[0] || e->d[1] || e->d[2] || e->d[3] || e->d[4] || e->d[5]) es = e; } /* if all segments contain zeros, the integer is zero */ if (es == NULL) { mpz_set_si(x, 0); goto done; } /* remove non-significant (leading) zero segments */ while (es->next != NULL) { e = es->next; es->next = e->next; gmp_free_atom(e, sizeof(struct mpz_seg)); } /* convert the integer to short format, if possible */ e = x->ptr; if (e->next == NULL && e->d[1] <= 0x7FFF && !e->d[2] && !e->d[3] && !e->d[4] && !e->d[5]) { int val; val = (int)e->d[0] + ((int)e->d[1] << 16); if (x->val < 0) val = - val; mpz_set_si(x, val); } done: return; } void mpz_add(mpz_t z, mpz_t x, mpz_t y) { /* set z to x + y */ static struct mpz_seg zero = { { 0, 0, 0, 0, 0, 0 }, NULL }; struct mpz_seg dumx, dumy, *ex, *ey, *ez, *es, *ee; int k, sx, sy, sz; unsigned int t; /* if [x] = 0 then [z] = [y] */ if (x->val == 0) { xassert(x->ptr == NULL); mpz_set(z, y); goto done; } /* if [y] = 0 then [z] = [x] */ if (y->val == 0) { xassert(y->ptr == NULL); mpz_set(z, x); goto done; } /* special case when both [x] and [y] are in short format */ if (x->ptr == NULL && y->ptr == NULL) { int xval = x->val, yval = y->val, zval = x->val + y->val; xassert(xval != 0x80000000 && yval != 0x80000000); if (!(xval > 0 && yval > 0 && zval <= 0 || xval < 0 && yval < 0 && zval >= 0)) { mpz_set_si(z, zval); goto done; } } /* convert [x] to long format, if necessary */ if (x->ptr == NULL) { xassert(x->val != 0x80000000); if (x->val >= 0) { sx = +1; t = (unsigned int)(+ x->val); } else { sx = -1; t = (unsigned int)(- x->val); } ex = &dumx; ex->d[0] = (unsigned short)t; ex->d[1] = (unsigned short)(t >> 16); ex->d[2] = ex->d[3] = ex->d[4] = ex->d[5] = 0; ex->next = NULL; } else { sx = x->val; xassert(sx == +1 || sx == -1); ex = x->ptr; } /* convert [y] to long format, if necessary */ if (y->ptr == NULL) { xassert(y->val != 0x80000000); if (y->val >= 0) { sy = +1; t = (unsigned int)(+ y->val); } else { sy = -1; t = (unsigned int)(- y->val); } ey = &dumy; ey->d[0] = (unsigned short)t; ey->d[1] = (unsigned short)(t >> 16); ey->d[2] = ey->d[3] = ey->d[4] = ey->d[5] = 0; ey->next = NULL; } else { sy = y->val; xassert(sy == +1 || sy == -1); ey = y->ptr; } /* main fragment */ sz = sx; ez = es = NULL; if (sx > 0 && sy > 0 || sx < 0 && sy < 0) { /* [x] and [y] have identical signs -- addition */ t = 0; for (; ex || ey; ex = ex->next, ey = ey->next) { if (ex == NULL) ex = &zero; if (ey == NULL) ey = &zero; ee = gmp_get_atom(sizeof(struct mpz_seg)); for (k = 0; k <= 5; k++) { t += (unsigned int)ex->d[k]; t += (unsigned int)ey->d[k]; ee->d[k] = (unsigned short)t; t >>= 16; } ee->next = NULL; if (ez == NULL) ez = ee; else es->next = ee; es = ee; } if (t) { /* overflow -- one extra digit is needed */ ee = gmp_get_atom(sizeof(struct mpz_seg)); ee->d[0] = 1; ee->d[1] = ee->d[2] = ee->d[3] = ee->d[4] = ee->d[5] = 0; ee->next = NULL; xassert(es != NULL); es->next = ee; } } else { /* [x] and [y] have different signs -- subtraction */ t = 1; for (; ex || ey; ex = ex->next, ey = ey->next) { if (ex == NULL) ex = &zero; if (ey == NULL) ey = &zero; ee = gmp_get_atom(sizeof(struct mpz_seg)); for (k = 0; k <= 5; k++) { t += (unsigned int)ex->d[k]; t += (0xFFFF - (unsigned int)ey->d[k]); ee->d[k] = (unsigned short)t; t >>= 16; } ee->next = NULL; if (ez == NULL) ez = ee; else es->next = ee; es = ee; } if (!t) { /* |[x]| < |[y]| -- result in complement coding */ sz = - sz; t = 1; for (ee = ez; ee != NULL; ee = ee->next) for (k = 0; k <= 5; k++) { t += (0xFFFF - (unsigned int)ee->d[k]); ee->d[k] = (unsigned short)t; t >>= 16; } } } /* contruct and normalize result */ mpz_set_si(z, 0); z->val = sz; z->ptr = ez; normalize(z); done: return; } void mpz_sub(mpz_t z, mpz_t x, mpz_t y) { /* set z to x - y */ if (x == y) mpz_set_si(z, 0); else { y->val = - y->val; mpz_add(z, x, y); if (y != z) y->val = - y->val; } return; } void mpz_mul(mpz_t z, mpz_t x, mpz_t y) { /* set z to x * y */ struct mpz_seg dumx, dumy, *ex, *ey, *es, *e; int sx, sy, k, nx, ny, n; unsigned int t; unsigned short *work, *wx, *wy; /* if [x] = 0 then [z] = 0 */ if (x->val == 0) { xassert(x->ptr == NULL); mpz_set_si(z, 0); goto done; } /* if [y] = 0 then [z] = 0 */ if (y->val == 0) { xassert(y->ptr == NULL); mpz_set_si(z, 0); goto done; } /* special case when both [x] and [y] are in short format */ if (x->ptr == NULL && y->ptr == NULL) { int xval = x->val, yval = y->val, sz = +1; xassert(xval != 0x80000000 && yval != 0x80000000); if (xval < 0) xval = - xval, sz = - sz; if (yval < 0) yval = - yval, sz = - sz; if (xval <= 0x7FFFFFFF / yval) { mpz_set_si(z, sz * (xval * yval)); goto done; } } /* convert [x] to long format, if necessary */ if (x->ptr == NULL) { xassert(x->val != 0x80000000); if (x->val >= 0) { sx = +1; t = (unsigned int)(+ x->val); } else { sx = -1; t = (unsigned int)(- x->val); } ex = &dumx; ex->d[0] = (unsigned short)t; ex->d[1] = (unsigned short)(t >> 16); ex->d[2] = ex->d[3] = ex->d[4] = ex->d[5] = 0; ex->next = NULL; } else { sx = x->val; xassert(sx == +1 || sx == -1); ex = x->ptr; } /* convert [y] to long format, if necessary */ if (y->ptr == NULL) { xassert(y->val != 0x80000000); if (y->val >= 0) { sy = +1; t = (unsigned int)(+ y->val); } else { sy = -1; t = (unsigned int)(- y->val); } ey = &dumy; ey->d[0] = (unsigned short)t; ey->d[1] = (unsigned short)(t >> 16); ey->d[2] = ey->d[3] = ey->d[4] = ey->d[5] = 0; ey->next = NULL; } else { sy = y->val; xassert(sy == +1 || sy == -1); ey = y->ptr; } /* determine the number of digits of [x] */ nx = n = 0; for (e = ex; e != NULL; e = e->next) for (k = 0; k <= 5; k++) { n++; if (e->d[k]) nx = n; } xassert(nx > 0); /* determine the number of digits of [y] */ ny = n = 0; for (e = ey; e != NULL; e = e->next) for (k = 0; k <= 5; k++) { n++; if (e->d[k]) ny = n; } xassert(ny > 0); /* we need working array containing at least nx+ny+ny places */ work = gmp_get_work(nx+ny+ny); /* load digits of [x] */ wx = &work[0]; for (n = 0; n < nx; n++) wx[ny+n] = 0; for (n = 0, e = ex; e != NULL; e = e->next) for (k = 0; k <= 5; k++, n++) if (e->d[k]) wx[ny+n] = e->d[k]; /* load digits of [y] */ wy = &work[nx+ny]; for (n = 0; n < ny; n++) wy[n] = 0; for (n = 0, e = ey; e != NULL; e = e->next) for (k = 0; k <= 5; k++, n++) if (e->d[k]) wy[n] = e->d[k]; /* compute [x] * [y] */ bigmul(nx, ny, wx, wy); /* construct and normalize result */ mpz_set_si(z, 0); z->val = sx * sy; es = NULL; k = 6; for (n = 0; n < nx+ny; n++) { if (k > 5) { e = gmp_get_atom(sizeof(struct mpz_seg)); e->d[0] = e->d[1] = e->d[2] = 0; e->d[3] = e->d[4] = e->d[5] = 0; e->next = NULL; if (z->ptr == NULL) z->ptr = e; else es->next = e; es = e; k = 0; } es->d[k++] = wx[n]; } normalize(z); done: return; } void mpz_neg(mpz_t z, mpz_t x) { /* set z to 0 - x */ mpz_set(z, x); z->val = - z->val; return; } void mpz_abs(mpz_t z, mpz_t x) { /* set z to the absolute value of x */ mpz_set(z, x); if (z->val < 0) z->val = - z->val; return; } void mpz_div(mpz_t q, mpz_t r, mpz_t x, mpz_t y) { /* divide x by y, forming quotient q and/or remainder r if q = NULL then quotient is not stored; if r = NULL then remainder is not stored the sign of quotient is determined as in algebra while the sign of remainder is the same as the sign of dividend: +26 : +7 = +3, remainder is +5 -26 : +7 = -3, remainder is -5 +26 : -7 = -3, remainder is +5 -26 : -7 = +3, remainder is -5 */ struct mpz_seg dumx, dumy, *ex, *ey, *es, *e; int sx, sy, k, nx, ny, n; unsigned int t; unsigned short *work, *wx, *wy; /* divide by zero is not allowed */ if (y->val == 0) { xassert(y->ptr == NULL); xfault("mpz_div: divide by zero not allowed\n"); } /* if [x] = 0 then [q] = [r] = 0 */ if (x->val == 0) { xassert(x->ptr == NULL); if (q != NULL) mpz_set_si(q, 0); if (r != NULL) mpz_set_si(r, 0); goto done; } /* special case when both [x] and [y] are in short format */ if (x->ptr == NULL && y->ptr == NULL) { int xval = x->val, yval = y->val; xassert(xval != 0x80000000 && yval != 0x80000000); if (q != NULL) mpz_set_si(q, xval / yval); if (r != NULL) mpz_set_si(r, xval % yval); goto done; } /* convert [x] to long format, if necessary */ if (x->ptr == NULL) { xassert(x->val != 0x80000000); if (x->val >= 0) { sx = +1; t = (unsigned int)(+ x->val); } else { sx = -1; t = (unsigned int)(- x->val); } ex = &dumx; ex->d[0] = (unsigned short)t; ex->d[1] = (unsigned short)(t >> 16); ex->d[2] = ex->d[3] = ex->d[4] = ex->d[5] = 0; ex->next = NULL; } else { sx = x->val; xassert(sx == +1 || sx == -1); ex = x->ptr; } /* convert [y] to long format, if necessary */ if (y->ptr == NULL) { xassert(y->val != 0x80000000); if (y->val >= 0) { sy = +1; t = (unsigned int)(+ y->val); } else { sy = -1; t = (unsigned int)(- y->val); } ey = &dumy; ey->d[0] = (unsigned short)t; ey->d[1] = (unsigned short)(t >> 16); ey->d[2] = ey->d[3] = ey->d[4] = ey->d[5] = 0; ey->next = NULL; } else { sy = y->val; xassert(sy == +1 || sy == -1); ey = y->ptr; } /* determine the number of digits of [x] */ nx = n = 0; for (e = ex; e != NULL; e = e->next) for (k = 0; k <= 5; k++) { n++; if (e->d[k]) nx = n; } xassert(nx > 0); /* determine the number of digits of [y] */ ny = n = 0; for (e = ey; e != NULL; e = e->next) for (k = 0; k <= 5; k++) { n++; if (e->d[k]) ny = n; } xassert(ny > 0); /* if nx < ny then [q] = 0 and [r] = [x] */ if (nx < ny) { if (r != NULL) mpz_set(r, x); if (q != NULL) mpz_set_si(q, 0); goto done; } /* we need working array containing at least nx+ny+1 places */ work = gmp_get_work(nx+ny+1); /* load digits of [x] */ wx = &work[0]; for (n = 0; n < nx; n++) wx[n] = 0; for (n = 0, e = ex; e != NULL; e = e->next) for (k = 0; k <= 5; k++, n++) if (e->d[k]) wx[n] = e->d[k]; /* load digits of [y] */ wy = &work[nx+1]; for (n = 0; n < ny; n++) wy[n] = 0; for (n = 0, e = ey; e != NULL; e = e->next) for (k = 0; k <= 5; k++, n++) if (e->d[k]) wy[n] = e->d[k]; /* compute quotient and remainder */ xassert(wy[ny-1] != 0); bigdiv(nx-ny, ny, wx, wy); /* construct and normalize quotient */ if (q != NULL) { mpz_set_si(q, 0); q->val = sx * sy; es = NULL; k = 6; for (n = ny; n <= nx; n++) { if (k > 5) { e = gmp_get_atom(sizeof(struct mpz_seg)); e->d[0] = e->d[1] = e->d[2] = 0; e->d[3] = e->d[4] = e->d[5] = 0; e->next = NULL; if (q->ptr == NULL) q->ptr = e; else es->next = e; es = e; k = 0; } es->d[k++] = wx[n]; } normalize(q); } /* construct and normalize remainder */ if (r != NULL) { mpz_set_si(r, 0); r->val = sx; es = NULL; k = 6; for (n = 0; n < ny; n++) { if (k > 5) { e = gmp_get_atom(sizeof(struct mpz_seg)); e->d[0] = e->d[1] = e->d[2] = 0; e->d[3] = e->d[4] = e->d[5] = 0; e->next = NULL; if (r->ptr == NULL) r->ptr = e; else es->next = e; es = e; k = 0; } es->d[k++] = wx[n]; } normalize(r); } done: return; } void mpz_gcd(mpz_t z, mpz_t x, mpz_t y) { /* set z to the greatest common divisor of x and y */ /* in case of arbitrary integers GCD(x, y) = GCD(|x|, |y|), and, in particular, GCD(0, 0) = 0 */ mpz_t u, v, r; mpz_init(u); mpz_init(v); mpz_init(r); mpz_abs(u, x); mpz_abs(v, y); while (mpz_sgn(v)) { mpz_div(NULL, r, u, v); mpz_set(u, v); mpz_set(v, r); } mpz_set(z, u); mpz_clear(u); mpz_clear(v); mpz_clear(r); return; } int mpz_cmp(mpz_t x, mpz_t y) { /* compare x and y; return a positive value if x > y, zero if x = y, or a nefative value if x < y */ static struct mpz_seg zero = { { 0, 0, 0, 0, 0, 0 }, NULL }; struct mpz_seg dumx, dumy, *ex, *ey; int cc, sx, sy, k; unsigned int t; if (x == y) { cc = 0; goto done; } /* special case when both [x] and [y] are in short format */ if (x->ptr == NULL && y->ptr == NULL) { int xval = x->val, yval = y->val; xassert(xval != 0x80000000 && yval != 0x80000000); cc = (xval > yval ? +1 : xval < yval ? -1 : 0); goto done; } /* special case when [x] and [y] have different signs */ if (x->val > 0 && y->val <= 0 || x->val == 0 && y->val < 0) { cc = +1; goto done; } if (x->val < 0 && y->val >= 0 || x->val == 0 && y->val > 0) { cc = -1; goto done; } /* convert [x] to long format, if necessary */ if (x->ptr == NULL) { xassert(x->val != 0x80000000); if (x->val >= 0) { sx = +1; t = (unsigned int)(+ x->val); } else { sx = -1; t = (unsigned int)(- x->val); } ex = &dumx; ex->d[0] = (unsigned short)t; ex->d[1] = (unsigned short)(t >> 16); ex->d[2] = ex->d[3] = ex->d[4] = ex->d[5] = 0; ex->next = NULL; } else { sx = x->val; xassert(sx == +1 || sx == -1); ex = x->ptr; } /* convert [y] to long format, if necessary */ if (y->ptr == NULL) { xassert(y->val != 0x80000000); if (y->val >= 0) { sy = +1; t = (unsigned int)(+ y->val); } else { sy = -1; t = (unsigned int)(- y->val); } ey = &dumy; ey->d[0] = (unsigned short)t; ey->d[1] = (unsigned short)(t >> 16); ey->d[2] = ey->d[3] = ey->d[4] = ey->d[5] = 0; ey->next = NULL; } else { sy = y->val; xassert(sy == +1 || sy == -1); ey = y->ptr; } /* main fragment */ xassert(sx > 0 && sy > 0 || sx < 0 && sy < 0); cc = 0; for (; ex || ey; ex = ex->next, ey = ey->next) { if (ex == NULL) ex = &zero; if (ey == NULL) ey = &zero; for (k = 0; k <= 5; k++) { if (ex->d[k] > ey->d[k]) cc = +1; if (ex->d[k] < ey->d[k]) cc = -1; } } if (sx < 0) cc = - cc; done: return cc; } int mpz_sgn(mpz_t x) { /* return +1 if x > 0, 0 if x = 0, and -1 if x < 0 */ int s; s = (x->val > 0 ? +1 : x->val < 0 ? -1 : 0); return s; } int mpz_out_str(void *_fp, int base, mpz_t x) { /* output x on stream fp, as a string in given base; the base may vary from 2 to 36; return the number of bytes written, or if an error occurred, return 0 */ FILE *fp = _fp; mpz_t b, y, r; int n, j, nwr = 0; unsigned char *d; static char *set = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ"; if (!(2 <= base && base <= 36)) xfault("mpz_out_str: base = %d; invalid base\n", base); mpz_init(b); mpz_set_si(b, base); mpz_init(y); mpz_init(r); /* determine the number of digits */ mpz_abs(y, x); for (n = 0; mpz_sgn(y) != 0; n++) mpz_div(y, NULL, y, b); if (n == 0) n = 1; /* compute the digits */ d = xmalloc(n); mpz_abs(y, x); for (j = 0; j < n; j++) { mpz_div(y, r, y, b); xassert(0 <= r->val && r->val < base && r->ptr == NULL); d[j] = (unsigned char)r->val; } /* output the integer to the stream */ if (fp == NULL) fp = stdout; if (mpz_sgn(x) < 0) fputc('-', fp), nwr++; for (j = n-1; j >= 0; j--) fputc(set[d[j]], fp), nwr++; if (ferror(fp)) nwr = 0; mpz_clear(b); mpz_clear(y); mpz_clear(r); xfree(d); return nwr; } /*====================================================================*/ mpq_t _mpq_init(void) { /* initialize x, and set its value to 0/1 */ mpq_t x; x = gmp_get_atom(sizeof(struct mpq)); x->p.val = 0; x->p.ptr = NULL; x->q.val = 1; x->q.ptr = NULL; return x; } void mpq_clear(mpq_t x) { /* free the space occupied by x */ mpz_set_si(&x->p, 0); xassert(x->p.ptr == NULL); mpz_set_si(&x->q, 0); xassert(x->q.ptr == NULL); /* free the number descriptor */ gmp_free_atom(x, sizeof(struct mpq)); return; } void mpq_canonicalize(mpq_t x) { /* remove any factors that are common to the numerator and denominator of x, and make the denominator positive */ mpz_t f; xassert(x->q.val != 0); if (x->q.val < 0) { mpz_neg(&x->p, &x->p); mpz_neg(&x->q, &x->q); } mpz_init(f); mpz_gcd(f, &x->p, &x->q); if (!(f->val == 1 && f->ptr == NULL)) { mpz_div(&x->p, NULL, &x->p, f); mpz_div(&x->q, NULL, &x->q, f); } mpz_clear(f); return; } void mpq_set(mpq_t z, mpq_t x) { /* set the value of z from x */ if (z != x) { mpz_set(&z->p, &x->p); mpz_set(&z->q, &x->q); } return; } void mpq_set_si(mpq_t x, int p, unsigned int q) { /* set the value of x to p/q */ if (q == 0) xfault("mpq_set_si: zero denominator not allowed\n"); mpz_set_si(&x->p, p); xassert(q <= 0x7FFFFFFF); mpz_set_si(&x->q, q); return; } double mpq_get_d(mpq_t x) { /* convert x to a double, truncating if necessary */ int np, nq; double p, q; p = mpz_get_d_2exp(&np, &x->p); q = mpz_get_d_2exp(&nq, &x->q); return ldexp(p / q, np - nq); } void mpq_set_d(mpq_t x, double val) { /* set x to val; there is no rounding, the conversion is exact */ int s, n, d, j; double f; mpz_t temp; xassert(-DBL_MAX <= val && val <= +DBL_MAX); mpq_set_si(x, 0, 1); if (val > 0.0) s = +1; else if (val < 0.0) s = -1; else goto done; f = frexp(fabs(val), &n); /* |val| = f * 2^n, where 0.5 <= f < 1.0 */ mpz_init(temp); while (f != 0.0) { f *= 16.0, n -= 4; d = (int)f; xassert(0 <= d && d <= 15); f -= (double)d; /* x := 16 * x + d */ mpz_set_si(temp, 16); mpz_mul(&x->p, &x->p, temp); mpz_set_si(temp, d); mpz_add(&x->p, &x->p, temp); } mpz_clear(temp); /* x := x * 2^n */ if (n > 0) { for (j = 1; j <= n; j++) mpz_add(&x->p, &x->p, &x->p); } else if (n < 0) { for (j = 1; j <= -n; j++) mpz_add(&x->q, &x->q, &x->q); mpq_canonicalize(x); } if (s < 0) mpq_neg(x, x); done: return; } void mpq_add(mpq_t z, mpq_t x, mpq_t y) { /* set z to x + y */ mpz_t p, q; mpz_init(p); mpz_init(q); mpz_mul(p, &x->p, &y->q); mpz_mul(q, &x->q, &y->p); mpz_add(p, p, q); mpz_mul(q, &x->q, &y->q); mpz_set(&z->p, p); mpz_set(&z->q, q); mpz_clear(p); mpz_clear(q); mpq_canonicalize(z); return; } void mpq_sub(mpq_t z, mpq_t x, mpq_t y) { /* set z to x - y */ mpz_t p, q; mpz_init(p); mpz_init(q); mpz_mul(p, &x->p, &y->q); mpz_mul(q, &x->q, &y->p); mpz_sub(p, p, q); mpz_mul(q, &x->q, &y->q); mpz_set(&z->p, p); mpz_set(&z->q, q); mpz_clear(p); mpz_clear(q); mpq_canonicalize(z); return; } void mpq_mul(mpq_t z, mpq_t x, mpq_t y) { /* set z to x * y */ mpz_mul(&z->p, &x->p, &y->p); mpz_mul(&z->q, &x->q, &y->q); mpq_canonicalize(z); return; } void mpq_div(mpq_t z, mpq_t x, mpq_t y) { /* set z to x / y */ mpz_t p, q; if (mpq_sgn(y) == 0) xfault("mpq_div: zero divisor not allowed\n"); mpz_init(p); mpz_init(q); mpz_mul(p, &x->p, &y->q); mpz_mul(q, &x->q, &y->p); mpz_set(&z->p, p); mpz_set(&z->q, q); mpz_clear(p); mpz_clear(q); mpq_canonicalize(z); return; } void mpq_neg(mpq_t z, mpq_t x) { /* set z to 0 - x */ mpq_set(z, x); mpz_neg(&z->p, &z->p); return; } void mpq_abs(mpq_t z, mpq_t x) { /* set z to the absolute value of x */ mpq_set(z, x); mpz_abs(&z->p, &z->p); xassert(mpz_sgn(&x->q) > 0); return; } int mpq_cmp(mpq_t x, mpq_t y) { /* compare x and y; return a positive value if x > y, zero if x = y, or a nefative value if x < y */ mpq_t temp; int s; mpq_init(temp); mpq_sub(temp, x, y); s = mpq_sgn(temp); mpq_clear(temp); return s; } int mpq_sgn(mpq_t x) { /* return +1 if x > 0, 0 if x = 0, and -1 if x < 0 */ int s; s = mpz_sgn(&x->p); xassert(mpz_sgn(&x->q) > 0); return s; } int mpq_out_str(void *_fp, int base, mpq_t x) { /* output x on stream fp, as a string in given base; the base may vary from 2 to 36; output is in the form 'num/den' or if the denominator is 1 then just 'num'; if the parameter fp is a null pointer, stdout is assumed; return the number of bytes written, or if an error occurred, return 0 */ FILE *fp = _fp; int nwr; if (!(2 <= base && base <= 36)) xfault("mpq_out_str: base = %d; invalid base\n", base); if (fp == NULL) fp = stdout; nwr = mpz_out_str(fp, base, &x->p); if (x->q.val == 1 && x->q.ptr == NULL) ; else { fputc('/', fp), nwr++; nwr += mpz_out_str(fp, base, &x->q); } if (ferror(fp)) nwr = 0; return nwr; } #endif /* eof */ sources_5316/external/glpk/colamd.c0000644000176700017670000037005211401660400016104 0ustar paulpaul/* ========================================================================== */ /* === colamd/symamd - a sparse matrix column ordering algorithm ============ */ /* ========================================================================== */ /* COLAMD / SYMAMD colamd: an approximate minimum degree column ordering algorithm, for LU factorization of symmetric or unsymmetric matrices, QR factorization, least squares, interior point methods for linear programming problems, and other related problems. symamd: an approximate minimum degree ordering algorithm for Cholesky factorization of symmetric matrices. Purpose: Colamd computes a permutation Q such that the Cholesky factorization of (AQ)'(AQ) has less fill-in and requires fewer floating point operations than A'A. This also provides a good ordering for sparse partial pivoting methods, P(AQ) = LU, where Q is computed prior to numerical factorization, and P is computed during numerical factorization via conventional partial pivoting with row interchanges. Colamd is the column ordering method used in SuperLU, part of the ScaLAPACK library. It is also available as built-in function in MATLAB Version 6, available from MathWorks, Inc. (http://www.mathworks.com). This routine can be used in place of colmmd in MATLAB. Symamd computes a permutation P of a symmetric matrix A such that the Cholesky factorization of PAP' has less fill-in and requires fewer floating point operations than A. Symamd constructs a matrix M such that M'M has the same nonzero pattern of A, and then orders the columns of M using colmmd. The column ordering of M is then returned as the row and column ordering P of A. Authors: The authors of the code itself are Stefan I. Larimore and Timothy A. Davis (davis at cise.ufl.edu), University of Florida. The algorithm was developed in collaboration with John Gilbert, Xerox PARC, and Esmond Ng, Oak Ridge National Laboratory. Acknowledgements: This work was supported by the National Science Foundation, under grants DMS-9504974 and DMS-9803599. Copyright and License: Copyright (c) 1998-2007, Timothy A. Davis, All Rights Reserved. COLAMD is also available under alternate licenses, contact T. Davis for details. This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA Permission is hereby granted to use or copy this program under the terms of the GNU LGPL, provided that the Copyright, this License, and the Availability of the original version is retained on all copies. User documentation of any code that uses this code or any modified version of this code must cite the Copyright, this License, the Availability note, and "Used by permission." Permission to modify the code and to distribute modified code is granted, provided the Copyright, this License, and the Availability note are retained, and a notice that the code was modified is included. Availability: The colamd/symamd library is available at http://www.cise.ufl.edu/research/sparse/colamd/ This is the http://www.cise.ufl.edu/research/sparse/colamd/colamd.c file. It requires the colamd.h file. It is required by the colamdmex.c and symamdmex.c files, for the MATLAB interface to colamd and symamd. Appears as ACM Algorithm 836. See the ChangeLog file for changes since Version 1.0. References: T. A. Davis, J. R. Gilbert, S. Larimore, E. Ng, An approximate column minimum degree ordering algorithm, ACM Transactions on Mathematical Software, vol. 30, no. 3., pp. 353-376, 2004. T. A. Davis, J. R. Gilbert, S. Larimore, E. Ng, Algorithm 836: COLAMD, an approximate column minimum degree ordering algorithm, ACM Transactions on Mathematical Software, vol. 30, no. 3., pp. 377-380, 2004. */ /* ========================================================================== */ /* === Description of user-callable routines ================================ */ /* ========================================================================== */ /* COLAMD includes both int and UF_long versions of all its routines. The * description below is for the int version. For UF_long, all int arguments * become UF_long. UF_long is normally defined as long, except for WIN64. ---------------------------------------------------------------------------- colamd_recommended: ---------------------------------------------------------------------------- C syntax: #include "colamd.h" size_t colamd_recommended (int nnz, int n_row, int n_col) ; size_t colamd_l_recommended (UF_long nnz, UF_long n_row, UF_long n_col) ; Purpose: Returns recommended value of Alen for use by colamd. Returns 0 if any input argument is negative. The use of this routine is optional. Not needed for symamd, which dynamically allocates its own memory. Note that in v2.4 and earlier, these routines returned int or long. They now return a value of type size_t. Arguments (all input arguments): int nnz ; Number of nonzeros in the matrix A. This must be the same value as p [n_col] in the call to colamd - otherwise you will get a wrong value of the recommended memory to use. int n_row ; Number of rows in the matrix A. int n_col ; Number of columns in the matrix A. ---------------------------------------------------------------------------- colamd_set_defaults: ---------------------------------------------------------------------------- C syntax: #include "colamd.h" colamd_set_defaults (double knobs [COLAMD_KNOBS]) ; colamd_l_set_defaults (double knobs [COLAMD_KNOBS]) ; Purpose: Sets the default parameters. The use of this routine is optional. Arguments: double knobs [COLAMD_KNOBS] ; Output only. NOTE: the meaning of the dense row/col knobs has changed in v2.4 knobs [0] and knobs [1] control dense row and col detection: Colamd: rows with more than max (16, knobs [COLAMD_DENSE_ROW] * sqrt (n_col)) entries are removed prior to ordering. Columns with more than max (16, knobs [COLAMD_DENSE_COL] * sqrt (MIN (n_row,n_col))) entries are removed prior to ordering, and placed last in the output column ordering. Symamd: uses only knobs [COLAMD_DENSE_ROW], which is knobs [0]. Rows and columns with more than max (16, knobs [COLAMD_DENSE_ROW] * sqrt (n)) entries are removed prior to ordering, and placed last in the output ordering. COLAMD_DENSE_ROW and COLAMD_DENSE_COL are defined as 0 and 1, respectively, in colamd.h. Default values of these two knobs are both 10. Currently, only knobs [0] and knobs [1] are used, but future versions may use more knobs. If so, they will be properly set to their defaults by the future version of colamd_set_defaults, so that the code that calls colamd will not need to change, assuming that you either use colamd_set_defaults, or pass a (double *) NULL pointer as the knobs array to colamd or symamd. knobs [2]: aggressive absorption knobs [COLAMD_AGGRESSIVE] controls whether or not to do aggressive absorption during the ordering. Default is TRUE. ---------------------------------------------------------------------------- colamd: ---------------------------------------------------------------------------- C syntax: #include "colamd.h" int colamd (int n_row, int n_col, int Alen, int *A, int *p, double knobs [COLAMD_KNOBS], int stats [COLAMD_STATS]) ; UF_long colamd_l (UF_long n_row, UF_long n_col, UF_long Alen, UF_long *A, UF_long *p, double knobs [COLAMD_KNOBS], UF_long stats [COLAMD_STATS]) ; Purpose: Computes a column ordering (Q) of A such that P(AQ)=LU or (AQ)'AQ=LL' have less fill-in and require fewer floating point operations than factorizing the unpermuted matrix A or A'A, respectively. Returns: TRUE (1) if successful, FALSE (0) otherwise. Arguments: int n_row ; Input argument. Number of rows in the matrix A. Restriction: n_row >= 0. Colamd returns FALSE if n_row is negative. int n_col ; Input argument. Number of columns in the matrix A. Restriction: n_col >= 0. Colamd returns FALSE if n_col is negative. int Alen ; Input argument. Restriction (see note): Alen >= 2*nnz + 6*(n_col+1) + 4*(n_row+1) + n_col Colamd returns FALSE if these conditions are not met. Note: this restriction makes an modest assumption regarding the size of the two typedef's structures in colamd.h. We do, however, guarantee that Alen >= colamd_recommended (nnz, n_row, n_col) will be sufficient. Note: the macro version does not check for integer overflow, and thus is not recommended. Use the colamd_recommended routine instead. int A [Alen] ; Input argument, undefined on output. A is an integer array of size Alen. Alen must be at least as large as the bare minimum value given above, but this is very low, and can result in excessive run time. For best performance, we recommend that Alen be greater than or equal to colamd_recommended (nnz, n_row, n_col), which adds nnz/5 to the bare minimum value given above. On input, the row indices of the entries in column c of the matrix are held in A [(p [c]) ... (p [c+1]-1)]. The row indices in a given column c need not be in ascending order, and duplicate row indices may be be present. However, colamd will work a little faster if both of these conditions are met (Colamd puts the matrix into this format, if it finds that the the conditions are not met). The matrix is 0-based. That is, rows are in the range 0 to n_row-1, and columns are in the range 0 to n_col-1. Colamd returns FALSE if any row index is out of range. The contents of A are modified during ordering, and are undefined on output. int p [n_col+1] ; Both input and output argument. p is an integer array of size n_col+1. On input, it holds the "pointers" for the column form of the matrix A. Column c of the matrix A is held in A [(p [c]) ... (p [c+1]-1)]. The first entry, p [0], must be zero, and p [c] <= p [c+1] must hold for all c in the range 0 to n_col-1. The value p [n_col] is thus the total number of entries in the pattern of the matrix A. Colamd returns FALSE if these conditions are not met. On output, if colamd returns TRUE, the array p holds the column permutation (Q, for P(AQ)=LU or (AQ)'(AQ)=LL'), where p [0] is the first column index in the new ordering, and p [n_col-1] is the last. That is, p [k] = j means that column j of A is the kth pivot column, in AQ, where k is in the range 0 to n_col-1 (p [0] = j means that column j of A is the first column in AQ). If colamd returns FALSE, then no permutation is returned, and p is undefined on output. double knobs [COLAMD_KNOBS] ; Input argument. See colamd_set_defaults for a description. int stats [COLAMD_STATS] ; Output argument. Statistics on the ordering, and error status. See colamd.h for related definitions. Colamd returns FALSE if stats is not present. stats [0]: number of dense or empty rows ignored. stats [1]: number of dense or empty columns ignored (and ordered last in the output permutation p) Note that a row can become "empty" if it contains only "dense" and/or "empty" columns, and similarly a column can become "empty" if it only contains "dense" and/or "empty" rows. stats [2]: number of garbage collections performed. This can be excessively high if Alen is close to the minimum required value. stats [3]: status code. < 0 is an error code. > 1 is a warning or notice. 0 OK. Each column of the input matrix contained row indices in increasing order, with no duplicates. 1 OK, but columns of input matrix were jumbled (unsorted columns or duplicate entries). Colamd had to do some extra work to sort the matrix first and remove duplicate entries, but it still was able to return a valid permutation (return value of colamd was TRUE). stats [4]: highest numbered column that is unsorted or has duplicate entries. stats [5]: last seen duplicate or unsorted row index. stats [6]: number of duplicate or unsorted row indices. -1 A is a null pointer -2 p is a null pointer -3 n_row is negative stats [4]: n_row -4 n_col is negative stats [4]: n_col -5 number of nonzeros in matrix is negative stats [4]: number of nonzeros, p [n_col] -6 p [0] is nonzero stats [4]: p [0] -7 A is too small stats [4]: required size stats [5]: actual size (Alen) -8 a column has a negative number of entries stats [4]: column with < 0 entries stats [5]: number of entries in col -9 a row index is out of bounds stats [4]: column with bad row index stats [5]: bad row index stats [6]: n_row, # of rows of matrx -10 (unused; see symamd.c) -999 (unused; see symamd.c) Future versions may return more statistics in the stats array. Example: See http://www.cise.ufl.edu/research/sparse/colamd/example.c for a complete example. To order the columns of a 5-by-4 matrix with 11 nonzero entries in the following nonzero pattern x 0 x 0 x 0 x x 0 x x 0 0 0 x x x x 0 0 with default knobs and no output statistics, do the following: #include "colamd.h" #define ALEN 100 int A [ALEN] = {0, 1, 4, 2, 4, 0, 1, 2, 3, 1, 3} ; int p [ ] = {0, 3, 5, 9, 11} ; int stats [COLAMD_STATS] ; colamd (5, 4, ALEN, A, p, (double *) NULL, stats) ; The permutation is returned in the array p, and A is destroyed. ---------------------------------------------------------------------------- symamd: ---------------------------------------------------------------------------- C syntax: #include "colamd.h" int symamd (int n, int *A, int *p, int *perm, double knobs [COLAMD_KNOBS], int stats [COLAMD_STATS], void (*allocate) (size_t, size_t), void (*release) (void *)) ; UF_long symamd_l (UF_long n, UF_long *A, UF_long *p, UF_long *perm, double knobs [COLAMD_KNOBS], UF_long stats [COLAMD_STATS], void (*allocate) (size_t, size_t), void (*release) (void *)) ; Purpose: The symamd routine computes an ordering P of a symmetric sparse matrix A such that the Cholesky factorization PAP' = LL' remains sparse. It is based on a column ordering of a matrix M constructed so that the nonzero pattern of M'M is the same as A. The matrix A is assumed to be symmetric; only the strictly lower triangular part is accessed. You must pass your selected memory allocator (usually calloc/free or mxCalloc/mxFree) to symamd, for it to allocate memory for the temporary matrix M. Returns: TRUE (1) if successful, FALSE (0) otherwise. Arguments: int n ; Input argument. Number of rows and columns in the symmetrix matrix A. Restriction: n >= 0. Symamd returns FALSE if n is negative. int A [nnz] ; Input argument. A is an integer array of size nnz, where nnz = p [n]. The row indices of the entries in column c of the matrix are held in A [(p [c]) ... (p [c+1]-1)]. The row indices in a given column c need not be in ascending order, and duplicate row indices may be present. However, symamd will run faster if the columns are in sorted order with no duplicate entries. The matrix is 0-based. That is, rows are in the range 0 to n-1, and columns are in the range 0 to n-1. Symamd returns FALSE if any row index is out of range. The contents of A are not modified. int p [n+1] ; Input argument. p is an integer array of size n+1. On input, it holds the "pointers" for the column form of the matrix A. Column c of the matrix A is held in A [(p [c]) ... (p [c+1]-1)]. The first entry, p [0], must be zero, and p [c] <= p [c+1] must hold for all c in the range 0 to n-1. The value p [n] is thus the total number of entries in the pattern of the matrix A. Symamd returns FALSE if these conditions are not met. The contents of p are not modified. int perm [n+1] ; Output argument. On output, if symamd returns TRUE, the array perm holds the permutation P, where perm [0] is the first index in the new ordering, and perm [n-1] is the last. That is, perm [k] = j means that row and column j of A is the kth column in PAP', where k is in the range 0 to n-1 (perm [0] = j means that row and column j of A are the first row and column in PAP'). The array is used as a workspace during the ordering, which is why it must be of length n+1, not just n. double knobs [COLAMD_KNOBS] ; Input argument. See colamd_set_defaults for a description. int stats [COLAMD_STATS] ; Output argument. Statistics on the ordering, and error status. See colamd.h for related definitions. Symamd returns FALSE if stats is not present. stats [0]: number of dense or empty row and columns ignored (and ordered last in the output permutation perm). Note that a row/column can become "empty" if it contains only "dense" and/or "empty" columns/rows. stats [1]: (same as stats [0]) stats [2]: number of garbage collections performed. stats [3]: status code. < 0 is an error code. > 1 is a warning or notice. 0 OK. Each column of the input matrix contained row indices in increasing order, with no duplicates. 1 OK, but columns of input matrix were jumbled (unsorted columns or duplicate entries). Symamd had to do some extra work to sort the matrix first and remove duplicate entries, but it still was able to return a valid permutation (return value of symamd was TRUE). stats [4]: highest numbered column that is unsorted or has duplicate entries. stats [5]: last seen duplicate or unsorted row index. stats [6]: number of duplicate or unsorted row indices. -1 A is a null pointer -2 p is a null pointer -3 (unused, see colamd.c) -4 n is negative stats [4]: n -5 number of nonzeros in matrix is negative stats [4]: # of nonzeros (p [n]). -6 p [0] is nonzero stats [4]: p [0] -7 (unused) -8 a column has a negative number of entries stats [4]: column with < 0 entries stats [5]: number of entries in col -9 a row index is out of bounds stats [4]: column with bad row index stats [5]: bad row index stats [6]: n_row, # of rows of matrx -10 out of memory (unable to allocate temporary workspace for M or count arrays using the "allocate" routine passed into symamd). Future versions may return more statistics in the stats array. void * (*allocate) (size_t, size_t) A pointer to a function providing memory allocation. The allocated memory must be returned initialized to zero. For a C application, this argument should normally be a pointer to calloc. For a MATLAB mexFunction, the routine mxCalloc is passed instead. void (*release) (size_t, size_t) A pointer to a function that frees memory allocated by the memory allocation routine above. For a C application, this argument should normally be a pointer to free. For a MATLAB mexFunction, the routine mxFree is passed instead. ---------------------------------------------------------------------------- colamd_report: ---------------------------------------------------------------------------- C syntax: #include "colamd.h" colamd_report (int stats [COLAMD_STATS]) ; colamd_l_report (UF_long stats [COLAMD_STATS]) ; Purpose: Prints the error status and statistics recorded in the stats array on the standard error output (for a standard C routine) or on the MATLAB output (for a mexFunction). Arguments: int stats [COLAMD_STATS] ; Input only. Statistics from colamd. ---------------------------------------------------------------------------- symamd_report: ---------------------------------------------------------------------------- C syntax: #include "colamd.h" symamd_report (int stats [COLAMD_STATS]) ; symamd_l_report (UF_long stats [COLAMD_STATS]) ; Purpose: Prints the error status and statistics recorded in the stats array on the standard error output (for a standard C routine) or on the MATLAB output (for a mexFunction). Arguments: int stats [COLAMD_STATS] ; Input only. Statistics from symamd. */ /* ========================================================================== */ /* === Scaffolding code definitions ======================================== */ /* ========================================================================== */ /* Ensure that debugging is turned off: */ #ifndef NDEBUG #define NDEBUG #endif /* turn on debugging by uncommenting the following line #undef NDEBUG */ /* Our "scaffolding code" philosophy: In our opinion, well-written library code should keep its "debugging" code, and just normally have it turned off by the compiler so as not to interfere with performance. This serves several purposes: (1) assertions act as comments to the reader, telling you what the code expects at that point. All assertions will always be true (unless there really is a bug, of course). (2) leaving in the scaffolding code assists anyone who would like to modify the code, or understand the algorithm (by reading the debugging output, one can get a glimpse into what the code is doing). (3) (gasp!) for actually finding bugs. This code has been heavily tested and "should" be fully functional and bug-free ... but you never know... The code will become outrageously slow when debugging is enabled. To control the level of debugging output, set an environment variable D to 0 (little), 1 (some), 2, 3, or 4 (lots). When debugging, you should see the following message on the standard output: colamd: debug version, D = 1 (THIS WILL BE SLOW!) or a similar message for symamd. If you don't, then debugging has not been enabled. */ /* ========================================================================== */ /* === Include files ======================================================== */ /* ========================================================================== */ #include "colamd.h" #if 0 /* by mao */ #include #include #ifdef MATLAB_MEX_FILE #include "mex.h" #include "matrix.h" #endif /* MATLAB_MEX_FILE */ #if !defined (NPRINT) || !defined (NDEBUG) #include #endif #ifndef NULL #define NULL ((void *) 0) #endif #endif /* ========================================================================== */ /* === int or UF_long ======================================================= */ /* ========================================================================== */ #if 0 /* by mao */ /* define UF_long */ #include "UFconfig.h" #endif #ifdef DLONG #define Int UF_long #define ID UF_long_id #define Int_MAX UF_long_max #define COLAMD_recommended colamd_l_recommended #define COLAMD_set_defaults colamd_l_set_defaults #define COLAMD_MAIN colamd_l #define SYMAMD_MAIN symamd_l #define COLAMD_report colamd_l_report #define SYMAMD_report symamd_l_report #else #define Int int #define ID "%d" #define Int_MAX INT_MAX #define COLAMD_recommended colamd_recommended #define COLAMD_set_defaults colamd_set_defaults #define COLAMD_MAIN colamd #define SYMAMD_MAIN symamd #define COLAMD_report colamd_report #define SYMAMD_report symamd_report #endif /* ========================================================================== */ /* === Row and Column structures ============================================ */ /* ========================================================================== */ /* User code that makes use of the colamd/symamd routines need not directly */ /* reference these structures. They are used only for colamd_recommended. */ typedef struct Colamd_Col_struct { Int start ; /* index for A of first row in this column, or DEAD */ /* if column is dead */ Int length ; /* number of rows in this column */ union { Int thickness ; /* number of original columns represented by this */ /* col, if the column is alive */ Int parent ; /* parent in parent tree super-column structure, if */ /* the column is dead */ } shared1 ; union { Int score ; /* the score used to maintain heap, if col is alive */ Int order ; /* pivot ordering of this column, if col is dead */ } shared2 ; union { Int headhash ; /* head of a hash bucket, if col is at the head of */ /* a degree list */ Int hash ; /* hash value, if col is not in a degree list */ Int prev ; /* previous column in degree list, if col is in a */ /* degree list (but not at the head of a degree list) */ } shared3 ; union { Int degree_next ; /* next column, if col is in a degree list */ Int hash_next ; /* next column, if col is in a hash list */ } shared4 ; } Colamd_Col ; typedef struct Colamd_Row_struct { Int start ; /* index for A of first col in this row */ Int length ; /* number of principal columns in this row */ union { Int degree ; /* number of principal & non-principal columns in row */ Int p ; /* used as a row pointer in init_rows_cols () */ } shared1 ; union { Int mark ; /* for computing set differences and marking dead rows*/ Int first_column ;/* first column in row (used in garbage collection) */ } shared2 ; } Colamd_Row ; /* ========================================================================== */ /* === Definitions ========================================================== */ /* ========================================================================== */ /* Routines are either PUBLIC (user-callable) or PRIVATE (not user-callable) */ #define PUBLIC #define PRIVATE static #define DENSE_DEGREE(alpha,n) \ ((Int) MAX (16.0, (alpha) * sqrt ((double) (n)))) #define MAX(a,b) (((a) > (b)) ? (a) : (b)) #define MIN(a,b) (((a) < (b)) ? (a) : (b)) #define ONES_COMPLEMENT(r) (-(r)-1) /* -------------------------------------------------------------------------- */ /* Change for version 2.1: define TRUE and FALSE only if not yet defined */ /* -------------------------------------------------------------------------- */ #ifndef TRUE #define TRUE (1) #endif #ifndef FALSE #define FALSE (0) #endif /* -------------------------------------------------------------------------- */ #define EMPTY (-1) /* Row and column status */ #define ALIVE (0) #define DEAD (-1) /* Column status */ #define DEAD_PRINCIPAL (-1) #define DEAD_NON_PRINCIPAL (-2) /* Macros for row and column status update and checking. */ #define ROW_IS_DEAD(r) ROW_IS_MARKED_DEAD (Row[r].shared2.mark) #define ROW_IS_MARKED_DEAD(row_mark) (row_mark < ALIVE) #define ROW_IS_ALIVE(r) (Row [r].shared2.mark >= ALIVE) #define COL_IS_DEAD(c) (Col [c].start < ALIVE) #define COL_IS_ALIVE(c) (Col [c].start >= ALIVE) #define COL_IS_DEAD_PRINCIPAL(c) (Col [c].start == DEAD_PRINCIPAL) #define KILL_ROW(r) { Row [r].shared2.mark = DEAD ; } #define KILL_PRINCIPAL_COL(c) { Col [c].start = DEAD_PRINCIPAL ; } #define KILL_NON_PRINCIPAL_COL(c) { Col [c].start = DEAD_NON_PRINCIPAL ; } /* ========================================================================== */ /* === Colamd reporting mechanism =========================================== */ /* ========================================================================== */ #if defined (MATLAB_MEX_FILE) || defined (MATHWORKS) /* In MATLAB, matrices are 1-based to the user, but 0-based internally */ #define INDEX(i) ((i)+1) #else /* In C, matrices are 0-based and indices are reported as such in *_report */ #define INDEX(i) (i) #endif /* All output goes through the PRINTF macro. */ #define PRINTF(params) { if (colamd_printf != NULL) (void) colamd_printf params ; } /* ========================================================================== */ /* === Prototypes of PRIVATE routines ======================================= */ /* ========================================================================== */ PRIVATE Int init_rows_cols ( Int n_row, Int n_col, Colamd_Row Row [], Colamd_Col Col [], Int A [], Int p [], Int stats [COLAMD_STATS] ) ; PRIVATE void init_scoring ( Int n_row, Int n_col, Colamd_Row Row [], Colamd_Col Col [], Int A [], Int head [], double knobs [COLAMD_KNOBS], Int *p_n_row2, Int *p_n_col2, Int *p_max_deg ) ; PRIVATE Int find_ordering ( Int n_row, Int n_col, Int Alen, Colamd_Row Row [], Colamd_Col Col [], Int A [], Int head [], Int n_col2, Int max_deg, Int pfree, Int aggressive ) ; PRIVATE void order_children ( Int n_col, Colamd_Col Col [], Int p [] ) ; PRIVATE void detect_super_cols ( #ifndef NDEBUG Int n_col, Colamd_Row Row [], #endif /* NDEBUG */ Colamd_Col Col [], Int A [], Int head [], Int row_start, Int row_length ) ; PRIVATE Int garbage_collection ( Int n_row, Int n_col, Colamd_Row Row [], Colamd_Col Col [], Int A [], Int *pfree ) ; PRIVATE Int clear_mark ( Int tag_mark, Int max_mark, Int n_row, Colamd_Row Row [] ) ; PRIVATE void print_report ( char *method, Int stats [COLAMD_STATS] ) ; /* ========================================================================== */ /* === Debugging prototypes and definitions ================================= */ /* ========================================================================== */ #ifndef NDEBUG #if 0 /* by mao */ #include #endif /* colamd_debug is the *ONLY* global variable, and is only */ /* present when debugging */ PRIVATE Int colamd_debug = 0 ; /* debug print level */ #define DEBUG0(params) { PRINTF (params) ; } #define DEBUG1(params) { if (colamd_debug >= 1) PRINTF (params) ; } #define DEBUG2(params) { if (colamd_debug >= 2) PRINTF (params) ; } #define DEBUG3(params) { if (colamd_debug >= 3) PRINTF (params) ; } #define DEBUG4(params) { if (colamd_debug >= 4) PRINTF (params) ; } #if 0 /* by mao */ #ifdef MATLAB_MEX_FILE #define ASSERT(expression) (mxAssert ((expression), "")) #else #define ASSERT(expression) (assert (expression)) #endif /* MATLAB_MEX_FILE */ #else #define ASSERT xassert #endif PRIVATE void colamd_get_debug /* gets the debug print level from getenv */ ( char *method ) ; PRIVATE void debug_deg_lists ( Int n_row, Int n_col, Colamd_Row Row [], Colamd_Col Col [], Int head [], Int min_score, Int should, Int max_deg ) ; PRIVATE void debug_mark ( Int n_row, Colamd_Row Row [], Int tag_mark, Int max_mark ) ; PRIVATE void debug_matrix ( Int n_row, Int n_col, Colamd_Row Row [], Colamd_Col Col [], Int A [] ) ; PRIVATE void debug_structures ( Int n_row, Int n_col, Colamd_Row Row [], Colamd_Col Col [], Int A [], Int n_col2 ) ; #else /* NDEBUG */ /* === No debugging ========================================================= */ #define DEBUG0(params) ; #define DEBUG1(params) ; #define DEBUG2(params) ; #define DEBUG3(params) ; #define DEBUG4(params) ; #define ASSERT(expression) #endif /* NDEBUG */ /* ========================================================================== */ /* === USER-CALLABLE ROUTINES: ============================================== */ /* ========================================================================== */ /* ========================================================================== */ /* === colamd_recommended =================================================== */ /* ========================================================================== */ /* The colamd_recommended routine returns the suggested size for Alen. This value has been determined to provide good balance between the number of garbage collections and the memory requirements for colamd. If any argument is negative, or if integer overflow occurs, a 0 is returned as an error condition. 2*nnz space is required for the row and column indices of the matrix. COLAMD_C (n_col) + COLAMD_R (n_row) space is required for the Col and Row arrays, respectively, which are internal to colamd (roughly 6*n_col + 4*n_row). An additional n_col space is the minimal amount of "elbow room", and nnz/5 more space is recommended for run time efficiency. Alen is approximately 2.2*nnz + 7*n_col + 4*n_row + 10. This function is not needed when using symamd. */ /* add two values of type size_t, and check for integer overflow */ static size_t t_add (size_t a, size_t b, int *ok) { (*ok) = (*ok) && ((a + b) >= MAX (a,b)) ; return ((*ok) ? (a + b) : 0) ; } /* compute a*k where k is a small integer, and check for integer overflow */ static size_t t_mult (size_t a, size_t k, int *ok) { size_t i, s = 0 ; for (i = 0 ; i < k ; i++) { s = t_add (s, a, ok) ; } return (s) ; } /* size of the Col and Row structures */ #define COLAMD_C(n_col,ok) \ ((t_mult (t_add (n_col, 1, ok), sizeof (Colamd_Col), ok) / sizeof (Int))) #define COLAMD_R(n_row,ok) \ ((t_mult (t_add (n_row, 1, ok), sizeof (Colamd_Row), ok) / sizeof (Int))) PUBLIC size_t COLAMD_recommended /* returns recommended value of Alen. */ ( /* === Parameters ======================================================= */ Int nnz, /* number of nonzeros in A */ Int n_row, /* number of rows in A */ Int n_col /* number of columns in A */ ) { size_t s, c, r ; int ok = TRUE ; if (nnz < 0 || n_row < 0 || n_col < 0) { return (0) ; } s = t_mult (nnz, 2, &ok) ; /* 2*nnz */ c = COLAMD_C (n_col, &ok) ; /* size of column structures */ r = COLAMD_R (n_row, &ok) ; /* size of row structures */ s = t_add (s, c, &ok) ; s = t_add (s, r, &ok) ; s = t_add (s, n_col, &ok) ; /* elbow room */ s = t_add (s, nnz/5, &ok) ; /* elbow room */ ok = ok && (s < Int_MAX) ; return (ok ? s : 0) ; } /* ========================================================================== */ /* === colamd_set_defaults ================================================== */ /* ========================================================================== */ /* The colamd_set_defaults routine sets the default values of the user- controllable parameters for colamd and symamd: Colamd: rows with more than max (16, knobs [0] * sqrt (n_col)) entries are removed prior to ordering. Columns with more than max (16, knobs [1] * sqrt (MIN (n_row,n_col))) entries are removed prior to ordering, and placed last in the output column ordering. Symamd: Rows and columns with more than max (16, knobs [0] * sqrt (n)) entries are removed prior to ordering, and placed last in the output ordering. knobs [0] dense row control knobs [1] dense column control knobs [2] if nonzero, do aggresive absorption knobs [3..19] unused, but future versions might use this */ PUBLIC void COLAMD_set_defaults ( /* === Parameters ======================================================= */ double knobs [COLAMD_KNOBS] /* knob array */ ) { /* === Local variables ================================================== */ Int i ; if (!knobs) { return ; /* no knobs to initialize */ } for (i = 0 ; i < COLAMD_KNOBS ; i++) { knobs [i] = 0 ; } knobs [COLAMD_DENSE_ROW] = 10 ; knobs [COLAMD_DENSE_COL] = 10 ; knobs [COLAMD_AGGRESSIVE] = TRUE ; /* default: do aggressive absorption*/ } /* ========================================================================== */ /* === symamd =============================================================== */ /* ========================================================================== */ PUBLIC Int SYMAMD_MAIN /* return TRUE if OK, FALSE otherwise */ ( /* === Parameters ======================================================= */ Int n, /* number of rows and columns of A */ Int A [], /* row indices of A */ Int p [], /* column pointers of A */ Int perm [], /* output permutation, size n+1 */ double knobs [COLAMD_KNOBS], /* parameters (uses defaults if NULL) */ Int stats [COLAMD_STATS], /* output statistics and error codes */ void * (*allocate) (size_t, size_t), /* pointer to calloc (ANSI C) or */ /* mxCalloc (for MATLAB mexFunction) */ void (*release) (void *) /* pointer to free (ANSI C) or */ /* mxFree (for MATLAB mexFunction) */ ) { /* === Local variables ================================================== */ Int *count ; /* length of each column of M, and col pointer*/ Int *mark ; /* mark array for finding duplicate entries */ Int *M ; /* row indices of matrix M */ size_t Mlen ; /* length of M */ Int n_row ; /* number of rows in M */ Int nnz ; /* number of entries in A */ Int i ; /* row index of A */ Int j ; /* column index of A */ Int k ; /* row index of M */ Int mnz ; /* number of nonzeros in M */ Int pp ; /* index into a column of A */ Int last_row ; /* last row seen in the current column */ Int length ; /* number of nonzeros in a column */ double cknobs [COLAMD_KNOBS] ; /* knobs for colamd */ double default_knobs [COLAMD_KNOBS] ; /* default knobs for colamd */ #ifndef NDEBUG colamd_get_debug ("symamd") ; #endif /* NDEBUG */ /* === Check the input arguments ======================================== */ if (!stats) { DEBUG0 (("symamd: stats not present\n")) ; return (FALSE) ; } for (i = 0 ; i < COLAMD_STATS ; i++) { stats [i] = 0 ; } stats [COLAMD_STATUS] = COLAMD_OK ; stats [COLAMD_INFO1] = -1 ; stats [COLAMD_INFO2] = -1 ; if (!A) { stats [COLAMD_STATUS] = COLAMD_ERROR_A_not_present ; DEBUG0 (("symamd: A not present\n")) ; return (FALSE) ; } if (!p) /* p is not present */ { stats [COLAMD_STATUS] = COLAMD_ERROR_p_not_present ; DEBUG0 (("symamd: p not present\n")) ; return (FALSE) ; } if (n < 0) /* n must be >= 0 */ { stats [COLAMD_STATUS] = COLAMD_ERROR_ncol_negative ; stats [COLAMD_INFO1] = n ; DEBUG0 (("symamd: n negative %d\n", n)) ; return (FALSE) ; } nnz = p [n] ; if (nnz < 0) /* nnz must be >= 0 */ { stats [COLAMD_STATUS] = COLAMD_ERROR_nnz_negative ; stats [COLAMD_INFO1] = nnz ; DEBUG0 (("symamd: number of entries negative %d\n", nnz)) ; return (FALSE) ; } if (p [0] != 0) { stats [COLAMD_STATUS] = COLAMD_ERROR_p0_nonzero ; stats [COLAMD_INFO1] = p [0] ; DEBUG0 (("symamd: p[0] not zero %d\n", p [0])) ; return (FALSE) ; } /* === If no knobs, set default knobs =================================== */ if (!knobs) { COLAMD_set_defaults (default_knobs) ; knobs = default_knobs ; } /* === Allocate count and mark ========================================== */ count = (Int *) ((*allocate) (n+1, sizeof (Int))) ; if (!count) { stats [COLAMD_STATUS] = COLAMD_ERROR_out_of_memory ; DEBUG0 (("symamd: allocate count (size %d) failed\n", n+1)) ; return (FALSE) ; } mark = (Int *) ((*allocate) (n+1, sizeof (Int))) ; if (!mark) { stats [COLAMD_STATUS] = COLAMD_ERROR_out_of_memory ; (*release) ((void *) count) ; DEBUG0 (("symamd: allocate mark (size %d) failed\n", n+1)) ; return (FALSE) ; } /* === Compute column counts of M, check if A is valid ================== */ stats [COLAMD_INFO3] = 0 ; /* number of duplicate or unsorted row indices*/ for (i = 0 ; i < n ; i++) { mark [i] = -1 ; } for (j = 0 ; j < n ; j++) { last_row = -1 ; length = p [j+1] - p [j] ; if (length < 0) { /* column pointers must be non-decreasing */ stats [COLAMD_STATUS] = COLAMD_ERROR_col_length_negative ; stats [COLAMD_INFO1] = j ; stats [COLAMD_INFO2] = length ; (*release) ((void *) count) ; (*release) ((void *) mark) ; DEBUG0 (("symamd: col %d negative length %d\n", j, length)) ; return (FALSE) ; } for (pp = p [j] ; pp < p [j+1] ; pp++) { i = A [pp] ; if (i < 0 || i >= n) { /* row index i, in column j, is out of bounds */ stats [COLAMD_STATUS] = COLAMD_ERROR_row_index_out_of_bounds ; stats [COLAMD_INFO1] = j ; stats [COLAMD_INFO2] = i ; stats [COLAMD_INFO3] = n ; (*release) ((void *) count) ; (*release) ((void *) mark) ; DEBUG0 (("symamd: row %d col %d out of bounds\n", i, j)) ; return (FALSE) ; } if (i <= last_row || mark [i] == j) { /* row index is unsorted or repeated (or both), thus col */ /* is jumbled. This is a notice, not an error condition. */ stats [COLAMD_STATUS] = COLAMD_OK_BUT_JUMBLED ; stats [COLAMD_INFO1] = j ; stats [COLAMD_INFO2] = i ; (stats [COLAMD_INFO3]) ++ ; DEBUG1 (("symamd: row %d col %d unsorted/duplicate\n", i, j)) ; } if (i > j && mark [i] != j) { /* row k of M will contain column indices i and j */ count [i]++ ; count [j]++ ; } /* mark the row as having been seen in this column */ mark [i] = j ; last_row = i ; } } /* v2.4: removed free(mark) */ /* === Compute column pointers of M ===================================== */ /* use output permutation, perm, for column pointers of M */ perm [0] = 0 ; for (j = 1 ; j <= n ; j++) { perm [j] = perm [j-1] + count [j-1] ; } for (j = 0 ; j < n ; j++) { count [j] = perm [j] ; } /* === Construct M ====================================================== */ mnz = perm [n] ; n_row = mnz / 2 ; Mlen = COLAMD_recommended (mnz, n_row, n) ; M = (Int *) ((*allocate) (Mlen, sizeof (Int))) ; DEBUG0 (("symamd: M is %d-by-%d with %d entries, Mlen = %g\n", n_row, n, mnz, (double) Mlen)) ; if (!M) { stats [COLAMD_STATUS] = COLAMD_ERROR_out_of_memory ; (*release) ((void *) count) ; (*release) ((void *) mark) ; DEBUG0 (("symamd: allocate M (size %g) failed\n", (double) Mlen)) ; return (FALSE) ; } k = 0 ; if (stats [COLAMD_STATUS] == COLAMD_OK) { /* Matrix is OK */ for (j = 0 ; j < n ; j++) { ASSERT (p [j+1] - p [j] >= 0) ; for (pp = p [j] ; pp < p [j+1] ; pp++) { i = A [pp] ; ASSERT (i >= 0 && i < n) ; if (i > j) { /* row k of M contains column indices i and j */ M [count [i]++] = k ; M [count [j]++] = k ; k++ ; } } } } else { /* Matrix is jumbled. Do not add duplicates to M. Unsorted cols OK. */ DEBUG0 (("symamd: Duplicates in A.\n")) ; for (i = 0 ; i < n ; i++) { mark [i] = -1 ; } for (j = 0 ; j < n ; j++) { ASSERT (p [j+1] - p [j] >= 0) ; for (pp = p [j] ; pp < p [j+1] ; pp++) { i = A [pp] ; ASSERT (i >= 0 && i < n) ; if (i > j && mark [i] != j) { /* row k of M contains column indices i and j */ M [count [i]++] = k ; M [count [j]++] = k ; k++ ; mark [i] = j ; } } } /* v2.4: free(mark) moved below */ } /* count and mark no longer needed */ (*release) ((void *) count) ; (*release) ((void *) mark) ; /* v2.4: free (mark) moved here */ ASSERT (k == n_row) ; /* === Adjust the knobs for M =========================================== */ for (i = 0 ; i < COLAMD_KNOBS ; i++) { cknobs [i] = knobs [i] ; } /* there are no dense rows in M */ cknobs [COLAMD_DENSE_ROW] = -1 ; cknobs [COLAMD_DENSE_COL] = knobs [COLAMD_DENSE_ROW] ; /* === Order the columns of M =========================================== */ /* v2.4: colamd cannot fail here, so the error check is removed */ (void) COLAMD_MAIN (n_row, n, (Int) Mlen, M, perm, cknobs, stats) ; /* Note that the output permutation is now in perm */ /* === get the statistics for symamd from colamd ======================== */ /* a dense column in colamd means a dense row and col in symamd */ stats [COLAMD_DENSE_ROW] = stats [COLAMD_DENSE_COL] ; /* === Free M =========================================================== */ (*release) ((void *) M) ; DEBUG0 (("symamd: done.\n")) ; return (TRUE) ; } /* ========================================================================== */ /* === colamd =============================================================== */ /* ========================================================================== */ /* The colamd routine computes a column ordering Q of a sparse matrix A such that the LU factorization P(AQ) = LU remains sparse, where P is selected via partial pivoting. The routine can also be viewed as providing a permutation Q such that the Cholesky factorization (AQ)'(AQ) = LL' remains sparse. */ PUBLIC Int COLAMD_MAIN /* returns TRUE if successful, FALSE otherwise*/ ( /* === Parameters ======================================================= */ Int n_row, /* number of rows in A */ Int n_col, /* number of columns in A */ Int Alen, /* length of A */ Int A [], /* row indices of A */ Int p [], /* pointers to columns in A */ double knobs [COLAMD_KNOBS],/* parameters (uses defaults if NULL) */ Int stats [COLAMD_STATS] /* output statistics and error codes */ ) { /* === Local variables ================================================== */ Int i ; /* loop index */ Int nnz ; /* nonzeros in A */ size_t Row_size ; /* size of Row [], in integers */ size_t Col_size ; /* size of Col [], in integers */ size_t need ; /* minimum required length of A */ Colamd_Row *Row ; /* pointer into A of Row [0..n_row] array */ Colamd_Col *Col ; /* pointer into A of Col [0..n_col] array */ Int n_col2 ; /* number of non-dense, non-empty columns */ Int n_row2 ; /* number of non-dense, non-empty rows */ Int ngarbage ; /* number of garbage collections performed */ Int max_deg ; /* maximum row degree */ double default_knobs [COLAMD_KNOBS] ; /* default knobs array */ Int aggressive ; /* do aggressive absorption */ int ok ; #ifndef NDEBUG colamd_get_debug ("colamd") ; #endif /* NDEBUG */ /* === Check the input arguments ======================================== */ if (!stats) { DEBUG0 (("colamd: stats not present\n")) ; return (FALSE) ; } for (i = 0 ; i < COLAMD_STATS ; i++) { stats [i] = 0 ; } stats [COLAMD_STATUS] = COLAMD_OK ; stats [COLAMD_INFO1] = -1 ; stats [COLAMD_INFO2] = -1 ; if (!A) /* A is not present */ { stats [COLAMD_STATUS] = COLAMD_ERROR_A_not_present ; DEBUG0 (("colamd: A not present\n")) ; return (FALSE) ; } if (!p) /* p is not present */ { stats [COLAMD_STATUS] = COLAMD_ERROR_p_not_present ; DEBUG0 (("colamd: p not present\n")) ; return (FALSE) ; } if (n_row < 0) /* n_row must be >= 0 */ { stats [COLAMD_STATUS] = COLAMD_ERROR_nrow_negative ; stats [COLAMD_INFO1] = n_row ; DEBUG0 (("colamd: nrow negative %d\n", n_row)) ; return (FALSE) ; } if (n_col < 0) /* n_col must be >= 0 */ { stats [COLAMD_STATUS] = COLAMD_ERROR_ncol_negative ; stats [COLAMD_INFO1] = n_col ; DEBUG0 (("colamd: ncol negative %d\n", n_col)) ; return (FALSE) ; } nnz = p [n_col] ; if (nnz < 0) /* nnz must be >= 0 */ { stats [COLAMD_STATUS] = COLAMD_ERROR_nnz_negative ; stats [COLAMD_INFO1] = nnz ; DEBUG0 (("colamd: number of entries negative %d\n", nnz)) ; return (FALSE) ; } if (p [0] != 0) { stats [COLAMD_STATUS] = COLAMD_ERROR_p0_nonzero ; stats [COLAMD_INFO1] = p [0] ; DEBUG0 (("colamd: p[0] not zero %d\n", p [0])) ; return (FALSE) ; } /* === If no knobs, set default knobs =================================== */ if (!knobs) { COLAMD_set_defaults (default_knobs) ; knobs = default_knobs ; } aggressive = (knobs [COLAMD_AGGRESSIVE] != FALSE) ; /* === Allocate the Row and Col arrays from array A ===================== */ ok = TRUE ; Col_size = COLAMD_C (n_col, &ok) ; /* size of Col array of structs */ Row_size = COLAMD_R (n_row, &ok) ; /* size of Row array of structs */ /* need = 2*nnz + n_col + Col_size + Row_size ; */ need = t_mult (nnz, 2, &ok) ; need = t_add (need, n_col, &ok) ; need = t_add (need, Col_size, &ok) ; need = t_add (need, Row_size, &ok) ; if (!ok || need > (size_t) Alen || need > Int_MAX) { /* not enough space in array A to perform the ordering */ stats [COLAMD_STATUS] = COLAMD_ERROR_A_too_small ; stats [COLAMD_INFO1] = need ; stats [COLAMD_INFO2] = Alen ; DEBUG0 (("colamd: Need Alen >= %d, given only Alen = %d\n", need,Alen)); return (FALSE) ; } Alen -= Col_size + Row_size ; Col = (Colamd_Col *) &A [Alen] ; Row = (Colamd_Row *) &A [Alen + Col_size] ; /* === Construct the row and column data structures ===================== */ if (!init_rows_cols (n_row, n_col, Row, Col, A, p, stats)) { /* input matrix is invalid */ DEBUG0 (("colamd: Matrix invalid\n")) ; return (FALSE) ; } /* === Initialize scores, kill dense rows/columns ======================= */ init_scoring (n_row, n_col, Row, Col, A, p, knobs, &n_row2, &n_col2, &max_deg) ; /* === Order the supercolumns =========================================== */ ngarbage = find_ordering (n_row, n_col, Alen, Row, Col, A, p, n_col2, max_deg, 2*nnz, aggressive) ; /* === Order the non-principal columns ================================== */ order_children (n_col, Col, p) ; /* === Return statistics in stats ======================================= */ stats [COLAMD_DENSE_ROW] = n_row - n_row2 ; stats [COLAMD_DENSE_COL] = n_col - n_col2 ; stats [COLAMD_DEFRAG_COUNT] = ngarbage ; DEBUG0 (("colamd: done.\n")) ; return (TRUE) ; } /* ========================================================================== */ /* === colamd_report ======================================================== */ /* ========================================================================== */ PUBLIC void COLAMD_report ( Int stats [COLAMD_STATS] ) { print_report ("colamd", stats) ; } /* ========================================================================== */ /* === symamd_report ======================================================== */ /* ========================================================================== */ PUBLIC void SYMAMD_report ( Int stats [COLAMD_STATS] ) { print_report ("symamd", stats) ; } /* ========================================================================== */ /* === NON-USER-CALLABLE ROUTINES: ========================================== */ /* ========================================================================== */ /* There are no user-callable routines beyond this point in the file */ /* ========================================================================== */ /* === init_rows_cols ======================================================= */ /* ========================================================================== */ /* Takes the column form of the matrix in A and creates the row form of the matrix. Also, row and column attributes are stored in the Col and Row structs. If the columns are un-sorted or contain duplicate row indices, this routine will also sort and remove duplicate row indices from the column form of the matrix. Returns FALSE if the matrix is invalid, TRUE otherwise. Not user-callable. */ PRIVATE Int init_rows_cols /* returns TRUE if OK, or FALSE otherwise */ ( /* === Parameters ======================================================= */ Int n_row, /* number of rows of A */ Int n_col, /* number of columns of A */ Colamd_Row Row [], /* of size n_row+1 */ Colamd_Col Col [], /* of size n_col+1 */ Int A [], /* row indices of A, of size Alen */ Int p [], /* pointers to columns in A, of size n_col+1 */ Int stats [COLAMD_STATS] /* colamd statistics */ ) { /* === Local variables ================================================== */ Int col ; /* a column index */ Int row ; /* a row index */ Int *cp ; /* a column pointer */ Int *cp_end ; /* a pointer to the end of a column */ Int *rp ; /* a row pointer */ Int *rp_end ; /* a pointer to the end of a row */ Int last_row ; /* previous row */ /* === Initialize columns, and check column pointers ==================== */ for (col = 0 ; col < n_col ; col++) { Col [col].start = p [col] ; Col [col].length = p [col+1] - p [col] ; if (Col [col].length < 0) { /* column pointers must be non-decreasing */ stats [COLAMD_STATUS] = COLAMD_ERROR_col_length_negative ; stats [COLAMD_INFO1] = col ; stats [COLAMD_INFO2] = Col [col].length ; DEBUG0 (("colamd: col %d length %d < 0\n", col, Col [col].length)) ; return (FALSE) ; } Col [col].shared1.thickness = 1 ; Col [col].shared2.score = 0 ; Col [col].shared3.prev = EMPTY ; Col [col].shared4.degree_next = EMPTY ; } /* p [0..n_col] no longer needed, used as "head" in subsequent routines */ /* === Scan columns, compute row degrees, and check row indices ========= */ stats [COLAMD_INFO3] = 0 ; /* number of duplicate or unsorted row indices*/ for (row = 0 ; row < n_row ; row++) { Row [row].length = 0 ; Row [row].shared2.mark = -1 ; } for (col = 0 ; col < n_col ; col++) { last_row = -1 ; cp = &A [p [col]] ; cp_end = &A [p [col+1]] ; while (cp < cp_end) { row = *cp++ ; /* make sure row indices within range */ if (row < 0 || row >= n_row) { stats [COLAMD_STATUS] = COLAMD_ERROR_row_index_out_of_bounds ; stats [COLAMD_INFO1] = col ; stats [COLAMD_INFO2] = row ; stats [COLAMD_INFO3] = n_row ; DEBUG0 (("colamd: row %d col %d out of bounds\n", row, col)) ; return (FALSE) ; } if (row <= last_row || Row [row].shared2.mark == col) { /* row index are unsorted or repeated (or both), thus col */ /* is jumbled. This is a notice, not an error condition. */ stats [COLAMD_STATUS] = COLAMD_OK_BUT_JUMBLED ; stats [COLAMD_INFO1] = col ; stats [COLAMD_INFO2] = row ; (stats [COLAMD_INFO3]) ++ ; DEBUG1 (("colamd: row %d col %d unsorted/duplicate\n",row,col)); } if (Row [row].shared2.mark != col) { Row [row].length++ ; } else { /* this is a repeated entry in the column, */ /* it will be removed */ Col [col].length-- ; } /* mark the row as having been seen in this column */ Row [row].shared2.mark = col ; last_row = row ; } } /* === Compute row pointers ============================================= */ /* row form of the matrix starts directly after the column */ /* form of matrix in A */ Row [0].start = p [n_col] ; Row [0].shared1.p = Row [0].start ; Row [0].shared2.mark = -1 ; for (row = 1 ; row < n_row ; row++) { Row [row].start = Row [row-1].start + Row [row-1].length ; Row [row].shared1.p = Row [row].start ; Row [row].shared2.mark = -1 ; } /* === Create row form ================================================== */ if (stats [COLAMD_STATUS] == COLAMD_OK_BUT_JUMBLED) { /* if cols jumbled, watch for repeated row indices */ for (col = 0 ; col < n_col ; col++) { cp = &A [p [col]] ; cp_end = &A [p [col+1]] ; while (cp < cp_end) { row = *cp++ ; if (Row [row].shared2.mark != col) { A [(Row [row].shared1.p)++] = col ; Row [row].shared2.mark = col ; } } } } else { /* if cols not jumbled, we don't need the mark (this is faster) */ for (col = 0 ; col < n_col ; col++) { cp = &A [p [col]] ; cp_end = &A [p [col+1]] ; while (cp < cp_end) { A [(Row [*cp++].shared1.p)++] = col ; } } } /* === Clear the row marks and set row degrees ========================== */ for (row = 0 ; row < n_row ; row++) { Row [row].shared2.mark = 0 ; Row [row].shared1.degree = Row [row].length ; } /* === See if we need to re-create columns ============================== */ if (stats [COLAMD_STATUS] == COLAMD_OK_BUT_JUMBLED) { DEBUG0 (("colamd: reconstructing column form, matrix jumbled\n")) ; #ifndef NDEBUG /* make sure column lengths are correct */ for (col = 0 ; col < n_col ; col++) { p [col] = Col [col].length ; } for (row = 0 ; row < n_row ; row++) { rp = &A [Row [row].start] ; rp_end = rp + Row [row].length ; while (rp < rp_end) { p [*rp++]-- ; } } for (col = 0 ; col < n_col ; col++) { ASSERT (p [col] == 0) ; } /* now p is all zero (different than when debugging is turned off) */ #endif /* NDEBUG */ /* === Compute col pointers ========================================= */ /* col form of the matrix starts at A [0]. */ /* Note, we may have a gap between the col form and the row */ /* form if there were duplicate entries, if so, it will be */ /* removed upon the first garbage collection */ Col [0].start = 0 ; p [0] = Col [0].start ; for (col = 1 ; col < n_col ; col++) { /* note that the lengths here are for pruned columns, i.e. */ /* no duplicate row indices will exist for these columns */ Col [col].start = Col [col-1].start + Col [col-1].length ; p [col] = Col [col].start ; } /* === Re-create col form =========================================== */ for (row = 0 ; row < n_row ; row++) { rp = &A [Row [row].start] ; rp_end = rp + Row [row].length ; while (rp < rp_end) { A [(p [*rp++])++] = row ; } } } /* === Done. Matrix is not (or no longer) jumbled ====================== */ return (TRUE) ; } /* ========================================================================== */ /* === init_scoring ========================================================= */ /* ========================================================================== */ /* Kills dense or empty columns and rows, calculates an initial score for each column, and places all columns in the degree lists. Not user-callable. */ PRIVATE void init_scoring ( /* === Parameters ======================================================= */ Int n_row, /* number of rows of A */ Int n_col, /* number of columns of A */ Colamd_Row Row [], /* of size n_row+1 */ Colamd_Col Col [], /* of size n_col+1 */ Int A [], /* column form and row form of A */ Int head [], /* of size n_col+1 */ double knobs [COLAMD_KNOBS],/* parameters */ Int *p_n_row2, /* number of non-dense, non-empty rows */ Int *p_n_col2, /* number of non-dense, non-empty columns */ Int *p_max_deg /* maximum row degree */ ) { /* === Local variables ================================================== */ Int c ; /* a column index */ Int r, row ; /* a row index */ Int *cp ; /* a column pointer */ Int deg ; /* degree of a row or column */ Int *cp_end ; /* a pointer to the end of a column */ Int *new_cp ; /* new column pointer */ Int col_length ; /* length of pruned column */ Int score ; /* current column score */ Int n_col2 ; /* number of non-dense, non-empty columns */ Int n_row2 ; /* number of non-dense, non-empty rows */ Int dense_row_count ; /* remove rows with more entries than this */ Int dense_col_count ; /* remove cols with more entries than this */ Int min_score ; /* smallest column score */ Int max_deg ; /* maximum row degree */ Int next_col ; /* Used to add to degree list.*/ #ifndef NDEBUG Int debug_count ; /* debug only. */ #endif /* NDEBUG */ /* === Extract knobs ==================================================== */ /* Note: if knobs contains a NaN, this is undefined: */ if (knobs [COLAMD_DENSE_ROW] < 0) { /* only remove completely dense rows */ dense_row_count = n_col-1 ; } else { dense_row_count = DENSE_DEGREE (knobs [COLAMD_DENSE_ROW], n_col) ; } if (knobs [COLAMD_DENSE_COL] < 0) { /* only remove completely dense columns */ dense_col_count = n_row-1 ; } else { dense_col_count = DENSE_DEGREE (knobs [COLAMD_DENSE_COL], MIN (n_row, n_col)) ; } DEBUG1 (("colamd: densecount: %d %d\n", dense_row_count, dense_col_count)) ; max_deg = 0 ; n_col2 = n_col ; n_row2 = n_row ; /* === Kill empty columns =============================================== */ /* Put the empty columns at the end in their natural order, so that LU */ /* factorization can proceed as far as possible. */ for (c = n_col-1 ; c >= 0 ; c--) { deg = Col [c].length ; if (deg == 0) { /* this is a empty column, kill and order it last */ Col [c].shared2.order = --n_col2 ; KILL_PRINCIPAL_COL (c) ; } } DEBUG1 (("colamd: null columns killed: %d\n", n_col - n_col2)) ; /* === Kill dense columns =============================================== */ /* Put the dense columns at the end, in their natural order */ for (c = n_col-1 ; c >= 0 ; c--) { /* skip any dead columns */ if (COL_IS_DEAD (c)) { continue ; } deg = Col [c].length ; if (deg > dense_col_count) { /* this is a dense column, kill and order it last */ Col [c].shared2.order = --n_col2 ; /* decrement the row degrees */ cp = &A [Col [c].start] ; cp_end = cp + Col [c].length ; while (cp < cp_end) { Row [*cp++].shared1.degree-- ; } KILL_PRINCIPAL_COL (c) ; } } DEBUG1 (("colamd: Dense and null columns killed: %d\n", n_col - n_col2)) ; /* === Kill dense and empty rows ======================================== */ for (r = 0 ; r < n_row ; r++) { deg = Row [r].shared1.degree ; ASSERT (deg >= 0 && deg <= n_col) ; if (deg > dense_row_count || deg == 0) { /* kill a dense or empty row */ KILL_ROW (r) ; --n_row2 ; } else { /* keep track of max degree of remaining rows */ max_deg = MAX (max_deg, deg) ; } } DEBUG1 (("colamd: Dense and null rows killed: %d\n", n_row - n_row2)) ; /* === Compute initial column scores ==================================== */ /* At this point the row degrees are accurate. They reflect the number */ /* of "live" (non-dense) columns in each row. No empty rows exist. */ /* Some "live" columns may contain only dead rows, however. These are */ /* pruned in the code below. */ /* now find the initial matlab score for each column */ for (c = n_col-1 ; c >= 0 ; c--) { /* skip dead column */ if (COL_IS_DEAD (c)) { continue ; } score = 0 ; cp = &A [Col [c].start] ; new_cp = cp ; cp_end = cp + Col [c].length ; while (cp < cp_end) { /* get a row */ row = *cp++ ; /* skip if dead */ if (ROW_IS_DEAD (row)) { continue ; } /* compact the column */ *new_cp++ = row ; /* add row's external degree */ score += Row [row].shared1.degree - 1 ; /* guard against integer overflow */ score = MIN (score, n_col) ; } /* determine pruned column length */ col_length = (Int) (new_cp - &A [Col [c].start]) ; if (col_length == 0) { /* a newly-made null column (all rows in this col are "dense" */ /* and have already been killed) */ DEBUG2 (("Newly null killed: %d\n", c)) ; Col [c].shared2.order = --n_col2 ; KILL_PRINCIPAL_COL (c) ; } else { /* set column length and set score */ ASSERT (score >= 0) ; ASSERT (score <= n_col) ; Col [c].length = col_length ; Col [c].shared2.score = score ; } } DEBUG1 (("colamd: Dense, null, and newly-null columns killed: %d\n", n_col-n_col2)) ; /* At this point, all empty rows and columns are dead. All live columns */ /* are "clean" (containing no dead rows) and simplicial (no supercolumns */ /* yet). Rows may contain dead columns, but all live rows contain at */ /* least one live column. */ #ifndef NDEBUG debug_structures (n_row, n_col, Row, Col, A, n_col2) ; #endif /* NDEBUG */ /* === Initialize degree lists ========================================== */ #ifndef NDEBUG debug_count = 0 ; #endif /* NDEBUG */ /* clear the hash buckets */ for (c = 0 ; c <= n_col ; c++) { head [c] = EMPTY ; } min_score = n_col ; /* place in reverse order, so low column indices are at the front */ /* of the lists. This is to encourage natural tie-breaking */ for (c = n_col-1 ; c >= 0 ; c--) { /* only add principal columns to degree lists */ if (COL_IS_ALIVE (c)) { DEBUG4 (("place %d score %d minscore %d ncol %d\n", c, Col [c].shared2.score, min_score, n_col)) ; /* === Add columns score to DList =============================== */ score = Col [c].shared2.score ; ASSERT (min_score >= 0) ; ASSERT (min_score <= n_col) ; ASSERT (score >= 0) ; ASSERT (score <= n_col) ; ASSERT (head [score] >= EMPTY) ; /* now add this column to dList at proper score location */ next_col = head [score] ; Col [c].shared3.prev = EMPTY ; Col [c].shared4.degree_next = next_col ; /* if there already was a column with the same score, set its */ /* previous pointer to this new column */ if (next_col != EMPTY) { Col [next_col].shared3.prev = c ; } head [score] = c ; /* see if this score is less than current min */ min_score = MIN (min_score, score) ; #ifndef NDEBUG debug_count++ ; #endif /* NDEBUG */ } } #ifndef NDEBUG DEBUG1 (("colamd: Live cols %d out of %d, non-princ: %d\n", debug_count, n_col, n_col-debug_count)) ; ASSERT (debug_count == n_col2) ; debug_deg_lists (n_row, n_col, Row, Col, head, min_score, n_col2, max_deg) ; #endif /* NDEBUG */ /* === Return number of remaining columns, and max row degree =========== */ *p_n_col2 = n_col2 ; *p_n_row2 = n_row2 ; *p_max_deg = max_deg ; } /* ========================================================================== */ /* === find_ordering ======================================================== */ /* ========================================================================== */ /* Order the principal columns of the supercolumn form of the matrix (no supercolumns on input). Uses a minimum approximate column minimum degree ordering method. Not user-callable. */ PRIVATE Int find_ordering /* return the number of garbage collections */ ( /* === Parameters ======================================================= */ Int n_row, /* number of rows of A */ Int n_col, /* number of columns of A */ Int Alen, /* size of A, 2*nnz + n_col or larger */ Colamd_Row Row [], /* of size n_row+1 */ Colamd_Col Col [], /* of size n_col+1 */ Int A [], /* column form and row form of A */ Int head [], /* of size n_col+1 */ Int n_col2, /* Remaining columns to order */ Int max_deg, /* Maximum row degree */ Int pfree, /* index of first free slot (2*nnz on entry) */ Int aggressive ) { /* === Local variables ================================================== */ Int k ; /* current pivot ordering step */ Int pivot_col ; /* current pivot column */ Int *cp ; /* a column pointer */ Int *rp ; /* a row pointer */ Int pivot_row ; /* current pivot row */ Int *new_cp ; /* modified column pointer */ Int *new_rp ; /* modified row pointer */ Int pivot_row_start ; /* pointer to start of pivot row */ Int pivot_row_degree ; /* number of columns in pivot row */ Int pivot_row_length ; /* number of supercolumns in pivot row */ Int pivot_col_score ; /* score of pivot column */ Int needed_memory ; /* free space needed for pivot row */ Int *cp_end ; /* pointer to the end of a column */ Int *rp_end ; /* pointer to the end of a row */ Int row ; /* a row index */ Int col ; /* a column index */ Int max_score ; /* maximum possible score */ Int cur_score ; /* score of current column */ unsigned Int hash ; /* hash value for supernode detection */ Int head_column ; /* head of hash bucket */ Int first_col ; /* first column in hash bucket */ Int tag_mark ; /* marker value for mark array */ Int row_mark ; /* Row [row].shared2.mark */ Int set_difference ; /* set difference size of row with pivot row */ Int min_score ; /* smallest column score */ Int col_thickness ; /* "thickness" (no. of columns in a supercol) */ Int max_mark ; /* maximum value of tag_mark */ Int pivot_col_thickness ; /* number of columns represented by pivot col */ Int prev_col ; /* Used by Dlist operations. */ Int next_col ; /* Used by Dlist operations. */ Int ngarbage ; /* number of garbage collections performed */ #ifndef NDEBUG Int debug_d ; /* debug loop counter */ Int debug_step = 0 ; /* debug loop counter */ #endif /* NDEBUG */ /* === Initialization and clear mark ==================================== */ max_mark = INT_MAX - n_col ; /* INT_MAX defined in */ tag_mark = clear_mark (0, max_mark, n_row, Row) ; min_score = 0 ; ngarbage = 0 ; DEBUG1 (("colamd: Ordering, n_col2=%d\n", n_col2)) ; /* === Order the columns ================================================ */ for (k = 0 ; k < n_col2 ; /* 'k' is incremented below */) { #ifndef NDEBUG if (debug_step % 100 == 0) { DEBUG2 (("\n... Step k: %d out of n_col2: %d\n", k, n_col2)) ; } else { DEBUG3 (("\n----------Step k: %d out of n_col2: %d\n", k, n_col2)) ; } debug_step++ ; debug_deg_lists (n_row, n_col, Row, Col, head, min_score, n_col2-k, max_deg) ; debug_matrix (n_row, n_col, Row, Col, A) ; #endif /* NDEBUG */ /* === Select pivot column, and order it ============================ */ /* make sure degree list isn't empty */ ASSERT (min_score >= 0) ; ASSERT (min_score <= n_col) ; ASSERT (head [min_score] >= EMPTY) ; #ifndef NDEBUG for (debug_d = 0 ; debug_d < min_score ; debug_d++) { ASSERT (head [debug_d] == EMPTY) ; } #endif /* NDEBUG */ /* get pivot column from head of minimum degree list */ while (head [min_score] == EMPTY && min_score < n_col) { min_score++ ; } pivot_col = head [min_score] ; ASSERT (pivot_col >= 0 && pivot_col <= n_col) ; next_col = Col [pivot_col].shared4.degree_next ; head [min_score] = next_col ; if (next_col != EMPTY) { Col [next_col].shared3.prev = EMPTY ; } ASSERT (COL_IS_ALIVE (pivot_col)) ; /* remember score for defrag check */ pivot_col_score = Col [pivot_col].shared2.score ; /* the pivot column is the kth column in the pivot order */ Col [pivot_col].shared2.order = k ; /* increment order count by column thickness */ pivot_col_thickness = Col [pivot_col].shared1.thickness ; k += pivot_col_thickness ; ASSERT (pivot_col_thickness > 0) ; DEBUG3 (("Pivot col: %d thick %d\n", pivot_col, pivot_col_thickness)) ; /* === Garbage_collection, if necessary ============================= */ needed_memory = MIN (pivot_col_score, n_col - k) ; if (pfree + needed_memory >= Alen) { pfree = garbage_collection (n_row, n_col, Row, Col, A, &A [pfree]) ; ngarbage++ ; /* after garbage collection we will have enough */ ASSERT (pfree + needed_memory < Alen) ; /* garbage collection has wiped out the Row[].shared2.mark array */ tag_mark = clear_mark (0, max_mark, n_row, Row) ; #ifndef NDEBUG debug_matrix (n_row, n_col, Row, Col, A) ; #endif /* NDEBUG */ } /* === Compute pivot row pattern ==================================== */ /* get starting location for this new merged row */ pivot_row_start = pfree ; /* initialize new row counts to zero */ pivot_row_degree = 0 ; /* tag pivot column as having been visited so it isn't included */ /* in merged pivot row */ Col [pivot_col].shared1.thickness = -pivot_col_thickness ; /* pivot row is the union of all rows in the pivot column pattern */ cp = &A [Col [pivot_col].start] ; cp_end = cp + Col [pivot_col].length ; while (cp < cp_end) { /* get a row */ row = *cp++ ; DEBUG4 (("Pivot col pattern %d %d\n", ROW_IS_ALIVE (row), row)) ; /* skip if row is dead */ if (ROW_IS_ALIVE (row)) { rp = &A [Row [row].start] ; rp_end = rp + Row [row].length ; while (rp < rp_end) { /* get a column */ col = *rp++ ; /* add the column, if alive and untagged */ col_thickness = Col [col].shared1.thickness ; if (col_thickness > 0 && COL_IS_ALIVE (col)) { /* tag column in pivot row */ Col [col].shared1.thickness = -col_thickness ; ASSERT (pfree < Alen) ; /* place column in pivot row */ A [pfree++] = col ; pivot_row_degree += col_thickness ; } } } } /* clear tag on pivot column */ Col [pivot_col].shared1.thickness = pivot_col_thickness ; max_deg = MAX (max_deg, pivot_row_degree) ; #ifndef NDEBUG DEBUG3 (("check2\n")) ; debug_mark (n_row, Row, tag_mark, max_mark) ; #endif /* NDEBUG */ /* === Kill all rows used to construct pivot row ==================== */ /* also kill pivot row, temporarily */ cp = &A [Col [pivot_col].start] ; cp_end = cp + Col [pivot_col].length ; while (cp < cp_end) { /* may be killing an already dead row */ row = *cp++ ; DEBUG3 (("Kill row in pivot col: %d\n", row)) ; KILL_ROW (row) ; } /* === Select a row index to use as the new pivot row =============== */ pivot_row_length = pfree - pivot_row_start ; if (pivot_row_length > 0) { /* pick the "pivot" row arbitrarily (first row in col) */ pivot_row = A [Col [pivot_col].start] ; DEBUG3 (("Pivotal row is %d\n", pivot_row)) ; } else { /* there is no pivot row, since it is of zero length */ pivot_row = EMPTY ; ASSERT (pivot_row_length == 0) ; } ASSERT (Col [pivot_col].length > 0 || pivot_row_length == 0) ; /* === Approximate degree computation =============================== */ /* Here begins the computation of the approximate degree. The column */ /* score is the sum of the pivot row "length", plus the size of the */ /* set differences of each row in the column minus the pattern of the */ /* pivot row itself. The column ("thickness") itself is also */ /* excluded from the column score (we thus use an approximate */ /* external degree). */ /* The time taken by the following code (compute set differences, and */ /* add them up) is proportional to the size of the data structure */ /* being scanned - that is, the sum of the sizes of each column in */ /* the pivot row. Thus, the amortized time to compute a column score */ /* is proportional to the size of that column (where size, in this */ /* context, is the column "length", or the number of row indices */ /* in that column). The number of row indices in a column is */ /* monotonically non-decreasing, from the length of the original */ /* column on input to colamd. */ /* === Compute set differences ====================================== */ DEBUG3 (("** Computing set differences phase. **\n")) ; /* pivot row is currently dead - it will be revived later. */ DEBUG3 (("Pivot row: ")) ; /* for each column in pivot row */ rp = &A [pivot_row_start] ; rp_end = rp + pivot_row_length ; while (rp < rp_end) { col = *rp++ ; ASSERT (COL_IS_ALIVE (col) && col != pivot_col) ; DEBUG3 (("Col: %d\n", col)) ; /* clear tags used to construct pivot row pattern */ col_thickness = -Col [col].shared1.thickness ; ASSERT (col_thickness > 0) ; Col [col].shared1.thickness = col_thickness ; /* === Remove column from degree list =========================== */ cur_score = Col [col].shared2.score ; prev_col = Col [col].shared3.prev ; next_col = Col [col].shared4.degree_next ; ASSERT (cur_score >= 0) ; ASSERT (cur_score <= n_col) ; ASSERT (cur_score >= EMPTY) ; if (prev_col == EMPTY) { head [cur_score] = next_col ; } else { Col [prev_col].shared4.degree_next = next_col ; } if (next_col != EMPTY) { Col [next_col].shared3.prev = prev_col ; } /* === Scan the column ========================================== */ cp = &A [Col [col].start] ; cp_end = cp + Col [col].length ; while (cp < cp_end) { /* get a row */ row = *cp++ ; row_mark = Row [row].shared2.mark ; /* skip if dead */ if (ROW_IS_MARKED_DEAD (row_mark)) { continue ; } ASSERT (row != pivot_row) ; set_difference = row_mark - tag_mark ; /* check if the row has been seen yet */ if (set_difference < 0) { ASSERT (Row [row].shared1.degree <= max_deg) ; set_difference = Row [row].shared1.degree ; } /* subtract column thickness from this row's set difference */ set_difference -= col_thickness ; ASSERT (set_difference >= 0) ; /* absorb this row if the set difference becomes zero */ if (set_difference == 0 && aggressive) { DEBUG3 (("aggressive absorption. Row: %d\n", row)) ; KILL_ROW (row) ; } else { /* save the new mark */ Row [row].shared2.mark = set_difference + tag_mark ; } } } #ifndef NDEBUG debug_deg_lists (n_row, n_col, Row, Col, head, min_score, n_col2-k-pivot_row_degree, max_deg) ; #endif /* NDEBUG */ /* === Add up set differences for each column ======================= */ DEBUG3 (("** Adding set differences phase. **\n")) ; /* for each column in pivot row */ rp = &A [pivot_row_start] ; rp_end = rp + pivot_row_length ; while (rp < rp_end) { /* get a column */ col = *rp++ ; ASSERT (COL_IS_ALIVE (col) && col != pivot_col) ; hash = 0 ; cur_score = 0 ; cp = &A [Col [col].start] ; /* compact the column */ new_cp = cp ; cp_end = cp + Col [col].length ; DEBUG4 (("Adding set diffs for Col: %d.\n", col)) ; while (cp < cp_end) { /* get a row */ row = *cp++ ; ASSERT(row >= 0 && row < n_row) ; row_mark = Row [row].shared2.mark ; /* skip if dead */ if (ROW_IS_MARKED_DEAD (row_mark)) { DEBUG4 ((" Row %d, dead\n", row)) ; continue ; } DEBUG4 ((" Row %d, set diff %d\n", row, row_mark-tag_mark)); ASSERT (row_mark >= tag_mark) ; /* compact the column */ *new_cp++ = row ; /* compute hash function */ hash += row ; /* add set difference */ cur_score += row_mark - tag_mark ; /* integer overflow... */ cur_score = MIN (cur_score, n_col) ; } /* recompute the column's length */ Col [col].length = (Int) (new_cp - &A [Col [col].start]) ; /* === Further mass elimination ================================= */ if (Col [col].length == 0) { DEBUG4 (("further mass elimination. Col: %d\n", col)) ; /* nothing left but the pivot row in this column */ KILL_PRINCIPAL_COL (col) ; pivot_row_degree -= Col [col].shared1.thickness ; ASSERT (pivot_row_degree >= 0) ; /* order it */ Col [col].shared2.order = k ; /* increment order count by column thickness */ k += Col [col].shared1.thickness ; } else { /* === Prepare for supercolumn detection ==================== */ DEBUG4 (("Preparing supercol detection for Col: %d.\n", col)) ; /* save score so far */ Col [col].shared2.score = cur_score ; /* add column to hash table, for supercolumn detection */ hash %= n_col + 1 ; DEBUG4 ((" Hash = %d, n_col = %d.\n", hash, n_col)) ; ASSERT (((Int) hash) <= n_col) ; head_column = head [hash] ; if (head_column > EMPTY) { /* degree list "hash" is non-empty, use prev (shared3) of */ /* first column in degree list as head of hash bucket */ first_col = Col [head_column].shared3.headhash ; Col [head_column].shared3.headhash = col ; } else { /* degree list "hash" is empty, use head as hash bucket */ first_col = - (head_column + 2) ; head [hash] = - (col + 2) ; } Col [col].shared4.hash_next = first_col ; /* save hash function in Col [col].shared3.hash */ Col [col].shared3.hash = (Int) hash ; ASSERT (COL_IS_ALIVE (col)) ; } } /* The approximate external column degree is now computed. */ /* === Supercolumn detection ======================================== */ DEBUG3 (("** Supercolumn detection phase. **\n")) ; detect_super_cols ( #ifndef NDEBUG n_col, Row, #endif /* NDEBUG */ Col, A, head, pivot_row_start, pivot_row_length) ; /* === Kill the pivotal column ====================================== */ KILL_PRINCIPAL_COL (pivot_col) ; /* === Clear mark =================================================== */ tag_mark = clear_mark (tag_mark+max_deg+1, max_mark, n_row, Row) ; #ifndef NDEBUG DEBUG3 (("check3\n")) ; debug_mark (n_row, Row, tag_mark, max_mark) ; #endif /* NDEBUG */ /* === Finalize the new pivot row, and column scores ================ */ DEBUG3 (("** Finalize scores phase. **\n")) ; /* for each column in pivot row */ rp = &A [pivot_row_start] ; /* compact the pivot row */ new_rp = rp ; rp_end = rp + pivot_row_length ; while (rp < rp_end) { col = *rp++ ; /* skip dead columns */ if (COL_IS_DEAD (col)) { continue ; } *new_rp++ = col ; /* add new pivot row to column */ A [Col [col].start + (Col [col].length++)] = pivot_row ; /* retrieve score so far and add on pivot row's degree. */ /* (we wait until here for this in case the pivot */ /* row's degree was reduced due to mass elimination). */ cur_score = Col [col].shared2.score + pivot_row_degree ; /* calculate the max possible score as the number of */ /* external columns minus the 'k' value minus the */ /* columns thickness */ max_score = n_col - k - Col [col].shared1.thickness ; /* make the score the external degree of the union-of-rows */ cur_score -= Col [col].shared1.thickness ; /* make sure score is less or equal than the max score */ cur_score = MIN (cur_score, max_score) ; ASSERT (cur_score >= 0) ; /* store updated score */ Col [col].shared2.score = cur_score ; /* === Place column back in degree list ========================= */ ASSERT (min_score >= 0) ; ASSERT (min_score <= n_col) ; ASSERT (cur_score >= 0) ; ASSERT (cur_score <= n_col) ; ASSERT (head [cur_score] >= EMPTY) ; next_col = head [cur_score] ; Col [col].shared4.degree_next = next_col ; Col [col].shared3.prev = EMPTY ; if (next_col != EMPTY) { Col [next_col].shared3.prev = col ; } head [cur_score] = col ; /* see if this score is less than current min */ min_score = MIN (min_score, cur_score) ; } #ifndef NDEBUG debug_deg_lists (n_row, n_col, Row, Col, head, min_score, n_col2-k, max_deg) ; #endif /* NDEBUG */ /* === Resurrect the new pivot row ================================== */ if (pivot_row_degree > 0) { /* update pivot row length to reflect any cols that were killed */ /* during super-col detection and mass elimination */ Row [pivot_row].start = pivot_row_start ; Row [pivot_row].length = (Int) (new_rp - &A[pivot_row_start]) ; ASSERT (Row [pivot_row].length > 0) ; Row [pivot_row].shared1.degree = pivot_row_degree ; Row [pivot_row].shared2.mark = 0 ; /* pivot row is no longer dead */ DEBUG1 (("Resurrect Pivot_row %d deg: %d\n", pivot_row, pivot_row_degree)) ; } } /* === All principal columns have now been ordered ====================== */ return (ngarbage) ; } /* ========================================================================== */ /* === order_children ======================================================= */ /* ========================================================================== */ /* The find_ordering routine has ordered all of the principal columns (the representatives of the supercolumns). The non-principal columns have not yet been ordered. This routine orders those columns by walking up the parent tree (a column is a child of the column which absorbed it). The final permutation vector is then placed in p [0 ... n_col-1], with p [0] being the first column, and p [n_col-1] being the last. It doesn't look like it at first glance, but be assured that this routine takes time linear in the number of columns. Although not immediately obvious, the time taken by this routine is O (n_col), that is, linear in the number of columns. Not user-callable. */ PRIVATE void order_children ( /* === Parameters ======================================================= */ Int n_col, /* number of columns of A */ Colamd_Col Col [], /* of size n_col+1 */ Int p [] /* p [0 ... n_col-1] is the column permutation*/ ) { /* === Local variables ================================================== */ Int i ; /* loop counter for all columns */ Int c ; /* column index */ Int parent ; /* index of column's parent */ Int order ; /* column's order */ /* === Order each non-principal column ================================== */ for (i = 0 ; i < n_col ; i++) { /* find an un-ordered non-principal column */ ASSERT (COL_IS_DEAD (i)) ; if (!COL_IS_DEAD_PRINCIPAL (i) && Col [i].shared2.order == EMPTY) { parent = i ; /* once found, find its principal parent */ do { parent = Col [parent].shared1.parent ; } while (!COL_IS_DEAD_PRINCIPAL (parent)) ; /* now, order all un-ordered non-principal columns along path */ /* to this parent. collapse tree at the same time */ c = i ; /* get order of parent */ order = Col [parent].shared2.order ; do { ASSERT (Col [c].shared2.order == EMPTY) ; /* order this column */ Col [c].shared2.order = order++ ; /* collaps tree */ Col [c].shared1.parent = parent ; /* get immediate parent of this column */ c = Col [c].shared1.parent ; /* continue until we hit an ordered column. There are */ /* guarranteed not to be anymore unordered columns */ /* above an ordered column */ } while (Col [c].shared2.order == EMPTY) ; /* re-order the super_col parent to largest order for this group */ Col [parent].shared2.order = order ; } } /* === Generate the permutation ========================================= */ for (c = 0 ; c < n_col ; c++) { p [Col [c].shared2.order] = c ; } } /* ========================================================================== */ /* === detect_super_cols ==================================================== */ /* ========================================================================== */ /* Detects supercolumns by finding matches between columns in the hash buckets. Check amongst columns in the set A [row_start ... row_start + row_length-1]. The columns under consideration are currently *not* in the degree lists, and have already been placed in the hash buckets. The hash bucket for columns whose hash function is equal to h is stored as follows: if head [h] is >= 0, then head [h] contains a degree list, so: head [h] is the first column in degree bucket h. Col [head [h]].headhash gives the first column in hash bucket h. otherwise, the degree list is empty, and: -(head [h] + 2) is the first column in hash bucket h. For a column c in a hash bucket, Col [c].shared3.prev is NOT a "previous column" pointer. Col [c].shared3.hash is used instead as the hash number for that column. The value of Col [c].shared4.hash_next is the next column in the same hash bucket. Assuming no, or "few" hash collisions, the time taken by this routine is linear in the sum of the sizes (lengths) of each column whose score has just been computed in the approximate degree computation. Not user-callable. */ PRIVATE void detect_super_cols ( /* === Parameters ======================================================= */ #ifndef NDEBUG /* these two parameters are only needed when debugging is enabled: */ Int n_col, /* number of columns of A */ Colamd_Row Row [], /* of size n_row+1 */ #endif /* NDEBUG */ Colamd_Col Col [], /* of size n_col+1 */ Int A [], /* row indices of A */ Int head [], /* head of degree lists and hash buckets */ Int row_start, /* pointer to set of columns to check */ Int row_length /* number of columns to check */ ) { /* === Local variables ================================================== */ Int hash ; /* hash value for a column */ Int *rp ; /* pointer to a row */ Int c ; /* a column index */ Int super_c ; /* column index of the column to absorb into */ Int *cp1 ; /* column pointer for column super_c */ Int *cp2 ; /* column pointer for column c */ Int length ; /* length of column super_c */ Int prev_c ; /* column preceding c in hash bucket */ Int i ; /* loop counter */ Int *rp_end ; /* pointer to the end of the row */ Int col ; /* a column index in the row to check */ Int head_column ; /* first column in hash bucket or degree list */ Int first_col ; /* first column in hash bucket */ /* === Consider each column in the row ================================== */ rp = &A [row_start] ; rp_end = rp + row_length ; while (rp < rp_end) { col = *rp++ ; if (COL_IS_DEAD (col)) { continue ; } /* get hash number for this column */ hash = Col [col].shared3.hash ; ASSERT (hash <= n_col) ; /* === Get the first column in this hash bucket ===================== */ head_column = head [hash] ; if (head_column > EMPTY) { first_col = Col [head_column].shared3.headhash ; } else { first_col = - (head_column + 2) ; } /* === Consider each column in the hash bucket ====================== */ for (super_c = first_col ; super_c != EMPTY ; super_c = Col [super_c].shared4.hash_next) { ASSERT (COL_IS_ALIVE (super_c)) ; ASSERT (Col [super_c].shared3.hash == hash) ; length = Col [super_c].length ; /* prev_c is the column preceding column c in the hash bucket */ prev_c = super_c ; /* === Compare super_c with all columns after it ================ */ for (c = Col [super_c].shared4.hash_next ; c != EMPTY ; c = Col [c].shared4.hash_next) { ASSERT (c != super_c) ; ASSERT (COL_IS_ALIVE (c)) ; ASSERT (Col [c].shared3.hash == hash) ; /* not identical if lengths or scores are different */ if (Col [c].length != length || Col [c].shared2.score != Col [super_c].shared2.score) { prev_c = c ; continue ; } /* compare the two columns */ cp1 = &A [Col [super_c].start] ; cp2 = &A [Col [c].start] ; for (i = 0 ; i < length ; i++) { /* the columns are "clean" (no dead rows) */ ASSERT (ROW_IS_ALIVE (*cp1)) ; ASSERT (ROW_IS_ALIVE (*cp2)) ; /* row indices will same order for both supercols, */ /* no gather scatter nessasary */ if (*cp1++ != *cp2++) { break ; } } /* the two columns are different if the for-loop "broke" */ if (i != length) { prev_c = c ; continue ; } /* === Got it! two columns are identical =================== */ ASSERT (Col [c].shared2.score == Col [super_c].shared2.score) ; Col [super_c].shared1.thickness += Col [c].shared1.thickness ; Col [c].shared1.parent = super_c ; KILL_NON_PRINCIPAL_COL (c) ; /* order c later, in order_children() */ Col [c].shared2.order = EMPTY ; /* remove c from hash bucket */ Col [prev_c].shared4.hash_next = Col [c].shared4.hash_next ; } } /* === Empty this hash bucket ======================================= */ if (head_column > EMPTY) { /* corresponding degree list "hash" is not empty */ Col [head_column].shared3.headhash = EMPTY ; } else { /* corresponding degree list "hash" is empty */ head [hash] = EMPTY ; } } } /* ========================================================================== */ /* === garbage_collection =================================================== */ /* ========================================================================== */ /* Defragments and compacts columns and rows in the workspace A. Used when all avaliable memory has been used while performing row merging. Returns the index of the first free position in A, after garbage collection. The time taken by this routine is linear is the size of the array A, which is itself linear in the number of nonzeros in the input matrix. Not user-callable. */ PRIVATE Int garbage_collection /* returns the new value of pfree */ ( /* === Parameters ======================================================= */ Int n_row, /* number of rows */ Int n_col, /* number of columns */ Colamd_Row Row [], /* row info */ Colamd_Col Col [], /* column info */ Int A [], /* A [0 ... Alen-1] holds the matrix */ Int *pfree /* &A [0] ... pfree is in use */ ) { /* === Local variables ================================================== */ Int *psrc ; /* source pointer */ Int *pdest ; /* destination pointer */ Int j ; /* counter */ Int r ; /* a row index */ Int c ; /* a column index */ Int length ; /* length of a row or column */ #ifndef NDEBUG Int debug_rows ; DEBUG2 (("Defrag..\n")) ; for (psrc = &A[0] ; psrc < pfree ; psrc++) ASSERT (*psrc >= 0) ; debug_rows = 0 ; #endif /* NDEBUG */ /* === Defragment the columns =========================================== */ pdest = &A[0] ; for (c = 0 ; c < n_col ; c++) { if (COL_IS_ALIVE (c)) { psrc = &A [Col [c].start] ; /* move and compact the column */ ASSERT (pdest <= psrc) ; Col [c].start = (Int) (pdest - &A [0]) ; length = Col [c].length ; for (j = 0 ; j < length ; j++) { r = *psrc++ ; if (ROW_IS_ALIVE (r)) { *pdest++ = r ; } } Col [c].length = (Int) (pdest - &A [Col [c].start]) ; } } /* === Prepare to defragment the rows =================================== */ for (r = 0 ; r < n_row ; r++) { if (ROW_IS_DEAD (r) || (Row [r].length == 0)) { /* This row is already dead, or is of zero length. Cannot compact * a row of zero length, so kill it. NOTE: in the current version, * there are no zero-length live rows. Kill the row (for the first * time, or again) just to be safe. */ KILL_ROW (r) ; } else { /* save first column index in Row [r].shared2.first_column */ psrc = &A [Row [r].start] ; Row [r].shared2.first_column = *psrc ; ASSERT (ROW_IS_ALIVE (r)) ; /* flag the start of the row with the one's complement of row */ *psrc = ONES_COMPLEMENT (r) ; #ifndef NDEBUG debug_rows++ ; #endif /* NDEBUG */ } } /* === Defragment the rows ============================================== */ psrc = pdest ; while (psrc < pfree) { /* find a negative number ... the start of a row */ if (*psrc++ < 0) { psrc-- ; /* get the row index */ r = ONES_COMPLEMENT (*psrc) ; ASSERT (r >= 0 && r < n_row) ; /* restore first column index */ *psrc = Row [r].shared2.first_column ; ASSERT (ROW_IS_ALIVE (r)) ; ASSERT (Row [r].length > 0) ; /* move and compact the row */ ASSERT (pdest <= psrc) ; Row [r].start = (Int) (pdest - &A [0]) ; length = Row [r].length ; for (j = 0 ; j < length ; j++) { c = *psrc++ ; if (COL_IS_ALIVE (c)) { *pdest++ = c ; } } Row [r].length = (Int) (pdest - &A [Row [r].start]) ; ASSERT (Row [r].length > 0) ; #ifndef NDEBUG debug_rows-- ; #endif /* NDEBUG */ } } /* ensure we found all the rows */ ASSERT (debug_rows == 0) ; /* === Return the new value of pfree ==================================== */ return ((Int) (pdest - &A [0])) ; } /* ========================================================================== */ /* === clear_mark =========================================================== */ /* ========================================================================== */ /* Clears the Row [].shared2.mark array, and returns the new tag_mark. Return value is the new tag_mark. Not user-callable. */ PRIVATE Int clear_mark /* return the new value for tag_mark */ ( /* === Parameters ======================================================= */ Int tag_mark, /* new value of tag_mark */ Int max_mark, /* max allowed value of tag_mark */ Int n_row, /* number of rows in A */ Colamd_Row Row [] /* Row [0 ... n_row-1].shared2.mark is set to zero */ ) { /* === Local variables ================================================== */ Int r ; if (tag_mark <= 0 || tag_mark >= max_mark) { for (r = 0 ; r < n_row ; r++) { if (ROW_IS_ALIVE (r)) { Row [r].shared2.mark = 0 ; } } tag_mark = 1 ; } return (tag_mark) ; } /* ========================================================================== */ /* === print_report ========================================================= */ /* ========================================================================== */ PRIVATE void print_report ( char *method, Int stats [COLAMD_STATS] ) { Int i1, i2, i3 ; PRINTF (("\n%s version %d.%d, %s: ", method, COLAMD_MAIN_VERSION, COLAMD_SUB_VERSION, COLAMD_DATE)) ; if (!stats) { PRINTF (("No statistics available.\n")) ; return ; } i1 = stats [COLAMD_INFO1] ; i2 = stats [COLAMD_INFO2] ; i3 = stats [COLAMD_INFO3] ; if (stats [COLAMD_STATUS] >= 0) { PRINTF (("OK. ")) ; } else { PRINTF (("ERROR. ")) ; } switch (stats [COLAMD_STATUS]) { case COLAMD_OK_BUT_JUMBLED: PRINTF(("Matrix has unsorted or duplicate row indices.\n")) ; PRINTF(("%s: number of duplicate or out-of-order row indices: %d\n", method, i3)) ; PRINTF(("%s: last seen duplicate or out-of-order row index: %d\n", method, INDEX (i2))) ; PRINTF(("%s: last seen in column: %d", method, INDEX (i1))) ; /* no break - fall through to next case instead */ case COLAMD_OK: PRINTF(("\n")) ; PRINTF(("%s: number of dense or empty rows ignored: %d\n", method, stats [COLAMD_DENSE_ROW])) ; PRINTF(("%s: number of dense or empty columns ignored: %d\n", method, stats [COLAMD_DENSE_COL])) ; PRINTF(("%s: number of garbage collections performed: %d\n", method, stats [COLAMD_DEFRAG_COUNT])) ; break ; case COLAMD_ERROR_A_not_present: PRINTF(("Array A (row indices of matrix) not present.\n")) ; break ; case COLAMD_ERROR_p_not_present: PRINTF(("Array p (column pointers for matrix) not present.\n")) ; break ; case COLAMD_ERROR_nrow_negative: PRINTF(("Invalid number of rows (%d).\n", i1)) ; break ; case COLAMD_ERROR_ncol_negative: PRINTF(("Invalid number of columns (%d).\n", i1)) ; break ; case COLAMD_ERROR_nnz_negative: PRINTF(("Invalid number of nonzero entries (%d).\n", i1)) ; break ; case COLAMD_ERROR_p0_nonzero: PRINTF(("Invalid column pointer, p [0] = %d, must be zero.\n", i1)); break ; case COLAMD_ERROR_A_too_small: PRINTF(("Array A too small.\n")) ; PRINTF((" Need Alen >= %d, but given only Alen = %d.\n", i1, i2)) ; break ; case COLAMD_ERROR_col_length_negative: PRINTF (("Column %d has a negative number of nonzero entries (%d).\n", INDEX (i1), i2)) ; break ; case COLAMD_ERROR_row_index_out_of_bounds: PRINTF (("Row index (row %d) out of bounds (%d to %d) in column %d.\n", INDEX (i2), INDEX (0), INDEX (i3-1), INDEX (i1))) ; break ; case COLAMD_ERROR_out_of_memory: PRINTF(("Out of memory.\n")) ; break ; /* v2.4: internal-error case deleted */ } } /* ========================================================================== */ /* === colamd debugging routines ============================================ */ /* ========================================================================== */ /* When debugging is disabled, the remainder of this file is ignored. */ #ifndef NDEBUG /* ========================================================================== */ /* === debug_structures ===================================================== */ /* ========================================================================== */ /* At this point, all empty rows and columns are dead. All live columns are "clean" (containing no dead rows) and simplicial (no supercolumns yet). Rows may contain dead columns, but all live rows contain at least one live column. */ PRIVATE void debug_structures ( /* === Parameters ======================================================= */ Int n_row, Int n_col, Colamd_Row Row [], Colamd_Col Col [], Int A [], Int n_col2 ) { /* === Local variables ================================================== */ Int i ; Int c ; Int *cp ; Int *cp_end ; Int len ; Int score ; Int r ; Int *rp ; Int *rp_end ; Int deg ; /* === Check A, Row, and Col ============================================ */ for (c = 0 ; c < n_col ; c++) { if (COL_IS_ALIVE (c)) { len = Col [c].length ; score = Col [c].shared2.score ; DEBUG4 (("initial live col %5d %5d %5d\n", c, len, score)) ; ASSERT (len > 0) ; ASSERT (score >= 0) ; ASSERT (Col [c].shared1.thickness == 1) ; cp = &A [Col [c].start] ; cp_end = cp + len ; while (cp < cp_end) { r = *cp++ ; ASSERT (ROW_IS_ALIVE (r)) ; } } else { i = Col [c].shared2.order ; ASSERT (i >= n_col2 && i < n_col) ; } } for (r = 0 ; r < n_row ; r++) { if (ROW_IS_ALIVE (r)) { i = 0 ; len = Row [r].length ; deg = Row [r].shared1.degree ; ASSERT (len > 0) ; ASSERT (deg > 0) ; rp = &A [Row [r].start] ; rp_end = rp + len ; while (rp < rp_end) { c = *rp++ ; if (COL_IS_ALIVE (c)) { i++ ; } } ASSERT (i > 0) ; } } } /* ========================================================================== */ /* === debug_deg_lists ====================================================== */ /* ========================================================================== */ /* Prints the contents of the degree lists. Counts the number of columns in the degree list and compares it to the total it should have. Also checks the row degrees. */ PRIVATE void debug_deg_lists ( /* === Parameters ======================================================= */ Int n_row, Int n_col, Colamd_Row Row [], Colamd_Col Col [], Int head [], Int min_score, Int should, Int max_deg ) { /* === Local variables ================================================== */ Int deg ; Int col ; Int have ; Int row ; /* === Check the degree lists =========================================== */ if (n_col > 10000 && colamd_debug <= 0) { return ; } have = 0 ; DEBUG4 (("Degree lists: %d\n", min_score)) ; for (deg = 0 ; deg <= n_col ; deg++) { col = head [deg] ; if (col == EMPTY) { continue ; } DEBUG4 (("%d:", deg)) ; while (col != EMPTY) { DEBUG4 ((" %d", col)) ; have += Col [col].shared1.thickness ; ASSERT (COL_IS_ALIVE (col)) ; col = Col [col].shared4.degree_next ; } DEBUG4 (("\n")) ; } DEBUG4 (("should %d have %d\n", should, have)) ; ASSERT (should == have) ; /* === Check the row degrees ============================================ */ if (n_row > 10000 && colamd_debug <= 0) { return ; } for (row = 0 ; row < n_row ; row++) { if (ROW_IS_ALIVE (row)) { ASSERT (Row [row].shared1.degree <= max_deg) ; } } } /* ========================================================================== */ /* === debug_mark =========================================================== */ /* ========================================================================== */ /* Ensures that the tag_mark is less that the maximum and also ensures that each entry in the mark array is less than the tag mark. */ PRIVATE void debug_mark ( /* === Parameters ======================================================= */ Int n_row, Colamd_Row Row [], Int tag_mark, Int max_mark ) { /* === Local variables ================================================== */ Int r ; /* === Check the Row marks ============================================== */ ASSERT (tag_mark > 0 && tag_mark <= max_mark) ; if (n_row > 10000 && colamd_debug <= 0) { return ; } for (r = 0 ; r < n_row ; r++) { ASSERT (Row [r].shared2.mark < tag_mark) ; } } /* ========================================================================== */ /* === debug_matrix ========================================================= */ /* ========================================================================== */ /* Prints out the contents of the columns and the rows. */ PRIVATE void debug_matrix ( /* === Parameters ======================================================= */ Int n_row, Int n_col, Colamd_Row Row [], Colamd_Col Col [], Int A [] ) { /* === Local variables ================================================== */ Int r ; Int c ; Int *rp ; Int *rp_end ; Int *cp ; Int *cp_end ; /* === Dump the rows and columns of the matrix ========================== */ if (colamd_debug < 3) { return ; } DEBUG3 (("DUMP MATRIX:\n")) ; for (r = 0 ; r < n_row ; r++) { DEBUG3 (("Row %d alive? %d\n", r, ROW_IS_ALIVE (r))) ; if (ROW_IS_DEAD (r)) { continue ; } DEBUG3 (("start %d length %d degree %d\n", Row [r].start, Row [r].length, Row [r].shared1.degree)) ; rp = &A [Row [r].start] ; rp_end = rp + Row [r].length ; while (rp < rp_end) { c = *rp++ ; DEBUG4 ((" %d col %d\n", COL_IS_ALIVE (c), c)) ; } } for (c = 0 ; c < n_col ; c++) { DEBUG3 (("Col %d alive? %d\n", c, COL_IS_ALIVE (c))) ; if (COL_IS_DEAD (c)) { continue ; } DEBUG3 (("start %d length %d shared1 %d shared2 %d\n", Col [c].start, Col [c].length, Col [c].shared1.thickness, Col [c].shared2.score)) ; cp = &A [Col [c].start] ; cp_end = cp + Col [c].length ; while (cp < cp_end) { r = *cp++ ; DEBUG4 ((" %d row %d\n", ROW_IS_ALIVE (r), r)) ; } } } PRIVATE void colamd_get_debug ( char *method ) { FILE *f ; colamd_debug = 0 ; /* no debug printing */ f = fopen ("debug", "r") ; if (f == (FILE *) NULL) { colamd_debug = 0 ; } else { fscanf (f, "%d", &colamd_debug) ; fclose (f) ; } DEBUG0 (("%s: debug version, D = %d (THIS WILL BE SLOW!)\n", method, colamd_debug)) ; } #endif /* NDEBUG */ sources_5316/external/glpk/glpios02.c0000644000176700017670000006451711401660400016312 0ustar paulpaul/* glpios02.c (preprocess current subproblem) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*********************************************************************** * prepare_row_info - prepare row info to determine implied bounds * * Given a row (linear form) * * n * sum a[j] * x[j] (1) * j=1 * * and bounds of columns (variables) * * l[j] <= x[j] <= u[j] (2) * * this routine computes f_min, j_min, f_max, j_max needed to determine * implied bounds. * * ALGORITHM * * Let J+ = {j : a[j] > 0} and J- = {j : a[j] < 0}. * * Parameters f_min and j_min are computed as follows: * * 1) if there is no x[k] such that k in J+ and l[k] = -inf or k in J- * and u[k] = +inf, then * * f_min := sum a[j] * l[j] + sum a[j] * u[j] * j in J+ j in J- * (3) * j_min := 0 * * 2) if there is exactly one x[k] such that k in J+ and l[k] = -inf * or k in J- and u[k] = +inf, then * * f_min := sum a[j] * l[j] + sum a[j] * u[j] * j in J+\{k} j in J-\{k} * (4) * j_min := k * * 3) if there are two or more x[k] such that k in J+ and l[k] = -inf * or k in J- and u[k] = +inf, then * * f_min := -inf * (5) * j_min := 0 * * Parameters f_max and j_max are computed in a similar way as follows: * * 1) if there is no x[k] such that k in J+ and u[k] = +inf or k in J- * and l[k] = -inf, then * * f_max := sum a[j] * u[j] + sum a[j] * l[j] * j in J+ j in J- * (6) * j_max := 0 * * 2) if there is exactly one x[k] such that k in J+ and u[k] = +inf * or k in J- and l[k] = -inf, then * * f_max := sum a[j] * u[j] + sum a[j] * l[j] * j in J+\{k} j in J-\{k} * (7) * j_max := k * * 3) if there are two or more x[k] such that k in J+ and u[k] = +inf * or k in J- and l[k] = -inf, then * * f_max := +inf * (8) * j_max := 0 */ struct f_info { int j_min, j_max; double f_min, f_max; }; static void prepare_row_info(int n, const double a[], const double l[], const double u[], struct f_info *f) { int j, j_min, j_max; double f_min, f_max; xassert(n >= 0); /* determine f_min and j_min */ f_min = 0.0, j_min = 0; for (j = 1; j <= n; j++) { if (a[j] > 0.0) { if (l[j] == -DBL_MAX) { if (j_min == 0) j_min = j; else { f_min = -DBL_MAX, j_min = 0; break; } } else f_min += a[j] * l[j]; } else if (a[j] < 0.0) { if (u[j] == +DBL_MAX) { if (j_min == 0) j_min = j; else { f_min = -DBL_MAX, j_min = 0; break; } } else f_min += a[j] * u[j]; } else xassert(a != a); } f->f_min = f_min, f->j_min = j_min; /* determine f_max and j_max */ f_max = 0.0, j_max = 0; for (j = 1; j <= n; j++) { if (a[j] > 0.0) { if (u[j] == +DBL_MAX) { if (j_max == 0) j_max = j; else { f_max = +DBL_MAX, j_max = 0; break; } } else f_max += a[j] * u[j]; } else if (a[j] < 0.0) { if (l[j] == -DBL_MAX) { if (j_max == 0) j_max = j; else { f_max = +DBL_MAX, j_max = 0; break; } } else f_max += a[j] * l[j]; } else xassert(a != a); } f->f_max = f_max, f->j_max = j_max; return; } /*********************************************************************** * row_implied_bounds - determine row implied bounds * * Given a row (linear form) * * n * sum a[j] * x[j] * j=1 * * and bounds of columns (variables) * * l[j] <= x[j] <= u[j] * * this routine determines implied bounds of the row. * * ALGORITHM * * Let J+ = {j : a[j] > 0} and J- = {j : a[j] < 0}. * * The implied lower bound of the row is computed as follows: * * L' := sum a[j] * l[j] + sum a[j] * u[j] (9) * j in J+ j in J- * * and as it follows from (3), (4), and (5): * * L' := if j_min = 0 then f_min else -inf (10) * * The implied upper bound of the row is computed as follows: * * U' := sum a[j] * u[j] + sum a[j] * l[j] (11) * j in J+ j in J- * * and as it follows from (6), (7), and (8): * * U' := if j_max = 0 then f_max else +inf (12) * * The implied bounds are stored in locations LL and UU. */ static void row_implied_bounds(const struct f_info *f, double *LL, double *UU) { *LL = (f->j_min == 0 ? f->f_min : -DBL_MAX); *UU = (f->j_max == 0 ? f->f_max : +DBL_MAX); return; } /*********************************************************************** * col_implied_bounds - determine column implied bounds * * Given a row (constraint) * * n * L <= sum a[j] * x[j] <= U (13) * j=1 * * and bounds of columns (variables) * * l[j] <= x[j] <= u[j] * * this routine determines implied bounds of variable x[k]. * * It is assumed that if L != -inf, the lower bound of the row can be * active, and if U != +inf, the upper bound of the row can be active. * * ALGORITHM * * From (13) it follows that * * L <= sum a[j] * x[j] + a[k] * x[k] <= U * j!=k * or * * L - sum a[j] * x[j] <= a[k] * x[k] <= U - sum a[j] * x[j] * j!=k j!=k * * Thus, if the row lower bound L can be active, implied lower bound of * term a[k] * x[k] can be determined as follows: * * ilb(a[k] * x[k]) = min(L - sum a[j] * x[j]) = * j!=k * (14) * = L - max sum a[j] * x[j] * j!=k * * where, as it follows from (6), (7), and (8) * * / f_max - a[k] * u[k], j_max = 0, a[k] > 0 * | * | f_max - a[k] * l[k], j_max = 0, a[k] < 0 * max sum a[j] * x[j] = { * j!=k | f_max, j_max = k * | * \ +inf, j_max != 0 * * and if the upper bound U can be active, implied upper bound of term * a[k] * x[k] can be determined as follows: * * iub(a[k] * x[k]) = max(U - sum a[j] * x[j]) = * j!=k * (15) * = U - min sum a[j] * x[j] * j!=k * * where, as it follows from (3), (4), and (5) * * / f_min - a[k] * l[k], j_min = 0, a[k] > 0 * | * | f_min - a[k] * u[k], j_min = 0, a[k] < 0 * min sum a[j] * x[j] = { * j!=k | f_min, j_min = k * | * \ -inf, j_min != 0 * * Since * * ilb(a[k] * x[k]) <= a[k] * x[k] <= iub(a[k] * x[k]) * * implied lower and upper bounds of x[k] are determined as follows: * * l'[k] := if a[k] > 0 then ilb / a[k] else ulb / a[k] (16) * * u'[k] := if a[k] > 0 then ulb / a[k] else ilb / a[k] (17) * * The implied bounds are stored in locations ll and uu. */ static void col_implied_bounds(const struct f_info *f, int n, const double a[], double L, double U, const double l[], const double u[], int k, double *ll, double *uu) { double ilb, iub; xassert(n >= 0); xassert(1 <= k && k <= n); /* determine implied lower bound of term a[k] * x[k] (14) */ if (L == -DBL_MAX || f->f_max == +DBL_MAX) ilb = -DBL_MAX; else if (f->j_max == 0) { if (a[k] > 0.0) { xassert(u[k] != +DBL_MAX); ilb = L - (f->f_max - a[k] * u[k]); } else if (a[k] < 0.0) { xassert(l[k] != -DBL_MAX); ilb = L - (f->f_max - a[k] * l[k]); } else xassert(a != a); } else if (f->j_max == k) ilb = L - f->f_max; else ilb = -DBL_MAX; /* determine implied upper bound of term a[k] * x[k] (15) */ if (U == +DBL_MAX || f->f_min == -DBL_MAX) iub = +DBL_MAX; else if (f->j_min == 0) { if (a[k] > 0.0) { xassert(l[k] != -DBL_MAX); iub = U - (f->f_min - a[k] * l[k]); } else if (a[k] < 0.0) { xassert(u[k] != +DBL_MAX); iub = U - (f->f_min - a[k] * u[k]); } else xassert(a != a); } else if (f->j_min == k) iub = U - f->f_min; else iub = +DBL_MAX; /* determine implied bounds of x[k] (16) and (17) */ #if 1 /* do not use a[k] if it has small magnitude to prevent wrong implied bounds; for example, 1e-15 * x1 >= x2 + x3, where x1 >= -10, x2, x3 >= 0, would lead to wrong conclusion that x1 >= 0 */ if (fabs(a[k]) < 1e-6) *ll = -DBL_MAX, *uu = +DBL_MAX; else #endif if (a[k] > 0.0) { *ll = (ilb == -DBL_MAX ? -DBL_MAX : ilb / a[k]); *uu = (iub == +DBL_MAX ? +DBL_MAX : iub / a[k]); } else if (a[k] < 0.0) { *ll = (iub == +DBL_MAX ? -DBL_MAX : iub / a[k]); *uu = (ilb == -DBL_MAX ? +DBL_MAX : ilb / a[k]); } else xassert(a != a); return; } /*********************************************************************** * check_row_bounds - check and relax original row bounds * * Given a row (constraint) * * n * L <= sum a[j] * x[j] <= U * j=1 * * and bounds of columns (variables) * * l[j] <= x[j] <= u[j] * * this routine checks the original row bounds L and U for feasibility * and redundancy. If the original lower bound L or/and upper bound U * cannot be active due to bounds of variables, the routine remove them * replacing by -inf or/and +inf, respectively. * * If no primal infeasibility is detected, the routine returns zero, * otherwise non-zero. */ static int check_row_bounds(const struct f_info *f, double *L_, double *U_) { int ret = 0; double L = *L_, U = *U_, LL, UU; /* determine implied bounds of the row */ row_implied_bounds(f, &LL, &UU); /* check if the original lower bound is infeasible */ if (L != -DBL_MAX) { double eps = 1e-3 * (1.0 + fabs(L)); if (UU < L - eps) { ret = 1; goto done; } } /* check if the original upper bound is infeasible */ if (U != +DBL_MAX) { double eps = 1e-3 * (1.0 + fabs(U)); if (LL > U + eps) { ret = 1; goto done; } } /* check if the original lower bound is redundant */ if (L != -DBL_MAX) { double eps = 1e-12 * (1.0 + fabs(L)); if (LL > L - eps) { /* it cannot be active, so remove it */ *L_ = -DBL_MAX; } } /* check if the original upper bound is redundant */ if (U != +DBL_MAX) { double eps = 1e-12 * (1.0 + fabs(U)); if (UU < U + eps) { /* it cannot be active, so remove it */ *U_ = +DBL_MAX; } } done: return ret; } /*********************************************************************** * check_col_bounds - check and tighten original column bounds * * Given a row (constraint) * * n * L <= sum a[j] * x[j] <= U * j=1 * * and bounds of columns (variables) * * l[j] <= x[j] <= u[j] * * for column (variable) x[j] this routine checks the original column * bounds l[j] and u[j] for feasibility and redundancy. If the original * lower bound l[j] or/and upper bound u[j] cannot be active due to * bounds of the constraint and other variables, the routine tighten * them replacing by corresponding implied bounds, if possible. * * NOTE: It is assumed that if L != -inf, the row lower bound can be * active, and if U != +inf, the row upper bound can be active. * * The flag means that variable x[j] is required to be integer. * * New actual bounds for x[j] are stored in locations lj and uj. * * If no primal infeasibility is detected, the routine returns zero, * otherwise non-zero. */ static int check_col_bounds(const struct f_info *f, int n, const double a[], double L, double U, const double l[], const double u[], int flag, int j, double *_lj, double *_uj) { int ret = 0; double lj, uj, ll, uu; xassert(n >= 0); xassert(1 <= j && j <= n); lj = l[j], uj = u[j]; /* determine implied bounds of the column */ col_implied_bounds(f, n, a, L, U, l, u, j, &ll, &uu); /* if x[j] is integral, round its implied bounds */ if (flag) { if (ll != -DBL_MAX) ll = (ll - floor(ll) < 1e-3 ? floor(ll) : ceil(ll)); if (uu != +DBL_MAX) uu = (ceil(uu) - uu < 1e-3 ? ceil(uu) : floor(uu)); } /* check if the original lower bound is infeasible */ if (lj != -DBL_MAX) { double eps = 1e-3 * (1.0 + fabs(lj)); if (uu < lj - eps) { ret = 1; goto done; } } /* check if the original upper bound is infeasible */ if (uj != +DBL_MAX) { double eps = 1e-3 * (1.0 + fabs(uj)); if (ll > uj + eps) { ret = 1; goto done; } } /* check if the original lower bound is redundant */ if (ll != -DBL_MAX) { double eps = 1e-3 * (1.0 + fabs(ll)); if (lj < ll - eps) { /* it cannot be active, so tighten it */ lj = ll; } } /* check if the original upper bound is redundant */ if (uu != +DBL_MAX) { double eps = 1e-3 * (1.0 + fabs(uu)); if (uj > uu + eps) { /* it cannot be active, so tighten it */ uj = uu; } } /* due to round-off errors it may happen that lj > uj (although lj < uj + eps, since no primal infeasibility is detected), so adjuct the new actual bounds to provide lj <= uj */ if (!(lj == -DBL_MAX || uj == +DBL_MAX)) { double t1 = fabs(lj), t2 = fabs(uj); double eps = 1e-10 * (1.0 + (t1 <= t2 ? t1 : t2)); if (lj > uj - eps) { if (lj == l[j]) uj = lj; else if (uj == u[j]) lj = uj; else if (t1 <= t2) uj = lj; else lj = uj; } } *_lj = lj, *_uj = uj; done: return ret; } /*********************************************************************** * check_efficiency - check if change in column bounds is efficient * * Given the original bounds of a column l and u and its new actual * bounds l' and u' (possibly tighten by the routine check_col_bounds) * this routine checks if the change in the column bounds is efficient * enough. If so, the routine returns non-zero, otherwise zero. * * The flag means that the variable is required to be integer. */ static int check_efficiency(int flag, double l, double u, double ll, double uu) { int eff = 0; /* check efficiency for lower bound */ if (l < ll) { if (flag || l == -DBL_MAX) eff++; else { double r; if (u == +DBL_MAX) r = 1.0 + fabs(l); else r = 1.0 + (u - l); if (ll - l >= 0.25 * r) eff++; } } /* check efficiency for upper bound */ if (u > uu) { if (flag || u == +DBL_MAX) eff++; else { double r; if (l == -DBL_MAX) r = 1.0 + fabs(u); else r = 1.0 + (u - l); if (u - uu >= 0.25 * r) eff++; } } return eff; } /*********************************************************************** * basic_preprocessing - perform basic preprocessing * * This routine performs basic preprocessing of the specified MIP that * includes relaxing some row bounds and tightening some column bounds. * * On entry the arrays L and U contains original row bounds, and the * arrays l and u contains original column bounds: * * L[0] is the lower bound of the objective row; * L[i], i = 1,...,m, is the lower bound of i-th row; * U[0] is the upper bound of the objective row; * U[i], i = 1,...,m, is the upper bound of i-th row; * l[0] is not used; * l[j], j = 1,...,n, is the lower bound of j-th column; * u[0] is not used; * u[j], j = 1,...,n, is the upper bound of j-th column. * * On exit the arrays L, U, l, and u contain new actual bounds of rows * and column in the same locations. * * The parameters nrs and num specify an initial list of rows to be * processed: * * nrs is the number of rows in the initial list, 0 <= nrs <= m+1; * num[0] is not used; * num[1,...,nrs] are row numbers (0 means the objective row). * * The parameter max_pass specifies the maximal number of times that * each row can be processed, max_pass > 0. * * If no primal infeasibility is detected, the routine returns zero, * otherwise non-zero. */ static int basic_preprocessing(glp_prob *mip, double L[], double U[], double l[], double u[], int nrs, const int num[], int max_pass) { int m = mip->m; int n = mip->n; struct f_info f; int i, j, k, len, size, ret = 0; int *ind, *list, *mark, *pass; double *val, *lb, *ub; xassert(0 <= nrs && nrs <= m+1); xassert(max_pass > 0); /* allocate working arrays */ ind = xcalloc(1+n, sizeof(int)); list = xcalloc(1+m+1, sizeof(int)); mark = xcalloc(1+m+1, sizeof(int)); memset(&mark[0], 0, (m+1) * sizeof(int)); pass = xcalloc(1+m+1, sizeof(int)); memset(&pass[0], 0, (m+1) * sizeof(int)); val = xcalloc(1+n, sizeof(double)); lb = xcalloc(1+n, sizeof(double)); ub = xcalloc(1+n, sizeof(double)); /* initialize the list of rows to be processed */ size = 0; for (k = 1; k <= nrs; k++) { i = num[k]; xassert(0 <= i && i <= m); /* duplicate row numbers are not allowed */ xassert(!mark[i]); list[++size] = i, mark[i] = 1; } xassert(size == nrs); /* process rows in the list until it becomes empty */ while (size > 0) { /* get a next row from the list */ i = list[size--], mark[i] = 0; /* increase the row processing count */ pass[i]++; /* if the row is free, skip it */ if (L[i] == -DBL_MAX && U[i] == +DBL_MAX) continue; /* obtain coefficients of the row */ len = 0; if (i == 0) { for (j = 1; j <= n; j++) { GLPCOL *col = mip->col[j]; if (col->coef != 0.0) len++, ind[len] = j, val[len] = col->coef; } } else { GLPROW *row = mip->row[i]; GLPAIJ *aij; for (aij = row->ptr; aij != NULL; aij = aij->r_next) len++, ind[len] = aij->col->j, val[len] = aij->val; } /* determine lower and upper bounds of columns corresponding to non-zero row coefficients */ for (k = 1; k <= len; k++) j = ind[k], lb[k] = l[j], ub[k] = u[j]; /* prepare the row info to determine implied bounds */ prepare_row_info(len, val, lb, ub, &f); /* check and relax bounds of the row */ if (check_row_bounds(&f, &L[i], &U[i])) { /* the feasible region is empty */ ret = 1; goto done; } /* if the row became free, drop it */ if (L[i] == -DBL_MAX && U[i] == +DBL_MAX) continue; /* process columns having non-zero coefficients in the row */ for (k = 1; k <= len; k++) { GLPCOL *col; int flag, eff; double ll, uu; /* take a next column in the row */ j = ind[k], col = mip->col[j]; flag = col->kind != GLP_CV; /* check and tighten bounds of the column */ if (check_col_bounds(&f, len, val, L[i], U[i], lb, ub, flag, k, &ll, &uu)) { /* the feasible region is empty */ ret = 1; goto done; } /* check if change in the column bounds is efficient */ eff = check_efficiency(flag, l[j], u[j], ll, uu); /* set new actual bounds of the column */ l[j] = ll, u[j] = uu; /* if the change is efficient, add all rows affected by the corresponding column, to the list */ if (eff > 0) { GLPAIJ *aij; for (aij = col->ptr; aij != NULL; aij = aij->c_next) { int ii = aij->row->i; /* if the row was processed maximal number of times, skip it */ if (pass[ii] >= max_pass) continue; /* if the row is free, skip it */ if (L[ii] == -DBL_MAX && U[ii] == +DBL_MAX) continue; /* put the row into the list */ if (mark[ii] == 0) { xassert(size <= m); list[++size] = ii, mark[ii] = 1; } } } } } done: /* free working arrays */ xfree(ind); xfree(list); xfree(mark); xfree(pass); xfree(val); xfree(lb); xfree(ub); return ret; } /*********************************************************************** * NAME * * ios_preprocess_node - preprocess current subproblem * * SYNOPSIS * * #include "glpios.h" * int ios_preprocess_node(glp_tree *tree, int max_pass); * * DESCRIPTION * * The routine ios_preprocess_node performs basic preprocessing of the * current subproblem. * * RETURNS * * If no primal infeasibility is detected, the routine returns zero, * otherwise non-zero. */ int ios_preprocess_node(glp_tree *tree, int max_pass) { glp_prob *mip = tree->mip; int m = mip->m; int n = mip->n; int i, j, nrs, *num, ret = 0; double *L, *U, *l, *u; /* the current subproblem must exist */ xassert(tree->curr != NULL); /* determine original row bounds */ L = xcalloc(1+m, sizeof(double)); U = xcalloc(1+m, sizeof(double)); switch (mip->mip_stat) { case GLP_UNDEF: L[0] = -DBL_MAX, U[0] = +DBL_MAX; break; case GLP_FEAS: switch (mip->dir) { case GLP_MIN: L[0] = -DBL_MAX, U[0] = mip->mip_obj - mip->c0; break; case GLP_MAX: L[0] = mip->mip_obj - mip->c0, U[0] = +DBL_MAX; break; default: xassert(mip != mip); } break; default: xassert(mip != mip); } for (i = 1; i <= m; i++) { L[i] = glp_get_row_lb(mip, i); U[i] = glp_get_row_ub(mip, i); } /* determine original column bounds */ l = xcalloc(1+n, sizeof(double)); u = xcalloc(1+n, sizeof(double)); for (j = 1; j <= n; j++) { l[j] = glp_get_col_lb(mip, j); u[j] = glp_get_col_ub(mip, j); } /* build the initial list of rows to be analyzed */ nrs = m + 1; num = xcalloc(1+nrs, sizeof(int)); for (i = 1; i <= nrs; i++) num[i] = i - 1; /* perform basic preprocessing */ if (basic_preprocessing(mip , L, U, l, u, nrs, num, max_pass)) { ret = 1; goto done; } /* set new actual (relaxed) row bounds */ for (i = 1; i <= m; i++) { /* consider only non-active rows to keep dual feasibility */ if (glp_get_row_stat(mip, i) == GLP_BS) { if (L[i] == -DBL_MAX && U[i] == +DBL_MAX) glp_set_row_bnds(mip, i, GLP_FR, 0.0, 0.0); else if (U[i] == +DBL_MAX) glp_set_row_bnds(mip, i, GLP_LO, L[i], 0.0); else if (L[i] == -DBL_MAX) glp_set_row_bnds(mip, i, GLP_UP, 0.0, U[i]); } } /* set new actual (tightened) column bounds */ for (j = 1; j <= n; j++) { int type; if (l[j] == -DBL_MAX && u[j] == +DBL_MAX) type = GLP_FR; else if (u[j] == +DBL_MAX) type = GLP_LO; else if (l[j] == -DBL_MAX) type = GLP_UP; else if (l[j] != u[j]) type = GLP_DB; else type = GLP_FX; glp_set_col_bnds(mip, j, type, l[j], u[j]); } done: /* free working arrays and return */ xfree(L); xfree(U); xfree(l); xfree(u); xfree(num); return ret; } /* eof */ sources_5316/external/glpk/glprng.h0000644000176700017670000000434611401660400016143 0ustar paulpaul/* glprng.h (pseudo-random number generator) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPRNG_H #define GLPRNG_H typedef struct RNG RNG; struct RNG { /* Knuth's portable pseudo-random number generator */ int A[56]; /* pseudo-random values */ int *fptr; /* the next A value to be exported */ }; #define rng_create_rand _glp_rng_create_rand RNG *rng_create_rand(void); /* create pseudo-random number generator */ #define rng_init_rand _glp_rng_init_rand void rng_init_rand(RNG *rand, int seed); /* initialize pseudo-random number generator */ #define rng_next_rand _glp_rng_next_rand int rng_next_rand(RNG *rand); /* obtain pseudo-random integer in the range [0, 2^31-1] */ #define rng_unif_rand _glp_rng_unif_rand int rng_unif_rand(RNG *rand, int m); /* obtain pseudo-random integer in the range [0, m-1] */ #define rng_delete_rand _glp_rng_delete_rand void rng_delete_rand(RNG *rand); /* delete pseudo-random number generator */ #define rng_unif_01 _glp_rng_unif_01 double rng_unif_01(RNG *rand); /* obtain pseudo-random number in the range [0, 1] */ #define rng_uniform _glp_rng_uniform double rng_uniform(RNG *rand, double a, double b); /* obtain pseudo-random number in the range [a, b] */ #endif /* eof */ sources_5316/external/glpk/glpnet07.c0000644000176700017670000001653411401660400016307 0ustar paulpaul/* glpnet07.c (Ford-Fulkerson algorithm) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glpnet.h" /*********************************************************************** * NAME * * ffalg - Ford-Fulkerson algorithm * * SYNOPSIS * * #include "glpnet.h" * void ffalg(int nv, int na, const int tail[], const int head[], * int s, int t, const int cap[], int x[], char cut[]); * * DESCRIPTION * * The routine ffalg implements the Ford-Fulkerson algorithm to find a * maximal flow in the specified flow network. * * INPUT PARAMETERS * * nv is the number of nodes, nv >= 2. * * na is the number of arcs, na >= 0. * * tail[a], a = 1,...,na, is the index of tail node of arc a. * * head[a], a = 1,...,na, is the index of head node of arc a. * * s is the source node index, 1 <= s <= nv. * * t is the sink node index, 1 <= t <= nv, t != s. * * cap[a], a = 1,...,na, is the capacity of arc a, cap[a] >= 0. * * NOTE: Multiple arcs are allowed, but self-loops are not allowed. * * OUTPUT PARAMETERS * * x[a], a = 1,...,na, is optimal value of the flow through arc a. * * cut[i], i = 1,...,nv, is 1 if node i is labelled, and 0 otherwise. * The set of arcs, whose one endpoint is labelled and other is not, * defines the minimal cut corresponding to the maximal flow found. * If the parameter cut is NULL, the cut information are not stored. * * REFERENCES * * L.R.Ford, Jr., and D.R.Fulkerson, "Flows in Networks," The RAND * Corp., Report R-375-PR (August 1962), Chap. I "Static Maximal Flow," * pp.30-33. */ void ffalg(int nv, int na, const int tail[], const int head[], int s, int t, const int cap[], int x[], char cut[]) { int a, delta, i, j, k, pos1, pos2, temp, *ptr, *arc, *link, *list; /* sanity checks */ xassert(nv >= 2); xassert(na >= 0); xassert(1 <= s && s <= nv); xassert(1 <= t && t <= nv); xassert(s != t); for (a = 1; a <= na; a++) { i = tail[a], j = head[a]; xassert(1 <= i && i <= nv); xassert(1 <= j && j <= nv); xassert(i != j); xassert(cap[a] >= 0); } /* allocate working arrays */ ptr = xcalloc(1+nv+1, sizeof(int)); arc = xcalloc(1+na+na, sizeof(int)); link = xcalloc(1+nv, sizeof(int)); list = xcalloc(1+nv, sizeof(int)); /* ptr[i] := (degree of node i) */ for (i = 1; i <= nv; i++) ptr[i] = 0; for (a = 1; a <= na; a++) { ptr[tail[a]]++; ptr[head[a]]++; } /* initialize arc pointers */ ptr[1]++; for (i = 1; i < nv; i++) ptr[i+1] += ptr[i]; ptr[nv+1] = ptr[nv]; /* build arc lists */ for (a = 1; a <= na; a++) { arc[--ptr[tail[a]]] = a; arc[--ptr[head[a]]] = a; } xassert(ptr[1] == 1); xassert(ptr[nv+1] == na+na+1); /* now the indices of arcs incident to node i are stored in locations arc[ptr[i]], arc[ptr[i]+1], ..., arc[ptr[i+1]-1] */ /* initialize arc flows */ for (a = 1; a <= na; a++) x[a] = 0; loop: /* main loop starts here */ /* build augmenting tree rooted at s */ /* link[i] = 0 means that node i is not labelled yet; link[i] = a means that arc a immediately precedes node i */ /* initially node s is labelled as the root */ for (i = 1; i <= nv; i++) link[i] = 0; link[s] = -1, list[1] = s, pos1 = pos2 = 1; /* breadth first search */ while (pos1 <= pos2) { /* dequeue node i */ i = list[pos1++]; /* consider all arcs incident to node i */ for (k = ptr[i]; k < ptr[i+1]; k++) { a = arc[k]; if (tail[a] == i) { /* a = i->j is a forward arc from s to t */ j = head[a]; /* if node j has been labelled, skip the arc */ if (link[j] != 0) continue; /* if the arc does not allow increasing the flow through it, skip the arc */ if (x[a] == cap[a]) continue; } else if (head[a] == i) { /* a = i<-j is a backward arc from s to t */ j = tail[a]; /* if node j has been labelled, skip the arc */ if (link[j] != 0) continue; /* if the arc does not allow decreasing the flow through it, skip the arc */ if (x[a] == 0) continue; } else xassert(a != a); /* label node j and enqueue it */ link[j] = a, list[++pos2] = j; /* check for breakthrough */ if (j == t) goto brkt; } } /* NONBREAKTHROUGH */ /* no augmenting path exists; current flow is maximal */ /* store minimal cut information, if necessary */ if (cut != NULL) { for (i = 1; i <= nv; i++) cut[i] = (char)(link[i] != 0); } goto done; brkt: /* BREAKTHROUGH */ /* walk through arcs of the augmenting path (s, ..., t) found in the reverse order and determine maximal change of the flow */ delta = 0; for (j = t; j != s; j = i) { /* arc a immediately precedes node j in the path */ a = link[j]; if (head[a] == j) { /* a = i->j is a forward arc of the cycle */ i = tail[a]; /* x[a] may be increased until its upper bound */ temp = cap[a] - x[a]; } else if (tail[a] == j) { /* a = i<-j is a backward arc of the cycle */ i = head[a]; /* x[a] may be decreased until its lower bound */ temp = x[a]; } else xassert(a != a); if (delta == 0 || delta > temp) delta = temp; } xassert(delta > 0); /* increase the flow along the path */ for (j = t; j != s; j = i) { /* arc a immediately precedes node j in the path */ a = link[j]; if (head[a] == j) { /* a = i->j is a forward arc of the cycle */ i = tail[a]; x[a] += delta; } else if (tail[a] == j) { /* a = i<-j is a backward arc of the cycle */ i = head[a]; x[a] -= delta; } else xassert(a != a); } goto loop; done: /* free working arrays */ xfree(ptr); xfree(arc); xfree(link); xfree(list); return; } /* eof */ sources_5316/external/glpk/glpnet09.c0000644000176700017670000002230111401660400016276 0ustar paulpaul/* glpnet09.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" #include "glpnet.h" /*********************************************************************** * NAME * * kellerman - cover edges by cliques with Kellerman's heuristic * * SYNOPSIS * * #include "glpnet.h" * int kellerman(int n, int (*func)(void *info, int i, int ind[]), * void *info, glp_graph *H); * * DESCRIPTION * * The routine kellerman implements Kellerman's heuristic algorithm * to find a minimal set of cliques which cover all edges of specified * graph G = (V, E). * * The parameter n specifies the number of vertices |V|, n >= 0. * * Formal routine func specifies the set of edges E in the following * way. Running the routine kellerman calls the routine func and passes * to it parameter i, which is the number of some vertex, 1 <= i <= n. * In response the routine func should store numbers of all vertices * adjacent to vertex i to locations ind[1], ind[2], ..., ind[len] and * return the value of len, which is the number of adjacent vertices, * 0 <= len <= n. Self-loops are allowed, but ignored. Multiple edges * are not allowed. * * The parameter info is a transit pointer (magic cookie) passed to the * formal routine func as its first parameter. * * The result provided by the routine kellerman is the bipartite graph * H = (V union C, F), which defines the covering found. (The program * object of type glp_graph specified by the parameter H should be * previously created with the routine glp_create_graph. On entry the * routine kellerman erases the content of this object with the routine * glp_erase_graph.) Vertices of first part V correspond to vertices of * the graph G and have the same ordinal numbers 1, 2, ..., n. Vertices * of second part C correspond to cliques and have ordinal numbers * n+1, n+2, ..., n+k, where k is the total number of cliques in the * edge covering found. Every edge f in F in the program object H is * represented as arc f = (i->j), where i in V and j in C, which means * that vertex i of the graph G is in clique C[j], 1 <= j <= k. (Thus, * if two vertices of the graph G are in the same clique, these vertices * are adjacent in G, and corresponding edge is covered by that clique.) * * RETURNS * * The routine Kellerman returns k, the total number of cliques in the * edge covering found. * * REFERENCE * * For more details see: glpk/doc/notes/keller.pdf (in Russian). */ struct set { /* set of vertices */ int size; /* size (cardinality) of the set, 0 <= card <= n */ int *list; /* int list[1+n]; */ /* the set contains vertices list[1,...,size] */ int *pos; /* int pos[1+n]; */ /* pos[i] > 0 means that vertex i is in the set and list[pos[i]] = i; pos[i] = 0 means that vertex i is not in the set */ }; int kellerman(int n, int (*func)(void *info, int i, int ind[]), void *info, void /* glp_graph */ *H_) { glp_graph *H = H_; struct set W_, *W = &W_, V_, *V = &V_; glp_arc *a; int i, j, k, m, t, len, card, best; xassert(n >= 0); /* H := (V, 0; 0), where V is the set of vertices of graph G */ glp_erase_graph(H, H->v_size, H->a_size); glp_add_vertices(H, n); /* W := 0 */ W->size = 0; W->list = xcalloc(1+n, sizeof(int)); W->pos = xcalloc(1+n, sizeof(int)); memset(&W->pos[1], 0, sizeof(int) * n); /* V := 0 */ V->size = 0; V->list = xcalloc(1+n, sizeof(int)); V->pos = xcalloc(1+n, sizeof(int)); memset(&V->pos[1], 0, sizeof(int) * n); /* main loop */ for (i = 1; i <= n; i++) { /* W must be empty */ xassert(W->size == 0); /* W := { j : i > j and (i,j) in E } */ len = func(info, i, W->list); xassert(0 <= len && len <= n); for (t = 1; t <= len; t++) { j = W->list[t]; xassert(1 <= j && j <= n); if (j >= i) continue; xassert(W->pos[j] == 0); W->list[++W->size] = j, W->pos[j] = W->size; } /* on i-th iteration we need to cover edges (i,j) for all j in W */ /* if W is empty, it is a special case */ if (W->size == 0) { /* set k := k + 1 and create new clique C[k] = { i } */ k = glp_add_vertices(H, 1) - n; glp_add_arc(H, i, n + k); continue; } /* try to include vertex i into existing cliques */ /* V must be empty */ xassert(V->size == 0); /* k is the number of cliques found so far */ k = H->nv - n; for (m = 1; m <= k; m++) { /* do while V != W; since here V is within W, we can use equivalent condition: do while |V| < |W| */ if (V->size == W->size) break; /* check if C[m] is within W */ for (a = H->v[n + m]->in; a != NULL; a = a->h_next) { j = a->tail->i; if (W->pos[j] == 0) break; } if (a != NULL) continue; /* C[m] is within W, expand clique C[m] with vertex i */ /* C[m] := C[m] union {i} */ glp_add_arc(H, i, n + m); /* V is a set of vertices whose incident edges are already covered by existing cliques */ /* V := V union C[m] */ for (a = H->v[n + m]->in; a != NULL; a = a->h_next) { j = a->tail->i; if (V->pos[j] == 0) V->list[++V->size] = j, V->pos[j] = V->size; } } /* remove from set W the vertices whose incident edges are already covered by existing cliques */ /* W := W \ V, V := 0 */ for (t = 1; t <= V->size; t++) { j = V->list[t], V->pos[j] = 0; if (W->pos[j] != 0) { /* remove vertex j from W */ if (W->pos[j] != W->size) { int jj = W->list[W->size]; W->list[W->pos[j]] = jj; W->pos[jj] = W->pos[j]; } W->size--, W->pos[j] = 0; } } V->size = 0; /* now set W contains only vertices whose incident edges are still not covered by existing cliques; create new cliques to cover remaining edges until set W becomes empty */ while (W->size > 0) { /* find clique C[m], 1 <= m <= k, which shares maximal number of vertices with W; to break ties choose clique having smallest number m */ m = 0, best = -1; k = H->nv - n; for (t = 1; t <= k; t++) { /* compute cardinality of intersection of W and C[t] */ card = 0; for (a = H->v[n + t]->in; a != NULL; a = a->h_next) { j = a->tail->i; if (W->pos[j] != 0) card++; } if (best < card) m = t, best = card; } xassert(m > 0); /* set k := k + 1 and create new clique: C[k] := (W intersect C[m]) union { i }, which covers all edges incident to vertices from (W intersect C[m]) */ k = glp_add_vertices(H, 1) - n; for (a = H->v[n + m]->in; a != NULL; a = a->h_next) { j = a->tail->i; if (W->pos[j] != 0) { /* vertex j is in both W and C[m]; include it in new clique C[k] */ glp_add_arc(H, j, n + k); /* remove vertex j from W, since edge (i,j) will be covered by new clique C[k] */ if (W->pos[j] != W->size) { int jj = W->list[W->size]; W->list[W->pos[j]] = jj; W->pos[jj] = W->pos[j]; } W->size--, W->pos[j] = 0; } } /* include vertex i to new clique C[k] to cover edges (i,j) incident to all vertices j just removed from W */ glp_add_arc(H, i, n + k); } } /* free working arrays */ xfree(W->list); xfree(W->pos); xfree(V->list); xfree(V->pos); /* return the number of cliques in the edge covering found */ return H->nv - n; } /* eof */ sources_5316/external/glpk/amd_control.c0000644000176700017670000000370111401660400017140 0ustar paulpaul/* ========================================================================= */ /* === AMD_control ========================================================= */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* User-callable. Prints the control parameters for AMD. See amd.h * for details. If the Control array is not present, the defaults are * printed instead. */ #include "amd_internal.h" GLOBAL void AMD_control ( double Control [ ] ) { double alpha ; Int aggressive ; if (Control != (double *) NULL) { alpha = Control [AMD_DENSE] ; aggressive = Control [AMD_AGGRESSIVE] != 0 ; } else { alpha = AMD_DEFAULT_DENSE ; aggressive = AMD_DEFAULT_AGGRESSIVE ; } PRINTF (("\nAMD version %d.%d.%d, %s: approximate minimum degree ordering\n" " dense row parameter: %g\n", AMD_MAIN_VERSION, AMD_SUB_VERSION, AMD_SUBSUB_VERSION, AMD_DATE, alpha)) ; if (alpha < 0) { PRINTF ((" no rows treated as dense\n")) ; } else { PRINTF (( " (rows with more than max (%g * sqrt (n), 16) entries are\n" " considered \"dense\", and placed last in output permutation)\n", alpha)) ; } if (aggressive) { PRINTF ((" aggressive absorption: yes\n")) ; } else { PRINTF ((" aggressive absorption: no\n")) ; } PRINTF ((" size of AMD integer: %d\n\n", sizeof (Int))) ; } sources_5316/external/glpk/glpapi03.c0000644000176700017670000001215711401660400016263 0ustar paulpaul/* glpapi03.c (row and column searching routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_create_index - create the name index * * SYNOPSIS * * void glp_create_index(glp_prob *lp); * * DESCRIPTION * * The routine glp_create_index creates the name index for the * specified problem object. The name index is an auxiliary data * structure, which is intended to quickly (i.e. for logarithmic time) * find rows and columns by their names. * * This routine can be called at any time. If the name index already * exists, the routine does nothing. */ void glp_create_index(glp_prob *lp) { GLPROW *row; GLPCOL *col; int i, j; /* create row name index */ if (lp->r_tree == NULL) { lp->r_tree = avl_create_tree(avl_strcmp, NULL); for (i = 1; i <= lp->m; i++) { row = lp->row[i]; xassert(row->node == NULL); if (row->name != NULL) { row->node = avl_insert_node(lp->r_tree, row->name); avl_set_node_link(row->node, row); } } } /* create column name index */ if (lp->c_tree == NULL) { lp->c_tree = avl_create_tree(avl_strcmp, NULL); for (j = 1; j <= lp->n; j++) { col = lp->col[j]; xassert(col->node == NULL); if (col->name != NULL) { col->node = avl_insert_node(lp->c_tree, col->name); avl_set_node_link(col->node, col); } } } return; } /*********************************************************************** * NAME * * glp_find_row - find row by its name * * SYNOPSIS * * int glp_find_row(glp_prob *lp, const char *name); * * RETURNS * * The routine glp_find_row returns the ordinal number of a row, * which is assigned (by the routine glp_set_row_name) the specified * symbolic name. If no such row exists, the routine returns 0. */ int glp_find_row(glp_prob *lp, const char *name) { AVLNODE *node; int i = 0; if (lp->r_tree == NULL) xerror("glp_find_row: row name index does not exist\n"); if (!(name == NULL || name[0] == '\0' || strlen(name) > 255)) { node = avl_find_node(lp->r_tree, name); if (node != NULL) i = ((GLPROW *)avl_get_node_link(node))->i; } return i; } /*********************************************************************** * NAME * * glp_find_col - find column by its name * * SYNOPSIS * * int glp_find_col(glp_prob *lp, const char *name); * * RETURNS * * The routine glp_find_col returns the ordinal number of a column, * which is assigned (by the routine glp_set_col_name) the specified * symbolic name. If no such column exists, the routine returns 0. */ int glp_find_col(glp_prob *lp, const char *name) { AVLNODE *node; int j = 0; if (lp->c_tree == NULL) xerror("glp_find_col: column name index does not exist\n"); if (!(name == NULL || name[0] == '\0' || strlen(name) > 255)) { node = avl_find_node(lp->c_tree, name); if (node != NULL) j = ((GLPCOL *)avl_get_node_link(node))->j; } return j; } /*********************************************************************** * NAME * * glp_delete_index - delete the name index * * SYNOPSIS * * void glp_delete_index(glp_prob *lp); * * DESCRIPTION * * The routine glp_delete_index deletes the name index previously * created by the routine glp_create_index and frees the memory * allocated to this auxiliary data structure. * * This routine can be called at any time. If the name index does not * exist, the routine does nothing. */ void glp_delete_index(glp_prob *lp) { int i, j; /* delete row name index */ if (lp->r_tree != NULL) { for (i = 1; i <= lp->m; i++) lp->row[i]->node = NULL; avl_delete_tree(lp->r_tree), lp->r_tree = NULL; } /* delete column name index */ if (lp->c_tree != NULL) { for (j = 1; j <= lp->n; j++) lp->col[j]->node = NULL; avl_delete_tree(lp->c_tree), lp->c_tree = NULL; } return; } /* eof */ sources_5316/external/glpk/glplpx03.c0000644000176700017670000002127111401660400016312 0ustar paulpaul/* glplpx03.c (OPB format) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Author: Oscar Gustafsson . * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_ERRNO #define _GLPSTD_STDIO #include "glpapi.h" #if 0 /* 24/XII-2009; by mao */ #include "glpipp.h" #endif /*---------------------------------------------------------------------- -- lpx_write_pb - write problem data in (normalized) OPB format. -- -- *Synopsis* -- -- #include "glplpx.h" -- int lpx_write_pb(LPX *lp, const char *fname, int normalized, -- int binarize); -- -- *Description* -- -- The routine lpx_write_pb writes problem data in OPB format -- to an output text file whose name is the character string fname. -- If normalized is non-zero the output will be generated in a -- normalized form with sequentially numbered variables, x1, x2 etc. -- If binarize, any integer variable will be repalzec by binary ones, -- see ipp_binarize -- -- *Returns* -- -- If the operation was successful, the routine returns zero. Otherwise -- the routine prints an error message and returns non-zero. */ #if 1 /* 24/XII-2009; by mao (disabled, because IPP was removed) */ int lpx_write_pb(LPX *lp, const char *fname, int normalized, int binarize) { xassert(lp == lp); xassert(fname == fname); xassert(normalized == normalized); xassert(binarize == binarize); xprintf("lpx_write_pb: sorry, currently this operation is not ava" "ilable\n"); return 1; } #else int lpx_write_pb(LPX *lp, const char *fname, int normalized, int binarize) { FILE* fp; int m,n,i,j,k,o,nonfree=0, obj_dir, dbl, *ndx, row_type, emptylhs=0; double coeff, *val, bound, constant/*=0.0*/; char* objconstname = "dummy_one"; char* emptylhsname = "dummy_zero"; /* Variables needed for possible binarization */ /*LPX* tlp;*/ IPP *ipp = NULL; /*tlp=lp;*/ if(binarize) /* Transform integer variables to binary ones */ { ipp = ipp_create_wksp(); ipp_load_orig(ipp, lp); ipp_binarize(ipp); lp = ipp_build_prob(ipp); } fp = fopen(fname, "w"); if(fp!= NULL) { xprintf( "lpx_write_pb: writing problem in %sOPB format to `%s'...\n", (normalized?"normalized ":""), fname); m = glp_get_num_rows(lp); n = glp_get_num_cols(lp); for(i=1;i<=m;i++) { switch(glp_get_row_type(lp,i)) { case GLP_LO: case GLP_UP: case GLP_FX: { nonfree += 1; break; } case GLP_DB: { nonfree += 2; break; } } } constant=glp_get_obj_coef(lp,0); fprintf(fp,"* #variables = %d #constraints = %d\n", n + (constant == 0?1:0), nonfree + (constant == 0?1:0)); /* Objective function */ obj_dir = glp_get_obj_dir(lp); fprintf(fp,"min: "); for(i=1;i<=n;i++) { coeff = glp_get_obj_coef(lp,i); if(coeff != 0.0) { if(obj_dir == GLP_MAX) coeff=-coeff; if(normalized) fprintf(fp, " %d x%d", (int)coeff, i); else fprintf(fp, " %d*%s", (int)coeff, glp_get_col_name(lp,i)); } } if(constant) { if(normalized) fprintf(fp, " %d x%d", (int)constant, n+1); else fprintf(fp, " %d*%s", (int)constant, objconstname); } fprintf(fp,";\n"); if(normalized && !binarize) /* Name substitution */ { fprintf(fp,"* Variable name substitution:\n"); for(j=1;j<=n;j++) { fprintf(fp, "* x%d = %s\n", j, glp_get_col_name(lp,j)); } if(constant) fprintf(fp, "* x%d = %s\n", n+1, objconstname); } ndx = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(double)); /* Constraints */ for(j=1;j<=m;j++) { row_type=glp_get_row_type(lp,j); if(row_type!=GLP_FR) { if(row_type == GLP_DB) { dbl=2; row_type = GLP_UP; } else { dbl=1; } k=glp_get_mat_row(lp, j, ndx, val); for(o=1;o<=dbl;o++) { if(o==2) { row_type = GLP_LO; } if(k==0) /* Empty LHS */ { emptylhs = 1; if(normalized) { fprintf(fp, "0 x%d ", n+2); } else { fprintf(fp, "0*%s ", emptylhsname); } } for(i=1;i<=k;i++) { if(val[i] != 0.0) { if(normalized) { fprintf(fp, "%d x%d ", (row_type==GLP_UP)?(-(int)val[i]):((int)val[i]), ndx[i]); } else { fprintf(fp, "%d*%s ", (int)val[i], glp_get_col_name(lp,ndx[i])); } } } switch(row_type) { case GLP_LO: { fprintf(fp, ">="); bound = glp_get_row_lb(lp,j); break; } case GLP_UP: { if(normalized) { fprintf(fp, ">="); bound = -glp_get_row_ub(lp,j); } else { fprintf(fp, "<="); bound = glp_get_row_ub(lp,j); } break; } case GLP_FX: { fprintf(fp, "="); bound = glp_get_row_lb(lp,j); break; } } fprintf(fp," %d;\n",(int)bound); } } } xfree(ndx); xfree(val); if(constant) { xprintf( "lpx_write_pb: adding constant objective function variable\n"); if(normalized) fprintf(fp, "1 x%d = 1;\n", n+1); else fprintf(fp, "1*%s = 1;\n", objconstname); } if(emptylhs) { xprintf( "lpx_write_pb: adding dummy variable for empty left-hand si" "de constraint\n"); if(normalized) fprintf(fp, "1 x%d = 0;\n", n+2); else fprintf(fp, "1*%s = 0;\n", emptylhsname); } } else { xprintf("Problems opening file for writing: %s\n", fname); return(1); } fflush(fp); if (ferror(fp)) { xprintf("lpx_write_pb: can't write to `%s' - %s\n", fname, strerror(errno)); goto fail; } fclose(fp); if(binarize) { /* delete the resultant problem object */ if (lp != NULL) lpx_delete_prob(lp); /* delete MIP presolver workspace */ if (ipp != NULL) ipp_delete_wksp(ipp); /*lp=tlp;*/ } return 0; fail: if (fp != NULL) fclose(fp); return 1; } #endif /* eof */ sources_5316/external/glpk/glpnet05.c0000644000176700017670000002600511401660400016277 0ustar paulpaul/* glpnet05.c (Goldfarb's maximum flow problem generator) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * This code is a modified version of the program RMFGEN, a maxflow * problem generator developed by D.Goldfarb and M.Grigoriadis, and * originally implemented by Tamas Badics . * The original code is publically available on the DIMACS ftp site at: * . * * All changes concern only the program interface, so this modified * version produces exactly the same instances as the original version. * * Changes were made by Andrew Makhorin . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" #include "glprng.h" /*********************************************************************** * NAME * * glp_rmfgen - Goldfarb's maximum flow problem generator * * SYNOPSIS * * int glp_rmfgen(glp_graph *G, int *s, int *t, int a_cap, * const int parm[1+5]); * * DESCRIPTION * * The routine glp_rmfgen is a maximum flow problem generator developed * by D.Goldfarb and M.Grigoriadis. * * The parameter G specifies the graph object, to which the generated * problem data have to be stored. Note that on entry the graph object * is erased with the routine glp_erase_graph. * * The pointer s specifies a location, to which the routine stores the * source node number. If s is NULL, the node number is not stored. * * The pointer t specifies a location, to which the routine stores the * sink node number. If t is NULL, the node number is not stored. * * The parameter a_cap specifies an offset of the field of type double * in the arc data block, to which the routine stores the arc capacity. * If a_cap < 0, the capacity is not stored. * * The array parm contains description of the network to be generated: * * parm[0] not used * parm[1] (seed) random number seed (a positive integer) * parm[2] (a) frame size * parm[3] (b) depth * parm[4] (c1) minimal arc capacity * parm[5] (c2) maximal arc capacity * * RETURNS * * If the instance was successfully generated, the routine glp_netgen * returns zero; otherwise, if specified parameters are inconsistent, * the routine returns a non-zero error code. * * COMMENTS * * The generated network is as follows. It has b pieces of frames of * size a * a. (So alltogether the number of vertices is a * a * b) * * In each frame all the vertices are connected with their neighbours * (forth and back). In addition the vertices of a frame are connected * one to one with the vertices of next frame using a random permutation * of those vertices. * * The source is the lower left vertex of the first frame, the sink is * the upper right vertex of the b'th frame. * * t * +-------+ * | .| * | . | * / | / | * +-------+/ -+ b * | | |/. * a | -v- |/ * | | |/ * +-------+ 1 * s a * * The capacities are randomly chosen integers from the range of [c1,c2] * in the case of interconnecting edges, and c2 * a * a for the in-frame * edges. * * REFERENCES * * D.Goldfarb and M.D.Grigoriadis, "A computational comparison of the * Dinic and network simplex methods for maximum flow." Annals of Op. * Res. 13 (1988), pp. 83-123. * * U.Derigs and W.Meier, "Implementing Goldberg's max-flow algorithm: * A computational investigation." Zeitschrift fuer Operations Research * 33 (1989), pp. 383-403. */ typedef struct VERTEX { struct EDGE **edgelist; /* Pointer to the list of pointers to the adjacent edges. (No matter that to or from edges) */ struct EDGE **current; /* Pointer to the current edge */ int degree; /* Number of adjacent edges (both direction) */ int index; } vertex; typedef struct EDGE { int from; int to; int cap; /* Capacity */ } edge; typedef struct NETWORK { struct NETWORK *next, *prev; int vertnum; int edgenum; vertex *verts; /* Vertex array[1..vertnum] */ edge *edges; /* Edge array[1..edgenum] */ int source; /* Pointer to the source */ int sink; /* Pointer to the sink */ } network; struct csa { /* common storage area */ glp_graph *G; int *s, *t, a_cap; RNG *rand; network *N; int *Parr; int A, AA, C2AA, Ec; }; #define G (csa->G) #define s (csa->s) #define t (csa->t) #define a_cap (csa->a_cap) #define N (csa->N) #define Parr (csa->Parr) #define A (csa->A) #define AA (csa->AA) #define C2AA (csa->C2AA) #define Ec (csa->Ec) #undef random #define random(A) (int)(rng_unif_01(csa->rand) * (double)(A)) #define RANDOM(A, B) (int)(random((B) - (A) + 1) + (A)) #define sgn(A) (((A) > 0) ? 1 : ((A) == 0) ? 0 : -1) static void make_edge(struct csa *csa, int from, int to, int c1, int c2) { Ec++; N->edges[Ec].from = from; N->edges[Ec].to = to; N->edges[Ec].cap = RANDOM(c1, c2); return; } static void permute(struct csa *csa) { int i, j, tmp; for (i = 1; i < AA; i++) { j = RANDOM(i, AA); tmp = Parr[i]; Parr[i] = Parr[j]; Parr[j] = tmp; } return; } static void connect(struct csa *csa, int offset, int cv, int x1, int y1) { int cv1; cv1 = offset + (x1 - 1) * A + y1; Ec++; N->edges[Ec].from = cv; N->edges[Ec].to = cv1; N->edges[Ec].cap = C2AA; return; } static network *gen_rmf(struct csa *csa, int a, int b, int c1, int c2) { /* generates a network with a*a*b nodes and 6a*a*b-4ab-2a*a edges random_frame network: Derigs & Meier, Methods & Models of OR (1989), 33:383-403 */ int x, y, z, offset, cv; A = a; AA = a * a; C2AA = c2 * AA; Ec = 0; N = (network *)xmalloc(sizeof(network)); N->vertnum = AA * b; N->edgenum = 5 * AA * b - 4 * A * b - AA; N->edges = (edge *)xcalloc(N->edgenum + 1, sizeof(edge)); N->source = 1; N->sink = N->vertnum; Parr = (int *)xcalloc(AA + 1, sizeof(int)); for (x = 1; x <= AA; x++) Parr[x] = x; for (z = 1; z <= b; z++) { offset = AA * (z - 1); if (z != b) permute(csa); for (x = 1; x <= A; x++) { for (y = 1; y <= A; y++) { cv = offset + (x - 1) * A + y; if (z != b) make_edge(csa, cv, offset + AA + Parr[cv - offset], c1, c2); /* the intermediate edges */ if (y < A) connect(csa, offset, cv, x, y + 1); if (y > 1) connect(csa, offset, cv, x, y - 1); if (x < A) connect(csa, offset, cv, x + 1, y); if (x > 1) connect(csa, offset, cv, x - 1, y); } } } xfree(Parr); return N; } static void print_max_format(struct csa *csa, network *n, char *comm[], int dim) { /* prints a network heading with dim lines of comments (no \n needs at the ends) */ int i, vnum, e_num; edge *e; vnum = n->vertnum; e_num = n->edgenum; if (G == NULL) { for (i = 0; i < dim; i++) xprintf("c %s\n", comm[i]); xprintf("p max %7d %10d\n", vnum, e_num); xprintf("n %7d s\n", n->source); xprintf("n %7d t\n", n->sink); } else { glp_add_vertices(G, vnum); if (s != NULL) *s = n->source; if (t != NULL) *t = n->sink; } for (i = 1; i <= e_num; i++) { e = &n->edges[i]; if (G == NULL) xprintf("a %7d %7d %10d\n", e->from, e->to, (int)e->cap); else { glp_arc *a = glp_add_arc(G, e->from, e->to); if (a_cap >= 0) { double temp = (double)e->cap; memcpy((char *)a->data + a_cap, &temp, sizeof(double)); } } } return; } static void gen_free_net(network *n) { xfree(n->edges); xfree(n); return; } int glp_rmfgen(glp_graph *G_, int *_s, int *_t, int _a_cap, const int parm[1+5]) { struct csa _csa, *csa = &_csa; network *n; char comm[10][80], *com1[10]; int seed, a, b, c1, c2, ret; G = G_; s = _s; t = _t; a_cap = _a_cap; if (G != NULL) { if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_rmfgen: a_cap = %d; invalid offset\n", a_cap); } seed = parm[1]; a = parm[2]; b = parm[3]; c1 = parm[4]; c2 = parm[5]; if (!(seed > 0 && 1 <= a && a <= 1000 && 1 <= b && b <= 1000 && 0 <= c1 && c1 <= c2 && c2 <= 1000)) { ret = 1; goto done; } if (G != NULL) { glp_erase_graph(G, G->v_size, G->a_size); glp_set_graph_name(G, "RMFGEN"); } csa->rand = rng_create_rand(); rng_init_rand(csa->rand, seed); n = gen_rmf(csa, a, b, c1, c2); sprintf(comm[0], "This file was generated by genrmf."); sprintf(comm[1], "The parameters are: a: %d b: %d c1: %d c2: %d", a, b, c1, c2); com1[0] = comm[0]; com1[1] = comm[1]; print_max_format(csa, n, com1, 2); gen_free_net(n); rng_delete_rand(csa->rand); ret = 0; done: return ret; } /**********************************************************************/ #if 0 int main(int argc, char *argv[]) { int seed, a, b, c1, c2, i, parm[1+5]; seed = 123; a = b = c1 = c2 = -1; for (i = 1; i < argc; i++) { if (strcmp(argv[i], "-seed") == 0) seed = atoi(argv[++i]); else if (strcmp(argv[i], "-a") == 0) a = atoi(argv[++i]); else if (strcmp(argv[i], "-b") == 0) b = atoi(argv[++i]); else if (strcmp(argv[i], "-c1") == 0) c1 = atoi(argv[++i]); else if (strcmp(argv[i], "-c2") == 0) c2 = atoi(argv[++i]); } if (a < 0 || b < 0 || c1 < 0 || c2 < 0) { xprintf("Usage:\n"); xprintf("genrmf [-seed seed] -a frame_size -b depth\n"); xprintf(" -c1 cap_range1 -c2 cap_range2\n"); } else { parm[1] = seed; parm[2] = a; parm[3] = b; parm[4] = c1; parm[5] = c2; glp_rmfgen(NULL, NULL, NULL, 0, parm); } return 0; } #endif /* eof */ sources_5316/external/glpk/glpbfd.h0000644000176700017670000000507411401660400016107 0ustar paulpaul/* glpbfd.h (LP basis factorization driver) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPBFD_H #define GLPBFD_H #ifndef GLPBFD_PRIVATE typedef struct { double _opaque_bfd[100]; } BFD; #endif /* return codes: */ #define BFD_ESING 1 /* singular matrix */ #define BFD_ECOND 2 /* ill-conditioned matrix */ #define BFD_ECHECK 3 /* insufficient accuracy */ #define BFD_ELIMIT 4 /* update limit reached */ #define BFD_EROOM 5 /* SVA overflow */ #define bfd_create_it _glp_bfd_create_it BFD *bfd_create_it(void); /* create LP basis factorization */ #define bfd_set_parm _glp_bfd_set_parm void bfd_set_parm(BFD *bfd, const void *parm); /* change LP basis factorization control parameters */ #define bfd_factorize _glp_bfd_factorize int bfd_factorize(BFD *bfd, int m, const int bh[], int (*col) (void *info, int j, int ind[], double val[]), void *info); /* compute LP basis factorization */ #define bfd_ftran _glp_bfd_ftran void bfd_ftran(BFD *bfd, double x[]); /* perform forward transformation (solve system B*x = b) */ #define bfd_btran _glp_bfd_btran void bfd_btran(BFD *bfd, double x[]); /* perform backward transformation (solve system B'*x = b) */ #define bfd_update_it _glp_bfd_update_it int bfd_update_it(BFD *bfd, int j, int bh, int len, const int ind[], const double val[]); /* update LP basis factorization */ #define bfd_get_count _glp_bfd_get_count int bfd_get_count(BFD *bfd); /* determine factorization update count */ #define bfd_delete_it _glp_bfd_delete_it void bfd_delete_it(BFD *bfd); /* delete LP basis factorization */ #endif /* eof */ sources_5316/external/glpk/glpnpp02.c0000644000176700017670000012623411401660400016310 0ustar paulpaul/* glpnpp02.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpnpp.h" /*********************************************************************** * NAME * * npp_free_row - process free (unbounded) row * * SYNOPSIS * * #include "glpnpp.h" * void npp_free_row(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_free_row processes row p, which is free (i.e. has * no finite bounds): * * -inf < sum a[p,j] x[j] < +inf. (1) * j * * PROBLEM TRANSFORMATION * * Constraint (1) cannot be active, so it is redundant and can be * removed from the original problem. * * Removing row p leads to removing a column of multiplier pi[p] for * this row in the dual system. Since row p has no bounds, pi[p] = 0, * so removing the column does not affect the dual solution. * * RECOVERING BASIC SOLUTION * * In solution to the original problem row p is inactive constraint, * so it is assigned status GLP_BS, and multiplier pi[p] is assigned * zero value. * * RECOVERING INTERIOR-POINT SOLUTION * * In solution to the original problem row p is inactive constraint, * so its multiplier pi[p] is assigned zero value. * * RECOVERING MIP SOLUTION * * None needed. */ struct free_row { /* free (unbounded) row */ int p; /* row reference number */ }; static int rcv_free_row(NPP *npp, void *info); void npp_free_row(NPP *npp, NPPROW *p) { /* process free (unbounded) row */ struct free_row *info; /* the row must be free */ xassert(p->lb == -DBL_MAX && p->ub == +DBL_MAX); /* create transformation stack entry */ info = npp_push_tse(npp, rcv_free_row, sizeof(struct free_row)); info->p = p->i; /* remove the row from the problem */ npp_del_row(npp, p); return; } static int rcv_free_row(NPP *npp, void *_info) { /* recover free (unbounded) row */ struct free_row *info = _info; if (npp->sol == GLP_SOL) npp->r_stat[info->p] = GLP_BS; if (npp->sol != GLP_MIP) npp->r_pi[info->p] = 0.0; return 0; } /*********************************************************************** * NAME * * npp_geq_row - process row of 'not less than' type * * SYNOPSIS * * #include "glpnpp.h" * void npp_geq_row(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_geq_row processes row p, which is 'not less than' * inequality constraint: * * L[p] <= sum a[p,j] x[j] (<= U[p]), (1) * j * * where L[p] < U[p], and upper bound may not exist (U[p] = +oo). * * PROBLEM TRANSFORMATION * * Constraint (1) can be replaced by equality constraint: * * sum a[p,j] x[j] - s = L[p], (2) * j * * where * * 0 <= s (<= U[p] - L[p]) (3) * * is a non-negative surplus variable. * * Since in the primal system there appears column s having the only * non-zero coefficient in row p, in the dual system there appears a * new row: * * (-1) pi[p] + lambda = 0, (4) * * where (-1) is coefficient of column s in row p, pi[p] is multiplier * of row p, lambda is multiplier of column q, 0 is coefficient of * column s in the objective row. * * RECOVERING BASIC SOLUTION * * Status of row p in solution to the original problem is determined * by its status and status of column q in solution to the transformed * problem as follows: * * +--------------------------------------+------------------+ * | Transformed problem | Original problem | * +-----------------+--------------------+------------------+ * | Status of row p | Status of column s | Status of row p | * +-----------------+--------------------+------------------+ * | GLP_BS | GLP_BS | N/A | * | GLP_BS | GLP_NL | GLP_BS | * | GLP_BS | GLP_NU | GLP_BS | * | GLP_NS | GLP_BS | GLP_BS | * | GLP_NS | GLP_NL | GLP_NL | * | GLP_NS | GLP_NU | GLP_NU | * +-----------------+--------------------+------------------+ * * Value of row multiplier pi[p] in solution to the original problem * is the same as in solution to the transformed problem. * * 1. In solution to the transformed problem row p and column q cannot * be basic at the same time; otherwise the basis matrix would have * two linear dependent columns: unity column of auxiliary variable * of row p and unity column of variable s. * * 2. Though in the transformed problem row p is equality constraint, * it may be basic due to primal degenerate solution. * * RECOVERING INTERIOR-POINT SOLUTION * * Value of row multiplier pi[p] in solution to the original problem * is the same as in solution to the transformed problem. * * RECOVERING MIP SOLUTION * * None needed. */ struct ineq_row { /* inequality constraint row */ int p; /* row reference number */ int s; /* column reference number for slack/surplus variable */ }; static int rcv_geq_row(NPP *npp, void *info); void npp_geq_row(NPP *npp, NPPROW *p) { /* process row of 'not less than' type */ struct ineq_row *info; NPPCOL *s; /* the row must have lower bound */ xassert(p->lb != -DBL_MAX); xassert(p->lb < p->ub); /* create column for surplus variable */ s = npp_add_col(npp); s->lb = 0.0; s->ub = (p->ub == +DBL_MAX ? +DBL_MAX : p->ub - p->lb); /* and add it to the transformed problem */ npp_add_aij(npp, p, s, -1.0); /* create transformation stack entry */ info = npp_push_tse(npp, rcv_geq_row, sizeof(struct ineq_row)); info->p = p->i; info->s = s->j; /* replace the row by equality constraint */ p->ub = p->lb; return; } static int rcv_geq_row(NPP *npp, void *_info) { /* recover row of 'not less than' type */ struct ineq_row *info = _info; if (npp->sol == GLP_SOL) { if (npp->r_stat[info->p] == GLP_BS) { if (npp->c_stat[info->s] == GLP_BS) { npp_error(); return 1; } else if (npp->c_stat[info->s] == GLP_NL || npp->c_stat[info->s] == GLP_NU) npp->r_stat[info->p] = GLP_BS; else { npp_error(); return 1; } } else if (npp->r_stat[info->p] == GLP_NS) { if (npp->c_stat[info->s] == GLP_BS) npp->r_stat[info->p] = GLP_BS; else if (npp->c_stat[info->s] == GLP_NL) npp->r_stat[info->p] = GLP_NL; else if (npp->c_stat[info->s] == GLP_NU) npp->r_stat[info->p] = GLP_NU; else { npp_error(); return 1; } } else { npp_error(); return 1; } } return 0; } /*********************************************************************** * NAME * * npp_leq_row - process row of 'not greater than' type * * SYNOPSIS * * #include "glpnpp.h" * void npp_leq_row(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_leq_row processes row p, which is 'not greater than' * inequality constraint: * * (L[p] <=) sum a[p,j] x[j] <= U[p], (1) * j * * where L[p] < U[p], and lower bound may not exist (L[p] = +oo). * * PROBLEM TRANSFORMATION * * Constraint (1) can be replaced by equality constraint: * * sum a[p,j] x[j] + s = L[p], (2) * j * * where * * 0 <= s (<= U[p] - L[p]) (3) * * is a non-negative slack variable. * * Since in the primal system there appears column s having the only * non-zero coefficient in row p, in the dual system there appears a * new row: * * (+1) pi[p] + lambda = 0, (4) * * where (+1) is coefficient of column s in row p, pi[p] is multiplier * of row p, lambda is multiplier of column q, 0 is coefficient of * column s in the objective row. * * RECOVERING BASIC SOLUTION * * Status of row p in solution to the original problem is determined * by its status and status of column q in solution to the transformed * problem as follows: * * +--------------------------------------+------------------+ * | Transformed problem | Original problem | * +-----------------+--------------------+------------------+ * | Status of row p | Status of column s | Status of row p | * +-----------------+--------------------+------------------+ * | GLP_BS | GLP_BS | N/A | * | GLP_BS | GLP_NL | GLP_BS | * | GLP_BS | GLP_NU | GLP_BS | * | GLP_NS | GLP_BS | GLP_BS | * | GLP_NS | GLP_NL | GLP_NU | * | GLP_NS | GLP_NU | GLP_NL | * +-----------------+--------------------+------------------+ * * Value of row multiplier pi[p] in solution to the original problem * is the same as in solution to the transformed problem. * * 1. In solution to the transformed problem row p and column q cannot * be basic at the same time; otherwise the basis matrix would have * two linear dependent columns: unity column of auxiliary variable * of row p and unity column of variable s. * * 2. Though in the transformed problem row p is equality constraint, * it may be basic due to primal degeneracy. * * RECOVERING INTERIOR-POINT SOLUTION * * Value of row multiplier pi[p] in solution to the original problem * is the same as in solution to the transformed problem. * * RECOVERING MIP SOLUTION * * None needed. */ static int rcv_leq_row(NPP *npp, void *info); void npp_leq_row(NPP *npp, NPPROW *p) { /* process row of 'not greater than' type */ struct ineq_row *info; NPPCOL *s; /* the row must have upper bound */ xassert(p->ub != +DBL_MAX); xassert(p->lb < p->ub); /* create column for slack variable */ s = npp_add_col(npp); s->lb = 0.0; s->ub = (p->lb == -DBL_MAX ? +DBL_MAX : p->ub - p->lb); /* and add it to the transformed problem */ npp_add_aij(npp, p, s, +1.0); /* create transformation stack entry */ info = npp_push_tse(npp, rcv_leq_row, sizeof(struct ineq_row)); info->p = p->i; info->s = s->j; /* replace the row by equality constraint */ p->lb = p->ub; return; } static int rcv_leq_row(NPP *npp, void *_info) { /* recover row of 'not greater than' type */ struct ineq_row *info = _info; if (npp->sol == GLP_SOL) { if (npp->r_stat[info->p] == GLP_BS) { if (npp->c_stat[info->s] == GLP_BS) { npp_error(); return 1; } else if (npp->c_stat[info->s] == GLP_NL || npp->c_stat[info->s] == GLP_NU) npp->r_stat[info->p] = GLP_BS; else { npp_error(); return 1; } } else if (npp->r_stat[info->p] == GLP_NS) { if (npp->c_stat[info->s] == GLP_BS) npp->r_stat[info->p] = GLP_BS; else if (npp->c_stat[info->s] == GLP_NL) npp->r_stat[info->p] = GLP_NU; else if (npp->c_stat[info->s] == GLP_NU) npp->r_stat[info->p] = GLP_NL; else { npp_error(); return 1; } } else { npp_error(); return 1; } } return 0; } /*********************************************************************** * NAME * * npp_free_col - process free (unbounded) column * * SYNOPSIS * * #include "glpnpp.h" * void npp_free_col(NPP *npp, NPPCOL *q); * * DESCRIPTION * * The routine npp_free_col processes column q, which is free (i.e. has * no finite bounds): * * -oo < x[q] < +oo. (1) * * PROBLEM TRANSFORMATION * * Free (unbounded) variable can be replaced by the difference of two * non-negative variables: * * x[q] = s' - s'', s', s'' >= 0. (2) * * Assuming that in the transformed problem x[q] becomes s', * transformation (2) causes new column s'' to appear, which differs * from column s' only in the sign of coefficients in constraint and * objective rows. Thus, if in the dual system the following row * corresponds to column s': * * sum a[i,q] pi[i] + lambda' = c[q], (3) * i * * the row which corresponds to column s'' is the following: * * sum (-a[i,q]) pi[i] + lambda'' = -c[q]. (4) * i * * Then from (3) and (4) it follows that: * * lambda' + lambda'' = 0 => lambda' = lmabda'' = 0, (5) * * where lambda' and lambda'' are multipliers for columns s' and s'', * resp. * * RECOVERING BASIC SOLUTION * * With respect to (5) status of column q in solution to the original * problem is determined by statuses of columns s' and s'' in solution * to the transformed problem as follows: * * +--------------------------------------+------------------+ * | Transformed problem | Original problem | * +------------------+-------------------+------------------+ * | Status of col s' | Status of col s'' | Status of col q | * +------------------+-------------------+------------------+ * | GLP_BS | GLP_BS | N/A | * | GLP_BS | GLP_NL | GLP_BS | * | GLP_NL | GLP_BS | GLP_BS | * | GLP_NL | GLP_NL | GLP_NF | * +------------------+-------------------+------------------+ * * Value of column q is computed with formula (2). * * 1. In solution to the transformed problem columns s' and s'' cannot * be basic at the same time, because they differ only in the sign, * hence, are linear dependent. * * 2. Though column q is free, it can be non-basic due to dual * degeneracy. * * 3. If column q is integral, columns s' and s'' are also integral. * * RECOVERING INTERIOR-POINT SOLUTION * * Value of column q is computed with formula (2). * * RECOVERING MIP SOLUTION * * Value of column q is computed with formula (2). */ struct free_col { /* free (unbounded) column */ int q; /* column reference number for variables x[q] and s' */ int s; /* column reference number for variable s'' */ }; static int rcv_free_col(NPP *npp, void *info); void npp_free_col(NPP *npp, NPPCOL *q) { /* process free (unbounded) column */ struct free_col *info; NPPCOL *s; NPPAIJ *aij; /* the column must be free */ xassert(q->lb == -DBL_MAX && q->ub == +DBL_MAX); /* variable x[q] becomes s' */ q->lb = 0.0, q->ub = +DBL_MAX; /* create variable s'' */ s = npp_add_col(npp); s->is_int = q->is_int; s->lb = 0.0, s->ub = +DBL_MAX; /* duplicate objective coefficient */ s->coef = -q->coef; /* duplicate column of the constraint matrix */ for (aij = q->ptr; aij != NULL; aij = aij->c_next) npp_add_aij(npp, aij->row, s, -aij->val); /* create transformation stack entry */ info = npp_push_tse(npp, rcv_free_col, sizeof(struct free_col)); info->q = q->j; info->s = s->j; return; } static int rcv_free_col(NPP *npp, void *_info) { /* recover free (unbounded) column */ struct free_col *info = _info; if (npp->sol == GLP_SOL) { if (npp->c_stat[info->q] == GLP_BS) { if (npp->c_stat[info->s] == GLP_BS) { npp_error(); return 1; } else if (npp->c_stat[info->s] == GLP_NL) npp->c_stat[info->q] = GLP_BS; else { npp_error(); return -1; } } else if (npp->c_stat[info->q] == GLP_NL) { if (npp->c_stat[info->s] == GLP_BS) npp->c_stat[info->q] = GLP_BS; else if (npp->c_stat[info->s] == GLP_NL) npp->c_stat[info->q] = GLP_NF; else { npp_error(); return -1; } } else { npp_error(); return -1; } } /* compute value of x[q] with formula (2) */ npp->c_value[info->q] -= npp->c_value[info->s]; return 0; } /*********************************************************************** * NAME * * npp_lbnd_col - process column with (non-zero) lower bound * * SYNOPSIS * * #include "glpnpp.h" * void npp_lbnd_col(NPP *npp, NPPCOL *q); * * DESCRIPTION * * The routine npp_lbnd_col processes column q, which has (non-zero) * lower bound: * * l[q] <= x[q] (<= u[q]), (1) * * where l[q] < u[q], and upper bound may not exist (u[q] = +oo). * * PROBLEM TRANSFORMATION * * Column q can be replaced as follows: * * x[q] = l[q] + s, (2) * * where * * 0 <= s (<= u[q] - l[q]) (3) * * is a non-negative variable. * * Substituting x[q] from (2) into the objective row, we have: * * z = sum c[j] x[j] + c0 = * j * * = sum c[j] x[j] + c[q] x[q] + c0 = * j!=q * * = sum c[j] x[j] + c[q] (l[q] + s) + c0 = * j!=q * * = sum c[j] x[j] + c[q] s + c~0, * * where * * c~0 = c0 + c[q] l[q] (4) * * is the constant term of the objective in the transformed problem. * Similarly, substituting x[q] into constraint row i, we have: * * L[i] <= sum a[i,j] x[j] <= U[i] ==> * j * * L[i] <= sum a[i,j] x[j] + a[i,q] x[q] <= U[i] ==> * j!=q * * L[i] <= sum a[i,j] x[j] + a[i,q] (l[q] + s) <= U[i] ==> * j!=q * * L~[i] <= sum a[i,j] x[j] + a[i,q] s <= U~[i], * j!=q * * where * * L~[i] = L[i] - a[i,q] l[q], U~[i] = U[i] - a[i,q] l[q] (5) * * are lower and upper bounds of row i in the transformed problem, * resp. * * Transformation (2) does not affect the dual system. * * RECOVERING BASIC SOLUTION * * Status of column q in solution to the original problem is the same * as in solution to the transformed problem (GLP_BS, GLP_NL or GLP_NU). * Value of column q is computed with formula (2). * * RECOVERING INTERIOR-POINT SOLUTION * * Value of column q is computed with formula (2). * * RECOVERING MIP SOLUTION * * Value of column q is computed with formula (2). */ struct bnd_col { /* bounded column */ int q; /* column reference number for variables x[q] and s */ double bnd; /* lower/upper bound l[q] or u[q] */ }; static int rcv_lbnd_col(NPP *npp, void *info); void npp_lbnd_col(NPP *npp, NPPCOL *q) { /* process column with (non-zero) lower bound */ struct bnd_col *info; NPPROW *i; NPPAIJ *aij; /* the column must have non-zero lower bound */ xassert(q->lb != 0.0); xassert(q->lb != -DBL_MAX); xassert(q->lb < q->ub); /* create transformation stack entry */ info = npp_push_tse(npp, rcv_lbnd_col, sizeof(struct bnd_col)); info->q = q->j; info->bnd = q->lb; /* substitute x[q] into objective row */ npp->c0 += q->coef * q->lb; /* substitute x[q] into constraint rows */ for (aij = q->ptr; aij != NULL; aij = aij->c_next) { i = aij->row; if (i->lb == i->ub) i->ub = (i->lb -= aij->val * q->lb); else { if (i->lb != -DBL_MAX) i->lb -= aij->val * q->lb; if (i->ub != +DBL_MAX) i->ub -= aij->val * q->lb; } } /* column x[q] becomes column s */ if (q->ub != +DBL_MAX) q->ub -= q->lb; q->lb = 0.0; return; } static int rcv_lbnd_col(NPP *npp, void *_info) { /* recover column with (non-zero) lower bound */ struct bnd_col *info = _info; if (npp->sol == GLP_SOL) { if (npp->c_stat[info->q] == GLP_BS || npp->c_stat[info->q] == GLP_NL || npp->c_stat[info->q] == GLP_NU) npp->c_stat[info->q] = npp->c_stat[info->q]; else { npp_error(); return 1; } } /* compute value of x[q] with formula (2) */ npp->c_value[info->q] = info->bnd + npp->c_value[info->q]; return 0; } /*********************************************************************** * NAME * * npp_ubnd_col - process column with upper bound * * SYNOPSIS * * #include "glpnpp.h" * void npp_ubnd_col(NPP *npp, NPPCOL *q); * * DESCRIPTION * * The routine npp_ubnd_col processes column q, which has upper bound: * * (l[q] <=) x[q] <= u[q], (1) * * where l[q] < u[q], and lower bound may not exist (l[q] = -oo). * * PROBLEM TRANSFORMATION * * Column q can be replaced as follows: * * x[q] = u[q] - s, (2) * * where * * 0 <= s (<= u[q] - l[q]) (3) * * is a non-negative variable. * * Substituting x[q] from (2) into the objective row, we have: * * z = sum c[j] x[j] + c0 = * j * * = sum c[j] x[j] + c[q] x[q] + c0 = * j!=q * * = sum c[j] x[j] + c[q] (u[q] - s) + c0 = * j!=q * * = sum c[j] x[j] - c[q] s + c~0, * * where * * c~0 = c0 + c[q] u[q] (4) * * is the constant term of the objective in the transformed problem. * Similarly, substituting x[q] into constraint row i, we have: * * L[i] <= sum a[i,j] x[j] <= U[i] ==> * j * * L[i] <= sum a[i,j] x[j] + a[i,q] x[q] <= U[i] ==> * j!=q * * L[i] <= sum a[i,j] x[j] + a[i,q] (u[q] - s) <= U[i] ==> * j!=q * * L~[i] <= sum a[i,j] x[j] - a[i,q] s <= U~[i], * j!=q * * where * * L~[i] = L[i] - a[i,q] u[q], U~[i] = U[i] - a[i,q] u[q] (5) * * are lower and upper bounds of row i in the transformed problem, * resp. * * Note that in the transformed problem coefficients c[q] and a[i,q] * change their sign. Thus, the row of the dual system corresponding to * column q: * * sum a[i,q] pi[i] + lambda[q] = c[q] (6) * i * * in the transformed problem becomes the following: * * sum (-a[i,q]) pi[i] + lambda[s] = -c[q]. (7) * i * * Therefore: * * lambda[q] = - lambda[s], (8) * * where lambda[q] is multiplier for column q, lambda[s] is multiplier * for column s. * * RECOVERING BASIC SOLUTION * * With respect to (8) status of column q in solution to the original * problem is determined by status of column s in solution to the * transformed problem as follows: * * +-----------------------+--------------------+ * | Status of column s | Status of column q | * | (transformed problem) | (original problem) | * +-----------------------+--------------------+ * | GLP_BS | GLP_BS | * | GLP_NL | GLP_NU | * | GLP_NU | GLP_NL | * +-----------------------+--------------------+ * * Value of column q is computed with formula (2). * * RECOVERING INTERIOR-POINT SOLUTION * * Value of column q is computed with formula (2). * * RECOVERING MIP SOLUTION * * Value of column q is computed with formula (2). */ static int rcv_ubnd_col(NPP *npp, void *info); void npp_ubnd_col(NPP *npp, NPPCOL *q) { /* process column with upper bound */ struct bnd_col *info; NPPROW *i; NPPAIJ *aij; /* the column must have upper bound */ xassert(q->ub != +DBL_MAX); xassert(q->lb < q->ub); /* create transformation stack entry */ info = npp_push_tse(npp, rcv_ubnd_col, sizeof(struct bnd_col)); info->q = q->j; info->bnd = q->ub; /* substitute x[q] into objective row */ npp->c0 += q->coef * q->ub; q->coef = -q->coef; /* substitute x[q] into constraint rows */ for (aij = q->ptr; aij != NULL; aij = aij->c_next) { i = aij->row; if (i->lb == i->ub) i->ub = (i->lb -= aij->val * q->ub); else { if (i->lb != -DBL_MAX) i->lb -= aij->val * q->ub; if (i->ub != +DBL_MAX) i->ub -= aij->val * q->ub; } aij->val = -aij->val; } /* column x[q] becomes column s */ if (q->lb != -DBL_MAX) q->ub -= q->lb; else q->ub = +DBL_MAX; q->lb = 0.0; return; } static int rcv_ubnd_col(NPP *npp, void *_info) { /* recover column with upper bound */ struct bnd_col *info = _info; if (npp->sol == GLP_BS) { if (npp->c_stat[info->q] == GLP_BS) npp->c_stat[info->q] = GLP_BS; else if (npp->c_stat[info->q] == GLP_NL) npp->c_stat[info->q] = GLP_NU; else if (npp->c_stat[info->q] == GLP_NU) npp->c_stat[info->q] = GLP_NL; else { npp_error(); return 1; } } /* compute value of x[q] with formula (2) */ npp->c_value[info->q] = info->bnd - npp->c_value[info->q]; return 0; } /*********************************************************************** * NAME * * npp_dbnd_col - process non-negative column with upper bound * * SYNOPSIS * * #include "glpnpp.h" * void npp_dbnd_col(NPP *npp, NPPCOL *q); * * DESCRIPTION * * The routine npp_dbnd_col processes column q, which is non-negative * and has upper bound: * * 0 <= x[q] <= u[q], (1) * * where u[q] > 0. * * PROBLEM TRANSFORMATION * * Upper bound of column q can be replaced by the following equality * constraint: * * x[q] + s = u[q], (2) * * where s >= 0 is a non-negative complement variable. * * Since in the primal system along with new row (2) there appears a * new column s having the only non-zero coefficient in this row, in * the dual system there appears a new row: * * (+1)pi + lambda[s] = 0, (3) * * where (+1) is coefficient at column s in row (2), pi is multiplier * for row (2), lambda[s] is multiplier for column s, 0 is coefficient * at column s in the objective row. * * RECOVERING BASIC SOLUTION * * Status of column q in solution to the original problem is determined * by its status and status of column s in solution to the transformed * problem as follows: * * +-----------------------------------+------------------+ * | Transformed problem | Original problem | * +-----------------+-----------------+------------------+ * | Status of col q | Status of col s | Status of col q | * +-----------------+-----------------+------------------+ * | GLP_BS | GLP_BS | GLP_BS | * | GLP_BS | GLP_NL | GLP_NU | * | GLP_NL | GLP_BS | GLP_NL | * | GLP_NL | GLP_NL | GLP_NL (*) | * +-----------------+-----------------+------------------+ * * Value of column q in solution to the original problem is the same as * in solution to the transformed problem. * * 1. Formally, in solution to the transformed problem columns q and s * cannot be non-basic at the same time, since the constraint (2) * would be violated. However, if u[q] is close to zero, violation * may be less than a working precision even if both columns q and s * are non-basic. In this degenerate case row (2) can be only basic, * i.e. non-active constraint (otherwise corresponding row of the * basis matrix would be zero). This allows to pivot out auxiliary * variable and pivot in column s, in which case the row becomes * active while column s becomes basic. * * 2. If column q is integral, column s is also integral. * * RECOVERING INTERIOR-POINT SOLUTION * * Value of column q in solution to the original problem is the same as * in solution to the transformed problem. * * RECOVERING MIP SOLUTION * * Value of column q in solution to the original problem is the same as * in solution to the transformed problem. */ struct dbnd_col { /* double-bounded column */ int q; /* column reference number for variable x[q] */ int s; /* column reference number for complement variable s */ }; static int rcv_dbnd_col(NPP *npp, void *info); void npp_dbnd_col(NPP *npp, NPPCOL *q) { /* process non-negative column with upper bound */ struct dbnd_col *info; NPPROW *p; NPPCOL *s; /* the column must be non-negative with upper bound */ xassert(q->lb == 0.0); xassert(q->ub > 0.0); xassert(q->ub != +DBL_MAX); /* create variable s */ s = npp_add_col(npp); s->is_int = q->is_int; s->lb = 0.0, s->ub = +DBL_MAX; /* create equality constraint (2) */ p = npp_add_row(npp); p->lb = p->ub = q->ub; npp_add_aij(npp, p, q, +1.0); npp_add_aij(npp, p, s, +1.0); /* create transformation stack entry */ info = npp_push_tse(npp, rcv_dbnd_col, sizeof(struct dbnd_col)); info->q = q->j; info->s = s->j; /* remove upper bound of x[q] */ q->ub = +DBL_MAX; return; } static int rcv_dbnd_col(NPP *npp, void *_info) { /* recover non-negative column with upper bound */ struct dbnd_col *info = _info; if (npp->sol == GLP_BS) { if (npp->c_stat[info->q] == GLP_BS) { if (npp->c_stat[info->s] == GLP_BS) npp->c_stat[info->q] = GLP_BS; else if (npp->c_stat[info->s] == GLP_NL) npp->c_stat[info->q] = GLP_NU; else { npp_error(); return 1; } } else if (npp->c_stat[info->q] == GLP_NL) { if (npp->c_stat[info->s] == GLP_BS || npp->c_stat[info->s] == GLP_NL) npp->c_stat[info->q] = GLP_NL; else { npp_error(); return 1; } } else { npp_error(); return 1; } } return 0; } /*********************************************************************** * NAME * * npp_fixed_col - process fixed column * * SYNOPSIS * * #include "glpnpp.h" * void npp_fixed_col(NPP *npp, NPPCOL *q); * * DESCRIPTION * * The routine npp_fixed_col processes column q, which is fixed: * * x[q] = s[q], (1) * * where s[q] is a fixed column value. * * PROBLEM TRANSFORMATION * * The value of a fixed column can be substituted into the objective * and constraint rows that allows removing the column from the problem. * * Substituting x[q] = s[q] into the objective row, we have: * * z = sum c[j] x[j] + c0 = * j * * = sum c[j] x[j] + c[q] x[q] + c0 = * j!=q * * = sum c[j] x[j] + c[q] s[q] + c0 = * j!=q * * = sum c[j] x[j] + c~0, * j!=q * * where * * c~0 = c0 + c[q] s[q] (2) * * is the constant term of the objective in the transformed problem. * Similarly, substituting x[q] = s[q] into constraint row i, we have: * * L[i] <= sum a[i,j] x[j] <= U[i] ==> * j * * L[i] <= sum a[i,j] x[j] + a[i,q] x[q] <= U[i] ==> * j!=q * * L[i] <= sum a[i,j] x[j] + a[i,q] s[q] <= U[i] ==> * j!=q * * L~[i] <= sum a[i,j] x[j] + a[i,q] s <= U~[i], * j!=q * * where * * L~[i] = L[i] - a[i,q] s[q], U~[i] = U[i] - a[i,q] s[q] (3) * * are lower and upper bounds of row i in the transformed problem, * resp. * * RECOVERING BASIC SOLUTION * * Column q is assigned status GLP_NS and its value is assigned s[q]. * * RECOVERING INTERIOR-POINT SOLUTION * * Value of column q is assigned s[q]. * * RECOVERING MIP SOLUTION * * Value of column q is assigned s[q]. */ struct fixed_col { /* fixed column */ int q; /* column reference number for variable x[q] */ double s; /* value, at which x[q] is fixed */ }; static int rcv_fixed_col(NPP *npp, void *info); void npp_fixed_col(NPP *npp, NPPCOL *q) { /* process fixed column */ struct fixed_col *info; NPPROW *i; NPPAIJ *aij; /* the column must be fixed */ xassert(q->lb == q->ub); /* create transformation stack entry */ info = npp_push_tse(npp, rcv_fixed_col, sizeof(struct fixed_col)); info->q = q->j; info->s = q->lb; /* substitute x[q] = s[q] into objective row */ npp->c0 += q->coef * q->lb; /* substitute x[q] = s[q] into constraint rows */ for (aij = q->ptr; aij != NULL; aij = aij->c_next) { i = aij->row; if (i->lb == i->ub) i->ub = (i->lb -= aij->val * q->lb); else { if (i->lb != -DBL_MAX) i->lb -= aij->val * q->lb; if (i->ub != +DBL_MAX) i->ub -= aij->val * q->lb; } } /* remove the column from the problem */ npp_del_col(npp, q); return; } static int rcv_fixed_col(NPP *npp, void *_info) { /* recover fixed column */ struct fixed_col *info = _info; if (npp->sol == GLP_SOL) npp->c_stat[info->q] = GLP_NS; npp->c_value[info->q] = info->s; return 0; } /*********************************************************************** * NAME * * npp_make_equality - process row with almost identical bounds * * SYNOPSIS * * #include "glpnpp.h" * int npp_make_equality(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_make_equality processes row p: * * L[p] <= sum a[p,j] x[j] <= U[p], (1) * j * * where -oo < L[p] < U[p] < +oo, i.e. which is double-sided inequality * constraint. * * RETURNS * * 0 - row bounds have not been changed; * * 1 - row has been replaced by equality constraint. * * PROBLEM TRANSFORMATION * * If bounds of row (1) are very close to each other: * * U[p] - L[p] <= eps, (2) * * where eps is an absolute tolerance for row value, the row can be * replaced by the following almost equivalent equiality constraint: * * sum a[p,j] x[j] = b, (3) * j * * where b = (L[p] + U[p]) / 2. If the right-hand side in (3) happens * to be very close to its nearest integer: * * |b - floor(b + 0.5)| <= eps, (4) * * it is reasonable to use this nearest integer as the right-hand side. * * RECOVERING BASIC SOLUTION * * Status of row p in solution to the original problem is determined * by its status and the sign of its multiplier pi[p] in solution to * the transformed problem as follows: * * +-----------------------+---------+--------------------+ * | Status of row p | Sign of | Status of row p | * | (transformed problem) | pi[p] | (original problem) | * +-----------------------+---------+--------------------+ * | GLP_BS | + / - | GLP_BS | * | GLP_NS | + | GLP_NL | * | GLP_NS | - | GLP_NU | * +-----------------------+---------+--------------------+ * * Value of row multiplier pi[p] in solution to the original problem is * the same as in solution to the transformed problem. * * RECOVERING INTERIOR POINT SOLUTION * * Value of row multiplier pi[p] in solution to the original problem is * the same as in solution to the transformed problem. * * RECOVERING MIP SOLUTION * * None needed. */ struct make_equality { /* row with almost identical bounds */ int p; /* row reference number */ }; static int rcv_make_equality(NPP *npp, void *info); int npp_make_equality(NPP *npp, NPPROW *p) { /* process row with almost identical bounds */ struct make_equality *info; double b, eps, nint; /* the row must be double-sided inequality */ xassert(p->lb != -DBL_MAX); xassert(p->ub != +DBL_MAX); xassert(p->lb < p->ub); /* check row bounds */ eps = 1e-9 + 1e-12 * fabs(p->lb); if (p->ub - p->lb > eps) return 0; /* row bounds are very close to each other */ /* create transformation stack entry */ info = npp_push_tse(npp, rcv_make_equality, sizeof(struct make_equality)); info->p = p->i; /* compute right-hand side */ b = 0.5 * (p->ub + p->lb); nint = floor(b + 0.5); if (fabs(b - nint) <= eps) b = nint; /* replace row p by almost equivalent equality constraint */ p->lb = p->ub = b; return 1; } int rcv_make_equality(NPP *npp, void *_info) { /* recover row with almost identical bounds */ struct make_equality *info = _info; if (npp->sol == GLP_SOL) { if (npp->r_stat[info->p] == GLP_BS) npp->r_stat[info->p] = GLP_BS; else if (npp->r_stat[info->p] == GLP_NS) { if (npp->r_pi[info->p] >= 0.0) npp->r_stat[info->p] = GLP_NL; else npp->r_stat[info->p] = GLP_NU; } else { npp_error(); return 1; } } return 0; } /*********************************************************************** * NAME * * npp_make_fixed - process column with almost identical bounds * * SYNOPSIS * * #include "glpnpp.h" * int npp_make_fixed(NPP *npp, NPPCOL *q); * * DESCRIPTION * * The routine npp_make_fixed processes column q: * * l[q] <= x[q] <= u[q], (1) * * where -oo < l[q] < u[q] < +oo, i.e. which has both lower and upper * bounds. * * RETURNS * * 0 - column bounds have not been changed; * * 1 - column has been fixed. * * PROBLEM TRANSFORMATION * * If bounds of column (1) are very close to each other: * * u[q] - l[q] <= eps, (2) * * where eps is an absolute tolerance for column value, the column can * be fixed: * * x[q] = s[q], (3) * * where s[q] = (l[q] + u[q]) / 2. And if the fixed column value s[q] * happens to be very close to its nearest integer: * * |s[q] - floor(s[q] + 0.5)| <= eps, (4) * * it is reasonable to use this nearest integer as the fixed value. * * RECOVERING BASIC SOLUTION * * In the dual system of the original (as well as transformed) problem * column q corresponds to the following row: * * sum a[i,q] pi[i] + lambda[q] = c[q]. (5) * i * * Since multipliers pi[i] are known for all rows from solution to the * transformed problem, formula (5) allows computing value of multiplier * (reduced cost) for column q: * * lambda[q] = c[q] - sum a[i,q] pi[i]. (6) * i * * Status of column q in solution to the original problem is determined * by its status and the sign of its multiplier lambda[q] in solution to * the transformed problem as follows: * * +-----------------------+-----------+--------------------+ * | Status of column q | Sign of | Status of column q | * | (transformed problem) | lambda[q] | (original problem) | * +-----------------------+-----------+--------------------+ * | GLP_BS | + / - | GLP_BS | * | GLP_NS | + | GLP_NL | * | GLP_NS | - | GLP_NU | * +-----------------------+-----------+--------------------+ * * Value of column q in solution to the original problem is the same as * in solution to the transformed problem. * * RECOVERING INTERIOR POINT SOLUTION * * Value of column q in solution to the original problem is the same as * in solution to the transformed problem. * * RECOVERING MIP SOLUTION * * None needed. */ struct make_fixed { /* column with almost identical bounds */ int q; /* column reference number */ double c; /* objective coefficient at x[q] */ NPPLFE *ptr; /* list of non-zero coefficients a[i,q] */ }; static int rcv_make_fixed(NPP *npp, void *info); int npp_make_fixed(NPP *npp, NPPCOL *q) { /* process column with almost identical bounds */ struct make_fixed *info; NPPAIJ *aij; NPPLFE *lfe; double s, eps, nint; /* the column must be double-bounded */ xassert(q->lb != -DBL_MAX); xassert(q->ub != +DBL_MAX); xassert(q->lb < q->ub); /* check column bounds */ eps = 1e-9 + 1e-12 * fabs(q->lb); if (q->ub - q->lb > eps) return 0; /* column bounds are very close to each other */ /* create transformation stack entry */ info = npp_push_tse(npp, rcv_make_fixed, sizeof(struct make_fixed)); info->q = q->j; info->c = q->coef; info->ptr = NULL; /* save column coefficients a[i,q] (needed for basic solution only) */ if (npp->sol == GLP_SOL) { for (aij = q->ptr; aij != NULL; aij = aij->c_next) { lfe = dmp_get_atom(npp->stack, sizeof(NPPLFE)); lfe->ref = aij->row->i; lfe->val = aij->val; lfe->next = info->ptr; info->ptr = lfe; } } /* compute column fixed value */ s = 0.5 * (q->ub + q->lb); nint = floor(s + 0.5); if (fabs(s - nint) <= eps) s = nint; /* make column q fixed */ q->lb = q->ub = s; return 1; } static int rcv_make_fixed(NPP *npp, void *_info) { /* recover column with almost identical bounds */ struct make_fixed *info = _info; NPPLFE *lfe; double lambda; if (npp->sol == GLP_SOL) { if (npp->c_stat[info->q] == GLP_BS) npp->c_stat[info->q] = GLP_BS; else if (npp->c_stat[info->q] == GLP_NS) { /* compute multiplier for column q with formula (6) */ lambda = info->c; for (lfe = info->ptr; lfe != NULL; lfe = lfe->next) lambda -= lfe->val * npp->r_pi[lfe->ref]; /* assign status to non-basic column */ if (lambda >= 0.0) npp->c_stat[info->q] = GLP_NL; else npp->c_stat[info->q] = GLP_NU; } else { npp_error(); return 1; } } return 0; } /* eof */ sources_5316/external/glpk/glpluf.h0000644000176700017670000003546211401660400016146 0ustar paulpaul/* glpluf.h (LU-factorization) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPLUF_H #define GLPLUF_H /*********************************************************************** * The structure LUF defines LU-factorization of a square matrix A and * is the following quartet: * * [A] = (F, V, P, Q), (1) * * where F and V are such matrices that * * A = F * V, (2) * * and P and Q are such permutation matrices that the matrix * * L = P * F * inv(P) (3) * * is lower triangular with unity diagonal, and the matrix * * U = P * V * Q (4) * * is upper triangular. All the matrices have the order n. * * Matrices F and V are stored in row- and column-wise sparse format * as row and column linked lists of non-zero elements. Unity elements * on the main diagonal of matrix F are not stored. Pivot elements of * matrix V (which correspond to diagonal elements of matrix U) are * stored separately in an ordinary array. * * Permutation matrices P and Q are stored in ordinary arrays in both * row- and column-like formats. * * Matrices L and U are completely defined by matrices F, V, P, and Q * and therefore not stored explicitly. * * The factorization (1)-(4) is a version of LU-factorization. Indeed, * from (3) and (4) it follows that: * * F = inv(P) * L * P, * * U = inv(P) * U * inv(Q), * * and substitution into (2) leads to: * * A = F * V = inv(P) * L * U * inv(Q). * * For more details see the program documentation. */ typedef struct LUF LUF; struct LUF { /* LU-factorization of a square matrix */ int n_max; /* maximal value of n (increased automatically, if necessary) */ int n; /* the order of matrices A, F, V, P, Q */ int valid; /* the factorization is valid only if this flag is set */ /*--------------------------------------------------------------*/ /* matrix F in row-wise format */ int *fr_ptr; /* int fr_ptr[1+n_max]; */ /* fr_ptr[i], i = 1,...,n, is a pointer to the first element of i-th row in SVA */ int *fr_len; /* int fr_len[1+n_max]; */ /* fr_len[i], i = 1,...,n, is the number of elements in i-th row (except unity diagonal element) */ /*--------------------------------------------------------------*/ /* matrix F in column-wise format */ int *fc_ptr; /* int fc_ptr[1+n_max]; */ /* fc_ptr[j], j = 1,...,n, is a pointer to the first element of j-th column in SVA */ int *fc_len; /* int fc_len[1+n_max]; */ /* fc_len[j], j = 1,...,n, is the number of elements in j-th column (except unity diagonal element) */ /*--------------------------------------------------------------*/ /* matrix V in row-wise format */ int *vr_ptr; /* int vr_ptr[1+n_max]; */ /* vr_ptr[i], i = 1,...,n, is a pointer to the first element of i-th row in SVA */ int *vr_len; /* int vr_len[1+n_max]; */ /* vr_len[i], i = 1,...,n, is the number of elements in i-th row (except pivot element) */ int *vr_cap; /* int vr_cap[1+n_max]; */ /* vr_cap[i], i = 1,...,n, is the capacity of i-th row, i.e. maximal number of elements which can be stored in the row without relocating it, vr_cap[i] >= vr_len[i] */ double *vr_piv; /* double vr_piv[1+n_max]; */ /* vr_piv[p], p = 1,...,n, is the pivot element v[p,q] which corresponds to a diagonal element of matrix U = P*V*Q */ /*--------------------------------------------------------------*/ /* matrix V in column-wise format */ int *vc_ptr; /* int vc_ptr[1+n_max]; */ /* vc_ptr[j], j = 1,...,n, is a pointer to the first element of j-th column in SVA */ int *vc_len; /* int vc_len[1+n_max]; */ /* vc_len[j], j = 1,...,n, is the number of elements in j-th column (except pivot element) */ int *vc_cap; /* int vc_cap[1+n_max]; */ /* vc_cap[j], j = 1,...,n, is the capacity of j-th column, i.e. maximal number of elements which can be stored in the column without relocating it, vc_cap[j] >= vc_len[j] */ /*--------------------------------------------------------------*/ /* matrix P */ int *pp_row; /* int pp_row[1+n_max]; */ /* pp_row[i] = j means that P[i,j] = 1 */ int *pp_col; /* int pp_col[1+n_max]; */ /* pp_col[j] = i means that P[i,j] = 1 */ /* if i-th row or column of matrix F is i'-th row or column of matrix L, or if i-th row of matrix V is i'-th row of matrix U, then pp_row[i'] = i and pp_col[i] = i' */ /*--------------------------------------------------------------*/ /* matrix Q */ int *qq_row; /* int qq_row[1+n_max]; */ /* qq_row[i] = j means that Q[i,j] = 1 */ int *qq_col; /* int qq_col[1+n_max]; */ /* qq_col[j] = i means that Q[i,j] = 1 */ /* if j-th column of matrix V is j'-th column of matrix U, then qq_row[j] = j' and qq_col[j'] = j */ /*--------------------------------------------------------------*/ /* the Sparse Vector Area (SVA) is a set of locations used to store sparse vectors representing rows and columns of matrices F and V; each location is a doublet (ind, val), where ind is an index, and val is a numerical value of a sparse vector element; in the whole each sparse vector is a set of adjacent locations defined by a pointer to the first element and the number of elements; these pointer and number are stored in the corresponding matrix data structure (see above); the left part of SVA is used to store rows and columns of matrix V, and its right part is used to store rows and columns of matrix F; the middle part of SVA contains free (unused) locations */ int sv_size; /* the size of SVA, in locations; all locations are numbered by integers 1, ..., n, and location 0 is not used; if necessary, the SVA size is automatically increased */ int sv_beg, sv_end; /* SVA partitioning pointers: locations from 1 to sv_beg-1 belong to the left part locations from sv_beg to sv_end-1 belong to the middle part locations from sv_end to sv_size belong to the right part the size of the middle part is (sv_end - sv_beg) */ int *sv_ind; /* sv_ind[1+sv_size]; */ /* sv_ind[k], 1 <= k <= sv_size, is the index field of k-th location */ double *sv_val; /* sv_val[1+sv_size]; */ /* sv_val[k], 1 <= k <= sv_size, is the value field of k-th location */ /*--------------------------------------------------------------*/ /* in order to efficiently defragment the left part of SVA there is a doubly linked list of rows and columns of matrix V, where rows are numbered by 1, ..., n, while columns are numbered by n+1, ..., n+n, that allows uniquely identifying each row and column of V by only one integer; in this list rows and columns are ordered by ascending their pointers vr_ptr and vc_ptr */ int sv_head; /* the number of leftmost row/column */ int sv_tail; /* the number of rightmost row/column */ int *sv_prev; /* int sv_prev[1+n_max+n_max]; */ /* sv_prev[k], k = 1,...,n+n, is the number of a row/column which precedes k-th row/column */ int *sv_next; /* int sv_next[1+n_max+n_max]; */ /* sv_next[k], k = 1,...,n+n, is the number of a row/column which succedes k-th row/column */ /*--------------------------------------------------------------*/ /* working segment (used only during factorization) */ double *vr_max; /* int vr_max[1+n_max]; */ /* vr_max[i], 1 <= i <= n, is used only if i-th row of matrix V is active (i.e. belongs to the active submatrix), and is the largest magnitude of elements in i-th row; if vr_max[i] < 0, the largest magnitude is not known yet and should be computed by the pivoting routine */ /*--------------------------------------------------------------*/ /* in order to efficiently implement Markowitz strategy and Duff search technique there are two families {R[0], R[1], ..., R[n]} and {C[0], C[1], ..., C[n]}; member R[k] is the set of active rows of matrix V, which have k non-zeros, and member C[k] is the set of active columns of V, which have k non-zeros in the active submatrix (i.e. in the active rows); each set R[k] and C[k] is implemented as a separate doubly linked list */ int *rs_head; /* int rs_head[1+n_max]; */ /* rs_head[k], 0 <= k <= n, is the number of first active row, which has k non-zeros */ int *rs_prev; /* int rs_prev[1+n_max]; */ /* rs_prev[i], 1 <= i <= n, is the number of previous row, which has the same number of non-zeros as i-th row */ int *rs_next; /* int rs_next[1+n_max]; */ /* rs_next[i], 1 <= i <= n, is the number of next row, which has the same number of non-zeros as i-th row */ int *cs_head; /* int cs_head[1+n_max]; */ /* cs_head[k], 0 <= k <= n, is the number of first active column, which has k non-zeros (in the active rows) */ int *cs_prev; /* int cs_prev[1+n_max]; */ /* cs_prev[j], 1 <= j <= n, is the number of previous column, which has the same number of non-zeros (in the active rows) as j-th column */ int *cs_next; /* int cs_next[1+n_max]; */ /* cs_next[j], 1 <= j <= n, is the number of next column, which has the same number of non-zeros (in the active rows) as j-th column */ /* (end of working segment) */ /*--------------------------------------------------------------*/ /* working arrays */ int *flag; /* int flag[1+n_max]; */ /* integer working array */ double *work; /* double work[1+n_max]; */ /* floating-point working array */ /*--------------------------------------------------------------*/ /* control parameters */ int new_sva; /* new required size of the sparse vector area, in locations; set automatically by the factorizing routine */ double piv_tol; /* threshold pivoting tolerance, 0 < piv_tol < 1; element v[i,j] of the active submatrix fits to be pivot if it satisfies to the stability criterion |v[i,j]| >= piv_tol * max |v[i,*]|, i.e. if it is not very small in the magnitude among other elements in the same row; decreasing this parameter gives better sparsity at the expense of numerical accuracy and vice versa */ int piv_lim; /* maximal allowable number of pivot candidates to be considered; if piv_lim pivot candidates have been considered, the pivoting routine terminates the search with the best candidate found */ int suhl; /* if this flag is set, the pivoting routine applies a heuristic proposed by Uwe Suhl: if a column of the active submatrix has no eligible pivot candidates (i.e. all its elements do not satisfy to the stability criterion), the routine excludes it from futher consideration until it becomes column singleton; in many cases this allows reducing the time needed for pivot searching */ double eps_tol; /* epsilon tolerance; each element of the active submatrix, whose magnitude is less than eps_tol, is replaced by exact zero */ double max_gro; /* maximal allowable growth of elements of matrix V during all the factorization process; if on some eliminaion step the ratio big_v / max_a (see below) becomes greater than max_gro, matrix A is considered as ill-conditioned (assuming that the pivoting tolerance piv_tol has an appropriate value) */ /*--------------------------------------------------------------*/ /* some statistics */ int nnz_a; /* the number of non-zeros in matrix A */ int nnz_f; /* the number of non-zeros in matrix F (except diagonal elements, which are not stored) */ int nnz_v; /* the number of non-zeros in matrix V (except its pivot elements, which are stored in a separate array) */ double max_a; /* the largest magnitude of elements of matrix A */ double big_v; /* the largest magnitude of elements of matrix V appeared in the active submatrix during all the factorization process */ int rank; /* estimated rank of matrix A */ }; /* return codes: */ #define LUF_ESING 1 /* singular matrix */ #define LUF_ECOND 2 /* ill-conditioned matrix */ #define luf_create_it _glp_luf_create_it LUF *luf_create_it(void); /* create LU-factorization */ #define luf_defrag_sva _glp_luf_defrag_sva void luf_defrag_sva(LUF *luf); /* defragment the sparse vector area */ #define luf_enlarge_row _glp_luf_enlarge_row int luf_enlarge_row(LUF *luf, int i, int cap); /* enlarge row capacity */ #define luf_enlarge_col _glp_luf_enlarge_col int luf_enlarge_col(LUF *luf, int j, int cap); /* enlarge column capacity */ #define luf_factorize _glp_luf_factorize int luf_factorize(LUF *luf, int n, int (*col)(void *info, int j, int ind[], double val[]), void *info); /* compute LU-factorization */ #define luf_f_solve _glp_luf_f_solve void luf_f_solve(LUF *luf, int tr, double x[]); /* solve system F*x = b or F'*x = b */ #define luf_v_solve _glp_luf_v_solve void luf_v_solve(LUF *luf, int tr, double x[]); /* solve system V*x = b or V'*x = b */ #define luf_a_solve _glp_luf_a_solve void luf_a_solve(LUF *luf, int tr, double x[]); /* solve system A*x = b or A'*x = b */ #define luf_delete_it _glp_luf_delete_it void luf_delete_it(LUF *luf); /* delete LU-factorization */ #endif /* eof */ sources_5316/external/glpk/glpmpl04.c0000644000176700017670000013424111411455543016315 0ustar paulpaul/* glpmpl04.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_ERRNO #define _GLPSTD_STDIO #include "glpmpl.h" #define xfault xerror #define dmp_create_poolx(size) dmp_create_pool() /**********************************************************************/ /* * * GENERATING AND POSTSOLVING MODEL * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- alloc_content - allocate content arrays for all model objects. -- -- This routine allocates content arrays for all existing model objects -- and thereby finalizes creating model. -- -- This routine must be called immediately after reading model section, -- i.e. before reading data section or generating model. */ void alloc_content(MPL *mpl) { STATEMENT *stmt; /* walk through all model statements */ for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { switch (stmt->type) { case A_SET: /* model set */ xassert(stmt->u.set->array == NULL); stmt->u.set->array = create_array(mpl, A_ELEMSET, stmt->u.set->dim); break; case A_PARAMETER: /* model parameter */ xassert(stmt->u.par->array == NULL); switch (stmt->u.par->type) { case A_NUMERIC: case A_INTEGER: case A_BINARY: stmt->u.par->array = create_array(mpl, A_NUMERIC, stmt->u.par->dim); break; case A_SYMBOLIC: stmt->u.par->array = create_array(mpl, A_SYMBOLIC, stmt->u.par->dim); break; default: xassert(stmt != stmt); } break; case A_VARIABLE: /* model variable */ xassert(stmt->u.var->array == NULL); stmt->u.var->array = create_array(mpl, A_ELEMVAR, stmt->u.var->dim); break; case A_CONSTRAINT: /* model constraint/objective */ xassert(stmt->u.con->array == NULL); stmt->u.con->array = create_array(mpl, A_ELEMCON, stmt->u.con->dim); break; #if 1 /* 11/II-2008 */ case A_TABLE: #endif case A_SOLVE: case A_CHECK: case A_DISPLAY: case A_PRINTF: case A_FOR: /* functional statements have no content array */ break; default: xassert(stmt != stmt); } } return; } /*---------------------------------------------------------------------- -- generate_model - generate model. -- -- This routine executes the model statements which precede the solve -- statement. */ void generate_model(MPL *mpl) { STATEMENT *stmt; xassert(!mpl->flag_p); for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { execute_statement(mpl, stmt); if (mpl->stmt->type == A_SOLVE) break; } mpl->stmt = stmt; return; } /*---------------------------------------------------------------------- -- build_problem - build problem instance. -- -- This routine builds lists of rows and columns for problem instance, -- which corresponds to the generated model. */ void build_problem(MPL *mpl) { STATEMENT *stmt; MEMBER *memb; VARIABLE *v; CONSTRAINT *c; FORMULA *t; int i, j; xassert(mpl->m == 0); xassert(mpl->n == 0); xassert(mpl->row == NULL); xassert(mpl->col == NULL); /* check that all elemental variables has zero column numbers */ for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_VARIABLE) { v = stmt->u.var; for (memb = v->array->head; memb != NULL; memb = memb->next) xassert(memb->value.var->j == 0); } } /* assign row numbers to elemental constraints and objectives */ for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_CONSTRAINT) { c = stmt->u.con; for (memb = c->array->head; memb != NULL; memb = memb->next) { xassert(memb->value.con->i == 0); memb->value.con->i = ++mpl->m; /* walk through linear form and mark elemental variables, which are referenced at least once */ for (t = memb->value.con->form; t != NULL; t = t->next) { xassert(t->var != NULL); t->var->memb->value.var->j = -1; } } } } /* assign column numbers to marked elemental variables */ for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_VARIABLE) { v = stmt->u.var; for (memb = v->array->head; memb != NULL; memb = memb->next) if (memb->value.var->j != 0) memb->value.var->j = ++mpl->n; } } /* build list of rows */ mpl->row = xcalloc(1+mpl->m, sizeof(ELEMCON *)); for (i = 1; i <= mpl->m; i++) mpl->row[i] = NULL; for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_CONSTRAINT) { c = stmt->u.con; for (memb = c->array->head; memb != NULL; memb = memb->next) { i = memb->value.con->i; xassert(1 <= i && i <= mpl->m); xassert(mpl->row[i] == NULL); mpl->row[i] = memb->value.con; } } } for (i = 1; i <= mpl->m; i++) xassert(mpl->row[i] != NULL); /* build list of columns */ mpl->col = xcalloc(1+mpl->n, sizeof(ELEMVAR *)); for (j = 1; j <= mpl->n; j++) mpl->col[j] = NULL; for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_VARIABLE) { v = stmt->u.var; for (memb = v->array->head; memb != NULL; memb = memb->next) { j = memb->value.var->j; if (j == 0) continue; xassert(1 <= j && j <= mpl->n); xassert(mpl->col[j] == NULL); mpl->col[j] = memb->value.var; } } } for (j = 1; j <= mpl->n; j++) xassert(mpl->col[j] != NULL); return; } /*---------------------------------------------------------------------- -- postsolve_model - postsolve model. -- -- This routine executes the model statements which follow the solve -- statement. */ void postsolve_model(MPL *mpl) { STATEMENT *stmt; xassert(!mpl->flag_p); mpl->flag_p = 1; for (stmt = mpl->stmt; stmt != NULL; stmt = stmt->next) execute_statement(mpl, stmt); mpl->stmt = NULL; return; } /*---------------------------------------------------------------------- -- clean_model - clean model content. -- -- This routine cleans the model content that assumes deleting all stuff -- dynamically allocated on generating/postsolving phase. -- -- Actually cleaning model content is not needed. This function is used -- mainly to be sure that there were no logical errors on using dynamic -- memory pools during the generation phase. -- -- NOTE: This routine must not be called if any errors were detected on -- the generation phase. */ void clean_model(MPL *mpl) { STATEMENT *stmt; for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) clean_statement(mpl, stmt); /* check that all atoms have been returned to their pools */ if (dmp_in_use(mpl->strings).lo != 0) mpl_error(mpl, "internal logic error: %d string segment(s) were lo" "st", dmp_in_use(mpl->strings).lo); if (dmp_in_use(mpl->symbols).lo != 0) mpl_error(mpl, "internal logic error: %d symbol(s) were lost", dmp_in_use(mpl->symbols).lo); if (dmp_in_use(mpl->tuples).lo != 0) mpl_error(mpl, "internal logic error: %d n-tuple component(s) were" " lost", dmp_in_use(mpl->tuples).lo); if (dmp_in_use(mpl->arrays).lo != 0) mpl_error(mpl, "internal logic error: %d array(s) were lost", dmp_in_use(mpl->arrays).lo); if (dmp_in_use(mpl->members).lo != 0) mpl_error(mpl, "internal logic error: %d array member(s) were lost" , dmp_in_use(mpl->members).lo); if (dmp_in_use(mpl->elemvars).lo != 0) mpl_error(mpl, "internal logic error: %d elemental variable(s) wer" "e lost", dmp_in_use(mpl->elemvars).lo); if (dmp_in_use(mpl->formulae).lo != 0) mpl_error(mpl, "internal logic error: %d linear term(s) were lost", dmp_in_use(mpl->formulae).lo); if (dmp_in_use(mpl->elemcons).lo != 0) mpl_error(mpl, "internal logic error: %d elemental constraint(s) w" "ere lost", dmp_in_use(mpl->elemcons).lo); return; } /**********************************************************************/ /* * * INPUT/OUTPUT * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- open_input - open input text file. -- -- This routine opens the input text file for scanning. */ void open_input(MPL *mpl, char *file) { mpl->line = 0; mpl->c = '\n'; mpl->token = 0; mpl->imlen = 0; mpl->image[0] = '\0'; mpl->value = 0.0; mpl->b_token = T_EOF; mpl->b_imlen = 0; mpl->b_image[0] = '\0'; mpl->b_value = 0.0; mpl->f_dots = 0; mpl->f_scan = 0; mpl->f_token = 0; mpl->f_imlen = 0; mpl->f_image[0] = '\0'; mpl->f_value = 0.0; memset(mpl->context, ' ', CONTEXT_SIZE); mpl->c_ptr = 0; xassert(mpl->in_fp == NULL); mpl->in_fp = xfopen(file, "r"); if (mpl->in_fp == NULL) mpl_error(mpl, "unable to open %s - %s", file, xerrmsg()); mpl->in_file = file; /* scan the very first character */ get_char(mpl); /* scan the very first token */ get_token(mpl); return; } /*---------------------------------------------------------------------- -- read_char - read next character from input text file. -- -- This routine returns a next ASCII character read from the input text -- file. If the end of file has been reached, EOF is returned. */ int read_char(MPL *mpl) { int c; xassert(mpl->in_fp != NULL); c = xfgetc(mpl->in_fp); if (c < 0) { if (xferror(mpl->in_fp)) mpl_error(mpl, "read error on %s - %s", mpl->in_file, xerrmsg()); c = EOF; } return c; } /*---------------------------------------------------------------------- -- close_input - close input text file. -- -- This routine closes the input text file. */ void close_input(MPL *mpl) { xassert(mpl->in_fp != NULL); xfclose(mpl->in_fp); mpl->in_fp = NULL; mpl->in_file = NULL; return; } /*---------------------------------------------------------------------- -- open_output - open output text file. -- -- This routine opens the output text file for writing data produced by -- display and printf statements. */ void open_output(MPL *mpl, char *file) { xassert(mpl->out_fp == NULL); if (file == NULL) { file = ""; mpl->out_fp = (void *)stdout; } else { mpl->out_fp = xfopen(file, "w"); if (mpl->out_fp == NULL) mpl_error(mpl, "unable to create %s - %s", file, xerrmsg()); } mpl->out_file = xmalloc(strlen(file)+1); strcpy(mpl->out_file, file); return; } /*---------------------------------------------------------------------- -- write_char - write next character to output text file. -- -- This routine writes an ASCII character to the output text file. */ void write_char(MPL *mpl, int c) { xassert(mpl->out_fp != NULL); if (mpl->out_fp == (void *)stdout) xprintf("%c", c); else xfprintf(mpl->out_fp, "%c", c); return; } /*---------------------------------------------------------------------- -- write_text - format and write text to output text file. -- -- This routine formats a text using the format control string and then -- writes this text to the output text file. */ void write_text(MPL *mpl, char *fmt, ...) { va_list arg; char buf[OUTBUF_SIZE], *c; va_start(arg, fmt); vsprintf(buf, fmt, arg); xassert(strlen(buf) < sizeof(buf)); va_end(arg); for (c = buf; *c != '\0'; c++) write_char(mpl, *c); return; } /*---------------------------------------------------------------------- -- flush_output - finalize writing data to output text file. -- -- This routine finalizes writing data to the output text file. */ void flush_output(MPL *mpl) { xassert(mpl->out_fp != NULL); if (mpl->out_fp != (void *)stdout) { xfflush(mpl->out_fp); if (xferror(mpl->out_fp)) mpl_error(mpl, "write error on %s - %s", mpl->out_file, xerrmsg()); } return; } /**********************************************************************/ /* * * SOLVER INTERFACE * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- error - print error message and terminate model processing. -- -- This routine formats and prints an error message and then terminates -- model processing. */ void mpl_error(MPL *mpl, char *fmt, ...) { va_list arg; char msg[4095+1]; va_start(arg, fmt); vsprintf(msg, fmt, arg); xassert(strlen(msg) < sizeof(msg)); va_end(arg); switch (mpl->phase) { case 1: case 2: /* translation phase */ xprintf("%s:%d: %s\n", mpl->in_file == NULL ? "(unknown)" : mpl->in_file, mpl->line, msg); print_context(mpl); break; case 3: /* generation/postsolve phase */ xprintf("%s:%d: %s\n", mpl->mod_file == NULL ? "(unknown)" : mpl->mod_file, mpl->stmt == NULL ? 0 : mpl->stmt->line, msg); break; default: xassert(mpl != mpl); } mpl->phase = 4; longjmp(mpl->jump, 1); /* no return */ } /*---------------------------------------------------------------------- -- warning - print warning message and continue model processing. -- -- This routine formats and prints a warning message and returns to the -- calling program. */ void warning(MPL *mpl, char *fmt, ...) { va_list arg; char msg[4095+1]; va_start(arg, fmt); vsprintf(msg, fmt, arg); xassert(strlen(msg) < sizeof(msg)); va_end(arg); switch (mpl->phase) { case 1: case 2: /* translation phase */ xprintf("%s:%d: warning: %s\n", mpl->in_file == NULL ? "(unknown)" : mpl->in_file, mpl->line, msg); break; case 3: /* generation/postsolve phase */ xprintf("%s:%d: warning: %s\n", mpl->mod_file == NULL ? "(unknown)" : mpl->mod_file, mpl->stmt == NULL ? 0 : mpl->stmt->line, msg); break; default: xassert(mpl != mpl); } return; } /*---------------------------------------------------------------------- -- mpl_initialize - create and initialize translator database. -- -- *Synopsis* -- -- #include "glpmpl.h" -- MPL *mpl_initialize(void); -- -- *Description* -- -- The routine mpl_initialize creates and initializes the database used -- by the GNU MathProg translator. -- -- *Returns* -- -- The routine returns a pointer to the database created. */ MPL *mpl_initialize(void) { MPL *mpl; mpl = xmalloc(sizeof(MPL)); /* scanning segment */ mpl->line = 0; mpl->c = 0; mpl->token = 0; mpl->imlen = 0; mpl->image = xcalloc(MAX_LENGTH+1, sizeof(char)); mpl->image[0] = '\0'; mpl->value = 0.0; mpl->b_token = 0; mpl->b_imlen = 0; mpl->b_image = xcalloc(MAX_LENGTH+1, sizeof(char)); mpl->b_image[0] = '\0'; mpl->b_value = 0.0; mpl->f_dots = 0; mpl->f_scan = 0; mpl->f_token = 0; mpl->f_imlen = 0; mpl->f_image = xcalloc(MAX_LENGTH+1, sizeof(char)); mpl->f_image[0] = '\0'; mpl->f_value = 0.0; mpl->context = xcalloc(CONTEXT_SIZE, sizeof(char)); memset(mpl->context, ' ', CONTEXT_SIZE); mpl->c_ptr = 0; mpl->flag_d = 0; /* translating segment */ mpl->pool = dmp_create_poolx(0); mpl->tree = avl_create_tree(avl_strcmp, NULL); mpl->model = NULL; mpl->flag_x = 0; mpl->as_within = 0; mpl->as_in = 0; mpl->as_binary = 0; mpl->flag_s = 0; /* common segment */ mpl->strings = dmp_create_poolx(sizeof(STRING)); mpl->symbols = dmp_create_poolx(sizeof(SYMBOL)); mpl->tuples = dmp_create_poolx(sizeof(TUPLE)); mpl->arrays = dmp_create_poolx(sizeof(ARRAY)); mpl->members = dmp_create_poolx(sizeof(MEMBER)); mpl->elemvars = dmp_create_poolx(sizeof(ELEMVAR)); mpl->formulae = dmp_create_poolx(sizeof(FORMULA)); mpl->elemcons = dmp_create_poolx(sizeof(ELEMCON)); mpl->a_list = NULL; mpl->sym_buf = xcalloc(255+1, sizeof(char)); mpl->sym_buf[0] = '\0'; mpl->tup_buf = xcalloc(255+1, sizeof(char)); mpl->tup_buf[0] = '\0'; /* generating/postsolving segment */ mpl->rand = rng_create_rand(); mpl->flag_p = 0; mpl->stmt = NULL; #if 1 /* 11/II-2008 */ mpl->dca = NULL; #endif mpl->m = 0; mpl->n = 0; mpl->row = NULL; mpl->col = NULL; /* input/output segment */ mpl->in_fp = NULL; mpl->in_file = NULL; mpl->out_fp = NULL; mpl->out_file = NULL; mpl->prt_fp = NULL; mpl->prt_file = NULL; /* solver interface segment */ if (setjmp(mpl->jump)) xassert(mpl != mpl); mpl->phase = 0; mpl->mod_file = NULL; mpl->mpl_buf = xcalloc(255+1, sizeof(char)); mpl->mpl_buf[0] = '\0'; return mpl; } /*---------------------------------------------------------------------- -- mpl_read_model - read model section and optional data section. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_read_model(MPL *mpl, char *file, int skip_data); -- -- *Description* -- -- The routine mpl_read_model reads model section and optionally data -- section, which may follow the model section, from the text file, -- whose name is the character string file, performs translating model -- statements and data blocks, and stores all the information in the -- translator database. -- -- The parameter skip_data is a flag. If the input file contains the -- data section and this flag is set, the data section is not read as -- if there were no data section and a warning message is issued. This -- allows reading the data section from another input file. -- -- This routine should be called once after the routine mpl_initialize -- and before other API routines. -- -- *Returns* -- -- The routine mpl_read_model returns one the following codes: -- -- 1 - translation successful. The input text file contains only model -- section. In this case the calling program may call the routine -- mpl_read_data to read data section from another file. -- 2 - translation successful. The input text file contains both model -- and data section. -- 4 - processing failed due to some errors. In this case the calling -- program should call the routine mpl_terminate to terminate model -- processing. */ int mpl_read_model(MPL *mpl, char *file, int skip_data) { if (mpl->phase != 0) xfault("mpl_read_model: invalid call sequence\n"); if (file == NULL) xfault("mpl_read_model: no input filename specified\n"); /* set up error handler */ if (setjmp(mpl->jump)) goto done; /* translate model section */ mpl->phase = 1; xprintf("Reading model section from %s...\n", file); open_input(mpl, file); model_section(mpl); if (mpl->model == NULL) mpl_error(mpl, "empty model section not allowed"); /* save name of the input text file containing model section for error diagnostics during the generation phase */ mpl->mod_file = xcalloc(strlen(file)+1, sizeof(char)); strcpy(mpl->mod_file, mpl->in_file); /* allocate content arrays for all model objects */ alloc_content(mpl); /* optional data section may begin with the keyword 'data' */ if (is_keyword(mpl, "data")) { if (skip_data) { warning(mpl, "data section ignored"); goto skip; } mpl->flag_d = 1; get_token(mpl /* data */); if (mpl->token != T_SEMICOLON) mpl_error(mpl, "semicolon missing where expected"); get_token(mpl /* ; */); /* translate data section */ mpl->phase = 2; xprintf("Reading data section from %s...\n", file); data_section(mpl); } /* process end statement */ end_statement(mpl); skip: xprintf("%d line%s were read\n", mpl->line, mpl->line == 1 ? "" : "s"); close_input(mpl); done: /* return to the calling program */ return mpl->phase; } /*---------------------------------------------------------------------- -- mpl_read_data - read data section. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_read_data(MPL *mpl, char *file); -- -- *Description* -- -- The routine mpl_read_data reads data section from the text file, -- whose name is the character string file, performs translating data -- blocks, and stores the data read in the translator database. -- -- If this routine is used, it should be called once after the routine -- mpl_read_model and if the latter returned the code 1. -- -- *Returns* -- -- The routine mpl_read_data returns one of the following codes: -- -- 2 - data section has been successfully processed. -- 4 - processing failed due to some errors. In this case the calling -- program should call the routine mpl_terminate to terminate model -- processing. */ int mpl_read_data(MPL *mpl, char *file) #if 0 /* 02/X-2008 */ { if (mpl->phase != 1) #else { if (!(mpl->phase == 1 || mpl->phase == 2)) #endif xfault("mpl_read_data: invalid call sequence\n"); if (file == NULL) xfault("mpl_read_data: no input filename specified\n"); /* set up error handler */ if (setjmp(mpl->jump)) goto done; /* process data section */ mpl->phase = 2; xprintf("Reading data section from %s...\n", file); mpl->flag_d = 1; open_input(mpl, file); /* in this case the keyword 'data' is optional */ if (is_literal(mpl, "data")) { get_token(mpl /* data */); if (mpl->token != T_SEMICOLON) mpl_error(mpl, "semicolon missing where expected"); get_token(mpl /* ; */); } data_section(mpl); /* process end statement */ end_statement(mpl); xprintf("%d line%s were read\n", mpl->line, mpl->line == 1 ? "" : "s"); close_input(mpl); done: /* return to the calling program */ return mpl->phase; } /*---------------------------------------------------------------------- -- mpl_generate - generate model. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_generate(MPL *mpl, char *file); -- -- *Description* -- -- The routine mpl_generate generates the model using its description -- stored in the translator database. This phase means generating all -- variables, constraints, and objectives, executing check and display -- statements, which precede the solve statement (if it is presented), -- and building the problem instance. -- -- The character string file specifies the name of output text file, to -- which output produced by display statements should be written. It is -- allowed to specify NULL, in which case the output goes to stdout via -- the routine print. -- -- This routine should be called once after the routine mpl_read_model -- or mpl_read_data and if one of the latters returned the code 2. -- -- *Returns* -- -- The routine mpl_generate returns one of the following codes: -- -- 3 - model has been successfully generated. In this case the calling -- program may call other api routines to obtain components of the -- problem instance from the translator database. -- 4 - processing failed due to some errors. In this case the calling -- program should call the routine mpl_terminate to terminate model -- processing. */ int mpl_generate(MPL *mpl, char *file) { if (!(mpl->phase == 1 || mpl->phase == 2)) xfault("mpl_generate: invalid call sequence\n"); /* set up error handler */ if (setjmp(mpl->jump)) goto done; /* generate model */ mpl->phase = 3; open_output(mpl, file); generate_model(mpl); flush_output(mpl); /* build problem instance */ build_problem(mpl); /* generation phase has been finished */ xprintf("Model has been successfully generated\n"); done: /* return to the calling program */ return mpl->phase; } /*---------------------------------------------------------------------- -- mpl_get_prob_name - obtain problem (model) name. -- -- *Synopsis* -- -- #include "glpmpl.h" -- char *mpl_get_prob_name(MPL *mpl); -- -- *Returns* -- -- The routine mpl_get_prob_name returns a pointer to internal buffer, -- which contains symbolic name of the problem (model). -- -- *Note* -- -- Currently MathProg has no feature to assign a symbolic name to the -- model. Therefore the routine mpl_get_prob_name tries to construct -- such name using the name of input text file containing model section, -- although this is not a good idea (due to portability problems). */ char *mpl_get_prob_name(MPL *mpl) { char *name = mpl->mpl_buf; char *file = mpl->mod_file; int k; if (mpl->phase != 3) xfault("mpl_get_prob_name: invalid call sequence\n"); for (;;) { if (strchr(file, '/') != NULL) file = strchr(file, '/') + 1; else if (strchr(file, '\\') != NULL) file = strchr(file, '\\') + 1; else if (strchr(file, ':') != NULL) file = strchr(file, ':') + 1; else break; } for (k = 0; ; k++) { if (k == 255) break; if (!(isalnum((unsigned char)*file) || *file == '_')) break; name[k] = *file++; } if (k == 0) strcpy(name, "Unknown"); else name[k] = '\0'; xassert(strlen(name) <= 255); return name; } /*---------------------------------------------------------------------- -- mpl_get_num_rows - determine number of rows. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_get_num_rows(MPL *mpl); -- -- *Returns* -- -- The routine mpl_get_num_rows returns total number of rows in the -- problem, where each row is an individual constraint or objective. */ int mpl_get_num_rows(MPL *mpl) { if (mpl->phase != 3) xfault("mpl_get_num_rows: invalid call sequence\n"); return mpl->m; } /*---------------------------------------------------------------------- -- mpl_get_num_cols - determine number of columns. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_get_num_cols(MPL *mpl); -- -- *Returns* -- -- The routine mpl_get_num_cols returns total number of columns in the -- problem, where each column is an individual variable. */ int mpl_get_num_cols(MPL *mpl) { if (mpl->phase != 3) xfault("mpl_get_num_cols: invalid call sequence\n"); return mpl->n; } /*---------------------------------------------------------------------- -- mpl_get_row_name - obtain row name. -- -- *Synopsis* -- -- #include "glpmpl.h" -- char *mpl_get_row_name(MPL *mpl, int i); -- -- *Returns* -- -- The routine mpl_get_row_name returns a pointer to internal buffer, -- which contains symbolic name of i-th row of the problem. */ char *mpl_get_row_name(MPL *mpl, int i) { char *name = mpl->mpl_buf, *t; int len; if (mpl->phase != 3) xfault("mpl_get_row_name: invalid call sequence\n"); if (!(1 <= i && i <= mpl->m)) xfault("mpl_get_row_name: i = %d; row number out of range\n", i); strcpy(name, mpl->row[i]->con->name); len = strlen(name); xassert(len <= 255); t = format_tuple(mpl, '[', mpl->row[i]->memb->tuple); while (*t) { if (len == 255) break; name[len++] = *t++; } name[len] = '\0'; if (len == 255) strcpy(name+252, "..."); xassert(strlen(name) <= 255); return name; } /*---------------------------------------------------------------------- -- mpl_get_row_kind - determine row kind. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_get_row_kind(MPL *mpl, int i); -- -- *Returns* -- -- The routine mpl_get_row_kind returns the kind of i-th row, which can -- be one of the following: -- -- MPL_ST - non-free (constraint) row; -- MPL_MIN - free (objective) row to be minimized; -- MPL_MAX - free (objective) row to be maximized. */ int mpl_get_row_kind(MPL *mpl, int i) { int kind; if (mpl->phase != 3) xfault("mpl_get_row_kind: invalid call sequence\n"); if (!(1 <= i && i <= mpl->m)) xfault("mpl_get_row_kind: i = %d; row number out of range\n", i); switch (mpl->row[i]->con->type) { case A_CONSTRAINT: kind = MPL_ST; break; case A_MINIMIZE: kind = MPL_MIN; break; case A_MAXIMIZE: kind = MPL_MAX; break; default: xassert(mpl != mpl); } return kind; } /*---------------------------------------------------------------------- -- mpl_get_row_bnds - obtain row bounds. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_get_row_bnds(MPL *mpl, int i, double *lb, double *ub); -- -- *Description* -- -- The routine mpl_get_row_bnds stores lower and upper bounds of i-th -- row of the problem to the locations, which the parameters lb and ub -- point to, respectively. Besides the routine returns the type of the -- i-th row. -- -- If some of the parameters lb and ub is NULL, the corresponding bound -- value is not stored. -- -- Types and bounds have the following meaning: -- -- Type Bounds Note -- ----------------------------------------------------------- -- MPL_FR -inf < f(x) < +inf Free linear form -- MPL_LO lb <= f(x) < +inf Inequality f(x) >= lb -- MPL_UP -inf < f(x) <= ub Inequality f(x) <= ub -- MPL_DB lb <= f(x) <= ub Inequality lb <= f(x) <= ub -- MPL_FX f(x) = lb Equality f(x) = lb -- -- where f(x) is the corresponding linear form of the i-th row. -- -- If the row has no lower bound, *lb is set to zero; if the row has -- no upper bound, *ub is set to zero; and if the row is of fixed type, -- both *lb and *ub are set to the same value. -- -- *Returns* -- -- The routine returns the type of the i-th row as it is stated in the -- table above. */ int mpl_get_row_bnds(MPL *mpl, int i, double *_lb, double *_ub) { ELEMCON *con; int type; double lb, ub; if (mpl->phase != 3) xfault("mpl_get_row_bnds: invalid call sequence\n"); if (!(1 <= i && i <= mpl->m)) xfault("mpl_get_row_bnds: i = %d; row number out of range\n", i); con = mpl->row[i]; #if 0 /* 21/VII-2006 */ if (con->con->lbnd == NULL && con->con->ubnd == NULL) type = MPL_FR, lb = ub = 0.0; else if (con->con->ubnd == NULL) type = MPL_LO, lb = con->lbnd, ub = 0.0; else if (con->con->lbnd == NULL) type = MPL_UP, lb = 0.0, ub = con->ubnd; else if (con->con->lbnd != con->con->ubnd) type = MPL_DB, lb = con->lbnd, ub = con->ubnd; else type = MPL_FX, lb = ub = con->lbnd; #else lb = (con->con->lbnd == NULL ? -DBL_MAX : con->lbnd); ub = (con->con->ubnd == NULL ? +DBL_MAX : con->ubnd); if (lb == -DBL_MAX && ub == +DBL_MAX) type = MPL_FR, lb = ub = 0.0; else if (ub == +DBL_MAX) type = MPL_LO, ub = 0.0; else if (lb == -DBL_MAX) type = MPL_UP, lb = 0.0; else if (con->con->lbnd != con->con->ubnd) type = MPL_DB; else type = MPL_FX; #endif if (_lb != NULL) *_lb = lb; if (_ub != NULL) *_ub = ub; return type; } /*---------------------------------------------------------------------- -- mpl_get_mat_row - obtain row of the constraint matrix. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_get_mat_row(MPL *mpl, int i, int ndx[], double val[]); -- -- *Description* -- -- The routine mpl_get_mat_row stores column indices and numeric values -- of constraint coefficients for the i-th row to locations ndx[1], ..., -- ndx[len] and val[1], ..., val[len], respectively, where 0 <= len <= n -- is number of (structural) non-zero constraint coefficients, and n is -- number of columns in the problem. -- -- If the parameter ndx is NULL, column indices are not stored. If the -- parameter val is NULL, numeric values are not stored. -- -- Note that free rows may have constant terms, which are not part of -- the constraint matrix and therefore not reported by this routine. The -- constant term of a particular row can be obtained, if necessary, via -- the routine mpl_get_row_c0. -- -- *Returns* -- -- The routine mpl_get_mat_row returns len, which is length of i-th row -- of the constraint matrix (i.e. number of non-zero coefficients). */ int mpl_get_mat_row(MPL *mpl, int i, int ndx[], double val[]) { FORMULA *term; int len = 0; if (mpl->phase != 3) xfault("mpl_get_mat_row: invalid call sequence\n"); if (!(1 <= i && i <= mpl->m)) xfault("mpl_get_mat_row: i = %d; row number out of range\n", i); for (term = mpl->row[i]->form; term != NULL; term = term->next) { xassert(term->var != NULL); len++; xassert(len <= mpl->n); if (ndx != NULL) ndx[len] = term->var->j; if (val != NULL) val[len] = term->coef; } return len; } /*---------------------------------------------------------------------- -- mpl_get_row_c0 - obtain constant term of free row. -- -- *Synopsis* -- -- #include "glpmpl.h" -- double mpl_get_row_c0(MPL *mpl, int i); -- -- *Returns* -- -- The routine mpl_get_row_c0 returns numeric value of constant term of -- i-th row. -- -- Note that only free rows may have non-zero constant terms. Therefore -- if i-th row is not free, the routine returns zero. */ double mpl_get_row_c0(MPL *mpl, int i) { ELEMCON *con; double c0; if (mpl->phase != 3) xfault("mpl_get_row_c0: invalid call sequence\n"); if (!(1 <= i && i <= mpl->m)) xfault("mpl_get_row_c0: i = %d; row number out of range\n", i); con = mpl->row[i]; if (con->con->lbnd == NULL && con->con->ubnd == NULL) c0 = - con->lbnd; else c0 = 0.0; return c0; } /*---------------------------------------------------------------------- -- mpl_get_col_name - obtain column name. -- -- *Synopsis* -- -- #include "glpmpl.h" -- char *mpl_get_col_name(MPL *mpl, int j); -- -- *Returns* -- -- The routine mpl_get_col_name returns a pointer to internal buffer, -- which contains symbolic name of j-th column of the problem. */ char *mpl_get_col_name(MPL *mpl, int j) { char *name = mpl->mpl_buf, *t; int len; if (mpl->phase != 3) xfault("mpl_get_col_name: invalid call sequence\n"); if (!(1 <= j && j <= mpl->n)) xfault("mpl_get_col_name: j = %d; column number out of range\n" , j); strcpy(name, mpl->col[j]->var->name); len = strlen(name); xassert(len <= 255); t = format_tuple(mpl, '[', mpl->col[j]->memb->tuple); while (*t) { if (len == 255) break; name[len++] = *t++; } name[len] = '\0'; if (len == 255) strcpy(name+252, "..."); xassert(strlen(name) <= 255); return name; } /*---------------------------------------------------------------------- -- mpl_get_col_kind - determine column kind. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_get_col_kind(MPL *mpl, int j); -- -- *Returns* -- -- The routine mpl_get_col_kind returns the kind of j-th column, which -- can be one of the following: -- -- MPL_NUM - continuous variable; -- MPL_INT - integer variable; -- MPL_BIN - binary variable. -- -- Note that column kinds are defined independently on type and bounds -- (reported by the routine mpl_get_col_bnds) of corresponding columns. -- This means, in particular, that bounds of an integer column may be -- fractional, or a binary column may have lower and upper bounds that -- are not 0 and 1 (or it may have no lower/upper bound at all). */ int mpl_get_col_kind(MPL *mpl, int j) { int kind; if (mpl->phase != 3) xfault("mpl_get_col_kind: invalid call sequence\n"); if (!(1 <= j && j <= mpl->n)) xfault("mpl_get_col_kind: j = %d; column number out of range\n" , j); switch (mpl->col[j]->var->type) { case A_NUMERIC: kind = MPL_NUM; break; case A_INTEGER: kind = MPL_INT; break; case A_BINARY: kind = MPL_BIN; break; default: xassert(mpl != mpl); } return kind; } /*---------------------------------------------------------------------- -- mpl_get_col_bnds - obtain column bounds. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_get_col_bnds(MPL *mpl, int j, double *lb, double *ub); -- -- *Description* -- -- The routine mpl_get_col_bnds stores lower and upper bound of j-th -- column of the problem to the locations, which the parameters lb and -- ub point to, respectively. Besides the routine returns the type of -- the j-th column. -- -- If some of the parameters lb and ub is NULL, the corresponding bound -- value is not stored. -- -- Types and bounds have the following meaning: -- -- Type Bounds Note -- ------------------------------------------------------ -- MPL_FR -inf < x < +inf Free (unbounded) variable -- MPL_LO lb <= x < +inf Variable with lower bound -- MPL_UP -inf < x <= ub Variable with upper bound -- MPL_DB lb <= x <= ub Double-bounded variable -- MPL_FX x = lb Fixed variable -- -- where x is individual variable corresponding to the j-th column. -- -- If the column has no lower bound, *lb is set to zero; if the column -- has no upper bound, *ub is set to zero; and if the column is of fixed -- type, both *lb and *ub are set to the same value. -- -- *Returns* -- -- The routine returns the type of the j-th column as it is stated in -- the table above. */ int mpl_get_col_bnds(MPL *mpl, int j, double *_lb, double *_ub) { ELEMVAR *var; int type; double lb, ub; if (mpl->phase != 3) xfault("mpl_get_col_bnds: invalid call sequence\n"); if (!(1 <= j && j <= mpl->n)) xfault("mpl_get_col_bnds: j = %d; column number out of range\n" , j); var = mpl->col[j]; #if 0 /* 21/VII-2006 */ if (var->var->lbnd == NULL && var->var->ubnd == NULL) type = MPL_FR, lb = ub = 0.0; else if (var->var->ubnd == NULL) type = MPL_LO, lb = var->lbnd, ub = 0.0; else if (var->var->lbnd == NULL) type = MPL_UP, lb = 0.0, ub = var->ubnd; else if (var->var->lbnd != var->var->ubnd) type = MPL_DB, lb = var->lbnd, ub = var->ubnd; else type = MPL_FX, lb = ub = var->lbnd; #else lb = (var->var->lbnd == NULL ? -DBL_MAX : var->lbnd); ub = (var->var->ubnd == NULL ? +DBL_MAX : var->ubnd); if (lb == -DBL_MAX && ub == +DBL_MAX) type = MPL_FR, lb = ub = 0.0; else if (ub == +DBL_MAX) type = MPL_LO, ub = 0.0; else if (lb == -DBL_MAX) type = MPL_UP, lb = 0.0; else if (var->var->lbnd != var->var->ubnd) type = MPL_DB; else type = MPL_FX; #endif if (_lb != NULL) *_lb = lb; if (_ub != NULL) *_ub = ub; return type; } /*---------------------------------------------------------------------- -- mpl_has_solve_stmt - check if model has solve statement. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_has_solve_stmt(MPL *mpl); -- -- *Returns* -- -- If the model has the solve statement, the routine returns non-zero, -- otherwise zero is returned. */ int mpl_has_solve_stmt(MPL *mpl) { if (mpl->phase != 3) xfault("mpl_has_solve_stmt: invalid call sequence\n"); return mpl->flag_s; } #if 1 /* 15/V-2010 */ void mpl_put_row_soln(MPL *mpl, int i, int stat, double prim, double dual) { /* store row (constraint/objective) solution components */ xassert(mpl->phase == 3); xassert(1 <= i && i <= mpl->m); mpl->row[i]->stat = stat; mpl->row[i]->prim = prim; mpl->row[i]->dual = dual; return; } #endif #if 1 /* 15/V-2010 */ void mpl_put_col_soln(MPL *mpl, int j, int stat, double prim, double dual) { /* store column (variable) solution components */ xassert(mpl->phase == 3); xassert(1 <= j && j <= mpl->n); mpl->col[j]->stat = stat; mpl->col[j]->prim = prim; mpl->col[j]->dual = dual; return; } #endif #if 0 /* 15/V-2010 */ /*---------------------------------------------------------------------- -- mpl_put_col_value - store column value. -- -- *Synopsis* -- -- #include "glpmpl.h" -- void mpl_put_col_value(MPL *mpl, int j, double val); -- -- *Description* -- -- The routine mpl_put_col_value stores numeric value of j-th column -- into the translator database. It is assumed that the column value is -- provided by the solver. */ void mpl_put_col_value(MPL *mpl, int j, double val) { if (mpl->phase != 3) xfault("mpl_put_col_value: invalid call sequence\n"); if (!(1 <= j && j <= mpl->n)) xfault( "mpl_put_col_value: j = %d; column number out of range\n", j); mpl->col[j]->prim = val; return; } #endif /*---------------------------------------------------------------------- -- mpl_postsolve - postsolve model. -- -- *Synopsis* -- -- #include "glpmpl.h" -- int mpl_postsolve(MPL *mpl); -- -- *Description* -- -- The routine mpl_postsolve performs postsolving of the model using -- its description stored in the translator database. This phase means -- executing statements, which follow the solve statement. -- -- If this routine is used, it should be called once after the routine -- mpl_generate and if the latter returned the code 3. -- -- *Returns* -- -- The routine mpl_postsolve returns one of the following codes: -- -- 3 - model has been successfully postsolved. -- 4 - processing failed due to some errors. In this case the calling -- program should call the routine mpl_terminate to terminate model -- processing. */ int mpl_postsolve(MPL *mpl) { if (!(mpl->phase == 3 && !mpl->flag_p)) xfault("mpl_postsolve: invalid call sequence\n"); /* set up error handler */ if (setjmp(mpl->jump)) goto done; /* perform postsolving */ postsolve_model(mpl); flush_output(mpl); /* postsolving phase has been finished */ xprintf("Model has been successfully processed\n"); done: /* return to the calling program */ return mpl->phase; } /*---------------------------------------------------------------------- -- mpl_terminate - free all resources used by translator. -- -- *Synopsis* -- -- #include "glpmpl.h" -- void mpl_terminate(MPL *mpl); -- -- *Description* -- -- The routine mpl_terminate frees all the resources used by the GNU -- MathProg translator. */ void mpl_terminate(MPL *mpl) { if (setjmp(mpl->jump)) xassert(mpl != mpl); switch (mpl->phase) { case 0: case 1: case 2: case 3: /* there were no errors; clean the model content */ clean_model(mpl); xassert(mpl->a_list == NULL); #if 1 /* 11/II-2008 */ xassert(mpl->dca == NULL); #endif break; case 4: /* model processing has been finished due to error; delete search trees, which may be created for some arrays */ { ARRAY *a; for (a = mpl->a_list; a != NULL; a = a->next) if (a->tree != NULL) avl_delete_tree(a->tree); } #if 1 /* 11/II-2008 */ free_dca(mpl); #endif break; default: xassert(mpl != mpl); } /* delete the translator database */ xfree(mpl->image); xfree(mpl->b_image); xfree(mpl->f_image); xfree(mpl->context); dmp_delete_pool(mpl->pool); avl_delete_tree(mpl->tree); dmp_delete_pool(mpl->strings); dmp_delete_pool(mpl->symbols); dmp_delete_pool(mpl->tuples); dmp_delete_pool(mpl->arrays); dmp_delete_pool(mpl->members); dmp_delete_pool(mpl->elemvars); dmp_delete_pool(mpl->formulae); dmp_delete_pool(mpl->elemcons); xfree(mpl->sym_buf); xfree(mpl->tup_buf); rng_delete_rand(mpl->rand); if (mpl->row != NULL) xfree(mpl->row); if (mpl->col != NULL) xfree(mpl->col); if (mpl->in_fp != NULL) xfclose(mpl->in_fp); if (mpl->out_fp != NULL && mpl->out_fp != (void *)stdout) xfclose(mpl->out_fp); if (mpl->out_file != NULL) xfree(mpl->out_file); if (mpl->prt_fp != NULL) xfclose(mpl->prt_fp); if (mpl->prt_file != NULL) xfree(mpl->prt_file); if (mpl->mod_file != NULL) xfree(mpl->mod_file); xfree(mpl->mpl_buf); xfree(mpl); return; } /* eof */ sources_5316/external/glpk/Makefile0000644000176700017670000000304011630501213016127 0ustar paulpaul# Makefile for library "num/glpk" # Paul Boersma, 3 September 2011 include ../../makefile.defs OBJECTS = amd_1.o amd_2.o amd_aat.o amd_control.o amd_defaults.o amd_info.o \ amd_order.o amd_post_tree.o amd_postorder.o amd_preprocess.o amd_valid.o \ colamd.o \ glpapi01.o glpapi02.o glpapi03.o glpapi04.o glpapi05.o glpapi06.o glpapi07.o \ glpapi08.o glpapi09.o glpapi10.o glpapi11.o glpapi12.o glpapi13.o glpapi14.o \ glpapi15.o glpapi16.o glpapi17.o glpapi18.o glpapi19.o \ glpavl.o glpbfd.o glpbfx.o glpcpx.o glpdmp.o glpdmx.o \ glpenv01.o glpenv02.o glpenv03.o glpenv04.o \ glpenv05.o glpenv06.o glpenv07.o glpenv08.o \ glpfhv.o glpgmp.o glphbm.o glpini01.o glpini02.o \ glpios01.o glpios02.o glpios03.o glpios04.o glpios05.o glpios06.o \ glpios07.o glpios08.o glpios09.o glpios10.o glpios11.o glpios12.o \ glpipm.o glplib01.o glplib02.o glplib03.o glplpf.o \ glplpx01.o glplpx02.o glplpx03.o \ glpluf.o glplux.o glpmat.o \ glpmpl01.o glpmpl02.o glpmpl03.o glpmpl04.o glpmpl05.o glpmpl06.o glpmps.o \ glpnet01.o glpnet02.o glpnet03.o glpnet04.o glpnet05.o \ glpnet06.o glpnet07.o glpnet08.o glpnet09.o \ glpnpp01.o glpnpp02.o glpnpp03.o glpnpp04.o glpnpp05.o \ glpqmd.o glprgr.o glprng01.o glprng02.o \ glpscf.o glpscl.o glpsdf.o glpspm.o glpspx01.o glpspx02.o \ glpsql.o glpssx01.o glpssx02.o glptsp.o .PHONY: all clean all: libglpk.a clean: $(RM) $(OBJECTS) $(RM) libglpk.a libglpk.a: $(OBJECTS) touch libglpk.a rm libglpk.a ar cq libglpk.a $(OBJECTS) $(RANLIB) libglpk.a $(OBJECTS): *.h sources_5316/external/glpk/glplux.c0000644000176700017670000011400011401660400016145 0ustar paulpaul/* glplux.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glplux.h" #define xfault xerror #define dmp_create_poolx(size) dmp_create_pool() /*---------------------------------------------------------------------- // lux_create - create LU-factorization. // // SYNOPSIS // // #include "glplux.h" // LUX *lux_create(int n); // // DESCRIPTION // // The routine lux_create creates LU-factorization data structure for // a matrix of the order n. Initially the factorization corresponds to // the unity matrix (F = V = P = Q = I, so A = I). // // RETURNS // // The routine returns a pointer to the created LU-factorization data // structure, which represents the unity matrix of the order n. */ LUX *lux_create(int n) { LUX *lux; int k; if (n < 1) xfault("lux_create: n = %d; invalid parameter\n", n); lux = xmalloc(sizeof(LUX)); lux->n = n; lux->pool = dmp_create_poolx(sizeof(LUXELM)); lux->F_row = xcalloc(1+n, sizeof(LUXELM *)); lux->F_col = xcalloc(1+n, sizeof(LUXELM *)); lux->V_piv = xcalloc(1+n, sizeof(mpq_t)); lux->V_row = xcalloc(1+n, sizeof(LUXELM *)); lux->V_col = xcalloc(1+n, sizeof(LUXELM *)); lux->P_row = xcalloc(1+n, sizeof(int)); lux->P_col = xcalloc(1+n, sizeof(int)); lux->Q_row = xcalloc(1+n, sizeof(int)); lux->Q_col = xcalloc(1+n, sizeof(int)); for (k = 1; k <= n; k++) { lux->F_row[k] = lux->F_col[k] = NULL; mpq_init(lux->V_piv[k]); mpq_set_si(lux->V_piv[k], 1, 1); lux->V_row[k] = lux->V_col[k] = NULL; lux->P_row[k] = lux->P_col[k] = k; lux->Q_row[k] = lux->Q_col[k] = k; } lux->rank = n; return lux; } /*---------------------------------------------------------------------- // initialize - initialize LU-factorization data structures. // // This routine initializes data structures for subsequent computing // the LU-factorization of a given matrix A, which is specified by the // formal routine col. On exit V = A and F = P = Q = I, where I is the // unity matrix. */ static void initialize(LUX *lux, int (*col)(void *info, int j, int ind[], mpq_t val[]), void *info, LUXWKA *wka) { int n = lux->n; DMP *pool = lux->pool; LUXELM **F_row = lux->F_row; LUXELM **F_col = lux->F_col; mpq_t *V_piv = lux->V_piv; LUXELM **V_row = lux->V_row; LUXELM **V_col = lux->V_col; int *P_row = lux->P_row; int *P_col = lux->P_col; int *Q_row = lux->Q_row; int *Q_col = lux->Q_col; int *R_len = wka->R_len; int *R_head = wka->R_head; int *R_prev = wka->R_prev; int *R_next = wka->R_next; int *C_len = wka->C_len; int *C_head = wka->C_head; int *C_prev = wka->C_prev; int *C_next = wka->C_next; LUXELM *fij, *vij; int i, j, k, len, *ind; mpq_t *val; /* F := I */ for (i = 1; i <= n; i++) { while (F_row[i] != NULL) { fij = F_row[i], F_row[i] = fij->r_next; mpq_clear(fij->val); dmp_free_atom(pool, fij, sizeof(LUXELM)); } } for (j = 1; j <= n; j++) F_col[j] = NULL; /* V := 0 */ for (k = 1; k <= n; k++) mpq_set_si(V_piv[k], 0, 1); for (i = 1; i <= n; i++) { while (V_row[i] != NULL) { vij = V_row[i], V_row[i] = vij->r_next; mpq_clear(vij->val); dmp_free_atom(pool, vij, sizeof(LUXELM)); } } for (j = 1; j <= n; j++) V_col[j] = NULL; /* V := A */ ind = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(mpq_t)); for (k = 1; k <= n; k++) mpq_init(val[k]); for (j = 1; j <= n; j++) { /* obtain j-th column of matrix A */ len = col(info, j, ind, val); if (!(0 <= len && len <= n)) xfault("lux_decomp: j = %d: len = %d; invalid column length" "\n", j, len); /* copy elements of j-th column to matrix V */ for (k = 1; k <= len; k++) { /* get row index of a[i,j] */ i = ind[k]; if (!(1 <= i && i <= n)) xfault("lux_decomp: j = %d: i = %d; row index out of ran" "ge\n", j, i); /* check for duplicate indices */ if (V_row[i] != NULL && V_row[i]->j == j) xfault("lux_decomp: j = %d: i = %d; duplicate row indice" "s not allowed\n", j, i); /* check for zero value */ if (mpq_sgn(val[k]) == 0) xfault("lux_decomp: j = %d: i = %d; zero elements not al" "lowed\n", j, i); /* add new element v[i,j] = a[i,j] to V */ vij = dmp_get_atom(pool, sizeof(LUXELM)); vij->i = i, vij->j = j; mpq_init(vij->val); mpq_set(vij->val, val[k]); vij->r_prev = NULL; vij->r_next = V_row[i]; vij->c_prev = NULL; vij->c_next = V_col[j]; if (vij->r_next != NULL) vij->r_next->r_prev = vij; if (vij->c_next != NULL) vij->c_next->c_prev = vij; V_row[i] = V_col[j] = vij; } } xfree(ind); for (k = 1; k <= n; k++) mpq_clear(val[k]); xfree(val); /* P := Q := I */ for (k = 1; k <= n; k++) P_row[k] = P_col[k] = Q_row[k] = Q_col[k] = k; /* the rank of A and V is not determined yet */ lux->rank = -1; /* initially the entire matrix V is active */ /* determine its row lengths */ for (i = 1; i <= n; i++) { len = 0; for (vij = V_row[i]; vij != NULL; vij = vij->r_next) len++; R_len[i] = len; } /* build linked lists of active rows */ for (len = 0; len <= n; len++) R_head[len] = 0; for (i = 1; i <= n; i++) { len = R_len[i]; R_prev[i] = 0; R_next[i] = R_head[len]; if (R_next[i] != 0) R_prev[R_next[i]] = i; R_head[len] = i; } /* determine its column lengths */ for (j = 1; j <= n; j++) { len = 0; for (vij = V_col[j]; vij != NULL; vij = vij->c_next) len++; C_len[j] = len; } /* build linked lists of active columns */ for (len = 0; len <= n; len++) C_head[len] = 0; for (j = 1; j <= n; j++) { len = C_len[j]; C_prev[j] = 0; C_next[j] = C_head[len]; if (C_next[j] != 0) C_prev[C_next[j]] = j; C_head[len] = j; } return; } /*---------------------------------------------------------------------- // find_pivot - choose a pivot element. // // This routine chooses a pivot element v[p,q] in the active submatrix // of matrix U = P*V*Q. // // It is assumed that on entry the matrix U has the following partially // triangularized form: // // 1 k n // 1 x x x x x x x x x x // . x x x x x x x x x // . . x x x x x x x x // . . . x x x x x x x // k . . . . * * * * * * // . . . . * * * * * * // . . . . * * * * * * // . . . . * * * * * * // . . . . * * * * * * // n . . . . * * * * * * // // where rows and columns k, k+1, ..., n belong to the active submatrix // (elements of the active submatrix are marked by '*'). // // Since the matrix U = P*V*Q is not stored, the routine works with the // matrix V. It is assumed that the row-wise representation corresponds // to the matrix V, but the column-wise representation corresponds to // the active submatrix of the matrix V, i.e. elements of the matrix V, // which does not belong to the active submatrix, are missing from the // column linked lists. It is also assumed that each active row of the // matrix V is in the set R[len], where len is number of non-zeros in // the row, and each active column of the matrix V is in the set C[len], // where len is number of non-zeros in the column (in the latter case // only elements of the active submatrix are counted; such elements are // marked by '*' on the figure above). // // Due to exact arithmetic any non-zero element of the active submatrix // can be chosen as a pivot. However, to keep sparsity of the matrix V // the routine uses Markowitz strategy, trying to choose such element // v[p,q], which has smallest Markowitz cost (nr[p]-1) * (nc[q]-1), // where nr[p] and nc[q] are the number of non-zero elements, resp., in // p-th row and in q-th column of the active submatrix. // // In order to reduce the search, i.e. not to walk through all elements // of the active submatrix, the routine exploits a technique proposed by // I.Duff. This technique is based on using the sets R[len] and C[len] // of active rows and columns. // // On exit the routine returns a pointer to a pivot v[p,q] chosen, or // NULL, if the active submatrix is empty. */ static LUXELM *find_pivot(LUX *lux, LUXWKA *wka) { int n = lux->n; LUXELM **V_row = lux->V_row; LUXELM **V_col = lux->V_col; int *R_len = wka->R_len; int *R_head = wka->R_head; int *R_next = wka->R_next; int *C_len = wka->C_len; int *C_head = wka->C_head; int *C_next = wka->C_next; LUXELM *piv, *some, *vij; int i, j, len, min_len, ncand, piv_lim = 5; double best, cost; /* nothing is chosen so far */ piv = NULL, best = DBL_MAX, ncand = 0; /* if in the active submatrix there is a column that has the only non-zero (column singleton), choose it as a pivot */ j = C_head[1]; if (j != 0) { xassert(C_len[j] == 1); piv = V_col[j]; xassert(piv != NULL && piv->c_next == NULL); goto done; } /* if in the active submatrix there is a row that has the only non-zero (row singleton), choose it as a pivot */ i = R_head[1]; if (i != 0) { xassert(R_len[i] == 1); piv = V_row[i]; xassert(piv != NULL && piv->r_next == NULL); goto done; } /* there are no singletons in the active submatrix; walk through other non-empty rows and columns */ for (len = 2; len <= n; len++) { /* consider active columns having len non-zeros */ for (j = C_head[len]; j != 0; j = C_next[j]) { /* j-th column has len non-zeros */ /* find an element in the row of minimal length */ some = NULL, min_len = INT_MAX; for (vij = V_col[j]; vij != NULL; vij = vij->c_next) { if (min_len > R_len[vij->i]) some = vij, min_len = R_len[vij->i]; /* if Markowitz cost of this element is not greater than (len-1)**2, it can be chosen right now; this heuristic reduces the search and works well in many cases */ if (min_len <= len) { piv = some; goto done; } } /* j-th column has been scanned */ /* the minimal element found is a next pivot candidate */ xassert(some != NULL); ncand++; /* compute its Markowitz cost */ cost = (double)(min_len - 1) * (double)(len - 1); /* choose between the current candidate and this element */ if (cost < best) piv = some, best = cost; /* if piv_lim candidates have been considered, there is a doubt that a much better candidate exists; therefore it is the time to terminate the search */ if (ncand == piv_lim) goto done; } /* now consider active rows having len non-zeros */ for (i = R_head[len]; i != 0; i = R_next[i]) { /* i-th row has len non-zeros */ /* find an element in the column of minimal length */ some = NULL, min_len = INT_MAX; for (vij = V_row[i]; vij != NULL; vij = vij->r_next) { if (min_len > C_len[vij->j]) some = vij, min_len = C_len[vij->j]; /* if Markowitz cost of this element is not greater than (len-1)**2, it can be chosen right now; this heuristic reduces the search and works well in many cases */ if (min_len <= len) { piv = some; goto done; } } /* i-th row has been scanned */ /* the minimal element found is a next pivot candidate */ xassert(some != NULL); ncand++; /* compute its Markowitz cost */ cost = (double)(len - 1) * (double)(min_len - 1); /* choose between the current candidate and this element */ if (cost < best) piv = some, best = cost; /* if piv_lim candidates have been considered, there is a doubt that a much better candidate exists; therefore it is the time to terminate the search */ if (ncand == piv_lim) goto done; } } done: /* bring the pivot v[p,q] to the factorizing routine */ return piv; } /*---------------------------------------------------------------------- // eliminate - perform gaussian elimination. // // This routine performs elementary gaussian transformations in order // to eliminate subdiagonal elements in the k-th column of the matrix // U = P*V*Q using the pivot element u[k,k], where k is the number of // the current elimination step. // // The parameter piv specifies the pivot element v[p,q] = u[k,k]. // // Each time when the routine applies the elementary transformation to // a non-pivot row of the matrix V, it stores the corresponding element // to the matrix F in order to keep the main equality A = F*V. // // The routine assumes that on entry the matrices L = P*F*inv(P) and // U = P*V*Q are the following: // // 1 k 1 k n // 1 1 . . . . . . . . . 1 x x x x x x x x x x // x 1 . . . . . . . . . x x x x x x x x x // x x 1 . . . . . . . . . x x x x x x x x // x x x 1 . . . . . . . . . x x x x x x x // k x x x x 1 . . . . . k . . . . * * * * * * // x x x x _ 1 . . . . . . . . # * * * * * // x x x x _ . 1 . . . . . . . # * * * * * // x x x x _ . . 1 . . . . . . # * * * * * // x x x x _ . . . 1 . . . . . # * * * * * // n x x x x _ . . . . 1 n . . . . # * * * * * // // matrix L matrix U // // where rows and columns of the matrix U with numbers k, k+1, ..., n // form the active submatrix (eliminated elements are marked by '#' and // other elements of the active submatrix are marked by '*'). Note that // each eliminated non-zero element u[i,k] of the matrix U gives the // corresponding element l[i,k] of the matrix L (marked by '_'). // // Actually all operations are performed on the matrix V. Should note // that the row-wise representation corresponds to the matrix V, but the // column-wise representation corresponds to the active submatrix of the // matrix V, i.e. elements of the matrix V, which doesn't belong to the // active submatrix, are missing from the column linked lists. // // Let u[k,k] = v[p,q] be the pivot. In order to eliminate subdiagonal // elements u[i',k] = v[i,q], i' = k+1, k+2, ..., n, the routine applies // the following elementary gaussian transformations: // // (i-th row of V) := (i-th row of V) - f[i,p] * (p-th row of V), // // where f[i,p] = v[i,q] / v[p,q] is a gaussian multiplier. // // Additionally, in order to keep the main equality A = F*V, each time // when the routine applies the transformation to i-th row of the matrix // V, it also adds f[i,p] as a new element to the matrix F. // // IMPORTANT: On entry the working arrays flag and work should contain // zeros. This status is provided by the routine on exit. */ static void eliminate(LUX *lux, LUXWKA *wka, LUXELM *piv, int flag[], mpq_t work[]) { DMP *pool = lux->pool; LUXELM **F_row = lux->F_row; LUXELM **F_col = lux->F_col; mpq_t *V_piv = lux->V_piv; LUXELM **V_row = lux->V_row; LUXELM **V_col = lux->V_col; int *R_len = wka->R_len; int *R_head = wka->R_head; int *R_prev = wka->R_prev; int *R_next = wka->R_next; int *C_len = wka->C_len; int *C_head = wka->C_head; int *C_prev = wka->C_prev; int *C_next = wka->C_next; LUXELM *fip, *vij, *vpj, *viq, *next; mpq_t temp; int i, j, p, q; mpq_init(temp); /* determine row and column indices of the pivot v[p,q] */ xassert(piv != NULL); p = piv->i, q = piv->j; /* remove p-th (pivot) row from the active set; it will never return there */ if (R_prev[p] == 0) R_head[R_len[p]] = R_next[p]; else R_next[R_prev[p]] = R_next[p]; if (R_next[p] == 0) ; else R_prev[R_next[p]] = R_prev[p]; /* remove q-th (pivot) column from the active set; it will never return there */ if (C_prev[q] == 0) C_head[C_len[q]] = C_next[q]; else C_next[C_prev[q]] = C_next[q]; if (C_next[q] == 0) ; else C_prev[C_next[q]] = C_prev[q]; /* store the pivot value in a separate array */ mpq_set(V_piv[p], piv->val); /* remove the pivot from p-th row */ if (piv->r_prev == NULL) V_row[p] = piv->r_next; else piv->r_prev->r_next = piv->r_next; if (piv->r_next == NULL) ; else piv->r_next->r_prev = piv->r_prev; R_len[p]--; /* remove the pivot from q-th column */ if (piv->c_prev == NULL) V_col[q] = piv->c_next; else piv->c_prev->c_next = piv->c_next; if (piv->c_next == NULL) ; else piv->c_next->c_prev = piv->c_prev; C_len[q]--; /* free the space occupied by the pivot */ mpq_clear(piv->val); dmp_free_atom(pool, piv, sizeof(LUXELM)); /* walk through p-th (pivot) row, which already does not contain the pivot v[p,q], and do the following... */ for (vpj = V_row[p]; vpj != NULL; vpj = vpj->r_next) { /* get column index of v[p,j] */ j = vpj->j; /* store v[p,j] in the working array */ flag[j] = 1; mpq_set(work[j], vpj->val); /* remove j-th column from the active set; it will return there later with a new length */ if (C_prev[j] == 0) C_head[C_len[j]] = C_next[j]; else C_next[C_prev[j]] = C_next[j]; if (C_next[j] == 0) ; else C_prev[C_next[j]] = C_prev[j]; /* v[p,j] leaves the active submatrix, so remove it from j-th column; however, v[p,j] is kept in p-th row */ if (vpj->c_prev == NULL) V_col[j] = vpj->c_next; else vpj->c_prev->c_next = vpj->c_next; if (vpj->c_next == NULL) ; else vpj->c_next->c_prev = vpj->c_prev; C_len[j]--; } /* now walk through q-th (pivot) column, which already does not contain the pivot v[p,q], and perform gaussian elimination */ while (V_col[q] != NULL) { /* element v[i,q] has to be eliminated */ viq = V_col[q]; /* get row index of v[i,q] */ i = viq->i; /* remove i-th row from the active set; later it will return there with a new length */ if (R_prev[i] == 0) R_head[R_len[i]] = R_next[i]; else R_next[R_prev[i]] = R_next[i]; if (R_next[i] == 0) ; else R_prev[R_next[i]] = R_prev[i]; /* compute gaussian multiplier f[i,p] = v[i,q] / v[p,q] and store it in the matrix F */ fip = dmp_get_atom(pool, sizeof(LUXELM)); fip->i = i, fip->j = p; mpq_init(fip->val); mpq_div(fip->val, viq->val, V_piv[p]); fip->r_prev = NULL; fip->r_next = F_row[i]; fip->c_prev = NULL; fip->c_next = F_col[p]; if (fip->r_next != NULL) fip->r_next->r_prev = fip; if (fip->c_next != NULL) fip->c_next->c_prev = fip; F_row[i] = F_col[p] = fip; /* v[i,q] has to be eliminated, so remove it from i-th row */ if (viq->r_prev == NULL) V_row[i] = viq->r_next; else viq->r_prev->r_next = viq->r_next; if (viq->r_next == NULL) ; else viq->r_next->r_prev = viq->r_prev; R_len[i]--; /* and also from q-th column */ V_col[q] = viq->c_next; C_len[q]--; /* free the space occupied by v[i,q] */ mpq_clear(viq->val); dmp_free_atom(pool, viq, sizeof(LUXELM)); /* perform gaussian transformation: (i-th row) := (i-th row) - f[i,p] * (p-th row) note that now p-th row, which is in the working array, does not contain the pivot v[p,q], and i-th row does not contain the element v[i,q] to be eliminated */ /* walk through i-th row and transform existing non-zero elements */ for (vij = V_row[i]; vij != NULL; vij = next) { next = vij->r_next; /* get column index of v[i,j] */ j = vij->j; /* v[i,j] := v[i,j] - f[i,p] * v[p,j] */ if (flag[j]) { /* v[p,j] != 0 */ flag[j] = 0; mpq_mul(temp, fip->val, work[j]); mpq_sub(vij->val, vij->val, temp); if (mpq_sgn(vij->val) == 0) { /* new v[i,j] is zero, so remove it from the active submatrix */ /* remove v[i,j] from i-th row */ if (vij->r_prev == NULL) V_row[i] = vij->r_next; else vij->r_prev->r_next = vij->r_next; if (vij->r_next == NULL) ; else vij->r_next->r_prev = vij->r_prev; R_len[i]--; /* remove v[i,j] from j-th column */ if (vij->c_prev == NULL) V_col[j] = vij->c_next; else vij->c_prev->c_next = vij->c_next; if (vij->c_next == NULL) ; else vij->c_next->c_prev = vij->c_prev; C_len[j]--; /* free the space occupied by v[i,j] */ mpq_clear(vij->val); dmp_free_atom(pool, vij, sizeof(LUXELM)); } } } /* now flag is the pattern of the set v[p,*] \ v[i,*] */ /* walk through p-th (pivot) row and create new elements in i-th row, which appear due to fill-in */ for (vpj = V_row[p]; vpj != NULL; vpj = vpj->r_next) { j = vpj->j; if (flag[j]) { /* create new non-zero v[i,j] = 0 - f[i,p] * v[p,j] and add it to i-th row and j-th column */ vij = dmp_get_atom(pool, sizeof(LUXELM)); vij->i = i, vij->j = j; mpq_init(vij->val); mpq_mul(vij->val, fip->val, work[j]); mpq_neg(vij->val, vij->val); vij->r_prev = NULL; vij->r_next = V_row[i]; vij->c_prev = NULL; vij->c_next = V_col[j]; if (vij->r_next != NULL) vij->r_next->r_prev = vij; if (vij->c_next != NULL) vij->c_next->c_prev = vij; V_row[i] = V_col[j] = vij; R_len[i]++, C_len[j]++; } else { /* there is no fill-in, because v[i,j] already exists in i-th row; restore the flag, which was reset before */ flag[j] = 1; } } /* now i-th row has been completely transformed and can return to the active set with a new length */ R_prev[i] = 0; R_next[i] = R_head[R_len[i]]; if (R_next[i] != 0) R_prev[R_next[i]] = i; R_head[R_len[i]] = i; } /* at this point q-th (pivot) column must be empty */ xassert(C_len[q] == 0); /* walk through p-th (pivot) row again and do the following... */ for (vpj = V_row[p]; vpj != NULL; vpj = vpj->r_next) { /* get column index of v[p,j] */ j = vpj->j; /* erase v[p,j] from the working array */ flag[j] = 0; mpq_set_si(work[j], 0, 1); /* now j-th column has been completely transformed, so it can return to the active list with a new length */ C_prev[j] = 0; C_next[j] = C_head[C_len[j]]; if (C_next[j] != 0) C_prev[C_next[j]] = j; C_head[C_len[j]] = j; } mpq_clear(temp); /* return to the factorizing routine */ return; } /*---------------------------------------------------------------------- // lux_decomp - compute LU-factorization. // // SYNOPSIS // // #include "glplux.h" // int lux_decomp(LUX *lux, int (*col)(void *info, int j, int ind[], // mpq_t val[]), void *info); // // DESCRIPTION // // The routine lux_decomp computes LU-factorization of a given square // matrix A. // // The parameter lux specifies LU-factorization data structure built by // means of the routine lux_create. // // The formal routine col specifies the original matrix A. In order to // obtain j-th column of the matrix A the routine lux_decomp calls the // routine col with the parameter j (1 <= j <= n, where n is the order // of A). In response the routine col should store row indices and // numerical values of non-zero elements of j-th column of A to the // locations ind[1], ..., ind[len] and val[1], ..., val[len], resp., // where len is the number of non-zeros in j-th column, which should be // returned on exit. Neiter zero nor duplicate elements are allowed. // // The parameter info is a transit pointer passed to the formal routine // col; it can be used for various purposes. // // RETURNS // // The routine lux_decomp returns the singularity flag. Zero flag means // that the original matrix A is non-singular while non-zero flag means // that A is (exactly!) singular. // // Note that LU-factorization is valid in both cases, however, in case // of singularity some rows of the matrix V (including pivot elements) // will be empty. // // REPAIRING SINGULAR MATRIX // // If the routine lux_decomp returns non-zero flag, it provides all // necessary information that can be used for "repairing" the matrix A, // where "repairing" means replacing linearly dependent columns of the // matrix A by appropriate columns of the unity matrix. This feature is // needed when the routine lux_decomp is used for reinverting the basis // matrix within the simplex method procedure. // // On exit linearly dependent columns of the matrix U have the numbers // rank+1, rank+2, ..., n, where rank is the exact rank of the matrix A // stored by the routine to the member lux->rank. The correspondence // between columns of A and U is the same as between columns of V and U. // Thus, linearly dependent columns of the matrix A have the numbers // Q_col[rank+1], Q_col[rank+2], ..., Q_col[n], where Q_col is an array // representing the permutation matrix Q in column-like format. It is // understood that each j-th linearly dependent column of the matrix U // should be replaced by the unity vector, where all elements are zero // except the unity diagonal element u[j,j]. On the other hand j-th row // of the matrix U corresponds to the row of the matrix V (and therefore // of the matrix A) with the number P_row[j], where P_row is an array // representing the permutation matrix P in row-like format. Thus, each // j-th linearly dependent column of the matrix U should be replaced by // a column of the unity matrix with the number P_row[j]. // // The code that repairs the matrix A may look like follows: // // for (j = rank+1; j <= n; j++) // { replace column Q_col[j] of the matrix A by column P_row[j] of // the unity matrix; // } // // where rank, P_row, and Q_col are members of the structure LUX. */ int lux_decomp(LUX *lux, int (*col)(void *info, int j, int ind[], mpq_t val[]), void *info) { int n = lux->n; LUXELM **V_row = lux->V_row; LUXELM **V_col = lux->V_col; int *P_row = lux->P_row; int *P_col = lux->P_col; int *Q_row = lux->Q_row; int *Q_col = lux->Q_col; LUXELM *piv, *vij; LUXWKA *wka; int i, j, k, p, q, t, *flag; mpq_t *work; /* allocate working area */ wka = xmalloc(sizeof(LUXWKA)); wka->R_len = xcalloc(1+n, sizeof(int)); wka->R_head = xcalloc(1+n, sizeof(int)); wka->R_prev = xcalloc(1+n, sizeof(int)); wka->R_next = xcalloc(1+n, sizeof(int)); wka->C_len = xcalloc(1+n, sizeof(int)); wka->C_head = xcalloc(1+n, sizeof(int)); wka->C_prev = xcalloc(1+n, sizeof(int)); wka->C_next = xcalloc(1+n, sizeof(int)); /* initialize LU-factorization data structures */ initialize(lux, col, info, wka); /* allocate working arrays */ flag = xcalloc(1+n, sizeof(int)); work = xcalloc(1+n, sizeof(mpq_t)); for (k = 1; k <= n; k++) { flag[k] = 0; mpq_init(work[k]); } /* main elimination loop */ for (k = 1; k <= n; k++) { /* choose a pivot element v[p,q] */ piv = find_pivot(lux, wka); if (piv == NULL) { /* no pivot can be chosen, because the active submatrix is empty */ break; } /* determine row and column indices of the pivot element */ p = piv->i, q = piv->j; /* let v[p,q] correspond to u[i',j']; permute k-th and i'-th rows and k-th and j'-th columns of the matrix U = P*V*Q to move the element u[i',j'] to the position u[k,k] */ i = P_col[p], j = Q_row[q]; xassert(k <= i && i <= n && k <= j && j <= n); /* permute k-th and i-th rows of the matrix U */ t = P_row[k]; P_row[i] = t, P_col[t] = i; P_row[k] = p, P_col[p] = k; /* permute k-th and j-th columns of the matrix U */ t = Q_col[k]; Q_col[j] = t, Q_row[t] = j; Q_col[k] = q, Q_row[q] = k; /* eliminate subdiagonal elements of k-th column of the matrix U = P*V*Q using the pivot element u[k,k] = v[p,q] */ eliminate(lux, wka, piv, flag, work); } /* determine the rank of A (and V) */ lux->rank = k - 1; /* free working arrays */ xfree(flag); for (k = 1; k <= n; k++) mpq_clear(work[k]); xfree(work); /* build column lists of the matrix V using its row lists */ for (j = 1; j <= n; j++) xassert(V_col[j] == NULL); for (i = 1; i <= n; i++) { for (vij = V_row[i]; vij != NULL; vij = vij->r_next) { j = vij->j; vij->c_prev = NULL; vij->c_next = V_col[j]; if (vij->c_next != NULL) vij->c_next->c_prev = vij; V_col[j] = vij; } } /* free working area */ xfree(wka->R_len); xfree(wka->R_head); xfree(wka->R_prev); xfree(wka->R_next); xfree(wka->C_len); xfree(wka->C_head); xfree(wka->C_prev); xfree(wka->C_next); xfree(wka); /* return to the calling program */ return (lux->rank < n); } /*---------------------------------------------------------------------- // lux_f_solve - solve system F*x = b or F'*x = b. // // SYNOPSIS // // #include "glplux.h" // void lux_f_solve(LUX *lux, int tr, mpq_t x[]); // // DESCRIPTION // // The routine lux_f_solve solves either the system F*x = b (if the // flag tr is zero) or the system F'*x = b (if the flag tr is non-zero), // where the matrix F is a component of LU-factorization specified by // the parameter lux, F' is a matrix transposed to F. // // On entry the array x should contain elements of the right-hand side // vector b in locations x[1], ..., x[n], where n is the order of the // matrix F. On exit this array will contain elements of the solution // vector x in the same locations. */ void lux_f_solve(LUX *lux, int tr, mpq_t x[]) { int n = lux->n; LUXELM **F_row = lux->F_row; LUXELM **F_col = lux->F_col; int *P_row = lux->P_row; LUXELM *fik, *fkj; int i, j, k; mpq_t temp; mpq_init(temp); if (!tr) { /* solve the system F*x = b */ for (j = 1; j <= n; j++) { k = P_row[j]; if (mpq_sgn(x[k]) != 0) { for (fik = F_col[k]; fik != NULL; fik = fik->c_next) { mpq_mul(temp, fik->val, x[k]); mpq_sub(x[fik->i], x[fik->i], temp); } } } } else { /* solve the system F'*x = b */ for (i = n; i >= 1; i--) { k = P_row[i]; if (mpq_sgn(x[k]) != 0) { for (fkj = F_row[k]; fkj != NULL; fkj = fkj->r_next) { mpq_mul(temp, fkj->val, x[k]); mpq_sub(x[fkj->j], x[fkj->j], temp); } } } } mpq_clear(temp); return; } /*---------------------------------------------------------------------- // lux_v_solve - solve system V*x = b or V'*x = b. // // SYNOPSIS // // #include "glplux.h" // void lux_v_solve(LUX *lux, int tr, double x[]); // // DESCRIPTION // // The routine lux_v_solve solves either the system V*x = b (if the // flag tr is zero) or the system V'*x = b (if the flag tr is non-zero), // where the matrix V is a component of LU-factorization specified by // the parameter lux, V' is a matrix transposed to V. // // On entry the array x should contain elements of the right-hand side // vector b in locations x[1], ..., x[n], where n is the order of the // matrix V. On exit this array will contain elements of the solution // vector x in the same locations. */ void lux_v_solve(LUX *lux, int tr, mpq_t x[]) { int n = lux->n; mpq_t *V_piv = lux->V_piv; LUXELM **V_row = lux->V_row; LUXELM **V_col = lux->V_col; int *P_row = lux->P_row; int *Q_col = lux->Q_col; LUXELM *vij; int i, j, k; mpq_t *b, temp; b = xcalloc(1+n, sizeof(mpq_t)); for (k = 1; k <= n; k++) mpq_init(b[k]), mpq_set(b[k], x[k]), mpq_set_si(x[k], 0, 1); mpq_init(temp); if (!tr) { /* solve the system V*x = b */ for (k = n; k >= 1; k--) { i = P_row[k], j = Q_col[k]; if (mpq_sgn(b[i]) != 0) { mpq_set(x[j], b[i]); mpq_div(x[j], x[j], V_piv[i]); for (vij = V_col[j]; vij != NULL; vij = vij->c_next) { mpq_mul(temp, vij->val, x[j]); mpq_sub(b[vij->i], b[vij->i], temp); } } } } else { /* solve the system V'*x = b */ for (k = 1; k <= n; k++) { i = P_row[k], j = Q_col[k]; if (mpq_sgn(b[j]) != 0) { mpq_set(x[i], b[j]); mpq_div(x[i], x[i], V_piv[i]); for (vij = V_row[i]; vij != NULL; vij = vij->r_next) { mpq_mul(temp, vij->val, x[i]); mpq_sub(b[vij->j], b[vij->j], temp); } } } } for (k = 1; k <= n; k++) mpq_clear(b[k]); mpq_clear(temp); xfree(b); return; } /*---------------------------------------------------------------------- // lux_solve - solve system A*x = b or A'*x = b. // // SYNOPSIS // // #include "glplux.h" // void lux_solve(LUX *lux, int tr, mpq_t x[]); // // DESCRIPTION // // The routine lux_solve solves either the system A*x = b (if the flag // tr is zero) or the system A'*x = b (if the flag tr is non-zero), // where the parameter lux specifies LU-factorization of the matrix A, // A' is a matrix transposed to A. // // On entry the array x should contain elements of the right-hand side // vector b in locations x[1], ..., x[n], where n is the order of the // matrix A. On exit this array will contain elements of the solution // vector x in the same locations. */ void lux_solve(LUX *lux, int tr, mpq_t x[]) { if (lux->rank < lux->n) xfault("lux_solve: LU-factorization has incomplete rank\n"); if (!tr) { /* A = F*V, therefore inv(A) = inv(V)*inv(F) */ lux_f_solve(lux, 0, x); lux_v_solve(lux, 0, x); } else { /* A' = V'*F', therefore inv(A') = inv(F')*inv(V') */ lux_v_solve(lux, 1, x); lux_f_solve(lux, 1, x); } return; } /*---------------------------------------------------------------------- // lux_delete - delete LU-factorization. // // SYNOPSIS // // #include "glplux.h" // void lux_delete(LUX *lux); // // DESCRIPTION // // The routine lux_delete deletes LU-factorization data structure, // which the parameter lux points to, freeing all the memory allocated // to this object. */ void lux_delete(LUX *lux) { int n = lux->n; LUXELM *fij, *vij; int i; for (i = 1; i <= n; i++) { for (fij = lux->F_row[i]; fij != NULL; fij = fij->r_next) mpq_clear(fij->val); mpq_clear(lux->V_piv[i]); for (vij = lux->V_row[i]; vij != NULL; vij = vij->r_next) mpq_clear(vij->val); } dmp_delete_pool(lux->pool); xfree(lux->F_row); xfree(lux->F_col); xfree(lux->V_piv); xfree(lux->V_row); xfree(lux->V_col); xfree(lux->P_row); xfree(lux->P_col); xfree(lux->Q_row); xfree(lux->Q_col); xfree(lux); return; } /* eof */ sources_5316/external/glpk/glpmpl06.c0000644000176700017670000007516211411455614016324 0ustar paulpaul/* glpmpl06.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_ERRNO #define _GLPSTD_STDIO #include "glpmpl.h" #include "glpsql.h" /**********************************************************************/ #define CSV_FIELD_MAX 50 /* maximal number of fields in record */ #define CSV_FDLEN_MAX 100 /* maximal field length */ struct csv { /* comma-separated values file */ int mode; /* 'R' = reading; 'W' = writing */ char *fname; /* name of csv file */ FILE *fp; /* stream assigned to csv file */ jmp_buf jump; /* address for non-local go to in case of error */ int count; /* record count */ /*--------------------------------------------------------------*/ /* used only for input csv file */ int c; /* current character or EOF */ int what; /* current marker: */ #define CSV_EOF 0 /* end-of-file */ #define CSV_EOR 1 /* end-of-record */ #define CSV_NUM 2 /* floating-point number */ #define CSV_STR 3 /* character string */ char field[CSV_FDLEN_MAX+1]; /* current field just read */ int nf; /* number of fields in the csv file */ int ref[1+CSV_FIELD_MAX]; /* ref[k] = k', if k-th field of the csv file corresponds to k'-th field in the table statement; if ref[k] = 0, k-th field of the csv file is ignored */ #if 1 /* 01/VI-2010 */ int nskip; /* number of comment records preceding the header record */ #endif }; #undef read_char static void read_char(struct csv *csv) { /* read character from csv data file */ int c; xassert(csv->c != EOF); if (csv->c == '\n') csv->count++; loop: c = fgetc(csv->fp); if (ferror(csv->fp)) { xprintf("%s:%d: read error - %s\n", csv->fname, csv->count, strerror(errno)); longjmp(csv->jump, 0); } if (feof(csv->fp)) { if (csv->c == '\n') { csv->count--; c = EOF; } else { xprintf("%s:%d: warning: missing final end-of-line\n", csv->fname, csv->count); c = '\n'; } } else if (c == '\r') goto loop; else if (c == '\n') ; else if (iscntrl(c)) { xprintf("%s:%d: invalid control character 0x%02X\n", csv->fname, csv->count, c); longjmp(csv->jump, 0); } csv->c = c; return; } static void read_field(struct csv *csv) { /* read field from csv data file */ /* check for end of file */ if (csv->c == EOF) { csv->what = CSV_EOF; strcpy(csv->field, "EOF"); goto done; } /* check for end of record */ if (csv->c == '\n') { csv->what = CSV_EOR; strcpy(csv->field, "EOR"); read_char(csv); if (csv->c == ',') err1: { xprintf("%s:%d: empty field not allowed\n", csv->fname, csv->count); longjmp(csv->jump, 0); } if (csv->c == '\n') { xprintf("%s:%d: empty record not allowed\n", csv->fname, csv->count); longjmp(csv->jump, 0); } #if 1 /* 01/VI-2010 */ /* skip comment records; may appear only before the very first record containing field names */ if (csv->c == '#' && csv->count == 1) { while (csv->c == '#') { while (csv->c != '\n') read_char(csv); read_char(csv); csv->nskip++; } } #endif goto done; } /* skip comma before next field */ if (csv->c == ',') read_char(csv); /* read field */ if (csv->c == '\'' || csv->c == '"') { /* read a field enclosed in quotes */ int quote = csv->c, len = 0; csv->what = CSV_STR; /* skip opening quote */ read_char(csv); /* read field characters within quotes */ for (;;) { /* check for closing quote and read it */ if (csv->c == quote) { read_char(csv); if (csv->c == quote) ; else if (csv->c == ',' || csv->c == '\n') break; else { xprintf("%s:%d: invalid field\n", csv->fname, csv->count); longjmp(csv->jump, 0); } } /* check the current field length */ if (len == CSV_FDLEN_MAX) err2: { xprintf("%s:%d: field too long\n", csv->fname, csv->count); longjmp(csv->jump, 0); } /* add the current character to the field */ csv->field[len++] = (char)csv->c; /* read the next character */ read_char(csv); } /* the field has been read */ if (len == 0) goto err1; csv->field[len] = '\0'; } else { /* read a field not enclosed in quotes */ int len = 0; double temp; csv->what = CSV_NUM; while (!(csv->c == ',' || csv->c == '\n')) { /* quotes within the field are not allowed */ if (csv->c == '\'' || csv->c == '"') { xprintf("%s:%d: invalid use of single or double quote wi" "thin field\n", csv->fname, csv->count); longjmp(csv->jump, 0); } /* check the current field length */ if (len == CSV_FDLEN_MAX) goto err2; /* add the current character to the field */ csv->field[len++] = (char)csv->c; /* read the next character */ read_char(csv); } /* the field has been read */ if (len == 0) goto err1; csv->field[len] = '\0'; /* check the field type */ if (str2num(csv->field, &temp)) csv->what = CSV_STR; } done: return; } static struct csv *csv_open_file(TABDCA *dca, int mode) { /* open csv data file */ struct csv *csv; /* create control structure */ csv = xmalloc(sizeof(struct csv)); csv->mode = mode; csv->fname = NULL; csv->fp = NULL; if (setjmp(csv->jump)) goto fail; csv->count = 0; csv->c = '\n'; csv->what = 0; csv->field[0] = '\0'; csv->nf = 0; /* try to open the csv data file */ if (mpl_tab_num_args(dca) < 2) { xprintf("csv_driver: file name not specified\n"); longjmp(csv->jump, 0); } csv->fname = xmalloc(strlen(mpl_tab_get_arg(dca, 2))+1); strcpy(csv->fname, mpl_tab_get_arg(dca, 2)); if (mode == 'R') { /* open the file for reading */ int k; csv->fp = fopen(csv->fname, "r"); if (csv->fp == NULL) { xprintf("csv_driver: unable to open %s - %s\n", csv->fname, strerror(errno)); longjmp(csv->jump, 0); } #if 1 /* 01/VI-2010 */ csv->nskip = 0; #endif /* skip fake new-line */ read_field(csv); xassert(csv->what == CSV_EOR); /* read field names */ xassert(csv->nf == 0); for (;;) { read_field(csv); if (csv->what == CSV_EOR) break; if (csv->what != CSV_STR) { xprintf("%s:%d: invalid field name\n", csv->fname, csv->count); longjmp(csv->jump, 0); } if (csv->nf == CSV_FIELD_MAX) { xprintf("%s:%d: too many fields\n", csv->fname, csv->count); longjmp(csv->jump, 0); } csv->nf++; /* find corresponding field in the table statement */ for (k = mpl_tab_num_flds(dca); k >= 1; k--) { if (strcmp(mpl_tab_get_name(dca, k), csv->field) == 0) break; } csv->ref[csv->nf] = k; } /* find dummy RECNO field in the table statement */ for (k = mpl_tab_num_flds(dca); k >= 1; k--) if (strcmp(mpl_tab_get_name(dca, k), "RECNO") == 0) break; csv->ref[0] = k; } else if (mode == 'W') { /* open the file for writing */ int k, nf; csv->fp = fopen(csv->fname, "w"); if (csv->fp == NULL) { xprintf("csv_driver: unable to create %s - %s\n", csv->fname, strerror(errno)); longjmp(csv->jump, 0); } /* write field names */ nf = mpl_tab_num_flds(dca); for (k = 1; k <= nf; k++) fprintf(csv->fp, "%s%c", mpl_tab_get_name(dca, k), k < nf ? ',' : '\n'); csv->count++; } else xassert(mode != mode); /* the file has been open */ return csv; fail: /* the file cannot be open */ if (csv->fname != NULL) xfree(csv->fname); if (csv->fp != NULL) fclose(csv->fp); xfree(csv); return NULL; } static int csv_read_record(TABDCA *dca, struct csv *csv) { /* read next record from csv data file */ int k, ret = 0; xassert(csv->mode == 'R'); if (setjmp(csv->jump)) { ret = 1; goto done; } /* read dummy RECNO field */ if (csv->ref[0] > 0) #if 0 /* 01/VI-2010 */ mpl_tab_set_num(dca, csv->ref[0], csv->count-1); #else mpl_tab_set_num(dca, csv->ref[0], csv->count-csv->nskip-1); #endif /* read fields */ for (k = 1; k <= csv->nf; k++) { read_field(csv); if (csv->what == CSV_EOF) { /* end-of-file reached */ xassert(k == 1); ret = -1; goto done; } else if (csv->what == CSV_EOR) { /* end-of-record reached */ int lack = csv->nf - k + 1; if (lack == 1) xprintf("%s:%d: one field missing\n", csv->fname, csv->count); else xprintf("%s:%d: %d fields missing\n", csv->fname, csv->count, lack); longjmp(csv->jump, 0); } else if (csv->what == CSV_NUM) { /* floating-point number */ if (csv->ref[k] > 0) { double num; xassert(str2num(csv->field, &num) == 0); mpl_tab_set_num(dca, csv->ref[k], num); } } else if (csv->what == CSV_STR) { /* character string */ if (csv->ref[k] > 0) mpl_tab_set_str(dca, csv->ref[k], csv->field); } else xassert(csv != csv); } /* now there must be NL */ read_field(csv); xassert(csv->what != CSV_EOF); if (csv->what != CSV_EOR) { xprintf("%s:%d: too many fields\n", csv->fname, csv->count); longjmp(csv->jump, 0); } done: return ret; } static int csv_write_record(TABDCA *dca, struct csv *csv) { /* write next record to csv data file */ int k, nf, ret = 0; const char *c; xassert(csv->mode == 'W'); nf = mpl_tab_num_flds(dca); for (k = 1; k <= nf; k++) { switch (mpl_tab_get_type(dca, k)) { case 'N': fprintf(csv->fp, "%.*g", DBL_DIG, mpl_tab_get_num(dca, k)); break; case 'S': fputc('"', csv->fp); for (c = mpl_tab_get_str(dca, k); *c != '\0'; c++) { if (*c == '"') fputc('"', csv->fp), fputc('"', csv->fp); else fputc(*c, csv->fp); } fputc('"', csv->fp); break; default: xassert(dca != dca); } fputc(k < nf ? ',' : '\n', csv->fp); } csv->count++; if (ferror(csv->fp)) { xprintf("%s:%d: write error - %s\n", csv->fname, csv->count, strerror(errno)); ret = 1; } return ret; } static int csv_close_file(TABDCA *dca, struct csv *csv) { /* close csv data file */ int ret = 0; xassert(dca == dca); if (csv->mode == 'W') { fflush(csv->fp); if (ferror(csv->fp)) { xprintf("%s:%d: write error - %s\n", csv->fname, csv->count, strerror(errno)); ret = 1; } } xfree(csv->fname); fclose(csv->fp); xfree(csv); return ret; } /**********************************************************************/ #define DBF_FIELD_MAX 50 /* maximal number of fields in record */ #define DBF_FDLEN_MAX 100 /* maximal field length */ struct dbf { /* xBASE data file */ int mode; /* 'R' = reading; 'W' = writing */ char *fname; /* name of xBASE file */ FILE *fp; /* stream assigned to xBASE file */ jmp_buf jump; /* address for non-local go to in case of error */ int offset; /* offset of a byte to be read next */ int count; /* record count */ int nf; /* number of fields */ int ref[1+DBF_FIELD_MAX]; /* ref[k] = k', if k-th field of the csv file corresponds to k'-th field in the table statement; if ref[k] = 0, k-th field of the csv file is ignored */ int type[1+DBF_FIELD_MAX]; /* type[k] is type of k-th field */ int len[1+DBF_FIELD_MAX]; /* len[k] is length of k-th field */ int prec[1+DBF_FIELD_MAX]; /* prec[k] is precision of k-th field */ }; static int read_byte(struct dbf *dbf) { /* read byte from xBASE data file */ int b; b = fgetc(dbf->fp); if (ferror(dbf->fp)) { xprintf("%s:0x%X: read error - %s\n", dbf->fname, dbf->offset, strerror(errno)); longjmp(dbf->jump, 0); } if (feof(dbf->fp)) { xprintf("%s:0x%X: unexpected end of file\n", dbf->fname, dbf->offset); longjmp(dbf->jump, 0); } xassert(0x00 <= b && b <= 0xFF); dbf->offset++; return b; } static void read_header(TABDCA *dca, struct dbf *dbf) { /* read xBASE data file header */ int b, j, k, recl; char name[10+1]; /* (ignored) */ for (j = 1; j <= 10; j++) read_byte(dbf); /* length of each record, in bytes */ recl = read_byte(dbf); recl += read_byte(dbf) << 8; /* (ignored) */ for (j = 1; j <= 20; j++) read_byte(dbf); /* field descriptor array */ xassert(dbf->nf == 0); for (;;) { /* check for end of array */ b = read_byte(dbf); if (b == 0x0D) break; if (dbf->nf == DBF_FIELD_MAX) { xprintf("%s:0x%X: too many fields\n", dbf->fname, dbf->offset); longjmp(dbf->jump, 0); } dbf->nf++; /* field name */ name[0] = (char)b; for (j = 1; j < 10; j++) { b = read_byte(dbf); name[j] = (char)b; } name[10] = '\0'; b = read_byte(dbf); if (b != 0x00) { xprintf("%s:0x%X: invalid field name\n", dbf->fname, dbf->offset); longjmp(dbf->jump, 0); } /* find corresponding field in the table statement */ for (k = mpl_tab_num_flds(dca); k >= 1; k--) if (strcmp(mpl_tab_get_name(dca, k), name) == 0) break; dbf->ref[dbf->nf] = k; /* field type */ b = read_byte(dbf); if (!(b == 'C' || b == 'N')) { xprintf("%s:0x%X: invalid field type\n", dbf->fname, dbf->offset); longjmp(dbf->jump, 0); } dbf->type[dbf->nf] = b; /* (ignored) */ for (j = 1; j <= 4; j++) read_byte(dbf); /* field length */ b = read_byte(dbf); if (b == 0) { xprintf("%s:0x%X: invalid field length\n", dbf->fname, dbf->offset); longjmp(dbf->jump, 0); } if (b > DBF_FDLEN_MAX) { xprintf("%s:0x%X: field too long\n", dbf->fname, dbf->offset); longjmp(dbf->jump, 0); } dbf->len[dbf->nf] = b; recl -= b; /* (ignored) */ for (j = 1; j <= 15; j++) read_byte(dbf); } if (recl != 1) { xprintf("%s:0x%X: invalid file header\n", dbf->fname, dbf->offset); longjmp(dbf->jump, 0); } /* find dummy RECNO field in the table statement */ for (k = mpl_tab_num_flds(dca); k >= 1; k--) if (strcmp(mpl_tab_get_name(dca, k), "RECNO") == 0) break; dbf->ref[0] = k; return; } static void parse_third_arg(TABDCA *dca, struct dbf *dbf) { /* parse xBASE file format (third argument) */ int j, k, temp; const char *arg; dbf->nf = mpl_tab_num_flds(dca); arg = mpl_tab_get_arg(dca, 3), j = 0; for (k = 1; k <= dbf->nf; k++) { /* parse specification of k-th field */ if (arg[j] == '\0') { xprintf("xBASE driver: field %s: specification missing\n", mpl_tab_get_name(dca, k)); longjmp(dbf->jump, 0); } /* parse field type */ if (arg[j] == 'C' || arg[j] == 'N') dbf->type[k] = arg[j], j++; else { xprintf("xBASE driver: field %s: invalid field type\n", mpl_tab_get_name(dca, k)); longjmp(dbf->jump, 0); } /* check for left parenthesis */ if (arg[j] == '(') j++; else err: { xprintf("xBASE driver: field %s: invalid field format\n", mpl_tab_get_name(dca, k)); longjmp(dbf->jump, 0); } /* parse field length */ temp = 0; while (isdigit(arg[j])) { if (temp > DBF_FDLEN_MAX) break; temp = 10 * temp + (arg[j] - '0'), j++; } if (!(1 <= temp && temp <= DBF_FDLEN_MAX)) { xprintf("xBASE driver: field %s: invalid field length\n", mpl_tab_get_name(dca, k)); longjmp(dbf->jump, 0); } dbf->len[k] = temp; /* parse optional field precision */ if (dbf->type[k] == 'N' && arg[j] == ',') { j++; temp = 0; while (isdigit(arg[j])) { if (temp > dbf->len[k]) break; temp = 10 * temp + (arg[j] - '0'), j++; } if (temp > dbf->len[k]) { xprintf("xBASE driver: field %s: invalid field precision" "\n", mpl_tab_get_name(dca, k)); longjmp(dbf->jump, 0); } dbf->prec[k] = temp; } else dbf->prec[k] = 0; /* check for right parenthesis */ if (arg[j] == ')') j++; else goto err; } /* ignore other specifications */ return; } static void write_byte(struct dbf *dbf, int b) { /* write byte to xBASE data file */ fputc(b, dbf->fp); dbf->offset++; return; } static void write_header(TABDCA *dca, struct dbf *dbf) { /* write xBASE data file header */ int j, k, temp; const char *name; /* version number */ write_byte(dbf, 0x03 /* file without DBT */); /* date of last update (YYMMDD) */ write_byte(dbf, 70 /* 1970 */); write_byte(dbf, 1 /* January */); write_byte(dbf, 1 /* 1st */); /* number of records (unknown so far) */ for (j = 1; j <= 4; j++) write_byte(dbf, 0xFF); /* length of the header, in bytes */ temp = 32 + dbf->nf * 32 + 1; write_byte(dbf, temp); write_byte(dbf, temp >> 8); /* length of each record, in bytes */ temp = 1; for (k = 1; k <= dbf->nf; k++) temp += dbf->len[k]; write_byte(dbf, temp); write_byte(dbf, temp >> 8); /* (reserved) */ for (j = 1; j <= 20; j++) write_byte(dbf, 0x00); /* field descriptor array */ for (k = 1; k <= dbf->nf; k++) { /* field name (terminated by 0x00) */ name = mpl_tab_get_name(dca, k); for (j = 0; j < 10 && name[j] != '\0'; j++) write_byte(dbf, name[j]); for (j = j; j < 11; j++) write_byte(dbf, 0x00); /* field type */ write_byte(dbf, dbf->type[k]); /* (reserved) */ for (j = 1; j <= 4; j++) write_byte(dbf, 0x00); /* field length */ write_byte(dbf, dbf->len[k]); /* field precision */ write_byte(dbf, dbf->prec[k]); /* (reserved) */ for (j = 1; j <= 14; j++) write_byte(dbf, 0x00); } /* end of header */ write_byte(dbf, 0x0D); return; } static struct dbf *dbf_open_file(TABDCA *dca, int mode) { /* open xBASE data file */ struct dbf *dbf; /* create control structure */ dbf = xmalloc(sizeof(struct dbf)); dbf->mode = mode; dbf->fname = NULL; dbf->fp = NULL; if (setjmp(dbf->jump)) goto fail; dbf->offset = 0; dbf->count = 0; dbf->nf = 0; /* try to open the xBASE data file */ if (mpl_tab_num_args(dca) < 2) { xprintf("xBASE driver: file name not specified\n"); longjmp(dbf->jump, 0); } dbf->fname = xmalloc(strlen(mpl_tab_get_arg(dca, 2))+1); strcpy(dbf->fname, mpl_tab_get_arg(dca, 2)); if (mode == 'R') { /* open the file for reading */ dbf->fp = fopen(dbf->fname, "rb"); if (dbf->fp == NULL) { xprintf("xBASE driver: unable to open %s - %s\n", dbf->fname, strerror(errno)); longjmp(dbf->jump, 0); } read_header(dca, dbf); } else if (mode == 'W') { /* open the file for writing */ if (mpl_tab_num_args(dca) < 3) { xprintf("xBASE driver: file format not specified\n"); longjmp(dbf->jump, 0); } parse_third_arg(dca, dbf); dbf->fp = fopen(dbf->fname, "wb"); if (dbf->fp == NULL) { xprintf("xBASE driver: unable to create %s - %s\n", dbf->fname, strerror(errno)); longjmp(dbf->jump, 0); } write_header(dca, dbf); } else xassert(mode != mode); /* the file has been open */ return dbf; fail: /* the file cannot be open */ if (dbf->fname != NULL) xfree(dbf->fname); if (dbf->fp != NULL) fclose(dbf->fp); xfree(dbf); return NULL; } static int dbf_read_record(TABDCA *dca, struct dbf *dbf) { /* read next record from xBASE data file */ int b, j, k, ret = 0; char buf[DBF_FDLEN_MAX+1]; xassert(dbf->mode == 'R'); if (setjmp(dbf->jump)) { ret = 1; goto done; } /* check record flag */ b = read_byte(dbf); if (b == 0x1A) { /* end of data */ ret = -1; goto done; } if (b != 0x20) { xprintf("%s:0x%X: invalid record flag\n", dbf->fname, dbf->offset); longjmp(dbf->jump, 0); } /* read dummy RECNO field */ if (dbf->ref[0] > 0) mpl_tab_set_num(dca, dbf->ref[0], dbf->count+1); /* read fields */ for (k = 1; k <= dbf->nf; k++) { /* read k-th field */ for (j = 0; j < dbf->len[k]; j++) buf[j] = (char)read_byte(dbf); buf[dbf->len[k]] = '\0'; /* set field value */ if (dbf->type[k] == 'C') { /* character field */ if (dbf->ref[k] > 0) mpl_tab_set_str(dca, dbf->ref[k], strtrim(buf)); } else if (dbf->type[k] == 'N') { /* numeric field */ if (dbf->ref[k] > 0) { double num; strspx(buf); xassert(str2num(buf, &num) == 0); mpl_tab_set_num(dca, dbf->ref[k], num); } } else xassert(dbf != dbf); } /* increase record count */ dbf->count++; done: return ret; } static int dbf_write_record(TABDCA *dca, struct dbf *dbf) { /* write next record to xBASE data file */ int j, k, ret = 0; char buf[255+1]; xassert(dbf->mode == 'W'); if (setjmp(dbf->jump)) { ret = 1; goto done; } /* record flag */ write_byte(dbf, 0x20); xassert(dbf->nf == mpl_tab_num_flds(dca)); for (k = 1; k <= dbf->nf; k++) { if (dbf->type[k] == 'C') { /* character field */ const char *str; if (mpl_tab_get_type(dca, k) == 'N') { sprintf(buf, "%.*g", DBL_DIG, mpl_tab_get_num(dca, k)); str = buf; } else if (mpl_tab_get_type(dca, k) == 'S') str = mpl_tab_get_str(dca, k); else xassert(dca != dca); if ((int)strlen(str) > dbf->len[k]) { xprintf("xBASE driver: field %s: cannot convert %.15s..." " to field format\n", mpl_tab_get_name(dca, k), str); longjmp(dbf->jump, 0); } for (j = 0; j < dbf->len[k] && str[j] != '\0'; j++) write_byte(dbf, str[j]); for (j = j; j < dbf->len[k]; j++) write_byte(dbf, ' '); } else if (dbf->type[k] == 'N') { /* numeric field */ double num = mpl_tab_get_num(dca, k); if (fabs(num) > 1e20) err: { xprintf("xBASE driver: field %s: cannot convert %g to fi" "eld format\n", mpl_tab_get_name(dca, k), num); longjmp(dbf->jump, 0); } sprintf(buf, "%*.*f", dbf->len[k], dbf->prec[k], num); xassert(strlen(buf) < sizeof(buf)); if ((int)strlen(buf) != dbf->len[k]) goto err; for (j = 0; j < dbf->len[k]; j++) write_byte(dbf, buf[j]); } else xassert(dbf != dbf); } /* increase record count */ dbf->count++; done: return ret; } static int dbf_close_file(TABDCA *dca, struct dbf *dbf) { /* close xBASE data file */ int ret = 0; xassert(dca == dca); if (dbf->mode == 'W') { if (setjmp(dbf->jump)) { ret = 1; goto skip; } /* end-of-file flag */ write_byte(dbf, 0x1A); /* number of records */ dbf->offset = 4; if (fseek(dbf->fp, dbf->offset, SEEK_SET)) { xprintf("%s:0x%X: seek error - %s\n", dbf->fname, dbf->offset, strerror(errno)); longjmp(dbf->jump, 0); } write_byte(dbf, dbf->count); write_byte(dbf, dbf->count >> 8); write_byte(dbf, dbf->count >> 16); write_byte(dbf, dbf->count >> 24); fflush(dbf->fp); if (ferror(dbf->fp)) { xprintf("%s:0x%X: write error - %s\n", dbf->fname, dbf->offset, strerror(errno)); longjmp(dbf->jump, 0); } skip: ; } xfree(dbf->fname); fclose(dbf->fp); xfree(dbf); return ret; } /**********************************************************************/ #define TAB_CSV 1 #define TAB_XBASE 2 #define TAB_ODBC 3 #define TAB_MYSQL 4 void mpl_tab_drv_open(MPL *mpl, int mode) { TABDCA *dca = mpl->dca; xassert(dca->id == 0); xassert(dca->link == NULL); xassert(dca->na >= 1); if (strcmp(dca->arg[1], "CSV") == 0) { dca->id = TAB_CSV; dca->link = csv_open_file(dca, mode); } else if (strcmp(dca->arg[1], "xBASE") == 0) { dca->id = TAB_XBASE; dca->link = dbf_open_file(dca, mode); } else if (strcmp(dca->arg[1], "ODBC") == 0 || strcmp(dca->arg[1], "iODBC") == 0) { dca->id = TAB_ODBC; dca->link = db_iodbc_open(dca, mode); } else if (strcmp(dca->arg[1], "MySQL") == 0) { dca->id = TAB_MYSQL; dca->link = db_mysql_open(dca, mode); } else xprintf("Invalid table driver `%s'\n", dca->arg[1]); if (dca->link == NULL) mpl_error(mpl, "error on opening table %s", mpl->stmt->u.tab->name); return; } int mpl_tab_drv_read(MPL *mpl) { TABDCA *dca = mpl->dca; int ret; switch (dca->id) { case TAB_CSV: ret = csv_read_record(dca, dca->link); break; case TAB_XBASE: ret = dbf_read_record(dca, dca->link); break; case TAB_ODBC: ret = db_iodbc_read(dca, dca->link); break; case TAB_MYSQL: ret = db_mysql_read(dca, dca->link); break; default: xassert(dca != dca); } if (ret > 0) mpl_error(mpl, "error on reading data from table %s", mpl->stmt->u.tab->name); return ret; } void mpl_tab_drv_write(MPL *mpl) { TABDCA *dca = mpl->dca; int ret; switch (dca->id) { case TAB_CSV: ret = csv_write_record(dca, dca->link); break; case TAB_XBASE: ret = dbf_write_record(dca, dca->link); break; case TAB_ODBC: ret = db_iodbc_write(dca, dca->link); break; case TAB_MYSQL: ret = db_mysql_write(dca, dca->link); break; default: xassert(dca != dca); } if (ret) mpl_error(mpl, "error on writing data to table %s", mpl->stmt->u.tab->name); return; } void mpl_tab_drv_close(MPL *mpl) { TABDCA *dca = mpl->dca; int ret; switch (dca->id) { case TAB_CSV: ret = csv_close_file(dca, dca->link); break; case TAB_XBASE: ret = dbf_close_file(dca, dca->link); break; case TAB_ODBC: ret = db_iodbc_close(dca, dca->link); break; case TAB_MYSQL: ret = db_mysql_close(dca, dca->link); break; default: xassert(dca != dca); } dca->id = 0; dca->link = NULL; if (ret) mpl_error(mpl, "error on closing table %s", mpl->stmt->u.tab->name); return; } /* eof */ sources_5316/external/glpk/glpspx02.c0000644000176700017670000030607611401660400016331 0ustar paulpaul/* glpspx02.c (dual simplex method) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpspx.h" #define GLP_DEBUG 1 #if 0 #define GLP_LONG_STEP 1 #endif struct csa { /* common storage area */ /*--------------------------------------------------------------*/ /* LP data */ int m; /* number of rows (auxiliary variables), m > 0 */ int n; /* number of columns (structural variables), n > 0 */ char *type; /* char type[1+m+n]; */ /* type[0] is not used; type[k], 1 <= k <= m+n, is the type of variable x[k]: GLP_FR - free variable GLP_LO - variable with lower bound GLP_UP - variable with upper bound GLP_DB - double-bounded variable GLP_FX - fixed variable */ double *lb; /* double lb[1+m+n]; */ /* lb[0] is not used; lb[k], 1 <= k <= m+n, is an lower bound of variable x[k]; if x[k] has no lower bound, lb[k] is zero */ double *ub; /* double ub[1+m+n]; */ /* ub[0] is not used; ub[k], 1 <= k <= m+n, is an upper bound of variable x[k]; if x[k] has no upper bound, ub[k] is zero; if x[k] is of fixed type, ub[k] is the same as lb[k] */ double *coef; /* double coef[1+m+n]; */ /* coef[0] is not used; coef[k], 1 <= k <= m+n, is an objective coefficient at variable x[k] */ /*--------------------------------------------------------------*/ /* original bounds of variables */ char *orig_type; /* char orig_type[1+m+n]; */ double *orig_lb; /* double orig_lb[1+m+n]; */ double *orig_ub; /* double orig_ub[1+m+n]; */ /*--------------------------------------------------------------*/ /* original objective function */ double *obj; /* double obj[1+n]; */ /* obj[0] is a constant term of the original objective function; obj[j], 1 <= j <= n, is an original objective coefficient at structural variable x[m+j] */ double zeta; /* factor used to scale original objective coefficients; its sign defines original optimization direction: zeta > 0 means minimization, zeta < 0 means maximization */ /*--------------------------------------------------------------*/ /* constraint matrix A; it has m rows and n columns and is stored by columns */ int *A_ptr; /* int A_ptr[1+n+1]; */ /* A_ptr[0] is not used; A_ptr[j], 1 <= j <= n, is starting position of j-th column in arrays A_ind and A_val; note that A_ptr[1] is always 1; A_ptr[n+1] indicates the position after the last element in arrays A_ind and A_val */ int *A_ind; /* int A_ind[A_ptr[n+1]]; */ /* row indices */ double *A_val; /* double A_val[A_ptr[n+1]]; */ /* non-zero element values */ #if 1 /* 06/IV-2009 */ /* constraint matrix A stored by rows */ int *AT_ptr; /* int AT_ptr[1+m+1]; /* AT_ptr[0] is not used; AT_ptr[i], 1 <= i <= m, is starting position of i-th row in arrays AT_ind and AT_val; note that AT_ptr[1] is always 1; AT_ptr[m+1] indicates the position after the last element in arrays AT_ind and AT_val */ int *AT_ind; /* int AT_ind[AT_ptr[m+1]]; */ /* column indices */ double *AT_val; /* double AT_val[AT_ptr[m+1]]; */ /* non-zero element values */ #endif /*--------------------------------------------------------------*/ /* basis header */ int *head; /* int head[1+m+n]; */ /* head[0] is not used; head[i], 1 <= i <= m, is the ordinal number of basic variable xB[i]; head[i] = k means that xB[i] = x[k] and i-th column of matrix B is k-th column of matrix (I|-A); head[m+j], 1 <= j <= n, is the ordinal number of non-basic variable xN[j]; head[m+j] = k means that xN[j] = x[k] and j-th column of matrix N is k-th column of matrix (I|-A) */ #if 1 /* 06/IV-2009 */ int *bind; /* int bind[1+m+n]; */ /* bind[0] is not used; bind[k], 1 <= k <= m+n, is the position of k-th column of the matrix (I|-A) in the matrix (B|N); that is, bind[k] = k' means that head[k'] = k */ #endif char *stat; /* char stat[1+n]; */ /* stat[0] is not used; stat[j], 1 <= j <= n, is the status of non-basic variable xN[j], which defines its active bound: GLP_NL - lower bound is active GLP_NU - upper bound is active GLP_NF - free variable GLP_NS - fixed variable */ /*--------------------------------------------------------------*/ /* matrix B is the basis matrix; it is composed from columns of the augmented constraint matrix (I|-A) corresponding to basic variables and stored in a factorized (invertable) form */ int valid; /* factorization is valid only if this flag is set */ BFD *bfd; /* BFD bfd[1:m,1:m]; */ /* factorized (invertable) form of the basis matrix */ #if 0 /* 06/IV-2009 */ /*--------------------------------------------------------------*/ /* matrix N is a matrix composed from columns of the augmented constraint matrix (I|-A) corresponding to non-basic variables except fixed ones; it is stored by rows and changes every time the basis changes */ int *N_ptr; /* int N_ptr[1+m+1]; */ /* N_ptr[0] is not used; N_ptr[i], 1 <= i <= m, is starting position of i-th row in arrays N_ind and N_val; note that N_ptr[1] is always 1; N_ptr[m+1] indicates the position after the last element in arrays N_ind and N_val */ int *N_len; /* int N_len[1+m]; */ /* N_len[0] is not used; N_len[i], 1 <= i <= m, is length of i-th row (0 to n) */ int *N_ind; /* int N_ind[N_ptr[m+1]]; */ /* column indices */ double *N_val; /* double N_val[N_ptr[m+1]]; */ /* non-zero element values */ #endif /*--------------------------------------------------------------*/ /* working parameters */ int phase; /* search phase: 0 - not determined yet 1 - search for dual feasible solution 2 - search for optimal solution */ glp_long tm_beg; /* time value at the beginning of the search */ int it_beg; /* simplex iteration count at the beginning of the search */ int it_cnt; /* simplex iteration count; it increases by one every time the basis changes */ int it_dpy; /* simplex iteration count at the most recent display output */ /*--------------------------------------------------------------*/ /* basic solution components */ double *bbar; /* double bbar[1+m]; */ /* bbar[0] is not used on phase I; on phase II it is the current value of the original objective function; bbar[i], 1 <= i <= m, is primal value of basic variable xB[i] (if xB[i] is free, its primal value is not updated) */ double *cbar; /* double cbar[1+n]; */ /* cbar[0] is not used; cbar[j], 1 <= j <= n, is reduced cost of non-basic variable xN[j] (if xN[j] is fixed, its reduced cost is not updated) */ /*--------------------------------------------------------------*/ /* the following pricing technique options may be used: GLP_PT_STD - standard ("textbook") pricing; GLP_PT_PSE - projected steepest edge; GLP_PT_DVX - Devex pricing (not implemented yet); in case of GLP_PT_STD the reference space is not used, and all steepest edge coefficients are set to 1 */ int refct; /* this count is set to an initial value when the reference space is defined and decreases by one every time the basis changes; once this count reaches zero, the reference space is redefined again */ char *refsp; /* char refsp[1+m+n]; */ /* refsp[0] is not used; refsp[k], 1 <= k <= m+n, is the flag which means that variable x[k] belongs to the current reference space */ double *gamma; /* double gamma[1+m]; */ /* gamma[0] is not used; gamma[i], 1 <= i <= n, is the steepest edge coefficient for basic variable xB[i]; if xB[i] is free, gamma[i] is not used and just set to 1 */ /*--------------------------------------------------------------*/ /* basic variable xB[p] chosen to leave the basis */ int p; /* index of the basic variable xB[p] chosen, 1 <= p <= m; if the set of eligible basic variables is empty (i.e. if the current basic solution is primal feasible within a tolerance) and thus no variable has been chosen, p is set to 0 */ double delta; /* change of xB[p] in the adjacent basis; delta > 0 means that xB[p] violates its lower bound and will increase to achieve it in the adjacent basis; delta < 0 means that xB[p] violates its upper bound and will decrease to achieve it in the adjacent basis */ /*--------------------------------------------------------------*/ /* pivot row of the simplex table corresponding to basic variable xB[p] chosen is the following vector: T' * e[p] = - N' * inv(B') * e[p] = - N' * rho, where B' is a matrix transposed to the current basis matrix, N' is a matrix, whose rows are columns of the matrix (I|-A) corresponding to non-basic non-fixed variables */ int trow_nnz; /* number of non-zero components, 0 <= nnz <= n */ int *trow_ind; /* int trow_ind[1+n]; */ /* trow_ind[0] is not used; trow_ind[t], 1 <= t <= nnz, is an index of non-zero component, i.e. trow_ind[t] = j means that trow_vec[j] != 0 */ double *trow_vec; /* int trow_vec[1+n]; */ /* trow_vec[0] is not used; trow_vec[j], 1 <= j <= n, is a numeric value of j-th component of the row */ double trow_max; /* infinity (maximum) norm of the row (max |trow_vec[j]|) */ int trow_num; /* number of significant non-zero components, which means that: |trow_vec[j]| >= eps for j in trow_ind[1,...,num], |tcol_vec[j]| < eps for j in trow_ind[num+1,...,nnz], where eps is a pivot tolerance */ /*--------------------------------------------------------------*/ #ifdef GLP_LONG_STEP /* 07/IV-2009 */ int nbps; /* number of breakpoints, 0 <= nbps <= n */ struct bkpt { int j; /* index of non-basic variable xN[j], 1 <= j <= n */ double t; /* value of dual ray parameter at breakpoint, t >= 0 */ double dz; /* dz = zeta(t = t[k]) - zeta(t = 0) */ } *bkpt; /* struct bkpt bkpt[1+n]; */ /* bkpt[0] is not used; bkpt[k], 1 <= k <= nbps, is k-th breakpoint of the dual objective */ #endif /*--------------------------------------------------------------*/ /* non-basic variable xN[q] chosen to enter the basis */ int q; /* index of the non-basic variable xN[q] chosen, 1 <= q <= n; if no variable has been chosen, q is set to 0 */ double new_dq; /* reduced cost of xN[q] in the adjacent basis (it is the change of lambdaB[p]) */ /*--------------------------------------------------------------*/ /* pivot column of the simplex table corresponding to non-basic variable xN[q] chosen is the following vector: T * e[q] = - inv(B) * N * e[q] = - inv(B) * N[q], where B is the current basis matrix, N[q] is a column of the matrix (I|-A) corresponding to xN[q] */ int tcol_nnz; /* number of non-zero components, 0 <= nnz <= m */ int *tcol_ind; /* int tcol_ind[1+m]; */ /* tcol_ind[0] is not used; tcol_ind[t], 1 <= t <= nnz, is an index of non-zero component, i.e. tcol_ind[t] = i means that tcol_vec[i] != 0 */ double *tcol_vec; /* double tcol_vec[1+m]; */ /* tcol_vec[0] is not used; tcol_vec[i], 1 <= i <= m, is a numeric value of i-th component of the column */ /*--------------------------------------------------------------*/ /* working arrays */ double *work1; /* double work1[1+m]; */ double *work2; /* double work2[1+m]; */ double *work3; /* double work3[1+m]; */ double *work4; /* double work4[1+m]; */ }; static const double kappa = 0.10; /*********************************************************************** * alloc_csa - allocate common storage area * * This routine allocates all arrays in the common storage area (CSA) * and returns a pointer to the CSA. */ static struct csa *alloc_csa(glp_prob *lp) { struct csa *csa; int m = lp->m; int n = lp->n; int nnz = lp->nnz; csa = xmalloc(sizeof(struct csa)); xassert(m > 0 && n > 0); csa->m = m; csa->n = n; csa->type = xcalloc(1+m+n, sizeof(char)); csa->lb = xcalloc(1+m+n, sizeof(double)); csa->ub = xcalloc(1+m+n, sizeof(double)); csa->coef = xcalloc(1+m+n, sizeof(double)); csa->orig_type = xcalloc(1+m+n, sizeof(char)); csa->orig_lb = xcalloc(1+m+n, sizeof(double)); csa->orig_ub = xcalloc(1+m+n, sizeof(double)); csa->obj = xcalloc(1+n, sizeof(double)); csa->A_ptr = xcalloc(1+n+1, sizeof(int)); csa->A_ind = xcalloc(1+nnz, sizeof(int)); csa->A_val = xcalloc(1+nnz, sizeof(double)); #if 1 /* 06/IV-2009 */ csa->AT_ptr = xcalloc(1+m+1, sizeof(int)); csa->AT_ind = xcalloc(1+nnz, sizeof(int)); csa->AT_val = xcalloc(1+nnz, sizeof(double)); #endif csa->head = xcalloc(1+m+n, sizeof(int)); #if 1 /* 06/IV-2009 */ csa->bind = xcalloc(1+m+n, sizeof(int)); #endif csa->stat = xcalloc(1+n, sizeof(char)); #if 0 /* 06/IV-2009 */ csa->N_ptr = xcalloc(1+m+1, sizeof(int)); csa->N_len = xcalloc(1+m, sizeof(int)); csa->N_ind = NULL; /* will be allocated later */ csa->N_val = NULL; /* will be allocated later */ #endif csa->bbar = xcalloc(1+m, sizeof(double)); csa->cbar = xcalloc(1+n, sizeof(double)); csa->refsp = xcalloc(1+m+n, sizeof(char)); csa->gamma = xcalloc(1+m, sizeof(double)); csa->trow_ind = xcalloc(1+n, sizeof(int)); csa->trow_vec = xcalloc(1+n, sizeof(double)); #ifdef GLP_LONG_STEP /* 07/IV-2009 */ csa->bkpt = xcalloc(1+n, sizeof(struct bkpt)); #endif csa->tcol_ind = xcalloc(1+m, sizeof(int)); csa->tcol_vec = xcalloc(1+m, sizeof(double)); csa->work1 = xcalloc(1+m, sizeof(double)); csa->work2 = xcalloc(1+m, sizeof(double)); csa->work3 = xcalloc(1+m, sizeof(double)); csa->work4 = xcalloc(1+m, sizeof(double)); return csa; } /*********************************************************************** * init_csa - initialize common storage area * * This routine initializes all data structures in the common storage * area (CSA). */ static void init_csa(struct csa *csa, glp_prob *lp) { int m = csa->m; int n = csa->n; char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; double *coef = csa->coef; char *orig_type = csa->orig_type; double *orig_lb = csa->orig_lb; double *orig_ub = csa->orig_ub; double *obj = csa->obj; int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; #if 1 /* 06/IV-2009 */ int *AT_ptr = csa->AT_ptr; int *AT_ind = csa->AT_ind; double *AT_val = csa->AT_val; #endif int *head = csa->head; #if 1 /* 06/IV-2009 */ int *bind = csa->bind; #endif char *stat = csa->stat; char *refsp = csa->refsp; double *gamma = csa->gamma; int i, j, k, loc; double cmax; /* auxiliary variables */ for (i = 1; i <= m; i++) { GLPROW *row = lp->row[i]; type[i] = (char)row->type; lb[i] = row->lb * row->rii; ub[i] = row->ub * row->rii; coef[i] = 0.0; } /* structural variables */ for (j = 1; j <= n; j++) { GLPCOL *col = lp->col[j]; type[m+j] = (char)col->type; lb[m+j] = col->lb / col->sjj; ub[m+j] = col->ub / col->sjj; coef[m+j] = col->coef * col->sjj; } /* original bounds of variables */ memcpy(&orig_type[1], &type[1], (m+n) * sizeof(char)); memcpy(&orig_lb[1], &lb[1], (m+n) * sizeof(double)); memcpy(&orig_ub[1], &ub[1], (m+n) * sizeof(double)); /* original objective function */ obj[0] = lp->c0; memcpy(&obj[1], &coef[m+1], n * sizeof(double)); /* factor used to scale original objective coefficients */ cmax = 0.0; for (j = 1; j <= n; j++) if (cmax < fabs(obj[j])) cmax = fabs(obj[j]); if (cmax == 0.0) cmax = 1.0; switch (lp->dir) { case GLP_MIN: csa->zeta = + 1.0 / cmax; break; case GLP_MAX: csa->zeta = - 1.0 / cmax; break; default: xassert(lp != lp); } #if 1 if (fabs(csa->zeta) < 1.0) csa->zeta *= 1000.0; #endif /* scale working objective coefficients */ for (j = 1; j <= n; j++) coef[m+j] *= csa->zeta; /* matrix A (by columns) */ loc = 1; for (j = 1; j <= n; j++) { GLPAIJ *aij; A_ptr[j] = loc; for (aij = lp->col[j]->ptr; aij != NULL; aij = aij->c_next) { A_ind[loc] = aij->row->i; A_val[loc] = aij->row->rii * aij->val * aij->col->sjj; loc++; } } A_ptr[n+1] = loc; xassert(loc-1 == lp->nnz); #if 1 /* 06/IV-2009 */ /* matrix A (by rows) */ loc = 1; for (i = 1; i <= m; i++) { GLPAIJ *aij; AT_ptr[i] = loc; for (aij = lp->row[i]->ptr; aij != NULL; aij = aij->r_next) { AT_ind[loc] = aij->col->j; AT_val[loc] = aij->row->rii * aij->val * aij->col->sjj; loc++; } } AT_ptr[m+1] = loc; xassert(loc-1 == lp->nnz); #endif /* basis header */ xassert(lp->valid); memcpy(&head[1], &lp->head[1], m * sizeof(int)); k = 0; for (i = 1; i <= m; i++) { GLPROW *row = lp->row[i]; if (row->stat != GLP_BS) { k++; xassert(k <= n); head[m+k] = i; stat[k] = (char)row->stat; } } for (j = 1; j <= n; j++) { GLPCOL *col = lp->col[j]; if (col->stat != GLP_BS) { k++; xassert(k <= n); head[m+k] = m + j; stat[k] = (char)col->stat; } } xassert(k == n); #if 1 /* 06/IV-2009 */ for (k = 1; k <= m+n; k++) bind[head[k]] = k; #endif /* factorization of matrix B */ csa->valid = 1, lp->valid = 0; csa->bfd = lp->bfd, lp->bfd = NULL; #if 0 /* 06/IV-2009 */ /* matrix N (by rows) */ alloc_N(csa); build_N(csa); #endif /* working parameters */ csa->phase = 0; csa->tm_beg = xtime(); csa->it_beg = csa->it_cnt = lp->it_cnt; csa->it_dpy = -1; /* reference space and steepest edge coefficients */ csa->refct = 0; memset(&refsp[1], 0, (m+n) * sizeof(char)); for (i = 1; i <= m; i++) gamma[i] = 1.0; return; } #if 1 /* copied from primal */ /*********************************************************************** * invert_B - compute factorization of the basis matrix * * This routine computes factorization of the current basis matrix B. * * If the operation is successful, the routine returns zero, otherwise * non-zero. */ static int inv_col(void *info, int i, int ind[], double val[]) { /* this auxiliary routine returns row indices and numeric values of non-zero elements of i-th column of the basis matrix */ struct csa *csa = info; int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; int k, len, ptr, t; #ifdef GLP_DEBUG xassert(1 <= i && i <= m); #endif k = head[i]; /* B[i] is k-th column of (I|-A) */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k <= m) { /* B[i] is k-th column of submatrix I */ len = 1; ind[1] = k; val[1] = 1.0; } else { /* B[i] is (k-m)-th column of submatrix (-A) */ ptr = A_ptr[k-m]; len = A_ptr[k-m+1] - ptr; memcpy(&ind[1], &A_ind[ptr], len * sizeof(int)); memcpy(&val[1], &A_val[ptr], len * sizeof(double)); for (t = 1; t <= len; t++) val[t] = - val[t]; } return len; } static int invert_B(struct csa *csa) { int ret; ret = bfd_factorize(csa->bfd, csa->m, NULL, inv_col, csa); csa->valid = (ret == 0); return ret; } #endif #if 1 /* copied from primal */ /*********************************************************************** * update_B - update factorization of the basis matrix * * This routine replaces i-th column of the basis matrix B by k-th * column of the augmented constraint matrix (I|-A) and then updates * the factorization of B. * * If the factorization has been successfully updated, the routine * returns zero, otherwise non-zero. */ static int update_B(struct csa *csa, int i, int k) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int ret; #ifdef GLP_DEBUG xassert(1 <= i && i <= m); xassert(1 <= k && k <= m+n); #endif if (k <= m) { /* new i-th column of B is k-th column of I */ int ind[1+1]; double val[1+1]; ind[1] = k; val[1] = 1.0; xassert(csa->valid); ret = bfd_update_it(csa->bfd, i, 0, 1, ind, val); } else { /* new i-th column of B is (k-m)-th column of (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; double *val = csa->work1; int beg, end, ptr, len; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; len = 0; for (ptr = beg; ptr < end; ptr++) val[++len] = - A_val[ptr]; xassert(csa->valid); ret = bfd_update_it(csa->bfd, i, 0, len, &A_ind[beg-1], val); } csa->valid = (ret == 0); return ret; } #endif #if 1 /* copied from primal */ /*********************************************************************** * error_ftran - compute residual vector r = h - B * x * * This routine computes the residual vector r = h - B * x, where B is * the current basis matrix, h is the vector of right-hand sides, x is * the solution vector. */ static void error_ftran(struct csa *csa, double h[], double x[], double r[]) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; int i, k, beg, end, ptr; double temp; /* compute the residual vector: r = h - B * x = h - B[1] * x[1] - ... - B[m] * x[m], where B[1], ..., B[m] are columns of matrix B */ memcpy(&r[1], &h[1], m * sizeof(double)); for (i = 1; i <= m; i++) { temp = x[i]; if (temp == 0.0) continue; k = head[i]; /* B[i] is k-th column of (I|-A) */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k <= m) { /* B[i] is k-th column of submatrix I */ r[k] -= temp; } else { /* B[i] is (k-m)-th column of submatrix (-A) */ beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) r[A_ind[ptr]] += A_val[ptr] * temp; } } return; } #endif #if 1 /* copied from primal */ /*********************************************************************** * refine_ftran - refine solution of B * x = h * * This routine performs one iteration to refine the solution of * the system B * x = h, where B is the current basis matrix, h is the * vector of right-hand sides, x is the solution vector. */ static void refine_ftran(struct csa *csa, double h[], double x[]) { int m = csa->m; double *r = csa->work1; double *d = csa->work1; int i; /* compute the residual vector r = h - B * x */ error_ftran(csa, h, x, r); /* compute the correction vector d = inv(B) * r */ xassert(csa->valid); bfd_ftran(csa->bfd, d); /* refine the solution vector (new x) = (old x) + d */ for (i = 1; i <= m; i++) x[i] += d[i]; return; } #endif #if 1 /* copied from primal */ /*********************************************************************** * error_btran - compute residual vector r = h - B'* x * * This routine computes the residual vector r = h - B'* x, where B' * is a matrix transposed to the current basis matrix, h is the vector * of right-hand sides, x is the solution vector. */ static void error_btran(struct csa *csa, double h[], double x[], double r[]) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; int i, k, beg, end, ptr; double temp; /* compute the residual vector r = b - B'* x */ for (i = 1; i <= m; i++) { /* r[i] := b[i] - (i-th column of B)'* x */ k = head[i]; /* B[i] is k-th column of (I|-A) */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif temp = h[i]; if (k <= m) { /* B[i] is k-th column of submatrix I */ temp -= x[k]; } else { /* B[i] is (k-m)-th column of submatrix (-A) */ beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) temp += A_val[ptr] * x[A_ind[ptr]]; } r[i] = temp; } return; } #endif #if 1 /* copied from primal */ /*********************************************************************** * refine_btran - refine solution of B'* x = h * * This routine performs one iteration to refine the solution of the * system B'* x = h, where B' is a matrix transposed to the current * basis matrix, h is the vector of right-hand sides, x is the solution * vector. */ static void refine_btran(struct csa *csa, double h[], double x[]) { int m = csa->m; double *r = csa->work1; double *d = csa->work1; int i; /* compute the residual vector r = h - B'* x */ error_btran(csa, h, x, r); /* compute the correction vector d = inv(B') * r */ xassert(csa->valid); bfd_btran(csa->bfd, d); /* refine the solution vector (new x) = (old x) + d */ for (i = 1; i <= m; i++) x[i] += d[i]; return; } #endif #if 1 /* copied from primal */ /*********************************************************************** * get_xN - determine current value of non-basic variable xN[j] * * This routine returns the current value of non-basic variable xN[j], * which is a value of its active bound. */ static double get_xN(struct csa *csa, int j) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif double *lb = csa->lb; double *ub = csa->ub; int *head = csa->head; char *stat = csa->stat; int k; double xN; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); #endif k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif switch (stat[j]) { case GLP_NL: /* x[k] is on its lower bound */ xN = lb[k]; break; case GLP_NU: /* x[k] is on its upper bound */ xN = ub[k]; break; case GLP_NF: /* x[k] is free non-basic variable */ xN = 0.0; break; case GLP_NS: /* x[k] is fixed non-basic variable */ xN = lb[k]; break; default: xassert(stat != stat); } return xN; } #endif #if 1 /* copied from primal */ /*********************************************************************** * eval_beta - compute primal values of basic variables * * This routine computes current primal values of all basic variables: * * beta = - inv(B) * N * xN, * * where B is the current basis matrix, N is a matrix built of columns * of matrix (I|-A) corresponding to non-basic variables, and xN is the * vector of current values of non-basic variables. */ static void eval_beta(struct csa *csa, double beta[]) { int m = csa->m; int n = csa->n; int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; double *h = csa->work2; int i, j, k, beg, end, ptr; double xN; /* compute the right-hand side vector: h := - N * xN = - N[1] * xN[1] - ... - N[n] * xN[n], where N[1], ..., N[n] are columns of matrix N */ for (i = 1; i <= m; i++) h[i] = 0.0; for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* determine current value of xN[j] */ xN = get_xN(csa, j); if (xN == 0.0) continue; if (k <= m) { /* N[j] is k-th column of submatrix I */ h[k] -= xN; } else { /* N[j] is (k-m)-th column of submatrix (-A) */ beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) h[A_ind[ptr]] += xN * A_val[ptr]; } } /* solve system B * beta = h */ memcpy(&beta[1], &h[1], m * sizeof(double)); xassert(csa->valid); bfd_ftran(csa->bfd, beta); /* and refine the solution */ refine_ftran(csa, h, beta); return; } #endif #if 1 /* copied from primal */ /*********************************************************************** * eval_pi - compute vector of simplex multipliers * * This routine computes the vector of current simplex multipliers: * * pi = inv(B') * cB, * * where B' is a matrix transposed to the current basis matrix, cB is * a subvector of objective coefficients at basic variables. */ static void eval_pi(struct csa *csa, double pi[]) { int m = csa->m; double *c = csa->coef; int *head = csa->head; double *cB = csa->work2; int i; /* construct the right-hand side vector cB */ for (i = 1; i <= m; i++) cB[i] = c[head[i]]; /* solve system B'* pi = cB */ memcpy(&pi[1], &cB[1], m * sizeof(double)); xassert(csa->valid); bfd_btran(csa->bfd, pi); /* and refine the solution */ refine_btran(csa, cB, pi); return; } #endif #if 1 /* copied from primal */ /*********************************************************************** * eval_cost - compute reduced cost of non-basic variable xN[j] * * This routine computes the current reduced cost of non-basic variable * xN[j]: * * d[j] = cN[j] - N'[j] * pi, * * where cN[j] is the objective coefficient at variable xN[j], N[j] is * a column of the augmented constraint matrix (I|-A) corresponding to * xN[j], pi is the vector of simplex multipliers. */ static double eval_cost(struct csa *csa, double pi[], int j) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif double *coef = csa->coef; int *head = csa->head; int k; double dj; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); #endif k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif dj = coef[k]; if (k <= m) { /* N[j] is k-th column of submatrix I */ dj -= pi[k]; } else { /* N[j] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) dj += A_val[ptr] * pi[A_ind[ptr]]; } return dj; } #endif #if 1 /* copied from primal */ /*********************************************************************** * eval_bbar - compute and store primal values of basic variables * * This routine computes primal values of all basic variables and then * stores them in the solution array. */ static void eval_bbar(struct csa *csa) { eval_beta(csa, csa->bbar); return; } #endif #if 1 /* copied from primal */ /*********************************************************************** * eval_cbar - compute and store reduced costs of non-basic variables * * This routine computes reduced costs of all non-basic variables and * then stores them in the solution array. */ static void eval_cbar(struct csa *csa) { #ifdef GLP_DEBUG int m = csa->m; #endif int n = csa->n; #ifdef GLP_DEBUG int *head = csa->head; #endif double *cbar = csa->cbar; double *pi = csa->work3; int j; #ifdef GLP_DEBUG int k; #endif /* compute simplex multipliers */ eval_pi(csa, pi); /* compute and store reduced costs */ for (j = 1; j <= n; j++) { #ifdef GLP_DEBUG k = head[m+j]; /* x[k] = xN[j] */ xassert(1 <= k && k <= m+n); #endif cbar[j] = eval_cost(csa, pi, j); } return; } #endif /*********************************************************************** * reset_refsp - reset the reference space * * This routine resets (redefines) the reference space used in the * projected steepest edge pricing algorithm. */ static void reset_refsp(struct csa *csa) { int m = csa->m; int n = csa->n; int *head = csa->head; char *refsp = csa->refsp; double *gamma = csa->gamma; int i, k; xassert(csa->refct == 0); csa->refct = 1000; memset(&refsp[1], 0, (m+n) * sizeof(char)); for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ refsp[k] = 1; gamma[i] = 1.0; } return; } /*********************************************************************** * eval_gamma - compute steepest edge coefficients * * This routine computes the vector of steepest edge coefficients for * all basic variables (except free ones) using its direct definition: * * gamma[i] = eta[i] + sum alfa[i,j]^2, i = 1,...,m, * j in C * * where eta[i] = 1 means that xB[i] is in the current reference space, * and 0 otherwise; C is a set of non-basic non-fixed variables xN[j], * which are in the current reference space; alfa[i,j] are elements of * the current simplex table. * * NOTE: The routine is intended only for debugginig purposes. */ static void eval_gamma(struct csa *csa, double gamma[]) { int m = csa->m; int n = csa->n; char *type = csa->type; int *head = csa->head; char *refsp = csa->refsp; double *alfa = csa->work3; double *h = csa->work3; int i, j, k; /* gamma[i] := eta[i] (or 1, if xB[i] is free) */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (type[k] == GLP_FR) gamma[i] = 1.0; else gamma[i] = (refsp[k] ? 1.0 : 0.0); } /* compute columns of the current simplex table */ for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* skip column, if xN[j] is not in C */ if (!refsp[k]) continue; #ifdef GLP_DEBUG /* set C must not contain fixed variables */ xassert(type[k] != GLP_FX); #endif /* construct the right-hand side vector h = - N[j] */ for (i = 1; i <= m; i++) h[i] = 0.0; if (k <= m) { /* N[j] is k-th column of submatrix I */ h[k] = -1.0; } else { /* N[j] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) h[A_ind[ptr]] = A_val[ptr]; } /* solve system B * alfa = h */ xassert(csa->valid); bfd_ftran(csa->bfd, alfa); /* gamma[i] := gamma[i] + alfa[i,j]^2 */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ if (type[k] != GLP_FR) gamma[i] += alfa[i] * alfa[i]; } } return; } /*********************************************************************** * chuzr - choose basic variable (row of the simplex table) * * This routine chooses basic variable xB[p] having largest weighted * bound violation: * * |r[p]| / sqrt(gamma[p]) = max |r[i]| / sqrt(gamma[i]), * i in I * * / lB[i] - beta[i], if beta[i] < lB[i] * | * r[i] = < 0, if lB[i] <= beta[i] <= uB[i] * | * \ uB[i] - beta[i], if beta[i] > uB[i] * * where beta[i] is primal value of xB[i] in the current basis, lB[i] * and uB[i] are lower and upper bounds of xB[i], I is a subset of * eligible basic variables, which significantly violates their bounds, * gamma[i] is the steepest edge coefficient. * * If |r[i]| is less than a specified tolerance, xB[i] is not included * in I and therefore ignored. * * If I is empty and no variable has been chosen, p is set to 0. */ static void chuzr(struct csa *csa, double tol_bnd) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; int *head = csa->head; double *bbar = csa->bbar; double *gamma = csa->gamma; int i, k, p; double delta, best, eps, ri, temp; /* nothing is chosen so far */ p = 0, delta = 0.0, best = 0.0; /* look through the list of basic variables */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* determine bound violation ri[i] */ ri = 0.0; if (type[k] == GLP_LO || type[k] == GLP_DB || type[k] == GLP_FX) { /* xB[i] has lower bound */ eps = tol_bnd * (1.0 + kappa * fabs(lb[k])); if (bbar[i] < lb[k] - eps) { /* and significantly violates it */ ri = lb[k] - bbar[i]; } } if (type[k] == GLP_UP || type[k] == GLP_DB || type[k] == GLP_FX) { /* xB[i] has upper bound */ eps = tol_bnd * (1.0 + kappa * fabs(ub[k])); if (bbar[i] > ub[k] + eps) { /* and significantly violates it */ ri = ub[k] - bbar[i]; } } /* if xB[i] is not eligible, skip it */ if (ri == 0.0) continue; /* xB[i] is eligible basic variable; choose one with largest weighted bound violation */ #ifdef GLP_DEBUG xassert(gamma[i] >= 0.0); #endif temp = gamma[i]; if (temp < DBL_EPSILON) temp = DBL_EPSILON; temp = (ri * ri) / temp; if (best < temp) p = i, delta = ri, best = temp; } /* store the index of basic variable xB[p] chosen and its change in the adjacent basis */ csa->p = p; csa->delta = delta; return; } #if 1 /* copied from primal */ /*********************************************************************** * eval_rho - compute pivot row of the inverse * * This routine computes the pivot (p-th) row of the inverse inv(B), * which corresponds to basic variable xB[p] chosen: * * rho = inv(B') * e[p], * * where B' is a matrix transposed to the current basis matrix, e[p] * is unity vector. */ static void eval_rho(struct csa *csa, double rho[]) { int m = csa->m; int p = csa->p; double *e = rho; int i; #ifdef GLP_DEBUG xassert(1 <= p && p <= m); #endif /* construct the right-hand side vector e[p] */ for (i = 1; i <= m; i++) e[i] = 0.0; e[p] = 1.0; /* solve system B'* rho = e[p] */ xassert(csa->valid); bfd_btran(csa->bfd, rho); return; } #endif #if 1 /* copied from primal */ /*********************************************************************** * refine_rho - refine pivot row of the inverse * * This routine refines the pivot row of the inverse inv(B) assuming * that it was previously computed by the routine eval_rho. */ static void refine_rho(struct csa *csa, double rho[]) { int m = csa->m; int p = csa->p; double *e = csa->work3; int i; #ifdef GLP_DEBUG xassert(1 <= p && p <= m); #endif /* construct the right-hand side vector e[p] */ for (i = 1; i <= m; i++) e[i] = 0.0; e[p] = 1.0; /* refine solution of B'* rho = e[p] */ refine_btran(csa, e, rho); return; } #endif #if 1 /* 06/IV-2009 */ /*********************************************************************** * eval_trow - compute pivot row of the simplex table * * This routine computes the pivot row of the simplex table, which * corresponds to basic variable xB[p] chosen. * * The pivot row is the following vector: * * trow = T'* e[p] = - N'* inv(B') * e[p] = - N' * rho, * * where rho is the pivot row of the inverse inv(B) previously computed * by the routine eval_rho. * * Note that elements of the pivot row corresponding to fixed non-basic * variables are not computed. * * NOTES * * Computing pivot row of the simplex table is one of the most time * consuming operations, and for some instances it may take more than * 50% of the total solution time. * * In the current implementation there are two routines to compute the * pivot row. The routine eval_trow1 computes elements of the pivot row * as inner products of columns of the matrix N and the vector rho; it * is used when the vector rho is relatively dense. The routine * eval_trow2 computes the pivot row as a linear combination of rows of * the matrix N; it is used when the vector rho is relatively sparse. */ static void eval_trow1(struct csa *csa, double rho[]) { int m = csa->m; int n = csa->n; int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; char *stat = csa->stat; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; int j, k, beg, end, ptr, nnz; double temp; /* compute the pivot row as inner products of columns of the matrix N and vector rho: trow[j] = - rho * N[j] */ nnz = 0; for (j = 1; j <= n; j++) { if (stat[j] == GLP_NS) { /* xN[j] is fixed */ trow_vec[j] = 0.0; continue; } k = head[m+j]; /* x[k] = xN[j] */ if (k <= m) { /* N[j] is k-th column of submatrix I */ temp = - rho[k]; } else { /* N[j] is (k-m)-th column of submatrix (-A) */ beg = A_ptr[k-m], end = A_ptr[k-m+1]; temp = 0.0; for (ptr = beg; ptr < end; ptr++) temp += rho[A_ind[ptr]] * A_val[ptr]; } if (temp != 0.0) trow_ind[++nnz] = j; trow_vec[j] = temp; } csa->trow_nnz = nnz; return; } static void eval_trow2(struct csa *csa, double rho[]) { int m = csa->m; int n = csa->n; int *AT_ptr = csa->AT_ptr; int *AT_ind = csa->AT_ind; double *AT_val = csa->AT_val; int *bind = csa->bind; char *stat = csa->stat; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; int i, j, beg, end, ptr, nnz; double temp; /* clear the pivot row */ for (j = 1; j <= n; j++) trow_vec[j] = 0.0; /* compute the pivot row as a linear combination of rows of the matrix N: trow = - rho[1] * N'[1] - ... - rho[m] * N'[m] */ for (i = 1; i <= m; i++) { temp = rho[i]; if (temp == 0.0) continue; /* trow := trow - rho[i] * N'[i] */ j = bind[i] - m; /* x[i] = xN[j] */ if (j >= 1 && stat[j] != GLP_NS) trow_vec[j] -= temp; beg = AT_ptr[i], end = AT_ptr[i+1]; for (ptr = beg; ptr < end; ptr++) { j = bind[m + AT_ind[ptr]] - m; /* x[k] = xN[j] */ if (j >= 1 && stat[j] != GLP_NS) trow_vec[j] += temp * AT_val[ptr]; } } /* construct sparse pattern of the pivot row */ nnz = 0; for (j = 1; j <= n; j++) { if (trow_vec[j] != 0.0) trow_ind[++nnz] = j; } csa->trow_nnz = nnz; return; } static void eval_trow(struct csa *csa, double rho[]) { int m = csa->m; int i, nnz; double dens; /* determine the density of the vector rho */ nnz = 0; for (i = 1; i <= m; i++) if (rho[i] != 0.0) nnz++; dens = (double)nnz / (double)m; if (dens >= 0.20) { /* rho is relatively dense */ eval_trow1(csa, rho); } else { /* rho is relatively sparse */ eval_trow2(csa, rho); } return; } #endif /*********************************************************************** * sort_trow - sort pivot row of the simplex table * * This routine reorders the list of non-zero elements of the pivot * row to put significant elements, whose magnitude is not less than * a specified tolerance, in front of the list, and stores the number * of significant elements in trow_num. */ static void sort_trow(struct csa *csa, double tol_piv) { #ifdef GLP_DEBUG int n = csa->n; char *stat = csa->stat; #endif int nnz = csa->trow_nnz; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; int j, num, pos; double big, eps, temp; /* compute infinity (maximum) norm of the row */ big = 0.0; for (pos = 1; pos <= nnz; pos++) { #ifdef GLP_DEBUG j = trow_ind[pos]; xassert(1 <= j && j <= n); xassert(stat[j] != GLP_NS); #endif temp = fabs(trow_vec[trow_ind[pos]]); if (big < temp) big = temp; } csa->trow_max = big; /* determine absolute pivot tolerance */ eps = tol_piv * (1.0 + 0.01 * big); /* move significant row components to the front of the list */ for (num = 0; num < nnz; ) { j = trow_ind[nnz]; if (fabs(trow_vec[j]) < eps) nnz--; else { num++; trow_ind[nnz] = trow_ind[num]; trow_ind[num] = j; } } csa->trow_num = num; return; } #ifdef GLP_LONG_STEP /* 07/IV-2009 */ static int ls_func(const void *p1_, const void *p2_) { const struct bkpt *p1 = p1_, *p2 = p2_; if (p1->t < p2->t) return -1; if (p1->t > p2->t) return +1; return 0; } static int ls_func1(const void *p1_, const void *p2_) { const struct bkpt *p1 = p1_, *p2 = p2_; if (p1->dz < p2->dz) return -1; if (p1->dz > p2->dz) return +1; return 0; } static void long_step(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; int *head = csa->head; char *stat = csa->stat; double *cbar = csa->cbar; double delta = csa->delta; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; int trow_num = csa->trow_num; struct bkpt *bkpt = csa->bkpt; int j, k, kk, nbps, pos; double alfa, s, slope, dzmax; /* delta > 0 means that xB[p] violates its lower bound, so to increase the dual objective lambdaB[p] must increase; delta < 0 means that xB[p] violates its upper bound, so to increase the dual objective lambdaB[p] must decrease */ /* s := sign(delta) */ s = (delta > 0.0 ? +1.0 : -1.0); /* determine breakpoints of the dual objective */ nbps = 0; for (pos = 1; pos <= trow_num; pos++) { j = trow_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); xassert(stat[j] != GLP_NS); #endif /* if there is free non-basic variable, switch to the standard ratio test */ if (stat[j] == GLP_NF) { nbps = 0; goto done; } /* lambdaN[j] = ... - alfa * t - ..., where t = s * lambdaB[i] is the dual ray parameter, t >= 0 */ alfa = s * trow_vec[j]; #ifdef GLP_DEBUG xassert(alfa != 0.0); xassert(stat[j] == GLP_NL || stat[j] == GLP_NU); #endif if (alfa > 0.0 && stat[j] == GLP_NL || alfa < 0.0 && stat[j] == GLP_NU) { /* either lambdaN[j] >= 0 (if stat = GLP_NL) and decreases or lambdaN[j] <= 0 (if stat = GLP_NU) and increases; in both cases we have a breakpoint */ nbps++; #ifdef GLP_DEBUG xassert(nbps <= n); #endif bkpt[nbps].j = j; bkpt[nbps].t = cbar[j] / alfa; /* if (stat[j] == GLP_NL && cbar[j] < 0.0 || stat[j] == GLP_NU && cbar[j] > 0.0) xprintf("%d %g\n", stat[j], cbar[j]); */ /* if t is negative, replace it by exact zero (see comments in the routine chuzc) */ if (bkpt[nbps].t < 0.0) bkpt[nbps].t = 0.0; } } /* if there are less than two breakpoints, switch to the standard ratio test */ if (nbps < 2) { nbps = 0; goto done; } /* sort breakpoints by ascending the dual ray parameter, t */ qsort(&bkpt[1], nbps, sizeof(struct bkpt), ls_func); /* determine last breakpoint, at which the dual objective still greater than at t = 0 */ dzmax = 0.0; slope = fabs(delta); /* initial slope */ for (kk = 1; kk <= nbps; kk++) { if (kk == 1) bkpt[kk].dz = 0.0 + slope * (bkpt[kk].t - 0.0); else bkpt[kk].dz = bkpt[kk-1].dz + slope * (bkpt[kk].t - bkpt[kk-1].t); if (dzmax < bkpt[kk].dz) dzmax = bkpt[kk].dz; else if (bkpt[kk].dz < 0.05 * (1.0 + dzmax)) { nbps = kk - 1; break; } j = bkpt[kk].j; k = head[m+j]; /* x[k] = xN[j] */ if (type[k] == GLP_DB) slope -= fabs(trow_vec[j]) * (ub[k] - lb[k]); else { nbps = kk; break; } } /* if there are less than two breakpoints, switch to the standard ratio test */ if (nbps < 2) { nbps = 0; goto done; } /* sort breakpoints by ascending the dual change, dz */ qsort(&bkpt[1], nbps, sizeof(struct bkpt), ls_func1); /* for (kk = 1; kk <= nbps; kk++) xprintf("%d; t = %g; dz = %g\n", kk, bkpt[kk].t, bkpt[kk].dz); */ done: csa->nbps = nbps; return; } #endif /*********************************************************************** * chuzc - choose non-basic variable (column of the simplex table) * * This routine chooses non-basic variable xN[q], which being entered * in the basis keeps dual feasibility of the basic solution. * * The parameter rtol is a relative tolerance used to relax zero bounds * of reduced costs of non-basic variables. If rtol = 0, the routine * implements the standard ratio test. Otherwise, if rtol > 0, the * routine implements Harris' two-pass ratio test. In the latter case * rtol should be about three times less than a tolerance used to check * dual feasibility. */ static void chuzc(struct csa *csa, double rtol) { #ifdef GLP_DEBUG int m = csa->m; int n = csa->n; #endif char *stat = csa->stat; double *cbar = csa->cbar; #ifdef GLP_DEBUG int p = csa->p; #endif double delta = csa->delta; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; int trow_num = csa->trow_num; int j, pos, q; double alfa, big, s, t, teta, tmax; #ifdef GLP_DEBUG xassert(1 <= p && p <= m); #endif /* delta > 0 means that xB[p] violates its lower bound and goes to it in the adjacent basis, so lambdaB[p] is increasing from its lower zero bound; delta < 0 means that xB[p] violates its upper bound and goes to it in the adjacent basis, so lambdaB[p] is decreasing from its upper zero bound */ #ifdef GLP_DEBUG xassert(delta != 0.0); #endif /* s := sign(delta) */ s = (delta > 0.0 ? +1.0 : -1.0); /*** FIRST PASS ***/ /* nothing is chosen so far */ q = 0, teta = DBL_MAX, big = 0.0; /* walk through significant elements of the pivot row */ for (pos = 1; pos <= trow_num; pos++) { j = trow_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); #endif alfa = s * trow_vec[j]; #ifdef GLP_DEBUG xassert(alfa != 0.0); #endif /* lambdaN[j] = ... - alfa * lambdaB[p] - ..., and due to s we need to consider only increasing lambdaB[p] */ if (alfa > 0.0) { /* lambdaN[j] is decreasing */ if (stat[j] == GLP_NL || stat[j] == GLP_NF) { /* lambdaN[j] has zero lower bound */ t = (cbar[j] + rtol) / alfa; } else { /* lambdaN[j] has no lower bound */ continue; } } else { /* lambdaN[j] is increasing */ if (stat[j] == GLP_NU || stat[j] == GLP_NF) { /* lambdaN[j] has zero upper bound */ t = (cbar[j] - rtol) / alfa; } else { /* lambdaN[j] has no upper bound */ continue; } } /* t is a change of lambdaB[p], on which lambdaN[j] reaches its zero bound (possibly relaxed); since the basic solution is assumed to be dual feasible, t has to be non-negative by definition; however, it may happen that lambdaN[j] slightly (i.e. within a tolerance) violates its zero bound, that leads to negative t; in the latter case, if xN[j] is chosen, negative t means that lambdaB[p] changes in wrong direction that may cause wrong results on updating reduced costs; thus, if t is negative, we should replace it by exact zero assuming that lambdaN[j] is exactly on its zero bound, and violation appears due to round-off errors */ if (t < 0.0) t = 0.0; /* apply minimal ratio test */ if (teta > t || teta == t && big < fabs(alfa)) q = j, teta = t, big = fabs(alfa); } /* the second pass is skipped in the following cases: */ /* if the standard ratio test is used */ if (rtol == 0.0) goto done; /* if no non-basic variable has been chosen on the first pass */ if (q == 0) goto done; /* if lambdaN[q] prevents lambdaB[p] from any change */ if (teta == 0.0) goto done; /*** SECOND PASS ***/ /* here tmax is a maximal change of lambdaB[p], on which the solution remains dual feasible within a tolerance */ #if 0 tmax = (1.0 + 10.0 * DBL_EPSILON) * teta; #else tmax = teta; #endif /* nothing is chosen so far */ q = 0, teta = DBL_MAX, big = 0.0; /* walk through significant elements of the pivot row */ for (pos = 1; pos <= trow_num; pos++) { j = trow_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); #endif alfa = s * trow_vec[j]; #ifdef GLP_DEBUG xassert(alfa != 0.0); #endif /* lambdaN[j] = ... - alfa * lambdaB[p] - ..., and due to s we need to consider only increasing lambdaB[p] */ if (alfa > 0.0) { /* lambdaN[j] is decreasing */ if (stat[j] == GLP_NL || stat[j] == GLP_NF) { /* lambdaN[j] has zero lower bound */ t = cbar[j] / alfa; } else { /* lambdaN[j] has no lower bound */ continue; } } else { /* lambdaN[j] is increasing */ if (stat[j] == GLP_NU || stat[j] == GLP_NF) { /* lambdaN[j] has zero upper bound */ t = cbar[j] / alfa; } else { /* lambdaN[j] has no upper bound */ continue; } } /* (see comments for the first pass) */ if (t < 0.0) t = 0.0; /* t is a change of lambdaB[p], on which lambdaN[j] reaches its zero (lower or upper) bound; if t <= tmax, all reduced costs can violate their zero bounds only within relaxation tolerance rtol, so we can choose non-basic variable having largest influence coefficient to avoid possible numerical instability */ if (t <= tmax && big < fabs(alfa)) q = j, teta = t, big = fabs(alfa); } /* something must be chosen on the second pass */ xassert(q != 0); done: /* store the index of non-basic variable xN[q] chosen */ csa->q = q; /* store reduced cost of xN[q] in the adjacent basis */ csa->new_dq = s * teta; return; } #if 1 /* copied from primal */ /*********************************************************************** * eval_tcol - compute pivot column of the simplex table * * This routine computes the pivot column of the simplex table, which * corresponds to non-basic variable xN[q] chosen. * * The pivot column is the following vector: * * tcol = T * e[q] = - inv(B) * N * e[q] = - inv(B) * N[q], * * where B is the current basis matrix, N[q] is a column of the matrix * (I|-A) corresponding to variable xN[q]. */ static void eval_tcol(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *head = csa->head; int q = csa->q; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; double *h = csa->tcol_vec; int i, k, nnz; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); #endif k = head[m+q]; /* x[k] = xN[q] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* construct the right-hand side vector h = - N[q] */ for (i = 1; i <= m; i++) h[i] = 0.0; if (k <= m) { /* N[q] is k-th column of submatrix I */ h[k] = -1.0; } else { /* N[q] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) h[A_ind[ptr]] = A_val[ptr]; } /* solve system B * tcol = h */ xassert(csa->valid); bfd_ftran(csa->bfd, tcol_vec); /* construct sparse pattern of the pivot column */ nnz = 0; for (i = 1; i <= m; i++) { if (tcol_vec[i] != 0.0) tcol_ind[++nnz] = i; } csa->tcol_nnz = nnz; return; } #endif #if 1 /* copied from primal */ /*********************************************************************** * refine_tcol - refine pivot column of the simplex table * * This routine refines the pivot column of the simplex table assuming * that it was previously computed by the routine eval_tcol. */ static void refine_tcol(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *head = csa->head; int q = csa->q; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; double *h = csa->work3; int i, k, nnz; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); #endif k = head[m+q]; /* x[k] = xN[q] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* construct the right-hand side vector h = - N[q] */ for (i = 1; i <= m; i++) h[i] = 0.0; if (k <= m) { /* N[q] is k-th column of submatrix I */ h[k] = -1.0; } else { /* N[q] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) h[A_ind[ptr]] = A_val[ptr]; } /* refine solution of B * tcol = h */ refine_ftran(csa, h, tcol_vec); /* construct sparse pattern of the pivot column */ nnz = 0; for (i = 1; i <= m; i++) { if (tcol_vec[i] != 0.0) tcol_ind[++nnz] = i; } csa->tcol_nnz = nnz; return; } #endif /*********************************************************************** * update_cbar - update reduced costs of non-basic variables * * This routine updates reduced costs of all (except fixed) non-basic * variables for the adjacent basis. */ static void update_cbar(struct csa *csa) { #ifdef GLP_DEBUG int n = csa->n; #endif double *cbar = csa->cbar; int trow_nnz = csa->trow_nnz; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; int q = csa->q; double new_dq = csa->new_dq; int j, pos; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); #endif /* set new reduced cost of xN[q] */ cbar[q] = new_dq; /* update reduced costs of other non-basic variables */ if (new_dq == 0.0) goto done; for (pos = 1; pos <= trow_nnz; pos++) { j = trow_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); #endif if (j != q) cbar[j] -= trow_vec[j] * new_dq; } done: return; } /*********************************************************************** * update_bbar - update values of basic variables * * This routine updates values of all basic variables for the adjacent * basis. */ static void update_bbar(struct csa *csa) { #ifdef GLP_DEBUG int m = csa->m; int n = csa->n; #endif double *bbar = csa->bbar; int p = csa->p; double delta = csa->delta; int q = csa->q; int tcol_nnz = csa->tcol_nnz; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; int i, pos; double teta; #ifdef GLP_DEBUG xassert(1 <= p && p <= m); xassert(1 <= q && q <= n); #endif /* determine the change of xN[q] in the adjacent basis */ #ifdef GLP_DEBUG xassert(tcol_vec[p] != 0.0); #endif teta = delta / tcol_vec[p]; /* set new primal value of xN[q] */ bbar[p] = get_xN(csa, q) + teta; /* update primal values of other basic variables */ if (teta == 0.0) goto done; for (pos = 1; pos <= tcol_nnz; pos++) { i = tcol_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= i && i <= m); #endif if (i != p) bbar[i] += tcol_vec[i] * teta; } done: return; } /*********************************************************************** * update_gamma - update steepest edge coefficients * * This routine updates steepest-edge coefficients for the adjacent * basis. */ static void update_gamma(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif char *type = csa->type; int *head = csa->head; char *refsp = csa->refsp; double *gamma = csa->gamma; int p = csa->p; int trow_nnz = csa->trow_nnz; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; int q = csa->q; int tcol_nnz = csa->tcol_nnz; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; double *u = csa->work3; int i, j, k,pos; double gamma_p, eta_p, pivot, t, t1, t2; #ifdef GLP_DEBUG xassert(1 <= p && p <= m); xassert(1 <= q && q <= n); #endif /* the basis changes, so decrease the count */ xassert(csa->refct > 0); csa->refct--; /* recompute gamma[p] for the current basis more accurately and compute auxiliary vector u */ #ifdef GLP_DEBUG xassert(type[head[p]] != GLP_FR); #endif gamma_p = eta_p = (refsp[head[p]] ? 1.0 : 0.0); for (i = 1; i <= m; i++) u[i] = 0.0; for (pos = 1; pos <= trow_nnz; pos++) { j = trow_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); #endif k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); xassert(type[k] != GLP_FX); #endif if (!refsp[k]) continue; t = trow_vec[j]; gamma_p += t * t; /* u := u + N[j] * delta[j] * trow[j] */ if (k <= m) { /* N[k] = k-j stolbec submatrix I */ u[k] += t; } else { /* N[k] = k-m-k stolbec (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) u[A_ind[ptr]] -= t * A_val[ptr]; } } xassert(csa->valid); bfd_ftran(csa->bfd, u); /* update gamma[i] for other basic variables (except xB[p] and free variables) */ pivot = tcol_vec[p]; #ifdef GLP_DEBUG xassert(pivot != 0.0); #endif for (pos = 1; pos <= tcol_nnz; pos++) { i = tcol_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= i && i <= m); #endif k = head[i]; #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* skip xB[p] */ if (i == p) continue; /* skip free basic variable */ if (type[head[i]] == GLP_FR) { #ifdef GLP_DEBUG xassert(gamma[i] == 1.0); #endif continue; } /* compute gamma[i] for the adjacent basis */ t = tcol_vec[i] / pivot; t1 = gamma[i] + t * t * gamma_p + 2.0 * t * u[i]; t2 = (refsp[k] ? 1.0 : 0.0) + eta_p * t * t; gamma[i] = (t1 >= t2 ? t1 : t2); /* (though gamma[i] can be exact zero, because the reference space does not include non-basic fixed variables) */ if (gamma[i] < DBL_EPSILON) gamma[i] = DBL_EPSILON; } /* compute gamma[p] for the adjacent basis */ if (type[head[m+q]] == GLP_FR) gamma[p] = 1.0; else { gamma[p] = gamma_p / (pivot * pivot); if (gamma[p] < DBL_EPSILON) gamma[p] = DBL_EPSILON; } /* if xB[p], which becomes xN[q] in the adjacent basis, is fixed and belongs to the reference space, remove it from there, and change all gamma's appropriately */ k = head[p]; if (type[k] == GLP_FX && refsp[k]) { refsp[k] = 0; for (pos = 1; pos <= tcol_nnz; pos++) { i = tcol_ind[pos]; if (i == p) { if (type[head[m+q]] == GLP_FR) continue; t = 1.0 / tcol_vec[p]; } else { if (type[head[i]] == GLP_FR) continue; t = tcol_vec[i] / tcol_vec[p]; } gamma[i] -= t * t; if (gamma[i] < DBL_EPSILON) gamma[i] = DBL_EPSILON; } } return; } #if 1 /* copied from primal */ /*********************************************************************** * err_in_bbar - compute maximal relative error in primal solution * * This routine returns maximal relative error: * * max |beta[i] - bbar[i]| / (1 + |beta[i]|), * * where beta and bbar are, respectively, directly computed and the * current (updated) values of basic variables. * * NOTE: The routine is intended only for debugginig purposes. */ static double err_in_bbar(struct csa *csa) { int m = csa->m; double *bbar = csa->bbar; int i; double e, emax, *beta; beta = xcalloc(1+m, sizeof(double)); eval_beta(csa, beta); emax = 0.0; for (i = 1; i <= m; i++) { e = fabs(beta[i] - bbar[i]) / (1.0 + fabs(beta[i])); if (emax < e) emax = e; } xfree(beta); return emax; } #endif #if 1 /* copied from primal */ /*********************************************************************** * err_in_cbar - compute maximal relative error in dual solution * * This routine returns maximal relative error: * * max |cost[j] - cbar[j]| / (1 + |cost[j]|), * * where cost and cbar are, respectively, directly computed and the * current (updated) reduced costs of non-basic non-fixed variables. * * NOTE: The routine is intended only for debugginig purposes. */ static double err_in_cbar(struct csa *csa) { int m = csa->m; int n = csa->n; char *stat = csa->stat; double *cbar = csa->cbar; int j; double e, emax, cost, *pi; pi = xcalloc(1+m, sizeof(double)); eval_pi(csa, pi); emax = 0.0; for (j = 1; j <= n; j++) { if (stat[j] == GLP_NS) continue; cost = eval_cost(csa, pi, j); e = fabs(cost - cbar[j]) / (1.0 + fabs(cost)); if (emax < e) emax = e; } xfree(pi); return emax; } #endif /*********************************************************************** * err_in_gamma - compute maximal relative error in steepest edge cff. * * This routine returns maximal relative error: * * max |gamma'[j] - gamma[j]| / (1 + |gamma'[j]), * * where gamma'[j] and gamma[j] are, respectively, directly computed * and the current (updated) steepest edge coefficients for non-basic * non-fixed variable x[j]. * * NOTE: The routine is intended only for debugginig purposes. */ static double err_in_gamma(struct csa *csa) { int m = csa->m; char *type = csa->type; int *head = csa->head; double *gamma = csa->gamma; double *exact = csa->work4; int i; double e, emax, temp; eval_gamma(csa, exact); emax = 0.0; for (i = 1; i <= m; i++) { if (type[head[i]] == GLP_FR) { xassert(gamma[i] == 1.0); xassert(exact[i] == 1.0); continue; } temp = exact[i]; e = fabs(temp - gamma[i]) / (1.0 + fabs(temp)); if (emax < e) emax = e; } return emax; } /*********************************************************************** * change_basis - change basis header * * This routine changes the basis header to make it corresponding to * the adjacent basis. */ static void change_basis(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif char *type = csa->type; int *head = csa->head; #if 1 /* 06/IV-2009 */ int *bind = csa->bind; #endif char *stat = csa->stat; int p = csa->p; double delta = csa->delta; int q = csa->q; int k; /* xB[p] leaves the basis, xN[q] enters the basis */ #ifdef GLP_DEBUG xassert(1 <= p && p <= m); xassert(1 <= q && q <= n); #endif /* xB[p] <-> xN[q] */ k = head[p], head[p] = head[m+q], head[m+q] = k; #if 1 /* 06/IV-2009 */ bind[head[p]] = p, bind[head[m+q]] = m + q; #endif if (type[k] == GLP_FX) stat[q] = GLP_NS; else if (delta > 0.0) { #ifdef GLP_DEBUG xassert(type[k] == GLP_LO || type[k] == GLP_DB); #endif stat[q] = GLP_NL; } else /* delta < 0.0 */ { #ifdef GLP_DEBUG xassert(type[k] == GLP_UP || type[k] == GLP_DB); #endif stat[q] = GLP_NU; } return; } /*********************************************************************** * check_feas - check dual feasibility of basic solution * * If the current basic solution is dual feasible within a tolerance, * this routine returns zero, otherwise it returns non-zero. */ static int check_feas(struct csa *csa, double tol_dj) { int m = csa->m; int n = csa->n; char *orig_type = csa->orig_type; int *head = csa->head; double *cbar = csa->cbar; int j, k; for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (cbar[j] < - tol_dj) if (orig_type[k] == GLP_LO || orig_type[k] == GLP_FR) return 1; if (cbar[j] > + tol_dj) if (orig_type[k] == GLP_UP || orig_type[k] == GLP_FR) return 1; } return 0; } /*********************************************************************** * set_aux_bnds - assign auxiliary bounds to variables * * This routine assigns auxiliary bounds to variables to construct an * LP problem solved on phase I. */ static void set_aux_bnds(struct csa *csa) { int m = csa->m; int n = csa->n; char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; char *orig_type = csa->orig_type; int *head = csa->head; char *stat = csa->stat; double *cbar = csa->cbar; int j, k; for (k = 1; k <= m+n; k++) { switch (orig_type[k]) { case GLP_FR: #if 0 type[k] = GLP_DB, lb[k] = -1.0, ub[k] = +1.0; #else /* to force free variables to enter the basis */ type[k] = GLP_DB, lb[k] = -1e3, ub[k] = +1e3; #endif break; case GLP_LO: type[k] = GLP_DB, lb[k] = 0.0, ub[k] = +1.0; break; case GLP_UP: type[k] = GLP_DB, lb[k] = -1.0, ub[k] = 0.0; break; case GLP_DB: case GLP_FX: type[k] = GLP_FX, lb[k] = ub[k] = 0.0; break; default: xassert(orig_type != orig_type); } } for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (type[k] == GLP_FX) stat[j] = GLP_NS; else if (cbar[j] >= 0.0) stat[j] = GLP_NL; else stat[j] = GLP_NU; } return; } /*********************************************************************** * set_orig_bnds - restore original bounds of variables * * This routine restores original types and bounds of variables and * determines statuses of non-basic variables assuming that the current * basis is dual feasible. */ static void set_orig_bnds(struct csa *csa) { int m = csa->m; int n = csa->n; char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; char *orig_type = csa->orig_type; double *orig_lb = csa->orig_lb; double *orig_ub = csa->orig_ub; int *head = csa->head; char *stat = csa->stat; double *cbar = csa->cbar; int j, k; memcpy(&type[1], &orig_type[1], (m+n) * sizeof(char)); memcpy(&lb[1], &orig_lb[1], (m+n) * sizeof(double)); memcpy(&ub[1], &orig_ub[1], (m+n) * sizeof(double)); for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif switch (type[k]) { case GLP_FR: stat[j] = GLP_NF; break; case GLP_LO: stat[j] = GLP_NL; break; case GLP_UP: stat[j] = GLP_NU; break; case GLP_DB: if (cbar[j] >= +DBL_EPSILON) stat[j] = GLP_NL; else if (cbar[j] <= -DBL_EPSILON) stat[j] = GLP_NU; else if (fabs(lb[k]) <= fabs(ub[k])) stat[j] = GLP_NL; else stat[j] = GLP_NU; break; case GLP_FX: stat[j] = GLP_NS; break; default: xassert(type != type); } } return; } /*********************************************************************** * check_stab - check numerical stability of basic solution * * If the current basic solution is dual feasible within a tolerance, * this routine returns zero, otherwise it returns non-zero. */ static int check_stab(struct csa *csa, double tol_dj) { int n = csa->n; char *stat = csa->stat; double *cbar = csa->cbar; int j; for (j = 1; j <= n; j++) { if (cbar[j] < - tol_dj) if (stat[j] == GLP_NL || stat[j] == GLP_NF) return 1; if (cbar[j] > + tol_dj) if (stat[j] == GLP_NU || stat[j] == GLP_NF) return 1; } return 0; } #if 1 /* copied from primal */ /*********************************************************************** * eval_obj - compute original objective function * * This routine computes the current value of the original objective * function. */ static double eval_obj(struct csa *csa) { int m = csa->m; int n = csa->n; double *obj = csa->obj; int *head = csa->head; double *bbar = csa->bbar; int i, j, k; double sum; sum = obj[0]; /* walk through the list of basic variables */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k > m) sum += obj[k-m] * bbar[i]; } /* walk through the list of non-basic variables */ for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k > m) sum += obj[k-m] * get_xN(csa, j); } return sum; } #endif /*********************************************************************** * display - display the search progress * * This routine displays some information about the search progress. */ static void display(struct csa *csa, const glp_smcp *parm, int spec) { int m = csa->m; int n = csa->n; double *coef = csa->coef; char *orig_type = csa->orig_type; int *head = csa->head; char *stat = csa->stat; int phase = csa->phase; double *bbar = csa->bbar; double *cbar = csa->cbar; int i, j, cnt; double sum; if (parm->msg_lev < GLP_MSG_ON) goto skip; if (parm->out_dly > 0 && 1000.0 * xdifftime(xtime(), csa->tm_beg) < parm->out_dly) goto skip; if (csa->it_cnt == csa->it_dpy) goto skip; if (!spec && csa->it_cnt % parm->out_frq != 0) goto skip; /* compute the sum of dual infeasibilities */ sum = 0.0; if (phase == 1) { for (i = 1; i <= m; i++) sum -= coef[head[i]] * bbar[i]; for (j = 1; j <= n; j++) sum -= coef[head[m+j]] * get_xN(csa, j); } else { for (j = 1; j <= n; j++) { if (cbar[j] < 0.0) if (stat[j] == GLP_NL || stat[j] == GLP_NF) sum -= cbar[j]; if (cbar[j] > 0.0) if (stat[j] == GLP_NU || stat[j] == GLP_NF) sum += cbar[j]; } } /* determine the number of basic fixed variables */ cnt = 0; for (i = 1; i <= m; i++) if (orig_type[head[i]] == GLP_FX) cnt++; if (csa->phase == 1) xprintf(" %6d: %24s infeas = %10.3e (%d)\n", csa->it_cnt, "", sum, cnt); else xprintf("|%6d: obj = %17.9e infeas = %10.3e (%d)\n", csa->it_cnt, eval_obj(csa), sum, cnt); csa->it_dpy = csa->it_cnt; skip: return; } #if 1 /* copied from primal */ /*********************************************************************** * store_sol - store basic solution back to the problem object * * This routine stores basic solution components back to the problem * object. */ static void store_sol(struct csa *csa, glp_prob *lp, int p_stat, int d_stat, int ray) { int m = csa->m; int n = csa->n; double zeta = csa->zeta; int *head = csa->head; char *stat = csa->stat; double *bbar = csa->bbar; double *cbar = csa->cbar; int i, j, k; #ifdef GLP_DEBUG xassert(lp->m == m); xassert(lp->n == n); #endif /* basis factorization */ #ifdef GLP_DEBUG xassert(!lp->valid && lp->bfd == NULL); xassert(csa->valid && csa->bfd != NULL); #endif lp->valid = 1, csa->valid = 0; lp->bfd = csa->bfd, csa->bfd = NULL; memcpy(&lp->head[1], &head[1], m * sizeof(int)); /* basic solution status */ lp->pbs_stat = p_stat; lp->dbs_stat = d_stat; /* objective function value */ lp->obj_val = eval_obj(csa); /* simplex iteration count */ lp->it_cnt = csa->it_cnt; /* unbounded ray */ lp->some = ray; /* basic variables */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k <= m) { GLPROW *row = lp->row[k]; row->stat = GLP_BS; row->bind = i; row->prim = bbar[i] / row->rii; row->dual = 0.0; } else { GLPCOL *col = lp->col[k-m]; col->stat = GLP_BS; col->bind = i; col->prim = bbar[i] * col->sjj; col->dual = 0.0; } } /* non-basic variables */ for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k <= m) { GLPROW *row = lp->row[k]; row->stat = stat[j]; row->bind = 0; #if 0 row->prim = get_xN(csa, j) / row->rii; #else switch (stat[j]) { case GLP_NL: row->prim = row->lb; break; case GLP_NU: row->prim = row->ub; break; case GLP_NF: row->prim = 0.0; break; case GLP_NS: row->prim = row->lb; break; default: xassert(stat != stat); } #endif row->dual = (cbar[j] * row->rii) / zeta; } else { GLPCOL *col = lp->col[k-m]; col->stat = stat[j]; col->bind = 0; #if 0 col->prim = get_xN(csa, j) * col->sjj; #else switch (stat[j]) { case GLP_NL: col->prim = col->lb; break; case GLP_NU: col->prim = col->ub; break; case GLP_NF: col->prim = 0.0; break; case GLP_NS: col->prim = col->lb; break; default: xassert(stat != stat); } #endif col->dual = (cbar[j] / col->sjj) / zeta; } } return; } #endif /*********************************************************************** * free_csa - deallocate common storage area * * This routine frees all the memory allocated to arrays in the common * storage area (CSA). */ static void free_csa(struct csa *csa) { xfree(csa->type); xfree(csa->lb); xfree(csa->ub); xfree(csa->coef); xfree(csa->orig_type); xfree(csa->orig_lb); xfree(csa->orig_ub); xfree(csa->obj); xfree(csa->A_ptr); xfree(csa->A_ind); xfree(csa->A_val); #if 1 /* 06/IV-2009 */ xfree(csa->AT_ptr); xfree(csa->AT_ind); xfree(csa->AT_val); #endif xfree(csa->head); #if 1 /* 06/IV-2009 */ xfree(csa->bind); #endif xfree(csa->stat); #if 0 /* 06/IV-2009 */ xfree(csa->N_ptr); xfree(csa->N_len); xfree(csa->N_ind); xfree(csa->N_val); #endif xfree(csa->bbar); xfree(csa->cbar); xfree(csa->refsp); xfree(csa->gamma); xfree(csa->trow_ind); xfree(csa->trow_vec); #ifdef GLP_LONG_STEP /* 07/IV-2009 */ xfree(csa->bkpt); #endif xfree(csa->tcol_ind); xfree(csa->tcol_vec); xfree(csa->work1); xfree(csa->work2); xfree(csa->work3); xfree(csa->work4); xfree(csa); return; } /*********************************************************************** * spx_dual - core LP solver based on the dual simplex method * * SYNOPSIS * * #include "glpspx.h" * int spx_dual(glp_prob *lp, const glp_smcp *parm); * * DESCRIPTION * * The routine spx_dual is a core LP solver based on the two-phase dual * simplex method. * * RETURNS * * 0 LP instance has been successfully solved. * * GLP_EOBJLL * Objective lower limit has been reached (maximization). * * GLP_EOBJUL * Objective upper limit has been reached (minimization). * * GLP_EITLIM * Iteration limit has been exhausted. * * GLP_ETMLIM * Time limit has been exhausted. * * GLP_EFAIL * The solver failed to solve LP instance. */ int spx_dual(glp_prob *lp, const glp_smcp *parm) { struct csa *csa; int binv_st = 2; /* status of basis matrix factorization: 0 - invalid; 1 - just computed; 2 - updated */ int bbar_st = 0; /* status of primal values of basic variables: 0 - invalid; 1 - just computed; 2 - updated */ int cbar_st = 0; /* status of reduced costs of non-basic variables: 0 - invalid; 1 - just computed; 2 - updated */ int rigorous = 0; /* rigorous mode flag; this flag is used to enable iterative refinement on computing pivot rows and columns of the simplex table */ int check = 0; int p_stat, d_stat, ret; /* allocate and initialize the common storage area */ csa = alloc_csa(lp); init_csa(csa, lp); if (parm->msg_lev >= GLP_MSG_DBG) xprintf("Objective scale factor = %g\n", csa->zeta); loop: /* main loop starts here */ /* compute factorization of the basis matrix */ if (binv_st == 0) { ret = invert_B(csa); if (ret != 0) { if (parm->msg_lev >= GLP_MSG_ERR) { xprintf("Error: unable to factorize the basis matrix (%d" ")\n", ret); xprintf("Sorry, basis recovery procedure not implemented" " yet\n"); } xassert(!lp->valid && lp->bfd == NULL); lp->bfd = csa->bfd, csa->bfd = NULL; lp->pbs_stat = lp->dbs_stat = GLP_UNDEF; lp->obj_val = 0.0; lp->it_cnt = csa->it_cnt; lp->some = 0; ret = GLP_EFAIL; goto done; } csa->valid = 1; binv_st = 1; /* just computed */ /* invalidate basic solution components */ bbar_st = cbar_st = 0; } /* compute reduced costs of non-basic variables */ if (cbar_st == 0) { eval_cbar(csa); cbar_st = 1; /* just computed */ /* determine the search phase, if not determined yet */ if (csa->phase == 0) { if (check_feas(csa, 0.90 * parm->tol_dj) != 0) { /* current basic solution is dual infeasible */ /* start searching for dual feasible solution */ csa->phase = 1; set_aux_bnds(csa); } else { /* current basic solution is dual feasible */ /* start searching for optimal solution */ csa->phase = 2; set_orig_bnds(csa); } xassert(check_stab(csa, parm->tol_dj) == 0); /* some non-basic double-bounded variables might become fixed (on phase I) or vice versa (on phase II) */ #if 0 /* 06/IV-2009 */ build_N(csa); #endif csa->refct = 0; /* bounds of non-basic variables have been changed, so invalidate primal values */ bbar_st = 0; } /* make sure that the current basic solution remains dual feasible */ if (check_stab(csa, parm->tol_dj) != 0) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("Warning: numerical instability (dual simplex, p" "hase %s)\n", csa->phase == 1 ? "I" : "II"); #if 1 if (parm->meth == GLP_DUALP) { store_sol(csa, lp, GLP_UNDEF, GLP_UNDEF, 0); ret = GLP_EFAIL; goto done; } #endif /* restart the search */ csa->phase = 0; binv_st = 0; rigorous = 5; goto loop; } } xassert(csa->phase == 1 || csa->phase == 2); /* on phase I we do not need to wait until the current basic solution becomes primal feasible; it is sufficient to make sure that all reduced costs have correct signs */ if (csa->phase == 1 && check_feas(csa, parm->tol_dj) == 0) { /* the current basis is dual feasible; switch to phase II */ display(csa, parm, 1); csa->phase = 2; if (cbar_st != 1) { eval_cbar(csa); cbar_st = 1; } set_orig_bnds(csa); #if 0 /* 06/IV-2009 */ build_N(csa); #endif csa->refct = 0; bbar_st = 0; } /* compute primal values of basic variables */ if (bbar_st == 0) { eval_bbar(csa); if (csa->phase == 2) csa->bbar[0] = eval_obj(csa); bbar_st = 1; /* just computed */ } /* redefine the reference space, if required */ switch (parm->pricing) { case GLP_PT_STD: break; case GLP_PT_PSE: if (csa->refct == 0) reset_refsp(csa); break; default: xassert(parm != parm); } /* at this point the basis factorization and all basic solution components are valid */ xassert(binv_st && bbar_st && cbar_st); /* check accuracy of current basic solution components (only for debugging) */ if (check) { double e_bbar = err_in_bbar(csa); double e_cbar = err_in_cbar(csa); double e_gamma = (parm->pricing == GLP_PT_PSE ? err_in_gamma(csa) : 0.0); xprintf("e_bbar = %10.3e; e_cbar = %10.3e; e_gamma = %10.3e\n", e_bbar, e_cbar, e_gamma); xassert(e_bbar <= 1e-5 && e_cbar <= 1e-5 && e_gamma <= 1e-3); } /* if the objective has to be maximized, check if it has reached its lower limit */ if (csa->phase == 2 && csa->zeta < 0.0 && parm->obj_ll > -DBL_MAX && csa->bbar[0] <= parm->obj_ll) { if (bbar_st != 1 || cbar_st != 1) { if (bbar_st != 1) bbar_st = 0; if (cbar_st != 1) cbar_st = 0; goto loop; } display(csa, parm, 1); if (parm->msg_lev >= GLP_MSG_ALL) xprintf("OBJECTIVE LOWER LIMIT REACHED; SEARCH TERMINATED\n" ); store_sol(csa, lp, GLP_INFEAS, GLP_FEAS, 0); ret = GLP_EOBJLL; goto done; } /* if the objective has to be minimized, check if it has reached its upper limit */ if (csa->phase == 2 && csa->zeta > 0.0 && parm->obj_ul < +DBL_MAX && csa->bbar[0] >= parm->obj_ul) { if (bbar_st != 1 || cbar_st != 1) { if (bbar_st != 1) bbar_st = 0; if (cbar_st != 1) cbar_st = 0; goto loop; } display(csa, parm, 1); if (parm->msg_lev >= GLP_MSG_ALL) xprintf("OBJECTIVE UPPER LIMIT REACHED; SEARCH TERMINATED\n" ); store_sol(csa, lp, GLP_INFEAS, GLP_FEAS, 0); ret = GLP_EOBJUL; goto done; } /* check if the iteration limit has been exhausted */ if (parm->it_lim < INT_MAX && csa->it_cnt - csa->it_beg >= parm->it_lim) { if (csa->phase == 2 && bbar_st != 1 || cbar_st != 1) { if (csa->phase == 2 && bbar_st != 1) bbar_st = 0; if (cbar_st != 1) cbar_st = 0; goto loop; } display(csa, parm, 1); if (parm->msg_lev >= GLP_MSG_ALL) xprintf("ITERATION LIMIT EXCEEDED; SEARCH TERMINATED\n"); switch (csa->phase) { case 1: d_stat = GLP_INFEAS; set_orig_bnds(csa); eval_bbar(csa); break; case 2: d_stat = GLP_FEAS; break; default: xassert(csa != csa); } store_sol(csa, lp, GLP_INFEAS, d_stat, 0); ret = GLP_EITLIM; goto done; } /* check if the time limit has been exhausted */ if (parm->tm_lim < INT_MAX && 1000.0 * xdifftime(xtime(), csa->tm_beg) >= parm->tm_lim) { if (csa->phase == 2 && bbar_st != 1 || cbar_st != 1) { if (csa->phase == 2 && bbar_st != 1) bbar_st = 0; if (cbar_st != 1) cbar_st = 0; goto loop; } display(csa, parm, 1); if (parm->msg_lev >= GLP_MSG_ALL) xprintf("TIME LIMIT EXCEEDED; SEARCH TERMINATED\n"); switch (csa->phase) { case 1: d_stat = GLP_INFEAS; set_orig_bnds(csa); eval_bbar(csa); break; case 2: d_stat = GLP_FEAS; break; default: xassert(csa != csa); } store_sol(csa, lp, GLP_INFEAS, d_stat, 0); ret = GLP_ETMLIM; goto done; } /* display the search progress */ display(csa, parm, 0); /* choose basic variable xB[p] */ chuzr(csa, parm->tol_bnd); if (csa->p == 0) { if (bbar_st != 1 || cbar_st != 1) { if (bbar_st != 1) bbar_st = 0; if (cbar_st != 1) cbar_st = 0; goto loop; } display(csa, parm, 1); switch (csa->phase) { case 1: if (parm->msg_lev >= GLP_MSG_ALL) xprintf("PROBLEM HAS NO DUAL FEASIBLE SOLUTION\n"); set_orig_bnds(csa); eval_bbar(csa); p_stat = GLP_INFEAS, d_stat = GLP_NOFEAS; break; case 2: if (parm->msg_lev >= GLP_MSG_ALL) xprintf("OPTIMAL SOLUTION FOUND\n"); p_stat = d_stat = GLP_FEAS; break; default: xassert(csa != csa); } store_sol(csa, lp, p_stat, d_stat, 0); ret = 0; goto done; } /* compute pivot row of the simplex table */ { double *rho = csa->work4; eval_rho(csa, rho); if (rigorous) refine_rho(csa, rho); eval_trow(csa, rho); sort_trow(csa, parm->tol_bnd); } /* unlike primal simplex there is no need to check accuracy of the primal value of xB[p] (which might be computed using the pivot row), since bbar is a result of FTRAN */ #ifdef GLP_LONG_STEP /* 07/IV-2009 */ long_step(csa); if (csa->nbps > 0) { csa->q = csa->bkpt[csa->nbps].j; if (csa->delta > 0.0) csa->new_dq = + csa->bkpt[csa->nbps].t; else csa->new_dq = - csa->bkpt[csa->nbps].t; } else #endif /* choose non-basic variable xN[q] */ switch (parm->r_test) { case GLP_RT_STD: chuzc(csa, 0.0); break; case GLP_RT_HAR: chuzc(csa, 0.30 * parm->tol_dj); break; default: xassert(parm != parm); } if (csa->q == 0) { if (bbar_st != 1 || cbar_st != 1 || !rigorous) { if (bbar_st != 1) bbar_st = 0; if (cbar_st != 1) cbar_st = 0; rigorous = 1; goto loop; } display(csa, parm, 1); switch (csa->phase) { case 1: if (parm->msg_lev >= GLP_MSG_ERR) xprintf("Error: unable to choose basic variable on ph" "ase I\n"); xassert(!lp->valid && lp->bfd == NULL); lp->bfd = csa->bfd, csa->bfd = NULL; lp->pbs_stat = lp->dbs_stat = GLP_UNDEF; lp->obj_val = 0.0; lp->it_cnt = csa->it_cnt; lp->some = 0; ret = GLP_EFAIL; break; case 2: if (parm->msg_lev >= GLP_MSG_ALL) xprintf("PROBLEM HAS NO FEASIBLE SOLUTION\n"); store_sol(csa, lp, GLP_NOFEAS, GLP_FEAS, csa->head[csa->p]); ret = 0; break; default: xassert(csa != csa); } goto done; } /* check if the pivot element is acceptable */ { double piv = csa->trow_vec[csa->q]; double eps = 1e-5 * (1.0 + 0.01 * csa->trow_max); if (fabs(piv) < eps) { if (parm->msg_lev >= GLP_MSG_DBG) xprintf("piv = %.12g; eps = %g\n", piv, eps); if (!rigorous) { rigorous = 5; goto loop; } } } /* now xN[q] and xB[p] have been chosen anyhow */ /* compute pivot column of the simplex table */ eval_tcol(csa); if (rigorous) refine_tcol(csa); /* accuracy check based on the pivot element */ { double piv1 = csa->tcol_vec[csa->p]; /* more accurate */ double piv2 = csa->trow_vec[csa->q]; /* less accurate */ xassert(piv1 != 0.0); if (fabs(piv1 - piv2) > 1e-8 * (1.0 + fabs(piv1)) || !(piv1 > 0.0 && piv2 > 0.0 || piv1 < 0.0 && piv2 < 0.0)) { if (parm->msg_lev >= GLP_MSG_DBG) xprintf("piv1 = %.12g; piv2 = %.12g\n", piv1, piv2); if (binv_st != 1 || !rigorous) { if (binv_st != 1) binv_st = 0; rigorous = 5; goto loop; } /* (not a good idea; should be revised later) */ if (csa->tcol_vec[csa->p] == 0.0) { csa->tcol_nnz++; xassert(csa->tcol_nnz <= csa->m); csa->tcol_ind[csa->tcol_nnz] = csa->p; } csa->tcol_vec[csa->p] = piv2; } } /* update primal values of basic variables */ #ifdef GLP_LONG_STEP /* 07/IV-2009 */ if (csa->nbps > 0) { int kk, j, k; for (kk = 1; kk < csa->nbps; kk++) { if (csa->bkpt[kk].t >= csa->bkpt[csa->nbps].t) continue; j = csa->bkpt[kk].j; k = csa->head[csa->m + j]; xassert(csa->type[k] == GLP_DB); if (csa->stat[j] == GLP_NL) csa->stat[j] = GLP_NU; else csa->stat[j] = GLP_NL; } } bbar_st = 0; #else update_bbar(csa); if (csa->phase == 2) csa->bbar[0] += (csa->cbar[csa->q] / csa->zeta) * (csa->delta / csa->tcol_vec[csa->p]); bbar_st = 2; /* updated */ #endif /* update reduced costs of non-basic variables */ update_cbar(csa); cbar_st = 2; /* updated */ /* update steepest edge coefficients */ switch (parm->pricing) { case GLP_PT_STD: break; case GLP_PT_PSE: if (csa->refct > 0) update_gamma(csa); break; default: xassert(parm != parm); } /* update factorization of the basis matrix */ ret = update_B(csa, csa->p, csa->head[csa->m+csa->q]); if (ret == 0) binv_st = 2; /* updated */ else { csa->valid = 0; binv_st = 0; /* invalid */ } #if 0 /* 06/IV-2009 */ /* update matrix N */ del_N_col(csa, csa->q, csa->head[csa->m+csa->q]); if (csa->type[csa->head[csa->p]] != GLP_FX) add_N_col(csa, csa->q, csa->head[csa->p]); #endif /* change the basis header */ change_basis(csa); /* iteration complete */ csa->it_cnt++; if (rigorous > 0) rigorous--; goto loop; done: /* deallocate the common storage area */ free_csa(csa); /* return to the calling program */ return ret; } /* eof */ sources_5316/external/glpk/glpavl.h0000644000176700017670000001035611401660400016135 0ustar paulpaul/* glpavl.h (binary search tree) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPAVL_H #define GLPAVL_H #include "glpdmp.h" typedef struct AVL AVL; typedef struct AVLNODE AVLNODE; struct AVL { /* AVL tree (Adelson-Velsky & Landis binary search tree) */ DMP *pool; /* memory pool for allocating nodes */ AVLNODE *root; /* pointer to the root node */ int (*fcmp)(void *info, const void *key1, const void *key2); /* application-defined key comparison routine */ void *info; /* transit pointer passed to the routine fcmp */ int size; /* the tree size (the total number of nodes) */ int height; /* the tree height */ }; struct AVLNODE { /* node of AVL tree */ const void *key; /* pointer to the node key (data structure for representing keys is supplied by the application) */ int rank; /* node rank = relative position of the node in its own subtree = the number of nodes in the left subtree plus one */ int type; /* reserved for the application specific information */ void *link; /* reserved for the application specific information */ AVLNODE *up; /* pointer to the parent node */ short int flag; /* node flag: 0 - this node is the left child of its parent (or this node is the root of the tree and has no parent) 1 - this node is the right child of its parent */ short int bal; /* node balance = the difference between heights of the right and left subtrees: -1 - the left subtree is higher than the right one; 0 - the left and right subtrees have the same height; +1 - the left subtree is lower than the right one */ AVLNODE *left; /* pointer to the root of the left subtree */ AVLNODE *right; /* pointer to the root of the right subtree */ }; #define avl_create_tree _glp_avl_create_tree AVL *avl_create_tree(int (*fcmp)(void *info, const void *key1, const void *key2), void *info); /* create AVL tree */ #define avl_strcmp _glp_avl_strcmp int avl_strcmp(void *info, const void *key1, const void *key2); /* compare character string keys */ #define avl_insert_node _glp_avl_insert_node AVLNODE *avl_insert_node(AVL *tree, const void *key); /* insert new node into AVL tree */ #define avl_set_node_type _glp_avl_set_node_type void avl_set_node_type(AVLNODE *node, int type); /* assign the type field of specified node */ #define avl_set_node_link _glp_avl_set_node_link void avl_set_node_link(AVLNODE *node, void *link); /* assign the link field of specified node */ #define avl_find_node _glp_avl_find_node AVLNODE *avl_find_node(AVL *tree, const void *key); /* find node in AVL tree */ #define avl_get_node_type _glp_avl_get_node_type int avl_get_node_type(AVLNODE *node); /* retrieve the type field of specified node */ #define avl_get_node_link _glp_avl_get_node_link void *avl_get_node_link(AVLNODE *node); /* retrieve the link field of specified node */ #define avl_delete_node _glp_avl_delete_node void avl_delete_node(AVL *tree, AVLNODE *node); /* delete specified node from AVL tree */ #define avl_delete_tree _glp_avl_delete_tree void avl_delete_tree(AVL *tree); /* delete AVL tree */ #endif /* eof */ sources_5316/external/glpk/glpenv06.c0000644000176700017670000001116311401660400016301 0ustar paulpaul/* glpenv06.c (standard time) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifdef HAVE_CONFIG_H #include #endif #include "glpapi.h" /*********************************************************************** * NAME * * glp_time - determine current universal time * * SYNOPSIS * * glp_long glp_time(void); * * RETURNS * * The routine glp_time returns the current universal time (UTC), in * milliseconds, elapsed since 00:00:00 GMT January 1, 1970. */ static const int epoch = 2440588; /* = jday(1, 1, 1970) */ /* POSIX version ******************************************************/ #if defined(HAVE_SYS_TIME_H) && defined(HAVE_GETTIMEOFDAY) #include #include glp_long glp_time(void) { struct timeval tv; struct tm *tm; glp_long t; int j; gettimeofday(&tv, NULL); tm = gmtime(&tv.tv_sec); j = jday(tm->tm_mday, tm->tm_mon + 1, 1900 + tm->tm_year); xassert(j >= 0); t = xlset(j - epoch); t = xlmul(t, xlset(24)); t = xladd(t, xlset(tm->tm_hour)); t = xlmul(t, xlset(60)); t = xladd(t, xlset(tm->tm_min)); t = xlmul(t, xlset(60)); t = xladd(t, xlset(tm->tm_sec)); t = xlmul(t, xlset(1000)); t = xladd(t, xlset(tv.tv_usec / 1000)); return t; } /* Windows version ****************************************************/ #elif defined(__WOE__) #include glp_long glp_time(void) { SYSTEMTIME st; glp_long t; int j; GetSystemTime(&st); j = jday(st.wDay, st.wMonth, st.wYear); xassert(j >= 0); t = xlset(j - epoch); t = xlmul(t, xlset(24)); t = xladd(t, xlset(st.wHour)); t = xlmul(t, xlset(60)); t = xladd(t, xlset(st.wMinute)); t = xlmul(t, xlset(60)); t = xladd(t, xlset(st.wSecond)); t = xlmul(t, xlset(1000)); t = xladd(t, xlset(st.wMilliseconds)); return t; } /* portable ISO C version *********************************************/ #else #include glp_long glp_time(void) { time_t timer; struct tm *tm; glp_long t; int j; timer = time(NULL); tm = gmtime(&timer); j = jday(tm->tm_mday, tm->tm_mon + 1, 1900 + tm->tm_year); xassert(j >= 0); t = xlset(j - epoch); t = xlmul(t, xlset(24)); t = xladd(t, xlset(tm->tm_hour)); t = xlmul(t, xlset(60)); t = xladd(t, xlset(tm->tm_min)); t = xlmul(t, xlset(60)); t = xladd(t, xlset(tm->tm_sec)); t = xlmul(t, xlset(1000)); return t; } #endif /*********************************************************************** * NAME * * glp_difftime - compute difference between two time values * * SYNOPSIS * * double glp_difftime(glp_long t1, glp_long t0); * * RETURNS * * The routine glp_difftime returns the difference between two time * values t1 and t0, expressed in seconds. */ double glp_difftime(glp_long t1, glp_long t0) { return xltod(xlsub(t1, t0)) / 1000.0; } /**********************************************************************/ #if 0 int main(void) { glp_long t; glp_ldiv d; int ttt, ss, mm, hh, day, month, year; char s[50]; t = glp_time(); xprintf("t = %s\n", xltoa(t, s)); d = xldiv(t, xlset(1000)); ttt = d.rem.lo, t = d.quot; d = xldiv(t, xlset(60)); ss = d.rem.lo, t = d.quot; d = xldiv(t, xlset(60)); mm = d.rem.lo, t = d.quot; d = xldiv(t, xlset(24)); hh = d.rem.lo, t = d.quot; xassert(jdate(t.lo + epoch, &day, &month, &year) == 0); xprintf("%04d-%02d-%02d %02d:%02d:%02d.%03d\n", year, month, day, hh, mm, ss, ttt); return 0; } #endif /* eof */ sources_5316/external/glpk/glpapi09.c0000644000176700017670000005754411401660400016302 0ustar paulpaul/* glpapi09.c (mixed integer programming routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" #include "glpnpp.h" /*********************************************************************** * NAME * * glp_set_col_kind - set (change) column kind * * SYNOPSIS * * void glp_set_col_kind(glp_prob *mip, int j, int kind); * * DESCRIPTION * * The routine glp_set_col_kind sets (changes) the kind of j-th column * (structural variable) as specified by the parameter kind: * * GLP_CV - continuous variable; * GLP_IV - integer variable; * GLP_BV - binary variable. */ void glp_set_col_kind(glp_prob *mip, int j, int kind) { GLPCOL *col; if (!(1 <= j && j <= mip->n)) xerror("glp_set_col_kind: j = %d; column number out of range\n" , j); col = mip->col[j]; switch (kind) { case GLP_CV: col->kind = GLP_CV; break; case GLP_IV: col->kind = GLP_IV; break; case GLP_BV: col->kind = GLP_IV; if (!(col->type == GLP_DB && col->lb == 0.0 && col->ub == 1.0)) glp_set_col_bnds(mip, j, GLP_DB, 0.0, 1.0); break; default: xerror("glp_set_col_kind: j = %d; kind = %d; invalid column" " kind\n", j, kind); } return; } /*********************************************************************** * NAME * * glp_get_col_kind - retrieve column kind * * SYNOPSIS * * int glp_get_col_kind(glp_prob *mip, int j); * * RETURNS * * The routine glp_get_col_kind returns the kind of j-th column, i.e. * the kind of corresponding structural variable, as follows: * * GLP_CV - continuous variable; * GLP_IV - integer variable; * GLP_BV - binary variable */ int glp_get_col_kind(glp_prob *mip, int j) { GLPCOL *col; int kind; if (!(1 <= j && j <= mip->n)) xerror("glp_get_col_kind: j = %d; column number out of range\n" , j); col = mip->col[j]; kind = col->kind; switch (kind) { case GLP_CV: break; case GLP_IV: if (col->type == GLP_DB && col->lb == 0.0 && col->ub == 1.0) kind = GLP_BV; break; default: xassert(kind != kind); } return kind; } /*********************************************************************** * NAME * * glp_get_num_int - retrieve number of integer columns * * SYNOPSIS * * int glp_get_num_int(glp_prob *mip); * * RETURNS * * The routine glp_get_num_int returns the current number of columns, * which are marked as integer. */ int glp_get_num_int(glp_prob *mip) { GLPCOL *col; int j, count = 0; for (j = 1; j <= mip->n; j++) { col = mip->col[j]; if (col->kind == GLP_IV) count++; } return count; } /*********************************************************************** * NAME * * glp_get_num_bin - retrieve number of binary columns * * SYNOPSIS * * int glp_get_num_bin(glp_prob *mip); * * RETURNS * * The routine glp_get_num_bin returns the current number of columns, * which are marked as binary. */ int glp_get_num_bin(glp_prob *mip) { GLPCOL *col; int j, count = 0; for (j = 1; j <= mip->n; j++) { col = mip->col[j]; if (col->kind == GLP_IV && col->type == GLP_DB && col->lb == 0.0 && col->ub == 1.0) count++; } return count; } /*********************************************************************** * NAME * * glp_intopt - solve MIP problem with the branch-and-bound method * * SYNOPSIS * * int glp_intopt(glp_prob *P, const glp_iocp *parm); * * DESCRIPTION * * The routine glp_intopt is a driver to the MIP solver based on the * branch-and-bound method. * * On entry the problem object should contain optimal solution to LP * relaxation (which can be obtained with the routine glp_simplex). * * The MIP solver has a set of control parameters. Values of the control * parameters can be passed in a structure glp_iocp, which the parameter * parm points to. * * The parameter parm can be specified as NULL, in which case the MIP * solver uses default settings. * * RETURNS * * 0 The MIP problem instance has been successfully solved. This code * does not necessarily mean that the solver has found optimal * solution. It only means that the solution process was successful. * * GLP_EBOUND * Unable to start the search, because some double-bounded variables * have incorrect bounds or some integer variables have non-integer * (fractional) bounds. * * GLP_EROOT * Unable to start the search, because optimal basis for initial LP * relaxation is not provided. * * GLP_EFAIL * The search was prematurely terminated due to the solver failure. * * GLP_EMIPGAP * The search was prematurely terminated, because the relative mip * gap tolerance has been reached. * * GLP_ETMLIM * The search was prematurely terminated, because the time limit has * been exceeded. * * GLP_ENOPFS * The MIP problem instance has no primal feasible solution (only if * the MIP presolver is used). * * GLP_ENODFS * LP relaxation of the MIP problem instance has no dual feasible * solution (only if the MIP presolver is used). * * GLP_ESTOP * The search was prematurely terminated by application. */ static int solve_mip(glp_prob *P, const glp_iocp *parm) { /* solve MIP directly without using the preprocessor */ glp_tree *T; int ret; /* optimal basis to LP relaxation must be provided */ if (glp_get_status(P) != GLP_OPT) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_intopt: optimal basis to initial LP relaxation" " not provided\n"); ret = GLP_EROOT; goto done; } /* it seems all is ok */ if (parm->msg_lev >= GLP_MSG_ALL) xprintf("Integer optimization begins...\n"); /* create the branch-and-bound tree */ T = ios_create_tree(P, parm); /* solve the problem instance */ ret = ios_driver(T); /* delete the branch-and-bound tree */ ios_delete_tree(T); /* analyze exit code reported by the mip driver */ if (ret == 0) { if (P->mip_stat == GLP_FEAS) { if (parm->msg_lev >= GLP_MSG_ALL) xprintf("INTEGER OPTIMAL SOLUTION FOUND\n"); P->mip_stat = GLP_OPT; } else { if (parm->msg_lev >= GLP_MSG_ALL) xprintf("PROBLEM HAS NO INTEGER FEASIBLE SOLUTION\n"); P->mip_stat = GLP_NOFEAS; } } else if (ret == GLP_EMIPGAP) { if (parm->msg_lev >= GLP_MSG_ALL) xprintf("RELATIVE MIP GAP TOLERANCE REACHED; SEARCH TERMINA" "TED\n"); } else if (ret == GLP_ETMLIM) { if (parm->msg_lev >= GLP_MSG_ALL) xprintf("TIME LIMIT EXCEEDED; SEARCH TERMINATED\n"); } else if (ret == GLP_EFAIL) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_intopt: cannot solve current LP relaxation\n"); } else if (ret == GLP_ESTOP) { if (parm->msg_lev >= GLP_MSG_ALL) xprintf("SEARCH TERMINATED BY APPLICATION\n"); } else xassert(ret != ret); done: return ret; } static int preprocess_and_solve_mip(glp_prob *P, const glp_iocp *parm) { /* solve MIP using the preprocessor */ ENV *env = get_env_ptr(); int term_out = env->term_out; NPP *npp; glp_prob *mip = NULL; glp_bfcp bfcp; glp_smcp smcp; int ret; if (parm->msg_lev >= GLP_MSG_ALL) xprintf("Preprocessing...\n"); /* create preprocessor workspace */ npp = npp_create_wksp(); /* load original problem into the preprocessor workspace */ npp_load_prob(npp, P, GLP_OFF, GLP_MIP, GLP_OFF); /* process MIP prior to applying the branch-and-bound method */ if (!term_out || parm->msg_lev < GLP_MSG_ALL) env->term_out = GLP_OFF; else env->term_out = GLP_ON; ret = npp_integer(npp, parm); env->term_out = term_out; if (ret == 0) ; else if (ret == GLP_ENOPFS) { if (parm->msg_lev >= GLP_MSG_ALL) xprintf("PROBLEM HAS NO PRIMAL FEASIBLE SOLUTION\n"); } else if (ret == GLP_ENODFS) { if (parm->msg_lev >= GLP_MSG_ALL) xprintf("LP RELAXATION HAS NO DUAL FEASIBLE SOLUTION\n"); } else xassert(ret != ret); if (ret != 0) goto done; /* build transformed MIP */ mip = glp_create_prob(); npp_build_prob(npp, mip); /* if the transformed MIP is empty, it has empty solution, which is optimal */ if (mip->m == 0 && mip->n == 0) { mip->mip_stat = GLP_OPT; mip->mip_obj = mip->c0; if (parm->msg_lev >= GLP_MSG_ALL) { xprintf("Objective value = %17.9e\n", mip->mip_obj); xprintf("INTEGER OPTIMAL SOLUTION FOUND BY MIP PREPROCESSOR" "\n"); } goto post; } /* display some statistics */ if (parm->msg_lev >= GLP_MSG_ALL) { int ni = glp_get_num_int(mip); int nb = glp_get_num_bin(mip); char s[50]; xprintf("%d row%s, %d column%s, %d non-zero%s\n", mip->m, mip->m == 1 ? "" : "s", mip->n, mip->n == 1 ? "" : "s", mip->nnz, mip->nnz == 1 ? "" : "s"); if (nb == 0) strcpy(s, "none of"); else if (ni == 1 && nb == 1) strcpy(s, ""); else if (nb == 1) strcpy(s, "one of"); else if (nb == ni) strcpy(s, "all of"); else sprintf(s, "%d of", nb); xprintf("%d integer variable%s, %s which %s binary\n", ni, ni == 1 ? "" : "s", s, nb == 1 ? "is" : "are"); } /* inherit basis factorization control parameters */ glp_get_bfcp(P, &bfcp); glp_set_bfcp(mip, &bfcp); /* scale the transformed problem */ if (!term_out || parm->msg_lev < GLP_MSG_ALL) env->term_out = GLP_OFF; else env->term_out = GLP_ON; glp_scale_prob(mip, GLP_SF_GM | GLP_SF_EQ | GLP_SF_2N | GLP_SF_SKIP); env->term_out = term_out; /* build advanced initial basis */ if (!term_out || parm->msg_lev < GLP_MSG_ALL) env->term_out = GLP_OFF; else env->term_out = GLP_ON; glp_adv_basis(mip, 0); env->term_out = term_out; /* solve initial LP relaxation */ if (parm->msg_lev >= GLP_MSG_ALL) xprintf("Solving LP relaxation...\n"); glp_init_smcp(&smcp); smcp.msg_lev = parm->msg_lev; mip->it_cnt = P->it_cnt; ret = glp_simplex(mip, &smcp); P->it_cnt = mip->it_cnt; if (ret != 0) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_intopt: cannot solve LP relaxation\n"); ret = GLP_EFAIL; goto done; } /* check status of the basic solution */ ret = glp_get_status(mip); if (ret == GLP_OPT) ret = 0; else if (ret == GLP_NOFEAS) ret = GLP_ENOPFS; else if (ret == GLP_UNBND) ret = GLP_ENODFS; else xassert(ret != ret); if (ret != 0) goto done; /* solve the transformed MIP */ mip->it_cnt = P->it_cnt; ret = solve_mip(mip, parm); P->it_cnt = mip->it_cnt; /* only integer feasible solution can be postprocessed */ if (!(mip->mip_stat == GLP_OPT || mip->mip_stat == GLP_FEAS)) { P->mip_stat = mip->mip_stat; goto done; } /* postprocess solution from the transformed MIP */ post: npp_postprocess(npp, mip); /* the transformed MIP is no longer needed */ glp_delete_prob(mip), mip = NULL; /* store solution to the original problem */ npp_unload_sol(npp, P); done: /* delete the transformed MIP, if it exists */ if (mip != NULL) glp_delete_prob(mip); /* delete preprocessor workspace */ npp_delete_wksp(npp); return ret; } #ifndef HAVE_ALIEN_SOLVER /* 28/V-2010 */ int _glp_intopt1(glp_prob *P, const glp_iocp *parm) { xassert(P == P); xassert(parm == parm); xprintf("glp_intopt: no alien solver is available\n"); return GLP_EFAIL; } #endif int glp_intopt(glp_prob *P, const glp_iocp *parm) { /* solve MIP problem with the branch-and-bound method */ glp_iocp _parm; int i, j, ret; /* check problem object */ if (P == NULL || P->magic != GLP_PROB_MAGIC) xerror("glp_intopt: P = %p; invalid problem object\n", P); if (P->tree != NULL) xerror("glp_intopt: operation not allowed\n"); /* check control parameters */ if (parm == NULL) parm = &_parm, glp_init_iocp((glp_iocp *)parm); if (!(parm->msg_lev == GLP_MSG_OFF || parm->msg_lev == GLP_MSG_ERR || parm->msg_lev == GLP_MSG_ON || parm->msg_lev == GLP_MSG_ALL || parm->msg_lev == GLP_MSG_DBG)) xerror("glp_intopt: msg_lev = %d; invalid parameter\n", parm->msg_lev); if (!(parm->br_tech == GLP_BR_FFV || parm->br_tech == GLP_BR_LFV || parm->br_tech == GLP_BR_MFV || parm->br_tech == GLP_BR_DTH || parm->br_tech == GLP_BR_PCH)) xerror("glp_intopt: br_tech = %d; invalid parameter\n", parm->br_tech); if (!(parm->bt_tech == GLP_BT_DFS || parm->bt_tech == GLP_BT_BFS || parm->bt_tech == GLP_BT_BLB || parm->bt_tech == GLP_BT_BPH)) xerror("glp_intopt: bt_tech = %d; invalid parameter\n", parm->bt_tech); if (!(0.0 < parm->tol_int && parm->tol_int < 1.0)) xerror("glp_intopt: tol_int = %g; invalid parameter\n", parm->tol_int); if (!(0.0 < parm->tol_obj && parm->tol_obj < 1.0)) xerror("glp_intopt: tol_obj = %g; invalid parameter\n", parm->tol_obj); if (parm->tm_lim < 0) xerror("glp_intopt: tm_lim = %d; invalid parameter\n", parm->tm_lim); if (parm->out_frq < 0) xerror("glp_intopt: out_frq = %d; invalid parameter\n", parm->out_frq); if (parm->out_dly < 0) xerror("glp_intopt: out_dly = %d; invalid parameter\n", parm->out_dly); if (!(0 <= parm->cb_size && parm->cb_size <= 256)) xerror("glp_intopt: cb_size = %d; invalid parameter\n", parm->cb_size); if (!(parm->pp_tech == GLP_PP_NONE || parm->pp_tech == GLP_PP_ROOT || parm->pp_tech == GLP_PP_ALL)) xerror("glp_intopt: pp_tech = %d; invalid parameter\n", parm->pp_tech); if (parm->mip_gap < 0.0) xerror("glp_intopt: mip_gap = %g; invalid parameter\n", parm->mip_gap); if (!(parm->mir_cuts == GLP_ON || parm->mir_cuts == GLP_OFF)) xerror("glp_intopt: mir_cuts = %d; invalid parameter\n", parm->mir_cuts); if (!(parm->gmi_cuts == GLP_ON || parm->gmi_cuts == GLP_OFF)) xerror("glp_intopt: gmi_cuts = %d; invalid parameter\n", parm->gmi_cuts); if (!(parm->cov_cuts == GLP_ON || parm->cov_cuts == GLP_OFF)) xerror("glp_intopt: cov_cuts = %d; invalid parameter\n", parm->cov_cuts); if (!(parm->clq_cuts == GLP_ON || parm->clq_cuts == GLP_OFF)) xerror("glp_intopt: clq_cuts = %d; invalid parameter\n", parm->clq_cuts); if (!(parm->presolve == GLP_ON || parm->presolve == GLP_OFF)) xerror("glp_intopt: presolve = %d; invalid parameter\n", parm->presolve); if (!(parm->binarize == GLP_ON || parm->binarize == GLP_OFF)) xerror("glp_intopt: binarize = %d; invalid parameter\n", parm->binarize); if (!(parm->fp_heur == GLP_ON || parm->fp_heur == GLP_OFF)) xerror("glp_intopt: fp_heur = %d; invalid parameter\n", parm->fp_heur); #if 1 /* 28/V-2010 */ if (!(parm->alien == GLP_ON || parm->alien == GLP_OFF)) xerror("glp_intopt: alien = %d; invalid parameter\n", parm->alien); #endif /* integer solution is currently undefined */ P->mip_stat = GLP_UNDEF; P->mip_obj = 0.0; /* check bounds of double-bounded variables */ for (i = 1; i <= P->m; i++) { GLPROW *row = P->row[i]; if (row->type == GLP_DB && row->lb >= row->ub) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_intopt: row %d: lb = %g, ub = %g; incorrect" " bounds\n", i, row->lb, row->ub); ret = GLP_EBOUND; goto done; } } for (j = 1; j <= P->n; j++) { GLPCOL *col = P->col[j]; if (col->type == GLP_DB && col->lb >= col->ub) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_intopt: column %d: lb = %g, ub = %g; incorr" "ect bounds\n", j, col->lb, col->ub); ret = GLP_EBOUND; goto done; } } /* bounds of all integer variables must be integral */ for (j = 1; j <= P->n; j++) { GLPCOL *col = P->col[j]; if (col->kind != GLP_IV) continue; if (col->type == GLP_LO || col->type == GLP_DB) { if (col->lb != floor(col->lb)) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_intopt: integer column %d has non-intege" "r lower bound %g\n", j, col->lb); ret = GLP_EBOUND; goto done; } } if (col->type == GLP_UP || col->type == GLP_DB) { if (col->ub != floor(col->ub)) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_intopt: integer column %d has non-intege" "r upper bound %g\n", j, col->ub); ret = GLP_EBOUND; goto done; } } if (col->type == GLP_FX) { if (col->lb != floor(col->lb)) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_intopt: integer column %d has non-intege" "r fixed value %g\n", j, col->lb); ret = GLP_EBOUND; goto done; } } } /* solve MIP problem */ if (parm->msg_lev >= GLP_MSG_ALL) { int ni = glp_get_num_int(P); int nb = glp_get_num_bin(P); char s[50]; xprintf("GLPK Integer Optimizer, v%s\n", glp_version()); xprintf("%d row%s, %d column%s, %d non-zero%s\n", P->m, P->m == 1 ? "" : "s", P->n, P->n == 1 ? "" : "s", P->nnz, P->nnz == 1 ? "" : "s"); if (nb == 0) strcpy(s, "none of"); else if (ni == 1 && nb == 1) strcpy(s, ""); else if (nb == 1) strcpy(s, "one of"); else if (nb == ni) strcpy(s, "all of"); else sprintf(s, "%d of", nb); xprintf("%d integer variable%s, %s which %s binary\n", ni, ni == 1 ? "" : "s", s, nb == 1 ? "is" : "are"); } #if 1 /* 28/V-2010 */ if (parm->alien) { /* use alien integer optimizer */ ret = _glp_intopt1(P, parm); goto done; } #endif if (!parm->presolve) ret = solve_mip(P, parm); else ret = preprocess_and_solve_mip(P, parm); done: /* return to the application program */ return ret; } /*********************************************************************** * NAME * * glp_init_iocp - initialize integer optimizer control parameters * * SYNOPSIS * * void glp_init_iocp(glp_iocp *parm); * * DESCRIPTION * * The routine glp_init_iocp initializes control parameters, which are * used by the integer optimizer, with default values. * * Default values of the control parameters are stored in a glp_iocp * structure, which the parameter parm points to. */ void glp_init_iocp(glp_iocp *parm) { parm->msg_lev = GLP_MSG_ALL; parm->br_tech = GLP_BR_DTH; parm->bt_tech = GLP_BT_BLB; parm->tol_int = 1e-5; parm->tol_obj = 1e-7; parm->tm_lim = INT_MAX; parm->out_frq = 5000; parm->out_dly = 10000; parm->cb_func = NULL; parm->cb_info = NULL; parm->cb_size = 0; parm->pp_tech = GLP_PP_ALL; parm->mip_gap = 0.0; parm->mir_cuts = GLP_OFF; parm->gmi_cuts = GLP_OFF; parm->cov_cuts = GLP_OFF; parm->clq_cuts = GLP_OFF; parm->presolve = GLP_OFF; parm->binarize = GLP_OFF; parm->fp_heur = GLP_OFF; #if 1 /* 28/V-2010 */ parm->alien = GLP_OFF; #endif return; } /*********************************************************************** * NAME * * glp_mip_status - retrieve status of MIP solution * * SYNOPSIS * * int glp_mip_status(glp_prob *mip); * * RETURNS * * The routine lpx_mip_status reports the status of MIP solution found * by the branch-and-bound solver as follows: * * GLP_UNDEF - MIP solution is undefined; * GLP_OPT - MIP solution is integer optimal; * GLP_FEAS - MIP solution is integer feasible but its optimality * (or non-optimality) has not been proven, perhaps due to * premature termination of the search; * GLP_NOFEAS - problem has no integer feasible solution (proven by the * solver). */ int glp_mip_status(glp_prob *mip) { int mip_stat = mip->mip_stat; return mip_stat; } /*********************************************************************** * NAME * * glp_mip_obj_val - retrieve objective value (MIP solution) * * SYNOPSIS * * double glp_mip_obj_val(glp_prob *mip); * * RETURNS * * The routine glp_mip_obj_val returns value of the objective function * for MIP solution. */ double glp_mip_obj_val(glp_prob *mip) { /*struct LPXCPS *cps = mip->cps;*/ double z; z = mip->mip_obj; /*if (cps->round && fabs(z) < 1e-9) z = 0.0;*/ return z; } /*********************************************************************** * NAME * * glp_mip_row_val - retrieve row value (MIP solution) * * SYNOPSIS * * double glp_mip_row_val(glp_prob *mip, int i); * * RETURNS * * The routine glp_mip_row_val returns value of the auxiliary variable * associated with i-th row. */ double glp_mip_row_val(glp_prob *mip, int i) { /*struct LPXCPS *cps = mip->cps;*/ double mipx; if (!(1 <= i && i <= mip->m)) xerror("glp_mip_row_val: i = %d; row number out of range\n", i) ; mipx = mip->row[i]->mipx; /*if (cps->round && fabs(mipx) < 1e-9) mipx = 0.0;*/ return mipx; } /*********************************************************************** * NAME * * glp_mip_col_val - retrieve column value (MIP solution) * * SYNOPSIS * * double glp_mip_col_val(glp_prob *mip, int j); * * RETURNS * * The routine glp_mip_col_val returns value of the structural variable * associated with j-th column. */ double glp_mip_col_val(glp_prob *mip, int j) { /*struct LPXCPS *cps = mip->cps;*/ double mipx; if (!(1 <= j && j <= mip->n)) xerror("glp_mip_col_val: j = %d; column number out of range\n", j); mipx = mip->col[j]->mipx; /*if (cps->round && fabs(mipx) < 1e-9) mipx = 0.0;*/ return mipx; } /* eof */ sources_5316/external/glpk/glpdmx.c0000644000176700017670000014303011401660400016132 0ustar paulpaul/* glpdmx.c (reading/writing data in DIMACS format) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_STDIO #include "glpapi.h" struct csa { /* common storage area */ jmp_buf jump; /* label for go to in case of error */ const char *fname; /* name of input text file */ XFILE *fp; /* stream assigned to input text file */ int count; /* line count */ int c; /* current character */ char field[255+1]; /* data field */ int empty; /* warning 'empty line ignored' was printed */ int nonint; /* warning 'non-integer data detected' was printed */ }; static void error(struct csa *csa, const char *fmt, ...) { /* print error message and terminate processing */ va_list arg; xprintf("%s:%d: error: ", csa->fname, csa->count); va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); xprintf("\n"); longjmp(csa->jump, 1); /* no return */ } static void warning(struct csa *csa, const char *fmt, ...) { /* print warning message and continue processing */ va_list arg; xprintf("%s:%d: warning: ", csa->fname, csa->count); va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); xprintf("\n"); return; } static void read_char(struct csa *csa) { /* read character from input text file */ int c; if (csa->c == '\n') csa->count++; c = xfgetc(csa->fp); if (c < 0) { if (xferror(csa->fp)) error(csa, "read error - %s", xerrmsg()); else if (csa->c == '\n') error(csa, "unexpected end of file"); else { warning(csa, "missing final end of line"); c = '\n'; } } else if (c == '\n') ; else if (isspace(c)) c = ' '; else if (iscntrl(c)) error(csa, "invalid control character 0x%02X", c); csa->c = c; return; } static void read_designator(struct csa *csa) { /* read one-character line designator */ xassert(csa->c == '\n'); read_char(csa); for (;;) { /* skip preceding white-space characters */ while (csa->c == ' ') read_char(csa); if (csa->c == '\n') { /* ignore empty line */ if (!csa->empty) { warning(csa, "empty line ignored"); csa->empty = 1; } read_char(csa); } else if (csa->c == 'c') { /* skip comment line */ while (csa->c != '\n') read_char(csa); read_char(csa); } else { /* hmm... looks like a line designator */ csa->field[0] = (char)csa->c, csa->field[1] = '\0'; /* check that it is followed by a white-space character */ read_char(csa); if (!(csa->c == ' ' || csa->c == '\n')) error(csa, "line designator missing or invalid"); break; } } return; } static void read_field(struct csa *csa) { /* read data field */ int len = 0; /* skip preceding white-space characters */ while (csa->c == ' ') read_char(csa); /* scan data field */ if (csa->c == '\n') error(csa, "unexpected end of line"); while (!(csa->c == ' ' || csa->c == '\n')) { if (len == sizeof(csa->field)-1) error(csa, "data field `%.15s...' too long", csa->field); csa->field[len++] = (char)csa->c; read_char(csa); } csa->field[len] = '\0'; return; } static void end_of_line(struct csa *csa) { /* skip white-space characters until end of line */ while (csa->c == ' ') read_char(csa); if (csa->c != '\n') error(csa, "too many data fields specified"); return; } static void check_int(struct csa *csa, double num) { /* print a warning if non-integer data are detected */ if (!csa->nonint && num != floor(num)) { warning(csa, "non-integer data detected"); csa->nonint = 1; } return; } /*********************************************************************** * NAME * * glp_read_mincost - read min-cost flow problem data in DIMACS format * * SYNOPSIS * * int glp_read_mincost(glp_graph *G, int v_rhs, int a_low, int a_cap, * int a_cost, const char *fname); * * DESCRIPTION * * The routine glp_read_mincost reads minimum cost flow problem data in * DIMACS format from a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_read_mincost(glp_graph *G, int v_rhs, int a_low, int a_cap, int a_cost, const char *fname) { struct csa _csa, *csa = &_csa; glp_vertex *v; glp_arc *a; int i, j, k, nv, na, ret = 0; double rhs, low, cap, cost; char *flag = NULL; if (v_rhs >= 0 && v_rhs > G->v_size - (int)sizeof(double)) xerror("glp_read_mincost: v_rhs = %d; invalid offset\n", v_rhs); if (a_low >= 0 && a_low > G->a_size - (int)sizeof(double)) xerror("glp_read_mincost: a_low = %d; invalid offset\n", a_low); if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_read_mincost: a_cap = %d; invalid offset\n", a_cap); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_read_mincost: a_cost = %d; invalid offset\n", a_cost); glp_erase_graph(G, G->v_size, G->a_size); if (setjmp(csa->jump)) { ret = 1; goto done; } csa->fname = fname; csa->fp = NULL; csa->count = 0; csa->c = '\n'; csa->field[0] = '\0'; csa->empty = csa->nonint = 0; xprintf("Reading min-cost flow problem data from `%s'...\n", fname); csa->fp = xfopen(fname, "r"); if (csa->fp == NULL) { xprintf("Unable to open `%s' - %s\n", fname, xerrmsg()); longjmp(csa->jump, 1); } /* read problem line */ read_designator(csa); if (strcmp(csa->field, "p") != 0) error(csa, "problem line missing or invalid"); read_field(csa); if (strcmp(csa->field, "min") != 0) error(csa, "wrong problem designator; `min' expected"); read_field(csa); if (!(str2int(csa->field, &nv) == 0 && nv >= 0)) error(csa, "number of nodes missing or invalid"); read_field(csa); if (!(str2int(csa->field, &na) == 0 && na >= 0)) error(csa, "number of arcs missing or invalid"); xprintf("Flow network has %d node%s and %d arc%s\n", nv, nv == 1 ? "" : "s", na, na == 1 ? "" : "s"); if (nv > 0) glp_add_vertices(G, nv); end_of_line(csa); /* read node descriptor lines */ flag = xcalloc(1+nv, sizeof(char)); memset(&flag[1], 0, nv * sizeof(char)); if (v_rhs >= 0) { rhs = 0.0; for (i = 1; i <= nv; i++) { v = G->v[i]; memcpy((char *)v->data + v_rhs, &rhs, sizeof(double)); } } for (;;) { read_designator(csa); if (strcmp(csa->field, "n") != 0) break; read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "node number missing or invalid"); if (!(1 <= i && i <= nv)) error(csa, "node number %d out of range", i); if (flag[i]) error(csa, "duplicate descriptor of node %d", i); read_field(csa); if (str2num(csa->field, &rhs) != 0) error(csa, "node supply/demand missing or invalid"); check_int(csa, rhs); if (v_rhs >= 0) { v = G->v[i]; memcpy((char *)v->data + v_rhs, &rhs, sizeof(double)); } flag[i] = 1; end_of_line(csa); } xfree(flag), flag = NULL; /* read arc descriptor lines */ for (k = 1; k <= na; k++) { if (k > 1) read_designator(csa); if (strcmp(csa->field, "a") != 0) error(csa, "wrong line designator; `a' expected"); read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "starting node number missing or invalid"); if (!(1 <= i && i <= nv)) error(csa, "starting node number %d out of range", i); read_field(csa); if (str2int(csa->field, &j) != 0) error(csa, "ending node number missing or invalid"); if (!(1 <= j && j <= nv)) error(csa, "ending node number %d out of range", j); read_field(csa); if (!(str2num(csa->field, &low) == 0 && low >= 0.0)) error(csa, "lower bound of arc flow missing or invalid"); check_int(csa, low); read_field(csa); if (!(str2num(csa->field, &cap) == 0 && cap >= low)) error(csa, "upper bound of arc flow missing or invalid"); check_int(csa, cap); read_field(csa); if (str2num(csa->field, &cost) != 0) error(csa, "per-unit cost of arc flow missing or invalid"); check_int(csa, cost); a = glp_add_arc(G, i, j); if (a_low >= 0) memcpy((char *)a->data + a_low, &low, sizeof(double)); if (a_cap >= 0) memcpy((char *)a->data + a_cap, &cap, sizeof(double)); if (a_cost >= 0) memcpy((char *)a->data + a_cost, &cost, sizeof(double)); end_of_line(csa); } xprintf("%d lines were read\n", csa->count); done: if (ret) glp_erase_graph(G, G->v_size, G->a_size); if (csa->fp != NULL) xfclose(csa->fp); if (flag != NULL) xfree(flag); return ret; } /*********************************************************************** * NAME * * glp_write_mincost - write min-cost flow problem data in DIMACS format * * SYNOPSIS * * int glp_write_mincost(glp_graph *G, int v_rhs, int a_low, int a_cap, * int a_cost, const char *fname); * * DESCRIPTION * * The routine glp_write_mincost writes minimum cost flow problem data * in DIMACS format to a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_write_mincost(glp_graph *G, int v_rhs, int a_low, int a_cap, int a_cost, const char *fname) { XFILE *fp; glp_vertex *v; glp_arc *a; int i, count = 0, ret; double rhs, low, cap, cost; if (v_rhs >= 0 && v_rhs > G->v_size - (int)sizeof(double)) xerror("glp_write_mincost: v_rhs = %d; invalid offset\n", v_rhs); if (a_low >= 0 && a_low > G->a_size - (int)sizeof(double)) xerror("glp_write_mincost: a_low = %d; invalid offset\n", a_low); if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_write_mincost: a_cap = %d; invalid offset\n", a_cap); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_write_mincost: a_cost = %d; invalid offset\n", a_cost); xprintf("Writing min-cost flow problem data to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xfprintf(fp, "c %s\n", G->name == NULL ? "unknown" : G->name), count++; xfprintf(fp, "p min %d %d\n", G->nv, G->na), count++; if (v_rhs >= 0) { for (i = 1; i <= G->nv; i++) { v = G->v[i]; memcpy(&rhs, (char *)v->data + v_rhs, sizeof(double)); if (rhs != 0.0) xfprintf(fp, "n %d %.*g\n", i, DBL_DIG, rhs), count++; } } for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { if (a_low >= 0) memcpy(&low, (char *)a->data + a_low, sizeof(double)); else low = 0.0; if (a_cap >= 0) memcpy(&cap, (char *)a->data + a_cap, sizeof(double)); else cap = 1.0; if (a_cost >= 0) memcpy(&cost, (char *)a->data + a_cost, sizeof(double)); else cost = 0.0; xfprintf(fp, "a %d %d %.*g %.*g %.*g\n", a->tail->i, a->head->i, DBL_DIG, low, DBL_DIG, cap, DBL_DIG, cost), count++; } } xfprintf(fp, "c eof\n"), count++; xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xprintf("%d lines were written\n", count); ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /*********************************************************************** * NAME * * glp_read_maxflow - read maximum flow problem data in DIMACS format * * SYNOPSIS * * int glp_read_maxflow(glp_graph *G, int *s, int *t, int a_cap, * const char *fname); * * DESCRIPTION * * The routine glp_read_maxflow reads maximum flow problem data in * DIMACS format from a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_read_maxflow(glp_graph *G, int *_s, int *_t, int a_cap, const char *fname) { struct csa _csa, *csa = &_csa; glp_arc *a; int i, j, k, s, t, nv, na, ret = 0; double cap; if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_read_maxflow: a_cap = %d; invalid offset\n", a_cap); glp_erase_graph(G, G->v_size, G->a_size); if (setjmp(csa->jump)) { ret = 1; goto done; } csa->fname = fname; csa->fp = NULL; csa->count = 0; csa->c = '\n'; csa->field[0] = '\0'; csa->empty = csa->nonint = 0; xprintf("Reading maximum flow problem data from `%s'...\n", fname); csa->fp = xfopen(fname, "r"); if (csa->fp == NULL) { xprintf("Unable to open `%s' - %s\n", fname, xerrmsg()); longjmp(csa->jump, 1); } /* read problem line */ read_designator(csa); if (strcmp(csa->field, "p") != 0) error(csa, "problem line missing or invalid"); read_field(csa); if (strcmp(csa->field, "max") != 0) error(csa, "wrong problem designator; `max' expected"); read_field(csa); if (!(str2int(csa->field, &nv) == 0 && nv >= 2)) error(csa, "number of nodes missing or invalid"); read_field(csa); if (!(str2int(csa->field, &na) == 0 && na >= 0)) error(csa, "number of arcs missing or invalid"); xprintf("Flow network has %d node%s and %d arc%s\n", nv, nv == 1 ? "" : "s", na, na == 1 ? "" : "s"); if (nv > 0) glp_add_vertices(G, nv); end_of_line(csa); /* read node descriptor lines */ s = t = 0; for (;;) { read_designator(csa); if (strcmp(csa->field, "n") != 0) break; read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "node number missing or invalid"); if (!(1 <= i && i <= nv)) error(csa, "node number %d out of range", i); read_field(csa); if (strcmp(csa->field, "s") == 0) { if (s > 0) error(csa, "only one source node allowed"); s = i; } else if (strcmp(csa->field, "t") == 0) { if (t > 0) error(csa, "only one sink node allowed"); t = i; } else error(csa, "wrong node designator; `s' or `t' expected"); if (s > 0 && s == t) error(csa, "source and sink nodes must be distinct"); end_of_line(csa); } if (s == 0) error(csa, "source node descriptor missing\n"); if (t == 0) error(csa, "sink node descriptor missing\n"); if (_s != NULL) *_s = s; if (_t != NULL) *_t = t; /* read arc descriptor lines */ for (k = 1; k <= na; k++) { if (k > 1) read_designator(csa); if (strcmp(csa->field, "a") != 0) error(csa, "wrong line designator; `a' expected"); read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "starting node number missing or invalid"); if (!(1 <= i && i <= nv)) error(csa, "starting node number %d out of range", i); read_field(csa); if (str2int(csa->field, &j) != 0) error(csa, "ending node number missing or invalid"); if (!(1 <= j && j <= nv)) error(csa, "ending node number %d out of range", j); read_field(csa); if (!(str2num(csa->field, &cap) == 0 && cap >= 0.0)) error(csa, "arc capacity missing or invalid"); check_int(csa, cap); a = glp_add_arc(G, i, j); if (a_cap >= 0) memcpy((char *)a->data + a_cap, &cap, sizeof(double)); end_of_line(csa); } xprintf("%d lines were read\n", csa->count); done: if (ret) glp_erase_graph(G, G->v_size, G->a_size); if (csa->fp != NULL) xfclose(csa->fp); return ret; } /*********************************************************************** * NAME * * glp_write_maxflow - write maximum flow problem data in DIMACS format * * SYNOPSIS * * int glp_write_maxflow(glp_graph *G, int s, int t, int a_cap, * const char *fname); * * DESCRIPTION * * The routine glp_write_maxflow writes maximum flow problem data in * DIMACS format to a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_write_maxflow(glp_graph *G, int s, int t, int a_cap, const char *fname) { XFILE *fp; glp_vertex *v; glp_arc *a; int i, count = 0, ret; double cap; if (!(1 <= s && s <= G->nv)) xerror("glp_write_maxflow: s = %d; source node number out of r" "ange\n", s); if (!(1 <= t && t <= G->nv)) xerror("glp_write_maxflow: t = %d: sink node number out of ran" "ge\n", t); if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_write_mincost: a_cap = %d; invalid offset\n", a_cap); xprintf("Writing maximum flow problem data to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xfprintf(fp, "c %s\n", G->name == NULL ? "unknown" : G->name), count++; xfprintf(fp, "p max %d %d\n", G->nv, G->na), count++; xfprintf(fp, "n %d s\n", s), count++; xfprintf(fp, "n %d t\n", t), count++; for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { if (a_cap >= 0) memcpy(&cap, (char *)a->data + a_cap, sizeof(double)); else cap = 1.0; xfprintf(fp, "a %d %d %.*g\n", a->tail->i, a->head->i, DBL_DIG, cap), count++; } } xfprintf(fp, "c eof\n"), count++; xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xprintf("%d lines were written\n", count); ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /*********************************************************************** * NAME * * glp_read_asnprob - read assignment problem data in DIMACS format * * SYNOPSIS * * int glp_read_asnprob(glp_graph *G, int v_set, int a_cost, * const char *fname); * * DESCRIPTION * * The routine glp_read_asnprob reads assignment problem data in DIMACS * format from a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_read_asnprob(glp_graph *G, int v_set, int a_cost, const char *fname) { struct csa _csa, *csa = &_csa; glp_vertex *v; glp_arc *a; int nv, na, n1, i, j, k, ret = 0; double cost; char *flag = NULL; if (v_set >= 0 && v_set > G->v_size - (int)sizeof(int)) xerror("glp_read_asnprob: v_set = %d; invalid offset\n", v_set); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_read_asnprob: a_cost = %d; invalid offset\n", a_cost); glp_erase_graph(G, G->v_size, G->a_size); if (setjmp(csa->jump)) { ret = 1; goto done; } csa->fname = fname; csa->fp = NULL; csa->count = 0; csa->c = '\n'; csa->field[0] = '\0'; csa->empty = csa->nonint = 0; xprintf("Reading assignment problem data from `%s'...\n", fname); csa->fp = xfopen(fname, "r"); if (csa->fp == NULL) { xprintf("Unable to open `%s' - %s\n", fname, xerrmsg()); longjmp(csa->jump, 1); } /* read problem line */ read_designator(csa); if (strcmp(csa->field, "p") != 0) error(csa, "problem line missing or invalid"); read_field(csa); if (strcmp(csa->field, "asn") != 0) error(csa, "wrong problem designator; `asn' expected"); read_field(csa); if (!(str2int(csa->field, &nv) == 0 && nv >= 0)) error(csa, "number of nodes missing or invalid"); read_field(csa); if (!(str2int(csa->field, &na) == 0 && na >= 0)) error(csa, "number of arcs missing or invalid"); if (nv > 0) glp_add_vertices(G, nv); end_of_line(csa); /* read node descriptor lines */ flag = xcalloc(1+nv, sizeof(char)); memset(&flag[1], 0, nv * sizeof(char)); n1 = 0; for (;;) { read_designator(csa); if (strcmp(csa->field, "n") != 0) break; read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "node number missing or invalid"); if (!(1 <= i && i <= nv)) error(csa, "node number %d out of range", i); if (flag[i]) error(csa, "duplicate descriptor of node %d", i); flag[i] = 1, n1++; end_of_line(csa); } xprintf( "Assignment problem has %d + %d = %d node%s and %d arc%s\n", n1, nv - n1, nv, nv == 1 ? "" : "s", na, na == 1 ? "" : "s"); if (v_set >= 0) { for (i = 1; i <= nv; i++) { v = G->v[i]; k = (flag[i] ? 0 : 1); memcpy((char *)v->data + v_set, &k, sizeof(int)); } } /* read arc descriptor lines */ for (k = 1; k <= na; k++) { if (k > 1) read_designator(csa); if (strcmp(csa->field, "a") != 0) error(csa, "wrong line designator; `a' expected"); read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "starting node number missing or invalid"); if (!(1 <= i && i <= nv)) error(csa, "starting node number %d out of range", i); if (!flag[i]) error(csa, "node %d cannot be a starting node", i); read_field(csa); if (str2int(csa->field, &j) != 0) error(csa, "ending node number missing or invalid"); if (!(1 <= j && j <= nv)) error(csa, "ending node number %d out of range", j); if (flag[j]) error(csa, "node %d cannot be an ending node", j); read_field(csa); if (str2num(csa->field, &cost) != 0) error(csa, "arc cost missing or invalid"); check_int(csa, cost); a = glp_add_arc(G, i, j); if (a_cost >= 0) memcpy((char *)a->data + a_cost, &cost, sizeof(double)); end_of_line(csa); } xprintf("%d lines were read\n", csa->count); done: if (ret) glp_erase_graph(G, G->v_size, G->a_size); if (csa->fp != NULL) xfclose(csa->fp); if (flag != NULL) xfree(flag); return ret; } /*********************************************************************** * NAME * * glp_write_asnprob - write assignment problem data in DIMACS format * * SYNOPSIS * * int glp_write_asnprob(glp_graph *G, int v_set, int a_cost, * const char *fname); * * DESCRIPTION * * The routine glp_write_asnprob writes assignment problem data in * DIMACS format to a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_write_asnprob(glp_graph *G, int v_set, int a_cost, const char *fname) { XFILE *fp; glp_vertex *v; glp_arc *a; int i, k, count = 0, ret; double cost; if (v_set >= 0 && v_set > G->v_size - (int)sizeof(int)) xerror("glp_write_asnprob: v_set = %d; invalid offset\n", v_set); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_write_asnprob: a_cost = %d; invalid offset\n", a_cost); xprintf("Writing assignment problem data to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xfprintf(fp, "c %s\n", G->name == NULL ? "unknown" : G->name), count++; xfprintf(fp, "p asn %d %d\n", G->nv, G->na), count++; for (i = 1; i <= G->nv; i++) { v = G->v[i]; if (v_set >= 0) memcpy(&k, (char *)v->data + v_set, sizeof(int)); else k = (v->out != NULL ? 0 : 1); if (k == 0) xfprintf(fp, "n %d\n", i), count++; } for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { if (a_cost >= 0) memcpy(&cost, (char *)a->data + a_cost, sizeof(double)); else cost = 1.0; xfprintf(fp, "a %d %d %.*g\n", a->tail->i, a->head->i, DBL_DIG, cost), count++; } } xfprintf(fp, "c eof\n"), count++; xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xprintf("%d lines were written\n", count); ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /*********************************************************************** * NAME * * glp_read_ccdata - read graph in DIMACS clique/coloring format * * SYNOPSIS * * int glp_read_ccdata(glp_graph *G, int v_wgt, const char *fname); * * DESCRIPTION * * The routine glp_read_ccdata reads an (undirected) graph in DIMACS * clique/coloring format from a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_read_ccdata(glp_graph *G, int v_wgt, const char *fname) { struct csa _csa, *csa = &_csa; glp_vertex *v; int i, j, k, nv, ne, ret = 0; double w; char *flag = NULL; if (v_wgt >= 0 && v_wgt > G->v_size - (int)sizeof(double)) xerror("glp_read_ccdata: v_wgt = %d; invalid offset\n", v_wgt); glp_erase_graph(G, G->v_size, G->a_size); if (setjmp(csa->jump)) { ret = 1; goto done; } csa->fname = fname; csa->fp = NULL; csa->count = 0; csa->c = '\n'; csa->field[0] = '\0'; csa->empty = csa->nonint = 0; xprintf("Reading graph from `%s'...\n", fname); csa->fp = xfopen(fname, "r"); if (csa->fp == NULL) { xprintf("Unable to open `%s' - %s\n", fname, xerrmsg()); longjmp(csa->jump, 1); } /* read problem line */ read_designator(csa); if (strcmp(csa->field, "p") != 0) error(csa, "problem line missing or invalid"); read_field(csa); if (strcmp(csa->field, "edge") != 0) error(csa, "wrong problem designator; `edge' expected"); read_field(csa); if (!(str2int(csa->field, &nv) == 0 && nv >= 0)) error(csa, "number of vertices missing or invalid"); read_field(csa); if (!(str2int(csa->field, &ne) == 0 && ne >= 0)) error(csa, "number of edges missing or invalid"); xprintf("Graph has %d vert%s and %d edge%s\n", nv, nv == 1 ? "ex" : "ices", ne, ne == 1 ? "" : "s"); if (nv > 0) glp_add_vertices(G, nv); end_of_line(csa); /* read node descriptor lines */ flag = xcalloc(1+nv, sizeof(char)); memset(&flag[1], 0, nv * sizeof(char)); if (v_wgt >= 0) { w = 1.0; for (i = 1; i <= nv; i++) { v = G->v[i]; memcpy((char *)v->data + v_wgt, &w, sizeof(double)); } } for (;;) { read_designator(csa); if (strcmp(csa->field, "n") != 0) break; read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "vertex number missing or invalid"); if (!(1 <= i && i <= nv)) error(csa, "vertex number %d out of range", i); if (flag[i]) error(csa, "duplicate descriptor of vertex %d", i); read_field(csa); if (str2num(csa->field, &w) != 0) error(csa, "vertex weight missing or invalid"); check_int(csa, w); if (v_wgt >= 0) { v = G->v[i]; memcpy((char *)v->data + v_wgt, &w, sizeof(double)); } flag[i] = 1; end_of_line(csa); } xfree(flag), flag = NULL; /* read edge descriptor lines */ for (k = 1; k <= ne; k++) { if (k > 1) read_designator(csa); if (strcmp(csa->field, "e") != 0) error(csa, "wrong line designator; `e' expected"); read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "first vertex number missing or invalid"); if (!(1 <= i && i <= nv)) error(csa, "first vertex number %d out of range", i); read_field(csa); if (str2int(csa->field, &j) != 0) error(csa, "second vertex number missing or invalid"); if (!(1 <= j && j <= nv)) error(csa, "second vertex number %d out of range", j); glp_add_arc(G, i, j); end_of_line(csa); } xprintf("%d lines were read\n", csa->count); done: if (ret) glp_erase_graph(G, G->v_size, G->a_size); if (csa->fp != NULL) xfclose(csa->fp); if (flag != NULL) xfree(flag); return ret; } /*********************************************************************** * NAME * * glp_write_ccdata - write graph in DIMACS clique/coloring format * * SYNOPSIS * * int glp_write_ccdata(glp_graph *G, int v_wgt, const char *fname); * * DESCRIPTION * * The routine glp_write_ccdata writes the specified graph in DIMACS * clique/coloring format to a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_write_ccdata(glp_graph *G, int v_wgt, const char *fname) { XFILE *fp; glp_vertex *v; glp_arc *e; int i, count = 0, ret; double w; if (v_wgt >= 0 && v_wgt > G->v_size - (int)sizeof(double)) xerror("glp_write_ccdata: v_wgt = %d; invalid offset\n", v_wgt); xprintf("Writing graph to `%s'\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xfprintf(fp, "c %s\n", G->name == NULL ? "unknown" : G->name), count++; xfprintf(fp, "p edge %d %d\n", G->nv, G->na), count++; if (v_wgt >= 0) { for (i = 1; i <= G->nv; i++) { v = G->v[i]; memcpy(&w, (char *)v->data + v_wgt, sizeof(double)); if (w != 1.0) xfprintf(fp, "n %d %.*g\n", i, DBL_DIG, w), count++; } } for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (e = v->out; e != NULL; e = e->t_next) xfprintf(fp, "e %d %d\n", e->tail->i, e->head->i), count++; } xfprintf(fp, "c eof\n"), count++; xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xprintf("%d lines were written\n", count); ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /*********************************************************************** * NAME * * glp_read_prob - read problem data in GLPK format * * SYNOPSIS * * int glp_read_prob(glp_prob *P, int flags, const char *fname); * * The routine glp_read_prob reads problem data in GLPK LP/MIP format * from a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_read_prob(glp_prob *P, int flags, const char *fname) { struct csa _csa, *csa = &_csa; int mip, m, n, nnz, ne, i, j, k, type, kind, ret, *ln = NULL, *ia = NULL, *ja = NULL; double lb, ub, temp, *ar = NULL; char *rf = NULL, *cf = NULL; if (P == NULL || P->magic != GLP_PROB_MAGIC) xerror("glp_read_prob: P = %p; invalid problem object\n", P); if (flags != 0) xerror("glp_read_prob: flags = %d; invalid parameter\n", flags); if (fname == NULL) xerror("glp_read_prob: fname = %d; invalid parameter\n", fname); glp_erase_prob(P); if (setjmp(csa->jump)) { ret = 1; goto done; } csa->fname = fname; csa->fp = NULL; csa->count = 0; csa->c = '\n'; csa->field[0] = '\0'; csa->empty = csa->nonint = 0; xprintf("Reading problem data from `%s'...\n", fname); csa->fp = xfopen(fname, "r"); if (csa->fp == NULL) { xprintf("Unable to open `%s' - %s\n", fname, xerrmsg()); longjmp(csa->jump, 1); } /* read problem line */ read_designator(csa); if (strcmp(csa->field, "p") != 0) error(csa, "problem line missing or invalid"); read_field(csa); if (strcmp(csa->field, "lp") == 0) mip = 0; else if (strcmp(csa->field, "mip") == 0) mip = 1; else error(csa, "wrong problem designator; `lp' or `mip' expected\n" ); read_field(csa); if (strcmp(csa->field, "min") == 0) glp_set_obj_dir(P, GLP_MIN); else if (strcmp(csa->field, "max") == 0) glp_set_obj_dir(P, GLP_MAX); else error(csa, "objective sense missing or invalid"); read_field(csa); if (!(str2int(csa->field, &m) == 0 && m >= 0)) error(csa, "number of rows missing or invalid"); read_field(csa); if (!(str2int(csa->field, &n) == 0 && n >= 0)) error(csa, "number of columns missing or invalid"); read_field(csa); if (!(str2int(csa->field, &nnz) == 0 && nnz >= 0)) error(csa, "number of constraint coefficients missing or inval" "id"); if (m > 0) { glp_add_rows(P, m); for (i = 1; i <= m; i++) glp_set_row_bnds(P, i, GLP_FX, 0.0, 0.0); } if (n > 0) { glp_add_cols(P, n); for (j = 1; j <= n; j++) { if (!mip) glp_set_col_bnds(P, j, GLP_LO, 0.0, 0.0); else glp_set_col_kind(P, j, GLP_BV); } } end_of_line(csa); /* allocate working arrays */ rf = xcalloc(1+m, sizeof(char)); memset(rf, 0, 1+m); cf = xcalloc(1+n, sizeof(char)); memset(cf, 0, 1+n); ln = xcalloc(1+nnz, sizeof(int)); ia = xcalloc(1+nnz, sizeof(int)); ja = xcalloc(1+nnz, sizeof(int)); ar = xcalloc(1+nnz, sizeof(double)); /* read descriptor lines */ ne = 0; for (;;) { read_designator(csa); if (strcmp(csa->field, "i") == 0) { /* row descriptor */ read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "row number missing or invalid"); if (!(1 <= i && i <= m)) error(csa, "row number out of range"); read_field(csa); if (strcmp(csa->field, "f") == 0) type = GLP_FR; else if (strcmp(csa->field, "l") == 0) type = GLP_LO; else if (strcmp(csa->field, "u") == 0) type = GLP_UP; else if (strcmp(csa->field, "d") == 0) type = GLP_DB; else if (strcmp(csa->field, "s") == 0) type = GLP_FX; else error(csa, "row type missing or invalid"); if (type == GLP_LO || type == GLP_DB || type == GLP_FX) { read_field(csa); if (str2num(csa->field, &lb) != 0) error(csa, "row lower bound/fixed value missing or in" "valid"); } else lb = 0.0; if (type == GLP_UP || type == GLP_DB) { read_field(csa); if (str2num(csa->field, &ub) != 0) error(csa, "row upper bound missing or invalid"); } else ub = 0.0; if (rf[i] & 0x01) error(csa, "duplicate row descriptor"); glp_set_row_bnds(P, i, type, lb, ub), rf[i] |= 0x01; } else if (strcmp(csa->field, "j") == 0) { /* column descriptor */ read_field(csa); if (str2int(csa->field, &j) != 0) error(csa, "column number missing or invalid"); if (!(1 <= j && j <= n)) error(csa, "column number out of range"); if (!mip) kind = GLP_CV; else { read_field(csa); if (strcmp(csa->field, "c") == 0) kind = GLP_CV; else if (strcmp(csa->field, "i") == 0) kind = GLP_IV; else if (strcmp(csa->field, "b") == 0) { kind = GLP_IV; type = GLP_DB, lb = 0.0, ub = 1.0; goto skip; } else error(csa, "column kind missing or invalid"); } read_field(csa); if (strcmp(csa->field, "f") == 0) type = GLP_FR; else if (strcmp(csa->field, "l") == 0) type = GLP_LO; else if (strcmp(csa->field, "u") == 0) type = GLP_UP; else if (strcmp(csa->field, "d") == 0) type = GLP_DB; else if (strcmp(csa->field, "s") == 0) type = GLP_FX; else error(csa, "column type missing or invalid"); if (type == GLP_LO || type == GLP_DB || type == GLP_FX) { read_field(csa); if (str2num(csa->field, &lb) != 0) error(csa, "column lower bound/fixed value missing or" " invalid"); } else lb = 0.0; if (type == GLP_UP || type == GLP_DB) { read_field(csa); if (str2num(csa->field, &ub) != 0) error(csa, "column upper bound missing or invalid"); } else ub = 0.0; skip: if (cf[j] & 0x01) error(csa, "duplicate column descriptor"); glp_set_col_kind(P, j, kind); glp_set_col_bnds(P, j, type, lb, ub), cf[j] |= 0x01; } else if (strcmp(csa->field, "a") == 0) { /* coefficient descriptor */ read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "row number missing or invalid"); if (!(0 <= i && i <= m)) error(csa, "row number out of range"); read_field(csa); if (str2int(csa->field, &j) != 0) error(csa, "column number missing or invalid"); if (!((i == 0 ? 0 : 1) <= j && j <= n)) error(csa, "column number out of range"); read_field(csa); if (i == 0) { if (str2num(csa->field, &temp) != 0) error(csa, "objective %s missing or invalid", j == 0 ? "constant term" : "coefficient"); if (cf[j] & 0x10) error(csa, "duplicate objective %s", j == 0 ? "constant term" : "coefficient"); glp_set_obj_coef(P, j, temp), cf[j] |= 0x10; } else { if (str2num(csa->field, &temp) != 0) error(csa, "constraint coefficient missing or invalid" ); if (ne == nnz) error(csa, "too many constraint coefficient descripto" "rs"); ln[++ne] = csa->count; ia[ne] = i, ja[ne] = j, ar[ne] = temp; } } else if (strcmp(csa->field, "n") == 0) { /* symbolic name descriptor */ read_field(csa); if (strcmp(csa->field, "p") == 0) { /* problem name */ read_field(csa); if (P->name != NULL) error(csa, "duplicate problem name"); glp_set_prob_name(P, csa->field); } else if (strcmp(csa->field, "z") == 0) { /* objective name */ read_field(csa); if (P->obj != NULL) error(csa, "duplicate objective name"); glp_set_obj_name(P, csa->field); } else if (strcmp(csa->field, "i") == 0) { /* row name */ read_field(csa); if (str2int(csa->field, &i) != 0) error(csa, "row number missing or invalid"); if (!(1 <= i && i <= m)) error(csa, "row number out of range"); read_field(csa); if (P->row[i]->name != NULL) error(csa, "duplicate row name"); glp_set_row_name(P, i, csa->field); } else if (strcmp(csa->field, "j") == 0) { /* column name */ read_field(csa); if (str2int(csa->field, &j) != 0) error(csa, "column number missing or invalid"); if (!(1 <= j && j <= n)) error(csa, "column number out of range"); read_field(csa); if (P->col[j]->name != NULL) error(csa, "duplicate column name"); glp_set_col_name(P, j, csa->field); } else error(csa, "object designator missing or invalid"); } else if (strcmp(csa->field, "e") == 0) break; else error(csa, "line designator missing or invalid"); end_of_line(csa); } if (ne < nnz) error(csa, "too few constraint coefficient descriptors"); xassert(ne == nnz); k = glp_check_dup(m, n, ne, ia, ja); xassert(0 <= k && k <= nnz); if (k > 0) { csa->count = ln[k]; error(csa, "duplicate constraint coefficient"); } glp_load_matrix(P, ne, ia, ja, ar); /* print some statistics */ if (P->name != NULL) xprintf("Problem: %s\n", P->name); if (P->obj != NULL) xprintf("Objective: %s\n", P->obj); xprintf("%d row%s, %d column%s, %d non-zero%s\n", m, m == 1 ? "" : "s", n, n == 1 ? "" : "s", nnz, nnz == 1 ? "" : "s"); if (glp_get_num_int(P) > 0) { int ni = glp_get_num_int(P); int nb = glp_get_num_bin(P); if (ni == 1) { if (nb == 0) xprintf("One variable is integer\n"); else xprintf("One variable is binary\n"); } else { xprintf("%d integer variables, ", ni); if (nb == 0) xprintf("none"); else if (nb == 1) xprintf("one"); else if (nb == ni) xprintf("all"); else xprintf("%d", nb); xprintf(" of which %s binary\n", nb == 1 ? "is" : "are"); } } xprintf("%d lines were read\n", csa->count); /* problem data has been successfully read */ glp_sort_matrix(P); ret = 0; done: if (csa->fp != NULL) xfclose(csa->fp); if (rf != NULL) xfree(rf); if (cf != NULL) xfree(cf); if (ln != NULL) xfree(ln); if (ia != NULL) xfree(ia); if (ja != NULL) xfree(ja); if (ar != NULL) xfree(ar); if (ret) glp_erase_prob(P); return ret; } /*********************************************************************** * NAME * * glp_write_prob - write problem data in GLPK format * * SYNOPSIS * * int glp_write_prob(glp_prob *P, int flags, const char *fname); * * The routine glp_write_prob writes problem data in GLPK LP/MIP format * to a text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_write_prob(glp_prob *P, int flags, const char *fname) { XFILE *fp; GLPROW *row; GLPCOL *col; GLPAIJ *aij; int mip, i, j, count, ret; if (P == NULL || P->magic != GLP_PROB_MAGIC) xerror("glp_write_prob: P = %p; invalid problem object\n", P); if (flags != 0) xerror("glp_write_prob: flags = %d; invalid parameter\n", flags); if (fname == NULL) xerror("glp_write_prob: fname = %d; invalid parameter\n", fname); xprintf("Writing problem data to `%s'...\n", fname); fp = xfopen(fname, "w"), count = 0; if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* write problem line */ mip = (glp_get_num_int(P) > 0); xfprintf(fp, "p %s %s %d %d %d\n", !mip ? "lp" : "mip", P->dir == GLP_MIN ? "min" : P->dir == GLP_MAX ? "max" : "???", P->m, P->n, P->nnz), count++; if (P->name != NULL) xfprintf(fp, "n p %s\n", P->name), count++; if (P->obj != NULL) xfprintf(fp, "n z %s\n", P->obj), count++; /* write row descriptors */ for (i = 1; i <= P->m; i++) { row = P->row[i]; if (row->type == GLP_FX && row->lb == 0.0) goto skip1; xfprintf(fp, "i %d ", i), count++; if (row->type == GLP_FR) xfprintf(fp, "f\n"); else if (row->type == GLP_LO) xfprintf(fp, "l %.*g\n", DBL_DIG, row->lb); else if (row->type == GLP_UP) xfprintf(fp, "u %.*g\n", DBL_DIG, row->ub); else if (row->type == GLP_DB) xfprintf(fp, "d %.*g %.*g\n", DBL_DIG, row->lb, DBL_DIG, row->ub); else if (row->type == GLP_FX) xfprintf(fp, "s %.*g\n", DBL_DIG, row->lb); else xassert(row != row); skip1: if (row->name != NULL) xfprintf(fp, "n i %d %s\n", i, row->name), count++; } /* write column descriptors */ for (j = 1; j <= P->n; j++) { col = P->col[j]; if (!mip && col->type == GLP_LO && col->lb == 0.0) goto skip2; if (mip && col->kind == GLP_IV && col->type == GLP_DB && col->lb == 0.0 && col->ub == 1.0) goto skip2; xfprintf(fp, "j %d ", j), count++; if (mip) { if (col->kind == GLP_CV) xfprintf(fp, "c "); else if (col->kind == GLP_IV) xfprintf(fp, "i "); else xassert(col != col); } if (col->type == GLP_FR) xfprintf(fp, "f\n"); else if (col->type == GLP_LO) xfprintf(fp, "l %.*g\n", DBL_DIG, col->lb); else if (col->type == GLP_UP) xfprintf(fp, "u %.*g\n", DBL_DIG, col->ub); else if (col->type == GLP_DB) xfprintf(fp, "d %.*g %.*g\n", DBL_DIG, col->lb, DBL_DIG, col->ub); else if (col->type == GLP_FX) xfprintf(fp, "s %.*g\n", DBL_DIG, col->lb); else xassert(col != col); skip2: if (col->name != NULL) xfprintf(fp, "n j %d %s\n", j, col->name), count++; } /* write objective coefficient descriptors */ if (P->c0 != 0.0) xfprintf(fp, "a 0 0 %.*g\n", DBL_DIG, P->c0), count++; for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->coef != 0.0) xfprintf(fp, "a 0 %d %.*g\n", j, DBL_DIG, col->coef), count++; } /* write constraint coefficient descriptors */ for (i = 1; i <= P->m; i++) { row = P->row[i]; for (aij = row->ptr; aij != NULL; aij = aij->r_next) xfprintf(fp, "a %d %d %.*g\n", i, aij->col->j, DBL_DIG, aij->val), count++; } /* write end line */ xfprintf(fp, "e o f\n"), count++; xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xprintf("%d lines were written\n", count); ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /* eof */ sources_5316/external/glpk/glpqmd.c0000644000176700017670000004356511401660400016137 0ustar paulpaul/* glpqmd.c (quotient minimum degree algorithm) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * THIS CODE IS THE RESULT OF TRANSLATION OF THE FORTRAN SUBROUTINES * GENQMD, QMDRCH, QMDQT, QMDUPD, AND QMDMRG FROM THE BOOK: * * ALAN GEORGE, JOSEPH W-H LIU. COMPUTER SOLUTION OF LARGE SPARSE * POSITIVE DEFINITE SYSTEMS. PRENTICE-HALL, 1981. * * THE TRANSLATION HAS BEEN DONE WITH THE PERMISSION OF THE AUTHORS * OF THE ORIGINAL FORTRAN SUBROUTINES: ALAN GEORGE AND JOSEPH LIU, * UNIVERSITY OF WATERLOO, WATERLOO, ONTARIO, CANADA. * * The translation was made by Andrew Makhorin . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpqmd.h" /*********************************************************************** * NAME * * genqmd - GENeral Quotient Minimum Degree algorithm * * SYNOPSIS * * #include "glpqmd.h" * void genqmd(int *neqns, int xadj[], int adjncy[], int perm[], * int invp[], int deg[], int marker[], int rchset[], int nbrhd[], * int qsize[], int qlink[], int *nofsub); * * PURPOSE * * This routine implements the minimum degree algorithm. It makes use * of the implicit representation of the elimination graph by quotient * graphs, and the notion of indistinguishable nodes. * * CAUTION * * The adjancy vector adjncy will be destroyed. * * INPUT PARAMETERS * * neqns - number of equations; * (xadj, adjncy) - * the adjancy structure. * * OUTPUT PARAMETERS * * perm - the minimum degree ordering; * invp - the inverse of perm. * * WORKING PARAMETERS * * deg - the degree vector. deg[i] is negative means node i has been * numbered; * marker - a marker vector, where marker[i] is negative means node i * has been merged with another nodeand thus can be ignored; * rchset - vector used for the reachable set; * nbrhd - vector used for neighborhood set; * qsize - vector used to store the size of indistinguishable * supernodes; * qlink - vector used to store indistinguishable nodes, i, qlink[i], * qlink[qlink[i]], ... are the members of the supernode * represented by i. * * PROGRAM SUBROUTINES * * qmdrch, qmdqt, qmdupd. ***********************************************************************/ void genqmd(int *_neqns, int xadj[], int adjncy[], int perm[], int invp[], int deg[], int marker[], int rchset[], int nbrhd[], int qsize[], int qlink[], int *_nofsub) { int inode, ip, irch, j, mindeg, ndeg, nhdsze, node, np, num, nump1, nxnode, rchsze, search, thresh; # define neqns (*_neqns) # define nofsub (*_nofsub) /* Initialize degree vector and other working variables. */ mindeg = neqns; nofsub = 0; for (node = 1; node <= neqns; node++) { perm[node] = node; invp[node] = node; marker[node] = 0; qsize[node] = 1; qlink[node] = 0; ndeg = xadj[node+1] - xadj[node]; deg[node] = ndeg; if (ndeg < mindeg) mindeg = ndeg; } num = 0; /* Perform threshold search to get a node of min degree. Variable search point to where search should start. */ s200: search = 1; thresh = mindeg; mindeg = neqns; s300: nump1 = num + 1; if (nump1 > search) search = nump1; for (j = search; j <= neqns; j++) { node = perm[j]; if (marker[node] >= 0) { ndeg = deg[node]; if (ndeg <= thresh) goto s500; if (ndeg < mindeg) mindeg = ndeg; } } goto s200; /* Node has minimum degree. Find its reachable sets by calling qmdrch. */ s500: search = j; nofsub += deg[node]; marker[node] = 1; qmdrch(&node, xadj, adjncy, deg, marker, &rchsze, rchset, &nhdsze, nbrhd); /* Eliminate all nodes indistinguishable from node. They are given by node, qlink[node], ... . */ nxnode = node; s600: num++; np = invp[nxnode]; ip = perm[num]; perm[np] = ip; invp[ip] = np; perm[num] = nxnode; invp[nxnode] = num; deg[nxnode] = -1; nxnode = qlink[nxnode]; if (nxnode > 0) goto s600; if (rchsze > 0) { /* Update the degrees of the nodes in the reachable set and identify indistinguishable nodes. */ qmdupd(xadj, adjncy, &rchsze, rchset, deg, qsize, qlink, marker, &rchset[rchsze+1], &nbrhd[nhdsze+1]); /* Reset marker value of nodes in reach set. Update threshold value for cyclic search. Also call qmdqt to form new quotient graph. */ marker[node] = 0; for (irch = 1; irch <= rchsze; irch++) { inode = rchset[irch]; if (marker[inode] >= 0) { marker[inode] = 0; ndeg = deg[inode]; if (ndeg < mindeg) mindeg = ndeg; if (ndeg <= thresh) { mindeg = thresh; thresh = ndeg; search = invp[inode]; } } } if (nhdsze > 0) qmdqt(&node, xadj, adjncy, marker, &rchsze, rchset, nbrhd); } if (num < neqns) goto s300; return; # undef neqns # undef nofsub } /*********************************************************************** * NAME * * qmdrch - Quotient MD ReaCHable set * * SYNOPSIS * * #include "glpqmd.h" * void qmdrch(int *root, int xadj[], int adjncy[], int deg[], * int marker[], int *rchsze, int rchset[], int *nhdsze, * int nbrhd[]); * * PURPOSE * * This subroutine determines the reachable set of a node through a * given subset. The adjancy structure is assumed to be stored in a * quotient graph format. * * INPUT PARAMETERS * * root - the given node not in the subset; * (xadj, adjncy) - * the adjancy structure pair; * deg - the degree vector. deg[i] < 0 means the node belongs to the * given subset. * * OUTPUT PARAMETERS * * (rchsze, rchset) - * the reachable set; * (nhdsze, nbrhd) - * the neighborhood set. * * UPDATED PARAMETERS * * marker - the marker vector for reach and nbrhd sets. > 0 means the * node is in reach set. < 0 means the node has been merged * with others in the quotient or it is in nbrhd set. ***********************************************************************/ void qmdrch(int *_root, int xadj[], int adjncy[], int deg[], int marker[], int *_rchsze, int rchset[], int *_nhdsze, int nbrhd[]) { int i, istop, istrt, j, jstop, jstrt, nabor, node; # define root (*_root) # define rchsze (*_rchsze) # define nhdsze (*_nhdsze) /* Loop through the neighbors of root in the quotient graph. */ nhdsze = 0; rchsze = 0; istrt = xadj[root]; istop = xadj[root+1] - 1; if (istop < istrt) return; for (i = istrt; i <= istop; i++) { nabor = adjncy[i]; if (nabor == 0) return; if (marker[nabor] == 0) { if (deg[nabor] >= 0) { /* Include nabor into the reachable set. */ rchsze++; rchset[rchsze] = nabor; marker[nabor] = 1; goto s600; } /* nabor has been eliminated. Find nodes reachable from it. */ marker[nabor] = -1; nhdsze++; nbrhd[nhdsze] = nabor; s300: jstrt = xadj[nabor]; jstop = xadj[nabor+1] - 1; for (j = jstrt; j <= jstop; j++) { node = adjncy[j]; nabor = - node; if (node < 0) goto s300; if (node == 0) goto s600; if (marker[node] == 0) { rchsze++; rchset[rchsze] = node; marker[node] = 1; } } } s600: ; } return; # undef root # undef rchsze # undef nhdsze } /*********************************************************************** * NAME * * qmdqt - Quotient MD Quotient graph Transformation * * SYNOPSIS * * #include "glpqmd.h" * void qmdqt(int *root, int xadj[], int adjncy[], int marker[], * int *rchsze, int rchset[], int nbrhd[]); * * PURPOSE * * This subroutine performs the quotient graph transformation after a * node has been eliminated. * * INPUT PARAMETERS * * root - the node just eliminated. It becomes the representative of * the new supernode; * (xadj, adjncy) - * the adjancy structure; * (rchsze, rchset) - * the reachable set of root in the old quotient graph; * nbrhd - the neighborhood set which will be merged with root to form * the new supernode; * marker - the marker vector. * * UPDATED PARAMETERS * * adjncy - becomes the adjncy of the quotient graph. ***********************************************************************/ void qmdqt(int *_root, int xadj[], int adjncy[], int marker[], int *_rchsze, int rchset[], int nbrhd[]) { int inhd, irch, j, jstop, jstrt, link, nabor, node; # define root (*_root) # define rchsze (*_rchsze) irch = 0; inhd = 0; node = root; s100: jstrt = xadj[node]; jstop = xadj[node+1] - 2; if (jstop >= jstrt) { /* Place reach nodes into the adjacent list of node. */ for (j = jstrt; j <= jstop; j++) { irch++; adjncy[j] = rchset[irch]; if (irch >= rchsze) goto s400; } } /* Link to other space provided by the nbrhd set. */ link = adjncy[jstop+1]; node = - link; if (link >= 0) { inhd++; node = nbrhd[inhd]; adjncy[jstop+1] = - node; } goto s100; /* All reachable nodes have been saved. End the adjacent list. Add root to the neighborhood list of each node in the reach set. */ s400: adjncy[j+1] = 0; for (irch = 1; irch <= rchsze; irch++) { node = rchset[irch]; if (marker[node] >= 0) { jstrt = xadj[node]; jstop = xadj[node+1] - 1; for (j = jstrt; j <= jstop; j++) { nabor = adjncy[j]; if (marker[nabor] < 0) { adjncy[j] = root; goto s600; } } } s600: ; } return; # undef root # undef rchsze } /*********************************************************************** * NAME * * qmdupd - Quotient MD UPDate * * SYNOPSIS * * #include "glpqmd.h" * void qmdupd(int xadj[], int adjncy[], int *nlist, int list[], * int deg[], int qsize[], int qlink[], int marker[], int rchset[], * int nbrhd[]); * * PURPOSE * * This routine performs degree update for a set of nodes in the minimum * degree algorithm. * * INPUT PARAMETERS * * (xadj, adjncy) - * the adjancy structure; * (nlist, list) - * the list of nodes whose degree has to be updated. * * UPDATED PARAMETERS * * deg - the degree vector; * qsize - size of indistinguishable supernodes; * qlink - linked list for indistinguishable nodes; * marker - used to mark those nodes in reach/nbrhd sets. * * WORKING PARAMETERS * * rchset - the reachable set; * nbrhd - the neighborhood set. * * PROGRAM SUBROUTINES * * qmdmrg. ***********************************************************************/ void qmdupd(int xadj[], int adjncy[], int *_nlist, int list[], int deg[], int qsize[], int qlink[], int marker[], int rchset[], int nbrhd[]) { int deg0, deg1, il, inhd, inode, irch, j, jstop, jstrt, mark, nabor, nhdsze, node, rchsze; # define nlist (*_nlist) /* Find all eliminated supernodes that are adjacent to some nodes in the given list. Put them into (nhdsze, nbrhd). deg0 contains the number of nodes in the list. */ if (nlist <= 0) return; deg0 = 0; nhdsze = 0; for (il = 1; il <= nlist; il++) { node = list[il]; deg0 += qsize[node]; jstrt = xadj[node]; jstop = xadj[node+1] - 1; for (j = jstrt; j <= jstop; j++) { nabor = adjncy[j]; if (marker[nabor] == 0 && deg[nabor] < 0) { marker[nabor] = -1; nhdsze++; nbrhd[nhdsze] = nabor; } } } /* Merge indistinguishable nodes in the list by calling the subroutine qmdmrg. */ if (nhdsze > 0) qmdmrg(xadj, adjncy, deg, qsize, qlink, marker, °0, &nhdsze, nbrhd, rchset, &nbrhd[nhdsze+1]); /* Find the new degrees of the nodes that have not been merged. */ for (il = 1; il <= nlist; il++) { node = list[il]; mark = marker[node]; if (mark == 0 || mark == 1) { marker[node] = 2; qmdrch(&node, xadj, adjncy, deg, marker, &rchsze, rchset, &nhdsze, nbrhd); deg1 = deg0; if (rchsze > 0) { for (irch = 1; irch <= rchsze; irch++) { inode = rchset[irch]; deg1 += qsize[inode]; marker[inode] = 0; } } deg[node] = deg1 - 1; if (nhdsze > 0) { for (inhd = 1; inhd <= nhdsze; inhd++) { inode = nbrhd[inhd]; marker[inode] = 0; } } } } return; # undef nlist } /*********************************************************************** * NAME * * qmdmrg - Quotient MD MeRGe * * SYNOPSIS * * #include "qmdmrg.h" * void qmdmrg(int xadj[], int adjncy[], int deg[], int qsize[], * int qlink[], int marker[], int *deg0, int *nhdsze, int nbrhd[], * int rchset[], int ovrlp[]); * * PURPOSE * * This routine merges indistinguishable nodes in the minimum degree * ordering algorithm. It also computes the new degrees of these new * supernodes. * * INPUT PARAMETERS * * (xadj, adjncy) - * the adjancy structure; * deg0 - the number of nodes in the given set; * (nhdsze, nbrhd) - * the set of eliminated supernodes adjacent to some nodes in * the set. * * UPDATED PARAMETERS * * deg - the degree vector; * qsize - size of indistinguishable nodes; * qlink - linked list for indistinguishable nodes; * marker - the given set is given by those nodes with marker value set * to 1. Those nodes with degree updated will have marker value * set to 2. * * WORKING PARAMETERS * * rchset - the reachable set; * ovrlp - temp vector to store the intersection of two reachable sets. ***********************************************************************/ void qmdmrg(int xadj[], int adjncy[], int deg[], int qsize[], int qlink[], int marker[], int *_deg0, int *_nhdsze, int nbrhd[], int rchset[], int ovrlp[]) { int deg1, head, inhd, iov, irch, j, jstop, jstrt, link, lnode, mark, mrgsze, nabor, node, novrlp, rchsze, root; # define deg0 (*_deg0) # define nhdsze (*_nhdsze) /* Initialization. */ if (nhdsze <= 0) return; for (inhd = 1; inhd <= nhdsze; inhd++) { root = nbrhd[inhd]; marker[root] = 0; } /* Loop through each eliminated supernode in the set (nhdsze, nbrhd). */ for (inhd = 1; inhd <= nhdsze; inhd++) { root = nbrhd[inhd]; marker[root] = -1; rchsze = 0; novrlp = 0; deg1 = 0; s200: jstrt = xadj[root]; jstop = xadj[root+1] - 1; /* Determine the reachable set and its intersection with the input reachable set. */ for (j = jstrt; j <= jstop; j++) { nabor = adjncy[j]; root = - nabor; if (nabor < 0) goto s200; if (nabor == 0) break; mark = marker[nabor]; if (mark == 0) { rchsze++; rchset[rchsze] = nabor; deg1 += qsize[nabor]; marker[nabor] = 1; } else if (mark == 1) { novrlp++; ovrlp[novrlp] = nabor; marker[nabor] = 2; } } /* From the overlapped set, determine the nodes that can be merged together. */ head = 0; mrgsze = 0; for (iov = 1; iov <= novrlp; iov++) { node = ovrlp[iov]; jstrt = xadj[node]; jstop = xadj[node+1] - 1; for (j = jstrt; j <= jstop; j++) { nabor = adjncy[j]; if (marker[nabor] == 0) { marker[node] = 1; goto s1100; } } /* Node belongs to the new merged supernode. Update the vectors qlink and qsize. */ mrgsze += qsize[node]; marker[node] = -1; lnode = node; s900: link = qlink[lnode]; if (link > 0) { lnode = link; goto s900; } qlink[lnode] = head; head = node; s1100: ; } if (head > 0) { qsize[head] = mrgsze; deg[head] = deg0 + deg1 - 1; marker[head] = 2; } /* Reset marker values. */ root = nbrhd[inhd]; marker[root] = 0; if (rchsze > 0) { for (irch = 1; irch <= rchsze; irch++) { node = rchset[irch]; marker[node] = 0; } } } return; # undef deg0 # undef nhdsze } /* eof */ sources_5316/external/glpk/glpapi10.c0000644000176700017670000002304311401660400016255 0ustar paulpaul/* glpapi10.c (solution checking routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" void _glp_check_kkt(glp_prob *P, int sol, int cond, double *_ae_max, int *_ae_ind, double *_re_max, int *_re_ind) { /* check feasibility and optimality conditions */ int m = P->m; int n = P->n; GLPROW *row; GLPCOL *col; GLPAIJ *aij; int i, j, ae_ind, re_ind; double e, sp, sn, t, ae_max, re_max; if (!(sol == GLP_SOL || sol == GLP_IPT || sol == GLP_MIP)) xerror("glp_check_kkt: sol = %d; invalid solution indicator\n", sol); if (!(cond == GLP_KKT_PE || cond == GLP_KKT_PB || cond == GLP_KKT_DE || cond == GLP_KKT_DB || cond == GLP_KKT_CS)) xerror("glp_check_kkt: cond = %d; invalid condition indicator " "\n", cond); ae_max = re_max = 0.0; ae_ind = re_ind = 0; if (cond == GLP_KKT_PE) { /* xR - A * xS = 0 */ for (i = 1; i <= m; i++) { row = P->row[i]; sp = sn = 0.0; /* t := xR[i] */ if (sol == GLP_SOL) t = row->prim; else if (sol == GLP_IPT) t = row->pval; else if (sol == GLP_MIP) t = row->mipx; else xassert(sol != sol); if (t >= 0.0) sp += t; else sn -= t; for (aij = row->ptr; aij != NULL; aij = aij->r_next) { col = aij->col; /* t := - a[i,j] * xS[j] */ if (sol == GLP_SOL) t = - aij->val * col->prim; else if (sol == GLP_IPT) t = - aij->val * col->pval; else if (sol == GLP_MIP) t = - aij->val * col->mipx; else xassert(sol != sol); if (t >= 0.0) sp += t; else sn -= t; } /* absolute error */ e = fabs(sp - sn); if (ae_max < e) ae_max = e, ae_ind = i; /* relative error */ e /= (1.0 + sp + sn); if (re_max < e) re_max = e, re_ind = i; } } else if (cond == GLP_KKT_PB) { /* lR <= xR <= uR */ for (i = 1; i <= m; i++) { row = P->row[i]; /* t := xR[i] */ if (sol == GLP_SOL) t = row->prim; else if (sol == GLP_IPT) t = row->pval; else if (sol == GLP_MIP) t = row->mipx; else xassert(sol != sol); /* check lower bound */ if (row->type == GLP_LO || row->type == GLP_DB || row->type == GLP_FX) { if (t < row->lb) { /* absolute error */ e = row->lb - t; if (ae_max < e) ae_max = e, ae_ind = i; /* relative error */ e /= (1.0 + fabs(row->lb)); if (re_max < e) re_max = e, re_ind = i; } } /* check upper bound */ if (row->type == GLP_UP || row->type == GLP_DB || row->type == GLP_FX) { if (t > row->ub) { /* absolute error */ e = t - row->ub; if (ae_max < e) ae_max = e, ae_ind = i; /* relative error */ e /= (1.0 + fabs(row->ub)); if (re_max < e) re_max = e, re_ind = i; } } } /* lS <= xS <= uS */ for (j = 1; j <= n; j++) { col = P->col[j]; /* t := xS[j] */ if (sol == GLP_SOL) t = col->prim; else if (sol == GLP_IPT) t = col->pval; else if (sol == GLP_MIP) t = col->mipx; else xassert(sol != sol); /* check lower bound */ if (col->type == GLP_LO || col->type == GLP_DB || col->type == GLP_FX) { if (t < col->lb) { /* absolute error */ e = col->lb - t; if (ae_max < e) ae_max = e, ae_ind = m+j; /* relative error */ e /= (1.0 + fabs(col->lb)); if (re_max < e) re_max = e, re_ind = m+j; } } /* check upper bound */ if (col->type == GLP_UP || col->type == GLP_DB || col->type == GLP_FX) { if (t > col->ub) { /* absolute error */ e = t - col->ub; if (ae_max < e) ae_max = e, ae_ind = m+j; /* relative error */ e /= (1.0 + fabs(col->ub)); if (re_max < e) re_max = e, re_ind = m+j; } } } } else if (cond == GLP_KKT_DE) { /* A' * (lambdaR - cR) + (lambdaS - cS) = 0 */ for (j = 1; j <= n; j++) { col = P->col[j]; sp = sn = 0.0; /* t := lambdaS[j] - cS[j] */ if (sol == GLP_SOL) t = col->dual - col->coef; else if (sol == GLP_IPT) t = col->dval - col->coef; else xassert(sol != sol); if (t >= 0.0) sp += t; else sn -= t; for (aij = col->ptr; aij != NULL; aij = aij->c_next) { row = aij->row; /* t := a[i,j] * (lambdaR[i] - cR[i]) */ if (sol == GLP_SOL) t = aij->val * row->dual; else if (sol == GLP_IPT) t = aij->val * row->dval; else xassert(sol != sol); if (t >= 0.0) sp += t; else sn -= t; } /* absolute error */ e = fabs(sp - sn); if (ae_max < e) ae_max = e, ae_ind = m+j; /* relative error */ e /= (1.0 + sp + sn); if (re_max < e) re_max = e, re_ind = m+j; } } else if (cond == GLP_KKT_DB) { /* check lambdaR */ for (i = 1; i <= m; i++) { row = P->row[i]; /* t := lambdaR[i] */ if (sol == GLP_SOL) t = row->dual; else if (sol == GLP_IPT) t = row->dval; else xassert(sol != sol); /* correct sign */ if (P->dir == GLP_MIN) t = + t; else if (P->dir == GLP_MAX) t = - t; else xassert(P != P); /* check for positivity */ if (row->type == GLP_FR || row->type == GLP_LO) { if (t < 0.0) { e = - t; if (ae_max < e) ae_max = re_max = e, ae_ind = re_ind = i; } } /* check for negativity */ if (row->type == GLP_FR || row->type == GLP_UP) { if (t > 0.0) { e = + t; if (ae_max < e) ae_max = re_max = e, ae_ind = re_ind = i; } } } /* check lambdaS */ for (j = 1; j <= n; j++) { col = P->col[j]; /* t := lambdaS[j] */ if (sol == GLP_SOL) t = col->dual; else if (sol == GLP_IPT) t = col->dval; else xassert(sol != sol); /* correct sign */ if (P->dir == GLP_MIN) t = + t; else if (P->dir == GLP_MAX) t = - t; else xassert(P != P); /* check for positivity */ if (col->type == GLP_FR || col->type == GLP_LO) { if (t < 0.0) { e = - t; if (ae_max < e) ae_max = re_max = e, ae_ind = re_ind = m+j; } } /* check for negativity */ if (col->type == GLP_FR || col->type == GLP_UP) { if (t > 0.0) { e = + t; if (ae_max < e) ae_max = re_max = e, ae_ind = re_ind = m+j; } } } } else xassert(cond != cond); if (_ae_max != NULL) *_ae_max = ae_max; if (_ae_ind != NULL) *_ae_ind = ae_ind; if (_re_max != NULL) *_re_max = re_max; if (_re_ind != NULL) *_re_ind = re_ind; return; } /* eof */ sources_5316/external/glpk/glpdmp.c0000644000176700017670000001712711401660400016131 0ustar paulpaul/* glpdmp.c (dynamic memory pool) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpdmp.h" #if 1 /* 29/VIII-2008 */ /* some processors need data to be properly aligned; the macro align_datasize enlarges the specified size of a data item to provide a proper alignment of immediately following data */ #define align_datasize(size) ((((size) + 7) / 8) * 8) /* 8 bytes is sufficient in both 32- and 64-bit environments */ #endif #ifdef GLP_DEBUG struct info { DMP *pool; int size; }; #endif /*********************************************************************** * NAME * * dmp_create_pool - create dynamic memory pool * * SYNOPSIS * * #include "glpdmp.h" * DMP *dmp_create_pool(void); * * DESCRIPTION * * The routine dmp_create_pool creates a dynamic memory pool. * * RETURNS * * The routine returns a pointer to the memory pool created. */ DMP *dmp_create_pool(void) { DMP *pool; int k; #ifdef GLP_DEBUG xprintf("dmp_create_pool: warning: debug mode enabled\n"); #endif pool = xmalloc(sizeof(DMP)); #if 0 pool->size = 0; #endif for (k = 0; k <= 31; k++) pool->avail[k] = NULL; pool->block = NULL; pool->used = DMP_BLK_SIZE; pool->count.lo = pool->count.hi = 0; return pool; } /*********************************************************************** * NAME * * dmp_get_atom - get free atom from dynamic memory pool * * SYNOPSIS * * #include "glpdmp.h" * void *dmp_get_atom(DMP *pool, int size); * * DESCRIPTION * * The routine dmp_get_atom obtains a free atom (memory block) from the * specified memory pool. * * The parameter size is the atom size, in bytes, 1 <= size <= 256. * * Note that the free atom contains arbitrary data, not binary zeros. * * RETURNS * * The routine returns a pointer to the free atom obtained. */ void *dmp_get_atom(DMP *pool, int size) { void *atom; int k; #ifdef GLP_DEBUG int orig_size = size; #endif if (!(1 <= size && size <= 256)) xerror("dmp_get_atom: size = %d; invalid atom size\n", size); #if 0 if (!(pool->size == 0 || pool->size == size)) xerror("dmp_get_atom: size = %d; wrong atom size\n", size); #endif /* adjust the size to provide the proper data alignment */ size = align_datasize(size); #ifdef GLP_DEBUG size += align_datasize(sizeof(struct info)); #endif /* adjust the size to make it multiple of 8 bytes, if needed */ size = ((size + 7) / 8) * 8; /* determine the corresponding list of free cells */ k = size / 8 - 1; xassert(0 <= k && k <= 31); /* obtain a free atom */ if (pool->avail[k] == NULL) { /* the list of free cells is empty */ if (pool->used + size > DMP_BLK_SIZE) { /* allocate a new memory block */ void *block = xmalloc(DMP_BLK_SIZE); *(void **)block = pool->block; pool->block = block; pool->used = align_datasize(sizeof(void *)); } /* place the atom in the current memory block */ atom = (char *)pool->block + pool->used; pool->used += size; } else { /* obtain the atom from the list of free cells */ atom = pool->avail[k]; pool->avail[k] = *(void **)atom; } memset(atom, '?', size); /* increase the number of atoms which are currently in use */ pool->count.lo++; if (pool->count.lo == 0) pool->count.hi++; #ifdef GLP_DEBUG ((struct info *)atom)->pool = pool; ((struct info *)atom)->size = orig_size; atom = (char *)atom + align_datasize(sizeof(struct info)); #endif return atom; } /*********************************************************************** * NAME * * dmp_free_atom - return atom to dynamic memory pool * * SYNOPSIS * * #include "glpdmp.h" * void dmp_free_atom(DMP *pool, void *atom, int size); * * DESCRIPTION * * The routine dmp_free_atom returns the specified atom (memory block) * to the specified memory pool, making it free. * * The parameter size is the atom size, in bytes, 1 <= size <= 256. * * Note that the atom can be returned only to the pool, from which it * was obtained, and its size must be exactly the same as on obtaining * it from the pool. */ void dmp_free_atom(DMP *pool, void *atom, int size) { int k; if (!(1 <= size && size <= 256)) xerror("dmp_free_atom: size = %d; invalid atom size\n", size); #if 0 if (!(pool->size == 0 || pool->size == size)) xerror("dmp_free_atom: size = %d; wrong atom size\n", size); #endif if (pool->count.lo == 0 && pool->count.hi == 0) xerror("dmp_free_atom: pool allocation error\n"); #ifdef GLP_DEBUG atom = (char *)atom - align_datasize(sizeof(struct info)); xassert(((struct info *)atom)->pool == pool); xassert(((struct info *)atom)->size == size); #endif /* adjust the size to provide the proper data alignment */ size = align_datasize(size); #ifdef GLP_DEBUG size += align_datasize(sizeof(struct info)); #endif /* adjust the size to make it multiple of 8 bytes, if needed */ size = ((size + 7) / 8) * 8; /* determine the corresponding list of free cells */ k = size / 8 - 1; xassert(0 <= k && k <= 31); /* return the atom to the list of free cells */ *(void **)atom = pool->avail[k]; pool->avail[k] = atom; /* decrease the number of atoms which are currently in use */ pool->count.lo--; if (pool->count.lo == 0xFFFFFFFF) pool->count.hi--; return; } /*********************************************************************** * NAME * * dmp_in_use - determine how many atoms are still in use * * SYNOPSIS * * #include "glpdmp.h" * glp_long dmp_in_use(DMP *pool); * * DESCRIPTION * * The routine dmp_in_use determines how many atoms allocated from the * specified memory pool with the routine dmp_get_atom are still in use, * i.e. not returned to the pool with the routine dmp_free_atom. * * RETURNS * * The routine returns the number of atoms which are still in use. */ glp_long dmp_in_use(DMP *pool) { return pool->count; } /*********************************************************************** * NAME * * dmp_delete_pool - delete dynamic memory pool * * SYNOPSIS * * #include "glpdmp.h" * void dmp_delete_pool(DMP *pool); * * DESCRIPTION * * The routine dmp_delete_pool deletes the specified dynamic memory * pool and frees all the memory allocated to this object. */ void dmp_delete_pool(DMP *pool) { while (pool->block != NULL) { void *block = pool->block; pool->block = *(void **)block; xfree(block); } xfree(pool); return; } /* eof */ sources_5316/external/glpk/glphbm.c0000644000176700017670000004556711401660400016130 0ustar paulpaul/* glphbm.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_ERRNO #define _GLPSTD_STDIO #include "glphbm.h" #include "glpenv.h" /*********************************************************************** * NAME * * hbm_read_mat - read sparse matrix in Harwell-Boeing format * * SYNOPSIS * * #include "glphbm.h" * HBM *hbm_read_mat(const char *fname); * * DESCRIPTION * * The routine hbm_read_mat reads a sparse matrix in the Harwell-Boeing * format from a text file whose name is the character string fname. * * Detailed description of the Harwell-Boeing format recognised by this * routine is given in the following report: * * I.S.Duff, R.G.Grimes, J.G.Lewis. User's Guide for the Harwell-Boeing * Sparse Matrix Collection (Release I), TR/PA/92/86, October 1992. * * RETURNS * * If no error occured, the routine hbm_read_mat returns a pointer to * a data structure containing the matrix. In case of error the routine * prints an appropriate error message and returns NULL. */ struct dsa { /* working area used by routine hbm_read_mat */ const char *fname; /* name of input text file */ FILE *fp; /* stream assigned to input text file */ int seqn; /* card sequential number */ char card[80+1]; /* card image buffer */ int fmt_p; /* scale factor */ int fmt_k; /* iterator */ int fmt_f; /* format code */ int fmt_w; /* field width */ int fmt_d; /* number of decimal places after point */ }; /*********************************************************************** * read_card - read next data card * * This routine reads the next 80-column card from the input text file * and stores its image into the character string card. If the card was * read successfully, the routine returns zero, otherwise non-zero. */ static int read_card(struct dsa *dsa) { int k, c; dsa->seqn++; memset(dsa->card, ' ', 80), dsa->card[80] = '\0'; k = 0; for (;;) { c = fgetc(dsa->fp); if (ferror(dsa->fp)) { xprintf("%s:%d: read error - %s\n", dsa->fname, dsa->seqn, strerror(errno)); return 1; } if (feof(dsa->fp)) { if (k == 0) xprintf("%s:%d: unexpected EOF\n", dsa->fname, dsa->seqn); else xprintf("%s:%d: missing final LF\n", dsa->fname, dsa->seqn); return 1; } if (c == '\r') continue; if (c == '\n') break; if (iscntrl(c)) { xprintf("%s:%d: invalid control character 0x%02X\n", dsa->fname, dsa->seqn, c); return 1; } if (k == 80) { xprintf("%s:%d: card image too long\n", dsa->fname, dsa->seqn); return 1; } dsa->card[k++] = (char)c; } return 0; } /*********************************************************************** * scan_int - scan integer value from the current card * * This routine scans an integer value from the current card, where fld * is the name of the field, pos is the position of the field, width is * the width of the field, val points to a location to which the scanned * value should be stored. If the value was scanned successfully, the * routine returns zero, otherwise non-zero. */ static int scan_int(struct dsa *dsa, char *fld, int pos, int width, int *val) { char str[80+1]; xassert(1 <= width && width <= 80); memcpy(str, dsa->card + pos, width), str[width] = '\0'; if (str2int(strspx(str), val)) { xprintf("%s:%d: field `%s' contains invalid value `%s'\n", dsa->fname, dsa->seqn, fld, str); return 1; } return 0; } /*********************************************************************** * parse_fmt - parse Fortran format specification * * This routine parses the Fortran format specification represented as * character string which fmt points to and stores format elements into * appropriate static locations. Should note that not all valid Fortran * format specifications may be recognised. If the format specification * was recognised, the routine returns zero, otherwise non-zero. */ static int parse_fmt(struct dsa *dsa, char *fmt) { int k, s, val; char str[80+1]; /* first character should be left parenthesis */ if (fmt[0] != '(') fail: { xprintf("hbm_read_mat: format `%s' not recognised\n", fmt); return 1; } k = 1; /* optional scale factor */ dsa->fmt_p = 0; if (isdigit((unsigned char)fmt[k])) { s = 0; while (isdigit((unsigned char)fmt[k])) { if (s == 80) goto fail; str[s++] = fmt[k++]; } str[s] = '\0'; if (str2int(str, &val)) goto fail; if (toupper((unsigned char)fmt[k]) != 'P') goto iter; dsa->fmt_p = val, k++; if (!(0 <= dsa->fmt_p && dsa->fmt_p <= 255)) goto fail; /* optional comma may follow scale factor */ if (fmt[k] == ',') k++; } /* optional iterator */ dsa->fmt_k = 1; if (isdigit((unsigned char)fmt[k])) { s = 0; while (isdigit((unsigned char)fmt[k])) { if (s == 80) goto fail; str[s++] = fmt[k++]; } str[s] = '\0'; if (str2int(str, &val)) goto fail; iter: dsa->fmt_k = val; if (!(1 <= dsa->fmt_k && dsa->fmt_k <= 255)) goto fail; } /* format code */ dsa->fmt_f = toupper((unsigned char)fmt[k++]); if (!(dsa->fmt_f == 'D' || dsa->fmt_f == 'E' || dsa->fmt_f == 'F' || dsa->fmt_f == 'G' || dsa->fmt_f == 'I')) goto fail; /* field width */ if (!isdigit((unsigned char)fmt[k])) goto fail; s = 0; while (isdigit((unsigned char)fmt[k])) { if (s == 80) goto fail; str[s++] = fmt[k++]; } str[s] = '\0'; if (str2int(str, &dsa->fmt_w)) goto fail; if (!(1 <= dsa->fmt_w && dsa->fmt_w <= 255)) goto fail; /* optional number of decimal places after point */ dsa->fmt_d = 0; if (fmt[k] == '.') { k++; if (!isdigit((unsigned char)fmt[k])) goto fail; s = 0; while (isdigit((unsigned char)fmt[k])) { if (s == 80) goto fail; str[s++] = fmt[k++]; } str[s] = '\0'; if (str2int(str, &dsa->fmt_d)) goto fail; if (!(0 <= dsa->fmt_d && dsa->fmt_d <= 255)) goto fail; } /* last character should be right parenthesis */ if (!(fmt[k] == ')' && fmt[k+1] == '\0')) goto fail; return 0; } /*********************************************************************** * read_int_array - read array of integer type * * This routine reads an integer array from the input text file, where * name is array name, fmt is Fortran format specification that controls * reading, n is number of array elements, val is array of integer type. * If the array was read successful, the routine returns zero, otherwise * non-zero. */ static int read_int_array(struct dsa *dsa, char *name, char *fmt, int n, int val[]) { int k, pos; char str[80+1]; if (parse_fmt(dsa, fmt)) return 1; if (!(dsa->fmt_f == 'I' && dsa->fmt_w <= 80 && dsa->fmt_k * dsa->fmt_w <= 80)) { xprintf( "%s:%d: can't read array `%s' - invalid format `%s'\n", dsa->fname, dsa->seqn, name, fmt); return 1; } for (k = 1, pos = INT_MAX; k <= n; k++, pos++) { if (pos >= dsa->fmt_k) { if (read_card(dsa)) return 1; pos = 0; } memcpy(str, dsa->card + dsa->fmt_w * pos, dsa->fmt_w); str[dsa->fmt_w] = '\0'; strspx(str); if (str2int(str, &val[k])) { xprintf( "%s:%d: can't read array `%s' - invalid value `%s'\n", dsa->fname, dsa->seqn, name, str); return 1; } } return 0; } /*********************************************************************** * read_real_array - read array of real type * * This routine reads a real array from the input text file, where name * is array name, fmt is Fortran format specification that controls * reading, n is number of array elements, val is array of real type. * If the array was read successful, the routine returns zero, otherwise * non-zero. */ static int read_real_array(struct dsa *dsa, char *name, char *fmt, int n, double val[]) { int k, pos; char str[80+1], *ptr; if (parse_fmt(dsa, fmt)) return 1; if (!(dsa->fmt_f != 'I' && dsa->fmt_w <= 80 && dsa->fmt_k * dsa->fmt_w <= 80)) { xprintf( "%s:%d: can't read array `%s' - invalid format `%s'\n", dsa->fname, dsa->seqn, name, fmt); return 1; } for (k = 1, pos = INT_MAX; k <= n; k++, pos++) { if (pos >= dsa->fmt_k) { if (read_card(dsa)) return 1; pos = 0; } memcpy(str, dsa->card + dsa->fmt_w * pos, dsa->fmt_w); str[dsa->fmt_w] = '\0'; strspx(str); if (strchr(str, '.') == NULL && strcmp(str, "0")) { xprintf("%s(%d): can't read array `%s' - value `%s' has no " "decimal point\n", dsa->fname, dsa->seqn, name, str); return 1; } /* sometimes lower case letters appear */ for (ptr = str; *ptr; ptr++) *ptr = (char)toupper((unsigned char)*ptr); ptr = strchr(str, 'D'); if (ptr != NULL) *ptr = 'E'; /* value may appear with decimal exponent but without letters E or D (for example, -123.456-012), so missing letter should be inserted */ ptr = strchr(str+1, '+'); if (ptr == NULL) ptr = strchr(str+1, '-'); if (ptr != NULL && *(ptr-1) != 'E') { xassert(strlen(str) < 80); memmove(ptr+1, ptr, strlen(ptr)+1); *ptr = 'E'; } if (str2num(str, &val[k])) { xprintf( "%s:%d: can't read array `%s' - invalid value `%s'\n", dsa->fname, dsa->seqn, name, str); return 1; } } return 0; } HBM *hbm_read_mat(const char *fname) { struct dsa _dsa, *dsa = &_dsa; HBM *hbm = NULL; dsa->fname = fname; xprintf("hbm_read_mat: reading matrix from `%s'...\n", dsa->fname); dsa->fp = fopen(dsa->fname, "r"); if (dsa->fp == NULL) { xprintf("hbm_read_mat: unable to open `%s' - %s\n", dsa->fname, strerror(errno)); goto fail; } dsa->seqn = 0; hbm = xmalloc(sizeof(HBM)); memset(hbm, 0, sizeof(HBM)); /* read the first heading card */ if (read_card(dsa)) goto fail; memcpy(hbm->title, dsa->card, 72), hbm->title[72] = '\0'; strtrim(hbm->title); xprintf("%s\n", hbm->title); memcpy(hbm->key, dsa->card+72, 8), hbm->key[8] = '\0'; strspx(hbm->key); xprintf("key = %s\n", hbm->key); /* read the second heading card */ if (read_card(dsa)) goto fail; if (scan_int(dsa, "totcrd", 0, 14, &hbm->totcrd)) goto fail; if (scan_int(dsa, "ptrcrd", 14, 14, &hbm->ptrcrd)) goto fail; if (scan_int(dsa, "indcrd", 28, 14, &hbm->indcrd)) goto fail; if (scan_int(dsa, "valcrd", 42, 14, &hbm->valcrd)) goto fail; if (scan_int(dsa, "rhscrd", 56, 14, &hbm->rhscrd)) goto fail; xprintf("totcrd = %d; ptrcrd = %d; indcrd = %d; valcrd = %d; rhsc" "rd = %d\n", hbm->totcrd, hbm->ptrcrd, hbm->indcrd, hbm->valcrd, hbm->rhscrd); /* read the third heading card */ if (read_card(dsa)) goto fail; memcpy(hbm->mxtype, dsa->card, 3), hbm->mxtype[3] = '\0'; if (strchr("RCP", hbm->mxtype[0]) == NULL || strchr("SUHZR", hbm->mxtype[1]) == NULL || strchr("AE", hbm->mxtype[2]) == NULL) { xprintf("%s:%d: matrix type `%s' not recognised\n", dsa->fname, dsa->seqn, hbm->mxtype); goto fail; } if (scan_int(dsa, "nrow", 14, 14, &hbm->nrow)) goto fail; if (scan_int(dsa, "ncol", 28, 14, &hbm->ncol)) goto fail; if (scan_int(dsa, "nnzero", 42, 14, &hbm->nnzero)) goto fail; if (scan_int(dsa, "neltvl", 56, 14, &hbm->neltvl)) goto fail; xprintf("mxtype = %s; nrow = %d; ncol = %d; nnzero = %d; neltvl =" " %d\n", hbm->mxtype, hbm->nrow, hbm->ncol, hbm->nnzero, hbm->neltvl); /* read the fourth heading card */ if (read_card(dsa)) goto fail; memcpy(hbm->ptrfmt, dsa->card, 16), hbm->ptrfmt[16] = '\0'; strspx(hbm->ptrfmt); memcpy(hbm->indfmt, dsa->card+16, 16), hbm->indfmt[16] = '\0'; strspx(hbm->indfmt); memcpy(hbm->valfmt, dsa->card+32, 20), hbm->valfmt[20] = '\0'; strspx(hbm->valfmt); memcpy(hbm->rhsfmt, dsa->card+52, 20), hbm->rhsfmt[20] = '\0'; strspx(hbm->rhsfmt); xprintf("ptrfmt = %s; indfmt = %s; valfmt = %s; rhsfmt = %s\n", hbm->ptrfmt, hbm->indfmt, hbm->valfmt, hbm->rhsfmt); /* read the fifth heading card (optional) */ if (hbm->rhscrd <= 0) { strcpy(hbm->rhstyp, "???"); hbm->nrhs = 0; hbm->nrhsix = 0; } else { if (read_card(dsa)) goto fail; memcpy(hbm->rhstyp, dsa->card, 3), hbm->rhstyp[3] = '\0'; if (scan_int(dsa, "nrhs", 14, 14, &hbm->nrhs)) goto fail; if (scan_int(dsa, "nrhsix", 28, 14, &hbm->nrhsix)) goto fail; xprintf("rhstyp = `%s'; nrhs = %d; nrhsix = %d\n", hbm->rhstyp, hbm->nrhs, hbm->nrhsix); } /* read matrix structure */ hbm->colptr = xcalloc(1+hbm->ncol+1, sizeof(int)); if (read_int_array(dsa, "colptr", hbm->ptrfmt, hbm->ncol+1, hbm->colptr)) goto fail; hbm->rowind = xcalloc(1+hbm->nnzero, sizeof(int)); if (read_int_array(dsa, "rowind", hbm->indfmt, hbm->nnzero, hbm->rowind)) goto fail; /* read matrix values */ if (hbm->valcrd <= 0) goto done; if (hbm->mxtype[2] == 'A') { /* assembled matrix */ hbm->values = xcalloc(1+hbm->nnzero, sizeof(double)); if (read_real_array(dsa, "values", hbm->valfmt, hbm->nnzero, hbm->values)) goto fail; } else { /* elemental (unassembled) matrix */ hbm->values = xcalloc(1+hbm->neltvl, sizeof(double)); if (read_real_array(dsa, "values", hbm->valfmt, hbm->neltvl, hbm->values)) goto fail; } /* read right-hand sides */ if (hbm->nrhs <= 0) goto done; if (hbm->rhstyp[0] == 'F') { /* dense format */ hbm->nrhsvl = hbm->nrow * hbm->nrhs; hbm->rhsval = xcalloc(1+hbm->nrhsvl, sizeof(double)); if (read_real_array(dsa, "rhsval", hbm->rhsfmt, hbm->nrhsvl, hbm->rhsval)) goto fail; } else if (hbm->rhstyp[0] == 'M' && hbm->mxtype[2] == 'A') { /* sparse format */ /* read pointers */ hbm->rhsptr = xcalloc(1+hbm->nrhs+1, sizeof(int)); if (read_int_array(dsa, "rhsptr", hbm->ptrfmt, hbm->nrhs+1, hbm->rhsptr)) goto fail; /* read sparsity pattern */ hbm->rhsind = xcalloc(1+hbm->nrhsix, sizeof(int)); if (read_int_array(dsa, "rhsind", hbm->indfmt, hbm->nrhsix, hbm->rhsind)) goto fail; /* read values */ hbm->rhsval = xcalloc(1+hbm->nrhsix, sizeof(double)); if (read_real_array(dsa, "rhsval", hbm->rhsfmt, hbm->nrhsix, hbm->rhsval)) goto fail; } else if (hbm->rhstyp[0] == 'M' && hbm->mxtype[2] == 'E') { /* elemental format */ hbm->rhsval = xcalloc(1+hbm->nrhsvl, sizeof(double)); if (read_real_array(dsa, "rhsval", hbm->rhsfmt, hbm->nrhsvl, hbm->rhsval)) goto fail; } else { xprintf("%s:%d: right-hand side type `%c' not recognised\n", dsa->fname, dsa->seqn, hbm->rhstyp[0]); goto fail; } /* read starting guesses */ if (hbm->rhstyp[1] == 'G') { hbm->nguess = hbm->nrow * hbm->nrhs; hbm->sguess = xcalloc(1+hbm->nguess, sizeof(double)); if (read_real_array(dsa, "sguess", hbm->rhsfmt, hbm->nguess, hbm->sguess)) goto fail; } /* read solution vectors */ if (hbm->rhstyp[2] == 'X') { hbm->nexact = hbm->nrow * hbm->nrhs; hbm->xexact = xcalloc(1+hbm->nexact, sizeof(double)); if (read_real_array(dsa, "xexact", hbm->rhsfmt, hbm->nexact, hbm->xexact)) goto fail; } done: /* reading has been completed */ xprintf("hbm_read_mat: %d cards were read\n", dsa->seqn); fclose(dsa->fp); return hbm; fail: /* something wrong in Danish kingdom */ if (hbm != NULL) { if (hbm->colptr != NULL) xfree(hbm->colptr); if (hbm->rowind != NULL) xfree(hbm->rowind); if (hbm->rhsptr != NULL) xfree(hbm->rhsptr); if (hbm->rhsind != NULL) xfree(hbm->rhsind); if (hbm->values != NULL) xfree(hbm->values); if (hbm->rhsval != NULL) xfree(hbm->rhsval); if (hbm->sguess != NULL) xfree(hbm->sguess); if (hbm->xexact != NULL) xfree(hbm->xexact); xfree(hbm); } if (dsa->fp != NULL) fclose(dsa->fp); return NULL; } /*********************************************************************** * NAME * * hbm_free_mat - free sparse matrix in Harwell-Boeing format * * SYNOPSIS * * #include "glphbm.h" * void hbm_free_mat(HBM *hbm); * * DESCRIPTION * * The hbm_free_mat routine frees all the memory allocated to the data * structure containing a sparse matrix in the Harwell-Boeing format. */ void hbm_free_mat(HBM *hbm) { if (hbm->colptr != NULL) xfree(hbm->colptr); if (hbm->rowind != NULL) xfree(hbm->rowind); if (hbm->rhsptr != NULL) xfree(hbm->rhsptr); if (hbm->rhsind != NULL) xfree(hbm->rhsind); if (hbm->values != NULL) xfree(hbm->values); if (hbm->rhsval != NULL) xfree(hbm->rhsval); if (hbm->sguess != NULL) xfree(hbm->sguess); if (hbm->xexact != NULL) xfree(hbm->xexact); xfree(hbm); return; } /* eof */ sources_5316/external/glpk/glplpx01.c0000644000176700017670000013752011630513007016321 0ustar paulpaul/* glplpx01.c (obsolete API routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" struct LPXCPS { /* control parameters and statistics */ int msg_lev; /* level of messages output by the solver: 0 - no output 1 - error messages only 2 - normal output 3 - full output (includes informational messages) */ int scale; /* scaling option: 0 - no scaling 1 - equilibration scaling 2 - geometric mean scaling 3 - geometric mean scaling, then equilibration scaling */ int dual; /* dual simplex option: 0 - use primal simplex 1 - use dual simplex */ int price; /* pricing option (for both primal and dual simplex): 0 - textbook pricing 1 - steepest edge pricing */ double relax; /* relaxation parameter used in the ratio test; if it is zero, the textbook ratio test is used; if it is non-zero (should be positive), Harris' two-pass ratio test is used; in the latter case on the first pass basic variables (in the case of primal simplex) or reduced costs of non-basic variables (in the case of dual simplex) are allowed to slightly violate their bounds, but not more than (relax * tol_bnd) or (relax * tol_dj) (thus, relax is a percentage of tol_bnd or tol_dj) */ double tol_bnd; /* relative tolerance used to check if the current basic solution is primal feasible */ double tol_dj; /* absolute tolerance used to check if the current basic solution is dual feasible */ double tol_piv; /* relative tolerance used to choose eligible pivotal elements of the simplex table in the ratio test */ int round; /* solution rounding option: 0 - report all computed values and reduced costs "as is" 1 - if possible (allowed by the tolerances), replace computed values and reduced costs which are close to zero by exact zeros */ double obj_ll; /* lower limit of the objective function; if on the phase II the objective function reaches this limit and continues decreasing, the solver stops the search */ double obj_ul; /* upper limit of the objective function; if on the phase II the objective function reaches this limit and continues increasing, the solver stops the search */ int it_lim; /* simplex iterations limit; if this value is positive, it is decreased by one each time when one simplex iteration has been performed, and reaching zero value signals the solver to stop the search; negative value means no iterations limit */ double tm_lim; /* searching time limit, in seconds; if this value is positive, it is decreased each time when one simplex iteration has been performed by the amount of time spent for the iteration, and reaching zero value signals the solver to stop the search; negative value means no time limit */ int out_frq; /* output frequency, in iterations; this parameter specifies how frequently the solver sends information about the solution to the standard output */ double out_dly; /* output delay, in seconds; this parameter specifies how long the solver should delay sending information about the solution to the standard output; zero value means no delay */ int branch; /* MIP */ /* branching heuristic: 0 - branch on first variable 1 - branch on last variable 2 - branch using heuristic by Driebeck and Tomlin 3 - branch on most fractional variable */ int btrack; /* MIP */ /* backtracking heuristic: 0 - select most recent node (depth first search) 1 - select earliest node (breadth first search) 2 - select node using the best projection heuristic 3 - select node with best local bound */ double tol_int; /* MIP */ /* absolute tolerance used to check if the current basic solution is integer feasible */ double tol_obj; /* MIP */ /* relative tolerance used to check if the value of the objective function is not better than in the best known integer feasible solution */ int mps_info; /* lpx_write_mps */ /* if this flag is set, the routine lpx_write_mps outputs several comment cards that contains some information about the problem; otherwise the routine outputs no comment cards */ int mps_obj; /* lpx_write_mps */ /* this parameter tells the routine lpx_write_mps how to output the objective function row: 0 - never output objective function row 1 - always output objective function row 2 - output objective function row if and only if the problem has no free rows */ int mps_orig; /* lpx_write_mps */ /* if this flag is set, the routine lpx_write_mps uses original row and column symbolic names; otherwise the routine generates plain names using ordinal numbers of rows and columns */ int mps_wide; /* lpx_write_mps */ /* if this flag is set, the routine lpx_write_mps uses all data fields; otherwise the routine keeps fields 5 and 6 empty */ int mps_free; /* lpx_write_mps */ /* if this flag is set, the routine lpx_write_mps omits column and vector names everytime if possible (free style); otherwise the routine never omits these names (pedantic style) */ int mps_skip; /* lpx_write_mps */ /* if this flag is set, the routine lpx_write_mps skips empty columns (i.e. which has no constraint coefficients); otherwise the routine outputs all columns */ int lpt_orig; /* lpx_write_lpt */ /* if this flag is set, the routine lpx_write_lpt uses original row and column symbolic names; otherwise the routine generates plain names using ordinal numbers of rows and columns */ int presol; /* lpx_simplex */ /* LP presolver option: 0 - do not use LP presolver 1 - use LP presolver */ int binarize; /* lpx_intopt */ /* if this flag is set, the routine lpx_intopt replaces integer columns by binary ones */ int use_cuts; /* lpx_intopt */ /* if this flag is set, the routine lpx_intopt tries generating cutting planes: LPX_C_COVER - mixed cover cuts LPX_C_CLIQUE - clique cuts LPX_C_GOMORY - Gomory's mixed integer cuts LPX_C_ALL - all cuts */ double mip_gap; /* MIP */ /* relative MIP gap tolerance */ }; LPX *lpx_create_prob(void) { /* create problem object */ return glp_create_prob(); } void lpx_set_prob_name(LPX *lp, const char *name) { /* assign (change) problem name */ glp_set_prob_name(lp, name); return; } void lpx_set_obj_name(LPX *lp, const char *name) { /* assign (change) objective function name */ glp_set_obj_name(lp, name); return; } void lpx_set_obj_dir(LPX *lp, int dir) { /* set (change) optimization direction flag */ glp_set_obj_dir(lp, dir - LPX_MIN + GLP_MIN); return; } int lpx_add_rows(LPX *lp, int nrs) { /* add new rows to problem object */ return glp_add_rows(lp, nrs); } int lpx_add_cols(LPX *lp, int ncs) { /* add new columns to problem object */ return glp_add_cols(lp, ncs); } void lpx_set_row_name(LPX *lp, int i, const char *name) { /* assign (change) row name */ glp_set_row_name(lp, i, name); return; } void lpx_set_col_name(LPX *lp, int j, const char *name) { /* assign (change) column name */ glp_set_col_name(lp, j, name); return; } void lpx_set_row_bnds(LPX *lp, int i, int type, double lb, double ub) { /* set (change) row bounds */ glp_set_row_bnds(lp, i, type - LPX_FR + GLP_FR, lb, ub); return; } void lpx_set_col_bnds(LPX *lp, int j, int type, double lb, double ub) { /* set (change) column bounds */ glp_set_col_bnds(lp, j, type - LPX_FR + GLP_FR, lb, ub); return; } void lpx_set_obj_coef(glp_prob *lp, int j, double coef) { /* set (change) obj. coefficient or constant term */ glp_set_obj_coef(lp, j, coef); return; } void lpx_set_mat_row(LPX *lp, int i, int len, const int ind[], const double val[]) { /* set (replace) row of the constraint matrix */ glp_set_mat_row(lp, i, len, ind, val); return; } void lpx_set_mat_col(LPX *lp, int j, int len, const int ind[], const double val[]) { /* set (replace) column of the constraint matrix */ glp_set_mat_col(lp, j, len, ind, val); return; } void lpx_load_matrix(LPX *lp, int ne, const int ia[], const int ja[], const double ar[]) { /* load (replace) the whole constraint matrix */ glp_load_matrix(lp, ne, ia, ja, ar); return; } void lpx_del_rows(LPX *lp, int nrs, const int num[]) { /* delete specified rows from problem object */ glp_del_rows(lp, nrs, num); return; } void lpx_del_cols(LPX *lp, int ncs, const int num[]) { /* delete specified columns from problem object */ glp_del_cols(lp, ncs, num); return; } void lpx_delete_prob(LPX *lp) { /* delete problem object */ glp_delete_prob(lp); return; } const char *lpx_get_prob_name(LPX *lp) { /* retrieve problem name */ return glp_get_prob_name(lp); } const char *lpx_get_obj_name(LPX *lp) { /* retrieve objective function name */ return glp_get_obj_name(lp); } int lpx_get_obj_dir(LPX *lp) { /* retrieve optimization direction flag */ return glp_get_obj_dir(lp) - GLP_MIN + LPX_MIN; } int lpx_get_num_rows(LPX *lp) { /* retrieve number of rows */ return glp_get_num_rows(lp); } int lpx_get_num_cols(LPX *lp) { /* retrieve number of columns */ return glp_get_num_cols(lp); } const char *lpx_get_row_name(LPX *lp, int i) { /* retrieve row name */ return glp_get_row_name(lp, i); } const char *lpx_get_col_name(LPX *lp, int j) { /* retrieve column name */ return glp_get_col_name(lp, j); } int lpx_get_row_type(LPX *lp, int i) { /* retrieve row type */ return glp_get_row_type(lp, i) - GLP_FR + LPX_FR; } double lpx_get_row_lb(glp_prob *lp, int i) { /* retrieve row lower bound */ double lb; lb = glp_get_row_lb(lp, i); if (lb == -DBL_MAX) lb = 0.0; return lb; } double lpx_get_row_ub(glp_prob *lp, int i) { /* retrieve row upper bound */ double ub; ub = glp_get_row_ub(lp, i); if (ub == +DBL_MAX) ub = 0.0; return ub; } void lpx_get_row_bnds(glp_prob *lp, int i, int *typx, double *lb, double *ub) { /* retrieve row bounds */ if (typx != NULL) *typx = lpx_get_row_type(lp, i); if (lb != NULL) *lb = lpx_get_row_lb(lp, i); if (ub != NULL) *ub = lpx_get_row_ub(lp, i); return; } int lpx_get_col_type(LPX *lp, int j) { /* retrieve column type */ return glp_get_col_type(lp, j) - GLP_FR + LPX_FR; } double lpx_get_col_lb(glp_prob *lp, int j) { /* retrieve column lower bound */ double lb; lb = glp_get_col_lb(lp, j); if (lb == -DBL_MAX) lb = 0.0; return lb; } double lpx_get_col_ub(glp_prob *lp, int j) { /* retrieve column upper bound */ double ub; ub = glp_get_col_ub(lp, j); if (ub == +DBL_MAX) ub = 0.0; return ub; } void lpx_get_col_bnds(glp_prob *lp, int j, int *typx, double *lb, double *ub) { /* retrieve column bounds */ if (typx != NULL) *typx = lpx_get_col_type(lp, j); if (lb != NULL) *lb = lpx_get_col_lb(lp, j); if (ub != NULL) *ub = lpx_get_col_ub(lp, j); return; } double lpx_get_obj_coef(LPX *lp, int j) { /* retrieve obj. coefficient or constant term */ return glp_get_obj_coef(lp, j); } int lpx_get_num_nz(LPX *lp) { /* retrieve number of constraint coefficients */ return glp_get_num_nz(lp); } int lpx_get_mat_row(LPX *lp, int i, int ind[], double val[]) { /* retrieve row of the constraint matrix */ return glp_get_mat_row(lp, i, ind, val); } int lpx_get_mat_col(LPX *lp, int j, int ind[], double val[]) { /* retrieve column of the constraint matrix */ return glp_get_mat_col(lp, j, ind, val); } void lpx_create_index(LPX *lp) { /* create the name index */ glp_create_index(lp); return; } int lpx_find_row(LPX *lp, const char *name) { /* find row by its name */ return glp_find_row(lp, name); } int lpx_find_col(LPX *lp, const char *name) { /* find column by its name */ return glp_find_col(lp, name); } void lpx_delete_index(LPX *lp) { /* delete the name index */ glp_delete_index(lp); return; } void lpx_scale_prob(LPX *lp) { /* scale problem data */ switch (lpx_get_int_parm(lp, LPX_K_SCALE)) { case 0: /* no scaling */ glp_unscale_prob(lp); break; case 1: /* equilibration scaling */ glp_scale_prob(lp, GLP_SF_EQ); break; case 2: /* geometric mean scaling */ glp_scale_prob(lp, GLP_SF_GM); break; case 3: /* geometric mean scaling, then equilibration scaling */ glp_scale_prob(lp, GLP_SF_GM | GLP_SF_EQ); break; default: xassert(lp != lp); } return; } void lpx_unscale_prob(LPX *lp) { /* unscale problem data */ glp_unscale_prob(lp); return; } void lpx_set_row_stat(LPX *lp, int i, int stat) { /* set (change) row status */ glp_set_row_stat(lp, i, stat - LPX_BS + GLP_BS); return; } void lpx_set_col_stat(LPX *lp, int j, int stat) { /* set (change) column status */ glp_set_col_stat(lp, j, stat - LPX_BS + GLP_BS); return; } void lpx_std_basis(LPX *lp) { /* construct standard initial LP basis */ glp_std_basis(lp); return; } void lpx_adv_basis(LPX *lp) { /* construct advanced initial LP basis */ glp_adv_basis(lp, 0); return; } void lpx_cpx_basis(LPX *lp) { /* construct Bixby's initial LP basis */ glp_cpx_basis(lp); return; } static void fill_smcp(LPX *lp, glp_smcp *parm) { glp_init_smcp(parm); switch (lpx_get_int_parm(lp, LPX_K_MSGLEV)) { case 0: parm->msg_lev = GLP_MSG_OFF; break; case 1: parm->msg_lev = GLP_MSG_ERR; break; case 2: parm->msg_lev = GLP_MSG_ON; break; case 3: parm->msg_lev = GLP_MSG_ALL; break; default: xassert(lp != lp); } switch (lpx_get_int_parm(lp, LPX_K_DUAL)) { case 0: parm->meth = GLP_PRIMAL; break; case 1: parm->meth = GLP_DUAL; break; default: xassert(lp != lp); } switch (lpx_get_int_parm(lp, LPX_K_PRICE)) { case 0: parm->pricing = GLP_PT_STD; break; case 1: parm->pricing = GLP_PT_PSE; break; default: xassert(lp != lp); } if (lpx_get_real_parm(lp, LPX_K_RELAX) == 0.0) parm->r_test = GLP_RT_STD; else parm->r_test = GLP_RT_HAR; parm->tol_bnd = lpx_get_real_parm(lp, LPX_K_TOLBND); parm->tol_dj = lpx_get_real_parm(lp, LPX_K_TOLDJ); parm->tol_piv = lpx_get_real_parm(lp, LPX_K_TOLPIV); parm->obj_ll = lpx_get_real_parm(lp, LPX_K_OBJLL); parm->obj_ul = lpx_get_real_parm(lp, LPX_K_OBJUL); if (lpx_get_int_parm(lp, LPX_K_ITLIM) < 0) parm->it_lim = INT_MAX; else parm->it_lim = lpx_get_int_parm(lp, LPX_K_ITLIM); if (lpx_get_real_parm(lp, LPX_K_TMLIM) < 0.0) parm->tm_lim = INT_MAX; else parm->tm_lim = (int)(1000.0 * lpx_get_real_parm(lp, LPX_K_TMLIM)); parm->out_frq = lpx_get_int_parm(lp, LPX_K_OUTFRQ); parm->out_dly = (int)(1000.0 * lpx_get_real_parm(lp, LPX_K_OUTDLY)); switch (lpx_get_int_parm(lp, LPX_K_PRESOL)) { case 0: parm->presolve = GLP_OFF; break; case 1: parm->presolve = GLP_ON; break; default: xassert(lp != lp); } return; } int lpx_simplex(LPX *lp) { /* easy-to-use driver to the simplex method */ glp_smcp parm; int ret; fill_smcp(lp, &parm); ret = glp_simplex(lp, &parm); switch (ret) { case 0: ret = LPX_E_OK; break; case GLP_EBADB: case GLP_ESING: case GLP_ECOND: case GLP_EBOUND: ret = LPX_E_FAULT; break; case GLP_EFAIL: ret = LPX_E_SING; break; case GLP_EOBJLL: ret = LPX_E_OBJLL; break; case GLP_EOBJUL: ret = LPX_E_OBJUL; break; case GLP_EITLIM: ret = LPX_E_ITLIM; break; case GLP_ETMLIM: ret = LPX_E_TMLIM; break; case GLP_ENOPFS: ret = LPX_E_NOPFS; break; case GLP_ENODFS: ret = LPX_E_NODFS; break; default: xassert(ret != ret); } return ret; } int lpx_exact(LPX *lp) { /* easy-to-use driver to the exact simplex method */ glp_smcp parm; int ret; fill_smcp(lp, &parm); ret = glp_exact(lp, &parm); switch (ret) { case 0: ret = LPX_E_OK; break; case GLP_EBADB: case GLP_ESING: case GLP_EBOUND: case GLP_EFAIL: ret = LPX_E_FAULT; break; case GLP_EITLIM: ret = LPX_E_ITLIM; break; case GLP_ETMLIM: ret = LPX_E_TMLIM; break; default: xassert(ret != ret); } return ret; } int lpx_get_status(glp_prob *lp) { /* retrieve generic status of basic solution */ int status; switch (glp_get_status(lp)) { case GLP_OPT: status = LPX_OPT; break; case GLP_FEAS: status = LPX_FEAS; break; case GLP_INFEAS: status = LPX_INFEAS; break; case GLP_NOFEAS: status = LPX_NOFEAS; break; case GLP_UNBND: status = LPX_UNBND; break; case GLP_UNDEF: status = LPX_UNDEF; break; default: xassert(lp != lp); } return status; } int lpx_get_prim_stat(glp_prob *lp) { /* retrieve status of primal basic solution */ return glp_get_prim_stat(lp) - GLP_UNDEF + LPX_P_UNDEF; } int lpx_get_dual_stat(glp_prob *lp) { /* retrieve status of dual basic solution */ return glp_get_dual_stat(lp) - GLP_UNDEF + LPX_D_UNDEF; } double lpx_get_obj_val(LPX *lp) { /* retrieve objective value (basic solution) */ return glp_get_obj_val(lp); } int lpx_get_row_stat(LPX *lp, int i) { /* retrieve row status (basic solution) */ return glp_get_row_stat(lp, i) - GLP_BS + LPX_BS; } double lpx_get_row_prim(LPX *lp, int i) { /* retrieve row primal value (basic solution) */ return glp_get_row_prim(lp, i); } double lpx_get_row_dual(LPX *lp, int i) { /* retrieve row dual value (basic solution) */ return glp_get_row_dual(lp, i); } void lpx_get_row_info(glp_prob *lp, int i, int *tagx, double *vx, double *dx) { /* obtain row solution information */ if (tagx != NULL) *tagx = lpx_get_row_stat(lp, i); if (vx != NULL) *vx = lpx_get_row_prim(lp, i); if (dx != NULL) *dx = lpx_get_row_dual(lp, i); return; } int lpx_get_col_stat(LPX *lp, int j) { /* retrieve column status (basic solution) */ return glp_get_col_stat(lp, j) - GLP_BS + LPX_BS; } double lpx_get_col_prim(LPX *lp, int j) { /* retrieve column primal value (basic solution) */ return glp_get_col_prim(lp, j); } double lpx_get_col_dual(glp_prob *lp, int j) { /* retrieve column dual value (basic solution) */ return glp_get_col_dual(lp, j); } void lpx_get_col_info(glp_prob *lp, int j, int *tagx, double *vx, double *dx) { /* obtain column solution information */ if (tagx != NULL) *tagx = lpx_get_col_stat(lp, j); if (vx != NULL) *vx = lpx_get_col_prim(lp, j); if (dx != NULL) *dx = lpx_get_col_dual(lp, j); return; } int lpx_get_ray_info(LPX *lp) { /* determine what causes primal unboundness */ return glp_get_unbnd_ray(lp); } void lpx_check_kkt(LPX *lp, int scaled, LPXKKT *kkt) { /* check Karush-Kuhn-Tucker conditions */ int ae_ind, re_ind; double ae_max, re_max; xassert(scaled == scaled); _glp_check_kkt(lp, GLP_SOL, GLP_KKT_PE, &ae_max, &ae_ind, &re_max, &re_ind); kkt->pe_ae_max = ae_max; kkt->pe_ae_row = ae_ind; kkt->pe_re_max = re_max; kkt->pe_re_row = re_ind; if (re_max <= 1e-9) kkt->pe_quality = 'H'; else if (re_max <= 1e-6) kkt->pe_quality = 'M'; else if (re_max <= 1e-3) kkt->pe_quality = 'L'; else kkt->pe_quality = '?'; _glp_check_kkt(lp, GLP_SOL, GLP_KKT_PB, &ae_max, &ae_ind, &re_max, &re_ind); kkt->pb_ae_max = ae_max; kkt->pb_ae_ind = ae_ind; kkt->pb_re_max = re_max; kkt->pb_re_ind = re_ind; if (re_max <= 1e-9) kkt->pb_quality = 'H'; else if (re_max <= 1e-6) kkt->pb_quality = 'M'; else if (re_max <= 1e-3) kkt->pb_quality = 'L'; else kkt->pb_quality = '?'; _glp_check_kkt(lp, GLP_SOL, GLP_KKT_DE, &ae_max, &ae_ind, &re_max, &re_ind); kkt->de_ae_max = ae_max; if (ae_ind == 0) kkt->de_ae_col = 0; else kkt->de_ae_col = ae_ind - lp->m; kkt->de_re_max = re_max; if (re_ind == 0) kkt->de_re_col = 0; else kkt->de_re_col = ae_ind - lp->m; if (re_max <= 1e-9) kkt->de_quality = 'H'; else if (re_max <= 1e-6) kkt->de_quality = 'M'; else if (re_max <= 1e-3) kkt->de_quality = 'L'; else kkt->de_quality = '?'; _glp_check_kkt(lp, GLP_SOL, GLP_KKT_DB, &ae_max, &ae_ind, &re_max, &re_ind); kkt->db_ae_max = ae_max; kkt->db_ae_ind = ae_ind; kkt->db_re_max = re_max; kkt->db_re_ind = re_ind; if (re_max <= 1e-9) kkt->db_quality = 'H'; else if (re_max <= 1e-6) kkt->db_quality = 'M'; else if (re_max <= 1e-3) kkt->db_quality = 'L'; else kkt->db_quality = '?'; kkt->cs_ae_max = 0.0, kkt->cs_ae_ind = 0; kkt->cs_re_max = 0.0, kkt->cs_re_ind = 0; kkt->cs_quality = 'H'; return; } int lpx_warm_up(LPX *lp) { /* "warm up" LP basis */ int ret; ret = glp_warm_up(lp); if (ret == 0) ret = LPX_E_OK; else if (ret == GLP_EBADB) ret = LPX_E_BADB; else if (ret == GLP_ESING) ret = LPX_E_SING; else if (ret == GLP_ECOND) ret = LPX_E_SING; else xassert(ret != ret); return ret; } int lpx_eval_tab_row(LPX *lp, int k, int ind[], double val[]) { /* compute row of the simplex tableau */ return glp_eval_tab_row(lp, k, ind, val); } int lpx_eval_tab_col(LPX *lp, int k, int ind[], double val[]) { /* compute column of the simplex tableau */ return glp_eval_tab_col(lp, k, ind, val); } int lpx_transform_row(LPX *lp, int len, int ind[], double val[]) { /* transform explicitly specified row */ return glp_transform_row(lp, len, ind, val); } int lpx_transform_col(LPX *lp, int len, int ind[], double val[]) { /* transform explicitly specified column */ return glp_transform_col(lp, len, ind, val); } int lpx_prim_ratio_test(LPX *lp, int len, const int ind[], const double val[], int how, double tol) { /* perform primal ratio test */ int piv; piv = glp_prim_rtest(lp, len, ind, val, how, tol); xassert(0 <= piv && piv <= len); return piv == 0 ? 0 : ind[piv]; } int lpx_dual_ratio_test(LPX *lp, int len, const int ind[], const double val[], int how, double tol) { /* perform dual ratio test */ int piv; piv = glp_dual_rtest(lp, len, ind, val, how, tol); xassert(0 <= piv && piv <= len); return piv == 0 ? 0 : ind[piv]; } int lpx_interior(LPX *lp) { /* easy-to-use driver to the interior-point method */ int ret; ret = glp_interior(lp, NULL); switch (ret) { case 0: ret = LPX_E_OK; break; case GLP_EFAIL: ret = LPX_E_FAULT; break; case GLP_ENOFEAS: ret = LPX_E_NOFEAS; break; case GLP_ENOCVG: ret = LPX_E_NOCONV; break; case GLP_EITLIM: ret = LPX_E_ITLIM; break; case GLP_EINSTAB: ret = LPX_E_INSTAB; break; default: xassert(ret != ret); } return ret; } int lpx_ipt_status(glp_prob *lp) { /* retrieve status of interior-point solution */ int status; switch (glp_ipt_status(lp)) { case GLP_UNDEF: status = LPX_T_UNDEF; break; case GLP_OPT: status = LPX_T_OPT; break; default: xassert(lp != lp); } return status; } double lpx_ipt_obj_val(LPX *lp) { /* retrieve objective value (interior point) */ return glp_ipt_obj_val(lp); } double lpx_ipt_row_prim(LPX *lp, int i) { /* retrieve row primal value (interior point) */ return glp_ipt_row_prim(lp, i); } double lpx_ipt_row_dual(LPX *lp, int i) { /* retrieve row dual value (interior point) */ return glp_ipt_row_dual(lp, i); } double lpx_ipt_col_prim(LPX *lp, int j) { /* retrieve column primal value (interior point) */ return glp_ipt_col_prim(lp, j); } double lpx_ipt_col_dual(LPX *lp, int j) { /* retrieve column dual value (interior point) */ return glp_ipt_col_dual(lp, j); } void lpx_set_class(LPX *lp, int klass) { /* set problem class */ xassert(lp == lp); if (!(klass == LPX_LP || klass == LPX_MIP)) xerror("lpx_set_class: invalid problem class\n"); return; } int lpx_get_class(LPX *lp) { /* determine problem klass */ return glp_get_num_int(lp) == 0 ? LPX_LP : LPX_MIP; } void lpx_set_col_kind(LPX *lp, int j, int kind) { /* set (change) column kind */ glp_set_col_kind(lp, j, kind - LPX_CV + GLP_CV); return; } int lpx_get_col_kind(LPX *lp, int j) { /* retrieve column kind */ return glp_get_col_kind(lp, j) == GLP_CV ? LPX_CV : LPX_IV; } int lpx_get_num_int(LPX *lp) { /* retrieve number of integer columns */ return glp_get_num_int(lp); } int lpx_get_num_bin(LPX *lp) { /* retrieve number of binary columns */ return glp_get_num_bin(lp); } static int solve_mip(LPX *lp, int presolve) { glp_iocp parm; int ret; glp_init_iocp(&parm); switch (lpx_get_int_parm(lp, LPX_K_MSGLEV)) { case 0: parm.msg_lev = GLP_MSG_OFF; break; case 1: parm.msg_lev = GLP_MSG_ERR; break; case 2: parm.msg_lev = GLP_MSG_ON; break; case 3: parm.msg_lev = GLP_MSG_ALL; break; default: xassert(lp != lp); } switch (lpx_get_int_parm(lp, LPX_K_BRANCH)) { case 0: parm.br_tech = GLP_BR_FFV; break; case 1: parm.br_tech = GLP_BR_LFV; break; case 2: parm.br_tech = GLP_BR_DTH; break; case 3: parm.br_tech = GLP_BR_MFV; break; default: xassert(lp != lp); } switch (lpx_get_int_parm(lp, LPX_K_BTRACK)) { case 0: parm.bt_tech = GLP_BT_DFS; break; case 1: parm.bt_tech = GLP_BT_BFS; break; case 2: parm.bt_tech = GLP_BT_BPH; break; case 3: parm.bt_tech = GLP_BT_BLB; break; default: xassert(lp != lp); } parm.tol_int = lpx_get_real_parm(lp, LPX_K_TOLINT); parm.tol_obj = lpx_get_real_parm(lp, LPX_K_TOLOBJ); if (lpx_get_real_parm(lp, LPX_K_TMLIM) < 0.0 || lpx_get_real_parm(lp, LPX_K_TMLIM) > 1e6) parm.tm_lim = INT_MAX; else parm.tm_lim = (int)(1000.0 * lpx_get_real_parm(lp, LPX_K_TMLIM)); parm.mip_gap = lpx_get_real_parm(lp, LPX_K_MIPGAP); if (lpx_get_int_parm(lp, LPX_K_USECUTS) & LPX_C_GOMORY) parm.gmi_cuts = GLP_ON; else parm.gmi_cuts = GLP_OFF; if (lpx_get_int_parm(lp, LPX_K_USECUTS) & LPX_C_MIR) parm.mir_cuts = GLP_ON; else parm.mir_cuts = GLP_OFF; if (lpx_get_int_parm(lp, LPX_K_USECUTS) & LPX_C_COVER) parm.cov_cuts = GLP_ON; else parm.cov_cuts = GLP_OFF; if (lpx_get_int_parm(lp, LPX_K_USECUTS) & LPX_C_CLIQUE) parm.clq_cuts = GLP_ON; else parm.clq_cuts = GLP_OFF; parm.presolve = presolve; if (lpx_get_int_parm(lp, LPX_K_BINARIZE)) parm.binarize = GLP_ON; ret = glp_intopt(lp, &parm); switch (ret) { case 0: ret = LPX_E_OK; break; case GLP_ENOPFS: ret = LPX_E_NOPFS; break; case GLP_ENODFS: ret = LPX_E_NODFS; break; case GLP_EBOUND: case GLP_EROOT: ret = LPX_E_FAULT; break; case GLP_EFAIL: ret = LPX_E_SING; break; case GLP_EMIPGAP: ret = LPX_E_MIPGAP; break; case GLP_ETMLIM: ret = LPX_E_TMLIM; break; default: xassert(ret != ret); } return ret; } int lpx_integer(LPX *lp) { /* easy-to-use driver to the branch-and-bound method */ return solve_mip(lp, GLP_OFF); } int lpx_intopt(LPX *lp) { /* easy-to-use driver to the branch-and-bound method */ return solve_mip(lp, GLP_ON); } int lpx_mip_status(glp_prob *lp) { /* retrieve status of MIP solution */ int status; switch (glp_mip_status(lp)) { case GLP_UNDEF: status = LPX_I_UNDEF; break; case GLP_OPT: status = LPX_I_OPT; break; case GLP_FEAS: status = LPX_I_FEAS; break; case GLP_NOFEAS: status = LPX_I_NOFEAS; break; default: xassert(lp != lp); } return status; } double lpx_mip_obj_val(LPX *lp) { /* retrieve objective value (MIP solution) */ return glp_mip_obj_val(lp); } double lpx_mip_row_val(LPX *lp, int i) { /* retrieve row value (MIP solution) */ return glp_mip_row_val(lp, i); } double lpx_mip_col_val(LPX *lp, int j) { /* retrieve column value (MIP solution) */ return glp_mip_col_val(lp, j); } void lpx_check_int(LPX *lp, LPXKKT *kkt) { /* check integer feasibility conditions */ int ae_ind, re_ind; double ae_max, re_max; _glp_check_kkt(lp, GLP_MIP, GLP_KKT_PE, &ae_max, &ae_ind, &re_max, &re_ind); kkt->pe_ae_max = ae_max; kkt->pe_ae_row = ae_ind; kkt->pe_re_max = re_max; kkt->pe_re_row = re_ind; if (re_max <= 1e-9) kkt->pe_quality = 'H'; else if (re_max <= 1e-6) kkt->pe_quality = 'M'; else if (re_max <= 1e-3) kkt->pe_quality = 'L'; else kkt->pe_quality = '?'; _glp_check_kkt(lp, GLP_MIP, GLP_KKT_PB, &ae_max, &ae_ind, &re_max, &re_ind); kkt->pb_ae_max = ae_max; kkt->pb_ae_ind = ae_ind; kkt->pb_re_max = re_max; kkt->pb_re_ind = re_ind; if (re_max <= 1e-9) kkt->pb_quality = 'H'; else if (re_max <= 1e-6) kkt->pb_quality = 'M'; else if (re_max <= 1e-3) kkt->pb_quality = 'L'; else kkt->pb_quality = '?'; return; } #if 1 /* 17/XI-2009 */ static void reset_parms(LPX *lp) { /* reset control parameters to default values */ struct LPXCPS *cps = lp->parms; xassert(cps != NULL); cps->msg_lev = 3; cps->scale = 1; cps->dual = 0; cps->price = 1; cps->relax = 0.07; cps->tol_bnd = 1e-7; cps->tol_dj = 1e-7; cps->tol_piv = 1e-9; cps->round = 0; cps->obj_ll = -DBL_MAX; cps->obj_ul = +DBL_MAX; cps->it_lim = -1; lp->it_cnt = 0; cps->tm_lim = -1.0; cps->out_frq = 200; cps->out_dly = 0.0; cps->branch = 2; cps->btrack = 3; cps->tol_int = 1e-5; cps->tol_obj = 1e-7; cps->mps_info = 1; cps->mps_obj = 2; cps->mps_orig = 0; cps->mps_wide = 1; cps->mps_free = 0; cps->mps_skip = 0; cps->lpt_orig = 0; cps->presol = 0; cps->binarize = 0; cps->use_cuts = 0; cps->mip_gap = 0.0; return; } #endif #if 1 /* 17/XI-2009 */ static struct LPXCPS *access_parms(LPX *lp) { /* allocate and initialize control parameters, if necessary */ if (lp->parms == NULL) { lp->parms = xmalloc(sizeof(struct LPXCPS)); reset_parms(lp); } return lp->parms; } #endif #if 1 /* 17/XI-2009 */ void lpx_reset_parms(LPX *lp) { /* reset control parameters to default values */ access_parms(lp); reset_parms(lp); return; } #endif void lpx_set_int_parm(LPX *lp, int parm, int val) { /* set (change) integer control parameter */ #if 0 /* 17/XI-2009 */ struct LPXCPS *cps = lp->cps; #else struct LPXCPS *cps = access_parms(lp); #endif switch (parm) { case LPX_K_MSGLEV: if (!(0 <= val && val <= 3)) xerror("lpx_set_int_parm: MSGLEV = %d; invalid value\n", val); cps->msg_lev = val; break; case LPX_K_SCALE: if (!(0 <= val && val <= 3)) xerror("lpx_set_int_parm: SCALE = %d; invalid value\n", val); cps->scale = val; break; case LPX_K_DUAL: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: DUAL = %d; invalid value\n", val); cps->dual = val; break; case LPX_K_PRICE: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: PRICE = %d; invalid value\n", val); cps->price = val; break; case LPX_K_ROUND: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: ROUND = %d; invalid value\n", val); cps->round = val; break; case LPX_K_ITLIM: cps->it_lim = val; break; case LPX_K_ITCNT: lp->it_cnt = val; break; case LPX_K_OUTFRQ: if (!(val > 0)) xerror("lpx_set_int_parm: OUTFRQ = %d; invalid value\n", val); cps->out_frq = val; break; case LPX_K_BRANCH: if (!(val == 0 || val == 1 || val == 2 || val == 3)) xerror("lpx_set_int_parm: BRANCH = %d; invalid value\n", val); cps->branch = val; break; case LPX_K_BTRACK: if (!(val == 0 || val == 1 || val == 2 || val == 3)) xerror("lpx_set_int_parm: BTRACK = %d; invalid value\n", val); cps->btrack = val; break; case LPX_K_MPSINFO: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: MPSINFO = %d; invalid value\n", val); cps->mps_info = val; break; case LPX_K_MPSOBJ: if (!(val == 0 || val == 1 || val == 2)) xerror("lpx_set_int_parm: MPSOBJ = %d; invalid value\n", val); cps->mps_obj = val; break; case LPX_K_MPSORIG: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: MPSORIG = %d; invalid value\n", val); cps->mps_orig = val; break; case LPX_K_MPSWIDE: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: MPSWIDE = %d; invalid value\n", val); cps->mps_wide = val; break; case LPX_K_MPSFREE: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: MPSFREE = %d; invalid value\n", val); cps->mps_free = val; break; case LPX_K_MPSSKIP: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: MPSSKIP = %d; invalid value\n", val); cps->mps_skip = val; break; case LPX_K_LPTORIG: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: LPTORIG = %d; invalid value\n", val); cps->lpt_orig = val; break; case LPX_K_PRESOL: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: PRESOL = %d; invalid value\n", val); cps->presol = val; break; case LPX_K_BINARIZE: if (!(val == 0 || val == 1)) xerror("lpx_set_int_parm: BINARIZE = %d; invalid value\n" , val); cps->binarize = val; break; case LPX_K_USECUTS: if (val & ~LPX_C_ALL) xerror("lpx_set_int_parm: USECUTS = 0x%X; invalid value\n", val); cps->use_cuts = val; break; case LPX_K_BFTYPE: #if 0 if (!(1 <= val && val <= 3)) xerror("lpx_set_int_parm: BFTYPE = %d; invalid value\n", val); cps->bf_type = val; #else { glp_bfcp parm; glp_get_bfcp(lp, &parm); switch (val) { case 1: parm.type = GLP_BF_FT; break; case 2: parm.type = GLP_BF_BG; break; case 3: parm.type = GLP_BF_GR; break; default: xerror("lpx_set_int_parm: BFTYPE = %d; invalid val" "ue\n", val); } glp_set_bfcp(lp, &parm); } #endif break; default: xerror("lpx_set_int_parm: parm = %d; invalid parameter\n", parm); } return; } int lpx_get_int_parm(LPX *lp, int parm) { /* query integer control parameter */ #if 0 /* 17/XI-2009 */ struct LPXCPS *cps = lp->cps; #else struct LPXCPS *cps = access_parms(lp); #endif int val = 0; switch (parm) { case LPX_K_MSGLEV: val = cps->msg_lev; break; case LPX_K_SCALE: val = cps->scale; break; case LPX_K_DUAL: val = cps->dual; break; case LPX_K_PRICE: val = cps->price; break; case LPX_K_ROUND: val = cps->round; break; case LPX_K_ITLIM: val = cps->it_lim; break; case LPX_K_ITCNT: val = lp->it_cnt; break; case LPX_K_OUTFRQ: val = cps->out_frq; break; case LPX_K_BRANCH: val = cps->branch; break; case LPX_K_BTRACK: val = cps->btrack; break; case LPX_K_MPSINFO: val = cps->mps_info; break; case LPX_K_MPSOBJ: val = cps->mps_obj; break; case LPX_K_MPSORIG: val = cps->mps_orig; break; case LPX_K_MPSWIDE: val = cps->mps_wide; break; case LPX_K_MPSFREE: val = cps->mps_free; break; case LPX_K_MPSSKIP: val = cps->mps_skip; break; case LPX_K_LPTORIG: val = cps->lpt_orig; break; case LPX_K_PRESOL: val = cps->presol; break; case LPX_K_BINARIZE: val = cps->binarize; break; case LPX_K_USECUTS: val = cps->use_cuts; break; case LPX_K_BFTYPE: #if 0 val = cps->bf_type; break; #else { glp_bfcp parm; glp_get_bfcp(lp, &parm); switch (parm.type) { case GLP_BF_FT: val = 1; break; case GLP_BF_BG: val = 2; break; case GLP_BF_GR: val = 3; break; default: xassert(lp != lp); } } break; #endif default: xerror("lpx_get_int_parm: parm = %d; invalid parameter\n", parm); } return val; } void lpx_set_real_parm(LPX *lp, int parm, double val) { /* set (change) real control parameter */ #if 0 /* 17/XI-2009 */ struct LPXCPS *cps = lp->cps; #else struct LPXCPS *cps = access_parms(lp); #endif switch (parm) { case LPX_K_RELAX: if (!(0.0 <= val && val <= 1.0)) xerror("lpx_set_real_parm: RELAX = %g; invalid value\n", val); cps->relax = val; break; case LPX_K_TOLBND: if (!(DBL_EPSILON <= val && val <= 0.001)) xerror("lpx_set_real_parm: TOLBND = %g; invalid value\n", val); #if 0 if (cps->tol_bnd > val) { /* invalidate the basic solution */ lp->p_stat = LPX_P_UNDEF; lp->d_stat = LPX_D_UNDEF; } #endif cps->tol_bnd = val; break; case LPX_K_TOLDJ: if (!(DBL_EPSILON <= val && val <= 0.001)) xerror("lpx_set_real_parm: TOLDJ = %g; invalid value\n", val); #if 0 if (cps->tol_dj > val) { /* invalidate the basic solution */ lp->p_stat = LPX_P_UNDEF; lp->d_stat = LPX_D_UNDEF; } #endif cps->tol_dj = val; break; case LPX_K_TOLPIV: if (!(DBL_EPSILON <= val && val <= 0.001)) xerror("lpx_set_real_parm: TOLPIV = %g; invalid value\n", val); cps->tol_piv = val; break; case LPX_K_OBJLL: cps->obj_ll = val; break; case LPX_K_OBJUL: cps->obj_ul = val; break; case LPX_K_TMLIM: cps->tm_lim = val; break; case LPX_K_OUTDLY: cps->out_dly = val; break; case LPX_K_TOLINT: if (!(DBL_EPSILON <= val && val <= 0.001)) xerror("lpx_set_real_parm: TOLINT = %g; invalid value\n", val); cps->tol_int = val; break; case LPX_K_TOLOBJ: if (!(DBL_EPSILON <= val && val <= 0.001)) xerror("lpx_set_real_parm: TOLOBJ = %g; invalid value\n", val); cps->tol_obj = val; break; case LPX_K_MIPGAP: if (val < 0.0) xerror("lpx_set_real_parm: MIPGAP = %g; invalid value\n", val); cps->mip_gap = val; break; default: xerror("lpx_set_real_parm: parm = %d; invalid parameter\n", parm); } return; } double lpx_get_real_parm(LPX *lp, int parm) { /* query real control parameter */ #if 0 /* 17/XI-2009 */ struct LPXCPS *cps = lp->cps; #else struct LPXCPS *cps = access_parms(lp); #endif double val = 0.0; switch (parm) { case LPX_K_RELAX: val = cps->relax; break; case LPX_K_TOLBND: val = cps->tol_bnd; break; case LPX_K_TOLDJ: val = cps->tol_dj; break; case LPX_K_TOLPIV: val = cps->tol_piv; break; case LPX_K_OBJLL: val = cps->obj_ll; break; case LPX_K_OBJUL: val = cps->obj_ul; break; case LPX_K_TMLIM: val = cps->tm_lim; break; case LPX_K_OUTDLY: val = cps->out_dly; break; case LPX_K_TOLINT: val = cps->tol_int; break; case LPX_K_TOLOBJ: val = cps->tol_obj; break; case LPX_K_MIPGAP: val = cps->mip_gap; break; default: xerror("lpx_get_real_parm: parm = %d; invalid parameter\n", parm); } return val; } LPX *lpx_read_mps(const char *fname) { /* read problem data in fixed MPS format */ LPX *lp = lpx_create_prob(); if (glp_read_mps(lp, GLP_MPS_DECK, NULL, fname)) lpx_delete_prob(lp), lp = NULL; return lp; } int lpx_write_mps(LPX *lp, const char *fname) { /* write problem data in fixed MPS format */ return glp_write_mps(lp, GLP_MPS_DECK, NULL, fname); } int lpx_read_bas(LPX *lp, const char *fname) { /* read LP basis in fixed MPS format */ #if 0 /* 13/IV-2009 */ return read_bas(lp, fname); #else xassert(lp == lp); xassert(fname == fname); xerror("lpx_read_bas: operation not supported\n"); return 0; #endif } int lpx_write_bas(LPX *lp, const char *fname) { /* write LP basis in fixed MPS format */ #if 0 /* 13/IV-2009 */ return write_bas(lp, fname); #else xassert(lp == lp); xassert(fname == fname); xerror("lpx_write_bas: operation not supported\n"); return 0; #endif } LPX *lpx_read_freemps(const char *fname) { /* read problem data in free MPS format */ LPX *lp = lpx_create_prob(); if (glp_read_mps(lp, GLP_MPS_FILE, NULL, fname)) lpx_delete_prob(lp), lp = NULL; return lp; } int lpx_write_freemps(LPX *lp, const char *fname) { /* write problem data in free MPS format */ return glp_write_mps(lp, GLP_MPS_FILE, NULL, fname); } LPX *lpx_read_cpxlp(const char *fname) { /* read problem data in CPLEX LP format */ LPX *lp; lp = lpx_create_prob(); if (glp_read_lp(lp, NULL, fname)) lpx_delete_prob(lp), lp = NULL; return lp; } int lpx_write_cpxlp(LPX *lp, const char *fname) { /* write problem data in CPLEX LP format */ return glp_write_lp(lp, NULL, fname); } LPX *lpx_read_model(const char *model, const char *data, const char *output) { /* read LP/MIP model written in GNU MathProg language */ LPX *lp = NULL; glp_tran *tran; /* allocate the translator workspace */ tran = glp_mpl_alloc_wksp(); /* read model section and optional data section */ if (glp_mpl_read_model(tran, model, data != NULL)) goto done; /* read separate data section, if required */ if (data != NULL) if (glp_mpl_read_data(tran, data)) goto done; /* generate the model */ if (glp_mpl_generate(tran, output)) goto done; /* build the problem instance from the model */ lp = glp_create_prob(); glp_mpl_build_prob(tran, lp); done: /* free the translator workspace */ glp_mpl_free_wksp(tran); /* bring the problem object to the calling program */ return lp; } int lpx_print_prob(LPX *lp, const char *fname) { /* write problem data in plain text format */ return glp_write_lp(lp, NULL, fname); } int lpx_print_sol(LPX *lp, const char *fname) { /* write LP problem solution in printable format */ return glp_print_sol(lp, fname); } int lpx_print_sens_bnds(LPX *lp, const char *fname) { /* write bounds sensitivity information */ if (glp_get_status(lp) == GLP_OPT && !glp_bf_exists(lp)) glp_factorize(lp); return glp_print_ranges(lp, 0, NULL, 0, fname); } int lpx_print_ips(LPX *lp, const char *fname) { /* write interior point solution in printable format */ return glp_print_ipt(lp, fname); } int lpx_print_mip(LPX *lp, const char *fname) { /* write MIP problem solution in printable format */ return glp_print_mip(lp, fname); } int lpx_is_b_avail(glp_prob *lp) { /* check if LP basis is available */ return glp_bf_exists(lp); } int lpx_main(int argc, const char *argv[]) { /* stand-alone LP/MIP solver */ return glp_main(argc, argv); } /* eof */ sources_5316/external/glpk/glptsp.c0000644000176700017670000005707011401660400016160 0ustar paulpaul/* glptsp.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_ERRNO #define _GLPSTD_STDIO #include "glpenv.h" #include "glptsp.h" #define xfault xerror /*---------------------------------------------------------------------- -- tsp_read_data - read TSP instance data. -- -- *Synopsis* -- -- #include "glptsp.h" -- TSP *tsp_read_data(char *fname); -- -- *Description* -- -- The routine tsp_read_data reads a TSP (or related problem) instance -- data from the text file, whose name is the character string fname. -- -- For detailed description of the format recognized by the routine see -- the report: G.Reinelt, TSPLIB 95. -- -- *Returns* -- -- If no error occurred, the routine tsp_read_data returns a pointer to -- the TSP instance data block, which contains loaded data. In the case -- of error the routine prints an error message and returns NULL. */ struct dsa { /* dynamic storage area used by the routine tsp_read_data */ char *fname; /* name of the input text file */ FILE *fp; /* stream assigned to the input text file */ int seqn; /* line sequential number */ int c; /* current character */ char token[255+1]; /* current token */ }; static int get_char(struct dsa *dsa) { dsa->c = fgetc(dsa->fp); if (ferror(dsa->fp)) { xprintf("%s:%d: read error - %s\n", dsa->fname, dsa->seqn, strerror(errno)); return 1; } if (feof(dsa->fp)) dsa->c = EOF; else if (dsa->c == '\n') dsa->seqn++; else if (isspace(dsa->c)) dsa->c = ' '; else if (iscntrl(dsa->c)) { xprintf("%s:%d: invalid control character 0x%02X\n", dsa->fname, dsa->seqn, dsa->c); return 1; } return 0; } static int skip_spaces(struct dsa *dsa, int across) { while (dsa->c == ' ' || (across && dsa->c == '\n')) if (get_char(dsa)) return 1; return 0; } static int scan_keyword(struct dsa *dsa) { int len = 0; if (skip_spaces(dsa, 0)) return 1; dsa->token[0] = '\0'; while (isalnum(dsa->c) || dsa->c == '_') { if (len == 31) { xprintf("%s:%d: keyword `%s...' too long\n", dsa->fname, dsa->seqn, dsa->token); return 1; } dsa->token[len++] = (char)dsa->c, dsa->token[len] = '\0'; if (get_char(dsa)) return 1; } if (len == 0) { xprintf("%s:%d: missing keyword\n", dsa->fname, dsa->seqn); return 1; } return 0; } static int check_colon(struct dsa *dsa) { if (skip_spaces(dsa, 0)) return 1; if (dsa->c != ':') { xprintf("%s:%d: missing colon after `%s'\n", dsa->fname, dsa->seqn, dsa->token); return 1; } if (get_char(dsa)) return 1; return 0; } static int scan_token(struct dsa *dsa, int across) { int len = 0; if (skip_spaces(dsa, across)) return 1; dsa->token[0] = '\0'; while (!(dsa->c == EOF || dsa->c == '\n' || dsa->c == ' ')) { if (len == 255) { dsa->token[31] = '\0'; xprintf("%s:%d: token `%s...' too long\n", dsa->fname, dsa->seqn, dsa->token); return 1; } dsa->token[len++] = (char)dsa->c, dsa->token[len] = '\0'; if (get_char(dsa)) return 1; } return 0; } static int check_newline(struct dsa *dsa) { if (skip_spaces(dsa, 0)) return 1; if (!(dsa->c == EOF || dsa->c == '\n')) { xprintf("%s:%d: extra symbols detected\n", dsa->fname, dsa->seqn); return 1; } if (get_char(dsa)) return 1; return 0; } static int scan_comment(struct dsa *dsa) { int len = 0; if (skip_spaces(dsa, 0)) return 1; dsa->token[0] = '\0'; while (!(dsa->c == EOF || dsa->c == '\n')) { if (len == 255) { xprintf("%s:%d: comment too long\n", dsa->fname, dsa->seqn) ; return 1; } dsa->token[len++] = (char)dsa->c, dsa->token[len] = '\0'; if (get_char(dsa)) return 1; } return 0; } static int scan_integer(struct dsa *dsa, int across, int *val) { if (scan_token(dsa, across)) return 1; if (strlen(dsa->token) == 0) { xprintf("%s:%d: missing integer\n", dsa->fname, dsa->seqn); return 1; } if (str2int(dsa->token, val)) { xprintf("%s:%d: integer `%s' invalid\n", dsa->fname, dsa->seqn , dsa->token); return 1; } return 0; } static int scan_number(struct dsa *dsa, int across, double *val) { if (scan_token(dsa, across)) return 1; if (strlen(dsa->token) == 0) { xprintf("%s:%d: missing number\n", dsa->fname, dsa->seqn); return 1; } if (str2num(dsa->token, val)) { xprintf("%s:%d: number `%s' invalid\n", dsa->fname, dsa->seqn, dsa->token); return 1; } return 0; } TSP *tsp_read_data(char *fname) { struct dsa _dsa, *dsa = &_dsa; TSP *tsp = NULL; dsa->fname = fname; xprintf("tsp_read_data: reading TSP data from `%s'...\n", dsa->fname); dsa->fp = fopen(dsa->fname, "r"); if (dsa->fp == NULL) { xprintf("tsp_read_data: unable to open `%s' - %s\n", dsa->fname, strerror(errno)); goto fail; } tsp = xmalloc(sizeof(TSP)); tsp->name = NULL; tsp->type = TSP_UNDEF; tsp->comment = NULL; tsp->dimension = 0; tsp->edge_weight_type = TSP_UNDEF; tsp->edge_weight_format = TSP_UNDEF; tsp->display_data_type = TSP_UNDEF; tsp->node_x_coord = NULL; tsp->node_y_coord = NULL; tsp->dply_x_coord = NULL; tsp->dply_y_coord = NULL; tsp->tour = NULL; tsp->edge_weight = NULL; dsa->seqn = 1; if (get_char(dsa)) goto fail; loop: if (scan_keyword(dsa)) goto fail; if (strcmp(dsa->token, "NAME") == 0) { if (tsp->name != NULL) { xprintf("%s:%d: NAME entry multiply defined\n", dsa->fname, dsa->seqn); goto fail; } if (check_colon(dsa)) goto fail; if (scan_token(dsa, 0)) goto fail; if (strlen(dsa->token) == 0) { xprintf("%s:%d: NAME entry incomplete\n", dsa->fname, dsa->seqn); goto fail; } tsp->name = xmalloc(strlen(dsa->token) + 1); strcpy(tsp->name, dsa->token); xprintf("tsp_read_data: NAME: %s\n", tsp->name); if (check_newline(dsa)) goto fail; } else if (strcmp(dsa->token, "TYPE") == 0) { if (tsp->type != TSP_UNDEF) { xprintf("%s:%d: TYPE entry multiply defined\n", dsa->fname, dsa->seqn); goto fail; } if (check_colon(dsa)) goto fail; if (scan_keyword(dsa)) goto fail; if (strcmp(dsa->token, "TSP") == 0) tsp->type = TSP_TSP; else if (strcmp(dsa->token, "ATSP") == 0) tsp->type = TSP_ATSP; else if (strcmp(dsa->token, "TOUR") == 0) tsp->type = TSP_TOUR; else { xprintf("%s:%d: data type `%s' not recognized\n", dsa->fname, dsa->seqn, dsa->token); goto fail; } xprintf("tsp_read_data: TYPE: %s\n", dsa->token); if (check_newline(dsa)) goto fail; } else if (strcmp(dsa->token, "COMMENT") == 0) { if (tsp->comment != NULL) { xprintf("%s:%d: COMMENT entry multiply defined\n", dsa->fname, dsa->seqn); goto fail; } if (check_colon(dsa)) goto fail; if (scan_comment(dsa)) goto fail; tsp->comment = xmalloc(strlen(dsa->token) + 1); strcpy(tsp->comment, dsa->token); xprintf("tsp_read_data: COMMENT: %s\n", tsp->comment); if (check_newline(dsa)) goto fail; } else if (strcmp(dsa->token, "DIMENSION") == 0) { if (tsp->dimension != 0) { xprintf("%s:%d: DIMENSION entry multiply defined\n", dsa->fname, dsa->seqn); goto fail; } if (check_colon(dsa)) goto fail; if (scan_integer(dsa, 0, &tsp->dimension)) goto fail; if (tsp->dimension < 1) { xprintf("%s:%d: invalid dimension\n", dsa->fname, dsa->seqn); goto fail; } xprintf("tsp_read_data: DIMENSION: %d\n", tsp->dimension); if (check_newline(dsa)) goto fail; } else if (strcmp(dsa->token, "EDGE_WEIGHT_TYPE") == 0) { if (tsp->edge_weight_type != TSP_UNDEF) { xprintf("%s:%d: EDGE_WEIGHT_TYPE entry multiply defined\n", dsa->fname, dsa->seqn); goto fail; } if (check_colon(dsa)) goto fail; if (scan_keyword(dsa)) goto fail; if (strcmp(dsa->token, "GEO") == 0) tsp->edge_weight_type = TSP_GEO; else if (strcmp(dsa->token, "EUC_2D") == 0) tsp->edge_weight_type = TSP_EUC_2D; else if (strcmp(dsa->token, "ATT") == 0) tsp->edge_weight_type = TSP_ATT; else if (strcmp(dsa->token, "EXPLICIT") == 0) tsp->edge_weight_type = TSP_EXPLICIT; else if (strcmp(dsa->token, "CEIL_2D") == 0) tsp->edge_weight_type = TSP_CEIL_2D; else { xprintf("%s:%d: edge weight type `%s' not recognized\n", dsa->fname, dsa->seqn, dsa->token); goto fail; } xprintf("tsp_read_data: EDGE_WEIGHT_TYPE: %s\n", dsa->token); if (check_newline(dsa)) goto fail; } else if (strcmp(dsa->token, "EDGE_WEIGHT_FORMAT") == 0) { if (tsp->edge_weight_format != TSP_UNDEF) { xprintf( "%s:%d: EDGE_WEIGHT_FORMAT entry multiply defined\n", dsa->fname, dsa->seqn); goto fail; } if (check_colon(dsa)) goto fail; if (scan_keyword(dsa)) goto fail; if (strcmp(dsa->token, "UPPER_ROW") == 0) tsp->edge_weight_format = TSP_UPPER_ROW; else if (strcmp(dsa->token, "FULL_MATRIX") == 0) tsp->edge_weight_format = TSP_FULL_MATRIX; else if (strcmp(dsa->token, "FUNCTION") == 0) tsp->edge_weight_format = TSP_FUNCTION; else if (strcmp(dsa->token, "LOWER_DIAG_ROW") == 0) tsp->edge_weight_format = TSP_LOWER_DIAG_ROW; else { xprintf("%s:%d: edge weight format `%s' not recognized\n", dsa->fname, dsa->seqn, dsa->token); goto fail; } xprintf("tsp_read_data: EDGE_WEIGHT_FORMAT: %s\n", dsa->token); if (check_newline(dsa)) goto fail; } else if (strcmp(dsa->token, "DISPLAY_DATA_TYPE") == 0) { if (tsp->display_data_type != TSP_UNDEF) { xprintf("%s:%d: DISPLAY_DATA_TYPE entry multiply defined\n", dsa->fname, dsa->seqn); goto fail; } if (check_colon(dsa)) goto fail; if (scan_keyword(dsa)) goto fail; if (strcmp(dsa->token, "COORD_DISPLAY") == 0) tsp->display_data_type = TSP_COORD_DISPLAY; else if (strcmp(dsa->token, "TWOD_DISPLAY") == 0) tsp->display_data_type = TSP_TWOD_DISPLAY; else { xprintf("%s:%d: display data type `%s' not recognized\n", dsa->fname, dsa->seqn, dsa->token); goto fail; } xprintf("tsp_read_data: DISPLAY_DATA_TYPE: %s\n", dsa->token); if (check_newline(dsa)) goto fail; } else if (strcmp(dsa->token, "NODE_COORD_SECTION") == 0) { int n = tsp->dimension, k, node; if (n == 0) { xprintf("%s:%d: DIMENSION entry not specified\n", dsa->fname, dsa->seqn); goto fail; } if (tsp->node_x_coord != NULL) { xprintf("%s:%d: NODE_COORD_SECTION multiply specified\n", dsa->fname, dsa->seqn); goto fail; } if (check_newline(dsa)) goto fail; tsp->node_x_coord = xcalloc(1+n, sizeof(double)); tsp->node_y_coord = xcalloc(1+n, sizeof(double)); for (node = 1; node <= n; node++) tsp->node_x_coord[node] = tsp->node_y_coord[node] = DBL_MAX; for (k = 1; k <= n; k++) { if (scan_integer(dsa, 0, &node)) goto fail; if (!(1 <= node && node <= n)) { xprintf("%s:%d: invalid node number %d\n", dsa->fname, dsa->seqn, node); goto fail; } if (tsp->node_x_coord[node] != DBL_MAX) { xprintf("%s:%d: node number %d multiply specified\n", dsa->fname, dsa->seqn, node); goto fail; } if (scan_number(dsa, 0, &tsp->node_x_coord[node])) goto fail; if (scan_number(dsa, 0, &tsp->node_y_coord[node])) goto fail; if (check_newline(dsa)) goto fail; } } else if (strcmp(dsa->token, "DISPLAY_DATA_SECTION") == 0) { int n = tsp->dimension, k, node; if (n == 0) { xprintf("%s:%d: DIMENSION entry not specified\n", dsa->fname, dsa->seqn); goto fail; } if (tsp->dply_x_coord != NULL) { xprintf("%s:%d: DISPLAY_DATA_SECTION multiply specified\n", dsa->fname, dsa->seqn); goto fail; } if (check_newline(dsa)) goto fail; tsp->dply_x_coord = xcalloc(1+n, sizeof(double)); tsp->dply_y_coord = xcalloc(1+n, sizeof(double)); for (node = 1; node <= n; node++) tsp->dply_x_coord[node] = tsp->dply_y_coord[node] = DBL_MAX; for (k = 1; k <= n; k++) { if (scan_integer(dsa, 0, &node)) goto fail; if (!(1 <= node && node <= n)) { xprintf("%s:%d: invalid node number %d\n", dsa->fname, dsa->seqn, node); goto fail; } if (tsp->dply_x_coord[node] != DBL_MAX) { xprintf("%s:%d: node number %d multiply specified\n", dsa->fname, dsa->seqn, node); goto fail; } if (scan_number(dsa, 0, &tsp->dply_x_coord[node])) goto fail; if (scan_number(dsa, 0, &tsp->dply_y_coord[node])) goto fail; if (check_newline(dsa)) goto fail; } } else if (strcmp(dsa->token, "TOUR_SECTION") == 0) { int n = tsp->dimension, k, node; if (n == 0) { xprintf("%s:%d: DIMENSION entry not specified\n", dsa->fname, dsa->seqn); goto fail; } if (tsp->tour != NULL) { xprintf("%s:%d: TOUR_SECTION multiply specified\n", dsa->fname, dsa->seqn); goto fail; } if (check_newline(dsa)) goto fail; tsp->tour = xcalloc(1+n, sizeof(int)); for (k = 1; k <= n; k++) { if (scan_integer(dsa, 1, &node)) goto fail; if (!(1 <= node && node <= n)) { xprintf("%s:%d: invalid node number %d\n", dsa->fname, dsa->seqn, node); goto fail; } tsp->tour[k] = node; } if (scan_integer(dsa, 1, &node)) goto fail; if (node != -1) { xprintf("%s:%d: extra node(s) detected\n", dsa->fname, dsa->seqn); goto fail; } if (check_newline(dsa)) goto fail; } else if (strcmp(dsa->token, "EDGE_WEIGHT_SECTION") == 0) { int n = tsp->dimension, i, j, temp; if (n == 0) { xprintf("%s:%d: DIMENSION entry not specified\n", dsa->fname, dsa->seqn); goto fail; } if (tsp->edge_weight_format == TSP_UNDEF) { xprintf("%s:%d: EDGE_WEIGHT_FORMAT entry not specified\n", dsa->fname, dsa->seqn); goto fail; } if (tsp->edge_weight != NULL) { xprintf("%s:%d: EDGE_WEIGHT_SECTION multiply specified\n", dsa->fname, dsa->seqn); goto fail; } if (check_newline(dsa)) goto fail; tsp->edge_weight = xcalloc(1+n*n, sizeof(int)); switch (tsp->edge_weight_format) { case TSP_FULL_MATRIX: for (i = 1; i <= n; i++) { for (j = 1; j <= n; j++) { if (scan_integer(dsa, 1, &temp)) goto fail; tsp->edge_weight[(i - 1) * n + j] = temp; } } break; case TSP_UPPER_ROW: for (i = 1; i <= n; i++) { tsp->edge_weight[(i - 1) * n + i] = 0; for (j = i + 1; j <= n; j++) { if (scan_integer(dsa, 1, &temp)) goto fail; tsp->edge_weight[(i - 1) * n + j] = temp; tsp->edge_weight[(j - 1) * n + i] = temp; } } break; case TSP_LOWER_DIAG_ROW: for (i = 1; i <= n; i++) { for (j = 1; j <= i; j++) { if (scan_integer(dsa, 1, &temp)) goto fail; tsp->edge_weight[(i - 1) * n + j] = temp; tsp->edge_weight[(j - 1) * n + i] = temp; } } break; default: goto fail; } if (check_newline(dsa)) goto fail; } else if (strcmp(dsa->token, "EOF") == 0) { if (check_newline(dsa)) goto fail; goto done; } else { xprintf("%s:%d: keyword `%s' not recognized\n", dsa->fname, dsa->seqn, dsa->token); goto fail; } goto loop; done: xprintf("tsp_read_data: %d lines were read\n", dsa->seqn-1); fclose(dsa->fp); return tsp; fail: if (tsp != NULL) { if (tsp->name != NULL) xfree(tsp->name); if (tsp->comment != NULL) xfree(tsp->comment); if (tsp->node_x_coord != NULL) xfree(tsp->node_x_coord); if (tsp->node_y_coord != NULL) xfree(tsp->node_y_coord); if (tsp->dply_x_coord != NULL) xfree(tsp->dply_x_coord); if (tsp->dply_y_coord != NULL) xfree(tsp->dply_y_coord); if (tsp->tour != NULL) xfree(tsp->tour); if (tsp->edge_weight != NULL) xfree(tsp->edge_weight); xfree(tsp); } if (dsa->fp != NULL) fclose(dsa->fp); return NULL; } /*---------------------------------------------------------------------- -- tsp_free_data - free TSP instance data. -- -- *Synopsis* -- -- #include "glptsp.h" -- void tsp_free_data(TSP *tsp); -- -- *Description* -- -- The routine tsp_free_data frees all the memory allocated to the TSP -- instance data block, which the parameter tsp points to. */ void tsp_free_data(TSP *tsp) { if (tsp->name != NULL) xfree(tsp->name); if (tsp->comment != NULL) xfree(tsp->comment); if (tsp->node_x_coord != NULL) xfree(tsp->node_x_coord); if (tsp->node_y_coord != NULL) xfree(tsp->node_y_coord); if (tsp->dply_x_coord != NULL) xfree(tsp->dply_x_coord); if (tsp->dply_y_coord != NULL) xfree(tsp->dply_y_coord); if (tsp->tour != NULL) xfree(tsp->tour); if (tsp->edge_weight != NULL) xfree(tsp->edge_weight); xfree(tsp); return; } /*---------------------------------------------------------------------- -- tsp_distance - compute distance between two nodes. -- -- *Synopsis* -- -- #include "glptsp.h" -- int tsp_distance(TSP *tsp, int i, int j); -- -- *Description* -- -- The routine tsp_distance computes the distance between i-th and j-th -- nodes for the TSP instance, which tsp points to. -- -- *Returns* -- -- The routine tsp_distance returns the computed distance. */ #define nint(x) ((int)((x) + 0.5)) static double rad(double x) { /* convert input coordinate to longitude/latitude, in radians */ double pi = 3.141592, deg, min; deg = (int)x; min = x - deg; return pi * (deg + 5.0 * min / 3.0) / 180.0; } int tsp_distance(TSP *tsp, int i, int j) { int n = tsp->dimension, dij; if (!(tsp->type == TSP_TSP || tsp->type == TSP_ATSP)) xfault("tsp_distance: invalid TSP instance\n"); if (!(1 <= i && i <= n && 1 <= j && j <= n)) xfault("tsp_distance: node number out of range\n"); switch (tsp->edge_weight_type) { case TSP_UNDEF: xfault("tsp_distance: edge weight type not specified\n"); case TSP_EXPLICIT: if (tsp->edge_weight == NULL) xfault("tsp_distance: edge weights not specified\n"); dij = tsp->edge_weight[(i - 1) * n + j]; break; case TSP_EUC_2D: if (tsp->node_x_coord == NULL || tsp->node_y_coord == NULL) xfault("tsp_distance: node coordinates not specified\n"); { double xd, yd; xd = tsp->node_x_coord[i] - tsp->node_x_coord[j]; yd = tsp->node_y_coord[i] - tsp->node_y_coord[j]; dij = nint(sqrt(xd * xd + yd * yd)); } break; case TSP_CEIL_2D: if (tsp->node_x_coord == NULL || tsp->node_y_coord == NULL) xfault("tsp_distance: node coordinates not specified\n"); { double xd, yd; xd = tsp->node_x_coord[i] - tsp->node_x_coord[j]; yd = tsp->node_y_coord[i] - tsp->node_y_coord[j]; dij = (int)ceil(sqrt(xd * xd + yd * yd)); } break; case TSP_GEO: if (tsp->node_x_coord == NULL || tsp->node_y_coord == NULL) xfault("tsp_distance: node coordinates not specified\n"); { double rrr = 6378.388; double latitude_i = rad(tsp->node_x_coord[i]); double latitude_j = rad(tsp->node_x_coord[j]); double longitude_i = rad(tsp->node_y_coord[i]); double longitude_j = rad(tsp->node_y_coord[j]); double q1 = cos(longitude_i - longitude_j); double q2 = cos(latitude_i - latitude_j); double q3 = cos(latitude_i + latitude_j); dij = (int)(rrr * acos(0.5 * ((1.0 + q1) * q2 - (1.0 - q1) *q3)) + 1.0); } break; case TSP_ATT: if (tsp->node_x_coord == NULL || tsp->node_y_coord == NULL) xfault("tsp_distance: node coordinates not specified\n"); { int tij; double xd, yd, rij; xd = tsp->node_x_coord[i] - tsp->node_x_coord[j]; yd = tsp->node_y_coord[i] - tsp->node_y_coord[j]; rij = sqrt((xd * xd + yd * yd) / 10.0); tij = nint(rij); if (tij < rij) dij = tij + 1; else dij = tij; } break; default: xassert(tsp->edge_weight_type != tsp->edge_weight_type); } return dij; } /* eof */ sources_5316/external/glpk/glpapi06.c0000644000176700017670000006374211401660400016274 0ustar paulpaul/* glpapi06.c (simplex method routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" #include "glpnpp.h" #include "glpspx.h" /*********************************************************************** * NAME * * glp_simplex - solve LP problem with the simplex method * * SYNOPSIS * * int glp_simplex(glp_prob *P, const glp_smcp *parm); * * DESCRIPTION * * The routine glp_simplex is a driver to the LP solver based on the * simplex method. This routine retrieves problem data from the * specified problem object, calls the solver to solve the problem * instance, and stores results of computations back into the problem * object. * * The simplex solver has a set of control parameters. Values of the * control parameters can be passed in a structure glp_smcp, which the * parameter parm points to. * * The parameter parm can be specified as NULL, in which case the LP * solver uses default settings. * * RETURNS * * 0 The LP problem instance has been successfully solved. This code * does not necessarily mean that the solver has found optimal * solution. It only means that the solution process was successful. * * GLP_EBADB * Unable to start the search, because the initial basis specified * in the problem object is invalid--the number of basic (auxiliary * and structural) variables is not the same as the number of rows in * the problem object. * * GLP_ESING * Unable to start the search, because the basis matrix correspodning * to the initial basis is singular within the working precision. * * GLP_ECOND * Unable to start the search, because the basis matrix correspodning * to the initial basis is ill-conditioned, i.e. its condition number * is too large. * * GLP_EBOUND * Unable to start the search, because some double-bounded variables * have incorrect bounds. * * GLP_EFAIL * The search was prematurely terminated due to the solver failure. * * GLP_EOBJLL * The search was prematurely terminated, because the objective * function being maximized has reached its lower limit and continues * decreasing (dual simplex only). * * GLP_EOBJUL * The search was prematurely terminated, because the objective * function being minimized has reached its upper limit and continues * increasing (dual simplex only). * * GLP_EITLIM * The search was prematurely terminated, because the simplex * iteration limit has been exceeded. * * GLP_ETMLIM * The search was prematurely terminated, because the time limit has * been exceeded. * * GLP_ENOPFS * The LP problem instance has no primal feasible solution (only if * the LP presolver is used). * * GLP_ENODFS * The LP problem instance has no dual feasible solution (only if the * LP presolver is used). */ static void trivial_lp(glp_prob *P, const glp_smcp *parm) { /* solve trivial LP which has empty constraint matrix */ GLPROW *row; GLPCOL *col; int i, j; double p_infeas, d_infeas, zeta; P->valid = 0; P->pbs_stat = P->dbs_stat = GLP_FEAS; P->obj_val = P->c0; P->some = 0; p_infeas = d_infeas = 0.0; /* make all auxiliary variables basic */ for (i = 1; i <= P->m; i++) { row = P->row[i]; row->stat = GLP_BS; row->prim = row->dual = 0.0; /* check primal feasibility */ if (row->type == GLP_LO || row->type == GLP_DB || row->type == GLP_FX) { /* row has lower bound */ if (row->lb > + parm->tol_bnd) { P->pbs_stat = GLP_NOFEAS; if (P->some == 0 && parm->meth != GLP_PRIMAL) P->some = i; } if (p_infeas < + row->lb) p_infeas = + row->lb; } if (row->type == GLP_UP || row->type == GLP_DB || row->type == GLP_FX) { /* row has upper bound */ if (row->ub < - parm->tol_bnd) { P->pbs_stat = GLP_NOFEAS; if (P->some == 0 && parm->meth != GLP_PRIMAL) P->some = i; } if (p_infeas < - row->ub) p_infeas = - row->ub; } } /* determine scale factor for the objective row */ zeta = 1.0; for (j = 1; j <= P->n; j++) { col = P->col[j]; if (zeta < fabs(col->coef)) zeta = fabs(col->coef); } zeta = (P->dir == GLP_MIN ? +1.0 : -1.0) / zeta; /* make all structural variables non-basic */ for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->type == GLP_FR) col->stat = GLP_NF, col->prim = 0.0; else if (col->type == GLP_LO) lo: col->stat = GLP_NL, col->prim = col->lb; else if (col->type == GLP_UP) up: col->stat = GLP_NU, col->prim = col->ub; else if (col->type == GLP_DB) { if (zeta * col->coef > 0.0) goto lo; else if (zeta * col->coef < 0.0) goto up; else if (fabs(col->lb) <= fabs(col->ub)) goto lo; else goto up; } else if (col->type == GLP_FX) col->stat = GLP_NS, col->prim = col->lb; col->dual = col->coef; P->obj_val += col->coef * col->prim; /* check dual feasibility */ if (col->type == GLP_FR || col->type == GLP_LO) { /* column has no upper bound */ if (zeta * col->dual < - parm->tol_dj) { P->dbs_stat = GLP_NOFEAS; if (P->some == 0 && parm->meth == GLP_PRIMAL) P->some = P->m + j; } if (d_infeas < - zeta * col->dual) d_infeas = - zeta * col->dual; } if (col->type == GLP_FR || col->type == GLP_UP) { /* column has no lower bound */ if (zeta * col->dual > + parm->tol_dj) { P->dbs_stat = GLP_NOFEAS; if (P->some == 0 && parm->meth == GLP_PRIMAL) P->some = P->m + j; } if (d_infeas < + zeta * col->dual) d_infeas = + zeta * col->dual; } } /* simulate the simplex solver output */ if (parm->msg_lev >= GLP_MSG_ON && parm->out_dly == 0) { xprintf("~%6d: obj = %17.9e infeas = %10.3e\n", P->it_cnt, P->obj_val, parm->meth == GLP_PRIMAL ? p_infeas : d_infeas); } if (parm->msg_lev >= GLP_MSG_ALL && parm->out_dly == 0) { if (P->pbs_stat == GLP_FEAS && P->dbs_stat == GLP_FEAS) xprintf("OPTIMAL SOLUTION FOUND\n"); else if (P->pbs_stat == GLP_NOFEAS) xprintf("PROBLEM HAS NO FEASIBLE SOLUTION\n"); else if (parm->meth == GLP_PRIMAL) xprintf("PROBLEM HAS UNBOUNDED SOLUTION\n"); else xprintf("PROBLEM HAS NO DUAL FEASIBLE SOLUTION\n"); } return; } static int solve_lp(glp_prob *P, const glp_smcp *parm) { /* solve LP directly without using the preprocessor */ int ret; if (!glp_bf_exists(P)) { ret = glp_factorize(P); if (ret == 0) ; else if (ret == GLP_EBADB) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_simplex: initial basis is invalid\n"); } else if (ret == GLP_ESING) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_simplex: initial basis is singular\n"); } else if (ret == GLP_ECOND) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf( "glp_simplex: initial basis is ill-conditioned\n"); } else xassert(ret != ret); if (ret != 0) goto done; } if (parm->meth == GLP_PRIMAL) ret = spx_primal(P, parm); else if (parm->meth == GLP_DUALP) { ret = spx_dual(P, parm); if (ret == GLP_EFAIL && P->valid) ret = spx_primal(P, parm); } else if (parm->meth == GLP_DUAL) ret = spx_dual(P, parm); else xassert(parm != parm); done: return ret; } static int preprocess_and_solve_lp(glp_prob *P, const glp_smcp *parm) { /* solve LP using the preprocessor */ NPP *npp; glp_prob *lp = NULL; glp_bfcp bfcp; int ret; if (parm->msg_lev >= GLP_MSG_ALL) xprintf("Preprocessing...\n"); /* create preprocessor workspace */ npp = npp_create_wksp(); /* load original problem into the preprocessor workspace */ npp_load_prob(npp, P, GLP_OFF, GLP_SOL, GLP_OFF); /* process LP prior to applying primal/dual simplex method */ ret = npp_simplex(npp, parm); if (ret == 0) ; else if (ret == GLP_ENOPFS) { if (parm->msg_lev >= GLP_MSG_ALL) xprintf("PROBLEM HAS NO PRIMAL FEASIBLE SOLUTION\n"); } else if (ret == GLP_ENODFS) { if (parm->msg_lev >= GLP_MSG_ALL) xprintf("PROBLEM HAS NO DUAL FEASIBLE SOLUTION\n"); } else xassert(ret != ret); if (ret != 0) goto done; /* build transformed LP */ lp = glp_create_prob(); npp_build_prob(npp, lp); /* if the transformed LP is empty, it has empty solution, which is optimal */ if (lp->m == 0 && lp->n == 0) { lp->pbs_stat = lp->dbs_stat = GLP_FEAS; lp->obj_val = lp->c0; if (parm->msg_lev >= GLP_MSG_ON && parm->out_dly == 0) { xprintf("~%6d: obj = %17.9e infeas = %10.3e\n", P->it_cnt, lp->obj_val, 0.0); } if (parm->msg_lev >= GLP_MSG_ALL) xprintf("OPTIMAL SOLUTION FOUND BY LP PREPROCESSOR\n"); goto post; } if (parm->msg_lev >= GLP_MSG_ALL) { xprintf("%d row%s, %d column%s, %d non-zero%s\n", lp->m, lp->m == 1 ? "" : "s", lp->n, lp->n == 1 ? "" : "s", lp->nnz, lp->nnz == 1 ? "" : "s"); } /* inherit basis factorization control parameters */ glp_get_bfcp(P, &bfcp); glp_set_bfcp(lp, &bfcp); /* scale the transformed problem */ { ENV *env = get_env_ptr(); int term_out = env->term_out; if (!term_out || parm->msg_lev < GLP_MSG_ALL) env->term_out = GLP_OFF; else env->term_out = GLP_ON; glp_scale_prob(lp, GLP_SF_AUTO); env->term_out = term_out; } /* build advanced initial basis */ { ENV *env = get_env_ptr(); int term_out = env->term_out; if (!term_out || parm->msg_lev < GLP_MSG_ALL) env->term_out = GLP_OFF; else env->term_out = GLP_ON; glp_adv_basis(lp, 0); env->term_out = term_out; } /* solve the transformed LP */ lp->it_cnt = P->it_cnt; ret = solve_lp(lp, parm); P->it_cnt = lp->it_cnt; /* only optimal solution can be postprocessed */ if (!(ret == 0 && lp->pbs_stat == GLP_FEAS && lp->dbs_stat == GLP_FEAS)) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_simplex: unable to recover undefined or non-op" "timal solution\n"); if (ret == 0) { if (lp->pbs_stat == GLP_NOFEAS) ret = GLP_ENOPFS; else if (lp->dbs_stat == GLP_NOFEAS) ret = GLP_ENODFS; else xassert(lp != lp); } goto done; } post: /* postprocess solution from the transformed LP */ npp_postprocess(npp, lp); /* the transformed LP is no longer needed */ glp_delete_prob(lp), lp = NULL; /* store solution to the original problem */ npp_unload_sol(npp, P); /* the original LP has been successfully solved */ ret = 0; done: /* delete the transformed LP, if it exists */ if (lp != NULL) glp_delete_prob(lp); /* delete preprocessor workspace */ npp_delete_wksp(npp); return ret; } int glp_simplex(glp_prob *P, const glp_smcp *parm) { /* solve LP problem with the simplex method */ glp_smcp _parm; int i, j, ret; /* check problem object */ if (P == NULL || P->magic != GLP_PROB_MAGIC) xerror("glp_simplex: P = %p; invalid problem object\n", P); if (P->tree != NULL && P->tree->reason != 0) xerror("glp_simplex: operation not allowed\n"); /* check control parameters */ if (parm == NULL) parm = &_parm, glp_init_smcp((glp_smcp *)parm); if (!(parm->msg_lev == GLP_MSG_OFF || parm->msg_lev == GLP_MSG_ERR || parm->msg_lev == GLP_MSG_ON || parm->msg_lev == GLP_MSG_ALL || parm->msg_lev == GLP_MSG_DBG)) xerror("glp_simplex: msg_lev = %d; invalid parameter\n", parm->msg_lev); if (!(parm->meth == GLP_PRIMAL || parm->meth == GLP_DUALP || parm->meth == GLP_DUAL)) xerror("glp_simplex: meth = %d; invalid parameter\n", parm->meth); if (!(parm->pricing == GLP_PT_STD || parm->pricing == GLP_PT_PSE)) xerror("glp_simplex: pricing = %d; invalid parameter\n", parm->pricing); if (!(parm->r_test == GLP_RT_STD || parm->r_test == GLP_RT_HAR)) xerror("glp_simplex: r_test = %d; invalid parameter\n", parm->r_test); if (!(0.0 < parm->tol_bnd && parm->tol_bnd < 1.0)) xerror("glp_simplex: tol_bnd = %g; invalid parameter\n", parm->tol_bnd); if (!(0.0 < parm->tol_dj && parm->tol_dj < 1.0)) xerror("glp_simplex: tol_dj = %g; invalid parameter\n", parm->tol_dj); if (!(0.0 < parm->tol_piv && parm->tol_piv < 1.0)) xerror("glp_simplex: tol_piv = %g; invalid parameter\n", parm->tol_piv); if (parm->it_lim < 0) xerror("glp_simplex: it_lim = %d; invalid parameter\n", parm->it_lim); if (parm->tm_lim < 0) xerror("glp_simplex: tm_lim = %d; invalid parameter\n", parm->tm_lim); if (parm->out_frq < 1) xerror("glp_simplex: out_frq = %d; invalid parameter\n", parm->out_frq); if (parm->out_dly < 0) xerror("glp_simplex: out_dly = %d; invalid parameter\n", parm->out_dly); if (!(parm->presolve == GLP_ON || parm->presolve == GLP_OFF)) xerror("glp_simplex: presolve = %d; invalid parameter\n", parm->presolve); /* basic solution is currently undefined */ P->pbs_stat = P->dbs_stat = GLP_UNDEF; P->obj_val = 0.0; P->some = 0; /* check bounds of double-bounded variables */ for (i = 1; i <= P->m; i++) { GLPROW *row = P->row[i]; if (row->type == GLP_DB && row->lb >= row->ub) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_simplex: row %d: lb = %g, ub = %g; incorrec" "t bounds\n", i, row->lb, row->ub); ret = GLP_EBOUND; goto done; } } for (j = 1; j <= P->n; j++) { GLPCOL *col = P->col[j]; if (col->type == GLP_DB && col->lb >= col->ub) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_simplex: column %d: lb = %g, ub = %g; incor" "rect bounds\n", j, col->lb, col->ub); ret = GLP_EBOUND; goto done; } } /* solve LP problem */ if (parm->msg_lev >= GLP_MSG_ALL) { xprintf("GLPK Simplex Optimizer, v%s\n", glp_version()); xprintf("%d row%s, %d column%s, %d non-zero%s\n", P->m, P->m == 1 ? "" : "s", P->n, P->n == 1 ? "" : "s", P->nnz, P->nnz == 1 ? "" : "s"); } if (P->nnz == 0) trivial_lp(P, parm), ret = 0; else if (!parm->presolve) ret = solve_lp(P, parm); else ret = preprocess_and_solve_lp(P, parm); done: /* return to the application program */ return ret; } /*********************************************************************** * NAME * * glp_init_smcp - initialize simplex method control parameters * * SYNOPSIS * * void glp_init_smcp(glp_smcp *parm); * * DESCRIPTION * * The routine glp_init_smcp initializes control parameters, which are * used by the simplex solver, with default values. * * Default values of the control parameters are stored in a glp_smcp * structure, which the parameter parm points to. */ void glp_init_smcp(glp_smcp *parm) { parm->msg_lev = GLP_MSG_ALL; parm->meth = GLP_PRIMAL; parm->pricing = GLP_PT_PSE; parm->r_test = GLP_RT_HAR; parm->tol_bnd = 1e-7; parm->tol_dj = 1e-7; parm->tol_piv = 1e-10; parm->obj_ll = -DBL_MAX; parm->obj_ul = +DBL_MAX; parm->it_lim = INT_MAX; parm->tm_lim = INT_MAX; parm->out_frq = 500; parm->out_dly = 0; parm->presolve = GLP_OFF; return; } /*********************************************************************** * NAME * * glp_get_status - retrieve generic status of basic solution * * SYNOPSIS * * int glp_get_status(glp_prob *lp); * * RETURNS * * The routine glp_get_status reports the generic status of the basic * solution for the specified problem object as follows: * * GLP_OPT - solution is optimal; * GLP_FEAS - solution is feasible; * GLP_INFEAS - solution is infeasible; * GLP_NOFEAS - problem has no feasible solution; * GLP_UNBND - problem has unbounded solution; * GLP_UNDEF - solution is undefined. */ int glp_get_status(glp_prob *lp) { int status; status = glp_get_prim_stat(lp); switch (status) { case GLP_FEAS: switch (glp_get_dual_stat(lp)) { case GLP_FEAS: status = GLP_OPT; break; case GLP_NOFEAS: status = GLP_UNBND; break; case GLP_UNDEF: case GLP_INFEAS: status = status; break; default: xassert(lp != lp); } break; case GLP_UNDEF: case GLP_INFEAS: case GLP_NOFEAS: status = status; break; default: xassert(lp != lp); } return status; } /*********************************************************************** * NAME * * glp_get_prim_stat - retrieve status of primal basic solution * * SYNOPSIS * * int glp_get_prim_stat(glp_prob *lp); * * RETURNS * * The routine glp_get_prim_stat reports the status of the primal basic * solution for the specified problem object as follows: * * GLP_UNDEF - primal solution is undefined; * GLP_FEAS - primal solution is feasible; * GLP_INFEAS - primal solution is infeasible; * GLP_NOFEAS - no primal feasible solution exists. */ int glp_get_prim_stat(glp_prob *lp) { int pbs_stat = lp->pbs_stat; return pbs_stat; } /*********************************************************************** * NAME * * glp_get_dual_stat - retrieve status of dual basic solution * * SYNOPSIS * * int glp_get_dual_stat(glp_prob *lp); * * RETURNS * * The routine glp_get_dual_stat reports the status of the dual basic * solution for the specified problem object as follows: * * GLP_UNDEF - dual solution is undefined; * GLP_FEAS - dual solution is feasible; * GLP_INFEAS - dual solution is infeasible; * GLP_NOFEAS - no dual feasible solution exists. */ int glp_get_dual_stat(glp_prob *lp) { int dbs_stat = lp->dbs_stat; return dbs_stat; } /*********************************************************************** * NAME * * glp_get_obj_val - retrieve objective value (basic solution) * * SYNOPSIS * * double glp_get_obj_val(glp_prob *lp); * * RETURNS * * The routine glp_get_obj_val returns value of the objective function * for basic solution. */ double glp_get_obj_val(glp_prob *lp) { /*struct LPXCPS *cps = lp->cps;*/ double z; z = lp->obj_val; /*if (cps->round && fabs(z) < 1e-9) z = 0.0;*/ return z; } /*********************************************************************** * NAME * * glp_get_row_stat - retrieve row status * * SYNOPSIS * * int glp_get_row_stat(glp_prob *lp, int i); * * RETURNS * * The routine glp_get_row_stat returns current status assigned to the * auxiliary variable associated with i-th row as follows: * * GLP_BS - basic variable; * GLP_NL - non-basic variable on its lower bound; * GLP_NU - non-basic variable on its upper bound; * GLP_NF - non-basic free (unbounded) variable; * GLP_NS - non-basic fixed variable. */ int glp_get_row_stat(glp_prob *lp, int i) { if (!(1 <= i && i <= lp->m)) xerror("glp_get_row_stat: i = %d; row number out of range\n", i); return lp->row[i]->stat; } /*********************************************************************** * NAME * * glp_get_row_prim - retrieve row primal value (basic solution) * * SYNOPSIS * * double glp_get_row_prim(glp_prob *lp, int i); * * RETURNS * * The routine glp_get_row_prim returns primal value of the auxiliary * variable associated with i-th row. */ double glp_get_row_prim(glp_prob *lp, int i) { /*struct LPXCPS *cps = lp->cps;*/ double prim; if (!(1 <= i && i <= lp->m)) xerror("glp_get_row_prim: i = %d; row number out of range\n", i); prim = lp->row[i]->prim; /*if (cps->round && fabs(prim) < 1e-9) prim = 0.0;*/ return prim; } /*********************************************************************** * NAME * * glp_get_row_dual - retrieve row dual value (basic solution) * * SYNOPSIS * * double glp_get_row_dual(glp_prob *lp, int i); * * RETURNS * * The routine glp_get_row_dual returns dual value (i.e. reduced cost) * of the auxiliary variable associated with i-th row. */ double glp_get_row_dual(glp_prob *lp, int i) { /*struct LPXCPS *cps = lp->cps;*/ double dual; if (!(1 <= i && i <= lp->m)) xerror("glp_get_row_dual: i = %d; row number out of range\n", i); dual = lp->row[i]->dual; /*if (cps->round && fabs(dual) < 1e-9) dual = 0.0;*/ return dual; } /*********************************************************************** * NAME * * glp_get_col_stat - retrieve column status * * SYNOPSIS * * int glp_get_col_stat(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_col_stat returns current status assigned to the * structural variable associated with j-th column as follows: * * GLP_BS - basic variable; * GLP_NL - non-basic variable on its lower bound; * GLP_NU - non-basic variable on its upper bound; * GLP_NF - non-basic free (unbounded) variable; * GLP_NS - non-basic fixed variable. */ int glp_get_col_stat(glp_prob *lp, int j) { if (!(1 <= j && j <= lp->n)) xerror("glp_get_col_stat: j = %d; column number out of range\n" , j); return lp->col[j]->stat; } /*********************************************************************** * NAME * * glp_get_col_prim - retrieve column primal value (basic solution) * * SYNOPSIS * * double glp_get_col_prim(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_col_prim returns primal value of the structural * variable associated with j-th column. */ double glp_get_col_prim(glp_prob *lp, int j) { /*struct LPXCPS *cps = lp->cps;*/ double prim; if (!(1 <= j && j <= lp->n)) xerror("glp_get_col_prim: j = %d; column number out of range\n" , j); prim = lp->col[j]->prim; /*if (cps->round && fabs(prim) < 1e-9) prim = 0.0;*/ return prim; } /*********************************************************************** * NAME * * glp_get_col_dual - retrieve column dual value (basic solution) * * SYNOPSIS * * double glp_get_col_dual(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_col_dual returns dual value (i.e. reduced cost) * of the structural variable associated with j-th column. */ double glp_get_col_dual(glp_prob *lp, int j) { /*struct LPXCPS *cps = lp->cps;*/ double dual; if (!(1 <= j && j <= lp->n)) xerror("glp_get_col_dual: j = %d; column number out of range\n" , j); dual = lp->col[j]->dual; /*if (cps->round && fabs(dual) < 1e-9) dual = 0.0;*/ return dual; } /*********************************************************************** * NAME * * glp_get_unbnd_ray - determine variable causing unboundedness * * SYNOPSIS * * int glp_get_unbnd_ray(glp_prob *lp); * * RETURNS * * The routine glp_get_unbnd_ray returns the number k of a variable, * which causes primal or dual unboundedness. If 1 <= k <= m, it is * k-th auxiliary variable, and if m+1 <= k <= m+n, it is (k-m)-th * structural variable, where m is the number of rows, n is the number * of columns in the problem object. If such variable is not defined, * the routine returns 0. * * COMMENTS * * If it is not exactly known which version of the simplex solver * detected unboundedness, i.e. whether the unboundedness is primal or * dual, it is sufficient to check the status of the variable reported * with the routine glp_get_row_stat or glp_get_col_stat. If the * variable is non-basic, the unboundedness is primal, otherwise, if * the variable is basic, the unboundedness is dual (the latter case * means that the problem has no primal feasible dolution). */ int glp_get_unbnd_ray(glp_prob *lp) { int k; k = lp->some; xassert(k >= 0); if (k > lp->m + lp->n) k = 0; return k; } /* eof */ sources_5316/external/glpk/glpfhv.c0000644000176700017670000006542011401660400016133 0ustar paulpaul/* glpfhv.c (LP basis factorization, FHV eta file version) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpfhv.h" #include "glpenv.h" #define xfault xerror /* CAUTION: DO NOT CHANGE THE LIMIT BELOW */ #define M_MAX 100000000 /* = 100*10^6 */ /* maximal order of the basis matrix */ /*********************************************************************** * NAME * * fhv_create_it - create LP basis factorization * * SYNOPSIS * * #include "glpfhv.h" * FHV *fhv_create_it(void); * * DESCRIPTION * * The routine fhv_create_it creates a program object, which represents * a factorization of LP basis. * * RETURNS * * The routine fhv_create_it returns a pointer to the object created. */ FHV *fhv_create_it(void) { FHV *fhv; fhv = xmalloc(sizeof(FHV)); fhv->m_max = fhv->m = 0; fhv->valid = 0; fhv->luf = luf_create_it(); fhv->hh_max = 50; fhv->hh_nfs = 0; fhv->hh_ind = fhv->hh_ptr = fhv->hh_len = NULL; fhv->p0_row = fhv->p0_col = NULL; fhv->cc_ind = NULL; fhv->cc_val = NULL; fhv->upd_tol = 1e-6; fhv->nnz_h = 0; return fhv; } /*********************************************************************** * NAME * * fhv_factorize - compute LP basis factorization * * SYNOPSIS * * #include "glpfhv.h" * int fhv_factorize(FHV *fhv, int m, int (*col)(void *info, int j, * int ind[], double val[]), void *info); * * DESCRIPTION * * The routine fhv_factorize computes the factorization of the basis * matrix B specified by the routine col. * * The parameter fhv specified the basis factorization data structure * created by the routine fhv_create_it. * * The parameter m specifies the order of B, m > 0. * * The formal routine col specifies the matrix B to be factorized. To * obtain j-th column of A the routine fhv_factorize calls the routine * col with the parameter j (1 <= j <= n). In response the routine col * should store row indices and numerical values of non-zero elements * of j-th column of B to locations ind[1,...,len] and val[1,...,len], * respectively, where len is the number of non-zeros in j-th column * returned on exit. Neither zero nor duplicate elements are allowed. * * The parameter info is a transit pointer passed to the routine col. * * RETURNS * * 0 The factorization has been successfully computed. * * FHV_ESING * The specified matrix is singular within the working precision. * * FHV_ECOND * The specified matrix is ill-conditioned. * * For more details see comments to the routine luf_factorize. * * ALGORITHM * * The routine fhv_factorize calls the routine luf_factorize (see the * module GLPLUF), which actually computes LU-factorization of the basis * matrix B in the form * * [B] = (F, V, P, Q), * * where F and V are such matrices that * * B = F * V, * * and P and Q are such permutation matrices that the matrix * * L = P * F * inv(P) * * is lower triangular with unity diagonal, and the matrix * * U = P * V * Q * * is upper triangular. * * In order to build the complete representation of the factorization * (see formula (1) in the file glpfhv.h) the routine fhv_factorize just * additionally sets H = I and P0 = P. */ int fhv_factorize(FHV *fhv, int m, int (*col)(void *info, int j, int ind[], double val[]), void *info) { int ret; if (m < 1) xfault("fhv_factorize: m = %d; invalid parameter\n", m); if (m > M_MAX) xfault("fhv_factorize: m = %d; matrix too big\n", m); fhv->m = m; /* invalidate the factorization */ fhv->valid = 0; /* allocate/reallocate arrays, if necessary */ if (fhv->hh_ind == NULL) fhv->hh_ind = xcalloc(1+fhv->hh_max, sizeof(int)); if (fhv->hh_ptr == NULL) fhv->hh_ptr = xcalloc(1+fhv->hh_max, sizeof(int)); if (fhv->hh_len == NULL) fhv->hh_len = xcalloc(1+fhv->hh_max, sizeof(int)); if (fhv->m_max < m) { if (fhv->p0_row != NULL) xfree(fhv->p0_row); if (fhv->p0_col != NULL) xfree(fhv->p0_col); if (fhv->cc_ind != NULL) xfree(fhv->cc_ind); if (fhv->cc_val != NULL) xfree(fhv->cc_val); fhv->m_max = m + 100; fhv->p0_row = xcalloc(1+fhv->m_max, sizeof(int)); fhv->p0_col = xcalloc(1+fhv->m_max, sizeof(int)); fhv->cc_ind = xcalloc(1+fhv->m_max, sizeof(int)); fhv->cc_val = xcalloc(1+fhv->m_max, sizeof(double)); } /* try to factorize the basis matrix */ switch (luf_factorize(fhv->luf, m, col, info)) { case 0: break; case LUF_ESING: ret = FHV_ESING; goto done; case LUF_ECOND: ret = FHV_ECOND; goto done; default: xassert(fhv != fhv); } /* the basis matrix has been successfully factorized */ fhv->valid = 1; /* H := I */ fhv->hh_nfs = 0; /* P0 := P */ memcpy(&fhv->p0_row[1], &fhv->luf->pp_row[1], sizeof(int) * m); memcpy(&fhv->p0_col[1], &fhv->luf->pp_col[1], sizeof(int) * m); /* currently H has no factors */ fhv->nnz_h = 0; ret = 0; done: /* return to the calling program */ return ret; } /*********************************************************************** * NAME * * fhv_h_solve - solve system H*x = b or H'*x = b * * SYNOPSIS * * #include "glpfhv.h" * void fhv_h_solve(FHV *fhv, int tr, double x[]); * * DESCRIPTION * * The routine fhv_h_solve solves either the system H*x = b (if the * flag tr is zero) or the system H'*x = b (if the flag tr is non-zero), * where the matrix H is a component of the factorization specified by * the parameter fhv, H' is a matrix transposed to H. * * On entry the array x should contain elements of the right-hand side * vector b in locations x[1], ..., x[m], where m is the order of the * matrix H. On exit this array will contain elements of the solution * vector x in the same locations. */ void fhv_h_solve(FHV *fhv, int tr, double x[]) { int nfs = fhv->hh_nfs; int *hh_ind = fhv->hh_ind; int *hh_ptr = fhv->hh_ptr; int *hh_len = fhv->hh_len; int *sv_ind = fhv->luf->sv_ind; double *sv_val = fhv->luf->sv_val; int i, k, beg, end, ptr; double temp; if (!fhv->valid) xfault("fhv_h_solve: the factorization is not valid\n"); if (!tr) { /* solve the system H*x = b */ for (k = 1; k <= nfs; k++) { i = hh_ind[k]; temp = x[i]; beg = hh_ptr[k]; end = beg + hh_len[k] - 1; for (ptr = beg; ptr <= end; ptr++) temp -= sv_val[ptr] * x[sv_ind[ptr]]; x[i] = temp; } } else { /* solve the system H'*x = b */ for (k = nfs; k >= 1; k--) { i = hh_ind[k]; temp = x[i]; if (temp == 0.0) continue; beg = hh_ptr[k]; end = beg + hh_len[k] - 1; for (ptr = beg; ptr <= end; ptr++) x[sv_ind[ptr]] -= sv_val[ptr] * temp; } } return; } /*********************************************************************** * NAME * * fhv_ftran - perform forward transformation (solve system B*x = b) * * SYNOPSIS * * #include "glpfhv.h" * void fhv_ftran(FHV *fhv, double x[]); * * DESCRIPTION * * The routine fhv_ftran performs forward transformation, i.e. solves * the system B*x = b, where B is the basis matrix, x is the vector of * unknowns to be computed, b is the vector of right-hand sides. * * On entry elements of the vector b should be stored in dense format * in locations x[1], ..., x[m], where m is the number of rows. On exit * the routine stores elements of the vector x in the same locations. */ void fhv_ftran(FHV *fhv, double x[]) { int *pp_row = fhv->luf->pp_row; int *pp_col = fhv->luf->pp_col; int *p0_row = fhv->p0_row; int *p0_col = fhv->p0_col; if (!fhv->valid) xfault("fhv_ftran: the factorization is not valid\n"); /* B = F*H*V, therefore inv(B) = inv(V)*inv(H)*inv(F) */ fhv->luf->pp_row = p0_row; fhv->luf->pp_col = p0_col; luf_f_solve(fhv->luf, 0, x); fhv->luf->pp_row = pp_row; fhv->luf->pp_col = pp_col; fhv_h_solve(fhv, 0, x); luf_v_solve(fhv->luf, 0, x); return; } /*********************************************************************** * NAME * * fhv_btran - perform backward transformation (solve system B'*x = b) * * SYNOPSIS * * #include "glpfhv.h" * void fhv_btran(FHV *fhv, double x[]); * * DESCRIPTION * * The routine fhv_btran performs backward transformation, i.e. solves * the system B'*x = b, where B' is a matrix transposed to the basis * matrix B, x is the vector of unknowns to be computed, b is the vector * of right-hand sides. * * On entry elements of the vector b should be stored in dense format * in locations x[1], ..., x[m], where m is the number of rows. On exit * the routine stores elements of the vector x in the same locations. */ void fhv_btran(FHV *fhv, double x[]) { int *pp_row = fhv->luf->pp_row; int *pp_col = fhv->luf->pp_col; int *p0_row = fhv->p0_row; int *p0_col = fhv->p0_col; if (!fhv->valid) xfault("fhv_btran: the factorization is not valid\n"); /* B = F*H*V, therefore inv(B') = inv(F')*inv(H')*inv(V') */ luf_v_solve(fhv->luf, 1, x); fhv_h_solve(fhv, 1, x); fhv->luf->pp_row = p0_row; fhv->luf->pp_col = p0_col; luf_f_solve(fhv->luf, 1, x); fhv->luf->pp_row = pp_row; fhv->luf->pp_col = pp_col; return; } /*********************************************************************** * NAME * * fhv_update_it - update LP basis factorization * * SYNOPSIS * * #include "glpfhv.h" * int fhv_update_it(FHV *fhv, int j, int len, const int ind[], * const double val[]); * * DESCRIPTION * * The routine fhv_update_it updates the factorization of the basis * matrix B after replacing its j-th column by a new vector. * * The parameter j specifies the number of column of B, which has been * replaced, 1 <= j <= m, where m is the order of B. * * Row indices and numerical values of non-zero elements of the new * column of B should be placed in locations ind[1], ..., ind[len] and * val[1], ..., val[len], resp., where len is the number of non-zeros * in the column. Neither zero nor duplicate elements are allowed. * * RETURNS * * 0 The factorization has been successfully updated. * * FHV_ESING * The adjacent basis matrix is structurally singular, since after * changing j-th column of matrix V by the new column (see algorithm * below) the case k1 > k2 occured. * * FHV_ECHECK * The factorization is inaccurate, since after transforming k2-th * row of matrix U = P*V*Q, its diagonal element u[k2,k2] is zero or * close to zero, * * FHV_ELIMIT * Maximal number of H factors has been reached. * * FHV_EROOM * Overflow of the sparse vector area. * * In case of non-zero return code the factorization becomes invalid. * It should not be used until it has been recomputed with the routine * fhv_factorize. * * ALGORITHM * * The routine fhv_update_it is based on the transformation proposed by * Forrest and Tomlin. * * Let j-th column of the basis matrix B have been replaced by new * column B[j]. In order to keep the equality B = F*H*V j-th column of * matrix V should be replaced by the column inv(F*H)*B[j]. * * From the standpoint of matrix U = P*V*Q, replacement of j-th column * of matrix V is equivalent to replacement of k1-th column of matrix U, * where k1 is determined by permutation matrix Q. Thus, matrix U loses * its upper triangular form and becomes the following: * * 1 k1 k2 m * 1 x x * x x x x x x x * . x * x x x x x x x * k1 . . * x x x x x x x * . . * x x x x x x x * . . * . x x x x x x * . . * . . x x x x x * . . * . . . x x x x * k2 . . * . . . . x x x * . . . . . . . . x x * m . . . . . . . . . x * * where row index k2 corresponds to the lowest non-zero element of * k1-th column. * * The routine moves rows and columns k1+1, k1+2, ..., k2 of matrix U * by one position to the left and upwards and moves k1-th row and k1-th * column to position k2. As the result of such symmetric permutations * matrix U becomes the following: * * 1 k1 k2 m * 1 x x x x x x x * x x * . x x x x x x * x x * k1 . . x x x x x * x x * . . . x x x x * x x * . . . . x x x * x x * . . . . . x x * x x * . . . . . . x * x x * k2 . . x x x x x * x x * . . . . . . . . x x * m . . . . . . . . . x * * Then the routine performs gaussian elimination to eliminate elements * u[k2,k1], u[k2,k1+1], ..., u[k2,k2-1] using diagonal elements * u[k1,k1], u[k1+1,k1+1], ..., u[k2-1,k2-1] as pivots in the same way * as described in comments to the routine luf_factorize (see the module * GLPLUF). Note that actually all operations are performed on matrix V, * not on matrix U. During the elimination process the routine permutes * neither rows nor columns, so only k2-th row of matrix U is changed. * * To keep the main equality B = F*H*V, each time when the routine * applies elementary gaussian transformation to the transformed row of * matrix V (which corresponds to k2-th row of matrix U), it also adds * a new element (gaussian multiplier) to the current row-like factor * of matrix H, which corresponds to the transformed row of matrix V. */ int fhv_update_it(FHV *fhv, int j, int len, const int ind[], const double val[]) { int m = fhv->m; LUF *luf = fhv->luf; int *vr_ptr = luf->vr_ptr; int *vr_len = luf->vr_len; int *vr_cap = luf->vr_cap; double *vr_piv = luf->vr_piv; int *vc_ptr = luf->vc_ptr; int *vc_len = luf->vc_len; int *vc_cap = luf->vc_cap; int *pp_row = luf->pp_row; int *pp_col = luf->pp_col; int *qq_row = luf->qq_row; int *qq_col = luf->qq_col; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; double *work = luf->work; double eps_tol = luf->eps_tol; int *hh_ind = fhv->hh_ind; int *hh_ptr = fhv->hh_ptr; int *hh_len = fhv->hh_len; int *p0_row = fhv->p0_row; int *p0_col = fhv->p0_col; int *cc_ind = fhv->cc_ind; double *cc_val = fhv->cc_val; double upd_tol = fhv->upd_tol; int i, i_beg, i_end, i_ptr, j_beg, j_end, j_ptr, k, k1, k2, p, q, p_beg, p_end, p_ptr, ptr, ret; double f, temp; if (!fhv->valid) xfault("fhv_update_it: the factorization is not valid\n"); if (!(1 <= j && j <= m)) xfault("fhv_update_it: j = %d; column number out of range\n", j); /* check if the new factor of matrix H can be created */ if (fhv->hh_nfs == fhv->hh_max) { /* maximal number of updates has been reached */ fhv->valid = 0; ret = FHV_ELIMIT; goto done; } /* convert new j-th column of B to dense format */ for (i = 1; i <= m; i++) cc_val[i] = 0.0; for (k = 1; k <= len; k++) { i = ind[k]; if (!(1 <= i && i <= m)) xfault("fhv_update_it: ind[%d] = %d; row number out of rang" "e\n", k, i); if (cc_val[i] != 0.0) xfault("fhv_update_it: ind[%d] = %d; duplicate row index no" "t allowed\n", k, i); if (val[k] == 0.0) xfault("fhv_update_it: val[%d] = %g; zero element not allow" "ed\n", k, val[k]); cc_val[i] = val[k]; } /* new j-th column of V := inv(F * H) * (new B[j]) */ fhv->luf->pp_row = p0_row; fhv->luf->pp_col = p0_col; luf_f_solve(fhv->luf, 0, cc_val); fhv->luf->pp_row = pp_row; fhv->luf->pp_col = pp_col; fhv_h_solve(fhv, 0, cc_val); /* convert new j-th column of V to sparse format */ len = 0; for (i = 1; i <= m; i++) { temp = cc_val[i]; if (temp == 0.0 || fabs(temp) < eps_tol) continue; len++, cc_ind[len] = i, cc_val[len] = temp; } /* clear old content of j-th column of matrix V */ j_beg = vc_ptr[j]; j_end = j_beg + vc_len[j] - 1; for (j_ptr = j_beg; j_ptr <= j_end; j_ptr++) { /* get row index of v[i,j] */ i = sv_ind[j_ptr]; /* find v[i,j] in the i-th row */ i_beg = vr_ptr[i]; i_end = i_beg + vr_len[i] - 1; for (i_ptr = i_beg; sv_ind[i_ptr] != j; i_ptr++) /* nop */; xassert(i_ptr <= i_end); /* remove v[i,j] from the i-th row */ sv_ind[i_ptr] = sv_ind[i_end]; sv_val[i_ptr] = sv_val[i_end]; vr_len[i]--; } /* now j-th column of matrix V is empty */ luf->nnz_v -= vc_len[j]; vc_len[j] = 0; /* add new elements of j-th column of matrix V to corresponding row lists; determine indices k1 and k2 */ k1 = qq_row[j], k2 = 0; for (ptr = 1; ptr <= len; ptr++) { /* get row index of v[i,j] */ i = cc_ind[ptr]; /* at least one unused location is needed in i-th row */ if (vr_len[i] + 1 > vr_cap[i]) { if (luf_enlarge_row(luf, i, vr_len[i] + 10)) { /* overflow of the sparse vector area */ fhv->valid = 0; luf->new_sva = luf->sv_size + luf->sv_size; xassert(luf->new_sva > luf->sv_size); ret = FHV_EROOM; goto done; } } /* add v[i,j] to i-th row */ i_ptr = vr_ptr[i] + vr_len[i]; sv_ind[i_ptr] = j; sv_val[i_ptr] = cc_val[ptr]; vr_len[i]++; /* adjust index k2 */ if (k2 < pp_col[i]) k2 = pp_col[i]; } /* capacity of j-th column (which is currently empty) should be not less than len locations */ if (vc_cap[j] < len) { if (luf_enlarge_col(luf, j, len)) { /* overflow of the sparse vector area */ fhv->valid = 0; luf->new_sva = luf->sv_size + luf->sv_size; xassert(luf->new_sva > luf->sv_size); ret = FHV_EROOM; goto done; } } /* add new elements of matrix V to j-th column list */ j_ptr = vc_ptr[j]; memmove(&sv_ind[j_ptr], &cc_ind[1], len * sizeof(int)); memmove(&sv_val[j_ptr], &cc_val[1], len * sizeof(double)); vc_len[j] = len; luf->nnz_v += len; /* if k1 > k2, diagonal element u[k2,k2] of matrix U is zero and therefore the adjacent basis matrix is structurally singular */ if (k1 > k2) { fhv->valid = 0; ret = FHV_ESING; goto done; } /* perform implicit symmetric permutations of rows and columns of matrix U */ i = pp_row[k1], j = qq_col[k1]; for (k = k1; k < k2; k++) { pp_row[k] = pp_row[k+1], pp_col[pp_row[k]] = k; qq_col[k] = qq_col[k+1], qq_row[qq_col[k]] = k; } pp_row[k2] = i, pp_col[i] = k2; qq_col[k2] = j, qq_row[j] = k2; /* now i-th row of the matrix V is k2-th row of matrix U; since no pivoting is used, only this row will be transformed */ /* copy elements of i-th row of matrix V to the working array and remove these elements from matrix V */ for (j = 1; j <= m; j++) work[j] = 0.0; i_beg = vr_ptr[i]; i_end = i_beg + vr_len[i] - 1; for (i_ptr = i_beg; i_ptr <= i_end; i_ptr++) { /* get column index of v[i,j] */ j = sv_ind[i_ptr]; /* store v[i,j] to the working array */ work[j] = sv_val[i_ptr]; /* find v[i,j] in the j-th column */ j_beg = vc_ptr[j]; j_end = j_beg + vc_len[j] - 1; for (j_ptr = j_beg; sv_ind[j_ptr] != i; j_ptr++) /* nop */; xassert(j_ptr <= j_end); /* remove v[i,j] from the j-th column */ sv_ind[j_ptr] = sv_ind[j_end]; sv_val[j_ptr] = sv_val[j_end]; vc_len[j]--; } /* now i-th row of matrix V is empty */ luf->nnz_v -= vr_len[i]; vr_len[i] = 0; /* create the next row-like factor of the matrix H; this factor corresponds to i-th (transformed) row */ fhv->hh_nfs++; hh_ind[fhv->hh_nfs] = i; /* hh_ptr[] will be set later */ hh_len[fhv->hh_nfs] = 0; /* up to (k2 - k1) free locations are needed to add new elements to the non-trivial row of the row-like factor */ if (luf->sv_end - luf->sv_beg < k2 - k1) { luf_defrag_sva(luf); if (luf->sv_end - luf->sv_beg < k2 - k1) { /* overflow of the sparse vector area */ fhv->valid = luf->valid = 0; luf->new_sva = luf->sv_size + luf->sv_size; xassert(luf->new_sva > luf->sv_size); ret = FHV_EROOM; goto done; } } /* eliminate subdiagonal elements of matrix U */ for (k = k1; k < k2; k++) { /* v[p,q] = u[k,k] */ p = pp_row[k], q = qq_col[k]; /* this is the crucial point, where even tiny non-zeros should not be dropped */ if (work[q] == 0.0) continue; /* compute gaussian multiplier f = v[i,q] / v[p,q] */ f = work[q] / vr_piv[p]; /* perform gaussian transformation: (i-th row) := (i-th row) - f * (p-th row) in order to eliminate v[i,q] = u[k2,k] */ p_beg = vr_ptr[p]; p_end = p_beg + vr_len[p] - 1; for (p_ptr = p_beg; p_ptr <= p_end; p_ptr++) work[sv_ind[p_ptr]] -= f * sv_val[p_ptr]; /* store new element (gaussian multiplier that corresponds to p-th row) in the current row-like factor */ luf->sv_end--; sv_ind[luf->sv_end] = p; sv_val[luf->sv_end] = f; hh_len[fhv->hh_nfs]++; } /* set pointer to the current row-like factor of the matrix H (if no elements were added to this factor, it is unity matrix and therefore can be discarded) */ if (hh_len[fhv->hh_nfs] == 0) fhv->hh_nfs--; else { hh_ptr[fhv->hh_nfs] = luf->sv_end; fhv->nnz_h += hh_len[fhv->hh_nfs]; } /* store new pivot which corresponds to u[k2,k2] */ vr_piv[i] = work[qq_col[k2]]; /* new elements of i-th row of matrix V (which are non-diagonal elements u[k2,k2+1], ..., u[k2,m] of matrix U = P*V*Q) now are contained in the working array; add them to matrix V */ len = 0; for (k = k2+1; k <= m; k++) { /* get column index and value of v[i,j] = u[k2,k] */ j = qq_col[k]; temp = work[j]; /* if v[i,j] is close to zero, skip it */ if (fabs(temp) < eps_tol) continue; /* at least one unused location is needed in j-th column */ if (vc_len[j] + 1 > vc_cap[j]) { if (luf_enlarge_col(luf, j, vc_len[j] + 10)) { /* overflow of the sparse vector area */ fhv->valid = 0; luf->new_sva = luf->sv_size + luf->sv_size; xassert(luf->new_sva > luf->sv_size); ret = FHV_EROOM; goto done; } } /* add v[i,j] to j-th column */ j_ptr = vc_ptr[j] + vc_len[j]; sv_ind[j_ptr] = i; sv_val[j_ptr] = temp; vc_len[j]++; /* also store v[i,j] to the auxiliary array */ len++, cc_ind[len] = j, cc_val[len] = temp; } /* capacity of i-th row (which is currently empty) should be not less than len locations */ if (vr_cap[i] < len) { if (luf_enlarge_row(luf, i, len)) { /* overflow of the sparse vector area */ fhv->valid = 0; luf->new_sva = luf->sv_size + luf->sv_size; xassert(luf->new_sva > luf->sv_size); ret = FHV_EROOM; goto done; } } /* add new elements to i-th row list */ i_ptr = vr_ptr[i]; memmove(&sv_ind[i_ptr], &cc_ind[1], len * sizeof(int)); memmove(&sv_val[i_ptr], &cc_val[1], len * sizeof(double)); vr_len[i] = len; luf->nnz_v += len; /* updating is finished; check that diagonal element u[k2,k2] is not very small in absolute value among other elements in k2-th row and k2-th column of matrix U = P*V*Q */ /* temp = max(|u[k2,*]|, |u[*,k2]|) */ temp = 0.0; /* walk through k2-th row of U which is i-th row of V */ i = pp_row[k2]; i_beg = vr_ptr[i]; i_end = i_beg + vr_len[i] - 1; for (i_ptr = i_beg; i_ptr <= i_end; i_ptr++) if (temp < fabs(sv_val[i_ptr])) temp = fabs(sv_val[i_ptr]); /* walk through k2-th column of U which is j-th column of V */ j = qq_col[k2]; j_beg = vc_ptr[j]; j_end = j_beg + vc_len[j] - 1; for (j_ptr = j_beg; j_ptr <= j_end; j_ptr++) if (temp < fabs(sv_val[j_ptr])) temp = fabs(sv_val[j_ptr]); /* check that u[k2,k2] is not very small */ if (fabs(vr_piv[i]) < upd_tol * temp) { /* the factorization seems to be inaccurate and therefore must be recomputed */ fhv->valid = 0; ret = FHV_ECHECK; goto done; } /* the factorization has been successfully updated */ ret = 0; done: /* return to the calling program */ return ret; } /*********************************************************************** * NAME * * fhv_delete_it - delete LP basis factorization * * SYNOPSIS * * #include "glpfhv.h" * void fhv_delete_it(FHV *fhv); * * DESCRIPTION * * The routine fhv_delete_it deletes LP basis factorization specified * by the parameter fhv and frees all memory allocated to this program * object. */ void fhv_delete_it(FHV *fhv) { luf_delete_it(fhv->luf); if (fhv->hh_ind != NULL) xfree(fhv->hh_ind); if (fhv->hh_ptr != NULL) xfree(fhv->hh_ptr); if (fhv->hh_len != NULL) xfree(fhv->hh_len); if (fhv->p0_row != NULL) xfree(fhv->p0_row); if (fhv->p0_col != NULL) xfree(fhv->p0_col); if (fhv->cc_ind != NULL) xfree(fhv->cc_ind); if (fhv->cc_val != NULL) xfree(fhv->cc_val); xfree(fhv); return; } /* eof */ sources_5316/external/glpk/glplpf.c0000644000176700017670000007533011401660400016132 0ustar paulpaul/* glplpf.c (LP basis factorization, Schur complement version) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glplpf.h" #include "glpenv.h" #define xfault xerror #define _GLPLPF_DEBUG 0 /* CAUTION: DO NOT CHANGE THE LIMIT BELOW */ #define M_MAX 100000000 /* = 100*10^6 */ /* maximal order of the basis matrix */ /*********************************************************************** * NAME * * lpf_create_it - create LP basis factorization * * SYNOPSIS * * #include "glplpf.h" * LPF *lpf_create_it(void); * * DESCRIPTION * * The routine lpf_create_it creates a program object, which represents * a factorization of LP basis. * * RETURNS * * The routine lpf_create_it returns a pointer to the object created. */ LPF *lpf_create_it(void) { LPF *lpf; #if _GLPLPF_DEBUG xprintf("lpf_create_it: warning: debug mode enabled\n"); #endif lpf = xmalloc(sizeof(LPF)); lpf->valid = 0; lpf->m0_max = lpf->m0 = 0; lpf->luf = luf_create_it(); lpf->m = 0; lpf->B = NULL; lpf->n_max = 50; lpf->n = 0; lpf->R_ptr = lpf->R_len = NULL; lpf->S_ptr = lpf->S_len = NULL; lpf->scf = NULL; lpf->P_row = lpf->P_col = NULL; lpf->Q_row = lpf->Q_col = NULL; lpf->v_size = 1000; lpf->v_ptr = 0; lpf->v_ind = NULL; lpf->v_val = NULL; lpf->work1 = lpf->work2 = NULL; return lpf; } /*********************************************************************** * NAME * * lpf_factorize - compute LP basis factorization * * SYNOPSIS * * #include "glplpf.h" * int lpf_factorize(LPF *lpf, int m, const int bh[], int (*col) * (void *info, int j, int ind[], double val[]), void *info); * * DESCRIPTION * * The routine lpf_factorize computes the factorization of the basis * matrix B specified by the routine col. * * The parameter lpf specified the basis factorization data structure * created with the routine lpf_create_it. * * The parameter m specifies the order of B, m > 0. * * The array bh specifies the basis header: bh[j], 1 <= j <= m, is the * number of j-th column of B in some original matrix. The array bh is * optional and can be specified as NULL. * * The formal routine col specifies the matrix B to be factorized. To * obtain j-th column of A the routine lpf_factorize calls the routine * col with the parameter j (1 <= j <= n). In response the routine col * should store row indices and numerical values of non-zero elements * of j-th column of B to locations ind[1,...,len] and val[1,...,len], * respectively, where len is the number of non-zeros in j-th column * returned on exit. Neither zero nor duplicate elements are allowed. * * The parameter info is a transit pointer passed to the routine col. * * RETURNS * * 0 The factorization has been successfully computed. * * LPF_ESING * The specified matrix is singular within the working precision. * * LPF_ECOND * The specified matrix is ill-conditioned. * * For more details see comments to the routine luf_factorize. */ int lpf_factorize(LPF *lpf, int m, const int bh[], int (*col) (void *info, int j, int ind[], double val[]), void *info) { int k, ret; #if _GLPLPF_DEBUG int i, j, len, *ind; double *B, *val; #endif xassert(bh == bh); if (m < 1) xfault("lpf_factorize: m = %d; invalid parameter\n", m); if (m > M_MAX) xfault("lpf_factorize: m = %d; matrix too big\n", m); lpf->m0 = lpf->m = m; /* invalidate the factorization */ lpf->valid = 0; /* allocate/reallocate arrays, if necessary */ if (lpf->R_ptr == NULL) lpf->R_ptr = xcalloc(1+lpf->n_max, sizeof(int)); if (lpf->R_len == NULL) lpf->R_len = xcalloc(1+lpf->n_max, sizeof(int)); if (lpf->S_ptr == NULL) lpf->S_ptr = xcalloc(1+lpf->n_max, sizeof(int)); if (lpf->S_len == NULL) lpf->S_len = xcalloc(1+lpf->n_max, sizeof(int)); if (lpf->scf == NULL) lpf->scf = scf_create_it(lpf->n_max); if (lpf->v_ind == NULL) lpf->v_ind = xcalloc(1+lpf->v_size, sizeof(int)); if (lpf->v_val == NULL) lpf->v_val = xcalloc(1+lpf->v_size, sizeof(double)); if (lpf->m0_max < m) { if (lpf->P_row != NULL) xfree(lpf->P_row); if (lpf->P_col != NULL) xfree(lpf->P_col); if (lpf->Q_row != NULL) xfree(lpf->Q_row); if (lpf->Q_col != NULL) xfree(lpf->Q_col); if (lpf->work1 != NULL) xfree(lpf->work1); if (lpf->work2 != NULL) xfree(lpf->work2); lpf->m0_max = m + 100; lpf->P_row = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(int)); lpf->P_col = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(int)); lpf->Q_row = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(int)); lpf->Q_col = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(int)); lpf->work1 = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(double)); lpf->work2 = xcalloc(1+lpf->m0_max+lpf->n_max, sizeof(double)); } /* try to factorize the basis matrix */ switch (luf_factorize(lpf->luf, m, col, info)) { case 0: break; case LUF_ESING: ret = LPF_ESING; goto done; case LUF_ECOND: ret = LPF_ECOND; goto done; default: xassert(lpf != lpf); } /* the basis matrix has been successfully factorized */ lpf->valid = 1; #if _GLPLPF_DEBUG /* store the basis matrix for debugging */ if (lpf->B != NULL) xfree(lpf->B); xassert(m <= 32767); lpf->B = B = xcalloc(1+m*m, sizeof(double)); ind = xcalloc(1+m, sizeof(int)); val = xcalloc(1+m, sizeof(double)); for (k = 1; k <= m * m; k++) B[k] = 0.0; for (j = 1; j <= m; j++) { len = col(info, j, ind, val); xassert(0 <= len && len <= m); for (k = 1; k <= len; k++) { i = ind[k]; xassert(1 <= i && i <= m); xassert(B[(i - 1) * m + j] == 0.0); xassert(val[k] != 0.0); B[(i - 1) * m + j] = val[k]; } } xfree(ind); xfree(val); #endif /* B = B0, so there are no additional rows/columns */ lpf->n = 0; /* reset the Schur complement factorization */ scf_reset_it(lpf->scf); /* P := Q := I */ for (k = 1; k <= m; k++) { lpf->P_row[k] = lpf->P_col[k] = k; lpf->Q_row[k] = lpf->Q_col[k] = k; } /* make all SVA locations free */ lpf->v_ptr = 1; ret = 0; done: /* return to the calling program */ return ret; } /*********************************************************************** * The routine r_prod computes the product y := y + alpha * R * x, * where x is a n-vector, alpha is a scalar, y is a m0-vector. * * Since matrix R is available by columns, the product is computed as * a linear combination: * * y := y + alpha * (R[1] * x[1] + ... + R[n] * x[n]), * * where R[j] is j-th column of R. */ static void r_prod(LPF *lpf, double y[], double a, const double x[]) { int n = lpf->n; int *R_ptr = lpf->R_ptr; int *R_len = lpf->R_len; int *v_ind = lpf->v_ind; double *v_val = lpf->v_val; int j, beg, end, ptr; double t; for (j = 1; j <= n; j++) { if (x[j] == 0.0) continue; /* y := y + alpha * R[j] * x[j] */ t = a * x[j]; beg = R_ptr[j]; end = beg + R_len[j]; for (ptr = beg; ptr < end; ptr++) y[v_ind[ptr]] += t * v_val[ptr]; } return; } /*********************************************************************** * The routine rt_prod computes the product y := y + alpha * R' * x, * where R' is a matrix transposed to R, x is a m0-vector, alpha is a * scalar, y is a n-vector. * * Since matrix R is available by columns, the product components are * computed as inner products: * * y[j] := y[j] + alpha * (j-th column of R) * x * * for j = 1, 2, ..., n. */ static void rt_prod(LPF *lpf, double y[], double a, const double x[]) { int n = lpf->n; int *R_ptr = lpf->R_ptr; int *R_len = lpf->R_len; int *v_ind = lpf->v_ind; double *v_val = lpf->v_val; int j, beg, end, ptr; double t; for (j = 1; j <= n; j++) { /* t := (j-th column of R) * x */ t = 0.0; beg = R_ptr[j]; end = beg + R_len[j]; for (ptr = beg; ptr < end; ptr++) t += v_val[ptr] * x[v_ind[ptr]]; /* y[j] := y[j] + alpha * t */ y[j] += a * t; } return; } /*********************************************************************** * The routine s_prod computes the product y := y + alpha * S * x, * where x is a m0-vector, alpha is a scalar, y is a n-vector. * * Since matrix S is available by rows, the product components are * computed as inner products: * * y[i] = y[i] + alpha * (i-th row of S) * x * * for i = 1, 2, ..., n. */ static void s_prod(LPF *lpf, double y[], double a, const double x[]) { int n = lpf->n; int *S_ptr = lpf->S_ptr; int *S_len = lpf->S_len; int *v_ind = lpf->v_ind; double *v_val = lpf->v_val; int i, beg, end, ptr; double t; for (i = 1; i <= n; i++) { /* t := (i-th row of S) * x */ t = 0.0; beg = S_ptr[i]; end = beg + S_len[i]; for (ptr = beg; ptr < end; ptr++) t += v_val[ptr] * x[v_ind[ptr]]; /* y[i] := y[i] + alpha * t */ y[i] += a * t; } return; } /*********************************************************************** * The routine st_prod computes the product y := y + alpha * S' * x, * where S' is a matrix transposed to S, x is a n-vector, alpha is a * scalar, y is m0-vector. * * Since matrix R is available by rows, the product is computed as a * linear combination: * * y := y + alpha * (S'[1] * x[1] + ... + S'[n] * x[n]), * * where S'[i] is i-th row of S. */ static void st_prod(LPF *lpf, double y[], double a, const double x[]) { int n = lpf->n; int *S_ptr = lpf->S_ptr; int *S_len = lpf->S_len; int *v_ind = lpf->v_ind; double *v_val = lpf->v_val; int i, beg, end, ptr; double t; for (i = 1; i <= n; i++) { if (x[i] == 0.0) continue; /* y := y + alpha * S'[i] * x[i] */ t = a * x[i]; beg = S_ptr[i]; end = beg + S_len[i]; for (ptr = beg; ptr < end; ptr++) y[v_ind[ptr]] += t * v_val[ptr]; } return; } #if _GLPLPF_DEBUG /*********************************************************************** * The routine check_error computes the maximal relative error between * left- and right-hand sides for the system B * x = b (if tr is zero) * or B' * x = b (if tr is non-zero), where B' is a matrix transposed * to B. (This routine is intended for debugging only.) */ static void check_error(LPF *lpf, int tr, const double x[], const double b[]) { int m = lpf->m; double *B = lpf->B; int i, j; double d, dmax = 0.0, s, t, tmax; for (i = 1; i <= m; i++) { s = 0.0; tmax = 1.0; for (j = 1; j <= m; j++) { if (!tr) t = B[m * (i - 1) + j] * x[j]; else t = B[m * (j - 1) + i] * x[j]; if (tmax < fabs(t)) tmax = fabs(t); s += t; } d = fabs(s - b[i]) / tmax; if (dmax < d) dmax = d; } if (dmax > 1e-8) xprintf("%s: dmax = %g; relative error too large\n", !tr ? "lpf_ftran" : "lpf_btran", dmax); return; } #endif /*********************************************************************** * NAME * * lpf_ftran - perform forward transformation (solve system B*x = b) * * SYNOPSIS * * #include "glplpf.h" * void lpf_ftran(LPF *lpf, double x[]); * * DESCRIPTION * * The routine lpf_ftran performs forward transformation, i.e. solves * the system B*x = b, where B is the basis matrix, x is the vector of * unknowns to be computed, b is the vector of right-hand sides. * * On entry elements of the vector b should be stored in dense format * in locations x[1], ..., x[m], where m is the number of rows. On exit * the routine stores elements of the vector x in the same locations. * * BACKGROUND * * Solution of the system B * x = b can be obtained by solving the * following augmented system: * * ( B F^) ( x ) ( b ) * ( ) ( ) = ( ) * ( G^ H^) ( y ) ( 0 ) * * which, using the main equality, can be written as follows: * * ( L0 0 ) ( U0 R ) ( x ) ( b ) * P ( ) ( ) Q ( ) = ( ) * ( S I ) ( 0 C ) ( y ) ( 0 ) * * therefore, * * ( x ) ( U0 R )-1 ( L0 0 )-1 ( b ) * ( ) = Q' ( ) ( ) P' ( ) * ( y ) ( 0 C ) ( S I ) ( 0 ) * * Thus, computing the solution includes the following steps: * * 1. Compute * * ( f ) ( b ) * ( ) = P' ( ) * ( g ) ( 0 ) * * 2. Solve the system * * ( f1 ) ( L0 0 )-1 ( f ) ( L0 0 ) ( f1 ) ( f ) * ( ) = ( ) ( ) => ( ) ( ) = ( ) * ( g1 ) ( S I ) ( g ) ( S I ) ( g1 ) ( g ) * * from which it follows that: * * { L0 * f1 = f f1 = inv(L0) * f * { => * { S * f1 + g1 = g g1 = g - S * f1 * * 3. Solve the system * * ( f2 ) ( U0 R )-1 ( f1 ) ( U0 R ) ( f2 ) ( f1 ) * ( ) = ( ) ( ) => ( ) ( ) = ( ) * ( g2 ) ( 0 C ) ( g1 ) ( 0 C ) ( g2 ) ( g1 ) * * from which it follows that: * * { U0 * f2 + R * g2 = f1 f2 = inv(U0) * (f1 - R * g2) * { => * { C * g2 = g1 g2 = inv(C) * g1 * * 4. Compute * * ( x ) ( f2 ) * ( ) = Q' ( ) * ( y ) ( g2 ) */ void lpf_ftran(LPF *lpf, double x[]) { int m0 = lpf->m0; int m = lpf->m; int n = lpf->n; int *P_col = lpf->P_col; int *Q_col = lpf->Q_col; double *fg = lpf->work1; double *f = fg; double *g = fg + m0; int i, ii; #if _GLPLPF_DEBUG double *b; #endif if (!lpf->valid) xfault("lpf_ftran: the factorization is not valid\n"); xassert(0 <= m && m <= m0 + n); #if _GLPLPF_DEBUG /* save the right-hand side vector */ b = xcalloc(1+m, sizeof(double)); for (i = 1; i <= m; i++) b[i] = x[i]; #endif /* (f g) := inv(P) * (b 0) */ for (i = 1; i <= m0 + n; i++) fg[i] = ((ii = P_col[i]) <= m ? x[ii] : 0.0); /* f1 := inv(L0) * f */ luf_f_solve(lpf->luf, 0, f); /* g1 := g - S * f1 */ s_prod(lpf, g, -1.0, f); /* g2 := inv(C) * g1 */ scf_solve_it(lpf->scf, 0, g); /* f2 := inv(U0) * (f1 - R * g2) */ r_prod(lpf, f, -1.0, g); luf_v_solve(lpf->luf, 0, f); /* (x y) := inv(Q) * (f2 g2) */ for (i = 1; i <= m; i++) x[i] = fg[Q_col[i]]; #if _GLPLPF_DEBUG /* check relative error in solution */ check_error(lpf, 0, x, b); xfree(b); #endif return; } /*********************************************************************** * NAME * * lpf_btran - perform backward transformation (solve system B'*x = b) * * SYNOPSIS * * #include "glplpf.h" * void lpf_btran(LPF *lpf, double x[]); * * DESCRIPTION * * The routine lpf_btran performs backward transformation, i.e. solves * the system B'*x = b, where B' is a matrix transposed to the basis * matrix B, x is the vector of unknowns to be computed, b is the vector * of right-hand sides. * * On entry elements of the vector b should be stored in dense format * in locations x[1], ..., x[m], where m is the number of rows. On exit * the routine stores elements of the vector x in the same locations. * * BACKGROUND * * Solution of the system B' * x = b, where B' is a matrix transposed * to B, can be obtained by solving the following augmented system: * * ( B F^)T ( x ) ( b ) * ( ) ( ) = ( ) * ( G^ H^) ( y ) ( 0 ) * * which, using the main equality, can be written as follows: * * T ( U0 R )T ( L0 0 )T T ( x ) ( b ) * Q ( ) ( ) P ( ) = ( ) * ( 0 C ) ( S I ) ( y ) ( 0 ) * * or, equivalently, as follows: * * ( U'0 0 ) ( L'0 S') ( x ) ( b ) * Q' ( ) ( ) P' ( ) = ( ) * ( R' C') ( 0 I ) ( y ) ( 0 ) * * therefore, * * ( x ) ( L'0 S')-1 ( U'0 0 )-1 ( b ) * ( ) = P ( ) ( ) Q ( ) * ( y ) ( 0 I ) ( R' C') ( 0 ) * * Thus, computing the solution includes the following steps: * * 1. Compute * * ( f ) ( b ) * ( ) = Q ( ) * ( g ) ( 0 ) * * 2. Solve the system * * ( f1 ) ( U'0 0 )-1 ( f ) ( U'0 0 ) ( f1 ) ( f ) * ( ) = ( ) ( ) => ( ) ( ) = ( ) * ( g1 ) ( R' C') ( g ) ( R' C') ( g1 ) ( g ) * * from which it follows that: * * { U'0 * f1 = f f1 = inv(U'0) * f * { => * { R' * f1 + C' * g1 = g g1 = inv(C') * (g - R' * f1) * * 3. Solve the system * * ( f2 ) ( L'0 S')-1 ( f1 ) ( L'0 S') ( f2 ) ( f1 ) * ( ) = ( ) ( ) => ( ) ( ) = ( ) * ( g2 ) ( 0 I ) ( g1 ) ( 0 I ) ( g2 ) ( g1 ) * * from which it follows that: * * { L'0 * f2 + S' * g2 = f1 * { => f2 = inv(L'0) * ( f1 - S' * g2) * { g2 = g1 * * 4. Compute * * ( x ) ( f2 ) * ( ) = P ( ) * ( y ) ( g2 ) */ void lpf_btran(LPF *lpf, double x[]) { int m0 = lpf->m0; int m = lpf->m; int n = lpf->n; int *P_row = lpf->P_row; int *Q_row = lpf->Q_row; double *fg = lpf->work1; double *f = fg; double *g = fg + m0; int i, ii; #if _GLPLPF_DEBUG double *b; #endif if (!lpf->valid) xfault("lpf_btran: the factorization is not valid\n"); xassert(0 <= m && m <= m0 + n); #if _GLPLPF_DEBUG /* save the right-hand side vector */ b = xcalloc(1+m, sizeof(double)); for (i = 1; i <= m; i++) b[i] = x[i]; #endif /* (f g) := Q * (b 0) */ for (i = 1; i <= m0 + n; i++) fg[i] = ((ii = Q_row[i]) <= m ? x[ii] : 0.0); /* f1 := inv(U'0) * f */ luf_v_solve(lpf->luf, 1, f); /* g1 := inv(C') * (g - R' * f1) */ rt_prod(lpf, g, -1.0, f); scf_solve_it(lpf->scf, 1, g); /* g2 := g1 */ g = g; /* f2 := inv(L'0) * (f1 - S' * g2) */ st_prod(lpf, f, -1.0, g); luf_f_solve(lpf->luf, 1, f); /* (x y) := P * (f2 g2) */ for (i = 1; i <= m; i++) x[i] = fg[P_row[i]]; #if _GLPLPF_DEBUG /* check relative error in solution */ check_error(lpf, 1, x, b); xfree(b); #endif return; } /*********************************************************************** * The routine enlarge_sva enlarges the Sparse Vector Area to new_size * locations by reallocating the arrays v_ind and v_val. */ static void enlarge_sva(LPF *lpf, int new_size) { int v_size = lpf->v_size; int used = lpf->v_ptr - 1; int *v_ind = lpf->v_ind; double *v_val = lpf->v_val; xassert(v_size < new_size); while (v_size < new_size) v_size += v_size; lpf->v_size = v_size; lpf->v_ind = xcalloc(1+v_size, sizeof(int)); lpf->v_val = xcalloc(1+v_size, sizeof(double)); xassert(used >= 0); memcpy(&lpf->v_ind[1], &v_ind[1], used * sizeof(int)); memcpy(&lpf->v_val[1], &v_val[1], used * sizeof(double)); xfree(v_ind); xfree(v_val); return; } /*********************************************************************** * NAME * * lpf_update_it - update LP basis factorization * * SYNOPSIS * * #include "glplpf.h" * int lpf_update_it(LPF *lpf, int j, int bh, int len, const int ind[], * const double val[]); * * DESCRIPTION * * The routine lpf_update_it updates the factorization of the basis * matrix B after replacing its j-th column by a new vector. * * The parameter j specifies the number of column of B, which has been * replaced, 1 <= j <= m, where m is the order of B. * * The parameter bh specifies the basis header entry for the new column * of B, which is the number of the new column in some original matrix. * This parameter is optional and can be specified as 0. * * Row indices and numerical values of non-zero elements of the new * column of B should be placed in locations ind[1], ..., ind[len] and * val[1], ..., val[len], resp., where len is the number of non-zeros * in the column. Neither zero nor duplicate elements are allowed. * * RETURNS * * 0 The factorization has been successfully updated. * * LPF_ESING * New basis B is singular within the working precision. * * LPF_ELIMIT * Maximal number of additional rows and columns has been reached. * * BACKGROUND * * Let j-th column of the current basis matrix B have to be replaced by * a new column a. This replacement is equivalent to removing the old * j-th column by fixing it at zero and introducing the new column as * follows: * * ( B F^| a ) * ( B F^) ( | ) * ( ) ---> ( G^ H^| 0 ) * ( G^ H^) (-------+---) * ( e'j 0 | 0 ) * * where ej is a unit vector with 1 in j-th position which used to fix * the old j-th column of B (at zero). Then using the main equality we * have: * * ( B F^| a ) ( B0 F | f ) * ( | ) ( P 0 ) ( | ) ( Q 0 ) * ( G^ H^| 0 ) = ( ) ( G H | g ) ( ) = * (-------+---) ( 0 1 ) (-------+---) ( 0 1 ) * ( e'j 0 | 0 ) ( v' w'| 0 ) * * [ ( B0 F )| ( f ) ] [ ( B0 F ) | ( f ) ] * [ P ( )| P ( ) ] ( Q 0 ) [ P ( ) Q| P ( ) ] * = [ ( G H )| ( g ) ] ( ) = [ ( G H ) | ( g ) ] * [------------+-------- ] ( 0 1 ) [-------------+---------] * [ ( v' w')| 0 ] [ ( v' w') Q| 0 ] * * where: * * ( a ) ( f ) ( f ) ( a ) * ( ) = P ( ) => ( ) = P' * ( ) * ( 0 ) ( g ) ( g ) ( 0 ) * * ( ej ) ( v ) ( v ) ( ej ) * ( e'j 0 ) = ( v' w' ) Q => ( ) = Q' ( ) => ( ) = Q ( ) * ( 0 ) ( w ) ( w ) ( 0 ) * * On the other hand: * * ( B0| F f ) * ( P 0 ) (---+------) ( Q 0 ) ( B0 new F ) * ( ) ( G | H g ) ( ) = new P ( ) new Q * ( 0 1 ) ( | ) ( 0 1 ) ( new G new H ) * ( v'| w' 0 ) * * where: * ( G ) ( H g ) * new F = ( F f ), new G = ( ), new H = ( ), * ( v') ( w' 0 ) * * ( P 0 ) ( Q 0 ) * new P = ( ) , new Q = ( ) . * ( 0 1 ) ( 0 1 ) * * The factorization structure for the new augmented matrix remains the * same, therefore: * * ( B0 new F ) ( L0 0 ) ( U0 new R ) * new P ( ) new Q = ( ) ( ) * ( new G new H ) ( new S I ) ( 0 new C ) * * where: * * new F = L0 * new R => * * new R = inv(L0) * new F = inv(L0) * (F f) = ( R inv(L0)*f ) * * new G = new S * U0 => * * ( G ) ( S ) * new S = new G * inv(U0) = ( ) * inv(U0) = ( ) * ( v') ( v'*inv(U0) ) * * new H = new S * new R + new C => * * new C = new H - new S * new R = * * ( H g ) ( S ) * = ( ) - ( ) * ( R inv(L0)*f ) = * ( w' 0 ) ( v'*inv(U0) ) * * ( H - S*R g - S*inv(L0)*f ) ( C x ) * = ( ) = ( ) * ( w'- v'*inv(U0)*R -v'*inv(U0)*inv(L0)*f) ( y' z ) * * Note that new C is resulted by expanding old C with new column x, * row y', and diagonal element z, where: * * x = g - S * inv(L0) * f = g - S * (new column of R) * * y = w - R'* inv(U'0)* v = w - R'* (new row of S) * * z = - (new row of S) * (new column of R) * * Finally, to replace old B by new B we have to permute j-th and last * (just added) columns of the matrix * * ( B F^| a ) * ( | ) * ( G^ H^| 0 ) * (-------+---) * ( e'j 0 | 0 ) * * and to keep the main equality do the same for matrix Q. */ int lpf_update_it(LPF *lpf, int j, int bh, int len, const int ind[], const double val[]) { int m0 = lpf->m0; int m = lpf->m; #if _GLPLPF_DEBUG double *B = lpf->B; #endif int n = lpf->n; int *R_ptr = lpf->R_ptr; int *R_len = lpf->R_len; int *S_ptr = lpf->S_ptr; int *S_len = lpf->S_len; int *P_row = lpf->P_row; int *P_col = lpf->P_col; int *Q_row = lpf->Q_row; int *Q_col = lpf->Q_col; int v_ptr = lpf->v_ptr; int *v_ind = lpf->v_ind; double *v_val = lpf->v_val; double *a = lpf->work2; /* new column */ double *fg = lpf->work1, *f = fg, *g = fg + m0; double *vw = lpf->work2, *v = vw, *w = vw + m0; double *x = g, *y = w, z; int i, ii, k, ret; xassert(bh == bh); if (!lpf->valid) xfault("lpf_update_it: the factorization is not valid\n"); if (!(1 <= j && j <= m)) xfault("lpf_update_it: j = %d; column number out of range\n", j); xassert(0 <= m && m <= m0 + n); /* check if the basis factorization can be expanded */ if (n == lpf->n_max) { lpf->valid = 0; ret = LPF_ELIMIT; goto done; } /* convert new j-th column of B to dense format */ for (i = 1; i <= m; i++) a[i] = 0.0; for (k = 1; k <= len; k++) { i = ind[k]; if (!(1 <= i && i <= m)) xfault("lpf_update_it: ind[%d] = %d; row number out of rang" "e\n", k, i); if (a[i] != 0.0) xfault("lpf_update_it: ind[%d] = %d; duplicate row index no" "t allowed\n", k, i); if (val[k] == 0.0) xfault("lpf_update_it: val[%d] = %g; zero element not allow" "ed\n", k, val[k]); a[i] = val[k]; } #if _GLPLPF_DEBUG /* change column in the basis matrix for debugging */ for (i = 1; i <= m; i++) B[(i - 1) * m + j] = a[i]; #endif /* (f g) := inv(P) * (a 0) */ for (i = 1; i <= m0+n; i++) fg[i] = ((ii = P_col[i]) <= m ? a[ii] : 0.0); /* (v w) := Q * (ej 0) */ for (i = 1; i <= m0+n; i++) vw[i] = 0.0; vw[Q_col[j]] = 1.0; /* f1 := inv(L0) * f (new column of R) */ luf_f_solve(lpf->luf, 0, f); /* v1 := inv(U'0) * v (new row of S) */ luf_v_solve(lpf->luf, 1, v); /* we need at most 2 * m0 available locations in the SVA to store new column of matrix R and new row of matrix S */ if (lpf->v_size < v_ptr + m0 + m0) { enlarge_sva(lpf, v_ptr + m0 + m0); v_ind = lpf->v_ind; v_val = lpf->v_val; } /* store new column of R */ R_ptr[n+1] = v_ptr; for (i = 1; i <= m0; i++) { if (f[i] != 0.0) v_ind[v_ptr] = i, v_val[v_ptr] = f[i], v_ptr++; } R_len[n+1] = v_ptr - lpf->v_ptr; lpf->v_ptr = v_ptr; /* store new row of S */ S_ptr[n+1] = v_ptr; for (i = 1; i <= m0; i++) { if (v[i] != 0.0) v_ind[v_ptr] = i, v_val[v_ptr] = v[i], v_ptr++; } S_len[n+1] = v_ptr - lpf->v_ptr; lpf->v_ptr = v_ptr; /* x := g - S * f1 (new column of C) */ s_prod(lpf, x, -1.0, f); /* y := w - R' * v1 (new row of C) */ rt_prod(lpf, y, -1.0, v); /* z := - v1 * f1 (new diagonal element of C) */ z = 0.0; for (i = 1; i <= m0; i++) z -= v[i] * f[i]; /* update factorization of new matrix C */ switch (scf_update_exp(lpf->scf, x, y, z)) { case 0: break; case SCF_ESING: lpf->valid = 0; ret = LPF_ESING; goto done; case SCF_ELIMIT: xassert(lpf != lpf); default: xassert(lpf != lpf); } /* expand matrix P */ P_row[m0+n+1] = P_col[m0+n+1] = m0+n+1; /* expand matrix Q */ Q_row[m0+n+1] = Q_col[m0+n+1] = m0+n+1; /* permute j-th and last (just added) column of matrix Q */ i = Q_col[j], ii = Q_col[m0+n+1]; Q_row[i] = m0+n+1, Q_col[m0+n+1] = i; Q_row[ii] = j, Q_col[j] = ii; /* increase the number of additional rows and columns */ lpf->n++; xassert(lpf->n <= lpf->n_max); /* the factorization has been successfully updated */ ret = 0; done: /* return to the calling program */ return ret; } /*********************************************************************** * NAME * * lpf_delete_it - delete LP basis factorization * * SYNOPSIS * * #include "glplpf.h" * void lpf_delete_it(LPF *lpf) * * DESCRIPTION * * The routine lpf_delete_it deletes LP basis factorization specified * by the parameter lpf and frees all memory allocated to this program * object. */ void lpf_delete_it(LPF *lpf) { luf_delete_it(lpf->luf); #if _GLPLPF_DEBUG if (lpf->B != NULL) xfree(lpf->B); #else xassert(lpf->B == NULL); #endif if (lpf->R_ptr != NULL) xfree(lpf->R_ptr); if (lpf->R_len != NULL) xfree(lpf->R_len); if (lpf->S_ptr != NULL) xfree(lpf->S_ptr); if (lpf->S_len != NULL) xfree(lpf->S_len); if (lpf->scf != NULL) scf_delete_it(lpf->scf); if (lpf->P_row != NULL) xfree(lpf->P_row); if (lpf->P_col != NULL) xfree(lpf->P_col); if (lpf->Q_row != NULL) xfree(lpf->Q_row); if (lpf->Q_col != NULL) xfree(lpf->Q_col); if (lpf->v_ind != NULL) xfree(lpf->v_ind); if (lpf->v_val != NULL) xfree(lpf->v_val); if (lpf->work1 != NULL) xfree(lpf->work1); if (lpf->work2 != NULL) xfree(lpf->work2); xfree(lpf); return; } /* eof */ sources_5316/external/glpk/glpspx.h0000644000176700017670000000265411401660400016167 0ustar paulpaul/* glpspx.h (core simplex solvers) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPSPX_H #define GLPSPX_H #include "glpapi.h" #define spx_primal _glp_spx_primal int spx_primal(glp_prob *lp, const glp_smcp *parm); /* core LP solver based on the primal simplex method */ #define spx_dual _glp_spx_dual int spx_dual(glp_prob *lp, const glp_smcp *parm); /* core LP solver based on the dual simplex method */ #endif /* eof */ sources_5316/external/glpk/amd_1.c0000644000176700017670000001504311401660400015622 0ustar paulpaul/* ========================================================================= */ /* === AMD_1 =============================================================== */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* AMD_1: Construct A+A' for a sparse matrix A and perform the AMD ordering. * * The n-by-n sparse matrix A can be unsymmetric. It is stored in MATLAB-style * compressed-column form, with sorted row indices in each column, and no * duplicate entries. Diagonal entries may be present, but they are ignored. * Row indices of column j of A are stored in Ai [Ap [j] ... Ap [j+1]-1]. * Ap [0] must be zero, and nz = Ap [n] is the number of entries in A. The * size of the matrix, n, must be greater than or equal to zero. * * This routine must be preceded by a call to AMD_aat, which computes the * number of entries in each row/column in A+A', excluding the diagonal. * Len [j], on input, is the number of entries in row/column j of A+A'. This * routine constructs the matrix A+A' and then calls AMD_2. No error checking * is performed (this was done in AMD_valid). */ #include "amd_internal.h" GLOBAL void AMD_1 ( Int n, /* n > 0 */ const Int Ap [ ], /* input of size n+1, not modified */ const Int Ai [ ], /* input of size nz = Ap [n], not modified */ Int P [ ], /* size n output permutation */ Int Pinv [ ], /* size n output inverse permutation */ Int Len [ ], /* size n input, undefined on output */ Int slen, /* slen >= sum (Len [0..n-1]) + 7n, * ideally slen = 1.2 * sum (Len) + 8n */ Int S [ ], /* size slen workspace */ double Control [ ], /* input array of size AMD_CONTROL */ double Info [ ] /* output array of size AMD_INFO */ ) { Int i, j, k, p, pfree, iwlen, pj, p1, p2, pj2, *Iw, *Pe, *Nv, *Head, *Elen, *Degree, *s, *W, *Sp, *Tp ; /* --------------------------------------------------------------------- */ /* construct the matrix for AMD_2 */ /* --------------------------------------------------------------------- */ ASSERT (n > 0) ; iwlen = slen - 6*n ; s = S ; Pe = s ; s += n ; Nv = s ; s += n ; Head = s ; s += n ; Elen = s ; s += n ; Degree = s ; s += n ; W = s ; s += n ; Iw = s ; s += iwlen ; ASSERT (AMD_valid (n, n, Ap, Ai) == AMD_OK) ; /* construct the pointers for A+A' */ Sp = Nv ; /* use Nv and W as workspace for Sp and Tp [ */ Tp = W ; pfree = 0 ; for (j = 0 ; j < n ; j++) { Pe [j] = pfree ; Sp [j] = pfree ; pfree += Len [j] ; } /* Note that this restriction on iwlen is slightly more restrictive than * what is strictly required in AMD_2. AMD_2 can operate with no elbow * room at all, but it will be very slow. For better performance, at * least size-n elbow room is enforced. */ ASSERT (iwlen >= pfree + n) ; #ifndef NDEBUG for (p = 0 ; p < iwlen ; p++) Iw [p] = EMPTY ; #endif for (k = 0 ; k < n ; k++) { AMD_DEBUG1 (("Construct row/column k= "ID" of A+A'\n", k)) ; p1 = Ap [k] ; p2 = Ap [k+1] ; /* construct A+A' */ for (p = p1 ; p < p2 ; ) { /* scan the upper triangular part of A */ j = Ai [p] ; ASSERT (j >= 0 && j < n) ; if (j < k) { /* entry A (j,k) in the strictly upper triangular part */ ASSERT (Sp [j] < (j == n-1 ? pfree : Pe [j+1])) ; ASSERT (Sp [k] < (k == n-1 ? pfree : Pe [k+1])) ; Iw [Sp [j]++] = k ; Iw [Sp [k]++] = j ; p++ ; } else if (j == k) { /* skip the diagonal */ p++ ; break ; } else /* j > k */ { /* first entry below the diagonal */ break ; } /* scan lower triangular part of A, in column j until reaching * row k. Start where last scan left off. */ ASSERT (Ap [j] <= Tp [j] && Tp [j] <= Ap [j+1]) ; pj2 = Ap [j+1] ; for (pj = Tp [j] ; pj < pj2 ; ) { i = Ai [pj] ; ASSERT (i >= 0 && i < n) ; if (i < k) { /* A (i,j) is only in the lower part, not in upper */ ASSERT (Sp [i] < (i == n-1 ? pfree : Pe [i+1])) ; ASSERT (Sp [j] < (j == n-1 ? pfree : Pe [j+1])) ; Iw [Sp [i]++] = j ; Iw [Sp [j]++] = i ; pj++ ; } else if (i == k) { /* entry A (k,j) in lower part and A (j,k) in upper */ pj++ ; break ; } else /* i > k */ { /* consider this entry later, when k advances to i */ break ; } } Tp [j] = pj ; } Tp [k] = p ; } /* clean up, for remaining mismatched entries */ for (j = 0 ; j < n ; j++) { for (pj = Tp [j] ; pj < Ap [j+1] ; pj++) { i = Ai [pj] ; ASSERT (i >= 0 && i < n) ; /* A (i,j) is only in the lower part, not in upper */ ASSERT (Sp [i] < (i == n-1 ? pfree : Pe [i+1])) ; ASSERT (Sp [j] < (j == n-1 ? pfree : Pe [j+1])) ; Iw [Sp [i]++] = j ; Iw [Sp [j]++] = i ; } } #ifndef NDEBUG for (j = 0 ; j < n-1 ; j++) ASSERT (Sp [j] == Pe [j+1]) ; ASSERT (Sp [n-1] == pfree) ; #endif /* Tp and Sp no longer needed ] */ /* --------------------------------------------------------------------- */ /* order the matrix */ /* --------------------------------------------------------------------- */ AMD_2 (n, Pe, Iw, Len, iwlen, pfree, Nv, Pinv, P, Head, Elen, Degree, W, Control, Info) ; } sources_5316/external/glpk/glpenv.h0000644000176700017670000001551011401660400016140 0ustar paulpaul/* glpenv.h (GLPK environment) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPENV_H #define GLPENV_H #include "glpstd.h" #include "glplib.h" typedef struct ENV ENV; typedef struct MEM MEM; typedef struct XFILE XFILE; #define ENV_MAGIC 0x454E5631 /* environment block magic value */ #define TERM_BUF_SIZE 4096 /* terminal output buffer size, in bytes */ #define IOERR_MSG_SIZE 1024 /* i/o error message buffer size, in bytes */ #define MEM_MAGIC 0x4D454D31 /* memory block descriptor magic value */ struct ENV { /* environment block */ int magic; /* magic value used for debugging */ char version[7+1]; /* version string returned by the routine glp_version */ /*--------------------------------------------------------------*/ /* terminal output */ char *term_buf; /* char term_buf[TERM_BUF_SIZE]; */ /* terminal output buffer */ int term_out; /* flag to enable/disable terminal output */ int (*term_hook)(void *info, const char *s); /* user-defined routine to intercept terminal output */ void *term_info; /* transit pointer (cookie) passed to the routine term_hook */ FILE *tee_file; /* output stream used to copy terminal output */ /*--------------------------------------------------------------*/ /* error handling */ const char *err_file; /* value of the __FILE__ macro passed to glp_error */ int err_line; /* value of the __LINE__ macro passed to glp_error */ void (*err_hook)(void *info); /* user-defined routine to intercept abnormal termination */ void *err_info; /* transit pointer (cookie) passed to the routine err_hook */ /*--------------------------------------------------------------*/ /* memory allocation */ glp_long mem_limit; /* maximal amount of memory (in bytes) available for dynamic allocation */ MEM *mem_ptr; /* pointer to the linked list of allocated memory blocks */ int mem_count; /* total number of currently allocated memory blocks */ int mem_cpeak; /* peak value of mem_count */ glp_long mem_total; /* total amount of currently allocated memory (in bytes; is the sum of the size field over all memory block descriptors) */ glp_long mem_tpeak; /* peak value of mem_total */ /*--------------------------------------------------------------*/ /* stream input/output */ XFILE *file_ptr; /* pointer to the linked list of active stream descriptors */ char *ioerr_msg; /* char ioerr_msg[IOERR_MSG_SIZE]; */ /* input/output error message buffer */ /*--------------------------------------------------------------*/ /* shared libraries support */ void *h_odbc; /* handle to ODBC shared library */ void *h_mysql; /* handle to MySQL shared library */ }; struct MEM { /* memory block descriptor */ int flag; /* descriptor flag */ int size; /* size of block (in bytes, including descriptor) */ MEM *prev; /* pointer to previous memory block descriptor */ MEM *next; /* pointer to next memory block descriptor */ }; struct XFILE { /* input/output stream descriptor */ int type; /* stream handle type: */ #define FH_FILE 0x11 /* FILE */ #define FH_ZLIB 0x22 /* gzFile */ void *fh; /* pointer to stream handle */ XFILE *prev; /* pointer to previous stream descriptor */ XFILE *next; /* pointer to next stream descriptor */ }; #define XEOF (-1) #define get_env_ptr _glp_get_env_ptr ENV *get_env_ptr(void); /* retrieve pointer to environment block */ #define tls_set_ptr _glp_tls_set_ptr void tls_set_ptr(void *ptr); /* store global pointer in TLS */ #define tls_get_ptr _glp_tls_get_ptr void *tls_get_ptr(void); /* retrieve global pointer from TLS */ #define xprintf glp_printf void glp_printf(const char *fmt, ...); /* write formatted output to the terminal */ #define xvprintf glp_vprintf void glp_vprintf(const char *fmt, va_list arg); /* write formatted output to the terminal */ #ifndef GLP_ERROR_DEFINED #define GLP_ERROR_DEFINED typedef void (*_glp_error)(const char *fmt, ...); #endif #define xerror glp_error_(__FILE__, __LINE__) _glp_error glp_error_(const char *file, int line); /* display error message and terminate execution */ #define xassert(expr) \ ((void)((expr) || (glp_assert_(#expr, __FILE__, __LINE__), 1))) void glp_assert_(const char *expr, const char *file, int line); /* check for logical condition */ #define xmalloc glp_malloc void *glp_malloc(int size); /* allocate memory block */ #define xcalloc glp_calloc void *glp_calloc(int n, int size); /* allocate memory block */ #define xfree glp_free void glp_free(void *ptr); /* free memory block */ #define xtime glp_time glp_long glp_time(void); /* determine current universal time */ #define xdifftime glp_difftime double glp_difftime(glp_long t1, glp_long t0); /* compute difference between two time values, in seconds */ #define lib_err_msg _glp_lib_err_msg void lib_err_msg(const char *msg); #define xerrmsg _glp_lib_xerrmsg const char *xerrmsg(void); #define xfopen _glp_lib_xfopen XFILE *xfopen(const char *fname, const char *mode); #define xferror _glp_lib_xferror int xferror(XFILE *file); #define xfeof _glp_lib_xfeof int xfeof(XFILE *file); #define xfgetc _glp_lib_xfgetc int xfgetc(XFILE *file); #define xfputc _glp_lib_xfputc int xfputc(int c, XFILE *file); #define xfflush _glp_lib_xfflush int xfflush(XFILE *fp); #define xfclose _glp_lib_xfclose int xfclose(XFILE *file); #define xfprintf _glp_lib_xfprintf int xfprintf(XFILE *file, const char *fmt, ...); #define xdlopen _glp_xdlopen void *xdlopen(const char *module); #define xdlsym _glp_xdlsym void *xdlsym(void *h, const char *symbol); #define xdlclose _glp_xdlclose void xdlclose(void *h); #endif /* eof */ sources_5316/external/glpk/glpbfx.h0000644000176700017670000000455511401660400016136 0ustar paulpaul/* glpbfx.h (basis factorization interface, bignum arithmetic) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPBFX_H #define GLPBFX_H #include "glpgmp.h" #ifndef GLPBFX_DEFINED #define GLPBFX_DEFINED typedef struct { double _opaque_bfx; } BFX; #endif #define bfx_create_binv _glp_bfx_create_binv #define bfx_is_valid _glp_bfx_is_valid #define bfx_invalidate _glp_bfx_invalidate #define bfx_factorize _glp_bfx_factorize #define bfx_ftran _glp_bfx_ftran #define bfx_btran _glp_bfx_btran #define bfx_update _glp_bfx_update #define bfx_delete_binv _glp_bfx_delete_binv BFX *bfx_create_binv(void); /* create factorization of the basis matrix */ int bfx_is_valid(BFX *binv); /* check if factorization is valid */ void bfx_invalidate(BFX *binv); /* invalidate factorization of the basis matrix */ int bfx_factorize(BFX *binv, int m, int (*col)(void *info, int j, int ind[], mpq_t val[]), void *info); /* compute factorization of the basis matrix */ void bfx_ftran(BFX *binv, mpq_t x[], int save); /* perform forward transformation (FTRAN) */ void bfx_btran(BFX *binv, mpq_t x[]); /* perform backward transformation (BTRAN) */ int bfx_update(BFX *binv, int j); /* update factorization of the basis matrix */ void bfx_delete_binv(BFX *binv); /* delete factorization of the basis matrix */ #endif /* eof */ sources_5316/external/glpk/colamd.h0000644000176700017670000000411411401660400016102 0ustar paulpaul/* colamd.h */ /* Written by Andrew Makhorin . */ #ifndef COLAMD_H #define COLAMD_H #define _GLPSTD_STDIO #include "glpenv.h" #define COLAMD_DATE "Nov 1, 2007" #define COLAMD_VERSION_CODE(main, sub) ((main) * 1000 + (sub)) #define COLAMD_MAIN_VERSION 2 #define COLAMD_SUB_VERSION 7 #define COLAMD_SUBSUB_VERSION 1 #define COLAMD_VERSION \ COLAMD_VERSION_CODE(COLAMD_MAIN_VERSION, COLAMD_SUB_VERSION) #define COLAMD_KNOBS 20 #define COLAMD_STATS 20 #define COLAMD_DENSE_ROW 0 #define COLAMD_DENSE_COL 1 #define COLAMD_AGGRESSIVE 2 #define COLAMD_DEFRAG_COUNT 2 #define COLAMD_STATUS 3 #define COLAMD_INFO1 4 #define COLAMD_INFO2 5 #define COLAMD_INFO3 6 #define COLAMD_OK (0) #define COLAMD_OK_BUT_JUMBLED (1) #define COLAMD_ERROR_A_not_present (-1) #define COLAMD_ERROR_p_not_present (-2) #define COLAMD_ERROR_nrow_negative (-3) #define COLAMD_ERROR_ncol_negative (-4) #define COLAMD_ERROR_nnz_negative (-5) #define COLAMD_ERROR_p0_nonzero (-6) #define COLAMD_ERROR_A_too_small (-7) #define COLAMD_ERROR_col_length_negative (-8) #define COLAMD_ERROR_row_index_out_of_bounds (-9) #define COLAMD_ERROR_out_of_memory (-10) #define COLAMD_ERROR_internal_error (-999) #define colamd_recommended _glp_colamd_recommended size_t colamd_recommended(int nnz, int n_row, int n_col); #define colamd_set_defaults _glp_colamd_set_defaults void colamd_set_defaults(double knobs [COLAMD_KNOBS]); #define colamd _glp_colamd int colamd(int n_row, int n_col, int Alen, int A[], int p[], double knobs[COLAMD_KNOBS], int stats[COLAMD_STATS]); #define symamd _glp_symamd int symamd(int n, int A[], int p[], int perm[], double knobs[COLAMD_KNOBS], int stats[COLAMD_STATS], void *(*allocate)(size_t, size_t), void(*release)(void *)); #define colamd_report _glp_colamd_report void colamd_report(int stats[COLAMD_STATS]); #define symamd_report _glp_symamd_report void symamd_report(int stats[COLAMD_STATS]); #define colamd_printf xprintf #endif /* eof */ sources_5316/external/glpk/glpnpp05.c0000644000176700017670000006377511401660400016325 0ustar paulpaul/* glpnpp05.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpnpp.h" /*********************************************************************** * NAME * * npp_clean_prob - perform initial LP/MIP processing * * SYNOPSIS * * #include "glpnpp.h" * void npp_clean_prob(NPP *npp); * * DESCRIPTION * * The routine npp_clean_prob performs initial LP/MIP processing that * currently includes: * * 1) removing free rows; * * 2) replacing double-sided constraint rows with almost identical * bounds, by equality constraint rows; * * 3) removing fixed columns; * * 4) replacing double-bounded columns with almost identical bounds by * fixed columns and removing those columns; * * 5) initial processing constraint coefficients (not implemented); * * 6) initial processing objective coefficients (not implemented). */ void npp_clean_prob(NPP *npp) { /* perform initial LP/MIP processing */ NPPROW *row, *next_row; NPPCOL *col, *next_col; int ret; xassert(npp == npp); /* process rows which originally are free */ for (row = npp->r_head; row != NULL; row = next_row) { next_row = row->next; if (row->lb == -DBL_MAX && row->ub == +DBL_MAX) { /* process free row */ #ifdef GLP_DEBUG xprintf("1"); #endif npp_free_row(npp, row); /* row was deleted */ } } /* process rows which originally are double-sided inequalities */ for (row = npp->r_head; row != NULL; row = next_row) { next_row = row->next; if (row->lb != -DBL_MAX && row->ub != +DBL_MAX && row->lb < row->ub) { ret = npp_make_equality(npp, row); if (ret == 0) ; else if (ret == 1) { /* row was replaced by equality constraint */ #ifdef GLP_DEBUG xprintf("2"); #endif } else xassert(ret != ret); } } /* process columns which are originally fixed */ for (col = npp->c_head; col != NULL; col = next_col) { next_col = col->next; if (col->lb == col->ub) { /* process fixed column */ #ifdef GLP_DEBUG xprintf("3"); #endif npp_fixed_col(npp, col); /* column was deleted */ } } /* process columns which are originally double-bounded */ for (col = npp->c_head; col != NULL; col = next_col) { next_col = col->next; if (col->lb != -DBL_MAX && col->ub != +DBL_MAX && col->lb < col->ub) { ret = npp_make_fixed(npp, col); if (ret == 0) ; else if (ret == 1) { /* column was replaced by fixed column; process it */ #ifdef GLP_DEBUG xprintf("4"); #endif npp_fixed_col(npp, col); /* column was deleted */ } } } return; } /*********************************************************************** * NAME * * npp_process_row - perform basic row processing * * SYNOPSIS * * #include "glpnpp.h" * int npp_process_row(NPP *npp, NPPROW *row, int hard); * * DESCRIPTION * * The routine npp_process_row performs basic row processing that * currently includes: * * 1) removing empty row; * * 2) removing equality constraint row singleton and corresponding * column; * * 3) removing inequality constraint row singleton and corresponding * column if it was fixed; * * 4) performing general row analysis; * * 5) removing redundant row bounds; * * 6) removing forcing row and corresponding columns; * * 7) removing row which becomes free due to redundant bounds; * * 8) computing implied bounds for all columns in the row and using * them to strengthen current column bounds (MIP only, optional, * performed if the flag hard is on). * * Additionally the routine may activate affected rows and/or columns * for further processing. * * RETURNS * * 0 success; * * GLP_ENOPFS primal/integer infeasibility detected; * * GLP_ENODFS dual infeasibility detected. */ int npp_process_row(NPP *npp, NPPROW *row, int hard) { /* perform basic row processing */ NPPCOL *col; NPPAIJ *aij, *next_aij, *aaa; int ret; /* row must not be free */ xassert(!(row->lb == -DBL_MAX && row->ub == +DBL_MAX)); /* start processing row */ if (row->ptr == NULL) { /* empty row */ ret = npp_empty_row(npp, row); if (ret == 0) { /* row was deleted */ #ifdef GLP_DEBUG xprintf("A"); #endif return 0; } else if (ret == 1) { /* primal infeasibility */ return GLP_ENOPFS; } else xassert(ret != ret); } if (row->ptr->r_next == NULL) { /* row singleton */ col = row->ptr->col; if (row->lb == row->ub) { /* equality constraint */ ret = npp_eq_singlet(npp, row); if (ret == 0) { /* column was fixed, row was deleted */ #ifdef GLP_DEBUG xprintf("B"); #endif /* activate rows affected by column */ for (aij = col->ptr; aij != NULL; aij = aij->c_next) npp_activate_row(npp, aij->row); /* process fixed column */ npp_fixed_col(npp, col); /* column was deleted */ return 0; } else if (ret == 1 || ret == 2) { /* primal/integer infeasibility */ return GLP_ENOPFS; } else xassert(ret != ret); } else { /* inequality constraint */ ret = npp_ineq_singlet(npp, row); if (0 <= ret && ret <= 3) { /* row was deleted */ #ifdef GLP_DEBUG xprintf("C"); #endif /* activate column, since its length was changed due to row deletion */ npp_activate_col(npp, col); if (ret >= 2) { /* column bounds changed significantly or column was fixed */ /* activate rows affected by column */ for (aij = col->ptr; aij != NULL; aij = aij->c_next) npp_activate_row(npp, aij->row); } if (ret == 3) { /* column was fixed; process it */ #ifdef GLP_DEBUG xprintf("D"); #endif npp_fixed_col(npp, col); /* column was deleted */ } return 0; } else if (ret == 4) { /* primal infeasibility */ return GLP_ENOPFS; } else xassert(ret != ret); } } #if 0 /* sometimes this causes too large round-off errors; probably pivot coefficient should be chosen more carefully */ if (row->ptr->r_next->r_next == NULL) { /* row doubleton */ if (row->lb == row->ub) { /* equality constraint */ if (!(row->ptr->col->is_int || row->ptr->r_next->col->is_int)) { /* both columns are continuous */ NPPCOL *q; q = npp_eq_doublet(npp, row); if (q != NULL) { /* column q was eliminated */ #ifdef GLP_DEBUG xprintf("E"); #endif /* now column q is singleton of type "implied slack variable"; we process it here to make sure that on recovering basic solution the row is always active equality constraint (as required by the routine rcv_eq_doublet) */ xassert(npp_process_col(npp, q) == 0); /* column q was deleted; note that row p also may be deleted */ return 0; } } } } #endif /* general row analysis */ ret = npp_analyze_row(npp, row); xassert(0x00 <= ret && ret <= 0xFF); if (ret == 0x33) { /* row bounds are inconsistent with column bounds */ return GLP_ENOPFS; } if ((ret & 0x0F) == 0x00) { /* row lower bound does not exist or redundant */ if (row->lb != -DBL_MAX) { /* remove redundant row lower bound */ #ifdef GLP_DEBUG xprintf("F"); #endif npp_inactive_bound(npp, row, 0); } } else if ((ret & 0x0F) == 0x01) { /* row lower bound can be active */ /* see below */ } else if ((ret & 0x0F) == 0x02) { /* row lower bound is a forcing bound */ #ifdef GLP_DEBUG xprintf("G"); #endif /* process forcing row */ if (npp_forcing_row(npp, row, 0) == 0) fixup: { /* columns were fixed, row was made free */ for (aij = row->ptr; aij != NULL; aij = next_aij) { /* process column fixed by forcing row */ #ifdef GLP_DEBUG xprintf("H"); #endif col = aij->col; next_aij = aij->r_next; /* activate rows affected by column */ for (aaa = col->ptr; aaa != NULL; aaa = aaa->c_next) npp_activate_row(npp, aaa->row); /* process fixed column */ npp_fixed_col(npp, col); /* column was deleted */ } /* process free row (which now is empty due to deletion of all its columns) */ npp_free_row(npp, row); /* row was deleted */ return 0; } } else xassert(ret != ret); if ((ret & 0xF0) == 0x00) { /* row upper bound does not exist or redundant */ if (row->ub != +DBL_MAX) { /* remove redundant row upper bound */ #ifdef GLP_DEBUG xprintf("I"); #endif npp_inactive_bound(npp, row, 1); } } else if ((ret & 0xF0) == 0x10) { /* row upper bound can be active */ /* see below */ } else if ((ret & 0xF0) == 0x20) { /* row upper bound is a forcing bound */ #ifdef GLP_DEBUG xprintf("J"); #endif /* process forcing row */ if (npp_forcing_row(npp, row, 1) == 0) goto fixup; } else xassert(ret != ret); if (row->lb == -DBL_MAX && row->ub == +DBL_MAX) { /* row became free due to redundant bounds removal */ #ifdef GLP_DEBUG xprintf("K"); #endif /* activate its columns, since their length will change due to row deletion */ for (aij = row->ptr; aij != NULL; aij = aij->r_next) npp_activate_col(npp, aij->col); /* process free row */ npp_free_row(npp, row); /* row was deleted */ return 0; } #if 1 /* 23/XII-2009 */ /* row lower and/or upper bounds can be active */ if (npp->sol == GLP_MIP && hard) { /* improve current column bounds (optional) */ if (npp_improve_bounds(npp, row, 1) < 0) return GLP_ENOPFS; } #endif return 0; } /*********************************************************************** * NAME * * npp_improve_bounds - improve current column bounds * * SYNOPSIS * * #include "glpnpp.h" * int npp_improve_bounds(NPP *npp, NPPROW *row, int flag); * * DESCRIPTION * * The routine npp_improve_bounds analyzes specified row (inequality * or equality constraint) to determine implied column bounds and then * uses these bounds to improve (strengthen) current column bounds. * * If the flag is on and current column bounds changed significantly * or the column was fixed, the routine activate rows affected by the * column for further processing. (This feature is intended to be used * in the main loop of the routine npp_process_row.) * * NOTE: This operation can be used for MIP problem only. * * RETURNS * * The routine npp_improve_bounds returns the number of significantly * changed bounds plus the number of column having been fixed due to * bound improvements. However, if the routine detects primal/integer * infeasibility, it returns a negative value. */ int npp_improve_bounds(NPP *npp, NPPROW *row, int flag) { /* improve current column bounds */ NPPCOL *col; NPPAIJ *aij, *next_aij, *aaa; int kase, ret, count = 0; double lb, ub; xassert(npp->sol == GLP_MIP); /* row must not be free */ xassert(!(row->lb == -DBL_MAX && row->ub == +DBL_MAX)); /* determine implied column bounds */ npp_implied_bounds(npp, row); /* and use these bounds to strengthen current column bounds */ for (aij = row->ptr; aij != NULL; aij = next_aij) { col = aij->col; next_aij = aij->r_next; for (kase = 0; kase <= 1; kase++) { /* save current column bounds */ lb = col->lb, ub = col->ub; if (kase == 0) { /* process implied column lower bound */ if (col->ll.ll == -DBL_MAX) continue; ret = npp_implied_lower(npp, col, col->ll.ll); } else { /* process implied column upper bound */ if (col->uu.uu == +DBL_MAX) continue; ret = npp_implied_upper(npp, col, col->uu.uu); } if (ret == 0 || ret == 1) { /* current column bounds did not change or changed, but not significantly; restore current column bounds */ col->lb = lb, col->ub = ub; } else if (ret == 2 || ret == 3) { /* current column bounds changed significantly or column was fixed */ #ifdef GLP_DEBUG xprintf("L"); #endif count++; /* activate other rows affected by column, if required */ if (flag) { for (aaa = col->ptr; aaa != NULL; aaa = aaa->c_next) { if (aaa->row != row) npp_activate_row(npp, aaa->row); } } if (ret == 3) { /* process fixed column */ #ifdef GLP_DEBUG xprintf("M"); #endif npp_fixed_col(npp, col); /* column was deleted */ break; /* for kase */ } } else if (ret == 4) { /* primal/integer infeasibility */ return -1; } else xassert(ret != ret); } } return count; } /*********************************************************************** * NAME * * npp_process_col - perform basic column processing * * SYNOPSIS * * #include "glpnpp.h" * int npp_process_col(NPP *npp, NPPCOL *col); * * DESCRIPTION * * The routine npp_process_col performs basic column processing that * currently includes: * * 1) fixing and removing empty column; * * 2) removing column singleton, which is implied slack variable, and * corresponding row if it becomes free; * * 3) removing bounds of column, which is implied free variable, and * replacing corresponding row by equality constraint. * * Additionally the routine may activate affected rows and/or columns * for further processing. * * RETURNS * * 0 success; * * GLP_ENOPFS primal/integer infeasibility detected; * * GLP_ENODFS dual infeasibility detected. */ int npp_process_col(NPP *npp, NPPCOL *col) { /* perform basic column processing */ NPPROW *row; NPPAIJ *aij; int ret; /* column must not be fixed */ xassert(col->lb < col->ub); /* start processing column */ if (col->ptr == NULL) { /* empty column */ ret = npp_empty_col(npp, col); if (ret == 0) { /* column was fixed and deleted */ #ifdef GLP_DEBUG xprintf("N"); #endif return 0; } else if (ret == 1) { /* dual infeasibility */ return GLP_ENODFS; } else xassert(ret != ret); } if (col->ptr->c_next == NULL) { /* column singleton */ row = col->ptr->row; if (row->lb == row->ub) { /* equality constraint */ if (!col->is_int) slack: { /* implied slack variable */ #ifdef GLP_DEBUG xprintf("O"); #endif npp_implied_slack(npp, col); /* column was deleted */ if (row->lb == -DBL_MAX && row->ub == +DBL_MAX) { /* row became free due to implied slack variable */ #ifdef GLP_DEBUG xprintf("P"); #endif /* activate columns affected by row */ for (aij = row->ptr; aij != NULL; aij = aij->r_next) npp_activate_col(npp, aij->col); /* process free row */ npp_free_row(npp, row); /* row was deleted */ } else { /* row became inequality constraint; activate it since its length changed due to column deletion */ npp_activate_row(npp, row); } return 0; } } else { /* inequality constraint */ if (!col->is_int) { ret = npp_implied_free(npp, col); if (ret == 0) { /* implied free variable */ #ifdef GLP_DEBUG xprintf("Q"); #endif /* column bounds were removed, row was replaced by equality constraint */ goto slack; } else if (ret == 1) { /* column is not implied free variable, because its lower and/or upper bounds can be active */ } else if (ret == 2) { /* dual infeasibility */ return GLP_ENODFS; } } } } /* column still exists */ return 0; } /*********************************************************************** * NAME * * npp_process_prob - perform basic LP/MIP processing * * SYNOPSIS * * #include "glpnpp.h" * int npp_process_prob(NPP *npp, int hard); * * DESCRIPTION * * The routine npp_process_prob performs basic LP/MIP processing that * currently includes: * * 1) initial LP/MIP processing (see the routine npp_clean_prob), * * 2) basic row processing (see the routine npp_process_row), and * * 3) basic column processing (see the routine npp_process_col). * * If the flag hard is on, the routine attempts to improve current * column bounds multiple times within the main processing loop, in * which case this feature may take a time. Otherwise, if the flag hard * is off, improving column bounds is performed only once at the end of * the main loop. (Note that this feature is used for MIP only.) * * The routine uses two sets: the set of active rows and the set of * active columns. Rows/columns are marked by a flag (the field temp in * NPPROW/NPPCOL). If the flag is non-zero, the row/column is active, * in which case it is placed in the beginning of the row/column list; * otherwise, if the flag is zero, the row/column is inactive, in which * case it is placed in the end of the row/column list. If a row/column * being currently processed may affect other rows/columns, the latters * are activated for further processing. * * RETURNS * * 0 success; * * GLP_ENOPFS primal/integer infeasibility detected; * * GLP_ENODFS dual infeasibility detected. */ int npp_process_prob(NPP *npp, int hard) { /* perform basic LP/MIP processing */ NPPROW *row; NPPCOL *col; int processing, ret; /* perform initial LP/MIP processing */ npp_clean_prob(npp); /* activate all remaining rows and columns */ for (row = npp->r_head; row != NULL; row = row->next) row->temp = 1; for (col = npp->c_head; col != NULL; col = col->next) col->temp = 1; /* main processing loop */ processing = 1; while (processing) { processing = 0; /* process all active rows */ for (;;) { row = npp->r_head; if (row == NULL || !row->temp) break; npp_deactivate_row(npp, row); ret = npp_process_row(npp, row, hard); if (ret != 0) goto done; processing = 1; } /* process all active columns */ for (;;) { col = npp->c_head; if (col == NULL || !col->temp) break; npp_deactivate_col(npp, col); ret = npp_process_col(npp, col); if (ret != 0) goto done; processing = 1; } } #if 1 /* 23/XII-2009 */ if (npp->sol == GLP_MIP && !hard) { /* improve current column bounds (optional) */ for (row = npp->r_head; row != NULL; row = row->next) { if (npp_improve_bounds(npp, row, 0) < 0) { ret = GLP_ENOPFS; goto done; } } } #endif /* all seems ok */ ret = 0; done: xassert(ret == 0 || ret == GLP_ENOPFS || ret == GLP_ENODFS); #ifdef GLP_DEBUG xprintf("\n"); #endif return ret; } /**********************************************************************/ int npp_simplex(NPP *npp, const glp_smcp *parm) { /* process LP prior to applying primal/dual simplex method */ int ret; xassert(npp->sol == GLP_SOL); xassert(parm == parm); ret = npp_process_prob(npp, 0); return ret; } /**********************************************************************/ int npp_integer(NPP *npp, const glp_iocp *parm) { /* process MIP prior to applying branch-and-bound method */ NPPROW *row, *prev_row; NPPCOL *col; NPPAIJ *aij; int count, ret; xassert(npp->sol == GLP_MIP); xassert(parm == parm); /*==============================================================*/ /* perform basic MIP processing */ ret = npp_process_prob(npp, 1); if (ret != 0) goto done; /*==============================================================*/ /* binarize problem, if required */ if (parm->binarize) npp_binarize_prob(npp); /*==============================================================*/ /* identify hidden packing inequalities */ count = 0; /* new rows will be added to the end of the row list, so we go from the end to beginning of the row list */ for (row = npp->r_tail; row != NULL; row = prev_row) { prev_row = row->prev; /* skip free row */ if (row->lb == -DBL_MAX && row->ub == +DBL_MAX) continue; /* skip equality constraint */ if (row->lb == row->ub) continue; /* skip row having less than two variables */ if (row->ptr == NULL || row->ptr->r_next == NULL) continue; /* skip row having non-binary variables */ for (aij = row->ptr; aij != NULL; aij = aij->r_next) { col = aij->col; if (!(col->is_int && col->lb == 0.0 && col->ub == 1.0)) break; } if (aij != NULL) continue; count += npp_hidden_packing(npp, row); } if (count > 0) xprintf("%d hidden packing inequaliti(es) were detected\n", count); /*==============================================================*/ /* identify hidden covering inequalities */ count = 0; /* new rows will be added to the end of the row list, so we go from the end to beginning of the row list */ for (row = npp->r_tail; row != NULL; row = prev_row) { prev_row = row->prev; /* skip free row */ if (row->lb == -DBL_MAX && row->ub == +DBL_MAX) continue; /* skip equality constraint */ if (row->lb == row->ub) continue; /* skip row having less than three variables */ if (row->ptr == NULL || row->ptr->r_next == NULL || row->ptr->r_next->r_next == NULL) continue; /* skip row having non-binary variables */ for (aij = row->ptr; aij != NULL; aij = aij->r_next) { col = aij->col; if (!(col->is_int && col->lb == 0.0 && col->ub == 1.0)) break; } if (aij != NULL) continue; count += npp_hidden_covering(npp, row); } if (count > 0) xprintf("%d hidden covering inequaliti(es) were detected\n", count); /*==============================================================*/ /* reduce inequality constraint coefficients */ count = 0; /* new rows will be added to the end of the row list, so we go from the end to beginning of the row list */ for (row = npp->r_tail; row != NULL; row = prev_row) { prev_row = row->prev; /* skip equality constraint */ if (row->lb == row->ub) continue; count += npp_reduce_ineq_coef(npp, row); } if (count > 0) xprintf("%d constraint coefficient(s) were reduced\n", count); /*==============================================================*/ #ifdef GLP_DEBUG routine(npp); #endif /*==============================================================*/ /* all seems ok */ ret = 0; done: return ret; } /* eof */ sources_5316/external/glpk/glpscf.c0000644000176700017670000004757311401660400016134 0ustar paulpaul/* glpscf.c (Schur complement factorization) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glpscf.h" #define xfault xerror #define _GLPSCF_DEBUG 0 #define eps 1e-10 /*********************************************************************** * NAME * * scf_create_it - create Schur complement factorization * * SYNOPSIS * * #include "glpscf.h" * SCF *scf_create_it(int n_max); * * DESCRIPTION * * The routine scf_create_it creates the factorization of matrix C, * which initially has no rows and columns. * * The parameter n_max specifies the maximal order of matrix C to be * factorized, 1 <= n_max <= 32767. * * RETURNS * * The routine scf_create_it returns a pointer to the structure SCF, * which defines the factorization. */ SCF *scf_create_it(int n_max) { SCF *scf; #if _GLPSCF_DEBUG xprintf("scf_create_it: warning: debug mode enabled\n"); #endif if (!(1 <= n_max && n_max <= 32767)) xfault("scf_create_it: n_max = %d; invalid parameter\n", n_max); scf = xmalloc(sizeof(SCF)); scf->n_max = n_max; scf->n = 0; scf->f = xcalloc(1 + n_max * n_max, sizeof(double)); scf->u = xcalloc(1 + n_max * (n_max + 1) / 2, sizeof(double)); scf->p = xcalloc(1 + n_max, sizeof(int)); scf->t_opt = SCF_TBG; scf->rank = 0; #if _GLPSCF_DEBUG scf->c = xcalloc(1 + n_max * n_max, sizeof(double)); #else scf->c = NULL; #endif scf->w = xcalloc(1 + n_max, sizeof(double)); return scf; } /*********************************************************************** * The routine f_loc determines location of matrix element F[i,j] in * the one-dimensional array f. */ static int f_loc(SCF *scf, int i, int j) { int n_max = scf->n_max; int n = scf->n; xassert(1 <= i && i <= n); xassert(1 <= j && j <= n); return (i - 1) * n_max + j; } /*********************************************************************** * The routine u_loc determines location of matrix element U[i,j] in * the one-dimensional array u. */ static int u_loc(SCF *scf, int i, int j) { int n_max = scf->n_max; int n = scf->n; xassert(1 <= i && i <= n); xassert(i <= j && j <= n); return (i - 1) * n_max + j - i * (i - 1) / 2; } /*********************************************************************** * The routine bg_transform applies Bartels-Golub version of gaussian * elimination to restore triangular structure of matrix U. * * On entry matrix U has the following structure: * * 1 k n * 1 * * * * * * * * * * * . * * * * * * * * * * . . * * * * * * * * * . . . * * * * * * * * k . . . . * * * * * * * . . . . . * * * * * * . . . . . . * * * * * . . . . . . . * * * * . . . . . . . . * * * n . . . . # # # # # # * * where '#' is a row spike to be eliminated. * * Elements of n-th row are passed separately in locations un[k], ..., * un[n]. On exit the content of the array un is destroyed. * * REFERENCES * * R.H.Bartels, G.H.Golub, "The Simplex Method of Linear Programming * Using LU-decomposition", Comm. ACM, 12, pp. 266-68, 1969. */ static void bg_transform(SCF *scf, int k, double un[]) { int n = scf->n; double *f = scf->f; double *u = scf->u; int j, k1, kj, kk, n1, nj; double t; xassert(1 <= k && k <= n); /* main elimination loop */ for (k = k; k < n; k++) { /* determine location of U[k,k] */ kk = u_loc(scf, k, k); /* determine location of F[k,1] */ k1 = f_loc(scf, k, 1); /* determine location of F[n,1] */ n1 = f_loc(scf, n, 1); /* if |U[k,k]| < |U[n,k]|, interchange k-th and n-th rows to provide |U[k,k]| >= |U[n,k]| */ if (fabs(u[kk]) < fabs(un[k])) { /* interchange k-th and n-th rows of matrix U */ for (j = k, kj = kk; j <= n; j++, kj++) t = u[kj], u[kj] = un[j], un[j] = t; /* interchange k-th and n-th rows of matrix F to keep the main equality F * C = U * P */ for (j = 1, kj = k1, nj = n1; j <= n; j++, kj++, nj++) t = f[kj], f[kj] = f[nj], f[nj] = t; } /* now |U[k,k]| >= |U[n,k]| */ /* if U[k,k] is too small in the magnitude, replace U[k,k] and U[n,k] by exact zero */ if (fabs(u[kk]) < eps) u[kk] = un[k] = 0.0; /* if U[n,k] is already zero, elimination is not needed */ if (un[k] == 0.0) continue; /* compute gaussian multiplier t = U[n,k] / U[k,k] */ t = un[k] / u[kk]; /* apply gaussian elimination to nullify U[n,k] */ /* (n-th row of U) := (n-th row of U) - t * (k-th row of U) */ for (j = k+1, kj = kk+1; j <= n; j++, kj++) un[j] -= t * u[kj]; /* (n-th row of F) := (n-th row of F) - t * (k-th row of F) to keep the main equality F * C = U * P */ for (j = 1, kj = k1, nj = n1; j <= n; j++, kj++, nj++) f[nj] -= t * f[kj]; } /* if U[n,n] is too small in the magnitude, replace it by exact zero */ if (fabs(un[n]) < eps) un[n] = 0.0; /* store U[n,n] in a proper location */ u[u_loc(scf, n, n)] = un[n]; return; } /*********************************************************************** * The routine givens computes the parameters of Givens plane rotation * c = cos(teta) and s = sin(teta) such that: * * ( c -s ) ( a ) ( r ) * ( ) ( ) = ( ) , * ( s c ) ( b ) ( 0 ) * * where a and b are given scalars. * * REFERENCES * * G.H.Golub, C.F.Van Loan, "Matrix Computations", 2nd ed. */ static void givens(double a, double b, double *c, double *s) { double t; if (b == 0.0) (*c) = 1.0, (*s) = 0.0; else if (fabs(a) <= fabs(b)) t = - a / b, (*s) = 1.0 / sqrt(1.0 + t * t), (*c) = (*s) * t; else t = - b / a, (*c) = 1.0 / sqrt(1.0 + t * t), (*s) = (*c) * t; return; } /*---------------------------------------------------------------------- * The routine gr_transform applies Givens plane rotations to restore * triangular structure of matrix U. * * On entry matrix U has the following structure: * * 1 k n * 1 * * * * * * * * * * * . * * * * * * * * * * . . * * * * * * * * * . . . * * * * * * * * k . . . . * * * * * * * . . . . . * * * * * * . . . . . . * * * * * . . . . . . . * * * * . . . . . . . . * * * n . . . . # # # # # # * * where '#' is a row spike to be eliminated. * * Elements of n-th row are passed separately in locations un[k], ..., * un[n]. On exit the content of the array un is destroyed. * * REFERENCES * * R.H.Bartels, G.H.Golub, "The Simplex Method of Linear Programming * Using LU-decomposition", Comm. ACM, 12, pp. 266-68, 1969. */ static void gr_transform(SCF *scf, int k, double un[]) { int n = scf->n; double *f = scf->f; double *u = scf->u; int j, k1, kj, kk, n1, nj; double c, s; xassert(1 <= k && k <= n); /* main elimination loop */ for (k = k; k < n; k++) { /* determine location of U[k,k] */ kk = u_loc(scf, k, k); /* determine location of F[k,1] */ k1 = f_loc(scf, k, 1); /* determine location of F[n,1] */ n1 = f_loc(scf, n, 1); /* if both U[k,k] and U[n,k] are too small in the magnitude, replace them by exact zero */ if (fabs(u[kk]) < eps && fabs(un[k]) < eps) u[kk] = un[k] = 0.0; /* if U[n,k] is already zero, elimination is not needed */ if (un[k] == 0.0) continue; /* compute the parameters of Givens plane rotation */ givens(u[kk], un[k], &c, &s); /* apply Givens rotation to k-th and n-th rows of matrix U */ for (j = k, kj = kk; j <= n; j++, kj++) { double ukj = u[kj], unj = un[j]; u[kj] = c * ukj - s * unj; un[j] = s * ukj + c * unj; } /* apply Givens rotation to k-th and n-th rows of matrix F to keep the main equality F * C = U * P */ for (j = 1, kj = k1, nj = n1; j <= n; j++, kj++, nj++) { double fkj = f[kj], fnj = f[nj]; f[kj] = c * fkj - s * fnj; f[nj] = s * fkj + c * fnj; } } /* if U[n,n] is too small in the magnitude, replace it by exact zero */ if (fabs(un[n]) < eps) un[n] = 0.0; /* store U[n,n] in a proper location */ u[u_loc(scf, n, n)] = un[n]; return; } /*********************************************************************** * The routine transform restores triangular structure of matrix U. * It is a driver to the routines bg_transform and gr_transform (see * comments to these routines above). */ static void transform(SCF *scf, int k, double un[]) { switch (scf->t_opt) { case SCF_TBG: bg_transform(scf, k, un); break; case SCF_TGR: gr_transform(scf, k, un); break; default: xassert(scf != scf); } return; } /*********************************************************************** * The routine estimate_rank estimates the rank of matrix C. * * Since all transformations applied to matrix F are non-singular, * and F is assumed to be well conditioned, from the main equaility * F * C = U * P it follows that rank(C) = rank(U), where rank(U) is * estimated as the number of non-zero diagonal elements of U. */ static int estimate_rank(SCF *scf) { int n_max = scf->n_max; int n = scf->n; double *u = scf->u; int i, ii, inc, rank = 0; for (i = 1, ii = u_loc(scf, i, i), inc = n_max; i <= n; i++, ii += inc, inc--) if (u[ii] != 0.0) rank++; return rank; } #if _GLPSCF_DEBUG /*********************************************************************** * The routine check_error computes the maximal relative error between * left- and right-hand sides of the main equality F * C = U * P. (This * routine is intended only for debugging.) */ static void check_error(SCF *scf, const char *func) { int n = scf->n; double *f = scf->f; double *u = scf->u; int *p = scf->p; double *c = scf->c; int i, j, k; double d, dmax = 0.0, s, t; xassert(c != NULL); for (i = 1; i <= n; i++) { for (j = 1; j <= n; j++) { /* compute element (i,j) of product F * C */ s = 0.0; for (k = 1; k <= n; k++) s += f[f_loc(scf, i, k)] * c[f_loc(scf, k, j)]; /* compute element (i,j) of product U * P */ k = p[j]; t = (i <= k ? u[u_loc(scf, i, k)] : 0.0); /* compute the maximal relative error */ d = fabs(s - t) / (1.0 + fabs(t)); if (dmax < d) dmax = d; } } if (dmax > 1e-8) xprintf("%s: dmax = %g; relative error too large\n", func, dmax); return; } #endif /*********************************************************************** * NAME * * scf_update_exp - update factorization on expanding C * * SYNOPSIS * * #include "glpscf.h" * int scf_update_exp(SCF *scf, const double x[], const double y[], * double z); * * DESCRIPTION * * The routine scf_update_exp updates the factorization of matrix C on * expanding it by adding a new row and column as follows: * * ( C x ) * new C = ( ) * ( y' z ) * * where x[1,...,n] is a new column, y[1,...,n] is a new row, and z is * a new diagonal element. * * If on entry the factorization is empty, the parameters x and y can * be specified as NULL. * * RETURNS * * 0 The factorization has been successfully updated. * * SCF_ESING * The factorization has been successfully updated, however, new * matrix C is singular within working precision. Note that the new * factorization remains valid. * * SCF_ELIMIT * There is not enough room to expand the factorization, because * n = n_max. The factorization remains unchanged. * * ALGORITHM * * We can see that: * * ( F 0 ) ( C x ) ( FC Fx ) ( UP Fx ) * ( ) ( ) = ( ) = ( ) = * ( 0 1 ) ( y' z ) ( y' z ) ( y' z ) * * ( U Fx ) ( P 0 ) * = ( ) ( ), * ( y'P' z ) ( 0 1 ) * * therefore to keep the main equality F * C = U * P we can take: * * ( F 0 ) ( U Fx ) ( P 0 ) * new F = ( ), new U = ( ), new P = ( ), * ( 0 1 ) ( y'P' z ) ( 0 1 ) * * and eliminate the row spike y'P' in the last row of new U to restore * its upper triangular structure. */ int scf_update_exp(SCF *scf, const double x[], const double y[], double z) { int n_max = scf->n_max; int n = scf->n; double *f = scf->f; double *u = scf->u; int *p = scf->p; #if _GLPSCF_DEBUG double *c = scf->c; #endif double *un = scf->w; int i, ij, in, j, k, nj, ret = 0; double t; /* check if the factorization can be expanded */ if (n == n_max) { /* there is not enough room */ ret = SCF_ELIMIT; goto done; } /* increase the order of the factorization */ scf->n = ++n; /* fill new zero column of matrix F */ for (i = 1, in = f_loc(scf, i, n); i < n; i++, in += n_max) f[in] = 0.0; /* fill new zero row of matrix F */ for (j = 1, nj = f_loc(scf, n, j); j < n; j++, nj++) f[nj] = 0.0; /* fill new unity diagonal element of matrix F */ f[f_loc(scf, n, n)] = 1.0; /* compute new column of matrix U, which is (old F) * x */ for (i = 1; i < n; i++) { /* u[i,n] := (i-th row of old F) * x */ t = 0.0; for (j = 1, ij = f_loc(scf, i, 1); j < n; j++, ij++) t += f[ij] * x[j]; u[u_loc(scf, i, n)] = t; } /* compute new (spiked) row of matrix U, which is (old P) * y */ for (j = 1; j < n; j++) un[j] = y[p[j]]; /* store new diagonal element of matrix U, which is z */ un[n] = z; /* expand matrix P */ p[n] = n; #if _GLPSCF_DEBUG /* expand matrix C */ /* fill its new column, which is x */ for (i = 1, in = f_loc(scf, i, n); i < n; i++, in += n_max) c[in] = x[i]; /* fill its new row, which is y */ for (j = 1, nj = f_loc(scf, n, j); j < n; j++, nj++) c[nj] = y[j]; /* fill its new diagonal element, which is z */ c[f_loc(scf, n, n)] = z; #endif /* restore upper triangular structure of matrix U */ for (k = 1; k < n; k++) if (un[k] != 0.0) break; transform(scf, k, un); /* estimate the rank of matrices C and U */ scf->rank = estimate_rank(scf); if (scf->rank != n) ret = SCF_ESING; #if _GLPSCF_DEBUG /* check that the factorization is accurate enough */ check_error(scf, "scf_update_exp"); #endif done: return ret; } /*********************************************************************** * The routine solve solves the system C * x = b. * * From the main equation F * C = U * P it follows that: * * C * x = b => F * C * x = F * b => U * P * x = F * b => * * P * x = inv(U) * F * b => x = P' * inv(U) * F * b. * * On entry the array x contains right-hand side vector b. On exit this * array contains solution vector x. */ static void solve(SCF *scf, double x[]) { int n = scf->n; double *f = scf->f; double *u = scf->u; int *p = scf->p; double *y = scf->w; int i, j, ij; double t; /* y := F * b */ for (i = 1; i <= n; i++) { /* y[i] = (i-th row of F) * b */ t = 0.0; for (j = 1, ij = f_loc(scf, i, 1); j <= n; j++, ij++) t += f[ij] * x[j]; y[i] = t; } /* y := inv(U) * y */ for (i = n; i >= 1; i--) { t = y[i]; for (j = n, ij = u_loc(scf, i, n); j > i; j--, ij--) t -= u[ij] * y[j]; y[i] = t / u[ij]; } /* x := P' * y */ for (i = 1; i <= n; i++) x[p[i]] = y[i]; return; } /*********************************************************************** * The routine tsolve solves the transposed system C' * x = b. * * From the main equation F * C = U * P it follows that: * * C' * F' = P' * U', * * therefore: * * C' * x = b => C' * F' * inv(F') * x = b => * * P' * U' * inv(F') * x = b => U' * inv(F') * x = P * b => * * inv(F') * x = inv(U') * P * b => x = F' * inv(U') * P * b. * * On entry the array x contains right-hand side vector b. On exit this * array contains solution vector x. */ static void tsolve(SCF *scf, double x[]) { int n = scf->n; double *f = scf->f; double *u = scf->u; int *p = scf->p; double *y = scf->w; int i, j, ij; double t; /* y := P * b */ for (i = 1; i <= n; i++) y[i] = x[p[i]]; /* y := inv(U') * y */ for (i = 1; i <= n; i++) { /* compute y[i] */ ij = u_loc(scf, i, i); t = (y[i] /= u[ij]); /* substitute y[i] in other equations */ for (j = i+1, ij++; j <= n; j++, ij++) y[j] -= u[ij] * t; } /* x := F' * y (computed as linear combination of rows of F) */ for (j = 1; j <= n; j++) x[j] = 0.0; for (i = 1; i <= n; i++) { t = y[i]; /* coefficient of linear combination */ for (j = 1, ij = f_loc(scf, i, 1); j <= n; j++, ij++) x[j] += f[ij] * t; } return; } /*********************************************************************** * NAME * * scf_solve_it - solve either system C * x = b or C' * x = b * * SYNOPSIS * * #include "glpscf.h" * void scf_solve_it(SCF *scf, int tr, double x[]); * * DESCRIPTION * * The routine scf_solve_it solves either the system C * x = b (if tr * is zero) or the system C' * x = b, where C' is a matrix transposed * to C (if tr is non-zero). C is assumed to be non-singular. * * On entry the array x should contain the right-hand side vector b in * locations x[1], ..., x[n], where n is the order of matrix C. On exit * the array x contains the solution vector x in the same locations. */ void scf_solve_it(SCF *scf, int tr, double x[]) { if (scf->rank < scf->n) xfault("scf_solve_it: singular matrix\n"); if (!tr) solve(scf, x); else tsolve(scf, x); return; } void scf_reset_it(SCF *scf) { /* reset factorization for empty matrix C */ scf->n = scf->rank = 0; return; } /*********************************************************************** * NAME * * scf_delete_it - delete Schur complement factorization * * SYNOPSIS * * #include "glpscf.h" * void scf_delete_it(SCF *scf); * * DESCRIPTION * * The routine scf_delete_it deletes the specified factorization and * frees all the memory allocated to this object. */ void scf_delete_it(SCF *scf) { xfree(scf->f); xfree(scf->u); xfree(scf->p); #if _GLPSCF_DEBUG xfree(scf->c); #endif xfree(scf->w); xfree(scf); return; } /* eof */ sources_5316/external/glpk/glpnpp03.c0000644000176700017670000030074711401660400016314 0ustar paulpaul/* glpnpp03.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpnpp.h" /*********************************************************************** * NAME * * npp_empty_row - process empty row * * SYNOPSIS * * #include "glpnpp.h" * int npp_empty_row(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_empty_row processes row p, which is empty, i.e. * coefficients at all columns in this row are zero: * * L[p] <= sum 0 x[j] <= U[p], (1) * * where L[p] <= U[p]. * * RETURNS * * 0 - success; * * 1 - problem has no primal feasible solution. * * PROBLEM TRANSFORMATION * * If the following conditions hold: * * L[p] <= +eps, U[p] >= -eps, (2) * * where eps is an absolute tolerance for row value, the row p is * redundant. In this case it can be replaced by equivalent redundant * row, which is free (unbounded), and then removed from the problem. * Otherwise, the row p is infeasible and, thus, the problem has no * primal feasible solution. * * RECOVERING BASIC SOLUTION * * See the routine npp_free_row. * * RECOVERING INTERIOR-POINT SOLUTION * * See the routine npp_free_row. * * RECOVERING MIP SOLUTION * * None needed. */ int npp_empty_row(NPP *npp, NPPROW *p) { /* process empty row */ double eps = 1e-3; /* the row must be empty */ xassert(p->ptr == NULL); /* check primal feasibility */ if (p->lb > +eps || p->ub < -eps) return 1; /* replace the row by equivalent free (unbounded) row */ p->lb = -DBL_MAX, p->ub = +DBL_MAX; /* and process it */ npp_free_row(npp, p); return 0; } /*********************************************************************** * NAME * * npp_empty_col - process empty column * * SYNOPSIS * * #include "glpnpp.h" * int npp_empty_col(NPP *npp, NPPCOL *q); * * DESCRIPTION * * The routine npp_empty_col processes column q: * * l[q] <= x[q] <= u[q], (1) * * where l[q] <= u[q], which is empty, i.e. has zero coefficients in * all constraint rows. * * RETURNS * * 0 - success; * * 1 - problem has no dual feasible solution. * * PROBLEM TRANSFORMATION * * The row of the dual system corresponding to the empty column is the * following: * * sum 0 pi[i] + lambda[q] = c[q], (2) * i * * from which it follows that: * * lambda[q] = c[q]. (3) * * If the following condition holds: * * c[q] < - eps, (4) * * where eps is an absolute tolerance for column multiplier, the lower * column bound l[q] must be active to provide dual feasibility (note * that being preprocessed the problem is always minimization). In this * case the column can be fixed on its lower bound and removed from the * problem (if the column is integral, its bounds are also assumed to * be integral). And if the column has no lower bound (l[q] = -oo), the * problem has no dual feasible solution. * * If the following condition holds: * * c[q] > + eps, (5) * * the upper column bound u[q] must be active to provide dual * feasibility. In this case the column can be fixed on its upper bound * and removed from the problem. And if the column has no upper bound * (u[q] = +oo), the problem has no dual feasible solution. * * Finally, if the following condition holds: * * - eps <= c[q] <= +eps, (6) * * dual feasibility does not depend on a particular value of column q. * In this case the column can be fixed either on its lower bound (if * l[q] > -oo) or on its upper bound (if u[q] < +oo) or at zero (if the * column is unbounded) and then removed from the problem. * * RECOVERING BASIC SOLUTION * * See the routine npp_fixed_col. Having been recovered the column * is assigned status GLP_NS. However, if actually it is not fixed * (l[q] < u[q]), its status should be changed to GLP_NL, GLP_NU, or * GLP_NF depending on which bound it was fixed on transformation stage. * * RECOVERING INTERIOR-POINT SOLUTION * * See the routine npp_fixed_col. * * RECOVERING MIP SOLUTION * * See the routine npp_fixed_col. */ struct empty_col { /* empty column */ int q; /* column reference number */ char stat; /* status in basic solution */ }; static int rcv_empty_col(NPP *npp, void *info); int npp_empty_col(NPP *npp, NPPCOL *q) { /* process empty column */ struct empty_col *info; double eps = 1e-3; /* the column must be empty */ xassert(q->ptr == NULL); /* check dual feasibility */ if (q->coef > +eps && q->lb == -DBL_MAX) return 1; if (q->coef < -eps && q->ub == +DBL_MAX) return 1; /* create transformation stack entry */ info = npp_push_tse(npp, rcv_empty_col, sizeof(struct empty_col)); info->q = q->j; /* fix the column */ if (q->lb == -DBL_MAX && q->ub == +DBL_MAX) { /* free column */ info->stat = GLP_NF; q->lb = q->ub = 0.0; } else if (q->ub == +DBL_MAX) lo: { /* column with lower bound */ info->stat = GLP_NL; q->ub = q->lb; } else if (q->lb == -DBL_MAX) up: { /* column with upper bound */ info->stat = GLP_NU; q->lb = q->ub; } else if (q->lb != q->ub) { /* double-bounded column */ if (q->coef >= +DBL_EPSILON) goto lo; if (q->coef <= -DBL_EPSILON) goto up; if (fabs(q->lb) <= fabs(q->ub)) goto lo; else goto up; } else { /* fixed column */ info->stat = GLP_NS; } /* process fixed column */ npp_fixed_col(npp, q); return 0; } static int rcv_empty_col(NPP *npp, void *_info) { /* recover empty column */ struct empty_col *info = _info; if (npp->sol == GLP_SOL) npp->c_stat[info->q] = info->stat; return 0; } /*********************************************************************** * NAME * * npp_implied_value - process implied column value * * SYNOPSIS * * #include "glpnpp.h" * int npp_implied_value(NPP *npp, NPPCOL *q, double s); * * DESCRIPTION * * For column q: * * l[q] <= x[q] <= u[q], (1) * * where l[q] < u[q], the routine npp_implied_value processes its * implied value s[q]. If this implied value satisfies to the current * column bounds and integrality condition, the routine fixes column q * at the given point. Note that the column is kept in the problem in * any case. * * RETURNS * * 0 - column has been fixed; * * 1 - implied value violates to current column bounds; * * 2 - implied value violates integrality condition. * * ALGORITHM * * Implied column value s[q] satisfies to the current column bounds if * the following condition holds: * * l[q] - eps <= s[q] <= u[q] + eps, (2) * * where eps is an absolute tolerance for column value. If the column * is integral, the following condition also must hold: * * |s[q] - floor(s[q]+0.5)| <= eps, (3) * * where floor(s[q]+0.5) is the nearest integer to s[q]. * * If both condition (2) and (3) are satisfied, the column can be fixed * at the value s[q], or, if it is integral, at floor(s[q]+0.5). * Otherwise, if s[q] violates (2) or (3), the problem has no feasible * solution. * * Note: If s[q] is close to l[q] or u[q], it seems to be reasonable to * fix the column at its lower or upper bound, resp. rather than at the * implied value. */ int npp_implied_value(NPP *npp, NPPCOL *q, double s) { /* process implied column value */ double eps, nint; xassert(npp == npp); /* column must not be fixed */ xassert(q->lb < q->ub); /* check integrality */ if (q->is_int) { nint = floor(s + 0.5); if (fabs(s - nint) <= 1e-5) s = nint; else return 2; } /* check current column lower bound */ if (q->lb != -DBL_MAX) { eps = (q->is_int ? 1e-5 : 1e-5 + 1e-8 * fabs(q->lb)); if (s < q->lb - eps) return 1; /* if s[q] is close to l[q], fix column at its lower bound rather than at the implied value */ if (s < q->lb + 1e-3 * eps) { q->ub = q->lb; return 0; } } /* check current column upper bound */ if (q->ub != +DBL_MAX) { eps = (q->is_int ? 1e-5 : 1e-5 + 1e-8 * fabs(q->ub)); if (s > q->ub + eps) return 1; /* if s[q] is close to u[q], fix column at its upper bound rather than at the implied value */ if (s > q->ub - 1e-3 * eps) { q->lb = q->ub; return 0; } } /* fix column at the implied value */ q->lb = q->ub = s; return 0; } /*********************************************************************** * NAME * * npp_eq_singlet - process row singleton (equality constraint) * * SYNOPSIS * * #include "glpnpp.h" * int npp_eq_singlet(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_eq_singlet processes row p, which is equiality * constraint having the only non-zero coefficient: * * a[p,q] x[q] = b. (1) * * RETURNS * * 0 - success; * * 1 - problem has no primal feasible solution; * * 2 - problem has no integer feasible solution. * * PROBLEM TRANSFORMATION * * The equality constraint defines implied value of column q: * * x[q] = s[q] = b / a[p,q]. (2) * * If the implied value s[q] satisfies to the column bounds (see the * routine npp_implied_value), the column can be fixed at s[q] and * removed from the problem. In this case row p becomes redundant, so * it can be replaced by equivalent free row and also removed from the * problem. * * Note that the routine removes from the problem only row p. Column q * becomes fixed, however, it is kept in the problem. * * RECOVERING BASIC SOLUTION * * In solution to the original problem row p is assigned status GLP_NS * (active equality constraint), and column q is assigned status GLP_BS * (basic column). * * Multiplier for row p can be computed as follows. In the dual system * of the original problem column q corresponds to the following row: * * sum a[i,q] pi[i] + lambda[q] = c[q] ==> * i * * sum a[i,q] pi[i] + a[p,q] pi[p] + lambda[q] = c[q]. * i!=p * * Therefore: * * 1 * pi[p] = ------ (c[q] - lambda[q] - sum a[i,q] pi[i]), (3) * a[p,q] i!=q * * where lambda[q] = 0 (since column[q] is basic), and pi[i] for all * i != p are known in solution to the transformed problem. * * Value of column q in solution to the original problem is assigned * its implied value s[q]. * * RECOVERING INTERIOR-POINT SOLUTION * * Multiplier for row p is computed with formula (3). Value of column * q is assigned its implied value s[q]. * * RECOVERING MIP SOLUTION * * Value of column q is assigned its implied value s[q]. */ struct eq_singlet { /* row singleton (equality constraint) */ int p; /* row reference number */ int q; /* column reference number */ double apq; /* constraint coefficient a[p,q] */ double c; /* objective coefficient at x[q] */ NPPLFE *ptr; /* list of non-zero coefficients a[i,q], i != p */ }; static int rcv_eq_singlet(NPP *npp, void *info); int npp_eq_singlet(NPP *npp, NPPROW *p) { /* process row singleton (equality constraint) */ struct eq_singlet *info; NPPCOL *q; NPPAIJ *aij; NPPLFE *lfe; int ret; double s; /* the row must be singleton equality constraint */ xassert(p->lb == p->ub); xassert(p->ptr != NULL && p->ptr->r_next == NULL); /* compute and process implied column value */ aij = p->ptr; q = aij->col; s = p->lb / aij->val; ret = npp_implied_value(npp, q, s); xassert(0 <= ret && ret <= 2); if (ret != 0) return ret; /* create transformation stack entry */ info = npp_push_tse(npp, rcv_eq_singlet, sizeof(struct eq_singlet)); info->p = p->i; info->q = q->j; info->apq = aij->val; info->c = q->coef; info->ptr = NULL; /* save column coefficients a[i,q], i != p (not needed for MIP solution) */ if (npp->sol != GLP_MIP) { for (aij = q->ptr; aij != NULL; aij = aij->c_next) { if (aij->row == p) continue; /* skip a[p,q] */ lfe = dmp_get_atom(npp->stack, sizeof(NPPLFE)); lfe->ref = aij->row->i; lfe->val = aij->val; lfe->next = info->ptr; info->ptr = lfe; } } /* remove the row from the problem */ npp_del_row(npp, p); return 0; } static int rcv_eq_singlet(NPP *npp, void *_info) { /* recover row singleton (equality constraint) */ struct eq_singlet *info = _info; NPPLFE *lfe; double temp; if (npp->sol == GLP_SOL) { /* column q must be already recovered as GLP_NS */ if (npp->c_stat[info->q] != GLP_NS) { npp_error(); return 1; } npp->r_stat[info->p] = GLP_NS; npp->c_stat[info->q] = GLP_BS; } if (npp->sol != GLP_MIP) { /* compute multiplier for row p with formula (3) */ temp = info->c; for (lfe = info->ptr; lfe != NULL; lfe = lfe->next) temp -= lfe->val * npp->r_pi[lfe->ref]; npp->r_pi[info->p] = temp / info->apq; } return 0; } /*********************************************************************** * NAME * * npp_implied_lower - process implied column lower bound * * SYNOPSIS * * #include "glpnpp.h" * int npp_implied_lower(NPP *npp, NPPCOL *q, double l); * * DESCRIPTION * * For column q: * * l[q] <= x[q] <= u[q], (1) * * where l[q] < u[q], the routine npp_implied_lower processes its * implied lower bound l'[q]. As the result the current column lower * bound may increase. Note that the column is kept in the problem in * any case. * * RETURNS * * 0 - current column lower bound has not changed; * * 1 - current column lower bound has changed, but not significantly; * * 2 - current column lower bound has significantly changed; * * 3 - column has been fixed on its upper bound; * * 4 - implied lower bound violates current column upper bound. * * ALGORITHM * * If column q is integral, before processing its implied lower bound * should be rounded up: * * ( floor(l'[q]+0.5), if |l'[q] - floor(l'[q]+0.5)| <= eps * l'[q] := < (2) * ( ceil(l'[q]), otherwise * * where floor(l'[q]+0.5) is the nearest integer to l'[q], ceil(l'[q]) * is smallest integer not less than l'[q], and eps is an absolute * tolerance for column value. * * Processing implied column lower bound l'[q] includes the following * cases: * * 1) if l'[q] < l[q] + eps, implied lower bound is redundant; * * 2) if l[q] + eps <= l[q] <= u[q] + eps, current column lower bound * l[q] can be strengthened by replacing it with l'[q]. If in this * case new column lower bound becomes close to current column upper * bound u[q], the column can be fixed on its upper bound; * * 3) if l'[q] > u[q] + eps, implied lower bound violates current * column upper bound u[q], in which case the problem has no primal * feasible solution. */ int npp_implied_lower(NPP *npp, NPPCOL *q, double l) { /* process implied column lower bound */ int ret; double eps, nint; xassert(npp == npp); /* column must not be fixed */ xassert(q->lb < q->ub); /* implied lower bound must be finite */ xassert(l != -DBL_MAX); /* if column is integral, round up l'[q] */ if (q->is_int) { nint = floor(l + 0.5); if (fabs(l - nint) <= 1e-5) l = nint; else l = ceil(l); } /* check current column lower bound */ if (q->lb != -DBL_MAX) { eps = (q->is_int ? 1e-3 : 1e-3 + 1e-6 * fabs(q->lb)); if (l < q->lb + eps) { ret = 0; /* redundant */ goto done; } } /* check current column upper bound */ if (q->ub != +DBL_MAX) { eps = (q->is_int ? 1e-5 : 1e-5 + 1e-8 * fabs(q->ub)); if (l > q->ub + eps) { ret = 4; /* infeasible */ goto done; } /* if l'[q] is close to u[q], fix column at its upper bound */ if (l > q->ub - 1e-3 * eps) { q->lb = q->ub; ret = 3; /* fixed */ goto done; } } /* check if column lower bound changes significantly */ if (q->lb == -DBL_MAX) ret = 2; /* significantly */ else if (q->is_int && l > q->lb + 0.5) ret = 2; /* significantly */ else if (l > q->lb + 0.30 * (1.0 + fabs(q->lb))) ret = 2; /* significantly */ else ret = 1; /* not significantly */ /* set new column lower bound */ q->lb = l; done: return ret; } /*********************************************************************** * NAME * * npp_implied_upper - process implied column upper bound * * SYNOPSIS * * #include "glpnpp.h" * int npp_implied_upper(NPP *npp, NPPCOL *q, double u); * * DESCRIPTION * * For column q: * * l[q] <= x[q] <= u[q], (1) * * where l[q] < u[q], the routine npp_implied_upper processes its * implied upper bound u'[q]. As the result the current column upper * bound may decrease. Note that the column is kept in the problem in * any case. * * RETURNS * * 0 - current column upper bound has not changed; * * 1 - current column upper bound has changed, but not significantly; * * 2 - current column upper bound has significantly changed; * * 3 - column has been fixed on its lower bound; * * 4 - implied upper bound violates current column lower bound. * * ALGORITHM * * If column q is integral, before processing its implied upper bound * should be rounded down: * * ( floor(u'[q]+0.5), if |u'[q] - floor(l'[q]+0.5)| <= eps * u'[q] := < (2) * ( floor(l'[q]), otherwise * * where floor(u'[q]+0.5) is the nearest integer to u'[q], * floor(u'[q]) is largest integer not greater than u'[q], and eps is * an absolute tolerance for column value. * * Processing implied column upper bound u'[q] includes the following * cases: * * 1) if u'[q] > u[q] - eps, implied upper bound is redundant; * * 2) if l[q] - eps <= u[q] <= u[q] - eps, current column upper bound * u[q] can be strengthened by replacing it with u'[q]. If in this * case new column upper bound becomes close to current column lower * bound, the column can be fixed on its lower bound; * * 3) if u'[q] < l[q] - eps, implied upper bound violates current * column lower bound l[q], in which case the problem has no primal * feasible solution. */ int npp_implied_upper(NPP *npp, NPPCOL *q, double u) { int ret; double eps, nint; xassert(npp == npp); /* column must not be fixed */ xassert(q->lb < q->ub); /* implied upper bound must be finite */ xassert(u != +DBL_MAX); /* if column is integral, round down u'[q] */ if (q->is_int) { nint = floor(u + 0.5); if (fabs(u - nint) <= 1e-5) u = nint; else u = floor(u); } /* check current column upper bound */ if (q->ub != +DBL_MAX) { eps = (q->is_int ? 1e-3 : 1e-3 + 1e-6 * fabs(q->ub)); if (u > q->ub - eps) { ret = 0; /* redundant */ goto done; } } /* check current column lower bound */ if (q->lb != -DBL_MAX) { eps = (q->is_int ? 1e-5 : 1e-5 + 1e-8 * fabs(q->lb)); if (u < q->lb - eps) { ret = 4; /* infeasible */ goto done; } /* if u'[q] is close to l[q], fix column at its lower bound */ if (u < q->lb + 1e-3 * eps) { q->ub = q->lb; ret = 3; /* fixed */ goto done; } } /* check if column upper bound changes significantly */ if (q->ub == +DBL_MAX) ret = 2; /* significantly */ else if (q->is_int && u < q->ub - 0.5) ret = 2; /* significantly */ else if (u < q->ub - 0.30 * (1.0 + fabs(q->ub))) ret = 2; /* significantly */ else ret = 1; /* not significantly */ /* set new column upper bound */ q->ub = u; done: return ret; } /*********************************************************************** * NAME * * npp_ineq_singlet - process row singleton (inequality constraint) * * SYNOPSIS * * #include "glpnpp.h" * int npp_ineq_singlet(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_ineq_singlet processes row p, which is inequality * constraint having the only non-zero coefficient: * * L[p] <= a[p,q] * x[q] <= U[p], (1) * * where L[p] < U[p], L[p] > -oo and/or U[p] < +oo. * * RETURNS * * 0 - current column bounds have not changed; * * 1 - current column bounds have changed, but not significantly; * * 2 - current column bounds have significantly changed; * * 3 - column has been fixed on its lower or upper bound; * * 4 - problem has no primal feasible solution. * * PROBLEM TRANSFORMATION * * Inequality constraint (1) defines implied bounds of column q: * * ( L[p] / a[p,q], if a[p,q] > 0 * l'[q] = < (2) * ( U[p] / a[p,q], if a[p,q] < 0 * * ( U[p] / a[p,q], if a[p,q] > 0 * u'[q] = < (3) * ( L[p] / a[p,q], if a[p,q] < 0 * * If these implied bounds do not violate current bounds of column q: * * l[q] <= x[q] <= u[q], (4) * * they can be used to strengthen the current column bounds: * * l[q] := max(l[q], l'[q]), (5) * * u[q] := min(u[q], u'[q]). (6) * * (See the routines npp_implied_lower and npp_implied_upper.) * * Once bounds of row p (1) have been carried over column q, the row * becomes redundant, so it can be replaced by equivalent free row and * removed from the problem. * * Note that the routine removes from the problem only row p. Column q, * even it has been fixed, is kept in the problem. * * RECOVERING BASIC SOLUTION * * Note that the row in the dual system corresponding to column q is * the following: * * sum a[i,q] pi[i] + lambda[q] = c[q] ==> * i * (7) * sum a[i,q] pi[i] + a[p,q] pi[p] + lambda[q] = c[q], * i!=p * * where pi[i] for all i != p are known in solution to the transformed * problem. Row p does not exist in the transformed problem, so it has * zero multiplier there. This allows computing multiplier for column q * in solution to the transformed problem: * * lambda~[q] = c[q] - sum a[i,q] pi[i]. (8) * i!=p * * Let in solution to the transformed problem column q be non-basic * with lower bound active (GLP_NL, lambda~[q] >= 0), and this lower * bound be implied one l'[q]. From the original problem's standpoint * this then means that actually the original column lower bound l[q] * is inactive, and active is that row bound L[p] or U[p] that defines * the implied bound l'[q] (2). In this case in solution to the * original problem column q is assigned status GLP_BS while row p is * assigned status GLP_NL (if a[p,q] > 0) or GLP_NU (if a[p,q] < 0). * Since now column q is basic, its multiplier lambda[q] is zero. This * allows using (7) and (8) to find multiplier for row p in solution to * the original problem: * * 1 * pi[p] = ------ (c[q] - sum a[i,q] pi[i]) = lambda~[q] / a[p,q] (9) * a[p,q] i!=p * * Now let in solution to the transformed problem column q be non-basic * with upper bound active (GLP_NU, lambda~[q] <= 0), and this upper * bound be implied one u'[q]. As in the previous case this then means * that from the original problem's standpoint actually the original * column upper bound u[q] is inactive, and active is that row bound * L[p] or U[p] that defines the implied bound u'[q] (3). In this case * in solution to the original problem column q is assigned status * GLP_BS, row p is assigned status GLP_NU (if a[p,q] > 0) or GLP_NL * (if a[p,q] < 0), and its multiplier is computed with formula (9). * * Strengthening bounds of column q according to (5) and (6) may make * it fixed. Thus, if in solution to the transformed problem column q is * non-basic and fixed (GLP_NS), we can suppose that if lambda~[q] > 0, * column q has active lower bound (GLP_NL), and if lambda~[q] < 0, * column q has active upper bound (GLP_NU), reducing this case to two * previous ones. If, however, lambda~[q] is close to zero or * corresponding bound of row p does not exist (this may happen if * lambda~[q] has wrong sign due to round-off errors, in which case it * is expected to be close to zero, since solution is assumed to be dual * feasible), column q can be assigned status GLP_BS (basic), and row p * can be made active on its existing bound. In the latter case row * multiplier pi[p] computed with formula (9) will be also close to * zero, and dual feasibility will be kept. * * In all other cases, namely, if in solution to the transformed * problem column q is basic (GLP_BS), or non-basic with original lower * bound l[q] active (GLP_NL), or non-basic with original upper bound * u[q] active (GLP_NU), constraint (1) is inactive. So in solution to * the original problem status of column q remains unchanged, row p is * assigned status GLP_BS, and its multiplier pi[p] is assigned zero * value. * * RECOVERING INTERIOR-POINT SOLUTION * * First, value of multiplier for column q in solution to the original * problem is computed with formula (8). If lambda~[q] > 0 and column q * has implied lower bound, or if lambda~[q] < 0 and column q has * implied upper bound, this means that from the original problem's * standpoint actually row p has corresponding active bound, in which * case its multiplier pi[p] is computed with formula (9). In other * cases, when the sign of lambda~[q] corresponds to original bound of * column q, or when lambda~[q] =~ 0, value of row multiplier pi[p] is * assigned zero value. * * RECOVERING MIP SOLUTION * * None needed. */ struct ineq_singlet { /* row singleton (inequality constraint) */ int p; /* row reference number */ int q; /* column reference number */ double apq; /* constraint coefficient a[p,q] */ double c; /* objective coefficient at x[q] */ double lb; /* row lower bound */ double ub; /* row upper bound */ char lb_changed; /* this flag is set if column lower bound was changed */ char ub_changed; /* this flag is set if column upper bound was changed */ NPPLFE *ptr; /* list of non-zero coefficients a[i,q], i != p */ }; static int rcv_ineq_singlet(NPP *npp, void *info); int npp_ineq_singlet(NPP *npp, NPPROW *p) { /* process row singleton (inequality constraint) */ struct ineq_singlet *info; NPPCOL *q; NPPAIJ *apq, *aij; NPPLFE *lfe; int lb_changed, ub_changed; double ll, uu; /* the row must be singleton inequality constraint */ xassert(p->lb != -DBL_MAX || p->ub != +DBL_MAX); xassert(p->lb < p->ub); xassert(p->ptr != NULL && p->ptr->r_next == NULL); /* compute implied column bounds */ apq = p->ptr; q = apq->col; xassert(q->lb < q->ub); if (apq->val > 0.0) { ll = (p->lb == -DBL_MAX ? -DBL_MAX : p->lb / apq->val); uu = (p->ub == +DBL_MAX ? +DBL_MAX : p->ub / apq->val); } else { ll = (p->ub == +DBL_MAX ? -DBL_MAX : p->ub / apq->val); uu = (p->lb == -DBL_MAX ? +DBL_MAX : p->lb / apq->val); } /* process implied column lower bound */ if (ll == -DBL_MAX) lb_changed = 0; else { lb_changed = npp_implied_lower(npp, q, ll); xassert(0 <= lb_changed && lb_changed <= 4); if (lb_changed == 4) return 4; /* infeasible */ } /* process implied column upper bound */ if (uu == +DBL_MAX) ub_changed = 0; else if (lb_changed == 3) { /* column was fixed on its upper bound due to l'[q] = u[q] */ /* note that L[p] < U[p], so l'[q] = u[q] < u'[q] */ ub_changed = 0; } else { ub_changed = npp_implied_upper(npp, q, uu); xassert(0 <= ub_changed && ub_changed <= 4); if (ub_changed == 4) return 4; /* infeasible */ } /* if neither lower nor upper column bound was changed, the row is originally redundant and can be replaced by free row */ if (!lb_changed && !ub_changed) { p->lb = -DBL_MAX, p->ub = +DBL_MAX; npp_free_row(npp, p); return 0; } /* create transformation stack entry */ info = npp_push_tse(npp, rcv_ineq_singlet, sizeof(struct ineq_singlet)); info->p = p->i; info->q = q->j; info->apq = apq->val; info->c = q->coef; info->lb = p->lb; info->ub = p->ub; info->lb_changed = (char)lb_changed; info->ub_changed = (char)ub_changed; info->ptr = NULL; /* save column coefficients a[i,q], i != p (not needed for MIP solution) */ if (npp->sol != GLP_MIP) { for (aij = q->ptr; aij != NULL; aij = aij->c_next) { if (aij == apq) continue; /* skip a[p,q] */ lfe = dmp_get_atom(npp->stack, sizeof(NPPLFE)); lfe->ref = aij->row->i; lfe->val = aij->val; lfe->next = info->ptr; info->ptr = lfe; } } /* remove the row from the problem */ npp_del_row(npp, p); return lb_changed >= ub_changed ? lb_changed : ub_changed; } static int rcv_ineq_singlet(NPP *npp, void *_info) { /* recover row singleton (inequality constraint) */ struct ineq_singlet *info = _info; NPPLFE *lfe; double lambda; if (npp->sol == GLP_MIP) goto done; /* compute lambda~[q] in solution to the transformed problem with formula (8) */ lambda = info->c; for (lfe = info->ptr; lfe != NULL; lfe = lfe->next) lambda -= lfe->val * npp->r_pi[lfe->ref]; if (npp->sol == GLP_SOL) { /* recover basic solution */ if (npp->c_stat[info->q] == GLP_BS) { /* column q is basic, so row p is inactive */ npp->r_stat[info->p] = GLP_BS; npp->r_pi[info->p] = 0.0; } else if (npp->c_stat[info->q] == GLP_NL) nl: { /* column q is non-basic with lower bound active */ if (info->lb_changed) { /* it is implied bound, so actually row p is active while column q is basic */ npp->r_stat[info->p] = (char)(info->apq > 0.0 ? GLP_NL : GLP_NU); npp->c_stat[info->q] = GLP_BS; npp->r_pi[info->p] = lambda / info->apq; } else { /* it is original bound, so row p is inactive */ npp->r_stat[info->p] = GLP_BS; npp->r_pi[info->p] = 0.0; } } else if (npp->c_stat[info->q] == GLP_NU) nu: { /* column q is non-basic with upper bound active */ if (info->ub_changed) { /* it is implied bound, so actually row p is active while column q is basic */ npp->r_stat[info->p] = (char)(info->apq > 0.0 ? GLP_NU : GLP_NL); npp->c_stat[info->q] = GLP_BS; npp->r_pi[info->p] = lambda / info->apq; } else { /* it is original bound, so row p is inactive */ npp->r_stat[info->p] = GLP_BS; npp->r_pi[info->p] = 0.0; } } else if (npp->c_stat[info->q] == GLP_NS) { /* column q is non-basic and fixed; note, however, that in in the original problem it is non-fixed */ if (lambda > +1e-7) { if (info->apq > 0.0 && info->lb != -DBL_MAX || info->apq < 0.0 && info->ub != +DBL_MAX || !info->lb_changed) { /* either corresponding bound of row p exists or column q remains non-basic with its original lower bound active */ npp->c_stat[info->q] = GLP_NL; goto nl; } } if (lambda < -1e-7) { if (info->apq > 0.0 && info->ub != +DBL_MAX || info->apq < 0.0 && info->lb != -DBL_MAX || !info->ub_changed) { /* either corresponding bound of row p exists or column q remains non-basic with its original upper bound active */ npp->c_stat[info->q] = GLP_NU; goto nu; } } /* either lambda~[q] is close to zero, or corresponding bound of row p does not exist, because lambda~[q] has wrong sign due to round-off errors; in the latter case lambda~[q] is also assumed to be close to zero; so, we can make row p active on its existing bound and column q basic; pi[p] will have wrong sign, but it also will be close to zero (rarus casus of dual degeneracy) */ if (info->lb != -DBL_MAX && info->ub == +DBL_MAX) { /* row lower bound exists, but upper bound doesn't */ npp->r_stat[info->p] = GLP_NL; } else if (info->lb == -DBL_MAX && info->ub != +DBL_MAX) { /* row upper bound exists, but lower bound doesn't */ npp->r_stat[info->p] = GLP_NU; } else if (info->lb != -DBL_MAX && info->ub != +DBL_MAX) { /* both row lower and upper bounds exist */ /* to choose proper active row bound we should not use lambda~[q], because its value being close to zero is unreliable; so we choose that bound which provides primal feasibility for original constraint (1) */ if (info->apq * npp->c_value[info->q] <= 0.5 * (info->lb + info->ub)) npp->r_stat[info->p] = GLP_NL; else npp->r_stat[info->p] = GLP_NU; } else { npp_error(); return 1; } npp->c_stat[info->q] = GLP_BS; npp->r_pi[info->p] = lambda / info->apq; } else { npp_error(); return 1; } } if (npp->sol == GLP_IPT) { /* recover interior-point solution */ if (lambda > +DBL_EPSILON && info->lb_changed || lambda < -DBL_EPSILON && info->ub_changed) { /* actually row p has corresponding active bound */ npp->r_pi[info->p] = lambda / info->apq; } else { /* either bounds of column q are both inactive or its original bound is active */ npp->r_pi[info->p] = 0.0; } } done: return 0; } /*********************************************************************** * NAME * * npp_implied_slack - process column singleton (implied slack variable) * * SYNOPSIS * * #include "glpnpp.h" * void npp_implied_slack(NPP *npp, NPPCOL *q); * * DESCRIPTION * * The routine npp_implied_slack processes column q: * * l[q] <= x[q] <= u[q], (1) * * where l[q] < u[q], having the only non-zero coefficient in row p, * which is equality constraint: * * sum a[p,j] x[j] + a[p,q] x[q] = b. (2) * j!=q * * PROBLEM TRANSFORMATION * * (If x[q] is integral, this transformation must not be used.) * * The term a[p,q] x[q] in constraint (2) can be considered as a slack * variable that allows to carry bounds of column q over row p and then * remove column q from the problem. * * Constraint (2) can be written as follows: * * sum a[p,j] x[j] = b - a[p,q] x[q]. (3) * j!=q * * According to (1) constraint (3) is equivalent to the following * inequality constraint: * * L[p] <= sum a[p,j] x[j] <= U[p], (4) * j!=q * * where * * ( b - a[p,q] u[q], if a[p,q] > 0 * L[p] = < (5) * ( b - a[p,q] l[q], if a[p,q] < 0 * * ( b - a[p,q] l[q], if a[p,q] > 0 * U[p] = < (6) * ( b - a[p,q] u[q], if a[p,q] < 0 * * From (2) it follows that: * * 1 * x[q] = ------ (b - sum a[p,j] x[j]). (7) * a[p,q] j!=q * * In order to eliminate x[q] from the objective row we substitute it * from (6) to that row: * * z = sum c[j] x[j] + c[q] x[q] + c[0] = * j!=q * 1 * = sum c[j] x[j] + c[q] [------ (b - sum a[p,j] x[j])] + c0 = * j!=q a[p,q] j!=q * * = sum c~[j] x[j] + c~[0], * j!=q * a[p,j] b * c~[j] = c[j] - c[q] ------, c~0 = c0 - c[q] ------ (8) * a[p,q] a[p,q] * * are values of objective coefficients and constant term, resp., in * the transformed problem. * * Note that column q is column singleton, so in the dual system of the * original problem it corresponds to the following row singleton: * * a[p,q] pi[p] + lambda[q] = c[q]. (9) * * In the transformed problem row (9) would be the following: * * a[p,q] pi~[p] + lambda[q] = c~[q] = 0. (10) * * Subtracting (10) from (9) we have: * * a[p,q] (pi[p] - pi~[p]) = c[q] * * that gives the following formula to compute multiplier for row p in * solution to the original problem using its value in solution to the * transformed problem: * * pi[p] = pi~[p] + c[q] / a[p,q]. (11) * * RECOVERING BASIC SOLUTION * * Status of column q in solution to the original problem is defined * by status of row p in solution to the transformed problem and the * sign of coefficient a[p,q] in the original inequality constraint (2) * as follows: * * +-----------------------+---------+--------------------+ * | Status of row p | Sign of | Status of column q | * | (transformed problem) | a[p,q] | (original problem) | * +-----------------------+---------+--------------------+ * | GLP_BS | + / - | GLP_BS | * | GLP_NL | + | GLP_NU | * | GLP_NL | - | GLP_NL | * | GLP_NU | + | GLP_NL | * | GLP_NU | - | GLP_NU | * | GLP_NF | + / - | GLP_NF | * +-----------------------+---------+--------------------+ * * Value of column q is computed with formula (7). Since originally row * p is equality constraint, its status is assigned GLP_NS, and value of * its multiplier pi[p] is computed with formula (11). * * RECOVERING INTERIOR-POINT SOLUTION * * Value of column q is computed with formula (7). Row multiplier value * pi[p] is computed with formula (11). * * RECOVERING MIP SOLUTION * * Value of column q is computed with formula (7). */ struct implied_slack { /* column singleton (implied slack variable) */ int p; /* row reference number */ int q; /* column reference number */ double apq; /* constraint coefficient a[p,q] */ double b; /* right-hand side of original equality constraint */ double c; /* original objective coefficient at x[q] */ NPPLFE *ptr; /* list of non-zero coefficients a[p,j], j != q */ }; static int rcv_implied_slack(NPP *npp, void *info); void npp_implied_slack(NPP *npp, NPPCOL *q) { /* process column singleton (implied slack variable) */ struct implied_slack *info; NPPROW *p; NPPAIJ *aij; NPPLFE *lfe; /* the column must be non-integral non-fixed singleton */ xassert(!q->is_int); xassert(q->lb < q->ub); xassert(q->ptr != NULL && q->ptr->c_next == NULL); /* corresponding row must be equality constraint */ aij = q->ptr; p = aij->row; xassert(p->lb == p->ub); /* create transformation stack entry */ info = npp_push_tse(npp, rcv_implied_slack, sizeof(struct implied_slack)); info->p = p->i; info->q = q->j; info->apq = aij->val; info->b = p->lb; info->c = q->coef; info->ptr = NULL; /* save row coefficients a[p,j], j != q, and substitute x[q] into the objective row */ for (aij = p->ptr; aij != NULL; aij = aij->r_next) { if (aij->col == q) continue; /* skip a[p,q] */ lfe = dmp_get_atom(npp->stack, sizeof(NPPLFE)); lfe->ref = aij->col->j; lfe->val = aij->val; lfe->next = info->ptr; info->ptr = lfe; aij->col->coef -= info->c * (aij->val / info->apq); } npp->c0 += info->c * (info->b / info->apq); /* compute new row bounds */ if (info->apq > 0.0) { p->lb = (q->ub == +DBL_MAX ? -DBL_MAX : info->b - info->apq * q->ub); p->ub = (q->lb == -DBL_MAX ? +DBL_MAX : info->b - info->apq * q->lb); } else { p->lb = (q->lb == -DBL_MAX ? -DBL_MAX : info->b - info->apq * q->lb); p->ub = (q->ub == +DBL_MAX ? +DBL_MAX : info->b - info->apq * q->ub); } /* remove the column from the problem */ npp_del_col(npp, q); return; } static int rcv_implied_slack(NPP *npp, void *_info) { /* recover column singleton (implied slack variable) */ struct implied_slack *info = _info; NPPLFE *lfe; double temp; if (npp->sol == GLP_SOL) { /* assign statuses to row p and column q */ if (npp->r_stat[info->p] == GLP_BS || npp->r_stat[info->p] == GLP_NF) npp->c_stat[info->q] = npp->r_stat[info->p]; else if (npp->r_stat[info->p] == GLP_NL) npp->c_stat[info->q] = (char)(info->apq > 0.0 ? GLP_NU : GLP_NL); else if (npp->r_stat[info->p] == GLP_NU) npp->c_stat[info->q] = (char)(info->apq > 0.0 ? GLP_NL : GLP_NU); else { npp_error(); return 1; } npp->r_stat[info->p] = GLP_NS; } if (npp->sol != GLP_MIP) { /* compute multiplier for row p */ npp->r_pi[info->p] += info->c / info->apq; } /* compute value of column q */ temp = info->b; for (lfe = info->ptr; lfe != NULL; lfe = lfe->next) temp -= lfe->val * npp->c_value[lfe->ref]; npp->c_value[info->q] = temp / info->apq; return 0; } /*********************************************************************** * NAME * * npp_implied_free - process column singleton (implied free variable) * * SYNOPSIS * * #include "glpnpp.h" * int npp_implied_free(NPP *npp, NPPCOL *q); * * DESCRIPTION * * The routine npp_implied_free processes column q: * * l[q] <= x[q] <= u[q], (1) * * having non-zero coefficient in the only row p, which is inequality * constraint: * * L[p] <= sum a[p,j] x[j] + a[p,q] x[q] <= U[p], (2) * j!=q * * where l[q] < u[q], L[p] < U[p], L[p] > -oo and/or U[p] < +oo. * * RETURNS * * 0 - success; * * 1 - column lower and/or upper bound(s) can be active; * * 2 - problem has no dual feasible solution. * * PROBLEM TRANSFORMATION * * Constraint (2) can be written as follows: * * L[p] - sum a[p,j] x[j] <= a[p,q] x[q] <= U[p] - sum a[p,j] x[j], * j!=q j!=q * * from which it follows that: * * alfa <= a[p,q] x[q] <= beta, (3) * * where * * alfa = inf(L[p] - sum a[p,j] x[j]) = * j!=q * * = L[p] - sup sum a[p,j] x[j] = (4) * j!=q * * = L[p] - sum a[p,j] u[j] - sum a[p,j] l[j], * j in Jp j in Jn * * beta = sup(L[p] - sum a[p,j] x[j]) = * j!=q * * = L[p] - inf sum a[p,j] x[j] = (5) * j!=q * * = L[p] - sum a[p,j] l[j] - sum a[p,j] u[j], * j in Jp j in Jn * * Jp = {j != q: a[p,j] > 0}, Jn = {j != q: a[p,j] < 0}. (6) * * Inequality (3) defines implied bounds of variable x[q]: * * l'[q] <= x[q] <= u'[q], (7) * * where * * ( alfa / a[p,q], if a[p,q] > 0 * l'[q] = < (8a) * ( beta / a[p,q], if a[p,q] < 0 * * ( beta / a[p,q], if a[p,q] > 0 * u'[q] = < (8b) * ( alfa / a[p,q], if a[p,q] < 0 * * Thus, if l'[q] > l[q] - eps and u'[q] < u[q] + eps, where eps is * an absolute tolerance for column value, column bounds (1) cannot be * active, in which case column q can be replaced by equivalent free * (unbounded) column. * * Note that column q is column singleton, so in the dual system of the * original problem it corresponds to the following row singleton: * * a[p,q] pi[p] + lambda[q] = c[q], (9) * * from which it follows that: * * pi[p] = (c[q] - lambda[q]) / a[p,q]. (10) * * Let x[q] be implied free (unbounded) variable. Then column q can be * only basic, so its multiplier lambda[q] is equal to zero, and from * (10) we have: * * pi[p] = c[q] / a[p,q]. (11) * * There are possible three cases: * * 1) pi[p] < -eps, where eps is an absolute tolerance for row * multiplier. In this case, to provide dual feasibility of the * original problem, row p must be active on its lower bound, and * if its lower bound does not exist (L[p] = -oo), the problem has * no dual feasible solution; * * 2) pi[p] > +eps. In this case row p must be active on its upper * bound, and if its upper bound does not exist (U[p] = +oo), the * problem has no dual feasible solution; * * 3) -eps <= pi[p] <= +eps. In this case any (either lower or upper) * bound of row p can be active, because this does not affect dual * feasibility. * * Thus, in all three cases original inequality constraint (2) can be * replaced by equality constraint, where the right-hand side is either * lower or upper bound of row p, and bounds of column q can be removed * that makes it free (unbounded). (May note that this transformation * can be followed by transformation "Column singleton (implied slack * variable)" performed by the routine npp_implied_slack.) * * RECOVERING BASIC SOLUTION * * Status of row p in solution to the original problem is determined * by its status in solution to the transformed problem and its bound, * which was choosen to be active: * * +-----------------------+--------+--------------------+ * | Status of row p | Active | Status of row p | * | (transformed problem) | bound | (original problem) | * +-----------------------+--------+--------------------+ * | GLP_BS | L[p] | GLP_BS | * | GLP_BS | U[p] | GLP_BS | * | GLP_NS | L[p] | GLP_NL | * | GLP_NS | U[p] | GLP_NU | * +-----------------------+--------+--------------------+ * * Value of row multiplier pi[p] (as well as value of column q) in * solution to the original problem is the same as in solution to the * transformed problem. * * RECOVERING INTERIOR-POINT SOLUTION * * Value of row multiplier pi[p] in solution to the original problem is * the same as in solution to the transformed problem. * * RECOVERING MIP SOLUTION * * None needed. */ struct implied_free { /* column singleton (implied free variable) */ int p; /* row reference number */ char stat; /* row status: GLP_NL - active constraint on lower bound GLP_NU - active constraint on upper bound */ }; static int rcv_implied_free(NPP *npp, void *info); int npp_implied_free(NPP *npp, NPPCOL *q) { /* process column singleton (implied free variable) */ struct implied_free *info; NPPROW *p; NPPAIJ *apq, *aij; double alfa, beta, l, u, pi, eps; /* the column must be non-fixed singleton */ xassert(q->lb < q->ub); xassert(q->ptr != NULL && q->ptr->c_next == NULL); /* corresponding row must be inequality constraint */ apq = q->ptr; p = apq->row; xassert(p->lb != -DBL_MAX || p->ub != +DBL_MAX); xassert(p->lb < p->ub); /* compute alfa */ alfa = p->lb; if (alfa != -DBL_MAX) { for (aij = p->ptr; aij != NULL; aij = aij->r_next) { if (aij == apq) continue; /* skip a[p,q] */ if (aij->val > 0.0) { if (aij->col->ub == +DBL_MAX) { alfa = -DBL_MAX; break; } alfa -= aij->val * aij->col->ub; } else /* < 0.0 */ { if (aij->col->lb == -DBL_MAX) { alfa = -DBL_MAX; break; } alfa -= aij->val * aij->col->lb; } } } /* compute beta */ beta = p->ub; if (beta != +DBL_MAX) { for (aij = p->ptr; aij != NULL; aij = aij->r_next) { if (aij == apq) continue; /* skip a[p,q] */ if (aij->val > 0.0) { if (aij->col->lb == -DBL_MAX) { beta = +DBL_MAX; break; } beta -= aij->val * aij->col->lb; } else /* < 0.0 */ { if (aij->col->ub == +DBL_MAX) { beta = +DBL_MAX; break; } beta -= aij->val * aij->col->ub; } } } /* compute implied column lower bound l'[q] */ if (apq->val > 0.0) l = (alfa == -DBL_MAX ? -DBL_MAX : alfa / apq->val); else /* < 0.0 */ l = (beta == +DBL_MAX ? -DBL_MAX : beta / apq->val); /* compute implied column upper bound u'[q] */ if (apq->val > 0.0) u = (beta == +DBL_MAX ? +DBL_MAX : beta / apq->val); else u = (alfa == -DBL_MAX ? +DBL_MAX : alfa / apq->val); /* check if column lower bound l[q] can be active */ if (q->lb != -DBL_MAX) { eps = 1e-9 + 1e-12 * fabs(q->lb); if (l < q->lb - eps) return 1; /* yes, it can */ } /* check if column upper bound u[q] can be active */ if (q->ub != +DBL_MAX) { eps = 1e-9 + 1e-12 * fabs(q->ub); if (u > q->ub + eps) return 1; /* yes, it can */ } /* okay; make column q free (unbounded) */ q->lb = -DBL_MAX, q->ub = +DBL_MAX; /* create transformation stack entry */ info = npp_push_tse(npp, rcv_implied_free, sizeof(struct implied_free)); info->p = p->i; info->stat = -1; /* compute row multiplier pi[p] */ pi = q->coef / apq->val; /* check dual feasibility for row p */ if (pi > +DBL_EPSILON) { /* lower bound L[p] must be active */ if (p->lb != -DBL_MAX) nl: { info->stat = GLP_NL; p->ub = p->lb; } else { if (pi > +1e-5) return 2; /* dual infeasibility */ /* take a chance on U[p] */ xassert(p->ub != +DBL_MAX); goto nu; } } else if (pi < -DBL_EPSILON) { /* upper bound U[p] must be active */ if (p->ub != +DBL_MAX) nu: { info->stat = GLP_NU; p->lb = p->ub; } else { if (pi < -1e-5) return 2; /* dual infeasibility */ /* take a chance on L[p] */ xassert(p->lb != -DBL_MAX); goto nl; } } else { /* any bound (either L[p] or U[p]) can be made active */ if (p->ub == +DBL_MAX) { xassert(p->lb != -DBL_MAX); goto nl; } if (p->lb == -DBL_MAX) { xassert(p->ub != +DBL_MAX); goto nu; } if (fabs(p->lb) <= fabs(p->ub)) goto nl; else goto nu; } return 0; } static int rcv_implied_free(NPP *npp, void *_info) { /* recover column singleton (implied free variable) */ struct implied_free *info = _info; if (npp->sol == GLP_SOL) { if (npp->r_stat[info->p] == GLP_BS) npp->r_stat[info->p] = GLP_BS; else if (npp->r_stat[info->p] == GLP_NS) { xassert(info->stat == GLP_NL || info->stat == GLP_NU); npp->r_stat[info->p] = info->stat; } else { npp_error(); return 1; } } return 0; } /*********************************************************************** * NAME * * npp_eq_doublet - process row doubleton (equality constraint) * * SYNOPSIS * * #include "glpnpp.h" * NPPCOL *npp_eq_doublet(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_eq_doublet processes row p, which is equality * constraint having exactly two non-zero coefficients: * * a[p,q] x[q] + a[p,r] x[r] = b. (1) * * As the result of processing one of columns q or r is eliminated from * all other rows and, thus, becomes column singleton of type "implied * slack variable". Row p is not changed and along with column q and r * remains in the problem. * * RETURNS * * The routine npp_eq_doublet returns pointer to the descriptor of that * column q or r which has been eliminated. If, due to some reason, the * elimination was not performed, the routine returns NULL. * * PROBLEM TRANSFORMATION * * First, we decide which column q or r will be eliminated. Let it be * column q. Consider i-th constraint row, where column q has non-zero * coefficient a[i,q] != 0: * * L[i] <= sum a[i,j] x[j] <= U[i]. (2) * j * * In order to eliminate column q from row (2) we subtract from it row * (1) multiplied by gamma[i] = a[i,q] / a[p,q], i.e. we replace in the * transformed problem row (2) by its linear combination with row (1). * This transformation changes only coefficients in columns q and r, * and bounds of row i as follows: * * a~[i,q] = a[i,q] - gamma[i] a[p,q] = 0, (3) * * a~[i,r] = a[i,r] - gamma[i] a[p,r], (4) * * L~[i] = L[i] - gamma[i] b, (5) * * U~[i] = U[i] - gamma[i] b. (6) * * RECOVERING BASIC SOLUTION * * The transformation of the primal system of the original problem: * * L <= A x <= U (7) * * is equivalent to multiplying from the left a transformation matrix F * by components of this primal system, which in the transformed problem * becomes the following: * * F L <= F A x <= F U ==> L~ <= A~x <= U~. (8) * * The matrix F has the following structure: * * ( 1 -gamma[1] ) * ( ) * ( 1 -gamma[2] ) * ( ) * ( ... ... ) * ( ) * F = ( 1 -gamma[p-1] ) (9) * ( ) * ( 1 ) * ( ) * ( -gamma[p+1] 1 ) * ( ) * ( ... ... ) * * where its column containing elements -gamma[i] corresponds to row p * of the primal system. * * From (8) it follows that the dual system of the original problem: * * A'pi + lambda = c, (10) * * in the transformed problem becomes the following: * * A'F'inv(F')pi + lambda = c ==> (A~)'pi~ + lambda = c, (11) * * where: * * pi~ = inv(F')pi (12) * * is the vector of row multipliers in the transformed problem. Thus: * * pi = F'pi~. (13) * * Therefore, as it follows from (13), value of multiplier for row p in * solution to the original problem can be computed as follows: * * pi[p] = pi~[p] - sum gamma[i] pi~[i], (14) * i * * where pi~[i] = pi[i] is multiplier for row i (i != p). * * Note that the statuses of all rows and columns are not changed. * * RECOVERING INTERIOR-POINT SOLUTION * * Multiplier for row p in solution to the original problem is computed * with formula (14). * * RECOVERING MIP SOLUTION * * None needed. */ struct eq_doublet { /* row doubleton (equality constraint) */ int p; /* row reference number */ double apq; /* constraint coefficient a[p,q] */ NPPLFE *ptr; /* list of non-zero coefficients a[i,q], i != p */ }; static int rcv_eq_doublet(NPP *npp, void *info); NPPCOL *npp_eq_doublet(NPP *npp, NPPROW *p) { /* process row doubleton (equality constraint) */ struct eq_doublet *info; NPPROW *i; NPPCOL *q, *r; NPPAIJ *apq, *apr, *aiq, *air, *next; NPPLFE *lfe; double gamma; /* the row must be doubleton equality constraint */ xassert(p->lb == p->ub); xassert(p->ptr != NULL && p->ptr->r_next != NULL && p->ptr->r_next->r_next == NULL); /* choose column to be eliminated */ { NPPAIJ *a1, *a2; a1 = p->ptr, a2 = a1->r_next; if (fabs(a2->val) < 0.001 * fabs(a1->val)) { /* only first column can be eliminated, because second one has too small constraint coefficient */ apq = a1, apr = a2; } else if (fabs(a1->val) < 0.001 * fabs(a2->val)) { /* only second column can be eliminated, because first one has too small constraint coefficient */ apq = a2, apr = a1; } else { /* both columns are appropriate; choose that one which is shorter to minimize fill-in */ if (npp_col_nnz(npp, a1->col) <= npp_col_nnz(npp, a2->col)) { /* first column is shorter */ apq = a1, apr = a2; } else { /* second column is shorter */ apq = a2, apr = a1; } } } /* now columns q and r have been chosen */ q = apq->col, r = apr->col; /* create transformation stack entry */ info = npp_push_tse(npp, rcv_eq_doublet, sizeof(struct eq_doublet)); info->p = p->i; info->apq = apq->val; info->ptr = NULL; /* transform each row i (i != p), where a[i,q] != 0, to eliminate column q */ for (aiq = q->ptr; aiq != NULL; aiq = next) { next = aiq->c_next; if (aiq == apq) continue; /* skip row p */ i = aiq->row; /* row i to be transformed */ /* save constraint coefficient a[i,q] */ if (npp->sol != GLP_MIP) { lfe = dmp_get_atom(npp->stack, sizeof(NPPLFE)); lfe->ref = i->i; lfe->val = aiq->val; lfe->next = info->ptr; info->ptr = lfe; } /* find coefficient a[i,r] in row i */ for (air = i->ptr; air != NULL; air = air->r_next) if (air->col == r) break; /* if a[i,r] does not exist, create a[i,r] = 0 */ if (air == NULL) air = npp_add_aij(npp, i, r, 0.0); /* compute gamma[i] = a[i,q] / a[p,q] */ gamma = aiq->val / apq->val; /* (row i) := (row i) - gamma[i] * (row p); see (3)-(6) */ /* new a[i,q] is exact zero due to elimnation; remove it from row i */ npp_del_aij(npp, aiq); /* compute new a[i,r] */ air->val -= gamma * apr->val; /* if new a[i,r] is close to zero due to numeric cancelation, remove it from row i */ if (fabs(air->val) <= 1e-10) npp_del_aij(npp, air); /* compute new lower and upper bounds of row i */ if (i->lb == i->ub) i->lb = i->ub = (i->lb - gamma * p->lb); else { if (i->lb != -DBL_MAX) i->lb -= gamma * p->lb; if (i->ub != +DBL_MAX) i->ub -= gamma * p->lb; } } return q; } static int rcv_eq_doublet(NPP *npp, void *_info) { /* recover row doubleton (equality constraint) */ struct eq_doublet *info = _info; NPPLFE *lfe; double gamma, temp; /* we assume that processing row p is followed by processing column q as singleton of type "implied slack variable", in which case row p must always be active equality constraint */ if (npp->sol == GLP_SOL) { if (npp->r_stat[info->p] != GLP_NS) { npp_error(); return 1; } } if (npp->sol != GLP_MIP) { /* compute value of multiplier for row p; see (14) */ temp = npp->r_pi[info->p]; for (lfe = info->ptr; lfe != NULL; lfe = lfe->next) { gamma = lfe->val / info->apq; /* a[i,q] / a[p,q] */ temp -= gamma * npp->r_pi[lfe->ref]; } npp->r_pi[info->p] = temp; } return 0; } /*********************************************************************** * NAME * * npp_forcing_row - process forcing row * * SYNOPSIS * * #include "glpnpp.h" * int npp_forcing_row(NPP *npp, NPPROW *p, int at); * * DESCRIPTION * * The routine npp_forcing row processes row p of general format: * * L[p] <= sum a[p,j] x[j] <= U[p], (1) * j * * l[j] <= x[j] <= u[j], (2) * * where L[p] <= U[p] and l[j] < u[j] for all a[p,j] != 0. It is also * assumed that: * * 1) if at = 0 then |L[p] - U'[p]| <= eps, where U'[p] is implied * row upper bound (see below), eps is an absolute tolerance for row * value; * * 2) if at = 1 then |U[p] - L'[p]| <= eps, where L'[p] is implied * row lower bound (see below). * * RETURNS * * 0 - success; * * 1 - cannot fix columns due to too small constraint coefficients. * * PROBLEM TRANSFORMATION * * Implied lower and upper bounds of row (1) are determined by bounds * of corresponding columns (variables) as follows: * * L'[p] = inf sum a[p,j] x[j] = * j * (3) * = sum a[p,j] l[j] + sum a[p,j] u[j], * j in Jp j in Jn * * U'[p] = sup sum a[p,j] x[j] = * (4) * = sum a[p,j] u[j] + sum a[p,j] l[j], * j in Jp j in Jn * * Jp = {j: a[p,j] > 0}, Jn = {j: a[p,j] < 0}. (5) * * If L[p] =~ U'[p] (at = 0), solution can be primal feasible only when * all variables take their boundary values as defined by (4): * * ( u[j], if j in Jp * x[j] = < (6) * ( l[j], if j in Jn * * Similarly, if U[p] =~ L'[p] (at = 1), solution can be primal feasible * only when all variables take their boundary values as defined by (3): * * ( l[j], if j in Jp * x[j] = < (7) * ( u[j], if j in Jn * * Condition (6) or (7) allows fixing all columns (variables x[j]) * in row (1) on their bounds and then removing them from the problem * (see the routine npp_fixed_col). Due to this row p becomes redundant, * so it can be replaced by equivalent free (unbounded) row and also * removed from the problem (see the routine npp_free_row). * * 1. To apply this transformation row (1) should not have coefficients * whose magnitude is too small, i.e. all a[p,j] should satisfy to * the following condition: * * |a[p,j]| >= eps * max(1, |a[p,k]|), (8) * k * where eps is a relative tolerance for constraint coefficients. * Otherwise, fixing columns may be numerically unreliable and may * lead to wrong solution. * * 2. The routine fixes columns and remove bounds of row p, however, * it does not remove the row and columns from the problem. * * RECOVERING BASIC SOLUTION * * In the transformed problem row p being inactive constraint is * assigned status GLP_BS (as the result of transformation of free * row), and all columns in this row are assigned status GLP_NS (as the * result of transformation of fixed columns). * * Note that in the dual system of the transformed (as well as original) * problem every column j in row p corresponds to the following row: * * sum a[i,j] pi[i] + a[p,j] pi[p] + lambda[j] = c[j], (9) * i!=p * * from which it follows that: * * lambda[j] = c[j] - sum a[i,j] pi[i] - a[p,j] pi[p]. (10) * i!=p * * In the transformed problem values of all multipliers pi[i] are known * (including pi[i], whose value is zero, since row p is inactive). * Thus, using formula (10) it is possible to compute values of * multipliers lambda[j] for all columns in row p. * * Note also that in the original problem all columns in row p are * bounded, not fixed. So status GLP_NS assigned to every such column * must be changed to GLP_NL or GLP_NU depending on which bound the * corresponding column has been fixed. This status change may lead to * dual feasibility violation for solution of the original problem, * because now column multipliers must satisfy to the following * condition: * * ( >= 0, if status of column j is GLP_NL, * lambda[j] < (11) * ( <= 0, if status of column j is GLP_NU. * * If this condition holds, solution to the original problem is the * same as to the transformed problem. Otherwise, we have to perform * one degenerate pivoting step of the primal simplex method to obtain * dual feasible (hence, optimal) solution to the original problem as * follows. If, on problem transformation, row p was made active on its * lower bound (case at = 0), we change its status to GLP_NL (or GLP_NS) * and start increasing its multiplier pi[p]. Otherwise, if row p was * made active on its upper bound (case at = 1), we change its status * to GLP_NU (or GLP_NS) and start decreasing pi[p]. From (10) it * follows that: * * delta lambda[j] = - a[p,j] * delta pi[p] = - a[p,j] pi[p]. (12) * * Simple analysis of formulae (3)-(5) shows that changing pi[p] in the * specified direction causes increasing lambda[j] for every column j * assigned status GLP_NL (delta lambda[j] > 0) and decreasing lambda[j] * for every column j assigned status GLP_NU (delta lambda[j] < 0). It * is understood that once the last lambda[q], which violates condition * (11), has reached zero, multipliers lambda[j] for all columns get * valid signs. Such column q can be determined as follows. Let d[j] be * initial value of lambda[j] (i.e. reduced cost of column j) in the * transformed problem computed with formula (10) when pi[p] = 0. Then * lambda[j] = d[j] + delta lambda[j], and from (12) it follows that * lambda[j] becomes zero if: * * delta lambda[j] = - a[p,j] pi[p] = - d[j] ==> * (13) * pi[p] = d[j] / a[p,j]. * * Therefore, the last column q, for which lambda[q] becomes zero, can * be determined from the following condition: * * |d[q] / a[p,q]| = max |pi[p]| = max |d[j] / a[p,j]|, (14) * j in D j in D * * where D is a set of columns j whose, reduced costs d[j] have invalid * signs, i.e. violate condition (11). (Thus, if D is empty, solution * to the original problem is the same as solution to the transformed * problem, and no correction is needed as was noticed above.) In * solution to the original problem column q is assigned status GLP_BS, * since it replaces column of auxiliary variable of row p (becoming * active) in the basis, and multiplier for row p is assigned its new * value, which is pi[p] = d[q] / a[p,q]. Note that due to primal * degeneracy values of all columns having non-zero coefficients in row * p remain unchanged. * * RECOVERING INTERIOR-POINT SOLUTION * * Value of multiplier pi[p] in solution to the original problem is * corrected in the same way as for basic solution. Values of all * columns having non-zero coefficients in row p remain unchanged. * * RECOVERING MIP SOLUTION * * None needed. */ struct forcing_col { /* column fixed on its bound by forcing row */ int j; /* column reference number */ char stat; /* original column status: GLP_NL - fixed on lower bound GLP_NU - fixed on upper bound */ double a; /* constraint coefficient a[p,j] */ double c; /* objective coefficient c[j] */ NPPLFE *ptr; /* list of non-zero coefficients a[i,j], i != p */ struct forcing_col *next; /* pointer to another column fixed by forcing row */ }; struct forcing_row { /* forcing row */ int p; /* row reference number */ char stat; /* status assigned to the row if it becomes active: GLP_NS - active equality constraint GLP_NL - inequality constraint with lower bound active GLP_NU - inequality constraint with upper bound active */ struct forcing_col *ptr; /* list of all columns having non-zero constraint coefficient a[p,j] in the forcing row */ }; static int rcv_forcing_row(NPP *npp, void *info); int npp_forcing_row(NPP *npp, NPPROW *p, int at) { /* process forcing row */ struct forcing_row *info; struct forcing_col *col = NULL; NPPCOL *j; NPPAIJ *apj, *aij; NPPLFE *lfe; double big; xassert(at == 0 || at == 1); /* determine maximal magnitude of the row coefficients */ big = 1.0; for (apj = p->ptr; apj != NULL; apj = apj->r_next) if (big < fabs(apj->val)) big = fabs(apj->val); /* if there are too small coefficients in the row, transformation should not be applied */ for (apj = p->ptr; apj != NULL; apj = apj->r_next) if (fabs(apj->val) < 1e-7 * big) return 1; /* create transformation stack entry */ info = npp_push_tse(npp, rcv_forcing_row, sizeof(struct forcing_row)); info->p = p->i; if (p->lb == p->ub) { /* equality constraint */ info->stat = GLP_NS; } else if (at == 0) { /* inequality constraint; case L[p] = U'[p] */ info->stat = GLP_NL; xassert(p->lb != -DBL_MAX); } else /* at == 1 */ { /* inequality constraint; case U[p] = L'[p] */ info->stat = GLP_NU; xassert(p->ub != +DBL_MAX); } info->ptr = NULL; /* scan the forcing row, fix columns at corresponding bounds, and save column information (the latter is not needed for MIP) */ for (apj = p->ptr; apj != NULL; apj = apj->r_next) { /* column j has non-zero coefficient in the forcing row */ j = apj->col; /* it must be non-fixed */ xassert(j->lb < j->ub); /* allocate stack entry to save column information */ if (npp->sol != GLP_MIP) { col = dmp_get_atom(npp->stack, sizeof(struct forcing_col)); col->j = j->j; col->stat = -1; /* will be set below */ col->a = apj->val; col->c = j->coef; col->ptr = NULL; col->next = info->ptr; info->ptr = col; } /* fix column j */ if (at == 0 && apj->val < 0.0 || at != 0 && apj->val > 0.0) { /* at its lower bound */ if (npp->sol != GLP_MIP) col->stat = GLP_NL; xassert(j->lb != -DBL_MAX); j->ub = j->lb; } else { /* at its upper bound */ if (npp->sol != GLP_MIP) col->stat = GLP_NU; xassert(j->ub != +DBL_MAX); j->lb = j->ub; } /* save column coefficients a[i,j], i != p */ if (npp->sol != GLP_MIP) { for (aij = j->ptr; aij != NULL; aij = aij->c_next) { if (aij == apj) continue; /* skip a[p,j] */ lfe = dmp_get_atom(npp->stack, sizeof(NPPLFE)); lfe->ref = aij->row->i; lfe->val = aij->val; lfe->next = col->ptr; col->ptr = lfe; } } } /* make the row free (unbounded) */ p->lb = -DBL_MAX, p->ub = +DBL_MAX; return 0; } static int rcv_forcing_row(NPP *npp, void *_info) { /* recover forcing row */ struct forcing_row *info = _info; struct forcing_col *col, *piv; NPPLFE *lfe; double d, big, temp; if (npp->sol == GLP_MIP) goto done; /* initially solution to the original problem is the same as to the transformed problem, where row p is inactive constraint with pi[p] = 0, and all columns are non-basic */ if (npp->sol == GLP_SOL) { if (npp->r_stat[info->p] != GLP_BS) { npp_error(); return 1; } for (col = info->ptr; col != NULL; col = col->next) { if (npp->c_stat[col->j] != GLP_NS) { npp_error(); return 1; } npp->c_stat[col->j] = col->stat; /* original status */ } } /* compute reduced costs d[j] for all columns with formula (10) and store them in col.c instead objective coefficients */ for (col = info->ptr; col != NULL; col = col->next) { d = col->c; for (lfe = col->ptr; lfe != NULL; lfe = lfe->next) d -= lfe->val * npp->r_pi[lfe->ref]; col->c = d; } /* consider columns j, whose multipliers lambda[j] has wrong sign in solution to the transformed problem (where lambda[j] = d[j]), and choose column q, whose multipler lambda[q] reaches zero last on changing row multiplier pi[p]; see (14) */ piv = NULL, big = 0.0; for (col = info->ptr; col != NULL; col = col->next) { d = col->c; /* d[j] */ temp = fabs(d / col->a); if (col->stat == GLP_NL) { /* column j has active lower bound */ if (d < 0.0 && big < temp) piv = col, big = temp; } else if (col->stat == GLP_NU) { /* column j has active upper bound */ if (d > 0.0 && big < temp) piv = col, big = temp; } else { npp_error(); return 1; } } /* if column q does not exist, no correction is needed */ if (piv != NULL) { /* correct solution; row p becomes active constraint while column q becomes basic */ if (npp->sol == GLP_SOL) { npp->r_stat[info->p] = info->stat; npp->c_stat[piv->j] = GLP_BS; } /* assign new value to row multiplier pi[p] = d[p] / a[p,q] */ npp->r_pi[info->p] = piv->c / piv->a; } done: return 0; } /*********************************************************************** * NAME * * npp_analyze_row - perform general row analysis * * SYNOPSIS * * #include "glpnpp.h" * int npp_analyze_row(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_analyze_row performs analysis of row p of general * format: * * L[p] <= sum a[p,j] x[j] <= U[p], (1) * j * * l[j] <= x[j] <= u[j], (2) * * where L[p] <= U[p] and l[j] <= u[j] for all a[p,j] != 0. * * RETURNS * * 0x?0 - row lower bound does not exist or is redundant; * * 0x?1 - row lower bound can be active; * * 0x?2 - row lower bound is a forcing bound; * * 0x0? - row upper bound does not exist or is redundant; * * 0x1? - row upper bound can be active; * * 0x2? - row upper bound is a forcing bound; * * 0x33 - row bounds are inconsistent with column bounds. * * ALGORITHM * * Analysis of row (1) is based on analysis of its implied lower and * upper bounds, which are determined by bounds of corresponding columns * (variables) as follows: * * L'[p] = inf sum a[p,j] x[j] = * j * (3) * = sum a[p,j] l[j] + sum a[p,j] u[j], * j in Jp j in Jn * * U'[p] = sup sum a[p,j] x[j] = * (4) * = sum a[p,j] u[j] + sum a[p,j] l[j], * j in Jp j in Jn * * Jp = {j: a[p,j] > 0}, Jn = {j: a[p,j] < 0}. (5) * * (Note that bounds of all columns in row p are assumed to be correct, * so L'[p] <= U'[p].) * * Analysis of row lower bound L[p] includes the following cases: * * 1) if L[p] > U'[p] + eps, where eps is an absolute tolerance for row * value, row lower bound L[p] and implied row upper bound U'[p] are * inconsistent, ergo, the problem has no primal feasible solution; * * 2) if U'[p] - eps <= L[p] <= U'[p] + eps, i.e. if L[p] =~ U'[p], * the row is a forcing row on its lower bound (see description of * the routine npp_forcing_row); * * 3) if L[p] > L'[p] + eps, row lower bound L[p] can be active (this * conclusion does not account other rows in the problem); * * 4) if L[p] <= L'[p] + eps, row lower bound L[p] cannot be active, so * it is redundant and can be removed (replaced by -oo). * * Analysis of row upper bound U[p] is performed in a similar way and * includes the following cases: * * 1) if U[p] < L'[p] - eps, row upper bound U[p] and implied row lower * bound L'[p] are inconsistent, ergo the problem has no primal * feasible solution; * * 2) if L'[p] - eps <= U[p] <= L'[p] + eps, i.e. if U[p] =~ L'[p], * the row is a forcing row on its upper bound (see description of * the routine npp_forcing_row); * * 3) if U[p] < U'[p] - eps, row upper bound U[p] can be active (this * conclusion does not account other rows in the problem); * * 4) if U[p] >= U'[p] - eps, row upper bound U[p] cannot be active, so * it is redundant and can be removed (replaced by +oo). */ int npp_analyze_row(NPP *npp, NPPROW *p) { /* perform general row analysis */ NPPAIJ *aij; int ret = 0x00; double l, u, eps; xassert(npp == npp); /* compute implied lower bound L'[p]; see (3) */ l = 0.0; for (aij = p->ptr; aij != NULL; aij = aij->r_next) { if (aij->val > 0.0) { if (aij->col->lb == -DBL_MAX) { l = -DBL_MAX; break; } l += aij->val * aij->col->lb; } else /* aij->val < 0.0 */ { if (aij->col->ub == +DBL_MAX) { l = -DBL_MAX; break; } l += aij->val * aij->col->ub; } } /* compute implied upper bound U'[p]; see (4) */ u = 0.0; for (aij = p->ptr; aij != NULL; aij = aij->r_next) { if (aij->val > 0.0) { if (aij->col->ub == +DBL_MAX) { u = +DBL_MAX; break; } u += aij->val * aij->col->ub; } else /* aij->val < 0.0 */ { if (aij->col->lb == -DBL_MAX) { u = +DBL_MAX; break; } u += aij->val * aij->col->lb; } } /* column bounds are assumed correct, so L'[p] <= U'[p] */ /* check if row lower bound is consistent */ if (p->lb != -DBL_MAX) { eps = 1e-3 + 1e-6 * fabs(p->lb); if (p->lb - eps > u) { ret = 0x33; goto done; } } /* check if row upper bound is consistent */ if (p->ub != +DBL_MAX) { eps = 1e-3 + 1e-6 * fabs(p->ub); if (p->ub + eps < l) { ret = 0x33; goto done; } } /* check if row lower bound can be active/forcing */ if (p->lb != -DBL_MAX) { eps = 1e-9 + 1e-12 * fabs(p->lb); if (p->lb - eps > l) { if (p->lb + eps <= u) ret |= 0x01; else ret |= 0x02; } } /* check if row upper bound can be active/forcing */ if (p->ub != +DBL_MAX) { eps = 1e-9 + 1e-12 * fabs(p->ub); if (p->ub + eps < u) { /* check if the upper bound is forcing */ if (p->ub - eps >= l) ret |= 0x10; else ret |= 0x20; } } done: return ret; } /*********************************************************************** * NAME * * npp_inactive_bound - remove row lower/upper inactive bound * * SYNOPSIS * * #include "glpnpp.h" * void npp_inactive_bound(NPP *npp, NPPROW *p, int which); * * DESCRIPTION * * The routine npp_inactive_bound removes lower (if which = 0) or upper * (if which = 1) bound of row p: * * L[p] <= sum a[p,j] x[j] <= U[p], * * which (bound) is assumed to be redundant. * * PROBLEM TRANSFORMATION * * If which = 0, current lower bound L[p] of row p is assigned -oo. * If which = 1, current upper bound U[p] of row p is assigned +oo. * * RECOVERING BASIC SOLUTION * * If in solution to the transformed problem row p is inactive * constraint (GLP_BS), its status is not changed in solution to the * original problem. Otherwise, status of row p in solution to the * original problem is defined by its type before transformation and * its status in solution to the transformed problem as follows: * * +---------------------+-------+---------------+---------------+ * | Row | Flag | Row status in | Row status in | * | type | which | transfmd soln | original soln | * +---------------------+-------+---------------+---------------+ * | sum >= L[p] | 0 | GLP_NF | GLP_NL | * | sum <= U[p] | 1 | GLP_NF | GLP_NU | * | L[p] <= sum <= U[p] | 0 | GLP_NU | GLP_NU | * | L[p] <= sum <= U[p] | 1 | GLP_NL | GLP_NL | * | sum = L[p] = U[p] | 0 | GLP_NU | GLP_NS | * | sum = L[p] = U[p] | 1 | GLP_NL | GLP_NS | * +---------------------+-------+---------------+---------------+ * * RECOVERING INTERIOR-POINT SOLUTION * * None needed. * * RECOVERING MIP SOLUTION * * None needed. */ struct inactive_bound { /* row inactive bound */ int p; /* row reference number */ char stat; /* row status (if active constraint) */ }; static int rcv_inactive_bound(NPP *npp, void *info); void npp_inactive_bound(NPP *npp, NPPROW *p, int which) { /* remove row lower/upper inactive bound */ struct inactive_bound *info; if (npp->sol == GLP_SOL) { /* create transformation stack entry */ info = npp_push_tse(npp, rcv_inactive_bound, sizeof(struct inactive_bound)); info->p = p->i; if (p->ub == +DBL_MAX) info->stat = GLP_NL; else if (p->lb == -DBL_MAX) info->stat = GLP_NU; else if (p->lb != p->ub) info->stat = (char)(which == 0 ? GLP_NU : GLP_NL); else info->stat = GLP_NS; } /* remove row inactive bound */ if (which == 0) { xassert(p->lb != -DBL_MAX); p->lb = -DBL_MAX; } else if (which == 1) { xassert(p->ub != +DBL_MAX); p->ub = +DBL_MAX; } else xassert(which != which); return; } static int rcv_inactive_bound(NPP *npp, void *_info) { /* recover row status */ struct inactive_bound *info = _info; if (npp->sol != GLP_SOL) { npp_error(); return 1; } if (npp->r_stat[info->p] == GLP_BS) npp->r_stat[info->p] = GLP_BS; else npp->r_stat[info->p] = info->stat; return 0; } /*********************************************************************** * NAME * * npp_implied_bounds - determine implied column bounds * * SYNOPSIS * * #include "glpnpp.h" * void npp_implied_bounds(NPP *npp, NPPROW *p); * * DESCRIPTION * * The routine npp_implied_bounds inspects general row (constraint) p: * * L[p] <= sum a[p,j] x[j] <= U[p], (1) * * l[j] <= x[j] <= u[j], (2) * * where L[p] <= U[p] and l[j] <= u[j] for all a[p,j] != 0, to compute * implied bounds of columns (variables x[j]) in this row. * * The routine stores implied column bounds l'[j] and u'[j] in column * descriptors (NPPCOL); it does not change current column bounds l[j] * and u[j]. (Implied column bounds can be then used to strengthen the * current column bounds; see the routines npp_implied_lower and * npp_implied_upper). * * ALGORITHM * * Current column bounds (2) define implied lower and upper bounds of * row (1) as follows: * * L'[p] = inf sum a[p,j] x[j] = * j * (3) * = sum a[p,j] l[j] + sum a[p,j] u[j], * j in Jp j in Jn * * U'[p] = sup sum a[p,j] x[j] = * (4) * = sum a[p,j] u[j] + sum a[p,j] l[j], * j in Jp j in Jn * * Jp = {j: a[p,j] > 0}, Jn = {j: a[p,j] < 0}. (5) * * (Note that bounds of all columns in row p are assumed to be correct, * so L'[p] <= U'[p].) * * If L[p] > L'[p] and/or U[p] < U'[p], the lower and/or upper bound of * row (1) can be active, in which case such row defines implied bounds * of its variables. * * Let x[k] be some variable having in row (1) coefficient a[p,k] != 0. * Consider a case when row lower bound can be active (L[p] > L'[p]): * * sum a[p,j] x[j] >= L[p] ==> * j * * sum a[p,j] x[j] + a[p,k] x[k] >= L[p] ==> * j!=k * (6) * a[p,k] x[k] >= L[p] - sum a[p,j] x[j] ==> * j!=k * * a[p,k] x[k] >= L[p,k], * * where * * L[p,k] = inf(L[p] - sum a[p,j] x[j]) = * j!=k * * = L[p] - sup sum a[p,j] x[j] = (7) * j!=k * * = L[p] - sum a[p,j] u[j] - sum a[p,j] l[j]. * j in Jp\{k} j in Jn\{k} * * Thus: * * x[k] >= l'[k] = L[p,k] / a[p,k], if a[p,k] > 0, (8) * * x[k] <= u'[k] = L[p,k] / a[p,k], if a[p,k] < 0. (9) * * where l'[k] and u'[k] are implied lower and upper bounds of variable * x[k], resp. * * Now consider a similar case when row upper bound can be active * (U[p] < U'[p]): * * sum a[p,j] x[j] <= U[p] ==> * j * * sum a[p,j] x[j] + a[p,k] x[k] <= U[p] ==> * j!=k * (10) * a[p,k] x[k] <= U[p] - sum a[p,j] x[j] ==> * j!=k * * a[p,k] x[k] <= U[p,k], * * where: * * U[p,k] = sup(U[p] - sum a[p,j] x[j]) = * j!=k * * = U[p] - inf sum a[p,j] x[j] = (11) * j!=k * * = U[p] - sum a[p,j] l[j] - sum a[p,j] u[j]. * j in Jp\{k} j in Jn\{k} * * Thus: * * x[k] <= u'[k] = U[p,k] / a[p,k], if a[p,k] > 0, (12) * * x[k] >= l'[k] = U[p,k] / a[p,k], if a[p,k] < 0. (13) * * Note that in formulae (8), (9), (12), and (13) coefficient a[p,k] * must not be too small in magnitude relatively to other non-zero * coefficients in row (1), i.e. the following condition must hold: * * |a[p,k]| >= eps * max(1, |a[p,j]|), (14) * j * * where eps is a relative tolerance for constraint coefficients. * Otherwise the implied column bounds can be numerical inreliable. For * example, using formula (8) for the following inequality constraint: * * 1e-12 x1 - x2 - x3 >= 0, * * where x1 >= -1, x2, x3, >= 0, may lead to numerically unreliable * conclusion that x1 >= 0. * * Using formulae (8), (9), (12), and (13) to compute implied bounds * for one variable requires |J| operations, where J = {j: a[p,j] != 0}, * because this needs computing L[p,k] and U[p,k]. Thus, computing * implied bounds for all variables in row (1) would require |J|^2 * operations, that is not a good technique. However, the total number * of operations can be reduced to |J| as follows. * * Let a[p,k] > 0. Then from (7) and (11) we have: * * L[p,k] = L[p] - (U'[p] - a[p,k] u[k]) = * * = L[p] - U'[p] + a[p,k] u[k], * * U[p,k] = U[p] - (L'[p] - a[p,k] l[k]) = * * = U[p] - L'[p] + a[p,k] l[k], * * where L'[p] and U'[p] are implied row lower and upper bounds defined * by formulae (3) and (4). Substituting these expressions into (8) and * (12) gives: * * l'[k] = L[p,k] / a[p,k] = u[k] + (L[p] - U'[p]) / a[p,k], (15) * * u'[k] = U[p,k] / a[p,k] = l[k] + (U[p] - L'[p]) / a[p,k]. (16) * * Similarly, if a[p,k] < 0, according to (7) and (11) we have: * * L[p,k] = L[p] - (U'[p] - a[p,k] l[k]) = * * = L[p] - U'[p] + a[p,k] l[k], * * U[p,k] = U[p] - (L'[p] - a[p,k] u[k]) = * * = U[p] - L'[p] + a[p,k] u[k], * * and substituting these expressions into (8) and (12) gives: * * l'[k] = U[p,k] / a[p,k] = u[k] + (U[p] - L'[p]) / a[p,k], (17) * * u'[k] = L[p,k] / a[p,k] = l[k] + (L[p] - U'[p]) / a[p,k]. (18) * * Note that formulae (15)-(18) can be used only if L'[p] and U'[p] * exist. However, if for some variable x[j] it happens that l[j] = -oo * and/or u[j] = +oo, values of L'[p] (if a[p,j] > 0) and/or U'[p] (if * a[p,j] < 0) are undefined. Consider, therefore, the most general * situation, when some column bounds (2) may not exist. * * Let: * * J' = {j : (a[p,j] > 0 and l[j] = -oo) or * (19) * (a[p,j] < 0 and u[j] = +oo)}. * * Then (assuming that row upper bound U[p] can be active) the following * three cases are possible: * * 1) |J'| = 0. In this case L'[p] exists, thus, for all variables x[j] * in row (1) we can use formulae (16) and (17); * * 2) J' = {k}. In this case L'[p] = -oo, however, U[p,k] (11) exists, * so for variable x[k] we can use formulae (12) and (13). Note that * for all other variables x[j] (j != k) l'[j] = -oo (if a[p,j] < 0) * or u'[j] = +oo (if a[p,j] > 0); * * 3) |J'| > 1. In this case for all variables x[j] in row [1] we have * l'[j] = -oo (if a[p,j] < 0) or u'[j] = +oo (if a[p,j] > 0). * * Similarly, let: * * J'' = {j : (a[p,j] > 0 and u[j] = +oo) or * (20) * (a[p,j] < 0 and l[j] = -oo)}. * * Then (assuming that row lower bound L[p] can be active) the following * three cases are possible: * * 1) |J''| = 0. In this case U'[p] exists, thus, for all variables x[j] * in row (1) we can use formulae (15) and (18); * * 2) J'' = {k}. In this case U'[p] = +oo, however, L[p,k] (7) exists, * so for variable x[k] we can use formulae (8) and (9). Note that * for all other variables x[j] (j != k) l'[j] = -oo (if a[p,j] > 0) * or u'[j] = +oo (if a[p,j] < 0); * * 3) |J''| > 1. In this case for all variables x[j] in row (1) we have * l'[j] = -oo (if a[p,j] > 0) or u'[j] = +oo (if a[p,j] < 0). */ void npp_implied_bounds(NPP *npp, NPPROW *p) { NPPAIJ *apj, *apk; double big, eps, temp; xassert(npp == npp); /* initialize implied bounds for all variables and determine maximal magnitude of row coefficients a[p,j] */ big = 1.0; for (apj = p->ptr; apj != NULL; apj = apj->r_next) { apj->col->ll.ll = -DBL_MAX, apj->col->uu.uu = +DBL_MAX; if (big < fabs(apj->val)) big = fabs(apj->val); } eps = 1e-6 * big; /* process row lower bound (assuming that it can be active) */ if (p->lb != -DBL_MAX) { apk = NULL; for (apj = p->ptr; apj != NULL; apj = apj->r_next) { if (apj->val > 0.0 && apj->col->ub == +DBL_MAX || apj->val < 0.0 && apj->col->lb == -DBL_MAX) { if (apk == NULL) apk = apj; else goto skip1; } } /* if a[p,k] = NULL then |J'| = 0 else J' = { k } */ temp = p->lb; for (apj = p->ptr; apj != NULL; apj = apj->r_next) { if (apj == apk) /* skip a[p,k] */; else if (apj->val > 0.0) temp -= apj->val * apj->col->ub; else /* apj->val < 0.0 */ temp -= apj->val * apj->col->lb; } /* compute column implied bounds */ if (apk == NULL) { /* temp = L[p] - U'[p] */ for (apj = p->ptr; apj != NULL; apj = apj->r_next) { if (apj->val >= +eps) { /* l'[j] := u[j] + (L[p] - U'[p]) / a[p,j] */ apj->col->ll.ll = apj->col->ub + temp / apj->val; } else if (apj->val <= -eps) { /* u'[j] := l[j] + (L[p] - U'[p]) / a[p,j] */ apj->col->uu.uu = apj->col->lb + temp / apj->val; } } } else { /* temp = L[p,k] */ if (apk->val >= +eps) { /* l'[k] := L[p,k] / a[p,k] */ apk->col->ll.ll = temp / apk->val; } else if (apk->val <= -eps) { /* u'[k] := L[p,k] / a[p,k] */ apk->col->uu.uu = temp / apk->val; } } skip1: ; } /* process row upper bound (assuming that it can be active) */ if (p->ub != +DBL_MAX) { apk = NULL; for (apj = p->ptr; apj != NULL; apj = apj->r_next) { if (apj->val > 0.0 && apj->col->lb == -DBL_MAX || apj->val < 0.0 && apj->col->ub == +DBL_MAX) { if (apk == NULL) apk = apj; else goto skip2; } } /* if a[p,k] = NULL then |J''| = 0 else J'' = { k } */ temp = p->ub; for (apj = p->ptr; apj != NULL; apj = apj->r_next) { if (apj == apk) /* skip a[p,k] */; else if (apj->val > 0.0) temp -= apj->val * apj->col->lb; else /* apj->val < 0.0 */ temp -= apj->val * apj->col->ub; } /* compute column implied bounds */ if (apk == NULL) { /* temp = U[p] - L'[p] */ for (apj = p->ptr; apj != NULL; apj = apj->r_next) { if (apj->val >= +eps) { /* u'[j] := l[j] + (U[p] - L'[p]) / a[p,j] */ apj->col->uu.uu = apj->col->lb + temp / apj->val; } else if (apj->val <= -eps) { /* l'[j] := u[j] + (U[p] - L'[p]) / a[p,j] */ apj->col->ll.ll = apj->col->ub + temp / apj->val; } } } else { /* temp = U[p,k] */ if (apk->val >= +eps) { /* u'[k] := U[p,k] / a[p,k] */ apk->col->uu.uu = temp / apk->val; } else if (apk->val <= -eps) { /* l'[k] := U[p,k] / a[p,k] */ apk->col->ll.ll = temp / apk->val; } } skip2: ; } return; } /* eof */ sources_5316/external/glpk/glprng02.c0000644000176700017670000000440711401660400016276 0ustar paulpaul/* glprng02.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glprng.h" #define xfault xerror /*********************************************************************** * NAME * * rng_unif_01 - obtain pseudo-random number in the range [0, 1] * * SYNOPSIS * * #include "glprng.h" * double rng_unif_01(RNG *rand); * * RETURNS * * The routine rng_unif_01 returns a next pseudo-random number which is * uniformly distributed in the range [0, 1]. */ double rng_unif_01(RNG *rand) { double x; x = (double)rng_next_rand(rand) / 2147483647.0; xassert(0.0 <= x && x <= 1.0); return x; } /*********************************************************************** * NAME * * rng_uniform - obtain pseudo-random number in the range [a, b] * * SYNOPSIS * * #include "glprng.h" * double rng_uniform(RNG *rand, double a, double b); * * RETURNS * * The routine rng_uniform returns a next pseudo-random number which is * uniformly distributed in the range [a, b]. */ double rng_uniform(RNG *rand, double a, double b) { double x; if (a >= b) xfault("rng_uniform: a = %g, b = %g; invalid range\n", a, b); x = rng_unif_01(rand); x = a * (1.0 - x) + b * x; xassert(a <= x && x <= b); return x; } /* eof */ sources_5316/external/glpk/glpapi01.c0000644000176700017670000014724511401660400016270 0ustar paulpaul/* glpapi01.c (problem creating and modifying routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /* CAUTION: DO NOT CHANGE THE LIMITS BELOW */ #define M_MAX 100000000 /* = 100*10^6 */ /* maximal number of rows in the problem object */ #define N_MAX 100000000 /* = 100*10^6 */ /* maximal number of columns in the problem object */ #define NNZ_MAX 500000000 /* = 500*10^6 */ /* maximal number of constraint coefficients in the problem object */ /*********************************************************************** * NAME * * glp_create_prob - create problem object * * SYNOPSIS * * glp_prob *glp_create_prob(void); * * DESCRIPTION * * The routine glp_create_prob creates a new problem object, which is * initially "empty", i.e. has no rows and columns. * * RETURNS * * The routine returns a pointer to the object created, which should be * used in any subsequent operations on this object. */ static void create_prob(glp_prob *lp) { lp->magic = GLP_PROB_MAGIC; lp->pool = dmp_create_pool(); #if 0 /* 17/XI-2009 */ lp->cps = xmalloc(sizeof(struct LPXCPS)); lpx_reset_parms(lp); #else lp->parms = NULL; #endif lp->tree = NULL; #if 0 lp->lwa = 0; lp->cwa = NULL; #endif /* LP/MIP data */ lp->name = NULL; lp->obj = NULL; lp->dir = GLP_MIN; lp->c0 = 0.0; lp->m_max = 100; lp->n_max = 200; lp->m = lp->n = 0; lp->nnz = 0; lp->row = xcalloc(1+lp->m_max, sizeof(GLPROW *)); lp->col = xcalloc(1+lp->n_max, sizeof(GLPCOL *)); lp->r_tree = lp->c_tree = NULL; /* basis factorization */ lp->valid = 0; lp->head = xcalloc(1+lp->m_max, sizeof(int)); lp->bfcp = NULL; lp->bfd = NULL; /* basic solution (LP) */ lp->pbs_stat = lp->dbs_stat = GLP_UNDEF; lp->obj_val = 0.0; lp->it_cnt = 0; lp->some = 0; /* interior-point solution (LP) */ lp->ipt_stat = GLP_UNDEF; lp->ipt_obj = 0.0; /* integer solution (MIP) */ lp->mip_stat = GLP_UNDEF; lp->mip_obj = 0.0; return; } glp_prob *glp_create_prob(void) { glp_prob *lp; lp = xmalloc(sizeof(glp_prob)); create_prob(lp); return lp; } /*********************************************************************** * NAME * * glp_set_prob_name - assign (change) problem name * * SYNOPSIS * * void glp_set_prob_name(glp_prob *lp, const char *name); * * DESCRIPTION * * The routine glp_set_prob_name assigns a given symbolic name (1 up to * 255 characters) to the specified problem object. * * If the parameter name is NULL or empty string, the routine erases an * existing symbolic name of the problem object. */ void glp_set_prob_name(glp_prob *lp, const char *name) { glp_tree *tree = lp->tree; if (tree != NULL && tree->reason != 0) xerror("glp_set_prob_name: operation not allowed\n"); if (lp->name != NULL) { dmp_free_atom(lp->pool, lp->name, strlen(lp->name)+1); lp->name = NULL; } if (!(name == NULL || name[0] == '\0')) { int k; for (k = 0; name[k] != '\0'; k++) { if (k == 256) xerror("glp_set_prob_name: problem name too long\n"); if (iscntrl((unsigned char)name[k])) xerror("glp_set_prob_name: problem name contains invalid" " character(s)\n"); } lp->name = dmp_get_atom(lp->pool, strlen(name)+1); strcpy(lp->name, name); } return; } /*********************************************************************** * NAME * * glp_set_obj_name - assign (change) objective function name * * SYNOPSIS * * void glp_set_obj_name(glp_prob *lp, const char *name); * * DESCRIPTION * * The routine glp_set_obj_name assigns a given symbolic name (1 up to * 255 characters) to the objective function of the specified problem * object. * * If the parameter name is NULL or empty string, the routine erases an * existing name of the objective function. */ void glp_set_obj_name(glp_prob *lp, const char *name) { glp_tree *tree = lp->tree; if (tree != NULL && tree->reason != 0) xerror("glp_set_obj_name: operation not allowed\n"); if (lp->obj != NULL) { dmp_free_atom(lp->pool, lp->obj, strlen(lp->obj)+1); lp->obj = NULL; } if (!(name == NULL || name[0] == '\0')) { int k; for (k = 0; name[k] != '\0'; k++) { if (k == 256) xerror("glp_set_obj_name: objective name too long\n"); if (iscntrl((unsigned char)name[k])) xerror("glp_set_obj_name: objective name contains invali" "d character(s)\n"); } lp->obj = dmp_get_atom(lp->pool, strlen(name)+1); strcpy(lp->obj, name); } return; } /*********************************************************************** * NAME * * glp_set_obj_dir - set (change) optimization direction flag * * SYNOPSIS * * void glp_set_obj_dir(glp_prob *lp, int dir); * * DESCRIPTION * * The routine glp_set_obj_dir sets (changes) optimization direction * flag (i.e. "sense" of the objective function) as specified by the * parameter dir: * * GLP_MIN - minimization; * GLP_MAX - maximization. */ void glp_set_obj_dir(glp_prob *lp, int dir) { glp_tree *tree = lp->tree; if (tree != NULL && tree->reason != 0) xerror("glp_set_obj_dir: operation not allowed\n"); if (!(dir == GLP_MIN || dir == GLP_MAX)) xerror("glp_set_obj_dir: dir = %d; invalid direction flag\n", dir); lp->dir = dir; return; } /*********************************************************************** * NAME * * glp_add_rows - add new rows to problem object * * SYNOPSIS * * int glp_add_rows(glp_prob *lp, int nrs); * * DESCRIPTION * * The routine glp_add_rows adds nrs rows (constraints) to the specified * problem object. New rows are always added to the end of the row list, * so the ordinal numbers of existing rows remain unchanged. * * Being added each new row is initially free (unbounded) and has empty * list of the constraint coefficients. * * RETURNS * * The routine glp_add_rows returns the ordinal number of the first new * row added to the problem object. */ int glp_add_rows(glp_prob *lp, int nrs) { glp_tree *tree = lp->tree; GLPROW *row; int m_new, i; /* determine new number of rows */ if (nrs < 1) xerror("glp_add_rows: nrs = %d; invalid number of rows\n", nrs); if (nrs > M_MAX - lp->m) xerror("glp_add_rows: nrs = %d; too many rows\n", nrs); m_new = lp->m + nrs; /* increase the room, if necessary */ if (lp->m_max < m_new) { GLPROW **save = lp->row; while (lp->m_max < m_new) { lp->m_max += lp->m_max; xassert(lp->m_max > 0); } lp->row = xcalloc(1+lp->m_max, sizeof(GLPROW *)); memcpy(&lp->row[1], &save[1], lp->m * sizeof(GLPROW *)); xfree(save); /* do not forget about the basis header */ xfree(lp->head); lp->head = xcalloc(1+lp->m_max, sizeof(int)); } /* add new rows to the end of the row list */ for (i = lp->m+1; i <= m_new; i++) { /* create row descriptor */ lp->row[i] = row = dmp_get_atom(lp->pool, sizeof(GLPROW)); row->i = i; row->name = NULL; row->node = NULL; #if 1 /* 20/IX-2008 */ row->level = 0; row->origin = 0; row->klass = 0; if (tree != NULL) { switch (tree->reason) { case 0: break; case GLP_IROWGEN: xassert(tree->curr != NULL); row->level = tree->curr->level; row->origin = GLP_RF_LAZY; break; case GLP_ICUTGEN: xassert(tree->curr != NULL); row->level = tree->curr->level; row->origin = GLP_RF_CUT; break; default: xassert(tree != tree); } } #endif row->type = GLP_FR; row->lb = row->ub = 0.0; row->ptr = NULL; row->rii = 1.0; row->stat = GLP_BS; #if 0 row->bind = -1; #else row->bind = 0; #endif row->prim = row->dual = 0.0; row->pval = row->dval = 0.0; row->mipx = 0.0; } /* set new number of rows */ lp->m = m_new; /* invalidate the basis factorization */ lp->valid = 0; #if 1 if (tree != NULL && tree->reason != 0) tree->reopt = 1; #endif /* return the ordinal number of the first row added */ return m_new - nrs + 1; } /*********************************************************************** * NAME * * glp_add_cols - add new columns to problem object * * SYNOPSIS * * int glp_add_cols(glp_prob *lp, int ncs); * * DESCRIPTION * * The routine glp_add_cols adds ncs columns (structural variables) to * the specified problem object. New columns are always added to the end * of the column list, so the ordinal numbers of existing columns remain * unchanged. * * Being added each new column is initially fixed at zero and has empty * list of the constraint coefficients. * * RETURNS * * The routine glp_add_cols returns the ordinal number of the first new * column added to the problem object. */ int glp_add_cols(glp_prob *lp, int ncs) { glp_tree *tree = lp->tree; GLPCOL *col; int n_new, j; if (tree != NULL && tree->reason != 0) xerror("glp_add_cols: operation not allowed\n"); /* determine new number of columns */ if (ncs < 1) xerror("glp_add_cols: ncs = %d; invalid number of columns\n", ncs); if (ncs > N_MAX - lp->n) xerror("glp_add_cols: ncs = %d; too many columns\n", ncs); n_new = lp->n + ncs; /* increase the room, if necessary */ if (lp->n_max < n_new) { GLPCOL **save = lp->col; while (lp->n_max < n_new) { lp->n_max += lp->n_max; xassert(lp->n_max > 0); } lp->col = xcalloc(1+lp->n_max, sizeof(GLPCOL *)); memcpy(&lp->col[1], &save[1], lp->n * sizeof(GLPCOL *)); xfree(save); } /* add new columns to the end of the column list */ for (j = lp->n+1; j <= n_new; j++) { /* create column descriptor */ lp->col[j] = col = dmp_get_atom(lp->pool, sizeof(GLPCOL)); col->j = j; col->name = NULL; col->node = NULL; col->kind = GLP_CV; col->type = GLP_FX; col->lb = col->ub = 0.0; col->coef = 0.0; col->ptr = NULL; col->sjj = 1.0; col->stat = GLP_NS; #if 0 col->bind = -1; #else col->bind = 0; /* the basis may remain valid */ #endif col->prim = col->dual = 0.0; col->pval = col->dval = 0.0; col->mipx = 0.0; } /* set new number of columns */ lp->n = n_new; /* return the ordinal number of the first column added */ return n_new - ncs + 1; } /*********************************************************************** * NAME * * glp_set_row_name - assign (change) row name * * SYNOPSIS * * void glp_set_row_name(glp_prob *lp, int i, const char *name); * * DESCRIPTION * * The routine glp_set_row_name assigns a given symbolic name (1 up to * 255 characters) to i-th row (auxiliary variable) of the specified * problem object. * * If the parameter name is NULL or empty string, the routine erases an * existing name of i-th row. */ void glp_set_row_name(glp_prob *lp, int i, const char *name) { glp_tree *tree = lp->tree; GLPROW *row; if (!(1 <= i && i <= lp->m)) xerror("glp_set_row_name: i = %d; row number out of range\n", i); row = lp->row[i]; if (tree != NULL && tree->reason != 0) { xassert(tree->curr != NULL); xassert(row->level == tree->curr->level); } if (row->name != NULL) { if (row->node != NULL) { xassert(lp->r_tree != NULL); avl_delete_node(lp->r_tree, row->node); row->node = NULL; } dmp_free_atom(lp->pool, row->name, strlen(row->name)+1); row->name = NULL; } if (!(name == NULL || name[0] == '\0')) { int k; for (k = 0; name[k] != '\0'; k++) { if (k == 256) xerror("glp_set_row_name: i = %d; row name too long\n", i); if (iscntrl((unsigned char)name[k])) xerror("glp_set_row_name: i = %d: row name contains inva" "lid character(s)\n", i); } row->name = dmp_get_atom(lp->pool, strlen(name)+1); strcpy(row->name, name); if (lp->r_tree != NULL) { xassert(row->node == NULL); row->node = avl_insert_node(lp->r_tree, row->name); avl_set_node_link(row->node, row); } } return; } /*********************************************************************** * NAME * * glp_set_col_name - assign (change) column name * * SYNOPSIS * * void glp_set_col_name(glp_prob *lp, int j, const char *name); * * DESCRIPTION * * The routine glp_set_col_name assigns a given symbolic name (1 up to * 255 characters) to j-th column (structural variable) of the specified * problem object. * * If the parameter name is NULL or empty string, the routine erases an * existing name of j-th column. */ void glp_set_col_name(glp_prob *lp, int j, const char *name) { glp_tree *tree = lp->tree; GLPCOL *col; if (tree != NULL && tree->reason != 0) xerror("glp_set_col_name: operation not allowed\n"); if (!(1 <= j && j <= lp->n)) xerror("glp_set_col_name: j = %d; column number out of range\n" , j); col = lp->col[j]; if (col->name != NULL) { if (col->node != NULL) { xassert(lp->c_tree != NULL); avl_delete_node(lp->c_tree, col->node); col->node = NULL; } dmp_free_atom(lp->pool, col->name, strlen(col->name)+1); col->name = NULL; } if (!(name == NULL || name[0] == '\0')) { int k; for (k = 0; name[k] != '\0'; k++) { if (k == 256) xerror("glp_set_col_name: j = %d; column name too long\n" , j); if (iscntrl((unsigned char)name[k])) xerror("glp_set_col_name: j = %d: column name contains i" "nvalid character(s)\n", j); } col->name = dmp_get_atom(lp->pool, strlen(name)+1); strcpy(col->name, name); if (lp->c_tree != NULL && col->name != NULL) { xassert(col->node == NULL); col->node = avl_insert_node(lp->c_tree, col->name); avl_set_node_link(col->node, col); } } return; } /*********************************************************************** * NAME * * glp_set_row_bnds - set (change) row bounds * * SYNOPSIS * * void glp_set_row_bnds(glp_prob *lp, int i, int type, double lb, * double ub); * * DESCRIPTION * * The routine glp_set_row_bnds sets (changes) the type and bounds of * i-th row (auxiliary variable) of the specified problem object. * * Parameters type, lb, and ub specify the type, lower bound, and upper * bound, respectively, as follows: * * Type Bounds Comments * ------------------------------------------------------ * GLP_FR -inf < x < +inf Free variable * GLP_LO lb <= x < +inf Variable with lower bound * GLP_UP -inf < x <= ub Variable with upper bound * GLP_DB lb <= x <= ub Double-bounded variable * GLP_FX x = lb Fixed variable * * where x is the auxiliary variable associated with i-th row. * * If the row has no lower bound, the parameter lb is ignored. If the * row has no upper bound, the parameter ub is ignored. If the row is * an equality constraint (i.e. the corresponding auxiliary variable is * of fixed type), only the parameter lb is used while the parameter ub * is ignored. */ void glp_set_row_bnds(glp_prob *lp, int i, int type, double lb, double ub) { GLPROW *row; if (!(1 <= i && i <= lp->m)) xerror("glp_set_row_bnds: i = %d; row number out of range\n", i); row = lp->row[i]; row->type = type; switch (type) { case GLP_FR: row->lb = row->ub = 0.0; if (row->stat != GLP_BS) row->stat = GLP_NF; break; case GLP_LO: row->lb = lb, row->ub = 0.0; if (row->stat != GLP_BS) row->stat = GLP_NL; break; case GLP_UP: row->lb = 0.0, row->ub = ub; if (row->stat != GLP_BS) row->stat = GLP_NU; break; case GLP_DB: row->lb = lb, row->ub = ub; if (!(row->stat == GLP_BS || row->stat == GLP_NL || row->stat == GLP_NU)) row->stat = (fabs(lb) <= fabs(ub) ? GLP_NL : GLP_NU); break; case GLP_FX: row->lb = row->ub = lb; if (row->stat != GLP_BS) row->stat = GLP_NS; break; default: xerror("glp_set_row_bnds: i = %d; type = %d; invalid row ty" "pe\n", i, type); } return; } /*********************************************************************** * NAME * * glp_set_col_bnds - set (change) column bounds * * SYNOPSIS * * void glp_set_col_bnds(glp_prob *lp, int j, int type, double lb, * double ub); * * DESCRIPTION * * The routine glp_set_col_bnds sets (changes) the type and bounds of * j-th column (structural variable) of the specified problem object. * * Parameters type, lb, and ub specify the type, lower bound, and upper * bound, respectively, as follows: * * Type Bounds Comments * ------------------------------------------------------ * GLP_FR -inf < x < +inf Free variable * GLP_LO lb <= x < +inf Variable with lower bound * GLP_UP -inf < x <= ub Variable with upper bound * GLP_DB lb <= x <= ub Double-bounded variable * GLP_FX x = lb Fixed variable * * where x is the structural variable associated with j-th column. * * If the column has no lower bound, the parameter lb is ignored. If the * column has no upper bound, the parameter ub is ignored. If the column * is of fixed type, only the parameter lb is used while the parameter * ub is ignored. */ void glp_set_col_bnds(glp_prob *lp, int j, int type, double lb, double ub) { GLPCOL *col; if (!(1 <= j && j <= lp->n)) xerror("glp_set_col_bnds: j = %d; column number out of range\n" , j); col = lp->col[j]; col->type = type; switch (type) { case GLP_FR: col->lb = col->ub = 0.0; if (col->stat != GLP_BS) col->stat = GLP_NF; break; case GLP_LO: col->lb = lb, col->ub = 0.0; if (col->stat != GLP_BS) col->stat = GLP_NL; break; case GLP_UP: col->lb = 0.0, col->ub = ub; if (col->stat != GLP_BS) col->stat = GLP_NU; break; case GLP_DB: col->lb = lb, col->ub = ub; if (!(col->stat == GLP_BS || col->stat == GLP_NL || col->stat == GLP_NU)) col->stat = (fabs(lb) <= fabs(ub) ? GLP_NL : GLP_NU); break; case GLP_FX: col->lb = col->ub = lb; if (col->stat != GLP_BS) col->stat = GLP_NS; break; default: xerror("glp_set_col_bnds: j = %d; type = %d; invalid column" " type\n", j, type); } return; } /*********************************************************************** * NAME * * glp_set_obj_coef - set (change) obj. coefficient or constant term * * SYNOPSIS * * void glp_set_obj_coef(glp_prob *lp, int j, double coef); * * DESCRIPTION * * The routine glp_set_obj_coef sets (changes) objective coefficient at * j-th column (structural variable) of the specified problem object. * * If the parameter j is 0, the routine sets (changes) the constant term * ("shift") of the objective function. */ void glp_set_obj_coef(glp_prob *lp, int j, double coef) { glp_tree *tree = lp->tree; if (tree != NULL && tree->reason != 0) xerror("glp_set_obj_coef: operation not allowed\n"); if (!(0 <= j && j <= lp->n)) xerror("glp_set_obj_coef: j = %d; column number out of range\n" , j); if (j == 0) lp->c0 = coef; else lp->col[j]->coef = coef; return; } /*********************************************************************** * NAME * * glp_set_mat_row - set (replace) row of the constraint matrix * * SYNOPSIS * * void glp_set_mat_row(glp_prob *lp, int i, int len, const int ind[], * const double val[]); * * DESCRIPTION * * The routine glp_set_mat_row stores (replaces) the contents of i-th * row of the constraint matrix of the specified problem object. * * Column indices and numeric values of new row elements must be placed * in locations ind[1], ..., ind[len] and val[1], ..., val[len], where * 0 <= len <= n is the new length of i-th row, n is the current number * of columns in the problem object. Elements with identical column * indices are not allowed. Zero elements are allowed, but they are not * stored in the constraint matrix. * * If the parameter len is zero, the parameters ind and/or val can be * specified as NULL. */ void glp_set_mat_row(glp_prob *lp, int i, int len, const int ind[], const double val[]) { glp_tree *tree = lp->tree; GLPROW *row; GLPCOL *col; GLPAIJ *aij, *next; int j, k; /* obtain pointer to i-th row */ if (!(1 <= i && i <= lp->m)) xerror("glp_set_mat_row: i = %d; row number out of range\n", i); row = lp->row[i]; if (tree != NULL && tree->reason != 0) { xassert(tree->curr != NULL); xassert(row->level == tree->curr->level); } /* remove all existing elements from i-th row */ while (row->ptr != NULL) { /* take next element in the row */ aij = row->ptr; /* remove the element from the row list */ row->ptr = aij->r_next; /* obtain pointer to corresponding column */ col = aij->col; /* remove the element from the column list */ if (aij->c_prev == NULL) col->ptr = aij->c_next; else aij->c_prev->c_next = aij->c_next; if (aij->c_next == NULL) ; else aij->c_next->c_prev = aij->c_prev; /* return the element to the memory pool */ dmp_free_atom(lp->pool, aij, sizeof(GLPAIJ)), lp->nnz--; /* if the corresponding column is basic, invalidate the basis factorization */ if (col->stat == GLP_BS) lp->valid = 0; } /* store new contents of i-th row */ if (!(0 <= len && len <= lp->n)) xerror("glp_set_mat_row: i = %d; len = %d; invalid row length " "\n", i, len); if (len > NNZ_MAX - lp->nnz) xerror("glp_set_mat_row: i = %d; len = %d; too many constraint" " coefficients\n", i, len); for (k = 1; k <= len; k++) { /* take number j of corresponding column */ j = ind[k]; /* obtain pointer to j-th column */ if (!(1 <= j && j <= lp->n)) xerror("glp_set_mat_row: i = %d; ind[%d] = %d; column index" " out of range\n", i, k, j); col = lp->col[j]; /* if there is element with the same column index, it can only be found in the beginning of j-th column list */ if (col->ptr != NULL && col->ptr->row->i == i) xerror("glp_set_mat_row: i = %d; ind[%d] = %d; duplicate co" "lumn indices not allowed\n", i, k, j); /* create new element */ aij = dmp_get_atom(lp->pool, sizeof(GLPAIJ)), lp->nnz++; aij->row = row; aij->col = col; aij->val = val[k]; /* add the new element to the beginning of i-th row and j-th column lists */ aij->r_prev = NULL; aij->r_next = row->ptr; aij->c_prev = NULL; aij->c_next = col->ptr; if (aij->r_next != NULL) aij->r_next->r_prev = aij; if (aij->c_next != NULL) aij->c_next->c_prev = aij; row->ptr = col->ptr = aij; /* if the corresponding column is basic, invalidate the basis factorization */ if (col->stat == GLP_BS && aij->val != 0.0) lp->valid = 0; } /* remove zero elements from i-th row */ for (aij = row->ptr; aij != NULL; aij = next) { next = aij->r_next; if (aij->val == 0.0) { /* remove the element from the row list */ if (aij->r_prev == NULL) row->ptr = next; else aij->r_prev->r_next = next; if (next == NULL) ; else next->r_prev = aij->r_prev; /* remove the element from the column list */ xassert(aij->c_prev == NULL); aij->col->ptr = aij->c_next; if (aij->c_next != NULL) aij->c_next->c_prev = NULL; /* return the element to the memory pool */ dmp_free_atom(lp->pool, aij, sizeof(GLPAIJ)), lp->nnz--; } } return; } /*********************************************************************** * NAME * * glp_set_mat_col - set (replace) column of the constraint matrix * * SYNOPSIS * * void glp_set_mat_col(glp_prob *lp, int j, int len, const int ind[], * const double val[]); * * DESCRIPTION * * The routine glp_set_mat_col stores (replaces) the contents of j-th * column of the constraint matrix of the specified problem object. * * Row indices and numeric values of new column elements must be placed * in locations ind[1], ..., ind[len] and val[1], ..., val[len], where * 0 <= len <= m is the new length of j-th column, m is the current * number of rows in the problem object. Elements with identical column * indices are not allowed. Zero elements are allowed, but they are not * stored in the constraint matrix. * * If the parameter len is zero, the parameters ind and/or val can be * specified as NULL. */ void glp_set_mat_col(glp_prob *lp, int j, int len, const int ind[], const double val[]) { glp_tree *tree = lp->tree; GLPROW *row; GLPCOL *col; GLPAIJ *aij, *next; int i, k; if (tree != NULL && tree->reason != 0) xerror("glp_set_mat_col: operation not allowed\n"); /* obtain pointer to j-th column */ if (!(1 <= j && j <= lp->n)) xerror("glp_set_mat_col: j = %d; column number out of range\n", j); col = lp->col[j]; /* remove all existing elements from j-th column */ while (col->ptr != NULL) { /* take next element in the column */ aij = col->ptr; /* remove the element from the column list */ col->ptr = aij->c_next; /* obtain pointer to corresponding row */ row = aij->row; /* remove the element from the row list */ if (aij->r_prev == NULL) row->ptr = aij->r_next; else aij->r_prev->r_next = aij->r_next; if (aij->r_next == NULL) ; else aij->r_next->r_prev = aij->r_prev; /* return the element to the memory pool */ dmp_free_atom(lp->pool, aij, sizeof(GLPAIJ)), lp->nnz--; } /* store new contents of j-th column */ if (!(0 <= len && len <= lp->m)) xerror("glp_set_mat_col: j = %d; len = %d; invalid column leng" "th\n", j, len); if (len > NNZ_MAX - lp->nnz) xerror("glp_set_mat_col: j = %d; len = %d; too many constraint" " coefficients\n", j, len); for (k = 1; k <= len; k++) { /* take number i of corresponding row */ i = ind[k]; /* obtain pointer to i-th row */ if (!(1 <= i && i <= lp->m)) xerror("glp_set_mat_col: j = %d; ind[%d] = %d; row index ou" "t of range\n", j, k, i); row = lp->row[i]; /* if there is element with the same row index, it can only be found in the beginning of i-th row list */ if (row->ptr != NULL && row->ptr->col->j == j) xerror("glp_set_mat_col: j = %d; ind[%d] = %d; duplicate ro" "w indices not allowed\n", j, k, i); /* create new element */ aij = dmp_get_atom(lp->pool, sizeof(GLPAIJ)), lp->nnz++; aij->row = row; aij->col = col; aij->val = val[k]; /* add the new element to the beginning of i-th row and j-th column lists */ aij->r_prev = NULL; aij->r_next = row->ptr; aij->c_prev = NULL; aij->c_next = col->ptr; if (aij->r_next != NULL) aij->r_next->r_prev = aij; if (aij->c_next != NULL) aij->c_next->c_prev = aij; row->ptr = col->ptr = aij; } /* remove zero elements from j-th column */ for (aij = col->ptr; aij != NULL; aij = next) { next = aij->c_next; if (aij->val == 0.0) { /* remove the element from the row list */ xassert(aij->r_prev == NULL); aij->row->ptr = aij->r_next; if (aij->r_next != NULL) aij->r_next->r_prev = NULL; /* remove the element from the column list */ if (aij->c_prev == NULL) col->ptr = next; else aij->c_prev->c_next = next; if (next == NULL) ; else next->c_prev = aij->c_prev; /* return the element to the memory pool */ dmp_free_atom(lp->pool, aij, sizeof(GLPAIJ)), lp->nnz--; } } /* if j-th column is basic, invalidate the basis factorization */ if (col->stat == GLP_BS) lp->valid = 0; return; } /*********************************************************************** * NAME * * glp_load_matrix - load (replace) the whole constraint matrix * * SYNOPSIS * * void glp_load_matrix(glp_prob *lp, int ne, const int ia[], * const int ja[], const double ar[]); * * DESCRIPTION * * The routine glp_load_matrix loads the constraint matrix passed in * the arrays ia, ja, and ar into the specified problem object. Before * loading the current contents of the constraint matrix is destroyed. * * Constraint coefficients (elements of the constraint matrix) must be * specified as triplets (ia[k], ja[k], ar[k]) for k = 1, ..., ne, * where ia[k] is the row index, ja[k] is the column index, ar[k] is a * numeric value of corresponding constraint coefficient. The parameter * ne specifies the total number of (non-zero) elements in the matrix * to be loaded. Coefficients with identical indices are not allowed. * Zero coefficients are allowed, however, they are not stored in the * constraint matrix. * * If the parameter ne is zero, the parameters ia, ja, and ar can be * specified as NULL. */ void glp_load_matrix(glp_prob *lp, int ne, const int ia[], const int ja[], const double ar[]) { glp_tree *tree = lp->tree; GLPROW *row; GLPCOL *col; GLPAIJ *aij, *next; int i, j, k; if (tree != NULL && tree->reason != 0) xerror("glp_load_matrix: operation not allowed\n"); /* clear the constraint matrix */ for (i = 1; i <= lp->m; i++) { row = lp->row[i]; while (row->ptr != NULL) { aij = row->ptr; row->ptr = aij->r_next; dmp_free_atom(lp->pool, aij, sizeof(GLPAIJ)), lp->nnz--; } } xassert(lp->nnz == 0); for (j = 1; j <= lp->n; j++) lp->col[j]->ptr = NULL; /* load the new contents of the constraint matrix and build its row lists */ if (ne < 0) xerror("glp_load_matrix: ne = %d; invalid number of constraint" " coefficients\n", ne); if (ne > NNZ_MAX) xerror("glp_load_matrix: ne = %d; too many constraint coeffici" "ents\n", ne); for (k = 1; k <= ne; k++) { /* take indices of new element */ i = ia[k], j = ja[k]; /* obtain pointer to i-th row */ if (!(1 <= i && i <= lp->m)) xerror("glp_load_matrix: ia[%d] = %d; row index out of rang" "e\n", k, i); row = lp->row[i]; /* obtain pointer to j-th column */ if (!(1 <= j && j <= lp->n)) xerror("glp_load_matrix: ja[%d] = %d; column index out of r" "ange\n", k, j); col = lp->col[j]; /* create new element */ aij = dmp_get_atom(lp->pool, sizeof(GLPAIJ)), lp->nnz++; aij->row = row; aij->col = col; aij->val = ar[k]; /* add the new element to the beginning of i-th row list */ aij->r_prev = NULL; aij->r_next = row->ptr; if (aij->r_next != NULL) aij->r_next->r_prev = aij; row->ptr = aij; } xassert(lp->nnz == ne); /* build column lists of the constraint matrix and check elements with identical indices */ for (i = 1; i <= lp->m; i++) { for (aij = lp->row[i]->ptr; aij != NULL; aij = aij->r_next) { /* obtain pointer to corresponding column */ col = aij->col; /* if there is element with identical indices, it can only be found in the beginning of j-th column list */ if (col->ptr != NULL && col->ptr->row->i == i) { for (k = 1; k <= ne; k++) if (ia[k] == i && ja[k] == col->j) break; xerror("glp_load_mat: ia[%d] = %d; ja[%d] = %d; duplicat" "e indices not allowed\n", k, i, k, col->j); } /* add the element to the beginning of j-th column list */ aij->c_prev = NULL; aij->c_next = col->ptr; if (aij->c_next != NULL) aij->c_next->c_prev = aij; col->ptr = aij; } } /* remove zero elements from the constraint matrix */ for (i = 1; i <= lp->m; i++) { row = lp->row[i]; for (aij = row->ptr; aij != NULL; aij = next) { next = aij->r_next; if (aij->val == 0.0) { /* remove the element from the row list */ if (aij->r_prev == NULL) row->ptr = next; else aij->r_prev->r_next = next; if (next == NULL) ; else next->r_prev = aij->r_prev; /* remove the element from the column list */ if (aij->c_prev == NULL) aij->col->ptr = aij->c_next; else aij->c_prev->c_next = aij->c_next; if (aij->c_next == NULL) ; else aij->c_next->c_prev = aij->c_prev; /* return the element to the memory pool */ dmp_free_atom(lp->pool, aij, sizeof(GLPAIJ)), lp->nnz--; } } } /* invalidate the basis factorization */ lp->valid = 0; return; } /*********************************************************************** * NAME * * glp_check_dup - check for duplicate elements in sparse matrix * * SYNOPSIS * * int glp_check_dup(int m, int n, int ne, const int ia[], * const int ja[]); * * DESCRIPTION * * The routine glp_check_dup checks for duplicate elements (that is, * elements with identical indices) in a sparse matrix specified in the * coordinate format. * * The parameters m and n specifies, respectively, the number of rows * and columns in the matrix, m >= 0, n >= 0. * * The parameter ne specifies the number of (structurally) non-zero * elements in the matrix, ne >= 0. * * Elements of the matrix are specified as doublets (ia[k],ja[k]) for * k = 1,...,ne, where ia[k] is a row index, ja[k] is a column index. * * The routine glp_check_dup can be used prior to a call to the routine * glp_load_matrix to check that the constraint matrix to be loaded has * no duplicate elements. * * RETURNS * * The routine glp_check_dup returns one of the following values: * * 0 - the matrix has no duplicate elements; * * -k - indices ia[k] or/and ja[k] are out of range; * * +k - element (ia[k],ja[k]) is duplicate. */ int glp_check_dup(int m, int n, int ne, const int ia[], const int ja[]) { int i, j, k, *ptr, *next, ret; char *flag; if (m < 0) xerror("glp_check_dup: m = %d; invalid parameter\n"); if (n < 0) xerror("glp_check_dup: n = %d; invalid parameter\n"); if (ne < 0) xerror("glp_check_dup: ne = %d; invalid parameter\n"); if (ne > 0 && ia == NULL) xerror("glp_check_dup: ia = %p; invalid parameter\n", ia); if (ne > 0 && ja == NULL) xerror("glp_check_dup: ja = %p; invalid parameter\n", ja); for (k = 1; k <= ne; k++) { i = ia[k], j = ja[k]; if (!(1 <= i && i <= m && 1 <= j && j <= n)) { ret = -k; goto done; } } if (m == 0 || n == 0) { ret = 0; goto done; } /* allocate working arrays */ ptr = xcalloc(1+m, sizeof(int)); next = xcalloc(1+ne, sizeof(int)); flag = xcalloc(1+n, sizeof(char)); /* build row lists */ for (i = 1; i <= m; i++) ptr[i] = 0; for (k = 1; k <= ne; k++) { i = ia[k]; next[k] = ptr[i]; ptr[i] = k; } /* clear column flags */ for (j = 1; j <= n; j++) flag[j] = 0; /* check for duplicate elements */ for (i = 1; i <= m; i++) { for (k = ptr[i]; k != 0; k = next[k]) { j = ja[k]; if (flag[j]) { /* find first element (i,j) */ for (k = 1; k <= ne; k++) if (ia[k] == i && ja[k] == j) break; xassert(k <= ne); /* find next (duplicate) element (i,j) */ for (k++; k <= ne; k++) if (ia[k] == i && ja[k] == j) break; xassert(k <= ne); ret = +k; goto skip; } flag[j] = 1; } /* clear column flags */ for (k = ptr[i]; k != 0; k = next[k]) flag[ja[k]] = 0; } /* no duplicate element found */ ret = 0; skip: /* free working arrays */ xfree(ptr); xfree(next); xfree(flag); done: return ret; } /*********************************************************************** * NAME * * glp_sort_matrix - sort elements of the constraint matrix * * SYNOPSIS * * void glp_sort_matrix(glp_prob *P); * * DESCRIPTION * * The routine glp_sort_matrix sorts elements of the constraint matrix * rebuilding its row and column linked lists. On exit from the routine * the constraint matrix is not changed, however, elements in the row * linked lists become ordered by ascending column indices, and the * elements in the column linked lists become ordered by ascending row * indices. */ void glp_sort_matrix(glp_prob *P) { GLPAIJ *aij; int i, j; if (P == NULL || P->magic != GLP_PROB_MAGIC) xerror("glp_sort_matrix: P = %p; invalid problem object\n", P); /* rebuild row linked lists */ for (i = P->m; i >= 1; i--) P->row[i]->ptr = NULL; for (j = P->n; j >= 1; j--) { for (aij = P->col[j]->ptr; aij != NULL; aij = aij->c_next) { i = aij->row->i; aij->r_prev = NULL; aij->r_next = P->row[i]->ptr; if (aij->r_next != NULL) aij->r_next->r_prev = aij; P->row[i]->ptr = aij; } } /* rebuild column linked lists */ for (j = P->n; j >= 1; j--) P->col[j]->ptr = NULL; for (i = P->m; i >= 1; i--) { for (aij = P->row[i]->ptr; aij != NULL; aij = aij->r_next) { j = aij->col->j; aij->c_prev = NULL; aij->c_next = P->col[j]->ptr; if (aij->c_next != NULL) aij->c_next->c_prev = aij; P->col[j]->ptr = aij; } } return; } /*********************************************************************** * NAME * * glp_del_rows - delete rows from problem object * * SYNOPSIS * * void glp_del_rows(glp_prob *lp, int nrs, const int num[]); * * DESCRIPTION * * The routine glp_del_rows deletes rows from the specified problem * object. Ordinal numbers of rows to be deleted should be placed in * locations num[1], ..., num[nrs], where nrs > 0. * * Note that deleting rows involves changing ordinal numbers of other * rows remaining in the problem object. New ordinal numbers of the * remaining rows are assigned under the assumption that the original * order of rows is not changed. */ void glp_del_rows(glp_prob *lp, int nrs, const int num[]) { glp_tree *tree = lp->tree; GLPROW *row; int i, k, m_new; /* mark rows to be deleted */ if (!(1 <= nrs && nrs <= lp->m)) xerror("glp_del_rows: nrs = %d; invalid number of rows\n", nrs); for (k = 1; k <= nrs; k++) { /* take the number of row to be deleted */ i = num[k]; /* obtain pointer to i-th row */ if (!(1 <= i && i <= lp->m)) xerror("glp_del_rows: num[%d] = %d; row number out of range" "\n", k, i); row = lp->row[i]; if (tree != NULL && tree->reason != 0) { if (!(tree->reason == GLP_IROWGEN || tree->reason == GLP_ICUTGEN)) xerror("glp_del_rows: operation not allowed\n"); xassert(tree->curr != NULL); if (row->level != tree->curr->level) xerror("glp_del_rows: num[%d] = %d; invalid attempt to d" "elete row created not in current subproblem\n", k,i); if (row->stat != GLP_BS) xerror("glp_del_rows: num[%d] = %d; invalid attempt to d" "elete active row (constraint)\n", k, i); tree->reinv = 1; } /* check that the row is not marked yet */ if (row->i == 0) xerror("glp_del_rows: num[%d] = %d; duplicate row numbers n" "ot allowed\n", k, i); /* erase symbolic name assigned to the row */ glp_set_row_name(lp, i, NULL); xassert(row->node == NULL); /* erase corresponding row of the constraint matrix */ glp_set_mat_row(lp, i, 0, NULL, NULL); xassert(row->ptr == NULL); /* mark the row to be deleted */ row->i = 0; } /* delete all marked rows from the row list */ m_new = 0; for (i = 1; i <= lp->m; i++) { /* obtain pointer to i-th row */ row = lp->row[i]; /* check if the row is marked */ if (row->i == 0) { /* it is marked, delete it */ dmp_free_atom(lp->pool, row, sizeof(GLPROW)); } else { /* it is not marked; keep it */ row->i = ++m_new; lp->row[row->i] = row; } } /* set new number of rows */ lp->m = m_new; /* invalidate the basis factorization */ lp->valid = 0; return; } /*********************************************************************** * NAME * * glp_del_cols - delete columns from problem object * * SYNOPSIS * * void glp_del_cols(glp_prob *lp, int ncs, const int num[]); * * DESCRIPTION * * The routine glp_del_cols deletes columns from the specified problem * object. Ordinal numbers of columns to be deleted should be placed in * locations num[1], ..., num[ncs], where ncs > 0. * * Note that deleting columns involves changing ordinal numbers of * other columns remaining in the problem object. New ordinal numbers * of the remaining columns are assigned under the assumption that the * original order of columns is not changed. */ void glp_del_cols(glp_prob *lp, int ncs, const int num[]) { glp_tree *tree = lp->tree; GLPCOL *col; int j, k, n_new; if (tree != NULL && tree->reason != 0) xerror("glp_del_cols: operation not allowed\n"); /* mark columns to be deleted */ if (!(1 <= ncs && ncs <= lp->n)) xerror("glp_del_cols: ncs = %d; invalid number of columns\n", ncs); for (k = 1; k <= ncs; k++) { /* take the number of column to be deleted */ j = num[k]; /* obtain pointer to j-th column */ if (!(1 <= j && j <= lp->n)) xerror("glp_del_cols: num[%d] = %d; column number out of ra" "nge", k, j); col = lp->col[j]; /* check that the column is not marked yet */ if (col->j == 0) xerror("glp_del_cols: num[%d] = %d; duplicate column number" "s not allowed\n", k, j); /* erase symbolic name assigned to the column */ glp_set_col_name(lp, j, NULL); xassert(col->node == NULL); /* erase corresponding column of the constraint matrix */ glp_set_mat_col(lp, j, 0, NULL, NULL); xassert(col->ptr == NULL); /* mark the column to be deleted */ col->j = 0; /* if it is basic, invalidate the basis factorization */ if (col->stat == GLP_BS) lp->valid = 0; } /* delete all marked columns from the column list */ n_new = 0; for (j = 1; j <= lp->n; j++) { /* obtain pointer to j-th column */ col = lp->col[j]; /* check if the column is marked */ if (col->j == 0) { /* it is marked; delete it */ dmp_free_atom(lp->pool, col, sizeof(GLPCOL)); } else { /* it is not marked; keep it */ col->j = ++n_new; lp->col[col->j] = col; } } /* set new number of columns */ lp->n = n_new; /* if the basis header is still valid, adjust it */ if (lp->valid) { int m = lp->m; int *head = lp->head; for (j = 1; j <= n_new; j++) { k = lp->col[j]->bind; if (k != 0) { xassert(1 <= k && k <= m); head[k] = m + j; } } } return; } /*********************************************************************** * NAME * * glp_copy_prob - copy problem object content * * SYNOPSIS * * void glp_copy_prob(glp_prob *dest, glp_prob *prob, int names); * * DESCRIPTION * * The routine glp_copy_prob copies the content of the problem object * prob to the problem object dest. * * The parameter names is a flag. If it is non-zero, the routine also * copies all symbolic names; otherwise, if it is zero, symbolic names * are not copied. */ void glp_copy_prob(glp_prob *dest, glp_prob *prob, int names) { glp_tree *tree = dest->tree; glp_bfcp bfcp; int i, j, len, *ind; double *val; if (tree != NULL && tree->reason != 0) xerror("glp_copy_prob: operation not allowed\n"); if (dest == prob) xerror("glp_copy_prob: copying problem object to itself not al" "lowed\n"); if (!(names == GLP_ON || names == GLP_OFF)) xerror("glp_copy_prob: names = %d; invalid parameter\n", names); glp_erase_prob(dest); if (names && prob->name != NULL) glp_set_prob_name(dest, prob->name); if (names && prob->obj != NULL) glp_set_obj_name(dest, prob->obj); dest->dir = prob->dir; dest->c0 = prob->c0; if (prob->m > 0) glp_add_rows(dest, prob->m); if (prob->n > 0) glp_add_cols(dest, prob->n); glp_get_bfcp(prob, &bfcp); glp_set_bfcp(dest, &bfcp); dest->pbs_stat = prob->pbs_stat; dest->dbs_stat = prob->dbs_stat; dest->obj_val = prob->obj_val; dest->some = prob->some; dest->ipt_stat = prob->ipt_stat; dest->ipt_obj = prob->ipt_obj; dest->mip_stat = prob->mip_stat; dest->mip_obj = prob->mip_obj; for (i = 1; i <= prob->m; i++) { GLPROW *to = dest->row[i]; GLPROW *from = prob->row[i]; if (names && from->name != NULL) glp_set_row_name(dest, i, from->name); to->type = from->type; to->lb = from->lb; to->ub = from->ub; to->rii = from->rii; to->stat = from->stat; to->prim = from->prim; to->dual = from->dual; to->pval = from->pval; to->dval = from->dval; to->mipx = from->mipx; } ind = xcalloc(1+prob->m, sizeof(int)); val = xcalloc(1+prob->m, sizeof(double)); for (j = 1; j <= prob->n; j++) { GLPCOL *to = dest->col[j]; GLPCOL *from = prob->col[j]; if (names && from->name != NULL) glp_set_col_name(dest, j, from->name); to->kind = from->kind; to->type = from->type; to->lb = from->lb; to->ub = from->ub; to->coef = from->coef; len = glp_get_mat_col(prob, j, ind, val); glp_set_mat_col(dest, j, len, ind, val); to->sjj = from->sjj; to->stat = from->stat; to->prim = from->prim; to->dual = from->dual; to->pval = from->pval; to->dval = from->dval; to->mipx = from->mipx; } xfree(ind); xfree(val); return; } /*********************************************************************** * NAME * * glp_erase_prob - erase problem object content * * SYNOPSIS * * void glp_erase_prob(glp_prob *lp); * * DESCRIPTION * * The routine glp_erase_prob erases the content of the specified * problem object. The effect of this operation is the same as if the * problem object would be deleted with the routine glp_delete_prob and * then created anew with the routine glp_create_prob, with exception * that the handle (pointer) to the problem object remains valid. */ static void delete_prob(glp_prob *lp); void glp_erase_prob(glp_prob *lp) { glp_tree *tree = lp->tree; if (tree != NULL && tree->reason != 0) xerror("glp_erase_prob: operation not allowed\n"); delete_prob(lp); create_prob(lp); return; } /*********************************************************************** * NAME * * glp_delete_prob - delete problem object * * SYNOPSIS * * void glp_delete_prob(glp_prob *lp); * * DESCRIPTION * * The routine glp_delete_prob deletes the specified problem object and * frees all the memory allocated to it. */ static void delete_prob(glp_prob *lp) { lp->magic = 0x3F3F3F3F; dmp_delete_pool(lp->pool); #if 0 /* 17/XI-2009 */ xfree(lp->cps); #else if (lp->parms != NULL) xfree(lp->parms); #endif xassert(lp->tree == NULL); #if 0 if (lp->cwa != NULL) xfree(lp->cwa); #endif xfree(lp->row); xfree(lp->col); if (lp->r_tree != NULL) avl_delete_tree(lp->r_tree); if (lp->c_tree != NULL) avl_delete_tree(lp->c_tree); xfree(lp->head); if (lp->bfcp != NULL) xfree(lp->bfcp); if (lp->bfd != NULL) bfd_delete_it(lp->bfd); return; } void glp_delete_prob(glp_prob *lp) { glp_tree *tree = lp->tree; if (tree != NULL && tree->reason != 0) xerror("glp_delete_prob: operation not allowed\n"); delete_prob(lp); xfree(lp); return; } /* eof */ sources_5316/external/glpk/glpenv05.c0000644000176700017670000001613011401660400016277 0ustar paulpaul/* glpenv05.c (memory allocation) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /* some processors need data to be properly aligned; the macro align_datasize enlarges the specified size of a data item to provide a proper alignment of immediately following data */ #define align_datasize(size) ((((size) + 15) / 16) * 16) /* 16 bytes is sufficient in both 32- and 64-bit environments (8 bytes is not sufficient in 64-bit environment due to jmp_buf) */ /*********************************************************************** * NAME * * glp_malloc - allocate memory block * * SYNOPSIS * * void *glp_malloc(int size); * * DESCRIPTION * * The routine glp_malloc allocates a memory block of size bytes long. * * Note that being allocated the memory block contains arbitrary data * (not binary zeros). * * RETURNS * * The routine glp_malloc returns a pointer to the allocated block. * To free this block the routine glp_free (not free!) must be used. */ void *glp_malloc(int size) { ENV *env = get_env_ptr(); MEM *desc; int size_of_desc = align_datasize(sizeof(MEM)); if (size < 1 || size > INT_MAX - size_of_desc) xerror("glp_malloc: size = %d; invalid parameter\n", size); size += size_of_desc; if (xlcmp(xlset(size), xlsub(env->mem_limit, env->mem_total)) > 0) xerror("glp_malloc: memory limit exceeded\n"); if (env->mem_count == INT_MAX) xerror("glp_malloc: too many memory blocks allocated\n"); desc = malloc(size); if (desc == NULL) xerror("glp_malloc: no memory available\n"); memset(desc, '?', size); desc->flag = MEM_MAGIC; desc->size = size; desc->prev = NULL; desc->next = env->mem_ptr; if (desc->next != NULL) desc->next->prev = desc; env->mem_ptr = desc; env->mem_count++; if (env->mem_cpeak < env->mem_count) env->mem_cpeak = env->mem_count; env->mem_total = xladd(env->mem_total, xlset(size)); if (xlcmp(env->mem_tpeak, env->mem_total) < 0) env->mem_tpeak = env->mem_total; return (void *)((char *)desc + size_of_desc); } /*********************************************************************** * NAME * * glp_calloc - allocate memory block * * SYNOPSIS * * void *glp_calloc(int n, int size); * * DESCRIPTION * * The routine glp_calloc allocates a memory block of (n*size) bytes * long. * * Note that being allocated the memory block contains arbitrary data * (not binary zeros). * * RETURNS * * The routine glp_calloc returns a pointer to the allocated block. * To free this block the routine glp_free (not free!) must be used. */ void *glp_calloc(int n, int size) { if (n < 1) xerror("glp_calloc: n = %d; invalid parameter\n", n); if (size < 1) xerror("glp_calloc: size = %d; invalid parameter\n", size); if (n > INT_MAX / size) xerror("glp_calloc: n = %d; size = %d; array too big\n", n, size); return xmalloc(n * size); } /*********************************************************************** * NAME * * glp_free - free memory block * * SYNOPSIS * * void glp_free(void *ptr); * * DESCRIPTION * * The routine glp_free frees a memory block pointed to by ptr, which * was previuosly allocated by the routine glp_malloc or glp_calloc. */ void glp_free(void *ptr) { ENV *env = get_env_ptr(); MEM *desc; int size_of_desc = align_datasize(sizeof(MEM)); if (ptr == NULL) xerror("glp_free: ptr = %p; null pointer\n", ptr); desc = (void *)((char *)ptr - size_of_desc); if (desc->flag != MEM_MAGIC) xerror("glp_free: ptr = %p; invalid pointer\n", ptr); if (env->mem_count == 0 || xlcmp(env->mem_total, xlset(desc->size)) < 0) xerror("glp_free: memory allocation error\n"); if (desc->prev == NULL) env->mem_ptr = desc->next; else desc->prev->next = desc->next; if (desc->next == NULL) ; else desc->next->prev = desc->prev; env->mem_count--; env->mem_total = xlsub(env->mem_total, xlset(desc->size)); memset(desc, '?', size_of_desc); free(desc); return; } /*********************************************************************** * NAME * * glp_mem_limit - set memory usage limit * * SYNOPSIS * * void glp_mem_limit(int limit); * * DESCRIPTION * * The routine glp_mem_limit limits the amount of memory available for * dynamic allocation (in GLPK routines) to limit megabytes. */ void glp_mem_limit(int limit) { ENV *env = get_env_ptr(); if (limit < 0) xerror("glp_mem_limit: limit = %d; invalid parameter\n", limit); env->mem_limit = xlmul(xlset(limit), xlset(1 << 20)); return; } /*********************************************************************** * NAME * * glp_mem_usage - get memory usage information * * SYNOPSIS * * void glp_mem_usage(int *count, int *cpeak, glp_long *total, * glp_long *tpeak); * * DESCRIPTION * * The routine glp_mem_usage reports some information about utilization * of the memory by GLPK routines. Information is stored to locations * specified by corresponding parameters (see below). Any parameter can * be specified as NULL, in which case corresponding information is not * stored. * * *count is the number of the memory blocks currently allocated by the * routines xmalloc and xcalloc (one call to xmalloc or xcalloc results * in allocating one memory block). * * *cpeak is the peak value of *count reached since the initialization * of the GLPK library environment. * * *total is the total amount, in bytes, of the memory blocks currently * allocated by the routines xmalloc and xcalloc. * * *tpeak is the peak value of *total reached since the initialization * of the GLPK library envirionment. */ void glp_mem_usage(int *count, int *cpeak, glp_long *total, glp_long *tpeak) { ENV *env = get_env_ptr(); if (count != NULL) *count = env->mem_count; if (cpeak != NULL) *cpeak = env->mem_cpeak; if (total != NULL) *total = env->mem_total; if (tpeak != NULL) *tpeak = env->mem_tpeak; return; } /* eof */ sources_5316/external/glpk/glpbfd.c0000644000176700017670000003454411401660400016106 0ustar paulpaul/* glpbfd.c (LP basis factorization driver) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ typedef struct BFD BFD; #define GLPBFD_PRIVATE #include "glpapi.h" #include "glpfhv.h" #include "glplpf.h" /* CAUTION: DO NOT CHANGE THE LIMIT BELOW */ #define M_MAX 100000000 /* = 100*10^6 */ /* maximal order of the basis matrix */ struct BFD { /* LP basis factorization */ int valid; /* factorization is valid only if this flag is set */ int type; /* factorization type: GLP_BF_FT - LUF + Forrest-Tomlin GLP_BF_BG - LUF + Schur compl. + Bartels-Golub GLP_BF_GR - LUF + Schur compl. + Givens rotation */ FHV *fhv; /* LP basis factorization (GLP_BF_FT) */ LPF *lpf; /* LP basis factorization (GLP_BF_BG, GLP_BF_GR) */ int lu_size; /* luf.sv_size */ double piv_tol; /* luf.piv_tol */ int piv_lim; /* luf.piv_lim */ int suhl; /* luf.suhl */ double eps_tol; /* luf.eps_tol */ double max_gro; /* luf.max_gro */ int nfs_max; /* fhv.hh_max */ double upd_tol; /* fhv.upd_tol */ int nrs_max; /* lpf.n_max */ int rs_size; /* lpf.v_size */ /* internal control parameters */ int upd_lim; /* the factorization update limit */ int upd_cnt; /* the factorization update count */ }; /*********************************************************************** * NAME * * bfd_create_it - create LP basis factorization * * SYNOPSIS * * #include "glpbfd.h" * BFD *bfd_create_it(void); * * DESCRIPTION * * The routine bfd_create_it creates a program object, which represents * a factorization of LP basis. * * RETURNS * * The routine bfd_create_it returns a pointer to the object created. */ BFD *bfd_create_it(void) { BFD *bfd; bfd = xmalloc(sizeof(BFD)); bfd->valid = 0; bfd->type = GLP_BF_FT; bfd->fhv = NULL; bfd->lpf = NULL; bfd->lu_size = 0; bfd->piv_tol = 0.10; bfd->piv_lim = 4; bfd->suhl = 1; bfd->eps_tol = 1e-15; bfd->max_gro = 1e+10; bfd->nfs_max = 100; bfd->upd_tol = 1e-6; bfd->nrs_max = 100; bfd->rs_size = 1000; bfd->upd_lim = -1; bfd->upd_cnt = 0; return bfd; } /**********************************************************************/ void bfd_set_parm(BFD *bfd, const void *_parm) { /* change LP basis factorization control parameters */ const glp_bfcp *parm = _parm; xassert(bfd != NULL); bfd->type = parm->type; bfd->lu_size = parm->lu_size; bfd->piv_tol = parm->piv_tol; bfd->piv_lim = parm->piv_lim; bfd->suhl = parm->suhl; bfd->eps_tol = parm->eps_tol; bfd->max_gro = parm->max_gro; bfd->nfs_max = parm->nfs_max; bfd->upd_tol = parm->upd_tol; bfd->nrs_max = parm->nrs_max; bfd->rs_size = parm->rs_size; return; } /*********************************************************************** * NAME * * bfd_factorize - compute LP basis factorization * * SYNOPSIS * * #include "glpbfd.h" * int bfd_factorize(BFD *bfd, int m, int bh[], int (*col)(void *info, * int j, int ind[], double val[]), void *info); * * DESCRIPTION * * The routine bfd_factorize computes the factorization of the basis * matrix B specified by the routine col. * * The parameter bfd specified the basis factorization data structure * created with the routine bfd_create_it. * * The parameter m specifies the order of B, m > 0. * * The array bh specifies the basis header: bh[j], 1 <= j <= m, is the * number of j-th column of B in some original matrix. The array bh is * optional and can be specified as NULL. * * The formal routine col specifies the matrix B to be factorized. To * obtain j-th column of A the routine bfd_factorize calls the routine * col with the parameter j (1 <= j <= n). In response the routine col * should store row indices and numerical values of non-zero elements * of j-th column of B to locations ind[1,...,len] and val[1,...,len], * respectively, where len is the number of non-zeros in j-th column * returned on exit. Neither zero nor duplicate elements are allowed. * * The parameter info is a transit pointer passed to the routine col. * * RETURNS * * 0 The factorization has been successfully computed. * * BFD_ESING * The specified matrix is singular within the working precision. * * BFD_ECOND * The specified matrix is ill-conditioned. * * For more details see comments to the routine luf_factorize. */ int bfd_factorize(BFD *bfd, int m, const int bh[], int (*col) (void *info, int j, int ind[], double val[]), void *info) { LUF *luf; int nov, ret; xassert(bfd != NULL); xassert(1 <= m && m <= M_MAX); /* invalidate the factorization */ bfd->valid = 0; /* create the factorization, if necessary */ nov = 0; switch (bfd->type) { case GLP_BF_FT: if (bfd->lpf != NULL) lpf_delete_it(bfd->lpf), bfd->lpf = NULL; if (bfd->fhv == NULL) bfd->fhv = fhv_create_it(), nov = 1; break; case GLP_BF_BG: case GLP_BF_GR: if (bfd->fhv != NULL) fhv_delete_it(bfd->fhv), bfd->fhv = NULL; if (bfd->lpf == NULL) bfd->lpf = lpf_create_it(), nov = 1; break; default: xassert(bfd != bfd); } /* set control parameters specific to LUF */ if (bfd->fhv != NULL) luf = bfd->fhv->luf; else if (bfd->lpf != NULL) luf = bfd->lpf->luf; else xassert(bfd != bfd); if (nov) luf->new_sva = bfd->lu_size; luf->piv_tol = bfd->piv_tol; luf->piv_lim = bfd->piv_lim; luf->suhl = bfd->suhl; luf->eps_tol = bfd->eps_tol; luf->max_gro = bfd->max_gro; /* set control parameters specific to FHV */ if (bfd->fhv != NULL) { if (nov) bfd->fhv->hh_max = bfd->nfs_max; bfd->fhv->upd_tol = bfd->upd_tol; } /* set control parameters specific to LPF */ if (bfd->lpf != NULL) { if (nov) bfd->lpf->n_max = bfd->nrs_max; if (nov) bfd->lpf->v_size = bfd->rs_size; } /* try to factorize the basis matrix */ if (bfd->fhv != NULL) { switch (fhv_factorize(bfd->fhv, m, col, info)) { case 0: break; case FHV_ESING: ret = BFD_ESING; goto done; case FHV_ECOND: ret = BFD_ECOND; goto done; default: xassert(bfd != bfd); } } else if (bfd->lpf != NULL) { switch (lpf_factorize(bfd->lpf, m, bh, col, info)) { case 0: /* set the Schur complement update type */ switch (bfd->type) { case GLP_BF_BG: /* Bartels-Golub update */ bfd->lpf->scf->t_opt = SCF_TBG; break; case GLP_BF_GR: /* Givens rotation update */ bfd->lpf->scf->t_opt = SCF_TGR; break; default: xassert(bfd != bfd); } break; case LPF_ESING: ret = BFD_ESING; goto done; case LPF_ECOND: ret = BFD_ECOND; goto done; default: xassert(bfd != bfd); } } else xassert(bfd != bfd); /* the basis matrix has been successfully factorized */ bfd->valid = 1; bfd->upd_cnt = 0; ret = 0; done: /* return to the calling program */ return ret; } /*********************************************************************** * NAME * * bfd_ftran - perform forward transformation (solve system B*x = b) * * SYNOPSIS * * #include "glpbfd.h" * void bfd_ftran(BFD *bfd, double x[]); * * DESCRIPTION * * The routine bfd_ftran performs forward transformation, i.e. solves * the system B*x = b, where B is the basis matrix, x is the vector of * unknowns to be computed, b is the vector of right-hand sides. * * On entry elements of the vector b should be stored in dense format * in locations x[1], ..., x[m], where m is the number of rows. On exit * the routine stores elements of the vector x in the same locations. */ void bfd_ftran(BFD *bfd, double x[]) { xassert(bfd != NULL); xassert(bfd->valid); if (bfd->fhv != NULL) fhv_ftran(bfd->fhv, x); else if (bfd->lpf != NULL) lpf_ftran(bfd->lpf, x); else xassert(bfd != bfd); return; } /*********************************************************************** * NAME * * bfd_btran - perform backward transformation (solve system B'*x = b) * * SYNOPSIS * * #include "glpbfd.h" * void bfd_btran(BFD *bfd, double x[]); * * DESCRIPTION * * The routine bfd_btran performs backward transformation, i.e. solves * the system B'*x = b, where B' is a matrix transposed to the basis * matrix B, x is the vector of unknowns to be computed, b is the vector * of right-hand sides. * * On entry elements of the vector b should be stored in dense format * in locations x[1], ..., x[m], where m is the number of rows. On exit * the routine stores elements of the vector x in the same locations. */ void bfd_btran(BFD *bfd, double x[]) { xassert(bfd != NULL); xassert(bfd->valid); if (bfd->fhv != NULL) fhv_btran(bfd->fhv, x); else if (bfd->lpf != NULL) lpf_btran(bfd->lpf, x); else xassert(bfd != bfd); return; } /*********************************************************************** * NAME * * bfd_update_it - update LP basis factorization * * SYNOPSIS * * #include "glpbfd.h" * int bfd_update_it(BFD *bfd, int j, int bh, int len, const int ind[], * const double val[]); * * DESCRIPTION * * The routine bfd_update_it updates the factorization of the basis * matrix B after replacing its j-th column by a new vector. * * The parameter j specifies the number of column of B, which has been * replaced, 1 <= j <= m, where m is the order of B. * * The parameter bh specifies the basis header entry for the new column * of B, which is the number of the new column in some original matrix. * This parameter is optional and can be specified as 0. * * Row indices and numerical values of non-zero elements of the new * column of B should be placed in locations ind[1], ..., ind[len] and * val[1], ..., val[len], resp., where len is the number of non-zeros * in the column. Neither zero nor duplicate elements are allowed. * * RETURNS * * 0 The factorization has been successfully updated. * * BFD_ESING * New basis matrix is singular within the working precision. * * BFD_ECHECK * The factorization is inaccurate. * * BFD_ELIMIT * Factorization update limit has been reached. * * BFD_EROOM * Overflow of the sparse vector area. * * In case of non-zero return code the factorization becomes invalid. * It should not be used until it has been recomputed with the routine * bfd_factorize. */ int bfd_update_it(BFD *bfd, int j, int bh, int len, const int ind[], const double val[]) { int ret; xassert(bfd != NULL); xassert(bfd->valid); /* try to update the factorization */ if (bfd->fhv != NULL) { switch (fhv_update_it(bfd->fhv, j, len, ind, val)) { case 0: break; case FHV_ESING: bfd->valid = 0; ret = BFD_ESING; goto done; case FHV_ECHECK: bfd->valid = 0; ret = BFD_ECHECK; goto done; case FHV_ELIMIT: bfd->valid = 0; ret = BFD_ELIMIT; goto done; case FHV_EROOM: bfd->valid = 0; ret = BFD_EROOM; goto done; default: xassert(bfd != bfd); } } else if (bfd->lpf != NULL) { switch (lpf_update_it(bfd->lpf, j, bh, len, ind, val)) { case 0: break; case LPF_ESING: bfd->valid = 0; ret = BFD_ESING; goto done; case LPF_ELIMIT: bfd->valid = 0; ret = BFD_ELIMIT; goto done; default: xassert(bfd != bfd); } } else xassert(bfd != bfd); /* the factorization has been successfully updated */ /* increase the update count */ bfd->upd_cnt++; ret = 0; done: /* return to the calling program */ return ret; } /**********************************************************************/ int bfd_get_count(BFD *bfd) { /* determine factorization update count */ xassert(bfd != NULL); xassert(bfd->valid); return bfd->upd_cnt; } /*********************************************************************** * NAME * * bfd_delete_it - delete LP basis factorization * * SYNOPSIS * * #include "glpbfd.h" * void bfd_delete_it(BFD *bfd); * * DESCRIPTION * * The routine bfd_delete_it deletes LP basis factorization specified * by the parameter fhv and frees all memory allocated to this program * object. */ void bfd_delete_it(BFD *bfd) { xassert(bfd != NULL); if (bfd->fhv != NULL) fhv_delete_it(bfd->fhv); if (bfd->lpf != NULL) lpf_delete_it(bfd->lpf); xfree(bfd); return; } /* eof */ sources_5316/external/glpk/glpqmd.h0000644000176700017670000000430511401660400016131 0ustar paulpaul/* glpqmd.h (quotient minimum degree algorithm) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPQMD_H #define GLPQMD_H #define genqmd _glp_qmd_genqmd void genqmd(int *neqns, int xadj[], int adjncy[], int perm[], int invp[], int deg[], int marker[], int rchset[], int nbrhd[], int qsize[], int qlink[], int *nofsub); /* GENeral Quotient Minimum Degree algorithm */ #define qmdrch _glp_qmd_qmdrch void qmdrch(int *root, int xadj[], int adjncy[], int deg[], int marker[], int *rchsze, int rchset[], int *nhdsze, int nbrhd[]); /* Quotient MD ReaCHable set */ #define qmdqt _glp_qmd_qmdqt void qmdqt(int *root, int xadj[], int adjncy[], int marker[], int *rchsze, int rchset[], int nbrhd[]); /* Quotient MD Quotient graph Transformation */ #define qmdupd _glp_qmd_qmdupd void qmdupd(int xadj[], int adjncy[], int *nlist, int list[], int deg[], int qsize[], int qlink[], int marker[], int rchset[], int nbrhd[]); /* Quotient MD UPDate */ #define qmdmrg _glp_qmd_qmdmrg void qmdmrg(int xadj[], int adjncy[], int deg[], int qsize[], int qlink[], int marker[], int *deg0, int *nhdsze, int nbrhd[], int rchset[], int ovrlp[]); /* Quotient MD MeRGe */ #endif /* eof */ sources_5316/external/glpk/glpgmp.h0000644000176700017670000001431511401660400016135 0ustar paulpaul/* glpgmp.h (bignum arithmetic) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPGMP_H #define GLPGMP_H #ifdef HAVE_CONFIG_H #include #endif #ifdef HAVE_GMP /* use GNU MP bignum library */ #include #define gmp_pool_count _glp_gmp_pool_count #define gmp_free_mem _glp_gmp_free_mem int gmp_pool_count(void); void gmp_free_mem(void); #else /* use GLPK bignum module */ /*---------------------------------------------------------------------- // INTEGER NUMBERS // // Depending on its magnitude an integer number of arbitrary precision // is represented either in short format or in long format. // // Short format corresponds to the int type and allows representing // integer numbers in the range [-(2^31-1), +(2^31-1)]. Note that for // the most negative number of int type the short format is not used. // // In long format integer numbers are represented using the positional // system with the base (radix) 2^16 = 65536: // // x = (-1)^s sum{j in 0..n-1} d[j] * 65536^j, // // where x is the integer to be represented, s is its sign (+1 or -1), // d[j] are its digits (0 <= d[j] <= 65535). // // RATIONAL NUMBERS // // A rational number is represented as an irreducible fraction: // // p / q, // // where p (numerator) and q (denominator) are integer numbers (q > 0) // having no common divisors. */ struct mpz { /* integer number */ int val; /* if ptr is a null pointer, the number is in short format, and val is its value; otherwise, the number is in long format, and val is its sign (+1 or -1) */ struct mpz_seg *ptr; /* pointer to the linked list of the number segments ordered in ascending of powers of the base */ }; struct mpz_seg { /* integer number segment */ unsigned short d[6]; /* six digits of the number ordered in ascending of powers of the base */ struct mpz_seg *next; /* pointer to the next number segment */ }; struct mpq { /* rational number (p / q) */ struct mpz p; /* numerator */ struct mpz q; /* denominator */ }; typedef struct mpz *mpz_t; typedef struct mpq *mpq_t; #define gmp_get_atom _glp_gmp_get_atom #define gmp_free_atom _glp_gmp_free_atom #define gmp_pool_count _glp_gmp_pool_count #define gmp_get_work _glp_gmp_get_work #define gmp_free_mem _glp_gmp_free_mem #define _mpz_init _glp_mpz_init #define mpz_clear _glp_mpz_clear #define mpz_set _glp_mpz_set #define mpz_set_si _glp_mpz_set_si #define mpz_get_d _glp_mpz_get_d #define mpz_get_d_2exp _glp_mpz_get_d_2exp #define mpz_swap _glp_mpz_swap #define mpz_add _glp_mpz_add #define mpz_sub _glp_mpz_sub #define mpz_mul _glp_mpz_mul #define mpz_neg _glp_mpz_neg #define mpz_abs _glp_mpz_abs #define mpz_div _glp_mpz_div #define mpz_gcd _glp_mpz_gcd #define mpz_cmp _glp_mpz_cmp #define mpz_sgn _glp_mpz_sgn #define mpz_out_str _glp_mpz_out_str #define _mpq_init _glp_mpq_init #define mpq_clear _glp_mpq_clear #define mpq_canonicalize _glp_mpq_canonicalize #define mpq_set _glp_mpq_set #define mpq_set_si _glp_mpq_set_si #define mpq_get_d _glp_mpq_get_d #define mpq_set_d _glp_mpq_set_d #define mpq_add _glp_mpq_add #define mpq_sub _glp_mpq_sub #define mpq_mul _glp_mpq_mul #define mpq_div _glp_mpq_div #define mpq_neg _glp_mpq_neg #define mpq_abs _glp_mpq_abs #define mpq_cmp _glp_mpq_cmp #define mpq_sgn _glp_mpq_sgn #define mpq_out_str _glp_mpq_out_str void *gmp_get_atom(int size); void gmp_free_atom(void *ptr, int size); int gmp_pool_count(void); unsigned short *gmp_get_work(int size); void gmp_free_mem(void); mpz_t _mpz_init(void); #define mpz_init(x) (void)((x) = _mpz_init()) void mpz_clear(mpz_t x); void mpz_set(mpz_t z, mpz_t x); void mpz_set_si(mpz_t x, int val); double mpz_get_d(mpz_t x); double mpz_get_d_2exp(int *exp, mpz_t x); void mpz_swap(mpz_t x, mpz_t y); void mpz_add(mpz_t, mpz_t, mpz_t); void mpz_sub(mpz_t, mpz_t, mpz_t); void mpz_mul(mpz_t, mpz_t, mpz_t); void mpz_neg(mpz_t z, mpz_t x); void mpz_abs(mpz_t z, mpz_t x); void mpz_div(mpz_t q, mpz_t r, mpz_t x, mpz_t y); void mpz_gcd(mpz_t z, mpz_t x, mpz_t y); int mpz_cmp(mpz_t x, mpz_t y); int mpz_sgn(mpz_t x); int mpz_out_str(void *fp, int base, mpz_t x); mpq_t _mpq_init(void); #define mpq_init(x) (void)((x) = _mpq_init()) void mpq_clear(mpq_t x); void mpq_canonicalize(mpq_t x); void mpq_set(mpq_t z, mpq_t x); void mpq_set_si(mpq_t x, int p, unsigned int q); double mpq_get_d(mpq_t x); void mpq_set_d(mpq_t x, double val); void mpq_add(mpq_t z, mpq_t x, mpq_t y); void mpq_sub(mpq_t z, mpq_t x, mpq_t y); void mpq_mul(mpq_t z, mpq_t x, mpq_t y); void mpq_div(mpq_t z, mpq_t x, mpq_t y); void mpq_neg(mpq_t z, mpq_t x); void mpq_abs(mpq_t z, mpq_t x); int mpq_cmp(mpq_t x, mpq_t y); int mpq_sgn(mpq_t x); int mpq_out_str(void *fp, int base, mpq_t x); #endif #endif /* eof */ sources_5316/external/glpk/glpapi11.c0000644000176700017670000012675611401660400016275 0ustar paulpaul/* glpapi11.c (utility routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" int glp_print_sol(glp_prob *P, const char *fname) { /* write basic solution in printable format */ XFILE *fp; GLPROW *row; GLPCOL *col; int i, j, t, ae_ind, re_ind, ret; double ae_max, re_max; xprintf("Writing basic solution to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xfprintf(fp, "%-12s%s\n", "Problem:", P->name == NULL ? "" : P->name); xfprintf(fp, "%-12s%d\n", "Rows:", P->m); xfprintf(fp, "%-12s%d\n", "Columns:", P->n); xfprintf(fp, "%-12s%d\n", "Non-zeros:", P->nnz); t = glp_get_status(P); xfprintf(fp, "%-12s%s\n", "Status:", t == GLP_OPT ? "OPTIMAL" : t == GLP_FEAS ? "FEASIBLE" : t == GLP_INFEAS ? "INFEASIBLE (INTERMEDIATE)" : t == GLP_NOFEAS ? "INFEASIBLE (FINAL)" : t == GLP_UNBND ? "UNBOUNDED" : t == GLP_UNDEF ? "UNDEFINED" : "???"); xfprintf(fp, "%-12s%s%s%.10g (%s)\n", "Objective:", P->obj == NULL ? "" : P->obj, P->obj == NULL ? "" : " = ", P->obj_val, P->dir == GLP_MIN ? "MINimum" : P->dir == GLP_MAX ? "MAXimum" : "???"); xfprintf(fp, "\n"); xfprintf(fp, " No. Row name St Activity Lower bound " " Upper bound Marginal\n"); xfprintf(fp, "------ ------------ -- ------------- ------------- " "------------- -------------\n"); for (i = 1; i <= P->m; i++) { row = P->row[i]; xfprintf(fp, "%6d ", i); if (row->name == NULL || strlen(row->name) <= 12) xfprintf(fp, "%-12s ", row->name == NULL ? "" : row->name); else xfprintf(fp, "%s\n%20s", row->name, ""); xfprintf(fp, "%s ", row->stat == GLP_BS ? "B " : row->stat == GLP_NL ? "NL" : row->stat == GLP_NU ? "NU" : row->stat == GLP_NF ? "NF" : row->stat == GLP_NS ? "NS" : "??"); xfprintf(fp, "%13.6g ", fabs(row->prim) <= 1e-9 ? 0.0 : row->prim); if (row->type == GLP_LO || row->type == GLP_DB || row->type == GLP_FX) xfprintf(fp, "%13.6g ", row->lb); else xfprintf(fp, "%13s ", ""); if (row->type == GLP_UP || row->type == GLP_DB) xfprintf(fp, "%13.6g ", row->ub); else xfprintf(fp, "%13s ", row->type == GLP_FX ? "=" : ""); if (row->stat != GLP_BS) { if (fabs(row->dual) <= 1e-9) xfprintf(fp, "%13s", "< eps"); else xfprintf(fp, "%13.6g ", row->dual); } xfprintf(fp, "\n"); } xfprintf(fp, "\n"); xfprintf(fp, " No. Column name St Activity Lower bound " " Upper bound Marginal\n"); xfprintf(fp, "------ ------------ -- ------------- ------------- " "------------- -------------\n"); for (j = 1; j <= P->n; j++) { col = P->col[j]; xfprintf(fp, "%6d ", j); if (col->name == NULL || strlen(col->name) <= 12) xfprintf(fp, "%-12s ", col->name == NULL ? "" : col->name); else xfprintf(fp, "%s\n%20s", col->name, ""); xfprintf(fp, "%s ", col->stat == GLP_BS ? "B " : col->stat == GLP_NL ? "NL" : col->stat == GLP_NU ? "NU" : col->stat == GLP_NF ? "NF" : col->stat == GLP_NS ? "NS" : "??"); xfprintf(fp, "%13.6g ", fabs(col->prim) <= 1e-9 ? 0.0 : col->prim); if (col->type == GLP_LO || col->type == GLP_DB || col->type == GLP_FX) xfprintf(fp, "%13.6g ", col->lb); else xfprintf(fp, "%13s ", ""); if (col->type == GLP_UP || col->type == GLP_DB) xfprintf(fp, "%13.6g ", col->ub); else xfprintf(fp, "%13s ", col->type == GLP_FX ? "=" : ""); if (col->stat != GLP_BS) { if (fabs(col->dual) <= 1e-9) xfprintf(fp, "%13s", "< eps"); else xfprintf(fp, "%13.6g ", col->dual); } xfprintf(fp, "\n"); } xfprintf(fp, "\n"); xfprintf(fp, "Karush-Kuhn-Tucker optimality conditions:\n"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_SOL, GLP_KKT_PE, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.PE: max.abs.err = %.2e on row %d\n", ae_max, ae_ind); xfprintf(fp, " max.rel.err = %.2e on row %d\n", re_max, re_ind); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "PRIMAL SOLUTION IS WRONG"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_SOL, GLP_KKT_PB, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.PB: max.abs.err = %.2e on %s %d\n", ae_max, ae_ind <= P->m ? "row" : "column", ae_ind <= P->m ? ae_ind : ae_ind - P->m); xfprintf(fp, " max.rel.err = %.2e on %s %d\n", re_max, re_ind <= P->m ? "row" : "column", re_ind <= P->m ? re_ind : re_ind - P->m); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "PRIMAL SOLUTION IS INFEASIBL" "E"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_SOL, GLP_KKT_DE, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.DE: max.abs.err = %.2e on column %d\n", ae_max, ae_ind == 0 ? 0 : ae_ind - P->m); xfprintf(fp, " max.rel.err = %.2e on column %d\n", re_max, re_ind == 0 ? 0 : re_ind - P->m); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "DUAL SOLUTION IS WRONG"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_SOL, GLP_KKT_DB, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.DB: max.abs.err = %.2e on %s %d\n", ae_max, ae_ind <= P->m ? "row" : "column", ae_ind <= P->m ? ae_ind : ae_ind - P->m); xfprintf(fp, " max.rel.err = %.2e on %s %d\n", re_max, re_ind <= P->m ? "row" : "column", re_ind <= P->m ? re_ind : re_ind - P->m); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "DUAL SOLUTION IS INFEASIBLE") ; xfprintf(fp, "\n"); xfprintf(fp, "End of output\n"); xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /*********************************************************************** * NAME * * glp_read_sol - read basic solution from text file * * SYNOPSIS * * int glp_read_sol(glp_prob *lp, const char *fname); * * DESCRIPTION * * The routine glp_read_sol reads basic solution from a text file whose * name is specified by the parameter fname into the problem object. * * For the file format see description of the routine glp_write_sol. * * RETURNS * * On success the routine returns zero, otherwise non-zero. */ int glp_read_sol(glp_prob *lp, const char *fname) { glp_data *data; jmp_buf jump; int i, j, k, ret = 0; xprintf("Reading basic solution from `%s'...\n", fname); data = glp_sdf_open_file(fname); if (data == NULL) { ret = 1; goto done; } if (setjmp(jump)) { ret = 1; goto done; } glp_sdf_set_jump(data, jump); /* number of rows, number of columns */ k = glp_sdf_read_int(data); if (k != lp->m) glp_sdf_error(data, "wrong number of rows\n"); k = glp_sdf_read_int(data); if (k != lp->n) glp_sdf_error(data, "wrong number of columns\n"); /* primal status, dual status, objective value */ k = glp_sdf_read_int(data); if (!(k == GLP_UNDEF || k == GLP_FEAS || k == GLP_INFEAS || k == GLP_NOFEAS)) glp_sdf_error(data, "invalid primal status\n"); lp->pbs_stat = k; k = glp_sdf_read_int(data); if (!(k == GLP_UNDEF || k == GLP_FEAS || k == GLP_INFEAS || k == GLP_NOFEAS)) glp_sdf_error(data, "invalid dual status\n"); lp->dbs_stat = k; lp->obj_val = glp_sdf_read_num(data); /* rows (auxiliary variables) */ for (i = 1; i <= lp->m; i++) { GLPROW *row = lp->row[i]; /* status, primal value, dual value */ k = glp_sdf_read_int(data); if (!(k == GLP_BS || k == GLP_NL || k == GLP_NU || k == GLP_NF || k == GLP_NS)) glp_sdf_error(data, "invalid row status\n"); glp_set_row_stat(lp, i, k); row->prim = glp_sdf_read_num(data); row->dual = glp_sdf_read_num(data); } /* columns (structural variables) */ for (j = 1; j <= lp->n; j++) { GLPCOL *col = lp->col[j]; /* status, primal value, dual value */ k = glp_sdf_read_int(data); if (!(k == GLP_BS || k == GLP_NL || k == GLP_NU || k == GLP_NF || k == GLP_NS)) glp_sdf_error(data, "invalid column status\n"); glp_set_col_stat(lp, j, k); col->prim = glp_sdf_read_num(data); col->dual = glp_sdf_read_num(data); } xprintf("%d lines were read\n", glp_sdf_line(data)); done: if (ret) lp->pbs_stat = lp->dbs_stat = GLP_UNDEF; if (data != NULL) glp_sdf_close_file(data); return ret; } /*********************************************************************** * NAME * * glp_write_sol - write basic solution to text file * * SYNOPSIS * * int glp_write_sol(glp_prob *lp, const char *fname); * * DESCRIPTION * * The routine glp_write_sol writes the current basic solution to a * text file whose name is specified by the parameter fname. This file * can be read back with the routine glp_read_sol. * * RETURNS * * On success the routine returns zero, otherwise non-zero. * * FILE FORMAT * * The file created by the routine glp_write_sol is a plain text file, * which contains the following information: * * m n * p_stat d_stat obj_val * r_stat[1] r_prim[1] r_dual[1] * . . . * r_stat[m] r_prim[m] r_dual[m] * c_stat[1] c_prim[1] c_dual[1] * . . . * c_stat[n] c_prim[n] c_dual[n] * * where: * m is the number of rows (auxiliary variables); * n is the number of columns (structural variables); * p_stat is the primal status of the basic solution (GLP_UNDEF = 1, * GLP_FEAS = 2, GLP_INFEAS = 3, or GLP_NOFEAS = 4); * d_stat is the dual status of the basic solution (GLP_UNDEF = 1, * GLP_FEAS = 2, GLP_INFEAS = 3, or GLP_NOFEAS = 4); * obj_val is the objective value; * r_stat[i], i = 1,...,m, is the status of i-th row (GLP_BS = 1, * GLP_NL = 2, GLP_NU = 3, GLP_NF = 4, or GLP_NS = 5); * r_prim[i], i = 1,...,m, is the primal value of i-th row; * r_dual[i], i = 1,...,m, is the dual value of i-th row; * c_stat[j], j = 1,...,n, is the status of j-th column (GLP_BS = 1, * GLP_NL = 2, GLP_NU = 3, GLP_NF = 4, or GLP_NS = 5); * c_prim[j], j = 1,...,n, is the primal value of j-th column; * c_dual[j], j = 1,...,n, is the dual value of j-th column. */ int glp_write_sol(glp_prob *lp, const char *fname) { XFILE *fp; int i, j, ret = 0; xprintf("Writing basic solution to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* number of rows, number of columns */ xfprintf(fp, "%d %d\n", lp->m, lp->n); /* primal status, dual status, objective value */ xfprintf(fp, "%d %d %.*g\n", lp->pbs_stat, lp->dbs_stat, DBL_DIG, lp->obj_val); /* rows (auxiliary variables) */ for (i = 1; i <= lp->m; i++) { GLPROW *row = lp->row[i]; /* status, primal value, dual value */ xfprintf(fp, "%d %.*g %.*g\n", row->stat, DBL_DIG, row->prim, DBL_DIG, row->dual); } /* columns (structural variables) */ for (j = 1; j <= lp->n; j++) { GLPCOL *col = lp->col[j]; /* status, primal value, dual value */ xfprintf(fp, "%d %.*g %.*g\n", col->stat, DBL_DIG, col->prim, DBL_DIG, col->dual); } xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xprintf("%d lines were written\n", 2 + lp->m + lp->n); done: if (fp != NULL) xfclose(fp); return ret; } /**********************************************************************/ static char *format(char buf[13+1], double x) { /* format floating-point number in MPS/360-like style */ if (x == -DBL_MAX) strcpy(buf, " -Inf"); else if (x == +DBL_MAX) strcpy(buf, " +Inf"); else if (fabs(x) <= 999999.99998) { sprintf(buf, "%13.5f", x); #if 1 if (strcmp(buf, " 0.00000") == 0 || strcmp(buf, " -0.00000") == 0) strcpy(buf, " . "); else if (memcmp(buf, " 0.", 8) == 0) memcpy(buf, " .", 8); else if (memcmp(buf, " -0.", 8) == 0) memcpy(buf, " -.", 8); #endif } else sprintf(buf, "%13.6g", x); return buf; } int glp_print_ranges(glp_prob *P, int len, const int list[], int flags, const char *fname) { /* print sensitivity analysis report */ XFILE *fp = NULL; GLPROW *row; GLPCOL *col; int m, n, pass, k, t, numb, type, stat, var1, var2, count, page, ret; double lb, ub, slack, coef, prim, dual, value1, value2, coef1, coef2, obj1, obj2; const char *name, *limit; char buf[13+1]; /* sanity checks */ if (P == NULL || P->magic != GLP_PROB_MAGIC) xerror("glp_print_ranges: P = %p; invalid problem object\n", P); m = P->m, n = P->n; if (len < 0) xerror("glp_print_ranges: len = %d; invalid list length\n", len); if (len > 0) { if (list == NULL) xerror("glp_print_ranges: list = %p: invalid parameter\n", list); for (t = 1; t <= len; t++) { k = list[t]; if (!(1 <= k && k <= m+n)) xerror("glp_print_ranges: list[%d] = %d; row/column numb" "er out of range\n", t, k); } } if (flags != 0) xerror("glp_print_ranges: flags = %d; invalid parameter\n", flags); if (fname == NULL) xerror("glp_print_ranges: fname = %p; invalid parameter\n", fname); if (glp_get_status(P) != GLP_OPT) { xprintf("glp_print_ranges: optimal basic solution required\n"); ret = 1; goto done; } if (!glp_bf_exists(P)) { xprintf("glp_print_ranges: basis factorization required\n"); ret = 2; goto done; } /* start reporting */ xprintf("Write sensitivity analysis report to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 3; goto done; } page = count = 0; for (pass = 1; pass <= 2; pass++) for (t = 1; t <= (len == 0 ? m+n : len); t++) { if (t == 1) count = 0; k = (len == 0 ? t : list[t]); if (pass == 1 && k > m || pass == 2 && k <= m) continue; if (count == 0) { xfprintf(fp, "GLPK %-4s - SENSITIVITY ANALYSIS REPORT%73sPa" "ge%4d\n", glp_version(), "", ++page); xfprintf(fp, "\n"); xfprintf(fp, "%-12s%s\n", "Problem:", P->name == NULL ? "" : P->name); xfprintf(fp, "%-12s%s%s%.10g (%s)\n", "Objective:", P->obj == NULL ? "" : P->obj, P->obj == NULL ? "" : " = ", P->obj_val, P->dir == GLP_MIN ? "MINimum" : P->dir == GLP_MAX ? "MAXimum" : "???"); xfprintf(fp, "\n"); xfprintf(fp, "%6s %-12s %2s %13s %13s %13s %13s %13s %13s " "%s\n", "No.", pass == 1 ? "Row name" : "Column name", "St", "Activity", pass == 1 ? "Slack" : "Obj coef", "Lower bound", "Activity", "Obj coef", "Obj value at", "Limiting"); xfprintf(fp, "%6s %-12s %2s %13s %13s %13s %13s %13s %13s " "%s\n", "", "", "", "", "Marginal", "Upper bound", "range", "range", "break point", "variable"); xfprintf(fp, "------ ------------ -- ------------- --------" "----- ------------- ------------- ------------- ------" "------- ------------\n"); } if (pass == 1) { numb = k; xassert(1 <= numb && numb <= m); row = P->row[numb]; name = row->name; type = row->type; lb = glp_get_row_lb(P, numb); ub = glp_get_row_ub(P, numb); coef = 0.0; stat = row->stat; prim = row->prim; if (type == GLP_FR) slack = - prim; else if (type == GLP_LO) slack = lb - prim; else if (type == GLP_UP || type == GLP_DB || type == GLP_FX) slack = ub - prim; dual = row->dual; } else { numb = k - m; xassert(1 <= numb && numb <= n); col = P->col[numb]; name = col->name; lb = glp_get_col_lb(P, numb); ub = glp_get_col_ub(P, numb); coef = col->coef; stat = col->stat; prim = col->prim; slack = 0.0; dual = col->dual; } if (stat != GLP_BS) { glp_analyze_bound(P, k, &value1, &var1, &value2, &var2); if (stat == GLP_NF) coef1 = coef2 = coef; else if (stat == GLP_NS) coef1 = -DBL_MAX, coef2 = +DBL_MAX; else if (stat == GLP_NL && P->dir == GLP_MIN || stat == GLP_NU && P->dir == GLP_MAX) coef1 = coef - dual, coef2 = +DBL_MAX; else coef1 = -DBL_MAX, coef2 = coef - dual; if (value1 == -DBL_MAX) { if (dual < -1e-9) obj1 = +DBL_MAX; else if (dual > +1e-9) obj1 = -DBL_MAX; else obj1 = P->obj_val; } else obj1 = P->obj_val + dual * (value1 - prim); if (value2 == +DBL_MAX) { if (dual < -1e-9) obj2 = -DBL_MAX; else if (dual > +1e-9) obj2 = +DBL_MAX; else obj2 = P->obj_val; } else obj2 = P->obj_val + dual * (value2 - prim); } else { glp_analyze_coef(P, k, &coef1, &var1, &value1, &coef2, &var2, &value2); if (coef1 == -DBL_MAX) { if (prim < -1e-9) obj1 = +DBL_MAX; else if (prim > +1e-9) obj1 = -DBL_MAX; else obj1 = P->obj_val; } else obj1 = P->obj_val + (coef1 - coef) * prim; if (coef2 == +DBL_MAX) { if (prim < -1e-9) obj2 = -DBL_MAX; else if (prim > +1e-9) obj2 = +DBL_MAX; else obj2 = P->obj_val; } else obj2 = P->obj_val + (coef2 - coef) * prim; } /*** first line ***/ /* row/column number */ xfprintf(fp, "%6d", numb); /* row/column name */ xfprintf(fp, " %-12.12s", name == NULL ? "" : name); if (name != NULL && strlen(name) > 12) xfprintf(fp, "%s\n%6s %12s", name+12, "", ""); /* row/column status */ xfprintf(fp, " %2s", stat == GLP_BS ? "BS" : stat == GLP_NL ? "NL" : stat == GLP_NU ? "NU" : stat == GLP_NF ? "NF" : stat == GLP_NS ? "NS" : "??"); /* row/column activity */ xfprintf(fp, " %s", format(buf, prim)); /* row slack, column objective coefficient */ xfprintf(fp, " %s", format(buf, k <= m ? slack : coef)); /* row/column lower bound */ xfprintf(fp, " %s", format(buf, lb)); /* row/column activity range */ xfprintf(fp, " %s", format(buf, value1)); /* row/column objective coefficient range */ xfprintf(fp, " %s", format(buf, coef1)); /* objective value at break point */ xfprintf(fp, " %s", format(buf, obj1)); /* limiting variable name */ if (var1 != 0) { if (var1 <= m) limit = glp_get_row_name(P, var1); else limit = glp_get_col_name(P, var1 - m); if (limit != NULL) xfprintf(fp, " %s", limit); } xfprintf(fp, "\n"); /*** second line ***/ xfprintf(fp, "%6s %-12s %2s %13s", "", "", "", ""); /* row/column reduced cost */ xfprintf(fp, " %s", format(buf, dual)); /* row/column upper bound */ xfprintf(fp, " %s", format(buf, ub)); /* row/column activity range */ xfprintf(fp, " %s", format(buf, value2)); /* row/column objective coefficient range */ xfprintf(fp, " %s", format(buf, coef2)); /* objective value at break point */ xfprintf(fp, " %s", format(buf, obj2)); /* limiting variable name */ if (var2 != 0) { if (var2 <= m) limit = glp_get_row_name(P, var2); else limit = glp_get_col_name(P, var2 - m); if (limit != NULL) xfprintf(fp, " %s", limit); } xfprintf(fp, "\n"); xfprintf(fp, "\n"); /* print 10 items per page */ count = (count + 1) % 10; } xfprintf(fp, "End of report\n"); xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 4; goto done; } ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /**********************************************************************/ int glp_print_ipt(glp_prob *P, const char *fname) { /* write interior-point solution in printable format */ XFILE *fp; GLPROW *row; GLPCOL *col; int i, j, t, ae_ind, re_ind, ret; double ae_max, re_max; xprintf("Writing interior-point solution to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xfprintf(fp, "%-12s%s\n", "Problem:", P->name == NULL ? "" : P->name); xfprintf(fp, "%-12s%d\n", "Rows:", P->m); xfprintf(fp, "%-12s%d\n", "Columns:", P->n); xfprintf(fp, "%-12s%d\n", "Non-zeros:", P->nnz); t = glp_ipt_status(P); xfprintf(fp, "%-12s%s\n", "Status:", t == GLP_OPT ? "OPTIMAL" : t == GLP_UNDEF ? "UNDEFINED" : t == GLP_INFEAS ? "INFEASIBLE (INTERMEDIATE)" : t == GLP_NOFEAS ? "INFEASIBLE (FINAL)" : "???"); xfprintf(fp, "%-12s%s%s%.10g (%s)\n", "Objective:", P->obj == NULL ? "" : P->obj, P->obj == NULL ? "" : " = ", P->ipt_obj, P->dir == GLP_MIN ? "MINimum" : P->dir == GLP_MAX ? "MAXimum" : "???"); xfprintf(fp, "\n"); xfprintf(fp, " No. Row name Activity Lower bound " " Upper bound Marginal\n"); xfprintf(fp, "------ ------------ ------------- ------------- " "------------- -------------\n"); for (i = 1; i <= P->m; i++) { row = P->row[i]; xfprintf(fp, "%6d ", i); if (row->name == NULL || strlen(row->name) <= 12) xfprintf(fp, "%-12s ", row->name == NULL ? "" : row->name); else xfprintf(fp, "%s\n%20s", row->name, ""); xfprintf(fp, "%3s", ""); xfprintf(fp, "%13.6g ", fabs(row->pval) <= 1e-9 ? 0.0 : row->pval); if (row->type == GLP_LO || row->type == GLP_DB || row->type == GLP_FX) xfprintf(fp, "%13.6g ", row->lb); else xfprintf(fp, "%13s ", ""); if (row->type == GLP_UP || row->type == GLP_DB) xfprintf(fp, "%13.6g ", row->ub); else xfprintf(fp, "%13s ", row->type == GLP_FX ? "=" : ""); if (fabs(row->dval) <= 1e-9) xfprintf(fp, "%13s", "< eps"); else xfprintf(fp, "%13.6g ", row->dval); xfprintf(fp, "\n"); } xfprintf(fp, "\n"); xfprintf(fp, " No. Column name Activity Lower bound " " Upper bound Marginal\n"); xfprintf(fp, "------ ------------ ------------- ------------- " "------------- -------------\n"); for (j = 1; j <= P->n; j++) { col = P->col[j]; xfprintf(fp, "%6d ", j); if (col->name == NULL || strlen(col->name) <= 12) xfprintf(fp, "%-12s ", col->name == NULL ? "" : col->name); else xfprintf(fp, "%s\n%20s", col->name, ""); xfprintf(fp, "%3s", ""); xfprintf(fp, "%13.6g ", fabs(col->pval) <= 1e-9 ? 0.0 : col->pval); if (col->type == GLP_LO || col->type == GLP_DB || col->type == GLP_FX) xfprintf(fp, "%13.6g ", col->lb); else xfprintf(fp, "%13s ", ""); if (col->type == GLP_UP || col->type == GLP_DB) xfprintf(fp, "%13.6g ", col->ub); else xfprintf(fp, "%13s ", col->type == GLP_FX ? "=" : ""); if (fabs(col->dval) <= 1e-9) xfprintf(fp, "%13s", "< eps"); else xfprintf(fp, "%13.6g ", col->dval); xfprintf(fp, "\n"); } xfprintf(fp, "\n"); xfprintf(fp, "Karush-Kuhn-Tucker optimality conditions:\n"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_IPT, GLP_KKT_PE, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.PE: max.abs.err = %.2e on row %d\n", ae_max, ae_ind); xfprintf(fp, " max.rel.err = %.2e on row %d\n", re_max, re_ind); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "PRIMAL SOLUTION IS WRONG"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_IPT, GLP_KKT_PB, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.PB: max.abs.err = %.2e on %s %d\n", ae_max, ae_ind <= P->m ? "row" : "column", ae_ind <= P->m ? ae_ind : ae_ind - P->m); xfprintf(fp, " max.rel.err = %.2e on %s %d\n", re_max, re_ind <= P->m ? "row" : "column", re_ind <= P->m ? re_ind : re_ind - P->m); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "PRIMAL SOLUTION IS INFEASIBL" "E"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_IPT, GLP_KKT_DE, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.DE: max.abs.err = %.2e on column %d\n", ae_max, ae_ind == 0 ? 0 : ae_ind - P->m); xfprintf(fp, " max.rel.err = %.2e on column %d\n", re_max, re_ind == 0 ? 0 : re_ind - P->m); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "DUAL SOLUTION IS WRONG"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_IPT, GLP_KKT_DB, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.DB: max.abs.err = %.2e on %s %d\n", ae_max, ae_ind <= P->m ? "row" : "column", ae_ind <= P->m ? ae_ind : ae_ind - P->m); xfprintf(fp, " max.rel.err = %.2e on %s %d\n", re_max, re_ind <= P->m ? "row" : "column", re_ind <= P->m ? re_ind : re_ind - P->m); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "DUAL SOLUTION IS INFEASIBLE") ; xfprintf(fp, "\n"); xfprintf(fp, "End of output\n"); xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /*********************************************************************** * NAME * * glp_read_ipt - read interior-point solution from text file * * SYNOPSIS * * int glp_read_ipt(glp_prob *lp, const char *fname); * * DESCRIPTION * * The routine glp_read_ipt reads interior-point solution from a text * file whose name is specified by the parameter fname into the problem * object. * * For the file format see description of the routine glp_write_ipt. * * RETURNS * * On success the routine returns zero, otherwise non-zero. */ int glp_read_ipt(glp_prob *lp, const char *fname) { glp_data *data; jmp_buf jump; int i, j, k, ret = 0; xprintf("Reading interior-point solution from `%s'...\n", fname); data = glp_sdf_open_file(fname); if (data == NULL) { ret = 1; goto done; } if (setjmp(jump)) { ret = 1; goto done; } glp_sdf_set_jump(data, jump); /* number of rows, number of columns */ k = glp_sdf_read_int(data); if (k != lp->m) glp_sdf_error(data, "wrong number of rows\n"); k = glp_sdf_read_int(data); if (k != lp->n) glp_sdf_error(data, "wrong number of columns\n"); /* solution status, objective value */ k = glp_sdf_read_int(data); if (!(k == GLP_UNDEF || k == GLP_OPT)) glp_sdf_error(data, "invalid solution status\n"); lp->ipt_stat = k; lp->ipt_obj = glp_sdf_read_num(data); /* rows (auxiliary variables) */ for (i = 1; i <= lp->m; i++) { GLPROW *row = lp->row[i]; /* primal value, dual value */ row->pval = glp_sdf_read_num(data); row->dval = glp_sdf_read_num(data); } /* columns (structural variables) */ for (j = 1; j <= lp->n; j++) { GLPCOL *col = lp->col[j]; /* primal value, dual value */ col->pval = glp_sdf_read_num(data); col->dval = glp_sdf_read_num(data); } xprintf("%d lines were read\n", glp_sdf_line(data)); done: if (ret) lp->ipt_stat = GLP_UNDEF; if (data != NULL) glp_sdf_close_file(data); return ret; } /*********************************************************************** * NAME * * glp_write_ipt - write interior-point solution to text file * * SYNOPSIS * * int glp_write_ipt(glp_prob *lp, const char *fname); * * DESCRIPTION * * The routine glp_write_ipt writes the current interior-point solution * to a text file whose name is specified by the parameter fname. This * file can be read back with the routine glp_read_ipt. * * RETURNS * * On success the routine returns zero, otherwise non-zero. * * FILE FORMAT * * The file created by the routine glp_write_ipt is a plain text file, * which contains the following information: * * m n * stat obj_val * r_prim[1] r_dual[1] * . . . * r_prim[m] r_dual[m] * c_prim[1] c_dual[1] * . . . * c_prim[n] c_dual[n] * * where: * m is the number of rows (auxiliary variables); * n is the number of columns (structural variables); * stat is the solution status (GLP_UNDEF = 1 or GLP_OPT = 5); * obj_val is the objective value; * r_prim[i], i = 1,...,m, is the primal value of i-th row; * r_dual[i], i = 1,...,m, is the dual value of i-th row; * c_prim[j], j = 1,...,n, is the primal value of j-th column; * c_dual[j], j = 1,...,n, is the dual value of j-th column. */ int glp_write_ipt(glp_prob *lp, const char *fname) { XFILE *fp; int i, j, ret = 0; xprintf("Writing interior-point solution to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* number of rows, number of columns */ xfprintf(fp, "%d %d\n", lp->m, lp->n); /* solution status, objective value */ xfprintf(fp, "%d %.*g\n", lp->ipt_stat, DBL_DIG, lp->ipt_obj); /* rows (auxiliary variables) */ for (i = 1; i <= lp->m; i++) { GLPROW *row = lp->row[i]; /* primal value, dual value */ xfprintf(fp, "%.*g %.*g\n", DBL_DIG, row->pval, DBL_DIG, row->dval); } /* columns (structural variables) */ for (j = 1; j <= lp->n; j++) { GLPCOL *col = lp->col[j]; /* primal value, dual value */ xfprintf(fp, "%.*g %.*g\n", DBL_DIG, col->pval, DBL_DIG, col->dval); } xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xprintf("%d lines were written\n", 2 + lp->m + lp->n); done: if (fp != NULL) xfclose(fp); return ret; } /**********************************************************************/ int glp_print_mip(glp_prob *P, const char *fname) { /* write MIP solution in printable format */ XFILE *fp; GLPROW *row; GLPCOL *col; int i, j, t, ae_ind, re_ind, ret; double ae_max, re_max; xprintf("Writing MIP solution to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xfprintf(fp, "%-12s%s\n", "Problem:", P->name == NULL ? "" : P->name); xfprintf(fp, "%-12s%d\n", "Rows:", P->m); xfprintf(fp, "%-12s%d (%d integer, %d binary)\n", "Columns:", P->n, glp_get_num_int(P), glp_get_num_bin(P)); xfprintf(fp, "%-12s%d\n", "Non-zeros:", P->nnz); t = glp_mip_status(P); xfprintf(fp, "%-12s%s\n", "Status:", t == GLP_OPT ? "INTEGER OPTIMAL" : t == GLP_FEAS ? "INTEGER NON-OPTIMAL" : t == GLP_NOFEAS ? "INTEGER EMPTY" : t == GLP_UNDEF ? "INTEGER UNDEFINED" : "???"); xfprintf(fp, "%-12s%s%s%.10g (%s)\n", "Objective:", P->obj == NULL ? "" : P->obj, P->obj == NULL ? "" : " = ", P->mip_obj, P->dir == GLP_MIN ? "MINimum" : P->dir == GLP_MAX ? "MAXimum" : "???"); xfprintf(fp, "\n"); xfprintf(fp, " No. Row name Activity Lower bound " " Upper bound\n"); xfprintf(fp, "------ ------------ ------------- ------------- " "-------------\n"); for (i = 1; i <= P->m; i++) { row = P->row[i]; xfprintf(fp, "%6d ", i); if (row->name == NULL || strlen(row->name) <= 12) xfprintf(fp, "%-12s ", row->name == NULL ? "" : row->name); else xfprintf(fp, "%s\n%20s", row->name, ""); xfprintf(fp, "%3s", ""); xfprintf(fp, "%13.6g ", fabs(row->mipx) <= 1e-9 ? 0.0 : row->mipx); if (row->type == GLP_LO || row->type == GLP_DB || row->type == GLP_FX) xfprintf(fp, "%13.6g ", row->lb); else xfprintf(fp, "%13s ", ""); if (row->type == GLP_UP || row->type == GLP_DB) xfprintf(fp, "%13.6g ", row->ub); else xfprintf(fp, "%13s ", row->type == GLP_FX ? "=" : ""); xfprintf(fp, "\n"); } xfprintf(fp, "\n"); xfprintf(fp, " No. Column name Activity Lower bound " " Upper bound\n"); xfprintf(fp, "------ ------------ ------------- ------------- " "-------------\n"); for (j = 1; j <= P->n; j++) { col = P->col[j]; xfprintf(fp, "%6d ", j); if (col->name == NULL || strlen(col->name) <= 12) xfprintf(fp, "%-12s ", col->name == NULL ? "" : col->name); else xfprintf(fp, "%s\n%20s", col->name, ""); xfprintf(fp, "%s ", col->kind == GLP_CV ? " " : col->kind == GLP_IV ? "*" : "?"); xfprintf(fp, "%13.6g ", fabs(col->mipx) <= 1e-9 ? 0.0 : col->mipx); if (col->type == GLP_LO || col->type == GLP_DB || col->type == GLP_FX) xfprintf(fp, "%13.6g ", col->lb); else xfprintf(fp, "%13s ", ""); if (col->type == GLP_UP || col->type == GLP_DB) xfprintf(fp, "%13.6g ", col->ub); else xfprintf(fp, "%13s ", col->type == GLP_FX ? "=" : ""); xfprintf(fp, "\n"); } xfprintf(fp, "\n"); xfprintf(fp, "Integer feasibility conditions:\n"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_MIP, GLP_KKT_PE, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.PE: max.abs.err = %.2e on row %d\n", ae_max, ae_ind); xfprintf(fp, " max.rel.err = %.2e on row %d\n", re_max, re_ind); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "SOLUTION IS WRONG"); xfprintf(fp, "\n"); _glp_check_kkt(P, GLP_MIP, GLP_KKT_PB, &ae_max, &ae_ind, &re_max, &re_ind); xfprintf(fp, "KKT.PB: max.abs.err = %.2e on %s %d\n", ae_max, ae_ind <= P->m ? "row" : "column", ae_ind <= P->m ? ae_ind : ae_ind - P->m); xfprintf(fp, " max.rel.err = %.2e on %s %d\n", re_max, re_ind <= P->m ? "row" : "column", re_ind <= P->m ? re_ind : re_ind - P->m); xfprintf(fp, "%8s%s\n", "", re_max <= 1e-9 ? "High quality" : re_max <= 1e-6 ? "Medium quality" : re_max <= 1e-3 ? "Low quality" : "SOLUTION IS INFEASIBLE"); xfprintf(fp, "\n"); xfprintf(fp, "End of output\n"); xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /*********************************************************************** * NAME * * glp_read_mip - read MIP solution from text file * * SYNOPSIS * * int glp_read_mip(glp_prob *mip, const char *fname); * * DESCRIPTION * * The routine glp_read_mip reads MIP solution from a text file whose * name is specified by the parameter fname into the problem object. * * For the file format see description of the routine glp_write_mip. * * RETURNS * * On success the routine returns zero, otherwise non-zero. */ int glp_read_mip(glp_prob *mip, const char *fname) { glp_data *data; jmp_buf jump; int i, j, k, ret = 0; xprintf("Reading MIP solution from `%s'...\n", fname); data = glp_sdf_open_file(fname); if (data == NULL) { ret = 1; goto done; } if (setjmp(jump)) { ret = 1; goto done; } glp_sdf_set_jump(data, jump); /* number of rows, number of columns */ k = glp_sdf_read_int(data); if (k != mip->m) glp_sdf_error(data, "wrong number of rows\n"); k = glp_sdf_read_int(data); if (k != mip->n) glp_sdf_error(data, "wrong number of columns\n"); /* solution status, objective value */ k = glp_sdf_read_int(data); if (!(k == GLP_UNDEF || k == GLP_OPT || k == GLP_FEAS || k == GLP_NOFEAS)) glp_sdf_error(data, "invalid solution status\n"); mip->mip_stat = k; mip->mip_obj = glp_sdf_read_num(data); /* rows (auxiliary variables) */ for (i = 1; i <= mip->m; i++) { GLPROW *row = mip->row[i]; row->mipx = glp_sdf_read_num(data); } /* columns (structural variables) */ for (j = 1; j <= mip->n; j++) { GLPCOL *col = mip->col[j]; col->mipx = glp_sdf_read_num(data); if (col->kind == GLP_IV && col->mipx != floor(col->mipx)) glp_sdf_error(data, "non-integer column value"); } xprintf("%d lines were read\n", glp_sdf_line(data)); done: if (ret) mip->mip_stat = GLP_UNDEF; if (data != NULL) glp_sdf_close_file(data); return ret; } /*********************************************************************** * NAME * * glp_write_mip - write MIP solution to text file * * SYNOPSIS * * int glp_write_mip(glp_prob *mip, const char *fname); * * DESCRIPTION * * The routine glp_write_mip writes the current MIP solution to a text * file whose name is specified by the parameter fname. This file can * be read back with the routine glp_read_mip. * * RETURNS * * On success the routine returns zero, otherwise non-zero. * * FILE FORMAT * * The file created by the routine glp_write_sol is a plain text file, * which contains the following information: * * m n * stat obj_val * r_val[1] * . . . * r_val[m] * c_val[1] * . . . * c_val[n] * * where: * m is the number of rows (auxiliary variables); * n is the number of columns (structural variables); * stat is the solution status (GLP_UNDEF = 1, GLP_FEAS = 2, * GLP_NOFEAS = 4, or GLP_OPT = 5); * obj_val is the objective value; * r_val[i], i = 1,...,m, is the value of i-th row; * c_val[j], j = 1,...,n, is the value of j-th column. */ int glp_write_mip(glp_prob *mip, const char *fname) { XFILE *fp; int i, j, ret = 0; xprintf("Writing MIP solution to `%s'...\n", fname); fp = xfopen(fname, "w"); if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* number of rows, number of columns */ xfprintf(fp, "%d %d\n", mip->m, mip->n); /* solution status, objective value */ xfprintf(fp, "%d %.*g\n", mip->mip_stat, DBL_DIG, mip->mip_obj); /* rows (auxiliary variables) */ for (i = 1; i <= mip->m; i++) xfprintf(fp, "%.*g\n", DBL_DIG, mip->row[i]->mipx); /* columns (structural variables) */ for (j = 1; j <= mip->n; j++) xfprintf(fp, "%.*g\n", DBL_DIG, mip->col[j]->mipx); xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xprintf("%d lines were written\n", 2 + mip->m + mip->n); done: if (fp != NULL) xfclose(fp); return ret; } /* eof */ sources_5316/external/glpk/glpmpl01.c0000644000176700017670000053064611411455314016317 0ustar paulpaul/* glpmpl01.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_STDIO #include "glpmpl.h" #define dmp_get_atomv dmp_get_atom /**********************************************************************/ /* * * PROCESSING MODEL SECTION * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- enter_context - enter current token into context queue. -- -- This routine enters the current token into the context queue. */ void enter_context(MPL *mpl) { char *image, *s; if (mpl->token == T_EOF) image = "_|_"; else if (mpl->token == T_STRING) image = "'...'"; else image = mpl->image; xassert(0 <= mpl->c_ptr && mpl->c_ptr < CONTEXT_SIZE); mpl->context[mpl->c_ptr++] = ' '; if (mpl->c_ptr == CONTEXT_SIZE) mpl->c_ptr = 0; for (s = image; *s != '\0'; s++) { mpl->context[mpl->c_ptr++] = *s; if (mpl->c_ptr == CONTEXT_SIZE) mpl->c_ptr = 0; } return; } /*---------------------------------------------------------------------- -- print_context - print current content of context queue. -- -- This routine prints current content of the context queue. */ void print_context(MPL *mpl) { int c; while (mpl->c_ptr > 0) { mpl->c_ptr--; c = mpl->context[0]; memmove(mpl->context, mpl->context+1, CONTEXT_SIZE-1); mpl->context[CONTEXT_SIZE-1] = (char)c; } xprintf("Context: %s%.*s\n", mpl->context[0] == ' ' ? "" : "...", CONTEXT_SIZE, mpl->context); return; } /*---------------------------------------------------------------------- -- get_char - scan next character from input text file. -- -- This routine scans a next ASCII character from the input text file. -- In case of end-of-file, the character is assigned EOF. */ void get_char(MPL *mpl) { int c; if (mpl->c == EOF) goto done; if (mpl->c == '\n') mpl->line++; c = read_char(mpl); if (c == EOF) { if (mpl->c == '\n') mpl->line--; else warning(mpl, "final NL missing before end of file"); } else if (c == '\n') ; else if (isspace(c)) c = ' '; else if (iscntrl(c)) { enter_context(mpl); mpl_error(mpl, "control character 0x%02X not allowed", c); } mpl->c = c; done: return; } /*---------------------------------------------------------------------- -- append_char - append character to current token. -- -- This routine appends the current character to the current token and -- then scans a next character. */ void append_char(MPL *mpl) { xassert(0 <= mpl->imlen && mpl->imlen <= MAX_LENGTH); if (mpl->imlen == MAX_LENGTH) { switch (mpl->token) { case T_NAME: enter_context(mpl); mpl_error(mpl, "symbolic name %s... too long", mpl->image); case T_SYMBOL: enter_context(mpl); mpl_error(mpl, "symbol %s... too long", mpl->image); case T_NUMBER: enter_context(mpl); mpl_error(mpl, "numeric literal %s... too long", mpl->image); case T_STRING: enter_context(mpl); mpl_error(mpl, "string literal too long"); default: xassert(mpl != mpl); } } mpl->image[mpl->imlen++] = (char)mpl->c; mpl->image[mpl->imlen] = '\0'; get_char(mpl); return; } /*---------------------------------------------------------------------- -- get_token - scan next token from input text file. -- -- This routine scans a next token from the input text file using the -- standard finite automation technique. */ void get_token(MPL *mpl) { /* save the current token */ mpl->b_token = mpl->token; mpl->b_imlen = mpl->imlen; strcpy(mpl->b_image, mpl->image); mpl->b_value = mpl->value; /* if the next token is already scanned, make it current */ if (mpl->f_scan) { mpl->f_scan = 0; mpl->token = mpl->f_token; mpl->imlen = mpl->f_imlen; strcpy(mpl->image, mpl->f_image); mpl->value = mpl->f_value; goto done; } loop: /* nothing has been scanned so far */ mpl->token = 0; mpl->imlen = 0; mpl->image[0] = '\0'; mpl->value = 0.0; /* skip any uninteresting characters */ while (mpl->c == ' ' || mpl->c == '\n') get_char(mpl); /* recognize and construct the token */ if (mpl->c == EOF) { /* end-of-file reached */ mpl->token = T_EOF; } else if (mpl->c == '#') { /* comment; skip anything until end-of-line */ while (mpl->c != '\n' && mpl->c != EOF) get_char(mpl); goto loop; } else if (!mpl->flag_d && (isalpha(mpl->c) || mpl->c == '_')) { /* symbolic name or reserved keyword */ mpl->token = T_NAME; while (isalnum(mpl->c) || mpl->c == '_') append_char(mpl); if (strcmp(mpl->image, "and") == 0) mpl->token = T_AND; else if (strcmp(mpl->image, "by") == 0) mpl->token = T_BY; else if (strcmp(mpl->image, "cross") == 0) mpl->token = T_CROSS; else if (strcmp(mpl->image, "diff") == 0) mpl->token = T_DIFF; else if (strcmp(mpl->image, "div") == 0) mpl->token = T_DIV; else if (strcmp(mpl->image, "else") == 0) mpl->token = T_ELSE; else if (strcmp(mpl->image, "if") == 0) mpl->token = T_IF; else if (strcmp(mpl->image, "in") == 0) mpl->token = T_IN; #if 1 /* 21/VII-2006 */ else if (strcmp(mpl->image, "Infinity") == 0) mpl->token = T_INFINITY; #endif else if (strcmp(mpl->image, "inter") == 0) mpl->token = T_INTER; else if (strcmp(mpl->image, "less") == 0) mpl->token = T_LESS; else if (strcmp(mpl->image, "mod") == 0) mpl->token = T_MOD; else if (strcmp(mpl->image, "not") == 0) mpl->token = T_NOT; else if (strcmp(mpl->image, "or") == 0) mpl->token = T_OR; else if (strcmp(mpl->image, "s") == 0 && mpl->c == '.') { mpl->token = T_SPTP; append_char(mpl); if (mpl->c != 't') sptp: { enter_context(mpl); mpl_error(mpl, "keyword s.t. incomplete"); } append_char(mpl); if (mpl->c != '.') goto sptp; append_char(mpl); } else if (strcmp(mpl->image, "symdiff") == 0) mpl->token = T_SYMDIFF; else if (strcmp(mpl->image, "then") == 0) mpl->token = T_THEN; else if (strcmp(mpl->image, "union") == 0) mpl->token = T_UNION; else if (strcmp(mpl->image, "within") == 0) mpl->token = T_WITHIN; } else if (!mpl->flag_d && isdigit(mpl->c)) { /* numeric literal */ mpl->token = T_NUMBER; /* scan integer part */ while (isdigit(mpl->c)) append_char(mpl); /* scan optional fractional part */ if (mpl->c == '.') { append_char(mpl); if (mpl->c == '.') { /* hmm, it is not the fractional part, it is dots that follow the integer part */ mpl->imlen--; mpl->image[mpl->imlen] = '\0'; mpl->f_dots = 1; goto conv; } frac: while (isdigit(mpl->c)) append_char(mpl); } /* scan optional decimal exponent */ if (mpl->c == 'e' || mpl->c == 'E') { append_char(mpl); if (mpl->c == '+' || mpl->c == '-') append_char(mpl); if (!isdigit(mpl->c)) { enter_context(mpl); mpl_error(mpl, "numeric literal %s incomplete", mpl->image); } while (isdigit(mpl->c)) append_char(mpl); } /* there must be no letter following the numeric literal */ if (isalpha(mpl->c) || mpl->c == '_') { enter_context(mpl); mpl_error(mpl, "symbol %s%c... should be enclosed in quotes", mpl->image, mpl->c); } conv: /* convert numeric literal to floating-point */ if (str2num(mpl->image, &mpl->value)) err: { enter_context(mpl); mpl_error(mpl, "cannot convert numeric literal %s to floating-p" "oint number", mpl->image); } } else if (mpl->c == '\'' || mpl->c == '"') { /* character string */ int quote = mpl->c; mpl->token = T_STRING; get_char(mpl); for (;;) { if (mpl->c == '\n' || mpl->c == EOF) { enter_context(mpl); mpl_error(mpl, "unexpected end of line; string literal incom" "plete"); } if (mpl->c == quote) { get_char(mpl); if (mpl->c != quote) break; } append_char(mpl); } } else if (!mpl->flag_d && mpl->c == '+') mpl->token = T_PLUS, append_char(mpl); else if (!mpl->flag_d && mpl->c == '-') mpl->token = T_MINUS, append_char(mpl); else if (mpl->c == '*') { mpl->token = T_ASTERISK, append_char(mpl); if (mpl->c == '*') mpl->token = T_POWER, append_char(mpl); } else if (mpl->c == '/') { mpl->token = T_SLASH, append_char(mpl); if (mpl->c == '*') { /* comment sequence */ get_char(mpl); for (;;) { if (mpl->c == EOF) { /* do not call enter_context at this point */ mpl_error(mpl, "unexpected end of file; comment sequence " "incomplete"); } else if (mpl->c == '*') { get_char(mpl); if (mpl->c == '/') break; } else get_char(mpl); } get_char(mpl); goto loop; } } else if (mpl->c == '^') mpl->token = T_POWER, append_char(mpl); else if (mpl->c == '<') { mpl->token = T_LT, append_char(mpl); if (mpl->c == '=') mpl->token = T_LE, append_char(mpl); else if (mpl->c == '>') mpl->token = T_NE, append_char(mpl); #if 1 /* 11/II-2008 */ else if (mpl->c == '-') mpl->token = T_INPUT, append_char(mpl); #endif } else if (mpl->c == '=') { mpl->token = T_EQ, append_char(mpl); if (mpl->c == '=') append_char(mpl); } else if (mpl->c == '>') { mpl->token = T_GT, append_char(mpl); if (mpl->c == '=') mpl->token = T_GE, append_char(mpl); #if 1 /* 14/VII-2006 */ else if (mpl->c == '>') mpl->token = T_APPEND, append_char(mpl); #endif } else if (mpl->c == '!') { mpl->token = T_NOT, append_char(mpl); if (mpl->c == '=') mpl->token = T_NE, append_char(mpl); } else if (mpl->c == '&') { mpl->token = T_CONCAT, append_char(mpl); if (mpl->c == '&') mpl->token = T_AND, append_char(mpl); } else if (mpl->c == '|') { mpl->token = T_BAR, append_char(mpl); if (mpl->c == '|') mpl->token = T_OR, append_char(mpl); } else if (!mpl->flag_d && mpl->c == '.') { mpl->token = T_POINT, append_char(mpl); if (mpl->f_dots) { /* dots; the first dot was read on the previous call to the scanner, so the current character is the second dot */ mpl->token = T_DOTS; mpl->imlen = 2; strcpy(mpl->image, ".."); mpl->f_dots = 0; } else if (mpl->c == '.') mpl->token = T_DOTS, append_char(mpl); else if (isdigit(mpl->c)) { /* numeric literal that begins with the decimal point */ mpl->token = T_NUMBER, append_char(mpl); goto frac; } } else if (mpl->c == ',') mpl->token = T_COMMA, append_char(mpl); else if (mpl->c == ':') { mpl->token = T_COLON, append_char(mpl); if (mpl->c == '=') mpl->token = T_ASSIGN, append_char(mpl); } else if (mpl->c == ';') mpl->token = T_SEMICOLON, append_char(mpl); else if (mpl->c == '(') mpl->token = T_LEFT, append_char(mpl); else if (mpl->c == ')') mpl->token = T_RIGHT, append_char(mpl); else if (mpl->c == '[') mpl->token = T_LBRACKET, append_char(mpl); else if (mpl->c == ']') mpl->token = T_RBRACKET, append_char(mpl); else if (mpl->c == '{') mpl->token = T_LBRACE, append_char(mpl); else if (mpl->c == '}') mpl->token = T_RBRACE, append_char(mpl); #if 1 /* 11/II-2008 */ else if (mpl->c == '~') mpl->token = T_TILDE, append_char(mpl); #endif else if (isalnum(mpl->c) || strchr("+-._", mpl->c) != NULL) { /* symbol */ xassert(mpl->flag_d); mpl->token = T_SYMBOL; while (isalnum(mpl->c) || strchr("+-._", mpl->c) != NULL) append_char(mpl); switch (str2num(mpl->image, &mpl->value)) { case 0: mpl->token = T_NUMBER; break; case 1: goto err; case 2: break; default: xassert(mpl != mpl); } } else { enter_context(mpl); mpl_error(mpl, "character %c not allowed", mpl->c); } /* enter the current token into the context queue */ enter_context(mpl); /* reset the flag, which may be set by indexing_expression() and is used by expression_list() */ mpl->flag_x = 0; done: return; } /*---------------------------------------------------------------------- -- unget_token - return current token back to input stream. -- -- This routine returns the current token back to the input stream, so -- the previously scanned token becomes the current one. */ void unget_token(MPL *mpl) { /* save the current token, which becomes the next one */ xassert(!mpl->f_scan); mpl->f_scan = 1; mpl->f_token = mpl->token; mpl->f_imlen = mpl->imlen; strcpy(mpl->f_image, mpl->image); mpl->f_value = mpl->value; /* restore the previous token, which becomes the current one */ mpl->token = mpl->b_token; mpl->imlen = mpl->b_imlen; strcpy(mpl->image, mpl->b_image); mpl->value = mpl->b_value; return; } /*---------------------------------------------------------------------- -- is_keyword - check if current token is given non-reserved keyword. -- -- If the current token is given (non-reserved) keyword, this routine -- returns non-zero. Otherwise zero is returned. */ int is_keyword(MPL *mpl, char *keyword) { return mpl->token == T_NAME && strcmp(mpl->image, keyword) == 0; } /*---------------------------------------------------------------------- -- is_reserved - check if current token is reserved keyword. -- -- If the current token is a reserved keyword, this routine returns -- non-zero. Otherwise zero is returned. */ int is_reserved(MPL *mpl) { return mpl->token == T_AND && mpl->image[0] == 'a' || mpl->token == T_BY || mpl->token == T_CROSS || mpl->token == T_DIFF || mpl->token == T_DIV || mpl->token == T_ELSE || mpl->token == T_IF || mpl->token == T_IN || mpl->token == T_INTER || mpl->token == T_LESS || mpl->token == T_MOD || mpl->token == T_NOT && mpl->image[0] == 'n' || mpl->token == T_OR && mpl->image[0] == 'o' || mpl->token == T_SYMDIFF || mpl->token == T_THEN || mpl->token == T_UNION || mpl->token == T_WITHIN; } /*---------------------------------------------------------------------- -- make_code - generate pseudo-code (basic routine). -- -- This routine generates specified pseudo-code. It is assumed that all -- other translator routines use this basic routine. */ CODE *make_code(MPL *mpl, int op, OPERANDS *arg, int type, int dim) { CODE *code; DOMAIN *domain; DOMAIN_BLOCK *block; ARG_LIST *e; /* generate pseudo-code */ code = alloc(CODE); code->op = op; code->vflag = 0; /* is inherited from operand(s) */ /* copy operands and also make them referring to the pseudo-code being generated, because the latter becomes the parent for all its operands */ memset(&code->arg, '?', sizeof(OPERANDS)); switch (op) { case O_NUMBER: code->arg.num = arg->num; break; case O_STRING: code->arg.str = arg->str; break; case O_INDEX: code->arg.index.slot = arg->index.slot; code->arg.index.next = arg->index.next; break; case O_MEMNUM: case O_MEMSYM: for (e = arg->par.list; e != NULL; e = e->next) { xassert(e->x != NULL); xassert(e->x->up == NULL); e->x->up = code; code->vflag |= e->x->vflag; } code->arg.par.par = arg->par.par; code->arg.par.list = arg->par.list; break; case O_MEMSET: for (e = arg->set.list; e != NULL; e = e->next) { xassert(e->x != NULL); xassert(e->x->up == NULL); e->x->up = code; code->vflag |= e->x->vflag; } code->arg.set.set = arg->set.set; code->arg.set.list = arg->set.list; break; case O_MEMVAR: for (e = arg->var.list; e != NULL; e = e->next) { xassert(e->x != NULL); xassert(e->x->up == NULL); e->x->up = code; code->vflag |= e->x->vflag; } code->arg.var.var = arg->var.var; code->arg.var.list = arg->var.list; #if 1 /* 15/V-2010 */ code->arg.var.suff = arg->var.suff; #endif break; #if 1 /* 15/V-2010 */ case O_MEMCON: for (e = arg->con.list; e != NULL; e = e->next) { xassert(e->x != NULL); xassert(e->x->up == NULL); e->x->up = code; code->vflag |= e->x->vflag; } code->arg.con.con = arg->con.con; code->arg.con.list = arg->con.list; code->arg.con.suff = arg->con.suff; break; #endif case O_TUPLE: case O_MAKE: for (e = arg->list; e != NULL; e = e->next) { xassert(e->x != NULL); xassert(e->x->up == NULL); e->x->up = code; code->vflag |= e->x->vflag; } code->arg.list = arg->list; break; case O_SLICE: xassert(arg->slice != NULL); code->arg.slice = arg->slice; break; case O_IRAND224: case O_UNIFORM01: case O_NORMAL01: case O_GMTIME: code->vflag = 1; break; case O_CVTNUM: case O_CVTSYM: case O_CVTLOG: case O_CVTTUP: case O_CVTLFM: case O_PLUS: case O_MINUS: case O_NOT: case O_ABS: case O_CEIL: case O_FLOOR: case O_EXP: case O_LOG: case O_LOG10: case O_SQRT: case O_SIN: case O_COS: case O_ATAN: case O_ROUND: case O_TRUNC: case O_CARD: case O_LENGTH: /* unary operation */ xassert(arg->arg.x != NULL); xassert(arg->arg.x->up == NULL); arg->arg.x->up = code; code->vflag |= arg->arg.x->vflag; code->arg.arg.x = arg->arg.x; break; case O_ADD: case O_SUB: case O_LESS: case O_MUL: case O_DIV: case O_IDIV: case O_MOD: case O_POWER: case O_ATAN2: case O_ROUND2: case O_TRUNC2: case O_UNIFORM: if (op == O_UNIFORM) code->vflag = 1; case O_NORMAL: if (op == O_NORMAL) code->vflag = 1; case O_CONCAT: case O_LT: case O_LE: case O_EQ: case O_GE: case O_GT: case O_NE: case O_AND: case O_OR: case O_UNION: case O_DIFF: case O_SYMDIFF: case O_INTER: case O_CROSS: case O_IN: case O_NOTIN: case O_WITHIN: case O_NOTWITHIN: case O_SUBSTR: case O_STR2TIME: case O_TIME2STR: /* binary operation */ xassert(arg->arg.x != NULL); xassert(arg->arg.x->up == NULL); arg->arg.x->up = code; code->vflag |= arg->arg.x->vflag; xassert(arg->arg.y != NULL); xassert(arg->arg.y->up == NULL); arg->arg.y->up = code; code->vflag |= arg->arg.y->vflag; code->arg.arg.x = arg->arg.x; code->arg.arg.y = arg->arg.y; break; case O_DOTS: case O_FORK: case O_SUBSTR3: /* ternary operation */ xassert(arg->arg.x != NULL); xassert(arg->arg.x->up == NULL); arg->arg.x->up = code; code->vflag |= arg->arg.x->vflag; xassert(arg->arg.y != NULL); xassert(arg->arg.y->up == NULL); arg->arg.y->up = code; code->vflag |= arg->arg.y->vflag; if (arg->arg.z != NULL) { xassert(arg->arg.z->up == NULL); arg->arg.z->up = code; code->vflag |= arg->arg.z->vflag; } code->arg.arg.x = arg->arg.x; code->arg.arg.y = arg->arg.y; code->arg.arg.z = arg->arg.z; break; case O_MIN: case O_MAX: /* n-ary operation */ for (e = arg->list; e != NULL; e = e->next) { xassert(e->x != NULL); xassert(e->x->up == NULL); e->x->up = code; code->vflag |= e->x->vflag; } code->arg.list = arg->list; break; case O_SUM: case O_PROD: case O_MINIMUM: case O_MAXIMUM: case O_FORALL: case O_EXISTS: case O_SETOF: case O_BUILD: /* iterated operation */ domain = arg->loop.domain; xassert(domain != NULL); if (domain->code != NULL) { xassert(domain->code->up == NULL); domain->code->up = code; code->vflag |= domain->code->vflag; } for (block = domain->list; block != NULL; block = block->next) { xassert(block->code != NULL); xassert(block->code->up == NULL); block->code->up = code; code->vflag |= block->code->vflag; } if (arg->loop.x != NULL) { xassert(arg->loop.x->up == NULL); arg->loop.x->up = code; code->vflag |= arg->loop.x->vflag; } code->arg.loop.domain = arg->loop.domain; code->arg.loop.x = arg->loop.x; break; default: xassert(op != op); } /* set other attributes of the pseudo-code */ code->type = type; code->dim = dim; code->up = NULL; code->valid = 0; memset(&code->value, '?', sizeof(VALUE)); return code; } /*---------------------------------------------------------------------- -- make_unary - generate pseudo-code for unary operation. -- -- This routine generates pseudo-code for unary operation. */ CODE *make_unary(MPL *mpl, int op, CODE *x, int type, int dim) { CODE *code; OPERANDS arg; xassert(x != NULL); arg.arg.x = x; code = make_code(mpl, op, &arg, type, dim); return code; } /*---------------------------------------------------------------------- -- make_binary - generate pseudo-code for binary operation. -- -- This routine generates pseudo-code for binary operation. */ CODE *make_binary(MPL *mpl, int op, CODE *x, CODE *y, int type, int dim) { CODE *code; OPERANDS arg; xassert(x != NULL); xassert(y != NULL); arg.arg.x = x; arg.arg.y = y; code = make_code(mpl, op, &arg, type, dim); return code; } /*---------------------------------------------------------------------- -- make_ternary - generate pseudo-code for ternary operation. -- -- This routine generates pseudo-code for ternary operation. */ CODE *make_ternary(MPL *mpl, int op, CODE *x, CODE *y, CODE *z, int type, int dim) { CODE *code; OPERANDS arg; xassert(x != NULL); xassert(y != NULL); /* third operand can be NULL */ arg.arg.x = x; arg.arg.y = y; arg.arg.z = z; code = make_code(mpl, op, &arg, type, dim); return code; } /*---------------------------------------------------------------------- -- numeric_literal - parse reference to numeric literal. -- -- This routine parses primary expression using the syntax: -- -- ::= */ CODE *numeric_literal(MPL *mpl) { CODE *code; OPERANDS arg; xassert(mpl->token == T_NUMBER); arg.num = mpl->value; code = make_code(mpl, O_NUMBER, &arg, A_NUMERIC, 0); get_token(mpl /* */); return code; } /*---------------------------------------------------------------------- -- string_literal - parse reference to string literal. -- -- This routine parses primary expression using the syntax: -- -- ::= */ CODE *string_literal(MPL *mpl) { CODE *code; OPERANDS arg; xassert(mpl->token == T_STRING); arg.str = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(arg.str, mpl->image); code = make_code(mpl, O_STRING, &arg, A_SYMBOLIC, 0); get_token(mpl /* */); return code; } /*---------------------------------------------------------------------- -- create_arg_list - create empty operands list. -- -- This routine creates operands list, which is initially empty. */ ARG_LIST *create_arg_list(MPL *mpl) { ARG_LIST *list; xassert(mpl == mpl); list = NULL; return list; } /*---------------------------------------------------------------------- -- expand_arg_list - append operand to operands list. -- -- This routine appends new operand to specified operands list. */ ARG_LIST *expand_arg_list(MPL *mpl, ARG_LIST *list, CODE *x) { ARG_LIST *tail, *temp; xassert(x != NULL); /* create new operands list entry */ tail = alloc(ARG_LIST); tail->x = x; tail->next = NULL; /* and append it to the operands list */ if (list == NULL) list = tail; else { for (temp = list; temp->next != NULL; temp = temp->next); temp->next = tail; } return list; } /*---------------------------------------------------------------------- -- arg_list_len - determine length of operands list. -- -- This routine returns the number of operands in operands list. */ int arg_list_len(MPL *mpl, ARG_LIST *list) { ARG_LIST *temp; int len; xassert(mpl == mpl); len = 0; for (temp = list; temp != NULL; temp = temp->next) len++; return len; } /*---------------------------------------------------------------------- -- subscript_list - parse subscript list. -- -- This routine parses subscript list using the syntax: -- -- ::= -- ::= , -- ::= */ ARG_LIST *subscript_list(MPL *mpl) { ARG_LIST *list; CODE *x; list = create_arg_list(mpl); for (;;) { /* parse subscript expression */ x = expression_5(mpl); /* convert it to symbolic type, if necessary */ if (x->type == A_NUMERIC) x = make_unary(mpl, O_CVTSYM, x, A_SYMBOLIC, 0); /* check that now the expression is of symbolic type */ if (x->type != A_SYMBOLIC) mpl_error(mpl, "subscript expression has invalid type"); xassert(x->dim == 0); /* and append it to the subscript list */ list = expand_arg_list(mpl, list, x); /* check a token that follows the subscript expression */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_RBRACKET) break; else mpl_error(mpl, "syntax error in subscript list"); } return list; } #if 1 /* 15/V-2010 */ /*---------------------------------------------------------------------- -- object_reference - parse reference to named object. -- -- This routine parses primary expression using the syntax: -- -- ::= -- ::= -- ::= [ ] -- ::= -- ::= [ ] -- ::= -- ::= [ ] -- -- ::= -- ::= [ ] -- -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= | .lb | .ub | .status | .val | .dual */ CODE *object_reference(MPL *mpl) { AVLNODE *node; DOMAIN_SLOT *slot; SET *set; PARAMETER *par; VARIABLE *var; CONSTRAINT *con; ARG_LIST *list; OPERANDS arg; CODE *code; char *name; int dim, suff; /* find the object in the symbolic name table */ xassert(mpl->token == T_NAME); node = avl_find_node(mpl->tree, mpl->image); if (node == NULL) mpl_error(mpl, "%s not defined", mpl->image); /* check the object type and obtain its dimension */ switch (avl_get_node_type(node)) { case A_INDEX: /* dummy index */ slot = (DOMAIN_SLOT *)avl_get_node_link(node); name = slot->name; dim = 0; break; case A_SET: /* model set */ set = (SET *)avl_get_node_link(node); name = set->name; dim = set->dim; /* if a set object is referenced in its own declaration and the dimen attribute is not specified yet, use dimen 1 by default */ if (set->dimen == 0) set->dimen = 1; break; case A_PARAMETER: /* model parameter */ par = (PARAMETER *)avl_get_node_link(node); name = par->name; dim = par->dim; break; case A_VARIABLE: /* model variable */ var = (VARIABLE *)avl_get_node_link(node); name = var->name; dim = var->dim; break; case A_CONSTRAINT: /* model constraint or objective */ con = (CONSTRAINT *)avl_get_node_link(node); name = con->name; dim = con->dim; break; default: xassert(node != node); } get_token(mpl /* */); /* parse optional subscript list */ if (mpl->token == T_LBRACKET) { /* subscript list is specified */ if (dim == 0) mpl_error(mpl, "%s cannot be subscripted", name); get_token(mpl /* [ */); list = subscript_list(mpl); if (dim != arg_list_len(mpl, list)) mpl_error(mpl, "%s must have %d subscript%s rather than %d", name, dim, dim == 1 ? "" : "s", arg_list_len(mpl, list)); xassert(mpl->token == T_RBRACKET); get_token(mpl /* ] */); } else { /* subscript list is not specified */ if (dim != 0) mpl_error(mpl, "%s must be subscripted", name); list = create_arg_list(mpl); } /* parse optional suffix */ if (!mpl->flag_s && avl_get_node_type(node) == A_VARIABLE) suff = DOT_NONE; else suff = DOT_VAL; if (mpl->token == T_POINT) { get_token(mpl /* . */); if (mpl->token != T_NAME) mpl_error(mpl, "invalid use of period"); if (!(avl_get_node_type(node) == A_VARIABLE || avl_get_node_type(node) == A_CONSTRAINT)) mpl_error(mpl, "%s cannot have a suffix", name); if (strcmp(mpl->image, "lb") == 0) suff = DOT_LB; else if (strcmp(mpl->image, "ub") == 0) suff = DOT_UB; else if (strcmp(mpl->image, "status") == 0) suff = DOT_STATUS; else if (strcmp(mpl->image, "val") == 0) suff = DOT_VAL; else if (strcmp(mpl->image, "dual") == 0) suff = DOT_DUAL; else mpl_error(mpl, "suffix .%s invalid", mpl->image); get_token(mpl /* suffix */); } /* generate pseudo-code to take value of the object */ switch (avl_get_node_type(node)) { case A_INDEX: arg.index.slot = slot; arg.index.next = slot->list; code = make_code(mpl, O_INDEX, &arg, A_SYMBOLIC, 0); slot->list = code; break; case A_SET: arg.set.set = set; arg.set.list = list; code = make_code(mpl, O_MEMSET, &arg, A_ELEMSET, set->dimen); break; case A_PARAMETER: arg.par.par = par; arg.par.list = list; if (par->type == A_SYMBOLIC) code = make_code(mpl, O_MEMSYM, &arg, A_SYMBOLIC, 0); else code = make_code(mpl, O_MEMNUM, &arg, A_NUMERIC, 0); break; case A_VARIABLE: if (!mpl->flag_s && (suff == DOT_STATUS || suff == DOT_VAL || suff == DOT_DUAL)) mpl_error(mpl, "invalid reference to status, primal value, o" "r dual value of variable %s above solve statement", var->name); arg.var.var = var; arg.var.list = list; arg.var.suff = suff; code = make_code(mpl, O_MEMVAR, &arg, suff == DOT_NONE ? A_FORMULA : A_NUMERIC, 0); break; case A_CONSTRAINT: if (!mpl->flag_s && (suff == DOT_STATUS || suff == DOT_VAL || suff == DOT_DUAL)) mpl_error(mpl, "invalid reference to status, primal value, o" "r dual value of %s %s above solve statement", con->type == A_CONSTRAINT ? "constraint" : "objective" , con->name); arg.con.con = con; arg.con.list = list; arg.con.suff = suff; code = make_code(mpl, O_MEMCON, &arg, A_NUMERIC, 0); break; default: xassert(node != node); } return code; } #endif /*---------------------------------------------------------------------- -- numeric_argument - parse argument passed to built-in function. -- -- This routine parses an argument passed to numeric built-in function -- using the syntax: -- -- ::= */ CODE *numeric_argument(MPL *mpl, char *func) { CODE *x; x = expression_5(mpl); /* convert the argument to numeric type, if necessary */ if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); /* check that now the argument is of numeric type */ if (x->type != A_NUMERIC) mpl_error(mpl, "argument for %s has invalid type", func); xassert(x->dim == 0); return x; } #if 1 /* 15/VII-2006 */ CODE *symbolic_argument(MPL *mpl, char *func) { CODE *x; x = expression_5(mpl); /* convert the argument to symbolic type, if necessary */ if (x->type == A_NUMERIC) x = make_unary(mpl, O_CVTSYM, x, A_SYMBOLIC, 0); /* check that now the argument is of symbolic type */ if (x->type != A_SYMBOLIC) mpl_error(mpl, "argument for %s has invalid type", func); xassert(x->dim == 0); return x; } #endif #if 1 /* 15/VII-2006 */ CODE *elemset_argument(MPL *mpl, char *func) { CODE *x; x = expression_9(mpl); if (x->type != A_ELEMSET) mpl_error(mpl, "argument for %s has invalid type", func); xassert(x->dim > 0); return x; } #endif /*---------------------------------------------------------------------- -- function_reference - parse reference to built-in function. -- -- This routine parses primary expression using the syntax: -- -- ::= abs ( ) -- ::= ceil ( ) -- ::= floor ( ) -- ::= exp ( ) -- ::= log ( ) -- ::= log10 ( ) -- ::= max ( ) -- ::= min ( ) -- ::= sqrt ( ) -- ::= sin ( ) -- ::= cos ( ) -- ::= atan ( ) -- ::= atan2 ( , ) -- ::= round ( ) -- ::= round ( , ) -- ::= trunc ( ) -- ::= trunc ( , ) -- ::= Irand224 ( ) -- ::= Uniform01 ( ) -- ::= Uniform ( , ) -- ::= Normal01 ( ) -- ::= Normal ( , ) -- ::= card ( ) -- ::= length ( ) -- ::= substr ( , ) -- ::= substr ( , , ) -- ::= str2time ( , ) -- ::= time2str ( , ) -- ::= gmtime ( ) -- ::= -- ::= , */ CODE *function_reference(MPL *mpl) { CODE *code; OPERANDS arg; int op; char func[15+1]; /* determine operation code */ xassert(mpl->token == T_NAME); if (strcmp(mpl->image, "abs") == 0) op = O_ABS; else if (strcmp(mpl->image, "ceil") == 0) op = O_CEIL; else if (strcmp(mpl->image, "floor") == 0) op = O_FLOOR; else if (strcmp(mpl->image, "exp") == 0) op = O_EXP; else if (strcmp(mpl->image, "log") == 0) op = O_LOG; else if (strcmp(mpl->image, "log10") == 0) op = O_LOG10; else if (strcmp(mpl->image, "sqrt") == 0) op = O_SQRT; else if (strcmp(mpl->image, "sin") == 0) op = O_SIN; else if (strcmp(mpl->image, "cos") == 0) op = O_COS; else if (strcmp(mpl->image, "atan") == 0) op = O_ATAN; else if (strcmp(mpl->image, "min") == 0) op = O_MIN; else if (strcmp(mpl->image, "max") == 0) op = O_MAX; else if (strcmp(mpl->image, "round") == 0) op = O_ROUND; else if (strcmp(mpl->image, "trunc") == 0) op = O_TRUNC; else if (strcmp(mpl->image, "Irand224") == 0) op = O_IRAND224; else if (strcmp(mpl->image, "Uniform01") == 0) op = O_UNIFORM01; else if (strcmp(mpl->image, "Uniform") == 0) op = O_UNIFORM; else if (strcmp(mpl->image, "Normal01") == 0) op = O_NORMAL01; else if (strcmp(mpl->image, "Normal") == 0) op = O_NORMAL; else if (strcmp(mpl->image, "card") == 0) op = O_CARD; else if (strcmp(mpl->image, "length") == 0) op = O_LENGTH; else if (strcmp(mpl->image, "substr") == 0) op = O_SUBSTR; else if (strcmp(mpl->image, "str2time") == 0) op = O_STR2TIME; else if (strcmp(mpl->image, "time2str") == 0) op = O_TIME2STR; else if (strcmp(mpl->image, "gmtime") == 0) op = O_GMTIME; else mpl_error(mpl, "function %s unknown", mpl->image); /* save symbolic name of the function */ strcpy(func, mpl->image); xassert(strlen(func) < sizeof(func)); get_token(mpl /* */); /* check the left parenthesis that follows the function name */ xassert(mpl->token == T_LEFT); get_token(mpl /* ( */); /* parse argument list */ if (op == O_MIN || op == O_MAX) { /* min and max allow arbitrary number of arguments */ arg.list = create_arg_list(mpl); /* parse argument list */ for (;;) { /* parse argument and append it to the operands list */ arg.list = expand_arg_list(mpl, arg.list, numeric_argument(mpl, func)); /* check a token that follows the argument */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_RIGHT) break; else mpl_error(mpl, "syntax error in argument list for %s", func); } } else if (op == O_IRAND224 || op == O_UNIFORM01 || op == O_NORMAL01 || op == O_GMTIME) { /* Irand224, Uniform01, Normal01, gmtime need no arguments */ if (mpl->token != T_RIGHT) mpl_error(mpl, "%s needs no arguments", func); } else if (op == O_UNIFORM || op == O_NORMAL) { /* Uniform and Normal need two arguments */ /* parse the first argument */ arg.arg.x = numeric_argument(mpl, func); /* check a token that follows the first argument */ if (mpl->token == T_COMMA) ; else if (mpl->token == T_RIGHT) mpl_error(mpl, "%s needs two arguments", func); else mpl_error(mpl, "syntax error in argument for %s", func); get_token(mpl /* , */); /* parse the second argument */ arg.arg.y = numeric_argument(mpl, func); /* check a token that follows the second argument */ if (mpl->token == T_COMMA) mpl_error(mpl, "%s needs two argument", func); else if (mpl->token == T_RIGHT) ; else mpl_error(mpl, "syntax error in argument for %s", func); } else if (op == O_ATAN || op == O_ROUND || op == O_TRUNC) { /* atan, round, and trunc need one or two arguments */ /* parse the first argument */ arg.arg.x = numeric_argument(mpl, func); /* parse the second argument, if specified */ if (mpl->token == T_COMMA) { switch (op) { case O_ATAN: op = O_ATAN2; break; case O_ROUND: op = O_ROUND2; break; case O_TRUNC: op = O_TRUNC2; break; default: xassert(op != op); } get_token(mpl /* , */); arg.arg.y = numeric_argument(mpl, func); } /* check a token that follows the last argument */ if (mpl->token == T_COMMA) mpl_error(mpl, "%s needs one or two arguments", func); else if (mpl->token == T_RIGHT) ; else mpl_error(mpl, "syntax error in argument for %s", func); } else if (op == O_SUBSTR) { /* substr needs two or three arguments */ /* parse the first argument */ arg.arg.x = symbolic_argument(mpl, func); /* check a token that follows the first argument */ if (mpl->token == T_COMMA) ; else if (mpl->token == T_RIGHT) mpl_error(mpl, "%s needs two or three arguments", func); else mpl_error(mpl, "syntax error in argument for %s", func); get_token(mpl /* , */); /* parse the second argument */ arg.arg.y = numeric_argument(mpl, func); /* parse the third argument, if specified */ if (mpl->token == T_COMMA) { op = O_SUBSTR3; get_token(mpl /* , */); arg.arg.z = numeric_argument(mpl, func); } /* check a token that follows the last argument */ if (mpl->token == T_COMMA) mpl_error(mpl, "%s needs two or three arguments", func); else if (mpl->token == T_RIGHT) ; else mpl_error(mpl, "syntax error in argument for %s", func); } else if (op == O_STR2TIME) { /* str2time needs two arguments, both symbolic */ /* parse the first argument */ arg.arg.x = symbolic_argument(mpl, func); /* check a token that follows the first argument */ if (mpl->token == T_COMMA) ; else if (mpl->token == T_RIGHT) mpl_error(mpl, "%s needs two arguments", func); else mpl_error(mpl, "syntax error in argument for %s", func); get_token(mpl /* , */); /* parse the second argument */ arg.arg.y = symbolic_argument(mpl, func); /* check a token that follows the second argument */ if (mpl->token == T_COMMA) mpl_error(mpl, "%s needs two argument", func); else if (mpl->token == T_RIGHT) ; else mpl_error(mpl, "syntax error in argument for %s", func); } else if (op == O_TIME2STR) { /* time2str needs two arguments, numeric and symbolic */ /* parse the first argument */ arg.arg.x = numeric_argument(mpl, func); /* check a token that follows the first argument */ if (mpl->token == T_COMMA) ; else if (mpl->token == T_RIGHT) mpl_error(mpl, "%s needs two arguments", func); else mpl_error(mpl, "syntax error in argument for %s", func); get_token(mpl /* , */); /* parse the second argument */ arg.arg.y = symbolic_argument(mpl, func); /* check a token that follows the second argument */ if (mpl->token == T_COMMA) mpl_error(mpl, "%s needs two argument", func); else if (mpl->token == T_RIGHT) ; else mpl_error(mpl, "syntax error in argument for %s", func); } else { /* other functions need one argument */ if (op == O_CARD) arg.arg.x = elemset_argument(mpl, func); else if (op == O_LENGTH) arg.arg.x = symbolic_argument(mpl, func); else arg.arg.x = numeric_argument(mpl, func); /* check a token that follows the argument */ if (mpl->token == T_COMMA) mpl_error(mpl, "%s needs one argument", func); else if (mpl->token == T_RIGHT) ; else mpl_error(mpl, "syntax error in argument for %s", func); } /* make pseudo-code to call the built-in function */ if (op == O_SUBSTR || op == O_SUBSTR3 || op == O_TIME2STR) code = make_code(mpl, op, &arg, A_SYMBOLIC, 0); else code = make_code(mpl, op, &arg, A_NUMERIC, 0); /* the reference ends with the right parenthesis */ xassert(mpl->token == T_RIGHT); get_token(mpl /* ) */); return code; } /*---------------------------------------------------------------------- -- create_domain - create empty domain. -- -- This routine creates empty domain, which is initially empty, i.e. -- has no domain blocks. */ DOMAIN *create_domain(MPL *mpl) { DOMAIN *domain; domain = alloc(DOMAIN); domain->list = NULL; domain->code = NULL; return domain; } /*---------------------------------------------------------------------- -- create_block - create empty domain block. -- -- This routine creates empty domain block, which is initially empty, -- i.e. has no domain slots. */ DOMAIN_BLOCK *create_block(MPL *mpl) { DOMAIN_BLOCK *block; block = alloc(DOMAIN_BLOCK); block->list = NULL; block->code = NULL; block->backup = NULL; block->next = NULL; return block; } /*---------------------------------------------------------------------- -- append_block - append domain block to specified domain. -- -- This routine adds given domain block to the end of the block list of -- specified domain. */ void append_block(MPL *mpl, DOMAIN *domain, DOMAIN_BLOCK *block) { DOMAIN_BLOCK *temp; xassert(mpl == mpl); xassert(domain != NULL); xassert(block != NULL); xassert(block->next == NULL); if (domain->list == NULL) domain->list = block; else { for (temp = domain->list; temp->next != NULL; temp = temp->next); temp->next = block; } return; } /*---------------------------------------------------------------------- -- append_slot - create and append new slot to domain block. -- -- This routine creates new domain slot and adds it to the end of slot -- list of specified domain block. -- -- The parameter name is symbolic name of the dummy index associated -- with the slot (the character string must be allocated). NULL means -- the dummy index is not explicitly specified. -- -- The parameter code is pseudo-code for computing symbolic value, at -- which the dummy index is bounded. NULL means the dummy index is free -- in the domain scope. */ DOMAIN_SLOT *append_slot(MPL *mpl, DOMAIN_BLOCK *block, char *name, CODE *code) { DOMAIN_SLOT *slot, *temp; xassert(block != NULL); slot = alloc(DOMAIN_SLOT); slot->name = name; slot->code = code; slot->value = NULL; slot->list = NULL; slot->next = NULL; if (block->list == NULL) block->list = slot; else { for (temp = block->list; temp->next != NULL; temp = temp->next); temp->next = slot; } return slot; } /*---------------------------------------------------------------------- -- expression_list - parse expression list. -- -- This routine parses a list of one or more expressions enclosed into -- the parentheses using the syntax: -- -- ::= ( ) -- ::= -- ::= , -- -- Note that this construction may have three different meanings: -- -- 1. If consists of only one expression, is a parenthesized expression, which may be of any -- valid type (not necessarily 1-tuple). -- -- 2. If consists of several expressions separated by -- commae, where no expression is undeclared symbolic name, is a n-tuple. -- -- 3. If consists of several expressions separated by -- commae, where at least one expression is undeclared symbolic name -- (that denotes a dummy index), is a slice and -- can be only used as constituent of indexing expression. */ #define max_dim 20 /* maximal number of components allowed within parentheses */ CODE *expression_list(MPL *mpl) { CODE *code; OPERANDS arg; struct { char *name; CODE *code; } list[1+max_dim]; int flag_x, next_token, dim, j, slice = 0; xassert(mpl->token == T_LEFT); /* the flag, which allows recognizing undeclared symbolic names as dummy indices, will be automatically reset by get_token(), so save it before scanning the next token */ flag_x = mpl->flag_x; get_token(mpl /* ( */); /* parse */ for (dim = 1; ; dim++) { if (dim > max_dim) mpl_error(mpl, "too many components within parentheses"); /* current component of can be either dummy index or expression */ if (mpl->token == T_NAME) { /* symbolic name is recognized as dummy index only if: the flag, which allows that, is set, and the name is followed by comma or right parenthesis, and the name is undeclared */ get_token(mpl /* */); next_token = mpl->token; unget_token(mpl); if (!(flag_x && (next_token == T_COMMA || next_token == T_RIGHT) && avl_find_node(mpl->tree, mpl->image) == NULL)) { /* this is not dummy index */ goto expr; } /* all dummy indices within the same slice must have unique symbolic names */ for (j = 1; j < dim; j++) { if (list[j].name != NULL && strcmp(list[j].name, mpl->image) == 0) mpl_error(mpl, "duplicate dummy index %s not allowed", mpl->image); } /* current component of is dummy index */ list[dim].name = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(list[dim].name, mpl->image); list[dim].code = NULL; get_token(mpl /* */); /* is a slice, because at least one dummy index has appeared */ slice = 1; /* note that the context ( ) is not allowed, i.e. in this case is considered as a parenthesized expression */ if (dim == 1 && mpl->token == T_RIGHT) mpl_error(mpl, "%s not defined", list[dim].name); } else expr: { /* current component of is expression */ code = expression_13(mpl); /* if the current expression is followed by comma or it is not the very first expression, entire is n-tuple or slice, in which case the current expression should be converted to symbolic type, if necessary */ if (mpl->token == T_COMMA || dim > 1) { if (code->type == A_NUMERIC) code = make_unary(mpl, O_CVTSYM, code, A_SYMBOLIC, 0); /* now the expression must be of symbolic type */ if (code->type != A_SYMBOLIC) mpl_error(mpl, "component expression has invalid type"); xassert(code->dim == 0); } list[dim].name = NULL; list[dim].code = code; } /* check a token that follows the current component */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_RIGHT) break; else mpl_error(mpl, "right parenthesis missing where expected"); } /* generate pseudo-code for */ if (dim == 1 && !slice) { /* is a parenthesized expression */ code = list[1].code; } else if (!slice) { /* is a n-tuple */ arg.list = create_arg_list(mpl); for (j = 1; j <= dim; j++) arg.list = expand_arg_list(mpl, arg.list, list[j].code); code = make_code(mpl, O_TUPLE, &arg, A_TUPLE, dim); } else { /* is a slice */ arg.slice = create_block(mpl); for (j = 1; j <= dim; j++) append_slot(mpl, arg.slice, list[j].name, list[j].code); /* note that actually pseudo-codes with op = O_SLICE are never evaluated */ code = make_code(mpl, O_SLICE, &arg, A_TUPLE, dim); } get_token(mpl /* ) */); /* if is a slice, there must be the keyword 'in', which follows the right parenthesis */ if (slice && mpl->token != T_IN) mpl_error(mpl, "keyword in missing where expected"); /* if the slice flag is set and there is the keyword 'in', which follows , the latter must be a slice */ if (flag_x && mpl->token == T_IN && !slice) { if (dim == 1) mpl_error(mpl, "syntax error in indexing expression"); else mpl_error(mpl, "0-ary slice not allowed"); } return code; } /*---------------------------------------------------------------------- -- literal set - parse literal set. -- -- This routine parses literal set using the syntax: -- -- ::= { } -- ::= -- ::= , -- ::= -- -- It is assumed that the left curly brace and the very first member -- expression that follows it are already parsed. The right curly brace -- remains unscanned on exit. */ CODE *literal_set(MPL *mpl, CODE *code) { OPERANDS arg; int j; xassert(code != NULL); arg.list = create_arg_list(mpl); /* parse */ for (j = 1; ; j++) { /* all member expressions must be n-tuples; so, if the current expression is not n-tuple, convert it to 1-tuple */ if (code->type == A_NUMERIC) code = make_unary(mpl, O_CVTSYM, code, A_SYMBOLIC, 0); if (code->type == A_SYMBOLIC) code = make_unary(mpl, O_CVTTUP, code, A_TUPLE, 1); /* now the expression must be n-tuple */ if (code->type != A_TUPLE) mpl_error(mpl, "member expression has invalid type"); /* all member expressions must have identical dimension */ if (arg.list != NULL && arg.list->x->dim != code->dim) mpl_error(mpl, "member %d has %d component%s while member %d ha" "s %d component%s", j-1, arg.list->x->dim, arg.list->x->dim == 1 ? "" : "s", j, code->dim, code->dim == 1 ? "" : "s"); /* append the current expression to the member list */ arg.list = expand_arg_list(mpl, arg.list, code); /* check a token that follows the current expression */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_RBRACE) break; else mpl_error(mpl, "syntax error in literal set"); /* parse the next expression that follows the comma */ code = expression_5(mpl); } /* generate pseudo-code for */ code = make_code(mpl, O_MAKE, &arg, A_ELEMSET, arg.list->x->dim); return code; } /*---------------------------------------------------------------------- -- indexing_expression - parse indexing expression. -- -- This routine parses indexing expression using the syntax: -- -- ::= -- ::= { } -- ::= { : } -- ::= -- ::= , -- ::= -- ::= in -- ::= in -- ::= -- ::= ( ) -- ::= -- ::= -- -- This routine creates domain for , where each -- domain block corresponds to , and each domain slot -- corresponds to individual indexing position. */ DOMAIN *indexing_expression(MPL *mpl) { DOMAIN *domain; DOMAIN_BLOCK *block; DOMAIN_SLOT *slot; CODE *code; xassert(mpl->token == T_LBRACE); get_token(mpl /* { */); if (mpl->token == T_RBRACE) mpl_error(mpl, "empty indexing expression not allowed"); /* create domain to be constructed */ domain = create_domain(mpl); /* parse either or that follows the left brace */ for (;;) { /* domain block for is not created yet */ block = NULL; /* pseudo-code for is not generated yet */ code = NULL; /* check a token, which begins with */ if (mpl->token == T_NAME) { /* it is a symbolic name */ int next_token; char *name; /* symbolic name is recognized as dummy index only if it is followed by the keyword 'in' and not declared */ get_token(mpl /* */); next_token = mpl->token; unget_token(mpl); if (!(next_token == T_IN && avl_find_node(mpl->tree, mpl->image) == NULL)) { /* this is not dummy index; the symbolic name begins an expression, which is either or the very first in */ goto expr; } /* create domain block with one slot, which is assigned the dummy index */ block = create_block(mpl); name = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(name, mpl->image); append_slot(mpl, block, name, NULL); get_token(mpl /* */); /* the keyword 'in' is already checked above */ xassert(mpl->token == T_IN); get_token(mpl /* in */); /* that follows the keyword 'in' will be parsed below */ } else if (mpl->token == T_LEFT) { /* it is the left parenthesis; parse expression that begins with this parenthesis (the flag is set in order to allow recognizing slices; see the routine expression_list) */ mpl->flag_x = 1; code = expression_9(mpl); if (code->op != O_SLICE) { /* this is either or the very first in */ goto expr; } /* this is a slice; besides the corresponding domain block is already created by expression_list() */ block = code->arg.slice; code = NULL; /* is not parsed yet */ /* the keyword 'in' following the slice is already checked by expression_list() */ xassert(mpl->token == T_IN); get_token(mpl /* in */); /* that follows the keyword 'in' will be parsed below */ } expr: /* parse expression that follows either the keyword 'in' (in which case it can be as well as the very first in ); note that this expression can be already parsed above */ if (code == NULL) code = expression_9(mpl); /* check the type of the expression just parsed */ if (code->type != A_ELEMSET) { /* it is not and therefore it can only be the very first in ; however, then there must be no dummy index neither slice between the left brace and this expression */ if (block != NULL) mpl_error(mpl, "domain expression has invalid type"); /* parse the rest part of and make this set be , i.e. the construction {a, b, c} is parsed as it were written as {A}, where A = {a, b, c} is a temporary elemental set */ code = literal_set(mpl, code); } /* now pseudo-code for has been built */ xassert(code != NULL); xassert(code->type == A_ELEMSET); xassert(code->dim > 0); /* if domain block for the current is still not created, create it for fake slice of the same dimension as */ if (block == NULL) { int j; block = create_block(mpl); for (j = 1; j <= code->dim; j++) append_slot(mpl, block, NULL, NULL); } /* number of indexing positions in must be the same as dimension of n-tuples in basic set */ { int dim = 0; for (slot = block->list; slot != NULL; slot = slot->next) dim++; if (dim != code->dim) mpl_error(mpl,"%d %s specified for set of dimension %d", dim, dim == 1 ? "index" : "indices", code->dim); } /* store pseudo-code for in the domain block */ xassert(block->code == NULL); block->code = code; /* and append the domain block to the domain */ append_block(mpl, domain, block); /* the current has been completely parsed; include all its dummy indices into the symbolic name table to make them available for referencing from expressions; implicit declarations of dummy indices remain valid while the corresponding domain scope is valid */ for (slot = block->list; slot != NULL; slot = slot->next) if (slot->name != NULL) { AVLNODE *node; xassert(avl_find_node(mpl->tree, slot->name) == NULL); node = avl_insert_node(mpl->tree, slot->name); avl_set_node_type(node, A_INDEX); avl_set_node_link(node, (void *)slot); } /* check a token that follows */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_COLON || mpl->token == T_RBRACE) break; else mpl_error(mpl, "syntax error in indexing expression"); } /* parse that follows the colon */ if (mpl->token == T_COLON) { get_token(mpl /* : */); code = expression_13(mpl); /* convert the expression to logical type, if necessary */ if (code->type == A_SYMBOLIC) code = make_unary(mpl, O_CVTNUM, code, A_NUMERIC, 0); if (code->type == A_NUMERIC) code = make_unary(mpl, O_CVTLOG, code, A_LOGICAL, 0); /* now the expression must be of logical type */ if (code->type != A_LOGICAL) mpl_error(mpl, "expression following colon has invalid type"); xassert(code->dim == 0); domain->code = code; /* the right brace must follow the logical expression */ if (mpl->token != T_RBRACE) mpl_error(mpl, "syntax error in indexing expression"); } get_token(mpl /* } */); return domain; } /*---------------------------------------------------------------------- -- close_scope - close scope of indexing expression. -- -- The routine closes the scope of indexing expression specified by its -- domain and thereby makes all dummy indices introduced in the indexing -- expression no longer available for referencing. */ void close_scope(MPL *mpl, DOMAIN *domain) { DOMAIN_BLOCK *block; DOMAIN_SLOT *slot; AVLNODE *node; xassert(domain != NULL); /* remove all dummy indices from the symbolic names table */ for (block = domain->list; block != NULL; block = block->next) { for (slot = block->list; slot != NULL; slot = slot->next) { if (slot->name != NULL) { node = avl_find_node(mpl->tree, slot->name); xassert(node != NULL); xassert(avl_get_node_type(node) == A_INDEX); avl_delete_node(mpl->tree, node); } } } return; } /*---------------------------------------------------------------------- -- iterated_expression - parse iterated expression. -- -- This routine parses primary expression using the syntax: -- -- ::= -- ::= sum -- ::= prod -- ::= min -- ::= max -- ::= exists -- -- ::= forall -- -- ::= setof -- -- Note that parsing "integrand" depends on the iterated operator. */ #if 1 /* 07/IX-2008 */ static void link_up(CODE *code) { /* if we have something like sum{(i+1,j,k-1) in E} x[i,j,k], where i and k are dummy indices defined out of the iterated expression, we should link up pseudo-code for computing i+1 and k-1 to pseudo-code for computing the iterated expression; this is needed to invalidate current value of the iterated expression once i or k have been changed */ DOMAIN_BLOCK *block; DOMAIN_SLOT *slot; for (block = code->arg.loop.domain->list; block != NULL; block = block->next) { for (slot = block->list; slot != NULL; slot = slot->next) { if (slot->code != NULL) { xassert(slot->code->up == NULL); slot->code->up = code; } } } return; } #endif CODE *iterated_expression(MPL *mpl) { CODE *code; OPERANDS arg; int op; char opstr[8]; /* determine operation code */ xassert(mpl->token == T_NAME); if (strcmp(mpl->image, "sum") == 0) op = O_SUM; else if (strcmp(mpl->image, "prod") == 0) op = O_PROD; else if (strcmp(mpl->image, "min") == 0) op = O_MINIMUM; else if (strcmp(mpl->image, "max") == 0) op = O_MAXIMUM; else if (strcmp(mpl->image, "forall") == 0) op = O_FORALL; else if (strcmp(mpl->image, "exists") == 0) op = O_EXISTS; else if (strcmp(mpl->image, "setof") == 0) op = O_SETOF; else mpl_error(mpl, "operator %s unknown", mpl->image); strcpy(opstr, mpl->image); xassert(strlen(opstr) < sizeof(opstr)); get_token(mpl /* */); /* check the left brace that follows the operator name */ xassert(mpl->token == T_LBRACE); /* parse indexing expression that controls iterating */ arg.loop.domain = indexing_expression(mpl); /* parse "integrand" expression and generate pseudo-code */ switch (op) { case O_SUM: case O_PROD: case O_MINIMUM: case O_MAXIMUM: arg.loop.x = expression_3(mpl); /* convert the integrand to numeric type, if necessary */ if (arg.loop.x->type == A_SYMBOLIC) arg.loop.x = make_unary(mpl, O_CVTNUM, arg.loop.x, A_NUMERIC, 0); /* now the integrand must be of numeric type or linear form (the latter is only allowed for the sum operator) */ if (!(arg.loop.x->type == A_NUMERIC || op == O_SUM && arg.loop.x->type == A_FORMULA)) err: mpl_error(mpl, "integrand following %s{...} has invalid type" , opstr); xassert(arg.loop.x->dim == 0); /* generate pseudo-code */ code = make_code(mpl, op, &arg, arg.loop.x->type, 0); break; case O_FORALL: case O_EXISTS: arg.loop.x = expression_12(mpl); /* convert the integrand to logical type, if necessary */ if (arg.loop.x->type == A_SYMBOLIC) arg.loop.x = make_unary(mpl, O_CVTNUM, arg.loop.x, A_NUMERIC, 0); if (arg.loop.x->type == A_NUMERIC) arg.loop.x = make_unary(mpl, O_CVTLOG, arg.loop.x, A_LOGICAL, 0); /* now the integrand must be of logical type */ if (arg.loop.x->type != A_LOGICAL) goto err; xassert(arg.loop.x->dim == 0); /* generate pseudo-code */ code = make_code(mpl, op, &arg, A_LOGICAL, 0); break; case O_SETOF: arg.loop.x = expression_5(mpl); /* convert the integrand to 1-tuple, if necessary */ if (arg.loop.x->type == A_NUMERIC) arg.loop.x = make_unary(mpl, O_CVTSYM, arg.loop.x, A_SYMBOLIC, 0); if (arg.loop.x->type == A_SYMBOLIC) arg.loop.x = make_unary(mpl, O_CVTTUP, arg.loop.x, A_TUPLE, 1); /* now the integrand must be n-tuple */ if (arg.loop.x->type != A_TUPLE) goto err; xassert(arg.loop.x->dim > 0); /* generate pseudo-code */ code = make_code(mpl, op, &arg, A_ELEMSET, arg.loop.x->dim); break; default: xassert(op != op); } /* close the scope of the indexing expression */ close_scope(mpl, arg.loop.domain); #if 1 /* 07/IX-2008 */ link_up(code); #endif return code; } /*---------------------------------------------------------------------- -- domain_arity - determine arity of domain. -- -- This routine returns arity of specified domain, which is number of -- its free dummy indices. */ int domain_arity(MPL *mpl, DOMAIN *domain) { DOMAIN_BLOCK *block; DOMAIN_SLOT *slot; int arity; xassert(mpl == mpl); arity = 0; for (block = domain->list; block != NULL; block = block->next) for (slot = block->list; slot != NULL; slot = slot->next) if (slot->code == NULL) arity++; return arity; } /*---------------------------------------------------------------------- -- set_expression - parse set expression. -- -- This routine parses primary expression using the syntax: -- -- ::= { } -- ::= */ CODE *set_expression(MPL *mpl) { CODE *code; OPERANDS arg; xassert(mpl->token == T_LBRACE); get_token(mpl /* { */); /* check a token that follows the left brace */ if (mpl->token == T_RBRACE) { /* it is the right brace, so the resultant is an empty set of dimension 1 */ arg.list = NULL; /* generate pseudo-code to build the resultant set */ code = make_code(mpl, O_MAKE, &arg, A_ELEMSET, 1); get_token(mpl /* } */); } else { /* the next token begins an indexing expression */ unget_token(mpl); arg.loop.domain = indexing_expression(mpl); arg.loop.x = NULL; /* integrand is not used */ /* close the scope of the indexing expression */ close_scope(mpl, arg.loop.domain); /* generate pseudo-code to build the resultant set */ code = make_code(mpl, O_BUILD, &arg, A_ELEMSET, domain_arity(mpl, arg.loop.domain)); #if 1 /* 07/IX-2008 */ link_up(code); #endif } return code; } /*---------------------------------------------------------------------- -- branched_expression - parse conditional expression. -- -- This routine parses primary expression using the syntax: -- -- ::= -- ::= if then -- ::= if then -- else -- ::= */ CODE *branched_expression(MPL *mpl) { CODE *code, *x, *y, *z; xassert(mpl->token == T_IF); get_token(mpl /* if */); /* parse that follows 'if' */ x = expression_13(mpl); /* convert the expression to logical type, if necessary */ if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type == A_NUMERIC) x = make_unary(mpl, O_CVTLOG, x, A_LOGICAL, 0); /* now the expression must be of logical type */ if (x->type != A_LOGICAL) mpl_error(mpl, "expression following if has invalid type"); xassert(x->dim == 0); /* the keyword 'then' must follow the logical expression */ if (mpl->token != T_THEN) mpl_error(mpl, "keyword then missing where expected"); get_token(mpl /* then */); /* parse that follows 'then' and check its type */ y = expression_9(mpl); if (!(y->type == A_NUMERIC || y->type == A_SYMBOLIC || y->type == A_ELEMSET || y->type == A_FORMULA)) mpl_error(mpl, "expression following then has invalid type"); /* if the expression that follows the keyword 'then' is elemental set, the keyword 'else' cannot be omitted; otherwise else-part is optional */ if (mpl->token != T_ELSE) { if (y->type == A_ELEMSET) mpl_error(mpl, "keyword else missing where expected"); z = NULL; goto skip; } get_token(mpl /* else */); /* parse that follow 'else' and check its type */ z = expression_9(mpl); if (!(z->type == A_NUMERIC || z->type == A_SYMBOLIC || z->type == A_ELEMSET || z->type == A_FORMULA)) mpl_error(mpl, "expression following else has invalid type"); /* convert to identical types, if necessary */ if (y->type == A_FORMULA || z->type == A_FORMULA) { if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type == A_NUMERIC) y = make_unary(mpl, O_CVTLFM, y, A_FORMULA, 0); if (z->type == A_SYMBOLIC) z = make_unary(mpl, O_CVTNUM, z, A_NUMERIC, 0); if (z->type == A_NUMERIC) z = make_unary(mpl, O_CVTLFM, z, A_FORMULA, 0); } if (y->type == A_SYMBOLIC || z->type == A_SYMBOLIC) { if (y->type == A_NUMERIC) y = make_unary(mpl, O_CVTSYM, y, A_SYMBOLIC, 0); if (z->type == A_NUMERIC) z = make_unary(mpl, O_CVTSYM, z, A_SYMBOLIC, 0); } /* now both expressions must have identical types */ if (y->type != z->type) mpl_error(mpl, "expressions following then and else have incompati" "ble types"); /* and identical dimensions */ if (y->dim != z->dim) mpl_error(mpl, "expressions following then and else have different" " dimensions %d and %d, respectively", y->dim, z->dim); skip: /* generate pseudo-code to perform branching */ code = make_ternary(mpl, O_FORK, x, y, z, y->type, y->dim); return code; } /*---------------------------------------------------------------------- -- primary_expression - parse primary expression. -- -- This routine parses primary expression using the syntax: -- -- ::= -- ::= Infinity -- ::= -- ::= -- ::= -- ::= [ ] -- ::= -- ::= [ ] -- ::= -- ::= [ ] -- ::= ( ) -- ::= ( ) -- ::= -- ::= { } -- ::= -- ::= -- -- For complete list of syntactic rules for see -- comments to the corresponding parsing routines. */ CODE *primary_expression(MPL *mpl) { CODE *code; if (mpl->token == T_NUMBER) { /* parse numeric literal */ code = numeric_literal(mpl); } #if 1 /* 21/VII-2006 */ else if (mpl->token == T_INFINITY) { /* parse "infinity" */ OPERANDS arg; arg.num = DBL_MAX; code = make_code(mpl, O_NUMBER, &arg, A_NUMERIC, 0); get_token(mpl /* Infinity */); } #endif else if (mpl->token == T_STRING) { /* parse string literal */ code = string_literal(mpl); } else if (mpl->token == T_NAME) { int next_token; get_token(mpl /* */); next_token = mpl->token; unget_token(mpl); /* check a token that follows */ switch (next_token) { case T_LBRACKET: /* parse reference to subscripted object */ code = object_reference(mpl); break; case T_LEFT: /* parse reference to built-in function */ code = function_reference(mpl); break; case T_LBRACE: /* parse iterated expression */ code = iterated_expression(mpl); break; default: /* parse reference to unsubscripted object */ code = object_reference(mpl); break; } } else if (mpl->token == T_LEFT) { /* parse parenthesized expression */ code = expression_list(mpl); } else if (mpl->token == T_LBRACE) { /* parse set expression */ code = set_expression(mpl); } else if (mpl->token == T_IF) { /* parse conditional expression */ code = branched_expression(mpl); } else if (is_reserved(mpl)) { /* other reserved keywords cannot be used here */ mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); } else mpl_error(mpl, "syntax error in expression"); return code; } /*---------------------------------------------------------------------- -- error_preceding - raise error if preceding operand has wrong type. -- -- This routine is called to raise error if operand that precedes some -- infix operator has invalid type. */ void error_preceding(MPL *mpl, char *opstr) { mpl_error(mpl, "operand preceding %s has invalid type", opstr); /* no return */ } /*---------------------------------------------------------------------- -- error_following - raise error if following operand has wrong type. -- -- This routine is called to raise error if operand that follows some -- infix operator has invalid type. */ void error_following(MPL *mpl, char *opstr) { mpl_error(mpl, "operand following %s has invalid type", opstr); /* no return */ } /*---------------------------------------------------------------------- -- error_dimension - raise error if operands have different dimension. -- -- This routine is called to raise error if two operands of some infix -- operator have different dimension. */ void error_dimension(MPL *mpl, char *opstr, int dim1, int dim2) { mpl_error(mpl, "operands preceding and following %s have different di" "mensions %d and %d, respectively", opstr, dim1, dim2); /* no return */ } /*---------------------------------------------------------------------- -- expression_0 - parse expression of level 0. -- -- This routine parses expression of level 0 using the syntax: -- -- ::= */ CODE *expression_0(MPL *mpl) { CODE *code; code = primary_expression(mpl); return code; } /*---------------------------------------------------------------------- -- expression_1 - parse expression of level 1. -- -- This routine parses expression of level 1 using the syntax: -- -- ::= -- ::= -- ::= -- ::= ^ | ** */ CODE *expression_1(MPL *mpl) { CODE *x, *y; char opstr[8]; x = expression_0(mpl); if (mpl->token == T_POWER) { strcpy(opstr, mpl->image); xassert(strlen(opstr) < sizeof(opstr)); if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type != A_NUMERIC) error_preceding(mpl, opstr); get_token(mpl /* ^ | ** */); if (mpl->token == T_PLUS || mpl->token == T_MINUS) y = expression_2(mpl); else y = expression_1(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type != A_NUMERIC) error_following(mpl, opstr); x = make_binary(mpl, O_POWER, x, y, A_NUMERIC, 0); } return x; } /*---------------------------------------------------------------------- -- expression_2 - parse expression of level 2. -- -- This routine parses expression of level 2 using the syntax: -- -- ::= -- ::= + -- ::= - */ CODE *expression_2(MPL *mpl) { CODE *x; if (mpl->token == T_PLUS) { get_token(mpl /* + */); x = expression_1(mpl); if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (!(x->type == A_NUMERIC || x->type == A_FORMULA)) error_following(mpl, "+"); x = make_unary(mpl, O_PLUS, x, x->type, 0); } else if (mpl->token == T_MINUS) { get_token(mpl /* - */); x = expression_1(mpl); if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (!(x->type == A_NUMERIC || x->type == A_FORMULA)) error_following(mpl, "-"); x = make_unary(mpl, O_MINUS, x, x->type, 0); } else x = expression_1(mpl); return x; } /*---------------------------------------------------------------------- -- expression_3 - parse expression of level 3. -- -- This routine parses expression of level 3 using the syntax: -- -- ::= -- ::= * -- ::= / -- ::= div -- ::= mod */ CODE *expression_3(MPL *mpl) { CODE *x, *y; x = expression_2(mpl); for (;;) { if (mpl->token == T_ASTERISK) { if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (!(x->type == A_NUMERIC || x->type == A_FORMULA)) error_preceding(mpl, "*"); get_token(mpl /* * */); y = expression_2(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (!(y->type == A_NUMERIC || y->type == A_FORMULA)) error_following(mpl, "*"); if (x->type == A_FORMULA && y->type == A_FORMULA) mpl_error(mpl, "multiplication of linear forms not allowed"); if (x->type == A_NUMERIC && y->type == A_NUMERIC) x = make_binary(mpl, O_MUL, x, y, A_NUMERIC, 0); else x = make_binary(mpl, O_MUL, x, y, A_FORMULA, 0); } else if (mpl->token == T_SLASH) { if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (!(x->type == A_NUMERIC || x->type == A_FORMULA)) error_preceding(mpl, "/"); get_token(mpl /* / */); y = expression_2(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type != A_NUMERIC) error_following(mpl, "/"); if (x->type == A_NUMERIC) x = make_binary(mpl, O_DIV, x, y, A_NUMERIC, 0); else x = make_binary(mpl, O_DIV, x, y, A_FORMULA, 0); } else if (mpl->token == T_DIV) { if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type != A_NUMERIC) error_preceding(mpl, "div"); get_token(mpl /* div */); y = expression_2(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type != A_NUMERIC) error_following(mpl, "div"); x = make_binary(mpl, O_IDIV, x, y, A_NUMERIC, 0); } else if (mpl->token == T_MOD) { if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type != A_NUMERIC) error_preceding(mpl, "mod"); get_token(mpl /* mod */); y = expression_2(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type != A_NUMERIC) error_following(mpl, "mod"); x = make_binary(mpl, O_MOD, x, y, A_NUMERIC, 0); } else break; } return x; } /*---------------------------------------------------------------------- -- expression_4 - parse expression of level 4. -- -- This routine parses expression of level 4 using the syntax: -- -- ::= -- ::= + -- ::= - -- ::= less */ CODE *expression_4(MPL *mpl) { CODE *x, *y; x = expression_3(mpl); for (;;) { if (mpl->token == T_PLUS) { if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (!(x->type == A_NUMERIC || x->type == A_FORMULA)) error_preceding(mpl, "+"); get_token(mpl /* + */); y = expression_3(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (!(y->type == A_NUMERIC || y->type == A_FORMULA)) error_following(mpl, "+"); if (x->type == A_NUMERIC && y->type == A_FORMULA) x = make_unary(mpl, O_CVTLFM, x, A_FORMULA, 0); if (x->type == A_FORMULA && y->type == A_NUMERIC) y = make_unary(mpl, O_CVTLFM, y, A_FORMULA, 0); x = make_binary(mpl, O_ADD, x, y, x->type, 0); } else if (mpl->token == T_MINUS) { if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (!(x->type == A_NUMERIC || x->type == A_FORMULA)) error_preceding(mpl, "-"); get_token(mpl /* - */); y = expression_3(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (!(y->type == A_NUMERIC || y->type == A_FORMULA)) error_following(mpl, "-"); if (x->type == A_NUMERIC && y->type == A_FORMULA) x = make_unary(mpl, O_CVTLFM, x, A_FORMULA, 0); if (x->type == A_FORMULA && y->type == A_NUMERIC) y = make_unary(mpl, O_CVTLFM, y, A_FORMULA, 0); x = make_binary(mpl, O_SUB, x, y, x->type, 0); } else if (mpl->token == T_LESS) { if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type != A_NUMERIC) error_preceding(mpl, "less"); get_token(mpl /* less */); y = expression_3(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type != A_NUMERIC) error_following(mpl, "less"); x = make_binary(mpl, O_LESS, x, y, A_NUMERIC, 0); } else break; } return x; } /*---------------------------------------------------------------------- -- expression_5 - parse expression of level 5. -- -- This routine parses expression of level 5 using the syntax: -- -- ::= -- ::= & */ CODE *expression_5(MPL *mpl) { CODE *x, *y; x = expression_4(mpl); for (;;) { if (mpl->token == T_CONCAT) { if (x->type == A_NUMERIC) x = make_unary(mpl, O_CVTSYM, x, A_SYMBOLIC, 0); if (x->type != A_SYMBOLIC) error_preceding(mpl, "&"); get_token(mpl /* & */); y = expression_4(mpl); if (y->type == A_NUMERIC) y = make_unary(mpl, O_CVTSYM, y, A_SYMBOLIC, 0); if (y->type != A_SYMBOLIC) error_following(mpl, "&"); x = make_binary(mpl, O_CONCAT, x, y, A_SYMBOLIC, 0); } else break; } return x; } /*---------------------------------------------------------------------- -- expression_6 - parse expression of level 6. -- -- This routine parses expression of level 6 using the syntax: -- -- ::= -- ::= .. -- ::= .. by -- */ CODE *expression_6(MPL *mpl) { CODE *x, *y, *z; x = expression_5(mpl); if (mpl->token == T_DOTS) { if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type != A_NUMERIC) error_preceding(mpl, ".."); get_token(mpl /* .. */); y = expression_5(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type != A_NUMERIC) error_following(mpl, ".."); if (mpl->token == T_BY) { get_token(mpl /* by */); z = expression_5(mpl); if (z->type == A_SYMBOLIC) z = make_unary(mpl, O_CVTNUM, z, A_NUMERIC, 0); if (z->type != A_NUMERIC) error_following(mpl, "by"); } else z = NULL; x = make_ternary(mpl, O_DOTS, x, y, z, A_ELEMSET, 1); } return x; } /*---------------------------------------------------------------------- -- expression_7 - parse expression of level 7. -- -- This routine parses expression of level 7 using the syntax: -- -- ::= -- ::= cross */ CODE *expression_7(MPL *mpl) { CODE *x, *y; x = expression_6(mpl); for (;;) { if (mpl->token == T_CROSS) { if (x->type != A_ELEMSET) error_preceding(mpl, "cross"); get_token(mpl /* cross */); y = expression_6(mpl); if (y->type != A_ELEMSET) error_following(mpl, "cross"); x = make_binary(mpl, O_CROSS, x, y, A_ELEMSET, x->dim + y->dim); } else break; } return x; } /*---------------------------------------------------------------------- -- expression_8 - parse expression of level 8. -- -- This routine parses expression of level 8 using the syntax: -- -- ::= -- ::= inter */ CODE *expression_8(MPL *mpl) { CODE *x, *y; x = expression_7(mpl); for (;;) { if (mpl->token == T_INTER) { if (x->type != A_ELEMSET) error_preceding(mpl, "inter"); get_token(mpl /* inter */); y = expression_7(mpl); if (y->type != A_ELEMSET) error_following(mpl, "inter"); if (x->dim != y->dim) error_dimension(mpl, "inter", x->dim, y->dim); x = make_binary(mpl, O_INTER, x, y, A_ELEMSET, x->dim); } else break; } return x; } /*---------------------------------------------------------------------- -- expression_9 - parse expression of level 9. -- -- This routine parses expression of level 9 using the syntax: -- -- ::= -- ::= union -- ::= diff -- ::= symdiff */ CODE *expression_9(MPL *mpl) { CODE *x, *y; x = expression_8(mpl); for (;;) { if (mpl->token == T_UNION) { if (x->type != A_ELEMSET) error_preceding(mpl, "union"); get_token(mpl /* union */); y = expression_8(mpl); if (y->type != A_ELEMSET) error_following(mpl, "union"); if (x->dim != y->dim) error_dimension(mpl, "union", x->dim, y->dim); x = make_binary(mpl, O_UNION, x, y, A_ELEMSET, x->dim); } else if (mpl->token == T_DIFF) { if (x->type != A_ELEMSET) error_preceding(mpl, "diff"); get_token(mpl /* diff */); y = expression_8(mpl); if (y->type != A_ELEMSET) error_following(mpl, "diff"); if (x->dim != y->dim) error_dimension(mpl, "diff", x->dim, y->dim); x = make_binary(mpl, O_DIFF, x, y, A_ELEMSET, x->dim); } else if (mpl->token == T_SYMDIFF) { if (x->type != A_ELEMSET) error_preceding(mpl, "symdiff"); get_token(mpl /* symdiff */); y = expression_8(mpl); if (y->type != A_ELEMSET) error_following(mpl, "symdiff"); if (x->dim != y->dim) error_dimension(mpl, "symdiff", x->dim, y->dim); x = make_binary(mpl, O_SYMDIFF, x, y, A_ELEMSET, x->dim); } else break; } return x; } /*---------------------------------------------------------------------- -- expression_10 - parse expression of level 10. -- -- This routine parses expression of level 10 using the syntax: -- -- ::= -- ::= -- ::= < | <= | = | == | >= | > | <> | != | in | not in | ! in | -- within | not within | ! within */ CODE *expression_10(MPL *mpl) { CODE *x, *y; int op = -1; char opstr[16]; x = expression_9(mpl); strcpy(opstr, ""); switch (mpl->token) { case T_LT: op = O_LT; break; case T_LE: op = O_LE; break; case T_EQ: op = O_EQ; break; case T_GE: op = O_GE; break; case T_GT: op = O_GT; break; case T_NE: op = O_NE; break; case T_IN: op = O_IN; break; case T_WITHIN: op = O_WITHIN; break; case T_NOT: strcpy(opstr, mpl->image); get_token(mpl /* not | ! */); if (mpl->token == T_IN) op = O_NOTIN; else if (mpl->token == T_WITHIN) op = O_NOTWITHIN; else mpl_error(mpl, "invalid use of %s", opstr); strcat(opstr, " "); break; default: goto done; } strcat(opstr, mpl->image); xassert(strlen(opstr) < sizeof(opstr)); switch (op) { case O_EQ: case O_NE: #if 1 /* 02/VIII-2008 */ case O_LT: case O_LE: case O_GT: case O_GE: #endif if (!(x->type == A_NUMERIC || x->type == A_SYMBOLIC)) error_preceding(mpl, opstr); get_token(mpl /* */); y = expression_9(mpl); if (!(y->type == A_NUMERIC || y->type == A_SYMBOLIC)) error_following(mpl, opstr); if (x->type == A_NUMERIC && y->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTSYM, x, A_SYMBOLIC, 0); if (x->type == A_SYMBOLIC && y->type == A_NUMERIC) y = make_unary(mpl, O_CVTSYM, y, A_SYMBOLIC, 0); x = make_binary(mpl, op, x, y, A_LOGICAL, 0); break; #if 0 /* 02/VIII-2008 */ case O_LT: case O_LE: case O_GT: case O_GE: if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type != A_NUMERIC) error_preceding(mpl, opstr); get_token(mpl /* */); y = expression_9(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type != A_NUMERIC) error_following(mpl, opstr); x = make_binary(mpl, op, x, y, A_LOGICAL, 0); break; #endif case O_IN: case O_NOTIN: if (x->type == A_NUMERIC) x = make_unary(mpl, O_CVTSYM, x, A_SYMBOLIC, 0); if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTTUP, x, A_TUPLE, 1); if (x->type != A_TUPLE) error_preceding(mpl, opstr); get_token(mpl /* */); y = expression_9(mpl); if (y->type != A_ELEMSET) error_following(mpl, opstr); if (x->dim != y->dim) error_dimension(mpl, opstr, x->dim, y->dim); x = make_binary(mpl, op, x, y, A_LOGICAL, 0); break; case O_WITHIN: case O_NOTWITHIN: if (x->type != A_ELEMSET) error_preceding(mpl, opstr); get_token(mpl /* */); y = expression_9(mpl); if (y->type != A_ELEMSET) error_following(mpl, opstr); if (x->dim != y->dim) error_dimension(mpl, opstr, x->dim, y->dim); x = make_binary(mpl, op, x, y, A_LOGICAL, 0); break; default: xassert(op != op); } done: return x; } /*---------------------------------------------------------------------- -- expression_11 - parse expression of level 11. -- -- This routine parses expression of level 11 using the syntax: -- -- ::= -- ::= not -- ::= ! */ CODE *expression_11(MPL *mpl) { CODE *x; char opstr[8]; if (mpl->token == T_NOT) { strcpy(opstr, mpl->image); xassert(strlen(opstr) < sizeof(opstr)); get_token(mpl /* not | ! */); x = expression_10(mpl); if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type == A_NUMERIC) x = make_unary(mpl, O_CVTLOG, x, A_LOGICAL, 0); if (x->type != A_LOGICAL) error_following(mpl, opstr); x = make_unary(mpl, O_NOT, x, A_LOGICAL, 0); } else x = expression_10(mpl); return x; } /*---------------------------------------------------------------------- -- expression_12 - parse expression of level 12. -- -- This routine parses expression of level 12 using the syntax: -- -- ::= -- ::= and -- ::= && */ CODE *expression_12(MPL *mpl) { CODE *x, *y; char opstr[8]; x = expression_11(mpl); for (;;) { if (mpl->token == T_AND) { strcpy(opstr, mpl->image); xassert(strlen(opstr) < sizeof(opstr)); if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type == A_NUMERIC) x = make_unary(mpl, O_CVTLOG, x, A_LOGICAL, 0); if (x->type != A_LOGICAL) error_preceding(mpl, opstr); get_token(mpl /* and | && */); y = expression_11(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type == A_NUMERIC) y = make_unary(mpl, O_CVTLOG, y, A_LOGICAL, 0); if (y->type != A_LOGICAL) error_following(mpl, opstr); x = make_binary(mpl, O_AND, x, y, A_LOGICAL, 0); } else break; } return x; } /*---------------------------------------------------------------------- -- expression_13 - parse expression of level 13. -- -- This routine parses expression of level 13 using the syntax: -- -- ::= -- ::= or -- ::= || */ CODE *expression_13(MPL *mpl) { CODE *x, *y; char opstr[8]; x = expression_12(mpl); for (;;) { if (mpl->token == T_OR) { strcpy(opstr, mpl->image); xassert(strlen(opstr) < sizeof(opstr)); if (x->type == A_SYMBOLIC) x = make_unary(mpl, O_CVTNUM, x, A_NUMERIC, 0); if (x->type == A_NUMERIC) x = make_unary(mpl, O_CVTLOG, x, A_LOGICAL, 0); if (x->type != A_LOGICAL) error_preceding(mpl, opstr); get_token(mpl /* or | || */); y = expression_12(mpl); if (y->type == A_SYMBOLIC) y = make_unary(mpl, O_CVTNUM, y, A_NUMERIC, 0); if (y->type == A_NUMERIC) y = make_unary(mpl, O_CVTLOG, y, A_LOGICAL, 0); if (y->type != A_LOGICAL) error_following(mpl, opstr); x = make_binary(mpl, O_OR, x, y, A_LOGICAL, 0); } else break; } return x; } /*---------------------------------------------------------------------- -- set_statement - parse set statement. -- -- This routine parses set statement using the syntax: -- -- ::= set -- ; -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= , dimen -- ::= , within -- ::= , := -- ::= , default -- -- Commae in are optional and may be omitted anywhere. */ SET *set_statement(MPL *mpl) { SET *set; int dimen_used = 0; xassert(is_keyword(mpl, "set")); get_token(mpl /* set */); /* symbolic name must follow the keyword 'set' */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "symbolic name missing where expected"); /* there must be no other object with the same name */ if (avl_find_node(mpl->tree, mpl->image) != NULL) mpl_error(mpl, "%s multiply declared", mpl->image); /* create model set */ set = alloc(SET); set->name = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(set->name, mpl->image); set->alias = NULL; set->dim = 0; set->domain = NULL; set->dimen = 0; set->within = NULL; set->assign = NULL; set->option = NULL; set->gadget = NULL; set->data = 0; set->array = NULL; get_token(mpl /* */); /* parse optional alias */ if (mpl->token == T_STRING) { set->alias = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(set->alias, mpl->image); get_token(mpl /* */); } /* parse optional indexing expression */ if (mpl->token == T_LBRACE) { set->domain = indexing_expression(mpl); set->dim = domain_arity(mpl, set->domain); } /* include the set name in the symbolic names table */ { AVLNODE *node; node = avl_insert_node(mpl->tree, set->name); avl_set_node_type(node, A_SET); avl_set_node_link(node, (void *)set); } /* parse the list of optional attributes */ for (;;) { if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_SEMICOLON) break; if (is_keyword(mpl, "dimen")) { /* dimension of set members */ int dimen; get_token(mpl /* dimen */); if (!(mpl->token == T_NUMBER && 1.0 <= mpl->value && mpl->value <= 20.0 && floor(mpl->value) == mpl->value)) mpl_error(mpl, "dimension must be integer between 1 and 20"); dimen = (int)(mpl->value + 0.5); if (dimen_used) mpl_error(mpl, "at most one dimension attribute allowed"); if (set->dimen > 0) mpl_error(mpl, "dimension %d conflicts with dimension %d alr" "eady determined", dimen, set->dimen); set->dimen = dimen; dimen_used = 1; get_token(mpl /* */); } else if (mpl->token == T_WITHIN || mpl->token == T_IN) { /* restricting superset */ WITHIN *within, *temp; if (mpl->token == T_IN && !mpl->as_within) { warning(mpl, "keyword in understood as within"); mpl->as_within = 1; } get_token(mpl /* within */); /* create new restricting superset list entry and append it to the within-list */ within = alloc(WITHIN); within->code = NULL; within->next = NULL; if (set->within == NULL) set->within = within; else { for (temp = set->within; temp->next != NULL; temp = temp->next); temp->next = within; } /* parse an expression that follows 'within' */ within->code = expression_9(mpl); if (within->code->type != A_ELEMSET) mpl_error(mpl, "expression following within has invalid type" ); xassert(within->code->dim > 0); /* check/set dimension of set members */ if (set->dimen == 0) set->dimen = within->code->dim; if (set->dimen != within->code->dim) mpl_error(mpl, "set expression following within must have di" "mension %d rather than %d", set->dimen, within->code->dim); } else if (mpl->token == T_ASSIGN) { /* assignment expression */ if (!(set->assign == NULL && set->option == NULL && set->gadget == NULL)) err: mpl_error(mpl, "at most one := or default/data allowed"); get_token(mpl /* := */); /* parse an expression that follows ':=' */ set->assign = expression_9(mpl); if (set->assign->type != A_ELEMSET) mpl_error(mpl, "expression following := has invalid type"); xassert(set->assign->dim > 0); /* check/set dimension of set members */ if (set->dimen == 0) set->dimen = set->assign->dim; if (set->dimen != set->assign->dim) mpl_error(mpl, "set expression following := must have dimens" "ion %d rather than %d", set->dimen, set->assign->dim); } else if (is_keyword(mpl, "default")) { /* expression for default value */ if (!(set->assign == NULL && set->option == NULL)) goto err; get_token(mpl /* := */); /* parse an expression that follows 'default' */ set->option = expression_9(mpl); if (set->option->type != A_ELEMSET) mpl_error(mpl, "expression following default has invalid typ" "e"); xassert(set->option->dim > 0); /* check/set dimension of set members */ if (set->dimen == 0) set->dimen = set->option->dim; if (set->dimen != set->option->dim) mpl_error(mpl, "set expression following default must have d" "imension %d rather than %d", set->dimen, set->option->dim); } #if 1 /* 12/XII-2008 */ else if (is_keyword(mpl, "data")) { /* gadget to initialize the set by data from plain set */ GADGET *gadget; AVLNODE *node; int i, k, fff[20]; if (!(set->assign == NULL && set->gadget == NULL)) goto err; get_token(mpl /* data */); set->gadget = gadget = alloc(GADGET); /* set name must follow the keyword 'data' */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "set name missing where expected"); /* find the set in the symbolic name table */ node = avl_find_node(mpl->tree, mpl->image); if (node == NULL) mpl_error(mpl, "%s not defined", mpl->image); if (avl_get_node_type(node) != A_SET) err1: mpl_error(mpl, "%s not a plain set", mpl->image); gadget->set = avl_get_node_link(node); if (gadget->set->dim != 0) goto err1; if (gadget->set == set) mpl_error(mpl, "set cannot be initialized by itself"); /* check and set dimensions */ if (set->dim >= gadget->set->dimen) err2: mpl_error(mpl, "dimension of %s too small", mpl->image); if (set->dimen == 0) set->dimen = gadget->set->dimen - set->dim; if (set->dim + set->dimen > gadget->set->dimen) goto err2; else if (set->dim + set->dimen < gadget->set->dimen) mpl_error(mpl, "dimension of %s too big", mpl->image); get_token(mpl /* set name */); /* left parenthesis must follow the set name */ if (mpl->token == T_LEFT) get_token(mpl /* ( */); else mpl_error(mpl, "left parenthesis missing where expected"); /* parse permutation of component numbers */ for (k = 0; k < gadget->set->dimen; k++) fff[k] = 0; k = 0; for (;;) { if (mpl->token != T_NUMBER) mpl_error(mpl, "component number missing where expected"); if (str2int(mpl->image, &i) != 0) err3: mpl_error(mpl, "component number must be integer between " "1 and %d", gadget->set->dimen); if (!(1 <= i && i <= gadget->set->dimen)) goto err3; if (fff[i-1] != 0) mpl_error(mpl, "component %d multiply specified", i); gadget->ind[k++] = i, fff[i-1] = 1; xassert(k <= gadget->set->dimen); get_token(mpl /* number */); if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_RIGHT) break; else mpl_error(mpl, "syntax error in data attribute"); } if (k < gadget->set->dimen) mpl_error(mpl, "there are must be %d components rather than " "%d", gadget->set->dimen, k); get_token(mpl /* ) */); } #endif else mpl_error(mpl, "syntax error in set statement"); } /* close the domain scope */ if (set->domain != NULL) close_scope(mpl, set->domain); /* if dimension of set members is still unknown, set it to 1 */ if (set->dimen == 0) set->dimen = 1; /* the set statement has been completely parsed */ xassert(mpl->token == T_SEMICOLON); get_token(mpl /* ; */); return set; } /*---------------------------------------------------------------------- -- parameter_statement - parse parameter statement. -- -- This routine parses parameter statement using the syntax: -- -- ::= param -- ; -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= , integer -- ::= , binary -- ::= , symbolic -- ::= , -- ::= , in -- ::= , := -- ::= , default -- ::= < | <= | = | == | >= | > | <> | != -- -- Commae in are optional and may be omitted anywhere. */ PARAMETER *parameter_statement(MPL *mpl) { PARAMETER *par; int integer_used = 0, binary_used = 0, symbolic_used = 0; xassert(is_keyword(mpl, "param")); get_token(mpl /* param */); /* symbolic name must follow the keyword 'param' */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "symbolic name missing where expected"); /* there must be no other object with the same name */ if (avl_find_node(mpl->tree, mpl->image) != NULL) mpl_error(mpl, "%s multiply declared", mpl->image); /* create model parameter */ par = alloc(PARAMETER); par->name = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(par->name, mpl->image); par->alias = NULL; par->dim = 0; par->domain = NULL; par->type = A_NUMERIC; par->cond = NULL; par->in = NULL; par->assign = NULL; par->option = NULL; par->data = 0; par->defval = NULL; par->array = NULL; get_token(mpl /* */); /* parse optional alias */ if (mpl->token == T_STRING) { par->alias = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(par->alias, mpl->image); get_token(mpl /* */); } /* parse optional indexing expression */ if (mpl->token == T_LBRACE) { par->domain = indexing_expression(mpl); par->dim = domain_arity(mpl, par->domain); } /* include the parameter name in the symbolic names table */ { AVLNODE *node; node = avl_insert_node(mpl->tree, par->name); avl_set_node_type(node, A_PARAMETER); avl_set_node_link(node, (void *)par); } /* parse the list of optional attributes */ for (;;) { if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_SEMICOLON) break; if (is_keyword(mpl, "integer")) { if (integer_used) mpl_error(mpl, "at most one integer allowed"); if (par->type == A_SYMBOLIC) mpl_error(mpl, "symbolic parameter cannot be integer"); if (par->type != A_BINARY) par->type = A_INTEGER; integer_used = 1; get_token(mpl /* integer */); } else if (is_keyword(mpl, "binary")) bin: { if (binary_used) mpl_error(mpl, "at most one binary allowed"); if (par->type == A_SYMBOLIC) mpl_error(mpl, "symbolic parameter cannot be binary"); par->type = A_BINARY; binary_used = 1; get_token(mpl /* binary */); } else if (is_keyword(mpl, "logical")) { if (!mpl->as_binary) { warning(mpl, "keyword logical understood as binary"); mpl->as_binary = 1; } goto bin; } else if (is_keyword(mpl, "symbolic")) { if (symbolic_used) mpl_error(mpl, "at most one symbolic allowed"); if (par->type != A_NUMERIC) mpl_error(mpl, "integer or binary parameter cannot be symbol" "ic"); /* the parameter may be referenced from expressions given in the same parameter declaration, so its type must be completed before parsing that expressions */ if (!(par->cond == NULL && par->in == NULL && par->assign == NULL && par->option == NULL)) mpl_error(mpl, "keyword symbolic must precede any other para" "meter attributes"); par->type = A_SYMBOLIC; symbolic_used = 1; get_token(mpl /* symbolic */); } else if (mpl->token == T_LT || mpl->token == T_LE || mpl->token == T_EQ || mpl->token == T_GE || mpl->token == T_GT || mpl->token == T_NE) { /* restricting condition */ CONDITION *cond, *temp; char opstr[8]; /* create new restricting condition list entry and append it to the conditions list */ cond = alloc(CONDITION); switch (mpl->token) { case T_LT: cond->rho = O_LT, strcpy(opstr, mpl->image); break; case T_LE: cond->rho = O_LE, strcpy(opstr, mpl->image); break; case T_EQ: cond->rho = O_EQ, strcpy(opstr, mpl->image); break; case T_GE: cond->rho = O_GE, strcpy(opstr, mpl->image); break; case T_GT: cond->rho = O_GT, strcpy(opstr, mpl->image); break; case T_NE: cond->rho = O_NE, strcpy(opstr, mpl->image); break; default: xassert(mpl->token != mpl->token); } xassert(strlen(opstr) < sizeof(opstr)); cond->code = NULL; cond->next = NULL; if (par->cond == NULL) par->cond = cond; else { for (temp = par->cond; temp->next != NULL; temp = temp->next); temp->next = cond; } #if 0 /* 13/VIII-2008 */ if (par->type == A_SYMBOLIC && !(cond->rho == O_EQ || cond->rho == O_NE)) mpl_error(mpl, "inequality restriction not allowed"); #endif get_token(mpl /* rho */); /* parse an expression that follows relational operator */ cond->code = expression_5(mpl); if (!(cond->code->type == A_NUMERIC || cond->code->type == A_SYMBOLIC)) mpl_error(mpl, "expression following %s has invalid type", opstr); xassert(cond->code->dim == 0); /* convert to the parameter type, if necessary */ if (par->type != A_SYMBOLIC && cond->code->type == A_SYMBOLIC) cond->code = make_unary(mpl, O_CVTNUM, cond->code, A_NUMERIC, 0); if (par->type == A_SYMBOLIC && cond->code->type != A_SYMBOLIC) cond->code = make_unary(mpl, O_CVTSYM, cond->code, A_SYMBOLIC, 0); } else if (mpl->token == T_IN || mpl->token == T_WITHIN) { /* restricting superset */ WITHIN *in, *temp; if (mpl->token == T_WITHIN && !mpl->as_in) { warning(mpl, "keyword within understood as in"); mpl->as_in = 1; } get_token(mpl /* in */); /* create new restricting superset list entry and append it to the in-list */ in = alloc(WITHIN); in->code = NULL; in->next = NULL; if (par->in == NULL) par->in = in; else { for (temp = par->in; temp->next != NULL; temp = temp->next); temp->next = in; } /* parse an expression that follows 'in' */ in->code = expression_9(mpl); if (in->code->type != A_ELEMSET) mpl_error(mpl, "expression following in has invalid type"); xassert(in->code->dim > 0); if (in->code->dim != 1) mpl_error(mpl, "set expression following in must have dimens" "ion 1 rather than %d", in->code->dim); } else if (mpl->token == T_ASSIGN) { /* assignment expression */ if (!(par->assign == NULL && par->option == NULL)) err: mpl_error(mpl, "at most one := or default allowed"); get_token(mpl /* := */); /* parse an expression that follows ':=' */ par->assign = expression_5(mpl); /* the expression must be of numeric/symbolic type */ if (!(par->assign->type == A_NUMERIC || par->assign->type == A_SYMBOLIC)) mpl_error(mpl, "expression following := has invalid type"); xassert(par->assign->dim == 0); /* convert to the parameter type, if necessary */ if (par->type != A_SYMBOLIC && par->assign->type == A_SYMBOLIC) par->assign = make_unary(mpl, O_CVTNUM, par->assign, A_NUMERIC, 0); if (par->type == A_SYMBOLIC && par->assign->type != A_SYMBOLIC) par->assign = make_unary(mpl, O_CVTSYM, par->assign, A_SYMBOLIC, 0); } else if (is_keyword(mpl, "default")) { /* expression for default value */ if (!(par->assign == NULL && par->option == NULL)) goto err; get_token(mpl /* default */); /* parse an expression that follows 'default' */ par->option = expression_5(mpl); if (!(par->option->type == A_NUMERIC || par->option->type == A_SYMBOLIC)) mpl_error(mpl, "expression following default has invalid typ" "e"); xassert(par->option->dim == 0); /* convert to the parameter type, if necessary */ if (par->type != A_SYMBOLIC && par->option->type == A_SYMBOLIC) par->option = make_unary(mpl, O_CVTNUM, par->option, A_NUMERIC, 0); if (par->type == A_SYMBOLIC && par->option->type != A_SYMBOLIC) par->option = make_unary(mpl, O_CVTSYM, par->option, A_SYMBOLIC, 0); } else mpl_error(mpl, "syntax error in parameter statement"); } /* close the domain scope */ if (par->domain != NULL) close_scope(mpl, par->domain); /* the parameter statement has been completely parsed */ xassert(mpl->token == T_SEMICOLON); get_token(mpl /* ; */); return par; } /*---------------------------------------------------------------------- -- variable_statement - parse variable statement. -- -- This routine parses variable statement using the syntax: -- -- ::= var -- ; -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= , integer -- ::= , binary -- ::= , -- ::= >= | <= | = | == -- -- Commae in are optional and may be omitted anywhere. */ VARIABLE *variable_statement(MPL *mpl) { VARIABLE *var; int integer_used = 0, binary_used = 0; xassert(is_keyword(mpl, "var")); if (mpl->flag_s) mpl_error(mpl, "variable statement must precede solve statement"); get_token(mpl /* var */); /* symbolic name must follow the keyword 'var' */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "symbolic name missing where expected"); /* there must be no other object with the same name */ if (avl_find_node(mpl->tree, mpl->image) != NULL) mpl_error(mpl, "%s multiply declared", mpl->image); /* create model variable */ var = alloc(VARIABLE); var->name = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(var->name, mpl->image); var->alias = NULL; var->dim = 0; var->domain = NULL; var->type = A_NUMERIC; var->lbnd = NULL; var->ubnd = NULL; var->array = NULL; get_token(mpl /* */); /* parse optional alias */ if (mpl->token == T_STRING) { var->alias = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(var->alias, mpl->image); get_token(mpl /* */); } /* parse optional indexing expression */ if (mpl->token == T_LBRACE) { var->domain = indexing_expression(mpl); var->dim = domain_arity(mpl, var->domain); } /* include the variable name in the symbolic names table */ { AVLNODE *node; node = avl_insert_node(mpl->tree, var->name); avl_set_node_type(node, A_VARIABLE); avl_set_node_link(node, (void *)var); } /* parse the list of optional attributes */ for (;;) { if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_SEMICOLON) break; if (is_keyword(mpl, "integer")) { if (integer_used) mpl_error(mpl, "at most one integer allowed"); if (var->type != A_BINARY) var->type = A_INTEGER; integer_used = 1; get_token(mpl /* integer */); } else if (is_keyword(mpl, "binary")) bin: { if (binary_used) mpl_error(mpl, "at most one binary allowed"); var->type = A_BINARY; binary_used = 1; get_token(mpl /* binary */); } else if (is_keyword(mpl, "logical")) { if (!mpl->as_binary) { warning(mpl, "keyword logical understood as binary"); mpl->as_binary = 1; } goto bin; } else if (is_keyword(mpl, "symbolic")) mpl_error(mpl, "variable cannot be symbolic"); else if (mpl->token == T_GE) { /* lower bound */ if (var->lbnd != NULL) { if (var->lbnd == var->ubnd) mpl_error(mpl, "both fixed value and lower bound not allo" "wed"); else mpl_error(mpl, "at most one lower bound allowed"); } get_token(mpl /* >= */); /* parse an expression that specifies the lower bound */ var->lbnd = expression_5(mpl); if (var->lbnd->type == A_SYMBOLIC) var->lbnd = make_unary(mpl, O_CVTNUM, var->lbnd, A_NUMERIC, 0); if (var->lbnd->type != A_NUMERIC) mpl_error(mpl, "expression following >= has invalid type"); xassert(var->lbnd->dim == 0); } else if (mpl->token == T_LE) { /* upper bound */ if (var->ubnd != NULL) { if (var->ubnd == var->lbnd) mpl_error(mpl, "both fixed value and upper bound not allo" "wed"); else mpl_error(mpl, "at most one upper bound allowed"); } get_token(mpl /* <= */); /* parse an expression that specifies the upper bound */ var->ubnd = expression_5(mpl); if (var->ubnd->type == A_SYMBOLIC) var->ubnd = make_unary(mpl, O_CVTNUM, var->ubnd, A_NUMERIC, 0); if (var->ubnd->type != A_NUMERIC) mpl_error(mpl, "expression following <= has invalid type"); xassert(var->ubnd->dim == 0); } else if (mpl->token == T_EQ) { /* fixed value */ char opstr[8]; if (!(var->lbnd == NULL && var->ubnd == NULL)) { if (var->lbnd == var->ubnd) mpl_error(mpl, "at most one fixed value allowed"); else if (var->lbnd != NULL) mpl_error(mpl, "both lower bound and fixed value not allo" "wed"); else mpl_error(mpl, "both upper bound and fixed value not allo" "wed"); } strcpy(opstr, mpl->image); xassert(strlen(opstr) < sizeof(opstr)); get_token(mpl /* = | == */); /* parse an expression that specifies the fixed value */ var->lbnd = expression_5(mpl); if (var->lbnd->type == A_SYMBOLIC) var->lbnd = make_unary(mpl, O_CVTNUM, var->lbnd, A_NUMERIC, 0); if (var->lbnd->type != A_NUMERIC) mpl_error(mpl, "expression following %s has invalid type", opstr); xassert(var->lbnd->dim == 0); /* indicate that the variable is fixed, not bounded */ var->ubnd = var->lbnd; } else if (mpl->token == T_LT || mpl->token == T_GT || mpl->token == T_NE) mpl_error(mpl, "strict bound not allowed"); else mpl_error(mpl, "syntax error in variable statement"); } /* close the domain scope */ if (var->domain != NULL) close_scope(mpl, var->domain); /* the variable statement has been completely parsed */ xassert(mpl->token == T_SEMICOLON); get_token(mpl /* ; */); return var; } /*---------------------------------------------------------------------- -- constraint_statement - parse constraint statement. -- -- This routine parses constraint statement using the syntax: -- -- ::= -- : ; -- ::= -- ::= subject to -- ::= subj to -- ::= s.t. -- ::= -- ::= -- ::= -- ::= -- ::= , >= -- ::= , <= -- ::= , = -- ::= , <= , <= -- ::= , >= , >= -- ::= -- -- Commae in are optional and may be omitted anywhere. */ CONSTRAINT *constraint_statement(MPL *mpl) { CONSTRAINT *con; CODE *first, *second, *third; int rho; char opstr[8]; if (mpl->flag_s) mpl_error(mpl, "constraint statement must precede solve statement") ; if (is_keyword(mpl, "subject")) { get_token(mpl /* subject */); if (!is_keyword(mpl, "to")) mpl_error(mpl, "keyword subject to incomplete"); get_token(mpl /* to */); } else if (is_keyword(mpl, "subj")) { get_token(mpl /* subj */); if (!is_keyword(mpl, "to")) mpl_error(mpl, "keyword subj to incomplete"); get_token(mpl /* to */); } else if (mpl->token == T_SPTP) get_token(mpl /* s.t. */); /* the current token must be symbolic name of constraint */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "symbolic name missing where expected"); /* there must be no other object with the same name */ if (avl_find_node(mpl->tree, mpl->image) != NULL) mpl_error(mpl, "%s multiply declared", mpl->image); /* create model constraint */ con = alloc(CONSTRAINT); con->name = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(con->name, mpl->image); con->alias = NULL; con->dim = 0; con->domain = NULL; con->type = A_CONSTRAINT; con->code = NULL; con->lbnd = NULL; con->ubnd = NULL; con->array = NULL; get_token(mpl /* */); /* parse optional alias */ if (mpl->token == T_STRING) { con->alias = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(con->alias, mpl->image); get_token(mpl /* */); } /* parse optional indexing expression */ if (mpl->token == T_LBRACE) { con->domain = indexing_expression(mpl); con->dim = domain_arity(mpl, con->domain); } /* include the constraint name in the symbolic names table */ { AVLNODE *node; node = avl_insert_node(mpl->tree, con->name); avl_set_node_type(node, A_CONSTRAINT); avl_set_node_link(node, (void *)con); } /* the colon must precede the first expression */ if (mpl->token != T_COLON) mpl_error(mpl, "colon missing where expected"); get_token(mpl /* : */); /* parse the first expression */ first = expression_5(mpl); if (first->type == A_SYMBOLIC) first = make_unary(mpl, O_CVTNUM, first, A_NUMERIC, 0); if (!(first->type == A_NUMERIC || first->type == A_FORMULA)) mpl_error(mpl, "expression following colon has invalid type"); xassert(first->dim == 0); /* relational operator must follow the first expression */ if (mpl->token == T_COMMA) get_token(mpl /* , */); switch (mpl->token) { case T_LE: case T_GE: case T_EQ: break; case T_LT: case T_GT: case T_NE: mpl_error(mpl, "strict inequality not allowed"); case T_SEMICOLON: mpl_error(mpl, "constraint must be equality or inequality"); default: goto err; } rho = mpl->token; strcpy(opstr, mpl->image); xassert(strlen(opstr) < sizeof(opstr)); get_token(mpl /* rho */); /* parse the second expression */ second = expression_5(mpl); if (second->type == A_SYMBOLIC) second = make_unary(mpl, O_CVTNUM, second, A_NUMERIC, 0); if (!(second->type == A_NUMERIC || second->type == A_FORMULA)) mpl_error(mpl, "expression following %s has invalid type", opstr); xassert(second->dim == 0); /* check a token that follow the second expression */ if (mpl->token == T_COMMA) { get_token(mpl /* , */); if (mpl->token == T_SEMICOLON) goto err; } if (mpl->token == T_LT || mpl->token == T_LE || mpl->token == T_EQ || mpl->token == T_GE || mpl->token == T_GT || mpl->token == T_NE) { /* it is another relational operator, therefore the constraint is double inequality */ if (rho == T_EQ || mpl->token != rho) mpl_error(mpl, "double inequality must be ... <= ... <= ... or " "... >= ... >= ..."); /* the first expression cannot be linear form */ if (first->type == A_FORMULA) mpl_error(mpl, "leftmost expression in double inequality cannot" " be linear form"); get_token(mpl /* rho */); /* parse the third expression */ third = expression_5(mpl); if (third->type == A_SYMBOLIC) third = make_unary(mpl, O_CVTNUM, second, A_NUMERIC, 0); if (!(third->type == A_NUMERIC || third->type == A_FORMULA)) mpl_error(mpl, "rightmost expression in double inequality const" "raint has invalid type"); xassert(third->dim == 0); /* the third expression also cannot be linear form */ if (third->type == A_FORMULA) mpl_error(mpl, "rightmost expression in double inequality canno" "t be linear form"); } else { /* the constraint is equality or single inequality */ third = NULL; } /* close the domain scope */ if (con->domain != NULL) close_scope(mpl, con->domain); /* convert all expressions to linear form, if necessary */ if (first->type != A_FORMULA) first = make_unary(mpl, O_CVTLFM, first, A_FORMULA, 0); if (second->type != A_FORMULA) second = make_unary(mpl, O_CVTLFM, second, A_FORMULA, 0); if (third != NULL) third = make_unary(mpl, O_CVTLFM, third, A_FORMULA, 0); /* arrange expressions in the constraint */ if (third == NULL) { /* the constraint is equality or single inequality */ switch (rho) { case T_LE: /* first <= second */ con->code = first; con->lbnd = NULL; con->ubnd = second; break; case T_GE: /* first >= second */ con->code = first; con->lbnd = second; con->ubnd = NULL; break; case T_EQ: /* first = second */ con->code = first; con->lbnd = second; con->ubnd = second; break; default: xassert(rho != rho); } } else { /* the constraint is double inequality */ switch (rho) { case T_LE: /* first <= second <= third */ con->code = second; con->lbnd = first; con->ubnd = third; break; case T_GE: /* first >= second >= third */ con->code = second; con->lbnd = third; con->ubnd = first; break; default: xassert(rho != rho); } } /* the constraint statement has been completely parsed */ if (mpl->token != T_SEMICOLON) err: mpl_error(mpl, "syntax error in constraint statement"); get_token(mpl /* ; */); return con; } /*---------------------------------------------------------------------- -- objective_statement - parse objective statement. -- -- This routine parses objective statement using the syntax: -- -- ::= : -- ; -- ::= minimize -- ::= maximize -- ::= -- ::= -- ::= -- ::= -- ::= */ CONSTRAINT *objective_statement(MPL *mpl) { CONSTRAINT *obj; int type; if (is_keyword(mpl, "minimize")) type = A_MINIMIZE; else if (is_keyword(mpl, "maximize")) type = A_MAXIMIZE; else xassert(mpl != mpl); if (mpl->flag_s) mpl_error(mpl, "objective statement must precede solve statement"); get_token(mpl /* minimize | maximize */); /* symbolic name must follow the verb 'minimize' or 'maximize' */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "symbolic name missing where expected"); /* there must be no other object with the same name */ if (avl_find_node(mpl->tree, mpl->image) != NULL) mpl_error(mpl, "%s multiply declared", mpl->image); /* create model objective */ obj = alloc(CONSTRAINT); obj->name = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(obj->name, mpl->image); obj->alias = NULL; obj->dim = 0; obj->domain = NULL; obj->type = type; obj->code = NULL; obj->lbnd = NULL; obj->ubnd = NULL; obj->array = NULL; get_token(mpl /* */); /* parse optional alias */ if (mpl->token == T_STRING) { obj->alias = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(obj->alias, mpl->image); get_token(mpl /* */); } /* parse optional indexing expression */ if (mpl->token == T_LBRACE) { obj->domain = indexing_expression(mpl); obj->dim = domain_arity(mpl, obj->domain); } /* include the constraint name in the symbolic names table */ { AVLNODE *node; node = avl_insert_node(mpl->tree, obj->name); avl_set_node_type(node, A_CONSTRAINT); avl_set_node_link(node, (void *)obj); } /* the colon must precede the objective expression */ if (mpl->token != T_COLON) mpl_error(mpl, "colon missing where expected"); get_token(mpl /* : */); /* parse the objective expression */ obj->code = expression_5(mpl); if (obj->code->type == A_SYMBOLIC) obj->code = make_unary(mpl, O_CVTNUM, obj->code, A_NUMERIC, 0); if (obj->code->type == A_NUMERIC) obj->code = make_unary(mpl, O_CVTLFM, obj->code, A_FORMULA, 0); if (obj->code->type != A_FORMULA) mpl_error(mpl, "expression following colon has invalid type"); xassert(obj->code->dim == 0); /* close the domain scope */ if (obj->domain != NULL) close_scope(mpl, obj->domain); /* the objective statement has been completely parsed */ if (mpl->token != T_SEMICOLON) mpl_error(mpl, "syntax error in objective statement"); get_token(mpl /* ; */); return obj; } #if 1 /* 11/II-2008 */ /*********************************************************************** * table_statement - parse table statement * * This routine parses table statement using the syntax: * * ::= *
::= * * ::= * table
IN : * [ ] , ; * ::= * ::= * ::= * ::= * ::= , * ::= * ::= <- * ::= * ::= , * ::= * ::= , * ::= * ::= ~ * * ::= * table
OUT : * ; * ::= * ::= * ::= , * ::= * ::= ~ */ TABLE *table_statement(MPL *mpl) { TABLE *tab; TABARG *last_arg, *arg; TABFLD *last_fld, *fld; TABIN *last_in, *in; TABOUT *last_out, *out; AVLNODE *node; int nflds; char name[MAX_LENGTH+1]; xassert(is_keyword(mpl, "table")); get_token(mpl /* solve */); /* symbolic name must follow the keyword table */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "symbolic name missing where expected"); /* there must be no other object with the same name */ if (avl_find_node(mpl->tree, mpl->image) != NULL) mpl_error(mpl, "%s multiply declared", mpl->image); /* create data table */ tab = alloc(TABLE); tab->name = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(tab->name, mpl->image); get_token(mpl /* */); /* parse optional alias */ if (mpl->token == T_STRING) { tab->alias = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(tab->alias, mpl->image); get_token(mpl /* */); } else tab->alias = NULL; /* parse optional indexing expression */ if (mpl->token == T_LBRACE) { /* this is output table */ tab->type = A_OUTPUT; tab->u.out.domain = indexing_expression(mpl); if (!is_keyword(mpl, "OUT")) mpl_error(mpl, "keyword OUT missing where expected"); get_token(mpl /* OUT */); } else { /* this is input table */ tab->type = A_INPUT; if (!is_keyword(mpl, "IN")) mpl_error(mpl, "keyword IN missing where expected"); get_token(mpl /* IN */); } /* parse argument list */ tab->arg = last_arg = NULL; for (;;) { /* create argument list entry */ arg = alloc(TABARG); /* parse argument expression */ if (mpl->token == T_COMMA || mpl->token == T_COLON || mpl->token == T_SEMICOLON) mpl_error(mpl, "argument expression missing where expected"); arg->code = expression_5(mpl); /* convert the result to symbolic type, if necessary */ if (arg->code->type == A_NUMERIC) arg->code = make_unary(mpl, O_CVTSYM, arg->code, A_SYMBOLIC, 0); /* check that now the result is of symbolic type */ if (arg->code->type != A_SYMBOLIC) mpl_error(mpl, "argument expression has invalid type"); /* add the entry to the end of the list */ arg->next = NULL; if (last_arg == NULL) tab->arg = arg; else last_arg->next = arg; last_arg = arg; /* argument expression has been parsed */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_COLON || mpl->token == T_SEMICOLON) break; } xassert(tab->arg != NULL); /* argument list must end with colon */ if (mpl->token == T_COLON) get_token(mpl /* : */); else mpl_error(mpl, "colon missing where expected"); /* parse specific part of the table statement */ switch (tab->type) { case A_INPUT: goto input_table; case A_OUTPUT: goto output_table; default: xassert(tab != tab); } input_table: /* parse optional set name */ if (mpl->token == T_NAME) { node = avl_find_node(mpl->tree, mpl->image); if (node == NULL) mpl_error(mpl, "%s not defined", mpl->image); if (avl_get_node_type(node) != A_SET) mpl_error(mpl, "%s not a set", mpl->image); tab->u.in.set = (SET *)avl_get_node_link(node); if (tab->u.in.set->assign != NULL) mpl_error(mpl, "%s needs no data", mpl->image); if (tab->u.in.set->dim != 0) mpl_error(mpl, "%s must be a simple set", mpl->image); get_token(mpl /* */); if (mpl->token == T_INPUT) get_token(mpl /* <- */); else mpl_error(mpl, "delimiter <- missing where expected"); } else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else tab->u.in.set = NULL; /* parse field list */ tab->u.in.fld = last_fld = NULL; nflds = 0; if (mpl->token == T_LBRACKET) get_token(mpl /* [ */); else mpl_error(mpl, "field list missing where expected"); for (;;) { /* create field list entry */ fld = alloc(TABFLD); /* parse field name */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "field name missing where expected"); fld->name = dmp_get_atomv(mpl->pool, strlen(mpl->image)+1); strcpy(fld->name, mpl->image); get_token(mpl /* */); /* add the entry to the end of the list */ fld->next = NULL; if (last_fld == NULL) tab->u.in.fld = fld; else last_fld->next = fld; last_fld = fld; nflds++; /* field name has been parsed */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_RBRACKET) break; else mpl_error(mpl, "syntax error in field list"); } /* check that the set dimen is equal to the number of fields */ if (tab->u.in.set != NULL && tab->u.in.set->dimen != nflds) mpl_error(mpl, "there must be %d field%s rather than %d", tab->u.in.set->dimen, tab->u.in.set->dimen == 1 ? "" : "s", nflds); get_token(mpl /* ] */); /* parse optional input list */ tab->u.in.list = last_in = NULL; while (mpl->token == T_COMMA) { get_token(mpl /* , */); /* create input list entry */ in = alloc(TABIN); /* parse parameter name */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "parameter name missing where expected"); node = avl_find_node(mpl->tree, mpl->image); if (node == NULL) mpl_error(mpl, "%s not defined", mpl->image); if (avl_get_node_type(node) != A_PARAMETER) mpl_error(mpl, "%s not a parameter", mpl->image); in->par = (PARAMETER *)avl_get_node_link(node); if (in->par->dim != nflds) mpl_error(mpl, "%s must have %d subscript%s rather than %d", mpl->image, nflds, nflds == 1 ? "" : "s", in->par->dim); if (in->par->assign != NULL) mpl_error(mpl, "%s needs no data", mpl->image); get_token(mpl /* */); /* parse optional field name */ if (mpl->token == T_TILDE) { get_token(mpl /* ~ */); /* parse field name */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "field name missing where expected"); xassert(strlen(mpl->image) < sizeof(name)); strcpy(name, mpl->image); get_token(mpl /* */); } else { /* field name is the same as the parameter name */ xassert(strlen(in->par->name) < sizeof(name)); strcpy(name, in->par->name); } /* assign field name */ in->name = dmp_get_atomv(mpl->pool, strlen(name)+1); strcpy(in->name, name); /* add the entry to the end of the list */ in->next = NULL; if (last_in == NULL) tab->u.in.list = in; else last_in->next = in; last_in = in; } goto end_of_table; output_table: /* parse output list */ tab->u.out.list = last_out = NULL; for (;;) { /* create output list entry */ out = alloc(TABOUT); /* parse expression */ if (mpl->token == T_COMMA || mpl->token == T_SEMICOLON) mpl_error(mpl, "expression missing where expected"); if (mpl->token == T_NAME) { xassert(strlen(mpl->image) < sizeof(name)); strcpy(name, mpl->image); } else name[0] = '\0'; out->code = expression_5(mpl); /* parse optional field name */ if (mpl->token == T_TILDE) { get_token(mpl /* ~ */); /* parse field name */ if (mpl->token == T_NAME) ; else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "field name missing where expected"); xassert(strlen(mpl->image) < sizeof(name)); strcpy(name, mpl->image); get_token(mpl /* */); } /* assign field name */ if (name[0] == '\0') mpl_error(mpl, "field name required"); out->name = dmp_get_atomv(mpl->pool, strlen(name)+1); strcpy(out->name, name); /* add the entry to the end of the list */ out->next = NULL; if (last_out == NULL) tab->u.out.list = out; else last_out->next = out; last_out = out; /* output item has been parsed */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else if (mpl->token == T_SEMICOLON) break; else mpl_error(mpl, "syntax error in output list"); } /* close the domain scope */ close_scope(mpl,tab->u.out.domain); end_of_table: /* the table statement must end with semicolon */ if (mpl->token != T_SEMICOLON) mpl_error(mpl, "syntax error in table statement"); get_token(mpl /* ; */); return tab; } #endif /*---------------------------------------------------------------------- -- solve_statement - parse solve statement. -- -- This routine parses solve statement using the syntax: -- -- ::= solve ; -- -- The solve statement can be used at most once. */ void *solve_statement(MPL *mpl) { xassert(is_keyword(mpl, "solve")); if (mpl->flag_s) mpl_error(mpl, "at most one solve statement allowed"); mpl->flag_s = 1; get_token(mpl /* solve */); /* semicolon must follow solve statement */ if (mpl->token != T_SEMICOLON) mpl_error(mpl, "syntax error in solve statement"); get_token(mpl /* ; */); return NULL; } /*---------------------------------------------------------------------- -- check_statement - parse check statement. -- -- This routine parses check statement using the syntax: -- -- ::= check : ; -- ::= -- ::= -- -- If is omitted, colon following it may also be omitted. */ CHECK *check_statement(MPL *mpl) { CHECK *chk; xassert(is_keyword(mpl, "check")); /* create check descriptor */ chk = alloc(CHECK); chk->domain = NULL; chk->code = NULL; get_token(mpl /* check */); /* parse optional indexing expression */ if (mpl->token == T_LBRACE) { chk->domain = indexing_expression(mpl); #if 0 if (mpl->token != T_COLON) mpl_error(mpl, "colon missing where expected"); #endif } /* skip optional colon */ if (mpl->token == T_COLON) get_token(mpl /* : */); /* parse logical expression */ chk->code = expression_13(mpl); if (chk->code->type != A_LOGICAL) mpl_error(mpl, "expression has invalid type"); xassert(chk->code->dim == 0); /* close the domain scope */ if (chk->domain != NULL) close_scope(mpl, chk->domain); /* the check statement has been completely parsed */ if (mpl->token != T_SEMICOLON) mpl_error(mpl, "syntax error in check statement"); get_token(mpl /* ; */); return chk; } #if 1 /* 15/V-2010 */ /*---------------------------------------------------------------------- -- display_statement - parse display statement. -- -- This routine parses display statement using the syntax: -- -- ::= display : ; -- ::= display ; -- ::= -- ::= -- ::= -- ::= , -- ::= -- ::= -- ::= [ ] -- ::= -- ::= [ ] -- ::= -- ::= [ ] -- ::= -- ::= [ ] -- ::= */ DISPLAY *display_statement(MPL *mpl) { DISPLAY *dpy; DISPLAY1 *entry, *last_entry; xassert(is_keyword(mpl, "display")); /* create display descriptor */ dpy = alloc(DISPLAY); dpy->domain = NULL; dpy->list = last_entry = NULL; get_token(mpl /* display */); /* parse optional indexing expression */ if (mpl->token == T_LBRACE) dpy->domain = indexing_expression(mpl); /* skip optional colon */ if (mpl->token == T_COLON) get_token(mpl /* : */); /* parse display list */ for (;;) { /* create new display entry */ entry = alloc(DISPLAY1); entry->type = 0; entry->next = NULL; /* and append it to the display list */ if (dpy->list == NULL) dpy->list = entry; else last_entry->next = entry; last_entry = entry; /* parse display entry */ if (mpl->token == T_NAME) { AVLNODE *node; int next_token; get_token(mpl /* */); next_token = mpl->token; unget_token(mpl); if (!(next_token == T_COMMA || next_token == T_SEMICOLON)) { /* symbolic name begins expression */ goto expr; } /* display entry is dummy index or model object */ node = avl_find_node(mpl->tree, mpl->image); if (node == NULL) mpl_error(mpl, "%s not defined", mpl->image); entry->type = avl_get_node_type(node); switch (avl_get_node_type(node)) { case A_INDEX: entry->u.slot = (DOMAIN_SLOT *)avl_get_node_link(node); break; case A_SET: entry->u.set = (SET *)avl_get_node_link(node); break; case A_PARAMETER: entry->u.par = (PARAMETER *)avl_get_node_link(node); break; case A_VARIABLE: entry->u.var = (VARIABLE *)avl_get_node_link(node); if (!mpl->flag_s) mpl_error(mpl, "invalid reference to variable %s above" " solve statement", entry->u.var->name); break; case A_CONSTRAINT: entry->u.con = (CONSTRAINT *)avl_get_node_link(node); if (!mpl->flag_s) mpl_error(mpl, "invalid reference to %s %s above solve" " statement", entry->u.con->type == A_CONSTRAINT ? "constraint" : "objective", entry->u.con->name); break; default: xassert(node != node); } get_token(mpl /* */); } else expr: { /* display entry is expression */ entry->type = A_EXPRESSION; entry->u.code = expression_13(mpl); } /* check a token that follows the entry parsed */ if (mpl->token == T_COMMA) get_token(mpl /* , */); else break; } /* close the domain scope */ if (dpy->domain != NULL) close_scope(mpl, dpy->domain); /* the display statement has been completely parsed */ if (mpl->token != T_SEMICOLON) mpl_error(mpl, "syntax error in display statement"); get_token(mpl /* ; */); return dpy; } #endif /*---------------------------------------------------------------------- -- printf_statement - parse printf statement. -- -- This routine parses print statement using the syntax: -- -- ::= ; -- ::= > ; -- ::= >> ; -- ::= printf : -- ::= printf -- ::= -- ::= -- ::= -- ::= -- ::= , -- ::= -- ::= */ PRINTF *printf_statement(MPL *mpl) { PRINTF *prt; PRINTF1 *entry, *last_entry; xassert(is_keyword(mpl, "printf")); /* create printf descriptor */ prt = alloc(PRINTF); prt->domain = NULL; prt->fmt = NULL; prt->list = last_entry = NULL; get_token(mpl /* printf */); /* parse optional indexing expression */ if (mpl->token == T_LBRACE) { prt->domain = indexing_expression(mpl); #if 0 if (mpl->token != T_COLON) mpl_error(mpl, "colon missing where expected"); #endif } /* skip optional colon */ if (mpl->token == T_COLON) get_token(mpl /* : */); /* parse expression for format string */ prt->fmt = expression_5(mpl); /* convert it to symbolic type, if necessary */ if (prt->fmt->type == A_NUMERIC) prt->fmt = make_unary(mpl, O_CVTSYM, prt->fmt, A_SYMBOLIC, 0); /* check that now the expression is of symbolic type */ if (prt->fmt->type != A_SYMBOLIC) mpl_error(mpl, "format expression has invalid type"); /* parse printf list */ while (mpl->token == T_COMMA) { get_token(mpl /* , */); /* create new printf entry */ entry = alloc(PRINTF1); entry->code = NULL; entry->next = NULL; /* and append it to the printf list */ if (prt->list == NULL) prt->list = entry; else last_entry->next = entry; last_entry = entry; /* parse printf entry */ entry->code = expression_9(mpl); if (!(entry->code->type == A_NUMERIC || entry->code->type == A_SYMBOLIC || entry->code->type == A_LOGICAL)) mpl_error(mpl, "only numeric, symbolic, or logical expression a" "llowed"); } /* close the domain scope */ if (prt->domain != NULL) close_scope(mpl, prt->domain); #if 1 /* 14/VII-2006 */ /* parse optional redirection */ prt->fname = NULL, prt->app = 0; if (mpl->token == T_GT || mpl->token == T_APPEND) { prt->app = (mpl->token == T_APPEND); get_token(mpl /* > or >> */); /* parse expression for file name string */ prt->fname = expression_5(mpl); /* convert it to symbolic type, if necessary */ if (prt->fname->type == A_NUMERIC) prt->fname = make_unary(mpl, O_CVTSYM, prt->fname, A_SYMBOLIC, 0); /* check that now the expression is of symbolic type */ if (prt->fname->type != A_SYMBOLIC) mpl_error(mpl, "file name expression has invalid type"); } #endif /* the printf statement has been completely parsed */ if (mpl->token != T_SEMICOLON) mpl_error(mpl, "syntax error in printf statement"); get_token(mpl /* ; */); return prt; } /*---------------------------------------------------------------------- -- for_statement - parse for statement. -- -- This routine parses for statement using the syntax: -- -- ::= for -- ::= for { } -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= */ FOR *for_statement(MPL *mpl) { FOR *fur; STATEMENT *stmt, *last_stmt; xassert(is_keyword(mpl, "for")); /* create for descriptor */ fur = alloc(FOR); fur->domain = NULL; fur->list = last_stmt = NULL; get_token(mpl /* for */); /* parse indexing expression */ if (mpl->token != T_LBRACE) mpl_error(mpl, "indexing expression missing where expected"); fur->domain = indexing_expression(mpl); /* skip optional colon */ if (mpl->token == T_COLON) get_token(mpl /* : */); /* parse for statement body */ if (mpl->token != T_LBRACE) { /* parse simple statement */ fur->list = simple_statement(mpl, 1); } else { /* parse compound statement */ get_token(mpl /* { */); while (mpl->token != T_RBRACE) { /* parse statement */ stmt = simple_statement(mpl, 1); /* and append it to the end of the statement list */ if (last_stmt == NULL) fur->list = stmt; else last_stmt->next = stmt; last_stmt = stmt; } get_token(mpl /* } */); } /* close the domain scope */ xassert(fur->domain != NULL); close_scope(mpl, fur->domain); /* the for statement has been completely parsed */ return fur; } /*---------------------------------------------------------------------- -- end_statement - parse end statement. -- -- This routine parses end statement using the syntax: -- -- ::= end ; */ void end_statement(MPL *mpl) { if (!mpl->flag_d && is_keyword(mpl, "end") || mpl->flag_d && is_literal(mpl, "end")) { get_token(mpl /* end */); if (mpl->token == T_SEMICOLON) get_token(mpl /* ; */); else warning(mpl, "no semicolon following end statement; missing" " semicolon inserted"); } else warning(mpl, "unexpected end of file; missing end statement in" "serted"); if (mpl->token != T_EOF) warning(mpl, "some text detected beyond end statement; text ig" "nored"); return; } /*---------------------------------------------------------------------- -- simple_statement - parse simple statement. -- -- This routine parses simple statement using the syntax: -- -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= -- ::= -- -- If the flag spec is set, some statements cannot be used. */ STATEMENT *simple_statement(MPL *mpl, int spec) { STATEMENT *stmt; stmt = alloc(STATEMENT); stmt->line = mpl->line; stmt->next = NULL; if (is_keyword(mpl, "set")) { if (spec) mpl_error(mpl, "set statement not allowed here"); stmt->type = A_SET; stmt->u.set = set_statement(mpl); } else if (is_keyword(mpl, "param")) { if (spec) mpl_error(mpl, "parameter statement not allowed here"); stmt->type = A_PARAMETER; stmt->u.par = parameter_statement(mpl); } else if (is_keyword(mpl, "var")) { if (spec) mpl_error(mpl, "variable statement not allowed here"); stmt->type = A_VARIABLE; stmt->u.var = variable_statement(mpl); } else if (is_keyword(mpl, "subject") || is_keyword(mpl, "subj") || mpl->token == T_SPTP) { if (spec) mpl_error(mpl, "constraint statement not allowed here"); stmt->type = A_CONSTRAINT; stmt->u.con = constraint_statement(mpl); } else if (is_keyword(mpl, "minimize") || is_keyword(mpl, "maximize")) { if (spec) mpl_error(mpl, "objective statement not allowed here"); stmt->type = A_CONSTRAINT; stmt->u.con = objective_statement(mpl); } #if 1 /* 11/II-2008 */ else if (is_keyword(mpl, "table")) { if (spec) mpl_error(mpl, "table statement not allowed here"); stmt->type = A_TABLE; stmt->u.tab = table_statement(mpl); } #endif else if (is_keyword(mpl, "solve")) { if (spec) mpl_error(mpl, "solve statement not allowed here"); stmt->type = A_SOLVE; stmt->u.slv = solve_statement(mpl); } else if (is_keyword(mpl, "check")) { stmt->type = A_CHECK; stmt->u.chk = check_statement(mpl); } else if (is_keyword(mpl, "display")) { stmt->type = A_DISPLAY; stmt->u.dpy = display_statement(mpl); } else if (is_keyword(mpl, "printf")) { stmt->type = A_PRINTF; stmt->u.prt = printf_statement(mpl); } else if (is_keyword(mpl, "for")) { stmt->type = A_FOR; stmt->u.fur = for_statement(mpl); } else if (mpl->token == T_NAME) { if (spec) mpl_error(mpl, "constraint statement not allowed here"); stmt->type = A_CONSTRAINT; stmt->u.con = constraint_statement(mpl); } else if (is_reserved(mpl)) mpl_error(mpl, "invalid use of reserved keyword %s", mpl->image); else mpl_error(mpl, "syntax error in model section"); return stmt; } /*---------------------------------------------------------------------- -- model_section - parse model section. -- -- This routine parses model section using the syntax: -- -- ::= -- ::= -- -- Parsing model section is terminated by either the keyword 'data', or -- the keyword 'end', or the end of file. */ void model_section(MPL *mpl) { STATEMENT *stmt, *last_stmt; xassert(mpl->model == NULL); last_stmt = NULL; while (!(mpl->token == T_EOF || is_keyword(mpl, "data") || is_keyword(mpl, "end"))) { /* parse statement */ stmt = simple_statement(mpl, 0); /* and append it to the end of the statement list */ if (last_stmt == NULL) mpl->model = stmt; else last_stmt->next = stmt; last_stmt = stmt; } return; } /* eof */ sources_5316/external/glpk/glpspx01.c0000644000176700017670000030116511401660400016322 0ustar paulpaul/* glpspx01.c (primal simplex method) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpspx.h" struct csa { /* common storage area */ /*--------------------------------------------------------------*/ /* LP data */ int m; /* number of rows (auxiliary variables), m > 0 */ int n; /* number of columns (structural variables), n > 0 */ char *type; /* char type[1+m+n]; */ /* type[0] is not used; type[k], 1 <= k <= m+n, is the type of variable x[k]: GLP_FR - free variable GLP_LO - variable with lower bound GLP_UP - variable with upper bound GLP_DB - double-bounded variable GLP_FX - fixed variable */ double *lb; /* double lb[1+m+n]; */ /* lb[0] is not used; lb[k], 1 <= k <= m+n, is an lower bound of variable x[k]; if x[k] has no lower bound, lb[k] is zero */ double *ub; /* double ub[1+m+n]; */ /* ub[0] is not used; ub[k], 1 <= k <= m+n, is an upper bound of variable x[k]; if x[k] has no upper bound, ub[k] is zero; if x[k] is of fixed type, ub[k] is the same as lb[k] */ double *coef; /* double coef[1+m+n]; */ /* coef[0] is not used; coef[k], 1 <= k <= m+n, is an objective coefficient at variable x[k] (note that on phase I auxiliary variables also may have non-zero objective coefficients) */ /*--------------------------------------------------------------*/ /* original objective function */ double *obj; /* double obj[1+n]; */ /* obj[0] is a constant term of the original objective function; obj[j], 1 <= j <= n, is an original objective coefficient at structural variable x[m+j] */ double zeta; /* factor used to scale original objective coefficients; its sign defines original optimization direction: zeta > 0 means minimization, zeta < 0 means maximization */ /*--------------------------------------------------------------*/ /* constraint matrix A; it has m rows and n columns and is stored by columns */ int *A_ptr; /* int A_ptr[1+n+1]; */ /* A_ptr[0] is not used; A_ptr[j], 1 <= j <= n, is starting position of j-th column in arrays A_ind and A_val; note that A_ptr[1] is always 1; A_ptr[n+1] indicates the position after the last element in arrays A_ind and A_val */ int *A_ind; /* int A_ind[A_ptr[n+1]]; */ /* row indices */ double *A_val; /* double A_val[A_ptr[n+1]]; */ /* non-zero element values */ /*--------------------------------------------------------------*/ /* basis header */ int *head; /* int head[1+m+n]; */ /* head[0] is not used; head[i], 1 <= i <= m, is the ordinal number of basic variable xB[i]; head[i] = k means that xB[i] = x[k] and i-th column of matrix B is k-th column of matrix (I|-A); head[m+j], 1 <= j <= n, is the ordinal number of non-basic variable xN[j]; head[m+j] = k means that xN[j] = x[k] and j-th column of matrix N is k-th column of matrix (I|-A) */ char *stat; /* char stat[1+n]; */ /* stat[0] is not used; stat[j], 1 <= j <= n, is the status of non-basic variable xN[j], which defines its active bound: GLP_NL - lower bound is active GLP_NU - upper bound is active GLP_NF - free variable GLP_NS - fixed variable */ /*--------------------------------------------------------------*/ /* matrix B is the basis matrix; it is composed from columns of the augmented constraint matrix (I|-A) corresponding to basic variables and stored in a factorized (invertable) form */ int valid; /* factorization is valid only if this flag is set */ BFD *bfd; /* BFD bfd[1:m,1:m]; */ /* factorized (invertable) form of the basis matrix */ /*--------------------------------------------------------------*/ /* matrix N is a matrix composed from columns of the augmented constraint matrix (I|-A) corresponding to non-basic variables except fixed ones; it is stored by rows and changes every time the basis changes */ int *N_ptr; /* int N_ptr[1+m+1]; */ /* N_ptr[0] is not used; N_ptr[i], 1 <= i <= m, is starting position of i-th row in arrays N_ind and N_val; note that N_ptr[1] is always 1; N_ptr[m+1] indicates the position after the last element in arrays N_ind and N_val */ int *N_len; /* int N_len[1+m]; */ /* N_len[0] is not used; N_len[i], 1 <= i <= m, is length of i-th row (0 to n) */ int *N_ind; /* int N_ind[N_ptr[m+1]]; */ /* column indices */ double *N_val; /* double N_val[N_ptr[m+1]]; */ /* non-zero element values */ /*--------------------------------------------------------------*/ /* working parameters */ int phase; /* search phase: 0 - not determined yet 1 - search for primal feasible solution 2 - search for optimal solution */ glp_long tm_beg; /* time value at the beginning of the search */ int it_beg; /* simplex iteration count at the beginning of the search */ int it_cnt; /* simplex iteration count; it increases by one every time the basis changes (including the case when a non-basic variable jumps to its opposite bound) */ int it_dpy; /* simplex iteration count at the most recent display output */ /*--------------------------------------------------------------*/ /* basic solution components */ double *bbar; /* double bbar[1+m]; */ /* bbar[0] is not used; bbar[i], 1 <= i <= m, is primal value of basic variable xB[i] (if xB[i] is free, its primal value is not updated) */ double *cbar; /* double cbar[1+n]; */ /* cbar[0] is not used; cbar[j], 1 <= j <= n, is reduced cost of non-basic variable xN[j] (if xN[j] is fixed, its reduced cost is not updated) */ /*--------------------------------------------------------------*/ /* the following pricing technique options may be used: GLP_PT_STD - standard ("textbook") pricing; GLP_PT_PSE - projected steepest edge; GLP_PT_DVX - Devex pricing (not implemented yet); in case of GLP_PT_STD the reference space is not used, and all steepest edge coefficients are set to 1 */ int refct; /* this count is set to an initial value when the reference space is defined and decreases by one every time the basis changes; once this count reaches zero, the reference space is redefined again */ char *refsp; /* char refsp[1+m+n]; */ /* refsp[0] is not used; refsp[k], 1 <= k <= m+n, is the flag which means that variable x[k] belongs to the current reference space */ double *gamma; /* double gamma[1+n]; */ /* gamma[0] is not used; gamma[j], 1 <= j <= n, is the steepest edge coefficient for non-basic variable xN[j]; if xN[j] is fixed, gamma[j] is not used and just set to 1 */ /*--------------------------------------------------------------*/ /* non-basic variable xN[q] chosen to enter the basis */ int q; /* index of the non-basic variable xN[q] chosen, 1 <= q <= n; if the set of eligible non-basic variables is empty and thus no variable has been chosen, q is set to 0 */ /*--------------------------------------------------------------*/ /* pivot column of the simplex table corresponding to non-basic variable xN[q] chosen is the following vector: T * e[q] = - inv(B) * N * e[q] = - inv(B) * N[q], where B is the current basis matrix, N[q] is a column of the matrix (I|-A) corresponding to xN[q] */ int tcol_nnz; /* number of non-zero components, 0 <= nnz <= m */ int *tcol_ind; /* int tcol_ind[1+m]; */ /* tcol_ind[0] is not used; tcol_ind[t], 1 <= t <= nnz, is an index of non-zero component, i.e. tcol_ind[t] = i means that tcol_vec[i] != 0 */ double *tcol_vec; /* double tcol_vec[1+m]; */ /* tcol_vec[0] is not used; tcol_vec[i], 1 <= i <= m, is a numeric value of i-th component of the column */ double tcol_max; /* infinity (maximum) norm of the column (max |tcol_vec[i]|) */ int tcol_num; /* number of significant non-zero components, which means that: |tcol_vec[i]| >= eps for i in tcol_ind[1,...,num], |tcol_vec[i]| < eps for i in tcol_ind[num+1,...,nnz], where eps is a pivot tolerance */ /*--------------------------------------------------------------*/ /* basic variable xB[p] chosen to leave the basis */ int p; /* index of the basic variable xB[p] chosen, 1 <= p <= m; p = 0 means that no basic variable reaches its bound; p < 0 means that non-basic variable xN[q] reaches its opposite bound before any basic variable */ int p_stat; /* new status (GLP_NL, GLP_NU, or GLP_NS) to be assigned to xB[p] once it has left the basis */ double teta; /* change of non-basic variable xN[q] (see above), on which xB[p] (or, if p < 0, xN[q] itself) reaches its bound */ /*--------------------------------------------------------------*/ /* pivot row of the simplex table corresponding to basic variable xB[p] chosen is the following vector: T' * e[p] = - N' * inv(B') * e[p] = - N' * rho, where B' is a matrix transposed to the current basis matrix, N' is a matrix, whose rows are columns of the matrix (I|-A) corresponding to non-basic non-fixed variables */ int trow_nnz; /* number of non-zero components, 0 <= nnz <= n */ int *trow_ind; /* int trow_ind[1+n]; */ /* trow_ind[0] is not used; trow_ind[t], 1 <= t <= nnz, is an index of non-zero component, i.e. trow_ind[t] = j means that trow_vec[j] != 0 */ double *trow_vec; /* int trow_vec[1+n]; */ /* trow_vec[0] is not used; trow_vec[j], 1 <= j <= n, is a numeric value of j-th component of the row */ /*--------------------------------------------------------------*/ /* working arrays */ double *work1; /* double work1[1+m]; */ double *work2; /* double work2[1+m]; */ double *work3; /* double work3[1+m]; */ double *work4; /* double work4[1+m]; */ }; static const double kappa = 0.10; /*********************************************************************** * alloc_csa - allocate common storage area * * This routine allocates all arrays in the common storage area (CSA) * and returns a pointer to the CSA. */ static struct csa *alloc_csa(glp_prob *lp) { struct csa *csa; int m = lp->m; int n = lp->n; int nnz = lp->nnz; csa = xmalloc(sizeof(struct csa)); xassert(m > 0 && n > 0); csa->m = m; csa->n = n; csa->type = xcalloc(1+m+n, sizeof(char)); csa->lb = xcalloc(1+m+n, sizeof(double)); csa->ub = xcalloc(1+m+n, sizeof(double)); csa->coef = xcalloc(1+m+n, sizeof(double)); csa->obj = xcalloc(1+n, sizeof(double)); csa->A_ptr = xcalloc(1+n+1, sizeof(int)); csa->A_ind = xcalloc(1+nnz, sizeof(int)); csa->A_val = xcalloc(1+nnz, sizeof(double)); csa->head = xcalloc(1+m+n, sizeof(int)); csa->stat = xcalloc(1+n, sizeof(char)); csa->N_ptr = xcalloc(1+m+1, sizeof(int)); csa->N_len = xcalloc(1+m, sizeof(int)); csa->N_ind = NULL; /* will be allocated later */ csa->N_val = NULL; /* will be allocated later */ csa->bbar = xcalloc(1+m, sizeof(double)); csa->cbar = xcalloc(1+n, sizeof(double)); csa->refsp = xcalloc(1+m+n, sizeof(char)); csa->gamma = xcalloc(1+n, sizeof(double)); csa->tcol_ind = xcalloc(1+m, sizeof(int)); csa->tcol_vec = xcalloc(1+m, sizeof(double)); csa->trow_ind = xcalloc(1+n, sizeof(int)); csa->trow_vec = xcalloc(1+n, sizeof(double)); csa->work1 = xcalloc(1+m, sizeof(double)); csa->work2 = xcalloc(1+m, sizeof(double)); csa->work3 = xcalloc(1+m, sizeof(double)); csa->work4 = xcalloc(1+m, sizeof(double)); return csa; } /*********************************************************************** * init_csa - initialize common storage area * * This routine initializes all data structures in the common storage * area (CSA). */ static void alloc_N(struct csa *csa); static void build_N(struct csa *csa); static void init_csa(struct csa *csa, glp_prob *lp) { int m = csa->m; int n = csa->n; char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; double *coef = csa->coef; double *obj = csa->obj; int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; char *stat = csa->stat; char *refsp = csa->refsp; double *gamma = csa->gamma; int i, j, k, loc; double cmax; /* auxiliary variables */ for (i = 1; i <= m; i++) { GLPROW *row = lp->row[i]; type[i] = (char)row->type; lb[i] = row->lb * row->rii; ub[i] = row->ub * row->rii; coef[i] = 0.0; } /* structural variables */ for (j = 1; j <= n; j++) { GLPCOL *col = lp->col[j]; type[m+j] = (char)col->type; lb[m+j] = col->lb / col->sjj; ub[m+j] = col->ub / col->sjj; coef[m+j] = col->coef * col->sjj; } /* original objective function */ obj[0] = lp->c0; memcpy(&obj[1], &coef[m+1], n * sizeof(double)); /* factor used to scale original objective coefficients */ cmax = 0.0; for (j = 1; j <= n; j++) if (cmax < fabs(obj[j])) cmax = fabs(obj[j]); if (cmax == 0.0) cmax = 1.0; switch (lp->dir) { case GLP_MIN: csa->zeta = + 1.0 / cmax; break; case GLP_MAX: csa->zeta = - 1.0 / cmax; break; default: xassert(lp != lp); } #if 1 if (fabs(csa->zeta) < 1.0) csa->zeta *= 1000.0; #endif /* matrix A (by columns) */ loc = 1; for (j = 1; j <= n; j++) { GLPAIJ *aij; A_ptr[j] = loc; for (aij = lp->col[j]->ptr; aij != NULL; aij = aij->c_next) { A_ind[loc] = aij->row->i; A_val[loc] = aij->row->rii * aij->val * aij->col->sjj; loc++; } } A_ptr[n+1] = loc; xassert(loc == lp->nnz+1); /* basis header */ xassert(lp->valid); memcpy(&head[1], &lp->head[1], m * sizeof(int)); k = 0; for (i = 1; i <= m; i++) { GLPROW *row = lp->row[i]; if (row->stat != GLP_BS) { k++; xassert(k <= n); head[m+k] = i; stat[k] = (char)row->stat; } } for (j = 1; j <= n; j++) { GLPCOL *col = lp->col[j]; if (col->stat != GLP_BS) { k++; xassert(k <= n); head[m+k] = m + j; stat[k] = (char)col->stat; } } xassert(k == n); /* factorization of matrix B */ csa->valid = 1, lp->valid = 0; csa->bfd = lp->bfd, lp->bfd = NULL; /* matrix N (by rows) */ alloc_N(csa); build_N(csa); /* working parameters */ csa->phase = 0; csa->tm_beg = xtime(); csa->it_beg = csa->it_cnt = lp->it_cnt; csa->it_dpy = -1; /* reference space and steepest edge coefficients */ csa->refct = 0; memset(&refsp[1], 0, (m+n) * sizeof(char)); for (j = 1; j <= n; j++) gamma[j] = 1.0; return; } /*********************************************************************** * invert_B - compute factorization of the basis matrix * * This routine computes factorization of the current basis matrix B. * * If the operation is successful, the routine returns zero, otherwise * non-zero. */ static int inv_col(void *info, int i, int ind[], double val[]) { /* this auxiliary routine returns row indices and numeric values of non-zero elements of i-th column of the basis matrix */ struct csa *csa = info; int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; int k, len, ptr, t; #ifdef GLP_DEBUG xassert(1 <= i && i <= m); #endif k = head[i]; /* B[i] is k-th column of (I|-A) */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k <= m) { /* B[i] is k-th column of submatrix I */ len = 1; ind[1] = k; val[1] = 1.0; } else { /* B[i] is (k-m)-th column of submatrix (-A) */ ptr = A_ptr[k-m]; len = A_ptr[k-m+1] - ptr; memcpy(&ind[1], &A_ind[ptr], len * sizeof(int)); memcpy(&val[1], &A_val[ptr], len * sizeof(double)); for (t = 1; t <= len; t++) val[t] = - val[t]; } return len; } static int invert_B(struct csa *csa) { int ret; ret = bfd_factorize(csa->bfd, csa->m, NULL, inv_col, csa); csa->valid = (ret == 0); return ret; } /*********************************************************************** * update_B - update factorization of the basis matrix * * This routine replaces i-th column of the basis matrix B by k-th * column of the augmented constraint matrix (I|-A) and then updates * the factorization of B. * * If the factorization has been successfully updated, the routine * returns zero, otherwise non-zero. */ static int update_B(struct csa *csa, int i, int k) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int ret; #ifdef GLP_DEBUG xassert(1 <= i && i <= m); xassert(1 <= k && k <= m+n); #endif if (k <= m) { /* new i-th column of B is k-th column of I */ int ind[1+1]; double val[1+1]; ind[1] = k; val[1] = 1.0; xassert(csa->valid); ret = bfd_update_it(csa->bfd, i, 0, 1, ind, val); } else { /* new i-th column of B is (k-m)-th column of (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; double *val = csa->work1; int beg, end, ptr, len; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; len = 0; for (ptr = beg; ptr < end; ptr++) val[++len] = - A_val[ptr]; xassert(csa->valid); ret = bfd_update_it(csa->bfd, i, 0, len, &A_ind[beg-1], val); } csa->valid = (ret == 0); return ret; } /*********************************************************************** * error_ftran - compute residual vector r = h - B * x * * This routine computes the residual vector r = h - B * x, where B is * the current basis matrix, h is the vector of right-hand sides, x is * the solution vector. */ static void error_ftran(struct csa *csa, double h[], double x[], double r[]) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; int i, k, beg, end, ptr; double temp; /* compute the residual vector: r = h - B * x = h - B[1] * x[1] - ... - B[m] * x[m], where B[1], ..., B[m] are columns of matrix B */ memcpy(&r[1], &h[1], m * sizeof(double)); for (i = 1; i <= m; i++) { temp = x[i]; if (temp == 0.0) continue; k = head[i]; /* B[i] is k-th column of (I|-A) */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k <= m) { /* B[i] is k-th column of submatrix I */ r[k] -= temp; } else { /* B[i] is (k-m)-th column of submatrix (-A) */ beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) r[A_ind[ptr]] += A_val[ptr] * temp; } } return; } /*********************************************************************** * refine_ftran - refine solution of B * x = h * * This routine performs one iteration to refine the solution of * the system B * x = h, where B is the current basis matrix, h is the * vector of right-hand sides, x is the solution vector. */ static void refine_ftran(struct csa *csa, double h[], double x[]) { int m = csa->m; double *r = csa->work1; double *d = csa->work1; int i; /* compute the residual vector r = h - B * x */ error_ftran(csa, h, x, r); /* compute the correction vector d = inv(B) * r */ xassert(csa->valid); bfd_ftran(csa->bfd, d); /* refine the solution vector (new x) = (old x) + d */ for (i = 1; i <= m; i++) x[i] += d[i]; return; } /*********************************************************************** * error_btran - compute residual vector r = h - B'* x * * This routine computes the residual vector r = h - B'* x, where B' * is a matrix transposed to the current basis matrix, h is the vector * of right-hand sides, x is the solution vector. */ static void error_btran(struct csa *csa, double h[], double x[], double r[]) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; int i, k, beg, end, ptr; double temp; /* compute the residual vector r = b - B'* x */ for (i = 1; i <= m; i++) { /* r[i] := b[i] - (i-th column of B)'* x */ k = head[i]; /* B[i] is k-th column of (I|-A) */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif temp = h[i]; if (k <= m) { /* B[i] is k-th column of submatrix I */ temp -= x[k]; } else { /* B[i] is (k-m)-th column of submatrix (-A) */ beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) temp += A_val[ptr] * x[A_ind[ptr]]; } r[i] = temp; } return; } /*********************************************************************** * refine_btran - refine solution of B'* x = h * * This routine performs one iteration to refine the solution of the * system B'* x = h, where B' is a matrix transposed to the current * basis matrix, h is the vector of right-hand sides, x is the solution * vector. */ static void refine_btran(struct csa *csa, double h[], double x[]) { int m = csa->m; double *r = csa->work1; double *d = csa->work1; int i; /* compute the residual vector r = h - B'* x */ error_btran(csa, h, x, r); /* compute the correction vector d = inv(B') * r */ xassert(csa->valid); bfd_btran(csa->bfd, d); /* refine the solution vector (new x) = (old x) + d */ for (i = 1; i <= m; i++) x[i] += d[i]; return; } /*********************************************************************** * alloc_N - allocate matrix N * * This routine determines maximal row lengths of matrix N, sets its * row pointers, and then allocates arrays N_ind and N_val. * * Note that some fixed structural variables may temporarily become * double-bounded, so corresponding columns of matrix A should not be * ignored on calculating maximal row lengths of matrix N. */ static void alloc_N(struct csa *csa) { int m = csa->m; int n = csa->n; int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; int *N_ptr = csa->N_ptr; int *N_len = csa->N_len; int i, j, beg, end, ptr; /* determine number of non-zeros in each row of the augmented constraint matrix (I|-A) */ for (i = 1; i <= m; i++) N_len[i] = 1; for (j = 1; j <= n; j++) { beg = A_ptr[j]; end = A_ptr[j+1]; for (ptr = beg; ptr < end; ptr++) N_len[A_ind[ptr]]++; } /* determine maximal row lengths of matrix N and set its row pointers */ N_ptr[1] = 1; for (i = 1; i <= m; i++) { /* row of matrix N cannot have more than n non-zeros */ if (N_len[i] > n) N_len[i] = n; N_ptr[i+1] = N_ptr[i] + N_len[i]; } /* now maximal number of non-zeros in matrix N is known */ csa->N_ind = xcalloc(N_ptr[m+1], sizeof(int)); csa->N_val = xcalloc(N_ptr[m+1], sizeof(double)); return; } /*********************************************************************** * add_N_col - add column of matrix (I|-A) to matrix N * * This routine adds j-th column to matrix N which is k-th column of * the augmented constraint matrix (I|-A). (It is assumed that old j-th * column was previously removed from matrix N.) */ static void add_N_col(struct csa *csa, int j, int k) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *N_ptr = csa->N_ptr; int *N_len = csa->N_len; int *N_ind = csa->N_ind; double *N_val = csa->N_val; int pos; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); xassert(1 <= k && k <= m+n); #endif if (k <= m) { /* N[j] is k-th column of submatrix I */ pos = N_ptr[k] + (N_len[k]++); #ifdef GLP_DEBUG xassert(pos < N_ptr[k+1]); #endif N_ind[pos] = j; N_val[pos] = 1.0; } else { /* N[j] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int i, beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) { i = A_ind[ptr]; /* row number */ pos = N_ptr[i] + (N_len[i]++); #ifdef GLP_DEBUG xassert(pos < N_ptr[i+1]); #endif N_ind[pos] = j; N_val[pos] = - A_val[ptr]; } } return; } /*********************************************************************** * del_N_col - remove column of matrix (I|-A) from matrix N * * This routine removes j-th column from matrix N which is k-th column * of the augmented constraint matrix (I|-A). */ static void del_N_col(struct csa *csa, int j, int k) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *N_ptr = csa->N_ptr; int *N_len = csa->N_len; int *N_ind = csa->N_ind; double *N_val = csa->N_val; int pos, head, tail; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); xassert(1 <= k && k <= m+n); #endif if (k <= m) { /* N[j] is k-th column of submatrix I */ /* find element in k-th row of N */ head = N_ptr[k]; for (pos = head; N_ind[pos] != j; pos++) /* nop */; /* and remove it from the row list */ tail = head + (--N_len[k]); #ifdef GLP_DEBUG xassert(pos <= tail); #endif N_ind[pos] = N_ind[tail]; N_val[pos] = N_val[tail]; } else { /* N[j] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; int i, beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) { i = A_ind[ptr]; /* row number */ /* find element in i-th row of N */ head = N_ptr[i]; for (pos = head; N_ind[pos] != j; pos++) /* nop */; /* and remove it from the row list */ tail = head + (--N_len[i]); #ifdef GLP_DEBUG xassert(pos <= tail); #endif N_ind[pos] = N_ind[tail]; N_val[pos] = N_val[tail]; } } return; } /*********************************************************************** * build_N - build matrix N for current basis * * This routine builds matrix N for the current basis from columns * of the augmented constraint matrix (I|-A) corresponding to non-basic * non-fixed variables. */ static void build_N(struct csa *csa) { int m = csa->m; int n = csa->n; int *head = csa->head; char *stat = csa->stat; int *N_len = csa->N_len; int j, k; /* N := empty matrix */ memset(&N_len[1], 0, m * sizeof(int)); /* go through non-basic columns of matrix (I|-A) */ for (j = 1; j <= n; j++) { if (stat[j] != GLP_NS) { /* xN[j] is non-fixed; add j-th column to matrix N which is k-th column of matrix (I|-A) */ k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif add_N_col(csa, j, k); } } return; } /*********************************************************************** * get_xN - determine current value of non-basic variable xN[j] * * This routine returns the current value of non-basic variable xN[j], * which is a value of its active bound. */ static double get_xN(struct csa *csa, int j) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif double *lb = csa->lb; double *ub = csa->ub; int *head = csa->head; char *stat = csa->stat; int k; double xN; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); #endif k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif switch (stat[j]) { case GLP_NL: /* x[k] is on its lower bound */ xN = lb[k]; break; case GLP_NU: /* x[k] is on its upper bound */ xN = ub[k]; break; case GLP_NF: /* x[k] is free non-basic variable */ xN = 0.0; break; case GLP_NS: /* x[k] is fixed non-basic variable */ xN = lb[k]; break; default: xassert(stat != stat); } return xN; } /*********************************************************************** * eval_beta - compute primal values of basic variables * * This routine computes current primal values of all basic variables: * * beta = - inv(B) * N * xN, * * where B is the current basis matrix, N is a matrix built of columns * of matrix (I|-A) corresponding to non-basic variables, and xN is the * vector of current values of non-basic variables. */ static void eval_beta(struct csa *csa, double beta[]) { int m = csa->m; int n = csa->n; int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; double *h = csa->work2; int i, j, k, beg, end, ptr; double xN; /* compute the right-hand side vector: h := - N * xN = - N[1] * xN[1] - ... - N[n] * xN[n], where N[1], ..., N[n] are columns of matrix N */ for (i = 1; i <= m; i++) h[i] = 0.0; for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* determine current value of xN[j] */ xN = get_xN(csa, j); if (xN == 0.0) continue; if (k <= m) { /* N[j] is k-th column of submatrix I */ h[k] -= xN; } else { /* N[j] is (k-m)-th column of submatrix (-A) */ beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) h[A_ind[ptr]] += xN * A_val[ptr]; } } /* solve system B * beta = h */ memcpy(&beta[1], &h[1], m * sizeof(double)); xassert(csa->valid); bfd_ftran(csa->bfd, beta); /* and refine the solution */ refine_ftran(csa, h, beta); return; } /*********************************************************************** * eval_pi - compute vector of simplex multipliers * * This routine computes the vector of current simplex multipliers: * * pi = inv(B') * cB, * * where B' is a matrix transposed to the current basis matrix, cB is * a subvector of objective coefficients at basic variables. */ static void eval_pi(struct csa *csa, double pi[]) { int m = csa->m; double *c = csa->coef; int *head = csa->head; double *cB = csa->work2; int i; /* construct the right-hand side vector cB */ for (i = 1; i <= m; i++) cB[i] = c[head[i]]; /* solve system B'* pi = cB */ memcpy(&pi[1], &cB[1], m * sizeof(double)); xassert(csa->valid); bfd_btran(csa->bfd, pi); /* and refine the solution */ refine_btran(csa, cB, pi); return; } /*********************************************************************** * eval_cost - compute reduced cost of non-basic variable xN[j] * * This routine computes the current reduced cost of non-basic variable * xN[j]: * * d[j] = cN[j] - N'[j] * pi, * * where cN[j] is the objective coefficient at variable xN[j], N[j] is * a column of the augmented constraint matrix (I|-A) corresponding to * xN[j], pi is the vector of simplex multipliers. */ static double eval_cost(struct csa *csa, double pi[], int j) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif double *coef = csa->coef; int *head = csa->head; int k; double dj; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); #endif k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif dj = coef[k]; if (k <= m) { /* N[j] is k-th column of submatrix I */ dj -= pi[k]; } else { /* N[j] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) dj += A_val[ptr] * pi[A_ind[ptr]]; } return dj; } /*********************************************************************** * eval_bbar - compute and store primal values of basic variables * * This routine computes primal values of all basic variables and then * stores them in the solution array. */ static void eval_bbar(struct csa *csa) { eval_beta(csa, csa->bbar); return; } /*********************************************************************** * eval_cbar - compute and store reduced costs of non-basic variables * * This routine computes reduced costs of all non-basic variables and * then stores them in the solution array. */ static void eval_cbar(struct csa *csa) { #ifdef GLP_DEBUG int m = csa->m; #endif int n = csa->n; #ifdef GLP_DEBUG int *head = csa->head; #endif double *cbar = csa->cbar; double *pi = csa->work3; int j; #ifdef GLP_DEBUG int k; #endif /* compute simplex multipliers */ eval_pi(csa, pi); /* compute and store reduced costs */ for (j = 1; j <= n; j++) { #ifdef GLP_DEBUG k = head[m+j]; /* x[k] = xN[j] */ xassert(1 <= k && k <= m+n); #endif cbar[j] = eval_cost(csa, pi, j); } return; } /*********************************************************************** * reset_refsp - reset the reference space * * This routine resets (redefines) the reference space used in the * projected steepest edge pricing algorithm. */ static void reset_refsp(struct csa *csa) { int m = csa->m; int n = csa->n; int *head = csa->head; char *refsp = csa->refsp; double *gamma = csa->gamma; int j, k; xassert(csa->refct == 0); csa->refct = 1000; memset(&refsp[1], 0, (m+n) * sizeof(char)); for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ refsp[k] = 1; gamma[j] = 1.0; } return; } /*********************************************************************** * eval_gamma - compute steepest edge coefficient * * This routine computes the steepest edge coefficient for non-basic * variable xN[j] using its direct definition: * * gamma[j] = delta[j] + sum alfa[i,j]^2, * i in R * * where delta[j] = 1, if xN[j] is in the current reference space, * and 0 otherwise; R is a set of basic variables xB[i], which are in * the current reference space; alfa[i,j] are elements of the current * simplex table. * * NOTE: The routine is intended only for debugginig purposes. */ static double eval_gamma(struct csa *csa, int j) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *head = csa->head; char *refsp = csa->refsp; double *alfa = csa->work3; double *h = csa->work3; int i, k; double gamma; #ifdef GLP_DEBUG xassert(1 <= j && j <= n); #endif k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* construct the right-hand side vector h = - N[j] */ for (i = 1; i <= m; i++) h[i] = 0.0; if (k <= m) { /* N[j] is k-th column of submatrix I */ h[k] = -1.0; } else { /* N[j] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) h[A_ind[ptr]] = A_val[ptr]; } /* solve system B * alfa = h */ xassert(csa->valid); bfd_ftran(csa->bfd, alfa); /* compute gamma */ gamma = (refsp[k] ? 1.0 : 0.0); for (i = 1; i <= m; i++) { k = head[i]; #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (refsp[k]) gamma += alfa[i] * alfa[i]; } return gamma; } /*********************************************************************** * chuzc - choose non-basic variable (column of the simplex table) * * This routine chooses non-basic variable xN[q], which has largest * weighted reduced cost: * * |d[q]| / sqrt(gamma[q]) = max |d[j]| / sqrt(gamma[j]), * j in J * * where J is a subset of eligible non-basic variables xN[j], d[j] is * reduced cost of xN[j], gamma[j] is the steepest edge coefficient. * * The working objective function is always minimized, so the sign of * d[q] determines direction, in which xN[q] has to change: * * if d[q] < 0, xN[q] has to increase; * * if d[q] > 0, xN[q] has to decrease. * * If |d[j]| <= tol_dj, where tol_dj is a specified tolerance, xN[j] * is not included in J and therefore ignored. (It is assumed that the * working objective row is appropriately scaled, i.e. max|c[k]| = 1.) * * If J is empty and no variable has been chosen, q is set to 0. */ static void chuzc(struct csa *csa, double tol_dj) { int n = csa->n; char *stat = csa->stat; double *cbar = csa->cbar; double *gamma = csa->gamma; int j, q; double dj, best, temp; /* nothing is chosen so far */ q = 0, best = 0.0; /* look through the list of non-basic variables */ for (j = 1; j <= n; j++) { dj = cbar[j]; switch (stat[j]) { case GLP_NL: /* xN[j] can increase */ if (dj >= - tol_dj) continue; break; case GLP_NU: /* xN[j] can decrease */ if (dj <= + tol_dj) continue; break; case GLP_NF: /* xN[j] can change in any direction */ if (- tol_dj <= dj && dj <= + tol_dj) continue; break; case GLP_NS: /* xN[j] cannot change at all */ continue; default: xassert(stat != stat); } /* xN[j] is eligible non-basic variable; choose one which has largest weighted reduced cost */ #ifdef GLP_DEBUG xassert(gamma[j] > 0.0); #endif temp = (dj * dj) / gamma[j]; if (best < temp) q = j, best = temp; } /* store the index of non-basic variable xN[q] chosen */ csa->q = q; return; } /*********************************************************************** * eval_tcol - compute pivot column of the simplex table * * This routine computes the pivot column of the simplex table, which * corresponds to non-basic variable xN[q] chosen. * * The pivot column is the following vector: * * tcol = T * e[q] = - inv(B) * N * e[q] = - inv(B) * N[q], * * where B is the current basis matrix, N[q] is a column of the matrix * (I|-A) corresponding to variable xN[q]. */ static void eval_tcol(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *head = csa->head; int q = csa->q; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; double *h = csa->tcol_vec; int i, k, nnz; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); #endif k = head[m+q]; /* x[k] = xN[q] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* construct the right-hand side vector h = - N[q] */ for (i = 1; i <= m; i++) h[i] = 0.0; if (k <= m) { /* N[q] is k-th column of submatrix I */ h[k] = -1.0; } else { /* N[q] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) h[A_ind[ptr]] = A_val[ptr]; } /* solve system B * tcol = h */ xassert(csa->valid); bfd_ftran(csa->bfd, tcol_vec); /* construct sparse pattern of the pivot column */ nnz = 0; for (i = 1; i <= m; i++) { if (tcol_vec[i] != 0.0) tcol_ind[++nnz] = i; } csa->tcol_nnz = nnz; return; } /*********************************************************************** * refine_tcol - refine pivot column of the simplex table * * This routine refines the pivot column of the simplex table assuming * that it was previously computed by the routine eval_tcol. */ static void refine_tcol(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif int *head = csa->head; int q = csa->q; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; double *h = csa->work3; int i, k, nnz; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); #endif k = head[m+q]; /* x[k] = xN[q] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif /* construct the right-hand side vector h = - N[q] */ for (i = 1; i <= m; i++) h[i] = 0.0; if (k <= m) { /* N[q] is k-th column of submatrix I */ h[k] = -1.0; } else { /* N[q] is (k-m)-th column of submatrix (-A) */ int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int beg, end, ptr; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) h[A_ind[ptr]] = A_val[ptr]; } /* refine solution of B * tcol = h */ refine_ftran(csa, h, tcol_vec); /* construct sparse pattern of the pivot column */ nnz = 0; for (i = 1; i <= m; i++) { if (tcol_vec[i] != 0.0) tcol_ind[++nnz] = i; } csa->tcol_nnz = nnz; return; } /*********************************************************************** * sort_tcol - sort pivot column of the simplex table * * This routine reorders the list of non-zero elements of the pivot * column to put significant elements, whose magnitude is not less than * a specified tolerance, in front of the list, and stores the number * of significant elements in tcol_num. */ static void sort_tcol(struct csa *csa, double tol_piv) { #ifdef GLP_DEBUG int m = csa->m; #endif int nnz = csa->tcol_nnz; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; int i, num, pos; double big, eps, temp; /* compute infinity (maximum) norm of the column */ big = 0.0; for (pos = 1; pos <= nnz; pos++) { #ifdef GLP_DEBUG i = tcol_ind[pos]; xassert(1 <= i && i <= m); #endif temp = fabs(tcol_vec[tcol_ind[pos]]); if (big < temp) big = temp; } csa->tcol_max = big; /* determine absolute pivot tolerance */ eps = tol_piv * (1.0 + 0.01 * big); /* move significant column components to front of the list */ for (num = 0; num < nnz; ) { i = tcol_ind[nnz]; if (fabs(tcol_vec[i]) < eps) nnz--; else { num++; tcol_ind[nnz] = tcol_ind[num]; tcol_ind[num] = i; } } csa->tcol_num = num; return; } /*********************************************************************** * chuzr - choose basic variable (row of the simplex table) * * This routine chooses basic variable xB[p], which reaches its bound * first on changing non-basic variable xN[q] in valid direction. * * The parameter rtol is a relative tolerance used to relax bounds of * basic variables. If rtol = 0, the routine implements the standard * ratio test. Otherwise, if rtol > 0, the routine implements Harris' * two-pass ratio test. In the latter case rtol should be about three * times less than a tolerance used to check primal feasibility. */ static void chuzr(struct csa *csa, double rtol) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; double *coef = csa->coef; int *head = csa->head; int phase = csa->phase; double *bbar = csa->bbar; double *cbar = csa->cbar; int q = csa->q; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; int tcol_num = csa->tcol_num; int i, i_stat, k, p, p_stat, pos; double alfa, big, delta, s, t, teta, tmax; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); #endif /* s := - sign(d[q]), where d[q] is reduced cost of xN[q] */ #ifdef GLP_DEBUG xassert(cbar[q] != 0.0); #endif s = (cbar[q] > 0.0 ? -1.0 : +1.0); /*** FIRST PASS ***/ k = head[m+q]; /* x[k] = xN[q] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (type[k] == GLP_DB) { /* xN[q] has both lower and upper bounds */ p = -1, p_stat = 0, teta = ub[k] - lb[k], big = 1.0; } else { /* xN[q] has no opposite bound */ p = 0, p_stat = 0, teta = DBL_MAX, big = 0.0; } /* walk through significant elements of the pivot column */ for (pos = 1; pos <= tcol_num; pos++) { i = tcol_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= i && i <= m); #endif k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif alfa = s * tcol_vec[i]; #ifdef GLP_DEBUG xassert(alfa != 0.0); #endif /* xB[i] = ... + alfa * xN[q] + ..., and due to s we need to consider the only case when xN[q] is increasing */ if (alfa > 0.0) { /* xB[i] is increasing */ if (phase == 1 && coef[k] < 0.0) { /* xB[i] violates its lower bound, which plays the role of an upper bound on phase I */ delta = rtol * (1.0 + kappa * fabs(lb[k])); t = ((lb[k] + delta) - bbar[i]) / alfa; i_stat = GLP_NL; } else if (phase == 1 && coef[k] > 0.0) { /* xB[i] violates its upper bound, which plays the role of an lower bound on phase I */ continue; } else if (type[k] == GLP_UP || type[k] == GLP_DB || type[k] == GLP_FX) { /* xB[i] is within its bounds and has an upper bound */ delta = rtol * (1.0 + kappa * fabs(ub[k])); t = ((ub[k] + delta) - bbar[i]) / alfa; i_stat = GLP_NU; } else { /* xB[i] is within its bounds and has no upper bound */ continue; } } else { /* xB[i] is decreasing */ if (phase == 1 && coef[k] > 0.0) { /* xB[i] violates its upper bound, which plays the role of an lower bound on phase I */ delta = rtol * (1.0 + kappa * fabs(ub[k])); t = ((ub[k] - delta) - bbar[i]) / alfa; i_stat = GLP_NU; } else if (phase == 1 && coef[k] < 0.0) { /* xB[i] violates its lower bound, which plays the role of an upper bound on phase I */ continue; } else if (type[k] == GLP_LO || type[k] == GLP_DB || type[k] == GLP_FX) { /* xB[i] is within its bounds and has an lower bound */ delta = rtol * (1.0 + kappa * fabs(lb[k])); t = ((lb[k] - delta) - bbar[i]) / alfa; i_stat = GLP_NL; } else { /* xB[i] is within its bounds and has no lower bound */ continue; } } /* t is a change of xN[q], on which xB[i] reaches its bound (possibly relaxed); since the basic solution is assumed to be primal feasible (or pseudo feasible on phase I), t has to be non-negative by definition; however, it may happen that xB[i] slightly (i.e. within a tolerance) violates its bound, that leads to negative t; in the latter case, if xB[i] is chosen, negative t means that xN[q] changes in wrong direction; if pivot alfa[i,q] is close to zero, even small bound violation of xB[i] may lead to a large change of xN[q] in wrong direction; let, for example, xB[i] >= 0 and in the current basis its value be -5e-9; let also xN[q] be on its zero bound and should increase; from the ratio test rule it follows that the pivot alfa[i,q] < 0; however, if alfa[i,q] is, say, -1e-9, the change of xN[q] in wrong direction is 5e-9 / (-1e-9) = -5, and using it for updating values of other basic variables will give absolutely wrong results; therefore, if t is negative, we should replace it by exact zero assuming that xB[i] is exactly on its bound, and the violation appears due to round-off errors */ if (t < 0.0) t = 0.0; /* apply minimal ratio test */ if (teta > t || teta == t && big < fabs(alfa)) p = i, p_stat = i_stat, teta = t, big = fabs(alfa); } /* the second pass is skipped in the following cases: */ /* if the standard ratio test is used */ if (rtol == 0.0) goto done; /* if xN[q] reaches its opposite bound or if no basic variable has been chosen on the first pass */ if (p <= 0) goto done; /* if xB[p] is a blocking variable, i.e. if it prevents xN[q] from any change */ if (teta == 0.0) goto done; /*** SECOND PASS ***/ /* here tmax is a maximal change of xN[q], on which the solution remains primal feasible (or pseudo feasible on phase I) within a tolerance */ #if 0 tmax = (1.0 + 10.0 * DBL_EPSILON) * teta; #else tmax = teta; #endif /* nothing is chosen so far */ p = 0, p_stat = 0, teta = DBL_MAX, big = 0.0; /* walk through significant elements of the pivot column */ for (pos = 1; pos <= tcol_num; pos++) { i = tcol_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= i && i <= m); #endif k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif alfa = s * tcol_vec[i]; #ifdef GLP_DEBUG xassert(alfa != 0.0); #endif /* xB[i] = ... + alfa * xN[q] + ..., and due to s we need to consider the only case when xN[q] is increasing */ if (alfa > 0.0) { /* xB[i] is increasing */ if (phase == 1 && coef[k] < 0.0) { /* xB[i] violates its lower bound, which plays the role of an upper bound on phase I */ t = (lb[k] - bbar[i]) / alfa; i_stat = GLP_NL; } else if (phase == 1 && coef[k] > 0.0) { /* xB[i] violates its upper bound, which plays the role of an lower bound on phase I */ continue; } else if (type[k] == GLP_UP || type[k] == GLP_DB || type[k] == GLP_FX) { /* xB[i] is within its bounds and has an upper bound */ t = (ub[k] - bbar[i]) / alfa; i_stat = GLP_NU; } else { /* xB[i] is within its bounds and has no upper bound */ continue; } } else { /* xB[i] is decreasing */ if (phase == 1 && coef[k] > 0.0) { /* xB[i] violates its upper bound, which plays the role of an lower bound on phase I */ t = (ub[k] - bbar[i]) / alfa; i_stat = GLP_NU; } else if (phase == 1 && coef[k] < 0.0) { /* xB[i] violates its lower bound, which plays the role of an upper bound on phase I */ continue; } else if (type[k] == GLP_LO || type[k] == GLP_DB || type[k] == GLP_FX) { /* xB[i] is within its bounds and has an lower bound */ t = (lb[k] - bbar[i]) / alfa; i_stat = GLP_NL; } else { /* xB[i] is within its bounds and has no lower bound */ continue; } } /* (see comments for the first pass) */ if (t < 0.0) t = 0.0; /* t is a change of xN[q], on which xB[i] reaches its bound; if t <= tmax, all basic variables can violate their bounds only within relaxation tolerance delta; we can use this freedom and choose basic variable having largest influence coefficient to avoid possible numeric instability */ if (t <= tmax && big < fabs(alfa)) p = i, p_stat = i_stat, teta = t, big = fabs(alfa); } /* something must be chosen on the second pass */ xassert(p != 0); done: /* store the index and status of basic variable xB[p] chosen */ csa->p = p; if (p > 0 && type[head[p]] == GLP_FX) csa->p_stat = GLP_NS; else csa->p_stat = p_stat; /* store corresponding change of non-basic variable xN[q] */ #ifdef GLP_DEBUG xassert(teta >= 0.0); #endif csa->teta = s * teta; return; } /*********************************************************************** * eval_rho - compute pivot row of the inverse * * This routine computes the pivot (p-th) row of the inverse inv(B), * which corresponds to basic variable xB[p] chosen: * * rho = inv(B') * e[p], * * where B' is a matrix transposed to the current basis matrix, e[p] * is unity vector. */ static void eval_rho(struct csa *csa, double rho[]) { int m = csa->m; int p = csa->p; double *e = rho; int i; #ifdef GLP_DEBUG xassert(1 <= p && p <= m); #endif /* construct the right-hand side vector e[p] */ for (i = 1; i <= m; i++) e[i] = 0.0; e[p] = 1.0; /* solve system B'* rho = e[p] */ xassert(csa->valid); bfd_btran(csa->bfd, rho); return; } /*********************************************************************** * refine_rho - refine pivot row of the inverse * * This routine refines the pivot row of the inverse inv(B) assuming * that it was previously computed by the routine eval_rho. */ static void refine_rho(struct csa *csa, double rho[]) { int m = csa->m; int p = csa->p; double *e = csa->work3; int i; #ifdef GLP_DEBUG xassert(1 <= p && p <= m); #endif /* construct the right-hand side vector e[p] */ for (i = 1; i <= m; i++) e[i] = 0.0; e[p] = 1.0; /* refine solution of B'* rho = e[p] */ refine_btran(csa, e, rho); return; } /*********************************************************************** * eval_trow - compute pivot row of the simplex table * * This routine computes the pivot row of the simplex table, which * corresponds to basic variable xB[p] chosen. * * The pivot row is the following vector: * * trow = T'* e[p] = - N'* inv(B') * e[p] = - N' * rho, * * where rho is the pivot row of the inverse inv(B) previously computed * by the routine eval_rho. * * Note that elements of the pivot row corresponding to fixed non-basic * variables are not computed. */ static void eval_trow(struct csa *csa, double rho[]) { int m = csa->m; int n = csa->n; #ifdef GLP_DEBUG char *stat = csa->stat; #endif int *N_ptr = csa->N_ptr; int *N_len = csa->N_len; int *N_ind = csa->N_ind; double *N_val = csa->N_val; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; int i, j, beg, end, ptr, nnz; double temp; /* clear the pivot row */ for (j = 1; j <= n; j++) trow_vec[j] = 0.0; /* compute the pivot row as a linear combination of rows of the matrix N: trow = - rho[1] * N'[1] - ... - rho[m] * N'[m] */ for (i = 1; i <= m; i++) { temp = rho[i]; if (temp == 0.0) continue; /* trow := trow - rho[i] * N'[i] */ beg = N_ptr[i]; end = beg + N_len[i]; for (ptr = beg; ptr < end; ptr++) { #ifdef GLP_DEBUG j = N_ind[ptr]; xassert(1 <= j && j <= n); xassert(stat[j] != GLP_NS); #endif trow_vec[N_ind[ptr]] -= temp * N_val[ptr]; } } /* construct sparse pattern of the pivot row */ nnz = 0; for (j = 1; j <= n; j++) { if (trow_vec[j] != 0.0) trow_ind[++nnz] = j; } csa->trow_nnz = nnz; return; } /*********************************************************************** * update_bbar - update values of basic variables * * This routine updates values of all basic variables for the adjacent * basis. */ static void update_bbar(struct csa *csa) { #ifdef GLP_DEBUG int m = csa->m; int n = csa->n; #endif double *bbar = csa->bbar; int q = csa->q; int tcol_nnz = csa->tcol_nnz; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; int p = csa->p; double teta = csa->teta; int i, pos; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); xassert(p < 0 || 1 <= p && p <= m); #endif /* if xN[q] leaves the basis, compute its value in the adjacent basis, where it will replace xB[p] */ if (p > 0) bbar[p] = get_xN(csa, q) + teta; /* update values of other basic variables (except xB[p], because it will be replaced by xN[q]) */ if (teta == 0.0) goto done; for (pos = 1; pos <= tcol_nnz; pos++) { i = tcol_ind[pos]; /* skip xB[p] */ if (i == p) continue; /* (change of xB[i]) = alfa[i,q] * (change of xN[q]) */ bbar[i] += tcol_vec[i] * teta; } done: return; } /*********************************************************************** * reeval_cost - recompute reduced cost of non-basic variable xN[q] * * This routine recomputes reduced cost of non-basic variable xN[q] for * the current basis more accurately using its direct definition: * * d[q] = cN[q] - N'[q] * pi = * * = cN[q] - N'[q] * (inv(B') * cB) = * * = cN[q] - (cB' * inv(B) * N[q]) = * * = cN[q] + cB' * (pivot column). * * It is assumed that the pivot column of the simplex table is already * computed. */ static double reeval_cost(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif double *coef = csa->coef; int *head = csa->head; int q = csa->q; int tcol_nnz = csa->tcol_nnz; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; int i, pos; double dq; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); #endif dq = coef[head[m+q]]; for (pos = 1; pos <= tcol_nnz; pos++) { i = tcol_ind[pos]; #ifdef GLP_DEBUG xassert(1 <= i && i <= m); #endif dq += coef[head[i]] * tcol_vec[i]; } return dq; } /*********************************************************************** * update_cbar - update reduced costs of non-basic variables * * This routine updates reduced costs of all (except fixed) non-basic * variables for the adjacent basis. */ static void update_cbar(struct csa *csa) { #ifdef GLP_DEBUG int n = csa->n; #endif double *cbar = csa->cbar; int q = csa->q; int trow_nnz = csa->trow_nnz; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; int j, pos; double new_dq; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); #endif /* compute reduced cost of xB[p] in the adjacent basis, where it will replace xN[q] */ #ifdef GLP_DEBUG xassert(trow_vec[q] != 0.0); #endif new_dq = (cbar[q] /= trow_vec[q]); /* update reduced costs of other non-basic variables (except xN[q], because it will be replaced by xB[p]) */ for (pos = 1; pos <= trow_nnz; pos++) { j = trow_ind[pos]; /* skip xN[q] */ if (j == q) continue; cbar[j] -= trow_vec[j] * new_dq; } return; } /*********************************************************************** * update_gamma - update steepest edge coefficients * * This routine updates steepest-edge coefficients for the adjacent * basis. */ static void update_gamma(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif char *type = csa->type; int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int *head = csa->head; char *refsp = csa->refsp; double *gamma = csa->gamma; int q = csa->q; int tcol_nnz = csa->tcol_nnz; int *tcol_ind = csa->tcol_ind; double *tcol_vec = csa->tcol_vec; int p = csa->p; int trow_nnz = csa->trow_nnz; int *trow_ind = csa->trow_ind; double *trow_vec = csa->trow_vec; double *u = csa->work3; int i, j, k, pos, beg, end, ptr; double gamma_q, delta_q, pivot, s, t, t1, t2; #ifdef GLP_DEBUG xassert(1 <= p && p <= m); xassert(1 <= q && q <= n); #endif /* the basis changes, so decrease the count */ xassert(csa->refct > 0); csa->refct--; /* recompute gamma[q] for the current basis more accurately and compute auxiliary vector u */ gamma_q = delta_q = (refsp[head[m+q]] ? 1.0 : 0.0); for (i = 1; i <= m; i++) u[i] = 0.0; for (pos = 1; pos <= tcol_nnz; pos++) { i = tcol_ind[pos]; if (refsp[head[i]]) { u[i] = t = tcol_vec[i]; gamma_q += t * t; } else u[i] = 0.0; } xassert(csa->valid); bfd_btran(csa->bfd, u); /* update gamma[k] for other non-basic variables (except fixed variables and xN[q], because it will be replaced by xB[p]) */ pivot = trow_vec[q]; #ifdef GLP_DEBUG xassert(pivot != 0.0); #endif for (pos = 1; pos <= trow_nnz; pos++) { j = trow_ind[pos]; /* skip xN[q] */ if (j == q) continue; /* compute t */ t = trow_vec[j] / pivot; /* compute inner product s = N'[j] * u */ k = head[m+j]; /* x[k] = xN[j] */ if (k <= m) s = u[k]; else { s = 0.0; beg = A_ptr[k-m]; end = A_ptr[k-m+1]; for (ptr = beg; ptr < end; ptr++) s -= A_val[ptr] * u[A_ind[ptr]]; } /* compute gamma[k] for the adjacent basis */ t1 = gamma[j] + t * t * gamma_q + 2.0 * t * s; t2 = (refsp[k] ? 1.0 : 0.0) + delta_q * t * t; gamma[j] = (t1 >= t2 ? t1 : t2); if (gamma[j] < DBL_EPSILON) gamma[j] = DBL_EPSILON; } /* compute gamma[q] for the adjacent basis */ if (type[head[p]] == GLP_FX) gamma[q] = 1.0; else { gamma[q] = gamma_q / (pivot * pivot); if (gamma[q] < DBL_EPSILON) gamma[q] = DBL_EPSILON; } return; } /*********************************************************************** * err_in_bbar - compute maximal relative error in primal solution * * This routine returns maximal relative error: * * max |beta[i] - bbar[i]| / (1 + |beta[i]|), * * where beta and bbar are, respectively, directly computed and the * current (updated) values of basic variables. * * NOTE: The routine is intended only for debugginig purposes. */ static double err_in_bbar(struct csa *csa) { int m = csa->m; double *bbar = csa->bbar; int i; double e, emax, *beta; beta = xcalloc(1+m, sizeof(double)); eval_beta(csa, beta); emax = 0.0; for (i = 1; i <= m; i++) { e = fabs(beta[i] - bbar[i]) / (1.0 + fabs(beta[i])); if (emax < e) emax = e; } xfree(beta); return emax; } /*********************************************************************** * err_in_cbar - compute maximal relative error in dual solution * * This routine returns maximal relative error: * * max |cost[j] - cbar[j]| / (1 + |cost[j]|), * * where cost and cbar are, respectively, directly computed and the * current (updated) reduced costs of non-basic non-fixed variables. * * NOTE: The routine is intended only for debugginig purposes. */ static double err_in_cbar(struct csa *csa) { int m = csa->m; int n = csa->n; char *stat = csa->stat; double *cbar = csa->cbar; int j; double e, emax, cost, *pi; pi = xcalloc(1+m, sizeof(double)); eval_pi(csa, pi); emax = 0.0; for (j = 1; j <= n; j++) { if (stat[j] == GLP_NS) continue; cost = eval_cost(csa, pi, j); e = fabs(cost - cbar[j]) / (1.0 + fabs(cost)); if (emax < e) emax = e; } xfree(pi); return emax; } /*********************************************************************** * err_in_gamma - compute maximal relative error in steepest edge cff. * * This routine returns maximal relative error: * * max |gamma'[j] - gamma[j]| / (1 + |gamma'[j]), * * where gamma'[j] and gamma[j] are, respectively, directly computed * and the current (updated) steepest edge coefficients for non-basic * non-fixed variable x[j]. * * NOTE: The routine is intended only for debugginig purposes. */ static double err_in_gamma(struct csa *csa) { int n = csa->n; char *stat = csa->stat; double *gamma = csa->gamma; int j; double e, emax, temp; emax = 0.0; for (j = 1; j <= n; j++) { if (stat[j] == GLP_NS) { xassert(gamma[j] == 1.0); continue; } temp = eval_gamma(csa, j); e = fabs(temp - gamma[j]) / (1.0 + fabs(temp)); if (emax < e) emax = e; } return emax; } /*********************************************************************** * change_basis - change basis header * * This routine changes the basis header to make it corresponding to * the adjacent basis. */ static void change_basis(struct csa *csa) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; char *type = csa->type; #endif int *head = csa->head; char *stat = csa->stat; int q = csa->q; int p = csa->p; int p_stat = csa->p_stat; int k; #ifdef GLP_DEBUG xassert(1 <= q && q <= n); #endif if (p < 0) { /* xN[q] goes to its opposite bound */ #ifdef GLP_DEBUG k = head[m+q]; /* x[k] = xN[q] */ xassert(1 <= k && k <= m+n); xassert(type[k] == GLP_DB); #endif switch (stat[q]) { case GLP_NL: /* xN[q] increases */ stat[q] = GLP_NU; break; case GLP_NU: /* xN[q] decreases */ stat[q] = GLP_NL; break; default: xassert(stat != stat); } } else { /* xB[p] leaves the basis, xN[q] enters the basis */ #ifdef GLP_DEBUG xassert(1 <= p && p <= m); k = head[p]; /* x[k] = xB[p] */ switch (p_stat) { case GLP_NL: /* xB[p] goes to its lower bound */ xassert(type[k] == GLP_LO || type[k] == GLP_DB); break; case GLP_NU: /* xB[p] goes to its upper bound */ xassert(type[k] == GLP_UP || type[k] == GLP_DB); break; case GLP_NS: /* xB[p] goes to its fixed value */ xassert(type[k] == GLP_NS); break; default: xassert(p_stat != p_stat); } #endif /* xB[p] <-> xN[q] */ k = head[p], head[p] = head[m+q], head[m+q] = k; stat[q] = (char)p_stat; } return; } /*********************************************************************** * set_aux_obj - construct auxiliary objective function * * The auxiliary objective function is a separable piecewise linear * convex function, which is the sum of primal infeasibilities: * * z = t[1] + ... + t[m+n] -> minimize, * * where: * * / lb[k] - x[k], if x[k] < lb[k] * | * t[k] = < 0, if lb[k] <= x[k] <= ub[k] * | * \ x[k] - ub[k], if x[k] > ub[k] * * This routine computes objective coefficients for the current basis * and returns the number of non-zero terms t[k]. */ static int set_aux_obj(struct csa *csa, double tol_bnd) { int m = csa->m; int n = csa->n; char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; double *coef = csa->coef; int *head = csa->head; double *bbar = csa->bbar; int i, k, cnt = 0; double eps; /* use a bit more restrictive tolerance */ tol_bnd *= 0.90; /* clear all objective coefficients */ for (k = 1; k <= m+n; k++) coef[k] = 0.0; /* walk through the list of basic variables */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ if (type[k] == GLP_LO || type[k] == GLP_DB || type[k] == GLP_FX) { /* x[k] has lower bound */ eps = tol_bnd * (1.0 + kappa * fabs(lb[k])); if (bbar[i] < lb[k] - eps) { /* and violates it */ coef[k] = -1.0; cnt++; } } if (type[k] == GLP_UP || type[k] == GLP_DB || type[k] == GLP_FX) { /* x[k] has upper bound */ eps = tol_bnd * (1.0 + kappa * fabs(ub[k])); if (bbar[i] > ub[k] + eps) { /* and violates it */ coef[k] = +1.0; cnt++; } } } return cnt; } /*********************************************************************** * set_orig_obj - restore original objective function * * This routine assigns scaled original objective coefficients to the * working objective function. */ static void set_orig_obj(struct csa *csa) { int m = csa->m; int n = csa->n; double *coef = csa->coef; double *obj = csa->obj; double zeta = csa->zeta; int i, j; for (i = 1; i <= m; i++) coef[i] = 0.0; for (j = 1; j <= n; j++) coef[m+j] = zeta * obj[j]; return; } /*********************************************************************** * check_stab - check numerical stability of basic solution * * If the current basic solution is primal feasible (or pseudo feasible * on phase I) within a tolerance, this routine returns zero, otherwise * it returns non-zero. */ static int check_stab(struct csa *csa, double tol_bnd) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; double *coef = csa->coef; int *head = csa->head; int phase = csa->phase; double *bbar = csa->bbar; int i, k; double eps; /* walk through the list of basic variables */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (phase == 1 && coef[k] < 0.0) { /* x[k] must not be greater than its lower bound */ #ifdef GLP_DEBUG xassert(type[k] == GLP_LO || type[k] == GLP_DB || type[k] == GLP_FX); #endif eps = tol_bnd * (1.0 + kappa * fabs(lb[k])); if (bbar[i] > lb[k] + eps) return 1; } else if (phase == 1 && coef[k] > 0.0) { /* x[k] must not be less than its upper bound */ #ifdef GLP_DEBUG xassert(type[k] == GLP_UP || type[k] == GLP_DB || type[k] == GLP_FX); #endif eps = tol_bnd * (1.0 + kappa * fabs(ub[k])); if (bbar[i] < ub[k] - eps) return 1; } else { /* either phase = 1 and coef[k] = 0, or phase = 2 */ if (type[k] == GLP_LO || type[k] == GLP_DB || type[k] == GLP_FX) { /* x[k] must not be less than its lower bound */ eps = tol_bnd * (1.0 + kappa * fabs(lb[k])); if (bbar[i] < lb[k] - eps) return 1; } if (type[k] == GLP_UP || type[k] == GLP_DB || type[k] == GLP_FX) { /* x[k] must not be greater then its upper bound */ eps = tol_bnd * (1.0 + kappa * fabs(ub[k])); if (bbar[i] > ub[k] + eps) return 1; } } } /* basic solution is primal feasible within a tolerance */ return 0; } /*********************************************************************** * check_feas - check primal feasibility of basic solution * * If the current basic solution is primal feasible within a tolerance, * this routine returns zero, otherwise it returns non-zero. */ static int check_feas(struct csa *csa, double tol_bnd) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; char *type = csa->type; #endif double *lb = csa->lb; double *ub = csa->ub; double *coef = csa->coef; int *head = csa->head; double *bbar = csa->bbar; int i, k; double eps; xassert(csa->phase == 1); /* walk through the list of basic variables */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (coef[k] < 0.0) { /* check if x[k] still violates its lower bound */ #ifdef GLP_DEBUG xassert(type[k] == GLP_LO || type[k] == GLP_DB || type[k] == GLP_FX); #endif eps = tol_bnd * (1.0 + kappa * fabs(lb[k])); if (bbar[i] < lb[k] - eps) return 1; } else if (coef[k] > 0.0) { /* check if x[k] still violates its upper bound */ #ifdef GLP_DEBUG xassert(type[k] == GLP_UP || type[k] == GLP_DB || type[k] == GLP_FX); #endif eps = tol_bnd * (1.0 + kappa * fabs(ub[k])); if (bbar[i] > ub[k] + eps) return 1; } } /* basic solution is primal feasible within a tolerance */ return 0; } /*********************************************************************** * eval_obj - compute original objective function * * This routine computes the current value of the original objective * function. */ static double eval_obj(struct csa *csa) { int m = csa->m; int n = csa->n; double *obj = csa->obj; int *head = csa->head; double *bbar = csa->bbar; int i, j, k; double sum; sum = obj[0]; /* walk through the list of basic variables */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k > m) sum += obj[k-m] * bbar[i]; } /* walk through the list of non-basic variables */ for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k > m) sum += obj[k-m] * get_xN(csa, j); } return sum; } /*********************************************************************** * display - display the search progress * * This routine displays some information about the search progress * that includes: * * the search phase; * * the number of simplex iterations performed by the solver; * * the original objective value; * * the sum of (scaled) primal infeasibilities; * * the number of basic fixed variables. */ static void display(struct csa *csa, const glp_smcp *parm, int spec) { int m = csa->m; #ifdef GLP_DEBUG int n = csa->n; #endif char *type = csa->type; double *lb = csa->lb; double *ub = csa->ub; int phase = csa->phase; int *head = csa->head; double *bbar = csa->bbar; int i, k, cnt; double sum; if (parm->msg_lev < GLP_MSG_ON) goto skip; if (parm->out_dly > 0 && 1000.0 * xdifftime(xtime(), csa->tm_beg) < parm->out_dly) goto skip; if (csa->it_cnt == csa->it_dpy) goto skip; if (!spec && csa->it_cnt % parm->out_frq != 0) goto skip; /* compute the sum of primal infeasibilities and determine the number of basic fixed variables */ sum = 0.0, cnt = 0; for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (type[k] == GLP_LO || type[k] == GLP_DB || type[k] == GLP_FX) { /* x[k] has lower bound */ if (bbar[i] < lb[k]) sum += (lb[k] - bbar[i]); } if (type[k] == GLP_UP || type[k] == GLP_DB || type[k] == GLP_FX) { /* x[k] has upper bound */ if (bbar[i] > ub[k]) sum += (bbar[i] - ub[k]); } if (type[k] == GLP_FX) cnt++; } xprintf("%c%6d: obj = %17.9e infeas = %10.3e (%d)\n", phase == 1 ? ' ' : '*', csa->it_cnt, eval_obj(csa), sum, cnt); csa->it_dpy = csa->it_cnt; skip: return; } /*********************************************************************** * store_sol - store basic solution back to the problem object * * This routine stores basic solution components back to the problem * object. */ static void store_sol(struct csa *csa, glp_prob *lp, int p_stat, int d_stat, int ray) { int m = csa->m; int n = csa->n; double zeta = csa->zeta; int *head = csa->head; char *stat = csa->stat; double *bbar = csa->bbar; double *cbar = csa->cbar; int i, j, k; #ifdef GLP_DEBUG xassert(lp->m == m); xassert(lp->n == n); #endif /* basis factorization */ #ifdef GLP_DEBUG xassert(!lp->valid && lp->bfd == NULL); xassert(csa->valid && csa->bfd != NULL); #endif lp->valid = 1, csa->valid = 0; lp->bfd = csa->bfd, csa->bfd = NULL; memcpy(&lp->head[1], &head[1], m * sizeof(int)); /* basic solution status */ lp->pbs_stat = p_stat; lp->dbs_stat = d_stat; /* objective function value */ lp->obj_val = eval_obj(csa); /* simplex iteration count */ lp->it_cnt = csa->it_cnt; /* unbounded ray */ lp->some = ray; /* basic variables */ for (i = 1; i <= m; i++) { k = head[i]; /* x[k] = xB[i] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k <= m) { GLPROW *row = lp->row[k]; row->stat = GLP_BS; row->bind = i; row->prim = bbar[i] / row->rii; row->dual = 0.0; } else { GLPCOL *col = lp->col[k-m]; col->stat = GLP_BS; col->bind = i; col->prim = bbar[i] * col->sjj; col->dual = 0.0; } } /* non-basic variables */ for (j = 1; j <= n; j++) { k = head[m+j]; /* x[k] = xN[j] */ #ifdef GLP_DEBUG xassert(1 <= k && k <= m+n); #endif if (k <= m) { GLPROW *row = lp->row[k]; row->stat = stat[j]; row->bind = 0; #if 0 row->prim = get_xN(csa, j) / row->rii; #else switch (stat[j]) { case GLP_NL: row->prim = row->lb; break; case GLP_NU: row->prim = row->ub; break; case GLP_NF: row->prim = 0.0; break; case GLP_NS: row->prim = row->lb; break; default: xassert(stat != stat); } #endif row->dual = (cbar[j] * row->rii) / zeta; } else { GLPCOL *col = lp->col[k-m]; col->stat = stat[j]; col->bind = 0; #if 0 col->prim = get_xN(csa, j) * col->sjj; #else switch (stat[j]) { case GLP_NL: col->prim = col->lb; break; case GLP_NU: col->prim = col->ub; break; case GLP_NF: col->prim = 0.0; break; case GLP_NS: col->prim = col->lb; break; default: xassert(stat != stat); } #endif col->dual = (cbar[j] / col->sjj) / zeta; } } return; } /*********************************************************************** * free_csa - deallocate common storage area * * This routine frees all the memory allocated to arrays in the common * storage area (CSA). */ static void free_csa(struct csa *csa) { xfree(csa->type); xfree(csa->lb); xfree(csa->ub); xfree(csa->coef); xfree(csa->obj); xfree(csa->A_ptr); xfree(csa->A_ind); xfree(csa->A_val); xfree(csa->head); xfree(csa->stat); xfree(csa->N_ptr); xfree(csa->N_len); xfree(csa->N_ind); xfree(csa->N_val); xfree(csa->bbar); xfree(csa->cbar); xfree(csa->refsp); xfree(csa->gamma); xfree(csa->tcol_ind); xfree(csa->tcol_vec); xfree(csa->trow_ind); xfree(csa->trow_vec); xfree(csa->work1); xfree(csa->work2); xfree(csa->work3); xfree(csa->work4); xfree(csa); return; } /*********************************************************************** * spx_primal - core LP solver based on the primal simplex method * * SYNOPSIS * * #include "glpspx.h" * int spx_primal(glp_prob *lp, const glp_smcp *parm); * * DESCRIPTION * * The routine spx_primal is a core LP solver based on the two-phase * primal simplex method. * * RETURNS * * 0 LP instance has been successfully solved. * * GLP_EITLIM * Iteration limit has been exhausted. * * GLP_ETMLIM * Time limit has been exhausted. * * GLP_EFAIL * The solver failed to solve LP instance. */ int spx_primal(glp_prob *lp, const glp_smcp *parm) { struct csa *csa; int binv_st = 2; /* status of basis matrix factorization: 0 - invalid; 1 - just computed; 2 - updated */ int bbar_st = 0; /* status of primal values of basic variables: 0 - invalid; 1 - just computed; 2 - updated */ int cbar_st = 0; /* status of reduced costs of non-basic variables: 0 - invalid; 1 - just computed; 2 - updated */ int rigorous = 0; /* rigorous mode flag; this flag is used to enable iterative refinement on computing pivot rows and columns of the simplex table */ int check = 0; int p_stat, d_stat, ret; /* allocate and initialize the common storage area */ csa = alloc_csa(lp); init_csa(csa, lp); if (parm->msg_lev >= GLP_MSG_DBG) xprintf("Objective scale factor = %g\n", csa->zeta); loop: /* main loop starts here */ /* compute factorization of the basis matrix */ if (binv_st == 0) { ret = invert_B(csa); if (ret != 0) { if (parm->msg_lev >= GLP_MSG_ERR) { xprintf("Error: unable to factorize the basis matrix (%d" ")\n", ret); xprintf("Sorry, basis recovery procedure not implemented" " yet\n"); } xassert(!lp->valid && lp->bfd == NULL); lp->bfd = csa->bfd, csa->bfd = NULL; lp->pbs_stat = lp->dbs_stat = GLP_UNDEF; lp->obj_val = 0.0; lp->it_cnt = csa->it_cnt; lp->some = 0; ret = GLP_EFAIL; goto done; } csa->valid = 1; binv_st = 1; /* just computed */ /* invalidate basic solution components */ bbar_st = cbar_st = 0; } /* compute primal values of basic variables */ if (bbar_st == 0) { eval_bbar(csa); bbar_st = 1; /* just computed */ /* determine the search phase, if not determined yet */ if (csa->phase == 0) { if (set_aux_obj(csa, parm->tol_bnd) > 0) { /* current basic solution is primal infeasible */ /* start to minimize the sum of infeasibilities */ csa->phase = 1; } else { /* current basic solution is primal feasible */ /* start to minimize the original objective function */ set_orig_obj(csa); csa->phase = 2; } xassert(check_stab(csa, parm->tol_bnd) == 0); /* working objective coefficients have been changed, so invalidate reduced costs */ cbar_st = 0; display(csa, parm, 1); } /* make sure that the current basic solution remains primal feasible (or pseudo feasible on phase I) */ if (check_stab(csa, parm->tol_bnd)) { /* there are excessive bound violations due to round-off errors */ if (parm->msg_lev >= GLP_MSG_ERR) xprintf("Warning: numerical instability (primal simplex," " phase %s)\n", csa->phase == 1 ? "I" : "II"); /* restart the search */ csa->phase = 0; binv_st = 0; rigorous = 5; goto loop; } } xassert(csa->phase == 1 || csa->phase == 2); /* on phase I we do not need to wait until the current basic solution becomes dual feasible; it is sufficient to make sure that no basic variable violates its bounds */ if (csa->phase == 1 && !check_feas(csa, parm->tol_bnd)) { /* the current basis is primal feasible; switch to phase II */ csa->phase = 2; set_orig_obj(csa); cbar_st = 0; display(csa, parm, 1); } /* compute reduced costs of non-basic variables */ if (cbar_st == 0) { eval_cbar(csa); cbar_st = 1; /* just computed */ } /* redefine the reference space, if required */ switch (parm->pricing) { case GLP_PT_STD: break; case GLP_PT_PSE: if (csa->refct == 0) reset_refsp(csa); break; default: xassert(parm != parm); } /* at this point the basis factorization and all basic solution components are valid */ xassert(binv_st && bbar_st && cbar_st); /* check accuracy of current basic solution components (only for debugging) */ if (check) { double e_bbar = err_in_bbar(csa); double e_cbar = err_in_cbar(csa); double e_gamma = (parm->pricing == GLP_PT_PSE ? err_in_gamma(csa) : 0.0); xprintf("e_bbar = %10.3e; e_cbar = %10.3e; e_gamma = %10.3e\n", e_bbar, e_cbar, e_gamma); xassert(e_bbar <= 1e-5 && e_cbar <= 1e-5 && e_gamma <= 1e-3); } /* check if the iteration limit has been exhausted */ if (parm->it_lim < INT_MAX && csa->it_cnt - csa->it_beg >= parm->it_lim) { if (bbar_st != 1 || csa->phase == 2 && cbar_st != 1) { if (bbar_st != 1) bbar_st = 0; if (csa->phase == 2 && cbar_st != 1) cbar_st = 0; goto loop; } display(csa, parm, 1); if (parm->msg_lev >= GLP_MSG_ALL) xprintf("ITERATION LIMIT EXCEEDED; SEARCH TERMINATED\n"); switch (csa->phase) { case 1: p_stat = GLP_INFEAS; set_orig_obj(csa); eval_cbar(csa); break; case 2: p_stat = GLP_FEAS; break; default: xassert(csa != csa); } chuzc(csa, parm->tol_dj); d_stat = (csa->q == 0 ? GLP_FEAS : GLP_INFEAS); store_sol(csa, lp, p_stat, d_stat, 0); ret = GLP_EITLIM; goto done; } /* check if the time limit has been exhausted */ if (parm->tm_lim < INT_MAX && 1000.0 * xdifftime(xtime(), csa->tm_beg) >= parm->tm_lim) { if (bbar_st != 1 || csa->phase == 2 && cbar_st != 1) { if (bbar_st != 1) bbar_st = 0; if (csa->phase == 2 && cbar_st != 1) cbar_st = 0; goto loop; } display(csa, parm, 1); if (parm->msg_lev >= GLP_MSG_ALL) xprintf("TIME LIMIT EXCEEDED; SEARCH TERMINATED\n"); switch (csa->phase) { case 1: p_stat = GLP_INFEAS; set_orig_obj(csa); eval_cbar(csa); break; case 2: p_stat = GLP_FEAS; break; default: xassert(csa != csa); } chuzc(csa, parm->tol_dj); d_stat = (csa->q == 0 ? GLP_FEAS : GLP_INFEAS); store_sol(csa, lp, p_stat, d_stat, 0); ret = GLP_ETMLIM; goto done; } /* display the search progress */ display(csa, parm, 0); /* choose non-basic variable xN[q] */ chuzc(csa, parm->tol_dj); if (csa->q == 0) { if (bbar_st != 1 || cbar_st != 1) { if (bbar_st != 1) bbar_st = 0; if (cbar_st != 1) cbar_st = 0; goto loop; } display(csa, parm, 1); switch (csa->phase) { case 1: if (parm->msg_lev >= GLP_MSG_ALL) xprintf("PROBLEM HAS NO FEASIBLE SOLUTION\n"); p_stat = GLP_NOFEAS; set_orig_obj(csa); eval_cbar(csa); chuzc(csa, parm->tol_dj); d_stat = (csa->q == 0 ? GLP_FEAS : GLP_INFEAS); break; case 2: if (parm->msg_lev >= GLP_MSG_ALL) xprintf("OPTIMAL SOLUTION FOUND\n"); p_stat = d_stat = GLP_FEAS; break; default: xassert(csa != csa); } store_sol(csa, lp, p_stat, d_stat, 0); ret = 0; goto done; } /* compute pivot column of the simplex table */ eval_tcol(csa); if (rigorous) refine_tcol(csa); sort_tcol(csa, parm->tol_piv); /* check accuracy of the reduced cost of xN[q] */ { double d1 = csa->cbar[csa->q]; /* less accurate */ double d2 = reeval_cost(csa); /* more accurate */ xassert(d1 != 0.0); if (fabs(d1 - d2) > 1e-5 * (1.0 + fabs(d2)) || !(d1 < 0.0 && d2 < 0.0 || d1 > 0.0 && d2 > 0.0)) { if (parm->msg_lev >= GLP_MSG_DBG) xprintf("d1 = %.12g; d2 = %.12g\n", d1, d2); if (cbar_st != 1 || !rigorous) { if (cbar_st != 1) cbar_st = 0; rigorous = 5; goto loop; } } /* replace cbar[q] by more accurate value keeping its sign */ if (d1 > 0.0) csa->cbar[csa->q] = (d2 > 0.0 ? d2 : +DBL_EPSILON); else csa->cbar[csa->q] = (d2 < 0.0 ? d2 : -DBL_EPSILON); } /* choose basic variable xB[p] */ switch (parm->r_test) { case GLP_RT_STD: chuzr(csa, 0.0); break; case GLP_RT_HAR: chuzr(csa, 0.30 * parm->tol_bnd); break; default: xassert(parm != parm); } if (csa->p == 0) { if (bbar_st != 1 || cbar_st != 1 || !rigorous) { if (bbar_st != 1) bbar_st = 0; if (cbar_st != 1) cbar_st = 0; rigorous = 1; goto loop; } display(csa, parm, 1); switch (csa->phase) { case 1: if (parm->msg_lev >= GLP_MSG_ERR) xprintf("Error: unable to choose basic variable on ph" "ase I\n"); xassert(!lp->valid && lp->bfd == NULL); lp->bfd = csa->bfd, csa->bfd = NULL; lp->pbs_stat = lp->dbs_stat = GLP_UNDEF; lp->obj_val = 0.0; lp->it_cnt = csa->it_cnt; lp->some = 0; ret = GLP_EFAIL; break; case 2: if (parm->msg_lev >= GLP_MSG_ALL) xprintf("PROBLEM HAS UNBOUNDED SOLUTION\n"); store_sol(csa, lp, GLP_FEAS, GLP_NOFEAS, csa->head[csa->m+csa->q]); ret = 0; break; default: xassert(csa != csa); } goto done; } /* check if the pivot element is acceptable */ if (csa->p > 0) { double piv = csa->tcol_vec[csa->p]; double eps = 1e-5 * (1.0 + 0.01 * csa->tcol_max); if (fabs(piv) < eps) { if (parm->msg_lev >= GLP_MSG_DBG) xprintf("piv = %.12g; eps = %g\n", piv, eps); if (!rigorous) { rigorous = 5; goto loop; } } } /* now xN[q] and xB[p] have been chosen anyhow */ /* compute pivot row of the simplex table */ if (csa->p > 0) { double *rho = csa->work4; eval_rho(csa, rho); if (rigorous) refine_rho(csa, rho); eval_trow(csa, rho); } /* accuracy check based on the pivot element */ if (csa->p > 0) { double piv1 = csa->tcol_vec[csa->p]; /* more accurate */ double piv2 = csa->trow_vec[csa->q]; /* less accurate */ xassert(piv1 != 0.0); if (fabs(piv1 - piv2) > 1e-8 * (1.0 + fabs(piv1)) || !(piv1 > 0.0 && piv2 > 0.0 || piv1 < 0.0 && piv2 < 0.0)) { if (parm->msg_lev >= GLP_MSG_DBG) xprintf("piv1 = %.12g; piv2 = %.12g\n", piv1, piv2); if (binv_st != 1 || !rigorous) { if (binv_st != 1) binv_st = 0; rigorous = 5; goto loop; } /* use more accurate version in the pivot row */ if (csa->trow_vec[csa->q] == 0.0) { csa->trow_nnz++; xassert(csa->trow_nnz <= csa->n); csa->trow_ind[csa->trow_nnz] = csa->q; } csa->trow_vec[csa->q] = piv1; } } /* update primal values of basic variables */ update_bbar(csa); bbar_st = 2; /* updated */ /* update reduced costs of non-basic variables */ if (csa->p > 0) { update_cbar(csa); cbar_st = 2; /* updated */ /* on phase I objective coefficient of xB[p] in the adjacent basis becomes zero */ if (csa->phase == 1) { int k = csa->head[csa->p]; /* x[k] = xB[p] -> xN[q] */ csa->cbar[csa->q] -= csa->coef[k]; csa->coef[k] = 0.0; } } /* update steepest edge coefficients */ if (csa->p > 0) { switch (parm->pricing) { case GLP_PT_STD: break; case GLP_PT_PSE: if (csa->refct > 0) update_gamma(csa); break; default: xassert(parm != parm); } } /* update factorization of the basis matrix */ if (csa->p > 0) { ret = update_B(csa, csa->p, csa->head[csa->m+csa->q]); if (ret == 0) binv_st = 2; /* updated */ else { csa->valid = 0; binv_st = 0; /* invalid */ } } /* update matrix N */ if (csa->p > 0) { del_N_col(csa, csa->q, csa->head[csa->m+csa->q]); if (csa->type[csa->head[csa->p]] != GLP_FX) add_N_col(csa, csa->q, csa->head[csa->p]); } /* change the basis header */ change_basis(csa); /* iteration complete */ csa->it_cnt++; if (rigorous > 0) rigorous--; goto loop; done: /* deallocate the common storage area */ free_csa(csa); /* return to the calling program */ return ret; } /* eof */ sources_5316/external/glpk/glpavl.c0000644000176700017670000002621011401660400016124 0ustar paulpaul/* glpavl.c (binary search tree) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpavl.h" AVL *avl_create_tree(int (*fcmp)(void *info, const void *key1, const void *key2), void *info) { /* create AVL tree */ AVL *tree; tree = xmalloc(sizeof(AVL)); tree->pool = dmp_create_pool(); tree->root = NULL; tree->fcmp = fcmp; tree->info = info; tree->size = 0; tree->height = 0; return tree; } int avl_strcmp(void *info, const void *key1, const void *key2) { /* compare character string keys */ xassert(info == info); return strcmp(key1, key2); } static AVLNODE *rotate_subtree(AVL *tree, AVLNODE *node); AVLNODE *avl_insert_node(AVL *tree, const void *key) { /* insert new node into AVL tree */ AVLNODE *p, *q, *r; short int flag; /* find an appropriate point for insertion */ p = NULL; q = tree->root; while (q != NULL) { p = q; if (tree->fcmp(tree->info, key, p->key) <= 0) { flag = 0; q = p->left; p->rank++; } else { flag = 1; q = p->right; } } /* create new node and insert it into the tree */ r = dmp_get_atom(tree->pool, sizeof(AVLNODE)); r->key = key; r->type = 0; r->link = NULL; r->rank = 1; r->up = p; r->flag = (short int)(p == NULL ? 0 : flag); r->bal = 0; r->left = NULL; r->right = NULL; tree->size++; if (p == NULL) tree->root = r; else if (flag == 0) p->left = r; else p->right = r; /* go upstairs to the root and correct all subtrees affected by insertion */ while (p != NULL) { if (flag == 0) { /* the height of the left subtree of [p] is increased */ if (p->bal > 0) { p->bal = 0; break; } if (p->bal < 0) { rotate_subtree(tree, p); break; } p->bal = -1; flag = p->flag; p = p->up; } else { /* the height of the right subtree of [p] is increased */ if (p->bal < 0) { p->bal = 0; break; } if (p->bal > 0) { rotate_subtree(tree, p); break; } p->bal = +1; flag = p->flag; p = p->up; } } /* if the root has been reached, the height of the entire tree is increased */ if (p == NULL) tree->height++; return r; } void avl_set_node_type(AVLNODE *node, int type) { /* assign the type field of specified node */ node->type = type; return; } void avl_set_node_link(AVLNODE *node, void *link) { /* assign the link field of specified node */ node->link = link; return; } AVLNODE *avl_find_node(AVL *tree, const void *key) { /* find node in AVL tree */ AVLNODE *p; int c; p = tree->root; while (p != NULL) { c = tree->fcmp(tree->info, key, p->key); if (c == 0) break; p = (c < 0 ? p->left : p->right); } return p; } int avl_get_node_type(AVLNODE *node) { /* retrieve the type field of specified node */ return node->type; } void *avl_get_node_link(AVLNODE *node) { /* retrieve the link field of specified node */ return node->link; } static AVLNODE *find_next_node(AVL *tree, AVLNODE *node) { /* find next node in AVL tree */ AVLNODE *p, *q; if (tree->root == NULL) return NULL; p = node; q = (p == NULL ? tree->root : p->right); if (q == NULL) { /* go upstairs from the left subtree */ for (;;) { q = p->up; if (q == NULL) break; if (p->flag == 0) break; p = q; } } else { /* go downstairs into the right subtree */ for (;;) { p = q->left; if (p == NULL) break; q = p; } } return q; } void avl_delete_node(AVL *tree, AVLNODE *node) { /* delete specified node from AVL tree */ AVLNODE *f, *p, *q, *r, *s, *x, *y; short int flag; p = node; /* if both subtrees of the specified node are non-empty, the node should be interchanged with the next one, at least one subtree of which is always empty */ if (p->left == NULL || p->right == NULL) goto skip; f = p->up; q = p->left; r = find_next_node(tree, p); s = r->right; if (p->right == r) { if (f == NULL) tree->root = r; else if (p->flag == 0) f->left = r; else f->right = r; r->rank = p->rank; r->up = f; r->flag = p->flag; r->bal = p->bal; r->left = q; r->right = p; q->up = r; p->rank = 1; p->up = r; p->flag = 1; p->bal = (short int)(s == NULL ? 0 : +1); p->left = NULL; p->right = s; if (s != NULL) s->up = p; } else { x = p->right; y = r->up; if (f == NULL) tree->root = r; else if (p->flag == 0) f->left = r; else f->right = r; r->rank = p->rank; r->up = f; r->flag = p->flag; r->bal = p->bal; r->left = q; r->right = x; q->up = r; x->up = r; y->left = p; p->rank = 1; p->up = y; p->flag = 0; p->bal = (short int)(s == NULL ? 0 : +1); p->left = NULL; p->right = s; if (s != NULL) s->up = p; } skip: /* now the specified node [p] has at least one empty subtree; go upstairs to the root and adjust the rank field of all nodes affected by deletion */ q = p; f = q->up; while (f != NULL) { if (q->flag == 0) f->rank--; q = f; f = q->up; } /* delete the specified node from the tree */ f = p->up; flag = p->flag; q = p->left != NULL ? p->left : p->right; if (f == NULL) tree->root = q; else if (flag == 0) f->left = q; else f->right = q; if (q != NULL) q->up = f, q->flag = flag; tree->size--; /* go upstairs to the root and correct all subtrees affected by deletion */ while (f != NULL) { if (flag == 0) { /* the height of the left subtree of [f] is decreased */ if (f->bal == 0) { f->bal = +1; break; } if (f->bal < 0) f->bal = 0; else { f = rotate_subtree(tree, f); if (f->bal < 0) break; } flag = f->flag; f = f->up; } else { /* the height of the right subtree of [f] is decreased */ if (f->bal == 0) { f->bal = -1; break; } if (f->bal > 0) f->bal = 0; else { f = rotate_subtree(tree, f); if (f->bal > 0) break; } flag = f->flag; f = f->up; } } /* if the root has been reached, the height of the entire tree is decreased */ if (f == NULL) tree->height--; /* returns the deleted node to the memory pool */ dmp_free_atom(tree->pool, p, sizeof(AVLNODE)); return; } static AVLNODE *rotate_subtree(AVL *tree, AVLNODE *node) { /* restore balance of AVL subtree */ AVLNODE *f, *p, *q, *r, *x, *y; xassert(node != NULL); p = node; if (p->bal < 0) { /* perform negative (left) rotation */ f = p->up; q = p->left; r = q->right; if (q->bal <= 0) { /* perform single negative rotation */ if (f == NULL) tree->root = q; else if (p->flag == 0) f->left = q; else f->right = q; p->rank -= q->rank; q->up = f; q->flag = p->flag; q->bal++; q->right = p; p->up = q; p->flag = 1; p->bal = (short int)(-q->bal); p->left = r; if (r != NULL) r->up = p, r->flag = 0; node = q; } else { /* perform double negative rotation */ x = r->left; y = r->right; if (f == NULL) tree->root = r; else if (p->flag == 0) f->left = r; else f->right = r; p->rank -= (q->rank + r->rank); r->rank += q->rank; p->bal = (short int)(r->bal >= 0 ? 0 : +1); q->bal = (short int)(r->bal <= 0 ? 0 : -1); r->up = f; r->flag = p->flag; r->bal = 0; r->left = q; r->right = p; p->up = r; p->flag = 1; p->left = y; q->up = r; q->flag = 0; q->right = x; if (x != NULL) x->up = q, x->flag = 1; if (y != NULL) y->up = p, y->flag = 0; node = r; } } else { /* perform positive (right) rotation */ f = p->up; q = p->right; r = q->left; if (q->bal >= 0) { /* perform single positive rotation */ if (f == NULL) tree->root = q; else if (p->flag == 0) f->left = q; else f->right = q; q->rank += p->rank; q->up = f; q->flag = p->flag; q->bal--; q->left = p; p->up = q; p->flag = 0; p->bal = (short int)(-q->bal); p->right = r; if (r != NULL) r->up = p, r->flag = 1; node = q; } else { /* perform double positive rotation */ x = r->left; y = r->right; if (f == NULL) tree->root = r; else if (p->flag == 0) f->left = r; else f->right = r; q->rank -= r->rank; r->rank += p->rank; p->bal = (short int)(r->bal <= 0 ? 0 : -1); q->bal = (short int)(r->bal >= 0 ? 0 : +1); r->up = f; r->flag = p->flag; r->bal = 0; r->left = p; r->right = q; p->up = r; p->flag = 0; p->right = x; q->up = r; q->flag = 1; q->left = y; if (x != NULL) x->up = p, x->flag = 1; if (y != NULL) y->up = q, y->flag = 0; node = r; } } return node; } void avl_delete_tree(AVL *tree) { /* delete AVL tree */ dmp_delete_pool(tree->pool); xfree(tree); return; } /* eof */ sources_5316/external/glpk/glpios.h0000644000176700017670000005356611401660400016157 0ustar paulpaul/* glpios.h (integer optimization suite) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPIOS_H #define GLPIOS_H #define GLP_TREE_DEFINED typedef struct glp_tree glp_tree; #include "glpapi.h" typedef struct IOSLOT IOSLOT; typedef struct IOSNPD IOSNPD; typedef struct IOSBND IOSBND; typedef struct IOSTAT IOSTAT; typedef struct IOSROW IOSROW; typedef struct IOSAIJ IOSAIJ; typedef struct IOSPOOL IOSPOOL; typedef struct IOSCUT IOSCUT; struct glp_tree { /* branch-and-bound tree */ int magic; /* magic value used for debugging */ DMP *pool; /* memory pool to store all IOS components */ int n; /* number of columns (variables) */ /*--------------------------------------------------------------*/ /* problem components corresponding to the original MIP and its LP relaxation (used to restore the original problem object on exit from the solver) */ int orig_m; /* number of rows */ unsigned char *orig_type; /* uchar orig_type[1+orig_m+n]; */ /* types of all variables */ double *orig_lb; /* double orig_lb[1+orig_m+n]; */ /* lower bounds of all variables */ double *orig_ub; /* double orig_ub[1+orig_m+n]; */ /* upper bounds of all variables */ unsigned char *orig_stat; /* uchar orig_stat[1+orig_m+n]; */ /* statuses of all variables */ double *orig_prim; /* double orig_prim[1+orig_m+n]; */ /* primal values of all variables */ double *orig_dual; /* double orig_dual[1+orig_m+n]; */ /* dual values of all variables */ double orig_obj; /* optimal objective value for LP relaxation */ /*--------------------------------------------------------------*/ /* branch-and-bound tree */ int nslots; /* length of the array of slots (enlarged automatically) */ int avail; /* index of the first free slot; 0 means all slots are in use */ IOSLOT *slot; /* IOSLOT slot[1+nslots]; */ /* array of slots: slot[0] is not used; slot[p], 1 <= p <= nslots, either contains a pointer to some node of the branch-and-bound tree, in which case p is used on API level as the reference number of corresponding subproblem, or is free; all free slots are linked into single linked list; slot[1] always contains a pointer to the root node (it is free only if the tree is empty) */ IOSNPD *head; /* pointer to the head of the active list */ IOSNPD *tail; /* pointer to the tail of the active list */ /* the active list is a doubly linked list of active subproblems which correspond to leaves of the tree; all subproblems in the active list are ordered chronologically (each a new subproblem is always added to the tail of the list) */ int a_cnt; /* current number of active nodes (including the current one) */ int n_cnt; /* current number of all (active and inactive) nodes */ int t_cnt; /* total number of nodes including those which have been already removed from the tree; this count is increased by one whenever a new node is created and never decreased */ /*--------------------------------------------------------------*/ /* problem components corresponding to the root subproblem */ int root_m; /* number of rows */ unsigned char *root_type; /* uchar root_type[1+root_m+n]; */ /* types of all variables */ double *root_lb; /* double root_lb[1+root_m+n]; */ /* lower bounds of all variables */ double *root_ub; /* double root_ub[1+root_m+n]; */ /* upper bounds of all variables */ unsigned char *root_stat; /* uchar root_stat[1+root_m+n]; */ /* statuses of all variables */ /*--------------------------------------------------------------*/ /* current subproblem and its LP relaxation */ IOSNPD *curr; /* pointer to the current subproblem (which can be only active); NULL means the current subproblem does not exist */ glp_prob *mip; /* original problem object passed to the solver; if the current subproblem exists, its LP segment corresponds to LP relaxation of the current subproblem; if the current subproblem does not exist, its LP segment corresponds to LP relaxation of the root subproblem (note that the root subproblem may differ from the original MIP, because it may be preprocessed and/or may have additional rows) */ unsigned char *non_int; /* uchar non_int[1+n]; */ /* these column flags are set each time when LP relaxation of the current subproblem has been solved; non_int[0] is not used; non_int[j], 1 <= j <= n, is j-th column flag; if this flag is set, corresponding variable is required to be integer, but its value in basic solution is fractional */ /*--------------------------------------------------------------*/ /* problem components corresponding to the parent (predecessor) subproblem for the current subproblem; used to inspect changes on freezing the current subproblem */ int pred_m; /* number of rows */ int pred_max; /* length of the following four arrays (enlarged automatically), pred_max >= pred_m + n */ unsigned char *pred_type; /* uchar pred_type[1+pred_m+n]; */ /* types of all variables */ double *pred_lb; /* double pred_lb[1+pred_m+n]; */ /* lower bounds of all variables */ double *pred_ub; /* double pred_ub[1+pred_m+n]; */ /* upper bounds of all variables */ unsigned char *pred_stat; /* uchar pred_stat[1+pred_m+n]; */ /* statuses of all variables */ /****************************************************************/ /* built-in cut generators segment */ IOSPOOL *local; /* local cut pool */ void *mir_gen; /* pointer to working area used by the MIR cut generator */ void *clq_gen; /* pointer to working area used by the clique cut generator */ /*--------------------------------------------------------------*/ void *pcost; /* pointer to working area used on pseudocost branching */ int *iwrk; /* int iwrk[1+n]; */ /* working array */ double *dwrk; /* double dwrk[1+n]; */ /* working array */ /*--------------------------------------------------------------*/ /* control parameters and statistics */ const glp_iocp *parm; /* copy of control parameters passed to the solver */ glp_long tm_beg; /* starting time of the search, in seconds; the total time of the search is the difference between xtime() and tm_beg */ glp_long tm_lag; /* the most recent time, in seconds, at which the progress of the the search was displayed */ int sol_cnt; /* number of integer feasible solutions found */ /*--------------------------------------------------------------*/ /* advanced solver interface */ int reason; /* flag indicating the reason why the callback routine is being called (see glpk.h) */ int stop; /* flag indicating that the callback routine requires premature termination of the search */ int next_p; /* reference number of active subproblem selected to continue the search; 0 means no subproblem has been selected */ int reopt; /* flag indicating that the current LP relaxation needs to be re-optimized */ int reinv; /* flag indicating that some (non-active) rows were removed from the current LP relaxation, so if there no new rows appear, the basis must be re-factorized */ int br_var; /* the number of variable chosen to branch on */ int br_sel; /* flag indicating which branch (subproblem) is suggested to be selected to continue the search: GLP_DN_BRNCH - select down-branch GLP_UP_BRNCH - select up-branch GLP_NO_BRNCH - use general selection technique */ int child; /* subproblem reference number corresponding to br_sel */ }; struct IOSLOT { /* node subproblem slot */ IOSNPD *node; /* pointer to subproblem descriptor; NULL means free slot */ int next; /* index of another free slot (only if this slot is free) */ }; struct IOSNPD { /* node subproblem descriptor */ int p; /* subproblem reference number (it is the index to corresponding slot, i.e. slot[p] points to this descriptor) */ IOSNPD *up; /* pointer to the parent subproblem; NULL means this node is the root of the tree, in which case p = 1 */ int level; /* node level (the root node has level 0) */ int count; /* if count = 0, this subproblem is active; if count > 0, this subproblem is inactive, in which case count is the number of its child subproblems */ /* the following three linked lists are destroyed on reviving and built anew on freezing the subproblem: */ IOSBND *b_ptr; /* linked list of rows and columns of the parent subproblem whose types and bounds were changed */ IOSTAT *s_ptr; /* linked list of rows and columns of the parent subproblem whose statuses were changed */ IOSROW *r_ptr; /* linked list of rows (cuts) added to the parent subproblem */ int solved; /* how many times LP relaxation of this subproblem was solved; for inactive subproblem this count is always non-zero; for active subproblem, which is not current, this count may be non-zero, if the subproblem was temporarily suspended */ double lp_obj; /* optimal objective value to LP relaxation of this subproblem; on creating a subproblem this value is inherited from its parent; for the root subproblem, which has no parent, this value is initially set to -DBL_MAX (minimization) or +DBL_MAX (maximization); each time the subproblem is re-optimized, this value is appropriately changed */ double bound; /* local lower (minimization) or upper (maximization) bound for integer optimal solution to *this* subproblem; this bound is local in the sense that only subproblems in the subtree rooted at this node cannot have better integer feasible solutions; on creating a subproblem its local bound is inherited from its parent and then can be made stronger (never weaker); for the root subproblem its local bound is initially set to -DBL_MAX (minimization) or +DBL_MAX (maximization) and then improved as the root LP relaxation has been solved */ /* the following two quantities are defined only if LP relaxation of this subproblem was solved at least once (solved > 0): */ int ii_cnt; /* number of integer variables whose value in optimal solution to LP relaxation of this subproblem is fractional */ double ii_sum; /* sum of integer infeasibilities */ #if 1 /* 30/XI-2009 */ int changed; /* how many times this subproblem was re-formulated (by adding cutting plane constraints) */ #endif int br_var; /* ordinal number of branching variable, 1 <= br_var <= n, used to split this subproblem; 0 means that either this subproblem is active or branching was made on a constraint */ double br_val; /* (fractional) value of branching variable in optimal solution to final LP relaxation of this subproblem */ void *data; /* char data[tree->cb_size]; */ /* pointer to the application-specific data */ IOSNPD *temp; /* working pointer used by some routines */ IOSNPD *prev; /* pointer to previous subproblem in the active list */ IOSNPD *next; /* pointer to next subproblem in the active list */ }; struct IOSBND { /* bounds change entry */ int k; /* ordinal number of corresponding row (1 <= k <= m) or column (m+1 <= k <= m+n), where m and n are the number of rows and columns, resp., in the parent subproblem */ unsigned char type; /* new type */ double lb; /* new lower bound */ double ub; /* new upper bound */ IOSBND *next; /* pointer to next entry for the same subproblem */ }; struct IOSTAT { /* status change entry */ int k; /* ordinal number of corresponding row (1 <= k <= m) or column (m+1 <= k <= m+n), where m and n are the number of rows and columns, resp., in the parent subproblem */ unsigned char stat; /* new status */ IOSTAT *next; /* pointer to next entry for the same subproblem */ }; struct IOSROW { /* row (constraint) addition entry */ char *name; /* row name or NULL */ unsigned char origin; /* row origin flag (see glp_attr.origin) */ unsigned char klass; /* row class descriptor (see glp_attr.klass) */ unsigned char type; /* row type (GLP_LO, GLP_UP, etc.) */ double lb; /* row lower bound */ double ub; /* row upper bound */ IOSAIJ *ptr; /* pointer to the row coefficient list */ double rii; /* row scale factor */ unsigned char stat; /* row status (GLP_BS, GLP_NL, etc.) */ IOSROW *next; /* pointer to next entry for the same subproblem */ }; struct IOSAIJ { /* constraint coefficient */ int j; /* variable (column) number, 1 <= j <= n */ double val; /* non-zero coefficient value */ IOSAIJ *next; /* pointer to next coefficient for the same row */ }; struct IOSPOOL { /* cut pool */ int size; /* pool size = number of cuts in the pool */ IOSCUT *head; /* pointer to the first cut */ IOSCUT *tail; /* pointer to the last cut */ int ord; /* ordinal number of the current cut, 1 <= ord <= size */ IOSCUT *curr; /* pointer to the current cut */ }; struct IOSCUT { /* cut (cutting plane constraint) */ char *name; /* cut name or NULL */ unsigned char klass; /* cut class descriptor (see glp_attr.klass) */ IOSAIJ *ptr; /* pointer to the cut coefficient list */ unsigned char type; /* cut type: GLP_LO: sum a[j] * x[j] >= b GLP_UP: sum a[j] * x[j] <= b GLP_FX: sum a[j] * x[j] = b */ double rhs; /* cut right-hand side */ IOSCUT *prev; /* pointer to previous cut */ IOSCUT *next; /* pointer to next cut */ }; #define ios_create_tree _glp_ios_create_tree glp_tree *ios_create_tree(glp_prob *mip, const glp_iocp *parm); /* create branch-and-bound tree */ #define ios_revive_node _glp_ios_revive_node void ios_revive_node(glp_tree *tree, int p); /* revive specified subproblem */ #define ios_freeze_node _glp_ios_freeze_node void ios_freeze_node(glp_tree *tree); /* freeze current subproblem */ #define ios_clone_node _glp_ios_clone_node void ios_clone_node(glp_tree *tree, int p, int nnn, int ref[]); /* clone specified subproblem */ #define ios_delete_node _glp_ios_delete_node void ios_delete_node(glp_tree *tree, int p); /* delete specified subproblem */ #define ios_delete_tree _glp_ios_delete_tree void ios_delete_tree(glp_tree *tree); /* delete branch-and-bound tree */ #define ios_eval_degrad _glp_ios_eval_degrad void ios_eval_degrad(glp_tree *tree, int j, double *dn, double *up); /* estimate obj. degrad. for down- and up-branches */ #define ios_round_bound _glp_ios_round_bound double ios_round_bound(glp_tree *tree, double bound); /* improve local bound by rounding */ #define ios_is_hopeful _glp_ios_is_hopeful int ios_is_hopeful(glp_tree *tree, double bound); /* check if subproblem is hopeful */ #define ios_best_node _glp_ios_best_node int ios_best_node(glp_tree *tree); /* find active node with best local bound */ #define ios_relative_gap _glp_ios_relative_gap double ios_relative_gap(glp_tree *tree); /* compute relative mip gap */ #define ios_solve_node _glp_ios_solve_node int ios_solve_node(glp_tree *tree); /* solve LP relaxation of current subproblem */ #define ios_create_pool _glp_ios_create_pool IOSPOOL *ios_create_pool(glp_tree *tree); /* create cut pool */ #define ios_add_row _glp_ios_add_row int ios_add_row(glp_tree *tree, IOSPOOL *pool, const char *name, int klass, int flags, int len, const int ind[], const double val[], int type, double rhs); /* add row (constraint) to the cut pool */ #define ios_find_row _glp_ios_find_row IOSCUT *ios_find_row(IOSPOOL *pool, int i); /* find row (constraint) in the cut pool */ #define ios_del_row _glp_ios_del_row void ios_del_row(glp_tree *tree, IOSPOOL *pool, int i); /* remove row (constraint) from the cut pool */ #define ios_clear_pool _glp_ios_clear_pool void ios_clear_pool(glp_tree *tree, IOSPOOL *pool); /* remove all rows (constraints) from the cut pool */ #define ios_delete_pool _glp_ios_delete_pool void ios_delete_pool(glp_tree *tree, IOSPOOL *pool); /* delete cut pool */ #define ios_preprocess_node _glp_ios_preprocess_node int ios_preprocess_node(glp_tree *tree, int max_pass); /* preprocess current subproblem */ #define ios_driver _glp_ios_driver int ios_driver(glp_tree *tree); /* branch-and-bound driver */ /**********************************************************************/ typedef struct IOSVEC IOSVEC; struct IOSVEC { /* sparse vector v = (v[j]) */ int n; /* dimension, n >= 0 */ int nnz; /* number of non-zero components, 0 <= nnz <= n */ int *pos; /* int pos[1+n]; */ /* pos[j] = k, 1 <= j <= n, is position of (non-zero) v[j] in the arrays ind and val, where 1 <= k <= nnz; pos[j] = 0 means that v[j] is structural zero */ int *ind; /* int ind[1+n]; */ /* ind[k] = j, 1 <= k <= nnz, is index of v[j] */ double *val; /* double val[1+n]; */ /* val[k], 1 <= k <= nnz, is a numeric value of v[j] */ }; #define ios_create_vec _glp_ios_create_vec IOSVEC *ios_create_vec(int n); /* create sparse vector */ #define ios_check_vec _glp_ios_check_vec void ios_check_vec(IOSVEC *v); /* check that sparse vector has correct representation */ #define ios_get_vj _glp_ios_get_vj double ios_get_vj(IOSVEC *v, int j); /* retrieve component of sparse vector */ #define ios_set_vj _glp_ios_set_vj void ios_set_vj(IOSVEC *v, int j, double val); /* set/change component of sparse vector */ #define ios_clear_vec _glp_ios_clear_vec void ios_clear_vec(IOSVEC *v); /* set all components of sparse vector to zero */ #define ios_clean_vec _glp_ios_clean_vec void ios_clean_vec(IOSVEC *v, double eps); /* remove zero or small components from sparse vector */ #define ios_copy_vec _glp_ios_copy_vec void ios_copy_vec(IOSVEC *x, IOSVEC *y); /* copy sparse vector (x := y) */ #define ios_linear_comb _glp_ios_linear_comb void ios_linear_comb(IOSVEC *x, double a, IOSVEC *y); /* compute linear combination (x := x + a * y) */ #define ios_delete_vec _glp_ios_delete_vec void ios_delete_vec(IOSVEC *v); /* delete sparse vector */ /**********************************************************************/ #define ios_gmi_gen _glp_ios_gmi_gen void ios_gmi_gen(glp_tree *tree); /* generate Gomory's mixed integer cuts */ #define ios_mir_init _glp_ios_mir_init void *ios_mir_init(glp_tree *tree); /* initialize MIR cut generator */ #define ios_mir_gen _glp_ios_mir_gen void ios_mir_gen(glp_tree *tree, void *gen); /* generate MIR cuts */ #define ios_mir_term _glp_ios_mir_term void ios_mir_term(void *gen); /* terminate MIR cut generator */ #define ios_cov_gen _glp_ios_cov_gen void ios_cov_gen(glp_tree *tree); /* generate mixed cover cuts */ #define ios_clq_init _glp_ios_clq_init void *ios_clq_init(glp_tree *tree); /* initialize clique cut generator */ #define ios_clq_gen _glp_ios_clq_gen void ios_clq_gen(glp_tree *tree, void *gen); /* generate clique cuts */ #define ios_clq_term _glp_ios_clq_term void ios_clq_term(void *gen); /* terminate clique cut generator */ #define ios_pcost_init _glp_ios_pcost_init void *ios_pcost_init(glp_tree *tree); /* initialize working data used on pseudocost branching */ #define ios_pcost_branch _glp_ios_pcost_branch int ios_pcost_branch(glp_tree *T, int *next); /* choose branching variable with pseudocost branching */ #define ios_pcost_update _glp_ios_pcost_update void ios_pcost_update(glp_tree *tree); /* update history information for pseudocost branching */ #define ios_pcost_free _glp_ios_pcost_free void ios_pcost_free(glp_tree *tree); /* free working area used on pseudocost branching */ #define ios_feas_pump _glp_ios_feas_pump void ios_feas_pump(glp_tree *T); /* feasibility pump heuristic */ #define ios_process_cuts _glp_ios_process_cuts void ios_process_cuts(glp_tree *T); /* process cuts stored in the local cut pool */ #define ios_choose_node _glp_ios_choose_node int ios_choose_node(glp_tree *T); /* select subproblem to continue the search */ #define ios_choose_var _glp_ios_choose_var int ios_choose_var(glp_tree *T, int *next); /* select variable to branch on */ #endif /* eof */ sources_5316/external/glpk/glpdmp.h0000644000176700017670000000522611401660400016133 0ustar paulpaul/* glpdmp.h (dynamic memory pool) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPDMP_H #define GLPDMP_H #include "glpenv.h" typedef struct DMP DMP; #define DMP_BLK_SIZE 8000 /* size of memory blocks, in bytes, allocated for memory pools */ struct DMP { /* dynamic memory pool */ #if 0 int size; /* size of atoms, in bytes, 1 <= size <= 256; if size = 0, atoms may have different sizes */ #endif void *avail[32]; /* avail[k], 0 <= k <= 31, is a pointer to the first available (free) cell of (k+1)*8 bytes long; in the beginning of each free cell there is a pointer to another free cell of the same length */ void *block; /* pointer to the most recently allocated memory block; in the beginning of each allocated memory block there is a pointer to the previously allocated memory block */ int used; /* number of bytes used in the most recently allocated memory block */ glp_long count; /* number of atoms which are currently in use */ }; #define dmp_create_pool _glp_dmp_create_pool DMP *dmp_create_pool(void); /* create dynamic memory pool */ #define dmp_get_atom _glp_dmp_get_atom void *dmp_get_atom(DMP *pool, int size); /* get free atom from dynamic memory pool */ #define dmp_free_atom _glp_dmp_free_atom void dmp_free_atom(DMP *pool, void *atom, int size); /* return atom to dynamic memory pool */ #define dmp_in_use _glp_dmp_in_use glp_long dmp_in_use(DMP *pool); /* determine how many atoms are still in use */ #define dmp_delete_pool _glp_dmp_delete_pool void dmp_delete_pool(DMP *pool); /* delete dynamic memory pool */ #endif /* eof */ sources_5316/external/glpk/glpscf.h0000644000176700017670000001074411401660400016127 0ustar paulpaul/* glpscf.h (Schur complement factorization) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPSCF_H #define GLPSCF_H /*********************************************************************** * The structure SCF defines the following factorization of a square * nxn matrix C (which is the Schur complement): * * F * C = U * P, * * where F is a square transforming matrix, U is an upper triangular * matrix, P is a permutation matrix. * * It is assumed that matrix C is small and dense, so matrices F and U * are stored in the dense format by rows as follows: * * 1 n n_max 1 n n_max * 1 * * * * * * x x x x 1 * * * * * * x x x x * * * * * * * x x x x . * * * * * x x x x * * * * * * * x x x x . . * * * * x x x x * * * * * * * x x x x . . . * * * x x x x * * * * * * * x x x x . . . . * * x x x x * n * * * * * * x x x x n . . . . . * x x x x * x x x x x x x x x x . . . . . . x x x x * x x x x x x x x x x . . . . . . . x x x * x x x x x x x x x x . . . . . . . . x x * n_max x x x x x x x x x x n_max . . . . . . . . . x * * matrix F matrix U * * where '*' are matrix elements, 'x' are reserved locations. * * Permutation matrix P is stored in row-like format. * * Matrix C normally is not stored. * * REFERENCES * * 1. M.A.Saunders, "LUSOL: A basis package for constrained optimiza- * tion," SCCM, Stanford University, 2006. * * 2. M.A.Saunders, "Notes 5: Basis Updates," CME 318, Stanford Univer- * sity, Spring 2006. * * 3. M.A.Saunders, "Notes 6: LUSOL---a Basis Factorization Package," * ibid. */ typedef struct SCF SCF; struct SCF { /* Schur complement factorization */ int n_max; /* maximal order of matrices C, F, U, P; n_max >= 1 */ int n; /* current order of matrices C, F, U, P; n >= 0 */ double *f; /* double f[1+n_max*n_max]; */ /* matrix F stored by rows */ double *u; /* double u[1+n_max*(n_max+1)/2]; */ /* upper triangle of matrix U stored by rows */ int *p; /* int p[1+n_max]; */ /* matrix P; p[i] = j means that P[i,j] = 1 */ int t_opt; /* type of transformation used to restore triangular structure of matrix U: */ #define SCF_TBG 1 /* Bartels-Golub elimination */ #define SCF_TGR 2 /* Givens plane rotation */ int rank; /* estimated rank of matrices C and U */ double *c; /* double c[1+n_max*n_max]; */ /* matrix C stored in the same format as matrix F and used only for debugging; normally this array is not allocated */ double *w; /* double w[1+n_max]; */ /* working array */ }; /* return codes: */ #define SCF_ESING 1 /* singular matrix */ #define SCF_ELIMIT 2 /* update limit reached */ #define scf_create_it _glp_scf_create_it SCF *scf_create_it(int n_max); /* create Schur complement factorization */ #define scf_update_exp _glp_scf_update_exp int scf_update_exp(SCF *scf, const double x[], const double y[], double z); /* update factorization on expanding C */ #define scf_solve_it _glp_scf_solve_it void scf_solve_it(SCF *scf, int tr, double x[]); /* solve either system C * x = b or C' * x = b */ #define scf_reset_it _glp_scf_reset_it void scf_reset_it(SCF *scf); /* reset factorization for empty matrix C */ #define scf_delete_it _glp_scf_delete_it void scf_delete_it(SCF *scf); /* delete Schur complement factorization */ #endif /* eof */ sources_5316/external/glpk/glpios03.c0000644000176700017670000012431011401660400016277 0ustar paulpaul/* glpios03.c (branch-and-cut driver) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*********************************************************************** * show_progress - display current progress of the search * * This routine displays some information about current progress of the * search. * * The information includes: * * the current number of iterations performed by the simplex solver; * * the objective value for the best known integer feasible solution, * which is upper (minimization) or lower (maximization) global bound * for optimal solution of the original mip problem; * * the best local bound for active nodes, which is lower (minimization) * or upper (maximization) global bound for optimal solution of the * original mip problem; * * the relative mip gap, in percents; * * the number of open (active) subproblems; * * the number of completely explored subproblems, i.e. whose nodes have * been removed from the tree. */ static void show_progress(glp_tree *T, int bingo) { int p; double temp; char best_mip[50], best_bound[50], *rho, rel_gap[50]; /* format the best known integer feasible solution */ if (T->mip->mip_stat == GLP_FEAS) sprintf(best_mip, "%17.9e", T->mip->mip_obj); else sprintf(best_mip, "%17s", "not found yet"); /* determine reference number of an active subproblem whose local bound is best */ p = ios_best_node(T); /* format the best bound */ if (p == 0) sprintf(best_bound, "%17s", "tree is empty"); else { temp = T->slot[p].node->bound; if (temp == -DBL_MAX) sprintf(best_bound, "%17s", "-inf"); else if (temp == +DBL_MAX) sprintf(best_bound, "%17s", "+inf"); else sprintf(best_bound, "%17.9e", temp); } /* choose the relation sign between global bounds */ if (T->mip->dir == GLP_MIN) rho = ">="; else if (T->mip->dir == GLP_MAX) rho = "<="; else xassert(T != T); /* format the relative mip gap */ temp = ios_relative_gap(T); if (temp == 0.0) sprintf(rel_gap, " 0.0%%"); else if (temp < 0.001) sprintf(rel_gap, "< 0.1%%"); else if (temp <= 9.999) sprintf(rel_gap, "%5.1f%%", 100.0 * temp); else sprintf(rel_gap, "%6s", ""); /* display progress of the search */ xprintf("+%6d: %s %s %s %s %s (%d; %d)\n", T->mip->it_cnt, bingo ? ">>>>>" : "mip =", best_mip, rho, best_bound, rel_gap, T->a_cnt, T->t_cnt - T->n_cnt); T->tm_lag = xtime(); return; } /*********************************************************************** * is_branch_hopeful - check if specified branch is hopeful * * This routine checks if the specified subproblem can have an integer * optimal solution which is better than the best known one. * * The check is based on comparison of the local objective bound stored * in the subproblem descriptor and the incumbent objective value which * is the global objective bound. * * If there is a chance that the specified subproblem can have a better * integer optimal solution, the routine returns non-zero. Otherwise, if * the corresponding branch can pruned, zero is returned. */ static int is_branch_hopeful(glp_tree *T, int p) { xassert(1 <= p && p <= T->nslots); xassert(T->slot[p].node != NULL); return ios_is_hopeful(T, T->slot[p].node->bound); } /*********************************************************************** * check_integrality - check integrality of basic solution * * This routine checks if the basic solution of LP relaxation of the * current subproblem satisfies to integrality conditions, i.e. that all * variables of integer kind have integral primal values. (The solution * is assumed to be optimal.) * * For each variable of integer kind the routine computes the following * quantity: * * ii(x[j]) = min(x[j] - floor(x[j]), ceil(x[j]) - x[j]), (1) * * which is a measure of the integer infeasibility (non-integrality) of * x[j] (for example, ii(2.1) = 0.1, ii(3.7) = 0.3, ii(5.0) = 0). It is * understood that 0 <= ii(x[j]) <= 0.5, and variable x[j] is integer * feasible if ii(x[j]) = 0. However, due to floating-point arithmetic * the routine checks less restrictive condition: * * ii(x[j]) <= tol_int, (2) * * where tol_int is a given tolerance (small positive number) and marks * each variable which does not satisfy to (2) as integer infeasible by * setting its fractionality flag. * * In order to characterize integer infeasibility of the basic solution * in the whole the routine computes two parameters: ii_cnt, which is * the number of variables with the fractionality flag set, and ii_sum, * which is the sum of integer infeasibilities (1). */ static void check_integrality(glp_tree *T) { glp_prob *mip = T->mip; int j, type, ii_cnt = 0; double lb, ub, x, temp1, temp2, ii_sum = 0.0; /* walk through the set of columns (structural variables) */ for (j = 1; j <= mip->n; j++) { GLPCOL *col = mip->col[j]; T->non_int[j] = 0; /* if the column is not integer, skip it */ if (col->kind != GLP_IV) continue; /* if the column is non-basic, it is integer feasible */ if (col->stat != GLP_BS) continue; /* obtain the type and bounds of the column */ type = col->type, lb = col->lb, ub = col->ub; /* obtain value of the column in optimal basic solution */ x = col->prim; /* if the column's primal value is close to the lower bound, the column is integer feasible within given tolerance */ if (type == GLP_LO || type == GLP_DB || type == GLP_FX) { temp1 = lb - T->parm->tol_int; temp2 = lb + T->parm->tol_int; if (temp1 <= x && x <= temp2) continue; #if 0 /* the lower bound must not be violated */ xassert(x >= lb); #else if (x < lb) continue; #endif } /* if the column's primal value is close to the upper bound, the column is integer feasible within given tolerance */ if (type == GLP_UP || type == GLP_DB || type == GLP_FX) { temp1 = ub - T->parm->tol_int; temp2 = ub + T->parm->tol_int; if (temp1 <= x && x <= temp2) continue; #if 0 /* the upper bound must not be violated */ xassert(x <= ub); #else if (x > ub) continue; #endif } /* if the column's primal value is close to nearest integer, the column is integer feasible within given tolerance */ temp1 = floor(x + 0.5) - T->parm->tol_int; temp2 = floor(x + 0.5) + T->parm->tol_int; if (temp1 <= x && x <= temp2) continue; /* otherwise the column is integer infeasible */ T->non_int[j] = 1; /* increase the number of fractional-valued columns */ ii_cnt++; /* compute the sum of integer infeasibilities */ temp1 = x - floor(x); temp2 = ceil(x) - x; xassert(temp1 > 0.0 && temp2 > 0.0); ii_sum += (temp1 <= temp2 ? temp1 : temp2); } /* store ii_cnt and ii_sum to the current problem descriptor */ xassert(T->curr != NULL); T->curr->ii_cnt = ii_cnt; T->curr->ii_sum = ii_sum; /* and also display these parameters */ if (T->parm->msg_lev >= GLP_MSG_DBG) { if (ii_cnt == 0) xprintf("There are no fractional columns\n"); else if (ii_cnt == 1) xprintf("There is one fractional column, integer infeasibil" "ity is %.3e\n", ii_sum); else xprintf("There are %d fractional columns, integer infeasibi" "lity is %.3e\n", ii_cnt, ii_sum); } return; } /*********************************************************************** * record_solution - record better integer feasible solution * * This routine records optimal basic solution of LP relaxation of the * current subproblem, which being integer feasible is better than the * best known integer feasible solution. */ static void record_solution(glp_tree *T) { glp_prob *mip = T->mip; int i, j; mip->mip_stat = GLP_FEAS; mip->mip_obj = mip->obj_val; for (i = 1; i <= mip->m; i++) { GLPROW *row = mip->row[i]; row->mipx = row->prim; } for (j = 1; j <= mip->n; j++) { GLPCOL *col = mip->col[j]; if (col->kind == GLP_CV) col->mipx = col->prim; else if (col->kind == GLP_IV) { /* value of the integer column must be integral */ col->mipx = floor(col->prim + 0.5); } else xassert(col != col); } T->sol_cnt++; return; } /*********************************************************************** * fix_by_red_cost - fix non-basic integer columns by reduced costs * * This routine fixes some non-basic integer columns if their reduced * costs indicate that increasing (decreasing) the column at least by * one involves the objective value becoming worse than the incumbent * objective value. */ static void fix_by_red_cost(glp_tree *T) { glp_prob *mip = T->mip; int j, stat, fixed = 0; double obj, lb, ub, dj; /* the global bound must exist */ xassert(T->mip->mip_stat == GLP_FEAS); /* basic solution of LP relaxation must be optimal */ xassert(mip->pbs_stat == GLP_FEAS && mip->dbs_stat == GLP_FEAS); /* determine the objective function value */ obj = mip->obj_val; /* walk through the column list */ for (j = 1; j <= mip->n; j++) { GLPCOL *col = mip->col[j]; /* if the column is not integer, skip it */ if (col->kind != GLP_IV) continue; /* obtain bounds of j-th column */ lb = col->lb, ub = col->ub; /* and determine its status and reduced cost */ stat = col->stat, dj = col->dual; /* analyze the reduced cost */ switch (mip->dir) { case GLP_MIN: /* minimization */ if (stat == GLP_NL) { /* j-th column is non-basic on its lower bound */ if (dj < 0.0) dj = 0.0; if (obj + dj >= mip->mip_obj) glp_set_col_bnds(mip, j, GLP_FX, lb, lb), fixed++; } else if (stat == GLP_NU) { /* j-th column is non-basic on its upper bound */ if (dj > 0.0) dj = 0.0; if (obj - dj >= mip->mip_obj) glp_set_col_bnds(mip, j, GLP_FX, ub, ub), fixed++; } break; case GLP_MAX: /* maximization */ if (stat == GLP_NL) { /* j-th column is non-basic on its lower bound */ if (dj > 0.0) dj = 0.0; if (obj + dj <= mip->mip_obj) glp_set_col_bnds(mip, j, GLP_FX, lb, lb), fixed++; } else if (stat == GLP_NU) { /* j-th column is non-basic on its upper bound */ if (dj < 0.0) dj = 0.0; if (obj - dj <= mip->mip_obj) glp_set_col_bnds(mip, j, GLP_FX, ub, ub), fixed++; } break; default: xassert(T != T); } } if (T->parm->msg_lev >= GLP_MSG_DBG) { if (fixed == 0) /* nothing to say */; else if (fixed == 1) xprintf("One column has been fixed by reduced cost\n"); else xprintf("%d columns have been fixed by reduced costs\n", fixed); } /* fixing non-basic columns on their current bounds does not change the basic solution */ xassert(mip->pbs_stat == GLP_FEAS && mip->dbs_stat == GLP_FEAS); return; } /*********************************************************************** * branch_on - perform branching on specified variable * * This routine performs branching on j-th column (structural variable) * of the current subproblem. The specified column must be of integer * kind and must have a fractional value in optimal basic solution of * LP relaxation of the current subproblem (i.e. only columns for which * the flag non_int[j] is set are valid candidates to branch on). * * Let x be j-th structural variable, and beta be its primal fractional * value in the current basic solution. Branching on j-th variable is * dividing the current subproblem into two new subproblems, which are * identical to the current subproblem with the following exception: in * the first subproblem that begins the down-branch x has a new upper * bound x <= floor(beta), and in the second subproblem that begins the * up-branch x has a new lower bound x >= ceil(beta). * * Depending on estimation of local bounds for down- and up-branches * this routine returns the following: * * 0 - both branches have been created; * 1 - one branch is hopeless and has been pruned, so now the current * subproblem is other branch; * 2 - both branches are hopeless and have been pruned; new subproblem * selection is needed to continue the search. */ static int branch_on(glp_tree *T, int j, int next) { glp_prob *mip = T->mip; IOSNPD *node; int m = mip->m; int n = mip->n; int type, dn_type, up_type, dn_bad, up_bad, p, ret, clone[1+2]; double lb, ub, beta, new_ub, new_lb, dn_lp, up_lp, dn_bnd, up_bnd; /* determine bounds and value of x[j] in optimal solution to LP relaxation of the current subproblem */ xassert(1 <= j && j <= n); type = mip->col[j]->type; lb = mip->col[j]->lb; ub = mip->col[j]->ub; beta = mip->col[j]->prim; /* determine new bounds of x[j] for down- and up-branches */ new_ub = floor(beta); new_lb = ceil(beta); switch (type) { case GLP_FR: dn_type = GLP_UP; up_type = GLP_LO; break; case GLP_LO: xassert(lb <= new_ub); dn_type = (lb == new_ub ? GLP_FX : GLP_DB); xassert(lb + 1.0 <= new_lb); up_type = GLP_LO; break; case GLP_UP: xassert(new_ub <= ub - 1.0); dn_type = GLP_UP; xassert(new_lb <= ub); up_type = (new_lb == ub ? GLP_FX : GLP_DB); break; case GLP_DB: xassert(lb <= new_ub && new_ub <= ub - 1.0); dn_type = (lb == new_ub ? GLP_FX : GLP_DB); xassert(lb + 1.0 <= new_lb && new_lb <= ub); up_type = (new_lb == ub ? GLP_FX : GLP_DB); break; default: xassert(type != type); } /* compute local bounds to LP relaxation for both branches */ ios_eval_degrad(T, j, &dn_lp, &up_lp); /* and improve them by rounding */ dn_bnd = ios_round_bound(T, dn_lp); up_bnd = ios_round_bound(T, up_lp); /* check local bounds for down- and up-branches */ dn_bad = !ios_is_hopeful(T, dn_bnd); up_bad = !ios_is_hopeful(T, up_bnd); if (dn_bad && up_bad) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Both down- and up-branches are hopeless\n"); ret = 2; goto done; } else if (up_bad) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Up-branch is hopeless\n"); glp_set_col_bnds(mip, j, dn_type, lb, new_ub); T->curr->lp_obj = dn_lp; if (mip->dir == GLP_MIN) { if (T->curr->bound < dn_bnd) T->curr->bound = dn_bnd; } else if (mip->dir == GLP_MAX) { if (T->curr->bound > dn_bnd) T->curr->bound = dn_bnd; } else xassert(mip != mip); ret = 1; goto done; } else if (dn_bad) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Down-branch is hopeless\n"); glp_set_col_bnds(mip, j, up_type, new_lb, ub); T->curr->lp_obj = up_lp; if (mip->dir == GLP_MIN) { if (T->curr->bound < up_bnd) T->curr->bound = up_bnd; } else if (mip->dir == GLP_MAX) { if (T->curr->bound > up_bnd) T->curr->bound = up_bnd; } else xassert(mip != mip); ret = 1; goto done; } /* both down- and up-branches seem to be hopeful */ if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Branching on column %d, primal value is %.9e\n", j, beta); /* determine the reference number of the current subproblem */ xassert(T->curr != NULL); p = T->curr->p; T->curr->br_var = j; T->curr->br_val = beta; /* freeze the current subproblem */ ios_freeze_node(T); /* create two clones of the current subproblem; the first clone begins the down-branch, the second one begins the up-branch */ ios_clone_node(T, p, 2, clone); if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Node %d begins down branch, node %d begins up branch " "\n", clone[1], clone[2]); /* set new upper bound of j-th column in the down-branch */ node = T->slot[clone[1]].node; xassert(node != NULL); xassert(node->up != NULL); xassert(node->b_ptr == NULL); node->b_ptr = dmp_get_atom(T->pool, sizeof(IOSBND)); node->b_ptr->k = m + j; node->b_ptr->type = (unsigned char)dn_type; node->b_ptr->lb = lb; node->b_ptr->ub = new_ub; node->b_ptr->next = NULL; node->lp_obj = dn_lp; if (mip->dir == GLP_MIN) { if (node->bound < dn_bnd) node->bound = dn_bnd; } else if (mip->dir == GLP_MAX) { if (node->bound > dn_bnd) node->bound = dn_bnd; } else xassert(mip != mip); /* set new lower bound of j-th column in the up-branch */ node = T->slot[clone[2]].node; xassert(node != NULL); xassert(node->up != NULL); xassert(node->b_ptr == NULL); node->b_ptr = dmp_get_atom(T->pool, sizeof(IOSBND)); node->b_ptr->k = m + j; node->b_ptr->type = (unsigned char)up_type; node->b_ptr->lb = new_lb; node->b_ptr->ub = ub; node->b_ptr->next = NULL; node->lp_obj = up_lp; if (mip->dir == GLP_MIN) { if (node->bound < up_bnd) node->bound = up_bnd; } else if (mip->dir == GLP_MAX) { if (node->bound > up_bnd) node->bound = up_bnd; } else xassert(mip != mip); /* suggest the subproblem to be solved next */ xassert(T->child == 0); if (next == GLP_NO_BRNCH) T->child = 0; else if (next == GLP_DN_BRNCH) T->child = clone[1]; else if (next == GLP_UP_BRNCH) T->child = clone[2]; else xassert(next != next); ret = 0; done: return ret; } /*********************************************************************** * cleanup_the_tree - prune hopeless branches from the tree * * This routine walks through the active list and checks the local * bound for every active subproblem. If the local bound indicates that * the subproblem cannot have integer optimal solution better than the * incumbent objective value, the routine deletes such subproblem that, * in turn, involves pruning the corresponding branch of the tree. */ static void cleanup_the_tree(glp_tree *T) { IOSNPD *node, *next_node; int count = 0; /* the global bound must exist */ xassert(T->mip->mip_stat == GLP_FEAS); /* walk through the list of active subproblems */ for (node = T->head; node != NULL; node = next_node) { /* deleting some active problem node may involve deleting its parents recursively; however, all its parents being created *before* it are always *precede* it in the node list, so the next problem node is never affected by such deletion */ next_node = node->next; /* if the branch is hopeless, prune it */ if (!is_branch_hopeful(T, node->p)) ios_delete_node(T, node->p), count++; } if (T->parm->msg_lev >= GLP_MSG_DBG) { if (count == 1) xprintf("One hopeless branch has been pruned\n"); else if (count > 1) xprintf("%d hopeless branches have been pruned\n", count); } return; } /**********************************************************************/ static void generate_cuts(glp_tree *T) { /* generate generic cuts with built-in generators */ if (!(T->parm->mir_cuts == GLP_ON || T->parm->gmi_cuts == GLP_ON || T->parm->cov_cuts == GLP_ON || T->parm->clq_cuts == GLP_ON)) goto done; #if 1 /* 20/IX-2008 */ { int i, max_cuts, added_cuts; max_cuts = T->n; if (max_cuts < 1000) max_cuts = 1000; added_cuts = 0; for (i = T->orig_m+1; i <= T->mip->m; i++) { if (T->mip->row[i]->origin == GLP_RF_CUT) added_cuts++; } /* xprintf("added_cuts = %d\n", added_cuts); */ if (added_cuts >= max_cuts) goto done; } #endif /* generate and add to POOL all cuts violated by x* */ if (T->parm->gmi_cuts == GLP_ON) { if (T->curr->changed < 5) ios_gmi_gen(T); } if (T->parm->mir_cuts == GLP_ON) { xassert(T->mir_gen != NULL); ios_mir_gen(T, T->mir_gen); } if (T->parm->cov_cuts == GLP_ON) { /* cover cuts works well along with mir cuts */ /*if (T->round <= 5)*/ ios_cov_gen(T); } if (T->parm->clq_cuts == GLP_ON) { if (T->clq_gen != NULL) { if (T->curr->level == 0 && T->curr->changed < 50 || T->curr->level > 0 && T->curr->changed < 5) ios_clq_gen(T, T->clq_gen); } } done: return; } /**********************************************************************/ static void remove_cuts(glp_tree *T) { /* remove inactive cuts (some valueable globally valid cut might be saved in the global cut pool) */ int i, cnt = 0, *num = NULL; xassert(T->curr != NULL); for (i = T->orig_m+1; i <= T->mip->m; i++) { if (T->mip->row[i]->origin == GLP_RF_CUT && T->mip->row[i]->level == T->curr->level && T->mip->row[i]->stat == GLP_BS) { if (num == NULL) num = xcalloc(1+T->mip->m, sizeof(int)); num[++cnt] = i; } } if (cnt > 0) { glp_del_rows(T->mip, cnt, num); #if 0 xprintf("%d inactive cut(s) removed\n", cnt); #endif xfree(num); xassert(glp_factorize(T->mip) == 0); } return; } /**********************************************************************/ static void display_cut_info(glp_tree *T) { glp_prob *mip = T->mip; int i, gmi = 0, mir = 0, cov = 0, clq = 0, app = 0; for (i = mip->m; i > 0; i--) { GLPROW *row; row = mip->row[i]; /* if (row->level < T->curr->level) break; */ if (row->origin == GLP_RF_CUT) { if (row->klass == GLP_RF_GMI) gmi++; else if (row->klass == GLP_RF_MIR) mir++; else if (row->klass == GLP_RF_COV) cov++; else if (row->klass == GLP_RF_CLQ) clq++; else app++; } } xassert(T->curr != NULL); if (gmi + mir + cov + clq + app > 0) { xprintf("Cuts on level %d:", T->curr->level); if (gmi > 0) xprintf(" gmi = %d;", gmi); if (mir > 0) xprintf(" mir = %d;", mir); if (cov > 0) xprintf(" cov = %d;", cov); if (clq > 0) xprintf(" clq = %d;", clq); if (app > 0) xprintf(" app = %d;", app); xprintf("\n"); } return; } /*********************************************************************** * NAME * * ios_driver - branch-and-cut driver * * SYNOPSIS * * #include "glpios.h" * int ios_driver(glp_tree *T); * * DESCRIPTION * * The routine ios_driver is a branch-and-cut driver. It controls the * MIP solution process. * * RETURNS * * 0 The MIP problem instance has been successfully solved. This code * does not necessarily mean that the solver has found optimal * solution. It only means that the solution process was successful. * * GLP_EFAIL * The search was prematurely terminated due to the solver failure. * * GLP_EMIPGAP * The search was prematurely terminated, because the relative mip * gap tolerance has been reached. * * GLP_ETMLIM * The search was prematurely terminated, because the time limit has * been exceeded. * * GLP_ESTOP * The search was prematurely terminated by application. */ int ios_driver(glp_tree *T) { int p, curr_p, p_stat, d_stat, ret; #if 1 /* carry out to glp_tree */ int pred_p = 0; /* if the current subproblem has been just created due to branching, pred_p is the reference number of its parent subproblem, otherwise pred_p is zero */ #endif glp_long ttt = T->tm_beg; #if 0 ((glp_iocp *)T->parm)->msg_lev = GLP_MSG_DBG; #endif /* on entry to the B&B driver it is assumed that the active list contains the only active (i.e. root) subproblem, which is the original MIP problem to be solved */ loop: /* main loop starts here */ /* at this point the current subproblem does not exist */ xassert(T->curr == NULL); /* if the active list is empty, the search is finished */ if (T->head == NULL) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Active list is empty!\n"); xassert(dmp_in_use(T->pool).lo == 0); ret = 0; goto done; } /* select some active subproblem to continue the search */ xassert(T->next_p == 0); /* let the application program select subproblem */ if (T->parm->cb_func != NULL) { xassert(T->reason == 0); T->reason = GLP_ISELECT; T->parm->cb_func(T, T->parm->cb_info); T->reason = 0; if (T->stop) { ret = GLP_ESTOP; goto done; } } if (T->next_p != 0) { /* the application program has selected something */ ; } else if (T->a_cnt == 1) { /* the only active subproblem exists, so select it */ xassert(T->head->next == NULL); T->next_p = T->head->p; } else if (T->child != 0) { /* select one of branching childs suggested by the branching heuristic */ T->next_p = T->child; } else { /* select active subproblem as specified by the backtracking technique option */ T->next_p = ios_choose_node(T); } /* the active subproblem just selected becomes current */ ios_revive_node(T, T->next_p); T->next_p = T->child = 0; /* invalidate pred_p, if it is not the reference number of the parent of the current subproblem */ if (T->curr->up != NULL && T->curr->up->p != pred_p) pred_p = 0; /* determine the reference number of the current subproblem */ p = T->curr->p; if (T->parm->msg_lev >= GLP_MSG_DBG) { xprintf("-----------------------------------------------------" "-------------------\n"); xprintf("Processing node %d at level %d\n", p, T->curr->level); } /* if it is the root subproblem, initialize cut generators */ if (p == 1) { if (T->parm->gmi_cuts == GLP_ON) { if (T->parm->msg_lev >= GLP_MSG_ALL) xprintf("Gomory's cuts enabled\n"); } if (T->parm->mir_cuts == GLP_ON) { if (T->parm->msg_lev >= GLP_MSG_ALL) xprintf("MIR cuts enabled\n"); xassert(T->mir_gen == NULL); T->mir_gen = ios_mir_init(T); } if (T->parm->cov_cuts == GLP_ON) { if (T->parm->msg_lev >= GLP_MSG_ALL) xprintf("Cover cuts enabled\n"); } if (T->parm->clq_cuts == GLP_ON) { xassert(T->clq_gen == NULL); if (T->parm->msg_lev >= GLP_MSG_ALL) xprintf("Clique cuts enabled\n"); T->clq_gen = ios_clq_init(T); } } more: /* minor loop starts here */ /* at this point the current subproblem needs either to be solved for the first time or re-optimized due to reformulation */ /* display current progress of the search */ if (T->parm->msg_lev >= GLP_MSG_DBG || T->parm->msg_lev >= GLP_MSG_ON && (double)(T->parm->out_frq - 1) <= 1000.0 * xdifftime(xtime(), T->tm_lag)) show_progress(T, 0); if (T->parm->msg_lev >= GLP_MSG_ALL && xdifftime(xtime(), ttt) >= 60.0) { glp_long total; glp_mem_usage(NULL, NULL, &total, NULL); xprintf("Time used: %.1f secs. Memory used: %.1f Mb.\n", xdifftime(xtime(), T->tm_beg), xltod(total) / 1048576.0); ttt = xtime(); } /* check the mip gap */ if (T->parm->mip_gap > 0.0 && ios_relative_gap(T) <= T->parm->mip_gap) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Relative gap tolerance reached; search terminated " "\n"); ret = GLP_EMIPGAP; goto done; } /* check if the time limit has been exhausted */ if (T->parm->tm_lim < INT_MAX && (double)(T->parm->tm_lim - 1) <= 1000.0 * xdifftime(xtime(), T->tm_beg)) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Time limit exhausted; search terminated\n"); ret = GLP_ETMLIM; goto done; } /* let the application program preprocess the subproblem */ if (T->parm->cb_func != NULL) { xassert(T->reason == 0); T->reason = GLP_IPREPRO; T->parm->cb_func(T, T->parm->cb_info); T->reason = 0; if (T->stop) { ret = GLP_ESTOP; goto done; } } /* perform basic preprocessing */ if (T->parm->pp_tech == GLP_PP_NONE) ; else if (T->parm->pp_tech == GLP_PP_ROOT) { if (T->curr->level == 0) { if (ios_preprocess_node(T, 100)) goto fath; } } else if (T->parm->pp_tech == GLP_PP_ALL) { if (ios_preprocess_node(T, T->curr->level == 0 ? 100 : 10)) goto fath; } else xassert(T != T); /* preprocessing may improve the global bound */ if (!is_branch_hopeful(T, p)) { xprintf("*** not tested yet ***\n"); goto fath; } /* solve LP relaxation of the current subproblem */ if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Solving LP relaxation...\n"); ret = ios_solve_node(T); if (!(ret == 0 || ret == GLP_EOBJLL || ret == GLP_EOBJUL)) { if (T->parm->msg_lev >= GLP_MSG_ERR) xprintf("ios_driver: unable to solve current LP relaxation;" " glp_simplex returned %d\n", ret); ret = GLP_EFAIL; goto done; } /* analyze status of the basic solution to LP relaxation found */ p_stat = T->mip->pbs_stat; d_stat = T->mip->dbs_stat; if (p_stat == GLP_FEAS && d_stat == GLP_FEAS) { /* LP relaxation has optimal solution */ if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Found optimal solution to LP relaxation\n"); } else if (d_stat == GLP_NOFEAS) { /* LP relaxation has no dual feasible solution */ /* since the current subproblem cannot have a larger feasible region than its parent, there is something wrong */ if (T->parm->msg_lev >= GLP_MSG_ERR) xprintf("ios_driver: current LP relaxation has no dual feas" "ible solution\n"); ret = GLP_EFAIL; goto done; } else if (p_stat == GLP_INFEAS && d_stat == GLP_FEAS) { /* LP relaxation has no primal solution which is better than the incumbent objective value */ xassert(T->mip->mip_stat == GLP_FEAS); if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("LP relaxation has no solution better than incumben" "t objective value\n"); /* prune the branch */ goto fath; } else if (p_stat == GLP_NOFEAS) { /* LP relaxation has no primal feasible solution */ if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("LP relaxation has no feasible solution\n"); /* prune the branch */ goto fath; } else { /* other cases cannot appear */ xassert(T->mip != T->mip); } /* at this point basic solution to LP relaxation of the current subproblem is optimal */ xassert(p_stat == GLP_FEAS && d_stat == GLP_FEAS); xassert(T->curr != NULL); T->curr->lp_obj = T->mip->obj_val; /* thus, it defines a local bound to integer optimal solution of the current subproblem */ { double bound = T->mip->obj_val; /* some local bound to the current subproblem could be already set before, so we should only improve it */ bound = ios_round_bound(T, bound); if (T->mip->dir == GLP_MIN) { if (T->curr->bound < bound) T->curr->bound = bound; } else if (T->mip->dir == GLP_MAX) { if (T->curr->bound > bound) T->curr->bound = bound; } else xassert(T->mip != T->mip); if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Local bound is %.9e\n", bound); } /* if the local bound indicates that integer optimal solution of the current subproblem cannot be better than the global bound, prune the branch */ if (!is_branch_hopeful(T, p)) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Current branch is hopeless and can be pruned\n"); goto fath; } /* let the application program generate additional rows ("lazy" constraints) */ xassert(T->reopt == 0); xassert(T->reinv == 0); if (T->parm->cb_func != NULL) { xassert(T->reason == 0); T->reason = GLP_IROWGEN; T->parm->cb_func(T, T->parm->cb_info); T->reason = 0; if (T->stop) { ret = GLP_ESTOP; goto done; } if (T->reopt) { /* some rows were added; re-optimization is needed */ T->reopt = T->reinv = 0; goto more; } if (T->reinv) { /* no rows were added, however, some inactive rows were removed */ T->reinv = 0; xassert(glp_factorize(T->mip) == 0); } } /* check if the basic solution is integer feasible */ check_integrality(T); /* if the basic solution satisfies to all integrality conditions, it is a new, better integer feasible solution */ if (T->curr->ii_cnt == 0) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("New integer feasible solution found\n"); if (T->parm->msg_lev >= GLP_MSG_ALL) display_cut_info(T); record_solution(T); if (T->parm->msg_lev >= GLP_MSG_ON) show_progress(T, 1); /* make the application program happy */ if (T->parm->cb_func != NULL) { xassert(T->reason == 0); T->reason = GLP_IBINGO; T->parm->cb_func(T, T->parm->cb_info); T->reason = 0; if (T->stop) { ret = GLP_ESTOP; goto done; } } /* since the current subproblem has been fathomed, prune its branch */ goto fath; } /* at this point basic solution to LP relaxation of the current subproblem is optimal, but integer infeasible */ /* try to fix some non-basic structural variables of integer kind on their current bounds due to reduced costs */ if (T->mip->mip_stat == GLP_FEAS) fix_by_red_cost(T); /* let the application program try to find some solution to the original MIP with a primal heuristic */ if (T->parm->cb_func != NULL) { xassert(T->reason == 0); T->reason = GLP_IHEUR; T->parm->cb_func(T, T->parm->cb_info); T->reason = 0; if (T->stop) { ret = GLP_ESTOP; goto done; } /* check if the current branch became hopeless */ if (!is_branch_hopeful(T, p)) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Current branch became hopeless and can be prune" "d\n"); goto fath; } } /* try to find solution with the feasibility pump heuristic */ if (T->parm->fp_heur) { xassert(T->reason == 0); T->reason = GLP_IHEUR; ios_feas_pump(T); T->reason = 0; /* check if the current branch became hopeless */ if (!is_branch_hopeful(T, p)) { if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Current branch became hopeless and can be prune" "d\n"); goto fath; } } /* it's time to generate cutting planes */ xassert(T->local != NULL); xassert(T->local->size == 0); /* let the application program generate some cuts; note that it can add cuts either to the local cut pool or directly to the current subproblem */ if (T->parm->cb_func != NULL) { xassert(T->reason == 0); T->reason = GLP_ICUTGEN; T->parm->cb_func(T, T->parm->cb_info); T->reason = 0; if (T->stop) { ret = GLP_ESTOP; goto done; } } /* try to generate generic cuts with built-in generators (as suggested by Matteo Fischetti et al. the built-in cuts are not generated at each branching node; an intense attempt of generating new cuts is only made at the root node, and then a moderate effort is spent after each backtracking step) */ if (T->curr->level == 0 || pred_p == 0) { xassert(T->reason == 0); T->reason = GLP_ICUTGEN; generate_cuts(T); T->reason = 0; } /* if the local cut pool is not empty, select useful cuts and add them to the current subproblem */ if (T->local->size > 0) { xassert(T->reason == 0); T->reason = GLP_ICUTGEN; ios_process_cuts(T); T->reason = 0; } /* clear the local cut pool */ ios_clear_pool(T, T->local); /* perform re-optimization, if necessary */ if (T->reopt) { T->reopt = 0; T->curr->changed++; goto more; } /* no cuts were generated; remove inactive cuts */ remove_cuts(T); if (T->parm->msg_lev >= GLP_MSG_ALL && T->curr->level == 0) display_cut_info(T); /* update history information used on pseudocost branching */ if (T->pcost != NULL) ios_pcost_update(T); /* it's time to perform branching */ xassert(T->br_var == 0); xassert(T->br_sel == 0); /* let the application program choose variable to branch on */ if (T->parm->cb_func != NULL) { xassert(T->reason == 0); xassert(T->br_var == 0); xassert(T->br_sel == 0); T->reason = GLP_IBRANCH; T->parm->cb_func(T, T->parm->cb_info); T->reason = 0; if (T->stop) { ret = GLP_ESTOP; goto done; } } /* if nothing has been chosen, choose some variable as specified by the branching technique option */ if (T->br_var == 0) T->br_var = ios_choose_var(T, &T->br_sel); /* perform actual branching */ curr_p = T->curr->p; ret = branch_on(T, T->br_var, T->br_sel); T->br_var = T->br_sel = 0; if (ret == 0) { /* both branches have been created */ pred_p = curr_p; goto loop; } else if (ret == 1) { /* one branch is hopeless and has been pruned, so now the current subproblem is other branch */ /* the current subproblem should be considered as a new one, since one bound of the branching variable was changed */ T->curr->solved = T->curr->changed = 0; goto more; } else if (ret == 2) { /* both branches are hopeless and have been pruned; new subproblem selection is needed to continue the search */ goto fath; } else xassert(ret != ret); fath: /* the current subproblem has been fathomed */ if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("Node %d fathomed\n", p); /* freeze the current subproblem */ ios_freeze_node(T); /* and prune the corresponding branch of the tree */ ios_delete_node(T, p); /* if a new integer feasible solution has just been found, other branches may become hopeless and therefore must be pruned */ if (T->mip->mip_stat == GLP_FEAS) cleanup_the_tree(T); /* new subproblem selection is needed due to backtracking */ pred_p = 0; goto loop; done: /* display progress of the search on exit from the solver */ if (T->parm->msg_lev >= GLP_MSG_ON) show_progress(T, 0); if (T->mir_gen != NULL) ios_mir_term(T->mir_gen), T->mir_gen = NULL; if (T->clq_gen != NULL) ios_clq_term(T->clq_gen), T->clq_gen = NULL; /* return to the calling program */ return ret; } /* eof */ sources_5316/external/glpk/glpnet02.c0000644000176700017670000002443611401660400016302 0ustar paulpaul/* glpnet02.c (permutations to block triangular form) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * This code is the result of translation of the Fortran subroutines * MC13D and MC13E associated with the following paper: * * I.S.Duff, J.K.Reid, Algorithm 529: Permutations to block triangular * form, ACM Trans. on Math. Softw. 4 (1978), 189-192. * * Use of ACM Algorithms is subject to the ACM Software Copyright and * License Agreement. See . * * The translation was made by Andrew Makhorin . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpnet.h" /*********************************************************************** * NAME * * mc13d - permutations to block triangular form * * SYNOPSIS * * #include "glpnet.h" * int mc13d(int n, const int icn[], const int ip[], const int lenr[], * int ior[], int ib[], int lowl[], int numb[], int prev[]); * * DESCRIPTION * * Given the column numbers of the nonzeros in each row of the sparse * matrix, the routine mc13d finds a symmetric permutation that makes * the matrix block lower triangular. * * INPUT PARAMETERS * * n order of the matrix. * * icn array containing the column indices of the non-zeros. Those * belonging to a single row must be contiguous but the ordering * of column indices within each row is unimportant and wasted * space between rows is permitted. * * ip ip[i], i = 1,2,...,n, is the position in array icn of the * first column index of a non-zero in row i. * * lenr lenr[i], i = 1,2,...,n, is the number of non-zeros in row i. * * OUTPUT PARAMETERS * * ior ior[i], i = 1,2,...,n, gives the position on the original * ordering of the row or column which is in position i in the * permuted form. * * ib ib[i], i = 1,2,...,num, is the row number in the permuted * matrix of the beginning of block i, 1 <= num <= n. * * WORKING ARRAYS * * arp working array of length [1+n], where arp[0] is not used. * arp[i] is one less than the number of unsearched edges leaving * node i. At the end of the algorithm it is set to a permutation * which puts the matrix in block lower triangular form. * * ib working array of length [1+n], where ib[0] is not used. * ib[i] is the position in the ordering of the start of the ith * block. ib[n+1-i] holds the node number of the ith node on the * stack. * * lowl working array of length [1+n], where lowl[0] is not used. * lowl[i] is the smallest stack position of any node to which a * path from node i has been found. It is set to n+1 when node i * is removed from the stack. * * numb working array of length [1+n], where numb[0] is not used. * numb[i] is the position of node i in the stack if it is on it, * is the permuted order of node i for those nodes whose final * position has been found and is otherwise zero. * * prev working array of length [1+n], where prev[0] is not used. * prev[i] is the node at the end of the path when node i was * placed on the stack. * * RETURNS * * The routine mc13d returns num, the number of blocks found. */ int mc13d(int n, const int icn[], const int ip[], const int lenr[], int ior[], int ib[], int lowl[], int numb[], int prev[]) { int *arp = ior; int dummy, i, i1, i2, icnt, ii, isn, ist, ist1, iv, iw, j, lcnt, nnm1, num, stp; /* icnt is the number of nodes whose positions in final ordering have been found. */ icnt = 0; /* num is the number of blocks that have been found. */ num = 0; nnm1 = n + n - 1; /* Initialization of arrays. */ for (j = 1; j <= n; j++) { numb[j] = 0; arp[j] = lenr[j] - 1; } for (isn = 1; isn <= n; isn++) { /* Look for a starting node. */ if (numb[isn] != 0) continue; iv = isn; /* ist is the number of nodes on the stack ... it is the stack pointer. */ ist = 1; /* Put node iv at beginning of stack. */ lowl[iv] = numb[iv] = 1; ib[n] = iv; /* The body of this loop puts a new node on the stack or backtracks. */ for (dummy = 1; dummy <= nnm1; dummy++) { i1 = arp[iv]; /* Have all edges leaving node iv been searched? */ if (i1 >= 0) { i2 = ip[iv] + lenr[iv] - 1; i1 = i2 - i1; /* Look at edges leaving node iv until one enters a new node or all edges are exhausted. */ for (ii = i1; ii <= i2; ii++) { iw = icn[ii]; /* Has node iw been on stack already? */ if (numb[iw] == 0) goto L70; /* Update value of lowl[iv] if necessary. */ if (lowl[iw] < lowl[iv]) lowl[iv] = lowl[iw]; } /* There are no more edges leaving node iv. */ arp[iv] = -1; } /* Is node iv the root of a block? */ if (lowl[iv] < numb[iv]) goto L60; /* Order nodes in a block. */ num++; ist1 = n + 1 - ist; lcnt = icnt + 1; /* Peel block off the top of the stack starting at the top and working down to the root of the block. */ for (stp = ist1; stp <= n; stp++) { iw = ib[stp]; lowl[iw] = n + 1; numb[iw] = ++icnt; if (iw == iv) break; } ist = n - stp; ib[num] = lcnt; /* Are there any nodes left on the stack? */ if (ist != 0) goto L60; /* Have all the nodes been ordered? */ if (icnt < n) break; goto L100; L60: /* Backtrack to previous node on path. */ iw = iv; iv = prev[iv]; /* Update value of lowl[iv] if necessary. */ if (lowl[iw] < lowl[iv]) lowl[iv] = lowl[iw]; continue; L70: /* Put new node on the stack. */ arp[iv] = i2 - ii - 1; prev[iw] = iv; iv = iw; lowl[iv] = numb[iv] = ++ist; ib[n+1-ist] = iv; } } L100: /* Put permutation in the required form. */ for (i = 1; i <= n; i++) arp[numb[i]] = i; return num; } /**********************************************************************/ #if 0 #include "glplib.h" void test(int n, int ipp); int main(void) { /* test program for routine mc13d */ test( 1, 0); test( 2, 1); test( 2, 2); test( 3, 3); test( 4, 4); test( 5, 10); test(10, 10); test(10, 20); test(20, 20); test(20, 50); test(50, 50); test(50, 200); return 0; } void fa01bs(int max, int *nrand); void setup(int n, char a[1+50][1+50], int ip[], int icn[], int lenr[]); void test(int n, int ipp) { int ip[1+50], icn[1+1000], ior[1+50], ib[1+51], iw[1+150], lenr[1+50]; char a[1+50][1+50], hold[1+100]; int i, ii, iblock, ij, index, j, jblock, jj, k9, num; xprintf("\n\n\nMatrix is of order %d and has %d off-diagonal non-" "zeros\n", n, ipp); for (j = 1; j <= n; j++) { for (i = 1; i <= n; i++) a[i][j] = 0; a[j][j] = 1; } for (k9 = 1; k9 <= ipp; k9++) { /* these statements should be replaced by calls to your favorite random number generator to place two pseudo-random numbers between 1 and n in the variables i and j */ for (;;) { fa01bs(n, &i); fa01bs(n, &j); if (!a[i][j]) break; } a[i][j] = 1; } /* setup converts matrix a[i,j] to required sparsity-oriented storage format */ setup(n, a, ip, icn, lenr); num = mc13d(n, icn, ip, lenr, ior, ib, &iw[0], &iw[n], &iw[n+n]); /* output reordered matrix with blocking to improve clarity */ xprintf("\nThe reordered matrix which has %d block%s is of the fo" "rm\n", num, num == 1 ? "" : "s"); ib[num+1] = n + 1; index = 100; iblock = 1; for (i = 1; i <= n; i++) { for (ij = 1; ij <= index; ij++) hold[ij] = ' '; if (i == ib[iblock]) { xprintf("\n"); iblock++; } jblock = 1; index = 0; for (j = 1; j <= n; j++) { if (j == ib[jblock]) { hold[++index] = ' '; jblock++; } ii = ior[i]; jj = ior[j]; hold[++index] = (char)(a[ii][jj] ? 'X' : '0'); } xprintf("%.*s\n", index, &hold[1]); } xprintf("\nThe starting point for each block is given by\n"); for (i = 1; i <= num; i++) { if ((i - 1) % 12 == 0) xprintf("\n"); xprintf(" %4d", ib[i]); } xprintf("\n"); return; } void setup(int n, char a[1+50][1+50], int ip[], int icn[], int lenr[]) { int i, j, ind; for (i = 1; i <= n; i++) lenr[i] = 0; ind = 1; for (i = 1; i <= n; i++) { ip[i] = ind; for (j = 1; j <= n; j++) { if (a[i][j]) { lenr[i]++; icn[ind++] = j; } } } return; } double g = 1431655765.0; double fa01as(int i) { /* random number generator */ g = fmod(g * 9228907.0, 4294967296.0); if (i >= 0) return g / 4294967296.0; else return 2.0 * g / 4294967296.0 - 1.0; } void fa01bs(int max, int *nrand) { *nrand = (int)(fa01as(1) * (double)max) + 1; return; } #endif /* eof */ sources_5316/external/glpk/glpmps.c0000644000176700017670000013325011632723645016165 0ustar paulpaul/* glpmps.c (MPS format routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_init_mpscp - initialize MPS format control parameters * * SYNOPSIS * * void glp_init_mpscp(glp_mpscp *parm); * * DESCRIPTION * * The routine glp_init_mpscp initializes control parameters, which are * used by the MPS input/output routines glp_read_mps and glp_write_mps, * with default values. * * Default values of the control parameters are stored in the glp_mpscp * structure, which the parameter parm points to. */ void glp_init_mpscp(glp_mpscp *parm) { parm->blank = '\0'; parm->obj_name = NULL; parm->tol_mps = 1e-12; return; } static void check_parm(const char *func, const glp_mpscp *parm) { /* check control parameters */ if (!(0x00 <= parm->blank && parm->blank <= 0xFF) || !(parm->blank == '\0' || isprint(parm->blank))) xerror("%s: blank = 0x%02X; invalid parameter\n", func, parm->blank); if (!(parm->obj_name == NULL || strlen(parm->obj_name) <= 255)) xerror("%s: obj_name = \"%.12s...\"; parameter too long\n", func, parm->obj_name); if (!(0.0 <= parm->tol_mps && parm->tol_mps < 1.0)) xerror("%s: tol_mps = %g; invalid parameter\n", func, parm->tol_mps); return; } /*********************************************************************** * NAME * * glp_read_mps - read problem data in MPS format * * SYNOPSIS * * int glp_read_mps(glp_prob *P, int fmt, const glp_mpscp *parm, * const char *fname); * * DESCRIPTION * * The routine glp_read_mps reads problem data in MPS format from a * text file. * * The parameter fmt specifies the version of MPS format: * * GLP_MPS_DECK - fixed (ancient) MPS format; * GLP_MPS_FILE - free (modern) MPS format. * * The parameter parm is a pointer to the structure glp_mpscp, which * specifies control parameters used by the routine. If parm is NULL, * the routine uses default settings. * * The character string fname specifies a name of the text file to be * read. * * Note that before reading data the current content of the problem * object is completely erased with the routine glp_erase_prob. * * RETURNS * * If the operation was successful, the routine glp_read_mps returns * zero. Otherwise, it prints an error message and returns non-zero. */ struct csa { /* common storage area */ glp_prob *P; /* pointer to problem object */ int deck; /* MPS format (0 - free, 1 - fixed) */ const glp_mpscp *parm; /* pointer to control parameters */ const char *fname; /* name of input MPS file */ XFILE *fp; /* stream assigned to input MPS file */ jmp_buf jump; /* label for go to in case of error */ int recno; /* current record (card) number */ int recpos; /* current record (card) position */ int c; /* current character */ int fldno; /* current field number */ char field[255+1]; /* current field content */ int w80; /* warning 'record must not be longer than 80 chars' issued */ int wef; /* warning 'extra fields detected beyond field 6' issued */ int obj_row; /* objective row number */ void *work1, *work2, *work3; /* working arrays */ }; static void error(struct csa *csa, const char *fmt, ...) { /* print error message and terminate processing */ va_list arg; xprintf("%s:%d: ", csa->fname, csa->recno); va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); longjmp(csa->jump, 1); /* no return */ } static void warning(struct csa *csa, const char *fmt, ...) { /* print warning message and continue processing */ va_list arg; xprintf("%s:%d: warning: ", csa->fname, csa->recno); va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); return; } static void read_char(struct csa *csa) { /* read next character */ int c; if (csa->c == '\n') csa->recno++, csa->recpos = 0; csa->recpos++; read: c = xfgetc(csa->fp); if (c < 0) { if (xferror(csa->fp)) error(csa, "read error - %s\n", xerrmsg()); else if (csa->c == '\n') error(csa, "unexpected end of file\n"); else { warning(csa, "missing final end of line\n"); c = '\n'; } } else if (c == '\n') ; else if (csa->c == '\r') { c = '\r'; goto badc; } else if (csa->deck && c == '\r') { csa->c = '\r'; goto read; } else if (c == ' ') ; else if (isspace(c)) { if (csa->deck) badc: error(csa, "in fixed MPS format white-space character 0x%02" "X is not allowed\n", c); c = ' '; } else if (iscntrl(c)) error(csa, "invalid control character 0x%02X\n", c); if (csa->deck && csa->recpos == 81 && c != '\n' && csa->w80 < 1) { warning(csa, "in fixed MPS format record must not be longer th" "an 80 characters\n"); csa->w80++; } csa->c = c; return; } static int indicator(struct csa *csa, int name) { /* skip comment records and read possible indicator record */ int ret; /* reset current field number */ csa->fldno = 0; loop: /* read the very first character of the next record */ xassert(csa->c == '\n'); read_char(csa); if (csa->c == ' ' || csa->c == '\n') { /* data record */ ret = 0; } else if (csa->c == '*') { /* comment record */ while (csa->c != '\n') read_char(csa); goto loop; } else { /* indicator record */ int len = 0; while (csa->c != ' ' && csa->c != '\n' && len < 12) { csa->field[len++] = (char)csa->c; read_char(csa); } csa->field[len] = '\0'; if (!(strcmp(csa->field, "NAME") == 0 || strcmp(csa->field, "ROWS") == 0 || strcmp(csa->field, "COLUMNS") == 0 || strcmp(csa->field, "RHS") == 0 || strcmp(csa->field, "RANGES") == 0 || strcmp(csa->field, "BOUNDS") == 0 || strcmp(csa->field, "ENDATA") == 0)) error(csa, "invalid indicator record\n"); if (!name) { while (csa->c != '\n') read_char(csa); } ret = 1; } return ret; } static void read_field(struct csa *csa) { /* read next field of the current data record */ csa->fldno++; if (csa->deck) { /* fixed MPS format */ int beg, end, pos; /* determine predefined field positions */ if (csa->fldno == 1) beg = 2, end = 3; else if (csa->fldno == 2) beg = 5, end = 12; else if (csa->fldno == 3) beg = 15, end = 22; else if (csa->fldno == 4) beg = 25, end = 36; else if (csa->fldno == 5) beg = 40, end = 47; else if (csa->fldno == 6) beg = 50, end = 61; else xassert(csa != csa); /* skip blanks preceding the current field */ if (csa->c != '\n') { pos = csa->recpos; while (csa->recpos < beg) { if (csa->c == ' ') ; else if (csa->c == '\n') break; else error(csa, "in fixed MPS format positions %d-%d must " "be blank\n", pos, beg-1); read_char(csa); } } /* skip possible comment beginning in the field 3 or 5 */ if ((csa->fldno == 3 || csa->fldno == 5) && csa->c == '$') { while (csa->c != '\n') read_char(csa); } /* read the current field */ for (pos = beg; pos <= end; pos++) { if (csa->c == '\n') break; csa->field[pos-beg] = (char)csa->c; read_char(csa); } csa->field[pos-beg] = '\0'; strtrim(csa->field); /* skip blanks following the last field */ if (csa->fldno == 6 && csa->c != '\n') { while (csa->recpos <= 72) { if (csa->c == ' ') ; else if (csa->c == '\n') break; else error(csa, "in fixed MPS format positions 62-72 must " "be blank\n"); read_char(csa); } while (csa->c != '\n') read_char(csa); } } else { /* free MPS format */ int len; /* skip blanks preceding the current field */ while (csa->c == ' ') read_char(csa); /* skip possible comment */ if (csa->c == '$') { while (csa->c != '\n') read_char(csa); } /* read the current field */ len = 0; while (!(csa->c == ' ' || csa->c == '\n')) { if (len == 255) error(csa, "length of field %d exceeds 255 characters\n", csa->fldno++); csa->field[len++] = (char)csa->c; read_char(csa); } csa->field[len] = '\0'; /* skip anything following the last field (any extra fields are considered to be comments) */ if (csa->fldno == 6) { while (csa->c == ' ') read_char(csa); if (csa->c != '$' && csa->c != '\n' && csa->wef < 1) { warning(csa, "some extra field(s) detected beyond field " "6; field(s) ignored\n"); csa->wef++; } while (csa->c != '\n') read_char(csa); } } return; } static void patch_name(struct csa *csa, char *name) { /* process embedded blanks in symbolic name */ int blank = csa->parm->blank; if (blank == '\0') { /* remove emedded blanks */ strspx(name); } else { /* replace embedded blanks by specified character */ for (; *name != '\0'; name++) if (*name == ' ') *name = (char)blank; } return; } static double read_number(struct csa *csa) { /* read next field and convert it to floating-point number */ double x; char *s; /* read next field */ read_field(csa); xassert(csa->fldno == 4 || csa->fldno == 6); if (csa->field[0] == '\0') error(csa, "missing numeric value in field %d\n", csa->fldno); /* skip initial spaces of the field */ for (s = csa->field; *s == ' '; s++) ; /* perform conversion */ if (str2num(s, &x) != 0) error(csa, "cannot convert `%s' to floating-point number\n", s); return x; } static void skip_field(struct csa *csa) { /* read and skip next field (assumed to be blank) */ read_field(csa); if (csa->field[0] != '\0') error(csa, "field %d must be blank\n", csa->fldno); return; } static void read_name(struct csa *csa) { /* read NAME indicator record */ if (!(indicator(csa, 1) && strcmp(csa->field, "NAME") == 0)) error(csa, "missing NAME indicator record\n"); /* this indicator record looks like a data record; simulate that fields 1 and 2 were read */ csa->fldno = 2; /* field 3: model name */ read_field(csa), patch_name(csa, csa->field); if (csa->field[0] == '\0') warning(csa, "missing model name in field 3\n"); else glp_set_prob_name(csa->P, csa->field); /* skip anything following field 3 */ while (csa->c != '\n') read_char(csa); return; } static void read_rows(struct csa *csa) { /* read ROWS section */ int i, type; loop: if (indicator(csa, 0)) goto done; /* field 1: row type */ read_field(csa), strspx(csa->field); if (strcmp(csa->field, "N") == 0) type = GLP_FR; else if (strcmp(csa->field, "G") == 0) type = GLP_LO; else if (strcmp(csa->field, "L") == 0) type = GLP_UP; else if (strcmp(csa->field, "E") == 0) type = GLP_FX; else if (csa->field[0] == '\0') error(csa, "missing row type in field 1\n"); else error(csa, "invalid row type in field 1\n"); /* field 2: row name */ read_field(csa), patch_name(csa, csa->field); if (csa->field[0] == '\0') error(csa, "missing row name in field 2\n"); if (glp_find_row(csa->P, csa->field) != 0) error(csa, "row `%s' multiply specified\n", csa->field); i = glp_add_rows(csa->P, 1); glp_set_row_name(csa->P, i, csa->field); glp_set_row_bnds(csa->P, i, type, 0.0, 0.0); /* fields 3, 4, 5, and 6 must be blank */ skip_field(csa); skip_field(csa); skip_field(csa); skip_field(csa); goto loop; done: return; } static void read_columns(struct csa *csa) { /* read COLUMNS section */ int i, j, f, len, kind = GLP_CV, *ind; double aij, *val; char name[255+1], *flag; /* allocate working arrays */ csa->work1 = ind = xcalloc(1+csa->P->m, sizeof(int)); csa->work2 = val = xcalloc(1+csa->P->m, sizeof(double)); csa->work3 = flag = xcalloc(1+csa->P->m, sizeof(char)); memset(&flag[1], 0, csa->P->m); /* no current column exists */ j = 0, len = 0; loop: if (indicator(csa, 0)) goto done; /* field 1 must be blank */ if (csa->deck) { read_field(csa); if (csa->field[0] != '\0') error(csa, "field 1 must be blank\n"); } else csa->fldno++; /* field 2: column or kind name */ read_field(csa), patch_name(csa, csa->field); strcpy(name, csa->field); /* field 3: row name or keyword 'MARKER' */ read_field(csa), patch_name(csa, csa->field); if (strcmp(csa->field, "'MARKER'") == 0) { /* process kind data record */ /* field 4 must be blank */ if (csa->deck) { read_field(csa); if (csa->field[0] != '\0') error(csa, "field 4 must be blank\n"); } else csa->fldno++; /* field 5: keyword 'INTORG' or 'INTEND' */ read_field(csa), patch_name(csa, csa->field); if (strcmp(csa->field, "'INTORG'") == 0) kind = GLP_IV; else if (strcmp(csa->field, "'INTEND'") == 0) kind = GLP_CV; else if (csa->field[0] == '\0') error(csa, "missing keyword in field 5\n"); else error(csa, "invalid keyword in field 5\n"); /* field 6 must be blank */ skip_field(csa); goto loop; } /* process column name specified in field 2 */ if (name[0] == '\0') { /* the same column as in previous data record */ if (j == 0) error(csa, "missing column name in field 2\n"); } else if (j != 0 && strcmp(name, csa->P->col[j]->name) == 0) { /* the same column as in previous data record */ xassert(j != 0); } else { /* store the current column */ if (j != 0) { glp_set_mat_col(csa->P, j, len, ind, val); while (len > 0) flag[ind[len--]] = 0; } /* create new column */ if (glp_find_col(csa->P, name) != 0) error(csa, "column `%s' multiply specified\n", name); j = glp_add_cols(csa->P, 1); glp_set_col_name(csa->P, j, name); glp_set_col_kind(csa->P, j, kind); if (kind == GLP_CV) glp_set_col_bnds(csa->P, j, GLP_LO, 0.0, 0.0); else if (kind == GLP_IV) glp_set_col_bnds(csa->P, j, GLP_DB, 0.0, 1.0); else xassert(kind != kind); } /* process fields 3-4 and 5-6 */ for (f = 3; f <= 5; f += 2) { /* field 3 or 5: row name */ if (f == 3) { if (csa->field[0] == '\0') error(csa, "missing row name in field 3\n"); } else { read_field(csa), patch_name(csa, csa->field); if (csa->field[0] == '\0') { /* if field 5 is blank, field 6 also must be blank */ skip_field(csa); continue; } } i = glp_find_row(csa->P, csa->field); if (i == 0) error(csa, "row `%s' not found\n", csa->field); if (flag[i]) error(csa, "duplicate coefficient in row `%s'\n", csa->field); /* field 4 or 6: coefficient value */ aij = read_number(csa); if (fabs(aij) < csa->parm->tol_mps) aij = 0.0; len++, ind[len] = i, val[len] = aij, flag[i] = 1; } goto loop; done: /* store the last column */ if (j != 0) glp_set_mat_col(csa->P, j, len, ind, val); /* free working arrays */ xfree(ind); xfree(val); xfree(flag); csa->work1 = csa->work2 = csa->work3 = NULL; return; } static void read_rhs(struct csa *csa) { /* read RHS section */ int i, f, v, type; double rhs; char name[255+1], *flag; /* allocate working array */ csa->work3 = flag = xcalloc(1+csa->P->m, sizeof(char)); memset(&flag[1], 0, csa->P->m); /* no current RHS vector exists */ v = 0; loop: if (indicator(csa, 0)) goto done; /* field 1 must be blank */ if (csa->deck) { read_field(csa); if (csa->field[0] != '\0') error(csa, "field 1 must be blank\n"); } else csa->fldno++; /* field 2: RHS vector name */ read_field(csa), patch_name(csa, csa->field); if (csa->field[0] == '\0') { /* the same RHS vector as in previous data record */ if (v == 0) { warning(csa, "missing RHS vector name in field 2\n"); goto blnk; } } else if (v != 0 && strcmp(csa->field, name) == 0) { /* the same RHS vector as in previous data record */ xassert(v != 0); } else blnk: { /* new RHS vector */ if (v != 0) error(csa, "multiple RHS vectors not supported\n"); v++; strcpy(name, csa->field); } /* process fields 3-4 and 5-6 */ for (f = 3; f <= 5; f += 2) { /* field 3 or 5: row name */ read_field(csa), patch_name(csa, csa->field); if (csa->field[0] == '\0') { if (f == 3) error(csa, "missing row name in field 3\n"); else { /* if field 5 is blank, field 6 also must be blank */ skip_field(csa); continue; } } i = glp_find_row(csa->P, csa->field); if (i == 0) error(csa, "row `%s' not found\n", csa->field); if (flag[i]) error(csa, "duplicate right-hand side for row `%s'\n", csa->field); /* field 4 or 6: right-hand side value */ rhs = read_number(csa); if (fabs(rhs) < csa->parm->tol_mps) rhs = 0.0; type = csa->P->row[i]->type; if (type == GLP_FR) { if (i == csa->obj_row) glp_set_obj_coef(csa->P, 0, rhs); else if (rhs != 0.0) warning(csa, "non-zero right-hand side for free row `%s'" " ignored\n", csa->P->row[i]->name); } else glp_set_row_bnds(csa->P, i, type, rhs, rhs); flag[i] = 1; } goto loop; done: /* free working array */ xfree(flag); csa->work3 = NULL; return; } static void read_ranges(struct csa *csa) { /* read RANGES section */ int i, f, v, type; double rhs, rng; char name[255+1], *flag; /* allocate working array */ csa->work3 = flag = xcalloc(1+csa->P->m, sizeof(char)); memset(&flag[1], 0, csa->P->m); /* no current RANGES vector exists */ v = 0; loop: if (indicator(csa, 0)) goto done; /* field 1 must be blank */ if (csa->deck) { read_field(csa); if (csa->field[0] != '\0') error(csa, "field 1 must be blank\n"); } else csa->fldno++; /* field 2: RANGES vector name */ read_field(csa), patch_name(csa, csa->field); if (csa->field[0] == '\0') { /* the same RANGES vector as in previous data record */ if (v == 0) { warning(csa, "missing RANGES vector name in field 2\n"); goto blnk; } } else if (v != 0 && strcmp(csa->field, name) == 0) { /* the same RANGES vector as in previous data record */ xassert(v != 0); } else blnk: { /* new RANGES vector */ if (v != 0) error(csa, "multiple RANGES vectors not supported\n"); v++; strcpy(name, csa->field); } /* process fields 3-4 and 5-6 */ for (f = 3; f <= 5; f += 2) { /* field 3 or 5: row name */ read_field(csa), patch_name(csa, csa->field); if (csa->field[0] == '\0') { if (f == 3) error(csa, "missing row name in field 3\n"); else { /* if field 5 is blank, field 6 also must be blank */ skip_field(csa); continue; } } i = glp_find_row(csa->P, csa->field); if (i == 0) error(csa, "row `%s' not found\n", csa->field); if (flag[i]) error(csa, "duplicate range for row `%s'\n", csa->field); /* field 4 or 6: range value */ rng = read_number(csa); if (fabs(rng) < csa->parm->tol_mps) rng = 0.0; type = csa->P->row[i]->type; if (type == GLP_FR) warning(csa, "range for free row `%s' ignored\n", csa->P->row[i]->name); else if (type == GLP_LO) { rhs = csa->P->row[i]->lb; glp_set_row_bnds(csa->P, i, rhs == 0.0 ? GLP_FX : GLP_DB, rhs, rhs + fabs(rng)); } else if (type == GLP_UP) { rhs = csa->P->row[i]->ub; glp_set_row_bnds(csa->P, i, rhs == 0.0 ? GLP_FX : GLP_DB, rhs - fabs(rng), rhs); } else if (type == GLP_FX) { rhs = csa->P->row[i]->lb; if (rng > 0.0) glp_set_row_bnds(csa->P, i, GLP_DB, rhs, rhs + rng); else if (rng < 0.0) glp_set_row_bnds(csa->P, i, GLP_DB, rhs + rng, rhs); } else xassert(type != type); flag[i] = 1; } goto loop; done: /* free working array */ xfree(flag); csa->work3 = NULL; return; } static void read_bounds(struct csa *csa) { /* read BOUNDS section */ GLPCOL *col; int j, v, mask, data; double bnd, lb, ub; char type[2+1], name[255+1], *flag; /* allocate working array */ csa->work3 = flag = xcalloc(1+csa->P->n, sizeof(char)); memset(&flag[1], 0, csa->P->n); /* no current BOUNDS vector exists */ v = 0; loop: if (indicator(csa, 0)) goto done; /* field 1: bound type */ read_field(csa); if (strcmp(csa->field, "LO") == 0) mask = 0x01, data = 1; else if (strcmp(csa->field, "UP") == 0) mask = 0x10, data = 1; else if (strcmp(csa->field, "FX") == 0) mask = 0x11, data = 1; else if (strcmp(csa->field, "FR") == 0) mask = 0x11, data = 0; else if (strcmp(csa->field, "MI") == 0) mask = 0x01, data = 0; else if (strcmp(csa->field, "PL") == 0) mask = 0x10, data = 0; else if (strcmp(csa->field, "LI") == 0) mask = 0x01, data = 1; else if (strcmp(csa->field, "UI") == 0) mask = 0x10, data = 1; else if (strcmp(csa->field, "BV") == 0) mask = 0x11, data = 0; else if (csa->field[0] == '\0') error(csa, "missing bound type in field 1\n"); else error(csa, "invalid bound type in field 1\n"); strcpy(type, csa->field); /* field 2: BOUNDS vector name */ read_field(csa), patch_name(csa, csa->field); if (csa->field[0] == '\0') { /* the same BOUNDS vector as in previous data record */ if (v == 0) { warning(csa, "missing BOUNDS vector name in field 2\n"); goto blnk; } } else if (v != 0 && strcmp(csa->field, name) == 0) { /* the same BOUNDS vector as in previous data record */ xassert(v != 0); } else blnk: { /* new BOUNDS vector */ if (v != 0) error(csa, "multiple BOUNDS vectors not supported\n"); v++; strcpy(name, csa->field); } /* field 3: column name */ read_field(csa), patch_name(csa, csa->field); if (csa->field[0] == '\0') error(csa, "missing column name in field 3\n"); j = glp_find_col(csa->P, csa->field); if (j == 0) error(csa, "column `%s' not found\n", csa->field); if ((flag[j] & mask) == 0x01) error(csa, "duplicate lower bound for column `%s'\n", csa->field); if ((flag[j] & mask) == 0x10) error(csa, "duplicate upper bound for column `%s'\n", csa->field); xassert((flag[j] & mask) == 0x00); /* field 4: bound value */ if (data) { bnd = read_number(csa); if (fabs(bnd) < csa->parm->tol_mps) bnd = 0.0; } else read_field(csa), bnd = 0.0; /* get current column bounds */ col = csa->P->col[j]; if (col->type == GLP_FR) lb = -DBL_MAX, ub = +DBL_MAX; else if (col->type == GLP_LO) lb = col->lb, ub = +DBL_MAX; else if (col->type == GLP_UP) lb = -DBL_MAX, ub = col->ub; else if (col->type == GLP_DB) lb = col->lb, ub = col->ub; else if (col->type == GLP_FX) lb = ub = col->lb; else xassert(col != col); /* change column bounds */ if (strcmp(type, "LO") == 0) lb = bnd; else if (strcmp(type, "UP") == 0) ub = bnd; else if (strcmp(type, "FX") == 0) lb = ub = bnd; else if (strcmp(type, "FR") == 0) lb = -DBL_MAX, ub = +DBL_MAX; else if (strcmp(type, "MI") == 0) lb = -DBL_MAX; else if (strcmp(type, "PL") == 0) ub = +DBL_MAX; else if (strcmp(type, "LI") == 0) { glp_set_col_kind(csa->P, j, GLP_IV); lb = ceil(bnd); } else if (strcmp(type, "UI") == 0) { glp_set_col_kind(csa->P, j, GLP_IV); ub = floor(bnd); } else if (strcmp(type, "BV") == 0) { glp_set_col_kind(csa->P, j, GLP_IV); lb = 0.0, ub = 1.0; } else xassert(type != type); /* set new column bounds */ if (lb == -DBL_MAX && ub == +DBL_MAX) glp_set_col_bnds(csa->P, j, GLP_FR, lb, ub); else if (ub == +DBL_MAX) glp_set_col_bnds(csa->P, j, GLP_LO, lb, ub); else if (lb == -DBL_MAX) glp_set_col_bnds(csa->P, j, GLP_UP, lb, ub); else if (lb != ub) glp_set_col_bnds(csa->P, j, GLP_DB, lb, ub); else glp_set_col_bnds(csa->P, j, GLP_FX, lb, ub); flag[j] |= (char)mask; /* fields 5 and 6 must be blank */ skip_field(csa); skip_field(csa); goto loop; done: /* free working array */ xfree(flag); csa->work3 = NULL; return; } int glp_read_mps(glp_prob *P, int fmt, const glp_mpscp *parm, const char *fname) { /* read problem data in MPS format */ glp_mpscp _parm; struct csa _csa, *csa = &_csa; int ret; xprintf("Reading problem data from `%s'...\n", fname); if (!(fmt == GLP_MPS_DECK || fmt == GLP_MPS_FILE)) xerror("glp_read_mps: fmt = %d; invalid parameter\n", fmt); if (parm == NULL) glp_init_mpscp(&_parm), parm = &_parm; /* check control parameters */ check_parm("glp_read_mps", parm); /* initialize common storage area */ csa->P = P; csa->deck = (fmt == GLP_MPS_DECK); csa->parm = parm; csa->fname = fname; csa->fp = NULL; if (setjmp(csa->jump)) { ret = 1; goto done; } csa->recno = csa->recpos = 0; csa->c = '\n'; csa->fldno = 0; csa->field[0] = '\0'; csa->w80 = csa->wef = 0; csa->obj_row = 0; csa->work1 = csa->work2 = csa->work3 = NULL; /* erase problem object */ glp_erase_prob(P); glp_create_index(P); /* open input MPS file */ csa->fp = xfopen(fname, "r"); if (csa->fp == NULL) { xprintf("Unable to open `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* read NAME indicator record */ read_name(csa); if (P->name != NULL) xprintf("Problem: %s\n", P->name); /* read ROWS section */ if (!(indicator(csa, 0) && strcmp(csa->field, "ROWS") == 0)) error(csa, "missing ROWS indicator record\n"); read_rows(csa); /* determine objective row */ if (parm->obj_name == NULL || parm->obj_name[0] == '\0') { /* use the first row of N type */ int i; for (i = 1; i <= P->m; i++) { if (P->row[i]->type == GLP_FR) { csa->obj_row = i; break; } } if (csa->obj_row == 0) warning(csa, "unable to determine objective row\n"); } else { /* use a row with specified name */ int i; for (i = 1; i <= P->m; i++) { xassert(P->row[i]->name != NULL); if (strcmp(parm->obj_name, P->row[i]->name) == 0) { csa->obj_row = i; break; } } if (csa->obj_row == 0) error(csa, "objective row `%s' not found\n", parm->obj_name); } if (csa->obj_row != 0) { glp_set_obj_name(P, P->row[csa->obj_row]->name); xprintf("Objective: %s\n", P->obj); } /* read COLUMNS section */ if (strcmp(csa->field, "COLUMNS") != 0) error(csa, "missing COLUMNS indicator record\n"); read_columns(csa); /* set objective coefficients */ if (csa->obj_row != 0) { GLPAIJ *aij; for (aij = P->row[csa->obj_row]->ptr; aij != NULL; aij = aij->r_next) glp_set_obj_coef(P, aij->col->j, aij->val); } /* read optional RHS section */ if (strcmp(csa->field, "RHS") == 0) read_rhs(csa); /* read optional RANGES section */ if (strcmp(csa->field, "RANGES") == 0) read_ranges(csa); /* read optional BOUNDS section */ if (strcmp(csa->field, "BOUNDS") == 0) read_bounds(csa); /* read ENDATA indicator record */ if (strcmp(csa->field, "ENDATA") != 0) error(csa, "invalid use of %s indicator record\n", csa->field); /* print some statistics */ xprintf("%d row%s, %d column%s, %d non-zero%s\n", P->m, P->m == 1 ? "" : "s", P->n, P->n == 1 ? "" : "s", P->nnz, P->nnz == 1 ? "" : "s"); if (glp_get_num_int(P) > 0) { int ni = glp_get_num_int(P); int nb = glp_get_num_bin(P); if (ni == 1) { if (nb == 0) xprintf("One variable is integer\n"); else xprintf("One variable is binary\n"); } else { xprintf("%d integer variables, ", ni); if (nb == 0) xprintf("none"); else if (nb == 1) xprintf("one"); else if (nb == ni) xprintf("all"); else xprintf("%d", nb); xprintf(" of which %s binary\n", nb == 1 ? "is" : "are"); } } xprintf("%d records were read\n", csa->recno); /* problem data has been successfully read */ glp_delete_index(P); glp_sort_matrix(P); ret = 0; done: if (csa->fp != NULL) xfclose(csa->fp); if (csa->work1 != NULL) xfree(csa->work1); if (csa->work2 != NULL) xfree(csa->work2); if (csa->work3 != NULL) xfree(csa->work3); if (ret != 0) glp_erase_prob(P); return ret; } /*********************************************************************** * NAME * * glp_write_mps - write problem data in MPS format * * SYNOPSIS * * int glp_write_mps(glp_prob *P, int fmt, const glp_mpscp *parm, * const char *fname); * * DESCRIPTION * * The routine glp_write_mps writes problem data in MPS format to a * text file. * * The parameter fmt specifies the version of MPS format: * * GLP_MPS_DECK - fixed (ancient) MPS format; * GLP_MPS_FILE - free (modern) MPS format. * * The parameter parm is a pointer to the structure glp_mpscp, which * specifies control parameters used by the routine. If parm is NULL, * the routine uses default settings. * * The character string fname specifies a name of the text file to be * written. * * RETURNS * * If the operation was successful, the routine glp_read_mps returns * zero. Otherwise, it prints an error message and returns non-zero. */ #define csa csa1 struct csa { /* common storage area */ glp_prob *P; /* pointer to problem object */ int deck; /* MPS format (0 - free, 1 - fixed) */ const glp_mpscp *parm; /* pointer to control parameters */ char field[255+1]; /* field buffer */ }; static char *mps_name(struct csa *csa) { /* make problem name */ char *f; if (csa->P->name == NULL) csa->field[0] = '\0'; else if (csa->deck) { strncpy(csa->field, csa->P->name, 8); csa->field[8] = '\0'; } else strcpy(csa->field, csa->P->name); for (f = csa->field; *f != '\0'; f++) if (*f == ' ') *f = '_'; return csa->field; } static char *row_name(struct csa *csa, int i) { /* make i-th row name */ char *f; xassert(0 <= i && i <= csa->P->m); if (i == 0 || csa->P->row[i]->name == NULL || csa->deck && strlen(csa->P->row[i]->name) > 8) sprintf(csa->field, "R%07d", i); else { strcpy(csa->field, csa->P->row[i]->name); for (f = csa->field; *f != '\0'; f++) if (*f == ' ') *f = '_'; } return csa->field; } static char *col_name(struct csa *csa, int j) { /* make j-th column name */ char *f; xassert(1 <= j && j <= csa->P->n); if (csa->P->col[j]->name == NULL || csa->deck && strlen(csa->P->col[j]->name) > 8) sprintf(csa->field, "C%07d", j); else { strcpy(csa->field, csa->P->col[j]->name); for (f = csa->field; *f != '\0'; f++) if (*f == ' ') *f = '_'; } return csa->field; } static char *mps_numb(struct csa *csa, double val) { /* format floating-point number */ int dig; char *exp; for (dig = 12; dig >= 6; dig--) { if (val != 0.0 && fabs(val) < 0.002) sprintf(csa->field, "%.*E", dig-1, val); else sprintf(csa->field, "%.*G", dig, val); exp = strchr(csa->field, 'E'); if (exp != NULL) sprintf(exp+1, "%d", atoi(exp+1)); if (strlen(csa->field) <= 12) break; } xassert(strlen(csa->field) <= 12); return csa->field; } int glp_write_mps(glp_prob *P, int fmt, const glp_mpscp *parm, const char *fname) { /* write problem data in MPS format */ glp_mpscp _parm; struct csa _csa, *csa = &_csa; XFILE *fp; int out_obj, one_col = 0, empty = 0; int i, j, recno, marker, count, gap, ret; xprintf("Writing problem data to `%s'...\n", fname); if (!(fmt == GLP_MPS_DECK || fmt == GLP_MPS_FILE)) xerror("glp_write_mps: fmt = %d; invalid parameter\n", fmt); if (parm == NULL) glp_init_mpscp(&_parm), parm = &_parm; /* check control parameters */ check_parm("glp_write_mps", parm); /* initialize common storage area */ csa->P = P; csa->deck = (fmt == GLP_MPS_DECK); csa->parm = parm; /* create output MPS file */ fp = xfopen(fname, "w"), recno = 0; if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* write comment records */ xfprintf(fp, "* %-*s%s\n", P->name == NULL ? 1 : 12, "Problem:", P->name == NULL ? "" : P->name), recno++; xfprintf(fp, "* %-12s%s\n", "Class:", glp_get_num_int(P) == 0 ? "LP" : "MIP"), recno++; xfprintf(fp, "* %-12s%d\n", "Rows:", P->m), recno++; if (glp_get_num_int(P) == 0) xfprintf(fp, "* %-12s%d\n", "Columns:", P->n), recno++; else xfprintf(fp, "* %-12s%d (%d integer, %d binary)\n", "Columns:", P->n, glp_get_num_int(P), glp_get_num_bin(P)), recno++; xfprintf(fp, "* %-12s%d\n", "Non-zeros:", P->nnz), recno++; xfprintf(fp, "* %-12s%s\n", "Format:", csa->deck ? "Fixed MPS" : "Free MPS"), recno++; xfprintf(fp, "*\n", recno++); /* write NAME indicator record */ xfprintf(fp, "NAME%*s%s\n", P->name == NULL ? 0 : csa->deck ? 10 : 1, "", mps_name(csa)), recno++; #if 1 /* determine whether to write the objective row */ out_obj = 1; for (i = 1; i <= P->m; i++) { if (P->row[i]->type == GLP_FR) { out_obj = 0; break; } } #endif /* write ROWS section */ xfprintf(fp, "ROWS\n"), recno++; for (i = (out_obj ? 0 : 1); i <= P->m; i++) { int type; type = (i == 0 ? GLP_FR : P->row[i]->type); if (type == GLP_FR) type = 'N'; else if (type == GLP_LO) type = 'G'; else if (type == GLP_UP) type = 'L'; else if (type == GLP_DB || type == GLP_FX) type = 'E'; else xassert(type != type); xfprintf(fp, " %c%*s%s\n", type, csa->deck ? 2 : 1, "", row_name(csa, i)), recno++; } /* write COLUMNS section */ xfprintf(fp, "COLUMNS\n"), recno++; marker = 0; for (j = 1; j <= P->n; j++) { GLPAIJ cj, *aij; int kind; kind = P->col[j]->kind; if (kind == GLP_CV) { if (marker % 2 == 1) { /* close current integer block */ marker++; xfprintf(fp, "%*sM%07d%*s'MARKER'%*s'INTEND'\n", csa->deck ? 4 : 1, "", marker, csa->deck ? 2 : 1, "", csa->deck ? 17 : 1, ""), recno++; } } else if (kind == GLP_IV) { if (marker % 2 == 0) { /* open new integer block */ marker++; xfprintf(fp, "%*sM%07d%*s'MARKER'%*s'INTORG'\n", csa->deck ? 4 : 1, "", marker, csa->deck ? 2 : 1, "", csa->deck ? 17 : 1, ""), recno++; } } else xassert(kind != kind); if (out_obj && P->col[j]->coef != 0.0) { /* make fake objective coefficient */ aij = &cj; aij->row = NULL; aij->val = P->col[j]->coef; aij->c_next = P->col[j]->ptr; } else aij = P->col[j]->ptr; #if 1 /* FIXME */ if (aij == NULL) { /* empty column */ empty++; xfprintf(fp, "%*s%-*s", csa->deck ? 4 : 1, "", csa->deck ? 8 : 1, col_name(csa, j)); /* we need a row */ xassert(P->m > 0); xfprintf(fp, "%*s%-*s", csa->deck ? 2 : 1, "", csa->deck ? 8 : 1, row_name(csa, 1)); xfprintf(fp, "%*s0%*s$ empty column\n", csa->deck ? 13 : 1, "", csa->deck ? 3 : 1, ""), recno++; } #endif count = 0; for (aij = aij; aij != NULL; aij = aij->c_next) { if (one_col || count % 2 == 0) xfprintf(fp, "%*s%-*s", csa->deck ? 4 : 1, "", csa->deck ? 8 : 1, col_name(csa, j)); gap = (one_col || count % 2 == 0 ? 2 : 3); xfprintf(fp, "%*s%-*s", csa->deck ? gap : 1, "", csa->deck ? 8 : 1, row_name(csa, aij->row == NULL ? 0 : aij->row->i)); xfprintf(fp, "%*s%*s", csa->deck ? 2 : 1, "", csa->deck ? 12 : 1, mps_numb(csa, aij->val)), count++; if (one_col || count % 2 == 0) xfprintf(fp, "\n"), recno++; } if (!(one_col || count % 2 == 0)) xfprintf(fp, "\n"), recno++; } if (marker % 2 == 1) { /* close last integer block */ marker++; xfprintf(fp, "%*sM%07d%*s'MARKER'%*s'INTEND'\n", csa->deck ? 4 : 1, "", marker, csa->deck ? 2 : 1, "", csa->deck ? 17 : 1, ""), recno++; } #if 1 if (empty > 0) xprintf("Warning: problem has %d empty column(s)\n", empty); #endif /* write RHS section */ xfprintf(fp, "RHS\n"), recno++; count = 0; for (i = (out_obj ? 0 : 1); i <= P->m; i++) { int type; double rhs; if (i == 0) rhs = P->c0; else { type = P->row[i]->type; if (type == GLP_FR) rhs = 0.0; else if (type == GLP_LO) rhs = P->row[i]->lb; else if (type == GLP_UP) rhs = P->row[i]->ub; else if (type == GLP_DB || type == GLP_FX) rhs = P->row[i]->lb; else xassert(type != type); } if (rhs != 0.0) { if (one_col || count % 2 == 0) xfprintf(fp, "%*s%-*s", csa->deck ? 4 : 1, "", csa->deck ? 8 : 1, "RHS1"); gap = (one_col || count % 2 == 0 ? 2 : 3); xfprintf(fp, "%*s%-*s", csa->deck ? gap : 1, "", csa->deck ? 8 : 1, row_name(csa, i)); xfprintf(fp, "%*s%*s", csa->deck ? 2 : 1, "", csa->deck ? 12 : 1, mps_numb(csa, rhs)), count++; if (one_col || count % 2 == 0) xfprintf(fp, "\n"), recno++; } } if (!(one_col || count % 2 == 0)) xfprintf(fp, "\n"), recno++; /* write RANGES section */ for (i = P->m; i >= 1; i--) if (P->row[i]->type == GLP_DB) break; if (i == 0) goto bnds; xfprintf(fp, "RANGES\n"), recno++; count = 0; for (i = 1; i <= P->m; i++) { if (P->row[i]->type == GLP_DB) { if (one_col || count % 2 == 0) xfprintf(fp, "%*s%-*s", csa->deck ? 4 : 1, "", csa->deck ? 8 : 1, "RNG1"); gap = (one_col || count % 2 == 0 ? 2 : 3); xfprintf(fp, "%*s%-*s", csa->deck ? gap : 1, "", csa->deck ? 8 : 1, row_name(csa, i)); xfprintf(fp, "%*s%*s", csa->deck ? 2 : 1, "", csa->deck ? 12 : 1, mps_numb(csa, P->row[i]->ub - P->row[i]->lb)), count++; if (one_col || count % 2 == 0) xfprintf(fp, "\n"), recno++; } } if (!(one_col || count % 2 == 0)) xfprintf(fp, "\n"), recno++; bnds: /* write BOUNDS section */ for (j = P->n; j >= 1; j--) if (!(P->col[j]->type == GLP_LO && P->col[j]->lb == 0.0)) break; if (j == 0) goto endt; xfprintf(fp, "BOUNDS\n"), recno++; for (j = 1; j <= P->n; j++) { int type, data[2]; double bnd[2]; char *spec[2]; spec[0] = spec[1] = NULL; type = P->col[j]->type; if (type == GLP_FR) spec[0] = "FR", data[0] = 0; else if (type == GLP_LO) { if (P->col[j]->lb != 0.0) spec[0] = "LO", data[0] = 1, bnd[0] = P->col[j]->lb; if (P->col[j]->kind == GLP_IV) spec[1] = "PL", data[1] = 0; } else if (type == GLP_UP) { spec[0] = "MI", data[0] = 0; spec[1] = "UP", data[1] = 1, bnd[1] = P->col[j]->ub; } else if (type == GLP_DB) { if (P->col[j]->lb != 0.0) spec[0] = "LO", data[0] = 1, bnd[0] = P->col[j]->lb; spec[1] = "UP", data[1] = 1, bnd[1] = P->col[j]->ub; } else if (type == GLP_FX) spec[0] = "FX", data[0] = 1, bnd[0] = P->col[j]->lb; else xassert(type != type); for (i = 0; i <= 1; i++) { if (spec[i] != NULL) { xfprintf(fp, " %s %-*s%*s%-*s", spec[i], csa->deck ? 8 : 1, "BND1", csa->deck ? 2 : 1, "", csa->deck ? 8 : 1, col_name(csa, j)); if (data[i]) xfprintf(fp, "%*s%*s", csa->deck ? 2 : 1, "", csa->deck ? 12 : 1, mps_numb(csa, bnd[i])); xfprintf(fp, "\n"), recno++; } } } endt: /* write ENDATA indicator record */ xfprintf(fp, "ENDATA\n"), recno++; xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* problem data has been successfully written */ xprintf("%d records were written\n", recno); ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /* eof */ sources_5316/external/glpk/amd_valid.c0000644000176700017670000000651511401660400016565 0ustar paulpaul/* ========================================================================= */ /* === AMD_valid =========================================================== */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* Check if a column-form matrix is valid or not. The matrix A is * n_row-by-n_col. The row indices of entries in column j are in * Ai [Ap [j] ... Ap [j+1]-1]. Required conditions are: * * n_row >= 0 * n_col >= 0 * nz = Ap [n_col] >= 0 number of entries in the matrix * Ap [0] == 0 * Ap [j] <= Ap [j+1] for all j in the range 0 to n_col. * Ai [0 ... nz-1] must be in the range 0 to n_row-1. * * If any of the above conditions hold, AMD_INVALID is returned. If the * following condition holds, AMD_OK_BUT_JUMBLED is returned (a warning, * not an error): * * row indices in Ai [Ap [j] ... Ap [j+1]-1] are not sorted in ascending * order, and/or duplicate entries exist. * * Otherwise, AMD_OK is returned. * * In v1.2 and earlier, this function returned TRUE if the matrix was valid * (now returns AMD_OK), or FALSE otherwise (now returns AMD_INVALID or * AMD_OK_BUT_JUMBLED). */ #include "amd_internal.h" GLOBAL Int AMD_valid ( /* inputs, not modified on output: */ Int n_row, /* A is n_row-by-n_col */ Int n_col, const Int Ap [ ], /* column pointers of A, of size n_col+1 */ const Int Ai [ ] /* row indices of A, of size nz = Ap [n_col] */ ) { Int nz, j, p1, p2, ilast, i, p, result = AMD_OK ; if (n_row < 0 || n_col < 0 || Ap == NULL || Ai == NULL) { return (AMD_INVALID) ; } nz = Ap [n_col] ; if (Ap [0] != 0 || nz < 0) { /* column pointers must start at Ap [0] = 0, and Ap [n] must be >= 0 */ AMD_DEBUG0 (("column 0 pointer bad or nz < 0\n")) ; return (AMD_INVALID) ; } for (j = 0 ; j < n_col ; j++) { p1 = Ap [j] ; p2 = Ap [j+1] ; AMD_DEBUG2 (("\nColumn: "ID" p1: "ID" p2: "ID"\n", j, p1, p2)) ; if (p1 > p2) { /* column pointers must be ascending */ AMD_DEBUG0 (("column "ID" pointer bad\n", j)) ; return (AMD_INVALID) ; } ilast = EMPTY ; for (p = p1 ; p < p2 ; p++) { i = Ai [p] ; AMD_DEBUG3 (("row: "ID"\n", i)) ; if (i < 0 || i >= n_row) { /* row index out of range */ AMD_DEBUG0 (("index out of range, col "ID" row "ID"\n", j, i)); return (AMD_INVALID) ; } if (i <= ilast) { /* row index unsorted, or duplicate entry present */ AMD_DEBUG1 (("index unsorted/dupl col "ID" row "ID"\n", j, i)); result = AMD_OK_BUT_JUMBLED ; } ilast = i ; } } return (result) ; } sources_5316/external/glpk/glpnet03.c0000644000176700017670000006040511401660400016277 0ustar paulpaul/* glpnet03.c (Klingman's network problem generator) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * This code is the result of translation of the Fortran program NETGEN * developed by Dr. Darwin Klingman, which is publically available from * NETLIB at . * * The translation was made by Andrew Makhorin . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_netgen - Klingman's network problem generator * * SYNOPSIS * * int glp_netgen(glp_graph *G, int v_rhs, int a_cap, int a_cost, * const int parm[1+15]); * * DESCRIPTION * * The routine glp_netgen is a network problem generator developed by * Dr. Darwin Klingman. It can create capacitated and uncapacitated * minimum cost flow (or transshipment), transportation, and assignment * problems. * * The parameter G specifies the graph object, to which the generated * problem data have to be stored. Note that on entry the graph object * is erased with the routine glp_erase_graph. * * The parameter v_rhs specifies an offset of the field of type double * in the vertex data block, to which the routine stores the supply or * demand value. If v_rhs < 0, the value is not stored. * * The parameter a_cap specifies an offset of the field of type double * in the arc data block, to which the routine stores the arc capacity. * If a_cap < 0, the capacity is not stored. * * The parameter a_cost specifies an offset of the field of type double * in the arc data block, to which the routine stores the per-unit cost * if the arc flow. If a_cost < 0, the cost is not stored. * * The array parm contains description of the network to be generated: * * parm[0] not used * parm[1] (iseed) 8-digit positive random number seed * parm[2] (nprob) 8-digit problem id number * parm[3] (nodes) total number of nodes * parm[4] (nsorc) total number of source nodes (including * transshipment nodes) * parm[5] (nsink) total number of sink nodes (including * transshipment nodes) * parm[6] (iarcs) number of arcs * parm[7] (mincst) minimum cost for arcs * parm[8] (maxcst) maximum cost for arcs * parm[9] (itsup) total supply * parm[10] (ntsorc) number of transshipment source nodes * parm[11] (ntsink) number of transshipment sink nodes * parm[12] (iphic) percentage of skeleton arcs to be given * the maximum cost * parm[13] (ipcap) percentage of arcs to be capacitated * parm[14] (mincap) minimum upper bound for capacitated arcs * parm[15] (maxcap) maximum upper bound for capacitated arcs * * The routine generates a transportation problem if: * * nsorc + nsink = nodes, ntsorc = 0, and ntsink = 0. * * The routine generates an assignment problem if the requirements for * a transportation problem are met and: * * nsorc = nsink and itsup = nsorc. * * RETURNS * * If the instance was successfully generated, the routine glp_netgen * returns zero; otherwise, if specified parameters are inconsistent, * the routine returns a non-zero error code. * * REFERENCES * * D.Klingman, A.Napier, and J.Stutz. NETGEN: A program for generating * large scale capacitated assignment, transportation, and minimum cost * flow networks. Management Science 20 (1974), 814-20. */ struct csa { /* common storage area */ glp_graph *G; int v_rhs, a_cap, a_cost; int nodes, iarcs, mincst, maxcst, itsup, nsorc, nsink, nonsor, nfsink, narcs, nsort, nftsor, ipcap, mincap, maxcap, ktl, nodlft, *ipred, *ihead, *itail, *iflag, *isup, *lsinks, mult, modul, i15, i16, jran; }; #define G (csa->G) #define v_rhs (csa->v_rhs) #define a_cap (csa->a_cap) #define a_cost (csa->a_cost) #define nodes (csa->nodes) #define iarcs (csa->iarcs) #define mincst (csa->mincst) #define maxcst (csa->maxcst) #define itsup (csa->itsup) #define nsorc (csa->nsorc) #define nsink (csa->nsink) #define nonsor (csa->nonsor) #define nfsink (csa->nfsink) #define narcs (csa->narcs) #define nsort (csa->nsort) #define nftsor (csa->nftsor) #define ipcap (csa->ipcap) #define mincap (csa->mincap) #define maxcap (csa->maxcap) #define ktl (csa->ktl) #define nodlft (csa->nodlft) #if 0 /* spent a day to find out this bug */ #define ist (csa->ist) #else #define ist (ipred[0]) #endif #define ipred (csa->ipred) #define ihead (csa->ihead) #define itail (csa->itail) #define iflag (csa->iflag) #define isup (csa->isup) #define lsinks (csa->lsinks) #define mult (csa->mult) #define modul (csa->modul) #define i15 (csa->i15) #define i16 (csa->i16) #define jran (csa->jran) static void cresup(struct csa *csa); static void chain(struct csa *csa, int lpick, int lsorc); static void chnarc(struct csa *csa, int lsorc); static void sort(struct csa *csa); static void pickj(struct csa *csa, int it); static void assign(struct csa *csa); static void setran(struct csa *csa, int iseed); static int iran(struct csa *csa, int ilow, int ihigh); int glp_netgen(glp_graph *G_, int _v_rhs, int _a_cap, int _a_cost, const int parm[1+15]) { struct csa _csa, *csa = &_csa; int iseed, nprob, ntsorc, ntsink, iphic, i, nskel, nltr, ltsink, ntrans, npsink, nftr, npsorc, ntravl, ntrrem, lsorc, lpick, nsksr, nsrchn, j, item, l, ks, k, ksp, li, n, ii, it, ih, icap, jcap, icost, jcost, ret; G = G_; v_rhs = _v_rhs; a_cap = _a_cap; a_cost = _a_cost; if (G != NULL) { if (v_rhs >= 0 && v_rhs > G->v_size - (int)sizeof(double)) xerror("glp_netgen: v_rhs = %d; invalid offset\n", v_rhs); if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_netgen: a_cap = %d; invalid offset\n", a_cap); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_netgen: a_cost = %d; invalid offset\n", a_cost); } /* Input the user's random number seed and fix it if non-positive. */ iseed = parm[1]; nprob = parm[2]; if (iseed <= 0) iseed = 13502460; setran(csa, iseed); /* Input the user's problem characteristics. */ nodes = parm[3]; nsorc = parm[4]; nsink = parm[5]; iarcs = parm[6]; mincst = parm[7]; maxcst = parm[8]; itsup = parm[9]; ntsorc = parm[10]; ntsink = parm[11]; iphic = parm[12]; ipcap = parm[13]; mincap = parm[14]; maxcap = parm[15]; /* Check the size of the problem. */ if (!(10 <= nodes && nodes <= 100000)) { ret = 1; goto done; } /* Check user supplied parameters for consistency. */ if (!(nsorc >= 0 && nsink >= 0 && nsorc + nsink <= nodes)) { ret = 2; goto done; } if (iarcs < 0) { ret = 3; goto done; } if (mincst > maxcst) { ret = 4; goto done; } if (itsup < 0) { ret = 5; goto done; } if (!(0 <= ntsorc && ntsorc <= nsorc)) { ret = 6; goto done; } if (!(0 <= ntsink && ntsink <= nsink)) { ret = 7; goto done; } if (!(0 <= iphic && iphic <= 100)) { ret = 8; goto done; } if (!(0 <= ipcap && ipcap <= 100)) { ret = 9; goto done; } if (mincap > maxcap) { ret = 10; goto done; } /* Initailize the graph object. */ if (G != NULL) { glp_erase_graph(G, G->v_size, G->a_size); glp_add_vertices(G, nodes); if (v_rhs >= 0) { double zero = 0.0; for (i = 1; i <= nodes; i++) { glp_vertex *v = G->v[i]; memcpy((char *)v->data + v_rhs, &zero, sizeof(double)); } } } /* Allocate working arrays. */ ipred = xcalloc(1+nodes, sizeof(int)); ihead = xcalloc(1+nodes, sizeof(int)); itail = xcalloc(1+nodes, sizeof(int)); iflag = xcalloc(1+nodes, sizeof(int)); isup = xcalloc(1+nodes, sizeof(int)); lsinks = xcalloc(1+nodes, sizeof(int)); /* Print the problem documentation records. */ if (G == NULL) { xprintf("BEGIN\n"); xprintf("NETGEN PROBLEM%8d%10s%10d NODES AND%10d ARCS\n", nprob, "", nodes, iarcs); xprintf("USER:%11d%11d%11d%11d%11d%11d\nDATA:%11d%11d%11d%11d%" "11d%11d\n", iseed, nsorc, nsink, mincst, maxcst, itsup, ntsorc, ntsink, iphic, ipcap, mincap, maxcap); } else glp_set_graph_name(G, "NETGEN"); /* Set various constants used in the program. */ narcs = 0; nskel = 0; nltr = nodes - nsink; ltsink = nltr + ntsink; ntrans = nltr - nsorc; nfsink = nltr + 1; nonsor = nodes - nsorc + ntsorc; npsink = nsink - ntsink; nodlft = nodes - nsink + ntsink; nftr = nsorc + 1; nftsor = nsorc - ntsorc + 1; npsorc = nsorc - ntsorc; /* Randomly distribute the supply among the source nodes. */ if (npsorc + npsink == nodes && npsorc == npsink && itsup == nsorc) { assign(csa); nskel = nsorc; goto L390; } cresup(csa); /* Print the supply records. */ if (G == NULL) { xprintf("SUPPLY\n"); for (i = 1; i <= nsorc; i++) xprintf("%6s%6d%18s%10d\n", "", i, "", isup[i]); xprintf("ARCS\n"); } else { if (v_rhs >= 0) { for (i = 1; i <= nsorc; i++) { double temp = (double)isup[i]; glp_vertex *v = G->v[i]; memcpy((char *)v->data + v_rhs, &temp, sizeof(double)); } } } /* Make the sources point to themselves in ipred array. */ for (i = 1; i <= nsorc; i++) ipred[i] = i; if (ntrans == 0) goto L170; /* Chain the transshipment nodes together in the ipred array. */ ist = nftr; ipred[nltr] = 0; for (i = nftr; i < nltr; i++) ipred[i] = i+1; /* Form even length chains for 60 percent of the transshipments.*/ ntravl = 6 * ntrans / 10; ntrrem = ntrans - ntravl; L140: lsorc = 1; while (ntravl != 0) { lpick = iran(csa, 1, ntravl + ntrrem); ntravl--; chain(csa, lpick, lsorc); if (lsorc == nsorc) goto L140; lsorc++; } /* Add the remaining transshipments to the chains. */ while (ntrrem != 0) { lpick = iran(csa, 1, ntrrem); ntrrem--; lsorc = iran(csa, 1, nsorc); chain(csa, lpick, lsorc); } L170: /* Set all demands equal to zero. */ for (i = nfsink; i <= nodes; i++) ipred[i] = 0; /* The following loop takes one chain at a time (through the use of logic contained in the loop and calls to other routines) and creates the remaining network arcs. */ for (lsorc = 1; lsorc <= nsorc; lsorc++) { chnarc(csa, lsorc); for (i = nfsink; i <= nodes; i++) iflag[i] = 0; /* Choose the number of sinks to be hooked up to the current chain. */ if (ntrans != 0) nsksr = (nsort * 2 * nsink) / ntrans; else nsksr = nsink / nsorc + 1; if (nsksr < 2) nsksr = 2; if (nsksr > nsink) nsksr = nsink; nsrchn = nsort; /* Randomly pick nsksr sinks and put their names in lsinks. */ ktl = nsink; for (j = 1; j <= nsksr; j++) { item = iran(csa, 1, ktl); ktl--; for (l = nfsink; l <= nodes; l++) { if (iflag[l] != 1) { item--; if (item == 0) goto L230; } } break; L230: lsinks[j] = l; iflag[l] = 1; } /* If last source chain, add all sinks with zero demand to lsinks list. */ if (lsorc == nsorc) { for (j = nfsink; j <= nodes; j++) { if (ipred[j] == 0 && iflag[j] != 1) { nsksr++; lsinks[nsksr] = j; iflag[j] = 1; } } } /* Create demands for group of sinks in lsinks. */ ks = isup[lsorc] / nsksr; k = ipred[lsorc]; for (i = 1; i <= nsksr; i++) { nsort++; ksp = iran(csa, 1, ks); j = iran(csa, 1, nsksr); itail[nsort] = k; li = lsinks[i]; ihead[nsort] = li; ipred[li] += ksp; li = lsinks[j]; ipred[li] += ks - ksp; n = iran(csa, 1, nsrchn); k = lsorc; for (ii = 1; ii <= n; ii++) k = ipred[k]; } li = lsinks[1]; ipred[li] += isup[lsorc] - ks * nsksr; nskel += nsort; /* Sort the arcs in the chain from source lsorc using itail as sort key. */ sort(csa); /* Print this part of skeleton and create the arcs for these nodes. */ i = 1; itail[nsort+1] = 0; L300: for (j = nftsor; j <= nodes; j++) iflag[j] = 0; ktl = nonsor - 1; it = itail[i]; iflag[it] = 1; L320: ih = ihead[i]; iflag[ih] = 1; narcs++; ktl--; /* Determine if this skeleton arc should be capacitated. */ icap = itsup; jcap = iran(csa, 1, 100); if (jcap <= ipcap) { icap = isup[lsorc]; if (mincap > icap) icap = mincap; } /* Determine if this skeleton arc should have the maximum cost. */ icost = maxcst; jcost = iran(csa, 1, 100); if (jcost > iphic) icost = iran(csa, mincst, maxcst); if (G == NULL) xprintf("%6s%6d%6d%2s%10d%10d\n", "", it, ih, "", icost, icap); else { glp_arc *a = glp_add_arc(G, it, ih); if (a_cap >= 0) { double temp = (double)icap; memcpy((char *)a->data + a_cap, &temp, sizeof(double)); } if (a_cost >= 0) { double temp = (double)icost; memcpy((char *)a->data + a_cost, &temp, sizeof(double)); } } i++; if (itail[i] == it) goto L320; pickj(csa, it); if (i <= nsort) goto L300; } /* Create arcs from the transshipment sinks. */ if (ntsink != 0) { for (i = nfsink; i <= ltsink; i++) { for (j = nftsor; j <= nodes; j++) iflag[j] = 0; ktl = nonsor - 1; iflag[i] = 1; pickj(csa, i); } } L390: /* Print the demand records and end record. */ if (G == NULL) { xprintf("DEMAND\n"); for (i = nfsink; i <= nodes; i++) xprintf("%6s%6d%18s%10d\n", "", i, "", ipred[i]); xprintf("END\n"); } else { if (v_rhs >= 0) { for (i = nfsink; i <= nodes; i++) { double temp = - (double)ipred[i]; glp_vertex *v = G->v[i]; memcpy((char *)v->data + v_rhs, &temp, sizeof(double)); } } } /* Free working arrays. */ xfree(ipred); xfree(ihead); xfree(itail); xfree(iflag); xfree(isup); xfree(lsinks); /* The instance has been successfully generated. */ ret = 0; done: return ret; } /*********************************************************************** * The routine cresup randomly distributes the total supply among the * source nodes. */ static void cresup(struct csa *csa) { int i, j, ks, ksp; xassert(itsup > nsorc); ks = itsup / nsorc; for (i = 1; i <= nsorc; i++) isup[i] = 0; for (i = 1; i <= nsorc; i++) { ksp = iran(csa, 1, ks); j = iran(csa, 1, nsorc); isup[i] += ksp; isup[j] += ks - ksp; } j = iran(csa, 1, nsorc); isup[j] += itsup - ks * nsorc; return; } /*********************************************************************** * The routine chain adds node lpick to the end of the chain with source * node lsorc. */ static void chain(struct csa *csa, int lpick, int lsorc) { int i, j, k, l, m; k = 0; m = ist; for (i = 1; i <= lpick; i++) { l = k; k = m; m = ipred[k]; } ipred[l] = m; j = ipred[lsorc]; ipred[k] = j; ipred[lsorc] = k; return; } /*********************************************************************** * The routine chnarc puts the arcs in the chain from source lsorc into * the ihead and itail arrays for sorting. */ static void chnarc(struct csa *csa, int lsorc) { int ito, ifrom; nsort = 0; ito = ipred[lsorc]; L10: if (ito == lsorc) return; nsort++; ifrom = ipred[ito]; ihead[nsort] = ito; itail[nsort] = ifrom; ito = ifrom; goto L10; } /*********************************************************************** * The routine sort sorts the nsort arcs in the ihead and itail arrays. * ihead is used as the sort key (i.e. forward star sort order). */ static void sort(struct csa *csa) { int i, j, k, l, m, n, it; n = nsort; m = n; L10: m /= 2; if (m == 0) return; k = n - m; j = 1; L20: i = j; L30: l = i + m; if (itail[i] <= itail[l]) goto L40; it = itail[i]; itail[i] = itail[l]; itail[l] = it; it = ihead[i]; ihead[i] = ihead[l]; ihead[l] = it; i -= m; if (i >= 1) goto L30; L40: j++; if (j <= k) goto L20; goto L10; } /*********************************************************************** * The routine pickj creates a random number of arcs out of node 'it'. * Various parameters are dynamically adjusted in an attempt to ensure * that the generated network has the correct number of arcs. */ static void pickj(struct csa *csa, int it) { int j, k, l, nn, nupbnd, icap, jcap, icost; if ((nodlft - 1) * 2 > iarcs - narcs - 1) { nodlft--; return; } if ((iarcs - narcs + nonsor - ktl - 1) / nodlft - nonsor + 1 >= 0) k = nonsor; else { nupbnd = (iarcs - narcs - nodlft) / nodlft * 2; L40: k = iran(csa, 1, nupbnd); if (nodlft == 1) k = iarcs - narcs; if ((nodlft - 1) * (nonsor - 1) < iarcs - narcs - k) goto L40; } nodlft--; for (j = 1; j <= k; j++) { nn = iran(csa, 1, ktl); ktl--; for (l = nftsor; l <= nodes; l++) { if (iflag[l] != 1) { nn--; if (nn == 0) goto L70; } } return; L70: iflag[l] = 1; icap = itsup; jcap = iran(csa, 1, 100); if (jcap <= ipcap) icap = iran(csa, mincap, maxcap); icost = iran(csa, mincst, maxcst); if (G == NULL) xprintf("%6s%6d%6d%2s%10d%10d\n", "", it, l, "", icost, icap); else { glp_arc *a = glp_add_arc(G, it, l); if (a_cap >= 0) { double temp = (double)icap; memcpy((char *)a->data + a_cap, &temp, sizeof(double)); } if (a_cost >= 0) { double temp = (double)icost; memcpy((char *)a->data + a_cost, &temp, sizeof(double)); } } narcs++; } return; } /*********************************************************************** * The routine assign generate assignment problems. It defines the unit * supplies, builds a skeleton, then calls pickj to create the arcs. */ static void assign(struct csa *csa) { int i, it, nn, l, ll, icost; if (G == NULL) xprintf("SUPPLY\n"); for (i = 1; i <= nsorc; i++) { isup[i] = 1; iflag[i] = 0; if (G == NULL) xprintf("%6s%6d%18s%10d\n", "", i, "", isup[i]); else { if (v_rhs >= 0) { double temp = (double)isup[i]; glp_vertex *v = G->v[i]; memcpy((char *)v->data + v_rhs, &temp, sizeof(double)); } } } if (G == NULL) xprintf("ARCS\n"); for (i = nfsink; i <= nodes; i++) ipred[i] = 1; for (it = 1; it <= nsorc; it++) { for (i = nfsink; i <= nodes; i++) iflag[i] = 0; ktl = nsink - 1; nn = iran(csa, 1, nsink - it + 1); for (l = 1; l <= nsorc; l++) { if (iflag[l] != 1) { nn--; if (nn == 0) break; } } narcs++; ll = nsorc + l; icost = iran(csa, mincst, maxcst); if (G == NULL) xprintf("%6s%6d%6d%2s%10d%10d\n", "", it, ll, "", icost, isup[1]); else { glp_arc *a = glp_add_arc(G, it, ll); if (a_cap >= 0) { double temp = (double)isup[1]; memcpy((char *)a->data + a_cap, &temp, sizeof(double)); } if (a_cost >= 0) { double temp = (double)icost; memcpy((char *)a->data + a_cost, &temp, sizeof(double)); } } iflag[l] = 1; iflag[ll] = 1; pickj(csa, it); } return; } /*********************************************************************** * Portable congruential (uniform) random number generator: * * next_value = ((7**5) * previous_value) modulo ((2**31)-1) * * This generator consists of three routines: * * (1) setran - initializes constants and seed * (2) iran - generates an integer random number * (3) rran - generates a real random number * * The generator requires a machine with at least 32 bits of precision. * The seed (iseed) must be in the range [1,(2**31)-1]. */ static void setran(struct csa *csa, int iseed) { xassert(iseed >= 1); mult = 16807; modul = 2147483647; i15 = 1 << 15; i16 = 1 << 16; jran = iseed; return; } /*********************************************************************** * The routine iran generates an integer random number between ilow and * ihigh. If ilow > ihigh then iran returns ihigh. */ static int iran(struct csa *csa, int ilow, int ihigh) { int ixhi, ixlo, ixalo, leftlo, ixahi, ifulhi, irtlo, iover, irthi, j; ixhi = jran / i16; ixlo = jran - ixhi * i16; ixalo = ixlo * mult; leftlo = ixalo / i16; ixahi = ixhi * mult; ifulhi = ixahi + leftlo; irtlo = ixalo - leftlo * i16; iover = ifulhi / i15; irthi = ifulhi - iover * i15; jran = ((irtlo - modul) + irthi * i16) + iover; if (jran < 0) jran += modul; j = ihigh - ilow + 1; if (j > 0) return jran % j + ilow; else return ihigh; } /**********************************************************************/ #if 0 static int scan(char card[80+1], int pos, int len) { char buf[10+1]; memcpy(buf, &card[pos-1], len); buf[len] = '\0'; return atoi(buf); } int main(void) { int parm[1+15]; char card[80+1]; xassert(fgets(card, sizeof(card), stdin) == card); parm[1] = scan(card, 1, 8); parm[2] = scan(card, 9, 8); xassert(fgets(card, sizeof(card), stdin) == card); parm[3] = scan(card, 1, 5); parm[4] = scan(card, 6, 5); parm[5] = scan(card, 11, 5); parm[6] = scan(card, 16, 5); parm[7] = scan(card, 21, 5); parm[8] = scan(card, 26, 5); parm[9] = scan(card, 31, 10); parm[10] = scan(card, 41, 5); parm[11] = scan(card, 46, 5); parm[12] = scan(card, 51, 5); parm[13] = scan(card, 56, 5); parm[14] = scan(card, 61, 10); parm[15] = scan(card, 71, 10); glp_netgen(NULL, 0, 0, 0, parm); return 0; } #endif /* eof */ sources_5316/external/glpk/glplpx02.c0000644000176700017670000002376311401660400016321 0ustar paulpaul/* glplpx02.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * lpx_put_solution - store basic solution components * * SYNOPSIS * * void lpx_put_solution(glp_prob *lp, int inval, const int *p_stat, * const int *d_stat, const double *obj_val, const int r_stat[], * const double r_prim[], const double r_dual[], const int c_stat[], * const double c_prim[], const double c_dual[]) * * DESCRIPTION * * The routine lpx_put_solution stores basic solution components to the * specified problem object. * * The parameter inval is the basis factorization invalidity flag. * If this flag is clear, the current status of the basis factorization * remains unchanged. If this flag is set, the routine invalidates the * basis factorization. * * The parameter p_stat is a pointer to the status of primal basic * solution, which should be specified as follows: * * GLP_UNDEF - primal solution is undefined; * GLP_FEAS - primal solution is feasible; * GLP_INFEAS - primal solution is infeasible; * GLP_NOFEAS - no primal feasible solution exists. * * If the parameter p_stat is NULL, the current status of primal basic * solution remains unchanged. * * The parameter d_stat is a pointer to the status of dual basic * solution, which should be specified as follows: * * GLP_UNDEF - dual solution is undefined; * GLP_FEAS - dual solution is feasible; * GLP_INFEAS - dual solution is infeasible; * GLP_NOFEAS - no dual feasible solution exists. * * If the parameter d_stat is NULL, the current status of dual basic * solution remains unchanged. * * The parameter obj_val is a pointer to the objective function value. * If it is NULL, the current value of the objective function remains * unchanged. * * The array element r_stat[i], 1 <= i <= m (where m is the number of * rows in the problem object), specifies the status of i-th auxiliary * variable, which should be specified as follows: * * GLP_BS - basic variable; * GLP_NL - non-basic variable on lower bound; * GLP_NU - non-basic variable on upper bound; * GLP_NF - non-basic free variable; * GLP_NS - non-basic fixed variable. * * If the parameter r_stat is NULL, the current statuses of auxiliary * variables remain unchanged. * * The array element r_prim[i], 1 <= i <= m (where m is the number of * rows in the problem object), specifies a primal value of i-th * auxiliary variable. If the parameter r_prim is NULL, the current * primal values of auxiliary variables remain unchanged. * * The array element r_dual[i], 1 <= i <= m (where m is the number of * rows in the problem object), specifies a dual value (reduced cost) * of i-th auxiliary variable. If the parameter r_dual is NULL, the * current dual values of auxiliary variables remain unchanged. * * The array element c_stat[j], 1 <= j <= n (where n is the number of * columns in the problem object), specifies the status of j-th * structural variable, which should be specified as follows: * * GLP_BS - basic variable; * GLP_NL - non-basic variable on lower bound; * GLP_NU - non-basic variable on upper bound; * GLP_NF - non-basic free variable; * GLP_NS - non-basic fixed variable. * * If the parameter c_stat is NULL, the current statuses of structural * variables remain unchanged. * * The array element c_prim[j], 1 <= j <= n (where n is the number of * columns in the problem object), specifies a primal value of j-th * structural variable. If the parameter c_prim is NULL, the current * primal values of structural variables remain unchanged. * * The array element c_dual[j], 1 <= j <= n (where n is the number of * columns in the problem object), specifies a dual value (reduced cost) * of j-th structural variable. If the parameter c_dual is NULL, the * current dual values of structural variables remain unchanged. */ void lpx_put_solution(glp_prob *lp, int inval, const int *p_stat, const int *d_stat, const double *obj_val, const int r_stat[], const double r_prim[], const double r_dual[], const int c_stat[], const double c_prim[], const double c_dual[]) { GLPROW *row; GLPCOL *col; int i, j; /* invalidate the basis factorization, if required */ if (inval) lp->valid = 0; /* store primal status */ if (p_stat != NULL) { if (!(*p_stat == GLP_UNDEF || *p_stat == GLP_FEAS || *p_stat == GLP_INFEAS || *p_stat == GLP_NOFEAS)) xerror("lpx_put_solution: p_stat = %d; invalid primal statu" "s\n", *p_stat); lp->pbs_stat = *p_stat; } /* store dual status */ if (d_stat != NULL) { if (!(*d_stat == GLP_UNDEF || *d_stat == GLP_FEAS || *d_stat == GLP_INFEAS || *d_stat == GLP_NOFEAS)) xerror("lpx_put_solution: d_stat = %d; invalid dual status " "\n", *d_stat); lp->dbs_stat = *d_stat; } /* store objective function value */ if (obj_val != NULL) lp->obj_val = *obj_val; /* store row solution components */ for (i = 1; i <= lp->m; i++) { row = lp->row[i]; if (r_stat != NULL) { if (!(r_stat[i] == GLP_BS || row->type == GLP_FR && r_stat[i] == GLP_NF || row->type == GLP_LO && r_stat[i] == GLP_NL || row->type == GLP_UP && r_stat[i] == GLP_NU || row->type == GLP_DB && r_stat[i] == GLP_NL || row->type == GLP_DB && r_stat[i] == GLP_NU || row->type == GLP_FX && r_stat[i] == GLP_NS)) xerror("lpx_put_solution: r_stat[%d] = %d; invalid row s" "tatus\n", i, r_stat[i]); row->stat = r_stat[i]; } if (r_prim != NULL) row->prim = r_prim[i]; if (r_dual != NULL) row->dual = r_dual[i]; } /* store column solution components */ for (j = 1; j <= lp->n; j++) { col = lp->col[j]; if (c_stat != NULL) { if (!(c_stat[j] == GLP_BS || col->type == GLP_FR && c_stat[j] == GLP_NF || col->type == GLP_LO && c_stat[j] == GLP_NL || col->type == GLP_UP && c_stat[j] == GLP_NU || col->type == GLP_DB && c_stat[j] == GLP_NL || col->type == GLP_DB && c_stat[j] == GLP_NU || col->type == GLP_FX && c_stat[j] == GLP_NS)) xerror("lpx_put_solution: c_stat[%d] = %d; invalid colum" "n status\n", j, c_stat[j]); col->stat = c_stat[j]; } if (c_prim != NULL) col->prim = c_prim[j]; if (c_dual != NULL) col->dual = c_dual[j]; } return; } /*---------------------------------------------------------------------- -- lpx_put_mip_soln - store mixed integer solution components. -- -- *Synopsis* -- -- #include "glplpx.h" -- void lpx_put_mip_soln(glp_prob *lp, int i_stat, double row_mipx[], -- double col_mipx[]); -- -- *Description* -- -- The routine lpx_put_mip_soln stores solution components obtained by -- branch-and-bound solver into the specified problem object. -- -- NOTE: This routine is intended for internal use only. */ void lpx_put_mip_soln(glp_prob *lp, int i_stat, double row_mipx[], double col_mipx[]) { GLPROW *row; GLPCOL *col; int i, j; double sum; /* store mixed integer status */ #if 0 if (!(i_stat == LPX_I_UNDEF || i_stat == LPX_I_OPT || i_stat == LPX_I_FEAS || i_stat == LPX_I_NOFEAS)) fault("lpx_put_mip_soln: i_stat = %d; invalid mixed integer st" "atus", i_stat); lp->i_stat = i_stat; #else switch (i_stat) { case LPX_I_UNDEF: lp->mip_stat = GLP_UNDEF; break; case LPX_I_OPT: lp->mip_stat = GLP_OPT; break; case LPX_I_FEAS: lp->mip_stat = GLP_FEAS; break; case LPX_I_NOFEAS: lp->mip_stat = GLP_NOFEAS; break; default: xerror("lpx_put_mip_soln: i_stat = %d; invalid mixed intege" "r status\n", i_stat); } #endif /* store row solution components */ if (row_mipx != NULL) { for (i = 1; i <= lp->m; i++) { row = lp->row[i]; row->mipx = row_mipx[i]; } } /* store column solution components */ if (col_mipx != NULL) { for (j = 1; j <= lp->n; j++) { col = lp->col[j]; col->mipx = col_mipx[j]; } } /* if the solution is claimed to be integer feasible, check it */ if (lp->mip_stat == GLP_OPT || lp->mip_stat == GLP_FEAS) { for (j = 1; j <= lp->n; j++) { col = lp->col[j]; if (col->kind == GLP_IV && col->mipx != floor(col->mipx)) xerror("lpx_put_mip_soln: col_mipx[%d] = %.*g; must be i" "ntegral\n", j, DBL_DIG, col->mipx); } } /* compute the objective function value */ sum = lp->c0; for (j = 1; j <= lp->n; j++) { col = lp->col[j]; sum += col->coef * col->mipx; } lp->mip_obj = sum; return; } /* eof */ sources_5316/external/glpk/glpapi18.c0000644000176700017670000001022111401660400016257 0ustar paulpaul/* glpapi18.c (maximum clique problem) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" #include "glpnet.h" static void set_edge(int nv, unsigned char a[], int i, int j) { int k; xassert(1 <= j && j < i && i <= nv); k = ((i - 1) * (i - 2)) / 2 + (j - 1); a[k / CHAR_BIT] |= (unsigned char)(1 << ((CHAR_BIT - 1) - k % CHAR_BIT)); return; } int glp_wclique_exact(glp_graph *G, int v_wgt, double *sol, int v_set) { /* find maximum weight clique with exact algorithm */ glp_arc *e; int i, j, k, len, x, *w, *ind, ret = 0; unsigned char *a; double s, t; if (v_wgt >= 0 && v_wgt > G->v_size - (int)sizeof(double)) xerror("glp_wclique_exact: v_wgt = %d; invalid parameter\n", v_wgt); if (v_set >= 0 && v_set > G->v_size - (int)sizeof(int)) xerror("glp_wclique_exact: v_set = %d; invalid parameter\n", v_set); if (G->nv == 0) { /* empty graph has only empty clique */ if (sol != NULL) *sol = 0.0; return 0; } /* allocate working arrays */ w = xcalloc(1+G->nv, sizeof(int)); ind = xcalloc(1+G->nv, sizeof(int)); len = G->nv; /* # vertices */ len = len * (len - 1) / 2; /* # entries in lower triangle */ len = (len + (CHAR_BIT - 1)) / CHAR_BIT; /* # bytes needed */ a = xcalloc(len, sizeof(char)); memset(a, 0, len * sizeof(char)); /* determine vertex weights */ s = 0.0; for (i = 1; i <= G->nv; i++) { if (v_wgt >= 0) { memcpy(&t, (char *)G->v[i]->data + v_wgt, sizeof(double)); if (!(0.0 <= t && t <= (double)INT_MAX && t == floor(t))) { ret = GLP_EDATA; goto done; } w[i] = (int)t; } else w[i] = 1; s += (double)w[i]; } if (s > (double)INT_MAX) { ret = GLP_EDATA; goto done; } /* build the adjacency matrix */ for (i = 1; i <= G->nv; i++) { for (e = G->v[i]->in; e != NULL; e = e->h_next) { j = e->tail->i; /* there exists edge (j,i) in the graph */ if (i > j) set_edge(G->nv, a, i, j); } for (e = G->v[i]->out; e != NULL; e = e->t_next) { j = e->head->i; /* there exists edge (i,j) in the graph */ if (i > j) set_edge(G->nv, a, i, j); } } /* find maximum weight clique in the graph */ len = wclique(G->nv, w, a, ind); /* compute the clique weight */ s = 0.0; for (k = 1; k <= len; k++) { i = ind[k]; xassert(1 <= i && i <= G->nv); s += (double)w[i]; } if (sol != NULL) *sol = s; /* mark vertices included in the clique */ if (v_set >= 0) { x = 0; for (i = 1; i <= G->nv; i++) memcpy((char *)G->v[i]->data + v_set, &x, sizeof(int)); x = 1; for (k = 1; k <= len; k++) { i = ind[k]; memcpy((char *)G->v[i]->data + v_set, &x, sizeof(int)); } } done: /* free working arrays */ xfree(w); xfree(ind); xfree(a); return ret; } /* eof */ sources_5316/external/glpk/glphbm.h0000644000176700017670000001102011401660400016106 0ustar paulpaul/* glphbm.h (Harwell-Boeing sparse matrix format) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPHBM_H #define GLPHBM_H typedef struct HBM HBM; struct HBM { /* sparse matrix in Harwell-Boeing format; for details see the report: I.S.Duff, R.G.Grimes, J.G.Lewis. User's Guide for the Harwell-Boeing Sparse Matrix Collection (Release I), 1992 */ char title[72+1]; /* matrix title (informative) */ char key[8+1]; /* matrix key (informative) */ char mxtype[3+1]; /* matrix type: R.. real matrix C.. complex matrix P.. pattern only (no numerical values supplied) .S. symmetric (lower triangle + main diagonal) .U. unsymmetric .H. hermitian (lower triangle + main diagonal) .Z. skew symmetric (lower triangle only) .R. rectangular ..A assembled ..E elemental (unassembled) */ char rhstyp[3+1]; /* optional types: F.. right-hand sides in dense format M.. right-hand sides in same format as matrix .G. starting vector(s) (guess) is supplied ..X exact solution vector(s) is supplied */ char ptrfmt[16+1]; /* format for pointers */ char indfmt[16+1]; /* format for row (or variable) indices */ char valfmt[20+1]; /* format for numerical values of coefficient matrix */ char rhsfmt[20+1]; /* format for numerical values of right-hand sides */ int totcrd; /* total number of cards excluding header */ int ptrcrd; /* number of cards for ponters */ int indcrd; /* number of cards for row (or variable) indices */ int valcrd; /* number of cards for numerical values */ int rhscrd; /* number of lines for right-hand sides; including starting guesses and solution vectors if present; zero indicates no right-hand side data is present */ int nrow; /* number of rows (or variables) */ int ncol; /* number of columns (or elements) */ int nnzero; /* number of row (or variable) indices; equal to number of entries for assembled matrix */ int neltvl; /* number of elemental matrix entries; zero in case of assembled matrix */ int nrhs; /* number of right-hand sides */ int nrhsix; /* number of row indices; ignored in case of unassembled matrix */ int nrhsvl; /* total number of entries in all right-hand sides */ int nguess; /* total number of entries in all starting guesses */ int nexact; /* total number of entries in all solution vectors */ int *colptr; /* alias: eltptr */ /* column pointers (in case of assembled matrix); elemental matrix pointers (in case of unassembled matrix) */ int *rowind; /* alias: varind */ /* row indices (in case of assembled matrix); variable indices (in case of unassembled matrix) */ int *rhsptr; /* right-hand side pointers */ int *rhsind; /* right-hand side indices */ double *values; /* matrix values */ double *rhsval; /* right-hand side values */ double *sguess; /* starting guess values */ double *xexact; /* solution vector values */ }; #define hbm_read_mat _glp_hbm_read_mat HBM *hbm_read_mat(const char *fname); /* read sparse matrix in Harwell-Boeing format */ #define hbm_free_mat _glp_hbm_free_mat void hbm_free_mat(HBM *hbm); /* free sparse matrix in Harwell-Boeing format */ #endif /* eof */ sources_5316/external/glpk/glpsql.c0000644000176700017670000013117111401660400016144 0ustar paulpaul/* glpsql.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Author: Heinrich Schuchardt . * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifdef HAVE_CONFIG_H #include #endif #include "glpmpl.h" #include "glpsql.h" #ifdef ODBC_DLNAME #define HAVE_ODBC #define libodbc ODBC_DLNAME #define h_odbc (get_env_ptr()->h_odbc) #endif #ifdef MYSQL_DLNAME #define HAVE_MYSQL #define libmysql MYSQL_DLNAME #define h_mysql (get_env_ptr()->h_mysql) #endif static void *db_iodbc_open_int(TABDCA *dca, int mode, const char **sqllines); static void *db_mysql_open_int(TABDCA *dca, int mode, const char **sqllines); /**********************************************************************/ #if defined(HAVE_ODBC) || defined(HAVE_MYSQL) #define SQL_FIELD_MAX 100 /* maximal field count */ #define SQL_FDLEN_MAX 255 /* maximal field length */ /*********************************************************************** * NAME * * args_concat - concatenate arguments * * SYNOPSIS * * static char **args_concat(TABDCA *dca); * * DESCRIPTION * * The arguments passed in dca are SQL statements. A SQL statement may * be split over multiple arguments. The last argument of a SQL * statement will be terminated with a semilocon. Each SQL statement is * merged into a single zero terminated string. Boundaries between * arguments are replaced by space. * * RETURNS * * Buffer with SQL statements */ static char **args_concat(TABDCA *dca) { const char *arg; int i; int j; int j0; int j1; int len; int lentot; int narg; int nline = 0; void *ret; char **sqllines = NULL; narg = mpl_tab_num_args(dca); /* The SQL statements start with argument 3. */ if (narg < 3) return NULL; /* Count the SQL statements */ for (j = 3; j <= narg; j++) { arg = mpl_tab_get_arg(dca, j); len = strlen(arg); if (arg[len-1] == ';' || j == narg) nline ++; } /* Allocate string buffer. */ sqllines = (char **) xmalloc((nline+1) * sizeof(char **)); /* Join arguments */ sqllines[0] = NULL; j0 = 3; i = 0; lentot = 0; for (j = 3; j <= narg; j++) { arg = mpl_tab_get_arg(dca, j); len = strlen(arg); lentot += len; if (arg[len-1] == ';' || j == narg) { /* Join arguments for a single SQL statement */ sqllines[i] = xmalloc(lentot+1); sqllines[i+1] = NULL; sqllines[i][0] = 0x00; for (j1 = j0; j1 <= j; j1++) { if(j1>j0) strcat(sqllines[i], " "); strcat(sqllines[i], mpl_tab_get_arg(dca, j1)); } len = strlen(sqllines[i]); if (sqllines[i][len-1] == ';') sqllines[i][len-1] = 0x00; j0 = j+1; i++; lentot = 0; } } return sqllines; } /*********************************************************************** * NAME * * free_buffer - free multiline string buffer * * SYNOPSIS * * static void free_buffer(char **buf); * * DESCRIPTION * * buf is a list of strings terminated by NULL. * The memory for the strings and for the list is released. */ static void free_buffer(char **buf) { int i; for(i = 0; buf[i] != NULL; i++) xfree(buf[i]); xfree(buf); } static int db_escaped_string_length(const char* from) /* length of escaped string */ { int count; const char *pointer; for (pointer = from, count = 0; *pointer != (char) '\0'; pointer++, count++) { switch (*pointer) { case '\'': count++; break; } } return count; } static int db_escape_string (char *to, const char *from) /* escape string*/ { const char *source = from; char *target = to; unsigned int remaining; remaining = strlen(from); if (to == NULL) to = (char *) (from + remaining); while (remaining > 0) { switch (*source) { case '\'': *target = '\''; target++; *target = '\''; break; default: *target = *source; } source++; target++; remaining--; } /* Write the terminating NUL character. */ *target = '\0'; return target - to; } static char *db_generate_select_stmt(TABDCA *dca) /* generate select statement */ { char *arg; char const *field; char *query; int j; int narg; int nf; int total; total = 50; nf = mpl_tab_num_flds(dca); narg = mpl_tab_num_args(dca); for (j=1; j <= nf && j <= SQL_FIELD_MAX; j++) { field = mpl_tab_get_name(dca, j); total += strlen(field); total += 2; } arg = (char *) mpl_tab_get_arg(dca, narg); total += strlen(arg); query = xmalloc( total * sizeof(char)); strcpy (query, "SELECT "); for (j=1; j <= nf && j <= SQL_FIELD_MAX; j++) { field = mpl_tab_get_name(dca, j); strcat(query, field); if ( j < nf ) strcat(query, ", "); } strcat(query, " FROM "); strcat(query, arg); return query; } static char *db_generate_insert_stmt(TABDCA *dca) /* generate insert statement */ { char *arg; char const *field; char *query; int j; int narg; int nf; int total; total = 50; nf = mpl_tab_num_flds(dca); narg = mpl_tab_num_args(dca); for (j=1; j <= nf && j <= SQL_FIELD_MAX; j++) { field = mpl_tab_get_name(dca, j); total += strlen(field); total += 5; } arg = (char *) mpl_tab_get_arg(dca, narg); total += strlen(arg); query = xmalloc( (total+1) * sizeof(char)); strcpy (query, "INSERT INTO "); strcat(query, arg); strcat(query, " ( "); for (j=1; j <= nf && j <= SQL_FIELD_MAX; j++) { field = mpl_tab_get_name(dca, j); strcat(query, field); if ( j < nf ) strcat(query, ", "); } strcat(query, " ) VALUES ( "); for (j=1; j <= nf && j <= SQL_FIELD_MAX; j++) { strcat(query, "?"); if ( j < nf ) strcat(query, ", "); } strcat(query, " )"); return query; } #endif /**********************************************************************/ #ifndef HAVE_ODBC void *db_iodbc_open(TABDCA *dca, int mode) { xassert(dca == dca); xassert(mode == mode); xprintf("iODBC table driver not supported\n"); return NULL; } int db_iodbc_read(TABDCA *dca, void *link) { xassert(dca != dca); xassert(link != link); return 0; } int db_iodbc_write(TABDCA *dca, void *link) { xassert(dca != dca); xassert(link != link); return 0; } int db_iodbc_close(TABDCA *dca, void *link) { xassert(dca != dca); xassert(link != link); return 0; } #else #if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__WOE__) #include #endif #include #include struct db_odbc { int mode; /*'R' = Read, 'W' = Write*/ SQLHDBC hdbc; /*connection handle*/ SQLHENV henv; /*environment handle*/ SQLHSTMT hstmt; /*statement handle*/ SQLSMALLINT nresultcols; /* columns in result*/ SQLULEN collen[SQL_FIELD_MAX+1]; SQLLEN outlen[SQL_FIELD_MAX+1]; SQLSMALLINT coltype[SQL_FIELD_MAX+1]; SQLCHAR data[SQL_FIELD_MAX+1][SQL_FDLEN_MAX+1]; SQLCHAR colname[SQL_FIELD_MAX+1][SQL_FDLEN_MAX+1]; int isnumeric[SQL_FIELD_MAX+1]; int nf; /* number of fields in the csv file */ int ref[1+SQL_FIELD_MAX]; /* ref[k] = k', if k-th field of the csv file corresponds to k'-th field in the table statement; if ref[k] = 0, k-th field of the csv file is ignored */ SQLCHAR *query; /* query generated by db_iodbc_open */ }; SQLRETURN SQL_API dl_SQLAllocHandle ( SQLSMALLINT HandleType, SQLHANDLE InputHandle, SQLHANDLE *OutputHandle) { typedef SQLRETURN SQL_API ep_SQLAllocHandle( SQLSMALLINT HandleType, SQLHANDLE InputHandle, SQLHANDLE *OutputHandle); ep_SQLAllocHandle *fn; fn = (ep_SQLAllocHandle *) xdlsym(h_odbc, "SQLAllocHandle"); xassert(fn != NULL); return (*fn)(HandleType, InputHandle, OutputHandle); } SQLRETURN SQL_API dl_SQLBindCol ( SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber, SQLSMALLINT TargetType, SQLPOINTER TargetValue, SQLLEN BufferLength, SQLLEN *StrLen_or_Ind) { typedef SQLRETURN SQL_API ep_SQLBindCol( SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber, SQLSMALLINT TargetType, SQLPOINTER TargetValue, SQLLEN BufferLength, SQLLEN *StrLen_or_Ind); ep_SQLBindCol *fn; fn = (ep_SQLBindCol *) xdlsym(h_odbc, "SQLBindCol"); xassert(fn != NULL); return (*fn)(StatementHandle, ColumnNumber, TargetType, TargetValue, BufferLength, StrLen_or_Ind); } SQLRETURN SQL_API dl_SQLCloseCursor ( SQLHSTMT StatementHandle) { typedef SQLRETURN SQL_API ep_SQLCloseCursor ( SQLHSTMT StatementHandle); ep_SQLCloseCursor *fn; fn = (ep_SQLCloseCursor *) xdlsym(h_odbc, "SQLCloseCursor"); xassert(fn != NULL); return (*fn)(StatementHandle); } SQLRETURN SQL_API dl_SQLDisconnect ( SQLHDBC ConnectionHandle) { typedef SQLRETURN SQL_API ep_SQLDisconnect( SQLHDBC ConnectionHandle); ep_SQLDisconnect *fn; fn = (ep_SQLDisconnect *) xdlsym(h_odbc, "SQLDisconnect"); xassert(fn != NULL); return (*fn)(ConnectionHandle); } SQLRETURN SQL_API dl_SQLDriverConnect ( SQLHDBC hdbc, SQLHWND hwnd, SQLCHAR *szConnStrIn, SQLSMALLINT cbConnStrIn, SQLCHAR *szConnStrOut, SQLSMALLINT cbConnStrOutMax, SQLSMALLINT *pcbConnStrOut, SQLUSMALLINT fDriverCompletion) { typedef SQLRETURN SQL_API ep_SQLDriverConnect( SQLHDBC hdbc, SQLHWND hwnd, SQLCHAR * szConnStrIn, SQLSMALLINT cbConnStrIn, SQLCHAR * szConnStrOut, SQLSMALLINT cbConnStrOutMax, SQLSMALLINT * pcbConnStrOut, SQLUSMALLINT fDriverCompletion); ep_SQLDriverConnect *fn; fn = (ep_SQLDriverConnect *) xdlsym(h_odbc, "SQLDriverConnect"); xassert(fn != NULL); return (*fn)(hdbc, hwnd, szConnStrIn, cbConnStrIn, szConnStrOut, cbConnStrOutMax, pcbConnStrOut, fDriverCompletion); } SQLRETURN SQL_API dl_SQLEndTran ( SQLSMALLINT HandleType, SQLHANDLE Handle, SQLSMALLINT CompletionType) { typedef SQLRETURN SQL_API ep_SQLEndTran ( SQLSMALLINT HandleType, SQLHANDLE Handle, SQLSMALLINT CompletionType); ep_SQLEndTran *fn; fn = (ep_SQLEndTran *) xdlsym(h_odbc, "SQLEndTran"); xassert(fn != NULL); return (*fn)(HandleType, Handle, CompletionType); } SQLRETURN SQL_API dl_SQLExecDirect ( SQLHSTMT StatementHandle, SQLCHAR * StatementText, SQLINTEGER TextLength) { typedef SQLRETURN SQL_API ep_SQLExecDirect ( SQLHSTMT StatementHandle, SQLCHAR * StatementText, SQLINTEGER TextLength); ep_SQLExecDirect *fn; fn = (ep_SQLExecDirect *) xdlsym(h_odbc, "SQLExecDirect"); xassert(fn != NULL); return (*fn)(StatementHandle, StatementText, TextLength); } SQLRETURN SQL_API dl_SQLFetch ( SQLHSTMT StatementHandle) { typedef SQLRETURN SQL_API ep_SQLFetch ( SQLHSTMT StatementHandle); ep_SQLFetch *fn; fn = (ep_SQLFetch*) xdlsym(h_odbc, "SQLFetch"); xassert(fn != NULL); return (*fn)(StatementHandle); } SQLRETURN SQL_API dl_SQLFreeHandle ( SQLSMALLINT HandleType, SQLHANDLE Handle) { typedef SQLRETURN SQL_API ep_SQLFreeHandle ( SQLSMALLINT HandleType, SQLHANDLE Handle); ep_SQLFreeHandle *fn; fn = (ep_SQLFreeHandle *) xdlsym(h_odbc, "SQLFreeHandle"); xassert(fn != NULL); return (*fn)(HandleType, Handle); } SQLRETURN SQL_API dl_SQLDescribeCol ( SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber, SQLCHAR * ColumnName, SQLSMALLINT BufferLength, SQLSMALLINT * NameLength, SQLSMALLINT * DataType, SQLULEN * ColumnSize, SQLSMALLINT * DecimalDigits, SQLSMALLINT * Nullable) { typedef SQLRETURN SQL_API ep_SQLDescribeCol ( SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber, SQLCHAR *ColumnName, SQLSMALLINT BufferLength, SQLSMALLINT *NameLength, SQLSMALLINT *DataType, SQLULEN *ColumnSize, SQLSMALLINT *DecimalDigits, SQLSMALLINT *Nullable); ep_SQLDescribeCol *fn; fn = (ep_SQLDescribeCol *) xdlsym(h_odbc, "SQLDescribeCol"); xassert(fn != NULL); return (*fn)(StatementHandle, ColumnNumber, ColumnName, BufferLength, NameLength, DataType, ColumnSize, DecimalDigits, Nullable); } SQLRETURN SQL_API dl_SQLGetDiagRec ( SQLSMALLINT HandleType, SQLHANDLE Handle, SQLSMALLINT RecNumber, SQLCHAR *Sqlstate, SQLINTEGER *NativeError, SQLCHAR *MessageText, SQLSMALLINT BufferLength, SQLSMALLINT *TextLength) { typedef SQLRETURN SQL_API ep_SQLGetDiagRec ( SQLSMALLINT HandleType, SQLHANDLE Handle, SQLSMALLINT RecNumber, SQLCHAR *Sqlstate, SQLINTEGER *NativeError, SQLCHAR *MessageText, SQLSMALLINT BufferLength, SQLSMALLINT *TextLength); ep_SQLGetDiagRec *fn; fn = (ep_SQLGetDiagRec *) xdlsym(h_odbc, "SQLGetDiagRec"); xassert(fn != NULL); return (*fn)(HandleType, Handle, RecNumber, Sqlstate, NativeError, MessageText, BufferLength, TextLength); } SQLRETURN SQL_API dl_SQLGetInfo ( SQLHDBC ConnectionHandle, SQLUSMALLINT InfoType, SQLPOINTER InfoValue, SQLSMALLINT BufferLength, SQLSMALLINT *StringLength) { typedef SQLRETURN SQL_API ep_SQLGetInfo ( SQLHDBC ConnectionHandle, SQLUSMALLINT InfoType, SQLPOINTER InfoValue, SQLSMALLINT BufferLength, SQLSMALLINT *StringLength); ep_SQLGetInfo *fn; fn = (ep_SQLGetInfo *) xdlsym(h_odbc, "SQLGetInfo"); xassert(fn != NULL); return (*fn)(ConnectionHandle, InfoType, InfoValue, BufferLength, StringLength); } SQLRETURN SQL_API dl_SQLNumResultCols ( SQLHSTMT StatementHandle, SQLSMALLINT *ColumnCount) { typedef SQLRETURN SQL_API ep_SQLNumResultCols ( SQLHSTMT StatementHandle, SQLSMALLINT *ColumnCount); ep_SQLNumResultCols *fn; fn = (ep_SQLNumResultCols *) xdlsym(h_odbc, "SQLNumResultCols"); xassert(fn != NULL); return (*fn)(StatementHandle, ColumnCount); } SQLRETURN SQL_API dl_SQLSetConnectAttr ( SQLHDBC ConnectionHandle, SQLINTEGER Attribute, SQLPOINTER Value, SQLINTEGER StringLength) { typedef SQLRETURN SQL_API ep_SQLSetConnectAttr ( SQLHDBC ConnectionHandle, SQLINTEGER Attribute, SQLPOINTER Value, SQLINTEGER StringLength); ep_SQLSetConnectAttr *fn; fn = (ep_SQLSetConnectAttr *) xdlsym(h_odbc, "SQLSetConnectAttr"); xassert(fn != NULL); return (*fn)(ConnectionHandle, Attribute, Value, StringLength); } SQLRETURN SQL_API dl_SQLSetEnvAttr ( SQLHENV EnvironmentHandle, SQLINTEGER Attribute, SQLPOINTER Value, SQLINTEGER StringLength) { typedef SQLRETURN SQL_API ep_SQLSetEnvAttr ( SQLHENV EnvironmentHandle, SQLINTEGER Attribute, SQLPOINTER Value, SQLINTEGER StringLength); ep_SQLSetEnvAttr *fn; fn = (ep_SQLSetEnvAttr *) xdlsym(h_odbc, "SQLSetEnvAttr"); xassert(fn != NULL); return (*fn)(EnvironmentHandle, Attribute, Value, StringLength); } static void extract_error( char *fn, SQLHANDLE handle, SQLSMALLINT type); static int is_numeric( SQLSMALLINT coltype); /*********************************************************************** * NAME * * db_iodbc_open - open connection to ODBC data base * * SYNOPSIS * * #include "glpsql.h" * void *db_iodbc_open(TABDCA *dca, int mode); * * DESCRIPTION * * The routine db_iodbc_open opens a connection to an ODBC data base. * It then executes the sql statements passed. * * In the case of table read the SELECT statement is executed. * * In the case of table write the INSERT statement is prepared. * RETURNS * * The routine returns a pointer to data storage area created. */ void *db_iodbc_open(TABDCA *dca, int mode) { void *ret; char **sqllines; sqllines = args_concat(dca); if (sqllines == NULL) { xprintf("Missing arguments in table statement.\n" "Please, supply table driver, dsn, and query.\n"); return NULL; } ret = db_iodbc_open_int(dca, mode, (const char **) sqllines); free_buffer(sqllines); return ret; } static void *db_iodbc_open_int(TABDCA *dca, int mode, const char **sqllines) { struct db_odbc *sql; SQLRETURN ret; SQLCHAR FAR *dsn; SQLCHAR info[256]; SQLSMALLINT colnamelen; SQLSMALLINT nullable; SQLSMALLINT scale; const char *arg; int narg; int i, j; int total; if (libodbc == NULL) { xprintf("No loader for shared ODBC library available\n"); return NULL; } if (h_odbc == NULL) { h_odbc = xdlopen(libodbc); if (h_odbc == NULL) { xprintf("unable to open library %s\n", libodbc); xprintf("%s\n", xerrmsg()); return NULL; } } sql = (struct db_odbc *) xmalloc(sizeof(struct db_odbc)); if (sql == NULL) return NULL; sql->mode = mode; sql->hdbc = NULL; sql->henv = NULL; sql->hstmt = NULL; sql->query = NULL; narg = mpl_tab_num_args(dca); dsn = (SQLCHAR FAR *) mpl_tab_get_arg(dca, 2); /* allocate an environment handle */ ret = dl_SQLAllocHandle(SQL_HANDLE_ENV, SQL_NULL_HANDLE, &(sql->henv)); /* set attribute to enable application to run as ODBC 3.0 application */ ret = dl_SQLSetEnvAttr(sql->henv, SQL_ATTR_ODBC_VERSION, (void *) SQL_OV_ODBC3, 0); /* allocate a connection handle */ ret = dl_SQLAllocHandle(SQL_HANDLE_DBC, sql->henv, &(sql->hdbc)); /* connect */ ret = dl_SQLDriverConnect(sql->hdbc, NULL, dsn, SQL_NTS, NULL, 0, NULL, SQL_DRIVER_COMPLETE); if (SQL_SUCCEEDED(ret)) { /* output information about data base connection */ xprintf("Connected to "); dl_SQLGetInfo(sql->hdbc, SQL_DBMS_NAME, (SQLPOINTER)info, sizeof(info), NULL); xprintf("%s ", info); dl_SQLGetInfo(sql->hdbc, SQL_DBMS_VER, (SQLPOINTER)info, sizeof(info), NULL); xprintf("%s - ", info); dl_SQLGetInfo(sql->hdbc, SQL_DATABASE_NAME, (SQLPOINTER)info, sizeof(info), NULL); xprintf("%s\n", info); } else { /* describe error */ xprintf("Failed to connect\n"); extract_error("SQLDriverConnect", sql->hdbc, SQL_HANDLE_DBC); dl_SQLFreeHandle(SQL_HANDLE_DBC, sql->hdbc); dl_SQLFreeHandle(SQL_HANDLE_ENV, sql->henv); xfree(sql); return NULL; } /* set AUTOCOMMIT on*/ ret = dl_SQLSetConnectAttr(sql->hdbc, SQL_ATTR_AUTOCOMMIT, (SQLPOINTER)SQL_AUTOCOMMIT_ON, 0); /* allocate a statement handle */ ret = dl_SQLAllocHandle(SQL_HANDLE_STMT, sql->hdbc, &(sql->hstmt)); /* initialization queries */ for(j = 0; sqllines[j+1] != NULL; j++) { sql->query = (SQLCHAR *) sqllines[j]; xprintf("%s\n", sql->query); ret = dl_SQLExecDirect(sql->hstmt, sql->query, SQL_NTS); switch (ret) { case SQL_SUCCESS: case SQL_SUCCESS_WITH_INFO: case SQL_NO_DATA_FOUND: break; default: xprintf("db_iodbc_open: Query\n\"%s\"\nfailed.\n", sql->query); extract_error("SQLExecDirect", sql->hstmt, SQL_HANDLE_STMT); dl_SQLFreeHandle(SQL_HANDLE_STMT, sql->hstmt); dl_SQLDisconnect(sql->hdbc); dl_SQLFreeHandle(SQL_HANDLE_DBC, sql->hdbc); dl_SQLFreeHandle(SQL_HANDLE_ENV, sql->henv); xfree(sql); return NULL; } /* commit statement */ dl_SQLEndTran(SQL_HANDLE_ENV, sql->henv, SQL_COMMIT); } if ( sql->mode == 'R' ) { sql->nf = mpl_tab_num_flds(dca); for(j = 0; sqllines[j] != NULL; j++) arg = sqllines[j]; total = strlen(arg); if (total > 7 && 0 == strncmp(arg, "SELECT ", 7)) { total = strlen(arg); sql->query = xmalloc( (total+1) * sizeof(char)); strcpy (sql->query, arg); } else { sql->query = db_generate_select_stmt(dca); } xprintf("%s\n", sql->query); if (dl_SQLExecDirect(sql->hstmt, sql->query, SQL_NTS) != SQL_SUCCESS) { xprintf("db_iodbc_open: Query\n\"%s\"\nfailed.\n", sql->query); extract_error("SQLExecDirect", sql->hstmt, SQL_HANDLE_STMT); dl_SQLFreeHandle(SQL_HANDLE_STMT, sql->hstmt); dl_SQLDisconnect(sql->hdbc); dl_SQLFreeHandle(SQL_HANDLE_DBC, sql->hdbc); dl_SQLFreeHandle(SQL_HANDLE_ENV, sql->henv); xfree(sql->query); xfree(sql); return NULL; } xfree(sql->query); /* determine number of result columns */ ret = dl_SQLNumResultCols(sql->hstmt, &sql->nresultcols); total = sql->nresultcols; if (total > SQL_FIELD_MAX) { xprintf("db_iodbc_open: Too many fields (> %d) in query.\n" "\"%s\"\n", SQL_FIELD_MAX, sql->query); dl_SQLFreeHandle(SQL_HANDLE_STMT, sql->hstmt); dl_SQLDisconnect(sql->hdbc); dl_SQLFreeHandle(SQL_HANDLE_DBC, sql->hdbc); dl_SQLFreeHandle(SQL_HANDLE_ENV, sql->henv); xfree(sql->query); return NULL; } for (i = 1; i <= total; i++) { /* return a set of attributes for a column */ ret = dl_SQLDescribeCol(sql->hstmt, (SQLSMALLINT) i, sql->colname[i], SQL_FDLEN_MAX, &colnamelen, &(sql->coltype[i]), &(sql->collen[i]), &scale, &nullable); sql->isnumeric[i] = is_numeric(sql->coltype[i]); /* bind columns to program vars, converting all types to CHAR*/ dl_SQLBindCol(sql->hstmt, i, SQL_CHAR, sql->data[i], SQL_FDLEN_MAX, &(sql->outlen[i])); for (j = sql->nf; j >= 1; j--) { if (strcmp(mpl_tab_get_name(dca, j), sql->colname[i]) == 0) break; } sql->ref[i] = j; } } else if ( sql->mode == 'W' ) { for(j = 0; sqllines[j] != NULL; j++) arg = sqllines[j]; if ( NULL != strchr(arg, '?') ) { total = strlen(arg); sql->query = xmalloc( (total+1) * sizeof(char)); strcpy (sql->query, arg); } else { sql->query = db_generate_insert_stmt(dca); } xprintf("%s\n", sql->query); } return sql; } int db_iodbc_read(TABDCA *dca, void *link) { struct db_odbc *sql; SQLRETURN ret; char buf[SQL_FDLEN_MAX+1]; int i; int len; double num; sql = (struct db_odbc *) link; xassert(sql != NULL); xassert(sql->mode == 'R'); ret=dl_SQLFetch(sql->hstmt); if (ret== SQL_ERROR) return -1; if (ret== SQL_NO_DATA_FOUND) return -1; /*EOF*/ for (i=1; i <= sql->nresultcols; i++) { if (sql->ref[i] > 0) { len = sql->outlen[i]; if (len != SQL_NULL_DATA) { if (len > SQL_FDLEN_MAX) len = SQL_FDLEN_MAX; else if (len < 0) len = 0; strncpy(buf, (const char *) sql->data[i], len); buf[len] = 0x00; if (0 != (sql->isnumeric[i])) { strspx(buf); /* remove spaces*/ if (str2num(buf, &num) != 0) { xprintf("'%s' cannot be converted to a number.\n", buf); return 1; } mpl_tab_set_num(dca, sql->ref[i], num); } else { mpl_tab_set_str(dca, sql->ref[i], strtrim(buf)); } } } } return 0; } int db_iodbc_write(TABDCA *dca, void *link) { struct db_odbc *sql; char *part; char *query; char *template; char num[50]; int k; int len; int nf; sql = (struct db_odbc *) link; xassert(sql != NULL); xassert(sql->mode == 'W'); len = strlen(sql->query); template = (char *) xmalloc( (len + 1) * sizeof(char) ); strcpy(template, sql->query); nf = mpl_tab_num_flds(dca); for (k = 1; k <= nf; k++) { switch (mpl_tab_get_type(dca, k)) { case 'N': len += 20; break; case 'S': len += db_escaped_string_length(mpl_tab_get_str(dca, k)); len += 2; break; default: xassert(dca != dca); } } query = xmalloc( (len + 1 ) * sizeof(char) ); query[0] = 0x00; for (k = 1, part = strtok (template, "?"); (part != NULL); part = strtok (NULL, "?"), k++) { if (k > nf) break; strcat( query, part ); switch (mpl_tab_get_type(dca, k)) { case 'N': sprintf(num, "%-18g",mpl_tab_get_num(dca, k)); strcat( query, num ); break; case 'S': strcat( query, "'"); db_escape_string( query + strlen(query), mpl_tab_get_str(dca, k) ); strcat( query, "'"); break; default: xassert(dca != dca); } } if (part != NULL) strcat(query, part); if (dl_SQLExecDirect(sql->hstmt, (SQLCHAR *) query, SQL_NTS) != SQL_SUCCESS) { xprintf("db_iodbc_write: Query\n\"%s\"\nfailed.\n", query); extract_error("SQLExecDirect", sql->hdbc, SQL_HANDLE_DBC); xfree(query); xfree(template); return 1; } xfree(query); xfree(template); return 0; } int db_iodbc_close(TABDCA *dca, void *link) { struct db_odbc *sql; sql = (struct db_odbc *) link; xassert(sql != NULL); /* Commit */ if ( sql->mode == 'W' ) dl_SQLEndTran(SQL_HANDLE_ENV, sql->henv, SQL_COMMIT); if ( sql->mode == 'R' ) dl_SQLCloseCursor(sql->hstmt); dl_SQLFreeHandle(SQL_HANDLE_STMT, sql->hstmt); dl_SQLDisconnect(sql->hdbc); dl_SQLFreeHandle(SQL_HANDLE_DBC, sql->hdbc); dl_SQLFreeHandle(SQL_HANDLE_ENV, sql->henv); if ( sql->mode == 'W' ) xfree(sql->query); xfree(sql); dca->link = NULL; return 0; } static void extract_error( char *fn, SQLHANDLE handle, SQLSMALLINT type) { SQLINTEGER i = 0; SQLINTEGER native; SQLCHAR state[ 7 ]; SQLCHAR text[256]; SQLSMALLINT len; SQLRETURN ret; xprintf("\nThe driver reported the following diagnostics whilst " "running %s\n", fn); do { ret = dl_SQLGetDiagRec(type, handle, ++i, state, &native, text, sizeof(text), &len ); if (SQL_SUCCEEDED(ret)) xprintf("%s:%ld:%ld:%s\n", state, i, native, text); } while( ret == SQL_SUCCESS ); } static int is_numeric(SQLSMALLINT coltype) { int ret = 0; switch (coltype) { case SQL_DECIMAL: case SQL_NUMERIC: case SQL_SMALLINT: case SQL_INTEGER: case SQL_REAL: case SQL_FLOAT: case SQL_DOUBLE: case SQL_TINYINT: case SQL_BIGINT: ret = 1; break; } return ret; } #endif /**********************************************************************/ #ifndef HAVE_MYSQL void *db_mysql_open(TABDCA *dca, int mode) { xassert(dca == dca); xassert(mode == mode); xprintf("MySQL table driver not supported\n"); return NULL; } int db_mysql_read(TABDCA *dca, void *link) { xassert(dca != dca); xassert(link != link); return 0; } int db_mysql_write(TABDCA *dca, void *link) { xassert(dca != dca); xassert(link != link); return 0; } int db_mysql_close(TABDCA *dca, void *link) { xassert(dca != dca); xassert(link != link); return 0; } #else #if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__WOE__) #include #endif #ifdef __CYGWIN__ #define byte_defined 1 #endif #include #include #include struct db_mysql { int mode; /*'R' = Read, 'W' = Write*/ MYSQL *con; /*connection*/ MYSQL_RES *res; /*result*/ int nf; /* number of fields in the csv file */ int ref[1+SQL_FIELD_MAX]; /* ref[k] = k', if k-th field of the csv file corresponds to k'-th field in the table statement; if ref[k] = 0, k-th field of the csv file is ignored */ char *query; /* query generated by db_mysql_open */ }; void STDCALL dl_mysql_close(MYSQL *sock) { typedef void STDCALL ep_mysql_close(MYSQL *sock); ep_mysql_close *fn; fn = (ep_mysql_close *) xdlsym(h_mysql, "mysql_close"); xassert(fn != NULL); return (*fn)(sock); } const char * STDCALL dl_mysql_error(MYSQL *mysql) { typedef const char * STDCALL ep_mysql_error(MYSQL *mysql); ep_mysql_error *fn; fn = (ep_mysql_error *) xdlsym(h_mysql, "mysql_error"); xassert(fn != NULL); return (*fn)(mysql); } MYSQL_FIELD * STDCALL dl_mysql_fetch_fields(MYSQL_RES *res) { typedef MYSQL_FIELD * STDCALL ep_mysql_fetch_fields(MYSQL_RES *res); ep_mysql_fetch_fields *fn; fn = (ep_mysql_fetch_fields *) xdlsym(h_mysql, "mysql_fetch_fields"); xassert(fn != NULL); return (*fn)(res); } unsigned long * STDCALL dl_mysql_fetch_lengths(MYSQL_RES *result) { typedef unsigned long * STDCALL ep_mysql_fetch_lengths(MYSQL_RES *result); ep_mysql_fetch_lengths *fn; fn = (ep_mysql_fetch_lengths *) xdlsym(h_mysql, "mysql_fetch_lengths"); xassert(fn != NULL); return (*fn)(result); } MYSQL_ROW STDCALL dl_mysql_fetch_row(MYSQL_RES *result) { typedef MYSQL_ROW STDCALL ep_mysql_fetch_row(MYSQL_RES *result); ep_mysql_fetch_row *fn; fn = (ep_mysql_fetch_row *) xdlsym(h_mysql, "mysql_fetch_row"); xassert(fn != NULL); return (*fn)(result); } unsigned int STDCALL dl_mysql_field_count(MYSQL *mysql) { typedef unsigned int STDCALL ep_mysql_field_count(MYSQL *mysql); ep_mysql_field_count *fn; fn = (ep_mysql_field_count *) xdlsym(h_mysql, "mysql_field_count"); xassert(fn != NULL); return (*fn)(mysql); } MYSQL * STDCALL dl_mysql_init(MYSQL *mysql) { typedef MYSQL * STDCALL ep_mysql_init(MYSQL *mysql); ep_mysql_init *fn; fn = (ep_mysql_init *) xdlsym(h_mysql, "mysql_init"); xassert(fn != NULL); return (*fn)(mysql); } unsigned int STDCALL dl_mysql_num_fields(MYSQL_RES *res) { typedef unsigned int STDCALL ep_mysql_num_fields(MYSQL_RES *res); ep_mysql_num_fields *fn; fn = (ep_mysql_num_fields *) xdlsym(h_mysql, "mysql_num_fields"); xassert(fn != NULL); return (*fn)(res); } int STDCALL dl_mysql_query(MYSQL *mysql, const char *q) { typedef int STDCALL ep_mysql_query(MYSQL *mysql, const char *q); ep_mysql_query *fn; fn = (ep_mysql_query *) xdlsym(h_mysql, "mysql_query"); xassert(fn != NULL); return (*fn)(mysql, q); } MYSQL * STDCALL dl_mysql_real_connect(MYSQL *mysql, const char *host, const char *user, const char *passwd, const char *db, unsigned int port, const char *unix_socket, unsigned long clientflag) { typedef MYSQL * STDCALL ep_mysql_real_connect(MYSQL *mysql, const char *host, const char *user, const char *passwd, const char *db, unsigned int port, const char *unix_socket, unsigned long clientflag); ep_mysql_real_connect *fn; fn = (ep_mysql_real_connect *) xdlsym(h_mysql, "mysql_real_connect"); xassert(fn != NULL); return (*fn)(mysql, host, user, passwd, db, port, unix_socket, clientflag); } MYSQL_RES * STDCALL dl_mysql_use_result(MYSQL *mysql) { typedef MYSQL_RES * STDCALL ep_mysql_use_result(MYSQL *mysql); ep_mysql_use_result *fn; fn = (ep_mysql_use_result *) xdlsym(h_mysql, "mysql_use_result"); xassert(fn != NULL); return (*fn)(mysql); } /*********************************************************************** * NAME * * db_mysql_open - open connection to ODBC data base * * SYNOPSIS * * #include "glpsql.h" * void *db_mysql_open(TABDCA *dca, int mode); * * DESCRIPTION * * The routine db_mysql_open opens a connection to a MySQL data base. * It then executes the sql statements passed. * * In the case of table read the SELECT statement is executed. * * In the case of table write the INSERT statement is prepared. * RETURNS * * The routine returns a pointer to data storage area created. */ void *db_mysql_open(TABDCA *dca, int mode) { void *ret; char **sqllines; sqllines = args_concat(dca); if (sqllines == NULL) { xprintf("Missing arguments in table statement.\n" "Please, supply table driver, dsn, and query.\n"); return NULL; } ret = db_mysql_open_int(dca, mode, (const char **) sqllines); free_buffer(sqllines); return ret; } static void *db_mysql_open_int(TABDCA *dca, int mode, const char **sqllines) { struct db_mysql *sql = NULL; char *arg = NULL; const char *field; MYSQL_FIELD *fields; char *keyword; char *value; char *query; char *dsn; /* "Server=[server_name];Database=[database_name];UID=[username];*/ /* PWD=[password];Port=[port]"*/ char *server = NULL; /* Server */ char *user = NULL; /* UID */ char *password = NULL; /* PWD */ char *database = NULL; /* Database */ unsigned int port = 0; /* Port */ int narg; int i, j, total; if (libmysql == NULL) { xprintf("No loader for shared MySQL library available\n"); return NULL; } if (h_mysql == NULL) { h_mysql = xdlopen(libmysql); if (h_mysql == NULL) { xprintf("unable to open library %s\n", libmysql); xprintf("%s\n", xerrmsg()); return NULL; } } sql = (struct db_mysql *) xmalloc(sizeof(struct db_mysql)); if (sql == NULL) return NULL; sql->mode = mode; sql->res = NULL; sql->query = NULL; sql->nf = mpl_tab_num_flds(dca); narg = mpl_tab_num_args(dca); if (narg < 3 ) xprintf("MySQL driver: string list too short \n"); /* get connection string*/ dsn = (char *) mpl_tab_get_arg(dca, 2); /* copy connection string*/ i = strlen(dsn); i++; arg = xmalloc(i * sizeof(char)); strcpy(arg, dsn); /*tokenize connection string*/ for (i = 1, keyword = strtok (arg, "="); (keyword != NULL); keyword = strtok (NULL, "="), i++) { value = strtok (NULL, ";"); if (value==NULL) { xprintf("db_mysql_open: Missing value for keyword %s\n", keyword); xfree(arg); xfree(sql); return NULL; } if (0 == strcmp(keyword, "Server")) server = value; else if (0 == strcmp(keyword, "Database")) database = value; else if (0 == strcmp(keyword, "UID")) user = value; else if (0 == strcmp(keyword, "PWD")) password = value; else if (0 == strcmp(keyword, "Port")) port = (unsigned int) atol(value); } /* Connect to database */ sql->con = dl_mysql_init(NULL); if (!dl_mysql_real_connect(sql->con, server, user, password, database, port, NULL, 0)) { xprintf("db_mysql_open: Connect failed\n"); xprintf("%s\n", dl_mysql_error(sql->con)); xfree(arg); xfree(sql); return NULL; } xfree(arg); for(j = 0; sqllines[j+1] != NULL; j++) { query = (char *) sqllines[j]; xprintf("%s\n", query); if (dl_mysql_query(sql->con, query)) { xprintf("db_mysql_open: Query\n\"%s\"\nfailed.\n", query); xprintf("%s\n",dl_mysql_error(sql->con)); dl_mysql_close(sql->con); xfree(sql); return NULL; } } if ( sql->mode == 'R' ) { sql->nf = mpl_tab_num_flds(dca); for(j = 0; sqllines[j] != NULL; j++) arg = (char *) sqllines[j]; total = strlen(arg); if (total > 7 && 0 == strncmp(arg, "SELECT ", 7)) { total = strlen(arg); query = xmalloc( (total+1) * sizeof(char)); strcpy (query, arg); } else { query = db_generate_select_stmt(dca); } xprintf("%s\n", query); if (dl_mysql_query(sql->con, query)) { xprintf("db_mysql_open: Query\n\"%s\"\nfailed.\n", query); xprintf("%s\n",dl_mysql_error(sql->con)); dl_mysql_close(sql->con); xfree(query); xfree(sql); return NULL; } xfree(query); sql->res = dl_mysql_use_result(sql->con); if (sql->res) { /* create references between query results and table fields*/ total = dl_mysql_num_fields(sql->res); if (total > SQL_FIELD_MAX) { xprintf("db_mysql_open: Too many fields (> %d) in query.\n" "\"%s\"\n", SQL_FIELD_MAX, query); xprintf("%s\n",dl_mysql_error(sql->con)); dl_mysql_close(sql->con); xfree(query); xfree(sql); return NULL; } fields = dl_mysql_fetch_fields(sql->res); for (i = 1; i <= total; i++) { for (j = sql->nf; j >= 1; j--) { if (strcmp(mpl_tab_get_name(dca, j), fields[i-1].name) == 0) break; } sql->ref[i] = j; } } else { if(dl_mysql_field_count(sql->con) == 0) { xprintf("db_mysql_open: Query was not a SELECT\n\"%s\"\n", query); xprintf("%s\n",dl_mysql_error(sql->con)); xfree(query); xfree(sql); return NULL; } else { xprintf("db_mysql_open: Query\n\"%s\"\nfailed.\n", query); xprintf("%s\n",dl_mysql_error(sql->con)); xfree(query); xfree(sql); return NULL; } } } else if ( sql->mode == 'W' ) { for(j = 0; sqllines[j] != NULL; j++) arg = (char *) sqllines[j]; if ( NULL != strchr(arg, '?') ) { total = strlen(arg); query = xmalloc( (total+1) * sizeof(char)); strcpy (query, arg); } else query = db_generate_insert_stmt(dca); sql->query = query; xprintf("%s\n", query); } return sql; } int db_mysql_read(TABDCA *dca, void *link) { struct db_mysql *sql; char buf[255+1]; char **row; unsigned long *lengths; MYSQL_FIELD *fields; double num; int len; unsigned long num_fields; int i; sql = (struct db_mysql *) link; xassert(sql != NULL); xassert(sql->mode == 'R'); if (NULL == sql->res) { xprintf("db_mysql_read: no result set available"); return 1; } if (NULL==(row = (char **)dl_mysql_fetch_row(sql->res))) { return -1; /*EOF*/ } lengths = dl_mysql_fetch_lengths(sql->res); fields = dl_mysql_fetch_fields(sql->res); num_fields = dl_mysql_num_fields(sql->res); for (i=1; i <= num_fields; i++) { if (row[i-1] != NULL) { len = (size_t) lengths[i-1]; if (len > 255) len = 255; strncpy(buf, (const char *) row[i-1], len); buf[len] = 0x00; if (0 != (fields[i-1].flags & NUM_FLAG)) { strspx(buf); /* remove spaces*/ if (str2num(buf, &num) != 0) { xprintf("'%s' cannot be converted to a number.\n", buf); return 1; } if (sql->ref[i] > 0) mpl_tab_set_num(dca, sql->ref[i], num); } else { if (sql->ref[i] > 0) mpl_tab_set_str(dca, sql->ref[i], strtrim(buf)); } } } return 0; } int db_mysql_write(TABDCA *dca, void *link) { struct db_mysql *sql; char *part; char *query; char *template; char num[50]; int k; int len; int nf; sql = (struct db_mysql *) link; xassert(sql != NULL); xassert(sql->mode == 'W'); len = strlen(sql->query); template = (char *) xmalloc( (len + 1) * sizeof(char) ); strcpy(template, sql->query); nf = mpl_tab_num_flds(dca); for (k = 1; k <= nf; k++) { switch (mpl_tab_get_type(dca, k)) { case 'N': len += 20; break; case 'S': len += db_escaped_string_length(mpl_tab_get_str(dca, k)); len += 2; break; default: xassert(dca != dca); } } query = xmalloc( (len + 1 ) * sizeof(char) ); query[0] = 0x00; for (k = 1, part = strtok (template, "?"); (part != NULL); part = strtok (NULL, "?"), k++) { if (k > nf) break; strcat( query, part ); switch (mpl_tab_get_type(dca, k)) { case 'N': sprintf(num, "%-18g",mpl_tab_get_num(dca, k)); strcat( query, num ); break; case 'S': strcat( query, "'"); db_escape_string( query + strlen(query), mpl_tab_get_str(dca, k) ); strcat( query, "'"); break; default: xassert(dca != dca); } } if (part != NULL) strcat(query, part); if (dl_mysql_query(sql->con, query)) { xprintf("db_mysql_write: Query\n\"%s\"\nfailed.\n", query); xprintf("%s\n",dl_mysql_error(sql->con)); xfree(query); xfree(template); return 1; } xfree(query); xfree(template); return 0; } int db_mysql_close(TABDCA *dca, void *link) { struct db_mysql *sql; sql = (struct db_mysql *) link; xassert(sql != NULL); dl_mysql_close(sql->con); if ( sql->mode == 'W' ) xfree(sql->query); xfree(sql); dca->link = NULL; return 0; } #endif /* eof */ sources_5316/external/glpk/glpipm.h0000644000176700017670000000245611401660400016142 0ustar paulpaul/* glpipm.h (primal-dual interior-point method) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPIPM_H #define GLPIPM_H #include "glpapi.h" #define ipm_solve _glp_ipm_solve int ipm_solve(glp_prob *P, const glp_iptcp *parm); /* core LP solver based on the interior-point method */ #endif /* eof */ sources_5316/external/glpk/amd_internal.h0000644000176700017670000000601011411461770017307 0ustar paulpaul/* amd_internal.h */ /* Written by Andrew Makhorin . */ #ifndef AMD_INTERNAL_H #define AMD_INTERNAL_H /* AMD will be exceedingly slow when running in debug mode. */ #if 1 #define NDEBUG #endif #include "amd.h" #define _GLPSTD_STDIO #include "glpenv.h" #define Int int #define ID "%d" #define Int_MAX INT_MAX #if !defined (SIZE_T_MAX) #define SIZE_T_MAX ((size_t)(-1)) // ifndef'ed by ppgb #endif #define EMPTY (-1) #define FLIP(i) (-(i)-2) #define UNFLIP(i) ((i < EMPTY) ? FLIP (i) : (i)) #define MAX(a,b) (((a) > (b)) ? (a) : (b)) #define MIN(a,b) (((a) < (b)) ? (a) : (b)) #define IMPLIES(p, q) (!(p) || (q)) #define GLOBAL #define AMD_order amd_order #define AMD_defaults amd_defaults #define AMD_control amd_control #define AMD_info amd_info #define AMD_1 amd_1 #define AMD_2 amd_2 #define AMD_valid amd_valid #define AMD_aat amd_aat #define AMD_postorder amd_postorder #define AMD_post_tree amd_post_tree #define AMD_dump amd_dump #define AMD_debug amd_debug #define AMD_debug_init amd_debug_init #define AMD_preprocess amd_preprocess #define amd_malloc xmalloc #if 0 /* 24/V-2009 */ #define amd_free xfree #else #define amd_free(ptr) { if ((ptr) != NULL) xfree(ptr); } #endif #define amd_printf xprintf #define PRINTF(params) { amd_printf params; } #ifndef NDEBUG #define ASSERT(expr) xassert(expr) #define AMD_DEBUG0(params) { PRINTF(params); } #define AMD_DEBUG1(params) { if (AMD_debug >= 1) PRINTF(params); } #define AMD_DEBUG2(params) { if (AMD_debug >= 2) PRINTF(params); } #define AMD_DEBUG3(params) { if (AMD_debug >= 3) PRINTF(params); } #define AMD_DEBUG4(params) { if (AMD_debug >= 4) PRINTF(params); } #else #define ASSERT(expression) #define AMD_DEBUG0(params) #define AMD_DEBUG1(params) #define AMD_DEBUG2(params) #define AMD_DEBUG3(params) #define AMD_DEBUG4(params) #endif #define amd_aat _glp_amd_aat size_t AMD_aat(Int n, const Int Ap[], const Int Ai[], Int Len[], Int Tp[], double Info[]); #define amd_1 _glp_amd_1 void AMD_1(Int n, const Int Ap[], const Int Ai[], Int P[], Int Pinv[], Int Len[], Int slen, Int S[], double Control[], double Info[]); #define amd_postorder _glp_amd_postorder void AMD_postorder(Int nn, Int Parent[], Int Npiv[], Int Fsize[], Int Order[], Int Child[], Int Sibling[], Int Stack[]); #define amd_post_tree _glp_amd_post_tree #ifndef NDEBUG Int AMD_post_tree(Int root, Int k, Int Child[], const Int Sibling[], Int Order[], Int Stack[], Int nn); #else Int AMD_post_tree(Int root, Int k, Int Child[], const Int Sibling[], Int Order[], Int Stack[]); #endif #define amd_preprocess _glp_amd_preprocess void AMD_preprocess(Int n, const Int Ap[], const Int Ai[], Int Rp[], Int Ri[], Int W[], Int Flag[]); #define amd_debug _glp_amd_debug extern Int AMD_debug; #define amd_debug_init _glp_amd_debug_init void AMD_debug_init(char *s); #define amd_dump _glp_amd_dump void AMD_dump(Int n, Int Pe[], Int Iw[], Int Len[], Int iwlen, Int pfree, Int Nv[], Int Next[], Int Last[], Int Head[], Int Elen[], Int Degree[], Int W[], Int nel); #endif /* eof */ sources_5316/external/glpk/amd_order.c0000644000176700017670000001451611401660400016601 0ustar paulpaul/* ========================================================================= */ /* === AMD_order =========================================================== */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* User-callable AMD minimum degree ordering routine. See amd.h for * documentation. */ #include "amd_internal.h" /* ========================================================================= */ /* === AMD_order =========================================================== */ /* ========================================================================= */ GLOBAL Int AMD_order ( Int n, const Int Ap [ ], const Int Ai [ ], Int P [ ], double Control [ ], double Info [ ] ) { Int *Len, *S, nz, i, *Pinv, info, status, *Rp, *Ri, *Cp, *Ci, ok ; size_t nzaat, slen ; double mem = 0 ; #ifndef NDEBUG AMD_debug_init ("amd") ; #endif /* clear the Info array, if it exists */ info = Info != (double *) NULL ; if (info) { for (i = 0 ; i < AMD_INFO ; i++) { Info [i] = EMPTY ; } Info [AMD_N] = n ; Info [AMD_STATUS] = AMD_OK ; } /* make sure inputs exist and n is >= 0 */ if (Ai == (Int *) NULL || Ap == (Int *) NULL || P == (Int *) NULL || n < 0) { if (info) Info [AMD_STATUS] = AMD_INVALID ; return (AMD_INVALID) ; /* arguments are invalid */ } if (n == 0) { return (AMD_OK) ; /* n is 0 so there's nothing to do */ } nz = Ap [n] ; if (info) { Info [AMD_NZ] = nz ; } if (nz < 0) { if (info) Info [AMD_STATUS] = AMD_INVALID ; return (AMD_INVALID) ; } /* check if n or nz will cause size_t overflow */ if (((size_t) n) >= SIZE_T_MAX / sizeof (Int) || ((size_t) nz) >= SIZE_T_MAX / sizeof (Int)) { if (info) Info [AMD_STATUS] = AMD_OUT_OF_MEMORY ; return (AMD_OUT_OF_MEMORY) ; /* problem too large */ } /* check the input matrix: AMD_OK, AMD_INVALID, or AMD_OK_BUT_JUMBLED */ status = AMD_valid (n, n, Ap, Ai) ; if (status == AMD_INVALID) { if (info) Info [AMD_STATUS] = AMD_INVALID ; return (AMD_INVALID) ; /* matrix is invalid */ } /* allocate two size-n integer workspaces */ Len = amd_malloc (n * sizeof (Int)) ; Pinv = amd_malloc (n * sizeof (Int)) ; mem += n ; mem += n ; if (!Len || !Pinv) { /* :: out of memory :: */ amd_free (Len) ; amd_free (Pinv) ; if (info) Info [AMD_STATUS] = AMD_OUT_OF_MEMORY ; return (AMD_OUT_OF_MEMORY) ; } if (status == AMD_OK_BUT_JUMBLED) { /* sort the input matrix and remove duplicate entries */ AMD_DEBUG1 (("Matrix is jumbled\n")) ; Rp = amd_malloc ((n+1) * sizeof (Int)) ; Ri = amd_malloc (MAX (nz,1) * sizeof (Int)) ; mem += (n+1) ; mem += MAX (nz,1) ; if (!Rp || !Ri) { /* :: out of memory :: */ amd_free (Rp) ; amd_free (Ri) ; amd_free (Len) ; amd_free (Pinv) ; if (info) Info [AMD_STATUS] = AMD_OUT_OF_MEMORY ; return (AMD_OUT_OF_MEMORY) ; } /* use Len and Pinv as workspace to create R = A' */ AMD_preprocess (n, Ap, Ai, Rp, Ri, Len, Pinv) ; Cp = Rp ; Ci = Ri ; } else { /* order the input matrix as-is. No need to compute R = A' first */ Rp = NULL ; Ri = NULL ; Cp = (Int *) Ap ; Ci = (Int *) Ai ; } /* --------------------------------------------------------------------- */ /* determine the symmetry and count off-diagonal nonzeros in A+A' */ /* --------------------------------------------------------------------- */ nzaat = AMD_aat (n, Cp, Ci, Len, P, Info) ; AMD_DEBUG1 (("nzaat: %g\n", (double) nzaat)) ; ASSERT ((MAX (nz-n, 0) <= nzaat) && (nzaat <= 2 * (size_t) nz)) ; /* --------------------------------------------------------------------- */ /* allocate workspace for matrix, elbow room, and 6 size-n vectors */ /* --------------------------------------------------------------------- */ S = NULL ; slen = nzaat ; /* space for matrix */ ok = ((slen + nzaat/5) >= slen) ; /* check for size_t overflow */ slen += nzaat/5 ; /* add elbow room */ for (i = 0 ; ok && i < 7 ; i++) { ok = ((slen + n) > slen) ; /* check for size_t overflow */ slen += n ; /* size-n elbow room, 6 size-n work */ } mem += slen ; ok = ok && (slen < SIZE_T_MAX / sizeof (Int)) ; /* check for overflow */ ok = ok && (slen < Int_MAX) ; /* S[i] for Int i must be OK */ if (ok) { S = amd_malloc (slen * sizeof (Int)) ; } AMD_DEBUG1 (("slen %g\n", (double) slen)) ; if (!S) { /* :: out of memory :: (or problem too large) */ amd_free (Rp) ; amd_free (Ri) ; amd_free (Len) ; amd_free (Pinv) ; if (info) Info [AMD_STATUS] = AMD_OUT_OF_MEMORY ; return (AMD_OUT_OF_MEMORY) ; } if (info) { /* memory usage, in bytes. */ Info [AMD_MEMORY] = mem * sizeof (Int) ; } /* --------------------------------------------------------------------- */ /* order the matrix */ /* --------------------------------------------------------------------- */ AMD_1 (n, Cp, Ci, P, Pinv, Len, slen, S, Control, Info) ; /* --------------------------------------------------------------------- */ /* free the workspace */ /* --------------------------------------------------------------------- */ amd_free (Rp) ; amd_free (Ri) ; amd_free (Len) ; amd_free (Pinv) ; amd_free (S) ; if (info) Info [AMD_STATUS] = status ; return (status) ; /* successful ordering */ } sources_5316/external/glpk/glpssx02.c0000644000176700017670000004070311401660400016324 0ustar paulpaul/* glpssx02.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glpssx.h" static void show_progress(SSX *ssx, int phase) { /* this auxiliary routine displays information about progress of the search */ int i, def = 0; for (i = 1; i <= ssx->m; i++) if (ssx->type[ssx->Q_col[i]] == SSX_FX) def++; xprintf("%s%6d: %s = %22.15g (%d)\n", phase == 1 ? " " : "*", ssx->it_cnt, phase == 1 ? "infsum" : "objval", mpq_get_d(ssx->bbar[0]), def); #if 0 ssx->tm_lag = utime(); #else ssx->tm_lag = xtime(); #endif return; } /*---------------------------------------------------------------------- // ssx_phase_I - find primal feasible solution. // // This routine implements phase I of the primal simplex method. // // On exit the routine returns one of the following codes: // // 0 - feasible solution found; // 1 - problem has no feasible solution; // 2 - iterations limit exceeded; // 3 - time limit exceeded. ----------------------------------------------------------------------*/ int ssx_phase_I(SSX *ssx) { int m = ssx->m; int n = ssx->n; int *type = ssx->type; mpq_t *lb = ssx->lb; mpq_t *ub = ssx->ub; mpq_t *coef = ssx->coef; int *A_ptr = ssx->A_ptr; int *A_ind = ssx->A_ind; mpq_t *A_val = ssx->A_val; int *Q_col = ssx->Q_col; mpq_t *bbar = ssx->bbar; mpq_t *pi = ssx->pi; mpq_t *cbar = ssx->cbar; int *orig_type, orig_dir; mpq_t *orig_lb, *orig_ub, *orig_coef; int i, k, ret; /* save components of the original LP problem, which are changed by the routine */ orig_type = xcalloc(1+m+n, sizeof(int)); orig_lb = xcalloc(1+m+n, sizeof(mpq_t)); orig_ub = xcalloc(1+m+n, sizeof(mpq_t)); orig_coef = xcalloc(1+m+n, sizeof(mpq_t)); for (k = 1; k <= m+n; k++) { orig_type[k] = type[k]; mpq_init(orig_lb[k]); mpq_set(orig_lb[k], lb[k]); mpq_init(orig_ub[k]); mpq_set(orig_ub[k], ub[k]); } orig_dir = ssx->dir; for (k = 0; k <= m+n; k++) { mpq_init(orig_coef[k]); mpq_set(orig_coef[k], coef[k]); } /* build an artificial basic solution, which is primal feasible, and also build an auxiliary objective function to minimize the sum of infeasibilities for the original problem */ ssx->dir = SSX_MIN; for (k = 0; k <= m+n; k++) mpq_set_si(coef[k], 0, 1); mpq_set_si(bbar[0], 0, 1); for (i = 1; i <= m; i++) { int t; k = Q_col[i]; /* x[k] = xB[i] */ t = type[k]; if (t == SSX_LO || t == SSX_DB || t == SSX_FX) { /* in the original problem x[k] has lower bound */ if (mpq_cmp(bbar[i], lb[k]) < 0) { /* which is violated */ type[k] = SSX_UP; mpq_set(ub[k], lb[k]); mpq_set_si(lb[k], 0, 1); mpq_set_si(coef[k], -1, 1); mpq_add(bbar[0], bbar[0], ub[k]); mpq_sub(bbar[0], bbar[0], bbar[i]); } } if (t == SSX_UP || t == SSX_DB || t == SSX_FX) { /* in the original problem x[k] has upper bound */ if (mpq_cmp(bbar[i], ub[k]) > 0) { /* which is violated */ type[k] = SSX_LO; mpq_set(lb[k], ub[k]); mpq_set_si(ub[k], 0, 1); mpq_set_si(coef[k], +1, 1); mpq_add(bbar[0], bbar[0], bbar[i]); mpq_sub(bbar[0], bbar[0], lb[k]); } } } /* now the initial basic solution should be primal feasible due to changes of bounds of some basic variables, which turned to implicit artifical variables */ /* compute simplex multipliers and reduced costs */ ssx_eval_pi(ssx); ssx_eval_cbar(ssx); /* display initial progress of the search */ show_progress(ssx, 1); /* main loop starts here */ for (;;) { /* display current progress of the search */ #if 0 if (utime() - ssx->tm_lag >= ssx->out_frq - 0.001) #else if (xdifftime(xtime(), ssx->tm_lag) >= ssx->out_frq - 0.001) #endif show_progress(ssx, 1); /* we do not need to wait until all artificial variables have left the basis */ if (mpq_sgn(bbar[0]) == 0) { /* the sum of infeasibilities is zero, therefore the current solution is primal feasible for the original problem */ ret = 0; break; } /* check if the iterations limit has been exhausted */ if (ssx->it_lim == 0) { ret = 2; break; } /* check if the time limit has been exhausted */ #if 0 if (ssx->tm_lim >= 0.0 && ssx->tm_lim <= utime() - ssx->tm_beg) #else if (ssx->tm_lim >= 0.0 && ssx->tm_lim <= xdifftime(xtime(), ssx->tm_beg)) #endif { ret = 3; break; } /* choose non-basic variable xN[q] */ ssx_chuzc(ssx); /* if xN[q] cannot be chosen, the sum of infeasibilities is minimal but non-zero; therefore the original problem has no primal feasible solution */ if (ssx->q == 0) { ret = 1; break; } /* compute q-th column of the simplex table */ ssx_eval_col(ssx); /* choose basic variable xB[p] */ ssx_chuzr(ssx); /* the sum of infeasibilities cannot be negative, therefore the auxiliary lp problem cannot have unbounded solution */ xassert(ssx->p != 0); /* update values of basic variables */ ssx_update_bbar(ssx); if (ssx->p > 0) { /* compute p-th row of the inverse inv(B) */ ssx_eval_rho(ssx); /* compute p-th row of the simplex table */ ssx_eval_row(ssx); xassert(mpq_cmp(ssx->aq[ssx->p], ssx->ap[ssx->q]) == 0); /* update simplex multipliers */ ssx_update_pi(ssx); /* update reduced costs of non-basic variables */ ssx_update_cbar(ssx); } /* xB[p] is leaving the basis; if it is implicit artificial variable, the corresponding residual vanishes; therefore bounds of this variable should be restored to the original values */ if (ssx->p > 0) { k = Q_col[ssx->p]; /* x[k] = xB[p] */ if (type[k] != orig_type[k]) { /* x[k] is implicit artificial variable */ type[k] = orig_type[k]; mpq_set(lb[k], orig_lb[k]); mpq_set(ub[k], orig_ub[k]); xassert(ssx->p_stat == SSX_NL || ssx->p_stat == SSX_NU); ssx->p_stat = (ssx->p_stat == SSX_NL ? SSX_NU : SSX_NL); if (type[k] == SSX_FX) ssx->p_stat = SSX_NS; /* nullify the objective coefficient at x[k] */ mpq_set_si(coef[k], 0, 1); /* since coef[k] has been changed, we need to compute new reduced cost of x[k], which it will have in the adjacent basis */ /* the formula d[j] = cN[j] - pi' * N[j] is used (note that the vector pi is not changed, because it depends on objective coefficients at basic variables, but in the adjacent basis, for which the vector pi has been just recomputed, x[k] is non-basic) */ if (k <= m) { /* x[k] is auxiliary variable */ mpq_neg(cbar[ssx->q], pi[k]); } else { /* x[k] is structural variable */ int ptr; mpq_t temp; mpq_init(temp); mpq_set_si(cbar[ssx->q], 0, 1); for (ptr = A_ptr[k-m]; ptr < A_ptr[k-m+1]; ptr++) { mpq_mul(temp, pi[A_ind[ptr]], A_val[ptr]); mpq_add(cbar[ssx->q], cbar[ssx->q], temp); } mpq_clear(temp); } } } /* jump to the adjacent vertex of the polyhedron */ ssx_change_basis(ssx); /* one simplex iteration has been performed */ if (ssx->it_lim > 0) ssx->it_lim--; ssx->it_cnt++; } /* display final progress of the search */ show_progress(ssx, 1); /* restore components of the original problem, which were changed by the routine */ for (k = 1; k <= m+n; k++) { type[k] = orig_type[k]; mpq_set(lb[k], orig_lb[k]); mpq_clear(orig_lb[k]); mpq_set(ub[k], orig_ub[k]); mpq_clear(orig_ub[k]); } ssx->dir = orig_dir; for (k = 0; k <= m+n; k++) { mpq_set(coef[k], orig_coef[k]); mpq_clear(orig_coef[k]); } xfree(orig_type); xfree(orig_lb); xfree(orig_ub); xfree(orig_coef); /* return to the calling program */ return ret; } /*---------------------------------------------------------------------- // ssx_phase_II - find optimal solution. // // This routine implements phase II of the primal simplex method. // // On exit the routine returns one of the following codes: // // 0 - optimal solution found; // 1 - problem has unbounded solution; // 2 - iterations limit exceeded; // 3 - time limit exceeded. ----------------------------------------------------------------------*/ int ssx_phase_II(SSX *ssx) { int ret; /* display initial progress of the search */ show_progress(ssx, 2); /* main loop starts here */ for (;;) { /* display current progress of the search */ #if 0 if (utime() - ssx->tm_lag >= ssx->out_frq - 0.001) #else if (xdifftime(xtime(), ssx->tm_lag) >= ssx->out_frq - 0.001) #endif show_progress(ssx, 2); /* check if the iterations limit has been exhausted */ if (ssx->it_lim == 0) { ret = 2; break; } /* check if the time limit has been exhausted */ #if 0 if (ssx->tm_lim >= 0.0 && ssx->tm_lim <= utime() - ssx->tm_beg) #else if (ssx->tm_lim >= 0.0 && ssx->tm_lim <= xdifftime(xtime(), ssx->tm_beg)) #endif { ret = 3; break; } /* choose non-basic variable xN[q] */ ssx_chuzc(ssx); /* if xN[q] cannot be chosen, the current basic solution is dual feasible and therefore optimal */ if (ssx->q == 0) { ret = 0; break; } /* compute q-th column of the simplex table */ ssx_eval_col(ssx); /* choose basic variable xB[p] */ ssx_chuzr(ssx); /* if xB[p] cannot be chosen, the problem has no dual feasible solution (i.e. unbounded) */ if (ssx->p == 0) { ret = 1; break; } /* update values of basic variables */ ssx_update_bbar(ssx); if (ssx->p > 0) { /* compute p-th row of the inverse inv(B) */ ssx_eval_rho(ssx); /* compute p-th row of the simplex table */ ssx_eval_row(ssx); xassert(mpq_cmp(ssx->aq[ssx->p], ssx->ap[ssx->q]) == 0); #if 0 /* update simplex multipliers */ ssx_update_pi(ssx); #endif /* update reduced costs of non-basic variables */ ssx_update_cbar(ssx); } /* jump to the adjacent vertex of the polyhedron */ ssx_change_basis(ssx); /* one simplex iteration has been performed */ if (ssx->it_lim > 0) ssx->it_lim--; ssx->it_cnt++; } /* display final progress of the search */ show_progress(ssx, 2); /* return to the calling program */ return ret; } /*---------------------------------------------------------------------- // ssx_driver - base driver to exact simplex method. // // This routine is a base driver to a version of the primal simplex // method using exact (bignum) arithmetic. // // On exit the routine returns one of the following codes: // // 0 - optimal solution found; // 1 - problem has no feasible solution; // 2 - problem has unbounded solution; // 3 - iterations limit exceeded (phase I); // 4 - iterations limit exceeded (phase II); // 5 - time limit exceeded (phase I); // 6 - time limit exceeded (phase II); // 7 - initial basis matrix is exactly singular. ----------------------------------------------------------------------*/ int ssx_driver(SSX *ssx) { int m = ssx->m; int *type = ssx->type; mpq_t *lb = ssx->lb; mpq_t *ub = ssx->ub; int *Q_col = ssx->Q_col; mpq_t *bbar = ssx->bbar; int i, k, ret; ssx->tm_beg = xtime(); /* factorize the initial basis matrix */ if (ssx_factorize(ssx)) { xprintf("Initial basis matrix is singular\n"); ret = 7; goto done; } /* compute values of basic variables */ ssx_eval_bbar(ssx); /* check if the initial basic solution is primal feasible */ for (i = 1; i <= m; i++) { int t; k = Q_col[i]; /* x[k] = xB[i] */ t = type[k]; if (t == SSX_LO || t == SSX_DB || t == SSX_FX) { /* x[k] has lower bound */ if (mpq_cmp(bbar[i], lb[k]) < 0) { /* which is violated */ break; } } if (t == SSX_UP || t == SSX_DB || t == SSX_FX) { /* x[k] has upper bound */ if (mpq_cmp(bbar[i], ub[k]) > 0) { /* which is violated */ break; } } } if (i > m) { /* no basic variable violates its bounds */ ret = 0; goto skip; } /* phase I: find primal feasible solution */ ret = ssx_phase_I(ssx); switch (ret) { case 0: ret = 0; break; case 1: xprintf("PROBLEM HAS NO FEASIBLE SOLUTION\n"); ret = 1; break; case 2: xprintf("ITERATIONS LIMIT EXCEEDED; SEARCH TERMINATED\n"); ret = 3; break; case 3: xprintf("TIME LIMIT EXCEEDED; SEARCH TERMINATED\n"); ret = 5; break; default: xassert(ret != ret); } /* compute values of basic variables (actually only the objective value needs to be computed) */ ssx_eval_bbar(ssx); skip: /* compute simplex multipliers */ ssx_eval_pi(ssx); /* compute reduced costs of non-basic variables */ ssx_eval_cbar(ssx); /* if phase I failed, do not start phase II */ if (ret != 0) goto done; /* phase II: find optimal solution */ ret = ssx_phase_II(ssx); switch (ret) { case 0: xprintf("OPTIMAL SOLUTION FOUND\n"); ret = 0; break; case 1: xprintf("PROBLEM HAS UNBOUNDED SOLUTION\n"); ret = 2; break; case 2: xprintf("ITERATIONS LIMIT EXCEEDED; SEARCH TERMINATED\n"); ret = 4; break; case 3: xprintf("TIME LIMIT EXCEEDED; SEARCH TERMINATED\n"); ret = 6; break; default: xassert(ret != ret); } done: /* decrease the time limit by the spent amount of time */ if (ssx->tm_lim >= 0.0) #if 0 { ssx->tm_lim -= utime() - ssx->tm_beg; #else { ssx->tm_lim -= xdifftime(xtime(), ssx->tm_beg); #endif if (ssx->tm_lim < 0.0) ssx->tm_lim = 0.0; } return ret; } /* eof */ sources_5316/external/glpk/glplib.h0000644000176700017670000000765111401660400016125 0ustar paulpaul/* glplib.h (miscellaneous library routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPLIB_H #define GLPLIB_H #define bigmul _glp_lib_bigmul void bigmul(int n, int m, unsigned short x[], unsigned short y[]); /* multiply unsigned integer numbers of arbitrary precision */ #define bigdiv _glp_lib_bigdiv void bigdiv(int n, int m, unsigned short x[], unsigned short y[]); /* divide unsigned integer numbers of arbitrary precision */ #ifndef GLP_LONG_DEFINED #define GLP_LONG_DEFINED typedef struct { int lo, hi; } glp_long; /* long integer data type */ #endif typedef struct { glp_long quot, rem; } glp_ldiv; /* result of long integer division */ #define xlset _glp_lib_xlset glp_long xlset(int x); /* expand integer to long integer */ #define xlneg _glp_lib_xlneg glp_long xlneg(glp_long x); /* negate long integer */ #define xladd _glp_lib_xladd glp_long xladd(glp_long x, glp_long y); /* add long integers */ #define xlsub _glp_lib_xlsub glp_long xlsub(glp_long x, glp_long y); /* subtract long integers */ #define xlcmp _glp_lib_xlcmp int xlcmp(glp_long x, glp_long y); /* compare long integers */ #define xlmul _glp_lib_xlmul glp_long xlmul(glp_long x, glp_long y); /* multiply long integers */ #define xldiv _glp_lib_xldiv glp_ldiv xldiv(glp_long x, glp_long y); /* divide long integers */ #define xltod _glp_lib_xltod double xltod(glp_long x); /* convert long integer to double */ #define xltoa _glp_lib_xltoa char *xltoa(glp_long x, char *s); /* convert long integer to character string */ #define str2int _glp_lib_str2int int str2int(const char *str, int *val); /* convert character string to value of int type */ #define str2num _glp_lib_str2num int str2num(const char *str, double *val); /* convert character string to value of double type */ #define strspx _glp_lib_strspx char *strspx(char *str); /* remove all spaces from character string */ #define strtrim _glp_lib_strtrim char *strtrim(char *str); /* remove trailing spaces from character string */ #define strrev _glp_lib_strrev char *strrev(char *s); /* reverse character string */ #define gcd _glp_lib_gcd int gcd(int x, int y); /* find greatest common divisor of two integers */ #define gcdn _glp_lib_gcdn int gcdn(int n, int x[]); /* find greatest common divisor of n integers */ #define lcm _glp_lib_lcm int lcm(int x, int y); /* find least common multiple of two integers */ #define lcmn _glp_lib_lcmn int lcmn(int n, int x[]); /* find least common multiple of n integers */ #define round2n _glp_lib_round2n double round2n(double x); /* round floating-point number to nearest power of two */ #define fp2rat _glp_lib_fp2rat int fp2rat(double x, double eps, double *p, double *q); /* convert floating-point number to rational number */ #define jday _glp_lib_jday int jday(int d, int m, int y); /* convert calendar date to Julian day number */ #define jdate _glp_lib_jdate int jdate(int j, int *d, int *m, int *y); /* convert Julian day number to calendar date */ #endif /* eof */ sources_5316/external/glpk/glpnpp04.c0000644000176700017670000014253111401660400016310 0ustar paulpaul/* glpnpp04.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpnpp.h" /*********************************************************************** * NAME * * npp_binarize_prob - binarize MIP problem * * SYNOPSIS * * #include "glpnpp.h" * int npp_binarize_prob(NPP *npp); * * DESCRIPTION * * The routine npp_binarize_prob replaces in the original MIP problem * every integer variable: * * l[q] <= x[q] <= u[q], (1) * * where l[q] < u[q], by an equivalent sum of binary variables. * * RETURNS * * The routine returns the number of integer variables for which the * transformation failed, because u[q] - l[q] > d_max. * * PROBLEM TRANSFORMATION * * If variable x[q] has non-zero lower bound, it is first processed * with the routine npp_lbnd_col. Thus, we can assume that: * * 0 <= x[q] <= u[q]. (2) * * If u[q] = 1, variable x[q] is already binary, so further processing * is not needed. Let, therefore, that 2 <= u[q] <= d_max, and n be a * smallest integer such that u[q] <= 2^n - 1 (n >= 2, since u[q] >= 2). * Then variable x[q] can be replaced by the following sum: * * n-1 * x[q] = sum 2^k x[k], (3) * k=0 * * where x[k] are binary columns (variables). If u[q] < 2^n - 1, the * following additional inequality constraint must be also included in * the transformed problem: * * n-1 * sum 2^k x[k] <= u[q]. (4) * k=0 * * Note: Assuming that in the transformed problem x[q] becomes binary * variable x[0], this transformation causes new n-1 binary variables * to appear. * * Substituting x[q] from (3) to the objective row gives: * * z = sum c[j] x[j] + c[0] = * j * * = sum c[j] x[j] + c[q] x[q] + c[0] = * j!=q * n-1 * = sum c[j] x[j] + c[q] sum 2^k x[k] + c[0] = * j!=q k=0 * n-1 * = sum c[j] x[j] + sum c[k] x[k] + c[0], * j!=q k=0 * * where: * * c[k] = 2^k c[q], k = 0, ..., n-1. (5) * * And substituting x[q] from (3) to i-th constraint row i gives: * * L[i] <= sum a[i,j] x[j] <= U[i] ==> * j * * L[i] <= sum a[i,j] x[j] + a[i,q] x[q] <= U[i] ==> * j!=q * n-1 * L[i] <= sum a[i,j] x[j] + a[i,q] sum 2^k x[k] <= U[i] ==> * j!=q k=0 * n-1 * L[i] <= sum a[i,j] x[j] + sum a[i,k] x[k] <= U[i], * j!=q k=0 * * where: * * a[i,k] = 2^k a[i,q], k = 0, ..., n-1. (6) * * RECOVERING SOLUTION * * Value of variable x[q] is computed with formula (3). */ struct binarize { int q; /* column reference number for x[q] = x[0] */ int j; /* column reference number for x[1]; x[2] has reference number j+1, x[3] - j+2, etc. */ int n; /* total number of binary variables, n >= 2 */ }; static int rcv_binarize_prob(NPP *npp, void *info); int npp_binarize_prob(NPP *npp) { /* binarize MIP problem */ struct binarize *info; NPPROW *row; NPPCOL *col, *bin; NPPAIJ *aij; int u, n, k, temp, nfails, nvars, nbins, nrows; /* new variables will be added to the end of the column list, so we go from the end to beginning of the column list */ nfails = nvars = nbins = nrows = 0; for (col = npp->c_tail; col != NULL; col = col->prev) { /* skip continuous variable */ if (!col->is_int) continue; /* skip fixed variable */ if (col->lb == col->ub) continue; /* skip binary variable */ if (col->lb == 0.0 && col->ub == 1.0) continue; /* check if the transformation is applicable */ if (col->lb < -1e6 || col->ub > +1e6 || col->ub - col->lb > 4095.0) { /* unfortunately, not */ nfails++; continue; } /* process integer non-binary variable x[q] */ nvars++; /* make x[q] non-negative, if its lower bound is non-zero */ if (col->lb != 0.0) npp_lbnd_col(npp, col); /* now 0 <= x[q] <= u[q] */ xassert(col->lb == 0.0); u = (int)col->ub; xassert(col->ub == (double)u); /* if x[q] is binary, further processing is not needed */ if (u == 1) continue; /* determine smallest n such that u <= 2^n - 1 (thus, n is the number of binary variables needed) */ n = 2, temp = 4; while (u >= temp) n++, temp += temp; nbins += n; /* create transformation stack entry */ info = npp_push_tse(npp, rcv_binarize_prob, sizeof(struct binarize)); info->q = col->j; info->j = 0; /* will be set below */ info->n = n; /* if u < 2^n - 1, we need one additional row for (4) */ if (u < temp - 1) { row = npp_add_row(npp), nrows++; row->lb = -DBL_MAX, row->ub = u; } else row = NULL; /* in the transformed problem variable x[q] becomes binary variable x[0], so its objective and constraint coefficients are not changed */ col->ub = 1.0; /* include x[0] into constraint (4) */ if (row != NULL) npp_add_aij(npp, row, col, 1.0); /* add other binary variables x[1], ..., x[n-1] */ for (k = 1, temp = 2; k < n; k++, temp += temp) { /* add new binary variable x[k] */ bin = npp_add_col(npp); bin->is_int = 1; bin->lb = 0.0, bin->ub = 1.0; bin->coef = (double)temp * col->coef; /* store column reference number for x[1] */ if (info->j == 0) info->j = bin->j; else xassert(info->j + (k-1) == bin->j); /* duplicate constraint coefficients for x[k]; this also automatically includes x[k] into constraint (4) */ for (aij = col->ptr; aij != NULL; aij = aij->c_next) npp_add_aij(npp, aij->row, bin, (double)temp * aij->val); } } if (nvars > 0) xprintf("%d integer variable(s) were replaced by %d binary one" "s\n", nvars, nbins); if (nrows > 0) xprintf("%d row(s) were added due to binarization\n", nrows); if (nfails > 0) xprintf("Binarization failed for %d integer variable(s)\n", nfails); return nfails; } static int rcv_binarize_prob(NPP *npp, void *_info) { /* recovery binarized variable */ struct binarize *info = _info; int k, temp; double sum; /* compute value of x[q]; see formula (3) */ sum = npp->c_value[info->q]; for (k = 1, temp = 2; k < info->n; k++, temp += temp) sum += (double)temp * npp->c_value[info->j + (k-1)]; npp->c_value[info->q] = sum; return 0; } /**********************************************************************/ struct elem { /* linear form element a[j] x[j] */ double aj; /* non-zero coefficient value */ NPPCOL *xj; /* pointer to variable (column) */ struct elem *next; /* pointer to another term */ }; static struct elem *copy_form(NPP *npp, NPPROW *row, double s) { /* copy linear form */ NPPAIJ *aij; struct elem *ptr, *e; ptr = NULL; for (aij = row->ptr; aij != NULL; aij = aij->r_next) { e = dmp_get_atom(npp->pool, sizeof(struct elem)); e->aj = s * aij->val; e->xj = aij->col; e->next = ptr; ptr = e; } return ptr; } static void drop_form(NPP *npp, struct elem *ptr) { /* drop linear form */ struct elem *e; while (ptr != NULL) { e = ptr; ptr = e->next; dmp_free_atom(npp->pool, e, sizeof(struct elem)); } return; } /*********************************************************************** * NAME * * npp_is_packing - test if constraint is packing inequality * * SYNOPSIS * * #include "glpnpp.h" * int npp_is_packing(NPP *npp, NPPROW *row); * * RETURNS * * If the specified row (constraint) is packing inequality (see below), * the routine npp_is_packing returns non-zero. Otherwise, it returns * zero. * * PACKING INEQUALITIES * * In canonical format the packing inequality is the following: * * sum x[j] <= 1, (1) * j in J * * where all variables x[j] are binary. This inequality expresses the * condition that in any integer feasible solution at most one variable * from set J can take non-zero (unity) value while other variables * must be equal to zero. W.l.o.g. it is assumed that |J| >= 2, because * if J is empty or |J| = 1, the inequality (1) is redundant. * * In general case the packing inequality may include original variables * x[j] as well as their complements x~[j]: * * sum x[j] + sum x~[j] <= 1, (2) * j in Jp j in Jn * * where Jp and Jn are not intersected. Therefore, using substitution * x~[j] = 1 - x[j] gives the packing inequality in generalized format: * * sum x[j] - sum x[j] <= 1 - |Jn|. (3) * j in Jp j in Jn */ int npp_is_packing(NPP *npp, NPPROW *row) { /* test if constraint is packing inequality */ NPPCOL *col; NPPAIJ *aij; int b; xassert(npp == npp); if (!(row->lb == -DBL_MAX && row->ub != +DBL_MAX)) return 0; b = 1; for (aij = row->ptr; aij != NULL; aij = aij->r_next) { col = aij->col; if (!(col->is_int && col->lb == 0.0 && col->ub == 1.0)) return 0; if (aij->val == +1.0) ; else if (aij->val == -1.0) b--; else return 0; } if (row->ub != (double)b) return 0; return 1; } /*********************************************************************** * NAME * * npp_hidden_packing - identify hidden packing inequality * * SYNOPSIS * * #include "glpnpp.h" * int npp_hidden_packing(NPP *npp, NPPROW *row); * * DESCRIPTION * * The routine npp_hidden_packing processes specified inequality * constraint, which includes only binary variables, and the number of * the variables is not less than two. If the original inequality is * equivalent to a packing inequality, the routine replaces it by this * equivalent inequality. If the original constraint is double-sided * inequality, it is replaced by a pair of single-sided inequalities, * if necessary. * * RETURNS * * If the original inequality constraint was replaced by equivalent * packing inequality, the routine npp_hidden_packing returns non-zero. * Otherwise, it returns zero. * * PROBLEM TRANSFORMATION * * Consider an inequality constraint: * * sum a[j] x[j] <= b, (1) * j in J * * where all variables x[j] are binary, and |J| >= 2. (In case of '>=' * inequality it can be transformed to '<=' format by multiplying both * its sides by -1.) * * Let Jp = {j: a[j] > 0}, Jn = {j: a[j] < 0}. Performing substitution * x[j] = 1 - x~[j] for all j in Jn, we have: * * sum a[j] x[j] <= b ==> * j in J * * sum a[j] x[j] + sum a[j] x[j] <= b ==> * j in Jp j in Jn * * sum a[j] x[j] + sum a[j] (1 - x~[j]) <= b ==> * j in Jp j in Jn * * sum a[j] x[j] - sum a[j] x~[j] <= b - sum a[j]. * j in Jp j in Jn j in Jn * * Thus, meaning the transformation above, we can assume that in * inequality (1) all coefficients a[j] are positive. Moreover, we can * assume that a[j] <= b. In fact, let a[j] > b; then the following * three cases are possible: * * 1) b < 0. In this case inequality (1) is infeasible, so the problem * has no feasible solution (see the routine npp_analyze_row); * * 2) b = 0. In this case inequality (1) is a forcing inequality on its * upper bound (see the routine npp_forcing row), from which it * follows that all variables x[j] should be fixed at zero; * * 3) b > 0. In this case inequality (1) defines an implied zero upper * bound for variable x[j] (see the routine npp_implied_bounds), from * which it follows that x[j] should be fixed at zero. * * It is assumed that all three cases listed above have been recognized * by the routine npp_process_prob, which performs basic MIP processing * prior to a call the routine npp_hidden_packing. So, if one of these * cases occurs, we should just skip processing such constraint. * * Thus, let 0 < a[j] <= b. Then it is obvious that constraint (1) is * equivalent to packing inquality only if: * * a[j] + a[k] > b + eps (2) * * for all j, k in J, j != k, where eps is an absolute tolerance for * row (linear form) value. Checking the condition (2) for all j and k, * j != k, requires time O(|J|^2). However, this time can be reduced to * O(|J|), if use minimal a[j] and a[k], in which case it is sufficient * to check the condition (2) only once. * * Once the original inequality (1) is replaced by equivalent packing * inequality, we need to perform back substitution x~[j] = 1 - x[j] for * all j in Jn (see above). * * RECOVERING SOLUTION * * None needed. */ static int hidden_packing(NPP *npp, struct elem *ptr, double *_b) { /* process inequality constraint: sum a[j] x[j] <= b; 0 - specified row is NOT hidden packing inequality; 1 - specified row is packing inequality; 2 - specified row is hidden packing inequality. */ struct elem *e, *ej, *ek; int neg; double b = *_b, eps; xassert(npp == npp); /* a[j] must be non-zero, x[j] must be binary, for all j in J */ for (e = ptr; e != NULL; e = e->next) { xassert(e->aj != 0.0); xassert(e->xj->is_int); xassert(e->xj->lb == 0.0 && e->xj->ub == 1.0); } /* check if the specified inequality constraint already has the form of packing inequality */ neg = 0; /* neg is |Jn| */ for (e = ptr; e != NULL; e = e->next) { if (e->aj == +1.0) ; else if (e->aj == -1.0) neg++; else break; } if (e == NULL) { /* all coefficients a[j] are +1 or -1; check rhs b */ if (b == (double)(1 - neg)) { /* it is packing inequality; no processing is needed */ return 1; } } /* substitute x[j] = 1 - x~[j] for all j in Jn to make all a[j] positive; the result is a~[j] = |a[j]| and new rhs b */ for (e = ptr; e != NULL; e = e->next) if (e->aj < 0) b -= e->aj; /* now a[j] > 0 for all j in J (actually |a[j]| are used) */ /* if a[j] > b, skip processing--this case must not appear */ for (e = ptr; e != NULL; e = e->next) if (fabs(e->aj) > b) return 0; /* now 0 < a[j] <= b for all j in J */ /* find two minimal coefficients a[j] and a[k], j != k */ ej = NULL; for (e = ptr; e != NULL; e = e->next) if (ej == NULL || fabs(ej->aj) > fabs(e->aj)) ej = e; xassert(ej != NULL); ek = NULL; for (e = ptr; e != NULL; e = e->next) if (e != ej) if (ek == NULL || fabs(ek->aj) > fabs(e->aj)) ek = e; xassert(ek != NULL); /* the specified constraint is equivalent to packing inequality iff a[j] + a[k] > b + eps */ eps = 1e-3 + 1e-6 * fabs(b); if (fabs(ej->aj) + fabs(ek->aj) <= b + eps) return 0; /* perform back substitution x~[j] = 1 - x[j] and construct the final equivalent packing inequality in generalized format */ b = 1.0; for (e = ptr; e != NULL; e = e->next) { if (e->aj > 0.0) e->aj = +1.0; else /* e->aj < 0.0 */ e->aj = -1.0, b -= 1.0; } *_b = b; return 2; } int npp_hidden_packing(NPP *npp, NPPROW *row) { /* identify hidden packing inequality */ NPPROW *copy; NPPAIJ *aij; struct elem *ptr, *e; int kase, ret, count = 0; double b; /* the row must be inequality constraint */ xassert(row->lb < row->ub); for (kase = 0; kase <= 1; kase++) { if (kase == 0) { /* process row upper bound */ if (row->ub == +DBL_MAX) continue; ptr = copy_form(npp, row, +1.0); b = + row->ub; } else { /* process row lower bound */ if (row->lb == -DBL_MAX) continue; ptr = copy_form(npp, row, -1.0); b = - row->lb; } /* now the inequality has the form "sum a[j] x[j] <= b" */ ret = hidden_packing(npp, ptr, &b); xassert(0 <= ret && ret <= 2); if (kase == 1 && ret == 1 || ret == 2) { /* the original inequality has been identified as hidden packing inequality */ count++; #ifdef GLP_DEBUG xprintf("Original constraint:\n"); for (aij = row->ptr; aij != NULL; aij = aij->r_next) xprintf(" %+g x%d", aij->val, aij->col->j); if (row->lb != -DBL_MAX) xprintf(", >= %g", row->lb); if (row->ub != +DBL_MAX) xprintf(", <= %g", row->ub); xprintf("\n"); xprintf("Equivalent packing inequality:\n"); for (e = ptr; e != NULL; e = e->next) xprintf(" %sx%d", e->aj > 0.0 ? "+" : "-", e->xj->j); xprintf(", <= %g\n", b); #endif if (row->lb == -DBL_MAX || row->ub == +DBL_MAX) { /* the original row is single-sided inequality; no copy is needed */ copy = NULL; } else { /* the original row is double-sided inequality; we need to create its copy for other bound before replacing it with the equivalent inequality */ copy = npp_add_row(npp); if (kase == 0) { /* the copy is for lower bound */ copy->lb = row->lb, copy->ub = +DBL_MAX; } else { /* the copy is for upper bound */ copy->lb = -DBL_MAX, copy->ub = row->ub; } /* copy original row coefficients */ for (aij = row->ptr; aij != NULL; aij = aij->r_next) npp_add_aij(npp, copy, aij->col, aij->val); } /* replace the original inequality by equivalent one */ npp_erase_row(npp, row); row->lb = -DBL_MAX, row->ub = b; for (e = ptr; e != NULL; e = e->next) npp_add_aij(npp, row, e->xj, e->aj); /* continue processing lower bound for the copy */ if (copy != NULL) row = copy; } drop_form(npp, ptr); } return count; } /*********************************************************************** * NAME * * npp_implied_packing - identify implied packing inequality * * SYNOPSIS * * #include "glpnpp.h" * int npp_implied_packing(NPP *npp, NPPROW *row, int which, * NPPCOL *var[], char set[]); * * DESCRIPTION * * The routine npp_implied_packing processes specified row (constraint) * of general format: * * L <= sum a[j] x[j] <= U. (1) * j * * If which = 0, only lower bound L, which must exist, is considered, * while upper bound U is ignored. Similarly, if which = 1, only upper * bound U, which must exist, is considered, while lower bound L is * ignored. Thus, if the specified row is a double-sided inequality or * equality constraint, this routine should be called twice for both * lower and upper bounds. * * The routine npp_implied_packing attempts to find a non-trivial (i.e. * having not less than two binary variables) packing inequality: * * sum x[j] - sum x[j] <= 1 - |Jn|, (2) * j in Jp j in Jn * * which is relaxation of the constraint (1) in the sense that any * solution satisfying to that constraint also satisfies to the packing * inequality (2). If such relaxation exists, the routine stores * pointers to descriptors of corresponding binary variables and their * flags, resp., to locations var[1], var[2], ..., var[len] and set[1], * set[2], ..., set[len], where set[j] = 0 means that j in Jp and * set[j] = 1 means that j in Jn. * * RETURNS * * The routine npp_implied_packing returns len, which is the total * number of binary variables in the packing inequality found, len >= 2. * However, if the relaxation does not exist, the routine returns zero. * * ALGORITHM * * If which = 0, the constraint coefficients (1) are multiplied by -1 * and b is assigned -L; if which = 1, the constraint coefficients (1) * are not changed and b is assigned +U. In both cases the specified * constraint gets the following format: * * sum a[j] x[j] <= b. (3) * j * * (Note that (3) is a relaxation of (1), because one of bounds L or U * is ignored.) * * Let J be set of binary variables, Kp be set of non-binary (integer * or continuous) variables with a[j] > 0, and Kn be set of non-binary * variables with a[j] < 0. Then the inequality (3) can be written as * follows: * * sum a[j] x[j] <= b - sum a[j] x[j] - sum a[j] x[j]. (4) * j in J j in Kp j in Kn * * To get rid of non-binary variables we can replace the inequality (4) * by the following relaxed inequality: * * sum a[j] x[j] <= b~, (5) * j in J * * where: * * b~ = sup(b - sum a[j] x[j] - sum a[j] x[j]) = * j in Kp j in Kn * * = b - inf sum a[j] x[j] - inf sum a[j] x[j] = (6) * j in Kp j in Kn * * = b - sum a[j] l[j] - sum a[j] u[j]. * j in Kp j in Kn * * Note that if lower bound l[j] (if j in Kp) or upper bound u[j] * (if j in Kn) of some non-binary variable x[j] does not exist, then * formally b = +oo, in which case further analysis is not performed. * * Let Bp = {j in J: a[j] > 0}, Bn = {j in J: a[j] < 0}. To make all * the inequality coefficients in (5) positive, we replace all x[j] in * Bn by their complementaries, substituting x[j] = 1 - x~[j] for all * j in Bn, that gives: * * sum a[j] x[j] - sum a[j] x~[j] <= b~ - sum a[j]. (7) * j in Bp j in Bn j in Bn * * This inequality is a relaxation of the original constraint (1), and * it is a binary knapsack inequality. Writing it in the standard format * we have: * * sum alfa[j] z[j] <= beta, (8) * j in J * * where: * ( + a[j], if j in Bp, * alfa[j] = < (9) * ( - a[j], if j in Bn, * * ( x[j], if j in Bp, * z[j] = < (10) * ( 1 - x[j], if j in Bn, * * beta = b~ - sum a[j]. (11) * j in Bn * * In the inequality (8) all coefficients are positive, therefore, the * packing relaxation to be found for this inequality is the following: * * sum z[j] <= 1. (12) * j in P * * It is obvious that set P within J, which we would like to find, must * satisfy to the following condition: * * alfa[j] + alfa[k] > beta + eps for all j, k in P, j != k, (13) * * where eps is an absolute tolerance for value of the linear form. * Thus, it is natural to take P = {j: alpha[j] > (beta + eps) / 2}. * Moreover, if in the equality (8) there exist coefficients alfa[k], * for which alfa[k] <= (beta + eps) / 2, but which, nevertheless, * satisfies to the condition (13) for all j in P, *one* corresponding * variable z[k] (having, for example, maximal coefficient alfa[k]) can * be included in set P, that allows increasing the number of binary * variables in (12) by one. * * Once the set P has been built, for the inequality (12) we need to * perform back substitution according to (10) in order to express it * through the original binary variables. As the result of such back * substitution the relaxed packing inequality get its final format (2), * where Jp = J intersect Bp, and Jn = J intersect Bn. */ int npp_implied_packing(NPP *npp, NPPROW *row, int which, NPPCOL *var[], char set[]) { struct elem *ptr, *e, *i, *k; int len = 0; double b, eps; /* build inequality (3) */ if (which == 0) { ptr = copy_form(npp, row, -1.0); xassert(row->lb != -DBL_MAX); b = - row->lb; } else if (which == 1) { ptr = copy_form(npp, row, +1.0); xassert(row->ub != +DBL_MAX); b = + row->ub; } /* remove non-binary variables to build relaxed inequality (5); compute its right-hand side b~ with formula (6) */ for (e = ptr; e != NULL; e = e->next) { if (!(e->xj->is_int && e->xj->lb == 0.0 && e->xj->ub == 1.0)) { /* x[j] is non-binary variable */ if (e->aj > 0.0) { if (e->xj->lb == -DBL_MAX) goto done; b -= e->aj * e->xj->lb; } else /* e->aj < 0.0 */ { if (e->xj->ub == +DBL_MAX) goto done; b -= e->aj * e->xj->ub; } /* a[j] = 0 means that variable x[j] is removed */ e->aj = 0.0; } } /* substitute x[j] = 1 - x~[j] to build knapsack inequality (8); compute its right-hand side beta with formula (11) */ for (e = ptr; e != NULL; e = e->next) if (e->aj < 0.0) b -= e->aj; /* if beta is close to zero, the knapsack inequality is either infeasible or forcing inequality; this must never happen, so we skip further analysis */ if (b < 1e-3) goto done; /* build set P as well as sets Jp and Jn, and determine x[k] as explained above in comments to the routine */ eps = 1e-3 + 1e-6 * b; i = k = NULL; for (e = ptr; e != NULL; e = e->next) { /* note that alfa[j] = |a[j]| */ if (fabs(e->aj) > 0.5 * (b + eps)) { /* alfa[j] > (b + eps) / 2; include x[j] in set P, i.e. in set Jp or Jn */ var[++len] = e->xj; set[len] = (char)(e->aj > 0.0 ? 0 : 1); /* alfa[i] = min alfa[j] over all j included in set P */ if (i == NULL || fabs(i->aj) > fabs(e->aj)) i = e; } else if (fabs(e->aj) >= 1e-3) { /* alfa[k] = max alfa[j] over all j not included in set P; we skip coefficient a[j] if it is close to zero to avoid numerically unreliable results */ if (k == NULL || fabs(k->aj) < fabs(e->aj)) k = e; } } /* if alfa[k] satisfies to condition (13) for all j in P, include x[k] in P */ if (i != NULL && k != NULL && fabs(i->aj) + fabs(k->aj) > b + eps) { var[++len] = k->xj; set[len] = (char)(k->aj > 0.0 ? 0 : 1); } /* trivial packing inequality being redundant must never appear, so we just ignore it */ if (len < 2) len = 0; done: drop_form(npp, ptr); return len; } /*********************************************************************** * NAME * * npp_is_covering - test if constraint is covering inequality * * SYNOPSIS * * #include "glpnpp.h" * int npp_is_covering(NPP *npp, NPPROW *row); * * RETURNS * * If the specified row (constraint) is covering inequality (see below), * the routine npp_is_covering returns non-zero. Otherwise, it returns * zero. * * COVERING INEQUALITIES * * In canonical format the covering inequality is the following: * * sum x[j] >= 1, (1) * j in J * * where all variables x[j] are binary. This inequality expresses the * condition that in any integer feasible solution variables in set J * cannot be all equal to zero at the same time, i.e. at least one * variable must take non-zero (unity) value. W.l.o.g. it is assumed * that |J| >= 2, because if J is empty, the inequality (1) is * infeasible, and if |J| = 1, the inequality (1) is a forcing row. * * In general case the covering inequality may include original * variables x[j] as well as their complements x~[j]: * * sum x[j] + sum x~[j] >= 1, (2) * j in Jp j in Jn * * where Jp and Jn are not intersected. Therefore, using substitution * x~[j] = 1 - x[j] gives the packing inequality in generalized format: * * sum x[j] - sum x[j] >= 1 - |Jn|. (3) * j in Jp j in Jn * * (May note that the inequality (3) cuts off infeasible solutions, * where x[j] = 0 for all j in Jp and x[j] = 1 for all j in Jn.) * * NOTE: If |J| = 2, the inequality (3) is equivalent to packing * inequality (see the routine npp_is_packing). */ int npp_is_covering(NPP *npp, NPPROW *row) { /* test if constraint is covering inequality */ NPPCOL *col; NPPAIJ *aij; int b; xassert(npp == npp); if (!(row->lb != -DBL_MAX && row->ub == +DBL_MAX)) return 0; b = 1; for (aij = row->ptr; aij != NULL; aij = aij->r_next) { col = aij->col; if (!(col->is_int && col->lb == 0.0 && col->ub == 1.0)) return 0; if (aij->val == +1.0) ; else if (aij->val == -1.0) b--; else return 0; } if (row->lb != (double)b) return 0; return 1; } /*********************************************************************** * NAME * * npp_hidden_covering - identify hidden covering inequality * * SYNOPSIS * * #include "glpnpp.h" * int npp_hidden_covering(NPP *npp, NPPROW *row); * * DESCRIPTION * * The routine npp_hidden_covering processes specified inequality * constraint, which includes only binary variables, and the number of * the variables is not less than three. If the original inequality is * equivalent to a covering inequality (see below), the routine * replaces it by the equivalent inequality. If the original constraint * is double-sided inequality, it is replaced by a pair of single-sided * inequalities, if necessary. * * RETURNS * * If the original inequality constraint was replaced by equivalent * covering inequality, the routine npp_hidden_covering returns * non-zero. Otherwise, it returns zero. * * PROBLEM TRANSFORMATION * * Consider an inequality constraint: * * sum a[j] x[j] >= b, (1) * j in J * * where all variables x[j] are binary, and |J| >= 3. (In case of '<=' * inequality it can be transformed to '>=' format by multiplying both * its sides by -1.) * * Let Jp = {j: a[j] > 0}, Jn = {j: a[j] < 0}. Performing substitution * x[j] = 1 - x~[j] for all j in Jn, we have: * * sum a[j] x[j] >= b ==> * j in J * * sum a[j] x[j] + sum a[j] x[j] >= b ==> * j in Jp j in Jn * * sum a[j] x[j] + sum a[j] (1 - x~[j]) >= b ==> * j in Jp j in Jn * * sum m a[j] x[j] - sum a[j] x~[j] >= b - sum a[j]. * j in Jp j in Jn j in Jn * * Thus, meaning the transformation above, we can assume that in * inequality (1) all coefficients a[j] are positive. Moreover, we can * assume that b > 0, because otherwise the inequality (1) would be * redundant (see the routine npp_analyze_row). It is then obvious that * constraint (1) is equivalent to covering inequality only if: * * a[j] >= b, (2) * * for all j in J. * * Once the original inequality (1) is replaced by equivalent covering * inequality, we need to perform back substitution x~[j] = 1 - x[j] for * all j in Jn (see above). * * RECOVERING SOLUTION * * None needed. */ static int hidden_covering(NPP *npp, struct elem *ptr, double *_b) { /* process inequality constraint: sum a[j] x[j] >= b; 0 - specified row is NOT hidden covering inequality; 1 - specified row is covering inequality; 2 - specified row is hidden covering inequality. */ struct elem *e; int neg; double b = *_b, eps; xassert(npp == npp); /* a[j] must be non-zero, x[j] must be binary, for all j in J */ for (e = ptr; e != NULL; e = e->next) { xassert(e->aj != 0.0); xassert(e->xj->is_int); xassert(e->xj->lb == 0.0 && e->xj->ub == 1.0); } /* check if the specified inequality constraint already has the form of covering inequality */ neg = 0; /* neg is |Jn| */ for (e = ptr; e != NULL; e = e->next) { if (e->aj == +1.0) ; else if (e->aj == -1.0) neg++; else break; } if (e == NULL) { /* all coefficients a[j] are +1 or -1; check rhs b */ if (b == (double)(1 - neg)) { /* it is covering inequality; no processing is needed */ return 1; } } /* substitute x[j] = 1 - x~[j] for all j in Jn to make all a[j] positive; the result is a~[j] = |a[j]| and new rhs b */ for (e = ptr; e != NULL; e = e->next) if (e->aj < 0) b -= e->aj; /* now a[j] > 0 for all j in J (actually |a[j]| are used) */ /* if b <= 0, skip processing--this case must not appear */ if (b < 1e-3) return 0; /* now a[j] > 0 for all j in J, and b > 0 */ /* the specified constraint is equivalent to covering inequality iff a[j] >= b for all j in J */ eps = 1e-9 + 1e-12 * fabs(b); for (e = ptr; e != NULL; e = e->next) if (fabs(e->aj) < b - eps) return 0; /* perform back substitution x~[j] = 1 - x[j] and construct the final equivalent covering inequality in generalized format */ b = 1.0; for (e = ptr; e != NULL; e = e->next) { if (e->aj > 0.0) e->aj = +1.0; else /* e->aj < 0.0 */ e->aj = -1.0, b -= 1.0; } *_b = b; return 2; } int npp_hidden_covering(NPP *npp, NPPROW *row) { /* identify hidden covering inequality */ NPPROW *copy; NPPAIJ *aij; struct elem *ptr, *e; int kase, ret, count = 0; double b; /* the row must be inequality constraint */ xassert(row->lb < row->ub); for (kase = 0; kase <= 1; kase++) { if (kase == 0) { /* process row lower bound */ if (row->lb == -DBL_MAX) continue; ptr = copy_form(npp, row, +1.0); b = + row->lb; } else { /* process row upper bound */ if (row->ub == +DBL_MAX) continue; ptr = copy_form(npp, row, -1.0); b = - row->ub; } /* now the inequality has the form "sum a[j] x[j] >= b" */ ret = hidden_covering(npp, ptr, &b); xassert(0 <= ret && ret <= 2); if (kase == 1 && ret == 1 || ret == 2) { /* the original inequality has been identified as hidden covering inequality */ count++; #ifdef GLP_DEBUG xprintf("Original constraint:\n"); for (aij = row->ptr; aij != NULL; aij = aij->r_next) xprintf(" %+g x%d", aij->val, aij->col->j); if (row->lb != -DBL_MAX) xprintf(", >= %g", row->lb); if (row->ub != +DBL_MAX) xprintf(", <= %g", row->ub); xprintf("\n"); xprintf("Equivalent covering inequality:\n"); for (e = ptr; e != NULL; e = e->next) xprintf(" %sx%d", e->aj > 0.0 ? "+" : "-", e->xj->j); xprintf(", >= %g\n", b); #endif if (row->lb == -DBL_MAX || row->ub == +DBL_MAX) { /* the original row is single-sided inequality; no copy is needed */ copy = NULL; } else { /* the original row is double-sided inequality; we need to create its copy for other bound before replacing it with the equivalent inequality */ copy = npp_add_row(npp); if (kase == 0) { /* the copy is for upper bound */ copy->lb = -DBL_MAX, copy->ub = row->ub; } else { /* the copy is for lower bound */ copy->lb = row->lb, copy->ub = +DBL_MAX; } /* copy original row coefficients */ for (aij = row->ptr; aij != NULL; aij = aij->r_next) npp_add_aij(npp, copy, aij->col, aij->val); } /* replace the original inequality by equivalent one */ npp_erase_row(npp, row); row->lb = b, row->ub = +DBL_MAX; for (e = ptr; e != NULL; e = e->next) npp_add_aij(npp, row, e->xj, e->aj); /* continue processing upper bound for the copy */ if (copy != NULL) row = copy; } drop_form(npp, ptr); } return count; } /*********************************************************************** * NAME * * npp_is_partitioning - test if constraint is partitioning equality * * SYNOPSIS * * #include "glpnpp.h" * int npp_is_partitioning(NPP *npp, NPPROW *row); * * RETURNS * * If the specified row (constraint) is partitioning equality (see * below), the routine npp_is_partitioning returns non-zero. Otherwise, * it returns zero. * * PARTITIONING EQUALITIES * * In canonical format the partitioning equality is the following: * * sum x[j] = 1, (1) * j in J * * where all variables x[j] are binary. This equality expresses the * condition that in any integer feasible solution exactly one variable * in set J must take non-zero (unity) value while other variables must * be equal to zero. W.l.o.g. it is assumed that |J| >= 2, because if * J is empty, the inequality (1) is infeasible, and if |J| = 1, the * inequality (1) is a fixing row. * * In general case the partitioning equality may include original * variables x[j] as well as their complements x~[j]: * * sum x[j] + sum x~[j] = 1, (2) * j in Jp j in Jn * * where Jp and Jn are not intersected. Therefore, using substitution * x~[j] = 1 - x[j] leads to the partitioning equality in generalized * format: * * sum x[j] - sum x[j] = 1 - |Jn|. (3) * j in Jp j in Jn */ int npp_is_partitioning(NPP *npp, NPPROW *row) { /* test if constraint is partitioning equality */ NPPCOL *col; NPPAIJ *aij; int b; xassert(npp == npp); if (row->lb != row->ub) return 0; b = 1; for (aij = row->ptr; aij != NULL; aij = aij->r_next) { col = aij->col; if (!(col->is_int && col->lb == 0.0 && col->ub == 1.0)) return 0; if (aij->val == +1.0) ; else if (aij->val == -1.0) b--; else return 0; } if (row->lb != (double)b) return 0; return 1; } /*********************************************************************** * NAME * * npp_reduce_ineq_coef - reduce inequality constraint coefficients * * SYNOPSIS * * #include "glpnpp.h" * int npp_reduce_ineq_coef(NPP *npp, NPPROW *row); * * DESCRIPTION * * The routine npp_reduce_ineq_coef processes specified inequality * constraint attempting to replace it by an equivalent constraint, * where magnitude of coefficients at binary variables is smaller than * in the original constraint. If the inequality is double-sided, it is * replaced by a pair of single-sided inequalities, if necessary. * * RETURNS * * The routine npp_reduce_ineq_coef returns the number of coefficients * reduced. * * BACKGROUND * * Consider an inequality constraint: * * sum a[j] x[j] >= b. (1) * j in J * * (In case of '<=' inequality it can be transformed to '>=' format by * multiplying both its sides by -1.) Let x[k] be a binary variable; * other variables can be integer as well as continuous. We can write * constraint (1) as follows: * * a[k] x[k] + t[k] >= b, (2) * * where: * * t[k] = sum a[j] x[j]. (3) * j in J\{k} * * Since x[k] is binary, constraint (2) is equivalent to disjunction of * the following two constraints: * * x[k] = 0, t[k] >= b (4) * * OR * * x[k] = 1, t[k] >= b - a[k]. (5) * * Let also that for the partial sum t[k] be known some its implied * lower bound inf t[k]. * * Case a[k] > 0. Let inf t[k] < b, since otherwise both constraints * (4) and (5) and therefore constraint (2) are redundant. * If inf t[k] > b - a[k], only constraint (5) is redundant, in which * case it can be replaced with the following redundant and therefore * equivalent constraint: * * t[k] >= b - a'[k] = inf t[k], (6) * * where: * * a'[k] = b - inf t[k]. (7) * * Thus, the original constraint (2) is equivalent to the following * constraint with coefficient at variable x[k] changed: * * a'[k] x[k] + t[k] >= b. (8) * * From inf t[k] < b it follows that a'[k] > 0, i.e. the coefficient * at x[k] keeps its sign. And from inf t[k] > b - a[k] it follows that * a'[k] < a[k], i.e. the coefficient reduces in magnitude. * * Case a[k] < 0. Let inf t[k] < b - a[k], since otherwise both * constraints (4) and (5) and therefore constraint (2) are redundant. * If inf t[k] > b, only constraint (4) is redundant, in which case it * can be replaced with the following redundant and therefore equivalent * constraint: * * t[k] >= b' = inf t[k]. (9) * * Rewriting constraint (5) as follows: * * t[k] >= b - a[k] = b' - a'[k], (10) * * where: * * a'[k] = a[k] + b' - b = a[k] + inf t[k] - b, (11) * * we can see that disjunction of constraint (9) and (10) is equivalent * to disjunction of constraint (4) and (5), from which it follows that * the original constraint (2) is equivalent to the following constraint * with both coefficient at variable x[k] and right-hand side changed: * * a'[k] x[k] + t[k] >= b'. (12) * * From inf t[k] < b - a[k] it follows that a'[k] < 0, i.e. the * coefficient at x[k] keeps its sign. And from inf t[k] > b it follows * that a'[k] > a[k], i.e. the coefficient reduces in magnitude. * * PROBLEM TRANSFORMATION * * In the routine npp_reduce_ineq_coef the following implied lower * bound of the partial sum (3) is used: * * inf t[k] = sum a[j] l[j] + sum a[j] u[j], (13) * j in Jp\{k} k in Jn\{k} * * where Jp = {j : a[j] > 0}, Jn = {j : a[j] < 0}, l[j] and u[j] are * lower and upper bounds, resp., of variable x[j]. * * In order to compute inf t[k] more efficiently, the following formula, * which is equivalent to (13), is actually used: * * ( h - a[k] l[k] = h, if a[k] > 0, * inf t[k] = < (14) * ( h - a[k] u[k] = h - a[k], if a[k] < 0, * * where: * * h = sum a[j] l[j] + sum a[j] u[j] (15) * j in Jp j in Jn * * is the implied lower bound of row (1). * * Reduction of positive coefficient (a[k] > 0) does not change value * of h, since l[k] = 0. In case of reduction of negative coefficient * (a[k] < 0) from (11) it follows that: * * delta a[k] = a'[k] - a[k] = inf t[k] - b (> 0), (16) * * so new value of h (accounting that u[k] = 1) can be computed as * follows: * * h := h + delta a[k] = h + (inf t[k] - b). (17) * * RECOVERING SOLUTION * * None needed. */ static int reduce_ineq_coef(NPP *npp, struct elem *ptr, double *_b) { /* process inequality constraint: sum a[j] x[j] >= b */ /* returns: the number of coefficients reduced */ struct elem *e; int count = 0; double h, inf_t, new_a, b = *_b; xassert(npp == npp); /* compute h; see (15) */ h = 0.0; for (e = ptr; e != NULL; e = e->next) { if (e->aj > 0.0) { if (e->xj->lb == -DBL_MAX) goto done; h += e->aj * e->xj->lb; } else /* e->aj < 0.0 */ { if (e->xj->ub == +DBL_MAX) goto done; h += e->aj * e->xj->ub; } } /* perform reduction of coefficients at binary variables */ for (e = ptr; e != NULL; e = e->next) { /* skip non-binary variable */ if (!(e->xj->is_int && e->xj->lb == 0.0 && e->xj->ub == 1.0)) continue; if (e->aj > 0.0) { /* compute inf t[k]; see (14) */ inf_t = h; if (b - e->aj < inf_t && inf_t < b) { /* compute reduced coefficient a'[k]; see (7) */ new_a = b - inf_t; if (new_a >= +1e-3 && e->aj - new_a >= 0.01 * (1.0 + e->aj)) { /* accept a'[k] */ #ifdef GLP_DEBUG xprintf("+"); #endif e->aj = new_a; count++; } } } else /* e->aj < 0.0 */ { /* compute inf t[k]; see (14) */ inf_t = h - e->aj; if (b < inf_t && inf_t < b - e->aj) { /* compute reduced coefficient a'[k]; see (11) */ new_a = e->aj + (inf_t - b); if (new_a <= -1e-3 && new_a - e->aj >= 0.01 * (1.0 - e->aj)) { /* accept a'[k] */ #ifdef GLP_DEBUG xprintf("-"); #endif e->aj = new_a; /* update h; see (17) */ h += (inf_t - b); /* compute b'; see (9) */ b = inf_t; count++; } } } } *_b = b; done: return count; } int npp_reduce_ineq_coef(NPP *npp, NPPROW *row) { /* reduce inequality constraint coefficients */ NPPROW *copy; NPPAIJ *aij; struct elem *ptr, *e; int kase, count[2]; double b; /* the row must be inequality constraint */ xassert(row->lb < row->ub); count[0] = count[1] = 0; for (kase = 0; kase <= 1; kase++) { if (kase == 0) { /* process row lower bound */ if (row->lb == -DBL_MAX) continue; #ifdef GLP_DEBUG xprintf("L"); #endif ptr = copy_form(npp, row, +1.0); b = + row->lb; } else { /* process row upper bound */ if (row->ub == +DBL_MAX) continue; #ifdef GLP_DEBUG xprintf("U"); #endif ptr = copy_form(npp, row, -1.0); b = - row->ub; } /* now the inequality has the form "sum a[j] x[j] >= b" */ count[kase] = reduce_ineq_coef(npp, ptr, &b); if (count[kase] > 0) { /* the original inequality has been replaced by equivalent one with coefficients reduced */ if (row->lb == -DBL_MAX || row->ub == +DBL_MAX) { /* the original row is single-sided inequality; no copy is needed */ copy = NULL; } else { /* the original row is double-sided inequality; we need to create its copy for other bound before replacing it with the equivalent inequality */ #ifdef GLP_DEBUG xprintf("*"); #endif copy = npp_add_row(npp); if (kase == 0) { /* the copy is for upper bound */ copy->lb = -DBL_MAX, copy->ub = row->ub; } else { /* the copy is for lower bound */ copy->lb = row->lb, copy->ub = +DBL_MAX; } /* copy original row coefficients */ for (aij = row->ptr; aij != NULL; aij = aij->r_next) npp_add_aij(npp, copy, aij->col, aij->val); } /* replace the original inequality by equivalent one */ npp_erase_row(npp, row); row->lb = b, row->ub = +DBL_MAX; for (e = ptr; e != NULL; e = e->next) npp_add_aij(npp, row, e->xj, e->aj); /* continue processing upper bound for the copy */ if (copy != NULL) row = copy; } drop_form(npp, ptr); } return count[0] + count[1]; } /* eof */ sources_5316/external/glpk/glpluf.c0000644000176700017670000021356311401660400016141 0ustar paulpaul/* glpluf.c (LU-factorization) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glpluf.h" #define xfault xerror /* CAUTION: DO NOT CHANGE THE LIMIT BELOW */ #define N_MAX 100000000 /* = 100*10^6 */ /* maximal order of the original matrix */ /*********************************************************************** * NAME * * luf_create_it - create LU-factorization * * SYNOPSIS * * #include "glpluf.h" * LUF *luf_create_it(void); * * DESCRIPTION * * The routine luf_create_it creates a program object, which represents * LU-factorization of a square matrix. * * RETURNS * * The routine luf_create_it returns a pointer to the object created. */ LUF *luf_create_it(void) { LUF *luf; luf = xmalloc(sizeof(LUF)); luf->n_max = luf->n = 0; luf->valid = 0; luf->fr_ptr = luf->fr_len = NULL; luf->fc_ptr = luf->fc_len = NULL; luf->vr_ptr = luf->vr_len = luf->vr_cap = NULL; luf->vr_piv = NULL; luf->vc_ptr = luf->vc_len = luf->vc_cap = NULL; luf->pp_row = luf->pp_col = NULL; luf->qq_row = luf->qq_col = NULL; luf->sv_size = 0; luf->sv_beg = luf->sv_end = 0; luf->sv_ind = NULL; luf->sv_val = NULL; luf->sv_head = luf->sv_tail = 0; luf->sv_prev = luf->sv_next = NULL; luf->vr_max = NULL; luf->rs_head = luf->rs_prev = luf->rs_next = NULL; luf->cs_head = luf->cs_prev = luf->cs_next = NULL; luf->flag = NULL; luf->work = NULL; luf->new_sva = 0; luf->piv_tol = 0.10; luf->piv_lim = 4; luf->suhl = 1; luf->eps_tol = 1e-15; luf->max_gro = 1e+10; luf->nnz_a = luf->nnz_f = luf->nnz_v = 0; luf->max_a = luf->big_v = 0.0; luf->rank = 0; return luf; } /*********************************************************************** * NAME * * luf_defrag_sva - defragment the sparse vector area * * SYNOPSIS * * #include "glpluf.h" * void luf_defrag_sva(LUF *luf); * * DESCRIPTION * * The routine luf_defrag_sva defragments the sparse vector area (SVA) * gathering all unused locations in one continuous extent. In order to * do that the routine moves all unused locations from the left part of * SVA (which contains rows and columns of the matrix V) to the middle * part (which contains free locations). This is attained by relocating * elements of rows and columns of the matrix V toward the beginning of * the left part. * * NOTE that this "garbage collection" involves changing row and column * pointers of the matrix V. */ void luf_defrag_sva(LUF *luf) { int n = luf->n; int *vr_ptr = luf->vr_ptr; int *vr_len = luf->vr_len; int *vr_cap = luf->vr_cap; int *vc_ptr = luf->vc_ptr; int *vc_len = luf->vc_len; int *vc_cap = luf->vc_cap; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; int *sv_next = luf->sv_next; int sv_beg = 1; int i, j, k; /* skip rows and columns, which do not need to be relocated */ for (k = luf->sv_head; k != 0; k = sv_next[k]) { if (k <= n) { /* i-th row of the matrix V */ i = k; if (vr_ptr[i] != sv_beg) break; vr_cap[i] = vr_len[i]; sv_beg += vr_cap[i]; } else { /* j-th column of the matrix V */ j = k - n; if (vc_ptr[j] != sv_beg) break; vc_cap[j] = vc_len[j]; sv_beg += vc_cap[j]; } } /* relocate other rows and columns in order to gather all unused locations in one continuous extent */ for (k = k; k != 0; k = sv_next[k]) { if (k <= n) { /* i-th row of the matrix V */ i = k; memmove(&sv_ind[sv_beg], &sv_ind[vr_ptr[i]], vr_len[i] * sizeof(int)); memmove(&sv_val[sv_beg], &sv_val[vr_ptr[i]], vr_len[i] * sizeof(double)); vr_ptr[i] = sv_beg; vr_cap[i] = vr_len[i]; sv_beg += vr_cap[i]; } else { /* j-th column of the matrix V */ j = k - n; memmove(&sv_ind[sv_beg], &sv_ind[vc_ptr[j]], vc_len[j] * sizeof(int)); memmove(&sv_val[sv_beg], &sv_val[vc_ptr[j]], vc_len[j] * sizeof(double)); vc_ptr[j] = sv_beg; vc_cap[j] = vc_len[j]; sv_beg += vc_cap[j]; } } /* set new pointer to the beginning of the free part */ luf->sv_beg = sv_beg; return; } /*********************************************************************** * NAME * * luf_enlarge_row - enlarge row capacity * * SYNOPSIS * * #include "glpluf.h" * int luf_enlarge_row(LUF *luf, int i, int cap); * * DESCRIPTION * * The routine luf_enlarge_row enlarges capacity of the i-th row of the * matrix V to cap locations (assuming that its current capacity is less * than cap). In order to do that the routine relocates elements of the * i-th row to the end of the left part of SVA (which contains rows and * columns of the matrix V) and then expands the left part by allocating * cap free locations from the free part. If there are less than cap * free locations, the routine defragments the sparse vector area. * * Due to "garbage collection" this operation may change row and column * pointers of the matrix V. * * RETURNS * * If no error occured, the routine returns zero. Otherwise, in case of * overflow of the sparse vector area, the routine returns non-zero. */ int luf_enlarge_row(LUF *luf, int i, int cap) { int n = luf->n; int *vr_ptr = luf->vr_ptr; int *vr_len = luf->vr_len; int *vr_cap = luf->vr_cap; int *vc_cap = luf->vc_cap; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; int *sv_prev = luf->sv_prev; int *sv_next = luf->sv_next; int ret = 0; int cur, k, kk; xassert(1 <= i && i <= n); xassert(vr_cap[i] < cap); /* if there are less than cap free locations, defragment SVA */ if (luf->sv_end - luf->sv_beg < cap) { luf_defrag_sva(luf); if (luf->sv_end - luf->sv_beg < cap) { ret = 1; goto done; } } /* save current capacity of the i-th row */ cur = vr_cap[i]; /* copy existing elements to the beginning of the free part */ memmove(&sv_ind[luf->sv_beg], &sv_ind[vr_ptr[i]], vr_len[i] * sizeof(int)); memmove(&sv_val[luf->sv_beg], &sv_val[vr_ptr[i]], vr_len[i] * sizeof(double)); /* set new pointer and new capacity of the i-th row */ vr_ptr[i] = luf->sv_beg; vr_cap[i] = cap; /* set new pointer to the beginning of the free part */ luf->sv_beg += cap; /* now the i-th row starts in the rightmost location among other rows and columns of the matrix V, so its node should be moved to the end of the row/column linked list */ k = i; /* remove the i-th row node from the linked list */ if (sv_prev[k] == 0) luf->sv_head = sv_next[k]; else { /* capacity of the previous row/column can be increased at the expense of old locations of the i-th row */ kk = sv_prev[k]; if (kk <= n) vr_cap[kk] += cur; else vc_cap[kk-n] += cur; sv_next[sv_prev[k]] = sv_next[k]; } if (sv_next[k] == 0) luf->sv_tail = sv_prev[k]; else sv_prev[sv_next[k]] = sv_prev[k]; /* insert the i-th row node to the end of the linked list */ sv_prev[k] = luf->sv_tail; sv_next[k] = 0; if (sv_prev[k] == 0) luf->sv_head = k; else sv_next[sv_prev[k]] = k; luf->sv_tail = k; done: return ret; } /*********************************************************************** * NAME * * luf_enlarge_col - enlarge column capacity * * SYNOPSIS * * #include "glpluf.h" * int luf_enlarge_col(LUF *luf, int j, int cap); * * DESCRIPTION * * The routine luf_enlarge_col enlarges capacity of the j-th column of * the matrix V to cap locations (assuming that its current capacity is * less than cap). In order to do that the routine relocates elements * of the j-th column to the end of the left part of SVA (which contains * rows and columns of the matrix V) and then expands the left part by * allocating cap free locations from the free part. If there are less * than cap free locations, the routine defragments the sparse vector * area. * * Due to "garbage collection" this operation may change row and column * pointers of the matrix V. * * RETURNS * * If no error occured, the routine returns zero. Otherwise, in case of * overflow of the sparse vector area, the routine returns non-zero. */ int luf_enlarge_col(LUF *luf, int j, int cap) { int n = luf->n; int *vr_cap = luf->vr_cap; int *vc_ptr = luf->vc_ptr; int *vc_len = luf->vc_len; int *vc_cap = luf->vc_cap; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; int *sv_prev = luf->sv_prev; int *sv_next = luf->sv_next; int ret = 0; int cur, k, kk; xassert(1 <= j && j <= n); xassert(vc_cap[j] < cap); /* if there are less than cap free locations, defragment SVA */ if (luf->sv_end - luf->sv_beg < cap) { luf_defrag_sva(luf); if (luf->sv_end - luf->sv_beg < cap) { ret = 1; goto done; } } /* save current capacity of the j-th column */ cur = vc_cap[j]; /* copy existing elements to the beginning of the free part */ memmove(&sv_ind[luf->sv_beg], &sv_ind[vc_ptr[j]], vc_len[j] * sizeof(int)); memmove(&sv_val[luf->sv_beg], &sv_val[vc_ptr[j]], vc_len[j] * sizeof(double)); /* set new pointer and new capacity of the j-th column */ vc_ptr[j] = luf->sv_beg; vc_cap[j] = cap; /* set new pointer to the beginning of the free part */ luf->sv_beg += cap; /* now the j-th column starts in the rightmost location among other rows and columns of the matrix V, so its node should be moved to the end of the row/column linked list */ k = n + j; /* remove the j-th column node from the linked list */ if (sv_prev[k] == 0) luf->sv_head = sv_next[k]; else { /* capacity of the previous row/column can be increased at the expense of old locations of the j-th column */ kk = sv_prev[k]; if (kk <= n) vr_cap[kk] += cur; else vc_cap[kk-n] += cur; sv_next[sv_prev[k]] = sv_next[k]; } if (sv_next[k] == 0) luf->sv_tail = sv_prev[k]; else sv_prev[sv_next[k]] = sv_prev[k]; /* insert the j-th column node to the end of the linked list */ sv_prev[k] = luf->sv_tail; sv_next[k] = 0; if (sv_prev[k] == 0) luf->sv_head = k; else sv_next[sv_prev[k]] = k; luf->sv_tail = k; done: return ret; } /*********************************************************************** * reallocate - reallocate LU-factorization arrays * * This routine reallocates arrays, whose size depends of n, the order * of the matrix A to be factorized. */ static void reallocate(LUF *luf, int n) { int n_max = luf->n_max; luf->n = n; if (n <= n_max) goto done; if (luf->fr_ptr != NULL) xfree(luf->fr_ptr); if (luf->fr_len != NULL) xfree(luf->fr_len); if (luf->fc_ptr != NULL) xfree(luf->fc_ptr); if (luf->fc_len != NULL) xfree(luf->fc_len); if (luf->vr_ptr != NULL) xfree(luf->vr_ptr); if (luf->vr_len != NULL) xfree(luf->vr_len); if (luf->vr_cap != NULL) xfree(luf->vr_cap); if (luf->vr_piv != NULL) xfree(luf->vr_piv); if (luf->vc_ptr != NULL) xfree(luf->vc_ptr); if (luf->vc_len != NULL) xfree(luf->vc_len); if (luf->vc_cap != NULL) xfree(luf->vc_cap); if (luf->pp_row != NULL) xfree(luf->pp_row); if (luf->pp_col != NULL) xfree(luf->pp_col); if (luf->qq_row != NULL) xfree(luf->qq_row); if (luf->qq_col != NULL) xfree(luf->qq_col); if (luf->sv_prev != NULL) xfree(luf->sv_prev); if (luf->sv_next != NULL) xfree(luf->sv_next); if (luf->vr_max != NULL) xfree(luf->vr_max); if (luf->rs_head != NULL) xfree(luf->rs_head); if (luf->rs_prev != NULL) xfree(luf->rs_prev); if (luf->rs_next != NULL) xfree(luf->rs_next); if (luf->cs_head != NULL) xfree(luf->cs_head); if (luf->cs_prev != NULL) xfree(luf->cs_prev); if (luf->cs_next != NULL) xfree(luf->cs_next); if (luf->flag != NULL) xfree(luf->flag); if (luf->work != NULL) xfree(luf->work); luf->n_max = n_max = n + 100; luf->fr_ptr = xcalloc(1+n_max, sizeof(int)); luf->fr_len = xcalloc(1+n_max, sizeof(int)); luf->fc_ptr = xcalloc(1+n_max, sizeof(int)); luf->fc_len = xcalloc(1+n_max, sizeof(int)); luf->vr_ptr = xcalloc(1+n_max, sizeof(int)); luf->vr_len = xcalloc(1+n_max, sizeof(int)); luf->vr_cap = xcalloc(1+n_max, sizeof(int)); luf->vr_piv = xcalloc(1+n_max, sizeof(double)); luf->vc_ptr = xcalloc(1+n_max, sizeof(int)); luf->vc_len = xcalloc(1+n_max, sizeof(int)); luf->vc_cap = xcalloc(1+n_max, sizeof(int)); luf->pp_row = xcalloc(1+n_max, sizeof(int)); luf->pp_col = xcalloc(1+n_max, sizeof(int)); luf->qq_row = xcalloc(1+n_max, sizeof(int)); luf->qq_col = xcalloc(1+n_max, sizeof(int)); luf->sv_prev = xcalloc(1+n_max+n_max, sizeof(int)); luf->sv_next = xcalloc(1+n_max+n_max, sizeof(int)); luf->vr_max = xcalloc(1+n_max, sizeof(double)); luf->rs_head = xcalloc(1+n_max, sizeof(int)); luf->rs_prev = xcalloc(1+n_max, sizeof(int)); luf->rs_next = xcalloc(1+n_max, sizeof(int)); luf->cs_head = xcalloc(1+n_max, sizeof(int)); luf->cs_prev = xcalloc(1+n_max, sizeof(int)); luf->cs_next = xcalloc(1+n_max, sizeof(int)); luf->flag = xcalloc(1+n_max, sizeof(int)); luf->work = xcalloc(1+n_max, sizeof(double)); done: return; } /*********************************************************************** * initialize - initialize LU-factorization data structures * * This routine initializes data structures for subsequent computing * the LU-factorization of a given matrix A, which is specified by the * formal routine col. On exit V = A and F = P = Q = I, where I is the * unity matrix. (Row-wise representation of the matrix F is not used * at the factorization stage and therefore is not initialized.) * * If no error occured, the routine returns zero. Otherwise, in case of * overflow of the sparse vector area, the routine returns non-zero. */ static int initialize(LUF *luf, int (*col)(void *info, int j, int rn[], double aj[]), void *info) { int n = luf->n; int *fc_ptr = luf->fc_ptr; int *fc_len = luf->fc_len; int *vr_ptr = luf->vr_ptr; int *vr_len = luf->vr_len; int *vr_cap = luf->vr_cap; int *vc_ptr = luf->vc_ptr; int *vc_len = luf->vc_len; int *vc_cap = luf->vc_cap; int *pp_row = luf->pp_row; int *pp_col = luf->pp_col; int *qq_row = luf->qq_row; int *qq_col = luf->qq_col; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; int *sv_prev = luf->sv_prev; int *sv_next = luf->sv_next; double *vr_max = luf->vr_max; int *rs_head = luf->rs_head; int *rs_prev = luf->rs_prev; int *rs_next = luf->rs_next; int *cs_head = luf->cs_head; int *cs_prev = luf->cs_prev; int *cs_next = luf->cs_next; int *flag = luf->flag; double *work = luf->work; int ret = 0; int i, i_ptr, j, j_beg, j_end, k, len, nnz, sv_beg, sv_end, ptr; double big, val; /* free all locations of the sparse vector area */ sv_beg = 1; sv_end = luf->sv_size + 1; /* (row-wise representation of the matrix F is not initialized, because it is not used at the factorization stage) */ /* build the matrix F in column-wise format (initially F = I) */ for (j = 1; j <= n; j++) { fc_ptr[j] = sv_end; fc_len[j] = 0; } /* clear rows of the matrix V; clear the flag array */ for (i = 1; i <= n; i++) vr_len[i] = vr_cap[i] = 0, flag[i] = 0; /* build the matrix V in column-wise format (initially V = A); count non-zeros in rows of this matrix; count total number of non-zeros; compute largest of absolute values of elements */ nnz = 0; big = 0.0; for (j = 1; j <= n; j++) { int *rn = pp_row; double *aj = work; /* obtain j-th column of the matrix A */ len = col(info, j, rn, aj); if (!(0 <= len && len <= n)) xfault("luf_factorize: j = %d; len = %d; invalid column len" "gth\n", j, len); /* check for free locations */ if (sv_end - sv_beg < len) { /* overflow of the sparse vector area */ ret = 1; goto done; } /* set pointer to the j-th column */ vc_ptr[j] = sv_beg; /* set length of the j-th column */ vc_len[j] = vc_cap[j] = len; /* count total number of non-zeros */ nnz += len; /* walk through elements of the j-th column */ for (ptr = 1; ptr <= len; ptr++) { /* get row index and numerical value of a[i,j] */ i = rn[ptr]; val = aj[ptr]; if (!(1 <= i && i <= n)) xfault("luf_factorize: i = %d; j = %d; invalid row index" "\n", i, j); if (flag[i]) xfault("luf_factorize: i = %d; j = %d; duplicate element" " not allowed\n", i, j); if (val == 0.0) xfault("luf_factorize: i = %d; j = %d; zero element not " "allowed\n", i, j); /* add new element v[i,j] = a[i,j] to j-th column */ sv_ind[sv_beg] = i; sv_val[sv_beg] = val; sv_beg++; /* big := max(big, |a[i,j]|) */ if (val < 0.0) val = - val; if (big < val) big = val; /* mark non-zero in the i-th position of the j-th column */ flag[i] = 1; /* increase length of the i-th row */ vr_cap[i]++; } /* reset all non-zero marks */ for (ptr = 1; ptr <= len; ptr++) flag[rn[ptr]] = 0; } /* allocate rows of the matrix V */ for (i = 1; i <= n; i++) { /* get length of the i-th row */ len = vr_cap[i]; /* check for free locations */ if (sv_end - sv_beg < len) { /* overflow of the sparse vector area */ ret = 1; goto done; } /* set pointer to the i-th row */ vr_ptr[i] = sv_beg; /* reserve locations for the i-th row */ sv_beg += len; } /* build the matrix V in row-wise format using representation of this matrix in column-wise format */ for (j = 1; j <= n; j++) { /* walk through elements of the j-th column */ j_beg = vc_ptr[j]; j_end = j_beg + vc_len[j] - 1; for (k = j_beg; k <= j_end; k++) { /* get row index and numerical value of v[i,j] */ i = sv_ind[k]; val = sv_val[k]; /* store element in the i-th row */ i_ptr = vr_ptr[i] + vr_len[i]; sv_ind[i_ptr] = j; sv_val[i_ptr] = val; /* increase count of the i-th row */ vr_len[i]++; } } /* initialize the matrices P and Q (initially P = Q = I) */ for (k = 1; k <= n; k++) pp_row[k] = pp_col[k] = qq_row[k] = qq_col[k] = k; /* set sva partitioning pointers */ luf->sv_beg = sv_beg; luf->sv_end = sv_end; /* the initial physical order of rows and columns of the matrix V is n+1, ..., n+n, 1, ..., n (firstly columns, then rows) */ luf->sv_head = n+1; luf->sv_tail = n; for (i = 1; i <= n; i++) { sv_prev[i] = i-1; sv_next[i] = i+1; } sv_prev[1] = n+n; sv_next[n] = 0; for (j = 1; j <= n; j++) { sv_prev[n+j] = n+j-1; sv_next[n+j] = n+j+1; } sv_prev[n+1] = 0; sv_next[n+n] = 1; /* clear working arrays */ for (k = 1; k <= n; k++) { flag[k] = 0; work[k] = 0.0; } /* initialize some statistics */ luf->nnz_a = nnz; luf->nnz_f = 0; luf->nnz_v = nnz; luf->max_a = big; luf->big_v = big; luf->rank = -1; /* initially the active submatrix is the entire matrix V */ /* largest of absolute values of elements in each active row is unknown yet */ for (i = 1; i <= n; i++) vr_max[i] = -1.0; /* build linked lists of active rows */ for (len = 0; len <= n; len++) rs_head[len] = 0; for (i = 1; i <= n; i++) { len = vr_len[i]; rs_prev[i] = 0; rs_next[i] = rs_head[len]; if (rs_next[i] != 0) rs_prev[rs_next[i]] = i; rs_head[len] = i; } /* build linked lists of active columns */ for (len = 0; len <= n; len++) cs_head[len] = 0; for (j = 1; j <= n; j++) { len = vc_len[j]; cs_prev[j] = 0; cs_next[j] = cs_head[len]; if (cs_next[j] != 0) cs_prev[cs_next[j]] = j; cs_head[len] = j; } done: /* return to the factorizing routine */ return ret; } /*********************************************************************** * find_pivot - choose a pivot element * * This routine chooses a pivot element in the active submatrix of the * matrix U = P*V*Q. * * It is assumed that on entry the matrix U has the following partially * triangularized form: * * 1 k n * 1 x x x x x x x x x x * . x x x x x x x x x * . . x x x x x x x x * . . . x x x x x x x * k . . . . * * * * * * * . . . . * * * * * * * . . . . * * * * * * * . . . . * * * * * * * . . . . * * * * * * * n . . . . * * * * * * * * where rows and columns k, k+1, ..., n belong to the active submatrix * (elements of the active submatrix are marked by '*'). * * Since the matrix U = P*V*Q is not stored, the routine works with the * matrix V. It is assumed that the row-wise representation corresponds * to the matrix V, but the column-wise representation corresponds to * the active submatrix of the matrix V, i.e. elements of the matrix V, * which doesn't belong to the active submatrix, are missing from the * column linked lists. It is also assumed that each active row of the * matrix V is in the set R[len], where len is number of non-zeros in * the row, and each active column of the matrix V is in the set C[len], * where len is number of non-zeros in the column (in the latter case * only elements of the active submatrix are counted; such elements are * marked by '*' on the figure above). * * For the reason of numerical stability the routine applies so called * threshold pivoting proposed by J.Reid. It is assumed that an element * v[i,j] can be selected as a pivot candidate if it is not very small * (in absolute value) among other elements in the same row, i.e. if it * satisfies to the stability condition |v[i,j]| >= tol * max|v[i,*]|, * where 0 < tol < 1 is a given tolerance. * * In order to keep sparsity of the matrix V the routine uses Markowitz * strategy, trying to choose such element v[p,q], which satisfies to * the stability condition (see above) and has smallest Markowitz cost * (nr[p]-1) * (nc[q]-1), where nr[p] and nc[q] are numbers of non-zero * elements, respectively, in the p-th row and in the q-th column of the * active submatrix. * * In order to reduce the search, i.e. not to walk through all elements * of the active submatrix, the routine exploits a technique proposed by * I.Duff. This technique is based on using the sets R[len] and C[len] * of active rows and columns. * * If the pivot element v[p,q] has been chosen, the routine stores its * indices to the locations *p and *q and returns zero. Otherwise, if * the active submatrix is empty and therefore the pivot element can't * be chosen, the routine returns non-zero. */ static int find_pivot(LUF *luf, int *_p, int *_q) { int n = luf->n; int *vr_ptr = luf->vr_ptr; int *vr_len = luf->vr_len; int *vc_ptr = luf->vc_ptr; int *vc_len = luf->vc_len; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; double *vr_max = luf->vr_max; int *rs_head = luf->rs_head; int *rs_next = luf->rs_next; int *cs_head = luf->cs_head; int *cs_prev = luf->cs_prev; int *cs_next = luf->cs_next; double piv_tol = luf->piv_tol; int piv_lim = luf->piv_lim; int suhl = luf->suhl; int p, q, len, i, i_beg, i_end, i_ptr, j, j_beg, j_end, j_ptr, ncand, next_j, min_p, min_q, min_len; double best, cost, big, temp; /* initially no pivot candidates have been found so far */ p = q = 0, best = DBL_MAX, ncand = 0; /* if in the active submatrix there is a column that has the only non-zero (column singleton), choose it as pivot */ j = cs_head[1]; if (j != 0) { xassert(vc_len[j] == 1); p = sv_ind[vc_ptr[j]], q = j; goto done; } /* if in the active submatrix there is a row that has the only non-zero (row singleton), choose it as pivot */ i = rs_head[1]; if (i != 0) { xassert(vr_len[i] == 1); p = i, q = sv_ind[vr_ptr[i]]; goto done; } /* there are no singletons in the active submatrix; walk through other non-empty rows and columns */ for (len = 2; len <= n; len++) { /* consider active columns that have len non-zeros */ for (j = cs_head[len]; j != 0; j = next_j) { /* the j-th column has len non-zeros */ j_beg = vc_ptr[j]; j_end = j_beg + vc_len[j] - 1; /* save pointer to the next column with the same length */ next_j = cs_next[j]; /* find an element in the j-th column, which is placed in a row with minimal number of non-zeros and satisfies to the stability condition (such element may not exist) */ min_p = min_q = 0, min_len = INT_MAX; for (j_ptr = j_beg; j_ptr <= j_end; j_ptr++) { /* get row index of v[i,j] */ i = sv_ind[j_ptr]; i_beg = vr_ptr[i]; i_end = i_beg + vr_len[i] - 1; /* if the i-th row is not shorter than that one, where minimal element is currently placed, skip v[i,j] */ if (vr_len[i] >= min_len) continue; /* determine the largest of absolute values of elements in the i-th row */ big = vr_max[i]; if (big < 0.0) { /* the largest value is unknown yet; compute it */ for (i_ptr = i_beg; i_ptr <= i_end; i_ptr++) { temp = sv_val[i_ptr]; if (temp < 0.0) temp = - temp; if (big < temp) big = temp; } vr_max[i] = big; } /* find v[i,j] in the i-th row */ for (i_ptr = vr_ptr[i]; sv_ind[i_ptr] != j; i_ptr++); xassert(i_ptr <= i_end); /* if v[i,j] doesn't satisfy to the stability condition, skip it */ temp = sv_val[i_ptr]; if (temp < 0.0) temp = - temp; if (temp < piv_tol * big) continue; /* v[i,j] is better than the current minimal element */ min_p = i, min_q = j, min_len = vr_len[i]; /* if Markowitz cost of the current minimal element is not greater than (len-1)**2, it can be chosen right now; this heuristic reduces the search and works well in many cases */ if (min_len <= len) { p = min_p, q = min_q; goto done; } } /* the j-th column has been scanned */ if (min_p != 0) { /* the minimal element is a next pivot candidate */ ncand++; /* compute its Markowitz cost */ cost = (double)(min_len - 1) * (double)(len - 1); /* choose between the minimal element and the current candidate */ if (cost < best) p = min_p, q = min_q, best = cost; /* if piv_lim candidates have been considered, there are doubts that a much better candidate exists; therefore it's time to terminate the search */ if (ncand == piv_lim) goto done; } else { /* the j-th column has no elements, which satisfy to the stability condition; Uwe Suhl suggests to exclude such column from the further consideration until it becomes a column singleton; in hard cases this significantly reduces a time needed for pivot searching */ if (suhl) { /* remove the j-th column from the active set */ if (cs_prev[j] == 0) cs_head[len] = cs_next[j]; else cs_next[cs_prev[j]] = cs_next[j]; if (cs_next[j] == 0) /* nop */; else cs_prev[cs_next[j]] = cs_prev[j]; /* the following assignment is used to avoid an error when the routine eliminate (see below) will try to remove the j-th column from the active set */ cs_prev[j] = cs_next[j] = j; } } } /* consider active rows that have len non-zeros */ for (i = rs_head[len]; i != 0; i = rs_next[i]) { /* the i-th row has len non-zeros */ i_beg = vr_ptr[i]; i_end = i_beg + vr_len[i] - 1; /* determine the largest of absolute values of elements in the i-th row */ big = vr_max[i]; if (big < 0.0) { /* the largest value is unknown yet; compute it */ for (i_ptr = i_beg; i_ptr <= i_end; i_ptr++) { temp = sv_val[i_ptr]; if (temp < 0.0) temp = - temp; if (big < temp) big = temp; } vr_max[i] = big; } /* find an element in the i-th row, which is placed in a column with minimal number of non-zeros and satisfies to the stability condition (such element always exists) */ min_p = min_q = 0, min_len = INT_MAX; for (i_ptr = i_beg; i_ptr <= i_end; i_ptr++) { /* get column index of v[i,j] */ j = sv_ind[i_ptr]; /* if the j-th column is not shorter than that one, where minimal element is currently placed, skip v[i,j] */ if (vc_len[j] >= min_len) continue; /* if v[i,j] doesn't satisfy to the stability condition, skip it */ temp = sv_val[i_ptr]; if (temp < 0.0) temp = - temp; if (temp < piv_tol * big) continue; /* v[i,j] is better than the current minimal element */ min_p = i, min_q = j, min_len = vc_len[j]; /* if Markowitz cost of the current minimal element is not greater than (len-1)**2, it can be chosen right now; this heuristic reduces the search and works well in many cases */ if (min_len <= len) { p = min_p, q = min_q; goto done; } } /* the i-th row has been scanned */ if (min_p != 0) { /* the minimal element is a next pivot candidate */ ncand++; /* compute its Markowitz cost */ cost = (double)(len - 1) * (double)(min_len - 1); /* choose between the minimal element and the current candidate */ if (cost < best) p = min_p, q = min_q, best = cost; /* if piv_lim candidates have been considered, there are doubts that a much better candidate exists; therefore it's time to terminate the search */ if (ncand == piv_lim) goto done; } else { /* this can't be because this can never be */ xassert(min_p != min_p); } } } done: /* bring the pivot to the factorizing routine */ *_p = p, *_q = q; return (p == 0); } /*********************************************************************** * eliminate - perform gaussian elimination. * * This routine performs elementary gaussian transformations in order * to eliminate subdiagonal elements in the k-th column of the matrix * U = P*V*Q using the pivot element u[k,k], where k is the number of * the current elimination step. * * The parameters p and q are, respectively, row and column indices of * the element v[p,q], which corresponds to the element u[k,k]. * * Each time when the routine applies the elementary transformation to * a non-pivot row of the matrix V, it stores the corresponding element * to the matrix F in order to keep the main equality A = F*V. * * The routine assumes that on entry the matrices L = P*F*inv(P) and * U = P*V*Q are the following: * * 1 k 1 k n * 1 1 . . . . . . . . . 1 x x x x x x x x x x * x 1 . . . . . . . . . x x x x x x x x x * x x 1 . . . . . . . . . x x x x x x x x * x x x 1 . . . . . . . . . x x x x x x x * k x x x x 1 . . . . . k . . . . * * * * * * * x x x x _ 1 . . . . . . . . # * * * * * * x x x x _ . 1 . . . . . . . # * * * * * * x x x x _ . . 1 . . . . . . # * * * * * * x x x x _ . . . 1 . . . . . # * * * * * * n x x x x _ . . . . 1 n . . . . # * * * * * * * matrix L matrix U * * where rows and columns of the matrix U with numbers k, k+1, ..., n * form the active submatrix (eliminated elements are marked by '#' and * other elements of the active submatrix are marked by '*'). Note that * each eliminated non-zero element u[i,k] of the matrix U gives the * corresponding element l[i,k] of the matrix L (marked by '_'). * * Actually all operations are performed on the matrix V. Should note * that the row-wise representation corresponds to the matrix V, but the * column-wise representation corresponds to the active submatrix of the * matrix V, i.e. elements of the matrix V, which doesn't belong to the * active submatrix, are missing from the column linked lists. * * Let u[k,k] = v[p,q] be the pivot. In order to eliminate subdiagonal * elements u[i',k] = v[i,q], i' = k+1, k+2, ..., n, the routine applies * the following elementary gaussian transformations: * * (i-th row of V) := (i-th row of V) - f[i,p] * (p-th row of V), * * where f[i,p] = v[i,q] / v[p,q] is a gaussian multiplier. * * Additionally, in order to keep the main equality A = F*V, each time * when the routine applies the transformation to i-th row of the matrix * V, it also adds f[i,p] as a new element to the matrix F. * * IMPORTANT: On entry the working arrays flag and work should contain * zeros. This status is provided by the routine on exit. * * If no error occured, the routine returns zero. Otherwise, in case of * overflow of the sparse vector area, the routine returns non-zero. */ static int eliminate(LUF *luf, int p, int q) { int n = luf->n; int *fc_ptr = luf->fc_ptr; int *fc_len = luf->fc_len; int *vr_ptr = luf->vr_ptr; int *vr_len = luf->vr_len; int *vr_cap = luf->vr_cap; double *vr_piv = luf->vr_piv; int *vc_ptr = luf->vc_ptr; int *vc_len = luf->vc_len; int *vc_cap = luf->vc_cap; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; int *sv_prev = luf->sv_prev; int *sv_next = luf->sv_next; double *vr_max = luf->vr_max; int *rs_head = luf->rs_head; int *rs_prev = luf->rs_prev; int *rs_next = luf->rs_next; int *cs_head = luf->cs_head; int *cs_prev = luf->cs_prev; int *cs_next = luf->cs_next; int *flag = luf->flag; double *work = luf->work; double eps_tol = luf->eps_tol; /* at this stage the row-wise representation of the matrix F is not used, so fr_len can be used as a working array */ int *ndx = luf->fr_len; int ret = 0; int len, fill, i, i_beg, i_end, i_ptr, j, j_beg, j_end, j_ptr, k, p_beg, p_end, p_ptr, q_beg, q_end, q_ptr; double fip, val, vpq, temp; xassert(1 <= p && p <= n); xassert(1 <= q && q <= n); /* remove the p-th (pivot) row from the active set; this row will never return there */ if (rs_prev[p] == 0) rs_head[vr_len[p]] = rs_next[p]; else rs_next[rs_prev[p]] = rs_next[p]; if (rs_next[p] == 0) ; else rs_prev[rs_next[p]] = rs_prev[p]; /* remove the q-th (pivot) column from the active set; this column will never return there */ if (cs_prev[q] == 0) cs_head[vc_len[q]] = cs_next[q]; else cs_next[cs_prev[q]] = cs_next[q]; if (cs_next[q] == 0) ; else cs_prev[cs_next[q]] = cs_prev[q]; /* find the pivot v[p,q] = u[k,k] in the p-th row */ p_beg = vr_ptr[p]; p_end = p_beg + vr_len[p] - 1; for (p_ptr = p_beg; sv_ind[p_ptr] != q; p_ptr++) /* nop */; xassert(p_ptr <= p_end); /* store value of the pivot */ vpq = (vr_piv[p] = sv_val[p_ptr]); /* remove the pivot from the p-th row */ sv_ind[p_ptr] = sv_ind[p_end]; sv_val[p_ptr] = sv_val[p_end]; vr_len[p]--; p_end--; /* find the pivot v[p,q] = u[k,k] in the q-th column */ q_beg = vc_ptr[q]; q_end = q_beg + vc_len[q] - 1; for (q_ptr = q_beg; sv_ind[q_ptr] != p; q_ptr++) /* nop */; xassert(q_ptr <= q_end); /* remove the pivot from the q-th column */ sv_ind[q_ptr] = sv_ind[q_end]; vc_len[q]--; q_end--; /* walk through the p-th (pivot) row, which doesn't contain the pivot v[p,q] already, and do the following... */ for (p_ptr = p_beg; p_ptr <= p_end; p_ptr++) { /* get column index of v[p,j] */ j = sv_ind[p_ptr]; /* store v[p,j] to the working array */ flag[j] = 1; work[j] = sv_val[p_ptr]; /* remove the j-th column from the active set; this column will return there later with new length */ if (cs_prev[j] == 0) cs_head[vc_len[j]] = cs_next[j]; else cs_next[cs_prev[j]] = cs_next[j]; if (cs_next[j] == 0) ; else cs_prev[cs_next[j]] = cs_prev[j]; /* find v[p,j] in the j-th column */ j_beg = vc_ptr[j]; j_end = j_beg + vc_len[j] - 1; for (j_ptr = j_beg; sv_ind[j_ptr] != p; j_ptr++) /* nop */; xassert(j_ptr <= j_end); /* since v[p,j] leaves the active submatrix, remove it from the j-th column; however, v[p,j] is kept in the p-th row */ sv_ind[j_ptr] = sv_ind[j_end]; vc_len[j]--; } /* walk through the q-th (pivot) column, which doesn't contain the pivot v[p,q] already, and perform gaussian elimination */ while (q_beg <= q_end) { /* element v[i,q] should be eliminated */ /* get row index of v[i,q] */ i = sv_ind[q_beg]; /* remove the i-th row from the active set; later this row will return there with new length */ if (rs_prev[i] == 0) rs_head[vr_len[i]] = rs_next[i]; else rs_next[rs_prev[i]] = rs_next[i]; if (rs_next[i] == 0) ; else rs_prev[rs_next[i]] = rs_prev[i]; /* find v[i,q] in the i-th row */ i_beg = vr_ptr[i]; i_end = i_beg + vr_len[i] - 1; for (i_ptr = i_beg; sv_ind[i_ptr] != q; i_ptr++) /* nop */; xassert(i_ptr <= i_end); /* compute gaussian multiplier f[i,p] = v[i,q] / v[p,q] */ fip = sv_val[i_ptr] / vpq; /* since v[i,q] should be eliminated, remove it from the i-th row */ sv_ind[i_ptr] = sv_ind[i_end]; sv_val[i_ptr] = sv_val[i_end]; vr_len[i]--; i_end--; /* and from the q-th column */ sv_ind[q_beg] = sv_ind[q_end]; vc_len[q]--; q_end--; /* perform gaussian transformation: (i-th row) := (i-th row) - f[i,p] * (p-th row) note that now the p-th row, which is in the working array, doesn't contain the pivot v[p,q], and the i-th row doesn't contain the eliminated element v[i,q] */ /* walk through the i-th row and transform existing non-zero elements */ fill = vr_len[p]; for (i_ptr = i_beg; i_ptr <= i_end; i_ptr++) { /* get column index of v[i,j] */ j = sv_ind[i_ptr]; /* v[i,j] := v[i,j] - f[i,p] * v[p,j] */ if (flag[j]) { /* v[p,j] != 0 */ temp = (sv_val[i_ptr] -= fip * work[j]); if (temp < 0.0) temp = - temp; flag[j] = 0; fill--; /* since both v[i,j] and v[p,j] exist */ if (temp == 0.0 || temp < eps_tol) { /* new v[i,j] is closer to zero; replace it by exact zero, i.e. remove it from the active submatrix */ /* remove v[i,j] from the i-th row */ sv_ind[i_ptr] = sv_ind[i_end]; sv_val[i_ptr] = sv_val[i_end]; vr_len[i]--; i_ptr--; i_end--; /* find v[i,j] in the j-th column */ j_beg = vc_ptr[j]; j_end = j_beg + vc_len[j] - 1; for (j_ptr = j_beg; sv_ind[j_ptr] != i; j_ptr++); xassert(j_ptr <= j_end); /* remove v[i,j] from the j-th column */ sv_ind[j_ptr] = sv_ind[j_end]; vc_len[j]--; } else { /* v_big := max(v_big, |v[i,j]|) */ if (luf->big_v < temp) luf->big_v = temp; } } } /* now flag is the pattern of the set v[p,*] \ v[i,*], and fill is number of non-zeros in this set; therefore up to fill new non-zeros may appear in the i-th row */ if (vr_len[i] + fill > vr_cap[i]) { /* enlarge the i-th row */ if (luf_enlarge_row(luf, i, vr_len[i] + fill)) { /* overflow of the sparse vector area */ ret = 1; goto done; } /* defragmentation may change row and column pointers of the matrix V */ p_beg = vr_ptr[p]; p_end = p_beg + vr_len[p] - 1; q_beg = vc_ptr[q]; q_end = q_beg + vc_len[q] - 1; } /* walk through the p-th (pivot) row and create new elements of the i-th row that appear due to fill-in; column indices of these new elements are accumulated in the array ndx */ len = 0; for (p_ptr = p_beg; p_ptr <= p_end; p_ptr++) { /* get column index of v[p,j], which may cause fill-in */ j = sv_ind[p_ptr]; if (flag[j]) { /* compute new non-zero v[i,j] = 0 - f[i,p] * v[p,j] */ temp = (val = - fip * work[j]); if (temp < 0.0) temp = - temp; if (temp == 0.0 || temp < eps_tol) /* if v[i,j] is closer to zero; just ignore it */; else { /* add v[i,j] to the i-th row */ i_ptr = vr_ptr[i] + vr_len[i]; sv_ind[i_ptr] = j; sv_val[i_ptr] = val; vr_len[i]++; /* remember column index of v[i,j] */ ndx[++len] = j; /* big_v := max(big_v, |v[i,j]|) */ if (luf->big_v < temp) luf->big_v = temp; } } else { /* there is no fill-in, because v[i,j] already exists in the i-th row; restore the flag of the element v[p,j], which was reset before */ flag[j] = 1; } } /* add new non-zeros v[i,j] to the corresponding columns */ for (k = 1; k <= len; k++) { /* get column index of new non-zero v[i,j] */ j = ndx[k]; /* one free location is needed in the j-th column */ if (vc_len[j] + 1 > vc_cap[j]) { /* enlarge the j-th column */ if (luf_enlarge_col(luf, j, vc_len[j] + 10)) { /* overflow of the sparse vector area */ ret = 1; goto done; } /* defragmentation may change row and column pointers of the matrix V */ p_beg = vr_ptr[p]; p_end = p_beg + vr_len[p] - 1; q_beg = vc_ptr[q]; q_end = q_beg + vc_len[q] - 1; } /* add new non-zero v[i,j] to the j-th column */ j_ptr = vc_ptr[j] + vc_len[j]; sv_ind[j_ptr] = i; vc_len[j]++; } /* now the i-th row has been completely transformed, therefore it can return to the active set with new length */ rs_prev[i] = 0; rs_next[i] = rs_head[vr_len[i]]; if (rs_next[i] != 0) rs_prev[rs_next[i]] = i; rs_head[vr_len[i]] = i; /* the largest of absolute values of elements in the i-th row is currently unknown */ vr_max[i] = -1.0; /* at least one free location is needed to store the gaussian multiplier */ if (luf->sv_end - luf->sv_beg < 1) { /* there are no free locations at all; defragment SVA */ luf_defrag_sva(luf); if (luf->sv_end - luf->sv_beg < 1) { /* overflow of the sparse vector area */ ret = 1; goto done; } /* defragmentation may change row and column pointers of the matrix V */ p_beg = vr_ptr[p]; p_end = p_beg + vr_len[p] - 1; q_beg = vc_ptr[q]; q_end = q_beg + vc_len[q] - 1; } /* add the element f[i,p], which is the gaussian multiplier, to the matrix F */ luf->sv_end--; sv_ind[luf->sv_end] = i; sv_val[luf->sv_end] = fip; fc_len[p]++; /* end of elimination loop */ } /* at this point the q-th (pivot) column should be empty */ xassert(vc_len[q] == 0); /* reset capacity of the q-th column */ vc_cap[q] = 0; /* remove node of the q-th column from the addressing list */ k = n + q; if (sv_prev[k] == 0) luf->sv_head = sv_next[k]; else sv_next[sv_prev[k]] = sv_next[k]; if (sv_next[k] == 0) luf->sv_tail = sv_prev[k]; else sv_prev[sv_next[k]] = sv_prev[k]; /* the p-th column of the matrix F has been completely built; set its pointer */ fc_ptr[p] = luf->sv_end; /* walk through the p-th (pivot) row and do the following... */ for (p_ptr = p_beg; p_ptr <= p_end; p_ptr++) { /* get column index of v[p,j] */ j = sv_ind[p_ptr]; /* erase v[p,j] from the working array */ flag[j] = 0; work[j] = 0.0; /* the j-th column has been completely transformed, therefore it can return to the active set with new length; however the special case c_prev[j] = c_next[j] = j means that the routine find_pivot excluded the j-th column from the active set due to Uwe Suhl's rule, and therefore in this case the column can return to the active set only if it is a column singleton */ if (!(vc_len[j] != 1 && cs_prev[j] == j && cs_next[j] == j)) { cs_prev[j] = 0; cs_next[j] = cs_head[vc_len[j]]; if (cs_next[j] != 0) cs_prev[cs_next[j]] = j; cs_head[vc_len[j]] = j; } } done: /* return to the factorizing routine */ return ret; } /*********************************************************************** * build_v_cols - build the matrix V in column-wise format * * This routine builds the column-wise representation of the matrix V * using its row-wise representation. * * If no error occured, the routine returns zero. Otherwise, in case of * overflow of the sparse vector area, the routine returns non-zero. */ static int build_v_cols(LUF *luf) { int n = luf->n; int *vr_ptr = luf->vr_ptr; int *vr_len = luf->vr_len; int *vc_ptr = luf->vc_ptr; int *vc_len = luf->vc_len; int *vc_cap = luf->vc_cap; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; int *sv_prev = luf->sv_prev; int *sv_next = luf->sv_next; int ret = 0; int i, i_beg, i_end, i_ptr, j, j_ptr, k, nnz; /* it is assumed that on entry all columns of the matrix V are empty, i.e. vc_len[j] = vc_cap[j] = 0 for all j = 1, ..., n, and have been removed from the addressing list */ /* count non-zeros in columns of the matrix V; count total number of non-zeros in this matrix */ nnz = 0; for (i = 1; i <= n; i++) { /* walk through elements of the i-th row and count non-zeros in the corresponding columns */ i_beg = vr_ptr[i]; i_end = i_beg + vr_len[i] - 1; for (i_ptr = i_beg; i_ptr <= i_end; i_ptr++) vc_cap[sv_ind[i_ptr]]++; /* count total number of non-zeros */ nnz += vr_len[i]; } /* store total number of non-zeros */ luf->nnz_v = nnz; /* check for free locations */ if (luf->sv_end - luf->sv_beg < nnz) { /* overflow of the sparse vector area */ ret = 1; goto done; } /* allocate columns of the matrix V */ for (j = 1; j <= n; j++) { /* set pointer to the j-th column */ vc_ptr[j] = luf->sv_beg; /* reserve locations for the j-th column */ luf->sv_beg += vc_cap[j]; } /* build the matrix V in column-wise format using this matrix in row-wise format */ for (i = 1; i <= n; i++) { /* walk through elements of the i-th row */ i_beg = vr_ptr[i]; i_end = i_beg + vr_len[i] - 1; for (i_ptr = i_beg; i_ptr <= i_end; i_ptr++) { /* get column index */ j = sv_ind[i_ptr]; /* store element in the j-th column */ j_ptr = vc_ptr[j] + vc_len[j]; sv_ind[j_ptr] = i; sv_val[j_ptr] = sv_val[i_ptr]; /* increase length of the j-th column */ vc_len[j]++; } } /* now columns are placed in the sparse vector area behind rows in the order n+1, n+2, ..., n+n; so insert column nodes in the addressing list using this order */ for (k = n+1; k <= n+n; k++) { sv_prev[k] = k-1; sv_next[k] = k+1; } sv_prev[n+1] = luf->sv_tail; sv_next[luf->sv_tail] = n+1; sv_next[n+n] = 0; luf->sv_tail = n+n; done: /* return to the factorizing routine */ return ret; } /*********************************************************************** * build_f_rows - build the matrix F in row-wise format * * This routine builds the row-wise representation of the matrix F using * its column-wise representation. * * If no error occured, the routine returns zero. Otherwise, in case of * overflow of the sparse vector area, the routine returns non-zero. */ static int build_f_rows(LUF *luf) { int n = luf->n; int *fr_ptr = luf->fr_ptr; int *fr_len = luf->fr_len; int *fc_ptr = luf->fc_ptr; int *fc_len = luf->fc_len; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; int ret = 0; int i, j, j_beg, j_end, j_ptr, ptr, nnz; /* clear rows of the matrix F */ for (i = 1; i <= n; i++) fr_len[i] = 0; /* count non-zeros in rows of the matrix F; count total number of non-zeros in this matrix */ nnz = 0; for (j = 1; j <= n; j++) { /* walk through elements of the j-th column and count non-zeros in the corresponding rows */ j_beg = fc_ptr[j]; j_end = j_beg + fc_len[j] - 1; for (j_ptr = j_beg; j_ptr <= j_end; j_ptr++) fr_len[sv_ind[j_ptr]]++; /* increase total number of non-zeros */ nnz += fc_len[j]; } /* store total number of non-zeros */ luf->nnz_f = nnz; /* check for free locations */ if (luf->sv_end - luf->sv_beg < nnz) { /* overflow of the sparse vector area */ ret = 1; goto done; } /* allocate rows of the matrix F */ for (i = 1; i <= n; i++) { /* set pointer to the end of the i-th row; later this pointer will be set to the beginning of the i-th row */ fr_ptr[i] = luf->sv_end; /* reserve locations for the i-th row */ luf->sv_end -= fr_len[i]; } /* build the matrix F in row-wise format using this matrix in column-wise format */ for (j = 1; j <= n; j++) { /* walk through elements of the j-th column */ j_beg = fc_ptr[j]; j_end = j_beg + fc_len[j] - 1; for (j_ptr = j_beg; j_ptr <= j_end; j_ptr++) { /* get row index */ i = sv_ind[j_ptr]; /* store element in the i-th row */ ptr = --fr_ptr[i]; sv_ind[ptr] = j; sv_val[ptr] = sv_val[j_ptr]; } } done: /* return to the factorizing routine */ return ret; } /*********************************************************************** * NAME * * luf_factorize - compute LU-factorization * * SYNOPSIS * * #include "glpluf.h" * int luf_factorize(LUF *luf, int n, int (*col)(void *info, int j, * int ind[], double val[]), void *info); * * DESCRIPTION * * The routine luf_factorize computes LU-factorization of a specified * square matrix A. * * The parameter luf specifies LU-factorization program object created * by the routine luf_create_it. * * The parameter n specifies the order of A, n > 0. * * The formal routine col specifies the matrix A to be factorized. To * obtain j-th column of A the routine luf_factorize calls the routine * col with the parameter j (1 <= j <= n). In response the routine col * should store row indices and numerical values of non-zero elements * of j-th column of A to locations ind[1,...,len] and val[1,...,len], * respectively, where len is the number of non-zeros in j-th column * returned on exit. Neither zero nor duplicate elements are allowed. * * The parameter info is a transit pointer passed to the routine col. * * RETURNS * * 0 LU-factorization has been successfully computed. * * LUF_ESING * The specified matrix is singular within the working precision. * (On some elimination step the active submatrix is exactly zero, * so no pivot can be chosen.) * * LUF_ECOND * The specified matrix is ill-conditioned. * (On some elimination step too intensive growth of elements of the * active submatix has been detected.) * * If matrix A is well scaled, the return code LUF_ECOND may also mean * that the threshold pivoting tolerance piv_tol should be increased. * * In case of non-zero return code the factorization becomes invalid. * It should not be used in other operations until the cause of failure * has been eliminated and the factorization has been recomputed again * with the routine luf_factorize. * * REPAIRING SINGULAR MATRIX * * If the routine luf_factorize returns non-zero code, it provides all * necessary information that can be used for "repairing" the matrix A, * where "repairing" means replacing linearly dependent columns of the * matrix A by appropriate columns of the unity matrix. This feature is * needed when this routine is used for factorizing the basis matrix * within the simplex method procedure. * * On exit linearly dependent columns of the (partially transformed) * matrix U have numbers rank+1, rank+2, ..., n, where rank is estimated * rank of the matrix A stored by the routine to the member luf->rank. * The correspondence between columns of A and U is the same as between * columns of V and U. Thus, linearly dependent columns of the matrix A * have numbers qq_col[rank+1], qq_col[rank+2], ..., qq_col[n], where * qq_col is the column-like representation of the permutation matrix Q. * It is understood that each j-th linearly dependent column of the * matrix U should be replaced by the unity vector, where all elements * are zero except the unity diagonal element u[j,j]. On the other hand * j-th row of the matrix U corresponds to the row of the matrix V (and * therefore of the matrix A) with the number pp_row[j], where pp_row is * the row-like representation of the permutation matrix P. Thus, each * j-th linearly dependent column of the matrix U should be replaced by * column of the unity matrix with the number pp_row[j]. * * The code that repairs the matrix A may look like follows: * * for (j = rank+1; j <= n; j++) * { replace the column qq_col[j] of the matrix A by the column * pp_row[j] of the unity matrix; * } * * where rank, pp_row, and qq_col are members of the structure LUF. */ int luf_factorize(LUF *luf, int n, int (*col)(void *info, int j, int ind[], double val[]), void *info) { int *pp_row, *pp_col, *qq_row, *qq_col; double max_gro = luf->max_gro; int i, j, k, p, q, t, ret; if (n < 1) xfault("luf_factorize: n = %d; invalid parameter\n", n); if (n > N_MAX) xfault("luf_factorize: n = %d; matrix too big\n", n); /* invalidate the factorization */ luf->valid = 0; /* reallocate arrays, if necessary */ reallocate(luf, n); pp_row = luf->pp_row; pp_col = luf->pp_col; qq_row = luf->qq_row; qq_col = luf->qq_col; /* estimate initial size of the SVA, if not specified */ if (luf->sv_size == 0 && luf->new_sva == 0) luf->new_sva = 5 * (n + 10); more: /* reallocate the sparse vector area, if required */ if (luf->new_sva > 0) { if (luf->sv_ind != NULL) xfree(luf->sv_ind); if (luf->sv_val != NULL) xfree(luf->sv_val); luf->sv_size = luf->new_sva; luf->sv_ind = xcalloc(1+luf->sv_size, sizeof(int)); luf->sv_val = xcalloc(1+luf->sv_size, sizeof(double)); luf->new_sva = 0; } /* initialize LU-factorization data structures */ if (initialize(luf, col, info)) { /* overflow of the sparse vector area */ luf->new_sva = luf->sv_size + luf->sv_size; xassert(luf->new_sva > luf->sv_size); goto more; } /* main elimination loop */ for (k = 1; k <= n; k++) { /* choose a pivot element v[p,q] */ if (find_pivot(luf, &p, &q)) { /* no pivot can be chosen, because the active submatrix is exactly zero */ luf->rank = k - 1; ret = LUF_ESING; goto done; } /* let v[p,q] correspond to u[i',j']; permute k-th and i'-th rows and k-th and j'-th columns of the matrix U = P*V*Q to move the element u[i',j'] to the position u[k,k] */ i = pp_col[p], j = qq_row[q]; xassert(k <= i && i <= n && k <= j && j <= n); /* permute k-th and i-th rows of the matrix U */ t = pp_row[k]; pp_row[i] = t, pp_col[t] = i; pp_row[k] = p, pp_col[p] = k; /* permute k-th and j-th columns of the matrix U */ t = qq_col[k]; qq_col[j] = t, qq_row[t] = j; qq_col[k] = q, qq_row[q] = k; /* eliminate subdiagonal elements of k-th column of the matrix U = P*V*Q using the pivot element u[k,k] = v[p,q] */ if (eliminate(luf, p, q)) { /* overflow of the sparse vector area */ luf->new_sva = luf->sv_size + luf->sv_size; xassert(luf->new_sva > luf->sv_size); goto more; } /* check relative growth of elements of the matrix V */ if (luf->big_v > max_gro * luf->max_a) { /* the growth is too intensive, therefore most probably the matrix A is ill-conditioned */ luf->rank = k - 1; ret = LUF_ECOND; goto done; } } /* now the matrix U = P*V*Q is upper triangular, the matrix V has been built in row-wise format, and the matrix F has been built in column-wise format */ /* defragment the sparse vector area in order to merge all free locations in one continuous extent */ luf_defrag_sva(luf); /* build the matrix V in column-wise format */ if (build_v_cols(luf)) { /* overflow of the sparse vector area */ luf->new_sva = luf->sv_size + luf->sv_size; xassert(luf->new_sva > luf->sv_size); goto more; } /* build the matrix F in row-wise format */ if (build_f_rows(luf)) { /* overflow of the sparse vector area */ luf->new_sva = luf->sv_size + luf->sv_size; xassert(luf->new_sva > luf->sv_size); goto more; } /* the LU-factorization has been successfully computed */ luf->valid = 1; luf->rank = n; ret = 0; /* if there are few free locations in the sparse vector area, try increasing its size in the future */ t = 3 * (n + luf->nnz_v) + 2 * luf->nnz_f; if (luf->sv_size < t) { luf->new_sva = luf->sv_size; while (luf->new_sva < t) { k = luf->new_sva; luf->new_sva = k + k; xassert(luf->new_sva > k); } } done: /* return to the calling program */ return ret; } /*********************************************************************** * NAME * * luf_f_solve - solve system F*x = b or F'*x = b * * SYNOPSIS * * #include "glpluf.h" * void luf_f_solve(LUF *luf, int tr, double x[]); * * DESCRIPTION * * The routine luf_f_solve solves either the system F*x = b (if the * flag tr is zero) or the system F'*x = b (if the flag tr is non-zero), * where the matrix F is a component of LU-factorization specified by * the parameter luf, F' is a matrix transposed to F. * * On entry the array x should contain elements of the right-hand side * vector b in locations x[1], ..., x[n], where n is the order of the * matrix F. On exit this array will contain elements of the solution * vector x in the same locations. */ void luf_f_solve(LUF *luf, int tr, double x[]) { int n = luf->n; int *fr_ptr = luf->fr_ptr; int *fr_len = luf->fr_len; int *fc_ptr = luf->fc_ptr; int *fc_len = luf->fc_len; int *pp_row = luf->pp_row; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; int i, j, k, beg, end, ptr; double xk; if (!luf->valid) xfault("luf_f_solve: LU-factorization is not valid\n"); if (!tr) { /* solve the system F*x = b */ for (j = 1; j <= n; j++) { k = pp_row[j]; xk = x[k]; if (xk != 0.0) { beg = fc_ptr[k]; end = beg + fc_len[k] - 1; for (ptr = beg; ptr <= end; ptr++) x[sv_ind[ptr]] -= sv_val[ptr] * xk; } } } else { /* solve the system F'*x = b */ for (i = n; i >= 1; i--) { k = pp_row[i]; xk = x[k]; if (xk != 0.0) { beg = fr_ptr[k]; end = beg + fr_len[k] - 1; for (ptr = beg; ptr <= end; ptr++) x[sv_ind[ptr]] -= sv_val[ptr] * xk; } } } return; } /*********************************************************************** * NAME * * luf_v_solve - solve system V*x = b or V'*x = b * * SYNOPSIS * * #include "glpluf.h" * void luf_v_solve(LUF *luf, int tr, double x[]); * * DESCRIPTION * * The routine luf_v_solve solves either the system V*x = b (if the * flag tr is zero) or the system V'*x = b (if the flag tr is non-zero), * where the matrix V is a component of LU-factorization specified by * the parameter luf, V' is a matrix transposed to V. * * On entry the array x should contain elements of the right-hand side * vector b in locations x[1], ..., x[n], where n is the order of the * matrix V. On exit this array will contain elements of the solution * vector x in the same locations. */ void luf_v_solve(LUF *luf, int tr, double x[]) { int n = luf->n; int *vr_ptr = luf->vr_ptr; int *vr_len = luf->vr_len; double *vr_piv = luf->vr_piv; int *vc_ptr = luf->vc_ptr; int *vc_len = luf->vc_len; int *pp_row = luf->pp_row; int *qq_col = luf->qq_col; int *sv_ind = luf->sv_ind; double *sv_val = luf->sv_val; double *b = luf->work; int i, j, k, beg, end, ptr; double temp; if (!luf->valid) xfault("luf_v_solve: LU-factorization is not valid\n"); for (k = 1; k <= n; k++) b[k] = x[k], x[k] = 0.0; if (!tr) { /* solve the system V*x = b */ for (k = n; k >= 1; k--) { i = pp_row[k], j = qq_col[k]; temp = b[i]; if (temp != 0.0) { x[j] = (temp /= vr_piv[i]); beg = vc_ptr[j]; end = beg + vc_len[j] - 1; for (ptr = beg; ptr <= end; ptr++) b[sv_ind[ptr]] -= sv_val[ptr] * temp; } } } else { /* solve the system V'*x = b */ for (k = 1; k <= n; k++) { i = pp_row[k], j = qq_col[k]; temp = b[j]; if (temp != 0.0) { x[i] = (temp /= vr_piv[i]); beg = vr_ptr[i]; end = beg + vr_len[i] - 1; for (ptr = beg; ptr <= end; ptr++) b[sv_ind[ptr]] -= sv_val[ptr] * temp; } } } return; } /*********************************************************************** * NAME * * luf_a_solve - solve system A*x = b or A'*x = b * * SYNOPSIS * * #include "glpluf.h" * void luf_a_solve(LUF *luf, int tr, double x[]); * * DESCRIPTION * * The routine luf_a_solve solves either the system A*x = b (if the * flag tr is zero) or the system A'*x = b (if the flag tr is non-zero), * where the parameter luf specifies LU-factorization of the matrix A, * A' is a matrix transposed to A. * * On entry the array x should contain elements of the right-hand side * vector b in locations x[1], ..., x[n], where n is the order of the * matrix A. On exit this array will contain elements of the solution * vector x in the same locations. */ void luf_a_solve(LUF *luf, int tr, double x[]) { if (!luf->valid) xfault("luf_a_solve: LU-factorization is not valid\n"); if (!tr) { /* A = F*V, therefore inv(A) = inv(V)*inv(F) */ luf_f_solve(luf, 0, x); luf_v_solve(luf, 0, x); } else { /* A' = V'*F', therefore inv(A') = inv(F')*inv(V') */ luf_v_solve(luf, 1, x); luf_f_solve(luf, 1, x); } return; } /*********************************************************************** * NAME * * luf_delete_it - delete LU-factorization * * SYNOPSIS * * #include "glpluf.h" * void luf_delete_it(LUF *luf); * * DESCRIPTION * * The routine luf_delete deletes LU-factorization specified by the * parameter luf and frees all the memory allocated to this program * object. */ void luf_delete_it(LUF *luf) { if (luf->fr_ptr != NULL) xfree(luf->fr_ptr); if (luf->fr_len != NULL) xfree(luf->fr_len); if (luf->fc_ptr != NULL) xfree(luf->fc_ptr); if (luf->fc_len != NULL) xfree(luf->fc_len); if (luf->vr_ptr != NULL) xfree(luf->vr_ptr); if (luf->vr_len != NULL) xfree(luf->vr_len); if (luf->vr_cap != NULL) xfree(luf->vr_cap); if (luf->vr_piv != NULL) xfree(luf->vr_piv); if (luf->vc_ptr != NULL) xfree(luf->vc_ptr); if (luf->vc_len != NULL) xfree(luf->vc_len); if (luf->vc_cap != NULL) xfree(luf->vc_cap); if (luf->pp_row != NULL) xfree(luf->pp_row); if (luf->pp_col != NULL) xfree(luf->pp_col); if (luf->qq_row != NULL) xfree(luf->qq_row); if (luf->qq_col != NULL) xfree(luf->qq_col); if (luf->sv_ind != NULL) xfree(luf->sv_ind); if (luf->sv_val != NULL) xfree(luf->sv_val); if (luf->sv_prev != NULL) xfree(luf->sv_prev); if (luf->sv_next != NULL) xfree(luf->sv_next); if (luf->vr_max != NULL) xfree(luf->vr_max); if (luf->rs_head != NULL) xfree(luf->rs_head); if (luf->rs_prev != NULL) xfree(luf->rs_prev); if (luf->rs_next != NULL) xfree(luf->rs_next); if (luf->cs_head != NULL) xfree(luf->cs_head); if (luf->cs_prev != NULL) xfree(luf->cs_prev); if (luf->cs_next != NULL) xfree(luf->cs_next); if (luf->flag != NULL) xfree(luf->flag); if (luf->work != NULL) xfree(luf->work); xfree(luf); return; } /* eof */ sources_5316/external/glpk/amd_postorder.c0000644000176700017670000001543111401660400017504 0ustar paulpaul/* ========================================================================= */ /* === AMD_postorder ======================================================= */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* Perform a postordering (via depth-first search) of an assembly tree. */ #include "amd_internal.h" GLOBAL void AMD_postorder ( /* inputs, not modified on output: */ Int nn, /* nodes are in the range 0..nn-1 */ Int Parent [ ], /* Parent [j] is the parent of j, or EMPTY if root */ Int Nv [ ], /* Nv [j] > 0 number of pivots represented by node j, * or zero if j is not a node. */ Int Fsize [ ], /* Fsize [j]: size of node j */ /* output, not defined on input: */ Int Order [ ], /* output post-order */ /* workspaces of size nn: */ Int Child [ ], Int Sibling [ ], Int Stack [ ] ) { Int i, j, k, parent, frsize, f, fprev, maxfrsize, bigfprev, bigf, fnext ; for (j = 0 ; j < nn ; j++) { Child [j] = EMPTY ; Sibling [j] = EMPTY ; } /* --------------------------------------------------------------------- */ /* place the children in link lists - bigger elements tend to be last */ /* --------------------------------------------------------------------- */ for (j = nn-1 ; j >= 0 ; j--) { if (Nv [j] > 0) { /* this is an element */ parent = Parent [j] ; if (parent != EMPTY) { /* place the element in link list of the children its parent */ /* bigger elements will tend to be at the end of the list */ Sibling [j] = Child [parent] ; Child [parent] = j ; } } } #ifndef NDEBUG { Int nels, ff, nchild ; AMD_DEBUG1 (("\n\n================================ AMD_postorder:\n")); nels = 0 ; for (j = 0 ; j < nn ; j++) { if (Nv [j] > 0) { AMD_DEBUG1 (( ""ID" : nels "ID" npiv "ID" size "ID " parent "ID" maxfr "ID"\n", j, nels, Nv [j], Fsize [j], Parent [j], Fsize [j])) ; /* this is an element */ /* dump the link list of children */ nchild = 0 ; AMD_DEBUG1 ((" Children: ")) ; for (ff = Child [j] ; ff != EMPTY ; ff = Sibling [ff]) { AMD_DEBUG1 ((ID" ", ff)) ; ASSERT (Parent [ff] == j) ; nchild++ ; ASSERT (nchild < nn) ; } AMD_DEBUG1 (("\n")) ; parent = Parent [j] ; if (parent != EMPTY) { ASSERT (Nv [parent] > 0) ; } nels++ ; } } } AMD_DEBUG1 (("\n\nGo through the children of each node, and put\n" "the biggest child last in each list:\n")) ; #endif /* --------------------------------------------------------------------- */ /* place the largest child last in the list of children for each node */ /* --------------------------------------------------------------------- */ for (i = 0 ; i < nn ; i++) { if (Nv [i] > 0 && Child [i] != EMPTY) { #ifndef NDEBUG Int nchild ; AMD_DEBUG1 (("Before partial sort, element "ID"\n", i)) ; nchild = 0 ; for (f = Child [i] ; f != EMPTY ; f = Sibling [f]) { ASSERT (f >= 0 && f < nn) ; AMD_DEBUG1 ((" f: "ID" size: "ID"\n", f, Fsize [f])) ; nchild++ ; ASSERT (nchild <= nn) ; } #endif /* find the biggest element in the child list */ fprev = EMPTY ; maxfrsize = EMPTY ; bigfprev = EMPTY ; bigf = EMPTY ; for (f = Child [i] ; f != EMPTY ; f = Sibling [f]) { ASSERT (f >= 0 && f < nn) ; frsize = Fsize [f] ; if (frsize >= maxfrsize) { /* this is the biggest seen so far */ maxfrsize = frsize ; bigfprev = fprev ; bigf = f ; } fprev = f ; } ASSERT (bigf != EMPTY) ; fnext = Sibling [bigf] ; AMD_DEBUG1 (("bigf "ID" maxfrsize "ID" bigfprev "ID" fnext "ID " fprev " ID"\n", bigf, maxfrsize, bigfprev, fnext, fprev)) ; if (fnext != EMPTY) { /* if fnext is EMPTY then bigf is already at the end of list */ if (bigfprev == EMPTY) { /* delete bigf from the element of the list */ Child [i] = fnext ; } else { /* delete bigf from the middle of the list */ Sibling [bigfprev] = fnext ; } /* put bigf at the end of the list */ Sibling [bigf] = EMPTY ; ASSERT (Child [i] != EMPTY) ; ASSERT (fprev != bigf) ; ASSERT (fprev != EMPTY) ; Sibling [fprev] = bigf ; } #ifndef NDEBUG AMD_DEBUG1 (("After partial sort, element "ID"\n", i)) ; for (f = Child [i] ; f != EMPTY ; f = Sibling [f]) { ASSERT (f >= 0 && f < nn) ; AMD_DEBUG1 ((" "ID" "ID"\n", f, Fsize [f])) ; ASSERT (Nv [f] > 0) ; nchild-- ; } ASSERT (nchild == 0) ; #endif } } /* --------------------------------------------------------------------- */ /* postorder the assembly tree */ /* --------------------------------------------------------------------- */ for (i = 0 ; i < nn ; i++) { Order [i] = EMPTY ; } k = 0 ; for (i = 0 ; i < nn ; i++) { if (Parent [i] == EMPTY && Nv [i] > 0) { AMD_DEBUG1 (("Root of assembly tree "ID"\n", i)) ; k = AMD_post_tree (i, k, Child, Sibling, Order, Stack #ifndef NDEBUG , nn #endif ) ; } } } sources_5316/external/glpk/glplux.h0000644000176700017670000002122211401660400016155 0ustar paulpaul/* glplux.h (LU-factorization, bignum arithmetic) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPLUX_H #define GLPLUX_H #include "glpdmp.h" #include "glpgmp.h" /*---------------------------------------------------------------------- // The structure LUX defines LU-factorization of a square matrix A, // which is the following quartet: // // [A] = (F, V, P, Q), (1) // // where F and V are such matrices that // // A = F * V, (2) // // and P and Q are such permutation matrices that the matrix // // L = P * F * inv(P) (3) // // is lower triangular with unity diagonal, and the matrix // // U = P * V * Q (4) // // is upper triangular. All the matrices have the order n. // // The matrices F and V are stored in row/column-wise sparse format as // row and column linked lists of non-zero elements. Unity elements on // the main diagonal of the matrix F are not stored. Pivot elements of // the matrix V (that correspond to diagonal elements of the matrix U) // are also missing from the row and column lists and stored separately // in an ordinary array. // // The permutation matrices P and Q are stored as ordinary arrays using // both row- and column-like formats. // // The matrices L and U being completely defined by the matrices F, V, // P, and Q are not stored explicitly. // // It is easy to show that the factorization (1)-(3) is some version of // LU-factorization. Indeed, from (3) and (4) it follows that: // // F = inv(P) * L * P, // // V = inv(P) * U * inv(Q), // // and substitution into (2) gives: // // A = F * V = inv(P) * L * U * inv(Q). // // For more details see the program documentation. */ typedef struct LUX LUX; typedef struct LUXELM LUXELM; typedef struct LUXWKA LUXWKA; struct LUX { /* LU-factorization of a square matrix */ int n; /* the order of matrices A, F, V, P, Q */ DMP *pool; /* memory pool for elements of matrices F and V */ LUXELM **F_row; /* LUXELM *F_row[1+n]; */ /* F_row[0] is not used; F_row[i], 1 <= i <= n, is a pointer to the list of elements in i-th row of matrix F (diagonal elements are not stored) */ LUXELM **F_col; /* LUXELM *F_col[1+n]; */ /* F_col[0] is not used; F_col[j], 1 <= j <= n, is a pointer to the list of elements in j-th column of matrix F (diagonal elements are not stored) */ mpq_t *V_piv; /* mpq_t V_piv[1+n]; */ /* V_piv[0] is not used; V_piv[p], 1 <= p <= n, is a pivot element v[p,q] corresponding to a diagonal element u[k,k] of matrix U = P*V*Q (used on k-th elimination step, k = 1, 2, ..., n) */ LUXELM **V_row; /* LUXELM *V_row[1+n]; */ /* V_row[0] is not used; V_row[i], 1 <= i <= n, is a pointer to the list of elements in i-th row of matrix V (except pivot elements) */ LUXELM **V_col; /* LUXELM *V_col[1+n]; */ /* V_col[0] is not used; V_col[j], 1 <= j <= n, is a pointer to the list of elements in j-th column of matrix V (except pivot elements) */ int *P_row; /* int P_row[1+n]; */ /* P_row[0] is not used; P_row[i] = j means that p[i,j] = 1, where p[i,j] is an element of permutation matrix P */ int *P_col; /* int P_col[1+n]; */ /* P_col[0] is not used; P_col[j] = i means that p[i,j] = 1, where p[i,j] is an element of permutation matrix P */ /* if i-th row or column of matrix F is i'-th row or column of matrix L = P*F*inv(P), or if i-th row of matrix V is i'-th row of matrix U = P*V*Q, then P_row[i'] = i and P_col[i] = i' */ int *Q_row; /* int Q_row[1+n]; */ /* Q_row[0] is not used; Q_row[i] = j means that q[i,j] = 1, where q[i,j] is an element of permutation matrix Q */ int *Q_col; /* int Q_col[1+n]; */ /* Q_col[0] is not used; Q_col[j] = i means that q[i,j] = 1, where q[i,j] is an element of permutation matrix Q */ /* if j-th column of matrix V is j'-th column of matrix U = P*V*Q, then Q_row[j] = j' and Q_col[j'] = j */ int rank; /* the (exact) rank of matrices A and V */ }; struct LUXELM { /* element of matrix F or V */ int i; /* row index, 1 <= i <= m */ int j; /* column index, 1 <= j <= n */ mpq_t val; /* numeric (non-zero) element value */ LUXELM *r_prev; /* pointer to previous element in the same row */ LUXELM *r_next; /* pointer to next element in the same row */ LUXELM *c_prev; /* pointer to previous element in the same column */ LUXELM *c_next; /* pointer to next element in the same column */ }; struct LUXWKA { /* working area (used only during factorization) */ /* in order to efficiently implement Markowitz strategy and Duff search technique there are two families {R[0], R[1], ..., R[n]} and {C[0], C[1], ..., C[n]}; member R[k] is a set of active rows of matrix V having k non-zeros, and member C[k] is a set of active columns of matrix V having k non-zeros (in the active submatrix); each set R[k] and C[k] is implemented as a separate doubly linked list */ int *R_len; /* int R_len[1+n]; */ /* R_len[0] is not used; R_len[i], 1 <= i <= n, is the number of non-zero elements in i-th row of matrix V (that is the length of i-th row) */ int *R_head; /* int R_head[1+n]; */ /* R_head[k], 0 <= k <= n, is the number of a first row, which is active and whose length is k */ int *R_prev; /* int R_prev[1+n]; */ /* R_prev[0] is not used; R_prev[i], 1 <= i <= n, is the number of a previous row, which is active and has the same length as i-th row */ int *R_next; /* int R_next[1+n]; */ /* R_prev[0] is not used; R_prev[i], 1 <= i <= n, is the number of a next row, which is active and has the same length as i-th row */ int *C_len; /* int C_len[1+n]; */ /* C_len[0] is not used; C_len[j], 1 <= j <= n, is the number of non-zero elements in j-th column of the active submatrix of matrix V (that is the length of j-th column in the active submatrix) */ int *C_head; /* int C_head[1+n]; */ /* C_head[k], 0 <= k <= n, is the number of a first column, which is active and whose length is k */ int *C_prev; /* int C_prev[1+n]; */ /* C_prev[0] is not used; C_prev[j], 1 <= j <= n, is the number of a previous column, which is active and has the same length as j-th column */ int *C_next; /* int C_next[1+n]; */ /* C_next[0] is not used; C_next[j], 1 <= j <= n, is the number of a next column, which is active and has the same length as j-th column */ }; #define lux_create _glp_lux_create #define lux_decomp _glp_lux_decomp #define lux_f_solve _glp_lux_f_solve #define lux_v_solve _glp_lux_v_solve #define lux_solve _glp_lux_solve #define lux_delete _glp_lux_delete LUX *lux_create(int n); /* create LU-factorization */ int lux_decomp(LUX *lux, int (*col)(void *info, int j, int ind[], mpq_t val[]), void *info); /* compute LU-factorization */ void lux_f_solve(LUX *lux, int tr, mpq_t x[]); /* solve system F*x = b or F'*x = b */ void lux_v_solve(LUX *lux, int tr, mpq_t x[]); /* solve system V*x = b or V'*x = b */ void lux_solve(LUX *lux, int tr, mpq_t x[]); /* solve system A*x = b or A'*x = b */ void lux_delete(LUX *lux); /* delete LU-factorization */ #endif /* eof */ sources_5316/external/glpk/glpios05.c0000644000176700017670000002361611401660400016310 0ustar paulpaul/* glpios05.c (Gomory's mixed integer cut generator) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*********************************************************************** * NAME * * ios_gmi_gen - generate Gomory's mixed integer cuts. * * SYNOPSIS * * #include "glpios.h" * void ios_gmi_gen(glp_tree *tree, IOSPOOL *pool); * * DESCRIPTION * * The routine ios_gmi_gen generates Gomory's mixed integer cuts for * the current point and adds them to the cut pool. */ #define MAXCUTS 50 /* maximal number of cuts to be generated for one round */ struct worka { /* Gomory's cut generator working area */ int *ind; /* int ind[1+n]; */ double *val; /* double val[1+n]; */ double *phi; /* double phi[1+m+n]; */ }; #define f(x) ((x) - floor(x)) /* compute fractional part of x */ static void gen_cut(glp_tree *tree, struct worka *worka, int j) { /* this routine tries to generate Gomory's mixed integer cut for specified structural variable x[m+j] of integer kind, which is basic and has fractional value in optimal solution to current LP relaxation */ glp_prob *mip = tree->mip; int m = mip->m; int n = mip->n; int *ind = worka->ind; double *val = worka->val; double *phi = worka->phi; int i, k, len, kind, stat; double lb, ub, alfa, beta, ksi, phi1, rhs; /* compute row of the simplex tableau, which (row) corresponds to specified basic variable xB[i] = x[m+j]; see (23) */ len = glp_eval_tab_row(mip, m+j, ind, val); /* determine beta[i], which a value of xB[i] in optimal solution to current LP relaxation; note that this value is the same as if it would be computed with formula (27); it is assumed that beta[i] is fractional enough */ beta = mip->col[j]->prim; /* compute cut coefficients phi and right-hand side rho, which correspond to formula (30); dense format is used, because rows of the simplex tableau is usually dense */ for (k = 1; k <= m+n; k++) phi[k] = 0.0; rhs = f(beta); /* initial value of rho; see (28), (32) */ for (j = 1; j <= len; j++) { /* determine original number of non-basic variable xN[j] */ k = ind[j]; xassert(1 <= k && k <= m+n); /* determine the kind, bounds and current status of xN[j] in optimal solution to LP relaxation */ if (k <= m) { /* auxiliary variable */ GLPROW *row = mip->row[k]; kind = GLP_CV; lb = row->lb; ub = row->ub; stat = row->stat; } else { /* structural variable */ GLPCOL *col = mip->col[k-m]; kind = col->kind; lb = col->lb; ub = col->ub; stat = col->stat; } /* xN[j] cannot be basic */ xassert(stat != GLP_BS); /* determine row coefficient ksi[i,j] at xN[j]; see (23) */ ksi = val[j]; /* if ksi[i,j] is too large in the magnitude, do not generate the cut */ if (fabs(ksi) > 1e+05) goto fini; /* if ksi[i,j] is too small in the magnitude, skip it */ if (fabs(ksi) < 1e-10) goto skip; /* compute row coefficient alfa[i,j] at y[j]; see (26) */ switch (stat) { case GLP_NF: /* xN[j] is free (unbounded) having non-zero ksi[i,j]; do not generate the cut */ goto fini; case GLP_NL: /* xN[j] has active lower bound */ alfa = - ksi; break; case GLP_NU: /* xN[j] has active upper bound */ alfa = + ksi; break; case GLP_NS: /* xN[j] is fixed; skip it */ goto skip; default: xassert(stat != stat); } /* compute cut coefficient phi'[j] at y[j]; see (21), (28) */ switch (kind) { case GLP_IV: /* y[j] is integer */ if (fabs(alfa - floor(alfa + 0.5)) < 1e-10) { /* alfa[i,j] is close to nearest integer; skip it */ goto skip; } else if (f(alfa) <= f(beta)) phi1 = f(alfa); else phi1 = (f(beta) / (1.0 - f(beta))) * (1.0 - f(alfa)); break; case GLP_CV: /* y[j] is continuous */ if (alfa >= 0.0) phi1 = + alfa; else phi1 = (f(beta) / (1.0 - f(beta))) * (- alfa); break; default: xassert(kind != kind); } /* compute cut coefficient phi[j] at xN[j] and update right- hand side rho; see (31), (32) */ switch (stat) { case GLP_NL: /* xN[j] has active lower bound */ phi[k] = + phi1; rhs += phi1 * lb; break; case GLP_NU: /* xN[j] has active upper bound */ phi[k] = - phi1; rhs -= phi1 * ub; break; default: xassert(stat != stat); } skip: ; } /* now the cut has the form sum_k phi[k] * x[k] >= rho, where cut coefficients are stored in the array phi in dense format; x[1,...,m] are auxiliary variables, x[m+1,...,m+n] are struc- tural variables; see (30) */ /* eliminate auxiliary variables in order to express the cut only through structural variables; see (33) */ for (i = 1; i <= m; i++) { GLPROW *row; GLPAIJ *aij; if (fabs(phi[i]) < 1e-10) continue; /* auxiliary variable x[i] has non-zero cut coefficient */ row = mip->row[i]; /* x[i] cannot be fixed */ xassert(row->type != GLP_FX); /* substitute x[i] = sum_j a[i,j] * x[m+j] */ for (aij = row->ptr; aij != NULL; aij = aij->r_next) phi[m+aij->col->j] += phi[i] * aij->val; } /* convert the final cut to sparse format and substitute fixed (structural) variables */ len = 0; for (j = 1; j <= n; j++) { GLPCOL *col; if (fabs(phi[m+j]) < 1e-10) continue; /* structural variable x[m+j] has non-zero cut coefficient */ col = mip->col[j]; if (col->type == GLP_FX) { /* eliminate x[m+j] */ rhs -= phi[m+j] * col->lb; } else { len++; ind[len] = j; val[len] = phi[m+j]; } } if (fabs(rhs) < 1e-12) rhs = 0.0; /* if the cut inequality seems to be badly scaled, reject it to avoid numeric difficulties */ for (k = 1; k <= len; k++) { if (fabs(val[k]) < 1e-03) goto fini; if (fabs(val[k]) > 1e+03) goto fini; } /* add the cut to the cut pool for further consideration */ #if 0 ios_add_cut_row(tree, pool, GLP_RF_GMI, len, ind, val, GLP_LO, rhs); #else glp_ios_add_row(tree, NULL, GLP_RF_GMI, 0, len, ind, val, GLP_LO, rhs); #endif fini: return; } struct var { int j; double f; }; static int fcmp(const void *p1, const void *p2) { const struct var *v1 = p1, *v2 = p2; if (v1->f > v2->f) return -1; if (v1->f < v2->f) return +1; return 0; } void ios_gmi_gen(glp_tree *tree) { /* main routine to generate Gomory's cuts */ glp_prob *mip = tree->mip; int m = mip->m; int n = mip->n; struct var *var; int k, nv, j, size; struct worka _worka, *worka = &_worka; /* allocate working arrays */ var = xcalloc(1+n, sizeof(struct var)); worka->ind = xcalloc(1+n, sizeof(int)); worka->val = xcalloc(1+n, sizeof(double)); worka->phi = xcalloc(1+m+n, sizeof(double)); /* build the list of integer structural variables, which are basic and have fractional value in optimal solution to current LP relaxation */ nv = 0; for (j = 1; j <= n; j++) { GLPCOL *col = mip->col[j]; double frac; if (col->kind != GLP_IV) continue; if (col->type == GLP_FX) continue; if (col->stat != GLP_BS) continue; frac = f(col->prim); if (!(0.05 <= frac && frac <= 0.95)) continue; /* add variable to the list */ nv++, var[nv].j = j, var[nv].f = frac; } /* order the list by descending fractionality */ qsort(&var[1], nv, sizeof(struct var), fcmp); /* try to generate cuts by one for each variable in the list, but not more than MAXCUTS cuts */ size = glp_ios_pool_size(tree); for (k = 1; k <= nv; k++) { if (glp_ios_pool_size(tree) - size >= MAXCUTS) break; gen_cut(tree, worka, var[k].j); } /* free working arrays */ xfree(var); xfree(worka->ind); xfree(worka->val); xfree(worka->phi); return; } /* eof */ sources_5316/external/glpk/glpmat.c0000644000176700017670000010034311411446072016133 0ustar paulpaul/* glpmat.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glpmat.h" #include "glpqmd.h" #include "amd.h" #include "colamd.h" /*---------------------------------------------------------------------- -- check_fvs - check sparse vector in full-vector storage format. -- -- SYNOPSIS -- -- #include "glpmat.h" -- int check_fvs(int n, int nnz, int ind[], double vec[]); -- -- DESCRIPTION -- -- The routine check_fvs checks if a given vector of dimension n in -- full-vector storage format has correct representation. -- -- RETURNS -- -- The routine returns one of the following codes: -- -- 0 - the vector is correct; -- 1 - the number of elements (n) is negative; -- 2 - the number of non-zero elements (nnz) is negative; -- 3 - some element index is out of range; -- 4 - some element index is duplicate; -- 5 - some non-zero element is out of pattern. */ int check_fvs(int n, int nnz, int ind[], double vec[]) { int i, t, ret, *flag = NULL; /* check the number of elements */ if (n < 0) { ret = 1; goto done; } /* check the number of non-zero elements */ if (nnz < 0) { ret = 2; goto done; } /* check vector indices */ flag = xcalloc(1+n, sizeof(int)); for (i = 1; i <= n; i++) flag[i] = 0; for (t = 1; t <= nnz; t++) { i = ind[t]; if (!(1 <= i && i <= n)) { ret = 3; goto done; } if (flag[i]) { ret = 4; goto done; } flag[i] = 1; } /* check vector elements */ for (i = 1; i <= n; i++) { if (!flag[i] && vec[i] != 0.0) { ret = 5; goto done; } } /* the vector is ok */ ret = 0; done: if (flag != NULL) xfree(flag); return ret; } /*---------------------------------------------------------------------- -- check_pattern - check pattern of sparse matrix. -- -- SYNOPSIS -- -- #include "glpmat.h" -- int check_pattern(int m, int n, int A_ptr[], int A_ind[]); -- -- DESCRIPTION -- -- The routine check_pattern checks the pattern of a given mxn matrix -- in storage-by-rows format. -- -- RETURNS -- -- The routine returns one of the following codes: -- -- 0 - the pattern is correct; -- 1 - the number of rows (m) is negative; -- 2 - the number of columns (n) is negative; -- 3 - A_ptr[1] is not 1; -- 4 - some column index is out of range; -- 5 - some column indices are duplicate. */ int check_pattern(int m, int n, int A_ptr[], int A_ind[]) { int i, j, ptr, ret, *flag = NULL; /* check the number of rows */ if (m < 0) { ret = 1; goto done; } /* check the number of columns */ if (n < 0) { ret = 2; goto done; } /* check location A_ptr[1] */ if (A_ptr[1] != 1) { ret = 3; goto done; } /* check row patterns */ flag = xcalloc(1+n, sizeof(int)); for (j = 1; j <= n; j++) flag[j] = 0; for (i = 1; i <= m; i++) { /* check pattern of row i */ for (ptr = A_ptr[i]; ptr < A_ptr[i+1]; ptr++) { j = A_ind[ptr]; /* check column index */ if (!(1 <= j && j <= n)) { ret = 4; goto done; } /* check for duplication */ if (flag[j]) { ret = 5; goto done; } flag[j] = 1; } /* clear flags */ for (ptr = A_ptr[i]; ptr < A_ptr[i+1]; ptr++) { j = A_ind[ptr]; flag[j] = 0; } } /* the pattern is ok */ ret = 0; done: if (flag != NULL) xfree(flag); return ret; } /*---------------------------------------------------------------------- -- transpose - transpose sparse matrix. -- -- *Synopsis* -- -- #include "glpmat.h" -- void transpose(int m, int n, int A_ptr[], int A_ind[], -- double A_val[], int AT_ptr[], int AT_ind[], double AT_val[]); -- -- *Description* -- -- For a given mxn sparse matrix A the routine transpose builds a nxm -- sparse matrix A' which is a matrix transposed to A. -- -- The arrays A_ptr, A_ind, and A_val specify a given mxn matrix A to -- be transposed in storage-by-rows format. The parameter A_val can be -- NULL, in which case numeric values are not copied. The arrays A_ptr, -- A_ind, and A_val are not changed on exit. -- -- On entry the arrays AT_ptr, AT_ind, and AT_val must be allocated, -- but their content is ignored. On exit the routine stores a resultant -- nxm matrix A' in these arrays in storage-by-rows format. Note that -- if the parameter A_val is NULL, the array AT_val is not used. -- -- The routine transpose has a side effect that elements in rows of the -- resultant matrix A' follow in ascending their column indices. */ void transpose(int m, int n, int A_ptr[], int A_ind[], double A_val[], int AT_ptr[], int AT_ind[], double AT_val[]) { int i, j, t, beg, end, pos, len; /* determine row lengths of resultant matrix */ for (j = 1; j <= n; j++) AT_ptr[j] = 0; for (i = 1; i <= m; i++) { beg = A_ptr[i], end = A_ptr[i+1]; for (t = beg; t < end; t++) AT_ptr[A_ind[t]]++; } /* set up row pointers of resultant matrix */ pos = 1; for (j = 1; j <= n; j++) len = AT_ptr[j], pos += len, AT_ptr[j] = pos; AT_ptr[n+1] = pos; /* build resultant matrix */ for (i = m; i >= 1; i--) { beg = A_ptr[i], end = A_ptr[i+1]; for (t = beg; t < end; t++) { pos = --AT_ptr[A_ind[t]]; AT_ind[pos] = i; if (A_val != NULL) AT_val[pos] = A_val[t]; } } return; } /*---------------------------------------------------------------------- -- adat_symbolic - compute S = P*A*D*A'*P' (symbolic phase). -- -- *Synopsis* -- -- #include "glpmat.h" -- int *adat_symbolic(int m, int n, int P_per[], int A_ptr[], -- int A_ind[], int S_ptr[]); -- -- *Description* -- -- The routine adat_symbolic implements the symbolic phase to compute -- symmetric matrix S = P*A*D*A'*P', where P is a permutation matrix, -- A is a given sparse matrix, D is a diagonal matrix, A' is a matrix -- transposed to A, P' is an inverse of P. -- -- The parameter m is the number of rows in A and the order of P. -- -- The parameter n is the number of columns in A and the order of D. -- -- The array P_per specifies permutation matrix P. It is not changed on -- exit. -- -- The arrays A_ptr and A_ind specify the pattern of matrix A. They are -- not changed on exit. -- -- On exit the routine stores the pattern of upper triangular part of -- matrix S without diagonal elements in the arrays S_ptr and S_ind in -- storage-by-rows format. The array S_ptr should be allocated on entry, -- however, its content is ignored. The array S_ind is allocated by the -- routine itself which returns a pointer to it. -- -- *Returns* -- -- The routine returns a pointer to the array S_ind. */ int *adat_symbolic(int m, int n, int P_per[], int A_ptr[], int A_ind[], int S_ptr[]) { int i, j, t, ii, jj, tt, k, size, len; int *S_ind, *AT_ptr, *AT_ind, *ind, *map, *temp; /* build the pattern of A', which is a matrix transposed to A, to efficiently access A in column-wise manner */ AT_ptr = xcalloc(1+n+1, sizeof(int)); AT_ind = xcalloc(A_ptr[m+1], sizeof(int)); transpose(m, n, A_ptr, A_ind, NULL, AT_ptr, AT_ind, NULL); /* allocate the array S_ind */ size = A_ptr[m+1] - 1; if (size < m) size = m; S_ind = xcalloc(1+size, sizeof(int)); /* allocate and initialize working arrays */ ind = xcalloc(1+m, sizeof(int)); map = xcalloc(1+m, sizeof(int)); for (jj = 1; jj <= m; jj++) map[jj] = 0; /* compute pattern of S; note that symbolically S = B*B', where B = P*A, B' is matrix transposed to B */ S_ptr[1] = 1; for (ii = 1; ii <= m; ii++) { /* compute pattern of ii-th row of S */ len = 0; i = P_per[ii]; /* i-th row of A = ii-th row of B */ for (t = A_ptr[i]; t < A_ptr[i+1]; t++) { k = A_ind[t]; /* walk through k-th column of A */ for (tt = AT_ptr[k]; tt < AT_ptr[k+1]; tt++) { j = AT_ind[tt]; jj = P_per[m+j]; /* j-th row of A = jj-th row of B */ /* a[i,k] != 0 and a[j,k] != 0 ergo s[ii,jj] != 0 */ if (ii < jj && !map[jj]) ind[++len] = jj, map[jj] = 1; } } /* now (ind) is pattern of ii-th row of S */ S_ptr[ii+1] = S_ptr[ii] + len; /* at least (S_ptr[ii+1] - 1) locations should be available in the array S_ind */ if (S_ptr[ii+1] - 1 > size) { temp = S_ind; size += size; S_ind = xcalloc(1+size, sizeof(int)); memcpy(&S_ind[1], &temp[1], (S_ptr[ii] - 1) * sizeof(int)); xfree(temp); } xassert(S_ptr[ii+1] - 1 <= size); /* (ii-th row of S) := (ind) */ memcpy(&S_ind[S_ptr[ii]], &ind[1], len * sizeof(int)); /* clear the row pattern map */ for (t = 1; t <= len; t++) map[ind[t]] = 0; } /* free working arrays */ xfree(AT_ptr); xfree(AT_ind); xfree(ind); xfree(map); /* reallocate the array S_ind to free unused locations */ temp = S_ind; size = S_ptr[m+1] - 1; S_ind = xcalloc(1+size, sizeof(int)); memcpy(&S_ind[1], &temp[1], size * sizeof(int)); xfree(temp); return S_ind; } /*---------------------------------------------------------------------- -- adat_numeric - compute S = P*A*D*A'*P' (numeric phase). -- -- *Synopsis* -- -- #include "glpmat.h" -- void adat_numeric(int m, int n, int P_per[], -- int A_ptr[], int A_ind[], double A_val[], double D_diag[], -- int S_ptr[], int S_ind[], double S_val[], double S_diag[]); -- -- *Description* -- -- The routine adat_numeric implements the numeric phase to compute -- symmetric matrix S = P*A*D*A'*P', where P is a permutation matrix, -- A is a given sparse matrix, D is a diagonal matrix, A' is a matrix -- transposed to A, P' is an inverse of P. -- -- The parameter m is the number of rows in A and the order of P. -- -- The parameter n is the number of columns in A and the order of D. -- -- The matrix P is specified in the array P_per, which is not changed -- on exit. -- -- The matrix A is specified in the arrays A_ptr, A_ind, and A_val in -- storage-by-rows format. These arrays are not changed on exit. -- -- Diagonal elements of the matrix D are specified in the array D_diag, -- where D_diag[0] is not used, D_diag[i] = d[i,i] for i = 1, ..., n. -- The array D_diag is not changed on exit. -- -- The pattern of the upper triangular part of the matrix S without -- diagonal elements (previously computed by the routine adat_symbolic) -- is specified in the arrays S_ptr and S_ind, which are not changed on -- exit. Numeric values of non-diagonal elements of S are stored in -- corresponding locations of the array S_val, and values of diagonal -- elements of S are stored in locations S_diag[1], ..., S_diag[n]. */ void adat_numeric(int m, int n, int P_per[], int A_ptr[], int A_ind[], double A_val[], double D_diag[], int S_ptr[], int S_ind[], double S_val[], double S_diag[]) { int i, j, t, ii, jj, tt, beg, end, beg1, end1, k; double sum, *work; work = xcalloc(1+n, sizeof(double)); for (j = 1; j <= n; j++) work[j] = 0.0; /* compute S = B*D*B', where B = P*A, B' is a matrix transposed to B */ for (ii = 1; ii <= m; ii++) { i = P_per[ii]; /* i-th row of A = ii-th row of B */ /* (work) := (i-th row of A) */ beg = A_ptr[i], end = A_ptr[i+1]; for (t = beg; t < end; t++) work[A_ind[t]] = A_val[t]; /* compute ii-th row of S */ beg = S_ptr[ii], end = S_ptr[ii+1]; for (t = beg; t < end; t++) { jj = S_ind[t]; j = P_per[jj]; /* j-th row of A = jj-th row of B */ /* s[ii,jj] := sum a[i,k] * d[k,k] * a[j,k] */ sum = 0.0; beg1 = A_ptr[j], end1 = A_ptr[j+1]; for (tt = beg1; tt < end1; tt++) { k = A_ind[tt]; sum += work[k] * D_diag[k] * A_val[tt]; } S_val[t] = sum; } /* s[ii,ii] := sum a[i,k] * d[k,k] * a[i,k] */ sum = 0.0; beg = A_ptr[i], end = A_ptr[i+1]; for (t = beg; t < end; t++) { k = A_ind[t]; sum += A_val[t] * D_diag[k] * A_val[t]; work[k] = 0.0; } S_diag[ii] = sum; } xfree(work); return; } /*---------------------------------------------------------------------- -- min_degree - minimum degree ordering. -- -- *Synopsis* -- -- #include "glpmat.h" -- void min_degree(int n, int A_ptr[], int A_ind[], int P_per[]); -- -- *Description* -- -- The routine min_degree uses the minimum degree ordering algorithm -- to find a permutation matrix P for a given sparse symmetric positive -- matrix A which minimizes the number of non-zeros in upper triangular -- factor U for Cholesky factorization P*A*P' = U'*U. -- -- The parameter n is the order of matrices A and P. -- -- The pattern of the given matrix A is specified on entry in the arrays -- A_ptr and A_ind in storage-by-rows format. Only the upper triangular -- part without diagonal elements (which all are assumed to be non-zero) -- should be specified as if A were upper triangular. The arrays A_ptr -- and A_ind are not changed on exit. -- -- The permutation matrix P is stored by the routine in the array P_per -- on exit. -- -- *Algorithm* -- -- The routine min_degree is based on some subroutines from the package -- SPARSPAK (see comments in the module glpqmd). */ void min_degree(int n, int A_ptr[], int A_ind[], int P_per[]) { int i, j, ne, t, pos, len; int *xadj, *adjncy, *deg, *marker, *rchset, *nbrhd, *qsize, *qlink, nofsub; /* determine number of non-zeros in complete pattern */ ne = A_ptr[n+1] - 1; ne += ne; /* allocate working arrays */ xadj = xcalloc(1+n+1, sizeof(int)); adjncy = xcalloc(1+ne, sizeof(int)); deg = xcalloc(1+n, sizeof(int)); marker = xcalloc(1+n, sizeof(int)); rchset = xcalloc(1+n, sizeof(int)); nbrhd = xcalloc(1+n, sizeof(int)); qsize = xcalloc(1+n, sizeof(int)); qlink = xcalloc(1+n, sizeof(int)); /* determine row lengths in complete pattern */ for (i = 1; i <= n; i++) xadj[i] = 0; for (i = 1; i <= n; i++) { for (t = A_ptr[i]; t < A_ptr[i+1]; t++) { j = A_ind[t]; xassert(i < j && j <= n); xadj[i]++, xadj[j]++; } } /* set up row pointers for complete pattern */ pos = 1; for (i = 1; i <= n; i++) len = xadj[i], pos += len, xadj[i] = pos; xadj[n+1] = pos; xassert(pos - 1 == ne); /* construct complete pattern */ for (i = 1; i <= n; i++) { for (t = A_ptr[i]; t < A_ptr[i+1]; t++) { j = A_ind[t]; adjncy[--xadj[i]] = j, adjncy[--xadj[j]] = i; } } /* call the main minimimum degree ordering routine */ genqmd(&n, xadj, adjncy, P_per, P_per + n, deg, marker, rchset, nbrhd, qsize, qlink, &nofsub); /* make sure that permutation matrix P is correct */ for (i = 1; i <= n; i++) { j = P_per[i]; xassert(1 <= j && j <= n); xassert(P_per[n+j] == i); } /* free working arrays */ xfree(xadj); xfree(adjncy); xfree(deg); xfree(marker); xfree(rchset); xfree(nbrhd); xfree(qsize); xfree(qlink); return; } /**********************************************************************/ void amd_order1(int n, int A_ptr[], int A_ind[], int P_per[]) { /* approximate minimum degree ordering (AMD) */ int k, ret; double Control[AMD_CONTROL], Info[AMD_INFO]; /* get the default parameters */ amd_defaults(Control); #if 0 /* and print them */ amd_control(Control); #endif /* make all indices 0-based */ for (k = 1; k < A_ptr[n+1]; k++) A_ind[k]--; for (k = 1; k <= n+1; k++) A_ptr[k]--; /* call the ordering routine */ ret = amd_order(n, &A_ptr[1], &A_ind[1], &P_per[1], Control, Info) ; #if 0 amd_info(Info); #endif xassert(ret == AMD_OK || ret == AMD_OK_BUT_JUMBLED); /* retsore 1-based indices */ for (k = 1; k <= n+1; k++) A_ptr[k]++; for (k = 1; k < A_ptr[n+1]; k++) A_ind[k]++; /* patch up permutation matrix */ memset(&P_per[n+1], 0, n * sizeof(int)); for (k = 1; k <= n; k++) { P_per[k]++; xassert(1 <= P_per[k] && P_per[k] <= n); xassert(P_per[n+P_per[k]] == 0); P_per[n+P_per[k]] = k; } return; } /**********************************************************************/ static void *allocate(size_t n, size_t size) { void *ptr; ptr = xcalloc(n, size); memset(ptr, 0, n * size); return ptr; } static void release(void *ptr) { xfree(ptr); return; } void symamd_ord(int n, int A_ptr[], int A_ind[], int P_per[]) { /* approximate minimum degree ordering (SYMAMD) */ int k, ok; int stats[COLAMD_STATS]; /* make all indices 0-based */ for (k = 1; k < A_ptr[n+1]; k++) A_ind[k]--; for (k = 1; k <= n+1; k++) A_ptr[k]--; /* call the ordering routine */ ok = symamd(n, &A_ind[1], &A_ptr[1], &P_per[1], NULL, stats, allocate, release); #if 0 symamd_report(stats); #endif xassert(ok); /* restore 1-based indices */ for (k = 1; k <= n+1; k++) A_ptr[k]++; for (k = 1; k < A_ptr[n+1]; k++) A_ind[k]++; /* patch up permutation matrix */ memset(&P_per[n+1], 0, n * sizeof(int)); for (k = 1; k <= n; k++) { P_per[k]++; xassert(1 <= P_per[k] && P_per[k] <= n); xassert(P_per[n+P_per[k]] == 0); P_per[n+P_per[k]] = k; } return; } /*---------------------------------------------------------------------- -- chol_symbolic - compute Cholesky factorization (symbolic phase). -- -- *Synopsis* -- -- #include "glpmat.h" -- int *chol_symbolic(int n, int A_ptr[], int A_ind[], int U_ptr[]); -- -- *Description* -- -- The routine chol_symbolic implements the symbolic phase of Cholesky -- factorization A = U'*U, where A is a given sparse symmetric positive -- definite matrix, U is a resultant upper triangular factor, U' is a -- matrix transposed to U. -- -- The parameter n is the order of matrices A and U. -- -- The pattern of the given matrix A is specified on entry in the arrays -- A_ptr and A_ind in storage-by-rows format. Only the upper triangular -- part without diagonal elements (which all are assumed to be non-zero) -- should be specified as if A were upper triangular. The arrays A_ptr -- and A_ind are not changed on exit. -- -- The pattern of the matrix U without diagonal elements (which all are -- assumed to be non-zero) is stored on exit from the routine in the -- arrays U_ptr and U_ind in storage-by-rows format. The array U_ptr -- should be allocated on entry, however, its content is ignored. The -- array U_ind is allocated by the routine which returns a pointer to it -- on exit. -- -- *Returns* -- -- The routine returns a pointer to the array U_ind. -- -- *Method* -- -- The routine chol_symbolic computes the pattern of the matrix U in a -- row-wise manner. No pivoting is used. -- -- It is known that to compute the pattern of row k of the matrix U we -- need to merge the pattern of row k of the matrix A and the patterns -- of each row i of U, where u[i,k] is non-zero (these rows are already -- computed and placed above row k). -- -- However, to reduce the number of rows to be merged the routine uses -- an advanced algorithm proposed in: -- -- D.J.Rose, R.E.Tarjan, and G.S.Lueker. Algorithmic aspects of vertex -- elimination on graphs. SIAM J. Comput. 5, 1976, 266-83. -- -- The authors of the cited paper show that we have the same result if -- we merge row k of the matrix A and such rows of the matrix U (among -- rows 1, ..., k-1) whose leftmost non-diagonal non-zero element is -- placed in k-th column. This feature signficantly reduces the number -- of rows to be merged, especially on the final steps, where rows of -- the matrix U become quite dense. -- -- To determine rows, which should be merged on k-th step, for a fixed -- time the routine uses linked lists of row numbers of the matrix U. -- Location head[k] contains the number of a first row, whose leftmost -- non-diagonal non-zero element is placed in column k, and location -- next[i] contains the number of a next row with the same property as -- row i. */ int *chol_symbolic(int n, int A_ptr[], int A_ind[], int U_ptr[]) { int i, j, k, t, len, size, beg, end, min_j, *U_ind, *head, *next, *ind, *map, *temp; /* initially we assume that on computing the pattern of U fill-in will double the number of non-zeros in A */ size = A_ptr[n+1] - 1; if (size < n) size = n; size += size; U_ind = xcalloc(1+size, sizeof(int)); /* allocate and initialize working arrays */ head = xcalloc(1+n, sizeof(int)); for (i = 1; i <= n; i++) head[i] = 0; next = xcalloc(1+n, sizeof(int)); ind = xcalloc(1+n, sizeof(int)); map = xcalloc(1+n, sizeof(int)); for (j = 1; j <= n; j++) map[j] = 0; /* compute the pattern of matrix U */ U_ptr[1] = 1; for (k = 1; k <= n; k++) { /* compute the pattern of k-th row of U, which is the union of k-th row of A and those rows of U (among 1, ..., k-1) whose leftmost non-diagonal non-zero is placed in k-th column */ /* (ind) := (k-th row of A) */ len = A_ptr[k+1] - A_ptr[k]; memcpy(&ind[1], &A_ind[A_ptr[k]], len * sizeof(int)); for (t = 1; t <= len; t++) { j = ind[t]; xassert(k < j && j <= n); map[j] = 1; } /* walk through rows of U whose leftmost non-diagonal non-zero is placed in k-th column */ for (i = head[k]; i != 0; i = next[i]) { /* (ind) := (ind) union (i-th row of U) */ beg = U_ptr[i], end = U_ptr[i+1]; for (t = beg; t < end; t++) { j = U_ind[t]; if (j > k && !map[j]) ind[++len] = j, map[j] = 1; } } /* now (ind) is the pattern of k-th row of U */ U_ptr[k+1] = U_ptr[k] + len; /* at least (U_ptr[k+1] - 1) locations should be available in the array U_ind */ if (U_ptr[k+1] - 1 > size) { temp = U_ind; size += size; U_ind = xcalloc(1+size, sizeof(int)); memcpy(&U_ind[1], &temp[1], (U_ptr[k] - 1) * sizeof(int)); xfree(temp); } xassert(U_ptr[k+1] - 1 <= size); /* (k-th row of U) := (ind) */ memcpy(&U_ind[U_ptr[k]], &ind[1], len * sizeof(int)); /* determine column index of leftmost non-diagonal non-zero in k-th row of U and clear the row pattern map */ min_j = n + 1; for (t = 1; t <= len; t++) { j = ind[t], map[j] = 0; if (min_j > j) min_j = j; } /* include k-th row into corresponding linked list */ if (min_j <= n) next[k] = head[min_j], head[min_j] = k; } /* free working arrays */ xfree(head); xfree(next); xfree(ind); xfree(map); /* reallocate the array U_ind to free unused locations */ temp = U_ind; size = U_ptr[n+1] - 1; U_ind = xcalloc(1+size, sizeof(int)); memcpy(&U_ind[1], &temp[1], size * sizeof(int)); xfree(temp); return U_ind; } /*---------------------------------------------------------------------- -- chol_numeric - compute Cholesky factorization (numeric phase). -- -- *Synopsis* -- -- #include "glpmat.h" -- int chol_numeric(int n, -- int A_ptr[], int A_ind[], double A_val[], double A_diag[], -- int U_ptr[], int U_ind[], double U_val[], double U_diag[]); -- -- *Description* -- -- The routine chol_symbolic implements the numeric phase of Cholesky -- factorization A = U'*U, where A is a given sparse symmetric positive -- definite matrix, U is a resultant upper triangular factor, U' is a -- matrix transposed to U. -- -- The parameter n is the order of matrices A and U. -- -- Upper triangular part of the matrix A without diagonal elements is -- specified in the arrays A_ptr, A_ind, and A_val in storage-by-rows -- format. Diagonal elements of A are specified in the array A_diag, -- where A_diag[0] is not used, A_diag[i] = a[i,i] for i = 1, ..., n. -- The arrays A_ptr, A_ind, A_val, and A_diag are not changed on exit. -- -- The pattern of the matrix U without diagonal elements (previously -- computed with the routine chol_symbolic) is specified in the arrays -- U_ptr and U_ind, which are not changed on exit. Numeric values of -- non-diagonal elements of U are stored in corresponding locations of -- the array U_val, and values of diagonal elements of U are stored in -- locations U_diag[1], ..., U_diag[n]. -- -- *Returns* -- -- The routine returns the number of non-positive diagonal elements of -- the matrix U which have been replaced by a huge positive number (see -- the method description below). Zero return code means the matrix A -- has been successfully factorized. -- -- *Method* -- -- The routine chol_numeric computes the matrix U in a row-wise manner -- using standard gaussian elimination technique. No pivoting is used. -- -- Initially the routine sets U = A, and before k-th elimination step -- the matrix U is the following: -- -- 1 k n -- 1 x x x x x x x x x x -- . x x x x x x x x x -- . . x x x x x x x x -- . . . x x x x x x x -- k . . . . * * * * * * -- . . . . * * * * * * -- . . . . * * * * * * -- . . . . * * * * * * -- . . . . * * * * * * -- n . . . . * * * * * * -- -- where 'x' are elements of already computed rows, '*' are elements of -- the active submatrix. (Note that the lower triangular part of the -- active submatrix being symmetric is not stored and diagonal elements -- are stored separately in the array U_diag.) -- -- The matrix A is assumed to be positive definite. However, if it is -- close to semi-definite, on some elimination step a pivot u[k,k] may -- happen to be non-positive due to round-off errors. In this case the -- routine uses a technique proposed in: -- -- S.J.Wright. The Cholesky factorization in interior-point and barrier -- methods. Preprint MCS-P600-0596, Mathematics and Computer Science -- Division, Argonne National Laboratory, Argonne, Ill., May 1996. -- -- The routine just replaces non-positive u[k,k] by a huge positive -- number. This involves non-diagonal elements in k-th row of U to be -- close to zero that, in turn, involves k-th component of a solution -- vector to be close to zero. Note, however, that this technique works -- only if the system A*x = b is consistent. */ int chol_numeric(int n, int A_ptr[], int A_ind[], double A_val[], double A_diag[], int U_ptr[], int U_ind[], double U_val[], double U_diag[]) { int i, j, k, t, t1, beg, end, beg1, end1, count = 0; double ukk, uki, *work; work = xcalloc(1+n, sizeof(double)); for (j = 1; j <= n; j++) work[j] = 0.0; /* U := (upper triangle of A) */ /* note that the upper traingle of A is a subset of U */ for (i = 1; i <= n; i++) { beg = A_ptr[i], end = A_ptr[i+1]; for (t = beg; t < end; t++) j = A_ind[t], work[j] = A_val[t]; beg = U_ptr[i], end = U_ptr[i+1]; for (t = beg; t < end; t++) j = U_ind[t], U_val[t] = work[j], work[j] = 0.0; U_diag[i] = A_diag[i]; } /* main elimination loop */ for (k = 1; k <= n; k++) { /* transform k-th row of U */ ukk = U_diag[k]; if (ukk > 0.0) U_diag[k] = ukk = sqrt(ukk); else U_diag[k] = ukk = DBL_MAX, count++; /* (work) := (transformed k-th row) */ beg = U_ptr[k], end = U_ptr[k+1]; for (t = beg; t < end; t++) work[U_ind[t]] = (U_val[t] /= ukk); /* transform other rows of U */ for (t = beg; t < end; t++) { i = U_ind[t]; xassert(i > k); /* (i-th row) := (i-th row) - u[k,i] * (k-th row) */ uki = work[i]; beg1 = U_ptr[i], end1 = U_ptr[i+1]; for (t1 = beg1; t1 < end1; t1++) U_val[t1] -= uki * work[U_ind[t1]]; U_diag[i] -= uki * uki; } /* (work) := 0 */ for (t = beg; t < end; t++) work[U_ind[t]] = 0.0; } xfree(work); return count; } /*---------------------------------------------------------------------- -- u_solve - solve upper triangular system U*x = b. -- -- *Synopsis* -- -- #include "glpmat.h" -- void u_solve(int n, int U_ptr[], int U_ind[], double U_val[], -- double U_diag[], double x[]); -- -- *Description* -- -- The routine u_solve solves an linear system U*x = b, where U is an -- upper triangular matrix. -- -- The parameter n is the order of matrix U. -- -- The matrix U without diagonal elements is specified in the arrays -- U_ptr, U_ind, and U_val in storage-by-rows format. Diagonal elements -- of U are specified in the array U_diag, where U_diag[0] is not used, -- U_diag[i] = u[i,i] for i = 1, ..., n. All these four arrays are not -- changed on exit. -- -- The right-hand side vector b is specified on entry in the array x, -- where x[0] is not used, and x[i] = b[i] for i = 1, ..., n. On exit -- the routine stores computed components of the vector of unknowns x -- in the array x in the same manner. */ void u_solve(int n, int U_ptr[], int U_ind[], double U_val[], double U_diag[], double x[]) { int i, t, beg, end; double temp; for (i = n; i >= 1; i--) { temp = x[i]; beg = U_ptr[i], end = U_ptr[i+1]; for (t = beg; t < end; t++) temp -= U_val[t] * x[U_ind[t]]; xassert(U_diag[i] != 0.0); x[i] = temp / U_diag[i]; } return; } /*---------------------------------------------------------------------- -- ut_solve - solve lower triangular system U'*x = b. -- -- *Synopsis* -- -- #include "glpmat.h" -- void ut_solve(int n, int U_ptr[], int U_ind[], double U_val[], -- double U_diag[], double x[]); -- -- *Description* -- -- The routine ut_solve solves an linear system U'*x = b, where U is a -- matrix transposed to an upper triangular matrix. -- -- The parameter n is the order of matrix U. -- -- The matrix U without diagonal elements is specified in the arrays -- U_ptr, U_ind, and U_val in storage-by-rows format. Diagonal elements -- of U are specified in the array U_diag, where U_diag[0] is not used, -- U_diag[i] = u[i,i] for i = 1, ..., n. All these four arrays are not -- changed on exit. -- -- The right-hand side vector b is specified on entry in the array x, -- where x[0] is not used, and x[i] = b[i] for i = 1, ..., n. On exit -- the routine stores computed components of the vector of unknowns x -- in the array x in the same manner. */ void ut_solve(int n, int U_ptr[], int U_ind[], double U_val[], double U_diag[], double x[]) { int i, t, beg, end; double temp; for (i = 1; i <= n; i++) { xassert(U_diag[i] != 0.0); temp = (x[i] /= U_diag[i]); if (temp == 0.0) continue; beg = U_ptr[i], end = U_ptr[i+1]; for (t = beg; t < end; t++) x[U_ind[t]] -= U_val[t] * temp; } return; } /* eof */ sources_5316/external/glpk/glpios12.c0000644000176700017670000001326011401660400016300 0ustar paulpaul/* glpios12.c (node selection heuristics) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*********************************************************************** * NAME * * ios_choose_node - select subproblem to continue the search * * SYNOPSIS * * #include "glpios.h" * int ios_choose_node(glp_tree *T); * * DESCRIPTION * * The routine ios_choose_node selects a subproblem from the active * list to continue the search. The choice depends on the backtracking * technique option. * * RETURNS * * The routine ios_choose_node return the reference number of the * subproblem selected. */ static int most_feas(glp_tree *T); static int best_proj(glp_tree *T); static int best_node(glp_tree *T); int ios_choose_node(glp_tree *T) { int p; if (T->parm->bt_tech == GLP_BT_DFS) { /* depth first search */ xassert(T->tail != NULL); p = T->tail->p; } else if (T->parm->bt_tech == GLP_BT_BFS) { /* breadth first search */ xassert(T->head != NULL); p = T->head->p; } else if (T->parm->bt_tech == GLP_BT_BLB) { /* select node with best local bound */ p = best_node(T); } else if (T->parm->bt_tech == GLP_BT_BPH) { if (T->mip->mip_stat == GLP_UNDEF) { /* "most integer feasible" subproblem */ p = most_feas(T); } else { /* best projection heuristic */ p = best_proj(T); } } else xassert(T != T); return p; } static int most_feas(glp_tree *T) { /* select subproblem whose parent has minimal sum of integer infeasibilities */ IOSNPD *node; int p; double best; p = 0, best = DBL_MAX; for (node = T->head; node != NULL; node = node->next) { xassert(node->up != NULL); if (best > node->up->ii_sum) p = node->p, best = node->up->ii_sum; } return p; } static int best_proj(glp_tree *T) { /* select subproblem using the best projection heuristic */ IOSNPD *root, *node; int p; double best, deg, obj; /* the global bound must exist */ xassert(T->mip->mip_stat == GLP_FEAS); /* obtain pointer to the root node, which must exist */ root = T->slot[1].node; xassert(root != NULL); /* deg estimates degradation of the objective function per unit of the sum of integer infeasibilities */ xassert(root->ii_sum > 0.0); deg = (T->mip->mip_obj - root->bound) / root->ii_sum; /* nothing has been selected so far */ p = 0, best = DBL_MAX; /* walk through the list of active subproblems */ for (node = T->head; node != NULL; node = node->next) { xassert(node->up != NULL); /* obj estimates optimal objective value if the sum of integer infeasibilities were zero */ obj = node->up->bound + deg * node->up->ii_sum; if (T->mip->dir == GLP_MAX) obj = - obj; /* select the subproblem which has the best estimated optimal objective value */ if (best > obj) p = node->p, best = obj; } return p; } static int best_node(glp_tree *T) { /* select subproblem with best local bound */ IOSNPD *node, *best = NULL; double bound, eps; switch (T->mip->dir) { case GLP_MIN: bound = +DBL_MAX; for (node = T->head; node != NULL; node = node->next) if (bound > node->bound) bound = node->bound; xassert(bound != +DBL_MAX); eps = 0.001 * (1.0 + fabs(bound)); for (node = T->head; node != NULL; node = node->next) { if (node->bound <= bound + eps) { xassert(node->up != NULL); if (best == NULL || #if 1 best->up->ii_sum > node->up->ii_sum) best = node; #else best->lp_obj > node->lp_obj) best = node; #endif } } break; case GLP_MAX: bound = -DBL_MAX; for (node = T->head; node != NULL; node = node->next) if (bound < node->bound) bound = node->bound; xassert(bound != -DBL_MAX); eps = 0.001 * (1.0 + fabs(bound)); for (node = T->head; node != NULL; node = node->next) { if (node->bound >= bound - eps) { xassert(node->up != NULL); if (best == NULL || #if 1 best->up->ii_sum > node->up->ii_sum) best = node; #else best->lp_obj < node->lp_obj) best = node; #endif } } break; default: xassert(T != T); } xassert(best != NULL); return best->p; } /* eof */ sources_5316/external/glpk/glpenv08.c0000644000176700017670000000743211401660400016307 0ustar paulpaul/* glpenv08.c (shared library support) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifdef HAVE_CONFIG_H #include #endif #include "glpenv.h" /* GNU version ********************************************************/ #if defined(HAVE_LTDL) #include void *xdlopen(const char *module) { void *h = NULL; if (lt_dlinit() != 0) { lib_err_msg(lt_dlerror()); goto done; } h = lt_dlopen(module); if (h == NULL) { lib_err_msg(lt_dlerror()); if (lt_dlexit() != 0) xerror("xdlopen: %s\n", lt_dlerror()); } done: return h; } void *xdlsym(void *h, const char *symbol) { void *ptr; xassert(h != NULL); ptr = lt_dlsym(h, symbol); if (ptr == NULL) xerror("xdlsym: %s: %s\n", symbol, lt_dlerror()); return ptr; } void xdlclose(void *h) { xassert(h != NULL); if (lt_dlclose(h) != 0) xerror("xdlclose: %s\n", lt_dlerror()); if (lt_dlexit() != 0) xerror("xdlclose: %s\n", lt_dlerror()); return; } /* POSIX version ******************************************************/ #elif defined(HAVE_DLFCN) #include void *xdlopen(const char *module) { void *h; h = dlopen(module, RTLD_NOW); if (h == NULL) lib_err_msg(dlerror()); return h; } void *xdlsym(void *h, const char *symbol) { void *ptr; xassert(h != NULL); ptr = dlsym(h, symbol); if (ptr == NULL) xerror("xdlsym: %s: %s\n", symbol, dlerror()); return ptr; } void xdlclose(void *h) { xassert(h != NULL); if (dlclose(h) != 0) xerror("xdlclose: %s\n", dlerror()); return; } /* Windows version ****************************************************/ #elif defined(__WOE__) #include void *xdlopen(const char *module) { void *h; h = LoadLibrary(module); if (h == NULL) { char msg[20]; sprintf(msg, "Error %d", GetLastError()); lib_err_msg(msg); } return h; } void *xdlsym(void *h, const char *symbol) { void *ptr; xassert(h != NULL); ptr = GetProcAddress(h, symbol); if (ptr == NULL) xerror("xdlsym: %s: Error %d\n", symbol, GetLastError()); return ptr; } void xdlclose(void *h) { xassert(h != NULL); if (!FreeLibrary(h)) xerror("xdlclose: Error %d\n", GetLastError()); return; } /* NULL version *******************************************************/ #else void *xdlopen(const char *module) { xassert(module == module); lib_err_msg("Shared libraries not supported"); return NULL; } void *xdlsym(void *h, const char *symbol) { xassert(h != h); xassert(symbol != symbol); return NULL; } void xdlclose(void *h) { xassert(h != h); return; } #endif /* eof */ sources_5316/external/glpk/amd_post_tree.c0000644000176700017670000001070511401660400017466 0ustar paulpaul/* ========================================================================= */ /* === AMD_post_tree ======================================================= */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* Post-ordering of a supernodal elimination tree. */ #include "amd_internal.h" GLOBAL Int AMD_post_tree ( Int root, /* root of the tree */ Int k, /* start numbering at k */ Int Child [ ], /* input argument of size nn, undefined on * output. Child [i] is the head of a link * list of all nodes that are children of node * i in the tree. */ const Int Sibling [ ], /* input argument of size nn, not modified. * If f is a node in the link list of the * children of node i, then Sibling [f] is the * next child of node i. */ Int Order [ ], /* output order, of size nn. Order [i] = k * if node i is the kth node of the reordered * tree. */ Int Stack [ ] /* workspace of size nn */ #ifndef NDEBUG , Int nn /* nodes are in the range 0..nn-1. */ #endif ) { Int f, head, h, i ; #if 0 /* --------------------------------------------------------------------- */ /* recursive version (Stack [ ] is not used): */ /* --------------------------------------------------------------------- */ /* this is simple, but can caouse stack overflow if nn is large */ i = root ; for (f = Child [i] ; f != EMPTY ; f = Sibling [f]) { k = AMD_post_tree (f, k, Child, Sibling, Order, Stack, nn) ; } Order [i] = k++ ; return (k) ; #endif /* --------------------------------------------------------------------- */ /* non-recursive version, using an explicit stack */ /* --------------------------------------------------------------------- */ /* push root on the stack */ head = 0 ; Stack [0] = root ; while (head >= 0) { /* get head of stack */ ASSERT (head < nn) ; i = Stack [head] ; AMD_DEBUG1 (("head of stack "ID" \n", i)) ; ASSERT (i >= 0 && i < nn) ; if (Child [i] != EMPTY) { /* the children of i are not yet ordered */ /* push each child onto the stack in reverse order */ /* so that small ones at the head of the list get popped first */ /* and the biggest one at the end of the list gets popped last */ for (f = Child [i] ; f != EMPTY ; f = Sibling [f]) { head++ ; ASSERT (head < nn) ; ASSERT (f >= 0 && f < nn) ; } h = head ; ASSERT (head < nn) ; for (f = Child [i] ; f != EMPTY ; f = Sibling [f]) { ASSERT (h > 0) ; Stack [h--] = f ; AMD_DEBUG1 (("push "ID" on stack\n", f)) ; ASSERT (f >= 0 && f < nn) ; } ASSERT (Stack [h] == i) ; /* delete child list so that i gets ordered next time we see it */ Child [i] = EMPTY ; } else { /* the children of i (if there were any) are already ordered */ /* remove i from the stack and order it. Front i is kth front */ head-- ; AMD_DEBUG1 (("pop "ID" order "ID"\n", i, k)) ; Order [i] = k++ ; ASSERT (k <= nn) ; } #ifndef NDEBUG AMD_DEBUG1 (("\nStack:")) ; for (h = head ; h >= 0 ; h--) { Int j = Stack [h] ; AMD_DEBUG1 ((" "ID, j)) ; ASSERT (j >= 0 && j < nn) ; } AMD_DEBUG1 (("\n\n")) ; ASSERT (head < nn) ; #endif } return (k) ; } sources_5316/external/glpk/glplib01.c0000644000176700017670000002257711401660400016265 0ustar paulpaul/* glplib01.c (bignum arithmetic) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glplib.h" /*********************************************************************** * Two routines below are intended to multiply and divide unsigned * integer numbers of arbitrary precision. * * The routines assume that an unsigned integer number is represented in * the positional numeral system with the base 2^16 = 65536, i.e. each * "digit" of the number is in the range [0, 65535] and represented as * a 16-bit value of the unsigned short type. In other words, a number x * has the following representation: * * n-1 * x = sum d[j] * 65536^j, * j=0 * * where n is the number of places (positions), and d[j] is j-th "digit" * of x, 0 <= d[j] <= 65535. ***********************************************************************/ /*********************************************************************** * NAME * * bigmul - multiply unsigned integer numbers of arbitrary precision * * SYNOPSIS * * #include "glplib.h" * void bigmul(int n, int m, unsigned short x[], unsigned short y[]); * * DESCRIPTION * * The routine bigmul multiplies unsigned integer numbers of arbitrary * precision. * * n is the number of digits of multiplicand, n >= 1; * * m is the number of digits of multiplier, m >= 1; * * x is an array containing digits of the multiplicand in elements * x[m], x[m+1], ..., x[n+m-1]. Contents of x[0], x[1], ..., x[m-1] are * ignored on entry. * * y is an array containing digits of the multiplier in elements y[0], * y[1], ..., y[m-1]. * * On exit digits of the product are stored in elements x[0], x[1], ..., * x[n+m-1]. The array y is not changed. */ void bigmul(int n, int m, unsigned short x[], unsigned short y[]) { int i, j; unsigned int t; xassert(n >= 1); xassert(m >= 1); for (j = 0; j < m; j++) x[j] = 0; for (i = 0; i < n; i++) { if (x[i+m]) { t = 0; for (j = 0; j < m; j++) { t += (unsigned int)x[i+m] * (unsigned int)y[j] + (unsigned int)x[i+j]; x[i+j] = (unsigned short)t; t >>= 16; } x[i+m] = (unsigned short)t; } } return; } /*********************************************************************** * NAME * * bigdiv - divide unsigned integer numbers of arbitrary precision * * SYNOPSIS * * #include "glplib.h" * void bigdiv(int n, int m, unsigned short x[], unsigned short y[]); * * DESCRIPTION * * The routine bigdiv divides one unsigned integer number of arbitrary * precision by another with the algorithm described in [1]. * * n is the difference between the number of digits of dividend and the * number of digits of divisor, n >= 0. * * m is the number of digits of divisor, m >= 1. * * x is an array containing digits of the dividend in elements x[0], * x[1], ..., x[n+m-1]. * * y is an array containing digits of the divisor in elements y[0], * y[1], ..., y[m-1]. The highest digit y[m-1] must be non-zero. * * On exit n+1 digits of the quotient are stored in elements x[m], * x[m+1], ..., x[n+m], and m digits of the remainder are stored in * elements x[0], x[1], ..., x[m-1]. The array y is changed but then * restored. * * REFERENCES * * 1. D. Knuth. The Art of Computer Programming. Vol. 2: Seminumerical * Algorithms. Stanford University, 1969. */ void bigdiv(int n, int m, unsigned short x[], unsigned short y[]) { int i, j; unsigned int t; unsigned short d, q, r; xassert(n >= 0); xassert(m >= 1); xassert(y[m-1] != 0); /* special case when divisor has the only digit */ if (m == 1) { d = 0; for (i = n; i >= 0; i--) { t = ((unsigned int)d << 16) + (unsigned int)x[i]; x[i+1] = (unsigned short)(t / y[0]); d = (unsigned short)(t % y[0]); } x[0] = d; goto done; } /* multiply dividend and divisor by a normalizing coefficient in order to provide the condition y[m-1] >= base / 2 */ d = (unsigned short)(0x10000 / ((unsigned int)y[m-1] + 1)); if (d == 1) x[n+m] = 0; else { t = 0; for (i = 0; i < n+m; i++) { t += (unsigned int)x[i] * (unsigned int)d; x[i] = (unsigned short)t; t >>= 16; } x[n+m] = (unsigned short)t; t = 0; for (j = 0; j < m; j++) { t += (unsigned int)y[j] * (unsigned int)d; y[j] = (unsigned short)t; t >>= 16; } } /* main loop */ for (i = n; i >= 0; i--) { /* estimate and correct the current digit of quotient */ if (x[i+m] < y[m-1]) { t = ((unsigned int)x[i+m] << 16) + (unsigned int)x[i+m-1]; q = (unsigned short)(t / (unsigned int)y[m-1]); r = (unsigned short)(t % (unsigned int)y[m-1]); if (q == 0) goto putq; else goto test; } q = 0; r = x[i+m-1]; decr: q--; /* if q = 0 then q-- = 0xFFFF */ t = (unsigned int)r + (unsigned int)y[m-1]; r = (unsigned short)t; if (t > 0xFFFF) goto msub; test: t = (unsigned int)y[m-2] * (unsigned int)q; if ((unsigned short)(t >> 16) > r) goto decr; if ((unsigned short)(t >> 16) < r) goto msub; if ((unsigned short)t > x[i+m-2]) goto decr; msub: /* now subtract divisor multiplied by the current digit of quotient from the current dividend */ if (q == 0) goto putq; t = 0; for (j = 0; j < m; j++) { t += (unsigned int)y[j] * (unsigned int)q; if (x[i+j] < (unsigned short)t) t += 0x10000; x[i+j] -= (unsigned short)t; t >>= 16; } if (x[i+m] >= (unsigned short)t) goto putq; /* perform correcting addition, because the current digit of quotient is greater by one than its correct value */ q--; t = 0; for (j = 0; j < m; j++) { t += (unsigned int)x[i+j] + (unsigned int)y[j]; x[i+j] = (unsigned short)t; t >>= 16; } putq: /* store the current digit of quotient */ x[i+m] = q; } /* divide divisor and remainder by the normalizing coefficient in order to restore their original values */ if (d > 1) { t = 0; for (i = m-1; i >= 0; i--) { t = (t << 16) + (unsigned int)x[i]; x[i] = (unsigned short)(t / (unsigned int)d); t %= (unsigned int)d; } t = 0; for (j = m-1; j >= 0; j--) { t = (t << 16) + (unsigned int)y[j]; y[j] = (unsigned short)(t / (unsigned int)d); t %= (unsigned int)d; } } done: return; } /**********************************************************************/ #if 0 #include #include #include #include "glprng.h" #define N_MAX 7 /* maximal number of digits in multiplicand */ #define M_MAX 5 /* maximal number of digits in multiplier */ #define N_TEST 1000000 /* number of tests */ int main(void) { RNG *rand; int d, j, n, m, test; unsigned short x[N_MAX], y[M_MAX], z[N_MAX+M_MAX]; rand = rng_create_rand(); for (test = 1; test <= N_TEST; test++) { /* x[0,...,n-1] := multiplicand */ n = 1 + rng_unif_rand(rand, N_MAX-1); assert(1 <= n && n <= N_MAX); for (j = 0; j < n; j++) { d = rng_unif_rand(rand, 65536); assert(0 <= d && d <= 65535); x[j] = (unsigned short)d; } /* y[0,...,m-1] := multiplier */ m = 1 + rng_unif_rand(rand, M_MAX-1); assert(1 <= m && m <= M_MAX); for (j = 0; j < m; j++) { d = rng_unif_rand(rand, 65536); assert(0 <= d && d <= 65535); y[j] = (unsigned short)d; } if (y[m-1] == 0) y[m-1] = 1; /* z[0,...,n+m-1] := x * y */ for (j = 0; j < n; j++) z[m+j] = x[j]; bigmul(n, m, z, y); /* z[0,...,m-1] := z mod y, z[m,...,n+m-1] := z div y */ bigdiv(n, m, z, y); /* z mod y must be 0 */ for (j = 0; j < m; j++) assert(z[j] == 0); /* z div y must be x */ for (j = 0; j < n; j++) assert(z[m+j] == x[j]); } fprintf(stderr, "%d tests successfully passed\n", N_TEST); rng_delete_rand(rand); return 0; } #endif /* eof */ sources_5316/external/glpk/glptsp.h0000644000176700017670000001051711401660400016160 0ustar paulpaul/* glptsp.h (TSP format) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPTSP_H #define GLPTSP_H typedef struct TSP TSP; struct TSP { /* TSP (or related problem) instance in the format described in the report [G.Reinelt, TSPLIB 95] */ /*--------------------------------------------------------------*/ /* the specification part */ char *name; /* identifies the data file */ int type; /* specifies the type of data: */ #define TSP_UNDEF 0 /* undefined */ #define TSP_TSP 1 /* symmetric TSP */ #define TSP_ATSP 2 /* asymmetric TSP */ #define TSP_TOUR 3 /* collection of tours */ char *comment; /* additional comments (usually the name of the contributor or creator of the problem instance is given here) */ int dimension; /* for a TSP or ATSP, the dimension is the number of its nodes for a TOUR it is the dimension of the corresponding problem */ int edge_weight_type; /* specifies how the edge weights (or distances) are given: */ #define TSP_UNDEF 0 /* undefined */ #define TSP_EXPLICIT 1 /* listed explicitly */ #define TSP_EUC_2D 2 /* Eucl. distances in 2-D */ #define TSP_CEIL_2D 3 /* Eucl. distances in 2-D rounded up */ #define TSP_GEO 4 /* geographical distances */ #define TSP_ATT 5 /* special distance function */ int edge_weight_format; /* describes the format of the edge weights if they are given explicitly: */ #define TSP_UNDEF 0 /* undefined */ #define TSP_FUNCTION 1 /* given by a function */ #define TSP_FULL_MATRIX 2 /* given by a full matrix */ #define TSP_UPPER_ROW 3 /* upper triangulat matrix (row-wise without diagonal entries) */ #define TSP_LOWER_DIAG_ROW 4 /* lower triangular matrix (row-wise including diagonal entries) */ int display_data_type; /* specifies how a graphical display of the nodes can be obtained: */ #define TSP_UNDEF 0 /* undefined */ #define TSP_COORD_DISPLAY 1 /* display is generated from the node coordinates */ #define TSP_TWOD_DISPLAY 2 /* explicit coordinates in 2-D are given */ /*--------------------------------------------------------------*/ /* data part */ /* NODE_COORD_SECTION: */ double *node_x_coord; /* double node_x_coord[1+dimension]; */ double *node_y_coord; /* double node_y_coord[1+dimension]; */ /* DISPLAY_DATA_SECTION: */ double *dply_x_coord; /* double dply_x_coord[1+dimension]; */ double *dply_y_coord; /* double dply_y_coord[1+dimension]; */ /* TOUR_SECTION: */ int *tour; /* int tour[1+dimension]; */ /* EDGE_WEIGHT_SECTION: */ int *edge_weight; /* int edge_weight[1+dimension*dimension]; */ }; #define tsp_read_data _glp_tsp_read_data #define tsp_free_data _glp_tsp_free_data #define tsp_distance _glp_tsp_distance TSP *tsp_read_data(char *fname); /* read TSP instance data */ void tsp_free_data(TSP *tsp); /* free TSP instance data */ int tsp_distance(TSP *tsp, int i, int j); /* compute distance between two nodes */ #endif /* eof */ sources_5316/external/glpk/glpenv03.c0000644000176700017670000001474111401660400016303 0ustar paulpaul/* glpenv03.c (terminal output) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_printf - write formatted output to terminal * * SYNOPSIS * * void glp_printf(const char *fmt, ...); * * DESCRIPTION * * The routine glp_printf uses the format control string fmt to format * its parameters and writes the formatted output to the terminal. */ void glp_printf(const char *fmt, ...) { va_list arg; va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); return; } /*********************************************************************** * NAME * * glp_vprintf - write formatted output to terminal * * SYNOPSIS * * void glp_vprintf(const char *fmt, va_list arg); * * DESCRIPTION * * The routine glp_vprintf uses the format control string fmt to format * its parameters specified by the list arg and writes the formatted * output to the terminal. */ void glp_vprintf(const char *fmt, va_list arg) { ENV *env = get_env_ptr(); /* if terminal output is disabled, do nothing */ if (!env->term_out) goto skip; /* format the output */ vsprintf(env->term_buf, fmt, arg); /* pass the output to the user-defined routine */ if (env->term_hook != NULL) { if (env->term_hook(env->term_info, env->term_buf) != 0) goto skip; } /* send the output to the terminal */ fputs(env->term_buf, stdout); fflush(stdout); /* copy the output to the text file */ if (env->tee_file != NULL) { fputs(env->term_buf, env->tee_file); fflush(env->tee_file); } skip: return; } /*********************************************************************** * NAME * * glp_term_out - enable/disable terminal output * * SYNOPSIS * * int glp_term_out(int flag); * * DESCRIPTION * * Depending on the parameter flag the routine glp_term_out enables or * disables terminal output performed by glpk routines: * * GLP_ON - enable terminal output; * GLP_OFF - disable terminal output. * * RETURNS * * The routine glp_term_out returns the previous value of the terminal * output flag. */ int glp_term_out(int flag) { ENV *env = get_env_ptr(); int old = env->term_out; if (!(flag == GLP_ON || flag == GLP_OFF)) xerror("glp_term_out: flag = %d; invalid value\n", flag); env->term_out = flag; return old; } /*********************************************************************** * NAME * * glp_term_hook - install hook to intercept terminal output * * SYNOPSIS * * void glp_term_hook(int (*func)(void *info, const char *s), * void *info); * * DESCRIPTION * * The routine glp_term_hook installs a user-defined hook routine to * intercept all terminal output performed by glpk routines. * * This feature can be used to redirect the terminal output to other * destination, for example to a file or a text window. * * The parameter func specifies the user-defined hook routine. It is * called from an internal printing routine, which passes to it two * parameters: info and s. The parameter info is a transit pointer, * specified in the corresponding call to the routine glp_term_hook; * it may be used to pass some information to the hook routine. The * parameter s is a pointer to the null terminated character string, * which is intended to be written to the terminal. If the hook routine * returns zero, the printing routine writes the string s to the * terminal in a usual way; otherwise, if the hook routine returns * non-zero, no terminal output is performed. * * To uninstall the hook routine the parameters func and info should be * specified as NULL. */ void glp_term_hook(int (*func)(void *info, const char *s), void *info) { ENV *env = get_env_ptr(); if (func == NULL) { env->term_hook = NULL; env->term_info = NULL; } else { env->term_hook = func; env->term_info = info; } return; } /*********************************************************************** * NAME * * glp_open_tee - start copying terminal output to text file * * SYNOPSIS * * int glp_open_tee(const char *fname); * * DESCRIPTION * * The routine glp_open_tee starts copying all the terminal output to * an output text file, whose name is specified by the character string * fname. * * RETURNS * * 0 - operation successful * 1 - copying terminal output is already active * 2 - unable to create output file */ int glp_open_tee(const char *fname) { ENV *env = get_env_ptr(); if (env->tee_file != NULL) { /* copying terminal output is already active */ return 1; } env->tee_file = fopen(fname, "w"); if (env->tee_file == NULL) { /* unable to create output file */ return 2; } return 0; } /*********************************************************************** * NAME * * glp_close_tee - stop copying terminal output to text file * * SYNOPSIS * * int glp_close_tee(void); * * DESCRIPTION * * The routine glp_close_tee stops copying the terminal output to the * output text file previously open by the routine glp_open_tee closing * that file. * * RETURNS * * 0 - operation successful * 1 - copying terminal output was not started */ int glp_close_tee(void) { ENV *env = get_env_ptr(); if (env->tee_file == NULL) { /* copying terminal output was not started */ return 1; } fclose(env->tee_file); env->tee_file = NULL; return 0; } /* eof */ sources_5316/external/glpk/glpstd.h0000644000176700017670000000254611401660400016147 0ustar paulpaul/* glpstd.h (standard C headers) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPSTD_H #define GLPSTD_H #include #include #include #include #include #include #include #include #include #include #include #include #endif /* eof */ sources_5316/external/glpk/glpenv01.c0000644000176700017670000001637211401660400016303 0ustar paulpaul/* glpenv01.c (environment initialization/termination) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_init_env - initialize GLPK environment * * SYNOPSIS * * int glp_init_env(void); * * DESCRIPTION * * The routine glp_init_env initializes the GLPK environment. Normally * the application program does not need to call this routine, because * it is called automatically on the first call to any API routine. * * RETURNS * * The routine glp_init_env returns one of the following codes: * * 0 - initialization successful; * 1 - environment has been already initialized; * 2 - initialization failed (insufficient memory); * 3 - initialization failed (unsupported programming model). */ int glp_init_env(void) { ENV *env; int ok; /* check if the programming model is supported */ ok = (CHAR_BIT == 8 && sizeof(char) == 1 && sizeof(short) == 2 && sizeof(int) == 4 && (sizeof(void *) == 4 || sizeof(void *) == 8)); if (!ok) return 3; /* check if the environment is already initialized */ if (tls_get_ptr() != NULL) return 1; /* allocate and initialize the environment block */ env = malloc(sizeof(ENV)); if (env == NULL) return 2; env->magic = ENV_MAGIC; sprintf(env->version, "%d.%d", GLP_MAJOR_VERSION, GLP_MINOR_VERSION); env->term_buf = malloc(TERM_BUF_SIZE); if (env->term_buf == NULL) { free(env); return 2; } env->term_out = GLP_ON; env->term_hook = NULL; env->term_info = NULL; env->tee_file = NULL; env->err_file = ""; env->err_line = 0; env->err_hook = NULL; env->err_info = NULL; env->mem_limit.hi = 0x7FFFFFFF, env->mem_limit.lo = 0xFFFFFFFF; env->mem_ptr = NULL; env->mem_count = env->mem_cpeak = 0; env->mem_total = env->mem_tpeak = xlset(0); env->file_ptr = NULL; env->ioerr_msg = malloc(IOERR_MSG_SIZE); if (env->ioerr_msg == NULL) { free(env->term_buf); free(env); return 2; } strcpy(env->ioerr_msg, "No error"); env->h_odbc = env->h_mysql = NULL; /* save pointer to the environment block */ tls_set_ptr(env); /* initialization successful */ return 0; } /*********************************************************************** * NAME * * get_env_ptr - retrieve pointer to environment block * * SYNOPSIS * * #include "glpenv.h" * ENV *get_env_ptr(void); * * DESCRIPTION * * The routine get_env_ptr retrieves and returns a pointer to the GLPK * environment block. * * If the GLPK environment has not been initialized yet, the routine * performs initialization. If initialization fails, the routine prints * an error message to stderr and terminates the program. * * RETURNS * * The routine returns a pointer to the environment block. */ ENV *get_env_ptr(void) { ENV *env = tls_get_ptr(); /* check if the environment has been initialized */ if (env == NULL) { /* not initialized yet; perform initialization */ if (glp_init_env() != 0) { /* initialization failed; display an error message */ fprintf(stderr, "GLPK initialization failed\n"); fflush(stderr); /* and abnormally terminate the program */ abort(); } /* initialization successful; retrieve the pointer */ env = tls_get_ptr(); } /* check if the environment block is valid */ if (env->magic != ENV_MAGIC) { fprintf(stderr, "Invalid GLPK environment\n"); fflush(stderr); abort(); } return env; } /*********************************************************************** * NAME * * glp_version - determine library version * * SYNOPSIS * * const char *glp_version(void); * * RETURNS * * The routine glp_version returns a pointer to a null-terminated * character string, which specifies the version of the GLPK library in * the form "X.Y", where X is the major version number, and Y is the * minor version number, for example, "4.16". */ const char *glp_version(void) { ENV *env = get_env_ptr(); return env->version; } /*********************************************************************** * NAME * * glp_free_env - free GLPK environment * * SYNOPSIS * * int glp_free_env(void); * * DESCRIPTION * * The routine glp_free_env frees all resources used by GLPK routines * (memory blocks, etc.) which are currently still in use. * * Normally the application program does not need to call this routine, * because GLPK routines always free all unused resources. However, if * the application program even has deleted all problem objects, there * will be several memory blocks still allocated for the library needs. * For some reasons the application program may want GLPK to free this * memory, in which case it should call glp_free_env. * * Note that a call to glp_free_env invalidates all problem objects as * if no GLPK routine were called. * * RETURNS * * 0 - termination successful; * 1 - environment is inactive (was not initialized). */ int glp_free_env(void) { ENV *env = tls_get_ptr(); MEM *desc; /* check if the environment is active */ if (env == NULL) return 1; /* check if the environment block is valid */ if (env->magic != ENV_MAGIC) { fprintf(stderr, "Invalid GLPK environment\n"); fflush(stderr); abort(); } /* close handles to shared libraries */ if (env->h_odbc != NULL) xdlclose(env->h_odbc); if (env->h_mysql != NULL) xdlclose(env->h_mysql); /* close streams which are still open */ while (env->file_ptr != NULL) xfclose(env->file_ptr); /* free memory blocks which are still allocated */ while (env->mem_ptr != NULL) { desc = env->mem_ptr; env->mem_ptr = desc->next; free(desc); } /* invalidate the environment block */ env->magic = -1; /* free memory allocated to the environment block */ free(env->term_buf); free(env->ioerr_msg); free(env); /* reset a pointer to the environment block */ tls_set_ptr(NULL); /* termination successful */ return 0; } /* eof */ sources_5316/external/glpk/glpapi12.c0000644000176700017670000023513211401660400016263 0ustar paulpaul/* glpapi12.c (basis factorization and simplex tableau routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_bf_exists - check if the basis factorization exists * * SYNOPSIS * * int glp_bf_exists(glp_prob *lp); * * RETURNS * * If the basis factorization for the current basis associated with * the specified problem object exists and therefore is available for * computations, the routine glp_bf_exists returns non-zero. Otherwise * the routine returns zero. */ int glp_bf_exists(glp_prob *lp) { int ret; ret = (lp->m == 0 || lp->valid); return ret; } /*********************************************************************** * NAME * * glp_factorize - compute the basis factorization * * SYNOPSIS * * int glp_factorize(glp_prob *lp); * * DESCRIPTION * * The routine glp_factorize computes the basis factorization for the * current basis associated with the specified problem object. * * RETURNS * * 0 The basis factorization has been successfully computed. * * GLP_EBADB * The basis matrix is invalid, i.e. the number of basic (auxiliary * and structural) variables differs from the number of rows in the * problem object. * * GLP_ESING * The basis matrix is singular within the working precision. * * GLP_ECOND * The basis matrix is ill-conditioned. */ static int b_col(void *info, int j, int ind[], double val[]) { glp_prob *lp = info; int m = lp->m; GLPAIJ *aij; int k, len; xassert(1 <= j && j <= m); /* determine the ordinal number of basic auxiliary or structural variable x[k] corresponding to basic variable xB[j] */ k = lp->head[j]; /* build j-th column of the basic matrix, which is k-th column of the scaled augmented matrix (I | -R*A*S) */ if (k <= m) { /* x[k] is auxiliary variable */ len = 1; ind[1] = k; val[1] = 1.0; } else { /* x[k] is structural variable */ len = 0; for (aij = lp->col[k-m]->ptr; aij != NULL; aij = aij->c_next) { len++; ind[len] = aij->row->i; val[len] = - aij->row->rii * aij->val * aij->col->sjj; } } return len; } static void copy_bfcp(glp_prob *lp); int glp_factorize(glp_prob *lp) { int m = lp->m; int n = lp->n; GLPROW **row = lp->row; GLPCOL **col = lp->col; int *head = lp->head; int j, k, stat, ret; /* invalidate the basis factorization */ lp->valid = 0; /* build the basis header */ j = 0; for (k = 1; k <= m+n; k++) { if (k <= m) { stat = row[k]->stat; row[k]->bind = 0; } else { stat = col[k-m]->stat; col[k-m]->bind = 0; } if (stat == GLP_BS) { j++; if (j > m) { /* too many basic variables */ ret = GLP_EBADB; goto fini; } head[j] = k; if (k <= m) row[k]->bind = j; else col[k-m]->bind = j; } } if (j < m) { /* too few basic variables */ ret = GLP_EBADB; goto fini; } /* try to factorize the basis matrix */ if (m > 0) { if (lp->bfd == NULL) { lp->bfd = bfd_create_it(); copy_bfcp(lp); } switch (bfd_factorize(lp->bfd, m, lp->head, b_col, lp)) { case 0: /* ok */ break; case BFD_ESING: /* singular matrix */ ret = GLP_ESING; goto fini; case BFD_ECOND: /* ill-conditioned matrix */ ret = GLP_ECOND; goto fini; default: xassert(lp != lp); } lp->valid = 1; } /* factorization successful */ ret = 0; fini: /* bring the return code to the calling program */ return ret; } /*********************************************************************** * NAME * * glp_bf_updated - check if the basis factorization has been updated * * SYNOPSIS * * int glp_bf_updated(glp_prob *lp); * * RETURNS * * If the basis factorization has been just computed from scratch, the * routine glp_bf_updated returns zero. Otherwise, if the factorization * has been updated one or more times, the routine returns non-zero. */ int glp_bf_updated(glp_prob *lp) { int cnt; if (!(lp->m == 0 || lp->valid)) xerror("glp_bf_update: basis factorization does not exist\n"); #if 0 /* 15/XI-2009 */ cnt = (lp->m == 0 ? 0 : lp->bfd->upd_cnt); #else cnt = (lp->m == 0 ? 0 : bfd_get_count(lp->bfd)); #endif return cnt; } /*********************************************************************** * NAME * * glp_get_bfcp - retrieve basis factorization control parameters * * SYNOPSIS * * void glp_get_bfcp(glp_prob *lp, glp_bfcp *parm); * * DESCRIPTION * * The routine glp_get_bfcp retrieves control parameters, which are * used on computing and updating the basis factorization associated * with the specified problem object. * * Current values of control parameters are stored by the routine in * a glp_bfcp structure, which the parameter parm points to. */ void glp_get_bfcp(glp_prob *lp, glp_bfcp *parm) { glp_bfcp *bfcp = lp->bfcp; if (bfcp == NULL) { parm->type = GLP_BF_FT; parm->lu_size = 0; parm->piv_tol = 0.10; parm->piv_lim = 4; parm->suhl = GLP_ON; parm->eps_tol = 1e-15; parm->max_gro = 1e+10; parm->nfs_max = 100; parm->upd_tol = 1e-6; parm->nrs_max = 100; parm->rs_size = 0; } else memcpy(parm, bfcp, sizeof(glp_bfcp)); return; } /*********************************************************************** * NAME * * glp_set_bfcp - change basis factorization control parameters * * SYNOPSIS * * void glp_set_bfcp(glp_prob *lp, const glp_bfcp *parm); * * DESCRIPTION * * The routine glp_set_bfcp changes control parameters, which are used * by internal GLPK routines in computing and updating the basis * factorization associated with the specified problem object. * * New values of the control parameters should be passed in a structure * glp_bfcp, which the parameter parm points to. * * The parameter parm can be specified as NULL, in which case all * control parameters are reset to their default values. */ #if 0 /* 15/XI-2009 */ static void copy_bfcp(glp_prob *lp) { glp_bfcp _parm, *parm = &_parm; BFD *bfd = lp->bfd; glp_get_bfcp(lp, parm); xassert(bfd != NULL); bfd->type = parm->type; bfd->lu_size = parm->lu_size; bfd->piv_tol = parm->piv_tol; bfd->piv_lim = parm->piv_lim; bfd->suhl = parm->suhl; bfd->eps_tol = parm->eps_tol; bfd->max_gro = parm->max_gro; bfd->nfs_max = parm->nfs_max; bfd->upd_tol = parm->upd_tol; bfd->nrs_max = parm->nrs_max; bfd->rs_size = parm->rs_size; return; } #else static void copy_bfcp(glp_prob *lp) { glp_bfcp _parm, *parm = &_parm; glp_get_bfcp(lp, parm); bfd_set_parm(lp->bfd, parm); return; } #endif void glp_set_bfcp(glp_prob *lp, const glp_bfcp *parm) { glp_bfcp *bfcp = lp->bfcp; if (parm == NULL) { /* reset to default values */ if (bfcp != NULL) xfree(bfcp), lp->bfcp = NULL; } else { /* set to specified values */ if (bfcp == NULL) bfcp = lp->bfcp = xmalloc(sizeof(glp_bfcp)); memcpy(bfcp, parm, sizeof(glp_bfcp)); if (!(bfcp->type == GLP_BF_FT || bfcp->type == GLP_BF_BG || bfcp->type == GLP_BF_GR)) xerror("glp_set_bfcp: type = %d; invalid parameter\n", bfcp->type); if (bfcp->lu_size < 0) xerror("glp_set_bfcp: lu_size = %d; invalid parameter\n", bfcp->lu_size); if (!(0.0 < bfcp->piv_tol && bfcp->piv_tol < 1.0)) xerror("glp_set_bfcp: piv_tol = %g; invalid parameter\n", bfcp->piv_tol); if (bfcp->piv_lim < 1) xerror("glp_set_bfcp: piv_lim = %d; invalid parameter\n", bfcp->piv_lim); if (!(bfcp->suhl == GLP_ON || bfcp->suhl == GLP_OFF)) xerror("glp_set_bfcp: suhl = %d; invalid parameter\n", bfcp->suhl); if (!(0.0 <= bfcp->eps_tol && bfcp->eps_tol <= 1e-6)) xerror("glp_set_bfcp: eps_tol = %g; invalid parameter\n", bfcp->eps_tol); if (bfcp->max_gro < 1.0) xerror("glp_set_bfcp: max_gro = %g; invalid parameter\n", bfcp->max_gro); if (!(1 <= bfcp->nfs_max && bfcp->nfs_max <= 32767)) xerror("glp_set_bfcp: nfs_max = %d; invalid parameter\n", bfcp->nfs_max); if (!(0.0 < bfcp->upd_tol && bfcp->upd_tol < 1.0)) xerror("glp_set_bfcp: upd_tol = %g; invalid parameter\n", bfcp->upd_tol); if (!(1 <= bfcp->nrs_max && bfcp->nrs_max <= 32767)) xerror("glp_set_bfcp: nrs_max = %d; invalid parameter\n", bfcp->nrs_max); if (bfcp->rs_size < 0) xerror("glp_set_bfcp: rs_size = %d; invalid parameter\n", bfcp->nrs_max); if (bfcp->rs_size == 0) bfcp->rs_size = 20 * bfcp->nrs_max; } if (lp->bfd != NULL) copy_bfcp(lp); return; } /*********************************************************************** * NAME * * glp_get_bhead - retrieve the basis header information * * SYNOPSIS * * int glp_get_bhead(glp_prob *lp, int k); * * DESCRIPTION * * The routine glp_get_bhead returns the basis header information for * the current basis associated with the specified problem object. * * RETURNS * * If xB[k], 1 <= k <= m, is i-th auxiliary variable (1 <= i <= m), the * routine returns i. Otherwise, if xB[k] is j-th structural variable * (1 <= j <= n), the routine returns m+j. Here m is the number of rows * and n is the number of columns in the problem object. */ int glp_get_bhead(glp_prob *lp, int k) { if (!(lp->m == 0 || lp->valid)) xerror("glp_get_bhead: basis factorization does not exist\n"); if (!(1 <= k && k <= lp->m)) xerror("glp_get_bhead: k = %d; index out of range\n", k); return lp->head[k]; } /*********************************************************************** * NAME * * glp_get_row_bind - retrieve row index in the basis header * * SYNOPSIS * * int glp_get_row_bind(glp_prob *lp, int i); * * RETURNS * * The routine glp_get_row_bind returns the index k of basic variable * xB[k], 1 <= k <= m, which is i-th auxiliary variable, 1 <= i <= m, * in the current basis associated with the specified problem object, * where m is the number of rows. However, if i-th auxiliary variable * is non-basic, the routine returns zero. */ int glp_get_row_bind(glp_prob *lp, int i) { if (!(lp->m == 0 || lp->valid)) xerror("glp_get_row_bind: basis factorization does not exist\n" ); if (!(1 <= i && i <= lp->m)) xerror("glp_get_row_bind: i = %d; row number out of range\n", i); return lp->row[i]->bind; } /*********************************************************************** * NAME * * glp_get_col_bind - retrieve column index in the basis header * * SYNOPSIS * * int glp_get_col_bind(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_col_bind returns the index k of basic variable * xB[k], 1 <= k <= m, which is j-th structural variable, 1 <= j <= n, * in the current basis associated with the specified problem object, * where m is the number of rows, n is the number of columns. However, * if j-th structural variable is non-basic, the routine returns zero.*/ int glp_get_col_bind(glp_prob *lp, int j) { if (!(lp->m == 0 || lp->valid)) xerror("glp_get_col_bind: basis factorization does not exist\n" ); if (!(1 <= j && j <= lp->n)) xerror("glp_get_col_bind: j = %d; column number out of range\n" , j); return lp->col[j]->bind; } /*********************************************************************** * NAME * * glp_ftran - perform forward transformation (solve system B*x = b) * * SYNOPSIS * * void glp_ftran(glp_prob *lp, double x[]); * * DESCRIPTION * * The routine glp_ftran performs forward transformation, i.e. solves * the system B*x = b, where B is the basis matrix corresponding to the * current basis for the specified problem object, x is the vector of * unknowns to be computed, b is the vector of right-hand sides. * * On entry elements of the vector b should be stored in dense format * in locations x[1], ..., x[m], where m is the number of rows. On exit * the routine stores elements of the vector x in the same locations. * * SCALING/UNSCALING * * Let A~ = (I | -A) is the augmented constraint matrix of the original * (unscaled) problem. In the scaled LP problem instead the matrix A the * scaled matrix A" = R*A*S is actually used, so * * A~" = (I | A") = (I | R*A*S) = (R*I*inv(R) | R*A*S) = * (1) * = R*(I | A)*S~ = R*A~*S~, * * is the scaled augmented constraint matrix, where R and S are diagonal * scaling matrices used to scale rows and columns of the matrix A, and * * S~ = diag(inv(R) | S) (2) * * is an augmented diagonal scaling matrix. * * By definition: * * A~ = (B | N), (3) * * where B is the basic matrix, which consists of basic columns of the * augmented constraint matrix A~, and N is a matrix, which consists of * non-basic columns of A~. From (1) it follows that: * * A~" = (B" | N") = (R*B*SB | R*N*SN), (4) * * where SB and SN are parts of the augmented scaling matrix S~, which * correspond to basic and non-basic variables, respectively. Therefore * * B" = R*B*SB, (5) * * which is the scaled basis matrix. */ void glp_ftran(glp_prob *lp, double x[]) { int m = lp->m; GLPROW **row = lp->row; GLPCOL **col = lp->col; int i, k; /* B*x = b ===> (R*B*SB)*(inv(SB)*x) = R*b ===> B"*x" = b", where b" = R*b, x = SB*x" */ if (!(m == 0 || lp->valid)) xerror("glp_ftran: basis factorization does not exist\n"); /* b" := R*b */ for (i = 1; i <= m; i++) x[i] *= row[i]->rii; /* x" := inv(B")*b" */ if (m > 0) bfd_ftran(lp->bfd, x); /* x := SB*x" */ for (i = 1; i <= m; i++) { k = lp->head[i]; if (k <= m) x[i] /= row[k]->rii; else x[i] *= col[k-m]->sjj; } return; } /*********************************************************************** * NAME * * glp_btran - perform backward transformation (solve system B'*x = b) * * SYNOPSIS * * void glp_btran(glp_prob *lp, double x[]); * * DESCRIPTION * * The routine glp_btran performs backward transformation, i.e. solves * the system B'*x = b, where B' is a matrix transposed to the basis * matrix corresponding to the current basis for the specified problem * problem object, x is the vector of unknowns to be computed, b is the * vector of right-hand sides. * * On entry elements of the vector b should be stored in dense format * in locations x[1], ..., x[m], where m is the number of rows. On exit * the routine stores elements of the vector x in the same locations. * * SCALING/UNSCALING * * See comments to the routine glp_ftran. */ void glp_btran(glp_prob *lp, double x[]) { int m = lp->m; GLPROW **row = lp->row; GLPCOL **col = lp->col; int i, k; /* B'*x = b ===> (SB*B'*R)*(inv(R)*x) = SB*b ===> (B")'*x" = b", where b" = SB*b, x = R*x" */ if (!(m == 0 || lp->valid)) xerror("glp_btran: basis factorization does not exist\n"); /* b" := SB*b */ for (i = 1; i <= m; i++) { k = lp->head[i]; if (k <= m) x[i] /= row[k]->rii; else x[i] *= col[k-m]->sjj; } /* x" := inv[(B")']*b" */ if (m > 0) bfd_btran(lp->bfd, x); /* x := R*x" */ for (i = 1; i <= m; i++) x[i] *= row[i]->rii; return; } /*********************************************************************** * NAME * * glp_warm_up - "warm up" LP basis * * SYNOPSIS * * int glp_warm_up(glp_prob *P); * * DESCRIPTION * * The routine glp_warm_up "warms up" the LP basis for the specified * problem object using current statuses assigned to rows and columns * (that is, to auxiliary and structural variables). * * This operation includes computing factorization of the basis matrix * (if it does not exist), computing primal and dual components of basic * solution, and determining the solution status. * * RETURNS * * 0 The operation has been successfully performed. * * GLP_EBADB * The basis matrix is invalid, i.e. the number of basic (auxiliary * and structural) variables differs from the number of rows in the * problem object. * * GLP_ESING * The basis matrix is singular within the working precision. * * GLP_ECOND * The basis matrix is ill-conditioned. */ int glp_warm_up(glp_prob *P) { GLPROW *row; GLPCOL *col; GLPAIJ *aij; int i, j, type, ret; double eps, temp, *work; /* invalidate basic solution */ P->pbs_stat = P->dbs_stat = GLP_UNDEF; P->obj_val = 0.0; P->some = 0; for (i = 1; i <= P->m; i++) { row = P->row[i]; row->prim = row->dual = 0.0; } for (j = 1; j <= P->n; j++) { col = P->col[j]; col->prim = col->dual = 0.0; } /* compute the basis factorization, if necessary */ if (!glp_bf_exists(P)) { ret = glp_factorize(P); if (ret != 0) goto done; } /* allocate working array */ work = xcalloc(1+P->m, sizeof(double)); /* determine and store values of non-basic variables, compute vector (- N * xN) */ for (i = 1; i <= P->m; i++) work[i] = 0.0; for (i = 1; i <= P->m; i++) { row = P->row[i]; if (row->stat == GLP_BS) continue; else if (row->stat == GLP_NL) row->prim = row->lb; else if (row->stat == GLP_NU) row->prim = row->ub; else if (row->stat == GLP_NF) row->prim = 0.0; else if (row->stat == GLP_NS) row->prim = row->lb; else xassert(row != row); /* N[j] is i-th column of matrix (I|-A) */ work[i] -= row->prim; } for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->stat == GLP_BS) continue; else if (col->stat == GLP_NL) col->prim = col->lb; else if (col->stat == GLP_NU) col->prim = col->ub; else if (col->stat == GLP_NF) col->prim = 0.0; else if (col->stat == GLP_NS) col->prim = col->lb; else xassert(col != col); /* N[j] is (m+j)-th column of matrix (I|-A) */ if (col->prim != 0.0) { for (aij = col->ptr; aij != NULL; aij = aij->c_next) work[aij->row->i] += aij->val * col->prim; } } /* compute vector of basic variables xB = - inv(B) * N * xN */ glp_ftran(P, work); /* store values of basic variables, check primal feasibility */ P->pbs_stat = GLP_FEAS; for (i = 1; i <= P->m; i++) { row = P->row[i]; if (row->stat != GLP_BS) continue; row->prim = work[row->bind]; type = row->type; if (type == GLP_LO || type == GLP_DB || type == GLP_FX) { eps = 1e-6 + 1e-9 * fabs(row->lb); if (row->prim < row->lb - eps) P->pbs_stat = GLP_INFEAS; } if (type == GLP_UP || type == GLP_DB || type == GLP_FX) { eps = 1e-6 + 1e-9 * fabs(row->ub); if (row->prim > row->ub + eps) P->pbs_stat = GLP_INFEAS; } } for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->stat != GLP_BS) continue; col->prim = work[col->bind]; type = col->type; if (type == GLP_LO || type == GLP_DB || type == GLP_FX) { eps = 1e-6 + 1e-9 * fabs(col->lb); if (col->prim < col->lb - eps) P->pbs_stat = GLP_INFEAS; } if (type == GLP_UP || type == GLP_DB || type == GLP_FX) { eps = 1e-6 + 1e-9 * fabs(col->ub); if (col->prim > col->ub + eps) P->pbs_stat = GLP_INFEAS; } } /* compute value of the objective function */ P->obj_val = P->c0; for (j = 1; j <= P->n; j++) { col = P->col[j]; P->obj_val += col->coef * col->prim; } /* build vector cB of objective coefficients at basic variables */ for (i = 1; i <= P->m; i++) work[i] = 0.0; for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->stat == GLP_BS) work[col->bind] = col->coef; } /* compute vector of simplex multipliers pi = inv(B') * cB */ glp_btran(P, work); /* compute and store reduced costs of non-basic variables d[j] = c[j] - N'[j] * pi, check dual feasibility */ P->dbs_stat = GLP_FEAS; for (i = 1; i <= P->m; i++) { row = P->row[i]; if (row->stat == GLP_BS) { row->dual = 0.0; continue; } /* N[j] is i-th column of matrix (I|-A) */ row->dual = - work[i]; type = row->type; temp = (P->dir == GLP_MIN ? + row->dual : - row->dual); if ((type == GLP_FR || type == GLP_LO) && temp < -1e-5 || (type == GLP_FR || type == GLP_UP) && temp > +1e-5) P->dbs_stat = GLP_INFEAS; } for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->stat == GLP_BS) { col->dual = 0.0; continue; } /* N[j] is (m+j)-th column of matrix (I|-A) */ col->dual = col->coef; for (aij = col->ptr; aij != NULL; aij = aij->c_next) col->dual += aij->val * work[aij->row->i]; type = col->type; temp = (P->dir == GLP_MIN ? + col->dual : - col->dual); if ((type == GLP_FR || type == GLP_LO) && temp < -1e-5 || (type == GLP_FR || type == GLP_UP) && temp > +1e-5) P->dbs_stat = GLP_INFEAS; } /* free working array */ xfree(work); ret = 0; done: return ret; } /*********************************************************************** * NAME * * glp_eval_tab_row - compute row of the simplex tableau * * SYNOPSIS * * int glp_eval_tab_row(glp_prob *lp, int k, int ind[], double val[]); * * DESCRIPTION * * The routine glp_eval_tab_row computes a row of the current simplex * tableau for the basic variable, which is specified by the number k: * if 1 <= k <= m, x[k] is k-th auxiliary variable; if m+1 <= k <= m+n, * x[k] is (k-m)-th structural variable, where m is number of rows, and * n is number of columns. The current basis must be available. * * The routine stores column indices and numerical values of non-zero * elements of the computed row using sparse format to the locations * ind[1], ..., ind[len] and val[1], ..., val[len], respectively, where * 0 <= len <= n is number of non-zeros returned on exit. * * Element indices stored in the array ind have the same sense as the * index k, i.e. indices 1 to m denote auxiliary variables and indices * m+1 to m+n denote structural ones (all these variables are obviously * non-basic by definition). * * The computed row shows how the specified basic variable x[k] = xB[i] * depends on non-basic variables: * * xB[i] = alfa[i,1]*xN[1] + alfa[i,2]*xN[2] + ... + alfa[i,n]*xN[n], * * where alfa[i,j] are elements of the simplex table row, xN[j] are * non-basic (auxiliary and structural) variables. * * RETURNS * * The routine returns number of non-zero elements in the simplex table * row stored in the arrays ind and val. * * BACKGROUND * * The system of equality constraints of the LP problem is: * * xR = A * xS, (1) * * where xR is the vector of auxliary variables, xS is the vector of * structural variables, A is the matrix of constraint coefficients. * * The system (1) can be written in homogenous form as follows: * * A~ * x = 0, (2) * * where A~ = (I | -A) is the augmented constraint matrix (has m rows * and m+n columns), x = (xR | xS) is the vector of all (auxiliary and * structural) variables. * * By definition for the current basis we have: * * A~ = (B | N), (3) * * where B is the basis matrix. Thus, the system (2) can be written as: * * B * xB + N * xN = 0. (4) * * From (4) it follows that: * * xB = A^ * xN, (5) * * where the matrix * * A^ = - inv(B) * N (6) * * is called the simplex table. * * It is understood that i-th row of the simplex table is: * * e * A^ = - e * inv(B) * N, (7) * * where e is a unity vector with e[i] = 1. * * To compute i-th row of the simplex table the routine first computes * i-th row of the inverse: * * rho = inv(B') * e, (8) * * where B' is a matrix transposed to B, and then computes elements of * i-th row of the simplex table as scalar products: * * alfa[i,j] = - rho * N[j] for all j, (9) * * where N[j] is a column of the augmented constraint matrix A~, which * corresponds to some non-basic auxiliary or structural variable. */ int glp_eval_tab_row(glp_prob *lp, int k, int ind[], double val[]) { int m = lp->m; int n = lp->n; int i, t, len, lll, *iii; double alfa, *rho, *vvv; if (!(m == 0 || lp->valid)) xerror("glp_eval_tab_row: basis factorization does not exist\n" ); if (!(1 <= k && k <= m+n)) xerror("glp_eval_tab_row: k = %d; variable number out of range" , k); /* determine xB[i] which corresponds to x[k] */ if (k <= m) i = glp_get_row_bind(lp, k); else i = glp_get_col_bind(lp, k-m); if (i == 0) xerror("glp_eval_tab_row: k = %d; variable must be basic", k); xassert(1 <= i && i <= m); /* allocate working arrays */ rho = xcalloc(1+m, sizeof(double)); iii = xcalloc(1+m, sizeof(int)); vvv = xcalloc(1+m, sizeof(double)); /* compute i-th row of the inverse; see (8) */ for (t = 1; t <= m; t++) rho[t] = 0.0; rho[i] = 1.0; glp_btran(lp, rho); /* compute i-th row of the simplex table */ len = 0; for (k = 1; k <= m+n; k++) { if (k <= m) { /* x[k] is auxiliary variable, so N[k] is a unity column */ if (glp_get_row_stat(lp, k) == GLP_BS) continue; /* compute alfa[i,j]; see (9) */ alfa = - rho[k]; } else { /* x[k] is structural variable, so N[k] is a column of the original constraint matrix A with negative sign */ if (glp_get_col_stat(lp, k-m) == GLP_BS) continue; /* compute alfa[i,j]; see (9) */ lll = glp_get_mat_col(lp, k-m, iii, vvv); alfa = 0.0; for (t = 1; t <= lll; t++) alfa += rho[iii[t]] * vvv[t]; } /* store alfa[i,j] */ if (alfa != 0.0) len++, ind[len] = k, val[len] = alfa; } xassert(len <= n); /* free working arrays */ xfree(rho); xfree(iii); xfree(vvv); /* return to the calling program */ return len; } /*********************************************************************** * NAME * * glp_eval_tab_col - compute column of the simplex tableau * * SYNOPSIS * * int glp_eval_tab_col(glp_prob *lp, int k, int ind[], double val[]); * * DESCRIPTION * * The routine glp_eval_tab_col computes a column of the current simplex * table for the non-basic variable, which is specified by the number k: * if 1 <= k <= m, x[k] is k-th auxiliary variable; if m+1 <= k <= m+n, * x[k] is (k-m)-th structural variable, where m is number of rows, and * n is number of columns. The current basis must be available. * * The routine stores row indices and numerical values of non-zero * elements of the computed column using sparse format to the locations * ind[1], ..., ind[len] and val[1], ..., val[len] respectively, where * 0 <= len <= m is number of non-zeros returned on exit. * * Element indices stored in the array ind have the same sense as the * index k, i.e. indices 1 to m denote auxiliary variables and indices * m+1 to m+n denote structural ones (all these variables are obviously * basic by the definition). * * The computed column shows how basic variables depend on the specified * non-basic variable x[k] = xN[j]: * * xB[1] = ... + alfa[1,j]*xN[j] + ... * xB[2] = ... + alfa[2,j]*xN[j] + ... * . . . . . . * xB[m] = ... + alfa[m,j]*xN[j] + ... * * where alfa[i,j] are elements of the simplex table column, xB[i] are * basic (auxiliary and structural) variables. * * RETURNS * * The routine returns number of non-zero elements in the simplex table * column stored in the arrays ind and val. * * BACKGROUND * * As it was explained in comments to the routine glp_eval_tab_row (see * above) the simplex table is the following matrix: * * A^ = - inv(B) * N. (1) * * Therefore j-th column of the simplex table is: * * A^ * e = - inv(B) * N * e = - inv(B) * N[j], (2) * * where e is a unity vector with e[j] = 1, B is the basis matrix, N[j] * is a column of the augmented constraint matrix A~, which corresponds * to the given non-basic auxiliary or structural variable. */ int glp_eval_tab_col(glp_prob *lp, int k, int ind[], double val[]) { int m = lp->m; int n = lp->n; int t, len, stat; double *col; if (!(m == 0 || lp->valid)) xerror("glp_eval_tab_col: basis factorization does not exist\n" ); if (!(1 <= k && k <= m+n)) xerror("glp_eval_tab_col: k = %d; variable number out of range" , k); if (k <= m) stat = glp_get_row_stat(lp, k); else stat = glp_get_col_stat(lp, k-m); if (stat == GLP_BS) xerror("glp_eval_tab_col: k = %d; variable must be non-basic", k); /* obtain column N[k] with negative sign */ col = xcalloc(1+m, sizeof(double)); for (t = 1; t <= m; t++) col[t] = 0.0; if (k <= m) { /* x[k] is auxiliary variable, so N[k] is a unity column */ col[k] = -1.0; } else { /* x[k] is structural variable, so N[k] is a column of the original constraint matrix A with negative sign */ len = glp_get_mat_col(lp, k-m, ind, val); for (t = 1; t <= len; t++) col[ind[t]] = val[t]; } /* compute column of the simplex table, which corresponds to the specified non-basic variable x[k] */ glp_ftran(lp, col); len = 0; for (t = 1; t <= m; t++) { if (col[t] != 0.0) { len++; ind[len] = glp_get_bhead(lp, t); val[len] = col[t]; } } xfree(col); /* return to the calling program */ return len; } /*********************************************************************** * NAME * * glp_transform_row - transform explicitly specified row * * SYNOPSIS * * int glp_transform_row(glp_prob *P, int len, int ind[], double val[]); * * DESCRIPTION * * The routine glp_transform_row performs the same operation as the * routine glp_eval_tab_row with exception that the row to be * transformed is specified explicitly as a sparse vector. * * The explicitly specified row may be thought as a linear form: * * x = a[1]*x[m+1] + a[2]*x[m+2] + ... + a[n]*x[m+n], (1) * * where x is an auxiliary variable for this row, a[j] are coefficients * of the linear form, x[m+j] are structural variables. * * On entry column indices and numerical values of non-zero elements of * the row should be stored in locations ind[1], ..., ind[len] and * val[1], ..., val[len], where len is the number of non-zero elements. * * This routine uses the system of equality constraints and the current * basis in order to express the auxiliary variable x in (1) through the * current non-basic variables (as if the transformed row were added to * the problem object and its auxiliary variable were basic), i.e. the * resultant row has the form: * * x = alfa[1]*xN[1] + alfa[2]*xN[2] + ... + alfa[n]*xN[n], (2) * * where xN[j] are non-basic (auxiliary or structural) variables, n is * the number of columns in the LP problem object. * * On exit the routine stores indices and numerical values of non-zero * elements of the resultant row (2) in locations ind[1], ..., ind[len'] * and val[1], ..., val[len'], where 0 <= len' <= n is the number of * non-zero elements in the resultant row returned by the routine. Note * that indices (numbers) of non-basic variables stored in the array ind * correspond to original ordinal numbers of variables: indices 1 to m * mean auxiliary variables and indices m+1 to m+n mean structural ones. * * RETURNS * * The routine returns len', which is the number of non-zero elements in * the resultant row stored in the arrays ind and val. * * BACKGROUND * * The explicitly specified row (1) is transformed in the same way as it * were the objective function row. * * From (1) it follows that: * * x = aB * xB + aN * xN, (3) * * where xB is the vector of basic variables, xN is the vector of * non-basic variables. * * The simplex table, which corresponds to the current basis, is: * * xB = [-inv(B) * N] * xN. (4) * * Therefore substituting xB from (4) to (3) we have: * * x = aB * [-inv(B) * N] * xN + aN * xN = * (5) * = rho * (-N) * xN + aN * xN = alfa * xN, * * where: * * rho = inv(B') * aB, (6) * * and * * alfa = aN + rho * (-N) (7) * * is the resultant row computed by the routine. */ int glp_transform_row(glp_prob *P, int len, int ind[], double val[]) { int i, j, k, m, n, t, lll, *iii; double alfa, *a, *aB, *rho, *vvv; if (!glp_bf_exists(P)) xerror("glp_transform_row: basis factorization does not exist " "\n"); m = glp_get_num_rows(P); n = glp_get_num_cols(P); /* unpack the row to be transformed to the array a */ a = xcalloc(1+n, sizeof(double)); for (j = 1; j <= n; j++) a[j] = 0.0; if (!(0 <= len && len <= n)) xerror("glp_transform_row: len = %d; invalid row length\n", len); for (t = 1; t <= len; t++) { j = ind[t]; if (!(1 <= j && j <= n)) xerror("glp_transform_row: ind[%d] = %d; column index out o" "f range\n", t, j); if (val[t] == 0.0) xerror("glp_transform_row: val[%d] = 0; zero coefficient no" "t allowed\n", t); if (a[j] != 0.0) xerror("glp_transform_row: ind[%d] = %d; duplicate column i" "ndices not allowed\n", t, j); a[j] = val[t]; } /* construct the vector aB */ aB = xcalloc(1+m, sizeof(double)); for (i = 1; i <= m; i++) { k = glp_get_bhead(P, i); /* xB[i] is k-th original variable */ xassert(1 <= k && k <= m+n); aB[i] = (k <= m ? 0.0 : a[k-m]); } /* solve the system B'*rho = aB to compute the vector rho */ rho = aB, glp_btran(P, rho); /* compute coefficients at non-basic auxiliary variables */ len = 0; for (i = 1; i <= m; i++) { if (glp_get_row_stat(P, i) != GLP_BS) { alfa = - rho[i]; if (alfa != 0.0) { len++; ind[len] = i; val[len] = alfa; } } } /* compute coefficients at non-basic structural variables */ iii = xcalloc(1+m, sizeof(int)); vvv = xcalloc(1+m, sizeof(double)); for (j = 1; j <= n; j++) { if (glp_get_col_stat(P, j) != GLP_BS) { alfa = a[j]; lll = glp_get_mat_col(P, j, iii, vvv); for (t = 1; t <= lll; t++) alfa += vvv[t] * rho[iii[t]]; if (alfa != 0.0) { len++; ind[len] = m+j; val[len] = alfa; } } } xassert(len <= n); xfree(iii); xfree(vvv); xfree(aB); xfree(a); return len; } /*********************************************************************** * NAME * * glp_transform_col - transform explicitly specified column * * SYNOPSIS * * int glp_transform_col(glp_prob *P, int len, int ind[], double val[]); * * DESCRIPTION * * The routine glp_transform_col performs the same operation as the * routine glp_eval_tab_col with exception that the column to be * transformed is specified explicitly as a sparse vector. * * The explicitly specified column may be thought as if it were added * to the original system of equality constraints: * * x[1] = a[1,1]*x[m+1] + ... + a[1,n]*x[m+n] + a[1]*x * x[2] = a[2,1]*x[m+1] + ... + a[2,n]*x[m+n] + a[2]*x (1) * . . . . . . . . . . . . . . . * x[m] = a[m,1]*x[m+1] + ... + a[m,n]*x[m+n] + a[m]*x * * where x[i] are auxiliary variables, x[m+j] are structural variables, * x is a structural variable for the explicitly specified column, a[i] * are constraint coefficients for x. * * On entry row indices and numerical values of non-zero elements of * the column should be stored in locations ind[1], ..., ind[len] and * val[1], ..., val[len], where len is the number of non-zero elements. * * This routine uses the system of equality constraints and the current * basis in order to express the current basic variables through the * structural variable x in (1) (as if the transformed column were added * to the problem object and the variable x were non-basic), i.e. the * resultant column has the form: * * xB[1] = ... + alfa[1]*x * xB[2] = ... + alfa[2]*x (2) * . . . . . . * xB[m] = ... + alfa[m]*x * * where xB are basic (auxiliary and structural) variables, m is the * number of rows in the problem object. * * On exit the routine stores indices and numerical values of non-zero * elements of the resultant column (2) in locations ind[1], ..., * ind[len'] and val[1], ..., val[len'], where 0 <= len' <= m is the * number of non-zero element in the resultant column returned by the * routine. Note that indices (numbers) of basic variables stored in * the array ind correspond to original ordinal numbers of variables: * indices 1 to m mean auxiliary variables and indices m+1 to m+n mean * structural ones. * * RETURNS * * The routine returns len', which is the number of non-zero elements * in the resultant column stored in the arrays ind and val. * * BACKGROUND * * The explicitly specified column (1) is transformed in the same way * as any other column of the constraint matrix using the formula: * * alfa = inv(B) * a, (3) * * where alfa is the resultant column computed by the routine. */ int glp_transform_col(glp_prob *P, int len, int ind[], double val[]) { int i, m, t; double *a, *alfa; if (!glp_bf_exists(P)) xerror("glp_transform_col: basis factorization does not exist " "\n"); m = glp_get_num_rows(P); /* unpack the column to be transformed to the array a */ a = xcalloc(1+m, sizeof(double)); for (i = 1; i <= m; i++) a[i] = 0.0; if (!(0 <= len && len <= m)) xerror("glp_transform_col: len = %d; invalid column length\n", len); for (t = 1; t <= len; t++) { i = ind[t]; if (!(1 <= i && i <= m)) xerror("glp_transform_col: ind[%d] = %d; row index out of r" "ange\n", t, i); if (val[t] == 0.0) xerror("glp_transform_col: val[%d] = 0; zero coefficient no" "t allowed\n", t); if (a[i] != 0.0) xerror("glp_transform_col: ind[%d] = %d; duplicate row indi" "ces not allowed\n", t, i); a[i] = val[t]; } /* solve the system B*a = alfa to compute the vector alfa */ alfa = a, glp_ftran(P, alfa); /* store resultant coefficients */ len = 0; for (i = 1; i <= m; i++) { if (alfa[i] != 0.0) { len++; ind[len] = glp_get_bhead(P, i); val[len] = alfa[i]; } } xfree(a); return len; } /*********************************************************************** * NAME * * glp_prim_rtest - perform primal ratio test * * SYNOPSIS * * int glp_prim_rtest(glp_prob *P, int len, const int ind[], * const double val[], int dir, double eps); * * DESCRIPTION * * The routine glp_prim_rtest performs the primal ratio test using an * explicitly specified column of the simplex table. * * The current basic solution associated with the LP problem object * must be primal feasible. * * The explicitly specified column of the simplex table shows how the * basic variables xB depend on some non-basic variable x (which is not * necessarily presented in the problem object): * * xB[1] = ... + alfa[1] * x + ... * xB[2] = ... + alfa[2] * x + ... (*) * . . . . . . . . * xB[m] = ... + alfa[m] * x + ... * * The column (*) is specifed on entry to the routine using the sparse * format. Ordinal numbers of basic variables xB[i] should be placed in * locations ind[1], ..., ind[len], where ordinal number 1 to m denote * auxiliary variables, and ordinal numbers m+1 to m+n denote structural * variables. The corresponding non-zero coefficients alfa[i] should be * placed in locations val[1], ..., val[len]. The arrays ind and val are * not changed on exit. * * The parameter dir specifies direction in which the variable x changes * on entering the basis: +1 means increasing, -1 means decreasing. * * The parameter eps is an absolute tolerance (small positive number) * used by the routine to skip small alfa[j] of the row (*). * * The routine determines which basic variable (among specified in * ind[1], ..., ind[len]) should leave the basis in order to keep primal * feasibility. * * RETURNS * * The routine glp_prim_rtest returns the index piv in the arrays ind * and val corresponding to the pivot element chosen, 1 <= piv <= len. * If the adjacent basic solution is primal unbounded and therefore the * choice cannot be made, the routine returns zero. * * COMMENTS * * If the non-basic variable x is presented in the LP problem object, * the column (*) can be computed with the routine glp_eval_tab_col; * otherwise it can be computed with the routine glp_transform_col. */ int glp_prim_rtest(glp_prob *P, int len, const int ind[], const double val[], int dir, double eps) { int k, m, n, piv, t, type, stat; double alfa, big, beta, lb, ub, temp, teta; if (glp_get_prim_stat(P) != GLP_FEAS) xerror("glp_prim_rtest: basic solution is not primal feasible " "\n"); if (!(dir == +1 || dir == -1)) xerror("glp_prim_rtest: dir = %d; invalid parameter\n", dir); if (!(0.0 < eps && eps < 1.0)) xerror("glp_prim_rtest: eps = %g; invalid parameter\n", eps); m = glp_get_num_rows(P); n = glp_get_num_cols(P); /* initial settings */ piv = 0, teta = DBL_MAX, big = 0.0; /* walk through the entries of the specified column */ for (t = 1; t <= len; t++) { /* get the ordinal number of basic variable */ k = ind[t]; if (!(1 <= k && k <= m+n)) xerror("glp_prim_rtest: ind[%d] = %d; variable number out o" "f range\n", t, k); /* determine type, bounds, status and primal value of basic variable xB[i] = x[k] in the current basic solution */ if (k <= m) { type = glp_get_row_type(P, k); lb = glp_get_row_lb(P, k); ub = glp_get_row_ub(P, k); stat = glp_get_row_stat(P, k); beta = glp_get_row_prim(P, k); } else { type = glp_get_col_type(P, k-m); lb = glp_get_col_lb(P, k-m); ub = glp_get_col_ub(P, k-m); stat = glp_get_col_stat(P, k-m); beta = glp_get_col_prim(P, k-m); } if (stat != GLP_BS) xerror("glp_prim_rtest: ind[%d] = %d; non-basic variable no" "t allowed\n", t, k); /* determine influence coefficient at basic variable xB[i] in the explicitly specified column and turn to the case of increasing the variable x in order to simplify the program logic */ alfa = (dir > 0 ? + val[t] : - val[t]); /* analyze main cases */ if (type == GLP_FR) { /* xB[i] is free variable */ continue; } else if (type == GLP_LO) lo: { /* xB[i] has an lower bound */ if (alfa > - eps) continue; temp = (lb - beta) / alfa; } else if (type == GLP_UP) up: { /* xB[i] has an upper bound */ if (alfa < + eps) continue; temp = (ub - beta) / alfa; } else if (type == GLP_DB) { /* xB[i] has both lower and upper bounds */ if (alfa < 0.0) goto lo; else goto up; } else if (type == GLP_FX) { /* xB[i] is fixed variable */ if (- eps < alfa && alfa < + eps) continue; temp = 0.0; } else xassert(type != type); /* if the value of the variable xB[i] violates its lower or upper bound (slightly, because the current basis is assumed to be primal feasible), temp is negative; we can think this happens due to round-off errors and the value is exactly on the bound; this allows replacing temp by zero */ if (temp < 0.0) temp = 0.0; /* apply the minimal ratio test */ if (teta > temp || teta == temp && big < fabs(alfa)) piv = t, teta = temp, big = fabs(alfa); } /* return index of the pivot element chosen */ return piv; } /*********************************************************************** * NAME * * glp_dual_rtest - perform dual ratio test * * SYNOPSIS * * int glp_dual_rtest(glp_prob *P, int len, const int ind[], * const double val[], int dir, double eps); * * DESCRIPTION * * The routine glp_dual_rtest performs the dual ratio test using an * explicitly specified row of the simplex table. * * The current basic solution associated with the LP problem object * must be dual feasible. * * The explicitly specified row of the simplex table is a linear form * that shows how some basic variable x (which is not necessarily * presented in the problem object) depends on non-basic variables xN: * * x = alfa[1] * xN[1] + alfa[2] * xN[2] + ... + alfa[n] * xN[n]. (*) * * The row (*) is specified on entry to the routine using the sparse * format. Ordinal numbers of non-basic variables xN[j] should be placed * in locations ind[1], ..., ind[len], where ordinal numbers 1 to m * denote auxiliary variables, and ordinal numbers m+1 to m+n denote * structural variables. The corresponding non-zero coefficients alfa[j] * should be placed in locations val[1], ..., val[len]. The arrays ind * and val are not changed on exit. * * The parameter dir specifies direction in which the variable x changes * on leaving the basis: +1 means that x goes to its lower bound, and -1 * means that x goes to its upper bound. * * The parameter eps is an absolute tolerance (small positive number) * used by the routine to skip small alfa[j] of the row (*). * * The routine determines which non-basic variable (among specified in * ind[1], ..., ind[len]) should enter the basis in order to keep dual * feasibility. * * RETURNS * * The routine glp_dual_rtest returns the index piv in the arrays ind * and val corresponding to the pivot element chosen, 1 <= piv <= len. * If the adjacent basic solution is dual unbounded and therefore the * choice cannot be made, the routine returns zero. * * COMMENTS * * If the basic variable x is presented in the LP problem object, the * row (*) can be computed with the routine glp_eval_tab_row; otherwise * it can be computed with the routine glp_transform_row. */ int glp_dual_rtest(glp_prob *P, int len, const int ind[], const double val[], int dir, double eps) { int k, m, n, piv, t, stat; double alfa, big, cost, obj, temp, teta; if (glp_get_dual_stat(P) != GLP_FEAS) xerror("glp_dual_rtest: basic solution is not dual feasible\n") ; if (!(dir == +1 || dir == -1)) xerror("glp_dual_rtest: dir = %d; invalid parameter\n", dir); if (!(0.0 < eps && eps < 1.0)) xerror("glp_dual_rtest: eps = %g; invalid parameter\n", eps); m = glp_get_num_rows(P); n = glp_get_num_cols(P); /* take into account optimization direction */ obj = (glp_get_obj_dir(P) == GLP_MIN ? +1.0 : -1.0); /* initial settings */ piv = 0, teta = DBL_MAX, big = 0.0; /* walk through the entries of the specified row */ for (t = 1; t <= len; t++) { /* get ordinal number of non-basic variable */ k = ind[t]; if (!(1 <= k && k <= m+n)) xerror("glp_dual_rtest: ind[%d] = %d; variable number out o" "f range\n", t, k); /* determine status and reduced cost of non-basic variable x[k] = xN[j] in the current basic solution */ if (k <= m) { stat = glp_get_row_stat(P, k); cost = glp_get_row_dual(P, k); } else { stat = glp_get_col_stat(P, k-m); cost = glp_get_col_dual(P, k-m); } if (stat == GLP_BS) xerror("glp_dual_rtest: ind[%d] = %d; basic variable not al" "lowed\n", t, k); /* determine influence coefficient at non-basic variable xN[j] in the explicitly specified row and turn to the case of increasing the variable x in order to simplify the program logic */ alfa = (dir > 0 ? + val[t] : - val[t]); /* analyze main cases */ if (stat == GLP_NL) { /* xN[j] is on its lower bound */ if (alfa < + eps) continue; temp = (obj * cost) / alfa; } else if (stat == GLP_NU) { /* xN[j] is on its upper bound */ if (alfa > - eps) continue; temp = (obj * cost) / alfa; } else if (stat == GLP_NF) { /* xN[j] is non-basic free variable */ if (- eps < alfa && alfa < + eps) continue; temp = 0.0; } else if (stat == GLP_NS) { /* xN[j] is non-basic fixed variable */ continue; } else xassert(stat != stat); /* if the reduced cost of the variable xN[j] violates its zero bound (slightly, because the current basis is assumed to be dual feasible), temp is negative; we can think this happens due to round-off errors and the reduced cost is exact zero; this allows replacing temp by zero */ if (temp < 0.0) temp = 0.0; /* apply the minimal ratio test */ if (teta > temp || teta == temp && big < fabs(alfa)) piv = t, teta = temp, big = fabs(alfa); } /* return index of the pivot element chosen */ return piv; } /*********************************************************************** * NAME * * glp_analyze_row - simulate one iteration of dual simplex method * * SYNOPSIS * * int glp_analyze_row(glp_prob *P, int len, const int ind[], * const double val[], int type, double rhs, double eps, int *piv, * double *x, double *dx, double *y, double *dy, double *dz); * * DESCRIPTION * * Let the current basis be optimal or dual feasible, and there be * specified a row (constraint), which is violated by the current basic * solution. The routine glp_analyze_row simulates one iteration of the * dual simplex method to determine some information on the adjacent * basis (see below), where the specified row becomes active constraint * (i.e. its auxiliary variable becomes non-basic). * * The current basic solution associated with the problem object passed * to the routine must be dual feasible, and its primal components must * be defined. * * The row to be analyzed must be previously transformed either with * the routine glp_eval_tab_row (if the row is in the problem object) * or with the routine glp_transform_row (if the row is external, i.e. * not in the problem object). This is needed to express the row only * through (auxiliary and structural) variables, which are non-basic in * the current basis: * * y = alfa[1] * xN[1] + alfa[2] * xN[2] + ... + alfa[n] * xN[n], * * where y is an auxiliary variable of the row, alfa[j] is an influence * coefficient, xN[j] is a non-basic variable. * * The row is passed to the routine in sparse format. Ordinal numbers * of non-basic variables are stored in locations ind[1], ..., ind[len], * where numbers 1 to m denote auxiliary variables while numbers m+1 to * m+n denote structural variables. Corresponding non-zero coefficients * alfa[j] are stored in locations val[1], ..., val[len]. The arrays * ind and val are ot changed on exit. * * The parameters type and rhs specify the row type and its right-hand * side as follows: * * type = GLP_LO: y = sum alfa[j] * xN[j] >= rhs * * type = GLP_UP: y = sum alfa[j] * xN[j] <= rhs * * The parameter eps is an absolute tolerance (small positive number) * used by the routine to skip small coefficients alfa[j] on performing * the dual ratio test. * * If the operation was successful, the routine stores the following * information to corresponding location (if some parameter is NULL, * its value is not stored): * * piv index in the array ind and val, 1 <= piv <= len, determining * the non-basic variable, which would enter the adjacent basis; * * x value of the non-basic variable in the current basis; * * dx difference between values of the non-basic variable in the * adjacent and current bases, dx = x.new - x.old; * * y value of the row (i.e. of its auxiliary variable) in the * current basis; * * dy difference between values of the row in the adjacent and * current bases, dy = y.new - y.old; * * dz difference between values of the objective function in the * adjacent and current bases, dz = z.new - z.old. Note that in * case of minimization dz >= 0, and in case of maximization * dz <= 0, i.e. in the adjacent basis the objective function * always gets worse (degrades). */ int _glp_analyze_row(glp_prob *P, int len, const int ind[], const double val[], int type, double rhs, double eps, int *_piv, double *_x, double *_dx, double *_y, double *_dy, double *_dz) { int t, k, dir, piv, ret = 0; double x, dx, y, dy, dz; if (P->pbs_stat == GLP_UNDEF) xerror("glp_analyze_row: primal basic solution components are " "undefined\n"); if (P->dbs_stat != GLP_FEAS) xerror("glp_analyze_row: basic solution is not dual feasible\n" ); /* compute the row value y = sum alfa[j] * xN[j] in the current basis */ if (!(0 <= len && len <= P->n)) xerror("glp_analyze_row: len = %d; invalid row length\n", len); y = 0.0; for (t = 1; t <= len; t++) { /* determine value of x[k] = xN[j] in the current basis */ k = ind[t]; if (!(1 <= k && k <= P->m+P->n)) xerror("glp_analyze_row: ind[%d] = %d; row/column index out" " of range\n", t, k); if (k <= P->m) { /* x[k] is auxiliary variable */ if (P->row[k]->stat == GLP_BS) xerror("glp_analyze_row: ind[%d] = %d; basic auxiliary v" "ariable is not allowed\n", t, k); x = P->row[k]->prim; } else { /* x[k] is structural variable */ if (P->col[k-P->m]->stat == GLP_BS) xerror("glp_analyze_row: ind[%d] = %d; basic structural " "variable is not allowed\n", t, k); x = P->col[k-P->m]->prim; } y += val[t] * x; } /* check if the row is primal infeasible in the current basis, i.e. the constraint is violated at the current point */ if (type == GLP_LO) { if (y >= rhs) { /* the constraint is not violated */ ret = 1; goto done; } /* in the adjacent basis y goes to its lower bound */ dir = +1; } else if (type == GLP_UP) { if (y <= rhs) { /* the constraint is not violated */ ret = 1; goto done; } /* in the adjacent basis y goes to its upper bound */ dir = -1; } else xerror("glp_analyze_row: type = %d; invalid parameter\n", type); /* compute dy = y.new - y.old */ dy = rhs - y; /* perform dual ratio test to determine which non-basic variable should enter the adjacent basis to keep it dual feasible */ piv = glp_dual_rtest(P, len, ind, val, dir, eps); if (piv == 0) { /* no dual feasible adjacent basis exists */ ret = 2; goto done; } /* non-basic variable x[k] = xN[j] should enter the basis */ k = ind[piv]; xassert(1 <= k && k <= P->m+P->n); /* determine its value in the current basis */ if (k <= P->m) x = P->row[k]->prim; else x = P->col[k-P->m]->prim; /* compute dx = x.new - x.old = dy / alfa[j] */ xassert(val[piv] != 0.0); dx = dy / val[piv]; /* compute dz = z.new - z.old = d[j] * dx, where d[j] is reduced cost of xN[j] in the current basis */ if (k <= P->m) dz = P->row[k]->dual * dx; else dz = P->col[k-P->m]->dual * dx; /* store the analysis results */ if (_piv != NULL) *_piv = piv; if (_x != NULL) *_x = x; if (_dx != NULL) *_dx = dx; if (_y != NULL) *_y = y; if (_dy != NULL) *_dy = dy; if (_dz != NULL) *_dz = dz; done: return ret; } #if 0 int main(void) { /* example program for the routine glp_analyze_row */ glp_prob *P; glp_smcp parm; int i, k, len, piv, ret, ind[1+100]; double rhs, x, dx, y, dy, dz, val[1+100]; P = glp_create_prob(); /* read plan.mps (see glpk/examples) */ ret = glp_read_mps(P, GLP_MPS_DECK, NULL, "plan.mps"); glp_assert(ret == 0); /* and solve it to optimality */ ret = glp_simplex(P, NULL); glp_assert(ret == 0); glp_assert(glp_get_status(P) == GLP_OPT); /* the optimal objective value is 296.217 */ /* we would like to know what happens if we would add a new row (constraint) to plan.mps: .01 * bin1 + .01 * bin2 + .02 * bin4 + .02 * bin5 <= 12 */ /* first, we specify this new row */ glp_create_index(P); len = 0; ind[++len] = glp_find_col(P, "BIN1"), val[len] = .01; ind[++len] = glp_find_col(P, "BIN2"), val[len] = .01; ind[++len] = glp_find_col(P, "BIN4"), val[len] = .02; ind[++len] = glp_find_col(P, "BIN5"), val[len] = .02; rhs = 12; /* then we can compute value of the row (i.e. of its auxiliary variable) in the current basis to see if the constraint is violated */ y = 0.0; for (k = 1; k <= len; k++) y += val[k] * glp_get_col_prim(P, ind[k]); glp_printf("y = %g\n", y); /* this prints y = 15.1372, so the constraint is violated, since we require that y <= rhs = 12 */ /* now we transform the row to express it only through non-basic (auxiliary and artificial) variables */ len = glp_transform_row(P, len, ind, val); /* finally, we simulate one step of the dual simplex method to obtain necessary information for the adjacent basis */ ret = _glp_analyze_row(P, len, ind, val, GLP_UP, rhs, 1e-9, &piv, &x, &dx, &y, &dy, &dz); glp_assert(ret == 0); glp_printf("k = %d, x = %g; dx = %g; y = %g; dy = %g; dz = %g\n", ind[piv], x, dx, y, dy, dz); /* this prints dz = 5.64418 and means that in the adjacent basis the objective function would be 296.217 + 5.64418 = 301.861 */ /* now we actually include the row into the problem object; note that the arrays ind and val are clobbered, so we need to build them once again */ len = 0; ind[++len] = glp_find_col(P, "BIN1"), val[len] = .01; ind[++len] = glp_find_col(P, "BIN2"), val[len] = .01; ind[++len] = glp_find_col(P, "BIN4"), val[len] = .02; ind[++len] = glp_find_col(P, "BIN5"), val[len] = .02; rhs = 12; i = glp_add_rows(P, 1); glp_set_row_bnds(P, i, GLP_UP, 0, rhs); glp_set_mat_row(P, i, len, ind, val); /* and perform one dual simplex iteration */ glp_init_smcp(&parm); parm.meth = GLP_DUAL; parm.it_lim = 1; glp_simplex(P, &parm); /* the current objective value is 301.861 */ return 0; } #endif /*********************************************************************** * NAME * * glp_analyze_bound - analyze active bound of non-basic variable * * SYNOPSIS * * void glp_analyze_bound(glp_prob *P, int k, double *limit1, int *var1, * double *limit2, int *var2); * * DESCRIPTION * * The routine glp_analyze_bound analyzes the effect of varying the * active bound of specified non-basic variable. * * The non-basic variable is specified by the parameter k, where * 1 <= k <= m means auxiliary variable of corresponding row while * m+1 <= k <= m+n means structural variable (column). * * Note that the current basic solution must be optimal, and the basis * factorization must exist. * * Results of the analysis have the following meaning. * * value1 is the minimal value of the active bound, at which the basis * still remains primal feasible and thus optimal. -DBL_MAX means that * the active bound has no lower limit. * * var1 is the ordinal number of an auxiliary (1 to m) or structural * (m+1 to n) basic variable, which reaches its bound first and thereby * limits further decreasing the active bound being analyzed. * if value1 = -DBL_MAX, var1 is set to 0. * * value2 is the maximal value of the active bound, at which the basis * still remains primal feasible and thus optimal. +DBL_MAX means that * the active bound has no upper limit. * * var2 is the ordinal number of an auxiliary (1 to m) or structural * (m+1 to n) basic variable, which reaches its bound first and thereby * limits further increasing the active bound being analyzed. * if value2 = +DBL_MAX, var2 is set to 0. */ void glp_analyze_bound(glp_prob *P, int k, double *value1, int *var1, double *value2, int *var2) { GLPROW *row; GLPCOL *col; int m, n, stat, kase, p, len, piv, *ind; double x, new_x, ll, uu, xx, delta, *val; /* sanity checks */ if (P == NULL || P->magic != GLP_PROB_MAGIC) xerror("glp_analyze_bound: P = %p; invalid problem object\n", P); m = P->m, n = P->n; if (!(P->pbs_stat == GLP_FEAS && P->dbs_stat == GLP_FEAS)) xerror("glp_analyze_bound: optimal basic solution required\n"); if (!(m == 0 || P->valid)) xerror("glp_analyze_bound: basis factorization required\n"); if (!(1 <= k && k <= m+n)) xerror("glp_analyze_bound: k = %d; variable number out of rang" "e\n", k); /* retrieve information about the specified non-basic variable x[k] whose active bound is to be analyzed */ if (k <= m) { row = P->row[k]; stat = row->stat; x = row->prim; } else { col = P->col[k-m]; stat = col->stat; x = col->prim; } if (stat == GLP_BS) xerror("glp_analyze_bound: k = %d; basic variable not allowed " "\n", k); /* allocate working arrays */ ind = xcalloc(1+m, sizeof(int)); val = xcalloc(1+m, sizeof(double)); /* compute column of the simplex table corresponding to the non-basic variable x[k] */ len = glp_eval_tab_col(P, k, ind, val); xassert(0 <= len && len <= m); /* perform analysis */ for (kase = -1; kase <= +1; kase += 2) { /* kase < 0 means active bound of x[k] is decreasing; kase > 0 means active bound of x[k] is increasing */ /* use the primal ratio test to determine some basic variable x[p] which reaches its bound first */ piv = glp_prim_rtest(P, len, ind, val, kase, 1e-9); if (piv == 0) { /* nothing limits changing the active bound of x[k] */ p = 0; new_x = (kase < 0 ? -DBL_MAX : +DBL_MAX); goto store; } /* basic variable x[p] limits changing the active bound of x[k]; determine its value in the current basis */ xassert(1 <= piv && piv <= len); p = ind[piv]; if (p <= m) { row = P->row[p]; ll = glp_get_row_lb(P, row->i); uu = glp_get_row_ub(P, row->i); stat = row->stat; xx = row->prim; } else { col = P->col[p-m]; ll = glp_get_col_lb(P, col->j); uu = glp_get_col_ub(P, col->j); stat = col->stat; xx = col->prim; } xassert(stat == GLP_BS); /* determine delta x[p] = bound of x[p] - value of x[p] */ if (kase < 0 && val[piv] > 0.0 || kase > 0 && val[piv] < 0.0) { /* delta x[p] < 0, so x[p] goes toward its lower bound */ xassert(ll != -DBL_MAX); delta = ll - xx; } else { /* delta x[p] > 0, so x[p] goes toward its upper bound */ xassert(uu != +DBL_MAX); delta = uu - xx; } /* delta x[p] = alfa[p,k] * delta x[k], so new x[k] = x[k] + delta x[k] = x[k] + delta x[p] / alfa[p,k] is the value of x[k] in the adjacent basis */ xassert(val[piv] != 0.0); new_x = x + delta / val[piv]; store: /* store analysis results */ if (kase < 0) { if (value1 != NULL) *value1 = new_x; if (var1 != NULL) *var1 = p; } else { if (value2 != NULL) *value2 = new_x; if (var2 != NULL) *var2 = p; } } /* free working arrays */ xfree(ind); xfree(val); return; } /*********************************************************************** * NAME * * glp_analyze_coef - analyze objective coefficient at basic variable * * SYNOPSIS * * void glp_analyze_coef(glp_prob *P, int k, double *coef1, int *var1, * double *value1, double *coef2, int *var2, double *value2); * * DESCRIPTION * * The routine glp_analyze_coef analyzes the effect of varying the * objective coefficient at specified basic variable. * * The basic variable is specified by the parameter k, where * 1 <= k <= m means auxiliary variable of corresponding row while * m+1 <= k <= m+n means structural variable (column). * * Note that the current basic solution must be optimal, and the basis * factorization must exist. * * Results of the analysis have the following meaning. * * coef1 is the minimal value of the objective coefficient, at which * the basis still remains dual feasible and thus optimal. -DBL_MAX * means that the objective coefficient has no lower limit. * * var1 is the ordinal number of an auxiliary (1 to m) or structural * (m+1 to n) non-basic variable, whose reduced cost reaches its zero * bound first and thereby limits further decreasing the objective * coefficient being analyzed. If coef1 = -DBL_MAX, var1 is set to 0. * * value1 is value of the basic variable being analyzed in an adjacent * basis, which is defined as follows. Let the objective coefficient * reaches its minimal value (coef1) and continues decreasing. Then the * reduced cost of the limiting non-basic variable (var1) becomes dual * infeasible and the current basis becomes non-optimal that forces the * limiting non-basic variable to enter the basis replacing there some * basic variable that leaves the basis to keep primal feasibility. * Should note that on determining the adjacent basis current bounds * of the basic variable being analyzed are ignored as if it were free * (unbounded) variable, so it cannot leave the basis. It may happen * that no dual feasible adjacent basis exists, in which case value1 is * set to -DBL_MAX or +DBL_MAX. * * coef2 is the maximal value of the objective coefficient, at which * the basis still remains dual feasible and thus optimal. +DBL_MAX * means that the objective coefficient has no upper limit. * * var2 is the ordinal number of an auxiliary (1 to m) or structural * (m+1 to n) non-basic variable, whose reduced cost reaches its zero * bound first and thereby limits further increasing the objective * coefficient being analyzed. If coef2 = +DBL_MAX, var2 is set to 0. * * value2 is value of the basic variable being analyzed in an adjacent * basis, which is defined exactly in the same way as value1 above with * exception that now the objective coefficient is increasing. */ void glp_analyze_coef(glp_prob *P, int k, double *coef1, int *var1, double *value1, double *coef2, int *var2, double *value2) { GLPROW *row; GLPCOL *col; int m, n, type, stat, kase, p, q, dir, clen, cpiv, rlen, rpiv, *cind, *rind; double lb, ub, coef, x, lim_coef, new_x, d, delta, ll, uu, xx, *rval, *cval; /* sanity checks */ if (P == NULL || P->magic != GLP_PROB_MAGIC) xerror("glp_analyze_coef: P = %p; invalid problem object\n", P); m = P->m, n = P->n; if (!(P->pbs_stat == GLP_FEAS && P->dbs_stat == GLP_FEAS)) xerror("glp_analyze_coef: optimal basic solution required\n"); if (!(m == 0 || P->valid)) xerror("glp_analyze_coef: basis factorization required\n"); if (!(1 <= k && k <= m+n)) xerror("glp_analyze_coef: k = %d; variable number out of range" "\n", k); /* retrieve information about the specified basic variable x[k] whose objective coefficient c[k] is to be analyzed */ if (k <= m) { row = P->row[k]; type = row->type; lb = row->lb; ub = row->ub; coef = 0.0; stat = row->stat; x = row->prim; } else { col = P->col[k-m]; type = col->type; lb = col->lb; ub = col->ub; coef = col->coef; stat = col->stat; x = col->prim; } if (stat != GLP_BS) xerror("glp_analyze_coef: k = %d; non-basic variable not allow" "ed\n", k); /* allocate working arrays */ cind = xcalloc(1+m, sizeof(int)); cval = xcalloc(1+m, sizeof(double)); rind = xcalloc(1+n, sizeof(int)); rval = xcalloc(1+n, sizeof(double)); /* compute row of the simplex table corresponding to the basic variable x[k] */ rlen = glp_eval_tab_row(P, k, rind, rval); xassert(0 <= rlen && rlen <= n); /* perform analysis */ for (kase = -1; kase <= +1; kase += 2) { /* kase < 0 means objective coefficient c[k] is decreasing; kase > 0 means objective coefficient c[k] is increasing */ /* note that decreasing c[k] is equivalent to increasing dual variable lambda[k] and vice versa; we need to correctly set the dir flag as required by the routine glp_dual_rtest */ if (P->dir == GLP_MIN) dir = - kase; else if (P->dir == GLP_MAX) dir = + kase; else xassert(P != P); /* use the dual ratio test to determine non-basic variable x[q] whose reduced cost d[q] reaches zero bound first */ rpiv = glp_dual_rtest(P, rlen, rind, rval, dir, 1e-9); if (rpiv == 0) { /* nothing limits changing c[k] */ lim_coef = (kase < 0 ? -DBL_MAX : +DBL_MAX); q = 0; /* x[k] keeps its current value */ new_x = x; goto store; } /* non-basic variable x[q] limits changing coefficient c[k]; determine its status and reduced cost d[k] in the current basis */ xassert(1 <= rpiv && rpiv <= rlen); q = rind[rpiv]; xassert(1 <= q && q <= m+n); if (q <= m) { row = P->row[q]; stat = row->stat; d = row->dual; } else { col = P->col[q-m]; stat = col->stat; d = col->dual; } /* note that delta d[q] = new d[q] - d[q] = - d[q], because new d[q] = 0; delta d[q] = alfa[k,q] * delta c[k], so delta c[k] = delta d[q] / alfa[k,q] = - d[q] / alfa[k,q] */ xassert(rval[rpiv] != 0.0); delta = - d / rval[rpiv]; /* compute new c[k] = c[k] + delta c[k], which is the limiting value of the objective coefficient c[k] */ lim_coef = coef + delta; /* let c[k] continue decreasing/increasing that makes d[q] dual infeasible and forces x[q] to enter the basis; to perform the primal ratio test we need to know in which direction x[q] changes on entering the basis; we determine that analyzing the sign of delta d[q] (see above), since d[q] may be close to zero having wrong sign */ /* let, for simplicity, the problem is minimization */ if (kase < 0 && rval[rpiv] > 0.0 || kase > 0 && rval[rpiv] < 0.0) { /* delta d[q] < 0, so d[q] being non-negative will become negative, so x[q] will increase */ dir = +1; } else { /* delta d[q] > 0, so d[q] being non-positive will become positive, so x[q] will decrease */ dir = -1; } /* if the problem is maximization, correct the direction */ if (P->dir == GLP_MAX) dir = - dir; /* check that we didn't make a silly mistake */ if (dir > 0) xassert(stat == GLP_NL || stat == GLP_NF); else xassert(stat == GLP_NU || stat == GLP_NF); /* compute column of the simplex table corresponding to the non-basic variable x[q] */ clen = glp_eval_tab_col(P, q, cind, cval); /* make x[k] temporarily free (unbounded) */ if (k <= m) { row = P->row[k]; row->type = GLP_FR; row->lb = row->ub = 0.0; } else { col = P->col[k-m]; col->type = GLP_FR; col->lb = col->ub = 0.0; } /* use the primal ratio test to determine some basic variable which leaves the basis */ cpiv = glp_prim_rtest(P, clen, cind, cval, dir, 1e-9); /* restore original bounds of the basic variable x[k] */ if (k <= m) { row = P->row[k]; row->type = type; row->lb = lb, row->ub = ub; } else { col = P->col[k-m]; col->type = type; col->lb = lb, col->ub = ub; } if (cpiv == 0) { /* non-basic variable x[q] can change unlimitedly */ if (dir < 0 && rval[rpiv] > 0.0 || dir > 0 && rval[rpiv] < 0.0) { /* delta x[k] = alfa[k,q] * delta x[q] < 0 */ new_x = -DBL_MAX; } else { /* delta x[k] = alfa[k,q] * delta x[q] > 0 */ new_x = +DBL_MAX; } goto store; } /* some basic variable x[p] limits changing non-basic variable x[q] in the adjacent basis */ xassert(1 <= cpiv && cpiv <= clen); p = cind[cpiv]; xassert(1 <= p && p <= m+n); xassert(p != k); if (p <= m) { row = P->row[p]; xassert(row->stat == GLP_BS); ll = glp_get_row_lb(P, row->i); uu = glp_get_row_ub(P, row->i); xx = row->prim; } else { col = P->col[p-m]; xassert(col->stat == GLP_BS); ll = glp_get_col_lb(P, col->j); uu = glp_get_col_ub(P, col->j); xx = col->prim; } /* determine delta x[p] = new x[p] - x[p] */ if (dir < 0 && cval[cpiv] > 0.0 || dir > 0 && cval[cpiv] < 0.0) { /* delta x[p] < 0, so x[p] goes toward its lower bound */ xassert(ll != -DBL_MAX); delta = ll - xx; } else { /* delta x[p] > 0, so x[p] goes toward its upper bound */ xassert(uu != +DBL_MAX); delta = uu - xx; } /* compute new x[k] = x[k] + alfa[k,q] * delta x[q], where delta x[q] = delta x[p] / alfa[p,q] */ xassert(cval[cpiv] != 0.0); new_x = x + (rval[rpiv] / cval[cpiv]) * delta; store: /* store analysis results */ if (kase < 0) { if (coef1 != NULL) *coef1 = lim_coef; if (var1 != NULL) *var1 = q; if (value1 != NULL) *value1 = new_x; } else { if (coef2 != NULL) *coef2 = lim_coef; if (var2 != NULL) *var2 = q; if (value2 != NULL) *value2 = new_x; } } /* free working arrays */ xfree(cind); xfree(cval); xfree(rind); xfree(rval); return; } /* eof */ sources_5316/external/glpk/glpnpp01.c0000644000176700017670000007064711401660400016315 0ustar paulpaul/* glpnpp01.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpnpp.h" NPP *npp_create_wksp(void) { /* create LP/MIP preprocessor workspace */ NPP *npp; npp = xmalloc(sizeof(NPP)); npp->orig_dir = 0; npp->orig_m = npp->orig_n = npp->orig_nnz = 0; npp->pool = dmp_create_pool(); npp->name = npp->obj = NULL; npp->c0 = 0.0; npp->nrows = npp->ncols = 0; npp->r_head = npp->r_tail = NULL; npp->c_head = npp->c_tail = NULL; npp->stack = dmp_create_pool(); npp->top = NULL; #if 0 /* 16/XII-2009 */ memset(&npp->count, 0, sizeof(npp->count)); #endif npp->m = npp->n = npp->nnz = 0; npp->row_ref = npp->col_ref = NULL; npp->sol = npp->scaling = 0; npp->p_stat = npp->d_stat = npp->t_stat = npp->i_stat = 0; npp->r_stat = NULL; /*npp->r_prim =*/ npp->r_pi = NULL; npp->c_stat = NULL; npp->c_value = /*npp->c_dual =*/ NULL; return npp; } void npp_insert_row(NPP *npp, NPPROW *row, int where) { /* insert row to the row list */ if (where == 0) { /* insert row to the beginning of the row list */ row->prev = NULL; row->next = npp->r_head; if (row->next == NULL) npp->r_tail = row; else row->next->prev = row; npp->r_head = row; } else { /* insert row to the end of the row list */ row->prev = npp->r_tail; row->next = NULL; if (row->prev == NULL) npp->r_head = row; else row->prev->next = row; npp->r_tail = row; } return; } void npp_remove_row(NPP *npp, NPPROW *row) { /* remove row from the row list */ if (row->prev == NULL) npp->r_head = row->next; else row->prev->next = row->next; if (row->next == NULL) npp->r_tail = row->prev; else row->next->prev = row->prev; return; } void npp_activate_row(NPP *npp, NPPROW *row) { /* make row active */ if (!row->temp) { row->temp = 1; /* move the row to the beginning of the row list */ npp_remove_row(npp, row); npp_insert_row(npp, row, 0); } return; } void npp_deactivate_row(NPP *npp, NPPROW *row) { /* make row inactive */ if (row->temp) { row->temp = 0; /* move the row to the end of the row list */ npp_remove_row(npp, row); npp_insert_row(npp, row, 1); } return; } void npp_insert_col(NPP *npp, NPPCOL *col, int where) { /* insert column to the column list */ if (where == 0) { /* insert column to the beginning of the column list */ col->prev = NULL; col->next = npp->c_head; if (col->next == NULL) npp->c_tail = col; else col->next->prev = col; npp->c_head = col; } else { /* insert column to the end of the column list */ col->prev = npp->c_tail; col->next = NULL; if (col->prev == NULL) npp->c_head = col; else col->prev->next = col; npp->c_tail = col; } return; } void npp_remove_col(NPP *npp, NPPCOL *col) { /* remove column from the column list */ if (col->prev == NULL) npp->c_head = col->next; else col->prev->next = col->next; if (col->next == NULL) npp->c_tail = col->prev; else col->next->prev = col->prev; return; } void npp_activate_col(NPP *npp, NPPCOL *col) { /* make column active */ if (!col->temp) { col->temp = 1; /* move the column to the beginning of the column list */ npp_remove_col(npp, col); npp_insert_col(npp, col, 0); } return; } void npp_deactivate_col(NPP *npp, NPPCOL *col) { /* make column inactive */ if (col->temp) { col->temp = 0; /* move the column to the end of the column list */ npp_remove_col(npp, col); npp_insert_col(npp, col, 1); } return; } NPPROW *npp_add_row(NPP *npp) { /* add new row to the current problem */ NPPROW *row; row = dmp_get_atom(npp->pool, sizeof(NPPROW)); row->i = ++(npp->nrows); row->name = NULL; row->lb = -DBL_MAX, row->ub = +DBL_MAX; row->ptr = NULL; row->temp = 0; npp_insert_row(npp, row, 1); return row; } NPPCOL *npp_add_col(NPP *npp) { /* add new column to the current problem */ NPPCOL *col; col = dmp_get_atom(npp->pool, sizeof(NPPCOL)); col->j = ++(npp->ncols); col->name = NULL; #if 0 col->kind = GLP_CV; #else col->is_int = 0; #endif col->lb = col->ub = col->coef = 0.0; col->ptr = NULL; col->temp = 0; npp_insert_col(npp, col, 1); return col; } NPPAIJ *npp_add_aij(NPP *npp, NPPROW *row, NPPCOL *col, double val) { /* add new element to the constraint matrix */ NPPAIJ *aij; aij = dmp_get_atom(npp->pool, sizeof(NPPAIJ)); aij->row = row; aij->col = col; aij->val = val; aij->r_prev = NULL; aij->r_next = row->ptr; aij->c_prev = NULL; aij->c_next = col->ptr; if (aij->r_next != NULL) aij->r_next->r_prev = aij; if (aij->c_next != NULL) aij->c_next->c_prev = aij; row->ptr = col->ptr = aij; return aij; } int npp_row_nnz(NPP *npp, NPPROW *row) { /* count number of non-zero coefficients in row */ NPPAIJ *aij; int nnz; xassert(npp == npp); nnz = 0; for (aij = row->ptr; aij != NULL; aij = aij->r_next) nnz++; return nnz; } int npp_col_nnz(NPP *npp, NPPCOL *col) { /* count number of non-zero coefficients in column */ NPPAIJ *aij; int nnz; xassert(npp == npp); nnz = 0; for (aij = col->ptr; aij != NULL; aij = aij->c_next) nnz++; return nnz; } void *npp_push_tse(NPP *npp, int (*func)(NPP *npp, void *info), int size) { /* push new entry to the transformation stack */ NPPTSE *tse; tse = dmp_get_atom(npp->stack, sizeof(NPPTSE)); tse->func = func; tse->info = dmp_get_atom(npp->stack, size); tse->link = npp->top; npp->top = tse; return tse->info; } #if 1 /* 23/XII-2009 */ void npp_erase_row(NPP *npp, NPPROW *row) { /* erase row content to make it empty */ NPPAIJ *aij; while (row->ptr != NULL) { aij = row->ptr; row->ptr = aij->r_next; if (aij->c_prev == NULL) aij->col->ptr = aij->c_next; else aij->c_prev->c_next = aij->c_next; if (aij->c_next == NULL) ; else aij->c_next->c_prev = aij->c_prev; dmp_free_atom(npp->pool, aij, sizeof(NPPAIJ)); } return; } #endif void npp_del_row(NPP *npp, NPPROW *row) { /* remove row from the current problem */ #if 0 /* 23/XII-2009 */ NPPAIJ *aij; #endif if (row->name != NULL) dmp_free_atom(npp->pool, row->name, strlen(row->name)+1); #if 0 /* 23/XII-2009 */ while (row->ptr != NULL) { aij = row->ptr; row->ptr = aij->r_next; if (aij->c_prev == NULL) aij->col->ptr = aij->c_next; else aij->c_prev->c_next = aij->c_next; if (aij->c_next == NULL) ; else aij->c_next->c_prev = aij->c_prev; dmp_free_atom(npp->pool, aij, sizeof(NPPAIJ)); } #else npp_erase_row(npp, row); #endif npp_remove_row(npp, row); dmp_free_atom(npp->pool, row, sizeof(NPPROW)); return; } void npp_del_col(NPP *npp, NPPCOL *col) { /* remove column from the current problem */ NPPAIJ *aij; if (col->name != NULL) dmp_free_atom(npp->pool, col->name, strlen(col->name)+1); while (col->ptr != NULL) { aij = col->ptr; col->ptr = aij->c_next; if (aij->r_prev == NULL) aij->row->ptr = aij->r_next; else aij->r_prev->r_next = aij->r_next; if (aij->r_next == NULL) ; else aij->r_next->r_prev = aij->r_prev; dmp_free_atom(npp->pool, aij, sizeof(NPPAIJ)); } npp_remove_col(npp, col); dmp_free_atom(npp->pool, col, sizeof(NPPCOL)); return; } void npp_del_aij(NPP *npp, NPPAIJ *aij) { /* remove element from the constraint matrix */ if (aij->r_prev == NULL) aij->row->ptr = aij->r_next; else aij->r_prev->r_next = aij->r_next; if (aij->r_next == NULL) ; else aij->r_next->r_prev = aij->r_prev; if (aij->c_prev == NULL) aij->col->ptr = aij->c_next; else aij->c_prev->c_next = aij->c_next; if (aij->c_next == NULL) ; else aij->c_next->c_prev = aij->c_prev; dmp_free_atom(npp->pool, aij, sizeof(NPPAIJ)); return; } void npp_load_prob(NPP *npp, glp_prob *orig, int names, int sol, int scaling) { /* load original problem into the preprocessor workspace */ int m = orig->m; int n = orig->n; NPPROW **link; int i, j; double dir; xassert(names == GLP_OFF || names == GLP_ON); xassert(sol == GLP_SOL || sol == GLP_IPT || sol == GLP_MIP); xassert(scaling == GLP_OFF || scaling == GLP_ON); if (sol == GLP_MIP) xassert(!scaling); npp->orig_dir = orig->dir; if (npp->orig_dir == GLP_MIN) dir = +1.0; else if (npp->orig_dir == GLP_MAX) dir = -1.0; else xassert(npp != npp); npp->orig_m = m; npp->orig_n = n; npp->orig_nnz = orig->nnz; if (names && orig->name != NULL) { npp->name = dmp_get_atom(npp->pool, strlen(orig->name)+1); strcpy(npp->name, orig->name); } if (names && orig->obj != NULL) { npp->obj = dmp_get_atom(npp->pool, strlen(orig->obj)+1); strcpy(npp->obj, orig->obj); } npp->c0 = dir * orig->c0; /* load rows */ link = xcalloc(1+m, sizeof(NPPROW *)); for (i = 1; i <= m; i++) { GLPROW *rrr = orig->row[i]; NPPROW *row; link[i] = row = npp_add_row(npp); xassert(row->i == i); if (names && rrr->name != NULL) { row->name = dmp_get_atom(npp->pool, strlen(rrr->name)+1); strcpy(row->name, rrr->name); } if (!scaling) { if (rrr->type == GLP_FR) row->lb = -DBL_MAX, row->ub = +DBL_MAX; else if (rrr->type == GLP_LO) row->lb = rrr->lb, row->ub = +DBL_MAX; else if (rrr->type == GLP_UP) row->lb = -DBL_MAX, row->ub = rrr->ub; else if (rrr->type == GLP_DB) row->lb = rrr->lb, row->ub = rrr->ub; else if (rrr->type == GLP_FX) row->lb = row->ub = rrr->lb; else xassert(rrr != rrr); } else { double rii = rrr->rii; if (rrr->type == GLP_FR) row->lb = -DBL_MAX, row->ub = +DBL_MAX; else if (rrr->type == GLP_LO) row->lb = rrr->lb * rii, row->ub = +DBL_MAX; else if (rrr->type == GLP_UP) row->lb = -DBL_MAX, row->ub = rrr->ub * rii; else if (rrr->type == GLP_DB) row->lb = rrr->lb * rii, row->ub = rrr->ub * rii; else if (rrr->type == GLP_FX) row->lb = row->ub = rrr->lb * rii; else xassert(rrr != rrr); } } /* load columns and constraint coefficients */ for (j = 1; j <= n; j++) { GLPCOL *ccc = orig->col[j]; GLPAIJ *aaa; NPPCOL *col; col = npp_add_col(npp); xassert(col->j == j); if (names && ccc->name != NULL) { col->name = dmp_get_atom(npp->pool, strlen(ccc->name)+1); strcpy(col->name, ccc->name); } if (sol == GLP_MIP) #if 0 col->kind = ccc->kind; #else col->is_int = (char)(ccc->kind == GLP_IV); #endif if (!scaling) { if (ccc->type == GLP_FR) col->lb = -DBL_MAX, col->ub = +DBL_MAX; else if (ccc->type == GLP_LO) col->lb = ccc->lb, col->ub = +DBL_MAX; else if (ccc->type == GLP_UP) col->lb = -DBL_MAX, col->ub = ccc->ub; else if (ccc->type == GLP_DB) col->lb = ccc->lb, col->ub = ccc->ub; else if (ccc->type == GLP_FX) col->lb = col->ub = ccc->lb; else xassert(ccc != ccc); col->coef = dir * ccc->coef; for (aaa = ccc->ptr; aaa != NULL; aaa = aaa->c_next) npp_add_aij(npp, link[aaa->row->i], col, aaa->val); } else { double sjj = ccc->sjj; if (ccc->type == GLP_FR) col->lb = -DBL_MAX, col->ub = +DBL_MAX; else if (ccc->type == GLP_LO) col->lb = ccc->lb / sjj, col->ub = +DBL_MAX; else if (ccc->type == GLP_UP) col->lb = -DBL_MAX, col->ub = ccc->ub / sjj; else if (ccc->type == GLP_DB) col->lb = ccc->lb / sjj, col->ub = ccc->ub / sjj; else if (ccc->type == GLP_FX) col->lb = col->ub = ccc->lb / sjj; else xassert(ccc != ccc); col->coef = dir * ccc->coef * sjj; for (aaa = ccc->ptr; aaa != NULL; aaa = aaa->c_next) npp_add_aij(npp, link[aaa->row->i], col, aaa->row->rii * aaa->val * sjj); } } xfree(link); /* keep solution indicator and scaling option */ npp->sol = sol; npp->scaling = scaling; return; } void npp_build_prob(NPP *npp, glp_prob *prob) { /* build resultant (preprocessed) problem */ NPPROW *row; NPPCOL *col; NPPAIJ *aij; int i, j, type, len, *ind; double dir, *val; glp_erase_prob(prob); glp_set_prob_name(prob, npp->name); glp_set_obj_name(prob, npp->obj); glp_set_obj_dir(prob, npp->orig_dir); if (npp->orig_dir == GLP_MIN) dir = +1.0; else if (npp->orig_dir == GLP_MAX) dir = -1.0; else xassert(npp != npp); glp_set_obj_coef(prob, 0, dir * npp->c0); /* build rows */ for (row = npp->r_head; row != NULL; row = row->next) { row->temp = i = glp_add_rows(prob, 1); glp_set_row_name(prob, i, row->name); if (row->lb == -DBL_MAX && row->ub == +DBL_MAX) type = GLP_FR; else if (row->ub == +DBL_MAX) type = GLP_LO; else if (row->lb == -DBL_MAX) type = GLP_UP; else if (row->lb != row->ub) type = GLP_DB; else type = GLP_FX; glp_set_row_bnds(prob, i, type, row->lb, row->ub); } /* build columns and the constraint matrix */ ind = xcalloc(1+prob->m, sizeof(int)); val = xcalloc(1+prob->m, sizeof(double)); for (col = npp->c_head; col != NULL; col = col->next) { j = glp_add_cols(prob, 1); glp_set_col_name(prob, j, col->name); #if 0 glp_set_col_kind(prob, j, col->kind); #else glp_set_col_kind(prob, j, col->is_int ? GLP_IV : GLP_CV); #endif if (col->lb == -DBL_MAX && col->ub == +DBL_MAX) type = GLP_FR; else if (col->ub == +DBL_MAX) type = GLP_LO; else if (col->lb == -DBL_MAX) type = GLP_UP; else if (col->lb != col->ub) type = GLP_DB; else type = GLP_FX; glp_set_col_bnds(prob, j, type, col->lb, col->ub); glp_set_obj_coef(prob, j, dir * col->coef); len = 0; for (aij = col->ptr; aij != NULL; aij = aij->c_next) { len++; ind[len] = aij->row->temp; val[len] = aij->val; } glp_set_mat_col(prob, j, len, ind, val); } xfree(ind); xfree(val); /* resultant problem has been built */ npp->m = prob->m; npp->n = prob->n; npp->nnz = prob->nnz; npp->row_ref = xcalloc(1+npp->m, sizeof(int)); npp->col_ref = xcalloc(1+npp->n, sizeof(int)); for (row = npp->r_head, i = 0; row != NULL; row = row->next) npp->row_ref[++i] = row->i; for (col = npp->c_head, j = 0; col != NULL; col = col->next) npp->col_ref[++j] = col->j; /* transformed problem segment is no longer needed */ dmp_delete_pool(npp->pool), npp->pool = NULL; npp->name = npp->obj = NULL; npp->c0 = 0.0; npp->r_head = npp->r_tail = NULL; npp->c_head = npp->c_tail = NULL; return; } void npp_postprocess(NPP *npp, glp_prob *prob) { /* postprocess solution from the resultant problem */ GLPROW *row; GLPCOL *col; NPPTSE *tse; int i, j, k; double dir; xassert(npp->orig_dir == prob->dir); if (npp->orig_dir == GLP_MIN) dir = +1.0; else if (npp->orig_dir == GLP_MAX) dir = -1.0; else xassert(npp != npp); xassert(npp->m == prob->m); xassert(npp->n == prob->n); xassert(npp->nnz == prob->nnz); /* copy solution status */ if (npp->sol == GLP_SOL) { npp->p_stat = prob->pbs_stat; npp->d_stat = prob->dbs_stat; } else if (npp->sol == GLP_IPT) npp->t_stat = prob->ipt_stat; else if (npp->sol == GLP_MIP) npp->i_stat = prob->mip_stat; else xassert(npp != npp); /* allocate solution arrays */ if (npp->sol == GLP_SOL) { if (npp->r_stat == NULL) npp->r_stat = xcalloc(1+npp->nrows, sizeof(char)); for (i = 1; i <= npp->nrows; i++) npp->r_stat[i] = 0; if (npp->c_stat == NULL) npp->c_stat = xcalloc(1+npp->ncols, sizeof(char)); for (j = 1; j <= npp->ncols; j++) npp->c_stat[j] = 0; } #if 0 if (npp->r_prim == NULL) npp->r_prim = xcalloc(1+npp->nrows, sizeof(double)); for (i = 1; i <= npp->nrows; i++) npp->r_prim[i] = DBL_MAX; #endif if (npp->c_value == NULL) npp->c_value = xcalloc(1+npp->ncols, sizeof(double)); for (j = 1; j <= npp->ncols; j++) npp->c_value[j] = DBL_MAX; if (npp->sol != GLP_MIP) { if (npp->r_pi == NULL) npp->r_pi = xcalloc(1+npp->nrows, sizeof(double)); for (i = 1; i <= npp->nrows; i++) npp->r_pi[i] = DBL_MAX; #if 0 if (npp->c_dual == NULL) npp->c_dual = xcalloc(1+npp->ncols, sizeof(double)); for (j = 1; j <= npp->ncols; j++) npp->c_dual[j] = DBL_MAX; #endif } /* copy solution components from the resultant problem */ if (npp->sol == GLP_SOL) { for (i = 1; i <= npp->m; i++) { row = prob->row[i]; k = npp->row_ref[i]; npp->r_stat[k] = (char)row->stat; /*npp->r_prim[k] = row->prim;*/ npp->r_pi[k] = dir * row->dual; } for (j = 1; j <= npp->n; j++) { col = prob->col[j]; k = npp->col_ref[j]; npp->c_stat[k] = (char)col->stat; npp->c_value[k] = col->prim; /*npp->c_dual[k] = dir * col->dual;*/ } } else if (npp->sol == GLP_IPT) { for (i = 1; i <= npp->m; i++) { row = prob->row[i]; k = npp->row_ref[i]; /*npp->r_prim[k] = row->pval;*/ npp->r_pi[k] = dir * row->dval; } for (j = 1; j <= npp->n; j++) { col = prob->col[j]; k = npp->col_ref[j]; npp->c_value[k] = col->pval; /*npp->c_dual[k] = dir * col->dval;*/ } } else if (npp->sol == GLP_MIP) { #if 0 for (i = 1; i <= npp->m; i++) { row = prob->row[i]; k = npp->row_ref[i]; /*npp->r_prim[k] = row->mipx;*/ } #endif for (j = 1; j <= npp->n; j++) { col = prob->col[j]; k = npp->col_ref[j]; npp->c_value[k] = col->mipx; } } else xassert(npp != npp); /* perform postprocessing to construct solution to the original problem */ for (tse = npp->top; tse != NULL; tse = tse->link) { xassert(tse->func != NULL); xassert(tse->func(npp, tse->info) == 0); } return; } void npp_unload_sol(NPP *npp, glp_prob *orig) { /* store solution to the original problem */ GLPROW *row; GLPCOL *col; int i, j; double dir; xassert(npp->orig_dir == orig->dir); if (npp->orig_dir == GLP_MIN) dir = +1.0; else if (npp->orig_dir == GLP_MAX) dir = -1.0; else xassert(npp != npp); xassert(npp->orig_m == orig->m); xassert(npp->orig_n == orig->n); xassert(npp->orig_nnz == orig->nnz); if (npp->sol == GLP_SOL) { /* store basic solution */ orig->valid = 0; orig->pbs_stat = npp->p_stat; orig->dbs_stat = npp->d_stat; orig->obj_val = orig->c0; orig->some = 0; for (i = 1; i <= orig->m; i++) { row = orig->row[i]; row->stat = npp->r_stat[i]; if (!npp->scaling) { /*row->prim = npp->r_prim[i];*/ row->dual = dir * npp->r_pi[i]; } else { /*row->prim = npp->r_prim[i] / row->rii;*/ row->dual = dir * npp->r_pi[i] * row->rii; } if (row->stat == GLP_BS) row->dual = 0.0; else if (row->stat == GLP_NL) { xassert(row->type == GLP_LO || row->type == GLP_DB); row->prim = row->lb; } else if (row->stat == GLP_NU) { xassert(row->type == GLP_UP || row->type == GLP_DB); row->prim = row->ub; } else if (row->stat == GLP_NF) { xassert(row->type == GLP_FR); row->prim = 0.0; } else if (row->stat == GLP_NS) { xassert(row->type == GLP_FX); row->prim = row->lb; } else xassert(row != row); } for (j = 1; j <= orig->n; j++) { col = orig->col[j]; col->stat = npp->c_stat[j]; if (!npp->scaling) { col->prim = npp->c_value[j]; /*col->dual = dir * npp->c_dual[j];*/ } else { col->prim = npp->c_value[j] * col->sjj; /*col->dual = dir * npp->c_dual[j] / col->sjj;*/ } if (col->stat == GLP_BS) col->dual = 0.0; #if 1 else if (col->stat == GLP_NL) { xassert(col->type == GLP_LO || col->type == GLP_DB); col->prim = col->lb; } else if (col->stat == GLP_NU) { xassert(col->type == GLP_UP || col->type == GLP_DB); col->prim = col->ub; } else if (col->stat == GLP_NF) { xassert(col->type == GLP_FR); col->prim = 0.0; } else if (col->stat == GLP_NS) { xassert(col->type == GLP_FX); col->prim = col->lb; } else xassert(col != col); #endif orig->obj_val += col->coef * col->prim; } #if 1 /* compute primal values of inactive rows */ for (i = 1; i <= orig->m; i++) { row = orig->row[i]; if (row->stat == GLP_BS) { GLPAIJ *aij; double temp; temp = 0.0; for (aij = row->ptr; aij != NULL; aij = aij->r_next) temp += aij->val * aij->col->prim; row->prim = temp; } } /* compute reduced costs of active columns */ for (j = 1; j <= orig->n; j++) { col = orig->col[j]; if (col->stat != GLP_BS) { GLPAIJ *aij; double temp; temp = col->coef; for (aij = col->ptr; aij != NULL; aij = aij->c_next) temp -= aij->val * aij->row->dual; col->dual = temp; } } #endif } else if (npp->sol == GLP_IPT) { /* store interior-point solution */ orig->ipt_stat = npp->t_stat; orig->ipt_obj = orig->c0; for (i = 1; i <= orig->m; i++) { row = orig->row[i]; if (!npp->scaling) { /*row->pval = npp->r_prim[i];*/ row->dval = dir * npp->r_pi[i]; } else { /*row->pval = npp->r_prim[i] / row->rii;*/ row->dval = dir * npp->r_pi[i] * row->rii; } } for (j = 1; j <= orig->n; j++) { col = orig->col[j]; if (!npp->scaling) { col->pval = npp->c_value[j]; /*col->dval = dir * npp->c_dual[j];*/ } else { col->pval = npp->c_value[j] * col->sjj; /*col->dval = dir * npp->c_dual[j] / col->sjj;*/ } orig->ipt_obj += col->coef * col->pval; } #if 1 /* compute row primal values */ for (i = 1; i <= orig->m; i++) { row = orig->row[i]; { GLPAIJ *aij; double temp; temp = 0.0; for (aij = row->ptr; aij != NULL; aij = aij->r_next) temp += aij->val * aij->col->pval; row->pval = temp; } } /* compute column dual values */ for (j = 1; j <= orig->n; j++) { col = orig->col[j]; { GLPAIJ *aij; double temp; temp = col->coef; for (aij = col->ptr; aij != NULL; aij = aij->c_next) temp -= aij->val * aij->row->dval; col->dval = temp; } } #endif } else if (npp->sol == GLP_MIP) { /* store MIP solution */ xassert(!npp->scaling); orig->mip_stat = npp->i_stat; orig->mip_obj = orig->c0; #if 0 for (i = 1; i <= orig->m; i++) { row = orig->row[i]; /*row->mipx = npp->r_prim[i];*/ } #endif for (j = 1; j <= orig->n; j++) { col = orig->col[j]; col->mipx = npp->c_value[j]; if (col->kind == GLP_IV) xassert(col->mipx == floor(col->mipx)); orig->mip_obj += col->coef * col->mipx; } #if 1 /* compute row primal values */ for (i = 1; i <= orig->m; i++) { row = orig->row[i]; { GLPAIJ *aij; double temp; temp = 0.0; for (aij = row->ptr; aij != NULL; aij = aij->r_next) temp += aij->val * aij->col->mipx; row->mipx = temp; } } #endif } else xassert(npp != npp); return; } void npp_delete_wksp(NPP *npp) { /* delete LP/MIP preprocessor workspace */ if (npp->pool != NULL) dmp_delete_pool(npp->pool); if (npp->stack != NULL) dmp_delete_pool(npp->stack); if (npp->row_ref != NULL) xfree(npp->row_ref); if (npp->col_ref != NULL) xfree(npp->col_ref); if (npp->r_stat != NULL) xfree(npp->r_stat); #if 0 if (npp->r_prim != NULL) xfree(npp->r_prim); #endif if (npp->r_pi != NULL) xfree(npp->r_pi); if (npp->c_stat != NULL) xfree(npp->c_stat); if (npp->c_value != NULL) xfree(npp->c_value); #if 0 if (npp->c_dual != NULL) xfree(npp->c_dual); #endif xfree(npp); return; } /* eof */ sources_5316/external/glpk/glpenv02.c0000644000176700017670000000410511401660400016273 0ustar paulpaul/* glpenv02.c (thread local storage) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" static void *tls = NULL; /* in a re-entrant version of the package this variable must be placed in the Thread Local Storage (TLS) */ /*********************************************************************** * NAME * * tls_set_ptr - store global pointer in TLS * * SYNOPSIS * * #include "glpenv.h" * void tls_set_ptr(void *ptr); * * DESCRIPTION * * The routine tls_set_ptr stores a pointer specified by the parameter * ptr in the Thread Local Storage (TLS). */ void tls_set_ptr(void *ptr) { tls = ptr; return; } /*********************************************************************** * NAME * * tls_get_ptr - retrieve global pointer from TLS * * SYNOPSIS * * #include "glpenv.h" * void *tls_get_ptr(void); * * RETURNS * * The routine tls_get_ptr returns a pointer previously stored by the * routine tls_set_ptr. If the latter has not been called yet, NULL is * returned. */ void *tls_get_ptr(void) { void *ptr; ptr = tls; return ptr; } /* eof */ sources_5316/external/glpk/glpmpl03.c0000644000176700017670000064541011411455471016321 0ustar paulpaul/* glpmpl03.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_ERRNO #define _GLPSTD_STDIO #include "glpenv.h" #include "glpmpl.h" /**********************************************************************/ /* * * FLOATING-POINT NUMBERS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- fp_add - floating-point addition. -- -- This routine computes the sum x + y. */ double fp_add(MPL *mpl, double x, double y) { if (x > 0.0 && y > 0.0 && x > + 0.999 * DBL_MAX - y || x < 0.0 && y < 0.0 && x < - 0.999 * DBL_MAX - y) mpl_error(mpl, "%.*g + %.*g; floating-point overflow", DBL_DIG, x, DBL_DIG, y); return x + y; } /*---------------------------------------------------------------------- -- fp_sub - floating-point subtraction. -- -- This routine computes the difference x - y. */ double fp_sub(MPL *mpl, double x, double y) { if (x > 0.0 && y < 0.0 && x > + 0.999 * DBL_MAX + y || x < 0.0 && y > 0.0 && x < - 0.999 * DBL_MAX + y) mpl_error(mpl, "%.*g - %.*g; floating-point overflow", DBL_DIG, x, DBL_DIG, y); return x - y; } /*---------------------------------------------------------------------- -- fp_less - floating-point non-negative subtraction. -- -- This routine computes the non-negative difference max(0, x - y). */ double fp_less(MPL *mpl, double x, double y) { if (x < y) return 0.0; if (x > 0.0 && y < 0.0 && x > + 0.999 * DBL_MAX + y) mpl_error(mpl, "%.*g less %.*g; floating-point overflow", DBL_DIG, x, DBL_DIG, y); return x - y; } /*---------------------------------------------------------------------- -- fp_mul - floating-point multiplication. -- -- This routine computes the product x * y. */ double fp_mul(MPL *mpl, double x, double y) { if (fabs(y) > 1.0 && fabs(x) > (0.999 * DBL_MAX) / fabs(y)) mpl_error(mpl, "%.*g * %.*g; floating-point overflow", DBL_DIG, x, DBL_DIG, y); return x * y; } /*---------------------------------------------------------------------- -- fp_div - floating-point division. -- -- This routine computes the quotient x / y. */ double fp_div(MPL *mpl, double x, double y) { if (fabs(y) < DBL_MIN) mpl_error(mpl, "%.*g / %.*g; floating-point zero divide", DBL_DIG, x, DBL_DIG, y); if (fabs(y) < 1.0 && fabs(x) > (0.999 * DBL_MAX) * fabs(y)) mpl_error(mpl, "%.*g / %.*g; floating-point overflow", DBL_DIG, x, DBL_DIG, y); return x / y; } /*---------------------------------------------------------------------- -- fp_idiv - floating-point quotient of exact division. -- -- This routine computes the quotient of exact division x div y. */ double fp_idiv(MPL *mpl, double x, double y) { if (fabs(y) < DBL_MIN) mpl_error(mpl, "%.*g div %.*g; floating-point zero divide", DBL_DIG, x, DBL_DIG, y); if (fabs(y) < 1.0 && fabs(x) > (0.999 * DBL_MAX) * fabs(y)) mpl_error(mpl, "%.*g div %.*g; floating-point overflow", DBL_DIG, x, DBL_DIG, y); x /= y; return x > 0.0 ? floor(x) : x < 0.0 ? ceil(x) : 0.0; } /*---------------------------------------------------------------------- -- fp_mod - floating-point remainder of exact division. -- -- This routine computes the remainder of exact division x mod y. -- -- NOTE: By definition x mod y = x - y * floor(x / y). */ double fp_mod(MPL *mpl, double x, double y) { double r; xassert(mpl == mpl); if (x == 0.0) r = 0.0; else if (y == 0.0) r = x; else { r = fmod(fabs(x), fabs(y)); if (r != 0.0) { if (x < 0.0) r = - r; if (x > 0.0 && y < 0.0 || x < 0.0 && y > 0.0) r += y; } } return r; } /*---------------------------------------------------------------------- -- fp_power - floating-point exponentiation (raise to power). -- -- This routine computes the exponentiation x ** y. */ double fp_power(MPL *mpl, double x, double y) { double r; if (x == 0.0 && y <= 0.0 || x < 0.0 && y != floor(y)) mpl_error(mpl, "%.*g ** %.*g; result undefined", DBL_DIG, x, DBL_DIG, y); if (x == 0.0) goto eval; if (fabs(x) > 1.0 && y > +1.0 && +log(fabs(x)) > (0.999 * log(DBL_MAX)) / y || fabs(x) < 1.0 && y < -1.0 && +log(fabs(x)) < (0.999 * log(DBL_MAX)) / y) mpl_error(mpl, "%.*g ** %.*g; floating-point overflow", DBL_DIG, x, DBL_DIG, y); if (fabs(x) > 1.0 && y < -1.0 && -log(fabs(x)) < (0.999 * log(DBL_MAX)) / y || fabs(x) < 1.0 && y > +1.0 && -log(fabs(x)) > (0.999 * log(DBL_MAX)) / y) r = 0.0; else eval: r = pow(x, y); return r; } /*---------------------------------------------------------------------- -- fp_exp - floating-point base-e exponential. -- -- This routine computes the base-e exponential e ** x. */ double fp_exp(MPL *mpl, double x) { if (x > 0.999 * log(DBL_MAX)) mpl_error(mpl, "exp(%.*g); floating-point overflow", DBL_DIG, x); return exp(x); } /*---------------------------------------------------------------------- -- fp_log - floating-point natural logarithm. -- -- This routine computes the natural logarithm log x. */ double fp_log(MPL *mpl, double x) { if (x <= 0.0) mpl_error(mpl, "log(%.*g); non-positive argument", DBL_DIG, x); return log(x); } /*---------------------------------------------------------------------- -- fp_log10 - floating-point common (decimal) logarithm. -- -- This routine computes the common (decimal) logarithm lg x. */ double fp_log10(MPL *mpl, double x) { if (x <= 0.0) mpl_error(mpl, "log10(%.*g); non-positive argument", DBL_DIG, x); return log10(x); } /*---------------------------------------------------------------------- -- fp_sqrt - floating-point square root. -- -- This routine computes the square root x ** 0.5. */ double fp_sqrt(MPL *mpl, double x) { if (x < 0.0) mpl_error(mpl, "sqrt(%.*g); negative argument", DBL_DIG, x); return sqrt(x); } /*---------------------------------------------------------------------- -- fp_sin - floating-point trigonometric sine. -- -- This routine computes the trigonometric sine sin(x). */ double fp_sin(MPL *mpl, double x) { if (!(-1e6 <= x && x <= +1e6)) mpl_error(mpl, "sin(%.*g); argument too large", DBL_DIG, x); return sin(x); } /*---------------------------------------------------------------------- -- fp_cos - floating-point trigonometric cosine. -- -- This routine computes the trigonometric cosine cos(x). */ double fp_cos(MPL *mpl, double x) { if (!(-1e6 <= x && x <= +1e6)) mpl_error(mpl, "cos(%.*g); argument too large", DBL_DIG, x); return cos(x); } /*---------------------------------------------------------------------- -- fp_atan - floating-point trigonometric arctangent. -- -- This routine computes the trigonometric arctangent atan(x). */ double fp_atan(MPL *mpl, double x) { xassert(mpl == mpl); return atan(x); } /*---------------------------------------------------------------------- -- fp_atan2 - floating-point trigonometric arctangent. -- -- This routine computes the trigonometric arctangent atan(y / x). */ double fp_atan2(MPL *mpl, double y, double x) { xassert(mpl == mpl); return atan2(y, x); } /*---------------------------------------------------------------------- -- fp_round - round floating-point value to n fractional digits. -- -- This routine rounds given floating-point value x to n fractional -- digits with the formula: -- -- round(x, n) = floor(x * 10^n + 0.5) / 10^n. -- -- The parameter n is assumed to be integer. */ double fp_round(MPL *mpl, double x, double n) { double ten_to_n; if (n != floor(n)) mpl_error(mpl, "round(%.*g, %.*g); non-integer second argument", DBL_DIG, x, DBL_DIG, n); if (n <= DBL_DIG + 2) { ten_to_n = pow(10.0, n); if (fabs(x) < (0.999 * DBL_MAX) / ten_to_n) { x = floor(x * ten_to_n + 0.5); if (x != 0.0) x /= ten_to_n; } } return x; } /*---------------------------------------------------------------------- -- fp_trunc - truncate floating-point value to n fractional digits. -- -- This routine truncates given floating-point value x to n fractional -- digits with the formula: -- -- ( floor(x * 10^n) / 10^n, if x >= 0 -- trunc(x, n) = < -- ( ceil(x * 10^n) / 10^n, if x < 0 -- -- The parameter n is assumed to be integer. */ double fp_trunc(MPL *mpl, double x, double n) { double ten_to_n; if (n != floor(n)) mpl_error(mpl, "trunc(%.*g, %.*g); non-integer second argument", DBL_DIG, x, DBL_DIG, n); if (n <= DBL_DIG + 2) { ten_to_n = pow(10.0, n); if (fabs(x) < (0.999 * DBL_MAX) / ten_to_n) { x = (x >= 0.0 ? floor(x * ten_to_n) : ceil(x * ten_to_n)); if (x != 0.0) x /= ten_to_n; } } return x; } /**********************************************************************/ /* * * PSEUDO-RANDOM NUMBER GENERATORS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- fp_irand224 - pseudo-random integer in the range [0, 2^24). -- -- This routine returns a next pseudo-random integer (converted to -- floating-point) which is uniformly distributed between 0 and 2^24-1, -- inclusive. */ #define two_to_the_24 0x1000000 double fp_irand224(MPL *mpl) { return (double)rng_unif_rand(mpl->rand, two_to_the_24); } /*---------------------------------------------------------------------- -- fp_uniform01 - pseudo-random number in the range [0, 1). -- -- This routine returns a next pseudo-random number which is uniformly -- distributed in the range [0, 1). */ #define two_to_the_31 ((unsigned int)0x80000000) double fp_uniform01(MPL *mpl) { return (double)rng_next_rand(mpl->rand) / (double)two_to_the_31; } /*---------------------------------------------------------------------- -- fp_uniform - pseudo-random number in the range [a, b). -- -- This routine returns a next pseudo-random number which is uniformly -- distributed in the range [a, b). */ double fp_uniform(MPL *mpl, double a, double b) { double x; if (a >= b) mpl_error(mpl, "Uniform(%.*g, %.*g); invalid range", DBL_DIG, a, DBL_DIG, b); x = fp_uniform01(mpl); #if 0 x = a * (1.0 - x) + b * x; #else x = fp_add(mpl, a * (1.0 - x), b * x); #endif return x; } /*---------------------------------------------------------------------- -- fp_normal01 - Gaussian random variate with mu = 0 and sigma = 1. -- -- This routine returns a Gaussian random variate with zero mean and -- unit standard deviation. The polar (Box-Mueller) method is used. -- -- This code is a modified version of the routine gsl_ran_gaussian from -- the GNU Scientific Library Version 1.0. */ double fp_normal01(MPL *mpl) { double x, y, r2; do { /* choose x, y in uniform square (-1,-1) to (+1,+1) */ x = -1.0 + 2.0 * fp_uniform01(mpl); y = -1.0 + 2.0 * fp_uniform01(mpl); /* see if it is in the unit circle */ r2 = x * x + y * y; } while (r2 > 1.0 || r2 == 0.0); /* Box-Muller transform */ return y * sqrt(-2.0 * log (r2) / r2); } /*---------------------------------------------------------------------- -- fp_normal - Gaussian random variate with specified mu and sigma. -- -- This routine returns a Gaussian random variate with mean mu and -- standard deviation sigma. */ double fp_normal(MPL *mpl, double mu, double sigma) { double x; #if 0 x = mu + sigma * fp_normal01(mpl); #else x = fp_add(mpl, mu, fp_mul(mpl, sigma, fp_normal01(mpl))); #endif return x; } /**********************************************************************/ /* * * SEGMENTED CHARACTER STRINGS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- create_string - create character string. -- -- This routine creates a segmented character string, which is exactly -- equivalent to specified character string. */ STRING *create_string ( MPL *mpl, char buf[MAX_LENGTH+1] /* not changed */ ) #if 0 { STRING *head, *tail; int i, j; xassert(buf != NULL); xassert(strlen(buf) <= MAX_LENGTH); head = tail = dmp_get_atom(mpl->strings, sizeof(STRING)); for (i = j = 0; ; i++) { if ((tail->seg[j++] = buf[i]) == '\0') break; if (j == STRSEG_SIZE) tail = (tail->next = dmp_get_atom(mpl->strings, sizeof(STRING))), j = 0; } tail->next = NULL; return head; } #else { STRING *str; xassert(strlen(buf) <= MAX_LENGTH); str = dmp_get_atom(mpl->strings, strlen(buf)+1); strcpy(str, buf); return str; } #endif /*---------------------------------------------------------------------- -- copy_string - make copy of character string. -- -- This routine returns an exact copy of segmented character string. */ STRING *copy_string ( MPL *mpl, STRING *str /* not changed */ ) #if 0 { STRING *head, *tail; xassert(str != NULL); head = tail = dmp_get_atom(mpl->strings, sizeof(STRING)); for (; str != NULL; str = str->next) { memcpy(tail->seg, str->seg, STRSEG_SIZE); if (str->next != NULL) tail = (tail->next = dmp_get_atom(mpl->strings, sizeof(STRING))); } tail->next = NULL; return head; } #else { xassert(mpl == mpl); return create_string(mpl, str); } #endif /*---------------------------------------------------------------------- -- compare_strings - compare one character string with another. -- -- This routine compares one segmented character strings with another -- and returns the result of comparison as follows: -- -- = 0 - both strings are identical; -- < 0 - the first string precedes the second one; -- > 0 - the first string follows the second one. */ int compare_strings ( MPL *mpl, STRING *str1, /* not changed */ STRING *str2 /* not changed */ ) #if 0 { int j, c1, c2; xassert(mpl == mpl); for (;; str1 = str1->next, str2 = str2->next) { xassert(str1 != NULL); xassert(str2 != NULL); for (j = 0; j < STRSEG_SIZE; j++) { c1 = (unsigned char)str1->seg[j]; c2 = (unsigned char)str2->seg[j]; if (c1 < c2) return -1; if (c1 > c2) return +1; if (c1 == '\0') goto done; } } done: return 0; } #else { xassert(mpl == mpl); return strcmp(str1, str2); } #endif /*---------------------------------------------------------------------- -- fetch_string - extract content of character string. -- -- This routine returns a character string, which is exactly equivalent -- to specified segmented character string. */ char *fetch_string ( MPL *mpl, STRING *str, /* not changed */ char buf[MAX_LENGTH+1] /* modified */ ) #if 0 { int i, j; xassert(mpl == mpl); xassert(buf != NULL); for (i = 0; ; str = str->next) { xassert(str != NULL); for (j = 0; j < STRSEG_SIZE; j++) if ((buf[i++] = str->seg[j]) == '\0') goto done; } done: xassert(strlen(buf) <= MAX_LENGTH); return buf; } #else { xassert(mpl == mpl); return strcpy(buf, str); } #endif /*---------------------------------------------------------------------- -- delete_string - delete character string. -- -- This routine deletes specified segmented character string. */ void delete_string ( MPL *mpl, STRING *str /* destroyed */ ) #if 0 { STRING *temp; xassert(str != NULL); while (str != NULL) { temp = str; str = str->next; dmp_free_atom(mpl->strings, temp, sizeof(STRING)); } return; } #else { dmp_free_atom(mpl->strings, str, strlen(str)+1); return; } #endif /**********************************************************************/ /* * * SYMBOLS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- create_symbol_num - create symbol of numeric type. -- -- This routine creates a symbol, which has a numeric value specified -- as floating-point number. */ SYMBOL *create_symbol_num(MPL *mpl, double num) { SYMBOL *sym; sym = dmp_get_atom(mpl->symbols, sizeof(SYMBOL)); sym->num = num; sym->str = NULL; return sym; } /*---------------------------------------------------------------------- -- create_symbol_str - create symbol of abstract type. -- -- This routine creates a symbol, which has an abstract value specified -- as segmented character string. */ SYMBOL *create_symbol_str ( MPL *mpl, STRING *str /* destroyed */ ) { SYMBOL *sym; xassert(str != NULL); sym = dmp_get_atom(mpl->symbols, sizeof(SYMBOL)); sym->num = 0.0; sym->str = str; return sym; } /*---------------------------------------------------------------------- -- copy_symbol - make copy of symbol. -- -- This routine returns an exact copy of symbol. */ SYMBOL *copy_symbol ( MPL *mpl, SYMBOL *sym /* not changed */ ) { SYMBOL *copy; xassert(sym != NULL); copy = dmp_get_atom(mpl->symbols, sizeof(SYMBOL)); if (sym->str == NULL) { copy->num = sym->num; copy->str = NULL; } else { copy->num = 0.0; copy->str = copy_string(mpl, sym->str); } return copy; } /*---------------------------------------------------------------------- -- compare_symbols - compare one symbol with another. -- -- This routine compares one symbol with another and returns the result -- of comparison as follows: -- -- = 0 - both symbols are identical; -- < 0 - the first symbol precedes the second one; -- > 0 - the first symbol follows the second one. -- -- Note that the linear order, in which symbols follow each other, is -- implementation-dependent. It may be not an alphabetical order. */ int compare_symbols ( MPL *mpl, SYMBOL *sym1, /* not changed */ SYMBOL *sym2 /* not changed */ ) { xassert(sym1 != NULL); xassert(sym2 != NULL); /* let all numeric quantities precede all symbolic quantities */ if (sym1->str == NULL && sym2->str == NULL) { if (sym1->num < sym2->num) return -1; if (sym1->num > sym2->num) return +1; return 0; } if (sym1->str == NULL) return -1; if (sym2->str == NULL) return +1; return compare_strings(mpl, sym1->str, sym2->str); } /*---------------------------------------------------------------------- -- delete_symbol - delete symbol. -- -- This routine deletes specified symbol. */ void delete_symbol ( MPL *mpl, SYMBOL *sym /* destroyed */ ) { xassert(sym != NULL); if (sym->str != NULL) delete_string(mpl, sym->str); dmp_free_atom(mpl->symbols, sym, sizeof(SYMBOL)); return; } /*---------------------------------------------------------------------- -- format_symbol - format symbol for displaying or printing. -- -- This routine converts specified symbol to a charater string, which -- is suitable for displaying or printing. -- -- The resultant string is never longer than 255 characters. If it gets -- longer, it is truncated from the right and appended by dots. */ char *format_symbol ( MPL *mpl, SYMBOL *sym /* not changed */ ) { char *buf = mpl->sym_buf; xassert(sym != NULL); if (sym->str == NULL) sprintf(buf, "%.*g", DBL_DIG, sym->num); else { char str[MAX_LENGTH+1]; int quoted, j, len; fetch_string(mpl, sym->str, str); if (!(isalpha((unsigned char)str[0]) || str[0] == '_')) quoted = 1; else { quoted = 0; for (j = 1; str[j] != '\0'; j++) { if (!(isalnum((unsigned char)str[j]) || strchr("+-._", (unsigned char)str[j]) != NULL)) { quoted = 1; break; } } } # define safe_append(c) \ (void)(len < 255 ? (buf[len++] = (char)(c)) : 0) buf[0] = '\0', len = 0; if (quoted) safe_append('\''); for (j = 0; str[j] != '\0'; j++) { if (quoted && str[j] == '\'') safe_append('\''); safe_append(str[j]); } if (quoted) safe_append('\''); # undef safe_append buf[len] = '\0'; if (len == 255) strcpy(buf+252, "..."); } xassert(strlen(buf) <= 255); return buf; } /*---------------------------------------------------------------------- -- concat_symbols - concatenate one symbol with another. -- -- This routine concatenates values of two given symbols and assigns -- the resultant character string to a new symbol, which is returned on -- exit. Both original symbols are destroyed. */ SYMBOL *concat_symbols ( MPL *mpl, SYMBOL *sym1, /* destroyed */ SYMBOL *sym2 /* destroyed */ ) { char str1[MAX_LENGTH+1], str2[MAX_LENGTH+1]; xassert(MAX_LENGTH >= DBL_DIG + DBL_DIG); if (sym1->str == NULL) sprintf(str1, "%.*g", DBL_DIG, sym1->num); else fetch_string(mpl, sym1->str, str1); if (sym2->str == NULL) sprintf(str2, "%.*g", DBL_DIG, sym2->num); else fetch_string(mpl, sym2->str, str2); if (strlen(str1) + strlen(str2) > MAX_LENGTH) { char buf[255+1]; strcpy(buf, format_symbol(mpl, sym1)); xassert(strlen(buf) < sizeof(buf)); mpl_error(mpl, "%s & %s; resultant symbol exceeds %d characters", buf, format_symbol(mpl, sym2), MAX_LENGTH); } delete_symbol(mpl, sym1); delete_symbol(mpl, sym2); return create_symbol_str(mpl, create_string(mpl, strcat(str1, str2))); } /**********************************************************************/ /* * * N-TUPLES * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- create_tuple - create n-tuple. -- -- This routine creates a n-tuple, which initially has no components, -- i.e. which is 0-tuple. */ TUPLE *create_tuple(MPL *mpl) { TUPLE *tuple; xassert(mpl == mpl); tuple = NULL; return tuple; } /*---------------------------------------------------------------------- -- expand_tuple - append symbol to n-tuple. -- -- This routine expands n-tuple appending to it a given symbol, which -- becomes its new last component. */ TUPLE *expand_tuple ( MPL *mpl, TUPLE *tuple, /* destroyed */ SYMBOL *sym /* destroyed */ ) { TUPLE *tail, *temp; xassert(sym != NULL); /* create a new component */ tail = dmp_get_atom(mpl->tuples, sizeof(TUPLE)); tail->sym = sym; tail->next = NULL; /* and append it to the component list */ if (tuple == NULL) tuple = tail; else { for (temp = tuple; temp->next != NULL; temp = temp->next); temp->next = tail; } return tuple; } /*---------------------------------------------------------------------- -- tuple_dimen - determine dimension of n-tuple. -- -- This routine returns dimension of n-tuple, i.e. number of components -- in the n-tuple. */ int tuple_dimen ( MPL *mpl, TUPLE *tuple /* not changed */ ) { TUPLE *temp; int dim = 0; xassert(mpl == mpl); for (temp = tuple; temp != NULL; temp = temp->next) dim++; return dim; } /*---------------------------------------------------------------------- -- copy_tuple - make copy of n-tuple. -- -- This routine returns an exact copy of n-tuple. */ TUPLE *copy_tuple ( MPL *mpl, TUPLE *tuple /* not changed */ ) { TUPLE *head, *tail; if (tuple == NULL) head = NULL; else { head = tail = dmp_get_atom(mpl->tuples, sizeof(TUPLE)); for (; tuple != NULL; tuple = tuple->next) { xassert(tuple->sym != NULL); tail->sym = copy_symbol(mpl, tuple->sym); if (tuple->next != NULL) tail = (tail->next = dmp_get_atom(mpl->tuples, sizeof(TUPLE))); } tail->next = NULL; } return head; } /*---------------------------------------------------------------------- -- compare_tuples - compare one n-tuple with another. -- -- This routine compares two given n-tuples, which must have the same -- dimension (not checked for the sake of efficiency), and returns one -- of the following codes: -- -- = 0 - both n-tuples are identical; -- < 0 - the first n-tuple precedes the second one; -- > 0 - the first n-tuple follows the second one. -- -- Note that the linear order, in which n-tuples follow each other, is -- implementation-dependent. It may be not an alphabetical order. */ int compare_tuples ( MPL *mpl, TUPLE *tuple1, /* not changed */ TUPLE *tuple2 /* not changed */ ) { TUPLE *item1, *item2; int ret; xassert(mpl == mpl); for (item1 = tuple1, item2 = tuple2; item1 != NULL; item1 = item1->next, item2 = item2->next) { xassert(item2 != NULL); xassert(item1->sym != NULL); xassert(item2->sym != NULL); ret = compare_symbols(mpl, item1->sym, item2->sym); if (ret != 0) return ret; } xassert(item2 == NULL); return 0; } /*---------------------------------------------------------------------- -- build_subtuple - build subtuple of given n-tuple. -- -- This routine builds subtuple, which consists of first dim components -- of given n-tuple. */ TUPLE *build_subtuple ( MPL *mpl, TUPLE *tuple, /* not changed */ int dim ) { TUPLE *head, *temp; int j; head = create_tuple(mpl); for (j = 1, temp = tuple; j <= dim; j++, temp = temp->next) { xassert(temp != NULL); head = expand_tuple(mpl, head, copy_symbol(mpl, temp->sym)); } return head; } /*---------------------------------------------------------------------- -- delete_tuple - delete n-tuple. -- -- This routine deletes specified n-tuple. */ void delete_tuple ( MPL *mpl, TUPLE *tuple /* destroyed */ ) { TUPLE *temp; while (tuple != NULL) { temp = tuple; tuple = temp->next; xassert(temp->sym != NULL); delete_symbol(mpl, temp->sym); dmp_free_atom(mpl->tuples, temp, sizeof(TUPLE)); } return; } /*---------------------------------------------------------------------- -- format_tuple - format n-tuple for displaying or printing. -- -- This routine converts specified n-tuple to a character string, which -- is suitable for displaying or printing. -- -- The resultant string is never longer than 255 characters. If it gets -- longer, it is truncated from the right and appended by dots. */ char *format_tuple ( MPL *mpl, int c, TUPLE *tuple /* not changed */ ) { TUPLE *temp; int dim, j, len; char *buf = mpl->tup_buf, str[255+1], *save; # define safe_append(c) \ (void)(len < 255 ? (buf[len++] = (char)(c)) : 0) buf[0] = '\0', len = 0; dim = tuple_dimen(mpl, tuple); if (c == '[' && dim > 0) safe_append('['); if (c == '(' && dim > 1) safe_append('('); for (temp = tuple; temp != NULL; temp = temp->next) { if (temp != tuple) safe_append(','); xassert(temp->sym != NULL); save = mpl->sym_buf; mpl->sym_buf = str; format_symbol(mpl, temp->sym); mpl->sym_buf = save; xassert(strlen(str) < sizeof(str)); for (j = 0; str[j] != '\0'; j++) safe_append(str[j]); } if (c == '[' && dim > 0) safe_append(']'); if (c == '(' && dim > 1) safe_append(')'); # undef safe_append buf[len] = '\0'; if (len == 255) strcpy(buf+252, "..."); xassert(strlen(buf) <= 255); return buf; } /**********************************************************************/ /* * * ELEMENTAL SETS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- create_elemset - create elemental set. -- -- This routine creates an elemental set, whose members are n-tuples of -- specified dimension. Being created the set is initially empty. */ ELEMSET *create_elemset(MPL *mpl, int dim) { ELEMSET *set; xassert(dim > 0); set = create_array(mpl, A_NONE, dim); return set; } /*---------------------------------------------------------------------- -- find_tuple - check if elemental set contains given n-tuple. -- -- This routine finds given n-tuple in specified elemental set in order -- to check if the set contains that n-tuple. If the n-tuple is found, -- the routine returns pointer to corresponding array member. Otherwise -- null pointer is returned. */ MEMBER *find_tuple ( MPL *mpl, ELEMSET *set, /* not changed */ TUPLE *tuple /* not changed */ ) { xassert(set != NULL); xassert(set->type == A_NONE); xassert(set->dim == tuple_dimen(mpl, tuple)); return find_member(mpl, set, tuple); } /*---------------------------------------------------------------------- -- add_tuple - add new n-tuple to elemental set. -- -- This routine adds given n-tuple to specified elemental set. -- -- For the sake of efficiency this routine doesn't check whether the -- set already contains the same n-tuple or not. Therefore the calling -- program should use the routine find_tuple (if necessary) in order to -- make sure that the given n-tuple is not contained in the set, since -- duplicate n-tuples within the same set are not allowed. */ MEMBER *add_tuple ( MPL *mpl, ELEMSET *set, /* modified */ TUPLE *tuple /* destroyed */ ) { MEMBER *memb; xassert(set != NULL); xassert(set->type == A_NONE); xassert(set->dim == tuple_dimen(mpl, tuple)); memb = add_member(mpl, set, tuple); memb->value.none = NULL; return memb; } /*---------------------------------------------------------------------- -- check_then_add - check and add new n-tuple to elemental set. -- -- This routine is equivalent to the routine add_tuple except that it -- does check for duplicate n-tuples. */ MEMBER *check_then_add ( MPL *mpl, ELEMSET *set, /* modified */ TUPLE *tuple /* destroyed */ ) { if (find_tuple(mpl, set, tuple) != NULL) mpl_error(mpl, "duplicate tuple %s detected", format_tuple(mpl, '(', tuple)); return add_tuple(mpl, set, tuple); } /*---------------------------------------------------------------------- -- copy_elemset - make copy of elemental set. -- -- This routine makes an exact copy of elemental set. */ ELEMSET *copy_elemset ( MPL *mpl, ELEMSET *set /* not changed */ ) { ELEMSET *copy; MEMBER *memb; xassert(set != NULL); xassert(set->type == A_NONE); xassert(set->dim > 0); copy = create_elemset(mpl, set->dim); for (memb = set->head; memb != NULL; memb = memb->next) add_tuple(mpl, copy, copy_tuple(mpl, memb->tuple)); return copy; } /*---------------------------------------------------------------------- -- delete_elemset - delete elemental set. -- -- This routine deletes specified elemental set. */ void delete_elemset ( MPL *mpl, ELEMSET *set /* destroyed */ ) { xassert(set != NULL); xassert(set->type == A_NONE); delete_array(mpl, set); return; } /*---------------------------------------------------------------------- -- arelset_size - compute size of "arithmetic" elemental set. -- -- This routine computes the size of "arithmetic" elemental set, which -- is specified in the form of arithmetic progression: -- -- { t0 .. tf by dt }. -- -- The size is computed using the formula: -- -- n = max(0, floor((tf - t0) / dt) + 1). */ int arelset_size(MPL *mpl, double t0, double tf, double dt) { double temp; if (dt == 0.0) mpl_error(mpl, "%.*g .. %.*g by %.*g; zero stride not allowed", DBL_DIG, t0, DBL_DIG, tf, DBL_DIG, dt); if (tf > 0.0 && t0 < 0.0 && tf > + 0.999 * DBL_MAX + t0) temp = +DBL_MAX; else if (tf < 0.0 && t0 > 0.0 && tf < - 0.999 * DBL_MAX + t0) temp = -DBL_MAX; else temp = tf - t0; if (fabs(dt) < 1.0 && fabs(temp) > (0.999 * DBL_MAX) * fabs(dt)) { if (temp > 0.0 && dt > 0.0 || temp < 0.0 && dt < 0.0) temp = +DBL_MAX; else temp = 0.0; } else { temp = floor(temp / dt) + 1.0; if (temp < 0.0) temp = 0.0; } xassert(temp >= 0.0); if (temp > (double)(INT_MAX - 1)) mpl_error(mpl, "%.*g .. %.*g by %.*g; set too large", DBL_DIG, t0, DBL_DIG, tf, DBL_DIG, dt); return (int)(temp + 0.5); } /*---------------------------------------------------------------------- -- arelset_member - compute member of "arithmetic" elemental set. -- -- This routine returns a numeric value of symbol, which is equivalent -- to j-th member of given "arithmetic" elemental set specified in the -- form of arithmetic progression: -- -- { t0 .. tf by dt }. -- -- The symbol value is computed with the formula: -- -- j-th member = t0 + (j - 1) * dt, -- -- The number j must satisfy to the restriction 1 <= j <= n, where n is -- the set size computed by the routine arelset_size. */ double arelset_member(MPL *mpl, double t0, double tf, double dt, int j) { xassert(1 <= j && j <= arelset_size(mpl, t0, tf, dt)); return t0 + (double)(j - 1) * dt; } /*---------------------------------------------------------------------- -- create_arelset - create "arithmetic" elemental set. -- -- This routine creates "arithmetic" elemental set, which is specified -- in the form of arithmetic progression: -- -- { t0 .. tf by dt }. -- -- Components of this set are 1-tuples. */ ELEMSET *create_arelset(MPL *mpl, double t0, double tf, double dt) { ELEMSET *set; int j, n; set = create_elemset(mpl, 1); n = arelset_size(mpl, t0, tf, dt); for (j = 1; j <= n; j++) { add_tuple ( mpl, set, expand_tuple ( mpl, create_tuple(mpl), create_symbol_num ( mpl, arelset_member(mpl, t0, tf, dt, j) ) ) ); } return set; } /*---------------------------------------------------------------------- -- set_union - union of two elemental sets. -- -- This routine computes the union: -- -- X U Y = { j | (j in X) or (j in Y) }, -- -- where X and Y are given elemental sets (destroyed on exit). */ ELEMSET *set_union ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ) { MEMBER *memb; xassert(X != NULL); xassert(X->type == A_NONE); xassert(X->dim > 0); xassert(Y != NULL); xassert(Y->type == A_NONE); xassert(Y->dim > 0); xassert(X->dim == Y->dim); for (memb = Y->head; memb != NULL; memb = memb->next) { if (find_tuple(mpl, X, memb->tuple) == NULL) add_tuple(mpl, X, copy_tuple(mpl, memb->tuple)); } delete_elemset(mpl, Y); return X; } /*---------------------------------------------------------------------- -- set_diff - difference between two elemental sets. -- -- This routine computes the difference: -- -- X \ Y = { j | (j in X) and (j not in Y) }, -- -- where X and Y are given elemental sets (destroyed on exit). */ ELEMSET *set_diff ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ) { ELEMSET *Z; MEMBER *memb; xassert(X != NULL); xassert(X->type == A_NONE); xassert(X->dim > 0); xassert(Y != NULL); xassert(Y->type == A_NONE); xassert(Y->dim > 0); xassert(X->dim == Y->dim); Z = create_elemset(mpl, X->dim); for (memb = X->head; memb != NULL; memb = memb->next) { if (find_tuple(mpl, Y, memb->tuple) == NULL) add_tuple(mpl, Z, copy_tuple(mpl, memb->tuple)); } delete_elemset(mpl, X); delete_elemset(mpl, Y); return Z; } /*---------------------------------------------------------------------- -- set_symdiff - symmetric difference between two elemental sets. -- -- This routine computes the symmetric difference: -- -- X (+) Y = (X \ Y) U (Y \ X), -- -- where X and Y are given elemental sets (destroyed on exit). */ ELEMSET *set_symdiff ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ) { ELEMSET *Z; MEMBER *memb; xassert(X != NULL); xassert(X->type == A_NONE); xassert(X->dim > 0); xassert(Y != NULL); xassert(Y->type == A_NONE); xassert(Y->dim > 0); xassert(X->dim == Y->dim); /* Z := X \ Y */ Z = create_elemset(mpl, X->dim); for (memb = X->head; memb != NULL; memb = memb->next) { if (find_tuple(mpl, Y, memb->tuple) == NULL) add_tuple(mpl, Z, copy_tuple(mpl, memb->tuple)); } /* Z := Z U (Y \ X) */ for (memb = Y->head; memb != NULL; memb = memb->next) { if (find_tuple(mpl, X, memb->tuple) == NULL) add_tuple(mpl, Z, copy_tuple(mpl, memb->tuple)); } delete_elemset(mpl, X); delete_elemset(mpl, Y); return Z; } /*---------------------------------------------------------------------- -- set_inter - intersection of two elemental sets. -- -- This routine computes the intersection: -- -- X ^ Y = { j | (j in X) and (j in Y) }, -- -- where X and Y are given elemental sets (destroyed on exit). */ ELEMSET *set_inter ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ) { ELEMSET *Z; MEMBER *memb; xassert(X != NULL); xassert(X->type == A_NONE); xassert(X->dim > 0); xassert(Y != NULL); xassert(Y->type == A_NONE); xassert(Y->dim > 0); xassert(X->dim == Y->dim); Z = create_elemset(mpl, X->dim); for (memb = X->head; memb != NULL; memb = memb->next) { if (find_tuple(mpl, Y, memb->tuple) != NULL) add_tuple(mpl, Z, copy_tuple(mpl, memb->tuple)); } delete_elemset(mpl, X); delete_elemset(mpl, Y); return Z; } /*---------------------------------------------------------------------- -- set_cross - cross (Cartesian) product of two elemental sets. -- -- This routine computes the cross (Cartesian) product: -- -- X x Y = { (i,j) | (i in X) and (j in Y) }, -- -- where X and Y are given elemental sets (destroyed on exit). */ ELEMSET *set_cross ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ) { ELEMSET *Z; MEMBER *memx, *memy; TUPLE *tuple, *temp; xassert(X != NULL); xassert(X->type == A_NONE); xassert(X->dim > 0); xassert(Y != NULL); xassert(Y->type == A_NONE); xassert(Y->dim > 0); Z = create_elemset(mpl, X->dim + Y->dim); for (memx = X->head; memx != NULL; memx = memx->next) { for (memy = Y->head; memy != NULL; memy = memy->next) { tuple = copy_tuple(mpl, memx->tuple); for (temp = memy->tuple; temp != NULL; temp = temp->next) tuple = expand_tuple(mpl, tuple, copy_symbol(mpl, temp->sym)); add_tuple(mpl, Z, tuple); } } delete_elemset(mpl, X); delete_elemset(mpl, Y); return Z; } /**********************************************************************/ /* * * ELEMENTAL VARIABLES * * */ /**********************************************************************/ /* (there are no specific routines for elemental variables) */ /**********************************************************************/ /* * * LINEAR FORMS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- constant_term - create constant term. -- -- This routine creates the linear form, which is a constant term. */ FORMULA *constant_term(MPL *mpl, double coef) { FORMULA *form; if (coef == 0.0) form = NULL; else { form = dmp_get_atom(mpl->formulae, sizeof(FORMULA)); form->coef = coef; form->var = NULL; form->next = NULL; } return form; } /*---------------------------------------------------------------------- -- single_variable - create single variable. -- -- This routine creates the linear form, which is a single elemental -- variable. */ FORMULA *single_variable ( MPL *mpl, ELEMVAR *var /* referenced */ ) { FORMULA *form; xassert(var != NULL); form = dmp_get_atom(mpl->formulae, sizeof(FORMULA)); form->coef = 1.0; form->var = var; form->next = NULL; return form; } /*---------------------------------------------------------------------- -- copy_formula - make copy of linear form. -- -- This routine returns an exact copy of linear form. */ FORMULA *copy_formula ( MPL *mpl, FORMULA *form /* not changed */ ) { FORMULA *head, *tail; if (form == NULL) head = NULL; else { head = tail = dmp_get_atom(mpl->formulae, sizeof(FORMULA)); for (; form != NULL; form = form->next) { tail->coef = form->coef; tail->var = form->var; if (form->next != NULL) tail = (tail->next = dmp_get_atom(mpl->formulae, sizeof(FORMULA))); } tail->next = NULL; } return head; } /*---------------------------------------------------------------------- -- delete_formula - delete linear form. -- -- This routine deletes specified linear form. */ void delete_formula ( MPL *mpl, FORMULA *form /* destroyed */ ) { FORMULA *temp; while (form != NULL) { temp = form; form = form->next; dmp_free_atom(mpl->formulae, temp, sizeof(FORMULA)); } return; } /*---------------------------------------------------------------------- -- linear_comb - linear combination of two linear forms. -- -- This routine computes the linear combination: -- -- a * fx + b * fy, -- -- where a and b are numeric coefficients, fx and fy are linear forms -- (destroyed on exit). */ FORMULA *linear_comb ( MPL *mpl, double a, FORMULA *fx, /* destroyed */ double b, FORMULA *fy /* destroyed */ ) { FORMULA *form = NULL, *term, *temp; double c0 = 0.0; for (term = fx; term != NULL; term = term->next) { if (term->var == NULL) c0 = fp_add(mpl, c0, fp_mul(mpl, a, term->coef)); else term->var->temp = fp_add(mpl, term->var->temp, fp_mul(mpl, a, term->coef)); } for (term = fy; term != NULL; term = term->next) { if (term->var == NULL) c0 = fp_add(mpl, c0, fp_mul(mpl, b, term->coef)); else term->var->temp = fp_add(mpl, term->var->temp, fp_mul(mpl, b, term->coef)); } for (term = fx; term != NULL; term = term->next) { if (term->var != NULL && term->var->temp != 0.0) { temp = dmp_get_atom(mpl->formulae, sizeof(FORMULA)); temp->coef = term->var->temp, temp->var = term->var; temp->next = form, form = temp; term->var->temp = 0.0; } } for (term = fy; term != NULL; term = term->next) { if (term->var != NULL && term->var->temp != 0.0) { temp = dmp_get_atom(mpl->formulae, sizeof(FORMULA)); temp->coef = term->var->temp, temp->var = term->var; temp->next = form, form = temp; term->var->temp = 0.0; } } if (c0 != 0.0) { temp = dmp_get_atom(mpl->formulae, sizeof(FORMULA)); temp->coef = c0, temp->var = NULL; temp->next = form, form = temp; } delete_formula(mpl, fx); delete_formula(mpl, fy); return form; } /*---------------------------------------------------------------------- -- remove_constant - remove constant term from linear form. -- -- This routine removes constant term from linear form and stores its -- value to given location. */ FORMULA *remove_constant ( MPL *mpl, FORMULA *form, /* destroyed */ double *coef /* modified */ ) { FORMULA *head = NULL, *temp; *coef = 0.0; while (form != NULL) { temp = form; form = form->next; if (temp->var == NULL) { /* constant term */ *coef = fp_add(mpl, *coef, temp->coef); dmp_free_atom(mpl->formulae, temp, sizeof(FORMULA)); } else { /* linear term */ temp->next = head; head = temp; } } return head; } /*---------------------------------------------------------------------- -- reduce_terms - reduce identical terms in linear form. -- -- This routine reduces identical terms in specified linear form. */ FORMULA *reduce_terms ( MPL *mpl, FORMULA *form /* destroyed */ ) { FORMULA *term, *next_term; double c0 = 0.0; for (term = form; term != NULL; term = term->next) { if (term->var == NULL) c0 = fp_add(mpl, c0, term->coef); else term->var->temp = fp_add(mpl, term->var->temp, term->coef); } next_term = form, form = NULL; for (term = next_term; term != NULL; term = next_term) { next_term = term->next; if (term->var == NULL && c0 != 0.0) { term->coef = c0, c0 = 0.0; term->next = form, form = term; } else if (term->var != NULL && term->var->temp != 0.0) { term->coef = term->var->temp, term->var->temp = 0.0; term->next = form, form = term; } else dmp_free_atom(mpl->formulae, term, sizeof(FORMULA)); } return form; } /**********************************************************************/ /* * * ELEMENTAL CONSTRAINTS * * */ /**********************************************************************/ /* (there are no specific routines for elemental constraints) */ /**********************************************************************/ /* * * GENERIC VALUES * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- delete_value - delete generic value. -- -- This routine deletes specified generic value. -- -- NOTE: The generic value to be deleted must be valid. */ void delete_value ( MPL *mpl, int type, VALUE *value /* content destroyed */ ) { xassert(value != NULL); switch (type) { case A_NONE: value->none = NULL; break; case A_NUMERIC: value->num = 0.0; break; case A_SYMBOLIC: delete_symbol(mpl, value->sym), value->sym = NULL; break; case A_LOGICAL: value->bit = 0; break; case A_TUPLE: delete_tuple(mpl, value->tuple), value->tuple = NULL; break; case A_ELEMSET: delete_elemset(mpl, value->set), value->set = NULL; break; case A_ELEMVAR: value->var = NULL; break; case A_FORMULA: delete_formula(mpl, value->form), value->form = NULL; break; case A_ELEMCON: value->con = NULL; break; default: xassert(type != type); } return; } /**********************************************************************/ /* * * SYMBOLICALLY INDEXED ARRAYS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- create_array - create array. -- -- This routine creates an array of specified type and dimension. Being -- created the array is initially empty. -- -- The type indicator determines generic values, which can be assigned -- to the array members: -- -- A_NONE - none (members have no assigned values) -- A_NUMERIC - floating-point numbers -- A_SYMBOLIC - symbols -- A_ELEMSET - elemental sets -- A_ELEMVAR - elemental variables -- A_ELEMCON - elemental constraints -- -- The dimension may be 0, in which case the array consists of the only -- member (such arrays represent 0-dimensional objects). */ ARRAY *create_array(MPL *mpl, int type, int dim) { ARRAY *array; xassert(type == A_NONE || type == A_NUMERIC || type == A_SYMBOLIC || type == A_ELEMSET || type == A_ELEMVAR || type == A_ELEMCON); xassert(dim >= 0); array = dmp_get_atom(mpl->arrays, sizeof(ARRAY)); array->type = type; array->dim = dim; array->size = 0; array->head = NULL; array->tail = NULL; array->tree = NULL; array->prev = NULL; array->next = mpl->a_list; /* include the array in the global array list */ if (array->next != NULL) array->next->prev = array; mpl->a_list = array; return array; } /*---------------------------------------------------------------------- -- find_member - find array member with given n-tuple. -- -- This routine finds an array member, which has given n-tuple. If the -- array is short, the linear search is used. Otherwise the routine -- autimatically creates the search tree (i.e. the array index) to find -- members for logarithmic time. */ static int compare_member_tuples(void *info, const void *key1, const void *key2) { /* this is an auxiliary routine used to compare keys, which are n-tuples assigned to array members */ return compare_tuples((MPL *)info, (TUPLE *)key1, (TUPLE *)key2); } MEMBER *find_member ( MPL *mpl, ARRAY *array, /* not changed */ TUPLE *tuple /* not changed */ ) { MEMBER *memb; xassert(array != NULL); /* the n-tuple must have the same dimension as the array */ xassert(tuple_dimen(mpl, tuple) == array->dim); /* if the array is large enough, create the search tree and index all existing members of the array */ if (array->size > 30 && array->tree == NULL) { array->tree = avl_create_tree(compare_member_tuples, mpl); for (memb = array->head; memb != NULL; memb = memb->next) avl_set_node_link(avl_insert_node(array->tree, memb->tuple), (void *)memb); } /* find a member, which has the given tuple */ if (array->tree == NULL) { /* the search tree doesn't exist; use the linear search */ for (memb = array->head; memb != NULL; memb = memb->next) if (compare_tuples(mpl, memb->tuple, tuple) == 0) break; } else { /* the search tree exists; use the binary search */ AVLNODE *node; node = avl_find_node(array->tree, tuple); memb = (MEMBER *)(node == NULL ? NULL : avl_get_node_link(node)); } return memb; } /*---------------------------------------------------------------------- -- add_member - add new member to array. -- -- This routine creates a new member with given n-tuple and adds it to -- specified array. -- -- For the sake of efficiency this routine doesn't check whether the -- array already contains a member with the given n-tuple or not. Thus, -- if necessary, the calling program should use the routine find_member -- in order to be sure that the array contains no member with the same -- n-tuple, because members with duplicate n-tuples are not allowed. -- -- This routine assigns no generic value to the new member, because the -- calling program must do that. */ MEMBER *add_member ( MPL *mpl, ARRAY *array, /* modified */ TUPLE *tuple /* destroyed */ ) { MEMBER *memb; xassert(array != NULL); /* the n-tuple must have the same dimension as the array */ xassert(tuple_dimen(mpl, tuple) == array->dim); /* create new member */ memb = dmp_get_atom(mpl->members, sizeof(MEMBER)); memb->tuple = tuple; memb->next = NULL; memset(&memb->value, '?', sizeof(VALUE)); /* and append it to the member list */ array->size++; if (array->head == NULL) array->head = memb; else array->tail->next = memb; array->tail = memb; /* if the search tree exists, index the new member */ if (array->tree != NULL) avl_set_node_link(avl_insert_node(array->tree, memb->tuple), (void *)memb); return memb; } /*---------------------------------------------------------------------- -- delete_array - delete array. -- -- This routine deletes specified array. -- -- Generic values assigned to the array members are not deleted by this -- routine. The calling program itself must delete all assigned generic -- values before deleting the array. */ void delete_array ( MPL *mpl, ARRAY *array /* destroyed */ ) { MEMBER *memb; xassert(array != NULL); /* delete all existing array members */ while (array->head != NULL) { memb = array->head; array->head = memb->next; delete_tuple(mpl, memb->tuple); dmp_free_atom(mpl->members, memb, sizeof(MEMBER)); } /* if the search tree exists, also delete it */ if (array->tree != NULL) avl_delete_tree(array->tree); /* remove the array from the global array list */ if (array->prev == NULL) mpl->a_list = array->next; else array->prev->next = array->next; if (array->next == NULL) ; else array->next->prev = array->prev; /* delete the array descriptor */ dmp_free_atom(mpl->arrays, array, sizeof(ARRAY)); return; } /**********************************************************************/ /* * * DOMAINS AND DUMMY INDICES * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- assign_dummy_index - assign new value to dummy index. -- -- This routine assigns new value to specified dummy index and, that is -- important, invalidates all temporary resultant values, which depends -- on that dummy index. */ void assign_dummy_index ( MPL *mpl, DOMAIN_SLOT *slot, /* modified */ SYMBOL *value /* not changed */ ) { CODE *leaf, *code; xassert(slot != NULL); xassert(value != NULL); /* delete the current value assigned to the dummy index */ if (slot->value != NULL) { /* if the current value and the new one are identical, actual assignment is not needed */ if (compare_symbols(mpl, slot->value, value) == 0) goto done; /* delete a symbol, which is the current value */ delete_symbol(mpl, slot->value), slot->value = NULL; } /* now walk through all the pseudo-codes with op = O_INDEX, which refer to the dummy index to be changed (these pseudo-codes are leaves in the forest of *all* expressions in the database) */ for (leaf = slot->list; leaf != NULL; leaf = leaf->arg.index. next) { xassert(leaf->op == O_INDEX); /* invalidate all resultant values, which depend on the dummy index, walking from the current leaf toward the root of the corresponding expression tree */ for (code = leaf; code != NULL; code = code->up) { if (code->valid) { /* invalidate and delete resultant value */ code->valid = 0; delete_value(mpl, code->type, &code->value); } } } /* assign new value to the dummy index */ slot->value = copy_symbol(mpl, value); done: return; } /*---------------------------------------------------------------------- -- update_dummy_indices - update current values of dummy indices. -- -- This routine assigns components of "backup" n-tuple to dummy indices -- of specified domain block. If no "backup" n-tuple is defined for the -- domain block, values of the dummy indices remain untouched. */ void update_dummy_indices ( MPL *mpl, DOMAIN_BLOCK *block /* not changed */ ) { DOMAIN_SLOT *slot; TUPLE *temp; if (block->backup != NULL) { for (slot = block->list, temp = block->backup; slot != NULL; slot = slot->next, temp = temp->next) { xassert(temp != NULL); xassert(temp->sym != NULL); assign_dummy_index(mpl, slot, temp->sym); } } return; } /*---------------------------------------------------------------------- -- enter_domain_block - enter domain block. -- -- Let specified domain block have the form: -- -- { ..., (j1, j2, ..., jn) in J, ... } -- -- where j1, j2, ..., jn are dummy indices, J is a basic set. -- -- This routine does the following: -- -- 1. Checks if the given n-tuple is a member of the basic set J. Note -- that J being *out of the scope* of the domain block cannot depend -- on the dummy indices in the same and inner domain blocks, so it -- can be computed before the dummy indices are assigned new values. -- If this check fails, the routine returns with non-zero code. -- -- 2. Saves current values of the dummy indices j1, j2, ..., jn. -- -- 3. Assigns new values, which are components of the given n-tuple, to -- the dummy indices j1, j2, ..., jn. If dimension of the n-tuple is -- larger than n, its extra components n+1, n+2, ... are not used. -- -- 4. Calls the formal routine func which either enters the next domain -- block or evaluates some code within the domain scope. -- -- 5. Restores former values of the dummy indices j1, j2, ..., jn. -- -- Since current values assigned to the dummy indices on entry to this -- routine are restored on exit, the formal routine func is allowed to -- call this routine recursively. */ int enter_domain_block ( MPL *mpl, DOMAIN_BLOCK *block, /* not changed */ TUPLE *tuple, /* not changed */ void *info, void (*func)(MPL *mpl, void *info) ) { TUPLE *backup; int ret = 0; /* check if the given n-tuple is a member of the basic set */ xassert(block->code != NULL); if (!is_member(mpl, block->code, tuple)) { ret = 1; goto done; } /* save reference to "backup" n-tuple, which was used to assign current values of the dummy indices (it is sufficient to save reference, not value, because that n-tuple is defined in some outer level of recursion and therefore cannot be changed on this and deeper recursive calls) */ backup = block->backup; /* set up new "backup" n-tuple, which defines new values of the dummy indices */ block->backup = tuple; /* assign new values to the dummy indices */ update_dummy_indices(mpl, block); /* call the formal routine that does the rest part of the job */ func(mpl, info); /* restore reference to the former "backup" n-tuple */ block->backup = backup; /* restore former values of the dummy indices; note that if the domain block just escaped has no other active instances which may exist due to recursion (it is indicated by a null pointer to the former n-tuple), former values of the dummy indices are undefined; therefore in this case the routine keeps currently assigned values of the dummy indices that involves keeping all dependent temporary results and thereby, if this domain block is not used recursively, allows improving efficiency */ update_dummy_indices(mpl, block); done: return ret; } /*---------------------------------------------------------------------- -- eval_within_domain - perform evaluation within domain scope. -- -- This routine assigns new values (symbols) to all dummy indices of -- specified domain and calls the formal routine func, which is used to -- evaluate some code in the domain scope. Each free dummy index in the -- domain is assigned a value specified in the corresponding component -- of given n-tuple. Non-free dummy indices are assigned values, which -- are computed by this routine. -- -- Number of components in the given n-tuple must be the same as number -- of free indices in the domain. -- -- If the given n-tuple is not a member of the domain set, the routine -- func is not called, and non-zero code is returned. -- -- For the sake of convenience it is allowed to specify domain as NULL -- (then n-tuple also must be 0-tuple, i.e. empty), in which case this -- routine just calls the routine func and returns zero. -- -- This routine allows recursive calls from the routine func providing -- correct values of dummy indices for each instance. -- -- NOTE: The n-tuple passed to this routine must not be changed by any -- other routines called from the formal routine func until this -- routine has returned. */ struct eval_domain_info { /* working info used by the routine eval_within_domain */ DOMAIN *domain; /* domain, which has to be entered */ DOMAIN_BLOCK *block; /* domain block, which is currently processed */ TUPLE *tuple; /* tail of original n-tuple, whose components have to be assigned to free dummy indices in the current domain block */ void *info; /* transit pointer passed to the formal routine func */ void (*func)(MPL *mpl, void *info); /* routine, which has to be executed in the domain scope */ int failure; /* this flag indicates that given n-tuple is not a member of the domain set */ }; static void eval_domain_func(MPL *mpl, void *_my_info) { /* this routine recursively enters into the domain scope and then calls the routine func */ struct eval_domain_info *my_info = _my_info; if (my_info->block != NULL) { /* the current domain block to be entered exists */ DOMAIN_BLOCK *block; DOMAIN_SLOT *slot; TUPLE *tuple = NULL, *temp = NULL; /* save pointer to the current domain block */ block = my_info->block; /* and get ready to enter the next block (if it exists) */ my_info->block = block->next; /* construct temporary n-tuple, whose components correspond to dummy indices (slots) of the current domain; components of the temporary n-tuple that correspond to free dummy indices are assigned references (not values!) to symbols specified in the corresponding components of the given n-tuple, while other components that correspond to non-free dummy indices are assigned symbolic values computed here */ for (slot = block->list; slot != NULL; slot = slot->next) { /* create component that corresponds to the current slot */ if (tuple == NULL) tuple = temp = dmp_get_atom(mpl->tuples, sizeof(TUPLE)); else temp = (temp->next = dmp_get_atom(mpl->tuples, sizeof(TUPLE))); if (slot->code == NULL) { /* dummy index is free; take reference to symbol, which is specified in the corresponding component of given n-tuple */ xassert(my_info->tuple != NULL); temp->sym = my_info->tuple->sym; xassert(temp->sym != NULL); my_info->tuple = my_info->tuple->next; } else { /* dummy index is non-free; compute symbolic value to be temporarily assigned to the dummy index */ temp->sym = eval_symbolic(mpl, slot->code); } } temp->next = NULL; /* enter the current domain block */ if (enter_domain_block(mpl, block, tuple, my_info, eval_domain_func)) my_info->failure = 1; /* delete temporary n-tuple as well as symbols that correspond to non-free dummy indices (they were computed here) */ for (slot = block->list; slot != NULL; slot = slot->next) { xassert(tuple != NULL); temp = tuple; tuple = tuple->next; if (slot->code != NULL) { /* dummy index is non-free; delete symbolic value */ delete_symbol(mpl, temp->sym); } /* delete component that corresponds to the current slot */ dmp_free_atom(mpl->tuples, temp, sizeof(TUPLE)); } } else { /* there are no more domain blocks, i.e. we have reached the domain scope */ xassert(my_info->tuple == NULL); /* check optional predicate specified for the domain */ if (my_info->domain->code != NULL && !eval_logical(mpl, my_info->domain->code)) { /* the predicate is false */ my_info->failure = 2; } else { /* the predicate is true; do the job */ my_info->func(mpl, my_info->info); } } return; } int eval_within_domain ( MPL *mpl, DOMAIN *domain, /* not changed */ TUPLE *tuple, /* not changed */ void *info, void (*func)(MPL *mpl, void *info) ) { /* this routine performs evaluation within domain scope */ struct eval_domain_info _my_info, *my_info = &_my_info; if (domain == NULL) { xassert(tuple == NULL); func(mpl, info); my_info->failure = 0; } else { xassert(tuple != NULL); my_info->domain = domain; my_info->block = domain->list; my_info->tuple = tuple; my_info->info = info; my_info->func = func; my_info->failure = 0; /* enter the very first domain block */ eval_domain_func(mpl, my_info); } return my_info->failure; } /*---------------------------------------------------------------------- -- loop_within_domain - perform iterations within domain scope. -- -- This routine iteratively assigns new values (symbols) to the dummy -- indices of specified domain by enumerating all n-tuples, which are -- members of the domain set, and for every n-tuple it calls the formal -- routine func to evaluate some code within the domain scope. -- -- If the routine func returns non-zero, enumeration within the domain -- is prematurely terminated. -- -- For the sake of convenience it is allowed to specify domain as NULL, -- in which case this routine just calls the routine func only once and -- returns zero. -- -- This routine allows recursive calls from the routine func providing -- correct values of dummy indices for each instance. */ struct loop_domain_info { /* working info used by the routine loop_within_domain */ DOMAIN *domain; /* domain, which has to be entered */ DOMAIN_BLOCK *block; /* domain block, which is currently processed */ int looping; /* clearing this flag leads to terminating enumeration */ void *info; /* transit pointer passed to the formal routine func */ int (*func)(MPL *mpl, void *info); /* routine, which needs to be executed in the domain scope */ }; static void loop_domain_func(MPL *mpl, void *_my_info) { /* this routine enumerates all n-tuples in the basic set of the current domain block, enters recursively into the domain scope for every n-tuple, and then calls the routine func */ struct loop_domain_info *my_info = _my_info; if (my_info->block != NULL) { /* the current domain block to be entered exists */ DOMAIN_BLOCK *block; DOMAIN_SLOT *slot; TUPLE *bound; /* save pointer to the current domain block */ block = my_info->block; /* and get ready to enter the next block (if it exists) */ my_info->block = block->next; /* compute symbolic values, at which non-free dummy indices of the current domain block are bound; since that values don't depend on free dummy indices of the current block, they can be computed once out of the enumeration loop */ bound = create_tuple(mpl); for (slot = block->list; slot != NULL; slot = slot->next) { if (slot->code != NULL) bound = expand_tuple(mpl, bound, eval_symbolic(mpl, slot->code)); } /* start enumeration */ xassert(block->code != NULL); if (block->code->op == O_DOTS) { /* the basic set is "arithmetic", in which case it doesn't need to be computed explicitly */ TUPLE *tuple; int n, j; double t0, tf, dt; /* compute "parameters" of the basic set */ t0 = eval_numeric(mpl, block->code->arg.arg.x); tf = eval_numeric(mpl, block->code->arg.arg.y); if (block->code->arg.arg.z == NULL) dt = 1.0; else dt = eval_numeric(mpl, block->code->arg.arg.z); /* determine cardinality of the basic set */ n = arelset_size(mpl, t0, tf, dt); /* create dummy 1-tuple for members of the basic set */ tuple = expand_tuple(mpl, create_tuple(mpl), create_symbol_num(mpl, 0.0)); /* in case of "arithmetic" set there is exactly one dummy index, which cannot be non-free */ xassert(bound == NULL); /* walk through 1-tuples of the basic set */ for (j = 1; j <= n && my_info->looping; j++) { /* construct dummy 1-tuple for the current member */ tuple->sym->num = arelset_member(mpl, t0, tf, dt, j); /* enter the current domain block */ enter_domain_block(mpl, block, tuple, my_info, loop_domain_func); } /* delete dummy 1-tuple */ delete_tuple(mpl, tuple); } else { /* the basic set is of general kind, in which case it needs to be explicitly computed */ ELEMSET *set; MEMBER *memb; TUPLE *temp1, *temp2; /* compute the basic set */ set = eval_elemset(mpl, block->code); /* walk through all n-tuples of the basic set */ for (memb = set->head; memb != NULL && my_info->looping; memb = memb->next) { /* all components of the current n-tuple that correspond to non-free dummy indices must be feasible; otherwise the n-tuple is not in the basic set */ temp1 = memb->tuple; temp2 = bound; for (slot = block->list; slot != NULL; slot = slot->next) { xassert(temp1 != NULL); if (slot->code != NULL) { /* non-free dummy index */ xassert(temp2 != NULL); if (compare_symbols(mpl, temp1->sym, temp2->sym) != 0) { /* the n-tuple is not in the basic set */ goto skip; } temp2 = temp2->next; } temp1 = temp1->next; } xassert(temp1 == NULL); xassert(temp2 == NULL); /* enter the current domain block */ enter_domain_block(mpl, block, memb->tuple, my_info, loop_domain_func); skip: ; } /* delete the basic set */ delete_elemset(mpl, set); } /* delete symbolic values binding non-free dummy indices */ delete_tuple(mpl, bound); /* restore pointer to the current domain block */ my_info->block = block; } else { /* there are no more domain blocks, i.e. we have reached the domain scope */ /* check optional predicate specified for the domain */ if (my_info->domain->code != NULL && !eval_logical(mpl, my_info->domain->code)) { /* the predicate is false */ /* nop */; } else { /* the predicate is true; do the job */ my_info->looping = !my_info->func(mpl, my_info->info); } } return; } void loop_within_domain ( MPL *mpl, DOMAIN *domain, /* not changed */ void *info, int (*func)(MPL *mpl, void *info) ) { /* this routine performs iterations within domain scope */ struct loop_domain_info _my_info, *my_info = &_my_info; if (domain == NULL) func(mpl, info); else { my_info->domain = domain; my_info->block = domain->list; my_info->looping = 1; my_info->info = info; my_info->func = func; /* enter the very first domain block */ loop_domain_func(mpl, my_info); } return; } /*---------------------------------------------------------------------- -- out_of_domain - raise domain exception. -- -- This routine is called when a reference is made to a member of some -- model object, but its n-tuple is out of the object domain. */ void out_of_domain ( MPL *mpl, char *name, /* not changed */ TUPLE *tuple /* not changed */ ) { xassert(name != NULL); xassert(tuple != NULL); mpl_error(mpl, "%s%s out of domain", name, format_tuple(mpl, '[', tuple)); /* no return */ } /*---------------------------------------------------------------------- -- get_domain_tuple - obtain current n-tuple from domain. -- -- This routine constructs n-tuple, whose components are current values -- assigned to *free* dummy indices of specified domain. -- -- For the sake of convenience it is allowed to specify domain as NULL, -- in which case this routine returns 0-tuple. -- -- NOTE: This routine must not be called out of domain scope. */ TUPLE *get_domain_tuple ( MPL *mpl, DOMAIN *domain /* not changed */ ) { DOMAIN_BLOCK *block; DOMAIN_SLOT *slot; TUPLE *tuple; tuple = create_tuple(mpl); if (domain != NULL) { for (block = domain->list; block != NULL; block = block->next) { for (slot = block->list; slot != NULL; slot = slot->next) { if (slot->code == NULL) { xassert(slot->value != NULL); tuple = expand_tuple(mpl, tuple, copy_symbol(mpl, slot->value)); } } } } return tuple; } /*---------------------------------------------------------------------- -- clean_domain - clean domain. -- -- This routine cleans specified domain that assumes deleting all stuff -- dynamically allocated during the generation phase. */ void clean_domain(MPL *mpl, DOMAIN *domain) { DOMAIN_BLOCK *block; DOMAIN_SLOT *slot; /* if no domain is specified, do nothing */ if (domain == NULL) goto done; /* clean all domain blocks */ for (block = domain->list; block != NULL; block = block->next) { /* clean all domain slots */ for (slot = block->list; slot != NULL; slot = slot->next) { /* clean pseudo-code for computing bound value */ clean_code(mpl, slot->code); /* delete symbolic value assigned to dummy index */ if (slot->value != NULL) delete_symbol(mpl, slot->value), slot->value = NULL; } /* clean pseudo-code for computing basic set */ clean_code(mpl, block->code); } /* clean pseudo-code for computing domain predicate */ clean_code(mpl, domain->code); done: return; } /**********************************************************************/ /* * * MODEL SETS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- check_elem_set - check elemental set assigned to set member. -- -- This routine checks if given elemental set being assigned to member -- of specified model set satisfies to all restrictions. -- -- NOTE: This routine must not be called out of domain scope. */ void check_elem_set ( MPL *mpl, SET *set, /* not changed */ TUPLE *tuple, /* not changed */ ELEMSET *refer /* not changed */ ) { WITHIN *within; MEMBER *memb; int eqno; /* elemental set must be within all specified supersets */ for (within = set->within, eqno = 1; within != NULL; within = within->next, eqno++) { xassert(within->code != NULL); for (memb = refer->head; memb != NULL; memb = memb->next) { if (!is_member(mpl, within->code, memb->tuple)) { char buf[255+1]; strcpy(buf, format_tuple(mpl, '(', memb->tuple)); xassert(strlen(buf) < sizeof(buf)); mpl_error(mpl, "%s%s contains %s which not within specified " "set; see (%d)", set->name, format_tuple(mpl, '[', tuple), buf, eqno); } } } return; } /*---------------------------------------------------------------------- -- take_member_set - obtain elemental set assigned to set member. -- -- This routine obtains a reference to elemental set assigned to given -- member of specified model set and returns it on exit. -- -- NOTE: This routine must not be called out of domain scope. */ ELEMSET *take_member_set /* returns reference, not value */ ( MPL *mpl, SET *set, /* not changed */ TUPLE *tuple /* not changed */ ) { MEMBER *memb; ELEMSET *refer; /* find member in the set array */ memb = find_member(mpl, set->array, tuple); if (memb != NULL) { /* member exists, so just take the reference */ refer = memb->value.set; } else if (set->assign != NULL) { /* compute value using assignment expression */ refer = eval_elemset(mpl, set->assign); add: /* check that the elemental set satisfies to all restrictions, assign it to new member, and add the member to the array */ check_elem_set(mpl, set, tuple, refer); memb = add_member(mpl, set->array, copy_tuple(mpl, tuple)); memb->value.set = refer; } else if (set->option != NULL) { /* compute default elemental set */ refer = eval_elemset(mpl, set->option); goto add; } else { /* no value (elemental set) is provided */ mpl_error(mpl, "no value for %s%s", set->name, format_tuple(mpl, '[', tuple)); } return refer; } /*---------------------------------------------------------------------- -- eval_member_set - evaluate elemental set assigned to set member. -- -- This routine evaluates a reference to elemental set assigned to given -- member of specified model set and returns it on exit. */ struct eval_set_info { /* working info used by the routine eval_member_set */ SET *set; /* model set */ TUPLE *tuple; /* n-tuple, which defines set member */ MEMBER *memb; /* normally this pointer is NULL; the routine uses this pointer to check data provided in the data section, in which case it points to a member currently checked; this check is performed automatically only once when a reference to any member occurs for the first time */ ELEMSET *refer; /* evaluated reference to elemental set */ }; static void eval_set_func(MPL *mpl, void *_info) { /* this is auxiliary routine to work within domain scope */ struct eval_set_info *info = _info; if (info->memb != NULL) { /* checking call; check elemental set being assigned */ check_elem_set(mpl, info->set, info->memb->tuple, info->memb->value.set); } else { /* normal call; evaluate member, which has given n-tuple */ info->refer = take_member_set(mpl, info->set, info->tuple); } return; } #if 1 /* 12/XII-2008 */ static void saturate_set(MPL *mpl, SET *set) { GADGET *gadget = set->gadget; ELEMSET *data; MEMBER *elem, *memb; TUPLE *tuple, *work[20]; int i; xprintf("Generating %s...\n", set->name); eval_whole_set(mpl, gadget->set); /* gadget set must have exactly one member */ xassert(gadget->set->array != NULL); xassert(gadget->set->array->head != NULL); xassert(gadget->set->array->head == gadget->set->array->tail); data = gadget->set->array->head->value.set; xassert(data->type == A_NONE); xassert(data->dim == gadget->set->dimen); /* walk thru all elements of the plain set */ for (elem = data->head; elem != NULL; elem = elem->next) { /* create a copy of n-tuple */ tuple = copy_tuple(mpl, elem->tuple); /* rearrange component of the n-tuple */ for (i = 0; i < gadget->set->dimen; i++) work[i] = NULL; for (i = 0; tuple != NULL; tuple = tuple->next) work[gadget->ind[i++]-1] = tuple; xassert(i == gadget->set->dimen); for (i = 0; i < gadget->set->dimen; i++) { xassert(work[i] != NULL); work[i]->next = work[i+1]; } /* construct subscript list from first set->dim components */ if (set->dim == 0) tuple = NULL; else tuple = work[0], work[set->dim-1]->next = NULL; /* find corresponding member of the set to be initialized */ memb = find_member(mpl, set->array, tuple); if (memb == NULL) { /* not found; add new member to the set and assign it empty elemental set */ memb = add_member(mpl, set->array, tuple); memb->value.set = create_elemset(mpl, set->dimen); } else { /* found; free subscript list */ delete_tuple(mpl, tuple); } /* construct new n-tuple from rest set->dimen components */ tuple = work[set->dim]; xassert(set->dim + set->dimen == gadget->set->dimen); work[gadget->set->dimen-1]->next = NULL; /* and add it to the elemental set assigned to the member (no check for duplicates is needed) */ add_tuple(mpl, memb->value.set, tuple); } /* the set has been saturated with data */ set->data = 1; return; } #endif ELEMSET *eval_member_set /* returns reference, not value */ ( MPL *mpl, SET *set, /* not changed */ TUPLE *tuple /* not changed */ ) { /* this routine evaluates set member */ struct eval_set_info _info, *info = &_info; xassert(set->dim == tuple_dimen(mpl, tuple)); info->set = set; info->tuple = tuple; #if 1 /* 12/XII-2008 */ if (set->gadget != NULL && set->data == 0) { /* initialize the set with data from a plain set */ saturate_set(mpl, set); } #endif if (set->data == 1) { /* check data, which are provided in the data section, but not checked yet */ /* save pointer to the last array member; note that during the check new members may be added beyond the last member due to references to the same parameter from default expression as well as from expressions that define restricting supersets; however, values assigned to the new members will be checked by other routine, so we don't need to check them here */ MEMBER *tail = set->array->tail; /* change the data status to prevent infinite recursive loop due to references to the same set during the check */ set->data = 2; /* check elemental sets assigned to array members in the data section until the marked member has been reached */ for (info->memb = set->array->head; info->memb != NULL; info->memb = info->memb->next) { if (eval_within_domain(mpl, set->domain, info->memb->tuple, info, eval_set_func)) out_of_domain(mpl, set->name, info->memb->tuple); if (info->memb == tail) break; } /* the check has been finished */ } /* evaluate member, which has given n-tuple */ info->memb = NULL; if (eval_within_domain(mpl, info->set->domain, info->tuple, info, eval_set_func)) out_of_domain(mpl, set->name, info->tuple); /* bring evaluated reference to the calling program */ return info->refer; } /*---------------------------------------------------------------------- -- eval_whole_set - evaluate model set over entire domain. -- -- This routine evaluates all members of specified model set over entire -- domain. */ static int whole_set_func(MPL *mpl, void *info) { /* this is auxiliary routine to work within domain scope */ SET *set = (SET *)info; TUPLE *tuple = get_domain_tuple(mpl, set->domain); eval_member_set(mpl, set, tuple); delete_tuple(mpl, tuple); return 0; } void eval_whole_set(MPL *mpl, SET *set) { loop_within_domain(mpl, set->domain, set, whole_set_func); return; } /*---------------------------------------------------------------------- -- clean set - clean model set. -- -- This routine cleans specified model set that assumes deleting all -- stuff dynamically allocated during the generation phase. */ void clean_set(MPL *mpl, SET *set) { WITHIN *within; MEMBER *memb; /* clean subscript domain */ clean_domain(mpl, set->domain); /* clean pseudo-code for computing supersets */ for (within = set->within; within != NULL; within = within->next) clean_code(mpl, within->code); /* clean pseudo-code for computing assigned value */ clean_code(mpl, set->assign); /* clean pseudo-code for computing default value */ clean_code(mpl, set->option); /* reset data status flag */ set->data = 0; /* delete content array */ for (memb = set->array->head; memb != NULL; memb = memb->next) delete_value(mpl, set->array->type, &memb->value); delete_array(mpl, set->array), set->array = NULL; return; } /**********************************************************************/ /* * * MODEL PARAMETERS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- check_value_num - check numeric value assigned to parameter member. -- -- This routine checks if numeric value being assigned to some member -- of specified numeric model parameter satisfies to all restrictions. -- -- NOTE: This routine must not be called out of domain scope. */ void check_value_num ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple, /* not changed */ double value ) { CONDITION *cond; WITHIN *in; int eqno; /* the value must satisfy to the parameter type */ switch (par->type) { case A_NUMERIC: break; case A_INTEGER: if (value != floor(value)) mpl_error(mpl, "%s%s = %.*g not integer", par->name, format_tuple(mpl, '[', tuple), DBL_DIG, value); break; case A_BINARY: if (!(value == 0.0 || value == 1.0)) mpl_error(mpl, "%s%s = %.*g not binary", par->name, format_tuple(mpl, '[', tuple), DBL_DIG, value); break; default: xassert(par != par); } /* the value must satisfy to all specified conditions */ for (cond = par->cond, eqno = 1; cond != NULL; cond = cond->next, eqno++) { double bound; char *rho; xassert(cond->code != NULL); bound = eval_numeric(mpl, cond->code); switch (cond->rho) { case O_LT: if (!(value < bound)) { rho = "<"; err: mpl_error(mpl, "%s%s = %.*g not %s %.*g; see (%d)", par->name, format_tuple(mpl, '[', tuple), DBL_DIG, value, rho, DBL_DIG, bound, eqno); } break; case O_LE: if (!(value <= bound)) { rho = "<="; goto err; } break; case O_EQ: if (!(value == bound)) { rho = "="; goto err; } break; case O_GE: if (!(value >= bound)) { rho = ">="; goto err; } break; case O_GT: if (!(value > bound)) { rho = ">"; goto err; } break; case O_NE: if (!(value != bound)) { rho = "<>"; goto err; } break; default: xassert(cond != cond); } } /* the value must be in all specified supersets */ for (in = par->in, eqno = 1; in != NULL; in = in->next, eqno++) { TUPLE *dummy; xassert(in->code != NULL); xassert(in->code->dim == 1); dummy = expand_tuple(mpl, create_tuple(mpl), create_symbol_num(mpl, value)); if (!is_member(mpl, in->code, dummy)) mpl_error(mpl, "%s%s = %.*g not in specified set; see (%d)", par->name, format_tuple(mpl, '[', tuple), DBL_DIG, value, eqno); delete_tuple(mpl, dummy); } return; } /*---------------------------------------------------------------------- -- take_member_num - obtain num. value assigned to parameter member. -- -- This routine obtains a numeric value assigned to member of specified -- numeric model parameter and returns it on exit. -- -- NOTE: This routine must not be called out of domain scope. */ double take_member_num ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* not changed */ ) { MEMBER *memb; double value; /* find member in the parameter array */ memb = find_member(mpl, par->array, tuple); if (memb != NULL) { /* member exists, so just take its value */ value = memb->value.num; } else if (par->assign != NULL) { /* compute value using assignment expression */ value = eval_numeric(mpl, par->assign); add: /* check that the value satisfies to all restrictions, assign it to new member, and add the member to the array */ check_value_num(mpl, par, tuple, value); memb = add_member(mpl, par->array, copy_tuple(mpl, tuple)); memb->value.num = value; } else if (par->option != NULL) { /* compute default value */ value = eval_numeric(mpl, par->option); goto add; } else if (par->defval != NULL) { /* take default value provided in the data section */ if (par->defval->str != NULL) mpl_error(mpl, "cannot convert %s to floating-point number", format_symbol(mpl, par->defval)); value = par->defval->num; goto add; } else { /* no value is provided */ mpl_error(mpl, "no value for %s%s", par->name, format_tuple(mpl, '[', tuple)); } return value; } /*---------------------------------------------------------------------- -- eval_member_num - evaluate num. value assigned to parameter member. -- -- This routine evaluates a numeric value assigned to given member of -- specified numeric model parameter and returns it on exit. */ struct eval_num_info { /* working info used by the routine eval_member_num */ PARAMETER *par; /* model parameter */ TUPLE *tuple; /* n-tuple, which defines parameter member */ MEMBER *memb; /* normally this pointer is NULL; the routine uses this pointer to check data provided in the data section, in which case it points to a member currently checked; this check is performed automatically only once when a reference to any member occurs for the first time */ double value; /* evaluated numeric value */ }; static void eval_num_func(MPL *mpl, void *_info) { /* this is auxiliary routine to work within domain scope */ struct eval_num_info *info = _info; if (info->memb != NULL) { /* checking call; check numeric value being assigned */ check_value_num(mpl, info->par, info->memb->tuple, info->memb->value.num); } else { /* normal call; evaluate member, which has given n-tuple */ info->value = take_member_num(mpl, info->par, info->tuple); } return; } double eval_member_num ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* not changed */ ) { /* this routine evaluates numeric parameter member */ struct eval_num_info _info, *info = &_info; xassert(par->type == A_NUMERIC || par->type == A_INTEGER || par->type == A_BINARY); xassert(par->dim == tuple_dimen(mpl, tuple)); info->par = par; info->tuple = tuple; if (par->data == 1) { /* check data, which are provided in the data section, but not checked yet */ /* save pointer to the last array member; note that during the check new members may be added beyond the last member due to references to the same parameter from default expression as well as from expressions that define restricting conditions; however, values assigned to the new members will be checked by other routine, so we don't need to check them here */ MEMBER *tail = par->array->tail; /* change the data status to prevent infinite recursive loop due to references to the same parameter during the check */ par->data = 2; /* check values assigned to array members in the data section until the marked member has been reached */ for (info->memb = par->array->head; info->memb != NULL; info->memb = info->memb->next) { if (eval_within_domain(mpl, par->domain, info->memb->tuple, info, eval_num_func)) out_of_domain(mpl, par->name, info->memb->tuple); if (info->memb == tail) break; } /* the check has been finished */ } /* evaluate member, which has given n-tuple */ info->memb = NULL; if (eval_within_domain(mpl, info->par->domain, info->tuple, info, eval_num_func)) out_of_domain(mpl, par->name, info->tuple); /* bring evaluated value to the calling program */ return info->value; } /*---------------------------------------------------------------------- -- check_value_sym - check symbolic value assigned to parameter member. -- -- This routine checks if symbolic value being assigned to some member -- of specified symbolic model parameter satisfies to all restrictions. -- -- NOTE: This routine must not be called out of domain scope. */ void check_value_sym ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple, /* not changed */ SYMBOL *value /* not changed */ ) { CONDITION *cond; WITHIN *in; int eqno; /* the value must satisfy to all specified conditions */ for (cond = par->cond, eqno = 1; cond != NULL; cond = cond->next, eqno++) { SYMBOL *bound; char buf[255+1]; xassert(cond->code != NULL); bound = eval_symbolic(mpl, cond->code); switch (cond->rho) { #if 1 /* 13/VIII-2008 */ case O_LT: if (!(compare_symbols(mpl, value, bound) < 0)) { strcpy(buf, format_symbol(mpl, bound)); xassert(strlen(buf) < sizeof(buf)); mpl_error(mpl, "%s%s = %s not < %s", par->name, format_tuple(mpl, '[', tuple), format_symbol(mpl, value), buf, eqno); } break; case O_LE: if (!(compare_symbols(mpl, value, bound) <= 0)) { strcpy(buf, format_symbol(mpl, bound)); xassert(strlen(buf) < sizeof(buf)); mpl_error(mpl, "%s%s = %s not <= %s", par->name, format_tuple(mpl, '[', tuple), format_symbol(mpl, value), buf, eqno); } break; #endif case O_EQ: if (!(compare_symbols(mpl, value, bound) == 0)) { strcpy(buf, format_symbol(mpl, bound)); xassert(strlen(buf) < sizeof(buf)); mpl_error(mpl, "%s%s = %s not = %s", par->name, format_tuple(mpl, '[', tuple), format_symbol(mpl, value), buf, eqno); } break; #if 1 /* 13/VIII-2008 */ case O_GE: if (!(compare_symbols(mpl, value, bound) >= 0)) { strcpy(buf, format_symbol(mpl, bound)); xassert(strlen(buf) < sizeof(buf)); mpl_error(mpl, "%s%s = %s not >= %s", par->name, format_tuple(mpl, '[', tuple), format_symbol(mpl, value), buf, eqno); } break; case O_GT: if (!(compare_symbols(mpl, value, bound) > 0)) { strcpy(buf, format_symbol(mpl, bound)); xassert(strlen(buf) < sizeof(buf)); mpl_error(mpl, "%s%s = %s not > %s", par->name, format_tuple(mpl, '[', tuple), format_symbol(mpl, value), buf, eqno); } break; #endif case O_NE: if (!(compare_symbols(mpl, value, bound) != 0)) { strcpy(buf, format_symbol(mpl, bound)); xassert(strlen(buf) < sizeof(buf)); mpl_error(mpl, "%s%s = %s not <> %s", par->name, format_tuple(mpl, '[', tuple), format_symbol(mpl, value), buf, eqno); } break; default: xassert(cond != cond); } delete_symbol(mpl, bound); } /* the value must be in all specified supersets */ for (in = par->in, eqno = 1; in != NULL; in = in->next, eqno++) { TUPLE *dummy; xassert(in->code != NULL); xassert(in->code->dim == 1); dummy = expand_tuple(mpl, create_tuple(mpl), copy_symbol(mpl, value)); if (!is_member(mpl, in->code, dummy)) mpl_error(mpl, "%s%s = %s not in specified set; see (%d)", par->name, format_tuple(mpl, '[', tuple), format_symbol(mpl, value), eqno); delete_tuple(mpl, dummy); } return; } /*---------------------------------------------------------------------- -- take_member_sym - obtain symb. value assigned to parameter member. -- -- This routine obtains a symbolic value assigned to member of specified -- symbolic model parameter and returns it on exit. -- -- NOTE: This routine must not be called out of domain scope. */ SYMBOL *take_member_sym /* returns value, not reference */ ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* not changed */ ) { MEMBER *memb; SYMBOL *value; /* find member in the parameter array */ memb = find_member(mpl, par->array, tuple); if (memb != NULL) { /* member exists, so just take its value */ value = copy_symbol(mpl, memb->value.sym); } else if (par->assign != NULL) { /* compute value using assignment expression */ value = eval_symbolic(mpl, par->assign); add: /* check that the value satisfies to all restrictions, assign it to new member, and add the member to the array */ check_value_sym(mpl, par, tuple, value); memb = add_member(mpl, par->array, copy_tuple(mpl, tuple)); memb->value.sym = copy_symbol(mpl, value); } else if (par->option != NULL) { /* compute default value */ value = eval_symbolic(mpl, par->option); goto add; } else if (par->defval != NULL) { /* take default value provided in the data section */ value = copy_symbol(mpl, par->defval); goto add; } else { /* no value is provided */ mpl_error(mpl, "no value for %s%s", par->name, format_tuple(mpl, '[', tuple)); } return value; } /*---------------------------------------------------------------------- -- eval_member_sym - evaluate symb. value assigned to parameter member. -- -- This routine evaluates a symbolic value assigned to given member of -- specified symbolic model parameter and returns it on exit. */ struct eval_sym_info { /* working info used by the routine eval_member_sym */ PARAMETER *par; /* model parameter */ TUPLE *tuple; /* n-tuple, which defines parameter member */ MEMBER *memb; /* normally this pointer is NULL; the routine uses this pointer to check data provided in the data section, in which case it points to a member currently checked; this check is performed automatically only once when a reference to any member occurs for the first time */ SYMBOL *value; /* evaluated symbolic value */ }; static void eval_sym_func(MPL *mpl, void *_info) { /* this is auxiliary routine to work within domain scope */ struct eval_sym_info *info = _info; if (info->memb != NULL) { /* checking call; check symbolic value being assigned */ check_value_sym(mpl, info->par, info->memb->tuple, info->memb->value.sym); } else { /* normal call; evaluate member, which has given n-tuple */ info->value = take_member_sym(mpl, info->par, info->tuple); } return; } SYMBOL *eval_member_sym /* returns value, not reference */ ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* not changed */ ) { /* this routine evaluates symbolic parameter member */ struct eval_sym_info _info, *info = &_info; xassert(par->type == A_SYMBOLIC); xassert(par->dim == tuple_dimen(mpl, tuple)); info->par = par; info->tuple = tuple; if (par->data == 1) { /* check data, which are provided in the data section, but not checked yet */ /* save pointer to the last array member; note that during the check new members may be added beyond the last member due to references to the same parameter from default expression as well as from expressions that define restricting conditions; however, values assigned to the new members will be checked by other routine, so we don't need to check them here */ MEMBER *tail = par->array->tail; /* change the data status to prevent infinite recursive loop due to references to the same parameter during the check */ par->data = 2; /* check values assigned to array members in the data section until the marked member has been reached */ for (info->memb = par->array->head; info->memb != NULL; info->memb = info->memb->next) { if (eval_within_domain(mpl, par->domain, info->memb->tuple, info, eval_sym_func)) out_of_domain(mpl, par->name, info->memb->tuple); if (info->memb == tail) break; } /* the check has been finished */ } /* evaluate member, which has given n-tuple */ info->memb = NULL; if (eval_within_domain(mpl, info->par->domain, info->tuple, info, eval_sym_func)) out_of_domain(mpl, par->name, info->tuple); /* bring evaluated value to the calling program */ return info->value; } /*---------------------------------------------------------------------- -- eval_whole_par - evaluate model parameter over entire domain. -- -- This routine evaluates all members of specified model parameter over -- entire domain. */ static int whole_par_func(MPL *mpl, void *info) { /* this is auxiliary routine to work within domain scope */ PARAMETER *par = (PARAMETER *)info; TUPLE *tuple = get_domain_tuple(mpl, par->domain); switch (par->type) { case A_NUMERIC: case A_INTEGER: case A_BINARY: eval_member_num(mpl, par, tuple); break; case A_SYMBOLIC: delete_symbol(mpl, eval_member_sym(mpl, par, tuple)); break; default: xassert(par != par); } delete_tuple(mpl, tuple); return 0; } void eval_whole_par(MPL *mpl, PARAMETER *par) { loop_within_domain(mpl, par->domain, par, whole_par_func); return; } /*---------------------------------------------------------------------- -- clean_parameter - clean model parameter. -- -- This routine cleans specified model parameter that assumes deleting -- all stuff dynamically allocated during the generation phase. */ void clean_parameter(MPL *mpl, PARAMETER *par) { CONDITION *cond; WITHIN *in; MEMBER *memb; /* clean subscript domain */ clean_domain(mpl, par->domain); /* clean pseudo-code for computing restricting conditions */ for (cond = par->cond; cond != NULL; cond = cond->next) clean_code(mpl, cond->code); /* clean pseudo-code for computing restricting supersets */ for (in = par->in; in != NULL; in = in->next) clean_code(mpl, in->code); /* clean pseudo-code for computing assigned value */ clean_code(mpl, par->assign); /* clean pseudo-code for computing default value */ clean_code(mpl, par->option); /* reset data status flag */ par->data = 0; /* delete default symbolic value */ if (par->defval != NULL) delete_symbol(mpl, par->defval), par->defval = NULL; /* delete content array */ for (memb = par->array->head; memb != NULL; memb = memb->next) delete_value(mpl, par->array->type, &memb->value); delete_array(mpl, par->array), par->array = NULL; return; } /**********************************************************************/ /* * * MODEL VARIABLES * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- take_member_var - obtain reference to elemental variable. -- -- This routine obtains a reference to elemental variable assigned to -- given member of specified model variable and returns it on exit. If -- necessary, new elemental variable is created. -- -- NOTE: This routine must not be called out of domain scope. */ ELEMVAR *take_member_var /* returns reference */ ( MPL *mpl, VARIABLE *var, /* not changed */ TUPLE *tuple /* not changed */ ) { MEMBER *memb; ELEMVAR *refer; /* find member in the variable array */ memb = find_member(mpl, var->array, tuple); if (memb != NULL) { /* member exists, so just take the reference */ refer = memb->value.var; } else { /* member is referenced for the first time and therefore does not exist; create new elemental variable, assign it to new member, and add the member to the variable array */ memb = add_member(mpl, var->array, copy_tuple(mpl, tuple)); refer = (memb->value.var = dmp_get_atom(mpl->elemvars, sizeof(ELEMVAR))); refer->j = 0; refer->var = var; refer->memb = memb; /* compute lower bound */ if (var->lbnd == NULL) refer->lbnd = 0.0; else refer->lbnd = eval_numeric(mpl, var->lbnd); /* compute upper bound */ if (var->ubnd == NULL) refer->ubnd = 0.0; else if (var->ubnd == var->lbnd) refer->ubnd = refer->lbnd; else refer->ubnd = eval_numeric(mpl, var->ubnd); /* nullify working quantity */ refer->temp = 0.0; #if 1 /* 15/V-2010 */ /* solution has not been obtained by the solver yet */ refer->stat = 0; refer->prim = refer->dual = 0.0; #endif } return refer; } /*---------------------------------------------------------------------- -- eval_member_var - evaluate reference to elemental variable. -- -- This routine evaluates a reference to elemental variable assigned to -- member of specified model variable and returns it on exit. */ struct eval_var_info { /* working info used by the routine eval_member_var */ VARIABLE *var; /* model variable */ TUPLE *tuple; /* n-tuple, which defines variable member */ ELEMVAR *refer; /* evaluated reference to elemental variable */ }; static void eval_var_func(MPL *mpl, void *_info) { /* this is auxiliary routine to work within domain scope */ struct eval_var_info *info = _info; info->refer = take_member_var(mpl, info->var, info->tuple); return; } ELEMVAR *eval_member_var /* returns reference */ ( MPL *mpl, VARIABLE *var, /* not changed */ TUPLE *tuple /* not changed */ ) { /* this routine evaluates variable member */ struct eval_var_info _info, *info = &_info; xassert(var->dim == tuple_dimen(mpl, tuple)); info->var = var; info->tuple = tuple; /* evaluate member, which has given n-tuple */ if (eval_within_domain(mpl, info->var->domain, info->tuple, info, eval_var_func)) out_of_domain(mpl, var->name, info->tuple); /* bring evaluated reference to the calling program */ return info->refer; } /*---------------------------------------------------------------------- -- eval_whole_var - evaluate model variable over entire domain. -- -- This routine evaluates all members of specified model variable over -- entire domain. */ static int whole_var_func(MPL *mpl, void *info) { /* this is auxiliary routine to work within domain scope */ VARIABLE *var = (VARIABLE *)info; TUPLE *tuple = get_domain_tuple(mpl, var->domain); eval_member_var(mpl, var, tuple); delete_tuple(mpl, tuple); return 0; } void eval_whole_var(MPL *mpl, VARIABLE *var) { loop_within_domain(mpl, var->domain, var, whole_var_func); return; } /*---------------------------------------------------------------------- -- clean_variable - clean model variable. -- -- This routine cleans specified model variable that assumes deleting -- all stuff dynamically allocated during the generation phase. */ void clean_variable(MPL *mpl, VARIABLE *var) { MEMBER *memb; /* clean subscript domain */ clean_domain(mpl, var->domain); /* clean code for computing lower bound */ clean_code(mpl, var->lbnd); /* clean code for computing upper bound */ if (var->ubnd != var->lbnd) clean_code(mpl, var->ubnd); /* delete content array */ for (memb = var->array->head; memb != NULL; memb = memb->next) dmp_free_atom(mpl->elemvars, memb->value.var, sizeof(ELEMVAR)); delete_array(mpl, var->array), var->array = NULL; return; } /**********************************************************************/ /* * * MODEL CONSTRAINTS AND OBJECTIVES * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- take_member_con - obtain reference to elemental constraint. -- -- This routine obtains a reference to elemental constraint assigned -- to given member of specified model constraint and returns it on exit. -- If necessary, new elemental constraint is created. -- -- NOTE: This routine must not be called out of domain scope. */ ELEMCON *take_member_con /* returns reference */ ( MPL *mpl, CONSTRAINT *con, /* not changed */ TUPLE *tuple /* not changed */ ) { MEMBER *memb; ELEMCON *refer; /* find member in the constraint array */ memb = find_member(mpl, con->array, tuple); if (memb != NULL) { /* member exists, so just take the reference */ refer = memb->value.con; } else { /* member is referenced for the first time and therefore does not exist; create new elemental constraint, assign it to new member, and add the member to the constraint array */ memb = add_member(mpl, con->array, copy_tuple(mpl, tuple)); refer = (memb->value.con = dmp_get_atom(mpl->elemcons, sizeof(ELEMCON))); refer->i = 0; refer->con = con; refer->memb = memb; /* compute linear form */ xassert(con->code != NULL); refer->form = eval_formula(mpl, con->code); /* compute lower and upper bounds */ if (con->lbnd == NULL && con->ubnd == NULL) { /* objective has no bounds */ double temp; xassert(con->type == A_MINIMIZE || con->type == A_MAXIMIZE); /* carry the constant term to the right-hand side */ refer->form = remove_constant(mpl, refer->form, &temp); refer->lbnd = refer->ubnd = - temp; } else if (con->lbnd != NULL && con->ubnd == NULL) { /* constraint a * x + b >= c * y + d is transformed to the standard form a * x - c * y >= d - b */ double temp; xassert(con->type == A_CONSTRAINT); refer->form = linear_comb(mpl, +1.0, refer->form, -1.0, eval_formula(mpl, con->lbnd)); refer->form = remove_constant(mpl, refer->form, &temp); refer->lbnd = - temp; refer->ubnd = 0.0; } else if (con->lbnd == NULL && con->ubnd != NULL) { /* constraint a * x + b <= c * y + d is transformed to the standard form a * x - c * y <= d - b */ double temp; xassert(con->type == A_CONSTRAINT); refer->form = linear_comb(mpl, +1.0, refer->form, -1.0, eval_formula(mpl, con->ubnd)); refer->form = remove_constant(mpl, refer->form, &temp); refer->lbnd = 0.0; refer->ubnd = - temp; } else if (con->lbnd == con->ubnd) { /* constraint a * x + b = c * y + d is transformed to the standard form a * x - c * y = d - b */ double temp; xassert(con->type == A_CONSTRAINT); refer->form = linear_comb(mpl, +1.0, refer->form, -1.0, eval_formula(mpl, con->lbnd)); refer->form = remove_constant(mpl, refer->form, &temp); refer->lbnd = refer->ubnd = - temp; } else { /* ranged constraint c <= a * x + b <= d is transformed to the standard form c - b <= a * x <= d - b */ double temp, temp1, temp2; xassert(con->type == A_CONSTRAINT); refer->form = remove_constant(mpl, refer->form, &temp); xassert(remove_constant(mpl, eval_formula(mpl, con->lbnd), &temp1) == NULL); xassert(remove_constant(mpl, eval_formula(mpl, con->ubnd), &temp2) == NULL); refer->lbnd = fp_sub(mpl, temp1, temp); refer->ubnd = fp_sub(mpl, temp2, temp); } #if 1 /* 15/V-2010 */ /* solution has not been obtained by the solver yet */ refer->stat = 0; refer->prim = refer->dual = 0.0; #endif } return refer; } /*---------------------------------------------------------------------- -- eval_member_con - evaluate reference to elemental constraint. -- -- This routine evaluates a reference to elemental constraint assigned -- to member of specified model constraint and returns it on exit. */ struct eval_con_info { /* working info used by the routine eval_member_con */ CONSTRAINT *con; /* model constraint */ TUPLE *tuple; /* n-tuple, which defines constraint member */ ELEMCON *refer; /* evaluated reference to elemental constraint */ }; static void eval_con_func(MPL *mpl, void *_info) { /* this is auxiliary routine to work within domain scope */ struct eval_con_info *info = _info; info->refer = take_member_con(mpl, info->con, info->tuple); return; } ELEMCON *eval_member_con /* returns reference */ ( MPL *mpl, CONSTRAINT *con, /* not changed */ TUPLE *tuple /* not changed */ ) { /* this routine evaluates constraint member */ struct eval_con_info _info, *info = &_info; xassert(con->dim == tuple_dimen(mpl, tuple)); info->con = con; info->tuple = tuple; /* evaluate member, which has given n-tuple */ if (eval_within_domain(mpl, info->con->domain, info->tuple, info, eval_con_func)) out_of_domain(mpl, con->name, info->tuple); /* bring evaluated reference to the calling program */ return info->refer; } /*---------------------------------------------------------------------- -- eval_whole_con - evaluate model constraint over entire domain. -- -- This routine evaluates all members of specified model constraint over -- entire domain. */ static int whole_con_func(MPL *mpl, void *info) { /* this is auxiliary routine to work within domain scope */ CONSTRAINT *con = (CONSTRAINT *)info; TUPLE *tuple = get_domain_tuple(mpl, con->domain); eval_member_con(mpl, con, tuple); delete_tuple(mpl, tuple); return 0; } void eval_whole_con(MPL *mpl, CONSTRAINT *con) { loop_within_domain(mpl, con->domain, con, whole_con_func); return; } /*---------------------------------------------------------------------- -- clean_constraint - clean model constraint. -- -- This routine cleans specified model constraint that assumes deleting -- all stuff dynamically allocated during the generation phase. */ void clean_constraint(MPL *mpl, CONSTRAINT *con) { MEMBER *memb; /* clean subscript domain */ clean_domain(mpl, con->domain); /* clean code for computing main linear form */ clean_code(mpl, con->code); /* clean code for computing lower bound */ clean_code(mpl, con->lbnd); /* clean code for computing upper bound */ if (con->ubnd != con->lbnd) clean_code(mpl, con->ubnd); /* delete content array */ for (memb = con->array->head; memb != NULL; memb = memb->next) { delete_formula(mpl, memb->value.con->form); dmp_free_atom(mpl->elemcons, memb->value.con, sizeof(ELEMCON)); } delete_array(mpl, con->array), con->array = NULL; return; } /**********************************************************************/ /* * * PSEUDO-CODE * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- eval_numeric - evaluate pseudo-code to determine numeric value. -- -- This routine evaluates specified pseudo-code to determine resultant -- numeric value, which is returned on exit. */ struct iter_num_info { /* working info used by the routine iter_num_func */ CODE *code; /* pseudo-code for iterated operation to be performed */ double value; /* resultant value */ }; static int iter_num_func(MPL *mpl, void *_info) { /* this is auxiliary routine used to perform iterated operation on numeric "integrand" within domain scope */ struct iter_num_info *info = _info; double temp; temp = eval_numeric(mpl, info->code->arg.loop.x); switch (info->code->op) { case O_SUM: /* summation over domain */ info->value = fp_add(mpl, info->value, temp); break; case O_PROD: /* multiplication over domain */ info->value = fp_mul(mpl, info->value, temp); break; case O_MINIMUM: /* minimum over domain */ if (info->value > temp) info->value = temp; break; case O_MAXIMUM: /* maximum over domain */ if (info->value < temp) info->value = temp; break; default: xassert(info != info); } return 0; } double eval_numeric(MPL *mpl, CODE *code) { double value; xassert(code != NULL); xassert(code->type == A_NUMERIC); xassert(code->dim == 0); /* if the operation has a side effect, invalidate and delete the resultant value */ if (code->vflag && code->valid) { code->valid = 0; delete_value(mpl, code->type, &code->value); } /* if resultant value is valid, no evaluation is needed */ if (code->valid) { value = code->value.num; goto done; } /* evaluate pseudo-code recursively */ switch (code->op) { case O_NUMBER: /* take floating-point number */ value = code->arg.num; break; case O_MEMNUM: /* take member of numeric parameter */ { TUPLE *tuple; ARG_LIST *e; tuple = create_tuple(mpl); for (e = code->arg.par.list; e != NULL; e = e->next) tuple = expand_tuple(mpl, tuple, eval_symbolic(mpl, e->x)); value = eval_member_num(mpl, code->arg.par.par, tuple); delete_tuple(mpl, tuple); } break; case O_MEMVAR: /* take computed value of elemental variable */ { TUPLE *tuple; ARG_LIST *e; #if 1 /* 15/V-2010 */ ELEMVAR *var; #endif tuple = create_tuple(mpl); for (e = code->arg.var.list; e != NULL; e = e->next) tuple = expand_tuple(mpl, tuple, eval_symbolic(mpl, e->x)); #if 0 /* 15/V-2010 */ value = eval_member_var(mpl, code->arg.var.var, tuple) ->value; #else var = eval_member_var(mpl, code->arg.var.var, tuple); switch (code->arg.var.suff) { case DOT_LB: if (var->var->lbnd == NULL) value = -DBL_MAX; else value = var->lbnd; break; case DOT_UB: if (var->var->ubnd == NULL) value = +DBL_MAX; else value = var->ubnd; break; case DOT_STATUS: value = var->stat; break; case DOT_VAL: value = var->prim; break; case DOT_DUAL: value = var->dual; break; default: xassert(code != code); } #endif delete_tuple(mpl, tuple); } break; #if 1 /* 15/V-2010 */ case O_MEMCON: /* take computed value of elemental constraint */ { TUPLE *tuple; ARG_LIST *e; ELEMCON *con; tuple = create_tuple(mpl); for (e = code->arg.con.list; e != NULL; e = e->next) tuple = expand_tuple(mpl, tuple, eval_symbolic(mpl, e->x)); con = eval_member_con(mpl, code->arg.con.con, tuple); switch (code->arg.con.suff) { case DOT_LB: if (con->con->lbnd == NULL) value = -DBL_MAX; else value = con->lbnd; break; case DOT_UB: if (con->con->ubnd == NULL) value = +DBL_MAX; else value = con->ubnd; break; case DOT_STATUS: value = con->stat; break; case DOT_VAL: value = con->prim; break; case DOT_DUAL: value = con->dual; break; default: xassert(code != code); } delete_tuple(mpl, tuple); } break; #endif case O_IRAND224: /* pseudo-random in [0, 2^24-1] */ value = fp_irand224(mpl); break; case O_UNIFORM01: /* pseudo-random in [0, 1) */ value = fp_uniform01(mpl); break; case O_NORMAL01: /* gaussian random, mu = 0, sigma = 1 */ value = fp_normal01(mpl); break; case O_GMTIME: /* current calendar time */ value = fn_gmtime(mpl); break; case O_CVTNUM: /* conversion to numeric */ { SYMBOL *sym; sym = eval_symbolic(mpl, code->arg.arg.x); #if 0 /* 23/XI-2008 */ if (sym->str != NULL) mpl_error(mpl, "cannot convert %s to floating-point numbe" "r", format_symbol(mpl, sym)); value = sym->num; #else if (sym->str == NULL) value = sym->num; else { if (str2num(sym->str, &value)) mpl_error(mpl, "cannot convert %s to floating-point nu" "mber", format_symbol(mpl, sym)); } #endif delete_symbol(mpl, sym); } break; case O_PLUS: /* unary plus */ value = + eval_numeric(mpl, code->arg.arg.x); break; case O_MINUS: /* unary minus */ value = - eval_numeric(mpl, code->arg.arg.x); break; case O_ABS: /* absolute value */ value = fabs(eval_numeric(mpl, code->arg.arg.x)); break; case O_CEIL: /* round upward ("ceiling of x") */ value = ceil(eval_numeric(mpl, code->arg.arg.x)); break; case O_FLOOR: /* round downward ("floor of x") */ value = floor(eval_numeric(mpl, code->arg.arg.x)); break; case O_EXP: /* base-e exponential */ value = fp_exp(mpl, eval_numeric(mpl, code->arg.arg.x)); break; case O_LOG: /* natural logarithm */ value = fp_log(mpl, eval_numeric(mpl, code->arg.arg.x)); break; case O_LOG10: /* common (decimal) logarithm */ value = fp_log10(mpl, eval_numeric(mpl, code->arg.arg.x)); break; case O_SQRT: /* square root */ value = fp_sqrt(mpl, eval_numeric(mpl, code->arg.arg.x)); break; case O_SIN: /* trigonometric sine */ value = fp_sin(mpl, eval_numeric(mpl, code->arg.arg.x)); break; case O_COS: /* trigonometric cosine */ value = fp_cos(mpl, eval_numeric(mpl, code->arg.arg.x)); break; case O_ATAN: /* trigonometric arctangent (one argument) */ value = fp_atan(mpl, eval_numeric(mpl, code->arg.arg.x)); break; case O_ATAN2: /* trigonometric arctangent (two arguments) */ value = fp_atan2(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_ROUND: /* round to nearest integer */ value = fp_round(mpl, eval_numeric(mpl, code->arg.arg.x), 0.0); break; case O_ROUND2: /* round to n fractional digits */ value = fp_round(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_TRUNC: /* truncate to nearest integer */ value = fp_trunc(mpl, eval_numeric(mpl, code->arg.arg.x), 0.0); break; case O_TRUNC2: /* truncate to n fractional digits */ value = fp_trunc(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_ADD: /* addition */ value = fp_add(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_SUB: /* subtraction */ value = fp_sub(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_LESS: /* non-negative subtraction */ value = fp_less(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_MUL: /* multiplication */ value = fp_mul(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_DIV: /* division */ value = fp_div(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_IDIV: /* quotient of exact division */ value = fp_idiv(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_MOD: /* remainder of exact division */ value = fp_mod(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_POWER: /* exponentiation (raise to power) */ value = fp_power(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_UNIFORM: /* pseudo-random in [a, b) */ value = fp_uniform(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_NORMAL: /* gaussian random, given mu and sigma */ value = fp_normal(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y)); break; case O_CARD: { ELEMSET *set; set = eval_elemset(mpl, code->arg.arg.x); value = set->size; delete_array(mpl, set); } break; case O_LENGTH: { SYMBOL *sym; char str[MAX_LENGTH+1]; sym = eval_symbolic(mpl, code->arg.arg.x); if (sym->str == NULL) sprintf(str, "%.*g", DBL_DIG, sym->num); else fetch_string(mpl, sym->str, str); delete_symbol(mpl, sym); value = strlen(str); } break; case O_STR2TIME: { SYMBOL *sym; char str[MAX_LENGTH+1], fmt[MAX_LENGTH+1]; sym = eval_symbolic(mpl, code->arg.arg.x); if (sym->str == NULL) sprintf(str, "%.*g", DBL_DIG, sym->num); else fetch_string(mpl, sym->str, str); delete_symbol(mpl, sym); sym = eval_symbolic(mpl, code->arg.arg.y); if (sym->str == NULL) sprintf(fmt, "%.*g", DBL_DIG, sym->num); else fetch_string(mpl, sym->str, fmt); delete_symbol(mpl, sym); value = fn_str2time(mpl, str, fmt); } break; case O_FORK: /* if-then-else */ if (eval_logical(mpl, code->arg.arg.x)) value = eval_numeric(mpl, code->arg.arg.y); else if (code->arg.arg.z == NULL) value = 0.0; else value = eval_numeric(mpl, code->arg.arg.z); break; case O_MIN: /* minimal value (n-ary) */ { ARG_LIST *e; double temp; value = +DBL_MAX; for (e = code->arg.list; e != NULL; e = e->next) { temp = eval_numeric(mpl, e->x); if (value > temp) value = temp; } } break; case O_MAX: /* maximal value (n-ary) */ { ARG_LIST *e; double temp; value = -DBL_MAX; for (e = code->arg.list; e != NULL; e = e->next) { temp = eval_numeric(mpl, e->x); if (value < temp) value = temp; } } break; case O_SUM: /* summation over domain */ { struct iter_num_info _info, *info = &_info; info->code = code; info->value = 0.0; loop_within_domain(mpl, code->arg.loop.domain, info, iter_num_func); value = info->value; } break; case O_PROD: /* multiplication over domain */ { struct iter_num_info _info, *info = &_info; info->code = code; info->value = 1.0; loop_within_domain(mpl, code->arg.loop.domain, info, iter_num_func); value = info->value; } break; case O_MINIMUM: /* minimum over domain */ { struct iter_num_info _info, *info = &_info; info->code = code; info->value = +DBL_MAX; loop_within_domain(mpl, code->arg.loop.domain, info, iter_num_func); if (info->value == +DBL_MAX) mpl_error(mpl, "min{} over empty set; result undefined"); value = info->value; } break; case O_MAXIMUM: /* maximum over domain */ { struct iter_num_info _info, *info = &_info; info->code = code; info->value = -DBL_MAX; loop_within_domain(mpl, code->arg.loop.domain, info, iter_num_func); if (info->value == -DBL_MAX) mpl_error(mpl, "max{} over empty set; result undefined"); value = info->value; } break; default: xassert(code != code); } /* save resultant value */ xassert(!code->valid); code->valid = 1; code->value.num = value; done: return value; } /*---------------------------------------------------------------------- -- eval_symbolic - evaluate pseudo-code to determine symbolic value. -- -- This routine evaluates specified pseudo-code to determine resultant -- symbolic value, which is returned on exit. */ SYMBOL *eval_symbolic(MPL *mpl, CODE *code) { SYMBOL *value; xassert(code != NULL); xassert(code->type == A_SYMBOLIC); xassert(code->dim == 0); /* if the operation has a side effect, invalidate and delete the resultant value */ if (code->vflag && code->valid) { code->valid = 0; delete_value(mpl, code->type, &code->value); } /* if resultant value is valid, no evaluation is needed */ if (code->valid) { value = copy_symbol(mpl, code->value.sym); goto done; } /* evaluate pseudo-code recursively */ switch (code->op) { case O_STRING: /* take character string */ value = create_symbol_str(mpl, create_string(mpl, code->arg.str)); break; case O_INDEX: /* take dummy index */ xassert(code->arg.index.slot->value != NULL); value = copy_symbol(mpl, code->arg.index.slot->value); break; case O_MEMSYM: /* take member of symbolic parameter */ { TUPLE *tuple; ARG_LIST *e; tuple = create_tuple(mpl); for (e = code->arg.par.list; e != NULL; e = e->next) tuple = expand_tuple(mpl, tuple, eval_symbolic(mpl, e->x)); value = eval_member_sym(mpl, code->arg.par.par, tuple); delete_tuple(mpl, tuple); } break; case O_CVTSYM: /* conversion to symbolic */ value = create_symbol_num(mpl, eval_numeric(mpl, code->arg.arg.x)); break; case O_CONCAT: /* concatenation */ value = concat_symbols(mpl, eval_symbolic(mpl, code->arg.arg.x), eval_symbolic(mpl, code->arg.arg.y)); break; case O_FORK: /* if-then-else */ if (eval_logical(mpl, code->arg.arg.x)) value = eval_symbolic(mpl, code->arg.arg.y); else if (code->arg.arg.z == NULL) value = create_symbol_num(mpl, 0.0); else value = eval_symbolic(mpl, code->arg.arg.z); break; case O_SUBSTR: case O_SUBSTR3: { double pos, len; char str[MAX_LENGTH+1]; value = eval_symbolic(mpl, code->arg.arg.x); if (value->str == NULL) sprintf(str, "%.*g", DBL_DIG, value->num); else fetch_string(mpl, value->str, str); delete_symbol(mpl, value); if (code->op == O_SUBSTR) { pos = eval_numeric(mpl, code->arg.arg.y); if (pos != floor(pos)) mpl_error(mpl, "substr('...', %.*g); non-integer secon" "d argument", DBL_DIG, pos); if (pos < 1 || pos > strlen(str) + 1) mpl_error(mpl, "substr('...', %.*g); substring out of " "range", DBL_DIG, pos); } else { pos = eval_numeric(mpl, code->arg.arg.y); len = eval_numeric(mpl, code->arg.arg.z); if (pos != floor(pos) || len != floor(len)) mpl_error(mpl, "substr('...', %.*g, %.*g); non-integer" " second and/or third argument", DBL_DIG, pos, DBL_DIG, len); if (pos < 1 || len < 0 || pos + len > strlen(str) + 1) mpl_error(mpl, "substr('...', %.*g, %.*g); substring o" "ut of range", DBL_DIG, pos, DBL_DIG, len); str[(int)pos + (int)len - 1] = '\0'; } value = create_symbol_str(mpl, create_string(mpl, str + (int)pos - 1)); } break; case O_TIME2STR: { double num; SYMBOL *sym; char str[MAX_LENGTH+1], fmt[MAX_LENGTH+1]; num = eval_numeric(mpl, code->arg.arg.x); sym = eval_symbolic(mpl, code->arg.arg.y); if (sym->str == NULL) sprintf(fmt, "%.*g", DBL_DIG, sym->num); else fetch_string(mpl, sym->str, fmt); delete_symbol(mpl, sym); fn_time2str(mpl, str, num, fmt); value = create_symbol_str(mpl, create_string(mpl, str)); } break; default: xassert(code != code); } /* save resultant value */ xassert(!code->valid); code->valid = 1; code->value.sym = copy_symbol(mpl, value); done: return value; } /*---------------------------------------------------------------------- -- eval_logical - evaluate pseudo-code to determine logical value. -- -- This routine evaluates specified pseudo-code to determine resultant -- logical value, which is returned on exit. */ struct iter_log_info { /* working info used by the routine iter_log_func */ CODE *code; /* pseudo-code for iterated operation to be performed */ int value; /* resultant value */ }; static int iter_log_func(MPL *mpl, void *_info) { /* this is auxiliary routine used to perform iterated operation on logical "integrand" within domain scope */ struct iter_log_info *info = _info; int ret = 0; switch (info->code->op) { case O_FORALL: /* conjunction over domain */ info->value &= eval_logical(mpl, info->code->arg.loop.x); if (!info->value) ret = 1; break; case O_EXISTS: /* disjunction over domain */ info->value |= eval_logical(mpl, info->code->arg.loop.x); if (info->value) ret = 1; break; default: xassert(info != info); } return ret; } int eval_logical(MPL *mpl, CODE *code) { int value; xassert(code->type == A_LOGICAL); xassert(code->dim == 0); /* if the operation has a side effect, invalidate and delete the resultant value */ if (code->vflag && code->valid) { code->valid = 0; delete_value(mpl, code->type, &code->value); } /* if resultant value is valid, no evaluation is needed */ if (code->valid) { value = code->value.bit; goto done; } /* evaluate pseudo-code recursively */ switch (code->op) { case O_CVTLOG: /* conversion to logical */ value = (eval_numeric(mpl, code->arg.arg.x) != 0.0); break; case O_NOT: /* negation (logical "not") */ value = !eval_logical(mpl, code->arg.arg.x); break; case O_LT: /* comparison on 'less than' */ #if 0 /* 02/VIII-2008 */ value = (eval_numeric(mpl, code->arg.arg.x) < eval_numeric(mpl, code->arg.arg.y)); #else xassert(code->arg.arg.x != NULL); if (code->arg.arg.x->type == A_NUMERIC) value = (eval_numeric(mpl, code->arg.arg.x) < eval_numeric(mpl, code->arg.arg.y)); else { SYMBOL *sym1 = eval_symbolic(mpl, code->arg.arg.x); SYMBOL *sym2 = eval_symbolic(mpl, code->arg.arg.y); value = (compare_symbols(mpl, sym1, sym2) < 0); delete_symbol(mpl, sym1); delete_symbol(mpl, sym2); } #endif break; case O_LE: /* comparison on 'not greater than' */ #if 0 /* 02/VIII-2008 */ value = (eval_numeric(mpl, code->arg.arg.x) <= eval_numeric(mpl, code->arg.arg.y)); #else xassert(code->arg.arg.x != NULL); if (code->arg.arg.x->type == A_NUMERIC) value = (eval_numeric(mpl, code->arg.arg.x) <= eval_numeric(mpl, code->arg.arg.y)); else { SYMBOL *sym1 = eval_symbolic(mpl, code->arg.arg.x); SYMBOL *sym2 = eval_symbolic(mpl, code->arg.arg.y); value = (compare_symbols(mpl, sym1, sym2) <= 0); delete_symbol(mpl, sym1); delete_symbol(mpl, sym2); } #endif break; case O_EQ: /* comparison on 'equal to' */ xassert(code->arg.arg.x != NULL); if (code->arg.arg.x->type == A_NUMERIC) value = (eval_numeric(mpl, code->arg.arg.x) == eval_numeric(mpl, code->arg.arg.y)); else { SYMBOL *sym1 = eval_symbolic(mpl, code->arg.arg.x); SYMBOL *sym2 = eval_symbolic(mpl, code->arg.arg.y); value = (compare_symbols(mpl, sym1, sym2) == 0); delete_symbol(mpl, sym1); delete_symbol(mpl, sym2); } break; case O_GE: /* comparison on 'not less than' */ #if 0 /* 02/VIII-2008 */ value = (eval_numeric(mpl, code->arg.arg.x) >= eval_numeric(mpl, code->arg.arg.y)); #else xassert(code->arg.arg.x != NULL); if (code->arg.arg.x->type == A_NUMERIC) value = (eval_numeric(mpl, code->arg.arg.x) >= eval_numeric(mpl, code->arg.arg.y)); else { SYMBOL *sym1 = eval_symbolic(mpl, code->arg.arg.x); SYMBOL *sym2 = eval_symbolic(mpl, code->arg.arg.y); value = (compare_symbols(mpl, sym1, sym2) >= 0); delete_symbol(mpl, sym1); delete_symbol(mpl, sym2); } #endif break; case O_GT: /* comparison on 'greater than' */ #if 0 /* 02/VIII-2008 */ value = (eval_numeric(mpl, code->arg.arg.x) > eval_numeric(mpl, code->arg.arg.y)); #else xassert(code->arg.arg.x != NULL); if (code->arg.arg.x->type == A_NUMERIC) value = (eval_numeric(mpl, code->arg.arg.x) > eval_numeric(mpl, code->arg.arg.y)); else { SYMBOL *sym1 = eval_symbolic(mpl, code->arg.arg.x); SYMBOL *sym2 = eval_symbolic(mpl, code->arg.arg.y); value = (compare_symbols(mpl, sym1, sym2) > 0); delete_symbol(mpl, sym1); delete_symbol(mpl, sym2); } #endif break; case O_NE: /* comparison on 'not equal to' */ xassert(code->arg.arg.x != NULL); if (code->arg.arg.x->type == A_NUMERIC) value = (eval_numeric(mpl, code->arg.arg.x) != eval_numeric(mpl, code->arg.arg.y)); else { SYMBOL *sym1 = eval_symbolic(mpl, code->arg.arg.x); SYMBOL *sym2 = eval_symbolic(mpl, code->arg.arg.y); value = (compare_symbols(mpl, sym1, sym2) != 0); delete_symbol(mpl, sym1); delete_symbol(mpl, sym2); } break; case O_AND: /* conjunction (logical "and") */ value = eval_logical(mpl, code->arg.arg.x) && eval_logical(mpl, code->arg.arg.y); break; case O_OR: /* disjunction (logical "or") */ value = eval_logical(mpl, code->arg.arg.x) || eval_logical(mpl, code->arg.arg.y); break; case O_IN: /* test on 'x in Y' */ { TUPLE *tuple; tuple = eval_tuple(mpl, code->arg.arg.x); value = is_member(mpl, code->arg.arg.y, tuple); delete_tuple(mpl, tuple); } break; case O_NOTIN: /* test on 'x not in Y' */ { TUPLE *tuple; tuple = eval_tuple(mpl, code->arg.arg.x); value = !is_member(mpl, code->arg.arg.y, tuple); delete_tuple(mpl, tuple); } break; case O_WITHIN: /* test on 'X within Y' */ { ELEMSET *set; MEMBER *memb; set = eval_elemset(mpl, code->arg.arg.x); value = 1; for (memb = set->head; memb != NULL; memb = memb->next) { if (!is_member(mpl, code->arg.arg.y, memb->tuple)) { value = 0; break; } } delete_elemset(mpl, set); } break; case O_NOTWITHIN: /* test on 'X not within Y' */ { ELEMSET *set; MEMBER *memb; set = eval_elemset(mpl, code->arg.arg.x); value = 1; for (memb = set->head; memb != NULL; memb = memb->next) { if (is_member(mpl, code->arg.arg.y, memb->tuple)) { value = 0; break; } } delete_elemset(mpl, set); } break; case O_FORALL: /* conjunction (A-quantification) */ { struct iter_log_info _info, *info = &_info; info->code = code; info->value = 1; loop_within_domain(mpl, code->arg.loop.domain, info, iter_log_func); value = info->value; } break; case O_EXISTS: /* disjunction (E-quantification) */ { struct iter_log_info _info, *info = &_info; info->code = code; info->value = 0; loop_within_domain(mpl, code->arg.loop.domain, info, iter_log_func); value = info->value; } break; default: xassert(code != code); } /* save resultant value */ xassert(!code->valid); code->valid = 1; code->value.bit = value; done: return value; } /*---------------------------------------------------------------------- -- eval_tuple - evaluate pseudo-code to construct n-tuple. -- -- This routine evaluates specified pseudo-code to construct resultant -- n-tuple, which is returned on exit. */ TUPLE *eval_tuple(MPL *mpl, CODE *code) { TUPLE *value; xassert(code != NULL); xassert(code->type == A_TUPLE); xassert(code->dim > 0); /* if the operation has a side effect, invalidate and delete the resultant value */ if (code->vflag && code->valid) { code->valid = 0; delete_value(mpl, code->type, &code->value); } /* if resultant value is valid, no evaluation is needed */ if (code->valid) { value = copy_tuple(mpl, code->value.tuple); goto done; } /* evaluate pseudo-code recursively */ switch (code->op) { case O_TUPLE: /* make n-tuple */ { ARG_LIST *e; value = create_tuple(mpl); for (e = code->arg.list; e != NULL; e = e->next) value = expand_tuple(mpl, value, eval_symbolic(mpl, e->x)); } break; case O_CVTTUP: /* convert to 1-tuple */ value = expand_tuple(mpl, create_tuple(mpl), eval_symbolic(mpl, code->arg.arg.x)); break; default: xassert(code != code); } /* save resultant value */ xassert(!code->valid); code->valid = 1; code->value.tuple = copy_tuple(mpl, value); done: return value; } /*---------------------------------------------------------------------- -- eval_elemset - evaluate pseudo-code to construct elemental set. -- -- This routine evaluates specified pseudo-code to construct resultant -- elemental set, which is returned on exit. */ struct iter_set_info { /* working info used by the routine iter_set_func */ CODE *code; /* pseudo-code for iterated operation to be performed */ ELEMSET *value; /* resultant value */ }; static int iter_set_func(MPL *mpl, void *_info) { /* this is auxiliary routine used to perform iterated operation on n-tuple "integrand" within domain scope */ struct iter_set_info *info = _info; TUPLE *tuple; switch (info->code->op) { case O_SETOF: /* compute next n-tuple and add it to the set; in this case duplicate n-tuples are silently ignored */ tuple = eval_tuple(mpl, info->code->arg.loop.x); if (find_tuple(mpl, info->value, tuple) == NULL) add_tuple(mpl, info->value, tuple); else delete_tuple(mpl, tuple); break; case O_BUILD: /* construct next n-tuple using current values assigned to *free* dummy indices as its components and add it to the set; in this case duplicate n-tuples cannot appear */ add_tuple(mpl, info->value, get_domain_tuple(mpl, info->code->arg.loop.domain)); break; default: xassert(info != info); } return 0; } ELEMSET *eval_elemset(MPL *mpl, CODE *code) { ELEMSET *value; xassert(code != NULL); xassert(code->type == A_ELEMSET); xassert(code->dim > 0); /* if the operation has a side effect, invalidate and delete the resultant value */ if (code->vflag && code->valid) { code->valid = 0; delete_value(mpl, code->type, &code->value); } /* if resultant value is valid, no evaluation is needed */ if (code->valid) { value = copy_elemset(mpl, code->value.set); goto done; } /* evaluate pseudo-code recursively */ switch (code->op) { case O_MEMSET: /* take member of set */ { TUPLE *tuple; ARG_LIST *e; tuple = create_tuple(mpl); for (e = code->arg.set.list; e != NULL; e = e->next) tuple = expand_tuple(mpl, tuple, eval_symbolic(mpl, e->x)); value = copy_elemset(mpl, eval_member_set(mpl, code->arg.set.set, tuple)); delete_tuple(mpl, tuple); } break; case O_MAKE: /* make elemental set of n-tuples */ { ARG_LIST *e; value = create_elemset(mpl, code->dim); for (e = code->arg.list; e != NULL; e = e->next) check_then_add(mpl, value, eval_tuple(mpl, e->x)); } break; case O_UNION: /* union of two elemental sets */ value = set_union(mpl, eval_elemset(mpl, code->arg.arg.x), eval_elemset(mpl, code->arg.arg.y)); break; case O_DIFF: /* difference between two elemental sets */ value = set_diff(mpl, eval_elemset(mpl, code->arg.arg.x), eval_elemset(mpl, code->arg.arg.y)); break; case O_SYMDIFF: /* symmetric difference between two elemental sets */ value = set_symdiff(mpl, eval_elemset(mpl, code->arg.arg.x), eval_elemset(mpl, code->arg.arg.y)); break; case O_INTER: /* intersection of two elemental sets */ value = set_inter(mpl, eval_elemset(mpl, code->arg.arg.x), eval_elemset(mpl, code->arg.arg.y)); break; case O_CROSS: /* cross (Cartesian) product of two elemental sets */ value = set_cross(mpl, eval_elemset(mpl, code->arg.arg.x), eval_elemset(mpl, code->arg.arg.y)); break; case O_DOTS: /* build "arithmetic" elemental set */ value = create_arelset(mpl, eval_numeric(mpl, code->arg.arg.x), eval_numeric(mpl, code->arg.arg.y), code->arg.arg.z == NULL ? 1.0 : eval_numeric(mpl, code->arg.arg.z)); break; case O_FORK: /* if-then-else */ if (eval_logical(mpl, code->arg.arg.x)) value = eval_elemset(mpl, code->arg.arg.y); else value = eval_elemset(mpl, code->arg.arg.z); break; case O_SETOF: /* compute elemental set */ { struct iter_set_info _info, *info = &_info; info->code = code; info->value = create_elemset(mpl, code->dim); loop_within_domain(mpl, code->arg.loop.domain, info, iter_set_func); value = info->value; } break; case O_BUILD: /* build elemental set identical to domain set */ { struct iter_set_info _info, *info = &_info; info->code = code; info->value = create_elemset(mpl, code->dim); loop_within_domain(mpl, code->arg.loop.domain, info, iter_set_func); value = info->value; } break; default: xassert(code != code); } /* save resultant value */ xassert(!code->valid); code->valid = 1; code->value.set = copy_elemset(mpl, value); done: return value; } /*---------------------------------------------------------------------- -- is_member - check if n-tuple is in set specified by pseudo-code. -- -- This routine checks if given n-tuple is a member of elemental set -- specified in the form of pseudo-code (i.e. by expression). -- -- The n-tuple may have more components that dimension of the elemental -- set, in which case the extra components are ignored. */ static void null_func(MPL *mpl, void *info) { /* this is dummy routine used to enter the domain scope */ xassert(mpl == mpl); xassert(info == NULL); return; } int is_member(MPL *mpl, CODE *code, TUPLE *tuple) { int value; xassert(code != NULL); xassert(code->type == A_ELEMSET); xassert(code->dim > 0); xassert(tuple != NULL); switch (code->op) { case O_MEMSET: /* check if given n-tuple is member of elemental set, which is assigned to member of model set */ { ARG_LIST *e; TUPLE *temp; ELEMSET *set; /* evaluate reference to elemental set */ temp = create_tuple(mpl); for (e = code->arg.set.list; e != NULL; e = e->next) temp = expand_tuple(mpl, temp, eval_symbolic(mpl, e->x)); set = eval_member_set(mpl, code->arg.set.set, temp); delete_tuple(mpl, temp); /* check if the n-tuple is contained in the set array */ temp = build_subtuple(mpl, tuple, set->dim); value = (find_tuple(mpl, set, temp) != NULL); delete_tuple(mpl, temp); } break; case O_MAKE: /* check if given n-tuple is member of literal set */ { ARG_LIST *e; TUPLE *temp, *that; value = 0; temp = build_subtuple(mpl, tuple, code->dim); for (e = code->arg.list; e != NULL; e = e->next) { that = eval_tuple(mpl, e->x); value = (compare_tuples(mpl, temp, that) == 0); delete_tuple(mpl, that); if (value) break; } delete_tuple(mpl, temp); } break; case O_UNION: value = is_member(mpl, code->arg.arg.x, tuple) || is_member(mpl, code->arg.arg.y, tuple); break; case O_DIFF: value = is_member(mpl, code->arg.arg.x, tuple) && !is_member(mpl, code->arg.arg.y, tuple); break; case O_SYMDIFF: { int in1 = is_member(mpl, code->arg.arg.x, tuple); int in2 = is_member(mpl, code->arg.arg.y, tuple); value = (in1 && !in2) || (!in1 && in2); } break; case O_INTER: value = is_member(mpl, code->arg.arg.x, tuple) && is_member(mpl, code->arg.arg.y, tuple); break; case O_CROSS: { int j; value = is_member(mpl, code->arg.arg.x, tuple); if (value) { for (j = 1; j <= code->arg.arg.x->dim; j++) { xassert(tuple != NULL); tuple = tuple->next; } value = is_member(mpl, code->arg.arg.y, tuple); } } break; case O_DOTS: /* check if given 1-tuple is member of "arithmetic" set */ { int j; double x, t0, tf, dt; xassert(code->dim == 1); /* compute "parameters" of the "arithmetic" set */ t0 = eval_numeric(mpl, code->arg.arg.x); tf = eval_numeric(mpl, code->arg.arg.y); if (code->arg.arg.z == NULL) dt = 1.0; else dt = eval_numeric(mpl, code->arg.arg.z); /* make sure the parameters are correct */ arelset_size(mpl, t0, tf, dt); /* if component of 1-tuple is symbolic, not numeric, the 1-tuple cannot be member of "arithmetic" set */ xassert(tuple->sym != NULL); if (tuple->sym->str != NULL) { value = 0; break; } /* determine numeric value of the component */ x = tuple->sym->num; /* if the component value is out of the set range, the 1-tuple is not in the set */ if (dt > 0.0 && !(t0 <= x && x <= tf) || dt < 0.0 && !(tf <= x && x <= t0)) { value = 0; break; } /* estimate ordinal number of the 1-tuple in the set */ j = (int)(((x - t0) / dt) + 0.5) + 1; /* perform the main check */ value = (arelset_member(mpl, t0, tf, dt, j) == x); } break; case O_FORK: /* check if given n-tuple is member of conditional set */ if (eval_logical(mpl, code->arg.arg.x)) value = is_member(mpl, code->arg.arg.y, tuple); else value = is_member(mpl, code->arg.arg.z, tuple); break; case O_SETOF: /* check if given n-tuple is member of computed set */ /* it is not clear how to efficiently perform the check not computing the entire elemental set :+( */ mpl_error(mpl, "implementation restriction; in/within setof{} n" "ot allowed"); break; case O_BUILD: /* check if given n-tuple is member of domain set */ { TUPLE *temp; temp = build_subtuple(mpl, tuple, code->dim); /* try to enter the domain scope; if it is successful, the n-tuple is in the domain set */ value = (eval_within_domain(mpl, code->arg.loop.domain, temp, NULL, null_func) == 0); delete_tuple(mpl, temp); } break; default: xassert(code != code); } return value; } /*---------------------------------------------------------------------- -- eval_formula - evaluate pseudo-code to construct linear form. -- -- This routine evaluates specified pseudo-code to construct resultant -- linear form, which is returned on exit. */ struct iter_form_info { /* working info used by the routine iter_form_func */ CODE *code; /* pseudo-code for iterated operation to be performed */ FORMULA *value; /* resultant value */ FORMULA *tail; /* pointer to the last term */ }; static int iter_form_func(MPL *mpl, void *_info) { /* this is auxiliary routine used to perform iterated operation on linear form "integrand" within domain scope */ struct iter_form_info *info = _info; switch (info->code->op) { case O_SUM: /* summation over domain */ #if 0 info->value = linear_comb(mpl, +1.0, info->value, +1.0, eval_formula(mpl, info->code->arg.loop.x)); #else /* the routine linear_comb needs to look through all terms of both linear forms to reduce identical terms, so using it here is not a good idea (for example, evaluation of sum{i in 1..n} x[i] required quadratic time); the better idea is to gather all terms of the integrand in one list and reduce identical terms only once after all terms of the resultant linear form have been evaluated */ { FORMULA *form, *term; form = eval_formula(mpl, info->code->arg.loop.x); if (info->value == NULL) { xassert(info->tail == NULL); info->value = form; } else { xassert(info->tail != NULL); info->tail->next = form; } for (term = form; term != NULL; term = term->next) info->tail = term; } #endif break; default: xassert(info != info); } return 0; } FORMULA *eval_formula(MPL *mpl, CODE *code) { FORMULA *value; xassert(code != NULL); xassert(code->type == A_FORMULA); xassert(code->dim == 0); /* if the operation has a side effect, invalidate and delete the resultant value */ if (code->vflag && code->valid) { code->valid = 0; delete_value(mpl, code->type, &code->value); } /* if resultant value is valid, no evaluation is needed */ if (code->valid) { value = copy_formula(mpl, code->value.form); goto done; } /* evaluate pseudo-code recursively */ switch (code->op) { case O_MEMVAR: /* take member of variable */ { TUPLE *tuple; ARG_LIST *e; tuple = create_tuple(mpl); for (e = code->arg.var.list; e != NULL; e = e->next) tuple = expand_tuple(mpl, tuple, eval_symbolic(mpl, e->x)); #if 1 /* 15/V-2010 */ xassert(code->arg.var.suff == DOT_NONE); #endif value = single_variable(mpl, eval_member_var(mpl, code->arg.var.var, tuple)); delete_tuple(mpl, tuple); } break; case O_CVTLFM: /* convert to linear form */ value = constant_term(mpl, eval_numeric(mpl, code->arg.arg.x)); break; case O_PLUS: /* unary plus */ value = linear_comb(mpl, 0.0, constant_term(mpl, 0.0), +1.0, eval_formula(mpl, code->arg.arg.x)); break; case O_MINUS: /* unary minus */ value = linear_comb(mpl, 0.0, constant_term(mpl, 0.0), -1.0, eval_formula(mpl, code->arg.arg.x)); break; case O_ADD: /* addition */ value = linear_comb(mpl, +1.0, eval_formula(mpl, code->arg.arg.x), +1.0, eval_formula(mpl, code->arg.arg.y)); break; case O_SUB: /* subtraction */ value = linear_comb(mpl, +1.0, eval_formula(mpl, code->arg.arg.x), -1.0, eval_formula(mpl, code->arg.arg.y)); break; case O_MUL: /* multiplication */ xassert(code->arg.arg.x != NULL); xassert(code->arg.arg.y != NULL); if (code->arg.arg.x->type == A_NUMERIC) { xassert(code->arg.arg.y->type == A_FORMULA); value = linear_comb(mpl, eval_numeric(mpl, code->arg.arg.x), eval_formula(mpl, code->arg.arg.y), 0.0, constant_term(mpl, 0.0)); } else { xassert(code->arg.arg.x->type == A_FORMULA); xassert(code->arg.arg.y->type == A_NUMERIC); value = linear_comb(mpl, eval_numeric(mpl, code->arg.arg.y), eval_formula(mpl, code->arg.arg.x), 0.0, constant_term(mpl, 0.0)); } break; case O_DIV: /* division */ value = linear_comb(mpl, fp_div(mpl, 1.0, eval_numeric(mpl, code->arg.arg.y)), eval_formula(mpl, code->arg.arg.x), 0.0, constant_term(mpl, 0.0)); break; case O_FORK: /* if-then-else */ if (eval_logical(mpl, code->arg.arg.x)) value = eval_formula(mpl, code->arg.arg.y); else if (code->arg.arg.z == NULL) value = constant_term(mpl, 0.0); else value = eval_formula(mpl, code->arg.arg.z); break; case O_SUM: /* summation over domain */ { struct iter_form_info _info, *info = &_info; info->code = code; info->value = constant_term(mpl, 0.0); info->tail = NULL; loop_within_domain(mpl, code->arg.loop.domain, info, iter_form_func); value = reduce_terms(mpl, info->value); } break; default: xassert(code != code); } /* save resultant value */ xassert(!code->valid); code->valid = 1; code->value.form = copy_formula(mpl, value); done: return value; } /*---------------------------------------------------------------------- -- clean_code - clean pseudo-code. -- -- This routine recursively cleans specified pseudo-code that assumes -- deleting all temporary resultant values. */ void clean_code(MPL *mpl, CODE *code) { ARG_LIST *e; /* if no pseudo-code is specified, do nothing */ if (code == NULL) goto done; /* if resultant value is valid (exists), delete it */ if (code->valid) { code->valid = 0; delete_value(mpl, code->type, &code->value); } /* recursively clean pseudo-code for operands */ switch (code->op) { case O_NUMBER: case O_STRING: case O_INDEX: break; case O_MEMNUM: case O_MEMSYM: for (e = code->arg.par.list; e != NULL; e = e->next) clean_code(mpl, e->x); break; case O_MEMSET: for (e = code->arg.set.list; e != NULL; e = e->next) clean_code(mpl, e->x); break; case O_MEMVAR: for (e = code->arg.var.list; e != NULL; e = e->next) clean_code(mpl, e->x); break; #if 1 /* 15/V-2010 */ case O_MEMCON: for (e = code->arg.con.list; e != NULL; e = e->next) clean_code(mpl, e->x); break; #endif case O_TUPLE: case O_MAKE: for (e = code->arg.list; e != NULL; e = e->next) clean_code(mpl, e->x); break; case O_SLICE: xassert(code != code); case O_IRAND224: case O_UNIFORM01: case O_NORMAL01: case O_GMTIME: break; case O_CVTNUM: case O_CVTSYM: case O_CVTLOG: case O_CVTTUP: case O_CVTLFM: case O_PLUS: case O_MINUS: case O_NOT: case O_ABS: case O_CEIL: case O_FLOOR: case O_EXP: case O_LOG: case O_LOG10: case O_SQRT: case O_SIN: case O_COS: case O_ATAN: case O_ROUND: case O_TRUNC: case O_CARD: case O_LENGTH: /* unary operation */ clean_code(mpl, code->arg.arg.x); break; case O_ADD: case O_SUB: case O_LESS: case O_MUL: case O_DIV: case O_IDIV: case O_MOD: case O_POWER: case O_ATAN2: case O_ROUND2: case O_TRUNC2: case O_UNIFORM: case O_NORMAL: case O_CONCAT: case O_LT: case O_LE: case O_EQ: case O_GE: case O_GT: case O_NE: case O_AND: case O_OR: case O_UNION: case O_DIFF: case O_SYMDIFF: case O_INTER: case O_CROSS: case O_IN: case O_NOTIN: case O_WITHIN: case O_NOTWITHIN: case O_SUBSTR: case O_STR2TIME: case O_TIME2STR: /* binary operation */ clean_code(mpl, code->arg.arg.x); clean_code(mpl, code->arg.arg.y); break; case O_DOTS: case O_FORK: case O_SUBSTR3: /* ternary operation */ clean_code(mpl, code->arg.arg.x); clean_code(mpl, code->arg.arg.y); clean_code(mpl, code->arg.arg.z); break; case O_MIN: case O_MAX: /* n-ary operation */ for (e = code->arg.list; e != NULL; e = e->next) clean_code(mpl, e->x); break; case O_SUM: case O_PROD: case O_MINIMUM: case O_MAXIMUM: case O_FORALL: case O_EXISTS: case O_SETOF: case O_BUILD: /* iterated operation */ clean_domain(mpl, code->arg.loop.domain); clean_code(mpl, code->arg.loop.x); break; default: xassert(code->op != code->op); } done: return; } #if 1 /* 11/II-2008 */ /**********************************************************************/ /* * * DATA TABLES * * */ /**********************************************************************/ int mpl_tab_num_args(TABDCA *dca) { /* returns the number of arguments */ return dca->na; } const char *mpl_tab_get_arg(TABDCA *dca, int k) { /* returns pointer to k-th argument */ xassert(1 <= k && k <= dca->na); return dca->arg[k]; } int mpl_tab_num_flds(TABDCA *dca) { /* returns the number of fields */ return dca->nf; } const char *mpl_tab_get_name(TABDCA *dca, int k) { /* returns pointer to name of k-th field */ xassert(1 <= k && k <= dca->nf); return dca->name[k]; } int mpl_tab_get_type(TABDCA *dca, int k) { /* returns type of k-th field */ xassert(1 <= k && k <= dca->nf); return dca->type[k]; } double mpl_tab_get_num(TABDCA *dca, int k) { /* returns numeric value of k-th field */ xassert(1 <= k && k <= dca->nf); xassert(dca->type[k] == 'N'); return dca->num[k]; } const char *mpl_tab_get_str(TABDCA *dca, int k) { /* returns pointer to string value of k-th field */ xassert(1 <= k && k <= dca->nf); xassert(dca->type[k] == 'S'); xassert(dca->str[k] != NULL); return dca->str[k]; } void mpl_tab_set_num(TABDCA *dca, int k, double num) { /* assign numeric value to k-th field */ xassert(1 <= k && k <= dca->nf); xassert(dca->type[k] == '?'); dca->type[k] = 'N'; dca->num[k] = num; return; } void mpl_tab_set_str(TABDCA *dca, int k, const char *str) { /* assign string value to k-th field */ xassert(1 <= k && k <= dca->nf); xassert(dca->type[k] == '?'); xassert(strlen(str) <= MAX_LENGTH); xassert(dca->str[k] != NULL); dca->type[k] = 'S'; strcpy(dca->str[k], str); return; } static int write_func(MPL *mpl, void *info) { /* this is auxiliary routine to work within domain scope */ TABLE *tab = info; TABDCA *dca = mpl->dca; TABOUT *out; SYMBOL *sym; int k; char buf[MAX_LENGTH+1]; /* evaluate field values */ k = 0; for (out = tab->u.out.list; out != NULL; out = out->next) { k++; switch (out->code->type) { case A_NUMERIC: dca->type[k] = 'N'; dca->num[k] = eval_numeric(mpl, out->code); dca->str[k][0] = '\0'; break; case A_SYMBOLIC: sym = eval_symbolic(mpl, out->code); if (sym->str == NULL) { dca->type[k] = 'N'; dca->num[k] = sym->num; dca->str[k][0] = '\0'; } else { dca->type[k] = 'S'; dca->num[k] = 0.0; fetch_string(mpl, sym->str, buf); strcpy(dca->str[k], buf); } delete_symbol(mpl, sym); break; default: xassert(out != out); } } /* write record to output table */ mpl_tab_drv_write(mpl); return 0; } void execute_table(MPL *mpl, TABLE *tab) { /* execute table statement */ TABARG *arg; TABFLD *fld; TABIN *in; TABOUT *out; TABDCA *dca; SET *set; int k; char buf[MAX_LENGTH+1]; /* allocate table driver communication area */ xassert(mpl->dca == NULL); mpl->dca = dca = xmalloc(sizeof(TABDCA)); dca->id = 0; dca->link = NULL; dca->na = 0; dca->arg = NULL; dca->nf = 0; dca->name = NULL; dca->type = NULL; dca->num = NULL; dca->str = NULL; /* allocate arguments */ xassert(dca->na == 0); for (arg = tab->arg; arg != NULL; arg = arg->next) dca->na++; dca->arg = xcalloc(1+dca->na, sizeof(char *)); #if 1 /* 28/IX-2008 */ for (k = 1; k <= dca->na; k++) dca->arg[k] = NULL; #endif /* evaluate argument values */ k = 0; for (arg = tab->arg; arg != NULL; arg = arg->next) { SYMBOL *sym; k++; xassert(arg->code->type == A_SYMBOLIC); sym = eval_symbolic(mpl, arg->code); if (sym->str == NULL) sprintf(buf, "%.*g", DBL_DIG, sym->num); else fetch_string(mpl, sym->str, buf); delete_symbol(mpl, sym); dca->arg[k] = xmalloc(strlen(buf)+1); strcpy(dca->arg[k], buf); } /* perform table input/output */ switch (tab->type) { case A_INPUT: goto read_table; case A_OUTPUT: goto write_table; default: xassert(tab != tab); } read_table: /* read data from input table */ /* add the only member to the control set and assign it empty elemental set */ set = tab->u.in.set; if (set != NULL) { if (set->data) mpl_error(mpl, "%s already provided with data", set->name); xassert(set->array->head == NULL); add_member(mpl, set->array, NULL)->value.set = create_elemset(mpl, set->dimen); set->data = 1; } /* check parameters specified in the input list */ for (in = tab->u.in.list; in != NULL; in = in->next) { if (in->par->data) mpl_error(mpl, "%s already provided with data", in->par->name); in->par->data = 1; } /* allocate and initialize fields */ xassert(dca->nf == 0); for (fld = tab->u.in.fld; fld != NULL; fld = fld->next) dca->nf++; for (in = tab->u.in.list; in != NULL; in = in->next) dca->nf++; dca->name = xcalloc(1+dca->nf, sizeof(char *)); dca->type = xcalloc(1+dca->nf, sizeof(int)); dca->num = xcalloc(1+dca->nf, sizeof(double)); dca->str = xcalloc(1+dca->nf, sizeof(char *)); k = 0; for (fld = tab->u.in.fld; fld != NULL; fld = fld->next) { k++; dca->name[k] = fld->name; dca->type[k] = '?'; dca->num[k] = 0.0; dca->str[k] = xmalloc(MAX_LENGTH+1); dca->str[k][0] = '\0'; } for (in = tab->u.in.list; in != NULL; in = in->next) { k++; dca->name[k] = in->name; dca->type[k] = '?'; dca->num[k] = 0.0; dca->str[k] = xmalloc(MAX_LENGTH+1); dca->str[k][0] = '\0'; } /* open input table */ mpl_tab_drv_open(mpl, 'R'); /* read and process records */ for (;;) { TUPLE *tup; /* reset field types */ for (k = 1; k <= dca->nf; k++) dca->type[k] = '?'; /* read next record */ if (mpl_tab_drv_read(mpl)) break; /* all fields must be set by the driver */ for (k = 1; k <= dca->nf; k++) { if (dca->type[k] == '?') mpl_error(mpl, "field %s missing in input table", dca->name[k]); } /* construct n-tuple */ tup = create_tuple(mpl); k = 0; for (fld = tab->u.in.fld; fld != NULL; fld = fld->next) { k++; xassert(k <= dca->nf); switch (dca->type[k]) { case 'N': tup = expand_tuple(mpl, tup, create_symbol_num(mpl, dca->num[k])); break; case 'S': xassert(strlen(dca->str[k]) <= MAX_LENGTH); tup = expand_tuple(mpl, tup, create_symbol_str(mpl, create_string(mpl, dca->str[k]))); break; default: xassert(dca != dca); } } /* add n-tuple just read to the control set */ if (tab->u.in.set != NULL) check_then_add(mpl, tab->u.in.set->array->head->value.set, copy_tuple(mpl, tup)); /* assign values to the parameters in the input list */ for (in = tab->u.in.list; in != NULL; in = in->next) { MEMBER *memb; k++; xassert(k <= dca->nf); /* there must be no member with the same n-tuple */ if (find_member(mpl, in->par->array, tup) != NULL) mpl_error(mpl, "%s%s already defined", in->par->name, format_tuple(mpl, '[', tup)); /* create new parameter member with given n-tuple */ memb = add_member(mpl, in->par->array, copy_tuple(mpl, tup)) ; /* assign value to the parameter member */ switch (in->par->type) { case A_NUMERIC: case A_INTEGER: case A_BINARY: if (dca->type[k] != 'N') mpl_error(mpl, "%s requires numeric data", in->par->name); memb->value.num = dca->num[k]; break; case A_SYMBOLIC: switch (dca->type[k]) { case 'N': memb->value.sym = create_symbol_num(mpl, dca->num[k]); break; case 'S': xassert(strlen(dca->str[k]) <= MAX_LENGTH); memb->value.sym = create_symbol_str(mpl, create_string(mpl,dca->str[k])); break; default: xassert(dca != dca); } break; default: xassert(in != in); } } /* n-tuple is no more needed */ delete_tuple(mpl, tup); } /* close input table */ mpl_tab_drv_close(mpl); goto done; write_table: /* write data to output table */ /* allocate and initialize fields */ xassert(dca->nf == 0); for (out = tab->u.out.list; out != NULL; out = out->next) dca->nf++; dca->name = xcalloc(1+dca->nf, sizeof(char *)); dca->type = xcalloc(1+dca->nf, sizeof(int)); dca->num = xcalloc(1+dca->nf, sizeof(double)); dca->str = xcalloc(1+dca->nf, sizeof(char *)); k = 0; for (out = tab->u.out.list; out != NULL; out = out->next) { k++; dca->name[k] = out->name; dca->type[k] = '?'; dca->num[k] = 0.0; dca->str[k] = xmalloc(MAX_LENGTH+1); dca->str[k][0] = '\0'; } /* open output table */ mpl_tab_drv_open(mpl, 'W'); /* evaluate fields and write records */ loop_within_domain(mpl, tab->u.out.domain, tab, write_func); /* close output table */ mpl_tab_drv_close(mpl); done: /* free table driver communication area */ free_dca(mpl); return; } void free_dca(MPL *mpl) { /* free table driver communucation area */ TABDCA *dca = mpl->dca; int k; if (dca != NULL) { if (dca->link != NULL) mpl_tab_drv_close(mpl); if (dca->arg != NULL) { for (k = 1; k <= dca->na; k++) #if 1 /* 28/IX-2008 */ if (dca->arg[k] != NULL) #endif xfree(dca->arg[k]); xfree(dca->arg); } if (dca->name != NULL) xfree(dca->name); if (dca->type != NULL) xfree(dca->type); if (dca->num != NULL) xfree(dca->num); if (dca->str != NULL) { for (k = 1; k <= dca->nf; k++) xfree(dca->str[k]); xfree(dca->str); } xfree(dca), mpl->dca = NULL; } return; } void clean_table(MPL *mpl, TABLE *tab) { /* clean table statement */ TABARG *arg; TABOUT *out; /* clean string list */ for (arg = tab->arg; arg != NULL; arg = arg->next) clean_code(mpl, arg->code); switch (tab->type) { case A_INPUT: break; case A_OUTPUT: /* clean subscript domain */ clean_domain(mpl, tab->u.out.domain); /* clean output list */ for (out = tab->u.out.list; out != NULL; out = out->next) clean_code(mpl, out->code); break; default: xassert(tab != tab); } return; } #endif /**********************************************************************/ /* * * MODEL STATEMENTS * * */ /**********************************************************************/ /*---------------------------------------------------------------------- -- execute_check - execute check statement. -- -- This routine executes specified check statement. */ static int check_func(MPL *mpl, void *info) { /* this is auxiliary routine to work within domain scope */ CHECK *chk = (CHECK *)info; if (!eval_logical(mpl, chk->code)) mpl_error(mpl, "check%s failed", format_tuple(mpl, '[', get_domain_tuple(mpl, chk->domain))); return 0; } void execute_check(MPL *mpl, CHECK *chk) { loop_within_domain(mpl, chk->domain, chk, check_func); return; } /*---------------------------------------------------------------------- -- clean_check - clean check statement. -- -- This routine cleans specified check statement that assumes deleting -- all stuff dynamically allocated on generating/postsolving phase. */ void clean_check(MPL *mpl, CHECK *chk) { /* clean subscript domain */ clean_domain(mpl, chk->domain); /* clean pseudo-code for computing predicate */ clean_code(mpl, chk->code); return; } /*---------------------------------------------------------------------- -- execute_display - execute display statement. -- -- This routine executes specified display statement. */ static void display_set(MPL *mpl, SET *set, MEMBER *memb) { /* display member of model set */ ELEMSET *s = memb->value.set; MEMBER *m; write_text(mpl, "%s%s%s\n", set->name, format_tuple(mpl, '[', memb->tuple), s->head == NULL ? " is empty" : ":"); for (m = s->head; m != NULL; m = m->next) write_text(mpl, " %s\n", format_tuple(mpl, '(', m->tuple)); return; } static void display_par(MPL *mpl, PARAMETER *par, MEMBER *memb) { /* display member of model parameter */ switch (par->type) { case A_NUMERIC: case A_INTEGER: case A_BINARY: write_text(mpl, "%s%s = %.*g\n", par->name, format_tuple(mpl, '[', memb->tuple), DBL_DIG, memb->value.num); break; case A_SYMBOLIC: write_text(mpl, "%s%s = %s\n", par->name, format_tuple(mpl, '[', memb->tuple), format_symbol(mpl, memb->value.sym)); break; default: xassert(par != par); } return; } #if 1 /* 15/V-2010 */ static void display_var(MPL *mpl, VARIABLE *var, MEMBER *memb, int suff) { /* display member of model variable */ if (suff == DOT_NONE || suff == DOT_VAL) write_text(mpl, "%s%s.val = %.*g\n", var->name, format_tuple(mpl, '[', memb->tuple), DBL_DIG, memb->value.var->prim); else if (suff == DOT_LB) write_text(mpl, "%s%s.lb = %.*g\n", var->name, format_tuple(mpl, '[', memb->tuple), DBL_DIG, memb->value.var->var->lbnd == NULL ? -DBL_MAX : memb->value.var->lbnd); else if (suff == DOT_UB) write_text(mpl, "%s%s.ub = %.*g\n", var->name, format_tuple(mpl, '[', memb->tuple), DBL_DIG, memb->value.var->var->ubnd == NULL ? +DBL_MAX : memb->value.var->ubnd); else if (suff == DOT_STATUS) write_text(mpl, "%s%s.status = %d\n", var->name, format_tuple (mpl, '[', memb->tuple), memb->value.var->stat); else if (suff == DOT_DUAL) write_text(mpl, "%s%s.dual = %.*g\n", var->name, format_tuple(mpl, '[', memb->tuple), DBL_DIG, memb->value.var->dual); else xassert(suff != suff); return; } #endif #if 1 /* 15/V-2010 */ static void display_con(MPL *mpl, CONSTRAINT *con, MEMBER *memb, int suff) { /* display member of model constraint */ if (suff == DOT_NONE || suff == DOT_VAL) write_text(mpl, "%s%s.val = %.*g\n", con->name, format_tuple(mpl, '[', memb->tuple), DBL_DIG, memb->value.con->prim); else if (suff == DOT_LB) write_text(mpl, "%s%s.lb = %.*g\n", con->name, format_tuple(mpl, '[', memb->tuple), DBL_DIG, memb->value.con->con->lbnd == NULL ? -DBL_MAX : memb->value.con->lbnd); else if (suff == DOT_UB) write_text(mpl, "%s%s.ub = %.*g\n", con->name, format_tuple(mpl, '[', memb->tuple), DBL_DIG, memb->value.con->con->ubnd == NULL ? +DBL_MAX : memb->value.con->ubnd); else if (suff == DOT_STATUS) write_text(mpl, "%s%s.status = %d\n", con->name, format_tuple (mpl, '[', memb->tuple), memb->value.con->stat); else if (suff == DOT_DUAL) write_text(mpl, "%s%s.dual = %.*g\n", con->name, format_tuple(mpl, '[', memb->tuple), DBL_DIG, memb->value.con->dual); else xassert(suff != suff); return; } #endif static void display_memb(MPL *mpl, CODE *code) { /* display member specified by pseudo-code */ MEMBER memb; ARG_LIST *e; xassert(code->op == O_MEMNUM || code->op == O_MEMSYM || code->op == O_MEMSET || code->op == O_MEMVAR || code->op == O_MEMCON); memb.tuple = create_tuple(mpl); for (e = code->arg.par.list; e != NULL; e = e->next) memb.tuple = expand_tuple(mpl, memb.tuple, eval_symbolic(mpl, e->x)); switch (code->op) { case O_MEMNUM: memb.value.num = eval_member_num(mpl, code->arg.par.par, memb.tuple); display_par(mpl, code->arg.par.par, &memb); break; case O_MEMSYM: memb.value.sym = eval_member_sym(mpl, code->arg.par.par, memb.tuple); display_par(mpl, code->arg.par.par, &memb); delete_symbol(mpl, memb.value.sym); break; case O_MEMSET: memb.value.set = eval_member_set(mpl, code->arg.set.set, memb.tuple); display_set(mpl, code->arg.set.set, &memb); break; case O_MEMVAR: memb.value.var = eval_member_var(mpl, code->arg.var.var, memb.tuple); display_var (mpl, code->arg.var.var, &memb, code->arg.var.suff); break; case O_MEMCON: memb.value.con = eval_member_con(mpl, code->arg.con.con, memb.tuple); display_con (mpl, code->arg.con.con, &memb, code->arg.con.suff); break; default: xassert(code != code); } delete_tuple(mpl, memb.tuple); return; } static void display_code(MPL *mpl, CODE *code) { /* display value of expression */ switch (code->type) { case A_NUMERIC: /* numeric value */ { double num; num = eval_numeric(mpl, code); write_text(mpl, "%.*g\n", DBL_DIG, num); } break; case A_SYMBOLIC: /* symbolic value */ { SYMBOL *sym; sym = eval_symbolic(mpl, code); write_text(mpl, "%s\n", format_symbol(mpl, sym)); delete_symbol(mpl, sym); } break; case A_LOGICAL: /* logical value */ { int bit; bit = eval_logical(mpl, code); write_text(mpl, "%s\n", bit ? "true" : "false"); } break; case A_TUPLE: /* n-tuple */ { TUPLE *tuple; tuple = eval_tuple(mpl, code); write_text(mpl, "%s\n", format_tuple(mpl, '(', tuple)); delete_tuple(mpl, tuple); } break; case A_ELEMSET: /* elemental set */ { ELEMSET *set; MEMBER *memb; set = eval_elemset(mpl, code); if (set->head == 0) write_text(mpl, "set is empty\n"); for (memb = set->head; memb != NULL; memb = memb->next) write_text(mpl, " %s\n", format_tuple(mpl, '(', memb->tuple)); delete_elemset(mpl, set); } break; case A_FORMULA: /* linear form */ { FORMULA *form, *term; form = eval_formula(mpl, code); if (form == NULL) write_text(mpl, "linear form is empty\n"); for (term = form; term != NULL; term = term->next) { if (term->var == NULL) write_text(mpl, " %.*g\n", term->coef); else write_text(mpl, " %.*g %s%s\n", DBL_DIG, term->coef, term->var->var->name, format_tuple(mpl, '[', term->var->memb->tuple)); } delete_formula(mpl, form); } break; default: xassert(code != code); } return; } static int display_func(MPL *mpl, void *info) { /* this is auxiliary routine to work within domain scope */ DISPLAY *dpy = (DISPLAY *)info; DISPLAY1 *entry; for (entry = dpy->list; entry != NULL; entry = entry->next) { if (entry->type == A_INDEX) { /* dummy index */ DOMAIN_SLOT *slot = entry->u.slot; write_text(mpl, "%s = %s\n", slot->name, format_symbol(mpl, slot->value)); } else if (entry->type == A_SET) { /* model set */ SET *set = entry->u.set; MEMBER *memb; if (set->assign != NULL) { /* the set has assignment expression; evaluate all its members over entire domain */ eval_whole_set(mpl, set); } else { /* the set has no assignment expression; refer to its any existing member ignoring resultant value to check the data provided the data section */ #if 1 /* 12/XII-2008 */ if (set->gadget != NULL && set->data == 0) { /* initialize the set with data from a plain set */ saturate_set(mpl, set); } #endif if (set->array->head != NULL) eval_member_set(mpl, set, set->array->head->tuple); } /* display all members of the set array */ if (set->array->head == NULL) write_text(mpl, "%s has empty content\n", set->name); for (memb = set->array->head; memb != NULL; memb = memb->next) display_set(mpl, set, memb); } else if (entry->type == A_PARAMETER) { /* model parameter */ PARAMETER *par = entry->u.par; MEMBER *memb; if (par->assign != NULL) { /* the parameter has an assignment expression; evaluate all its member over entire domain */ eval_whole_par(mpl, par); } else { /* the parameter has no assignment expression; refer to its any existing member ignoring resultant value to check the data provided in the data section */ if (par->array->head != NULL) { if (par->type != A_SYMBOLIC) eval_member_num(mpl, par, par->array->head->tuple); else delete_symbol(mpl, eval_member_sym(mpl, par, par->array->head->tuple)); } } /* display all members of the parameter array */ if (par->array->head == NULL) write_text(mpl, "%s has empty content\n", par->name); for (memb = par->array->head; memb != NULL; memb = memb->next) display_par(mpl, par, memb); } else if (entry->type == A_VARIABLE) { /* model variable */ VARIABLE *var = entry->u.var; MEMBER *memb; xassert(mpl->flag_p); /* display all members of the variable array */ if (var->array->head == NULL) write_text(mpl, "%s has empty content\n", var->name); for (memb = var->array->head; memb != NULL; memb = memb->next) display_var(mpl, var, memb, DOT_NONE); } else if (entry->type == A_CONSTRAINT) { /* model constraint */ CONSTRAINT *con = entry->u.con; MEMBER *memb; xassert(mpl->flag_p); /* display all members of the constraint array */ if (con->array->head == NULL) write_text(mpl, "%s has empty content\n", con->name); for (memb = con->array->head; memb != NULL; memb = memb->next) display_con(mpl, con, memb, DOT_NONE); } else if (entry->type == A_EXPRESSION) { /* expression */ CODE *code = entry->u.code; if (code->op == O_MEMNUM || code->op == O_MEMSYM || code->op == O_MEMSET || code->op == O_MEMVAR || code->op == O_MEMCON) display_memb(mpl, code); else display_code(mpl, code); } else xassert(entry != entry); } return 0; } void execute_display(MPL *mpl, DISPLAY *dpy) { loop_within_domain(mpl, dpy->domain, dpy, display_func); return; } /*---------------------------------------------------------------------- -- clean_display - clean display statement. -- -- This routine cleans specified display statement that assumes deleting -- all stuff dynamically allocated on generating/postsolving phase. */ void clean_display(MPL *mpl, DISPLAY *dpy) { DISPLAY1 *d; #if 0 /* 15/V-2010 */ ARG_LIST *e; #endif /* clean subscript domain */ clean_domain(mpl, dpy->domain); /* clean display list */ for (d = dpy->list; d != NULL; d = d->next) { /* clean pseudo-code for computing expression */ if (d->type == A_EXPRESSION) clean_code(mpl, d->u.code); #if 0 /* 15/V-2010 */ /* clean pseudo-code for computing subscripts */ for (e = d->list; e != NULL; e = e->next) clean_code(mpl, e->x); #endif } return; } /*---------------------------------------------------------------------- -- execute_printf - execute printf statement. -- -- This routine executes specified printf statement. */ #if 1 /* 14/VII-2006 */ static void print_char(MPL *mpl, int c) { if (mpl->prt_fp == NULL) write_char(mpl, c); else xfputc(c, mpl->prt_fp); return; } static void print_text(MPL *mpl, char *fmt, ...) { va_list arg; char buf[OUTBUF_SIZE], *c; va_start(arg, fmt); vsprintf(buf, fmt, arg); xassert(strlen(buf) < sizeof(buf)); va_end(arg); for (c = buf; *c != '\0'; c++) print_char(mpl, *c); return; } #endif static int printf_func(MPL *mpl, void *info) { /* this is auxiliary routine to work within domain scope */ PRINTF *prt = (PRINTF *)info; PRINTF1 *entry; SYMBOL *sym; char fmt[MAX_LENGTH+1], *c, *from, save; /* evaluate format control string */ sym = eval_symbolic(mpl, prt->fmt); if (sym->str == NULL) sprintf(fmt, "%.*g", DBL_DIG, sym->num); else fetch_string(mpl, sym->str, fmt); delete_symbol(mpl, sym); /* scan format control string and perform formatting output */ entry = prt->list; for (c = fmt; *c != '\0'; c++) { if (*c == '%') { /* scan format specifier */ from = c++; if (*c == '%') { print_char(mpl, '%'); continue; } if (entry == NULL) break; /* scan optional flags */ while (*c == '-' || *c == '+' || *c == ' ' || *c == '#' || *c == '0') c++; /* scan optional minimum field width */ while (isdigit((unsigned char)*c)) c++; /* scan optional precision */ if (*c == '.') { c++; while (isdigit((unsigned char)*c)) c++; } /* scan conversion specifier and perform formatting */ save = *(c+1), *(c+1) = '\0'; if (*c == 'd' || *c == 'i' || *c == 'e' || *c == 'E' || *c == 'f' || *c == 'F' || *c == 'g' || *c == 'G') { /* the specifier requires numeric value */ double value; xassert(entry != NULL); switch (entry->code->type) { case A_NUMERIC: value = eval_numeric(mpl, entry->code); break; case A_SYMBOLIC: sym = eval_symbolic(mpl, entry->code); if (sym->str != NULL) mpl_error(mpl, "cannot convert %s to floating-point" " number", format_symbol(mpl, sym)); value = sym->num; delete_symbol(mpl, sym); break; case A_LOGICAL: if (eval_logical(mpl, entry->code)) value = 1.0; else value = 0.0; break; default: xassert(entry != entry); } if (*c == 'd' || *c == 'i') { double int_max = (double)INT_MAX; if (!(-int_max <= value && value <= +int_max)) mpl_error(mpl, "cannot convert %.*g to integer", DBL_DIG, value); print_text(mpl, from, (int)floor(value + 0.5)); } else print_text(mpl, from, value); } else if (*c == 's') { /* the specifier requires symbolic value */ char value[MAX_LENGTH+1]; switch (entry->code->type) { case A_NUMERIC: sprintf(value, "%.*g", DBL_DIG, eval_numeric(mpl, entry->code)); break; case A_LOGICAL: if (eval_logical(mpl, entry->code)) strcpy(value, "T"); else strcpy(value, "F"); break; case A_SYMBOLIC: sym = eval_symbolic(mpl, entry->code); if (sym->str == NULL) sprintf(value, "%.*g", DBL_DIG, sym->num); else fetch_string(mpl, sym->str, value); delete_symbol(mpl, sym); break; default: xassert(entry != entry); } print_text(mpl, from, value); } else mpl_error(mpl, "format specifier missing or invalid"); *(c+1) = save; entry = entry->next; } else if (*c == '\\') { /* write some control character */ c++; if (*c == 't') print_char(mpl, '\t'); else if (*c == 'n') print_char(mpl, '\n'); else print_char(mpl, *c); } else { /* write character without formatting */ print_char(mpl, *c); } } return 0; } #if 0 /* 14/VII-2006 */ void execute_printf(MPL *mpl, PRINTF *prt) { loop_within_domain(mpl, prt->domain, prt, printf_func); return; } #else void execute_printf(MPL *mpl, PRINTF *prt) { if (prt->fname == NULL) { /* switch to the standard output */ if (mpl->prt_fp != NULL) { xfclose(mpl->prt_fp), mpl->prt_fp = NULL; xfree(mpl->prt_file), mpl->prt_file = NULL; } } else { /* evaluate file name string */ SYMBOL *sym; char fname[MAX_LENGTH+1]; sym = eval_symbolic(mpl, prt->fname); if (sym->str == NULL) sprintf(fname, "%.*g", DBL_DIG, sym->num); else fetch_string(mpl, sym->str, fname); delete_symbol(mpl, sym); /* close the current print file, if necessary */ if (mpl->prt_fp != NULL && (!prt->app || strcmp(mpl->prt_file, fname) != 0)) { xfclose(mpl->prt_fp), mpl->prt_fp = NULL; xfree(mpl->prt_file), mpl->prt_file = NULL; } /* open the specified print file, if necessary */ if (mpl->prt_fp == NULL) { mpl->prt_fp = xfopen(fname, prt->app ? "a" : "w"); if (mpl->prt_fp == NULL) mpl_error(mpl, "unable to open `%s' for writing - %s", fname, xerrmsg()); mpl->prt_file = xmalloc(strlen(fname)+1); strcpy(mpl->prt_file, fname); } } loop_within_domain(mpl, prt->domain, prt, printf_func); if (mpl->prt_fp != NULL) { xfflush(mpl->prt_fp); if (xferror(mpl->prt_fp)) mpl_error(mpl, "writing error to `%s' - %s", mpl->prt_file, xerrmsg()); } return; } #endif /*---------------------------------------------------------------------- -- clean_printf - clean printf statement. -- -- This routine cleans specified printf statement that assumes deleting -- all stuff dynamically allocated on generating/postsolving phase. */ void clean_printf(MPL *mpl, PRINTF *prt) { PRINTF1 *p; /* clean subscript domain */ clean_domain(mpl, prt->domain); /* clean pseudo-code for computing format string */ clean_code(mpl, prt->fmt); /* clean printf list */ for (p = prt->list; p != NULL; p = p->next) { /* clean pseudo-code for computing value to be printed */ clean_code(mpl, p->code); } #if 1 /* 14/VII-2006 */ /* clean pseudo-code for computing file name string */ clean_code(mpl, prt->fname); #endif return; } /*---------------------------------------------------------------------- -- execute_for - execute for statement. -- -- This routine executes specified for statement. */ static int for_func(MPL *mpl, void *info) { /* this is auxiliary routine to work within domain scope */ FOR *fur = (FOR *)info; STATEMENT *stmt, *save; save = mpl->stmt; for (stmt = fur->list; stmt != NULL; stmt = stmt->next) execute_statement(mpl, stmt); mpl->stmt = save; return 0; } void execute_for(MPL *mpl, FOR *fur) { loop_within_domain(mpl, fur->domain, fur, for_func); return; } /*---------------------------------------------------------------------- -- clean_for - clean for statement. -- -- This routine cleans specified for statement that assumes deleting all -- stuff dynamically allocated on generating/postsolving phase. */ void clean_for(MPL *mpl, FOR *fur) { STATEMENT *stmt; /* clean subscript domain */ clean_domain(mpl, fur->domain); /* clean all sub-statements */ for (stmt = fur->list; stmt != NULL; stmt = stmt->next) clean_statement(mpl, stmt); return; } /*---------------------------------------------------------------------- -- execute_statement - execute specified model statement. -- -- This routine executes specified model statement. */ void execute_statement(MPL *mpl, STATEMENT *stmt) { mpl->stmt = stmt; switch (stmt->type) { case A_SET: case A_PARAMETER: case A_VARIABLE: break; case A_CONSTRAINT: xprintf("Generating %s...\n", stmt->u.con->name); eval_whole_con(mpl, stmt->u.con); break; case A_TABLE: switch (stmt->u.tab->type) { case A_INPUT: xprintf("Reading %s...\n", stmt->u.tab->name); break; case A_OUTPUT: xprintf("Writing %s...\n", stmt->u.tab->name); break; default: xassert(stmt != stmt); } execute_table(mpl, stmt->u.tab); break; case A_SOLVE: break; case A_CHECK: xprintf("Checking (line %d)...\n", stmt->line); execute_check(mpl, stmt->u.chk); break; case A_DISPLAY: write_text(mpl, "Display statement at line %d\n", stmt->line); execute_display(mpl, stmt->u.dpy); break; case A_PRINTF: execute_printf(mpl, stmt->u.prt); break; case A_FOR: execute_for(mpl, stmt->u.fur); break; default: xassert(stmt != stmt); } return; } /*---------------------------------------------------------------------- -- clean_statement - clean specified model statement. -- -- This routine cleans specified model statement that assumes deleting -- all stuff dynamically allocated on generating/postsolving phase. */ void clean_statement(MPL *mpl, STATEMENT *stmt) { switch(stmt->type) { case A_SET: clean_set(mpl, stmt->u.set); break; case A_PARAMETER: clean_parameter(mpl, stmt->u.par); break; case A_VARIABLE: clean_variable(mpl, stmt->u.var); break; case A_CONSTRAINT: clean_constraint(mpl, stmt->u.con); break; #if 1 /* 11/II-2008 */ case A_TABLE: clean_table(mpl, stmt->u.tab); break; #endif case A_SOLVE: break; case A_CHECK: clean_check(mpl, stmt->u.chk); break; case A_DISPLAY: clean_display(mpl, stmt->u.dpy); break; case A_PRINTF: clean_printf(mpl, stmt->u.prt); break; case A_FOR: clean_for(mpl, stmt->u.fur); break; default: xassert(stmt != stmt); } return; } /* eof */ sources_5316/external/glpk/glpios10.c0000644000176700017670000002745511401660400016311 0ustar paulpaul/* glpios10.c (feasibility pump heuristic) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" #include "glprng.h" /*********************************************************************** * NAME * * ios_feas_pump - feasibility pump heuristic * * SYNOPSIS * * #include "glpios.h" * void ios_feas_pump(glp_tree *T); * * DESCRIPTION * * The routine ios_feas_pump is a simple implementation of the Feasi- * bility Pump heuristic. * * REFERENCES * * M.Fischetti, F.Glover, and A.Lodi. "The feasibility pump." Math. * Program., Ser. A 104, pp. 91-104 (2005). */ struct VAR { /* binary variable */ int j; /* ordinal number */ int x; /* value in the rounded solution (0 or 1) */ double d; /* sorting key */ }; static int fcmp(const void *x, const void *y) { /* comparison routine */ const struct VAR *vx = x, *vy = y; if (vx->d > vy->d) return -1; else if (vx->d < vy->d) return +1; else return 0; } void ios_feas_pump(glp_tree *T) { glp_prob *P = T->mip; int n = P->n; glp_prob *lp = NULL; struct VAR *var = NULL; RNG *rand = NULL; GLPCOL *col; glp_smcp parm; int j, k, new_x, nfail, npass, nv, ret, stalling; double dist, tol; xassert(glp_get_status(P) == GLP_OPT); /* this heuristic is applied only once on the root level */ if (!(T->curr->level == 0 && T->curr->solved == 1)) goto done; /* determine number of binary variables */ nv = 0; for (j = 1; j <= n; j++) { col = P->col[j]; /* if x[j] is continuous, skip it */ if (col->kind == GLP_CV) continue; /* if x[j] is fixed, skip it */ if (col->type == GLP_FX) continue; /* x[j] is non-fixed integer */ xassert(col->kind == GLP_IV); if (col->type == GLP_DB && col->lb == 0.0 && col->ub == 1.0) { /* x[j] is binary */ nv++; } else { /* x[j] is general integer */ if (T->parm->msg_lev >= GLP_MSG_ALL) xprintf("FPUMP heuristic cannot be applied due to genera" "l integer variables\n"); goto done; } } /* there must be at least one binary variable */ if (nv == 0) goto done; if (T->parm->msg_lev >= GLP_MSG_ALL) xprintf("Applying FPUMP heuristic...\n"); /* build the list of binary variables */ var = xcalloc(1+nv, sizeof(struct VAR)); k = 0; for (j = 1; j <= n; j++) { col = P->col[j]; if (col->kind == GLP_IV && col->type == GLP_DB) var[++k].j = j; } xassert(k == nv); /* create working problem object */ lp = glp_create_prob(); more: /* copy the original problem object to keep it intact */ glp_copy_prob(lp, P, GLP_OFF); /* we are interested to find an integer feasible solution, which is better than the best known one */ if (P->mip_stat == GLP_FEAS) { int *ind; double *val, bnd; /* add a row and make it identical to the objective row */ glp_add_rows(lp, 1); ind = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(double)); for (j = 1; j <= n; j++) { ind[j] = j; val[j] = P->col[j]->coef; } glp_set_mat_row(lp, lp->m, n, ind, val); xfree(ind); xfree(val); /* introduce upper (minimization) or lower (maximization) bound to the original objective function; note that this additional constraint is not violated at the optimal point to LP relaxation */ #if 0 /* modified by xypron */ if (P->dir == GLP_MIN) { bnd = P->mip_obj - 0.10 * (1.0 + fabs(P->mip_obj)); if (bnd < P->obj_val) bnd = P->obj_val; glp_set_row_bnds(lp, lp->m, GLP_UP, 0.0, bnd - P->c0); } else if (P->dir == GLP_MAX) { bnd = P->mip_obj + 0.10 * (1.0 + fabs(P->mip_obj)); if (bnd > P->obj_val) bnd = P->obj_val; glp_set_row_bnds(lp, lp->m, GLP_LO, bnd - P->c0, 0.0); } else xassert(P != P); #else bnd = 0.1 * P->obj_val + 0.9 * P->mip_obj; /* xprintf("bnd = %f\n", bnd); */ if (P->dir == GLP_MIN) glp_set_row_bnds(lp, lp->m, GLP_UP, 0.0, bnd - P->c0); else if (P->dir == GLP_MAX) glp_set_row_bnds(lp, lp->m, GLP_LO, bnd - P->c0, 0.0); else xassert(P != P); #endif } /* reset pass count */ npass = 0; /* invalidate the rounded point */ for (k = 1; k <= nv; k++) var[k].x = -1; pass: /* next pass starts here */ npass++; if (T->parm->msg_lev >= GLP_MSG_ALL) xprintf("Pass %d\n", npass); /* initialize minimal distance between the basic point and the rounded one obtained during this pass */ dist = DBL_MAX; /* reset failure count (the number of succeeded iterations failed to improve the distance) */ nfail = 0; /* if it is not the first pass, perturb the last rounded point rather than construct it from the basic solution */ if (npass > 1) { double rho, temp; if (rand == NULL) rand = rng_create_rand(); for (k = 1; k <= nv; k++) { j = var[k].j; col = lp->col[j]; rho = rng_uniform(rand, -0.3, 0.7); if (rho < 0.0) rho = 0.0; temp = fabs((double)var[k].x - col->prim); if (temp + rho > 0.5) var[k].x = 1 - var[k].x; } goto skip; } loop: /* innermost loop begins here */ /* round basic solution (which is assumed primal feasible) */ stalling = 1; for (k = 1; k <= nv; k++) { col = lp->col[var[k].j]; if (col->prim < 0.5) { /* rounded value is 0 */ new_x = 0; } else { /* rounded value is 1 */ new_x = 1; } if (var[k].x != new_x) { stalling = 0; var[k].x = new_x; } } /* if the rounded point has not changed (stalling), choose and flip some its entries heuristically */ if (stalling) { /* compute d[j] = |x[j] - round(x[j])| */ for (k = 1; k <= nv; k++) { col = lp->col[var[k].j]; var[k].d = fabs(col->prim - (double)var[k].x); } /* sort the list of binary variables by descending d[j] */ qsort(&var[1], nv, sizeof(struct VAR), fcmp); /* choose and flip some rounded components */ for (k = 1; k <= nv; k++) { if (k >= 5 && var[k].d < 0.35 || k >= 10) break; var[k].x = 1 - var[k].x; } } skip: /* check if the time limit has been exhausted */ if (T->parm->tm_lim < INT_MAX && (double)(T->parm->tm_lim - 1) <= 1000.0 * xdifftime(xtime(), T->tm_beg)) goto done; /* build the objective, which is the distance between the current (basic) point and the rounded one */ lp->dir = GLP_MIN; lp->c0 = 0.0; for (j = 1; j <= n; j++) lp->col[j]->coef = 0.0; for (k = 1; k <= nv; k++) { j = var[k].j; if (var[k].x == 0) lp->col[j]->coef = +1.0; else { lp->col[j]->coef = -1.0; lp->c0 += 1.0; } } /* minimize the distance with the simplex method */ glp_init_smcp(&parm); if (T->parm->msg_lev <= GLP_MSG_ERR) parm.msg_lev = T->parm->msg_lev; else if (T->parm->msg_lev <= GLP_MSG_ALL) { parm.msg_lev = GLP_MSG_ON; parm.out_dly = 10000; } ret = glp_simplex(lp, &parm); if (ret != 0) { if (T->parm->msg_lev >= GLP_MSG_ERR) xprintf("Warning: glp_simplex returned %d\n", ret); goto done; } ret = glp_get_status(lp); if (ret != GLP_OPT) { if (T->parm->msg_lev >= GLP_MSG_ERR) xprintf("Warning: glp_get_status returned %d\n", ret); goto done; } if (T->parm->msg_lev >= GLP_MSG_DBG) xprintf("delta = %g\n", lp->obj_val); /* check if the basic solution is integer feasible; note that it may be so even if the minimial distance is positive */ tol = 0.3 * T->parm->tol_int; for (k = 1; k <= nv; k++) { col = lp->col[var[k].j]; if (tol < col->prim && col->prim < 1.0 - tol) break; } if (k > nv) { /* okay; the basic solution seems to be integer feasible */ double *x = xcalloc(1+n, sizeof(double)); for (j = 1; j <= n; j++) { x[j] = lp->col[j]->prim; if (P->col[j]->kind == GLP_IV) x[j] = floor(x[j] + 0.5); } #if 1 /* modified by xypron */ /* reset direction and right-hand side of objective */ lp->c0 = P->c0; lp->dir = P->dir; /* fix integer variables */ for (k = 1; k <= nv; k++) { lp->col[var[k].j]->lb = x[var[k].j]; lp->col[var[k].j]->ub = x[var[k].j]; lp->col[var[k].j]->type = GLP_FX; } /* copy original objective function */ for (j = 1; j <= n; j++) lp->col[j]->coef = P->col[j]->coef; /* solve original LP and copy result */ ret = glp_simplex(lp, &parm); if (ret != 0) { if (T->parm->msg_lev >= GLP_MSG_ERR) xprintf("Warning: glp_simplex returned %d\n", ret); goto done; } ret = glp_get_status(lp); if (ret != GLP_OPT) { if (T->parm->msg_lev >= GLP_MSG_ERR) xprintf("Warning: glp_get_status returned %d\n", ret); goto done; } for (j = 1; j <= n; j++) if (P->col[j]->kind != GLP_IV) x[j] = lp->col[j]->prim; #endif ret = glp_ios_heur_sol(T, x); xfree(x); if (ret == 0) { /* the integer solution is accepted */ if (ios_is_hopeful(T, T->curr->bound)) { /* it is reasonable to apply the heuristic once again */ goto more; } else { /* the best known integer feasible solution just found is close to optimal solution to LP relaxation */ goto done; } } } /* the basic solution is fractional */ if (dist == DBL_MAX || lp->obj_val <= dist - 1e-6 * (1.0 + dist)) { /* the distance is reducing */ nfail = 0, dist = lp->obj_val; } else { /* improving the distance failed */ nfail++; } if (nfail < 3) goto loop; if (npass < 5) goto pass; done: /* delete working objects */ if (lp != NULL) glp_delete_prob(lp); if (var != NULL) xfree(var); if (rand != NULL) rng_delete_rand(rand); return; } /* eof */ sources_5316/external/glpk/glpenv07.c0000644000176700017670000003702511401660400016307 0ustar paulpaul/* glpenv07.c (stream input/output) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifdef HAVE_CONFIG_H #include #endif #include "glpenv.h" /*********************************************************************** * NAME * * lib_err_msg - save error message string * * SYNOPSIS * * #include "glpenv.h" * void lib_err_msg(const char *msg); * * DESCRIPTION * * The routine lib_err_msg saves an error message string specified by * the parameter msg. The message is obtained by some library routines * with a call to strerror(errno). */ void lib_err_msg(const char *msg) { ENV *env = get_env_ptr(); int len = strlen(msg); if (len >= IOERR_MSG_SIZE) len = IOERR_MSG_SIZE - 1; memcpy(env->ioerr_msg, msg, len); if (len > 0 && env->ioerr_msg[len-1] == '\n') len--; env->ioerr_msg[len] = '\0'; return; } /*********************************************************************** * NAME * * xerrmsg - retrieve error message string * * SYNOPSIS * * #include "glpenv.h" * const char *xerrmsg(void); * * RETURNS * * The routine xerrmsg returns a pointer to an error message string * previously set by some library routine to indicate an error. */ const char *xerrmsg(void) { ENV *env = get_env_ptr(); return env->ioerr_msg; } /*********************************************************************** * NAME * * xfopen - open a stream * * SYNOPSIS * * #include "glpenv.h" * XFILE *xfopen(const char *fname, const char *mode); * * DESCRIPTION * * The routine xfopen opens the file whose name is a string pointed to * by fname and associates a stream with it. * * The parameter mode points to a string, which indicates the open mode * and should be one of the following: * * "r" open text file for reading; * "w" truncate to zero length or create text file for writing; * "rb" open binary file for reading; * "wb" truncate to zero length or create binary file for writing. * * RETURNS * * The routine xfopen returns a pointer to the object controlling the * stream. If the open operation fails, xfopen returns NULL. */ static void *c_fopen(const char *fname, const char *mode); static void *z_fopen(const char *fname, const char *mode); static int is_gz_file(const char *fname) { char *ext = strrchr(fname, '.'); return ext != NULL && strcmp(ext, ".gz") == 0; } XFILE *xfopen(const char *fname, const char *mode) { ENV *env = get_env_ptr(); XFILE *fp; int type; void *fh; if (!is_gz_file(fname)) { type = FH_FILE; fh = c_fopen(fname, mode); } else { type = FH_ZLIB; fh = z_fopen(fname, mode); } if (fh == NULL) { fp = NULL; goto done; } fp = xmalloc(sizeof(XFILE)); fp->type = type; fp->fh = fh; fp->prev = NULL; fp->next = env->file_ptr; if (fp->next != NULL) fp->next->prev = fp; env->file_ptr = fp; done: return fp; } /*********************************************************************** * NAME * * xfgetc - read character from the stream * * SYNOPSIS * * #include "glpenv.h" * int xfgetc(XFILE *fp); * * DESCRIPTION * * If the end-of-file indicator for the input stream pointed to by fp * is not set and a next character is present, the routine xfgetc * obtains that character as an unsigned char converted to an int and * advances the associated file position indicator for the stream (if * defined). * * RETURNS * * If the end-of-file indicator for the stream is set, or if the * stream is at end-of-file, the end-of-file indicator for the stream * is set and the routine xfgetc returns XEOF. Otherwise, the routine * xfgetc returns the next character from the input stream pointed to * by fp. If a read error occurs, the error indicator for the stream is * set and the xfgetc routine returns XEOF. * * Note: An end-of-file and a read error can be distinguished by use of * the routines xfeof and xferror. */ static int c_fgetc(void *fh); static int z_fgetc(void *fh); int xfgetc(XFILE *fp) { int c; switch (fp->type) { case FH_FILE: c = c_fgetc(fp->fh); break; case FH_ZLIB: c = z_fgetc(fp->fh); break; default: xassert(fp != fp); } return c; } /*********************************************************************** * NAME * * xfputc - write character to the stream * * SYNOPSIS * * #include "glpenv.h" * int xfputc(int c, XFILE *fp); * * DESCRIPTION * * The routine xfputc writes the character specified by c (converted * to an unsigned char) to the output stream pointed to by fp, at the * position indicated by the associated file position indicator (if * defined), and advances the indicator appropriately. * * RETURNS * * The routine xfputc returns the character written. If a write error * occurs, the error indicator for the stream is set and xfputc returns * XEOF. */ static int c_fputc(int c, void *fh); static int z_fputc(int c, void *fh); int xfputc(int c, XFILE *fp) { switch (fp->type) { case FH_FILE: c = c_fputc(c, fp->fh); break; case FH_ZLIB: c = z_fputc(c, fp->fh); break; default: xassert(fp != fp); } return c; } /*********************************************************************** * NAME * * xferror - test error indicator for the stream * * SYNOPSIS * * #include "glpenv.h" * int xferror(XFILE *fp); * * DESCRIPTION * * The routine xferror tests the error indicator for the stream * pointed to by fp. * * RETURNS * * The routine xferror returns non-zero if and only if the error * indicator is set for the stream. */ static int c_ferror(void *fh); static int z_ferror(void *fh); int xferror(XFILE *fp) { int ret; switch (fp->type) { case FH_FILE: ret = c_ferror(fp->fh); break; case FH_ZLIB: ret = z_ferror(fp->fh); break; default: xassert(fp != fp); } return ret; } /*********************************************************************** * NAME * * xfeof - test end-of-file indicator for the stream * * SYNOPSIS * * #include "glpenv.h" * int xfeof(XFILE *fp); * * DESCRIPTION * * The routine xfeof tests the end-of-file indicator for the stream * pointed to by fp. * * RETURNS * * The routine xfeof returns non-zero if and only if the end-of-file * indicator is set for the stream. */ static int c_feof(void *fh); static int z_feof(void *fh); int xfeof(XFILE *fp) { int ret; switch (fp->type) { case FH_FILE: ret = c_feof(fp->fh); break; case FH_ZLIB: ret = z_feof(fp->fh); break; default: xassert(fp != fp); } return ret; } int xfprintf(XFILE *file, const char *fmt, ...) { ENV *env = get_env_ptr(); int cnt, j; va_list arg; va_start(arg, fmt); cnt = vsprintf(env->term_buf, fmt, arg); va_end(arg); for (j = 0; j < cnt; j++) { if (xfputc(env->term_buf[j], file) < 0) { cnt = -1; break; } } return cnt; } /*********************************************************************** * NAME * * xfflush - flush the stream * * SYNOPSIS * * #include "glpenv.h" * int xfflush(XFILE *fp); * * DESCRIPTION * * The routine xfflush causes any unwritten data for the output stream * pointed to by fp to be written to the associated file. * * RETURNS * * The routine xfflush returns zero if the stream was successfully * flushed. Otherwise, xfflush sets the error indicator for the stream * and returns XEOF. */ static int c_fflush(void *fh); static int z_fflush(void *fh); int xfflush(XFILE *fp) { int ret; switch (fp->type) { case FH_FILE: ret = c_fflush(fp->fh); break; case FH_ZLIB: ret = z_fflush(fp->fh); break; default: xassert(fp != fp); } return ret; } /*********************************************************************** * NAME * * xfclose - close the stream * * SYNOPSIS * * #include "glpenv.h" * int xfclose(XFILE *fp); * * DESCRIPTION * * A successful call to the routine xfclose causes the stream pointed * to by fp to be flushed and the associated file to be closed. Whether * or not the call succeeds, the stream is disassociated from the file. * * RETURNS * * The routine xfclose returns zero if the stream was successfully * closed, or XEOF if any errors were detected. */ static int c_fclose(void *fh); static int z_fclose(void *fh); int xfclose(XFILE *fp) { ENV *env = get_env_ptr(); int ret; switch (fp->type) { case FH_FILE: ret = c_fclose(fp->fh); break; case FH_ZLIB: ret = z_fclose(fp->fh); break; default: xassert(fp != fp); } fp->type = 0xF00BAD; if (fp->prev == NULL) env->file_ptr = fp->next; else fp->prev->next = fp->next; if (fp->next == NULL) ; else fp->next->prev = fp->prev; xfree(fp); return ret; } /*********************************************************************** * The following routines implement stream input/output based on the * standard C streams. */ static void *c_fopen(const char *fname, const char *mode) { FILE *fh; if (strcmp(fname, "/dev/stdin") == 0) fh = stdin; else if (strcmp(fname, "/dev/stdout") == 0) fh = stdout; else if (strcmp(fname, "/dev/stderr") == 0) fh = stderr; else fh = fopen(fname, mode); if (fh == NULL) lib_err_msg(strerror(errno)); return fh; } static int c_fgetc(void *_fh) { FILE *fh = _fh; int c; if (ferror(fh) || feof(fh)) { c = XEOF; goto done; } c = fgetc(fh); if (ferror(fh)) { lib_err_msg(strerror(errno)); c = XEOF; } else if (feof(fh)) c = XEOF; else xassert(0x00 <= c && c <= 0xFF); done: return c; } static int c_fputc(int c, void *_fh) { FILE *fh = _fh; if (ferror(fh)) { c = XEOF; goto done; } c = (unsigned char)c; fputc(c, fh); if (ferror(fh)) { lib_err_msg(strerror(errno)); c = XEOF; } done: return c; } static int c_ferror(void *_fh) { FILE *fh = _fh; return ferror(fh); } static int c_feof(void *_fh) { FILE *fh = _fh; return feof(fh); } static int c_fflush(void *_fh) { FILE *fh = _fh; int ret; ret = fflush(fh); if (ret != 0) { lib_err_msg(strerror(errno)); ret = XEOF; } return ret; } static int c_fclose(void *_fh) { FILE *fh = _fh; int ret; if (fh == stdin) ret = 0; else if (fh == stdout || fh == stderr) fflush(fh), ret = 0; else ret = fclose(fh); if (ret != 0) { lib_err_msg(strerror(errno)); ret = XEOF; } return ret; } /*********************************************************************** * The following routines implement stream input/output based on the * zlib library, which provides processing .gz files "on the fly". */ #ifndef HAVE_ZLIB static void *z_fopen(const char *fname, const char *mode) { xassert(fname == fname); xassert(mode == mode); lib_err_msg("Compressed files not supported"); return NULL; } static int z_fgetc(void *fh) { xassert(fh != fh); return 0; } static int z_fputc(int c, void *fh) { xassert(c != c); xassert(fh != fh); return 0; } static int z_ferror(void *fh) { xassert(fh != fh); return 0; } static int z_feof(void *fh) { xassert(fh != fh); return 0; } static int z_fflush(void *fh) { xassert(fh != fh); return 0; } static int z_fclose(void *fh) { xassert(fh != fh); return 0; } #else #include struct z_file { /* .gz file handle */ gzFile file; /* pointer to .gz stream */ int err; /* i/o error indicator */ int eof; /* end-of-file indicator */ }; static void *z_fopen(const char *fname, const char *mode) { struct z_file *fh; gzFile file; if (strcmp(mode, "r") == 0 || strcmp(mode, "rb") == 0) mode = "rb"; else if (strcmp(mode, "w") == 0 || strcmp(mode, "wb") == 0) mode = "wb"; else { lib_err_msg("Invalid open mode"); fh = NULL; goto done; } file = gzopen(fname, mode); if (file == NULL) { lib_err_msg(strerror(errno)); fh = NULL; goto done; } fh = xmalloc(sizeof(struct z_file)); fh->file = file; fh->err = fh->eof = 0; done: return fh; } static int z_fgetc(void *_fh) { struct z_file *fh = _fh; int c; if (fh->err || fh->eof) { c = XEOF; goto done; } c = gzgetc(fh->file); if (c < 0) { int errnum; const char *msg; msg = gzerror(fh->file, &errnum); if (errnum == Z_STREAM_END) fh->eof = 1; else if (errnum == Z_ERRNO) { fh->err = 1; lib_err_msg(strerror(errno)); } else { fh->err = 1; lib_err_msg(msg); } c = XEOF; } else xassert(0x00 <= c && c <= 0xFF); done: return c; } static int z_fputc(int c, void *_fh) { struct z_file *fh = _fh; if (fh->err) { c = XEOF; goto done; } c = (unsigned char)c; if (gzputc(fh->file, c) < 0) { int errnum; const char *msg; fh->err = 1; msg = gzerror(fh->file, &errnum); if (errnum == Z_ERRNO) lib_err_msg(strerror(errno)); else lib_err_msg(msg); c = XEOF; } done: return c; } static int z_ferror(void *_fh) { struct z_file *fh = _fh; return fh->err; } static int z_feof(void *_fh) { struct z_file *fh = _fh; return fh->eof; } static int z_fflush(void *_fh) { struct z_file *fh = _fh; int ret; ret = gzflush(fh->file, Z_FINISH); if (ret == Z_OK) ret = 0; else { int errnum; const char *msg; fh->err = 1; msg = gzerror(fh->file, &errnum); if (errnum == Z_ERRNO) lib_err_msg(strerror(errno)); else lib_err_msg(msg); ret = XEOF; } return ret; } static int z_fclose(void *_fh) { struct z_file *fh = _fh; gzclose(fh->file); xfree(fh); return 0; } #endif /* eof */ sources_5316/external/glpk/glpios01.c0000644000176700017670000015012411401660400016277 0ustar paulpaul/* glpios01.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*********************************************************************** * NAME * * ios_create_tree - create branch-and-bound tree * * SYNOPSIS * * #include "glpios.h" * glp_tree *ios_create_tree(glp_prob *mip, const glp_iocp *parm); * * DESCRIPTION * * The routine ios_create_tree creates the branch-and-bound tree. * * Being created the tree consists of the only root subproblem whose * reference number is 1. Note that initially the root subproblem is in * frozen state and therefore needs to be revived. * * RETURNS * * The routine returns a pointer to the tree created. */ static IOSNPD *new_node(glp_tree *tree, IOSNPD *parent); glp_tree *ios_create_tree(glp_prob *mip, const glp_iocp *parm) { int m = mip->m; int n = mip->n; glp_tree *tree; int i, j; xassert(mip->tree == NULL); mip->tree = tree = xmalloc(sizeof(glp_tree)); tree->pool = dmp_create_pool(); tree->n = n; /* save original problem components */ tree->orig_m = m; tree->orig_type = xcalloc(1+m+n, sizeof(char)); tree->orig_lb = xcalloc(1+m+n, sizeof(double)); tree->orig_ub = xcalloc(1+m+n, sizeof(double)); tree->orig_stat = xcalloc(1+m+n, sizeof(char)); tree->orig_prim = xcalloc(1+m+n, sizeof(double)); tree->orig_dual = xcalloc(1+m+n, sizeof(double)); for (i = 1; i <= m; i++) { GLPROW *row = mip->row[i]; tree->orig_type[i] = (char)row->type; tree->orig_lb[i] = row->lb; tree->orig_ub[i] = row->ub; tree->orig_stat[i] = (char)row->stat; tree->orig_prim[i] = row->prim; tree->orig_dual[i] = row->dual; } for (j = 1; j <= n; j++) { GLPCOL *col = mip->col[j]; tree->orig_type[m+j] = (char)col->type; tree->orig_lb[m+j] = col->lb; tree->orig_ub[m+j] = col->ub; tree->orig_stat[m+j] = (char)col->stat; tree->orig_prim[m+j] = col->prim; tree->orig_dual[m+j] = col->dual; } tree->orig_obj = mip->obj_val; /* initialize the branch-and-bound tree */ tree->nslots = 0; tree->avail = 0; tree->slot = NULL; tree->head = tree->tail = NULL; tree->a_cnt = tree->n_cnt = tree->t_cnt = 0; /* the root subproblem is not solved yet, so its final components are unknown so far */ tree->root_m = 0; tree->root_type = NULL; tree->root_lb = tree->root_ub = NULL; tree->root_stat = NULL; /* the current subproblem does not exist yet */ tree->curr = NULL; tree->mip = mip; /*tree->solved = 0;*/ tree->non_int = xcalloc(1+n, sizeof(char)); memset(&tree->non_int[1], 0, n); /* arrays to save parent subproblem components will be allocated later */ tree->pred_m = tree->pred_max = 0; tree->pred_type = NULL; tree->pred_lb = tree->pred_ub = NULL; tree->pred_stat = NULL; /* cut generator */ tree->local = ios_create_pool(tree); /*tree->first_attempt = 1;*/ /*tree->max_added_cuts = 0;*/ /*tree->min_eff = 0.0;*/ /*tree->miss = 0;*/ /*tree->just_selected = 0;*/ tree->mir_gen = NULL; tree->clq_gen = NULL; /*tree->round = 0;*/ #if 0 /* create the conflict graph */ tree->n_ref = xcalloc(1+n, sizeof(int)); memset(&tree->n_ref[1], 0, n * sizeof(int)); tree->c_ref = xcalloc(1+n, sizeof(int)); memset(&tree->c_ref[1], 0, n * sizeof(int)); tree->g = scg_create_graph(0); tree->j_ref = xcalloc(1+tree->g->n_max, sizeof(int)); #endif /* pseudocost branching */ tree->pcost = NULL; tree->iwrk = xcalloc(1+n, sizeof(int)); tree->dwrk = xcalloc(1+n, sizeof(double)); /* initialize control parameters */ tree->parm = parm; tree->tm_beg = xtime(); tree->tm_lag = xlset(0); tree->sol_cnt = 0; /* initialize advanced solver interface */ tree->reason = 0; tree->reopt = 0; tree->reinv = 0; tree->br_var = 0; tree->br_sel = 0; tree->child = 0; tree->next_p = 0; /*tree->btrack = NULL;*/ tree->stop = 0; /* create the root subproblem, which initially is identical to the original MIP */ new_node(tree, NULL); return tree; } /*********************************************************************** * NAME * * ios_revive_node - revive specified subproblem * * SYNOPSIS * * #include "glpios.h" * void ios_revive_node(glp_tree *tree, int p); * * DESCRIPTION * * The routine ios_revive_node revives the specified subproblem, whose * reference number is p, and thereby makes it the current subproblem. * Note that the specified subproblem must be active. Besides, if the * current subproblem already exists, it must be frozen before reviving * another subproblem. */ void ios_revive_node(glp_tree *tree, int p) { glp_prob *mip = tree->mip; IOSNPD *node, *root; /* obtain pointer to the specified subproblem */ xassert(1 <= p && p <= tree->nslots); node = tree->slot[p].node; xassert(node != NULL); /* the specified subproblem must be active */ xassert(node->count == 0); /* the current subproblem must not exist */ xassert(tree->curr == NULL); /* the specified subproblem becomes current */ tree->curr = node; /*tree->solved = 0;*/ /* obtain pointer to the root subproblem */ root = tree->slot[1].node; xassert(root != NULL); /* at this point problem object components correspond to the root subproblem, so if the root subproblem should be revived, there is nothing more to do */ if (node == root) goto done; xassert(mip->m == tree->root_m); /* build path from the root to the current node */ node->temp = NULL; for (node = node; node != NULL; node = node->up) { if (node->up == NULL) xassert(node == root); else node->up->temp = node; } /* go down from the root to the current node and make necessary changes to restore components of the current subproblem */ for (node = root; node != NULL; node = node->temp) { int m = mip->m; int n = mip->n; /* if the current node is reached, the problem object at this point corresponds to its parent, so save attributes of rows and columns for the parent subproblem */ if (node->temp == NULL) { int i, j; tree->pred_m = m; /* allocate/reallocate arrays, if necessary */ if (tree->pred_max < m + n) { int new_size = m + n + 100; if (tree->pred_type != NULL) xfree(tree->pred_type); if (tree->pred_lb != NULL) xfree(tree->pred_lb); if (tree->pred_ub != NULL) xfree(tree->pred_ub); if (tree->pred_stat != NULL) xfree(tree->pred_stat); tree->pred_max = new_size; tree->pred_type = xcalloc(1+new_size, sizeof(char)); tree->pred_lb = xcalloc(1+new_size, sizeof(double)); tree->pred_ub = xcalloc(1+new_size, sizeof(double)); tree->pred_stat = xcalloc(1+new_size, sizeof(char)); } /* save row attributes */ for (i = 1; i <= m; i++) { GLPROW *row = mip->row[i]; tree->pred_type[i] = (char)row->type; tree->pred_lb[i] = row->lb; tree->pred_ub[i] = row->ub; tree->pred_stat[i] = (char)row->stat; } /* save column attributes */ for (j = 1; j <= n; j++) { GLPCOL *col = mip->col[j]; tree->pred_type[mip->m+j] = (char)col->type; tree->pred_lb[mip->m+j] = col->lb; tree->pred_ub[mip->m+j] = col->ub; tree->pred_stat[mip->m+j] = (char)col->stat; } } /* change bounds of rows and columns */ { IOSBND *b; for (b = node->b_ptr; b != NULL; b = b->next) { if (b->k <= m) glp_set_row_bnds(mip, b->k, b->type, b->lb, b->ub); else glp_set_col_bnds(mip, b->k-m, b->type, b->lb, b->ub); } } /* change statuses of rows and columns */ { IOSTAT *s; for (s = node->s_ptr; s != NULL; s = s->next) { if (s->k <= m) glp_set_row_stat(mip, s->k, s->stat); else glp_set_col_stat(mip, s->k-m, s->stat); } } /* add new rows */ if (node->r_ptr != NULL) { IOSROW *r; IOSAIJ *a; int i, len, *ind; double *val; ind = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(double)); for (r = node->r_ptr; r != NULL; r = r->next) { i = glp_add_rows(mip, 1); glp_set_row_name(mip, i, r->name); #if 1 /* 20/IX-2008 */ xassert(mip->row[i]->level == 0); mip->row[i]->level = node->level; mip->row[i]->origin = r->origin; mip->row[i]->klass = r->klass; #endif glp_set_row_bnds(mip, i, r->type, r->lb, r->ub); len = 0; for (a = r->ptr; a != NULL; a = a->next) len++, ind[len] = a->j, val[len] = a->val; glp_set_mat_row(mip, i, len, ind, val); glp_set_rii(mip, i, r->rii); glp_set_row_stat(mip, i, r->stat); } xfree(ind); xfree(val); } #if 0 /* add new edges to the conflict graph */ /* add new cliques to the conflict graph */ /* (not implemented yet) */ xassert(node->own_nn == 0); xassert(node->own_nc == 0); xassert(node->e_ptr == NULL); #endif } /* the specified subproblem has been revived */ node = tree->curr; /* delete its bound change list */ while (node->b_ptr != NULL) { IOSBND *b; b = node->b_ptr; node->b_ptr = b->next; dmp_free_atom(tree->pool, b, sizeof(IOSBND)); } /* delete its status change list */ while (node->s_ptr != NULL) { IOSTAT *s; s = node->s_ptr; node->s_ptr = s->next; dmp_free_atom(tree->pool, s, sizeof(IOSTAT)); } #if 1 /* 20/XI-2009 */ /* delete its row addition list (additional rows may appear, for example, due to branching on GUB constraints */ while (node->r_ptr != NULL) { IOSROW *r; r = node->r_ptr; node->r_ptr = r->next; xassert(r->name == NULL); while (r->ptr != NULL) { IOSAIJ *a; a = r->ptr; r->ptr = a->next; dmp_free_atom(tree->pool, a, sizeof(IOSAIJ)); } dmp_free_atom(tree->pool, r, sizeof(IOSROW)); } #endif done: return; } /*********************************************************************** * NAME * * ios_freeze_node - freeze current subproblem * * SYNOPSIS * * #include "glpios.h" * void ios_freeze_node(glp_tree *tree); * * DESCRIPTION * * The routine ios_freeze_node freezes the current subproblem. */ void ios_freeze_node(glp_tree *tree) { glp_prob *mip = tree->mip; int m = mip->m; int n = mip->n; IOSNPD *node; /* obtain pointer to the current subproblem */ node = tree->curr; xassert(node != NULL); if (node->up == NULL) { /* freeze the root subproblem */ int k; xassert(node->p == 1); xassert(tree->root_m == 0); xassert(tree->root_type == NULL); xassert(tree->root_lb == NULL); xassert(tree->root_ub == NULL); xassert(tree->root_stat == NULL); tree->root_m = m; tree->root_type = xcalloc(1+m+n, sizeof(char)); tree->root_lb = xcalloc(1+m+n, sizeof(double)); tree->root_ub = xcalloc(1+m+n, sizeof(double)); tree->root_stat = xcalloc(1+m+n, sizeof(char)); for (k = 1; k <= m+n; k++) { if (k <= m) { GLPROW *row = mip->row[k]; tree->root_type[k] = (char)row->type; tree->root_lb[k] = row->lb; tree->root_ub[k] = row->ub; tree->root_stat[k] = (char)row->stat; } else { GLPCOL *col = mip->col[k-m]; tree->root_type[k] = (char)col->type; tree->root_lb[k] = col->lb; tree->root_ub[k] = col->ub; tree->root_stat[k] = (char)col->stat; } } } else { /* freeze non-root subproblem */ int root_m = tree->root_m; int pred_m = tree->pred_m; int i, j, k; xassert(pred_m <= m); /* build change lists for rows and columns which exist in the parent subproblem */ xassert(node->b_ptr == NULL); xassert(node->s_ptr == NULL); for (k = 1; k <= pred_m + n; k++) { int pred_type, pred_stat, type, stat; double pred_lb, pred_ub, lb, ub; /* determine attributes in the parent subproblem */ pred_type = tree->pred_type[k]; pred_lb = tree->pred_lb[k]; pred_ub = tree->pred_ub[k]; pred_stat = tree->pred_stat[k]; /* determine attributes in the current subproblem */ if (k <= pred_m) { GLPROW *row = mip->row[k]; type = row->type; lb = row->lb; ub = row->ub; stat = row->stat; } else { GLPCOL *col = mip->col[k - pred_m]; type = col->type; lb = col->lb; ub = col->ub; stat = col->stat; } /* save type and bounds of a row/column, if changed */ if (!(pred_type == type && pred_lb == lb && pred_ub == ub)) { IOSBND *b; b = dmp_get_atom(tree->pool, sizeof(IOSBND)); b->k = k; b->type = (unsigned char)type; b->lb = lb; b->ub = ub; b->next = node->b_ptr; node->b_ptr = b; } /* save status of a row/column, if changed */ if (pred_stat != stat) { IOSTAT *s; s = dmp_get_atom(tree->pool, sizeof(IOSTAT)); s->k = k; s->stat = (unsigned char)stat; s->next = node->s_ptr; node->s_ptr = s; } } /* save new rows added to the current subproblem */ xassert(node->r_ptr == NULL); if (pred_m < m) { int i, len, *ind; double *val; ind = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(double)); for (i = m; i > pred_m; i--) { GLPROW *row = mip->row[i]; IOSROW *r; const char *name; r = dmp_get_atom(tree->pool, sizeof(IOSROW)); name = glp_get_row_name(mip, i); if (name == NULL) r->name = NULL; else { r->name = dmp_get_atom(tree->pool, strlen(name)+1); strcpy(r->name, name); } #if 1 /* 20/IX-2008 */ r->origin = row->origin; r->klass = row->klass; #endif r->type = (unsigned char)row->type; r->lb = row->lb; r->ub = row->ub; r->ptr = NULL; len = glp_get_mat_row(mip, i, ind, val); for (k = 1; k <= len; k++) { IOSAIJ *a; a = dmp_get_atom(tree->pool, sizeof(IOSAIJ)); a->j = ind[k]; a->val = val[k]; a->next = r->ptr; r->ptr = a; } r->rii = row->rii; r->stat = (unsigned char)row->stat; r->next = node->r_ptr; node->r_ptr = r; } xfree(ind); xfree(val); } /* remove all rows missing in the root subproblem */ if (m != root_m) { int nrs, *num; nrs = m - root_m; xassert(nrs > 0); num = xcalloc(1+nrs, sizeof(int)); for (i = 1; i <= nrs; i++) num[i] = root_m + i; glp_del_rows(mip, nrs, num); xfree(num); } m = mip->m; /* and restore attributes of all rows and columns for the root subproblem */ xassert(m == root_m); for (i = 1; i <= m; i++) { glp_set_row_bnds(mip, i, tree->root_type[i], tree->root_lb[i], tree->root_ub[i]); glp_set_row_stat(mip, i, tree->root_stat[i]); } for (j = 1; j <= n; j++) { glp_set_col_bnds(mip, j, tree->root_type[m+j], tree->root_lb[m+j], tree->root_ub[m+j]); glp_set_col_stat(mip, j, tree->root_stat[m+j]); } #if 1 /* remove all edges and cliques missing in the conflict graph for the root subproblem */ /* (not implemented yet) */ #endif } /* the current subproblem has been frozen */ tree->curr = NULL; return; } /*********************************************************************** * NAME * * ios_clone_node - clone specified subproblem * * SYNOPSIS * * #include "glpios.h" * void ios_clone_node(glp_tree *tree, int p, int nnn, int ref[]); * * DESCRIPTION * * The routine ios_clone_node clones the specified subproblem, whose * reference number is p, creating its nnn exact copies. Note that the * specified subproblem must be active and must be in the frozen state * (i.e. it must not be the current subproblem). * * Each clone, an exact copy of the specified subproblem, becomes a new * active subproblem added to the end of the active list. After cloning * the specified subproblem becomes inactive. * * The reference numbers of clone subproblems are stored to locations * ref[1], ..., ref[nnn]. */ static int get_slot(glp_tree *tree) { int p; /* if no free slots are available, increase the room */ if (tree->avail == 0) { int nslots = tree->nslots; IOSLOT *save = tree->slot; if (nslots == 0) tree->nslots = 20; else { tree->nslots = nslots + nslots; xassert(tree->nslots > nslots); } tree->slot = xcalloc(1+tree->nslots, sizeof(IOSLOT)); if (save != NULL) { memcpy(&tree->slot[1], &save[1], nslots * sizeof(IOSLOT)); xfree(save); } /* push more free slots into the stack */ for (p = tree->nslots; p > nslots; p--) { tree->slot[p].node = NULL; tree->slot[p].next = tree->avail; tree->avail = p; } } /* pull a free slot from the stack */ p = tree->avail; tree->avail = tree->slot[p].next; xassert(tree->slot[p].node == NULL); tree->slot[p].next = 0; return p; } static IOSNPD *new_node(glp_tree *tree, IOSNPD *parent) { IOSNPD *node; int p; /* pull a free slot for the new node */ p = get_slot(tree); /* create descriptor of the new subproblem */ node = dmp_get_atom(tree->pool, sizeof(IOSNPD)); tree->slot[p].node = node; node->p = p; node->up = parent; node->level = (parent == NULL ? 0 : parent->level + 1); node->count = 0; node->b_ptr = NULL; node->s_ptr = NULL; node->r_ptr = NULL; node->solved = 0; #if 0 node->own_nn = node->own_nc = 0; node->e_ptr = NULL; #endif #if 1 /* 04/X-2008 */ node->lp_obj = (parent == NULL ? (tree->mip->dir == GLP_MIN ? -DBL_MAX : +DBL_MAX) : parent->lp_obj); #endif node->bound = (parent == NULL ? (tree->mip->dir == GLP_MIN ? -DBL_MAX : +DBL_MAX) : parent->bound); node->br_var = 0; node->br_val = 0.0; node->ii_cnt = 0; node->ii_sum = 0.0; #if 1 /* 30/XI-2009 */ node->changed = 0; #endif if (tree->parm->cb_size == 0) node->data = NULL; else { node->data = dmp_get_atom(tree->pool, tree->parm->cb_size); memset(node->data, 0, tree->parm->cb_size); } node->temp = NULL; node->prev = tree->tail; node->next = NULL; /* add the new subproblem to the end of the active list */ if (tree->head == NULL) tree->head = node; else tree->tail->next = node; tree->tail = node; tree->a_cnt++; tree->n_cnt++; tree->t_cnt++; /* increase the number of child subproblems */ if (parent == NULL) xassert(p == 1); else parent->count++; return node; } void ios_clone_node(glp_tree *tree, int p, int nnn, int ref[]) { IOSNPD *node; int k; /* obtain pointer to the subproblem to be cloned */ xassert(1 <= p && p <= tree->nslots); node = tree->slot[p].node; xassert(node != NULL); /* the specified subproblem must be active */ xassert(node->count == 0); /* and must be in the frozen state */ xassert(tree->curr != node); /* remove the specified subproblem from the active list, because it becomes inactive */ if (node->prev == NULL) tree->head = node->next; else node->prev->next = node->next; if (node->next == NULL) tree->tail = node->prev; else node->next->prev = node->prev; node->prev = node->next = NULL; tree->a_cnt--; /* create clone subproblems */ xassert(nnn > 0); for (k = 1; k <= nnn; k++) ref[k] = new_node(tree, node)->p; return; } /*********************************************************************** * NAME * * ios_delete_node - delete specified subproblem * * SYNOPSIS * * #include "glpios.h" * void ios_delete_node(glp_tree *tree, int p); * * DESCRIPTION * * The routine ios_delete_node deletes the specified subproblem, whose * reference number is p. The subproblem must be active and must be in * the frozen state (i.e. it must not be the current subproblem). * * Note that deletion is performed recursively, i.e. if a subproblem to * be deleted is the only child of its parent, the parent subproblem is * also deleted, etc. */ void ios_delete_node(glp_tree *tree, int p) { IOSNPD *node, *temp; /* obtain pointer to the subproblem to be deleted */ xassert(1 <= p && p <= tree->nslots); node = tree->slot[p].node; xassert(node != NULL); /* the specified subproblem must be active */ xassert(node->count == 0); /* and must be in the frozen state */ xassert(tree->curr != node); /* remove the specified subproblem from the active list, because it is gone from the tree */ if (node->prev == NULL) tree->head = node->next; else node->prev->next = node->next; if (node->next == NULL) tree->tail = node->prev; else node->next->prev = node->prev; node->prev = node->next = NULL; tree->a_cnt--; loop: /* recursive deletion starts here */ /* delete the bound change list */ { IOSBND *b; while (node->b_ptr != NULL) { b = node->b_ptr; node->b_ptr = b->next; dmp_free_atom(tree->pool, b, sizeof(IOSBND)); } } /* delete the status change list */ { IOSTAT *s; while (node->s_ptr != NULL) { s = node->s_ptr; node->s_ptr = s->next; dmp_free_atom(tree->pool, s, sizeof(IOSTAT)); } } /* delete the row addition list */ while (node->r_ptr != NULL) { IOSROW *r; r = node->r_ptr; if (r->name != NULL) dmp_free_atom(tree->pool, r->name, strlen(r->name)+1); while (r->ptr != NULL) { IOSAIJ *a; a = r->ptr; r->ptr = a->next; dmp_free_atom(tree->pool, a, sizeof(IOSAIJ)); } node->r_ptr = r->next; dmp_free_atom(tree->pool, r, sizeof(IOSROW)); } #if 0 /* delete the edge addition list */ /* delete the clique addition list */ /* (not implemented yet) */ xassert(node->own_nn == 0); xassert(node->own_nc == 0); xassert(node->e_ptr == NULL); #endif /* free application-specific data */ if (tree->parm->cb_size == 0) xassert(node->data == NULL); else dmp_free_atom(tree->pool, node->data, tree->parm->cb_size); /* free the corresponding node slot */ p = node->p; xassert(tree->slot[p].node == node); tree->slot[p].node = NULL; tree->slot[p].next = tree->avail; tree->avail = p; /* save pointer to the parent subproblem */ temp = node->up; /* delete the subproblem descriptor */ dmp_free_atom(tree->pool, node, sizeof(IOSNPD)); tree->n_cnt--; /* take pointer to the parent subproblem */ node = temp; if (node != NULL) { /* the parent subproblem exists; decrease the number of its child subproblems */ xassert(node->count > 0); node->count--; /* if now the parent subproblem has no childs, it also must be deleted */ if (node->count == 0) goto loop; } return; } /*********************************************************************** * NAME * * ios_delete_tree - delete branch-and-bound tree * * SYNOPSIS * * #include "glpios.h" * void ios_delete_tree(glp_tree *tree); * * DESCRIPTION * * The routine ios_delete_tree deletes the branch-and-bound tree, which * the parameter tree points to, and frees all the memory allocated to * this program object. * * On exit components of the problem object are restored to correspond * to the original MIP passed to the routine ios_create_tree. */ void ios_delete_tree(glp_tree *tree) { glp_prob *mip = tree->mip; int i, j; int m = mip->m; int n = mip->n; xassert(mip->tree == tree); /* remove all additional rows */ if (m != tree->orig_m) { int nrs, *num; nrs = m - tree->orig_m; xassert(nrs > 0); num = xcalloc(1+nrs, sizeof(int)); for (i = 1; i <= nrs; i++) num[i] = tree->orig_m + i; glp_del_rows(mip, nrs, num); xfree(num); } m = tree->orig_m; /* restore original attributes of rows and columns */ xassert(m == tree->orig_m); xassert(n == tree->n); for (i = 1; i <= m; i++) { glp_set_row_bnds(mip, i, tree->orig_type[i], tree->orig_lb[i], tree->orig_ub[i]); glp_set_row_stat(mip, i, tree->orig_stat[i]); mip->row[i]->prim = tree->orig_prim[i]; mip->row[i]->dual = tree->orig_dual[i]; } for (j = 1; j <= n; j++) { glp_set_col_bnds(mip, j, tree->orig_type[m+j], tree->orig_lb[m+j], tree->orig_ub[m+j]); glp_set_col_stat(mip, j, tree->orig_stat[m+j]); mip->col[j]->prim = tree->orig_prim[m+j]; mip->col[j]->dual = tree->orig_dual[m+j]; } mip->pbs_stat = mip->dbs_stat = GLP_FEAS; mip->obj_val = tree->orig_obj; /* delete the branch-and-bound tree */ xassert(tree->local != NULL); ios_delete_pool(tree, tree->local); dmp_delete_pool(tree->pool); xfree(tree->orig_type); xfree(tree->orig_lb); xfree(tree->orig_ub); xfree(tree->orig_stat); xfree(tree->orig_prim); xfree(tree->orig_dual); xfree(tree->slot); if (tree->root_type != NULL) xfree(tree->root_type); if (tree->root_lb != NULL) xfree(tree->root_lb); if (tree->root_ub != NULL) xfree(tree->root_ub); if (tree->root_stat != NULL) xfree(tree->root_stat); xfree(tree->non_int); #if 0 xfree(tree->n_ref); xfree(tree->c_ref); xfree(tree->j_ref); #endif if (tree->pcost != NULL) ios_pcost_free(tree); xfree(tree->iwrk); xfree(tree->dwrk); #if 0 scg_delete_graph(tree->g); #endif if (tree->pred_type != NULL) xfree(tree->pred_type); if (tree->pred_lb != NULL) xfree(tree->pred_lb); if (tree->pred_ub != NULL) xfree(tree->pred_ub); if (tree->pred_stat != NULL) xfree(tree->pred_stat); #if 0 xassert(tree->cut_gen == NULL); #endif xassert(tree->mir_gen == NULL); xassert(tree->clq_gen == NULL); xfree(tree); mip->tree = NULL; return; } /*********************************************************************** * NAME * * ios_eval_degrad - estimate obj. degrad. for down- and up-branches * * SYNOPSIS * * #include "glpios.h" * void ios_eval_degrad(glp_tree *tree, int j, double *dn, double *up); * * DESCRIPTION * * Given optimal basis to LP relaxation of the current subproblem the * routine ios_eval_degrad performs the dual ratio test to compute the * objective values in the adjacent basis for down- and up-branches, * which are stored in locations *dn and *up, assuming that x[j] is a * variable chosen to branch upon. */ void ios_eval_degrad(glp_tree *tree, int j, double *dn, double *up) { glp_prob *mip = tree->mip; int m = mip->m, n = mip->n; int len, kase, k, t, stat; double alfa, beta, gamma, delta, dz; int *ind = tree->iwrk; double *val = tree->dwrk; /* current basis must be optimal */ xassert(glp_get_status(mip) == GLP_OPT); /* basis factorization must exist */ xassert(glp_bf_exists(mip)); /* obtain (fractional) value of x[j] in optimal basic solution to LP relaxation of the current subproblem */ xassert(1 <= j && j <= n); beta = mip->col[j]->prim; /* since the value of x[j] is fractional, it is basic; compute corresponding row of the simplex table */ len = lpx_eval_tab_row(mip, m+j, ind, val); /* kase < 0 means down-branch; kase > 0 means up-branch */ for (kase = -1; kase <= +1; kase += 2) { /* for down-branch we introduce new upper bound floor(beta) for x[j]; similarly, for up-branch we introduce new lower bound ceil(beta) for x[j]; in the current basis this new upper/lower bound is violated, so in the adjacent basis x[j] will leave the basis and go to its new upper/lower bound; we need to know which non-basic variable x[k] should enter the basis to keep dual feasibility */ #if 0 /* 23/XI-2009 */ k = lpx_dual_ratio_test(mip, len, ind, val, kase, 1e-7); #else k = lpx_dual_ratio_test(mip, len, ind, val, kase, 1e-9); #endif /* if no variable has been chosen, current basis being primal infeasible due to the new upper/lower bound of x[j] is dual unbounded, therefore, LP relaxation to corresponding branch has no primal feasible solution */ if (k == 0) { if (mip->dir == GLP_MIN) { if (kase < 0) *dn = +DBL_MAX; else *up = +DBL_MAX; } else if (mip->dir == GLP_MAX) { if (kase < 0) *dn = -DBL_MAX; else *up = -DBL_MAX; } else xassert(mip != mip); continue; } xassert(1 <= k && k <= m+n); /* row of the simplex table corresponding to specified basic variable x[j] is the following: x[j] = ... + alfa * x[k] + ... ; we need to know influence coefficient, alfa, at non-basic variable x[k] chosen with the dual ratio test */ for (t = 1; t <= len; t++) if (ind[t] == k) break; xassert(1 <= t && t <= len); alfa = val[t]; /* determine status and reduced cost of variable x[k] */ if (k <= m) { stat = mip->row[k]->stat; gamma = mip->row[k]->dual; } else { stat = mip->col[k-m]->stat; gamma = mip->col[k-m]->dual; } /* x[k] cannot be basic or fixed non-basic */ xassert(stat == GLP_NL || stat == GLP_NU || stat == GLP_NF); /* if the current basis is dual degenerative, some reduced costs, which are close to zero, may have wrong sign due to round-off errors, so correct the sign of gamma */ if (mip->dir == GLP_MIN) { if (stat == GLP_NL && gamma < 0.0 || stat == GLP_NU && gamma > 0.0 || stat == GLP_NF) gamma = 0.0; } else if (mip->dir == GLP_MAX) { if (stat == GLP_NL && gamma > 0.0 || stat == GLP_NU && gamma < 0.0 || stat == GLP_NF) gamma = 0.0; } else xassert(mip != mip); /* determine the change of x[j] in the adjacent basis: delta x[j] = new x[j] - old x[j] */ delta = (kase < 0 ? floor(beta) : ceil(beta)) - beta; /* compute the change of x[k] in the adjacent basis: delta x[k] = new x[k] - old x[k] = delta x[j] / alfa */ delta /= alfa; /* compute the change of the objective in the adjacent basis: delta z = new z - old z = gamma * delta x[k] */ dz = gamma * delta; if (mip->dir == GLP_MIN) xassert(dz >= 0.0); else if (mip->dir == GLP_MAX) xassert(dz <= 0.0); else xassert(mip != mip); /* compute the new objective value in the adjacent basis: new z = old z + delta z */ if (kase < 0) *dn = mip->obj_val + dz; else *up = mip->obj_val + dz; } /*xprintf("obj = %g; dn = %g; up = %g\n", mip->obj_val, *dn, *up);*/ return; } /*********************************************************************** * NAME * * ios_round_bound - improve local bound by rounding * * SYNOPSIS * * #include "glpios.h" * double ios_round_bound(glp_tree *tree, double bound); * * RETURNS * * For the given local bound for any integer feasible solution to the * current subproblem the routine ios_round_bound returns an improved * local bound for the same integer feasible solution. * * BACKGROUND * * Let the current subproblem has the following objective function: * * z = sum c[j] * x[j] + s >= b, (1) * j in J * * where J = {j: c[j] is non-zero and integer, x[j] is integer}, s is * the sum of terms corresponding to fixed variables, b is an initial * local bound (minimization). * * From (1) it follows that: * * d * sum (c[j] / d) * x[j] + s >= b, (2) * j in J * * or, equivalently, * * sum (c[j] / d) * x[j] >= (b - s) / d = h, (3) * j in J * * where d = gcd(c[j]). Since the left-hand side of (3) is integer, * h = (b - s) / d can be rounded up to the nearest integer: * * h' = ceil(h) = (b' - s) / d, (4) * * that gives an rounded, improved local bound: * * b' = d * h' + s. (5) * * In case of maximization '>=' in (1) should be replaced by '<=' that * leads to the following formula: * * h' = floor(h) = (b' - s) / d, (6) * * which should used in the same way as (4). * * NOTE: If b is a valid local bound for a child of the current * subproblem, b' is also valid for that child subproblem. */ double ios_round_bound(glp_tree *tree, double bound) { glp_prob *mip = tree->mip; int n = mip->n; int d, j, nn, *c = tree->iwrk; double s, h; /* determine c[j] and compute s */ nn = 0, s = mip->c0, d = 0; for (j = 1; j <= n; j++) { GLPCOL *col = mip->col[j]; if (col->coef == 0.0) continue; if (col->type == GLP_FX) { /* fixed variable */ s += col->coef * col->prim; } else { /* non-fixed variable */ if (col->kind != GLP_IV) goto skip; if (col->coef != floor(col->coef)) goto skip; if (fabs(col->coef) <= (double)INT_MAX) c[++nn] = (int)fabs(col->coef); else d = 1; } } /* compute d = gcd(c[1],...c[nn]) */ if (d == 0) { if (nn == 0) goto skip; d = gcdn(nn, c); } xassert(d > 0); /* compute new local bound */ if (mip->dir == GLP_MIN) { if (bound != +DBL_MAX) { h = (bound - s) / (double)d; if (h >= floor(h) + 0.001) { /* round up */ h = ceil(h); /*xprintf("d = %d; old = %g; ", d, bound);*/ bound = (double)d * h + s; /*xprintf("new = %g\n", bound);*/ } } } else if (mip->dir == GLP_MAX) { if (bound != -DBL_MAX) { h = (bound - s) / (double)d; if (h <= ceil(h) - 0.001) { /* round down */ h = floor(h); bound = (double)d * h + s; } } } else xassert(mip != mip); skip: return bound; } /*********************************************************************** * NAME * * ios_is_hopeful - check if subproblem is hopeful * * SYNOPSIS * * #include "glpios.h" * int ios_is_hopeful(glp_tree *tree, double bound); * * DESCRIPTION * * Given the local bound of a subproblem the routine ios_is_hopeful * checks if the subproblem can have an integer optimal solution which * is better than the best one currently known. * * RETURNS * * If the subproblem can have a better integer optimal solution, the * routine returns non-zero; otherwise, if the corresponding branch can * be pruned, the routine returns zero. */ int ios_is_hopeful(glp_tree *tree, double bound) { glp_prob *mip = tree->mip; int ret = 1; double eps; if (mip->mip_stat == GLP_FEAS) { eps = tree->parm->tol_obj * (1.0 + fabs(mip->mip_obj)); switch (mip->dir) { case GLP_MIN: if (bound >= mip->mip_obj - eps) ret = 0; break; case GLP_MAX: if (bound <= mip->mip_obj + eps) ret = 0; break; default: xassert(mip != mip); } } else { switch (mip->dir) { case GLP_MIN: if (bound == +DBL_MAX) ret = 0; break; case GLP_MAX: if (bound == -DBL_MAX) ret = 0; break; default: xassert(mip != mip); } } return ret; } /*********************************************************************** * NAME * * ios_best_node - find active node with best local bound * * SYNOPSIS * * #include "glpios.h" * int ios_best_node(glp_tree *tree); * * DESCRIPTION * * The routine ios_best_node finds an active node whose local bound is * best among other active nodes. * * It is understood that the integer optimal solution of the original * mip problem cannot be better than the best bound, so the best bound * is an lower (minimization) or upper (maximization) global bound for * the original problem. * * RETURNS * * The routine ios_best_node returns the subproblem reference number * for the best node. However, if the tree is empty, it returns zero. */ int ios_best_node(glp_tree *tree) { IOSNPD *node, *best = NULL; switch (tree->mip->dir) { case GLP_MIN: /* minimization */ for (node = tree->head; node != NULL; node = node->next) if (best == NULL || best->bound > node->bound) best = node; break; case GLP_MAX: /* maximization */ for (node = tree->head; node != NULL; node = node->next) if (best == NULL || best->bound < node->bound) best = node; break; default: xassert(tree != tree); } return best == NULL ? 0 : best->p; } /*********************************************************************** * NAME * * ios_relative_gap - compute relative mip gap * * SYNOPSIS * * #include "glpios.h" * double ios_relative_gap(glp_tree *tree); * * DESCRIPTION * * The routine ios_relative_gap computes the relative mip gap using the * formula: * * gap = |best_mip - best_bnd| / (|best_mip| + DBL_EPSILON), * * where best_mip is the best integer feasible solution found so far, * best_bnd is the best (global) bound. If no integer feasible solution * has been found yet, rel_gap is set to DBL_MAX. * * RETURNS * * The routine ios_relative_gap returns the relative mip gap. */ double ios_relative_gap(glp_tree *tree) { glp_prob *mip = tree->mip; int p; double best_mip, best_bnd, gap; if (mip->mip_stat == GLP_FEAS) { best_mip = mip->mip_obj; p = ios_best_node(tree); if (p == 0) { /* the tree is empty */ gap = 0.0; } else { best_bnd = tree->slot[p].node->bound; gap = fabs(best_mip - best_bnd) / (fabs(best_mip) + DBL_EPSILON); } } else { /* no integer feasible solution has been found yet */ gap = DBL_MAX; } return gap; } /*********************************************************************** * NAME * * ios_solve_node - solve LP relaxation of current subproblem * * SYNOPSIS * * #include "glpios.h" * int ios_solve_node(glp_tree *tree); * * DESCRIPTION * * The routine ios_solve_node re-optimizes LP relaxation of the current * subproblem using the dual simplex method. * * RETURNS * * The routine returns the code which is reported by glp_simplex. */ int ios_solve_node(glp_tree *tree) { glp_prob *mip = tree->mip; glp_smcp parm; int ret; /* the current subproblem must exist */ xassert(tree->curr != NULL); /* set some control parameters */ glp_init_smcp(&parm); switch (tree->parm->msg_lev) { case GLP_MSG_OFF: parm.msg_lev = GLP_MSG_OFF; break; case GLP_MSG_ERR: parm.msg_lev = GLP_MSG_ERR; break; case GLP_MSG_ON: case GLP_MSG_ALL: parm.msg_lev = GLP_MSG_ON; break; case GLP_MSG_DBG: parm.msg_lev = GLP_MSG_ALL; break; default: xassert(tree != tree); } parm.meth = GLP_DUALP; if (tree->parm->msg_lev < GLP_MSG_DBG) parm.out_dly = tree->parm->out_dly; else parm.out_dly = 0; /* if the incumbent objective value is already known, use it to prematurely terminate the dual simplex search */ if (mip->mip_stat == GLP_FEAS) { switch (tree->mip->dir) { case GLP_MIN: parm.obj_ul = mip->mip_obj; break; case GLP_MAX: parm.obj_ll = mip->mip_obj; break; default: xassert(mip != mip); } } /* try to solve/re-optimize the LP relaxation */ ret = glp_simplex(mip, &parm); tree->curr->solved++; #if 0 xprintf("ret = %d; status = %d; pbs = %d; dbs = %d; some = %d\n", ret, glp_get_status(mip), mip->pbs_stat, mip->dbs_stat, mip->some); lpx_print_sol(mip, "sol"); #endif return ret; } /**********************************************************************/ IOSPOOL *ios_create_pool(glp_tree *tree) { /* create cut pool */ IOSPOOL *pool; #if 0 pool = dmp_get_atom(tree->pool, sizeof(IOSPOOL)); #else xassert(tree == tree); pool = xmalloc(sizeof(IOSPOOL)); #endif pool->size = 0; pool->head = pool->tail = NULL; pool->ord = 0, pool->curr = NULL; return pool; } int ios_add_row(glp_tree *tree, IOSPOOL *pool, const char *name, int klass, int flags, int len, const int ind[], const double val[], int type, double rhs) { /* add row (constraint) to the cut pool */ IOSCUT *cut; IOSAIJ *aij; int k; xassert(pool != NULL); cut = dmp_get_atom(tree->pool, sizeof(IOSCUT)); if (name == NULL || name[0] == '\0') cut->name = NULL; else { for (k = 0; name[k] != '\0'; k++) { if (k == 256) xerror("glp_ios_add_row: cut name too long\n"); if (iscntrl((unsigned char)name[k])) xerror("glp_ios_add_row: cut name contains invalid chara" "cter(s)\n"); } cut->name = dmp_get_atom(tree->pool, strlen(name)+1); strcpy(cut->name, name); } if (!(0 <= klass && klass <= 255)) xerror("glp_ios_add_row: klass = %d; invalid cut class\n", klass); cut->klass = (unsigned char)klass; if (flags != 0) xerror("glp_ios_add_row: flags = %d; invalid cut flags\n", flags); cut->ptr = NULL; if (!(0 <= len && len <= tree->n)) xerror("glp_ios_add_row: len = %d; invalid cut length\n", len); for (k = 1; k <= len; k++) { aij = dmp_get_atom(tree->pool, sizeof(IOSAIJ)); if (!(1 <= ind[k] && ind[k] <= tree->n)) xerror("glp_ios_add_row: ind[%d] = %d; column index out of " "range\n", k, ind[k]); aij->j = ind[k]; aij->val = val[k]; aij->next = cut->ptr; cut->ptr = aij; } if (!(type == GLP_LO || type == GLP_UP || type == GLP_FX)) xerror("glp_ios_add_row: type = %d; invalid cut type\n", type); cut->type = (unsigned char)type; cut->rhs = rhs; cut->prev = pool->tail; cut->next = NULL; if (cut->prev == NULL) pool->head = cut; else cut->prev->next = cut; pool->tail = cut; pool->size++; return pool->size; } IOSCUT *ios_find_row(IOSPOOL *pool, int i) { /* find row (constraint) in the cut pool */ /* (smart linear search) */ xassert(pool != NULL); xassert(1 <= i && i <= pool->size); if (pool->ord == 0) { xassert(pool->curr == NULL); pool->ord = 1; pool->curr = pool->head; } xassert(pool->curr != NULL); if (i < pool->ord) { if (i < pool->ord - i) { pool->ord = 1; pool->curr = pool->head; while (pool->ord != i) { pool->ord++; xassert(pool->curr != NULL); pool->curr = pool->curr->next; } } else { while (pool->ord != i) { pool->ord--; xassert(pool->curr != NULL); pool->curr = pool->curr->prev; } } } else if (i > pool->ord) { if (i - pool->ord < pool->size - i) { while (pool->ord != i) { pool->ord++; xassert(pool->curr != NULL); pool->curr = pool->curr->next; } } else { pool->ord = pool->size; pool->curr = pool->tail; while (pool->ord != i) { pool->ord--; xassert(pool->curr != NULL); pool->curr = pool->curr->prev; } } } xassert(pool->ord == i); xassert(pool->curr != NULL); return pool->curr; } void ios_del_row(glp_tree *tree, IOSPOOL *pool, int i) { /* remove row (constraint) from the cut pool */ IOSCUT *cut; IOSAIJ *aij; xassert(pool != NULL); if (!(1 <= i && i <= pool->size)) xerror("glp_ios_del_row: i = %d; cut number out of range\n", i); cut = ios_find_row(pool, i); xassert(pool->curr == cut); if (cut->next != NULL) pool->curr = cut->next; else if (cut->prev != NULL) pool->ord--, pool->curr = cut->prev; else pool->ord = 0, pool->curr = NULL; if (cut->name != NULL) dmp_free_atom(tree->pool, cut->name, strlen(cut->name)+1); if (cut->prev == NULL) { xassert(pool->head == cut); pool->head = cut->next; } else { xassert(cut->prev->next == cut); cut->prev->next = cut->next; } if (cut->next == NULL) { xassert(pool->tail == cut); pool->tail = cut->prev; } else { xassert(cut->next->prev == cut); cut->next->prev = cut->prev; } while (cut->ptr != NULL) { aij = cut->ptr; cut->ptr = aij->next; dmp_free_atom(tree->pool, aij, sizeof(IOSAIJ)); } dmp_free_atom(tree->pool, cut, sizeof(IOSCUT)); pool->size--; return; } void ios_clear_pool(glp_tree *tree, IOSPOOL *pool) { /* remove all rows (constraints) from the cut pool */ xassert(pool != NULL); while (pool->head != NULL) { IOSCUT *cut = pool->head; pool->head = cut->next; if (cut->name != NULL) dmp_free_atom(tree->pool, cut->name, strlen(cut->name)+1); while (cut->ptr != NULL) { IOSAIJ *aij = cut->ptr; cut->ptr = aij->next; dmp_free_atom(tree->pool, aij, sizeof(IOSAIJ)); } dmp_free_atom(tree->pool, cut, sizeof(IOSCUT)); } pool->size = 0; pool->head = pool->tail = NULL; pool->ord = 0, pool->curr = NULL; return; } void ios_delete_pool(glp_tree *tree, IOSPOOL *pool) { /* delete cut pool */ xassert(pool != NULL); ios_clear_pool(tree, pool); xfree(pool); return; } /**********************************************************************/ #if 0 static int refer_to_node(glp_tree *tree, int j) { /* determine node number corresponding to binary variable x[j] or its complement */ glp_prob *mip = tree->mip; int n = mip->n; int *ref; if (j > 0) ref = tree->n_ref; else ref = tree->c_ref, j = - j; xassert(1 <= j && j <= n); if (ref[j] == 0) { /* new node is needed */ SCG *g = tree->g; int n_max = g->n_max; ref[j] = scg_add_nodes(g, 1); if (g->n_max > n_max) { int *save = tree->j_ref; tree->j_ref = xcalloc(1+g->n_max, sizeof(int)); memcpy(&tree->j_ref[1], &save[1], g->n * sizeof(int)); xfree(save); } xassert(ref[j] == g->n); tree->j_ref[ref[j]] = j; xassert(tree->curr != NULL); if (tree->curr->level > 0) tree->curr->own_nn++; } return ref[j]; } #endif #if 0 void ios_add_edge(glp_tree *tree, int j1, int j2) { /* add new edge to the conflict graph */ glp_prob *mip = tree->mip; int n = mip->n; SCGRIB *e; int first, i1, i2; xassert(-n <= j1 && j1 <= +n && j1 != 0); xassert(-n <= j2 && j2 <= +n && j2 != 0); xassert(j1 != j2); /* determine number of the first node, which was added for the current subproblem */ xassert(tree->curr != NULL); first = tree->g->n - tree->curr->own_nn + 1; /* determine node numbers for both endpoints */ i1 = refer_to_node(tree, j1); i2 = refer_to_node(tree, j2); /* add edge (i1,i2) to the conflict graph */ e = scg_add_edge(tree->g, i1, i2); /* if the current subproblem is not the root and both endpoints were created on some previous levels, save the edge */ if (tree->curr->level > 0 && i1 < first && i2 < first) { IOSRIB *rib; rib = dmp_get_atom(tree->pool, sizeof(IOSRIB)); rib->j1 = j1; rib->j2 = j2; rib->e = e; rib->next = tree->curr->e_ptr; tree->curr->e_ptr = rib; } return; } #endif /* eof */ sources_5316/external/glpk/glpios08.c0000644000176700017670000006720211401660400016312 0ustar paulpaul/* glpios08.c (clique cut generator) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" static double get_row_lb(LPX *lp, int i) { /* this routine returns lower bound of row i or -DBL_MAX if the row has no lower bound */ double lb; switch (lpx_get_row_type(lp, i)) { case LPX_FR: case LPX_UP: lb = -DBL_MAX; break; case LPX_LO: case LPX_DB: case LPX_FX: lb = lpx_get_row_lb(lp, i); break; default: xassert(lp != lp); } return lb; } static double get_row_ub(LPX *lp, int i) { /* this routine returns upper bound of row i or +DBL_MAX if the row has no upper bound */ double ub; switch (lpx_get_row_type(lp, i)) { case LPX_FR: case LPX_LO: ub = +DBL_MAX; break; case LPX_UP: case LPX_DB: case LPX_FX: ub = lpx_get_row_ub(lp, i); break; default: xassert(lp != lp); } return ub; } static double get_col_lb(LPX *lp, int j) { /* this routine returns lower bound of column j or -DBL_MAX if the column has no lower bound */ double lb; switch (lpx_get_col_type(lp, j)) { case LPX_FR: case LPX_UP: lb = -DBL_MAX; break; case LPX_LO: case LPX_DB: case LPX_FX: lb = lpx_get_col_lb(lp, j); break; default: xassert(lp != lp); } return lb; } static double get_col_ub(LPX *lp, int j) { /* this routine returns upper bound of column j or +DBL_MAX if the column has no upper bound */ double ub; switch (lpx_get_col_type(lp, j)) { case LPX_FR: case LPX_LO: ub = +DBL_MAX; break; case LPX_UP: case LPX_DB: case LPX_FX: ub = lpx_get_col_ub(lp, j); break; default: xassert(lp != lp); } return ub; } static int is_binary(LPX *lp, int j) { /* this routine checks if variable x[j] is binary */ return lpx_get_col_kind(lp, j) == LPX_IV && lpx_get_col_type(lp, j) == LPX_DB && lpx_get_col_lb(lp, j) == 0.0 && lpx_get_col_ub(lp, j) == 1.0; } static double eval_lf_min(LPX *lp, int len, int ind[], double val[]) { /* this routine computes the minimum of a specified linear form sum a[j]*x[j] j using the formula: min = sum a[j]*lb[j] + sum a[j]*ub[j], j in J+ j in J- where J+ = {j: a[j] > 0}, J- = {j: a[j] < 0}, lb[j] and ub[j] are lower and upper bound of variable x[j], resp. */ int j, t; double lb, ub, sum; sum = 0.0; for (t = 1; t <= len; t++) { j = ind[t]; if (val[t] > 0.0) { lb = get_col_lb(lp, j); if (lb == -DBL_MAX) { sum = -DBL_MAX; break; } sum += val[t] * lb; } else if (val[t] < 0.0) { ub = get_col_ub(lp, j); if (ub == +DBL_MAX) { sum = -DBL_MAX; break; } sum += val[t] * ub; } else xassert(val != val); } return sum; } static double eval_lf_max(LPX *lp, int len, int ind[], double val[]) { /* this routine computes the maximum of a specified linear form sum a[j]*x[j] j using the formula: max = sum a[j]*ub[j] + sum a[j]*lb[j], j in J+ j in J- where J+ = {j: a[j] > 0}, J- = {j: a[j] < 0}, lb[j] and ub[j] are lower and upper bound of variable x[j], resp. */ int j, t; double lb, ub, sum; sum = 0.0; for (t = 1; t <= len; t++) { j = ind[t]; if (val[t] > 0.0) { ub = get_col_ub(lp, j); if (ub == +DBL_MAX) { sum = +DBL_MAX; break; } sum += val[t] * ub; } else if (val[t] < 0.0) { lb = get_col_lb(lp, j); if (lb == -DBL_MAX) { sum = +DBL_MAX; break; } sum += val[t] * lb; } else xassert(val != val); } return sum; } /*---------------------------------------------------------------------- -- probing - determine logical relation between binary variables. -- -- This routine tentatively sets a binary variable to 0 and then to 1 -- and examines whether another binary variable is caused to be fixed. -- -- The examination is based only on one row (constraint), which is the -- following: -- -- L <= sum a[j]*x[j] <= U. (1) -- j -- -- Let x[p] be a probing variable, x[q] be an examined variable. Then -- (1) can be written as: -- -- L <= sum a[j]*x[j] + a[p]*x[p] + a[q]*x[q] <= U, (2) -- j in J' -- -- where J' = {j: j != p and j != q}. -- -- Let -- -- L' = L - a[p]*x[p], (3) -- -- U' = U - a[p]*x[p], (4) -- -- where x[p] is assumed to be fixed at 0 or 1. So (2) can be rewritten -- as follows: -- -- L' <= sum a[j]*x[j] + a[q]*x[q] <= U', (5) -- j in J' -- -- from where we have: -- -- L' - sum a[j]*x[j] <= a[q]*x[q] <= U' - sum a[j]*x[j]. (6) -- j in J' j in J' -- -- Thus, -- -- min a[q]*x[q] = L' - MAX, (7) -- -- max a[q]*x[q] = U' - MIN, (8) -- -- where -- -- MIN = min sum a[j]*x[j], (9) -- j in J' -- -- MAX = max sum a[j]*x[j]. (10) -- j in J' -- -- Formulae (7) and (8) allows determining implied lower and upper -- bounds of x[q]. -- -- Parameters len, val, L and U specify the constraint (1). -- -- Parameters lf_min and lf_max specify implied lower and upper bounds -- of the linear form (1). It is assumed that these bounds are computed -- with the routines eval_lf_min and eval_lf_max (see above). -- -- Parameter p specifies the probing variable x[p], which is set to 0 -- (if set is 0) or to 1 (if set is 1). -- -- Parameter q specifies the examined variable x[q]. -- -- On exit the routine returns one of the following codes: -- -- 0 - there is no logical relation between x[p] and x[q]; -- 1 - x[q] can take only on value 0; -- 2 - x[q] can take only on value 1. */ static int probing(int len, double val[], double L, double U, double lf_min, double lf_max, int p, int set, int q) { double temp; xassert(1 <= p && p < q && q <= len); /* compute L' (3) */ if (L != -DBL_MAX && set) L -= val[p]; /* compute U' (4) */ if (U != +DBL_MAX && set) U -= val[p]; /* compute MIN (9) */ if (lf_min != -DBL_MAX) { if (val[p] < 0.0) lf_min -= val[p]; if (val[q] < 0.0) lf_min -= val[q]; } /* compute MAX (10) */ if (lf_max != +DBL_MAX) { if (val[p] > 0.0) lf_max -= val[p]; if (val[q] > 0.0) lf_max -= val[q]; } /* compute implied lower bound of x[q]; see (7), (8) */ if (val[q] > 0.0) { if (L == -DBL_MAX || lf_max == +DBL_MAX) temp = -DBL_MAX; else temp = (L - lf_max) / val[q]; } else { if (U == +DBL_MAX || lf_min == -DBL_MAX) temp = -DBL_MAX; else temp = (U - lf_min) / val[q]; } if (temp > 0.001) return 2; /* compute implied upper bound of x[q]; see (7), (8) */ if (val[q] > 0.0) { if (U == +DBL_MAX || lf_min == -DBL_MAX) temp = +DBL_MAX; else temp = (U - lf_min) / val[q]; } else { if (L == -DBL_MAX || lf_max == +DBL_MAX) temp = +DBL_MAX; else temp = (L - lf_max) / val[q]; } if (temp < 0.999) return 1; /* there is no logical relation between x[p] and x[q] */ return 0; } struct COG { /* conflict graph; it represents logical relations between binary variables and has a vertex for each binary variable and its complement, and an edge between two vertices when at most one of the variables represented by the vertices can equal one in an optimal solution */ int n; /* number of variables */ int nb; /* number of binary variables represented in the graph (note that not all binary variables can be represented); vertices which correspond to binary variables have numbers 1, ..., nb while vertices which correspond to complements of binary variables have numbers nb+1, ..., nb+nb */ int ne; /* number of edges in the graph */ int *vert; /* int vert[1+n]; */ /* if x[j] is a binary variable represented in the graph, vert[j] is the vertex number corresponding to x[j]; otherwise vert[j] is zero */ int *orig; /* int list[1:nb]; */ /* if vert[j] = k > 0, then orig[k] = j */ unsigned char *a; /* adjacency matrix of the graph having 2*nb rows and columns; only strict lower triangle is stored in dense packed form */ }; /*---------------------------------------------------------------------- -- lpx_create_cog - create the conflict graph. -- -- SYNOPSIS -- -- #include "glplpx.h" -- void *lpx_create_cog(LPX *lp); -- -- DESCRIPTION -- -- The routine lpx_create_cog creates the conflict graph for a given -- problem instance. -- -- RETURNS -- -- If the graph has been created, the routine returns a pointer to it. -- Otherwise the routine returns NULL. */ #define MAX_NB 4000 #define MAX_ROW_LEN 500 static void lpx_add_cog_edge(void *_cog, int i, int j); static void *lpx_create_cog(LPX *lp) { struct COG *cog = NULL; int m, n, nb, i, j, p, q, len, *ind, *vert, *orig; double L, U, lf_min, lf_max, *val; xprintf("Creating the conflict graph...\n"); m = lpx_get_num_rows(lp); n = lpx_get_num_cols(lp); /* determine which binary variables should be included in the conflict graph */ nb = 0; vert = xcalloc(1+n, sizeof(int)); for (j = 1; j <= n; j++) vert[j] = 0; orig = xcalloc(1+n, sizeof(int)); ind = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(double)); for (i = 1; i <= m; i++) { L = get_row_lb(lp, i); U = get_row_ub(lp, i); if (L == -DBL_MAX && U == +DBL_MAX) continue; len = lpx_get_mat_row(lp, i, ind, val); if (len > MAX_ROW_LEN) continue; lf_min = eval_lf_min(lp, len, ind, val); lf_max = eval_lf_max(lp, len, ind, val); for (p = 1; p <= len; p++) { if (!is_binary(lp, ind[p])) continue; for (q = p+1; q <= len; q++) { if (!is_binary(lp, ind[q])) continue; if (probing(len, val, L, U, lf_min, lf_max, p, 0, q) || probing(len, val, L, U, lf_min, lf_max, p, 1, q)) { /* there is a logical relation */ /* include the first variable in the graph */ j = ind[p]; if (vert[j] == 0) nb++, vert[j] = nb, orig[nb] = j; /* incude the second variable in the graph */ j = ind[q]; if (vert[j] == 0) nb++, vert[j] = nb, orig[nb] = j; } } } } /* if the graph is either empty or has too many vertices, do not create it */ if (nb == 0 || nb > MAX_NB) { xprintf("The conflict graph is either empty or too big\n"); xfree(vert); xfree(orig); goto done; } /* create the conflict graph */ cog = xmalloc(sizeof(struct COG)); cog->n = n; cog->nb = nb; cog->ne = 0; cog->vert = vert; cog->orig = orig; len = nb + nb; /* number of vertices */ len = (len * (len - 1)) / 2; /* number of entries in triangle */ len = (len + (CHAR_BIT - 1)) / CHAR_BIT; /* bytes needed */ cog->a = xmalloc(len); memset(cog->a, 0, len); for (j = 1; j <= nb; j++) { /* add edge between variable and its complement */ lpx_add_cog_edge(cog, +orig[j], -orig[j]); } for (i = 1; i <= m; i++) { L = get_row_lb(lp, i); U = get_row_ub(lp, i); if (L == -DBL_MAX && U == +DBL_MAX) continue; len = lpx_get_mat_row(lp, i, ind, val); if (len > MAX_ROW_LEN) continue; lf_min = eval_lf_min(lp, len, ind, val); lf_max = eval_lf_max(lp, len, ind, val); for (p = 1; p <= len; p++) { if (!is_binary(lp, ind[p])) continue; for (q = p+1; q <= len; q++) { if (!is_binary(lp, ind[q])) continue; /* set x[p] to 0 and examine x[q] */ switch (probing(len, val, L, U, lf_min, lf_max, p, 0, q)) { case 0: /* no logical relation */ break; case 1: /* x[p] = 0 implies x[q] = 0 */ lpx_add_cog_edge(cog, -ind[p], +ind[q]); break; case 2: /* x[p] = 0 implies x[q] = 1 */ lpx_add_cog_edge(cog, -ind[p], -ind[q]); break; default: xassert(lp != lp); } /* set x[p] to 1 and examine x[q] */ switch (probing(len, val, L, U, lf_min, lf_max, p, 1, q)) { case 0: /* no logical relation */ break; case 1: /* x[p] = 1 implies x[q] = 0 */ lpx_add_cog_edge(cog, +ind[p], +ind[q]); break; case 2: /* x[p] = 1 implies x[q] = 1 */ lpx_add_cog_edge(cog, +ind[p], -ind[q]); break; default: xassert(lp != lp); } } } } xprintf("The conflict graph has 2*%d vertices and %d edges\n", cog->nb, cog->ne); done: xfree(ind); xfree(val); return cog; } /*---------------------------------------------------------------------- -- lpx_add_cog_edge - add edge to the conflict graph. -- -- SYNOPSIS -- -- #include "glplpx.h" -- void lpx_add_cog_edge(void *cog, int i, int j); -- -- DESCRIPTION -- -- The routine lpx_add_cog_edge adds an edge to the conflict graph. -- The edge connects x[i] (if i > 0) or its complement (if i < 0) and -- x[j] (if j > 0) or its complement (if j < 0), where i and j are -- original ordinal numbers of corresponding variables. */ static void lpx_add_cog_edge(void *_cog, int i, int j) { struct COG *cog = _cog; int k; xassert(i != j); /* determine indices of corresponding vertices */ if (i > 0) { xassert(1 <= i && i <= cog->n); i = cog->vert[i]; xassert(i != 0); } else { i = -i; xassert(1 <= i && i <= cog->n); i = cog->vert[i]; xassert(i != 0); i += cog->nb; } if (j > 0) { xassert(1 <= j && j <= cog->n); j = cog->vert[j]; xassert(j != 0); } else { j = -j; xassert(1 <= j && j <= cog->n); j = cog->vert[j]; xassert(j != 0); j += cog->nb; } /* only lower triangle is stored, so we need i > j */ if (i < j) k = i, i = j, j = k; k = ((i - 1) * (i - 2)) / 2 + (j - 1); cog->a[k / CHAR_BIT] |= (unsigned char)(1 << ((CHAR_BIT - 1) - k % CHAR_BIT)); cog->ne++; return; } /*---------------------------------------------------------------------- -- MAXIMUM WEIGHT CLIQUE -- -- Two subroutines sub() and wclique() below are intended to find a -- maximum weight clique in a given undirected graph. These subroutines -- are slightly modified version of the program WCLIQUE developed by -- Patric Ostergard and based -- on ideas from the article "P. R. J. Ostergard, A new algorithm for -- the maximum-weight clique problem, submitted for publication", which -- in turn is a generalization of the algorithm for unweighted graphs -- presented in "P. R. J. Ostergard, A fast algorithm for the maximum -- clique problem, submitted for publication". -- -- USED WITH PERMISSION OF THE AUTHOR OF THE ORIGINAL CODE. */ struct dsa { /* dynamic storage area */ int n; /* number of vertices */ int *wt; /* int wt[0:n-1]; */ /* weights */ unsigned char *a; /* adjacency matrix (packed lower triangle without main diag.) */ int record; /* weight of best clique */ int rec_level; /* number of vertices in best clique */ int *rec; /* int rec[0:n-1]; */ /* best clique so far */ int *clique; /* int clique[0:n-1]; */ /* table for pruning */ int *set; /* int set[0:n-1]; */ /* current clique */ }; #define n (dsa->n) #define wt (dsa->wt) #define a (dsa->a) #define record (dsa->record) #define rec_level (dsa->rec_level) #define rec (dsa->rec) #define clique (dsa->clique) #define set (dsa->set) #if 0 static int is_edge(struct dsa *dsa, int i, int j) { /* if there is arc (i,j), the routine returns true; otherwise false; 0 <= i, j < n */ int k; xassert(0 <= i && i < n); xassert(0 <= j && j < n); if (i == j) return 0; if (i < j) k = i, i = j, j = k; k = (i * (i - 1)) / 2 + j; return a[k / CHAR_BIT] & (unsigned char)(1 << ((CHAR_BIT - 1) - k % CHAR_BIT)); } #else #define is_edge(dsa, i, j) ((i) == (j) ? 0 : \ (i) > (j) ? is_edge1(i, j) : is_edge1(j, i)) #define is_edge1(i, j) is_edge2(((i) * ((i) - 1)) / 2 + (j)) #define is_edge2(k) (a[(k) / CHAR_BIT] & \ (unsigned char)(1 << ((CHAR_BIT - 1) - (k) % CHAR_BIT))) #endif static void sub(struct dsa *dsa, int ct, int table[], int level, int weight, int l_weight) { int i, j, k, curr_weight, left_weight, *p1, *p2, *newtable; newtable = xcalloc(n, sizeof(int)); if (ct <= 0) { /* 0 or 1 elements left; include these */ if (ct == 0) { set[level++] = table[0]; weight += l_weight; } if (weight > record) { record = weight; rec_level = level; for (i = 0; i < level; i++) rec[i] = set[i]; } goto done; } for (i = ct; i >= 0; i--) { if ((level == 0) && (i < ct)) goto done; k = table[i]; if ((level > 0) && (clique[k] <= (record - weight))) goto done; /* prune */ set[level] = k; curr_weight = weight + wt[k]; l_weight -= wt[k]; if (l_weight <= (record - curr_weight)) goto done; /* prune */ p1 = newtable; p2 = table; left_weight = 0; while (p2 < table + i) { j = *p2++; if (is_edge(dsa, j, k)) { *p1++ = j; left_weight += wt[j]; } } if (left_weight <= (record - curr_weight)) continue; sub(dsa, p1 - newtable - 1, newtable, level + 1, curr_weight, left_weight); } done: xfree(newtable); return; } static int wclique(int _n, int w[], unsigned char _a[], int sol[]) { struct dsa _dsa, *dsa = &_dsa; int i, j, p, max_wt, max_nwt, wth, *used, *nwt, *pos; glp_long timer; n = _n; wt = &w[1]; a = _a; record = 0; rec_level = 0; rec = &sol[1]; clique = xcalloc(n, sizeof(int)); set = xcalloc(n, sizeof(int)); used = xcalloc(n, sizeof(int)); nwt = xcalloc(n, sizeof(int)); pos = xcalloc(n, sizeof(int)); /* start timer */ timer = xtime(); /* order vertices */ for (i = 0; i < n; i++) { nwt[i] = 0; for (j = 0; j < n; j++) if (is_edge(dsa, i, j)) nwt[i] += wt[j]; } for (i = 0; i < n; i++) used[i] = 0; for (i = n-1; i >= 0; i--) { max_wt = -1; max_nwt = -1; for (j = 0; j < n; j++) { if ((!used[j]) && ((wt[j] > max_wt) || (wt[j] == max_wt && nwt[j] > max_nwt))) { max_wt = wt[j]; max_nwt = nwt[j]; p = j; } } pos[i] = p; used[p] = 1; for (j = 0; j < n; j++) if ((!used[j]) && (j != p) && (is_edge(dsa, p, j))) nwt[j] -= wt[p]; } /* main routine */ wth = 0; for (i = 0; i < n; i++) { wth += wt[pos[i]]; sub(dsa, i, pos, 0, 0, wth); clique[pos[i]] = record; #if 0 if (utime() >= timer + 5.0) #else if (xdifftime(xtime(), timer) >= 5.0 - 0.001) #endif { /* print current record and reset timer */ xprintf("level = %d (%d); best = %d\n", i+1, n, record); #if 0 timer = utime(); #else timer = xtime(); #endif } } xfree(clique); xfree(set); xfree(used); xfree(nwt); xfree(pos); /* return the solution found */ for (i = 1; i <= rec_level; i++) sol[i]++; return rec_level; } #undef n #undef wt #undef a #undef record #undef rec_level #undef rec #undef clique #undef set /*---------------------------------------------------------------------- -- lpx_clique_cut - generate cluque cut. -- -- SYNOPSIS -- -- #include "glplpx.h" -- int lpx_clique_cut(LPX *lp, void *cog, int ind[], double val[]); -- -- DESCRIPTION -- -- The routine lpx_clique_cut generates a clique cut using the conflict -- graph specified by the parameter cog. -- -- If a violated clique cut has been found, it has the following form: -- -- sum{j in J} a[j]*x[j] <= b. -- -- Variable indices j in J are stored in elements ind[1], ..., ind[len] -- while corresponding constraint coefficients are stored in elements -- val[1], ..., val[len], where len is returned on exit. The right-hand -- side b is stored in element val[0]. -- -- RETURNS -- -- If the cutting plane has been successfully generated, the routine -- returns 1 <= len <= n, which is the number of non-zero coefficients -- in the inequality constraint. Otherwise, the routine returns zero. */ static int lpx_clique_cut(LPX *lp, void *_cog, int ind[], double val[]) { struct COG *cog = _cog; int n = lpx_get_num_cols(lp); int j, t, v, card, temp, len = 0, *w, *sol; double x, sum, b, *vec; /* allocate working arrays */ w = xcalloc(1 + 2 * cog->nb, sizeof(int)); sol = xcalloc(1 + 2 * cog->nb, sizeof(int)); vec = xcalloc(1+n, sizeof(double)); /* assign weights to vertices of the conflict graph */ for (t = 1; t <= cog->nb; t++) { j = cog->orig[t]; x = lpx_get_col_prim(lp, j); temp = (int)(100.0 * x + 0.5); if (temp < 0) temp = 0; if (temp > 100) temp = 100; w[t] = temp; w[cog->nb + t] = 100 - temp; } /* find a clique of maximum weight */ card = wclique(2 * cog->nb, w, cog->a, sol); /* compute the clique weight for unscaled values */ sum = 0.0; for ( t = 1; t <= card; t++) { v = sol[t]; xassert(1 <= v && v <= 2 * cog->nb); if (v <= cog->nb) { /* vertex v corresponds to binary variable x[j] */ j = cog->orig[v]; x = lpx_get_col_prim(lp, j); sum += x; } else { /* vertex v corresponds to the complement of x[j] */ j = cog->orig[v - cog->nb]; x = lpx_get_col_prim(lp, j); sum += 1.0 - x; } } /* if the sum of binary variables and their complements in the clique greater than 1, the clique cut is violated */ if (sum >= 1.01) { /* construct the inquality */ for (j = 1; j <= n; j++) vec[j] = 0; b = 1.0; for (t = 1; t <= card; t++) { v = sol[t]; if (v <= cog->nb) { /* vertex v corresponds to binary variable x[j] */ j = cog->orig[v]; xassert(1 <= j && j <= n); vec[j] += 1.0; } else { /* vertex v corresponds to the complement of x[j] */ j = cog->orig[v - cog->nb]; xassert(1 <= j && j <= n); vec[j] -= 1.0; b -= 1.0; } } xassert(len == 0); for (j = 1; j <= n; j++) { if (vec[j] != 0.0) { len++; ind[len] = j, val[len] = vec[j]; } } ind[0] = 0, val[0] = b; } /* free working arrays */ xfree(w); xfree(sol); xfree(vec); /* return to the calling program */ return len; } /*---------------------------------------------------------------------- -- lpx_delete_cog - delete the conflict graph. -- -- SYNOPSIS -- -- #include "glplpx.h" -- void lpx_delete_cog(void *cog); -- -- DESCRIPTION -- -- The routine lpx_delete_cog deletes the conflict graph, which the -- parameter cog points to, freeing all the memory allocated to this -- object. */ static void lpx_delete_cog(void *_cog) { struct COG *cog = _cog; xfree(cog->vert); xfree(cog->orig); xfree(cog->a); xfree(cog); } /**********************************************************************/ void *ios_clq_init(glp_tree *tree) { /* initialize clique cut generator */ glp_prob *mip = tree->mip; xassert(mip != NULL); return lpx_create_cog(mip); } /*********************************************************************** * NAME * * ios_clq_gen - generate clique cuts * * SYNOPSIS * * #include "glpios.h" * void ios_clq_gen(glp_tree *tree, void *gen); * * DESCRIPTION * * The routine ios_clq_gen generates clique cuts for the current point * and adds them to the clique pool. */ void ios_clq_gen(glp_tree *tree, void *gen) { int n = lpx_get_num_cols(tree->mip); int len, *ind; double *val; xassert(gen != NULL); ind = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(double)); len = lpx_clique_cut(tree->mip, gen, ind, val); if (len > 0) { /* xprintf("len = %d\n", len); */ glp_ios_add_row(tree, NULL, GLP_RF_CLQ, 0, len, ind, val, GLP_UP, val[0]); } xfree(ind); xfree(val); return; } /**********************************************************************/ void ios_clq_term(void *gen) { /* terminate clique cut generator */ xassert(gen != NULL); lpx_delete_cog(gen); return; } /* eof */ sources_5316/external/glpk/glpapi13.c0000644000176700017670000005445311401660400016271 0ustar paulpaul/* glpapi13.c (branch-and-bound interface routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*********************************************************************** * NAME * * glp_ios_reason - determine reason for calling the callback routine * * SYNOPSIS * * glp_ios_reason(glp_tree *tree); * * RETURNS * * The routine glp_ios_reason returns a code, which indicates why the * user-defined callback routine is being called. */ int glp_ios_reason(glp_tree *tree) { return tree->reason; } /*********************************************************************** * NAME * * glp_ios_get_prob - access the problem object * * SYNOPSIS * * glp_prob *glp_ios_get_prob(glp_tree *tree); * * DESCRIPTION * * The routine glp_ios_get_prob can be called from the user-defined * callback routine to access the problem object, which is used by the * MIP solver. It is the original problem object passed to the routine * glp_intopt if the MIP presolver is not used; otherwise it is an * internal problem object built by the presolver. If the current * subproblem exists, LP segment of the problem object corresponds to * its LP relaxation. * * RETURNS * * The routine glp_ios_get_prob returns a pointer to the problem object * used by the MIP solver. */ glp_prob *glp_ios_get_prob(glp_tree *tree) { return tree->mip; } /*********************************************************************** * NAME * * glp_ios_tree_size - determine size of the branch-and-bound tree * * SYNOPSIS * * void glp_ios_tree_size(glp_tree *tree, int *a_cnt, int *n_cnt, * int *t_cnt); * * DESCRIPTION * * The routine glp_ios_tree_size stores the following three counts which * characterize the current size of the branch-and-bound tree: * * a_cnt is the current number of active nodes, i.e. the current size of * the active list; * * n_cnt is the current number of all (active and inactive) nodes; * * t_cnt is the total number of nodes including those which have been * already removed from the tree. This count is increased whenever * a new node appears in the tree and never decreased. * * If some of the parameters a_cnt, n_cnt, t_cnt is a null pointer, the * corresponding count is not stored. */ void glp_ios_tree_size(glp_tree *tree, int *a_cnt, int *n_cnt, int *t_cnt) { if (a_cnt != NULL) *a_cnt = tree->a_cnt; if (n_cnt != NULL) *n_cnt = tree->n_cnt; if (t_cnt != NULL) *t_cnt = tree->t_cnt; return; } /*********************************************************************** * NAME * * glp_ios_curr_node - determine current active subproblem * * SYNOPSIS * * int glp_ios_curr_node(glp_tree *tree); * * RETURNS * * The routine glp_ios_curr_node returns the reference number of the * current active subproblem. However, if the current subproblem does * not exist, the routine returns zero. */ int glp_ios_curr_node(glp_tree *tree) { IOSNPD *node; /* obtain pointer to the current subproblem */ node = tree->curr; /* return its reference number */ return node == NULL ? 0 : node->p; } /*********************************************************************** * NAME * * glp_ios_next_node - determine next active subproblem * * SYNOPSIS * * int glp_ios_next_node(glp_tree *tree, int p); * * RETURNS * * If the parameter p is zero, the routine glp_ios_next_node returns * the reference number of the first active subproblem. However, if the * tree is empty, zero is returned. * * If the parameter p is not zero, it must specify the reference number * of some active subproblem, in which case the routine returns the * reference number of the next active subproblem. However, if there is * no next active subproblem in the list, zero is returned. * * All subproblems in the active list are ordered chronologically, i.e. * subproblem A precedes subproblem B if A was created before B. */ int glp_ios_next_node(glp_tree *tree, int p) { IOSNPD *node; if (p == 0) { /* obtain pointer to the first active subproblem */ node = tree->head; } else { /* obtain pointer to the specified subproblem */ if (!(1 <= p && p <= tree->nslots)) err: xerror("glp_ios_next_node: p = %d; invalid subproblem refer" "ence number\n", p); node = tree->slot[p].node; if (node == NULL) goto err; /* the specified subproblem must be active */ if (node->count != 0) xerror("glp_ios_next_node: p = %d; subproblem not in the ac" "tive list\n", p); /* obtain pointer to the next active subproblem */ node = node->next; } /* return the reference number */ return node == NULL ? 0 : node->p; } /*********************************************************************** * NAME * * glp_ios_prev_node - determine previous active subproblem * * SYNOPSIS * * int glp_ios_prev_node(glp_tree *tree, int p); * * RETURNS * * If the parameter p is zero, the routine glp_ios_prev_node returns * the reference number of the last active subproblem. However, if the * tree is empty, zero is returned. * * If the parameter p is not zero, it must specify the reference number * of some active subproblem, in which case the routine returns the * reference number of the previous active subproblem. However, if there * is no previous active subproblem in the list, zero is returned. * * All subproblems in the active list are ordered chronologically, i.e. * subproblem A precedes subproblem B if A was created before B. */ int glp_ios_prev_node(glp_tree *tree, int p) { IOSNPD *node; if (p == 0) { /* obtain pointer to the last active subproblem */ node = tree->tail; } else { /* obtain pointer to the specified subproblem */ if (!(1 <= p && p <= tree->nslots)) err: xerror("glp_ios_prev_node: p = %d; invalid subproblem refer" "ence number\n", p); node = tree->slot[p].node; if (node == NULL) goto err; /* the specified subproblem must be active */ if (node->count != 0) xerror("glp_ios_prev_node: p = %d; subproblem not in the ac" "tive list\n", p); /* obtain pointer to the previous active subproblem */ node = node->prev; } /* return the reference number */ return node == NULL ? 0 : node->p; } /*********************************************************************** * NAME * * glp_ios_up_node - determine parent subproblem * * SYNOPSIS * * int glp_ios_up_node(glp_tree *tree, int p); * * RETURNS * * The parameter p must specify the reference number of some (active or * inactive) subproblem, in which case the routine iet_get_up_node * returns the reference number of its parent subproblem. However, if * the specified subproblem is the root of the tree and, therefore, has * no parent, the routine returns zero. */ int glp_ios_up_node(glp_tree *tree, int p) { IOSNPD *node; /* obtain pointer to the specified subproblem */ if (!(1 <= p && p <= tree->nslots)) err: xerror("glp_ios_up_node: p = %d; invalid subproblem reference " "number\n", p); node = tree->slot[p].node; if (node == NULL) goto err; /* obtain pointer to the parent subproblem */ node = node->up; /* return the reference number */ return node == NULL ? 0 : node->p; } /*********************************************************************** * NAME * * glp_ios_node_level - determine subproblem level * * SYNOPSIS * * int glp_ios_node_level(glp_tree *tree, int p); * * RETURNS * * The routine glp_ios_node_level returns the level of the subproblem, * whose reference number is p, in the branch-and-bound tree. (The root * subproblem has level 0, and the level of any other subproblem is the * level of its parent plus one.) */ int glp_ios_node_level(glp_tree *tree, int p) { IOSNPD *node; /* obtain pointer to the specified subproblem */ if (!(1 <= p && p <= tree->nslots)) err: xerror("glp_ios_node_level: p = %d; invalid subproblem referen" "ce number\n", p); node = tree->slot[p].node; if (node == NULL) goto err; /* return the node level */ return node->level; } /*********************************************************************** * NAME * * glp_ios_node_bound - determine subproblem local bound * * SYNOPSIS * * double glp_ios_node_bound(glp_tree *tree, int p); * * RETURNS * * The routine glp_ios_node_bound returns the local bound for (active or * inactive) subproblem, whose reference number is p. * * COMMENTS * * The local bound for subproblem p is an lower (minimization) or upper * (maximization) bound for integer optimal solution to this subproblem * (not to the original problem). This bound is local in the sense that * only subproblems in the subtree rooted at node p cannot have better * integer feasible solutions. * * On creating a subproblem (due to the branching step) its local bound * is inherited from its parent and then may get only stronger (never * weaker). For the root subproblem its local bound is initially set to * -DBL_MAX (minimization) or +DBL_MAX (maximization) and then improved * as the root LP relaxation has been solved. * * Note that the local bound is not necessarily the optimal objective * value to corresponding LP relaxation; it may be stronger. */ double glp_ios_node_bound(glp_tree *tree, int p) { IOSNPD *node; /* obtain pointer to the specified subproblem */ if (!(1 <= p && p <= tree->nslots)) err: xerror("glp_ios_node_bound: p = %d; invalid subproblem referen" "ce number\n", p); node = tree->slot[p].node; if (node == NULL) goto err; /* return the node local bound */ return node->bound; } /*********************************************************************** * NAME * * glp_ios_best_node - find active subproblem with best local bound * * SYNOPSIS * * int glp_ios_best_node(glp_tree *tree); * * RETURNS * * The routine glp_ios_best_node returns the reference number of the * active subproblem, whose local bound is best (i.e. smallest in case * of minimization or largest in case of maximization). However, if the * tree is empty, the routine returns zero. * * COMMENTS * * The best local bound is an lower (minimization) or upper * (maximization) bound for integer optimal solution to the original * MIP problem. */ int glp_ios_best_node(glp_tree *tree) { return ios_best_node(tree); } /*********************************************************************** * NAME * * glp_ios_mip_gap - compute relative MIP gap * * SYNOPSIS * * double glp_ios_mip_gap(glp_tree *tree); * * DESCRIPTION * * The routine glp_ios_mip_gap computes the relative MIP gap with the * following formula: * * gap = |best_mip - best_bnd| / (|best_mip| + DBL_EPSILON), * * where best_mip is the best integer feasible solution found so far, * best_bnd is the best (global) bound. If no integer feasible solution * has been found yet, gap is set to DBL_MAX. * * RETURNS * * The routine glp_ios_mip_gap returns the relative MIP gap. */ double glp_ios_mip_gap(glp_tree *tree) { return ios_relative_gap(tree); } /*********************************************************************** * NAME * * glp_ios_node_data - access subproblem application-specific data * * SYNOPSIS * * void *glp_ios_node_data(glp_tree *tree, int p); * * DESCRIPTION * * The routine glp_ios_node_data allows the application accessing a * memory block allocated for the subproblem (which may be active or * inactive), whose reference number is p. * * The size of the block is defined by the control parameter cb_size * passed to the routine glp_intopt. The block is initialized by binary * zeros on creating corresponding subproblem, and its contents is kept * until the subproblem will be removed from the tree. * * The application may use these memory blocks to store specific data * for each subproblem. * * RETURNS * * The routine glp_ios_node_data returns a pointer to the memory block * for the specified subproblem. Note that if cb_size = 0, the routine * returns a null pointer. */ void *glp_ios_node_data(glp_tree *tree, int p) { IOSNPD *node; /* obtain pointer to the specified subproblem */ if (!(1 <= p && p <= tree->nslots)) err: xerror("glp_ios_node_level: p = %d; invalid subproblem referen" "ce number\n", p); node = tree->slot[p].node; if (node == NULL) goto err; /* return pointer to the application-specific data */ return node->data; } /*********************************************************************** * NAME * * glp_ios_row_attr - retrieve additional row attributes * * SYNOPSIS * * void glp_ios_row_attr(glp_tree *tree, int i, glp_attr *attr); * * DESCRIPTION * * The routine glp_ios_row_attr retrieves additional attributes of row * i and stores them in the structure glp_attr. */ void glp_ios_row_attr(glp_tree *tree, int i, glp_attr *attr) { GLPROW *row; if (!(1 <= i && i <= tree->mip->m)) xerror("glp_ios_row_attr: i = %d; row number out of range\n", i); row = tree->mip->row[i]; attr->level = row->level; attr->origin = row->origin; attr->klass = row->klass; return; } /**********************************************************************/ int glp_ios_pool_size(glp_tree *tree) { /* determine current size of the cut pool */ if (tree->reason != GLP_ICUTGEN) xerror("glp_ios_pool_size: operation not allowed\n"); xassert(tree->local != NULL); return tree->local->size; } /**********************************************************************/ int glp_ios_add_row(glp_tree *tree, const char *name, int klass, int flags, int len, const int ind[], const double val[], int type, double rhs) { /* add row (constraint) to the cut pool */ int num; if (tree->reason != GLP_ICUTGEN) xerror("glp_ios_add_row: operation not allowed\n"); xassert(tree->local != NULL); num = ios_add_row(tree, tree->local, name, klass, flags, len, ind, val, type, rhs); return num; } /**********************************************************************/ void glp_ios_del_row(glp_tree *tree, int i) { /* remove row (constraint) from the cut pool */ if (tree->reason != GLP_ICUTGEN) xerror("glp_ios_del_row: operation not allowed\n"); ios_del_row(tree, tree->local, i); return; } /**********************************************************************/ void glp_ios_clear_pool(glp_tree *tree) { /* remove all rows (constraints) from the cut pool */ if (tree->reason != GLP_ICUTGEN) xerror("glp_ios_clear_pool: operation not allowed\n"); ios_clear_pool(tree, tree->local); return; } /*********************************************************************** * NAME * * glp_ios_can_branch - check if can branch upon specified variable * * SYNOPSIS * * int glp_ios_can_branch(glp_tree *tree, int j); * * RETURNS * * If j-th variable (column) can be used to branch upon, the routine * glp_ios_can_branch returns non-zero, otherwise zero. */ int glp_ios_can_branch(glp_tree *tree, int j) { if (!(1 <= j && j <= tree->mip->n)) xerror("glp_ios_can_branch: j = %d; column number out of range" "\n", j); return tree->non_int[j]; } /*********************************************************************** * NAME * * glp_ios_branch_upon - choose variable to branch upon * * SYNOPSIS * * void glp_ios_branch_upon(glp_tree *tree, int j, int sel); * * DESCRIPTION * * The routine glp_ios_branch_upon can be called from the user-defined * callback routine in response to the reason GLP_IBRANCH to choose a * branching variable, whose ordinal number is j. Should note that only * variables, for which the routine glp_ios_can_branch returns non-zero, * can be used to branch upon. * * The parameter sel is a flag that indicates which branch (subproblem) * should be selected next to continue the search: * * GLP_DN_BRNCH - select down-branch; * GLP_UP_BRNCH - select up-branch; * GLP_NO_BRNCH - use general selection technique. */ void glp_ios_branch_upon(glp_tree *tree, int j, int sel) { if (!(1 <= j && j <= tree->mip->n)) xerror("glp_ios_branch_upon: j = %d; column number out of rang" "e\n", j); if (!(sel == GLP_DN_BRNCH || sel == GLP_UP_BRNCH || sel == GLP_NO_BRNCH)) xerror("glp_ios_branch_upon: sel = %d: invalid branch selectio" "n flag\n", sel); if (!(tree->non_int[j])) xerror("glp_ios_branch_upon: j = %d; variable cannot be used t" "o branch upon\n", j); if (tree->br_var != 0) xerror("glp_ios_branch_upon: branching variable already chosen" "\n"); tree->br_var = j; tree->br_sel = sel; return; } /*********************************************************************** * NAME * * glp_ios_select_node - select subproblem to continue the search * * SYNOPSIS * * void glp_ios_select_node(glp_tree *tree, int p); * * DESCRIPTION * * The routine glp_ios_select_node can be called from the user-defined * callback routine in response to the reason GLP_ISELECT to select an * active subproblem, whose reference number is p. The search will be * continued from the subproblem selected. */ void glp_ios_select_node(glp_tree *tree, int p) { IOSNPD *node; /* obtain pointer to the specified subproblem */ if (!(1 <= p && p <= tree->nslots)) err: xerror("glp_ios_select_node: p = %d; invalid subproblem refere" "nce number\n", p); node = tree->slot[p].node; if (node == NULL) goto err; /* the specified subproblem must be active */ if (node->count != 0) xerror("glp_ios_select_node: p = %d; subproblem not in the act" "ive list\n", p); /* no subproblem must be selected yet */ if (tree->next_p != 0) xerror("glp_ios_select_node: subproblem already selected\n"); /* select the specified subproblem to continue the search */ tree->next_p = p; return; } /*********************************************************************** * NAME * * glp_ios_heur_sol - provide solution found by heuristic * * SYNOPSIS * * int glp_ios_heur_sol(glp_tree *tree, const double x[]); * * DESCRIPTION * * The routine glp_ios_heur_sol can be called from the user-defined * callback routine in response to the reason GLP_IHEUR to provide an * integer feasible solution found by a primal heuristic. * * Primal values of *all* variables (columns) found by the heuristic * should be placed in locations x[1], ..., x[n], where n is the number * of columns in the original problem object. Note that the routine * glp_ios_heur_sol *does not* check primal feasibility of the solution * provided. * * Using the solution passed in the array x the routine computes value * of the objective function. If the objective value is better than the * best known integer feasible solution, the routine computes values of * auxiliary variables (rows) and stores all solution components in the * problem object. * * RETURNS * * If the provided solution is accepted, the routine glp_ios_heur_sol * returns zero. Otherwise, if the provided solution is rejected, the * routine returns non-zero. */ int glp_ios_heur_sol(glp_tree *tree, const double x[]) { glp_prob *mip = tree->mip; int m = tree->orig_m; int n = tree->n; int i, j; double obj; xassert(mip->m >= m); xassert(mip->n == n); /* check values of integer variables and compute value of the objective function */ obj = mip->c0; for (j = 1; j <= n; j++) { GLPCOL *col = mip->col[j]; if (col->kind == GLP_IV) { /* provided value must be integral */ if (x[j] != floor(x[j])) return 1; } obj += col->coef * x[j]; } /* check if the provided solution is better than the best known integer feasible solution */ if (mip->mip_stat == GLP_FEAS) { switch (mip->dir) { case GLP_MIN: if (obj >= tree->mip->mip_obj) return 1; break; case GLP_MAX: if (obj <= tree->mip->mip_obj) return 1; break; default: xassert(mip != mip); } } /* it is better; store it in the problem object */ if (tree->parm->msg_lev >= GLP_MSG_ON) xprintf("Solution found by heuristic: %.12g\n", obj); mip->mip_stat = GLP_FEAS; mip->mip_obj = obj; for (j = 1; j <= n; j++) mip->col[j]->mipx = x[j]; for (i = 1; i <= m; i++) { GLPROW *row = mip->row[i]; GLPAIJ *aij; row->mipx = 0.0; for (aij = row->ptr; aij != NULL; aij = aij->r_next) row->mipx += aij->val * aij->col->mipx; } return 0; } /*********************************************************************** * NAME * * glp_ios_terminate - terminate the solution process. * * SYNOPSIS * * void glp_ios_terminate(glp_tree *tree); * * DESCRIPTION * * The routine glp_ios_terminate sets a flag indicating that the MIP * solver should prematurely terminate the search. */ void glp_ios_terminate(glp_tree *tree) { if (tree->parm->msg_lev >= GLP_MSG_DBG) xprintf("The search is prematurely terminated due to applicati" "on request\n"); tree->stop = 1; return; } /* eof */ sources_5316/external/glpk/amd_aat.c0000644000176700017670000001340111401660400016223 0ustar paulpaul/* ========================================================================= */ /* === AMD_aat ============================================================= */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* AMD_aat: compute the symmetry of the pattern of A, and count the number of * nonzeros each column of A+A' (excluding the diagonal). Assumes the input * matrix has no errors, with sorted columns and no duplicates * (AMD_valid (n, n, Ap, Ai) must be AMD_OK, but this condition is not * checked). */ #include "amd_internal.h" GLOBAL size_t AMD_aat /* returns nz in A+A' */ ( Int n, const Int Ap [ ], const Int Ai [ ], Int Len [ ], /* Len [j]: length of column j of A+A', excl diagonal*/ Int Tp [ ], /* workspace of size n */ double Info [ ] ) { Int p1, p2, p, i, j, pj, pj2, k, nzdiag, nzboth, nz ; double sym ; size_t nzaat ; #ifndef NDEBUG AMD_debug_init ("AMD AAT") ; for (k = 0 ; k < n ; k++) Tp [k] = EMPTY ; ASSERT (AMD_valid (n, n, Ap, Ai) == AMD_OK) ; #endif if (Info != (double *) NULL) { /* clear the Info array, if it exists */ for (i = 0 ; i < AMD_INFO ; i++) { Info [i] = EMPTY ; } Info [AMD_STATUS] = AMD_OK ; } for (k = 0 ; k < n ; k++) { Len [k] = 0 ; } nzdiag = 0 ; nzboth = 0 ; nz = Ap [n] ; for (k = 0 ; k < n ; k++) { p1 = Ap [k] ; p2 = Ap [k+1] ; AMD_DEBUG2 (("\nAAT Column: "ID" p1: "ID" p2: "ID"\n", k, p1, p2)) ; /* construct A+A' */ for (p = p1 ; p < p2 ; ) { /* scan the upper triangular part of A */ j = Ai [p] ; if (j < k) { /* entry A (j,k) is in the strictly upper triangular part, * add both A (j,k) and A (k,j) to the matrix A+A' */ Len [j]++ ; Len [k]++ ; AMD_DEBUG3 ((" upper ("ID","ID") ("ID","ID")\n", j,k, k,j)); p++ ; } else if (j == k) { /* skip the diagonal */ p++ ; nzdiag++ ; break ; } else /* j > k */ { /* first entry below the diagonal */ break ; } /* scan lower triangular part of A, in column j until reaching * row k. Start where last scan left off. */ ASSERT (Tp [j] != EMPTY) ; ASSERT (Ap [j] <= Tp [j] && Tp [j] <= Ap [j+1]) ; pj2 = Ap [j+1] ; for (pj = Tp [j] ; pj < pj2 ; ) { i = Ai [pj] ; if (i < k) { /* A (i,j) is only in the lower part, not in upper. * add both A (i,j) and A (j,i) to the matrix A+A' */ Len [i]++ ; Len [j]++ ; AMD_DEBUG3 ((" lower ("ID","ID") ("ID","ID")\n", i,j, j,i)) ; pj++ ; } else if (i == k) { /* entry A (k,j) in lower part and A (j,k) in upper */ pj++ ; nzboth++ ; break ; } else /* i > k */ { /* consider this entry later, when k advances to i */ break ; } } Tp [j] = pj ; } /* Tp [k] points to the entry just below the diagonal in column k */ Tp [k] = p ; } /* clean up, for remaining mismatched entries */ for (j = 0 ; j < n ; j++) { for (pj = Tp [j] ; pj < Ap [j+1] ; pj++) { i = Ai [pj] ; /* A (i,j) is only in the lower part, not in upper. * add both A (i,j) and A (j,i) to the matrix A+A' */ Len [i]++ ; Len [j]++ ; AMD_DEBUG3 ((" lower cleanup ("ID","ID") ("ID","ID")\n", i,j, j,i)) ; } } /* --------------------------------------------------------------------- */ /* compute the symmetry of the nonzero pattern of A */ /* --------------------------------------------------------------------- */ /* Given a matrix A, the symmetry of A is: * B = tril (spones (A), -1) + triu (spones (A), 1) ; * sym = nnz (B & B') / nnz (B) ; * or 1 if nnz (B) is zero. */ if (nz == nzdiag) { sym = 1 ; } else { sym = (2 * (double) nzboth) / ((double) (nz - nzdiag)) ; } nzaat = 0 ; for (k = 0 ; k < n ; k++) { nzaat += Len [k] ; } AMD_DEBUG1 (("AMD nz in A+A', excluding diagonal (nzaat) = %g\n", (double) nzaat)) ; AMD_DEBUG1 ((" nzboth: "ID" nz: "ID" nzdiag: "ID" symmetry: %g\n", nzboth, nz, nzdiag, sym)) ; if (Info != (double *) NULL) { Info [AMD_STATUS] = AMD_OK ; Info [AMD_N] = n ; Info [AMD_NZ] = nz ; Info [AMD_SYMMETRY] = sym ; /* symmetry of pattern of A */ Info [AMD_NZDIAG] = nzdiag ; /* nonzeros on diagonal of A */ Info [AMD_NZ_A_PLUS_AT] = nzaat ; /* nonzeros in A+A' */ } return (nzaat) ; } sources_5316/external/glpk/glpapi14.c0000644000176700017670000002210611401660400016260 0ustar paulpaul/* glpapi14.c (processing models in GNU MathProg language) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define GLP_TRAN_DEFINED typedef struct MPL glp_tran; #include "glpmpl.h" #include "glpapi.h" glp_tran *glp_mpl_alloc_wksp(void) { /* allocate the MathProg translator workspace */ glp_tran *tran; tran = mpl_initialize(); return tran; } #if 1 /* 08/XII-2009 */ void _glp_mpl_init_rand(glp_tran *tran, int seed) { if (tran->phase != 0) xerror("glp_mpl_init_rand: invalid call sequence\n"); rng_init_rand(tran->rand, seed); return; } #endif int glp_mpl_read_model(glp_tran *tran, const char *fname, int skip) { /* read and translate model section */ int ret; if (tran->phase != 0) xerror("glp_mpl_read_model: invalid call sequence\n"); ret = mpl_read_model(tran, (char *)fname, skip); if (ret == 1 || ret == 2) ret = 0; else if (ret == 4) ret = 1; else xassert(ret != ret); return ret; } int glp_mpl_read_data(glp_tran *tran, const char *fname) { /* read and translate data section */ int ret; if (!(tran->phase == 1 || tran->phase == 2)) xerror("glp_mpl_read_data: invalid call sequence\n"); ret = mpl_read_data(tran, (char *)fname); if (ret == 2) ret = 0; else if (ret == 4) ret = 1; else xassert(ret != ret); return ret; } int glp_mpl_generate(glp_tran *tran, const char *fname) { /* generate the model */ int ret; if (!(tran->phase == 1 || tran->phase == 2)) xerror("glp_mpl_generate: invalid call sequence\n"); ret = mpl_generate(tran, (char *)fname); if (ret == 3) ret = 0; else if (ret == 4) ret = 1; return ret; } void glp_mpl_build_prob(glp_tran *tran, glp_prob *prob) { /* build LP/MIP problem instance from the model */ int m, n, i, j, t, kind, type, len, *ind; double lb, ub, *val; if (tran->phase != 3) xerror("glp_mpl_build_prob: invalid call sequence\n"); /* erase the problem object */ glp_erase_prob(prob); /* set problem name */ glp_set_prob_name(prob, mpl_get_prob_name(tran)); /* build rows (constraints) */ m = mpl_get_num_rows(tran); if (m > 0) glp_add_rows(prob, m); for (i = 1; i <= m; i++) { /* set row name */ glp_set_row_name(prob, i, mpl_get_row_name(tran, i)); /* set row bounds */ type = mpl_get_row_bnds(tran, i, &lb, &ub); switch (type) { case MPL_FR: type = GLP_FR; break; case MPL_LO: type = GLP_LO; break; case MPL_UP: type = GLP_UP; break; case MPL_DB: type = GLP_DB; break; case MPL_FX: type = GLP_FX; break; default: xassert(type != type); } if (type == GLP_DB && fabs(lb - ub) < 1e-9 * (1.0 + fabs(lb))) { type = GLP_FX; if (fabs(lb) <= fabs(ub)) ub = lb; else lb = ub; } glp_set_row_bnds(prob, i, type, lb, ub); /* warn about non-zero constant term */ if (mpl_get_row_c0(tran, i) != 0.0) xprintf("glp_mpl_build_prob: row %s; constant term %.12g ig" "nored\n", mpl_get_row_name(tran, i), mpl_get_row_c0(tran, i)); } /* build columns (variables) */ n = mpl_get_num_cols(tran); if (n > 0) glp_add_cols(prob, n); for (j = 1; j <= n; j++) { /* set column name */ glp_set_col_name(prob, j, mpl_get_col_name(tran, j)); /* set column kind */ kind = mpl_get_col_kind(tran, j); switch (kind) { case MPL_NUM: break; case MPL_INT: case MPL_BIN: glp_set_col_kind(prob, j, GLP_IV); break; default: xassert(kind != kind); } /* set column bounds */ type = mpl_get_col_bnds(tran, j, &lb, &ub); switch (type) { case MPL_FR: type = GLP_FR; break; case MPL_LO: type = GLP_LO; break; case MPL_UP: type = GLP_UP; break; case MPL_DB: type = GLP_DB; break; case MPL_FX: type = GLP_FX; break; default: xassert(type != type); } if (kind == MPL_BIN) { if (type == GLP_FR || type == GLP_UP || lb < 0.0) lb = 0.0; if (type == GLP_FR || type == GLP_LO || ub > 1.0) ub = 1.0; type = GLP_DB; } if (type == GLP_DB && fabs(lb - ub) < 1e-9 * (1.0 + fabs(lb))) { type = GLP_FX; if (fabs(lb) <= fabs(ub)) ub = lb; else lb = ub; } glp_set_col_bnds(prob, j, type, lb, ub); } /* load the constraint matrix */ ind = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(double)); for (i = 1; i <= m; i++) { len = mpl_get_mat_row(tran, i, ind, val); glp_set_mat_row(prob, i, len, ind, val); } /* build objective function (the first objective is used) */ for (i = 1; i <= m; i++) { kind = mpl_get_row_kind(tran, i); if (kind == MPL_MIN || kind == MPL_MAX) { /* set objective name */ glp_set_obj_name(prob, mpl_get_row_name(tran, i)); /* set optimization direction */ glp_set_obj_dir(prob, kind == MPL_MIN ? GLP_MIN : GLP_MAX); /* set constant term */ glp_set_obj_coef(prob, 0, mpl_get_row_c0(tran, i)); /* set objective coefficients */ len = mpl_get_mat_row(tran, i, ind, val); for (t = 1; t <= len; t++) glp_set_obj_coef(prob, ind[t], val[t]); break; } } /* free working arrays */ xfree(ind); xfree(val); return; } int glp_mpl_postsolve(glp_tran *tran, glp_prob *prob, int sol) { /* postsolve the model */ int i, j, m, n, stat, ret; double prim, dual; if (!(tran->phase == 3 && !tran->flag_p)) xerror("glp_mpl_postsolve: invalid call sequence\n"); if (!(sol == GLP_SOL || sol == GLP_IPT || sol == GLP_MIP)) xerror("glp_mpl_postsolve: sol = %d; invalid parameter\n", sol); m = mpl_get_num_rows(tran); n = mpl_get_num_cols(tran); if (!(m == glp_get_num_rows(prob) && n == glp_get_num_cols(prob))) xerror("glp_mpl_postsolve: wrong problem object\n"); if (!mpl_has_solve_stmt(tran)) { ret = 0; goto done; } for (i = 1; i <= m; i++) { if (sol == GLP_SOL) { stat = glp_get_row_stat(prob, i); prim = glp_get_row_prim(prob, i); dual = glp_get_row_dual(prob, i); } else if (sol == GLP_IPT) { stat = 0; prim = glp_ipt_row_prim(prob, i); dual = glp_ipt_row_dual(prob, i); } else if (sol == GLP_MIP) { stat = 0; prim = glp_mip_row_val(prob, i); dual = 0.0; } else xassert(sol != sol); if (fabs(prim) < 1e-9) prim = 0.0; if (fabs(dual) < 1e-9) dual = 0.0; mpl_put_row_soln(tran, i, stat, prim, dual); } for (j = 1; j <= n; j++) { if (sol == GLP_SOL) { stat = glp_get_col_stat(prob, j); prim = glp_get_col_prim(prob, j); dual = glp_get_col_dual(prob, j); } else if (sol == GLP_IPT) { stat = 0; prim = glp_ipt_col_prim(prob, j); dual = glp_ipt_col_dual(prob, j); } else if (sol == GLP_MIP) { stat = 0; prim = glp_mip_col_val(prob, j); dual = 0.0; } else xassert(sol != sol); if (fabs(prim) < 1e-9) prim = 0.0; if (fabs(dual) < 1e-9) dual = 0.0; mpl_put_col_soln(tran, j, stat, prim, dual); } ret = mpl_postsolve(tran); if (ret == 3) ret = 0; else if (ret == 4) ret = 1; done: return ret; } void glp_mpl_free_wksp(glp_tran *tran) { /* free the MathProg translator workspace */ mpl_terminate(tran); return; } /* eof */ sources_5316/external/glpk/glpsql.h0000644000176700017670000000414311401660400016147 0ustar paulpaul/* glpsql.h */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Author: Heinrich Schuchardt . * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPSQL_H #define GLPSQL_H #define db_iodbc_open _glp_db_iodbc_open void *db_iodbc_open(TABDCA *dca, int mode); /* open iODBC database connection */ #define db_iodbc_read _glp_db_iodbc_read int db_iodbc_read(TABDCA *dca, void *link); /* read data from iODBC */ #define db_iodbc_write _glp_db_iodbc_write int db_iodbc_write(TABDCA *dca, void *link); /* write data to iODBC */ #define db_iodbc_close _glp_db_iodbc_close int db_iodbc_close(TABDCA *dca, void *link); /* close iODBC database connection */ #define db_mysql_open _glp_db_mysql_open void *db_mysql_open(TABDCA *dca, int mode); /* open MySQL database connection */ #define db_mysql_read _glp_db_mysql_read int db_mysql_read(TABDCA *dca, void *link); /* read data from MySQL */ #define db_mysql_write _glp_db_mysql_write int db_mysql_write(TABDCA *dca, void *link); /* write data to MySQL */ #define db_mysql_close _glp_db_mysql_close int db_mysql_close(TABDCA *dca, void *link); /* close MySQL database connection */ #endif /* eof */ sources_5316/external/glpk/glpapi.h0000644000176700017670000003030211401660400016115 0ustar paulpaul/* glpapi.h (application program interface) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPAPI_H #define GLPAPI_H #define GLP_PROB_DEFINED typedef struct glp_prob glp_prob; #include "glpk.h" #include "glpavl.h" #include "glpbfd.h" typedef struct GLPROW GLPROW; typedef struct GLPCOL GLPCOL; typedef struct GLPAIJ GLPAIJ; #define GLP_PROB_MAGIC 0xD7D9D6C2 struct glp_prob { /* LP/MIP problem object */ int magic; /* magic value used for debugging */ DMP *pool; /* memory pool to store problem object components */ glp_tree *tree; /* pointer to the search tree; set by the MIP solver when this object is used in the tree as a core MIP object */ void *parms; /* reserved for backward compatibility */ /*--------------------------------------------------------------*/ /* LP/MIP data */ char *name; /* problem name (1 to 255 chars); NULL means no name is assigned to the problem */ char *obj; /* objective function name (1 to 255 chars); NULL means no name is assigned to the objective function */ int dir; /* optimization direction flag (objective "sense"): GLP_MIN - minimization GLP_MAX - maximization */ double c0; /* constant term of the objective function ("shift") */ int m_max; /* length of the array of rows (enlarged automatically) */ int n_max; /* length of the array of columns (enlarged automatically) */ int m; /* number of rows, 0 <= m <= m_max */ int n; /* number of columns, 0 <= n <= n_max */ int nnz; /* number of non-zero constraint coefficients, nnz >= 0 */ GLPROW **row; /* GLPROW *row[1+m_max]; */ /* row[i], 1 <= i <= m, is a pointer to i-th row */ GLPCOL **col; /* GLPCOL *col[1+n_max]; */ /* col[j], 1 <= j <= n, is a pointer to j-th column */ AVL *r_tree; /* row index to find rows by their names; NULL means this index does not exist */ AVL *c_tree; /* column index to find columns by their names; NULL means this index does not exist */ /*--------------------------------------------------------------*/ /* basis factorization (LP) */ int valid; /* the factorization is valid only if this flag is set */ int *head; /* int head[1+m_max]; */ /* basis header (valid only if the factorization is valid); head[i] = k is the ordinal number of auxiliary (1 <= k <= m) or structural (m+1 <= k <= m+n) variable which corresponds to i-th basic variable xB[i], 1 <= i <= m */ glp_bfcp *bfcp; /* basis factorization control parameters; may be NULL */ BFD *bfd; /* BFD bfd[1:m,1:m]; */ /* basis factorization driver; may be NULL */ /*--------------------------------------------------------------*/ /* basic solution (LP) */ int pbs_stat; /* primal basic solution status: GLP_UNDEF - primal solution is undefined GLP_FEAS - primal solution is feasible GLP_INFEAS - primal solution is infeasible GLP_NOFEAS - no primal feasible solution exists */ int dbs_stat; /* dual basic solution status: GLP_UNDEF - dual solution is undefined GLP_FEAS - dual solution is feasible GLP_INFEAS - dual solution is infeasible GLP_NOFEAS - no dual feasible solution exists */ double obj_val; /* objective function value */ int it_cnt; /* simplex method iteration count; increased by one on performing one simplex iteration */ int some; /* ordinal number of some auxiliary or structural variable having certain property, 0 <= some <= m+n */ /*--------------------------------------------------------------*/ /* interior-point solution (LP) */ int ipt_stat; /* interior-point solution status: GLP_UNDEF - interior solution is undefined GLP_OPT - interior solution is optimal GLP_INFEAS - interior solution is infeasible GLP_NOFEAS - no feasible solution exists */ double ipt_obj; /* objective function value */ /*--------------------------------------------------------------*/ /* integer solution (MIP) */ int mip_stat; /* integer solution status: GLP_UNDEF - integer solution is undefined GLP_OPT - integer solution is optimal GLP_FEAS - integer solution is feasible GLP_NOFEAS - no integer solution exists */ double mip_obj; /* objective function value */ }; struct GLPROW { /* LP/MIP row (auxiliary variable) */ int i; /* ordinal number (1 to m) assigned to this row */ char *name; /* row name (1 to 255 chars); NULL means no name is assigned to this row */ AVLNODE *node; /* pointer to corresponding node in the row index; NULL means that either the row index does not exist or this row has no name assigned */ #if 1 /* 20/IX-2008 */ int level; unsigned char origin; unsigned char klass; #endif int type; /* type of the auxiliary variable: GLP_FR - free variable GLP_LO - variable with lower bound GLP_UP - variable with upper bound GLP_DB - double-bounded variable GLP_FX - fixed variable */ double lb; /* non-scaled */ /* lower bound; if the row has no lower bound, lb is zero */ double ub; /* non-scaled */ /* upper bound; if the row has no upper bound, ub is zero */ /* if the row type is GLP_FX, ub is equal to lb */ GLPAIJ *ptr; /* non-scaled */ /* pointer to doubly linked list of constraint coefficients which are placed in this row */ double rii; /* diagonal element r[i,i] of scaling matrix R for this row; if the scaling is not used, r[i,i] is 1 */ int stat; /* status of the auxiliary variable: GLP_BS - basic variable GLP_NL - non-basic variable on lower bound GLP_NU - non-basic variable on upper bound GLP_NF - non-basic free variable GLP_NS - non-basic fixed variable */ int bind; /* if the auxiliary variable is basic, head[bind] refers to this row, otherwise, bind is 0; this attribute is valid only if the basis factorization is valid */ double prim; /* non-scaled */ /* primal value of the auxiliary variable in basic solution */ double dual; /* non-scaled */ /* dual value of the auxiliary variable in basic solution */ double pval; /* non-scaled */ /* primal value of the auxiliary variable in interior solution */ double dval; /* non-scaled */ /* dual value of the auxiliary variable in interior solution */ double mipx; /* non-scaled */ /* primal value of the auxiliary variable in integer solution */ }; struct GLPCOL { /* LP/MIP column (structural variable) */ int j; /* ordinal number (1 to n) assigned to this column */ char *name; /* column name (1 to 255 chars); NULL means no name is assigned to this column */ AVLNODE *node; /* pointer to corresponding node in the column index; NULL means that either the column index does not exist or the column has no name assigned */ int kind; /* kind of the structural variable: GLP_CV - continuous variable GLP_IV - integer or binary variable */ int type; /* type of the structural variable: GLP_FR - free variable GLP_LO - variable with lower bound GLP_UP - variable with upper bound GLP_DB - double-bounded variable GLP_FX - fixed variable */ double lb; /* non-scaled */ /* lower bound; if the column has no lower bound, lb is zero */ double ub; /* non-scaled */ /* upper bound; if the column has no upper bound, ub is zero */ /* if the column type is GLP_FX, ub is equal to lb */ double coef; /* non-scaled */ /* objective coefficient at the structural variable */ GLPAIJ *ptr; /* non-scaled */ /* pointer to doubly linked list of constraint coefficients which are placed in this column */ double sjj; /* diagonal element s[j,j] of scaling matrix S for this column; if the scaling is not used, s[j,j] is 1 */ int stat; /* status of the structural variable: GLP_BS - basic variable GLP_NL - non-basic variable on lower bound GLP_NU - non-basic variable on upper bound GLP_NF - non-basic free variable GLP_NS - non-basic fixed variable */ int bind; /* if the structural variable is basic, head[bind] refers to this column; otherwise, bind is 0; this attribute is valid only if the basis factorization is valid */ double prim; /* non-scaled */ /* primal value of the structural variable in basic solution */ double dual; /* non-scaled */ /* dual value of the structural variable in basic solution */ double pval; /* non-scaled */ /* primal value of the structural variable in interior solution */ double dval; /* non-scaled */ /* dual value of the structural variable in interior solution */ double mipx; /* non-scaled */ /* primal value of the structural variable in integer solution */ }; struct GLPAIJ { /* constraint coefficient a[i,j] */ GLPROW *row; /* pointer to row, where this coefficient is placed */ GLPCOL *col; /* pointer to column, where this coefficient is placed */ double val; /* numeric (non-zero) value of this coefficient */ GLPAIJ *r_prev; /* pointer to previous coefficient in the same row */ GLPAIJ *r_next; /* pointer to next coefficient in the same row */ GLPAIJ *c_prev; /* pointer to previous coefficient in the same column */ GLPAIJ *c_next; /* pointer to next coefficient in the same column */ }; void _glp_check_kkt(glp_prob *P, int sol, int cond, double *ae_max, int *ae_ind, double *re_max, int *re_ind); /* check feasibility and optimality conditions */ #define lpx_put_solution _glp_put_solution void lpx_put_solution(glp_prob *lp, int inval, const int *p_stat, const int *d_stat, const double *obj_val, const int r_stat[], const double r_prim[], const double r_dual[], const int c_stat[], const double c_prim[], const double c_dual[]); /* store basic solution components */ #define lpx_put_mip_soln _glp_put_mip_soln void lpx_put_mip_soln(LPX *lp, int i_stat, double row_mipx[], double col_mipx[]); /* store mixed integer solution components */ #if 1 /* 28/XI-2009 */ int _glp_analyze_row(glp_prob *P, int len, const int ind[], const double val[], int type, double rhs, double eps, int *_piv, double *_x, double *_dx, double *_y, double *_dy, double *_dz); /* simulate one iteration of dual simplex method */ #endif #if 1 /* 08/XII-2009 */ void _glp_mpl_init_rand(glp_tran *tran, int seed); #endif #define glp_skpgen _glp_skpgen void glp_skpgen(int n, int r, int type, int v, int s, int a[], int *b, int c[]); /* Pisinger's 0-1 single knapsack problem generator */ #if 1 /* 28/V-2010 */ int _glp_intopt1(glp_prob *P, const glp_iocp *parm); #endif #endif /* eof */ sources_5316/external/glpk/glplpf.h0000644000176700017670000001712211401660400016132 0ustar paulpaul/* glplpf.h (LP basis factorization, Schur complement version) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPLPF_H #define GLPLPF_H #include "glpscf.h" #include "glpluf.h" /*********************************************************************** * The structure LPF defines the factorization of the basis mxm matrix * B, where m is the number of rows in corresponding problem instance. * * This factorization is the following septet: * * [B] = (L0, U0, R, S, C, P, Q), (1) * * and is based on the following main equality: * * ( B F^) ( B0 F ) ( L0 0 ) ( U0 R ) * ( ) = P ( ) Q = P ( ) ( ) Q, (2) * ( G^ H^) ( G H ) ( S I ) ( 0 C ) * * where: * * B is the current basis matrix (not stored); * * F^, G^, H^ are some additional matrices (not stored); * * B0 is some initial basis matrix (not stored); * * F, G, H are some additional matrices (not stored); * * P, Q are permutation matrices (stored in both row- and column-like * formats); * * L0, U0 are some matrices that defines a factorization of the initial * basis matrix B0 = L0 * U0 (stored in an invertable form); * * R is a matrix defined from L0 * R = F, so R = inv(L0) * F (stored in * a column-wise sparse format); * * S is a matrix defined from S * U0 = G, so S = G * inv(U0) (stored in * a row-wise sparse format); * * C is the Schur complement for matrix (B0 F G H). It is defined from * S * R + C = H, so C = H - S * R = H - G * inv(U0) * inv(L0) * F = * = H - G * inv(B0) * F. Matrix C is stored in an invertable form. * * REFERENCES * * 1. M.A.Saunders, "LUSOL: A basis package for constrained optimiza- * tion," SCCM, Stanford University, 2006. * * 2. M.A.Saunders, "Notes 5: Basis Updates," CME 318, Stanford Univer- * sity, Spring 2006. * * 3. M.A.Saunders, "Notes 6: LUSOL---a Basis Factorization Package," * ibid. */ typedef struct LPF LPF; struct LPF { /* LP basis factorization */ int valid; /* the factorization is valid only if this flag is set */ /*--------------------------------------------------------------*/ /* initial basis matrix B0 */ int m0_max; /* maximal value of m0 (increased automatically, if necessary) */ int m0; /* the order of B0 */ LUF *luf; /* LU-factorization of B0 */ /*--------------------------------------------------------------*/ /* current basis matrix B */ int m; /* the order of B */ double *B; /* double B[1+m*m]; */ /* B in dense format stored by rows and used only for debugging; normally this array is not allocated */ /*--------------------------------------------------------------*/ /* augmented matrix (B0 F G H) of the order m0+n */ int n_max; /* maximal number of additional rows and columns */ int n; /* current number of additional rows and columns */ /*--------------------------------------------------------------*/ /* m0xn matrix R in column-wise format */ int *R_ptr; /* int R_ptr[1+n_max]; */ /* R_ptr[j], 1 <= j <= n, is a pointer to j-th column */ int *R_len; /* int R_len[1+n_max]; */ /* R_len[j], 1 <= j <= n, is the length of j-th column */ /*--------------------------------------------------------------*/ /* nxm0 matrix S in row-wise format */ int *S_ptr; /* int S_ptr[1+n_max]; */ /* S_ptr[i], 1 <= i <= n, is a pointer to i-th row */ int *S_len; /* int S_len[1+n_max]; */ /* S_len[i], 1 <= i <= n, is the length of i-th row */ /*--------------------------------------------------------------*/ /* Schur complement C of the order n */ SCF *scf; /* SCF scf[1:n_max]; */ /* factorization of the Schur complement */ /*--------------------------------------------------------------*/ /* matrix P of the order m0+n */ int *P_row; /* int P_row[1+m0_max+n_max]; */ /* P_row[i] = j means that P[i,j] = 1 */ int *P_col; /* int P_col[1+m0_max+n_max]; */ /* P_col[j] = i means that P[i,j] = 1 */ /*--------------------------------------------------------------*/ /* matrix Q of the order m0+n */ int *Q_row; /* int Q_row[1+m0_max+n_max]; */ /* Q_row[i] = j means that Q[i,j] = 1 */ int *Q_col; /* int Q_col[1+m0_max+n_max]; */ /* Q_col[j] = i means that Q[i,j] = 1 */ /*--------------------------------------------------------------*/ /* Sparse Vector Area (SVA) is a set of locations intended to store sparse vectors which represent columns of matrix R and rows of matrix S; each location is a doublet (ind, val), where ind is an index, val is a numerical value of a sparse vector element; in the whole each sparse vector is a set of adjacent locations defined by a pointer to its first element and its length, i.e. the number of its elements */ int v_size; /* the SVA size, in locations; locations are numbered by integers 1, 2, ..., v_size, and location 0 is not used */ int v_ptr; /* pointer to the first available location */ int *v_ind; /* int v_ind[1+v_size]; */ /* v_ind[k], 1 <= k <= v_size, is the index field of location k */ double *v_val; /* double v_val[1+v_size]; */ /* v_val[k], 1 <= k <= v_size, is the value field of location k */ /*--------------------------------------------------------------*/ double *work1; /* double work1[1+m0+n_max]; */ /* working array */ double *work2; /* double work2[1+m0+n_max]; */ /* working array */ }; /* return codes: */ #define LPF_ESING 1 /* singular matrix */ #define LPF_ECOND 2 /* ill-conditioned matrix */ #define LPF_ELIMIT 3 /* update limit reached */ #define lpf_create_it _glp_lpf_create_it LPF *lpf_create_it(void); /* create LP basis factorization */ #define lpf_factorize _glp_lpf_factorize int lpf_factorize(LPF *lpf, int m, const int bh[], int (*col) (void *info, int j, int ind[], double val[]), void *info); /* compute LP basis factorization */ #define lpf_ftran _glp_lpf_ftran void lpf_ftran(LPF *lpf, double x[]); /* perform forward transformation (solve system B*x = b) */ #define lpf_btran _glp_lpf_btran void lpf_btran(LPF *lpf, double x[]); /* perform backward transformation (solve system B'*x = b) */ #define lpf_update_it _glp_lpf_update_it int lpf_update_it(LPF *lpf, int j, int bh, int len, const int ind[], const double val[]); /* update LP basis factorization */ #define lpf_delete_it _glp_lpf_delete_it void lpf_delete_it(LPF *lpf); /* delete LP basis factorization */ #endif /* eof */ sources_5316/external/glpk/glpipm.c0000644000176700017670000011410711401660400016132 0ustar paulpaul/* glpipm.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpipm.h" #include "glpmat.h" #define ITER_MAX 100 /* maximal number of iterations */ struct csa { /* common storage area */ /*--------------------------------------------------------------*/ /* LP data */ int m; /* number of rows (equality constraints) */ int n; /* number of columns (structural variables) */ int *A_ptr; /* int A_ptr[1+m+1]; */ int *A_ind; /* int A_ind[A_ptr[m+1]]; */ double *A_val; /* double A_val[A_ptr[m+1]]; */ /* mxn-matrix A in storage-by-rows format */ double *b; /* double b[1+m]; */ /* m-vector b of right-hand sides */ double *c; /* double c[1+n]; */ /* n-vector c of objective coefficients; c[0] is constant term of the objective function */ /*--------------------------------------------------------------*/ /* LP solution */ double *x; /* double x[1+n]; */ double *y; /* double y[1+m]; */ double *z; /* double z[1+n]; */ /* current point in primal-dual space; the best point on exit */ /*--------------------------------------------------------------*/ /* control parameters */ const glp_iptcp *parm; /*--------------------------------------------------------------*/ /* working arrays and variables */ double *D; /* double D[1+n]; */ /* diagonal nxn-matrix D = X*inv(Z), where X = diag(x[j]) and Z = diag(z[j]) */ int *P; /* int P[1+m+m]; */ /* permutation mxm-matrix P used to minimize fill-in in Cholesky factorization */ int *S_ptr; /* int S_ptr[1+m+1]; */ int *S_ind; /* int S_ind[S_ptr[m+1]]; */ double *S_val; /* double S_val[S_ptr[m+1]]; */ double *S_diag; /* double S_diag[1+m]; */ /* symmetric mxm-matrix S = P*A*D*A'*P' whose upper triangular part without diagonal elements is stored in S_ptr, S_ind, and S_val in storage-by-rows format, diagonal elements are stored in S_diag */ int *U_ptr; /* int U_ptr[1+m+1]; */ int *U_ind; /* int U_ind[U_ptr[m+1]]; */ double *U_val; /* double U_val[U_ptr[m+1]]; */ double *U_diag; /* double U_diag[1+m]; */ /* upper triangular mxm-matrix U defining Cholesky factorization S = U'*U; its non-diagonal elements are stored in U_ptr, U_ind, U_val in storage-by-rows format, diagonal elements are stored in U_diag */ int iter; /* iteration number (0, 1, 2, ...); iter = 0 corresponds to the initial point */ double obj; /* current value of the objective function */ double rpi; /* relative primal infeasibility rpi = ||A*x-b||/(1+||b||) */ double rdi; /* relative dual infeasibility rdi = ||A'*y+z-c||/(1+||c||) */ double gap; /* primal-dual gap = |c'*x-b'*y|/(1+|c'*x|) which is a relative difference between primal and dual objective functions */ double phi; /* merit function phi = ||A*x-b||/max(1,||b||) + + ||A'*y+z-c||/max(1,||c||) + + |c'*x-b'*y|/max(1,||b||,||c||) */ double mu; /* duality measure mu = x'*z/n (used as barrier parameter) */ double rmu; /* rmu = max(||A*x-b||,||A'*y+z-c||)/mu */ double rmu0; /* the initial value of rmu on iteration 0 */ double *phi_min; /* double phi_min[1+ITER_MAX]; */ /* phi_min[k] = min(phi[k]), where phi[k] is the value of phi on k-th iteration, 0 <= k <= iter */ int best_iter; /* iteration number, on which the value of phi reached its best (minimal) value */ double *best_x; /* double best_x[1+n]; */ double *best_y; /* double best_y[1+m]; */ double *best_z; /* double best_z[1+n]; */ /* best point (in the sense of the merit function phi) which has been reached on iteration iter_best */ double best_obj; /* objective value at the best point */ double *dx_aff; /* double dx_aff[1+n]; */ double *dy_aff; /* double dy_aff[1+m]; */ double *dz_aff; /* double dz_aff[1+n]; */ /* affine scaling direction */ double alfa_aff_p, alfa_aff_d; /* maximal primal and dual stepsizes in affine scaling direction, on which x and z are still non-negative */ double mu_aff; /* duality measure mu_aff = x_aff'*z_aff/n in the boundary point x_aff' = x+alfa_aff_p*dx_aff, z_aff' = z+alfa_aff_d*dz_aff */ double sigma; /* Mehrotra's heuristic parameter (0 <= sigma <= 1) */ double *dx_cc; /* double dx_cc[1+n]; */ double *dy_cc; /* double dy_cc[1+m]; */ double *dz_cc; /* double dz_cc[1+n]; */ /* centering corrector direction */ double *dx; /* double dx[1+n]; */ double *dy; /* double dy[1+m]; */ double *dz; /* double dz[1+n]; */ /* final combined direction dx = dx_aff+dx_cc, dy = dy_aff+dy_cc, dz = dz_aff+dz_cc */ double alfa_max_p; double alfa_max_d; /* maximal primal and dual stepsizes in combined direction, on which x and z are still non-negative */ }; /*********************************************************************** * initialize - allocate and initialize common storage area * * This routine allocates and initializes the common storage area (CSA) * used by interior-point method routines. */ static void initialize(struct csa *csa) { int m = csa->m; int n = csa->n; int i; if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Matrix A has %d non-zeros\n", csa->A_ptr[m+1]-1); csa->D = xcalloc(1+n, sizeof(double)); /* P := I */ csa->P = xcalloc(1+m+m, sizeof(int)); for (i = 1; i <= m; i++) csa->P[i] = csa->P[m+i] = i; /* S := A*A', symbolically */ csa->S_ptr = xcalloc(1+m+1, sizeof(int)); csa->S_ind = adat_symbolic(m, n, csa->P, csa->A_ptr, csa->A_ind, csa->S_ptr); if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Matrix S = A*A' has %d non-zeros (upper triangle)\n", csa->S_ptr[m+1]-1 + m); /* determine P using specified ordering algorithm */ if (csa->parm->ord_alg == GLP_ORD_NONE) { if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Original ordering is being used\n"); for (i = 1; i <= m; i++) csa->P[i] = csa->P[m+i] = i; } else if (csa->parm->ord_alg == GLP_ORD_QMD) { if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Minimum degree ordering (QMD)...\n"); min_degree(m, csa->S_ptr, csa->S_ind, csa->P); } else if (csa->parm->ord_alg == GLP_ORD_AMD) { if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Approximate minimum degree ordering (AMD)...\n"); amd_order1(m, csa->S_ptr, csa->S_ind, csa->P); } else if (csa->parm->ord_alg == GLP_ORD_SYMAMD) { if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Approximate minimum degree ordering (SYMAMD)...\n") ; symamd_ord(m, csa->S_ptr, csa->S_ind, csa->P); } else xassert(csa != csa); /* S := P*A*A'*P', symbolically */ xfree(csa->S_ind); csa->S_ind = adat_symbolic(m, n, csa->P, csa->A_ptr, csa->A_ind, csa->S_ptr); csa->S_val = xcalloc(csa->S_ptr[m+1], sizeof(double)); csa->S_diag = xcalloc(1+m, sizeof(double)); /* compute Cholesky factorization S = U'*U, symbolically */ if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Computing Cholesky factorization S = L*L'...\n"); csa->U_ptr = xcalloc(1+m+1, sizeof(int)); csa->U_ind = chol_symbolic(m, csa->S_ptr, csa->S_ind, csa->U_ptr); if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Matrix L has %d non-zeros\n", csa->U_ptr[m+1]-1 + m); csa->U_val = xcalloc(csa->U_ptr[m+1], sizeof(double)); csa->U_diag = xcalloc(1+m, sizeof(double)); csa->iter = 0; csa->obj = 0.0; csa->rpi = 0.0; csa->rdi = 0.0; csa->gap = 0.0; csa->phi = 0.0; csa->mu = 0.0; csa->rmu = 0.0; csa->rmu0 = 0.0; csa->phi_min = xcalloc(1+ITER_MAX, sizeof(double)); csa->best_iter = 0; csa->best_x = xcalloc(1+n, sizeof(double)); csa->best_y = xcalloc(1+m, sizeof(double)); csa->best_z = xcalloc(1+n, sizeof(double)); csa->best_obj = 0.0; csa->dx_aff = xcalloc(1+n, sizeof(double)); csa->dy_aff = xcalloc(1+m, sizeof(double)); csa->dz_aff = xcalloc(1+n, sizeof(double)); csa->alfa_aff_p = 0.0; csa->alfa_aff_d = 0.0; csa->mu_aff = 0.0; csa->sigma = 0.0; csa->dx_cc = xcalloc(1+n, sizeof(double)); csa->dy_cc = xcalloc(1+m, sizeof(double)); csa->dz_cc = xcalloc(1+n, sizeof(double)); csa->dx = csa->dx_aff; csa->dy = csa->dy_aff; csa->dz = csa->dz_aff; csa->alfa_max_p = 0.0; csa->alfa_max_d = 0.0; return; } /*********************************************************************** * A_by_vec - compute y = A*x * * This routine computes matrix-vector product y = A*x, where A is the * constraint matrix. */ static void A_by_vec(struct csa *csa, double x[], double y[]) { /* compute y = A*x */ int m = csa->m; int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int i, t, beg, end; double temp; for (i = 1; i <= m; i++) { temp = 0.0; beg = A_ptr[i], end = A_ptr[i+1]; for (t = beg; t < end; t++) temp += A_val[t] * x[A_ind[t]]; y[i] = temp; } return; } /*********************************************************************** * AT_by_vec - compute y = A'*x * * This routine computes matrix-vector product y = A'*x, where A' is a * matrix transposed to the constraint matrix A. */ static void AT_by_vec(struct csa *csa, double x[], double y[]) { /* compute y = A'*x, where A' is transposed to A */ int m = csa->m; int n = csa->n; int *A_ptr = csa->A_ptr; int *A_ind = csa->A_ind; double *A_val = csa->A_val; int i, j, t, beg, end; double temp; for (j = 1; j <= n; j++) y[j] = 0.0; for (i = 1; i <= m; i++) { temp = x[i]; if (temp == 0.0) continue; beg = A_ptr[i], end = A_ptr[i+1]; for (t = beg; t < end; t++) y[A_ind[t]] += A_val[t] * temp; } return; } /*********************************************************************** * decomp_NE - numeric factorization of matrix S = P*A*D*A'*P' * * This routine implements numeric phase of Cholesky factorization of * the matrix S = P*A*D*A'*P', which is a permuted matrix of the normal * equation system. Matrix D is assumed to be already computed. */ static void decomp_NE(struct csa *csa) { adat_numeric(csa->m, csa->n, csa->P, csa->A_ptr, csa->A_ind, csa->A_val, csa->D, csa->S_ptr, csa->S_ind, csa->S_val, csa->S_diag); chol_numeric(csa->m, csa->S_ptr, csa->S_ind, csa->S_val, csa->S_diag, csa->U_ptr, csa->U_ind, csa->U_val, csa->U_diag); return; } /*********************************************************************** * solve_NE - solve normal equation system * * This routine solves the normal equation system: * * A*D*A'*y = h. * * It is assumed that the matrix A*D*A' has been previously factorized * by the routine decomp_NE. * * On entry the array y contains the vector of right-hand sides h. On * exit this array contains the computed vector of unknowns y. * * Once the vector y has been computed the routine checks for numeric * stability. If the residual vector: * * r = A*D*A'*y - h * * is relatively small, the routine returns zero, otherwise non-zero is * returned. */ static int solve_NE(struct csa *csa, double y[]) { int m = csa->m; int n = csa->n; int *P = csa->P; int i, j, ret = 0; double *h, *r, *w; /* save vector of right-hand sides h */ h = xcalloc(1+m, sizeof(double)); for (i = 1; i <= m; i++) h[i] = y[i]; /* solve normal equation system (A*D*A')*y = h */ /* since S = P*A*D*A'*P' = U'*U, then A*D*A' = P'*U'*U*P, so we have inv(A*D*A') = P'*inv(U)*inv(U')*P */ /* w := P*h */ w = xcalloc(1+m, sizeof(double)); for (i = 1; i <= m; i++) w[i] = y[P[i]]; /* w := inv(U')*w */ ut_solve(m, csa->U_ptr, csa->U_ind, csa->U_val, csa->U_diag, w); /* w := inv(U)*w */ u_solve(m, csa->U_ptr, csa->U_ind, csa->U_val, csa->U_diag, w); /* y := P'*w */ for (i = 1; i <= m; i++) y[i] = w[P[m+i]]; xfree(w); /* compute residual vector r = A*D*A'*y - h */ r = xcalloc(1+m, sizeof(double)); /* w := A'*y */ w = xcalloc(1+n, sizeof(double)); AT_by_vec(csa, y, w); /* w := D*w */ for (j = 1; j <= n; j++) w[j] *= csa->D[j]; /* r := A*w */ A_by_vec(csa, w, r); xfree(w); /* r := r - h */ for (i = 1; i <= m; i++) r[i] -= h[i]; /* check for numeric stability */ for (i = 1; i <= m; i++) { if (fabs(r[i]) / (1.0 + fabs(h[i])) > 1e-4) { ret = 1; break; } } xfree(h); xfree(r); return ret; } /*********************************************************************** * solve_NS - solve Newtonian system * * This routine solves the Newtonian system: * * A*dx = p * * A'*dy + dz = q * * Z*dx + X*dz = r * * where X = diag(x[j]), Z = diag(z[j]), by reducing it to the normal * equation system: * * (A*inv(Z)*X*A')*dy = A*inv(Z)*(X*q-r)+p * * (it is assumed that the matrix A*inv(Z)*X*A' has been factorized by * the routine decomp_NE). * * Once vector dy has been computed the routine computes vectors dx and * dz as follows: * * dx = inv(Z)*(X*(A'*dy-q)+r) * * dz = inv(X)*(r-Z*dx) * * The routine solve_NS returns the same code which was reported by the * routine solve_NE (see above). */ static int solve_NS(struct csa *csa, double p[], double q[], double r[], double dx[], double dy[], double dz[]) { int m = csa->m; int n = csa->n; double *x = csa->x; double *z = csa->z; int i, j, ret; double *w = dx; /* compute the vector of right-hand sides A*inv(Z)*(X*q-r)+p for the normal equation system */ for (j = 1; j <= n; j++) w[j] = (x[j] * q[j] - r[j]) / z[j]; A_by_vec(csa, w, dy); for (i = 1; i <= m; i++) dy[i] += p[i]; /* solve the normal equation system to compute vector dy */ ret = solve_NE(csa, dy); /* compute vectors dx and dz */ AT_by_vec(csa, dy, dx); for (j = 1; j <= n; j++) { dx[j] = (x[j] * (dx[j] - q[j]) + r[j]) / z[j]; dz[j] = (r[j] - z[j] * dx[j]) / x[j]; } return ret; } /*********************************************************************** * initial_point - choose initial point using Mehrotra's heuristic * * This routine chooses a starting point using a heuristic proposed in * the paper: * * S. Mehrotra. On the implementation of a primal-dual interior point * method. SIAM J. on Optim., 2(4), pp. 575-601, 1992. * * The starting point x in the primal space is chosen as a solution of * the following least squares problem: * * minimize ||x|| * * subject to A*x = b * * which can be computed explicitly as follows: * * x = A'*inv(A*A')*b * * Similarly, the starting point (y, z) in the dual space is chosen as * a solution of the following least squares problem: * * minimize ||z|| * * subject to A'*y + z = c * * which can be computed explicitly as follows: * * y = inv(A*A')*A*c * * z = c - A'*y * * However, some components of the vectors x and z may be non-positive * or close to zero, so the routine uses a Mehrotra's heuristic to find * a more appropriate starting point. */ static void initial_point(struct csa *csa) { int m = csa->m; int n = csa->n; double *b = csa->b; double *c = csa->c; double *x = csa->x; double *y = csa->y; double *z = csa->z; double *D = csa->D; int i, j; double dp, dd, ex, ez, xz; /* factorize A*A' */ for (j = 1; j <= n; j++) D[j] = 1.0; decomp_NE(csa); /* x~ = A'*inv(A*A')*b */ for (i = 1; i <= m; i++) y[i] = b[i]; solve_NE(csa, y); AT_by_vec(csa, y, x); /* y~ = inv(A*A')*A*c */ A_by_vec(csa, c, y); solve_NE(csa, y); /* z~ = c - A'*y~ */ AT_by_vec(csa, y,z); for (j = 1; j <= n; j++) z[j] = c[j] - z[j]; /* use Mehrotra's heuristic in order to choose more appropriate starting point with positive components of vectors x and z */ dp = dd = 0.0; for (j = 1; j <= n; j++) { if (dp < -1.5 * x[j]) dp = -1.5 * x[j]; if (dd < -1.5 * z[j]) dd = -1.5 * z[j]; } /* note that b = 0 involves x = 0, and c = 0 involves y = 0 and z = 0, so we need to be careful */ if (dp == 0.0) dp = 1.5; if (dd == 0.0) dd = 1.5; ex = ez = xz = 0.0; for (j = 1; j <= n; j++) { ex += (x[j] + dp); ez += (z[j] + dd); xz += (x[j] + dp) * (z[j] + dd); } dp += 0.5 * (xz / ez); dd += 0.5 * (xz / ex); for (j = 1; j <= n; j++) { x[j] += dp; z[j] += dd; xassert(x[j] > 0.0 && z[j] > 0.0); } return; } /*********************************************************************** * basic_info - perform basic computations at the current point * * This routine computes the following quantities at the current point: * * 1) value of the objective function: * * F = c'*x + c[0] * * 2) relative primal infeasibility: * * rpi = ||A*x-b|| / (1+||b||) * * 3) relative dual infeasibility: * * rdi = ||A'*y+z-c|| / (1+||c||) * * 4) primal-dual gap (relative difference between the primal and the * dual objective function values): * * gap = |c'*x-b'*y| / (1+|c'*x|) * * 5) merit function: * * phi = ||A*x-b|| / max(1,||b||) + ||A'*y+z-c|| / max(1,||c||) + * * + |c'*x-b'*y| / max(1,||b||,||c||) * * 6) duality measure: * * mu = x'*z / n * * 7) the ratio of infeasibility to mu: * * rmu = max(||A*x-b||,||A'*y+z-c||) / mu * * where ||*|| denotes euclidian norm, *' denotes transposition. */ static void basic_info(struct csa *csa) { int m = csa->m; int n = csa->n; double *b = csa->b; double *c = csa->c; double *x = csa->x; double *y = csa->y; double *z = csa->z; int i, j; double norm1, bnorm, norm2, cnorm, cx, by, *work, temp; /* compute value of the objective function */ temp = c[0]; for (j = 1; j <= n; j++) temp += c[j] * x[j]; csa->obj = temp; /* norm1 = ||A*x-b|| */ work = xcalloc(1+m, sizeof(double)); A_by_vec(csa, x, work); norm1 = 0.0; for (i = 1; i <= m; i++) norm1 += (work[i] - b[i]) * (work[i] - b[i]); norm1 = sqrt(norm1); xfree(work); /* bnorm = ||b|| */ bnorm = 0.0; for (i = 1; i <= m; i++) bnorm += b[i] * b[i]; bnorm = sqrt(bnorm); /* compute relative primal infeasibility */ csa->rpi = norm1 / (1.0 + bnorm); /* norm2 = ||A'*y+z-c|| */ work = xcalloc(1+n, sizeof(double)); AT_by_vec(csa, y, work); norm2 = 0.0; for (j = 1; j <= n; j++) norm2 += (work[j] + z[j] - c[j]) * (work[j] + z[j] - c[j]); norm2 = sqrt(norm2); xfree(work); /* cnorm = ||c|| */ cnorm = 0.0; for (j = 1; j <= n; j++) cnorm += c[j] * c[j]; cnorm = sqrt(cnorm); /* compute relative dual infeasibility */ csa->rdi = norm2 / (1.0 + cnorm); /* by = b'*y */ by = 0.0; for (i = 1; i <= m; i++) by += b[i] * y[i]; /* cx = c'*x */ cx = 0.0; for (j = 1; j <= n; j++) cx += c[j] * x[j]; /* compute primal-dual gap */ csa->gap = fabs(cx - by) / (1.0 + fabs(cx)); /* compute merit function */ csa->phi = 0.0; csa->phi += norm1 / (bnorm > 1.0 ? bnorm : 1.0); csa->phi += norm2 / (cnorm > 1.0 ? cnorm : 1.0); temp = 1.0; if (temp < bnorm) temp = bnorm; if (temp < cnorm) temp = cnorm; csa->phi += fabs(cx - by) / temp; /* compute duality measure */ temp = 0.0; for (j = 1; j <= n; j++) temp += x[j] * z[j]; csa->mu = temp / (double)n; /* compute the ratio of infeasibility to mu */ csa->rmu = (norm1 > norm2 ? norm1 : norm2) / csa->mu; return; } /*********************************************************************** * make_step - compute next point using Mehrotra's technique * * This routine computes the next point using the predictor-corrector * technique proposed in the paper: * * S. Mehrotra. On the implementation of a primal-dual interior point * method. SIAM J. on Optim., 2(4), pp. 575-601, 1992. * * At first, the routine computes so called affine scaling (predictor) * direction (dx_aff,dy_aff,dz_aff) which is a solution of the system: * * A*dx_aff = b - A*x * * A'*dy_aff + dz_aff = c - A'*y - z * * Z*dx_aff + X*dz_aff = - X*Z*e * * where (x,y,z) is the current point, X = diag(x[j]), Z = diag(z[j]), * e = (1,...,1)'. * * Then, the routine computes the centering parameter sigma, using the * following Mehrotra's heuristic: * * alfa_aff_p = inf{0 <= alfa <= 1 | x+alfa*dx_aff >= 0} * * alfa_aff_d = inf{0 <= alfa <= 1 | z+alfa*dz_aff >= 0} * * mu_aff = (x+alfa_aff_p*dx_aff)'*(z+alfa_aff_d*dz_aff)/n * * sigma = (mu_aff/mu)^3 * * where alfa_aff_p is the maximal stepsize along the affine scaling * direction in the primal space, alfa_aff_d is the maximal stepsize * along the same direction in the dual space. * * After determining sigma the routine computes so called centering * (corrector) direction (dx_cc,dy_cc,dz_cc) which is the solution of * the system: * * A*dx_cc = 0 * * A'*dy_cc + dz_cc = 0 * * Z*dx_cc + X*dz_cc = sigma*mu*e - X*Z*e * * Finally, the routine computes the combined direction * * (dx,dy,dz) = (dx_aff,dy_aff,dz_aff) + (dx_cc,dy_cc,dz_cc) * * and determines maximal primal and dual stepsizes along the combined * direction: * * alfa_max_p = inf{0 <= alfa <= 1 | x+alfa*dx >= 0} * * alfa_max_d = inf{0 <= alfa <= 1 | z+alfa*dz >= 0} * * In order to prevent the next point to be too close to the boundary * of the positive ortant, the routine decreases maximal stepsizes: * * alfa_p = gamma_p * alfa_max_p * * alfa_d = gamma_d * alfa_max_d * * where gamma_p and gamma_d are scaling factors, and computes the next * point: * * x_new = x + alfa_p * dx * * y_new = y + alfa_d * dy * * z_new = z + alfa_d * dz * * which becomes the current point on the next iteration. */ static int make_step(struct csa *csa) { int m = csa->m; int n = csa->n; double *b = csa->b; double *c = csa->c; double *x = csa->x; double *y = csa->y; double *z = csa->z; double *dx_aff = csa->dx_aff; double *dy_aff = csa->dy_aff; double *dz_aff = csa->dz_aff; double *dx_cc = csa->dx_cc; double *dy_cc = csa->dy_cc; double *dz_cc = csa->dz_cc; double *dx = csa->dx; double *dy = csa->dy; double *dz = csa->dz; int i, j, ret = 0; double temp, gamma_p, gamma_d, *p, *q, *r; /* allocate working arrays */ p = xcalloc(1+m, sizeof(double)); q = xcalloc(1+n, sizeof(double)); r = xcalloc(1+n, sizeof(double)); /* p = b - A*x */ A_by_vec(csa, x, p); for (i = 1; i <= m; i++) p[i] = b[i] - p[i]; /* q = c - A'*y - z */ AT_by_vec(csa, y,q); for (j = 1; j <= n; j++) q[j] = c[j] - q[j] - z[j]; /* r = - X * Z * e */ for (j = 1; j <= n; j++) r[j] = - x[j] * z[j]; /* solve the first Newtonian system */ if (solve_NS(csa, p, q, r, dx_aff, dy_aff, dz_aff)) { ret = 1; goto done; } /* alfa_aff_p = inf{0 <= alfa <= 1 | x + alfa*dx_aff >= 0} */ /* alfa_aff_d = inf{0 <= alfa <= 1 | z + alfa*dz_aff >= 0} */ csa->alfa_aff_p = csa->alfa_aff_d = 1.0; for (j = 1; j <= n; j++) { if (dx_aff[j] < 0.0) { temp = - x[j] / dx_aff[j]; if (csa->alfa_aff_p > temp) csa->alfa_aff_p = temp; } if (dz_aff[j] < 0.0) { temp = - z[j] / dz_aff[j]; if (csa->alfa_aff_d > temp) csa->alfa_aff_d = temp; } } /* mu_aff = (x+alfa_aff_p*dx_aff)' * (z+alfa_aff_d*dz_aff) / n */ temp = 0.0; for (j = 1; j <= n; j++) temp += (x[j] + csa->alfa_aff_p * dx_aff[j]) * (z[j] + csa->alfa_aff_d * dz_aff[j]); csa->mu_aff = temp / (double)n; /* sigma = (mu_aff/mu)^3 */ temp = csa->mu_aff / csa->mu; csa->sigma = temp * temp * temp; /* p = 0 */ for (i = 1; i <= m; i++) p[i] = 0.0; /* q = 0 */ for (j = 1; j <= n; j++) q[j] = 0.0; /* r = sigma * mu * e - X * Z * e */ for (j = 1; j <= n; j++) r[j] = csa->sigma * csa->mu - dx_aff[j] * dz_aff[j]; /* solve the second Newtonian system with the same coefficients but with altered right-hand sides */ if (solve_NS(csa, p, q, r, dx_cc, dy_cc, dz_cc)) { ret = 1; goto done; } /* (dx,dy,dz) = (dx_aff,dy_aff,dz_aff) + (dx_cc,dy_cc,dz_cc) */ for (j = 1; j <= n; j++) dx[j] = dx_aff[j] + dx_cc[j]; for (i = 1; i <= m; i++) dy[i] = dy_aff[i] + dy_cc[i]; for (j = 1; j <= n; j++) dz[j] = dz_aff[j] + dz_cc[j]; /* alfa_max_p = inf{0 <= alfa <= 1 | x + alfa*dx >= 0} */ /* alfa_max_d = inf{0 <= alfa <= 1 | z + alfa*dz >= 0} */ csa->alfa_max_p = csa->alfa_max_d = 1.0; for (j = 1; j <= n; j++) { if (dx[j] < 0.0) { temp = - x[j] / dx[j]; if (csa->alfa_max_p > temp) csa->alfa_max_p = temp; } if (dz[j] < 0.0) { temp = - z[j] / dz[j]; if (csa->alfa_max_d > temp) csa->alfa_max_d = temp; } } /* determine scale factors (not implemented yet) */ gamma_p = 0.90; gamma_d = 0.90; /* compute the next point */ for (j = 1; j <= n; j++) { x[j] += gamma_p * csa->alfa_max_p * dx[j]; xassert(x[j] > 0.0); } for (i = 1; i <= m; i++) y[i] += gamma_d * csa->alfa_max_d * dy[i]; for (j = 1; j <= n; j++) { z[j] += gamma_d * csa->alfa_max_d * dz[j]; xassert(z[j] > 0.0); } done: /* free working arrays */ xfree(p); xfree(q); xfree(r); return ret; } /*********************************************************************** * terminate - deallocate common storage area * * This routine frees all memory allocated to the common storage area * used by interior-point method routines. */ static void terminate(struct csa *csa) { xfree(csa->D); xfree(csa->P); xfree(csa->S_ptr); xfree(csa->S_ind); xfree(csa->S_val); xfree(csa->S_diag); xfree(csa->U_ptr); xfree(csa->U_ind); xfree(csa->U_val); xfree(csa->U_diag); xfree(csa->phi_min); xfree(csa->best_x); xfree(csa->best_y); xfree(csa->best_z); xfree(csa->dx_aff); xfree(csa->dy_aff); xfree(csa->dz_aff); xfree(csa->dx_cc); xfree(csa->dy_cc); xfree(csa->dz_cc); return; } /*********************************************************************** * ipm_main - main interior-point method routine * * This is a main routine of the primal-dual interior-point method. * * The routine ipm_main returns one of the following codes: * * 0 - optimal solution found; * 1 - problem has no feasible (primal or dual) solution; * 2 - no convergence; * 3 - iteration limit exceeded; * 4 - numeric instability on solving Newtonian system. * * In case of non-zero return code the routine returns the best point, * which has been reached during optimization. */ static int ipm_main(struct csa *csa) { int m = csa->m; int n = csa->n; int i, j, status; double temp; /* choose initial point using Mehrotra's heuristic */ if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Guessing initial point...\n"); initial_point(csa); /* main loop starts here */ if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Optimization begins...\n"); for (;;) { /* perform basic computations at the current point */ basic_info(csa); /* save initial value of rmu */ if (csa->iter == 0) csa->rmu0 = csa->rmu; /* accumulate values of min(phi[k]) and save the best point */ xassert(csa->iter <= ITER_MAX); if (csa->iter == 0 || csa->phi_min[csa->iter-1] > csa->phi) { csa->phi_min[csa->iter] = csa->phi; csa->best_iter = csa->iter; for (j = 1; j <= n; j++) csa->best_x[j] = csa->x[j]; for (i = 1; i <= m; i++) csa->best_y[i] = csa->y[i]; for (j = 1; j <= n; j++) csa->best_z[j] = csa->z[j]; csa->best_obj = csa->obj; } else csa->phi_min[csa->iter] = csa->phi_min[csa->iter-1]; /* display information at the current point */ if (csa->parm->msg_lev >= GLP_MSG_ON) xprintf("%3d: obj = %17.9e; rpi = %8.1e; rdi = %8.1e; gap =" " %8.1e\n", csa->iter, csa->obj, csa->rpi, csa->rdi, csa->gap); /* check if the current point is optimal */ if (csa->rpi < 1e-8 && csa->rdi < 1e-8 && csa->gap < 1e-8) { if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("OPTIMAL SOLUTION FOUND\n"); status = 0; break; } /* check if the problem has no feasible solution */ temp = 1e5 * csa->phi_min[csa->iter]; if (temp < 1e-8) temp = 1e-8; if (csa->phi >= temp) { if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("PROBLEM HAS NO FEASIBLE PRIMAL/DUAL SOLUTION\n") ; status = 1; break; } /* check for very slow convergence or divergence */ if (((csa->rpi >= 1e-8 || csa->rdi >= 1e-8) && csa->rmu / csa->rmu0 >= 1e6) || (csa->iter >= 30 && csa->phi_min[csa->iter] >= 0.5 * csa->phi_min[csa->iter - 30])) { if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("NO CONVERGENCE; SEARCH TERMINATED\n"); status = 2; break; } /* check for maximal number of iterations */ if (csa->iter == ITER_MAX) { if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("ITERATION LIMIT EXCEEDED; SEARCH TERMINATED\n"); status = 3; break; } /* start the next iteration */ csa->iter++; /* factorize normal equation system */ for (j = 1; j <= n; j++) csa->D[j] = csa->x[j] / csa->z[j]; decomp_NE(csa); /* compute the next point using Mehrotra's predictor-corrector technique */ if (make_step(csa)) { if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("NUMERIC INSTABILITY; SEARCH TERMINATED\n"); status = 4; break; } } /* restore the best point */ if (status != 0) { for (j = 1; j <= n; j++) csa->x[j] = csa->best_x[j]; for (i = 1; i <= m; i++) csa->y[i] = csa->best_y[i]; for (j = 1; j <= n; j++) csa->z[j] = csa->best_z[j]; if (csa->parm->msg_lev >= GLP_MSG_ALL) xprintf("Best point %17.9e was reached on iteration %d\n", csa->best_obj, csa->best_iter); } /* return to the calling program */ return status; } /*********************************************************************** * NAME * * ipm_solve - core LP solver based on the interior-point method * * SYNOPSIS * * #include "glpipm.h" * int ipm_solve(glp_prob *P, const glp_iptcp *parm); * * DESCRIPTION * * The routine ipm_solve is a core LP solver based on the primal-dual * interior-point method. * * The routine assumes the following standard formulation of LP problem * to be solved: * * minimize * * F = c[0] + c[1]*x[1] + c[2]*x[2] + ... + c[n]*x[n] * * subject to linear constraints * * a[1,1]*x[1] + a[1,2]*x[2] + ... + a[1,n]*x[n] = b[1] * * a[2,1]*x[1] + a[2,2]*x[2] + ... + a[2,n]*x[n] = b[2] * * . . . . . . * * a[m,1]*x[1] + a[m,2]*x[2] + ... + a[m,n]*x[n] = b[m] * * and non-negative variables * * x[1] >= 0, x[2] >= 0, ..., x[n] >= 0 * * where: * F is the objective function; * x[1], ..., x[n] are (structural) variables; * c[0] is a constant term of the objective function; * c[1], ..., c[n] are objective coefficients; * a[1,1], ..., a[m,n] are constraint coefficients; * b[1], ..., b[n] are right-hand sides. * * The solution is three vectors x, y, and z, which are stored by the * routine in the arrays x, y, and z, respectively. These vectors * correspond to the best primal-dual point found during optimization. * They are approximate solution of the following system (which is the * Karush-Kuhn-Tucker optimality conditions): * * A*x = b (primal feasibility condition) * * A'*y + z = c (dual feasibility condition) * * x'*z = 0 (primal-dual complementarity condition) * * x >= 0, z >= 0 (non-negativity condition) * * where: * x[1], ..., x[n] are primal (structural) variables; * y[1], ..., y[m] are dual variables (Lagrange multipliers) for * equality constraints; * z[1], ..., z[n] are dual variables (Lagrange multipliers) for * non-negativity constraints. * * RETURNS * * 0 LP has been successfully solved. * * GLP_ENOCVG * No convergence. * * GLP_EITLIM * Iteration limit exceeded. * * GLP_EINSTAB * Numeric instability on solving Newtonian system. * * In case of non-zero return code the routine returns the best point, * which has been reached during optimization. */ int ipm_solve(glp_prob *P, const glp_iptcp *parm) { struct csa _dsa, *csa = &_dsa; int m = P->m; int n = P->n; int nnz = P->nnz; GLPROW *row; GLPCOL *col; GLPAIJ *aij; int i, j, loc, ret, *A_ind, *A_ptr; double dir, *A_val, *b, *c, *x, *y, *z; xassert(m > 0); xassert(n > 0); /* allocate working arrays */ A_ptr = xcalloc(1+m+1, sizeof(int)); A_ind = xcalloc(1+nnz, sizeof(int)); A_val = xcalloc(1+nnz, sizeof(double)); b = xcalloc(1+m, sizeof(double)); c = xcalloc(1+n, sizeof(double)); x = xcalloc(1+n, sizeof(double)); y = xcalloc(1+m, sizeof(double)); z = xcalloc(1+n, sizeof(double)); /* prepare rows and constraint coefficients */ loc = 1; for (i = 1; i <= m; i++) { row = P->row[i]; xassert(row->type == GLP_FX); b[i] = row->lb * row->rii; A_ptr[i] = loc; for (aij = row->ptr; aij != NULL; aij = aij->r_next) { A_ind[loc] = aij->col->j; A_val[loc] = row->rii * aij->val * aij->col->sjj; loc++; } } A_ptr[m+1] = loc; xassert(loc-1 == nnz); /* prepare columns and objective coefficients */ if (P->dir == GLP_MIN) dir = +1.0; else if (P->dir == GLP_MAX) dir = -1.0; else xassert(P != P); c[0] = dir * P->c0; for (j = 1; j <= n; j++) { col = P->col[j]; xassert(col->type == GLP_LO && col->lb == 0.0); c[j] = dir * col->coef * col->sjj; } /* allocate and initialize the common storage area */ csa->m = m; csa->n = n; csa->A_ptr = A_ptr; csa->A_ind = A_ind; csa->A_val = A_val; csa->b = b; csa->c = c; csa->x = x; csa->y = y; csa->z = z; csa->parm = parm; initialize(csa); /* solve LP with the interior-point method */ ret = ipm_main(csa); /* deallocate the common storage area */ terminate(csa); /* determine solution status */ if (ret == 0) { /* optimal solution found */ P->ipt_stat = GLP_OPT; ret = 0; } else if (ret == 1) { /* problem has no feasible (primal or dual) solution */ P->ipt_stat = GLP_NOFEAS; ret = 0; } else if (ret == 2) { /* no convergence */ P->ipt_stat = GLP_INFEAS; ret = GLP_ENOCVG; } else if (ret == 3) { /* iteration limit exceeded */ P->ipt_stat = GLP_INFEAS; ret = GLP_EITLIM; } else if (ret == 4) { /* numeric instability on solving Newtonian system */ P->ipt_stat = GLP_INFEAS; ret = GLP_EINSTAB; } else xassert(ret != ret); /* store row solution components */ for (i = 1; i <= m; i++) { row = P->row[i]; row->pval = row->lb; row->dval = dir * y[i] * row->rii; } /* store column solution components */ P->ipt_obj = P->c0; for (j = 1; j <= n; j++) { col = P->col[j]; col->pval = x[j] * col->sjj; col->dval = dir * z[j] / col->sjj; P->ipt_obj += col->coef * col->pval; } /* free working arrays */ xfree(A_ptr); xfree(A_ind); xfree(A_val); xfree(b); xfree(c); xfree(x); xfree(y); xfree(z); return ret; } /* eof */ sources_5316/external/glpk/amd_dump.c0000644000176700017670000001400111401660400016420 0ustar paulpaul/* ========================================================================= */ /* === AMD_dump ============================================================ */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* Debugging routines for AMD. Not used if NDEBUG is not defined at compile- * time (the default). See comments in amd_internal.h on how to enable * debugging. Not user-callable. */ #include "amd_internal.h" #ifndef NDEBUG /* This global variable is present only when debugging */ GLOBAL Int AMD_debug = -999 ; /* default is no debug printing */ /* ========================================================================= */ /* === AMD_debug_init ====================================================== */ /* ========================================================================= */ /* Sets the debug print level, by reading the file debug.amd (if it exists) */ GLOBAL void AMD_debug_init ( char *s ) { FILE *f ; f = fopen ("debug.amd", "r") ; if (f == (FILE *) NULL) { AMD_debug = -999 ; } else { fscanf (f, ID, &AMD_debug) ; fclose (f) ; } if (AMD_debug >= 0) { printf ("%s: AMD_debug_init, D= "ID"\n", s, AMD_debug) ; } } /* ========================================================================= */ /* === AMD_dump ============================================================ */ /* ========================================================================= */ /* Dump AMD's data structure, except for the hash buckets. This routine * cannot be called when the hash buckets are non-empty. */ GLOBAL void AMD_dump ( Int n, /* A is n-by-n */ Int Pe [ ], /* pe [0..n-1]: index in iw of start of row i */ Int Iw [ ], /* workspace of size iwlen, iwlen [0..pfree-1] * holds the matrix on input */ Int Len [ ], /* len [0..n-1]: length for row i */ Int iwlen, /* length of iw */ Int pfree, /* iw [pfree ... iwlen-1] is empty on input */ Int Nv [ ], /* nv [0..n-1] */ Int Next [ ], /* next [0..n-1] */ Int Last [ ], /* last [0..n-1] */ Int Head [ ], /* head [0..n-1] */ Int Elen [ ], /* size n */ Int Degree [ ], /* size n */ Int W [ ], /* size n */ Int nel ) { Int i, pe, elen, nv, len, e, p, k, j, deg, w, cnt, ilast ; if (AMD_debug < 0) return ; ASSERT (pfree <= iwlen) ; AMD_DEBUG3 (("\nAMD dump, pfree: "ID"\n", pfree)) ; for (i = 0 ; i < n ; i++) { pe = Pe [i] ; elen = Elen [i] ; nv = Nv [i] ; len = Len [i] ; w = W [i] ; if (elen >= EMPTY) { if (nv == 0) { AMD_DEBUG3 (("\nI "ID": nonprincipal: ", i)) ; ASSERT (elen == EMPTY) ; if (pe == EMPTY) { AMD_DEBUG3 ((" dense node\n")) ; ASSERT (w == 1) ; } else { ASSERT (pe < EMPTY) ; AMD_DEBUG3 ((" i "ID" -> parent "ID"\n", i, FLIP (Pe[i]))); } } else { AMD_DEBUG3 (("\nI "ID": active principal supervariable:\n",i)); AMD_DEBUG3 ((" nv(i): "ID" Flag: %d\n", nv, (nv < 0))) ; ASSERT (elen >= 0) ; ASSERT (nv > 0 && pe >= 0) ; p = pe ; AMD_DEBUG3 ((" e/s: ")) ; if (elen == 0) AMD_DEBUG3 ((" : ")) ; ASSERT (pe + len <= pfree) ; for (k = 0 ; k < len ; k++) { j = Iw [p] ; AMD_DEBUG3 ((" "ID"", j)) ; ASSERT (j >= 0 && j < n) ; if (k == elen-1) AMD_DEBUG3 ((" : ")) ; p++ ; } AMD_DEBUG3 (("\n")) ; } } else { e = i ; if (w == 0) { AMD_DEBUG3 (("\nE "ID": absorbed element: w "ID"\n", e, w)) ; ASSERT (nv > 0 && pe < 0) ; AMD_DEBUG3 ((" e "ID" -> parent "ID"\n", e, FLIP (Pe [e]))) ; } else { AMD_DEBUG3 (("\nE "ID": unabsorbed element: w "ID"\n", e, w)) ; ASSERT (nv > 0 && pe >= 0) ; p = pe ; AMD_DEBUG3 ((" : ")) ; ASSERT (pe + len <= pfree) ; for (k = 0 ; k < len ; k++) { j = Iw [p] ; AMD_DEBUG3 ((" "ID"", j)) ; ASSERT (j >= 0 && j < n) ; p++ ; } AMD_DEBUG3 (("\n")) ; } } } /* this routine cannot be called when the hash buckets are non-empty */ AMD_DEBUG3 (("\nDegree lists:\n")) ; if (nel >= 0) { cnt = 0 ; for (deg = 0 ; deg < n ; deg++) { if (Head [deg] == EMPTY) continue ; ilast = EMPTY ; AMD_DEBUG3 ((ID": \n", deg)) ; for (i = Head [deg] ; i != EMPTY ; i = Next [i]) { AMD_DEBUG3 ((" "ID" : next "ID" last "ID" deg "ID"\n", i, Next [i], Last [i], Degree [i])) ; ASSERT (i >= 0 && i < n && ilast == Last [i] && deg == Degree [i]) ; cnt += Nv [i] ; ilast = i ; } AMD_DEBUG3 (("\n")) ; } ASSERT (cnt == n - nel) ; } } #endif sources_5316/external/glpk/glpbfx.c0000644000176700017670000000513311401660400016122 0ustar paulpaul/* glpbfx.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ typedef struct BFX BFX; #define GLPBFX_DEFINED #include "glpbfx.h" #include "glpenv.h" #include "glplux.h" struct BFX { int valid; LUX *lux; }; BFX *bfx_create_binv(void) { /* create factorization of the basis matrix */ BFX *bfx; bfx = xmalloc(sizeof(BFX)); bfx->valid = 0; bfx->lux = NULL; return bfx; } int bfx_factorize(BFX *binv, int m, int (*col)(void *info, int j, int ind[], mpq_t val[]), void *info) { /* compute factorization of the basis matrix */ int ret; xassert(m > 0); if (binv->lux != NULL && binv->lux->n != m) { lux_delete(binv->lux); binv->lux = NULL; } if (binv->lux == NULL) binv->lux = lux_create(m); ret = lux_decomp(binv->lux, col, info); binv->valid = (ret == 0); return ret; } void bfx_ftran(BFX *binv, mpq_t x[], int save) { /* perform forward transformation (FTRAN) */ xassert(binv->valid); lux_solve(binv->lux, 0, x); xassert(save == save); return; } void bfx_btran(BFX *binv, mpq_t x[]) { /* perform backward transformation (BTRAN) */ xassert(binv->valid); lux_solve(binv->lux, 1, x); return; } int bfx_update(BFX *binv, int j) { /* update factorization of the basis matrix */ xassert(binv->valid); xassert(1 <= j && j <= binv->lux->n); return 1; } void bfx_delete_binv(BFX *binv) { /* delete factorization of the basis matrix */ if (binv->lux != NULL) lux_delete(binv->lux); xfree(binv); return; } /* eof */ sources_5316/external/glpk/glprng01.c0000644000176700017670000001413311401660400016272 0ustar paulpaul/* glprng01.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * This code is a modified version of the module GB_FLIP, a portable * pseudo-random number generator. The original version of GB_FLIP is * a part of The Stanford GraphBase developed by Donald E. Knuth (see * http://www-cs-staff.stanford.edu/~knuth/sgb.html). * * Note that all changes concern only external names, so this modified * version produces exactly the same results as the original version. * * Changes were made by Andrew Makhorin . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glprng.h" #if 0 int A[56] = { -1 }; #else #define A (rand->A) #endif /* pseudo-random values */ #if 0 int *fptr = A; #else #define fptr (rand->fptr) #endif /* the next A value to be exported */ #define mod_diff(x, y) (((x) - (y)) & 0x7FFFFFFF) /* difference modulo 2^31 */ static int flip_cycle(RNG *rand) { /* this is an auxiliary routine to do 55 more steps of the basic recurrence, at high speed, and to reset fptr */ int *ii, *jj; for (ii = &A[1], jj = &A[32]; jj <= &A[55]; ii++, jj++) *ii = mod_diff(*ii, *jj); for (jj = &A[1]; ii <= &A[55]; ii++, jj++) *ii = mod_diff(*ii, *jj); fptr = &A[54]; return A[55]; } /*********************************************************************** * NAME * * rng_create_rand - create pseudo-random number generator * * SYNOPSIS * * #include "glprng.h" * RNG *rng_create_rand(void); * * DESCRIPTION * * The routine rng_create_rand creates and initializes a pseudo-random * number generator. * * RETURNS * * The routine returns a pointer to the generator created. */ RNG *rng_create_rand(void) { RNG *rand; int i; rand = xmalloc(sizeof(RNG)); A[0] = -1; for (i = 1; i <= 55; i++) A[i] = 0; fptr = A; rng_init_rand(rand, 1); return rand; } /*********************************************************************** * NAME * * rng_init_rand - initialize pseudo-random number generator * * SYNOPSIS * * #include "glprng.h" * void rng_init_rand(RNG *rand, int seed); * * DESCRIPTION * * The routine rng_init_rand initializes the pseudo-random number * generator. The parameter seed may be any integer number. Note that * on creating the generator this routine is called with the parameter * seed equal to 1. */ void rng_init_rand(RNG *rand, int seed) { int i; int prev = seed, next = 1; seed = prev = mod_diff(prev, 0); A[55] = prev; for (i = 21; i; i = (i + 21) % 55) { A[i] = next; next = mod_diff(prev, next); if (seed & 1) seed = 0x40000000 + (seed >> 1); else seed >>= 1; next = mod_diff(next, seed); prev = A[i]; } flip_cycle(rand); flip_cycle(rand); flip_cycle(rand); flip_cycle(rand); flip_cycle(rand); return; } /*********************************************************************** * NAME * * rng_next_rand - obtain pseudo-random integer in the range [0, 2^31-1] * * SYNOPSIS * * #include "glprng.h" * int rng_next_rand(RNG *rand); * * RETURNS * * The routine rng_next_rand returns a next pseudo-random integer which * is uniformly distributed between 0 and 2^31-1, inclusive. The period * length of the generated numbers is 2^85 - 2^30. The low order bits of * the generated numbers are just as random as the high-order bits. */ int rng_next_rand(RNG *rand) { return *fptr >= 0 ? *fptr-- : flip_cycle(rand); } /*********************************************************************** * NAME * * rng_unif_rand - obtain pseudo-random integer in the range [0, m-1] * * SYNOPSIS * * #include "glprng.h" * int rng_unif_rand(RNG *rand, int m); * * RETURNS * * The routine rng_unif_rand returns a next pseudo-random integer which * is uniformly distributed between 0 and m-1, inclusive, where m is any * positive integer less than 2^31. */ #define two_to_the_31 ((unsigned int)0x80000000) int rng_unif_rand(RNG *rand, int m) { unsigned int t = two_to_the_31 - (two_to_the_31 % m); int r; xassert(m > 0); do { r = rng_next_rand(rand); } while (t <= (unsigned int)r); return r % m; } /*********************************************************************** * NAME * * rng_delete_rand - delete pseudo-random number generator * * SYNOPSIS * * #include "glprng.h" * void rng_delete_rand(RNG *rand); * * DESCRIPTION * * The routine rng_delete_rand frees all the memory allocated to the * specified pseudo-random number generator. */ void rng_delete_rand(RNG *rand) { xfree(rand); return; } /**********************************************************************/ #if 0 /* To be sure that this modified version produces the same results as the original version, run this validation program. */ int main(void) { RNG *rand; int j; rand = rng_create_rand(); rng_init_rand(rand, -314159); if (rng_next_rand(rand) != 119318998) { fprintf(stderr, "Failure on the first try!\n"); return -1; } for (j = 1; j <= 133; j++) rng_next_rand(rand); if (rng_unif_rand(rand, 0x55555555) != 748103812) { fprintf(stderr, "Failure on the second try!\n"); return -2; } fprintf(stderr, "OK, the random-number generator routines seem to" " work!\n"); rng_delete_rand(rand); return 0; } #endif /* eof */ sources_5316/external/glpk/glpmat.h0000644000176700017670000001646011401660400016136 0ustar paulpaul/* glpmat.h (linear algebra routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPMAT_H #define GLPMAT_H /*********************************************************************** * FULL-VECTOR STORAGE * * For a sparse vector x having n elements, ne of which are non-zero, * the full-vector storage format uses two arrays x_ind and x_vec, which * are set up as follows: * * x_ind is an integer array of length [1+ne]. Location x_ind[0] is * not used, and locations x_ind[1], ..., x_ind[ne] contain indices of * non-zero elements in vector x. * * x_vec is a floating-point array of length [1+n]. Location x_vec[0] * is not used, and locations x_vec[1], ..., x_vec[n] contain numeric * values of ALL elements in vector x, including its zero elements. * * Let, for example, the following sparse vector x be given: * * (0, 1, 0, 0, 2, 3, 0, 4) * * Then the arrays are: * * x_ind = { X; 2, 5, 6, 8 } * * x_vec = { X; 0, 1, 0, 0, 2, 3, 0, 4 } * * COMPRESSED-VECTOR STORAGE * * For a sparse vector x having n elements, ne of which are non-zero, * the compressed-vector storage format uses two arrays x_ind and x_vec, * which are set up as follows: * * x_ind is an integer array of length [1+ne]. Location x_ind[0] is * not used, and locations x_ind[1], ..., x_ind[ne] contain indices of * non-zero elements in vector x. * * x_vec is a floating-point array of length [1+ne]. Location x_vec[0] * is not used, and locations x_vec[1], ..., x_vec[ne] contain numeric * values of corresponding non-zero elements in vector x. * * Let, for example, the following sparse vector x be given: * * (0, 1, 0, 0, 2, 3, 0, 4) * * Then the arrays are: * * x_ind = { X; 2, 5, 6, 8 } * * x_vec = { X; 1, 2, 3, 4 } * * STORAGE-BY-ROWS * * For a sparse matrix A, which has m rows, n columns, and ne non-zero * elements the storage-by-rows format uses three arrays A_ptr, A_ind, * and A_val, which are set up as follows: * * A_ptr is an integer array of length [1+m+1] also called "row pointer * array". It contains the relative starting positions of each row of A * in the arrays A_ind and A_val, i.e. element A_ptr[i], 1 <= i <= m, * indicates where row i begins in the arrays A_ind and A_val. If all * elements in row i are zero, then A_ptr[i] = A_ptr[i+1]. Location * A_ptr[0] is not used, location A_ptr[1] must contain 1, and location * A_ptr[m+1] must contain ne+1 that indicates the position after the * last element in the arrays A_ind and A_val. * * A_ind is an integer array of length [1+ne]. Location A_ind[0] is not * used, and locations A_ind[1], ..., A_ind[ne] contain column indices * of (non-zero) elements in matrix A. * * A_val is a floating-point array of length [1+ne]. Location A_val[0] * is not used, and locations A_val[1], ..., A_val[ne] contain numeric * values of non-zero elements in matrix A. * * Non-zero elements of matrix A are stored contiguously, and the rows * of matrix A are stored consecutively from 1 to m in the arrays A_ind * and A_val. The elements in each row of A may be stored in any order * in A_ind and A_val. Note that elements with duplicate column indices * are not allowed. * * Let, for example, the following sparse matrix A be given: * * | 11 . 13 . . . | * | 21 22 . 24 . . | * | . 32 33 . . . | * | . . 43 44 . 46 | * | . . . . . . | * | 61 62 . . . 66 | * * Then the arrays are: * * A_ptr = { X; 1, 3, 6, 8, 11, 11; 14 } * * A_ind = { X; 1, 3; 4, 2, 1; 2, 3; 4, 3, 6; 1, 2, 6 } * * A_val = { X; 11, 13; 24, 22, 21; 32, 33; 44, 43, 46; 61, 62, 66 } * * PERMUTATION MATRICES * * Let P be a permutation matrix of the order n. It is represented as * an integer array P_per of length [1+n+n] as follows: if p[i,j] = 1, * then P_per[i] = j and P_per[n+j] = i. Location P_per[0] is not used. * * Let A' = P*A. If i-th row of A corresponds to i'-th row of A', then * P_per[i'] = i and P_per[n+i] = i'. * * References: * * 1. Gustavson F.G. Some basic techniques for solving sparse systems of * linear equations. In Rose and Willoughby (1972), pp. 41-52. * * 2. Basic Linear Algebra Subprograms Technical (BLAST) Forum Standard. * University of Tennessee (2001). */ #define check_fvs _glp_mat_check_fvs int check_fvs(int n, int nnz, int ind[], double vec[]); /* check sparse vector in full-vector storage format */ #define check_pattern _glp_mat_check_pattern int check_pattern(int m, int n, int A_ptr[], int A_ind[]); /* check pattern of sparse matrix */ #define transpose _glp_mat_transpose void transpose(int m, int n, int A_ptr[], int A_ind[], double A_val[], int AT_ptr[], int AT_ind[], double AT_val[]); /* transpose sparse matrix */ #define adat_symbolic _glp_mat_adat_symbolic int *adat_symbolic(int m, int n, int P_per[], int A_ptr[], int A_ind[], int S_ptr[]); /* compute S = P*A*D*A'*P' (symbolic phase) */ #define adat_numeric _glp_mat_adat_numeric void adat_numeric(int m, int n, int P_per[], int A_ptr[], int A_ind[], double A_val[], double D_diag[], int S_ptr[], int S_ind[], double S_val[], double S_diag[]); /* compute S = P*A*D*A'*P' (numeric phase) */ #define min_degree _glp_mat_min_degree void min_degree(int n, int A_ptr[], int A_ind[], int P_per[]); /* minimum degree ordering */ #define amd_order1 _glp_mat_amd_order1 void amd_order1(int n, int A_ptr[], int A_ind[], int P_per[]); /* approximate minimum degree ordering (AMD) */ #define symamd_ord _glp_mat_symamd_ord void symamd_ord(int n, int A_ptr[], int A_ind[], int P_per[]); /* approximate minimum degree ordering (SYMAMD) */ #define chol_symbolic _glp_mat_chol_symbolic int *chol_symbolic(int n, int A_ptr[], int A_ind[], int U_ptr[]); /* compute Cholesky factorization (symbolic phase) */ #define chol_numeric _glp_mat_chol_numeric int chol_numeric(int n, int A_ptr[], int A_ind[], double A_val[], double A_diag[], int U_ptr[], int U_ind[], double U_val[], double U_diag[]); /* compute Cholesky factorization (numeric phase) */ #define u_solve _glp_mat_u_solve void u_solve(int n, int U_ptr[], int U_ind[], double U_val[], double U_diag[], double x[]); /* solve upper triangular system U*x = b */ #define ut_solve _glp_mat_ut_solve void ut_solve(int n, int U_ptr[], int U_ind[], double U_val[], double U_diag[], double x[]); /* solve lower triangular system U'*x = b */ #endif /* eof */ sources_5316/external/glpk/glpapi17.c0000644000176700017670000010376711401660400016300 0ustar paulpaul/* glpapi17.c (flow network problems) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" #include "glpnet.h" /*********************************************************************** * NAME * * glp_mincost_lp - convert minimum cost flow problem to LP * * SYNOPSIS * * void glp_mincost_lp(glp_prob *lp, glp_graph *G, int names, * int v_rhs, int a_low, int a_cap, int a_cost); * * DESCRIPTION * * The routine glp_mincost_lp builds an LP problem, which corresponds * to the minimum cost flow problem on the specified network G. */ void glp_mincost_lp(glp_prob *lp, glp_graph *G, int names, int v_rhs, int a_low, int a_cap, int a_cost) { glp_vertex *v; glp_arc *a; int i, j, type, ind[1+2]; double rhs, low, cap, cost, val[1+2]; if (!(names == GLP_ON || names == GLP_OFF)) xerror("glp_mincost_lp: names = %d; invalid parameter\n", names); if (v_rhs >= 0 && v_rhs > G->v_size - (int)sizeof(double)) xerror("glp_mincost_lp: v_rhs = %d; invalid offset\n", v_rhs); if (a_low >= 0 && a_low > G->a_size - (int)sizeof(double)) xerror("glp_mincost_lp: a_low = %d; invalid offset\n", a_low); if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_mincost_lp: a_cap = %d; invalid offset\n", a_cap); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_mincost_lp: a_cost = %d; invalid offset\n", a_cost) ; glp_erase_prob(lp); if (names) glp_set_prob_name(lp, G->name); if (G->nv > 0) glp_add_rows(lp, G->nv); for (i = 1; i <= G->nv; i++) { v = G->v[i]; if (names) glp_set_row_name(lp, i, v->name); if (v_rhs >= 0) memcpy(&rhs, (char *)v->data + v_rhs, sizeof(double)); else rhs = 0.0; glp_set_row_bnds(lp, i, GLP_FX, rhs, rhs); } if (G->na > 0) glp_add_cols(lp, G->na); for (i = 1, j = 0; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { j++; if (names) { char name[50+1]; sprintf(name, "x[%d,%d]", a->tail->i, a->head->i); xassert(strlen(name) < sizeof(name)); glp_set_col_name(lp, j, name); } if (a->tail->i != a->head->i) { ind[1] = a->tail->i, val[1] = +1.0; ind[2] = a->head->i, val[2] = -1.0; glp_set_mat_col(lp, j, 2, ind, val); } if (a_low >= 0) memcpy(&low, (char *)a->data + a_low, sizeof(double)); else low = 0.0; if (a_cap >= 0) memcpy(&cap, (char *)a->data + a_cap, sizeof(double)); else cap = 1.0; if (cap == DBL_MAX) type = GLP_LO; else if (low != cap) type = GLP_DB; else type = GLP_FX; glp_set_col_bnds(lp, j, type, low, cap); if (a_cost >= 0) memcpy(&cost, (char *)a->data + a_cost, sizeof(double)); else cost = 0.0; glp_set_obj_coef(lp, j, cost); } } xassert(j == G->na); return; } /**********************************************************************/ int glp_mincost_okalg(glp_graph *G, int v_rhs, int a_low, int a_cap, int a_cost, double *sol, int a_x, int v_pi) { /* find minimum-cost flow with out-of-kilter algorithm */ glp_vertex *v; glp_arc *a; int nv, na, i, k, s, t, *tail, *head, *low, *cap, *cost, *x, *pi, ret; double sum, temp; if (v_rhs >= 0 && v_rhs > G->v_size - (int)sizeof(double)) xerror("glp_mincost_okalg: v_rhs = %d; invalid offset\n", v_rhs); if (a_low >= 0 && a_low > G->a_size - (int)sizeof(double)) xerror("glp_mincost_okalg: a_low = %d; invalid offset\n", a_low); if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_mincost_okalg: a_cap = %d; invalid offset\n", a_cap); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_mincost_okalg: a_cost = %d; invalid offset\n", a_cost); if (a_x >= 0 && a_x > G->a_size - (int)sizeof(double)) xerror("glp_mincost_okalg: a_x = %d; invalid offset\n", a_x); if (v_pi >= 0 && v_pi > G->v_size - (int)sizeof(double)) xerror("glp_mincost_okalg: v_pi = %d; invalid offset\n", v_pi); /* s is artificial source node */ s = G->nv + 1; /* t is artificial sink node */ t = s + 1; /* nv is the total number of nodes in the resulting network */ nv = t; /* na is the total number of arcs in the resulting network */ na = G->na + 1; for (i = 1; i <= G->nv; i++) { v = G->v[i]; if (v_rhs >= 0) memcpy(&temp, (char *)v->data + v_rhs, sizeof(double)); else temp = 0.0; if (temp != 0.0) na++; } /* allocate working arrays */ tail = xcalloc(1+na, sizeof(int)); head = xcalloc(1+na, sizeof(int)); low = xcalloc(1+na, sizeof(int)); cap = xcalloc(1+na, sizeof(int)); cost = xcalloc(1+na, sizeof(int)); x = xcalloc(1+na, sizeof(int)); pi = xcalloc(1+nv, sizeof(int)); /* construct the resulting network */ k = 0; /* (original arcs) */ for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { k++; tail[k] = a->tail->i; head[k] = a->head->i; if (tail[k] == head[k]) { ret = GLP_EDATA; goto done; } if (a_low >= 0) memcpy(&temp, (char *)a->data + a_low, sizeof(double)); else temp = 0.0; if (!(0.0 <= temp && temp <= (double)INT_MAX && temp == floor(temp))) { ret = GLP_EDATA; goto done; } low[k] = (int)temp; if (a_cap >= 0) memcpy(&temp, (char *)a->data + a_cap, sizeof(double)); else temp = 1.0; if (!((double)low[k] <= temp && temp <= (double)INT_MAX && temp == floor(temp))) { ret = GLP_EDATA; goto done; } cap[k] = (int)temp; if (a_cost >= 0) memcpy(&temp, (char *)a->data + a_cost, sizeof(double)); else temp = 0.0; if (!(fabs(temp) <= (double)INT_MAX && temp == floor(temp))) { ret = GLP_EDATA; goto done; } cost[k] = (int)temp; } } /* (artificial arcs) */ sum = 0.0; for (i = 1; i <= G->nv; i++) { v = G->v[i]; if (v_rhs >= 0) memcpy(&temp, (char *)v->data + v_rhs, sizeof(double)); else temp = 0.0; if (!(fabs(temp) <= (double)INT_MAX && temp == floor(temp))) { ret = GLP_EDATA; goto done; } if (temp > 0.0) { /* artificial arc from s to original source i */ k++; tail[k] = s; head[k] = i; low[k] = cap[k] = (int)(+temp); /* supply */ cost[k] = 0; sum += (double)temp; } else if (temp < 0.0) { /* artificial arc from original sink i to t */ k++; tail[k] = i; head[k] = t; low[k] = cap[k] = (int)(-temp); /* demand */ cost[k] = 0; } } /* (feedback arc from t to s) */ k++; xassert(k == na); tail[k] = t; head[k] = s; if (sum > (double)INT_MAX) { ret = GLP_EDATA; goto done; } low[k] = cap[k] = (int)sum; /* total supply/demand */ cost[k] = 0; /* find minimal-cost circulation in the resulting network */ ret = okalg(nv, na, tail, head, low, cap, cost, x, pi); switch (ret) { case 0: /* optimal circulation found */ ret = 0; break; case 1: /* no feasible circulation exists */ ret = GLP_ENOPFS; break; case 2: /* integer overflow occured */ ret = GLP_ERANGE; goto done; case 3: /* optimality test failed (logic error) */ ret = GLP_EFAIL; goto done; default: xassert(ret != ret); } /* store solution components */ /* (objective function = the total cost) */ if (sol != NULL) { temp = 0.0; for (k = 1; k <= na; k++) temp += (double)cost[k] * (double)x[k]; *sol = temp; } /* (arc flows) */ if (a_x >= 0) { k = 0; for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { temp = (double)x[++k]; memcpy((char *)a->data + a_x, &temp, sizeof(double)); } } } /* (node potentials = Lagrange multipliers) */ if (v_pi >= 0) { for (i = 1; i <= G->nv; i++) { v = G->v[i]; temp = - (double)pi[i]; memcpy((char *)v->data + v_pi, &temp, sizeof(double)); } } done: /* free working arrays */ xfree(tail); xfree(head); xfree(low); xfree(cap); xfree(cost); xfree(x); xfree(pi); return ret; } /*********************************************************************** * NAME * * glp_maxflow_lp - convert maximum flow problem to LP * * SYNOPSIS * * void glp_maxflow_lp(glp_prob *lp, glp_graph *G, int names, int s, * int t, int a_cap); * * DESCRIPTION * * The routine glp_maxflow_lp builds an LP problem, which corresponds * to the maximum flow problem on the specified network G. */ void glp_maxflow_lp(glp_prob *lp, glp_graph *G, int names, int s, int t, int a_cap) { glp_vertex *v; glp_arc *a; int i, j, type, ind[1+2]; double cap, val[1+2]; if (!(names == GLP_ON || names == GLP_OFF)) xerror("glp_maxflow_lp: names = %d; invalid parameter\n", names); if (!(1 <= s && s <= G->nv)) xerror("glp_maxflow_lp: s = %d; source node number out of rang" "e\n", s); if (!(1 <= t && t <= G->nv)) xerror("glp_maxflow_lp: t = %d: sink node number out of range " "\n", t); if (s == t) xerror("glp_maxflow_lp: s = t = %d; source and sink nodes must" " be distinct\n", s); if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_maxflow_lp: a_cap = %d; invalid offset\n", a_cap); glp_erase_prob(lp); if (names) glp_set_prob_name(lp, G->name); glp_set_obj_dir(lp, GLP_MAX); glp_add_rows(lp, G->nv); for (i = 1; i <= G->nv; i++) { v = G->v[i]; if (names) glp_set_row_name(lp, i, v->name); if (i == s) type = GLP_LO; else if (i == t) type = GLP_UP; else type = GLP_FX; glp_set_row_bnds(lp, i, type, 0.0, 0.0); } if (G->na > 0) glp_add_cols(lp, G->na); for (i = 1, j = 0; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { j++; if (names) { char name[50+1]; sprintf(name, "x[%d,%d]", a->tail->i, a->head->i); xassert(strlen(name) < sizeof(name)); glp_set_col_name(lp, j, name); } if (a->tail->i != a->head->i) { ind[1] = a->tail->i, val[1] = +1.0; ind[2] = a->head->i, val[2] = -1.0; glp_set_mat_col(lp, j, 2, ind, val); } if (a_cap >= 0) memcpy(&cap, (char *)a->data + a_cap, sizeof(double)); else cap = 1.0; if (cap == DBL_MAX) type = GLP_LO; else if (cap != 0.0) type = GLP_DB; else type = GLP_FX; glp_set_col_bnds(lp, j, type, 0.0, cap); if (a->tail->i == s) glp_set_obj_coef(lp, j, +1.0); else if (a->head->i == s) glp_set_obj_coef(lp, j, -1.0); } } xassert(j == G->na); return; } int glp_maxflow_ffalg(glp_graph *G, int s, int t, int a_cap, double *sol, int a_x, int v_cut) { /* find maximal flow with Ford-Fulkerson algorithm */ glp_vertex *v; glp_arc *a; int nv, na, i, k, flag, *tail, *head, *cap, *x, ret; char *cut; double temp; if (!(1 <= s && s <= G->nv)) xerror("glp_maxflow_ffalg: s = %d; source node number out of r" "ange\n", s); if (!(1 <= t && t <= G->nv)) xerror("glp_maxflow_ffalg: t = %d: sink node number out of ran" "ge\n", t); if (s == t) xerror("glp_maxflow_ffalg: s = t = %d; source and sink nodes m" "ust be distinct\n", s); if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_maxflow_ffalg: a_cap = %d; invalid offset\n", a_cap); if (v_cut >= 0 && v_cut > G->v_size - (int)sizeof(int)) xerror("glp_maxflow_ffalg: v_cut = %d; invalid offset\n", v_cut); /* allocate working arrays */ nv = G->nv; na = G->na; tail = xcalloc(1+na, sizeof(int)); head = xcalloc(1+na, sizeof(int)); cap = xcalloc(1+na, sizeof(int)); x = xcalloc(1+na, sizeof(int)); if (v_cut < 0) cut = NULL; else cut = xcalloc(1+nv, sizeof(char)); /* copy the flow network */ k = 0; for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { k++; tail[k] = a->tail->i; head[k] = a->head->i; if (tail[k] == head[k]) { ret = GLP_EDATA; goto done; } if (a_cap >= 0) memcpy(&temp, (char *)a->data + a_cap, sizeof(double)); else temp = 1.0; if (!(0.0 <= temp && temp <= (double)INT_MAX && temp == floor(temp))) { ret = GLP_EDATA; goto done; } cap[k] = (int)temp; } } xassert(k == na); /* find maximal flow in the flow network */ ffalg(nv, na, tail, head, s, t, cap, x, cut); ret = 0; /* store solution components */ /* (objective function = total flow through the network) */ if (sol != NULL) { temp = 0.0; for (k = 1; k <= na; k++) { if (tail[k] == s) temp += (double)x[k]; else if (head[k] == s) temp -= (double)x[k]; } *sol = temp; } /* (arc flows) */ if (a_x >= 0) { k = 0; for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { temp = (double)x[++k]; memcpy((char *)a->data + a_x, &temp, sizeof(double)); } } } /* (node flags) */ if (v_cut >= 0) { for (i = 1; i <= G->nv; i++) { v = G->v[i]; flag = cut[i]; memcpy((char *)v->data + v_cut, &flag, sizeof(int)); } } done: /* free working arrays */ xfree(tail); xfree(head); xfree(cap); xfree(x); if (cut != NULL) xfree(cut); return ret; } /*********************************************************************** * NAME * * glp_check_asnprob - check correctness of assignment problem data * * SYNOPSIS * * int glp_check_asnprob(glp_graph *G, int v_set); * * RETURNS * * If the specified assignment problem data are correct, the routine * glp_check_asnprob returns zero, otherwise, non-zero. */ int glp_check_asnprob(glp_graph *G, int v_set) { glp_vertex *v; int i, k, ret = 0; if (v_set >= 0 && v_set > G->v_size - (int)sizeof(int)) xerror("glp_check_asnprob: v_set = %d; invalid offset\n", v_set); for (i = 1; i <= G->nv; i++) { v = G->v[i]; if (v_set >= 0) { memcpy(&k, (char *)v->data + v_set, sizeof(int)); if (k == 0) { if (v->in != NULL) { ret = 1; break; } } else if (k == 1) { if (v->out != NULL) { ret = 2; break; } } else { ret = 3; break; } } else { if (v->in != NULL && v->out != NULL) { ret = 4; break; } } } return ret; } /*********************************************************************** * NAME * * glp_asnprob_lp - convert assignment problem to LP * * SYNOPSIS * * int glp_asnprob_lp(glp_prob *P, int form, glp_graph *G, int names, * int v_set, int a_cost); * * DESCRIPTION * * The routine glp_asnprob_lp builds an LP problem, which corresponds * to the assignment problem on the specified graph G. * * RETURNS * * If the LP problem has been successfully built, the routine returns * zero, otherwise, non-zero. */ int glp_asnprob_lp(glp_prob *P, int form, glp_graph *G, int names, int v_set, int a_cost) { glp_vertex *v; glp_arc *a; int i, j, ret, ind[1+2]; double cost, val[1+2]; if (!(form == GLP_ASN_MIN || form == GLP_ASN_MAX || form == GLP_ASN_MMP)) xerror("glp_asnprob_lp: form = %d; invalid parameter\n", form); if (!(names == GLP_ON || names == GLP_OFF)) xerror("glp_asnprob_lp: names = %d; invalid parameter\n", names); if (v_set >= 0 && v_set > G->v_size - (int)sizeof(int)) xerror("glp_asnprob_lp: v_set = %d; invalid offset\n", v_set); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_asnprob_lp: a_cost = %d; invalid offset\n", a_cost); ret = glp_check_asnprob(G, v_set); if (ret != 0) goto done; glp_erase_prob(P); if (names) glp_set_prob_name(P, G->name); glp_set_obj_dir(P, form == GLP_ASN_MIN ? GLP_MIN : GLP_MAX); if (G->nv > 0) glp_add_rows(P, G->nv); for (i = 1; i <= G->nv; i++) { v = G->v[i]; if (names) glp_set_row_name(P, i, v->name); glp_set_row_bnds(P, i, form == GLP_ASN_MMP ? GLP_UP : GLP_FX, 1.0, 1.0); } if (G->na > 0) glp_add_cols(P, G->na); for (i = 1, j = 0; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { j++; if (names) { char name[50+1]; sprintf(name, "x[%d,%d]", a->tail->i, a->head->i); xassert(strlen(name) < sizeof(name)); glp_set_col_name(P, j, name); } ind[1] = a->tail->i, val[1] = +1.0; ind[2] = a->head->i, val[2] = +1.0; glp_set_mat_col(P, j, 2, ind, val); glp_set_col_bnds(P, j, GLP_DB, 0.0, 1.0); if (a_cost >= 0) memcpy(&cost, (char *)a->data + a_cost, sizeof(double)); else cost = 1.0; glp_set_obj_coef(P, j, cost); } } xassert(j == G->na); done: return ret; } /**********************************************************************/ int glp_asnprob_okalg(int form, glp_graph *G, int v_set, int a_cost, double *sol, int a_x) { /* solve assignment problem with out-of-kilter algorithm */ glp_vertex *v; glp_arc *a; int nv, na, i, k, *tail, *head, *low, *cap, *cost, *x, *pi, ret; double temp; if (!(form == GLP_ASN_MIN || form == GLP_ASN_MAX || form == GLP_ASN_MMP)) xerror("glp_asnprob_okalg: form = %d; invalid parameter\n", form); if (v_set >= 0 && v_set > G->v_size - (int)sizeof(int)) xerror("glp_asnprob_okalg: v_set = %d; invalid offset\n", v_set); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_asnprob_okalg: a_cost = %d; invalid offset\n", a_cost); if (a_x >= 0 && a_x > G->a_size - (int)sizeof(int)) xerror("glp_asnprob_okalg: a_x = %d; invalid offset\n", a_x); if (glp_check_asnprob(G, v_set)) return GLP_EDATA; /* nv is the total number of nodes in the resulting network */ nv = G->nv + 1; /* na is the total number of arcs in the resulting network */ na = G->na + G->nv; /* allocate working arrays */ tail = xcalloc(1+na, sizeof(int)); head = xcalloc(1+na, sizeof(int)); low = xcalloc(1+na, sizeof(int)); cap = xcalloc(1+na, sizeof(int)); cost = xcalloc(1+na, sizeof(int)); x = xcalloc(1+na, sizeof(int)); pi = xcalloc(1+nv, sizeof(int)); /* construct the resulting network */ k = 0; /* (original arcs) */ for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { k++; tail[k] = a->tail->i; head[k] = a->head->i; low[k] = 0; cap[k] = 1; if (a_cost >= 0) memcpy(&temp, (char *)a->data + a_cost, sizeof(double)); else temp = 1.0; if (!(fabs(temp) <= (double)INT_MAX && temp == floor(temp))) { ret = GLP_EDATA; goto done; } cost[k] = (int)temp; if (form != GLP_ASN_MIN) cost[k] = - cost[k]; } } /* (artificial arcs) */ for (i = 1; i <= G->nv; i++) { v = G->v[i]; k++; if (v->out == NULL) tail[k] = i, head[k] = nv; else if (v->in == NULL) tail[k] = nv, head[k] = i; else xassert(v != v); low[k] = (form == GLP_ASN_MMP ? 0 : 1); cap[k] = 1; cost[k] = 0; } xassert(k == na); /* find minimal-cost circulation in the resulting network */ ret = okalg(nv, na, tail, head, low, cap, cost, x, pi); switch (ret) { case 0: /* optimal circulation found */ ret = 0; break; case 1: /* no feasible circulation exists */ ret = GLP_ENOPFS; break; case 2: /* integer overflow occured */ ret = GLP_ERANGE; goto done; case 3: /* optimality test failed (logic error) */ ret = GLP_EFAIL; goto done; default: xassert(ret != ret); } /* store solution components */ /* (objective function = the total cost) */ if (sol != NULL) { temp = 0.0; for (k = 1; k <= na; k++) temp += (double)cost[k] * (double)x[k]; if (form != GLP_ASN_MIN) temp = - temp; *sol = temp; } /* (arc flows) */ if (a_x >= 0) { k = 0; for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { k++; if (ret == 0) xassert(x[k] == 0 || x[k] == 1); memcpy((char *)a->data + a_x, &x[k], sizeof(int)); } } } done: /* free working arrays */ xfree(tail); xfree(head); xfree(low); xfree(cap); xfree(cost); xfree(x); xfree(pi); return ret; } /*********************************************************************** * NAME * * glp_asnprob_hall - find bipartite matching of maximum cardinality * * SYNOPSIS * * int glp_asnprob_hall(glp_graph *G, int v_set, int a_x); * * DESCRIPTION * * The routine glp_asnprob_hall finds a matching of maximal cardinality * in the specified bipartite graph G. It uses a version of the Fortran * routine MC21A developed by I.S.Duff [1], which implements Hall's * algorithm [2]. * * RETURNS * * The routine glp_asnprob_hall returns the cardinality of the matching * found. However, if the specified graph is incorrect (as detected by * the routine glp_check_asnprob), the routine returns negative value. * * REFERENCES * * 1. I.S.Duff, Algorithm 575: Permutations for zero-free diagonal, ACM * Trans. on Math. Softw. 7 (1981), 387-390. * * 2. M.Hall, "An Algorithm for distinct representatives," Amer. Math. * Monthly 63 (1956), 716-717. */ int glp_asnprob_hall(glp_graph *G, int v_set, int a_x) { glp_vertex *v; glp_arc *a; int card, i, k, loc, n, n1, n2, xij; int *num, *icn, *ip, *lenr, *iperm, *pr, *arp, *cv, *out; if (v_set >= 0 && v_set > G->v_size - (int)sizeof(int)) xerror("glp_asnprob_hall: v_set = %d; invalid offset\n", v_set); if (a_x >= 0 && a_x > G->a_size - (int)sizeof(int)) xerror("glp_asnprob_hall: a_x = %d; invalid offset\n", a_x); if (glp_check_asnprob(G, v_set)) return -1; /* determine the number of vertices in sets R and S and renumber vertices in S which correspond to columns of the matrix; skip all isolated vertices */ num = xcalloc(1+G->nv, sizeof(int)); n1 = n2 = 0; for (i = 1; i <= G->nv; i++) { v = G->v[i]; if (v->in == NULL && v->out != NULL) n1++, num[i] = 0; /* vertex in R */ else if (v->in != NULL && v->out == NULL) n2++, num[i] = n2; /* vertex in S */ else { xassert(v->in == NULL && v->out == NULL); num[i] = -1; /* isolated vertex */ } } /* the matrix must be square, thus, if it has more columns than rows, extra rows will be just empty, and vice versa */ n = (n1 >= n2 ? n1 : n2); /* allocate working arrays */ icn = xcalloc(1+G->na, sizeof(int)); ip = xcalloc(1+n, sizeof(int)); lenr = xcalloc(1+n, sizeof(int)); iperm = xcalloc(1+n, sizeof(int)); pr = xcalloc(1+n, sizeof(int)); arp = xcalloc(1+n, sizeof(int)); cv = xcalloc(1+n, sizeof(int)); out = xcalloc(1+n, sizeof(int)); /* build the adjacency matrix of the bipartite graph in row-wise format (rows are vertices in R, columns are vertices in S) */ k = 0, loc = 1; for (i = 1; i <= G->nv; i++) { if (num[i] != 0) continue; /* vertex i in R */ ip[++k] = loc; v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { xassert(num[a->head->i] != 0); icn[loc++] = num[a->head->i]; } lenr[k] = loc - ip[k]; } xassert(loc-1 == G->na); /* make all extra rows empty (all extra columns are empty due to the row-wise format used) */ for (k++; k <= n; k++) ip[k] = loc, lenr[k] = 0; /* find a row permutation that maximizes the number of non-zeros on the main diagonal */ card = mc21a(n, icn, ip, lenr, iperm, pr, arp, cv, out); #if 1 /* 18/II-2010 */ /* FIXED: if card = n, arp remains clobbered on exit */ for (i = 1; i <= n; i++) arp[i] = 0; for (i = 1; i <= card; i++) { k = iperm[i]; xassert(1 <= k && k <= n); xassert(arp[k] == 0); arp[k] = i; } #endif /* store solution, if necessary */ if (a_x < 0) goto skip; k = 0; for (i = 1; i <= G->nv; i++) { if (num[i] != 0) continue; /* vertex i in R */ k++; v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) { /* arp[k] is the number of matched column or zero */ if (arp[k] == num[a->head->i]) { xassert(arp[k] != 0); xij = 1; } else xij = 0; memcpy((char *)a->data + a_x, &xij, sizeof(int)); } } skip: /* free working arrays */ xfree(num); xfree(icn); xfree(ip); xfree(lenr); xfree(iperm); xfree(pr); xfree(arp); xfree(cv); xfree(out); return card; } /*********************************************************************** * NAME * * glp_cpp - solve critical path problem * * SYNOPSIS * * double glp_cpp(glp_graph *G, int v_t, int v_es, int v_ls); * * DESCRIPTION * * The routine glp_cpp solves the critical path problem represented in * the form of the project network. * * The parameter G is a pointer to the graph object, which specifies * the project network. This graph must be acyclic. Multiple arcs are * allowed being considered as single arcs. * * The parameter v_t specifies an offset of the field of type double * in the vertex data block, which contains time t[i] >= 0 needed to * perform corresponding job j. If v_t < 0, it is assumed that t[i] = 1 * for all jobs. * * The parameter v_es specifies an offset of the field of type double * in the vertex data block, to which the routine stores earliest start * time for corresponding job. If v_es < 0, this time is not stored. * * The parameter v_ls specifies an offset of the field of type double * in the vertex data block, to which the routine stores latest start * time for corresponding job. If v_ls < 0, this time is not stored. * * RETURNS * * The routine glp_cpp returns the minimal project duration, that is, * minimal time needed to perform all jobs in the project. */ static void sorting(glp_graph *G, int list[]); double glp_cpp(glp_graph *G, int v_t, int v_es, int v_ls) { glp_vertex *v; glp_arc *a; int i, j, k, nv, *list; double temp, total, *t, *es, *ls; if (v_t >= 0 && v_t > G->v_size - (int)sizeof(double)) xerror("glp_cpp: v_t = %d; invalid offset\n", v_t); if (v_es >= 0 && v_es > G->v_size - (int)sizeof(double)) xerror("glp_cpp: v_es = %d; invalid offset\n", v_es); if (v_ls >= 0 && v_ls > G->v_size - (int)sizeof(double)) xerror("glp_cpp: v_ls = %d; invalid offset\n", v_ls); nv = G->nv; if (nv == 0) { total = 0.0; goto done; } /* allocate working arrays */ t = xcalloc(1+nv, sizeof(double)); es = xcalloc(1+nv, sizeof(double)); ls = xcalloc(1+nv, sizeof(double)); list = xcalloc(1+nv, sizeof(int)); /* retrieve job times */ for (i = 1; i <= nv; i++) { v = G->v[i]; if (v_t >= 0) { memcpy(&t[i], (char *)v->data + v_t, sizeof(double)); if (t[i] < 0.0) xerror("glp_cpp: t[%d] = %g; invalid time\n", i, t[i]); } else t[i] = 1.0; } /* perform topological sorting to determine the list of nodes (jobs) such that if list[k] = i and list[kk] = j and there exists arc (i->j), then k < kk */ sorting(G, list); /* FORWARD PASS */ /* determine earliest start times */ for (k = 1; k <= nv; k++) { j = list[k]; es[j] = 0.0; for (a = G->v[j]->in; a != NULL; a = a->h_next) { i = a->tail->i; /* there exists arc (i->j) in the project network */ temp = es[i] + t[i]; if (es[j] < temp) es[j] = temp; } } /* determine the minimal project duration */ total = 0.0; for (i = 1; i <= nv; i++) { temp = es[i] + t[i]; if (total < temp) total = temp; } /* BACKWARD PASS */ /* determine latest start times */ for (k = nv; k >= 1; k--) { i = list[k]; ls[i] = total - t[i]; for (a = G->v[i]->out; a != NULL; a = a->t_next) { j = a->head->i; /* there exists arc (i->j) in the project network */ temp = ls[j] - t[i]; if (ls[i] > temp) ls[i] = temp; } /* avoid possible round-off errors */ if (ls[i] < es[i]) ls[i] = es[i]; } /* store results, if necessary */ if (v_es >= 0) { for (i = 1; i <= nv; i++) { v = G->v[i]; memcpy((char *)v->data + v_es, &es[i], sizeof(double)); } } if (v_ls >= 0) { for (i = 1; i <= nv; i++) { v = G->v[i]; memcpy((char *)v->data + v_ls, &ls[i], sizeof(double)); } } /* free working arrays */ xfree(t); xfree(es); xfree(ls); xfree(list); done: return total; } static void sorting(glp_graph *G, int list[]) { /* perform topological sorting to determine the list of nodes (jobs) such that if list[k] = i and list[kk] = j and there exists arc (i->j), then k < kk */ int i, k, nv, v_size, *num; void **save; nv = G->nv; v_size = G->v_size; save = xcalloc(1+nv, sizeof(void *)); num = xcalloc(1+nv, sizeof(int)); G->v_size = sizeof(int); for (i = 1; i <= nv; i++) { save[i] = G->v[i]->data; G->v[i]->data = &num[i]; list[i] = 0; } if (glp_top_sort(G, 0) != 0) xerror("glp_cpp: project network is not acyclic\n"); G->v_size = v_size; for (i = 1; i <= nv; i++) { G->v[i]->data = save[i]; k = num[i]; xassert(1 <= k && k <= nv); xassert(list[k] == 0); list[k] = i; } xfree(save); xfree(num); return; } /* eof */ sources_5316/external/glpk/glpapi02.c0000644000176700017670000003227111401660400016261 0ustar paulpaul/* glpapi02.c (problem retrieving routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_get_prob_name - retrieve problem name * * SYNOPSIS * * const char *glp_get_prob_name(glp_prob *lp); * * RETURNS * * The routine glp_get_prob_name returns a pointer to an internal * buffer, which contains symbolic name of the problem. However, if the * problem has no assigned name, the routine returns NULL. */ const char *glp_get_prob_name(glp_prob *lp) { char *name; name = lp->name; return name; } /*********************************************************************** * NAME * * glp_get_obj_name - retrieve objective function name * * SYNOPSIS * * const char *glp_get_obj_name(glp_prob *lp); * * RETURNS * * The routine glp_get_obj_name returns a pointer to an internal * buffer, which contains a symbolic name of the objective function. * However, if the objective function has no assigned name, the routine * returns NULL. */ const char *glp_get_obj_name(glp_prob *lp) { char *name; name = lp->obj; return name; } /*********************************************************************** * NAME * * glp_get_obj_dir - retrieve optimization direction flag * * SYNOPSIS * * int glp_get_obj_dir(glp_prob *lp); * * RETURNS * * The routine glp_get_obj_dir returns the optimization direction flag * (i.e. "sense" of the objective function): * * GLP_MIN - minimization; * GLP_MAX - maximization. */ int glp_get_obj_dir(glp_prob *lp) { int dir = lp->dir; return dir; } /*********************************************************************** * NAME * * glp_get_num_rows - retrieve number of rows * * SYNOPSIS * * int glp_get_num_rows(glp_prob *lp); * * RETURNS * * The routine glp_get_num_rows returns the current number of rows in * the specified problem object. */ int glp_get_num_rows(glp_prob *lp) { int m = lp->m; return m; } /*********************************************************************** * NAME * * glp_get_num_cols - retrieve number of columns * * SYNOPSIS * * int glp_get_num_cols(glp_prob *lp); * * RETURNS * * The routine glp_get_num_cols returns the current number of columns * in the specified problem object. */ int glp_get_num_cols(glp_prob *lp) { int n = lp->n; return n; } /*********************************************************************** * NAME * * glp_get_row_name - retrieve row name * * SYNOPSIS * * const char *glp_get_row_name(glp_prob *lp, int i); * * RETURNS * * The routine glp_get_row_name returns a pointer to an internal * buffer, which contains symbolic name of i-th row. However, if i-th * row has no assigned name, the routine returns NULL. */ const char *glp_get_row_name(glp_prob *lp, int i) { char *name; if (!(1 <= i && i <= lp->m)) xerror("glp_get_row_name: i = %d; row number out of range\n", i); name = lp->row[i]->name; return name; } /*********************************************************************** * NAME * * glp_get_col_name - retrieve column name * * SYNOPSIS * * const char *glp_get_col_name(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_col_name returns a pointer to an internal * buffer, which contains symbolic name of j-th column. However, if j-th * column has no assigned name, the routine returns NULL. */ const char *glp_get_col_name(glp_prob *lp, int j) { char *name; if (!(1 <= j && j <= lp->n)) xerror("glp_get_col_name: j = %d; column number out of range\n" , j); name = lp->col[j]->name; return name; } /*********************************************************************** * NAME * * glp_get_row_type - retrieve row type * * SYNOPSIS * * int glp_get_row_type(glp_prob *lp, int i); * * RETURNS * * The routine glp_get_row_type returns the type of i-th row, i.e. the * type of corresponding auxiliary variable, as follows: * * GLP_FR - free (unbounded) variable; * GLP_LO - variable with lower bound; * GLP_UP - variable with upper bound; * GLP_DB - double-bounded variable; * GLP_FX - fixed variable. */ int glp_get_row_type(glp_prob *lp, int i) { if (!(1 <= i && i <= lp->m)) xerror("glp_get_row_type: i = %d; row number out of range\n", i); return lp->row[i]->type; } /*********************************************************************** * NAME * * glp_get_row_lb - retrieve row lower bound * * SYNOPSIS * * double glp_get_row_lb(glp_prob *lp, int i); * * RETURNS * * The routine glp_get_row_lb returns the lower bound of i-th row, i.e. * the lower bound of corresponding auxiliary variable. However, if the * row has no lower bound, the routine returns -DBL_MAX. */ double glp_get_row_lb(glp_prob *lp, int i) { double lb; if (!(1 <= i && i <= lp->m)) xerror("glp_get_row_lb: i = %d; row number out of range\n", i); switch (lp->row[i]->type) { case GLP_FR: case GLP_UP: lb = -DBL_MAX; break; case GLP_LO: case GLP_DB: case GLP_FX: lb = lp->row[i]->lb; break; default: xassert(lp != lp); } return lb; } /*********************************************************************** * NAME * * glp_get_row_ub - retrieve row upper bound * * SYNOPSIS * * double glp_get_row_ub(glp_prob *lp, int i); * * RETURNS * * The routine glp_get_row_ub returns the upper bound of i-th row, i.e. * the upper bound of corresponding auxiliary variable. However, if the * row has no upper bound, the routine returns +DBL_MAX. */ double glp_get_row_ub(glp_prob *lp, int i) { double ub; if (!(1 <= i && i <= lp->m)) xerror("glp_get_row_ub: i = %d; row number out of range\n", i); switch (lp->row[i]->type) { case GLP_FR: case GLP_LO: ub = +DBL_MAX; break; case GLP_UP: case GLP_DB: case GLP_FX: ub = lp->row[i]->ub; break; default: xassert(lp != lp); } return ub; } /*********************************************************************** * NAME * * glp_get_col_type - retrieve column type * * SYNOPSIS * * int glp_get_col_type(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_col_type returns the type of j-th column, i.e. * the type of corresponding structural variable, as follows: * * GLP_FR - free (unbounded) variable; * GLP_LO - variable with lower bound; * GLP_UP - variable with upper bound; * GLP_DB - double-bounded variable; * GLP_FX - fixed variable. */ int glp_get_col_type(glp_prob *lp, int j) { if (!(1 <= j && j <= lp->n)) xerror("glp_get_col_type: j = %d; column number out of range\n" , j); return lp->col[j]->type; } /*********************************************************************** * NAME * * glp_get_col_lb - retrieve column lower bound * * SYNOPSIS * * double glp_get_col_lb(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_col_lb returns the lower bound of j-th column, * i.e. the lower bound of corresponding structural variable. However, * if the column has no lower bound, the routine returns -DBL_MAX. */ double glp_get_col_lb(glp_prob *lp, int j) { double lb; if (!(1 <= j && j <= lp->n)) xerror("glp_get_col_lb: j = %d; column number out of range\n", j); switch (lp->col[j]->type) { case GLP_FR: case GLP_UP: lb = -DBL_MAX; break; case GLP_LO: case GLP_DB: case GLP_FX: lb = lp->col[j]->lb; break; default: xassert(lp != lp); } return lb; } /*********************************************************************** * NAME * * glp_get_col_ub - retrieve column upper bound * * SYNOPSIS * * double glp_get_col_ub(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_col_ub returns the upper bound of j-th column, * i.e. the upper bound of corresponding structural variable. However, * if the column has no upper bound, the routine returns +DBL_MAX. */ double glp_get_col_ub(glp_prob *lp, int j) { double ub; if (!(1 <= j && j <= lp->n)) xerror("glp_get_col_ub: j = %d; column number out of range\n", j); switch (lp->col[j]->type) { case GLP_FR: case GLP_LO: ub = +DBL_MAX; break; case GLP_UP: case GLP_DB: case GLP_FX: ub = lp->col[j]->ub; break; default: xassert(lp != lp); } return ub; } /*********************************************************************** * NAME * * glp_get_obj_coef - retrieve obj. coefficient or constant term * * SYNOPSIS * * double glp_get_obj_coef(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_obj_coef returns the objective coefficient at * j-th structural variable (column) of the specified problem object. * * If the parameter j is zero, the routine returns the constant term * ("shift") of the objective function. */ double glp_get_obj_coef(glp_prob *lp, int j) { if (!(0 <= j && j <= lp->n)) xerror("glp_get_obj_coef: j = %d; column number out of range\n" , j); return j == 0 ? lp->c0 : lp->col[j]->coef; } /*********************************************************************** * NAME * * glp_get_num_nz - retrieve number of constraint coefficients * * SYNOPSIS * * int glp_get_num_nz(glp_prob *lp); * * RETURNS * * The routine glp_get_num_nz returns the number of (non-zero) elements * in the constraint matrix of the specified problem object. */ int glp_get_num_nz(glp_prob *lp) { int nnz = lp->nnz; return nnz; } /*********************************************************************** * NAME * * glp_get_mat_row - retrieve row of the constraint matrix * * SYNOPSIS * * int glp_get_mat_row(glp_prob *lp, int i, int ind[], double val[]); * * DESCRIPTION * * The routine glp_get_mat_row scans (non-zero) elements of i-th row * of the constraint matrix of the specified problem object and stores * their column indices and numeric values to locations ind[1], ..., * ind[len] and val[1], ..., val[len], respectively, where 0 <= len <= n * is the number of elements in i-th row, n is the number of columns. * * The parameter ind and/or val can be specified as NULL, in which case * corresponding information is not stored. * * RETURNS * * The routine glp_get_mat_row returns the length len, i.e. the number * of (non-zero) elements in i-th row. */ int glp_get_mat_row(glp_prob *lp, int i, int ind[], double val[]) { GLPAIJ *aij; int len; if (!(1 <= i && i <= lp->m)) xerror("glp_get_mat_row: i = %d; row number out of range\n", i); len = 0; for (aij = lp->row[i]->ptr; aij != NULL; aij = aij->r_next) { len++; if (ind != NULL) ind[len] = aij->col->j; if (val != NULL) val[len] = aij->val; } xassert(len <= lp->n); return len; } /*********************************************************************** * NAME * * glp_get_mat_col - retrieve column of the constraint matrix * * SYNOPSIS * * int glp_get_mat_col(glp_prob *lp, int j, int ind[], double val[]); * * DESCRIPTION * * The routine glp_get_mat_col scans (non-zero) elements of j-th column * of the constraint matrix of the specified problem object and stores * their row indices and numeric values to locations ind[1], ..., * ind[len] and val[1], ..., val[len], respectively, where 0 <= len <= m * is the number of elements in j-th column, m is the number of rows. * * The parameter ind or/and val can be specified as NULL, in which case * corresponding information is not stored. * * RETURNS * * The routine glp_get_mat_col returns the length len, i.e. the number * of (non-zero) elements in j-th column. */ int glp_get_mat_col(glp_prob *lp, int j, int ind[], double val[]) { GLPAIJ *aij; int len; if (!(1 <= j && j <= lp->n)) xerror("glp_get_mat_col: j = %d; column number out of range\n", j); len = 0; for (aij = lp->col[j]->ptr; aij != NULL; aij = aij->c_next) { len++; if (ind != NULL) ind[len] = aij->row->i; if (val != NULL) val[len] = aij->val; } xassert(len <= lp->m); return len; } /* eof */ sources_5316/external/glpk/amd_2.c0000644000176700017670000023050111401660400015621 0ustar paulpaul/* ========================================================================= */ /* === AMD_2 =============================================================== */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* AMD_2: performs the AMD ordering on a symmetric sparse matrix A, followed * by a postordering (via depth-first search) of the assembly tree using the * AMD_postorder routine. */ #include "amd_internal.h" /* ========================================================================= */ /* === clear_flag ========================================================== */ /* ========================================================================= */ static Int clear_flag (Int wflg, Int wbig, Int W [ ], Int n) { Int x ; if (wflg < 2 || wflg >= wbig) { for (x = 0 ; x < n ; x++) { if (W [x] != 0) W [x] = 1 ; } wflg = 2 ; } /* at this point, W [0..n-1] < wflg holds */ return (wflg) ; } /* ========================================================================= */ /* === AMD_2 =============================================================== */ /* ========================================================================= */ GLOBAL void AMD_2 ( Int n, /* A is n-by-n, where n > 0 */ Int Pe [ ], /* Pe [0..n-1]: index in Iw of row i on input */ Int Iw [ ], /* workspace of size iwlen. Iw [0..pfree-1] * holds the matrix on input */ Int Len [ ], /* Len [0..n-1]: length for row/column i on input */ Int iwlen, /* length of Iw. iwlen >= pfree + n */ Int pfree, /* Iw [pfree ... iwlen-1] is empty on input */ /* 7 size-n workspaces, not defined on input: */ Int Nv [ ], /* the size of each supernode on output */ Int Next [ ], /* the output inverse permutation */ Int Last [ ], /* the output permutation */ Int Head [ ], Int Elen [ ], /* the size columns of L for each supernode */ Int Degree [ ], Int W [ ], /* control parameters and output statistics */ double Control [ ], /* array of size AMD_CONTROL */ double Info [ ] /* array of size AMD_INFO */ ) { /* * Given a representation of the nonzero pattern of a symmetric matrix, A, * (excluding the diagonal) perform an approximate minimum (UMFPACK/MA38-style) * degree ordering to compute a pivot order such that the introduction of * nonzeros (fill-in) in the Cholesky factors A = LL' is kept low. At each * step, the pivot selected is the one with the minimum UMFAPACK/MA38-style * upper-bound on the external degree. This routine can optionally perform * aggresive absorption (as done by MC47B in the Harwell Subroutine * Library). * * The approximate degree algorithm implemented here is the symmetric analog of * the degree update algorithm in MA38 and UMFPACK (the Unsymmetric-pattern * MultiFrontal PACKage, both by Davis and Duff). The routine is based on the * MA27 minimum degree ordering algorithm by Iain Duff and John Reid. * * This routine is a translation of the original AMDBAR and MC47B routines, * in Fortran, with the following modifications: * * (1) dense rows/columns are removed prior to ordering the matrix, and placed * last in the output order. The presence of a dense row/column can * increase the ordering time by up to O(n^2), unless they are removed * prior to ordering. * * (2) the minimum degree ordering is followed by a postordering (depth-first * search) of the assembly tree. Note that mass elimination (discussed * below) combined with the approximate degree update can lead to the mass * elimination of nodes with lower exact degree than the current pivot * element. No additional fill-in is caused in the representation of the * Schur complement. The mass-eliminated nodes merge with the current * pivot element. They are ordered prior to the current pivot element. * Because they can have lower exact degree than the current element, the * merger of two or more of these nodes in the current pivot element can * lead to a single element that is not a "fundamental supernode". The * diagonal block can have zeros in it. Thus, the assembly tree used here * is not guaranteed to be the precise supernodal elemination tree (with * "funadmental" supernodes), and the postordering performed by this * routine is not guaranteed to be a precise postordering of the * elimination tree. * * (3) input parameters are added, to control aggressive absorption and the * detection of "dense" rows/columns of A. * * (4) additional statistical information is returned, such as the number of * nonzeros in L, and the flop counts for subsequent LDL' and LU * factorizations. These are slight upper bounds, because of the mass * elimination issue discussed above. * * (5) additional routines are added to interface this routine to MATLAB * to provide a simple C-callable user-interface, to check inputs for * errors, compute the symmetry of the pattern of A and the number of * nonzeros in each row/column of A+A', to compute the pattern of A+A', * to perform the assembly tree postordering, and to provide debugging * ouput. Many of these functions are also provided by the Fortran * Harwell Subroutine Library routine MC47A. * * (6) both int and UF_long versions are provided. In the descriptions below * and integer is and int or UF_long depending on which version is * being used. ********************************************************************** ***** CAUTION: ARGUMENTS ARE NOT CHECKED FOR ERRORS ON INPUT. ****** ********************************************************************** ** If you want error checking, a more versatile input format, and a ** ** simpler user interface, use amd_order or amd_l_order instead. ** ** This routine is not meant to be user-callable. ** ********************************************************************** * ---------------------------------------------------------------------------- * References: * ---------------------------------------------------------------------------- * * [1] Timothy A. Davis and Iain Duff, "An unsymmetric-pattern multifrontal * method for sparse LU factorization", SIAM J. Matrix Analysis and * Applications, vol. 18, no. 1, pp. 140-158. Discusses UMFPACK / MA38, * which first introduced the approximate minimum degree used by this * routine. * * [2] Patrick Amestoy, Timothy A. Davis, and Iain S. Duff, "An approximate * minimum degree ordering algorithm," SIAM J. Matrix Analysis and * Applications, vol. 17, no. 4, pp. 886-905, 1996. Discusses AMDBAR and * MC47B, which are the Fortran versions of this routine. * * [3] Alan George and Joseph Liu, "The evolution of the minimum degree * ordering algorithm," SIAM Review, vol. 31, no. 1, pp. 1-19, 1989. * We list below the features mentioned in that paper that this code * includes: * * mass elimination: * Yes. MA27 relied on supervariable detection for mass elimination. * * indistinguishable nodes: * Yes (we call these "supervariables"). This was also in the MA27 * code - although we modified the method of detecting them (the * previous hash was the true degree, which we no longer keep track * of). A supervariable is a set of rows with identical nonzero * pattern. All variables in a supervariable are eliminated together. * Each supervariable has as its numerical name that of one of its * variables (its principal variable). * * quotient graph representation: * Yes. We use the term "element" for the cliques formed during * elimination. This was also in the MA27 code. The algorithm can * operate in place, but it will work more efficiently if given some * "elbow room." * * element absorption: * Yes. This was also in the MA27 code. * * external degree: * Yes. The MA27 code was based on the true degree. * * incomplete degree update and multiple elimination: * No. This was not in MA27, either. Our method of degree update * within MC47B is element-based, not variable-based. It is thus * not well-suited for use with incomplete degree update or multiple * elimination. * * Authors, and Copyright (C) 2004 by: * Timothy A. Davis, Patrick Amestoy, Iain S. Duff, John K. Reid. * * Acknowledgements: This work (and the UMFPACK package) was supported by the * National Science Foundation (ASC-9111263, DMS-9223088, and CCR-0203270). * The UMFPACK/MA38 approximate degree update algorithm, the unsymmetric analog * which forms the basis of AMD, was developed while Tim Davis was supported by * CERFACS (Toulouse, France) in a post-doctoral position. This C version, and * the etree postorder, were written while Tim Davis was on sabbatical at * Stanford University and Lawrence Berkeley National Laboratory. * ---------------------------------------------------------------------------- * INPUT ARGUMENTS (unaltered): * ---------------------------------------------------------------------------- * n: The matrix order. Restriction: n >= 1. * * iwlen: The size of the Iw array. On input, the matrix is stored in * Iw [0..pfree-1]. However, Iw [0..iwlen-1] should be slightly larger * than what is required to hold the matrix, at least iwlen >= pfree + n. * Otherwise, excessive compressions will take place. The recommended * value of iwlen is 1.2 * pfree + n, which is the value used in the * user-callable interface to this routine (amd_order.c). The algorithm * will not run at all if iwlen < pfree. Restriction: iwlen >= pfree + n. * Note that this is slightly more restrictive than the actual minimum * (iwlen >= pfree), but AMD_2 will be very slow with no elbow room. * Thus, this routine enforces a bare minimum elbow room of size n. * * pfree: On input the tail end of the array, Iw [pfree..iwlen-1], is empty, * and the matrix is stored in Iw [0..pfree-1]. During execution, * additional data is placed in Iw, and pfree is modified so that * Iw [pfree..iwlen-1] is always the unused part of Iw. * * Control: A double array of size AMD_CONTROL containing input parameters * that affect how the ordering is computed. If NULL, then default * settings are used. * * Control [AMD_DENSE] is used to determine whether or not a given input * row is "dense". A row is "dense" if the number of entries in the row * exceeds Control [AMD_DENSE] times sqrt (n), except that rows with 16 or * fewer entries are never considered "dense". To turn off the detection * of dense rows, set Control [AMD_DENSE] to a negative number, or to a * number larger than sqrt (n). The default value of Control [AMD_DENSE] * is AMD_DEFAULT_DENSE, which is defined in amd.h as 10. * * Control [AMD_AGGRESSIVE] is used to determine whether or not aggressive * absorption is to be performed. If nonzero, then aggressive absorption * is performed (this is the default). * ---------------------------------------------------------------------------- * INPUT/OUPUT ARGUMENTS: * ---------------------------------------------------------------------------- * * Pe: An integer array of size n. On input, Pe [i] is the index in Iw of * the start of row i. Pe [i] is ignored if row i has no off-diagonal * entries. Thus Pe [i] must be in the range 0 to pfree-1 for non-empty * rows. * * During execution, it is used for both supervariables and elements: * * Principal supervariable i: index into Iw of the description of * supervariable i. A supervariable represents one or more rows of * the matrix with identical nonzero pattern. In this case, * Pe [i] >= 0. * * Non-principal supervariable i: if i has been absorbed into another * supervariable j, then Pe [i] = FLIP (j), where FLIP (j) is defined * as (-(j)-2). Row j has the same pattern as row i. Note that j * might later be absorbed into another supervariable j2, in which * case Pe [i] is still FLIP (j), and Pe [j] = FLIP (j2) which is * < EMPTY, where EMPTY is defined as (-1) in amd_internal.h. * * Unabsorbed element e: the index into Iw of the description of element * e, if e has not yet been absorbed by a subsequent element. Element * e is created when the supervariable of the same name is selected as * the pivot. In this case, Pe [i] >= 0. * * Absorbed element e: if element e is absorbed into element e2, then * Pe [e] = FLIP (e2). This occurs when the pattern of e (which we * refer to as Le) is found to be a subset of the pattern of e2 (that * is, Le2). In this case, Pe [i] < EMPTY. If element e is "null" * (it has no nonzeros outside its pivot block), then Pe [e] = EMPTY, * and e is the root of an assembly subtree (or the whole tree if * there is just one such root). * * Dense variable i: if i is "dense", then Pe [i] = EMPTY. * * On output, Pe holds the assembly tree/forest, which implicitly * represents a pivot order with identical fill-in as the actual order * (via a depth-first search of the tree), as follows. If Nv [i] > 0, * then i represents a node in the assembly tree, and the parent of i is * Pe [i], or EMPTY if i is a root. If Nv [i] = 0, then (i, Pe [i]) * represents an edge in a subtree, the root of which is a node in the * assembly tree. Note that i refers to a row/column in the original * matrix, not the permuted matrix. * * Info: A double array of size AMD_INFO. If present, (that is, not NULL), * then statistics about the ordering are returned in the Info array. * See amd.h for a description. * ---------------------------------------------------------------------------- * INPUT/MODIFIED (undefined on output): * ---------------------------------------------------------------------------- * * Len: An integer array of size n. On input, Len [i] holds the number of * entries in row i of the matrix, excluding the diagonal. The contents * of Len are undefined on output. * * Iw: An integer array of size iwlen. On input, Iw [0..pfree-1] holds the * description of each row i in the matrix. The matrix must be symmetric, * and both upper and lower triangular parts must be present. The * diagonal must not be present. Row i is held as follows: * * Len [i]: the length of the row i data structure in the Iw array. * Iw [Pe [i] ... Pe [i] + Len [i] - 1]: * the list of column indices for nonzeros in row i (simple * supervariables), excluding the diagonal. All supervariables * start with one row/column each (supervariable i is just row i). * If Len [i] is zero on input, then Pe [i] is ignored on input. * * Note that the rows need not be in any particular order, and there * may be empty space between the rows. * * During execution, the supervariable i experiences fill-in. This is * represented by placing in i a list of the elements that cause fill-in * in supervariable i: * * Len [i]: the length of supervariable i in the Iw array. * Iw [Pe [i] ... Pe [i] + Elen [i] - 1]: * the list of elements that contain i. This list is kept short * by removing absorbed elements. * Iw [Pe [i] + Elen [i] ... Pe [i] + Len [i] - 1]: * the list of supervariables in i. This list is kept short by * removing nonprincipal variables, and any entry j that is also * contained in at least one of the elements (j in Le) in the list * for i (e in row i). * * When supervariable i is selected as pivot, we create an element e of * the same name (e=i): * * Len [e]: the length of element e in the Iw array. * Iw [Pe [e] ... Pe [e] + Len [e] - 1]: * the list of supervariables in element e. * * An element represents the fill-in that occurs when supervariable i is * selected as pivot (which represents the selection of row i and all * non-principal variables whose principal variable is i). We use the * term Le to denote the set of all supervariables in element e. Absorbed * supervariables and elements are pruned from these lists when * computationally convenient. * * CAUTION: THE INPUT MATRIX IS OVERWRITTEN DURING COMPUTATION. * The contents of Iw are undefined on output. * ---------------------------------------------------------------------------- * OUTPUT (need not be set on input): * ---------------------------------------------------------------------------- * * Nv: An integer array of size n. During execution, ABS (Nv [i]) is equal to * the number of rows that are represented by the principal supervariable * i. If i is a nonprincipal or dense variable, then Nv [i] = 0. * Initially, Nv [i] = 1 for all i. Nv [i] < 0 signifies that i is a * principal variable in the pattern Lme of the current pivot element me. * After element me is constructed, Nv [i] is set back to a positive * value. * * On output, Nv [i] holds the number of pivots represented by super * row/column i of the original matrix, or Nv [i] = 0 for non-principal * rows/columns. Note that i refers to a row/column in the original * matrix, not the permuted matrix. * * Elen: An integer array of size n. See the description of Iw above. At the * start of execution, Elen [i] is set to zero for all rows i. During * execution, Elen [i] is the number of elements in the list for * supervariable i. When e becomes an element, Elen [e] = FLIP (esize) is * set, where esize is the size of the element (the number of pivots, plus * the number of nonpivotal entries). Thus Elen [e] < EMPTY. * Elen (i) = EMPTY set when variable i becomes nonprincipal. * * For variables, Elen (i) >= EMPTY holds until just before the * postordering and permutation vectors are computed. For elements, * Elen [e] < EMPTY holds. * * On output, Elen [i] is the degree of the row/column in the Cholesky * factorization of the permuted matrix, corresponding to the original row * i, if i is a super row/column. It is equal to EMPTY if i is * non-principal. Note that i refers to a row/column in the original * matrix, not the permuted matrix. * * Note that the contents of Elen on output differ from the Fortran * version (Elen holds the inverse permutation in the Fortran version, * which is instead returned in the Next array in this C version, * described below). * * Last: In a degree list, Last [i] is the supervariable preceding i, or EMPTY * if i is the head of the list. In a hash bucket, Last [i] is the hash * key for i. * * Last [Head [hash]] is also used as the head of a hash bucket if * Head [hash] contains a degree list (see the description of Head, * below). * * On output, Last [0..n-1] holds the permutation. That is, if * i = Last [k], then row i is the kth pivot row (where k ranges from 0 to * n-1). Row Last [k] of A is the kth row in the permuted matrix, PAP'. * * Next: Next [i] is the supervariable following i in a link list, or EMPTY if * i is the last in the list. Used for two kinds of lists: degree lists * and hash buckets (a supervariable can be in only one kind of list at a * time). * * On output Next [0..n-1] holds the inverse permutation. That is, if * k = Next [i], then row i is the kth pivot row. Row i of A appears as * the (Next[i])-th row in the permuted matrix, PAP'. * * Note that the contents of Next on output differ from the Fortran * version (Next is undefined on output in the Fortran version). * ---------------------------------------------------------------------------- * LOCAL WORKSPACE (not input or output - used only during execution): * ---------------------------------------------------------------------------- * * Degree: An integer array of size n. If i is a supervariable, then * Degree [i] holds the current approximation of the external degree of * row i (an upper bound). The external degree is the number of nonzeros * in row i, minus ABS (Nv [i]), the diagonal part. The bound is equal to * the exact external degree if Elen [i] is less than or equal to two. * * We also use the term "external degree" for elements e to refer to * |Le \ Lme|. If e is an element, then Degree [e] is |Le|, which is the * degree of the off-diagonal part of the element e (not including the * diagonal part). * * Head: An integer array of size n. Head is used for degree lists. * Head [deg] is the first supervariable in a degree list. All * supervariables i in a degree list Head [deg] have the same approximate * degree, namely, deg = Degree [i]. If the list Head [deg] is empty then * Head [deg] = EMPTY. * * During supervariable detection Head [hash] also serves as a pointer to * a hash bucket. If Head [hash] >= 0, there is a degree list of degree * hash. The hash bucket head pointer is Last [Head [hash]]. If * Head [hash] = EMPTY, then the degree list and hash bucket are both * empty. If Head [hash] < EMPTY, then the degree list is empty, and * FLIP (Head [hash]) is the head of the hash bucket. After supervariable * detection is complete, all hash buckets are empty, and the * (Last [Head [hash]] = EMPTY) condition is restored for the non-empty * degree lists. * * W: An integer array of size n. The flag array W determines the status of * elements and variables, and the external degree of elements. * * for elements: * if W [e] = 0, then the element e is absorbed. * if W [e] >= wflg, then W [e] - wflg is the size of the set * |Le \ Lme|, in terms of nonzeros (the sum of ABS (Nv [i]) for * each principal variable i that is both in the pattern of * element e and NOT in the pattern of the current pivot element, * me). * if wflg > W [e] > 0, then e is not absorbed and has not yet been * seen in the scan of the element lists in the computation of * |Le\Lme| in Scan 1 below. * * for variables: * during supervariable detection, if W [j] != wflg then j is * not in the pattern of variable i. * * The W array is initialized by setting W [i] = 1 for all i, and by * setting wflg = 2. It is reinitialized if wflg becomes too large (to * ensure that wflg+n does not cause integer overflow). * ---------------------------------------------------------------------------- * LOCAL INTEGERS: * ---------------------------------------------------------------------------- */ Int deg, degme, dext, lemax, e, elenme, eln, i, ilast, inext, j, jlast, jnext, k, knt1, knt2, knt3, lenj, ln, me, mindeg, nel, nleft, nvi, nvj, nvpiv, slenme, wbig, we, wflg, wnvi, ok, ndense, ncmpa, dense, aggressive ; unsigned Int hash ; /* unsigned, so that hash % n is well defined.*/ /* * deg: the degree of a variable or element * degme: size, |Lme|, of the current element, me (= Degree [me]) * dext: external degree, |Le \ Lme|, of some element e * lemax: largest |Le| seen so far (called dmax in Fortran version) * e: an element * elenme: the length, Elen [me], of element list of pivotal variable * eln: the length, Elen [...], of an element list * hash: the computed value of the hash function * i: a supervariable * ilast: the entry in a link list preceding i * inext: the entry in a link list following i * j: a supervariable * jlast: the entry in a link list preceding j * jnext: the entry in a link list, or path, following j * k: the pivot order of an element or variable * knt1: loop counter used during element construction * knt2: loop counter used during element construction * knt3: loop counter used during compression * lenj: Len [j] * ln: length of a supervariable list * me: current supervariable being eliminated, and the current * element created by eliminating that supervariable * mindeg: current minimum degree * nel: number of pivots selected so far * nleft: n - nel, the number of nonpivotal rows/columns remaining * nvi: the number of variables in a supervariable i (= Nv [i]) * nvj: the number of variables in a supervariable j (= Nv [j]) * nvpiv: number of pivots in current element * slenme: number of variables in variable list of pivotal variable * wbig: = INT_MAX - n for the int version, UF_long_max - n for the * UF_long version. wflg is not allowed to be >= wbig. * we: W [e] * wflg: used for flagging the W array. See description of Iw. * wnvi: wflg - Nv [i] * x: either a supervariable or an element * * ok: true if supervariable j can be absorbed into i * ndense: number of "dense" rows/columns * dense: rows/columns with initial degree > dense are considered "dense" * aggressive: true if aggressive absorption is being performed * ncmpa: number of garbage collections * ---------------------------------------------------------------------------- * LOCAL DOUBLES, used for statistical output only (except for alpha): * ---------------------------------------------------------------------------- */ double f, r, ndiv, s, nms_lu, nms_ldl, dmax, alpha, lnz, lnzme ; /* * f: nvpiv * r: degme + nvpiv * ndiv: number of divisions for LU or LDL' factorizations * s: number of multiply-subtract pairs for LU factorization, for the * current element me * nms_lu number of multiply-subtract pairs for LU factorization * nms_ldl number of multiply-subtract pairs for LDL' factorization * dmax: the largest number of entries in any column of L, including the * diagonal * alpha: "dense" degree ratio * lnz: the number of nonzeros in L (excluding the diagonal) * lnzme: the number of nonzeros in L (excl. the diagonal) for the * current element me * ---------------------------------------------------------------------------- * LOCAL "POINTERS" (indices into the Iw array) * ---------------------------------------------------------------------------- */ Int p, p1, p2, p3, p4, pdst, pend, pj, pme, pme1, pme2, pn, psrc ; /* * Any parameter (Pe [...] or pfree) or local variable starting with "p" (for * Pointer) is an index into Iw, and all indices into Iw use variables starting * with "p." The only exception to this rule is the iwlen input argument. * * p: pointer into lots of things * p1: Pe [i] for some variable i (start of element list) * p2: Pe [i] + Elen [i] - 1 for some variable i * p3: index of first supervariable in clean list * p4: * pdst: destination pointer, for compression * pend: end of memory to compress * pj: pointer into an element or variable * pme: pointer into the current element (pme1...pme2) * pme1: the current element, me, is stored in Iw [pme1...pme2] * pme2: the end of the current element * pn: pointer into a "clean" variable, also used to compress * psrc: source pointer, for compression */ /* ========================================================================= */ /* INITIALIZATIONS */ /* ========================================================================= */ /* Note that this restriction on iwlen is slightly more restrictive than * what is actually required in AMD_2. AMD_2 can operate with no elbow * room at all, but it will be slow. For better performance, at least * size-n elbow room is enforced. */ ASSERT (iwlen >= pfree + n) ; ASSERT (n > 0) ; /* initialize output statistics */ lnz = 0 ; ndiv = 0 ; nms_lu = 0 ; nms_ldl = 0 ; dmax = 1 ; me = EMPTY ; mindeg = 0 ; ncmpa = 0 ; nel = 0 ; lemax = 0 ; /* get control parameters */ if (Control != (double *) NULL) { alpha = Control [AMD_DENSE] ; aggressive = (Control [AMD_AGGRESSIVE] != 0) ; } else { alpha = AMD_DEFAULT_DENSE ; aggressive = AMD_DEFAULT_AGGRESSIVE ; } /* Note: if alpha is NaN, this is undefined: */ if (alpha < 0) { /* only remove completely dense rows/columns */ dense = n-2 ; } else { dense = alpha * sqrt ((double) n) ; } dense = MAX (16, dense) ; dense = MIN (n, dense) ; AMD_DEBUG1 (("\n\nAMD (debug), alpha %g, aggr. "ID"\n", alpha, aggressive)) ; for (i = 0 ; i < n ; i++) { Last [i] = EMPTY ; Head [i] = EMPTY ; Next [i] = EMPTY ; /* if separate Hhead array is used for hash buckets: * Hhead [i] = EMPTY ; */ Nv [i] = 1 ; W [i] = 1 ; Elen [i] = 0 ; Degree [i] = Len [i] ; } #ifndef NDEBUG AMD_DEBUG1 (("\n======Nel "ID" initial\n", nel)) ; AMD_dump (n, Pe, Iw, Len, iwlen, pfree, Nv, Next, Last, Head, Elen, Degree, W, -1) ; #endif /* initialize wflg */ wbig = Int_MAX - n ; wflg = clear_flag (0, wbig, W, n) ; /* --------------------------------------------------------------------- */ /* initialize degree lists and eliminate dense and empty rows */ /* --------------------------------------------------------------------- */ ndense = 0 ; for (i = 0 ; i < n ; i++) { deg = Degree [i] ; ASSERT (deg >= 0 && deg < n) ; if (deg == 0) { /* ------------------------------------------------------------- * we have a variable that can be eliminated at once because * there is no off-diagonal non-zero in its row. Note that * Nv [i] = 1 for an empty variable i. It is treated just * the same as an eliminated element i. * ------------------------------------------------------------- */ Elen [i] = FLIP (1) ; nel++ ; Pe [i] = EMPTY ; W [i] = 0 ; } else if (deg > dense) { /* ------------------------------------------------------------- * Dense variables are not treated as elements, but as unordered, * non-principal variables that have no parent. They do not take * part in the postorder, since Nv [i] = 0. Note that the Fortran * version does not have this option. * ------------------------------------------------------------- */ AMD_DEBUG1 (("Dense node "ID" degree "ID"\n", i, deg)) ; ndense++ ; Nv [i] = 0 ; /* do not postorder this node */ Elen [i] = EMPTY ; nel++ ; Pe [i] = EMPTY ; } else { /* ------------------------------------------------------------- * place i in the degree list corresponding to its degree * ------------------------------------------------------------- */ inext = Head [deg] ; ASSERT (inext >= EMPTY && inext < n) ; if (inext != EMPTY) Last [inext] = i ; Next [i] = inext ; Head [deg] = i ; } } /* ========================================================================= */ /* WHILE (selecting pivots) DO */ /* ========================================================================= */ while (nel < n) { #ifndef NDEBUG AMD_DEBUG1 (("\n======Nel "ID"\n", nel)) ; if (AMD_debug >= 2) { AMD_dump (n, Pe, Iw, Len, iwlen, pfree, Nv, Next, Last, Head, Elen, Degree, W, nel) ; } #endif /* ========================================================================= */ /* GET PIVOT OF MINIMUM DEGREE */ /* ========================================================================= */ /* ----------------------------------------------------------------- */ /* find next supervariable for elimination */ /* ----------------------------------------------------------------- */ ASSERT (mindeg >= 0 && mindeg < n) ; for (deg = mindeg ; deg < n ; deg++) { me = Head [deg] ; if (me != EMPTY) break ; } mindeg = deg ; ASSERT (me >= 0 && me < n) ; AMD_DEBUG1 (("=================me: "ID"\n", me)) ; /* ----------------------------------------------------------------- */ /* remove chosen variable from link list */ /* ----------------------------------------------------------------- */ inext = Next [me] ; ASSERT (inext >= EMPTY && inext < n) ; if (inext != EMPTY) Last [inext] = EMPTY ; Head [deg] = inext ; /* ----------------------------------------------------------------- */ /* me represents the elimination of pivots nel to nel+Nv[me]-1. */ /* place me itself as the first in this set. */ /* ----------------------------------------------------------------- */ elenme = Elen [me] ; nvpiv = Nv [me] ; ASSERT (nvpiv > 0) ; nel += nvpiv ; /* ========================================================================= */ /* CONSTRUCT NEW ELEMENT */ /* ========================================================================= */ /* ----------------------------------------------------------------- * At this point, me is the pivotal supervariable. It will be * converted into the current element. Scan list of the pivotal * supervariable, me, setting tree pointers and constructing new list * of supervariables for the new element, me. p is a pointer to the * current position in the old list. * ----------------------------------------------------------------- */ /* flag the variable "me" as being in Lme by negating Nv [me] */ Nv [me] = -nvpiv ; degme = 0 ; ASSERT (Pe [me] >= 0 && Pe [me] < iwlen) ; if (elenme == 0) { /* ------------------------------------------------------------- */ /* construct the new element in place */ /* ------------------------------------------------------------- */ pme1 = Pe [me] ; pme2 = pme1 - 1 ; for (p = pme1 ; p <= pme1 + Len [me] - 1 ; p++) { i = Iw [p] ; ASSERT (i >= 0 && i < n && Nv [i] >= 0) ; nvi = Nv [i] ; if (nvi > 0) { /* ----------------------------------------------------- */ /* i is a principal variable not yet placed in Lme. */ /* store i in new list */ /* ----------------------------------------------------- */ /* flag i as being in Lme by negating Nv [i] */ degme += nvi ; Nv [i] = -nvi ; Iw [++pme2] = i ; /* ----------------------------------------------------- */ /* remove variable i from degree list. */ /* ----------------------------------------------------- */ ilast = Last [i] ; inext = Next [i] ; ASSERT (ilast >= EMPTY && ilast < n) ; ASSERT (inext >= EMPTY && inext < n) ; if (inext != EMPTY) Last [inext] = ilast ; if (ilast != EMPTY) { Next [ilast] = inext ; } else { /* i is at the head of the degree list */ ASSERT (Degree [i] >= 0 && Degree [i] < n) ; Head [Degree [i]] = inext ; } } } } else { /* ------------------------------------------------------------- */ /* construct the new element in empty space, Iw [pfree ...] */ /* ------------------------------------------------------------- */ p = Pe [me] ; pme1 = pfree ; slenme = Len [me] - elenme ; for (knt1 = 1 ; knt1 <= elenme + 1 ; knt1++) { if (knt1 > elenme) { /* search the supervariables in me. */ e = me ; pj = p ; ln = slenme ; AMD_DEBUG2 (("Search sv: "ID" "ID" "ID"\n", me,pj,ln)) ; } else { /* search the elements in me. */ e = Iw [p++] ; ASSERT (e >= 0 && e < n) ; pj = Pe [e] ; ln = Len [e] ; AMD_DEBUG2 (("Search element e "ID" in me "ID"\n", e,me)) ; ASSERT (Elen [e] < EMPTY && W [e] > 0 && pj >= 0) ; } ASSERT (ln >= 0 && (ln == 0 || (pj >= 0 && pj < iwlen))) ; /* --------------------------------------------------------- * search for different supervariables and add them to the * new list, compressing when necessary. this loop is * executed once for each element in the list and once for * all the supervariables in the list. * --------------------------------------------------------- */ for (knt2 = 1 ; knt2 <= ln ; knt2++) { i = Iw [pj++] ; ASSERT (i >= 0 && i < n && (i == me || Elen [i] >= EMPTY)); nvi = Nv [i] ; AMD_DEBUG2 ((": "ID" "ID" "ID" "ID"\n", i, Elen [i], Nv [i], wflg)) ; if (nvi > 0) { /* ------------------------------------------------- */ /* compress Iw, if necessary */ /* ------------------------------------------------- */ if (pfree >= iwlen) { AMD_DEBUG1 (("GARBAGE COLLECTION\n")) ; /* prepare for compressing Iw by adjusting pointers * and lengths so that the lists being searched in * the inner and outer loops contain only the * remaining entries. */ Pe [me] = p ; Len [me] -= knt1 ; /* check if nothing left of supervariable me */ if (Len [me] == 0) Pe [me] = EMPTY ; Pe [e] = pj ; Len [e] = ln - knt2 ; /* nothing left of element e */ if (Len [e] == 0) Pe [e] = EMPTY ; ncmpa++ ; /* one more garbage collection */ /* store first entry of each object in Pe */ /* FLIP the first entry in each object */ for (j = 0 ; j < n ; j++) { pn = Pe [j] ; if (pn >= 0) { ASSERT (pn >= 0 && pn < iwlen) ; Pe [j] = Iw [pn] ; Iw [pn] = FLIP (j) ; } } /* psrc/pdst point to source/destination */ psrc = 0 ; pdst = 0 ; pend = pme1 - 1 ; while (psrc <= pend) { /* search for next FLIP'd entry */ j = FLIP (Iw [psrc++]) ; if (j >= 0) { AMD_DEBUG2 (("Got object j: "ID"\n", j)) ; Iw [pdst] = Pe [j] ; Pe [j] = pdst++ ; lenj = Len [j] ; /* copy from source to destination */ for (knt3 = 0 ; knt3 <= lenj - 2 ; knt3++) { Iw [pdst++] = Iw [psrc++] ; } } } /* move the new partially-constructed element */ p1 = pdst ; for (psrc = pme1 ; psrc <= pfree-1 ; psrc++) { Iw [pdst++] = Iw [psrc] ; } pme1 = p1 ; pfree = pdst ; pj = Pe [e] ; p = Pe [me] ; } /* ------------------------------------------------- */ /* i is a principal variable not yet placed in Lme */ /* store i in new list */ /* ------------------------------------------------- */ /* flag i as being in Lme by negating Nv [i] */ degme += nvi ; Nv [i] = -nvi ; Iw [pfree++] = i ; AMD_DEBUG2 ((" s: "ID" nv "ID"\n", i, Nv [i])); /* ------------------------------------------------- */ /* remove variable i from degree link list */ /* ------------------------------------------------- */ ilast = Last [i] ; inext = Next [i] ; ASSERT (ilast >= EMPTY && ilast < n) ; ASSERT (inext >= EMPTY && inext < n) ; if (inext != EMPTY) Last [inext] = ilast ; if (ilast != EMPTY) { Next [ilast] = inext ; } else { /* i is at the head of the degree list */ ASSERT (Degree [i] >= 0 && Degree [i] < n) ; Head [Degree [i]] = inext ; } } } if (e != me) { /* set tree pointer and flag to indicate element e is * absorbed into new element me (the parent of e is me) */ AMD_DEBUG1 ((" Element "ID" => "ID"\n", e, me)) ; Pe [e] = FLIP (me) ; W [e] = 0 ; } } pme2 = pfree - 1 ; } /* ----------------------------------------------------------------- */ /* me has now been converted into an element in Iw [pme1..pme2] */ /* ----------------------------------------------------------------- */ /* degme holds the external degree of new element */ Degree [me] = degme ; Pe [me] = pme1 ; Len [me] = pme2 - pme1 + 1 ; ASSERT (Pe [me] >= 0 && Pe [me] < iwlen) ; Elen [me] = FLIP (nvpiv + degme) ; /* FLIP (Elen (me)) is now the degree of pivot (including * diagonal part). */ #ifndef NDEBUG AMD_DEBUG2 (("New element structure: length= "ID"\n", pme2-pme1+1)) ; for (pme = pme1 ; pme <= pme2 ; pme++) AMD_DEBUG3 ((" "ID"", Iw[pme])); AMD_DEBUG3 (("\n")) ; #endif /* ----------------------------------------------------------------- */ /* make sure that wflg is not too large. */ /* ----------------------------------------------------------------- */ /* With the current value of wflg, wflg+n must not cause integer * overflow */ wflg = clear_flag (wflg, wbig, W, n) ; /* ========================================================================= */ /* COMPUTE (W [e] - wflg) = |Le\Lme| FOR ALL ELEMENTS */ /* ========================================================================= */ /* ----------------------------------------------------------------- * Scan 1: compute the external degrees of previous elements with * respect to the current element. That is: * (W [e] - wflg) = |Le \ Lme| * for each element e that appears in any supervariable in Lme. The * notation Le refers to the pattern (list of supervariables) of a * previous element e, where e is not yet absorbed, stored in * Iw [Pe [e] + 1 ... Pe [e] + Len [e]]. The notation Lme * refers to the pattern of the current element (stored in * Iw [pme1..pme2]). If aggressive absorption is enabled, and * (W [e] - wflg) becomes zero, then the element e will be absorbed * in Scan 2. * ----------------------------------------------------------------- */ AMD_DEBUG2 (("me: ")) ; for (pme = pme1 ; pme <= pme2 ; pme++) { i = Iw [pme] ; ASSERT (i >= 0 && i < n) ; eln = Elen [i] ; AMD_DEBUG3 ((""ID" Elen "ID": \n", i, eln)) ; if (eln > 0) { /* note that Nv [i] has been negated to denote i in Lme: */ nvi = -Nv [i] ; ASSERT (nvi > 0 && Pe [i] >= 0 && Pe [i] < iwlen) ; wnvi = wflg - nvi ; for (p = Pe [i] ; p <= Pe [i] + eln - 1 ; p++) { e = Iw [p] ; ASSERT (e >= 0 && e < n) ; we = W [e] ; AMD_DEBUG4 ((" e "ID" we "ID" ", e, we)) ; if (we >= wflg) { /* unabsorbed element e has been seen in this loop */ AMD_DEBUG4 ((" unabsorbed, first time seen")) ; we -= nvi ; } else if (we != 0) { /* e is an unabsorbed element */ /* this is the first we have seen e in all of Scan 1 */ AMD_DEBUG4 ((" unabsorbed")) ; we = Degree [e] + wnvi ; } AMD_DEBUG4 (("\n")) ; W [e] = we ; } } } AMD_DEBUG2 (("\n")) ; /* ========================================================================= */ /* DEGREE UPDATE AND ELEMENT ABSORPTION */ /* ========================================================================= */ /* ----------------------------------------------------------------- * Scan 2: for each i in Lme, sum up the degree of Lme (which is * degme), plus the sum of the external degrees of each Le for the * elements e appearing within i, plus the supervariables in i. * Place i in hash list. * ----------------------------------------------------------------- */ for (pme = pme1 ; pme <= pme2 ; pme++) { i = Iw [pme] ; ASSERT (i >= 0 && i < n && Nv [i] < 0 && Elen [i] >= 0) ; AMD_DEBUG2 (("Updating: i "ID" "ID" "ID"\n", i, Elen[i], Len [i])); p1 = Pe [i] ; p2 = p1 + Elen [i] - 1 ; pn = p1 ; hash = 0 ; deg = 0 ; ASSERT (p1 >= 0 && p1 < iwlen && p2 >= -1 && p2 < iwlen) ; /* ------------------------------------------------------------- */ /* scan the element list associated with supervariable i */ /* ------------------------------------------------------------- */ /* UMFPACK/MA38-style approximate degree: */ if (aggressive) { for (p = p1 ; p <= p2 ; p++) { e = Iw [p] ; ASSERT (e >= 0 && e < n) ; we = W [e] ; if (we != 0) { /* e is an unabsorbed element */ /* dext = | Le \ Lme | */ dext = we - wflg ; if (dext > 0) { deg += dext ; Iw [pn++] = e ; hash += e ; AMD_DEBUG4 ((" e: "ID" hash = "ID"\n",e,hash)) ; } else { /* external degree of e is zero, absorb e into me*/ AMD_DEBUG1 ((" Element "ID" =>"ID" (aggressive)\n", e, me)) ; ASSERT (dext == 0) ; Pe [e] = FLIP (me) ; W [e] = 0 ; } } } } else { for (p = p1 ; p <= p2 ; p++) { e = Iw [p] ; ASSERT (e >= 0 && e < n) ; we = W [e] ; if (we != 0) { /* e is an unabsorbed element */ dext = we - wflg ; ASSERT (dext >= 0) ; deg += dext ; Iw [pn++] = e ; hash += e ; AMD_DEBUG4 ((" e: "ID" hash = "ID"\n",e,hash)) ; } } } /* count the number of elements in i (including me): */ Elen [i] = pn - p1 + 1 ; /* ------------------------------------------------------------- */ /* scan the supervariables in the list associated with i */ /* ------------------------------------------------------------- */ /* The bulk of the AMD run time is typically spent in this loop, * particularly if the matrix has many dense rows that are not * removed prior to ordering. */ p3 = pn ; p4 = p1 + Len [i] ; for (p = p2 + 1 ; p < p4 ; p++) { j = Iw [p] ; ASSERT (j >= 0 && j < n) ; nvj = Nv [j] ; if (nvj > 0) { /* j is unabsorbed, and not in Lme. */ /* add to degree and add to new list */ deg += nvj ; Iw [pn++] = j ; hash += j ; AMD_DEBUG4 ((" s: "ID" hash "ID" Nv[j]= "ID"\n", j, hash, nvj)) ; } } /* ------------------------------------------------------------- */ /* update the degree and check for mass elimination */ /* ------------------------------------------------------------- */ /* with aggressive absorption, deg==0 is identical to the * Elen [i] == 1 && p3 == pn test, below. */ ASSERT (IMPLIES (aggressive, (deg==0) == (Elen[i]==1 && p3==pn))) ; if (Elen [i] == 1 && p3 == pn) { /* --------------------------------------------------------- */ /* mass elimination */ /* --------------------------------------------------------- */ /* There is nothing left of this node except for an edge to * the current pivot element. Elen [i] is 1, and there are * no variables adjacent to node i. Absorb i into the * current pivot element, me. Note that if there are two or * more mass eliminations, fillin due to mass elimination is * possible within the nvpiv-by-nvpiv pivot block. It is this * step that causes AMD's analysis to be an upper bound. * * The reason is that the selected pivot has a lower * approximate degree than the true degree of the two mass * eliminated nodes. There is no edge between the two mass * eliminated nodes. They are merged with the current pivot * anyway. * * No fillin occurs in the Schur complement, in any case, * and this effect does not decrease the quality of the * ordering itself, just the quality of the nonzero and * flop count analysis. It also means that the post-ordering * is not an exact elimination tree post-ordering. */ AMD_DEBUG1 ((" MASS i "ID" => parent e "ID"\n", i, me)) ; Pe [i] = FLIP (me) ; nvi = -Nv [i] ; degme -= nvi ; nvpiv += nvi ; nel += nvi ; Nv [i] = 0 ; Elen [i] = EMPTY ; } else { /* --------------------------------------------------------- */ /* update the upper-bound degree of i */ /* --------------------------------------------------------- */ /* the following degree does not yet include the size * of the current element, which is added later: */ Degree [i] = MIN (Degree [i], deg) ; /* --------------------------------------------------------- */ /* add me to the list for i */ /* --------------------------------------------------------- */ /* move first supervariable to end of list */ Iw [pn] = Iw [p3] ; /* move first element to end of element part of list */ Iw [p3] = Iw [p1] ; /* add new element, me, to front of list. */ Iw [p1] = me ; /* store the new length of the list in Len [i] */ Len [i] = pn - p1 + 1 ; /* --------------------------------------------------------- */ /* place in hash bucket. Save hash key of i in Last [i]. */ /* --------------------------------------------------------- */ /* NOTE: this can fail if hash is negative, because the ANSI C * standard does not define a % b when a and/or b are negative. * That's why hash is defined as an unsigned Int, to avoid this * problem. */ hash = hash % n ; ASSERT (((Int) hash) >= 0 && ((Int) hash) < n) ; /* if the Hhead array is not used: */ j = Head [hash] ; if (j <= EMPTY) { /* degree list is empty, hash head is FLIP (j) */ Next [i] = FLIP (j) ; Head [hash] = FLIP (i) ; } else { /* degree list is not empty, use Last [Head [hash]] as * hash head. */ Next [i] = Last [j] ; Last [j] = i ; } /* if a separate Hhead array is used: * Next [i] = Hhead [hash] ; Hhead [hash] = i ; */ Last [i] = hash ; } } Degree [me] = degme ; /* ----------------------------------------------------------------- */ /* Clear the counter array, W [...], by incrementing wflg. */ /* ----------------------------------------------------------------- */ /* make sure that wflg+n does not cause integer overflow */ lemax = MAX (lemax, degme) ; wflg += lemax ; wflg = clear_flag (wflg, wbig, W, n) ; /* at this point, W [0..n-1] < wflg holds */ /* ========================================================================= */ /* SUPERVARIABLE DETECTION */ /* ========================================================================= */ AMD_DEBUG1 (("Detecting supervariables:\n")) ; for (pme = pme1 ; pme <= pme2 ; pme++) { i = Iw [pme] ; ASSERT (i >= 0 && i < n) ; AMD_DEBUG2 (("Consider i "ID" nv "ID"\n", i, Nv [i])) ; if (Nv [i] < 0) { /* i is a principal variable in Lme */ /* --------------------------------------------------------- * examine all hash buckets with 2 or more variables. We do * this by examing all unique hash keys for supervariables in * the pattern Lme of the current element, me * --------------------------------------------------------- */ /* let i = head of hash bucket, and empty the hash bucket */ ASSERT (Last [i] >= 0 && Last [i] < n) ; hash = Last [i] ; /* if Hhead array is not used: */ j = Head [hash] ; if (j == EMPTY) { /* hash bucket and degree list are both empty */ i = EMPTY ; } else if (j < EMPTY) { /* degree list is empty */ i = FLIP (j) ; Head [hash] = EMPTY ; } else { /* degree list is not empty, restore Last [j] of head j */ i = Last [j] ; Last [j] = EMPTY ; } /* if separate Hhead array is used: * i = Hhead [hash] ; Hhead [hash] = EMPTY ; */ ASSERT (i >= EMPTY && i < n) ; AMD_DEBUG2 (("----i "ID" hash "ID"\n", i, hash)) ; while (i != EMPTY && Next [i] != EMPTY) { /* ----------------------------------------------------- * this bucket has one or more variables following i. * scan all of them to see if i can absorb any entries * that follow i in hash bucket. Scatter i into w. * ----------------------------------------------------- */ ln = Len [i] ; eln = Elen [i] ; ASSERT (ln >= 0 && eln >= 0) ; ASSERT (Pe [i] >= 0 && Pe [i] < iwlen) ; /* do not flag the first element in the list (me) */ for (p = Pe [i] + 1 ; p <= Pe [i] + ln - 1 ; p++) { ASSERT (Iw [p] >= 0 && Iw [p] < n) ; W [Iw [p]] = wflg ; } /* ----------------------------------------------------- */ /* scan every other entry j following i in bucket */ /* ----------------------------------------------------- */ jlast = i ; j = Next [i] ; ASSERT (j >= EMPTY && j < n) ; while (j != EMPTY) { /* ------------------------------------------------- */ /* check if j and i have identical nonzero pattern */ /* ------------------------------------------------- */ AMD_DEBUG3 (("compare i "ID" and j "ID"\n", i,j)) ; /* check if i and j have the same Len and Elen */ ASSERT (Len [j] >= 0 && Elen [j] >= 0) ; ASSERT (Pe [j] >= 0 && Pe [j] < iwlen) ; ok = (Len [j] == ln) && (Elen [j] == eln) ; /* skip the first element in the list (me) */ for (p = Pe [j] + 1 ; ok && p <= Pe [j] + ln - 1 ; p++) { ASSERT (Iw [p] >= 0 && Iw [p] < n) ; if (W [Iw [p]] != wflg) ok = 0 ; } if (ok) { /* --------------------------------------------- */ /* found it! j can be absorbed into i */ /* --------------------------------------------- */ AMD_DEBUG1 (("found it! j "ID" => i "ID"\n", j,i)); Pe [j] = FLIP (i) ; /* both Nv [i] and Nv [j] are negated since they */ /* are in Lme, and the absolute values of each */ /* are the number of variables in i and j: */ Nv [i] += Nv [j] ; Nv [j] = 0 ; Elen [j] = EMPTY ; /* delete j from hash bucket */ ASSERT (j != Next [j]) ; j = Next [j] ; Next [jlast] = j ; } else { /* j cannot be absorbed into i */ jlast = j ; ASSERT (j != Next [j]) ; j = Next [j] ; } ASSERT (j >= EMPTY && j < n) ; } /* ----------------------------------------------------- * no more variables can be absorbed into i * go to next i in bucket and clear flag array * ----------------------------------------------------- */ wflg++ ; i = Next [i] ; ASSERT (i >= EMPTY && i < n) ; } } } AMD_DEBUG2 (("detect done\n")) ; /* ========================================================================= */ /* RESTORE DEGREE LISTS AND REMOVE NONPRINCIPAL SUPERVARIABLES FROM ELEMENT */ /* ========================================================================= */ p = pme1 ; nleft = n - nel ; for (pme = pme1 ; pme <= pme2 ; pme++) { i = Iw [pme] ; ASSERT (i >= 0 && i < n) ; nvi = -Nv [i] ; AMD_DEBUG3 (("Restore i "ID" "ID"\n", i, nvi)) ; if (nvi > 0) { /* i is a principal variable in Lme */ /* restore Nv [i] to signify that i is principal */ Nv [i] = nvi ; /* --------------------------------------------------------- */ /* compute the external degree (add size of current element) */ /* --------------------------------------------------------- */ deg = Degree [i] + degme - nvi ; deg = MIN (deg, nleft - nvi) ; ASSERT (IMPLIES (aggressive, deg > 0) && deg >= 0 && deg < n) ; /* --------------------------------------------------------- */ /* place the supervariable at the head of the degree list */ /* --------------------------------------------------------- */ inext = Head [deg] ; ASSERT (inext >= EMPTY && inext < n) ; if (inext != EMPTY) Last [inext] = i ; Next [i] = inext ; Last [i] = EMPTY ; Head [deg] = i ; /* --------------------------------------------------------- */ /* save the new degree, and find the minimum degree */ /* --------------------------------------------------------- */ mindeg = MIN (mindeg, deg) ; Degree [i] = deg ; /* --------------------------------------------------------- */ /* place the supervariable in the element pattern */ /* --------------------------------------------------------- */ Iw [p++] = i ; } } AMD_DEBUG2 (("restore done\n")) ; /* ========================================================================= */ /* FINALIZE THE NEW ELEMENT */ /* ========================================================================= */ AMD_DEBUG2 (("ME = "ID" DONE\n", me)) ; Nv [me] = nvpiv ; /* save the length of the list for the new element me */ Len [me] = p - pme1 ; if (Len [me] == 0) { /* there is nothing left of the current pivot element */ /* it is a root of the assembly tree */ Pe [me] = EMPTY ; W [me] = 0 ; } if (elenme != 0) { /* element was not constructed in place: deallocate part of */ /* it since newly nonprincipal variables may have been removed */ pfree = p ; } /* The new element has nvpiv pivots and the size of the contribution * block for a multifrontal method is degme-by-degme, not including * the "dense" rows/columns. If the "dense" rows/columns are included, * the frontal matrix is no larger than * (degme+ndense)-by-(degme+ndense). */ if (Info != (double *) NULL) { f = nvpiv ; r = degme + ndense ; dmax = MAX (dmax, f + r) ; /* number of nonzeros in L (excluding the diagonal) */ lnzme = f*r + (f-1)*f/2 ; lnz += lnzme ; /* number of divide operations for LDL' and for LU */ ndiv += lnzme ; /* number of multiply-subtract pairs for LU */ s = f*r*r + r*(f-1)*f + (f-1)*f*(2*f-1)/6 ; nms_lu += s ; /* number of multiply-subtract pairs for LDL' */ nms_ldl += (s + lnzme)/2 ; } #ifndef NDEBUG AMD_DEBUG2 (("finalize done nel "ID" n "ID"\n ::::\n", nel, n)) ; for (pme = Pe [me] ; pme <= Pe [me] + Len [me] - 1 ; pme++) { AMD_DEBUG3 ((" "ID"", Iw [pme])) ; } AMD_DEBUG3 (("\n")) ; #endif } /* ========================================================================= */ /* DONE SELECTING PIVOTS */ /* ========================================================================= */ if (Info != (double *) NULL) { /* count the work to factorize the ndense-by-ndense submatrix */ f = ndense ; dmax = MAX (dmax, (double) ndense) ; /* number of nonzeros in L (excluding the diagonal) */ lnzme = (f-1)*f/2 ; lnz += lnzme ; /* number of divide operations for LDL' and for LU */ ndiv += lnzme ; /* number of multiply-subtract pairs for LU */ s = (f-1)*f*(2*f-1)/6 ; nms_lu += s ; /* number of multiply-subtract pairs for LDL' */ nms_ldl += (s + lnzme)/2 ; /* number of nz's in L (excl. diagonal) */ Info [AMD_LNZ] = lnz ; /* number of divide ops for LU and LDL' */ Info [AMD_NDIV] = ndiv ; /* number of multiply-subtract pairs for LDL' */ Info [AMD_NMULTSUBS_LDL] = nms_ldl ; /* number of multiply-subtract pairs for LU */ Info [AMD_NMULTSUBS_LU] = nms_lu ; /* number of "dense" rows/columns */ Info [AMD_NDENSE] = ndense ; /* largest front is dmax-by-dmax */ Info [AMD_DMAX] = dmax ; /* number of garbage collections in AMD */ Info [AMD_NCMPA] = ncmpa ; /* successful ordering */ Info [AMD_STATUS] = AMD_OK ; } /* ========================================================================= */ /* POST-ORDERING */ /* ========================================================================= */ /* ------------------------------------------------------------------------- * Variables at this point: * * Pe: holds the elimination tree. The parent of j is FLIP (Pe [j]), * or EMPTY if j is a root. The tree holds both elements and * non-principal (unordered) variables absorbed into them. * Dense variables are non-principal and unordered. * * Elen: holds the size of each element, including the diagonal part. * FLIP (Elen [e]) > 0 if e is an element. For unordered * variables i, Elen [i] is EMPTY. * * Nv: Nv [e] > 0 is the number of pivots represented by the element e. * For unordered variables i, Nv [i] is zero. * * Contents no longer needed: * W, Iw, Len, Degree, Head, Next, Last. * * The matrix itself has been destroyed. * * n: the size of the matrix. * No other scalars needed (pfree, iwlen, etc.) * ------------------------------------------------------------------------- */ /* restore Pe */ for (i = 0 ; i < n ; i++) { Pe [i] = FLIP (Pe [i]) ; } /* restore Elen, for output information, and for postordering */ for (i = 0 ; i < n ; i++) { Elen [i] = FLIP (Elen [i]) ; } /* Now the parent of j is Pe [j], or EMPTY if j is a root. Elen [e] > 0 * is the size of element e. Elen [i] is EMPTY for unordered variable i. */ #ifndef NDEBUG AMD_DEBUG2 (("\nTree:\n")) ; for (i = 0 ; i < n ; i++) { AMD_DEBUG2 ((" "ID" parent: "ID" ", i, Pe [i])) ; ASSERT (Pe [i] >= EMPTY && Pe [i] < n) ; if (Nv [i] > 0) { /* this is an element */ e = i ; AMD_DEBUG2 ((" element, size is "ID"\n", Elen [i])) ; ASSERT (Elen [e] > 0) ; } AMD_DEBUG2 (("\n")) ; } AMD_DEBUG2 (("\nelements:\n")) ; for (e = 0 ; e < n ; e++) { if (Nv [e] > 0) { AMD_DEBUG3 (("Element e= "ID" size "ID" nv "ID" \n", e, Elen [e], Nv [e])) ; } } AMD_DEBUG2 (("\nvariables:\n")) ; for (i = 0 ; i < n ; i++) { Int cnt ; if (Nv [i] == 0) { AMD_DEBUG3 (("i unordered: "ID"\n", i)) ; j = Pe [i] ; cnt = 0 ; AMD_DEBUG3 ((" j: "ID"\n", j)) ; if (j == EMPTY) { AMD_DEBUG3 ((" i is a dense variable\n")) ; } else { ASSERT (j >= 0 && j < n) ; while (Nv [j] == 0) { AMD_DEBUG3 ((" j : "ID"\n", j)) ; j = Pe [j] ; AMD_DEBUG3 ((" j:: "ID"\n", j)) ; cnt++ ; if (cnt > n) break ; } e = j ; AMD_DEBUG3 ((" got to e: "ID"\n", e)) ; } } } #endif /* ========================================================================= */ /* compress the paths of the variables */ /* ========================================================================= */ for (i = 0 ; i < n ; i++) { if (Nv [i] == 0) { /* ------------------------------------------------------------- * i is an un-ordered row. Traverse the tree from i until * reaching an element, e. The element, e, was the principal * supervariable of i and all nodes in the path from i to when e * was selected as pivot. * ------------------------------------------------------------- */ AMD_DEBUG1 (("Path compression, i unordered: "ID"\n", i)) ; j = Pe [i] ; ASSERT (j >= EMPTY && j < n) ; AMD_DEBUG3 ((" j: "ID"\n", j)) ; if (j == EMPTY) { /* Skip a dense variable. It has no parent. */ AMD_DEBUG3 ((" i is a dense variable\n")) ; continue ; } /* while (j is a variable) */ while (Nv [j] == 0) { AMD_DEBUG3 ((" j : "ID"\n", j)) ; j = Pe [j] ; AMD_DEBUG3 ((" j:: "ID"\n", j)) ; ASSERT (j >= 0 && j < n) ; } /* got to an element e */ e = j ; AMD_DEBUG3 (("got to e: "ID"\n", e)) ; /* ------------------------------------------------------------- * traverse the path again from i to e, and compress the path * (all nodes point to e). Path compression allows this code to * compute in O(n) time. * ------------------------------------------------------------- */ j = i ; /* while (j is a variable) */ while (Nv [j] == 0) { jnext = Pe [j] ; AMD_DEBUG3 (("j "ID" jnext "ID"\n", j, jnext)) ; Pe [j] = e ; j = jnext ; ASSERT (j >= 0 && j < n) ; } } } /* ========================================================================= */ /* postorder the assembly tree */ /* ========================================================================= */ AMD_postorder (n, Pe, Nv, Elen, W, /* output order */ Head, Next, Last) ; /* workspace */ /* ========================================================================= */ /* compute output permutation and inverse permutation */ /* ========================================================================= */ /* W [e] = k means that element e is the kth element in the new * order. e is in the range 0 to n-1, and k is in the range 0 to * the number of elements. Use Head for inverse order. */ for (k = 0 ; k < n ; k++) { Head [k] = EMPTY ; Next [k] = EMPTY ; } for (e = 0 ; e < n ; e++) { k = W [e] ; ASSERT ((k == EMPTY) == (Nv [e] == 0)) ; if (k != EMPTY) { ASSERT (k >= 0 && k < n) ; Head [k] = e ; } } /* construct output inverse permutation in Next, * and permutation in Last */ nel = 0 ; for (k = 0 ; k < n ; k++) { e = Head [k] ; if (e == EMPTY) break ; ASSERT (e >= 0 && e < n && Nv [e] > 0) ; Next [e] = nel ; nel += Nv [e] ; } ASSERT (nel == n - ndense) ; /* order non-principal variables (dense, & those merged into supervar's) */ for (i = 0 ; i < n ; i++) { if (Nv [i] == 0) { e = Pe [i] ; ASSERT (e >= EMPTY && e < n) ; if (e != EMPTY) { /* This is an unordered variable that was merged * into element e via supernode detection or mass * elimination of i when e became the pivot element. * Place i in order just before e. */ ASSERT (Next [i] == EMPTY && Nv [e] > 0) ; Next [i] = Next [e] ; Next [e]++ ; } else { /* This is a dense unordered variable, with no parent. * Place it last in the output order. */ Next [i] = nel++ ; } } } ASSERT (nel == n) ; AMD_DEBUG2 (("\n\nPerm:\n")) ; for (i = 0 ; i < n ; i++) { k = Next [i] ; ASSERT (k >= 0 && k < n) ; Last [k] = i ; AMD_DEBUG2 ((" perm ["ID"] = "ID"\n", k, i)) ; } } sources_5316/external/glpk/glpapi05.c0000644000176700017670000001313111401660400016256 0ustar paulpaul/* glpapi05.c (LP basis constructing routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_set_row_stat - set (change) row status * * SYNOPSIS * * void glp_set_row_stat(glp_prob *lp, int i, int stat); * * DESCRIPTION * * The routine glp_set_row_stat sets (changes) status of the auxiliary * variable associated with i-th row. * * The new status of the auxiliary variable should be specified by the * parameter stat as follows: * * GLP_BS - basic variable; * GLP_NL - non-basic variable; * GLP_NU - non-basic variable on its upper bound; if the variable is * not double-bounded, this means the same as GLP_NL (only in * case of this routine); * GLP_NF - the same as GLP_NL (only in case of this routine); * GLP_NS - the same as GLP_NL (only in case of this routine). */ void glp_set_row_stat(glp_prob *lp, int i, int stat) { GLPROW *row; if (!(1 <= i && i <= lp->m)) xerror("glp_set_row_stat: i = %d; row number out of range\n", i); if (!(stat == GLP_BS || stat == GLP_NL || stat == GLP_NU || stat == GLP_NF || stat == GLP_NS)) xerror("glp_set_row_stat: i = %d; stat = %d; invalid status\n", i, stat); row = lp->row[i]; if (stat != GLP_BS) { switch (row->type) { case GLP_FR: stat = GLP_NF; break; case GLP_LO: stat = GLP_NL; break; case GLP_UP: stat = GLP_NU; break; case GLP_DB: if (stat != GLP_NU) stat = GLP_NL; break; case GLP_FX: stat = GLP_NS; break; default: xassert(row != row); } } if (row->stat == GLP_BS && stat != GLP_BS || row->stat != GLP_BS && stat == GLP_BS) { /* invalidate the basis factorization */ lp->valid = 0; } row->stat = stat; return; } /*********************************************************************** * NAME * * glp_set_col_stat - set (change) column status * * SYNOPSIS * * void glp_set_col_stat(glp_prob *lp, int j, int stat); * * DESCRIPTION * * The routine glp_set_col_stat sets (changes) status of the structural * variable associated with j-th column. * * The new status of the structural variable should be specified by the * parameter stat as follows: * * GLP_BS - basic variable; * GLP_NL - non-basic variable; * GLP_NU - non-basic variable on its upper bound; if the variable is * not double-bounded, this means the same as GLP_NL (only in * case of this routine); * GLP_NF - the same as GLP_NL (only in case of this routine); * GLP_NS - the same as GLP_NL (only in case of this routine). */ void glp_set_col_stat(glp_prob *lp, int j, int stat) { GLPCOL *col; if (!(1 <= j && j <= lp->n)) xerror("glp_set_col_stat: j = %d; column number out of range\n" , j); if (!(stat == GLP_BS || stat == GLP_NL || stat == GLP_NU || stat == GLP_NF || stat == GLP_NS)) xerror("glp_set_col_stat: j = %d; stat = %d; invalid status\n", j, stat); col = lp->col[j]; if (stat != GLP_BS) { switch (col->type) { case GLP_FR: stat = GLP_NF; break; case GLP_LO: stat = GLP_NL; break; case GLP_UP: stat = GLP_NU; break; case GLP_DB: if (stat != GLP_NU) stat = GLP_NL; break; case GLP_FX: stat = GLP_NS; break; default: xassert(col != col); } } if (col->stat == GLP_BS && stat != GLP_BS || col->stat != GLP_BS && stat == GLP_BS) { /* invalidate the basis factorization */ lp->valid = 0; } col->stat = stat; return; } /*********************************************************************** * NAME * * glp_std_basis - construct standard initial LP basis * * SYNOPSIS * * void glp_std_basis(glp_prob *lp); * * DESCRIPTION * * The routine glp_std_basis builds the "standard" (trivial) initial * basis for the specified problem object. * * In the "standard" basis all auxiliary variables are basic, and all * structural variables are non-basic. */ void glp_std_basis(glp_prob *lp) { int i, j; /* make all auxiliary variables basic */ for (i = 1; i <= lp->m; i++) glp_set_row_stat(lp, i, GLP_BS); /* make all structural variables non-basic */ for (j = 1; j <= lp->n; j++) { GLPCOL *col = lp->col[j]; if (col->type == GLP_DB && fabs(col->lb) > fabs(col->ub)) glp_set_col_stat(lp, j, GLP_NU); else glp_set_col_stat(lp, j, GLP_NL); } return; } /* eof */ sources_5316/external/glpk/glpini01.c0000644000176700017670000005415111401660400016267 0ustar paulpaul/* glpini01.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*---------------------------------------------------------------------- -- triang - find maximal triangular part of a rectangular matrix. -- -- *Synopsis* -- -- int triang(int m, int n, -- void *info, int (*mat)(void *info, int k, int ndx[]), -- int rn[], int cn[]); -- -- *Description* -- -- For a given rectangular (sparse) matrix A with m rows and n columns -- the routine triang tries to find such permutation matrices P and Q -- that the first rows and columns of the matrix B = P*A*Q form a lower -- triangular submatrix of as greatest size as possible: -- -- 1 n -- 1 * . . . . . . x x x x x x -- * * . . . . . x x x x x x -- * * * . . . . x x x x x x -- * * * * . . . x x x x x x -- B = P*A*Q = * * * * * . . x x x x x x -- * * * * * * . x x x x x x -- * * * * * * * x x x x x x -- x x x x x x x x x x x x x -- x x x x x x x x x x x x x -- m x x x x x x x x x x x x x -- -- where: '*' - elements of the lower triangular part, '.' - structural -- zeros, 'x' - other (either non-zero or zero) elements. -- -- The parameter info is a transit pointer passed to the formal routine -- mat (see below). -- -- The formal routine mat specifies the given matrix A in both row- and -- column-wise formats. In order to obtain an i-th row of the matrix A -- the routine triang calls the routine mat with the parameter k = +i, -- 1 <= i <= m. In response the routine mat should store column indices -- of (non-zero) elements of the i-th row to the locations ndx[1], ..., -- ndx[len], where len is number of non-zeros in the i-th row returned -- on exit. Analogously, in order to obtain a j-th column of the matrix -- A, the routine mat is called with the parameter k = -j, 1 <= j <= n, -- and should return pattern of the j-th column in the same way as for -- row patterns. Note that the routine mat may be called more than once -- for the same rows and columns. -- -- On exit the routine computes two resultant arrays rn and cn, which -- define the permutation matrices P and Q, respectively. The array rn -- should have at least 1+m locations, where rn[i] = i' (1 <= i <= m) -- means that i-th row of the original matrix A corresponds to i'-th row -- of the matrix B = P*A*Q. Similarly, the array cn should have at least -- 1+n locations, where cn[j] = j' (1 <= j <= n) means that j-th column -- of the matrix A corresponds to j'-th column of the matrix B. -- -- *Returns* -- -- The routine triang returns the size of the lower tringular part of -- the matrix B = P*A*Q (see the figure above). -- -- *Complexity* -- -- The time complexity of the routine triang is O(nnz), where nnz is -- number of non-zeros in the given matrix A. -- -- *Algorithm* -- -- The routine triang starts from the matrix B = P*Q*A, where P and Q -- are unity matrices, so initially B = A. -- -- Before the next iteration B = (B1 | B2 | B3), where B1 is partially -- built a lower triangular submatrix, B2 is the active submatrix, and -- B3 is a submatrix that contains rejected columns. Thus, the current -- matrix B looks like follows (initially k1 = 1 and k2 = n): -- -- 1 k1 k2 n -- 1 x . . . . . . . . . . . . . # # # -- x x . . . . . . . . . . . . # # # -- x x x . . . . . . . . . . # # # # -- x x x x . . . . . . . . . # # # # -- x x x x x . . . . . . . # # # # # -- k1 x x x x x * * * * * * * # # # # # -- x x x x x * * * * * * * # # # # # -- x x x x x * * * * * * * # # # # # -- x x x x x * * * * * * * # # # # # -- m x x x x x * * * * * * * # # # # # -- <--B1---> <----B2-----> <---B3--> -- -- On each iteartion the routine looks for a singleton row, i.e. some -- row that has the only non-zero in the active submatrix B2. If such -- row exists and the corresponding non-zero is b[i,j], where (by the -- definition) k1 <= i <= m and k1 <= j <= k2, the routine permutes -- k1-th and i-th rows and k1-th and j-th columns of the matrix B (in -- order to place the element in the position b[k1,k1]), removes the -- k1-th column from the active submatrix B2, and adds this column to -- the submatrix B1. If no row singletons exist, but B2 is not empty -- yet, the routine chooses a j-th column, which has maximal number of -- non-zeros among other columns of B2, removes this column from B2 and -- adds it to the submatrix B3 in the hope that new row singletons will -- appear in the active submatrix. */ static int triang(int m, int n, void *info, int (*mat)(void *info, int k, int ndx[]), int rn[], int cn[]) { int *ndx; /* int ndx[1+max(m,n)]; */ /* this array is used for querying row and column patterns of the given matrix A (the third parameter to the routine mat) */ int *rs_len; /* int rs_len[1+m]; */ /* rs_len[0] is not used; rs_len[i], 1 <= i <= m, is number of non-zeros in the i-th row of the matrix A, which (non-zeros) belong to the current active submatrix */ int *rs_head; /* int rs_head[1+n]; */ /* rs_head[len], 0 <= len <= n, is the number i of the first row of the matrix A, for which rs_len[i] = len */ int *rs_prev; /* int rs_prev[1+m]; */ /* rs_prev[0] is not used; rs_prev[i], 1 <= i <= m, is a number i' of the previous row of the matrix A, for which rs_len[i] = rs_len[i'] (zero marks the end of this linked list) */ int *rs_next; /* int rs_next[1+m]; */ /* rs_next[0] is not used; rs_next[i], 1 <= i <= m, is a number i' of the next row of the matrix A, for which rs_len[i] = rs_len[i'] (zero marks the end this linked list) */ int cs_head; /* is a number j of the first column of the matrix A, which has maximal number of non-zeros among other columns */ int *cs_prev; /* cs_prev[1+n]; */ /* cs_prev[0] is not used; cs_prev[j], 1 <= j <= n, is a number of the previous column of the matrix A with the same or greater number of non-zeros than in the j-th column (zero marks the end of this linked list) */ int *cs_next; /* cs_next[1+n]; */ /* cs_next[0] is not used; cs_next[j], 1 <= j <= n, is a number of the next column of the matrix A with the same or lesser number of non-zeros than in the j-th column (zero marks the end of this linked list) */ int i, j, ii, jj, k1, k2, len, t, size = 0; int *head, *rn_inv, *cn_inv; if (!(m > 0 && n > 0)) xerror("triang: m = %d; n = %d; invalid dimension\n", m, n); /* allocate working arrays */ ndx = xcalloc(1+(m >= n ? m : n), sizeof(int)); rs_len = xcalloc(1+m, sizeof(int)); rs_head = xcalloc(1+n, sizeof(int)); rs_prev = xcalloc(1+m, sizeof(int)); rs_next = xcalloc(1+m, sizeof(int)); cs_prev = xcalloc(1+n, sizeof(int)); cs_next = xcalloc(1+n, sizeof(int)); /* build linked lists of columns of the matrix A with the same number of non-zeros */ head = rs_len; /* currently rs_len is used as working array */ for (len = 0; len <= m; len ++) head[len] = 0; for (j = 1; j <= n; j++) { /* obtain length of the j-th column */ len = mat(info, -j, ndx); xassert(0 <= len && len <= m); /* include the j-th column in the corresponding linked list */ cs_prev[j] = head[len]; head[len] = j; } /* merge all linked lists of columns in one linked list, where columns are ordered by descending of their lengths */ cs_head = 0; for (len = 0; len <= m; len++) { for (j = head[len]; j != 0; j = cs_prev[j]) { cs_next[j] = cs_head; cs_head = j; } } jj = 0; for (j = cs_head; j != 0; j = cs_next[j]) { cs_prev[j] = jj; jj = j; } /* build initial doubly linked lists of rows of the matrix A with the same number of non-zeros */ for (len = 0; len <= n; len++) rs_head[len] = 0; for (i = 1; i <= m; i++) { /* obtain length of the i-th row */ rs_len[i] = len = mat(info, +i, ndx); xassert(0 <= len && len <= n); /* include the i-th row in the correspondng linked list */ rs_prev[i] = 0; rs_next[i] = rs_head[len]; if (rs_next[i] != 0) rs_prev[rs_next[i]] = i; rs_head[len] = i; } /* initially all rows and columns of the matrix A are active */ for (i = 1; i <= m; i++) rn[i] = 0; for (j = 1; j <= n; j++) cn[j] = 0; /* set initial bounds of the active submatrix */ k1 = 1, k2 = n; /* main loop starts here */ while (k1 <= k2) { i = rs_head[1]; if (i != 0) { /* the i-th row of the matrix A is a row singleton, since it has the only non-zero in the active submatrix */ xassert(rs_len[i] == 1); /* determine the number j of an active column of the matrix A, in which this non-zero is placed */ j = 0; t = mat(info, +i, ndx); xassert(0 <= t && t <= n); for (t = t; t >= 1; t--) { jj = ndx[t]; xassert(1 <= jj && jj <= n); if (cn[jj] == 0) { xassert(j == 0); j = jj; } } xassert(j != 0); /* the singleton is a[i,j]; move a[i,j] to the position b[k1,k1] of the matrix B */ rn[i] = cn[j] = k1; /* shift the left bound of the active submatrix */ k1++; /* increase the size of the lower triangular part */ size++; } else { /* the current active submatrix has no row singletons */ /* remove an active column with maximal number of non-zeros from the active submatrix */ j = cs_head; xassert(j != 0); cn[j] = k2; /* shift the right bound of the active submatrix */ k2--; } /* the j-th column of the matrix A has been removed from the active submatrix */ /* remove the j-th column from the linked list */ if (cs_prev[j] == 0) cs_head = cs_next[j]; else cs_next[cs_prev[j]] = cs_next[j]; if (cs_next[j] == 0) /* nop */; else cs_prev[cs_next[j]] = cs_prev[j]; /* go through non-zeros of the j-th columns and update active lengths of the corresponding rows */ t = mat(info, -j, ndx); xassert(0 <= t && t <= m); for (t = t; t >= 1; t--) { i = ndx[t]; xassert(1 <= i && i <= m); /* the non-zero a[i,j] has left the active submatrix */ len = rs_len[i]; xassert(len >= 1); /* remove the i-th row from the linked list of rows with active length len */ if (rs_prev[i] == 0) rs_head[len] = rs_next[i]; else rs_next[rs_prev[i]] = rs_next[i]; if (rs_next[i] == 0) /* nop */; else rs_prev[rs_next[i]] = rs_prev[i]; /* decrease the active length of the i-th row */ rs_len[i] = --len; /* return the i-th row to the corresponding linked list */ rs_prev[i] = 0; rs_next[i] = rs_head[len]; if (rs_next[i] != 0) rs_prev[rs_next[i]] = i; rs_head[len] = i; } } /* other rows of the matrix A, which are still active, correspond to rows k1, ..., m of the matrix B (in arbitrary order) */ for (i = 1; i <= m; i++) if (rn[i] == 0) rn[i] = k1++; /* but for columns this is not needed, because now the submatrix B2 has no columns */ for (j = 1; j <= n; j++) xassert(cn[j] != 0); /* perform some optional checks */ /* make sure that rn is a permutation of {1, ..., m} and cn is a permutation of {1, ..., n} */ rn_inv = rs_len; /* used as working array */ for (ii = 1; ii <= m; ii++) rn_inv[ii] = 0; for (i = 1; i <= m; i++) { ii = rn[i]; xassert(1 <= ii && ii <= m); xassert(rn_inv[ii] == 0); rn_inv[ii] = i; } cn_inv = rs_head; /* used as working array */ for (jj = 1; jj <= n; jj++) cn_inv[jj] = 0; for (j = 1; j <= n; j++) { jj = cn[j]; xassert(1 <= jj && jj <= n); xassert(cn_inv[jj] == 0); cn_inv[jj] = j; } /* make sure that the matrix B = P*A*Q really has the form, which was declared */ for (ii = 1; ii <= size; ii++) { int diag = 0; i = rn_inv[ii]; t = mat(info, +i, ndx); xassert(0 <= t && t <= n); for (t = t; t >= 1; t--) { j = ndx[t]; xassert(1 <= j && j <= n); jj = cn[j]; if (jj <= size) xassert(jj <= ii); if (jj == ii) { xassert(!diag); diag = 1; } } xassert(diag); } /* free working arrays */ xfree(ndx); xfree(rs_len); xfree(rs_head); xfree(rs_prev); xfree(rs_next); xfree(cs_prev); xfree(cs_next); /* return to the calling program */ return size; } /*---------------------------------------------------------------------- -- adv_basis - construct advanced initial LP basis. -- -- *Synopsis* -- -- #include "glpini.h" -- void adv_basis(glp_prob *lp); -- -- *Description* -- -- The routine adv_basis constructs an advanced initial basis for an LP -- problem object, which the parameter lp points to. -- -- In order to build the initial basis the routine does the following: -- -- 1) includes in the basis all non-fixed auxiliary variables; -- -- 2) includes in the basis as many as possible non-fixed structural -- variables preserving triangular form of the basis matrix; -- -- 3) includes in the basis appropriate (fixed) auxiliary variables -- in order to complete the basis. -- -- As a result the initial basis has minimum of fixed variables and the -- corresponding basis matrix is triangular. */ static int mat(void *info, int k, int ndx[]) { /* this auxiliary routine returns the pattern of a given row or a given column of the augmented constraint matrix A~ = (I|-A), in which columns of fixed variables are implicitly cleared */ LPX *lp = info; int m = lpx_get_num_rows(lp); int n = lpx_get_num_cols(lp); int typx, i, j, lll, len = 0; if (k > 0) { /* the pattern of the i-th row is required */ i = +k; xassert(1 <= i && i <= m); #if 0 /* 22/XII-2003 */ /* if the auxiliary variable x[i] is non-fixed, include its element (placed in the i-th column) in the pattern */ lpx_get_row_bnds(lp, i, &typx, NULL, NULL); if (typx != LPX_FX) ndx[++len] = i; /* include in the pattern elements placed in columns, which correspond to non-fixed structural varables */ i_beg = aa_ptr[i]; i_end = i_beg + aa_len[i] - 1; for (i_ptr = i_beg; i_ptr <= i_end; i_ptr++) { j = m + sv_ndx[i_ptr]; lpx_get_col_bnds(lp, j-m, &typx, NULL, NULL); if (typx != LPX_FX) ndx[++len] = j; } #else lll = lpx_get_mat_row(lp, i, ndx, NULL); for (k = 1; k <= lll; k++) { lpx_get_col_bnds(lp, ndx[k], &typx, NULL, NULL); if (typx != LPX_FX) ndx[++len] = m + ndx[k]; } lpx_get_row_bnds(lp, i, &typx, NULL, NULL); if (typx != LPX_FX) ndx[++len] = i; #endif } else { /* the pattern of the j-th column is required */ j = -k; xassert(1 <= j && j <= m+n); /* if the (auxiliary or structural) variable x[j] is fixed, the pattern of its column is empty */ if (j <= m) lpx_get_row_bnds(lp, j, &typx, NULL, NULL); else lpx_get_col_bnds(lp, j-m, &typx, NULL, NULL); if (typx != LPX_FX) { if (j <= m) { /* x[j] is non-fixed auxiliary variable */ ndx[++len] = j; } else { /* x[j] is non-fixed structural variables */ #if 0 /* 22/XII-2003 */ j_beg = aa_ptr[j]; j_end = j_beg + aa_len[j] - 1; for (j_ptr = j_beg; j_ptr <= j_end; j_ptr++) ndx[++len] = sv_ndx[j_ptr]; #else len = lpx_get_mat_col(lp, j-m, ndx, NULL); #endif } } } /* return the length of the row/column pattern */ return len; } static void adv_basis(glp_prob *lp) { int m = lpx_get_num_rows(lp); int n = lpx_get_num_cols(lp); int i, j, jj, k, size; int *rn, *cn, *rn_inv, *cn_inv; int typx, *tagx = xcalloc(1+m+n, sizeof(int)); double lb, ub; xprintf("Constructing initial basis...\n"); #if 0 /* 13/V-2009 */ if (m == 0) xerror("glp_adv_basis: problem has no rows\n"); if (n == 0) xerror("glp_adv_basis: problem has no columns\n"); #else if (m == 0 || n == 0) { glp_std_basis(lp); return; } #endif /* use the routine triang (see above) to find maximal triangular part of the augmented constraint matrix A~ = (I|-A); in order to prevent columns of fixed variables to be included in the triangular part, such columns are implictly removed from the matrix A~ by the routine adv_mat */ rn = xcalloc(1+m, sizeof(int)); cn = xcalloc(1+m+n, sizeof(int)); size = triang(m, m+n, lp, mat, rn, cn); if (lpx_get_int_parm(lp, LPX_K_MSGLEV) >= 3) xprintf("Size of triangular part = %d\n", size); /* the first size rows and columns of the matrix P*A~*Q (where P and Q are permutation matrices defined by the arrays rn and cn) form a lower triangular matrix; build the arrays (rn_inv and cn_inv), which define the matrices inv(P) and inv(Q) */ rn_inv = xcalloc(1+m, sizeof(int)); cn_inv = xcalloc(1+m+n, sizeof(int)); for (i = 1; i <= m; i++) rn_inv[rn[i]] = i; for (j = 1; j <= m+n; j++) cn_inv[cn[j]] = j; /* include the columns of the matrix A~, which correspond to the first size columns of the matrix P*A~*Q, in the basis */ for (k = 1; k <= m+n; k++) tagx[k] = -1; for (jj = 1; jj <= size; jj++) { j = cn_inv[jj]; /* the j-th column of A~ is the jj-th column of P*A~*Q */ tagx[j] = LPX_BS; } /* if size < m, we need to add appropriate columns of auxiliary variables to the basis */ for (jj = size + 1; jj <= m; jj++) { /* the jj-th column of P*A~*Q should be replaced by the column of the auxiliary variable, for which the only unity element is placed in the position [jj,jj] */ i = rn_inv[jj]; /* the jj-th row of P*A~*Q is the i-th row of A~, but in the i-th row of A~ the unity element belongs to the i-th column of A~; therefore the disired column corresponds to the i-th auxiliary variable (note that this column doesn't belong to the triangular part found by the routine triang) */ xassert(1 <= i && i <= m); xassert(cn[i] > size); tagx[i] = LPX_BS; } /* free working arrays */ xfree(rn); xfree(cn); xfree(rn_inv); xfree(cn_inv); /* build tags of non-basic variables */ for (k = 1; k <= m+n; k++) { if (tagx[k] != LPX_BS) { if (k <= m) lpx_get_row_bnds(lp, k, &typx, &lb, &ub); else lpx_get_col_bnds(lp, k-m, &typx, &lb, &ub); switch (typx) { case LPX_FR: tagx[k] = LPX_NF; break; case LPX_LO: tagx[k] = LPX_NL; break; case LPX_UP: tagx[k] = LPX_NU; break; case LPX_DB: tagx[k] = (fabs(lb) <= fabs(ub) ? LPX_NL : LPX_NU); break; case LPX_FX: tagx[k] = LPX_NS; break; default: xassert(typx != typx); } } } for (k = 1; k <= m+n; k++) { if (k <= m) lpx_set_row_stat(lp, k, tagx[k]); else lpx_set_col_stat(lp, k-m, tagx[k]); } xfree(tagx); return; } /*********************************************************************** * NAME * * glp_adv_basis - construct advanced initial LP basis * * SYNOPSIS * * void glp_adv_basis(glp_prob *lp, int flags); * * DESCRIPTION * * The routine glp_adv_basis constructs an advanced initial basis for * the specified problem object. * * The parameter flags is reserved for use in the future and must be * specified as zero. */ void glp_adv_basis(glp_prob *lp, int flags) { if (flags != 0) xerror("glp_adv_basis: flags = %d; invalid flags\n", flags); if (lp->m == 0 || lp->n == 0) glp_std_basis(lp); else adv_basis(lp); return; } /* eof */ sources_5316/external/glpk/glpk.h0000644000176700017670000016542711631540522015626 0ustar paulpaul/* glpk.h */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPK_H #define GLPK_H #include #include #if defined (__MINGW32__) && ! defined (DBL_EPSILON) #define DBL_EPSILON 2.2204460492503131e-16 // ppgb 20110903 #endif #ifdef __cplusplus extern "C" { #endif /* library version numbers: */ #define GLP_MAJOR_VERSION 4 #define GLP_MINOR_VERSION 44 #ifndef GLP_PROB_DEFINED #define GLP_PROB_DEFINED typedef struct { double _opaque_prob[100]; } glp_prob; /* LP/MIP problem object */ #endif /* optimization direction flag: */ #define GLP_MIN 1 /* minimization */ #define GLP_MAX 2 /* maximization */ /* kind of structural variable: */ #define GLP_CV 1 /* continuous variable */ #define GLP_IV 2 /* integer variable */ #define GLP_BV 3 /* binary variable */ /* type of auxiliary/structural variable: */ #define GLP_FR 1 /* free variable */ #define GLP_LO 2 /* variable with lower bound */ #define GLP_UP 3 /* variable with upper bound */ #define GLP_DB 4 /* double-bounded variable */ #define GLP_FX 5 /* fixed variable */ /* status of auxiliary/structural variable: */ #define GLP_BS 1 /* basic variable */ #define GLP_NL 2 /* non-basic variable on lower bound */ #define GLP_NU 3 /* non-basic variable on upper bound */ #define GLP_NF 4 /* non-basic free variable */ #define GLP_NS 5 /* non-basic fixed variable */ /* scaling options: */ #define GLP_SF_GM 0x01 /* perform geometric mean scaling */ #define GLP_SF_EQ 0x10 /* perform equilibration scaling */ #define GLP_SF_2N 0x20 /* round scale factors to power of two */ #define GLP_SF_SKIP 0x40 /* skip if problem is well scaled */ #define GLP_SF_AUTO 0x80 /* choose scaling options automatically */ /* solution indicator: */ #define GLP_SOL 1 /* basic solution */ #define GLP_IPT 2 /* interior-point solution */ #define GLP_MIP 3 /* mixed integer solution */ /* solution status: */ #define GLP_UNDEF 1 /* solution is undefined */ #define GLP_FEAS 2 /* solution is feasible */ #define GLP_INFEAS 3 /* solution is infeasible */ #define GLP_NOFEAS 4 /* no feasible solution exists */ #define GLP_OPT 5 /* solution is optimal */ #define GLP_UNBND 6 /* solution is unbounded */ typedef struct { /* basis factorization control parameters */ int msg_lev; /* (reserved) */ int type; /* factorization type: */ #define GLP_BF_FT 1 /* LUF + Forrest-Tomlin */ #define GLP_BF_BG 2 /* LUF + Schur compl. + Bartels-Golub */ #define GLP_BF_GR 3 /* LUF + Schur compl. + Givens rotation */ int lu_size; /* luf.sv_size */ double piv_tol; /* luf.piv_tol */ int piv_lim; /* luf.piv_lim */ int suhl; /* luf.suhl */ double eps_tol; /* luf.eps_tol */ double max_gro; /* luf.max_gro */ int nfs_max; /* fhv.hh_max */ double upd_tol; /* fhv.upd_tol */ int nrs_max; /* lpf.n_max */ int rs_size; /* lpf.v_size */ double foo_bar[38]; /* (reserved) */ } glp_bfcp; typedef struct { /* simplex method control parameters */ int msg_lev; /* message level: */ #define GLP_MSG_OFF 0 /* no output */ #define GLP_MSG_ERR 1 /* warning and error messages only */ #define GLP_MSG_ON 2 /* normal output */ #define GLP_MSG_ALL 3 /* full output */ #define GLP_MSG_DBG 4 /* debug output */ int meth; /* simplex method option: */ #define GLP_PRIMAL 1 /* use primal simplex */ #define GLP_DUALP 2 /* use dual; if it fails, use primal */ #define GLP_DUAL 3 /* use dual simplex */ int pricing; /* pricing technique: */ #define GLP_PT_STD 0x11 /* standard (Dantzig rule) */ #define GLP_PT_PSE 0x22 /* projected steepest edge */ int r_test; /* ratio test technique: */ #define GLP_RT_STD 0x11 /* standard (textbook) */ #define GLP_RT_HAR 0x22 /* two-pass Harris' ratio test */ double tol_bnd; /* spx.tol_bnd */ double tol_dj; /* spx.tol_dj */ double tol_piv; /* spx.tol_piv */ double obj_ll; /* spx.obj_ll */ double obj_ul; /* spx.obj_ul */ int it_lim; /* spx.it_lim */ int tm_lim; /* spx.tm_lim (milliseconds) */ int out_frq; /* spx.out_frq */ int out_dly; /* spx.out_dly (milliseconds) */ int presolve; /* enable/disable using LP presolver */ double foo_bar[36]; /* (reserved) */ } glp_smcp; typedef struct { /* interior-point solver control parameters */ int msg_lev; /* message level (see glp_smcp) */ int ord_alg; /* ordering algorithm: */ #define GLP_ORD_NONE 0 /* natural (original) ordering */ #define GLP_ORD_QMD 1 /* quotient minimum degree (QMD) */ #define GLP_ORD_AMD 2 /* approx. minimum degree (AMD) */ #define GLP_ORD_SYMAMD 3 /* approx. minimum degree (SYMAMD) */ double foo_bar[48]; /* (reserved) */ } glp_iptcp; #ifndef GLP_TREE_DEFINED #define GLP_TREE_DEFINED typedef struct { double _opaque_tree[100]; } glp_tree; /* branch-and-bound tree */ #endif typedef struct { /* integer optimizer control parameters */ int msg_lev; /* message level (see glp_smcp) */ int br_tech; /* branching technique: */ #define GLP_BR_FFV 1 /* first fractional variable */ #define GLP_BR_LFV 2 /* last fractional variable */ #define GLP_BR_MFV 3 /* most fractional variable */ #define GLP_BR_DTH 4 /* heuristic by Driebeck and Tomlin */ #define GLP_BR_PCH 5 /* hybrid pseudocost heuristic */ int bt_tech; /* backtracking technique: */ #define GLP_BT_DFS 1 /* depth first search */ #define GLP_BT_BFS 2 /* breadth first search */ #define GLP_BT_BLB 3 /* best local bound */ #define GLP_BT_BPH 4 /* best projection heuristic */ double tol_int; /* mip.tol_int */ double tol_obj; /* mip.tol_obj */ int tm_lim; /* mip.tm_lim (milliseconds) */ int out_frq; /* mip.out_frq (milliseconds) */ int out_dly; /* mip.out_dly (milliseconds) */ void (*cb_func)(glp_tree *T, void *info); /* mip.cb_func */ void *cb_info; /* mip.cb_info */ int cb_size; /* mip.cb_size */ int pp_tech; /* preprocessing technique: */ #define GLP_PP_NONE 0 /* disable preprocessing */ #define GLP_PP_ROOT 1 /* preprocessing only on root level */ #define GLP_PP_ALL 2 /* preprocessing on all levels */ double mip_gap; /* relative MIP gap tolerance */ int mir_cuts; /* MIR cuts (GLP_ON/GLP_OFF) */ int gmi_cuts; /* Gomory's cuts (GLP_ON/GLP_OFF) */ int cov_cuts; /* cover cuts (GLP_ON/GLP_OFF) */ int clq_cuts; /* clique cuts (GLP_ON/GLP_OFF) */ int presolve; /* enable/disable using MIP presolver */ int binarize; /* try to binarize integer variables */ int fp_heur; /* feasibility pump heuristic */ #if 1 /* 28/V-2010 */ int alien; /* use alien solver */ #endif double foo_bar[29]; /* (reserved) */ } glp_iocp; typedef struct { /* additional row attributes */ int level; /* subproblem level at which the row was added */ int origin; /* row origin flag: */ #define GLP_RF_REG 0 /* regular constraint */ #define GLP_RF_LAZY 1 /* "lazy" constraint */ #define GLP_RF_CUT 2 /* cutting plane constraint */ int klass; /* row class descriptor: */ #define GLP_RF_GMI 1 /* Gomory's mixed integer cut */ #define GLP_RF_MIR 2 /* mixed integer rounding cut */ #define GLP_RF_COV 3 /* mixed cover cut */ #define GLP_RF_CLQ 4 /* clique cut */ double foo_bar[7]; /* (reserved) */ } glp_attr; /* enable/disable flag: */ #define GLP_ON 1 /* enable something */ #define GLP_OFF 0 /* disable something */ /* reason codes: */ #define GLP_IROWGEN 0x01 /* request for row generation */ #define GLP_IBINGO 0x02 /* better integer solution found */ #define GLP_IHEUR 0x03 /* request for heuristic solution */ #define GLP_ICUTGEN 0x04 /* request for cut generation */ #define GLP_IBRANCH 0x05 /* request for branching */ #define GLP_ISELECT 0x06 /* request for subproblem selection */ #define GLP_IPREPRO 0x07 /* request for preprocessing */ /* branch selection indicator: */ #define GLP_NO_BRNCH 0 /* select no branch */ #define GLP_DN_BRNCH 1 /* select down-branch */ #define GLP_UP_BRNCH 2 /* select up-branch */ /* return codes: */ #define GLP_EBADB 0x01 /* invalid basis */ #define GLP_ESING 0x02 /* singular matrix */ #define GLP_ECOND 0x03 /* ill-conditioned matrix */ #define GLP_EBOUND 0x04 /* invalid bounds */ #define GLP_EFAIL 0x05 /* solver failed */ #define GLP_EOBJLL 0x06 /* objective lower limit reached */ #define GLP_EOBJUL 0x07 /* objective upper limit reached */ #define GLP_EITLIM 0x08 /* iteration limit exceeded */ #define GLP_ETMLIM 0x09 /* time limit exceeded */ #define GLP_ENOPFS 0x0A /* no primal feasible solution */ #define GLP_ENODFS 0x0B /* no dual feasible solution */ #define GLP_EROOT 0x0C /* root LP optimum not provided */ #define GLP_ESTOP 0x0D /* search terminated by application */ #define GLP_EMIPGAP 0x0E /* relative mip gap tolerance reached */ #define GLP_ENOFEAS 0x0F /* no primal/dual feasible solution */ #define GLP_ENOCVG 0x10 /* no convergence */ #define GLP_EINSTAB 0x11 /* numerical instability */ #define GLP_EDATA 0x12 /* invalid data */ #define GLP_ERANGE 0x13 /* result out of range */ /* condition indicator: */ #define GLP_KKT_PE 1 /* primal equalities */ #define GLP_KKT_PB 2 /* primal bounds */ #define GLP_KKT_DE 3 /* dual equalities */ #define GLP_KKT_DB 4 /* dual bounds */ #define GLP_KKT_CS 5 /* complementary slackness */ /* MPS file format: */ #define GLP_MPS_DECK 1 /* fixed (ancient) */ #define GLP_MPS_FILE 2 /* free (modern) */ typedef struct { /* MPS format control parameters */ int blank; /* character code to replace blanks in symbolic names */ char *obj_name; /* objective row name */ double tol_mps; /* zero tolerance for MPS data */ double foo_bar[17]; /* (reserved for use in the future) */ } glp_mpscp; typedef struct { /* CPLEX LP format control parameters */ double foo_bar[20]; /* (reserved for use in the future) */ } glp_cpxcp; #ifndef GLP_TRAN_DEFINED #define GLP_TRAN_DEFINED typedef struct { double _opaque_tran[100]; } glp_tran; /* MathProg translator workspace */ #endif glp_prob *glp_create_prob(void); /* create problem object */ void glp_set_prob_name(glp_prob *P, const char *name); /* assign (change) problem name */ void glp_set_obj_name(glp_prob *P, const char *name); /* assign (change) objective function name */ void glp_set_obj_dir(glp_prob *P, int dir); /* set (change) optimization direction flag */ int glp_add_rows(glp_prob *P, int nrs); /* add new rows to problem object */ int glp_add_cols(glp_prob *P, int ncs); /* add new columns to problem object */ void glp_set_row_name(glp_prob *P, int i, const char *name); /* assign (change) row name */ void glp_set_col_name(glp_prob *P, int j, const char *name); /* assign (change) column name */ void glp_set_row_bnds(glp_prob *P, int i, int type, double lb, double ub); /* set (change) row bounds */ void glp_set_col_bnds(glp_prob *P, int j, int type, double lb, double ub); /* set (change) column bounds */ void glp_set_obj_coef(glp_prob *P, int j, double coef); /* set (change) obj. coefficient or constant term */ void glp_set_mat_row(glp_prob *P, int i, int len, const int ind[], const double val[]); /* set (replace) row of the constraint matrix */ void glp_set_mat_col(glp_prob *P, int j, int len, const int ind[], const double val[]); /* set (replace) column of the constraint matrix */ void glp_load_matrix(glp_prob *P, int ne, const int ia[], const int ja[], const double ar[]); /* load (replace) the whole constraint matrix */ int glp_check_dup(int m, int n, int ne, const int ia[], const int ja[]); /* check for duplicate elements in sparse matrix */ void glp_sort_matrix(glp_prob *P); /* sort elements of the constraint matrix */ void glp_del_rows(glp_prob *P, int nrs, const int num[]); /* delete specified rows from problem object */ void glp_del_cols(glp_prob *P, int ncs, const int num[]); /* delete specified columns from problem object */ void glp_copy_prob(glp_prob *dest, glp_prob *prob, int names); /* copy problem object content */ void glp_erase_prob(glp_prob *P); /* erase problem object content */ void glp_delete_prob(glp_prob *P); /* delete problem object */ const char *glp_get_prob_name(glp_prob *P); /* retrieve problem name */ const char *glp_get_obj_name(glp_prob *P); /* retrieve objective function name */ int glp_get_obj_dir(glp_prob *P); /* retrieve optimization direction flag */ int glp_get_num_rows(glp_prob *P); /* retrieve number of rows */ int glp_get_num_cols(glp_prob *P); /* retrieve number of columns */ const char *glp_get_row_name(glp_prob *P, int i); /* retrieve row name */ const char *glp_get_col_name(glp_prob *P, int j); /* retrieve column name */ int glp_get_row_type(glp_prob *P, int i); /* retrieve row type */ double glp_get_row_lb(glp_prob *P, int i); /* retrieve row lower bound */ double glp_get_row_ub(glp_prob *P, int i); /* retrieve row upper bound */ int glp_get_col_type(glp_prob *P, int j); /* retrieve column type */ double glp_get_col_lb(glp_prob *P, int j); /* retrieve column lower bound */ double glp_get_col_ub(glp_prob *P, int j); /* retrieve column upper bound */ double glp_get_obj_coef(glp_prob *P, int j); /* retrieve obj. coefficient or constant term */ int glp_get_num_nz(glp_prob *P); /* retrieve number of constraint coefficients */ int glp_get_mat_row(glp_prob *P, int i, int ind[], double val[]); /* retrieve row of the constraint matrix */ int glp_get_mat_col(glp_prob *P, int j, int ind[], double val[]); /* retrieve column of the constraint matrix */ void glp_create_index(glp_prob *P); /* create the name index */ int glp_find_row(glp_prob *P, const char *name); /* find row by its name */ int glp_find_col(glp_prob *P, const char *name); /* find column by its name */ void glp_delete_index(glp_prob *P); /* delete the name index */ void glp_set_rii(glp_prob *P, int i, double rii); /* set (change) row scale factor */ void glp_set_sjj(glp_prob *P, int j, double sjj); /* set (change) column scale factor */ double glp_get_rii(glp_prob *P, int i); /* retrieve row scale factor */ double glp_get_sjj(glp_prob *P, int j); /* retrieve column scale factor */ void glp_scale_prob(glp_prob *P, int flags); /* scale problem data */ void glp_unscale_prob(glp_prob *P); /* unscale problem data */ void glp_set_row_stat(glp_prob *P, int i, int stat); /* set (change) row status */ void glp_set_col_stat(glp_prob *P, int j, int stat); /* set (change) column status */ void glp_std_basis(glp_prob *P); /* construct standard initial LP basis */ void glp_adv_basis(glp_prob *P, int flags); /* construct advanced initial LP basis */ void glp_cpx_basis(glp_prob *P); /* construct Bixby's initial LP basis */ int glp_simplex(glp_prob *P, const glp_smcp *parm); /* solve LP problem with the simplex method */ int glp_exact(glp_prob *P, const glp_smcp *parm); /* solve LP problem in exact arithmetic */ void glp_init_smcp(glp_smcp *parm); /* initialize simplex method control parameters */ int glp_get_status(glp_prob *P); /* retrieve generic status of basic solution */ int glp_get_prim_stat(glp_prob *P); /* retrieve status of primal basic solution */ int glp_get_dual_stat(glp_prob *P); /* retrieve status of dual basic solution */ double glp_get_obj_val(glp_prob *P); /* retrieve objective value (basic solution) */ int glp_get_row_stat(glp_prob *P, int i); /* retrieve row status */ double glp_get_row_prim(glp_prob *P, int i); /* retrieve row primal value (basic solution) */ double glp_get_row_dual(glp_prob *P, int i); /* retrieve row dual value (basic solution) */ int glp_get_col_stat(glp_prob *P, int j); /* retrieve column status */ double glp_get_col_prim(glp_prob *P, int j); /* retrieve column primal value (basic solution) */ double glp_get_col_dual(glp_prob *P, int j); /* retrieve column dual value (basic solution) */ int glp_get_unbnd_ray(glp_prob *P); /* determine variable causing unboundedness */ int glp_interior(glp_prob *P, const glp_iptcp *parm); /* solve LP problem with the interior-point method */ void glp_init_iptcp(glp_iptcp *parm); /* initialize interior-point solver control parameters */ int glp_ipt_status(glp_prob *P); /* retrieve status of interior-point solution */ double glp_ipt_obj_val(glp_prob *P); /* retrieve objective value (interior point) */ double glp_ipt_row_prim(glp_prob *P, int i); /* retrieve row primal value (interior point) */ double glp_ipt_row_dual(glp_prob *P, int i); /* retrieve row dual value (interior point) */ double glp_ipt_col_prim(glp_prob *P, int j); /* retrieve column primal value (interior point) */ double glp_ipt_col_dual(glp_prob *P, int j); /* retrieve column dual value (interior point) */ void glp_set_col_kind(glp_prob *P, int j, int kind); /* set (change) column kind */ int glp_get_col_kind(glp_prob *P, int j); /* retrieve column kind */ int glp_get_num_int(glp_prob *P); /* retrieve number of integer columns */ int glp_get_num_bin(glp_prob *P); /* retrieve number of binary columns */ int glp_intopt(glp_prob *P, const glp_iocp *parm); /* solve MIP problem with the branch-and-bound method */ void glp_init_iocp(glp_iocp *parm); /* initialize integer optimizer control parameters */ int glp_mip_status(glp_prob *P); /* retrieve status of MIP solution */ double glp_mip_obj_val(glp_prob *P); /* retrieve objective value (MIP solution) */ double glp_mip_row_val(glp_prob *P, int i); /* retrieve row value (MIP solution) */ double glp_mip_col_val(glp_prob *P, int j); /* retrieve column value (MIP solution) */ int glp_print_sol(glp_prob *P, const char *fname); /* write basic solution in printable format */ int glp_read_sol(glp_prob *P, const char *fname); /* read basic solution from text file */ int glp_write_sol(glp_prob *P, const char *fname); /* write basic solution to text file */ int glp_print_ranges(glp_prob *P, int len, const int list[], int flags, const char *fname); /* print sensitivity analysis report */ int glp_print_ipt(glp_prob *P, const char *fname); /* write interior-point solution in printable format */ int glp_read_ipt(glp_prob *P, const char *fname); /* read interior-point solution from text file */ int glp_write_ipt(glp_prob *P, const char *fname); /* write interior-point solution to text file */ int glp_print_mip(glp_prob *P, const char *fname); /* write MIP solution in printable format */ int glp_read_mip(glp_prob *P, const char *fname); /* read MIP solution from text file */ int glp_write_mip(glp_prob *P, const char *fname); /* write MIP solution to text file */ int glp_bf_exists(glp_prob *P); /* check if the basis factorization exists */ int glp_factorize(glp_prob *P); /* compute the basis factorization */ int glp_bf_updated(glp_prob *P); /* check if the basis factorization has been updated */ void glp_get_bfcp(glp_prob *P, glp_bfcp *parm); /* retrieve basis factorization control parameters */ void glp_set_bfcp(glp_prob *P, const glp_bfcp *parm); /* change basis factorization control parameters */ int glp_get_bhead(glp_prob *P, int k); /* retrieve the basis header information */ int glp_get_row_bind(glp_prob *P, int i); /* retrieve row index in the basis header */ int glp_get_col_bind(glp_prob *P, int j); /* retrieve column index in the basis header */ void glp_ftran(glp_prob *P, double x[]); /* perform forward transformation (solve system B*x = b) */ void glp_btran(glp_prob *P, double x[]); /* perform backward transformation (solve system B'*x = b) */ int glp_warm_up(glp_prob *P); /* "warm up" LP basis */ int glp_eval_tab_row(glp_prob *P, int k, int ind[], double val[]); /* compute row of the simplex tableau */ int glp_eval_tab_col(glp_prob *P, int k, int ind[], double val[]); /* compute column of the simplex tableau */ int glp_transform_row(glp_prob *P, int len, int ind[], double val[]); /* transform explicitly specified row */ int glp_transform_col(glp_prob *P, int len, int ind[], double val[]); /* transform explicitly specified column */ int glp_prim_rtest(glp_prob *P, int len, const int ind[], const double val[], int dir, double eps); /* perform primal ratio test */ int glp_dual_rtest(glp_prob *P, int len, const int ind[], const double val[], int dir, double eps); /* perform dual ratio test */ void glp_analyze_bound(glp_prob *P, int k, double *value1, int *var1, double *value2, int *var2); /* analyze active bound of non-basic variable */ void glp_analyze_coef(glp_prob *P, int k, double *coef1, int *var1, double *value1, double *coef2, int *var2, double *value2); /* analyze objective coefficient at basic variable */ int glp_ios_reason(glp_tree *T); /* determine reason for calling the callback routine */ glp_prob *glp_ios_get_prob(glp_tree *T); /* access the problem object */ void glp_ios_tree_size(glp_tree *T, int *a_cnt, int *n_cnt, int *t_cnt); /* determine size of the branch-and-bound tree */ int glp_ios_curr_node(glp_tree *T); /* determine current active subproblem */ int glp_ios_next_node(glp_tree *T, int p); /* determine next active subproblem */ int glp_ios_prev_node(glp_tree *T, int p); /* determine previous active subproblem */ int glp_ios_up_node(glp_tree *T, int p); /* determine parent subproblem */ int glp_ios_node_level(glp_tree *T, int p); /* determine subproblem level */ double glp_ios_node_bound(glp_tree *T, int p); /* determine subproblem local bound */ int glp_ios_best_node(glp_tree *T); /* find active subproblem with best local bound */ double glp_ios_mip_gap(glp_tree *T); /* compute relative MIP gap */ void *glp_ios_node_data(glp_tree *T, int p); /* access subproblem application-specific data */ void glp_ios_row_attr(glp_tree *T, int i, glp_attr *attr); /* retrieve additional row attributes */ int glp_ios_pool_size(glp_tree *T); /* determine current size of the cut pool */ int glp_ios_add_row(glp_tree *T, const char *name, int klass, int flags, int len, const int ind[], const double val[], int type, double rhs); /* add row (constraint) to the cut pool */ void glp_ios_del_row(glp_tree *T, int i); /* remove row (constraint) from the cut pool */ void glp_ios_clear_pool(glp_tree *T); /* remove all rows (constraints) from the cut pool */ int glp_ios_can_branch(glp_tree *T, int j); /* check if can branch upon specified variable */ void glp_ios_branch_upon(glp_tree *T, int j, int sel); /* choose variable to branch upon */ void glp_ios_select_node(glp_tree *T, int p); /* select subproblem to continue the search */ int glp_ios_heur_sol(glp_tree *T, const double x[]); /* provide solution found by heuristic */ void glp_ios_terminate(glp_tree *T); /* terminate the solution process */ void glp_init_mpscp(glp_mpscp *parm); /* initialize MPS format control parameters */ int glp_read_mps(glp_prob *P, int fmt, const glp_mpscp *parm, const char *fname); /* read problem data in MPS format */ int glp_write_mps(glp_prob *P, int fmt, const glp_mpscp *parm, const char *fname); /* write problem data in MPS format */ void glp_init_cpxcp(glp_cpxcp *parm); /* initialize CPLEX LP format control parameters */ int glp_read_lp(glp_prob *P, const glp_cpxcp *parm, const char *fname); /* read problem data in CPLEX LP format */ int glp_write_lp(glp_prob *P, const glp_cpxcp *parm, const char *fname); /* write problem data in CPLEX LP format */ int glp_read_prob(glp_prob *P, int flags, const char *fname); /* read problem data in GLPK format */ int glp_write_prob(glp_prob *P, int flags, const char *fname); /* write problem data in GLPK format */ glp_tran *glp_mpl_alloc_wksp(void); /* allocate the MathProg translator workspace */ int glp_mpl_read_model(glp_tran *tran, const char *fname, int skip); /* read and translate model section */ int glp_mpl_read_data(glp_tran *tran, const char *fname); /* read and translate data section */ int glp_mpl_generate(glp_tran *tran, const char *fname); /* generate the model */ void glp_mpl_build_prob(glp_tran *tran, glp_prob *prob); /* build LP/MIP problem instance from the model */ int glp_mpl_postsolve(glp_tran *tran, glp_prob *prob, int sol); /* postsolve the model */ void glp_mpl_free_wksp(glp_tran *tran); /* free the MathProg translator workspace */ int glp_main(int argc, const char *argv[]); /* stand-alone LP/MIP solver */ /**********************************************************************/ #ifndef GLP_LONG_DEFINED #define GLP_LONG_DEFINED typedef struct { int lo, hi; } glp_long; /* long integer data type */ #endif int glp_init_env(void); /* initialize GLPK environment */ const char *glp_version(void); /* determine library version */ int glp_free_env(void); /* free GLPK environment */ void glp_printf(const char *fmt, ...); /* write formatted output to terminal */ void glp_vprintf(const char *fmt, va_list arg); /* write formatted output to terminal */ int glp_term_out(int flag); /* enable/disable terminal output */ void glp_term_hook(int (*func)(void *info, const char *s), void *info); /* install hook to intercept terminal output */ int glp_open_tee(const char *fname); /* start copying terminal output to text file */ int glp_close_tee(void); /* stop copying terminal output to text file */ #ifndef GLP_ERROR_DEFINED #define GLP_ERROR_DEFINED typedef void (*_glp_error)(const char *fmt, ...); #endif #define glp_error glp_error_(__FILE__, __LINE__) _glp_error glp_error_(const char *file, int line); /* display error message and terminate execution */ #define glp_assert(expr) \ ((void)((expr) || (glp_assert_(#expr, __FILE__, __LINE__), 1))) void glp_assert_(const char *expr, const char *file, int line); /* check for logical condition */ void glp_error_hook(void (*func)(void *info), void *info); /* install hook to intercept abnormal termination */ void *glp_malloc(int size); /* allocate memory block */ void *glp_calloc(int n, int size); /* allocate memory block */ void glp_free(void *ptr); /* free memory block */ void glp_mem_limit(int limit); /* set memory usage limit */ void glp_mem_usage(int *count, int *cpeak, glp_long *total, glp_long *tpeak); /* get memory usage information */ glp_long glp_time(void); /* determine current universal time */ double glp_difftime(glp_long t1, glp_long t0); /* compute difference between two time values */ /**********************************************************************/ #ifndef GLP_DATA_DEFINED #define GLP_DATA_DEFINED typedef struct { double _opaque_data[100]; } glp_data; /* plain data file */ #endif glp_data *glp_sdf_open_file(const char *fname); /* open plain data file */ void glp_sdf_set_jump(glp_data *data, void *jump); /* set up error handling */ void glp_sdf_error(glp_data *data, const char *fmt, ...); /* print error message */ void glp_sdf_warning(glp_data *data, const char *fmt, ...); /* print warning message */ int glp_sdf_read_int(glp_data *data); /* read integer number */ double glp_sdf_read_num(glp_data *data); /* read floating-point number */ const char *glp_sdf_read_item(glp_data *data); /* read data item */ const char *glp_sdf_read_text(glp_data *data); /* read text until end of line */ int glp_sdf_line(glp_data *data); /* determine current line number */ void glp_sdf_close_file(glp_data *data); /* close plain data file */ /**********************************************************************/ typedef struct _glp_graph glp_graph; typedef struct _glp_vertex glp_vertex; typedef struct _glp_arc glp_arc; struct _glp_graph { /* graph descriptor */ void *pool; /* DMP *pool; */ /* memory pool to store graph components */ char *name; /* graph name (1 to 255 chars); NULL means no name is assigned to the graph */ int nv_max; /* length of the vertex list (enlarged automatically) */ int nv; /* number of vertices in the graph, 0 <= nv <= nv_max */ int na; /* number of arcs in the graph, na >= 0 */ glp_vertex **v; /* glp_vertex *v[1+nv_max]; */ /* v[i], 1 <= i <= nv, is a pointer to i-th vertex */ void *index; /* AVL *index; */ /* vertex index to find vertices by their names; NULL means the index does not exist */ int v_size; /* size of data associated with each vertex (0 to 256 bytes) */ int a_size; /* size of data associated with each arc (0 to 256 bytes) */ }; struct _glp_vertex { /* vertex descriptor */ int i; /* vertex ordinal number, 1 <= i <= nv */ char *name; /* vertex name (1 to 255 chars); NULL means no name is assigned to the vertex */ void *entry; /* AVLNODE *entry; */ /* pointer to corresponding entry in the vertex index; NULL means that either the index does not exist or the vertex has no name assigned */ void *data; /* pointer to data associated with the vertex */ void *temp; /* working pointer */ glp_arc *in; /* pointer to the (unordered) list of incoming arcs */ glp_arc *out; /* pointer to the (unordered) list of outgoing arcs */ }; struct _glp_arc { /* arc descriptor */ glp_vertex *tail; /* pointer to the tail endpoint */ glp_vertex *head; /* pointer to the head endpoint */ void *data; /* pointer to data associated with the arc */ void *temp; /* working pointer */ glp_arc *t_prev; /* pointer to previous arc having the same tail endpoint */ glp_arc *t_next; /* pointer to next arc having the same tail endpoint */ glp_arc *h_prev; /* pointer to previous arc having the same head endpoint */ glp_arc *h_next; /* pointer to next arc having the same head endpoint */ }; glp_graph *glp_create_graph(int v_size, int a_size); /* create graph */ void glp_set_graph_name(glp_graph *G, const char *name); /* assign (change) graph name */ int glp_add_vertices(glp_graph *G, int nadd); /* add new vertices to graph */ void glp_set_vertex_name(glp_graph *G, int i, const char *name); /* assign (change) vertex name */ glp_arc *glp_add_arc(glp_graph *G, int i, int j); /* add new arc to graph */ void glp_del_vertices(glp_graph *G, int ndel, const int num[]); /* delete vertices from graph */ void glp_del_arc(glp_graph *G, glp_arc *a); /* delete arc from graph */ void glp_erase_graph(glp_graph *G, int v_size, int a_size); /* erase graph content */ void glp_delete_graph(glp_graph *G); /* delete graph */ void glp_create_v_index(glp_graph *G); /* create vertex name index */ int glp_find_vertex(glp_graph *G, const char *name); /* find vertex by its name */ void glp_delete_v_index(glp_graph *G); /* delete vertex name index */ int glp_read_graph(glp_graph *G, const char *fname); /* read graph from plain text file */ int glp_write_graph(glp_graph *G, const char *fname); /* write graph to plain text file */ void glp_mincost_lp(glp_prob *P, glp_graph *G, int names, int v_rhs, int a_low, int a_cap, int a_cost); /* convert minimum cost flow problem to LP */ int glp_mincost_okalg(glp_graph *G, int v_rhs, int a_low, int a_cap, int a_cost, double *sol, int a_x, int v_pi); /* find minimum-cost flow with out-of-kilter algorithm */ void glp_maxflow_lp(glp_prob *P, glp_graph *G, int names, int s, int t, int a_cap); /* convert maximum flow problem to LP */ int glp_maxflow_ffalg(glp_graph *G, int s, int t, int a_cap, double *sol, int a_x, int v_cut); /* find maximal flow with Ford-Fulkerson algorithm */ int glp_check_asnprob(glp_graph *G, int v_set); /* check correctness of assignment problem data */ /* assignment problem formulation: */ #define GLP_ASN_MIN 1 /* perfect matching (minimization) */ #define GLP_ASN_MAX 2 /* perfect matching (maximization) */ #define GLP_ASN_MMP 3 /* maximum matching */ int glp_asnprob_lp(glp_prob *P, int form, glp_graph *G, int names, int v_set, int a_cost); /* convert assignment problem to LP */ int glp_asnprob_okalg(int form, glp_graph *G, int v_set, int a_cost, double *sol, int a_x); /* solve assignment problem with out-of-kilter algorithm */ int glp_asnprob_hall(glp_graph *G, int v_set, int a_x); /* find bipartite matching of maximum cardinality */ double glp_cpp(glp_graph *G, int v_t, int v_es, int v_ls); /* solve critical path problem */ int glp_read_mincost(glp_graph *G, int v_rhs, int a_low, int a_cap, int a_cost, const char *fname); /* read min-cost flow problem data in DIMACS format */ int glp_write_mincost(glp_graph *G, int v_rhs, int a_low, int a_cap, int a_cost, const char *fname); /* write min-cost flow problem data in DIMACS format */ int glp_read_maxflow(glp_graph *G, int *s, int *t, int a_cap, const char *fname); /* read maximum flow problem data in DIMACS format */ int glp_write_maxflow(glp_graph *G, int s, int t, int a_cap, const char *fname); /* write maximum flow problem data in DIMACS format */ int glp_read_asnprob(glp_graph *G, int v_set, int a_cost, const char *fname); /* read assignment problem data in DIMACS format */ int glp_write_asnprob(glp_graph *G, int v_set, int a_cost, const char *fname); /* write assignment problem data in DIMACS format */ int glp_read_ccdata(glp_graph *G, int v_wgt, const char *fname); /* read graph in DIMACS clique/coloring format */ int glp_write_ccdata(glp_graph *G, int v_wgt, const char *fname); /* write graph in DIMACS clique/coloring format */ int glp_netgen(glp_graph *G, int v_rhs, int a_cap, int a_cost, const int parm[1+15]); /* Klingman's network problem generator */ int glp_gridgen(glp_graph *G, int v_rhs, int a_cap, int a_cost, const int parm[1+14]); /* grid-like network problem generator */ int glp_rmfgen(glp_graph *G, int *s, int *t, int a_cap, const int parm[1+5]); /* Goldfarb's maximum flow problem generator */ int glp_weak_comp(glp_graph *G, int v_num); /* find all weakly connected components of graph */ int glp_strong_comp(glp_graph *G, int v_num); /* find all strongly connected components of graph */ int glp_top_sort(glp_graph *G, int v_num); /* topological sorting of acyclic digraph */ int glp_wclique_exact(glp_graph *G, int v_wgt, double *sol, int v_set); /* find maximum weight clique with exact algorithm */ /*********************************************************************** * NOTE: All symbols defined below are obsolete and kept here only for * backward compatibility. ***********************************************************************/ #define LPX glp_prob /* problem class: */ #define LPX_LP 100 /* linear programming (LP) */ #define LPX_MIP 101 /* mixed integer programming (MIP) */ /* type of auxiliary/structural variable: */ #define LPX_FR 110 /* free variable */ #define LPX_LO 111 /* variable with lower bound */ #define LPX_UP 112 /* variable with upper bound */ #define LPX_DB 113 /* double-bounded variable */ #define LPX_FX 114 /* fixed variable */ /* optimization direction flag: */ #define LPX_MIN 120 /* minimization */ #define LPX_MAX 121 /* maximization */ /* status of primal basic solution: */ #define LPX_P_UNDEF 132 /* primal solution is undefined */ #define LPX_P_FEAS 133 /* solution is primal feasible */ #define LPX_P_INFEAS 134 /* solution is primal infeasible */ #define LPX_P_NOFEAS 135 /* no primal feasible solution exists */ /* status of dual basic solution: */ #define LPX_D_UNDEF 136 /* dual solution is undefined */ #define LPX_D_FEAS 137 /* solution is dual feasible */ #define LPX_D_INFEAS 138 /* solution is dual infeasible */ #define LPX_D_NOFEAS 139 /* no dual feasible solution exists */ /* status of auxiliary/structural variable: */ #define LPX_BS 140 /* basic variable */ #define LPX_NL 141 /* non-basic variable on lower bound */ #define LPX_NU 142 /* non-basic variable on upper bound */ #define LPX_NF 143 /* non-basic free variable */ #define LPX_NS 144 /* non-basic fixed variable */ /* status of interior-point solution: */ #define LPX_T_UNDEF 150 /* interior solution is undefined */ #define LPX_T_OPT 151 /* interior solution is optimal */ /* kind of structural variable: */ #define LPX_CV 160 /* continuous variable */ #define LPX_IV 161 /* integer variable */ /* status of integer solution: */ #define LPX_I_UNDEF 170 /* integer solution is undefined */ #define LPX_I_OPT 171 /* integer solution is optimal */ #define LPX_I_FEAS 172 /* integer solution is feasible */ #define LPX_I_NOFEAS 173 /* no integer solution exists */ /* status codes reported by the routine lpx_get_status: */ #define LPX_OPT 180 /* optimal */ #define LPX_FEAS 181 /* feasible */ #define LPX_INFEAS 182 /* infeasible */ #define LPX_NOFEAS 183 /* no feasible */ #define LPX_UNBND 184 /* unbounded */ #define LPX_UNDEF 185 /* undefined */ /* exit codes returned by solver routines: */ #define LPX_E_OK 200 /* success */ #define LPX_E_EMPTY 201 /* empty problem */ #define LPX_E_BADB 202 /* invalid initial basis */ #define LPX_E_INFEAS 203 /* infeasible initial solution */ #define LPX_E_FAULT 204 /* unable to start the search */ #define LPX_E_OBJLL 205 /* objective lower limit reached */ #define LPX_E_OBJUL 206 /* objective upper limit reached */ #define LPX_E_ITLIM 207 /* iterations limit exhausted */ #define LPX_E_TMLIM 208 /* time limit exhausted */ #define LPX_E_NOFEAS 209 /* no feasible solution */ #define LPX_E_INSTAB 210 /* numerical instability */ #define LPX_E_SING 211 /* problems with basis matrix */ #define LPX_E_NOCONV 212 /* no convergence (interior) */ #define LPX_E_NOPFS 213 /* no primal feas. sol. (LP presolver) */ #define LPX_E_NODFS 214 /* no dual feas. sol. (LP presolver) */ #define LPX_E_MIPGAP 215 /* relative mip gap tolerance reached */ /* control parameter identifiers: */ #define LPX_K_MSGLEV 300 /* lp->msg_lev */ #define LPX_K_SCALE 301 /* lp->scale */ #define LPX_K_DUAL 302 /* lp->dual */ #define LPX_K_PRICE 303 /* lp->price */ #define LPX_K_RELAX 304 /* lp->relax */ #define LPX_K_TOLBND 305 /* lp->tol_bnd */ #define LPX_K_TOLDJ 306 /* lp->tol_dj */ #define LPX_K_TOLPIV 307 /* lp->tol_piv */ #define LPX_K_ROUND 308 /* lp->round */ #define LPX_K_OBJLL 309 /* lp->obj_ll */ #define LPX_K_OBJUL 310 /* lp->obj_ul */ #define LPX_K_ITLIM 311 /* lp->it_lim */ #define LPX_K_ITCNT 312 /* lp->it_cnt */ #define LPX_K_TMLIM 313 /* lp->tm_lim */ #define LPX_K_OUTFRQ 314 /* lp->out_frq */ #define LPX_K_OUTDLY 315 /* lp->out_dly */ #define LPX_K_BRANCH 316 /* lp->branch */ #define LPX_K_BTRACK 317 /* lp->btrack */ #define LPX_K_TOLINT 318 /* lp->tol_int */ #define LPX_K_TOLOBJ 319 /* lp->tol_obj */ #define LPX_K_MPSINFO 320 /* lp->mps_info */ #define LPX_K_MPSOBJ 321 /* lp->mps_obj */ #define LPX_K_MPSORIG 322 /* lp->mps_orig */ #define LPX_K_MPSWIDE 323 /* lp->mps_wide */ #define LPX_K_MPSFREE 324 /* lp->mps_free */ #define LPX_K_MPSSKIP 325 /* lp->mps_skip */ #define LPX_K_LPTORIG 326 /* lp->lpt_orig */ #define LPX_K_PRESOL 327 /* lp->presol */ #define LPX_K_BINARIZE 328 /* lp->binarize */ #define LPX_K_USECUTS 329 /* lp->use_cuts */ #define LPX_K_BFTYPE 330 /* lp->bfcp->type */ #define LPX_K_MIPGAP 331 /* lp->mip_gap */ #define LPX_C_COVER 0x01 /* mixed cover cuts */ #define LPX_C_CLIQUE 0x02 /* clique cuts */ #define LPX_C_GOMORY 0x04 /* Gomory's mixed integer cuts */ #define LPX_C_MIR 0x08 /* mixed integer rounding cuts */ #define LPX_C_ALL 0xFF /* all cuts */ typedef struct { /* this structure contains results reported by the routines which checks Karush-Kuhn-Tucker conditions (for details see comments to those routines) */ /*--------------------------------------------------------------*/ /* xR - A * xS = 0 (KKT.PE) */ double pe_ae_max; /* largest absolute error */ int pe_ae_row; /* number of row with largest absolute error */ double pe_re_max; /* largest relative error */ int pe_re_row; /* number of row with largest relative error */ int pe_quality; /* quality of primal solution: 'H' - high 'M' - medium 'L' - low '?' - primal solution is wrong */ /*--------------------------------------------------------------*/ /* l[k] <= x[k] <= u[k] (KKT.PB) */ double pb_ae_max; /* largest absolute error */ int pb_ae_ind; /* number of variable with largest absolute error */ double pb_re_max; /* largest relative error */ int pb_re_ind; /* number of variable with largest relative error */ int pb_quality; /* quality of primal feasibility: 'H' - high 'M' - medium 'L' - low '?' - primal solution is infeasible */ /*--------------------------------------------------------------*/ /* A' * (dR - cR) + (dS - cS) = 0 (KKT.DE) */ double de_ae_max; /* largest absolute error */ int de_ae_col; /* number of column with largest absolute error */ double de_re_max; /* largest relative error */ int de_re_col; /* number of column with largest relative error */ int de_quality; /* quality of dual solution: 'H' - high 'M' - medium 'L' - low '?' - dual solution is wrong */ /*--------------------------------------------------------------*/ /* d[k] >= 0 or d[k] <= 0 (KKT.DB) */ double db_ae_max; /* largest absolute error */ int db_ae_ind; /* number of variable with largest absolute error */ double db_re_max; /* largest relative error */ int db_re_ind; /* number of variable with largest relative error */ int db_quality; /* quality of dual feasibility: 'H' - high 'M' - medium 'L' - low '?' - dual solution is infeasible */ /*--------------------------------------------------------------*/ /* (x[k] - bound of x[k]) * d[k] = 0 (KKT.CS) */ double cs_ae_max; /* largest absolute error */ int cs_ae_ind; /* number of variable with largest absolute error */ double cs_re_max; /* largest relative error */ int cs_re_ind; /* number of variable with largest relative error */ int cs_quality; /* quality of complementary slackness: 'H' - high 'M' - medium 'L' - low '?' - primal and dual solutions are not complementary */ } LPXKKT; #define lpx_create_prob _glp_lpx_create_prob LPX *lpx_create_prob(void); /* create problem object */ #define lpx_set_prob_name _glp_lpx_set_prob_name void lpx_set_prob_name(LPX *lp, const char *name); /* assign (change) problem name */ #define lpx_set_obj_name _glp_lpx_set_obj_name void lpx_set_obj_name(LPX *lp, const char *name); /* assign (change) objective function name */ #define lpx_set_obj_dir _glp_lpx_set_obj_dir void lpx_set_obj_dir(LPX *lp, int dir); /* set (change) optimization direction flag */ #define lpx_add_rows _glp_lpx_add_rows int lpx_add_rows(LPX *lp, int nrs); /* add new rows to problem object */ #define lpx_add_cols _glp_lpx_add_cols int lpx_add_cols(LPX *lp, int ncs); /* add new columns to problem object */ #define lpx_set_row_name _glp_lpx_set_row_name void lpx_set_row_name(LPX *lp, int i, const char *name); /* assign (change) row name */ #define lpx_set_col_name _glp_lpx_set_col_name void lpx_set_col_name(LPX *lp, int j, const char *name); /* assign (change) column name */ #define lpx_set_row_bnds _glp_lpx_set_row_bnds void lpx_set_row_bnds(LPX *lp, int i, int type, double lb, double ub); /* set (change) row bounds */ #define lpx_set_col_bnds _glp_lpx_set_col_bnds void lpx_set_col_bnds(LPX *lp, int j, int type, double lb, double ub); /* set (change) column bounds */ #define lpx_set_obj_coef _glp_lpx_set_obj_coef void lpx_set_obj_coef(glp_prob *lp, int j, double coef); /* set (change) obj. coefficient or constant term */ #define lpx_set_mat_row _glp_lpx_set_mat_row void lpx_set_mat_row(LPX *lp, int i, int len, const int ind[], const double val[]); /* set (replace) row of the constraint matrix */ #define lpx_set_mat_col _glp_lpx_set_mat_col void lpx_set_mat_col(LPX *lp, int j, int len, const int ind[], const double val[]); /* set (replace) column of the constraint matrix */ #define lpx_load_matrix _glp_lpx_load_matrix void lpx_load_matrix(LPX *lp, int ne, const int ia[], const int ja[], const double ar[]); /* load (replace) the whole constraint matrix */ #define lpx_del_rows _glp_lpx_del_rows void lpx_del_rows(LPX *lp, int nrs, const int num[]); /* delete specified rows from problem object */ #define lpx_del_cols _glp_lpx_del_cols void lpx_del_cols(LPX *lp, int ncs, const int num[]); /* delete specified columns from problem object */ #define lpx_delete_prob _glp_lpx_delete_prob void lpx_delete_prob(LPX *lp); /* delete problem object */ #define lpx_get_prob_name _glp_lpx_get_prob_name const char *lpx_get_prob_name(LPX *lp); /* retrieve problem name */ #define lpx_get_obj_name _glp_lpx_get_obj_name const char *lpx_get_obj_name(LPX *lp); /* retrieve objective function name */ #define lpx_get_obj_dir _glp_lpx_get_obj_dir int lpx_get_obj_dir(LPX *lp); /* retrieve optimization direction flag */ #define lpx_get_num_rows _glp_lpx_get_num_rows int lpx_get_num_rows(LPX *lp); /* retrieve number of rows */ #define lpx_get_num_cols _glp_lpx_get_num_cols int lpx_get_num_cols(LPX *lp); /* retrieve number of columns */ #define lpx_get_row_name _glp_lpx_get_row_name const char *lpx_get_row_name(LPX *lp, int i); /* retrieve row name */ #define lpx_get_col_name _glp_lpx_get_col_name const char *lpx_get_col_name(LPX *lp, int j); /* retrieve column name */ #define lpx_get_row_type _glp_lpx_get_row_type int lpx_get_row_type(LPX *lp, int i); /* retrieve row type */ #define lpx_get_row_lb _glp_lpx_get_row_lb double lpx_get_row_lb(LPX *lp, int i); /* retrieve row lower bound */ #define lpx_get_row_ub _glp_lpx_get_row_ub double lpx_get_row_ub(LPX *lp, int i); /* retrieve row upper bound */ #define lpx_get_row_bnds _glp_lpx_get_row_bnds void lpx_get_row_bnds(LPX *lp, int i, int *typx, double *lb, double *ub); /* retrieve row bounds */ #define lpx_get_col_type _glp_lpx_get_col_type int lpx_get_col_type(LPX *lp, int j); /* retrieve column type */ #define lpx_get_col_lb _glp_lpx_get_col_lb double lpx_get_col_lb(LPX *lp, int j); /* retrieve column lower bound */ #define lpx_get_col_ub _glp_lpx_get_col_ub double lpx_get_col_ub(LPX *lp, int j); /* retrieve column upper bound */ #define lpx_get_col_bnds _glp_lpx_get_col_bnds void lpx_get_col_bnds(LPX *lp, int j, int *typx, double *lb, double *ub); /* retrieve column bounds */ #define lpx_get_obj_coef _glp_lpx_get_obj_coef double lpx_get_obj_coef(LPX *lp, int j); /* retrieve obj. coefficient or constant term */ #define lpx_get_num_nz _glp_lpx_get_num_nz int lpx_get_num_nz(LPX *lp); /* retrieve number of constraint coefficients */ #define lpx_get_mat_row _glp_lpx_get_mat_row int lpx_get_mat_row(LPX *lp, int i, int ind[], double val[]); /* retrieve row of the constraint matrix */ #define lpx_get_mat_col _glp_lpx_get_mat_col int lpx_get_mat_col(LPX *lp, int j, int ind[], double val[]); /* retrieve column of the constraint matrix */ #define lpx_create_index _glp_lpx_create_index void lpx_create_index(LPX *lp); /* create the name index */ #define lpx_find_row _glp_lpx_find_row int lpx_find_row(LPX *lp, const char *name); /* find row by its name */ #define lpx_find_col _glp_lpx_find_col int lpx_find_col(LPX *lp, const char *name); /* find column by its name */ #define lpx_delete_index _glp_lpx_delete_index void lpx_delete_index(LPX *lp); /* delete the name index */ #define lpx_scale_prob _glp_lpx_scale_prob void lpx_scale_prob(LPX *lp); /* scale problem data */ #define lpx_unscale_prob _glp_lpx_unscale_prob void lpx_unscale_prob(LPX *lp); /* unscale problem data */ #define lpx_set_row_stat _glp_lpx_set_row_stat void lpx_set_row_stat(LPX *lp, int i, int stat); /* set (change) row status */ #define lpx_set_col_stat _glp_lpx_set_col_stat void lpx_set_col_stat(LPX *lp, int j, int stat); /* set (change) column status */ #define lpx_std_basis _glp_lpx_std_basis void lpx_std_basis(LPX *lp); /* construct standard initial LP basis */ #define lpx_adv_basis _glp_lpx_adv_basis void lpx_adv_basis(LPX *lp); /* construct advanced initial LP basis */ #define lpx_cpx_basis _glp_lpx_cpx_basis void lpx_cpx_basis(LPX *lp); /* construct Bixby's initial LP basis */ #define lpx_simplex _glp_lpx_simplex int lpx_simplex(LPX *lp); /* easy-to-use driver to the simplex method */ #define lpx_exact _glp_lpx_exact int lpx_exact(LPX *lp); /* easy-to-use driver to the exact simplex method */ #define lpx_get_status _glp_lpx_get_status int lpx_get_status(LPX *lp); /* retrieve generic status of basic solution */ #define lpx_get_prim_stat _glp_lpx_get_prim_stat int lpx_get_prim_stat(LPX *lp); /* retrieve primal status of basic solution */ #define lpx_get_dual_stat _glp_lpx_get_dual_stat int lpx_get_dual_stat(LPX *lp); /* retrieve dual status of basic solution */ #define lpx_get_obj_val _glp_lpx_get_obj_val double lpx_get_obj_val(LPX *lp); /* retrieve objective value (basic solution) */ #define lpx_get_row_stat _glp_lpx_get_row_stat int lpx_get_row_stat(LPX *lp, int i); /* retrieve row status (basic solution) */ #define lpx_get_row_prim _glp_lpx_get_row_prim double lpx_get_row_prim(LPX *lp, int i); /* retrieve row primal value (basic solution) */ #define lpx_get_row_dual _glp_lpx_get_row_dual double lpx_get_row_dual(LPX *lp, int i); /* retrieve row dual value (basic solution) */ #define lpx_get_row_info _glp_lpx_get_row_info void lpx_get_row_info(LPX *lp, int i, int *tagx, double *vx, double *dx); /* obtain row solution information */ #define lpx_get_col_stat _glp_lpx_get_col_stat int lpx_get_col_stat(LPX *lp, int j); /* retrieve column status (basic solution) */ #define lpx_get_col_prim _glp_lpx_get_col_prim double lpx_get_col_prim(LPX *lp, int j); /* retrieve column primal value (basic solution) */ #define lpx_get_col_dual _glp_lpx_get_col_dual double lpx_get_col_dual(glp_prob *lp, int j); /* retrieve column dual value (basic solution) */ #define lpx_get_col_info _glp_lpx_get_col_info void lpx_get_col_info(LPX *lp, int j, int *tagx, double *vx, double *dx); /* obtain column solution information (obsolete) */ #define lpx_get_ray_info _glp_lpx_get_ray_info int lpx_get_ray_info(LPX *lp); /* determine what causes primal unboundness */ #define lpx_check_kkt _glp_lpx_check_kkt void lpx_check_kkt(LPX *lp, int scaled, LPXKKT *kkt); /* check Karush-Kuhn-Tucker conditions */ #define lpx_warm_up _glp_lpx_warm_up int lpx_warm_up(LPX *lp); /* "warm up" LP basis */ #define lpx_eval_tab_row _glp_lpx_eval_tab_row int lpx_eval_tab_row(LPX *lp, int k, int ind[], double val[]); /* compute row of the simplex table */ #define lpx_eval_tab_col _glp_lpx_eval_tab_col int lpx_eval_tab_col(LPX *lp, int k, int ind[], double val[]); /* compute column of the simplex table */ #define lpx_transform_row _glp_lpx_transform_row int lpx_transform_row(LPX *lp, int len, int ind[], double val[]); /* transform explicitly specified row */ #define lpx_transform_col _glp_lpx_transform_col int lpx_transform_col(LPX *lp, int len, int ind[], double val[]); /* transform explicitly specified column */ #define lpx_prim_ratio_test _glp_lpx_prim_ratio_test int lpx_prim_ratio_test(LPX *lp, int len, const int ind[], const double val[], int how, double tol); /* perform primal ratio test */ #define lpx_dual_ratio_test _glp_lpx_dual_ratio_test int lpx_dual_ratio_test(LPX *lp, int len, const int ind[], const double val[], int how, double tol); /* perform dual ratio test */ #define lpx_interior _glp_lpx_interior int lpx_interior(LPX *lp); /* easy-to-use driver to the interior point method */ #define lpx_ipt_status _glp_lpx_ipt_status int lpx_ipt_status(LPX *lp); /* retrieve status of interior-point solution */ #define lpx_ipt_obj_val _glp_lpx_ipt_obj_val double lpx_ipt_obj_val(LPX *lp); /* retrieve objective value (interior point) */ #define lpx_ipt_row_prim _glp_lpx_ipt_row_prim double lpx_ipt_row_prim(LPX *lp, int i); /* retrieve row primal value (interior point) */ #define lpx_ipt_row_dual _glp_lpx_ipt_row_dual double lpx_ipt_row_dual(LPX *lp, int i); /* retrieve row dual value (interior point) */ #define lpx_ipt_col_prim _glp_lpx_ipt_col_prim double lpx_ipt_col_prim(LPX *lp, int j); /* retrieve column primal value (interior point) */ #define lpx_ipt_col_dual _glp_lpx_ipt_col_dual double lpx_ipt_col_dual(LPX *lp, int j); /* retrieve column dual value (interior point) */ #define lpx_set_class _glp_lpx_set_class void lpx_set_class(LPX *lp, int klass); /* set problem class */ #define lpx_get_class _glp_lpx_get_class int lpx_get_class(LPX *lp); /* determine problem klass */ #define lpx_set_col_kind _glp_lpx_set_col_kind void lpx_set_col_kind(LPX *lp, int j, int kind); /* set (change) column kind */ #define lpx_get_col_kind _glp_lpx_get_col_kind int lpx_get_col_kind(LPX *lp, int j); /* retrieve column kind */ #define lpx_get_num_int _glp_lpx_get_num_int int lpx_get_num_int(LPX *lp); /* retrieve number of integer columns */ #define lpx_get_num_bin _glp_lpx_get_num_bin int lpx_get_num_bin(LPX *lp); /* retrieve number of binary columns */ #define lpx_integer _glp_lpx_integer int lpx_integer(LPX *lp); /* easy-to-use driver to the branch-and-bound method */ #define lpx_intopt _glp_lpx_intopt int lpx_intopt(LPX *lp); /* easy-to-use driver to the branch-and-bound method */ #define lpx_mip_status _glp_lpx_mip_status int lpx_mip_status(LPX *lp); /* retrieve status of MIP solution */ #define lpx_mip_obj_val _glp_lpx_mip_obj_val double lpx_mip_obj_val(LPX *lp); /* retrieve objective value (MIP solution) */ #define lpx_mip_row_val _glp_lpx_mip_row_val double lpx_mip_row_val(LPX *lp, int i); /* retrieve row value (MIP solution) */ #define lpx_mip_col_val _glp_lpx_mip_col_val double lpx_mip_col_val(LPX *lp, int j); /* retrieve column value (MIP solution) */ #define lpx_check_int _glp_lpx_check_int void lpx_check_int(LPX *lp, LPXKKT *kkt); /* check integer feasibility conditions */ #define lpx_reset_parms _glp_lpx_reset_parms void lpx_reset_parms(LPX *lp); /* reset control parameters to default values */ #define lpx_set_int_parm _glp_lpx_set_int_parm void lpx_set_int_parm(LPX *lp, int parm, int val); /* set (change) integer control parameter */ #define lpx_get_int_parm _glp_lpx_get_int_parm int lpx_get_int_parm(LPX *lp, int parm); /* query integer control parameter */ #define lpx_set_real_parm _glp_lpx_set_real_parm void lpx_set_real_parm(LPX *lp, int parm, double val); /* set (change) real control parameter */ #define lpx_get_real_parm _glp_lpx_get_real_parm double lpx_get_real_parm(LPX *lp, int parm); /* query real control parameter */ #define lpx_read_mps _glp_lpx_read_mps LPX *lpx_read_mps(const char *fname); /* read problem data in fixed MPS format */ #define lpx_write_mps _glp_lpx_write_mps int lpx_write_mps(LPX *lp, const char *fname); /* write problem data in fixed MPS format */ #define lpx_read_bas _glp_lpx_read_bas int lpx_read_bas(LPX *lp, const char *fname); /* read LP basis in fixed MPS format */ #define lpx_write_bas _glp_lpx_write_bas int lpx_write_bas(LPX *lp, const char *fname); /* write LP basis in fixed MPS format */ #define lpx_read_freemps _glp_lpx_read_freemps LPX *lpx_read_freemps(const char *fname); /* read problem data in free MPS format */ #define lpx_write_freemps _glp_lpx_write_freemps int lpx_write_freemps(LPX *lp, const char *fname); /* write problem data in free MPS format */ #define lpx_read_cpxlp _glp_lpx_read_cpxlp LPX *lpx_read_cpxlp(const char *fname); /* read problem data in CPLEX LP format */ #define lpx_write_cpxlp _glp_lpx_write_cpxlp int lpx_write_cpxlp(LPX *lp, const char *fname); /* write problem data in CPLEX LP format */ #define lpx_read_model _glp_lpx_read_model LPX *lpx_read_model(const char *model, const char *data, const char *output); /* read LP/MIP model written in GNU MathProg language */ #define lpx_print_prob _glp_lpx_print_prob int lpx_print_prob(LPX *lp, const char *fname); /* write problem data in plain text format */ #define lpx_print_sol _glp_lpx_print_sol int lpx_print_sol(LPX *lp, const char *fname); /* write LP problem solution in printable format */ #define lpx_print_sens_bnds _glp_lpx_print_sens_bnds int lpx_print_sens_bnds(LPX *lp, const char *fname); /* write bounds sensitivity information */ #define lpx_print_ips _glp_lpx_print_ips int lpx_print_ips(LPX *lp, const char *fname); /* write interior point solution in printable format */ #define lpx_print_mip _glp_lpx_print_mip int lpx_print_mip(LPX *lp, const char *fname); /* write MIP problem solution in printable format */ #define lpx_is_b_avail _glp_lpx_is_b_avail int lpx_is_b_avail(LPX *lp); /* check if LP basis is available */ #define lpx_write_pb _glp_lpx_write_pb int lpx_write_pb(LPX *lp, const char *fname, int normalized, int binarize); /* write problem data in (normalized) OPB format */ #define lpx_main _glp_lpx_main int lpx_main(int argc, const char *argv[]); /* stand-alone LP/MIP solver */ #ifdef __cplusplus } #endif #endif /* eof */ sources_5316/external/glpk/glpios09.c0000644000176700017670000006313011411453262016316 0ustar paulpaul/* glpios09.c (branching heuristics) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*********************************************************************** * NAME * * ios_choose_var - select variable to branch on * * SYNOPSIS * * #include "glpios.h" * int ios_choose_var(glp_tree *T, int *next); * * The routine ios_choose_var chooses a variable from the candidate * list to branch on. Additionally the routine provides a flag stored * in the location next to suggests which of the child subproblems * should be solved next. * * RETURNS * * The routine ios_choose_var returns the ordinal number of the column * choosen. */ static int branch_first(glp_tree *T, int *next); static int branch_last(glp_tree *T, int *next); static int branch_mostf(glp_tree *T, int *next); static int branch_drtom(glp_tree *T, int *next); int ios_choose_var(glp_tree *T, int *next) { int j; if (T->parm->br_tech == GLP_BR_FFV) { /* branch on first fractional variable */ j = branch_first(T, next); } else if (T->parm->br_tech == GLP_BR_LFV) { /* branch on last fractional variable */ j = branch_last(T, next); } else if (T->parm->br_tech == GLP_BR_MFV) { /* branch on most fractional variable */ j = branch_mostf(T, next); } else if (T->parm->br_tech == GLP_BR_DTH) { /* branch using the heuristic by Dreebeck and Tomlin */ j = branch_drtom(T, next); } else if (T->parm->br_tech == GLP_BR_PCH) { /* hybrid pseudocost heuristic */ j = ios_pcost_branch(T, next); } else xassert(T != T); return j; } /*********************************************************************** * branch_first - choose first branching variable * * This routine looks up the list of structural variables and chooses * the first one, which is of integer kind and has fractional value in * optimal solution to the current LP relaxation. * * This routine also selects the branch to be solved next where integer * infeasibility of the chosen variable is less than in other one. */ static int branch_first(glp_tree *T, int *_next) { int j, next; double beta; /* choose the column to branch on */ for (j = 1; j <= T->n; j++) if (T->non_int[j]) break; xassert(1 <= j && j <= T->n); /* select the branch to be solved next */ beta = glp_get_col_prim(T->mip, j); if (beta - floor(beta) < ceil(beta) - beta) next = GLP_DN_BRNCH; else next = GLP_UP_BRNCH; *_next = next; return j; } /*********************************************************************** * branch_last - choose last branching variable * * This routine looks up the list of structural variables and chooses * the last one, which is of integer kind and has fractional value in * optimal solution to the current LP relaxation. * * This routine also selects the branch to be solved next where integer * infeasibility of the chosen variable is less than in other one. */ static int branch_last(glp_tree *T, int *_next) { int j, next; double beta; /* choose the column to branch on */ for (j = T->n; j >= 1; j--) if (T->non_int[j]) break; xassert(1 <= j && j <= T->n); /* select the branch to be solved next */ beta = glp_get_col_prim(T->mip, j); if (beta - floor(beta) < ceil(beta) - beta) next = GLP_DN_BRNCH; else next = GLP_UP_BRNCH; *_next = next; return j; } /*********************************************************************** * branch_mostf - choose most fractional branching variable * * This routine looks up the list of structural variables and chooses * that one, which is of integer kind and has most fractional value in * optimal solution to the current LP relaxation. * * This routine also selects the branch to be solved next where integer * infeasibility of the chosen variable is less than in other one. * * (Alexander Martin notices that "...most infeasible is as good as * random...".) */ static int branch_mostf(glp_tree *T, int *_next) { int j, jj, next; double beta, most, temp; /* choose the column to branch on */ jj = 0, most = DBL_MAX; for (j = 1; j <= T->n; j++) { if (T->non_int[j]) { beta = glp_get_col_prim(T->mip, j); temp = floor(beta) + 0.5; if (most > fabs(beta - temp)) { jj = j, most = fabs(beta - temp); if (beta < temp) next = GLP_DN_BRNCH; else next = GLP_UP_BRNCH; } } } *_next = next; return jj; } /*********************************************************************** * branch_drtom - choose branching var using Driebeck-Tomlin heuristic * * This routine chooses a structural variable, which is required to be * integral and has fractional value in optimal solution of the current * LP relaxation, using a heuristic proposed by Driebeck and Tomlin. * * The routine also selects the branch to be solved next, again due to * Driebeck and Tomlin. * * This routine is based on the heuristic proposed in: * * Driebeck N.J. An algorithm for the solution of mixed-integer * programming problems, Management Science, 12: 576-87 (1966); * * and improved in: * * Tomlin J.A. Branch and bound methods for integer and non-convex * programming, in J.Abadie (ed.), Integer and Nonlinear Programming, * North-Holland, Amsterdam, pp. 437-50 (1970). * * Must note that this heuristic is time-expensive, because computing * one-step degradation (see the routine below) requires one BTRAN for * each fractional-valued structural variable. */ static int branch_drtom(glp_tree *T, int *_next) { glp_prob *mip = T->mip; int m = mip->m; int n = mip->n; unsigned char *non_int = T->non_int; int j, jj, k, t, next, kase, len, stat, *ind; double x, dk, alfa, delta_j, delta_k, delta_z, dz_dn, dz_up, dd_dn, dd_up, degrad, *val; /* basic solution of LP relaxation must be optimal */ xassert(glp_get_status(mip) == GLP_OPT); /* allocate working arrays */ ind = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(double)); /* nothing has been chosen so far */ jj = 0, degrad = -1.0; /* walk through the list of columns (structural variables) */ for (j = 1; j <= n; j++) { /* if j-th column is not marked as fractional, skip it */ if (!non_int[j]) continue; /* obtain (fractional) value of j-th column in basic solution of LP relaxation */ x = glp_get_col_prim(mip, j); /* since the value of j-th column is fractional, the column is basic; compute corresponding row of the simplex table */ len = glp_eval_tab_row(mip, m+j, ind, val); /* the following fragment computes a change in the objective function: delta Z = new Z - old Z, where old Z is the objective value in the current optimal basis, and new Z is the objective value in the adjacent basis, for two cases: 1) if new upper bound ub' = floor(x[j]) is introduced for j-th column (down branch); 2) if new lower bound lb' = ceil(x[j]) is introduced for j-th column (up branch); since in both cases the solution remaining dual feasible becomes primal infeasible, one implicit simplex iteration is performed to determine the change delta Z; it is obvious that new Z, which is never better than old Z, is a lower (minimization) or upper (maximization) bound of the objective function for down- and up-branches. */ for (kase = -1; kase <= +1; kase += 2) { /* if kase < 0, the new upper bound of x[j] is introduced; in this case x[j] should decrease in order to leave the basis and go to its new upper bound */ /* if kase > 0, the new lower bound of x[j] is introduced; in this case x[j] should increase in order to leave the basis and go to its new lower bound */ /* apply the dual ratio test in order to determine which auxiliary or structural variable should enter the basis to keep dual feasibility */ k = glp_dual_rtest(mip, len, ind, val, kase, 1e-9); if (k != 0) k = ind[k]; /* if no non-basic variable has been chosen, LP relaxation of corresponding branch being primal infeasible and dual unbounded has no primal feasible solution; in this case the change delta Z is formally set to infinity */ if (k == 0) { delta_z = (T->mip->dir == GLP_MIN ? +DBL_MAX : -DBL_MAX); goto skip; } /* row of the simplex table that corresponds to non-basic variable x[k] choosen by the dual ratio test is: x[j] = ... + alfa * x[k] + ... where alfa is the influence coefficient (an element of the simplex table row) */ /* determine the coefficient alfa */ for (t = 1; t <= len; t++) if (ind[t] == k) break; xassert(1 <= t && t <= len); alfa = val[t]; /* since in the adjacent basis the variable x[j] becomes non-basic, knowing its value in the current basis we can determine its change delta x[j] = new x[j] - old x[j] */ delta_j = (kase < 0 ? floor(x) : ceil(x)) - x; /* and knowing the coefficient alfa we can determine the corresponding change delta x[k] = new x[k] - old x[k], where old x[k] is a value of x[k] in the current basis, and new x[k] is a value of x[k] in the adjacent basis */ delta_k = delta_j / alfa; /* Tomlin noticed that if the variable x[k] is of integer kind, its change cannot be less (eventually) than one in the magnitude */ if (k > m && glp_get_col_kind(mip, k-m) != GLP_CV) { /* x[k] is structural integer variable */ if (fabs(delta_k - floor(delta_k + 0.5)) > 1e-3) { if (delta_k > 0.0) delta_k = ceil(delta_k); /* +3.14 -> +4 */ else delta_k = floor(delta_k); /* -3.14 -> -4 */ } } /* now determine the status and reduced cost of x[k] in the current basis */ if (k <= m) { stat = glp_get_row_stat(mip, k); dk = glp_get_row_dual(mip, k); } else { stat = glp_get_col_stat(mip, k-m); dk = glp_get_col_dual(mip, k-m); } /* if the current basis is dual degenerate, some reduced costs which are close to zero may have wrong sign due to round-off errors, so correct the sign of d[k] */ switch (T->mip->dir) { case GLP_MIN: if (stat == GLP_NL && dk < 0.0 || stat == GLP_NU && dk > 0.0 || stat == GLP_NF) dk = 0.0; break; case GLP_MAX: if (stat == GLP_NL && dk > 0.0 || stat == GLP_NU && dk < 0.0 || stat == GLP_NF) dk = 0.0; break; default: xassert(T != T); } /* now knowing the change of x[k] and its reduced cost d[k] we can compute the corresponding change in the objective function delta Z = new Z - old Z = d[k] * delta x[k]; note that due to Tomlin's modification new Z can be even worse than in the adjacent basis */ delta_z = dk * delta_k; skip: /* new Z is never better than old Z, therefore the change delta Z is always non-negative (in case of minimization) or non-positive (in case of maximization) */ switch (T->mip->dir) { case GLP_MIN: xassert(delta_z >= 0.0); break; case GLP_MAX: xassert(delta_z <= 0.0); break; default: xassert(T != T); } /* save the change in the objective fnction for down- and up-branches, respectively */ if (kase < 0) dz_dn = delta_z; else dz_up = delta_z; } /* thus, in down-branch no integer feasible solution can be better than Z + dz_dn, and in up-branch no integer feasible solution can be better than Z + dz_up, where Z is value of the objective function in the current basis */ /* following the heuristic by Driebeck and Tomlin we choose a column (i.e. structural variable) which provides largest degradation of the objective function in some of branches; besides, we select the branch with smaller degradation to be solved next and keep other branch with larger degradation in the active list hoping to minimize the number of further backtrackings */ if (degrad < fabs(dz_dn) || degrad < fabs(dz_up)) { jj = j; if (fabs(dz_dn) < fabs(dz_up)) { /* select down branch to be solved next */ next = GLP_DN_BRNCH; degrad = fabs(dz_up); } else { /* select up branch to be solved next */ next = GLP_UP_BRNCH; degrad = fabs(dz_dn); } /* save the objective changes for printing */ dd_dn = dz_dn, dd_up = dz_up; /* if down- or up-branch has no feasible solution, we does not need to consider other candidates (in principle, the corresponding branch could be pruned right now) */ if (degrad == DBL_MAX) break; } } /* free working arrays */ xfree(ind); xfree(val); /* something must be chosen */ xassert(1 <= jj && jj <= n); #if 1 /* 02/XI-2009 */ if (degrad < 1e-6 * (1.0 + 0.001 * fabs(mip->obj_val))) { jj = branch_mostf(T, &next); goto done; } #endif if (T->parm->msg_lev >= GLP_MSG_DBG) { xprintf("branch_drtom: column %d chosen to branch on\n", jj); if (fabs(dd_dn) == DBL_MAX) xprintf("branch_drtom: down-branch is infeasible\n"); else xprintf("branch_drtom: down-branch bound is %.9e\n", lpx_get_obj_val(mip) + dd_dn); if (fabs(dd_up) == DBL_MAX) xprintf("branch_drtom: up-branch is infeasible\n"); else xprintf("branch_drtom: up-branch bound is %.9e\n", lpx_get_obj_val(mip) + dd_up); } done: *_next = next; return jj; } /**********************************************************************/ struct csa { /* common storage area */ int *dn_cnt; /* int dn_cnt[1+n]; */ /* dn_cnt[j] is the number of subproblems, whose LP relaxations have been solved and which are down-branches for variable x[j]; dn_cnt[j] = 0 means the down pseudocost is uninitialized */ double *dn_sum; /* double dn_sum[1+n]; */ /* dn_sum[j] is the sum of per unit degradations of the objective over all dn_cnt[j] subproblems */ int *up_cnt; /* int up_cnt[1+n]; */ /* up_cnt[j] is the number of subproblems, whose LP relaxations have been solved and which are up-branches for variable x[j]; up_cnt[j] = 0 means the up pseudocost is uninitialized */ double *up_sum; /* double up_sum[1+n]; */ /* up_sum[j] is the sum of per unit degradations of the objective over all up_cnt[j] subproblems */ }; void *ios_pcost_init(glp_tree *tree) { /* initialize working data used on pseudocost branching */ struct csa *csa; int n = tree->n, j; csa = xmalloc(sizeof(struct csa)); csa->dn_cnt = xcalloc(1+n, sizeof(int)); csa->dn_sum = xcalloc(1+n, sizeof(double)); csa->up_cnt = xcalloc(1+n, sizeof(int)); csa->up_sum = xcalloc(1+n, sizeof(double)); for (j = 1; j <= n; j++) { csa->dn_cnt[j] = csa->up_cnt[j] = 0; csa->dn_sum[j] = csa->up_sum[j] = 0.0; } return csa; } static double eval_degrad(glp_prob *P, int j, double bnd) { /* compute degradation of the objective on fixing x[j] at given value with a limited number of dual simplex iterations */ /* this routine fixes column x[j] at specified value bnd, solves resulting LP, and returns a lower bound to degradation of the objective, degrad >= 0 */ glp_prob *lp; glp_smcp parm; int ret; double degrad; /* the current basis must be optimal */ xassert(glp_get_status(P) == GLP_OPT); /* create a copy of P */ lp = glp_create_prob(); glp_copy_prob(lp, P, 0); /* fix column x[j] at specified value */ glp_set_col_bnds(lp, j, GLP_FX, bnd, bnd); /* try to solve resulting LP */ glp_init_smcp(&parm); parm.msg_lev = GLP_MSG_OFF; parm.meth = GLP_DUAL; parm.it_lim = 30; parm.out_dly = 1000; parm.meth = GLP_DUAL; ret = glp_simplex(lp, &parm); if (ret == 0 || ret == GLP_EITLIM) { if (glp_get_prim_stat(lp) == GLP_NOFEAS) { /* resulting LP has no primal feasible solution */ degrad = DBL_MAX; } else if (glp_get_dual_stat(lp) == GLP_FEAS) { /* resulting basis is optimal or at least dual feasible, so we have the correct lower bound to degradation */ if (P->dir == GLP_MIN) degrad = lp->obj_val - P->obj_val; else if (P->dir == GLP_MAX) degrad = P->obj_val - lp->obj_val; else xassert(P != P); /* degradation cannot be negative by definition */ /* note that the lower bound to degradation may be close to zero even if its exact value is zero due to round-off errors on computing the objective value */ if (degrad < 1e-6 * (1.0 + 0.001 * fabs(P->obj_val))) degrad = 0.0; } else { /* the final basis reported by the simplex solver is dual infeasible, so we cannot determine a non-trivial lower bound to degradation */ degrad = 0.0; } } else { /* the simplex solver failed */ degrad = 0.0; } /* delete the copy of P */ glp_delete_prob(lp); return degrad; } void ios_pcost_update(glp_tree *tree) { /* update history information for pseudocost branching */ /* this routine is called every time when LP relaxation of the current subproblem has been solved to optimality with all lazy and cutting plane constraints included */ int j; double dx, dz, psi; struct csa *csa = tree->pcost; xassert(csa != NULL); xassert(tree->curr != NULL); /* if the current subproblem is the root, skip updating */ if (tree->curr->up == NULL) goto skip; /* determine branching variable x[j], which was used in the parent subproblem to create the current subproblem */ j = tree->curr->up->br_var; xassert(1 <= j && j <= tree->n); /* determine the change dx[j] = new x[j] - old x[j], where new x[j] is a value of x[j] in optimal solution to LP relaxation of the current subproblem, old x[j] is a value of x[j] in optimal solution to LP relaxation of the parent subproblem */ dx = tree->mip->col[j]->prim - tree->curr->up->br_val; xassert(dx != 0.0); /* determine corresponding change dz = new dz - old dz in the objective function value */ dz = tree->mip->obj_val - tree->curr->up->lp_obj; /* determine per unit degradation of the objective function */ psi = fabs(dz / dx); /* update history information */ if (dx < 0.0) { /* the current subproblem is down-branch */ csa->dn_cnt[j]++; csa->dn_sum[j] += psi; } else /* dx > 0.0 */ { /* the current subproblem is up-branch */ csa->up_cnt[j]++; csa->up_sum[j] += psi; } skip: return; } void ios_pcost_free(glp_tree *tree) { /* free working area used on pseudocost branching */ struct csa *csa = tree->pcost; xassert(csa != NULL); xfree(csa->dn_cnt); xfree(csa->dn_sum); xfree(csa->up_cnt); xfree(csa->up_sum); xfree(csa); tree->pcost = NULL; return; } static double eval_psi(glp_tree *T, int j, int brnch) { /* compute estimation of pseudocost of variable x[j] for down- or up-branch */ struct csa *csa = T->pcost; double beta, degrad, psi; xassert(csa != NULL); xassert(1 <= j && j <= T->n); if (brnch == GLP_DN_BRNCH) { /* down-branch */ if (csa->dn_cnt[j] == 0) { /* initialize down pseudocost */ beta = T->mip->col[j]->prim; degrad = eval_degrad(T->mip, j, floor(beta)); if (degrad == DBL_MAX) { psi = DBL_MAX; goto done; } csa->dn_cnt[j] = 1; csa->dn_sum[j] = degrad / (beta - floor(beta)); } psi = csa->dn_sum[j] / (double)csa->dn_cnt[j]; } else if (brnch == GLP_UP_BRNCH) { /* up-branch */ if (csa->up_cnt[j] == 0) { /* initialize up pseudocost */ beta = T->mip->col[j]->prim; degrad = eval_degrad(T->mip, j, ceil(beta)); if (degrad == DBL_MAX) { psi = DBL_MAX; goto done; } csa->up_cnt[j] = 1; csa->up_sum[j] = degrad / (ceil(beta) - beta); } psi = csa->up_sum[j] / (double)csa->up_cnt[j]; } else xassert(brnch != brnch); done: return psi; } static void progress(glp_tree *T) { /* display progress of pseudocost initialization */ struct csa *csa = T->pcost; int j, nv = 0, ni = 0; for (j = 1; j <= T->n; j++) { if (glp_ios_can_branch(T, j)) { nv++; if (csa->dn_cnt[j] > 0 && csa->up_cnt[j] > 0) ni++; } } xprintf("Pseudocosts initialized for %d of %d variables\n", ni, nv); return; } int ios_pcost_branch(glp_tree *T, int *_next) { /* choose branching variable with pseudocost branching */ glp_long t = xtime(); int j, jjj, sel; double beta, psi, d1, d2, d, dmax; /* initialize the working arrays */ if (T->pcost == NULL) T->pcost = ios_pcost_init(T); /* nothing has been chosen so far */ jjj = 0, dmax = -1.0; /* go through the list of branching candidates */ for (j = 1; j <= T->n; j++) { if (!glp_ios_can_branch(T, j)) continue; /* determine primal value of x[j] in optimal solution to LP relaxation of the current subproblem */ beta = T->mip->col[j]->prim; /* estimate pseudocost of x[j] for down-branch */ psi = eval_psi(T, j, GLP_DN_BRNCH); if (psi == DBL_MAX) { /* down-branch has no primal feasible solution */ jjj = j, sel = GLP_DN_BRNCH; goto done; } /* estimate degradation of the objective for down-branch */ d1 = psi * (beta - floor(beta)); /* estimate pseudocost of x[j] for up-branch */ psi = eval_psi(T, j, GLP_UP_BRNCH); if (psi == DBL_MAX) { /* up-branch has no primal feasible solution */ jjj = j, sel = GLP_UP_BRNCH; goto done; } /* estimate degradation of the objective for up-branch */ d2 = psi * (ceil(beta) - beta); /* determine d = max(d1, d2) */ d = (d1 > d2 ? d1 : d2); /* choose x[j] which provides maximal estimated degradation of the objective either in down- or up-branch */ if (dmax < d) { dmax = d; jjj = j; /* continue the search from a subproblem, where degradation is less than in other one */ sel = (d1 <= d2 ? GLP_DN_BRNCH : GLP_UP_BRNCH); } /* display progress of pseudocost initialization */ if (T->parm->msg_lev >= GLP_ON) { if (xdifftime(xtime(), t) >= 10.0) { progress(T); t = xtime(); } } } if (dmax == 0.0) { /* no degradation is indicated; choose a variable having most fractional value */ jjj = branch_mostf(T, &sel); } done: *_next = sel; return jjj; } /* eof */ sources_5316/external/glpk/glpspm.c0000644000176700017670000006047311401660400016152 0ustar paulpaul/* glpspm.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glphbm.h" #include "glprgr.h" #include "glpspm.h" /*********************************************************************** * NAME * * spm_create_mat - create general sparse matrix * * SYNOPSIS * * #include "glpspm.h" * SPM *spm_create_mat(int m, int n); * * DESCRIPTION * * The routine spm_create_mat creates a general sparse matrix having * m rows and n columns. Being created the matrix is zero (empty), i.e. * has no elements. * * RETURNS * * The routine returns a pointer to the matrix created. */ SPM *spm_create_mat(int m, int n) { SPM *A; xassert(0 <= m && m < INT_MAX); xassert(0 <= n && n < INT_MAX); A = xmalloc(sizeof(SPM)); A->m = m; A->n = n; if (m == 0 || n == 0) { A->pool = NULL; A->row = NULL; A->col = NULL; } else { int i, j; A->pool = dmp_create_pool(); A->row = xcalloc(1+m, sizeof(SPME *)); for (i = 1; i <= m; i++) A->row[i] = NULL; A->col = xcalloc(1+n, sizeof(SPME *)); for (j = 1; j <= n; j++) A->col[j] = NULL; } return A; } /*********************************************************************** * NAME * * spm_new_elem - add new element to sparse matrix * * SYNOPSIS * * #include "glpspm.h" * SPME *spm_new_elem(SPM *A, int i, int j, double val); * * DESCRIPTION * * The routine spm_new_elem adds a new element to the specified sparse * matrix. Parameters i, j, and val specify the row number, the column * number, and a numerical value of the element, respectively. * * RETURNS * * The routine returns a pointer to the new element added. */ SPME *spm_new_elem(SPM *A, int i, int j, double val) { SPME *e; xassert(1 <= i && i <= A->m); xassert(1 <= j && j <= A->n); e = dmp_get_atom(A->pool, sizeof(SPME)); e->i = i; e->j = j; e->val = val; e->r_prev = NULL; e->r_next = A->row[i]; if (e->r_next != NULL) e->r_next->r_prev = e; e->c_prev = NULL; e->c_next = A->col[j]; if (e->c_next != NULL) e->c_next->c_prev = e; A->row[i] = A->col[j] = e; return e; } /*********************************************************************** * NAME * * spm_delete_mat - delete general sparse matrix * * SYNOPSIS * * #include "glpspm.h" * void spm_delete_mat(SPM *A); * * DESCRIPTION * * The routine deletes the specified general sparse matrix freeing all * the memory allocated to this object. */ void spm_delete_mat(SPM *A) { /* delete sparse matrix */ if (A->pool != NULL) dmp_delete_pool(A->pool); if (A->row != NULL) xfree(A->row); if (A->col != NULL) xfree(A->col); xfree(A); return; } /*********************************************************************** * NAME * * spm_test_mat_e - create test sparse matrix of E(n,c) class * * SYNOPSIS * * #include "glpspm.h" * SPM *spm_test_mat_e(int n, int c); * * DESCRIPTION * * The routine spm_test_mat_e creates a test sparse matrix of E(n,c) * class as described in the book: Ole 0sterby, Zahari Zlatev. Direct * Methods for Sparse Matrices. Springer-Verlag, 1983. * * Matrix of E(n,c) class is a symmetric positive definite matrix of * the order n. It has the number 4 on its main diagonal and the number * -1 on its four co-diagonals, two of which are neighbour to the main * diagonal and two others are shifted from the main diagonal on the * distance c. * * It is necessary that n >= 3 and 2 <= c <= n-1. * * RETURNS * * The routine returns a pointer to the matrix created. */ SPM *spm_test_mat_e(int n, int c) { SPM *A; int i; xassert(n >= 3 && 2 <= c && c <= n-1); A = spm_create_mat(n, n); for (i = 1; i <= n; i++) spm_new_elem(A, i, i, 4.0); for (i = 1; i <= n-1; i++) { spm_new_elem(A, i, i+1, -1.0); spm_new_elem(A, i+1, i, -1.0); } for (i = 1; i <= n-c; i++) { spm_new_elem(A, i, i+c, -1.0); spm_new_elem(A, i+c, i, -1.0); } return A; } /*********************************************************************** * NAME * * spm_test_mat_d - create test sparse matrix of D(n,c) class * * SYNOPSIS * * #include "glpspm.h" * SPM *spm_test_mat_d(int n, int c); * * DESCRIPTION * * The routine spm_test_mat_d creates a test sparse matrix of D(n,c) * class as described in the book: Ole 0sterby, Zahari Zlatev. Direct * Methods for Sparse Matrices. Springer-Verlag, 1983. * * Matrix of D(n,c) class is a non-singular matrix of the order n. It * has unity main diagonal, three co-diagonals above the main diagonal * on the distance c, which are cyclically continued below the main * diagonal, and a triangle block of the size 10x10 in the upper right * corner. * * It is necessary that n >= 14 and 1 <= c <= n-13. * * RETURNS * * The routine returns a pointer to the matrix created. */ SPM *spm_test_mat_d(int n, int c) { SPM *A; int i, j; xassert(n >= 14 && 1 <= c && c <= n-13); A = spm_create_mat(n, n); for (i = 1; i <= n; i++) spm_new_elem(A, i, i, 1.0); for (i = 1; i <= n-c; i++) spm_new_elem(A, i, i+c, (double)(i+1)); for (i = n-c+1; i <= n; i++) spm_new_elem(A, i, i-n+c, (double)(i+1)); for (i = 1; i <= n-c-1; i++) spm_new_elem(A, i, i+c+1, (double)(-i)); for (i = n-c; i <= n; i++) spm_new_elem(A, i, i-n+c+1, (double)(-i)); for (i = 1; i <= n-c-2; i++) spm_new_elem(A, i, i+c+2, 16.0); for (i = n-c-1; i <= n; i++) spm_new_elem(A, i, i-n+c+2, 16.0); for (j = 1; j <= 10; j++) for (i = 1; i <= 11-j; i++) spm_new_elem(A, i, n-11+i+j, 100.0 * (double)j); return A; } /*********************************************************************** * NAME * * spm_show_mat - write sparse matrix pattern in BMP file format * * SYNOPSIS * * #include "glpspm.h" * int spm_show_mat(const SPM *A, const char *fname); * * DESCRIPTION * * The routine spm_show_mat writes pattern of the specified sparse * matrix in uncompressed BMP file format (Windows bitmap) to a binary * file whose name is specified by the character string fname. * * Each pixel corresponds to one matrix element. The pixel colors have * the following meaning: * * Black structurally zero element * White positive element * Cyan negative element * Green zero element * Red duplicate element * * RETURNS * * If no error occured, the routine returns zero. Otherwise, it prints * an appropriate error message and returns non-zero. */ int spm_show_mat(const SPM *A, const char *fname) { int m = A->m; int n = A->n; int i, j, k, ret; char *map; xprintf("spm_show_mat: writing matrix pattern to `%s'...\n", fname); xassert(1 <= m && m <= 32767); xassert(1 <= n && n <= 32767); map = xmalloc(m * n); memset(map, 0x08, m * n); for (i = 1; i <= m; i++) { SPME *e; for (e = A->row[i]; e != NULL; e = e->r_next) { j = e->j; xassert(1 <= j && j <= n); k = n * (i - 1) + (j - 1); if (map[k] != 0x08) map[k] = 0x0C; else if (e->val > 0.0) map[k] = 0x0F; else if (e->val < 0.0) map[k] = 0x0B; else map[k] = 0x0A; } } ret = rgr_write_bmp16(fname, m, n, map); xfree(map); return ret; } /*********************************************************************** * NAME * * spm_read_hbm - read sparse matrix in Harwell-Boeing format * * SYNOPSIS * * #include "glpspm.h" * SPM *spm_read_hbm(const char *fname); * * DESCRIPTION * * The routine spm_read_hbm reads a sparse matrix in the Harwell-Boeing * format from a text file whose name is the character string fname. * * Detailed description of the Harwell-Boeing format recognised by this * routine can be found in the following report: * * I.S.Duff, R.G.Grimes, J.G.Lewis. User's Guide for the Harwell-Boeing * Sparse Matrix Collection (Release I), TR/PA/92/86, October 1992. * * NOTE * * The routine spm_read_hbm reads the matrix "as is", due to which zero * and/or duplicate elements can appear in the matrix. * * RETURNS * * If no error occured, the routine returns a pointer to the matrix * created. Otherwise, the routine prints an appropriate error message * and returns NULL. */ SPM *spm_read_hbm(const char *fname) { SPM *A = NULL; HBM *hbm; int nrow, ncol, nnzero, i, j, beg, end, ptr, *colptr, *rowind; double val, *values; char *mxtype; hbm = hbm_read_mat(fname); if (hbm == NULL) { xprintf("spm_read_hbm: unable to read matrix\n"); goto fini; } mxtype = hbm->mxtype; nrow = hbm->nrow; ncol = hbm->ncol; nnzero = hbm->nnzero; colptr = hbm->colptr; rowind = hbm->rowind; values = hbm->values; if (!(strcmp(mxtype, "RSA") == 0 || strcmp(mxtype, "PSA") == 0 || strcmp(mxtype, "RUA") == 0 || strcmp(mxtype, "PUA") == 0 || strcmp(mxtype, "RRA") == 0 || strcmp(mxtype, "PRA") == 0)) { xprintf("spm_read_hbm: matrix type `%s' not supported\n", mxtype); goto fini; } A = spm_create_mat(nrow, ncol); if (mxtype[1] == 'S' || mxtype[1] == 'U') xassert(nrow == ncol); for (j = 1; j <= ncol; j++) { beg = colptr[j]; end = colptr[j+1]; xassert(1 <= beg && beg <= end && end <= nnzero + 1); for (ptr = beg; ptr < end; ptr++) { i = rowind[ptr]; xassert(1 <= i && i <= nrow); if (mxtype[0] == 'R') val = values[ptr]; else val = 1.0; spm_new_elem(A, i, j, val); if (mxtype[1] == 'S' && i != j) spm_new_elem(A, j, i, val); } } fini: if (hbm != NULL) hbm_free_mat(hbm); return A; } /*********************************************************************** * NAME * * spm_count_nnz - determine number of non-zeros in sparse matrix * * SYNOPSIS * * #include "glpspm.h" * int spm_count_nnz(const SPM *A); * * RETURNS * * The routine spm_count_nnz returns the number of structural non-zero * elements in the specified sparse matrix. */ int spm_count_nnz(const SPM *A) { SPME *e; int i, nnz = 0; for (i = 1; i <= A->m; i++) for (e = A->row[i]; e != NULL; e = e->r_next) nnz++; return nnz; } /*********************************************************************** * NAME * * spm_drop_zeros - remove zero elements from sparse matrix * * SYNOPSIS * * #include "glpspm.h" * int spm_drop_zeros(SPM *A, double eps); * * DESCRIPTION * * The routine spm_drop_zeros removes all elements from the specified * sparse matrix, whose absolute value is less than eps. * * If the parameter eps is 0, only zero elements are removed from the * matrix. * * RETURNS * * The routine returns the number of elements removed. */ int spm_drop_zeros(SPM *A, double eps) { SPME *e, *next; int i, count = 0; for (i = 1; i <= A->m; i++) { for (e = A->row[i]; e != NULL; e = next) { next = e->r_next; if (e->val == 0.0 || fabs(e->val) < eps) { /* remove element from the row list */ if (e->r_prev == NULL) A->row[e->i] = e->r_next; else e->r_prev->r_next = e->r_next; if (e->r_next == NULL) ; else e->r_next->r_prev = e->r_prev; /* remove element from the column list */ if (e->c_prev == NULL) A->col[e->j] = e->c_next; else e->c_prev->c_next = e->c_next; if (e->c_next == NULL) ; else e->c_next->c_prev = e->c_prev; /* return element to the memory pool */ dmp_free_atom(A->pool, e, sizeof(SPME)); count++; } } } return count; } /*********************************************************************** * NAME * * spm_read_mat - read sparse matrix from text file * * SYNOPSIS * * #include "glpspm.h" * SPM *spm_read_mat(const char *fname); * * DESCRIPTION * * The routine reads a sparse matrix from a text file whose name is * specified by the parameter fname. * * For the file format see description of the routine spm_write_mat. * * RETURNS * * On success the routine returns a pointer to the matrix created, * otherwise NULL. */ #if 1 SPM *spm_read_mat(const char *fname) { xassert(fname != fname); return NULL; } #else SPM *spm_read_mat(const char *fname) { SPM *A = NULL; PDS *pds; jmp_buf jump; int i, j, k, m, n, nnz, fail = 0; double val; xprintf("spm_read_mat: reading matrix from `%s'...\n", fname); pds = pds_open_file(fname); if (pds == NULL) { xprintf("spm_read_mat: unable to open `%s' - %s\n", fname, strerror(errno)); fail = 1; goto done; } if (setjmp(jump)) { fail = 1; goto done; } pds_set_jump(pds, jump); /* number of rows, number of columns, number of non-zeros */ m = pds_scan_int(pds); if (m < 0) pds_error(pds, "invalid number of rows\n"); n = pds_scan_int(pds); if (n < 0) pds_error(pds, "invalid number of columns\n"); nnz = pds_scan_int(pds); if (nnz < 0) pds_error(pds, "invalid number of non-zeros\n"); /* create matrix */ xprintf("spm_read_mat: %d rows, %d columns, %d non-zeros\n", m, n, nnz); A = spm_create_mat(m, n); /* read matrix elements */ for (k = 1; k <= nnz; k++) { /* row index, column index, element value */ i = pds_scan_int(pds); if (!(1 <= i && i <= m)) pds_error(pds, "row index out of range\n"); j = pds_scan_int(pds); if (!(1 <= j && j <= n)) pds_error(pds, "column index out of range\n"); val = pds_scan_num(pds); /* add new element to the matrix */ spm_new_elem(A, i, j, val); } xprintf("spm_read_mat: %d lines were read\n", pds->count); done: if (pds != NULL) pds_close_file(pds); if (fail && A != NULL) spm_delete_mat(A), A = NULL; return A; } #endif /*********************************************************************** * NAME * * spm_write_mat - write sparse matrix to text file * * SYNOPSIS * * #include "glpspm.h" * int spm_write_mat(const SPM *A, const char *fname); * * DESCRIPTION * * The routine spm_write_mat writes the specified sparse matrix to a * text file whose name is specified by the parameter fname. This file * can be read back with the routine spm_read_mat. * * RETURNS * * On success the routine returns zero, otherwise non-zero. * * FILE FORMAT * * The file created by the routine spm_write_mat is a plain text file, * which contains the following information: * * m n nnz * row[1] col[1] val[1] * row[2] col[2] val[2] * . . . * row[nnz] col[nnz] val[nnz] * * where: * m is the number of rows; * n is the number of columns; * nnz is the number of non-zeros; * row[k], k = 1,...,nnz, are row indices; * col[k], k = 1,...,nnz, are column indices; * val[k], k = 1,...,nnz, are element values. */ #if 1 int spm_write_mat(const SPM *A, const char *fname) { xassert(A != A); xassert(fname != fname); return 0; } #else int spm_write_mat(const SPM *A, const char *fname) { FILE *fp; int i, nnz, ret = 0; xprintf("spm_write_mat: writing matrix to `%s'...\n", fname); fp = fopen(fname, "w"); if (fp == NULL) { xprintf("spm_write_mat: unable to create `%s' - %s\n", fname, strerror(errno)); ret = 1; goto done; } /* number of rows, number of columns, number of non-zeros */ nnz = spm_count_nnz(A); fprintf(fp, "%d %d %d\n", A->m, A->n, nnz); /* walk through rows of the matrix */ for (i = 1; i <= A->m; i++) { SPME *e; /* walk through elements of i-th row */ for (e = A->row[i]; e != NULL; e = e->r_next) { /* row index, column index, element value */ fprintf(fp, "%d %d %.*g\n", e->i, e->j, DBL_DIG, e->val); } } fflush(fp); if (ferror(fp)) { xprintf("spm_write_mat: writing error on `%s' - %s\n", fname, strerror(errno)); ret = 1; goto done; } xprintf("spm_write_mat: %d lines were written\n", 1 + nnz); done: if (fp != NULL) fclose(fp); return ret; } #endif /*********************************************************************** * NAME * * spm_transpose - transpose sparse matrix * * SYNOPSIS * * #include "glpspm.h" * SPM *spm_transpose(const SPM *A); * * RETURNS * * The routine computes and returns sparse matrix B, which is a matrix * transposed to sparse matrix A. */ SPM *spm_transpose(const SPM *A) { SPM *B; int i; B = spm_create_mat(A->n, A->m); for (i = 1; i <= A->m; i++) { SPME *e; for (e = A->row[i]; e != NULL; e = e->r_next) spm_new_elem(B, e->j, i, e->val); } return B; } SPM *spm_add_sym(const SPM *A, const SPM *B) { /* add two sparse matrices (symbolic phase) */ SPM *C; int i, j, *flag; xassert(A->m == B->m); xassert(A->n == B->n); /* create resultant matrix */ C = spm_create_mat(A->m, A->n); /* allocate and clear the flag array */ flag = xcalloc(1+C->n, sizeof(int)); for (j = 1; j <= C->n; j++) flag[j] = 0; /* compute pattern of C = A + B */ for (i = 1; i <= C->m; i++) { SPME *e; /* at the beginning i-th row of C is empty */ /* (i-th row of C) := (i-th row of C) union (i-th row of A) */ for (e = A->row[i]; e != NULL; e = e->r_next) { /* (note that i-th row of A may have duplicate elements) */ j = e->j; if (!flag[j]) { spm_new_elem(C, i, j, 0.0); flag[j] = 1; } } /* (i-th row of C) := (i-th row of C) union (i-th row of B) */ for (e = B->row[i]; e != NULL; e = e->r_next) { /* (note that i-th row of B may have duplicate elements) */ j = e->j; if (!flag[j]) { spm_new_elem(C, i, j, 0.0); flag[j] = 1; } } /* reset the flag array */ for (e = C->row[i]; e != NULL; e = e->r_next) flag[e->j] = 0; } /* check and deallocate the flag array */ for (j = 1; j <= C->n; j++) xassert(!flag[j]); xfree(flag); return C; } void spm_add_num(SPM *C, double alfa, const SPM *A, double beta, const SPM *B) { /* add two sparse matrices (numeric phase) */ int i, j; double *work; /* allocate and clear the working array */ work = xcalloc(1+C->n, sizeof(double)); for (j = 1; j <= C->n; j++) work[j] = 0.0; /* compute matrix C = alfa * A + beta * B */ for (i = 1; i <= C->n; i++) { SPME *e; /* work := alfa * (i-th row of A) + beta * (i-th row of B) */ /* (note that A and/or B may have duplicate elements) */ for (e = A->row[i]; e != NULL; e = e->r_next) work[e->j] += alfa * e->val; for (e = B->row[i]; e != NULL; e = e->r_next) work[e->j] += beta * e->val; /* (i-th row of C) := work, work := 0 */ for (e = C->row[i]; e != NULL; e = e->r_next) { j = e->j; e->val = work[j]; work[j] = 0.0; } } /* check and deallocate the working array */ for (j = 1; j <= C->n; j++) xassert(work[j] == 0.0); xfree(work); return; } SPM *spm_add_mat(double alfa, const SPM *A, double beta, const SPM *B) { /* add two sparse matrices (driver routine) */ SPM *C; C = spm_add_sym(A, B); spm_add_num(C, alfa, A, beta, B); return C; } SPM *spm_mul_sym(const SPM *A, const SPM *B) { /* multiply two sparse matrices (symbolic phase) */ int i, j, k, *flag; SPM *C; xassert(A->n == B->m); /* create resultant matrix */ C = spm_create_mat(A->m, B->n); /* allocate and clear the flag array */ flag = xcalloc(1+C->n, sizeof(int)); for (j = 1; j <= C->n; j++) flag[j] = 0; /* compute pattern of C = A * B */ for (i = 1; i <= C->m; i++) { SPME *e, *ee; /* compute pattern of i-th row of C */ for (e = A->row[i]; e != NULL; e = e->r_next) { k = e->j; for (ee = B->row[k]; ee != NULL; ee = ee->r_next) { j = ee->j; /* if a[i,k] != 0 and b[k,j] != 0 then c[i,j] != 0 */ if (!flag[j]) { /* c[i,j] does not exist, so create it */ spm_new_elem(C, i, j, 0.0); flag[j] = 1; } } } /* reset the flag array */ for (e = C->row[i]; e != NULL; e = e->r_next) flag[e->j] = 0; } /* check and deallocate the flag array */ for (j = 1; j <= C->n; j++) xassert(!flag[j]); xfree(flag); return C; } void spm_mul_num(SPM *C, const SPM *A, const SPM *B) { /* multiply two sparse matrices (numeric phase) */ int i, j; double *work; /* allocate and clear the working array */ work = xcalloc(1+A->n, sizeof(double)); for (j = 1; j <= A->n; j++) work[j] = 0.0; /* compute matrix C = A * B */ for (i = 1; i <= C->m; i++) { SPME *e, *ee; double temp; /* work := (i-th row of A) */ /* (note that A may have duplicate elements) */ for (e = A->row[i]; e != NULL; e = e->r_next) work[e->j] += e->val; /* compute i-th row of C */ for (e = C->row[i]; e != NULL; e = e->r_next) { j = e->j; /* c[i,j] := work * (j-th column of B) */ temp = 0.0; for (ee = B->col[j]; ee != NULL; ee = ee->c_next) temp += work[ee->i] * ee->val; e->val = temp; } /* reset the working array */ for (e = A->row[i]; e != NULL; e = e->r_next) work[e->j] = 0.0; } /* check and deallocate the working array */ for (j = 1; j <= A->n; j++) xassert(work[j] == 0.0); xfree(work); return; } SPM *spm_mul_mat(const SPM *A, const SPM *B) { /* multiply two sparse matrices (driver routine) */ SPM *C; C = spm_mul_sym(A, B); spm_mul_num(C, A, B); return C; } PER *spm_create_per(int n) { /* create permutation matrix */ PER *P; int k; xassert(n >= 0); P = xmalloc(sizeof(PER)); P->n = n; P->row = xcalloc(1+n, sizeof(int)); P->col = xcalloc(1+n, sizeof(int)); /* initially it is identity matrix */ for (k = 1; k <= n; k++) P->row[k] = P->col[k] = k; return P; } void spm_check_per(PER *P) { /* check permutation matrix for correctness */ int i, j; xassert(P->n >= 0); for (i = 1; i <= P->n; i++) { j = P->row[i]; xassert(1 <= j && j <= P->n); xassert(P->col[j] == i); } return; } void spm_delete_per(PER *P) { /* delete permutation matrix */ xfree(P->row); xfree(P->col); xfree(P); return; } /* eof */ sources_5316/external/glpk/glpnet.h0000644000176700017670000000437311401660400016143 0ustar paulpaul/* glpnet.h (graph and network algorithms) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPNET_H #define GLPNET_H #define mc21a _glp_mc21a int mc21a(int n, const int icn[], const int ip[], const int lenr[], int iperm[], int pr[], int arp[], int cv[], int out[]); /* permutations for zero-free diagonal */ #define mc13d _glp_mc13d int mc13d(int n, const int icn[], const int ip[], const int lenr[], int ior[], int ib[], int lowl[], int numb[], int prev[]); /* permutations to block triangular form */ #define okalg _glp_okalg int okalg(int nv, int na, const int tail[], const int head[], const int low[], const int cap[], const int cost[], int x[], int pi[]); /* out-of-kilter algorithm */ #define ffalg _glp_ffalg void ffalg(int nv, int na, const int tail[], const int head[], int s, int t, const int cap[], int x[], char cut[]); /* Ford-Fulkerson algorithm */ #define wclique _glp_wclique int wclique(int n, const int w[], const unsigned char a[], int ind[]); /* find maximum weight clique with Ostergard's algorithm */ #define kellerman _glp_kellerman int kellerman(int n, int (*func)(void *info, int i, int ind[]), void *info, void /* glp_graph */ *H); /* cover edges by cliques with Kellerman's heuristic */ #endif /* eof */ sources_5316/external/glpk/glpnet06.c0000644000176700017670000003060611401660400016302 0ustar paulpaul/* glpnet06.c (out-of-kilter algorithm) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glpnet.h" /*********************************************************************** * NAME * * okalg - out-of-kilter algorithm * * SYNOPSIS * * #include "glpnet.h" * int okalg(int nv, int na, const int tail[], const int head[], * const int low[], const int cap[], const int cost[], int x[], * int pi[]); * * DESCRIPTION * * The routine okalg implements the out-of-kilter algorithm to find a * minimal-cost circulation in the specified flow network. * * INPUT PARAMETERS * * nv is the number of nodes, nv >= 0. * * na is the number of arcs, na >= 0. * * tail[a], a = 1,...,na, is the index of tail node of arc a. * * head[a], a = 1,...,na, is the index of head node of arc a. * * low[a], a = 1,...,na, is an lower bound to the flow through arc a. * * cap[a], a = 1,...,na, is an upper bound to the flow through arc a, * which is the capacity of the arc. * * cost[a], a = 1,...,na, is a per-unit cost of the flow through arc a. * * NOTES * * 1. Multiple arcs are allowed, but self-loops are not allowed. * * 2. It is required that 0 <= low[a] <= cap[a] for all arcs. * * 3. Arc costs may have any sign. * * OUTPUT PARAMETERS * * x[a], a = 1,...,na, is optimal value of the flow through arc a. * * pi[i], i = 1,...,nv, is Lagrange multiplier for flow conservation * equality constraint corresponding to node i (the node potential). * * RETURNS * * 0 optimal circulation found; * * 1 there is no feasible circulation; * * 2 integer overflow occured; * * 3 optimality test failed (logic error). * * REFERENCES * * L.R.Ford, Jr., and D.R.Fulkerson, "Flows in Networks," The RAND * Corp., Report R-375-PR (August 1962), Chap. III "Minimal Cost Flow * Problems," pp.113-26. */ static int overflow(int u, int v) { /* check for integer overflow on computing u + v */ if (u > 0 && v > 0 && u + v < 0) return 1; if (u < 0 && v < 0 && u + v > 0) return 1; return 0; } int okalg(int nv, int na, const int tail[], const int head[], const int low[], const int cap[], const int cost[], int x[], int pi[]) { int a, aok, delta, i, j, k, lambda, pos1, pos2, s, t, temp, ret, *ptr, *arc, *link, *list; /* sanity checks */ xassert(nv >= 0); xassert(na >= 0); for (a = 1; a <= na; a++) { i = tail[a], j = head[a]; xassert(1 <= i && i <= nv); xassert(1 <= j && j <= nv); xassert(i != j); xassert(0 <= low[a] && low[a] <= cap[a]); } /* allocate working arrays */ ptr = xcalloc(1+nv+1, sizeof(int)); arc = xcalloc(1+na+na, sizeof(int)); link = xcalloc(1+nv, sizeof(int)); list = xcalloc(1+nv, sizeof(int)); /* ptr[i] := (degree of node i) */ for (i = 1; i <= nv; i++) ptr[i] = 0; for (a = 1; a <= na; a++) { ptr[tail[a]]++; ptr[head[a]]++; } /* initialize arc pointers */ ptr[1]++; for (i = 1; i < nv; i++) ptr[i+1] += ptr[i]; ptr[nv+1] = ptr[nv]; /* build arc lists */ for (a = 1; a <= na; a++) { arc[--ptr[tail[a]]] = a; arc[--ptr[head[a]]] = a; } xassert(ptr[1] == 1); xassert(ptr[nv+1] == na+na+1); /* now the indices of arcs incident to node i are stored in locations arc[ptr[i]], arc[ptr[i]+1], ..., arc[ptr[i+1]-1] */ /* initialize arc flows and node potentials */ for (a = 1; a <= na; a++) x[a] = 0; for (i = 1; i <= nv; i++) pi[i] = 0; loop: /* main loop starts here */ /* find out-of-kilter arc */ aok = 0; for (a = 1; a <= na; a++) { i = tail[a], j = head[a]; if (overflow(cost[a], pi[i] - pi[j])) { ret = 2; goto done; } lambda = cost[a] + (pi[i] - pi[j]); if (x[a] < low[a] || lambda < 0 && x[a] < cap[a]) { /* arc a = i->j is out of kilter, and we need to increase the flow through this arc */ aok = a, s = j, t = i; break; } if (x[a] > cap[a] || lambda > 0 && x[a] > low[a]) { /* arc a = i->j is out of kilter, and we need to decrease the flow through this arc */ aok = a, s = i, t = j; break; } } if (aok == 0) { /* all arcs are in kilter */ /* check for feasibility */ for (a = 1; a <= na; a++) { if (!(low[a] <= x[a] && x[a] <= cap[a])) { ret = 3; goto done; } } for (i = 1; i <= nv; i++) { temp = 0; for (k = ptr[i]; k < ptr[i+1]; k++) { a = arc[k]; if (tail[a] == i) { /* a is outgoing arc */ temp += x[a]; } else if (head[a] == i) { /* a is incoming arc */ temp -= x[a]; } else xassert(a != a); } if (temp != 0) { ret = 3; goto done; } } /* check for optimality */ for (a = 1; a <= na; a++) { i = tail[a], j = head[a]; lambda = cost[a] + (pi[i] - pi[j]); if (lambda > 0 && x[a] != low[a] || lambda < 0 && x[a] != cap[a]) { ret = 3; goto done; } } /* current circulation is optimal */ ret = 0; goto done; } /* now we need to find a cycle (t, a, s, ..., t), which allows increasing the flow along it, where a is the out-of-kilter arc just found */ /* link[i] = 0 means that node i is not labelled yet; link[i] = a means that arc a immediately precedes node i */ /* initially only node s is labelled */ for (i = 1; i <= nv; i++) link[i] = 0; link[s] = aok, list[1] = s, pos1 = pos2 = 1; /* breadth first search */ while (pos1 <= pos2) { /* dequeue node i */ i = list[pos1++]; /* consider all arcs incident to node i */ for (k = ptr[i]; k < ptr[i+1]; k++) { a = arc[k]; if (tail[a] == i) { /* a = i->j is a forward arc from s to t */ j = head[a]; /* if node j has been labelled, skip the arc */ if (link[j] != 0) continue; /* if the arc does not allow increasing the flow through it, skip the arc */ if (x[a] >= cap[a]) continue; if (overflow(cost[a], pi[i] - pi[j])) { ret = 2; goto done; } lambda = cost[a] + (pi[i] - pi[j]); if (lambda > 0 && x[a] >= low[a]) continue; } else if (head[a] == i) { /* a = i<-j is a backward arc from s to t */ j = tail[a]; /* if node j has been labelled, skip the arc */ if (link[j] != 0) continue; /* if the arc does not allow decreasing the flow through it, skip the arc */ if (x[a] <= low[a]) continue; if (overflow(cost[a], pi[j] - pi[i])) { ret = 2; goto done; } lambda = cost[a] + (pi[j] - pi[i]); if (lambda < 0 && x[a] <= cap[a]) continue; } else xassert(a != a); /* label node j and enqueue it */ link[j] = a, list[++pos2] = j; /* check for breakthrough */ if (j == t) goto brkt; } } /* NONBREAKTHROUGH */ /* consider all arcs, whose one endpoint is labelled and other is not, and determine maximal change of node potentials */ delta = 0; for (a = 1; a <= na; a++) { i = tail[a], j = head[a]; if (link[i] != 0 && link[j] == 0) { /* a = i->j, where node i is labelled, node j is not */ if (overflow(cost[a], pi[i] - pi[j])) { ret = 2; goto done; } lambda = cost[a] + (pi[i] - pi[j]); if (x[a] <= cap[a] && lambda > 0) if (delta == 0 || delta > + lambda) delta = + lambda; } else if (link[i] == 0 && link[j] != 0) { /* a = j<-i, where node j is labelled, node i is not */ if (overflow(cost[a], pi[i] - pi[j])) { ret = 2; goto done; } lambda = cost[a] + (pi[i] - pi[j]); if (x[a] >= low[a] && lambda < 0) if (delta == 0 || delta > - lambda) delta = - lambda; } } if (delta == 0) { /* there is no feasible circulation */ ret = 1; goto done; } /* increase potentials of all unlabelled nodes */ for (i = 1; i <= nv; i++) { if (link[i] == 0) { if (overflow(pi[i], delta)) { ret = 2; goto done; } pi[i] += delta; } } goto loop; brkt: /* BREAKTHROUGH */ /* walk through arcs of the cycle (t, a, s, ..., t) found in the reverse order and determine maximal change of the flow */ delta = 0; for (j = t;; j = i) { /* arc a immediately precedes node j in the cycle */ a = link[j]; if (head[a] == j) { /* a = i->j is a forward arc of the cycle */ i = tail[a]; lambda = cost[a] + (pi[i] - pi[j]); if (lambda > 0 && x[a] < low[a]) { /* x[a] may be increased until its lower bound */ temp = low[a] - x[a]; } else if (lambda <= 0 && x[a] < cap[a]) { /* x[a] may be increased until its upper bound */ temp = cap[a] - x[a]; } else xassert(a != a); } else if (tail[a] == j) { /* a = i<-j is a backward arc of the cycle */ i = head[a]; lambda = cost[a] + (pi[j] - pi[i]); if (lambda < 0 && x[a] > cap[a]) { /* x[a] may be decreased until its upper bound */ temp = x[a] - cap[a]; } else if (lambda >= 0 && x[a] > low[a]) { /* x[a] may be decreased until its lower bound */ temp = x[a] - low[a]; } else xassert(a != a); } else xassert(a != a); if (delta == 0 || delta > temp) delta = temp; /* check for end of the cycle */ if (i == t) break; } xassert(delta > 0); /* increase the flow along the cycle */ for (j = t;; j = i) { /* arc a immediately precedes node j in the cycle */ a = link[j]; if (head[a] == j) { /* a = i->j is a forward arc of the cycle */ i = tail[a]; /* overflow cannot occur */ x[a] += delta; } else if (tail[a] == j) { /* a = i<-j is a backward arc of the cycle */ i = head[a]; /* overflow cannot occur */ x[a] -= delta; } else xassert(a != a); /* check for end of the cycle */ if (i == t) break; } goto loop; done: /* free working arrays */ xfree(ptr); xfree(arc); xfree(link); xfree(list); return ret; } /* eof */ sources_5316/external/glpk/glprgr.c0000644000176700017670000001415411401660400016140 0ustar paulpaul/* glprgr.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_ERRNO #define _GLPSTD_STDIO #include "glpenv.h" #include "glprgr.h" #define xfault xerror /*********************************************************************** * NAME * * rgr_write_bmp16 - write 16-color raster image in BMP file format * * SYNOPSIS * * #include "glprgr.h" * int rgr_write_bmp16(const char *fname, int m, int n, const char * map[]); * * DESCRIPTION * * The routine rgr_write_bmp16 writes 16-color raster image in * uncompressed BMP file format (Windows bitmap) to a binary file whose * name is specified by the character string fname. * * The parameters m and n specify, respectively, the number of rows and * the numbers of columns (i.e. height and width) of the raster image. * * The character array map has m*n elements. Elements map[0, ..., n-1] * correspond to the first (top) scanline, elements map[n, ..., 2*n-1] * correspond to the second scanline, etc. * * Each element of the array map specifies a color of the corresponding * pixel as 8-bit binary number XXXXIRGB, where four high-order bits (X) * are ignored, I is high intensity bit, R is red color bit, G is green * color bit, and B is blue color bit. Thus, all 16 possible colors are * coded as following hexadecimal numbers: * * 0x00 = black 0x08 = dark gray * 0x01 = blue 0x09 = bright blue * 0x02 = green 0x0A = bright green * 0x03 = cyan 0x0B = bright cyan * 0x04 = red 0x0C = bright red * 0x05 = magenta 0x0D = bright magenta * 0x06 = brown 0x0E = yellow * 0x07 = light gray 0x0F = white * * RETURNS * * If no error occured, the routine returns zero; otherwise, it prints * an appropriate error message and returns non-zero. */ static void put_byte(FILE *fp, int c) { fputc(c, fp); return; } static void put_word(FILE *fp, int w) { /* big endian */ put_byte(fp, w); put_byte(fp, w >> 8); return; } static void put_dword(FILE *fp, int d) { /* big endian */ put_word(fp, d); put_word(fp, d >> 16); return; } int rgr_write_bmp16(const char *fname, int m, int n, const char map[]) { FILE *fp; int offset, bmsize, i, j, b, ret = 0; if (!(1 <= m && m <= 32767)) xfault("rgr_write_bmp16: m = %d; invalid height\n", m); if (!(1 <= n && n <= 32767)) xfault("rgr_write_bmp16: n = %d; invalid width\n", n); fp = fopen(fname, "wb"); if (fp == NULL) { xprintf("rgr_write_bmp16: unable to create `%s' - %s\n", fname, strerror(errno)); ret = 1; goto fini; } offset = 14 + 40 + 16 * 4; bmsize = (4 * n + 31) / 32; /* struct BMPFILEHEADER (14 bytes) */ /* UINT bfType */ put_byte(fp, 'B'), put_byte(fp, 'M'); /* DWORD bfSize */ put_dword(fp, offset + bmsize * 4); /* UINT bfReserved1 */ put_word(fp, 0); /* UNIT bfReserved2 */ put_word(fp, 0); /* DWORD bfOffBits */ put_dword(fp, offset); /* struct BMPINFOHEADER (40 bytes) */ /* DWORD biSize */ put_dword(fp, 40); /* LONG biWidth */ put_dword(fp, n); /* LONG biHeight */ put_dword(fp, m); /* WORD biPlanes */ put_word(fp, 1); /* WORD biBitCount */ put_word(fp, 4); /* DWORD biCompression */ put_dword(fp, 0 /* BI_RGB */); /* DWORD biSizeImage */ put_dword(fp, 0); /* LONG biXPelsPerMeter */ put_dword(fp, 2953 /* 75 dpi */); /* LONG biYPelsPerMeter */ put_dword(fp, 2953 /* 75 dpi */); /* DWORD biClrUsed */ put_dword(fp, 0); /* DWORD biClrImportant */ put_dword(fp, 0); /* struct RGBQUAD (16 * 4 = 64 bytes) */ /* CGA-compatible colors: */ /* 0x00 = black */ put_dword(fp, 0x000000); /* 0x01 = blue */ put_dword(fp, 0x000080); /* 0x02 = green */ put_dword(fp, 0x008000); /* 0x03 = cyan */ put_dword(fp, 0x008080); /* 0x04 = red */ put_dword(fp, 0x800000); /* 0x05 = magenta */ put_dword(fp, 0x800080); /* 0x06 = brown */ put_dword(fp, 0x808000); /* 0x07 = light gray */ put_dword(fp, 0xC0C0C0); /* 0x08 = dark gray */ put_dword(fp, 0x808080); /* 0x09 = bright blue */ put_dword(fp, 0x0000FF); /* 0x0A = bright green */ put_dword(fp, 0x00FF00); /* 0x0B = bright cyan */ put_dword(fp, 0x00FFFF); /* 0x0C = bright red */ put_dword(fp, 0xFF0000); /* 0x0D = bright magenta */ put_dword(fp, 0xFF00FF); /* 0x0E = yellow */ put_dword(fp, 0xFFFF00); /* 0x0F = white */ put_dword(fp, 0xFFFFFF); /* pixel data bits */ b = 0; for (i = m - 1; i >= 0; i--) { for (j = 0; j < ((n + 7) / 8) * 8; j++) { b <<= 4; b |= (j < n ? map[i * n + j] & 15 : 0); if (j & 1) put_byte(fp, b); } } fflush(fp); if (ferror(fp)) { xprintf("rgr_write_bmp16: write error on `%s' - %s\n", fname, strerror(errno)); ret = 1; } fini: if (fp != NULL) fclose(fp); return ret; } /* eof */ sources_5316/external/glpk/glpios07.c0000644000176700017670000004523111401660400016307 0ustar paulpaul/* glpios07.c (mixed cover cut generator) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*---------------------------------------------------------------------- -- COVER INEQUALITIES -- -- Consider the set of feasible solutions to 0-1 knapsack problem: -- -- sum a[j]*x[j] <= b, (1) -- j in J -- -- x[j] is binary, (2) -- -- where, wlog, we assume that a[j] > 0 (since 0-1 variables can be -- complemented) and a[j] <= b (since a[j] > b implies x[j] = 0). -- -- A set C within J is called a cover if -- -- sum a[j] > b. (3) -- j in C -- -- For any cover C the inequality -- -- sum x[j] <= |C| - 1 (4) -- j in C -- -- is called a cover inequality and is valid for (1)-(2). -- -- MIXED COVER INEQUALITIES -- -- Consider the set of feasible solutions to mixed knapsack problem: -- -- sum a[j]*x[j] + y <= b, (5) -- j in J -- -- x[j] is binary, (6) -- -- 0 <= y <= u is continuous, (7) -- -- where again we assume that a[j] > 0. -- -- Let C within J be some set. From (1)-(4) it follows that -- -- sum a[j] > b - y (8) -- j in C -- -- implies -- -- sum x[j] <= |C| - 1. (9) -- j in C -- -- Thus, we need to modify the inequality (9) in such a way that it be -- a constraint only if the condition (8) is satisfied. -- -- Consider the following inequality: -- -- sum x[j] <= |C| - t. (10) -- j in C -- -- If 0 < t <= 1, then (10) is equivalent to (9), because all x[j] are -- binary variables. On the other hand, if t <= 0, (10) being satisfied -- for any values of x[j] is not a constraint. -- -- Let -- -- t' = sum a[j] + y - b. (11) -- j in C -- -- It is understood that the condition t' > 0 is equivalent to (8). -- Besides, from (6)-(7) it follows that t' has an implied upper bound: -- -- t'max = sum a[j] + u - b. (12) -- j in C -- -- This allows to express the parameter t having desired properties: -- -- t = t' / t'max. (13) -- -- In fact, t <= 1 by definition, and t > 0 being equivalent to t' > 0 -- is equivalent to (8). -- -- Thus, the inequality (10), where t is given by formula (13) is valid -- for (5)-(7). -- -- Note that if u = 0, then y = 0, so t = 1, and the conditions (8) and -- (10) is transformed to the conditions (3) and (4). -- -- GENERATING MIXED COVER CUTS -- -- To generate a mixed cover cut in the form (10) we need to find such -- set C which satisfies to the inequality (8) and for which, in turn, -- the inequality (10) is violated in the current point. -- -- Substituting t from (13) to (10) gives: -- -- 1 -- sum x[j] <= |C| - ----- (sum a[j] + y - b), (14) -- j in C t'max j in C -- -- and finally we have the cut inequality in the standard form: -- -- sum x[j] + alfa * y <= beta, (15) -- j in C -- -- where: -- -- alfa = 1 / t'max, (16) -- -- beta = |C| - alfa * (sum a[j] - b). (17) -- j in C */ #if 1 #define MAXTRY 1000 #else #define MAXTRY 10000 #endif static int cover2(int n, double a[], double b, double u, double x[], double y, int cov[], double *_alfa, double *_beta) { /* try to generate mixed cover cut using two-element cover */ int i, j, try = 0, ret = 0; double eps, alfa, beta, temp, rmax = 0.001; eps = 0.001 * (1.0 + fabs(b)); for (i = 0+1; i <= n; i++) for (j = i+1; j <= n; j++) { /* C = {i, j} */ try++; if (try > MAXTRY) goto done; /* check if condition (8) is satisfied */ if (a[i] + a[j] + y > b + eps) { /* compute parameters for inequality (15) */ temp = a[i] + a[j] - b; alfa = 1.0 / (temp + u); beta = 2.0 - alfa * temp; /* compute violation of inequality (15) */ temp = x[i] + x[j] + alfa * y - beta; /* choose C providing maximum violation */ if (rmax < temp) { rmax = temp; cov[1] = i; cov[2] = j; *_alfa = alfa; *_beta = beta; ret = 1; } } } done: return ret; } static int cover3(int n, double a[], double b, double u, double x[], double y, int cov[], double *_alfa, double *_beta) { /* try to generate mixed cover cut using three-element cover */ int i, j, k, try = 0, ret = 0; double eps, alfa, beta, temp, rmax = 0.001; eps = 0.001 * (1.0 + fabs(b)); for (i = 0+1; i <= n; i++) for (j = i+1; j <= n; j++) for (k = j+1; k <= n; k++) { /* C = {i, j, k} */ try++; if (try > MAXTRY) goto done; /* check if condition (8) is satisfied */ if (a[i] + a[j] + a[k] + y > b + eps) { /* compute parameters for inequality (15) */ temp = a[i] + a[j] + a[k] - b; alfa = 1.0 / (temp + u); beta = 3.0 - alfa * temp; /* compute violation of inequality (15) */ temp = x[i] + x[j] + x[k] + alfa * y - beta; /* choose C providing maximum violation */ if (rmax < temp) { rmax = temp; cov[1] = i; cov[2] = j; cov[3] = k; *_alfa = alfa; *_beta = beta; ret = 1; } } } done: return ret; } static int cover4(int n, double a[], double b, double u, double x[], double y, int cov[], double *_alfa, double *_beta) { /* try to generate mixed cover cut using four-element cover */ int i, j, k, l, try = 0, ret = 0; double eps, alfa, beta, temp, rmax = 0.001; eps = 0.001 * (1.0 + fabs(b)); for (i = 0+1; i <= n; i++) for (j = i+1; j <= n; j++) for (k = j+1; k <= n; k++) for (l = k+1; l <= n; l++) { /* C = {i, j, k, l} */ try++; if (try > MAXTRY) goto done; /* check if condition (8) is satisfied */ if (a[i] + a[j] + a[k] + a[l] + y > b + eps) { /* compute parameters for inequality (15) */ temp = a[i] + a[j] + a[k] + a[l] - b; alfa = 1.0 / (temp + u); beta = 4.0 - alfa * temp; /* compute violation of inequality (15) */ temp = x[i] + x[j] + x[k] + x[l] + alfa * y - beta; /* choose C providing maximum violation */ if (rmax < temp) { rmax = temp; cov[1] = i; cov[2] = j; cov[3] = k; cov[4] = l; *_alfa = alfa; *_beta = beta; ret = 1; } } } done: return ret; } static int cover(int n, double a[], double b, double u, double x[], double y, int cov[], double *alfa, double *beta) { /* try to generate mixed cover cut; input (see (5)): n is the number of binary variables; a[1:n] are coefficients at binary variables; b is the right-hand side; u is upper bound of continuous variable; x[1:n] are values of binary variables at current point; y is value of continuous variable at current point; output (see (15), (16), (17)): cov[1:r] are indices of binary variables included in cover C, where r is the set cardinality returned on exit; alfa coefficient at continuous variable; beta is the right-hand side; */ int j; /* perform some sanity checks */ xassert(n >= 2); for (j = 1; j <= n; j++) xassert(a[j] > 0.0); #if 1 /* ??? */ xassert(b > -1e-5); #else xassert(b > 0.0); #endif xassert(u >= 0.0); for (j = 1; j <= n; j++) xassert(0.0 <= x[j] && x[j] <= 1.0); xassert(0.0 <= y && y <= u); /* try to generate mixed cover cut */ if (cover2(n, a, b, u, x, y, cov, alfa, beta)) return 2; if (cover3(n, a, b, u, x, y, cov, alfa, beta)) return 3; if (cover4(n, a, b, u, x, y, cov, alfa, beta)) return 4; return 0; } /*---------------------------------------------------------------------- -- lpx_cover_cut - generate mixed cover cut. -- -- SYNOPSIS -- -- #include "glplpx.h" -- int lpx_cover_cut(LPX *lp, int len, int ind[], double val[], -- double work[]); -- -- DESCRIPTION -- -- The routine lpx_cover_cut generates a mixed cover cut for a given -- row of the MIP problem. -- -- The given row of the MIP problem should be explicitly specified in -- the form: -- -- sum{j in J} a[j]*x[j] <= b. (1) -- -- On entry indices (ordinal numbers) of structural variables, which -- have non-zero constraint coefficients, should be placed in locations -- ind[1], ..., ind[len], and corresponding constraint coefficients -- should be placed in locations val[1], ..., val[len]. The right-hand -- side b should be stored in location val[0]. -- -- The working array work should have at least nb locations, where nb -- is the number of binary variables in (1). -- -- The routine generates a mixed cover cut in the same form as (1) and -- stores the cut coefficients and right-hand side in the same way as -- just described above. -- -- RETURNS -- -- If the cutting plane has been successfully generated, the routine -- returns 1 <= len' <= n, which is the number of non-zero coefficients -- in the inequality constraint. Otherwise, the routine returns zero. */ static int lpx_cover_cut(LPX *lp, int len, int ind[], double val[], double work[]) { int cov[1+4], j, k, nb, newlen, r; double f_min, f_max, alfa, beta, u, *x = work, y; /* substitute and remove fixed variables */ newlen = 0; for (k = 1; k <= len; k++) { j = ind[k]; if (lpx_get_col_type(lp, j) == LPX_FX) val[0] -= val[k] * lpx_get_col_lb(lp, j); else { newlen++; ind[newlen] = ind[k]; val[newlen] = val[k]; } } len = newlen; /* move binary variables to the beginning of the list so that elements 1, 2, ..., nb correspond to binary variables, and elements nb+1, nb+2, ..., len correspond to rest variables */ nb = 0; for (k = 1; k <= len; k++) { j = ind[k]; if (lpx_get_col_kind(lp, j) == LPX_IV && lpx_get_col_type(lp, j) == LPX_DB && lpx_get_col_lb(lp, j) == 0.0 && lpx_get_col_ub(lp, j) == 1.0) { /* binary variable */ int ind_k; double val_k; nb++; ind_k = ind[nb], val_k = val[nb]; ind[nb] = ind[k], val[nb] = val[k]; ind[k] = ind_k, val[k] = val_k; } } /* now the specified row has the form: sum a[j]*x[j] + sum a[j]*y[j] <= b, where x[j] are binary variables, y[j] are rest variables */ /* at least two binary variables are needed */ if (nb < 2) return 0; /* compute implied lower and upper bounds for sum a[j]*y[j] */ f_min = f_max = 0.0; for (k = nb+1; k <= len; k++) { j = ind[k]; /* both bounds must be finite */ if (lpx_get_col_type(lp, j) != LPX_DB) return 0; if (val[k] > 0.0) { f_min += val[k] * lpx_get_col_lb(lp, j); f_max += val[k] * lpx_get_col_ub(lp, j); } else { f_min += val[k] * lpx_get_col_ub(lp, j); f_max += val[k] * lpx_get_col_lb(lp, j); } } /* sum a[j]*x[j] + sum a[j]*y[j] <= b ===> sum a[j]*x[j] + (sum a[j]*y[j] - f_min) <= b - f_min ===> sum a[j]*x[j] + y <= b - f_min, where y = sum a[j]*y[j] - f_min; note that 0 <= y <= u, u = f_max - f_min */ /* determine upper bound of y */ u = f_max - f_min; /* determine value of y at the current point */ y = 0.0; for (k = nb+1; k <= len; k++) { j = ind[k]; y += val[k] * lpx_get_col_prim(lp, j); } y -= f_min; if (y < 0.0) y = 0.0; if (y > u) y = u; /* modify the right-hand side b */ val[0] -= f_min; /* now the transformed row has the form: sum a[j]*x[j] + y <= b, where 0 <= y <= u */ /* determine values of x[j] at the current point */ for (k = 1; k <= nb; k++) { j = ind[k]; x[k] = lpx_get_col_prim(lp, j); if (x[k] < 0.0) x[k] = 0.0; if (x[k] > 1.0) x[k] = 1.0; } /* if a[j] < 0, replace x[j] by its complement 1 - x'[j] */ for (k = 1; k <= nb; k++) { if (val[k] < 0.0) { ind[k] = - ind[k]; val[k] = - val[k]; val[0] += val[k]; x[k] = 1.0 - x[k]; } } /* try to generate a mixed cover cut for the transformed row */ r = cover(nb, val, val[0], u, x, y, cov, &alfa, &beta); if (r == 0) return 0; xassert(2 <= r && r <= 4); /* now the cut is in the form: sum{j in C} x[j] + alfa * y <= beta */ /* store the right-hand side beta */ ind[0] = 0, val[0] = beta; /* restore the original ordinal numbers of x[j] */ for (j = 1; j <= r; j++) cov[j] = ind[cov[j]]; /* store cut coefficients at binary variables complementing back the variables having negative row coefficients */ xassert(r <= nb); for (k = 1; k <= r; k++) { if (cov[k] > 0) { ind[k] = +cov[k]; val[k] = +1.0; } else { ind[k] = -cov[k]; val[k] = -1.0; val[0] -= 1.0; } } /* substitute y = sum a[j]*y[j] - f_min */ for (k = nb+1; k <= len; k++) { r++; ind[r] = ind[k]; val[r] = alfa * val[k]; } val[0] += alfa * f_min; xassert(r <= len); len = r; return len; } /*---------------------------------------------------------------------- -- lpx_eval_row - compute explictily specified row. -- -- SYNOPSIS -- -- #include "glplpx.h" -- double lpx_eval_row(LPX *lp, int len, int ind[], double val[]); -- -- DESCRIPTION -- -- The routine lpx_eval_row computes the primal value of an explicitly -- specified row using current values of structural variables. -- -- The explicitly specified row may be thought as a linear form: -- -- y = a[1]*x[m+1] + a[2]*x[m+2] + ... + a[n]*x[m+n], -- -- where y is an auxiliary variable for this row, a[j] are coefficients -- of the linear form, x[m+j] are structural variables. -- -- On entry column indices and numerical values of non-zero elements of -- the row should be stored in locations ind[1], ..., ind[len] and -- val[1], ..., val[len], where len is the number of non-zero elements. -- The array ind and val are not changed on exit. -- -- RETURNS -- -- The routine returns a computed value of y, the auxiliary variable of -- the specified row. */ static double lpx_eval_row(LPX *lp, int len, int ind[], double val[]) { int n = lpx_get_num_cols(lp); int j, k; double sum = 0.0; if (len < 0) xerror("lpx_eval_row: len = %d; invalid row length\n", len); for (k = 1; k <= len; k++) { j = ind[k]; if (!(1 <= j && j <= n)) xerror("lpx_eval_row: j = %d; column number out of range\n", j); sum += val[k] * lpx_get_col_prim(lp, j); } return sum; } /*********************************************************************** * NAME * * ios_cov_gen - generate mixed cover cuts * * SYNOPSIS * * #include "glpios.h" * void ios_cov_gen(glp_tree *tree); * * DESCRIPTION * * The routine ios_cov_gen generates mixed cover cuts for the current * point and adds them to the cut pool. */ void ios_cov_gen(glp_tree *tree) { glp_prob *prob = tree->mip; int m = lpx_get_num_rows(prob); int n = lpx_get_num_cols(prob); int i, k, type, kase, len, *ind; double r, *val, *work; xassert(lpx_get_status(prob) == LPX_OPT); /* allocate working arrays */ ind = xcalloc(1+n, sizeof(int)); val = xcalloc(1+n, sizeof(double)); work = xcalloc(1+n, sizeof(double)); /* look through all rows */ for (i = 1; i <= m; i++) for (kase = 1; kase <= 2; kase++) { type = lpx_get_row_type(prob, i); if (kase == 1) { /* consider rows of '<=' type */ if (!(type == LPX_UP || type == LPX_DB)) continue; len = lpx_get_mat_row(prob, i, ind, val); val[0] = lpx_get_row_ub(prob, i); } else { /* consider rows of '>=' type */ if (!(type == LPX_LO || type == LPX_DB)) continue; len = lpx_get_mat_row(prob, i, ind, val); for (k = 1; k <= len; k++) val[k] = - val[k]; val[0] = - lpx_get_row_lb(prob, i); } /* generate mixed cover cut: sum{j in J} a[j] * x[j] <= b */ len = lpx_cover_cut(prob, len, ind, val, work); if (len == 0) continue; /* at the current point the cut inequality is violated, i.e. sum{j in J} a[j] * x[j] - b > 0 */ r = lpx_eval_row(prob, len, ind, val) - val[0]; if (r < 1e-3) continue; /* add the cut to the cut pool */ glp_ios_add_row(tree, NULL, GLP_RF_COV, 0, len, ind, val, GLP_UP, val[0]); } /* free working arrays */ xfree(ind); xfree(val); xfree(work); return; } /* eof */ sources_5316/external/glpk/amd.h0000644000176700017670000000327611401660400015414 0ustar paulpaul/* amd.h */ /* Written by Andrew Makhorin . */ #ifndef GLPAMD_H #define GLPAMD_H #define AMD_DATE "May 31, 2007" #define AMD_VERSION_CODE(main, sub) ((main) * 1000 + (sub)) #define AMD_MAIN_VERSION 2 #define AMD_SUB_VERSION 2 #define AMD_SUBSUB_VERSION 0 #define AMD_VERSION AMD_VERSION_CODE(AMD_MAIN_VERSION, AMD_SUB_VERSION) #define AMD_CONTROL 5 #define AMD_INFO 20 #define AMD_DENSE 0 #define AMD_AGGRESSIVE 1 #define AMD_DEFAULT_DENSE 10.0 #define AMD_DEFAULT_AGGRESSIVE 1 #define AMD_STATUS 0 #define AMD_N 1 #define AMD_NZ 2 #define AMD_SYMMETRY 3 #define AMD_NZDIAG 4 #define AMD_NZ_A_PLUS_AT 5 #define AMD_NDENSE 6 #define AMD_MEMORY 7 #define AMD_NCMPA 8 #define AMD_LNZ 9 #define AMD_NDIV 10 #define AMD_NMULTSUBS_LDL 11 #define AMD_NMULTSUBS_LU 12 #define AMD_DMAX 13 #define AMD_OK 0 #define AMD_OUT_OF_MEMORY (-1) #define AMD_INVALID (-2) #define AMD_OK_BUT_JUMBLED 1 #define amd_order _glp_amd_order int amd_order(int n, const int Ap[], const int Ai[], int P[], double Control[], double Info[]); #define amd_2 _glp_amd_2 void amd_2(int n, int Pe[], int Iw[], int Len[], int iwlen, int pfree, int Nv[], int Next[], int Last[], int Head[], int Elen[], int Degree[], int W[], double Control[], double Info[]); #define amd_valid _glp_amd_valid int amd_valid(int n_row, int n_col, const int Ap[], const int Ai[]); #define amd_defaults _glp_amd_defaults void amd_defaults(double Control[]); #define amd_control _glp_amd_control void amd_control(double Control[]); #define amd_info _glp_amd_info void amd_info(double Info[]); #endif /* eof */ sources_5316/external/glpk/glpios06.c0000644000176700017670000013750011401660400016307 0ustar paulpaul/* glpios06.c (MIR cut generator) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" #define _MIR_DEBUG 0 #define MAXAGGR 5 /* maximal number of rows which can be aggregated */ struct MIR { /* MIR cut generator working area */ /*--------------------------------------------------------------*/ /* global information valid for the root subproblem */ int m; /* number of rows (in the root subproblem) */ int n; /* number of columns */ char *skip; /* char skip[1+m]; */ /* skip[i], 1 <= i <= m, is a flag that means that row i should not be used because (1) it is not suitable, or (2) because it has been used in the aggregated constraint */ char *isint; /* char isint[1+m+n]; */ /* isint[k], 1 <= k <= m+n, is a flag that means that variable x[k] is integer (otherwise, continuous) */ double *lb; /* double lb[1+m+n]; */ /* lb[k], 1 <= k <= m+n, is lower bound of x[k]; -DBL_MAX means that x[k] has no lower bound */ int *vlb; /* int vlb[1+m+n]; */ /* vlb[k] = k', 1 <= k <= m+n, is the number of integer variable, which defines variable lower bound x[k] >= lb[k] * x[k']; zero means that x[k] has simple lower bound */ double *ub; /* double ub[1+m+n]; */ /* ub[k], 1 <= k <= m+n, is upper bound of x[k]; +DBL_MAX means that x[k] has no upper bound */ int *vub; /* int vub[1+m+n]; */ /* vub[k] = k', 1 <= k <= m+n, is the number of integer variable, which defines variable upper bound x[k] <= ub[k] * x[k']; zero means that x[k] has simple upper bound */ /*--------------------------------------------------------------*/ /* current (fractional) point to be separated */ double *x; /* double x[1+m+n]; */ /* x[k] is current value of auxiliary (1 <= k <= m) or structural (m+1 <= k <= m+n) variable */ /*--------------------------------------------------------------*/ /* aggregated constraint sum a[k] * x[k] = b, which is a linear combination of original constraints transformed to equalities by introducing auxiliary variables */ int agg_cnt; /* number of rows (original constraints) used to build aggregated constraint, 1 <= agg_cnt <= MAXAGGR */ int *agg_row; /* int agg_row[1+MAXAGGR]; */ /* agg_row[k], 1 <= k <= agg_cnt, is the row number used to build aggregated constraint */ IOSVEC *agg_vec; /* IOSVEC agg_vec[1:m+n]; */ /* sparse vector of aggregated constraint coefficients, a[k] */ double agg_rhs; /* right-hand side of the aggregated constraint, b */ /*--------------------------------------------------------------*/ /* bound substitution flags for modified constraint */ char *subst; /* char subst[1+m+n]; */ /* subst[k], 1 <= k <= m+n, is a bound substitution flag used for variable x[k]: '?' - x[k] is missing in modified constraint 'L' - x[k] = (lower bound) + x'[k] 'U' - x[k] = (upper bound) - x'[k] */ /*--------------------------------------------------------------*/ /* modified constraint sum a'[k] * x'[k] = b', where x'[k] >= 0, derived from aggregated constraint by substituting bounds; note that due to substitution of variable bounds there may be additional terms in the modified constraint */ IOSVEC *mod_vec; /* IOSVEC mod_vec[1:m+n]; */ /* sparse vector of modified constraint coefficients, a'[k] */ double mod_rhs; /* right-hand side of the modified constraint, b' */ /*--------------------------------------------------------------*/ /* cutting plane sum alpha[k] * x[k] <= beta */ IOSVEC *cut_vec; /* IOSVEC cut_vec[1:m+n]; */ /* sparse vector of cutting plane coefficients, alpha[k] */ double cut_rhs; /* right-hand size of the cutting plane, beta */ }; /*********************************************************************** * NAME * * ios_mir_init - initialize MIR cut generator * * SYNOPSIS * * #include "glpios.h" * void *ios_mir_init(glp_tree *tree); * * DESCRIPTION * * The routine ios_mir_init initializes the MIR cut generator assuming * that the current subproblem is the root subproblem. * * RETURNS * * The routine ios_mir_init returns a pointer to the MIR cut generator * working area. */ static void set_row_attrib(glp_tree *tree, struct MIR *mir) { /* set global row attributes */ glp_prob *mip = tree->mip; int m = mir->m; int k; for (k = 1; k <= m; k++) { GLPROW *row = mip->row[k]; mir->skip[k] = 0; mir->isint[k] = 0; switch (row->type) { case GLP_FR: mir->lb[k] = -DBL_MAX, mir->ub[k] = +DBL_MAX; break; case GLP_LO: mir->lb[k] = row->lb, mir->ub[k] = +DBL_MAX; break; case GLP_UP: mir->lb[k] = -DBL_MAX, mir->ub[k] = row->ub; break; case GLP_DB: mir->lb[k] = row->lb, mir->ub[k] = row->ub; break; case GLP_FX: mir->lb[k] = mir->ub[k] = row->lb; break; default: xassert(row != row); } mir->vlb[k] = mir->vub[k] = 0; } return; } static void set_col_attrib(glp_tree *tree, struct MIR *mir) { /* set global column attributes */ glp_prob *mip = tree->mip; int m = mir->m; int n = mir->n; int k; for (k = m+1; k <= m+n; k++) { GLPCOL *col = mip->col[k-m]; switch (col->kind) { case GLP_CV: mir->isint[k] = 0; break; case GLP_IV: mir->isint[k] = 1; break; default: xassert(col != col); } switch (col->type) { case GLP_FR: mir->lb[k] = -DBL_MAX, mir->ub[k] = +DBL_MAX; break; case GLP_LO: mir->lb[k] = col->lb, mir->ub[k] = +DBL_MAX; break; case GLP_UP: mir->lb[k] = -DBL_MAX, mir->ub[k] = col->ub; break; case GLP_DB: mir->lb[k] = col->lb, mir->ub[k] = col->ub; break; case GLP_FX: mir->lb[k] = mir->ub[k] = col->lb; break; default: xassert(col != col); } mir->vlb[k] = mir->vub[k] = 0; } return; } static void set_var_bounds(glp_tree *tree, struct MIR *mir) { /* set variable bounds */ glp_prob *mip = tree->mip; int m = mir->m; GLPAIJ *aij; int i, k1, k2; double a1, a2; for (i = 1; i <= m; i++) { /* we need the row to be '>= 0' or '<= 0' */ if (!(mir->lb[i] == 0.0 && mir->ub[i] == +DBL_MAX || mir->lb[i] == -DBL_MAX && mir->ub[i] == 0.0)) continue; /* take first term */ aij = mip->row[i]->ptr; if (aij == NULL) continue; k1 = m + aij->col->j, a1 = aij->val; /* take second term */ aij = aij->r_next; if (aij == NULL) continue; k2 = m + aij->col->j, a2 = aij->val; /* there must be only two terms */ if (aij->r_next != NULL) continue; /* interchange terms, if needed */ if (!mir->isint[k1] && mir->isint[k2]) ; else if (mir->isint[k1] && !mir->isint[k2]) { k2 = k1, a2 = a1; k1 = m + aij->col->j, a1 = aij->val; } else { /* both terms are either continuous or integer */ continue; } /* x[k2] should be double-bounded */ if (mir->lb[k2] == -DBL_MAX || mir->ub[k2] == +DBL_MAX || mir->lb[k2] == mir->ub[k2]) continue; /* change signs, if necessary */ if (mir->ub[i] == 0.0) a1 = - a1, a2 = - a2; /* now the row has the form a1 * x1 + a2 * x2 >= 0, where x1 is continuous, x2 is integer */ if (a1 > 0.0) { /* x1 >= - (a2 / a1) * x2 */ if (mir->vlb[k1] == 0) { /* set variable lower bound for x1 */ mir->lb[k1] = - a2 / a1; mir->vlb[k1] = k2; /* the row should not be used */ mir->skip[i] = 1; } } else /* a1 < 0.0 */ { /* x1 <= - (a2 / a1) * x2 */ if (mir->vub[k1] == 0) { /* set variable upper bound for x1 */ mir->ub[k1] = - a2 / a1; mir->vub[k1] = k2; /* the row should not be used */ mir->skip[i] = 1; } } } return; } static void mark_useless_rows(glp_tree *tree, struct MIR *mir) { /* mark rows which should not be used */ glp_prob *mip = tree->mip; int m = mir->m; GLPAIJ *aij; int i, k, nv; for (i = 1; i <= m; i++) { /* free rows should not be used */ if (mir->lb[i] == -DBL_MAX && mir->ub[i] == +DBL_MAX) { mir->skip[i] = 1; continue; } nv = 0; for (aij = mip->row[i]->ptr; aij != NULL; aij = aij->r_next) { k = m + aij->col->j; /* rows with free variables should not be used */ if (mir->lb[k] == -DBL_MAX && mir->ub[k] == +DBL_MAX) { mir->skip[i] = 1; break; } /* rows with integer variables having infinite (lower or upper) bound should not be used */ if (mir->isint[k] && mir->lb[k] == -DBL_MAX || mir->isint[k] && mir->ub[k] == +DBL_MAX) { mir->skip[i] = 1; break; } /* count non-fixed variables */ if (!(mir->vlb[k] == 0 && mir->vub[k] == 0 && mir->lb[k] == mir->ub[k])) nv++; } /* rows with all variables fixed should not be used */ if (nv == 0) { mir->skip[i] = 1; continue; } } return; } void *ios_mir_init(glp_tree *tree) { /* initialize MIR cut generator */ glp_prob *mip = tree->mip; int m = mip->m; int n = mip->n; struct MIR *mir; #if _MIR_DEBUG xprintf("ios_mir_init: warning: debug mode enabled\n"); #endif /* allocate working area */ mir = xmalloc(sizeof(struct MIR)); mir->m = m; mir->n = n; mir->skip = xcalloc(1+m, sizeof(char)); mir->isint = xcalloc(1+m+n, sizeof(char)); mir->lb = xcalloc(1+m+n, sizeof(double)); mir->vlb = xcalloc(1+m+n, sizeof(int)); mir->ub = xcalloc(1+m+n, sizeof(double)); mir->vub = xcalloc(1+m+n, sizeof(int)); mir->x = xcalloc(1+m+n, sizeof(double)); mir->agg_row = xcalloc(1+MAXAGGR, sizeof(int)); mir->agg_vec = ios_create_vec(m+n); mir->subst = xcalloc(1+m+n, sizeof(char)); mir->mod_vec = ios_create_vec(m+n); mir->cut_vec = ios_create_vec(m+n); /* set global row attributes */ set_row_attrib(tree, mir); /* set global column attributes */ set_col_attrib(tree, mir); /* set variable bounds */ set_var_bounds(tree, mir); /* mark rows which should not be used */ mark_useless_rows(tree, mir); return mir; } /*********************************************************************** * NAME * * ios_mir_gen - generate MIR cuts * * SYNOPSIS * * #include "glpios.h" * void ios_mir_gen(glp_tree *tree, void *gen, IOSPOOL *pool); * * DESCRIPTION * * The routine ios_mir_gen generates MIR cuts for the current point and * adds them to the cut pool. */ static void get_current_point(glp_tree *tree, struct MIR *mir) { /* obtain current point */ glp_prob *mip = tree->mip; int m = mir->m; int n = mir->n; int k; for (k = 1; k <= m; k++) mir->x[k] = mip->row[k]->prim; for (k = m+1; k <= m+n; k++) mir->x[k] = mip->col[k-m]->prim; return; } #if _MIR_DEBUG static void check_current_point(struct MIR *mir) { /* check current point */ int m = mir->m; int n = mir->n; int k, kk; double lb, ub, eps; for (k = 1; k <= m+n; k++) { /* determine lower bound */ lb = mir->lb[k]; kk = mir->vlb[k]; if (kk != 0) { xassert(lb != -DBL_MAX); xassert(!mir->isint[k]); xassert(mir->isint[kk]); lb *= mir->x[kk]; } /* check lower bound */ if (lb != -DBL_MAX) { eps = 1e-6 * (1.0 + fabs(lb)); xassert(mir->x[k] >= lb - eps); } /* determine upper bound */ ub = mir->ub[k]; kk = mir->vub[k]; if (kk != 0) { xassert(ub != +DBL_MAX); xassert(!mir->isint[k]); xassert(mir->isint[kk]); ub *= mir->x[kk]; } /* check upper bound */ if (ub != +DBL_MAX) { eps = 1e-6 * (1.0 + fabs(ub)); xassert(mir->x[k] <= ub + eps); } } return; } #endif static void initial_agg_row(glp_tree *tree, struct MIR *mir, int i) { /* use original i-th row as initial aggregated constraint */ glp_prob *mip = tree->mip; int m = mir->m; GLPAIJ *aij; xassert(1 <= i && i <= m); xassert(!mir->skip[i]); /* mark i-th row in order not to use it in the same aggregated constraint */ mir->skip[i] = 2; mir->agg_cnt = 1; mir->agg_row[1] = i; /* use x[i] - sum a[i,j] * x[m+j] = 0, where x[i] is auxiliary variable of row i, x[m+j] are structural variables */ ios_clear_vec(mir->agg_vec); ios_set_vj(mir->agg_vec, i, 1.0); for (aij = mip->row[i]->ptr; aij != NULL; aij = aij->r_next) ios_set_vj(mir->agg_vec, m + aij->col->j, - aij->val); mir->agg_rhs = 0.0; #if _MIR_DEBUG ios_check_vec(mir->agg_vec); #endif return; } #if _MIR_DEBUG static void check_agg_row(struct MIR *mir) { /* check aggregated constraint */ int m = mir->m; int n = mir->n; int j, k; double r, big; /* compute the residual r = sum a[k] * x[k] - b and determine big = max(1, |a[k]|, |b|) */ r = 0.0, big = 1.0; for (j = 1; j <= mir->agg_vec->nnz; j++) { k = mir->agg_vec->ind[j]; xassert(1 <= k && k <= m+n); r += mir->agg_vec->val[j] * mir->x[k]; if (big < fabs(mir->agg_vec->val[j])) big = fabs(mir->agg_vec->val[j]); } r -= mir->agg_rhs; if (big < fabs(mir->agg_rhs)) big = fabs(mir->agg_rhs); /* the residual must be close to zero */ xassert(fabs(r) <= 1e-6 * big); return; } #endif static void subst_fixed_vars(struct MIR *mir) { /* substitute fixed variables into aggregated constraint */ int m = mir->m; int n = mir->n; int j, k; for (j = 1; j <= mir->agg_vec->nnz; j++) { k = mir->agg_vec->ind[j]; xassert(1 <= k && k <= m+n); if (mir->vlb[k] == 0 && mir->vub[k] == 0 && mir->lb[k] == mir->ub[k]) { /* x[k] is fixed */ mir->agg_rhs -= mir->agg_vec->val[j] * mir->lb[k]; mir->agg_vec->val[j] = 0.0; } } /* remove terms corresponding to fixed variables */ ios_clean_vec(mir->agg_vec, DBL_EPSILON); #if _MIR_DEBUG ios_check_vec(mir->agg_vec); #endif return; } static void bound_subst_heur(struct MIR *mir) { /* bound substitution heuristic */ int m = mir->m; int n = mir->n; int j, k, kk; double d1, d2; for (j = 1; j <= mir->agg_vec->nnz; j++) { k = mir->agg_vec->ind[j]; xassert(1 <= k && k <= m+n); if (mir->isint[k]) continue; /* skip integer variable */ /* compute distance from x[k] to its lower bound */ kk = mir->vlb[k]; if (kk == 0) { if (mir->lb[k] == -DBL_MAX) d1 = DBL_MAX; else d1 = mir->x[k] - mir->lb[k]; } else { xassert(1 <= kk && kk <= m+n); xassert(mir->isint[kk]); xassert(mir->lb[k] != -DBL_MAX); d1 = mir->x[k] - mir->lb[k] * mir->x[kk]; } /* compute distance from x[k] to its upper bound */ kk = mir->vub[k]; if (kk == 0) { if (mir->vub[k] == +DBL_MAX) d2 = DBL_MAX; else d2 = mir->ub[k] - mir->x[k]; } else { xassert(1 <= kk && kk <= m+n); xassert(mir->isint[kk]); xassert(mir->ub[k] != +DBL_MAX); d2 = mir->ub[k] * mir->x[kk] - mir->x[k]; } /* x[k] cannot be free */ xassert(d1 != DBL_MAX || d2 != DBL_MAX); /* choose the bound which is closer to x[k] */ xassert(mir->subst[k] == '?'); if (d1 <= d2) mir->subst[k] = 'L'; else mir->subst[k] = 'U'; } return; } static void build_mod_row(struct MIR *mir) { /* substitute bounds and build modified constraint */ int m = mir->m; int n = mir->n; int j, jj, k, kk; /* initially modified constraint is aggregated constraint */ ios_copy_vec(mir->mod_vec, mir->agg_vec); mir->mod_rhs = mir->agg_rhs; #if _MIR_DEBUG ios_check_vec(mir->mod_vec); #endif /* substitute bounds for continuous variables; note that due to substitution of variable bounds additional terms may appear in modified constraint */ for (j = mir->mod_vec->nnz; j >= 1; j--) { k = mir->mod_vec->ind[j]; xassert(1 <= k && k <= m+n); if (mir->isint[k]) continue; /* skip integer variable */ if (mir->subst[k] == 'L') { /* x[k] = (lower bound) + x'[k] */ xassert(mir->lb[k] != -DBL_MAX); kk = mir->vlb[k]; if (kk == 0) { /* x[k] = lb[k] + x'[k] */ mir->mod_rhs -= mir->mod_vec->val[j] * mir->lb[k]; } else { /* x[k] = lb[k] * x[kk] + x'[k] */ xassert(mir->isint[kk]); jj = mir->mod_vec->pos[kk]; if (jj == 0) { ios_set_vj(mir->mod_vec, kk, 1.0); jj = mir->mod_vec->pos[kk]; mir->mod_vec->val[jj] = 0.0; } mir->mod_vec->val[jj] += mir->mod_vec->val[j] * mir->lb[k]; } } else if (mir->subst[k] == 'U') { /* x[k] = (upper bound) - x'[k] */ xassert(mir->ub[k] != +DBL_MAX); kk = mir->vub[k]; if (kk == 0) { /* x[k] = ub[k] - x'[k] */ mir->mod_rhs -= mir->mod_vec->val[j] * mir->ub[k]; } else { /* x[k] = ub[k] * x[kk] - x'[k] */ xassert(mir->isint[kk]); jj = mir->mod_vec->pos[kk]; if (jj == 0) { ios_set_vj(mir->mod_vec, kk, 1.0); jj = mir->mod_vec->pos[kk]; mir->mod_vec->val[jj] = 0.0; } mir->mod_vec->val[jj] += mir->mod_vec->val[j] * mir->ub[k]; } mir->mod_vec->val[j] = - mir->mod_vec->val[j]; } else xassert(k != k); } #if _MIR_DEBUG ios_check_vec(mir->mod_vec); #endif /* substitute bounds for integer variables */ for (j = 1; j <= mir->mod_vec->nnz; j++) { k = mir->mod_vec->ind[j]; xassert(1 <= k && k <= m+n); if (!mir->isint[k]) continue; /* skip continuous variable */ xassert(mir->subst[k] == '?'); xassert(mir->vlb[k] == 0 && mir->vub[k] == 0); xassert(mir->lb[k] != -DBL_MAX && mir->ub[k] != +DBL_MAX); if (fabs(mir->lb[k]) <= fabs(mir->ub[k])) { /* x[k] = lb[k] + x'[k] */ mir->subst[k] = 'L'; mir->mod_rhs -= mir->mod_vec->val[j] * mir->lb[k]; } else { /* x[k] = ub[k] - x'[k] */ mir->subst[k] = 'U'; mir->mod_rhs -= mir->mod_vec->val[j] * mir->ub[k]; mir->mod_vec->val[j] = - mir->mod_vec->val[j]; } } #if _MIR_DEBUG ios_check_vec(mir->mod_vec); #endif return; } #if _MIR_DEBUG static void check_mod_row(struct MIR *mir) { /* check modified constraint */ int m = mir->m; int n = mir->n; int j, k, kk; double r, big, x; /* compute the residual r = sum a'[k] * x'[k] - b' and determine big = max(1, |a[k]|, |b|) */ r = 0.0, big = 1.0; for (j = 1; j <= mir->mod_vec->nnz; j++) { k = mir->mod_vec->ind[j]; xassert(1 <= k && k <= m+n); if (mir->subst[k] == 'L') { /* x'[k] = x[k] - (lower bound) */ xassert(mir->lb[k] != -DBL_MAX); kk = mir->vlb[k]; if (kk == 0) x = mir->x[k] - mir->lb[k]; else x = mir->x[k] - mir->lb[k] * mir->x[kk]; } else if (mir->subst[k] == 'U') { /* x'[k] = (upper bound) - x[k] */ xassert(mir->ub[k] != +DBL_MAX); kk = mir->vub[k]; if (kk == 0) x = mir->ub[k] - mir->x[k]; else x = mir->ub[k] * mir->x[kk] - mir->x[k]; } else xassert(k != k); r += mir->mod_vec->val[j] * x; if (big < fabs(mir->mod_vec->val[j])) big = fabs(mir->mod_vec->val[j]); } r -= mir->mod_rhs; if (big < fabs(mir->mod_rhs)) big = fabs(mir->mod_rhs); /* the residual must be close to zero */ xassert(fabs(r) <= 1e-6 * big); return; } #endif /*********************************************************************** * mir_ineq - construct MIR inequality * * Given the single constraint mixed integer set * * |N| * X = {(x,s) in Z x R : sum a[j] * x[j] <= b + s}, * + + j in N * * this routine constructs the mixed integer rounding (MIR) inequality * * sum alpha[j] * x[j] <= beta + gamma * s, * j in N * * which is valid for X. * * If the MIR inequality has been successfully constructed, the routine * returns zero. Otherwise, if b is close to nearest integer, there may * be numeric difficulties due to big coefficients; so in this case the * routine returns non-zero. */ static int mir_ineq(const int n, const double a[], const double b, double alpha[], double *beta, double *gamma) { int j; double f, t; if (fabs(b - floor(b + .5)) < 0.01) return 1; f = b - floor(b); for (j = 1; j <= n; j++) { t = (a[j] - floor(a[j])) - f; if (t <= 0.0) alpha[j] = floor(a[j]); else alpha[j] = floor(a[j]) + t / (1.0 - f); } *beta = floor(b); *gamma = 1.0 / (1.0 - f); return 0; } /*********************************************************************** * cmir_ineq - construct c-MIR inequality * * Given the mixed knapsack set * * MK |N| * X = {(x,s) in Z x R : sum a[j] * x[j] <= b + s, * + + j in N * * x[j] <= u[j]}, * * a subset C of variables to be complemented, and a divisor delta > 0, * this routine constructs the complemented MIR (c-MIR) inequality * * sum alpha[j] * x[j] <= beta + gamma * s, * j in N * MK * which is valid for X . * * If the c-MIR inequality has been successfully constructed, the * routine returns zero. Otherwise, if there is a risk of numerical * difficulties due to big coefficients (see comments to the routine * mir_ineq), the routine cmir_ineq returns non-zero. */ static int cmir_ineq(const int n, const double a[], const double b, const double u[], const char cset[], const double delta, double alpha[], double *beta, double *gamma) { int j; double *aa, bb; aa = alpha, bb = b; for (j = 1; j <= n; j++) { aa[j] = a[j] / delta; if (cset[j]) aa[j] = - aa[j], bb -= a[j] * u[j]; } bb /= delta; if (mir_ineq(n, aa, bb, alpha, beta, gamma)) return 1; for (j = 1; j <= n; j++) { if (cset[j]) alpha[j] = - alpha[j], *beta += alpha[j] * u[j]; } *gamma /= delta; return 0; } /*********************************************************************** * cmir_sep - c-MIR separation heuristic * * Given the mixed knapsack set * * MK |N| * X = {(x,s) in Z x R : sum a[j] * x[j] <= b + s, * + + j in N * * x[j] <= u[j]} * * * * * and a fractional point (x , s ), this routine tries to construct * c-MIR inequality * * sum alpha[j] * x[j] <= beta + gamma * s, * j in N * MK * which is valid for X and has (desirably maximal) violation at the * fractional point given. This is attained by choosing an appropriate * set C of variables to be complemented and a divisor delta > 0, which * together define corresponding c-MIR inequality. * * If a violated c-MIR inequality has been successfully constructed, * the routine returns its violation: * * * * * sum alpha[j] * x [j] - beta - gamma * s , * j in N * * which is positive. In case of failure the routine returns zero. */ struct vset { int j; double v; }; static int cmir_cmp(const void *p1, const void *p2) { const struct vset *v1 = p1, *v2 = p2; if (v1->v < v2->v) return -1; if (v1->v > v2->v) return +1; return 0; } static double cmir_sep(const int n, const double a[], const double b, const double u[], const double x[], const double s, double alpha[], double *beta, double *gamma) { int fail, j, k, nv, v; double delta, eps, d_try[1+3], r, r_best; char *cset; struct vset *vset; /* allocate working arrays */ cset = xcalloc(1+n, sizeof(char)); vset = xcalloc(1+n, sizeof(struct vset)); /* choose initial C */ for (j = 1; j <= n; j++) cset[j] = (char)(x[j] >= 0.5 * u[j]); /* choose initial delta */ r_best = delta = 0.0; for (j = 1; j <= n; j++) { xassert(a[j] != 0.0); /* if x[j] is close to its bounds, skip it */ eps = 1e-9 * (1.0 + fabs(u[j])); if (x[j] < eps || x[j] > u[j] - eps) continue; /* try delta = |a[j]| to construct c-MIR inequality */ fail = cmir_ineq(n, a, b, u, cset, fabs(a[j]), alpha, beta, gamma); if (fail) continue; /* compute violation */ r = - (*beta) - (*gamma) * s; for (k = 1; k <= n; k++) r += alpha[k] * x[k]; if (r_best < r) r_best = r, delta = fabs(a[j]); } if (r_best < 0.001) r_best = 0.0; if (r_best == 0.0) goto done; xassert(delta > 0.0); /* try to increase violation by dividing delta by 2, 4, and 8, respectively */ d_try[1] = delta / 2.0; d_try[2] = delta / 4.0; d_try[3] = delta / 8.0; for (j = 1; j <= 3; j++) { /* construct c-MIR inequality */ fail = cmir_ineq(n, a, b, u, cset, d_try[j], alpha, beta, gamma); if (fail) continue; /* compute violation */ r = - (*beta) - (*gamma) * s; for (k = 1; k <= n; k++) r += alpha[k] * x[k]; if (r_best < r) r_best = r, delta = d_try[j]; } /* build subset of variables lying strictly between their bounds and order it by nondecreasing values of |x[j] - u[j]/2| */ nv = 0; for (j = 1; j <= n; j++) { /* if x[j] is close to its bounds, skip it */ eps = 1e-9 * (1.0 + fabs(u[j])); if (x[j] < eps || x[j] > u[j] - eps) continue; /* add x[j] to the subset */ nv++; vset[nv].j = j; vset[nv].v = fabs(x[j] - 0.5 * u[j]); } qsort(&vset[1], nv, sizeof(struct vset), cmir_cmp); /* try to increase violation by successively complementing each variable in the subset */ for (v = 1; v <= nv; v++) { j = vset[v].j; /* replace x[j] by its complement or vice versa */ cset[j] = (char)!cset[j]; /* construct c-MIR inequality */ fail = cmir_ineq(n, a, b, u, cset, delta, alpha, beta, gamma); /* restore the variable */ cset[j] = (char)!cset[j]; /* do not replace the variable in case of failure */ if (fail) continue; /* compute violation */ r = - (*beta) - (*gamma) * s; for (k = 1; k <= n; k++) r += alpha[k] * x[k]; if (r_best < r) r_best = r, cset[j] = (char)!cset[j]; } /* construct the best c-MIR inequality chosen */ fail = cmir_ineq(n, a, b, u, cset, delta, alpha, beta, gamma); xassert(!fail); done: /* free working arrays */ xfree(cset); xfree(vset); /* return to the calling routine */ return r_best; } static double generate(struct MIR *mir) { /* try to generate violated c-MIR cut for modified constraint */ int m = mir->m; int n = mir->n; int j, k, kk, nint; double s, *u, *x, *alpha, r_best = 0.0, b, beta, gamma; ios_copy_vec(mir->cut_vec, mir->mod_vec); mir->cut_rhs = mir->mod_rhs; /* remove small terms, which can appear due to substitution of variable bounds */ ios_clean_vec(mir->cut_vec, DBL_EPSILON); #if _MIR_DEBUG ios_check_vec(mir->cut_vec); #endif /* remove positive continuous terms to obtain MK relaxation */ for (j = 1; j <= mir->cut_vec->nnz; j++) { k = mir->cut_vec->ind[j]; xassert(1 <= k && k <= m+n); if (!mir->isint[k] && mir->cut_vec->val[j] > 0.0) mir->cut_vec->val[j] = 0.0; } ios_clean_vec(mir->cut_vec, 0.0); #if _MIR_DEBUG ios_check_vec(mir->cut_vec); #endif /* move integer terms to the beginning of the sparse vector and determine the number of integer variables */ nint = 0; for (j = 1; j <= mir->cut_vec->nnz; j++) { k = mir->cut_vec->ind[j]; xassert(1 <= k && k <= m+n); if (mir->isint[k]) { double temp; nint++; /* interchange elements [nint] and [j] */ kk = mir->cut_vec->ind[nint]; mir->cut_vec->pos[k] = nint; mir->cut_vec->pos[kk] = j; mir->cut_vec->ind[nint] = k; mir->cut_vec->ind[j] = kk; temp = mir->cut_vec->val[nint]; mir->cut_vec->val[nint] = mir->cut_vec->val[j]; mir->cut_vec->val[j] = temp; } } #if _MIR_DEBUG ios_check_vec(mir->cut_vec); #endif /* if there is no integer variable, nothing to generate */ if (nint == 0) goto done; /* allocate working arrays */ u = xcalloc(1+nint, sizeof(double)); x = xcalloc(1+nint, sizeof(double)); alpha = xcalloc(1+nint, sizeof(double)); /* determine u and x */ for (j = 1; j <= nint; j++) { k = mir->cut_vec->ind[j]; xassert(m+1 <= k && k <= m+n); xassert(mir->isint[k]); u[j] = mir->ub[k] - mir->lb[k]; xassert(u[j] >= 1.0); if (mir->subst[k] == 'L') x[j] = mir->x[k] - mir->lb[k]; else if (mir->subst[k] == 'U') x[j] = mir->ub[k] - mir->x[k]; else xassert(k != k); xassert(x[j] >= -0.001); if (x[j] < 0.0) x[j] = 0.0; } /* compute s = - sum of continuous terms */ s = 0.0; for (j = nint+1; j <= mir->cut_vec->nnz; j++) { double x; k = mir->cut_vec->ind[j]; xassert(1 <= k && k <= m+n); /* must be continuous */ xassert(!mir->isint[k]); if (mir->subst[k] == 'L') { xassert(mir->lb[k] != -DBL_MAX); kk = mir->vlb[k]; if (kk == 0) x = mir->x[k] - mir->lb[k]; else x = mir->x[k] - mir->lb[k] * mir->x[kk]; } else if (mir->subst[k] == 'U') { xassert(mir->ub[k] != +DBL_MAX); kk = mir->vub[k]; if (kk == 0) x = mir->ub[k] - mir->x[k]; else x = mir->ub[k] * mir->x[kk] - mir->x[k]; } else xassert(k != k); xassert(x >= -0.001); if (x < 0.0) x = 0.0; s -= mir->cut_vec->val[j] * x; } xassert(s >= 0.0); /* apply heuristic to obtain most violated c-MIR inequality */ b = mir->cut_rhs; r_best = cmir_sep(nint, mir->cut_vec->val, b, u, x, s, alpha, &beta, &gamma); if (r_best == 0.0) goto skip; xassert(r_best > 0.0); /* convert to raw cut */ /* sum alpha[j] * x[j] <= beta + gamma * s */ for (j = 1; j <= nint; j++) mir->cut_vec->val[j] = alpha[j]; for (j = nint+1; j <= mir->cut_vec->nnz; j++) { k = mir->cut_vec->ind[j]; if (k <= m+n) mir->cut_vec->val[j] *= gamma; } mir->cut_rhs = beta; #if _MIR_DEBUG ios_check_vec(mir->cut_vec); #endif skip: /* free working arrays */ xfree(u); xfree(x); xfree(alpha); done: return r_best; } #if _MIR_DEBUG static void check_raw_cut(struct MIR *mir, double r_best) { /* check raw cut before back bound substitution */ int m = mir->m; int n = mir->n; int j, k, kk; double r, big, x; /* compute the residual r = sum a[k] * x[k] - b and determine big = max(1, |a[k]|, |b|) */ r = 0.0, big = 1.0; for (j = 1; j <= mir->cut_vec->nnz; j++) { k = mir->cut_vec->ind[j]; xassert(1 <= k && k <= m+n); if (mir->subst[k] == 'L') { xassert(mir->lb[k] != -DBL_MAX); kk = mir->vlb[k]; if (kk == 0) x = mir->x[k] - mir->lb[k]; else x = mir->x[k] - mir->lb[k] * mir->x[kk]; } else if (mir->subst[k] == 'U') { xassert(mir->ub[k] != +DBL_MAX); kk = mir->vub[k]; if (kk == 0) x = mir->ub[k] - mir->x[k]; else x = mir->ub[k] * mir->x[kk] - mir->x[k]; } else xassert(k != k); r += mir->cut_vec->val[j] * x; if (big < fabs(mir->cut_vec->val[j])) big = fabs(mir->cut_vec->val[j]); } r -= mir->cut_rhs; if (big < fabs(mir->cut_rhs)) big = fabs(mir->cut_rhs); /* the residual must be close to r_best */ xassert(fabs(r - r_best) <= 1e-6 * big); return; } #endif static void back_subst(struct MIR *mir) { /* back substitution of original bounds */ int m = mir->m; int n = mir->n; int j, jj, k, kk; /* at first, restore bounds of integer variables (because on restoring variable bounds of continuous variables we need original, not shifted, bounds of integer variables) */ for (j = 1; j <= mir->cut_vec->nnz; j++) { k = mir->cut_vec->ind[j]; xassert(1 <= k && k <= m+n); if (!mir->isint[k]) continue; /* skip continuous */ if (mir->subst[k] == 'L') { /* x'[k] = x[k] - lb[k] */ xassert(mir->lb[k] != -DBL_MAX); xassert(mir->vlb[k] == 0); mir->cut_rhs += mir->cut_vec->val[j] * mir->lb[k]; } else if (mir->subst[k] == 'U') { /* x'[k] = ub[k] - x[k] */ xassert(mir->ub[k] != +DBL_MAX); xassert(mir->vub[k] == 0); mir->cut_rhs -= mir->cut_vec->val[j] * mir->ub[k]; mir->cut_vec->val[j] = - mir->cut_vec->val[j]; } else xassert(k != k); } /* now restore bounds of continuous variables */ for (j = 1; j <= mir->cut_vec->nnz; j++) { k = mir->cut_vec->ind[j]; xassert(1 <= k && k <= m+n); if (mir->isint[k]) continue; /* skip integer */ if (mir->subst[k] == 'L') { /* x'[k] = x[k] - (lower bound) */ xassert(mir->lb[k] != -DBL_MAX); kk = mir->vlb[k]; if (kk == 0) { /* x'[k] = x[k] - lb[k] */ mir->cut_rhs += mir->cut_vec->val[j] * mir->lb[k]; } else { /* x'[k] = x[k] - lb[k] * x[kk] */ jj = mir->cut_vec->pos[kk]; #if 0 xassert(jj != 0); #else if (jj == 0) { ios_set_vj(mir->cut_vec, kk, 1.0); jj = mir->cut_vec->pos[kk]; xassert(jj != 0); mir->cut_vec->val[jj] = 0.0; } #endif mir->cut_vec->val[jj] -= mir->cut_vec->val[j] * mir->lb[k]; } } else if (mir->subst[k] == 'U') { /* x'[k] = (upper bound) - x[k] */ xassert(mir->ub[k] != +DBL_MAX); kk = mir->vub[k]; if (kk == 0) { /* x'[k] = ub[k] - x[k] */ mir->cut_rhs -= mir->cut_vec->val[j] * mir->ub[k]; } else { /* x'[k] = ub[k] * x[kk] - x[k] */ jj = mir->cut_vec->pos[kk]; if (jj == 0) { ios_set_vj(mir->cut_vec, kk, 1.0); jj = mir->cut_vec->pos[kk]; xassert(jj != 0); mir->cut_vec->val[jj] = 0.0; } mir->cut_vec->val[jj] += mir->cut_vec->val[j] * mir->ub[k]; } mir->cut_vec->val[j] = - mir->cut_vec->val[j]; } else xassert(k != k); } #if _MIR_DEBUG ios_check_vec(mir->cut_vec); #endif return; } #if _MIR_DEBUG static void check_cut_row(struct MIR *mir, double r_best) { /* check the cut after back bound substitution or elimination of auxiliary variables */ int m = mir->m; int n = mir->n; int j, k; double r, big; /* compute the residual r = sum a[k] * x[k] - b and determine big = max(1, |a[k]|, |b|) */ r = 0.0, big = 1.0; for (j = 1; j <= mir->cut_vec->nnz; j++) { k = mir->cut_vec->ind[j]; xassert(1 <= k && k <= m+n); r += mir->cut_vec->val[j] * mir->x[k]; if (big < fabs(mir->cut_vec->val[j])) big = fabs(mir->cut_vec->val[j]); } r -= mir->cut_rhs; if (big < fabs(mir->cut_rhs)) big = fabs(mir->cut_rhs); /* the residual must be close to r_best */ xassert(fabs(r - r_best) <= 1e-6 * big); return; } #endif static void subst_aux_vars(glp_tree *tree, struct MIR *mir) { /* final substitution to eliminate auxiliary variables */ glp_prob *mip = tree->mip; int m = mir->m; int n = mir->n; GLPAIJ *aij; int j, k, kk, jj; for (j = mir->cut_vec->nnz; j >= 1; j--) { k = mir->cut_vec->ind[j]; xassert(1 <= k && k <= m+n); if (k > m) continue; /* skip structurals */ for (aij = mip->row[k]->ptr; aij != NULL; aij = aij->r_next) { kk = m + aij->col->j; /* structural */ jj = mir->cut_vec->pos[kk]; if (jj == 0) { ios_set_vj(mir->cut_vec, kk, 1.0); jj = mir->cut_vec->pos[kk]; mir->cut_vec->val[jj] = 0.0; } mir->cut_vec->val[jj] += mir->cut_vec->val[j] * aij->val; } mir->cut_vec->val[j] = 0.0; } ios_clean_vec(mir->cut_vec, 0.0); return; } static void add_cut(glp_tree *tree, struct MIR *mir) { /* add constructed cut inequality to the cut pool */ int m = mir->m; int n = mir->n; int j, k, len; int *ind = xcalloc(1+n, sizeof(int)); double *val = xcalloc(1+n, sizeof(double)); len = 0; for (j = mir->cut_vec->nnz; j >= 1; j--) { k = mir->cut_vec->ind[j]; xassert(m+1 <= k && k <= m+n); len++, ind[len] = k - m, val[len] = mir->cut_vec->val[j]; } #if 0 ios_add_cut_row(tree, pool, GLP_RF_MIR, len, ind, val, GLP_UP, mir->cut_rhs); #else glp_ios_add_row(tree, NULL, GLP_RF_MIR, 0, len, ind, val, GLP_UP, mir->cut_rhs); #endif xfree(ind); xfree(val); return; } static int aggregate_row(glp_tree *tree, struct MIR *mir) { /* try to aggregate another row */ glp_prob *mip = tree->mip; int m = mir->m; int n = mir->n; GLPAIJ *aij; IOSVEC *v; int ii, j, jj, k, kk, kappa = 0, ret = 0; double d1, d2, d, d_max = 0.0; /* choose appropriate structural variable in the aggregated row to be substituted */ for (j = 1; j <= mir->agg_vec->nnz; j++) { k = mir->agg_vec->ind[j]; xassert(1 <= k && k <= m+n); if (k <= m) continue; /* skip auxiliary var */ if (mir->isint[k]) continue; /* skip integer var */ if (fabs(mir->agg_vec->val[j]) < 0.001) continue; /* compute distance from x[k] to its lower bound */ kk = mir->vlb[k]; if (kk == 0) { if (mir->lb[k] == -DBL_MAX) d1 = DBL_MAX; else d1 = mir->x[k] - mir->lb[k]; } else { xassert(1 <= kk && kk <= m+n); xassert(mir->isint[kk]); xassert(mir->lb[k] != -DBL_MAX); d1 = mir->x[k] - mir->lb[k] * mir->x[kk]; } /* compute distance from x[k] to its upper bound */ kk = mir->vub[k]; if (kk == 0) { if (mir->vub[k] == +DBL_MAX) d2 = DBL_MAX; else d2 = mir->ub[k] - mir->x[k]; } else { xassert(1 <= kk && kk <= m+n); xassert(mir->isint[kk]); xassert(mir->ub[k] != +DBL_MAX); d2 = mir->ub[k] * mir->x[kk] - mir->x[k]; } /* x[k] cannot be free */ xassert(d1 != DBL_MAX || d2 != DBL_MAX); /* d = min(d1, d2) */ d = (d1 <= d2 ? d1 : d2); xassert(d != DBL_MAX); /* should not be close to corresponding bound */ if (d < 0.001) continue; if (d_max < d) d_max = d, kappa = k; } if (kappa == 0) { /* nothing chosen */ ret = 1; goto done; } /* x[kappa] has been chosen */ xassert(m+1 <= kappa && kappa <= m+n); xassert(!mir->isint[kappa]); /* find another row, which have not been used yet, to eliminate x[kappa] from the aggregated row */ for (ii = 1; ii <= m; ii++) { if (mir->skip[ii]) continue; for (aij = mip->row[ii]->ptr; aij != NULL; aij = aij->r_next) if (aij->col->j == kappa - m) break; if (aij != NULL && fabs(aij->val) >= 0.001) break; } if (ii > m) { /* nothing found */ ret = 2; goto done; } /* row ii has been found; include it in the aggregated list */ mir->agg_cnt++; xassert(mir->agg_cnt <= MAXAGGR); mir->agg_row[mir->agg_cnt] = ii; mir->skip[ii] = 2; /* v := new row */ v = ios_create_vec(m+n); ios_set_vj(v, ii, 1.0); for (aij = mip->row[ii]->ptr; aij != NULL; aij = aij->r_next) ios_set_vj(v, m + aij->col->j, - aij->val); #if _MIR_DEBUG ios_check_vec(v); #endif /* perform gaussian elimination to remove x[kappa] */ j = mir->agg_vec->pos[kappa]; xassert(j != 0); jj = v->pos[kappa]; xassert(jj != 0); ios_linear_comb(mir->agg_vec, - mir->agg_vec->val[j] / v->val[jj], v); ios_delete_vec(v); ios_set_vj(mir->agg_vec, kappa, 0.0); #if _MIR_DEBUG ios_check_vec(mir->agg_vec); #endif done: return ret; } void ios_mir_gen(glp_tree *tree, void *gen) { /* main routine to generate MIR cuts */ glp_prob *mip = tree->mip; struct MIR *mir = gen; int m = mir->m; int n = mir->n; int i; double r_best; xassert(mip->m >= m); xassert(mip->n == n); /* obtain current point */ get_current_point(tree, mir); #if _MIR_DEBUG /* check current point */ check_current_point(mir); #endif /* reset bound substitution flags */ memset(&mir->subst[1], '?', m+n); /* try to generate a set of violated MIR cuts */ for (i = 1; i <= m; i++) { if (mir->skip[i]) continue; /* use original i-th row as initial aggregated constraint */ initial_agg_row(tree, mir, i); loop: ; #if _MIR_DEBUG /* check aggregated row */ check_agg_row(mir); #endif /* substitute fixed variables into aggregated constraint */ subst_fixed_vars(mir); #if _MIR_DEBUG /* check aggregated row */ check_agg_row(mir); #endif #if _MIR_DEBUG /* check bound substitution flags */ { int k; for (k = 1; k <= m+n; k++) xassert(mir->subst[k] == '?'); } #endif /* apply bound substitution heuristic */ bound_subst_heur(mir); /* substitute bounds and build modified constraint */ build_mod_row(mir); #if _MIR_DEBUG /* check modified row */ check_mod_row(mir); #endif /* try to generate violated c-MIR cut for modified row */ r_best = generate(mir); if (r_best > 0.0) { /* success */ #if _MIR_DEBUG /* check raw cut before back bound substitution */ check_raw_cut(mir, r_best); #endif /* back substitution of original bounds */ back_subst(mir); #if _MIR_DEBUG /* check the cut after back bound substitution */ check_cut_row(mir, r_best); #endif /* final substitution to eliminate auxiliary variables */ subst_aux_vars(tree, mir); #if _MIR_DEBUG /* check the cut after elimination of auxiliaries */ check_cut_row(mir, r_best); #endif /* add constructed cut inequality to the cut pool */ add_cut(tree, mir); } /* reset bound substitution flags */ { int j, k; for (j = 1; j <= mir->mod_vec->nnz; j++) { k = mir->mod_vec->ind[j]; xassert(1 <= k && k <= m+n); xassert(mir->subst[k] != '?'); mir->subst[k] = '?'; } } if (r_best == 0.0) { /* failure */ if (mir->agg_cnt < MAXAGGR) { /* try to aggregate another row */ if (aggregate_row(tree, mir) == 0) goto loop; } } /* unmark rows used in the aggregated constraint */ { int k, ii; for (k = 1; k <= mir->agg_cnt; k++) { ii = mir->agg_row[k]; xassert(1 <= ii && ii <= m); xassert(mir->skip[ii] == 2); mir->skip[ii] = 0; } } } return; } /*********************************************************************** * NAME * * ios_mir_term - terminate MIR cut generator * * SYNOPSIS * * #include "glpios.h" * void ios_mir_term(void *gen); * * DESCRIPTION * * The routine ios_mir_term deletes the MIR cut generator working area * freeing all the memory allocated to it. */ void ios_mir_term(void *gen) { struct MIR *mir = gen; xfree(mir->skip); xfree(mir->isint); xfree(mir->lb); xfree(mir->vlb); xfree(mir->ub); xfree(mir->vub); xfree(mir->x); xfree(mir->agg_row); ios_delete_vec(mir->agg_vec); xfree(mir->subst); ios_delete_vec(mir->mod_vec); ios_delete_vec(mir->cut_vec); xfree(mir); return; } /* eof */ sources_5316/external/glpk/glpenv04.c0000644000176700017670000000751011401660400016300 0ustar paulpaul/* glpenv04.c (error handling) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_error - display error message and terminate execution * * SYNOPSIS * * void glp_error(const char *fmt, ...); * * DESCRIPTION * * The routine glp_error (implemented as a macro) formats its * parameters using the format control string fmt, writes the formatted * message to the terminal, and abnormally terminates the program. */ static void error(const char *fmt, ...) { ENV *env = get_env_ptr(); va_list arg; env->term_out = GLP_ON; va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); xprintf("Error detected in file %s at line %d\n", env->err_file, env->err_line); if (env->err_hook != NULL) env->err_hook(env->err_info); abort(); exit(EXIT_FAILURE); /* no return */ } _glp_error glp_error_(const char *file, int line) { ENV *env = get_env_ptr(); env->err_file = file; env->err_line = line; return error; } /*********************************************************************** * NAME * * glp_assert - check for logical condition * * SYNOPSIS * * #include "glplib.h" * void glp_assert(int expr); * * DESCRIPTION * * The routine glp_assert (implemented as a macro) checks for a logical * condition specified by the parameter expr. If the condition is false * (i.e. the value of expr is zero), the routine writes a message to * the terminal and abnormally terminates the program. */ void glp_assert_(const char *expr, const char *file, int line) { glp_error_(file, line)("Assertion failed: %s\n", expr); /* no return */ } /*********************************************************************** * NAME * * glp_error_hook - install hook to intercept abnormal termination * * SYNOPSIS * * void glp_error_hook(void (*func)(void *info), void *info); * * DESCRIPTION * * The routine glp_error_hook installs a user-defined hook routine to * intercept abnormal termination. * * The parameter func specifies the user-defined hook routine. It is * called from the routine glp_error before the latter calls the abort * function to abnormally terminate the application program because of * fatal error. The parameter info is a transit pointer, specified in * the corresponding call to the routine glp_error_hook; it may be used * to pass some information to the hook routine. * * To uninstall the hook routine the parameters func and info should be * specified as NULL. */ void glp_error_hook(void (*func)(void *info), void *info) { ENV *env = get_env_ptr(); if (func == NULL) { env->err_hook = NULL; env->err_info = NULL; } else { env->err_hook = func; env->err_info = info; } return; } /* eof */ sources_5316/external/glpk/glplib02.c0000644000176700017670000002103011401660400016245 0ustar paulpaul/* glplib02.c (64-bit arithmetic) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glplib.h" /*********************************************************************** * NAME * * xlset - expand integer to long integer * * SYNOPSIS * * #include "glplib.h" * glp_long xlset(int x); * * RETURNS * * The routine xlset returns x expanded to long integer. */ glp_long xlset(int x) { glp_long t; t.lo = x, t.hi = (x >= 0 ? 0 : -1); return t; } /*********************************************************************** * NAME * * xlneg - negate long integer * * SYNOPSIS * * #include "glplib.h" * glp_long xlneg(glp_long x); * * RETURNS * * The routine xlneg returns the difference 0 - x. */ glp_long xlneg(glp_long x) { if (x.lo) x.lo = - x.lo, x.hi = ~x.hi; else x.hi = - x.hi; return x; } /*********************************************************************** * NAME * * xladd - add long integers * * SYNOPSIS * * #include "glplib.h" * glp_long xladd(glp_long x, glp_long y); * * RETURNS * * The routine xladd returns the sum x + y. */ glp_long xladd(glp_long x, glp_long y) { if ((unsigned int)x.lo <= 0xFFFFFFFF - (unsigned int)y.lo) x.lo += y.lo, x.hi += y.hi; else x.lo += y.lo, x.hi += y.hi + 1; return x; } /*********************************************************************** * NAME * * xlsub - subtract long integers * * SYNOPSIS * * #include "glplib.h" * glp_long xlsub(glp_long x, glp_long y); * * RETURNS * * The routine xlsub returns the difference x - y. */ glp_long xlsub(glp_long x, glp_long y) { return xladd(x, xlneg(y)); } /*********************************************************************** * NAME * * xlcmp - compare long integers * * SYNOPSIS * * #include "glplib.h" * int xlcmp(glp_long x, glp_long y); * * RETURNS * * The routine xlcmp returns the sign of the difference x - y. */ int xlcmp(glp_long x, glp_long y) { if (x.hi >= 0 && y.hi < 0) return +1; if (x.hi < 0 && y.hi >= 0) return -1; if ((unsigned int)x.hi < (unsigned int)y.hi) return -1; if ((unsigned int)x.hi > (unsigned int)y.hi) return +1; if ((unsigned int)x.lo < (unsigned int)y.lo) return -1; if ((unsigned int)x.lo > (unsigned int)y.lo) return +1; return 0; } /*********************************************************************** * NAME * * xlmul - multiply long integers * * SYNOPSIS * * #include "glplib.h" * glp_long xlmul(glp_long x, glp_long y); * * RETURNS * * The routine xlmul returns the product x * y. */ glp_long xlmul(glp_long x, glp_long y) { unsigned short xx[8], yy[4]; xx[4] = (unsigned short)x.lo; xx[5] = (unsigned short)(x.lo >> 16); xx[6] = (unsigned short)x.hi; xx[7] = (unsigned short)(x.hi >> 16); yy[0] = (unsigned short)y.lo; yy[1] = (unsigned short)(y.lo >> 16); yy[2] = (unsigned short)y.hi; yy[3] = (unsigned short)(y.hi >> 16); bigmul(4, 4, xx, yy); x.lo = (unsigned int)xx[0] | ((unsigned int)xx[1] << 16); x.hi = (unsigned int)xx[2] | ((unsigned int)xx[3] << 16); return x; } /*********************************************************************** * NAME * * xldiv - divide long integers * * SYNOPSIS * * #include "glplib.h" * glp_ldiv xldiv(glp_long x, glp_long y); * * RETURNS * * The routine xldiv returns a structure of type glp_ldiv containing * members quot (the quotient) and rem (the remainder), both of type * glp_long. */ glp_ldiv xldiv(glp_long x, glp_long y) { glp_ldiv t; int m, sx, sy; unsigned short xx[8], yy[4]; /* sx := sign(x) */ sx = (x.hi < 0); /* sy := sign(y) */ sy = (y.hi < 0); /* x := |x| */ if (sx) x = xlneg(x); /* y := |y| */ if (sy) y = xlneg(y); /* compute x div y and x mod y */ xx[0] = (unsigned short)x.lo; xx[1] = (unsigned short)(x.lo >> 16); xx[2] = (unsigned short)x.hi; xx[3] = (unsigned short)(x.hi >> 16); yy[0] = (unsigned short)y.lo; yy[1] = (unsigned short)(y.lo >> 16); yy[2] = (unsigned short)y.hi; yy[3] = (unsigned short)(y.hi >> 16); if (yy[3]) m = 4; else if (yy[2]) m = 3; else if (yy[1]) m = 2; else if (yy[0]) m = 1; else xerror("xldiv: divide by zero\n"); bigdiv(4 - m, m, xx, yy); /* remainder in x[0], x[1], ..., x[m-1] */ t.rem.lo = (unsigned int)xx[0], t.rem.hi = 0; if (m >= 2) t.rem.lo |= (unsigned int)xx[1] << 16; if (m >= 3) t.rem.hi = (unsigned int)xx[2]; if (m >= 4) t.rem.hi |= (unsigned int)xx[3] << 16; if (sx) t.rem = xlneg(t.rem); /* quotient in x[m], x[m+1], ..., x[4] */ t.quot.lo = (unsigned int)xx[m], t.quot.hi = 0; if (m <= 3) t.quot.lo |= (unsigned int)xx[m+1] << 16; if (m <= 2) t.quot.hi = (unsigned int)xx[m+2]; if (m <= 1) t.quot.hi |= (unsigned int)xx[m+3] << 16; if (sx ^ sy) t.quot = xlneg(t.quot); return t; } /*********************************************************************** * NAME * * xltod - convert long integer to double * * SYNOPSIS * * #include "glplib.h" * double xltod(glp_long x); * * RETURNS * * The routine xltod returns x converted to double. */ double xltod(glp_long x) { double s, z; if (x.hi >= 0) s = +1.0; else s = -1.0, x = xlneg(x); if (x.hi >= 0) z = 4294967296.0 * (double)x.hi + (double)(unsigned int)x.lo; else { xassert(x.hi == 0x80000000 && x.lo == 0x00000000); z = 9223372036854775808.0; /* 2^63 */ } return s * z; } char *xltoa(glp_long x, char *s) { /* convert long integer to character string */ static const char *d = "0123456789"; glp_ldiv t; int neg, len; if (x.hi >= 0) neg = 0; else neg = 1, x = xlneg(x); if (x.hi >= 0) { len = 0; while (!(x.hi == 0 && x.lo == 0)) { t = xldiv(x, xlset(10)); xassert(0 <= t.rem.lo && t.rem.lo <= 9); s[len++] = d[t.rem.lo]; x = t.quot; } if (len == 0) s[len++] = d[0]; if (neg) s[len++] = '-'; s[len] = '\0'; strrev(s); } else strcpy(s, "-9223372036854775808"); /* -2^63 */ return s; } /**********************************************************************/ #if 0 #include "glprng.h" #define N_TEST 1000000 /* number of tests */ static glp_long myrand(RNG *rand) { glp_long x; int k; k = rng_unif_rand(rand, 4); xassert(0 <= k && k <= 3); x.lo = rng_unif_rand(rand, 65536); if (k == 1 || k == 3) { x.lo <<= 16; x.lo += rng_unif_rand(rand, 65536); } if (k <= 1) x.hi = 0; else x.hi = rng_unif_rand(rand, 65536); if (k == 3) { x.hi <<= 16; x.hi += rng_unif_rand(rand, 65536); } if (rng_unif_rand(rand, 2)) x = xlneg(x); return x; } int main(void) { RNG *rand; glp_long x, y; glp_ldiv z; int test; rand = rng_create_rand(); for (test = 1; test <= N_TEST; test++) { x = myrand(rand); y = myrand(rand); if (y.lo == 0 && y.hi == 0) y.lo = 1; /* z.quot := x div y, z.rem := x mod y */ z = xldiv(x, y); /* x must be equal to y * z.quot + z.rem */ xassert(xlcmp(x, xladd(xlmul(y, z.quot), z.rem)) == 0); } xprintf("%d tests successfully passed\n", N_TEST); rng_delete_rand(rand); return 0; } #endif /* eof */ sources_5316/external/glpk/glpsdf.c0000644000176700017670000001576311401660400016131 0ustar paulpaul/* glpsdf.c (plain data file reading routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define GLPSDF_H #define GLP_DATA_DEFINED typedef struct glp_data glp_data; #include "glpapi.h" struct glp_data { /* plain data file */ char *fname; /* name of data file */ XFILE *fp; /* stream assigned to data file */ void *jump; /* jmp_buf jump; */ /* label for go to in case of error */ int count; /* line count */ int c; /* current character of XEOF */ char item[255+1]; /* current data item */ }; static void next_char(glp_data *data); glp_data *glp_sdf_open_file(const char *fname) { /* open plain data file */ glp_data *data = NULL; XFILE *fp; jmp_buf jump; fp = xfopen(fname, "r"); if (fp == NULL) { xprintf("Unable to open `%s' - %s\n", fname, xerrmsg()); goto done; } data = xmalloc(sizeof(glp_data)); data->fname = xmalloc(strlen(fname)+1); strcpy(data->fname, fname); data->fp = fp; data->jump = NULL; data->count = 0; data->c = '\n'; data->item[0] = '\0'; /* read the very first character */ if (setjmp(jump)) { glp_sdf_close_file(data); data = NULL; goto done; } data->jump = jump; next_char(data); data->jump = NULL; done: return data; } void glp_sdf_set_jump(glp_data *data, void *jump) { /* set up error handling */ data->jump = jump; return; } void glp_sdf_error(glp_data *data, const char *fmt, ...) { /* print error message */ va_list arg; xprintf("%s:%d: ", data->fname, data->count); va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); if (data->jump == NULL) xerror(""); else longjmp(data->jump, 1); /* no return */ } void glp_sdf_warning(glp_data *data, const char *fmt, ...) { /* print warning message */ va_list arg; xprintf("%s:%d: warning: ", data->fname, data->count); va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); return; } static void next_char(glp_data *data) { /* read next character */ int c; if (data->c == XEOF) glp_sdf_error(data, "unexpected end of file\n"); else if (data->c == '\n') data->count++; c = xfgetc(data->fp); if (c < 0) { if (xferror(data->fp)) glp_sdf_error(data, "read error - %s\n", xerrmsg()); else if (data->c == '\n') c = XEOF; else { glp_sdf_warning(data, "missing final end of line\n"); c = '\n'; } } else if (c == '\n') ; else if (isspace(c)) c = ' '; else if (iscntrl(c)) glp_sdf_error(data, "invalid control character 0x%02X\n", c); data->c = c; return; } static void skip_pad(glp_data *data) { /* skip uninteresting characters and comments */ loop: while (data->c == ' ' || data->c == '\n') next_char(data); if (data->c == '/') { next_char(data); if (data->c != '*') glp_sdf_error(data, "invalid use of slash\n"); next_char(data); for (;;) { if (data->c == '*') { next_char(data); if (data->c == '/') { next_char(data); break; } } next_char(data); } goto loop; } return; } static void next_item(glp_data *data) { /* read next item */ int len; skip_pad(data); len = 0; while (!(data->c == ' ' || data->c == '\n')) { data->item[len++] = (char)data->c; if (len == sizeof(data->item)) glp_sdf_error(data, "data item `%.31s...' too long\n", data->item); next_char(data); } data->item[len] = '\0'; return; } int glp_sdf_read_int(glp_data *data) { /* read integer number */ int x; next_item(data); switch (str2int(data->item, &x)) { case 0: break; case 1: glp_sdf_error(data, "integer `%s' out of range\n", data->item); case 2: glp_sdf_error(data, "cannot convert `%s' to integer\n", data->item); default: xassert(data != data); } return x; } double glp_sdf_read_num(glp_data *data) { /* read floating-point number */ double x; next_item(data); switch (str2num(data->item, &x)) { case 0: break; case 1: glp_sdf_error(data, "number `%s' out of range\n", data->item); case 2: glp_sdf_error(data, "cannot convert `%s' to number\n", data->item); default: xassert(data != data); } return x; } const char *glp_sdf_read_item(glp_data *data) { /* read data item */ next_item(data); return data->item; } const char *glp_sdf_read_text(glp_data *data) { /* read text until end of line */ int c, len = 0; for (;;) { c = data->c; next_char(data); if (c == ' ') { /* ignore initial spaces */ if (len == 0) continue; /* and multiple ones */ if (data->item[len-1] == ' ') continue; } else if (c == '\n') { /* remove trailing space */ if (len > 0 && data->item[len-1] == ' ') len--; /* and stop reading */ break; } /* add current character to the buffer */ data->item[len++] = (char)c; if (len == sizeof(data->item)) glp_sdf_error(data, "line too long\n", data->item); } data->item[len] = '\0'; return data->item; } int glp_sdf_line(glp_data *data) { /* determine current line number */ return data->count; } void glp_sdf_close_file(glp_data *data) { /* close plain data file */ xfclose(data->fp); xfree(data->fname); xfree(data); return; } /* eof */ sources_5316/external/glpk/glpnet08.c0000644000176700017670000001642611401660400016310 0ustar paulpaul/* glpnet08.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Two subroutines sub() and wclique() below are intended to find a * maximum weight clique in a given undirected graph. These subroutines * are slightly modified version of the program WCLIQUE developed by * Patric Ostergard and based * on ideas from the article "P. R. J. Ostergard, A new algorithm for * the maximum-weight clique problem, submitted for publication", which * in turn is a generalization of the algorithm for unweighted graphs * presented in "P. R. J. Ostergard, A fast algorithm for the maximum * clique problem, submitted for publication". * * USED WITH PERMISSION OF THE AUTHOR OF THE ORIGINAL CODE. * * Changes were made by Andrew Makhorin . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpenv.h" #include "glpnet.h" /*********************************************************************** * NAME * * wclique - find maximum weight clique with Ostergard's algorithm * * SYNOPSIS * * int wclique(int n, const int w[], const unsigned char a[], * int ind[]); * * DESCRIPTION * * The routine wclique finds a maximum weight clique in an undirected * graph with Ostergard's algorithm. * * INPUT PARAMETERS * * n is the number of vertices, n > 0. * * w[i], i = 1,...,n, is a weight of vertex i. * * a[*] is the strict (without main diagonal) lower triangle of the * graph adjacency matrix in packed format. * * OUTPUT PARAMETER * * ind[k], k = 1,...,size, is the number of a vertex included in the * clique found, 1 <= ind[k] <= n, where size is the number of vertices * in the clique returned on exit. * * RETURNS * * The routine returns the clique size, i.e. the number of vertices in * the clique. */ struct csa { /* common storage area */ int n; /* number of vertices */ const int *wt; /* int wt[0:n-1]; */ /* weights */ const unsigned char *a; /* adjacency matrix (packed lower triangle without main diag.) */ int record; /* weight of best clique */ int rec_level; /* number of vertices in best clique */ int *rec; /* int rec[0:n-1]; */ /* best clique so far */ int *clique; /* int clique[0:n-1]; */ /* table for pruning */ int *set; /* int set[0:n-1]; */ /* current clique */ }; #define n (csa->n) #define wt (csa->wt) #define a (csa->a) #define record (csa->record) #define rec_level (csa->rec_level) #define rec (csa->rec) #define clique (csa->clique) #define set (csa->set) #if 0 static int is_edge(struct csa *csa, int i, int j) { /* if there is arc (i,j), the routine returns true; otherwise false; 0 <= i, j < n */ int k; xassert(0 <= i && i < n); xassert(0 <= j && j < n); if (i == j) return 0; if (i < j) k = i, i = j, j = k; k = (i * (i - 1)) / 2 + j; return a[k / CHAR_BIT] & (unsigned char)(1 << ((CHAR_BIT - 1) - k % CHAR_BIT)); } #else #define is_edge(csa, i, j) ((i) == (j) ? 0 : \ (i) > (j) ? is_edge1(i, j) : is_edge1(j, i)) #define is_edge1(i, j) is_edge2(((i) * ((i) - 1)) / 2 + (j)) #define is_edge2(k) (a[(k) / CHAR_BIT] & \ (unsigned char)(1 << ((CHAR_BIT - 1) - (k) % CHAR_BIT))) #endif static void sub(struct csa *csa, int ct, int table[], int level, int weight, int l_weight) { int i, j, k, curr_weight, left_weight, *p1, *p2, *newtable; newtable = xcalloc(n, sizeof(int)); if (ct <= 0) { /* 0 or 1 elements left; include these */ if (ct == 0) { set[level++] = table[0]; weight += l_weight; } if (weight > record) { record = weight; rec_level = level; for (i = 0; i < level; i++) rec[i] = set[i]; } goto done; } for (i = ct; i >= 0; i--) { if ((level == 0) && (i < ct)) goto done; k = table[i]; if ((level > 0) && (clique[k] <= (record - weight))) goto done; /* prune */ set[level] = k; curr_weight = weight + wt[k]; l_weight -= wt[k]; if (l_weight <= (record - curr_weight)) goto done; /* prune */ p1 = newtable; p2 = table; left_weight = 0; while (p2 < table + i) { j = *p2++; if (is_edge(csa, j, k)) { *p1++ = j; left_weight += wt[j]; } } if (left_weight <= (record - curr_weight)) continue; sub(csa, p1 - newtable - 1, newtable, level + 1, curr_weight, left_weight); } done: xfree(newtable); return; } int wclique(int _n, const int w[], const unsigned char _a[], int ind[]) { struct csa _csa, *csa = &_csa; int i, j, p, max_wt, max_nwt, wth, *used, *nwt, *pos; glp_long timer; n = _n; xassert(n > 0); wt = &w[1]; a = _a; record = 0; rec_level = 0; rec = &ind[1]; clique = xcalloc(n, sizeof(int)); set = xcalloc(n, sizeof(int)); used = xcalloc(n, sizeof(int)); nwt = xcalloc(n, sizeof(int)); pos = xcalloc(n, sizeof(int)); /* start timer */ timer = xtime(); /* order vertices */ for (i = 0; i < n; i++) { nwt[i] = 0; for (j = 0; j < n; j++) if (is_edge(csa, i, j)) nwt[i] += wt[j]; } for (i = 0; i < n; i++) used[i] = 0; for (i = n-1; i >= 0; i--) { max_wt = -1; max_nwt = -1; for (j = 0; j < n; j++) { if ((!used[j]) && ((wt[j] > max_wt) || (wt[j] == max_wt && nwt[j] > max_nwt))) { max_wt = wt[j]; max_nwt = nwt[j]; p = j; } } pos[i] = p; used[p] = 1; for (j = 0; j < n; j++) if ((!used[j]) && (j != p) && (is_edge(csa, p, j))) nwt[j] -= wt[p]; } /* main routine */ wth = 0; for (i = 0; i < n; i++) { wth += wt[pos[i]]; sub(csa, i, pos, 0, 0, wth); clique[pos[i]] = record; if (xdifftime(xtime(), timer) >= 5.0 - 0.001) { /* print current record and reset timer */ xprintf("level = %d (%d); best = %d\n", i+1, n, record); timer = xtime(); } } xfree(clique); xfree(set); xfree(used); xfree(nwt); xfree(pos); /* return the solution found */ for (i = 1; i <= rec_level; i++) ind[i]++; return rec_level; } #undef n #undef wt #undef a #undef record #undef rec_level #undef rec #undef clique #undef set /* eof */ sources_5316/external/glpk/glpios04.c0000644000176700017670000001664011401660400016306 0ustar paulpaul/* glpios04.c (operations on sparse vectors) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*********************************************************************** * NAME * * ios_create_vec - create sparse vector * * SYNOPSIS * * #include "glpios.h" * IOSVEC *ios_create_vec(int n); * * DESCRIPTION * * The routine ios_create_vec creates a sparse vector of dimension n, * which initially is a null vector. * * RETURNS * * The routine returns a pointer to the vector created. */ IOSVEC *ios_create_vec(int n) { IOSVEC *v; xassert(n >= 0); v = xmalloc(sizeof(IOSVEC)); v->n = n; v->nnz = 0; v->pos = xcalloc(1+n, sizeof(int)); memset(&v->pos[1], 0, n * sizeof(int)); v->ind = xcalloc(1+n, sizeof(int)); v->val = xcalloc(1+n, sizeof(double)); return v; } /*********************************************************************** * NAME * * ios_check_vec - check that sparse vector has correct representation * * SYNOPSIS * * #include "glpios.h" * void ios_check_vec(IOSVEC *v); * * DESCRIPTION * * The routine ios_check_vec checks that a sparse vector specified by * the parameter v has correct representation. * * NOTE * * Complexity of this operation is O(n). */ void ios_check_vec(IOSVEC *v) { int j, k, nnz; xassert(v->n >= 0); nnz = 0; for (j = v->n; j >= 1; j--) { k = v->pos[j]; xassert(0 <= k && k <= v->nnz); if (k != 0) { xassert(v->ind[k] == j); nnz++; } } xassert(v->nnz == nnz); return; } /*********************************************************************** * NAME * * ios_get_vj - retrieve component of sparse vector * * SYNOPSIS * * #include "glpios.h" * double ios_get_vj(IOSVEC *v, int j); * * RETURNS * * The routine ios_get_vj returns j-th component of a sparse vector * specified by the parameter v. */ double ios_get_vj(IOSVEC *v, int j) { int k; xassert(1 <= j && j <= v->n); k = v->pos[j]; xassert(0 <= k && k <= v->nnz); return (k == 0 ? 0.0 : v->val[k]); } /*********************************************************************** * NAME * * ios_set_vj - set/change component of sparse vector * * SYNOPSIS * * #include "glpios.h" * void ios_set_vj(IOSVEC *v, int j, double val); * * DESCRIPTION * * The routine ios_set_vj assigns val to j-th component of a sparse * vector specified by the parameter v. */ void ios_set_vj(IOSVEC *v, int j, double val) { int k; xassert(1 <= j && j <= v->n); k = v->pos[j]; if (val == 0.0) { if (k != 0) { /* remove j-th component */ v->pos[j] = 0; if (k < v->nnz) { v->pos[v->ind[v->nnz]] = k; v->ind[k] = v->ind[v->nnz]; v->val[k] = v->val[v->nnz]; } v->nnz--; } } else { if (k == 0) { /* create j-th component */ k = ++(v->nnz); v->pos[j] = k; v->ind[k] = j; } v->val[k] = val; } return; } /*********************************************************************** * NAME * * ios_clear_vec - set all components of sparse vector to zero * * SYNOPSIS * * #include "glpios.h" * void ios_clear_vec(IOSVEC *v); * * DESCRIPTION * * The routine ios_clear_vec sets all components of a sparse vector * specified by the parameter v to zero. */ void ios_clear_vec(IOSVEC *v) { int k; for (k = 1; k <= v->nnz; k++) v->pos[v->ind[k]] = 0; v->nnz = 0; return; } /*********************************************************************** * NAME * * ios_clean_vec - remove zero or small components from sparse vector * * SYNOPSIS * * #include "glpios.h" * void ios_clean_vec(IOSVEC *v, double eps); * * DESCRIPTION * * The routine ios_clean_vec removes zero components and components * whose magnitude is less than eps from a sparse vector specified by * the parameter v. If eps is 0.0, only zero components are removed. */ void ios_clean_vec(IOSVEC *v, double eps) { int k, nnz; nnz = 0; for (k = 1; k <= v->nnz; k++) { if (fabs(v->val[k]) == 0.0 || fabs(v->val[k]) < eps) { /* remove component */ v->pos[v->ind[k]] = 0; } else { /* keep component */ nnz++; v->pos[v->ind[k]] = nnz; v->ind[nnz] = v->ind[k]; v->val[nnz] = v->val[k]; } } v->nnz = nnz; return; } /*********************************************************************** * NAME * * ios_copy_vec - copy sparse vector (x := y) * * SYNOPSIS * * #include "glpios.h" * void ios_copy_vec(IOSVEC *x, IOSVEC *y); * * DESCRIPTION * * The routine ios_copy_vec copies a sparse vector specified by the * parameter y to a sparse vector specified by the parameter x. */ void ios_copy_vec(IOSVEC *x, IOSVEC *y) { int j; xassert(x != y); xassert(x->n == y->n); ios_clear_vec(x); x->nnz = y->nnz; memcpy(&x->ind[1], &y->ind[1], x->nnz * sizeof(int)); memcpy(&x->val[1], &y->val[1], x->nnz * sizeof(double)); for (j = 1; j <= x->nnz; j++) x->pos[x->ind[j]] = j; return; } /*********************************************************************** * NAME * * ios_linear_comb - compute linear combination (x := x + a * y) * * SYNOPSIS * * #include "glpios.h" * void ios_linear_comb(IOSVEC *x, double a, IOSVEC *y); * * DESCRIPTION * * The routine ios_linear_comb computes the linear combination * * x := x + a * y, * * where x and y are sparse vectors, a is a scalar. */ void ios_linear_comb(IOSVEC *x, double a, IOSVEC *y) { int j, k; double xj, yj; xassert(x != y); xassert(x->n == y->n); for (k = 1; k <= y->nnz; k++) { j = y->ind[k]; xj = ios_get_vj(x, j); yj = y->val[k]; ios_set_vj(x, j, xj + a * yj); } return; } /*********************************************************************** * NAME * * ios_delete_vec - delete sparse vector * * SYNOPSIS * * #include "glpios.h" * void ios_delete_vec(IOSVEC *v); * * DESCRIPTION * * The routine ios_delete_vec deletes a sparse vector specified by the * parameter v freeing all the memory allocated to this object. */ void ios_delete_vec(IOSVEC *v) { /* delete sparse vector */ xfree(v->pos); xfree(v->ind); xfree(v->val); xfree(v); return; } /* eof */ sources_5316/external/glpk/glpcpx.c0000644000176700017670000012476511401660400016152 0ustar paulpaul/* glpcpx.c (CPLEX LP format routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_init_cpxcp - initialize CPLEX LP format control parameters * * SYNOPSIS * * void glp_init_cpxcp(glp_cpxcp *parm): * * The routine glp_init_cpxcp initializes control parameters used by * the CPLEX LP input/output routines glp_read_lp and glp_write_lp with * default values. * * Default values of the control parameters are stored in the glp_cpxcp * structure, which the parameter parm points to. */ void glp_init_cpxcp(glp_cpxcp *parm) { xassert(parm != NULL); return; } static void check_parm(const char *func, const glp_cpxcp *parm) { /* check control parameters */ xassert(func != NULL); xassert(parm != NULL); return; } /*********************************************************************** * NAME * * glp_read_lp - read problem data in CPLEX LP format * * SYNOPSIS * * int glp_read_lp(glp_prob *P, const glp_cpxcp *parm, const char * *fname); * * DESCRIPTION * * The routine glp_read_lp reads problem data in CPLEX LP format from * a text file. * * The parameter parm is a pointer to the structure glp_cpxcp, which * specifies control parameters used by the routine. If parm is NULL, * the routine uses default settings. * * The character string fname specifies a name of the text file to be * read. * * Note that before reading data the current content of the problem * object is completely erased with the routine glp_erase_prob. * * RETURNS * * If the operation was successful, the routine glp_read_lp returns * zero. Otherwise, it prints an error message and returns non-zero. */ struct csa { /* common storage area */ glp_prob *P; /* LP/MIP problem object */ const glp_cpxcp *parm; /* pointer to control parameters */ const char *fname; /* name of input CPLEX LP file */ XFILE *fp; /* stream assigned to input CPLEX LP file */ jmp_buf jump; /* label for go to in case of error */ int count; /* line count */ int c; /* current character or XEOF */ int token; /* current token: */ #define T_EOF 0x00 /* end of file */ #define T_MINIMIZE 0x01 /* keyword 'minimize' */ #define T_MAXIMIZE 0x02 /* keyword 'maximize' */ #define T_SUBJECT_TO 0x03 /* keyword 'subject to' */ #define T_BOUNDS 0x04 /* keyword 'bounds' */ #define T_GENERAL 0x05 /* keyword 'general' */ #define T_INTEGER 0x06 /* keyword 'integer' */ #define T_BINARY 0x07 /* keyword 'binary' */ #define T_END 0x08 /* keyword 'end' */ #define T_NAME 0x09 /* symbolic name */ #define T_NUMBER 0x0A /* numeric constant */ #define T_PLUS 0x0B /* delimiter '+' */ #define T_MINUS 0x0C /* delimiter '-' */ #define T_COLON 0x0D /* delimiter ':' */ #define T_LE 0x0E /* delimiter '<=' */ #define T_GE 0x0F /* delimiter '>=' */ #define T_EQ 0x10 /* delimiter '=' */ char image[255+1]; /* image of current token */ int imlen; /* length of token image */ double value; /* value of numeric constant */ int n_max; /* length of the following five arrays (enlarged automatically, if necessary) */ int *ind; /* int ind[1+n_max]; */ double *val; /* double val[1+n_max]; */ char *flag; /* char flag[1+n_max]; */ /* working arrays used to construct linear forms */ double *lb; /* double lb[1+n_max]; */ double *ub; /* double ub[1+n_max]; */ /* lower and upper bounds of variables (columns) */ }; #define CHAR_SET "!\"#$%&()/,.;?@_`'{}|~" /* characters, which may appear in symbolic names */ static void error(struct csa *csa, const char *fmt, ...) { /* print error message and terminate processing */ va_list arg; xprintf("%s:%d: ", csa->fname, csa->count); va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); longjmp(csa->jump, 1); /* no return */ } static void warning(struct csa *csa, const char *fmt, ...) { /* print warning message and continue processing */ va_list arg; xprintf("%s:%d: warning: ", csa->fname, csa->count); va_start(arg, fmt); xvprintf(fmt, arg); va_end(arg); return; } static void read_char(struct csa *csa) { /* read next character from input file */ int c; xassert(csa->c != XEOF); if (csa->c == '\n') csa->count++; c = xfgetc(csa->fp); if (c < 0) { if (xferror(csa->fp)) error(csa, "read error - %s\n", xerrmsg()); else if (csa->c == '\n') { csa->count--; c = XEOF; } else { warning(csa, "missing final end of line\n"); c = '\n'; } } else if (c == '\n') ; else if (isspace(c)) c = ' '; else if (iscntrl(c)) error(csa, "invalid control character 0x%02X\n", c); csa->c = c; return; } static void add_char(struct csa *csa) { /* append current character to current token */ if (csa->imlen == sizeof(csa->image)-1) error(csa, "token `%.15s...' too long\n", csa->image); csa->image[csa->imlen++] = (char)csa->c; csa->image[csa->imlen] = '\0'; read_char(csa); return; } static int the_same(char *s1, char *s2) { /* compare two character strings ignoring case sensitivity */ for (; *s1 != '\0'; s1++, s2++) { if (tolower((unsigned char)*s1) != tolower((unsigned char)*s2)) return 0; } return 1; } static void scan_token(struct csa *csa) { /* scan next token */ int flag; csa->token = -1; csa->image[0] = '\0'; csa->imlen = 0; csa->value = 0.0; loop: flag = 0; /* skip non-significant characters */ while (csa->c == ' ') read_char(csa); /* recognize and scan current token */ if (csa->c == XEOF) csa->token = T_EOF; else if (csa->c == '\n') { read_char(csa); /* if the next character is letter, it may begin a keyword */ if (isalpha(csa->c)) { flag = 1; goto name; } goto loop; } else if (csa->c == '\\') { /* comment; ignore everything until end-of-line */ while (csa->c != '\n') read_char(csa); goto loop; } else if (isalpha(csa->c) || csa->c != '.' && strchr(CHAR_SET, csa->c) != NULL) name: { /* symbolic name */ csa->token = T_NAME; while (isalnum(csa->c) || strchr(CHAR_SET, csa->c) != NULL) add_char(csa); if (flag) { /* check for keyword */ if (the_same(csa->image, "minimize")) csa->token = T_MINIMIZE; else if (the_same(csa->image, "minimum")) csa->token = T_MINIMIZE; else if (the_same(csa->image, "min")) csa->token = T_MINIMIZE; else if (the_same(csa->image, "maximize")) csa->token = T_MAXIMIZE; else if (the_same(csa->image, "maximum")) csa->token = T_MAXIMIZE; else if (the_same(csa->image, "max")) csa->token = T_MAXIMIZE; else if (the_same(csa->image, "subject")) { if (csa->c == ' ') { read_char(csa); if (tolower(csa->c) == 't') { csa->token = T_SUBJECT_TO; csa->image[csa->imlen++] = ' '; csa->image[csa->imlen] = '\0'; add_char(csa); if (tolower(csa->c) != 'o') error(csa, "keyword `subject to' incomplete\n"); add_char(csa); if (isalpha(csa->c)) error(csa, "keyword `%s%c...' not recognized\n", csa->image, csa->c); } } } else if (the_same(csa->image, "such")) { if (csa->c == ' ') { read_char(csa); if (tolower(csa->c) == 't') { csa->token = T_SUBJECT_TO; csa->image[csa->imlen++] = ' '; csa->image[csa->imlen] = '\0'; add_char(csa); if (tolower(csa->c) != 'h') err: error(csa, "keyword `such that' incomplete\n"); add_char(csa); if (tolower(csa->c) != 'a') goto err; add_char(csa); if (tolower(csa->c) != 't') goto err; add_char(csa); if (isalpha(csa->c)) error(csa, "keyword `%s%c...' not recognized\n", csa->image, csa->c); } } } else if (the_same(csa->image, "st")) csa->token = T_SUBJECT_TO; else if (the_same(csa->image, "s.t.")) csa->token = T_SUBJECT_TO; else if (the_same(csa->image, "st.")) csa->token = T_SUBJECT_TO; else if (the_same(csa->image, "bounds")) csa->token = T_BOUNDS; else if (the_same(csa->image, "bound")) csa->token = T_BOUNDS; else if (the_same(csa->image, "general")) csa->token = T_GENERAL; else if (the_same(csa->image, "generals")) csa->token = T_GENERAL; else if (the_same(csa->image, "gen")) csa->token = T_GENERAL; else if (the_same(csa->image, "integer")) csa->token = T_INTEGER; else if (the_same(csa->image, "integers")) csa->token = T_INTEGER; else if (the_same(csa->image, "int")) csa->token = T_INTEGER; else if (the_same(csa->image, "binary")) csa->token = T_BINARY; else if (the_same(csa->image, "binaries")) csa->token = T_BINARY; else if (the_same(csa->image, "bin")) csa->token = T_BINARY; else if (the_same(csa->image, "end")) csa->token = T_END; } } else if (isdigit(csa->c) || csa->c == '.') { /* numeric constant */ csa->token = T_NUMBER; /* scan integer part */ while (isdigit(csa->c)) add_char(csa); /* scan optional fractional part (it is mandatory, if there is no integer part) */ if (csa->c == '.') { add_char(csa); if (csa->imlen == 1 && !isdigit(csa->c)) error(csa, "invalid use of decimal point\n"); while (isdigit(csa->c)) add_char(csa); } /* scan optional decimal exponent */ if (csa->c == 'e' || csa->c == 'E') { add_char(csa); if (csa->c == '+' || csa->c == '-') add_char(csa); if (!isdigit(csa->c)) error(csa, "numeric constant `%s' incomplete\n", csa->image); while (isdigit(csa->c)) add_char(csa); } /* convert the numeric constant to floating-point */ if (str2num(csa->image, &csa->value)) error(csa, "numeric constant `%s' out of range\n", csa->image); } else if (csa->c == '+') csa->token = T_PLUS, add_char(csa); else if (csa->c == '-') csa->token = T_MINUS, add_char(csa); else if (csa->c == ':') csa->token = T_COLON, add_char(csa); else if (csa->c == '<') { csa->token = T_LE, add_char(csa); if (csa->c == '=') add_char(csa); } else if (csa->c == '>') { csa->token = T_GE, add_char(csa); if (csa->c == '=') add_char(csa); } else if (csa->c == '=') { csa->token = T_EQ, add_char(csa); if (csa->c == '<') csa->token = T_LE, add_char(csa); else if (csa->c == '>') csa->token = T_GE, add_char(csa); } else error(csa, "character `%c' not recognized\n", csa->c); /* skip non-significant characters */ while (csa->c == ' ') read_char(csa); return; } static int find_col(struct csa *csa, char *name) { /* find column by its symbolic name */ int j; j = glp_find_col(csa->P, name); if (j == 0) { /* not found; create new column */ j = glp_add_cols(csa->P, 1); glp_set_col_name(csa->P, j, name); /* enlarge working arrays, if necessary */ if (csa->n_max < j) { int n_max = csa->n_max; int *ind = csa->ind; double *val = csa->val; char *flag = csa->flag; double *lb = csa->lb; double *ub = csa->ub; csa->n_max += csa->n_max; csa->ind = xcalloc(1+csa->n_max, sizeof(int)); memcpy(&csa->ind[1], &ind[1], n_max * sizeof(int)); xfree(ind); csa->val = xcalloc(1+csa->n_max, sizeof(double)); memcpy(&csa->val[1], &val[1], n_max * sizeof(double)); xfree(val); csa->flag = xcalloc(1+csa->n_max, sizeof(char)); memset(&csa->flag[1], 0, csa->n_max * sizeof(char)); memcpy(&csa->flag[1], &flag[1], n_max * sizeof(char)); xfree(flag); csa->lb = xcalloc(1+csa->n_max, sizeof(double)); memcpy(&csa->lb[1], &lb[1], n_max * sizeof(double)); xfree(lb); csa->ub = xcalloc(1+csa->n_max, sizeof(double)); memcpy(&csa->ub[1], &ub[1], n_max * sizeof(double)); xfree(ub); } csa->lb[j] = +DBL_MAX, csa->ub[j] = -DBL_MAX; } return j; } /*********************************************************************** * parse_linear_form - parse linear form * * This routine parses the linear form using the following syntax: * * ::= * ::= * ::= | * ::= | + | - | * + | - * * The routine returns the number of terms in the linear form. */ static int parse_linear_form(struct csa *csa) { int j, k, len = 0, newlen; double s, coef; loop: /* parse an optional sign */ if (csa->token == T_PLUS) s = +1.0, scan_token(csa); else if (csa->token == T_MINUS) s = -1.0, scan_token(csa); else s = +1.0; /* parse an optional coefficient */ if (csa->token == T_NUMBER) coef = csa->value, scan_token(csa); else coef = 1.0; /* parse a variable name */ if (csa->token != T_NAME) error(csa, "missing variable name\n"); /* find the corresponding column */ j = find_col(csa, csa->image); /* check if the variable is already used in the linear form */ if (csa->flag[j]) error(csa, "multiple use of variable `%s' not allowed\n", csa->image); /* add new term to the linear form */ len++, csa->ind[len] = j, csa->val[len] = s * coef; /* and mark that the variable is used in the linear form */ csa->flag[j] = 1; scan_token(csa); /* if the next token is a sign, there is another term */ if (csa->token == T_PLUS || csa->token == T_MINUS) goto loop; /* clear marks of the variables used in the linear form */ for (k = 1; k <= len; k++) csa->flag[csa->ind[k]] = 0; /* remove zero coefficients */ newlen = 0; for (k = 1; k <= len; k++) { if (csa->val[k] != 0.0) { newlen++; csa->ind[newlen] = csa->ind[k]; csa->val[newlen] = csa->val[k]; } } return newlen; } /*********************************************************************** * parse_objective - parse objective function * * This routine parses definition of the objective function using the * following syntax: * * ::= minimize | minimum | min | maximize | maximum | max * ::= | : * ::= */ static void parse_objective(struct csa *csa) { /* parse objective sense */ int k, len; /* parse the keyword 'minimize' or 'maximize' */ if (csa->token == T_MINIMIZE) glp_set_obj_dir(csa->P, GLP_MIN); else if (csa->token == T_MAXIMIZE) glp_set_obj_dir(csa->P, GLP_MAX); else xassert(csa != csa); scan_token(csa); /* parse objective name */ if (csa->token == T_NAME && csa->c == ':') { /* objective name is followed by a colon */ glp_set_obj_name(csa->P, csa->image); scan_token(csa); xassert(csa->token == T_COLON); scan_token(csa); } else { /* objective name is not specified; use default */ glp_set_obj_name(csa->P, "obj"); } /* parse linear form */ len = parse_linear_form(csa); for (k = 1; k <= len; k++) glp_set_obj_coef(csa->P, csa->ind[k], csa->val[k]); return; } /*********************************************************************** * parse_constraints - parse constraints section * * This routine parses the constraints section using the following * syntax: * * ::= | : * ::= < | <= | =< | > | >= | => | = * ::= | + | * - * ::= * * ::= subject to | such that | st | s.t. | st. * ::= | * */ static void parse_constraints(struct csa *csa) { int i, len, type; double s; /* parse the keyword 'subject to' */ xassert(csa->token == T_SUBJECT_TO); scan_token(csa); loop: /* create new row (constraint) */ i = glp_add_rows(csa->P, 1); /* parse row name */ if (csa->token == T_NAME && csa->c == ':') { /* row name is followed by a colon */ if (glp_find_row(csa->P, csa->image) != 0) error(csa, "constraint `%s' multiply defined\n", csa->image); glp_set_row_name(csa->P, i, csa->image); scan_token(csa); xassert(csa->token == T_COLON); scan_token(csa); } else { /* row name is not specified; use default */ char name[50]; sprintf(name, "r.%d", csa->count); glp_set_row_name(csa->P, i, name); } /* parse linear form */ len = parse_linear_form(csa); glp_set_mat_row(csa->P, i, len, csa->ind, csa->val); /* parse constraint sense */ if (csa->token == T_LE) type = GLP_UP, scan_token(csa); else if (csa->token == T_GE) type = GLP_LO, scan_token(csa); else if (csa->token == T_EQ) type = GLP_FX, scan_token(csa); else error(csa, "missing constraint sense\n"); /* parse right-hand side */ if (csa->token == T_PLUS) s = +1.0, scan_token(csa); else if (csa->token == T_MINUS) s = -1.0, scan_token(csa); else s = +1.0; if (csa->token != T_NUMBER) error(csa, "missing right-hand side\n"); glp_set_row_bnds(csa->P, i, type, s * csa->value, s * csa->value); /* the rest of the current line must be empty */ if (!(csa->c == '\n' || csa->c == XEOF)) error(csa, "invalid symbol(s) beyond right-hand side\n"); scan_token(csa); /* if the next token is a sign, numeric constant, or a symbolic name, here is another constraint */ if (csa->token == T_PLUS || csa->token == T_MINUS || csa->token == T_NUMBER || csa->token == T_NAME) goto loop; return; } static void set_lower_bound(struct csa *csa, int j, double lb) { /* set lower bound of j-th variable */ if (csa->lb[j] != +DBL_MAX) { warning(csa, "lower bound of variable `%s' redefined\n", glp_get_col_name(csa->P, j)); } csa->lb[j] = lb; return; } static void set_upper_bound(struct csa *csa, int j, double ub) { /* set upper bound of j-th variable */ if (csa->ub[j] != -DBL_MAX) { warning(csa, "upper bound of variable `%s' redefined\n", glp_get_col_name(csa->P, j)); } csa->ub[j] = ub; return; } /*********************************************************************** * parse_bounds - parse bounds section * * This routine parses the bounds section using the following syntax: * * ::= * ::= infinity | inf * ::= | + | * - | + | - * ::= < | <= | =< * ::= > | >= | => * ::= | * | | * | = | free * ::= bounds | bound * ::= | * */ static void parse_bounds(struct csa *csa) { int j, lb_flag; double lb, s; /* parse the keyword 'bounds' */ xassert(csa->token == T_BOUNDS); scan_token(csa); loop: /* bound definition can start with a sign, numeric constant, or a symbolic name */ if (!(csa->token == T_PLUS || csa->token == T_MINUS || csa->token == T_NUMBER || csa->token == T_NAME)) goto done; /* parse bound definition */ if (csa->token == T_PLUS || csa->token == T_MINUS) { /* parse signed lower bound */ lb_flag = 1; s = (csa->token == T_PLUS ? +1.0 : -1.0); scan_token(csa); if (csa->token == T_NUMBER) lb = s * csa->value, scan_token(csa); else if (the_same(csa->image, "infinity") || the_same(csa->image, "inf")) { if (s > 0.0) error(csa, "invalid use of `+inf' as lower bound\n"); lb = -DBL_MAX, scan_token(csa); } else error(csa, "missing lower bound\n"); } else if (csa->token == T_NUMBER) { /* parse unsigned lower bound */ lb_flag = 1; lb = csa->value, scan_token(csa); } else { /* lower bound is not specified */ lb_flag = 0; } /* parse the token that should follow the lower bound */ if (lb_flag) { if (csa->token != T_LE) error(csa, "missing `<', `<=', or `=<' after lower bound\n") ; scan_token(csa); } /* parse variable name */ if (csa->token != T_NAME) error(csa, "missing variable name\n"); j = find_col(csa, csa->image); /* set lower bound */ if (lb_flag) set_lower_bound(csa, j, lb); scan_token(csa); /* parse the context that follows the variable name */ if (csa->token == T_LE) { /* parse upper bound */ scan_token(csa); if (csa->token == T_PLUS || csa->token == T_MINUS) { /* parse signed upper bound */ s = (csa->token == T_PLUS ? +1.0 : -1.0); scan_token(csa); if (csa->token == T_NUMBER) { set_upper_bound(csa, j, s * csa->value); scan_token(csa); } else if (the_same(csa->image, "infinity") || the_same(csa->image, "inf")) { if (s < 0.0) error(csa, "invalid use of `-inf' as upper bound\n"); set_upper_bound(csa, j, +DBL_MAX); scan_token(csa); } else error(csa, "missing upper bound\n"); } else if (csa->token == T_NUMBER) { /* parse unsigned upper bound */ set_upper_bound(csa, j, csa->value); scan_token(csa); } else error(csa, "missing upper bound\n"); } else if (csa->token == T_GE) { /* parse lower bound */ if (lb_flag) { /* the context '... <= x >= ...' is invalid */ error(csa, "invalid bound definition\n"); } scan_token(csa); if (csa->token == T_PLUS || csa->token == T_MINUS) { /* parse signed lower bound */ s = (csa->token == T_PLUS ? +1.0 : -1.0); scan_token(csa); if (csa->token == T_NUMBER) { set_lower_bound(csa, j, s * csa->value); scan_token(csa); } else if (the_same(csa->image, "infinity") || the_same(csa->image, "inf") == 0) { if (s > 0.0) error(csa, "invalid use of `+inf' as lower bound\n"); set_lower_bound(csa, j, -DBL_MAX); scan_token(csa); } else error(csa, "missing lower bound\n"); } else if (csa->token == T_NUMBER) { /* parse unsigned lower bound */ set_lower_bound(csa, j, csa->value); scan_token(csa); } else error(csa, "missing lower bound\n"); } else if (csa->token == T_EQ) { /* parse fixed value */ if (lb_flag) { /* the context '... <= x = ...' is invalid */ error(csa, "invalid bound definition\n"); } scan_token(csa); if (csa->token == T_PLUS || csa->token == T_MINUS) { /* parse signed fixed value */ s = (csa->token == T_PLUS ? +1.0 : -1.0); scan_token(csa); if (csa->token == T_NUMBER) { set_lower_bound(csa, j, s * csa->value); set_upper_bound(csa, j, s * csa->value); scan_token(csa); } else error(csa, "missing fixed value\n"); } else if (csa->token == T_NUMBER) { /* parse unsigned fixed value */ set_lower_bound(csa, j, csa->value); set_upper_bound(csa, j, csa->value); scan_token(csa); } else error(csa, "missing fixed value\n"); } else if (the_same(csa->image, "free")) { /* parse the keyword 'free' */ if (lb_flag) { /* the context '... <= x free ...' is invalid */ error(csa, "invalid bound definition\n"); } set_lower_bound(csa, j, -DBL_MAX); set_upper_bound(csa, j, +DBL_MAX); scan_token(csa); } else if (!lb_flag) { /* neither lower nor upper bounds are specified */ error(csa, "invalid bound definition\n"); } goto loop; done: return; } /*********************************************************************** * parse_integer - parse general, integer, or binary section * * ::= * ::= general | generals | gen * ::= integer | integers | int * ::= binary | binaries | bin *
::= * ::=
| * */ static void parse_integer(struct csa *csa) { int j, binary; /* parse the keyword 'general', 'integer', or 'binary' */ if (csa->token == T_GENERAL) binary = 0, scan_token(csa); else if (csa->token == T_INTEGER) binary = 0, scan_token(csa); else if (csa->token == T_BINARY) binary = 1, scan_token(csa); else xassert(csa != csa); /* parse list of variables (may be empty) */ while (csa->token == T_NAME) { /* find the corresponding column */ j = find_col(csa, csa->image); /* change kind of the variable */ glp_set_col_kind(csa->P, j, GLP_IV); /* set 0-1 bounds for the binary variable */ if (binary) { set_lower_bound(csa, j, 0.0); set_upper_bound(csa, j, 1.0); } scan_token(csa); } return; } int glp_read_lp(glp_prob *P, const glp_cpxcp *parm, const char *fname) { /* read problem data in CPLEX LP format */ glp_cpxcp _parm; struct csa _csa, *csa = &_csa; int ret; xprintf("Reading problem data from `%s'...\n", fname); if (parm == NULL) glp_init_cpxcp(&_parm), parm = &_parm; /* check control parameters */ check_parm("glp_read_lp", parm); /* initialize common storage area */ csa->P = P; csa->parm = parm; csa->fname = fname; csa->fp = NULL; if (setjmp(csa->jump)) { ret = 1; goto done; } csa->count = 0; csa->c = '\n'; csa->token = T_EOF; csa->image[0] = '\0'; csa->imlen = 0; csa->value = 0.0; csa->n_max = 100; csa->ind = xcalloc(1+csa->n_max, sizeof(int)); csa->val = xcalloc(1+csa->n_max, sizeof(double)); csa->flag = xcalloc(1+csa->n_max, sizeof(char)); memset(&csa->flag[1], 0, csa->n_max * sizeof(char)); csa->lb = xcalloc(1+csa->n_max, sizeof(double)); csa->ub = xcalloc(1+csa->n_max, sizeof(double)); /* erase problem object */ glp_erase_prob(P); glp_create_index(P); /* open input CPLEX LP file */ csa->fp = xfopen(fname, "r"); if (csa->fp == NULL) { xprintf("Unable to open `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* scan very first token */ scan_token(csa); /* parse definition of the objective function */ if (!(csa->token == T_MINIMIZE || csa->token == T_MAXIMIZE)) error(csa, "`minimize' or `maximize' keyword missing\n"); parse_objective(csa); /* parse constraints section */ if (csa->token != T_SUBJECT_TO) error(csa, "constraints section missing\n"); parse_constraints(csa); /* parse optional bounds section */ if (csa->token == T_BOUNDS) parse_bounds(csa); /* parse optional general, integer, and binary sections */ while (csa->token == T_GENERAL || csa->token == T_INTEGER || csa->token == T_BINARY) parse_integer(csa); /* check for the keyword 'end' */ if (csa->token == T_END) scan_token(csa); else if (csa->token == T_EOF) warning(csa, "keyword `end' missing\n"); else error(csa, "symbol `%s' in wrong position\n", csa->image); /* nothing must follow the keyword 'end' (except comments) */ if (csa->token != T_EOF) error(csa, "extra symbol(s) detected beyond `end'\n"); /* set bounds of variables */ { int j, type; double lb, ub; for (j = 1; j <= P->n; j++) { lb = csa->lb[j]; ub = csa->ub[j]; if (lb == +DBL_MAX) lb = 0.0; /* default lb */ if (ub == -DBL_MAX) ub = +DBL_MAX; /* default ub */ if (lb == -DBL_MAX && ub == +DBL_MAX) type = GLP_FR; else if (ub == +DBL_MAX) type = GLP_LO; else if (lb == -DBL_MAX) type = GLP_UP; else if (lb != ub) type = GLP_DB; else type = GLP_FX; glp_set_col_bnds(csa->P, j, type, lb, ub); } } /* print some statistics */ xprintf("%d row%s, %d column%s, %d non-zero%s\n", P->m, P->m == 1 ? "" : "s", P->n, P->n == 1 ? "" : "s", P->nnz, P->nnz == 1 ? "" : "s"); if (glp_get_num_int(P) > 0) { int ni = glp_get_num_int(P); int nb = glp_get_num_bin(P); if (ni == 1) { if (nb == 0) xprintf("One variable is integer\n"); else xprintf("One variable is binary\n"); } else { xprintf("%d integer variables, ", ni); if (nb == 0) xprintf("none"); else if (nb == 1) xprintf("one"); else if (nb == ni) xprintf("all"); else xprintf("%d", nb); xprintf(" of which %s binary\n", nb == 1 ? "is" : "are"); } } xprintf("%d lines were read\n", csa->count); /* problem data has been successfully read */ glp_delete_index(P); glp_sort_matrix(P); ret = 0; done: if (csa->fp != NULL) xfclose(csa->fp); xfree(csa->ind); xfree(csa->val); xfree(csa->flag); xfree(csa->lb); xfree(csa->ub); if (ret != 0) glp_erase_prob(P); return ret; } /*********************************************************************** * NAME * * glp_write_lp - write problem data in CPLEX LP format * * SYNOPSIS * * int glp_write_lp(glp_prob *P, const glp_cpxcp *parm, const char * *fname); * * DESCRIPTION * * The routine glp_write_lp writes problem data in CPLEX LP format to * a text file. * * The parameter parm is a pointer to the structure glp_cpxcp, which * specifies control parameters used by the routine. If parm is NULL, * the routine uses default settings. * * The character string fname specifies a name of the text file to be * written. * * RETURNS * * If the operation was successful, the routine glp_write_lp returns * zero. Otherwise, it prints an error message and returns non-zero. */ #define csa csa1 struct csa { /* common storage area */ glp_prob *P; /* pointer to problem object */ const glp_cpxcp *parm; /* pointer to control parameters */ }; static int check_name(char *name) { /* check if specified name is valid for CPLEX LP format */ if (*name == '.') return 1; if (isdigit((unsigned char)*name)) return 1; for (; *name; name++) { if (!isalnum((unsigned char)*name) && strchr(CHAR_SET, (unsigned char)*name) == NULL) return 1; } return 0; /* name is ok */ } static void adjust_name(char *name) { /* attempt to adjust specified name to make it valid for CPLEX LP format */ for (; *name; name++) { if (*name == ' ') *name = '_'; else if (*name == '-') *name = '~'; else if (*name == '[') *name = '('; else if (*name == ']') *name = ')'; } return; } static char *row_name(struct csa *csa, int i, char rname[255+1]) { /* construct symbolic name of i-th row (constraint) */ const char *name; if (i == 0) name = glp_get_obj_name(csa->P); else name = glp_get_row_name(csa->P, i); if (name == NULL) goto fake; strcpy(rname, name); adjust_name(rname); if (check_name(rname)) goto fake; return rname; fake: if (i == 0) strcpy(rname, "obj"); else sprintf(rname, "r_%d", i); return rname; } static char *col_name(struct csa *csa, int j, char cname[255+1]) { /* construct symbolic name of j-th column (variable) */ const char *name; name = glp_get_col_name(csa->P, j); if (name == NULL) goto fake; strcpy(cname, name); adjust_name(cname); if (check_name(cname)) goto fake; return cname; fake: sprintf(cname, "x_%d", j); return cname; } int glp_write_lp(glp_prob *P, const glp_cpxcp *parm, const char *fname) { /* write problem data in CPLEX LP format */ glp_cpxcp _parm; struct csa _csa, *csa = &_csa; XFILE *fp; GLPROW *row; GLPCOL *col; GLPAIJ *aij; int i, j, len, flag, count, ret; char line[1000+1], term[500+1], name[255+1]; xprintf("Writing problem data to `%s'...\n", fname); if (parm == NULL) glp_init_cpxcp(&_parm), parm = &_parm; /* check control parameters */ check_parm("glp_write_lp", parm); /* initialize common storage area */ csa->P = P; csa->parm = parm; /* create output CPLEX LP file */ fp = xfopen(fname, "w"), count = 0; if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* write problem name */ xfprintf(fp, "\\* Problem: %s *\\\n", P->name == NULL ? "Unknown" : P->name), count++; xfprintf(fp, "\n"), count++; /* the problem should contain at least one row and one column */ if (!(P->m > 0 && P->n > 0)) { xprintf("Warning: problem has no rows/columns\n"); xfprintf(fp, "\\* WARNING: PROBLEM HAS NO ROWS/COLUMNS *\\\n"), count++; xfprintf(fp, "\n"), count++; goto skip; } /* write the objective function definition */ if (P->dir == GLP_MIN) xfprintf(fp, "Minimize\n"), count++; else if (P->dir == GLP_MAX) xfprintf(fp, "Maximize\n"), count++; else xassert(P != P); row_name(csa, 0, name); sprintf(line, " %s:", name); len = 0; for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->coef != 0.0 || col->ptr == NULL) { len++; col_name(csa, j, name); if (col->coef == 0.0) sprintf(term, " + 0 %s", name); /* empty column */ else if (col->coef == +1.0) sprintf(term, " + %s", name); else if (col->coef == -1.0) sprintf(term, " - %s", name); else if (col->coef > 0.0) sprintf(term, " + %.*g %s", DBL_DIG, +col->coef, name); else sprintf(term, " - %.*g %s", DBL_DIG, -col->coef, name); if (strlen(line) + strlen(term) > 72) xfprintf(fp, "%s\n", line), line[0] = '\0', count++; strcat(line, term); } } if (len == 0) { /* empty objective */ sprintf(term, " 0 %s", col_name(csa, 1, name)); strcat(line, term); } xfprintf(fp, "%s\n", line), count++; if (P->c0 != 0.0) xfprintf(fp, "\\* constant term = %.*g *\\\n", DBL_DIG, P->c0), count++; xfprintf(fp, "\n"), count++; /* write the constraints section */ xfprintf(fp, "Subject To\n"), count++; for (i = 1; i <= P->m; i++) { row = P->row[i]; if (row->type == GLP_FR) continue; /* skip free row */ row_name(csa, i, name); sprintf(line, " %s:", name); /* linear form */ for (aij = row->ptr; aij != NULL; aij = aij->r_next) { col_name(csa, aij->col->j, name); if (aij->val == +1.0) sprintf(term, " + %s", name); else if (aij->val == -1.0) sprintf(term, " - %s", name); else if (aij->val > 0.0) sprintf(term, " + %.*g %s", DBL_DIG, +aij->val, name); else sprintf(term, " - %.*g %s", DBL_DIG, -aij->val, name); if (strlen(line) + strlen(term) > 72) xfprintf(fp, "%s\n", line), line[0] = '\0', count++; strcat(line, term); } if (row->type == GLP_DB) { /* double-bounded (ranged) constraint */ sprintf(term, " - ~r_%d", i); if (strlen(line) + strlen(term) > 72) xfprintf(fp, "%s\n", line), line[0] = '\0', count++; strcat(line, term); } else if (row->ptr == NULL) { /* empty constraint */ sprintf(term, " 0 %s", col_name(csa, 1, name)); strcat(line, term); } /* right hand-side */ if (row->type == GLP_LO) sprintf(term, " >= %.*g", DBL_DIG, row->lb); else if (row->type == GLP_UP) sprintf(term, " <= %.*g", DBL_DIG, row->ub); else if (row->type == GLP_DB || row->type == GLP_FX) sprintf(term, " = %.*g", DBL_DIG, row->lb); else xassert(row != row); if (strlen(line) + strlen(term) > 72) xfprintf(fp, "%s\n", line), line[0] = '\0', count++; strcat(line, term); xfprintf(fp, "%s\n", line), count++; } xfprintf(fp, "\n"), count++; /* write the bounds section */ flag = 0; for (i = 1; i <= P->m; i++) { row = P->row[i]; if (row->type != GLP_DB) continue; if (!flag) xfprintf(fp, "Bounds\n"), flag = 1, count++; xfprintf(fp, " 0 <= ~r_%d <= %.*g\n", i, DBL_DIG, row->ub - row->lb), count++; } for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->type == GLP_LO && col->lb == 0.0) continue; if (!flag) xfprintf(fp, "Bounds\n"), flag = 1, count++; col_name(csa, j, name); if (col->type == GLP_FR) xfprintf(fp, " %s free\n", name), count++; else if (col->type == GLP_LO) xfprintf(fp, " %s >= %.*g\n", name, DBL_DIG, col->lb), count++; else if (col->type == GLP_UP) xfprintf(fp, " -Inf <= %s <= %.*g\n", name, DBL_DIG, col->ub), count++; else if (col->type == GLP_DB) xfprintf(fp, " %.*g <= %s <= %.*g\n", DBL_DIG, col->lb, name, DBL_DIG, col->ub), count++; else if (col->type == GLP_FX) xfprintf(fp, " %s = %.*g\n", name, DBL_DIG, col->lb), count++; else xassert(col != col); } if (flag) xfprintf(fp, "\n"), count++; /* write the integer section */ flag = 0; for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->kind == GLP_CV) continue; xassert(col->kind == GLP_IV); if (!flag) xfprintf(fp, "Generals\n"), flag = 1, count++; xfprintf(fp, " %s\n", col_name(csa, j, name)), count++; } if (flag) xfprintf(fp, "\n"), count++; skip: /* write the end keyword */ xfprintf(fp, "End\n"), count++; xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } /* problem data has been successfully written */ xprintf("%d lines were written\n", count); ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /* eof */ sources_5316/external/glpk/glpnpp.h0000644000176700017670000004331611401660400016152 0ustar paulpaul/* glpnpp.h (LP/MIP preprocessor) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPNPP_H #define GLPNPP_H #include "glpapi.h" typedef struct NPP NPP; typedef struct NPPROW NPPROW; typedef struct NPPCOL NPPCOL; typedef struct NPPAIJ NPPAIJ; typedef struct NPPTSE NPPTSE; typedef struct NPPLFE NPPLFE; struct NPP { /* LP/MIP preprocessor workspace */ /*--------------------------------------------------------------*/ /* original problem segment */ int orig_dir; /* optimization direction flag: GLP_MIN - minimization GLP_MAX - maximization */ int orig_m; /* number of rows */ int orig_n; /* number of columns */ int orig_nnz; /* number of non-zero constraint coefficients */ /*--------------------------------------------------------------*/ /* transformed problem segment (always minimization) */ DMP *pool; /* memory pool to store problem components */ char *name; /* problem name (1 to 255 chars); NULL means no name is assigned to the problem */ char *obj; /* objective function name (1 to 255 chars); NULL means no name is assigned to the objective function */ double c0; /* constant term of the objective function */ int nrows; /* number of rows introduced into the problem; this count increases by one every time a new row is added and never decreases; thus, actual number of rows may be less than nrows due to row deletions */ int ncols; /* number of columns introduced into the problem; this count increases by one every time a new column is added and never decreases; thus, actual number of column may be less than ncols due to column deletions */ NPPROW *r_head; /* pointer to the beginning of the row list */ NPPROW *r_tail; /* pointer to the end of the row list */ NPPCOL *c_head; /* pointer to the beginning of the column list */ NPPCOL *c_tail; /* pointer to the end of the column list */ /*--------------------------------------------------------------*/ /* transformation history */ DMP *stack; /* memory pool to store transformation entries */ NPPTSE *top; /* pointer to most recent transformation entry */ #if 0 /* 16/XII-2009 */ int count[1+25]; /* transformation statistics */ #endif /*--------------------------------------------------------------*/ /* resultant (preprocessed) problem segment */ int m; /* number of rows */ int n; /* number of columns */ int nnz; /* number of non-zero constraint coefficients */ int *row_ref; /* int row_ref[1+m]; */ /* row_ref[i], 1 <= i <= m, is the reference number assigned to a row, which is i-th row of the resultant problem */ int *col_ref; /* int col_ref[1+n]; */ /* col_ref[j], 1 <= j <= n, is the reference number assigned to a column, which is j-th column of the resultant problem */ /*--------------------------------------------------------------*/ /* recovered solution segment */ int sol; /* solution indicator: GLP_SOL - basic solution GLP_IPT - interior-point solution GLP_MIP - mixed integer solution */ int scaling; /* scaling option: GLP_OFF - scaling is disabled GLP_ON - scaling is enabled */ int p_stat; /* status of primal basic solution: GLP_UNDEF - primal solution is undefined GLP_FEAS - primal solution is feasible GLP_INFEAS - primal solution is infeasible GLP_NOFEAS - no primal feasible solution exists */ int d_stat; /* status of dual basic solution: GLP_UNDEF - dual solution is undefined GLP_FEAS - dual solution is feasible GLP_INFEAS - dual solution is infeasible GLP_NOFEAS - no dual feasible solution exists */ int t_stat; /* status of interior-point solution: GLP_UNDEF - interior solution is undefined GLP_OPT - interior solution is optimal */ int i_stat; /* status of mixed integer solution: GLP_UNDEF - integer solution is undefined GLP_OPT - integer solution is optimal GLP_FEAS - integer solution is feasible GLP_NOFEAS - no integer solution exists */ char *r_stat; /* char r_stat[1+nrows]; */ /* r_stat[i], 1 <= i <= nrows, is status of i-th row: GLP_BS - inactive constraint GLP_NL - active constraint on lower bound GLP_NU - active constraint on upper bound GLP_NF - active free row GLP_NS - active equality constraint */ char *c_stat; /* char c_stat[1+nrows]; */ /* c_stat[j], 1 <= j <= nrows, is status of j-th column: GLP_BS - basic variable GLP_NL - non-basic variable on lower bound GLP_NU - non-basic variable on upper bound GLP_NF - non-basic free variable GLP_NS - non-basic fixed variable */ double *r_pi; /* double r_pi[1+nrows]; */ /* r_pi[i], 1 <= i <= nrows, is Lagrange multiplier (dual value) for i-th row (constraint) */ double *c_value; /* double c_value[1+ncols]; */ /* c_value[j], 1 <= j <= ncols, is primal value of j-th column (structural variable) */ }; struct NPPROW { /* row (constraint) */ int i; /* reference number assigned to the row, 1 <= i <= nrows */ char *name; /* row name (1 to 255 chars); NULL means no name is assigned to the row */ double lb; /* lower bound; -DBL_MAX means the row has no lower bound */ double ub; /* upper bound; +DBL_MAX means the row has no upper bound */ NPPAIJ *ptr; /* pointer to the linked list of constraint coefficients */ int temp; /* working field used by preprocessor routines */ NPPROW *prev; /* pointer to previous row in the row list */ NPPROW *next; /* pointer to next row in the row list */ }; struct NPPCOL { /* column (variable) */ int j; /* reference number assigned to the column, 1 <= j <= ncols */ char *name; /* column name (1 to 255 chars); NULL means no name is assigned to the column */ char is_int; /* 0 means continuous variable; 1 means integer variable */ double lb; /* lower bound; -DBL_MAX means the column has no lower bound */ double ub; /* upper bound; +DBL_MAX means the column has no upper bound */ double coef; /* objective coefficient */ NPPAIJ *ptr; /* pointer to the linked list of constraint coefficients */ int temp; /* working field used by preprocessor routines */ #if 1 /* 28/XII-2009 */ union { double ll; /* implied column lower bound */ int pos; /* vertex ordinal number corresponding to this binary column in the conflict graph (0, if the vertex does not exist) */ } ll; union { double uu; /* implied column upper bound */ int neg; /* vertex ordinal number corresponding to complement of this binary column in the conflict graph (0, if the vertex does not exist) */ } uu; #endif NPPCOL *prev; /* pointer to previous column in the column list */ NPPCOL *next; /* pointer to next column in the column list */ }; struct NPPAIJ { /* constraint coefficient */ NPPROW *row; /* pointer to corresponding row */ NPPCOL *col; /* pointer to corresponding column */ double val; /* (non-zero) coefficient value */ NPPAIJ *r_prev; /* pointer to previous coefficient in the same row */ NPPAIJ *r_next; /* pointer to next coefficient in the same row */ NPPAIJ *c_prev; /* pointer to previous coefficient in the same column */ NPPAIJ *c_next; /* pointer to next coefficient in the same column */ }; struct NPPTSE { /* transformation stack entry */ int (*func)(NPP *npp, void *info); /* pointer to routine performing back transformation */ void *info; /* pointer to specific info (depends on the transformation) */ NPPTSE *link; /* pointer to another entry created *before* this entry */ }; struct NPPLFE { /* linear form element */ int ref; /* row/column reference number */ double val; /* (non-zero) coefficient value */ NPPLFE *next; /* pointer to another element */ }; #define npp_create_wksp _glp_npp_create_wksp NPP *npp_create_wksp(void); /* create LP/MIP preprocessor workspace */ #define npp_insert_row _glp_npp_insert_row void npp_insert_row(NPP *npp, NPPROW *row, int where); /* insert row to the row list */ #define npp_remove_row _glp_npp_remove_row void npp_remove_row(NPP *npp, NPPROW *row); /* remove row from the row list */ #define npp_activate_row _glp_npp_activate_row void npp_activate_row(NPP *npp, NPPROW *row); /* make row active */ #define npp_deactivate_row _glp_npp_deactivate_row void npp_deactivate_row(NPP *npp, NPPROW *row); /* make row inactive */ #define npp_insert_col _glp_npp_insert_col void npp_insert_col(NPP *npp, NPPCOL *col, int where); /* insert column to the column list */ #define npp_remove_col _glp_npp_remove_col void npp_remove_col(NPP *npp, NPPCOL *col); /* remove column from the column list */ #define npp_activate_col _glp_npp_activate_col void npp_activate_col(NPP *npp, NPPCOL *col); /* make column active */ #define npp_deactivate_col _glp_npp_deactivate_col void npp_deactivate_col(NPP *npp, NPPCOL *col); /* make column inactive */ #define npp_add_row _glp_npp_add_row NPPROW *npp_add_row(NPP *npp); /* add new row to the current problem */ #define npp_add_col _glp_npp_add_col NPPCOL *npp_add_col(NPP *npp); /* add new column to the current problem */ #define npp_add_aij _glp_npp_add_aij NPPAIJ *npp_add_aij(NPP *npp, NPPROW *row, NPPCOL *col, double val); /* add new element to the constraint matrix */ #define npp_row_nnz _glp_npp_row_nnz int npp_row_nnz(NPP *npp, NPPROW *row); /* count number of non-zero coefficients in row */ #define npp_col_nnz _glp_npp_col_nnz int npp_col_nnz(NPP *npp, NPPCOL *col); /* count number of non-zero coefficients in column */ #define npp_push_tse _glp_npp_push_tse void *npp_push_tse(NPP *npp, int (*func)(NPP *npp, void *info), int size); /* push new entry to the transformation stack */ #define npp_erase_row _glp_npp_erase_row void npp_erase_row(NPP *npp, NPPROW *row); /* erase row content to make it empty */ #define npp_del_row _glp_npp_del_row void npp_del_row(NPP *npp, NPPROW *row); /* remove row from the current problem */ #define npp_del_col _glp_npp_del_col void npp_del_col(NPP *npp, NPPCOL *col); /* remove column from the current problem */ #define npp_del_aij _glp_npp_del_aij void npp_del_aij(NPP *npp, NPPAIJ *aij); /* remove element from the constraint matrix */ #define npp_load_prob _glp_npp_load_prob void npp_load_prob(NPP *npp, glp_prob *orig, int names, int sol, int scaling); /* load original problem into the preprocessor workspace */ #define npp_build_prob _glp_npp_build_prob void npp_build_prob(NPP *npp, glp_prob *prob); /* build resultant (preprocessed) problem */ #define npp_postprocess _glp_npp_postprocess void npp_postprocess(NPP *npp, glp_prob *prob); /* postprocess solution from the resultant problem */ #define npp_unload_sol _glp_npp_unload_sol void npp_unload_sol(NPP *npp, glp_prob *orig); /* store solution to the original problem */ #define npp_delete_wksp _glp_npp_delete_wksp void npp_delete_wksp(NPP *npp); /* delete LP/MIP preprocessor workspace */ #define npp_error() #define npp_free_row _glp_npp_free_row void npp_free_row(NPP *npp, NPPROW *p); /* process free (unbounded) row */ #define npp_geq_row _glp_npp_geq_row void npp_geq_row(NPP *npp, NPPROW *p); /* process row of 'not less than' type */ #define npp_leq_row _glp_npp_leq_row void npp_leq_row(NPP *npp, NPPROW *p); /* process row of 'not greater than' type */ #define npp_free_col _glp_npp_free_col void npp_free_col(NPP *npp, NPPCOL *q); /* process free (unbounded) column */ #define npp_lbnd_col _glp_npp_lbnd_col void npp_lbnd_col(NPP *npp, NPPCOL *q); /* process column with (non-zero) lower bound */ #define npp_ubnd_col _glp_npp_ubnd_col void npp_ubnd_col(NPP *npp, NPPCOL *q); /* process column with upper bound */ #define npp_dbnd_col _glp_npp_dbnd_col void npp_dbnd_col(NPP *npp, NPPCOL *q); /* process non-negative column with upper bound */ #define npp_fixed_col _glp_npp_fixed_col void npp_fixed_col(NPP *npp, NPPCOL *q); /* process fixed column */ #define npp_make_equality _glp_npp_make_equality int npp_make_equality(NPP *npp, NPPROW *p); /* process row with almost identical bounds */ #define npp_make_fixed _glp_npp_make_fixed int npp_make_fixed(NPP *npp, NPPCOL *q); /* process column with almost identical bounds */ #define npp_empty_row _glp_npp_empty_row int npp_empty_row(NPP *npp, NPPROW *p); /* process empty row */ #define npp_empty_col _glp_npp_empty_col int npp_empty_col(NPP *npp, NPPCOL *q); /* process empty column */ #define npp_implied_value _glp_npp_implied_value int npp_implied_value(NPP *npp, NPPCOL *q, double s); /* process implied column value */ #define npp_eq_singlet _glp_npp_eq_singlet int npp_eq_singlet(NPP *npp, NPPROW *p); /* process row singleton (equality constraint) */ #define npp_implied_lower _glp_npp_implied_lower int npp_implied_lower(NPP *npp, NPPCOL *q, double l); /* process implied column lower bound */ #define npp_implied_upper _glp_npp_implied_upper int npp_implied_upper(NPP *npp, NPPCOL *q, double u); /* process implied upper bound of column */ #define npp_ineq_singlet _glp_npp_ineq_singlet int npp_ineq_singlet(NPP *npp, NPPROW *p); /* process row singleton (inequality constraint) */ #define npp_implied_slack _glp_npp_implied_slack void npp_implied_slack(NPP *npp, NPPCOL *q); /* process column singleton (implied slack variable) */ #define npp_implied_free _glp_npp_implied_free int npp_implied_free(NPP *npp, NPPCOL *q); /* process column singleton (implied free variable) */ #define npp_eq_doublet _glp_npp_eq_doublet NPPCOL *npp_eq_doublet(NPP *npp, NPPROW *p); /* process row doubleton (equality constraint) */ #define npp_forcing_row _glp_npp_forcing_row int npp_forcing_row(NPP *npp, NPPROW *p, int at); /* process forcing row */ #define npp_analyze_row _glp_npp_analyze_row int npp_analyze_row(NPP *npp, NPPROW *p); /* perform general row analysis */ #define npp_inactive_bound _glp_npp_inactive_bound void npp_inactive_bound(NPP *npp, NPPROW *p, int which); /* remove row lower/upper inactive bound */ #define npp_implied_bounds _glp_npp_implied_bounds void npp_implied_bounds(NPP *npp, NPPROW *p); /* determine implied column bounds */ #define npp_binarize_prob _glp_npp_binarize_prob int npp_binarize_prob(NPP *npp); /* binarize MIP problem */ #define npp_is_packing _glp_npp_is_packing int npp_is_packing(NPP *npp, NPPROW *row); /* test if constraint is packing inequality */ #define npp_hidden_packing _glp_npp_hidden_packing int npp_hidden_packing(NPP *npp, NPPROW *row); /* identify hidden packing inequality */ #define npp_implied_packing _glp_npp_implied_packing int npp_implied_packing(NPP *npp, NPPROW *row, int which, NPPCOL *var[], char set[]); /* identify implied packing inequality */ #define npp_is_covering _glp_npp_is_covering int npp_is_covering(NPP *npp, NPPROW *row); /* test if constraint is covering inequality */ #define npp_hidden_covering _glp_npp_hidden_covering int npp_hidden_covering(NPP *npp, NPPROW *row); /* identify hidden covering inequality */ #define npp_is_partitioning _glp_npp_is_partitioning int npp_is_partitioning(NPP *npp, NPPROW *row); /* test if constraint is partitioning equality */ #define npp_reduce_ineq_coef _glp_npp_reduce_ineq_coef int npp_reduce_ineq_coef(NPP *npp, NPPROW *row); /* reduce inequality constraint coefficients */ #define npp_clean_prob _glp_npp_clean_prob void npp_clean_prob(NPP *npp); /* perform initial LP/MIP processing */ #define npp_process_row _glp_npp_process_row int npp_process_row(NPP *npp, NPPROW *row, int hard); /* perform basic row processing */ #define npp_improve_bounds _glp_npp_improve_bounds int npp_improve_bounds(NPP *npp, NPPROW *row, int flag); /* improve current column bounds */ #define npp_process_col _glp_npp_process_col int npp_process_col(NPP *npp, NPPCOL *col); /* perform basic column processing */ #define npp_process_prob _glp_npp_process_prob int npp_process_prob(NPP *npp, int hard); /* perform basic LP/MIP processing */ #define npp_simplex _glp_npp_simplex int npp_simplex(NPP *npp, const glp_smcp *parm); /* process LP prior to applying primal/dual simplex method */ #define npp_integer _glp_npp_integer int npp_integer(NPP *npp, const glp_iocp *parm); /* process MIP prior to applying branch-and-bound method */ #endif /* eof */ sources_5316/external/glpk/glpapi04.c0000644000176700017670000001102411401660400016254 0ustar paulpaul/* glpapi04.c (problem scaling routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_set_rii - set (change) row scale factor * * SYNOPSIS * * void glp_set_rii(glp_prob *lp, int i, double rii); * * DESCRIPTION * * The routine glp_set_rii sets (changes) the scale factor r[i,i] for * i-th row of the specified problem object. */ void glp_set_rii(glp_prob *lp, int i, double rii) { if (!(1 <= i && i <= lp->m)) xerror("glp_set_rii: i = %d; row number out of range\n", i); if (rii <= 0.0) xerror("glp_set_rii: i = %d; rii = %g; invalid scale factor\n", i, rii); if (lp->valid && lp->row[i]->rii != rii) { GLPAIJ *aij; for (aij = lp->row[i]->ptr; aij != NULL; aij = aij->r_next) { if (aij->col->stat == GLP_BS) { /* invalidate the basis factorization */ lp->valid = 0; break; } } } lp->row[i]->rii = rii; return; } /*********************************************************************** * NAME * * glp_set sjj - set (change) column scale factor * * SYNOPSIS * * void glp_set_sjj(glp_prob *lp, int j, double sjj); * * DESCRIPTION * * The routine glp_set_sjj sets (changes) the scale factor s[j,j] for * j-th column of the specified problem object. */ void glp_set_sjj(glp_prob *lp, int j, double sjj) { if (!(1 <= j && j <= lp->n)) xerror("glp_set_sjj: j = %d; column number out of range\n", j); if (sjj <= 0.0) xerror("glp_set_sjj: j = %d; sjj = %g; invalid scale factor\n", j, sjj); if (lp->valid && lp->col[j]->sjj != sjj && lp->col[j]->stat == GLP_BS) { /* invalidate the basis factorization */ lp->valid = 0; } lp->col[j]->sjj = sjj; return; } /*********************************************************************** * NAME * * glp_get_rii - retrieve row scale factor * * SYNOPSIS * * double glp_get_rii(glp_prob *lp, int i); * * RETURNS * * The routine glp_get_rii returns current scale factor r[i,i] for i-th * row of the specified problem object. */ double glp_get_rii(glp_prob *lp, int i) { if (!(1 <= i && i <= lp->m)) xerror("glp_get_rii: i = %d; row number out of range\n", i); return lp->row[i]->rii; } /*********************************************************************** * NAME * * glp_get_sjj - retrieve column scale factor * * SYNOPSIS * * double glp_get_sjj(glp_prob *lp, int j); * * RETURNS * * The routine glp_get_sjj returns current scale factor s[j,j] for j-th * column of the specified problem object. */ double glp_get_sjj(glp_prob *lp, int j) { if (!(1 <= j && j <= lp->n)) xerror("glp_get_sjj: j = %d; column number out of range\n", j); return lp->col[j]->sjj; } /*********************************************************************** * NAME * * glp_unscale_prob - unscale problem data * * SYNOPSIS * * void glp_unscale_prob(glp_prob *lp); * * DESCRIPTION * * The routine glp_unscale_prob performs unscaling of problem data for * the specified problem object. * * "Unscaling" means replacing the current scaling matrices R and S by * unity matrices that cancels the scaling effect. */ void glp_unscale_prob(glp_prob *lp) { int m = glp_get_num_rows(lp); int n = glp_get_num_cols(lp); int i, j; for (i = 1; i <= m; i++) glp_set_rii(lp, i, 1.0); for (j = 1; j <= n; j++) glp_set_sjj(lp, j, 1.0); return; } /* eof */ sources_5316/external/glpk/glpmpl.h0000644000176700017670000025715711411454506016170 0ustar paulpaul/* glpmpl.h (GNU MathProg translator) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPMPL_H #define GLPMPL_H #include "glpavl.h" #include "glprng.h" typedef struct MPL MPL; typedef char STRING; typedef struct SYMBOL SYMBOL; typedef struct TUPLE TUPLE; typedef struct ARRAY ELEMSET; typedef struct ELEMVAR ELEMVAR; typedef struct FORMULA FORMULA; typedef struct ELEMCON ELEMCON; typedef union VALUE VALUE; typedef struct ARRAY ARRAY; typedef struct MEMBER MEMBER; #if 1 /* many C compilers have DOMAIN declared in :( */ #undef DOMAIN #define DOMAIN DOMAIN1 #endif typedef struct DOMAIN DOMAIN; typedef struct DOMAIN_BLOCK DOMAIN_BLOCK; typedef struct DOMAIN_SLOT DOMAIN_SLOT; typedef struct SET SET; typedef struct WITHIN WITHIN; typedef struct GADGET GADGET; typedef struct PARAMETER PARAMETER; typedef struct CONDITION CONDITION; typedef struct VARIABLE VARIABLE; typedef struct CONSTRAINT CONSTRAINT; typedef struct TABLE TABLE; typedef struct TABARG TABARG; typedef struct TABFLD TABFLD; typedef struct TABIN TABIN; typedef struct TABOUT TABOUT; typedef struct TABDCA TABDCA; typedef union OPERANDS OPERANDS; typedef struct ARG_LIST ARG_LIST; typedef struct CODE CODE; typedef struct CHECK CHECK; typedef struct DISPLAY DISPLAY; typedef struct DISPLAY1 DISPLAY1; typedef struct PRINTF PRINTF; typedef struct PRINTF1 PRINTF1; typedef struct FOR FOR; typedef struct STATEMENT STATEMENT; typedef struct TUPLE SLICE; /**********************************************************************/ /* * * TRANSLATOR DATABASE * * */ /**********************************************************************/ #define A_BINARY 101 /* something binary */ #define A_CHECK 102 /* check statement */ #define A_CONSTRAINT 103 /* model constraint */ #define A_DISPLAY 104 /* display statement */ #define A_ELEMCON 105 /* elemental constraint/objective */ #define A_ELEMSET 106 /* elemental set */ #define A_ELEMVAR 107 /* elemental variable */ #define A_EXPRESSION 108 /* expression */ #define A_FOR 109 /* for statement */ #define A_FORMULA 110 /* formula */ #define A_INDEX 111 /* dummy index */ #define A_INPUT 112 /* input table */ #define A_INTEGER 113 /* something integer */ #define A_LOGICAL 114 /* something logical */ #define A_MAXIMIZE 115 /* objective has to be maximized */ #define A_MINIMIZE 116 /* objective has to be minimized */ #define A_NONE 117 /* nothing */ #define A_NUMERIC 118 /* something numeric */ #define A_OUTPUT 119 /* output table */ #define A_PARAMETER 120 /* model parameter */ #define A_PRINTF 121 /* printf statement */ #define A_SET 122 /* model set */ #define A_SOLVE 123 /* solve statement */ #define A_SYMBOLIC 124 /* something symbolic */ #define A_TABLE 125 /* data table */ #define A_TUPLE 126 /* n-tuple */ #define A_VARIABLE 127 /* model variable */ #define MAX_LENGTH 100 /* maximal length of any symbolic value (this includes symbolic names, numeric and string literals, and all symbolic values that may appear during the evaluation phase) */ #define CONTEXT_SIZE 60 /* size of the context queue, in characters */ #define OUTBUF_SIZE 1024 /* size of the output buffer, in characters */ struct MPL { /* translator database */ /*--------------------------------------------------------------*/ /* scanning segment */ int line; /* number of the current text line */ int c; /* the current character or EOF */ int token; /* the current token: */ #define T_EOF 201 /* end of file */ #define T_NAME 202 /* symbolic name (model section only) */ #define T_SYMBOL 203 /* symbol (data section only) */ #define T_NUMBER 204 /* numeric literal */ #define T_STRING 205 /* string literal */ #define T_AND 206 /* and && */ #define T_BY 207 /* by */ #define T_CROSS 208 /* cross */ #define T_DIFF 209 /* diff */ #define T_DIV 210 /* div */ #define T_ELSE 211 /* else */ #define T_IF 212 /* if */ #define T_IN 213 /* in */ #define T_INFINITY 214 /* Infinity */ #define T_INTER 215 /* inter */ #define T_LESS 216 /* less */ #define T_MOD 217 /* mod */ #define T_NOT 218 /* not ! */ #define T_OR 219 /* or || */ #define T_SPTP 220 /* s.t. */ #define T_SYMDIFF 221 /* symdiff */ #define T_THEN 222 /* then */ #define T_UNION 223 /* union */ #define T_WITHIN 224 /* within */ #define T_PLUS 225 /* + */ #define T_MINUS 226 /* - */ #define T_ASTERISK 227 /* * */ #define T_SLASH 228 /* / */ #define T_POWER 229 /* ^ ** */ #define T_LT 230 /* < */ #define T_LE 231 /* <= */ #define T_EQ 232 /* = == */ #define T_GE 233 /* >= */ #define T_GT 234 /* > */ #define T_NE 235 /* <> != */ #define T_CONCAT 236 /* & */ #define T_BAR 237 /* | */ #define T_POINT 238 /* . */ #define T_COMMA 239 /* , */ #define T_COLON 240 /* : */ #define T_SEMICOLON 241 /* ; */ #define T_ASSIGN 242 /* := */ #define T_DOTS 243 /* .. */ #define T_LEFT 244 /* ( */ #define T_RIGHT 245 /* ) */ #define T_LBRACKET 246 /* [ */ #define T_RBRACKET 247 /* ] */ #define T_LBRACE 248 /* { */ #define T_RBRACE 249 /* } */ #define T_APPEND 250 /* >> */ #define T_TILDE 251 /* ~ */ #define T_INPUT 252 /* <- */ int imlen; /* length of the current token */ char *image; /* char image[MAX_LENGTH+1]; */ /* image of the current token */ double value; /* value of the current token (for T_NUMBER only) */ int b_token; /* the previous token */ int b_imlen; /* length of the previous token */ char *b_image; /* char b_image[MAX_LENGTH+1]; */ /* image of the previous token */ double b_value; /* value of the previous token (if token is T_NUMBER) */ int f_dots; /* if this flag is set, the next token should be recognized as T_DOTS, not as T_POINT */ int f_scan; /* if this flag is set, the next token is already scanned */ int f_token; /* the next token */ int f_imlen; /* length of the next token */ char *f_image; /* char f_image[MAX_LENGTH+1]; */ /* image of the next token */ double f_value; /* value of the next token (if token is T_NUMBER) */ char *context; /* char context[CONTEXT_SIZE]; */ /* context circular queue (not null-terminated!) */ int c_ptr; /* pointer to the current position in the context queue */ int flag_d; /* if this flag is set, the data section is being processed */ /*--------------------------------------------------------------*/ /* translating segment */ DMP *pool; /* memory pool used to allocate all data instances created during the translation phase */ AVL *tree; /* symbolic name table: node.type = A_INDEX => node.link -> DOMAIN_SLOT node.type = A_SET => node.link -> SET node.type = A_PARAMETER => node.link -> PARAMETER node.type = A_VARIABLE => node.link -> VARIABLE node.type = A_CONSTRANT => node.link -> CONSTRAINT */ STATEMENT *model; /* linked list of model statements in the original order */ int flag_x; /* if this flag is set, the current token being left parenthesis begins a slice that allows recognizing any undeclared symbolic names as dummy indices; this flag is automatically reset once the next token has been scanned */ int as_within; /* the warning "in understood as within" has been issued */ int as_in; /* the warning "within understood as in" has been issued */ int as_binary; /* the warning "logical understood as binary" has been issued */ int flag_s; /* if this flag is set, the solve statement has been parsed */ /*--------------------------------------------------------------*/ /* common segment */ DMP *strings; /* memory pool to allocate STRING data structures */ DMP *symbols; /* memory pool to allocate SYMBOL data structures */ DMP *tuples; /* memory pool to allocate TUPLE data structures */ DMP *arrays; /* memory pool to allocate ARRAY data structures */ DMP *members; /* memory pool to allocate MEMBER data structures */ DMP *elemvars; /* memory pool to allocate ELEMVAR data structures */ DMP *formulae; /* memory pool to allocate FORMULA data structures */ DMP *elemcons; /* memory pool to allocate ELEMCON data structures */ ARRAY *a_list; /* linked list of all arrays in the database */ char *sym_buf; /* char sym_buf[255+1]; */ /* working buffer used by the routine format_symbol */ char *tup_buf; /* char tup_buf[255+1]; */ /* working buffer used by the routine format_tuple */ /*--------------------------------------------------------------*/ /* generating/postsolving segment */ RNG *rand; /* pseudo-random number generator */ int flag_p; /* if this flag is set, the postsolving phase is in effect */ STATEMENT *stmt; /* model statement being currently executed */ TABDCA *dca; /* pointer to table driver communication area for table statement currently executed */ int m; /* number of rows in the problem, m >= 0 */ int n; /* number of columns in the problem, n >= 0 */ ELEMCON **row; /* ELEMCON *row[1+m]; */ /* row[0] is not used; row[i] is elemental constraint or objective, which corresponds to i-th row of the problem, 1 <= i <= m */ ELEMVAR **col; /* ELEMVAR *col[1+n]; */ /* col[0] is not used; col[j] is elemental variable, which corresponds to j-th column of the problem, 1 <= j <= n */ /*--------------------------------------------------------------*/ /* input/output segment */ XFILE *in_fp; /* stream assigned to the input text file */ char *in_file; /* name of the input text file */ XFILE *out_fp; /* stream assigned to the output text file used to write all data produced by display and printf statements; NULL means the data should be sent to stdout via the routine xprintf */ char *out_file; /* name of the output text file */ #if 0 /* 08/XI-2009 */ char *out_buf; /* char out_buf[OUTBUF_SIZE] */ /* buffer to accumulate output data */ int out_cnt; /* count of data bytes stored in the output buffer */ #endif XFILE *prt_fp; /* stream assigned to the print text file; may be NULL */ char *prt_file; /* name of the output print file */ /*--------------------------------------------------------------*/ /* solver interface segment */ jmp_buf jump; /* jump address for non-local go to in case of error */ int phase; /* phase of processing: 0 - database is being or has been initialized 1 - model section is being or has been read 2 - data section is being or has been read 3 - model is being or has been generated/postsolved 4 - model processing error has occurred */ char *mod_file; /* name of the input text file, which contains model section */ char *mpl_buf; /* char mpl_buf[255+1]; */ /* working buffer used by some interface routines */ }; /**********************************************************************/ /* * * PROCESSING MODEL SECTION * * */ /**********************************************************************/ #define alloc(type) ((type *)dmp_get_atomv(mpl->pool, sizeof(type))) /* allocate atom of given type */ #define enter_context _glp_mpl_enter_context void enter_context(MPL *mpl); /* enter current token into context queue */ #define print_context _glp_mpl_print_context void print_context(MPL *mpl); /* print current content of context queue */ #define get_char _glp_mpl_get_char void get_char(MPL *mpl); /* scan next character from input text file */ #define append_char _glp_mpl_append_char void append_char(MPL *mpl); /* append character to current token */ #define get_token _glp_mpl_get_token void get_token(MPL *mpl); /* scan next token from input text file */ #define unget_token _glp_mpl_unget_token void unget_token(MPL *mpl); /* return current token back to input stream */ #define is_keyword _glp_mpl_is_keyword int is_keyword(MPL *mpl, char *keyword); /* check if current token is given non-reserved keyword */ #define is_reserved _glp_mpl_is_reserved int is_reserved(MPL *mpl); /* check if current token is reserved keyword */ #define make_code _glp_mpl_make_code CODE *make_code(MPL *mpl, int op, OPERANDS *arg, int type, int dim); /* generate pseudo-code (basic routine) */ #define make_unary _glp_mpl_make_unary CODE *make_unary(MPL *mpl, int op, CODE *x, int type, int dim); /* generate pseudo-code for unary operation */ #define make_binary _glp_mpl_make_binary CODE *make_binary(MPL *mpl, int op, CODE *x, CODE *y, int type, int dim); /* generate pseudo-code for binary operation */ #define make_ternary _glp_mpl_make_ternary CODE *make_ternary(MPL *mpl, int op, CODE *x, CODE *y, CODE *z, int type, int dim); /* generate pseudo-code for ternary operation */ #define numeric_literal _glp_mpl_numeric_literal CODE *numeric_literal(MPL *mpl); /* parse reference to numeric literal */ #define string_literal _glp_mpl_string_literal CODE *string_literal(MPL *mpl); /* parse reference to string literal */ #define create_arg_list _glp_mpl_create_arg_list ARG_LIST *create_arg_list(MPL *mpl); /* create empty operands list */ #define expand_arg_list _glp_mpl_expand_arg_list ARG_LIST *expand_arg_list(MPL *mpl, ARG_LIST *list, CODE *x); /* append operand to operands list */ #define arg_list_len _glp_mpl_arg_list_len int arg_list_len(MPL *mpl, ARG_LIST *list); /* determine length of operands list */ #define subscript_list _glp_mpl_subscript_list ARG_LIST *subscript_list(MPL *mpl); /* parse subscript list */ #define object_reference _glp_mpl_object_reference CODE *object_reference(MPL *mpl); /* parse reference to named object */ #define numeric_argument _glp_mpl_numeric_argument CODE *numeric_argument(MPL *mpl, char *func); /* parse argument passed to built-in function */ #define symbolic_argument _glp_mpl_symbolic_argument CODE *symbolic_argument(MPL *mpl, char *func); #define elemset_argument _glp_mpl_elemset_argument CODE *elemset_argument(MPL *mpl, char *func); #define function_reference _glp_mpl_function_reference CODE *function_reference(MPL *mpl); /* parse reference to built-in function */ #define create_domain _glp_mpl_create_domain DOMAIN *create_domain(MPL *mpl); /* create empty domain */ #define create_block _glp_mpl_create_block DOMAIN_BLOCK *create_block(MPL *mpl); /* create empty domain block */ #define append_block _glp_mpl_append_block void append_block(MPL *mpl, DOMAIN *domain, DOMAIN_BLOCK *block); /* append domain block to specified domain */ #define append_slot _glp_mpl_append_slot DOMAIN_SLOT *append_slot(MPL *mpl, DOMAIN_BLOCK *block, char *name, CODE *code); /* create and append new slot to domain block */ #define expression_list _glp_mpl_expression_list CODE *expression_list(MPL *mpl); /* parse expression list */ #define literal_set _glp_mpl_literal_set CODE *literal_set(MPL *mpl, CODE *code); /* parse literal set */ #define indexing_expression _glp_mpl_indexing_expression DOMAIN *indexing_expression(MPL *mpl); /* parse indexing expression */ #define close_scope _glp_mpl_close_scope void close_scope(MPL *mpl, DOMAIN *domain); /* close scope of indexing expression */ #define iterated_expression _glp_mpl_iterated_expression CODE *iterated_expression(MPL *mpl); /* parse iterated expression */ #define domain_arity _glp_mpl_domain_arity int domain_arity(MPL *mpl, DOMAIN *domain); /* determine arity of domain */ #define set_expression _glp_mpl_set_expression CODE *set_expression(MPL *mpl); /* parse set expression */ #define branched_expression _glp_mpl_branched_expression CODE *branched_expression(MPL *mpl); /* parse conditional expression */ #define primary_expression _glp_mpl_primary_expression CODE *primary_expression(MPL *mpl); /* parse primary expression */ #define error_preceding _glp_mpl_error_preceding void error_preceding(MPL *mpl, char *opstr); /* raise error if preceding operand has wrong type */ #define error_following _glp_mpl_error_following void error_following(MPL *mpl, char *opstr); /* raise error if following operand has wrong type */ #define error_dimension _glp_mpl_error_dimension void error_dimension(MPL *mpl, char *opstr, int dim1, int dim2); /* raise error if operands have different dimension */ #define expression_0 _glp_mpl_expression_0 CODE *expression_0(MPL *mpl); /* parse expression of level 0 */ #define expression_1 _glp_mpl_expression_1 CODE *expression_1(MPL *mpl); /* parse expression of level 1 */ #define expression_2 _glp_mpl_expression_2 CODE *expression_2(MPL *mpl); /* parse expression of level 2 */ #define expression_3 _glp_mpl_expression_3 CODE *expression_3(MPL *mpl); /* parse expression of level 3 */ #define expression_4 _glp_mpl_expression_4 CODE *expression_4(MPL *mpl); /* parse expression of level 4 */ #define expression_5 _glp_mpl_expression_5 CODE *expression_5(MPL *mpl); /* parse expression of level 5 */ #define expression_6 _glp_mpl_expression_6 CODE *expression_6(MPL *mpl); /* parse expression of level 6 */ #define expression_7 _glp_mpl_expression_7 CODE *expression_7(MPL *mpl); /* parse expression of level 7 */ #define expression_8 _glp_mpl_expression_8 CODE *expression_8(MPL *mpl); /* parse expression of level 8 */ #define expression_9 _glp_mpl_expression_9 CODE *expression_9(MPL *mpl); /* parse expression of level 9 */ #define expression_10 _glp_mpl_expression_10 CODE *expression_10(MPL *mpl); /* parse expression of level 10 */ #define expression_11 _glp_mpl_expression_11 CODE *expression_11(MPL *mpl); /* parse expression of level 11 */ #define expression_12 _glp_mpl_expression_12 CODE *expression_12(MPL *mpl); /* parse expression of level 12 */ #define expression_13 _glp_mpl_expression_13 CODE *expression_13(MPL *mpl); /* parse expression of level 13 */ #define set_statement _glp_mpl_set_statement SET *set_statement(MPL *mpl); /* parse set statement */ #define parameter_statement _glp_mpl_parameter_statement PARAMETER *parameter_statement(MPL *mpl); /* parse parameter statement */ #define variable_statement _glp_mpl_variable_statement VARIABLE *variable_statement(MPL *mpl); /* parse variable statement */ #define constraint_statement _glp_mpl_constraint_statement CONSTRAINT *constraint_statement(MPL *mpl); /* parse constraint statement */ #define objective_statement _glp_mpl_objective_statement CONSTRAINT *objective_statement(MPL *mpl); /* parse objective statement */ #define table_statement _glp_mpl_table_statement TABLE *table_statement(MPL *mpl); /* parse table statement */ #define solve_statement _glp_mpl_solve_statement void *solve_statement(MPL *mpl); /* parse solve statement */ #define check_statement _glp_mpl_check_statement CHECK *check_statement(MPL *mpl); /* parse check statement */ #define display_statement _glp_mpl_display_statement DISPLAY *display_statement(MPL *mpl); /* parse display statement */ #define printf_statement _glp_mpl_printf_statement PRINTF *printf_statement(MPL *mpl); /* parse printf statement */ #define for_statement _glp_mpl_for_statement FOR *for_statement(MPL *mpl); /* parse for statement */ #define end_statement _glp_mpl_end_statement void end_statement(MPL *mpl); /* parse end statement */ #define simple_statement _glp_mpl_simple_statement STATEMENT *simple_statement(MPL *mpl, int spec); /* parse simple statement */ #define model_section _glp_mpl_model_section void model_section(MPL *mpl); /* parse model section */ /**********************************************************************/ /* * * PROCESSING DATA SECTION * * */ /**********************************************************************/ #if 2 + 2 == 5 struct SLICE /* see TUPLE */ { /* component of slice; the slice itself is associated with its first component; slices are similar to n-tuples with exception that some slice components (which are indicated by asterisks) don't refer to any symbols */ SYMBOL *sym; /* symbol, which this component refers to; can be NULL */ SLICE *next; /* the next component of slice */ }; #endif #define create_slice _glp_mpl_create_slice SLICE *create_slice(MPL *mpl); /* create slice */ #define expand_slice _glp_mpl_expand_slice SLICE *expand_slice ( MPL *mpl, SLICE *slice, /* destroyed */ SYMBOL *sym /* destroyed */ ); /* append new component to slice */ #define slice_dimen _glp_mpl_slice_dimen int slice_dimen ( MPL *mpl, SLICE *slice /* not changed */ ); /* determine dimension of slice */ #define slice_arity _glp_mpl_slice_arity int slice_arity ( MPL *mpl, SLICE *slice /* not changed */ ); /* determine arity of slice */ #define fake_slice _glp_mpl_fake_slice SLICE *fake_slice(MPL *mpl, int dim); /* create fake slice of all asterisks */ #define delete_slice _glp_mpl_delete_slice void delete_slice ( MPL *mpl, SLICE *slice /* destroyed */ ); /* delete slice */ #define is_number _glp_mpl_is_number int is_number(MPL *mpl); /* check if current token is number */ #define is_symbol _glp_mpl_is_symbol int is_symbol(MPL *mpl); /* check if current token is symbol */ #define is_literal _glp_mpl_is_literal int is_literal(MPL *mpl, char *literal); /* check if current token is given symbolic literal */ #define read_number _glp_mpl_read_number double read_number(MPL *mpl); /* read number */ #define read_symbol _glp_mpl_read_symbol SYMBOL *read_symbol(MPL *mpl); /* read symbol */ #define read_slice _glp_mpl_read_slice SLICE *read_slice ( MPL *mpl, char *name, /* not changed */ int dim ); /* read slice */ #define select_set _glp_mpl_select_set SET *select_set ( MPL *mpl, char *name /* not changed */ ); /* select set to saturate it with elemental sets */ #define simple_format _glp_mpl_simple_format void simple_format ( MPL *mpl, SET *set, /* not changed */ MEMBER *memb, /* modified */ SLICE *slice /* not changed */ ); /* read set data block in simple format */ #define matrix_format _glp_mpl_matrix_format void matrix_format ( MPL *mpl, SET *set, /* not changed */ MEMBER *memb, /* modified */ SLICE *slice, /* not changed */ int tr ); /* read set data block in matrix format */ #define set_data _glp_mpl_set_data void set_data(MPL *mpl); /* read set data */ #define select_parameter _glp_mpl_select_parameter PARAMETER *select_parameter ( MPL *mpl, char *name /* not changed */ ); /* select parameter to saturate it with data */ #define set_default _glp_mpl_set_default void set_default ( MPL *mpl, PARAMETER *par, /* not changed */ SYMBOL *altval /* destroyed */ ); /* set default parameter value */ #define read_value _glp_mpl_read_value MEMBER *read_value ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* destroyed */ ); /* read value and assign it to parameter member */ #define plain_format _glp_mpl_plain_format void plain_format ( MPL *mpl, PARAMETER *par, /* not changed */ SLICE *slice /* not changed */ ); /* read parameter data block in plain format */ #define tabular_format _glp_mpl_tabular_format void tabular_format ( MPL *mpl, PARAMETER *par, /* not changed */ SLICE *slice, /* not changed */ int tr ); /* read parameter data block in tabular format */ #define tabbing_format _glp_mpl_tabbing_format void tabbing_format ( MPL *mpl, SYMBOL *altval /* not changed */ ); /* read parameter data block in tabbing format */ #define parameter_data _glp_mpl_parameter_data void parameter_data(MPL *mpl); /* read parameter data */ #define data_section _glp_mpl_data_section void data_section(MPL *mpl); /* read data section */ /**********************************************************************/ /* * * FLOATING-POINT NUMBERS * * */ /**********************************************************************/ #define fp_add _glp_mpl_fp_add double fp_add(MPL *mpl, double x, double y); /* floating-point addition */ #define fp_sub _glp_mpl_fp_sub double fp_sub(MPL *mpl, double x, double y); /* floating-point subtraction */ #define fp_less _glp_mpl_fp_less double fp_less(MPL *mpl, double x, double y); /* floating-point non-negative subtraction */ #define fp_mul _glp_mpl_fp_mul double fp_mul(MPL *mpl, double x, double y); /* floating-point multiplication */ #define fp_div _glp_mpl_fp_div double fp_div(MPL *mpl, double x, double y); /* floating-point division */ #define fp_idiv _glp_mpl_fp_idiv double fp_idiv(MPL *mpl, double x, double y); /* floating-point quotient of exact division */ #define fp_mod _glp_mpl_fp_mod double fp_mod(MPL *mpl, double x, double y); /* floating-point remainder of exact division */ #define fp_power _glp_mpl_fp_power double fp_power(MPL *mpl, double x, double y); /* floating-point exponentiation (raise to power) */ #define fp_exp _glp_mpl_fp_exp double fp_exp(MPL *mpl, double x); /* floating-point base-e exponential */ #define fp_log _glp_mpl_fp_log double fp_log(MPL *mpl, double x); /* floating-point natural logarithm */ #define fp_log10 _glp_mpl_fp_log10 double fp_log10(MPL *mpl, double x); /* floating-point common (decimal) logarithm */ #define fp_sqrt _glp_mpl_fp_sqrt double fp_sqrt(MPL *mpl, double x); /* floating-point square root */ #define fp_sin _glp_mpl_fp_sin double fp_sin(MPL *mpl, double x); /* floating-point trigonometric sine */ #define fp_cos _glp_mpl_fp_cos double fp_cos(MPL *mpl, double x); /* floating-point trigonometric cosine */ #define fp_atan _glp_mpl_fp_atan double fp_atan(MPL *mpl, double x); /* floating-point trigonometric arctangent */ #define fp_atan2 _glp_mpl_fp_atan2 double fp_atan2(MPL *mpl, double y, double x); /* floating-point trigonometric arctangent */ #define fp_round _glp_mpl_fp_round double fp_round(MPL *mpl, double x, double n); /* round floating-point value to n fractional digits */ #define fp_trunc _glp_mpl_fp_trunc double fp_trunc(MPL *mpl, double x, double n); /* truncate floating-point value to n fractional digits */ /**********************************************************************/ /* * * PSEUDO-RANDOM NUMBER GENERATORS * * */ /**********************************************************************/ #define fp_irand224 _glp_mpl_fp_irand224 double fp_irand224(MPL *mpl); /* pseudo-random integer in the range [0, 2^24) */ #define fp_uniform01 _glp_mpl_fp_uniform01 double fp_uniform01(MPL *mpl); /* pseudo-random number in the range [0, 1) */ #define fp_uniform _glp_mpl_uniform double fp_uniform(MPL *mpl, double a, double b); /* pseudo-random number in the range [a, b) */ #define fp_normal01 _glp_mpl_fp_normal01 double fp_normal01(MPL *mpl); /* Gaussian random variate with mu = 0 and sigma = 1 */ #define fp_normal _glp_mpl_fp_normal double fp_normal(MPL *mpl, double mu, double sigma); /* Gaussian random variate with specified mu and sigma */ /**********************************************************************/ /* * * DATE/TIME * * */ /**********************************************************************/ #define fn_gmtime _glp_mpl_fn_gmtime double fn_gmtime(MPL *mpl); /* obtain the current calendar time (UTC) */ #define fn_str2time _glp_mpl_fn_str2time double fn_str2time(MPL *mpl, const char *str, const char *fmt); /* convert character string to the calendar time */ #define fn_time2str _glp_mpl_fn_time2str void fn_time2str(MPL *mpl, char *str, double t, const char *fmt); /* convert the calendar time to character string */ /**********************************************************************/ /* * * CHARACTER STRINGS * * */ /**********************************************************************/ #define create_string _glp_mpl_create_string STRING *create_string ( MPL *mpl, char buf[MAX_LENGTH+1] /* not changed */ ); /* create character string */ #define copy_string _glp_mpl_copy_string STRING *copy_string ( MPL *mpl, STRING *str /* not changed */ ); /* make copy of character string */ #define compare_strings _glp_mpl_compare_strings int compare_strings ( MPL *mpl, STRING *str1, /* not changed */ STRING *str2 /* not changed */ ); /* compare one character string with another */ #define fetch_string _glp_mpl_fetch_string char *fetch_string ( MPL *mpl, STRING *str, /* not changed */ char buf[MAX_LENGTH+1] /* modified */ ); /* extract content of character string */ #define delete_string _glp_mpl_delete_string void delete_string ( MPL *mpl, STRING *str /* destroyed */ ); /* delete character string */ /**********************************************************************/ /* * * SYMBOLS * * */ /**********************************************************************/ struct SYMBOL { /* symbol (numeric or abstract quantity) */ double num; /* numeric value of symbol (used only if str == NULL) */ STRING *str; /* abstract value of symbol (used only if str != NULL) */ }; #define create_symbol_num _glp_mpl_create_symbol_num SYMBOL *create_symbol_num(MPL *mpl, double num); /* create symbol of numeric type */ #define create_symbol_str _glp_mpl_create_symbol_str SYMBOL *create_symbol_str ( MPL *mpl, STRING *str /* destroyed */ ); /* create symbol of abstract type */ #define copy_symbol _glp_mpl_copy_symbol SYMBOL *copy_symbol ( MPL *mpl, SYMBOL *sym /* not changed */ ); /* make copy of symbol */ #define compare_symbols _glp_mpl_compare_symbols int compare_symbols ( MPL *mpl, SYMBOL *sym1, /* not changed */ SYMBOL *sym2 /* not changed */ ); /* compare one symbol with another */ #define delete_symbol _glp_mpl_delete_symbol void delete_symbol ( MPL *mpl, SYMBOL *sym /* destroyed */ ); /* delete symbol */ #define format_symbol _glp_mpl_format_symbol char *format_symbol ( MPL *mpl, SYMBOL *sym /* not changed */ ); /* format symbol for displaying or printing */ #define concat_symbols _glp_mpl_concat_symbols SYMBOL *concat_symbols ( MPL *mpl, SYMBOL *sym1, /* destroyed */ SYMBOL *sym2 /* destroyed */ ); /* concatenate one symbol with another */ /**********************************************************************/ /* * * N-TUPLES * * */ /**********************************************************************/ struct TUPLE { /* component of n-tuple; the n-tuple itself is associated with its first component; (note that 0-tuple has no components) */ SYMBOL *sym; /* symbol, which the component refers to; cannot be NULL */ TUPLE *next; /* the next component of n-tuple */ }; #define create_tuple _glp_mpl_create_tuple TUPLE *create_tuple(MPL *mpl); /* create n-tuple */ #define expand_tuple _glp_mpl_expand_tuple TUPLE *expand_tuple ( MPL *mpl, TUPLE *tuple, /* destroyed */ SYMBOL *sym /* destroyed */ ); /* append symbol to n-tuple */ #define tuple_dimen _glp_mpl_tuple_dimen int tuple_dimen ( MPL *mpl, TUPLE *tuple /* not changed */ ); /* determine dimension of n-tuple */ #define copy_tuple _glp_mpl_copy_tuple TUPLE *copy_tuple ( MPL *mpl, TUPLE *tuple /* not changed */ ); /* make copy of n-tuple */ #define compare_tuples _glp_mpl_compare_tuples int compare_tuples ( MPL *mpl, TUPLE *tuple1, /* not changed */ TUPLE *tuple2 /* not changed */ ); /* compare one n-tuple with another */ #define build_subtuple _glp_mpl_build_subtuple TUPLE *build_subtuple ( MPL *mpl, TUPLE *tuple, /* not changed */ int dim ); /* build subtuple of given n-tuple */ #define delete_tuple _glp_mpl_delete_tuple void delete_tuple ( MPL *mpl, TUPLE *tuple /* destroyed */ ); /* delete n-tuple */ #define format_tuple _glp_mpl_format_tuple char *format_tuple ( MPL *mpl, int c, TUPLE *tuple /* not changed */ ); /* format n-tuple for displaying or printing */ /**********************************************************************/ /* * * ELEMENTAL SETS * * */ /**********************************************************************/ #if 2 + 2 == 5 struct ELEMSET /* see ARRAY */ { /* elemental set of n-tuples; formally it is a "value" assigned to members of model sets (like numbers and symbols, which are values assigned to members of model parameters); note that a simple model set is not an elemental set, it is 0-dimensional array, the only member of which (if it exists) is assigned an elemental set */ #endif #define create_elemset _glp_mpl_create_elemset ELEMSET *create_elemset(MPL *mpl, int dim); /* create elemental set */ #define find_tuple _glp_mpl_find_tuple MEMBER *find_tuple ( MPL *mpl, ELEMSET *set, /* not changed */ TUPLE *tuple /* not changed */ ); /* check if elemental set contains given n-tuple */ #define add_tuple _glp_mpl_add_tuple MEMBER *add_tuple ( MPL *mpl, ELEMSET *set, /* modified */ TUPLE *tuple /* destroyed */ ); /* add new n-tuple to elemental set */ #define check_then_add _glp_mpl_check_then_add MEMBER *check_then_add ( MPL *mpl, ELEMSET *set, /* modified */ TUPLE *tuple /* destroyed */ ); /* check and add new n-tuple to elemental set */ #define copy_elemset _glp_mpl_copy_elemset ELEMSET *copy_elemset ( MPL *mpl, ELEMSET *set /* not changed */ ); /* make copy of elemental set */ #define delete_elemset _glp_mpl_delete_elemset void delete_elemset ( MPL *mpl, ELEMSET *set /* destroyed */ ); /* delete elemental set */ #define arelset_size _glp_mpl_arelset_size int arelset_size(MPL *mpl, double t0, double tf, double dt); /* compute size of "arithmetic" elemental set */ #define arelset_member _glp_mpl_arelset_member double arelset_member(MPL *mpl, double t0, double tf, double dt, int j); /* compute member of "arithmetic" elemental set */ #define create_arelset _glp_mpl_create_arelset ELEMSET *create_arelset(MPL *mpl, double t0, double tf, double dt); /* create "arithmetic" elemental set */ #define set_union _glp_mpl_set_union ELEMSET *set_union ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ); /* union of two elemental sets */ #define set_diff _glp_mpl_set_diff ELEMSET *set_diff ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ); /* difference between two elemental sets */ #define set_symdiff _glp_mpl_set_symdiff ELEMSET *set_symdiff ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ); /* symmetric difference between two elemental sets */ #define set_inter _glp_mpl_set_inter ELEMSET *set_inter ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ); /* intersection of two elemental sets */ #define set_cross _glp_mpl_set_cross ELEMSET *set_cross ( MPL *mpl, ELEMSET *X, /* destroyed */ ELEMSET *Y /* destroyed */ ); /* cross (Cartesian) product of two elemental sets */ /**********************************************************************/ /* * * ELEMENTAL VARIABLES * * */ /**********************************************************************/ struct ELEMVAR { /* elemental variable; formally it is a "value" assigned to members of model variables (like numbers and symbols, which are values assigned to members of model parameters) */ int j; /* LP column number assigned to this elemental variable */ VARIABLE *var; /* model variable, which contains this elemental variable */ MEMBER *memb; /* array member, which is assigned this elemental variable */ double lbnd; /* lower bound */ double ubnd; /* upper bound */ double temp; /* working quantity used in operations on linear forms; normally it contains floating-point zero */ #if 1 /* 15/V-2010 */ int stat; double prim, dual; /* solution components provided by the solver */ #endif }; /**********************************************************************/ /* * * LINEAR FORMS * * */ /**********************************************************************/ struct FORMULA { /* term of linear form c * x, where c is a coefficient, x is an elemental variable; the linear form itself is the sum of terms and is associated with its first term; (note that the linear form may be empty that means the sum is equal to zero) */ double coef; /* coefficient at elemental variable or constant term */ ELEMVAR *var; /* reference to elemental variable; NULL means constant term */ FORMULA *next; /* the next term of linear form */ }; #define constant_term _glp_mpl_constant_term FORMULA *constant_term(MPL *mpl, double coef); /* create constant term */ #define single_variable _glp_mpl_single_variable FORMULA *single_variable ( MPL *mpl, ELEMVAR *var /* referenced */ ); /* create single variable */ #define copy_formula _glp_mpl_copy_formula FORMULA *copy_formula ( MPL *mpl, FORMULA *form /* not changed */ ); /* make copy of linear form */ #define delete_formula _glp_mpl_delete_formula void delete_formula ( MPL *mpl, FORMULA *form /* destroyed */ ); /* delete linear form */ #define linear_comb _glp_mpl_linear_comb FORMULA *linear_comb ( MPL *mpl, double a, FORMULA *fx, /* destroyed */ double b, FORMULA *fy /* destroyed */ ); /* linear combination of two linear forms */ #define remove_constant _glp_mpl_remove_constant FORMULA *remove_constant ( MPL *mpl, FORMULA *form, /* destroyed */ double *coef /* modified */ ); /* remove constant term from linear form */ #define reduce_terms _glp_mpl_reduce_terms FORMULA *reduce_terms ( MPL *mpl, FORMULA *form /* destroyed */ ); /* reduce identical terms in linear form */ /**********************************************************************/ /* * * ELEMENTAL CONSTRAINTS * * */ /**********************************************************************/ struct ELEMCON { /* elemental constraint; formally it is a "value" assigned to members of model constraints (like numbers or symbols, which are values assigned to members of model parameters) */ int i; /* LP row number assigned to this elemental constraint */ CONSTRAINT *con; /* model constraint, which contains this elemental constraint */ MEMBER *memb; /* array member, which is assigned this elemental constraint */ FORMULA *form; /* linear form */ double lbnd; /* lower bound */ double ubnd; /* upper bound */ #if 1 /* 15/V-2010 */ int stat; double prim, dual; /* solution components provided by the solver */ #endif }; /**********************************************************************/ /* * * GENERIC VALUES * * */ /**********************************************************************/ union VALUE { /* generic value, which can be assigned to object member or be a result of evaluation of expression */ /* indicator that specifies the particular type of generic value is stored in the corresponding array or pseudo-code descriptor and can be one of the following: A_NONE - no value A_NUMERIC - floating-point number A_SYMBOLIC - symbol A_LOGICAL - logical value A_TUPLE - n-tuple A_ELEMSET - elemental set A_ELEMVAR - elemental variable A_FORMULA - linear form A_ELEMCON - elemental constraint */ void *none; /* null */ double num; /* value */ SYMBOL *sym; /* value */ int bit; /* value */ TUPLE *tuple; /* value */ ELEMSET *set; /* value */ ELEMVAR *var; /* reference */ FORMULA *form; /* value */ ELEMCON *con; /* reference */ }; #define delete_value _glp_mpl_delete_value void delete_value ( MPL *mpl, int type, VALUE *value /* content destroyed */ ); /* delete generic value */ /**********************************************************************/ /* * * SYMBOLICALLY INDEXED ARRAYS * * */ /**********************************************************************/ struct ARRAY { /* multi-dimensional array, a set of members indexed over simple or compound sets of symbols; arrays are used to represent the contents of model objects (i.e. sets, parameters, variables, constraints, and objectives); arrays also are used as "values" that are assigned to members of set objects, in which case the array itself represents an elemental set */ int type; /* type of generic values assigned to the array members: A_NONE - none (members have no assigned values) A_NUMERIC - floating-point numbers A_SYMBOLIC - symbols A_ELEMSET - elemental sets A_ELEMVAR - elemental variables A_ELEMCON - elemental constraints */ int dim; /* dimension of the array that determines number of components in n-tuples for all members of the array, dim >= 0; dim = 0 means the array is 0-dimensional */ int size; /* size of the array, i.e. number of its members */ MEMBER *head; /* the first array member; NULL means the array is empty */ MEMBER *tail; /* the last array member; NULL means the array is empty */ AVL *tree; /* the search tree intended to find array members for logarithmic time; NULL means the search tree doesn't exist */ ARRAY *prev; /* the previous array in the translator database */ ARRAY *next; /* the next array in the translator database */ }; struct MEMBER { /* array member */ TUPLE *tuple; /* n-tuple, which identifies the member; number of its components is the same for all members within the array and determined by the array dimension; duplicate members are not allowed */ MEMBER *next; /* the next array member */ VALUE value; /* generic value assigned to the member */ }; #define create_array _glp_mpl_create_array ARRAY *create_array(MPL *mpl, int type, int dim); /* create array */ #define find_member _glp_mpl_find_member MEMBER *find_member ( MPL *mpl, ARRAY *array, /* not changed */ TUPLE *tuple /* not changed */ ); /* find array member with given n-tuple */ #define add_member _glp_mpl_add_member MEMBER *add_member ( MPL *mpl, ARRAY *array, /* modified */ TUPLE *tuple /* destroyed */ ); /* add new member to array */ #define delete_array _glp_mpl_delete_array void delete_array ( MPL *mpl, ARRAY *array /* destroyed */ ); /* delete array */ /**********************************************************************/ /* * * DOMAINS AND DUMMY INDICES * * */ /**********************************************************************/ struct DOMAIN { /* domain (a simple or compound set); syntactically domain looks like '{ i in I, (j,k) in S, t in T : }'; domains are used to define sets, over which model objects are indexed, and also as constituents of iterated operators */ DOMAIN_BLOCK *list; /* linked list of domain blocks (in the example above such blocks are 'i in I', '(j,k) in S', and 't in T'); this list cannot be empty */ CODE *code; /* pseudo-code for computing the logical predicate, which follows the colon; NULL means no predicate is specified */ }; struct DOMAIN_BLOCK { /* domain block; syntactically domain blocks look like 'i in I', '(j,k) in S', and 't in T' in the example above (in the sequel sets like I, S, and T are called basic sets) */ DOMAIN_SLOT *list; /* linked list of domain slots (i.e. indexing positions); number of slots in this list is the same as dimension of n-tuples in the basic set; this list cannot be empty */ CODE *code; /* pseudo-code for computing basic set; cannot be NULL */ TUPLE *backup; /* if this n-tuple is not empty, current values of dummy indices in the domain block are the same as components of this n-tuple (note that this n-tuple may have larger dimension than number of dummy indices in this block, in which case extra components are ignored); this n-tuple is used to restore former values of dummy indices, if they were changed due to recursive calls to the domain block */ DOMAIN_BLOCK *next; /* the next block in the same domain */ }; struct DOMAIN_SLOT { /* domain slot; it specifies an individual indexing position and defines the corresponding dummy index */ char *name; /* symbolic name of the dummy index; null pointer means the dummy index is not explicitly specified */ CODE *code; /* pseudo-code for computing symbolic value, at which the dummy index is bound; NULL means the dummy index is free within the domain scope */ SYMBOL *value; /* current value assigned to the dummy index; NULL means no value is assigned at the moment */ CODE *list; /* linked list of pseudo-codes with operation O_INDEX referring to this slot; this linked list is used to invalidate resultant values of the operation, which depend on this dummy index */ DOMAIN_SLOT *next; /* the next slot in the same domain block */ }; #define assign_dummy_index _glp_mpl_assign_dummy_index void assign_dummy_index ( MPL *mpl, DOMAIN_SLOT *slot, /* modified */ SYMBOL *value /* not changed */ ); /* assign new value to dummy index */ #define update_dummy_indices _glp_mpl_update_dummy_indices void update_dummy_indices ( MPL *mpl, DOMAIN_BLOCK *block /* not changed */ ); /* update current values of dummy indices */ #define enter_domain_block _glp_mpl_enter_domain_block int enter_domain_block ( MPL *mpl, DOMAIN_BLOCK *block, /* not changed */ TUPLE *tuple, /* not changed */ void *info, void (*func)(MPL *mpl, void *info) ); /* enter domain block */ #define eval_within_domain _glp_mpl_eval_within_domain int eval_within_domain ( MPL *mpl, DOMAIN *domain, /* not changed */ TUPLE *tuple, /* not changed */ void *info, void (*func)(MPL *mpl, void *info) ); /* perform evaluation within domain scope */ #define loop_within_domain _glp_mpl_loop_within_domain void loop_within_domain ( MPL *mpl, DOMAIN *domain, /* not changed */ void *info, int (*func)(MPL *mpl, void *info) ); /* perform iterations within domain scope */ #define out_of_domain _glp_mpl_out_of_domain void out_of_domain ( MPL *mpl, char *name, /* not changed */ TUPLE *tuple /* not changed */ ); /* raise domain exception */ #define get_domain_tuple _glp_mpl_get_domain_tuple TUPLE *get_domain_tuple ( MPL *mpl, DOMAIN *domain /* not changed */ ); /* obtain current n-tuple from domain */ #define clean_domain _glp_mpl_clean_domain void clean_domain(MPL *mpl, DOMAIN *domain); /* clean domain */ /**********************************************************************/ /* * * MODEL SETS * * */ /**********************************************************************/ struct SET { /* model set */ char *name; /* symbolic name; cannot be NULL */ char *alias; /* alias; NULL means alias is not specified */ int dim; /* aka arity */ /* dimension (number of subscripts); dim = 0 means 0-dimensional (unsubscripted) set, dim > 0 means set of sets */ DOMAIN *domain; /* subscript domain; NULL for 0-dimensional set */ int dimen; /* dimension of n-tuples, which members of this set consist of (note that the model set itself is an array of elemental sets, which are its members; so, don't confuse this dimension with dimension of the model set); always non-zero */ WITHIN *within; /* list of supersets, which restrict each member of the set to be in every superset from this list; this list can be empty */ CODE *assign; /* pseudo-code for computing assigned value; can be NULL */ CODE *option; /* pseudo-code for computing default value; can be NULL */ GADGET *gadget; /* plain set used to initialize the array of sets; can be NULL */ int data; /* data status flag: 0 - no data are provided in the data section 1 - data are provided, but not checked yet 2 - data are provided and have been checked */ ARRAY *array; /* array of members, which are assigned elemental sets */ }; struct WITHIN { /* restricting superset list entry */ CODE *code; /* pseudo-code for computing the superset; cannot be NULL */ WITHIN *next; /* the next entry for the same set or parameter */ }; struct GADGET { /* plain set used to initialize the array of sets with data */ SET *set; /* pointer to plain set; cannot be NULL */ int ind[20]; /* ind[dim+dimen]; */ /* permutation of integers 1, 2, ..., dim+dimen */ }; #define check_elem_set _glp_mpl_check_elem_set void check_elem_set ( MPL *mpl, SET *set, /* not changed */ TUPLE *tuple, /* not changed */ ELEMSET *refer /* not changed */ ); /* check elemental set assigned to set member */ #define take_member_set _glp_mpl_take_member_set ELEMSET *take_member_set /* returns reference, not value */ ( MPL *mpl, SET *set, /* not changed */ TUPLE *tuple /* not changed */ ); /* obtain elemental set assigned to set member */ #define eval_member_set _glp_mpl_eval_member_set ELEMSET *eval_member_set /* returns reference, not value */ ( MPL *mpl, SET *set, /* not changed */ TUPLE *tuple /* not changed */ ); /* evaluate elemental set assigned to set member */ #define eval_whole_set _glp_mpl_eval_whole_set void eval_whole_set(MPL *mpl, SET *set); /* evaluate model set over entire domain */ #define clean_set _glp_mpl_clean_set void clean_set(MPL *mpl, SET *set); /* clean model set */ /**********************************************************************/ /* * * MODEL PARAMETERS * * */ /**********************************************************************/ struct PARAMETER { /* model parameter */ char *name; /* symbolic name; cannot be NULL */ char *alias; /* alias; NULL means alias is not specified */ int dim; /* aka arity */ /* dimension (number of subscripts); dim = 0 means 0-dimensional (unsubscripted) parameter */ DOMAIN *domain; /* subscript domain; NULL for 0-dimensional parameter */ int type; /* parameter type: A_NUMERIC - numeric A_INTEGER - integer A_BINARY - binary A_SYMBOLIC - symbolic */ CONDITION *cond; /* list of conditions, which restrict each parameter member to satisfy to every condition from this list; this list is used only for numeric parameters and can be empty */ WITHIN *in; /* list of supersets, which restrict each parameter member to be in every superset from this list; this list is used only for symbolic parameters and can be empty */ CODE *assign; /* pseudo-code for computing assigned value; can be NULL */ CODE *option; /* pseudo-code for computing default value; can be NULL */ int data; /* data status flag: 0 - no data are provided in the data section 1 - data are provided, but not checked yet 2 - data are provided and have been checked */ SYMBOL *defval; /* default value provided in the data section; can be NULL */ ARRAY *array; /* array of members, which are assigned numbers or symbols */ }; struct CONDITION { /* restricting condition list entry */ int rho; /* flag that specifies the form of the condition: O_LT - less than O_LE - less than or equal to O_EQ - equal to O_GE - greater than or equal to O_GT - greater than O_NE - not equal to */ CODE *code; /* pseudo-code for computing the reference value */ CONDITION *next; /* the next entry for the same parameter */ }; #define check_value_num _glp_mpl_check_value_num void check_value_num ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple, /* not changed */ double value ); /* check numeric value assigned to parameter member */ #define take_member_num _glp_mpl_take_member_num double take_member_num ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* not changed */ ); /* obtain numeric value assigned to parameter member */ #define eval_member_num _glp_mpl_eval_member_num double eval_member_num ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* not changed */ ); /* evaluate numeric value assigned to parameter member */ #define check_value_sym _glp_mpl_check_value_sym void check_value_sym ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple, /* not changed */ SYMBOL *value /* not changed */ ); /* check symbolic value assigned to parameter member */ #define take_member_sym _glp_mpl_take_member_sym SYMBOL *take_member_sym /* returns value, not reference */ ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* not changed */ ); /* obtain symbolic value assigned to parameter member */ #define eval_member_sym _glp_mpl_eval_member_sym SYMBOL *eval_member_sym /* returns value, not reference */ ( MPL *mpl, PARAMETER *par, /* not changed */ TUPLE *tuple /* not changed */ ); /* evaluate symbolic value assigned to parameter member */ #define eval_whole_par _glp_mpl_eval_whole_par void eval_whole_par(MPL *mpl, PARAMETER *par); /* evaluate model parameter over entire domain */ #define clean_parameter _glp_mpl_clean_parameter void clean_parameter(MPL *mpl, PARAMETER *par); /* clean model parameter */ /**********************************************************************/ /* * * MODEL VARIABLES * * */ /**********************************************************************/ struct VARIABLE { /* model variable */ char *name; /* symbolic name; cannot be NULL */ char *alias; /* alias; NULL means alias is not specified */ int dim; /* aka arity */ /* dimension (number of subscripts); dim = 0 means 0-dimensional (unsubscripted) variable */ DOMAIN *domain; /* subscript domain; NULL for 0-dimensional variable */ int type; /* variable type: A_NUMERIC - continuous A_INTEGER - integer A_BINARY - binary */ CODE *lbnd; /* pseudo-code for computing lower bound; NULL means lower bound is not specified */ CODE *ubnd; /* pseudo-code for computing upper bound; NULL means upper bound is not specified */ /* if both the pointers lbnd and ubnd refer to the same code, the variable is fixed at the corresponding value */ ARRAY *array; /* array of members, which are assigned elemental variables */ }; #define take_member_var _glp_mpl_take_member_var ELEMVAR *take_member_var /* returns reference */ ( MPL *mpl, VARIABLE *var, /* not changed */ TUPLE *tuple /* not changed */ ); /* obtain reference to elemental variable */ #define eval_member_var _glp_mpl_eval_member_var ELEMVAR *eval_member_var /* returns reference */ ( MPL *mpl, VARIABLE *var, /* not changed */ TUPLE *tuple /* not changed */ ); /* evaluate reference to elemental variable */ #define eval_whole_var _glp_mpl_eval_whole_var void eval_whole_var(MPL *mpl, VARIABLE *var); /* evaluate model variable over entire domain */ #define clean_variable _glp_mpl_clean_variable void clean_variable(MPL *mpl, VARIABLE *var); /* clean model variable */ /**********************************************************************/ /* * * MODEL CONSTRAINTS AND OBJECTIVES * * */ /**********************************************************************/ struct CONSTRAINT { /* model constraint or objective */ char *name; /* symbolic name; cannot be NULL */ char *alias; /* alias; NULL means alias is not specified */ int dim; /* aka arity */ /* dimension (number of subscripts); dim = 0 means 0-dimensional (unsubscripted) constraint */ DOMAIN *domain; /* subscript domain; NULL for 0-dimensional constraint */ int type; /* constraint type: A_CONSTRAINT - constraint A_MINIMIZE - objective (minimization) A_MAXIMIZE - objective (maximization) */ CODE *code; /* pseudo-code for computing main linear form; cannot be NULL */ CODE *lbnd; /* pseudo-code for computing lower bound; NULL means lower bound is not specified */ CODE *ubnd; /* pseudo-code for computing upper bound; NULL means upper bound is not specified */ /* if both the pointers lbnd and ubnd refer to the same code, the constraint has the form of equation */ ARRAY *array; /* array of members, which are assigned elemental constraints */ }; #define take_member_con _glp_mpl_take_member_con ELEMCON *take_member_con /* returns reference */ ( MPL *mpl, CONSTRAINT *con, /* not changed */ TUPLE *tuple /* not changed */ ); /* obtain reference to elemental constraint */ #define eval_member_con _glp_mpl_eval_member_con ELEMCON *eval_member_con /* returns reference */ ( MPL *mpl, CONSTRAINT *con, /* not changed */ TUPLE *tuple /* not changed */ ); /* evaluate reference to elemental constraint */ #define eval_whole_con _glp_mpl_eval_whole_con void eval_whole_con(MPL *mpl, CONSTRAINT *con); /* evaluate model constraint over entire domain */ #define clean_constraint _glp_mpl_clean_constraint void clean_constraint(MPL *mpl, CONSTRAINT *con); /* clean model constraint */ /**********************************************************************/ /* * * DATA TABLES * * */ /**********************************************************************/ struct TABLE { /* data table */ char *name; /* symbolic name; cannot be NULL */ char *alias; /* alias; NULL means alias is not specified */ int type; /* table type: A_INPUT - input table A_OUTPUT - output table */ TABARG *arg; /* argument list; cannot be empty */ union { struct { SET *set; /* input set; NULL means the set is not specified */ TABFLD *fld; /* field list; cannot be empty */ TABIN *list; /* input list; can be empty */ } in; struct { DOMAIN *domain; /* subscript domain; cannot be NULL */ TABOUT *list; /* output list; cannot be empty */ } out; } u; }; struct TABARG { /* table argument list entry */ CODE *code; /* pseudo-code for computing the argument */ TABARG *next; /* next entry for the same table */ }; struct TABFLD { /* table field list entry */ char *name; /* field name; cannot be NULL */ TABFLD *next; /* next entry for the same table */ }; struct TABIN { /* table input list entry */ PARAMETER *par; /* parameter to be read; cannot be NULL */ char *name; /* column name; cannot be NULL */ TABIN *next; /* next entry for the same table */ }; struct TABOUT { /* table output list entry */ CODE *code; /* pseudo-code for computing the value to be written */ char *name; /* column name; cannot be NULL */ TABOUT *next; /* next entry for the same table */ }; struct TABDCA { /* table driver communication area */ int id; /* driver identifier (set by mpl_tab_drv_open) */ void *link; /* driver link pointer (set by mpl_tab_drv_open) */ int na; /* number of arguments */ char **arg; /* char *arg[1+ns]; */ /* arg[k], 1 <= k <= ns, is pointer to k-th argument */ int nf; /* number of fields */ char **name; /* char *name[1+nc]; */ /* name[k], 1 <= k <= nc, is name of k-th field */ int *type; /* int type[1+nc]; */ /* type[k], 1 <= k <= nc, is type of k-th field: '?' - value not assigned 'N' - number 'S' - character string */ double *num; /* double num[1+nc]; */ /* num[k], 1 <= k <= nc, is numeric value of k-th field */ char **str; /* str[k], 1 <= k <= nc, is string value of k-th field */ }; #define mpl_tab_num_args _glp_mpl_tab_num_args int mpl_tab_num_args(TABDCA *dca); #define mpl_tab_get_arg _glp_mpl_tab_get_arg const char *mpl_tab_get_arg(TABDCA *dca, int k); #define mpl_tab_num_flds _glp_mpl_tab_num_flds int mpl_tab_num_flds(TABDCA *dca); #define mpl_tab_get_name _glp_mpl_tab_get_name const char *mpl_tab_get_name(TABDCA *dca, int k); #define mpl_tab_get_type _glp_mpl_tab_get_type int mpl_tab_get_type(TABDCA *dca, int k); #define mpl_tab_get_num _glp_mpl_tab_get_num double mpl_tab_get_num(TABDCA *dca, int k); #define mpl_tab_get_str _glp_mpl_tab_get_str const char *mpl_tab_get_str(TABDCA *dca, int k); #define mpl_tab_set_num _glp_mpl_tab_set_num void mpl_tab_set_num(TABDCA *dca, int k, double num); #define mpl_tab_set_str _glp_mpl_tab_set_str void mpl_tab_set_str(TABDCA *dca, int k, const char *str); #define mpl_tab_drv_open _glp_mpl_tab_drv_open void mpl_tab_drv_open(MPL *mpl, int mode); #define mpl_tab_drv_read _glp_mpl_tab_drv_read int mpl_tab_drv_read(MPL *mpl); #define mpl_tab_drv_write _glp_mpl_tab_drv_write void mpl_tab_drv_write(MPL *mpl); #define mpl_tab_drv_close _glp_mpl_tab_drv_close void mpl_tab_drv_close(MPL *mpl); /**********************************************************************/ /* * * PSEUDO-CODE * * */ /**********************************************************************/ union OPERANDS { /* operands that participate in pseudo-code operation (choice of particular operands depends on the operation code) */ /*--------------------------------------------------------------*/ double num; /* O_NUMBER */ /* floaing-point number to be taken */ /*--------------------------------------------------------------*/ char *str; /* O_STRING */ /* character string to be taken */ /*--------------------------------------------------------------*/ struct /* O_INDEX */ { DOMAIN_SLOT *slot; /* domain slot, which contains dummy index to be taken */ CODE *next; /* the next pseudo-code with op = O_INDEX, which refers to the same slot as this one; pointer to the beginning of this list is stored in the corresponding domain slot */ } index; /*--------------------------------------------------------------*/ struct /* O_MEMNUM, O_MEMSYM */ { PARAMETER *par; /* model parameter, which contains member to be taken */ ARG_LIST *list; /* list of subscripts; NULL for 0-dimensional parameter */ } par; /*--------------------------------------------------------------*/ struct /* O_MEMSET */ { SET *set; /* model set, which contains member to be taken */ ARG_LIST *list; /* list of subscripts; NULL for 0-dimensional set */ } set; /*--------------------------------------------------------------*/ struct /* O_MEMVAR */ { VARIABLE *var; /* model variable, which contains member to be taken */ ARG_LIST *list; /* list of subscripts; NULL for 0-dimensional variable */ #if 1 /* 15/V-2010 */ int suff; /* suffix specified: */ #define DOT_NONE 0x00 /* none (means variable itself) */ #define DOT_LB 0x01 /* .lb (lower bound) */ #define DOT_UB 0x02 /* .ub (upper bound) */ #define DOT_STATUS 0x03 /* .status (status) */ #define DOT_VAL 0x04 /* .val (primal value) */ #define DOT_DUAL 0x05 /* .dual (dual value) */ #endif } var; #if 1 /* 15/V-2010 */ /*--------------------------------------------------------------*/ struct /* O_MEMCON */ { CONSTRAINT *con; /* model constraint, which contains member to be taken */ ARG_LIST *list; /* list of subscripys; NULL for 0-dimensional constraint */ int suff; /* suffix specified (see O_MEMVAR above) */ } con; #endif /*--------------------------------------------------------------*/ ARG_LIST *list; /* O_TUPLE, O_MAKE, n-ary operations */ /* list of operands */ /*--------------------------------------------------------------*/ DOMAIN_BLOCK *slice; /* O_SLICE */ /* domain block, which specifies slice (i.e. n-tuple that contains free dummy indices); this operation is never evaluated */ /*--------------------------------------------------------------*/ struct /* unary, binary, ternary operations */ { CODE *x; /* pseudo-code for computing first operand */ CODE *y; /* pseudo-code for computing second operand */ CODE *z; /* pseudo-code for computing third operand */ } arg; /*--------------------------------------------------------------*/ struct /* iterated operations */ { DOMAIN *domain; /* domain, over which the operation is performed */ CODE *x; /* pseudo-code for computing "integrand" */ } loop; /*--------------------------------------------------------------*/ }; struct ARG_LIST { /* operands list entry */ CODE *x; /* pseudo-code for computing operand */ ARG_LIST *next; /* the next operand of the same operation */ }; struct CODE { /* pseudo-code (internal form of expressions) */ int op; /* operation code: */ #define O_NUMBER 301 /* take floating-point number */ #define O_STRING 302 /* take character string */ #define O_INDEX 303 /* take dummy index */ #define O_MEMNUM 304 /* take member of numeric parameter */ #define O_MEMSYM 305 /* take member of symbolic parameter */ #define O_MEMSET 306 /* take member of set */ #define O_MEMVAR 307 /* take member of variable */ #define O_MEMCON 308 /* take member of constraint */ #define O_TUPLE 309 /* make n-tuple */ #define O_MAKE 310 /* make elemental set of n-tuples */ #define O_SLICE 311 /* define domain block (dummy op) */ /* 0-ary operations --------------------*/ #define O_IRAND224 312 /* pseudo-random in [0, 2^24-1] */ #define O_UNIFORM01 313 /* pseudo-random in [0, 1) */ #define O_NORMAL01 314 /* gaussian random, mu = 0, sigma = 1 */ #define O_GMTIME 315 /* current calendar time (UTC) */ /* unary operations --------------------*/ #define O_CVTNUM 316 /* conversion to numeric */ #define O_CVTSYM 317 /* conversion to symbolic */ #define O_CVTLOG 318 /* conversion to logical */ #define O_CVTTUP 319 /* conversion to 1-tuple */ #define O_CVTLFM 320 /* conversion to linear form */ #define O_PLUS 321 /* unary plus */ #define O_MINUS 322 /* unary minus */ #define O_NOT 323 /* negation (logical "not") */ #define O_ABS 324 /* absolute value */ #define O_CEIL 325 /* round upward ("ceiling of x") */ #define O_FLOOR 326 /* round downward ("floor of x") */ #define O_EXP 327 /* base-e exponential */ #define O_LOG 328 /* natural logarithm */ #define O_LOG10 329 /* common (decimal) logarithm */ #define O_SQRT 330 /* square root */ #define O_SIN 331 /* trigonometric sine */ #define O_COS 332 /* trigonometric cosine */ #define O_ATAN 333 /* trigonometric arctangent */ #define O_ROUND 334 /* round to nearest integer */ #define O_TRUNC 335 /* truncate to nearest integer */ #define O_CARD 336 /* cardinality of set */ #define O_LENGTH 337 /* length of symbolic value */ /* binary operations -------------------*/ #define O_ADD 338 /* addition */ #define O_SUB 339 /* subtraction */ #define O_LESS 340 /* non-negative subtraction */ #define O_MUL 341 /* multiplication */ #define O_DIV 342 /* division */ #define O_IDIV 343 /* quotient of exact division */ #define O_MOD 344 /* remainder of exact division */ #define O_POWER 345 /* exponentiation (raise to power) */ #define O_ATAN2 346 /* trigonometric arctangent */ #define O_ROUND2 347 /* round to n fractional digits */ #define O_TRUNC2 348 /* truncate to n fractional digits */ #define O_UNIFORM 349 /* pseudo-random in [a, b) */ #define O_NORMAL 350 /* gaussian random, given mu and sigma */ #define O_CONCAT 351 /* concatenation */ #define O_LT 352 /* comparison on 'less than' */ #define O_LE 353 /* comparison on 'not greater than' */ #define O_EQ 354 /* comparison on 'equal to' */ #define O_GE 355 /* comparison on 'not less than' */ #define O_GT 356 /* comparison on 'greater than' */ #define O_NE 357 /* comparison on 'not equal to' */ #define O_AND 358 /* conjunction (logical "and") */ #define O_OR 359 /* disjunction (logical "or") */ #define O_UNION 360 /* union */ #define O_DIFF 361 /* difference */ #define O_SYMDIFF 362 /* symmetric difference */ #define O_INTER 363 /* intersection */ #define O_CROSS 364 /* cross (Cartesian) product */ #define O_IN 365 /* test on 'x in Y' */ #define O_NOTIN 366 /* test on 'x not in Y' */ #define O_WITHIN 367 /* test on 'X within Y' */ #define O_NOTWITHIN 368 /* test on 'X not within Y' */ #define O_SUBSTR 369 /* substring */ #define O_STR2TIME 370 /* convert string to time */ #define O_TIME2STR 371 /* convert time to string */ /* ternary operations ------------------*/ #define O_DOTS 372 /* build "arithmetic" set */ #define O_FORK 373 /* if-then-else */ #define O_SUBSTR3 374 /* substring */ /* n-ary operations --------------------*/ #define O_MIN 375 /* minimal value (n-ary) */ #define O_MAX 376 /* maximal value (n-ary) */ /* iterated operations -----------------*/ #define O_SUM 377 /* summation */ #define O_PROD 378 /* multiplication */ #define O_MINIMUM 379 /* minimum */ #define O_MAXIMUM 380 /* maximum */ #define O_FORALL 381 /* conjunction (A-quantification) */ #define O_EXISTS 382 /* disjunction (E-quantification) */ #define O_SETOF 383 /* compute elemental set */ #define O_BUILD 384 /* build elemental set */ OPERANDS arg; /* operands that participate in the operation */ int type; /* type of the resultant value: A_NUMERIC - numeric A_SYMBOLIC - symbolic A_LOGICAL - logical A_TUPLE - n-tuple A_ELEMSET - elemental set A_FORMULA - linear form */ int dim; /* dimension of the resultant value; for A_TUPLE and A_ELEMSET it is the dimension of the corresponding n-tuple(s) and cannot be zero; for other resultant types it is always zero */ CODE *up; /* parent pseudo-code, which refers to this pseudo-code as to its operand; NULL means this pseudo-code has no parent and defines an expression, which is not contained in another expression */ int vflag; /* volatile flag; being set this flag means that this operation has a side effect; for primary expressions this flag is set directly by corresponding parsing routines (for example, if primary expression is a reference to a function that generates pseudo-random numbers); in other cases this flag is inherited from operands */ int valid; /* if this flag is set, the resultant value, which is a temporary result of evaluating this operation on particular values of operands, is valid; if this flag is clear, the resultant value doesn't exist and therefore not valid; having been evaluated the resultant value is stored here and not destroyed until the dummy indices, which this value depends on, have been changed (and if it doesn't depend on dummy indices at all, it is never destroyed); thus, if the resultant value is valid, evaluating routine can immediately take its copy not computing the result from scratch; this mechanism is similar to moving invariants out of loops and allows improving efficiency at the expense of some extra memory needed to keep temporary results */ /* however, if the volatile flag (see above) is set, even if the resultant value is valid, evaluating routine computes it as if it were not valid, i.e. caching is not used in this case */ VALUE value; /* resultant value in generic format */ }; #define eval_numeric _glp_mpl_eval_numeric double eval_numeric(MPL *mpl, CODE *code); /* evaluate pseudo-code to determine numeric value */ #define eval_symbolic _glp_mpl_eval_symbolic SYMBOL *eval_symbolic(MPL *mpl, CODE *code); /* evaluate pseudo-code to determine symbolic value */ #define eval_logical _glp_mpl_eval_logical int eval_logical(MPL *mpl, CODE *code); /* evaluate pseudo-code to determine logical value */ #define eval_tuple _glp_mpl_eval_tuple TUPLE *eval_tuple(MPL *mpl, CODE *code); /* evaluate pseudo-code to construct n-tuple */ #define eval_elemset _glp_mpl_eval_elemset ELEMSET *eval_elemset(MPL *mpl, CODE *code); /* evaluate pseudo-code to construct elemental set */ #define is_member _glp_mpl_is_member int is_member(MPL *mpl, CODE *code, TUPLE *tuple); /* check if n-tuple is in set specified by pseudo-code */ #define eval_formula _glp_mpl_eval_formula FORMULA *eval_formula(MPL *mpl, CODE *code); /* evaluate pseudo-code to construct linear form */ #define clean_code _glp_mpl_clean_code void clean_code(MPL *mpl, CODE *code); /* clean pseudo-code */ /**********************************************************************/ /* * * MODEL STATEMENTS * * */ /**********************************************************************/ struct CHECK { /* check statement */ DOMAIN *domain; /* subscript domain; NULL means domain is not used */ CODE *code; /* code for computing the predicate to be checked */ }; struct DISPLAY { /* display statement */ DOMAIN *domain; /* subscript domain; NULL means domain is not used */ DISPLAY1 *list; /* display list; cannot be empty */ }; struct DISPLAY1 { /* display list entry */ int type; /* item type: A_INDEX - dummy index A_SET - model set A_PARAMETER - model parameter A_VARIABLE - model variable A_CONSTRAINT - model constraint/objective A_EXPRESSION - expression */ union { DOMAIN_SLOT *slot; SET *set; PARAMETER *par; VARIABLE *var; CONSTRAINT *con; CODE *code; } u; /* item to be displayed */ #if 0 /* 15/V-2010 */ ARG_LIST *list; /* optional subscript list (for constraint/objective only) */ #endif DISPLAY1 *next; /* the next entry for the same statement */ }; struct PRINTF { /* printf statement */ DOMAIN *domain; /* subscript domain; NULL means domain is not used */ CODE *fmt; /* pseudo-code for computing format string */ PRINTF1 *list; /* printf list; can be empty */ CODE *fname; /* pseudo-code for computing filename to redirect the output; NULL means the output goes to stdout */ int app; /* if this flag is set, the output is appended */ }; struct PRINTF1 { /* printf list entry */ CODE *code; /* pseudo-code for computing value to be printed */ PRINTF1 *next; /* the next entry for the same statement */ }; struct FOR { /* for statement */ DOMAIN *domain; /* subscript domain; cannot be NULL */ STATEMENT *list; /* linked list of model statements within this for statement in the original order */ }; struct STATEMENT { /* model statement */ int line; /* number of source text line, where statement begins */ int type; /* statement type: A_SET - set statement A_PARAMETER - parameter statement A_VARIABLE - variable statement A_CONSTRAINT - constraint/objective statement A_TABLE - table statement A_SOLVE - solve statement A_CHECK - check statement A_DISPLAY - display statement A_PRINTF - printf statement A_FOR - for statement */ union { SET *set; PARAMETER *par; VARIABLE *var; CONSTRAINT *con; TABLE *tab; void *slv; /* currently not used (set to NULL) */ CHECK *chk; DISPLAY *dpy; PRINTF *prt; FOR *fur; } u; /* specific part of statement */ STATEMENT *next; /* the next statement; in this list statements follow in the same order as they appear in the model section */ }; #define execute_table _glp_mpl_execute_table void execute_table(MPL *mpl, TABLE *tab); /* execute table statement */ #define free_dca _glp_mpl_free_dca void free_dca(MPL *mpl); /* free table driver communucation area */ #define clean_table _glp_mpl_clean_table void clean_table(MPL *mpl, TABLE *tab); /* clean table statement */ #define execute_check _glp_mpl_execute_check void execute_check(MPL *mpl, CHECK *chk); /* execute check statement */ #define clean_check _glp_mpl_clean_check void clean_check(MPL *mpl, CHECK *chk); /* clean check statement */ #define execute_display _glp_mpl_execute_display void execute_display(MPL *mpl, DISPLAY *dpy); /* execute display statement */ #define clean_display _glp_mpl_clean_display void clean_display(MPL *mpl, DISPLAY *dpy); /* clean display statement */ #define execute_printf _glp_mpl_execute_printf void execute_printf(MPL *mpl, PRINTF *prt); /* execute printf statement */ #define clean_printf _glp_mpl_clean_printf void clean_printf(MPL *mpl, PRINTF *prt); /* clean printf statement */ #define execute_for _glp_mpl_execute_for void execute_for(MPL *mpl, FOR *fur); /* execute for statement */ #define clean_for _glp_mpl_clean_for void clean_for(MPL *mpl, FOR *fur); /* clean for statement */ #define execute_statement _glp_mpl_execute_statement void execute_statement(MPL *mpl, STATEMENT *stmt); /* execute specified model statement */ #define clean_statement _glp_mpl_clean_statement void clean_statement(MPL *mpl, STATEMENT *stmt); /* clean specified model statement */ /**********************************************************************/ /* * * GENERATING AND POSTSOLVING MODEL * * */ /**********************************************************************/ #define alloc_content _glp_mpl_alloc_content void alloc_content(MPL *mpl); /* allocate content arrays for all model objects */ #define generate_model _glp_mpl_generate_model void generate_model(MPL *mpl); /* generate model */ #define build_problem _glp_mpl_build_problem void build_problem(MPL *mpl); /* build problem instance */ #define postsolve_model _glp_mpl_postsolve_model void postsolve_model(MPL *mpl); /* postsolve model */ #define clean_model _glp_mpl_clean_model void clean_model(MPL *mpl); /* clean model content */ /**********************************************************************/ /* * * INPUT/OUTPUT * * */ /**********************************************************************/ #define open_input _glp_mpl_open_input void open_input(MPL *mpl, char *file); /* open input text file */ #define read_char _glp_mpl_read_char int read_char(MPL *mpl); /* read next character from input text file */ #define close_input _glp_mpl_close_input void close_input(MPL *mpl); /* close input text file */ #define open_output _glp_mpl_open_output void open_output(MPL *mpl, char *file); /* open output text file */ #define write_char _glp_mpl_write_char void write_char(MPL *mpl, int c); /* write next character to output text file */ #define write_text _glp_mpl_write_text void write_text(MPL *mpl, char *fmt, ...); /* format and write text to output text file */ #define flush_output _glp_mpl_flush_output void flush_output(MPL *mpl); /* finalize writing data to output text file */ /**********************************************************************/ /* * * SOLVER INTERFACE * * */ /**********************************************************************/ #define MPL_FR 401 /* free (unbounded) */ #define MPL_LO 402 /* lower bound */ #define MPL_UP 403 /* upper bound */ #define MPL_DB 404 /* both lower and upper bounds */ #define MPL_FX 405 /* fixed */ #define MPL_ST 411 /* constraint */ #define MPL_MIN 412 /* objective (minimization) */ #define MPL_MAX 413 /* objective (maximization) */ #define MPL_NUM 421 /* continuous */ #define MPL_INT 422 /* integer */ #define MPL_BIN 423 /* binary */ #define mpl_error _glp_mpl_error void mpl_error(MPL *mpl, char *fmt, ...); /* print error message and terminate model processing */ #define warning _glp_mpl_warning void warning(MPL *mpl, char *fmt, ...); /* print warning message and continue model processing */ #define mpl_initialize _glp_mpl_initialize MPL *mpl_initialize(void); /* create and initialize translator database */ #define mpl_read_model _glp_mpl_read_model int mpl_read_model(MPL *mpl, char *file, int skip_data); /* read model section and optional data section */ #define mpl_read_data _glp_mpl_read_data int mpl_read_data(MPL *mpl, char *file); /* read data section */ #define mpl_generate _glp_mpl_generate int mpl_generate(MPL *mpl, char *file); /* generate model */ #define mpl_get_prob_name _glp_mpl_get_prob_name char *mpl_get_prob_name(MPL *mpl); /* obtain problem (model) name */ #define mpl_get_num_rows _glp_mpl_get_num_rows int mpl_get_num_rows(MPL *mpl); /* determine number of rows */ #define mpl_get_num_cols _glp_mpl_get_num_cols int mpl_get_num_cols(MPL *mpl); /* determine number of columns */ #define mpl_get_row_name _glp_mpl_get_row_name char *mpl_get_row_name(MPL *mpl, int i); /* obtain row name */ #define mpl_get_row_kind _glp_mpl_get_row_kind int mpl_get_row_kind(MPL *mpl, int i); /* determine row kind */ #define mpl_get_row_bnds _glp_mpl_get_row_bnds int mpl_get_row_bnds(MPL *mpl, int i, double *lb, double *ub); /* obtain row bounds */ #define mpl_get_mat_row _glp_mpl_get_mat_row int mpl_get_mat_row(MPL *mpl, int i, int ndx[], double val[]); /* obtain row of the constraint matrix */ #define mpl_get_row_c0 _glp_mpl_get_row_c0 double mpl_get_row_c0(MPL *mpl, int i); /* obtain constant term of free row */ #define mpl_get_col_name _glp_mpl_get_col_name char *mpl_get_col_name(MPL *mpl, int j); /* obtain column name */ #define mpl_get_col_kind _glp_mpl_get_col_kind int mpl_get_col_kind(MPL *mpl, int j); /* determine column kind */ #define mpl_get_col_bnds _glp_mpl_get_col_bnds int mpl_get_col_bnds(MPL *mpl, int j, double *lb, double *ub); /* obtain column bounds */ #define mpl_has_solve_stmt _glp_mpl_has_solve_stmt int mpl_has_solve_stmt(MPL *mpl); /* check if model has solve statement */ #if 1 /* 15/V-2010 */ #define mpl_put_row_soln _glp_mpl_put_row_soln void mpl_put_row_soln(MPL *mpl, int i, int stat, double prim, double dual); /* store row (constraint/objective) solution components */ #endif #if 1 /* 15/V-2010 */ #define mpl_put_col_soln _glp_mpl_put_col_soln void mpl_put_col_soln(MPL *mpl, int j, int stat, double prim, double dual); /* store column (variable) solution components */ #endif #if 0 /* 15/V-2010 */ #define mpl_put_col_value _glp_mpl_put_col_value void mpl_put_col_value(MPL *mpl, int j, double val); /* store column value */ #endif #define mpl_postsolve _glp_mpl_postsolve int mpl_postsolve(MPL *mpl); /* postsolve model */ #define mpl_terminate _glp_mpl_terminate void mpl_terminate(MPL *mpl); /* free all resources used by translator */ #endif /* eof */ sources_5316/external/glpk/glpini02.c0000644000176700017670000002144111401660400016264 0ustar paulpaul/* glpini02.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" struct var { /* structural variable */ int j; /* ordinal number */ double q; /* penalty value */ }; static int fcmp(const void *ptr1, const void *ptr2) { /* this routine is passed to the qsort() function */ struct var *col1 = (void *)ptr1, *col2 = (void *)ptr2; if (col1->q < col2->q) return -1; if (col1->q > col2->q) return +1; return 0; } static int get_column(glp_prob *lp, int j, int ind[], double val[]) { /* Bixby's algorithm assumes that the constraint matrix is scaled such that the maximum absolute value in every non-zero row and column is 1 */ int k, len; double big; len = glp_get_mat_col(lp, j, ind, val); big = 0.0; for (k = 1; k <= len; k++) if (big < fabs(val[k])) big = fabs(val[k]); if (big == 0.0) big = 1.0; for (k = 1; k <= len; k++) val[k] /= big; return len; } static void cpx_basis(glp_prob *lp) { /* main routine */ struct var *C, *C2, *C3, *C4; int m, n, i, j, jk, k, l, ll, t, n2, n3, n4, type, len, *I, *r, *ind; double alpha, gamma, cmax, temp, *v, *val; xprintf("Constructing initial basis...\n"); /* determine the number of rows and columns */ m = glp_get_num_rows(lp); n = glp_get_num_cols(lp); /* allocate working arrays */ C = xcalloc(1+n, sizeof(struct var)); I = xcalloc(1+m, sizeof(int)); r = xcalloc(1+m, sizeof(int)); v = xcalloc(1+m, sizeof(double)); ind = xcalloc(1+m, sizeof(int)); val = xcalloc(1+m, sizeof(double)); /* make all auxiliary variables non-basic */ for (i = 1; i <= m; i++) { if (glp_get_row_type(lp, i) != GLP_DB) glp_set_row_stat(lp, i, GLP_NS); else if (fabs(glp_get_row_lb(lp, i)) <= fabs(glp_get_row_ub(lp, i))) glp_set_row_stat(lp, i, GLP_NL); else glp_set_row_stat(lp, i, GLP_NU); } /* make all structural variables non-basic */ for (j = 1; j <= n; j++) { if (glp_get_col_type(lp, j) != GLP_DB) glp_set_col_stat(lp, j, GLP_NS); else if (fabs(glp_get_col_lb(lp, j)) <= fabs(glp_get_col_ub(lp, j))) glp_set_col_stat(lp, j, GLP_NL); else glp_set_col_stat(lp, j, GLP_NU); } /* C2 is a set of free structural variables */ n2 = 0, C2 = C + 0; for (j = 1; j <= n; j++) { type = glp_get_col_type(lp, j); if (type == GLP_FR) { n2++; C2[n2].j = j; C2[n2].q = 0.0; } } /* C3 is a set of structural variables having excatly one (lower or upper) bound */ n3 = 0, C3 = C2 + n2; for (j = 1; j <= n; j++) { type = glp_get_col_type(lp, j); if (type == GLP_LO) { n3++; C3[n3].j = j; C3[n3].q = + glp_get_col_lb(lp, j); } else if (type == GLP_UP) { n3++; C3[n3].j = j; C3[n3].q = - glp_get_col_ub(lp, j); } } /* C4 is a set of structural variables having both (lower and upper) bounds */ n4 = 0, C4 = C3 + n3; for (j = 1; j <= n; j++) { type = glp_get_col_type(lp, j); if (type == GLP_DB) { n4++; C4[n4].j = j; C4[n4].q = glp_get_col_lb(lp, j) - glp_get_col_ub(lp, j); } } /* compute gamma = max{|c[j]|: 1 <= j <= n} */ gamma = 0.0; for (j = 1; j <= n; j++) { temp = fabs(glp_get_obj_coef(lp, j)); if (gamma < temp) gamma = temp; } /* compute cmax */ cmax = (gamma == 0.0 ? 1.0 : 1000.0 * gamma); /* compute final penalty for all structural variables within sets C2, C3, and C4 */ switch (glp_get_obj_dir(lp)) { case GLP_MIN: temp = +1.0; break; case GLP_MAX: temp = -1.0; break; default: xassert(lp != lp); } for (k = 1; k <= n2+n3+n4; k++) { j = C[k].j; C[k].q += (temp * glp_get_obj_coef(lp, j)) / cmax; } /* sort structural variables within C2, C3, and C4 in ascending order of penalty value */ qsort(C2+1, n2, sizeof(struct var), fcmp); for (k = 1; k < n2; k++) xassert(C2[k].q <= C2[k+1].q); qsort(C3+1, n3, sizeof(struct var), fcmp); for (k = 1; k < n3; k++) xassert(C3[k].q <= C3[k+1].q); qsort(C4+1, n4, sizeof(struct var), fcmp); for (k = 1; k < n4; k++) xassert(C4[k].q <= C4[k+1].q); /*** STEP 1 ***/ for (i = 1; i <= m; i++) { type = glp_get_row_type(lp, i); if (type != GLP_FX) { /* row i is either free or inequality constraint */ glp_set_row_stat(lp, i, GLP_BS); I[i] = 1; r[i] = 1; } else { /* row i is equality constraint */ I[i] = 0; r[i] = 0; } v[i] = +DBL_MAX; } /*** STEP 2 ***/ for (k = 1; k <= n2+n3+n4; k++) { jk = C[k].j; len = get_column(lp, jk, ind, val); /* let alpha = max{|A[l,jk]|: r[l] = 0} and let l' be such that alpha = |A[l',jk]| */ alpha = 0.0, ll = 0; for (t = 1; t <= len; t++) { l = ind[t]; if (r[l] == 0 && alpha < fabs(val[t])) alpha = fabs(val[t]), ll = l; } if (alpha >= 0.99) { /* B := B union {jk} */ glp_set_col_stat(lp, jk, GLP_BS); I[ll] = 1; v[ll] = alpha; /* r[l] := r[l] + 1 for all l such that |A[l,jk]| != 0 */ for (t = 1; t <= len; t++) { l = ind[t]; if (val[t] != 0.0) r[l]++; } /* continue to the next k */ continue; } /* if |A[l,jk]| > 0.01 * v[l] for some l, continue to the next k */ for (t = 1; t <= len; t++) { l = ind[t]; if (fabs(val[t]) > 0.01 * v[l]) break; } if (t <= len) continue; /* otherwise, let alpha = max{|A[l,jk]|: I[l] = 0} and let l' be such that alpha = |A[l',jk]| */ alpha = 0.0, ll = 0; for (t = 1; t <= len; t++) { l = ind[t]; if (I[l] == 0 && alpha < fabs(val[t])) alpha = fabs(val[t]), ll = l; } /* if alpha = 0, continue to the next k */ if (alpha == 0.0) continue; /* B := B union {jk} */ glp_set_col_stat(lp, jk, GLP_BS); I[ll] = 1; v[ll] = alpha; /* r[l] := r[l] + 1 for all l such that |A[l,jk]| != 0 */ for (t = 1; t <= len; t++) { l = ind[t]; if (val[t] != 0.0) r[l]++; } } /*** STEP 3 ***/ /* add an artificial variable (auxiliary variable for equality constraint) to cover each remaining uncovered row */ for (i = 1; i <= m; i++) if (I[i] == 0) glp_set_row_stat(lp, i, GLP_BS); /* free working arrays */ xfree(C); xfree(I); xfree(r); xfree(v); xfree(ind); xfree(val); return; } /*********************************************************************** * NAME * * glp_cpx_basis - construct Bixby's initial LP basis * * SYNOPSIS * * void glp_cpx_basis(glp_prob *lp); * * DESCRIPTION * * The routine glp_cpx_basis constructs an advanced initial basis for * the specified problem object. * * The routine is based on Bixby's algorithm described in the paper: * * Robert E. Bixby. Implementing the Simplex Method: The Initial Basis. * ORSA Journal on Computing, Vol. 4, No. 3, 1992, pp. 267-84. */ void glp_cpx_basis(glp_prob *lp) { if (lp->m == 0 || lp->n == 0) glp_std_basis(lp); else cpx_basis(lp); return; } /* eof */ sources_5316/external/glpk/glpnet04.c0000644000176700017670000006213711401660400016304 0ustar paulpaul/* glpnet04.c (grid-like network problem generator) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * This code is a modified version of the program GRIDGEN, a grid-like * network problem generator developed by Yusin Lee and Jim Orlin. * The original code is publically available on the DIMACS ftp site at: * . * * All changes concern only the program interface, so this modified * version produces exactly the same instances as the original version. * * Changes were made by Andrew Makhorin . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * NAME * * glp_gridgen - grid-like network problem generator * * SYNOPSIS * * int glp_gridgen(glp_graph *G, int v_rhs, int a_cap, int a_cost, * const int parm[1+14]); * * DESCRIPTION * * The routine glp_gridgen is a grid-like network problem generator * developed by Yusin Lee and Jim Orlin. * * The parameter G specifies the graph object, to which the generated * problem data have to be stored. Note that on entry the graph object * is erased with the routine glp_erase_graph. * * The parameter v_rhs specifies an offset of the field of type double * in the vertex data block, to which the routine stores the supply or * demand value. If v_rhs < 0, the value is not stored. * * The parameter a_cap specifies an offset of the field of type double * in the arc data block, to which the routine stores the arc capacity. * If a_cap < 0, the capacity is not stored. * * The parameter a_cost specifies an offset of the field of type double * in the arc data block, to which the routine stores the per-unit cost * if the arc flow. If a_cost < 0, the cost is not stored. * * The array parm contains description of the network to be generated: * * parm[0] not used * parm[1] two-ways arcs indicator: * 1 - if links in both direction should be generated * 0 - otherwise * parm[2] random number seed (a positive integer) * parm[3] number of nodes (the number of nodes generated might be * slightly different to make the network a grid) * parm[4] grid width * parm[5] number of sources * parm[6] number of sinks * parm[7] average degree * parm[8] total flow * parm[9] distribution of arc costs: * 1 - uniform * 2 - exponential * parm[10] lower bound for arc cost (uniform) * 100 * lambda (exponential) * parm[11] upper bound for arc cost (uniform) * not used (exponential) * parm[12] distribution of arc capacities: * 1 - uniform * 2 - exponential * parm[13] lower bound for arc capacity (uniform) * 100 * lambda (exponential) * parm[14] upper bound for arc capacity (uniform) * not used (exponential) * * RETURNS * * If the instance was successfully generated, the routine glp_gridgen * returns zero; otherwise, if specified parameters are inconsistent, * the routine returns a non-zero error code. * * COMMENTS * * This network generator generates a grid-like network plus a super * node. In additional to the arcs connecting the nodes in the grid, * there is an arc from each supply node to the super node and from the * super node to each demand node to guarantee feasiblity. These arcs * have very high costs and very big capacities. * * The idea of this network generator is as follows: First, a grid of * n1 * n2 is generated. For example, 5 * 3. The nodes are numbered as * 1 to 15, and the supernode is numbered as n1*n2+1. Then arcs between * adjacent nodes are generated. For these arcs, the user is allowed to * specify either to generate two-way arcs or one-way arcs. If two-way * arcs are to be generated, two arcs, one in each direction, will be * generated between each adjacent node pairs. Otherwise, only one arc * will be generated. If this is the case, the arcs will be generated * in alterntive directions as shown below. * * 1 ---> 2 ---> 3 ---> 4 ---> 5 * | ^ | ^ | * | | | | | * V | V | V * 6 <--- 7 <--- 8 <--- 9 <--- 10 * | ^ | ^ | * | | | | | * V | V | V * 11 --->12 --->13 --->14 ---> 15 * * Then the arcs between the super node and the source/sink nodes are * added as mentioned before. If the number of arcs still doesn't reach * the requirement, additional arcs will be added by uniformly picking * random node pairs. There is no checking to prevent multiple arcs * between any pair of nodes. However, there will be no self-arcs (arcs * that poins back to its tail node) in the network. * * The source and sink nodes are selected uniformly in the network, and * the imbalances of each source/sink node are also assigned by uniform * distribution. */ struct stat_para { /* structure for statistical distributions */ int distribution; /* the distribution: */ #define UNIFORM 1 /* uniform distribution */ #define EXPONENTIAL 2 /* exponential distribution */ double parameter[5]; /* the parameters of the distribution */ }; struct arcs { int from; /* the FROM node of that arc */ int to; /* the TO node of that arc */ int cost; /* original cost of that arc */ int u; /* capacity of the arc */ }; struct imbalance { int node; /* Node ID */ int supply; /* Supply of that node */ }; struct csa { /* common storage area */ glp_graph *G; int v_rhs, a_cap, a_cost; int seed; /* random number seed */ int seed_original; /* the original seed from input */ int two_way; /* 0: generate arcs in both direction for the basic grid, except for the arcs to/from the super node. 1: o/w */ int n_node; /* total number of nodes in the network, numbered 1 to n_node, including the super node, which is the last one */ int n_arc; /* total number of arcs in the network, counting EVERY arc. */ int n_grid_arc; /* number of arcs in the basic grid, including the arcs to/from the super node */ int n_source, n_sink; /* number of source and sink nodes */ int avg_degree; /* average degree, arcs to and from the super node are counted */ int t_supply; /* total supply in the network */ int n1, n2; /* the two edges of the network grid. n1 >= n2 */ struct imbalance *source_list, *sink_list; /* head of the array of source/sink nodes */ struct stat_para arc_costs; /* the distribution of arc costs */ struct stat_para capacities; /* distribution of the capacities of the arcs */ struct arcs *arc_list; /* head of the arc list array. Arcs in this array are in the order of grid_arcs, arcs to/from super node, and other arcs */ }; #define G (csa->G) #define v_rhs (csa->v_rhs) #define a_cap (csa->a_cap) #define a_cost (csa->a_cost) #define seed (csa->seed) #define seed_original (csa->seed_original) #define two_way (csa->two_way) #define n_node (csa->n_node) #define n_arc (csa->n_arc) #define n_grid_arc (csa->n_grid_arc) #define n_source (csa->n_source) #define n_sink (csa->n_sink) #define avg_degree (csa->avg_degree) #define t_supply (csa->t_supply) #define n1 (csa->n1) #define n2 (csa->n2) #define source_list (csa->source_list) #define sink_list (csa->sink_list) #define arc_costs (csa->arc_costs) #define capacities (csa->capacities) #define arc_list (csa->arc_list) static void assign_capacities(struct csa *csa); static void assign_costs(struct csa *csa); static void assign_imbalance(struct csa *csa); static int exponential(struct csa *csa, double lambda[1]); static struct arcs *gen_additional_arcs(struct csa *csa, struct arcs *arc_ptr); static struct arcs *gen_basic_grid(struct csa *csa, struct arcs *arc_ptr); static void gen_more_arcs(struct csa *csa, struct arcs *arc_ptr); static void generate(struct csa *csa); static void output(struct csa *csa); static double randy(struct csa *csa); static void select_source_sinks(struct csa *csa); static int uniform(struct csa *csa, double a[2]); int glp_gridgen(glp_graph *G_, int _v_rhs, int _a_cap, int _a_cost, const int parm[1+14]) { struct csa _csa, *csa = &_csa; int n, ret; G = G_; v_rhs = _v_rhs; a_cap = _a_cap; a_cost = _a_cost; if (G != NULL) { if (v_rhs >= 0 && v_rhs > G->v_size - (int)sizeof(double)) xerror("glp_gridgen: v_rhs = %d; invalid offset\n", v_rhs); if (a_cap >= 0 && a_cap > G->a_size - (int)sizeof(double)) xerror("glp_gridgen: a_cap = %d; invalid offset\n", a_cap); if (a_cost >= 0 && a_cost > G->a_size - (int)sizeof(double)) xerror("glp_gridgen: a_cost = %d; invalid offset\n", a_cost) ; } /* Check the parameters for consistency. */ if (!(parm[1] == 0 || parm[1] == 1)) { ret = 1; goto done; } if (parm[2] < 1) { ret = 2; goto done; } if (!(10 <= parm[3] && parm[3] <= 40000)) { ret = 3; goto done; } if (!(1 <= parm[4] && parm[4] <= 40000)) { ret = 4; goto done; } if (!(parm[5] >= 0 && parm[6] >= 0 && parm[5] + parm[6] <= parm[3])) { ret = 5; goto done; } if (!(1 <= parm[7] && parm[7] <= parm[3])) { ret = 6; goto done; } if (parm[8] < 0) { ret = 7; goto done; } if (!(parm[9] == 1 || parm[9] == 2)) { ret = 8; goto done; } if (parm[9] == 1 && parm[10] > parm[11] || parm[9] == 2 && parm[10] < 1) { ret = 9; goto done; } if (!(parm[12] == 1 || parm[12] == 2)) { ret = 10; goto done; } if (parm[12] == 1 && !(0 <= parm[13] && parm[13] <= parm[14]) || parm[12] == 2 && parm[13] < 1) { ret = 11; goto done; } /* Initialize the graph object. */ if (G != NULL) { glp_erase_graph(G, G->v_size, G->a_size); glp_set_graph_name(G, "GRIDGEN"); } /* Copy the generator parameters. */ two_way = parm[1]; seed_original = seed = parm[2]; n_node = parm[3]; n = parm[4]; n_source = parm[5]; n_sink = parm[6]; avg_degree = parm[7]; t_supply = parm[8]; arc_costs.distribution = parm[9]; if (parm[9] == 1) { arc_costs.parameter[0] = parm[10]; arc_costs.parameter[1] = parm[11]; } else { arc_costs.parameter[0] = (double)parm[10] / 100.0; arc_costs.parameter[1] = 0.0; } capacities.distribution = parm[12]; if (parm[12] == 1) { capacities.parameter[0] = parm[13]; capacities.parameter[1] = parm[14]; } else { capacities.parameter[0] = (double)parm[13] / 100.0; capacities.parameter[1] = 0.0; } /* Calculate the edge lengths of the grid according to the input. */ if (n * n >= n_node) { n1 = n; n2 = (int)((double)n_node / (double)n + 0.5); } else { n2 = n; n1 = (int)((double)n_node / (double)n + 0.5); } /* Recalculate the total number of nodes and plus 1 for the super node. */ n_node = n1 * n2 + 1; n_arc = n_node * avg_degree; n_grid_arc = (two_way + 1) * ((n1 - 1) * n2 + (n2 - 1) * n1) + n_source + n_sink; if (n_grid_arc > n_arc) n_arc = n_grid_arc; arc_list = xcalloc(n_arc, sizeof(struct arcs)); source_list = xcalloc(n_source, sizeof(struct imbalance)); sink_list = xcalloc(n_sink, sizeof(struct imbalance)); /* Generate a random network. */ generate(csa); /* Output the network. */ output(csa); /* Free all allocated memory. */ xfree(arc_list); xfree(source_list); xfree(sink_list); /* The instance has been successfully generated. */ ret = 0; done: return ret; } #undef random static void assign_capacities(struct csa *csa) { /* Assign a capacity to each arc. */ struct arcs *arc_ptr = arc_list; int (*random)(struct csa *csa, double *); int i; /* Determine the random number generator to use. */ switch (arc_costs.distribution) { case UNIFORM: random = uniform; break; case EXPONENTIAL: random = exponential; break; default: xassert(csa != csa); } /* Assign capacities to grid arcs. */ for (i = n_source + n_sink; i < n_grid_arc; i++, arc_ptr++) arc_ptr->u = random(csa, capacities.parameter); i = i - n_source - n_sink; /* Assign capacities to arcs to/from supernode. */ for (; i < n_grid_arc; i++, arc_ptr++) arc_ptr->u = t_supply; /* Assign capacities to all other arcs. */ for (; i < n_arc; i++, arc_ptr++) arc_ptr->u = random(csa, capacities.parameter); return; } static void assign_costs(struct csa *csa) { /* Assign a cost to each arc. */ struct arcs *arc_ptr = arc_list; int (*random)(struct csa *csa, double *); int i; /* A high cost assigned to arcs to/from the supernode. */ int high_cost; /* The maximum cost assigned to arcs in the base grid. */ int max_cost = 0; /* Determine the random number generator to use. */ switch (arc_costs.distribution) { case UNIFORM: random = uniform; break; case EXPONENTIAL: random = exponential; break; default: xassert(csa != csa); } /* Assign costs to arcs in the base grid. */ for (i = n_source + n_sink; i < n_grid_arc; i++, arc_ptr++) { arc_ptr->cost = random(csa, arc_costs.parameter); if (max_cost < arc_ptr->cost) max_cost = arc_ptr->cost; } i = i - n_source - n_sink; /* Assign costs to arcs to/from the super node. */ high_cost = max_cost * 2; for (; i < n_grid_arc; i++, arc_ptr++) arc_ptr->cost = high_cost; /* Assign costs to all other arcs. */ for (; i < n_arc; i++, arc_ptr++) arc_ptr->cost = random(csa, arc_costs.parameter); return; } static void assign_imbalance(struct csa *csa) { /* Assign an imbalance to each node. */ int total, i; double avg; struct imbalance *ptr; /* assign the supply nodes */ avg = 2.0 * t_supply / n_source; do { for (i = 1, total = t_supply, ptr = source_list + 1; i < n_source; i++, ptr++) { ptr->supply = (int)(randy(csa) * avg + 0.5); total -= ptr->supply; } source_list->supply = total; } /* redo all if the assignment "overshooted" */ while (total <= 0); /* assign the demand nodes */ avg = -2.0 * t_supply / n_sink; do { for (i = 1, total = t_supply, ptr = sink_list + 1; i < n_sink; i++, ptr++) { ptr->supply = (int)(randy(csa) * avg - 0.5); total += ptr->supply; } sink_list->supply = - total; } while (total <= 0); return; } static int exponential(struct csa *csa, double lambda[1]) { /* Returns an "exponentially distributed" integer with parameter lambda. */ return ((int)(- lambda[0] * log((double)randy(csa)) + 0.5)); } static struct arcs *gen_additional_arcs(struct csa *csa, struct arcs *arc_ptr) { /* Generate an arc from each source to the supernode and from supernode to each sink. */ int i; for (i = 0; i < n_source; i++, arc_ptr++) { arc_ptr->from = source_list[i].node; arc_ptr->to = n_node; } for (i = 0; i < n_sink; i++, arc_ptr++) { arc_ptr->to = sink_list[i].node; arc_ptr->from = n_node; } return arc_ptr; } static struct arcs *gen_basic_grid(struct csa *csa, struct arcs *arc_ptr) { /* Generate the basic grid. */ int direction = 1, i, j, k; if (two_way) { /* Generate an arc in each direction. */ for (i = 1; i < n_node; i += n1) { for (j = i, k = j + n1 - 1; j < k; j++) { arc_ptr->from = j; arc_ptr->to = j + 1; arc_ptr++; arc_ptr->from = j + 1; arc_ptr->to = j; arc_ptr++; } } for (i = 1; i <= n1; i++) { for (j = i + n1; j < n_node; j += n1) { arc_ptr->from = j; arc_ptr->to = j - n1; arc_ptr++; arc_ptr->from = j - n1; arc_ptr->to = j; arc_ptr++; } } } else { /* Generate one arc in each direction. */ for (i = 1; i < n_node; i += n1) { if (direction == 1) j = i; else j = i + 1; for (k = j + n1 - 1; j < k; j++) { arc_ptr->from = j; arc_ptr->to = j + direction; arc_ptr++; } direction = - direction; } for (i = 1; i <= n1; i++) { j = i + n1; if (direction == 1) { for (; j < n_node; j += n1) { arc_ptr->from = j - n1; arc_ptr->to = j; arc_ptr++; } } else { for (; j < n_node; j += n1) { arc_ptr->from = j - n1; arc_ptr->to = j; arc_ptr++; } } direction = - direction; } } return arc_ptr; } static void gen_more_arcs(struct csa *csa, struct arcs *arc_ptr) { /* Generate random arcs to meet the specified density. */ int i; double ab[2]; ab[0] = 0.9; ab[1] = n_node - 0.99; /* upper limit is n_node-1 because the supernode cannot be selected */ for (i = n_grid_arc; i < n_arc; i++, arc_ptr++) { arc_ptr->from = uniform(csa, ab); arc_ptr->to = uniform(csa, ab); if (arc_ptr->from == arc_ptr->to) { arc_ptr--; i--; } } return; } static void generate(struct csa *csa) { /* Generate a random network. */ struct arcs *arc_ptr = arc_list; arc_ptr = gen_basic_grid(csa, arc_ptr); select_source_sinks(csa); arc_ptr = gen_additional_arcs(csa, arc_ptr); gen_more_arcs(csa, arc_ptr); assign_costs(csa); assign_capacities(csa); assign_imbalance(csa); return; } static void output(struct csa *csa) { /* Output the network in DIMACS format. */ struct arcs *arc_ptr; struct imbalance *imb_ptr; int i; if (G != NULL) goto skip; /* Output "c", "p" records. */ xprintf("c generated by GRIDGEN\n"); xprintf("c seed %d\n", seed_original); xprintf("c nodes %d\n", n_node); xprintf("c grid size %d X %d\n", n1, n2); xprintf("c sources %d sinks %d\n", n_source, n_sink); xprintf("c avg. degree %d\n", avg_degree); xprintf("c supply %d\n", t_supply); switch (arc_costs.distribution) { case UNIFORM: xprintf("c arc costs: UNIFORM distr. min %d max %d\n", (int)arc_costs.parameter[0], (int)arc_costs.parameter[1]); break; case EXPONENTIAL: xprintf("c arc costs: EXPONENTIAL distr. lambda %d\n", (int)arc_costs.parameter[0]); break; default: xassert(csa != csa); } switch (capacities.distribution) { case UNIFORM: xprintf("c arc caps : UNIFORM distr. min %d max %d\n", (int)capacities.parameter[0], (int)capacities.parameter[1]); break; case EXPONENTIAL: xprintf("c arc caps : EXPONENTIAL distr. %d lambda %d\n", (int)capacities.parameter[0]); break; default: xassert(csa != csa); } skip: if (G == NULL) xprintf("p min %d %d\n", n_node, n_arc); else { glp_add_vertices(G, n_node); if (v_rhs >= 0) { double zero = 0.0; for (i = 1; i <= n_node; i++) { glp_vertex *v = G->v[i]; memcpy((char *)v->data + v_rhs, &zero, sizeof(double)); } } } /* Output "n node supply". */ for (i = 0, imb_ptr = source_list; i < n_source; i++, imb_ptr++) { if (G == NULL) xprintf("n %d %d\n", imb_ptr->node, imb_ptr->supply); else { if (v_rhs >= 0) { double temp = (double)imb_ptr->supply; glp_vertex *v = G->v[imb_ptr->node]; memcpy((char *)v->data + v_rhs, &temp, sizeof(double)); } } } for (i = 0, imb_ptr = sink_list; i < n_sink; i++, imb_ptr++) { if (G == NULL) xprintf("n %d %d\n", imb_ptr->node, imb_ptr->supply); else { if (v_rhs >= 0) { double temp = (double)imb_ptr->supply; glp_vertex *v = G->v[imb_ptr->node]; memcpy((char *)v->data + v_rhs, &temp, sizeof(double)); } } } /* Output "a from to lowcap=0 hicap cost". */ for (i = 0, arc_ptr = arc_list; i < n_arc; i++, arc_ptr++) { if (G == NULL) xprintf("a %d %d 0 %d %d\n", arc_ptr->from, arc_ptr->to, arc_ptr->u, arc_ptr->cost); else { glp_arc *a = glp_add_arc(G, arc_ptr->from, arc_ptr->to); if (a_cap >= 0) { double temp = (double)arc_ptr->u; memcpy((char *)a->data + a_cap, &temp, sizeof(double)); } if (a_cost >= 0) { double temp = (double)arc_ptr->cost; memcpy((char *)a->data + a_cost, &temp, sizeof(double)); } } } return; } static double randy(struct csa *csa) { /* Returns a random number between 0.0 and 1.0. See Ward Cheney & David Kincaid, "Numerical Mathematics and Computing," 2Ed, pp. 335. */ seed = 16807 * seed % 2147483647; if (seed < 0) seed = - seed; return seed * 4.6566128752459e-10; } static void select_source_sinks(struct csa *csa) { /* Randomly select the source nodes and sink nodes. */ int i, *int_ptr; int *temp_list; /* a temporary list of nodes */ struct imbalance *ptr; double ab[2]; /* parameter for random number generator */ ab[0] = 0.9; ab[1] = n_node - 0.99; /* upper limit is n_node-1 because the supernode cannot be selected */ temp_list = xcalloc(n_node, sizeof(int)); for (i = 0, int_ptr = temp_list; i < n_node; i++, int_ptr++) *int_ptr = 0; /* Select the source nodes. */ for (i = 0, ptr = source_list; i < n_source; i++, ptr++) { ptr->node = uniform(csa, ab); if (temp_list[ptr->node] == 1) /* check for duplicates */ { ptr--; i--; } else temp_list[ptr->node] = 1; } /* Select the sink nodes. */ for (i = 0, ptr = sink_list; i < n_sink; i++, ptr++) { ptr->node = uniform(csa, ab); if (temp_list[ptr->node] == 1) { ptr--; i--; } else temp_list[ptr->node] = 1; } xfree(temp_list); return; } int uniform(struct csa *csa, double a[2]) { /* Generates an integer uniformly selected from [a[0],a[1]]. */ return (int)((a[1] - a[0]) * randy(csa) + a[0] + 0.5); } /**********************************************************************/ #if 0 int main(void) { int parm[1+14]; double temp; scanf("%d", &parm[1]); scanf("%d", &parm[2]); scanf("%d", &parm[3]); scanf("%d", &parm[4]); scanf("%d", &parm[5]); scanf("%d", &parm[6]); scanf("%d", &parm[7]); scanf("%d", &parm[8]); scanf("%d", &parm[9]); if (parm[9] == 1) { scanf("%d", &parm[10]); scanf("%d", &parm[11]); } else { scanf("%le", &temp); parm[10] = (int)(100.0 * temp + .5); parm[11] = 0; } scanf("%d", &parm[12]); if (parm[12] == 1) { scanf("%d", &parm[13]); scanf("%d", &parm[14]); } else { scanf("%le", &temp); parm[13] = (int)(100.0 * temp + .5); parm[14] = 0; } glp_gridgen(NULL, 0, 0, 0, parm); return 0; } #endif /* eof */ sources_5316/external/glpk/glpapi08.c0000644000176700017670000003030111401660400016257 0ustar paulpaul/* glpapi08.c (interior-point method routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" #include "glpipm.h" #include "glpnpp.h" /*********************************************************************** * NAME * * glp_interior - solve LP problem with the interior-point method * * SYNOPSIS * * int glp_interior(glp_prob *P, const glp_iptcp *parm); * * The routine glp_interior is a driver to the LP solver based on the * interior-point method. * * The interior-point solver has a set of control parameters. Values of * the control parameters can be passed in a structure glp_iptcp, which * the parameter parm points to. * * Currently this routine implements an easy variant of the primal-dual * interior-point method based on Mehrotra's technique. * * This routine transforms the original LP problem to an equivalent LP * problem in the standard formulation (all constraints are equalities, * all variables are non-negative), calls the routine ipm_main to solve * the transformed problem, and then transforms an obtained solution to * the solution of the original problem. * * RETURNS * * 0 The LP problem instance has been successfully solved. This code * does not necessarily mean that the solver has found optimal * solution. It only means that the solution process was successful. * * GLP_EFAIL * The problem has no rows/columns. * * GLP_ENOCVG * Very slow convergence or divergence. * * GLP_EITLIM * Iteration limit exceeded. * * GLP_EINSTAB * Numerical instability on solving Newtonian system. */ static void transform(NPP *npp) { /* transform LP to the standard formulation */ NPPROW *row, *prev_row; NPPCOL *col, *prev_col; for (row = npp->r_tail; row != NULL; row = prev_row) { prev_row = row->prev; if (row->lb == -DBL_MAX && row->ub == +DBL_MAX) npp_free_row(npp, row); else if (row->lb == -DBL_MAX) npp_leq_row(npp, row); else if (row->ub == +DBL_MAX) npp_geq_row(npp, row); else if (row->lb != row->ub) { if (fabs(row->lb) < fabs(row->ub)) npp_geq_row(npp, row); else npp_leq_row(npp, row); } } for (col = npp->c_tail; col != NULL; col = prev_col) { prev_col = col->prev; if (col->lb == -DBL_MAX && col->ub == +DBL_MAX) npp_free_col(npp, col); else if (col->lb == -DBL_MAX) npp_ubnd_col(npp, col); else if (col->ub == +DBL_MAX) { if (col->lb != 0.0) npp_lbnd_col(npp, col); } else if (col->lb != col->ub) { if (fabs(col->lb) < fabs(col->ub)) { if (col->lb != 0.0) npp_lbnd_col(npp, col); } else npp_ubnd_col(npp, col); npp_dbnd_col(npp, col); } else npp_fixed_col(npp, col); } for (row = npp->r_head; row != NULL; row = row->next) xassert(row->lb == row->ub); for (col = npp->c_head; col != NULL; col = col->next) xassert(col->lb == 0.0 && col->ub == +DBL_MAX); return; } int glp_interior(glp_prob *P, const glp_iptcp *parm) { glp_iptcp _parm; GLPROW *row; GLPCOL *col; NPP *npp = NULL; glp_prob *prob = NULL; int i, j, ret; /* check control parameters */ if (parm == NULL) glp_init_iptcp(&_parm), parm = &_parm; if (!(parm->msg_lev == GLP_MSG_OFF || parm->msg_lev == GLP_MSG_ERR || parm->msg_lev == GLP_MSG_ON || parm->msg_lev == GLP_MSG_ALL)) xerror("glp_interior: msg_lev = %d; invalid parameter\n", parm->msg_lev); if (!(parm->ord_alg == GLP_ORD_NONE || parm->ord_alg == GLP_ORD_QMD || parm->ord_alg == GLP_ORD_AMD || parm->ord_alg == GLP_ORD_SYMAMD)) xerror("glp_interior: ord_alg = %d; invalid parameter\n", parm->ord_alg); /* interior-point solution is currently undefined */ P->ipt_stat = GLP_UNDEF; P->ipt_obj = 0.0; /* check bounds of double-bounded variables */ for (i = 1; i <= P->m; i++) { row = P->row[i]; if (row->type == GLP_DB && row->lb >= row->ub) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_interior: row %d: lb = %g, ub = %g; incorre" "ct bounds\n", i, row->lb, row->ub); ret = GLP_EBOUND; goto done; } } for (j = 1; j <= P->n; j++) { col = P->col[j]; if (col->type == GLP_DB && col->lb >= col->ub) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_interior: column %d: lb = %g, ub = %g; inco" "rrect bounds\n", j, col->lb, col->ub); ret = GLP_EBOUND; goto done; } } /* transform LP to the standard formulation */ if (parm->msg_lev >= GLP_MSG_ALL) xprintf("Original LP has %d row(s), %d column(s), and %d non-z" "ero(s)\n", P->m, P->n, P->nnz); npp = npp_create_wksp(); npp_load_prob(npp, P, GLP_OFF, GLP_IPT, GLP_ON); transform(npp); prob = glp_create_prob(); npp_build_prob(npp, prob); if (parm->msg_lev >= GLP_MSG_ALL) xprintf("Working LP has %d row(s), %d column(s), and %d non-ze" "ro(s)\n", prob->m, prob->n, prob->nnz); #if 1 /* currently empty problem cannot be solved */ if (!(prob->m > 0 && prob->n > 0)) { if (parm->msg_lev >= GLP_MSG_ERR) xprintf("glp_interior: unable to solve empty problem\n"); ret = GLP_EFAIL; goto done; } #endif /* scale the resultant LP */ { ENV *env = get_env_ptr(); int term_out = env->term_out; env->term_out = GLP_OFF; glp_scale_prob(prob, GLP_SF_EQ); env->term_out = term_out; } /* warn about dense columns */ if (parm->msg_lev >= GLP_MSG_ON && prob->m >= 200) { int len, cnt = 0; for (j = 1; j <= prob->n; j++) { len = glp_get_mat_col(prob, j, NULL, NULL); if ((double)len >= 0.20 * (double)prob->m) cnt++; } if (cnt == 1) xprintf("WARNING: PROBLEM HAS ONE DENSE COLUMN\n"); else if (cnt > 0) xprintf("WARNING: PROBLEM HAS %d DENSE COLUMNS\n", cnt); } /* solve the transformed LP */ ret = ipm_solve(prob, parm); /* postprocess solution from the transformed LP */ npp_postprocess(npp, prob); /* and store solution to the original LP */ npp_unload_sol(npp, P); done: /* free working program objects */ if (npp != NULL) npp_delete_wksp(npp); if (prob != NULL) glp_delete_prob(prob); /* return to the application program */ return ret; } /*********************************************************************** * NAME * * glp_init_iptcp - initialize interior-point solver control parameters * * SYNOPSIS * * void glp_init_iptcp(glp_iptcp *parm); * * DESCRIPTION * * The routine glp_init_iptcp initializes control parameters, which are * used by the interior-point solver, with default values. * * Default values of the control parameters are stored in the glp_iptcp * structure, which the parameter parm points to. */ void glp_init_iptcp(glp_iptcp *parm) { parm->msg_lev = GLP_MSG_ALL; parm->ord_alg = GLP_ORD_AMD; return; } /*********************************************************************** * NAME * * glp_ipt_status - retrieve status of interior-point solution * * SYNOPSIS * * int glp_ipt_status(glp_prob *lp); * * RETURNS * * The routine glp_ipt_status reports the status of solution found by * the interior-point solver as follows: * * GLP_UNDEF - interior-point solution is undefined; * GLP_OPT - interior-point solution is optimal; * GLP_INFEAS - interior-point solution is infeasible; * GLP_NOFEAS - no feasible solution exists. */ int glp_ipt_status(glp_prob *lp) { int ipt_stat = lp->ipt_stat; return ipt_stat; } /*********************************************************************** * NAME * * glp_ipt_obj_val - retrieve objective value (interior point) * * SYNOPSIS * * double glp_ipt_obj_val(glp_prob *lp); * * RETURNS * * The routine glp_ipt_obj_val returns value of the objective function * for interior-point solution. */ double glp_ipt_obj_val(glp_prob *lp) { /*struct LPXCPS *cps = lp->cps;*/ double z; z = lp->ipt_obj; /*if (cps->round && fabs(z) < 1e-9) z = 0.0;*/ return z; } /*********************************************************************** * NAME * * glp_ipt_row_prim - retrieve row primal value (interior point) * * SYNOPSIS * * double glp_ipt_row_prim(glp_prob *lp, int i); * * RETURNS * * The routine glp_ipt_row_prim returns primal value of the auxiliary * variable associated with i-th row. */ double glp_ipt_row_prim(glp_prob *lp, int i) { /*struct LPXCPS *cps = lp->cps;*/ double pval; if (!(1 <= i && i <= lp->m)) xerror("glp_ipt_row_prim: i = %d; row number out of range\n", i); pval = lp->row[i]->pval; /*if (cps->round && fabs(pval) < 1e-9) pval = 0.0;*/ return pval; } /*********************************************************************** * NAME * * glp_ipt_row_dual - retrieve row dual value (interior point) * * SYNOPSIS * * double glp_ipt_row_dual(glp_prob *lp, int i); * * RETURNS * * The routine glp_ipt_row_dual returns dual value (i.e. reduced cost) * of the auxiliary variable associated with i-th row. */ double glp_ipt_row_dual(glp_prob *lp, int i) { /*struct LPXCPS *cps = lp->cps;*/ double dval; if (!(1 <= i && i <= lp->m)) xerror("glp_ipt_row_dual: i = %d; row number out of range\n", i); dval = lp->row[i]->dval; /*if (cps->round && fabs(dval) < 1e-9) dval = 0.0;*/ return dval; } /*********************************************************************** * NAME * * glp_ipt_col_prim - retrieve column primal value (interior point) * * SYNOPSIS * * double glp_ipt_col_prim(glp_prob *lp, int j); * * RETURNS * * The routine glp_ipt_col_prim returns primal value of the structural * variable associated with j-th column. */ double glp_ipt_col_prim(glp_prob *lp, int j) { /*struct LPXCPS *cps = lp->cps;*/ double pval; if (!(1 <= j && j <= lp->n)) xerror("glp_ipt_col_prim: j = %d; column number out of range\n" , j); pval = lp->col[j]->pval; /*if (cps->round && fabs(pval) < 1e-9) pval = 0.0;*/ return pval; } /*********************************************************************** * NAME * * glp_ipt_col_dual - retrieve column dual value (interior point) * * SYNOPSIS * * #include "glplpx.h" * double glp_ipt_col_dual(glp_prob *lp, int j); * * RETURNS * * The routine glp_ipt_col_dual returns dual value (i.e. reduced cost) * of the structural variable associated with j-th column. */ double glp_ipt_col_dual(glp_prob *lp, int j) { /*struct LPXCPS *cps = lp->cps;*/ double dval; if (!(1 <= j && j <= lp->n)) xerror("glp_ipt_col_dual: j = %d; column number out of range\n" , j); dval = lp->col[j]->dval; /*if (cps->round && fabs(dval) < 1e-9) dval = 0.0;*/ return dval; } /* eof */ sources_5316/external/glpk/amd_defaults.c0000644000176700017670000000257311401660400017275 0ustar paulpaul/* ========================================================================= */ /* === AMD_defaults ======================================================== */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* User-callable. Sets default control parameters for AMD. See amd.h * for details. */ #include "amd_internal.h" /* ========================================================================= */ /* === AMD defaults ======================================================== */ /* ========================================================================= */ GLOBAL void AMD_defaults ( double Control [ ] ) { Int i ; if (Control != (double *) NULL) { for (i = 0 ; i < AMD_CONTROL ; i++) { Control [i] = 0 ; } Control [AMD_DENSE] = AMD_DEFAULT_DENSE ; Control [AMD_AGGRESSIVE] = AMD_DEFAULT_AGGRESSIVE ; } } sources_5316/external/glpk/glpnet01.c0000644000176700017670000002335011401660400016273 0ustar paulpaul/* glpnet01.c (permutations for zero-free diagonal) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * This code is the result of translation of the Fortran subroutines * MC21A and MC21B associated with the following paper: * * I.S.Duff, Algorithm 575: Permutations for zero-free diagonal, ACM * Trans. on Math. Softw. 7 (1981), 387-390. * * Use of ACM Algorithms is subject to the ACM Software Copyright and * License Agreement. See . * * The translation was made by Andrew Makhorin . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpnet.h" /*********************************************************************** * NAME * * mc21a - permutations for zero-free diagonal * * SYNOPSIS * * #include "glpnet.h" * int mc21a(int n, const int icn[], const int ip[], const int lenr[], * int iperm[], int pr[], int arp[], int cv[], int out[]); * * DESCRIPTION * * Given the pattern of nonzeros of a sparse matrix, the routine mc21a * attempts to find a permutation of its rows that makes the matrix have * no zeros on its diagonal. * * INPUT PARAMETERS * * n order of matrix. * * icn array containing the column indices of the non-zeros. Those * belonging to a single row must be contiguous but the ordering * of column indices within each row is unimportant and wasted * space between rows is permitted. * * ip ip[i], i = 1,2,...,n, is the position in array icn of the * first column index of a non-zero in row i. * * lenr lenr[i], i = 1,2,...,n, is the number of non-zeros in row i. * * OUTPUT PARAMETER * * iperm contains permutation to make diagonal have the smallest * number of zeros on it. Elements (iperm[i], i), i = 1,2,...,n, * are non-zero at the end of the algorithm unless the matrix is * structurally singular. In this case, (iperm[i], i) will be * zero for n - numnz entries. * * WORKING ARRAYS * * pr working array of length [1+n], where pr[0] is not used. * pr[i] is the previous row to i in the depth first search. * * arp working array of length [1+n], where arp[0] is not used. * arp[i] is one less than the number of non-zeros in row i which * have not been scanned when looking for a cheap assignment. * * cv working array of length [1+n], where cv[0] is not used. * cv[i] is the most recent row extension at which column i was * visited. * * out working array of length [1+n], where out[0] is not used. * out[i] is one less than the number of non-zeros in row i * which have not been scanned during one pass through the main * loop. * * RETURNS * * The routine mc21a returns numnz, the number of non-zeros on diagonal * of permuted matrix. */ int mc21a(int n, const int icn[], const int ip[], const int lenr[], int iperm[], int pr[], int arp[], int cv[], int out[]) { int i, ii, in1, in2, j, j1, jord, k, kk, numnz; /* Initialization of arrays. */ for (i = 1; i <= n; i++) { arp[i] = lenr[i] - 1; cv[i] = iperm[i] = 0; } numnz = 0; /* Main loop. */ /* Each pass round this loop either results in a new assignment or gives a row with no assignment. */ for (jord = 1; jord <= n; jord++) { j = jord; pr[j] = -1; for (k = 1; k <= jord; k++) { /* Look for a cheap assignment. */ in1 = arp[j]; if (in1 >= 0) { in2 = ip[j] + lenr[j] - 1; in1 = in2 - in1; for (ii = in1; ii <= in2; ii++) { i = icn[ii]; if (iperm[i] == 0) goto L110; } /* No cheap assignment in row. */ arp[j] = -1; } /* Begin looking for assignment chain starting with row j.*/ out[j] = lenr[j] - 1; /* Inner loop. Extends chain by one or backtracks. */ for (kk = 1; kk <= jord; kk++) { in1 = out[j]; if (in1 >= 0) { in2 = ip[j] + lenr[j] - 1; in1 = in2 - in1; /* Forward scan. */ for (ii = in1; ii <= in2; ii++) { i = icn[ii]; if (cv[i] != jord) { /* Column i has not yet been accessed during this pass. */ j1 = j; j = iperm[i]; cv[i] = jord; pr[j] = j1; out[j1] = in2 - ii - 1; goto L100; } } } /* Backtracking step. */ j = pr[j]; if (j == -1) goto L130; } L100: ; } L110: /* New assignment is made. */ iperm[i] = j; arp[j] = in2 - ii - 1; numnz++; for (k = 1; k <= jord; k++) { j = pr[j]; if (j == -1) break; ii = ip[j] + lenr[j] - out[j] - 2; i = icn[ii]; iperm[i] = j; } L130: ; } /* If matrix is structurally singular, we now complete the permutation iperm. */ if (numnz < n) { for (i = 1; i <= n; i++) arp[i] = 0; k = 0; for (i = 1; i <= n; i++) { if (iperm[i] == 0) out[++k] = i; else arp[iperm[i]] = i; } k = 0; for (i = 1; i <= n; i++) { if (arp[i] == 0) iperm[out[++k]] = i; } } return numnz; } /**********************************************************************/ #if 0 #include "glplib.h" int sing; void ranmat(int m, int n, int icn[], int iptr[], int nnnp1, int *knum, int iw[]); void fa01bs(int max, int *nrand); int main(void) { /* test program for the routine mc21a */ /* these runs on random matrices cause all possible statements in mc21a to be executed */ int i, iold, j, j1, j2, jj, knum, l, licn, n, nov4, num, numnz; int ip[1+21], icn[1+1000], iperm[1+20], lenr[1+20], iw1[1+80]; licn = 1000; /* run on random matrices of orders 1 through 20 */ for (n = 1; n <= 20; n++) { nov4 = n / 4; if (nov4 < 1) nov4 = 1; L10: fa01bs(nov4, &l); knum = l * n; /* knum is requested number of non-zeros in random matrix */ if (knum > licn) goto L10; /* if sing is false, matrix is guaranteed structurally non-singular */ sing = ((n / 2) * 2 == n); /* call to subroutine to generate random matrix */ ranmat(n, n, icn, ip, n+1, &knum, iw1); /* knum is now actual number of non-zeros in random matrix */ if (knum > licn) goto L10; xprintf("n = %2d; nz = %4d; sing = %d\n", n, knum, sing); /* set up array of row lengths */ for (i = 1; i <= n; i++) lenr[i] = ip[i+1] - ip[i]; /* call to mc21a */ numnz = mc21a(n, icn, ip, lenr, iperm, &iw1[0], &iw1[n], &iw1[n+n], &iw1[n+n+n]); /* testing to see if there are numnz non-zeros on the diagonal of the permuted matrix. */ num = 0; for (i = 1; i <= n; i++) { iold = iperm[i]; j1 = ip[iold]; j2 = j1 + lenr[iold] - 1; if (j2 < j1) continue; for (jj = j1; jj <= j2; jj++) { j = icn[jj]; if (j == i) { num++; break; } } } if (num != numnz) xprintf("Failure in mc21a, numnz = %d instead of %d\n", numnz, num); } return 0; } void ranmat(int m, int n, int icn[], int iptr[], int nnnp1, int *knum, int iw[]) { /* subroutine to generate random matrix */ int i, ii, inum, j, lrow, matnum; inum = (*knum / n) * 2; if (inum > n-1) inum = n-1; matnum = 1; /* each pass through this loop generates a row of the matrix */ for (j = 1; j <= m; j++) { iptr[j] = matnum; if (!(sing || j > n)) icn[matnum++] = j; if (n == 1) continue; for (i = 1; i <= n; i++) iw[i] = 0; if (!sing) iw[j] = 1; fa01bs(inum, &lrow); lrow--; if (lrow == 0) continue; /* lrow off-diagonal non-zeros in row j of the matrix */ for (ii = 1; ii <= lrow; ii++) { for (;;) { fa01bs(n, &i); if (iw[i] != 1) break; } iw[i] = 1; icn[matnum++] = i; } } for (i = m+1; i <= nnnp1; i++) iptr[i] = matnum; *knum = matnum - 1; return; } double g = 1431655765.0; double fa01as(int i) { /* random number generator */ g = fmod(g * 9228907.0, 4294967296.0); if (i >= 0) return g / 4294967296.0; else return 2.0 * g / 4294967296.0 - 1.0; } void fa01bs(int max, int *nrand) { *nrand = (int)(fa01as(1) * (double)max) + 1; return; } #endif /* eof */ sources_5316/external/glpk/glpios11.c0000644000176700017670000002471611401660400016307 0ustar paulpaul/* glpios11.c (process cuts stored in the local cut pool) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpios.h" /*********************************************************************** * NAME * * ios_process_cuts - process cuts stored in the local cut pool * * SYNOPSIS * * #include "glpios.h" * void ios_process_cuts(glp_tree *T); * * DESCRIPTION * * The routine ios_process_cuts analyzes each cut currently stored in * the local cut pool, which must be non-empty, and either adds the cut * to the current subproblem or just discards it. All cuts are assumed * to be locally valid. On exit the local cut pool remains unchanged. * * REFERENCES * * 1. E.Balas, S.Ceria, G.Cornuejols, "Mixed 0-1 Programming by * Lift-and-Project in a Branch-and-Cut Framework", Management Sc., * 42 (1996) 1229-1246. * * 2. G.Andreello, A.Caprara, and M.Fischetti, "Embedding Cuts in * a Branch&Cut Framework: a Computational Study with {0,1/2}-Cuts", * Preliminary Draft, October 28, 2003, pp.6-8. */ struct info { /* estimated cut efficiency */ IOSCUT *cut; /* pointer to cut in the cut pool */ char flag; /* if this flag is set, the cut is included into the current subproblem */ double eff; /* cut efficacy (normalized residual) */ double deg; /* lower bound to objective degradation */ }; static int fcmp(const void *arg1, const void *arg2) { const struct info *info1 = arg1, *info2 = arg2; if (info1->deg == 0.0 && info2->deg == 0.0) { if (info1->eff > info2->eff) return -1; if (info1->eff < info2->eff) return +1; } else { if (info1->deg > info2->deg) return -1; if (info1->deg < info2->deg) return +1; } return 0; } static double parallel(IOSCUT *a, IOSCUT *b, double work[]); void ios_process_cuts(glp_tree *T) { IOSPOOL *pool; IOSCUT *cut; IOSAIJ *aij; struct info *info; int k, kk, max_cuts, len, ret, *ind; double *val, *work; /* the current subproblem must exist */ xassert(T->curr != NULL); /* the pool must exist and be non-empty */ pool = T->local; xassert(pool != NULL); xassert(pool->size > 0); /* allocate working arrays */ info = xcalloc(1+pool->size, sizeof(struct info)); ind = xcalloc(1+T->n, sizeof(int)); val = xcalloc(1+T->n, sizeof(double)); work = xcalloc(1+T->n, sizeof(double)); for (k = 1; k <= T->n; k++) work[k] = 0.0; /* build the list of cuts stored in the cut pool */ for (k = 0, cut = pool->head; cut != NULL; cut = cut->next) k++, info[k].cut = cut, info[k].flag = 0; xassert(k == pool->size); /* estimate efficiency of all cuts in the cut pool */ for (k = 1; k <= pool->size; k++) { double temp, dy, dz; cut = info[k].cut; /* build the vector of cut coefficients and compute its Euclidean norm */ len = 0; temp = 0.0; for (aij = cut->ptr; aij != NULL; aij = aij->next) { xassert(1 <= aij->j && aij->j <= T->n); len++, ind[len] = aij->j, val[len] = aij->val; temp += aij->val * aij->val; } if (temp < DBL_EPSILON * DBL_EPSILON) temp = DBL_EPSILON; /* transform the cut to express it only through non-basic (auxiliary and structural) variables */ len = glp_transform_row(T->mip, len, ind, val); /* determine change in the cut value and in the objective value for the adjacent basis by simulating one step of the dual simplex */ ret = _glp_analyze_row(T->mip, len, ind, val, cut->type, cut->rhs, 1e-9, NULL, NULL, NULL, NULL, &dy, &dz); /* determine normalized residual and lower bound to objective degradation */ if (ret == 0) { info[k].eff = fabs(dy) / sqrt(temp); /* if some reduced costs violates (slightly) their zero bounds (i.e. have wrong signs) due to round-off errors, dz also may have wrong sign being close to zero */ if (T->mip->dir == GLP_MIN) { if (dz < 0.0) dz = 0.0; info[k].deg = + dz; } else /* GLP_MAX */ { if (dz > 0.0) dz = 0.0; info[k].deg = - dz; } } else if (ret == 1) { /* the constraint is not violated at the current point */ info[k].eff = info[k].deg = 0.0; } else if (ret == 2) { /* no dual feasible adjacent basis exists */ info[k].eff = 1.0; info[k].deg = DBL_MAX; } else xassert(ret != ret); /* if the degradation is too small, just ignore it */ if (info[k].deg < 0.01) info[k].deg = 0.0; } /* sort the list of cuts by decreasing objective degradation and then by decreasing efficacy */ qsort(&info[1], pool->size, sizeof(struct info), fcmp); /* only first (most efficient) max_cuts in the list are qualified as candidates to be added to the current subproblem */ max_cuts = (T->curr->level == 0 ? 90 : 10); if (max_cuts > pool->size) max_cuts = pool->size; /* add cuts to the current subproblem */ #if 0 xprintf("*** adding cuts ***\n"); #endif for (k = 1; k <= max_cuts; k++) { int i, len; /* if this cut seems to be inefficient, skip it */ if (info[k].deg < 0.01 && info[k].eff < 0.01) continue; /* if the angle between this cut and every other cut included in the current subproblem is small, skip this cut */ for (kk = 1; kk < k; kk++) { if (info[kk].flag) { if (parallel(info[k].cut, info[kk].cut, work) > 0.90) break; } } if (kk < k) continue; /* add this cut to the current subproblem */ #if 0 xprintf("eff = %g; deg = %g\n", info[k].eff, info[k].deg); #endif cut = info[k].cut, info[k].flag = 1; i = glp_add_rows(T->mip, 1); if (cut->name != NULL) glp_set_row_name(T->mip, i, cut->name); xassert(T->mip->row[i]->origin == GLP_RF_CUT); T->mip->row[i]->klass = cut->klass; len = 0; for (aij = cut->ptr; aij != NULL; aij = aij->next) len++, ind[len] = aij->j, val[len] = aij->val; glp_set_mat_row(T->mip, i, len, ind, val); xassert(cut->type == GLP_LO || cut->type == GLP_UP); glp_set_row_bnds(T->mip, i, cut->type, cut->rhs, cut->rhs); } /* free working arrays */ xfree(info); xfree(ind); xfree(val); xfree(work); return; } #if 0 /*********************************************************************** * Given a cut a * x >= b (<= b) the routine efficacy computes the cut * efficacy as follows: * * eff = d * (a * x~ - b) / ||a||, * * where d is -1 (in case of '>= b') or +1 (in case of '<= b'), x~ is * the vector of values of structural variables in optimal solution to * LP relaxation of the current subproblem, ||a|| is the Euclidean norm * of the vector of cut coefficients. * * If the cut is violated at point x~, the efficacy eff is positive, * and its value is the Euclidean distance between x~ and the cut plane * a * x = b in the space of structural variables. * * Following geometrical intuition, it is quite natural to consider * this distance as a first-order measure of the expected efficacy of * the cut: the larger the distance the better the cut [1]. */ static double efficacy(glp_tree *T, IOSCUT *cut) { glp_prob *mip = T->mip; IOSAIJ *aij; double s = 0.0, t = 0.0, temp; for (aij = cut->ptr; aij != NULL; aij = aij->next) { xassert(1 <= aij->j && aij->j <= mip->n); s += aij->val * mip->col[aij->j]->prim; t += aij->val * aij->val; } temp = sqrt(t); if (temp < DBL_EPSILON) temp = DBL_EPSILON; if (cut->type == GLP_LO) temp = (s >= cut->rhs ? 0.0 : (cut->rhs - s) / temp); else if (cut->type == GLP_UP) temp = (s <= cut->rhs ? 0.0 : (s - cut->rhs) / temp); else xassert(cut != cut); return temp; } #endif /*********************************************************************** * Given two cuts a1 * x >= b1 (<= b1) and a2 * x >= b2 (<= b2) the * routine parallel computes the cosine of angle between the cut planes * a1 * x = b1 and a2 * x = b2 (which is the acute angle between two * normals to these planes) in the space of structural variables as * follows: * * cos phi = (a1' * a2) / (||a1|| * ||a2||), * * where (a1' * a2) is a dot product of vectors of cut coefficients, * ||a1|| and ||a2|| are Euclidean norms of vectors a1 and a2. * * Note that requirement cos phi = 0 forces the cuts to be orthogonal, * i.e. with disjoint support, while requirement cos phi <= 0.999 means * only avoiding duplicate (parallel) cuts [1]. */ static double parallel(IOSCUT *a, IOSCUT *b, double work[]) { IOSAIJ *aij; double s = 0.0, sa = 0.0, sb = 0.0, temp; for (aij = a->ptr; aij != NULL; aij = aij->next) { work[aij->j] = aij->val; sa += aij->val * aij->val; } for (aij = b->ptr; aij != NULL; aij = aij->next) { s += work[aij->j] * aij->val; sb += aij->val * aij->val; } for (aij = a->ptr; aij != NULL; aij = aij->next) work[aij->j] = 0.0; temp = sqrt(sa) * sqrt(sb); if (temp < DBL_EPSILON * DBL_EPSILON) temp = DBL_EPSILON; return s / temp; } /* eof */ sources_5316/external/glpk/glpssx.h0000644000176700017670000004013011401660400016161 0ustar paulpaul/* glpssx.h (simplex method, bignum arithmetic) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPSSX_H #define GLPSSX_H #include "glpbfx.h" #include "glpenv.h" typedef struct SSX SSX; struct SSX { /* simplex solver workspace */ /*---------------------------------------------------------------------- // LP PROBLEM DATA // // It is assumed that LP problem has the following statement: // // minimize (or maximize) // // z = c[1]*x[1] + ... + c[m+n]*x[m+n] + c[0] (1) // // subject to equality constraints // // x[1] - a[1,1]*x[m+1] - ... - a[1,n]*x[m+n] = 0 // // . . . . . . . (2) // // x[m] - a[m,1]*x[m+1] + ... - a[m,n]*x[m+n] = 0 // // and bounds of variables // // l[1] <= x[1] <= u[1] // // . . . . . . . (3) // // l[m+n] <= x[m+n] <= u[m+n] // // where: // x[1], ..., x[m] - auxiliary variables; // x[m+1], ..., x[m+n] - structural variables; // z - objective function; // c[1], ..., c[m+n] - coefficients of the objective function; // c[0] - constant term of the objective function; // a[1,1], ..., a[m,n] - constraint coefficients; // l[1], ..., l[m+n] - lower bounds of variables; // u[1], ..., u[m+n] - upper bounds of variables. // // Bounds of variables can be finite as well as inifinite. Besides, // lower and upper bounds can be equal to each other. So the following // five types of variables are possible: // // Bounds of variable Type of variable // ------------------------------------------------- // -inf < x[k] < +inf Free (unbounded) variable // l[k] <= x[k] < +inf Variable with lower bound // -inf < x[k] <= u[k] Variable with upper bound // l[k] <= x[k] <= u[k] Double-bounded variable // l[k] = x[k] = u[k] Fixed variable // // Using vector-matrix notations the LP problem (1)-(3) can be written // as follows: // // minimize (or maximize) // // z = c * x + c[0] (4) // // subject to equality constraints // // xR - A * xS = 0 (5) // // and bounds of variables // // l <= x <= u (6) // // where: // xR - vector of auxiliary variables; // xS - vector of structural variables; // x = (xR, xS) - vector of all variables; // z - objective function; // c - vector of objective coefficients; // c[0] - constant term of the objective function; // A - matrix of constraint coefficients (has m rows // and n columns); // l - vector of lower bounds of variables; // u - vector of upper bounds of variables. // // The simplex method makes no difference between auxiliary and // structural variables, so it is convenient to think the system of // equality constraints (5) written in a homogeneous form: // // (I | -A) * x = 0, (7) // // where (I | -A) is an augmented (m+n)xm constraint matrix, I is mxm // unity matrix whose columns correspond to auxiliary variables, and A // is the original mxn constraint matrix whose columns correspond to // structural variables. Note that only the matrix A is stored. ----------------------------------------------------------------------*/ int m; /* number of rows (auxiliary variables), m > 0 */ int n; /* number of columns (structural variables), n > 0 */ int *type; /* int type[1+m+n]; */ /* type[0] is not used; type[k], 1 <= k <= m+n, is the type of variable x[k]: */ #define SSX_FR 0 /* free (unbounded) variable */ #define SSX_LO 1 /* variable with lower bound */ #define SSX_UP 2 /* variable with upper bound */ #define SSX_DB 3 /* double-bounded variable */ #define SSX_FX 4 /* fixed variable */ mpq_t *lb; /* mpq_t lb[1+m+n]; alias: l */ /* lb[0] is not used; lb[k], 1 <= k <= m+n, is an lower bound of variable x[k]; if x[k] has no lower bound, lb[k] is zero */ mpq_t *ub; /* mpq_t ub[1+m+n]; alias: u */ /* ub[0] is not used; ub[k], 1 <= k <= m+n, is an upper bound of variable x[k]; if x[k] has no upper bound, ub[k] is zero; if x[k] is of fixed type, ub[k] is equal to lb[k] */ int dir; /* optimization direction (sense of the objective function): */ #define SSX_MIN 0 /* minimization */ #define SSX_MAX 1 /* maximization */ mpq_t *coef; /* mpq_t coef[1+m+n]; alias: c */ /* coef[0] is a constant term of the objective function; coef[k], 1 <= k <= m+n, is a coefficient of the objective function at variable x[k]; note that auxiliary variables also may have non-zero objective coefficients */ int *A_ptr; /* int A_ptr[1+n+1]; */ int *A_ind; /* int A_ind[A_ptr[n+1]]; */ mpq_t *A_val; /* mpq_t A_val[A_ptr[n+1]]; */ /* constraint matrix A (see (5)) in storage-by-columns format */ /*---------------------------------------------------------------------- // LP BASIS AND CURRENT BASIC SOLUTION // // The LP basis is defined by the following partition of the augmented // constraint matrix (7): // // (B | N) = (I | -A) * Q, (8) // // where B is a mxm non-singular basis matrix whose columns correspond // to basic variables xB, N is a mxn matrix whose columns correspond to // non-basic variables xN, and Q is a permutation (m+n)x(m+n) matrix. // // From (7) and (8) it follows that // // (I | -A) * x = (I | -A) * Q * Q' * x = (B | N) * (xB, xN), // // therefore // // (xB, xN) = Q' * x, (9) // // where x is the vector of all variables in the original order, xB is // a vector of basic variables, xN is a vector of non-basic variables, // Q' = inv(Q) is a matrix transposed to Q. // // Current values of non-basic variables xN[j], j = 1, ..., n, are not // stored; they are defined implicitly by their statuses as follows: // // 0, if xN[j] is free variable // lN[j], if xN[j] is on its lower bound (10) // uN[j], if xN[j] is on its upper bound // lN[j] = uN[j], if xN[j] is fixed variable // // where lN[j] and uN[j] are lower and upper bounds of xN[j]. // // Current values of basic variables xB[i], i = 1, ..., m, are computed // as follows: // // beta = - inv(B) * N * xN, (11) // // where current values of xN are defined by (10). // // Current values of simplex multipliers pi[i], i = 1, ..., m (which // are values of Lagrange multipliers for equality constraints (7) also // called shadow prices) are computed as follows: // // pi = inv(B') * cB, (12) // // where B' is a matrix transposed to B, cB is a vector of objective // coefficients at basic variables xB. // // Current values of reduced costs d[j], j = 1, ..., n, (which are // values of Langrange multipliers for active inequality constraints // corresponding to non-basic variables) are computed as follows: // // d = cN - N' * pi, (13) // // where N' is a matrix transposed to N, cN is a vector of objective // coefficients at non-basic variables xN. ----------------------------------------------------------------------*/ int *stat; /* int stat[1+m+n]; */ /* stat[0] is not used; stat[k], 1 <= k <= m+n, is the status of variable x[k]: */ #define SSX_BS 0 /* basic variable */ #define SSX_NL 1 /* non-basic variable on lower bound */ #define SSX_NU 2 /* non-basic variable on upper bound */ #define SSX_NF 3 /* non-basic free variable */ #define SSX_NS 4 /* non-basic fixed variable */ int *Q_row; /* int Q_row[1+m+n]; */ /* matrix Q in row-like format; Q_row[0] is not used; Q_row[i] = j means that q[i,j] = 1 */ int *Q_col; /* int Q_col[1+m+n]; */ /* matrix Q in column-like format; Q_col[0] is not used; Q_col[j] = i means that q[i,j] = 1 */ /* if k-th column of the matrix (I | A) is k'-th column of the matrix (B | N), then Q_row[k] = k' and Q_col[k'] = k; if x[k] is xB[i], then Q_row[k] = i and Q_col[i] = k; if x[k] is xN[j], then Q_row[k] = m+j and Q_col[m+j] = k */ BFX *binv; /* invertable form of the basis matrix B */ mpq_t *bbar; /* mpq_t bbar[1+m]; alias: beta */ /* bbar[0] is a value of the objective function; bbar[i], 1 <= i <= m, is a value of basic variable xB[i] */ mpq_t *pi; /* mpq_t pi[1+m]; */ /* pi[0] is not used; pi[i], 1 <= i <= m, is a simplex multiplier corresponding to i-th row (equality constraint) */ mpq_t *cbar; /* mpq_t cbar[1+n]; alias: d */ /* cbar[0] is not used; cbar[j], 1 <= j <= n, is a reduced cost of non-basic variable xN[j] */ /*---------------------------------------------------------------------- // SIMPLEX TABLE // // Due to (8) and (9) the system of equality constraints (7) for the // current basis can be written as follows: // // xB = A~ * xN, (14) // // where // // A~ = - inv(B) * N (15) // // is a mxn matrix called the simplex table. // // The revised simplex method uses only two components of A~, namely, // pivot column corresponding to non-basic variable xN[q] chosen to // enter the basis, and pivot row corresponding to basic variable xB[p] // chosen to leave the basis. // // Pivot column alfa_q is q-th column of A~, so // // alfa_q = A~ * e[q] = - inv(B) * N * e[q] = - inv(B) * N[q], (16) // // where N[q] is q-th column of the matrix N. // // Pivot row alfa_p is p-th row of A~ or, equivalently, p-th column of // A~', a matrix transposed to A~, so // // alfa_p = A~' * e[p] = - N' * inv(B') * e[p] = - N' * rho_p, (17) // // where (*)' means transposition, and // // rho_p = inv(B') * e[p], (18) // // is p-th column of inv(B') or, that is the same, p-th row of inv(B). ----------------------------------------------------------------------*/ int p; /* number of basic variable xB[p], 1 <= p <= m, chosen to leave the basis */ mpq_t *rho; /* mpq_t rho[1+m]; */ /* p-th row of the inverse inv(B); see (18) */ mpq_t *ap; /* mpq_t ap[1+n]; */ /* p-th row of the simplex table; see (17) */ int q; /* number of non-basic variable xN[q], 1 <= q <= n, chosen to enter the basis */ mpq_t *aq; /* mpq_t aq[1+m]; */ /* q-th column of the simplex table; see (16) */ /*--------------------------------------------------------------------*/ int q_dir; /* direction in which non-basic variable xN[q] should change on moving to the adjacent vertex of the polyhedron: +1 means that xN[q] increases -1 means that xN[q] decreases */ int p_stat; /* non-basic status which should be assigned to basic variable xB[p] when it has left the basis and become xN[q] */ mpq_t delta; /* actual change of xN[q] in the adjacent basis (it has the same sign as q_dir) */ /*--------------------------------------------------------------------*/ int it_lim; /* simplex iterations limit; if this value is positive, it is decreased by one each time when one simplex iteration has been performed, and reaching zero value signals the solver to stop the search; negative value means no iterations limit */ int it_cnt; /* simplex iterations count; this count is increased by one each time when one simplex iteration has been performed */ double tm_lim; /* searching time limit, in seconds; if this value is positive, it is decreased each time when one simplex iteration has been performed by the amount of time spent for the iteration, and reaching zero value signals the solver to stop the search; negative value means no time limit */ double out_frq; /* output frequency, in seconds; this parameter specifies how frequently the solver sends information about the progress of the search to the standard output */ glp_long tm_beg; /* starting time of the search, in seconds; the total time of the search is the difference between xtime() and tm_beg */ glp_long tm_lag; /* the most recent time, in seconds, at which the progress of the the search was displayed */ }; #define ssx_create _glp_ssx_create #define ssx_factorize _glp_ssx_factorize #define ssx_get_xNj _glp_ssx_get_xNj #define ssx_eval_bbar _glp_ssx_eval_bbar #define ssx_eval_pi _glp_ssx_eval_pi #define ssx_eval_dj _glp_ssx_eval_dj #define ssx_eval_cbar _glp_ssx_eval_cbar #define ssx_eval_rho _glp_ssx_eval_rho #define ssx_eval_row _glp_ssx_eval_row #define ssx_eval_col _glp_ssx_eval_col #define ssx_chuzc _glp_ssx_chuzc #define ssx_chuzr _glp_ssx_chuzr #define ssx_update_bbar _glp_ssx_update_bbar #define ssx_update_pi _glp_ssx_update_pi #define ssx_update_cbar _glp_ssx_update_cbar #define ssx_change_basis _glp_ssx_change_basis #define ssx_delete _glp_ssx_delete #define ssx_phase_I _glp_ssx_phase_I #define ssx_phase_II _glp_ssx_phase_II #define ssx_driver _glp_ssx_driver SSX *ssx_create(int m, int n, int nnz); /* create simplex solver workspace */ int ssx_factorize(SSX *ssx); /* factorize the current basis matrix */ void ssx_get_xNj(SSX *ssx, int j, mpq_t x); /* determine value of non-basic variable */ void ssx_eval_bbar(SSX *ssx); /* compute values of basic variables */ void ssx_eval_pi(SSX *ssx); /* compute values of simplex multipliers */ void ssx_eval_dj(SSX *ssx, int j, mpq_t dj); /* compute reduced cost of non-basic variable */ void ssx_eval_cbar(SSX *ssx); /* compute reduced costs of all non-basic variables */ void ssx_eval_rho(SSX *ssx); /* compute p-th row of the inverse */ void ssx_eval_row(SSX *ssx); /* compute pivot row of the simplex table */ void ssx_eval_col(SSX *ssx); /* compute pivot column of the simplex table */ void ssx_chuzc(SSX *ssx); /* choose pivot column */ void ssx_chuzr(SSX *ssx); /* choose pivot row */ void ssx_update_bbar(SSX *ssx); /* update values of basic variables */ void ssx_update_pi(SSX *ssx); /* update simplex multipliers */ void ssx_update_cbar(SSX *ssx); /* update reduced costs of non-basic variables */ void ssx_change_basis(SSX *ssx); /* change current basis to adjacent one */ void ssx_delete(SSX *ssx); /* delete simplex solver workspace */ int ssx_phase_I(SSX *ssx); /* find primal feasible solution */ int ssx_phase_II(SSX *ssx); /* find optimal solution */ int ssx_driver(SSX *ssx); /* base driver to exact simplex method */ #endif /* eof */ sources_5316/external/glpk/READ_ME.TXT0000644000176700017670000001656611704065313016215 0ustar paulpaulPraats/external/glpk/READ_ME.TXT Paul Boersma, 26 June 2010 This file describes the adaptations to the glpk 4.44 sources that are needed to make them compatible with Praat. The .c and .h files are put into the single glpk directory. The #include statements are flattened, e.g. #include amd/amd.h becomes #include amd.h. The redefinition of SIZE_T_MAX in amd_internal.h is ifndef'ed out. In glpios09.c, char is changed to unsigned char in line 197. GLPK is a heavy namespace polluter. Because of a name clash with the C library in CodeWarrior ("error" is a member of the FILE structure), I replaced the "error" macro with "mpl_error" in all glpmpl* files. ######################################################################## NOTE 1: The files named amd* are NOT part of the GLPK package, but are used with GLPK. The original code was modified according to GLPK requirements by Andrew Makhorin . ************************************************************************ AMD Version 2.2, Copyright (C) 2007 by Timothy A. Davis, Patrick R. Amestoy, and Iain S. Duff. All Rights Reserved. Description: AMD is a set of routines for pre-ordering sparse matrices prior to Cholesky or LU factorization, using the approximate minimum degree ordering algorithm. Written in ANSI/ISO C with a MATLAB interface, and in Fortran 77. Authors: Timothy A. Davis (davis at cise.ufl.edu), University of Florida. Patrick R. Amestoy, ENSEEIHT, Toulouse, France. Iain S. Duff, Rutherford Appleton Laboratory, UK. AMD License: Your use or distribution of AMD or any modified version of AMD implies that you agree to this License. This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. Permission is hereby granted to use or copy this program under the terms of the GNU LGPL, provided that the Copyright, this License, and the Availability of the original version is retained on all copies. User documentation of any code that uses this code or any modified version of this code must cite the Copyright, this License, the Availability note, and "Used by permission." Permission to modify the code and to distribute modified code is granted, provided the Copyright, this License, and the Availability note are retained, and a notice that the code was modified is included. AMD is available under alternate licences; contact T. Davis for details. Availability: http://www.cise.ufl.edu/research/sparse/amd ######################################################################## NOTE 2: The files named colamd* are NOT part of the GLPK package, but are used with GLPK. The original code was modified according to GLPK requirements by Andrew Makhorin . ************************************************************************ COLAMD/SYMAMD Version 2.7, Copyright (C) 1998-2007, Timothy A. Davis, All Rights Reserved. Description: colamd: an approximate minimum degree column ordering algorithm, for LU factorization of symmetric or unsymmetric matrices, QR factorization, least squares, interior point methods for linear programming problems, and other related problems. symamd: an approximate minimum degree ordering algorithm for Cholesky factorization of symmetric matrices. Purpose: Colamd computes a permutation Q such that the Cholesky factorization of (AQ)'(AQ) has less fill-in and requires fewer floating point operations than A'A. This also provides a good ordering for sparse partial pivoting methods, P(AQ) = LU, where Q is computed prior to numerical factorization, and P is computed during numerical factorization via conventional partial pivoting with row interchanges. Colamd is the column ordering method used in SuperLU, part of the ScaLAPACK library. It is also available as built-in function in MATLAB Version 6, available from MathWorks, Inc. (http://www.mathworks.com). This routine can be used in place of colmmd in MATLAB. Symamd computes a permutation P of a symmetric matrix A such that the Cholesky factorization of PAP' has less fill-in and requires fewer floating point operations than A. Symamd constructs a matrix M such that M'M has the same nonzero pattern of A, and then orders the columns of M using colmmd. The column ordering of M is then returned as the row and column ordering P of A. Authors: The authors of the code itself are Stefan I. Larimore and Timothy A. Davis (davis at cise.ufl.edu), University of Florida. The algorithm was developed in collaboration with John Gilbert, Xerox PARC, and Esmond Ng, Oak Ridge National Laboratory. Acknowledgements: This work was supported by the National Science Foundation, under grants DMS-9504974 and DMS-9803599. License: This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. Permission is hereby granted to use or copy this program under the terms of the GNU LGPL, provided that the Copyright, this License, and the Availability of the original version is retained on all copies. User documentation of any code that uses this code or any modified version of this code must cite the Copyright, this License, the Availability note, and "Used by permission." Permission to modify the code and to distribute modified code is granted, provided the Copyright, this License, and the Availability note are retained, and a notice that the code was modified is included. COLAMD is also available under alternate licenses, contact T. Davis for details. Availability: The colamd/symamd library is available at: http://www.cise.ufl.edu/research/sparse/colamd/ References: T. A. Davis, J. R. Gilbert, S. Larimore, E. Ng, An approximate column minimum degree ordering algorithm, ACM Transactions on Mathematical Software, vol. 30, no. 3., pp. 353-376, 2004. T. A. Davis, J. R. Gilbert, S. Larimore, E. Ng, Algorithm 836: COLAMD, an approximate column minimum degree ordering algorithm, ACM Transactions on Mathematical Software, vol. 30, no. 3., pp. 377-380, 2004. sources_5316/external/glpk/glpapi15.c0000644000176700017670000004447711401660400016300 0ustar paulpaul/* glpapi15.c (basic graph and network routines) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /* CAUTION: DO NOT CHANGE THE LIMITS BELOW */ #define NV_MAX 100000000 /* = 100*10^6 */ /* maximal number of vertices in the graph */ #define NA_MAX 500000000 /* = 500*10^6 */ /* maximal number of arcs in the graph */ /*********************************************************************** * NAME * * glp_create_graph - create graph * * SYNOPSIS * * glp_graph *glp_create_graph(int v_size, int a_size); * * DESCRIPTION * * The routine creates a new graph, which initially is empty, i.e. has * no vertices and arcs. * * The parameter v_size specifies the size of data associated with each * vertex of the graph (0 to 256 bytes). * * The parameter a_size specifies the size of data associated with each * arc of the graph (0 to 256 bytes). * * RETURNS * * The routine returns a pointer to the graph created. */ static void create_graph(glp_graph *G, int v_size, int a_size) { G->pool = dmp_create_pool(); G->name = NULL; G->nv_max = 50; G->nv = G->na = 0; G->v = xcalloc(1+G->nv_max, sizeof(glp_vertex *)); G->index = NULL; G->v_size = v_size; G->a_size = a_size; return; } glp_graph *glp_create_graph(int v_size, int a_size) { glp_graph *G; if (!(0 <= v_size && v_size <= 256)) xerror("glp_create_graph: v_size = %d; invalid size of vertex " "data\n", v_size); if (!(0 <= a_size && a_size <= 256)) xerror("glp_create_graph: a_size = %d; invalid size of arc dat" "a\n", a_size); G = xmalloc(sizeof(glp_graph)); create_graph(G, v_size, a_size); return G; } /*********************************************************************** * NAME * * glp_set_graph_name - assign (change) graph name * * SYNOPSIS * * void glp_set_graph_name(glp_graph *G, const char *name); * * DESCRIPTION * * The routine glp_set_graph_name assigns a symbolic name specified by * the character string name (1 to 255 chars) to the graph. * * If the parameter name is NULL or an empty string, the routine erases * the existing symbolic name of the graph. */ void glp_set_graph_name(glp_graph *G, const char *name) { if (G->name != NULL) { dmp_free_atom(G->pool, G->name, strlen(G->name)+1); G->name = NULL; } if (!(name == NULL || name[0] == '\0')) { int j; for (j = 0; name[j] != '\0'; j++) { if (j == 256) xerror("glp_set_graph_name: graph name too long\n"); if (iscntrl((unsigned char)name[j])) xerror("glp_set_graph_name: graph name contains invalid " "character(s)\n"); } G->name = dmp_get_atom(G->pool, strlen(name)+1); strcpy(G->name, name); } return; } /*********************************************************************** * NAME * * glp_add_vertices - add new vertices to graph * * SYNOPSIS * * int glp_add_vertices(glp_graph *G, int nadd); * * DESCRIPTION * * The routine glp_add_vertices adds nadd vertices to the specified * graph. New vertices are always added to the end of the vertex list, * so ordinal numbers of existing vertices remain unchanged. * * Being added each new vertex is isolated (has no incident arcs). * * RETURNS * * The routine glp_add_vertices returns an ordinal number of the first * new vertex added to the graph. */ int glp_add_vertices(glp_graph *G, int nadd) { int i, nv_new; if (nadd < 1) xerror("glp_add_vertices: nadd = %d; invalid number of vertice" "s\n", nadd); if (nadd > NV_MAX - G->nv) xerror("glp_add_vertices: nadd = %d; too many vertices\n", nadd); /* determine new number of vertices */ nv_new = G->nv + nadd; /* increase the room, if necessary */ if (G->nv_max < nv_new) { glp_vertex **save = G->v; while (G->nv_max < nv_new) { G->nv_max += G->nv_max; xassert(G->nv_max > 0); } G->v = xcalloc(1+G->nv_max, sizeof(glp_vertex *)); memcpy(&G->v[1], &save[1], G->nv * sizeof(glp_vertex *)); xfree(save); } /* add new vertices to the end of the vertex list */ for (i = G->nv+1; i <= nv_new; i++) { glp_vertex *v; G->v[i] = v = dmp_get_atom(G->pool, sizeof(glp_vertex)); v->i = i; v->name = NULL; v->entry = NULL; if (G->v_size == 0) v->data = NULL; else { v->data = dmp_get_atom(G->pool, G->v_size); memset(v->data, 0, G->v_size); } v->temp = NULL; v->in = v->out = NULL; } /* set new number of vertices */ G->nv = nv_new; /* return the ordinal number of the first vertex added */ return nv_new - nadd + 1; } /**********************************************************************/ void glp_set_vertex_name(glp_graph *G, int i, const char *name) { /* assign (change) vertex name */ glp_vertex *v; if (!(1 <= i && i <= G->nv)) xerror("glp_set_vertex_name: i = %d; vertex number out of rang" "e\n", i); v = G->v[i]; if (v->name != NULL) { if (v->entry != NULL) { xassert(G->index != NULL); avl_delete_node(G->index, v->entry); v->entry = NULL; } dmp_free_atom(G->pool, v->name, strlen(v->name)+1); v->name = NULL; } if (!(name == NULL || name[0] == '\0')) { int k; for (k = 0; name[k] != '\0'; k++) { if (k == 256) xerror("glp_set_vertex_name: i = %d; vertex name too lon" "g\n", i); if (iscntrl((unsigned char)name[k])) xerror("glp_set_vertex_name: i = %d; vertex name contain" "s invalid character(s)\n", i); } v->name = dmp_get_atom(G->pool, strlen(name)+1); strcpy(v->name, name); if (G->index != NULL) { xassert(v->entry == NULL); v->entry = avl_insert_node(G->index, v->name); avl_set_node_link(v->entry, v); } } return; } /*********************************************************************** * NAME * * glp_add_arc - add new arc to graph * * SYNOPSIS * * glp_arc *glp_add_arc(glp_graph *G, int i, int j); * * DESCRIPTION * * The routine glp_add_arc adds a new arc to the specified graph. * * The parameters i and j specify the ordinal numbers of, resp., tail * and head vertices of the arc. Note that self-loops and multiple arcs * are allowed. * * RETURNS * * The routine glp_add_arc returns a pointer to the arc added. */ glp_arc *glp_add_arc(glp_graph *G, int i, int j) { glp_arc *a; if (!(1 <= i && i <= G->nv)) xerror("glp_add_arc: i = %d; tail vertex number out of range\n" , i); if (!(1 <= j && j <= G->nv)) xerror("glp_add_arc: j = %d; head vertex number out of range\n" , j); if (G->na == NA_MAX) xerror("glp_add_arc: too many arcs\n"); a = dmp_get_atom(G->pool, sizeof(glp_arc)); a->tail = G->v[i]; a->head = G->v[j]; if (G->a_size == 0) a->data = NULL; else { a->data = dmp_get_atom(G->pool, G->a_size); memset(a->data, 0, G->a_size); } a->temp = NULL; a->t_prev = NULL; a->t_next = G->v[i]->out; if (a->t_next != NULL) a->t_next->t_prev = a; a->h_prev = NULL; a->h_next = G->v[j]->in; if (a->h_next != NULL) a->h_next->h_prev = a; G->v[i]->out = G->v[j]->in = a; G->na++; return a; } /*********************************************************************** * NAME * * glp_del_vertices - delete vertices from graph * * SYNOPSIS * * void glp_del_vertices(glp_graph *G, int ndel, const int num[]); * * DESCRIPTION * * The routine glp_del_vertices deletes vertices along with all * incident arcs from the specified graph. Ordinal numbers of vertices * to be deleted should be placed in locations num[1], ..., num[ndel], * ndel > 0. * * Note that deleting vertices involves changing ordinal numbers of * other vertices remaining in the graph. New ordinal numbers of the * remaining vertices are assigned under the assumption that the * original order of vertices is not changed. */ void glp_del_vertices(glp_graph *G, int ndel, const int num[]) { glp_vertex *v; int i, k, nv_new; /* scan the list of vertices to be deleted */ if (!(1 <= ndel && ndel <= G->nv)) xerror("glp_del_vertices: ndel = %d; invalid number of vertice" "s\n", ndel); for (k = 1; k <= ndel; k++) { /* take the number of vertex to be deleted */ i = num[k]; /* obtain pointer to i-th vertex */ if (!(1 <= i && i <= G->nv)) xerror("glp_del_vertices: num[%d] = %d; vertex number out o" "f range\n", k, i); v = G->v[i]; /* check that the vertex is not marked yet */ if (v->i == 0) xerror("glp_del_vertices: num[%d] = %d; duplicate vertex nu" "mbers not allowed\n", k, i); /* erase symbolic name assigned to the vertex */ glp_set_vertex_name(G, i, NULL); xassert(v->name == NULL); xassert(v->entry == NULL); /* free vertex data, if allocated */ if (v->data != NULL) dmp_free_atom(G->pool, v->data, G->v_size); /* delete all incoming arcs */ while (v->in != NULL) glp_del_arc(G, v->in); /* delete all outgoing arcs */ while (v->out != NULL) glp_del_arc(G, v->out); /* mark the vertex to be deleted */ v->i = 0; } /* delete all marked vertices from the vertex list */ nv_new = 0; for (i = 1; i <= G->nv; i++) { /* obtain pointer to i-th vertex */ v = G->v[i]; /* check if the vertex is marked */ if (v->i == 0) { /* it is marked, delete it */ dmp_free_atom(G->pool, v, sizeof(glp_vertex)); } else { /* it is not marked, keep it */ v->i = ++nv_new; G->v[v->i] = v; } } /* set new number of vertices in the graph */ G->nv = nv_new; return; } /*********************************************************************** * NAME * * glp_del_arc - delete arc from graph * * SYNOPSIS * * void glp_del_arc(glp_graph *G, glp_arc *a); * * DESCRIPTION * * The routine glp_del_arc deletes an arc from the specified graph. * The arc to be deleted must exist. */ void glp_del_arc(glp_graph *G, glp_arc *a) { /* some sanity checks */ xassert(G->na > 0); xassert(1 <= a->tail->i && a->tail->i <= G->nv); xassert(a->tail == G->v[a->tail->i]); xassert(1 <= a->head->i && a->head->i <= G->nv); xassert(a->head == G->v[a->head->i]); /* remove the arc from the list of incoming arcs */ if (a->h_prev == NULL) a->head->in = a->h_next; else a->h_prev->h_next = a->h_next; if (a->h_next == NULL) ; else a->h_next->h_prev = a->h_prev; /* remove the arc from the list of outgoing arcs */ if (a->t_prev == NULL) a->tail->out = a->t_next; else a->t_prev->t_next = a->t_next; if (a->t_next == NULL) ; else a->t_next->t_prev = a->t_prev; /* free arc data, if allocated */ if (a->data != NULL) dmp_free_atom(G->pool, a->data, G->a_size); /* delete the arc from the graph */ dmp_free_atom(G->pool, a, sizeof(glp_arc)); G->na--; return; } /*********************************************************************** * NAME * * glp_erase_graph - erase graph content * * SYNOPSIS * * void glp_erase_graph(glp_graph *G, int v_size, int a_size); * * DESCRIPTION * * The routine glp_erase_graph erases the content of the specified * graph. The effect of this operation is the same as if the graph * would be deleted with the routine glp_delete_graph and then created * anew with the routine glp_create_graph, with exception that the * handle (pointer) to the graph remains valid. */ static void delete_graph(glp_graph *G) { dmp_delete_pool(G->pool); xfree(G->v); if (G->index != NULL) avl_delete_tree(G->index); return; } void glp_erase_graph(glp_graph *G, int v_size, int a_size) { if (!(0 <= v_size && v_size <= 256)) xerror("glp_erase_graph: v_size = %d; invalid size of vertex d" "ata\n", v_size); if (!(0 <= a_size && a_size <= 256)) xerror("glp_erase_graph: a_size = %d; invalid size of arc data" "\n", a_size); delete_graph(G); create_graph(G, v_size, a_size); return; } /*********************************************************************** * NAME * * glp_delete_graph - delete graph * * SYNOPSIS * * void glp_delete_graph(glp_graph *G); * * DESCRIPTION * * The routine glp_delete_graph deletes the specified graph and frees * all the memory allocated to this program object. */ void glp_delete_graph(glp_graph *G) { delete_graph(G); xfree(G); return; } /**********************************************************************/ void glp_create_v_index(glp_graph *G) { /* create vertex name index */ glp_vertex *v; int i; if (G->index == NULL) { G->index = avl_create_tree(avl_strcmp, NULL); for (i = 1; i <= G->nv; i++) { v = G->v[i]; xassert(v->entry == NULL); if (v->name != NULL) { v->entry = avl_insert_node(G->index, v->name); avl_set_node_link(v->entry, v); } } } return; } int glp_find_vertex(glp_graph *G, const char *name) { /* find vertex by its name */ AVLNODE *node; int i = 0; if (G->index == NULL) xerror("glp_find_vertex: vertex name index does not exist\n"); if (!(name == NULL || name[0] == '\0' || strlen(name) > 255)) { node = avl_find_node(G->index, name); if (node != NULL) i = ((glp_vertex *)avl_get_node_link(node))->i; } return i; } void glp_delete_v_index(glp_graph *G) { /* delete vertex name index */ int i; if (G->index != NULL) { avl_delete_tree(G->index), G->index = NULL; for (i = 1; i <= G->nv; i++) G->v[i]->entry = NULL; } return; } /*********************************************************************** * NAME * * glp_read_graph - read graph from plain text file * * SYNOPSIS * * int glp_read_graph(glp_graph *G, const char *fname); * * DESCRIPTION * * The routine glp_read_graph reads a graph from a plain text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_read_graph(glp_graph *G, const char *fname) { glp_data *data; jmp_buf jump; int nv, na, i, j, k, ret; glp_erase_graph(G, G->v_size, G->a_size); xprintf("Reading graph from `%s'...\n", fname); data = glp_sdf_open_file(fname); if (data == NULL) { ret = 1; goto done; } if (setjmp(jump)) { ret = 1; goto done; } glp_sdf_set_jump(data, jump); nv = glp_sdf_read_int(data); if (nv < 0) glp_sdf_error(data, "invalid number of vertices\n"); na = glp_sdf_read_int(data); if (na < 0) glp_sdf_error(data, "invalid number of arcs\n"); xprintf("Graph has %d vert%s and %d arc%s\n", nv, nv == 1 ? "ex" : "ices", na, na == 1 ? "" : "s"); if (nv > 0) glp_add_vertices(G, nv); for (k = 1; k <= na; k++) { i = glp_sdf_read_int(data); if (!(1 <= i && i <= nv)) glp_sdf_error(data, "tail vertex number out of range\n"); j = glp_sdf_read_int(data); if (!(1 <= j && j <= nv)) glp_sdf_error(data, "head vertex number out of range\n"); glp_add_arc(G, i, j); } xprintf("%d lines were read\n", glp_sdf_line(data)); ret = 0; done: if (data != NULL) glp_sdf_close_file(data); return ret; } /*********************************************************************** * NAME * * glp_write_graph - write graph to plain text file * * SYNOPSIS * * int glp_write_graph(glp_graph *G, const char *fname). * * DESCRIPTION * * The routine glp_write_graph writes the specified graph to a plain * text file. * * RETURNS * * If the operation was successful, the routine returns zero. Otherwise * it prints an error message and returns non-zero. */ int glp_write_graph(glp_graph *G, const char *fname) { XFILE *fp; glp_vertex *v; glp_arc *a; int i, count, ret; xprintf("Writing graph to `%s'...\n", fname); fp = xfopen(fname, "w"), count = 0; if (fp == NULL) { xprintf("Unable to create `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xfprintf(fp, "%d %d\n", G->nv, G->na), count++; for (i = 1; i <= G->nv; i++) { v = G->v[i]; for (a = v->out; a != NULL; a = a->t_next) xfprintf(fp, "%d %d\n", a->tail->i, a->head->i), count++; } xfflush(fp); if (xferror(fp)) { xprintf("Write error on `%s' - %s\n", fname, xerrmsg()); ret = 1; goto done; } xprintf("%d lines were written\n", count); ret = 0; done: if (fp != NULL) xfclose(fp); return ret; } /* eof */ sources_5316/external/glpk/amd_preprocess.c0000644000176700017670000001017711401660400017652 0ustar paulpaul/* ========================================================================= */ /* === AMD_preprocess ====================================================== */ /* ========================================================================= */ /* ------------------------------------------------------------------------- */ /* AMD, Copyright (c) Timothy A. Davis, */ /* Patrick R. Amestoy, and Iain S. Duff. See ../README.txt for License. */ /* email: davis at cise.ufl.edu CISE Department, Univ. of Florida. */ /* web: http://www.cise.ufl.edu/research/sparse/amd */ /* ------------------------------------------------------------------------- */ /* Sorts, removes duplicate entries, and transposes from the nonzero pattern of * a column-form matrix A, to obtain the matrix R. The input matrix can have * duplicate entries and/or unsorted columns (AMD_valid (n,Ap,Ai) must not be * AMD_INVALID). * * This input condition is NOT checked. This routine is not user-callable. */ #include "amd_internal.h" /* ========================================================================= */ /* === AMD_preprocess ====================================================== */ /* ========================================================================= */ /* AMD_preprocess does not check its input for errors or allocate workspace. * On input, the condition (AMD_valid (n,n,Ap,Ai) != AMD_INVALID) must hold. */ GLOBAL void AMD_preprocess ( Int n, /* input matrix: A is n-by-n */ const Int Ap [ ], /* size n+1 */ const Int Ai [ ], /* size nz = Ap [n] */ /* output matrix R: */ Int Rp [ ], /* size n+1 */ Int Ri [ ], /* size nz (or less, if duplicates present) */ Int W [ ], /* workspace of size n */ Int Flag [ ] /* workspace of size n */ ) { /* --------------------------------------------------------------------- */ /* local variables */ /* --------------------------------------------------------------------- */ Int i, j, p, p2 ; ASSERT (AMD_valid (n, n, Ap, Ai) != AMD_INVALID) ; /* --------------------------------------------------------------------- */ /* count the entries in each row of A (excluding duplicates) */ /* --------------------------------------------------------------------- */ for (i = 0 ; i < n ; i++) { W [i] = 0 ; /* # of nonzeros in row i (excl duplicates) */ Flag [i] = EMPTY ; /* Flag [i] = j if i appears in column j */ } for (j = 0 ; j < n ; j++) { p2 = Ap [j+1] ; for (p = Ap [j] ; p < p2 ; p++) { i = Ai [p] ; if (Flag [i] != j) { /* row index i has not yet appeared in column j */ W [i]++ ; /* one more entry in row i */ Flag [i] = j ; /* flag row index i as appearing in col j*/ } } } /* --------------------------------------------------------------------- */ /* compute the row pointers for R */ /* --------------------------------------------------------------------- */ Rp [0] = 0 ; for (i = 0 ; i < n ; i++) { Rp [i+1] = Rp [i] + W [i] ; } for (i = 0 ; i < n ; i++) { W [i] = Rp [i] ; Flag [i] = EMPTY ; } /* --------------------------------------------------------------------- */ /* construct the row form matrix R */ /* --------------------------------------------------------------------- */ /* R = row form of pattern of A */ for (j = 0 ; j < n ; j++) { p2 = Ap [j+1] ; for (p = Ap [j] ; p < p2 ; p++) { i = Ai [p] ; if (Flag [i] != j) { /* row index i has not yet appeared in column j */ Ri [W [i]++] = j ; /* put col j in row i */ Flag [i] = j ; /* flag row index i as appearing in col j*/ } } } #ifndef NDEBUG ASSERT (AMD_valid (n, n, Rp, Ri) == AMD_OK) ; for (j = 0 ; j < n ; j++) { ASSERT (W [j] == Rp [j+1]) ; } #endif } sources_5316/external/glpk/glpmpl05.c0000644000176700017670000005335411411455570016323 0ustar paulpaul/* glpmpl05.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Authors: Andrew Makhorin * Heinrich Schuchardt * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #define _GLPSTD_STDIO #define _GLPSTD_TIME #include "glpmpl.h" double fn_gmtime(MPL *mpl) { /* obtain the current calendar time (UTC) */ time_t timer; struct tm *tm; int j; time(&timer); if (timer == (time_t)(-1)) err: mpl_error(mpl, "gmtime(); unable to obtain current calendar time"); tm = gmtime(&timer); if (tm == NULL) goto err; j = jday(tm->tm_mday, tm->tm_mon + 1, 1900 + tm->tm_year); if (j < 0) goto err; return (((double)(j - jday(1, 1, 1970)) * 24.0 + (double)tm->tm_hour) * 60.0 + (double)tm->tm_min) * 60.0 + (double)tm->tm_sec; } static char *week[] = { "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday" }; static char *moon[] = { "January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December" }; static void error1(MPL *mpl, const char *str, const char *s, const char *fmt, const char *f, const char *msg) { xprintf("Input string passed to str2time:\n"); xprintf("%s\n", str); xprintf("%*s\n", (s - str) + 1, "^"); xprintf("Format string passed to str2time:\n"); xprintf("%s\n", fmt); xprintf("%*s\n", (f - fmt) + 1, "^"); mpl_error(mpl, "%s", msg); /* no return */ } double fn_str2time(MPL *mpl, const char *str, const char *fmt) { /* convert character string to the calendar time */ int j, year, month, day, hh, mm, ss, zone; const char *s, *f; year = month = day = hh = mm = ss = -1, zone = INT_MAX; s = str; for (f = fmt; *f != '\0'; f++) { if (*f == '%') { f++; if (*f == 'b' || *f == 'h') { /* the abbreviated month name */ int k; char *name; if (month >= 0) error1(mpl, str, s, fmt, f, "month multiply specified" ); while (*s == ' ') s++; for (month = 1; month <= 12; month++) { name = moon[month-1]; for (k = 0; k <= 2; k++) { if (toupper((unsigned char)s[k]) != toupper((unsigned char)name[k])) goto next; } s += 3; for (k = 3; name[k] != '\0'; k++) { if (toupper((unsigned char)*s) != toupper((unsigned char)name[k])) break; s++; } break; next: ; } if (month > 12) error1(mpl, str, s, fmt, f, "abbreviated month name m" "issing or invalid"); } else if (*f == 'd') { /* the day of the month as a decimal number (01..31) */ if (day >= 0) error1(mpl, str, s, fmt, f, "day multiply specified"); while (*s == ' ') s++; if (!('0' <= *s && *s <= '9')) error1(mpl, str, s, fmt, f, "day missing or invalid"); day = (*s++) - '0'; if ('0' <= *s && *s <= '9') day = 10 * day + ((*s++) - '0'); if (!(1 <= day && day <= 31)) error1(mpl, str, s, fmt, f, "day out of range"); } else if (*f == 'H') { /* the hour as a decimal number, using a 24-hour clock (00..23) */ if (hh >= 0) error1(mpl, str, s, fmt, f, "hour multiply specified") ; while (*s == ' ') s++; if (!('0' <= *s && *s <= '9')) error1(mpl, str, s, fmt, f, "hour missing or invalid") ; hh = (*s++) - '0'; if ('0' <= *s && *s <= '9') hh = 10 * hh + ((*s++) - '0'); if (!(0 <= hh && hh <= 23)) error1(mpl, str, s, fmt, f, "hour out of range"); } else if (*f == 'm') { /* the month as a decimal number (01..12) */ if (month >= 0) error1(mpl, str, s, fmt, f, "month multiply specified" ); while (*s == ' ') s++; if (!('0' <= *s && *s <= '9')) error1(mpl, str, s, fmt, f, "month missing or invalid" ); month = (*s++) - '0'; if ('0' <= *s && *s <= '9') month = 10 * month + ((*s++) - '0'); if (!(1 <= month && month <= 12)) error1(mpl, str, s, fmt, f, "month out of range"); } else if (*f == 'M') { /* the minute as a decimal number (00..59) */ if (mm >= 0) error1(mpl, str, s, fmt, f, "minute multiply specifie" "d"); while (*s == ' ') s++; if (!('0' <= *s && *s <= '9')) error1(mpl, str, s, fmt, f, "minute missing or invali" "d"); mm = (*s++) - '0'; if ('0' <= *s && *s <= '9') mm = 10 * mm + ((*s++) - '0'); if (!(0 <= mm && mm <= 59)) error1(mpl, str, s, fmt, f, "minute out of range"); } else if (*f == 'S') { /* the second as a decimal number (00..60) */ if (ss >= 0) error1(mpl, str, s, fmt, f, "second multiply specifie" "d"); while (*s == ' ') s++; if (!('0' <= *s && *s <= '9')) error1(mpl, str, s, fmt, f, "second missing or invali" "d"); ss = (*s++) - '0'; if ('0' <= *s && *s <= '9') ss = 10 * ss + ((*s++) - '0'); if (!(0 <= ss && ss <= 60)) error1(mpl, str, s, fmt, f, "second out of range"); } else if (*f == 'y') { /* the year without a century as a decimal number (00..99); the values 00 to 68 mean the years 2000 to 2068 while the values 69 to 99 mean the years 1969 to 1999 */ if (year >= 0) error1(mpl, str, s, fmt, f, "year multiply specified") ; while (*s == ' ') s++; if (!('0' <= *s && *s <= '9')) error1(mpl, str, s, fmt, f, "year missing or invalid") ; year = (*s++) - '0'; if ('0' <= *s && *s <= '9') year = 10 * year + ((*s++) - '0'); year += (year >= 69 ? 1900 : 2000); } else if (*f == 'Y') { /* the year as a decimal number, using the Gregorian calendar */ if (year >= 0) error1(mpl, str, s, fmt, f, "year multiply specified") ; while (*s == ' ') s++; if (!('0' <= *s && *s <= '9')) error1(mpl, str, s, fmt, f, "year missing or invalid") ; year = 0; for (j = 1; j <= 4; j++) { if (!('0' <= *s && *s <= '9')) break; year = 10 * year + ((*s++) - '0'); } if (!(1 <= year && year <= 4000)) error1(mpl, str, s, fmt, f, "year out of range"); } else if (*f == 'z') { /* time zone offset in the form zhhmm */ int z, hh, mm; if (zone != INT_MAX) error1(mpl, str, s, fmt, f, "time zone offset multipl" "y specified"); while (*s == ' ') s++; if (*s == 'Z') { z = hh = mm = 0, s++; goto skip; } if (*s == '+') z = +1, s++; else if (*s == '-') z = -1, s++; else error1(mpl, str, s, fmt, f, "time zone offset sign mi" "ssing"); hh = 0; for (j = 1; j <= 2; j++) { if (!('0' <= *s && *s <= '9')) err1: error1(mpl, str, s, fmt, f, "time zone offset valu" "e incomplete or invalid"); hh = 10 * hh + ((*s++) - '0'); } if (hh > 23) err2: error1(mpl, str, s, fmt, f, "time zone offset value o" "ut of range"); if (*s == ':') { s++; if (!('0' <= *s && *s <= '9')) goto err1; } mm = 0; if (!('0' <= *s && *s <= '9')) goto skip; for (j = 1; j <= 2; j++) { if (!('0' <= *s && *s <= '9')) goto err1; mm = 10 * mm + ((*s++) - '0'); } if (mm > 59) goto err2; skip: zone = z * (60 * hh + mm); } else if (*f == '%') { /* literal % character */ goto test; } else error1(mpl, str, s, fmt, f, "invalid conversion specifie" "r"); } else if (*f == ' ') ; else test: { /* check a matching character in the input string */ if (*s != *f) error1(mpl, str, s, fmt, f, "character mismatch"); s++; } } if (year < 0) year = 1970; if (month < 0) month = 1; if (day < 0) day = 1; if (hh < 0) hh = 0; if (mm < 0) mm = 0; if (ss < 0) ss = 0; if (zone == INT_MAX) zone = 0; j = jday(day, month, year); xassert(j >= 0); return (((double)(j - jday(1, 1, 1970)) * 24.0 + (double)hh) * 60.0 + (double)mm) * 60.0 + (double)ss - 60.0 * (double)zone; } static void error2(MPL *mpl, const char *fmt, const char *f, const char *msg) { xprintf("Format string passed to time2str:\n"); xprintf("%s\n", fmt); xprintf("%*s\n", (f - fmt) + 1, "^"); mpl_error(mpl, "%s", msg); /* no return */ } static int weekday(int j) { /* determine weekday number (1 = Mon, ..., 7 = Sun) */ return (j + jday(1, 1, 1970)) % 7 + 1; } static int firstday(int year) { /* determine the first day of the first week for a specified year according to ISO 8601 */ int j; /* if 1 January is Monday, Tuesday, Wednesday or Thursday, it is in week 01; if 1 January is Friday, Saturday or Sunday, it is in week 52 or 53 of the previous year */ j = jday(1, 1, year) - jday(1, 1, 1970); switch (weekday(j)) { case 1: /* 1 Jan is Mon */ j += 0; break; case 2: /* 1 Jan is Tue */ j -= 1; break; case 3: /* 1 Jan is Wed */ j -= 2; break; case 4: /* 1 Jan is Thu */ j -= 3; break; case 5: /* 1 Jan is Fri */ j += 3; break; case 6: /* 1 Jan is Sat */ j += 2; break; case 7: /* 1 Jan is Sun */ j += 1; break; default: xassert(j != j); } /* the first day of the week must be Monday */ xassert(weekday(j) == 1); return j; } void fn_time2str(MPL *mpl, char *str, double t, const char *fmt) { /* convert the calendar time to character string */ int j, year, month, day, hh, mm, ss, len; double temp; const char *f; char buf[MAX_LENGTH+1]; if (!(-62135596800.0 <= t && t <= 64092211199.0)) mpl_error(mpl, "time2str(%.*g,...); argument out of range", DBL_DIG, t); t = floor(t + 0.5); temp = fabs(t) / 86400.0; j = (int)floor(temp); if (t < 0.0) { if (temp == floor(temp)) j = - j; else j = - (j + 1); } xassert(jdate(j + jday(1, 1, 1970), &day, &month, &year) == 0); ss = (int)(t - 86400.0 * (double)j); xassert(0 <= ss && ss < 86400); mm = ss / 60, ss %= 60; hh = mm / 60, mm %= 60; len = 0; for (f = fmt; *f != '\0'; f++) { if (*f == '%') { f++; if (*f == 'a') { /* the abbreviated weekday name */ memcpy(buf, week[weekday(j)-1], 3), buf[3] = '\0'; } else if (*f == 'A') { /* the full weekday name */ strcpy(buf, week[weekday(j)-1]); } else if (*f == 'b' || *f == 'h') { /* the abbreviated month name */ memcpy(buf, moon[month-1], 3), buf[3] = '\0'; } else if (*f == 'B') { /* the full month name */ strcpy(buf, moon[month-1]); } else if (*f == 'C') { /* the century of the year */ sprintf(buf, "%02d", year / 100); } else if (*f == 'd') { /* the day of the month as a decimal number (01..31) */ sprintf(buf, "%02d", day); } else if (*f == 'D') { /* the date using the format %m/%d/%y */ sprintf(buf, "%02d/%02d/%02d", month, day, year % 100); } else if (*f == 'e') { /* the day of the month like with %d, but padded with blank (1..31) */ sprintf(buf, "%2d", day); } else if (*f == 'F') { /* the date using the format %Y-%m-%d */ sprintf(buf, "%04d-%02d-%02d", year, month, day); } else if (*f == 'g') { /* the year corresponding to the ISO week number, but without the century (range 00 through 99); this has the same format and value as %y, except that if the ISO week number (see %V) belongs to the previous or next year, that year is used instead */ int iso; if (j < firstday(year)) iso = year - 1; else if (j < firstday(year + 1)) iso = year; else iso = year + 1; sprintf(buf, "%02d", iso % 100); } else if (*f == 'G') { /* the year corresponding to the ISO week number; this has the same format and value as %Y, excepth that if the ISO week number (see %V) belongs to the previous or next year, that year is used instead */ int iso; if (j < firstday(year)) iso = year - 1; else if (j < firstday(year + 1)) iso = year; else iso = year + 1; sprintf(buf, "%04d", iso); } else if (*f == 'H') { /* the hour as a decimal number, using a 24-hour clock (00..23) */ sprintf(buf, "%02d", hh); } else if (*f == 'I') { /* the hour as a decimal number, using a 12-hour clock (01..12) */ sprintf(buf, "%02d", hh == 0 ? 12 : hh <= 12 ? hh : hh - 12); } else if (*f == 'j') { /* the day of the year as a decimal number (001..366) */ sprintf(buf, "%03d", jday(day, month, year) - jday(1, 1, year) + 1); } else if (*f == 'k') { /* the hour as a decimal number, using a 24-hour clock like %H, but padded with blank (0..23) */ sprintf(buf, "%2d", hh); } else if (*f == 'l') { /* the hour as a decimal number, using a 12-hour clock like %I, but padded with blank (1..12) */ sprintf(buf, "%2d", hh == 0 ? 12 : hh <= 12 ? hh : hh - 12); } else if (*f == 'm') { /* the month as a decimal number (01..12) */ sprintf(buf, "%02d", month); } else if (*f == 'M') { /* the minute as a decimal number (00..59) */ sprintf(buf, "%02d", mm); } else if (*f == 'p') { /* either AM or PM, according to the given time value; noon is treated as PM and midnight as AM */ strcpy(buf, hh <= 11 ? "AM" : "PM"); } else if (*f == 'P') { /* either am or pm, according to the given time value; noon is treated as pm and midnight as am */ strcpy(buf, hh <= 11 ? "am" : "pm"); } else if (*f == 'r') { /* the calendar time using the format %I:%M:%S %p */ sprintf(buf, "%02d:%02d:%02d %s", hh == 0 ? 12 : hh <= 12 ? hh : hh - 12, mm, ss, hh <= 11 ? "AM" : "PM"); } else if (*f == 'R') { /* the hour and minute using the format %H:%M */ sprintf(buf, "%02d:%02d", hh, mm); } else if (*f == 'S') { /* the second as a decimal number (00..59) */ sprintf(buf, "%02d", ss); } else if (*f == 'T') { /* the time of day using the format %H:%M:%S */ sprintf(buf, "%02d:%02d:%02d", hh, mm, ss); } else if (*f == 'u') { /* the day of the week as a decimal number (1..7), Monday being 1 */ sprintf(buf, "%d", weekday(j)); } else if (*f == 'U') { /* the week number of the current year as a decimal number (range 00 through 53), starting with the first Sunday as the first day of the first week; days preceding the first Sunday in the year are considered to be in week 00 */ #if 1 /* 09/I-2009 */ #undef sun /* causes compilation error in SunOS */ #endif int sun; /* sun = the first Sunday of the year */ sun = jday(1, 1, year) - jday(1, 1, 1970); sun += (7 - weekday(sun)); sprintf(buf, "%02d", (j + 7 - sun) / 7); } else if (*f == 'V') { /* the ISO week number as a decimal number (range 01 through 53); ISO weeks start with Monday and end with Sunday; week 01 of a year is the first week which has the majority of its days in that year; week 01 of a year can contain days from the previous year; the week before week 01 of a year is the last week (52 or 53) of the previous year even if it contains days from the new year */ int iso; if (j < firstday(year)) iso = j - firstday(year - 1); else if (j < firstday(year + 1)) iso = j - firstday(year); else iso = j - firstday(year + 1); sprintf(buf, "%02d", iso / 7 + 1); } else if (*f == 'w') { /* the day of the week as a decimal number (0..6), Sunday being 0 */ sprintf(buf, "%d", weekday(j) % 7); } else if (*f == 'W') { /* the week number of the current year as a decimal number (range 00 through 53), starting with the first Monday as the first day of the first week; days preceding the first Monday in the year are considered to be in week 00 */ int mon; /* mon = the first Monday of the year */ mon = jday(1, 1, year) - jday(1, 1, 1970); mon += (8 - weekday(mon)) % 7; sprintf(buf, "%02d", (j + 7 - mon) / 7); } else if (*f == 'y') { /* the year without a century as a decimal number (00..99) */ sprintf(buf, "%02d", year % 100); } else if (*f == 'Y') { /* the year as a decimal number, using the Gregorian calendar */ sprintf(buf, "%04d", year); } else if (*f == '%') { /* a literal % character */ buf[0] = '%', buf[1] = '\0'; } else error2(mpl, fmt, f, "invalid conversion specifier"); } else buf[0] = *f, buf[1] = '\0'; if (len + strlen(buf) > MAX_LENGTH) mpl_error(mpl, "time2str; output string length exceeds %d chara" "cters", MAX_LENGTH); memcpy(str+len, buf, strlen(buf)); len += strlen(buf); } str[len] = '\0'; return; } /* eof */ sources_5316/external/glpk/glpspm.h0000644000176700017670000001174011401660400016150 0ustar paulpaul/* glpspm.h (general sparse matrix) */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #ifndef GLPSPM_H #define GLPSPM_H #include "glpdmp.h" typedef struct SPM SPM; typedef struct SPME SPME; struct SPM { /* general sparse matrix */ int m; /* number of rows, m >= 0 */ int n; /* number of columns, n >= 0 */ DMP *pool; /* memory pool to store matrix elements */ SPME **row; /* SPME *row[1+m]; */ /* row[i], 1 <= i <= m, is a pointer to i-th row list */ SPME **col; /* SPME *col[1+n]; */ /* col[j], 1 <= j <= n, is a pointer to j-th column list */ }; struct SPME { /* sparse matrix element */ int i; /* row number */ int j; /* column number */ double val; /* element value */ SPME *r_prev; /* pointer to previous element in the same row */ SPME *r_next; /* pointer to next element in the same row */ SPME *c_prev; /* pointer to previous element in the same column */ SPME *c_next; /* pointer to next element in the same column */ }; typedef struct PER PER; struct PER { /* permutation matrix */ int n; /* matrix order, n >= 0 */ int *row; /* int row[1+n]; */ /* row[i] = j means p[i,j] = 1 */ int *col; /* int col[1+n]; */ /* col[j] = i means p[i,j] = 1 */ }; #define spm_create_mat _glp_spm_create_mat SPM *spm_create_mat(int m, int n); /* create general sparse matrix */ #define spm_new_elem _glp_spm_new_elem SPME *spm_new_elem(SPM *A, int i, int j, double val); /* add new element to sparse matrix */ #define spm_delete_mat _glp_spm_delete_mat void spm_delete_mat(SPM *A); /* delete general sparse matrix */ #define spm_test_mat_e _glp_spm_test_mat_e SPM *spm_test_mat_e(int n, int c); /* create test sparse matrix of E(n,c) class */ #define spm_test_mat_d _glp_spm_test_mat_d SPM *spm_test_mat_d(int n, int c); /* create test sparse matrix of D(n,c) class */ #define spm_show_mat _glp_spm_show_mat int spm_show_mat(const SPM *A, const char *fname); /* write sparse matrix pattern in BMP file format */ #define spm_read_hbm _glp_spm_read_hbm SPM *spm_read_hbm(const char *fname); /* read sparse matrix in Harwell-Boeing format */ #define spm_count_nnz _glp_spm_count_nnz int spm_count_nnz(const SPM *A); /* determine number of non-zeros in sparse matrix */ #define spm_drop_zeros _glp_spm_drop_zeros int spm_drop_zeros(SPM *A, double eps); /* remove zero elements from sparse matrix */ #define spm_read_mat _glp_spm_read_mat SPM *spm_read_mat(const char *fname); /* read sparse matrix from text file */ #define spm_write_mat _glp_spm_write_mat int spm_write_mat(const SPM *A, const char *fname); /* write sparse matrix to text file */ #define spm_transpose _glp_spm_transpose SPM *spm_transpose(const SPM *A); /* transpose sparse matrix */ #define spm_add_sym _glp_spm_add_sym SPM *spm_add_sym(const SPM *A, const SPM *B); /* add two sparse matrices (symbolic phase) */ #define spm_add_num _glp_spm_add_num void spm_add_num(SPM *C, double alfa, const SPM *A, double beta, const SPM *B); /* add two sparse matrices (numeric phase) */ #define spm_add_mat _glp_spm_add_mat SPM *spm_add_mat(double alfa, const SPM *A, double beta, const SPM *B); /* add two sparse matrices (driver routine) */ #define spm_mul_sym _glp_spm_mul_sym SPM *spm_mul_sym(const SPM *A, const SPM *B); /* multiply two sparse matrices (symbolic phase) */ #define spm_mul_num _glp_spm_mul_num void spm_mul_num(SPM *C, const SPM *A, const SPM *B); /* multiply two sparse matrices (numeric phase) */ #define spm_mul_mat _glp_spm_mul_mat SPM *spm_mul_mat(const SPM *A, const SPM *B); /* multiply two sparse matrices (driver routine) */ #define spm_create_per _glp_spm_create_per PER *spm_create_per(int n); /* create permutation matrix */ #define spm_check_per _glp_spm_check_per void spm_check_per(PER *P); /* check permutation matrix for correctness */ #define spm_delete_per _glp_spm_delete_per void spm_delete_per(PER *P); /* delete permutation matrix */ #endif /* eof */ sources_5316/external/glpk/glpscl.c0000644000176700017670000003723211401660400016131 0ustar paulpaul/* glpscl.c */ /*********************************************************************** * This code is part of GLPK (GNU Linear Programming Kit). * * Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, * 2009, 2010 Andrew Makhorin, Department for Applied Informatics, * Moscow Aviation Institute, Moscow, Russia. All rights reserved. * E-mail: . * * GLPK is free software: you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GLPK is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public * License for more details. * * You should have received a copy of the GNU General Public License * along with GLPK. If not, see . ***********************************************************************/ #include "glpapi.h" /*********************************************************************** * min_row_aij - determine minimal |a[i,j]| in i-th row * * This routine returns minimal magnitude of (non-zero) constraint * coefficients in i-th row of the constraint matrix. * * If the parameter scaled is zero, the original constraint matrix A is * assumed. Otherwise, the scaled constraint matrix R*A*S is assumed. * * If i-th row of the matrix is empty, the routine returns 1. */ static double min_row_aij(glp_prob *lp, int i, int scaled) { GLPAIJ *aij; double min_aij, temp; xassert(1 <= i && i <= lp->m); min_aij = 1.0; for (aij = lp->row[i]->ptr; aij != NULL; aij = aij->r_next) { temp = fabs(aij->val); if (scaled) temp *= (aij->row->rii * aij->col->sjj); if (aij->r_prev == NULL || min_aij > temp) min_aij = temp; } return min_aij; } /*********************************************************************** * max_row_aij - determine maximal |a[i,j]| in i-th row * * This routine returns maximal magnitude of (non-zero) constraint * coefficients in i-th row of the constraint matrix. * * If the parameter scaled is zero, the original constraint matrix A is * assumed. Otherwise, the scaled constraint matrix R*A*S is assumed. * * If i-th row of the matrix is empty, the routine returns 1. */ static double max_row_aij(glp_prob *lp, int i, int scaled) { GLPAIJ *aij; double max_aij, temp; xassert(1 <= i && i <= lp->m); max_aij = 1.0; for (aij = lp->row[i]->ptr; aij != NULL; aij = aij->r_next) { temp = fabs(aij->val); if (scaled) temp *= (aij->row->rii * aij->col->sjj); if (aij->r_prev == NULL || max_aij < temp) max_aij = temp; } return max_aij; } /*********************************************************************** * min_col_aij - determine minimal |a[i,j]| in j-th column * * This routine returns minimal magnitude of (non-zero) constraint * coefficients in j-th column of the constraint matrix. * * If the parameter scaled is zero, the original constraint matrix A is * assumed. Otherwise, the scaled constraint matrix R*A*S is assumed. * * If j-th column of the matrix is empty, the routine returns 1. */ static double min_col_aij(glp_prob *lp, int j, int scaled) { GLPAIJ *aij; double min_aij, temp; xassert(1 <= j && j <= lp->n); min_aij = 1.0; for (aij = lp->col[j]->ptr; aij != NULL; aij = aij->c_next) { temp = fabs(aij->val); if (scaled) temp *= (aij->row->rii * aij->col->sjj); if (aij->c_prev == NULL || min_aij > temp) min_aij = temp; } return min_aij; } /*********************************************************************** * max_col_aij - determine maximal |a[i,j]| in j-th column * * This routine returns maximal magnitude of (non-zero) constraint * coefficients in j-th column of the constraint matrix. * * If the parameter scaled is zero, the original constraint matrix A is * assumed. Otherwise, the scaled constraint matrix R*A*S is assumed. * * If j-th column of the matrix is empty, the routine returns 1. */ static double max_col_aij(glp_prob *lp, int j, int scaled) { GLPAIJ *aij; double max_aij, temp; xassert(1 <= j && j <= lp->n); max_aij = 1.0; for (aij = lp->col[j]->ptr; aij != NULL; aij = aij->c_next) { temp = fabs(aij->val); if (scaled) temp *= (aij->row->rii * aij->col->sjj); if (aij->c_prev == NULL || max_aij < temp) max_aij = temp; } return max_aij; } /*********************************************************************** * min_mat_aij - determine minimal |a[i,j]| in constraint matrix * * This routine returns minimal magnitude of (non-zero) constraint * coefficients in the constraint matrix. * * If the parameter scaled is zero, the original constraint matrix A is * assumed. Otherwise, the scaled constraint matrix R*A*S is assumed. * * If the matrix is empty, the routine returns 1. */ static double min_mat_aij(glp_prob *lp, int scaled) { int i; double min_aij, temp; min_aij = 1.0; for (i = 1; i <= lp->m; i++) { temp = min_row_aij(lp, i, scaled); if (i == 1 || min_aij > temp) min_aij = temp; } return min_aij; } /*********************************************************************** * max_mat_aij - determine maximal |a[i,j]| in constraint matrix * * This routine returns maximal magnitude of (non-zero) constraint * coefficients in the constraint matrix. * * If the parameter scaled is zero, the original constraint matrix A is * assumed. Otherwise, the scaled constraint matrix R*A*S is assumed. * * If the matrix is empty, the routine returns 1. */ static double max_mat_aij(glp_prob *lp, int scaled) { int i; double max_aij, temp; max_aij = 1.0; for (i = 1; i <= lp->m; i++) { temp = max_row_aij(lp, i, scaled); if (i == 1 || max_aij < temp) max_aij = temp; } return max_aij; } /*********************************************************************** * eq_scaling - perform equilibration scaling * * This routine performs equilibration scaling of rows and columns of * the constraint matrix. * * If the parameter flag is zero, the routine scales rows at first and * then columns. Otherwise, the routine scales columns and then rows. * * Rows are scaled as follows: * * n * a'[i,j] = a[i,j] / max |a[i,j]|, i = 1,...,m. * j=1 * * This makes the infinity (maximum) norm of each row of the matrix * equal to 1. * * Columns are scaled as follows: * * n * a'[i,j] = a[i,j] / max |a[i,j]|, j = 1,...,n. * i=1 * * This makes the infinity (maximum) norm of each column of the matrix * equal to 1. */ static void eq_scaling(glp_prob *lp, int flag) { int i, j, pass; double temp; xassert(flag == 0 || flag == 1); for (pass = 0; pass <= 1; pass++) { if (pass == flag) { /* scale rows */ for (i = 1; i <= lp->m; i++) { temp = max_row_aij(lp, i, 1); glp_set_rii(lp, i, glp_get_rii(lp, i) / temp); } } else { /* scale columns */ for (j = 1; j <= lp->n; j++) { temp = max_col_aij(lp, j, 1); glp_set_sjj(lp, j, glp_get_sjj(lp, j) / temp); } } } return; } /*********************************************************************** * gm_scaling - perform geometric mean scaling * * This routine performs geometric mean scaling of rows and columns of * the constraint matrix. * * If the parameter flag is zero, the routine scales rows at first and * then columns. Otherwise, the routine scales columns and then rows. * * Rows are scaled as follows: * * a'[i,j] = a[i,j] / sqrt(alfa[i] * beta[i]), i = 1,...,m, * * where: * n n * alfa[i] = min |a[i,j]|, beta[i] = max |a[i,j]|. * j=1 j=1 * * This allows decreasing the ratio beta[i] / alfa[i] for each row of * the matrix. * * Columns are scaled as follows: * * a'[i,j] = a[i,j] / sqrt(alfa[j] * beta[j]), j = 1,...,n, * * where: * m m * alfa[j] = min |a[i,j]|, beta[j] = max |a[i,j]|. * i=1 i=1 * * This allows decreasing the ratio beta[j] / alfa[j] for each column * of the matrix. */ static void gm_scaling(glp_prob *lp, int flag) { int i, j, pass; double temp; xassert(flag == 0 || flag == 1); for (pass = 0; pass <= 1; pass++) { if (pass == flag) { /* scale rows */ for (i = 1; i <= lp->m; i++) { temp = min_row_aij(lp, i, 1) * max_row_aij(lp, i, 1); glp_set_rii(lp, i, glp_get_rii(lp, i) / sqrt(temp)); } } else { /* scale columns */ for (j = 1; j <= lp->n; j++) { temp = min_col_aij(lp, j, 1) * max_col_aij(lp, j, 1); glp_set_sjj(lp, j, glp_get_sjj(lp, j) / sqrt(temp)); } } } return; } /*********************************************************************** * max_row_ratio - determine worst scaling "quality" for rows * * This routine returns the worst scaling "quality" for rows of the * currently scaled constraint matrix: * * m * ratio = max ratio[i], * i=1 * where: * n n * ratio[i] = max |a[i,j]| / min |a[i,j]|, 1 <= i <= m, * j=1 j=1 * * is the scaling "quality" of i-th row. */ static double max_row_ratio(glp_prob *lp) { int i; double ratio, temp; ratio = 1.0; for (i = 1; i <= lp->m; i++) { temp = max_row_aij(lp, i, 1) / min_row_aij(lp, i, 1); if (i == 1 || ratio < temp) ratio = temp; } return ratio; } /*********************************************************************** * max_col_ratio - determine worst scaling "quality" for columns * * This routine returns the worst scaling "quality" for columns of the * currently scaled constraint matrix: * * n * ratio = max ratio[j], * j=1 * where: * m m * ratio[j] = max |a[i,j]| / min |a[i,j]|, 1 <= j <= n, * i=1 i=1 * * is the scaling "quality" of j-th column. */ static double max_col_ratio(glp_prob *lp) { int j; double ratio, temp; ratio = 1.0; for (j = 1; j <= lp->n; j++) { temp = max_col_aij(lp, j, 1) / min_col_aij(lp, j, 1); if (j == 1 || ratio < temp) ratio = temp; } return ratio; } /*********************************************************************** * gm_iterate - perform iterative geometric mean scaling * * This routine performs iterative geometric mean scaling of rows and * columns of the constraint matrix. * * The parameter it_max specifies the maximal number of iterations. * Recommended value of it_max is 15. * * The parameter tau specifies a minimal improvement of the scaling * "quality" on each iteration, 0 < tau < 1. It means than the scaling * process continues while the following condition is satisfied: * * ratio[k] <= tau * ratio[k-1], * * where ratio = max |a[i,j]| / min |a[i,j]| is the scaling "quality" * to be minimized, k is the iteration number. Recommended value of tau * is 0.90. */ static void gm_iterate(glp_prob *lp, int it_max, double tau) { int k, flag; double ratio = 0.0, r_old; /* if the scaling "quality" for rows is better than for columns, the rows are scaled first; otherwise, the columns are scaled first */ flag = (max_row_ratio(lp) > max_col_ratio(lp)); for (k = 1; k <= it_max; k++) { /* save the scaling "quality" from previous iteration */ r_old = ratio; /* determine the current scaling "quality" */ ratio = max_mat_aij(lp, 1) / min_mat_aij(lp, 1); #if 0 xprintf("k = %d; ratio = %g\n", k, ratio); #endif /* if improvement is not enough, terminate scaling */ if (k > 1 && ratio > tau * r_old) break; /* otherwise, perform another iteration */ gm_scaling(lp, flag); } return; } /*********************************************************************** * NAME * * scale_prob - scale problem data * * SYNOPSIS * * #include "glpscl.h" * void scale_prob(glp_prob *lp, int flags); * * DESCRIPTION * * The routine scale_prob performs automatic scaling of problem data * for the specified problem object. */ static void scale_prob(glp_prob *lp, int flags) { static const char *fmt = "%s: min|aij| = %10.3e max|aij| = %10.3e ratio = %10.3e\n"; double min_aij, max_aij, ratio; xprintf("Scaling...\n"); /* cancel the current scaling effect */ glp_unscale_prob(lp); /* report original scaling "quality" */ min_aij = min_mat_aij(lp, 1); max_aij = max_mat_aij(lp, 1); ratio = max_aij / min_aij; xprintf(fmt, " A", min_aij, max_aij, ratio); /* check if the problem is well scaled */ if (min_aij >= 0.10 && max_aij <= 10.0) { xprintf("Problem data seem to be well scaled\n"); /* skip scaling, if required */ if (flags & GLP_SF_SKIP) goto done; } /* perform iterative geometric mean scaling, if required */ if (flags & GLP_SF_GM) { gm_iterate(lp, 15, 0.90); min_aij = min_mat_aij(lp, 1); max_aij = max_mat_aij(lp, 1); ratio = max_aij / min_aij; xprintf(fmt, "GM", min_aij, max_aij, ratio); } /* perform equilibration scaling, if required */ if (flags & GLP_SF_EQ) { eq_scaling(lp, max_row_ratio(lp) > max_col_ratio(lp)); min_aij = min_mat_aij(lp, 1); max_aij = max_mat_aij(lp, 1); ratio = max_aij / min_aij; xprintf(fmt, "EQ", min_aij, max_aij, ratio); } /* round scale factors to nearest power of two, if required */ if (flags & GLP_SF_2N) { int i, j; for (i = 1; i <= lp->m; i++) glp_set_rii(lp, i, round2n(glp_get_rii(lp, i))); for (j = 1; j <= lp->n; j++) glp_set_sjj(lp, j, round2n(glp_get_sjj(lp, j))); min_aij = min_mat_aij(lp, 1); max_aij = max_mat_aij(lp, 1); ratio = max_aij / min_aij; xprintf(fmt, "2N", min_aij, max_aij, ratio); } done: return; } /*********************************************************************** * NAME * * glp_scale_prob - scale problem data * * SYNOPSIS * * void glp_scale_prob(glp_prob *lp, int flags); * * DESCRIPTION * * The routine glp_scale_prob performs automatic scaling of problem * data for the specified problem object. * * The parameter flags specifies scaling options used by the routine. * Options can be combined with the bitwise OR operator and may be the * following: * * GLP_SF_GM perform geometric mean scaling; * GLP_SF_EQ perform equilibration scaling; * GLP_SF_2N round scale factors to nearest power of two; * GLP_SF_SKIP skip scaling, if the problem is well scaled. * * The parameter flags may be specified as GLP_SF_AUTO, in which case * the routine chooses scaling options automatically. */ void glp_scale_prob(glp_prob *lp, int flags) { if (flags & ~(GLP_SF_GM | GLP_SF_EQ | GLP_SF_2N | GLP_SF_SKIP | GLP_SF_AUTO)) xerror("glp_scale_prob: flags = 0x%02X; invalid scaling option" "s\n", flags); if (flags & GLP_SF_AUTO) flags = (GLP_SF_GM | GLP_SF_EQ | GLP_SF_SKIP); scale_prob(lp, flags); return; } /* eof */ sources_5316/external/portaudio/0000755000176700017670000000000011755011202015545 5ustar paulpaulsources_5316/external/portaudio/pa_trace.h0000644000176700017670000000502010474003011017465 0ustar paulpaul#ifndef PA_TRACE_H #define PA_TRACE_H /* * $Id: pa_trace.h 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library Trace Facility * Store trace information in real-time for later printing. * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2000 Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Event trace mechanism for debugging. Allows data to be written to the buffer at interrupt time and dumped later. */ #define PA_TRACE_REALTIME_EVENTS (0) /* Keep log of various real-time events. */ #define PA_MAX_TRACE_RECORDS (2048) #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ #if PA_TRACE_REALTIME_EVENTS void PaUtil_ResetTraceMessages(); void PaUtil_AddTraceMessage( const char *msg, int data ); void PaUtil_DumpTraceMessages(); #else #define PaUtil_ResetTraceMessages() /* noop */ #define PaUtil_AddTraceMessage(msg,data) /* noop */ #define PaUtil_DumpTraceMessages() /* noop */ #endif #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_TRACE_H */ sources_5316/external/portaudio/pa_win_hostapis.c0000644000176700017670000000577211630755622021130 0ustar paulpaul#ifdef _WIN32 /* * $Id: pa_win_hostapis.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library Windows initialization table * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup win_src Win32 host API initialization function table. @todo Consider using PA_USE_WMME etc instead of PA_NO_WMME. This is what the Unix version does, we should consider being consistent. */ #include "pa_hostapi.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ PaError PaSkeleton_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaWinMme_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaWinDs_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaAsio_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaWinWdm_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaWinWasapi_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); #ifdef __cplusplus } #endif /* __cplusplus */ PaUtilHostApiInitializer *paHostApiInitializers[] = { PaSkeleton_Initialize, // 0; just for testing PaWinMme_Initialize, // 1 //PaWinDs_Initialize, // 2 //PaWinWdm_Initialize, // 3 //PaAsio_Initialize, //PaWinWasapi_Initialize, 0 /* NULL terminated array */ }; int paDefaultHostApiIndex = 1; #endif sources_5316/external/portaudio/pa_win_ds.c0000644000176700017670000027273111630755473017711 0ustar paulpaul#ifdef _WIN32 /* * $Id: pa_win_ds.c 1286 2007-09-26 21:34:23Z rossb $ * Portable Audio I/O Library DirectSound implementation * * Authors: Phil Burk, Robert Marsanyi & Ross Bencina * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2007 Ross Bencina, Phil Burk, Robert Marsanyi * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostaip_src @todo implement paInputOverflow callback status flag @todo implement paNeverDropInput. @todo implement host api specific extension to set i/o buffer sizes in frames @todo implement initialisation of PaDeviceInfo default*Latency fields (currently set to 0.) @todo implement ReadStream, WriteStream, GetStreamReadAvailable, GetStreamWriteAvailable @todo audit handling of DirectSound result codes - in many cases we could convert a HRESULT into a native portaudio error code. Standard DirectSound result codes are documented at msdn. @todo implement IsFormatSupported @todo call PaUtil_SetLastHostErrorInfo with a specific error string (currently just "DSound error"). @todo make sure all buffers have been played before stopping the stream when the stream callback returns paComplete @todo retrieve default devices using the DRVM_MAPPER_PREFERRED_GET functions used in the wmme api these wave device ids can be aligned with the directsound devices either by retrieving the system interface device name using DRV_QUERYDEVICEINTERFACE or by using the wave device id retrieved in KsPropertySetEnumerateCallback. old TODOs from phil, need to work out if these have been done: O- fix "patest_stop.c" */ #undef UNICODE #include #include /* strlen() */ #include #include /* We are only using DX3 in here, no need to polute the namespace - davidv */ #define DIRECTSOUND_VERSION 0x0300 #include #ifdef PAWIN_USE_WDMKS_DEVICE_INFO #include #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ #include "pa_util.h" #include "pa_allocation.h" #include "pa_hostapi.h" #include "pa_stream.h" #include "pa_cpuload.h" #include "pa_process.h" #include "pa_debugprint.h" #include "pa_win_ds.h" #include "pa_win_ds_dynlink.h" #include "pa_win_waveformat.h" #include "pa_win_wdmks_utils.h" #if (defined(WIN32) && (defined(_MSC_VER) && (_MSC_VER >= 1200))) /* MSC version 6 and above */ #pragma comment( lib, "dsound.lib" ) #pragma comment( lib, "winmm.lib" ) #endif /* provided in newer platform sdks and x64 */ #ifndef DWORD_PTR #define DWORD_PTR DWORD #endif #define PRINT(x) PA_DEBUG(x); #define ERR_RPT(x) PRINT(x) #define DBUG(x) PRINT(x) #define DBUGX(x) PRINT(x) #define PA_USE_HIGH_LATENCY (0) #if PA_USE_HIGH_LATENCY #define PA_WIN_9X_LATENCY (500) #define PA_WIN_NT_LATENCY (600) #else #define PA_WIN_9X_LATENCY (140) #define PA_WIN_NT_LATENCY (280) #endif #define PA_WIN_WDM_LATENCY (120) #define SECONDS_PER_MSEC (0.001) #define MSEC_PER_SECOND (1000) /* prototypes for functions declared in this file */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ PaError PaWinDs_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); #ifdef __cplusplus } #endif /* __cplusplus */ static void Terminate( struct PaUtilHostApiRepresentation *hostApi ); static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ); static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); static PaError CloseStream( PaStream* stream ); static PaError StartStream( PaStream *stream ); static PaError StopStream( PaStream *stream ); static PaError AbortStream( PaStream *stream ); static PaError IsStreamStopped( PaStream *s ); static PaError IsStreamActive( PaStream *stream ); static PaTime GetStreamTime( PaStream *stream ); static double GetStreamCpuLoad( PaStream* stream ); static PaError ReadStream( PaStream* stream, void *buffer, unsigned long frames ); static PaError WriteStream( PaStream* stream, const void *buffer, unsigned long frames ); static signed long GetStreamReadAvailable( PaStream* stream ); static signed long GetStreamWriteAvailable( PaStream* stream ); /* FIXME: should convert hr to a string */ #define PA_DS_SET_LAST_DIRECTSOUND_ERROR( hr ) \ PaUtil_SetLastHostErrorInfo( paDirectSound, hr, "DirectSound error" ) /************************************************* DX Prototypes **********/ static BOOL CALLBACK CollectGUIDsProc(LPGUID lpGUID, LPCTSTR lpszDesc, LPCTSTR lpszDrvName, LPVOID lpContext ); /************************************************************************************/ /********************** Structures **************************************************/ /************************************************************************************/ /* PaWinDsHostApiRepresentation - host api datastructure specific to this implementation */ typedef struct PaWinDsDeviceInfo { PaDeviceInfo inheritedDeviceInfo; GUID guid; GUID *lpGUID; double sampleRates[3]; char deviceInputChannelCountIsKnown; /**<< if the system returns 0xFFFF then we don't really know the number of supported channels (1=>known, 0=>unknown)*/ char deviceOutputChannelCountIsKnown; /**<< if the system returns 0xFFFF then we don't really know the number of supported channels (1=>known, 0=>unknown)*/ } PaWinDsDeviceInfo; typedef struct { PaUtilHostApiRepresentation inheritedHostApiRep; PaUtilStreamInterface callbackStreamInterface; PaUtilStreamInterface blockingStreamInterface; PaUtilAllocationGroup *allocations; /* implementation specific data goes here */ char comWasInitialized; } PaWinDsHostApiRepresentation; /* PaWinDsStream - a stream data structure specifically for this implementation */ typedef struct PaWinDsStream { PaUtilStreamRepresentation streamRepresentation; PaUtilCpuLoadMeasurer cpuLoadMeasurer; PaUtilBufferProcessor bufferProcessor; /* DirectSound specific data. */ /* Output */ LPDIRECTSOUND pDirectSound; LPDIRECTSOUNDBUFFER pDirectSoundOutputBuffer; DWORD outputBufferWriteOffsetBytes; /* last write position */ INT outputBufferSizeBytes; INT bytesPerOutputFrame; /* Try to detect play buffer underflows. */ LARGE_INTEGER perfCounterTicksPerBuffer; /* counter ticks it should take to play a full buffer */ LARGE_INTEGER previousPlayTime; UINT previousPlayCursor; UINT outputUnderflowCount; BOOL outputIsRunning; /* use double which lets us can play for several thousand years with enough precision */ double dsw_framesWritten; double framesPlayed; /* Input */ LPDIRECTSOUNDCAPTURE pDirectSoundCapture; LPDIRECTSOUNDCAPTUREBUFFER pDirectSoundInputBuffer; INT bytesPerInputFrame; UINT readOffset; /* last read position */ UINT inputSize; MMRESULT timerID; int framesPerDSBuffer; double framesWritten; double secondsPerHostByte; /* Used to optimize latency calculation for outTime */ PaStreamCallbackFlags callbackFlags; /* FIXME - move all below to PaUtilStreamRepresentation */ volatile int isStarted; volatile int isActive; volatile int stopProcessing; /* stop thread once existing buffers have been returned */ volatile int abortProcessing; /* stop thread immediately */ } PaWinDsStream; /************************************************************************************ ** Duplicate the input string using the allocations allocator. ** A NULL string is converted to a zero length string. ** If memory cannot be allocated, NULL is returned. **/ static char *DuplicateDeviceNameString( PaUtilAllocationGroup *allocations, const char* src ) { char *result = 0; if( src != NULL ) { size_t len = strlen(src); result = (char*)PaUtil_GroupAllocateMemory( allocations, (long)(len + 1) ); if( result ) memcpy( (void *) result, src, len+1 ); } else { result = (char*)PaUtil_GroupAllocateMemory( allocations, 1 ); if( result ) result[0] = '\0'; } return result; } /************************************************************************************ ** DSDeviceNameAndGUID, DSDeviceNameAndGUIDVector used for collecting preliminary ** information during device enumeration. */ typedef struct DSDeviceNameAndGUID{ char *name; // allocated from parent's allocations, never deleted by this structure GUID guid; LPGUID lpGUID; void *pnpInterface; // wchar_t* interface path, allocated using the DS host api's allocation group } DSDeviceNameAndGUID; typedef struct DSDeviceNameAndGUIDVector{ PaUtilAllocationGroup *allocations; PaError enumerationError; int count; int free; DSDeviceNameAndGUID *items; // Allocated using LocalAlloc() } DSDeviceNameAndGUIDVector; typedef struct DSDeviceNamesAndGUIDs{ PaWinDsHostApiRepresentation *winDsHostApi; DSDeviceNameAndGUIDVector inputNamesAndGUIDs; DSDeviceNameAndGUIDVector outputNamesAndGUIDs; } DSDeviceNamesAndGUIDs; static PaError InitializeDSDeviceNameAndGUIDVector( DSDeviceNameAndGUIDVector *guidVector, PaUtilAllocationGroup *allocations ) { PaError result = paNoError; guidVector->allocations = allocations; guidVector->enumerationError = paNoError; guidVector->count = 0; guidVector->free = 8; guidVector->items = (DSDeviceNameAndGUID*)LocalAlloc( LMEM_FIXED, sizeof(DSDeviceNameAndGUID) * guidVector->free ); if( guidVector->items == NULL ) result = paInsufficientMemory; return result; } static PaError ExpandDSDeviceNameAndGUIDVector( DSDeviceNameAndGUIDVector *guidVector ) { PaError result = paNoError; DSDeviceNameAndGUID *newItems; int i; /* double size of vector */ int size = guidVector->count + guidVector->free; guidVector->free += size; newItems = (DSDeviceNameAndGUID*)LocalAlloc( LMEM_FIXED, sizeof(DSDeviceNameAndGUID) * size * 2 ); if( newItems == NULL ) { result = paInsufficientMemory; } else { for( i=0; i < guidVector->count; ++i ) { newItems[i].name = guidVector->items[i].name; if( guidVector->items[i].lpGUID == NULL ) { newItems[i].lpGUID = NULL; } else { newItems[i].lpGUID = &newItems[i].guid; memcpy( &newItems[i].guid, guidVector->items[i].lpGUID, sizeof(GUID) );; } newItems[i].pnpInterface = guidVector->items[i].pnpInterface; } LocalFree( guidVector->items ); guidVector->items = newItems; } return result; } /* it's safe to call DSDeviceNameAndGUIDVector multiple times */ static PaError TerminateDSDeviceNameAndGUIDVector( DSDeviceNameAndGUIDVector *guidVector ) { PaError result = paNoError; if( guidVector->items != NULL ) { if( LocalFree( guidVector->items ) != NULL ) result = paInsufficientMemory; /** @todo this isn't the correct error to return from a deallocation failure */ guidVector->items = NULL; } return result; } /************************************************************************************ ** Collect preliminary device information during DirectSound enumeration */ static BOOL CALLBACK CollectGUIDsProc(LPGUID lpGUID, LPCTSTR lpszDesc, LPCTSTR lpszDrvName, LPVOID lpContext ) { DSDeviceNameAndGUIDVector *namesAndGUIDs = (DSDeviceNameAndGUIDVector*)lpContext; PaError error; (void) lpszDrvName; /* unused variable */ if( namesAndGUIDs->free == 0 ) { error = ExpandDSDeviceNameAndGUIDVector( namesAndGUIDs ); if( error != paNoError ) { namesAndGUIDs->enumerationError = error; return FALSE; } } /* Set GUID pointer, copy GUID to storage in DSDeviceNameAndGUIDVector. */ if( lpGUID == NULL ) { namesAndGUIDs->items[namesAndGUIDs->count].lpGUID = NULL; } else { namesAndGUIDs->items[namesAndGUIDs->count].lpGUID = &namesAndGUIDs->items[namesAndGUIDs->count].guid; memcpy( &namesAndGUIDs->items[namesAndGUIDs->count].guid, lpGUID, sizeof(GUID) ); } namesAndGUIDs->items[namesAndGUIDs->count].name = DuplicateDeviceNameString( namesAndGUIDs->allocations, lpszDesc ); if( namesAndGUIDs->items[namesAndGUIDs->count].name == NULL ) { namesAndGUIDs->enumerationError = paInsufficientMemory; return FALSE; } namesAndGUIDs->items[namesAndGUIDs->count].pnpInterface = 0; ++namesAndGUIDs->count; --namesAndGUIDs->free; return TRUE; } #ifdef PAWIN_USE_WDMKS_DEVICE_INFO static void *DuplicateWCharString( PaUtilAllocationGroup *allocations, wchar_t *source ) { size_t len; wchar_t *result; len = wcslen( source ); result = (wchar_t*)PaUtil_GroupAllocateMemory( allocations, (long) ((len+1) * sizeof(wchar_t)) ); wcscpy( result, source ); return result; } static BOOL CALLBACK KsPropertySetEnumerateCallback( PDSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_W_DATA data, LPVOID context ) { int i; DSDeviceNamesAndGUIDs *deviceNamesAndGUIDs = (DSDeviceNamesAndGUIDs*)context; if( data->DataFlow == DIRECTSOUNDDEVICE_DATAFLOW_RENDER ) { for( i=0; i < deviceNamesAndGUIDs->outputNamesAndGUIDs.count; ++i ) { if( deviceNamesAndGUIDs->outputNamesAndGUIDs.items[i].lpGUID && memcmp( &data->DeviceId, deviceNamesAndGUIDs->outputNamesAndGUIDs.items[i].lpGUID, sizeof(GUID) ) == 0 ) { deviceNamesAndGUIDs->outputNamesAndGUIDs.items[i].pnpInterface = (char*)DuplicateWCharString( deviceNamesAndGUIDs->winDsHostApi->allocations, data->Interface ); break; } } } else if( data->DataFlow == DIRECTSOUNDDEVICE_DATAFLOW_CAPTURE ) { for( i=0; i < deviceNamesAndGUIDs->inputNamesAndGUIDs.count; ++i ) { if( deviceNamesAndGUIDs->inputNamesAndGUIDs.items[i].lpGUID && memcmp( &data->DeviceId, deviceNamesAndGUIDs->inputNamesAndGUIDs.items[i].lpGUID, sizeof(GUID) ) == 0 ) { deviceNamesAndGUIDs->inputNamesAndGUIDs.items[i].pnpInterface = (char*)DuplicateWCharString( deviceNamesAndGUIDs->winDsHostApi->allocations, data->Interface ); break; } } } return TRUE; } static GUID pawin_CLSID_DirectSoundPrivate = { 0x11ab3ec0, 0x25ec, 0x11d1, 0xa4, 0xd8, 0x00, 0xc0, 0x4f, 0xc2, 0x8a, 0xca }; static GUID pawin_DSPROPSETID_DirectSoundDevice = { 0x84624f82, 0x25ec, 0x11d1, 0xa4, 0xd8, 0x00, 0xc0, 0x4f, 0xc2, 0x8a, 0xca }; static GUID pawin_IID_IKsPropertySet = { 0x31efac30, 0x515c, 0x11d0, 0xa9, 0xaa, 0x00, 0xaa, 0x00, 0x61, 0xbe, 0x93 }; /* FindDevicePnpInterfaces fills in the pnpInterface fields in deviceNamesAndGUIDs with UNICODE file paths to the devices. The DS documentation mentions at least two techniques by which these Interface paths can be found using IKsPropertySet on the DirectSound class object. One is using the DSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION property, and the other is using DSPROPERTY_DIRECTSOUNDDEVICE_ENUMERATE. I tried both methods and only the second worked. I found two postings on the net from people who had the same problem with the first method, so I think the method used here is more common/likely to work. The probem is that IKsPropertySet_Get returns S_OK but the fields of the device description are not filled in. The mechanism we use works by registering an enumeration callback which is called for every DSound device. Our callback searches for a device in our deviceNamesAndGUIDs list with the matching GUID and copies the pointer to the Interface path. Note that we could have used this enumeration callback to perform the original device enumeration, however we choose not to so we can disable this step easily. Apparently the IKsPropertySet mechanism was added in DirectSound 9c 2004 http://www.tech-archive.net/Archive/Development/microsoft.public.win32.programmer.mmedia/2004-12/0099.html -- rossb */ static void FindDevicePnpInterfaces( DSDeviceNamesAndGUIDs *deviceNamesAndGUIDs ) { IClassFactory *pClassFactory; if( paWinDsDSoundEntryPoints.DllGetClassObject(&pawin_CLSID_DirectSoundPrivate, &IID_IClassFactory, (PVOID *) &pClassFactory) == S_OK ){ IKsPropertySet *pPropertySet; if( pClassFactory->lpVtbl->CreateInstance( pClassFactory, NULL, &pawin_IID_IKsPropertySet, (PVOID *) &pPropertySet) == S_OK ){ DSPROPERTY_DIRECTSOUNDDEVICE_ENUMERATE_W_DATA data; ULONG bytesReturned; data.Callback = KsPropertySetEnumerateCallback; data.Context = deviceNamesAndGUIDs; IKsPropertySet_Get( pPropertySet, &pawin_DSPROPSETID_DirectSoundDevice, DSPROPERTY_DIRECTSOUNDDEVICE_ENUMERATE_W, NULL, 0, &data, sizeof(data), &bytesReturned ); IKsPropertySet_Release( pPropertySet ); } pClassFactory->lpVtbl->Release( pClassFactory ); } /* The following code fragment, which I chose not to use, queries for the device interface for a device with a specific GUID: ULONG BytesReturned; DSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_W_DATA Property; memset (&Property, 0, sizeof(Property)); Property.DataFlow = DIRECTSOUNDDEVICE_DATAFLOW_RENDER; Property.DeviceId = *lpGUID; hr = IKsPropertySet_Get( pPropertySet, &pawin_DSPROPSETID_DirectSoundDevice, DSPROPERTY_DIRECTSOUNDDEVICE_DESCRIPTION_W, NULL, 0, &Property, sizeof(Property), &BytesReturned ); if( hr == S_OK ) { //pnpInterface = Property.Interface; } */ } #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ /* GUIDs for emulated devices which we blacklist below. are there more than two of them?? */ GUID IID_IRolandVSCEmulated1 = {0xc2ad1800, 0xb243, 0x11ce, 0xa8, 0xa4, 0x00, 0xaa, 0x00, 0x6c, 0x45, 0x01}; GUID IID_IRolandVSCEmulated2 = {0xc2ad1800, 0xb243, 0x11ce, 0xa8, 0xa4, 0x00, 0xaa, 0x00, 0x6c, 0x45, 0x02}; #define PA_DEFAULTSAMPLERATESEARCHORDER_COUNT_ (13) /* must match array length below */ static double defaultSampleRateSearchOrder_[] = { 44100.0, 48000.0, 32000.0, 24000.0, 22050.0, 88200.0, 96000.0, 192000.0, 16000.0, 12000.0, 11025.0, 9600.0, 8000.0 }; /************************************************************************************ ** Extract capabilities from an output device, and add it to the device info list ** if successful. This function assumes that there is enough room in the ** device info list to accomodate all entries. ** ** The device will not be added to the device list if any errors are encountered. */ static PaError AddOutputDeviceInfoFromDirectSound( PaWinDsHostApiRepresentation *winDsHostApi, char *name, LPGUID lpGUID, char *pnpInterface ) { PaUtilHostApiRepresentation *hostApi = &winDsHostApi->inheritedHostApiRep; PaWinDsDeviceInfo *winDsDeviceInfo = (PaWinDsDeviceInfo*) hostApi->deviceInfos[hostApi->info.deviceCount]; PaDeviceInfo *deviceInfo = &winDsDeviceInfo->inheritedDeviceInfo; HRESULT hr; LPDIRECTSOUND lpDirectSound; DSCAPS caps; int deviceOK = TRUE; PaError result = paNoError; int i; /* Copy GUID to the device info structure. Set pointer. */ if( lpGUID == NULL ) { winDsDeviceInfo->lpGUID = NULL; } else { memcpy( &winDsDeviceInfo->guid, lpGUID, sizeof(GUID) ); winDsDeviceInfo->lpGUID = &winDsDeviceInfo->guid; } if( lpGUID ) { if (IsEqualGUID (&IID_IRolandVSCEmulated1,lpGUID) || IsEqualGUID (&IID_IRolandVSCEmulated2,lpGUID) ) { PA_DEBUG(("BLACKLISTED: %s \n",name)); return paNoError; } } /* Create a DirectSound object for the specified GUID Note that using CoCreateInstance doesn't work on windows CE. */ hr = paWinDsDSoundEntryPoints.DirectSoundCreate( lpGUID, &lpDirectSound, NULL ); /** try using CoCreateInstance because DirectSoundCreate was hanging under some circumstances - note this was probably related to the #define BOOL short bug which has now been fixed @todo delete this comment and the following code once we've ensured there is no bug. */ /* hr = CoCreateInstance( &CLSID_DirectSound, NULL, CLSCTX_INPROC_SERVER, &IID_IDirectSound, (void**)&lpDirectSound ); if( hr == S_OK ) { hr = IDirectSound_Initialize( lpDirectSound, lpGUID ); } */ if( hr != DS_OK ) { if (hr == DSERR_ALLOCATED) PA_DEBUG(("AddOutputDeviceInfoFromDirectSound %s DSERR_ALLOCATED\n",name)); DBUG(("Cannot create DirectSound for %s. Result = 0x%x\n", name, hr )); if (lpGUID) DBUG(("%s's GUID: {0x%x,0x%x,0x%x,0x%x,0x%x,0x%x,0x%x,0x%x,0x%x,0x%x, 0x%x} \n", name, lpGUID->Data1, lpGUID->Data2, lpGUID->Data3, lpGUID->Data4[0], lpGUID->Data4[1], lpGUID->Data4[2], lpGUID->Data4[3], lpGUID->Data4[4], lpGUID->Data4[5], lpGUID->Data4[6], lpGUID->Data4[7])); deviceOK = FALSE; } else { /* Query device characteristics. */ memset( &caps, 0, sizeof(caps) ); caps.dwSize = sizeof(caps); hr = IDirectSound_GetCaps( lpDirectSound, &caps ); if( hr != DS_OK ) { DBUG(("Cannot GetCaps() for DirectSound device %s. Result = 0x%x\n", name, hr )); deviceOK = FALSE; } else { #ifndef PA_NO_WMME if( caps.dwFlags & DSCAPS_EMULDRIVER ) { /* If WMME supported, then reject Emulated drivers because they are lousy. */ deviceOK = FALSE; } #endif if( deviceOK ) { deviceInfo->maxInputChannels = 0; winDsDeviceInfo->deviceInputChannelCountIsKnown = 1; /* DS output capabilities only indicate supported number of channels using two flags which indicate mono and/or stereo. We assume that stereo devices may support more than 2 channels (as is the case with 5.1 devices for example) and so set deviceOutputChannelCountIsKnown to 0 (unknown). In this case OpenStream will try to open the device when the user requests more than 2 channels, rather than returning an error. */ if( caps.dwFlags & DSCAPS_PRIMARYSTEREO ) { deviceInfo->maxOutputChannels = 2; winDsDeviceInfo->deviceOutputChannelCountIsKnown = 0; } else { deviceInfo->maxOutputChannels = 1; winDsDeviceInfo->deviceOutputChannelCountIsKnown = 1; } #ifdef PAWIN_USE_WDMKS_DEVICE_INFO if( pnpInterface ) { int count = PaWin_WDMKS_QueryFilterMaximumChannelCount( pnpInterface, /* isInput= */ 0 ); if( count > 0 ) { deviceInfo->maxOutputChannels = count; winDsDeviceInfo->deviceOutputChannelCountIsKnown = 1; } } #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ deviceInfo->defaultLowInputLatency = 0.; /** @todo IMPLEMENT ME */ deviceInfo->defaultLowOutputLatency = 0.; /** @todo IMPLEMENT ME */ deviceInfo->defaultHighInputLatency = 0.; /** @todo IMPLEMENT ME */ deviceInfo->defaultHighOutputLatency = 0.; /** @todo IMPLEMENT ME */ /* initialize defaultSampleRate */ if( caps.dwFlags & DSCAPS_CONTINUOUSRATE ) { /* initialize to caps.dwMaxSecondarySampleRate incase none of the standard rates match */ deviceInfo->defaultSampleRate = caps.dwMaxSecondarySampleRate; for( i = 0; i < PA_DEFAULTSAMPLERATESEARCHORDER_COUNT_; ++i ) { if( defaultSampleRateSearchOrder_[i] >= caps.dwMinSecondarySampleRate && defaultSampleRateSearchOrder_[i] <= caps.dwMaxSecondarySampleRate ) { deviceInfo->defaultSampleRate = defaultSampleRateSearchOrder_[i]; break; } } } else if( caps.dwMinSecondarySampleRate == caps.dwMaxSecondarySampleRate ) { if( caps.dwMinSecondarySampleRate == 0 ) { /* ** On my Thinkpad 380Z, DirectSoundV6 returns min-max=0 !! ** But it supports continuous sampling. ** So fake range of rates, and hope it really supports it. */ deviceInfo->defaultSampleRate = 44100.0f; DBUG(("PA - Reported rates both zero. Setting to fake values for device #%s\n", name )); } else { deviceInfo->defaultSampleRate = caps.dwMaxSecondarySampleRate; } } else if( (caps.dwMinSecondarySampleRate < 1000.0) && (caps.dwMaxSecondarySampleRate > 50000.0) ) { /* The EWS88MT drivers lie, lie, lie. The say they only support two rates, 100 & 100000. ** But we know that they really support a range of rates! ** So when we see a ridiculous set of rates, assume it is a range. */ deviceInfo->defaultSampleRate = 44100.0f; DBUG(("PA - Sample rate range used instead of two odd values for device #%s\n", name )); } else deviceInfo->defaultSampleRate = caps.dwMaxSecondarySampleRate; //printf( "min %d max %d\n", caps.dwMinSecondarySampleRate, caps.dwMaxSecondarySampleRate ); // dwFlags | DSCAPS_CONTINUOUSRATE } } IDirectSound_Release( lpDirectSound ); } if( deviceOK ) { deviceInfo->name = name; if( lpGUID == NULL ) hostApi->info.defaultOutputDevice = hostApi->info.deviceCount; hostApi->info.deviceCount++; } return result; } /************************************************************************************ ** Extract capabilities from an input device, and add it to the device info list ** if successful. This function assumes that there is enough room in the ** device info list to accomodate all entries. ** ** The device will not be added to the device list if any errors are encountered. */ static PaError AddInputDeviceInfoFromDirectSoundCapture( PaWinDsHostApiRepresentation *winDsHostApi, char *name, LPGUID lpGUID, char *pnpInterface ) { PaUtilHostApiRepresentation *hostApi = &winDsHostApi->inheritedHostApiRep; PaWinDsDeviceInfo *winDsDeviceInfo = (PaWinDsDeviceInfo*) hostApi->deviceInfos[hostApi->info.deviceCount]; PaDeviceInfo *deviceInfo = &winDsDeviceInfo->inheritedDeviceInfo; HRESULT hr; LPDIRECTSOUNDCAPTURE lpDirectSoundCapture; DSCCAPS caps; int deviceOK = TRUE; PaError result = paNoError; /* Copy GUID to the device info structure. Set pointer. */ if( lpGUID == NULL ) { winDsDeviceInfo->lpGUID = NULL; } else { winDsDeviceInfo->lpGUID = &winDsDeviceInfo->guid; memcpy( &winDsDeviceInfo->guid, lpGUID, sizeof(GUID) ); } hr = paWinDsDSoundEntryPoints.DirectSoundCaptureCreate( lpGUID, &lpDirectSoundCapture, NULL ); /** try using CoCreateInstance because DirectSoundCreate was hanging under some circumstances - note this was probably related to the #define BOOL short bug which has now been fixed @todo delete this comment and the following code once we've ensured there is no bug. */ /* hr = CoCreateInstance( &CLSID_DirectSoundCapture, NULL, CLSCTX_INPROC_SERVER, &IID_IDirectSoundCapture, (void**)&lpDirectSoundCapture ); */ if( hr != DS_OK ) { DBUG(("Cannot create Capture for %s. Result = 0x%x\n", name, hr )); deviceOK = FALSE; } else { /* Query device characteristics. */ memset( &caps, 0, sizeof(caps) ); caps.dwSize = sizeof(caps); hr = IDirectSoundCapture_GetCaps( lpDirectSoundCapture, &caps ); if( hr != DS_OK ) { DBUG(("Cannot GetCaps() for Capture device %s. Result = 0x%x\n", name, hr )); deviceOK = FALSE; } else { #ifndef PA_NO_WMME if( caps.dwFlags & DSCAPS_EMULDRIVER ) { /* If WMME supported, then reject Emulated drivers because they are lousy. */ deviceOK = FALSE; } #endif if( deviceOK ) { deviceInfo->maxInputChannels = caps.dwChannels; winDsDeviceInfo->deviceInputChannelCountIsKnown = 1; deviceInfo->maxOutputChannels = 0; winDsDeviceInfo->deviceOutputChannelCountIsKnown = 1; #ifdef PAWIN_USE_WDMKS_DEVICE_INFO if( pnpInterface ) { int count = PaWin_WDMKS_QueryFilterMaximumChannelCount( pnpInterface, /* isInput= */ 1 ); if( count > 0 ) { deviceInfo->maxInputChannels = count; winDsDeviceInfo->deviceInputChannelCountIsKnown = 1; } } #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ deviceInfo->defaultLowInputLatency = 0.; /** @todo IMPLEMENT ME */ deviceInfo->defaultLowOutputLatency = 0.; /** @todo IMPLEMENT ME */ deviceInfo->defaultHighInputLatency = 0.; /** @todo IMPLEMENT ME */ deviceInfo->defaultHighOutputLatency = 0.; /** @todo IMPLEMENT ME */ /* constants from a WINE patch by Francois Gouget, see: http://www.winehq.com/hypermail/wine-patches/2003/01/0290.html --- Date: Fri, 14 May 2004 10:38:12 +0200 (CEST) From: Francois Gouget To: Ross Bencina Subject: Re: Permission to use wine 48/96 wave patch in BSD licensed library [snip] I give you permission to use the patch below under the BSD license. http://www.winehq.com/hypermail/wine-patches/2003/01/0290.html [snip] */ #ifndef WAVE_FORMAT_48M08 #define WAVE_FORMAT_48M08 0x00001000 /* 48 kHz, Mono, 8-bit */ #define WAVE_FORMAT_48S08 0x00002000 /* 48 kHz, Stereo, 8-bit */ #define WAVE_FORMAT_48M16 0x00004000 /* 48 kHz, Mono, 16-bit */ #define WAVE_FORMAT_48S16 0x00008000 /* 48 kHz, Stereo, 16-bit */ #define WAVE_FORMAT_96M08 0x00010000 /* 96 kHz, Mono, 8-bit */ #define WAVE_FORMAT_96S08 0x00020000 /* 96 kHz, Stereo, 8-bit */ #define WAVE_FORMAT_96M16 0x00040000 /* 96 kHz, Mono, 16-bit */ #define WAVE_FORMAT_96S16 0x00080000 /* 96 kHz, Stereo, 16-bit */ #endif /* defaultSampleRate */ if( caps.dwChannels == 2 ) { if( caps.dwFormats & WAVE_FORMAT_4S16 ) deviceInfo->defaultSampleRate = 44100.0; else if( caps.dwFormats & WAVE_FORMAT_48S16 ) deviceInfo->defaultSampleRate = 48000.0; else if( caps.dwFormats & WAVE_FORMAT_2S16 ) deviceInfo->defaultSampleRate = 22050.0; else if( caps.dwFormats & WAVE_FORMAT_1S16 ) deviceInfo->defaultSampleRate = 11025.0; else if( caps.dwFormats & WAVE_FORMAT_96S16 ) deviceInfo->defaultSampleRate = 96000.0; else deviceInfo->defaultSampleRate = 0.; } else if( caps.dwChannels == 1 ) { if( caps.dwFormats & WAVE_FORMAT_4M16 ) deviceInfo->defaultSampleRate = 44100.0; else if( caps.dwFormats & WAVE_FORMAT_48M16 ) deviceInfo->defaultSampleRate = 48000.0; else if( caps.dwFormats & WAVE_FORMAT_2M16 ) deviceInfo->defaultSampleRate = 22050.0; else if( caps.dwFormats & WAVE_FORMAT_1M16 ) deviceInfo->defaultSampleRate = 11025.0; else if( caps.dwFormats & WAVE_FORMAT_96M16 ) deviceInfo->defaultSampleRate = 96000.0; else deviceInfo->defaultSampleRate = 0.; } else deviceInfo->defaultSampleRate = 0.; } } IDirectSoundCapture_Release( lpDirectSoundCapture ); } if( deviceOK ) { deviceInfo->name = name; if( lpGUID == NULL ) hostApi->info.defaultInputDevice = hostApi->info.deviceCount; hostApi->info.deviceCount++; } return result; } /***********************************************************************************/ PaError PaWinDs_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex hostApiIndex ) { PaError result = paNoError; int i, deviceCount; PaWinDsHostApiRepresentation *winDsHostApi; DSDeviceNamesAndGUIDs deviceNamesAndGUIDs; PaWinDsDeviceInfo *deviceInfoArray; char comWasInitialized = 0; /* If COM is already initialized CoInitialize will either return FALSE, or RPC_E_CHANGED_MODE if it was initialised in a different threading mode. In either case we shouldn't consider it an error but we need to be careful to not call CoUninitialize() if RPC_E_CHANGED_MODE was returned. */ HRESULT hr = CoInitialize(NULL); if( FAILED(hr) && hr != RPC_E_CHANGED_MODE ) return paUnanticipatedHostError; if( hr != RPC_E_CHANGED_MODE ) comWasInitialized = 1; /* initialise guid vectors so they can be safely deleted on error */ deviceNamesAndGUIDs.winDsHostApi = NULL; deviceNamesAndGUIDs.inputNamesAndGUIDs.items = NULL; deviceNamesAndGUIDs.outputNamesAndGUIDs.items = NULL; PaWinDs_InitializeDSoundEntryPoints(); winDsHostApi = (PaWinDsHostApiRepresentation*)PaUtil_AllocateMemory( sizeof(PaWinDsHostApiRepresentation) ); if( !winDsHostApi ) { result = paInsufficientMemory; goto error; } winDsHostApi->comWasInitialized = comWasInitialized; winDsHostApi->allocations = PaUtil_CreateAllocationGroup(); if( !winDsHostApi->allocations ) { result = paInsufficientMemory; goto error; } *hostApi = &winDsHostApi->inheritedHostApiRep; (*hostApi)->info.structVersion = 1; (*hostApi)->info.type = paDirectSound; (*hostApi)->info.name = "Windows DirectSound"; (*hostApi)->info.deviceCount = 0; (*hostApi)->info.defaultInputDevice = paNoDevice; (*hostApi)->info.defaultOutputDevice = paNoDevice; /* DSound - enumerate devices to count them and to gather their GUIDs */ result = InitializeDSDeviceNameAndGUIDVector( &deviceNamesAndGUIDs.inputNamesAndGUIDs, winDsHostApi->allocations ); if( result != paNoError ) goto error; result = InitializeDSDeviceNameAndGUIDVector( &deviceNamesAndGUIDs.outputNamesAndGUIDs, winDsHostApi->allocations ); if( result != paNoError ) goto error; paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerate( (LPDSENUMCALLBACK)CollectGUIDsProc, (void *)&deviceNamesAndGUIDs.inputNamesAndGUIDs ); paWinDsDSoundEntryPoints.DirectSoundEnumerate( (LPDSENUMCALLBACK)CollectGUIDsProc, (void *)&deviceNamesAndGUIDs.outputNamesAndGUIDs ); if( deviceNamesAndGUIDs.inputNamesAndGUIDs.enumerationError != paNoError ) { result = deviceNamesAndGUIDs.inputNamesAndGUIDs.enumerationError; goto error; } if( deviceNamesAndGUIDs.outputNamesAndGUIDs.enumerationError != paNoError ) { result = deviceNamesAndGUIDs.outputNamesAndGUIDs.enumerationError; goto error; } deviceCount = deviceNamesAndGUIDs.inputNamesAndGUIDs.count + deviceNamesAndGUIDs.outputNamesAndGUIDs.count; #ifdef PAWIN_USE_WDMKS_DEVICE_INFO if( deviceCount > 0 ) { deviceNamesAndGUIDs.winDsHostApi = winDsHostApi; FindDevicePnpInterfaces( &deviceNamesAndGUIDs ); } #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ if( deviceCount > 0 ) { /* allocate array for pointers to PaDeviceInfo structs */ (*hostApi)->deviceInfos = (PaDeviceInfo**)PaUtil_GroupAllocateMemory( winDsHostApi->allocations, sizeof(PaDeviceInfo*) * deviceCount ); if( !(*hostApi)->deviceInfos ) { result = paInsufficientMemory; goto error; } /* allocate all PaDeviceInfo structs in a contiguous block */ deviceInfoArray = (PaWinDsDeviceInfo*)PaUtil_GroupAllocateMemory( winDsHostApi->allocations, sizeof(PaWinDsDeviceInfo) * deviceCount ); if( !deviceInfoArray ) { result = paInsufficientMemory; goto error; } for( i=0; i < deviceCount; ++i ) { PaDeviceInfo *deviceInfo = &deviceInfoArray[i].inheritedDeviceInfo; deviceInfo->structVersion = 2; deviceInfo->hostApi = hostApiIndex; deviceInfo->name = 0; (*hostApi)->deviceInfos[i] = deviceInfo; } for( i=0; i < deviceNamesAndGUIDs.inputNamesAndGUIDs.count; ++i ) { result = AddInputDeviceInfoFromDirectSoundCapture( winDsHostApi, deviceNamesAndGUIDs.inputNamesAndGUIDs.items[i].name, deviceNamesAndGUIDs.inputNamesAndGUIDs.items[i].lpGUID, deviceNamesAndGUIDs.inputNamesAndGUIDs.items[i].pnpInterface ); if( result != paNoError ) goto error; } for( i=0; i < deviceNamesAndGUIDs.outputNamesAndGUIDs.count; ++i ) { result = AddOutputDeviceInfoFromDirectSound( winDsHostApi, deviceNamesAndGUIDs.outputNamesAndGUIDs.items[i].name, deviceNamesAndGUIDs.outputNamesAndGUIDs.items[i].lpGUID, deviceNamesAndGUIDs.outputNamesAndGUIDs.items[i].pnpInterface ); if( result != paNoError ) goto error; } } result = TerminateDSDeviceNameAndGUIDVector( &deviceNamesAndGUIDs.inputNamesAndGUIDs ); if( result != paNoError ) goto error; result = TerminateDSDeviceNameAndGUIDVector( &deviceNamesAndGUIDs.outputNamesAndGUIDs ); if( result != paNoError ) goto error; (*hostApi)->Terminate = Terminate; (*hostApi)->OpenStream = OpenStream; (*hostApi)->IsFormatSupported = IsFormatSupported; PaUtil_InitializeStreamInterface( &winDsHostApi->callbackStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, GetStreamCpuLoad, PaUtil_DummyRead, PaUtil_DummyWrite, PaUtil_DummyGetReadAvailable, PaUtil_DummyGetWriteAvailable ); PaUtil_InitializeStreamInterface( &winDsHostApi->blockingStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, PaUtil_DummyGetCpuLoad, ReadStream, WriteStream, GetStreamReadAvailable, GetStreamWriteAvailable ); return result; error: if( winDsHostApi ) { if( winDsHostApi->allocations ) { PaUtil_FreeAllAllocations( winDsHostApi->allocations ); PaUtil_DestroyAllocationGroup( winDsHostApi->allocations ); } PaUtil_FreeMemory( winDsHostApi ); } TerminateDSDeviceNameAndGUIDVector( &deviceNamesAndGUIDs.inputNamesAndGUIDs ); TerminateDSDeviceNameAndGUIDVector( &deviceNamesAndGUIDs.outputNamesAndGUIDs ); if( comWasInitialized ) CoUninitialize(); return result; } /***********************************************************************************/ static void Terminate( struct PaUtilHostApiRepresentation *hostApi ) { PaWinDsHostApiRepresentation *winDsHostApi = (PaWinDsHostApiRepresentation*)hostApi; char comWasInitialized = winDsHostApi->comWasInitialized; /* IMPLEMENT ME: - clean up any resources not handled by the allocation group */ if( winDsHostApi->allocations ) { PaUtil_FreeAllAllocations( winDsHostApi->allocations ); PaUtil_DestroyAllocationGroup( winDsHostApi->allocations ); } PaUtil_FreeMemory( winDsHostApi ); PaWinDs_TerminateDSoundEntryPoints(); if( comWasInitialized ) CoUninitialize(); } /* Set minimal latency based on whether NT or Win95. * NT has higher latency. */ static int PaWinDS_GetMinSystemLatency( void ) { int minLatencyMsec; /* Set minimal latency based on whether NT or other OS. * NT has higher latency. */ OSVERSIONINFO osvi; osvi.dwOSVersionInfoSize = sizeof( osvi ); GetVersionEx( &osvi ); DBUG(("PA - PlatformId = 0x%x\n", osvi.dwPlatformId )); DBUG(("PA - MajorVersion = 0x%x\n", osvi.dwMajorVersion )); DBUG(("PA - MinorVersion = 0x%x\n", osvi.dwMinorVersion )); /* Check for NT */ if( (osvi.dwMajorVersion == 4) && (osvi.dwPlatformId == 2) ) { minLatencyMsec = PA_WIN_NT_LATENCY; } else if(osvi.dwMajorVersion >= 5) { minLatencyMsec = PA_WIN_WDM_LATENCY; } else { minLatencyMsec = PA_WIN_9X_LATENCY; } return minLatencyMsec; } static PaError ValidateWinDirectSoundSpecificStreamInfo( const PaStreamParameters *streamParameters, const PaWinDirectSoundStreamInfo *streamInfo ) { if( streamInfo ) { if( streamInfo->size != sizeof( PaWinDirectSoundStreamInfo ) || streamInfo->version != 1 ) { return paIncompatibleHostApiSpecificStreamInfo; } } return paNoError; } /***********************************************************************************/ static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ) { PaError result; PaWinDsDeviceInfo *inputWinDsDeviceInfo, *outputWinDsDeviceInfo; PaDeviceInfo *inputDeviceInfo, *outputDeviceInfo; int inputChannelCount, outputChannelCount; PaSampleFormat inputSampleFormat, outputSampleFormat; PaWinDirectSoundStreamInfo *inputStreamInfo, *outputStreamInfo; if( inputParameters ) { inputWinDsDeviceInfo = (PaWinDsDeviceInfo*) hostApi->deviceInfos[ inputParameters->device ]; inputDeviceInfo = &inputWinDsDeviceInfo->inheritedDeviceInfo; inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that input device can support inputChannelCount */ if( inputWinDsDeviceInfo->deviceInputChannelCountIsKnown && inputChannelCount > inputDeviceInfo->maxInputChannels ) return paInvalidChannelCount; /* validate inputStreamInfo */ inputStreamInfo = (PaWinDirectSoundStreamInfo*)inputParameters->hostApiSpecificStreamInfo; result = ValidateWinDirectSoundSpecificStreamInfo( inputParameters, inputStreamInfo ); if( result != paNoError ) return result; } else { inputChannelCount = 0; } if( outputParameters ) { outputWinDsDeviceInfo = (PaWinDsDeviceInfo*) hostApi->deviceInfos[ outputParameters->device ]; outputDeviceInfo = &outputWinDsDeviceInfo->inheritedDeviceInfo; outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that output device can support inputChannelCount */ if( outputWinDsDeviceInfo->deviceOutputChannelCountIsKnown && outputChannelCount > outputDeviceInfo->maxOutputChannels ) return paInvalidChannelCount; /* validate outputStreamInfo */ outputStreamInfo = (PaWinDirectSoundStreamInfo*)outputParameters->hostApiSpecificStreamInfo; result = ValidateWinDirectSoundSpecificStreamInfo( outputParameters, outputStreamInfo ); if( result != paNoError ) return result; } else { outputChannelCount = 0; } /* IMPLEMENT ME: - if a full duplex stream is requested, check that the combination of input and output parameters is supported if necessary - check that the device supports sampleRate Because the buffer adapter handles conversion between all standard sample formats, the following checks are only required if paCustomFormat is implemented, or under some other unusual conditions. - check that input device can support inputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format - check that output device can support outputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format */ return paFormatIsSupported; } /************************************************************************* ** Determine minimum number of buffers required for this host based ** on minimum latency. Latency can be optionally set by user by setting ** an environment variable. For example, to set latency to 200 msec, put: ** ** set PA_MIN_LATENCY_MSEC=200 ** ** in the AUTOEXEC.BAT file and reboot. ** If the environment variable is not set, then the latency will be determined ** based on the OS. Windows NT has higher latency than Win95. */ #define PA_LATENCY_ENV_NAME ("PA_MIN_LATENCY_MSEC") #define PA_ENV_BUF_SIZE (32) static int PaWinDs_GetMinLatencyFrames( double sampleRate ) { char envbuf[PA_ENV_BUF_SIZE]; DWORD hresult; int minLatencyMsec = 0; /* Let user determine minimal latency by setting environment variable. */ hresult = GetEnvironmentVariableA( PA_LATENCY_ENV_NAME, envbuf, PA_ENV_BUF_SIZE ); if( (hresult > 0) && (hresult < PA_ENV_BUF_SIZE) ) { minLatencyMsec = atoi( envbuf ); } else { minLatencyMsec = PaWinDS_GetMinSystemLatency(); #if PA_USE_HIGH_LATENCY PRINT(("PA - Minimum Latency set to %d msec!\n", minLatencyMsec )); #endif } return (int) (minLatencyMsec * sampleRate * SECONDS_PER_MSEC); } static HRESULT InitInputBuffer( PaWinDsStream *stream, PaSampleFormat sampleFormat, unsigned long nFrameRate, WORD nChannels, int bytesPerBuffer, PaWinWaveFormatChannelMask channelMask ) { DSCBUFFERDESC captureDesc; PaWinWaveFormat waveFormat; HRESULT result; stream->bytesPerInputFrame = nChannels * Pa_GetSampleSize(sampleFormat); stream->inputSize = bytesPerBuffer; // ---------------------------------------------------------------------- // Setup the secondary buffer description ZeroMemory(&captureDesc, sizeof(DSCBUFFERDESC)); captureDesc.dwSize = sizeof(DSCBUFFERDESC); captureDesc.dwFlags = 0; captureDesc.dwBufferBytes = bytesPerBuffer; captureDesc.lpwfxFormat = (WAVEFORMATEX*)&waveFormat; // Create the capture buffer // first try WAVEFORMATEXTENSIBLE. if this fails, fall back to WAVEFORMATEX PaWin_InitializeWaveFormatExtensible( &waveFormat, nChannels, sampleFormat, nFrameRate, channelMask ); if( IDirectSoundCapture_CreateCaptureBuffer( stream->pDirectSoundCapture, &captureDesc, &stream->pDirectSoundInputBuffer, NULL) != DS_OK ) { PaWin_InitializeWaveFormatEx( &waveFormat, nChannels, sampleFormat, nFrameRate ); if ((result = IDirectSoundCapture_CreateCaptureBuffer( stream->pDirectSoundCapture, &captureDesc, &stream->pDirectSoundInputBuffer, NULL)) != DS_OK) return result; } stream->readOffset = 0; // reset last read position to start of buffer return DS_OK; } static HRESULT InitOutputBuffer( PaWinDsStream *stream, PaSampleFormat sampleFormat, unsigned long nFrameRate, WORD nChannels, int bytesPerBuffer, PaWinWaveFormatChannelMask channelMask ) { /** @todo FIXME: if InitOutputBuffer returns an error I'm not sure it frees all resources cleanly */ DWORD dwDataLen; DWORD playCursor; HRESULT result; LPDIRECTSOUNDBUFFER pPrimaryBuffer; HWND hWnd; HRESULT hr; PaWinWaveFormat waveFormat; DSBUFFERDESC primaryDesc; DSBUFFERDESC secondaryDesc; unsigned char* pDSBuffData; LARGE_INTEGER counterFrequency; int bytesPerSample = Pa_GetSampleSize(sampleFormat); stream->outputBufferSizeBytes = bytesPerBuffer; stream->outputIsRunning = FALSE; stream->outputUnderflowCount = 0; stream->dsw_framesWritten = 0; stream->bytesPerOutputFrame = nChannels * bytesPerSample; // We were using getForegroundWindow() but sometimes the ForegroundWindow may not be the // applications's window. Also if that window is closed before the Buffer is closed // then DirectSound can crash. (Thanks for Scott Patterson for reporting this.) // So we will use GetDesktopWindow() which was suggested by Miller Puckette. // hWnd = GetForegroundWindow(); // // FIXME: The example code I have on the net creates a hidden window that // is managed by our code - I think we should do that - one hidden // window for the whole of Pa_DS // hWnd = GetDesktopWindow(); // Set cooperative level to DSSCL_EXCLUSIVE so that we can get 16 bit output, 44.1 KHz. // Exclusize also prevents unexpected sounds from other apps during a performance. if ((hr = IDirectSound_SetCooperativeLevel( stream->pDirectSound, hWnd, DSSCL_EXCLUSIVE)) != DS_OK) { return hr; } // ----------------------------------------------------------------------- // Create primary buffer and set format just so we can specify our custom format. // Otherwise we would be stuck with the default which might be 8 bit or 22050 Hz. // Setup the primary buffer description ZeroMemory(&primaryDesc, sizeof(DSBUFFERDESC)); primaryDesc.dwSize = sizeof(DSBUFFERDESC); primaryDesc.dwFlags = DSBCAPS_PRIMARYBUFFER; // all panning, mixing, etc done by synth primaryDesc.dwBufferBytes = 0; primaryDesc.lpwfxFormat = NULL; // Create the buffer if ((result = IDirectSound_CreateSoundBuffer( stream->pDirectSound, &primaryDesc, &pPrimaryBuffer, NULL)) != DS_OK) return result; // Set the primary buffer's format // first try WAVEFORMATEXTENSIBLE. if this fails, fall back to WAVEFORMATEX PaWin_InitializeWaveFormatExtensible( &waveFormat, nChannels, sampleFormat, nFrameRate, channelMask ); if( IDirectSoundBuffer_SetFormat( pPrimaryBuffer, (WAVEFORMATEX*)&waveFormat) != DS_OK ) { PaWin_InitializeWaveFormatEx( &waveFormat, nChannels, sampleFormat, nFrameRate ); if((result = IDirectSoundBuffer_SetFormat( pPrimaryBuffer, (WAVEFORMATEX*)&waveFormat)) != DS_OK) return result; } // ---------------------------------------------------------------------- // Setup the secondary buffer description ZeroMemory(&secondaryDesc, sizeof(DSBUFFERDESC)); secondaryDesc.dwSize = sizeof(DSBUFFERDESC); secondaryDesc.dwFlags = DSBCAPS_GLOBALFOCUS | DSBCAPS_GETCURRENTPOSITION2; secondaryDesc.dwBufferBytes = bytesPerBuffer; secondaryDesc.lpwfxFormat = (WAVEFORMATEX*)&waveFormat; // Create the secondary buffer if ((result = IDirectSound_CreateSoundBuffer( stream->pDirectSound, &secondaryDesc, &stream->pDirectSoundOutputBuffer, NULL)) != DS_OK) return result; // Lock the DS buffer if ((result = IDirectSoundBuffer_Lock( stream->pDirectSoundOutputBuffer, 0, stream->outputBufferSizeBytes, (LPVOID*)&pDSBuffData, &dwDataLen, NULL, 0, 0)) != DS_OK) return result; // Zero the DS buffer ZeroMemory(pDSBuffData, dwDataLen); // Unlock the DS buffer if ((result = IDirectSoundBuffer_Unlock( stream->pDirectSoundOutputBuffer, pDSBuffData, dwDataLen, NULL, 0)) != DS_OK) return result; if( QueryPerformanceFrequency( &counterFrequency ) ) { int framesInBuffer = bytesPerBuffer / (nChannels * bytesPerSample); stream->perfCounterTicksPerBuffer.QuadPart = (counterFrequency.QuadPart * framesInBuffer) / nFrameRate; } else { stream->perfCounterTicksPerBuffer.QuadPart = 0; } // Let DSound set the starting write position because if we set it to zero, it looks like the // buffer is full to begin with. This causes a long pause before sound starts when using large buffers. hr = IDirectSoundBuffer_GetCurrentPosition( stream->pDirectSoundOutputBuffer, &playCursor, &stream->outputBufferWriteOffsetBytes ); if( hr != DS_OK ) { return hr; } stream->dsw_framesWritten = stream->outputBufferWriteOffsetBytes / stream->bytesPerOutputFrame; /* printf("DSW_InitOutputBuffer: playCursor = %d, writeCursor = %d\n", playCursor, dsw->dsw_WriteOffset ); */ return DS_OK; } /***********************************************************************************/ /* see pa_hostapi.h for a list of validity guarantees made about OpenStream parameters */ static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ) { PaError result = paNoError; PaWinDsHostApiRepresentation *winDsHostApi = (PaWinDsHostApiRepresentation*)hostApi; PaWinDsStream *stream = 0; PaWinDsDeviceInfo *inputWinDsDeviceInfo, *outputWinDsDeviceInfo; PaDeviceInfo *inputDeviceInfo, *outputDeviceInfo; int inputChannelCount, outputChannelCount; PaSampleFormat inputSampleFormat, outputSampleFormat; PaSampleFormat hostInputSampleFormat, hostOutputSampleFormat; unsigned long suggestedInputLatencyFrames, suggestedOutputLatencyFrames; PaWinDirectSoundStreamInfo *inputStreamInfo, *outputStreamInfo; PaWinWaveFormatChannelMask inputChannelMask, outputChannelMask; if( inputParameters ) { inputWinDsDeviceInfo = (PaWinDsDeviceInfo*) hostApi->deviceInfos[ inputParameters->device ]; inputDeviceInfo = &inputWinDsDeviceInfo->inheritedDeviceInfo; inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; suggestedInputLatencyFrames = (unsigned long)(inputParameters->suggestedLatency * sampleRate); /* IDEA: the following 3 checks could be performed by default by pa_front unless some flag indicated otherwise */ /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that input device can support inputChannelCount */ if( inputWinDsDeviceInfo->deviceInputChannelCountIsKnown && inputChannelCount > inputDeviceInfo->maxInputChannels ) return paInvalidChannelCount; /* validate hostApiSpecificStreamInfo */ inputStreamInfo = (PaWinDirectSoundStreamInfo*)inputParameters->hostApiSpecificStreamInfo; result = ValidateWinDirectSoundSpecificStreamInfo( inputParameters, inputStreamInfo ); if( result != paNoError ) return result; if( inputStreamInfo && inputStreamInfo->flags & paWinDirectSoundUseChannelMask ) inputChannelMask = inputStreamInfo->channelMask; else inputChannelMask = PaWin_DefaultChannelMask( inputChannelCount ); } else { inputChannelCount = 0; inputSampleFormat = 0; suggestedInputLatencyFrames = 0; } if( outputParameters ) { outputWinDsDeviceInfo = (PaWinDsDeviceInfo*) hostApi->deviceInfos[ outputParameters->device ]; outputDeviceInfo = &outputWinDsDeviceInfo->inheritedDeviceInfo; outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; suggestedOutputLatencyFrames = (unsigned long)(outputParameters->suggestedLatency * sampleRate); /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that output device can support outputChannelCount */ if( outputWinDsDeviceInfo->deviceOutputChannelCountIsKnown && outputChannelCount > outputDeviceInfo->maxOutputChannels ) return paInvalidChannelCount; /* validate hostApiSpecificStreamInfo */ outputStreamInfo = (PaWinDirectSoundStreamInfo*)outputParameters->hostApiSpecificStreamInfo; result = ValidateWinDirectSoundSpecificStreamInfo( outputParameters, outputStreamInfo ); if( result != paNoError ) return result; if( outputStreamInfo && outputStreamInfo->flags & paWinDirectSoundUseChannelMask ) outputChannelMask = outputStreamInfo->channelMask; else outputChannelMask = PaWin_DefaultChannelMask( outputChannelCount ); } else { outputChannelCount = 0; outputSampleFormat = 0; suggestedOutputLatencyFrames = 0; } /* IMPLEMENT ME: ( the following two checks are taken care of by PaUtil_InitializeBufferProcessor() ) - check that input device can support inputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format - check that output device can support outputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format - if a full duplex stream is requested, check that the combination of input and output parameters is supported - check that the device supports sampleRate - alter sampleRate to a close allowable rate if possible / necessary - validate suggestedInputLatency and suggestedOutputLatency parameters, use default values where necessary */ /* validate platform specific flags */ if( (streamFlags & paPlatformSpecificFlags) != 0 ) return paInvalidFlag; /* unexpected platform specific flag */ stream = (PaWinDsStream*)PaUtil_AllocateMemory( sizeof(PaWinDsStream) ); if( !stream ) { result = paInsufficientMemory; goto error; } memset( stream, 0, sizeof(PaWinDsStream) ); /* initialize all stream variables to 0 */ if( streamCallback ) { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &winDsHostApi->callbackStreamInterface, streamCallback, userData ); } else { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &winDsHostApi->blockingStreamInterface, streamCallback, userData ); } PaUtil_InitializeCpuLoadMeasurer( &stream->cpuLoadMeasurer, sampleRate ); if( inputParameters ) { /* IMPLEMENT ME - establish which host formats are available */ PaSampleFormat nativeInputFormats = paInt16; //PaSampleFormat nativeFormats = paUInt8 | paInt16 | paInt24 | paInt32 | paFloat32; hostInputSampleFormat = PaUtil_SelectClosestAvailableFormat( nativeInputFormats, inputParameters->sampleFormat ); } else { hostInputSampleFormat = 0; } if( outputParameters ) { /* IMPLEMENT ME - establish which host formats are available */ PaSampleFormat nativeOutputFormats = paInt16; //PaSampleFormat nativeOutputFormats = paUInt8 | paInt16 | paInt24 | paInt32 | paFloat32; hostOutputSampleFormat = PaUtil_SelectClosestAvailableFormat( nativeOutputFormats, outputParameters->sampleFormat ); } else { hostOutputSampleFormat = 0; } result = PaUtil_InitializeBufferProcessor( &stream->bufferProcessor, inputChannelCount, inputSampleFormat, hostInputSampleFormat, outputChannelCount, outputSampleFormat, hostOutputSampleFormat, sampleRate, streamFlags, framesPerBuffer, framesPerBuffer, /* ignored in paUtilVariableHostBufferSizePartialUsageAllowed mode. */ /* This next mode is required because DS can split the host buffer when it wraps around. */ paUtilVariableHostBufferSizePartialUsageAllowed, streamCallback, userData ); if( result != paNoError ) goto error; stream->streamRepresentation.streamInfo.inputLatency = PaUtil_GetBufferProcessorInputLatency(&stream->bufferProcessor); /* FIXME: not initialised anywhere else */ stream->streamRepresentation.streamInfo.outputLatency = PaUtil_GetBufferProcessorOutputLatency(&stream->bufferProcessor); /* FIXME: not initialised anywhere else */ stream->streamRepresentation.streamInfo.sampleRate = sampleRate; /* DirectSound specific initialization */ { HRESULT hr; int bytesPerDirectSoundBuffer; int userLatencyFrames; int minLatencyFrames; stream->timerID = 0; /* Get system minimum latency. */ minLatencyFrames = PaWinDs_GetMinLatencyFrames( sampleRate ); /* Let user override latency by passing latency parameter. */ userLatencyFrames = (suggestedInputLatencyFrames > suggestedOutputLatencyFrames) ? suggestedInputLatencyFrames : suggestedOutputLatencyFrames; if( userLatencyFrames > 0 ) minLatencyFrames = userLatencyFrames; /* Calculate stream->framesPerDSBuffer depending on framesPerBuffer */ if( framesPerBuffer == paFramesPerBufferUnspecified ) { /* App support variable framesPerBuffer */ stream->framesPerDSBuffer = minLatencyFrames; stream->streamRepresentation.streamInfo.outputLatency = (double)(minLatencyFrames - 1) / sampleRate; } else { /* Round up to number of buffers needed to guarantee that latency. */ int numUserBuffers = (minLatencyFrames + framesPerBuffer - 1) / framesPerBuffer; if( numUserBuffers < 1 ) numUserBuffers = 1; numUserBuffers += 1; /* So we have latency worth of buffers ahead of current buffer. */ stream->framesPerDSBuffer = framesPerBuffer * numUserBuffers; stream->streamRepresentation.streamInfo.outputLatency = (double)(framesPerBuffer * (numUserBuffers-1)) / sampleRate; } { /** @todo REVIEW: this calculation seems incorrect to me - rossb. */ int msecLatency = (int) ((stream->framesPerDSBuffer * MSEC_PER_SECOND) / sampleRate); PRINT(("PortAudio on DirectSound - Latency = %d frames, %d msec\n", stream->framesPerDSBuffer, msecLatency )); } /* ------------------ OUTPUT */ if( outputParameters ) { /* PaDeviceInfo *deviceInfo = hostApi->deviceInfos[ outputParameters->device ]; DBUG(("PaHost_OpenStream: deviceID = 0x%x\n", outputParameters->device)); */ int bytesPerSample = Pa_GetSampleSize(hostOutputSampleFormat); bytesPerDirectSoundBuffer = stream->framesPerDSBuffer * outputParameters->channelCount * bytesPerSample; if( bytesPerDirectSoundBuffer < DSBSIZE_MIN ) { result = paBufferTooSmall; goto error; } else if( bytesPerDirectSoundBuffer > DSBSIZE_MAX ) { result = paBufferTooBig; goto error; } hr = paWinDsDSoundEntryPoints.DirectSoundCreate( ((PaWinDsDeviceInfo*)hostApi->deviceInfos[outputParameters->device])->lpGUID, &stream->pDirectSound, NULL ); if( hr != DS_OK ) { ERR_RPT(("PortAudio: DirectSoundCreate() failed!\n")); result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hr ); goto error; } hr = InitOutputBuffer( stream, hostOutputSampleFormat, (unsigned long) (sampleRate + 0.5), (WORD)outputParameters->channelCount, bytesPerDirectSoundBuffer, outputChannelMask ); DBUG(("InitOutputBuffer() returns %x\n", hr)); if( hr != DS_OK ) { result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hr ); goto error; } /* Calculate value used in latency calculation to avoid real-time divides. */ stream->secondsPerHostByte = 1.0 / (stream->bufferProcessor.bytesPerHostOutputSample * outputChannelCount * sampleRate); } /* ------------------ INPUT */ if( inputParameters ) { /* PaDeviceInfo *deviceInfo = hostApi->deviceInfos[ inputParameters->device ]; DBUG(("PaHost_OpenStream: deviceID = 0x%x\n", inputParameters->device)); */ int bytesPerSample = Pa_GetSampleSize(hostInputSampleFormat); bytesPerDirectSoundBuffer = stream->framesPerDSBuffer * inputParameters->channelCount * bytesPerSample; if( bytesPerDirectSoundBuffer < DSBSIZE_MIN ) { result = paBufferTooSmall; goto error; } else if( bytesPerDirectSoundBuffer > DSBSIZE_MAX ) { result = paBufferTooBig; goto error; } hr = paWinDsDSoundEntryPoints.DirectSoundCaptureCreate( ((PaWinDsDeviceInfo*)hostApi->deviceInfos[inputParameters->device])->lpGUID, &stream->pDirectSoundCapture, NULL ); if( hr != DS_OK ) { ERR_RPT(("PortAudio: DirectSoundCaptureCreate() failed!\n")); result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hr ); goto error; } hr = InitInputBuffer( stream, hostInputSampleFormat, (unsigned long) (sampleRate + 0.5), (WORD)inputParameters->channelCount, bytesPerDirectSoundBuffer, inputChannelMask ); DBUG(("InitInputBuffer() returns %x\n", hr)); if( hr != DS_OK ) { ERR_RPT(("PortAudio: DSW_InitInputBuffer() returns %x\n", hr)); result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hr ); goto error; } } } *s = (PaStream*)stream; return result; error: if( stream ) PaUtil_FreeMemory( stream ); return result; } /************************************************************************************ * Determine how much space can be safely written to in DS buffer. * Detect underflows and overflows. * Does not allow writing into safety gap maintained by DirectSound. */ static HRESULT QueryOutputSpace( PaWinDsStream *stream, long *bytesEmpty ) { HRESULT hr; DWORD playCursor; DWORD writeCursor; long numBytesEmpty; long playWriteGap; // Query to see how much room is in buffer. hr = IDirectSoundBuffer_GetCurrentPosition( stream->pDirectSoundOutputBuffer, &playCursor, &writeCursor ); if( hr != DS_OK ) { return hr; } // Determine size of gap between playIndex and WriteIndex that we cannot write into. playWriteGap = writeCursor - playCursor; if( playWriteGap < 0 ) playWriteGap += stream->outputBufferSizeBytes; // unwrap /* DirectSound doesn't have a large enough playCursor so we cannot detect wrap-around. */ /* Attempt to detect playCursor wrap-around and correct it. */ if( stream->outputIsRunning && (stream->perfCounterTicksPerBuffer.QuadPart != 0) ) { /* How much time has elapsed since last check. */ LARGE_INTEGER currentTime; LARGE_INTEGER elapsedTime; long bytesPlayed; long bytesExpected; long buffersWrapped; QueryPerformanceCounter( ¤tTime ); elapsedTime.QuadPart = currentTime.QuadPart - stream->previousPlayTime.QuadPart; stream->previousPlayTime = currentTime; /* How many bytes does DirectSound say have been played. */ bytesPlayed = playCursor - stream->previousPlayCursor; if( bytesPlayed < 0 ) bytesPlayed += stream->outputBufferSizeBytes; // unwrap stream->previousPlayCursor = playCursor; /* Calculate how many bytes we would have expected to been played by now. */ bytesExpected = (long) ((elapsedTime.QuadPart * stream->outputBufferSizeBytes) / stream->perfCounterTicksPerBuffer.QuadPart); buffersWrapped = (bytesExpected - bytesPlayed) / stream->outputBufferSizeBytes; if( buffersWrapped > 0 ) { playCursor += (buffersWrapped * stream->outputBufferSizeBytes); bytesPlayed += (buffersWrapped * stream->outputBufferSizeBytes); } /* Maintain frame output cursor. */ stream->framesPlayed += (bytesPlayed / stream->bytesPerOutputFrame); } numBytesEmpty = playCursor - stream->outputBufferWriteOffsetBytes; if( numBytesEmpty < 0 ) numBytesEmpty += stream->outputBufferSizeBytes; // unwrap offset /* Have we underflowed? */ if( numBytesEmpty > (stream->outputBufferSizeBytes - playWriteGap) ) { if( stream->outputIsRunning ) { stream->outputUnderflowCount += 1; } stream->outputBufferWriteOffsetBytes = writeCursor; numBytesEmpty = stream->outputBufferSizeBytes - playWriteGap; } *bytesEmpty = numBytesEmpty; return hr; } /***********************************************************************************/ static PaError Pa_TimeSlice( PaWinDsStream *stream ) { PaError result = 0; /* FIXME: this should be declared int and this function should also return that type (same as stream callback return type)*/ long numFrames = 0; long bytesEmpty = 0; long bytesFilled = 0; long bytesToXfer = 0; long framesToXfer = 0; long numInFramesReady = 0; long numOutFramesReady = 0; long bytesProcessed; HRESULT hresult; double outputLatency = 0; PaStreamCallbackTimeInfo timeInfo = {0,0,0}; /** @todo implement inputBufferAdcTime */ /* Input */ LPBYTE lpInBuf1 = NULL; LPBYTE lpInBuf2 = NULL; DWORD dwInSize1 = 0; DWORD dwInSize2 = 0; /* Output */ LPBYTE lpOutBuf1 = NULL; LPBYTE lpOutBuf2 = NULL; DWORD dwOutSize1 = 0; DWORD dwOutSize2 = 0; /* How much input data is available? */ if( stream->bufferProcessor.inputChannelCount > 0 ) { HRESULT hr; DWORD capturePos; DWORD readPos; long filled = 0; // Query to see how much data is in buffer. // We don't need the capture position but sometimes DirectSound doesn't handle NULLS correctly // so let's pass a pointer just to be safe. hr = IDirectSoundCaptureBuffer_GetCurrentPosition( stream->pDirectSoundInputBuffer, &capturePos, &readPos ); if( hr == DS_OK ) { filled = readPos - stream->readOffset; if( filled < 0 ) filled += stream->inputSize; // unwrap offset bytesFilled = filled; } // FIXME: what happens if IDirectSoundCaptureBuffer_GetCurrentPosition fails? framesToXfer = numInFramesReady = bytesFilled / stream->bytesPerInputFrame; outputLatency = ((double)bytesFilled) * stream->secondsPerHostByte; /** @todo Check for overflow */ } /* How much output room is available? */ if( stream->bufferProcessor.outputChannelCount > 0 ) { UINT previousUnderflowCount = stream->outputUnderflowCount; QueryOutputSpace( stream, &bytesEmpty ); framesToXfer = numOutFramesReady = bytesEmpty / stream->bytesPerOutputFrame; /* Check for underflow */ if( stream->outputUnderflowCount != previousUnderflowCount ) stream->callbackFlags |= paOutputUnderflow; } if( (numInFramesReady > 0) && (numOutFramesReady > 0) ) { framesToXfer = (numOutFramesReady < numInFramesReady) ? numOutFramesReady : numInFramesReady; } if( framesToXfer > 0 ) { PaUtil_BeginCpuLoadMeasurement( &stream->cpuLoadMeasurer ); /* The outputBufferDacTime parameter should indicates the time at which the first sample of the output buffer is heard at the DACs. */ timeInfo.currentTime = PaUtil_GetTime(); timeInfo.outputBufferDacTime = timeInfo.currentTime + outputLatency; PaUtil_BeginBufferProcessing( &stream->bufferProcessor, &timeInfo, stream->callbackFlags ); stream->callbackFlags = 0; /* Input */ if( stream->bufferProcessor.inputChannelCount > 0 ) { bytesToXfer = framesToXfer * stream->bytesPerInputFrame; hresult = IDirectSoundCaptureBuffer_Lock ( stream->pDirectSoundInputBuffer, stream->readOffset, bytesToXfer, (void **) &lpInBuf1, &dwInSize1, (void **) &lpInBuf2, &dwInSize2, 0); if (hresult != DS_OK) { ERR_RPT(("DirectSound IDirectSoundCaptureBuffer_Lock failed, hresult = 0x%x\n",hresult)); result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hresult ); goto error2; } numFrames = dwInSize1 / stream->bytesPerInputFrame; PaUtil_SetInputFrameCount( &stream->bufferProcessor, numFrames ); PaUtil_SetInterleavedInputChannels( &stream->bufferProcessor, 0, lpInBuf1, 0 ); /* Is input split into two regions. */ if( dwInSize2 > 0 ) { numFrames = dwInSize2 / stream->bytesPerInputFrame; PaUtil_Set2ndInputFrameCount( &stream->bufferProcessor, numFrames ); PaUtil_Set2ndInterleavedInputChannels( &stream->bufferProcessor, 0, lpInBuf2, 0 ); } } /* Output */ if( stream->bufferProcessor.outputChannelCount > 0 ) { bytesToXfer = framesToXfer * stream->bytesPerOutputFrame; hresult = IDirectSoundBuffer_Lock ( stream->pDirectSoundOutputBuffer, stream->outputBufferWriteOffsetBytes, bytesToXfer, (void **) &lpOutBuf1, &dwOutSize1, (void **) &lpOutBuf2, &dwOutSize2, 0); if (hresult != DS_OK) { ERR_RPT(("DirectSound IDirectSoundBuffer_Lock failed, hresult = 0x%x\n",hresult)); result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hresult ); goto error1; } numFrames = dwOutSize1 / stream->bytesPerOutputFrame; PaUtil_SetOutputFrameCount( &stream->bufferProcessor, numFrames ); PaUtil_SetInterleavedOutputChannels( &stream->bufferProcessor, 0, lpOutBuf1, 0 ); /* Is output split into two regions. */ if( dwOutSize2 > 0 ) { numFrames = dwOutSize2 / stream->bytesPerOutputFrame; PaUtil_Set2ndOutputFrameCount( &stream->bufferProcessor, numFrames ); PaUtil_Set2ndInterleavedOutputChannels( &stream->bufferProcessor, 0, lpOutBuf2, 0 ); } } result = paContinue; numFrames = PaUtil_EndBufferProcessing( &stream->bufferProcessor, &result ); stream->framesWritten += numFrames; if( stream->bufferProcessor.outputChannelCount > 0 ) { /* FIXME: an underflow could happen here */ /* Update our buffer offset and unlock sound buffer */ bytesProcessed = numFrames * stream->bytesPerOutputFrame; stream->outputBufferWriteOffsetBytes = (stream->outputBufferWriteOffsetBytes + bytesProcessed) % stream->outputBufferSizeBytes; IDirectSoundBuffer_Unlock( stream->pDirectSoundOutputBuffer, lpOutBuf1, dwOutSize1, lpOutBuf2, dwOutSize2); stream->dsw_framesWritten += numFrames; } error1: if( stream->bufferProcessor.inputChannelCount > 0 ) { /* FIXME: an overflow could happen here */ /* Update our buffer offset and unlock sound buffer */ bytesProcessed = numFrames * stream->bytesPerInputFrame; stream->readOffset = (stream->readOffset + bytesProcessed) % stream->inputSize; IDirectSoundCaptureBuffer_Unlock( stream->pDirectSoundInputBuffer, lpInBuf1, dwInSize1, lpInBuf2, dwInSize2); } error2: PaUtil_EndCpuLoadMeasurement( &stream->cpuLoadMeasurer, numFrames ); } return result; } /*******************************************************************/ static HRESULT ZeroAvailableOutputSpace( PaWinDsStream *stream ) { HRESULT hr; LPBYTE lpbuf1 = NULL; LPBYTE lpbuf2 = NULL; DWORD dwsize1 = 0; DWORD dwsize2 = 0; long bytesEmpty; hr = QueryOutputSpace( stream, &bytesEmpty ); // updates framesPlayed if (hr != DS_OK) return hr; if( bytesEmpty == 0 ) return DS_OK; // Lock free space in the DS hr = IDirectSoundBuffer_Lock( stream->pDirectSoundOutputBuffer, stream->outputBufferWriteOffsetBytes, bytesEmpty, (void **) &lpbuf1, &dwsize1, (void **) &lpbuf2, &dwsize2, 0); if (hr == DS_OK) { // Copy the buffer into the DS ZeroMemory(lpbuf1, dwsize1); if(lpbuf2 != NULL) { ZeroMemory(lpbuf2, dwsize2); } // Update our buffer offset and unlock sound buffer stream->outputBufferWriteOffsetBytes = (stream->outputBufferWriteOffsetBytes + dwsize1 + dwsize2) % stream->outputBufferSizeBytes; IDirectSoundBuffer_Unlock( stream->pDirectSoundOutputBuffer, lpbuf1, dwsize1, lpbuf2, dwsize2); stream->dsw_framesWritten += bytesEmpty / stream->bytesPerOutputFrame; } return hr; } static void CALLBACK Pa_TimerCallback(UINT uID, UINT uMsg, DWORD_PTR dwUser, DWORD dw1, DWORD dw2) { PaWinDsStream *stream; /* suppress unused variable warnings */ (void) uID; (void) uMsg; (void) dw1; (void) dw2; stream = (PaWinDsStream *) dwUser; if( stream == NULL ) return; if( stream->isActive ) { if( stream->abortProcessing ) { stream->isActive = 0; } else if( stream->stopProcessing ) { if( stream->bufferProcessor.outputChannelCount > 0 ) { ZeroAvailableOutputSpace( stream ); /* clear isActive when all sound played */ if( stream->framesPlayed >= stream->framesWritten ) { stream->isActive = 0; } } else { stream->isActive = 0; } } else { if( Pa_TimeSlice( stream ) != 0) /* Call time slice independant of timing method. */ { /* FIXME implement handling of paComplete and paAbort if possible */ stream->stopProcessing = 1; } } if( !stream->isActive ) { if( stream->streamRepresentation.streamFinishedCallback != 0 ) stream->streamRepresentation.streamFinishedCallback( stream->streamRepresentation.userData ); } } } /*********************************************************************************** When CloseStream() is called, the multi-api layer ensures that the stream has already been stopped or aborted. */ static PaError CloseStream( PaStream* s ) { PaError result = paNoError; PaWinDsStream *stream = (PaWinDsStream*)s; // Cleanup the sound buffers if( stream->pDirectSoundOutputBuffer ) { IDirectSoundBuffer_Stop( stream->pDirectSoundOutputBuffer ); IDirectSoundBuffer_Release( stream->pDirectSoundOutputBuffer ); stream->pDirectSoundOutputBuffer = NULL; } if( stream->pDirectSoundInputBuffer ) { IDirectSoundCaptureBuffer_Stop( stream->pDirectSoundInputBuffer ); IDirectSoundCaptureBuffer_Release( stream->pDirectSoundInputBuffer ); stream->pDirectSoundInputBuffer = NULL; } if( stream->pDirectSoundCapture ) { IDirectSoundCapture_Release( stream->pDirectSoundCapture ); stream->pDirectSoundCapture = NULL; } if( stream->pDirectSound ) { IDirectSound_Release( stream->pDirectSound ); stream->pDirectSound = NULL; } PaUtil_TerminateBufferProcessor( &stream->bufferProcessor ); PaUtil_TerminateStreamRepresentation( &stream->streamRepresentation ); PaUtil_FreeMemory( stream ); return result; } /***********************************************************************************/ static PaError StartStream( PaStream *s ) { PaError result = paNoError; PaWinDsStream *stream = (PaWinDsStream*)s; HRESULT hr; PaUtil_ResetBufferProcessor( &stream->bufferProcessor ); if( stream->bufferProcessor.inputChannelCount > 0 ) { // Start the buffer playback if( stream->pDirectSoundInputBuffer != NULL ) // FIXME: not sure this check is necessary { hr = IDirectSoundCaptureBuffer_Start( stream->pDirectSoundInputBuffer, DSCBSTART_LOOPING ); } DBUG(("StartStream: DSW_StartInput returned = 0x%X.\n", hr)); if( hr != DS_OK ) { result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hr ); goto error; } } stream->framesWritten = 0; stream->callbackFlags = 0; stream->abortProcessing = 0; stream->stopProcessing = 0; stream->isActive = 1; if( stream->bufferProcessor.outputChannelCount > 0 ) { /* Give user callback a chance to pre-fill buffer. REVIEW - i thought we weren't pre-filling, rb. */ result = Pa_TimeSlice( stream ); if( result != paNoError ) return result; // FIXME - what if finished? QueryPerformanceCounter( &stream->previousPlayTime ); stream->previousPlayCursor = 0; stream->framesPlayed = 0; hr = IDirectSoundBuffer_SetCurrentPosition( stream->pDirectSoundOutputBuffer, 0 ); DBUG(("PaHost_StartOutput: IDirectSoundBuffer_SetCurrentPosition returned = 0x%X.\n", hr)); if( hr != DS_OK ) { result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hr ); goto error; } // Start the buffer playback in a loop. if( stream->pDirectSoundOutputBuffer != NULL ) // FIXME: not sure this needs to be checked here { hr = IDirectSoundBuffer_Play( stream->pDirectSoundOutputBuffer, 0, 0, DSBPLAY_LOOPING ); DBUG(("PaHost_StartOutput: IDirectSoundBuffer_Play returned = 0x%X.\n", hr)); if( hr != DS_OK ) { result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hr ); goto error; } stream->outputIsRunning = TRUE; } } /* Create timer that will wake us up so we can fill the DSound buffer. */ { int resolution; int framesPerWakeup = stream->framesPerDSBuffer / 4; int msecPerWakeup = MSEC_PER_SECOND * framesPerWakeup / (int) stream->streamRepresentation.streamInfo.sampleRate; if( msecPerWakeup < 10 ) msecPerWakeup = 10; else if( msecPerWakeup > 100 ) msecPerWakeup = 100; resolution = msecPerWakeup/4; stream->timerID = timeSetEvent( msecPerWakeup, resolution, (LPTIMECALLBACK) Pa_TimerCallback, (DWORD_PTR) stream, TIME_PERIODIC ); } if( stream->timerID == 0 ) { stream->isActive = 0; result = paUnanticipatedHostError; PA_DS_SET_LAST_DIRECTSOUND_ERROR( hr ); goto error; } stream->isStarted = TRUE; error: return result; } /***********************************************************************************/ static PaError StopStream( PaStream *s ) { PaError result = paNoError; PaWinDsStream *stream = (PaWinDsStream*)s; HRESULT hr; int timeoutMsec; stream->stopProcessing = 1; /* Set timeout at 20% beyond maximum time we might wait. */ timeoutMsec = (int) (1200.0 * stream->framesPerDSBuffer / stream->streamRepresentation.streamInfo.sampleRate); while( stream->isActive && (timeoutMsec > 0) ) { Sleep(10); timeoutMsec -= 10; } if( stream->timerID != 0 ) { timeKillEvent(stream->timerID); /* Stop callback timer. */ stream->timerID = 0; } if( stream->bufferProcessor.outputChannelCount > 0 ) { // Stop the buffer playback if( stream->pDirectSoundOutputBuffer != NULL ) { stream->outputIsRunning = FALSE; // FIXME: what happens if IDirectSoundBuffer_Stop returns an error? hr = IDirectSoundBuffer_Stop( stream->pDirectSoundOutputBuffer ); } } if( stream->bufferProcessor.inputChannelCount > 0 ) { // Stop the buffer capture if( stream->pDirectSoundInputBuffer != NULL ) { // FIXME: what happens if IDirectSoundCaptureBuffer_Stop returns an error? hr = IDirectSoundCaptureBuffer_Stop( stream->pDirectSoundInputBuffer ); } } stream->isStarted = FALSE; return result; } /***********************************************************************************/ static PaError AbortStream( PaStream *s ) { PaWinDsStream *stream = (PaWinDsStream*)s; stream->abortProcessing = 1; return StopStream( s ); } /***********************************************************************************/ static PaError IsStreamStopped( PaStream *s ) { PaWinDsStream *stream = (PaWinDsStream*)s; return !stream->isStarted; } /***********************************************************************************/ static PaError IsStreamActive( PaStream *s ) { PaWinDsStream *stream = (PaWinDsStream*)s; return stream->isActive; } /***********************************************************************************/ static PaTime GetStreamTime( PaStream *s ) { /* suppress unused variable warnings */ (void) s; return PaUtil_GetTime(); } /***********************************************************************************/ static double GetStreamCpuLoad( PaStream* s ) { PaWinDsStream *stream = (PaWinDsStream*)s; return PaUtil_GetCpuLoad( &stream->cpuLoadMeasurer ); } /*********************************************************************************** As separate stream interfaces are used for blocking and callback streams, the following functions can be guaranteed to only be called for blocking streams. */ static PaError ReadStream( PaStream* s, void *buffer, unsigned long frames ) { PaWinDsStream *stream = (PaWinDsStream*)s; /* suppress unused variable warnings */ (void) buffer; (void) frames; (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ return paNoError; } /***********************************************************************************/ static PaError WriteStream( PaStream* s, const void *buffer, unsigned long frames ) { PaWinDsStream *stream = (PaWinDsStream*)s; /* suppress unused variable warnings */ (void) buffer; (void) frames; (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ return paNoError; } /***********************************************************************************/ static signed long GetStreamReadAvailable( PaStream* s ) { PaWinDsStream *stream = (PaWinDsStream*)s; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ return 0; } /***********************************************************************************/ static signed long GetStreamWriteAvailable( PaStream* s ) { PaWinDsStream *stream = (PaWinDsStream*)s; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ return 0; } #endif sources_5316/external/portaudio/pa_win_wdmks_utils.h0000644000176700017670000000470510676550137021646 0ustar paulpaul#ifndef PA_WIN_WDMKS_UTILS_H #define PA_WIN_WDMKS_UTILS_H /* * PortAudio Portable Real-Time Audio Library * Windows WDM KS utilities * * Copyright (c) 1999 - 2007 Ross Bencina, Andrew Baldwin * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @brief Utilities for working with the Windows WDM KS API */ #ifdef __cplusplus extern "C" { #endif /** Query for the maximum number of channels supported by any pin of the specified device. Returns 0 if the query fails for any reason. @param wcharDevicePath A system level PnP interface path, supplied as a WCHAR unicode string. Declard as void* to avoid introducing a dependency on wchar_t here. @param isInput A flag specifying whether to query for input (non-zero) or output (zero) channels. */ int PaWin_WDMKS_QueryFilterMaximumChannelCount( void *wcharDevicePath, int isInput ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_WIN_WDMKS_UTILS_H */sources_5316/external/portaudio/pa_endianness.h0000644000176700017670000001242610632741650020544 0ustar paulpaul#ifndef PA_ENDIANNESS_H #define PA_ENDIANNESS_H /* * $Id: pa_endianness.h 1216 2007-06-10 09:26:00Z aknudsen $ * Portable Audio I/O Library current platform endianness macros * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Phil Burk, Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Configure endianness symbols for the target processor. Arrange for either the PA_LITTLE_ENDIAN or PA_BIG_ENDIAN preprocessor symbols to be defined. The one that is defined reflects the endianness of the target platform and may be used to implement conditional compilation of byte-order dependent code. If either PA_LITTLE_ENDIAN or PA_BIG_ENDIAN is defined already, then no attempt is made to override that setting. This may be useful if you have a better way of determining the platform's endianness. The autoconf mechanism uses this for example. A PA_VALIDATE_ENDIANNESS macro is provided to compare the compile time and runtime endiannes and raise an assertion if they don't match. */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ /* If this is an apple, we need to do detect endianness this way */ #if defined(__APPLE__) /* we need to do some endian detection that is sensitive to harware arch */ #if defined(__LITTLE_ENDIAN__) #if !defined( PA_LITTLE_ENDIAN ) #define PA_LITTLE_ENDIAN #endif #if defined( PA_BIG_ENDIAN ) #undef PA_BIG_ENDIAN #endif #else #if !defined( PA_BIG_ENDIAN ) #define PA_BIG_ENDIAN #endif #if defined( PA_LITTLE_ENDIAN ) #undef PA_LITTLE_ENDIAN #endif #endif #else /* this is not an apple, so first check the existing defines, and, failing that, detect well-known architechtures. */ #if defined(PA_LITTLE_ENDIAN) || defined(PA_BIG_ENDIAN) /* endianness define has been set externally, such as by autoconf */ #if defined(PA_LITTLE_ENDIAN) && defined(PA_BIG_ENDIAN) #error both PA_LITTLE_ENDIAN and PA_BIG_ENDIAN have been defined externally to pa_endianness.h - only one endianness at a time please #endif #else /* endianness define has not been set externally */ /* set PA_LITTLE_ENDIAN or PA_BIG_ENDIAN by testing well known platform specific defines */ #if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__NT__) || defined(LITTLE_ENDIAN) || defined(__i386) || defined(_M_IX86) || defined(__x86_64__) #define PA_LITTLE_ENDIAN /* win32, assume intel byte order */ #else #define PA_BIG_ENDIAN #endif #endif #if !defined(PA_LITTLE_ENDIAN) && !defined(PA_BIG_ENDIAN) /* If the following error is raised, you either need to modify the code above to automatically determine the endianness from other symbols defined on your platform, or define either PA_LITTLE_ENDIAN or PA_BIG_ENDIAN externally. */ #error pa_endianness.h was unable to automatically determine the endianness of the target platform #endif #endif /* PA_VALIDATE_ENDIANNESS compares the compile time and runtime endianness, and raises an assertion if they don't match. must be included in the context in which this macro is used. */ #if defined(PA_LITTLE_ENDIAN) #define PA_VALIDATE_ENDIANNESS \ { \ const long nativeOne = 1; \ assert( "PortAudio: compile time and runtime endianness don't match" && (((char *)&nativeOne)[0]) == 1 ); \ } #elif defined(PA_BIG_ENDIAN) #define PA_VALIDATE_ENDIANNESS \ { \ const long nativeOne = 1; \ assert( "PortAudio: compile time and runtime endianness don't match" && (((char *)&nativeOne)[0]) == 0 ); \ } #endif #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_ENDIANNESS_H */ sources_5316/external/portaudio/pa_debugprint.h0000644000176700017670000001166110634535037020562 0ustar paulpaul#ifndef PA_LOG_H #define PA_LOG_H /* * Log file redirector function * Copyright (c) 1999-2006 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ void PaUtil_DebugPrint( const char *format, ... ); /* The basic format for log messages is described below. If you need to add any log messages, please follow this format. Function entry (void function): "FunctionName called.\n" Function entry (non void function): "FunctionName called:\n" "\tParam1Type param1: param1Value\n" "\tParam2Type param2: param2Value\n" (etc...) Function exit (no return value): "FunctionName returned.\n" Function exit (simple return value): "FunctionName returned:\n" "\tReturnType: returnValue\n" If the return type is an error code, the error text is displayed in () If the return type is not an error code, but has taken a special value because an error occurred, then the reason for the error is shown in [] If the return type is a struct ptr, the struct is dumped. See the code below for examples */ /** PA_DEBUG() provides a simple debug message printing facility. The macro passes it's argument to a printf-like function called PaUtil_DebugPrint() which prints to stderr and always flushes the stream after printing. Because preprocessor macros cannot directly accept variable length argument lists, calls to the macro must include an additional set of parenthesis, eg: PA_DEBUG(("errorno: %d", 1001 )); */ #ifdef PA_ENABLE_DEBUG_OUTPUT #define PA_DEBUG(x) PaUtil_DebugPrint x ; #else #define PA_DEBUG(x) #endif #ifdef PA_LOG_API_CALLS #define PA_LOGAPI(x) PaUtil_DebugPrint x #define PA_LOGAPI_ENTER(functionName) PaUtil_DebugPrint( functionName " called.\n" ) #define PA_LOGAPI_ENTER_PARAMS(functionName) PaUtil_DebugPrint( functionName " called:\n" ) #define PA_LOGAPI_EXIT(functionName) PaUtil_DebugPrint( functionName " returned.\n" ) #define PA_LOGAPI_EXIT_PAERROR( functionName, result ) \ PaUtil_DebugPrint( functionName " returned:\n" ); \ PaUtil_DebugPrint("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) ) #define PA_LOGAPI_EXIT_T( functionName, resultFormatString, result ) \ PaUtil_DebugPrint( functionName " returned:\n" ); \ PaUtil_DebugPrint("\t" resultFormatString "\n", result ) #define PA_LOGAPI_EXIT_PAERROR_OR_T_RESULT( functionName, positiveResultFormatString, result ) \ PaUtil_DebugPrint( functionName " returned:\n" ); \ if( result > 0 ) \ PaUtil_DebugPrint("\t" positiveResultFormatString "\n", result ); \ else \ PaUtil_DebugPrint("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) ) #else #define PA_LOGAPI(x) #define PA_LOGAPI_ENTER(functionName) #define PA_LOGAPI_ENTER_PARAMS(functionName) #define PA_LOGAPI_EXIT(functionName) #define PA_LOGAPI_EXIT_PAERROR( functionName, result ) #define PA_LOGAPI_EXIT_T( functionName, resultFormatString, result ) #define PA_LOGAPI_EXIT_PAERROR_OR_T_RESULT( functionName, positiveResultFormatString, result ) #endif typedef void (*PaUtilLogCallback ) (const char *log); /** Install user provided log function */ void PaUtil_SetDebugPrintFunction(PaUtilLogCallback cb); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_LOG_H */ sources_5316/external/portaudio/pa_win_waveformat.h0000644000176700017670000002023410672511232021434 0ustar paulpaul#ifndef PA_WIN_WAVEFORMAT_H #define PA_WIN_WAVEFORMAT_H /* * PortAudio Portable Real-Time Audio Library * Windows WAVEFORMAT* data structure utilities * portaudio.h should be included before this file. * * Copyright (c) 2007 Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @brief Windows specific PortAudio API extension and utilities header file. */ #ifdef __cplusplus extern "C" { #endif /* The following #defines for speaker channel masks are the same as those in ksmedia.h, except with PAWIN_ prepended, KSAUDIO_ removed in some cases, and casts to PaWinWaveFormatChannelMask added. */ typedef unsigned long PaWinWaveFormatChannelMask; /* Speaker Positions: */ #define PAWIN_SPEAKER_FRONT_LEFT ((PaWinWaveFormatChannelMask)0x1) #define PAWIN_SPEAKER_FRONT_RIGHT ((PaWinWaveFormatChannelMask)0x2) #define PAWIN_SPEAKER_FRONT_CENTER ((PaWinWaveFormatChannelMask)0x4) #define PAWIN_SPEAKER_LOW_FREQUENCY ((PaWinWaveFormatChannelMask)0x8) #define PAWIN_SPEAKER_BACK_LEFT ((PaWinWaveFormatChannelMask)0x10) #define PAWIN_SPEAKER_BACK_RIGHT ((PaWinWaveFormatChannelMask)0x20) #define PAWIN_SPEAKER_FRONT_LEFT_OF_CENTER ((PaWinWaveFormatChannelMask)0x40) #define PAWIN_SPEAKER_FRONT_RIGHT_OF_CENTER ((PaWinWaveFormatChannelMask)0x80) #define PAWIN_SPEAKER_BACK_CENTER ((PaWinWaveFormatChannelMask)0x100) #define PAWIN_SPEAKER_SIDE_LEFT ((PaWinWaveFormatChannelMask)0x200) #define PAWIN_SPEAKER_SIDE_RIGHT ((PaWinWaveFormatChannelMask)0x400) #define PAWIN_SPEAKER_TOP_CENTER ((PaWinWaveFormatChannelMask)0x800) #define PAWIN_SPEAKER_TOP_FRONT_LEFT ((PaWinWaveFormatChannelMask)0x1000) #define PAWIN_SPEAKER_TOP_FRONT_CENTER ((PaWinWaveFormatChannelMask)0x2000) #define PAWIN_SPEAKER_TOP_FRONT_RIGHT ((PaWinWaveFormatChannelMask)0x4000) #define PAWIN_SPEAKER_TOP_BACK_LEFT ((PaWinWaveFormatChannelMask)0x8000) #define PAWIN_SPEAKER_TOP_BACK_CENTER ((PaWinWaveFormatChannelMask)0x10000) #define PAWIN_SPEAKER_TOP_BACK_RIGHT ((PaWinWaveFormatChannelMask)0x20000) /* Bit mask locations reserved for future use */ #define PAWIN_SPEAKER_RESERVED ((PaWinWaveFormatChannelMask)0x7FFC0000) /* Used to specify that any possible permutation of speaker configurations */ #define PAWIN_SPEAKER_ALL ((PaWinWaveFormatChannelMask)0x80000000) /* DirectSound Speaker Config */ #define PAWIN_SPEAKER_DIRECTOUT 0 #define PAWIN_SPEAKER_MONO (PAWIN_SPEAKER_FRONT_CENTER) #define PAWIN_SPEAKER_STEREO (PAWIN_SPEAKER_FRONT_LEFT | PAWIN_SPEAKER_FRONT_RIGHT) #define PAWIN_SPEAKER_QUAD (PAWIN_SPEAKER_FRONT_LEFT | PAWIN_SPEAKER_FRONT_RIGHT | \ PAWIN_SPEAKER_BACK_LEFT | PAWIN_SPEAKER_BACK_RIGHT) #define PAWIN_SPEAKER_SURROUND (PAWIN_SPEAKER_FRONT_LEFT | PAWIN_SPEAKER_FRONT_RIGHT | \ PAWIN_SPEAKER_FRONT_CENTER | PAWIN_SPEAKER_BACK_CENTER) #define PAWIN_SPEAKER_5POINT1 (PAWIN_SPEAKER_FRONT_LEFT | PAWIN_SPEAKER_FRONT_RIGHT | \ PAWIN_SPEAKER_FRONT_CENTER | PAWIN_SPEAKER_LOW_FREQUENCY | \ PAWIN_SPEAKER_BACK_LEFT | PAWIN_SPEAKER_BACK_RIGHT) #define PAWIN_SPEAKER_7POINT1 (PAWIN_SPEAKER_FRONT_LEFT | PAWIN_SPEAKER_FRONT_RIGHT | \ PAWIN_SPEAKER_FRONT_CENTER | PAWIN_SPEAKER_LOW_FREQUENCY | \ PAWIN_SPEAKER_BACK_LEFT | PAWIN_SPEAKER_BACK_RIGHT | \ PAWIN_SPEAKER_FRONT_LEFT_OF_CENTER | PAWIN_SPEAKER_FRONT_RIGHT_OF_CENTER) #define PAWIN_SPEAKER_5POINT1_SURROUND (PAWIN_SPEAKER_FRONT_LEFT | PAWIN_SPEAKER_FRONT_RIGHT | \ PAWIN_SPEAKER_FRONT_CENTER | PAWIN_SPEAKER_LOW_FREQUENCY | \ PAWIN_SPEAKER_SIDE_LEFT | PAWIN_SPEAKER_SIDE_RIGHT) #define PAWIN_SPEAKER_7POINT1_SURROUND (PAWIN_SPEAKER_FRONT_LEFT | PAWIN_SPEAKER_FRONT_RIGHT | \ PAWIN_SPEAKER_FRONT_CENTER | PAWIN_SPEAKER_LOW_FREQUENCY | \ PAWIN_SPEAKER_BACK_LEFT | PAWIN_SPEAKER_BACK_RIGHT | \ PAWIN_SPEAKER_SIDE_LEFT | PAWIN_SPEAKER_SIDE_RIGHT) /* According to the Microsoft documentation: The following are obsolete 5.1 and 7.1 settings (they lack side speakers). Note this means that the default 5.1 and 7.1 settings (KSAUDIO_SPEAKER_5POINT1 and KSAUDIO_SPEAKER_7POINT1 are similarly obsolete but are unchanged for compatibility reasons). */ #define PAWIN_SPEAKER_5POINT1_BACK PAWIN_SPEAKER_5POINT1 #define PAWIN_SPEAKER_7POINT1_WIDE PAWIN_SPEAKER_7POINT1 /* DVD Speaker Positions */ #define PAWIN_SPEAKER_GROUND_FRONT_LEFT PAWIN_SPEAKER_FRONT_LEFT #define PAWIN_SPEAKER_GROUND_FRONT_CENTER PAWIN_SPEAKER_FRONT_CENTER #define PAWIN_SPEAKER_GROUND_FRONT_RIGHT PAWIN_SPEAKER_FRONT_RIGHT #define PAWIN_SPEAKER_GROUND_REAR_LEFT PAWIN_SPEAKER_BACK_LEFT #define PAWIN_SPEAKER_GROUND_REAR_RIGHT PAWIN_SPEAKER_BACK_RIGHT #define PAWIN_SPEAKER_TOP_MIDDLE PAWIN_SPEAKER_TOP_CENTER #define PAWIN_SPEAKER_SUPER_WOOFER PAWIN_SPEAKER_LOW_FREQUENCY /* PaWinWaveFormat is defined here to provide compatibility with compilation environments which don't have headers defining WAVEFORMATEXTENSIBLE (e.g. older versions of MSVC, Borland C++ etc. The fields for WAVEFORMATEX and WAVEFORMATEXTENSIBLE are declared as an unsigned char array here to avoid clients who include this file having a dependency on windows.h and mmsystem.h, and also to to avoid having to write separate packing pragmas for each compiler. */ #define PAWIN_SIZEOF_WAVEFORMATEX 18 #define PAWIN_SIZEOF_WAVEFORMATEXTENSIBLE (PAWIN_SIZEOF_WAVEFORMATEX + 22) typedef struct{ unsigned char fields[ PAWIN_SIZEOF_WAVEFORMATEXTENSIBLE ]; unsigned long extraLongForAlignment; /* ensure that compiler aligns struct to DWORD */ } PaWinWaveFormat; /* WAVEFORMATEXTENSIBLE fields: union { WORD wValidBitsPerSample; WORD wSamplesPerBlock; WORD wReserved; } Samples; DWORD dwChannelMask; GUID SubFormat; */ #define PAWIN_INDEXOF_WVALIDBITSPERSAMPLE (PAWIN_SIZEOF_WAVEFORMATEX+0) #define PAWIN_INDEXOF_DWCHANNELMASK (PAWIN_SIZEOF_WAVEFORMATEX+2) #define PAWIN_INDEXOF_SUBFORMAT (PAWIN_SIZEOF_WAVEFORMATEX+6) /* Use the following two functions to initialize the waveformat structure. */ void PaWin_InitializeWaveFormatEx( PaWinWaveFormat *waveFormat, int numChannels, PaSampleFormat sampleFormat, double sampleRate ); void PaWin_InitializeWaveFormatExtensible( PaWinWaveFormat *waveFormat, int numChannels, PaSampleFormat sampleFormat, double sampleRate, PaWinWaveFormatChannelMask channelMask ); /* Map a channel count to a speaker channel mask */ PaWinWaveFormatChannelMask PaWin_DefaultChannelMask( int numChannels ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_WIN_WAVEFORMAT_H */sources_5316/external/portaudio/pa_win_ds_dynlink.c0000644000176700017670000001747311033222776021431 0ustar paulpaul/* * Interface for dynamically loading directsound and providing a dummy * implementation if it isn't present. * * Author: Ross Bencina (some portions Phil Burk & Robert Marsanyi) * * For PortAudio Portable Real-Time Audio Library * For more information see: http://www.portaudio.com * Copyright (c) 1999-2006 Phil Burk, Robert Marsanyi and Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostaip_src */ #undef UNICODE #include "pa_win_ds_dynlink.h" PaWinDsDSoundEntryPoints paWinDsDSoundEntryPoints = { 0, 0, 0, 0, 0, 0, 0 }; static HRESULT WINAPI DummyDllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID *ppv) { (void)rclsid; /* unused parameter */ (void)riid; /* unused parameter */ (void)ppv; /* unused parameter */ return CLASS_E_CLASSNOTAVAILABLE; } static HRESULT WINAPI DummyDirectSoundCreate(LPGUID lpcGuidDevice, LPDIRECTSOUND *ppDS, LPUNKNOWN pUnkOuter) { (void)lpcGuidDevice; /* unused parameter */ (void)ppDS; /* unused parameter */ (void)pUnkOuter; /* unused parameter */ return E_NOTIMPL; } static HRESULT WINAPI DummyDirectSoundEnumerateW(LPDSENUMCALLBACKW lpDSEnumCallback, LPVOID lpContext) { (void)lpDSEnumCallback; /* unused parameter */ (void)lpContext; /* unused parameter */ return E_NOTIMPL; } static HRESULT WINAPI DummyDirectSoundEnumerateA(LPDSENUMCALLBACKA lpDSEnumCallback, LPVOID lpContext) { (void)lpDSEnumCallback; /* unused parameter */ (void)lpContext; /* unused parameter */ return E_NOTIMPL; } static HRESULT WINAPI DummyDirectSoundCaptureCreate(LPGUID lpcGUID, LPDIRECTSOUNDCAPTURE *lplpDSC, LPUNKNOWN pUnkOuter) { (void)lpcGUID; /* unused parameter */ (void)lplpDSC; /* unused parameter */ (void)pUnkOuter; /* unused parameter */ return E_NOTIMPL; } static HRESULT WINAPI DummyDirectSoundCaptureEnumerateW(LPDSENUMCALLBACKW lpDSCEnumCallback, LPVOID lpContext) { (void)lpDSCEnumCallback; /* unused parameter */ (void)lpContext; /* unused parameter */ return E_NOTIMPL; } static HRESULT WINAPI DummyDirectSoundCaptureEnumerateA(LPDSENUMCALLBACKA lpDSCEnumCallback, LPVOID lpContext) { (void)lpDSCEnumCallback; /* unused parameter */ (void)lpContext; /* unused parameter */ return E_NOTIMPL; } void PaWinDs_InitializeDSoundEntryPoints(void) { paWinDsDSoundEntryPoints.hInstance_ = LoadLibraryA("dsound.dll"); if( paWinDsDSoundEntryPoints.hInstance_ != NULL ) { paWinDsDSoundEntryPoints.DllGetClassObject = (HRESULT (WINAPI *)(REFCLSID, REFIID , LPVOID *)) GetProcAddress( paWinDsDSoundEntryPoints.hInstance_, "DllGetClassObject" ); if( paWinDsDSoundEntryPoints.DllGetClassObject == NULL ) paWinDsDSoundEntryPoints.DllGetClassObject = DummyDllGetClassObject; paWinDsDSoundEntryPoints.DirectSoundCreate = (HRESULT (WINAPI *)(LPGUID, LPDIRECTSOUND *, LPUNKNOWN)) GetProcAddress( paWinDsDSoundEntryPoints.hInstance_, "DirectSoundCreate" ); if( paWinDsDSoundEntryPoints.DirectSoundCreate == NULL ) paWinDsDSoundEntryPoints.DirectSoundCreate = DummyDirectSoundCreate; paWinDsDSoundEntryPoints.DirectSoundEnumerateW = (HRESULT (WINAPI *)(LPDSENUMCALLBACKW, LPVOID)) GetProcAddress( paWinDsDSoundEntryPoints.hInstance_, "DirectSoundEnumerateW" ); if( paWinDsDSoundEntryPoints.DirectSoundEnumerateW == NULL ) paWinDsDSoundEntryPoints.DirectSoundEnumerateW = DummyDirectSoundEnumerateW; paWinDsDSoundEntryPoints.DirectSoundEnumerateA = (HRESULT (WINAPI *)(LPDSENUMCALLBACKA, LPVOID)) GetProcAddress( paWinDsDSoundEntryPoints.hInstance_, "DirectSoundEnumerateA" ); if( paWinDsDSoundEntryPoints.DirectSoundEnumerateA == NULL ) paWinDsDSoundEntryPoints.DirectSoundEnumerateA = DummyDirectSoundEnumerateA; paWinDsDSoundEntryPoints.DirectSoundCaptureCreate = (HRESULT (WINAPI *)(LPGUID, LPDIRECTSOUNDCAPTURE *, LPUNKNOWN)) GetProcAddress( paWinDsDSoundEntryPoints.hInstance_, "DirectSoundCaptureCreate" ); if( paWinDsDSoundEntryPoints.DirectSoundCaptureCreate == NULL ) paWinDsDSoundEntryPoints.DirectSoundCaptureCreate = DummyDirectSoundCaptureCreate; paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateW = (HRESULT (WINAPI *)(LPDSENUMCALLBACKW, LPVOID)) GetProcAddress( paWinDsDSoundEntryPoints.hInstance_, "DirectSoundCaptureEnumerateW" ); if( paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateW == NULL ) paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateW = DummyDirectSoundCaptureEnumerateW; paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateA = (HRESULT (WINAPI *)(LPDSENUMCALLBACKA, LPVOID)) GetProcAddress( paWinDsDSoundEntryPoints.hInstance_, "DirectSoundCaptureEnumerateA" ); if( paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateA == NULL ) paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateA = DummyDirectSoundCaptureEnumerateA; } else { /* initialize with dummy entry points to make live easy when ds isn't present */ paWinDsDSoundEntryPoints.DirectSoundCreate = DummyDirectSoundCreate; paWinDsDSoundEntryPoints.DirectSoundEnumerateW = DummyDirectSoundEnumerateW; paWinDsDSoundEntryPoints.DirectSoundEnumerateA = DummyDirectSoundEnumerateA; paWinDsDSoundEntryPoints.DirectSoundCaptureCreate = DummyDirectSoundCaptureCreate; paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateW = DummyDirectSoundCaptureEnumerateW; paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateA = DummyDirectSoundCaptureEnumerateA; } } void PaWinDs_TerminateDSoundEntryPoints(void) { if( paWinDsDSoundEntryPoints.hInstance_ != NULL ) { /* ensure that we crash reliably if the entry points arent initialised */ paWinDsDSoundEntryPoints.DirectSoundCreate = 0; paWinDsDSoundEntryPoints.DirectSoundEnumerateW = 0; paWinDsDSoundEntryPoints.DirectSoundEnumerateA = 0; paWinDsDSoundEntryPoints.DirectSoundCaptureCreate = 0; paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateW = 0; paWinDsDSoundEntryPoints.DirectSoundCaptureEnumerateA = 0; FreeLibrary( paWinDsDSoundEntryPoints.hInstance_ ); paWinDsDSoundEntryPoints.hInstance_ = NULL; } }sources_5316/external/portaudio/Makefile0000644000176700017670000000113611704273042017214 0ustar paulpaul# Makefile of the library "external/portaudio" # Paul Boersma, 14 January 2012 include ../../makefile.defs OBJECTS = pa_skeleton.o \ pa_unix_hostapis.o pa_unix_util.o pa_linux_alsa.o \ pa_win_hostapis.o pa_win_util.o pa_win_wmme.o pa_win_waveformat.o \ pa_front.o pa_debugprint.o pa_cpuload.o \ pa_allocation.o pa_process.o pa_converters.o pa_dither.o \ pa_stream.o .PHONY: all clean all: libportaudio.a clean: $(RM) $(OBJECTS) $(RM) libportaudio.a libportaudio.a: $(OBJECTS) touch libportaudio.a rm libportaudio.a ar cq libportaudio.a $(OBJECTS) $(RANLIB) libportaudio.a $(OBJECTS): *.h sources_5316/external/portaudio/pa_unix_util.c0000644000176700017670000004535411630477047020443 0ustar paulpaul#ifdef UNIX /* * $Id: pa_unix_util.c 1232 2007-06-16 14:49:43Z rossb $ * Portable Audio I/O Library * UNIX platform-specific support functions * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2000 Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup unix_src */ #include #include #include #include #include #include #include /* For memset */ #include #include #include "pa_util.h" #include "pa_unix_util.h" #include "pa_debugprint.h" /* Track memory allocations to avoid leaks. */ #if PA_TRACK_MEMORY static int numAllocations_ = 0; #endif void *PaUtil_AllocateMemory( long size ) { void *result = malloc( size ); #if PA_TRACK_MEMORY if( result != NULL ) numAllocations_ += 1; #endif return result; } void PaUtil_FreeMemory( void *block ) { if( block != NULL ) { free( block ); #if PA_TRACK_MEMORY numAllocations_ -= 1; #endif } } int PaUtil_CountCurrentlyAllocatedBlocks( void ) { #if PA_TRACK_MEMORY return numAllocations_; #else return 0; #endif } void Pa_Sleep( long msec ) { #ifdef HAVE_NANOSLEEP struct timespec req = {0}, rem = {0}; PaTime time = msec / 1.e3; req.tv_sec = (time_t)time; assert(time - req.tv_sec < 1.0); req.tv_nsec = (long)((time - req.tv_sec) * 1.e9); nanosleep(&req, &rem); /* XXX: Try sleeping the remaining time (contained in rem) if interrupted by a signal? */ #else while( msec > 999 ) /* For OpenBSD and IRIX, argument */ { /* to usleep must be < 1000000. */ usleep( 999000 ); msec -= 999; } usleep( msec * 1000 ); #endif } /* *** NOT USED YET: *** static int usePerformanceCounter_; static double microsecondsPerTick_; */ void PaUtil_InitializeClock( void ) { /* TODO */ } PaTime PaUtil_GetTime( void ) { #ifdef HAVE_CLOCK_GETTIME struct timespec tp; clock_gettime(CLOCK_REALTIME, &tp); return (PaTime)(tp.tv_sec + tp.tv_nsec / 1.e9); #else struct timeval tv; gettimeofday( &tv, NULL ); return (PaTime) tv.tv_usec / 1000000. + tv.tv_sec; #endif } PaError PaUtil_InitializeThreading( PaUtilThreading *threading ) { (void) paUtilErr_; return paNoError; } void PaUtil_TerminateThreading( PaUtilThreading *threading ) { } PaError PaUtil_StartThreading( PaUtilThreading *threading, void *(*threadRoutine)(void *), void *data ) { pthread_create( &threading->callbackThread, NULL, threadRoutine, data ); return paNoError; } PaError PaUtil_CancelThreading( PaUtilThreading *threading, int wait, PaError *exitResult ) { PaError result = paNoError; void *pret; if( exitResult ) *exitResult = paNoError; /* Only kill the thread if it isn't in the process of stopping (flushing adaptation buffers) */ if( !wait ) pthread_cancel( threading->callbackThread ); /* XXX: Safe to call this if the thread has exited on its own? */ pthread_join( threading->callbackThread, &pret ); #ifdef PTHREAD_CANCELED if( pret && PTHREAD_CANCELED != pret ) #else /* !wait means the thread may have been canceled */ if( pret && wait ) #endif { if( exitResult ) *exitResult = *(PaError *) pret; free( pret ); } return result; } /* Threading */ /* paUnixMainThread * We have to be a bit careful with defining this global variable, * as explained below. */ #ifdef __apple__ /* apple/gcc has a "problem" with global vars and dynamic libs. Initializing it seems to fix the problem. Described a bit in this thread: http://gcc.gnu.org/ml/gcc/2005-06/msg00179.html */ pthread_t paUnixMainThread = 0; #else /*pthreads are opaque. We don't know that asigning it an int value always makes sense, so we don't initialize it unless we have to.*/ pthread_t paUnixMainThread = 0; #endif PaError PaUnixThreading_Initialize() { paUnixMainThread = pthread_self(); return paNoError; } static PaError BoostPriority( PaUnixThread* self ) { PaError result = paNoError; struct sched_param spm = { 0 }; /* Priority should only matter between contending FIFO threads? */ spm.sched_priority = 1; assert( self ); if( pthread_setschedparam( self->thread, SCHED_FIFO, &spm ) != 0 ) { PA_UNLESS( errno == EPERM, paInternalError ); /* Lack permission to raise priority */ PA_DEBUG(( "Failed bumping priority\n" )); result = 0; } else { result = 1; /* Success */ } error: return result; } PaError PaUnixThread_New( PaUnixThread* self, void* (*threadFunc)( void* ), void* threadArg, PaTime waitForChild, int rtSched ) { PaError result = paNoError; pthread_attr_t attr; int started = 0; memset( self, 0, sizeof (PaUnixThread) ); PaUnixMutex_Initialize( &self->mtx ); PA_ASSERT_CALL( pthread_cond_init( &self->cond, NULL ), 0 ); self->parentWaiting = 0 != waitForChild; /* Spawn thread */ /* Temporarily disabled since we should test during configuration for presence of required mman.h header */ #if 0 #if defined _POSIX_MEMLOCK && (_POSIX_MEMLOCK != -1) if( rtSched ) { if( mlockall( MCL_CURRENT | MCL_FUTURE ) < 0 ) { int savedErrno = errno; /* In case errno gets overwritten */ assert( savedErrno != EINVAL ); /* Most likely a programmer error */ PA_UNLESS( (savedErrno == EPERM), paInternalError ); PA_DEBUG(( "%s: Failed locking memory\n", __FUNCTION__ )); } else PA_DEBUG(( "%s: Successfully locked memory\n", __FUNCTION__ )); } #endif #endif PA_UNLESS( !pthread_attr_init( &attr ), paInternalError ); /* Priority relative to other processes */ PA_UNLESS( !pthread_attr_setscope( &attr, PTHREAD_SCOPE_SYSTEM ), paInternalError ); PA_UNLESS( !pthread_create( &self->thread, &attr, threadFunc, threadArg ), paInternalError ); started = 1; if( rtSched ) { #if 0 if( self->useWatchdog ) { int err; struct sched_param wdSpm = { 0 }; /* Launch watchdog, watchdog sets callback thread priority */ int prio = PA_MIN( self->rtPrio + 4, sched_get_priority_max( SCHED_FIFO ) ); wdSpm.sched_priority = prio; PA_UNLESS( !pthread_attr_init( &attr ), paInternalError ); PA_UNLESS( !pthread_attr_setinheritsched( &attr, PTHREAD_EXPLICIT_SCHED ), paInternalError ); PA_UNLESS( !pthread_attr_setscope( &attr, PTHREAD_SCOPE_SYSTEM ), paInternalError ); PA_UNLESS( !pthread_attr_setschedpolicy( &attr, SCHED_FIFO ), paInternalError ); PA_UNLESS( !pthread_attr_setschedparam( &attr, &wdSpm ), paInternalError ); if( (err = pthread_create( &self->watchdogThread, &attr, &WatchdogFunc, self )) ) { PA_UNLESS( err == EPERM, paInternalError ); /* Permission error, go on without realtime privileges */ PA_DEBUG(( "Failed bumping priority\n" )); } else { int policy; self->watchdogRunning = 1; PA_ENSURE_SYSTEM( pthread_getschedparam( self->watchdogThread, &policy, &wdSpm ), 0 ); /* Check if priority is right, policy could potentially differ from SCHED_FIFO (but that's alright) */ if( wdSpm.sched_priority != prio ) { PA_DEBUG(( "Watchdog priority not set correctly (%d)\n", wdSpm.sched_priority )); PA_ENSURE( paInternalError ); } } } else #endif PA_ENSURE( BoostPriority( self ) ); { int policy; struct sched_param spm; pthread_getschedparam(self->thread, &policy, &spm); } } if( self->parentWaiting ) { PaTime till; struct timespec ts; int res = 0; PaTime now; PA_ENSURE( PaUnixMutex_Lock( &self->mtx ) ); /* Wait for stream to be started */ now = PaUtil_GetTime(); till = now + waitForChild; while( self->parentWaiting && !res ) { if( waitForChild > 0 ) { ts.tv_sec = (time_t) floor( till ); ts.tv_nsec = (long) ((till - floor( till )) * 1e9); res = pthread_cond_timedwait( &self->cond, &self->mtx.mtx, &ts ); } else { res = pthread_cond_wait( &self->cond, &self->mtx.mtx ); } } PA_ENSURE( PaUnixMutex_Unlock( &self->mtx ) ); PA_UNLESS( !res || ETIMEDOUT == res, paInternalError ); PA_DEBUG(( "%s: Waited for %g seconds for stream to start\n", __FUNCTION__, PaUtil_GetTime() - now )); if( ETIMEDOUT == res ) { PA_ENSURE( paTimedOut ); } } end: return result; error: if( started ) { PaUnixThread_Terminate( self, 0, NULL ); } goto end; } PaError PaUnixThread_Terminate( PaUnixThread* self, int wait, PaError* exitResult ) { PaError result = paNoError; void* pret; if( exitResult ) { *exitResult = paNoError; } #if 0 if( watchdogExitResult ) *watchdogExitResult = paNoError; if( th->watchdogRunning ) { pthread_cancel( th->watchdogThread ); PA_ENSURE_SYSTEM( pthread_join( th->watchdogThread, &pret ), 0 ); if( pret && pret != PTHREAD_CANCELED ) { if( watchdogExitResult ) *watchdogExitResult = *(PaError *) pret; free( pret ); } } #endif /* Only kill the thread if it isn't in the process of stopping (flushing adaptation buffers) */ /* TODO: Make join time out */ self->stopRequested = wait; if( !wait ) { PA_DEBUG(( "%s: Canceling thread %d\n", __FUNCTION__, self->thread )); /* XXX: Safe to call this if the thread has exited on its own? */ pthread_cancel( self->thread ); } PA_DEBUG(( "%s: Joining thread %d\n", __FUNCTION__, self->thread )); PA_ENSURE_SYSTEM( pthread_join( self->thread, &pret ), 0 ); if( pret && PTHREAD_CANCELED != pret ) { if( exitResult ) { *exitResult = *(PaError*)pret; } free( pret ); } error: PA_ASSERT_CALL( PaUnixMutex_Terminate( &self->mtx ), paNoError ); PA_ASSERT_CALL( pthread_cond_destroy( &self->cond ), 0 ); return result; } PaError PaUnixThread_PrepareNotify( PaUnixThread* self ) { PaError result = paNoError; PA_UNLESS( self->parentWaiting, paInternalError ); PA_ENSURE( PaUnixMutex_Lock( &self->mtx ) ); self->locked = 1; error: return result; } PaError PaUnixThread_NotifyParent( PaUnixThread* self ) { PaError result = paNoError; PA_UNLESS( self->parentWaiting, paInternalError ); if( !self->locked ) { PA_ENSURE( PaUnixMutex_Lock( &self->mtx ) ); self->locked = 1; } self->parentWaiting = 0; pthread_cond_signal( &self->cond ); PA_ENSURE( PaUnixMutex_Unlock( &self->mtx ) ); self->locked = 0; error: return result; } int PaUnixThread_StopRequested( PaUnixThread* self ) { return self->stopRequested; } PaError PaUnixMutex_Initialize( PaUnixMutex* self ) { PaError result = paNoError; PA_ASSERT_CALL( pthread_mutex_init( &self->mtx, NULL ), 0 ); return result; } PaError PaUnixMutex_Terminate( PaUnixMutex* self ) { PaError result = paNoError; PA_ASSERT_CALL( pthread_mutex_destroy( &self->mtx ), 0 ); return result; } /** Lock mutex. * * We're disabling thread cancellation while the thread is holding a lock, so mutexes are * properly unlocked at termination time. */ PaError PaUnixMutex_Lock( PaUnixMutex* self ) { PaError result = paNoError; int oldState; PA_ENSURE_SYSTEM( pthread_setcancelstate( PTHREAD_CANCEL_DISABLE, &oldState ), 0 ); PA_ENSURE_SYSTEM( pthread_mutex_lock( &self->mtx ), 0 ); error: return result; } /** Unlock mutex. * * Thread cancellation is enabled again after the mutex is properly unlocked. */ PaError PaUnixMutex_Unlock( PaUnixMutex* self ) { PaError result = paNoError; int oldState; PA_ENSURE_SYSTEM( pthread_mutex_unlock( &self->mtx ), 0 ); PA_ENSURE_SYSTEM( pthread_setcancelstate( PTHREAD_CANCEL_ENABLE, &oldState ), 0 ); error: return result; } #if 0 static void OnWatchdogExit( void *userData ) { PaAlsaThreading *th = (PaAlsaThreading *) userData; struct sched_param spm = { 0 }; assert( th ); PA_ASSERT_CALL( pthread_setschedparam( th->callbackThread, SCHED_OTHER, &spm ), 0 ); /* Lower before exiting */ PA_DEBUG(( "Watchdog exiting\n" )); } static void *WatchdogFunc( void *userData ) { PaError result = paNoError, *pres = NULL; int err; PaAlsaThreading *th = (PaAlsaThreading *) userData; unsigned intervalMsec = 500; const PaTime maxSeconds = 3.; /* Max seconds between callbacks */ PaTime timeThen = PaUtil_GetTime(), timeNow, timeElapsed, cpuTimeThen, cpuTimeNow, cpuTimeElapsed; double cpuLoad, avgCpuLoad = 0.; int throttled = 0; assert( th ); /* Execute OnWatchdogExit when exiting */ pthread_cleanup_push( &OnWatchdogExit, th ); /* Boost priority of callback thread */ PA_ENSURE( result = BoostPriority( th ) ); if( !result ) { /* Boost failed, might as well exit */ pthread_exit( NULL ); } cpuTimeThen = th->callbackCpuTime; { int policy; struct sched_param spm = { 0 }; pthread_getschedparam( pthread_self(), &policy, &spm ); PA_DEBUG(( "%s: Watchdog priority is %d\n", __FUNCTION__, spm.sched_priority )); } while( 1 ) { double lowpassCoeff = 0.9, lowpassCoeff1 = 0.99999 - lowpassCoeff; /* Test before and after in case whatever underlying sleep call isn't interrupted by pthread_cancel */ pthread_testcancel(); Pa_Sleep( intervalMsec ); pthread_testcancel(); if( PaUtil_GetTime() - th->callbackTime > maxSeconds ) { PA_DEBUG(( "Watchdog: Terminating callback thread\n" )); /* Tell thread to terminate */ err = pthread_kill( th->callbackThread, SIGKILL ); pthread_exit( NULL ); } PA_DEBUG(( "%s: PortAudio reports CPU load: %g\n", __FUNCTION__, PaUtil_GetCpuLoad( th->cpuLoadMeasurer ) )); /* Check if we should throttle, or unthrottle :P */ cpuTimeNow = th->callbackCpuTime; cpuTimeElapsed = cpuTimeNow - cpuTimeThen; cpuTimeThen = cpuTimeNow; timeNow = PaUtil_GetTime(); timeElapsed = timeNow - timeThen; timeThen = timeNow; cpuLoad = cpuTimeElapsed / timeElapsed; avgCpuLoad = avgCpuLoad * lowpassCoeff + cpuLoad * lowpassCoeff1; /* if( throttled ) PA_DEBUG(( "Watchdog: CPU load: %g, %g\n", avgCpuLoad, cpuTimeElapsed )); */ if( PaUtil_GetCpuLoad( th->cpuLoadMeasurer ) > .925 ) { static int policy; static struct sched_param spm = { 0 }; static const struct sched_param defaultSpm = { 0 }; PA_DEBUG(( "%s: Throttling audio thread, priority %d\n", __FUNCTION__, spm.sched_priority )); pthread_getschedparam( th->callbackThread, &policy, &spm ); if( !pthread_setschedparam( th->callbackThread, SCHED_OTHER, &defaultSpm ) ) { throttled = 1; } else PA_DEBUG(( "Watchdog: Couldn't lower priority of audio thread: %s\n", strerror( errno ) )); /* Give other processes a go, before raising priority again */ PA_DEBUG(( "%s: Watchdog sleeping for %lu msecs before unthrottling\n", __FUNCTION__, th->throttledSleepTime )); Pa_Sleep( th->throttledSleepTime ); /* Reset callback priority */ if( pthread_setschedparam( th->callbackThread, SCHED_FIFO, &spm ) != 0 ) { PA_DEBUG(( "%s: Couldn't raise priority of audio thread: %s\n", __FUNCTION__, strerror( errno ) )); } if( PaUtil_GetCpuLoad( th->cpuLoadMeasurer ) >= .99 ) intervalMsec = 50; else intervalMsec = 100; /* lowpassCoeff = .97; lowpassCoeff1 = .99999 - lowpassCoeff; */ } else if( throttled && avgCpuLoad < .8 ) { intervalMsec = 500; throttled = 0; /* lowpassCoeff = .9; lowpassCoeff1 = .99999 - lowpassCoeff; */ } } pthread_cleanup_pop( 1 ); /* Execute cleanup on exit */ error: /* Shouldn't get here in the normal case */ /* Pass on error code */ pres = malloc( sizeof (PaError) ); *pres = result; pthread_exit( pres ); } static void CallbackUpdate( PaAlsaThreading *th ) { th->callbackTime = PaUtil_GetTime(); th->callbackCpuTime = PaUtil_GetCpuLoad( th->cpuLoadMeasurer ); } /* static void *CanaryFunc( void *userData ) { const unsigned intervalMsec = 1000; PaUtilThreading *th = (PaUtilThreading *) userData; while( 1 ) { th->canaryTime = PaUtil_GetTime(); pthread_testcancel(); Pa_Sleep( intervalMsec ); } pthread_exit( NULL ); } */ #endif #endifsources_5316/external/portaudio/pa_converters.c0000644000176700017670000020366510474003011020573 0ustar paulpaul/* * $Id: pa_converters.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library sample conversion mechanism * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Phil Burk, Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Conversion functions implementations. If the C9x function lrintf() is available, define PA_USE_C99_LRINTF to use it @todo Consider whether functions which dither but don't clip should exist, V18 automatically enabled clipping whenever dithering was selected. Perhaps we should do the same. @todo implement the converters marked IMPLEMENT ME: Float32_To_UInt8_Dither, Float32_To_UInt8_Clip, Float32_To_UInt8_DitherClip, Int32_To_Int24_Dither, Int32_To_UInt8_Dither, Int24_To_Int16_Dither, Int24_To_Int8_Dither, Int24_To_UInt8_Dither, Int16_To_Int8_Dither, Int16_To_UInt8_Dither, @todo review the converters marked REVIEW: Float32_To_Int32, Float32_To_Int32_Dither, Float32_To_Int32_Clip, Float32_To_Int32_DitherClip, Int32_To_Int16_Dither, Int32_To_Int8_Dither, Int16_To_Int32 */ #include "pa_converters.h" #include "pa_dither.h" #include "pa_endianness.h" #include "pa_types.h" PaSampleFormat PaUtil_SelectClosestAvailableFormat( PaSampleFormat availableFormats, PaSampleFormat format ) { PaSampleFormat result; format &= ~paNonInterleaved; availableFormats &= ~paNonInterleaved; if( (format & availableFormats) == 0 ) { /* NOTE: this code depends on the sample format constants being in descending order of quality - ie best quality is 0 FIXME: should write an assert which checks that all of the known constants conform to that requirement. */ if( format != 0x01 ) { /* scan for better formats */ result = format; do { result >>= 1; } while( (result & availableFormats) == 0 && result != 0 ); } else { result = 0; } if( result == 0 ){ /* scan for worse formats */ result = format; do { result <<= 1; } while( (result & availableFormats) == 0 && result != paCustomFormat ); if( (result & availableFormats) == 0 ) result = paSampleFormatNotSupported; } }else{ result = format; } return result; } /* -------------------------------------------------------------------------- */ #define PA_SELECT_FORMAT_( format, float32, int32, int24, int16, int8, uint8 ) \ switch( format & ~paNonInterleaved ){ \ case paFloat32: \ float32 \ case paInt32: \ int32 \ case paInt24: \ int24 \ case paInt16: \ int16 \ case paInt8: \ int8 \ case paUInt8: \ uint8 \ default: return 0; \ } /* -------------------------------------------------------------------------- */ #define PA_SELECT_CONVERTER_DITHER_CLIP_( flags, source, destination ) \ if( flags & paClipOff ){ /* no clip */ \ if( flags & paDitherOff ){ /* no dither */ \ return paConverters. source ## _To_ ## destination; \ }else{ /* dither */ \ return paConverters. source ## _To_ ## destination ## _Dither; \ } \ }else{ /* clip */ \ if( flags & paDitherOff ){ /* no dither */ \ return paConverters. source ## _To_ ## destination ## _Clip; \ }else{ /* dither */ \ return paConverters. source ## _To_ ## destination ## _DitherClip; \ } \ } /* -------------------------------------------------------------------------- */ #define PA_SELECT_CONVERTER_DITHER_( flags, source, destination ) \ if( flags & paDitherOff ){ /* no dither */ \ return paConverters. source ## _To_ ## destination; \ }else{ /* dither */ \ return paConverters. source ## _To_ ## destination ## _Dither; \ } /* -------------------------------------------------------------------------- */ #define PA_USE_CONVERTER_( source, destination )\ return paConverters. source ## _To_ ## destination; /* -------------------------------------------------------------------------- */ #define PA_UNITY_CONVERSION_( wordlength )\ return paConverters. Copy_ ## wordlength ## _To_ ## wordlength; /* -------------------------------------------------------------------------- */ PaUtilConverter* PaUtil_SelectConverter( PaSampleFormat sourceFormat, PaSampleFormat destinationFormat, PaStreamFlags flags ) { PA_SELECT_FORMAT_( sourceFormat, /* paFloat32: */ PA_SELECT_FORMAT_( destinationFormat, /* paFloat32: */ PA_UNITY_CONVERSION_( 32 ), /* paInt32: */ PA_SELECT_CONVERTER_DITHER_CLIP_( flags, Float32, Int32 ), /* paInt24: */ PA_SELECT_CONVERTER_DITHER_CLIP_( flags, Float32, Int24 ), /* paInt16: */ PA_SELECT_CONVERTER_DITHER_CLIP_( flags, Float32, Int16 ), /* paInt8: */ PA_SELECT_CONVERTER_DITHER_CLIP_( flags, Float32, Int8 ), /* paUInt8: */ PA_SELECT_CONVERTER_DITHER_CLIP_( flags, Float32, UInt8 ) ), /* paInt32: */ PA_SELECT_FORMAT_( destinationFormat, /* paFloat32: */ PA_USE_CONVERTER_( Int32, Float32 ), /* paInt32: */ PA_UNITY_CONVERSION_( 32 ), /* paInt24: */ PA_SELECT_CONVERTER_DITHER_( flags, Int32, Int24 ), /* paInt16: */ PA_SELECT_CONVERTER_DITHER_( flags, Int32, Int16 ), /* paInt8: */ PA_SELECT_CONVERTER_DITHER_( flags, Int32, Int8 ), /* paUInt8: */ PA_SELECT_CONVERTER_DITHER_( flags, Int32, UInt8 ) ), /* paInt24: */ PA_SELECT_FORMAT_( destinationFormat, /* paFloat32: */ PA_USE_CONVERTER_( Int24, Float32 ), /* paInt32: */ PA_USE_CONVERTER_( Int24, Int32 ), /* paInt24: */ PA_UNITY_CONVERSION_( 24 ), /* paInt16: */ PA_SELECT_CONVERTER_DITHER_( flags, Int24, Int16 ), /* paInt8: */ PA_SELECT_CONVERTER_DITHER_( flags, Int24, Int8 ), /* paUInt8: */ PA_SELECT_CONVERTER_DITHER_( flags, Int24, UInt8 ) ), /* paInt16: */ PA_SELECT_FORMAT_( destinationFormat, /* paFloat32: */ PA_USE_CONVERTER_( Int16, Float32 ), /* paInt32: */ PA_USE_CONVERTER_( Int16, Int32 ), /* paInt24: */ PA_USE_CONVERTER_( Int16, Int24 ), /* paInt16: */ PA_UNITY_CONVERSION_( 16 ), /* paInt8: */ PA_SELECT_CONVERTER_DITHER_( flags, Int16, Int8 ), /* paUInt8: */ PA_SELECT_CONVERTER_DITHER_( flags, Int16, UInt8 ) ), /* paInt8: */ PA_SELECT_FORMAT_( destinationFormat, /* paFloat32: */ PA_USE_CONVERTER_( Int8, Float32 ), /* paInt32: */ PA_USE_CONVERTER_( Int8, Int32 ), /* paInt24: */ PA_USE_CONVERTER_( Int8, Int24 ), /* paInt16: */ PA_USE_CONVERTER_( Int8, Int16 ), /* paInt8: */ PA_UNITY_CONVERSION_( 8 ), /* paUInt8: */ PA_USE_CONVERTER_( Int8, UInt8 ) ), /* paUInt8: */ PA_SELECT_FORMAT_( destinationFormat, /* paFloat32: */ PA_USE_CONVERTER_( UInt8, Float32 ), /* paInt32: */ PA_USE_CONVERTER_( UInt8, Int32 ), /* paInt24: */ PA_USE_CONVERTER_( UInt8, Int24 ), /* paInt16: */ PA_USE_CONVERTER_( UInt8, Int16 ), /* paInt8: */ PA_USE_CONVERTER_( UInt8, Int8 ), /* paUInt8: */ PA_UNITY_CONVERSION_( 8 ) ) ) } /* -------------------------------------------------------------------------- */ #ifdef PA_NO_STANDARD_CONVERTERS /* -------------------------------------------------------------------------- */ PaUtilConverterTable paConverters = { 0, /* PaUtilConverter *Float32_To_Int32; */ 0, /* PaUtilConverter *Float32_To_Int32_Dither; */ 0, /* PaUtilConverter *Float32_To_Int32_Clip; */ 0, /* PaUtilConverter *Float32_To_Int32_DitherClip; */ 0, /* PaUtilConverter *Float32_To_Int24; */ 0, /* PaUtilConverter *Float32_To_Int24_Dither; */ 0, /* PaUtilConverter *Float32_To_Int24_Clip; */ 0, /* PaUtilConverter *Float32_To_Int24_DitherClip; */ 0, /* PaUtilConverter *Float32_To_Int16; */ 0, /* PaUtilConverter *Float32_To_Int16_Dither; */ 0, /* PaUtilConverter *Float32_To_Int16_Clip; */ 0, /* PaUtilConverter *Float32_To_Int16_DitherClip; */ 0, /* PaUtilConverter *Float32_To_Int8; */ 0, /* PaUtilConverter *Float32_To_Int8_Dither; */ 0, /* PaUtilConverter *Float32_To_Int8_Clip; */ 0, /* PaUtilConverter *Float32_To_Int8_DitherClip; */ 0, /* PaUtilConverter *Float32_To_UInt8; */ 0, /* PaUtilConverter *Float32_To_UInt8_Dither; */ 0, /* PaUtilConverter *Float32_To_UInt8_Clip; */ 0, /* PaUtilConverter *Float32_To_UInt8_DitherClip; */ 0, /* PaUtilConverter *Int32_To_Float32; */ 0, /* PaUtilConverter *Int32_To_Int24; */ 0, /* PaUtilConverter *Int32_To_Int24_Dither; */ 0, /* PaUtilConverter *Int32_To_Int16; */ 0, /* PaUtilConverter *Int32_To_Int16_Dither; */ 0, /* PaUtilConverter *Int32_To_Int8; */ 0, /* PaUtilConverter *Int32_To_Int8_Dither; */ 0, /* PaUtilConverter *Int32_To_UInt8; */ 0, /* PaUtilConverter *Int32_To_UInt8_Dither; */ 0, /* PaUtilConverter *Int24_To_Float32; */ 0, /* PaUtilConverter *Int24_To_Int32; */ 0, /* PaUtilConverter *Int24_To_Int16; */ 0, /* PaUtilConverter *Int24_To_Int16_Dither; */ 0, /* PaUtilConverter *Int24_To_Int8; */ 0, /* PaUtilConverter *Int24_To_Int8_Dither; */ 0, /* PaUtilConverter *Int24_To_UInt8; */ 0, /* PaUtilConverter *Int24_To_UInt8_Dither; */ 0, /* PaUtilConverter *Int16_To_Float32; */ 0, /* PaUtilConverter *Int16_To_Int32; */ 0, /* PaUtilConverter *Int16_To_Int24; */ 0, /* PaUtilConverter *Int16_To_Int8; */ 0, /* PaUtilConverter *Int16_To_Int8_Dither; */ 0, /* PaUtilConverter *Int16_To_UInt8; */ 0, /* PaUtilConverter *Int16_To_UInt8_Dither; */ 0, /* PaUtilConverter *Int8_To_Float32; */ 0, /* PaUtilConverter *Int8_To_Int32; */ 0, /* PaUtilConverter *Int8_To_Int24 */ 0, /* PaUtilConverter *Int8_To_Int16; */ 0, /* PaUtilConverter *Int8_To_UInt8; */ 0, /* PaUtilConverter *UInt8_To_Float32; */ 0, /* PaUtilConverter *UInt8_To_Int32; */ 0, /* PaUtilConverter *UInt8_To_Int24; */ 0, /* PaUtilConverter *UInt8_To_Int16; */ 0, /* PaUtilConverter *UInt8_To_Int8; */ 0, /* PaUtilConverter *Copy_8_To_8; */ 0, /* PaUtilConverter *Copy_16_To_16; */ 0, /* PaUtilConverter *Copy_24_To_24; */ 0 /* PaUtilConverter *Copy_32_To_32; */ }; /* -------------------------------------------------------------------------- */ #else /* PA_NO_STANDARD_CONVERTERS is not defined */ /* -------------------------------------------------------------------------- */ #define PA_CLIP_( val, min, max )\ { val = ((val) < (min)) ? (min) : (((val) > (max)) ? (max) : (val)); } static const float const_1_div_128_ = 1.0f / 128.0f; /* 8 bit multiplier */ static const float const_1_div_32768_ = 1.0f / 32768.f; /* 16 bit multiplier */ static const double const_1_div_2147483648_ = 1.0 / 2147483648.0; /* 32 bit multiplier */ /* -------------------------------------------------------------------------- */ static void Float32_To_Int32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; PaInt32 *dest = (PaInt32*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { /* REVIEW */ #ifdef PA_USE_C99_LRINTF float scaled = *src * 0x7FFFFFFF; *dest = lrintf(scaled-0.5f); #else double scaled = *src * 0x7FFFFFFF; *dest = (PaInt32) scaled; #endif src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int32_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; PaInt32 *dest = (PaInt32*)destinationBuffer; while( count-- ) { /* REVIEW */ #ifdef PA_USE_C99_LRINTF float dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ float dithered = ((float)*src * (2147483646.0f)) + dither; *dest = lrintf(dithered - 0.5f); #else double dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ double dithered = ((double)*src * (2147483646.0)) + dither; *dest = (PaInt32) dithered; #endif src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int32_Clip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; PaInt32 *dest = (PaInt32*)destinationBuffer; (void) ditherGenerator; /* unused parameter */ while( count-- ) { /* REVIEW */ #ifdef PA_USE_C99_LRINTF float scaled = *src * 0x7FFFFFFF; PA_CLIP_( scaled, -2147483648.f, 2147483647.f ); *dest = lrintf(scaled-0.5f); #else double scaled = *src * 0x7FFFFFFF; PA_CLIP_( scaled, -2147483648., 2147483647. ); *dest = (PaInt32) scaled; #endif src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int32_DitherClip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; PaInt32 *dest = (PaInt32*)destinationBuffer; while( count-- ) { /* REVIEW */ #ifdef PA_USE_C99_LRINTF float dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ float dithered = ((float)*src * (2147483646.0f)) + dither; PA_CLIP_( dithered, -2147483648.f, 2147483647.f ); *dest = lrintf(dithered-0.5f); #else double dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ double dithered = ((double)*src * (2147483646.0)) + dither; PA_CLIP_( dithered, -2147483648., 2147483647. ); *dest = (PaInt32) dithered; #endif src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int24( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; PaInt32 temp; (void) ditherGenerator; /* unused parameter */ while( count-- ) { /* convert to 32 bit and drop the low 8 bits */ double scaled = *src * 0x7FFFFFFF; temp = (PaInt32) scaled; #if defined(PA_LITTLE_ENDIAN) dest[0] = (unsigned char)(temp >> 8); dest[1] = (unsigned char)(temp >> 16); dest[2] = (unsigned char)(temp >> 24); #elif defined(PA_BIG_ENDIAN) dest[0] = (unsigned char)(temp >> 24); dest[1] = (unsigned char)(temp >> 16); dest[2] = (unsigned char)(temp >> 8); #endif src += sourceStride; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int24_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; PaInt32 temp; while( count-- ) { /* convert to 32 bit and drop the low 8 bits */ double dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ double dithered = ((double)*src * (2147483646.0)) + dither; temp = (PaInt32) dithered; #if defined(PA_LITTLE_ENDIAN) dest[0] = (unsigned char)(temp >> 8); dest[1] = (unsigned char)(temp >> 16); dest[2] = (unsigned char)(temp >> 24); #elif defined(PA_BIG_ENDIAN) dest[0] = (unsigned char)(temp >> 24); dest[1] = (unsigned char)(temp >> 16); dest[2] = (unsigned char)(temp >> 8); #endif src += sourceStride; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int24_Clip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; PaInt32 temp; (void) ditherGenerator; /* unused parameter */ while( count-- ) { /* convert to 32 bit and drop the low 8 bits */ double scaled = *src * 0x7FFFFFFF; PA_CLIP_( scaled, -2147483648., 2147483647. ); temp = (PaInt32) scaled; #if defined(PA_LITTLE_ENDIAN) dest[0] = (unsigned char)(temp >> 8); dest[1] = (unsigned char)(temp >> 16); dest[2] = (unsigned char)(temp >> 24); #elif defined(PA_BIG_ENDIAN) dest[0] = (unsigned char)(temp >> 24); dest[1] = (unsigned char)(temp >> 16); dest[2] = (unsigned char)(temp >> 8); #endif src += sourceStride; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int24_DitherClip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; PaInt32 temp; while( count-- ) { /* convert to 32 bit and drop the low 8 bits */ double dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ double dithered = ((double)*src * (2147483646.0)) + dither; PA_CLIP_( dithered, -2147483648., 2147483647. ); temp = (PaInt32) dithered; #if defined(PA_LITTLE_ENDIAN) dest[0] = (unsigned char)(temp >> 8); dest[1] = (unsigned char)(temp >> 16); dest[2] = (unsigned char)(temp >> 24); #elif defined(PA_BIG_ENDIAN) dest[0] = (unsigned char)(temp >> 24); dest[1] = (unsigned char)(temp >> 16); dest[2] = (unsigned char)(temp >> 8); #endif src += sourceStride; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int16( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; PaInt16 *dest = (PaInt16*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { #ifdef PA_USE_C99_LRINTF float tempf = (*src * (32767.0f)) ; *dest = lrintf(tempf-0.5f); #else short samp = (short) (*src * (32767.0f)); *dest = samp; #endif src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int16_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; PaInt16 *dest = (PaInt16*)destinationBuffer; while( count-- ) { float dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ float dithered = (*src * (32766.0f)) + dither; #ifdef PA_USE_C99_LRINTF *dest = lrintf(dithered-0.5f); #else *dest = (PaInt16) dithered; #endif src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int16_Clip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; PaInt16 *dest = (PaInt16*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { #ifdef PA_USE_C99_LRINTF long samp = lrintf((*src * (32767.0f)) -0.5f); #else long samp = (PaInt32) (*src * (32767.0f)); #endif PA_CLIP_( samp, -0x8000, 0x7FFF ); *dest = (PaInt16) samp; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int16_DitherClip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; PaInt16 *dest = (PaInt16*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { float dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ float dithered = (*src * (32766.0f)) + dither; PaInt32 samp = (PaInt32) dithered; PA_CLIP_( samp, -0x8000, 0x7FFF ); #ifdef PA_USE_C99_LRINTF *dest = lrintf(samp-0.5f); #else *dest = (PaInt16) samp; #endif src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { signed char samp = (signed char) (*src * (127.0f)); *dest = samp; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int8_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { float dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ float dithered = (*src * (126.0f)) + dither; PaInt32 samp = (PaInt32) dithered; *dest = (signed char) samp; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int8_Clip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { PaInt32 samp = (PaInt32)(*src * (127.0f)); PA_CLIP_( samp, -0x80, 0x7F ); *dest = (signed char) samp; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_Int8_DitherClip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { float dither = PaUtil_GenerateFloatTriangularDither( ditherGenerator ); /* use smaller scaler to prevent overflow when we add the dither */ float dithered = (*src * (126.0f)) + dither; PaInt32 samp = (PaInt32) dithered; PA_CLIP_( samp, -0x80, 0x7F ); *dest = (signed char) samp; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_UInt8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { unsigned char samp = (unsigned char)(128 + ((unsigned char) (*src * (127.0f)))); *dest = samp; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_UInt8_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { /* IMPLEMENT ME */ src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_UInt8_Clip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { /* IMPLEMENT ME */ src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Float32_To_UInt8_DitherClip( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { float *src = (float*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { /* IMPLEMENT ME */ src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int32_To_Float32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt32 *src = (PaInt32*)sourceBuffer; float *dest = (float*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { *dest = (float) ((double)*src * const_1_div_2147483648_); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int32_To_Int24( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt32 *src = (PaInt32*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void) ditherGenerator; /* unused parameter */ while( count-- ) { /* REVIEW */ #if defined(PA_LITTLE_ENDIAN) dest[0] = (unsigned char)(*src >> 8); dest[1] = (unsigned char)(*src >> 16); dest[2] = (unsigned char)(*src >> 24); #elif defined(PA_BIG_ENDIAN) dest[0] = (unsigned char)(*src >> 24); dest[1] = (unsigned char)(*src >> 16); dest[2] = (unsigned char)(*src >> 8); #endif src += sourceStride; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void Int32_To_Int24_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { (void) destinationBuffer; /* unused parameters */ (void) destinationStride; /* unused parameters */ (void) sourceBuffer; /* unused parameters */ (void) sourceStride; /* unused parameters */ (void) count; /* unused parameters */ (void) ditherGenerator; /* unused parameters */ /* IMPLEMENT ME */ } /* -------------------------------------------------------------------------- */ static void Int32_To_Int16( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt32 *src = (PaInt32*)sourceBuffer; PaInt16 *dest = (PaInt16*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { *dest = (PaInt16) ((*src) >> 16); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int32_To_Int16_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt32 *src = (PaInt32*)sourceBuffer; PaInt16 *dest = (PaInt16*)destinationBuffer; PaInt32 dither; while( count-- ) { /* REVIEW */ dither = PaUtil_Generate16BitTriangularDither( ditherGenerator ); *dest = (PaInt16) ((((*src)>>1) + dither) >> 15); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int32_To_Int8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt32 *src = (PaInt32*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { *dest = (signed char) ((*src) >> 24); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int32_To_Int8_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt32 *src = (PaInt32*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; PaInt32 dither; while( count-- ) { /* REVIEW */ dither = PaUtil_Generate16BitTriangularDither( ditherGenerator ); *dest = (signed char) ((((*src)>>1) + dither) >> 23); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int32_To_UInt8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt32 *src = (PaInt32*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { (*dest) = (unsigned char)(((*src) >> 24) + 128); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int32_To_UInt8_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt32 *src = (PaInt32*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { /* IMPLEMENT ME */ src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int24_To_Float32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; float *dest = (float*)destinationBuffer; PaInt32 temp; (void) ditherGenerator; /* unused parameter */ while( count-- ) { #if defined(PA_LITTLE_ENDIAN) temp = (((long)src[0]) << 8); temp = temp | (((long)src[1]) << 16); temp = temp | (((long)src[2]) << 24); #elif defined(PA_BIG_ENDIAN) temp = (((long)src[0]) << 24); temp = temp | (((long)src[1]) << 16); temp = temp | (((long)src[2]) << 8); #endif *dest = (float) ((double)temp * const_1_div_2147483648_); src += sourceStride * 3; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int24_To_Int32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; PaInt32 *dest = (PaInt32*) destinationBuffer; PaInt32 temp; (void) ditherGenerator; /* unused parameter */ while( count-- ) { #if defined(PA_LITTLE_ENDIAN) temp = (((long)src[0]) << 8); temp = temp | (((long)src[1]) << 16); temp = temp | (((long)src[2]) << 24); #elif defined(PA_BIG_ENDIAN) temp = (((long)src[0]) << 24); temp = temp | (((long)src[1]) << 16); temp = temp | (((long)src[2]) << 8); #endif *dest = temp; src += sourceStride * 3; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int24_To_Int16( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; PaInt16 *dest = (PaInt16*)destinationBuffer; PaInt16 temp; (void) ditherGenerator; /* unused parameter */ while( count-- ) { #if defined(PA_LITTLE_ENDIAN) /* src[0] is discarded */ temp = (((PaInt16)src[1])); temp = temp | (PaInt16)(((PaInt16)src[2]) << 8); #elif defined(PA_BIG_ENDIAN) /* src[2] is discarded */ temp = (PaInt16)(((PaInt16)src[0]) << 8); temp = temp | (((PaInt16)src[1])); #endif *dest = temp; src += sourceStride * 3; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int24_To_Int16_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { (void) destinationBuffer; /* unused parameters */ (void) destinationStride; /* unused parameters */ (void) sourceBuffer; /* unused parameters */ (void) sourceStride; /* unused parameters */ (void) count; /* unused parameters */ (void) ditherGenerator; /* unused parameters */ /* IMPLEMENT ME */ } /* -------------------------------------------------------------------------- */ static void Int24_To_Int8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; (void) ditherGenerator; /* unused parameter */ while( count-- ) { #if defined(PA_LITTLE_ENDIAN) /* src[0] is discarded */ /* src[1] is discarded */ *dest = src[2]; #elif defined(PA_BIG_ENDIAN) /* src[2] is discarded */ /* src[1] is discarded */ *dest = src[0]; #endif src += sourceStride * 3; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int24_To_Int8_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { (void) destinationBuffer; /* unused parameters */ (void) destinationStride; /* unused parameters */ (void) sourceBuffer; /* unused parameters */ (void) sourceStride; /* unused parameters */ (void) count; /* unused parameters */ (void) ditherGenerator; /* unused parameters */ /* IMPLEMENT ME */ } /* -------------------------------------------------------------------------- */ static void Int24_To_UInt8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void) ditherGenerator; /* unused parameter */ while( count-- ) { #if defined(PA_LITTLE_ENDIAN) /* src[0] is discarded */ /* src[1] is discarded */ *dest = (unsigned char)(src[2] + 128); #elif defined(PA_BIG_ENDIAN) *dest = (unsigned char)(src[0] + 128); /* src[1] is discarded */ /* src[2] is discarded */ #endif src += sourceStride * 3; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int24_To_UInt8_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { (void) destinationBuffer; /* unused parameters */ (void) destinationStride; /* unused parameters */ (void) sourceBuffer; /* unused parameters */ (void) sourceStride; /* unused parameters */ (void) count; /* unused parameters */ (void) ditherGenerator; /* unused parameters */ /* IMPLEMENT ME */ } /* -------------------------------------------------------------------------- */ static void Int16_To_Float32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt16 *src = (PaInt16*)sourceBuffer; float *dest = (float*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { float samp = *src * const_1_div_32768_; /* FIXME: i'm concerned about this being asymetrical with float->int16 -rb */ *dest = samp; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int16_To_Int32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt16 *src = (PaInt16*)sourceBuffer; PaInt32 *dest = (PaInt32*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { /* REVIEW: we should consider something like (*src << 16) | (*src & 0xFFFF) */ *dest = *src << 16; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int16_To_Int24( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt16 *src = (PaInt16*) sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; PaInt16 temp; (void) ditherGenerator; /* unused parameter */ while( count-- ) { temp = *src; #if defined(PA_LITTLE_ENDIAN) dest[0] = 0; dest[1] = (unsigned char)(temp); dest[2] = (unsigned char)(temp >> 8); #elif defined(PA_BIG_ENDIAN) dest[0] = (unsigned char)(temp >> 8); dest[1] = (unsigned char)(temp); dest[2] = 0; #endif src += sourceStride; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void Int16_To_Int8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt16 *src = (PaInt16*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { (*dest) = (signed char)((*src) >> 8); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int16_To_Int8_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt16 *src = (PaInt16*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { /* IMPLEMENT ME */ src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int16_To_UInt8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt16 *src = (PaInt16*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { (*dest) = (unsigned char)(((*src) >> 8) + 128); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int16_To_UInt8_Dither( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaInt16 *src = (PaInt16*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { /* IMPLEMENT ME */ src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int8_To_Float32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { signed char *src = (signed char*)sourceBuffer; float *dest = (float*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { float samp = *src * const_1_div_128_; *dest = samp; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int8_To_Int32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { signed char *src = (signed char*)sourceBuffer; PaInt32 *dest = (PaInt32*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { (*dest) = (*src) << 24; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int8_To_Int24( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { signed char *src = (signed char*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { #if defined(PA_LITTLE_ENDIAN) dest[0] = 0; dest[1] = 0; dest[2] = (*src); #elif defined(PA_BIG_ENDIAN) dest[0] = (*src); dest[1] = 0; dest[2] = 0; #endif src += sourceStride; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void Int8_To_Int16( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { signed char *src = (signed char*)sourceBuffer; PaInt16 *dest = (PaInt16*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { (*dest) = (PaInt16)((*src) << 8); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Int8_To_UInt8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { signed char *src = (signed char*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { (*dest) = (unsigned char)(*src + 128); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void UInt8_To_Float32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; float *dest = (float*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { float samp = (*src - 128) * const_1_div_128_; *dest = samp; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void UInt8_To_Int32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; PaInt32 *dest = (PaInt32*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { (*dest) = (*src - 128) << 24; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void UInt8_To_Int24( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void) ditherGenerator; /* unused parameters */ while( count-- ) { #if defined(PA_LITTLE_ENDIAN) dest[0] = 0; dest[1] = 0; dest[2] = (unsigned char)(*src - 128); #elif defined(PA_BIG_ENDIAN) dest[0] = (unsigned char)(*src - 128); dest[1] = 0; dest[2] = 0; #endif src += sourceStride; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void UInt8_To_Int16( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; PaInt16 *dest = (PaInt16*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { (*dest) = (PaInt16)((*src - 128) << 8); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void UInt8_To_Int8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; signed char *dest = (signed char*)destinationBuffer; (void)ditherGenerator; /* unused parameter */ while( count-- ) { (*dest) = (signed char)(*src - 128); src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Copy_8_To_8( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void) ditherGenerator; /* unused parameter */ while( count-- ) { *dest = *src; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Copy_16_To_16( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaUint16 *src = (PaUint16 *)sourceBuffer; PaUint16 *dest = (PaUint16 *)destinationBuffer; (void) ditherGenerator; /* unused parameter */ while( count-- ) { *dest = *src; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Copy_24_To_24( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { unsigned char *src = (unsigned char*)sourceBuffer; unsigned char *dest = (unsigned char*)destinationBuffer; (void) ditherGenerator; /* unused parameter */ while( count-- ) { dest[0] = src[0]; dest[1] = src[1]; dest[2] = src[2]; src += sourceStride * 3; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void Copy_32_To_32( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ) { PaUint32 *dest = (PaUint32 *)destinationBuffer; PaUint32 *src = (PaUint32 *)sourceBuffer; (void) ditherGenerator; /* unused parameter */ while( count-- ) { *dest = *src; src += sourceStride; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ PaUtilConverterTable paConverters = { Float32_To_Int32, /* PaUtilConverter *Float32_To_Int32; */ Float32_To_Int32_Dither, /* PaUtilConverter *Float32_To_Int32_Dither; */ Float32_To_Int32_Clip, /* PaUtilConverter *Float32_To_Int32_Clip; */ Float32_To_Int32_DitherClip, /* PaUtilConverter *Float32_To_Int32_DitherClip; */ Float32_To_Int24, /* PaUtilConverter *Float32_To_Int24; */ Float32_To_Int24_Dither, /* PaUtilConverter *Float32_To_Int24_Dither; */ Float32_To_Int24_Clip, /* PaUtilConverter *Float32_To_Int24_Clip; */ Float32_To_Int24_DitherClip, /* PaUtilConverter *Float32_To_Int24_DitherClip; */ Float32_To_Int16, /* PaUtilConverter *Float32_To_Int16; */ Float32_To_Int16_Dither, /* PaUtilConverter *Float32_To_Int16_Dither; */ Float32_To_Int16_Clip, /* PaUtilConverter *Float32_To_Int16_Clip; */ Float32_To_Int16_DitherClip, /* PaUtilConverter *Float32_To_Int16_DitherClip; */ Float32_To_Int8, /* PaUtilConverter *Float32_To_Int8; */ Float32_To_Int8_Dither, /* PaUtilConverter *Float32_To_Int8_Dither; */ Float32_To_Int8_Clip, /* PaUtilConverter *Float32_To_Int8_Clip; */ Float32_To_Int8_DitherClip, /* PaUtilConverter *Float32_To_Int8_DitherClip; */ Float32_To_UInt8, /* PaUtilConverter *Float32_To_UInt8; */ Float32_To_UInt8_Dither, /* PaUtilConverter *Float32_To_UInt8_Dither; */ Float32_To_UInt8_Clip, /* PaUtilConverter *Float32_To_UInt8_Clip; */ Float32_To_UInt8_DitherClip, /* PaUtilConverter *Float32_To_UInt8_DitherClip; */ Int32_To_Float32, /* PaUtilConverter *Int32_To_Float32; */ Int32_To_Int24, /* PaUtilConverter *Int32_To_Int24; */ Int32_To_Int24_Dither, /* PaUtilConverter *Int32_To_Int24_Dither; */ Int32_To_Int16, /* PaUtilConverter *Int32_To_Int16; */ Int32_To_Int16_Dither, /* PaUtilConverter *Int32_To_Int16_Dither; */ Int32_To_Int8, /* PaUtilConverter *Int32_To_Int8; */ Int32_To_Int8_Dither, /* PaUtilConverter *Int32_To_Int8_Dither; */ Int32_To_UInt8, /* PaUtilConverter *Int32_To_UInt8; */ Int32_To_UInt8_Dither, /* PaUtilConverter *Int32_To_UInt8_Dither; */ Int24_To_Float32, /* PaUtilConverter *Int24_To_Float32; */ Int24_To_Int32, /* PaUtilConverter *Int24_To_Int32; */ Int24_To_Int16, /* PaUtilConverter *Int24_To_Int16; */ Int24_To_Int16_Dither, /* PaUtilConverter *Int24_To_Int16_Dither; */ Int24_To_Int8, /* PaUtilConverter *Int24_To_Int8; */ Int24_To_Int8_Dither, /* PaUtilConverter *Int24_To_Int8_Dither; */ Int24_To_UInt8, /* PaUtilConverter *Int24_To_UInt8; */ Int24_To_UInt8_Dither, /* PaUtilConverter *Int24_To_UInt8_Dither; */ Int16_To_Float32, /* PaUtilConverter *Int16_To_Float32; */ Int16_To_Int32, /* PaUtilConverter *Int16_To_Int32; */ Int16_To_Int24, /* PaUtilConverter *Int16_To_Int24; */ Int16_To_Int8, /* PaUtilConverter *Int16_To_Int8; */ Int16_To_Int8_Dither, /* PaUtilConverter *Int16_To_Int8_Dither; */ Int16_To_UInt8, /* PaUtilConverter *Int16_To_UInt8; */ Int16_To_UInt8_Dither, /* PaUtilConverter *Int16_To_UInt8_Dither; */ Int8_To_Float32, /* PaUtilConverter *Int8_To_Float32; */ Int8_To_Int32, /* PaUtilConverter *Int8_To_Int32; */ Int8_To_Int24, /* PaUtilConverter *Int8_To_Int24 */ Int8_To_Int16, /* PaUtilConverter *Int8_To_Int16; */ Int8_To_UInt8, /* PaUtilConverter *Int8_To_UInt8; */ UInt8_To_Float32, /* PaUtilConverter *UInt8_To_Float32; */ UInt8_To_Int32, /* PaUtilConverter *UInt8_To_Int32; */ UInt8_To_Int24, /* PaUtilConverter *UInt8_To_Int24; */ UInt8_To_Int16, /* PaUtilConverter *UInt8_To_Int16; */ UInt8_To_Int8, /* PaUtilConverter *UInt8_To_Int8; */ Copy_8_To_8, /* PaUtilConverter *Copy_8_To_8; */ Copy_16_To_16, /* PaUtilConverter *Copy_16_To_16; */ Copy_24_To_24, /* PaUtilConverter *Copy_24_To_24; */ Copy_32_To_32 /* PaUtilConverter *Copy_32_To_32; */ }; /* -------------------------------------------------------------------------- */ #endif /* PA_NO_STANDARD_CONVERTERS */ /* -------------------------------------------------------------------------- */ PaUtilZeroer* PaUtil_SelectZeroer( PaSampleFormat destinationFormat ) { switch( destinationFormat & ~paNonInterleaved ){ case paFloat32: return paZeroers.Zero32; case paInt32: return paZeroers.Zero32; case paInt24: return paZeroers.Zero24; case paInt16: return paZeroers.Zero16; case paInt8: return paZeroers.Zero8; case paUInt8: return paZeroers.ZeroU8; default: return 0; } } /* -------------------------------------------------------------------------- */ #ifdef PA_NO_STANDARD_ZEROERS /* -------------------------------------------------------------------------- */ PaUtilZeroerTable paZeroers = { 0, /* PaUtilZeroer *ZeroU8; */ 0, /* PaUtilZeroer *Zero8; */ 0, /* PaUtilZeroer *Zero16; */ 0, /* PaUtilZeroer *Zero24; */ 0, /* PaUtilZeroer *Zero32; */ }; /* -------------------------------------------------------------------------- */ #else /* PA_NO_STANDARD_ZEROERS is not defined */ /* -------------------------------------------------------------------------- */ static void ZeroU8( void *destinationBuffer, signed int destinationStride, unsigned int count ) { unsigned char *dest = (unsigned char*)destinationBuffer; while( count-- ) { *dest = 128; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Zero8( void *destinationBuffer, signed int destinationStride, unsigned int count ) { unsigned char *dest = (unsigned char*)destinationBuffer; while( count-- ) { *dest = 0; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Zero16( void *destinationBuffer, signed int destinationStride, unsigned int count ) { PaUint16 *dest = (PaUint16 *)destinationBuffer; while( count-- ) { *dest = 0; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ static void Zero24( void *destinationBuffer, signed int destinationStride, unsigned int count ) { unsigned char *dest = (unsigned char*)destinationBuffer; while( count-- ) { dest[0] = 0; dest[1] = 0; dest[2] = 0; dest += destinationStride * 3; } } /* -------------------------------------------------------------------------- */ static void Zero32( void *destinationBuffer, signed int destinationStride, unsigned int count ) { PaUint32 *dest = (PaUint32 *)destinationBuffer; while( count-- ) { *dest = 0; dest += destinationStride; } } /* -------------------------------------------------------------------------- */ PaUtilZeroerTable paZeroers = { ZeroU8, /* PaUtilZeroer *ZeroU8; */ Zero8, /* PaUtilZeroer *Zero8; */ Zero16, /* PaUtilZeroer *Zero16; */ Zero24, /* PaUtilZeroer *Zero24; */ Zero32, /* PaUtilZeroer *Zero32; */ }; /* -------------------------------------------------------------------------- */ #endif /* PA_NO_STANDARD_ZEROERS */ sources_5316/external/portaudio/pa_hostapi.h0000644000176700017670000002344110474003011020045 0ustar paulpaul#ifndef PA_HOSTAPI_H #define PA_HOSTAPI_H /* * $Id: pa_hostapi.h 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library * host api representation * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Interface used by pa_front to virtualize functions which operate on host APIs. */ #include "portaudio.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ /** **FOR THE USE OF pa_front.c ONLY** Do NOT use fields in this structure, they my change at any time. Use functions defined in pa_util.h if you think you need functionality which can be derived from here. */ typedef struct PaUtilPrivatePaFrontHostApiInfo { unsigned long baseDeviceIndex; }PaUtilPrivatePaFrontHostApiInfo; /** The common header for all data structures whose pointers are passed through the hostApiSpecificStreamInfo field of the PaStreamParameters structure. Note that in order to keep the public PortAudio interface clean, this structure is not used explicitly when declaring hostApiSpecificStreamInfo data structures. However, some code in pa_front depends on the first 3 members being equivalent with this structure. @see PaStreamParameters */ typedef struct PaUtilHostApiSpecificStreamInfoHeader { unsigned long size; /**< size of whole structure including this header */ PaHostApiTypeId hostApiType; /**< host API for which this data is intended */ unsigned long version; /**< structure version */ } PaUtilHostApiSpecificStreamInfoHeader; /** A structure representing the interface to a host API. Contains both concrete data and pointers to functions which implement the interface. */ typedef struct PaUtilHostApiRepresentation { PaUtilPrivatePaFrontHostApiInfo privatePaFrontInfo; /** The host api implementation should populate the info field. In the case of info.defaultInputDevice and info.defaultOutputDevice the values stored should be 0 based indices within the host api's own device index range (0 to deviceCount). These values will be converted to global device indices by pa_front after PaUtilHostApiInitializer() returns. */ PaHostApiInfo info; PaDeviceInfo** deviceInfos; /** (*Terminate)() is guaranteed to be called with a valid parameter, which was previously returned from the same implementation's initializer. */ void (*Terminate)( struct PaUtilHostApiRepresentation *hostApi ); /** The inputParameters and outputParameters pointers should not be saved as they will not remain valid after OpenStream is called. The following guarantees are made about parameters to (*OpenStream)(): [NOTE: the following list up to *END PA FRONT VALIDATIONS* should be kept in sync with the one for ValidateOpenStreamParameters and Pa_OpenStream in pa_front.c] PaHostApiRepresentation *hostApi - is valid for this implementation PaStream** stream - is non-null - at least one of inputParameters & outputParmeters is valid (not NULL) - if inputParameters & outputParmeters are both valid, that inputParameters->device & outputParmeters->device both use the same host api PaDeviceIndex inputParameters->device - is within range (0 to Pa_CountDevices-1) Or: - is paUseHostApiSpecificDeviceSpecification and inputParameters->hostApiSpecificStreamInfo is non-NULL and refers to a valid host api int inputParameters->numChannels - if inputParameters->device is not paUseHostApiSpecificDeviceSpecification, numInputChannels is > 0 - upper bound is NOT validated against device capabilities PaSampleFormat inputParameters->sampleFormat - is one of the sample formats defined in portaudio.h void *inputParameters->hostApiSpecificStreamInfo - if supplied its hostApi field matches the input device's host Api PaDeviceIndex outputParmeters->device - is within range (0 to Pa_CountDevices-1) int outputParmeters->numChannels - if inputDevice is valid, numInputChannels is > 0 - upper bound is NOT validated against device capabilities PaSampleFormat outputParmeters->sampleFormat - is one of the sample formats defined in portaudio.h void *outputParmeters->hostApiSpecificStreamInfo - if supplied its hostApi field matches the output device's host Api double sampleRate - is not an 'absurd' rate (less than 1000. or greater than 200000.) - sampleRate is NOT validated against device capabilities PaStreamFlags streamFlags - unused platform neutral flags are zero - paNeverDropInput is only used for full-duplex callback streams with variable buffer size (paFramesPerBufferUnspecified) [*END PA FRONT VALIDATIONS*] The following validations MUST be performed by (*OpenStream)(): - check that input device can support numInputChannels - check that input device can support inputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format - if inputStreamInfo is supplied, validate its contents, or return an error if no inputStreamInfo is expected - check that output device can support numOutputChannels - check that output device can support outputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format - if outputStreamInfo is supplied, validate its contents, or return an error if no outputStreamInfo is expected - if a full duplex stream is requested, check that the combination of input and output parameters is supported - check that the device supports sampleRate - alter sampleRate to a close allowable rate if necessary - validate inputLatency and outputLatency - validate any platform specific flags, if flags are supplied they must be valid. */ PaError (*OpenStream)( struct PaUtilHostApiRepresentation *hostApi, PaStream** stream, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerCallback, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ); PaError (*IsFormatSupported)( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); } PaUtilHostApiRepresentation; /** Prototype for the initialization function which must be implemented by every host API. @see paHostApiInitializers */ typedef PaError PaUtilHostApiInitializer( PaUtilHostApiRepresentation**, PaHostApiIndex ); /** paHostApiInitializers is a NULL-terminated array of host API initialization functions. These functions are called by pa_front to initialize the host APIs when the client calls Pa_Initialize(). There is a platform specific file which defines paHostApiInitializers for that platform, pa_win/pa_win_hostapis.c contains the Win32 definitions for example. */ extern PaUtilHostApiInitializer *paHostApiInitializers[]; /** The index of the default host API in the paHostApiInitializers array. There is a platform specific file which defines paDefaultHostApiIndex for that platform, see pa_win/pa_win_hostapis.c for example. */ extern int paDefaultHostApiIndex; #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_HOSTAPI_H */ sources_5316/external/portaudio/pa_mac_util.h0000644000176700017670000001726110541046520020205 0ustar paulpaul/* * $Id: pa_unix_util.h 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library * UNIX platform-specific support functions * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2000 Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup unix_src */ #ifndef PA_UNIX_UTIL_H #define PA_UNIX_UTIL_H #include "pa_cpuload.h" #include #include #include #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ #define PA_MIN(x,y) ( (x) < (y) ? (x) : (y) ) #define PA_MAX(x,y) ( (x) > (y) ? (x) : (y) ) /* Utilize GCC branch prediction for error tests */ #if defined __GNUC__ && __GNUC__ >= 3 #define UNLIKELY(expr) __builtin_expect( (expr), 0 ) #else #define UNLIKELY(expr) (expr) #endif #define STRINGIZE_HELPER(expr) #expr #define STRINGIZE(expr) STRINGIZE_HELPER(expr) #define PA_UNLESS(expr, code) \ do { \ if( UNLIKELY( (expr) == 0 ) ) \ { \ PaUtil_DebugPrint(( "Expression '" #expr "' failed in '" __FILE__ "', line: " STRINGIZE( __LINE__ ) "\n" )); \ result = (code); \ goto error; \ } \ } while (0); static PaError paUtilErr_; /* Used with PA_ENSURE */ /* Check PaError */ #define PA_ENSURE(expr) \ do { \ if( UNLIKELY( (paUtilErr_ = (expr)) < paNoError ) ) \ { \ PaUtil_DebugPrint(( "Expression '" #expr "' failed in '" __FILE__ "', line: " STRINGIZE( __LINE__ ) "\n" )); \ result = paUtilErr_; \ goto error; \ } \ } while (0); #define PA_ASSERT_CALL(expr, success) \ paUtilErr_ = (expr); \ assert( success == paUtilErr_ ); #define PA_ENSURE_SYSTEM(expr, success) \ do { \ if( UNLIKELY( (paUtilErr_ = (expr)) != success ) ) \ { \ /* PaUtil_SetLastHostErrorInfo should only be used in the main thread */ \ if( pthread_equal(pthread_self(), paUnixMainThread) ) \ { \ PaUtil_SetLastHostErrorInfo( paALSA, paUtilErr_, strerror( paUtilErr_ ) ); \ } \ PaUtil_DebugPrint( "Expression '" #expr "' failed in '" __FILE__ "', line: " STRINGIZE( __LINE__ ) "\n" ); \ result = paUnanticipatedHostError; \ goto error; \ } \ } while( 0 ); typedef struct { pthread_t callbackThread; } PaUtilThreading; PaError PaUtil_InitializeThreading( PaUtilThreading *threading ); void PaUtil_TerminateThreading( PaUtilThreading *threading ); PaError PaUtil_StartThreading( PaUtilThreading *threading, void *(*threadRoutine)(void *), void *data ); PaError PaUtil_CancelThreading( PaUtilThreading *threading, int wait, PaError *exitResult ); /* State accessed by utility functions */ /* void PaUnix_SetRealtimeScheduling( int rt ); void PaUtil_InitializeThreading( PaUtilThreading *th, PaUtilCpuLoadMeasurer *clm ); PaError PaUtil_CreateCallbackThread( PaUtilThreading *th, void *(*CallbackThreadFunc)( void * ), PaStream *s ); PaError PaUtil_KillCallbackThread( PaUtilThreading *th, PaError *exitResult ); void PaUtil_CallbackUpdate( PaUtilThreading *th ); */ extern pthread_t paUnixMainThread; typedef struct { pthread_mutex_t mtx; } PaUnixMutex; PaError PaUnixMutex_Initialize( PaUnixMutex* self ); PaError PaUnixMutex_Terminate( PaUnixMutex* self ); PaError PaUnixMutex_Lock( PaUnixMutex* self ); PaError PaUnixMutex_Unlock( PaUnixMutex* self ); typedef struct { pthread_t thread; int parentWaiting; int stopRequested; int locked; PaUnixMutex mtx; pthread_cond_t cond; volatile sig_atomic_t stopRequest; } PaUnixThread; /** Initialize global threading state. */ PaError PaUnixThreading_Initialize(); /** Perish, passing on eventual error code. * * A thin wrapper around pthread_exit, will automatically pass on any error code to the joining thread. * If the result indicates an error, i.e. it is not equal to paNoError, this function will automatically * allocate a pointer so the error is passed on with pthread_exit. If the result indicates that all is * well however, only a NULL pointer will be handed to pthread_exit. Thus, the joining thread should * check whether a non-NULL result pointer is obtained from pthread_join and make sure to free it. * @param result: The error code to pass on to the joining thread. */ #define PaUnixThreading_EXIT(result) \ do { \ PaError* pres = NULL; \ if( paNoError != (result) ) \ { \ pres = malloc( sizeof (PaError) ); \ *pres = (result); \ } \ pthread_exit( pres ); \ } while (0); /** Spawn a thread. * * Intended for spawning the callback thread from the main thread. This function can even block (for a certain * time or indefinitely) untill notified by the callback thread (using PaUnixThread_NotifyParent), which can be * useful in order to make sure that callback has commenced before returning from Pa_StartStream. * @param threadFunc: The function to be executed in the child thread. * @param waitForChild: If not 0, wait for child thread to call PaUnixThread_NotifyParent. Less than 0 means * wait for ever, greater than 0 wait for the specified time. * @return: If timed out waiting on child, paTimedOut. */ PaError PaUnixThread_New( PaUnixThread* self, void* (*threadFunc)( void* ), void* threadArg, PaTime waitForChild ); /** Terminate thread. * * @param wait: If true, request that background thread stop and wait untill it does, else cancel it. * @param exitResult: If non-null this will upon return contain the exit status of the thread. */ PaError PaUnixThread_Terminate( PaUnixThread* self, int wait, PaError* exitResult ); /** Prepare to notify waiting parent thread. * * An internal lock must be held before the parent is notified in PaUnixThread_NotifyParent, call this to * acquire it beforehand. * @return: If parent is not waiting, paInternalError. */ PaError PaUnixThread_PrepareNotify( PaUnixThread* self ); /** Notify waiting parent thread. * * @return: If parent timed out waiting, paTimedOut. If parent was never waiting, paInternalError. */ PaError PaUnixThread_NotifyParent( PaUnixThread* self ); /** Has the parent thread requested this thread to stop? */ int PaUnixThread_StopRequested( PaUnixThread* self ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif sources_5316/external/portaudio/pa_dither.c0000644000176700017670000001562710474003011017657 0ustar paulpaul/* * $Id: pa_dither.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library triangular dither generator * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Phil Burk, Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Functions for generating dither noise */ #include "pa_dither.h" #include "pa_types.h" #define PA_DITHER_BITS_ (15) void PaUtil_InitializeTriangularDitherState( PaUtilTriangularDitherGenerator *state ) { state->previous = 0; state->randSeed1 = 22222; state->randSeed2 = 5555555; } signed long PaUtil_Generate16BitTriangularDither( PaUtilTriangularDitherGenerator *state ) { signed long current, highPass; /* Generate two random numbers. */ state->randSeed1 = (state->randSeed1 * 196314165) + 907633515; state->randSeed2 = (state->randSeed2 * 196314165) + 907633515; /* Generate triangular distribution about 0. * Shift before adding to prevent overflow which would skew the distribution. * Also shift an extra bit for the high pass filter. */ #define DITHER_SHIFT_ ((SIZEOF_LONG*8 - PA_DITHER_BITS_) + 1) current = (((signed long)state->randSeed1)>>DITHER_SHIFT_) + (((signed long)state->randSeed2)>>DITHER_SHIFT_); /* High pass filter to reduce audibility. */ highPass = current - state->previous; state->previous = current; return highPass; } /* Multiply by PA_FLOAT_DITHER_SCALE_ to get a float between -2.0 and +1.99999 */ #define PA_FLOAT_DITHER_SCALE_ (1.0f / ((1<randSeed1 = (state->randSeed1 * 196314165) + 907633515; state->randSeed2 = (state->randSeed2 * 196314165) + 907633515; /* Generate triangular distribution about 0. * Shift before adding to prevent overflow which would skew the distribution. * Also shift an extra bit for the high pass filter. */ #define DITHER_SHIFT_ ((SIZEOF_LONG*8 - PA_DITHER_BITS_) + 1) current = (((signed long)state->randSeed1)>>DITHER_SHIFT_) + (((signed long)state->randSeed2)>>DITHER_SHIFT_); /* High pass filter to reduce audibility. */ highPass = current - state->previous; state->previous = current; return ((float)highPass) * const_float_dither_scale_; } /* The following alternate dither algorithms (from musicdsp.org) could be considered */ /*Noise shaped dither (March 2000) ------------------- This is a simple implementation of highpass triangular-PDF dither with 2nd-order noise shaping, for use when truncating floating point audio data to fixed point. The noise shaping lowers the noise floor by 11dB below 5kHz (@ 44100Hz sample rate) compared to triangular-PDF dither. The code below assumes input data is in the range +1 to -1 and doesn't check for overloads! To save time when generating dither for multiple channels you can do things like this: r3=(r1 & 0x7F)<<8; instead of calling rand() again. int r1, r2; //rectangular-PDF random numbers float s1, s2; //error feedback buffers float s = 0.5f; //set to 0.0f for no noise shaping float w = pow(2.0,bits-1); //word length (usually bits=16) float wi= 1.0f/w; float d = wi / RAND_MAX; //dither amplitude (2 lsb) float o = wi * 0.5f; //remove dc offset float in, tmp; int out; //for each sample... r2=r1; //can make HP-TRI dither by r1=rand(); //subtracting previous rand() in += s * (s1 + s1 - s2); //error feedback tmp = in + o + d * (float)(r1 - r2); //dc offset and dither out = (int)(w * tmp); //truncate downwards if(tmp<0.0f) out--; //this is faster than floor() s2 = s1; s1 = in - wi * (float)out; //error -- paul.kellett@maxim.abel.co.uk http://www.maxim.abel.co.uk */ /* 16-to-8-bit first-order dither Type : First order error feedforward dithering code References : Posted by Jon Watte Notes : This is about as simple a dithering algorithm as you can implement, but it's likely to sound better than just truncating to N bits. Note that you might not want to carry forward the full difference for infinity. It's probably likely that the worst performance hit comes from the saturation conditionals, which can be avoided with appropriate instructions on many DSPs and integer SIMD type instructions, or CMOV. Last, if sound quality is paramount (such as when going from > 16 bits to 16 bits) you probably want to use a higher-order dither function found elsewhere on this site. Code : // This code will down-convert and dither a 16-bit signed short // mono signal into an 8-bit unsigned char signal, using a first // order forward-feeding error term dither. #define uchar unsigned char void dither_one_channel_16_to_8( short * input, uchar * output, int count, int * memory ) { int m = *memory; while( count-- > 0 ) { int i = *input++; i += m; int j = i + 32768 - 128; uchar o; if( j < 0 ) { o = 0; } else if( j > 65535 ) { o = 255; } else { o = (uchar)((j>>8)&0xff); } m = ((j-32768+128)-i); *output++ = o; } *memory = m; } */ sources_5316/external/portaudio/pa_win_wmme.c0000644000176700017670000044160511630755256020245 0ustar paulpaul#ifdef _WIN32 /* * $Id: pa_win_wmme.c 1286 2007-09-26 21:34:23Z rossb $ * pa_win_wmme.c * Implementation of PortAudio for Windows MultiMedia Extensions (WMME) * * PortAudio Portable Real-Time Audio Library * Latest Version at: http://www.portaudio.com * * Authors: Ross Bencina and Phil Burk * Copyright (c) 1999-2000 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /* Modification History: PLB = Phil Burk JM = Julien Maillard RDB = Ross Bencina PLB20010402 - sDevicePtrs now allocates based on sizeof(pointer) PLB20010413 - check for excessive numbers of channels PLB20010422 - apply Mike Berry's changes for CodeWarrior on PC including conditional inclusion of memory.h, and explicit typecasting on memory allocation PLB20010802 - use GlobalAlloc for sDevicesPtr instead of PaHost_AllocFastMemory PLB20010816 - pass process instead of thread to SetPriorityClass() PLB20010927 - use number of frames instead of real-time for CPULoad calculation. JM20020118 - prevent hung thread when buffers underflow. PLB20020321 - detect Win XP versus NT, 9x; fix DBUG typo; removed init of CurrentCount RDB20020411 - various renaming cleanups, factored streamData alloc and cpu usage init RDB20020417 - stopped counting WAVE_MAPPER when there were no real devices refactoring, renaming and fixed a few edge case bugs RDB20020531 - converted to V19 framework ** NOTE maintanance history is now stored in CVS ** */ /** @file @ingroup hostaip_src @todo Fix buffer catch up code, can sometimes get stuck (perhaps fixed now, needs to be reviewed and tested.) @todo implement paInputUnderflow, paOutputOverflow streamCallback statusFlags, paNeverDropInput. @todo BUG: PA_MME_SET_LAST_WAVEIN/OUT_ERROR is used in functions which may be called asynchronously from the callback thread. this is bad. @todo implement inputBufferAdcTime in callback thread @todo review/fix error recovery and cleanup in marked functions @todo implement timeInfo for stream priming @todo handle the case where the callback returns paAbort or paComplete during stream priming. @todo review input overflow and output underflow handling in ReadStream and WriteStream Non-critical stuff for the future: @todo Investigate supporting host buffer formats > 16 bits @todo define UNICODE and _UNICODE in the project settings and see what breaks @todo refactor conversion of MMSYSTEM errors into PA arrors into a single function. @todo cleanup WAVEFORMATEXTENSIBLE retry in InitializeWaveHandles to not use a for loop */ /* How it works: For both callback and blocking read/write streams we open the MME devices in CALLBACK_EVENT mode. In this mode, MME signals an Event object whenever it has finished with a buffer (either filled it for input, or played it for output). Where necessary we block waiting for Event objects using WaitMultipleObjects(). When implementing a PA callback stream, we set up a high priority thread which waits on the MME buffer Events and drains/fills the buffers when they are ready. When implementing a PA blocking read/write stream, we simply wait on these Events (when necessary) inside the ReadStream() and WriteStream() functions. */ #undef UNICODE #include #include #include #include #include #ifndef UNDER_CE #include #endif #include /* PLB20010422 - "memory.h" doesn't work on CodeWarrior for PC. Thanks Mike Berry for the mod. */ #ifndef __MWERKS__XXX #include #include #endif /* __MWERKS__ */ #include "portaudio.h" #include "pa_trace.h" #include "pa_util.h" #include "pa_allocation.h" #include "pa_hostapi.h" #include "pa_stream.h" #include "pa_cpuload.h" #include "pa_process.h" #include "pa_debugprint.h" #include "pa_win_wmme.h" #include "pa_win_waveformat.h" #ifdef PAWIN_USE_WDMKS_DEVICE_INFO #include "pa_win_wdmks_utils.h" #ifndef DRV_QUERYDEVICEINTERFACE #define DRV_QUERYDEVICEINTERFACE (DRV_RESERVED + 12) #endif #ifndef DRV_QUERYDEVICEINTERFACESIZE #define DRV_QUERYDEVICEINTERFACESIZE (DRV_RESERVED + 13) #endif #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ #if (defined(UNDER_CE)) #pragma comment(lib, "Coredll.lib") #elif (defined(WIN32) && (defined(_MSC_VER) && (_MSC_VER >= 1200))) /* MSC version 6 and above */ #pragma comment(lib, "winmm.lib") #endif /* provided in newer platform sdks */ #ifndef DWORD_PTR #define DWORD_PTR DWORD #endif /************************************************* Constants ********/ #define PA_MME_USE_HIGH_DEFAULT_LATENCY_ (0) /* For debugging glitches. */ #if PA_MME_USE_HIGH_DEFAULT_LATENCY_ #define PA_MME_WIN_9X_DEFAULT_LATENCY_ (0.4) #define PA_MME_MIN_HOST_OUTPUT_BUFFER_COUNT_ (4) #define PA_MME_MIN_HOST_INPUT_BUFFER_COUNT_FULL_DUPLEX_ (4) #define PA_MME_MIN_HOST_INPUT_BUFFER_COUNT_HALF_DUPLEX_ (4) #define PA_MME_MIN_HOST_BUFFER_FRAMES_WHEN_UNSPECIFIED_ (16) #define PA_MME_MAX_HOST_BUFFER_SECS_ (0.3) /* Do not exceed unless user buffer exceeds */ #define PA_MME_MAX_HOST_BUFFER_BYTES_ (32 * 1024) /* Has precedence over PA_MME_MAX_HOST_BUFFER_SECS_, some drivers are known to crash with buffer sizes > 32k */ #else #define PA_MME_WIN_9X_DEFAULT_LATENCY_ (0.2) #define PA_MME_MIN_HOST_OUTPUT_BUFFER_COUNT_ (2) #define PA_MME_MIN_HOST_INPUT_BUFFER_COUNT_FULL_DUPLEX_ (3) #define PA_MME_MIN_HOST_INPUT_BUFFER_COUNT_HALF_DUPLEX_ (2) #define PA_MME_MIN_HOST_BUFFER_FRAMES_WHEN_UNSPECIFIED_ (16) #define PA_MME_MAX_HOST_BUFFER_SECS_ (0.1) /* Do not exceed unless user buffer exceeds */ #define PA_MME_MAX_HOST_BUFFER_BYTES_ (32 * 1024) /* Has precedence over PA_MME_MAX_HOST_BUFFER_SECS_, some drivers are known to crash with buffer sizes > 32k */ #endif /* Use higher latency for NT because it is even worse at real-time operation than Win9x. */ #define PA_MME_WIN_NT_DEFAULT_LATENCY_ (PA_MME_WIN_9X_DEFAULT_LATENCY_ * 2) #define PA_MME_WIN_WDM_DEFAULT_LATENCY_ (PA_MME_WIN_9X_DEFAULT_LATENCY_) #define PA_MME_MIN_TIMEOUT_MSEC_ (1000) static const char constInputMapperSuffix_[] = " - Input"; static const char constOutputMapperSuffix_[] = " - Output"; /********************************************************************/ typedef struct PaWinMmeStream PaWinMmeStream; /* forward declaration */ /* prototypes for functions declared in this file */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ PaError PaWinMme_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); #ifdef __cplusplus } #endif /* __cplusplus */ static void Terminate( struct PaUtilHostApiRepresentation *hostApi ); static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** stream, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ); static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); static PaError CloseStream( PaStream* stream ); static PaError StartStream( PaStream *stream ); static PaError StopStream( PaStream *stream ); static PaError AbortStream( PaStream *stream ); static PaError IsStreamStopped( PaStream *s ); static PaError IsStreamActive( PaStream *stream ); static PaTime GetStreamTime( PaStream *stream ); static double GetStreamCpuLoad( PaStream* stream ); static PaError ReadStream( PaStream* stream, void *buffer, unsigned long frames ); static PaError WriteStream( PaStream* stream, const void *buffer, unsigned long frames ); static signed long GetStreamReadAvailable( PaStream* stream ); static signed long GetStreamWriteAvailable( PaStream* stream ); /* macros for setting last host error information */ #ifdef UNICODE #define PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ) \ { \ wchar_t mmeErrorTextWide[ MAXERRORLENGTH ]; \ char mmeErrorText[ MAXERRORLENGTH ]; \ waveInGetErrorText( mmresult, mmeErrorTextWide, MAXERRORLENGTH ); \ WideCharToMultiByte( CP_ACP, WC_COMPOSITECHECK | WC_DEFAULTCHAR,\ mmeErrorTextWide, -1, mmeErrorText, MAXERRORLENGTH, NULL, NULL ); \ PaUtil_SetLastHostErrorInfo( paMME, mmresult, mmeErrorText ); \ } #define PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ) \ { \ wchar_t mmeErrorTextWide[ MAXERRORLENGTH ]; \ char mmeErrorText[ MAXERRORLENGTH ]; \ waveOutGetErrorText( mmresult, mmeErrorTextWide, MAXERRORLENGTH ); \ WideCharToMultiByte( CP_ACP, WC_COMPOSITECHECK | WC_DEFAULTCHAR,\ mmeErrorTextWide, -1, mmeErrorText, MAXERRORLENGTH, NULL, NULL ); \ PaUtil_SetLastHostErrorInfo( paMME, mmresult, mmeErrorText ); \ } #else /* !UNICODE */ #define PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ) \ { \ char mmeErrorText[ MAXERRORLENGTH ]; \ waveInGetErrorText( mmresult, mmeErrorText, MAXERRORLENGTH ); \ PaUtil_SetLastHostErrorInfo( paMME, mmresult, mmeErrorText ); \ } #define PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ) \ { \ char mmeErrorText[ MAXERRORLENGTH ]; \ waveOutGetErrorText( mmresult, mmeErrorText, MAXERRORLENGTH ); \ PaUtil_SetLastHostErrorInfo( paMME, mmresult, mmeErrorText ); \ } #endif /* UNICODE */ static void PaMme_SetLastSystemError( DWORD errorCode ) { char *lpMsgBuf; FormatMessage( FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM, NULL, errorCode, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR) &lpMsgBuf, 0, NULL ); PaUtil_SetLastHostErrorInfo( paMME, errorCode, lpMsgBuf ); LocalFree( lpMsgBuf ); } #define PA_MME_SET_LAST_SYSTEM_ERROR( errorCode ) \ PaMme_SetLastSystemError( errorCode ) /* PaError returning wrappers for some commonly used win32 functions note that we allow passing a null ptr to have no effect. */ static PaError CreateEventWithPaError( HANDLE *handle, LPSECURITY_ATTRIBUTES lpEventAttributes, BOOL bManualReset, BOOL bInitialState, LPCTSTR lpName ) { PaError result = paNoError; *handle = NULL; *handle = CreateEvent( lpEventAttributes, bManualReset, bInitialState, lpName ); if( *handle == NULL ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_SYSTEM_ERROR( GetLastError() ); } return result; } static PaError ResetEventWithPaError( HANDLE handle ) { PaError result = paNoError; if( handle ) { if( ResetEvent( handle ) == 0 ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_SYSTEM_ERROR( GetLastError() ); } } return result; } static PaError CloseHandleWithPaError( HANDLE handle ) { PaError result = paNoError; if( handle ) { if( CloseHandle( handle ) == 0 ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_SYSTEM_ERROR( GetLastError() ); } } return result; } /* PaWinMmeHostApiRepresentation - host api datastructure specific to this implementation */ typedef struct { PaUtilHostApiRepresentation inheritedHostApiRep; PaUtilStreamInterface callbackStreamInterface; PaUtilStreamInterface blockingStreamInterface; PaUtilAllocationGroup *allocations; int inputDeviceCount, outputDeviceCount; /** winMmeDeviceIds is an array of WinMme device ids. fields in the range [0, inputDeviceCount) are input device ids, and [inputDeviceCount, inputDeviceCount + outputDeviceCount) are output device ids. */ UINT *winMmeDeviceIds; } PaWinMmeHostApiRepresentation; typedef struct { PaDeviceInfo inheritedDeviceInfo; DWORD dwFormats; /**<< standard formats bitmask from the WAVEINCAPS and WAVEOUTCAPS structures */ char deviceInputChannelCountIsKnown; /**<< if the system returns 0xFFFF then we don't really know the number of supported channels (1=>known, 0=>unknown)*/ char deviceOutputChannelCountIsKnown; /**<< if the system returns 0xFFFF then we don't really know the number of supported channels (1=>known, 0=>unknown)*/ } PaWinMmeDeviceInfo; /************************************************************************* * Returns recommended device ID. * On the PC, the recommended device can be specified by the user by * setting an environment variable. For example, to use device #1. * * set PA_RECOMMENDED_OUTPUT_DEVICE=1 * * The user should first determine the available device ID by using * the supplied application "pa_devs". */ #define PA_ENV_BUF_SIZE_ (32) #define PA_REC_IN_DEV_ENV_NAME_ ("PA_RECOMMENDED_INPUT_DEVICE") #define PA_REC_OUT_DEV_ENV_NAME_ ("PA_RECOMMENDED_OUTPUT_DEVICE") static PaDeviceIndex GetEnvDefaultDeviceID( char *envName ) { PaDeviceIndex recommendedIndex = paNoDevice; DWORD hresult; char envbuf[PA_ENV_BUF_SIZE_]; #ifndef WIN32_PLATFORM_PSPC /* no GetEnvironmentVariable on PocketPC */ /* Let user determine default device by setting environment variable. */ hresult = GetEnvironmentVariableA( envName, envbuf, PA_ENV_BUF_SIZE_ ); if( (hresult > 0) && (hresult < PA_ENV_BUF_SIZE_) ) { recommendedIndex = atoi( envbuf ); } #endif return recommendedIndex; } static void InitializeDefaultDeviceIdsFromEnv( PaWinMmeHostApiRepresentation *hostApi ) { PaDeviceIndex device; /* input */ device = GetEnvDefaultDeviceID( PA_REC_IN_DEV_ENV_NAME_ ); if( device != paNoDevice && ( device >= 0 && device < hostApi->inheritedHostApiRep.info.deviceCount ) && hostApi->inheritedHostApiRep.deviceInfos[ device ]->maxInputChannels > 0 ) { hostApi->inheritedHostApiRep.info.defaultInputDevice = device; } /* output */ device = GetEnvDefaultDeviceID( PA_REC_OUT_DEV_ENV_NAME_ ); if( device != paNoDevice && ( device >= 0 && device < hostApi->inheritedHostApiRep.info.deviceCount ) && hostApi->inheritedHostApiRep.deviceInfos[ device ]->maxOutputChannels > 0 ) { hostApi->inheritedHostApiRep.info.defaultOutputDevice = device; } } /** Convert external PA ID to a windows multimedia device ID */ static UINT LocalDeviceIndexToWinMmeDeviceId( PaWinMmeHostApiRepresentation *hostApi, PaDeviceIndex device ) { assert( device >= 0 && device < hostApi->inputDeviceCount + hostApi->outputDeviceCount ); return hostApi->winMmeDeviceIds[ device ]; } static PaError QueryInputWaveFormatEx( int deviceId, WAVEFORMATEX *waveFormatEx ) { MMRESULT mmresult; switch( mmresult = waveInOpen( NULL, deviceId, waveFormatEx, 0, 0, WAVE_FORMAT_QUERY ) ) { case MMSYSERR_NOERROR: return paNoError; case MMSYSERR_ALLOCATED: /* Specified resource is already allocated. */ return paDeviceUnavailable; case MMSYSERR_NODRIVER: /* No device driver is present. */ return paDeviceUnavailable; case MMSYSERR_NOMEM: /* Unable to allocate or lock memory. */ return paInsufficientMemory; case WAVERR_BADFORMAT: /* Attempted to open with an unsupported waveform-audio format. */ return paSampleFormatNotSupported; case MMSYSERR_BADDEVICEID: /* Specified device identifier is out of range. */ /* falls through */ default: PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); return paUnanticipatedHostError; } } static PaError QueryOutputWaveFormatEx( int deviceId, WAVEFORMATEX *waveFormatEx ) { MMRESULT mmresult; switch( mmresult = waveOutOpen( NULL, deviceId, waveFormatEx, 0, 0, WAVE_FORMAT_QUERY ) ) { case MMSYSERR_NOERROR: return paNoError; case MMSYSERR_ALLOCATED: /* Specified resource is already allocated. */ return paDeviceUnavailable; case MMSYSERR_NODRIVER: /* No device driver is present. */ return paDeviceUnavailable; case MMSYSERR_NOMEM: /* Unable to allocate or lock memory. */ return paInsufficientMemory; case WAVERR_BADFORMAT: /* Attempted to open with an unsupported waveform-audio format. */ return paSampleFormatNotSupported; case MMSYSERR_BADDEVICEID: /* Specified device identifier is out of range. */ /* falls through */ default: PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ); return paUnanticipatedHostError; } } static PaError QueryFormatSupported( PaDeviceInfo *deviceInfo, PaError (*waveFormatExQueryFunction)(int, WAVEFORMATEX*), int winMmeDeviceId, int channels, double sampleRate ) { PaWinMmeDeviceInfo *winMmeDeviceInfo = (PaWinMmeDeviceInfo*)deviceInfo; PaWinWaveFormat waveFormat; if( sampleRate == 11025.0 && ( (channels == 1 && (winMmeDeviceInfo->dwFormats & WAVE_FORMAT_1M16)) || (channels == 2 && (winMmeDeviceInfo->dwFormats & WAVE_FORMAT_1S16)) ) ){ return paNoError; } if( sampleRate == 22050.0 && ( (channels == 1 && (winMmeDeviceInfo->dwFormats & WAVE_FORMAT_2M16)) || (channels == 2 && (winMmeDeviceInfo->dwFormats & WAVE_FORMAT_2S16)) ) ){ return paNoError; } if( sampleRate == 44100.0 && ( (channels == 1 && (winMmeDeviceInfo->dwFormats & WAVE_FORMAT_4M16)) || (channels == 2 && (winMmeDeviceInfo->dwFormats & WAVE_FORMAT_4S16)) ) ){ return paNoError; } /* first, attempt to query the device using WAVEFORMATEXTENSIBLE, if this fails we fall back to WAVEFORMATEX */ /* @todo at the moment we only query with 16 bit sample format and directout speaker config*/ PaWin_InitializeWaveFormatExtensible( &waveFormat, channels, paInt16, sampleRate, PAWIN_SPEAKER_DIRECTOUT ); if( waveFormatExQueryFunction( winMmeDeviceId, (WAVEFORMATEX*)&waveFormat ) == paNoError ) return paNoError; PaWin_InitializeWaveFormatEx( &waveFormat, channels, paInt16, sampleRate ); return waveFormatExQueryFunction( winMmeDeviceId, (WAVEFORMATEX*)&waveFormat ); } #define PA_DEFAULTSAMPLERATESEARCHORDER_COUNT_ (13) /* must match array length below */ static double defaultSampleRateSearchOrder_[] = { 44100.0, 48000.0, 32000.0, 24000.0, 22050.0, 88200.0, 96000.0, 192000.0, 16000.0, 12000.0, 11025.0, 9600.0, 8000.0 }; static void DetectDefaultSampleRate( PaWinMmeDeviceInfo *winMmeDeviceInfo, int winMmeDeviceId, PaError (*waveFormatExQueryFunction)(int, WAVEFORMATEX*), int maxChannels ) { PaDeviceInfo *deviceInfo = &winMmeDeviceInfo->inheritedDeviceInfo; int i; deviceInfo->defaultSampleRate = 0.; for( i=0; i < PA_DEFAULTSAMPLERATESEARCHORDER_COUNT_; ++i ) { double sampleRate = defaultSampleRateSearchOrder_[ i ]; PaError paerror = QueryFormatSupported( deviceInfo, waveFormatExQueryFunction, winMmeDeviceId, maxChannels, sampleRate ); if( paerror == paNoError ) { deviceInfo->defaultSampleRate = sampleRate; break; } } } #ifdef PAWIN_USE_WDMKS_DEVICE_INFO static int QueryWaveInKSFilterMaxChannels( int waveInDeviceId, int *maxChannels ) { void *devicePath; DWORD devicePathSize; int result = 0; if( waveInMessage((HWAVEIN)waveInDeviceId, DRV_QUERYDEVICEINTERFACESIZE, (DWORD_PTR)&devicePathSize, 0 ) != MMSYSERR_NOERROR ) return 0; devicePath = PaUtil_AllocateMemory( devicePathSize ); if( !devicePath ) return 0; /* apparently DRV_QUERYDEVICEINTERFACE returns a unicode interface path, although this is undocumented */ if( waveInMessage((HWAVEIN)waveInDeviceId, DRV_QUERYDEVICEINTERFACE, (DWORD_PTR)devicePath, devicePathSize ) == MMSYSERR_NOERROR ) { int count = PaWin_WDMKS_QueryFilterMaximumChannelCount( devicePath, /* isInput= */ 1 ); if( count > 0 ) { *maxChannels = count; result = 1; } } PaUtil_FreeMemory( devicePath ); return result; } #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ static PaError InitializeInputDeviceInfo( PaWinMmeHostApiRepresentation *winMmeHostApi, PaWinMmeDeviceInfo *winMmeDeviceInfo, UINT winMmeInputDeviceId, int *success ) { PaError result = paNoError; char *deviceName; /* non-const ptr */ MMRESULT mmresult; WAVEINCAPSA wic; PaDeviceInfo *deviceInfo = &winMmeDeviceInfo->inheritedDeviceInfo; *success = 0; mmresult = waveInGetDevCapsA( winMmeInputDeviceId, &wic, sizeof( WAVEINCAPSA ) ); if( mmresult == MMSYSERR_NOMEM ) { result = paInsufficientMemory; goto error; } else if( mmresult != MMSYSERR_NOERROR ) { /* instead of returning paUnanticipatedHostError we return paNoError, but leave success set as 0. This allows Pa_Initialize to just ignore this device, without failing the entire initialisation process. */ return paNoError; } if( winMmeInputDeviceId == WAVE_MAPPER ) { /* Append I/O suffix to WAVE_MAPPER device. */ deviceName = (char *)PaUtil_GroupAllocateMemory( winMmeHostApi->allocations, strlen( wic.szPname ) + 1 + sizeof(constInputMapperSuffix_) ); if( !deviceName ) { result = paInsufficientMemory; goto error; } strcpy( deviceName, wic.szPname ); strcat( deviceName, constInputMapperSuffix_ ); } else { deviceName = (char*)PaUtil_GroupAllocateMemory( winMmeHostApi->allocations, strlen( wic.szPname ) + 1 ); if( !deviceName ) { result = paInsufficientMemory; goto error; } strcpy( deviceName, wic.szPname ); } deviceInfo->name = deviceName; if( wic.wChannels == 0xFFFF || wic.wChannels < 1 || wic.wChannels > 255 ){ /* For Windows versions using WDM (possibly Windows 98 ME and later) * the kernel mixer sits between the application and the driver. As a result, * wave*GetDevCaps often kernel mixer channel counts, which are unlimited. * When this happens we assume the device is stereo and set a flag * so that other channel counts can be tried with OpenStream -- i.e. when * device*ChannelCountIsKnown is false, OpenStream will try whatever * channel count you supply. * see also InitializeOutputDeviceInfo() below. */ PA_DEBUG(("Pa_GetDeviceInfo: Num input channels reported as %d! Changed to 2.\n", wic.wChannels )); deviceInfo->maxInputChannels = 2; winMmeDeviceInfo->deviceInputChannelCountIsKnown = 0; }else{ deviceInfo->maxInputChannels = wic.wChannels; winMmeDeviceInfo->deviceInputChannelCountIsKnown = 1; } #ifdef PAWIN_USE_WDMKS_DEVICE_INFO winMmeDeviceInfo->deviceInputChannelCountIsKnown = QueryWaveInKSFilterMaxChannels( winMmeInputDeviceId, &deviceInfo->maxInputChannels ); #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ winMmeDeviceInfo->dwFormats = wic.dwFormats; DetectDefaultSampleRate( winMmeDeviceInfo, winMmeInputDeviceId, QueryInputWaveFormatEx, deviceInfo->maxInputChannels ); *success = 1; error: return result; } #ifdef PAWIN_USE_WDMKS_DEVICE_INFO static int QueryWaveOutKSFilterMaxChannels( int waveOutDeviceId, int *maxChannels ) { void *devicePath; DWORD devicePathSize; int result = 0; if( waveOutMessage((HWAVEOUT)waveOutDeviceId, DRV_QUERYDEVICEINTERFACESIZE, (DWORD_PTR)&devicePathSize, 0 ) != MMSYSERR_NOERROR ) return 0; devicePath = PaUtil_AllocateMemory( devicePathSize ); if( !devicePath ) return 0; /* apparently DRV_QUERYDEVICEINTERFACE returns a unicode interface path, although this is undocumented */ if( waveOutMessage((HWAVEOUT)waveOutDeviceId, DRV_QUERYDEVICEINTERFACE, (DWORD_PTR)devicePath, devicePathSize ) == MMSYSERR_NOERROR ) { int count = PaWin_WDMKS_QueryFilterMaximumChannelCount( devicePath, /* isInput= */ 0 ); if( count > 0 ) { *maxChannels = count; result = 1; } } PaUtil_FreeMemory( devicePath ); return result; } #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ static PaError InitializeOutputDeviceInfo( PaWinMmeHostApiRepresentation *winMmeHostApi, PaWinMmeDeviceInfo *winMmeDeviceInfo, UINT winMmeOutputDeviceId, int *success ) { PaError result = paNoError; char *deviceName; /* non-const ptr */ MMRESULT mmresult; WAVEOUTCAPSA woc; PaDeviceInfo *deviceInfo = &winMmeDeviceInfo->inheritedDeviceInfo; *success = 0; mmresult = waveOutGetDevCapsA( winMmeOutputDeviceId, &woc, sizeof( WAVEOUTCAPSA ) ); if( mmresult == MMSYSERR_NOMEM ) { result = paInsufficientMemory; goto error; } else if( mmresult != MMSYSERR_NOERROR ) { /* instead of returning paUnanticipatedHostError we return paNoError, but leave success set as 0. This allows Pa_Initialize to just ignore this device, without failing the entire initialisation process. */ return paNoError; } if( winMmeOutputDeviceId == WAVE_MAPPER ) { /* Append I/O suffix to WAVE_MAPPER device. */ deviceName = (char *)PaUtil_GroupAllocateMemory( winMmeHostApi->allocations, strlen( woc.szPname ) + 1 + sizeof(constOutputMapperSuffix_) ); if( !deviceName ) { result = paInsufficientMemory; goto error; } strcpy( deviceName, woc.szPname ); strcat( deviceName, constOutputMapperSuffix_ ); } else { deviceName = (char*)PaUtil_GroupAllocateMemory( winMmeHostApi->allocations, strlen( woc.szPname ) + 1 ); if( !deviceName ) { result = paInsufficientMemory; goto error; } strcpy( deviceName, woc.szPname ); } deviceInfo->name = deviceName; if( woc.wChannels == 0xFFFF || woc.wChannels < 1 || woc.wChannels > 255 ){ /* For Windows versions using WDM (possibly Windows 98 ME and later) * the kernel mixer sits between the application and the driver. As a result, * wave*GetDevCaps often kernel mixer channel counts, which are unlimited. * When this happens we assume the device is stereo and set a flag * so that other channel counts can be tried with OpenStream -- i.e. when * device*ChannelCountIsKnown is false, OpenStream will try whatever * channel count you supply. * see also InitializeInputDeviceInfo() above. */ PA_DEBUG(("Pa_GetDeviceInfo: Num output channels reported as %d! Changed to 2.\n", woc.wChannels )); deviceInfo->maxOutputChannels = 2; winMmeDeviceInfo->deviceOutputChannelCountIsKnown = 0; }else{ deviceInfo->maxOutputChannels = woc.wChannels; winMmeDeviceInfo->deviceOutputChannelCountIsKnown = 1; } #ifdef PAWIN_USE_WDMKS_DEVICE_INFO winMmeDeviceInfo->deviceOutputChannelCountIsKnown = QueryWaveOutKSFilterMaxChannels( winMmeOutputDeviceId, &deviceInfo->maxOutputChannels ); #endif /* PAWIN_USE_WDMKS_DEVICE_INFO */ winMmeDeviceInfo->dwFormats = woc.dwFormats; DetectDefaultSampleRate( winMmeDeviceInfo, winMmeOutputDeviceId, QueryOutputWaveFormatEx, deviceInfo->maxOutputChannels ); *success = 1; error: return result; } static void GetDefaultLatencies( PaTime *defaultLowLatency, PaTime *defaultHighLatency ) { OSVERSIONINFO osvi; osvi.dwOSVersionInfoSize = sizeof( osvi ); GetVersionEx( &osvi ); /* Check for NT */ if( (osvi.dwMajorVersion == 4) && (osvi.dwPlatformId == 2) ) { *defaultLowLatency = PA_MME_WIN_NT_DEFAULT_LATENCY_; } else if(osvi.dwMajorVersion >= 5) { *defaultLowLatency = PA_MME_WIN_WDM_DEFAULT_LATENCY_; } else { *defaultLowLatency = PA_MME_WIN_9X_DEFAULT_LATENCY_; } *defaultHighLatency = *defaultLowLatency * 2; } PaError PaWinMme_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex hostApiIndex ) { PaError result = paNoError; int i; PaWinMmeHostApiRepresentation *winMmeHostApi; int inputDeviceCount, outputDeviceCount, maximumPossibleDeviceCount; PaWinMmeDeviceInfo *deviceInfoArray; int deviceInfoInitializationSucceeded; PaTime defaultLowLatency, defaultHighLatency; DWORD waveInPreferredDevice, waveOutPreferredDevice; DWORD preferredDeviceStatusFlags; winMmeHostApi = (PaWinMmeHostApiRepresentation*)PaUtil_AllocateMemory( sizeof(PaWinMmeHostApiRepresentation) ); if( !winMmeHostApi ) { result = paInsufficientMemory; goto error; } winMmeHostApi->allocations = PaUtil_CreateAllocationGroup(); if( !winMmeHostApi->allocations ) { result = paInsufficientMemory; goto error; } *hostApi = &winMmeHostApi->inheritedHostApiRep; (*hostApi)->info.structVersion = 1; (*hostApi)->info.type = paMME; (*hostApi)->info.name = "MME"; /* initialise device counts and default devices under the assumption that there are no devices. These values are incremented below if and when devices are successfully initialized. */ (*hostApi)->info.deviceCount = 0; (*hostApi)->info.defaultInputDevice = paNoDevice; (*hostApi)->info.defaultOutputDevice = paNoDevice; winMmeHostApi->inputDeviceCount = 0; winMmeHostApi->outputDeviceCount = 0; #if !defined(DRVM_MAPPER_PREFERRED_GET) /* DRVM_MAPPER_PREFERRED_GET is defined in mmddk.h but we avoid a dependency on the DDK by defining it here */ #define DRVM_MAPPER_PREFERRED_GET (0x2000+21) #endif /* the following calls assume that if wave*Message fails the preferred device parameter won't be modified */ preferredDeviceStatusFlags = 0; waveInPreferredDevice = -1; waveInMessage( (HWAVEIN)WAVE_MAPPER, DRVM_MAPPER_PREFERRED_GET, (DWORD)&waveInPreferredDevice, (DWORD)&preferredDeviceStatusFlags ); preferredDeviceStatusFlags = 0; waveOutPreferredDevice = -1; waveOutMessage( (HWAVEOUT)WAVE_MAPPER, DRVM_MAPPER_PREFERRED_GET, (DWORD)&waveOutPreferredDevice, (DWORD)&preferredDeviceStatusFlags ); maximumPossibleDeviceCount = 0; inputDeviceCount = waveInGetNumDevs(); if( inputDeviceCount > 0 ) maximumPossibleDeviceCount += inputDeviceCount + 1; /* assume there is a WAVE_MAPPER */ outputDeviceCount = waveOutGetNumDevs(); if( outputDeviceCount > 0 ) maximumPossibleDeviceCount += outputDeviceCount + 1; /* assume there is a WAVE_MAPPER */ if( maximumPossibleDeviceCount > 0 ){ (*hostApi)->deviceInfos = (PaDeviceInfo**)PaUtil_GroupAllocateMemory( winMmeHostApi->allocations, sizeof(PaDeviceInfo*) * maximumPossibleDeviceCount ); if( !(*hostApi)->deviceInfos ) { result = paInsufficientMemory; goto error; } /* allocate all device info structs in a contiguous block */ deviceInfoArray = (PaWinMmeDeviceInfo*)PaUtil_GroupAllocateMemory( winMmeHostApi->allocations, sizeof(PaWinMmeDeviceInfo) * maximumPossibleDeviceCount ); if( !deviceInfoArray ) { result = paInsufficientMemory; goto error; } winMmeHostApi->winMmeDeviceIds = (UINT*)PaUtil_GroupAllocateMemory( winMmeHostApi->allocations, sizeof(int) * maximumPossibleDeviceCount ); if( !winMmeHostApi->winMmeDeviceIds ) { result = paInsufficientMemory; goto error; } GetDefaultLatencies( &defaultLowLatency, &defaultHighLatency ); if( inputDeviceCount > 0 ){ /* -1 is the WAVE_MAPPER */ for( i = -1; i < inputDeviceCount; ++i ){ UINT winMmeDeviceId = (UINT)((i==-1) ? WAVE_MAPPER : i); PaWinMmeDeviceInfo *wmmeDeviceInfo = &deviceInfoArray[ (*hostApi)->info.deviceCount ]; PaDeviceInfo *deviceInfo = &wmmeDeviceInfo->inheritedDeviceInfo; deviceInfo->structVersion = 2; deviceInfo->hostApi = hostApiIndex; deviceInfo->maxInputChannels = 0; wmmeDeviceInfo->deviceInputChannelCountIsKnown = 1; deviceInfo->maxOutputChannels = 0; wmmeDeviceInfo->deviceOutputChannelCountIsKnown = 1; deviceInfo->defaultLowInputLatency = defaultLowLatency; deviceInfo->defaultLowOutputLatency = defaultLowLatency; deviceInfo->defaultHighInputLatency = defaultHighLatency; deviceInfo->defaultHighOutputLatency = defaultHighLatency; result = InitializeInputDeviceInfo( winMmeHostApi, wmmeDeviceInfo, winMmeDeviceId, &deviceInfoInitializationSucceeded ); if( result != paNoError ) goto error; if( deviceInfoInitializationSucceeded ){ if( (*hostApi)->info.defaultInputDevice == paNoDevice ){ /* if there is currently no default device, use the first one available */ (*hostApi)->info.defaultInputDevice = (*hostApi)->info.deviceCount; }else if( winMmeDeviceId == waveInPreferredDevice ){ /* set the default device to the system preferred device */ (*hostApi)->info.defaultInputDevice = (*hostApi)->info.deviceCount; } winMmeHostApi->winMmeDeviceIds[ (*hostApi)->info.deviceCount ] = winMmeDeviceId; (*hostApi)->deviceInfos[ (*hostApi)->info.deviceCount ] = deviceInfo; winMmeHostApi->inputDeviceCount++; (*hostApi)->info.deviceCount++; } } } if( outputDeviceCount > 0 ){ /* -1 is the WAVE_MAPPER */ for( i = -1; i < outputDeviceCount; ++i ){ UINT winMmeDeviceId = (UINT)((i==-1) ? WAVE_MAPPER : i); PaWinMmeDeviceInfo *wmmeDeviceInfo = &deviceInfoArray[ (*hostApi)->info.deviceCount ]; PaDeviceInfo *deviceInfo = &wmmeDeviceInfo->inheritedDeviceInfo; deviceInfo->structVersion = 2; deviceInfo->hostApi = hostApiIndex; deviceInfo->maxInputChannels = 0; wmmeDeviceInfo->deviceInputChannelCountIsKnown = 1; deviceInfo->maxOutputChannels = 0; wmmeDeviceInfo->deviceOutputChannelCountIsKnown = 1; deviceInfo->defaultLowInputLatency = defaultLowLatency; deviceInfo->defaultLowOutputLatency = defaultLowLatency; deviceInfo->defaultHighInputLatency = defaultHighLatency; deviceInfo->defaultHighOutputLatency = defaultHighLatency; result = InitializeOutputDeviceInfo( winMmeHostApi, wmmeDeviceInfo, winMmeDeviceId, &deviceInfoInitializationSucceeded ); if( result != paNoError ) goto error; if( deviceInfoInitializationSucceeded ){ if( (*hostApi)->info.defaultOutputDevice == paNoDevice ){ /* if there is currently no default device, use the first one available */ (*hostApi)->info.defaultOutputDevice = (*hostApi)->info.deviceCount; }else if( winMmeDeviceId == waveOutPreferredDevice ){ /* set the default device to the system preferred device */ (*hostApi)->info.defaultOutputDevice = (*hostApi)->info.deviceCount; } winMmeHostApi->winMmeDeviceIds[ (*hostApi)->info.deviceCount ] = winMmeDeviceId; (*hostApi)->deviceInfos[ (*hostApi)->info.deviceCount ] = deviceInfo; winMmeHostApi->outputDeviceCount++; (*hostApi)->info.deviceCount++; } } } } InitializeDefaultDeviceIdsFromEnv( winMmeHostApi ); (*hostApi)->Terminate = Terminate; (*hostApi)->OpenStream = OpenStream; (*hostApi)->IsFormatSupported = IsFormatSupported; PaUtil_InitializeStreamInterface( &winMmeHostApi->callbackStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, GetStreamCpuLoad, PaUtil_DummyRead, PaUtil_DummyWrite, PaUtil_DummyGetReadAvailable, PaUtil_DummyGetWriteAvailable ); PaUtil_InitializeStreamInterface( &winMmeHostApi->blockingStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, PaUtil_DummyGetCpuLoad, ReadStream, WriteStream, GetStreamReadAvailable, GetStreamWriteAvailable ); return result; error: if( winMmeHostApi ) { if( winMmeHostApi->allocations ) { PaUtil_FreeAllAllocations( winMmeHostApi->allocations ); PaUtil_DestroyAllocationGroup( winMmeHostApi->allocations ); } PaUtil_FreeMemory( winMmeHostApi ); } return result; } static void Terminate( struct PaUtilHostApiRepresentation *hostApi ) { PaWinMmeHostApiRepresentation *winMmeHostApi = (PaWinMmeHostApiRepresentation*)hostApi; if( winMmeHostApi->allocations ) { PaUtil_FreeAllAllocations( winMmeHostApi->allocations ); PaUtil_DestroyAllocationGroup( winMmeHostApi->allocations ); } PaUtil_FreeMemory( winMmeHostApi ); } static PaError IsInputChannelCountSupported( PaWinMmeDeviceInfo* deviceInfo, int channelCount ) { PaError result = paNoError; if( channelCount > 0 && deviceInfo->deviceInputChannelCountIsKnown && channelCount > deviceInfo->inheritedDeviceInfo.maxInputChannels ){ result = paInvalidChannelCount; } return result; } static PaError IsOutputChannelCountSupported( PaWinMmeDeviceInfo* deviceInfo, int channelCount ) { PaError result = paNoError; if( channelCount > 0 && deviceInfo->deviceOutputChannelCountIsKnown && channelCount > deviceInfo->inheritedDeviceInfo.maxOutputChannels ){ result = paInvalidChannelCount; } return result; } static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ) { PaWinMmeHostApiRepresentation *winMmeHostApi = (PaWinMmeHostApiRepresentation*)hostApi; PaDeviceInfo *inputDeviceInfo, *outputDeviceInfo; int inputChannelCount, outputChannelCount; int inputMultipleDeviceChannelCount, outputMultipleDeviceChannelCount; PaSampleFormat inputSampleFormat, outputSampleFormat; PaWinMmeStreamInfo *inputStreamInfo, *outputStreamInfo; UINT winMmeInputDeviceId, winMmeOutputDeviceId; unsigned int i; PaError paerror; /* The calls to QueryFormatSupported below are intended to detect invalid sample rates. If we assume that the channel count and format are OK, then the only thing that could fail is the sample rate. This isn't strictly true, but I can't think of a better way to test that the sample rate is valid. */ if( inputParameters ) { inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; inputStreamInfo = inputParameters->hostApiSpecificStreamInfo; /* all standard sample formats are supported by the buffer adapter, this implementation doesn't support any custom sample formats */ if( inputSampleFormat & paCustomFormat ) return paSampleFormatNotSupported; if( inputParameters->device == paUseHostApiSpecificDeviceSpecification && inputStreamInfo && (inputStreamInfo->flags & paWinMmeUseMultipleDevices) ) { inputMultipleDeviceChannelCount = 0; for( i=0; i< inputStreamInfo->deviceCount; ++i ) { inputMultipleDeviceChannelCount += inputStreamInfo->devices[i].channelCount; inputDeviceInfo = hostApi->deviceInfos[ inputStreamInfo->devices[i].device ]; /* check that input device can support inputChannelCount */ if( inputStreamInfo->devices[i].channelCount < 1 ) return paInvalidChannelCount; paerror = IsInputChannelCountSupported( (PaWinMmeDeviceInfo*)inputDeviceInfo, inputStreamInfo->devices[i].channelCount ); if( paerror != paNoError ) return paerror; /* test for valid sample rate, see comment above */ winMmeInputDeviceId = LocalDeviceIndexToWinMmeDeviceId( winMmeHostApi, inputStreamInfo->devices[i].device ); paerror = QueryFormatSupported( inputDeviceInfo, QueryInputWaveFormatEx, winMmeInputDeviceId, inputStreamInfo->devices[i].channelCount, sampleRate ); if( paerror != paNoError ) return paInvalidSampleRate; } if( inputMultipleDeviceChannelCount != inputChannelCount ) return paIncompatibleHostApiSpecificStreamInfo; } else { if( inputStreamInfo && (inputStreamInfo->flags & paWinMmeUseMultipleDevices) ) return paIncompatibleHostApiSpecificStreamInfo; /* paUseHostApiSpecificDeviceSpecification was not supplied as the input device */ inputDeviceInfo = hostApi->deviceInfos[ inputParameters->device ]; /* check that input device can support inputChannelCount */ paerror = IsInputChannelCountSupported( (PaWinMmeDeviceInfo*)inputDeviceInfo, inputChannelCount ); if( paerror != paNoError ) return paerror; /* test for valid sample rate, see comment above */ winMmeInputDeviceId = LocalDeviceIndexToWinMmeDeviceId( winMmeHostApi, inputParameters->device ); paerror = QueryFormatSupported( inputDeviceInfo, QueryInputWaveFormatEx, winMmeInputDeviceId, inputChannelCount, sampleRate ); if( paerror != paNoError ) return paInvalidSampleRate; } } if( outputParameters ) { outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; outputStreamInfo = outputParameters->hostApiSpecificStreamInfo; /* all standard sample formats are supported by the buffer adapter, this implementation doesn't support any custom sample formats */ if( outputSampleFormat & paCustomFormat ) return paSampleFormatNotSupported; if( outputParameters->device == paUseHostApiSpecificDeviceSpecification && outputStreamInfo && (outputStreamInfo->flags & paWinMmeUseMultipleDevices) ) { outputMultipleDeviceChannelCount = 0; for( i=0; i< outputStreamInfo->deviceCount; ++i ) { outputMultipleDeviceChannelCount += outputStreamInfo->devices[i].channelCount; outputDeviceInfo = hostApi->deviceInfos[ outputStreamInfo->devices[i].device ]; /* check that output device can support outputChannelCount */ if( outputStreamInfo->devices[i].channelCount < 1 ) return paInvalidChannelCount; paerror = IsOutputChannelCountSupported( (PaWinMmeDeviceInfo*)outputDeviceInfo, outputStreamInfo->devices[i].channelCount ); if( paerror != paNoError ) return paerror; /* test for valid sample rate, see comment above */ winMmeOutputDeviceId = LocalDeviceIndexToWinMmeDeviceId( winMmeHostApi, outputStreamInfo->devices[i].device ); paerror = QueryFormatSupported( outputDeviceInfo, QueryOutputWaveFormatEx, winMmeOutputDeviceId, outputStreamInfo->devices[i].channelCount, sampleRate ); if( paerror != paNoError ) return paInvalidSampleRate; } if( outputMultipleDeviceChannelCount != outputChannelCount ) return paIncompatibleHostApiSpecificStreamInfo; } else { if( outputStreamInfo && (outputStreamInfo->flags & paWinMmeUseMultipleDevices) ) return paIncompatibleHostApiSpecificStreamInfo; /* paUseHostApiSpecificDeviceSpecification was not supplied as the output device */ outputDeviceInfo = hostApi->deviceInfos[ outputParameters->device ]; /* check that output device can support outputChannelCount */ paerror = IsOutputChannelCountSupported( (PaWinMmeDeviceInfo*)outputDeviceInfo, outputChannelCount ); if( paerror != paNoError ) return paerror; /* test for valid sample rate, see comment above */ winMmeOutputDeviceId = LocalDeviceIndexToWinMmeDeviceId( winMmeHostApi, outputParameters->device ); paerror = QueryFormatSupported( outputDeviceInfo, QueryOutputWaveFormatEx, winMmeOutputDeviceId, outputChannelCount, sampleRate ); if( paerror != paNoError ) return paInvalidSampleRate; } } /* - if a full duplex stream is requested, check that the combination of input and output parameters is supported - check that the device supports sampleRate for mme all we can do is test that the input and output devices support the requested sample rate and number of channels. we cannot test for full duplex compatibility. */ return paFormatIsSupported; } static void SelectBufferSizeAndCount( unsigned long baseBufferSize, unsigned long requestedLatency, unsigned long baseBufferCount, unsigned long minimumBufferCount, unsigned long maximumBufferSize, unsigned long *hostBufferSize, unsigned long *hostBufferCount ) { unsigned long sizeMultiplier, bufferCount, latency; unsigned long nextLatency, nextBufferSize; int baseBufferSizeIsPowerOfTwo; sizeMultiplier = 1; bufferCount = baseBufferCount; /* count-1 below because latency is always determined by one less than the total number of buffers. */ latency = (baseBufferSize * sizeMultiplier) * (bufferCount-1); if( latency > requestedLatency ) { /* reduce number of buffers without falling below suggested latency */ nextLatency = (baseBufferSize * sizeMultiplier) * (bufferCount-2); while( bufferCount > minimumBufferCount && nextLatency >= requestedLatency ) { --bufferCount; nextLatency = (baseBufferSize * sizeMultiplier) * (bufferCount-2); } }else if( latency < requestedLatency ){ baseBufferSizeIsPowerOfTwo = (! (baseBufferSize & (baseBufferSize - 1))); if( baseBufferSizeIsPowerOfTwo ){ /* double size of buffers without exceeding requestedLatency */ nextBufferSize = (baseBufferSize * (sizeMultiplier*2)); nextLatency = nextBufferSize * (bufferCount-1); while( nextBufferSize <= maximumBufferSize && nextLatency < requestedLatency ) { sizeMultiplier *= 2; nextBufferSize = (baseBufferSize * (sizeMultiplier*2)); nextLatency = nextBufferSize * (bufferCount-1); } }else{ /* increase size of buffers upto first excess of requestedLatency */ nextBufferSize = (baseBufferSize * (sizeMultiplier+1)); nextLatency = nextBufferSize * (bufferCount-1); while( nextBufferSize <= maximumBufferSize && nextLatency < requestedLatency ) { ++sizeMultiplier; nextBufferSize = (baseBufferSize * (sizeMultiplier+1)); nextLatency = nextBufferSize * (bufferCount-1); } if( nextLatency < requestedLatency ) ++sizeMultiplier; } /* increase number of buffers until requestedLatency is reached */ latency = (baseBufferSize * sizeMultiplier) * (bufferCount-1); while( latency < requestedLatency ) { ++bufferCount; latency = (baseBufferSize * sizeMultiplier) * (bufferCount-1); } } *hostBufferSize = baseBufferSize * sizeMultiplier; *hostBufferCount = bufferCount; } static void ReselectBufferCount( unsigned long bufferSize, unsigned long requestedLatency, unsigned long baseBufferCount, unsigned long minimumBufferCount, unsigned long *hostBufferCount ) { unsigned long bufferCount, latency; unsigned long nextLatency; bufferCount = baseBufferCount; /* count-1 below because latency is always determined by one less than the total number of buffers. */ latency = bufferSize * (bufferCount-1); if( latency > requestedLatency ) { /* reduce number of buffers without falling below suggested latency */ nextLatency = bufferSize * (bufferCount-2); while( bufferCount > minimumBufferCount && nextLatency >= requestedLatency ) { --bufferCount; nextLatency = bufferSize * (bufferCount-2); } }else if( latency < requestedLatency ){ /* increase number of buffers until requestedLatency is reached */ latency = bufferSize * (bufferCount-1); while( latency < requestedLatency ) { ++bufferCount; latency = bufferSize * (bufferCount-1); } } *hostBufferCount = bufferCount; } /* CalculateBufferSettings() fills the framesPerHostInputBuffer, hostInputBufferCount, framesPerHostOutputBuffer and hostOutputBufferCount parameters based on the values of the other parameters. */ static PaError CalculateBufferSettings( unsigned long *framesPerHostInputBuffer, unsigned long *hostInputBufferCount, unsigned long *framesPerHostOutputBuffer, unsigned long *hostOutputBufferCount, int inputChannelCount, PaSampleFormat hostInputSampleFormat, PaTime suggestedInputLatency, PaWinMmeStreamInfo *inputStreamInfo, int outputChannelCount, PaSampleFormat hostOutputSampleFormat, PaTime suggestedOutputLatency, PaWinMmeStreamInfo *outputStreamInfo, double sampleRate, unsigned long framesPerBuffer ) { PaError result = paNoError; int effectiveInputChannelCount, effectiveOutputChannelCount; int hostInputFrameSize = 0; unsigned int i; if( inputChannelCount > 0 ) { int hostInputSampleSize = Pa_GetSampleSize( hostInputSampleFormat ); if( hostInputSampleSize < 0 ) { result = hostInputSampleSize; goto error; } if( inputStreamInfo && ( inputStreamInfo->flags & paWinMmeUseMultipleDevices ) ) { /* set effectiveInputChannelCount to the largest number of channels on any one device. */ effectiveInputChannelCount = 0; for( i=0; i< inputStreamInfo->deviceCount; ++i ) { if( inputStreamInfo->devices[i].channelCount > effectiveInputChannelCount ) effectiveInputChannelCount = inputStreamInfo->devices[i].channelCount; } } else { effectiveInputChannelCount = inputChannelCount; } hostInputFrameSize = hostInputSampleSize * effectiveInputChannelCount; if( inputStreamInfo && ( inputStreamInfo->flags & paWinMmeUseLowLevelLatencyParameters ) ) { if( inputStreamInfo->bufferCount <= 0 || inputStreamInfo->framesPerBuffer <= 0 ) { result = paIncompatibleHostApiSpecificStreamInfo; goto error; } *framesPerHostInputBuffer = inputStreamInfo->framesPerBuffer; *hostInputBufferCount = inputStreamInfo->bufferCount; } else { unsigned long hostBufferSizeBytes, hostBufferCount; unsigned long minimumBufferCount = (outputChannelCount > 0) ? PA_MME_MIN_HOST_INPUT_BUFFER_COUNT_FULL_DUPLEX_ : PA_MME_MIN_HOST_INPUT_BUFFER_COUNT_HALF_DUPLEX_; unsigned long maximumBufferSize = (long) ((PA_MME_MAX_HOST_BUFFER_SECS_ * sampleRate) * hostInputFrameSize); if( maximumBufferSize > PA_MME_MAX_HOST_BUFFER_BYTES_ ) maximumBufferSize = PA_MME_MAX_HOST_BUFFER_BYTES_; /* compute the following in bytes, then convert back to frames */ SelectBufferSizeAndCount( ((framesPerBuffer == paFramesPerBufferUnspecified) ? PA_MME_MIN_HOST_BUFFER_FRAMES_WHEN_UNSPECIFIED_ : framesPerBuffer ) * hostInputFrameSize, /* baseBufferSize */ ((unsigned long)(suggestedInputLatency * sampleRate)) * hostInputFrameSize, /* suggestedLatency */ 4, /* baseBufferCount */ minimumBufferCount, maximumBufferSize, &hostBufferSizeBytes, &hostBufferCount ); *framesPerHostInputBuffer = hostBufferSizeBytes / hostInputFrameSize; *hostInputBufferCount = hostBufferCount; } } else { *framesPerHostInputBuffer = 0; *hostInputBufferCount = 0; } if( outputChannelCount > 0 ) { if( outputStreamInfo && ( outputStreamInfo->flags & paWinMmeUseLowLevelLatencyParameters ) ) { if( outputStreamInfo->bufferCount <= 0 || outputStreamInfo->framesPerBuffer <= 0 ) { result = paIncompatibleHostApiSpecificStreamInfo; goto error; } *framesPerHostOutputBuffer = outputStreamInfo->framesPerBuffer; *hostOutputBufferCount = outputStreamInfo->bufferCount; if( inputChannelCount > 0 ) /* full duplex */ { if( *framesPerHostInputBuffer != *framesPerHostOutputBuffer ) { if( inputStreamInfo && ( inputStreamInfo->flags & paWinMmeUseLowLevelLatencyParameters ) ) { /* a custom StreamInfo was used for specifying both input and output buffer sizes, the larger buffer size must be a multiple of the smaller buffer size */ if( *framesPerHostInputBuffer < *framesPerHostOutputBuffer ) { if( *framesPerHostOutputBuffer % *framesPerHostInputBuffer != 0 ) { result = paIncompatibleHostApiSpecificStreamInfo; goto error; } } else { assert( *framesPerHostInputBuffer > *framesPerHostOutputBuffer ); if( *framesPerHostInputBuffer % *framesPerHostOutputBuffer != 0 ) { result = paIncompatibleHostApiSpecificStreamInfo; goto error; } } } else { /* a custom StreamInfo was not used for specifying the input buffer size, so use the output buffer size, and approximately the same latency. */ *framesPerHostInputBuffer = *framesPerHostOutputBuffer; *hostInputBufferCount = (((unsigned long)(suggestedInputLatency * sampleRate)) / *framesPerHostInputBuffer) + 1; if( *hostInputBufferCount < PA_MME_MIN_HOST_INPUT_BUFFER_COUNT_FULL_DUPLEX_ ) *hostInputBufferCount = PA_MME_MIN_HOST_INPUT_BUFFER_COUNT_FULL_DUPLEX_; } } } } else { unsigned long hostBufferSizeBytes, hostBufferCount; unsigned long minimumBufferCount = PA_MME_MIN_HOST_OUTPUT_BUFFER_COUNT_; unsigned long maximumBufferSize; int hostOutputFrameSize; int hostOutputSampleSize; hostOutputSampleSize = Pa_GetSampleSize( hostOutputSampleFormat ); if( hostOutputSampleSize < 0 ) { result = hostOutputSampleSize; goto error; } if( outputStreamInfo && ( outputStreamInfo->flags & paWinMmeUseMultipleDevices ) ) { /* set effectiveOutputChannelCount to the largest number of channels on any one device. */ effectiveOutputChannelCount = 0; for( i=0; i< outputStreamInfo->deviceCount; ++i ) { if( outputStreamInfo->devices[i].channelCount > effectiveOutputChannelCount ) effectiveOutputChannelCount = outputStreamInfo->devices[i].channelCount; } } else { effectiveOutputChannelCount = outputChannelCount; } hostOutputFrameSize = hostOutputSampleSize * effectiveOutputChannelCount; maximumBufferSize = (long) ((PA_MME_MAX_HOST_BUFFER_SECS_ * sampleRate) * hostOutputFrameSize); if( maximumBufferSize > PA_MME_MAX_HOST_BUFFER_BYTES_ ) maximumBufferSize = PA_MME_MAX_HOST_BUFFER_BYTES_; /* compute the following in bytes, then convert back to frames */ SelectBufferSizeAndCount( ((framesPerBuffer == paFramesPerBufferUnspecified) ? PA_MME_MIN_HOST_BUFFER_FRAMES_WHEN_UNSPECIFIED_ : framesPerBuffer ) * hostOutputFrameSize, /* baseBufferSize */ ((unsigned long)(suggestedOutputLatency * sampleRate)) * hostOutputFrameSize, /* suggestedLatency */ 4, /* baseBufferCount */ minimumBufferCount, maximumBufferSize, &hostBufferSizeBytes, &hostBufferCount ); *framesPerHostOutputBuffer = hostBufferSizeBytes / hostOutputFrameSize; *hostOutputBufferCount = hostBufferCount; if( inputChannelCount > 0 ) { /* ensure that both input and output buffer sizes are the same. if they don't match at this stage, choose the smallest one and use that for input and output */ if( *framesPerHostOutputBuffer != *framesPerHostInputBuffer ) { if( framesPerHostInputBuffer < framesPerHostOutputBuffer ) { unsigned long framesPerHostBuffer = *framesPerHostInputBuffer; minimumBufferCount = PA_MME_MIN_HOST_OUTPUT_BUFFER_COUNT_; ReselectBufferCount( framesPerHostBuffer * hostOutputFrameSize, /* bufferSize */ ((unsigned long)(suggestedOutputLatency * sampleRate)) * hostOutputFrameSize, /* suggestedLatency */ 4, /* baseBufferCount */ minimumBufferCount, &hostBufferCount ); *framesPerHostOutputBuffer = framesPerHostBuffer; *hostOutputBufferCount = hostBufferCount; } else { unsigned long framesPerHostBuffer = *framesPerHostOutputBuffer; minimumBufferCount = PA_MME_MIN_HOST_INPUT_BUFFER_COUNT_FULL_DUPLEX_; ReselectBufferCount( framesPerHostBuffer * hostInputFrameSize, /* bufferSize */ ((unsigned long)(suggestedInputLatency * sampleRate)) * hostInputFrameSize, /* suggestedLatency */ 4, /* baseBufferCount */ minimumBufferCount, &hostBufferCount ); *framesPerHostInputBuffer = framesPerHostBuffer; *hostInputBufferCount = hostBufferCount; } } } } } else { *framesPerHostOutputBuffer = 0; *hostOutputBufferCount = 0; } error: return result; } typedef struct { HANDLE bufferEvent; void *waveHandles; unsigned int deviceCount; /* unsigned int channelCount; */ WAVEHDR **waveHeaders; /* waveHeaders[device][buffer] */ unsigned int bufferCount; unsigned int currentBufferIndex; unsigned int framesPerBuffer; unsigned int framesUsedInCurrentBuffer; }PaWinMmeSingleDirectionHandlesAndBuffers; /* prototypes for functions operating on PaWinMmeSingleDirectionHandlesAndBuffers */ static void InitializeSingleDirectionHandlesAndBuffers( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers ); static PaError InitializeWaveHandles( PaWinMmeHostApiRepresentation *winMmeHostApi, PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers, unsigned long bytesPerHostSample, double sampleRate, PaWinMmeDeviceAndChannelCount *devices, unsigned int deviceCount, PaWinWaveFormatChannelMask channelMask, int isInput ); static PaError TerminateWaveHandles( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers, int isInput, int currentlyProcessingAnError ); static PaError InitializeWaveHeaders( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers, unsigned long hostBufferCount, PaSampleFormat hostSampleFormat, unsigned long framesPerHostBuffer, PaWinMmeDeviceAndChannelCount *devices, int isInput ); static void TerminateWaveHeaders( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers, int isInput ); static void InitializeSingleDirectionHandlesAndBuffers( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers ) { handlesAndBuffers->bufferEvent = 0; handlesAndBuffers->waveHandles = 0; handlesAndBuffers->deviceCount = 0; handlesAndBuffers->waveHeaders = 0; handlesAndBuffers->bufferCount = 0; } static PaError InitializeWaveHandles( PaWinMmeHostApiRepresentation *winMmeHostApi, PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers, unsigned long bytesPerHostSample, double sampleRate, PaWinMmeDeviceAndChannelCount *devices, unsigned int deviceCount, PaWinWaveFormatChannelMask channelMask, int isInput ) { PaError result; MMRESULT mmresult; signed int i, j; /* for error cleanup we expect that InitializeSingleDirectionHandlesAndBuffers() has already been called to zero some fields */ result = CreateEventWithPaError( &handlesAndBuffers->bufferEvent, NULL, FALSE, FALSE, NULL ); if( result != paNoError ) goto error; if( isInput ) handlesAndBuffers->waveHandles = (void*)PaUtil_AllocateMemory( sizeof(HWAVEIN) * deviceCount ); else handlesAndBuffers->waveHandles = (void*)PaUtil_AllocateMemory( sizeof(HWAVEOUT) * deviceCount ); if( !handlesAndBuffers->waveHandles ) { result = paInsufficientMemory; goto error; } handlesAndBuffers->deviceCount = deviceCount; for( i = 0; i < (signed int)deviceCount; ++i ) { if( isInput ) ((HWAVEIN*)handlesAndBuffers->waveHandles)[i] = 0; else ((HWAVEOUT*)handlesAndBuffers->waveHandles)[i] = 0; } for( i = 0; i < (signed int)deviceCount; ++i ) { PaWinWaveFormat waveFormat; UINT winMmeDeviceId = LocalDeviceIndexToWinMmeDeviceId( winMmeHostApi, devices[i].device ); /* @todo: consider providing a flag or #define to not try waveformat extensible this could just initialize j to 1 the first time round. */ for( j = 0; j < 2; ++j ) { if( j == 0 ) { /* first, attempt to open the device using WAVEFORMATEXTENSIBLE, if this fails we fall back to WAVEFORMATEX */ /* @todo at the moment we only use 16 bit sample format */ PaWin_InitializeWaveFormatExtensible( &waveFormat, devices[i].channelCount, paInt16, sampleRate, channelMask ); } else { /* retry with WAVEFORMATEX */ PaWin_InitializeWaveFormatEx( &waveFormat, devices[i].channelCount, paInt16, sampleRate ); } /* REVIEW: consider not firing an event for input when a full duplex stream is being used. this would probably depend on the neverDropInput flag. */ if( isInput ) { mmresult = waveInOpen( &((HWAVEIN*)handlesAndBuffers->waveHandles)[i], winMmeDeviceId, (WAVEFORMATEX*)&waveFormat, (DWORD_PTR)handlesAndBuffers->bufferEvent, (DWORD_PTR)0, CALLBACK_EVENT ); } else { mmresult = waveOutOpen( &((HWAVEOUT*)handlesAndBuffers->waveHandles)[i], winMmeDeviceId, (WAVEFORMATEX*)&waveFormat, (DWORD_PTR)handlesAndBuffers->bufferEvent, (DWORD_PTR)0, CALLBACK_EVENT ); } if( mmresult == MMSYSERR_NOERROR ) { break; /* success */ } else if( j == 0 ) { continue; /* try again with WAVEFORMATEX */ } else { switch( mmresult ) { case MMSYSERR_ALLOCATED: /* Specified resource is already allocated. */ result = paDeviceUnavailable; break; case MMSYSERR_NODRIVER: /* No device driver is present. */ result = paDeviceUnavailable; break; case MMSYSERR_NOMEM: /* Unable to allocate or lock memory. */ result = paInsufficientMemory; break; case MMSYSERR_BADDEVICEID: /* Specified device identifier is out of range. */ /* falls through */ case WAVERR_BADFORMAT: /* Attempted to open with an unsupported waveform-audio format. */ /* This can also occur if we try to open the device with an unsupported * number of channels. This is attempted when device*ChannelCountIsKnown is * set to 0. */ /* falls through */ default: result = paUnanticipatedHostError; if( isInput ) { PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); } else { PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ); } } goto error; } } } return result; error: TerminateWaveHandles( handlesAndBuffers, isInput, 1 /* currentlyProcessingAnError */ ); return result; } static PaError TerminateWaveHandles( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers, int isInput, int currentlyProcessingAnError ) { PaError result = paNoError; MMRESULT mmresult; signed int i; if( handlesAndBuffers->waveHandles ) { for( i = handlesAndBuffers->deviceCount-1; i >= 0; --i ) { if( isInput ) { if( ((HWAVEIN*)handlesAndBuffers->waveHandles)[i] ) mmresult = waveInClose( ((HWAVEIN*)handlesAndBuffers->waveHandles)[i] ); else mmresult = MMSYSERR_NOERROR; } else { if( ((HWAVEOUT*)handlesAndBuffers->waveHandles)[i] ) mmresult = waveOutClose( ((HWAVEOUT*)handlesAndBuffers->waveHandles)[i] ); else mmresult = MMSYSERR_NOERROR; } if( mmresult != MMSYSERR_NOERROR && !currentlyProcessingAnError ) /* don't update the error state if we're already processing an error */ { result = paUnanticipatedHostError; if( isInput ) { PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); } else { PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ); } /* note that we don't break here, we try to continue closing devices */ } } PaUtil_FreeMemory( handlesAndBuffers->waveHandles ); handlesAndBuffers->waveHandles = 0; } if( handlesAndBuffers->bufferEvent ) { result = CloseHandleWithPaError( handlesAndBuffers->bufferEvent ); handlesAndBuffers->bufferEvent = 0; } return result; } static PaError InitializeWaveHeaders( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers, unsigned long hostBufferCount, PaSampleFormat hostSampleFormat, unsigned long framesPerHostBuffer, PaWinMmeDeviceAndChannelCount *devices, int isInput ) { PaError result = paNoError; MMRESULT mmresult; WAVEHDR *deviceWaveHeaders; signed int i, j; /* for error cleanup we expect that InitializeSingleDirectionHandlesAndBuffers() has already been called to zero some fields */ /* allocate an array of pointers to arrays of wave headers, one array of wave headers per device */ handlesAndBuffers->waveHeaders = (WAVEHDR**)PaUtil_AllocateMemory( sizeof(WAVEHDR*) * handlesAndBuffers->deviceCount ); if( !handlesAndBuffers->waveHeaders ) { result = paInsufficientMemory; goto error; } for( i = 0; i < (signed int)handlesAndBuffers->deviceCount; ++i ) handlesAndBuffers->waveHeaders[i] = 0; handlesAndBuffers->bufferCount = hostBufferCount; for( i = 0; i < (signed int)handlesAndBuffers->deviceCount; ++i ) { int bufferBytes = Pa_GetSampleSize( hostSampleFormat ) * framesPerHostBuffer * devices[i].channelCount; if( bufferBytes < 0 ) { result = paInternalError; goto error; } /* Allocate an array of wave headers for device i */ deviceWaveHeaders = (WAVEHDR *) PaUtil_AllocateMemory( sizeof(WAVEHDR)*hostBufferCount ); if( !deviceWaveHeaders ) { result = paInsufficientMemory; goto error; } for( j=0; j < (signed int)hostBufferCount; ++j ) deviceWaveHeaders[j].lpData = 0; handlesAndBuffers->waveHeaders[i] = deviceWaveHeaders; /* Allocate a buffer for each wave header */ for( j=0; j < (signed int)hostBufferCount; ++j ) { deviceWaveHeaders[j].lpData = (char *)PaUtil_AllocateMemory( bufferBytes ); if( !deviceWaveHeaders[j].lpData ) { result = paInsufficientMemory; goto error; } deviceWaveHeaders[j].dwBufferLength = bufferBytes; deviceWaveHeaders[j].dwUser = 0xFFFFFFFF; /* indicates that *PrepareHeader() has not yet been called, for error clean up code */ if( isInput ) { mmresult = waveInPrepareHeader( ((HWAVEIN*)handlesAndBuffers->waveHandles)[i], &deviceWaveHeaders[j], sizeof(WAVEHDR) ); if( mmresult != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); goto error; } } else /* output */ { mmresult = waveOutPrepareHeader( ((HWAVEOUT*)handlesAndBuffers->waveHandles)[i], &deviceWaveHeaders[j], sizeof(WAVEHDR) ); if( mmresult != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); goto error; } } deviceWaveHeaders[j].dwUser = devices[i].channelCount; } } return result; error: TerminateWaveHeaders( handlesAndBuffers, isInput ); return result; } static void TerminateWaveHeaders( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers, int isInput ) { signed int i, j; WAVEHDR *deviceWaveHeaders; if( handlesAndBuffers->waveHeaders ) { for( i = handlesAndBuffers->deviceCount-1; i >= 0 ; --i ) { deviceWaveHeaders = handlesAndBuffers->waveHeaders[i]; /* wave headers for device i */ if( deviceWaveHeaders ) { for( j = handlesAndBuffers->bufferCount-1; j >= 0; --j ) { if( deviceWaveHeaders[j].lpData ) { if( deviceWaveHeaders[j].dwUser != 0xFFFFFFFF ) { if( isInput ) waveInUnprepareHeader( ((HWAVEIN*)handlesAndBuffers->waveHandles)[i], &deviceWaveHeaders[j], sizeof(WAVEHDR) ); else waveOutUnprepareHeader( ((HWAVEOUT*)handlesAndBuffers->waveHandles)[i], &deviceWaveHeaders[j], sizeof(WAVEHDR) ); } PaUtil_FreeMemory( deviceWaveHeaders[j].lpData ); } } PaUtil_FreeMemory( deviceWaveHeaders ); } } PaUtil_FreeMemory( handlesAndBuffers->waveHeaders ); handlesAndBuffers->waveHeaders = 0; } } /* PaWinMmeStream - a stream data structure specifically for this implementation */ /* note that struct PaWinMmeStream is typedeffed to PaWinMmeStream above. */ struct PaWinMmeStream { PaUtilStreamRepresentation streamRepresentation; PaUtilCpuLoadMeasurer cpuLoadMeasurer; PaUtilBufferProcessor bufferProcessor; int primeStreamUsingCallback; PaWinMmeSingleDirectionHandlesAndBuffers input; PaWinMmeSingleDirectionHandlesAndBuffers output; /* Processing thread management -------------- */ HANDLE abortEvent; HANDLE processingThread; DWORD processingThreadId; char throttleProcessingThreadOnOverload; /* 0 -> don't throtte, non-0 -> throttle */ int processingThreadPriority; int highThreadPriority; int throttledThreadPriority; unsigned long throttledSleepMsecs; int isStopped; volatile int isActive; volatile int stopProcessing; /* stop thread once existing buffers have been returned */ volatile int abortProcessing; /* stop thread immediately */ DWORD allBuffersDurationMs; /* used to calculate timeouts */ }; /* updates deviceCount if PaWinMmeUseMultipleDevices is used */ static PaError ValidateWinMmeSpecificStreamInfo( const PaStreamParameters *streamParameters, const PaWinMmeStreamInfo *streamInfo, char *throttleProcessingThreadOnOverload, unsigned long *deviceCount ) { if( streamInfo ) { if( streamInfo->size != sizeof( PaWinMmeStreamInfo ) || streamInfo->version != 1 ) { return paIncompatibleHostApiSpecificStreamInfo; } if( streamInfo->flags & paWinMmeDontThrottleOverloadedProcessingThread ) *throttleProcessingThreadOnOverload = 0; if( streamInfo->flags & paWinMmeUseMultipleDevices ) { if( streamParameters->device != paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; *deviceCount = streamInfo->deviceCount; } } return paNoError; } static PaError RetrieveDevicesFromStreamParameters( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *streamParameters, const PaWinMmeStreamInfo *streamInfo, PaWinMmeDeviceAndChannelCount *devices, unsigned long deviceCount ) { PaError result = paNoError; unsigned int i; int totalChannelCount; PaDeviceIndex hostApiDevice; if( streamInfo && streamInfo->flags & paWinMmeUseMultipleDevices ) { totalChannelCount = 0; for( i=0; i < deviceCount; ++i ) { /* validate that the device number is within range */ result = PaUtil_DeviceIndexToHostApiDeviceIndex( &hostApiDevice, streamInfo->devices[i].device, hostApi ); if( result != paNoError ) return result; devices[i].device = hostApiDevice; devices[i].channelCount = streamInfo->devices[i].channelCount; totalChannelCount += devices[i].channelCount; } if( totalChannelCount != streamParameters->channelCount ) { /* channelCount must match total channels specified by multiple devices */ return paInvalidChannelCount; /* REVIEW use of this error code */ } } else { devices[0].device = streamParameters->device; devices[0].channelCount = streamParameters->channelCount; } return result; } static PaError ValidateInputChannelCounts( struct PaUtilHostApiRepresentation *hostApi, PaWinMmeDeviceAndChannelCount *devices, unsigned long deviceCount ) { unsigned int i; PaWinMmeDeviceInfo *inputDeviceInfo; PaError paerror; for( i=0; i < deviceCount; ++i ) { if( devices[i].channelCount < 1 ) return paInvalidChannelCount; inputDeviceInfo = (PaWinMmeDeviceInfo*)hostApi->deviceInfos[ devices[i].device ]; paerror = IsInputChannelCountSupported( inputDeviceInfo, devices[i].channelCount ); if( paerror != paNoError ) return paerror; } return paNoError; } static PaError ValidateOutputChannelCounts( struct PaUtilHostApiRepresentation *hostApi, PaWinMmeDeviceAndChannelCount *devices, unsigned long deviceCount ) { unsigned int i; PaWinMmeDeviceInfo *outputDeviceInfo; PaError paerror; for( i=0; i < deviceCount; ++i ) { if( devices[i].channelCount < 1 ) return paInvalidChannelCount; outputDeviceInfo = (PaWinMmeDeviceInfo*)hostApi->deviceInfos[ devices[i].device ]; paerror = IsOutputChannelCountSupported( outputDeviceInfo, devices[i].channelCount ); if( paerror != paNoError ) return paerror; } return paNoError; } /* the following macros are intended to improve the readability of the following code */ #define PA_IS_INPUT_STREAM_( stream ) ( stream ->input.waveHandles ) #define PA_IS_OUTPUT_STREAM_( stream ) ( stream ->output.waveHandles ) #define PA_IS_FULL_DUPLEX_STREAM_( stream ) ( stream ->input.waveHandles && stream ->output.waveHandles ) #define PA_IS_HALF_DUPLEX_STREAM_( stream ) ( !(stream ->input.waveHandles && stream ->output.waveHandles) ) static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ) { PaError result; PaWinMmeHostApiRepresentation *winMmeHostApi = (PaWinMmeHostApiRepresentation*)hostApi; PaWinMmeStream *stream = 0; int bufferProcessorIsInitialized = 0; int streamRepresentationIsInitialized = 0; PaSampleFormat hostInputSampleFormat, hostOutputSampleFormat; int inputChannelCount, outputChannelCount; PaSampleFormat inputSampleFormat, outputSampleFormat; double suggestedInputLatency, suggestedOutputLatency; PaWinMmeStreamInfo *inputStreamInfo, *outputStreamInfo; PaWinWaveFormatChannelMask inputChannelMask, outputChannelMask; unsigned long framesPerHostInputBuffer; unsigned long hostInputBufferCount; unsigned long framesPerHostOutputBuffer; unsigned long hostOutputBufferCount; unsigned long framesPerBufferProcessorCall; PaWinMmeDeviceAndChannelCount *inputDevices = 0; /* contains all devices and channel counts as local host api ids, even when PaWinMmeUseMultipleDevices is not used */ unsigned long inputDeviceCount = 0; PaWinMmeDeviceAndChannelCount *outputDevices = 0; unsigned long outputDeviceCount = 0; /* contains all devices and channel counts as local host api ids, even when PaWinMmeUseMultipleDevices is not used */ char throttleProcessingThreadOnOverload = 1; if( inputParameters ) { inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; suggestedInputLatency = inputParameters->suggestedLatency; inputDeviceCount = 1; /* validate input hostApiSpecificStreamInfo */ inputStreamInfo = (PaWinMmeStreamInfo*)inputParameters->hostApiSpecificStreamInfo; result = ValidateWinMmeSpecificStreamInfo( inputParameters, inputStreamInfo, &throttleProcessingThreadOnOverload, &inputDeviceCount ); if( result != paNoError ) return result; inputDevices = (PaWinMmeDeviceAndChannelCount*)alloca( sizeof(PaWinMmeDeviceAndChannelCount) * inputDeviceCount ); if( !inputDevices ) return paInsufficientMemory; result = RetrieveDevicesFromStreamParameters( hostApi, inputParameters, inputStreamInfo, inputDevices, inputDeviceCount ); if( result != paNoError ) return result; result = ValidateInputChannelCounts( hostApi, inputDevices, inputDeviceCount ); if( result != paNoError ) return result; hostInputSampleFormat = PaUtil_SelectClosestAvailableFormat( paInt16 /* native formats */, inputSampleFormat ); if( inputDeviceCount != 1 ){ /* always use direct speakers when using multi-device multichannel mode */ inputChannelMask = PAWIN_SPEAKER_DIRECTOUT; } else { if( inputStreamInfo && inputStreamInfo->flags & paWinMmeUseChannelMask ) inputChannelMask = inputStreamInfo->channelMask; else inputChannelMask = PaWin_DefaultChannelMask( inputDevices[0].channelCount ); } } else { inputChannelCount = 0; inputSampleFormat = 0; suggestedInputLatency = 0.; inputStreamInfo = 0; hostInputSampleFormat = 0; } if( outputParameters ) { outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; suggestedOutputLatency = outputParameters->suggestedLatency; outputDeviceCount = 1; /* validate output hostApiSpecificStreamInfo */ outputStreamInfo = (PaWinMmeStreamInfo*)outputParameters->hostApiSpecificStreamInfo; result = ValidateWinMmeSpecificStreamInfo( outputParameters, outputStreamInfo, &throttleProcessingThreadOnOverload, &outputDeviceCount ); if( result != paNoError ) return result; outputDevices = (PaWinMmeDeviceAndChannelCount*)alloca( sizeof(PaWinMmeDeviceAndChannelCount) * outputDeviceCount ); if( !outputDevices ) return paInsufficientMemory; result = RetrieveDevicesFromStreamParameters( hostApi, outputParameters, outputStreamInfo, outputDevices, outputDeviceCount ); if( result != paNoError ) return result; result = ValidateOutputChannelCounts( hostApi, outputDevices, outputDeviceCount ); if( result != paNoError ) return result; hostOutputSampleFormat = PaUtil_SelectClosestAvailableFormat( paInt16 /* native formats */, outputSampleFormat ); if( outputDeviceCount != 1 ){ /* always use direct speakers when using multi-device multichannel mode */ outputChannelMask = PAWIN_SPEAKER_DIRECTOUT; } else { if( outputStreamInfo && outputStreamInfo->flags & paWinMmeUseChannelMask ) outputChannelMask = outputStreamInfo->channelMask; else outputChannelMask = PaWin_DefaultChannelMask( outputDevices[0].channelCount ); } } else { outputChannelCount = 0; outputSampleFormat = 0; outputStreamInfo = 0; hostOutputSampleFormat = 0; suggestedOutputLatency = 0.; } /* IMPLEMENT ME: - alter sampleRate to a close allowable rate if possible / necessary */ /* validate platform specific flags */ if( (streamFlags & paPlatformSpecificFlags) != 0 ) return paInvalidFlag; /* unexpected platform specific flag */ result = CalculateBufferSettings( &framesPerHostInputBuffer, &hostInputBufferCount, &framesPerHostOutputBuffer, &hostOutputBufferCount, inputChannelCount, hostInputSampleFormat, suggestedInputLatency, inputStreamInfo, outputChannelCount, hostOutputSampleFormat, suggestedOutputLatency, outputStreamInfo, sampleRate, framesPerBuffer ); if( result != paNoError ) goto error; stream = (PaWinMmeStream*)PaUtil_AllocateMemory( sizeof(PaWinMmeStream) ); if( !stream ) { result = paInsufficientMemory; goto error; } InitializeSingleDirectionHandlesAndBuffers( &stream->input ); InitializeSingleDirectionHandlesAndBuffers( &stream->output ); stream->abortEvent = 0; stream->processingThread = 0; stream->throttleProcessingThreadOnOverload = throttleProcessingThreadOnOverload; PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, ( (streamCallback) ? &winMmeHostApi->callbackStreamInterface : &winMmeHostApi->blockingStreamInterface ), streamCallback, userData ); streamRepresentationIsInitialized = 1; PaUtil_InitializeCpuLoadMeasurer( &stream->cpuLoadMeasurer, sampleRate ); if( inputParameters && outputParameters ) /* full duplex */ { if( framesPerHostInputBuffer < framesPerHostOutputBuffer ) { assert( (framesPerHostOutputBuffer % framesPerHostInputBuffer) == 0 ); /* CalculateBufferSettings() should guarantee this condition */ framesPerBufferProcessorCall = framesPerHostInputBuffer; } else { assert( (framesPerHostInputBuffer % framesPerHostOutputBuffer) == 0 ); /* CalculateBufferSettings() should guarantee this condition */ framesPerBufferProcessorCall = framesPerHostOutputBuffer; } } else if( inputParameters ) { framesPerBufferProcessorCall = framesPerHostInputBuffer; } else if( outputParameters ) { framesPerBufferProcessorCall = framesPerHostOutputBuffer; } stream->input.framesPerBuffer = framesPerHostInputBuffer; stream->output.framesPerBuffer = framesPerHostOutputBuffer; result = PaUtil_InitializeBufferProcessor( &stream->bufferProcessor, inputChannelCount, inputSampleFormat, hostInputSampleFormat, outputChannelCount, outputSampleFormat, hostOutputSampleFormat, sampleRate, streamFlags, framesPerBuffer, framesPerBufferProcessorCall, paUtilFixedHostBufferSize, streamCallback, userData ); if( result != paNoError ) goto error; bufferProcessorIsInitialized = 1; stream->streamRepresentation.streamInfo.inputLatency = (double)(PaUtil_GetBufferProcessorInputLatency(&stream->bufferProcessor) +(framesPerHostInputBuffer * (hostInputBufferCount-1))) / sampleRate; stream->streamRepresentation.streamInfo.outputLatency = (double)(PaUtil_GetBufferProcessorOutputLatency(&stream->bufferProcessor) +(framesPerHostOutputBuffer * (hostOutputBufferCount-1))) / sampleRate; stream->streamRepresentation.streamInfo.sampleRate = sampleRate; stream->primeStreamUsingCallback = ( (streamFlags&paPrimeOutputBuffersUsingStreamCallback) && streamCallback ) ? 1 : 0; /* time to sleep when throttling due to >100% cpu usage. -a quater of a buffer's duration */ stream->throttledSleepMsecs = (unsigned long)(stream->bufferProcessor.framesPerHostBuffer * stream->bufferProcessor.samplePeriod * .25 * 1000); stream->isStopped = 1; stream->isActive = 0; /* for maximum compatibility with multi-device multichannel drivers, we first open all devices, then we prepare all buffers, finally we start all devices ( in StartStream() ). teardown in reverse order. */ if( inputParameters ) { result = InitializeWaveHandles( winMmeHostApi, &stream->input, stream->bufferProcessor.bytesPerHostInputSample, sampleRate, inputDevices, inputDeviceCount, inputChannelMask, 1 /* isInput */ ); if( result != paNoError ) goto error; } if( outputParameters ) { result = InitializeWaveHandles( winMmeHostApi, &stream->output, stream->bufferProcessor.bytesPerHostOutputSample, sampleRate, outputDevices, outputDeviceCount, outputChannelMask, 0 /* isInput */ ); if( result != paNoError ) goto error; } if( inputParameters ) { result = InitializeWaveHeaders( &stream->input, hostInputBufferCount, hostInputSampleFormat, framesPerHostInputBuffer, inputDevices, 1 /* isInput */ ); if( result != paNoError ) goto error; } if( outputParameters ) { result = InitializeWaveHeaders( &stream->output, hostOutputBufferCount, hostOutputSampleFormat, framesPerHostOutputBuffer, outputDevices, 0 /* not isInput */ ); if( result != paNoError ) goto error; stream->allBuffersDurationMs = (DWORD) (1000.0 * (framesPerHostOutputBuffer * stream->output.bufferCount) / sampleRate); } else { stream->allBuffersDurationMs = (DWORD) (1000.0 * (framesPerHostInputBuffer * stream->input.bufferCount) / sampleRate); } if( streamCallback ) { /* abort event is only needed for callback streams */ result = CreateEventWithPaError( &stream->abortEvent, NULL, TRUE, FALSE, NULL ); if( result != paNoError ) goto error; } *s = (PaStream*)stream; return result; error: if( stream ) { if( stream->abortEvent ) CloseHandle( stream->abortEvent ); TerminateWaveHeaders( &stream->output, 0 /* not isInput */ ); TerminateWaveHeaders( &stream->input, 1 /* isInput */ ); TerminateWaveHandles( &stream->output, 0 /* not isInput */, 1 /* currentlyProcessingAnError */ ); TerminateWaveHandles( &stream->input, 1 /* isInput */, 1 /* currentlyProcessingAnError */ ); if( bufferProcessorIsInitialized ) PaUtil_TerminateBufferProcessor( &stream->bufferProcessor ); if( streamRepresentationIsInitialized ) PaUtil_TerminateStreamRepresentation( &stream->streamRepresentation ); PaUtil_FreeMemory( stream ); } return result; } /* return non-zero if all current buffers are done */ static int BuffersAreDone( WAVEHDR **waveHeaders, unsigned int deviceCount, int bufferIndex ) { unsigned int i; for( i=0; i < deviceCount; ++i ) { if( !(waveHeaders[i][ bufferIndex ].dwFlags & WHDR_DONE) ) { return 0; } } return 1; } static int CurrentInputBuffersAreDone( PaWinMmeStream *stream ) { return BuffersAreDone( stream->input.waveHeaders, stream->input.deviceCount, stream->input.currentBufferIndex ); } static int CurrentOutputBuffersAreDone( PaWinMmeStream *stream ) { return BuffersAreDone( stream->output.waveHeaders, stream->output.deviceCount, stream->output.currentBufferIndex ); } /* return non-zero if any buffers are queued */ static int NoBuffersAreQueued( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers ) { unsigned int i, j; if( handlesAndBuffers->waveHandles ) { for( i=0; i < handlesAndBuffers->bufferCount; ++i ) { for( j=0; j < handlesAndBuffers->deviceCount; ++j ) { if( !( handlesAndBuffers->waveHeaders[ j ][ i ].dwFlags & WHDR_DONE) ) { return 0; } } } } return 1; } #define PA_CIRCULAR_INCREMENT_( current, max )\ ( (((current) + 1) >= (max)) ? (0) : (current+1) ) #define PA_CIRCULAR_DECREMENT_( current, max )\ ( ((current) == 0) ? ((max)-1) : (current-1) ) static signed long GetAvailableFrames( PaWinMmeSingleDirectionHandlesAndBuffers *handlesAndBuffers ) { signed long result = 0; unsigned int i; if( BuffersAreDone( handlesAndBuffers->waveHeaders, handlesAndBuffers->deviceCount, handlesAndBuffers->currentBufferIndex ) ) { /* we could calculate the following in O(1) if we kept track of the last done buffer */ result = handlesAndBuffers->framesPerBuffer - handlesAndBuffers->framesUsedInCurrentBuffer; i = PA_CIRCULAR_INCREMENT_( handlesAndBuffers->currentBufferIndex, handlesAndBuffers->bufferCount ); while( i != handlesAndBuffers->currentBufferIndex ) { if( BuffersAreDone( handlesAndBuffers->waveHeaders, handlesAndBuffers->deviceCount, i ) ) { result += handlesAndBuffers->framesPerBuffer; i = PA_CIRCULAR_INCREMENT_( i, handlesAndBuffers->bufferCount ); } else break; } } return result; } static PaError AdvanceToNextInputBuffer( PaWinMmeStream *stream ) { PaError result = paNoError; MMRESULT mmresult; unsigned int i; for( i=0; i < stream->input.deviceCount; ++i ) { stream->input.waveHeaders[i][ stream->input.currentBufferIndex ].dwFlags &= ~WHDR_DONE; mmresult = waveInAddBuffer( ((HWAVEIN*)stream->input.waveHandles)[i], &stream->input.waveHeaders[i][ stream->input.currentBufferIndex ], sizeof(WAVEHDR) ); if( mmresult != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); } } stream->input.currentBufferIndex = PA_CIRCULAR_INCREMENT_( stream->input.currentBufferIndex, stream->input.bufferCount ); stream->input.framesUsedInCurrentBuffer = 0; return result; } static PaError AdvanceToNextOutputBuffer( PaWinMmeStream *stream ) { PaError result = paNoError; MMRESULT mmresult; unsigned int i; for( i=0; i < stream->output.deviceCount; ++i ) { mmresult = waveOutWrite( ((HWAVEOUT*)stream->output.waveHandles)[i], &stream->output.waveHeaders[i][ stream->output.currentBufferIndex ], sizeof(WAVEHDR) ); if( mmresult != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ); } } stream->output.currentBufferIndex = PA_CIRCULAR_INCREMENT_( stream->output.currentBufferIndex, stream->output.bufferCount ); stream->output.framesUsedInCurrentBuffer = 0; return result; } /* requeue all but the most recent input with the driver. Used for catching up after a total input buffer underrun */ static PaError CatchUpInputBuffers( PaWinMmeStream *stream ) { PaError result = paNoError; unsigned int i; for( i=0; i < stream->input.bufferCount - 1; ++i ) { result = AdvanceToNextInputBuffer( stream ); if( result != paNoError ) break; } return result; } /* take the most recent output and duplicate it to all other output buffers and requeue them. Used for catching up after a total output buffer underrun. */ static PaError CatchUpOutputBuffers( PaWinMmeStream *stream ) { PaError result = paNoError; unsigned int i, j; unsigned int previousBufferIndex = PA_CIRCULAR_DECREMENT_( stream->output.currentBufferIndex, stream->output.bufferCount ); for( i=0; i < stream->output.bufferCount - 1; ++i ) { for( j=0; j < stream->output.deviceCount; ++j ) { if( stream->output.waveHeaders[j][ stream->output.currentBufferIndex ].lpData != stream->output.waveHeaders[j][ previousBufferIndex ].lpData ) { CopyMemory( stream->output.waveHeaders[j][ stream->output.currentBufferIndex ].lpData, stream->output.waveHeaders[j][ previousBufferIndex ].lpData, stream->output.waveHeaders[j][ stream->output.currentBufferIndex ].dwBufferLength ); } } result = AdvanceToNextOutputBuffer( stream ); if( result != paNoError ) break; } return result; } static DWORD WINAPI ProcessingThreadProc( void *pArg ) { PaWinMmeStream *stream = (PaWinMmeStream *)pArg; HANDLE events[3]; int eventCount = 0; DWORD result = paNoError; DWORD waitResult; DWORD timeout = (unsigned long)(stream->allBuffersDurationMs * 0.5); int hostBuffersAvailable; signed int hostInputBufferIndex, hostOutputBufferIndex; PaStreamCallbackFlags statusFlags; int callbackResult; int done = 0; unsigned int channel, i; unsigned long framesProcessed; /* prepare event array for call to WaitForMultipleObjects() */ if( stream->input.bufferEvent ) events[eventCount++] = stream->input.bufferEvent; if( stream->output.bufferEvent ) events[eventCount++] = stream->output.bufferEvent; events[eventCount++] = stream->abortEvent; statusFlags = 0; /** @todo support paInputUnderflow, paOutputOverflow and paNeverDropInput */ /* loop until something causes us to stop */ do{ /* wait for MME to signal that a buffer is available, or for the PA abort event to be signaled. When this indicates that one or more buffers are available NoBuffersAreQueued() and Current*BuffersAreDone are used below to poll for additional done buffers. NoBuffersAreQueued() will fail to identify an underrun/overflow if the driver doesn't mark all done buffers prior to signalling the event. Some drivers do this (eg RME Digi96, and others don't eg VIA PC 97 input). This isn't a huge problem, it just means that we won't always be able to detect underflow/overflow. */ waitResult = WaitForMultipleObjects( eventCount, events, FALSE /* wait all = FALSE */, timeout ); if( waitResult == WAIT_FAILED ) { result = paUnanticipatedHostError; /** @todo FIXME/REVIEW: can't return host error info from an asyncronous thread */ done = 1; } else if( waitResult == WAIT_TIMEOUT ) { /* if a timeout is encountered, continue */ } if( stream->abortProcessing ) { /* Pa_AbortStream() has been called, stop processing immediately */ done = 1; } else if( stream->stopProcessing ) { /* Pa_StopStream() has been called or the user callback returned non-zero, processing will continue until all output buffers are marked as done. The stream will stop immediately if it is input-only. */ if( PA_IS_OUTPUT_STREAM_(stream) ) { if( NoBuffersAreQueued( &stream->output ) ) done = 1; /* Will cause thread to return. */ } else { /* input only stream */ done = 1; /* Will cause thread to return. */ } } else { hostBuffersAvailable = 1; /* process all available host buffers */ do { hostInputBufferIndex = -1; hostOutputBufferIndex = -1; if( PA_IS_INPUT_STREAM_(stream) ) { if( CurrentInputBuffersAreDone( stream ) ) { if( NoBuffersAreQueued( &stream->input ) ) { /** @todo if all of the other buffers are also ready then we discard all but the most recent. This is an input buffer overflow. FIXME: these buffers should be passed to the callback in a paNeverDropInput stream. note that it is also possible for an input overflow to happen while the callback is processing a buffer. that is handled further down. */ result = CatchUpInputBuffers( stream ); if( result != paNoError ) done = 1; statusFlags |= paInputOverflow; } hostInputBufferIndex = stream->input.currentBufferIndex; } } if( PA_IS_OUTPUT_STREAM_(stream) ) { if( CurrentOutputBuffersAreDone( stream ) ) { /* ok, we have an output buffer */ if( NoBuffersAreQueued( &stream->output ) ) { /* if all of the other buffers are also ready, catch up by copying the most recently generated buffer into all but one of the output buffers. note that this catch up code only handles the case where all buffers have been played out due to this thread not having woken up at all. a more common case occurs when this thread is woken up, processes one buffer, but takes too long, and as a result all the other buffers have become un-queued. that case is handled further down. */ result = CatchUpOutputBuffers( stream ); if( result != paNoError ) done = 1; statusFlags |= paOutputUnderflow; } hostOutputBufferIndex = stream->output.currentBufferIndex; } } if( (PA_IS_FULL_DUPLEX_STREAM_(stream) && hostInputBufferIndex != -1 && hostOutputBufferIndex != -1) || (PA_IS_HALF_DUPLEX_STREAM_(stream) && ( hostInputBufferIndex != -1 || hostOutputBufferIndex != -1 ) ) ) { PaStreamCallbackTimeInfo timeInfo = {0,0,0}; /** @todo implement inputBufferAdcTime */ if( PA_IS_OUTPUT_STREAM_(stream) ) { /* set timeInfo.currentTime and calculate timeInfo.outputBufferDacTime from the current wave out position */ MMTIME mmtime; double timeBeforeGetPosition, timeAfterGetPosition; double time; long framesInBufferRing; long writePosition; long playbackPosition; HWAVEOUT firstWaveOutDevice = ((HWAVEOUT*)stream->output.waveHandles)[0]; mmtime.wType = TIME_SAMPLES; timeBeforeGetPosition = PaUtil_GetTime(); waveOutGetPosition( firstWaveOutDevice, &mmtime, sizeof(MMTIME) ); timeAfterGetPosition = PaUtil_GetTime(); timeInfo.currentTime = timeAfterGetPosition; /* approximate time at which wave out position was measured as half way between timeBeforeGetPosition and timeAfterGetPosition */ time = timeBeforeGetPosition + (timeAfterGetPosition - timeBeforeGetPosition) * .5; framesInBufferRing = stream->output.bufferCount * stream->bufferProcessor.framesPerHostBuffer; playbackPosition = mmtime.u.sample % framesInBufferRing; writePosition = stream->output.currentBufferIndex * stream->bufferProcessor.framesPerHostBuffer + stream->output.framesUsedInCurrentBuffer; if( playbackPosition >= writePosition ){ timeInfo.outputBufferDacTime = time + ((double)( writePosition + (framesInBufferRing - playbackPosition) ) * stream->bufferProcessor.samplePeriod ); }else{ timeInfo.outputBufferDacTime = time + ((double)( writePosition - playbackPosition ) * stream->bufferProcessor.samplePeriod ); } } PaUtil_BeginCpuLoadMeasurement( &stream->cpuLoadMeasurer ); PaUtil_BeginBufferProcessing( &stream->bufferProcessor, &timeInfo, statusFlags ); /* reset status flags once they have been passed to the buffer processor */ statusFlags = 0; if( PA_IS_INPUT_STREAM_(stream) ) { PaUtil_SetInputFrameCount( &stream->bufferProcessor, 0 /* default to host buffer size */ ); channel = 0; for( i=0; iinput.deviceCount; ++i ) { /* we have stored the number of channels in the buffer in dwUser */ int channelCount = (int)stream->input.waveHeaders[i][ hostInputBufferIndex ].dwUser; PaUtil_SetInterleavedInputChannels( &stream->bufferProcessor, channel, stream->input.waveHeaders[i][ hostInputBufferIndex ].lpData + stream->input.framesUsedInCurrentBuffer * channelCount * stream->bufferProcessor.bytesPerHostInputSample, channelCount ); channel += channelCount; } } if( PA_IS_OUTPUT_STREAM_(stream) ) { PaUtil_SetOutputFrameCount( &stream->bufferProcessor, 0 /* default to host buffer size */ ); channel = 0; for( i=0; ioutput.deviceCount; ++i ) { /* we have stored the number of channels in the buffer in dwUser */ int channelCount = (int)stream->output.waveHeaders[i][ hostOutputBufferIndex ].dwUser; PaUtil_SetInterleavedOutputChannels( &stream->bufferProcessor, channel, stream->output.waveHeaders[i][ hostOutputBufferIndex ].lpData + stream->output.framesUsedInCurrentBuffer * channelCount * stream->bufferProcessor.bytesPerHostOutputSample, channelCount ); channel += channelCount; } } callbackResult = paContinue; framesProcessed = PaUtil_EndBufferProcessing( &stream->bufferProcessor, &callbackResult ); stream->input.framesUsedInCurrentBuffer += framesProcessed; stream->output.framesUsedInCurrentBuffer += framesProcessed; PaUtil_EndCpuLoadMeasurement( &stream->cpuLoadMeasurer, framesProcessed ); if( callbackResult == paContinue ) { /* nothing special to do */ } else if( callbackResult == paAbort ) { stream->abortProcessing = 1; done = 1; /** @todo FIXME: should probably reset the output device immediately once the callback returns paAbort */ result = paNoError; } else { /* User callback has asked us to stop with paComplete or other non-zero value */ stream->stopProcessing = 1; /* stop once currently queued audio has finished */ result = paNoError; } if( PA_IS_INPUT_STREAM_(stream) && stream->stopProcessing == 0 && stream->abortProcessing == 0 && stream->input.framesUsedInCurrentBuffer == stream->input.framesPerBuffer ) { if( NoBuffersAreQueued( &stream->input ) ) { /** @todo need to handle PaNeverDropInput here where necessary */ result = CatchUpInputBuffers( stream ); if( result != paNoError ) done = 1; statusFlags |= paInputOverflow; } result = AdvanceToNextInputBuffer( stream ); if( result != paNoError ) done = 1; } if( PA_IS_OUTPUT_STREAM_(stream) && !stream->abortProcessing ) { if( stream->stopProcessing && stream->output.framesUsedInCurrentBuffer < stream->output.framesPerBuffer ) { /* zero remaining samples in output output buffer and flush */ stream->output.framesUsedInCurrentBuffer += PaUtil_ZeroOutput( &stream->bufferProcessor, stream->output.framesPerBuffer - stream->output.framesUsedInCurrentBuffer ); /* we send the entire buffer to the output devices, but we could just send a partial buffer, rather than zeroing the unused samples. */ } if( stream->output.framesUsedInCurrentBuffer == stream->output.framesPerBuffer ) { /* check for underflow before enquing the just-generated buffer, but recover from underflow after enquing it. This ensures that the most recent audio segment is repeated */ int outputUnderflow = NoBuffersAreQueued( &stream->output ); result = AdvanceToNextOutputBuffer( stream ); if( result != paNoError ) done = 1; if( outputUnderflow && !done && !stream->stopProcessing ) { /* Recover from underflow in the case where the underflow occured while processing the buffer we just finished */ result = CatchUpOutputBuffers( stream ); if( result != paNoError ) done = 1; statusFlags |= paOutputUnderflow; } } } if( stream->throttleProcessingThreadOnOverload != 0 ) { if( stream->stopProcessing || stream->abortProcessing ) { if( stream->processingThreadPriority != stream->highThreadPriority ) { SetThreadPriority( stream->processingThread, stream->highThreadPriority ); stream->processingThreadPriority = stream->highThreadPriority; } } else if( PaUtil_GetCpuLoad( &stream->cpuLoadMeasurer ) > 1. ) { if( stream->processingThreadPriority != stream->throttledThreadPriority ) { SetThreadPriority( stream->processingThread, stream->throttledThreadPriority ); stream->processingThreadPriority = stream->throttledThreadPriority; } /* sleep to give other processes a go */ Sleep( stream->throttledSleepMsecs ); } else { if( stream->processingThreadPriority != stream->highThreadPriority ) { SetThreadPriority( stream->processingThread, stream->highThreadPriority ); stream->processingThreadPriority = stream->highThreadPriority; } } } } else { hostBuffersAvailable = 0; } } while( hostBuffersAvailable && stream->stopProcessing == 0 && stream->abortProcessing == 0 && !done ); } } while( !done ); stream->isActive = 0; if( stream->streamRepresentation.streamFinishedCallback != 0 ) stream->streamRepresentation.streamFinishedCallback( stream->streamRepresentation.userData ); PaUtil_ResetCpuLoadMeasurer( &stream->cpuLoadMeasurer ); return result; } /* When CloseStream() is called, the multi-api layer ensures that the stream has already been stopped or aborted. */ static PaError CloseStream( PaStream* s ) { PaError result; PaWinMmeStream *stream = (PaWinMmeStream*)s; result = CloseHandleWithPaError( stream->abortEvent ); if( result != paNoError ) goto error; TerminateWaveHeaders( &stream->output, 0 /* not isInput */ ); TerminateWaveHeaders( &stream->input, 1 /* isInput */ ); TerminateWaveHandles( &stream->output, 0 /* not isInput */, 0 /* not currentlyProcessingAnError */ ); TerminateWaveHandles( &stream->input, 1 /* isInput */, 0 /* not currentlyProcessingAnError */ ); PaUtil_TerminateBufferProcessor( &stream->bufferProcessor ); PaUtil_TerminateStreamRepresentation( &stream->streamRepresentation ); PaUtil_FreeMemory( stream ); error: /** @todo REVIEW: what is the best way to clean up a stream if an error is detected? */ return result; } static PaError StartStream( PaStream *s ) { PaError result; PaWinMmeStream *stream = (PaWinMmeStream*)s; MMRESULT mmresult; unsigned int i, j; int callbackResult; unsigned int channel; unsigned long framesProcessed; PaStreamCallbackTimeInfo timeInfo = {0,0,0}; /** @todo implement this for stream priming */ PaUtil_ResetBufferProcessor( &stream->bufferProcessor ); if( PA_IS_INPUT_STREAM_(stream) ) { for( i=0; iinput.bufferCount; ++i ) { for( j=0; jinput.deviceCount; ++j ) { stream->input.waveHeaders[j][i].dwFlags &= ~WHDR_DONE; mmresult = waveInAddBuffer( ((HWAVEIN*)stream->input.waveHandles)[j], &stream->input.waveHeaders[j][i], sizeof(WAVEHDR) ); if( mmresult != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); goto error; } } } stream->input.currentBufferIndex = 0; stream->input.framesUsedInCurrentBuffer = 0; } if( PA_IS_OUTPUT_STREAM_(stream) ) { for( i=0; ioutput.deviceCount; ++i ) { if( (mmresult = waveOutPause( ((HWAVEOUT*)stream->output.waveHandles)[i] )) != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ); goto error; } } for( i=0; ioutput.bufferCount; ++i ) { if( stream->primeStreamUsingCallback ) { stream->output.framesUsedInCurrentBuffer = 0; do{ PaUtil_BeginBufferProcessing( &stream->bufferProcessor, &timeInfo, paPrimingOutput | ((stream->input.bufferCount > 0 ) ? paInputUnderflow : 0)); if( stream->input.bufferCount > 0 ) PaUtil_SetNoInput( &stream->bufferProcessor ); PaUtil_SetOutputFrameCount( &stream->bufferProcessor, 0 /* default to host buffer size */ ); channel = 0; for( j=0; joutput.deviceCount; ++j ) { /* we have stored the number of channels in the buffer in dwUser */ int channelCount = (int)stream->output.waveHeaders[j][i].dwUser; PaUtil_SetInterleavedOutputChannels( &stream->bufferProcessor, channel, stream->output.waveHeaders[j][i].lpData + stream->output.framesUsedInCurrentBuffer * channelCount * stream->bufferProcessor.bytesPerHostOutputSample, channelCount ); /* we have stored the number of channels in the buffer in dwUser */ channel += channelCount; } callbackResult = paContinue; framesProcessed = PaUtil_EndBufferProcessing( &stream->bufferProcessor, &callbackResult ); stream->output.framesUsedInCurrentBuffer += framesProcessed; if( callbackResult != paContinue ) { /** @todo fix this, what do we do if callback result is non-zero during stream priming? for complete: play out primed waveHeaders as usual for abort: clean up immediately. */ } }while( stream->output.framesUsedInCurrentBuffer != stream->output.framesPerBuffer ); } else { for( j=0; joutput.deviceCount; ++j ) { ZeroMemory( stream->output.waveHeaders[j][i].lpData, stream->output.waveHeaders[j][i].dwBufferLength ); } } /* we queue all channels of a single buffer frame (accross all devices, because some multidevice multichannel drivers work better this way */ for( j=0; joutput.deviceCount; ++j ) { mmresult = waveOutWrite( ((HWAVEOUT*)stream->output.waveHandles)[j], &stream->output.waveHeaders[j][i], sizeof(WAVEHDR) ); if( mmresult != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ); goto error; } } } stream->output.currentBufferIndex = 0; stream->output.framesUsedInCurrentBuffer = 0; } stream->isStopped = 0; stream->isActive = 1; stream->stopProcessing = 0; stream->abortProcessing = 0; result = ResetEventWithPaError( stream->input.bufferEvent ); if( result != paNoError ) goto error; result = ResetEventWithPaError( stream->output.bufferEvent ); if( result != paNoError ) goto error; if( stream->streamRepresentation.streamCallback ) { /* callback stream */ result = ResetEventWithPaError( stream->abortEvent ); if( result != paNoError ) goto error; /* Create thread that waits for audio buffers to be ready for processing. */ stream->processingThread = CreateThread( 0, 0, ProcessingThreadProc, stream, 0, &stream->processingThreadId ); if( !stream->processingThread ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_SYSTEM_ERROR( GetLastError() ); goto error; } /** @todo could have mme specific stream parameters to allow the user to set the callback thread priorities */ stream->highThreadPriority = THREAD_PRIORITY_TIME_CRITICAL; stream->throttledThreadPriority = THREAD_PRIORITY_NORMAL; if( !SetThreadPriority( stream->processingThread, stream->highThreadPriority ) ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_SYSTEM_ERROR( GetLastError() ); goto error; } stream->processingThreadPriority = stream->highThreadPriority; } else { /* blocking read/write stream */ } if( PA_IS_INPUT_STREAM_(stream) ) { for( i=0; i < stream->input.deviceCount; ++i ) { mmresult = waveInStart( ((HWAVEIN*)stream->input.waveHandles)[i] ); PA_DEBUG(("Pa_StartStream: waveInStart returned = 0x%X.\n", mmresult)); if( mmresult != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); goto error; } } } if( PA_IS_OUTPUT_STREAM_(stream) ) { for( i=0; i < stream->output.deviceCount; ++i ) { if( (mmresult = waveOutRestart( ((HWAVEOUT*)stream->output.waveHandles)[i] )) != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ); goto error; } } } return result; error: /** @todo FIXME: implement recovery as best we can This should involve rolling back to a state as-if this function had never been called */ return result; } static PaError StopStream( PaStream *s ) { PaError result = paNoError; PaWinMmeStream *stream = (PaWinMmeStream*)s; int timeout; DWORD waitResult; MMRESULT mmresult; signed int hostOutputBufferIndex; unsigned int channel, waitCount, i; /** @todo REVIEW: the error checking in this function needs review. the basic idea is to return from this function in a known state - for example there is no point avoiding calling waveInReset just because the thread times out. */ if( stream->processingThread ) { /* callback stream */ /* Tell processing thread to stop generating more data and to let current data play out. */ stream->stopProcessing = 1; /* Calculate timeOut longer than longest time it could take to return all buffers. */ timeout = (int)(stream->allBuffersDurationMs * 1.5); if( timeout < PA_MME_MIN_TIMEOUT_MSEC_ ) timeout = PA_MME_MIN_TIMEOUT_MSEC_; PA_DEBUG(("WinMME StopStream: waiting for background thread.\n")); waitResult = WaitForSingleObject( stream->processingThread, timeout ); if( waitResult == WAIT_TIMEOUT ) { /* try to abort */ stream->abortProcessing = 1; SetEvent( stream->abortEvent ); waitResult = WaitForSingleObject( stream->processingThread, timeout ); if( waitResult == WAIT_TIMEOUT ) { PA_DEBUG(("WinMME StopStream: timed out while waiting for background thread to finish.\n")); result = paTimedOut; } } CloseHandle( stream->processingThread ); stream->processingThread = NULL; } else { /* blocking read / write stream */ if( PA_IS_OUTPUT_STREAM_(stream) ) { if( stream->output.framesUsedInCurrentBuffer > 0 ) { /* there are still unqueued frames in the current buffer, so flush them */ hostOutputBufferIndex = stream->output.currentBufferIndex; PaUtil_SetOutputFrameCount( &stream->bufferProcessor, stream->output.framesPerBuffer - stream->output.framesUsedInCurrentBuffer ); channel = 0; for( i=0; ioutput.deviceCount; ++i ) { /* we have stored the number of channels in the buffer in dwUser */ int channelCount = (int)stream->output.waveHeaders[i][ hostOutputBufferIndex ].dwUser; PaUtil_SetInterleavedOutputChannels( &stream->bufferProcessor, channel, stream->output.waveHeaders[i][ hostOutputBufferIndex ].lpData + stream->output.framesUsedInCurrentBuffer * channelCount * stream->bufferProcessor.bytesPerHostOutputSample, channelCount ); channel += channelCount; } PaUtil_ZeroOutput( &stream->bufferProcessor, stream->output.framesPerBuffer - stream->output.framesUsedInCurrentBuffer ); /* we send the entire buffer to the output devices, but we could just send a partial buffer, rather than zeroing the unused samples. */ AdvanceToNextOutputBuffer( stream ); } timeout = (stream->allBuffersDurationMs / stream->output.bufferCount) + 1; if( timeout < PA_MME_MIN_TIMEOUT_MSEC_ ) timeout = PA_MME_MIN_TIMEOUT_MSEC_; waitCount = 0; while( !NoBuffersAreQueued( &stream->output ) && waitCount <= stream->output.bufferCount ) { /* wait for MME to signal that a buffer is available */ waitResult = WaitForSingleObject( stream->output.bufferEvent, timeout ); if( waitResult == WAIT_FAILED ) { break; } else if( waitResult == WAIT_TIMEOUT ) { /* keep waiting */ } ++waitCount; } } } if( PA_IS_OUTPUT_STREAM_(stream) ) { for( i =0; i < stream->output.deviceCount; ++i ) { mmresult = waveOutReset( ((HWAVEOUT*)stream->output.waveHandles)[i] ); if( mmresult != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ); } } } if( PA_IS_INPUT_STREAM_(stream) ) { for( i=0; i < stream->input.deviceCount; ++i ) { mmresult = waveInReset( ((HWAVEIN*)stream->input.waveHandles)[i] ); if( mmresult != MMSYSERR_NOERROR ) { result = paUnanticipatedHostError; PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); } } } stream->isStopped = 1; stream->isActive = 0; return result; } static PaError AbortStream( PaStream *s ) { PaError result = paNoError; PaWinMmeStream *stream = (PaWinMmeStream*)s; int timeout; DWORD waitResult; MMRESULT mmresult; unsigned int i; /** @todo REVIEW: the error checking in this function needs review. the basic idea is to return from this function in a known state - for example there is no point avoiding calling waveInReset just because the thread times out. */ if( stream->processingThread ) { /* callback stream */ /* Tell processing thread to abort immediately */ stream->abortProcessing = 1; SetEvent( stream->abortEvent ); } if( PA_IS_OUTPUT_STREAM_(stream) ) { for( i =0; i < stream->output.deviceCount; ++i ) { mmresult = waveOutReset( ((HWAVEOUT*)stream->output.waveHandles)[i] ); if( mmresult != MMSYSERR_NOERROR ) { PA_MME_SET_LAST_WAVEOUT_ERROR( mmresult ); return paUnanticipatedHostError; } } } if( PA_IS_INPUT_STREAM_(stream) ) { for( i=0; i < stream->input.deviceCount; ++i ) { mmresult = waveInReset( ((HWAVEIN*)stream->input.waveHandles)[i] ); if( mmresult != MMSYSERR_NOERROR ) { PA_MME_SET_LAST_WAVEIN_ERROR( mmresult ); return paUnanticipatedHostError; } } } if( stream->processingThread ) { /* callback stream */ PA_DEBUG(("WinMME AbortStream: waiting for background thread.\n")); /* Calculate timeOut longer than longest time it could take to return all buffers. */ timeout = (int)(stream->allBuffersDurationMs * 1.5); if( timeout < PA_MME_MIN_TIMEOUT_MSEC_ ) timeout = PA_MME_MIN_TIMEOUT_MSEC_; waitResult = WaitForSingleObject( stream->processingThread, timeout ); if( waitResult == WAIT_TIMEOUT ) { PA_DEBUG(("WinMME AbortStream: timed out while waiting for background thread to finish.\n")); return paTimedOut; } CloseHandle( stream->processingThread ); stream->processingThread = NULL; } stream->isStopped = 1; stream->isActive = 0; return result; } static PaError IsStreamStopped( PaStream *s ) { PaWinMmeStream *stream = (PaWinMmeStream*)s; return stream->isStopped; } static PaError IsStreamActive( PaStream *s ) { PaWinMmeStream *stream = (PaWinMmeStream*)s; return stream->isActive; } static PaTime GetStreamTime( PaStream *s ) { (void) s; /* unused parameter */ return PaUtil_GetTime(); } static double GetStreamCpuLoad( PaStream* s ) { PaWinMmeStream *stream = (PaWinMmeStream*)s; return PaUtil_GetCpuLoad( &stream->cpuLoadMeasurer ); } /* As separate stream interfaces are used for blocking and callback streams, the following functions can be guaranteed to only be called for blocking streams. */ static PaError ReadStream( PaStream* s, void *buffer, unsigned long frames ) { PaError result = paNoError; PaWinMmeStream *stream = (PaWinMmeStream*)s; void *userBuffer; unsigned long framesRead = 0; unsigned long framesProcessed; signed int hostInputBufferIndex; DWORD waitResult; DWORD timeout = (unsigned long)(stream->allBuffersDurationMs * 0.5); unsigned int channel, i; if( PA_IS_INPUT_STREAM_(stream) ) { /* make a local copy of the user buffer pointer(s). this is necessary because PaUtil_CopyInput() advances these pointers every time it is called. */ if( stream->bufferProcessor.userInputIsInterleaved ) { userBuffer = buffer; } else { userBuffer = alloca( sizeof(void*) * stream->bufferProcessor.inputChannelCount ); if( !userBuffer ) return paInsufficientMemory; for( i = 0; ibufferProcessor.inputChannelCount; ++i ) ((void**)userBuffer)[i] = ((void**)buffer)[i]; } do{ if( CurrentInputBuffersAreDone( stream ) ) { if( NoBuffersAreQueued( &stream->input ) ) { /** @todo REVIEW: consider what to do if the input overflows. do we requeue all of the buffers? should we be running a thread to make sure they are always queued? */ result = paInputOverflowed; } hostInputBufferIndex = stream->input.currentBufferIndex; PaUtil_SetInputFrameCount( &stream->bufferProcessor, stream->input.framesPerBuffer - stream->input.framesUsedInCurrentBuffer ); channel = 0; for( i=0; iinput.deviceCount; ++i ) { /* we have stored the number of channels in the buffer in dwUser */ int channelCount = (int)stream->input.waveHeaders[i][ hostInputBufferIndex ].dwUser; PaUtil_SetInterleavedInputChannels( &stream->bufferProcessor, channel, stream->input.waveHeaders[i][ hostInputBufferIndex ].lpData + stream->input.framesUsedInCurrentBuffer * channelCount * stream->bufferProcessor.bytesPerHostInputSample, channelCount ); channel += channelCount; } framesProcessed = PaUtil_CopyInput( &stream->bufferProcessor, &userBuffer, frames - framesRead ); stream->input.framesUsedInCurrentBuffer += framesProcessed; if( stream->input.framesUsedInCurrentBuffer == stream->input.framesPerBuffer ) { result = AdvanceToNextInputBuffer( stream ); if( result != paNoError ) break; } framesRead += framesProcessed; }else{ /* wait for MME to signal that a buffer is available */ waitResult = WaitForSingleObject( stream->input.bufferEvent, timeout ); if( waitResult == WAIT_FAILED ) { result = paUnanticipatedHostError; break; } else if( waitResult == WAIT_TIMEOUT ) { /* if a timeout is encountered, continue, perhaps we should give up eventually */ } } }while( framesRead < frames ); } else { result = paCanNotReadFromAnOutputOnlyStream; } return result; } static PaError WriteStream( PaStream* s, const void *buffer, unsigned long frames ) { PaError result = paNoError; PaWinMmeStream *stream = (PaWinMmeStream*)s; const void *userBuffer; unsigned long framesWritten = 0; unsigned long framesProcessed; signed int hostOutputBufferIndex; DWORD waitResult; DWORD timeout = (unsigned long)(stream->allBuffersDurationMs * 0.5); unsigned int channel, i; if( PA_IS_OUTPUT_STREAM_(stream) ) { /* make a local copy of the user buffer pointer(s). this is necessary because PaUtil_CopyOutput() advances these pointers every time it is called. */ if( stream->bufferProcessor.userOutputIsInterleaved ) { userBuffer = buffer; } else { userBuffer = alloca( sizeof(void*) * stream->bufferProcessor.outputChannelCount ); if( !userBuffer ) return paInsufficientMemory; for( i = 0; ibufferProcessor.outputChannelCount; ++i ) ((const void**)userBuffer)[i] = ((const void**)buffer)[i]; } do{ if( CurrentOutputBuffersAreDone( stream ) ) { if( NoBuffersAreQueued( &stream->output ) ) { /** @todo REVIEW: consider what to do if the output underflows. do we requeue all the existing buffers with zeros? should we run a separate thread to keep the buffers enqueued at all times? */ result = paOutputUnderflowed; } hostOutputBufferIndex = stream->output.currentBufferIndex; PaUtil_SetOutputFrameCount( &stream->bufferProcessor, stream->output.framesPerBuffer - stream->output.framesUsedInCurrentBuffer ); channel = 0; for( i=0; ioutput.deviceCount; ++i ) { /* we have stored the number of channels in the buffer in dwUser */ int channelCount = (int)stream->output.waveHeaders[i][ hostOutputBufferIndex ].dwUser; PaUtil_SetInterleavedOutputChannels( &stream->bufferProcessor, channel, stream->output.waveHeaders[i][ hostOutputBufferIndex ].lpData + stream->output.framesUsedInCurrentBuffer * channelCount * stream->bufferProcessor.bytesPerHostOutputSample, channelCount ); channel += channelCount; } framesProcessed = PaUtil_CopyOutput( &stream->bufferProcessor, &userBuffer, frames - framesWritten ); stream->output.framesUsedInCurrentBuffer += framesProcessed; if( stream->output.framesUsedInCurrentBuffer == stream->output.framesPerBuffer ) { result = AdvanceToNextOutputBuffer( stream ); if( result != paNoError ) break; } framesWritten += framesProcessed; } else { /* wait for MME to signal that a buffer is available */ waitResult = WaitForSingleObject( stream->output.bufferEvent, timeout ); if( waitResult == WAIT_FAILED ) { result = paUnanticipatedHostError; break; } else if( waitResult == WAIT_TIMEOUT ) { /* if a timeout is encountered, continue, perhaps we should give up eventually */ } } }while( framesWritten < frames ); } else { result = paCanNotWriteToAnInputOnlyStream; } return result; } static signed long GetStreamReadAvailable( PaStream* s ) { PaWinMmeStream *stream = (PaWinMmeStream*)s; if( PA_IS_INPUT_STREAM_(stream) ) return GetAvailableFrames( &stream->input ); else return paCanNotReadFromAnOutputOnlyStream; } static signed long GetStreamWriteAvailable( PaStream* s ) { PaWinMmeStream *stream = (PaWinMmeStream*)s; if( PA_IS_OUTPUT_STREAM_(stream) ) return GetAvailableFrames( &stream->output ); else return paCanNotWriteToAnInputOnlyStream; } /* NOTE: the following functions are MME-stream specific, and are called directly by client code. We need to check for many more error conditions here because we don't have the benefit of pa_front.c's parameter checking. */ static PaError GetWinMMEStreamPointer( PaWinMmeStream **stream, PaStream *s ) { PaError result; PaUtilHostApiRepresentation *hostApi; PaWinMmeHostApiRepresentation *winMmeHostApi; result = PaUtil_ValidateStreamPointer( s ); if( result != paNoError ) return result; result = PaUtil_GetHostApiRepresentation( &hostApi, paMME ); if( result != paNoError ) return result; winMmeHostApi = (PaWinMmeHostApiRepresentation*)hostApi; /* note, the following would be easier if there was a generic way of testing that a stream belongs to a specific host API */ if( PA_STREAM_REP( s )->streamInterface == &winMmeHostApi->callbackStreamInterface || PA_STREAM_REP( s )->streamInterface == &winMmeHostApi->blockingStreamInterface ) { /* s is a WinMME stream */ *stream = (PaWinMmeStream *)s; return paNoError; } else { return paIncompatibleStreamHostApi; } } int PaWinMME_GetStreamInputHandleCount( PaStream* s ) { PaWinMmeStream *stream; PaError result = GetWinMMEStreamPointer( &stream, s ); if( result == paNoError ) return (PA_IS_INPUT_STREAM_(stream)) ? stream->input.deviceCount : 0; else return result; } HWAVEIN PaWinMME_GetStreamInputHandle( PaStream* s, int handleIndex ) { PaWinMmeStream *stream; PaError result = GetWinMMEStreamPointer( &stream, s ); if( result == paNoError && PA_IS_INPUT_STREAM_(stream) && handleIndex >= 0 && (unsigned int)handleIndex < stream->input.deviceCount ) return ((HWAVEIN*)stream->input.waveHandles)[handleIndex]; else return 0; } int PaWinMME_GetStreamOutputHandleCount( PaStream* s) { PaWinMmeStream *stream; PaError result = GetWinMMEStreamPointer( &stream, s ); if( result == paNoError ) return (PA_IS_OUTPUT_STREAM_(stream)) ? stream->output.deviceCount : 0; else return result; } HWAVEOUT PaWinMME_GetStreamOutputHandle( PaStream* s, int handleIndex ) { PaWinMmeStream *stream; PaError result = GetWinMMEStreamPointer( &stream, s ); if( result == paNoError && PA_IS_OUTPUT_STREAM_(stream) && handleIndex >= 0 && (unsigned int)handleIndex < stream->output.deviceCount ) return ((HWAVEOUT*)stream->output.waveHandles)[handleIndex]; else return 0; } #endif sources_5316/external/portaudio/pa_mac_core.h0000644000176700017670000001514711755011202020156 0ustar paulpaul#ifndef PA_MAC_CORE_H #define PA_MAC_CORE_H /* * PortAudio Portable Real-Time Audio Library * Macintosh Core Audio specific extensions * portaudio.h should be included before this file. * * Copyright (c) 2005-2006 Bjorn Roche * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ #include #include #ifdef __cplusplus extern "C" { #endif /* * A pointer to a paMacCoreStreamInfo may be passed as * the hostApiSpecificStreamInfo in the PaStreamParameters struct * when opening a stream or querying the format. Use NULL, for the * defaults. Note that for duplex streams, flags for input and output * should be the same or behaviour is undefined. */ typedef struct { unsigned long size; /**size of whole structure including this header */ PaHostApiTypeId hostApiType; /**host API for which this data is intended */ unsigned long version; /**structure version */ unsigned long flags; /* flags to modify behaviour */ SInt32 const * channelMap; /* Channel map for HAL channel mapping , if not needed, use NULL;*/ unsigned long channelMapSize; /* Channel map size for HAL channel mapping , if not needed, use 0;*/ } PaMacCoreStreamInfo; /* * Functions */ /* Use this function to initialize a paMacCoreStreamInfo struct * using the requested flags. Note that channel mapping is turned * off after a call to this function. * @param data The datastructure to initialize * @param flags The flags to initialize the datastructure with. */ void PaMacCore_SetupStreamInfo( PaMacCoreStreamInfo *data, unsigned long flags ); /* call this after pa_SetupMacCoreStreamInfo to use channel mapping as described in notes.txt. * @param data The stream info structure to assign a channel mapping to * @param channelMap The channel map array, as described in notes.txt. This array pointer will be used directly (ie the underlying data will not be copied), so the caller should not free the array until after the stream has been opened. * @param channelMapSize The size of the channel map array. */ void PaMacCore_SetupChannelMap( PaMacCoreStreamInfo *data, const SInt32 * const channelMap, unsigned long channelMapSize ); /* * Retrieve the AudioDeviceID of the input device assigned to an open stream * * @param s The stream to query. * * @return A valid AudioDeviceID, or NULL if an error occurred. */ AudioDeviceID PaMacCore_GetStreamInputDevice( PaStream* s ); /* * Retrieve the AudioDeviceID of the output device assigned to an open stream * * @param s The stream to query. * * @return A valid AudioDeviceID, or NULL if an error occurred. */ AudioDeviceID PaMacCore_GetStreamOutputDevice( PaStream* s ); /* * Returns a statically allocated string with the device's name * for the given channel. NULL will be returned on failure. * * This function's implemenation is not complete! * * @param device The PortAudio device index. * @param channel The channel number who's name is requested. * @return a statically allocated string with the name of the device. * Because this string is statically allocated, it must be * coppied if it is to be saved and used by the user after * another call to this function. * */ const char *PaMacCore_GetChannelName( int device, int channelIndex, bool input ); /* * Flags */ /* * The following flags alter the behaviour of PA on the mac platform. * they can be ORed together. These should work both for opening and * checking a device. */ /* Allows PortAudio to change things like the device's frame size, * which allows for much lower latency, but might disrupt the device * if other programs are using it, even when you are just Querying * the device. */ #define paMacCoreChangeDeviceParameters (0x01) /* In combination with the above flag, * causes the stream opening to fail, unless the exact sample rates * are supported by the device. */ #define paMacCoreFailIfConversionRequired (0x02) /* These flags set the SR conversion quality, if required. The wierd ordering * allows Maximum Quality to be the default.*/ #define paMacCoreConversionQualityMin (0x0100) #define paMacCoreConversionQualityMedium (0x0200) #define paMacCoreConversionQualityLow (0x0300) #define paMacCoreConversionQualityHigh (0x0400) #define paMacCoreConversionQualityMax (0x0000) /* * Here are some "preset" combinations of flags (above) to get to some * common configurations. THIS IS OVERKILL, but if more flags are added * it won't be. */ /*This is the default setting: do as much sample rate conversion as possible * and as little mucking with the device as possible. */ #define paMacCorePlayNice (0x00) /*This setting is tuned for pro audio apps. It allows SR conversion on input and output, but it tries to set the appropriate SR on the device.*/ #define paMacCorePro (0x01) /*This is a setting to minimize CPU usage and still play nice.*/ #define paMacCoreMinimizeCPUButPlayNice (0x0100) /*This is a setting to minimize CPU usage, even if that means interrupting the device. */ #define paMacCoreMinimizeCPU (0x0101) #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_MAC_CORE_H */ sources_5316/external/portaudio/pa_win_util.c0000644000176700017670000000740211630755154020243 0ustar paulpaul#ifdef _WIN32 /* * $Id: pa_win_util.c 1197 2007-05-04 13:07:10Z gordon_gidluck $ * Portable Audio I/O Library * Win32 platform-specific support functions * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2000 Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup win_src Win32 platform-specific support functions. @todo Implement workaround for QueryPerformanceCounter() skipping forward bug. (see msdn kb Q274323). */ #undef UNICODE #include #include /* for timeGetTime() */ #include "pa_util.h" /* Track memory allocations to avoid leaks. */ #if PA_TRACK_MEMORY static int numAllocations_ = 0; #endif void *PaUtil_AllocateMemory( long size ) { void *result = GlobalAlloc( GPTR, size ); #if PA_TRACK_MEMORY if( result != NULL ) numAllocations_ += 1; #endif return result; } void PaUtil_FreeMemory( void *block ) { if( block != NULL ) { GlobalFree( block ); #if PA_TRACK_MEMORY numAllocations_ -= 1; #endif } } int PaUtil_CountCurrentlyAllocatedBlocks( void ) { #if PA_TRACK_MEMORY return numAllocations_; #else return 0; #endif } void Pa_Sleep( long msec ) { Sleep( msec ); } static int usePerformanceCounter_; static double secondsPerTick_; void PaUtil_InitializeClock( void ) { LARGE_INTEGER ticksPerSecond; if( QueryPerformanceFrequency( &ticksPerSecond ) != 0 ) { usePerformanceCounter_ = 1; secondsPerTick_ = 1.0 / (double)ticksPerSecond.QuadPart; } else { usePerformanceCounter_ = 0; } } double PaUtil_GetTime( void ) { LARGE_INTEGER time; if( usePerformanceCounter_ ) { /* FIXME: according to this knowledge-base article, QueryPerformanceCounter can skip forward by seconds! http://support.microsoft.com/default.aspx?scid=KB;EN-US;Q274323& it may be better to use the rtdsc instruction using inline asm, however then a method is needed to calculate a ticks/seconds ratio. */ QueryPerformanceCounter( &time ); return time.QuadPart * secondsPerTick_; } else { #ifndef UNDER_CE return timeGetTime() * .001; #else return GetTickCount() * .001; #endif } } #endif sources_5316/external/portaudio/pa_win_ds_dynlink.h0000644000176700017670000000633410673064035021431 0ustar paulpaul/* * Interface for dynamically loading directsound and providing a dummy * implementation if it isn't present. * * Author: Ross Bencina (some portions Phil Burk & Robert Marsanyi) * * For PortAudio Portable Real-Time Audio Library * For more information see: http://www.portaudio.com * Copyright (c) 1999-2006 Phil Burk, Robert Marsanyi and Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostaip_src */ #ifndef INCLUDED_PA_DSOUND_DYNLINK_H #define INCLUDED_PA_DSOUND_DYNLINK_H /* on Borland compilers, WIN32 doesn't seem to be defined by default, which breaks dsound.h. Adding the define here fixes the problem. - rossb. */ #ifdef __BORLANDC__ #if !defined(WIN32) #define WIN32 #endif #endif /* We are only using DX3 in here, no need to polute the namespace - davidv */ #define DIRECTSOUND_VERSION 0x0300 #include #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ typedef struct { HINSTANCE hInstance_; HRESULT (WINAPI *DllGetClassObject)(REFCLSID , REFIID , LPVOID *); HRESULT (WINAPI *DirectSoundCreate)(LPGUID, LPDIRECTSOUND *, LPUNKNOWN); HRESULT (WINAPI *DirectSoundEnumerateW)(LPDSENUMCALLBACKW, LPVOID); HRESULT (WINAPI *DirectSoundEnumerateA)(LPDSENUMCALLBACKA, LPVOID); HRESULT (WINAPI *DirectSoundCaptureCreate)(LPGUID, LPDIRECTSOUNDCAPTURE *, LPUNKNOWN); HRESULT (WINAPI *DirectSoundCaptureEnumerateW)(LPDSENUMCALLBACKW, LPVOID); HRESULT (WINAPI *DirectSoundCaptureEnumerateA)(LPDSENUMCALLBACKA, LPVOID); }PaWinDsDSoundEntryPoints; extern PaWinDsDSoundEntryPoints paWinDsDSoundEntryPoints; void PaWinDs_InitializeDSoundEntryPoints(void); void PaWinDs_TerminateDSoundEntryPoints(void); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* INCLUDED_PA_DSOUND_DYNLINK_H */ sources_5316/external/portaudio/pa_unix_util.h0000644000176700017670000001737611474736145020456 0ustar paulpaul/* * $Id: pa_unix_util.h 1241 2007-07-23 20:08:31Z aknudsen $ * Portable Audio I/O Library * UNIX platform-specific support functions * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2000 Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup unix_src */ #ifndef PA_UNIX_UTIL_H #define PA_UNIX_UTIL_H #include "pa_cpuload.h" #include #include #include #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ #define PA_MIN(x,y) ( (x) < (y) ? (x) : (y) ) #define PA_MAX(x,y) ( (x) > (y) ? (x) : (y) ) /* Utilize GCC branch prediction for error tests */ #if defined __GNUC__ && __GNUC__ >= 3 #define UNLIKELY(expr) __builtin_expect( (expr), 0 ) #else #define UNLIKELY(expr) (expr) #endif #define STRINGIZE_HELPER(expr) #expr #define STRINGIZE(expr) STRINGIZE_HELPER(expr) #define PA_UNLESS(expr, code) \ do { \ if( UNLIKELY( (expr) == 0 ) ) \ { \ PaUtil_DebugPrint(( "Expression '" #expr "' failed in '" __FILE__ "', line: " STRINGIZE( __LINE__ ) "\n" )); \ result = (code); \ goto error; \ } \ } while (0); static PaError paUtilErr_; /* Used with PA_ENSURE */ /* Check PaError */ #define PA_ENSURE(expr) \ do { \ if( UNLIKELY( (paUtilErr_ = (expr)) < paNoError ) ) \ { \ PaUtil_DebugPrint(( "Expression '" #expr "' failed in '" __FILE__ "', line: " STRINGIZE( __LINE__ ) "\n" )); \ result = paUtilErr_; \ goto error; \ } \ } while (0); #define PA_ASSERT_CALL(expr, success) \ paUtilErr_ = (expr); \ assert( success == paUtilErr_ ); #define PA_ENSURE_SYSTEM(expr, success) \ do { \ if( UNLIKELY( (paUtilErr_ = (expr)) != success ) ) \ { \ /* PaUtil_SetLastHostErrorInfo should only be used in the main thread */ \ if( pthread_equal(pthread_self(), paUnixMainThread) ) \ { \ PaUtil_SetLastHostErrorInfo( paALSA, paUtilErr_, strerror( paUtilErr_ ) ); \ } \ PaUtil_DebugPrint( "Expression '" #expr "' failed in '" __FILE__ "', line: " STRINGIZE( __LINE__ ) "\n" ); \ result = paUnanticipatedHostError; \ goto error; \ } \ } while( 0 ); typedef struct { pthread_t callbackThread; } PaUtilThreading; PaError PaUtil_InitializeThreading( PaUtilThreading *threading ); void PaUtil_TerminateThreading( PaUtilThreading *threading ); PaError PaUtil_StartThreading( PaUtilThreading *threading, void *(*threadRoutine)(void *), void *data ); PaError PaUtil_CancelThreading( PaUtilThreading *threading, int wait, PaError *exitResult ); /* State accessed by utility functions */ /* void PaUnix_SetRealtimeScheduling( int rt ); void PaUtil_InitializeThreading( PaUtilThreading *th, PaUtilCpuLoadMeasurer *clm ); PaError PaUtil_CreateCallbackThread( PaUtilThreading *th, void *(*CallbackThreadFunc)( void * ), PaStream *s ); PaError PaUtil_KillCallbackThread( PaUtilThreading *th, PaError *exitResult ); void PaUtil_CallbackUpdate( PaUtilThreading *th ); */ extern pthread_t paUnixMainThread; typedef struct { pthread_mutex_t mtx; } PaUnixMutex; PaError PaUnixMutex_Initialize( PaUnixMutex* self ); PaError PaUnixMutex_Terminate( PaUnixMutex* self ); PaError PaUnixMutex_Lock( PaUnixMutex* self ); PaError PaUnixMutex_Unlock( PaUnixMutex* self ); typedef struct { pthread_t thread; int parentWaiting; int stopRequested; int locked; PaUnixMutex mtx; pthread_cond_t cond; volatile sig_atomic_t stopRequest; } PaUnixThread; /** Initialize global threading state. */ PaError PaUnixThreading_Initialize( void ); /** Perish, passing on eventual error code. * * A thin wrapper around pthread_exit, will automatically pass on any error code to the joining thread. * If the result indicates an error, i.e. it is not equal to paNoError, this function will automatically * allocate a pointer so the error is passed on with pthread_exit. If the result indicates that all is * well however, only a NULL pointer will be handed to pthread_exit. Thus, the joining thread should * check whether a non-NULL result pointer is obtained from pthread_join and make sure to free it. * @param result: The error code to pass on to the joining thread. */ #define PaUnixThreading_EXIT(result) \ do { \ PaError* pres = NULL; \ if( paNoError != (result) ) \ { \ pres = malloc( sizeof (PaError) ); \ *pres = (result); \ } \ pthread_exit( pres ); \ } while (0); /** Spawn a thread. * * Intended for spawning the callback thread from the main thread. This function can even block (for a certain * time or indefinitely) untill notified by the callback thread (using PaUnixThread_NotifyParent), which can be * useful in order to make sure that callback has commenced before returning from Pa_StartStream. * @param threadFunc: The function to be executed in the child thread. * @param waitForChild: If not 0, wait for child thread to call PaUnixThread_NotifyParent. Less than 0 means * wait for ever, greater than 0 wait for the specified time. * @param rtSched: Enable realtime scheduling? * @return: If timed out waiting on child, paTimedOut. */ PaError PaUnixThread_New( PaUnixThread* self, void* (*threadFunc)( void* ), void* threadArg, PaTime waitForChild, int rtSched ); /** Terminate thread. * * @param wait: If true, request that background thread stop and wait untill it does, else cancel it. * @param exitResult: If non-null this will upon return contain the exit status of the thread. */ PaError PaUnixThread_Terminate( PaUnixThread* self, int wait, PaError* exitResult ); /** Prepare to notify waiting parent thread. * * An internal lock must be held before the parent is notified in PaUnixThread_NotifyParent, call this to * acquire it beforehand. * @return: If parent is not waiting, paInternalError. */ PaError PaUnixThread_PrepareNotify( PaUnixThread* self ); /** Notify waiting parent thread. * * @return: If parent timed out waiting, paTimedOut. If parent was never waiting, paInternalError. */ PaError PaUnixThread_NotifyParent( PaUnixThread* self ); /** Has the parent thread requested this thread to stop? */ int PaUnixThread_StopRequested( PaUnixThread* self ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif sources_5316/external/portaudio/pa_mac_core_blocking.c0000644000176700017670000004652410716412660022035 0ustar paulpaul/* * Implementation of the PortAudio API for Apple AUHAL * * PortAudio Portable Real-Time Audio Library * Latest Version at: http://www.portaudio.com * * Written by Bjorn Roche of XO Audio LLC, from PA skeleton code. * Portions copied from code by Dominic Mazzoni (who wrote a HAL implementation) * * Dominic's code was based on code by Phil Burk, Darren Gibbs, * Gord Peters, Stephane Letz, and Greg Pfiel. * * The following people also deserve acknowledgements: * * Olivier Tristan for feedback and testing * Glenn Zelniker and Z-Systems engineering for sponsoring the Blocking I/O * interface. * * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostaip_src This file contains the implementation required for blocking I/O. It is separated from pa_mac_core.c simply to ease development. */ #include "pa_mac_core_blocking.h" #include "pa_mac_core_internal.h" #include #ifdef MOSX_USE_NON_ATOMIC_FLAG_BITS # define OSAtomicOr32( a, b ) ( (*(b)) |= (a) ) # define OSAtomicAnd32( a, b ) ( (*(b)) &= (a) ) #else # include #endif /* * This fnuction determines the size of a particular sample format. * if the format is not recognized, this returns zero. */ static size_t computeSampleSizeFromFormat( PaSampleFormat format ) { switch( format ) { case paFloat32: return 4; case paInt32: return 4; case paInt24: return 3; case paInt16: return 2; case paInt8: case paUInt8: return 1; default: return 0; } } /* * Same as computeSampleSizeFromFormat, except that if * the size is not a power of two, it returns the next power of two up */ static size_t computeSampleSizeFromFormatPow2( PaSampleFormat format ) { switch( format ) { case paFloat32: return 4; case paInt32: return 4; case paInt24: return 4; case paInt16: return 2; case paInt8: case paUInt8: return 1; default: return 0; } } /* * Functions for initializing, resetting, and destroying BLIO structures. * */ /* This should be called with the relevant info when initializing a stream for callback. */ PaError initializeBlioRingBuffers( PaMacBlio *blio, PaSampleFormat inputSampleFormat, PaSampleFormat outputSampleFormat, size_t framesPerBuffer, long ringBufferSize, int inChan, int outChan ) { void *data; int result; /* zeroify things */ bzero( blio, sizeof( PaMacBlio ) ); /* this is redundant, but the buffers are used to check if the bufffers have been initialized, so we do it explicitly. */ blio->inputRingBuffer.buffer = NULL; blio->outputRingBuffer.buffer = NULL; /* initialize simple data */ blio->ringBufferFrames = ringBufferSize; blio->inputSampleFormat = inputSampleFormat; blio->inputSampleSizeActual = computeSampleSizeFromFormat(inputSampleFormat); blio->inputSampleSizePow2 = computeSampleSizeFromFormatPow2(inputSampleFormat); blio->outputSampleFormat = outputSampleFormat; blio->outputSampleSizeActual = computeSampleSizeFromFormat(outputSampleFormat); blio->outputSampleSizePow2 = computeSampleSizeFromFormatPow2(outputSampleFormat); blio->framesPerBuffer = framesPerBuffer; blio->inChan = inChan; blio->outChan = outChan; blio->statusFlags = 0; blio->errors = paNoError; #ifdef PA_MAC_BLIO_MUTEX blio->isInputEmpty = false; blio->isOutputFull = false; #endif /* setup ring buffers */ #ifdef PA_MAC_BLIO_MUTEX result = PaMacCore_SetUnixError( pthread_mutex_init(&(blio->inputMutex),NULL), 0 ); if( result ) goto error; result = UNIX_ERR( pthread_cond_init( &(blio->inputCond), NULL ) ); if( result ) goto error; result = UNIX_ERR( pthread_mutex_init(&(blio->outputMutex),NULL) ); if( result ) goto error; result = UNIX_ERR( pthread_cond_init( &(blio->outputCond), NULL ) ); #endif if( inChan ) { data = calloc( ringBufferSize, blio->inputSampleSizePow2*inChan ); if( !data ) { result = paInsufficientMemory; goto error; } assert( 0 == PaUtil_InitializeRingBuffer( &blio->inputRingBuffer, ringBufferSize*blio->inputSampleSizePow2*inChan, data ) ); } if( outChan ) { data = calloc( ringBufferSize, blio->outputSampleSizePow2*outChan ); if( !data ) { result = paInsufficientMemory; goto error; } assert( 0 == PaUtil_InitializeRingBuffer( &blio->outputRingBuffer, ringBufferSize*blio->outputSampleSizePow2*outChan, data ) ); } result = resetBlioRingBuffers( blio ); if( result ) goto error; return 0; error: destroyBlioRingBuffers( blio ); return result; } #ifdef PA_MAC_BLIO_MUTEX PaError blioSetIsInputEmpty( PaMacBlio *blio, bool isEmpty ) { PaError result = paNoError; if( isEmpty == blio->isInputEmpty ) goto done; /* we need to update the value. Here's what we do: * - Lock the mutex, so noone else can write. * - update the value. * - unlock. * - broadcast to all listeners. */ result = UNIX_ERR( pthread_mutex_lock( &blio->inputMutex ) ); if( result ) goto done; blio->isInputEmpty = isEmpty; result = UNIX_ERR( pthread_mutex_unlock( &blio->inputMutex ) ); if( result ) goto done; result = UNIX_ERR( pthread_cond_broadcast( &blio->inputCond ) ); if( result ) goto done; done: return result; } PaError blioSetIsOutputFull( PaMacBlio *blio, bool isFull ) { PaError result = paNoError; if( isFull == blio->isOutputFull ) goto done; /* we need to update the value. Here's what we do: * - Lock the mutex, so noone else can write. * - update the value. * - unlock. * - broadcast to all listeners. */ result = UNIX_ERR( pthread_mutex_lock( &blio->outputMutex ) ); if( result ) goto done; blio->isOutputFull = isFull; result = UNIX_ERR( pthread_mutex_unlock( &blio->outputMutex ) ); if( result ) goto done; result = UNIX_ERR( pthread_cond_broadcast( &blio->outputCond ) ); if( result ) goto done; done: return result; } #endif /* This should be called after stopping or aborting the stream, so that on next start, the buffers will be ready. */ PaError resetBlioRingBuffers( PaMacBlio *blio ) { #ifdef PA_MAC__BLIO_MUTEX int result; #endif blio->statusFlags = 0; if( blio->outputRingBuffer.buffer ) { PaUtil_FlushRingBuffer( &blio->outputRingBuffer ); bzero( blio->outputRingBuffer.buffer, blio->outputRingBuffer.bufferSize ); /* Advance buffer */ PaUtil_AdvanceRingBufferWriteIndex( &blio->outputRingBuffer, blio->ringBufferFrames*blio->outputSampleSizeActual*blio->outChan ); //PaUtil_AdvanceRingBufferWriteIndex( &blio->outputRingBuffer, blio->outputRingBuffer.bufferSize ); /* Update isOutputFull. */ #ifdef PA_MAC__BLIO_MUTEX result = blioSetIsOutputFull( blio, toAdvance == blio->outputRingBuffer.bufferSize ); if( result ) goto error; #endif /* printf( "------%d\n" , blio->framesPerBuffer ); printf( "------%d\n" , blio->outChan ); printf( "------%d\n" , blio->outputSampleSize ); printf( "------%d\n" , blio->framesPerBuffer*blio->outChan*blio->outputSampleSize ); */ } if( blio->inputRingBuffer.buffer ) { PaUtil_FlushRingBuffer( &blio->inputRingBuffer ); bzero( blio->inputRingBuffer.buffer, blio->inputRingBuffer.bufferSize ); /* Update isInputEmpty. */ #ifdef PA_MAC__BLIO_MUTEX result = blioSetIsInputEmpty( blio, true ); if( result ) goto error; #endif } return paNoError; #ifdef PA_MAC__BLIO_MUTEX error: return result; #endif } /*This should be called when you are done with the blio. It can safely be called multiple times if there are no exceptions. */ PaError destroyBlioRingBuffers( PaMacBlio *blio ) { PaError result = paNoError; if( blio->inputRingBuffer.buffer ) { free( blio->inputRingBuffer.buffer ); #ifdef PA_MAC__BLIO_MUTEX result = UNIX_ERR( pthread_mutex_destroy( & blio->inputMutex ) ); if( result ) return result; result = UNIX_ERR( pthread_cond_destroy( & blio->inputCond ) ); if( result ) return result; #endif } blio->inputRingBuffer.buffer = NULL; if( blio->outputRingBuffer.buffer ) { free( blio->outputRingBuffer.buffer ); #ifdef PA_MAC__BLIO_MUTEX result = UNIX_ERR( pthread_mutex_destroy( & blio->outputMutex ) ); if( result ) return result; result = UNIX_ERR( pthread_cond_destroy( & blio->outputCond ) ); if( result ) return result; #endif } blio->outputRingBuffer.buffer = NULL; return result; } /* * this is the BlioCallback function. It expects to recieve a PaMacBlio Object * pointer as userData. * */ int BlioCallback( const void *input, void *output, unsigned long frameCount, const PaStreamCallbackTimeInfo* timeInfo, PaStreamCallbackFlags statusFlags, void *userData ) { PaMacBlio *blio = (PaMacBlio*)userData; long avail; long toRead; long toWrite; /* set flags returned by OS: */ OSAtomicOr32( statusFlags, &blio->statusFlags ) ; /* --- Handle Input Buffer --- */ if( blio->inChan ) { avail = PaUtil_GetRingBufferWriteAvailable( &blio->inputRingBuffer ); /* check for underflow */ if( avail < frameCount * blio->inputSampleSizeActual * blio->inChan ) OSAtomicOr32( paInputOverflow, &blio->statusFlags ); toRead = MIN( avail, frameCount * blio->inputSampleSizeActual * blio->inChan ); /* copy the data */ /*printf( "reading %d\n", toRead );*/ assert( toRead == PaUtil_WriteRingBuffer( &blio->inputRingBuffer, input, toRead ) ); #ifdef PA_MAC__BLIO_MUTEX /* Priority inversion. See notes below. */ blioSetIsInputEmpty( blio, false ); #endif } /* --- Handle Output Buffer --- */ if( blio->outChan ) { avail = PaUtil_GetRingBufferReadAvailable( &blio->outputRingBuffer ); /* check for underflow */ if( avail < frameCount * blio->outputSampleSizeActual * blio->outChan ) OSAtomicOr32( paOutputUnderflow, &blio->statusFlags ); toWrite = MIN( avail, frameCount * blio->outputSampleSizeActual * blio->outChan ); if( toWrite != frameCount * blio->outputSampleSizeActual * blio->outChan ) bzero( ((char *)output)+toWrite, frameCount * blio->outputSampleSizeActual * blio->outChan - toWrite ); /* copy the data */ /*printf( "writing %d\n", toWrite );*/ assert( toWrite == PaUtil_ReadRingBuffer( &blio->outputRingBuffer, output, toWrite ) ); #ifdef PA_MAC__BLIO_MUTEX /* We have a priority inversion here. However, we will only have to wait if this was true and is now false, which means we've got some room in the buffer. Hopefully problems will be minimized. */ blioSetIsOutputFull( blio, false ); #endif } return paContinue; } PaError ReadStream( PaStream* stream, void *buffer, unsigned long frames ) { PaMacBlio *blio = & ((PaMacCoreStream*)stream) -> blio; char *cbuf = (char *) buffer; PaError ret = paNoError; VVDBUG(("ReadStream()\n")); while( frames > 0 ) { long avail; long toRead; do { avail = PaUtil_GetRingBufferReadAvailable( &blio->inputRingBuffer ); /* printf( "Read Buffer is %%%g full: %ld of %ld.\n", 100 * (float)avail / (float) blio->inputRingBuffer.bufferSize, avail, blio->inputRingBuffer.bufferSize ); */ if( avail == 0 ) { #ifdef PA_MAC_BLIO_MUTEX /**block when empty*/ ret = UNIX_ERR( pthread_mutex_lock( &blio->inputMutex ) ); if( ret ) return ret; while( blio->isInputEmpty ) { ret = UNIX_ERR( pthread_cond_wait( &blio->inputCond, &blio->inputMutex ) ); if( ret ) return ret; } ret = UNIX_ERR( pthread_mutex_unlock( &blio->inputMutex ) ); if( ret ) return ret; #else Pa_Sleep( PA_MAC_BLIO_BUSY_WAIT_SLEEP_INTERVAL ); #endif } } while( avail == 0 ); toRead = MIN( avail, frames * blio->inputSampleSizeActual * blio->inChan ); toRead -= toRead % blio->inputSampleSizeActual * blio->inChan ; PaUtil_ReadRingBuffer( &blio->inputRingBuffer, (void *)cbuf, toRead ); cbuf += toRead; frames -= toRead / ( blio->inputSampleSizeActual * blio->inChan ); if( toRead == avail ) { #ifdef PA_MAC_BLIO_MUTEX /* we just emptied the buffer, so we need to mark it as empty. */ ret = blioSetIsInputEmpty( blio, true ); if( ret ) return ret; /* of course, in the meantime, the callback may have put some sats in, so so check for that, too, to avoid a race condition. */ if( PaUtil_GetRingBufferReadAvailable( &blio->inputRingBuffer ) ) { blioSetIsInputEmpty( blio, false ); if( ret ) return ret; } #endif } } /* Report either paNoError or paInputOverflowed. */ /* may also want to report other errors, but this is non-standard. */ ret = blio->statusFlags & paInputOverflow; /* report underflow only once: */ if( ret ) { OSAtomicAnd32( (uint32_t)(~paInputOverflow), &blio->statusFlags ); ret = paInputOverflowed; } return ret; } PaError WriteStream( PaStream* stream, const void *buffer, unsigned long frames ) { PaMacBlio *blio = & ((PaMacCoreStream*)stream) -> blio; char *cbuf = (char *) buffer; PaError ret = paNoError; VVDBUG(("WriteStream()\n")); while( frames > 0 ) { long avail = 0; long toWrite; do { avail = PaUtil_GetRingBufferWriteAvailable( &blio->outputRingBuffer ); /* printf( "Write Buffer is %%%g full: %ld of %ld.\n", 100 - 100 * (float)avail / (float) blio->outputRingBuffer.bufferSize, avail, blio->outputRingBuffer.bufferSize ); */ if( avail == 0 ) { #ifdef PA_MAC_BLIO_MUTEX /*block while full*/ ret = UNIX_ERR( pthread_mutex_lock( &blio->outputMutex ) ); if( ret ) return ret; while( blio->isOutputFull ) { ret = UNIX_ERR( pthread_cond_wait( &blio->outputCond, &blio->outputMutex ) ); if( ret ) return ret; } ret = UNIX_ERR( pthread_mutex_unlock( &blio->outputMutex ) ); if( ret ) return ret; #else Pa_Sleep( PA_MAC_BLIO_BUSY_WAIT_SLEEP_INTERVAL ); #endif } } while( avail == 0 ); toWrite = MIN( avail, frames * blio->outputSampleSizeActual * blio->outChan ); toWrite -= toWrite % blio->outputSampleSizeActual * blio->outChan ; PaUtil_WriteRingBuffer( &blio->outputRingBuffer, (void *)cbuf, toWrite ); cbuf += toWrite; frames -= toWrite / ( blio->outputSampleSizeActual * blio->outChan ); #ifdef PA_MAC_BLIO_MUTEX if( toWrite == avail ) { /* we just filled up the buffer, so we need to mark it as filled. */ ret = blioSetIsOutputFull( blio, true ); if( ret ) return ret; /* of course, in the meantime, we may have emptied the buffer, so so check for that, too, to avoid a race condition. */ if( PaUtil_GetRingBufferWriteAvailable( &blio->outputRingBuffer ) ) { blioSetIsOutputFull( blio, false ); if( ret ) return ret; } } #endif } /* Report either paNoError or paOutputUnderflowed. */ /* may also want to report other errors, but this is non-standard. */ ret = blio->statusFlags & paOutputUnderflow; /* report underflow only once: */ if( ret ) { OSAtomicAnd32( (uint32_t)(~paOutputUnderflow), &blio->statusFlags ); ret = paOutputUnderflowed; } return ret; } /* * */ void waitUntilBlioWriteBufferIsFlushed( PaMacBlio *blio ) { if( blio->outputRingBuffer.buffer ) { long avail = PaUtil_GetRingBufferWriteAvailable( &blio->outputRingBuffer ); while( avail != blio->outputRingBuffer.bufferSize ) { if( avail == 0 ) Pa_Sleep( PA_MAC_BLIO_BUSY_WAIT_SLEEP_INTERVAL ); avail = PaUtil_GetRingBufferWriteAvailable( &blio->outputRingBuffer ); } } } signed long GetStreamReadAvailable( PaStream* stream ) { PaMacBlio *blio = & ((PaMacCoreStream*)stream) -> blio; VVDBUG(("GetStreamReadAvailable()\n")); return PaUtil_GetRingBufferReadAvailable( &blio->inputRingBuffer ) / ( blio->outputSampleSizeActual * blio->outChan ); } signed long GetStreamWriteAvailable( PaStream* stream ) { PaMacBlio *blio = & ((PaMacCoreStream*)stream) -> blio; VVDBUG(("GetStreamWriteAvailable()\n")); return PaUtil_GetRingBufferWriteAvailable( &blio->outputRingBuffer ) / ( blio->outputSampleSizeActual * blio->outChan ); } sources_5316/external/portaudio/pa_unix_hostapis.c0000644000176700017670000000511111630754713021301 0ustar paulpaul#ifdef UNIX /* * $Id: pa_unix_hostapis.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library UNIX initialization table * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup unix_src */ #include "pa_hostapi.h" PaError PaJack_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaAlsa_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaOSS_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); /* Added for IRIX, Pieter, oct 2, 2003: */ PaError PaSGI_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); /* Linux AudioScience HPI */ PaError PaAsiHpi_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaUtilHostApiInitializer *paHostApiInitializers[] = { #if defined (linux) PaAlsa_Initialize, #elif defined (sgi) PaSGI_Initialize, #else PaOSS_Initialize, #endif 0 /* NULL terminated array */ }; int paDefaultHostApiIndex = 0; #endif sources_5316/external/portaudio/pa_process.h0000644000176700017670000007623410474003011020064 0ustar paulpaul#ifndef PA_PROCESS_H #define PA_PROCESS_H /* * $Id: pa_process.h 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library callback buffer processing adapters * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Phil Burk, Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Buffer Processor prototypes. A Buffer Processor performs buffer length adaption, coordinates sample format conversion, and interleaves/deinterleaves channels.

Overview

The "Buffer Processor" (PaUtilBufferProcessor) manages conversion of audio data from host buffers to user buffers and back again. Where required, the buffer processor takes care of converting between host and user sample formats, interleaving and deinterleaving multichannel buffers, and adapting between host and user buffers with different lengths. The buffer processor may be used with full and half duplex streams, for both callback streams and blocking read/write streams. One of the important capabilities provided by the buffer processor is the ability to adapt between user and host buffer sizes of different lengths with minimum latency. Although this task is relatively easy to perform when the host buffer size is an integer multiple of the user buffer size, the problem is more complicated when this is not the case - especially for full-duplex callback streams. Where necessary the adaption is implemented by internally buffering some input and/or output data. The buffer adation algorithm used by the buffer processor was originally implemented by Stephan Letz for the ASIO version of PortAudio, and is described in his Callback_adaption_.pdf which is included in the distribution. The buffer processor performs sample conversion using the functions provided by pa_converters.c. The following sections provide an overview of how to use the buffer processor. Interested readers are advised to consult the host API implementations for examples of buffer processor usage.

Initialization, resetting and termination

When a stream is opened, the buffer processor should be initialized using PaUtil_InitializeBufferProcessor. This function initializes internal state and allocates temporary buffers as neccesary according to the supplied configuration parameters. Some of the parameters correspond to those requested by the user in their call to Pa_OpenStream(), others reflect the requirements of the host API implementation - they indicate host buffer sizes, formats, and the type of buffering which the Host API uses. The buffer processor should be initialized for callback streams and blocking read/write streams. Call PaUtil_ResetBufferProcessor to clear any sample data which is present in the buffer processor before starting to use it (for example when Pa_StartStream is called). When the buffer processor is no longer used call PaUtil_TerminateBufferProcessor.

Using the buffer processor for a callback stream

The buffer processor's role in a callback stream is to take host input buffers process them with the stream callback, and fill host output buffers. For a full duplex stream, the buffer processor handles input and output simultaneously due to the requirements of the minimum-latency buffer adation algorithm. When a host buffer becomes available, the implementation should call the buffer processor to process the buffer. The buffer processor calls the stream callback to consume and/or produce audio data as necessary. The buffer processor will convert sample formats, interleave/deinterleave channels, and slice or chunk the data to the appropriate buffer lengths according to the requirements of the stream callback and the host API. To process a host buffer (or a pair of host buffers for a full-duplex stream) use the following calling sequence: -# Call PaUtil_BeginBufferProcessing -# For a stream which takes input: - Call PaUtil_SetInputFrameCount with the number of frames in the host input buffer. - Call one of the following functions one or more times to tell the buffer processor about the host input buffer(s): PaUtil_SetInputChannel, PaUtil_SetInterleavedInputChannels, PaUtil_SetNonInterleavedInputChannel. Which function you call will depend on whether the host buffer(s) are interleaved or not. - If the available host data is split accross two buffers (for example a data range at the end of a circular buffer and another range at the beginning of the circular buffer), also call PaUtil_Set2ndInputFrameCount, PaUtil_Set2ndInputChannel, PaUtil_Set2ndInterleavedInputChannels, PaUtil_Set2ndNonInterleavedInputChannel as necessary to tell the buffer processor about the second buffer. -# For a stream which generates output: - Call PaUtil_SetOutputFrameCount with the number of frames in the host output buffer. - Call one of the following functions one or more times to tell the buffer processor about the host output buffer(s): PaUtil_SetOutputChannel, PaUtil_SetInterleavedOutputChannels, PaUtil_SetNonInterleavedOutputChannel. Which function you call will depend on whether the host buffer(s) are interleaved or not. - If the available host output buffer space is split accross two buffers (for example a data range at the end of a circular buffer and another range at the beginning of the circular buffer), call PaUtil_Set2ndOutputFrameCount, PaUtil_Set2ndOutputChannel, PaUtil_Set2ndInterleavedOutputChannels, PaUtil_Set2ndNonInterleavedOutputChannel as necessary to tell the buffer processor about the second buffer. -# Call PaUtil_EndBufferProcessing, this function performs the actual data conversion and processing.

Using the buffer processor for a blocking read/write stream

Blocking read/write streams use the buffer processor to convert and copy user output data to a host buffer, and to convert and copy host input data to the user's buffer. The buffer processor does not perform any buffer adaption. When using the buffer processor in a blocking read/write stream the input and output conversion are performed separately by the PaUtil_CopyInput and PaUtil_CopyOutput functions. To copy data from a host input buffer to the buffer(s) which the user supplies to Pa_ReadStream, use the following calling sequence. - Repeat the following three steps until the user buffer(s) have been filled with samples from the host input buffers: -# Call PaUtil_SetInputFrameCount with the number of frames in the host input buffer. -# Call one of the following functions one or more times to tell the buffer processor about the host input buffer(s): PaUtil_SetInputChannel, PaUtil_SetInterleavedInputChannels, PaUtil_SetNonInterleavedInputChannel. Which function you call will depend on whether the host buffer(s) are interleaved or not. -# Call PaUtil_CopyInput with the user buffer pointer (or a copy of the array of buffer pointers for a non-interleaved stream) passed to Pa_ReadStream, along with the number of frames in the user buffer(s). Be careful to pass a copy of the user buffer pointers to PaUtil_CopyInput because PaUtil_CopyInput advances the pointers to the start of the next region to copy. - PaUtil_CopyInput will not copy more data than is available in the host buffer(s), so the above steps need to be repeated until the user buffer(s) are full. To copy data to the host output buffer from the user buffers(s) supplied to Pa_WriteStream use the following calling sequence. - Repeat the following three steps until all frames from the user buffer(s) have been copied to the host API: -# Call PaUtil_SetOutputFrameCount with the number of frames in the host output buffer. -# Call one of the following functions one or more times to tell the buffer processor about the host output buffer(s): PaUtil_SetOutputChannel, PaUtil_SetInterleavedOutputChannels, PaUtil_SetNonInterleavedOutputChannel. Which function you call will depend on whether the host buffer(s) are interleaved or not. -# Call PaUtil_CopyOutput with the user buffer pointer (or a copy of the array of buffer pointers for a non-interleaved stream) passed to Pa_WriteStream, along with the number of frames in the user buffer(s). Be careful to pass a copy of the user buffer pointers to PaUtil_CopyOutput because PaUtil_CopyOutput advances the pointers to the start of the next region to copy. - PaUtil_CopyOutput will not copy more data than fits in the host buffer(s), so the above steps need to be repeated until all user data is copied. */ #include "portaudio.h" #include "pa_converters.h" #include "pa_dither.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ /** @brief Mode flag passed to PaUtil_InitializeBufferProcessor indicating the type of buffering that the host API uses. The mode used depends on whether the host API or the implementation manages the buffers, and how these buffers are used (scatter gather, circular buffer). */ typedef enum { /** The host buffer size is a fixed known size. */ paUtilFixedHostBufferSize, /** The host buffer size may vary, but has a known maximum size. */ paUtilBoundedHostBufferSize, /** Nothing is known about the host buffer size. */ paUtilUnknownHostBufferSize, /** The host buffer size varies, and the client does not require the buffer processor to consume all of the input and fill all of the output buffer. This is useful when the implementation has access to the host API's circular buffer and only needs to consume/fill some of it, not necessarily all of it, with each call to the buffer processor. This is the only mode where PaUtil_EndBufferProcessing() may not consume the whole buffer. */ paUtilVariableHostBufferSizePartialUsageAllowed }PaUtilHostBufferSizeMode; /** @brief An auxilliary data structure used internally by the buffer processor to represent host input and output buffers. */ typedef struct PaUtilChannelDescriptor{ void *data; unsigned int stride; /**< stride in samples, not bytes */ }PaUtilChannelDescriptor; /** @brief The main buffer processor data structure. Allocate one of these, initialize it with PaUtil_InitializeBufferProcessor and terminate it with PaUtil_TerminateBufferProcessor. */ typedef struct { unsigned long framesPerUserBuffer; unsigned long framesPerHostBuffer; PaUtilHostBufferSizeMode hostBufferSizeMode; int useNonAdaptingProcess; unsigned long framesPerTempBuffer; unsigned int inputChannelCount; unsigned int bytesPerHostInputSample; unsigned int bytesPerUserInputSample; int userInputIsInterleaved; PaUtilConverter *inputConverter; PaUtilZeroer *inputZeroer; unsigned int outputChannelCount; unsigned int bytesPerHostOutputSample; unsigned int bytesPerUserOutputSample; int userOutputIsInterleaved; PaUtilConverter *outputConverter; PaUtilZeroer *outputZeroer; unsigned long initialFramesInTempInputBuffer; unsigned long initialFramesInTempOutputBuffer; void *tempInputBuffer; /**< used for slips, block adaption, and conversion. */ void **tempInputBufferPtrs; /**< storage for non-interleaved buffer pointers, NULL for interleaved user input */ unsigned long framesInTempInputBuffer; /**< frames remaining in input buffer from previous adaption iteration */ void *tempOutputBuffer; /**< used for slips, block adaption, and conversion. */ void **tempOutputBufferPtrs; /**< storage for non-interleaved buffer pointers, NULL for interleaved user output */ unsigned long framesInTempOutputBuffer; /**< frames remaining in input buffer from previous adaption iteration */ PaStreamCallbackTimeInfo *timeInfo; PaStreamCallbackFlags callbackStatusFlags; unsigned long hostInputFrameCount[2]; PaUtilChannelDescriptor *hostInputChannels[2]; /**< pointers to arrays of channel descriptors. pointers are NULL for half-duplex output processing. hostInputChannels[i].data is NULL when the caller calls PaUtil_SetNoInput() */ unsigned long hostOutputFrameCount[2]; PaUtilChannelDescriptor *hostOutputChannels[2]; /**< pointers to arrays of channel descriptors. pointers are NULL for half-duplex input processing. hostOutputChannels[i].data is NULL when the caller calls PaUtil_SetNoOutput() */ PaUtilTriangularDitherGenerator ditherGenerator; double samplePeriod; PaStreamCallback *streamCallback; void *userData; } PaUtilBufferProcessor; /** @name Initialization, termination, resetting and info */ /*@{*/ /** Initialize a buffer processor's representation stored in a PaUtilBufferProcessor structure. Be sure to call PaUtil_TerminateBufferProcessor after finishing with a buffer processor. @param bufferProcessor The buffer processor structure to initialize. @param inputChannelCount The number of input channels as passed to Pa_OpenStream or 0 for an output-only stream. @param userInputSampleFormat Format of user input samples, as passed to Pa_OpenStream. This parameter is ignored for ouput-only streams. @param hostInputSampleFormat Format of host input samples. This parameter is ignored for output-only streams. See note about host buffer interleave below. @param outputChannelCount The number of output channels as passed to Pa_OpenStream or 0 for an input-only stream. @param userOutputSampleFormat Format of user output samples, as passed to Pa_OpenStream. This parameter is ignored for input-only streams. @param hostOutputSampleFormat Format of host output samples. This parameter is ignored for input-only streams. See note about host buffer interleave below. @param sampleRate Sample rate of the stream. The more accurate this is the better - it is used for updating time stamps when adapting buffers. @param streamFlags Stream flags as passed to Pa_OpenStream, this parameter is used for selecting special sample conversion options such as clipping and dithering. @param framesPerUserBuffer Number of frames per user buffer, as requested by the framesPerBuffer parameter to Pa_OpenStream. This parameter may be zero to indicate that the user will accept any (and varying) buffer sizes. @param framesPerHostBuffer Specifies the number of frames per host buffer for the fixed buffer size mode, and the maximum number of frames per host buffer for the bounded host buffer size mode. It is ignored for the other modes. @param hostBufferSizeMode A mode flag indicating the size variability of host buffers that will be passed to the buffer processor. See PaUtilHostBufferSizeMode for further details. @param streamCallback The user stream callback passed to Pa_OpenStream. @param userData The user data field passed to Pa_OpenStream. @note The interleave flag is ignored for host buffer formats. Host interleave is determined by the use of different SetInput and SetOutput functions. @return An error code indicating whether the initialization was successful. If the error code is not PaNoError, the buffer processor was not initialized and should not be used. @see Pa_OpenStream, PaUtilHostBufferSizeMode, PaUtil_TerminateBufferProcessor */ PaError PaUtil_InitializeBufferProcessor( PaUtilBufferProcessor* bufferProcessor, int inputChannelCount, PaSampleFormat userInputSampleFormat, PaSampleFormat hostInputSampleFormat, int outputChannelCount, PaSampleFormat userOutputSampleFormat, PaSampleFormat hostOutputSampleFormat, double sampleRate, PaStreamFlags streamFlags, unsigned long framesPerUserBuffer, /* 0 indicates don't care */ unsigned long framesPerHostBuffer, PaUtilHostBufferSizeMode hostBufferSizeMode, PaStreamCallback *streamCallback, void *userData ); /** Terminate a buffer processor's representation. Deallocates any temporary buffers allocated by PaUtil_InitializeBufferProcessor. @param bufferProcessor The buffer processor structure to terminate. @see PaUtil_InitializeBufferProcessor. */ void PaUtil_TerminateBufferProcessor( PaUtilBufferProcessor* bufferProcessor ); /** Clear any internally buffered data. If you call PaUtil_InitializeBufferProcessor in your OpenStream routine, make sure you call PaUtil_ResetBufferProcessor in your StartStream call. @param bufferProcessor The buffer processor to reset. */ void PaUtil_ResetBufferProcessor( PaUtilBufferProcessor* bufferProcessor ); /** Retrieve the input latency of a buffer processor. @param bufferProcessor The buffer processor examine. @return The input latency introduced by the buffer processor, in frames. @see PaUtil_GetBufferProcessorOutputLatency */ unsigned long PaUtil_GetBufferProcessorInputLatency( PaUtilBufferProcessor* bufferProcessor ); /** Retrieve the output latency of a buffer processor. @param bufferProcessor The buffer processor examine. @return The output latency introduced by the buffer processor, in frames. @see PaUtil_GetBufferProcessorInputLatency */ unsigned long PaUtil_GetBufferProcessorOutputLatency( PaUtilBufferProcessor* bufferProcessor ); /*@}*/ /** @name Host buffer pointer configuration Functions to set host input and output buffers, used by both callback streams and blocking read/write streams. */ /*@{*/ /** Set the number of frames in the input host buffer(s) specified by the PaUtil_Set*InputChannel functions. @param bufferProcessor The buffer processor. @param frameCount The number of host input frames. A 0 frameCount indicates to use the framesPerHostBuffer value passed to PaUtil_InitializeBufferProcessor. @see PaUtil_SetNoInput, PaUtil_SetInputChannel, PaUtil_SetInterleavedInputChannels, PaUtil_SetNonInterleavedInputChannel */ void PaUtil_SetInputFrameCount( PaUtilBufferProcessor* bufferProcessor, unsigned long frameCount ); /** Indicate that no input is avalable. This function should be used when priming the output of a full-duplex stream opened with the paPrimeOutputBuffersUsingStreamCallback flag. Note that it is not necessary to call this or any othe PaUtil_Set*Input* functions for ouput-only streams. @param bufferProcessor The buffer processor. */ void PaUtil_SetNoInput( PaUtilBufferProcessor* bufferProcessor ); /** Provide the buffer processor with a pointer to a host input channel. @param bufferProcessor The buffer processor. @param channel The channel number. @param data The buffer. @param stride The stride from one sample to the next, in samples. For interleaved host buffers, the stride will usually be the same as the number of channels in the buffer. */ void PaUtil_SetInputChannel( PaUtilBufferProcessor* bufferProcessor, unsigned int channel, void *data, unsigned int stride ); /** Provide the buffer processor with a pointer to an number of interleaved host input channels. @param bufferProcessor The buffer processor. @param firstChannel The first channel number. @param data The buffer. @param channelCount The number of interleaved channels in the buffer. If channelCount is zero, the number of channels specified to PaUtil_InitializeBufferProcessor will be used. */ void PaUtil_SetInterleavedInputChannels( PaUtilBufferProcessor* bufferProcessor, unsigned int firstChannel, void *data, unsigned int channelCount ); /** Provide the buffer processor with a pointer to one non-interleaved host output channel. @param bufferProcessor The buffer processor. @param channel The channel number. @param data The buffer. */ void PaUtil_SetNonInterleavedInputChannel( PaUtilBufferProcessor* bufferProcessor, unsigned int channel, void *data ); /** Use for the second buffer half when the input buffer is split in two halves. @see PaUtil_SetInputFrameCount */ void PaUtil_Set2ndInputFrameCount( PaUtilBufferProcessor* bufferProcessor, unsigned long frameCount ); /** Use for the second buffer half when the input buffer is split in two halves. @see PaUtil_SetInputChannel */ void PaUtil_Set2ndInputChannel( PaUtilBufferProcessor* bufferProcessor, unsigned int channel, void *data, unsigned int stride ); /** Use for the second buffer half when the input buffer is split in two halves. @see PaUtil_SetInterleavedInputChannels */ void PaUtil_Set2ndInterleavedInputChannels( PaUtilBufferProcessor* bufferProcessor, unsigned int firstChannel, void *data, unsigned int channelCount ); /** Use for the second buffer half when the input buffer is split in two halves. @see PaUtil_SetNonInterleavedInputChannel */ void PaUtil_Set2ndNonInterleavedInputChannel( PaUtilBufferProcessor* bufferProcessor, unsigned int channel, void *data ); /** Set the number of frames in the output host buffer(s) specified by the PaUtil_Set*OutputChannel functions. @param bufferProcessor The buffer processor. @param frameCount The number of host output frames. A 0 frameCount indicates to use the framesPerHostBuffer value passed to PaUtil_InitializeBufferProcessor. @see PaUtil_SetOutputChannel, PaUtil_SetInterleavedOutputChannels, PaUtil_SetNonInterleavedOutputChannel */ void PaUtil_SetOutputFrameCount( PaUtilBufferProcessor* bufferProcessor, unsigned long frameCount ); /** Indicate that the output will be discarded. This function should be used when implementing the paNeverDropInput mode for full duplex streams. @param bufferProcessor The buffer processor. */ void PaUtil_SetNoOutput( PaUtilBufferProcessor* bufferProcessor ); /** Provide the buffer processor with a pointer to a host output channel. @param bufferProcessor The buffer processor. @param channel The channel number. @param data The buffer. @param stride The stride from one sample to the next, in samples. For interleaved host buffers, the stride will usually be the same as the number of channels in the buffer. */ void PaUtil_SetOutputChannel( PaUtilBufferProcessor* bufferProcessor, unsigned int channel, void *data, unsigned int stride ); /** Provide the buffer processor with a pointer to a number of interleaved host output channels. @param bufferProcessor The buffer processor. @param firstChannel The first channel number. @param data The buffer. @param channelCount The number of interleaved channels in the buffer. If channelCount is zero, the number of channels specified to PaUtil_InitializeBufferProcessor will be used. */ void PaUtil_SetInterleavedOutputChannels( PaUtilBufferProcessor* bufferProcessor, unsigned int firstChannel, void *data, unsigned int channelCount ); /** Provide the buffer processor with a pointer to one non-interleaved host output channel. @param bufferProcessor The buffer processor. @param channel The channel number. @param data The buffer. */ void PaUtil_SetNonInterleavedOutputChannel( PaUtilBufferProcessor* bufferProcessor, unsigned int channel, void *data ); /** Use for the second buffer half when the output buffer is split in two halves. @see PaUtil_SetOutputFrameCount */ void PaUtil_Set2ndOutputFrameCount( PaUtilBufferProcessor* bufferProcessor, unsigned long frameCount ); /** Use for the second buffer half when the output buffer is split in two halves. @see PaUtil_SetOutputChannel */ void PaUtil_Set2ndOutputChannel( PaUtilBufferProcessor* bufferProcessor, unsigned int channel, void *data, unsigned int stride ); /** Use for the second buffer half when the output buffer is split in two halves. @see PaUtil_SetInterleavedOutputChannels */ void PaUtil_Set2ndInterleavedOutputChannels( PaUtilBufferProcessor* bufferProcessor, unsigned int firstChannel, void *data, unsigned int channelCount ); /** Use for the second buffer half when the output buffer is split in two halves. @see PaUtil_SetNonInterleavedOutputChannel */ void PaUtil_Set2ndNonInterleavedOutputChannel( PaUtilBufferProcessor* bufferProcessor, unsigned int channel, void *data ); /*@}*/ /** @name Buffer processing functions for callback streams */ /*@{*/ /** Commence processing a host buffer (or a pair of host buffers in the full-duplex case) for a callback stream. @param bufferProcessor The buffer processor. @param timeInfo Timing information for the first sample of the host buffer(s). This information may be adjusted when buffer adaption is being performed. @param callbackStatusFlags Flags indicating whether underruns and overruns have occurred since the last time the buffer processor was called. */ void PaUtil_BeginBufferProcessing( PaUtilBufferProcessor* bufferProcessor, PaStreamCallbackTimeInfo* timeInfo, PaStreamCallbackFlags callbackStatusFlags ); /** Finish processing a host buffer (or a pair of host buffers in the full-duplex case) for a callback stream. @param bufferProcessor The buffer processor. @param callbackResult On input, indicates a previous callback result, and on exit, the result of the user stream callback, if it is called. On entry callbackResult should contain one of { paContinue, paComplete, or paAbort}. If paComplete is passed, the stream callback will not be called but any audio that was generated by previous stream callbacks will be copied to the output buffer(s). You can check whether the buffer processor's internal buffer is empty by calling PaUtil_IsBufferProcessorOutputEmpty. If the stream callback is called its result is stored in *callbackResult. If the stream callback returns paComplete or paAbort, all output buffers will be full of valid data - some of which may be zeros to acount for data that wasn't generated by the terminating callback. @return The number of frames processed. This usually corresponds to the number of frames specified by the PaUtil_Set*FrameCount functions, exept in the paUtilVariableHostBufferSizePartialUsageAllowed buffer size mode when a smaller value may be returned. */ unsigned long PaUtil_EndBufferProcessing( PaUtilBufferProcessor* bufferProcessor, int *callbackResult ); /** Determine whether any callback generated output remains in the bufffer processor's internal buffers. This method may be used to determine when to continue calling PaUtil_EndBufferProcessing() after the callback has returned a callbackResult of paComplete. @param bufferProcessor The buffer processor. @return Returns non-zero when callback generated output remains in the internal buffer and zero (0) when there internal buffer contains no callback generated data. */ int PaUtil_IsBufferProcessorOutputEmpty( PaUtilBufferProcessor* bufferProcessor ); /*@}*/ /** @name Buffer processing functions for blocking read/write streams */ /*@{*/ /** Copy samples from host input channels set up by the PaUtil_Set*InputChannels functions to a user supplied buffer. This function is intended for use with blocking read/write streams. Copies the minimum of the number of user frames (specified by the frameCount parameter) and the number of available host frames (specified in a previous call to SetInputFrameCount()). @param bufferProcessor The buffer processor. @param buffer A pointer to the user buffer pointer, or a pointer to a pointer to an array of user buffer pointers for a non-interleaved stream. It is important that this parameter points to a copy of the user buffer pointers, not to the actual user buffer pointers, because this function updates the pointers before returning. @param frameCount The number of frames of data in the buffer(s) pointed to by the buffer parameter. @return The number of frames copied. The buffer pointer(s) pointed to by the buffer parameter are advanced to point to the frame(s) following the last one filled. */ unsigned long PaUtil_CopyInput( PaUtilBufferProcessor* bufferProcessor, void **buffer, unsigned long frameCount ); /* Copy samples from a user supplied buffer to host output channels set up by the PaUtil_Set*OutputChannels functions. This function is intended for use with blocking read/write streams. Copies the minimum of the number of user frames (specified by the frameCount parameter) and the number of host frames (specified in a previous call to SetOutputFrameCount()). @param bufferProcessor The buffer processor. @param buffer A pointer to the user buffer pointer, or a pointer to a pointer to an array of user buffer pointers for a non-interleaved stream. It is important that this parameter points to a copy of the user buffer pointers, not to the actual user buffer pointers, because this function updates the pointers before returning. @param frameCount The number of frames of data in the buffer(s) pointed to by the buffer parameter. @return The number of frames copied. The buffer pointer(s) pointed to by the buffer parameter are advanced to point to the frame(s) following the last one copied. */ unsigned long PaUtil_CopyOutput( PaUtilBufferProcessor* bufferProcessor, const void ** buffer, unsigned long frameCount ); /* Zero samples in host output channels set up by the PaUtil_Set*OutputChannels functions. This function is useful for flushing streams. Zeros the minimum of frameCount and the number of host frames specified in a previous call to SetOutputFrameCount(). @param bufferProcessor The buffer processor. @param frameCount The maximum number of frames to zero. @return The number of frames zeroed. */ unsigned long PaUtil_ZeroOutput( PaUtilBufferProcessor* bufferProcessor, unsigned long frameCount ); /*@}*/ #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_PROCESS_H */ sources_5316/external/portaudio/pa_win_wdmks.c0000644000176700017670000032230011034436776020414 0ustar paulpaul/* * $Id: pa_win_wdmks.c 1263 2007-08-27 22:59:09Z rossb $ * PortAudio Windows WDM-KS interface * * Author: Andrew Baldwin * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2004 Andrew Baldwin, Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostaip_src @brief Portaudio WDM-KS host API. @note This is the implementation of the Portaudio host API using the Windows WDM/Kernel Streaming API in order to enable very low latency playback and recording on all modern Windows platforms (e.g. 2K, XP) Note: This API accesses the device drivers below the usual KMIXER component which is normally used to enable multi-client mixing and format conversion. That means that it will lock out all other users of a device for the duration of active stream using those devices */ #include /* Debugging/tracing support */ #define PA_LOGE_ #define PA_LOGL_ #ifdef __GNUC__ #include #define _WIN32_WINNT 0x0501 #define WINVER 0x0501 #endif #include /* strlen() */ #include #include "pa_util.h" #include "pa_allocation.h" #include "pa_hostapi.h" #include "pa_stream.h" #include "pa_cpuload.h" #include "pa_process.h" #include "portaudio.h" #include "pa_debugprint.h" #include #include // ppgb 20080707: #define _INC_MMSYSTEM #define _INC_MMREG #define DYNAMIC_GUID_THUNK(l,w1,w2,b1,b2,b3,b4,b5,b6,b7,b8) {l,w1,w2,{b1,b2,b3,b4,b5,b6,b7,b8}} #define DYNAMIC_GUID(data) DYNAMIC_GUID_THUNK(data) #define _NTRTL_ /* Turn off default definition of DEFINE_GUIDEX */ #define DEFINE_GUID_THUNK(name,guid) DEFINE_GUID(name,guid) #define DEFINE_GUIDEX(n) DEFINE_GUID_THUNK( n, STATIC_##n ) #if !defined( DEFINE_WAVEFORMATEX_GUID ) #define DEFINE_WAVEFORMATEX_GUID(x) (USHORT)(x), 0x0000, 0x0010, 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 #endif #define WAVE_FORMAT_ADPCM 0x0002 #define WAVE_FORMAT_IEEE_FLOAT 0x0003 #define WAVE_FORMAT_ALAW 0x0006 #define WAVE_FORMAT_MULAW 0x0007 #define WAVE_FORMAT_MPEG 0x0050 #define WAVE_FORMAT_DRM 0x0009 #ifdef __GNUC__ #undef PA_LOGE_ #define PA_LOGE_ PA_DEBUG(("%s {\n",__FUNCTION__)) #undef PA_LOGL_ #define PA_LOGL_ PA_DEBUG(("} %s\n",__FUNCTION__)) /* These defines are set in order to allow the WIndows DirectX * headers to compile with a GCC compiler such as MinGW * NOTE: The headers may generate a few warning in GCC, but * they should compile */ #define _INC_MMSYSTEM #define _INC_MMREG #define _NTRTL_ /* Turn off default definition of DEFINE_GUIDEX */ #define DEFINE_GUID_THUNK(name,guid) DEFINE_GUID(name,guid) #define DEFINE_GUIDEX(n) DEFINE_GUID_THUNK( n, STATIC_##n ) #if !defined( DEFINE_WAVEFORMATEX_GUID ) #define DEFINE_WAVEFORMATEX_GUID(x) (USHORT)(x), 0x0000, 0x0010, 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 #endif #define WAVE_FORMAT_ADPCM 0x0002 #define WAVE_FORMAT_IEEE_FLOAT 0x0003 #define WAVE_FORMAT_ALAW 0x0006 #define WAVE_FORMAT_MULAW 0x0007 #define WAVE_FORMAT_MPEG 0x0050 #define WAVE_FORMAT_DRM 0x0009 #define DYNAMIC_GUID_THUNK(l,w1,w2,b1,b2,b3,b4,b5,b6,b7,b8) {l,w1,w2,{b1,b2,b3,b4,b5,b6,b7,b8}} #define DYNAMIC_GUID(data) DYNAMIC_GUID_THUNK(data) #endif #ifdef _MSC_VER #define DYNAMIC_GUID(data) {data} #define _INC_MMREG #define _NTRTL_ /* Turn off default definition of DEFINE_GUIDEX */ #undef DEFINE_GUID #define DEFINE_GUID(n,data) EXTERN_C const GUID n = {data} #define DEFINE_GUID_THUNK(n,data) DEFINE_GUID(n,data) #define DEFINE_GUIDEX(n) DEFINE_GUID_THUNK(n, STATIC_##n) #if !defined( DEFINE_WAVEFORMATEX_GUID ) #define DEFINE_WAVEFORMATEX_GUID(x) (USHORT)(x), 0x0000, 0x0010, 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 #endif #define WAVE_FORMAT_ADPCM 0x0002 #define WAVE_FORMAT_IEEE_FLOAT 0x0003 #define WAVE_FORMAT_ALAW 0x0006 #define WAVE_FORMAT_MULAW 0x0007 #define WAVE_FORMAT_MPEG 0x0050 #define WAVE_FORMAT_DRM 0x0009 #endif #include #include #include #include #include /* These next definitions allow the use of the KSUSER DLL */ typedef /*KSDDKAPI ppgb 20080707*/ DWORD WINAPI KSCREATEPIN(HANDLE, PKSPIN_CONNECT, ACCESS_MASK, PHANDLE); extern HMODULE DllKsUser; extern KSCREATEPIN* FunctionKsCreatePin; /* Forward definition to break circular type reference between pin and filter */ struct __PaWinWdmFilter; typedef struct __PaWinWdmFilter PaWinWdmFilter; /* The Pin structure * A pin is an input or output node, e.g. for audio flow */ typedef struct __PaWinWdmPin { HANDLE handle; PaWinWdmFilter* parentFilter; unsigned long pinId; KSPIN_CONNECT* pinConnect; unsigned long pinConnectSize; KSDATAFORMAT_WAVEFORMATEX* ksDataFormatWfx; KSPIN_COMMUNICATION communication; KSDATARANGE* dataRanges; KSMULTIPLE_ITEM* dataRangesItem; KSPIN_DATAFLOW dataFlow; KSPIN_CINSTANCES instances; unsigned long frameSize; int maxChannels; unsigned long formats; int bestSampleRate; } PaWinWdmPin; /* The Filter structure * A filter has a number of pins and a "friendly name" */ struct __PaWinWdmFilter { HANDLE handle; int pinCount; PaWinWdmPin** pins; TCHAR filterName[MAX_PATH]; TCHAR friendlyName[MAX_PATH]; int maxInputChannels; int maxOutputChannels; unsigned long formats; int usageCount; int bestSampleRate; }; /* PaWinWdmHostApiRepresentation - host api datastructure specific to this implementation */ typedef struct __PaWinWdmHostApiRepresentation { PaUtilHostApiRepresentation inheritedHostApiRep; PaUtilStreamInterface callbackStreamInterface; PaUtilStreamInterface blockingStreamInterface; PaUtilAllocationGroup* allocations; PaWinWdmFilter** filters; int filterCount; } PaWinWdmHostApiRepresentation; typedef struct __PaWinWdmDeviceInfo { PaDeviceInfo inheritedDeviceInfo; PaWinWdmFilter* filter; } PaWinWdmDeviceInfo; typedef struct __DATAPACKET { KSSTREAM_HEADER Header; OVERLAPPED Signal; } DATAPACKET; /* PaWinWdmStream - a stream data structure specifically for this implementation */ typedef struct __PaWinWdmStream { PaUtilStreamRepresentation streamRepresentation; PaUtilCpuLoadMeasurer cpuLoadMeasurer; PaUtilBufferProcessor bufferProcessor; PaWinWdmPin* recordingPin; PaWinWdmPin* playbackPin; char* hostBuffer; unsigned long framesPerHostIBuffer; unsigned long framesPerHostOBuffer; int bytesPerInputFrame; int bytesPerOutputFrame; int streamStarted; int streamActive; int streamStop; int streamAbort; int oldProcessPriority; HANDLE streamThread; HANDLE events[5]; /* 2 play + 2 record packets + abort events */ DATAPACKET packets[4]; /* 2 play + 2 record */ PaStreamFlags streamFlags; /* These values handle the case where the user wants to use fewer * channels than the device has */ int userInputChannels; int deviceInputChannels; int userOutputChannels; int deviceOutputChannels; int inputSampleSize; int outputSampleSize; } PaWinWdmStream; #include HMODULE DllKsUser = NULL; KSCREATEPIN* FunctionKsCreatePin = NULL; /* prototypes for functions declared in this file */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ PaError PaWinWdm_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); #ifdef __cplusplus } #endif /* __cplusplus */ /* Low level I/O functions */ static PaError WdmSyncIoctl(HANDLE handle, unsigned long ioctlNumber, void* inBuffer, unsigned long inBufferCount, void* outBuffer, unsigned long outBufferCount, unsigned long* bytesReturned); static PaError WdmGetPropertySimple(HANDLE handle, const GUID* const guidPropertySet, unsigned long property, void* value, unsigned long valueCount, void* instance, unsigned long instanceCount); static PaError WdmSetPropertySimple(HANDLE handle, const GUID* const guidPropertySet, unsigned long property, void* value, unsigned long valueCount, void* instance, unsigned long instanceCount); static PaError WdmGetPinPropertySimple(HANDLE handle, unsigned long pinId, const GUID* const guidPropertySet, unsigned long property, void* value, unsigned long valueCount); static PaError WdmGetPinPropertyMulti(HANDLE handle, unsigned long pinId, const GUID* const guidPropertySet, unsigned long property, KSMULTIPLE_ITEM** ksMultipleItem); /** Pin management functions */ static PaWinWdmPin* PinNew(PaWinWdmFilter* parentFilter, unsigned long pinId, PaError* error); static void PinFree(PaWinWdmPin* pin); static void PinClose(PaWinWdmPin* pin); static PaError PinInstantiate(PaWinWdmPin* pin); /*static PaError PinGetState(PaWinWdmPin* pin, KSSTATE* state); NOT USED */ static PaError PinSetState(PaWinWdmPin* pin, KSSTATE state); static PaError PinSetFormat(PaWinWdmPin* pin, const WAVEFORMATEX* format); static PaError PinIsFormatSupported(PaWinWdmPin* pin, const WAVEFORMATEX* format); /* Filter management functions */ static PaWinWdmFilter* FilterNew( TCHAR* filterName, TCHAR* friendlyName, PaError* error); static void FilterFree(PaWinWdmFilter* filter); static PaWinWdmPin* FilterCreateRenderPin( PaWinWdmFilter* filter, const WAVEFORMATEX* wfex, PaError* error); static PaWinWdmPin* FilterFindViableRenderPin( PaWinWdmFilter* filter, const WAVEFORMATEX* wfex, PaError* error); static PaError FilterCanCreateRenderPin( PaWinWdmFilter* filter, const WAVEFORMATEX* wfex); static PaWinWdmPin* FilterCreateCapturePin( PaWinWdmFilter* filter, const WAVEFORMATEX* wfex, PaError* error); static PaWinWdmPin* FilterFindViableCapturePin( PaWinWdmFilter* filter, const WAVEFORMATEX* wfex, PaError* error); static PaError FilterCanCreateCapturePin( PaWinWdmFilter* filter, const WAVEFORMATEX* pwfx); static PaError FilterUse( PaWinWdmFilter* filter); static void FilterRelease( PaWinWdmFilter* filter); /* Interface functions */ static void Terminate( struct PaUtilHostApiRepresentation *hostApi ); static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ); static PaError CloseStream( PaStream* stream ); static PaError StartStream( PaStream *stream ); static PaError StopStream( PaStream *stream ); static PaError AbortStream( PaStream *stream ); static PaError IsStreamStopped( PaStream *s ); static PaError IsStreamActive( PaStream *stream ); static PaTime GetStreamTime( PaStream *stream ); static double GetStreamCpuLoad( PaStream* stream ); static PaError ReadStream( PaStream* stream, void *buffer, unsigned long frames ); static PaError WriteStream( PaStream* stream, const void *buffer, unsigned long frames ); static signed long GetStreamReadAvailable( PaStream* stream ); static signed long GetStreamWriteAvailable( PaStream* stream ); /* Utility functions */ static unsigned long GetWfexSize(const WAVEFORMATEX* wfex); static PaError BuildFilterList(PaWinWdmHostApiRepresentation* wdmHostApi); static BOOL PinWrite(HANDLE h, DATAPACKET* p); static BOOL PinRead(HANDLE h, DATAPACKET* p); static void DuplicateFirstChannelInt16(void* buffer, int channels, int samples); static void DuplicateFirstChannelInt24(void* buffer, int channels, int samples); static DWORD WINAPI ProcessingThread(LPVOID pParam); /* Function bodies */ static unsigned long GetWfexSize(const WAVEFORMATEX* wfex) { if( wfex->wFormatTag == WAVE_FORMAT_PCM ) { return sizeof( WAVEFORMATEX ); } else { return (sizeof( WAVEFORMATEX ) + wfex->cbSize); } } /* Low level pin/filter access functions */ static PaError WdmSyncIoctl( HANDLE handle, unsigned long ioctlNumber, void* inBuffer, unsigned long inBufferCount, void* outBuffer, unsigned long outBufferCount, unsigned long* bytesReturned) { PaError result = paNoError; OVERLAPPED overlapped; int boolResult; unsigned long dummyBytesReturned; unsigned long error; if( !bytesReturned ) { /* User a dummy as the caller hasn't supplied one */ bytesReturned = &dummyBytesReturned; } FillMemory((void *)&overlapped,sizeof(overlapped),0); overlapped.hEvent = CreateEvent(NULL,FALSE,FALSE,NULL); if( !overlapped.hEvent ) { result = paInsufficientMemory; goto error; } overlapped.hEvent = (HANDLE)((DWORD_PTR)overlapped.hEvent | 0x1); boolResult = DeviceIoControl(handle, ioctlNumber, inBuffer, inBufferCount, outBuffer, outBufferCount, bytesReturned, &overlapped); if( !boolResult ) { error = GetLastError(); if( error == ERROR_IO_PENDING ) { error = WaitForSingleObject(overlapped.hEvent,INFINITE); if( error != WAIT_OBJECT_0 ) { result = paUnanticipatedHostError; goto error; } } else if((( error == ERROR_INSUFFICIENT_BUFFER ) || ( error == ERROR_MORE_DATA )) && ( ioctlNumber == IOCTL_KS_PROPERTY ) && ( outBufferCount == 0 )) { boolResult = TRUE; } else { result = paUnanticipatedHostError; } } if( !boolResult ) *bytesReturned = 0; error: if( overlapped.hEvent ) { CloseHandle( overlapped.hEvent ); } return result; } static PaError WdmGetPropertySimple(HANDLE handle, const GUID* const guidPropertySet, unsigned long property, void* value, unsigned long valueCount, void* instance, unsigned long instanceCount) { PaError result; KSPROPERTY* ksProperty; unsigned long propertyCount; propertyCount = sizeof(KSPROPERTY) + instanceCount; ksProperty = (KSPROPERTY*)PaUtil_AllocateMemory( propertyCount ); if( !ksProperty ) { return paInsufficientMemory; } FillMemory((void*)ksProperty,sizeof(ksProperty),0); ksProperty->Set = *guidPropertySet; ksProperty->Id = property; ksProperty->Flags = KSPROPERTY_TYPE_GET; if( instance ) { memcpy( (void*)(((char*)ksProperty)+sizeof(KSPROPERTY)), instance, instanceCount ); } result = WdmSyncIoctl( handle, IOCTL_KS_PROPERTY, ksProperty, propertyCount, value, valueCount, NULL); PaUtil_FreeMemory( ksProperty ); return result; } static PaError WdmSetPropertySimple( HANDLE handle, const GUID* const guidPropertySet, unsigned long property, void* value, unsigned long valueCount, void* instance, unsigned long instanceCount) { PaError result; KSPROPERTY* ksProperty; unsigned long propertyCount = 0; propertyCount = sizeof(KSPROPERTY) + instanceCount; ksProperty = (KSPROPERTY*)PaUtil_AllocateMemory( propertyCount ); if( !ksProperty ) { return paInsufficientMemory; } ksProperty->Set = *guidPropertySet; ksProperty->Id = property; ksProperty->Flags = KSPROPERTY_TYPE_SET; if( instance ) { memcpy((void*)((char*)ksProperty + sizeof(KSPROPERTY)), instance, instanceCount); } result = WdmSyncIoctl( handle, IOCTL_KS_PROPERTY, ksProperty, propertyCount, value, valueCount, NULL); PaUtil_FreeMemory( ksProperty ); return result; } static PaError WdmGetPinPropertySimple( HANDLE handle, unsigned long pinId, const GUID* const guidPropertySet, unsigned long property, void* value, unsigned long valueCount) { PaError result; KSP_PIN ksPProp; ksPProp.Property.Set = *guidPropertySet; ksPProp.Property.Id = property; ksPProp.Property.Flags = KSPROPERTY_TYPE_GET; ksPProp.PinId = pinId; ksPProp.Reserved = 0; result = WdmSyncIoctl( handle, IOCTL_KS_PROPERTY, &ksPProp, sizeof(KSP_PIN), value, valueCount, NULL); return result; } static PaError WdmGetPinPropertyMulti( HANDLE handle, unsigned long pinId, const GUID* const guidPropertySet, unsigned long property, KSMULTIPLE_ITEM** ksMultipleItem) { PaError result; unsigned long multipleItemSize = 0; KSP_PIN ksPProp; ksPProp.Property.Set = *guidPropertySet; ksPProp.Property.Id = property; ksPProp.Property.Flags = KSPROPERTY_TYPE_GET; ksPProp.PinId = pinId; ksPProp.Reserved = 0; result = WdmSyncIoctl( handle, IOCTL_KS_PROPERTY, &ksPProp.Property, sizeof(KSP_PIN), NULL, 0, &multipleItemSize); if( result != paNoError ) { return result; } *ksMultipleItem = (KSMULTIPLE_ITEM*)PaUtil_AllocateMemory( multipleItemSize ); if( !*ksMultipleItem ) { return paInsufficientMemory; } result = WdmSyncIoctl( handle, IOCTL_KS_PROPERTY, &ksPProp, sizeof(KSP_PIN), (void*)*ksMultipleItem, multipleItemSize, NULL); if( result != paNoError ) { PaUtil_FreeMemory( ksMultipleItem ); } return result; } /* Create a new pin object belonging to a filter The pin object holds all the configuration information about the pin before it is opened, and then the handle of the pin after is opened */ static PaWinWdmPin* PinNew(PaWinWdmFilter* parentFilter, unsigned long pinId, PaError* error) { PaWinWdmPin* pin; PaError result; unsigned long i; KSMULTIPLE_ITEM* item = NULL; KSIDENTIFIER* identifier; KSDATARANGE* dataRange; PA_LOGE_; PA_DEBUG(("Creating pin %d:\n",pinId)); /* Allocate the new PIN object */ pin = (PaWinWdmPin*)PaUtil_AllocateMemory( sizeof(PaWinWdmPin) ); if( !pin ) { result = paInsufficientMemory; goto error; } /* Zero the pin object */ /* memset( (void*)pin, 0, sizeof(PaWinWdmPin) ); */ pin->parentFilter = parentFilter; pin->pinId = pinId; /* Allocate a connect structure */ pin->pinConnectSize = sizeof(KSPIN_CONNECT) + sizeof(KSDATAFORMAT_WAVEFORMATEX); pin->pinConnect = (KSPIN_CONNECT*)PaUtil_AllocateMemory( pin->pinConnectSize ); if( !pin->pinConnect ) { result = paInsufficientMemory; goto error; } /* Configure the connect structure with default values */ pin->pinConnect->Interface.Set = KSINTERFACESETID_Standard; pin->pinConnect->Interface.Id = KSINTERFACE_STANDARD_STREAMING; pin->pinConnect->Interface.Flags = 0; pin->pinConnect->Medium.Set = KSMEDIUMSETID_Standard; pin->pinConnect->Medium.Id = KSMEDIUM_TYPE_ANYINSTANCE; pin->pinConnect->Medium.Flags = 0; pin->pinConnect->PinId = pinId; pin->pinConnect->PinToHandle = NULL; pin->pinConnect->Priority.PriorityClass = KSPRIORITY_NORMAL; pin->pinConnect->Priority.PrioritySubClass = 1; pin->ksDataFormatWfx = (KSDATAFORMAT_WAVEFORMATEX*)(pin->pinConnect + 1); pin->ksDataFormatWfx->DataFormat.FormatSize = sizeof(KSDATAFORMAT_WAVEFORMATEX); pin->ksDataFormatWfx->DataFormat.Flags = 0; pin->ksDataFormatWfx->DataFormat.Reserved = 0; pin->ksDataFormatWfx->DataFormat.MajorFormat = KSDATAFORMAT_TYPE_AUDIO; pin->ksDataFormatWfx->DataFormat.SubFormat = KSDATAFORMAT_SUBTYPE_PCM; pin->ksDataFormatWfx->DataFormat.Specifier = KSDATAFORMAT_SPECIFIER_WAVEFORMATEX; pin->frameSize = 0; /* Unknown until we instantiate pin */ /* Get the COMMUNICATION property */ result = WdmGetPinPropertySimple( parentFilter->handle, pinId, &KSPROPSETID_Pin, KSPROPERTY_PIN_COMMUNICATION, &pin->communication, sizeof(KSPIN_COMMUNICATION)); if( result != paNoError ) goto error; if( /*(pin->communication != KSPIN_COMMUNICATION_SOURCE) &&*/ (pin->communication != KSPIN_COMMUNICATION_SINK) && (pin->communication != KSPIN_COMMUNICATION_BOTH) ) { PA_DEBUG(("Not source/sink\n")); result = paInvalidDevice; goto error; } /* Get dataflow information */ result = WdmGetPinPropertySimple( parentFilter->handle, pinId, &KSPROPSETID_Pin, KSPROPERTY_PIN_DATAFLOW, &pin->dataFlow, sizeof(KSPIN_DATAFLOW)); if( result != paNoError ) goto error; /* Get the INTERFACE property list */ result = WdmGetPinPropertyMulti( parentFilter->handle, pinId, &KSPROPSETID_Pin, KSPROPERTY_PIN_INTERFACES, &item); if( result != paNoError ) goto error; identifier = (KSIDENTIFIER*)(item+1); /* Check that at least one interface is STANDARD_STREAMING */ result = paUnanticipatedHostError; for( i = 0; i < item->Count; i++ ) { if( !memcmp( (void*)&identifier[i].Set, (void*)&KSINTERFACESETID_Standard, sizeof( GUID ) ) && ( identifier[i].Id == KSINTERFACE_STANDARD_STREAMING ) ) { result = paNoError; break; } } if( result != paNoError ) { PA_DEBUG(("No standard streaming\n")); goto error; } /* Don't need interfaces any more */ PaUtil_FreeMemory( item ); item = NULL; /* Get the MEDIUM properties list */ result = WdmGetPinPropertyMulti( parentFilter->handle, pinId, &KSPROPSETID_Pin, KSPROPERTY_PIN_MEDIUMS, &item); if( result != paNoError ) goto error; identifier = (KSIDENTIFIER*)(item+1); /* Not actually necessary... */ /* Check that at least one medium is STANDARD_DEVIO */ result = paUnanticipatedHostError; for( i = 0; i < item->Count; i++ ) { if( !memcmp( (void*)&identifier[i].Set, (void*)&KSMEDIUMSETID_Standard, sizeof( GUID ) ) && ( identifier[i].Id == KSMEDIUM_STANDARD_DEVIO ) ) { result = paNoError; break; } } if( result != paNoError ) { PA_DEBUG(("No standard devio\n")); goto error; } /* Don't need mediums any more */ PaUtil_FreeMemory( item ); item = NULL; /* Get DATARANGES */ result = WdmGetPinPropertyMulti( parentFilter->handle, pinId, &KSPROPSETID_Pin, KSPROPERTY_PIN_DATARANGES, &pin->dataRangesItem); if( result != paNoError ) goto error; pin->dataRanges = (KSDATARANGE*)(pin->dataRangesItem +1); /* Check that at least one datarange supports audio */ result = paUnanticipatedHostError; dataRange = pin->dataRanges; pin->maxChannels = 0; pin->bestSampleRate = 0; pin->formats = 0; for( i = 0; i dataRangesItem->Count; i++) { PA_DEBUG(("DR major format %x\n",*(unsigned long*)(&(dataRange->MajorFormat)))); /* Check that subformat is WAVEFORMATEX, PCM or WILDCARD */ if( IS_VALID_WAVEFORMATEX_GUID(&dataRange->SubFormat) || !memcmp((void*)&dataRange->SubFormat, (void*)&KSDATAFORMAT_SUBTYPE_PCM, sizeof ( GUID ) ) || ( !memcmp((void*)&dataRange->SubFormat, (void*)&KSDATAFORMAT_SUBTYPE_WILDCARD, sizeof ( GUID ) ) && ( !memcmp((void*)&dataRange->MajorFormat, (void*)&KSDATAFORMAT_TYPE_AUDIO, sizeof ( GUID ) ) ) ) ) { result = paNoError; /* Record the maximum possible channels with this pin */ PA_DEBUG(("MaxChannel: %d\n",pin->maxChannels)); if( (int)((KSDATARANGE_AUDIO*)dataRange)->MaximumChannels > pin->maxChannels ) { pin->maxChannels = ((KSDATARANGE_AUDIO*)dataRange)->MaximumChannels; /*PA_DEBUG(("MaxChannel: %d\n",pin->maxChannels));*/ } /* Record the formats (bit depths) that are supported */ if( ((KSDATARANGE_AUDIO*)dataRange)->MinimumBitsPerSample <= 16 ) { pin->formats |= paInt16; PA_DEBUG(("Format 16 bit supported\n")); } if( ((KSDATARANGE_AUDIO*)dataRange)->MaximumBitsPerSample >= 24 ) { pin->formats |= paInt24; PA_DEBUG(("Format 24 bit supported\n")); } if( ( pin->bestSampleRate != 48000) && (((KSDATARANGE_AUDIO*)dataRange)->MaximumSampleFrequency >= 48000) && (((KSDATARANGE_AUDIO*)dataRange)->MinimumSampleFrequency <= 48000) ) { pin->bestSampleRate = 48000; PA_DEBUG(("48kHz supported\n")); } else if(( pin->bestSampleRate != 48000) && ( pin->bestSampleRate != 44100 ) && (((KSDATARANGE_AUDIO*)dataRange)->MaximumSampleFrequency >= 44100) && (((KSDATARANGE_AUDIO*)dataRange)->MinimumSampleFrequency <= 44100) ) { pin->bestSampleRate = 44100; PA_DEBUG(("44.1kHz supported\n")); } else { pin->bestSampleRate = ((KSDATARANGE_AUDIO*)dataRange)->MaximumSampleFrequency; } } dataRange = (KSDATARANGE*)( ((char*)dataRange) + dataRange->FormatSize); } if( result != paNoError ) goto error; /* Get instance information */ result = WdmGetPinPropertySimple( parentFilter->handle, pinId, &KSPROPSETID_Pin, KSPROPERTY_PIN_CINSTANCES, &pin->instances, sizeof(KSPIN_CINSTANCES)); if( result != paNoError ) goto error; /* Success */ *error = paNoError; PA_DEBUG(("Pin created successfully\n")); PA_LOGL_; return pin; error: /* Error cleanup */ PaUtil_FreeMemory( item ); if( pin ) { PaUtil_FreeMemory( pin->pinConnect ); PaUtil_FreeMemory( pin->dataRangesItem ); PaUtil_FreeMemory( pin ); } *error = result; PA_LOGL_; return NULL; } /* Safely free all resources associated with the pin */ static void PinFree(PaWinWdmPin* pin) { PA_LOGE_; if( pin ) { PinClose(pin); if( pin->pinConnect ) { PaUtil_FreeMemory( pin->pinConnect ); } if( pin->dataRangesItem ) { PaUtil_FreeMemory( pin->dataRangesItem ); } PaUtil_FreeMemory( pin ); } PA_LOGL_; } /* If the pin handle is open, close it */ static void PinClose(PaWinWdmPin* pin) { PA_LOGE_; if( pin == NULL ) { PA_DEBUG(("Closing NULL pin!")); PA_LOGL_; return; } if( pin->handle != NULL ) { PinSetState( pin, KSSTATE_PAUSE ); PinSetState( pin, KSSTATE_STOP ); CloseHandle( pin->handle ); pin->handle = NULL; FilterRelease(pin->parentFilter); } PA_LOGL_; } /* Set the state of this (instantiated) pin */ static PaError PinSetState(PaWinWdmPin* pin, KSSTATE state) { PaError result; PA_LOGE_; if( pin == NULL ) return paInternalError; if( pin->handle == NULL ) return paInternalError; result = WdmSetPropertySimple( pin->handle, &KSPROPSETID_Connection, KSPROPERTY_CONNECTION_STATE, &state, sizeof(state), NULL, 0); PA_LOGL_; return result; } static PaError PinInstantiate(PaWinWdmPin* pin) { PaError result; unsigned long createResult; KSALLOCATOR_FRAMING ksaf; KSALLOCATOR_FRAMING_EX ksafex; PA_LOGE_; if( pin == NULL ) return paInternalError; if(!pin->pinConnect) return paInternalError; FilterUse(pin->parentFilter); createResult = FunctionKsCreatePin( pin->parentFilter->handle, pin->pinConnect, GENERIC_WRITE | GENERIC_READ, &pin->handle ); PA_DEBUG(("Pin create result = %x\n",createResult)); if( createResult != ERROR_SUCCESS ) { FilterRelease(pin->parentFilter); pin->handle = NULL; return paInvalidDevice; } result = WdmGetPropertySimple( pin->handle, &KSPROPSETID_Connection, KSPROPERTY_CONNECTION_ALLOCATORFRAMING, &ksaf, sizeof(ksaf), NULL, 0); if( result != paNoError ) { result = WdmGetPropertySimple( pin->handle, &KSPROPSETID_Connection, KSPROPERTY_CONNECTION_ALLOCATORFRAMING_EX, &ksafex, sizeof(ksafex), NULL, 0); if( result == paNoError ) { pin->frameSize = ksafex.FramingItem[0].FramingRange.Range.MinFrameSize; } } else { pin->frameSize = ksaf.FrameSize; } PA_LOGL_; return paNoError; } /* NOT USED static PaError PinGetState(PaWinWdmPin* pin, KSSTATE* state) { PaError result; if( state == NULL ) return paInternalError; if( pin == NULL ) return paInternalError; if( pin->handle == NULL ) return paInternalError; result = WdmGetPropertySimple( pin->handle, KSPROPSETID_Connection, KSPROPERTY_CONNECTION_STATE, state, sizeof(KSSTATE), NULL, 0); return result; } */ static PaError PinSetFormat(PaWinWdmPin* pin, const WAVEFORMATEX* format) { unsigned long size; void* newConnect; PA_LOGE_; if( pin == NULL ) return paInternalError; if( format == NULL ) return paInternalError; size = GetWfexSize(format) + sizeof(KSPIN_CONNECT) + sizeof(KSDATAFORMAT_WAVEFORMATEX) - sizeof(WAVEFORMATEX); if( pin->pinConnectSize != size ) { newConnect = PaUtil_AllocateMemory( size ); if( newConnect == NULL ) return paInsufficientMemory; memcpy( newConnect, (void*)pin->pinConnect, min(pin->pinConnectSize,size) ); PaUtil_FreeMemory( pin->pinConnect ); pin->pinConnect = (KSPIN_CONNECT*)newConnect; pin->pinConnectSize = size; pin->ksDataFormatWfx = (KSDATAFORMAT_WAVEFORMATEX*)((KSPIN_CONNECT*)newConnect + 1); pin->ksDataFormatWfx->DataFormat.FormatSize = size - sizeof(KSPIN_CONNECT); } memcpy( (void*)&(pin->ksDataFormatWfx->WaveFormatEx), format, GetWfexSize(format) ); pin->ksDataFormatWfx->DataFormat.SampleSize = (unsigned short)(format->nChannels * (format->wBitsPerSample / 8)); PA_LOGL_; return paNoError; } static PaError PinIsFormatSupported(PaWinWdmPin* pin, const WAVEFORMATEX* format) { KSDATARANGE_AUDIO* dataRange; unsigned long count; GUID guid = DYNAMIC_GUID( DEFINE_WAVEFORMATEX_GUID(format->wFormatTag) ); PaError result = paInvalidDevice; PA_LOGE_; if( format->wFormatTag == WAVE_FORMAT_EXTENSIBLE ) { guid = ((WAVEFORMATEXTENSIBLE*)format)->SubFormat; } dataRange = (KSDATARANGE_AUDIO*)pin->dataRanges; for(count = 0; countdataRangesItem->Count; count++) { if(( !memcmp(&(dataRange->DataRange.MajorFormat),&KSDATAFORMAT_TYPE_AUDIO,sizeof(GUID)) ) || ( !memcmp(&(dataRange->DataRange.MajorFormat),&KSDATAFORMAT_TYPE_WILDCARD,sizeof(GUID)) )) { /* This is an audio or wildcard datarange... */ if(( !memcmp(&(dataRange->DataRange.SubFormat),&KSDATAFORMAT_SUBTYPE_WILDCARD,sizeof(GUID)) ) || ( !memcmp(&(dataRange->DataRange.SubFormat),&guid,sizeof(GUID)) )) { if(( !memcmp(&(dataRange->DataRange.Specifier),&KSDATAFORMAT_SPECIFIER_WILDCARD,sizeof(GUID)) ) || ( !memcmp(&(dataRange->DataRange.Specifier),&KSDATAFORMAT_SPECIFIER_WAVEFORMATEX,sizeof(GUID) ))) { PA_DEBUG(("Pin:%x, DataRange:%d\n",(void*)pin,count)); PA_DEBUG(("\tFormatSize:%d, SampleSize:%d\n",dataRange->DataRange.FormatSize,dataRange->DataRange.SampleSize)); PA_DEBUG(("\tMaxChannels:%d\n",dataRange->MaximumChannels)); PA_DEBUG(("\tBits:%d-%d\n",dataRange->MinimumBitsPerSample,dataRange->MaximumBitsPerSample)); PA_DEBUG(("\tSampleRate:%d-%d\n",dataRange->MinimumSampleFrequency,dataRange->MaximumSampleFrequency)); if( dataRange->MaximumChannels < format->nChannels ) { result = paInvalidChannelCount; continue; } if( dataRange->MinimumBitsPerSample > format->wBitsPerSample ) { result = paSampleFormatNotSupported; continue; } if( dataRange->MaximumBitsPerSample < format->wBitsPerSample ) { result = paSampleFormatNotSupported; continue; } if( dataRange->MinimumSampleFrequency > format->nSamplesPerSec ) { result = paInvalidSampleRate; continue; } if( dataRange->MaximumSampleFrequency < format->nSamplesPerSec ) { result = paInvalidSampleRate; continue; } /* Success! */ PA_LOGL_; return paNoError; } } } dataRange = (KSDATARANGE_AUDIO*)( ((char*)dataRange) + dataRange->DataRange.FormatSize); } PA_LOGL_; return result; } /** * Create a new filter object */ static PaWinWdmFilter* FilterNew(TCHAR* filterName, TCHAR* friendlyName, PaError* error) { PaWinWdmFilter* filter; PaError result; int pinId; int valid; /* Allocate the new filter object */ filter = (PaWinWdmFilter*)PaUtil_AllocateMemory( sizeof(PaWinWdmFilter) ); if( !filter ) { result = paInsufficientMemory; goto error; } /* Zero the filter object - done by AllocateMemory */ /* memset( (void*)filter, 0, sizeof(PaWinWdmFilter) ); */ /* Copy the filter name */ _tcsncpy(filter->filterName, filterName, MAX_PATH); /* Copy the friendly name */ _tcsncpy(filter->friendlyName, friendlyName, MAX_PATH); /* Open the filter handle */ result = FilterUse(filter); if( result != paNoError ) { goto error; } /* Get pin count */ result = WdmGetPinPropertySimple ( filter->handle, 0, &KSPROPSETID_Pin, KSPROPERTY_PIN_CTYPES, &filter->pinCount, sizeof(filter->pinCount) ); if( result != paNoError) { goto error; } /* Allocate pointer array to hold the pins */ filter->pins = (PaWinWdmPin**)PaUtil_AllocateMemory( sizeof(PaWinWdmPin*) * filter->pinCount ); if( !filter->pins ) { result = paInsufficientMemory; goto error; } /* Create all the pins we can */ filter->maxInputChannels = 0; filter->maxOutputChannels = 0; filter->bestSampleRate = 0; valid = 0; for(pinId = 0; pinId < filter->pinCount; pinId++) { /* Create the pin with this Id */ PaWinWdmPin* newPin; newPin = PinNew(filter, pinId, &result); if( result == paInsufficientMemory ) goto error; if( newPin != NULL ) { filter->pins[pinId] = newPin; valid = 1; /* Get the max output channel count */ if(( newPin->dataFlow == KSPIN_DATAFLOW_IN ) && (( newPin->communication == KSPIN_COMMUNICATION_SINK) || ( newPin->communication == KSPIN_COMMUNICATION_BOTH))) { if(newPin->maxChannels > filter->maxOutputChannels) filter->maxOutputChannels = newPin->maxChannels; filter->formats |= newPin->formats; } /* Get the max input channel count */ if(( newPin->dataFlow == KSPIN_DATAFLOW_OUT ) && (( newPin->communication == KSPIN_COMMUNICATION_SINK) || ( newPin->communication == KSPIN_COMMUNICATION_BOTH))) { if(newPin->maxChannels > filter->maxInputChannels) filter->maxInputChannels = newPin->maxChannels; filter->formats |= newPin->formats; } if(newPin->bestSampleRate > filter->bestSampleRate) { filter->bestSampleRate = newPin->bestSampleRate; } } } if(( filter->maxInputChannels == 0) && ( filter->maxOutputChannels == 0)) { /* No input or output... not valid */ valid = 0; } if( !valid ) { /* No valid pin was found on this filter so we destroy it */ result = paDeviceUnavailable; goto error; } /* Close the filter handle for now * It will be opened later when needed */ FilterRelease(filter); *error = paNoError; return filter; error: /* Error cleanup */ if( filter ) { for( pinId = 0; pinId < filter->pinCount; pinId++ ) PinFree(filter->pins[pinId]); PaUtil_FreeMemory( filter->pins ); if( filter->handle ) CloseHandle( filter->handle ); PaUtil_FreeMemory( filter ); } *error = result; return NULL; } /** * Free a previously created filter */ static void FilterFree(PaWinWdmFilter* filter) { int pinId; PA_LOGL_; if( filter ) { for( pinId = 0; pinId < filter->pinCount; pinId++ ) PinFree(filter->pins[pinId]); PaUtil_FreeMemory( filter->pins ); if( filter->handle ) CloseHandle( filter->handle ); PaUtil_FreeMemory( filter ); } PA_LOGE_; } /** * Reopen the filter handle if necessary so it can be used **/ static PaError FilterUse(PaWinWdmFilter* filter) { assert( filter ); PA_LOGE_; if( filter->handle == NULL ) { /* Open the filter */ filter->handle = CreateFile( filter->filterName, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL | FILE_FLAG_OVERLAPPED, NULL); if( filter->handle == NULL ) { return paDeviceUnavailable; } } filter->usageCount++; PA_LOGL_; return paNoError; } /** * Release the filter handle if nobody is using it **/ static void FilterRelease(PaWinWdmFilter* filter) { assert( filter ); assert( filter->usageCount > 0 ); PA_LOGE_; filter->usageCount--; if( filter->usageCount == 0 ) { if( filter->handle != NULL ) { CloseHandle( filter->handle ); filter->handle = NULL; } } PA_LOGL_; } /** * Create a render (playback) Pin using the supplied format **/ static PaWinWdmPin* FilterCreateRenderPin(PaWinWdmFilter* filter, const WAVEFORMATEX* wfex, PaError* error) { PaError result; PaWinWdmPin* pin; assert( filter ); pin = FilterFindViableRenderPin(filter,wfex,&result); if(!pin) { goto error; } result = PinSetFormat(pin,wfex); if( result != paNoError ) { goto error; } result = PinInstantiate(pin); if( result != paNoError ) { goto error; } *error = paNoError; return pin; error: *error = result; return NULL; } /** * Find a pin that supports the given format **/ static PaWinWdmPin* FilterFindViableRenderPin(PaWinWdmFilter* filter, const WAVEFORMATEX* wfex, PaError* error) { int pinId; PaWinWdmPin* pin; PaError result = paDeviceUnavailable; *error = paNoError; assert( filter ); for( pinId = 0; pinIdpinCount; pinId++ ) { pin = filter->pins[pinId]; if( pin != NULL ) { if(( pin->dataFlow == KSPIN_DATAFLOW_IN ) && (( pin->communication == KSPIN_COMMUNICATION_SINK) || ( pin->communication == KSPIN_COMMUNICATION_BOTH))) { result = PinIsFormatSupported( pin, wfex ); if( result == paNoError ) { return pin; } } } } *error = result; return NULL; } /** * Check if there is a pin that should playback * with the supplied format **/ static PaError FilterCanCreateRenderPin(PaWinWdmFilter* filter, const WAVEFORMATEX* wfex) { PaWinWdmPin* pin; PaError result; assert ( filter ); pin = FilterFindViableRenderPin(filter,wfex,&result); /* result will be paNoError if pin found * or else an error code indicating what is wrong with the format **/ return result; } /** * Create a capture (record) Pin using the supplied format **/ static PaWinWdmPin* FilterCreateCapturePin(PaWinWdmFilter* filter, const WAVEFORMATEX* wfex, PaError* error) { PaError result; PaWinWdmPin* pin; assert( filter ); pin = FilterFindViableCapturePin(filter,wfex,&result); if(!pin) { goto error; } result = PinSetFormat(pin,wfex); if( result != paNoError ) { goto error; } result = PinInstantiate(pin); if( result != paNoError ) { goto error; } *error = paNoError; return pin; error: *error = result; return NULL; } /** * Find a capture pin that supports the given format **/ static PaWinWdmPin* FilterFindViableCapturePin(PaWinWdmFilter* filter, const WAVEFORMATEX* wfex, PaError* error) { int pinId; PaWinWdmPin* pin; PaError result = paDeviceUnavailable; *error = paNoError; assert( filter ); for( pinId = 0; pinIdpinCount; pinId++ ) { pin = filter->pins[pinId]; if( pin != NULL ) { if(( pin->dataFlow == KSPIN_DATAFLOW_OUT ) && (( pin->communication == KSPIN_COMMUNICATION_SINK) || ( pin->communication == KSPIN_COMMUNICATION_BOTH))) { result = PinIsFormatSupported( pin, wfex ); if( result == paNoError ) { return pin; } } } } *error = result; return NULL; } /** * Check if there is a pin that should playback * with the supplied format **/ static PaError FilterCanCreateCapturePin(PaWinWdmFilter* filter, const WAVEFORMATEX* wfex) { PaWinWdmPin* pin; PaError result; assert ( filter ); pin = FilterFindViableCapturePin(filter,wfex,&result); /* result will be paNoError if pin found * or else an error code indicating what is wrong with the format **/ return result; } /** * Build the list of available filters * Use the SetupDi API to enumerate all devices in the KSCATEGORY_AUDIO which * have a KSCATEGORY_RENDER or KSCATEGORY_CAPTURE alias. For each of these * devices initialise a PaWinWdmFilter structure by calling our NewFilter() * function. We enumerate devices twice, once to count how many there are, * and once to initialize the PaWinWdmFilter structures. */ static PaError BuildFilterList(PaWinWdmHostApiRepresentation* wdmHostApi) { PaError result = paNoError; HDEVINFO handle = NULL; int device; int invalidDevices; int slot; SP_DEVICE_INTERFACE_DATA interfaceData; SP_DEVICE_INTERFACE_DATA aliasData; SP_DEVINFO_DATA devInfoData; int noError; const int sizeInterface = sizeof(SP_DEVICE_INTERFACE_DETAIL_DATA) + (MAX_PATH * sizeof(WCHAR)); unsigned char interfaceDetailsArray[sizeof(SP_DEVICE_INTERFACE_DETAIL_DATA) + (MAX_PATH * sizeof(WCHAR))]; SP_DEVICE_INTERFACE_DETAIL_DATA* devInterfaceDetails = (SP_DEVICE_INTERFACE_DETAIL_DATA*)interfaceDetailsArray; TCHAR friendlyName[MAX_PATH]; HKEY hkey; DWORD sizeFriendlyName; DWORD type; PaWinWdmFilter* newFilter; GUID* category = (GUID*)&KSCATEGORY_AUDIO; GUID* alias_render = (GUID*)&KSCATEGORY_RENDER; GUID* alias_capture = (GUID*)&KSCATEGORY_CAPTURE; DWORD hasAlias; PA_LOGE_; devInterfaceDetails->cbSize = sizeof(SP_DEVICE_INTERFACE_DETAIL_DATA); /* Open a handle to search for devices (filters) */ handle = SetupDiGetClassDevs(category,NULL,NULL,DIGCF_PRESENT | DIGCF_DEVICEINTERFACE); if( handle == NULL ) { return paUnanticipatedHostError; } PA_DEBUG(("Setup called\n")); /* First let's count the number of devices so we can allocate a list */ invalidDevices = 0; for( device = 0;;device++ ) { interfaceData.cbSize = sizeof(SP_DEVICE_INTERFACE_DATA); interfaceData.Reserved = 0; aliasData.cbSize = sizeof(SP_DEVICE_INTERFACE_DATA); aliasData.Reserved = 0; noError = SetupDiEnumDeviceInterfaces(handle,NULL,category,device,&interfaceData); PA_DEBUG(("Enum called\n")); if( !noError ) break; /* No more devices */ /* Check this one has the render or capture alias */ hasAlias = 0; noError = SetupDiGetDeviceInterfaceAlias(handle,&interfaceData,alias_render,&aliasData); PA_DEBUG(("noError = %d\n",noError)); if(noError) { if(aliasData.Flags && (!(aliasData.Flags & SPINT_REMOVED))) { PA_DEBUG(("Device %d has render alias\n",device)); hasAlias |= 1; /* Has render alias */ } else { PA_DEBUG(("Device %d has no render alias\n",device)); } } noError = SetupDiGetDeviceInterfaceAlias(handle,&interfaceData,alias_capture,&aliasData); if(noError) { if(aliasData.Flags && (!(aliasData.Flags & SPINT_REMOVED))) { PA_DEBUG(("Device %d has capture alias\n",device)); hasAlias |= 2; /* Has capture alias */ } else { PA_DEBUG(("Device %d has no capture alias\n",device)); } } if(!hasAlias) invalidDevices++; /* This was not a valid capture or render audio device */ } /* Remember how many there are */ wdmHostApi->filterCount = device-invalidDevices; PA_DEBUG(("Interfaces found: %d\n",device-invalidDevices)); /* Now allocate the list of pointers to devices */ wdmHostApi->filters = (PaWinWdmFilter**)PaUtil_AllocateMemory( sizeof(PaWinWdmFilter*) * device ); if( !wdmHostApi->filters ) { if(handle != NULL) SetupDiDestroyDeviceInfoList(handle); return paInsufficientMemory; } /* Now create filter objects for each interface found */ slot = 0; for( device = 0;;device++ ) { interfaceData.cbSize = sizeof(SP_DEVICE_INTERFACE_DATA); interfaceData.Reserved = 0; aliasData.cbSize = sizeof(SP_DEVICE_INTERFACE_DATA); aliasData.Reserved = 0; devInfoData.cbSize = sizeof(SP_DEVINFO_DATA); devInfoData.Reserved = 0; noError = SetupDiEnumDeviceInterfaces(handle,NULL,category,device,&interfaceData); if( !noError ) break; /* No more devices */ /* Check this one has the render or capture alias */ hasAlias = 0; noError = SetupDiGetDeviceInterfaceAlias(handle,&interfaceData,alias_render,&aliasData); if(noError) { if(aliasData.Flags && (!(aliasData.Flags & SPINT_REMOVED))) { PA_DEBUG(("Device %d has render alias\n",device)); hasAlias |= 1; /* Has render alias */ } } noError = SetupDiGetDeviceInterfaceAlias(handle,&interfaceData,alias_capture,&aliasData); if(noError) { if(aliasData.Flags && (!(aliasData.Flags & SPINT_REMOVED))) { PA_DEBUG(("Device %d has capture alias\n",device)); hasAlias |= 2; /* Has capture alias */ } } if(!hasAlias) continue; /* This was not a valid capture or render audio device */ noError = SetupDiGetDeviceInterfaceDetail(handle,&interfaceData,devInterfaceDetails,sizeInterface,NULL,&devInfoData); if( noError ) { /* Try to get the "friendly name" for this interface */ sizeFriendlyName = sizeof(friendlyName); /* Fix contributed by Ben Allison * Removed KEY_SET_VALUE from flags on following call * as its causes failure when running without admin rights * and it was not required */ hkey=SetupDiOpenDeviceInterfaceRegKey(handle,&interfaceData,0,KEY_QUERY_VALUE); if(hkey!=INVALID_HANDLE_VALUE) { noError = RegQueryValueEx(hkey,TEXT("FriendlyName"),0,&type,(BYTE*)friendlyName,&sizeFriendlyName); if( noError == ERROR_SUCCESS ) { PA_DEBUG(("Interface %d, Name: %s\n",device,friendlyName)); RegCloseKey(hkey); } else { friendlyName[0] = 0; } } newFilter = FilterNew(devInterfaceDetails->DevicePath,friendlyName,&result); if( result == paNoError ) { PA_DEBUG(("Filter created\n")); wdmHostApi->filters[slot] = newFilter; slot++; } else { PA_DEBUG(("Filter NOT created\n")); /* As there are now less filters than we initially thought * we must reduce the count by one */ wdmHostApi->filterCount--; } } } /* Clean up */ if(handle != NULL) SetupDiDestroyDeviceInfoList(handle); return paNoError; } PaError PaWinWdm_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex hostApiIndex ) { PaError result = paNoError; int i, deviceCount; PaWinWdmHostApiRepresentation *wdmHostApi; PaWinWdmDeviceInfo *deviceInfoArray; PaWinWdmFilter* pFilter; PaWinWdmDeviceInfo *wdmDeviceInfo; PaDeviceInfo *deviceInfo; PA_LOGE_; /* Attempt to load the KSUSER.DLL without which we cannot create pins We will unload this on termination */ if(DllKsUser == NULL) { DllKsUser = LoadLibrary(TEXT("ksuser.dll")); if(DllKsUser == NULL) goto error; } FunctionKsCreatePin = (KSCREATEPIN*)GetProcAddress(DllKsUser, "KsCreatePin"); if(FunctionKsCreatePin == NULL) goto error; wdmHostApi = (PaWinWdmHostApiRepresentation*)PaUtil_AllocateMemory( sizeof(PaWinWdmHostApiRepresentation) ); if( !wdmHostApi ) { result = paInsufficientMemory; goto error; } wdmHostApi->allocations = PaUtil_CreateAllocationGroup(); if( !wdmHostApi->allocations ) { result = paInsufficientMemory; goto error; } result = BuildFilterList( wdmHostApi ); if( result != paNoError ) { goto error; } deviceCount = wdmHostApi->filterCount; *hostApi = &wdmHostApi->inheritedHostApiRep; (*hostApi)->info.structVersion = 1; (*hostApi)->info.type = paWDMKS; (*hostApi)->info.name = "Windows WDM-KS"; (*hostApi)->info.defaultInputDevice = paNoDevice; (*hostApi)->info.defaultOutputDevice = paNoDevice; if( deviceCount > 0 ) { (*hostApi)->deviceInfos = (PaDeviceInfo**)PaUtil_GroupAllocateMemory( wdmHostApi->allocations, sizeof(PaWinWdmDeviceInfo*) * deviceCount ); if( !(*hostApi)->deviceInfos ) { result = paInsufficientMemory; goto error; } /* allocate all device info structs in a contiguous block */ deviceInfoArray = (PaWinWdmDeviceInfo*)PaUtil_GroupAllocateMemory( wdmHostApi->allocations, sizeof(PaWinWdmDeviceInfo) * deviceCount ); if( !deviceInfoArray ) { result = paInsufficientMemory; goto error; } for( i=0; i < deviceCount; ++i ) { wdmDeviceInfo = &deviceInfoArray[i]; deviceInfo = &wdmDeviceInfo->inheritedDeviceInfo; pFilter = wdmHostApi->filters[i]; if( pFilter == NULL ) continue; wdmDeviceInfo->filter = pFilter; deviceInfo->structVersion = 2; deviceInfo->hostApi = hostApiIndex; deviceInfo->name = (char*)pFilter->friendlyName; PA_DEBUG(("Device found name: %s\n",(char*)pFilter->friendlyName)); deviceInfo->maxInputChannels = pFilter->maxInputChannels; if(deviceInfo->maxInputChannels > 0) { /* Set the default input device to the first device we find with * more than zero input channels **/ if((*hostApi)->info.defaultInputDevice == paNoDevice) { (*hostApi)->info.defaultInputDevice = i; } } deviceInfo->maxOutputChannels = pFilter->maxOutputChannels; if(deviceInfo->maxOutputChannels > 0) { /* Set the default output device to the first device we find with * more than zero output channels **/ if((*hostApi)->info.defaultOutputDevice == paNoDevice) { (*hostApi)->info.defaultOutputDevice = i; } } /* These low values are not very useful because * a) The lowest latency we end up with can depend on many factors such * as the device buffer sizes/granularities, sample rate, channels and format * b) We cannot know the device buffer sizes until we try to open/use it at * a particular setting * So: we give 512x48000Hz frames as the default low input latency **/ deviceInfo->defaultLowInputLatency = (512.0/48000.0); deviceInfo->defaultLowOutputLatency = (512.0/48000.0); deviceInfo->defaultHighInputLatency = (4096.0/48000.0); deviceInfo->defaultHighOutputLatency = (4096.0/48000.0); deviceInfo->defaultSampleRate = (double)(pFilter->bestSampleRate); (*hostApi)->deviceInfos[i] = deviceInfo; } } (*hostApi)->info.deviceCount = deviceCount; (*hostApi)->Terminate = Terminate; (*hostApi)->OpenStream = OpenStream; (*hostApi)->IsFormatSupported = IsFormatSupported; PaUtil_InitializeStreamInterface( &wdmHostApi->callbackStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, GetStreamCpuLoad, PaUtil_DummyRead, PaUtil_DummyWrite, PaUtil_DummyGetReadAvailable, PaUtil_DummyGetWriteAvailable ); PaUtil_InitializeStreamInterface( &wdmHostApi->blockingStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, PaUtil_DummyGetCpuLoad, ReadStream, WriteStream, GetStreamReadAvailable, GetStreamWriteAvailable ); PA_LOGL_; return result; error: if( DllKsUser != NULL ) { FreeLibrary( DllKsUser ); DllKsUser = NULL; } if( wdmHostApi ) { PaUtil_FreeMemory( wdmHostApi->filters ); if( wdmHostApi->allocations ) { PaUtil_FreeAllAllocations( wdmHostApi->allocations ); PaUtil_DestroyAllocationGroup( wdmHostApi->allocations ); } PaUtil_FreeMemory( wdmHostApi ); } PA_LOGL_; return result; } static void Terminate( struct PaUtilHostApiRepresentation *hostApi ) { PaWinWdmHostApiRepresentation *wdmHostApi = (PaWinWdmHostApiRepresentation*)hostApi; int i; PA_LOGE_; if( wdmHostApi->filters ) { for( i=0; ifilterCount; i++) { if( wdmHostApi->filters[i] != NULL ) { FilterFree( wdmHostApi->filters[i] ); wdmHostApi->filters[i] = NULL; } } } PaUtil_FreeMemory( wdmHostApi->filters ); if( wdmHostApi->allocations ) { PaUtil_FreeAllAllocations( wdmHostApi->allocations ); PaUtil_DestroyAllocationGroup( wdmHostApi->allocations ); } PaUtil_FreeMemory( wdmHostApi ); PA_LOGL_; } static void FillWFEXT( WAVEFORMATEXTENSIBLE* pwfext, PaSampleFormat sampleFormat, double sampleRate, int channelCount) { PA_LOGE_; PA_DEBUG(( "sampleFormat = %lx\n" , sampleFormat )); PA_DEBUG(( "sampleRate = %f\n" , sampleRate )); PA_DEBUG(( "chanelCount = %d\n", channelCount )); pwfext->Format.wFormatTag = WAVE_FORMAT_EXTENSIBLE; pwfext->Format.nChannels = channelCount; pwfext->Format.nSamplesPerSec = (int)sampleRate; if(channelCount == 1) pwfext->dwChannelMask = KSAUDIO_SPEAKER_DIRECTOUT; else pwfext->dwChannelMask = KSAUDIO_SPEAKER_STEREO; if(sampleFormat == paFloat32) { pwfext->Format.nBlockAlign = channelCount * 4; pwfext->Format.wBitsPerSample = 32; pwfext->Format.cbSize = sizeof(WAVEFORMATEXTENSIBLE)-sizeof(WAVEFORMATEX); pwfext->Samples.wValidBitsPerSample = 32; pwfext->SubFormat = KSDATAFORMAT_SUBTYPE_IEEE_FLOAT; } else if(sampleFormat == paInt32) { pwfext->Format.nBlockAlign = channelCount * 4; pwfext->Format.wBitsPerSample = 32; pwfext->Format.cbSize = sizeof(WAVEFORMATEXTENSIBLE)-sizeof(WAVEFORMATEX); pwfext->Samples.wValidBitsPerSample = 32; pwfext->SubFormat = KSDATAFORMAT_SUBTYPE_PCM; } else if(sampleFormat == paInt24) { pwfext->Format.nBlockAlign = channelCount * 3; pwfext->Format.wBitsPerSample = 24; pwfext->Format.cbSize = sizeof(WAVEFORMATEXTENSIBLE)-sizeof(WAVEFORMATEX); pwfext->Samples.wValidBitsPerSample = 24; pwfext->SubFormat = KSDATAFORMAT_SUBTYPE_PCM; } else if(sampleFormat == paInt16) { pwfext->Format.nBlockAlign = channelCount * 2; pwfext->Format.wBitsPerSample = 16; pwfext->Format.cbSize = sizeof(WAVEFORMATEXTENSIBLE)-sizeof(WAVEFORMATEX); pwfext->Samples.wValidBitsPerSample = 16; pwfext->SubFormat = KSDATAFORMAT_SUBTYPE_PCM; } pwfext->Format.nAvgBytesPerSec = pwfext->Format.nSamplesPerSec * pwfext->Format.nBlockAlign; PA_LOGL_; } static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ) { int inputChannelCount, outputChannelCount; PaSampleFormat inputSampleFormat, outputSampleFormat; PaWinWdmHostApiRepresentation *wdmHostApi = (PaWinWdmHostApiRepresentation*)hostApi; PaWinWdmFilter* pFilter; int result = paFormatIsSupported; WAVEFORMATEXTENSIBLE wfx; PA_LOGE_; if( inputParameters ) { inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; /* all standard sample formats are supported by the buffer adapter, this implementation doesn't support any custom sample formats */ if( inputSampleFormat & paCustomFormat ) return paSampleFormatNotSupported; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that input device can support inputChannelCount */ if( inputChannelCount > hostApi->deviceInfos[ inputParameters->device ]->maxInputChannels ) return paInvalidChannelCount; /* validate inputStreamInfo */ if( inputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ /* Check that the input format is supported */ FillWFEXT(&wfx,paInt16,sampleRate,inputChannelCount); pFilter = wdmHostApi->filters[inputParameters->device]; result = FilterCanCreateCapturePin(pFilter,(const WAVEFORMATEX*)&wfx); if( result != paNoError ) { /* Try a WAVE_FORMAT_PCM instead */ wfx.Format.wFormatTag = WAVE_FORMAT_PCM; wfx.Format.cbSize = 0; wfx.Samples.wValidBitsPerSample = 0; wfx.dwChannelMask = 0; wfx.SubFormat = GUID_NULL; result = FilterCanCreateCapturePin(pFilter,(const WAVEFORMATEX*)&wfx); if( result != paNoError ) return result; } } else { inputChannelCount = 0; } if( outputParameters ) { outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; /* all standard sample formats are supported by the buffer adapter, this implementation doesn't support any custom sample formats */ if( outputSampleFormat & paCustomFormat ) return paSampleFormatNotSupported; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that output device can support outputChannelCount */ if( outputChannelCount > hostApi->deviceInfos[ outputParameters->device ]->maxOutputChannels ) return paInvalidChannelCount; /* validate outputStreamInfo */ if( outputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ /* Check that the output format is supported */ FillWFEXT(&wfx,paInt16,sampleRate,outputChannelCount); pFilter = wdmHostApi->filters[outputParameters->device]; result = FilterCanCreateRenderPin(pFilter,(const WAVEFORMATEX*)&wfx); if( result != paNoError ) { /* Try a WAVE_FORMAT_PCM instead */ wfx.Format.wFormatTag = WAVE_FORMAT_PCM; wfx.Format.cbSize = 0; wfx.Samples.wValidBitsPerSample = 0; wfx.dwChannelMask = 0; wfx.SubFormat = GUID_NULL; result = FilterCanCreateRenderPin(pFilter,(const WAVEFORMATEX*)&wfx); if( result != paNoError ) return result; } } else { outputChannelCount = 0; } /* IMPLEMENT ME: - if a full duplex stream is requested, check that the combination of input and output parameters is supported if necessary - check that the device supports sampleRate Because the buffer adapter handles conversion between all standard sample formats, the following checks are only required if paCustomFormat is implemented, or under some other unusual conditions. - check that input device can support inputSampleFormat, or that we have the capability to convert from inputSampleFormat to a native format - check that output device can support outputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format */ if((inputChannelCount == 0)&&(outputChannelCount == 0)) result = paSampleFormatNotSupported; /* Not right error */ PA_LOGL_; return result; } /* see pa_hostapi.h for a list of validity guarantees made about OpenStream parameters */ static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ) { PaError result = paNoError; PaWinWdmHostApiRepresentation *wdmHostApi = (PaWinWdmHostApiRepresentation*)hostApi; PaWinWdmStream *stream = 0; /* unsigned long framesPerHostBuffer; these may not be equivalent for all implementations */ PaSampleFormat inputSampleFormat, outputSampleFormat; PaSampleFormat hostInputSampleFormat, hostOutputSampleFormat; int userInputChannels,userOutputChannels; int size; PaWinWdmFilter* pFilter; WAVEFORMATEXTENSIBLE wfx; PA_LOGE_; PA_DEBUG(("OpenStream:sampleRate = %f\n",sampleRate)); PA_DEBUG(("OpenStream:framesPerBuffer = %lu\n",framesPerBuffer)); if( inputParameters ) { userInputChannels = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that input device can support stream->userInputChannels */ if( userInputChannels > hostApi->deviceInfos[ inputParameters->device ]->maxInputChannels ) return paInvalidChannelCount; /* validate inputStreamInfo */ if( inputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ } else { userInputChannels = 0; inputSampleFormat = hostInputSampleFormat = paInt16; /* Surpress 'uninitialised var' warnings. */ } if( outputParameters ) { userOutputChannels = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that output device can support stream->userInputChannels */ if( userOutputChannels > hostApi->deviceInfos[ outputParameters->device ]->maxOutputChannels ) return paInvalidChannelCount; /* validate outputStreamInfo */ if( outputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ } else { userOutputChannels = 0; outputSampleFormat = hostOutputSampleFormat = paInt16; /* Surpress 'uninitialized var' warnings. */ } /* validate platform specific flags */ if( (streamFlags & paPlatformSpecificFlags) != 0 ) return paInvalidFlag; /* unexpected platform specific flag */ stream = (PaWinWdmStream*)PaUtil_AllocateMemory( sizeof(PaWinWdmStream) ); if( !stream ) { result = paInsufficientMemory; goto error; } /* Zero the stream object */ /* memset((void*)stream,0,sizeof(PaWinWdmStream)); */ if( streamCallback ) { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &wdmHostApi->callbackStreamInterface, streamCallback, userData ); } else { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &wdmHostApi->blockingStreamInterface, streamCallback, userData ); } PaUtil_InitializeCpuLoadMeasurer( &stream->cpuLoadMeasurer, sampleRate ); /* Instantiate the input pin if necessary */ if(userInputChannels > 0) { result = paSampleFormatNotSupported; pFilter = wdmHostApi->filters[inputParameters->device]; stream->userInputChannels = userInputChannels; if(((inputSampleFormat & ~paNonInterleaved) & pFilter->formats) != 0) { /* inputSampleFormat is supported, so try to use it */ hostInputSampleFormat = inputSampleFormat; FillWFEXT(&wfx, hostInputSampleFormat, sampleRate, stream->userInputChannels); stream->bytesPerInputFrame = wfx.Format.nBlockAlign; stream->recordingPin = FilterCreateCapturePin(pFilter, (const WAVEFORMATEX*)&wfx, &result); stream->deviceInputChannels = stream->userInputChannels; } if(result != paNoError) { /* Search through all PaSampleFormats to find one that works */ hostInputSampleFormat = paFloat32; do { FillWFEXT(&wfx, hostInputSampleFormat, sampleRate, stream->userInputChannels); stream->bytesPerInputFrame = wfx.Format.nBlockAlign; stream->recordingPin = FilterCreateCapturePin(pFilter, (const WAVEFORMATEX*)&wfx, &result); stream->deviceInputChannels = stream->userInputChannels; if(stream->recordingPin == NULL) result = paSampleFormatNotSupported; if(result != paNoError) hostInputSampleFormat <<= 1; } while(result != paNoError && hostInputSampleFormat <= paUInt8); } if(result != paNoError) { /* None of the PaSampleFormats worked. Set the hostInputSampleFormat to the best fit * and try a PCM format. **/ hostInputSampleFormat = PaUtil_SelectClosestAvailableFormat( pFilter->formats, inputSampleFormat ); /* Try a WAVE_FORMAT_PCM instead */ wfx.Format.wFormatTag = WAVE_FORMAT_PCM; wfx.Format.cbSize = 0; wfx.Samples.wValidBitsPerSample = 0; wfx.dwChannelMask = 0; wfx.SubFormat = GUID_NULL; stream->recordingPin = FilterCreateCapturePin(pFilter,(const WAVEFORMATEX*)&wfx,&result); if(stream->recordingPin == NULL) result = paSampleFormatNotSupported; } if( result != paNoError ) { /* Some or all KS devices can only handle the exact number of channels * they specify. But PortAudio clients expect to be able to * at least specify mono I/O on a multi-channel device * If this is the case, then we will do the channel mapping internally **/ if( stream->userInputChannels < pFilter->maxInputChannels ) { FillWFEXT(&wfx,hostInputSampleFormat,sampleRate,pFilter->maxInputChannels); stream->bytesPerInputFrame = wfx.Format.nBlockAlign; stream->recordingPin = FilterCreateCapturePin(pFilter,(const WAVEFORMATEX*)&wfx,&result); stream->deviceInputChannels = pFilter->maxInputChannels; if( result != paNoError ) { /* Try a WAVE_FORMAT_PCM instead */ wfx.Format.wFormatTag = WAVE_FORMAT_PCM; wfx.Format.cbSize = 0; wfx.Samples.wValidBitsPerSample = 0; wfx.dwChannelMask = 0; wfx.SubFormat = GUID_NULL; stream->recordingPin = FilterCreateCapturePin(pFilter,(const WAVEFORMATEX*)&wfx,&result); } } } if(stream->recordingPin == NULL) { goto error; } switch(hostInputSampleFormat) { case paInt16: stream->inputSampleSize = 2; break; case paInt24: stream->inputSampleSize = 3; break; case paInt32: case paFloat32: stream->inputSampleSize = 4; break; } stream->recordingPin->frameSize /= stream->bytesPerInputFrame; PA_DEBUG(("Pin output frames: %d\n",stream->recordingPin->frameSize)); } else { stream->recordingPin = NULL; stream->bytesPerInputFrame = 0; } /* Instantiate the output pin if necessary */ if(userOutputChannels > 0) { result = paSampleFormatNotSupported; pFilter = wdmHostApi->filters[outputParameters->device]; stream->userOutputChannels = userOutputChannels; if(((outputSampleFormat & ~paNonInterleaved) & pFilter->formats) != 0) { hostOutputSampleFormat = outputSampleFormat; FillWFEXT(&wfx,hostOutputSampleFormat,sampleRate,stream->userOutputChannels); stream->bytesPerOutputFrame = wfx.Format.nBlockAlign; stream->playbackPin = FilterCreateRenderPin(pFilter,(WAVEFORMATEX*)&wfx,&result); stream->deviceOutputChannels = stream->userOutputChannels; } if(result != paNoError) { hostOutputSampleFormat = paFloat32; do { FillWFEXT(&wfx,hostOutputSampleFormat,sampleRate,stream->userOutputChannels); stream->bytesPerOutputFrame = wfx.Format.nBlockAlign; stream->playbackPin = FilterCreateRenderPin(pFilter,(WAVEFORMATEX*)&wfx,&result); stream->deviceOutputChannels = stream->userOutputChannels; if(stream->playbackPin == NULL) result = paSampleFormatNotSupported; if(result != paNoError) hostOutputSampleFormat <<= 1; } while(result != paNoError && hostOutputSampleFormat <= paUInt8); } if(result != paNoError) { hostOutputSampleFormat = PaUtil_SelectClosestAvailableFormat( pFilter->formats, outputSampleFormat ); /* Try a WAVE_FORMAT_PCM instead */ wfx.Format.wFormatTag = WAVE_FORMAT_PCM; wfx.Format.cbSize = 0; wfx.Samples.wValidBitsPerSample = 0; wfx.dwChannelMask = 0; wfx.SubFormat = GUID_NULL; stream->playbackPin = FilterCreateRenderPin(pFilter,(WAVEFORMATEX*)&wfx,&result); if(stream->playbackPin == NULL) result = paSampleFormatNotSupported; } if( result != paNoError ) { /* Some or all KS devices can only handle the exact number of channels * they specify. But PortAudio clients expect to be able to * at least specify mono I/O on a multi-channel device * If this is the case, then we will do the channel mapping internally **/ if( stream->userOutputChannels < pFilter->maxOutputChannels ) { FillWFEXT(&wfx,hostOutputSampleFormat,sampleRate,pFilter->maxOutputChannels); stream->bytesPerOutputFrame = wfx.Format.nBlockAlign; stream->playbackPin = FilterCreateRenderPin(pFilter,(const WAVEFORMATEX*)&wfx,&result); stream->deviceOutputChannels = pFilter->maxOutputChannels; if( result != paNoError ) { /* Try a WAVE_FORMAT_PCM instead */ wfx.Format.wFormatTag = WAVE_FORMAT_PCM; wfx.Format.cbSize = 0; wfx.Samples.wValidBitsPerSample = 0; wfx.dwChannelMask = 0; wfx.SubFormat = GUID_NULL; stream->playbackPin = FilterCreateRenderPin(pFilter,(const WAVEFORMATEX*)&wfx,&result); } } } if(stream->playbackPin == NULL) { goto error; } switch(hostOutputSampleFormat) { case paInt16: stream->outputSampleSize = 2; break; case paInt24: stream->outputSampleSize = 3; break; case paInt32: case paFloat32: stream->outputSampleSize = 4; break; } stream->playbackPin->frameSize /= stream->bytesPerOutputFrame; PA_DEBUG(("Pin output frames: %d\n",stream->playbackPin->frameSize)); } else { stream->playbackPin = NULL; stream->bytesPerOutputFrame = 0; } /* Calculate the framesPerHostXxxxBuffer size based upon the suggested latency values */ /* Record the buffer length */ if(inputParameters) { /* Calculate the frames from the user's value - add a bit to round up */ stream->framesPerHostIBuffer = (unsigned long)((inputParameters->suggestedLatency*sampleRate)+0.0001); if(stream->framesPerHostIBuffer > (unsigned long)sampleRate) { /* Upper limit is 1 second */ stream->framesPerHostIBuffer = (unsigned long)sampleRate; } else if(stream->framesPerHostIBuffer < stream->recordingPin->frameSize) { stream->framesPerHostIBuffer = stream->recordingPin->frameSize; } PA_DEBUG(("Input frames chosen:%ld\n",stream->framesPerHostIBuffer)); } if(outputParameters) { /* Calculate the frames from the user's value - add a bit to round up */ stream->framesPerHostOBuffer = (unsigned long)((outputParameters->suggestedLatency*sampleRate)+0.0001); if(stream->framesPerHostOBuffer > (unsigned long)sampleRate) { /* Upper limit is 1 second */ stream->framesPerHostOBuffer = (unsigned long)sampleRate; } else if(stream->framesPerHostOBuffer < stream->playbackPin->frameSize) { stream->framesPerHostOBuffer = stream->playbackPin->frameSize; } PA_DEBUG(("Output frames chosen:%ld\n",stream->framesPerHostOBuffer)); } /* Host buffer size is bounded to the largest of the input and output frame sizes */ result = PaUtil_InitializeBufferProcessor( &stream->bufferProcessor, stream->userInputChannels, inputSampleFormat, hostInputSampleFormat, stream->userOutputChannels, outputSampleFormat, hostOutputSampleFormat, sampleRate, streamFlags, framesPerBuffer, max(stream->framesPerHostOBuffer,stream->framesPerHostIBuffer), paUtilBoundedHostBufferSize, streamCallback, userData ); if( result != paNoError ) goto error; stream->streamRepresentation.streamInfo.inputLatency = ((double)stream->framesPerHostIBuffer) / sampleRate; stream->streamRepresentation.streamInfo.outputLatency = ((double)stream->framesPerHostOBuffer) / sampleRate; stream->streamRepresentation.streamInfo.sampleRate = sampleRate; PA_DEBUG(("BytesPerInputFrame = %d\n",stream->bytesPerInputFrame)); PA_DEBUG(("BytesPerOutputFrame = %d\n",stream->bytesPerOutputFrame)); /* Allocate all the buffers for host I/O */ size = 2 * (stream->framesPerHostIBuffer*stream->bytesPerInputFrame + stream->framesPerHostOBuffer*stream->bytesPerOutputFrame); PA_DEBUG(("Buffer size = %d\n",size)); stream->hostBuffer = (char*)PaUtil_AllocateMemory(size); PA_DEBUG(("Buffer allocated\n")); if( !stream->hostBuffer ) { PA_DEBUG(("Cannot allocate host buffer!\n")); result = paInsufficientMemory; goto error; } PA_DEBUG(("Buffer start = %p\n",stream->hostBuffer)); /* memset(stream->hostBuffer,0,size); */ /* Set up the packets */ stream->events[0] = CreateEvent(NULL, FALSE, FALSE, NULL); ResetEvent(stream->events[0]); /* Record buffer 1 */ stream->events[1] = CreateEvent(NULL, FALSE, FALSE, NULL); ResetEvent(stream->events[1]); /* Record buffer 2 */ stream->events[2] = CreateEvent(NULL, FALSE, FALSE, NULL); ResetEvent(stream->events[2]); /* Play buffer 1 */ stream->events[3] = CreateEvent(NULL, FALSE, FALSE, NULL); ResetEvent(stream->events[3]); /* Play buffer 2 */ stream->events[4] = CreateEvent(NULL, FALSE, FALSE, NULL); ResetEvent(stream->events[4]); /* Abort event */ if(stream->userInputChannels > 0) { DATAPACKET *p = &(stream->packets[0]); p->Signal.hEvent = stream->events[0]; p->Header.Data = stream->hostBuffer; p->Header.FrameExtent = stream->framesPerHostIBuffer*stream->bytesPerInputFrame; p->Header.DataUsed = 0; p->Header.Size = sizeof(p->Header); p->Header.PresentationTime.Numerator = 1; p->Header.PresentationTime.Denominator = 1; p = &(stream->packets[1]); p->Signal.hEvent = stream->events[1]; p->Header.Data = stream->hostBuffer + stream->framesPerHostIBuffer*stream->bytesPerInputFrame; p->Header.FrameExtent = stream->framesPerHostIBuffer*stream->bytesPerInputFrame; p->Header.DataUsed = 0; p->Header.Size = sizeof(p->Header); p->Header.PresentationTime.Numerator = 1; p->Header.PresentationTime.Denominator = 1; } if(stream->userOutputChannels > 0) { DATAPACKET *p = &(stream->packets[2]); p->Signal.hEvent = stream->events[2]; p->Header.Data = stream->hostBuffer + 2*stream->framesPerHostIBuffer*stream->bytesPerInputFrame; p->Header.FrameExtent = stream->framesPerHostOBuffer*stream->bytesPerOutputFrame; p->Header.DataUsed = stream->framesPerHostOBuffer*stream->bytesPerOutputFrame; p->Header.Size = sizeof(p->Header); p->Header.PresentationTime.Numerator = 1; p->Header.PresentationTime.Denominator = 1; p = &(stream->packets[3]); p->Signal.hEvent = stream->events[3]; p->Header.Data = stream->hostBuffer + 2*stream->framesPerHostIBuffer*stream->bytesPerInputFrame + stream->framesPerHostOBuffer*stream->bytesPerOutputFrame; p->Header.FrameExtent = stream->framesPerHostOBuffer*stream->bytesPerOutputFrame; p->Header.DataUsed = stream->framesPerHostOBuffer*stream->bytesPerOutputFrame; p->Header.Size = sizeof(p->Header); p->Header.PresentationTime.Numerator = 1; p->Header.PresentationTime.Denominator = 1; } stream->streamStarted = 0; stream->streamActive = 0; stream->streamStop = 0; stream->streamAbort = 0; stream->streamFlags = streamFlags; stream->oldProcessPriority = REALTIME_PRIORITY_CLASS; *s = (PaStream*)stream; PA_LOGL_; return result; error: size = 5; while(size--) { if(stream->events[size] != NULL) { CloseHandle(stream->events[size]); stream->events[size] = NULL; } } if(stream->hostBuffer) PaUtil_FreeMemory( stream->hostBuffer ); if(stream->playbackPin) PinClose(stream->playbackPin); if(stream->recordingPin) PinClose(stream->recordingPin); if( stream ) PaUtil_FreeMemory( stream ); PA_LOGL_; return result; } /* When CloseStream() is called, the multi-api layer ensures that the stream has already been stopped or aborted. */ static PaError CloseStream( PaStream* s ) { PaError result = paNoError; PaWinWdmStream *stream = (PaWinWdmStream*)s; int size; PA_LOGE_; assert(!stream->streamStarted); assert(!stream->streamActive); PaUtil_TerminateBufferProcessor( &stream->bufferProcessor ); PaUtil_TerminateStreamRepresentation( &stream->streamRepresentation ); size = 5; while(size--) { if(stream->events[size] != NULL) { CloseHandle(stream->events[size]); stream->events[size] = NULL; } } if(stream->hostBuffer) PaUtil_FreeMemory( stream->hostBuffer ); if(stream->playbackPin) PinClose(stream->playbackPin); if(stream->recordingPin) PinClose(stream->recordingPin); PaUtil_FreeMemory( stream ); PA_LOGL_; return result; } /* Write the supplied packet to the pin Asynchronous Should return false on success */ static BOOL PinWrite(HANDLE h, DATAPACKET* p) { unsigned long cbReturned = 0; return DeviceIoControl(h,IOCTL_KS_WRITE_STREAM,NULL,0, &p->Header,p->Header.Size,&cbReturned,&p->Signal); } /* Read to the supplied packet from the pin Asynchronous Should return false on success */ static BOOL PinRead(HANDLE h, DATAPACKET* p) { unsigned long cbReturned = 0; return DeviceIoControl(h,IOCTL_KS_READ_STREAM,NULL,0, &p->Header,p->Header.Size,&cbReturned,&p->Signal); } /* Copy the first interleaved channel of 16 bit data to the other channels */ static void DuplicateFirstChannelInt16(void* buffer, int channels, int samples) { unsigned short* data = (unsigned short*)buffer; int channel; unsigned short sourceSample; while( samples-- ) { sourceSample = *data++; channel = channels-1; while( channel-- ) { *data++ = sourceSample; } } } /* Copy the first interleaved channel of 24 bit data to the other channels */ static void DuplicateFirstChannelInt24(void* buffer, int channels, int samples) { unsigned char* data = (unsigned char*)buffer; int channel; unsigned char sourceSample[3]; while( samples-- ) { sourceSample[0] = data[0]; sourceSample[1] = data[1]; sourceSample[2] = data[2]; data += 3; channel = channels-1; while( channel-- ) { data[0] = sourceSample[0]; data[1] = sourceSample[1]; data[2] = sourceSample[2]; data += 3; } } } /* Copy the first interleaved channel of 32 bit data to the other channels */ static void DuplicateFirstChannelInt32(void* buffer, int channels, int samples) { unsigned long* data = (unsigned long*)buffer; int channel; unsigned long sourceSample; while( samples-- ) { sourceSample = *data++; channel = channels-1; while( channel-- ) { *data++ = sourceSample; } } } static DWORD WINAPI ProcessingThread(LPVOID pParam) { PaWinWdmStream *stream = (PaWinWdmStream*)pParam; PaStreamCallbackTimeInfo ti; int cbResult = paContinue; int inbuf = 0; int outbuf = 0; int pending = 0; PaError result; unsigned long wait; unsigned long eventSignaled; int fillPlaybuf = 0; int emptyRecordbuf = 0; int framesProcessed; unsigned long timeout; int i; int doChannelCopy; int priming = 0; PaStreamCallbackFlags underover = 0; PA_LOGE_; ti.inputBufferAdcTime = 0.0; ti.currentTime = 0.0; ti.outputBufferDacTime = 0.0; /* Get double buffering going */ /* Submit buffers */ if(stream->playbackPin) { result = PinSetState(stream->playbackPin, KSSTATE_RUN); PA_DEBUG(("play state run = %d;",(int)result)); SetEvent(stream->events[outbuf+2]); outbuf = (outbuf+1)&1; SetEvent(stream->events[outbuf+2]); outbuf = (outbuf+1)&1; pending += 2; priming += 4; } if(stream->recordingPin) { result = PinSetState(stream->recordingPin, KSSTATE_RUN); PA_DEBUG(("recording state run = %d;",(int)result)); PinRead(stream->recordingPin->handle,&stream->packets[inbuf]); inbuf = (inbuf+1)&1; /* Increment and wrap */ PinRead(stream->recordingPin->handle,&stream->packets[inbuf]); inbuf = (inbuf+1)&1; /* Increment and wrap */ /* FIXME - do error checking */ pending += 2; } PA_DEBUG(("Out buffer len:%f\n",(2000*stream->framesPerHostOBuffer) / stream->streamRepresentation.streamInfo.sampleRate)); PA_DEBUG(("In buffer len:%f\n",(2000*stream->framesPerHostIBuffer) / stream->streamRepresentation.streamInfo.sampleRate)); timeout = max( ((2000*(DWORD)stream->framesPerHostOBuffer) / (DWORD)stream->streamRepresentation.streamInfo.sampleRate), ((2000*(DWORD)stream->framesPerHostIBuffer) / (DWORD)stream->streamRepresentation.streamInfo.sampleRate)); timeout = max(timeout,1); PA_DEBUG(("Timeout = %ld\n",timeout)); while(!stream->streamAbort) { fillPlaybuf = 0; emptyRecordbuf = 0; /* Wait for next input or output buffer to be finished with*/ assert(pending>0); if(stream->streamStop) { PA_DEBUG(("ss1:pending=%d ",pending)); } wait = WaitForMultipleObjects(5, stream->events, FALSE, 0); if( wait == WAIT_TIMEOUT ) { /* No (under|over)flow has ocurred */ wait = WaitForMultipleObjects(5, stream->events, FALSE, timeout); eventSignaled = wait - WAIT_OBJECT_0; } else { eventSignaled = wait - WAIT_OBJECT_0; if( eventSignaled < 2 ) { underover |= paInputOverflow; PA_DEBUG(("Input overflow\n")); } else if(( eventSignaled < 4 )&&(!priming)) { underover |= paOutputUnderflow; PA_DEBUG(("Output underflow\n")); } } if(stream->streamStop) { PA_DEBUG(("ss2:wait=%ld",wait)); } if(wait == WAIT_FAILED) { PA_DEBUG(("Wait fail = %ld! ",wait)); break; } if(wait == WAIT_TIMEOUT) { continue; } if(eventSignaled < 2) { /* Recording input buffer has been filled */ if(stream->playbackPin) { /* First check if also the next playback buffer has been signaled */ wait = WaitForSingleObject(stream->events[outbuf+2],0); if(wait == WAIT_OBJECT_0) { /* Yes, so do both buffers at same time */ fillPlaybuf = 1; pending--; /* Was this an underflow situation? */ if( underover ) underover |= paOutputUnderflow; /* Yes! */ } } emptyRecordbuf = 1; pending--; } else if(eventSignaled < 4) { /* Playback output buffer has been emptied */ if(stream->recordingPin) { /* First check if also the next recording buffer has been signaled */ wait = WaitForSingleObject(stream->events[inbuf],0); if(wait == WAIT_OBJECT_0) { /* Yes, so do both buffers at same time */ emptyRecordbuf = 1; pending--; /* Was this an overflow situation? */ if( underover ) underover |= paInputOverflow; /* Yes! */ } } fillPlaybuf = 1; pending--; } else { /* Abort event! */ assert(stream->streamAbort); /* Should have been set */ PA_DEBUG(("ABORTING ")); break; } ResetEvent(stream->events[eventSignaled]); if(stream->streamStop) { PA_DEBUG(("Stream stop! pending=%d",pending)); cbResult = paComplete; /* Stop, but play remaining buffers */ } /* Do necessary buffer processing (which will invoke user callback if necessary */ doChannelCopy = 0; if(cbResult==paContinue) { PaUtil_BeginCpuLoadMeasurement( &stream->cpuLoadMeasurer ); if((stream->bufferProcessor.hostInputFrameCount[0] + stream->bufferProcessor.hostInputFrameCount[1]) == (stream->bufferProcessor.hostOutputFrameCount[0] + stream->bufferProcessor.hostOutputFrameCount[1]) ) PaUtil_BeginBufferProcessing(&stream->bufferProcessor,&ti,underover); underover = 0; /* Reset the (under|over)flow status */ if(fillPlaybuf) { PaUtil_SetOutputFrameCount(&stream->bufferProcessor,0); if( stream->userOutputChannels == 1 ) { /* Write the single user channel to the first interleaved block */ PaUtil_SetOutputChannel(&stream->bufferProcessor,0,stream->packets[outbuf+2].Header.Data,stream->deviceOutputChannels); /* We will do a copy to the other channels after the data has been written */ doChannelCopy = 1; } else { for(i=0;iuserOutputChannels;i++) { /* Only write the user output channels. Leave the rest blank */ PaUtil_SetOutputChannel(&stream->bufferProcessor,i,((unsigned char*)(stream->packets[outbuf+2].Header.Data))+(i*stream->outputSampleSize),stream->deviceOutputChannels); } } } if(emptyRecordbuf) { PaUtil_SetInputFrameCount(&stream->bufferProcessor,stream->packets[inbuf].Header.DataUsed/stream->bytesPerInputFrame); for(i=0;iuserInputChannels;i++) { /* Only read as many channels as the user wants */ PaUtil_SetInputChannel(&stream->bufferProcessor,i,((unsigned char*)(stream->packets[inbuf].Header.Data))+(i*stream->inputSampleSize),stream->deviceInputChannels); } } /* Only call the EndBufferProcessing function is the total input frames == total output frames */ if((stream->bufferProcessor.hostInputFrameCount[0] + stream->bufferProcessor.hostInputFrameCount[1]) == (stream->bufferProcessor.hostOutputFrameCount[0] + stream->bufferProcessor.hostOutputFrameCount[1]) ) framesProcessed = PaUtil_EndBufferProcessing(&stream->bufferProcessor,&cbResult); else framesProcessed = 0; if( doChannelCopy ) { /* Copy the first output channel to the other channels */ switch(stream->outputSampleSize) { case 2: DuplicateFirstChannelInt16(stream->packets[outbuf+2].Header.Data,stream->deviceOutputChannels,stream->framesPerHostOBuffer); break; case 3: DuplicateFirstChannelInt24(stream->packets[outbuf+2].Header.Data,stream->deviceOutputChannels,stream->framesPerHostOBuffer); break; case 4: DuplicateFirstChannelInt32(stream->packets[outbuf+2].Header.Data,stream->deviceOutputChannels,stream->framesPerHostOBuffer); break; default: assert(0); /* Unsupported format! */ break; } } PaUtil_EndCpuLoadMeasurement( &stream->cpuLoadMeasurer, framesProcessed ); } else { fillPlaybuf = 0; emptyRecordbuf = 0; } /* if(cbResult != paContinue) { PA_DEBUG(("cbResult=%d, pending=%d:",cbResult,pending)); } */ /* Submit buffers */ if((fillPlaybuf)&&(cbResult!=paAbort)) { if(!PinWrite(stream->playbackPin->handle,&stream->packets[outbuf+2])) outbuf = (outbuf+1)&1; /* Increment and wrap */ pending++; if( priming ) priming--; /* Have to prime twice */ } if((emptyRecordbuf)&&(cbResult==paContinue)) { stream->packets[inbuf].Header.DataUsed = 0; /* Reset for reuse */ PinRead(stream->recordingPin->handle,&stream->packets[inbuf]); inbuf = (inbuf+1)&1; /* Increment and wrap */ pending++; } if(pending==0) { PA_DEBUG(("pending==0 finished...;")); break; } if((!stream->playbackPin)&&(cbResult!=paContinue)) { PA_DEBUG(("record only cbResult=%d...;",cbResult)); break; } } PA_DEBUG(("Finished thread")); /* Finished, either normally or aborted */ if(stream->playbackPin) { result = PinSetState(stream->playbackPin, KSSTATE_PAUSE); result = PinSetState(stream->playbackPin, KSSTATE_STOP); } if(stream->recordingPin) { result = PinSetState(stream->recordingPin, KSSTATE_PAUSE); result = PinSetState(stream->recordingPin, KSSTATE_STOP); } stream->streamActive = 0; if((!stream->streamStop)&&(!stream->streamAbort)) { /* Invoke the user stream finished callback */ /* Only do it from here if not being stopped/aborted by user */ if( stream->streamRepresentation.streamFinishedCallback != 0 ) stream->streamRepresentation.streamFinishedCallback( stream->streamRepresentation.userData ); } stream->streamStop = 0; stream->streamAbort = 0; /* Reset process priority if necessary */ if(stream->oldProcessPriority != REALTIME_PRIORITY_CLASS) { SetPriorityClass(GetCurrentProcess(),stream->oldProcessPriority); stream->oldProcessPriority = REALTIME_PRIORITY_CLASS; } PA_LOGL_; ExitThread(0); return 0; } static PaError StartStream( PaStream *s ) { PaError result = paNoError; PaWinWdmStream *stream = (PaWinWdmStream*)s; DWORD dwID; BOOL ret; int size; PA_LOGE_; stream->streamStop = 0; stream->streamAbort = 0; size = 5; while(size--) { if(stream->events[size] != NULL) { ResetEvent(stream->events[size]); } } PaUtil_ResetBufferProcessor( &stream->bufferProcessor ); stream->oldProcessPriority = GetPriorityClass(GetCurrentProcess()); /* Uncomment the following line to enable dynamic boosting of the process * priority to real time for best low latency support * Disabled by default because RT processes can easily block the OS */ /*ret = SetPriorityClass(GetCurrentProcess(),REALTIME_PRIORITY_CLASS); PA_DEBUG(("Class ret = %d;",ret));*/ stream->streamStarted = 1; stream->streamThread = CreateThread(NULL, 0, ProcessingThread, stream, 0, &dwID); if(stream->streamThread == NULL) { stream->streamStarted = 0; result = paInsufficientMemory; goto end; } ret = SetThreadPriority(stream->streamThread,THREAD_PRIORITY_TIME_CRITICAL); PA_DEBUG(("Priority ret = %d;",ret)); /* Make the stream active */ stream->streamActive = 1; end: PA_LOGL_; return result; } static PaError StopStream( PaStream *s ) { PaError result = paNoError; PaWinWdmStream *stream = (PaWinWdmStream*)s; int doCb = 0; PA_LOGE_; if(stream->streamActive) { doCb = 1; stream->streamStop = 1; while(stream->streamActive) { PA_DEBUG(("W.")); Sleep(10); /* Let thread sleep for 10 msec */ } } PA_DEBUG(("Terminating thread")); if(stream->streamStarted && stream->streamThread) { TerminateThread(stream->streamThread,0); stream->streamThread = NULL; } stream->streamStarted = 0; if(stream->oldProcessPriority != REALTIME_PRIORITY_CLASS) { SetPriorityClass(GetCurrentProcess(),stream->oldProcessPriority); stream->oldProcessPriority = REALTIME_PRIORITY_CLASS; } if(doCb) { /* Do user callback now after all state has been reset */ /* This means it should be safe for the called function */ /* to invoke e.g. StartStream */ if( stream->streamRepresentation.streamFinishedCallback != 0 ) stream->streamRepresentation.streamFinishedCallback( stream->streamRepresentation.userData ); } PA_LOGL_; return result; } static PaError AbortStream( PaStream *s ) { PaError result = paNoError; PaWinWdmStream *stream = (PaWinWdmStream*)s; int doCb = 0; PA_LOGE_; if(stream->streamActive) { doCb = 1; stream->streamAbort = 1; SetEvent(stream->events[4]); /* Signal immediately */ while(stream->streamActive) { Sleep(10); } } if(stream->streamStarted && stream->streamThread) { TerminateThread(stream->streamThread,0); stream->streamThread = NULL; } stream->streamStarted = 0; if(stream->oldProcessPriority != REALTIME_PRIORITY_CLASS) { SetPriorityClass(GetCurrentProcess(),stream->oldProcessPriority); stream->oldProcessPriority = REALTIME_PRIORITY_CLASS; } if(doCb) { /* Do user callback now after all state has been reset */ /* This means it should be safe for the called function */ /* to invoke e.g. StartStream */ if( stream->streamRepresentation.streamFinishedCallback != 0 ) stream->streamRepresentation.streamFinishedCallback( stream->streamRepresentation.userData ); } stream->streamActive = 0; stream->streamStarted = 0; PA_LOGL_; return result; } static PaError IsStreamStopped( PaStream *s ) { PaWinWdmStream *stream = (PaWinWdmStream*)s; int result = 0; PA_LOGE_; if(!stream->streamStarted) result = 1; PA_LOGL_; return result; } static PaError IsStreamActive( PaStream *s ) { PaWinWdmStream *stream = (PaWinWdmStream*)s; int result = 0; PA_LOGE_; if(stream->streamActive) result = 1; PA_LOGL_; return result; } static PaTime GetStreamTime( PaStream* s ) { PA_LOGE_; PA_LOGL_; (void)s; return PaUtil_GetTime(); } static double GetStreamCpuLoad( PaStream* s ) { PaWinWdmStream *stream = (PaWinWdmStream*)s; double result; PA_LOGE_; result = PaUtil_GetCpuLoad( &stream->cpuLoadMeasurer ); PA_LOGL_; return result; } /* As separate stream interfaces are used for blocking and callback streams, the following functions can be guaranteed to only be called for blocking streams. */ static PaError ReadStream( PaStream* s, void *buffer, unsigned long frames ) { PaWinWdmStream *stream = (PaWinWdmStream*)s; PA_LOGE_; /* suppress unused variable warnings */ (void) buffer; (void) frames; (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ PA_LOGL_; return paNoError; } static PaError WriteStream( PaStream* s, const void *buffer, unsigned long frames ) { PaWinWdmStream *stream = (PaWinWdmStream*)s; PA_LOGE_; /* suppress unused variable warnings */ (void) buffer; (void) frames; (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ PA_LOGL_; return paNoError; } static signed long GetStreamReadAvailable( PaStream* s ) { PaWinWdmStream *stream = (PaWinWdmStream*)s; PA_LOGE_; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ PA_LOGL_; return 0; } static signed long GetStreamWriteAvailable( PaStream* s ) { PaWinWdmStream *stream = (PaWinWdmStream*)s; PA_LOGE_; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ PA_LOGL_; return 0; }sources_5316/external/portaudio/pa_win_waveformat.c0000644000176700017670000001407311630755415021443 0ustar paulpaul#ifdef _WIN32 /* * PortAudio Portable Real-Time Audio Library * Windows WAVEFORMAT* data structure utilities * portaudio.h should be included before this file. * * Copyright (c) 2007 Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ #undef UNICODE #include #include #include "portaudio.h" #include "pa_win_waveformat.h" #if !defined(WAVE_FORMAT_EXTENSIBLE) #define WAVE_FORMAT_EXTENSIBLE 0xFFFE #endif #if !defined(WAVE_FORMAT_IEEE_FLOAT) #define WAVE_FORMAT_IEEE_FLOAT 0x0003 #endif static GUID pawin_ksDataFormatSubtypePcm = { (USHORT)(WAVE_FORMAT_PCM), 0x0000, 0x0010, 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 }; static GUID pawin_ksDataFormatSubtypeIeeeFloat = { (USHORT)(WAVE_FORMAT_IEEE_FLOAT), 0x0000, 0x0010, 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 }; void PaWin_InitializeWaveFormatEx( PaWinWaveFormat *waveFormat, int numChannels, PaSampleFormat sampleFormat, double sampleRate ) { WAVEFORMATEX *waveFormatEx = (WAVEFORMATEX*)waveFormat; int bytesPerSample = Pa_GetSampleSize(sampleFormat); unsigned long bytesPerFrame = numChannels * bytesPerSample; if( sampleFormat == paFloat32 ) waveFormatEx->wFormatTag = WAVE_FORMAT_IEEE_FLOAT; else waveFormatEx->wFormatTag = WAVE_FORMAT_PCM; waveFormatEx->nChannels = (WORD)numChannels; waveFormatEx->nSamplesPerSec = (DWORD)sampleRate; waveFormatEx->nAvgBytesPerSec = waveFormatEx->nSamplesPerSec * bytesPerFrame; waveFormatEx->nBlockAlign = (WORD)bytesPerFrame; waveFormatEx->wBitsPerSample = bytesPerSample * 8; waveFormatEx->cbSize = 0; } void PaWin_InitializeWaveFormatExtensible( PaWinWaveFormat *waveFormat, int numChannels, PaSampleFormat sampleFormat, double sampleRate, PaWinWaveFormatChannelMask channelMask ) { WAVEFORMATEX *waveFormatEx = (WAVEFORMATEX*)waveFormat; int bytesPerSample = Pa_GetSampleSize(sampleFormat); unsigned long bytesPerFrame = numChannels * bytesPerSample; waveFormatEx->wFormatTag = WAVE_FORMAT_EXTENSIBLE; waveFormatEx->nChannels = (WORD)numChannels; waveFormatEx->nSamplesPerSec = (DWORD)sampleRate; waveFormatEx->nAvgBytesPerSec = waveFormatEx->nSamplesPerSec * bytesPerFrame; waveFormatEx->nBlockAlign = (WORD)bytesPerFrame; waveFormatEx->wBitsPerSample = bytesPerSample * 8; waveFormatEx->cbSize = 22; *((WORD*)&waveFormat->fields[PAWIN_INDEXOF_WVALIDBITSPERSAMPLE]) = waveFormatEx->wBitsPerSample; *((DWORD*)&waveFormat->fields[PAWIN_INDEXOF_DWCHANNELMASK]) = channelMask; if( sampleFormat == paFloat32 ) *((GUID*)&waveFormat->fields[PAWIN_INDEXOF_SUBFORMAT]) = pawin_ksDataFormatSubtypeIeeeFloat; else *((GUID*)&waveFormat->fields[PAWIN_INDEXOF_SUBFORMAT]) = pawin_ksDataFormatSubtypePcm; } PaWinWaveFormatChannelMask PaWin_DefaultChannelMask( int numChannels ) { switch( numChannels ){ case 1: return PAWIN_SPEAKER_MONO; case 2: return PAWIN_SPEAKER_STEREO; case 3: return PAWIN_SPEAKER_FRONT_LEFT | PAWIN_SPEAKER_FRONT_CENTER | PAWIN_SPEAKER_FRONT_RIGHT; case 4: return PAWIN_SPEAKER_QUAD; case 5: return PAWIN_SPEAKER_QUAD | PAWIN_SPEAKER_FRONT_CENTER; case 6: /* The meaning of the PAWIN_SPEAKER_5POINT1 flag has changed over time: http://msdn2.microsoft.com/en-us/library/aa474707.aspx We use PAWIN_SPEAKER_5POINT1 (not PAWIN_SPEAKER_5POINT1_SURROUND) because on some cards (eg Audigy) PAWIN_SPEAKER_5POINT1_SURROUND results in a virtual mixdown placing the rear output in the front _and_ rear speakers. */ return PAWIN_SPEAKER_5POINT1; /* case 7: */ case 8: return PAWIN_SPEAKER_7POINT1; } /* Apparently some Audigy drivers will output silence if the direct-out constant (0) is used. So this is not ideal. */ return PAWIN_SPEAKER_DIRECTOUT; /* Note that Alec Rogers proposed the following as an alternate method to generate the default channel mask, however it doesn't seem to be an improvement over the above, since some drivers will matrix outputs mapping to non-present speakers accross multiple physical speakers. if(nChannels==1) { pwfFormat->dwChannelMask = SPEAKER_FRONT_CENTER; } else { pwfFormat->dwChannelMask = 0; for(i=0; idwChannelMask = (pwfFormat->dwChannelMask << 1) | 0x1; } */ } #endif sources_5316/external/portaudio/pa_debugprint.c0000644000176700017670000000637310702742630020554 0ustar paulpaul/* * $Id: pa_log.c $ * Portable Audio I/O Library Multi-Host API front end * Validate function parameters and manage multiple host APIs. * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2006 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Implements log function. PaUtil_SetLogPrintFunction can be user called to replace the provided DefaultLogPrint function, which writes to stderr. One can NOT pass var_args across compiler/dll boundaries as it is not "byte code/abi portable". So the technique used here is to allocate a local a static array, write in it, then callback the user with a pointer to its start. @todo Consider allocating strdump using dynamic allocation. @todo Consider reentrancy and possibly corrupted strdump buffer. */ #include #include #include "pa_debugprint.h" static PaUtilLogCallback userCB=0; void PaUtil_SetDebugPrintFunction(PaUtilLogCallback cb) { userCB = cb; } /* If your platform doesn’t have vsnprintf, you are stuck with a VERY dangerous alternative, vsprintf (with no n) */ #if (_MSC_VER) && (_MSC_VER <= 1400) #define VSNPRINTF _vsnprintf #else #define VSNPRINTF vsnprintf #endif #define SIZEDUMP 1024 static char strdump[SIZEDUMP]; void PaUtil_DebugPrint( const char *format, ... ) { if (userCB) { va_list ap; va_start( ap, format ); VSNPRINTF( strdump, SIZEDUMP, format, ap ); userCB(strdump); va_end( ap ); } else { va_list ap; va_start( ap, format ); vfprintf( stderr, format, ap ); va_end( ap ); fflush( stderr ); } } sources_5316/external/portaudio/portaudio.h0000644000176700017670000012412411033237127017735 0ustar paulpaul#ifndef PORTAUDIO_H #define PORTAUDIO_H /* * $Id: portaudio.h 1247 2007-08-11 16:29:09Z rossb $ * PortAudio Portable Real-Time Audio Library * PortAudio API Header File * Latest version available at: http://www.portaudio.com/ * * Copyright (c) 1999-2002 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @brief The PortAudio API. */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ /** Retrieve the release number of the currently running PortAudio build, eg 1900. */ int Pa_GetVersion( void ); /** Retrieve a textual description of the current PortAudio build, eg "PortAudio V19-devel 13 October 2002". */ const char* Pa_GetVersionText( void ); /** Error codes returned by PortAudio functions. Note that with the exception of paNoError, all PaErrorCodes are negative. */ typedef int PaError; typedef enum PaErrorCode { paNoError = 0, paNotInitialized = -10000, paUnanticipatedHostError, paInvalidChannelCount, paInvalidSampleRate, paInvalidDevice, paInvalidFlag, paSampleFormatNotSupported, paBadIODeviceCombination, paInsufficientMemory, paBufferTooBig, paBufferTooSmall, paNullCallback, paBadStreamPtr, paTimedOut, paInternalError, paDeviceUnavailable, paIncompatibleHostApiSpecificStreamInfo, paStreamIsStopped, paStreamIsNotStopped, paInputOverflowed, paOutputUnderflowed, paHostApiNotFound, paInvalidHostApi, paCanNotReadFromACallbackStream, /**< @todo review error code name */ paCanNotWriteToACallbackStream, /**< @todo review error code name */ paCanNotReadFromAnOutputOnlyStream, /**< @todo review error code name */ paCanNotWriteToAnInputOnlyStream, /**< @todo review error code name */ paIncompatibleStreamHostApi, paBadBufferPtr } PaErrorCode; /** Translate the supplied PortAudio error code into a human readable message. */ const char *Pa_GetErrorText( PaError errorCode ); /** Library initialization function - call this before using PortAudio. This function initialises internal data structures and prepares underlying host APIs for use. With the exception of Pa_GetVersion(), Pa_GetVersionText(), and Pa_GetErrorText(), this function MUST be called before using any other PortAudio API functions. If Pa_Initialize() is called multiple times, each successful call must be matched with a corresponding call to Pa_Terminate(). Pairs of calls to Pa_Initialize()/Pa_Terminate() may overlap, and are not required to be fully nested. Note that if Pa_Initialize() returns an error code, Pa_Terminate() should NOT be called. @return paNoError if successful, otherwise an error code indicating the cause of failure. @see Pa_Terminate */ PaError Pa_Initialize( void ); /** Library termination function - call this when finished using PortAudio. This function deallocates all resources allocated by PortAudio since it was initializied by a call to Pa_Initialize(). In cases where Pa_Initialise() has been called multiple times, each call must be matched with a corresponding call to Pa_Terminate(). The final matching call to Pa_Terminate() will automatically close any PortAudio streams that are still open. Pa_Terminate() MUST be called before exiting a program which uses PortAudio. Failure to do so may result in serious resource leaks, such as audio devices not being available until the next reboot. @return paNoError if successful, otherwise an error code indicating the cause of failure. @see Pa_Initialize */ PaError Pa_Terminate( void ); /** The type used to refer to audio devices. Values of this type usually range from 0 to (Pa_GetDeviceCount()-1), and may also take on the PaNoDevice and paUseHostApiSpecificDeviceSpecification values. @see Pa_GetDeviceCount, paNoDevice, paUseHostApiSpecificDeviceSpecification */ typedef int PaDeviceIndex; /** A special PaDeviceIndex value indicating that no device is available, or should be used. @see PaDeviceIndex */ #define paNoDevice ((PaDeviceIndex)-1) /** A special PaDeviceIndex value indicating that the device(s) to be used are specified in the host api specific stream info structure. @see PaDeviceIndex */ #define paUseHostApiSpecificDeviceSpecification ((PaDeviceIndex)-2) /* Host API enumeration mechanism */ /** The type used to enumerate to host APIs at runtime. Values of this type range from 0 to (Pa_GetHostApiCount()-1). @see Pa_GetHostApiCount */ typedef int PaHostApiIndex; /** Retrieve the number of available host APIs. Even if a host API is available it may have no devices available. @return A non-negative value indicating the number of available host APIs or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. @see PaHostApiIndex */ PaHostApiIndex Pa_GetHostApiCount( void ); /** Retrieve the index of the default host API. The default host API will be the lowest common denominator host API on the current platform and is unlikely to provide the best performance. @return A non-negative value ranging from 0 to (Pa_GetHostApiCount()-1) indicating the default host API index or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. */ PaHostApiIndex Pa_GetDefaultHostApi( void ); /** Unchanging unique identifiers for each supported host API. This type is used in the PaHostApiInfo structure. The values are guaranteed to be unique and to never change, thus allowing code to be written that conditionally uses host API specific extensions. New type ids will be allocated when support for a host API reaches "public alpha" status, prior to that developers should use the paInDevelopment type id. @see PaHostApiInfo */ typedef enum PaHostApiTypeId { paInDevelopment=0, /* use while developing support for a new host API */ paDirectSound=1, paMME=2, paASIO=3, paSoundManager=4, paCoreAudio=5, paOSS=7, paALSA=8, paAL=9, paBeOS=10, paWDMKS=11, paJACK=12, paWASAPI=13, paAudioScienceHPI=14 } PaHostApiTypeId; /** A structure containing information about a particular host API. */ typedef struct PaHostApiInfo { /** this is struct version 1 */ int structVersion; /** The well known unique identifier of this host API @see PaHostApiTypeId */ PaHostApiTypeId type; /** A textual description of the host API for display on user interfaces. */ const char *name; /** The number of devices belonging to this host API. This field may be used in conjunction with Pa_HostApiDeviceIndexToDeviceIndex() to enumerate all devices for this host API. @see Pa_HostApiDeviceIndexToDeviceIndex */ int deviceCount; /** The default input device for this host API. The value will be a device index ranging from 0 to (Pa_GetDeviceCount()-1), or paNoDevice if no default input device is available. */ PaDeviceIndex defaultInputDevice; /** The default output device for this host API. The value will be a device index ranging from 0 to (Pa_GetDeviceCount()-1), or paNoDevice if no default output device is available. */ PaDeviceIndex defaultOutputDevice; } PaHostApiInfo; /** Retrieve a pointer to a structure containing information about a specific host Api. @param hostApi A valid host API index ranging from 0 to (Pa_GetHostApiCount()-1) @return A pointer to an immutable PaHostApiInfo structure describing a specific host API. If the hostApi parameter is out of range or an error is encountered, the function returns NULL. The returned structure is owned by the PortAudio implementation and must not be manipulated or freed. The pointer is only guaranteed to be valid between calls to Pa_Initialize() and Pa_Terminate(). */ const PaHostApiInfo * Pa_GetHostApiInfo( PaHostApiIndex hostApi ); /** Convert a static host API unique identifier, into a runtime host API index. @param type A unique host API identifier belonging to the PaHostApiTypeId enumeration. @return A valid PaHostApiIndex ranging from 0 to (Pa_GetHostApiCount()-1) or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. The paHostApiNotFound error code indicates that the host API specified by the type parameter is not available. @see PaHostApiTypeId */ PaHostApiIndex Pa_HostApiTypeIdToHostApiIndex( PaHostApiTypeId type ); /** Convert a host-API-specific device index to standard PortAudio device index. This function may be used in conjunction with the deviceCount field of PaHostApiInfo to enumerate all devices for the specified host API. @param hostApi A valid host API index ranging from 0 to (Pa_GetHostApiCount()-1) @param hostApiDeviceIndex A valid per-host device index in the range 0 to (Pa_GetHostApiInfo(hostApi)->deviceCount-1) @return A non-negative PaDeviceIndex ranging from 0 to (Pa_GetDeviceCount()-1) or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. A paInvalidHostApi error code indicates that the host API index specified by the hostApi parameter is out of range. A paInvalidDevice error code indicates that the hostApiDeviceIndex parameter is out of range. @see PaHostApiInfo */ PaDeviceIndex Pa_HostApiDeviceIndexToDeviceIndex( PaHostApiIndex hostApi, int hostApiDeviceIndex ); /** Structure used to return information about a host error condition. */ typedef struct PaHostErrorInfo{ PaHostApiTypeId hostApiType; /**< the host API which returned the error code */ long errorCode; /**< the error code returned */ const char *errorText; /**< a textual description of the error if available, otherwise a zero-length string */ }PaHostErrorInfo; /** Return information about the last host error encountered. The error information returned by Pa_GetLastHostErrorInfo() will never be modified asyncronously by errors occurring in other PortAudio owned threads (such as the thread that manages the stream callback.) This function is provided as a last resort, primarily to enhance debugging by providing clients with access to all available error information. @return A pointer to an immutable structure constaining information about the host error. The values in this structure will only be valid if a PortAudio function has previously returned the paUnanticipatedHostError error code. */ const PaHostErrorInfo* Pa_GetLastHostErrorInfo( void ); /* Device enumeration and capabilities */ /** Retrieve the number of available devices. The number of available devices may be zero. @return A non-negative value indicating the number of available devices or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. */ PaDeviceIndex Pa_GetDeviceCount( void ); /** Retrieve the index of the default input device. The result can be used in the inputDevice parameter to Pa_OpenStream(). @return The default input device index for the default host API, or paNoDevice if no default input device is available or an error was encountered. */ PaDeviceIndex Pa_GetDefaultInputDevice( void ); /** Retrieve the index of the default output device. The result can be used in the outputDevice parameter to Pa_OpenStream(). @return The default output device index for the default host API, or paNoDevice if no default output device is available or an error was encountered. @note On the PC, the user can specify a default device by setting an environment variable. For example, to use device #1.
 set PA_RECOMMENDED_OUTPUT_DEVICE=1
The user should first determine the available device ids by using the supplied application "pa_devs". */ PaDeviceIndex Pa_GetDefaultOutputDevice( void ); /** The type used to represent monotonic time in seconds that can be used for syncronisation. The type is used for the outTime argument to the PaStreamCallback and as the result of Pa_GetStreamTime(). @see PaStreamCallback, Pa_GetStreamTime */ typedef double PaTime; /** A type used to specify one or more sample formats. Each value indicates a possible format for sound data passed to and from the stream callback, Pa_ReadStream and Pa_WriteStream. The standard formats paFloat32, paInt16, paInt32, paInt24, paInt8 and aUInt8 are usually implemented by all implementations. The floating point representation (paFloat32) uses +1.0 and -1.0 as the maximum and minimum respectively. paUInt8 is an unsigned 8 bit format where 128 is considered "ground" The paNonInterleaved flag indicates that a multichannel buffer is passed as a set of non-interleaved pointers. @see Pa_OpenStream, Pa_OpenDefaultStream, PaDeviceInfo @see paFloat32, paInt16, paInt32, paInt24, paInt8 @see paUInt8, paCustomFormat, paNonInterleaved */ typedef unsigned long PaSampleFormat; #define paFloat32 ((PaSampleFormat) 0x00000001) /**< @see PaSampleFormat */ #define paInt32 ((PaSampleFormat) 0x00000002) /**< @see PaSampleFormat */ #define paInt24 ((PaSampleFormat) 0x00000004) /**< Packed 24 bit format. @see PaSampleFormat */ #define paInt16 ((PaSampleFormat) 0x00000008) /**< @see PaSampleFormat */ #define paInt8 ((PaSampleFormat) 0x00000010) /**< @see PaSampleFormat */ #define paUInt8 ((PaSampleFormat) 0x00000020) /**< @see PaSampleFormat */ #define paCustomFormat ((PaSampleFormat) 0x00010000)/**< @see PaSampleFormat */ #define paNonInterleaved ((PaSampleFormat) 0x80000000) /** A structure providing information and capabilities of PortAudio devices. Devices may support input, output or both input and output. */ typedef struct PaDeviceInfo { int structVersion; /* this is struct version 2 */ const char *name; PaHostApiIndex hostApi; /* note this is a host API index, not a type id*/ int maxInputChannels; int maxOutputChannels; /* Default latency values for interactive performance. */ PaTime defaultLowInputLatency; PaTime defaultLowOutputLatency; /* Default latency values for robust non-interactive applications (eg. playing sound files). */ PaTime defaultHighInputLatency; PaTime defaultHighOutputLatency; double defaultSampleRate; } PaDeviceInfo; /** Retrieve a pointer to a PaDeviceInfo structure containing information about the specified device. @return A pointer to an immutable PaDeviceInfo structure. If the device parameter is out of range the function returns NULL. @param device A valid device index in the range 0 to (Pa_GetDeviceCount()-1) @note PortAudio manages the memory referenced by the returned pointer, the client must not manipulate or free the memory. The pointer is only guaranteed to be valid between calls to Pa_Initialize() and Pa_Terminate(). @see PaDeviceInfo, PaDeviceIndex */ const PaDeviceInfo* Pa_GetDeviceInfo( PaDeviceIndex device ); /** Parameters for one direction (input or output) of a stream. */ typedef struct PaStreamParameters { /** A valid device index in the range 0 to (Pa_GetDeviceCount()-1) specifying the device to be used or the special constant paUseHostApiSpecificDeviceSpecification which indicates that the actual device(s) to use are specified in hostApiSpecificStreamInfo. This field must not be set to paNoDevice. */ PaDeviceIndex device; /** The number of channels of sound to be delivered to the stream callback or accessed by Pa_ReadStream() or Pa_WriteStream(). It can range from 1 to the value of maxInputChannels in the PaDeviceInfo record for the device specified by the device parameter. */ int channelCount; /** The sample format of the buffer provided to the stream callback, a_ReadStream() or Pa_WriteStream(). It may be any of the formats described by the PaSampleFormat enumeration. */ PaSampleFormat sampleFormat; /** The desired latency in seconds. Where practical, implementations should configure their latency based on these parameters, otherwise they may choose the closest viable latency instead. Unless the suggested latency is greater than the absolute upper limit for the device implementations should round the suggestedLatency up to the next practial value - ie to provide an equal or higher latency than suggestedLatency wherever possibe. Actual latency values for an open stream may be retrieved using the inputLatency and outputLatency fields of the PaStreamInfo structure returned by Pa_GetStreamInfo(). @see default*Latency in PaDeviceInfo, *Latency in PaStreamInfo */ PaTime suggestedLatency; /** An optional pointer to a host api specific data structure containing additional information for device setup and/or stream processing. hostApiSpecificStreamInfo is never required for correct operation, if not used it should be set to NULL. */ void *hostApiSpecificStreamInfo; } PaStreamParameters; /** Return code for Pa_IsFormatSupported indicating success. */ #define paFormatIsSupported (0) /** Determine whether it would be possible to open a stream with the specified parameters. @param inputParameters A structure that describes the input parameters used to open a stream. The suggestedLatency field is ignored. See PaStreamParameters for a description of these parameters. inputParameters must be NULL for output-only streams. @param outputParameters A structure that describes the output parameters used to open a stream. The suggestedLatency field is ignored. See PaStreamParameters for a description of these parameters. outputParameters must be NULL for input-only streams. @param sampleRate The required sampleRate. For full-duplex streams it is the sample rate for both input and output @return Returns 0 if the format is supported, and an error code indicating why the format is not supported otherwise. The constant paFormatIsSupported is provided to compare with the return value for success. @see paFormatIsSupported, PaStreamParameters */ PaError Pa_IsFormatSupported( const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); /* Streaming types and functions */ /** A single PaStream can provide multiple channels of real-time streaming audio input and output to a client application. A stream provides access to audio hardware represented by one or more PaDevices. Depending on the underlying Host API, it may be possible to open multiple streams using the same device, however this behavior is implementation defined. Portable applications should assume that a PaDevice may be simultaneously used by at most one PaStream. Pointers to PaStream objects are passed between PortAudio functions that operate on streams. @see Pa_OpenStream, Pa_OpenDefaultStream, Pa_OpenDefaultStream, Pa_CloseStream, Pa_StartStream, Pa_StopStream, Pa_AbortStream, Pa_IsStreamActive, Pa_GetStreamTime, Pa_GetStreamCpuLoad */ typedef void PaStream; /** Can be passed as the framesPerBuffer parameter to Pa_OpenStream() or Pa_OpenDefaultStream() to indicate that the stream callback will accept buffers of any size. */ #define paFramesPerBufferUnspecified (0) /** Flags used to control the behavior of a stream. They are passed as parameters to Pa_OpenStream or Pa_OpenDefaultStream. Multiple flags may be ORed together. @see Pa_OpenStream, Pa_OpenDefaultStream @see paNoFlag, paClipOff, paDitherOff, paNeverDropInput, paPrimeOutputBuffersUsingStreamCallback, paPlatformSpecificFlags */ typedef unsigned long PaStreamFlags; /** @see PaStreamFlags */ #define paNoFlag ((PaStreamFlags) 0) /** Disable default clipping of out of range samples. @see PaStreamFlags */ #define paClipOff ((PaStreamFlags) 0x00000001) /** Disable default dithering. @see PaStreamFlags */ #define paDitherOff ((PaStreamFlags) 0x00000002) /** Flag requests that where possible a full duplex stream will not discard overflowed input samples without calling the stream callback. This flag is only valid for full duplex callback streams and only when used in combination with the paFramesPerBufferUnspecified (0) framesPerBuffer parameter. Using this flag incorrectly results in a paInvalidFlag error being returned from Pa_OpenStream and Pa_OpenDefaultStream. @see PaStreamFlags, paFramesPerBufferUnspecified */ #define paNeverDropInput ((PaStreamFlags) 0x00000004) /** Call the stream callback to fill initial output buffers, rather than the default behavior of priming the buffers with zeros (silence). This flag has no effect for input-only and blocking read/write streams. @see PaStreamFlags */ #define paPrimeOutputBuffersUsingStreamCallback ((PaStreamFlags) 0x00000008) /** A mask specifying the platform specific bits. @see PaStreamFlags */ #define paPlatformSpecificFlags ((PaStreamFlags)0xFFFF0000) /** Timing information for the buffers passed to the stream callback. */ typedef struct PaStreamCallbackTimeInfo{ PaTime inputBufferAdcTime; PaTime currentTime; PaTime outputBufferDacTime; } PaStreamCallbackTimeInfo; /** Flag bit constants for the statusFlags to PaStreamCallback. @see paInputUnderflow, paInputOverflow, paOutputUnderflow, paOutputOverflow, paPrimingOutput */ typedef unsigned long PaStreamCallbackFlags; /** In a stream opened with paFramesPerBufferUnspecified, indicates that input data is all silence (zeros) because no real data is available. In a stream opened without paFramesPerBufferUnspecified, it indicates that one or more zero samples have been inserted into the input buffer to compensate for an input underflow. @see PaStreamCallbackFlags */ #define paInputUnderflow ((PaStreamCallbackFlags) 0x00000001) /** In a stream opened with paFramesPerBufferUnspecified, indicates that data prior to the first sample of the input buffer was discarded due to an overflow, possibly because the stream callback is using too much CPU time. Otherwise indicates that data prior to one or more samples in the input buffer was discarded. @see PaStreamCallbackFlags */ #define paInputOverflow ((PaStreamCallbackFlags) 0x00000002) /** Indicates that output data (or a gap) was inserted, possibly because the stream callback is using too much CPU time. @see PaStreamCallbackFlags */ #define paOutputUnderflow ((PaStreamCallbackFlags) 0x00000004) /** Indicates that output data will be discarded because no room is available. @see PaStreamCallbackFlags */ #define paOutputOverflow ((PaStreamCallbackFlags) 0x00000008) /** Some of all of the output data will be used to prime the stream, input data may be zero. @see PaStreamCallbackFlags */ #define paPrimingOutput ((PaStreamCallbackFlags) 0x00000010) /** Allowable return values for the PaStreamCallback. @see PaStreamCallback */ typedef enum PaStreamCallbackResult { paContinue=0, paComplete=1, paAbort=2 } PaStreamCallbackResult; /** Functions of type PaStreamCallback are implemented by PortAudio clients. They consume, process or generate audio in response to requests from an active PortAudio stream. @param input and @param output are arrays of interleaved samples, the format, packing and number of channels used by the buffers are determined by parameters to Pa_OpenStream(). @param frameCount The number of sample frames to be processed by the stream callback. @param timeInfo The time in seconds when the first sample of the input buffer was received at the audio input, the time in seconds when the first sample of the output buffer will begin being played at the audio output, and the time in seconds when the stream callback was called. See also Pa_GetStreamTime() @param statusFlags Flags indicating whether input and/or output buffers have been inserted or will be dropped to overcome underflow or overflow conditions. @param userData The value of a user supplied pointer passed to Pa_OpenStream() intended for storing synthesis data etc. @return The stream callback should return one of the values in the PaStreamCallbackResult enumeration. To ensure that the callback continues to be called, it should return paContinue (0). Either paComplete or paAbort can be returned to finish stream processing, after either of these values is returned the callback will not be called again. If paAbort is returned the stream will finish as soon as possible. If paComplete is returned, the stream will continue until all buffers generated by the callback have been played. This may be useful in applications such as soundfile players where a specific duration of output is required. However, it is not necessary to utilise this mechanism as Pa_StopStream(), Pa_AbortStream() or Pa_CloseStream() can also be used to stop the stream. The callback must always fill the entire output buffer irrespective of its return value. @see Pa_OpenStream, Pa_OpenDefaultStream @note With the exception of Pa_GetStreamCpuLoad() it is not permissable to call PortAudio API functions from within the stream callback. */ typedef int PaStreamCallback( const void *input, void *output, unsigned long frameCount, const PaStreamCallbackTimeInfo* timeInfo, PaStreamCallbackFlags statusFlags, void *userData ); /** Opens a stream for either input, output or both. @param stream The address of a PaStream pointer which will receive a pointer to the newly opened stream. @param inputParameters A structure that describes the input parameters used by the opened stream. See PaStreamParameters for a description of these parameters. inputParameters must be NULL for output-only streams. @param outputParameters A structure that describes the output parameters used by the opened stream. See PaStreamParameters for a description of these parameters. outputParameters must be NULL for input-only streams. @param sampleRate The desired sampleRate. For full-duplex streams it is the sample rate for both input and output @param framesPerBuffer The number of frames passed to the stream callback function, or the preferred block granularity for a blocking read/write stream. The special value paFramesPerBufferUnspecified (0) may be used to request that the stream callback will recieve an optimal (and possibly varying) number of frames based on host requirements and the requested latency settings. Note: With some host APIs, the use of non-zero framesPerBuffer for a callback stream may introduce an additional layer of buffering which could introduce additional latency. PortAudio guarantees that the additional latency will be kept to the theoretical minimum however, it is strongly recommended that a non-zero framesPerBuffer value only be used when your algorithm requires a fixed number of frames per stream callback. @param streamFlags Flags which modify the behaviour of the streaming process. This parameter may contain a combination of flags ORed together. Some flags may only be relevant to certain buffer formats. @param streamCallback A pointer to a client supplied function that is responsible for processing and filling input and output buffers. If this parameter is NULL the stream will be opened in 'blocking read/write' mode. In blocking mode, the client can receive sample data using Pa_ReadStream and write sample data using Pa_WriteStream, the number of samples that may be read or written without blocking is returned by Pa_GetStreamReadAvailable and Pa_GetStreamWriteAvailable respectively. @param userData A client supplied pointer which is passed to the stream callback function. It could for example, contain a pointer to instance data necessary for processing the audio buffers. This parameter is ignored if streamCallback is NULL. @return Upon success Pa_OpenStream() returns paNoError and places a pointer to a valid PaStream in the stream argument. The stream is inactive (stopped). If a call to Pa_OpenStream() fails, a non-zero error code is returned (see PaError for possible error codes) and the value of stream is invalid. @see PaStreamParameters, PaStreamCallback, Pa_ReadStream, Pa_WriteStream, Pa_GetStreamReadAvailable, Pa_GetStreamWriteAvailable */ PaError Pa_OpenStream( PaStream** stream, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ); /** A simplified version of Pa_OpenStream() that opens the default input and/or output devices. @param stream The address of a PaStream pointer which will receive a pointer to the newly opened stream. @param numInputChannels The number of channels of sound that will be supplied to the stream callback or returned by Pa_ReadStream. It can range from 1 to the value of maxInputChannels in the PaDeviceInfo record for the default input device. If 0 the stream is opened as an output-only stream. @param numOutputChannels The number of channels of sound to be delivered to the stream callback or passed to Pa_WriteStream. It can range from 1 to the value of maxOutputChannels in the PaDeviceInfo record for the default output dvice. If 0 the stream is opened as an output-only stream. @param sampleFormat The sample format of both the input and output buffers provided to the callback or passed to and from Pa_ReadStream and Pa_WriteStream. sampleFormat may be any of the formats described by the PaSampleFormat enumeration. @param sampleRate Same as Pa_OpenStream parameter of the same name. @param framesPerBuffer Same as Pa_OpenStream parameter of the same name. @param streamCallback Same as Pa_OpenStream parameter of the same name. @param userData Same as Pa_OpenStream parameter of the same name. @return As for Pa_OpenStream @see Pa_OpenStream, PaStreamCallback */ PaError Pa_OpenDefaultStream( PaStream** stream, int numInputChannels, int numOutputChannels, PaSampleFormat sampleFormat, double sampleRate, unsigned long framesPerBuffer, PaStreamCallback *streamCallback, void *userData ); /** Closes an audio stream. If the audio stream is active it discards any pending buffers as if Pa_AbortStream() had been called. */ PaError Pa_CloseStream( PaStream *stream ); /** Functions of type PaStreamFinishedCallback are implemented by PortAudio clients. They can be registered with a stream using the Pa_SetStreamFinishedCallback function. Once registered they are called when the stream becomes inactive (ie once a call to Pa_StopStream() will not block). A stream will become inactive after the stream callback returns non-zero, or when Pa_StopStream or Pa_AbortStream is called. For a stream providing audio output, if the stream callback returns paComplete, or Pa_StopStream is called, the stream finished callback will not be called until all generated sample data has been played. @param userData The userData parameter supplied to Pa_OpenStream() @see Pa_SetStreamFinishedCallback */ typedef void PaStreamFinishedCallback( void *userData ); /** Register a stream finished callback function which will be called when the stream becomes inactive. See the description of PaStreamFinishedCallback for further details about when the callback will be called. @param stream a pointer to a PaStream that is in the stopped state - if the stream is not stopped, the stream's finished callback will remain unchanged and an error code will be returned. @param streamFinishedCallback a pointer to a function with the same signature as PaStreamFinishedCallback, that will be called when the stream becomes inactive. Passing NULL for this parameter will un-register a previously registered stream finished callback function. @return on success returns paNoError, otherwise an error code indicating the cause of the error. @see PaStreamFinishedCallback */ PaError Pa_SetStreamFinishedCallback( PaStream *stream, PaStreamFinishedCallback* streamFinishedCallback ); /** Commences audio processing. */ PaError Pa_StartStream( PaStream *stream ); /** Terminates audio processing. It waits until all pending audio buffers have been played before it returns. */ PaError Pa_StopStream( PaStream *stream ); /** Terminates audio processing immediately without waiting for pending buffers to complete. */ PaError Pa_AbortStream( PaStream *stream ); /** Determine whether the stream is stopped. A stream is considered to be stopped prior to a successful call to Pa_StartStream and after a successful call to Pa_StopStream or Pa_AbortStream. If a stream callback returns a value other than paContinue the stream is NOT considered to be stopped. @return Returns one (1) when the stream is stopped, zero (0) when the stream is running or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. @see Pa_StopStream, Pa_AbortStream, Pa_IsStreamActive */ PaError Pa_IsStreamStopped( PaStream *stream ); /** Determine whether the stream is active. A stream is active after a successful call to Pa_StartStream(), until it becomes inactive either as a result of a call to Pa_StopStream() or Pa_AbortStream(), or as a result of a return value other than paContinue from the stream callback. In the latter case, the stream is considered inactive after the last buffer has finished playing. @return Returns one (1) when the stream is active (ie playing or recording audio), zero (0) when not playing or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. @see Pa_StopStream, Pa_AbortStream, Pa_IsStreamStopped */ PaError Pa_IsStreamActive( PaStream *stream ); /** A structure containing unchanging information about an open stream. @see Pa_GetStreamInfo */ typedef struct PaStreamInfo { /** this is struct version 1 */ int structVersion; /** The input latency of the stream in seconds. This value provides the most accurate estimate of input latency available to the implementation. It may differ significantly from the suggestedLatency value passed to Pa_OpenStream(). The value of this field will be zero (0.) for output-only streams. @see PaTime */ PaTime inputLatency; /** The output latency of the stream in seconds. This value provides the most accurate estimate of output latency available to the implementation. It may differ significantly from the suggestedLatency value passed to Pa_OpenStream(). The value of this field will be zero (0.) for input-only streams. @see PaTime */ PaTime outputLatency; /** The sample rate of the stream in Hertz (samples per second). In cases where the hardware sample rate is inaccurate and PortAudio is aware of it, the value of this field may be different from the sampleRate parameter passed to Pa_OpenStream(). If information about the actual hardware sample rate is not available, this field will have the same value as the sampleRate parameter passed to Pa_OpenStream(). */ double sampleRate; } PaStreamInfo; /** Retrieve a pointer to a PaStreamInfo structure containing information about the specified stream. @return A pointer to an immutable PaStreamInfo structure. If the stream parameter invalid, or an error is encountered, the function returns NULL. @param stream A pointer to an open stream previously created with Pa_OpenStream. @note PortAudio manages the memory referenced by the returned pointer, the client must not manipulate or free the memory. The pointer is only guaranteed to be valid until the specified stream is closed. @see PaStreamInfo */ const PaStreamInfo* Pa_GetStreamInfo( PaStream *stream ); /** Determine the current time for the stream according to the same clock used to generate buffer timestamps. This time may be used for syncronising other events to the audio stream, for example synchronizing audio to MIDI. @return The stream's current time in seconds, or 0 if an error occurred. @see PaTime, PaStreamCallback */ PaTime Pa_GetStreamTime( PaStream *stream ); /** Retrieve CPU usage information for the specified stream. The "CPU Load" is a fraction of total CPU time consumed by a callback stream's audio processing routines including, but not limited to the client supplied stream callback. This function does not work with blocking read/write streams. This function may be called from the stream callback function or the application. @return A floating point value, typically between 0.0 and 1.0, where 1.0 indicates that the stream callback is consuming the maximum number of CPU cycles possible to maintain real-time operation. A value of 0.5 would imply that PortAudio and the stream callback was consuming roughly 50% of the available CPU time. The return value may exceed 1.0. A value of 0.0 will always be returned for a blocking read/write stream, or if an error occurrs. */ double Pa_GetStreamCpuLoad( PaStream* stream ); /** Read samples from an input stream. The function doesn't return until the entire buffer has been filled - this may involve waiting for the operating system to supply the data. @param stream A pointer to an open stream previously created with Pa_OpenStream. @param buffer A pointer to a buffer of sample frames. The buffer contains samples in the format specified by the inputParameters->sampleFormat field used to open the stream, and the number of channels specified by inputParameters->numChannels. If non-interleaved samples were requested, buffer is a pointer to the first element of an array of non-interleaved buffer pointers, one for each channel. @param frames The number of frames to be read into buffer. This parameter is not constrained to a specific range, however high performance applications will want to match this parameter to the framesPerBuffer parameter used when opening the stream. @return On success PaNoError will be returned, or PaInputOverflowed if input data was discarded by PortAudio after the previous call and before this call. */ PaError Pa_ReadStream( PaStream* stream, void *buffer, unsigned long frames ); /** Write samples to an output stream. This function doesn't return until the entire buffer has been consumed - this may involve waiting for the operating system to consume the data. @param stream A pointer to an open stream previously created with Pa_OpenStream. @param buffer A pointer to a buffer of sample frames. The buffer contains samples in the format specified by the outputParameters->sampleFormat field used to open the stream, and the number of channels specified by outputParameters->numChannels. If non-interleaved samples were requested, buffer is a pointer to the first element of an array of non-interleaved buffer pointers, one for each channel. @param frames The number of frames to be written from buffer. This parameter is not constrained to a specific range, however high performance applications will want to match this parameter to the framesPerBuffer parameter used when opening the stream. @return On success PaNoError will be returned, or paOutputUnderflowed if additional output data was inserted after the previous call and before this call. */ PaError Pa_WriteStream( PaStream* stream, const void *buffer, unsigned long frames ); /** Retrieve the number of frames that can be read from the stream without waiting. @return Returns a non-negative value representing the maximum number of frames that can be read from the stream without blocking or busy waiting or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. */ signed long Pa_GetStreamReadAvailable( PaStream* stream ); /** Retrieve the number of frames that can be written to the stream without waiting. @return Returns a non-negative value representing the maximum number of frames that can be written to the stream without blocking or busy waiting or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. */ signed long Pa_GetStreamWriteAvailable( PaStream* stream ); /* Miscellaneous utilities */ /** Retrieve the size of a given sample format in bytes. @return The size in bytes of a single sample in the specified format, or paSampleFormatNotSupported if the format is not supported. */ PaError Pa_GetSampleSize( PaSampleFormat format ); /** Put the caller to sleep for at least 'msec' milliseconds. This function is provided only as a convenience for authors of portable code (such as the tests and examples in the PortAudio distribution.) The function may sleep longer than requested so don't rely on this for accurate musical timing. */ void Pa_Sleep( long msec ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PORTAUDIO_H */ sources_5316/external/portaudio/pa_linux_alsa.c0000644000176700017670000036766611630476766020606 0ustar paulpaul#ifdef UNIX /* * $Id: pa_linux_alsa.c 1278 2007-09-12 17:39:48Z aknudsen $ * PortAudio Portable Real-Time Audio Library * Latest Version at: http://www.portaudio.com * ALSA implementation by Joshua Haberman and Arve Knudsen * * Copyright (c) 2002 Joshua Haberman * Copyright (c) 2005-2007 Arve Knudsen * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostapi_src */ #define ALSA_PCM_NEW_HW_PARAMS_API #define ALSA_PCM_NEW_SW_PARAMS_API #include #undef ALSA_PCM_NEW_HW_PARAMS_API #undef ALSA_PCM_NEW_SW_PARAMS_API #include #include /* strlen() */ #include #include #include #include #include #include #include /* For sig_atomic_t */ #include "portaudio.h" #include "pa_util.h" #include "pa_unix_util.h" #include "pa_allocation.h" #include "pa_hostapi.h" #include "pa_stream.h" #include "pa_cpuload.h" #include "pa_process.h" #include "pa_endianness.h" #include "pa_debugprint.h" #include "pa_linux_alsa.h" /* Check return value of ALSA function, and map it to PaError */ #define ENSURE_(expr, code) \ do { \ if( UNLIKELY( (aErr_ = (expr)) < 0 ) ) \ { \ /* PaUtil_SetLastHostErrorInfo should only be used in the main thread */ \ if( (code) == paUnanticipatedHostError && pthread_equal( pthread_self(), paUnixMainThread) ) \ { \ PaUtil_SetLastHostErrorInfo( paALSA, aErr_, snd_strerror( aErr_ ) ); \ } \ PaUtil_DebugPrint( "Expression '" #expr "' failed in '" __FILE__ "', line: " STRINGIZE( __LINE__ ) "\n" ); \ if( (code) == paUnanticipatedHostError ) \ PA_DEBUG(( "Host error description: %s\n", snd_strerror( aErr_ ) )); \ result = (code); \ goto error; \ } \ } while( 0 ); #define ASSERT_CALL_(expr, success) \ aErr_ = (expr); \ assert( success == aErr_ ); static int aErr_; /* Used with ENSURE_ */ static int numPeriods_ = 4; int PaAlsa_SetNumPeriods( int numPeriods ) { numPeriods_ = numPeriods; return paNoError; } typedef enum { StreamDirection_In, StreamDirection_Out } StreamDirection; typedef struct { PaSampleFormat hostSampleFormat; unsigned long framesPerBuffer; int numUserChannels, numHostChannels; int userInterleaved, hostInterleaved; PaDeviceIndex device; /* Keep the device index */ snd_pcm_t *pcm; snd_pcm_uframes_t bufferSize; snd_pcm_format_t nativeFormat; unsigned int nfds; int ready; /* Marked ready from poll */ void **userBuffers; snd_pcm_uframes_t offset; StreamDirection streamDir; snd_pcm_channel_area_t *channelAreas; /* Needed for channel adaption */ } PaAlsaStreamComponent; /* Implementation specific stream structure */ typedef struct PaAlsaStream { PaUtilStreamRepresentation streamRepresentation; PaUtilCpuLoadMeasurer cpuLoadMeasurer; PaUtilBufferProcessor bufferProcessor; PaUnixThread thread; unsigned long framesPerUserBuffer, maxFramesPerHostBuffer; int primeBuffers; int callbackMode; /* bool: are we running in callback mode? */ int pcmsSynced; /* Have we successfully synced pcms */ int rtSched; /* the callback thread uses these to poll the sound device(s), waiting * for data to be ready/available */ struct pollfd* pfds; int pollTimeout; /* Used in communication between threads */ volatile sig_atomic_t callback_finished; /* bool: are we in the "callback finished" state? */ volatile sig_atomic_t callbackAbort; /* Drop frames? */ volatile sig_atomic_t isActive; /* Is stream in active state? (Between StartStream and StopStream || !paContinue) */ PaUnixMutex stateMtx; /* Used to synchronize access to stream state */ int neverDropInput; PaTime underrun; PaTime overrun; PaAlsaStreamComponent capture, playback; } PaAlsaStream; /* PaAlsaHostApiRepresentation - host api datastructure specific to this implementation */ typedef struct PaAlsaHostApiRepresentation { PaUtilHostApiRepresentation baseHostApiRep; PaUtilStreamInterface callbackStreamInterface; PaUtilStreamInterface blockingStreamInterface; PaUtilAllocationGroup *allocations; PaHostApiIndex hostApiIndex; } PaAlsaHostApiRepresentation; typedef struct PaAlsaDeviceInfo { PaDeviceInfo baseDeviceInfo; char *alsaName; int isPlug; int minInputChannels; int minOutputChannels; } PaAlsaDeviceInfo; /* prototypes for functions declared in this file */ static void Terminate( struct PaUtilHostApiRepresentation *hostApi ); static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *callback, void *userData ); static PaError CloseStream( PaStream* stream ); static PaError StartStream( PaStream *stream ); static PaError StopStream( PaStream *stream ); static PaError AbortStream( PaStream *stream ); static PaError IsStreamStopped( PaStream *s ); static PaError IsStreamActive( PaStream *stream ); static PaTime GetStreamTime( PaStream *stream ); static double GetStreamCpuLoad( PaStream* stream ); static PaError BuildDeviceList( PaAlsaHostApiRepresentation *hostApi ); static int SetApproximateSampleRate( snd_pcm_t *pcm, snd_pcm_hw_params_t *hwParams, double sampleRate ); static int GetExactSampleRate( snd_pcm_hw_params_t *hwParams, double *sampleRate ); /* Callback prototypes */ static void *CallbackThreadFunc( void *userData ); /* Blocking prototypes */ static signed long GetStreamReadAvailable( PaStream* s ); static signed long GetStreamWriteAvailable( PaStream* s ); static PaError ReadStream( PaStream* stream, void *buffer, unsigned long frames ); static PaError WriteStream( PaStream* stream, const void *buffer, unsigned long frames ); static const PaAlsaDeviceInfo *GetDeviceInfo( const PaUtilHostApiRepresentation *hostApi, int device ) { return (const PaAlsaDeviceInfo *)hostApi->deviceInfos[device]; } static void AlsaErrorHandler(const char *file, int line, const char *function, int err, const char *fmt, ...) { } PaError PaAlsa_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex hostApiIndex ) { PaError result = paNoError; PaAlsaHostApiRepresentation *alsaHostApi = NULL; PA_UNLESS( alsaHostApi = (PaAlsaHostApiRepresentation*) PaUtil_AllocateMemory( sizeof(PaAlsaHostApiRepresentation) ), paInsufficientMemory ); PA_UNLESS( alsaHostApi->allocations = PaUtil_CreateAllocationGroup(), paInsufficientMemory ); alsaHostApi->hostApiIndex = hostApiIndex; *hostApi = (PaUtilHostApiRepresentation*)alsaHostApi; (*hostApi)->info.structVersion = 1; (*hostApi)->info.type = paALSA; (*hostApi)->info.name = "ALSA"; (*hostApi)->Terminate = Terminate; (*hostApi)->OpenStream = OpenStream; (*hostApi)->IsFormatSupported = IsFormatSupported; ENSURE_( snd_lib_error_set_handler(AlsaErrorHandler), paUnanticipatedHostError ); PA_ENSURE( BuildDeviceList( alsaHostApi ) ); PaUtil_InitializeStreamInterface( &alsaHostApi->callbackStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, GetStreamCpuLoad, PaUtil_DummyRead, PaUtil_DummyWrite, PaUtil_DummyGetReadAvailable, PaUtil_DummyGetWriteAvailable ); PaUtil_InitializeStreamInterface( &alsaHostApi->blockingStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, PaUtil_DummyGetCpuLoad, ReadStream, WriteStream, GetStreamReadAvailable, GetStreamWriteAvailable ); PA_ENSURE( PaUnixThreading_Initialize() ); return result; error: if( alsaHostApi ) { if( alsaHostApi->allocations ) { PaUtil_FreeAllAllocations( alsaHostApi->allocations ); PaUtil_DestroyAllocationGroup( alsaHostApi->allocations ); } PaUtil_FreeMemory( alsaHostApi ); } return result; } static void Terminate( struct PaUtilHostApiRepresentation *hostApi ) { PaAlsaHostApiRepresentation *alsaHostApi = (PaAlsaHostApiRepresentation*)hostApi; assert( hostApi ); if( alsaHostApi->allocations ) { PaUtil_FreeAllAllocations( alsaHostApi->allocations ); PaUtil_DestroyAllocationGroup( alsaHostApi->allocations ); } PaUtil_FreeMemory( alsaHostApi ); snd_config_update_free_global(); } /** Determine max channels and default latencies. * * This function provides functionality to grope an opened (might be opened for capture or playback) pcm device for * traits like max channels, suitable default latencies and default sample rate. Upon error, max channels is set to zero, * and a suitable result returned. The device is closed before returning. */ static PaError GropeDevice( snd_pcm_t* pcm, int isPlug, StreamDirection mode, int openBlocking, PaAlsaDeviceInfo* devInfo, int* canMmap ) { PaError result = paNoError; snd_pcm_hw_params_t *hwParams; snd_pcm_uframes_t lowLatency = 512, highLatency = 2048; unsigned int minChans, maxChans; int* minChannels, * maxChannels; double * defaultLowLatency, * defaultHighLatency, * defaultSampleRate = &devInfo->baseDeviceInfo.defaultSampleRate; double defaultSr = *defaultSampleRate; assert( pcm ); if( StreamDirection_In == mode ) { minChannels = &devInfo->minInputChannels; maxChannels = &devInfo->baseDeviceInfo.maxInputChannels; defaultLowLatency = &devInfo->baseDeviceInfo.defaultLowInputLatency; defaultHighLatency = &devInfo->baseDeviceInfo.defaultHighInputLatency; } else { minChannels = &devInfo->minOutputChannels; maxChannels = &devInfo->baseDeviceInfo.maxOutputChannels; defaultLowLatency = &devInfo->baseDeviceInfo.defaultLowOutputLatency; defaultHighLatency = &devInfo->baseDeviceInfo.defaultHighOutputLatency; } ENSURE_( snd_pcm_nonblock( pcm, 0 ), paUnanticipatedHostError ); snd_pcm_hw_params_alloca( &hwParams ); snd_pcm_hw_params_any( pcm, hwParams ); *canMmap = snd_pcm_hw_params_test_access( pcm, hwParams, SND_PCM_ACCESS_MMAP_INTERLEAVED ) >= 0 || snd_pcm_hw_params_test_access( pcm, hwParams, SND_PCM_ACCESS_MMAP_NONINTERLEAVED ) >= 0; if( defaultSr >= 0 ) { /* Could be that the device opened in one mode supports samplerates that the other mode wont have, * so try again .. */ if( SetApproximateSampleRate( pcm, hwParams, defaultSr ) < 0 ) { defaultSr = -1.; PA_DEBUG(( "%s: Original default samplerate failed, trying again ..\n", __FUNCTION__ )); } } if( defaultSr < 0. ) /* Default sample rate not set */ { unsigned int sampleRate = 44100; /* Will contain approximate rate returned by alsa-lib */ if( snd_pcm_hw_params_set_rate_near( pcm, hwParams, &sampleRate, NULL ) < 0) { result = paUnanticipatedHostError; goto error; } ENSURE_( GetExactSampleRate( hwParams, &defaultSr ), paUnanticipatedHostError ); } ENSURE_( snd_pcm_hw_params_get_channels_min( hwParams, &minChans ), paUnanticipatedHostError ); ENSURE_( snd_pcm_hw_params_get_channels_max( hwParams, &maxChans ), paUnanticipatedHostError ); assert( maxChans <= INT_MAX ); assert( maxChans > 0 ); /* Weird linking issue could cause wrong version of ALSA symbols to be called, resulting in zeroed values */ /* XXX: Limit to sensible number (ALSA plugins accept a crazy amount of channels)? */ if( isPlug && maxChans > 128 ) { maxChans = 128; PA_DEBUG(( "%s: Limiting number of plugin channels to %u\n", __FUNCTION__, maxChans )); } /* TWEAKME: * * Giving values for default min and max latency is not * straightforward. Here are our objectives: * * * for low latency, we want to give the lowest value * that will work reliably. This varies based on the * sound card, kernel, CPU, etc. I think it is better * to give sub-optimal latency than to give a number * too low and cause dropouts. My conservative * estimate at this point is to base it on 4096-sample * latency at 44.1 kHz, which gives a latency of 23ms. * * for high latency we want to give a large enough * value that dropouts are basically impossible. This * doesn't really require as much tweaking, since * providing too large a number will just cause us to * select the nearest setting that will work at stream * config time. */ ENSURE_( snd_pcm_hw_params_set_buffer_size_near( pcm, hwParams, &lowLatency ), paUnanticipatedHostError ); /* Have to reset hwParams, to set new buffer size */ ENSURE_( snd_pcm_hw_params_any( pcm, hwParams ), paUnanticipatedHostError ); ENSURE_( snd_pcm_hw_params_set_buffer_size_near( pcm, hwParams, &highLatency ), paUnanticipatedHostError ); *minChannels = (int)minChans; *maxChannels = (int)maxChans; *defaultSampleRate = defaultSr; *defaultLowLatency = (double) lowLatency / *defaultSampleRate; *defaultHighLatency = (double) highLatency / *defaultSampleRate; end: snd_pcm_close( pcm ); return result; error: goto end; } /* Initialize device info with invalid values (maxInputChannels and maxOutputChannels are set to zero since these indicate * wether input/output is available) */ static void InitializeDeviceInfo( PaDeviceInfo *deviceInfo ) { deviceInfo->structVersion = -1; deviceInfo->name = NULL; deviceInfo->hostApi = -1; deviceInfo->maxInputChannels = 0; deviceInfo->maxOutputChannels = 0; deviceInfo->defaultLowInputLatency = -1.; deviceInfo->defaultLowOutputLatency = -1.; deviceInfo->defaultHighInputLatency = -1.; deviceInfo->defaultHighOutputLatency = -1.; deviceInfo->defaultSampleRate = -1.; } /* Helper struct */ typedef struct { char *alsaName; char *name; int isPlug; int hasPlayback; int hasCapture; } HwDevInfo; HwDevInfo predefinedNames[] = { { "center_lfe", NULL, 0, 1, 0 }, /* { "default", NULL, 0, 1, 0 }, */ /* { "dmix", NULL, 0, 1, 0 }, */ /* { "dpl", NULL, 0, 1, 0 }, */ /* { "dsnoop", NULL, 0, 1, 0 }, */ { "front", NULL, 0, 1, 0 }, { "iec958", NULL, 0, 1, 0 }, /* { "modem", NULL, 0, 1, 0 }, */ { "rear", NULL, 0, 1, 0 }, { "side", NULL, 0, 1, 0 }, /* { "spdif", NULL, 0, 0, 0 }, */ { "surround40", NULL, 0, 1, 0 }, { "surround41", NULL, 0, 1, 0 }, { "surround50", NULL, 0, 1, 0 }, { "surround51", NULL, 0, 1, 0 }, { "surround71", NULL, 0, 1, 0 }, { NULL, NULL, 0, 1, 0 } }; static const HwDevInfo *FindDeviceName( const char *name ) { int i; for( i = 0; predefinedNames[i].alsaName; i++ ) { if( strcmp( name, predefinedNames[i].alsaName ) == 0 ) { return &predefinedNames[i]; } } return NULL; } static PaError PaAlsa_StrDup( PaAlsaHostApiRepresentation *alsaApi, char **dst, const char *src) { PaError result = paNoError; int len = strlen( src ) + 1; /* PA_DEBUG(("PaStrDup %s %d\n", src, len)); */ PA_UNLESS( *dst = (char *)PaUtil_GroupAllocateMemory( alsaApi->allocations, len ), paInsufficientMemory ); strncpy( *dst, src, len ); error: return result; } /* Disregard some standard plugins */ static int IgnorePlugin( const char *pluginId ) { static const char *ignoredPlugins[] = {"hw", "plughw", "plug", "dsnoop", "tee", "file", "null", "shm", "cards", "rate_convert", NULL}; int i = 0; while( ignoredPlugins[i] ) { if( !strcmp( pluginId, ignoredPlugins[i] ) ) { return 1; } ++i; } return 0; } /** Open PCM device. * * Wrapper around snd_pcm_open which may repeatedly retry opening a device if it is busy, for * a certain time. This is because dmix may temporarily hold on to a device after it (dmix) * has been opened and closed. * @param mode: Open mode (e.g., SND_PCM_BLOCKING). * @param waitOnBusy: Retry opening busy device for up to one second? **/ static int OpenPcm( snd_pcm_t **pcmp, const char *name, snd_pcm_stream_t stream, int mode, int waitOnBusy ) { int tries = 0, maxTries = waitOnBusy ? 100 : 0; int ret = snd_pcm_open( pcmp, name, stream, mode ); for( tries = 0; tries < maxTries && -EBUSY == ret; ++tries ) { Pa_Sleep( 10 ); ret = snd_pcm_open( pcmp, name, stream, mode ); if( -EBUSY != ret ) { PA_DEBUG(( "%s: Successfully opened initially busy device after %d tries\n", __FUNCTION__, tries )); } } if( -EBUSY == ret ) { PA_DEBUG(( "%s: Failed to open busy device '%s'\n", __FUNCTION__, name )); } return ret; } static PaError FillInDevInfo( PaAlsaHostApiRepresentation *alsaApi, HwDevInfo* deviceName, int blocking, PaAlsaDeviceInfo* devInfo, int* devIdx ) { PaError result = 0; PaDeviceInfo *baseDeviceInfo = &devInfo->baseDeviceInfo; snd_pcm_t *pcm; int canMmap = -1; PaUtilHostApiRepresentation *baseApi = &alsaApi->baseHostApiRep; /* Zero fields */ InitializeDeviceInfo( baseDeviceInfo ); /* to determine device capabilities, we must open the device and query the * hardware parameter configuration space */ /* Query capture */ if( deviceName->hasCapture && OpenPcm( &pcm, deviceName->alsaName, SND_PCM_STREAM_CAPTURE, blocking, 0 ) >= 0 ) { if( GropeDevice( pcm, deviceName->isPlug, StreamDirection_In, blocking, devInfo, &canMmap ) != paNoError ) { /* Error */ PA_DEBUG(("%s: Failed groping %s for capture\n", __FUNCTION__, deviceName->alsaName)); goto end; } } /* Query playback */ if( deviceName->hasPlayback && OpenPcm( &pcm, deviceName->alsaName, SND_PCM_STREAM_PLAYBACK, blocking, 0 ) >= 0 ) { if( GropeDevice( pcm, deviceName->isPlug, StreamDirection_Out, blocking, devInfo, &canMmap ) != paNoError ) { /* Error */ PA_DEBUG(("%s: Failed groping %s for playback\n", __FUNCTION__, deviceName->alsaName)); goto end; } } if( 0 == canMmap ) { PA_DEBUG(("%s: Device %s doesn't support mmap\n", __FUNCTION__, deviceName->alsaName)); goto end; } baseDeviceInfo->structVersion = 2; baseDeviceInfo->hostApi = alsaApi->hostApiIndex; baseDeviceInfo->name = deviceName->name; devInfo->alsaName = deviceName->alsaName; devInfo->isPlug = deviceName->isPlug; /* A: Storing pointer to PaAlsaDeviceInfo object as pointer to PaDeviceInfo object. * Should now be safe to add device info, unless the device supports neither capture nor playback */ if( baseDeviceInfo->maxInputChannels > 0 || baseDeviceInfo->maxOutputChannels > 0 ) { /* Make device default if there isn't already one or it is the ALSA "default" device */ if( (baseApi->info.defaultInputDevice == paNoDevice || !strcmp(deviceName->alsaName, "default" )) && baseDeviceInfo->maxInputChannels > 0 ) { baseApi->info.defaultInputDevice = *devIdx; PA_DEBUG(("Default input device: %s\n", deviceName->name)); } if( (baseApi->info.defaultOutputDevice == paNoDevice || !strcmp(deviceName->alsaName, "default" )) && baseDeviceInfo->maxOutputChannels > 0 ) { baseApi->info.defaultOutputDevice = *devIdx; PA_DEBUG(("Default output device: %s\n", deviceName->name)); } PA_DEBUG(("%s: Adding device %s: %d\n", __FUNCTION__, deviceName->name, *devIdx)); baseApi->deviceInfos[*devIdx] = (PaDeviceInfo *) devInfo; (*devIdx) += 1; } end: return result; } /* Build PaDeviceInfo list, ignore devices for which we cannot determine capabilities (possibly busy, sigh) */ static PaError BuildDeviceList( PaAlsaHostApiRepresentation *alsaApi ) { PaUtilHostApiRepresentation *baseApi = &alsaApi->baseHostApiRep; PaAlsaDeviceInfo *deviceInfoArray; int cardIdx = -1, devIdx = 0; snd_ctl_card_info_t *cardInfo; PaError result = paNoError; size_t numDeviceNames = 0, maxDeviceNames = 1, i; HwDevInfo *hwDevInfos = NULL; snd_config_t *topNode = NULL; snd_pcm_info_t *pcmInfo; int res; int blocking = SND_PCM_NONBLOCK; char alsaCardName[50]; #ifdef PA_ENABLE_DEBUG_OUTPUT PaTime startTime = PaUtil_GetTime(); #endif if( getenv( "PA_ALSA_INITIALIZE_BLOCK" ) && atoi( getenv( "PA_ALSA_INITIALIZE_BLOCK" ) ) ) blocking = 0; /* These two will be set to the first working input and output device, respectively */ baseApi->info.defaultInputDevice = paNoDevice; baseApi->info.defaultOutputDevice = paNoDevice; /* Gather info about hw devices * snd_card_next() modifies the integer passed to it to be: * the index of the first card if the parameter is -1 * the index of the next card if the parameter is the index of a card * -1 if there are no more cards * * The function itself returns 0 if it succeeded. */ cardIdx = -1; snd_ctl_card_info_alloca( &cardInfo ); snd_pcm_info_alloca( &pcmInfo ); while( snd_card_next( &cardIdx ) == 0 && cardIdx >= 0 ) { char *cardName; int devIdx = -1; snd_ctl_t *ctl; char buf[50]; snprintf( alsaCardName, sizeof (alsaCardName), "hw:%d", cardIdx ); /* Acquire name of card */ if( snd_ctl_open( &ctl, alsaCardName, 0 ) < 0 ) { /* Unable to open card :( */ PA_DEBUG(( "%s: Unable to open device %s\n", __FUNCTION__, alsaCardName )); continue; } snd_ctl_card_info( ctl, cardInfo ); PA_ENSURE( PaAlsa_StrDup( alsaApi, &cardName, snd_ctl_card_info_get_name( cardInfo )) ); while( snd_ctl_pcm_next_device( ctl, &devIdx ) == 0 && devIdx >= 0 ) { char *alsaDeviceName, *deviceName; size_t len; int hasPlayback = 0, hasCapture = 0; snprintf( buf, sizeof (buf), "hw:%d,%d", cardIdx, devIdx ); /* Obtain info about this particular device */ snd_pcm_info_set_device( pcmInfo, devIdx ); snd_pcm_info_set_subdevice( pcmInfo, 0 ); snd_pcm_info_set_stream( pcmInfo, SND_PCM_STREAM_CAPTURE ); if( snd_ctl_pcm_info( ctl, pcmInfo ) >= 0 ) { hasCapture = 1; } snd_pcm_info_set_stream( pcmInfo, SND_PCM_STREAM_PLAYBACK ); if( snd_ctl_pcm_info( ctl, pcmInfo ) >= 0 ) { hasPlayback = 1; } if( !hasPlayback && !hasCapture ) { /* Error */ continue; } /* The length of the string written by snprintf plus terminating 0 */ len = snprintf( NULL, 0, "%s: %s (%s)", cardName, snd_pcm_info_get_name( pcmInfo ), buf ) + 1; PA_UNLESS( deviceName = (char *)PaUtil_GroupAllocateMemory( alsaApi->allocations, len ), paInsufficientMemory ); snprintf( deviceName, len, "%s: %s (%s)", cardName, snd_pcm_info_get_name( pcmInfo ), buf ); ++numDeviceNames; if( !hwDevInfos || numDeviceNames > maxDeviceNames ) { maxDeviceNames *= 2; PA_UNLESS( hwDevInfos = (HwDevInfo *) realloc( hwDevInfos, maxDeviceNames * sizeof (HwDevInfo) ), paInsufficientMemory ); } PA_ENSURE( PaAlsa_StrDup( alsaApi, &alsaDeviceName, buf ) ); hwDevInfos[ numDeviceNames - 1 ].alsaName = alsaDeviceName; hwDevInfos[ numDeviceNames - 1 ].name = deviceName; hwDevInfos[ numDeviceNames - 1 ].isPlug = 0; hwDevInfos[ numDeviceNames - 1 ].hasPlayback = hasPlayback; hwDevInfos[ numDeviceNames - 1 ].hasCapture = hasCapture; } snd_ctl_close( ctl ); } /* Iterate over plugin devices */ if( NULL == snd_config ) { /* snd_config_update is called implicitly by some functions, if this hasn't happened snd_config will be NULL (bleh) */ ENSURE_( snd_config_update(), paUnanticipatedHostError ); PA_DEBUG(( "Updating snd_config\n" )); } assert( snd_config ); if( (res = snd_config_search( snd_config, "pcm", &topNode )) >= 0 ) { snd_config_iterator_t i, next; snd_config_for_each( i, next, topNode ) { const char *tpStr = "unknown", *idStr = NULL; int err = 0; char *alsaDeviceName, *deviceName; const HwDevInfo *predefined = NULL; snd_config_t *n = snd_config_iterator_entry( i ), * tp = NULL;; if( (err = snd_config_search( n, "type", &tp )) < 0 ) { if( -ENOENT != err ) { ENSURE_(err, paUnanticipatedHostError); } } else { ENSURE_( snd_config_get_string( tp, &tpStr ), paUnanticipatedHostError ); } ENSURE_( snd_config_get_id( n, &idStr ), paUnanticipatedHostError ); if( IgnorePlugin( idStr ) ) { PA_DEBUG(( "%s: Ignoring ALSA plugin device %s of type %s\n", __FUNCTION__, idStr, tpStr )); continue; } PA_DEBUG(( "%s: Found plugin %s of type %s\n", __FUNCTION__, idStr, tpStr )); PA_UNLESS( alsaDeviceName = (char*)PaUtil_GroupAllocateMemory( alsaApi->allocations, strlen(idStr) + 6 ), paInsufficientMemory ); strcpy( alsaDeviceName, idStr ); PA_UNLESS( deviceName = (char*)PaUtil_GroupAllocateMemory( alsaApi->allocations, strlen(idStr) + 1 ), paInsufficientMemory ); strcpy( deviceName, idStr ); ++numDeviceNames; if( !hwDevInfos || numDeviceNames > maxDeviceNames ) { maxDeviceNames *= 2; PA_UNLESS( hwDevInfos = (HwDevInfo *) realloc( hwDevInfos, maxDeviceNames * sizeof (HwDevInfo) ), paInsufficientMemory ); } predefined = FindDeviceName( alsaDeviceName ); hwDevInfos[numDeviceNames - 1].alsaName = alsaDeviceName; hwDevInfos[numDeviceNames - 1].name = deviceName; hwDevInfos[numDeviceNames - 1].isPlug = 1; if( predefined ) { hwDevInfos[numDeviceNames - 1].hasPlayback = predefined->hasPlayback; hwDevInfos[numDeviceNames - 1].hasCapture = predefined->hasCapture; } else { hwDevInfos[numDeviceNames - 1].hasPlayback = 1; hwDevInfos[numDeviceNames - 1].hasCapture = 1; } } } else PA_DEBUG(( "%s: Iterating over ALSA plugins failed: %s\n", __FUNCTION__, snd_strerror( res ) )); /* allocate deviceInfo memory based on the number of devices */ PA_UNLESS( baseApi->deviceInfos = (PaDeviceInfo**)PaUtil_GroupAllocateMemory( alsaApi->allocations, sizeof(PaDeviceInfo*) * (numDeviceNames) ), paInsufficientMemory ); /* allocate all device info structs in a contiguous block */ PA_UNLESS( deviceInfoArray = (PaAlsaDeviceInfo*)PaUtil_GroupAllocateMemory( alsaApi->allocations, sizeof(PaAlsaDeviceInfo) * numDeviceNames ), paInsufficientMemory ); /* Loop over list of cards, filling in info. If a device is deemed unavailable (can't get name), * it's ignored. * * Note that we do this in two stages. This is a workaround owing to the fact that the 'dmix' * plugin may cause the underlying hardware device to be busy for a short while even after it * (dmix) is closed. The 'default' plugin may also point to the dmix plugin, so the same goes * for this. */ for( i = 0, devIdx = 0; i < numDeviceNames; ++i ) { PaAlsaDeviceInfo* devInfo = &deviceInfoArray[i]; HwDevInfo* hwInfo = &hwDevInfos[i]; if( !strcmp( hwInfo->name, "dmix" ) || !strcmp( hwInfo->name, "default" ) ) { continue; } PA_ENSURE( FillInDevInfo( alsaApi, hwInfo, blocking, devInfo, &devIdx ) ); } assert( devIdx < numDeviceNames ); /* Now inspect 'dmix' and 'default' plugins */ for( i = 0; i < numDeviceNames; ++i ) { PaAlsaDeviceInfo* devInfo = &deviceInfoArray[i]; HwDevInfo* hwInfo = &hwDevInfos[i]; if( strcmp( hwInfo->name, "dmix" ) && strcmp( hwInfo->name, "default" ) ) { continue; } PA_ENSURE( FillInDevInfo( alsaApi, hwInfo, blocking, devInfo, &devIdx ) ); } free( hwDevInfos ); baseApi->info.deviceCount = devIdx; /* Number of successfully queried devices */ #ifdef PA_ENABLE_DEBUG_OUTPUT PA_DEBUG(( "%s: Building device list took %f seconds\n", __FUNCTION__, PaUtil_GetTime() - startTime )); #endif end: return result; error: /* No particular action */ goto end; } /* Check against known device capabilities */ static PaError ValidateParameters( const PaStreamParameters *parameters, PaUtilHostApiRepresentation *hostApi, StreamDirection mode ) { PaError result = paNoError; int maxChans; const PaAlsaDeviceInfo *deviceInfo = NULL; assert( parameters ); if( parameters->device != paUseHostApiSpecificDeviceSpecification ) { assert( parameters->device < hostApi->info.deviceCount ); PA_UNLESS( parameters->hostApiSpecificStreamInfo == NULL, paBadIODeviceCombination ); deviceInfo = GetDeviceInfo( hostApi, parameters->device ); } else { const PaAlsaStreamInfo *streamInfo = parameters->hostApiSpecificStreamInfo; PA_UNLESS( parameters->device == paUseHostApiSpecificDeviceSpecification, paInvalidDevice ); PA_UNLESS( streamInfo->size == sizeof (PaAlsaStreamInfo) && streamInfo->version == 1, paIncompatibleHostApiSpecificStreamInfo ); PA_UNLESS( streamInfo->deviceString != NULL, paInvalidDevice ); /* Skip further checking */ return paNoError; } assert( deviceInfo ); assert( parameters->hostApiSpecificStreamInfo == NULL ); maxChans = (StreamDirection_In == mode ? deviceInfo->baseDeviceInfo.maxInputChannels : deviceInfo->baseDeviceInfo.maxOutputChannels); PA_UNLESS( parameters->channelCount <= maxChans, paInvalidChannelCount ); error: return result; } /* Given an open stream, what sample formats are available? */ static PaSampleFormat GetAvailableFormats( snd_pcm_t *pcm ) { PaSampleFormat available = 0; snd_pcm_hw_params_t *hwParams; snd_pcm_hw_params_alloca( &hwParams ); snd_pcm_hw_params_any( pcm, hwParams ); if( snd_pcm_hw_params_test_format( pcm, hwParams, SND_PCM_FORMAT_FLOAT ) >= 0) available |= paFloat32; if( snd_pcm_hw_params_test_format( pcm, hwParams, SND_PCM_FORMAT_S32 ) >= 0) available |= paInt32; #ifdef PA_LITTLE_ENDIAN if( snd_pcm_hw_params_test_format( pcm, hwParams, SND_PCM_FORMAT_S24_3LE ) >= 0) available |= paInt24; #elif defined PA_BIG_ENDIAN if( snd_pcm_hw_params_test_format( pcm, hwParams, SND_PCM_FORMAT_S24_3BE ) >= 0) available |= paInt24; #endif if( snd_pcm_hw_params_test_format( pcm, hwParams, SND_PCM_FORMAT_S16 ) >= 0) available |= paInt16; if( snd_pcm_hw_params_test_format( pcm, hwParams, SND_PCM_FORMAT_U8 ) >= 0) available |= paUInt8; if( snd_pcm_hw_params_test_format( pcm, hwParams, SND_PCM_FORMAT_S8 ) >= 0) available |= paInt8; return available; } static snd_pcm_format_t Pa2AlsaFormat( PaSampleFormat paFormat ) { switch( paFormat ) { case paFloat32: return SND_PCM_FORMAT_FLOAT; case paInt16: return SND_PCM_FORMAT_S16; case paInt24: #ifdef PA_LITTLE_ENDIAN return SND_PCM_FORMAT_S24_3LE; #elif defined PA_BIG_ENDIAN return SND_PCM_FORMAT_S24_3BE; #endif case paInt32: return SND_PCM_FORMAT_S32; case paInt8: return SND_PCM_FORMAT_S8; case paUInt8: return SND_PCM_FORMAT_U8; default: return SND_PCM_FORMAT_UNKNOWN; } } /** Open an ALSA pcm handle. * * The device to be open can be specified in a custom PaAlsaStreamInfo struct, or it will be a device number. In case of a * device number, it maybe specified through an env variable (PA_ALSA_PLUGHW) that we should open the corresponding plugin * device. */ static PaError AlsaOpen( const PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *params, StreamDirection streamDir, snd_pcm_t **pcm ) { PaError result = paNoError; int ret; char dnameArray[50]; const char* deviceName = dnameArray; const PaAlsaDeviceInfo *deviceInfo = NULL; PaAlsaStreamInfo *streamInfo = (PaAlsaStreamInfo *)params->hostApiSpecificStreamInfo; if( !streamInfo ) { int usePlug = 0; deviceInfo = GetDeviceInfo( hostApi, params->device ); /* If device name starts with hw: and PA_ALSA_PLUGHW is 1, we open the plughw device instead */ if( !strncmp( "hw:", deviceInfo->alsaName, 3 ) && getenv( "PA_ALSA_PLUGHW" ) ) usePlug = atoi( getenv( "PA_ALSA_PLUGHW" ) ); if( usePlug ) snprintf( dnameArray, 50, "plug%s", deviceInfo->alsaName ); else deviceName = deviceInfo->alsaName; } else deviceName = streamInfo->deviceString; PA_DEBUG(( "%s: Opening device %s\n", __FUNCTION__, deviceName )); if( (ret = OpenPcm( pcm, deviceName, streamDir == StreamDirection_In ? SND_PCM_STREAM_CAPTURE : SND_PCM_STREAM_PLAYBACK, SND_PCM_NONBLOCK, 1 )) < 0 ) { /* Not to be closed */ *pcm = NULL; ENSURE_( ret, -EBUSY == ret ? paDeviceUnavailable : paBadIODeviceCombination ); } ENSURE_( snd_pcm_nonblock( *pcm, 0 ), paUnanticipatedHostError ); end: return result; error: goto end; } static PaError TestParameters( const PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *parameters, double sampleRate, StreamDirection streamDir ) { PaError result = paNoError; snd_pcm_t *pcm = NULL; PaSampleFormat availableFormats; /* We are able to adapt to a number of channels less than what the device supports */ unsigned int numHostChannels; PaSampleFormat hostFormat; snd_pcm_hw_params_t *hwParams; snd_pcm_hw_params_alloca( &hwParams ); if( !parameters->hostApiSpecificStreamInfo ) { const PaAlsaDeviceInfo *devInfo = GetDeviceInfo( hostApi, parameters->device ); numHostChannels = PA_MAX( parameters->channelCount, StreamDirection_In == streamDir ? devInfo->minInputChannels : devInfo->minOutputChannels ); } else numHostChannels = parameters->channelCount; PA_ENSURE( AlsaOpen( hostApi, parameters, streamDir, &pcm ) ); snd_pcm_hw_params_any( pcm, hwParams ); if( SetApproximateSampleRate( pcm, hwParams, sampleRate ) < 0 ) { result = paInvalidSampleRate; goto error; } if( snd_pcm_hw_params_set_channels( pcm, hwParams, numHostChannels ) < 0 ) { result = paInvalidChannelCount; goto error; } /* See if we can find a best possible match */ availableFormats = GetAvailableFormats( pcm ); PA_ENSURE( hostFormat = PaUtil_SelectClosestAvailableFormat( availableFormats, parameters->sampleFormat ) ); ENSURE_( snd_pcm_hw_params_set_format( pcm, hwParams, Pa2AlsaFormat( hostFormat ) ), paUnanticipatedHostError ); { /* It happens that this call fails because the device is busy */ int ret = 0; if( (ret = snd_pcm_hw_params( pcm, hwParams )) < 0) { if( -EINVAL == ret ) { /* Don't know what to return here */ result = paBadIODeviceCombination; goto error; } else if( -EBUSY == ret ) { result = paDeviceUnavailable; PA_DEBUG(( "%s: Device is busy\n", __FUNCTION__ )); } else { result = paUnanticipatedHostError; } ENSURE_( ret, result ); } } end: if( pcm ) { snd_pcm_close( pcm ); } return result; error: goto end; } static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ) { int inputChannelCount = 0, outputChannelCount = 0; PaSampleFormat inputSampleFormat, outputSampleFormat; PaError result = paFormatIsSupported; if( inputParameters ) { PA_ENSURE( ValidateParameters( inputParameters, hostApi, StreamDirection_In ) ); inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; } if( outputParameters ) { PA_ENSURE( ValidateParameters( outputParameters, hostApi, StreamDirection_Out ) ); outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; } if( inputChannelCount ) { if( (result = TestParameters( hostApi, inputParameters, sampleRate, StreamDirection_In )) != paNoError ) goto error; } if ( outputChannelCount ) { if( (result = TestParameters( hostApi, outputParameters, sampleRate, StreamDirection_Out )) != paNoError ) goto error; } return paFormatIsSupported; error: return result; } static PaError PaAlsaStreamComponent_Initialize( PaAlsaStreamComponent *self, PaAlsaHostApiRepresentation *alsaApi, const PaStreamParameters *params, StreamDirection streamDir, int callbackMode ) { PaError result = paNoError; PaSampleFormat userSampleFormat = params->sampleFormat, hostSampleFormat; assert( params->channelCount > 0 ); /* Make sure things have an initial value */ memset( self, 0, sizeof (PaAlsaStreamComponent) ); if( NULL == params->hostApiSpecificStreamInfo ) { const PaAlsaDeviceInfo *devInfo = GetDeviceInfo( &alsaApi->baseHostApiRep, params->device ); self->numHostChannels = PA_MAX( params->channelCount, StreamDirection_In == streamDir ? devInfo->minInputChannels : devInfo->minOutputChannels ); } else { /* We're blissfully unaware of the minimum channelCount */ self->numHostChannels = params->channelCount; } self->device = params->device; PA_ENSURE( AlsaOpen( &alsaApi->baseHostApiRep, params, streamDir, &self->pcm ) ); self->nfds = snd_pcm_poll_descriptors_count( self->pcm ); hostSampleFormat = PaUtil_SelectClosestAvailableFormat( GetAvailableFormats( self->pcm ), userSampleFormat ); self->hostSampleFormat = hostSampleFormat; self->nativeFormat = Pa2AlsaFormat( hostSampleFormat ); self->hostInterleaved = self->userInterleaved = !(userSampleFormat & paNonInterleaved); self->numUserChannels = params->channelCount; self->streamDir = streamDir; if( !callbackMode && !self->userInterleaved ) { /* Pre-allocate non-interleaved user provided buffers */ PA_UNLESS( self->userBuffers = PaUtil_AllocateMemory( sizeof (void *) * self->numUserChannels ), paInsufficientMemory ); } error: return result; } static void PaAlsaStreamComponent_Terminate( PaAlsaStreamComponent *self ) { snd_pcm_close( self->pcm ); if( self->userBuffers ) PaUtil_FreeMemory( self->userBuffers ); } /* static int nearbyint_(float value) { if( value - (int)value > .5 ) return (int)ceil( value ); return (int)floor( value ); } */ /** Initiate configuration, preparing for determining a period size suitable for both capture and playback components. * */ static PaError PaAlsaStreamComponent_InitialConfigure( PaAlsaStreamComponent *self, const PaStreamParameters *params, int primeBuffers, snd_pcm_hw_params_t *hwParams, double *sampleRate ) { /* Configuration consists of setting all of ALSA's parameters. * These parameters come in two flavors: hardware parameters * and software paramters. Hardware parameters will affect * the way the device is initialized, software parameters * affect the way ALSA interacts with me, the user-level client. */ PaError result = paNoError; snd_pcm_access_t accessMode, alternateAccessMode; int dir = 0; snd_pcm_t *pcm = self->pcm; double sr = *sampleRate; unsigned int minPeriods = 2; /* self->framesPerBuffer = framesPerHostBuffer; */ /* ... fill up the configuration space with all possibile * combinations of parameters this device will accept */ ENSURE_( snd_pcm_hw_params_any( pcm, hwParams ), paUnanticipatedHostError ); ENSURE_( snd_pcm_hw_params_set_periods_integer( pcm, hwParams ), paUnanticipatedHostError ); /* I think there should be at least 2 periods (even though ALSA doesn't appear to enforce this) */ dir = 0; ENSURE_( snd_pcm_hw_params_set_periods_min( pcm, hwParams, &minPeriods, &dir ), paUnanticipatedHostError ); if( self->userInterleaved ) { accessMode = SND_PCM_ACCESS_MMAP_INTERLEAVED; alternateAccessMode = SND_PCM_ACCESS_MMAP_NONINTERLEAVED; } else { accessMode = SND_PCM_ACCESS_MMAP_NONINTERLEAVED; alternateAccessMode = SND_PCM_ACCESS_MMAP_INTERLEAVED; } /* If requested access mode fails, try alternate mode */ if( snd_pcm_hw_params_set_access( pcm, hwParams, accessMode ) < 0 ) { int err = 0; if( (err = snd_pcm_hw_params_set_access( pcm, hwParams, alternateAccessMode )) < 0) { result = paUnanticipatedHostError; if( -EINVAL == err ) { PaUtil_SetLastHostErrorInfo( paALSA, err, "PA ALSA requires that a device supports mmap access" ); } else { PaUtil_SetLastHostErrorInfo( paALSA, err, snd_strerror( err ) ); } goto error; } /* Flip mode */ self->hostInterleaved = !self->userInterleaved; } ENSURE_( snd_pcm_hw_params_set_format( pcm, hwParams, self->nativeFormat ), paUnanticipatedHostError ); ENSURE_( SetApproximateSampleRate( pcm, hwParams, sr ), paInvalidSampleRate ); ENSURE_( GetExactSampleRate( hwParams, &sr ), paUnanticipatedHostError ); /* reject if there's no sample rate within 1% of the one requested */ if( (fabs( *sampleRate - sr ) / *sampleRate) > 0.01 ) { PA_DEBUG(("%s: Wanted %f, closest sample rate was %d\n", __FUNCTION__, sampleRate, sr )); PA_ENSURE( paInvalidSampleRate ); } ENSURE_( snd_pcm_hw_params_set_channels( pcm, hwParams, self->numHostChannels ), paInvalidChannelCount ); *sampleRate = sr; end: return result; error: /* No particular action */ goto end; } /** Finish the configuration of the component's ALSA device. * * As part of this method, the component's bufferSize attribute will be set. * @param latency: The latency for this component. */ static PaError PaAlsaStreamComponent_FinishConfigure( PaAlsaStreamComponent *self, snd_pcm_hw_params_t* hwParams, const PaStreamParameters *params, int primeBuffers, double sampleRate, PaTime* latency ) { PaError result = paNoError; snd_pcm_sw_params_t* swParams; snd_pcm_uframes_t bufSz = 0; *latency = -1.; snd_pcm_sw_params_alloca( &swParams ); bufSz = params->suggestedLatency * sampleRate; ENSURE_( snd_pcm_hw_params_set_buffer_size_near( self->pcm, hwParams, &bufSz ), paUnanticipatedHostError ); /* Set the parameters! */ { int r = snd_pcm_hw_params( self->pcm, hwParams ); #ifdef PA_ENABLE_DEBUG_OUTPUT if( r < 0 ) { snd_output_t *output = NULL; snd_output_stdio_attach( &output, stderr, 0 ); snd_pcm_hw_params_dump( hwParams, output ); } #endif ENSURE_(r, paUnanticipatedHostError ); } ENSURE_( snd_pcm_hw_params_get_buffer_size( hwParams, &self->bufferSize ), paUnanticipatedHostError ); /* Latency in seconds */ *latency = self->bufferSize / sampleRate; /* Now software parameters... */ ENSURE_( snd_pcm_sw_params_current( self->pcm, swParams ), paUnanticipatedHostError ); ENSURE_( snd_pcm_sw_params_set_start_threshold( self->pcm, swParams, self->framesPerBuffer ), paUnanticipatedHostError ); ENSURE_( snd_pcm_sw_params_set_stop_threshold( self->pcm, swParams, self->bufferSize ), paUnanticipatedHostError ); /* Silence buffer in the case of underrun */ if( !primeBuffers ) /* XXX: Make sense? */ { snd_pcm_uframes_t boundary; ENSURE_( snd_pcm_sw_params_get_boundary( swParams, &boundary ), paUnanticipatedHostError ); ENSURE_( snd_pcm_sw_params_set_silence_threshold( self->pcm, swParams, 0 ), paUnanticipatedHostError ); ENSURE_( snd_pcm_sw_params_set_silence_size( self->pcm, swParams, boundary ), paUnanticipatedHostError ); } ENSURE_( snd_pcm_sw_params_set_avail_min( self->pcm, swParams, self->framesPerBuffer ), paUnanticipatedHostError ); ENSURE_( snd_pcm_sw_params_set_xfer_align( self->pcm, swParams, 1 ), paUnanticipatedHostError ); ENSURE_( snd_pcm_sw_params_set_tstamp_mode( self->pcm, swParams, SND_PCM_TSTAMP_MMAP ), paUnanticipatedHostError ); /* Set the parameters! */ ENSURE_( snd_pcm_sw_params( self->pcm, swParams ), paUnanticipatedHostError ); error: return result; } static PaError PaAlsaStream_Initialize( PaAlsaStream *self, PaAlsaHostApiRepresentation *alsaApi, const PaStreamParameters *inParams, const PaStreamParameters *outParams, double sampleRate, unsigned long framesPerUserBuffer, PaStreamCallback callback, PaStreamFlags streamFlags, void *userData ) { PaError result = paNoError; assert( self ); memset( self, 0, sizeof (PaAlsaStream) ); if( NULL != callback ) { PaUtil_InitializeStreamRepresentation( &self->streamRepresentation, &alsaApi->callbackStreamInterface, callback, userData ); self->callbackMode = 1; } else { PaUtil_InitializeStreamRepresentation( &self->streamRepresentation, &alsaApi->blockingStreamInterface, NULL, userData ); } self->framesPerUserBuffer = framesPerUserBuffer; self->neverDropInput = streamFlags & paNeverDropInput; /* XXX: Ignore paPrimeOutputBuffersUsingStreamCallback untill buffer priming is fully supported in pa_process.c */ /* if( outParams & streamFlags & paPrimeOutputBuffersUsingStreamCallback ) self->primeBuffers = 1; */ memset( &self->capture, 0, sizeof (PaAlsaStreamComponent) ); memset( &self->playback, 0, sizeof (PaAlsaStreamComponent) ); if( inParams ) { PA_ENSURE( PaAlsaStreamComponent_Initialize( &self->capture, alsaApi, inParams, StreamDirection_In, NULL != callback ) ); } if( outParams ) { PA_ENSURE( PaAlsaStreamComponent_Initialize( &self->playback, alsaApi, outParams, StreamDirection_Out, NULL != callback ) ); } assert( self->capture.nfds || self->playback.nfds ); PA_UNLESS( self->pfds = (struct pollfd*)PaUtil_AllocateMemory( (self->capture.nfds + self->playback.nfds) * sizeof (struct pollfd) ), paInsufficientMemory ); PaUtil_InitializeCpuLoadMeasurer( &self->cpuLoadMeasurer, sampleRate ); ASSERT_CALL_( PaUnixMutex_Initialize( &self->stateMtx ), paNoError ); error: return result; } /** Free resources associated with stream, and eventually stream itself. * * Frees allocated memory, and terminates individual StreamComponents. */ static void PaAlsaStream_Terminate( PaAlsaStream *self ) { assert( self ); if( self->capture.pcm ) { PaAlsaStreamComponent_Terminate( &self->capture ); } if( self->playback.pcm ) { PaAlsaStreamComponent_Terminate( &self->playback ); } PaUtil_FreeMemory( self->pfds ); ASSERT_CALL_( PaUnixMutex_Terminate( &self->stateMtx ), paNoError ); PaUtil_FreeMemory( self ); } /** Calculate polling timeout * * @param frames Time to wait * @return Polling timeout in milliseconds */ static int CalculatePollTimeout( const PaAlsaStream *stream, unsigned long frames ) { assert( stream->streamRepresentation.streamInfo.sampleRate > 0.0 ); /* Period in msecs, rounded up */ return (int)ceil( 1000 * frames / stream->streamRepresentation.streamInfo.sampleRate ); } /** Determine size per host buffer. * * During this method call, the component's framesPerBuffer attribute gets computed, and the corresponding period size * gets configured for the device. * @param accurate: If the configured period size is non-integer, this will be set to 0. */ static PaError PaAlsaStreamComponent_DetermineFramesPerBuffer( PaAlsaStreamComponent* self, const PaStreamParameters* params, unsigned long framesPerUserBuffer, double sampleRate, snd_pcm_hw_params_t* hwParams, int* accurate ) { PaError result = paNoError; unsigned long bufferSize = params->suggestedLatency * sampleRate, framesPerHostBuffer; int dir = 0; { snd_pcm_uframes_t tmp; snd_pcm_hw_params_get_buffer_size_min( hwParams, &tmp ); bufferSize = PA_MAX( bufferSize, tmp ); snd_pcm_hw_params_get_buffer_size_max( hwParams, &tmp ); bufferSize = PA_MIN( bufferSize, tmp ); } assert( bufferSize > 0 ); if( framesPerUserBuffer != paFramesPerBufferUnspecified ) { /* Preferably the host buffer size should be a multiple of the user buffer size */ if( bufferSize > framesPerUserBuffer ) { snd_pcm_uframes_t remainder = bufferSize % framesPerUserBuffer; if( remainder > framesPerUserBuffer / 2. ) bufferSize += framesPerUserBuffer - remainder; else bufferSize -= remainder; assert( bufferSize % framesPerUserBuffer == 0 ); } else if( framesPerUserBuffer % bufferSize != 0 ) { /* Find a good compromise between user specified latency and buffer size */ if( bufferSize > framesPerUserBuffer * .75 ) { bufferSize = framesPerUserBuffer; } else { snd_pcm_uframes_t newSz = framesPerUserBuffer; while( newSz / 2 >= bufferSize ) { if( framesPerUserBuffer % (newSz / 2) != 0 ) { /* No use dividing any further */ break; } newSz /= 2; } bufferSize = newSz; } assert( framesPerUserBuffer % bufferSize == 0 ); } } /* Using the base number of periods, we try to approximate the suggested latency (+1 period), finding a combination of period/buffer size which best fits these constraints */ { unsigned numPeriods = numPeriods_, maxPeriods = 0; /* It may be that the device only supports 2 periods for instance */ dir = 0; ENSURE_( snd_pcm_hw_params_get_periods_max( hwParams, &maxPeriods, &dir ), paUnanticipatedHostError ); assert( maxPeriods > 1 ); numPeriods = PA_MIN( maxPeriods, numPeriods ); if( framesPerUserBuffer != paFramesPerBufferUnspecified ) { /* Try to get a power-of-two of the user buffer size. */ framesPerHostBuffer = framesPerUserBuffer; if( framesPerHostBuffer < bufferSize ) { while( bufferSize / framesPerHostBuffer > numPeriods ) { framesPerHostBuffer *= 2; } /* One extra period is preferrable to one less (should be more robust) */ if( bufferSize / framesPerHostBuffer < numPeriods ) { framesPerHostBuffer /= 2; } } else { while( bufferSize / framesPerHostBuffer < numPeriods ) { if( framesPerUserBuffer % (framesPerHostBuffer / 2) != 0 ) { /* Can't be divided any further */ break; } framesPerHostBuffer /= 2; } } if( framesPerHostBuffer < framesPerUserBuffer ) { assert( framesPerUserBuffer % framesPerHostBuffer == 0 ); if( snd_pcm_hw_params_test_period_size( self->pcm, hwParams, framesPerHostBuffer, 0 ) < 0 ) { if( snd_pcm_hw_params_test_period_size( self->pcm, hwParams, framesPerHostBuffer * 2, 0 ) == 0 ) framesPerHostBuffer *= 2; else if( snd_pcm_hw_params_test_period_size( self->pcm, hwParams, framesPerHostBuffer / 2, 0 ) == 0 ) framesPerHostBuffer /= 2; } } else { assert( framesPerHostBuffer % framesPerUserBuffer == 0 ); if( snd_pcm_hw_params_test_period_size( self->pcm, hwParams, framesPerHostBuffer, 0 ) < 0 ) { if( snd_pcm_hw_params_test_period_size( self->pcm, hwParams, framesPerHostBuffer + framesPerUserBuffer, 0 ) == 0 ) framesPerHostBuffer += framesPerUserBuffer; else if( snd_pcm_hw_params_test_period_size( self->pcm, hwParams, framesPerHostBuffer - framesPerUserBuffer, 0 ) == 0 ) framesPerHostBuffer -= framesPerUserBuffer; } } } else { framesPerHostBuffer = bufferSize / numPeriods; } } assert( framesPerHostBuffer > 0 ); { snd_pcm_uframes_t min = 0, max = 0; ENSURE_( snd_pcm_hw_params_get_period_size_min( hwParams, &min, NULL ), paUnanticipatedHostError ); ENSURE_( snd_pcm_hw_params_get_period_size_max( hwParams, &max, NULL ), paUnanticipatedHostError ); if( framesPerHostBuffer < min ) { PA_DEBUG(( "%s: The determined period size (%lu) is less than minimum (%lu)\n", __FUNCTION__, framesPerHostBuffer, min )); framesPerHostBuffer = min; } else if( framesPerHostBuffer > max ) { PA_DEBUG(( "%s: The determined period size (%lu) is greater than maximum (%lu)\n", __FUNCTION__, framesPerHostBuffer, max )); framesPerHostBuffer = max; } assert( framesPerHostBuffer >= min && framesPerHostBuffer <= max ); dir = 0; ENSURE_( snd_pcm_hw_params_set_period_size_near( self->pcm, hwParams, &framesPerHostBuffer, &dir ), paUnanticipatedHostError ); if( dir != 0 ) { PA_DEBUG(( "%s: The configured period size is non-integer.\n", __FUNCTION__, dir )); *accurate = 0; } } self->framesPerBuffer = framesPerHostBuffer; error: return result; } /* We need to determine how many frames per host buffer (period) to use. Our * goals are to provide the best possible performance, but also to * honor the requested latency settings as closely as we can. Therefore this * decision is based on: * * - the period sizes that playback and/or capture support. The * host buffer size has to be one of these. * - the number of periods that playback and/or capture support. * * We want to make period_size*(num_periods-1) to be as close as possible * to latency*rate for both playback and capture. * * This method will determine suitable period sizes for capture and playback handles, and report the maximum number of * frames per host buffer. The latter is relevant, in case we should be so unfortunate that the period size differs * between capture and playback. If this should happen, the stream's hostBufferSizeMode attribute will be set to * paUtilBoundedHostBufferSize, because the best we can do is limit the size of individual host buffers to the upper * bound. The size of host buffers scheduled for processing should only matter if the user has specified a buffer size, * but when he/she does we must strive for an optimal configuration. By default we'll opt for a fixed host buffer size, * which should be fine if the period size is the same for capture and playback. In general, if there is a specified user * buffer size, this method tries it best to determine a period size which is a multiple of the user buffer size. * * The framesPerBuffer attributes of the individual capture and playback components of the stream are set to corresponding * values determined here. Since these should be reported as * * This is one of those blocks of code that will just take a lot of * refinement to be any good. * * In the full-duplex case it is possible that the routine was unable * to find a number of frames per buffer acceptable to both devices * TODO: Implement an algorithm to find the value closest to acceptance * by both devices, to minimize difference between period sizes? * * @param determinedFramesPerHostBuffer: The determined host buffer size. */ static PaError PaAlsaStream_DetermineFramesPerBuffer( PaAlsaStream* self, double sampleRate, const PaStreamParameters* inputParameters, const PaStreamParameters* outputParameters, unsigned long framesPerUserBuffer, snd_pcm_hw_params_t* hwParamsCapture, snd_pcm_hw_params_t* hwParamsPlayback, PaUtilHostBufferSizeMode* hostBufferSizeMode ) { PaError result = paNoError; unsigned long framesPerHostBuffer = 0; int dir = 0; int accurate = 1; unsigned numPeriods = numPeriods_; if( self->capture.pcm && self->playback.pcm ) { if( framesPerUserBuffer == paFramesPerBufferUnspecified ) { /* Come up with a common desired latency */ snd_pcm_uframes_t desiredBufSz, e, minPeriodSize, maxPeriodSize, optimalPeriodSize, periodSize, minCapture, minPlayback, maxCapture, maxPlayback; dir = 0; ENSURE_( snd_pcm_hw_params_get_period_size_min( hwParamsCapture, &minCapture, &dir ), paUnanticipatedHostError ); dir = 0; ENSURE_( snd_pcm_hw_params_get_period_size_min( hwParamsPlayback, &minPlayback, &dir ), paUnanticipatedHostError ); dir = 0; ENSURE_( snd_pcm_hw_params_get_period_size_max( hwParamsCapture, &maxCapture, &dir ), paUnanticipatedHostError ); dir = 0; ENSURE_( snd_pcm_hw_params_get_period_size_max( hwParamsPlayback, &maxPlayback, &dir ), paUnanticipatedHostError ); minPeriodSize = PA_MAX( minPlayback, minCapture ); maxPeriodSize = PA_MIN( maxPlayback, maxCapture ); PA_UNLESS( minPeriodSize <= maxPeriodSize, paBadIODeviceCombination ); desiredBufSz = (snd_pcm_uframes_t)(PA_MIN( outputParameters->suggestedLatency, inputParameters->suggestedLatency ) * sampleRate); /* Clamp desiredBufSz */ { snd_pcm_uframes_t maxBufferSize; snd_pcm_uframes_t maxBufferSizeCapture, maxBufferSizePlayback; ENSURE_( snd_pcm_hw_params_get_buffer_size_max( hwParamsCapture, &maxBufferSizeCapture ), paUnanticipatedHostError ); ENSURE_( snd_pcm_hw_params_get_buffer_size_max( hwParamsPlayback, &maxBufferSizePlayback ), paUnanticipatedHostError ); maxBufferSize = PA_MIN( maxBufferSizeCapture, maxBufferSizePlayback ); desiredBufSz = PA_MIN( desiredBufSz, maxBufferSize ); } /* Find the closest power of 2 */ e = ilogb( minPeriodSize ); if( minPeriodSize & (minPeriodSize - 1) ) e += 1; periodSize = (snd_pcm_uframes_t)pow( 2, e ); while( periodSize <= maxPeriodSize ) { if( snd_pcm_hw_params_test_period_size( self->playback.pcm, hwParamsPlayback, periodSize, 0 ) >= 0 && snd_pcm_hw_params_test_period_size( self->capture.pcm, hwParamsCapture, periodSize, 0 ) >= 0 ) { /* OK! */ break; } periodSize *= 2; } optimalPeriodSize = PA_MAX( desiredBufSz / numPeriods, minPeriodSize ); optimalPeriodSize = PA_MIN( optimalPeriodSize, maxPeriodSize ); /* Find the closest power of 2 */ e = ilogb( optimalPeriodSize ); if( optimalPeriodSize & (optimalPeriodSize - 1) ) e += 1; optimalPeriodSize = (snd_pcm_uframes_t)pow( 2, e ); while( optimalPeriodSize >= periodSize ) { if( snd_pcm_hw_params_test_period_size( self->capture.pcm, hwParamsCapture, optimalPeriodSize, 0 ) >= 0 && snd_pcm_hw_params_test_period_size( self->playback.pcm, hwParamsPlayback, optimalPeriodSize, 0 ) >= 0 ) { break; } optimalPeriodSize /= 2; } if( optimalPeriodSize > periodSize ) periodSize = optimalPeriodSize; if( periodSize <= maxPeriodSize ) { /* Looks good, the periodSize _should_ be acceptable by both devices */ ENSURE_( snd_pcm_hw_params_set_period_size( self->capture.pcm, hwParamsCapture, periodSize, 0 ), paUnanticipatedHostError ); ENSURE_( snd_pcm_hw_params_set_period_size( self->playback.pcm, hwParamsPlayback, periodSize, 0 ), paUnanticipatedHostError ); self->capture.framesPerBuffer = self->playback.framesPerBuffer = periodSize; framesPerHostBuffer = periodSize; } else { /* Unable to find a common period size, oh well */ optimalPeriodSize = PA_MAX( desiredBufSz / numPeriods, minPeriodSize ); optimalPeriodSize = PA_MIN( optimalPeriodSize, maxPeriodSize ); self->capture.framesPerBuffer = optimalPeriodSize; dir = 0; ENSURE_( snd_pcm_hw_params_set_period_size_near( self->capture.pcm, hwParamsCapture, &self->capture.framesPerBuffer, &dir ), paUnanticipatedHostError ); self->playback.framesPerBuffer = optimalPeriodSize; dir = 0; ENSURE_( snd_pcm_hw_params_set_period_size_near( self->playback.pcm, hwParamsPlayback, &self->playback.framesPerBuffer, &dir ), paUnanticipatedHostError ); framesPerHostBuffer = PA_MAX( self->capture.framesPerBuffer, self->playback.framesPerBuffer ); *hostBufferSizeMode = paUtilBoundedHostBufferSize; } } else { /* We choose the simple route and determine a suitable number of frames per buffer for one component of * the stream, then we hope that this will work for the other component too (it should!). */ unsigned maxPeriods = 0; PaAlsaStreamComponent* first = &self->capture, * second = &self->playback; const PaStreamParameters* firstStreamParams = inputParameters; snd_pcm_hw_params_t* firstHwParams = hwParamsCapture, * secondHwParams = hwParamsPlayback; dir = 0; ENSURE_( snd_pcm_hw_params_get_periods_max( hwParamsPlayback, &maxPeriods, &dir ), paUnanticipatedHostError ); if( maxPeriods < numPeriods ) { /* The playback component is trickier to get right, try that first */ first = &self->playback; second = &self->capture; firstStreamParams = outputParameters; firstHwParams = hwParamsPlayback; secondHwParams = hwParamsCapture; } PA_ENSURE( PaAlsaStreamComponent_DetermineFramesPerBuffer( first, firstStreamParams, framesPerUserBuffer, sampleRate, firstHwParams, &accurate ) ); second->framesPerBuffer = first->framesPerBuffer; dir = 0; ENSURE_( snd_pcm_hw_params_set_period_size_near( second->pcm, secondHwParams, &second->framesPerBuffer, &dir ), paUnanticipatedHostError ); if( self->capture.framesPerBuffer == self->playback.framesPerBuffer ) { framesPerHostBuffer = self->capture.framesPerBuffer; } else { framesPerHostBuffer = PA_MAX( self->capture.framesPerBuffer, self->playback.framesPerBuffer ); *hostBufferSizeMode = paUtilBoundedHostBufferSize; } } } else /* half-duplex is a slightly simpler case */ { if( self->capture.pcm ) { PA_ENSURE( PaAlsaStreamComponent_DetermineFramesPerBuffer( &self->capture, inputParameters, framesPerUserBuffer, sampleRate, hwParamsCapture, &accurate) ); framesPerHostBuffer = self->capture.framesPerBuffer; } else { assert( self->playback.pcm ); PA_ENSURE( PaAlsaStreamComponent_DetermineFramesPerBuffer( &self->playback, outputParameters, framesPerUserBuffer, sampleRate, hwParamsPlayback, &accurate ) ); framesPerHostBuffer = self->playback.framesPerBuffer; } } PA_UNLESS( framesPerHostBuffer != 0, paInternalError ); self->maxFramesPerHostBuffer = framesPerHostBuffer; if( !accurate ) { /* Don't know the exact size per host buffer */ *hostBufferSizeMode = paUtilBoundedHostBufferSize; /* Raise upper bound */ ++self->maxFramesPerHostBuffer; } error: return result; } /** Set up ALSA stream parameters. * */ static PaError PaAlsaStream_Configure( PaAlsaStream *self, const PaStreamParameters *inParams, const PaStreamParameters* outParams, double sampleRate, unsigned long framesPerUserBuffer, double* inputLatency, double* outputLatency, PaUtilHostBufferSizeMode* hostBufferSizeMode ) { PaError result = paNoError; double realSr = sampleRate; snd_pcm_hw_params_t* hwParamsCapture, * hwParamsPlayback; snd_pcm_hw_params_alloca( &hwParamsCapture ); snd_pcm_hw_params_alloca( &hwParamsPlayback ); if( self->capture.pcm ) PA_ENSURE( PaAlsaStreamComponent_InitialConfigure( &self->capture, inParams, self->primeBuffers, hwParamsCapture, &realSr ) ); if( self->playback.pcm ) PA_ENSURE( PaAlsaStreamComponent_InitialConfigure( &self->playback, outParams, self->primeBuffers, hwParamsPlayback, &realSr ) ); PA_ENSURE( PaAlsaStream_DetermineFramesPerBuffer( self, realSr, inParams, outParams, framesPerUserBuffer, hwParamsCapture, hwParamsPlayback, hostBufferSizeMode ) ); if( self->capture.pcm ) { assert( self->capture.framesPerBuffer != 0 ); PA_ENSURE( PaAlsaStreamComponent_FinishConfigure( &self->capture, hwParamsCapture, inParams, self->primeBuffers, realSr, inputLatency ) ); PA_DEBUG(( "%s: Capture period size: %lu, latency: %f\n", __FUNCTION__, self->capture.framesPerBuffer, *inputLatency )); } if( self->playback.pcm ) { assert( self->playback.framesPerBuffer != 0 ); PA_ENSURE( PaAlsaStreamComponent_FinishConfigure( &self->playback, hwParamsPlayback, outParams, self->primeBuffers, realSr, outputLatency ) ); PA_DEBUG(( "%s: Playback period size: %lu, latency: %f\n", __FUNCTION__, self->playback.framesPerBuffer, *outputLatency )); } /* Should be exact now */ self->streamRepresentation.streamInfo.sampleRate = realSr; /* this will cause the two streams to automatically start/stop/prepare in sync. * We only need to execute these operations on one of the pair. * A: We don't want to do this on a blocking stream. */ if( self->callbackMode && self->capture.pcm && self->playback.pcm ) { int err = snd_pcm_link( self->capture.pcm, self->playback.pcm ); if( err == 0 ) self->pcmsSynced = 1; else PA_DEBUG(( "%s: Unable to sync pcms: %s\n", __FUNCTION__, snd_strerror( err ) )); } { unsigned long minFramesPerHostBuffer = PA_MIN( self->capture.pcm ? self->capture.framesPerBuffer : ULONG_MAX, self->playback.pcm ? self->playback.framesPerBuffer : ULONG_MAX ); self->pollTimeout = CalculatePollTimeout( self, minFramesPerHostBuffer ); /* Period in msecs, rounded up */ /* Time before watchdog unthrottles realtime thread == 1/4 of period time in msecs */ /* self->threading.throttledSleepTime = (unsigned long) (minFramesPerHostBuffer / sampleRate / 4 * 1000); */ } if( self->callbackMode ) { /* If the user expects a certain number of frames per callback we will either have to rely on block adaption * (framesPerHostBuffer is not an integer multiple of framesPerBuffer) or we can simply align the number * of host buffer frames with what the user specified */ if( self->framesPerUserBuffer != paFramesPerBufferUnspecified ) { /* self->alignFrames = 1; */ /* Unless the ratio between number of host and user buffer frames is an integer we will have to rely * on block adaption */ /* if( framesPerHostBuffer % framesPerBuffer != 0 || (self->capture.pcm && self->playback.pcm && self->capture.framesPerBuffer != self->playback.framesPerBuffer) ) self->useBlockAdaption = 1; else self->alignFrames = 1; */ } } error: return result; } static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback* callback, void *userData ) { PaError result = paNoError; PaAlsaHostApiRepresentation *alsaHostApi = (PaAlsaHostApiRepresentation*)hostApi; PaAlsaStream *stream = NULL; PaSampleFormat hostInputSampleFormat = 0, hostOutputSampleFormat = 0; PaSampleFormat inputSampleFormat = 0, outputSampleFormat = 0; int numInputChannels = 0, numOutputChannels = 0; PaTime inputLatency, outputLatency; /* Operate with fixed host buffer size by default, since other modes will invariably lead to block adaption */ /* XXX: Use Bounded by default? Output tends to get stuttery with Fixed ... */ PaUtilHostBufferSizeMode hostBufferSizeMode = paUtilFixedHostBufferSize; if( (streamFlags & paPlatformSpecificFlags) != 0 ) return paInvalidFlag; if( inputParameters ) { PA_ENSURE( ValidateParameters( inputParameters, hostApi, StreamDirection_In ) ); numInputChannels = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; } if( outputParameters ) { PA_ENSURE( ValidateParameters( outputParameters, hostApi, StreamDirection_Out ) ); numOutputChannels = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; } /* XXX: Why do we support this anyway? */ if( framesPerBuffer == paFramesPerBufferUnspecified && getenv( "PA_ALSA_PERIODSIZE" ) != NULL ) { PA_DEBUG(( "%s: Getting framesPerBuffer from environment\n", __FUNCTION__ )); framesPerBuffer = atoi( getenv("PA_ALSA_PERIODSIZE") ); } PA_UNLESS( stream = (PaAlsaStream*)PaUtil_AllocateMemory( sizeof(PaAlsaStream) ), paInsufficientMemory ); PA_ENSURE( PaAlsaStream_Initialize( stream, alsaHostApi, inputParameters, outputParameters, sampleRate, framesPerBuffer, callback, streamFlags, userData ) ); PA_ENSURE( PaAlsaStream_Configure( stream, inputParameters, outputParameters, sampleRate, framesPerBuffer, &inputLatency, &outputLatency, &hostBufferSizeMode ) ); hostInputSampleFormat = stream->capture.hostSampleFormat; hostOutputSampleFormat = stream->playback.hostSampleFormat; PA_ENSURE( PaUtil_InitializeBufferProcessor( &stream->bufferProcessor, numInputChannels, inputSampleFormat, hostInputSampleFormat, numOutputChannels, outputSampleFormat, hostOutputSampleFormat, sampleRate, streamFlags, framesPerBuffer, stream->maxFramesPerHostBuffer, hostBufferSizeMode, callback, userData ) ); /* Ok, buffer processor is initialized, now we can deduce it's latency */ if( numInputChannels > 0 ) stream->streamRepresentation.streamInfo.inputLatency = inputLatency + PaUtil_GetBufferProcessorInputLatency( &stream->bufferProcessor ); if( numOutputChannels > 0 ) stream->streamRepresentation.streamInfo.outputLatency = outputLatency + PaUtil_GetBufferProcessorOutputLatency( &stream->bufferProcessor ); *s = (PaStream*)stream; return result; error: if( stream ) { PA_DEBUG(( "%s: Stream in error, terminating\n", __FUNCTION__ )); PaAlsaStream_Terminate( stream ); } return result; } static PaError CloseStream( PaStream* s ) { PaError result = paNoError; PaAlsaStream *stream = (PaAlsaStream*)s; PaUtil_TerminateBufferProcessor( &stream->bufferProcessor ); PaUtil_TerminateStreamRepresentation( &stream->streamRepresentation ); PaAlsaStream_Terminate( stream ); return result; } static void SilenceBuffer( PaAlsaStream *stream ) { const snd_pcm_channel_area_t *areas; snd_pcm_uframes_t frames = (snd_pcm_uframes_t)snd_pcm_avail_update( stream->playback.pcm ), offset; snd_pcm_mmap_begin( stream->playback.pcm, &areas, &offset, &frames ); snd_pcm_areas_silence( areas, offset, stream->playback.numHostChannels, frames, stream->playback.nativeFormat ); snd_pcm_mmap_commit( stream->playback.pcm, offset, frames ); } /** Start/prepare pcm(s) for streaming. * * Depending on wether the stream is in callback or blocking mode, we will respectively start or simply * prepare the playback pcm. If the buffer has _not_ been primed, we will in callback mode prepare and * silence the buffer before starting playback. In blocking mode we simply prepare, as the playback will * be started automatically as the user writes to output. * * The capture pcm, however, will simply be prepared and started. */ static PaError AlsaStart( PaAlsaStream *stream, int priming ) { PaError result = paNoError; if( stream->playback.pcm ) { if( stream->callbackMode ) { if( !priming ) { /* Buffer isn't primed, so prepare and silence */ ENSURE_( snd_pcm_prepare( stream->playback.pcm ), paUnanticipatedHostError ); SilenceBuffer( stream ); } ENSURE_( snd_pcm_start( stream->playback.pcm ), paUnanticipatedHostError ); } else ENSURE_( snd_pcm_prepare( stream->playback.pcm ), paUnanticipatedHostError ); } if( stream->capture.pcm && !stream->pcmsSynced ) { ENSURE_( snd_pcm_prepare( stream->capture.pcm ), paUnanticipatedHostError ); /* For a blocking stream we want to start capture as well, since nothing will happen otherwise */ ENSURE_( snd_pcm_start( stream->capture.pcm ), paUnanticipatedHostError ); } end: return result; error: goto end; } /** Utility function for determining if pcms are in running state. * */ #if 0 static int IsRunning( PaAlsaStream *stream ) { int result = 0; PA_ENSURE( PaUnixMutex_Lock( &stream->stateMtx ) ); if( stream->capture.pcm ) { snd_pcm_state_t capture_state = snd_pcm_state( stream->capture.pcm ); if( capture_state == SND_PCM_STATE_RUNNING || capture_state == SND_PCM_STATE_XRUN || capture_state == SND_PCM_STATE_DRAINING ) { result = 1; goto end; } } if( stream->playback.pcm ) { snd_pcm_state_t playback_state = snd_pcm_state( stream->playback.pcm ); if( playback_state == SND_PCM_STATE_RUNNING || playback_state == SND_PCM_STATE_XRUN || playback_state == SND_PCM_STATE_DRAINING ) { result = 1; goto end; } } end: ASSERT_CALL_( PaUnixMutex_Unlock( &stream->stateMtx ), paNoError ); return result; error: goto error; } #endif static PaError StartStream( PaStream *s ) { PaError result = paNoError; PaAlsaStream* stream = (PaAlsaStream*)s; int streamStarted = 0; /* So we can know wether we need to take the stream down */ /* Ready the processor */ PaUtil_ResetBufferProcessor( &stream->bufferProcessor ); /* Set now, so we can test for activity further down */ stream->isActive = 1; if( stream->callbackMode ) { PA_ENSURE( PaUnixThread_New( &stream->thread, &CallbackThreadFunc, stream, 1., stream->rtSched ) ); } else { PA_ENSURE( AlsaStart( stream, 0 ) ); streamStarted = 1; } end: return result; error: if( streamStarted ) { AbortStream( stream ); } stream->isActive = 0; goto end; } /** Stop PCM handle, either softly or abruptly. */ static PaError AlsaStop( PaAlsaStream *stream, int abort ) { PaError result = paNoError; /* XXX: snd_pcm_drain tends to lock up, avoid it until we find out more */ abort = 1; /* if( stream->capture.pcm && !strcmp( Pa_GetDeviceInfo( stream->capture.device )->name, "dmix" ) ) { abort = 1; } else if( stream->playback.pcm && !strcmp( Pa_GetDeviceInfo( stream->playback.device )->name, "dmix" ) ) { abort = 1; } */ if( abort ) { if( stream->playback.pcm ) { ENSURE_( snd_pcm_drop( stream->playback.pcm ), paUnanticipatedHostError ); } if( stream->capture.pcm && !stream->pcmsSynced ) { ENSURE_( snd_pcm_drop( stream->capture.pcm ), paUnanticipatedHostError ); } PA_DEBUG(( "%s: Dropped frames\n", __FUNCTION__ )); } else { if( stream->playback.pcm ) { ENSURE_( snd_pcm_nonblock( stream->playback.pcm, 0 ), paUnanticipatedHostError ); if( snd_pcm_drain( stream->playback.pcm ) < 0 ) { PA_DEBUG(( "%s: Draining playback handle failed!\n", __FUNCTION__ )); } } if( stream->capture.pcm && !stream->pcmsSynced ) { /* We don't need to retrieve any remaining frames */ if( snd_pcm_drain( stream->capture.pcm ) < 0 ) { PA_DEBUG(( "%s: Draining capture handle failed!\n", __FUNCTION__ )); } } } end: return result; error: goto end; } /** Stop or abort stream. * * If a stream is in callback mode we will have to inspect wether the background thread has * finished, or we will have to take it out. In either case we join the thread before * returning. In blocking mode, we simply tell ALSA to stop abruptly (abort) or finish * buffers (drain) * * Stream will be considered inactive (!PaAlsaStream::isActive) after a call to this function */ static PaError RealStop( PaAlsaStream *stream, int abort ) { PaError result = paNoError; /* First deal with the callback thread, cancelling and/or joining * it if necessary */ if( stream->callbackMode ) { PaError threadRes; stream->callbackAbort = abort; if( !abort ) { PA_DEBUG(( "Stopping callback\n" )); } PA_ENSURE( PaUnixThread_Terminate( &stream->thread, !abort, &threadRes ) ); if( threadRes != paNoError ) { PA_DEBUG(( "Callback thread returned: %d\n", threadRes )); } #if 0 if( watchdogRes != paNoError ) PA_DEBUG(( "Watchdog thread returned: %d\n", watchdogRes )); #endif stream->callback_finished = 0; } else { PA_ENSURE( AlsaStop( stream, abort ) ); } stream->isActive = 0; end: return result; error: goto end; } static PaError StopStream( PaStream *s ) { return RealStop( (PaAlsaStream *) s, 0 ); } static PaError AbortStream( PaStream *s ) { return RealStop( (PaAlsaStream * ) s, 1 ); } /** The stream is considered stopped before StartStream, or AFTER a call to Abort/StopStream (callback * returning !paContinue is not considered) * */ static PaError IsStreamStopped( PaStream *s ) { PaAlsaStream *stream = (PaAlsaStream *)s; /* callback_finished indicates we need to join callback thread (ie. in Abort/StopStream) */ return !IsStreamActive( s ) && !stream->callback_finished; } static PaError IsStreamActive( PaStream *s ) { PaAlsaStream *stream = (PaAlsaStream*)s; return stream->isActive; } static PaTime GetStreamTime( PaStream *s ) { PaAlsaStream *stream = (PaAlsaStream*)s; snd_timestamp_t timestamp; snd_pcm_status_t* status; snd_pcm_status_alloca( &status ); /* TODO: what if we have both? does it really matter? */ /* TODO: if running in callback mode, this will mean * libasound routines are being called from multiple threads. * need to verify that libasound is thread-safe. */ if( stream->capture.pcm ) { snd_pcm_status( stream->capture.pcm, status ); } else if( stream->playback.pcm ) { snd_pcm_status( stream->playback.pcm, status ); } snd_pcm_status_get_tstamp( status, ×tamp ); return timestamp.tv_sec + (PaTime)timestamp.tv_usec / 1e6; } static double GetStreamCpuLoad( PaStream* s ) { PaAlsaStream *stream = (PaAlsaStream*)s; return PaUtil_GetCpuLoad( &stream->cpuLoadMeasurer ); } static int SetApproximateSampleRate( snd_pcm_t *pcm, snd_pcm_hw_params_t *hwParams, double sampleRate ) { unsigned long approx = (unsigned long) sampleRate; int dir = 0; double fraction = sampleRate - approx; assert( pcm && hwParams ); if( fraction > 0.0 ) { if( fraction > 0.5 ) { ++approx; dir = -1; } else dir = 1; } return snd_pcm_hw_params_set_rate( pcm, hwParams, approx, dir ); } /* Return exact sample rate in param sampleRate */ static int GetExactSampleRate( snd_pcm_hw_params_t *hwParams, double *sampleRate ) { unsigned int num, den; int err; assert( hwParams ); err = snd_pcm_hw_params_get_rate_numden( hwParams, &num, &den ); *sampleRate = (double) num / den; return err; } /* Utility functions for blocking/callback interfaces */ /* Atomic restart of stream (we don't want the intermediate state visible) */ static PaError AlsaRestart( PaAlsaStream *stream ) { PaError result = paNoError; PA_ENSURE( PaUnixMutex_Lock( &stream->stateMtx ) ); PA_ENSURE( AlsaStop( stream, 0 ) ); PA_ENSURE( AlsaStart( stream, 0 ) ); PA_DEBUG(( "%s: Restarted audio\n", __FUNCTION__ )); error: PA_ENSURE( PaUnixMutex_Unlock( &stream->stateMtx ) ); return result; } /** Recover from xrun state. * */ static PaError PaAlsaStream_HandleXrun( PaAlsaStream *self ) { PaError result = paNoError; snd_pcm_status_t *st; PaTime now = PaUtil_GetTime(); snd_timestamp_t t; snd_pcm_status_alloca( &st ); if( self->playback.pcm ) { snd_pcm_status( self->playback.pcm, st ); if( snd_pcm_status_get_state( st ) == SND_PCM_STATE_XRUN ) { snd_pcm_status_get_trigger_tstamp( st, &t ); self->underrun = now * 1000 - ((PaTime) t.tv_sec * 1000 + (PaTime) t.tv_usec / 1000); } } if( self->capture.pcm ) { snd_pcm_status( self->capture.pcm, st ); if( snd_pcm_status_get_state( st ) == SND_PCM_STATE_XRUN ) { snd_pcm_status_get_trigger_tstamp( st, &t ); self->overrun = now * 1000 - ((PaTime) t.tv_sec * 1000 + (PaTime) t.tv_usec / 1000); } } PA_ENSURE( AlsaRestart( self ) ); end: return result; error: goto end; } /** Decide if we should continue polling for specified direction, eventually adjust the poll timeout. * */ static PaError ContinuePoll( const PaAlsaStream *stream, StreamDirection streamDir, int *pollTimeout, int *continuePoll ) { PaError result = paNoError; snd_pcm_sframes_t delay, margin; int err; const PaAlsaStreamComponent *component = NULL, *otherComponent = NULL; *continuePoll = 1; if( StreamDirection_In == streamDir ) { component = &stream->capture; otherComponent = &stream->playback; } else { component = &stream->playback; otherComponent = &stream->capture; } /* ALSA docs say that negative delay should indicate xrun, but in my experience snd_pcm_delay returns -EPIPE */ if( (err = snd_pcm_delay( otherComponent->pcm, &delay )) < 0 ) { if( err == -EPIPE ) { /* Xrun */ *continuePoll = 0; goto error; } ENSURE_( err, paUnanticipatedHostError ); } if( StreamDirection_Out == streamDir ) { /* Number of eligible frames before capture overrun */ delay = otherComponent->bufferSize - delay; } margin = delay - otherComponent->framesPerBuffer / 2; if( margin < 0 ) { PA_DEBUG(( "%s: Stopping poll for %s\n", __FUNCTION__, StreamDirection_In == streamDir ? "capture" : "playback" )); *continuePoll = 0; } else if( margin < otherComponent->framesPerBuffer ) { *pollTimeout = CalculatePollTimeout( stream, margin ); PA_DEBUG(( "%s: Trying to poll again for %s frames, pollTimeout: %d\n", __FUNCTION__, StreamDirection_In == streamDir ? "capture" : "playback", *pollTimeout )); } error: return result; } /* Callback interface */ static void OnExit( void *data ) { PaAlsaStream *stream = (PaAlsaStream *) data; assert( data ); PaUtil_ResetCpuLoadMeasurer( &stream->cpuLoadMeasurer ); stream->callback_finished = 1; /* Let the outside world know stream was stopped in callback */ PA_DEBUG(( "%s: Stopping ALSA handles\n", __FUNCTION__ )); AlsaStop( stream, stream->callbackAbort ); PA_DEBUG(( "%s: Stoppage\n", __FUNCTION__ )); /* Eventually notify user all buffers have played */ if( stream->streamRepresentation.streamFinishedCallback ) { stream->streamRepresentation.streamFinishedCallback( stream->streamRepresentation.userData ); } stream->isActive = 0; } static void CalculateTimeInfo( PaAlsaStream *stream, PaStreamCallbackTimeInfo *timeInfo ) { snd_pcm_status_t *capture_status, *playback_status; snd_timestamp_t capture_timestamp, playback_timestamp; PaTime capture_time = 0., playback_time = 0.; snd_pcm_status_alloca( &capture_status ); snd_pcm_status_alloca( &playback_status ); if( stream->capture.pcm ) { snd_pcm_sframes_t capture_delay; snd_pcm_status( stream->capture.pcm, capture_status ); snd_pcm_status_get_tstamp( capture_status, &capture_timestamp ); capture_time = capture_timestamp.tv_sec + ((PaTime)capture_timestamp.tv_usec / 1000000.0); timeInfo->currentTime = capture_time; capture_delay = snd_pcm_status_get_delay( capture_status ); timeInfo->inputBufferAdcTime = timeInfo->currentTime - (PaTime)capture_delay / stream->streamRepresentation.streamInfo.sampleRate; } if( stream->playback.pcm ) { snd_pcm_sframes_t playback_delay; snd_pcm_status( stream->playback.pcm, playback_status ); snd_pcm_status_get_tstamp( playback_status, &playback_timestamp ); playback_time = playback_timestamp.tv_sec + ((PaTime)playback_timestamp.tv_usec / 1000000.0); if( stream->capture.pcm ) /* Full duplex */ { /* Hmm, we have both a playback and a capture timestamp. * Hopefully they are the same... */ if( fabs( capture_time - playback_time ) > 0.01 ) PA_DEBUG(("Capture time and playback time differ by %f\n", fabs(capture_time-playback_time))); } else timeInfo->currentTime = playback_time; playback_delay = snd_pcm_status_get_delay( playback_status ); timeInfo->outputBufferDacTime = timeInfo->currentTime + (PaTime)playback_delay / stream->streamRepresentation.streamInfo.sampleRate; } } /** Called after buffer processing is finished. * * A number of mmapped frames is committed, it is possible that an xrun has occurred in the meantime. * * @param numFrames The number of frames that has been processed * @param xrun Return whether an xrun has occurred */ static PaError PaAlsaStreamComponent_EndProcessing( PaAlsaStreamComponent *self, unsigned long numFrames, int *xrun ) { PaError result = paNoError; int res; /* @concern FullDuplex It is possible that only one direction is marked ready after polling, and processed * afterwards */ if( !self->ready ) goto end; res = snd_pcm_mmap_commit( self->pcm, self->offset, numFrames ); if( res == -EPIPE || res == -ESTRPIPE ) { *xrun = 1; } else { ENSURE_( res, paUnanticipatedHostError ); } end: error: return result; } /* Extract buffer from channel area */ static unsigned char *ExtractAddress( const snd_pcm_channel_area_t *area, snd_pcm_uframes_t offset ) { return (unsigned char *) area->addr + (area->first + offset * area->step) / 8; } /** Do necessary adaption between user and host channels. * @concern ChannelAdaption Adapting between user and host channels can involve silencing unused channels and duplicating mono information if host outputs come in pairs. */ static PaError PaAlsaStreamComponent_DoChannelAdaption( PaAlsaStreamComponent *self, PaUtilBufferProcessor *bp, int numFrames ) { PaError result = paNoError; unsigned char *p; int i; int unusedChans = self->numHostChannels - self->numUserChannels; unsigned char *src, *dst; int convertMono = (self->numHostChannels % 2) == 0 && (self->numUserChannels % 2) != 0; assert( StreamDirection_Out == self->streamDir ); if( self->hostInterleaved ) { int swidth = snd_pcm_format_size( self->nativeFormat, 1 ); unsigned char *buffer = ExtractAddress( self->channelAreas, self->offset ); /* Start after the last user channel */ p = buffer + self->numUserChannels * swidth; if( convertMono ) { /* Convert the last user channel into stereo pair */ src = buffer + (self->numUserChannels - 1) * swidth; for( i = 0; i < numFrames; ++i ) { dst = src + swidth; memcpy( dst, src, swidth ); src += self->numHostChannels * swidth; } /* Don't touch the channel we just wrote to */ p += swidth; --unusedChans; } if( unusedChans > 0 ) { /* Silence unused output channels */ for( i = 0; i < numFrames; ++i ) { memset( p, 0, swidth * unusedChans ); p += self->numHostChannels * swidth; } } } else { /* We extract the last user channel */ if( convertMono ) { ENSURE_( snd_pcm_area_copy( self->channelAreas + self->numUserChannels, self->offset, self->channelAreas + (self->numUserChannels - 1), self->offset, numFrames, self->nativeFormat ), paUnanticipatedHostError ); --unusedChans; } if( unusedChans > 0 ) { snd_pcm_areas_silence( self->channelAreas + (self->numHostChannels - unusedChans), self->offset, unusedChans, numFrames, self->nativeFormat ); } } error: return result; } static PaError PaAlsaStream_EndProcessing( PaAlsaStream *self, unsigned long numFrames, int *xrunOccurred ) { PaError result = paNoError; int xrun = 0; if( self->capture.pcm ) { PA_ENSURE( PaAlsaStreamComponent_EndProcessing( &self->capture, numFrames, &xrun ) ); } if( self->playback.pcm ) { if( self->playback.numHostChannels > self->playback.numUserChannels ) { PA_ENSURE( PaAlsaStreamComponent_DoChannelAdaption( &self->playback, &self->bufferProcessor, numFrames ) ); } PA_ENSURE( PaAlsaStreamComponent_EndProcessing( &self->playback, numFrames, &xrun ) ); } error: *xrunOccurred = xrun; return result; } /** Update the number of available frames. * */ static PaError PaAlsaStreamComponent_GetAvailableFrames( PaAlsaStreamComponent *self, unsigned long *numFrames, int *xrunOccurred ) { PaError result = paNoError; snd_pcm_sframes_t framesAvail = snd_pcm_avail_update( self->pcm ); *xrunOccurred = 0; if( -EPIPE == framesAvail ) { *xrunOccurred = 1; framesAvail = 0; } else { ENSURE_( framesAvail, paUnanticipatedHostError ); } *numFrames = framesAvail; error: return result; } /** Fill in pollfd objects. */ static PaError PaAlsaStreamComponent_BeginPolling( PaAlsaStreamComponent* self, struct pollfd* pfds ) { PaError result = paNoError; int ret = snd_pcm_poll_descriptors( self->pcm, pfds, self->nfds ); (void)ret; /* Prevent unused variable warning if asserts are turned off */ assert( ret == self->nfds ); self->ready = 0; return result; } /** Examine results from poll(). * * @param pfds pollfds to inspect * @param shouldPoll Should we continue to poll * @param xrun Has an xrun occurred */ static PaError PaAlsaStreamComponent_EndPolling( PaAlsaStreamComponent* self, struct pollfd* pfds, int* shouldPoll, int* xrun ) { PaError result = paNoError; unsigned short revents; ENSURE_( snd_pcm_poll_descriptors_revents( self->pcm, pfds, self->nfds, &revents ), paUnanticipatedHostError ); if( revents != 0 ) { if( revents & POLLERR ) { *xrun = 1; } else self->ready = 1; *shouldPoll = 0; } error: return result; } /** Return the number of available frames for this stream. * * @concern FullDuplex The minimum available for the two directions is calculated, it might be desirable to ignore * one direction however (not marked ready from poll), so this is controlled by queryCapture and queryPlayback. * * @param queryCapture Check available for capture * @param queryPlayback Check available for playback * @param available The returned number of frames * @param xrunOccurred Return whether an xrun has occurred */ static PaError PaAlsaStream_GetAvailableFrames( PaAlsaStream *self, int queryCapture, int queryPlayback, unsigned long *available, int *xrunOccurred ) { PaError result = paNoError; unsigned long captureFrames, playbackFrames; *xrunOccurred = 0; assert( queryCapture || queryPlayback ); if( queryCapture ) { assert( self->capture.pcm ); PA_ENSURE( PaAlsaStreamComponent_GetAvailableFrames( &self->capture, &captureFrames, xrunOccurred ) ); if( *xrunOccurred ) { goto end; } } if( queryPlayback ) { assert( self->playback.pcm ); PA_ENSURE( PaAlsaStreamComponent_GetAvailableFrames( &self->playback, &playbackFrames, xrunOccurred ) ); if( *xrunOccurred ) { goto end; } } if( queryCapture && queryPlayback ) { *available = PA_MIN( captureFrames, playbackFrames ); /*PA_DEBUG(("capture: %lu, playback: %lu, combined: %lu\n", captureFrames, playbackFrames, *available));*/ } else if( queryCapture ) { *available = captureFrames; } else { *available = playbackFrames; } end: error: return result; } /** Wait for and report available buffer space from ALSA. * * Unless ALSA reports a minimum of frames available for I/O, we poll the ALSA filedescriptors for more. * Both of these operations can uncover xrun conditions. * * @concern Xruns Both polling and querying available frames can report an xrun condition. * * @param framesAvail Return the number of available frames * @param xrunOccurred Return whether an xrun has occurred */ static PaError PaAlsaStream_WaitForFrames( PaAlsaStream *self, unsigned long *framesAvail, int *xrunOccurred ) { PaError result = paNoError; int pollPlayback = self->playback.pcm != NULL, pollCapture = self->capture.pcm != NULL; int pollTimeout = self->pollTimeout; int xrun = 0; assert( self ); assert( framesAvail ); if( !self->callbackMode ) { /* In blocking mode we will only wait if necessary */ PA_ENSURE( PaAlsaStream_GetAvailableFrames( self, self->capture.pcm != NULL, self->playback.pcm != NULL, framesAvail, &xrun ) ); if( xrun ) { goto end; } if( *framesAvail > 0 ) { /* Mark pcms ready from poll */ if( self->capture.pcm ) self->capture.ready = 1; if( self->playback.pcm ) self->playback.ready = 1; goto end; } } while( pollPlayback || pollCapture ) { int totalFds = 0; struct pollfd *capturePfds = NULL, *playbackPfds = NULL; pthread_testcancel(); if( pollCapture ) { capturePfds = self->pfds; PA_ENSURE( PaAlsaStreamComponent_BeginPolling( &self->capture, capturePfds ) ); totalFds += self->capture.nfds; } if( pollPlayback ) { playbackPfds = self->pfds + (self->capture.pcm ? self->capture.nfds : 0); PA_ENSURE( PaAlsaStreamComponent_BeginPolling( &self->playback, playbackPfds ) ); totalFds += self->playback.nfds; } if( poll( self->pfds, totalFds, pollTimeout ) < 0 ) { /* XXX: Depend on preprocessor condition? */ if( errno == EINTR ) { /* gdb */ continue; } /* TODO: Add macro for checking system calls */ PA_ENSURE( paInternalError ); } /* check the return status of our pfds */ if( pollCapture ) { PA_ENSURE( PaAlsaStreamComponent_EndPolling( &self->capture, capturePfds, &pollCapture, &xrun ) ); } if( pollPlayback ) { PA_ENSURE( PaAlsaStreamComponent_EndPolling( &self->playback, playbackPfds, &pollPlayback, &xrun ) ); } if( xrun ) { break; } /* @concern FullDuplex If only one of two pcms is ready we may want to compromise between the two. * If there is less than half a period's worth of samples left of frames in the other pcm's buffer we will * stop polling. */ if( self->capture.pcm && self->playback.pcm ) { if( pollCapture && !pollPlayback ) { PA_ENSURE( ContinuePoll( self, StreamDirection_In, &pollTimeout, &pollCapture ) ); } else if( pollPlayback && !pollCapture ) { PA_ENSURE( ContinuePoll( self, StreamDirection_Out, &pollTimeout, &pollPlayback ) ); } } } if( !xrun ) { /* Get the number of available frames for the pcms that are marked ready. * @concern FullDuplex If only one direction is marked ready (from poll), the number of frames available for * the other direction is returned. Output is normally preferred over capture however, so capture frames may be * discarded to avoid overrun unless paNeverDropInput is specified. */ int captureReady = self->capture.pcm ? self->capture.ready : 0, playbackReady = self->playback.pcm ? self->playback.ready : 0; PA_ENSURE( PaAlsaStream_GetAvailableFrames( self, captureReady, playbackReady, framesAvail, &xrun ) ); if( self->capture.pcm && self->playback.pcm ) { if( !self->playback.ready && !self->neverDropInput ) { /* Drop input, a period's worth */ assert( self->capture.ready ); PaAlsaStreamComponent_EndProcessing( &self->capture, PA_MIN( self->capture.framesPerBuffer, *framesAvail ), &xrun ); *framesAvail = 0; self->capture.ready = 0; } } else if( self->capture.pcm ) assert( self->capture.ready ); else assert( self->playback.ready ); } end: error: if( xrun ) { /* Recover from the xrun state */ PA_ENSURE( PaAlsaStream_HandleXrun( self ) ); *framesAvail = 0; } else { if( 0 != *framesAvail ) { /* If we're reporting frames eligible for processing, one of the handles better be ready */ PA_UNLESS( self->capture.ready || self->playback.ready, paInternalError ); } } *xrunOccurred = xrun; return result; } /** Register per-channel ALSA buffer information with buffer processor. * * Mmapped buffer space is acquired from ALSA, and registered with the buffer processor. Differences between the * number of host and user channels is taken into account. * * @param numFrames On entrance the number of requested frames, on exit the number of contiguously accessible frames. */ static PaError PaAlsaStreamComponent_RegisterChannels( PaAlsaStreamComponent* self, PaUtilBufferProcessor* bp, unsigned long* numFrames, int* xrun ) { PaError result = paNoError; const snd_pcm_channel_area_t *areas, *area; void (*setChannel)(PaUtilBufferProcessor *, unsigned int, void *, unsigned int) = StreamDirection_In == self->streamDir ? PaUtil_SetInputChannel : PaUtil_SetOutputChannel; unsigned char *buffer, *p; int i; unsigned long framesAvail; /* This _must_ be called before mmap_begin */ PA_ENSURE( PaAlsaStreamComponent_GetAvailableFrames( self, &framesAvail, xrun ) ); if( *xrun ) { *numFrames = 0; goto end; } ENSURE_( snd_pcm_mmap_begin( self->pcm, &areas, &self->offset, numFrames ), paUnanticipatedHostError ); if( self->hostInterleaved ) { int swidth = snd_pcm_format_size( self->nativeFormat, 1 ); p = buffer = ExtractAddress( areas, self->offset ); for( i = 0; i < self->numUserChannels; ++i ) { /* We're setting the channels up to userChannels, but the stride will be hostChannels samples */ setChannel( bp, i, p, self->numHostChannels ); p += swidth; } } else { for( i = 0; i < self->numUserChannels; ++i ) { area = areas + i; buffer = ExtractAddress( area, self->offset ); setChannel( bp, i, buffer, 1 ); } } /* @concern ChannelAdaption Buffer address is recorded so we can do some channel adaption later */ self->channelAreas = (snd_pcm_channel_area_t *)areas; end: error: return result; } /** Initiate buffer processing. * * ALSA buffers are registered with the PA buffer processor and the buffer size (in frames) set. * * @concern FullDuplex If both directions are being processed, the minimum amount of frames for the two directions is * calculated. * * @param numFrames On entrance the number of available frames, on exit the number of received frames * @param xrunOccurred Return whether an xrun has occurred */ static PaError PaAlsaStream_SetUpBuffers( PaAlsaStream* self, unsigned long* numFrames, int* xrunOccurred ) { PaError result = paNoError; unsigned long captureFrames = ULONG_MAX, playbackFrames = ULONG_MAX, commonFrames = 0; int xrun = 0; if( *xrunOccurred ) { *numFrames = 0; return result; } /* If we got here at least one of the pcm's should be marked ready */ PA_UNLESS( self->capture.ready || self->playback.ready, paInternalError ); /* Extract per-channel ALSA buffer pointers and register them with the buffer processor. * It is possible that a direction is not marked ready however, because it is out of sync with the other. */ if( self->capture.pcm && self->capture.ready ) { captureFrames = *numFrames; PA_ENSURE( PaAlsaStreamComponent_RegisterChannels( &self->capture, &self->bufferProcessor, &captureFrames, &xrun ) ); } if( self->playback.pcm && self->playback.ready ) { playbackFrames = *numFrames; PA_ENSURE( PaAlsaStreamComponent_RegisterChannels( &self->playback, &self->bufferProcessor, &playbackFrames, &xrun ) ); } if( xrun ) { /* Nothing more to do */ assert( 0 == commonFrames ); goto end; } commonFrames = PA_MIN( captureFrames, playbackFrames ); /* assert( commonFrames <= *numFrames ); */ if( commonFrames > *numFrames ) { /* Hmmm ... how come there are more frames available than we requested!? Blah. */ PA_DEBUG(( "%s: Common available frames are reported to be more than number requested: %lu, %lu, callbackMode: %d\n", __FUNCTION__, commonFrames, *numFrames, self->callbackMode )); if( self->capture.pcm ) { PA_DEBUG(( "%s: captureFrames: %lu, capture.ready: %d\n", __FUNCTION__, captureFrames, self->capture.ready )); } if( self->playback.pcm ) { PA_DEBUG(( "%s: playbackFrames: %lu, playback.ready: %d\n", __FUNCTION__, playbackFrames, self->playback.ready )); } commonFrames = 0; goto end; } /* Inform PortAudio of the number of frames we got. * @concern FullDuplex We might be experiencing underflow in either end; if its an input underflow, we go on * with output. If its output underflow however, depending on the paNeverDropInput flag, we may want to simply * discard the excess input or call the callback with paOutputOverflow flagged. */ if( self->capture.pcm ) { if( self->capture.ready ) { PaUtil_SetInputFrameCount( &self->bufferProcessor, commonFrames ); } else { /* We have input underflow */ PaUtil_SetNoInput( &self->bufferProcessor ); } } if( self->playback.pcm ) { if( self->playback.ready ) { PaUtil_SetOutputFrameCount( &self->bufferProcessor, commonFrames ); } else { /* We have output underflow, but keeping input data (paNeverDropInput) */ assert( self->neverDropInput ); assert( self->capture.pcm != NULL ); PA_DEBUG(( "%s: Setting output buffers to NULL\n", __FUNCTION__ )); PaUtil_SetNoOutput( &self->bufferProcessor ); } } end: *numFrames = commonFrames; error: if( xrun ) { PA_ENSURE( PaAlsaStream_HandleXrun( self ) ); *numFrames = 0; } *xrunOccurred = xrun; return result; } /** Callback thread's function. * * Roughly, the workflow can be described in the following way: The number of available frames that can be processed * directly is obtained from ALSA, we then request as much directly accessible memory as possible within this amount * from ALSA. The buffer memory is registered with the PA buffer processor and processing is carried out with * PaUtil_EndBufferProcessing. Finally, the number of processed frames is reported to ALSA. The processing can * happen in several iterations untill we have consumed the known number of available frames (or an xrun is detected). */ static void *CallbackThreadFunc( void *userData ) { PaError result = paNoError; PaAlsaStream *stream = (PaAlsaStream*) userData; PaStreamCallbackTimeInfo timeInfo = {0, 0, 0}; snd_pcm_sframes_t startThreshold = 0; int callbackResult = paContinue; PaStreamCallbackFlags cbFlags = 0; /* We might want to keep state across iterations */ int streamStarted = 0; assert( stream ); /* Execute OnExit when exiting */ pthread_cleanup_push( &OnExit, stream ); /* Not implemented */ assert( !stream->primeBuffers ); /* @concern StreamStart If the output is being primed the output pcm needs to be prepared, otherwise the * stream is started immediately. The latter involves signaling the waiting main thread. */ if( stream->primeBuffers ) { snd_pcm_sframes_t avail; if( stream->playback.pcm ) ENSURE_( snd_pcm_prepare( stream->playback.pcm ), paUnanticipatedHostError ); if( stream->capture.pcm && !stream->pcmsSynced ) ENSURE_( snd_pcm_prepare( stream->capture.pcm ), paUnanticipatedHostError ); /* We can't be certain that the whole ring buffer is available for priming, but there should be * at least one period */ avail = snd_pcm_avail_update( stream->playback.pcm ); startThreshold = avail - (avail % stream->playback.framesPerBuffer); assert( startThreshold >= stream->playback.framesPerBuffer ); } else { PA_ENSURE( PaUnixThread_PrepareNotify( &stream->thread ) ); /* Buffer will be zeroed */ PA_ENSURE( AlsaStart( stream, 0 ) ); PA_ENSURE( PaUnixThread_NotifyParent( &stream->thread ) ); streamStarted = 1; } while( 1 ) { unsigned long framesAvail, framesGot; int xrun = 0; pthread_testcancel(); /* @concern StreamStop if the main thread has requested a stop and the stream has not been effectively * stopped we signal this condition by modifying callbackResult (we'll want to flush buffered output). */ if( PaUnixThread_StopRequested( &stream->thread ) && paContinue == callbackResult ) { PA_DEBUG(( "Setting callbackResult to paComplete\n" )); callbackResult = paComplete; } if( paContinue != callbackResult ) { stream->callbackAbort = (paAbort == callbackResult); if( stream->callbackAbort || /** @concern BlockAdaption: Go on if adaption buffers are empty */ PaUtil_IsBufferProcessorOutputEmpty( &stream->bufferProcessor ) ) { goto end; } PA_DEBUG(( "%s: Flushing buffer processor\n", __FUNCTION__ )); /* There is still buffered output that needs to be processed */ } /* Wait for data to become available, this comes down to polling the ALSA file descriptors untill we have * a number of available frames. */ PA_ENSURE( PaAlsaStream_WaitForFrames( stream, &framesAvail, &xrun ) ); if( xrun ) { assert( 0 == framesAvail ); continue; /* XXX: Report xruns to the user? A situation is conceivable where the callback is never invoked due * to constant xruns, it might be desirable to notify the user of this. */ } /* Consume buffer space. Once we have a number of frames available for consumption we must retrieve the * mmapped buffers from ALSA, this is contiguously accessible memory however, so we may receive smaller * portions at a time than is available as a whole. Therefore we should be prepared to process several * chunks successively. The buffers are passed to the PA buffer processor. */ while( framesAvail > 0 ) { xrun = 0; pthread_testcancel(); /** @concern Xruns Under/overflows are to be reported to the callback */ if( stream->underrun > 0.0 ) { cbFlags |= paOutputUnderflow; stream->underrun = 0.0; } if( stream->overrun > 0.0 ) { cbFlags |= paInputOverflow; stream->overrun = 0.0; } if( stream->capture.pcm && stream->playback.pcm ) { /** @concern FullDuplex It's possible that only one direction is being processed to avoid an * under- or overflow, this should be reported correspondingly */ if( !stream->capture.ready ) { cbFlags |= paInputUnderflow; PA_DEBUG(( "%s: Input underflow\n", __FUNCTION__ )); } else if( !stream->playback.ready ) { cbFlags |= paOutputOverflow; PA_DEBUG(( "%s: Output overflow\n", __FUNCTION__ )); } } #if 0 CallbackUpdate( &stream->threading ); #endif CalculateTimeInfo( stream, &timeInfo ); PaUtil_BeginBufferProcessing( &stream->bufferProcessor, &timeInfo, cbFlags ); cbFlags = 0; /* CPU load measurement should include processing activivity external to the stream callback */ PaUtil_BeginCpuLoadMeasurement( &stream->cpuLoadMeasurer ); framesGot = framesAvail; if( paUtilFixedHostBufferSize == stream->bufferProcessor.hostBufferSizeMode ) { /* We've committed to a fixed host buffer size, stick to that */ framesGot = framesGot >= stream->maxFramesPerHostBuffer ? stream->maxFramesPerHostBuffer : 0; } else { /* We've committed to an upper bound on the size of host buffers */ assert( paUtilBoundedHostBufferSize == stream->bufferProcessor.hostBufferSizeMode ); framesGot = PA_MIN( framesGot, stream->maxFramesPerHostBuffer ); } PA_ENSURE( PaAlsaStream_SetUpBuffers( stream, &framesGot, &xrun ) ); /* Check the host buffer size against the buffer processor configuration */ framesAvail -= framesGot; if( framesGot > 0 ) { assert( !xrun ); PaUtil_EndBufferProcessing( &stream->bufferProcessor, &callbackResult ); PA_ENSURE( PaAlsaStream_EndProcessing( stream, framesGot, &xrun ) ); } PaUtil_EndCpuLoadMeasurement( &stream->cpuLoadMeasurer, framesGot ); if( 0 == framesGot ) { /* Go back to polling for more frames */ break; } if( paContinue != callbackResult ) break; } } /* Match pthread_cleanup_push */ pthread_cleanup_pop( 1 ); end: PA_DEBUG(( "%s: Thread %d exiting\n ", __FUNCTION__, pthread_self() )); PaUnixThreading_EXIT( result ); error: goto end; } /* Blocking interface */ static PaError ReadStream( PaStream* s, void *buffer, unsigned long frames ) { PaError result = paNoError; PaAlsaStream *stream = (PaAlsaStream*)s; unsigned long framesGot, framesAvail; void *userBuffer; snd_pcm_t *save = stream->playback.pcm; assert( stream ); PA_UNLESS( stream->capture.pcm, paCanNotReadFromAnOutputOnlyStream ); /* Disregard playback */ stream->playback.pcm = NULL; if( stream->overrun > 0. ) { result = paInputOverflowed; stream->overrun = 0.0; } if( stream->capture.userInterleaved ) { userBuffer = buffer; } else { /* Copy channels into local array */ userBuffer = stream->capture.userBuffers; memcpy( userBuffer, buffer, sizeof (void *) * stream->capture.numUserChannels ); } /* Start stream if in prepared state */ if( snd_pcm_state( stream->capture.pcm ) == SND_PCM_STATE_PREPARED ) { ENSURE_( snd_pcm_start( stream->capture.pcm ), paUnanticipatedHostError ); } while( frames > 0 ) { int xrun = 0; PA_ENSURE( PaAlsaStream_WaitForFrames( stream, &framesAvail, &xrun ) ); framesGot = PA_MIN( framesAvail, frames ); PA_ENSURE( PaAlsaStream_SetUpBuffers( stream, &framesGot, &xrun ) ); if( framesGot > 0 ) { framesGot = PaUtil_CopyInput( &stream->bufferProcessor, &userBuffer, framesGot ); PA_ENSURE( PaAlsaStream_EndProcessing( stream, framesGot, &xrun ) ); frames -= framesGot; } } end: stream->playback.pcm = save; return result; error: goto end; } static PaError WriteStream( PaStream* s, const void *buffer, unsigned long frames ) { PaError result = paNoError; signed long err; PaAlsaStream *stream = (PaAlsaStream*)s; snd_pcm_uframes_t framesGot, framesAvail; const void *userBuffer; snd_pcm_t *save = stream->capture.pcm; assert( stream ); PA_UNLESS( stream->playback.pcm, paCanNotWriteToAnInputOnlyStream ); /* Disregard capture */ stream->capture.pcm = NULL; if( stream->underrun > 0. ) { result = paOutputUnderflowed; stream->underrun = 0.0; } if( stream->playback.userInterleaved ) userBuffer = buffer; else /* Copy channels into local array */ { userBuffer = stream->playback.userBuffers; memcpy( (void *)userBuffer, buffer, sizeof (void *) * stream->playback.numUserChannels ); } while( frames > 0 ) { int xrun = 0; snd_pcm_uframes_t hwAvail; PA_ENSURE( PaAlsaStream_WaitForFrames( stream, &framesAvail, &xrun ) ); framesGot = PA_MIN( framesAvail, frames ); PA_ENSURE( PaAlsaStream_SetUpBuffers( stream, &framesGot, &xrun ) ); if( framesGot > 0 ) { framesGot = PaUtil_CopyOutput( &stream->bufferProcessor, &userBuffer, framesGot ); PA_ENSURE( PaAlsaStream_EndProcessing( stream, framesGot, &xrun ) ); frames -= framesGot; } /* Start stream after one period of samples worth */ /* Frames residing in buffer */ PA_ENSURE( err = GetStreamWriteAvailable( stream ) ); framesAvail = err; hwAvail = stream->playback.bufferSize - framesAvail; if( snd_pcm_state( stream->playback.pcm ) == SND_PCM_STATE_PREPARED && hwAvail >= stream->playback.framesPerBuffer ) { ENSURE_( snd_pcm_start( stream->playback.pcm ), paUnanticipatedHostError ); } } end: stream->capture.pcm = save; return result; error: goto end; } /* Return frames available for reading. In the event of an overflow, the capture pcm will be restarted */ static signed long GetStreamReadAvailable( PaStream* s ) { PaError result = paNoError; PaAlsaStream *stream = (PaAlsaStream*)s; unsigned long avail; int xrun; PA_ENSURE( PaAlsaStreamComponent_GetAvailableFrames( &stream->capture, &avail, &xrun ) ); if( xrun ) { PA_ENSURE( PaAlsaStream_HandleXrun( stream ) ); PA_ENSURE( PaAlsaStreamComponent_GetAvailableFrames( &stream->capture, &avail, &xrun ) ); if( xrun ) PA_ENSURE( paInputOverflowed ); } return (signed long)avail; error: return result; } static signed long GetStreamWriteAvailable( PaStream* s ) { PaError result = paNoError; PaAlsaStream *stream = (PaAlsaStream*)s; unsigned long avail; int xrun; PA_ENSURE( PaAlsaStreamComponent_GetAvailableFrames( &stream->playback, &avail, &xrun ) ); if( xrun ) { snd_pcm_sframes_t savail; PA_ENSURE( PaAlsaStream_HandleXrun( stream ) ); savail = snd_pcm_avail_update( stream->playback.pcm ); /* savail should not contain -EPIPE now, since PaAlsaStream_HandleXrun will only prepare the pcm */ ENSURE_( savail, paUnanticipatedHostError ); avail = (unsigned long) savail; } return (signed long)avail; error: return result; } /* Extensions */ void PaAlsa_InitializeStreamInfo( PaAlsaStreamInfo *info ) { info->size = sizeof (PaAlsaStreamInfo); info->hostApiType = paALSA; info->version = 1; info->deviceString = NULL; } void PaAlsa_EnableRealtimeScheduling( PaStream *s, int enable ) { PaAlsaStream *stream = (PaAlsaStream *) s; stream->rtSched = enable; } #if 0 void PaAlsa_EnableWatchdog( PaStream *s, int enable ) { PaAlsaStream *stream = (PaAlsaStream *) s; stream->thread.useWatchdog = enable; } #endif PaError PaAlsa_GetStreamInputCard(PaStream* s, int* card) { PaAlsaStream *stream = (PaAlsaStream *) s; snd_pcm_info_t* pcmInfo; PaError result = paNoError; /* XXX: More descriptive error? */ PA_UNLESS( stream->capture.pcm, paDeviceUnavailable ); snd_pcm_info_alloca( &pcmInfo ); PA_ENSURE( snd_pcm_info( stream->capture.pcm, pcmInfo ) ); *card = snd_pcm_info_get_card( pcmInfo ); error: return result; } PaError PaAlsa_GetStreamOutputCard(PaStream* s, int* card) { PaAlsaStream *stream = (PaAlsaStream *) s; snd_pcm_info_t* pcmInfo; PaError result = paNoError; /* XXX: More descriptive error? */ PA_UNLESS( stream->playback.pcm, paDeviceUnavailable ); snd_pcm_info_alloca( &pcmInfo ); PA_ENSURE( snd_pcm_info( stream->playback.pcm, pcmInfo ) ); *card = snd_pcm_info_get_card( pcmInfo ); error: return result; } #endifsources_5316/external/portaudio/pa_process.c0000644000176700017670000017716710474003011020066 0ustar paulpaul/* * $Id: pa_process.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library * streamCallback <-> host buffer processing adapter * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Buffer Processor implementation. The code in this file is not optimised yet - although it's not clear that it needs to be. there may appear to be redundancies that could be factored into common functions, but the redundanceis are left intentionally as each appearance may have different optimisation possibilities. The optimisations which are planned involve only converting data in-place where possible, rather than copying to the temp buffer(s). Note that in the extreme case of being able to convert in-place, and there being no conversion necessary there should be some code which short-circuits the operation. @todo Consider cache tilings for intereave<->deinterleave. @todo implement timeInfo->currentTime int PaUtil_BeginBufferProcessing() @todo specify and implement some kind of logical policy for handling the underflow and overflow stream flags when the underflow/overflow overlaps multiple user buffers/callbacks. @todo provide support for priming the buffers with data from the callback. The client interface is now implemented through PaUtil_SetNoInput() which sets bp->hostInputChannels[0][0].data to zero. However this is currently only implemented in NonAdaptingProcess(). It shouldn't be needed for AdaptingInputOnlyProcess() (no priming should ever be requested for AdaptingInputOnlyProcess()). Not sure if additional work should be required to make it work with AdaptingOutputOnlyProcess, but it definitely is required for AdaptingProcess. @todo implement PaUtil_SetNoOutput for AdaptingProcess @todo don't allocate temp buffers for blocking streams unless they are needed. At the moment they are needed, but perhaps for host APIs where the implementation passes a buffer to the host they could be used. */ #include #include /* memset() */ #include "pa_process.h" #include "pa_util.h" #define PA_FRAMES_PER_TEMP_BUFFER_WHEN_HOST_BUFFER_SIZE_IS_UNKNOWN_ 1024 #define PA_MIN_( a, b ) ( ((a)<(b)) ? (a) : (b) ) /* greatest common divisor - PGCD in French */ static unsigned long GCD( unsigned long a, unsigned long b ) { return (b==0) ? a : GCD( b, a%b); } /* least common multiple - PPCM in French */ static unsigned long LCM( unsigned long a, unsigned long b ) { return (a*b) / GCD(a,b); } #define PA_MAX_( a, b ) (((a) > (b)) ? (a) : (b)) static unsigned long CalculateFrameShift( unsigned long M, unsigned long N ) { unsigned long result = 0; unsigned long i; unsigned long lcm; assert( M > 0 ); assert( N > 0 ); lcm = LCM( M, N ); for( i = M; i < lcm; i += M ) result = PA_MAX_( result, i % N ); return result; } PaError PaUtil_InitializeBufferProcessor( PaUtilBufferProcessor* bp, int inputChannelCount, PaSampleFormat userInputSampleFormat, PaSampleFormat hostInputSampleFormat, int outputChannelCount, PaSampleFormat userOutputSampleFormat, PaSampleFormat hostOutputSampleFormat, double sampleRate, PaStreamFlags streamFlags, unsigned long framesPerUserBuffer, unsigned long framesPerHostBuffer, PaUtilHostBufferSizeMode hostBufferSizeMode, PaStreamCallback *streamCallback, void *userData ) { PaError result = paNoError; PaError bytesPerSample; unsigned long tempInputBufferSize, tempOutputBufferSize; if( streamFlags & paNeverDropInput ) { /* paNeverDropInput is only valid for full-duplex callback streams, with an unspecified number of frames per buffer. */ if( !streamCallback || !(inputChannelCount > 0 && outputChannelCount > 0) || framesPerUserBuffer != paFramesPerBufferUnspecified ) return paInvalidFlag; } /* initialize buffer ptrs to zero so they can be freed if necessary in error */ bp->tempInputBuffer = 0; bp->tempInputBufferPtrs = 0; bp->tempOutputBuffer = 0; bp->tempOutputBufferPtrs = 0; bp->framesPerUserBuffer = framesPerUserBuffer; bp->framesPerHostBuffer = framesPerHostBuffer; bp->inputChannelCount = inputChannelCount; bp->outputChannelCount = outputChannelCount; bp->hostBufferSizeMode = hostBufferSizeMode; bp->hostInputChannels[0] = bp->hostInputChannels[1] = 0; bp->hostOutputChannels[0] = bp->hostOutputChannels[1] = 0; if( framesPerUserBuffer == 0 ) /* streamCallback will accept any buffer size */ { bp->useNonAdaptingProcess = 1; bp->initialFramesInTempInputBuffer = 0; bp->initialFramesInTempOutputBuffer = 0; if( hostBufferSizeMode == paUtilFixedHostBufferSize || hostBufferSizeMode == paUtilBoundedHostBufferSize ) { bp->framesPerTempBuffer = framesPerHostBuffer; } else /* unknown host buffer size */ { bp->framesPerTempBuffer = PA_FRAMES_PER_TEMP_BUFFER_WHEN_HOST_BUFFER_SIZE_IS_UNKNOWN_; } } else { bp->framesPerTempBuffer = framesPerUserBuffer; if( hostBufferSizeMode == paUtilFixedHostBufferSize && framesPerHostBuffer % framesPerUserBuffer == 0 ) { bp->useNonAdaptingProcess = 1; bp->initialFramesInTempInputBuffer = 0; bp->initialFramesInTempOutputBuffer = 0; } else { bp->useNonAdaptingProcess = 0; if( inputChannelCount > 0 && outputChannelCount > 0 ) { /* full duplex */ if( hostBufferSizeMode == paUtilFixedHostBufferSize ) { unsigned long frameShift = CalculateFrameShift( framesPerHostBuffer, framesPerUserBuffer ); if( framesPerUserBuffer > framesPerHostBuffer ) { bp->initialFramesInTempInputBuffer = frameShift; bp->initialFramesInTempOutputBuffer = 0; } else { bp->initialFramesInTempInputBuffer = 0; bp->initialFramesInTempOutputBuffer = frameShift; } } else /* variable host buffer size, add framesPerUserBuffer latency */ { bp->initialFramesInTempInputBuffer = 0; bp->initialFramesInTempOutputBuffer = framesPerUserBuffer; } } else { /* half duplex */ bp->initialFramesInTempInputBuffer = 0; bp->initialFramesInTempOutputBuffer = 0; } } } bp->framesInTempInputBuffer = bp->initialFramesInTempInputBuffer; bp->framesInTempOutputBuffer = bp->initialFramesInTempOutputBuffer; if( inputChannelCount > 0 ) { bytesPerSample = Pa_GetSampleSize( hostInputSampleFormat ); if( bytesPerSample > 0 ) { bp->bytesPerHostInputSample = bytesPerSample; } else { result = bytesPerSample; goto error; } bytesPerSample = Pa_GetSampleSize( userInputSampleFormat ); if( bytesPerSample > 0 ) { bp->bytesPerUserInputSample = bytesPerSample; } else { result = bytesPerSample; goto error; } bp->inputConverter = PaUtil_SelectConverter( hostInputSampleFormat, userInputSampleFormat, streamFlags ); bp->inputZeroer = PaUtil_SelectZeroer( hostInputSampleFormat ); bp->userInputIsInterleaved = (userInputSampleFormat & paNonInterleaved)?0:1; tempInputBufferSize = bp->framesPerTempBuffer * bp->bytesPerUserInputSample * inputChannelCount; bp->tempInputBuffer = PaUtil_AllocateMemory( tempInputBufferSize ); if( bp->tempInputBuffer == 0 ) { result = paInsufficientMemory; goto error; } if( bp->framesInTempInputBuffer > 0 ) memset( bp->tempInputBuffer, 0, tempInputBufferSize ); if( userInputSampleFormat & paNonInterleaved ) { bp->tempInputBufferPtrs = (void **)PaUtil_AllocateMemory( sizeof(void*)*inputChannelCount ); if( bp->tempInputBufferPtrs == 0 ) { result = paInsufficientMemory; goto error; } } bp->hostInputChannels[0] = (PaUtilChannelDescriptor*) PaUtil_AllocateMemory( sizeof(PaUtilChannelDescriptor) * inputChannelCount * 2); if( bp->hostInputChannels[0] == 0 ) { result = paInsufficientMemory; goto error; } bp->hostInputChannels[1] = &bp->hostInputChannels[0][inputChannelCount]; } if( outputChannelCount > 0 ) { bytesPerSample = Pa_GetSampleSize( hostOutputSampleFormat ); if( bytesPerSample > 0 ) { bp->bytesPerHostOutputSample = bytesPerSample; } else { result = bytesPerSample; goto error; } bytesPerSample = Pa_GetSampleSize( userOutputSampleFormat ); if( bytesPerSample > 0 ) { bp->bytesPerUserOutputSample = bytesPerSample; } else { result = bytesPerSample; goto error; } bp->outputConverter = PaUtil_SelectConverter( userOutputSampleFormat, hostOutputSampleFormat, streamFlags ); bp->outputZeroer = PaUtil_SelectZeroer( hostOutputSampleFormat ); bp->userOutputIsInterleaved = (userOutputSampleFormat & paNonInterleaved)?0:1; tempOutputBufferSize = bp->framesPerTempBuffer * bp->bytesPerUserOutputSample * outputChannelCount; bp->tempOutputBuffer = PaUtil_AllocateMemory( tempOutputBufferSize ); if( bp->tempOutputBuffer == 0 ) { result = paInsufficientMemory; goto error; } if( bp->framesInTempOutputBuffer > 0 ) memset( bp->tempOutputBuffer, 0, tempOutputBufferSize ); if( userOutputSampleFormat & paNonInterleaved ) { bp->tempOutputBufferPtrs = (void **)PaUtil_AllocateMemory( sizeof(void*)*outputChannelCount ); if( bp->tempOutputBufferPtrs == 0 ) { result = paInsufficientMemory; goto error; } } bp->hostOutputChannels[0] = (PaUtilChannelDescriptor*) PaUtil_AllocateMemory( sizeof(PaUtilChannelDescriptor)*outputChannelCount * 2 ); if( bp->hostOutputChannels[0] == 0 ) { result = paInsufficientMemory; goto error; } bp->hostOutputChannels[1] = &bp->hostOutputChannels[0][outputChannelCount]; } PaUtil_InitializeTriangularDitherState( &bp->ditherGenerator ); bp->samplePeriod = 1. / sampleRate; bp->streamCallback = streamCallback; bp->userData = userData; return result; error: if( bp->tempInputBuffer ) PaUtil_FreeMemory( bp->tempInputBuffer ); if( bp->tempInputBufferPtrs ) PaUtil_FreeMemory( bp->tempInputBufferPtrs ); if( bp->hostInputChannels[0] ) PaUtil_FreeMemory( bp->hostInputChannels[0] ); if( bp->tempOutputBuffer ) PaUtil_FreeMemory( bp->tempOutputBuffer ); if( bp->tempOutputBufferPtrs ) PaUtil_FreeMemory( bp->tempOutputBufferPtrs ); if( bp->hostOutputChannels[0] ) PaUtil_FreeMemory( bp->hostOutputChannels[0] ); return result; } void PaUtil_TerminateBufferProcessor( PaUtilBufferProcessor* bp ) { if( bp->tempInputBuffer ) PaUtil_FreeMemory( bp->tempInputBuffer ); if( bp->tempInputBufferPtrs ) PaUtil_FreeMemory( bp->tempInputBufferPtrs ); if( bp->hostInputChannels[0] ) PaUtil_FreeMemory( bp->hostInputChannels[0] ); if( bp->tempOutputBuffer ) PaUtil_FreeMemory( bp->tempOutputBuffer ); if( bp->tempOutputBufferPtrs ) PaUtil_FreeMemory( bp->tempOutputBufferPtrs ); if( bp->hostOutputChannels[0] ) PaUtil_FreeMemory( bp->hostOutputChannels[0] ); } void PaUtil_ResetBufferProcessor( PaUtilBufferProcessor* bp ) { unsigned long tempInputBufferSize, tempOutputBufferSize; bp->framesInTempInputBuffer = bp->initialFramesInTempInputBuffer; bp->framesInTempOutputBuffer = bp->initialFramesInTempOutputBuffer; if( bp->framesInTempInputBuffer > 0 ) { tempInputBufferSize = bp->framesPerTempBuffer * bp->bytesPerUserInputSample * bp->inputChannelCount; memset( bp->tempInputBuffer, 0, tempInputBufferSize ); } if( bp->framesInTempOutputBuffer > 0 ) { tempOutputBufferSize = bp->framesPerTempBuffer * bp->bytesPerUserOutputSample * bp->outputChannelCount; memset( bp->tempOutputBuffer, 0, tempOutputBufferSize ); } } unsigned long PaUtil_GetBufferProcessorInputLatency( PaUtilBufferProcessor* bp ) { return bp->initialFramesInTempInputBuffer; } unsigned long PaUtil_GetBufferProcessorOutputLatency( PaUtilBufferProcessor* bp ) { return bp->initialFramesInTempOutputBuffer; } void PaUtil_SetInputFrameCount( PaUtilBufferProcessor* bp, unsigned long frameCount ) { if( frameCount == 0 ) bp->hostInputFrameCount[0] = bp->framesPerHostBuffer; else bp->hostInputFrameCount[0] = frameCount; } void PaUtil_SetNoInput( PaUtilBufferProcessor* bp ) { assert( bp->inputChannelCount > 0 ); bp->hostInputChannels[0][0].data = 0; } void PaUtil_SetInputChannel( PaUtilBufferProcessor* bp, unsigned int channel, void *data, unsigned int stride ) { assert( channel < bp->inputChannelCount ); bp->hostInputChannels[0][channel].data = data; bp->hostInputChannels[0][channel].stride = stride; } void PaUtil_SetInterleavedInputChannels( PaUtilBufferProcessor* bp, unsigned int firstChannel, void *data, unsigned int channelCount ) { unsigned int i; unsigned int channel = firstChannel; unsigned char *p = (unsigned char*)data; if( channelCount == 0 ) channelCount = bp->inputChannelCount; assert( firstChannel < bp->inputChannelCount ); assert( firstChannel + channelCount <= bp->inputChannelCount ); for( i=0; i< channelCount; ++i ) { bp->hostInputChannels[0][channel+i].data = p; p += bp->bytesPerHostInputSample; bp->hostInputChannels[0][channel+i].stride = channelCount; } } void PaUtil_SetNonInterleavedInputChannel( PaUtilBufferProcessor* bp, unsigned int channel, void *data ) { assert( channel < bp->inputChannelCount ); bp->hostInputChannels[0][channel].data = data; bp->hostInputChannels[0][channel].stride = 1; } void PaUtil_Set2ndInputFrameCount( PaUtilBufferProcessor* bp, unsigned long frameCount ) { bp->hostInputFrameCount[1] = frameCount; } void PaUtil_Set2ndInputChannel( PaUtilBufferProcessor* bp, unsigned int channel, void *data, unsigned int stride ) { assert( channel < bp->inputChannelCount ); bp->hostInputChannels[1][channel].data = data; bp->hostInputChannels[1][channel].stride = stride; } void PaUtil_Set2ndInterleavedInputChannels( PaUtilBufferProcessor* bp, unsigned int firstChannel, void *data, unsigned int channelCount ) { unsigned int i; unsigned int channel = firstChannel; unsigned char *p = (unsigned char*)data; if( channelCount == 0 ) channelCount = bp->inputChannelCount; assert( firstChannel < bp->inputChannelCount ); assert( firstChannel + channelCount <= bp->inputChannelCount ); for( i=0; i< channelCount; ++i ) { bp->hostInputChannels[1][channel+i].data = p; p += bp->bytesPerHostInputSample; bp->hostInputChannels[1][channel+i].stride = channelCount; } } void PaUtil_Set2ndNonInterleavedInputChannel( PaUtilBufferProcessor* bp, unsigned int channel, void *data ) { assert( channel < bp->inputChannelCount ); bp->hostInputChannels[1][channel].data = data; bp->hostInputChannels[1][channel].stride = 1; } void PaUtil_SetOutputFrameCount( PaUtilBufferProcessor* bp, unsigned long frameCount ) { if( frameCount == 0 ) bp->hostOutputFrameCount[0] = bp->framesPerHostBuffer; else bp->hostOutputFrameCount[0] = frameCount; } void PaUtil_SetNoOutput( PaUtilBufferProcessor* bp ) { assert( bp->outputChannelCount > 0 ); bp->hostOutputChannels[0][0].data = 0; } void PaUtil_SetOutputChannel( PaUtilBufferProcessor* bp, unsigned int channel, void *data, unsigned int stride ) { assert( channel < bp->outputChannelCount ); assert( data != NULL ); bp->hostOutputChannels[0][channel].data = data; bp->hostOutputChannels[0][channel].stride = stride; } void PaUtil_SetInterleavedOutputChannels( PaUtilBufferProcessor* bp, unsigned int firstChannel, void *data, unsigned int channelCount ) { unsigned int i; unsigned int channel = firstChannel; unsigned char *p = (unsigned char*)data; if( channelCount == 0 ) channelCount = bp->outputChannelCount; assert( firstChannel < bp->outputChannelCount ); assert( firstChannel + channelCount <= bp->outputChannelCount ); for( i=0; i< channelCount; ++i ) { PaUtil_SetOutputChannel( bp, channel + i, p, channelCount ); p += bp->bytesPerHostOutputSample; } } void PaUtil_SetNonInterleavedOutputChannel( PaUtilBufferProcessor* bp, unsigned int channel, void *data ) { assert( channel < bp->outputChannelCount ); PaUtil_SetOutputChannel( bp, channel, data, 1 ); } void PaUtil_Set2ndOutputFrameCount( PaUtilBufferProcessor* bp, unsigned long frameCount ) { bp->hostOutputFrameCount[1] = frameCount; } void PaUtil_Set2ndOutputChannel( PaUtilBufferProcessor* bp, unsigned int channel, void *data, unsigned int stride ) { assert( channel < bp->outputChannelCount ); assert( data != NULL ); bp->hostOutputChannels[1][channel].data = data; bp->hostOutputChannels[1][channel].stride = stride; } void PaUtil_Set2ndInterleavedOutputChannels( PaUtilBufferProcessor* bp, unsigned int firstChannel, void *data, unsigned int channelCount ) { unsigned int i; unsigned int channel = firstChannel; unsigned char *p = (unsigned char*)data; if( channelCount == 0 ) channelCount = bp->outputChannelCount; assert( firstChannel < bp->outputChannelCount ); assert( firstChannel + channelCount <= bp->outputChannelCount ); for( i=0; i< channelCount; ++i ) { PaUtil_Set2ndOutputChannel( bp, channel + i, p, channelCount ); p += bp->bytesPerHostOutputSample; } } void PaUtil_Set2ndNonInterleavedOutputChannel( PaUtilBufferProcessor* bp, unsigned int channel, void *data ) { assert( channel < bp->outputChannelCount ); PaUtil_Set2ndOutputChannel( bp, channel, data, 1 ); } void PaUtil_BeginBufferProcessing( PaUtilBufferProcessor* bp, PaStreamCallbackTimeInfo* timeInfo, PaStreamCallbackFlags callbackStatusFlags ) { bp->timeInfo = timeInfo; /* the first streamCallback will be called to process samples which are currently in the input buffer before the ones starting at the timeInfo time */ bp->timeInfo->inputBufferAdcTime -= bp->framesInTempInputBuffer * bp->samplePeriod; bp->timeInfo->currentTime = 0; /** FIXME: @todo time info currentTime not implemented */ /* the first streamCallback will be called to generate samples which will be outputted after the frames currently in the output buffer have been outputted. */ bp->timeInfo->outputBufferDacTime += bp->framesInTempOutputBuffer * bp->samplePeriod; bp->callbackStatusFlags = callbackStatusFlags; bp->hostInputFrameCount[1] = 0; bp->hostOutputFrameCount[1] = 0; } /* NonAdaptingProcess() is a simple buffer copying adaptor that can handle both full and half duplex copies. It processes framesToProcess frames, broken into blocks bp->framesPerTempBuffer long. This routine can be used when the streamCallback doesn't care what length the buffers are, or when framesToProcess is an integer multiple of bp->framesPerTempBuffer, in which case streamCallback will always be called with bp->framesPerTempBuffer samples. */ static unsigned long NonAdaptingProcess( PaUtilBufferProcessor *bp, int *streamCallbackResult, PaUtilChannelDescriptor *hostInputChannels, PaUtilChannelDescriptor *hostOutputChannels, unsigned long framesToProcess ) { void *userInput, *userOutput; unsigned char *srcBytePtr, *destBytePtr; unsigned int srcSampleStrideSamples; /* stride from one sample to the next within a channel, in samples */ unsigned int srcChannelStrideBytes; /* stride from one channel to the next, in bytes */ unsigned int destSampleStrideSamples; /* stride from one sample to the next within a channel, in samples */ unsigned int destChannelStrideBytes; /* stride from one channel to the next, in bytes */ unsigned int i; unsigned long frameCount; unsigned long framesToGo = framesToProcess; unsigned long framesProcessed = 0; if( *streamCallbackResult == paContinue ) { do { frameCount = PA_MIN_( bp->framesPerTempBuffer, framesToGo ); /* configure user input buffer and convert input data (host -> user) */ if( bp->inputChannelCount == 0 ) { /* no input */ userInput = 0; } else /* there are input channels */ { /* could use more elaborate logic here and sometimes process buffers in-place. */ destBytePtr = (unsigned char *)bp->tempInputBuffer; if( bp->userInputIsInterleaved ) { destSampleStrideSamples = bp->inputChannelCount; destChannelStrideBytes = bp->bytesPerUserInputSample; userInput = bp->tempInputBuffer; } else /* user input is not interleaved */ { destSampleStrideSamples = 1; destChannelStrideBytes = frameCount * bp->bytesPerUserInputSample; /* setup non-interleaved ptrs */ for( i=0; iinputChannelCount; ++i ) { bp->tempInputBufferPtrs[i] = ((unsigned char*)bp->tempInputBuffer) + i * bp->bytesPerUserInputSample * frameCount; } userInput = bp->tempInputBufferPtrs; } if( !bp->hostInputChannels[0][0].data ) { /* no input was supplied (see PaUtil_SetNoInput), so zero the input buffer */ for( i=0; iinputChannelCount; ++i ) { bp->inputZeroer( destBytePtr, destSampleStrideSamples, frameCount ); destBytePtr += destChannelStrideBytes; /* skip to next destination channel */ } } else { for( i=0; iinputChannelCount; ++i ) { bp->inputConverter( destBytePtr, destSampleStrideSamples, hostInputChannels[i].data, hostInputChannels[i].stride, frameCount, &bp->ditherGenerator ); destBytePtr += destChannelStrideBytes; /* skip to next destination channel */ /* advance src ptr for next iteration */ hostInputChannels[i].data = ((unsigned char*)hostInputChannels[i].data) + frameCount * hostInputChannels[i].stride * bp->bytesPerHostInputSample; } } } /* configure user output buffer */ if( bp->outputChannelCount == 0 ) { /* no output */ userOutput = 0; } else /* there are output channels */ { if( bp->userOutputIsInterleaved ) { userOutput = bp->tempOutputBuffer; } else /* user output is not interleaved */ { for( i = 0; i < bp->outputChannelCount; ++i ) { bp->tempOutputBufferPtrs[i] = ((unsigned char*)bp->tempOutputBuffer) + i * bp->bytesPerUserOutputSample * frameCount; } userOutput = bp->tempOutputBufferPtrs; } } *streamCallbackResult = bp->streamCallback( userInput, userOutput, frameCount, bp->timeInfo, bp->callbackStatusFlags, bp->userData ); if( *streamCallbackResult == paAbort ) { /* callback returned paAbort, don't advance framesProcessed and framesToGo, they will be handled below */ } else { bp->timeInfo->inputBufferAdcTime += frameCount * bp->samplePeriod; bp->timeInfo->outputBufferDacTime += frameCount * bp->samplePeriod; /* convert output data (user -> host) */ if( bp->outputChannelCount != 0 && bp->hostOutputChannels[0][0].data ) { /* could use more elaborate logic here and sometimes process buffers in-place. */ srcBytePtr = (unsigned char *)bp->tempOutputBuffer; if( bp->userOutputIsInterleaved ) { srcSampleStrideSamples = bp->outputChannelCount; srcChannelStrideBytes = bp->bytesPerUserOutputSample; } else /* user output is not interleaved */ { srcSampleStrideSamples = 1; srcChannelStrideBytes = frameCount * bp->bytesPerUserOutputSample; } for( i=0; ioutputChannelCount; ++i ) { bp->outputConverter( hostOutputChannels[i].data, hostOutputChannels[i].stride, srcBytePtr, srcSampleStrideSamples, frameCount, &bp->ditherGenerator ); srcBytePtr += srcChannelStrideBytes; /* skip to next source channel */ /* advance dest ptr for next iteration */ hostOutputChannels[i].data = ((unsigned char*)hostOutputChannels[i].data) + frameCount * hostOutputChannels[i].stride * bp->bytesPerHostOutputSample; } } framesProcessed += frameCount; framesToGo -= frameCount; } } while( framesToGo > 0 && *streamCallbackResult == paContinue ); } if( framesToGo > 0 ) { /* zero any remaining frames output. There will only be remaining frames if the callback has returned paComplete or paAbort */ frameCount = framesToGo; if( bp->outputChannelCount != 0 && bp->hostOutputChannels[0][0].data ) { for( i=0; ioutputChannelCount; ++i ) { bp->outputZeroer( hostOutputChannels[i].data, hostOutputChannels[i].stride, frameCount ); /* advance dest ptr for next iteration */ hostOutputChannels[i].data = ((unsigned char*)hostOutputChannels[i].data) + frameCount * hostOutputChannels[i].stride * bp->bytesPerHostOutputSample; } } framesProcessed += frameCount; } return framesProcessed; } /* AdaptingInputOnlyProcess() is a half duplex input buffer processor. It converts data from the input buffers into the temporary input buffer, when the temporary input buffer is full, it calls the streamCallback. */ static unsigned long AdaptingInputOnlyProcess( PaUtilBufferProcessor *bp, int *streamCallbackResult, PaUtilChannelDescriptor *hostInputChannels, unsigned long framesToProcess ) { void *userInput, *userOutput; unsigned char *destBytePtr; unsigned int destSampleStrideSamples; /* stride from one sample to the next within a channel, in samples */ unsigned int destChannelStrideBytes; /* stride from one channel to the next, in bytes */ unsigned int i; unsigned long frameCount; unsigned long framesToGo = framesToProcess; unsigned long framesProcessed = 0; userOutput = 0; do { frameCount = ( bp->framesInTempInputBuffer + framesToGo > bp->framesPerUserBuffer ) ? ( bp->framesPerUserBuffer - bp->framesInTempInputBuffer ) : framesToGo; /* convert frameCount samples into temp buffer */ if( bp->userInputIsInterleaved ) { destBytePtr = ((unsigned char*)bp->tempInputBuffer) + bp->bytesPerUserInputSample * bp->inputChannelCount * bp->framesInTempInputBuffer; destSampleStrideSamples = bp->inputChannelCount; destChannelStrideBytes = bp->bytesPerUserInputSample; userInput = bp->tempInputBuffer; } else /* user input is not interleaved */ { destBytePtr = ((unsigned char*)bp->tempInputBuffer) + bp->bytesPerUserInputSample * bp->framesInTempInputBuffer; destSampleStrideSamples = 1; destChannelStrideBytes = bp->framesPerUserBuffer * bp->bytesPerUserInputSample; /* setup non-interleaved ptrs */ for( i=0; iinputChannelCount; ++i ) { bp->tempInputBufferPtrs[i] = ((unsigned char*)bp->tempInputBuffer) + i * bp->bytesPerUserInputSample * bp->framesPerUserBuffer; } userInput = bp->tempInputBufferPtrs; } for( i=0; iinputChannelCount; ++i ) { bp->inputConverter( destBytePtr, destSampleStrideSamples, hostInputChannels[i].data, hostInputChannels[i].stride, frameCount, &bp->ditherGenerator ); destBytePtr += destChannelStrideBytes; /* skip to next destination channel */ /* advance src ptr for next iteration */ hostInputChannels[i].data = ((unsigned char*)hostInputChannels[i].data) + frameCount * hostInputChannels[i].stride * bp->bytesPerHostInputSample; } bp->framesInTempInputBuffer += frameCount; if( bp->framesInTempInputBuffer == bp->framesPerUserBuffer ) { /** @todo (non-critical optimisation) The conditional below implements the continue/complete/abort mechanism simply by continuing on iterating through the input buffer, but not passing the data to the callback. With care, the outer loop could be terminated earlier, thus some unneeded conversion cycles would be saved. */ if( *streamCallbackResult == paContinue ) { bp->timeInfo->outputBufferDacTime = 0; *streamCallbackResult = bp->streamCallback( userInput, userOutput, bp->framesPerUserBuffer, bp->timeInfo, bp->callbackStatusFlags, bp->userData ); bp->timeInfo->inputBufferAdcTime += frameCount * bp->samplePeriod; } bp->framesInTempInputBuffer = 0; } framesProcessed += frameCount; framesToGo -= frameCount; }while( framesToGo > 0 ); return framesProcessed; } /* AdaptingOutputOnlyProcess() is a half duplex output buffer processor. It converts data from the temporary output buffer, to the output buffers, when the temporary output buffer is empty, it calls the streamCallback. */ static unsigned long AdaptingOutputOnlyProcess( PaUtilBufferProcessor *bp, int *streamCallbackResult, PaUtilChannelDescriptor *hostOutputChannels, unsigned long framesToProcess ) { void *userInput, *userOutput; unsigned char *srcBytePtr; unsigned int srcSampleStrideSamples; /* stride from one sample to the next within a channel, in samples */ unsigned int srcChannelStrideBytes; /* stride from one channel to the next, in bytes */ unsigned int i; unsigned long frameCount; unsigned long framesToGo = framesToProcess; unsigned long framesProcessed = 0; do { if( bp->framesInTempOutputBuffer == 0 && *streamCallbackResult == paContinue ) { userInput = 0; /* setup userOutput */ if( bp->userOutputIsInterleaved ) { userOutput = bp->tempOutputBuffer; } else /* user output is not interleaved */ { for( i = 0; i < bp->outputChannelCount; ++i ) { bp->tempOutputBufferPtrs[i] = ((unsigned char*)bp->tempOutputBuffer) + i * bp->framesPerUserBuffer * bp->bytesPerUserOutputSample; } userOutput = bp->tempOutputBufferPtrs; } bp->timeInfo->inputBufferAdcTime = 0; *streamCallbackResult = bp->streamCallback( userInput, userOutput, bp->framesPerUserBuffer, bp->timeInfo, bp->callbackStatusFlags, bp->userData ); if( *streamCallbackResult == paAbort ) { /* if the callback returned paAbort, we disregard its output */ } else { bp->timeInfo->outputBufferDacTime += bp->framesPerUserBuffer * bp->samplePeriod; bp->framesInTempOutputBuffer = bp->framesPerUserBuffer; } } if( bp->framesInTempOutputBuffer > 0 ) { /* convert frameCount frames from user buffer to host buffer */ frameCount = PA_MIN_( bp->framesInTempOutputBuffer, framesToGo ); if( bp->userOutputIsInterleaved ) { srcBytePtr = ((unsigned char*)bp->tempOutputBuffer) + bp->bytesPerUserOutputSample * bp->outputChannelCount * (bp->framesPerUserBuffer - bp->framesInTempOutputBuffer); srcSampleStrideSamples = bp->outputChannelCount; srcChannelStrideBytes = bp->bytesPerUserOutputSample; } else /* user output is not interleaved */ { srcBytePtr = ((unsigned char*)bp->tempOutputBuffer) + bp->bytesPerUserOutputSample * (bp->framesPerUserBuffer - bp->framesInTempOutputBuffer); srcSampleStrideSamples = 1; srcChannelStrideBytes = bp->framesPerUserBuffer * bp->bytesPerUserOutputSample; } for( i=0; ioutputChannelCount; ++i ) { bp->outputConverter( hostOutputChannels[i].data, hostOutputChannels[i].stride, srcBytePtr, srcSampleStrideSamples, frameCount, &bp->ditherGenerator ); srcBytePtr += srcChannelStrideBytes; /* skip to next source channel */ /* advance dest ptr for next iteration */ hostOutputChannels[i].data = ((unsigned char*)hostOutputChannels[i].data) + frameCount * hostOutputChannels[i].stride * bp->bytesPerHostOutputSample; } bp->framesInTempOutputBuffer -= frameCount; } else { /* no more user data is available because the callback has returned paComplete or paAbort. Fill the remainder of the host buffer with zeros. */ frameCount = framesToGo; for( i=0; ioutputChannelCount; ++i ) { bp->outputZeroer( hostOutputChannels[i].data, hostOutputChannels[i].stride, frameCount ); /* advance dest ptr for next iteration */ hostOutputChannels[i].data = ((unsigned char*)hostOutputChannels[i].data) + frameCount * hostOutputChannels[i].stride * bp->bytesPerHostOutputSample; } } framesProcessed += frameCount; framesToGo -= frameCount; }while( framesToGo > 0 ); return framesProcessed; } /* CopyTempOutputBuffersToHostOutputBuffers is called from AdaptingProcess to copy frames from tempOutputBuffer to hostOutputChannels. This includes data conversion and interleaving. */ static void CopyTempOutputBuffersToHostOutputBuffers( PaUtilBufferProcessor *bp) { unsigned long maxFramesToCopy; PaUtilChannelDescriptor *hostOutputChannels; unsigned int frameCount; unsigned char *srcBytePtr; unsigned int srcSampleStrideSamples; /* stride from one sample to the next within a channel, in samples */ unsigned int srcChannelStrideBytes; /* stride from one channel to the next, in bytes */ unsigned int i; /* copy frames from user to host output buffers */ while( bp->framesInTempOutputBuffer > 0 && ((bp->hostOutputFrameCount[0] + bp->hostOutputFrameCount[1]) > 0) ) { maxFramesToCopy = bp->framesInTempOutputBuffer; /* select the output buffer set (1st or 2nd) */ if( bp->hostOutputFrameCount[0] > 0 ) { hostOutputChannels = bp->hostOutputChannels[0]; frameCount = PA_MIN_( bp->hostOutputFrameCount[0], maxFramesToCopy ); } else { hostOutputChannels = bp->hostOutputChannels[1]; frameCount = PA_MIN_( bp->hostOutputFrameCount[1], maxFramesToCopy ); } if( bp->userOutputIsInterleaved ) { srcBytePtr = ((unsigned char*)bp->tempOutputBuffer) + bp->bytesPerUserOutputSample * bp->outputChannelCount * (bp->framesPerUserBuffer - bp->framesInTempOutputBuffer); srcSampleStrideSamples = bp->outputChannelCount; srcChannelStrideBytes = bp->bytesPerUserOutputSample; } else /* user output is not interleaved */ { srcBytePtr = ((unsigned char*)bp->tempOutputBuffer) + bp->bytesPerUserOutputSample * (bp->framesPerUserBuffer - bp->framesInTempOutputBuffer); srcSampleStrideSamples = 1; srcChannelStrideBytes = bp->framesPerUserBuffer * bp->bytesPerUserOutputSample; } for( i=0; ioutputChannelCount; ++i ) { assert( hostOutputChannels[i].data != NULL ); bp->outputConverter( hostOutputChannels[i].data, hostOutputChannels[i].stride, srcBytePtr, srcSampleStrideSamples, frameCount, &bp->ditherGenerator ); srcBytePtr += srcChannelStrideBytes; /* skip to next source channel */ /* advance dest ptr for next iteration */ hostOutputChannels[i].data = ((unsigned char*)hostOutputChannels[i].data) + frameCount * hostOutputChannels[i].stride * bp->bytesPerHostOutputSample; } if( bp->hostOutputFrameCount[0] > 0 ) bp->hostOutputFrameCount[0] -= frameCount; else bp->hostOutputFrameCount[1] -= frameCount; bp->framesInTempOutputBuffer -= frameCount; } } /* AdaptingProcess is a full duplex adapting buffer processor. It converts data from the temporary output buffer into the host output buffers, then from the host input buffers into the temporary input buffers. Calling the streamCallback when necessary. When processPartialUserBuffers is 0, all available input data will be consumed and all available output space will be filled. When processPartialUserBuffers is non-zero, as many full user buffers as possible will be processed, but partial buffers will not be consumed. */ static unsigned long AdaptingProcess( PaUtilBufferProcessor *bp, int *streamCallbackResult, int processPartialUserBuffers ) { void *userInput, *userOutput; unsigned long framesProcessed = 0; unsigned long framesAvailable; unsigned long endProcessingMinFrameCount; unsigned long maxFramesToCopy; PaUtilChannelDescriptor *hostInputChannels, *hostOutputChannels; unsigned int frameCount; unsigned char *destBytePtr; unsigned int destSampleStrideSamples; /* stride from one sample to the next within a channel, in samples */ unsigned int destChannelStrideBytes; /* stride from one channel to the next, in bytes */ unsigned int i, j; framesAvailable = bp->hostInputFrameCount[0] + bp->hostInputFrameCount[1];/* this is assumed to be the same as the output buffer's frame count */ if( processPartialUserBuffers ) endProcessingMinFrameCount = 0; else endProcessingMinFrameCount = (bp->framesPerUserBuffer - 1); /* Fill host output with remaining frames in user output (tempOutputBuffer) */ CopyTempOutputBuffersToHostOutputBuffers( bp ); while( framesAvailable > endProcessingMinFrameCount ) { if( bp->framesInTempOutputBuffer == 0 && *streamCallbackResult != paContinue ) { /* the callback will not be called any more, so zero what remains of the host output buffers */ for( i=0; i<2; ++i ) { frameCount = bp->hostOutputFrameCount[i]; if( frameCount > 0 ) { hostOutputChannels = bp->hostOutputChannels[i]; for( j=0; joutputChannelCount; ++j ) { bp->outputZeroer( hostOutputChannels[j].data, hostOutputChannels[j].stride, frameCount ); /* advance dest ptr for next iteration */ hostOutputChannels[j].data = ((unsigned char*)hostOutputChannels[j].data) + frameCount * hostOutputChannels[j].stride * bp->bytesPerHostOutputSample; } bp->hostOutputFrameCount[i] = 0; } } } /* copy frames from host to user input buffers */ while( bp->framesInTempInputBuffer < bp->framesPerUserBuffer && ((bp->hostInputFrameCount[0] + bp->hostInputFrameCount[1]) > 0) ) { maxFramesToCopy = bp->framesPerUserBuffer - bp->framesInTempInputBuffer; /* select the input buffer set (1st or 2nd) */ if( bp->hostInputFrameCount[0] > 0 ) { hostInputChannels = bp->hostInputChannels[0]; frameCount = PA_MIN_( bp->hostInputFrameCount[0], maxFramesToCopy ); } else { hostInputChannels = bp->hostInputChannels[1]; frameCount = PA_MIN_( bp->hostInputFrameCount[1], maxFramesToCopy ); } /* configure conversion destination pointers */ if( bp->userInputIsInterleaved ) { destBytePtr = ((unsigned char*)bp->tempInputBuffer) + bp->bytesPerUserInputSample * bp->inputChannelCount * bp->framesInTempInputBuffer; destSampleStrideSamples = bp->inputChannelCount; destChannelStrideBytes = bp->bytesPerUserInputSample; } else /* user input is not interleaved */ { destBytePtr = ((unsigned char*)bp->tempInputBuffer) + bp->bytesPerUserInputSample * bp->framesInTempInputBuffer; destSampleStrideSamples = 1; destChannelStrideBytes = bp->framesPerUserBuffer * bp->bytesPerUserInputSample; } for( i=0; iinputChannelCount; ++i ) { bp->inputConverter( destBytePtr, destSampleStrideSamples, hostInputChannels[i].data, hostInputChannels[i].stride, frameCount, &bp->ditherGenerator ); destBytePtr += destChannelStrideBytes; /* skip to next destination channel */ /* advance src ptr for next iteration */ hostInputChannels[i].data = ((unsigned char*)hostInputChannels[i].data) + frameCount * hostInputChannels[i].stride * bp->bytesPerHostInputSample; } if( bp->hostInputFrameCount[0] > 0 ) bp->hostInputFrameCount[0] -= frameCount; else bp->hostInputFrameCount[1] -= frameCount; bp->framesInTempInputBuffer += frameCount; /* update framesAvailable and framesProcessed based on input consumed unless something is very wrong this will also correspond to the amount of output generated */ framesAvailable -= frameCount; framesProcessed += frameCount; } /* call streamCallback */ if( bp->framesInTempInputBuffer == bp->framesPerUserBuffer && bp->framesInTempOutputBuffer == 0 ) { if( *streamCallbackResult == paContinue ) { /* setup userInput */ if( bp->userInputIsInterleaved ) { userInput = bp->tempInputBuffer; } else /* user input is not interleaved */ { for( i = 0; i < bp->inputChannelCount; ++i ) { bp->tempInputBufferPtrs[i] = ((unsigned char*)bp->tempInputBuffer) + i * bp->framesPerUserBuffer * bp->bytesPerUserInputSample; } userInput = bp->tempInputBufferPtrs; } /* setup userOutput */ if( bp->userOutputIsInterleaved ) { userOutput = bp->tempOutputBuffer; } else /* user output is not interleaved */ { for( i = 0; i < bp->outputChannelCount; ++i ) { bp->tempOutputBufferPtrs[i] = ((unsigned char*)bp->tempOutputBuffer) + i * bp->framesPerUserBuffer * bp->bytesPerUserOutputSample; } userOutput = bp->tempOutputBufferPtrs; } /* call streamCallback */ *streamCallbackResult = bp->streamCallback( userInput, userOutput, bp->framesPerUserBuffer, bp->timeInfo, bp->callbackStatusFlags, bp->userData ); bp->timeInfo->inputBufferAdcTime += bp->framesPerUserBuffer * bp->samplePeriod; bp->timeInfo->outputBufferDacTime += bp->framesPerUserBuffer * bp->samplePeriod; bp->framesInTempInputBuffer = 0; if( *streamCallbackResult == paAbort ) bp->framesInTempOutputBuffer = 0; else bp->framesInTempOutputBuffer = bp->framesPerUserBuffer; } else { /* paComplete or paAbort has already been called. */ bp->framesInTempInputBuffer = 0; } } /* copy frames from user (tempOutputBuffer) to host output buffers (hostOutputChannels) Means to process the user output provided by the callback. Has to be called after each callback. */ CopyTempOutputBuffersToHostOutputBuffers( bp ); } return framesProcessed; } unsigned long PaUtil_EndBufferProcessing( PaUtilBufferProcessor* bp, int *streamCallbackResult ) { unsigned long framesToProcess, framesToGo; unsigned long framesProcessed = 0; if( bp->inputChannelCount != 0 && bp->outputChannelCount != 0 && bp->hostInputChannels[0][0].data /* input was supplied (see PaUtil_SetNoInput) */ && bp->hostOutputChannels[0][0].data /* output was supplied (see PaUtil_SetNoOutput) */ ) { assert( (bp->hostInputFrameCount[0] + bp->hostInputFrameCount[1]) == (bp->hostOutputFrameCount[0] + bp->hostOutputFrameCount[1]) ); } assert( *streamCallbackResult == paContinue || *streamCallbackResult == paComplete || *streamCallbackResult == paAbort ); /* don't forget to pass in a valid callback result value */ if( bp->useNonAdaptingProcess ) { if( bp->inputChannelCount != 0 && bp->outputChannelCount != 0 ) { /* full duplex non-adapting process, splice buffers if they are different lengths */ framesToGo = bp->hostOutputFrameCount[0] + bp->hostOutputFrameCount[1]; /* relies on assert above for input/output equivalence */ do{ unsigned long noInputInputFrameCount; unsigned long *hostInputFrameCount; PaUtilChannelDescriptor *hostInputChannels; unsigned long noOutputOutputFrameCount; unsigned long *hostOutputFrameCount; PaUtilChannelDescriptor *hostOutputChannels; unsigned long framesProcessedThisIteration; if( !bp->hostInputChannels[0][0].data ) { /* no input was supplied (see PaUtil_SetNoInput) NonAdaptingProcess knows how to deal with this */ noInputInputFrameCount = framesToGo; hostInputFrameCount = &noInputInputFrameCount; hostInputChannels = 0; } else if( bp->hostInputFrameCount[0] != 0 ) { hostInputFrameCount = &bp->hostInputFrameCount[0]; hostInputChannels = bp->hostInputChannels[0]; } else { hostInputFrameCount = &bp->hostInputFrameCount[1]; hostInputChannels = bp->hostInputChannels[1]; } if( !bp->hostOutputChannels[0][0].data ) { /* no output was supplied (see PaUtil_SetNoOutput) NonAdaptingProcess knows how to deal with this */ noOutputOutputFrameCount = framesToGo; hostOutputFrameCount = &noOutputOutputFrameCount; hostOutputChannels = 0; } if( bp->hostOutputFrameCount[0] != 0 ) { hostOutputFrameCount = &bp->hostOutputFrameCount[0]; hostOutputChannels = bp->hostOutputChannels[0]; } else { hostOutputFrameCount = &bp->hostOutputFrameCount[1]; hostOutputChannels = bp->hostOutputChannels[1]; } framesToProcess = PA_MIN_( *hostInputFrameCount, *hostOutputFrameCount ); assert( framesToProcess != 0 ); framesProcessedThisIteration = NonAdaptingProcess( bp, streamCallbackResult, hostInputChannels, hostOutputChannels, framesToProcess ); *hostInputFrameCount -= framesProcessedThisIteration; *hostOutputFrameCount -= framesProcessedThisIteration; framesProcessed += framesProcessedThisIteration; framesToGo -= framesProcessedThisIteration; }while( framesToGo > 0 ); } else { /* half duplex non-adapting process, just process 1st and 2nd buffer */ /* process first buffer */ framesToProcess = (bp->inputChannelCount != 0) ? bp->hostInputFrameCount[0] : bp->hostOutputFrameCount[0]; framesProcessed = NonAdaptingProcess( bp, streamCallbackResult, bp->hostInputChannels[0], bp->hostOutputChannels[0], framesToProcess ); /* process second buffer if provided */ framesToProcess = (bp->inputChannelCount != 0) ? bp->hostInputFrameCount[1] : bp->hostOutputFrameCount[1]; if( framesToProcess > 0 ) { framesProcessed += NonAdaptingProcess( bp, streamCallbackResult, bp->hostInputChannels[1], bp->hostOutputChannels[1], framesToProcess ); } } } else /* block adaption necessary*/ { if( bp->inputChannelCount != 0 && bp->outputChannelCount != 0 ) { /* full duplex */ if( bp->hostBufferSizeMode == paUtilVariableHostBufferSizePartialUsageAllowed ) { framesProcessed = AdaptingProcess( bp, streamCallbackResult, 0 /* dont process partial user buffers */ ); } else { framesProcessed = AdaptingProcess( bp, streamCallbackResult, 1 /* process partial user buffers */ ); } } else if( bp->inputChannelCount != 0 ) { /* input only */ framesToProcess = bp->hostInputFrameCount[0]; framesProcessed = AdaptingInputOnlyProcess( bp, streamCallbackResult, bp->hostInputChannels[0], framesToProcess ); framesToProcess = bp->hostInputFrameCount[1]; if( framesToProcess > 0 ) { framesProcessed += AdaptingInputOnlyProcess( bp, streamCallbackResult, bp->hostInputChannels[1], framesToProcess ); } } else { /* output only */ framesToProcess = bp->hostOutputFrameCount[0]; framesProcessed = AdaptingOutputOnlyProcess( bp, streamCallbackResult, bp->hostOutputChannels[0], framesToProcess ); framesToProcess = bp->hostOutputFrameCount[1]; if( framesToProcess > 0 ) { framesProcessed += AdaptingOutputOnlyProcess( bp, streamCallbackResult, bp->hostOutputChannels[1], framesToProcess ); } } } return framesProcessed; } int PaUtil_IsBufferProcessorOutputEmpty( PaUtilBufferProcessor* bp ) { return (bp->framesInTempOutputBuffer) ? 0 : 1; } unsigned long PaUtil_CopyInput( PaUtilBufferProcessor* bp, void **buffer, unsigned long frameCount ) { PaUtilChannelDescriptor *hostInputChannels; unsigned int framesToCopy; unsigned char *destBytePtr; void **nonInterleavedDestPtrs; unsigned int destSampleStrideSamples; /* stride from one sample to the next within a channel, in samples */ unsigned int destChannelStrideBytes; /* stride from one channel to the next, in bytes */ unsigned int i; hostInputChannels = bp->hostInputChannels[0]; framesToCopy = PA_MIN_( bp->hostInputFrameCount[0], frameCount ); if( bp->userInputIsInterleaved ) { destBytePtr = (unsigned char*)*buffer; destSampleStrideSamples = bp->inputChannelCount; destChannelStrideBytes = bp->bytesPerUserInputSample; for( i=0; iinputChannelCount; ++i ) { bp->inputConverter( destBytePtr, destSampleStrideSamples, hostInputChannels[i].data, hostInputChannels[i].stride, framesToCopy, &bp->ditherGenerator ); destBytePtr += destChannelStrideBytes; /* skip to next source channel */ /* advance dest ptr for next iteration */ hostInputChannels[i].data = ((unsigned char*)hostInputChannels[i].data) + framesToCopy * hostInputChannels[i].stride * bp->bytesPerHostInputSample; } /* advance callers dest pointer (buffer) */ *buffer = ((unsigned char *)*buffer) + framesToCopy * bp->inputChannelCount * bp->bytesPerUserInputSample; } else { /* user input is not interleaved */ nonInterleavedDestPtrs = (void**)*buffer; destSampleStrideSamples = 1; for( i=0; iinputChannelCount; ++i ) { destBytePtr = (unsigned char*)nonInterleavedDestPtrs[i]; bp->inputConverter( destBytePtr, destSampleStrideSamples, hostInputChannels[i].data, hostInputChannels[i].stride, framesToCopy, &bp->ditherGenerator ); /* advance callers dest pointer (nonInterleavedDestPtrs[i]) */ destBytePtr += bp->bytesPerUserInputSample * framesToCopy; nonInterleavedDestPtrs[i] = destBytePtr; /* advance dest ptr for next iteration */ hostInputChannels[i].data = ((unsigned char*)hostInputChannels[i].data) + framesToCopy * hostInputChannels[i].stride * bp->bytesPerHostInputSample; } } bp->hostInputFrameCount[0] -= framesToCopy; return framesToCopy; } unsigned long PaUtil_CopyOutput( PaUtilBufferProcessor* bp, const void ** buffer, unsigned long frameCount ) { PaUtilChannelDescriptor *hostOutputChannels; unsigned int framesToCopy; unsigned char *srcBytePtr; void **nonInterleavedSrcPtrs; unsigned int srcSampleStrideSamples; /* stride from one sample to the next within a channel, in samples */ unsigned int srcChannelStrideBytes; /* stride from one channel to the next, in bytes */ unsigned int i; hostOutputChannels = bp->hostOutputChannels[0]; framesToCopy = PA_MIN_( bp->hostOutputFrameCount[0], frameCount ); if( bp->userOutputIsInterleaved ) { srcBytePtr = (unsigned char*)*buffer; srcSampleStrideSamples = bp->outputChannelCount; srcChannelStrideBytes = bp->bytesPerUserOutputSample; for( i=0; ioutputChannelCount; ++i ) { bp->outputConverter( hostOutputChannels[i].data, hostOutputChannels[i].stride, srcBytePtr, srcSampleStrideSamples, framesToCopy, &bp->ditherGenerator ); srcBytePtr += srcChannelStrideBytes; /* skip to next source channel */ /* advance dest ptr for next iteration */ hostOutputChannels[i].data = ((unsigned char*)hostOutputChannels[i].data) + framesToCopy * hostOutputChannels[i].stride * bp->bytesPerHostOutputSample; } /* advance callers source pointer (buffer) */ *buffer = ((unsigned char *)*buffer) + framesToCopy * bp->outputChannelCount * bp->bytesPerUserOutputSample; } else { /* user output is not interleaved */ nonInterleavedSrcPtrs = (void**)*buffer; srcSampleStrideSamples = 1; for( i=0; ioutputChannelCount; ++i ) { srcBytePtr = (unsigned char*)nonInterleavedSrcPtrs[i]; bp->outputConverter( hostOutputChannels[i].data, hostOutputChannels[i].stride, srcBytePtr, srcSampleStrideSamples, framesToCopy, &bp->ditherGenerator ); /* advance callers source pointer (nonInterleavedSrcPtrs[i]) */ srcBytePtr += bp->bytesPerUserOutputSample * framesToCopy; nonInterleavedSrcPtrs[i] = srcBytePtr; /* advance dest ptr for next iteration */ hostOutputChannels[i].data = ((unsigned char*)hostOutputChannels[i].data) + framesToCopy * hostOutputChannels[i].stride * bp->bytesPerHostOutputSample; } } bp->hostOutputFrameCount[0] += framesToCopy; return framesToCopy; } unsigned long PaUtil_ZeroOutput( PaUtilBufferProcessor* bp, unsigned long frameCount ) { PaUtilChannelDescriptor *hostOutputChannels; unsigned int framesToZero; unsigned int i; hostOutputChannels = bp->hostOutputChannels[0]; framesToZero = PA_MIN_( bp->hostOutputFrameCount[0], frameCount ); for( i=0; ioutputChannelCount; ++i ) { bp->outputZeroer( hostOutputChannels[i].data, hostOutputChannels[i].stride, framesToZero ); /* advance dest ptr for next iteration */ hostOutputChannels[i].data = ((unsigned char*)hostOutputChannels[i].data) + framesToZero * hostOutputChannels[i].stride * bp->bytesPerHostOutputSample; } bp->hostOutputFrameCount[0] += framesToZero; return framesToZero; } sources_5316/external/portaudio/pa_unix_oss.c0000644000176700017670000020475610711210246020256 0ustar paulpaul/* * $Id: pa_unix_oss.c 1296 2007-10-28 22:43:50Z aknudsen $ * PortAudio Portable Real-Time Audio Library * Latest Version at: http://www.portaudio.com * OSS implementation by: * Douglas Repetto * Phil Burk * Dominic Mazzoni * Arve Knudsen * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostapi_src */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #ifdef HAVE_SYS_SOUNDCARD_H # include # define DEVICE_NAME_BASE "/dev/dsp" #elif defined(HAVE_LINUX_SOUNDCARD_H) # include # define DEVICE_NAME_BASE "/dev/dsp" #elif defined(HAVE_MACHINE_SOUNDCARD_H) # include /* JH20010905 */ # define DEVICE_NAME_BASE "/dev/audio" #else # error No sound card header file #endif #include "portaudio.h" #include "pa_util.h" #include "pa_allocation.h" #include "pa_hostapi.h" #include "pa_stream.h" #include "pa_cpuload.h" #include "pa_process.h" #include "pa_unix_util.h" #include "pa_debugprint.h" static int sysErr_; static pthread_t mainThread_; /* Check return value of system call, and map it to PaError */ #define ENSURE_(expr, code) \ do { \ if( UNLIKELY( (sysErr_ = (expr)) < 0 ) ) \ { \ /* PaUtil_SetLastHostErrorInfo should only be used in the main thread */ \ if( (code) == paUnanticipatedHostError && pthread_self() == mainThread_ ) \ { \ PaUtil_SetLastHostErrorInfo( paALSA, sysErr_, strerror( errno ) ); \ } \ \ PaUtil_DebugPrint(( "Expression '" #expr "' failed in '" __FILE__ "', line: " STRINGIZE( __LINE__ ) "\n" )); \ result = (code); \ goto error; \ } \ } while( 0 ); #ifndef AFMT_S16_NE #define AFMT_S16_NE Get_AFMT_S16_NE() /********************************************************************* * Some versions of OSS do not define AFMT_S16_NE. So check CPU. * PowerPC is Big Endian. X86 is Little Endian. */ static int Get_AFMT_S16_NE( void ) { long testData = 1; char *ptr = (char *) &testData; int isLittle = ( *ptr == 1 ); /* Does address point to least significant byte? */ return isLittle ? AFMT_S16_LE : AFMT_S16_BE; } #endif /* PaOSSHostApiRepresentation - host api datastructure specific to this implementation */ typedef struct { PaUtilHostApiRepresentation inheritedHostApiRep; PaUtilStreamInterface callbackStreamInterface; PaUtilStreamInterface blockingStreamInterface; PaUtilAllocationGroup *allocations; PaHostApiIndex hostApiIndex; } PaOSSHostApiRepresentation; /** Per-direction structure for PaOssStream. * * Aspect StreamChannels: In case the user requests to open the same device for both capture and playback, * but with different number of channels we will have to adapt between the number of user and host * channels for at least one direction, since the configuration space is the same for both directions * of an OSS device. */ typedef struct { int fd; const char *devName; int userChannelCount, hostChannelCount; int userInterleaved; void *buffer; PaSampleFormat userFormat, hostFormat; double latency; unsigned long hostFrames, numBufs; void **userBuffers; /* For non-interleaved blocking */ } PaOssStreamComponent; /** Implementation specific representation of a PaStream. * */ typedef struct PaOssStream { PaUtilStreamRepresentation streamRepresentation; PaUtilCpuLoadMeasurer cpuLoadMeasurer; PaUtilBufferProcessor bufferProcessor; PaUtilThreading threading; int sharedDevice; unsigned long framesPerHostBuffer; int triggered; /* Have the devices been triggered yet (first start) */ int isActive; int isStopped; int lastPosPtr; double lastStreamBytes; int framesProcessed; double sampleRate; int callbackMode; int callbackStop, callbackAbort; PaOssStreamComponent *capture, *playback; unsigned long pollTimeout; sem_t semaphore; } PaOssStream; typedef enum { StreamMode_In, StreamMode_Out } StreamMode; /* prototypes for functions declared in this file */ static void Terminate( struct PaUtilHostApiRepresentation *hostApi ); static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ); static PaError CloseStream( PaStream* stream ); static PaError StartStream( PaStream *stream ); static PaError StopStream( PaStream *stream ); static PaError AbortStream( PaStream *stream ); static PaError IsStreamStopped( PaStream *s ); static PaError IsStreamActive( PaStream *stream ); static PaTime GetStreamTime( PaStream *stream ); static double GetStreamCpuLoad( PaStream* stream ); static PaError ReadStream( PaStream* stream, void *buffer, unsigned long frames ); static PaError WriteStream( PaStream* stream, const void *buffer, unsigned long frames ); static signed long GetStreamReadAvailable( PaStream* stream ); static signed long GetStreamWriteAvailable( PaStream* stream ); static PaError BuildDeviceList( PaOSSHostApiRepresentation *hostApi ); /** Initialize the OSS API implementation. * * This function will initialize host API datastructures and query host devices for information. * * Aspect DeviceCapabilities: Enumeration of host API devices is initiated from here * * Aspect FreeResources: If an error is encountered under way we have to free each resource allocated in this function, * this happens with the usual "error" label. */ PaError PaOSS_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex hostApiIndex ) { PaError result = paNoError; PaOSSHostApiRepresentation *ossHostApi = NULL; PA_UNLESS( ossHostApi = (PaOSSHostApiRepresentation*)PaUtil_AllocateMemory( sizeof(PaOSSHostApiRepresentation) ), paInsufficientMemory ); PA_UNLESS( ossHostApi->allocations = PaUtil_CreateAllocationGroup(), paInsufficientMemory ); ossHostApi->hostApiIndex = hostApiIndex; /* Initialize host API structure */ *hostApi = &ossHostApi->inheritedHostApiRep; (*hostApi)->info.structVersion = 1; (*hostApi)->info.type = paOSS; (*hostApi)->info.name = "OSS"; (*hostApi)->Terminate = Terminate; (*hostApi)->OpenStream = OpenStream; (*hostApi)->IsFormatSupported = IsFormatSupported; PA_ENSURE( BuildDeviceList( ossHostApi ) ); PaUtil_InitializeStreamInterface( &ossHostApi->callbackStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, GetStreamCpuLoad, PaUtil_DummyRead, PaUtil_DummyWrite, PaUtil_DummyGetReadAvailable, PaUtil_DummyGetWriteAvailable ); PaUtil_InitializeStreamInterface( &ossHostApi->blockingStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, PaUtil_DummyGetCpuLoad, ReadStream, WriteStream, GetStreamReadAvailable, GetStreamWriteAvailable ); mainThread_ = pthread_self(); return result; error: if( ossHostApi ) { if( ossHostApi->allocations ) { PaUtil_FreeAllAllocations( ossHostApi->allocations ); PaUtil_DestroyAllocationGroup( ossHostApi->allocations ); } PaUtil_FreeMemory( ossHostApi ); } return result; } PaError PaUtil_InitializeDeviceInfo( PaDeviceInfo *deviceInfo, const char *name, PaHostApiIndex hostApiIndex, int maxInputChannels, int maxOutputChannels, PaTime defaultLowInputLatency, PaTime defaultLowOutputLatency, PaTime defaultHighInputLatency, PaTime defaultHighOutputLatency, double defaultSampleRate, PaUtilAllocationGroup *allocations ) { PaError result = paNoError; deviceInfo->structVersion = 2; if( allocations ) { size_t len = strlen( name ) + 1; PA_UNLESS( deviceInfo->name = PaUtil_GroupAllocateMemory( allocations, len ), paInsufficientMemory ); strncpy( (char *)deviceInfo->name, name, len ); } else deviceInfo->name = name; deviceInfo->hostApi = hostApiIndex; deviceInfo->maxInputChannels = maxInputChannels; deviceInfo->maxOutputChannels = maxOutputChannels; deviceInfo->defaultLowInputLatency = defaultLowInputLatency; deviceInfo->defaultLowOutputLatency = defaultLowOutputLatency; deviceInfo->defaultHighInputLatency = defaultHighInputLatency; deviceInfo->defaultHighOutputLatency = defaultHighOutputLatency; deviceInfo->defaultSampleRate = defaultSampleRate; error: return result; } static PaError QueryDirection( const char *deviceName, StreamMode mode, double *defaultSampleRate, int *maxChannelCount, double *defaultLowLatency, double *defaultHighLatency ) { PaError result = paNoError; int numChannels, maxNumChannels; int busy = 0; int devHandle = -1; int sr; *maxChannelCount = 0; /* Default value in case this fails */ if ( (devHandle = open( deviceName, (mode == StreamMode_In ? O_RDONLY : O_WRONLY) | O_NONBLOCK )) < 0 ) { if( errno == EBUSY || errno == EAGAIN ) { PA_DEBUG(( "%s: Device %s busy\n", __FUNCTION__, deviceName )); } else { PA_DEBUG(( "%s: Can't access device: %s\n", __FUNCTION__, strerror( errno ) )); } return paDeviceUnavailable; } /* Negotiate for the maximum number of channels for this device. PLB20010927 * Consider up to 16 as the upper number of channels. * Variable maxNumChannels should contain the actual upper limit after the call. * Thanks to John Lazzaro and Heiko Purnhagen for suggestions. */ maxNumChannels = 0; for( numChannels = 1; numChannels <= 16; numChannels++ ) { int temp = numChannels; if( ioctl( devHandle, SNDCTL_DSP_CHANNELS, &temp ) < 0 ) { busy = EAGAIN == errno || EBUSY == errno; /* ioctl() failed so bail out if we already have stereo */ if( maxNumChannels >= 2 ) break; } else { /* ioctl() worked but bail out if it does not support numChannels. * We don't want to leave gaps in the numChannels supported. */ if( (numChannels > 2) && (temp != numChannels) ) break; if( temp > maxNumChannels ) maxNumChannels = temp; /* Save maximum. */ } } /* A: We're able to open a device for capture if it's busy playing back and vice versa, * but we can't configure anything */ if( 0 == maxNumChannels && busy ) { result = paDeviceUnavailable; goto error; } /* The above negotiation may fail for an old driver so try this older technique. */ if( maxNumChannels < 1 ) { int stereo = 1; if( ioctl( devHandle, SNDCTL_DSP_STEREO, &stereo ) < 0 ) { maxNumChannels = 1; } else { maxNumChannels = (stereo) ? 2 : 1; } PA_DEBUG(( "%s: use SNDCTL_DSP_STEREO, maxNumChannels = %d\n", __FUNCTION__, maxNumChannels )); } /* During channel negotiation, the last ioctl() may have failed. This can * also cause sample rate negotiation to fail. Hence the following, to return * to a supported number of channels. SG20011005 */ { /* use most reasonable default value */ int temp = PA_MIN( maxNumChannels, 2 ); ENSURE_( ioctl( devHandle, SNDCTL_DSP_CHANNELS, &temp ), paUnanticipatedHostError ); } /* Get supported sample rate closest to 44100 Hz */ if( *defaultSampleRate < 0 ) { sr = 44100; if( ioctl( devHandle, SNDCTL_DSP_SPEED, &sr ) < 0 ) { result = paUnanticipatedHostError; goto error; } *defaultSampleRate = sr; } *maxChannelCount = maxNumChannels; /* TODO */ *defaultLowLatency = 512. / *defaultSampleRate; *defaultHighLatency = 2048. / *defaultSampleRate; error: if( devHandle >= 0 ) close( devHandle ); return result; } /** Query OSS device. * * This is where PaDeviceInfo objects are constructed and filled in with relevant information. * * Aspect DeviceCapabilities: The inferred device capabilities are recorded in a PaDeviceInfo object that is constructed * in place. */ static PaError QueryDevice( char *deviceName, PaOSSHostApiRepresentation *ossApi, PaDeviceInfo **deviceInfo ) { PaError result = paNoError; double sampleRate = -1.; int maxInputChannels, maxOutputChannels; PaTime defaultLowInputLatency, defaultLowOutputLatency, defaultHighInputLatency, defaultHighOutputLatency; PaError tmpRes = paNoError; int busy = 0; *deviceInfo = NULL; /* douglas: we have to do this querying in a slightly different order. apparently some sound cards will give you different info based on their settins. e.g. a card might give you stereo at 22kHz but only mono at 44kHz. the correct order for OSS is: format, channels, sample rate */ /* Aspect StreamChannels: The number of channels supported for a device may depend on the mode it is * opened in, it may have more channels available for capture than playback and vice versa. Therefore * we will open the device in both read- and write-only mode to determine the supported number. */ if( (tmpRes = QueryDirection( deviceName, StreamMode_In, &sampleRate, &maxInputChannels, &defaultLowInputLatency, &defaultHighInputLatency )) != paNoError ) { if( tmpRes != paDeviceUnavailable ) { PA_DEBUG(( "%s: Querying device %s for capture failed!\n", __FUNCTION__, deviceName )); /* PA_ENSURE( tmpRes ); */ } ++busy; } if( (tmpRes = QueryDirection( deviceName, StreamMode_Out, &sampleRate, &maxOutputChannels, &defaultLowOutputLatency, &defaultHighOutputLatency )) != paNoError ) { if( tmpRes != paDeviceUnavailable ) { PA_DEBUG(( "%s: Querying device %s for playback failed!\n", __FUNCTION__, deviceName )); /* PA_ENSURE( tmpRes ); */ } ++busy; } assert( 0 <= busy && busy <= 2 ); if( 2 == busy ) /* Both directions are unavailable to us */ { result = paDeviceUnavailable; goto error; } PA_UNLESS( *deviceInfo = PaUtil_GroupAllocateMemory( ossApi->allocations, sizeof (PaDeviceInfo) ), paInsufficientMemory ); PA_ENSURE( PaUtil_InitializeDeviceInfo( *deviceInfo, deviceName, ossApi->hostApiIndex, maxInputChannels, maxOutputChannels, defaultLowInputLatency, defaultLowOutputLatency, defaultHighInputLatency, defaultHighOutputLatency, sampleRate, ossApi->allocations ) ); error: return result; } /** Query host devices. * * Loop over host devices and query their capabilitiesu * * Aspect DeviceCapabilities: This function calls QueryDevice on each device entry and receives a filled in PaDeviceInfo object * per device, these are placed in the host api representation's deviceInfos array. */ static PaError BuildDeviceList( PaOSSHostApiRepresentation *ossApi ) { PaError result = paNoError; PaUtilHostApiRepresentation *commonApi = &ossApi->inheritedHostApiRep; int i; int numDevices = 0, maxDeviceInfos = 1; PaDeviceInfo **deviceInfos = NULL; /* These two will be set to the first working input and output device, respectively */ commonApi->info.defaultInputDevice = paNoDevice; commonApi->info.defaultOutputDevice = paNoDevice; /* Find devices by calling QueryDevice on each * potential device names. When we find a valid one, * add it to a linked list. * A: Set an arbitrary of 100 devices, should probably be a smarter way. */ for( i = 0; i < 100; i++ ) { char deviceName[32]; PaDeviceInfo *deviceInfo; int testResult; struct stat stbuf; if( i == 0 ) snprintf(deviceName, sizeof (deviceName), "%s", DEVICE_NAME_BASE); else snprintf(deviceName, sizeof (deviceName), "%s%d", DEVICE_NAME_BASE, i); /* PA_DEBUG(("PaOSS BuildDeviceList: trying device %s\n", deviceName )); */ if( stat( deviceName, &stbuf ) < 0 ) { if( ENOENT != errno ) PA_DEBUG(( "%s: Error stat'ing %s: %s\n", __FUNCTION__, deviceName, strerror( errno ) )); continue; } if( (testResult = QueryDevice( deviceName, ossApi, &deviceInfo )) != paNoError ) { if( testResult != paDeviceUnavailable ) PA_ENSURE( testResult ); continue; } ++numDevices; if( !deviceInfos || numDevices > maxDeviceInfos ) { maxDeviceInfos *= 2; PA_UNLESS( deviceInfos = (PaDeviceInfo **) realloc( deviceInfos, maxDeviceInfos * sizeof (PaDeviceInfo *) ), paInsufficientMemory ); } { int devIdx = numDevices - 1; deviceInfos[devIdx] = deviceInfo; if( commonApi->info.defaultInputDevice == paNoDevice && deviceInfo->maxInputChannels > 0 ) commonApi->info.defaultInputDevice = devIdx; if( commonApi->info.defaultOutputDevice == paNoDevice && deviceInfo->maxOutputChannels > 0 ) commonApi->info.defaultOutputDevice = devIdx; } } /* Make an array of PaDeviceInfo pointers out of the linked list */ PA_DEBUG(("PaOSS %s: Total number of devices found: %d\n", __FUNCTION__, numDevices)); commonApi->deviceInfos = (PaDeviceInfo**)PaUtil_GroupAllocateMemory( ossApi->allocations, sizeof(PaDeviceInfo*) * numDevices ); memcpy( commonApi->deviceInfos, deviceInfos, numDevices * sizeof (PaDeviceInfo *) ); commonApi->info.deviceCount = numDevices; error: free( deviceInfos ); return result; } static void Terminate( struct PaUtilHostApiRepresentation *hostApi ) { PaOSSHostApiRepresentation *ossHostApi = (PaOSSHostApiRepresentation*)hostApi; if( ossHostApi->allocations ) { PaUtil_FreeAllAllocations( ossHostApi->allocations ); PaUtil_DestroyAllocationGroup( ossHostApi->allocations ); } PaUtil_FreeMemory( ossHostApi ); } static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ) { PaError result = paNoError; PaDeviceIndex device; PaDeviceInfo *deviceInfo; char *deviceName; int inputChannelCount, outputChannelCount; int tempDevHandle = -1; int flags; PaSampleFormat inputSampleFormat, outputSampleFormat; if( inputParameters ) { inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that input device can support inputChannelCount */ if( inputChannelCount > hostApi->deviceInfos[ inputParameters->device ]->maxInputChannels ) return paInvalidChannelCount; /* validate inputStreamInfo */ if( inputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ } else { inputChannelCount = 0; } if( outputParameters ) { outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that output device can support inputChannelCount */ if( outputChannelCount > hostApi->deviceInfos[ outputParameters->device ]->maxOutputChannels ) return paInvalidChannelCount; /* validate outputStreamInfo */ if( outputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ } else { outputChannelCount = 0; } if (inputChannelCount == 0 && outputChannelCount == 0) return paInvalidChannelCount; /* if full duplex, make sure that they're the same device */ if (inputChannelCount > 0 && outputChannelCount > 0 && inputParameters->device != outputParameters->device) return paInvalidDevice; /* if full duplex, also make sure that they're the same number of channels */ if (inputChannelCount > 0 && outputChannelCount > 0 && inputChannelCount != outputChannelCount) return paInvalidChannelCount; /* open the device so we can do more tests */ if( inputChannelCount > 0 ) { result = PaUtil_DeviceIndexToHostApiDeviceIndex(&device, inputParameters->device, hostApi); if (result != paNoError) return result; } else { result = PaUtil_DeviceIndexToHostApiDeviceIndex(&device, outputParameters->device, hostApi); if (result != paNoError) return result; } deviceInfo = hostApi->deviceInfos[device]; deviceName = (char *)deviceInfo->name; flags = O_NONBLOCK; if (inputChannelCount > 0 && outputChannelCount > 0) flags |= O_RDWR; else if (inputChannelCount > 0) flags |= O_RDONLY; else flags |= O_WRONLY; ENSURE_( tempDevHandle = open( deviceInfo->name, flags ), paDeviceUnavailable ); /* PaOssStream_Configure will do the rest of the checking for us */ /* PA_ENSURE( PaOssStream_Configure( tempDevHandle, deviceName, outputChannelCount, &sampleRate ) ); */ /* everything succeeded! */ error: if( tempDevHandle >= 0 ) close( tempDevHandle ); return result; } /** Validate stream parameters. * * Aspect StreamChannels: We verify that the number of channels is within the allowed range for the device */ static PaError ValidateParameters( const PaStreamParameters *parameters, const PaDeviceInfo *deviceInfo, StreamMode mode ) { int maxChans; assert( parameters ); if( parameters->device == paUseHostApiSpecificDeviceSpecification ) { return paInvalidDevice; } maxChans = (mode == StreamMode_In ? deviceInfo->maxInputChannels : deviceInfo->maxOutputChannels); if( parameters->channelCount > maxChans ) { return paInvalidChannelCount; } return paNoError; } static PaError PaOssStreamComponent_Initialize( PaOssStreamComponent *component, const PaStreamParameters *parameters, int callbackMode, int fd, const char *deviceName ) { PaError result = paNoError; assert( component ); memset( component, 0, sizeof (PaOssStreamComponent) ); component->fd = fd; component->devName = deviceName; component->userChannelCount = parameters->channelCount; component->userFormat = parameters->sampleFormat; component->latency = parameters->suggestedLatency; component->userInterleaved = !(parameters->sampleFormat & paNonInterleaved); if( !callbackMode && !component->userInterleaved ) { /* Pre-allocate non-interleaved user provided buffers */ PA_UNLESS( component->userBuffers = PaUtil_AllocateMemory( sizeof (void *) * component->userChannelCount ), paInsufficientMemory ); } error: return result; } static void PaOssStreamComponent_Terminate( PaOssStreamComponent *component ) { assert( component ); if( component->fd >= 0 ) close( component->fd ); if( component->buffer ) PaUtil_FreeMemory( component->buffer ); if( component->userBuffers ) PaUtil_FreeMemory( component->userBuffers ); PaUtil_FreeMemory( component ); } static PaError ModifyBlocking( int fd, int blocking ) { PaError result = paNoError; int fflags; ENSURE_( fflags = fcntl( fd, F_GETFL ), paUnanticipatedHostError ); if( blocking ) fflags &= ~O_NONBLOCK; else fflags |= O_NONBLOCK; ENSURE_( fcntl( fd, F_SETFL, fflags ), paUnanticipatedHostError ); error: return result; } static PaError OpenDevices( const char *idevName, const char *odevName, int *idev, int *odev ) { PaError result = paNoError; int flags = O_NONBLOCK, duplex = 0; int enableBits = 0; *idev = *odev = -1; if( idevName && odevName ) { duplex = 1; flags |= O_RDWR; } else if( idevName ) flags |= O_RDONLY; else flags |= O_WRONLY; /* open first in nonblocking mode, in case it's busy... * A: then unset the non-blocking attribute */ assert( flags & O_NONBLOCK ); if( idevName ) { ENSURE_( *idev = open( idevName, flags ), paDeviceUnavailable ); PA_ENSURE( ModifyBlocking( *idev, 1 ) ); /* Blocking */ /* Initially disable */ enableBits = ~PCM_ENABLE_INPUT; ENSURE_( ioctl( *idev, SNDCTL_DSP_SETTRIGGER, &enableBits ), paUnanticipatedHostError ); } if( odevName ) { if( !idevName ) { ENSURE_( *odev = open( odevName, flags ), paDeviceUnavailable ); PA_ENSURE( ModifyBlocking( *odev, 1 ) ); /* Blocking */ /* Initially disable */ enableBits = ~PCM_ENABLE_OUTPUT; ENSURE_( ioctl( *odev, SNDCTL_DSP_SETTRIGGER, &enableBits ), paUnanticipatedHostError ); } else { ENSURE_( *odev = dup( *idev ), paUnanticipatedHostError ); } } error: return result; } static PaError PaOssStream_Initialize( PaOssStream *stream, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, PaStreamCallback callback, void *userData, PaStreamFlags streamFlags, PaOSSHostApiRepresentation *ossApi ) { PaError result = paNoError; int idev, odev; PaUtilHostApiRepresentation *hostApi = &ossApi->inheritedHostApiRep; const char *idevName = NULL, *odevName = NULL; assert( stream ); memset( stream, 0, sizeof (PaOssStream) ); stream->isStopped = 1; PA_ENSURE( PaUtil_InitializeThreading( &stream->threading ) ); if( inputParameters && outputParameters ) { if( inputParameters->device == outputParameters->device ) stream->sharedDevice = 1; } if( inputParameters ) idevName = hostApi->deviceInfos[inputParameters->device]->name; if( outputParameters ) odevName = hostApi->deviceInfos[outputParameters->device]->name; PA_ENSURE( OpenDevices( idevName, odevName, &idev, &odev ) ); if( inputParameters ) { PA_UNLESS( stream->capture = PaUtil_AllocateMemory( sizeof (PaOssStreamComponent) ), paInsufficientMemory ); PA_ENSURE( PaOssStreamComponent_Initialize( stream->capture, inputParameters, callback != NULL, idev, idevName ) ); } if( outputParameters ) { PA_UNLESS( stream->playback = PaUtil_AllocateMemory( sizeof (PaOssStreamComponent) ), paInsufficientMemory ); PA_ENSURE( PaOssStreamComponent_Initialize( stream->playback, outputParameters, callback != NULL, odev, odevName ) ); } if( callback != NULL ) { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &ossApi->callbackStreamInterface, callback, userData ); stream->callbackMode = 1; } else { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &ossApi->blockingStreamInterface, callback, userData ); } ENSURE_( sem_init( &stream->semaphore, 0, 0 ), paInternalError ); error: return result; } static void PaOssStream_Terminate( PaOssStream *stream ) { assert( stream ); PaUtil_TerminateStreamRepresentation( &stream->streamRepresentation ); PaUtil_TerminateThreading( &stream->threading ); if( stream->capture ) PaOssStreamComponent_Terminate( stream->capture ); if( stream->playback ) PaOssStreamComponent_Terminate( stream->playback ); sem_destroy( &stream->semaphore ); PaUtil_FreeMemory( stream ); } /** Translate from PA format to OSS native. * */ static PaError Pa2OssFormat( PaSampleFormat paFormat, int *ossFormat ) { switch( paFormat ) { case paUInt8: *ossFormat = AFMT_U8; break; case paInt8: *ossFormat = AFMT_S8; break; case paInt16: *ossFormat = AFMT_S16_NE; break; default: return paInternalError; /* This shouldn't happen */ } return paNoError; } /** Return the PA-compatible formats that this device can support. * */ static PaError GetAvailableFormats( PaOssStreamComponent *component, PaSampleFormat *availableFormats ) { PaError result = paNoError; int mask = 0; PaSampleFormat frmts = 0; ENSURE_( ioctl( component->fd, SNDCTL_DSP_GETFMTS, &mask ), paUnanticipatedHostError ); if( mask & AFMT_U8 ) frmts |= paUInt8; if( mask & AFMT_S8 ) frmts |= paInt8; if( mask & AFMT_S16_NE ) frmts |= paInt16; else result = paSampleFormatNotSupported; *availableFormats = frmts; error: return result; } static unsigned int PaOssStreamComponent_FrameSize( PaOssStreamComponent *component ) { return Pa_GetSampleSize( component->hostFormat ) * component->hostChannelCount; } /** Buffer size in bytes. * */ static unsigned long PaOssStreamComponent_BufferSize( PaOssStreamComponent *component ) { return PaOssStreamComponent_FrameSize( component ) * component->hostFrames * component->numBufs; } static int CalcHigherLogTwo( int n ) { int log2 = 0; while( (1<userChannelCount; int frgmt; int numBufs; int bytesPerBuf; unsigned long bufSz; unsigned long fragSz; audio_buf_info bufInfo; /* We may have a situation where only one component (the master) is configured, if both point to the same device. * In that case, the second component will copy settings from the other */ if( !master ) { /* Aspect BufferSettings: If framesPerBuffer is unspecified we have to infer a suitable fragment size. * The hardware need not respect the requested fragment size, so we may have to adapt. */ if( framesPerBuffer == paFramesPerBufferUnspecified ) { bufSz = (unsigned long)(component->latency * sampleRate); fragSz = bufSz / 4; } else { fragSz = framesPerBuffer; bufSz = (unsigned long)(component->latency * sampleRate) + fragSz; /* Latency + 1 buffer */ } PA_ENSURE( GetAvailableFormats( component, &availableFormats ) ); hostFormat = PaUtil_SelectClosestAvailableFormat( availableFormats, component->userFormat ); /* OSS demands at least 2 buffers, and 16 bytes per buffer */ numBufs = (int)PA_MAX( bufSz / fragSz, 2 ); bytesPerBuf = PA_MAX( fragSz * Pa_GetSampleSize( hostFormat ) * chans, 16 ); /* The fragment parameters are encoded like this: * Most significant byte: number of fragments * Least significant byte: exponent of fragment size (i.e., for 256, 8) */ frgmt = (numBufs << 16) + (CalcHigherLogTwo( bytesPerBuf ) & 0xffff); ENSURE_( ioctl( component->fd, SNDCTL_DSP_SETFRAGMENT, &frgmt ), paUnanticipatedHostError ); /* A: according to the OSS programmer's guide parameters should be set in this order: * format, channels, rate */ /* This format should be deemed good before we get this far */ PA_ENSURE( Pa2OssFormat( hostFormat, &temp ) ); nativeFormat = temp; ENSURE_( ioctl( component->fd, SNDCTL_DSP_SETFMT, &temp ), paUnanticipatedHostError ); PA_UNLESS( temp == nativeFormat, paInternalError ); /* try to set the number of channels */ ENSURE_( ioctl( component->fd, SNDCTL_DSP_CHANNELS, &chans ), paSampleFormatNotSupported ); /* XXX: Should be paInvalidChannelCount? */ /* It's possible that the minimum number of host channels is greater than what the user requested */ PA_UNLESS( chans >= component->userChannelCount, paInvalidChannelCount ); /* try to set the sample rate */ ENSURE_( ioctl( component->fd, SNDCTL_DSP_SPEED, &sr ), paInvalidSampleRate ); /* reject if there's no sample rate within 1% of the one requested */ if( (fabs( sampleRate - sr ) / sampleRate) > 0.01 ) { PA_DEBUG(("%s: Wanted %f, closest sample rate was %d\n", __FUNCTION__, sampleRate, sr )); PA_ENSURE( paInvalidSampleRate ); } ENSURE_( ioctl( component->fd, streamMode == StreamMode_In ? SNDCTL_DSP_GETISPACE : SNDCTL_DSP_GETOSPACE, &bufInfo ), paUnanticipatedHostError ); component->numBufs = bufInfo.fragstotal; /* This needs to be the last ioctl call before the first read/write, according to the OSS programmer's guide */ ENSURE_( ioctl( component->fd, SNDCTL_DSP_GETBLKSIZE, &bytesPerBuf ), paUnanticipatedHostError ); component->hostFrames = bytesPerBuf / Pa_GetSampleSize( hostFormat ) / chans; component->hostChannelCount = chans; component->hostFormat = hostFormat; } else { component->hostFormat = master->hostFormat; component->hostFrames = master->hostFrames; component->hostChannelCount = master->hostChannelCount; component->numBufs = master->numBufs; } PA_UNLESS( component->buffer = PaUtil_AllocateMemory( PaOssStreamComponent_BufferSize( component ) ), paInsufficientMemory ); error: return result; } static PaError PaOssStreamComponent_Read( PaOssStreamComponent *component, unsigned long *frames ) { PaError result = paNoError; size_t len = *frames * PaOssStreamComponent_FrameSize( component ); ssize_t bytesRead; ENSURE_( bytesRead = read( component->fd, component->buffer, len ), paUnanticipatedHostError ); *frames = bytesRead / PaOssStreamComponent_FrameSize( component ); /* TODO: Handle condition where number of frames read doesn't equal number of frames requested */ error: return result; } static PaError PaOssStreamComponent_Write( PaOssStreamComponent *component, unsigned long *frames ) { PaError result = paNoError; size_t len = *frames * PaOssStreamComponent_FrameSize( component ); ssize_t bytesWritten; ENSURE_( bytesWritten = write( component->fd, component->buffer, len ), paUnanticipatedHostError ); *frames = bytesWritten / PaOssStreamComponent_FrameSize( component ); /* TODO: Handle condition where number of frames written doesn't equal number of frames requested */ error: return result; } /** Configure the stream according to input/output parameters. * * Aspect StreamChannels: The minimum number of channels supported by the device may exceed that requested by * the user, if so we'll record the actual number of host channels and adapt later. */ static PaError PaOssStream_Configure( PaOssStream *stream, double sampleRate, unsigned long framesPerBuffer, double *inputLatency, double *outputLatency ) { PaError result = paNoError; int duplex = stream->capture && stream->playback; unsigned long framesPerHostBuffer = 0; /* We should request full duplex first thing after opening the device */ if( duplex && stream->sharedDevice ) ENSURE_( ioctl( stream->capture->fd, SNDCTL_DSP_SETDUPLEX, 0 ), paUnanticipatedHostError ); if( stream->capture ) { PaOssStreamComponent *component = stream->capture; PA_ENSURE( PaOssStreamComponent_Configure( component, sampleRate, framesPerBuffer, StreamMode_In, NULL ) ); assert( component->hostChannelCount > 0 ); assert( component->hostFrames > 0 ); *inputLatency = component->hostFrames * (component->numBufs - 1) / sampleRate; } if( stream->playback ) { PaOssStreamComponent *component = stream->playback, *master = stream->sharedDevice ? stream->capture : NULL; PA_ENSURE( PaOssStreamComponent_Configure( component, sampleRate, framesPerBuffer, StreamMode_Out, master ) ); assert( component->hostChannelCount > 0 ); assert( component->hostFrames > 0 ); *outputLatency = component->hostFrames * (component->numBufs - 1) / sampleRate; } if( duplex ) framesPerHostBuffer = PA_MIN( stream->capture->hostFrames, stream->playback->hostFrames ); else if( stream->capture ) framesPerHostBuffer = stream->capture->hostFrames; else if( stream->playback ) framesPerHostBuffer = stream->playback->hostFrames; stream->framesPerHostBuffer = framesPerHostBuffer; stream->pollTimeout = (int) ceil( 1e6 * framesPerHostBuffer / sampleRate ); /* Period in usecs, rounded up */ stream->sampleRate = stream->streamRepresentation.streamInfo.sampleRate = sampleRate; error: return result; } /* see pa_hostapi.h for a list of validity guarantees made about OpenStream parameters */ /** Open a PA OSS stream. * * Aspect StreamChannels: The number of channels is specified per direction (in/out), and can differ between the * two. However, OSS doesn't support separate configuration spaces for capture and playback so if both * directions are the same device we will demand the same number of channels. The number of channels can range * from 1 to the maximum supported by the device. * * Aspect BufferSettings: If framesPerBuffer != paFramesPerBufferUnspecified the number of frames per callback * must reflect this, in addition the host latency per device should approximate the corresponding * suggestedLatency. Based on these constraints we need to determine a number of frames per host buffer that * both capture and playback can agree on (they can be different devices), the buffer processor can adapt * between host and user buffer size, but the ratio should preferably be integral. */ static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ) { PaError result = paNoError; PaOSSHostApiRepresentation *ossHostApi = (PaOSSHostApiRepresentation*)hostApi; PaOssStream *stream = NULL; int inputChannelCount = 0, outputChannelCount = 0; PaSampleFormat inputSampleFormat = 0, outputSampleFormat = 0, inputHostFormat = 0, outputHostFormat = 0; const PaDeviceInfo *inputDeviceInfo = 0, *outputDeviceInfo = 0; int bpInitialized = 0; double inLatency = 0., outLatency = 0.; int i = 0; /* validate platform specific flags */ if( (streamFlags & paPlatformSpecificFlags) != 0 ) return paInvalidFlag; /* unexpected platform specific flag */ if( inputParameters ) { /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ inputDeviceInfo = hostApi->deviceInfos[inputParameters->device]; PA_ENSURE( ValidateParameters( inputParameters, inputDeviceInfo, StreamMode_In ) ); inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; } if( outputParameters ) { outputDeviceInfo = hostApi->deviceInfos[outputParameters->device]; PA_ENSURE( ValidateParameters( outputParameters, outputDeviceInfo, StreamMode_Out ) ); outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; } /* Aspect StreamChannels: We currently demand that number of input and output channels are the same, if the same * device is opened for both directions */ if( inputChannelCount > 0 && outputChannelCount > 0 ) { if( inputParameters->device == outputParameters->device ) { if( inputParameters->channelCount != outputParameters->channelCount ) return paInvalidChannelCount; } } /* Round framesPerBuffer to the next power-of-two to make OSS happy. */ if( framesPerBuffer != paFramesPerBufferUnspecified ) { framesPerBuffer &= INT_MAX; for (i = 1; framesPerBuffer > i; i <<= 1) ; framesPerBuffer = i; } /* allocate and do basic initialization of the stream structure */ PA_UNLESS( stream = (PaOssStream*)PaUtil_AllocateMemory( sizeof(PaOssStream) ), paInsufficientMemory ); PA_ENSURE( PaOssStream_Initialize( stream, inputParameters, outputParameters, streamCallback, userData, streamFlags, ossHostApi ) ); PA_ENSURE( PaOssStream_Configure( stream, sampleRate, framesPerBuffer, &inLatency, &outLatency ) ); PaUtil_InitializeCpuLoadMeasurer( &stream->cpuLoadMeasurer, sampleRate ); if( inputParameters ) { inputHostFormat = stream->capture->hostFormat; stream->streamRepresentation.streamInfo.inputLatency = inLatency + PaUtil_GetBufferProcessorInputLatency( &stream->bufferProcessor ) / sampleRate; } if( outputParameters ) { outputHostFormat = stream->playback->hostFormat; stream->streamRepresentation.streamInfo.outputLatency = outLatency + PaUtil_GetBufferProcessorOutputLatency( &stream->bufferProcessor ) / sampleRate; } /* Initialize buffer processor with fixed host buffer size. * Aspect StreamSampleFormat: Here we commit the user and host sample formats, PA infrastructure will * convert between the two. */ PA_ENSURE( PaUtil_InitializeBufferProcessor( &stream->bufferProcessor, inputChannelCount, inputSampleFormat, inputHostFormat, outputChannelCount, outputSampleFormat, outputHostFormat, sampleRate, streamFlags, framesPerBuffer, stream->framesPerHostBuffer, paUtilFixedHostBufferSize, streamCallback, userData ) ); bpInitialized = 1; *s = (PaStream*)stream; return result; error: if( bpInitialized ) PaUtil_TerminateBufferProcessor( &stream->bufferProcessor ); if( stream ) PaOssStream_Terminate( stream ); return result; } /*! Poll on I/O filedescriptors. Poll till we've determined there's data for read or write. In the full-duplex case, we don't want to hang around forever waiting for either input or output frames, so whenever we have a timed out filedescriptor we check if we're nearing under/overrun for the other direction (critical limit set at one buffer). If so, we exit the waiting state, and go on with what we got. We align the number of frames on a host buffer boundary because it is possible that the buffer size differs for the two directions and the host buffer size is a compromise between the two. */ static PaError PaOssStream_WaitForFrames( PaOssStream *stream, unsigned long *frames ) { PaError result = paNoError; int pollPlayback = 0, pollCapture = 0; int captureAvail = INT_MAX, playbackAvail = INT_MAX, commonAvail; audio_buf_info bufInfo; /* int ofs = 0, nfds = stream->nfds; */ fd_set readFds, writeFds; int nfds = 0; struct timeval selectTimeval = {0, 0}; unsigned long timeout = stream->pollTimeout; /* In usecs */ int captureFd = -1, playbackFd = -1; assert( stream ); assert( frames ); if( stream->capture ) { pollCapture = 1; captureFd = stream->capture->fd; /* stream->capture->pfd->events = POLLIN; */ } if( stream->playback ) { pollPlayback = 1; playbackFd = stream->playback->fd; /* stream->playback->pfd->events = POLLOUT; */ } FD_ZERO( &readFds ); FD_ZERO( &writeFds ); while( pollPlayback || pollCapture ) { pthread_testcancel(); /* select may modify the timeout parameter */ selectTimeval.tv_usec = timeout; nfds = 0; if( pollCapture ) { FD_SET( captureFd, &readFds ); nfds = captureFd + 1; } if( pollPlayback ) { FD_SET( playbackFd, &writeFds ); nfds = PA_MAX( nfds, playbackFd + 1 ); } ENSURE_( select( nfds, &readFds, &writeFds, NULL, &selectTimeval ), paUnanticipatedHostError ); /* if( poll( stream->pfds + ofs, nfds, stream->pollTimeout ) < 0 ) { ENSURE_( -1, paUnanticipatedHostError ); } */ pthread_testcancel(); if( pollCapture ) { if( FD_ISSET( captureFd, &readFds ) ) { FD_CLR( captureFd, &readFds ); pollCapture = 0; } /* if( stream->capture->pfd->revents & POLLIN ) { --nfds; ++ofs; pollCapture = 0; } */ else if( stream->playback ) /* Timed out, go on with playback? */ { /*PA_DEBUG(( "%s: Trying to poll again for capture frames, pollTimeout: %d\n", __FUNCTION__, stream->pollTimeout ));*/ } } if( pollPlayback ) { if( FD_ISSET( playbackFd, &writeFds ) ) { FD_CLR( playbackFd, &writeFds ); pollPlayback = 0; } /* if( stream->playback->pfd->revents & POLLOUT ) { --nfds; pollPlayback = 0; } */ else if( stream->capture ) /* Timed out, go on with capture? */ { /*PA_DEBUG(( "%s: Trying to poll again for playback frames, pollTimeout: %d\n\n", __FUNCTION__, stream->pollTimeout ));*/ } } } if( stream->capture ) { ENSURE_( ioctl( captureFd, SNDCTL_DSP_GETISPACE, &bufInfo ), paUnanticipatedHostError ); captureAvail = bufInfo.fragments * stream->capture->hostFrames; if( !captureAvail ) PA_DEBUG(( "%s: captureAvail: 0\n", __FUNCTION__ )); captureAvail = captureAvail == 0 ? INT_MAX : captureAvail; /* Disregard if zero */ } if( stream->playback ) { ENSURE_( ioctl( playbackFd, SNDCTL_DSP_GETOSPACE, &bufInfo ), paUnanticipatedHostError ); playbackAvail = bufInfo.fragments * stream->playback->hostFrames; if( !playbackAvail ) { PA_DEBUG(( "%s: playbackAvail: 0\n", __FUNCTION__ )); } playbackAvail = playbackAvail == 0 ? INT_MAX : playbackAvail; /* Disregard if zero */ } commonAvail = PA_MIN( captureAvail, playbackAvail ); if( commonAvail == INT_MAX ) commonAvail = 0; commonAvail -= commonAvail % stream->framesPerHostBuffer; assert( commonAvail != INT_MAX ); assert( commonAvail >= 0 ); *frames = commonAvail; error: return result; } /** Prepare stream for capture/playback. * * In order to synchronize capture and playback properly we use the SETTRIGGER command. */ static PaError PaOssStream_Prepare( PaOssStream *stream ) { PaError result = paNoError; int enableBits = 0; if( stream->triggered ) return result; if( stream->playback ) { size_t bufSz = PaOssStreamComponent_BufferSize( stream->playback ); memset( stream->playback->buffer, 0, bufSz ); /* Looks like we have to turn off blocking before we try this, but if we don't fill the buffer * OSS will complain. */ PA_ENSURE( ModifyBlocking( stream->playback->fd, 0 ) ); while (1) { if( write( stream->playback->fd, stream->playback->buffer, bufSz ) < 0 ) break; } PA_ENSURE( ModifyBlocking( stream->playback->fd, 1 ) ); } if( stream->sharedDevice ) { enableBits = PCM_ENABLE_INPUT | PCM_ENABLE_OUTPUT; ENSURE_( ioctl( stream->capture->fd, SNDCTL_DSP_SETTRIGGER, &enableBits ), paUnanticipatedHostError ); } else { if( stream->capture ) { enableBits = PCM_ENABLE_INPUT; ENSURE_( ioctl( stream->capture->fd, SNDCTL_DSP_SETTRIGGER, &enableBits ), paUnanticipatedHostError ); } if( stream->playback ) { enableBits = PCM_ENABLE_OUTPUT; ENSURE_( ioctl( stream->playback->fd, SNDCTL_DSP_SETTRIGGER, &enableBits ), paUnanticipatedHostError ); } } /* Ok, we have triggered the stream */ stream->triggered = 1; error: return result; } /** Stop audio processing * */ static PaError PaOssStream_Stop( PaOssStream *stream, int abort ) { PaError result = paNoError; /* Looks like the only safe way to stop audio without reopening the device is SNDCTL_DSP_POST. * Also disable capture/playback till the stream is started again */ if( stream->capture ) { ENSURE_( ioctl( stream->capture->fd, SNDCTL_DSP_POST, 0 ), paUnanticipatedHostError ); } if( stream->playback && !stream->sharedDevice ) { ENSURE_( ioctl( stream->playback->fd, SNDCTL_DSP_POST, 0 ), paUnanticipatedHostError ); } error: return result; } /** Clean up after thread exit. * * Aspect StreamState: If the user has registered a streamFinishedCallback it will be called here */ static void OnExit( void *data ) { PaOssStream *stream = (PaOssStream *) data; assert( data ); PaUtil_ResetCpuLoadMeasurer( &stream->cpuLoadMeasurer ); PaOssStream_Stop( stream, stream->callbackAbort ); PA_DEBUG(( "OnExit: Stoppage\n" )); /* Eventually notify user all buffers have played */ if( stream->streamRepresentation.streamFinishedCallback ) stream->streamRepresentation.streamFinishedCallback( stream->streamRepresentation.userData ); stream->callbackAbort = 0; /* Clear state */ stream->isActive = 0; } static PaError SetUpBuffers( PaOssStream *stream, unsigned long framesAvail ) { PaError result = paNoError; if( stream->capture ) { PaUtil_SetInterleavedInputChannels( &stream->bufferProcessor, 0, stream->capture->buffer, stream->capture->hostChannelCount ); PaUtil_SetInputFrameCount( &stream->bufferProcessor, framesAvail ); } if( stream->playback ) { PaUtil_SetInterleavedOutputChannels( &stream->bufferProcessor, 0, stream->playback->buffer, stream->playback->hostChannelCount ); PaUtil_SetOutputFrameCount( &stream->bufferProcessor, framesAvail ); } return result; } /** Thread procedure for callback processing. * * Aspect StreamState: StartStream will wait on this to initiate audio processing, useful in case the * callback should be used for buffer priming. When the stream is cancelled a separate function will * take care of the transition to the Callback Finished state (the stream isn't considered Stopped * before StopStream() or AbortStream() are called). */ static void *PaOSS_AudioThreadProc( void *userData ) { PaError result = paNoError; PaOssStream *stream = (PaOssStream*)userData; unsigned long framesAvail = 0, framesProcessed = 0; int callbackResult = paContinue; int triggered = stream->triggered; /* See if SNDCTL_DSP_TRIGGER has been issued already */ int initiateProcessing = triggered; /* Already triggered? */ PaStreamCallbackFlags cbFlags = 0; /* We might want to keep state across iterations */ PaStreamCallbackTimeInfo timeInfo = {0,0,0}; /* TODO: IMPLEMENT ME */ /* #if ( SOUND_VERSION > 0x030904 ) audio_errinfo errinfo; #endif */ assert( stream ); pthread_cleanup_push( &OnExit, stream ); /* Execute OnExit when exiting */ /* The first time the stream is started we use SNDCTL_DSP_TRIGGER to accurately start capture and * playback in sync, when the stream is restarted after being stopped we simply start by reading/ * writing. */ PA_ENSURE( PaOssStream_Prepare( stream ) ); /* If we are to initiate processing implicitly by reading/writing data, we start off in blocking mode */ if( initiateProcessing ) { /* Make sure devices are in blocking mode */ if( stream->capture ) ModifyBlocking( stream->capture->fd, 1 ); if( stream->playback ) ModifyBlocking( stream->playback->fd, 1 ); } while( 1 ) { pthread_testcancel(); if( stream->callbackStop && callbackResult == paContinue ) { PA_DEBUG(( "Setting callbackResult to paComplete\n" )); callbackResult = paComplete; } /* Aspect StreamState: Because of the messy OSS scheme we can't explicitly trigger device start unless * the stream has been recently started, we will have to go right ahead and read/write in blocking * fashion to trigger operation. Therefore we begin with processing one host buffer before we switch * to non-blocking mode. */ if( !initiateProcessing ) { /* Wait on available frames */ PA_ENSURE( PaOssStream_WaitForFrames( stream, &framesAvail ) ); assert( framesAvail % stream->framesPerHostBuffer == 0 ); } else { framesAvail = stream->framesPerHostBuffer; } while( framesAvail > 0 ) { unsigned long frames = framesAvail; pthread_testcancel(); PaUtil_BeginCpuLoadMeasurement( &stream->cpuLoadMeasurer ); /* Read data */ if ( stream->capture ) { PA_ENSURE( PaOssStreamComponent_Read( stream->capture, &frames ) ); if( frames < framesAvail ) { PA_DEBUG(( "Read %lu less frames than requested\n", framesAvail - frames )); framesAvail = frames; } } #if ( SOUND_VERSION >= 0x030904 ) /* Check with OSS to see if there have been any under/overruns since last time we checked. */ /* if( ioctl( stream->deviceHandle, SNDCTL_DSP_GETERROR, &errinfo ) >= 0 ) { if( errinfo.play_underruns ) cbFlags |= paOutputUnderflow ; if( errinfo.record_underruns ) cbFlags |= paInputUnderflow ; } else PA_DEBUG(( "SNDCTL_DSP_GETERROR command failed: %s\n", strerror( errno ) )); */ #endif PaUtil_BeginBufferProcessing( &stream->bufferProcessor, &timeInfo, cbFlags ); cbFlags = 0; PA_ENSURE( SetUpBuffers( stream, framesAvail ) ); framesProcessed = PaUtil_EndBufferProcessing( &stream->bufferProcessor, &callbackResult ); assert( framesProcessed == framesAvail ); PaUtil_EndCpuLoadMeasurement( &stream->cpuLoadMeasurer, framesProcessed ); if ( stream->playback ) { frames = framesAvail; PA_ENSURE( PaOssStreamComponent_Write( stream->playback, &frames ) ); if( frames < framesAvail ) { /* TODO: handle bytesWritten != bytesRequested (slippage?) */ PA_DEBUG(( "Wrote %lu less frames than requested\n", framesAvail - frames )); } } framesAvail -= framesProcessed; stream->framesProcessed += framesProcessed; if( callbackResult != paContinue ) break; } if( initiateProcessing || !triggered ) { /* Non-blocking */ if( stream->capture ) PA_ENSURE( ModifyBlocking( stream->capture->fd, 0 ) ); if( stream->playback && !stream->sharedDevice ) PA_ENSURE( ModifyBlocking( stream->playback->fd, 0 ) ); initiateProcessing = 0; sem_post( &stream->semaphore ); } if( callbackResult != paContinue ) { stream->callbackAbort = callbackResult == paAbort; if( stream->callbackAbort || PaUtil_IsBufferProcessorOutputEmpty( &stream->bufferProcessor ) ) break; } } pthread_cleanup_pop( 1 ); error: pthread_exit( NULL ); } /** Close the stream. * */ static PaError CloseStream( PaStream* s ) { PaError result = paNoError; PaOssStream *stream = (PaOssStream*)s; assert( stream ); PaUtil_TerminateBufferProcessor( &stream->bufferProcessor ); PaOssStream_Terminate( stream ); return result; } /** Start the stream. * * Aspect StreamState: After returning, the stream shall be in the Active state, implying that an eventual * callback will be repeatedly called in a separate thread. If a separate thread is started this function * will block untill it has started processing audio, otherwise audio processing is started directly. */ static PaError StartStream( PaStream *s ) { PaError result = paNoError; PaOssStream *stream = (PaOssStream*)s; stream->isActive = 1; stream->isStopped = 0; stream->lastPosPtr = 0; stream->lastStreamBytes = 0; stream->framesProcessed = 0; /* only use the thread for callback streams */ if( stream->bufferProcessor.streamCallback ) { PA_ENSURE( PaUtil_StartThreading( &stream->threading, &PaOSS_AudioThreadProc, stream ) ); sem_wait( &stream->semaphore ); } else PA_ENSURE( PaOssStream_Prepare( stream ) ); error: return result; } static PaError RealStop( PaOssStream *stream, int abort ) { PaError result = paNoError; if( stream->callbackMode ) { if( abort ) stream->callbackAbort = 1; else stream->callbackStop = 1; PA_ENSURE( PaUtil_CancelThreading( &stream->threading, !abort, NULL ) ); stream->callbackStop = stream->callbackAbort = 0; } else PA_ENSURE( PaOssStream_Stop( stream, abort ) ); stream->isStopped = 1; error: return result; } /** Stop the stream. * * Aspect StreamState: This will cause the stream to transition to the Stopped state, playing all enqueued * buffers. */ static PaError StopStream( PaStream *s ) { return RealStop( (PaOssStream *)s, 0 ); } /** Abort the stream. * * Aspect StreamState: This will cause the stream to transition to the Stopped state, discarding all enqueued * buffers. Note that the buffers are not currently correctly discarded, this is difficult without closing * the OSS device. */ static PaError AbortStream( PaStream *s ) { return RealStop( (PaOssStream *)s, 1 ); } /** Is the stream in the Stopped state. * */ static PaError IsStreamStopped( PaStream *s ) { PaOssStream *stream = (PaOssStream*)s; return (stream->isStopped); } /** Is the stream in the Active state. * */ static PaError IsStreamActive( PaStream *s ) { PaOssStream *stream = (PaOssStream*)s; return (stream->isActive); } static PaTime GetStreamTime( PaStream *s ) { PaOssStream *stream = (PaOssStream*)s; count_info info; int delta; if( stream->playback ) { if( ioctl( stream->playback->fd, SNDCTL_DSP_GETOPTR, &info) == 0 ) { delta = ( info.bytes - stream->lastPosPtr ) /* & 0x000FFFFF*/; return (float)(stream->lastStreamBytes + delta) / PaOssStreamComponent_FrameSize( stream->playback ) / stream->sampleRate; } } else { if (ioctl( stream->capture->fd, SNDCTL_DSP_GETIPTR, &info) == 0) { delta = (info.bytes - stream->lastPosPtr) /*& 0x000FFFFF*/; return (float)(stream->lastStreamBytes + delta) / PaOssStreamComponent_FrameSize( stream->capture ) / stream->sampleRate; } } /* the ioctl failed, but we can still give a coarse estimate */ return stream->framesProcessed / stream->sampleRate; } static double GetStreamCpuLoad( PaStream* s ) { PaOssStream *stream = (PaOssStream*)s; return PaUtil_GetCpuLoad( &stream->cpuLoadMeasurer ); } /* As separate stream interfaces are used for blocking and callback streams, the following functions can be guaranteed to only be called for blocking streams. */ static PaError ReadStream( PaStream* s, void *buffer, unsigned long frames ) { PaOssStream *stream = (PaOssStream*)s; int bytesRequested, bytesRead; unsigned long framesRequested; void *userBuffer; /* If user input is non-interleaved, PaUtil_CopyInput will manipulate the channel pointers, * so we copy the user provided pointers */ if( stream->bufferProcessor.userInputIsInterleaved ) userBuffer = buffer; else /* Copy channels into local array */ { userBuffer = stream->capture->userBuffers; memcpy( (void *)userBuffer, buffer, sizeof (void *) * stream->capture->userChannelCount ); } while( frames ) { framesRequested = PA_MIN( frames, stream->capture->hostFrames ); bytesRequested = framesRequested * PaOssStreamComponent_FrameSize( stream->capture ); bytesRead = read( stream->capture->fd, stream->capture->buffer, bytesRequested ); if ( bytesRequested != bytesRead ) return paUnanticipatedHostError; PaUtil_SetInputFrameCount( &stream->bufferProcessor, stream->capture->hostFrames ); PaUtil_SetInterleavedInputChannels( &stream->bufferProcessor, 0, stream->capture->buffer, stream->capture->hostChannelCount ); PaUtil_CopyInput( &stream->bufferProcessor, &userBuffer, framesRequested ); frames -= framesRequested; } return paNoError; } static PaError WriteStream( PaStream *s, const void *buffer, unsigned long frames ) { PaOssStream *stream = (PaOssStream*)s; int bytesRequested, bytesWritten; unsigned long framesConverted; const void *userBuffer; /* If user output is non-interleaved, PaUtil_CopyOutput will manipulate the channel pointers, * so we copy the user provided pointers */ if( stream->bufferProcessor.userOutputIsInterleaved ) userBuffer = buffer; else { /* Copy channels into local array */ userBuffer = stream->playback->userBuffers; memcpy( (void *)userBuffer, buffer, sizeof (void *) * stream->playback->userChannelCount ); } while( frames ) { PaUtil_SetOutputFrameCount( &stream->bufferProcessor, stream->playback->hostFrames ); PaUtil_SetInterleavedOutputChannels( &stream->bufferProcessor, 0, stream->playback->buffer, stream->playback->hostChannelCount ); framesConverted = PaUtil_CopyOutput( &stream->bufferProcessor, &userBuffer, frames ); frames -= framesConverted; bytesRequested = framesConverted * PaOssStreamComponent_FrameSize( stream->playback ); bytesWritten = write( stream->playback->fd, stream->playback->buffer, bytesRequested ); if ( bytesRequested != bytesWritten ) return paUnanticipatedHostError; } return paNoError; } static signed long GetStreamReadAvailable( PaStream* s ) { PaOssStream *stream = (PaOssStream*)s; audio_buf_info info; if( ioctl( stream->capture->fd, SNDCTL_DSP_GETISPACE, &info ) < 0 ) return paUnanticipatedHostError; return info.fragments * stream->capture->hostFrames; } /* TODO: Compute number of allocated bytes somewhere else, can we use ODELAY with capture */ static signed long GetStreamWriteAvailable( PaStream* s ) { PaOssStream *stream = (PaOssStream*)s; int delay = 0; if( ioctl( stream->playback->fd, SNDCTL_DSP_GETODELAY, &delay ) < 0 ) return paUnanticipatedHostError; return (PaOssStreamComponent_BufferSize( stream->playback ) - delay) / PaOssStreamComponent_FrameSize( stream->playback ); } sources_5316/external/portaudio/pa_linux_alsa.h0000644000176700017670000000637711474735745020601 0ustar paulpaul#ifndef PA_LINUX_ALSA_H #define PA_LINUX_ALSA_H /* * $Id: pa_linux_alsa.h 1236 2007-06-24 20:39:26Z aknudsen $ * PortAudio Portable Real-Time Audio Library * ALSA-specific extensions * * Copyright (c) 1999-2000 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file * ALSA-specific PortAudio API extension header file. */ #include "portaudio.h" #ifdef __cplusplus extern "C" { #endif typedef struct PaAlsaStreamInfo { unsigned long size; PaHostApiTypeId hostApiType; unsigned long version; const char *deviceString; } PaAlsaStreamInfo; /** Initialize host API specific structure, call this before setting relevant attributes. */ void PaAlsa_InitializeStreamInfo( PaAlsaStreamInfo *info ); /** Instruct whether to enable real-time priority when starting the audio thread. * * If this is turned on by the stream is started, the audio callback thread will be created * with the FIFO scheduling policy, which is suitable for realtime operation. **/ void PaAlsa_EnableRealtimeScheduling( PaStream *s, int enable ); #if 0 void PaAlsa_EnableWatchdog( PaStream *s, int enable ); #endif /** Get the ALSA-lib card index of this stream's input device. */ PaError PaAlsa_GetStreamInputCard( PaStream *s, int *card ); /** Get the ALSA-lib card index of this stream's output device. */ PaError PaAlsa_GetStreamOutputCard( PaStream *s, int *card ); /** Set the number of periods (buffer fragments) to configure devices with. * * By default the number of periods is 4, this is the lowest number of periods that works well on * the author's soundcard. * @param numPeriods The number of periods. */ PaError PaAlsa_SetNumPeriods( int numPeriods ); PaError PaAlsa_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex hostApiIndex ); #ifdef __cplusplus } #endif #endif sources_5316/external/portaudio/pa_mac_core.c0000644000176700017670000027052011320412065020147 0ustar paulpaul/* * Implementation of the PortAudio API for Apple AUHAL * * PortAudio Portable Real-Time Audio Library * Latest Version at: http://www.portaudio.com * * Written by Bjorn Roche of XO Audio LLC, from PA skeleton code. * Portions copied from code by Dominic Mazzoni (who wrote a HAL implementation) * * Dominic's code was based on code by Phil Burk, Darren Gibbs, * Gord Peters, Stephane Letz, and Greg Pfiel. * * The following people also deserve acknowledgements: * * Olivier Tristan for feedback and testing * Glenn Zelniker and Z-Systems engineering for sponsoring the Blocking I/O * interface. * * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file pa_mac_core @ingroup hostapi_src @author Bjorn Roche @brief AUHAL implementation of PortAudio */ /* FIXME: not all error conditions call PaUtil_SetLastHostErrorInfo() * PaMacCore_SetError() will do this. */ #include "pa_mac_core_internal.h" #include /* strlen(), memcmp() etc. */ #include #include #include "pa_mac_core.h" #include "pa_mac_core_utilities.h" #include "pa_mac_core_blocking.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ /* prototypes for functions declared in this file */ PaError PaMacCore_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); /* * Function declared in pa_mac_core.h. Sets up a PaMacCoreStreamInfoStruct * with the requested flags and initializes channel map. */ void PaMacCore_SetupStreamInfo( PaMacCoreStreamInfo *data, const unsigned long flags ) { bzero( data, sizeof( PaMacCoreStreamInfo ) ); data->size = sizeof( PaMacCoreStreamInfo ); data->hostApiType = paCoreAudio; data->version = 0x01; data->flags = flags; data->channelMap = NULL; data->channelMapSize = 0; } /* * Function declared in pa_mac_core.h. Adds channel mapping to a PaMacCoreStreamInfoStruct */ void PaMacCore_SetupChannelMap( PaMacCoreStreamInfo *data, const SInt32 * const channelMap, const unsigned long channelMapSize ) { data->channelMap = channelMap; data->channelMapSize = channelMapSize; } static char *channelName = NULL; static int channelNameSize = 0; static bool ensureChannelNameSize( int size ) { if( size >= channelNameSize ) { free( channelName ); channelName = (char *) malloc( ( channelNameSize = size ) + 1 ); if( !channelName ) { channelNameSize = 0; return false; } } return true; } /* * Function declared in pa_mac_core.h. retrives channel names. */ const char *PaMacCore_GetChannelName( int device, int channelIndex, bool input ) { struct PaUtilHostApiRepresentation *hostApi; PaError err; OSStatus error; err = PaUtil_GetHostApiRepresentation( &hostApi, paCoreAudio ); assert(err == paNoError); PaMacAUHAL *macCoreHostApi = (PaMacAUHAL*)hostApi; AudioDeviceID hostApiDevice = macCoreHostApi->devIds[device]; UInt32 size = 0; error = AudioDeviceGetPropertyInfo( hostApiDevice, channelIndex + 1, input, kAudioDevicePropertyChannelName, &size, NULL ); if( error ) { //try the CFString CFStringRef name; bool isDeviceName = false; size = sizeof( name ); error = AudioDeviceGetProperty( hostApiDevice, channelIndex + 1, input, kAudioDevicePropertyChannelNameCFString, &size, &name ); if( error ) { //as a last-ditch effort, get the device name. Later we'll append the channel number. size = sizeof( name ); error = AudioDeviceGetProperty( hostApiDevice, channelIndex + 1, input, kAudioDevicePropertyDeviceNameCFString, &size, &name ); if( error ) return NULL; isDeviceName = true; } if( isDeviceName ) { name = CFStringCreateWithFormat( NULL, NULL, CFSTR( "%@: %d"), name, channelIndex + 1 ); } CFIndex length = CFStringGetLength(name); while( ensureChannelNameSize( length * sizeof(UniChar) + 1 ) ) { if( CFStringGetCString( name, channelName, channelNameSize, kCFStringEncodingUTF8 ) ) { if( isDeviceName ) CFRelease( name ); return channelName; } if( length == 0 ) ++length; length *= 2; } if( isDeviceName ) CFRelease( name ); return NULL; } //continue with C string: if( !ensureChannelNameSize( size ) ) return NULL; error = AudioDeviceGetProperty( hostApiDevice, channelIndex + 1, input, kAudioDevicePropertyChannelName, &size, channelName ); if( error ) { ERR( error ); return NULL; } return channelName; } AudioDeviceID PaMacCore_GetStreamInputDevice( PaStream* s ) { PaMacCoreStream *stream = (PaMacCoreStream*)s; VVDBUG(("PaMacCore_GetStreamInputHandle()\n")); return ( stream->inputDevice ); } AudioDeviceID PaMacCore_GetStreamOutputDevice( PaStream* s ) { PaMacCoreStream *stream = (PaMacCoreStream*)s; VVDBUG(("PaMacCore_GetStreamOutputHandle()\n")); return ( stream->outputDevice ); } #ifdef __cplusplus } #endif /* __cplusplus */ #define RING_BUFFER_ADVANCE_DENOMINATOR (4) static void Terminate( struct PaUtilHostApiRepresentation *hostApi ); static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ); static PaError CloseStream( PaStream* stream ); static PaError StartStream( PaStream *stream ); static PaError StopStream( PaStream *stream ); static PaError AbortStream( PaStream *stream ); static PaError IsStreamStopped( PaStream *s ); static PaError IsStreamActive( PaStream *stream ); static PaTime GetStreamTime( PaStream *stream ); static void setStreamStartTime( PaStream *stream ); static OSStatus AudioIOProc( void *inRefCon, AudioUnitRenderActionFlags *ioActionFlags, const AudioTimeStamp *inTimeStamp, UInt32 inBusNumber, UInt32 inNumberFrames, AudioBufferList *ioData ); static double GetStreamCpuLoad( PaStream* stream ); static PaError GetChannelInfo( PaMacAUHAL *auhalHostApi, PaDeviceInfo *deviceInfo, AudioDeviceID macCoreDeviceId, int isInput); static PaError OpenAndSetupOneAudioUnit( const PaMacCoreStream *stream, const PaStreamParameters *inStreamParams, const PaStreamParameters *outStreamParams, const UInt32 requestedFramesPerBuffer, UInt32 *actualInputFramesPerBuffer, UInt32 *actualOutputFramesPerBuffer, const PaMacAUHAL *auhalHostApi, AudioUnit *audioUnit, AudioConverterRef *srConverter, AudioDeviceID *audioDevice, const double sampleRate, void *refCon ); /* for setting errors. */ #define PA_AUHAL_SET_LAST_HOST_ERROR( errorCode, errorText ) \ PaUtil_SetLastHostErrorInfo( paInDevelopment, errorCode, errorText ) /* * Callback for setting over/underrun flags. * */ static OSStatus xrunCallback( AudioDeviceID inDevice, UInt32 inChannel, Boolean isInput, AudioDevicePropertyID inPropertyID, void* inClientData) { PaMacCoreStream *stream = (PaMacCoreStream *) inClientData; if( stream->state != ACTIVE ) return 0; //if the stream isn't active, we don't care if the device is dropping if( isInput ) OSAtomicOr32( paInputUnderflow, (uint32_t *)&(stream->xrunFlags) ); else OSAtomicOr32( paOutputOverflow, (uint32_t *)&(stream->xrunFlags) ); return 0; } /* * Callback called when starting or stopping a stream. */ static void startStopCallback( void * inRefCon, AudioUnit ci, AudioUnitPropertyID inID, AudioUnitScope inScope, AudioUnitElement inElement ) { PaMacCoreStream *stream = (PaMacCoreStream *) inRefCon; UInt32 isRunning; UInt32 size = sizeof( isRunning ); assert( !AudioUnitGetProperty( ci, kAudioOutputUnitProperty_IsRunning, inScope, inElement, &isRunning, &size ) ); if( isRunning ) return; //We are only interested in when we are stopping // -- if we are using 2 I/O units, we only need one notification! if( stream->inputUnit && stream->outputUnit && stream->inputUnit != stream->outputUnit && ci == stream->inputUnit ) return; PaStreamFinishedCallback *sfc = stream->streamRepresentation.streamFinishedCallback; if( stream->state == STOPPING ) stream->state = STOPPED ; if( sfc ) sfc( stream->streamRepresentation.userData ); } /*currently, this is only used in initialization, but it might be modified to be used when the list of devices changes.*/ static PaError gatherDeviceInfo(PaMacAUHAL *auhalHostApi) { UInt32 size; UInt32 propsize; VVDBUG(("gatherDeviceInfo()\n")); /* -- free any previous allocations -- */ if( auhalHostApi->devIds ) PaUtil_GroupFreeMemory(auhalHostApi->allocations, auhalHostApi->devIds); auhalHostApi->devIds = NULL; /* -- figure out how many devices there are -- */ AudioHardwareGetPropertyInfo( kAudioHardwarePropertyDevices, &propsize, NULL ); auhalHostApi->devCount = propsize / sizeof( AudioDeviceID ); VDBUG( ( "Found %ld device(s).\n", auhalHostApi->devCount ) ); /* -- copy the device IDs -- */ auhalHostApi->devIds = (AudioDeviceID *)PaUtil_GroupAllocateMemory( auhalHostApi->allocations, propsize ); if( !auhalHostApi->devIds ) return paInsufficientMemory; AudioHardwareGetProperty( kAudioHardwarePropertyDevices, &propsize, auhalHostApi->devIds ); #ifdef MAC_CORE_VERBOSE_DEBUG { int i; for( i=0; idevCount; ++i ) printf( "Device %d\t: %ld\n", i, auhalHostApi->devIds[i] ); } #endif size = sizeof(AudioDeviceID); auhalHostApi->defaultIn = kAudioDeviceUnknown; auhalHostApi->defaultOut = kAudioDeviceUnknown; /* determine the default device. */ /* I am not sure how these calls to AudioHardwareGetProperty() could fail, but in case they do, we use the first available device as the default. */ if( 0 != AudioHardwareGetProperty(kAudioHardwarePropertyDefaultInputDevice, &size, &auhalHostApi->defaultIn) ) { int i; auhalHostApi->defaultIn = kAudioDeviceUnknown; VDBUG(("Failed to get default input device from OS.")); VDBUG((" I will substitute the first available input Device.")); for( i=0; idevCount; ++i ) { PaDeviceInfo devInfo; if( 0 != GetChannelInfo( auhalHostApi, &devInfo, auhalHostApi->devIds[i], TRUE ) ) if( devInfo.maxInputChannels ) { auhalHostApi->defaultIn = auhalHostApi->devIds[i]; break; } } } if( 0 != AudioHardwareGetProperty(kAudioHardwarePropertyDefaultOutputDevice, &size, &auhalHostApi->defaultOut) ) { int i; auhalHostApi->defaultIn = kAudioDeviceUnknown; VDBUG(("Failed to get default output device from OS.")); VDBUG((" I will substitute the first available output Device.")); for( i=0; idevCount; ++i ) { PaDeviceInfo devInfo; if( 0 != GetChannelInfo( auhalHostApi, &devInfo, auhalHostApi->devIds[i], FALSE ) ) if( devInfo.maxOutputChannels ) { auhalHostApi->defaultOut = auhalHostApi->devIds[i]; break; } } } VDBUG( ( "Default in : %ld\n", auhalHostApi->defaultIn ) ); VDBUG( ( "Default out: %ld\n", auhalHostApi->defaultOut ) ); return paNoError; } static PaError GetChannelInfo( PaMacAUHAL *auhalHostApi, PaDeviceInfo *deviceInfo, AudioDeviceID macCoreDeviceId, int isInput) { UInt32 propSize; PaError err = paNoError; UInt32 i; int numChannels = 0; AudioBufferList *buflist = NULL; UInt32 frameLatency; VVDBUG(("GetChannelInfo()\n")); /* Get the number of channels from the stream configuration. Fail if we can't get this. */ err = ERR(AudioDeviceGetPropertyInfo(macCoreDeviceId, 0, isInput, kAudioDevicePropertyStreamConfiguration, &propSize, NULL)); if (err) return err; buflist = PaUtil_AllocateMemory(propSize); if( !buflist ) return paInsufficientMemory; err = ERR(AudioDeviceGetProperty(macCoreDeviceId, 0, isInput, kAudioDevicePropertyStreamConfiguration, &propSize, buflist)); if (err) goto error; for (i = 0; i < buflist->mNumberBuffers; ++i) numChannels += buflist->mBuffers[i].mNumberChannels; if (isInput) deviceInfo->maxInputChannels = numChannels; else deviceInfo->maxOutputChannels = numChannels; if (numChannels > 0) /* do not try to retrieve the latency if there is no channels. */ { /* Get the latency. Don't fail if we can't get this. */ /* default to something reasonable */ deviceInfo->defaultLowInputLatency = .01; deviceInfo->defaultHighInputLatency = .10; deviceInfo->defaultLowOutputLatency = .01; deviceInfo->defaultHighOutputLatency = .10; propSize = sizeof(UInt32); err = WARNING(AudioDeviceGetProperty(macCoreDeviceId, 0, isInput, kAudioDevicePropertyLatency, &propSize, &frameLatency)); if (!err) { /** FEEDBACK: * This code was arrived at by trial and error, and some extentive, but not exhaustive * testing. Sebastien Beaulieu has suggested using * kAudioDevicePropertyLatency + kAudioDevicePropertySafetyOffset + buffer size instead. * At the time this code was written, many users were reporting dropouts with audio * programs that probably used this formula. This was probably * around 10.4.4, and the problem is probably fixed now. So perhaps * his formula should be reviewed and used. * */ double secondLatency = frameLatency / deviceInfo->defaultSampleRate; if (isInput) { deviceInfo->defaultLowInputLatency = 3 * secondLatency; deviceInfo->defaultHighInputLatency = 3 * 10 * secondLatency; } else { deviceInfo->defaultLowOutputLatency = 3 * secondLatency; deviceInfo->defaultHighOutputLatency = 3 * 10 * secondLatency; } } } PaUtil_FreeMemory( buflist ); return paNoError; error: PaUtil_FreeMemory( buflist ); return err; } static PaError InitializeDeviceInfo( PaMacAUHAL *auhalHostApi, PaDeviceInfo *deviceInfo, AudioDeviceID macCoreDeviceId, PaHostApiIndex hostApiIndex ) { Float64 sampleRate; char *name; PaError err = paNoError; UInt32 propSize; VVDBUG(("InitializeDeviceInfo(): macCoreDeviceId=%ld\n", macCoreDeviceId)); memset(deviceInfo, 0, sizeof(deviceInfo)); deviceInfo->structVersion = 2; deviceInfo->hostApi = hostApiIndex; /* Get the device name. Fail if we can't get it. */ err = ERR(AudioDeviceGetPropertyInfo(macCoreDeviceId, 0, 0, kAudioDevicePropertyDeviceName, &propSize, NULL)); if (err) return err; name = PaUtil_GroupAllocateMemory(auhalHostApi->allocations,propSize); if ( !name ) return paInsufficientMemory; err = ERR(AudioDeviceGetProperty(macCoreDeviceId, 0, 0, kAudioDevicePropertyDeviceName, &propSize, name)); if (err) return err; deviceInfo->name = name; /* Try to get the default sample rate. Don't fail if we can't get this. */ propSize = sizeof(Float64); err = ERR(AudioDeviceGetProperty(macCoreDeviceId, 0, 0, kAudioDevicePropertyNominalSampleRate, &propSize, &sampleRate)); if (err) deviceInfo->defaultSampleRate = 0.0; else deviceInfo->defaultSampleRate = sampleRate; /* Get the maximum number of input and output channels. Fail if we can't get this. */ err = GetChannelInfo(auhalHostApi, deviceInfo, macCoreDeviceId, 1); if (err) return err; err = GetChannelInfo(auhalHostApi, deviceInfo, macCoreDeviceId, 0); if (err) return err; return paNoError; } PaError PaMacCore_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex hostApiIndex ) { PaError result = paNoError; int i; PaMacAUHAL *auhalHostApi; PaDeviceInfo *deviceInfoArray; VVDBUG(("PaMacCore_Initialize(): hostApiIndex=%d\n", hostApiIndex)); auhalHostApi = (PaMacAUHAL*)PaUtil_AllocateMemory( sizeof(PaMacAUHAL) ); if( !auhalHostApi ) { result = paInsufficientMemory; goto error; } auhalHostApi->allocations = PaUtil_CreateAllocationGroup(); if( !auhalHostApi->allocations ) { result = paInsufficientMemory; goto error; } auhalHostApi->devIds = NULL; auhalHostApi->devCount = 0; /* get the info we need about the devices */ result = gatherDeviceInfo( auhalHostApi ); if( result != paNoError ) goto error; *hostApi = &auhalHostApi->inheritedHostApiRep; (*hostApi)->info.structVersion = 1; (*hostApi)->info.type = paCoreAudio; (*hostApi)->info.name = "Core Audio"; (*hostApi)->info.defaultInputDevice = paNoDevice; (*hostApi)->info.defaultOutputDevice = paNoDevice; (*hostApi)->info.deviceCount = 0; if( auhalHostApi->devCount > 0 ) { (*hostApi)->deviceInfos = (PaDeviceInfo**)PaUtil_GroupAllocateMemory( auhalHostApi->allocations, sizeof(PaDeviceInfo*) * auhalHostApi->devCount); if( !(*hostApi)->deviceInfos ) { result = paInsufficientMemory; goto error; } /* allocate all device info structs in a contiguous block */ deviceInfoArray = (PaDeviceInfo*)PaUtil_GroupAllocateMemory( auhalHostApi->allocations, sizeof(PaDeviceInfo) * auhalHostApi->devCount ); if( !deviceInfoArray ) { result = paInsufficientMemory; goto error; } for( i=0; i < auhalHostApi->devCount; ++i ) { int err; err = InitializeDeviceInfo( auhalHostApi, &deviceInfoArray[i], auhalHostApi->devIds[i], hostApiIndex ); if (err == paNoError) { /* copy some info and set the defaults */ (*hostApi)->deviceInfos[(*hostApi)->info.deviceCount] = &deviceInfoArray[i]; if (auhalHostApi->devIds[i] == auhalHostApi->defaultIn) (*hostApi)->info.defaultInputDevice = (*hostApi)->info.deviceCount; if (auhalHostApi->devIds[i] == auhalHostApi->defaultOut) (*hostApi)->info.defaultOutputDevice = (*hostApi)->info.deviceCount; (*hostApi)->info.deviceCount++; } else { /* there was an error. we need to shift the devices down, so we ignore this one */ int j; auhalHostApi->devCount--; for( j=i; jdevCount; ++j ) auhalHostApi->devIds[j] = auhalHostApi->devIds[j+1]; i--; } } } (*hostApi)->Terminate = Terminate; (*hostApi)->OpenStream = OpenStream; (*hostApi)->IsFormatSupported = IsFormatSupported; PaUtil_InitializeStreamInterface( &auhalHostApi->callbackStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, GetStreamCpuLoad, PaUtil_DummyRead, PaUtil_DummyWrite, PaUtil_DummyGetReadAvailable, PaUtil_DummyGetWriteAvailable ); PaUtil_InitializeStreamInterface( &auhalHostApi->blockingStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, PaUtil_DummyGetCpuLoad, ReadStream, WriteStream, GetStreamReadAvailable, GetStreamWriteAvailable ); return result; error: if( auhalHostApi ) { if( auhalHostApi->allocations ) { PaUtil_FreeAllAllocations( auhalHostApi->allocations ); PaUtil_DestroyAllocationGroup( auhalHostApi->allocations ); } PaUtil_FreeMemory( auhalHostApi ); } return result; } static void Terminate( struct PaUtilHostApiRepresentation *hostApi ) { PaMacAUHAL *auhalHostApi = (PaMacAUHAL*)hostApi; VVDBUG(("Terminate()\n")); /* IMPLEMENT ME: - clean up any resources not handled by the allocation group TODO: Double check that everything is handled by alloc group */ if( auhalHostApi->allocations ) { PaUtil_FreeAllAllocations( auhalHostApi->allocations ); PaUtil_DestroyAllocationGroup( auhalHostApi->allocations ); } PaUtil_FreeMemory( auhalHostApi ); } static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ) { int inputChannelCount, outputChannelCount; PaSampleFormat inputSampleFormat, outputSampleFormat; VVDBUG(("IsFormatSupported(): in chan=%d, in fmt=%ld, out chan=%d, out fmt=%ld sampleRate=%g\n", inputParameters ? inputParameters->channelCount : -1, inputParameters ? inputParameters->sampleFormat : -1, outputParameters ? outputParameters->channelCount : -1, outputParameters ? outputParameters->sampleFormat : -1, (float) sampleRate )); /** These first checks are standard PA checks. We do some fancier checks later. */ if( inputParameters ) { inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; /* all standard sample formats are supported by the buffer adapter, this implementation doesn't support any custom sample formats */ if( inputSampleFormat & paCustomFormat ) return paSampleFormatNotSupported; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that input device can support inputChannelCount */ if( inputChannelCount > hostApi->deviceInfos[ inputParameters->device ]->maxInputChannels ) return paInvalidChannelCount; } else { inputChannelCount = 0; } if( outputParameters ) { outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; /* all standard sample formats are supported by the buffer adapter, this implementation doesn't support any custom sample formats */ if( outputSampleFormat & paCustomFormat ) return paSampleFormatNotSupported; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that output device can support outputChannelCount */ if( outputChannelCount > hostApi->deviceInfos[ outputParameters->device ]->maxOutputChannels ) return paInvalidChannelCount; } else { outputChannelCount = 0; } /* FEEDBACK */ /* I think the only way to check a given format SR combo is */ /* to try opening it. This could be disruptive, is that Okay? */ /* The alternative is to just read off available sample rates, */ /* but this will not work %100 of the time (eg, a device that */ /* supports N output at one rate but only N/2 at a higher rate.)*/ /* The following code opens the device with the requested parameters to see if it works. */ { PaError err; PaStream *s; err = OpenStream( hostApi, &s, inputParameters, outputParameters, sampleRate, 1024, 0, (PaStreamCallback *)1, NULL ); if( err != paNoError && err != paInvalidSampleRate ) DBUG( ( "OpenStream @ %g returned: %d: %s\n", (float) sampleRate, err, Pa_GetErrorText( err ) ) ); if( err ) return err; err = CloseStream( s ); if( err ) { /* FEEDBACK: is this more serious? should we assert? */ DBUG( ( "WARNING: could not close Stream. %d: %s\n", err, Pa_GetErrorText( err ) ) ); } } return paFormatIsSupported; } static PaError OpenAndSetupOneAudioUnit( const PaMacCoreStream *stream, const PaStreamParameters *inStreamParams, const PaStreamParameters *outStreamParams, const UInt32 requestedFramesPerBuffer, UInt32 *actualInputFramesPerBuffer, UInt32 *actualOutputFramesPerBuffer, const PaMacAUHAL *auhalHostApi, AudioUnit *audioUnit, AudioConverterRef *srConverter, AudioDeviceID *audioDevice, const double sampleRate, void *refCon ) { ComponentDescription desc; Component comp; /*An Apple TN suggests using CAStreamBasicDescription, but that is C++*/ AudioStreamBasicDescription desiredFormat; OSStatus result = noErr; PaError paResult = paNoError; int line = 0; UInt32 callbackKey; AURenderCallbackStruct rcbs; unsigned long macInputStreamFlags = paMacCorePlayNice; unsigned long macOutputStreamFlags = paMacCorePlayNice; SInt32 const *inChannelMap = NULL; SInt32 const *outChannelMap = NULL; unsigned long inChannelMapSize = 0; unsigned long outChannelMapSize = 0; VVDBUG(("OpenAndSetupOneAudioUnit(): in chan=%d, in fmt=%ld, out chan=%d, out fmt=%ld, requestedFramesPerBuffer=%ld\n", inStreamParams ? inStreamParams->channelCount : -1, inStreamParams ? inStreamParams->sampleFormat : -1, outStreamParams ? outStreamParams->channelCount : -1, outStreamParams ? outStreamParams->sampleFormat : -1, requestedFramesPerBuffer )); /* -- handle the degenerate case -- */ if( !inStreamParams && !outStreamParams ) { *audioUnit = NULL; *audioDevice = kAudioDeviceUnknown; return paNoError; } /* -- get the user's api specific info, if they set any -- */ if( inStreamParams && inStreamParams->hostApiSpecificStreamInfo ) { macInputStreamFlags= ((PaMacCoreStreamInfo*)inStreamParams->hostApiSpecificStreamInfo) ->flags; inChannelMap = ((PaMacCoreStreamInfo*)inStreamParams->hostApiSpecificStreamInfo) ->channelMap; inChannelMapSize = ((PaMacCoreStreamInfo*)inStreamParams->hostApiSpecificStreamInfo) ->channelMapSize; } if( outStreamParams && outStreamParams->hostApiSpecificStreamInfo ) { macOutputStreamFlags= ((PaMacCoreStreamInfo*)outStreamParams->hostApiSpecificStreamInfo) ->flags; outChannelMap = ((PaMacCoreStreamInfo*)outStreamParams->hostApiSpecificStreamInfo) ->channelMap; outChannelMapSize = ((PaMacCoreStreamInfo*)outStreamParams->hostApiSpecificStreamInfo) ->channelMapSize; } /* Override user's flags here, if desired for testing. */ /* * The HAL AU is a Mac OS style "component". * the first few steps deal with that. * Later steps work on a combination of Mac OS * components and the slightly lower level * HAL. */ /* -- describe the output type AudioUnit -- */ /* Note: for the default AudioUnit, we could use the * componentSubType value kAudioUnitSubType_DefaultOutput; * but I don't think that's relevant here. */ desc.componentType = kAudioUnitType_Output; desc.componentSubType = kAudioUnitSubType_HALOutput; desc.componentManufacturer = kAudioUnitManufacturer_Apple; desc.componentFlags = 0; desc.componentFlagsMask = 0; /* -- find the component -- */ comp = FindNextComponent( NULL, &desc ); if( !comp ) { DBUG( ( "AUHAL component not found." ) ); *audioUnit = NULL; *audioDevice = kAudioDeviceUnknown; return paUnanticipatedHostError; } /* -- open it -- */ result = OpenAComponent( comp, audioUnit ); if( result ) { DBUG( ( "Failed to open AUHAL component." ) ); *audioUnit = NULL; *audioDevice = kAudioDeviceUnknown; return ERR( result ); } /* -- prepare a little error handling logic / hackery -- */ #define ERR_WRAP(mac_err) do { result = mac_err ; line = __LINE__ ; if ( result != noErr ) goto error ; } while(0) /* -- if there is input, we have to explicitly enable input -- */ if( inStreamParams ) { UInt32 enableIO = 1; ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioOutputUnitProperty_EnableIO, kAudioUnitScope_Input, INPUT_ELEMENT, &enableIO, sizeof(enableIO) ) ); } /* -- if there is no output, we must explicitly disable output -- */ if( !outStreamParams ) { UInt32 enableIO = 0; ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioOutputUnitProperty_EnableIO, kAudioUnitScope_Output, OUTPUT_ELEMENT, &enableIO, sizeof(enableIO) ) ); } /* -- set the devices -- */ /* make sure input and output are the same device if we are doing input and output. */ if( inStreamParams && outStreamParams ) { assert( outStreamParams->device == inStreamParams->device ); } if( inStreamParams ) { *audioDevice = auhalHostApi->devIds[inStreamParams->device] ; ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioOutputUnitProperty_CurrentDevice, kAudioUnitScope_Global, INPUT_ELEMENT, audioDevice, sizeof(AudioDeviceID) ) ); } if( outStreamParams && outStreamParams != inStreamParams ) { *audioDevice = auhalHostApi->devIds[outStreamParams->device] ; ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioOutputUnitProperty_CurrentDevice, kAudioUnitScope_Global, OUTPUT_ELEMENT, audioDevice, sizeof(AudioDeviceID) ) ); } /* -- add listener for dropouts -- */ ERR_WRAP( AudioDeviceAddPropertyListener( *audioDevice, 0, outStreamParams ? false : true, kAudioDeviceProcessorOverload, xrunCallback, (void *)stream) ); /* -- listen for stream start and stop -- */ ERR_WRAP( AudioUnitAddPropertyListener( *audioUnit, kAudioOutputUnitProperty_IsRunning, startStopCallback, (void *)stream ) ); /* -- set format -- */ bzero( &desiredFormat, sizeof(desiredFormat) ); desiredFormat.mFormatID = kAudioFormatLinearPCM ; desiredFormat.mFormatFlags = kAudioFormatFlagsNativeFloatPacked; desiredFormat.mFramesPerPacket = 1; desiredFormat.mBitsPerChannel = sizeof( float ) * 8; result = 0; /* set device format first, but only touch the device if the user asked */ if( inStreamParams ) { /*The callback never calls back if we don't set the FPB */ /*This seems wierd, because I would think setting anything on the device would be disruptive.*/ paResult = setBestFramesPerBuffer( *audioDevice, FALSE, requestedFramesPerBuffer, actualInputFramesPerBuffer ); if( paResult ) goto error; if( macInputStreamFlags & paMacCoreChangeDeviceParameters ) { bool requireExact; requireExact=macInputStreamFlags & paMacCoreFailIfConversionRequired; paResult = setBestSampleRateForDevice( *audioDevice, FALSE, requireExact, sampleRate ); if( paResult ) goto error; } if( actualInputFramesPerBuffer && actualOutputFramesPerBuffer ) *actualOutputFramesPerBuffer = *actualInputFramesPerBuffer ; } if( outStreamParams && !inStreamParams ) { /*The callback never calls back if we don't set the FPB */ /*This seems wierd, because I would think setting anything on the device would be disruptive.*/ paResult = setBestFramesPerBuffer( *audioDevice, TRUE, requestedFramesPerBuffer, actualOutputFramesPerBuffer ); if( paResult ) goto error; if( macOutputStreamFlags & paMacCoreChangeDeviceParameters ) { bool requireExact; requireExact=macOutputStreamFlags & paMacCoreFailIfConversionRequired; paResult = setBestSampleRateForDevice( *audioDevice, TRUE, requireExact, sampleRate ); if( paResult ) goto error; } } /* -- set the quality of the output converter -- */ if( outStreamParams ) { UInt32 value = kAudioConverterQuality_Max; switch( macOutputStreamFlags & 0x0700 ) { case 0x0100: /*paMacCore_ConversionQualityMin:*/ value=kRenderQuality_Min; break; case 0x0200: /*paMacCore_ConversionQualityLow:*/ value=kRenderQuality_Low; break; case 0x0300: /*paMacCore_ConversionQualityMedium:*/ value=kRenderQuality_Medium; break; case 0x0400: /*paMacCore_ConversionQualityHigh:*/ value=kRenderQuality_High; break; } ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioUnitProperty_RenderQuality, kAudioUnitScope_Global, OUTPUT_ELEMENT, &value, sizeof(value) ) ); } /* now set the format on the Audio Units. */ if( outStreamParams ) { desiredFormat.mSampleRate =sampleRate; desiredFormat.mBytesPerPacket=sizeof(float)*outStreamParams->channelCount; desiredFormat.mBytesPerFrame =sizeof(float)*outStreamParams->channelCount; desiredFormat.mChannelsPerFrame = outStreamParams->channelCount; ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioUnitProperty_StreamFormat, kAudioUnitScope_Input, OUTPUT_ELEMENT, &desiredFormat, sizeof(AudioStreamBasicDescription) ) ); } if( inStreamParams ) { AudioStreamBasicDescription sourceFormat; UInt32 size = sizeof( AudioStreamBasicDescription ); /* keep the sample rate of the device, or we confuse AUHAL */ ERR_WRAP( AudioUnitGetProperty( *audioUnit, kAudioUnitProperty_StreamFormat, kAudioUnitScope_Input, INPUT_ELEMENT, &sourceFormat, &size ) ); desiredFormat.mSampleRate = sourceFormat.mSampleRate; desiredFormat.mBytesPerPacket=sizeof(float)*inStreamParams->channelCount; desiredFormat.mBytesPerFrame =sizeof(float)*inStreamParams->channelCount; desiredFormat.mChannelsPerFrame = inStreamParams->channelCount; ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioUnitProperty_StreamFormat, kAudioUnitScope_Output, INPUT_ELEMENT, &desiredFormat, sizeof(AudioStreamBasicDescription) ) ); } /* set the maximumFramesPerSlice */ /* not doing this causes real problems (eg. the callback might not be called). The idea of setting both this and the frames per buffer on the device is that we'll be most likely to actually get the frame size we requested in the callback with the minimum latency. */ if( outStreamParams ) { UInt32 size = sizeof( *actualOutputFramesPerBuffer ); ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioUnitProperty_MaximumFramesPerSlice, kAudioUnitScope_Input, OUTPUT_ELEMENT, actualOutputFramesPerBuffer, sizeof(*actualOutputFramesPerBuffer) ) ); ERR_WRAP( AudioUnitGetProperty( *audioUnit, kAudioUnitProperty_MaximumFramesPerSlice, kAudioUnitScope_Global, OUTPUT_ELEMENT, actualOutputFramesPerBuffer, &size ) ); } if( inStreamParams ) { /*UInt32 size = sizeof( *actualInputFramesPerBuffer );*/ ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioUnitProperty_MaximumFramesPerSlice, kAudioUnitScope_Output, INPUT_ELEMENT, actualInputFramesPerBuffer, sizeof(*actualInputFramesPerBuffer) ) ); /* Don't know why this causes problems ERR_WRAP( AudioUnitGetProperty( *audioUnit, kAudioUnitProperty_MaximumFramesPerSlice, kAudioUnitScope_Global, //Output, INPUT_ELEMENT, actualInputFramesPerBuffer, &size ) ); */ } /* -- if we have input, we may need to setup an SR converter -- */ /* even if we got the sample rate we asked for, we need to do the conversion in case another program changes the underlying SR. */ /* FIXME: I think we need to monitor stream and change the converter if the incoming format changes. */ if( inStreamParams ) { AudioStreamBasicDescription desiredFormat; AudioStreamBasicDescription sourceFormat; UInt32 sourceSize = sizeof( sourceFormat ); bzero( &desiredFormat, sizeof(desiredFormat) ); desiredFormat.mSampleRate = sampleRate; desiredFormat.mFormatID = kAudioFormatLinearPCM ; desiredFormat.mFormatFlags = kAudioFormatFlagsNativeFloatPacked; desiredFormat.mFramesPerPacket = 1; desiredFormat.mBitsPerChannel = sizeof( float ) * 8; desiredFormat.mBytesPerPacket=sizeof(float)*inStreamParams->channelCount; desiredFormat.mBytesPerFrame =sizeof(float)*inStreamParams->channelCount; desiredFormat.mChannelsPerFrame = inStreamParams->channelCount; /* get the source format */ ERR_WRAP( AudioUnitGetProperty( *audioUnit, kAudioUnitProperty_StreamFormat, kAudioUnitScope_Output, INPUT_ELEMENT, &sourceFormat, &sourceSize ) ); if( desiredFormat.mSampleRate != sourceFormat.mSampleRate ) { UInt32 value = kAudioConverterQuality_Max; switch( macInputStreamFlags & 0x0700 ) { case 0x0100: /*paMacCore_ConversionQualityMin:*/ value=kAudioConverterQuality_Min; break; case 0x0200: /*paMacCore_ConversionQualityLow:*/ value=kAudioConverterQuality_Low; break; case 0x0300: /*paMacCore_ConversionQualityMedium:*/ value=kAudioConverterQuality_Medium; break; case 0x0400: /*paMacCore_ConversionQualityHigh:*/ value=kAudioConverterQuality_High; break; } VDBUG(( "Creating sample rate converter for input" " to convert from %g to %g\n", (float)sourceFormat.mSampleRate, (float)desiredFormat.mSampleRate ) ); /* create our converter */ ERR_WRAP( AudioConverterNew( &sourceFormat, &desiredFormat, srConverter ) ); /* Set quality */ ERR_WRAP( AudioConverterSetProperty( *srConverter, kAudioConverterSampleRateConverterQuality, sizeof( value ), &value ) ); } } /* -- set IOProc (callback) -- */ callbackKey = outStreamParams ? kAudioUnitProperty_SetRenderCallback : kAudioOutputUnitProperty_SetInputCallback ; rcbs.inputProc = AudioIOProc; rcbs.inputProcRefCon = refCon; ERR_WRAP( AudioUnitSetProperty( *audioUnit, callbackKey, kAudioUnitScope_Output, outStreamParams ? OUTPUT_ELEMENT : INPUT_ELEMENT, &rcbs, sizeof(rcbs)) ); if( inStreamParams && outStreamParams && *srConverter ) ERR_WRAP( AudioUnitSetProperty( *audioUnit, kAudioOutputUnitProperty_SetInputCallback, kAudioUnitScope_Output, INPUT_ELEMENT, &rcbs, sizeof(rcbs)) ); /* channel mapping. */ if(inChannelMap) { UInt32 mapSize = inChannelMapSize *sizeof(SInt32); //for each channel of desired input, map the channel from //the device's output channel. ERR_WRAP( AudioUnitSetProperty(*audioUnit, kAudioOutputUnitProperty_ChannelMap, kAudioUnitScope_Output, INPUT_ELEMENT, inChannelMap, mapSize)); } if(outChannelMap) { UInt32 mapSize = outChannelMapSize *sizeof(SInt32); //for each channel of desired output, map the channel from //the device's output channel. ERR_WRAP(AudioUnitSetProperty(*audioUnit, kAudioOutputUnitProperty_ChannelMap, kAudioUnitScope_Output, OUTPUT_ELEMENT, outChannelMap, mapSize)); } /* initialize the audio unit */ ERR_WRAP( AudioUnitInitialize(*audioUnit) ); if( inStreamParams && outStreamParams ) VDBUG( ("Opened device %ld for input and output.\n", *audioDevice ) ); else if( inStreamParams ) VDBUG( ("Opened device %ld for input.\n", *audioDevice ) ); else if( outStreamParams ) VDBUG( ("Opened device %ld for output.\n", *audioDevice ) ); return paNoError; #undef ERR_WRAP error: CloseComponent( *audioUnit ); *audioUnit = NULL; if( result ) return PaMacCore_SetError( result, line, 1 ); return paResult; } /* see pa_hostapi.h for a list of validity guarantees made about OpenStream parameters */ static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ) { PaError result = paNoError; PaMacAUHAL *auhalHostApi = (PaMacAUHAL*)hostApi; PaMacCoreStream *stream = 0; int inputChannelCount, outputChannelCount; PaSampleFormat inputSampleFormat, outputSampleFormat; PaSampleFormat hostInputSampleFormat, hostOutputSampleFormat; VVDBUG(("OpenStream(): in chan=%d, in fmt=%ld, out chan=%d, out fmt=%ld SR=%g, FPB=%ld\n", inputParameters ? inputParameters->channelCount : -1, inputParameters ? inputParameters->sampleFormat : -1, outputParameters ? outputParameters->channelCount : -1, outputParameters ? outputParameters->sampleFormat : -1, (float) sampleRate, framesPerBuffer )); VDBUG( ("Opening Stream.\n") ); /*These first few bits of code are from paSkeleton with few modifications.*/ if( inputParameters ) { inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that input device can support inputChannelCount */ if( inputChannelCount > hostApi->deviceInfos[ inputParameters->device ]->maxInputChannels ) return paInvalidChannelCount; /* Host supports interleaved float32 */ hostInputSampleFormat = paFloat32; } else { inputChannelCount = 0; inputSampleFormat = hostInputSampleFormat = paFloat32; /* Surpress 'uninitialised var' warnings. */ } if( outputParameters ) { outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that output device can support inputChannelCount */ if( outputChannelCount > hostApi->deviceInfos[ outputParameters->device ]->maxOutputChannels ) return paInvalidChannelCount; /* Host supports interleaved float32 */ hostOutputSampleFormat = paFloat32; } else { outputChannelCount = 0; outputSampleFormat = hostOutputSampleFormat = paFloat32; /* Surpress 'uninitialized var' warnings. */ } /* validate platform specific flags */ if( (streamFlags & paPlatformSpecificFlags) != 0 ) return paInvalidFlag; /* unexpected platform specific flag */ stream = (PaMacCoreStream*)PaUtil_AllocateMemory( sizeof(PaMacCoreStream) ); if( !stream ) { result = paInsufficientMemory; goto error; } /* If we fail after this point, we my be left in a bad state, with some data structures setup and others not. So, first thing we do is initialize everything so that if we fail, we know what hasn't been touched. */ stream->inputAudioBufferList.mBuffers[0].mData = NULL; stream->inputRingBuffer.buffer = NULL; bzero( &stream->blio, sizeof( PaMacBlio ) ); /* stream->blio.inputRingBuffer.buffer = NULL; stream->blio.outputRingBuffer.buffer = NULL; stream->blio.inputSampleFormat = inputParameters?inputParameters->sampleFormat:0; stream->blio.inputSampleSize = computeSampleSizeFromFormat(stream->blio.inputSampleFormat); stream->blio.outputSampleFormat=outputParameters?outputParameters->sampleFormat:0; stream->blio.outputSampleSize = computeSampleSizeFromFormat(stream->blio.outputSampleFormat); */ stream->inputSRConverter = NULL; stream->inputUnit = NULL; stream->outputUnit = NULL; stream->inputFramesPerBuffer = 0; stream->outputFramesPerBuffer = 0; stream->bufferProcessorIsInitialized = FALSE; /* assert( streamCallback ) ; */ /* only callback mode is implemented */ if( streamCallback ) { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &auhalHostApi->callbackStreamInterface, streamCallback, userData ); } else { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &auhalHostApi->blockingStreamInterface, BlioCallback, &stream->blio ); } PaUtil_InitializeCpuLoadMeasurer( &stream->cpuLoadMeasurer, sampleRate ); /* -- handle paFramesPerBufferUnspecified -- */ if( framesPerBuffer == paFramesPerBufferUnspecified ) { long requested = 64; if( inputParameters ) requested = MAX( requested, inputParameters->suggestedLatency * sampleRate / 2 ); if( outputParameters ) requested = MAX( requested, outputParameters->suggestedLatency *sampleRate / 2 ); VDBUG( ("Block Size unspecified. Based on Latency, the user wants a Block Size near: %ld.\n", requested ) ); if( requested <= 64 ) { /*requested a realtively low latency. make sure this is in range of devices */ /*try to get the device's min natural buffer size and use that (but no smaller than 64).*/ AudioValueRange audioRange; UInt32 size = sizeof( audioRange ); if( inputParameters ) { WARNING( result = AudioDeviceGetProperty( auhalHostApi->devIds[inputParameters->device], 0, false, kAudioDevicePropertyBufferFrameSizeRange, &size, &audioRange ) ); if( result ) requested = MAX( requested, audioRange.mMinimum ); } size = sizeof( audioRange ); if( outputParameters ) { WARNING( result = AudioDeviceGetProperty( auhalHostApi->devIds[outputParameters->device], 0, false, kAudioDevicePropertyBufferFrameSizeRange, &size, &audioRange ) ); if( result ) requested = MAX( requested, audioRange.mMinimum ); } } else { /* requested a realtively high latency. make sure this is in range of devices */ /*try to get the device's max natural buffer size and use that (but no larger than 1024).*/ AudioValueRange audioRange; UInt32 size = sizeof( audioRange ); requested = MIN( requested, 1024 ); if( inputParameters ) { WARNING( result = AudioDeviceGetProperty( auhalHostApi->devIds[inputParameters->device], 0, false, kAudioDevicePropertyBufferFrameSizeRange, &size, &audioRange ) ); if( result ) requested = MIN( requested, audioRange.mMaximum ); } size = sizeof( audioRange ); if( outputParameters ) { WARNING( result = AudioDeviceGetProperty( auhalHostApi->devIds[outputParameters->device], 0, false, kAudioDevicePropertyBufferFrameSizeRange, &size, &audioRange ) ); if( result ) requested = MIN( requested, audioRange.mMaximum ); } } /* -- double check ranges -- */ if( requested > 1024 ) requested = 1024; if( requested < 64 ) requested = 64; VDBUG(("After querying hardware, setting block size to %ld.\n", requested)); framesPerBuffer = requested; } /* -- Now we actually open and setup streams. -- */ if( inputParameters && outputParameters && outputParameters->device == inputParameters->device ) { /* full duplex. One device. */ UInt32 inputFramesPerBuffer = (UInt32) stream->inputFramesPerBuffer; UInt32 outputFramesPerBuffer = (UInt32) stream->outputFramesPerBuffer; result = OpenAndSetupOneAudioUnit( stream, inputParameters, outputParameters, framesPerBuffer, &inputFramesPerBuffer, &outputFramesPerBuffer, auhalHostApi, &(stream->inputUnit), &(stream->inputSRConverter), &(stream->inputDevice), sampleRate, stream ); stream->inputFramesPerBuffer = inputFramesPerBuffer; stream->outputFramesPerBuffer = outputFramesPerBuffer; stream->outputUnit = stream->inputUnit; stream->outputDevice = stream->inputDevice; if( result != paNoError ) goto error; } else { /* full duplex, different devices OR simplex */ UInt32 outputFramesPerBuffer = (UInt32) stream->outputFramesPerBuffer; UInt32 inputFramesPerBuffer = (UInt32) stream->inputFramesPerBuffer; result = OpenAndSetupOneAudioUnit( stream, NULL, outputParameters, framesPerBuffer, NULL, &outputFramesPerBuffer, auhalHostApi, &(stream->outputUnit), NULL, &(stream->outputDevice), sampleRate, stream ); if( result != paNoError ) goto error; result = OpenAndSetupOneAudioUnit( stream, inputParameters, NULL, framesPerBuffer, &inputFramesPerBuffer, NULL, auhalHostApi, &(stream->inputUnit), &(stream->inputSRConverter), &(stream->inputDevice), sampleRate, stream ); if( result != paNoError ) goto error; stream->inputFramesPerBuffer = inputFramesPerBuffer; stream->outputFramesPerBuffer = outputFramesPerBuffer; } if( stream->inputUnit ) { const size_t szfl = sizeof(float); /* setup the AudioBufferList used for input */ bzero( &stream->inputAudioBufferList, sizeof( AudioBufferList ) ); stream->inputAudioBufferList.mNumberBuffers = 1; stream->inputAudioBufferList.mBuffers[0].mNumberChannels = inputChannelCount; stream->inputAudioBufferList.mBuffers[0].mDataByteSize = stream->inputFramesPerBuffer*inputChannelCount*szfl; stream->inputAudioBufferList.mBuffers[0].mData = (float *) calloc( stream->inputFramesPerBuffer*inputChannelCount, szfl ); if( !stream->inputAudioBufferList.mBuffers[0].mData ) { result = paInsufficientMemory; goto error; } /* * If input and output devs are different or we are doing SR conversion, * we also need a * ring buffer to store inpt data while waiting for output * data. */ if( (stream->outputUnit && stream->inputUnit != stream->outputUnit) || stream->inputSRConverter ) { /* May want the ringSize ot initial position in ring buffer to depend somewhat on sample rate change */ void *data; long ringSize; ringSize = computeRingBufferSize( inputParameters, outputParameters, stream->inputFramesPerBuffer, stream->outputFramesPerBuffer, sampleRate ); /*ringSize <<= 4; *//*16x bigger, for testing */ /*now, we need to allocate memory for the ring buffer*/ data = calloc( ringSize, szfl ); if( !data ) { result = paInsufficientMemory; goto error; } /* now we can initialize the ring buffer */ PaUtil_InitializeRingBuffer( &stream->inputRingBuffer, ringSize*szfl, data ) ; /* advance the read point a little, so we are reading from the middle of the buffer */ if( stream->outputUnit ) PaUtil_AdvanceRingBufferWriteIndex( &stream->inputRingBuffer, ringSize*szfl / RING_BUFFER_ADVANCE_DENOMINATOR ); } } /* -- initialize Blio Buffer Processors -- */ if( !streamCallback ) { long ringSize; ringSize = computeRingBufferSize( inputParameters, outputParameters, stream->inputFramesPerBuffer, stream->outputFramesPerBuffer, sampleRate ); result = initializeBlioRingBuffers( &stream->blio, inputParameters?inputParameters->sampleFormat:0 , outputParameters?outputParameters->sampleFormat:0 , MAX(stream->inputFramesPerBuffer,stream->outputFramesPerBuffer), ringSize, inputParameters?inputChannelCount:0 , outputParameters?outputChannelCount:0 ) ; if( result != paNoError ) goto error; } /* -- initialize Buffer Processor -- */ { unsigned long maxHostFrames = stream->inputFramesPerBuffer; if( stream->outputFramesPerBuffer > maxHostFrames ) maxHostFrames = stream->outputFramesPerBuffer; result = PaUtil_InitializeBufferProcessor( &stream->bufferProcessor, inputChannelCount, inputSampleFormat, hostInputSampleFormat, outputChannelCount, outputSampleFormat, hostOutputSampleFormat, sampleRate, streamFlags, framesPerBuffer, /* If sample rate conversion takes place, the buffer size will not be known. */ maxHostFrames, stream->inputSRConverter ? paUtilUnknownHostBufferSize : paUtilBoundedHostBufferSize, streamCallback ? streamCallback : BlioCallback, streamCallback ? userData : &stream->blio ); if( result != paNoError ) goto error; } stream->bufferProcessorIsInitialized = TRUE; /* IMPLEMENT ME: initialise the following fields with estimated or actual values. I think this is okay the way it is br 12/1/05 maybe need to change input latency estimate if IO devs differ */ stream->streamRepresentation.streamInfo.inputLatency = PaUtil_GetBufferProcessorInputLatency(&stream->bufferProcessor)/sampleRate; stream->streamRepresentation.streamInfo.outputLatency = PaUtil_GetBufferProcessorOutputLatency(&stream->bufferProcessor)/sampleRate; stream->streamRepresentation.streamInfo.sampleRate = sampleRate; stream->sampleRate = sampleRate; stream->outDeviceSampleRate = 0; if( stream->outputUnit ) { Float64 rate; UInt32 size = sizeof( rate ); result = ERR( AudioDeviceGetProperty( stream->outputDevice, 0, FALSE, kAudioDevicePropertyNominalSampleRate, &size, &rate ) ); if( result ) goto error; stream->outDeviceSampleRate = rate; } stream->inDeviceSampleRate = 0; if( stream->inputUnit ) { Float64 rate; UInt32 size = sizeof( rate ); result = ERR( AudioDeviceGetProperty( stream->inputDevice, 0, TRUE, kAudioDevicePropertyNominalSampleRate, &size, &rate ) ); if( result ) goto error; stream->inDeviceSampleRate = rate; } stream->userInChan = inputChannelCount; stream->userOutChan = outputChannelCount; stream->isTimeSet = FALSE; stream->state = STOPPED; stream->xrunFlags = 0; *s = (PaStream*)stream; return result; error: CloseStream( stream ); return result; } PaTime GetStreamTime( PaStream *s ) { /* FIXME: I am not at all sure this timing info stuff is right. patest_sine_time reports negative latencies, which is wierd.*/ PaMacCoreStream *stream = (PaMacCoreStream*)s; AudioTimeStamp timeStamp; VVDBUG(("GetStreamTime()\n")); if ( !stream->isTimeSet ) return (PaTime)0; if ( stream->outputDevice ) { AudioDeviceGetCurrentTime( stream->outputDevice, &timeStamp); return (PaTime)(timeStamp.mSampleTime - stream->startTime.mSampleTime)/stream->outDeviceSampleRate; } else if ( stream->inputDevice ) { AudioDeviceGetCurrentTime( stream->inputDevice, &timeStamp); return (PaTime)(timeStamp.mSampleTime - stream->startTime.mSampleTime)/stream->inDeviceSampleRate; } else { return (PaTime)0; } } static void setStreamStartTime( PaStream *stream ) { /* FIXME: I am not at all sure this timing info stuff is right. patest_sine_time reports negative latencies, which is wierd.*/ PaMacCoreStream *s = (PaMacCoreStream *) stream; VVDBUG(("setStreamStartTime()\n")); if( s->outputDevice ) AudioDeviceGetCurrentTime( s->outputDevice, &s->startTime); else if( s->inputDevice ) AudioDeviceGetCurrentTime( s->inputDevice, &s->startTime); else bzero( &s->startTime, sizeof( s->startTime ) ); //FIXME: we need a memory barier here s->isTimeSet = TRUE; } static PaTime TimeStampToSecs(PaMacCoreStream *stream, const AudioTimeStamp* timeStamp) { VVDBUG(("TimeStampToSecs()\n")); //printf( "ATS: %lu, %g, %g\n", timeStamp->mFlags, timeStamp->mSampleTime, timeStamp->mRateScalar ); if (timeStamp->mFlags & kAudioTimeStampSampleTimeValid) return (timeStamp->mSampleTime / stream->sampleRate); else return 0; } #define RING_BUFFER_EMPTY (1000) static OSStatus ringBufferIOProc( AudioConverterRef inAudioConverter, UInt32*ioDataSize, void** outData, void*inUserData ) { void *dummyData; long dummySize; PaUtilRingBuffer *rb = (PaUtilRingBuffer *) inUserData; VVDBUG(("ringBufferIOProc()\n")); assert( sizeof( UInt32 ) == sizeof( long ) ); if( PaUtil_GetRingBufferReadAvailable( rb ) == 0 ) { *outData = NULL; *ioDataSize = 0; return RING_BUFFER_EMPTY; } PaUtil_GetRingBufferReadRegions( rb, *ioDataSize, outData, (long *)ioDataSize, &dummyData, &dummySize ); assert( *ioDataSize ); PaUtil_AdvanceRingBufferReadIndex( rb, *ioDataSize ); return noErr; } /* * Called by the AudioUnit API to process audio from the sound card. * This is where the magic happens. */ /* FEEDBACK: there is a lot of redundant code here because of how all the cases differ. This makes it hard to maintain, so if there are suggestinos for cleaning it up, I'm all ears. */ static OSStatus AudioIOProc( void *inRefCon, AudioUnitRenderActionFlags *ioActionFlags, const AudioTimeStamp *inTimeStamp, UInt32 inBusNumber, UInt32 inNumberFrames, AudioBufferList *ioData ) { unsigned long framesProcessed = 0; PaStreamCallbackTimeInfo timeInfo = {0,0,0}; PaMacCoreStream *stream = (PaMacCoreStream*)inRefCon; const bool isRender = inBusNumber == OUTPUT_ELEMENT; int callbackResult = paContinue ; VVDBUG(("AudioIOProc()\n")); PaUtil_BeginCpuLoadMeasurement( &stream->cpuLoadMeasurer ); /* -----------------------------------------------------------------*\ This output may be useful for debugging, But printing durring the callback is a bad enough idea that this is not enabled by enableing the usual debugging calls. \* -----------------------------------------------------------------*/ /* static int renderCount = 0; static int inputCount = 0; printf( "------------------- starting reder/input\n" ); if( isRender ) printf("Render callback (%d):\t", ++renderCount); else printf("Input callback (%d):\t", ++inputCount); printf( "Call totals: %d (input), %d (render)\n", inputCount, renderCount ); printf( "--- inBusNumber: %lu\n", inBusNumber ); printf( "--- inNumberFrames: %lu\n", inNumberFrames ); printf( "--- %x ioData\n", (unsigned) ioData ); if( ioData ) { int i=0; printf( "--- ioData.mNumBuffers %lu: \n", ioData->mNumberBuffers ); for( i=0; imNumberBuffers; ++i ) printf( "--- ioData buffer %d size: %lu.\n", i, ioData->mBuffers[i].mDataByteSize ); } ----------------------------------------------------------------- */ if( !stream->isTimeSet ) setStreamStartTime( stream ); if( isRender ) { AudioTimeStamp currentTime; timeInfo.outputBufferDacTime = TimeStampToSecs(stream, inTimeStamp); AudioDeviceGetCurrentTime(stream->outputDevice, ¤tTime); timeInfo.currentTime = TimeStampToSecs(stream, ¤tTime); } if( isRender && stream->inputUnit == stream->outputUnit ) timeInfo.inputBufferAdcTime = TimeStampToSecs(stream, inTimeStamp); if( !isRender ) { AudioTimeStamp currentTime; timeInfo.inputBufferAdcTime = TimeStampToSecs(stream, inTimeStamp); AudioDeviceGetCurrentTime(stream->inputDevice, ¤tTime); timeInfo.currentTime = TimeStampToSecs(stream, ¤tTime); } //printf( "---%g, %g, %g\n", timeInfo.inputBufferAdcTime, timeInfo.currentTime, timeInfo.outputBufferDacTime ); if( isRender && stream->inputUnit == stream->outputUnit && !stream->inputSRConverter ) { /* --------- Full Duplex, One Device, no SR Conversion ------- * * This is the lowest latency case, and also the simplest. * Input data and output data are available at the same time. * we do not use the input SR converter or the input ring buffer. * */ OSStatus err = 0; unsigned long frames; /* -- start processing -- */ PaUtil_BeginBufferProcessing( &(stream->bufferProcessor), &timeInfo, stream->xrunFlags ); stream->xrunFlags = 0; //FIXME: this flag also gets set outside by a callback, which calls the xrunCallback function. It should be in the same thread as the main audio callback, but the apple docs just use the word "usually" so it may be possible to loose an xrun notification, if that callback happens here. /* -- compute frames. do some checks -- */ assert( ioData->mNumberBuffers == 1 ); assert( ioData->mBuffers[0].mNumberChannels == stream->userOutChan ); frames = ioData->mBuffers[0].mDataByteSize; frames /= sizeof( float ) * ioData->mBuffers[0].mNumberChannels; /* -- copy and process input data -- */ err= AudioUnitRender(stream->inputUnit, ioActionFlags, inTimeStamp, INPUT_ELEMENT, inNumberFrames, &stream->inputAudioBufferList ); /* FEEDBACK: I'm not sure what to do when this call fails */ assert( !err ); PaUtil_SetInputFrameCount( &(stream->bufferProcessor), frames ); PaUtil_SetInterleavedInputChannels( &(stream->bufferProcessor), 0, stream->inputAudioBufferList.mBuffers[0].mData, stream->inputAudioBufferList.mBuffers[0].mNumberChannels); /* -- Copy and process output data -- */ PaUtil_SetOutputFrameCount( &(stream->bufferProcessor), frames ); PaUtil_SetInterleavedOutputChannels( &(stream->bufferProcessor), 0, ioData->mBuffers[0].mData, ioData->mBuffers[0].mNumberChannels); /* -- complete processing -- */ framesProcessed = PaUtil_EndBufferProcessing( &(stream->bufferProcessor), &callbackResult ); } else if( isRender ) { /* -------- Output Side of Full Duplex (Separate Devices or SR Conversion) * -- OR Simplex Output * * This case handles output data as in the full duplex case, * and, if there is input data, reads it off the ring buffer * and into the PA buffer processor. If sample rate conversion * is required on input, that is done here as well. */ unsigned long frames; /* Sometimes, when stopping a duplex stream we get erroneous xrun flags, so if this is our last run, clear the flags. */ int xrunFlags = stream->xrunFlags; /* if( xrunFlags & paInputUnderflow ) printf( "input underflow.\n" ); if( xrunFlags & paInputOverflow ) printf( "input overflow.\n" ); */ if( stream->state == STOPPING || stream->state == CALLBACK_STOPPED ) xrunFlags = 0; /* -- start processing -- */ PaUtil_BeginBufferProcessing( &(stream->bufferProcessor), &timeInfo, xrunFlags ); stream->xrunFlags = 0; /* FEEDBACK: we only send flags to Buf Proc once */ /* -- Copy and process output data -- */ assert( ioData->mNumberBuffers == 1 ); frames = ioData->mBuffers[0].mDataByteSize; frames /= sizeof( float ) * ioData->mBuffers[0].mNumberChannels; assert( ioData->mBuffers[0].mNumberChannels == stream->userOutChan ); PaUtil_SetOutputFrameCount( &(stream->bufferProcessor), frames ); PaUtil_SetInterleavedOutputChannels( &(stream->bufferProcessor), 0, ioData->mBuffers[0].mData, ioData->mBuffers[0].mNumberChannels); /* -- copy and process input data, and complete processing -- */ if( stream->inputUnit ) { const int flsz = sizeof( float ); /* Here, we read the data out of the ring buffer, through the audio converter. */ int inChan = stream->inputAudioBufferList.mBuffers[0].mNumberChannels; if( stream->inputSRConverter ) { OSStatus err; UInt32 size; float data[ inChan * frames ]; size = sizeof( data ); err = AudioConverterFillBuffer( stream->inputSRConverter, ringBufferIOProc, &stream->inputRingBuffer, &size, (void *)&data ); if( err == RING_BUFFER_EMPTY ) { /*the ring buffer callback underflowed */ err = 0; bzero( ((char *)data) + size, sizeof(data)-size ); stream->xrunFlags |= paInputUnderflow; } ERR( err ); assert( !err ); PaUtil_SetInputFrameCount( &(stream->bufferProcessor), frames ); PaUtil_SetInterleavedInputChannels( &(stream->bufferProcessor), 0, data, inChan ); framesProcessed = PaUtil_EndBufferProcessing( &(stream->bufferProcessor), &callbackResult ); } else { /* Without the AudioConverter is actually a bit more complex because we have to do a little buffer processing that the AudioConverter would otherwise handle for us. */ void *data1, *data2; long size1, size2; PaUtil_GetRingBufferReadRegions( &stream->inputRingBuffer, inChan*frames*flsz, &data1, &size1, &data2, &size2 ); if( size1 / ( flsz * inChan ) == frames ) { /* simplest case: all in first buffer */ PaUtil_SetInputFrameCount( &(stream->bufferProcessor), frames ); PaUtil_SetInterleavedInputChannels( &(stream->bufferProcessor), 0, data1, inChan ); framesProcessed = PaUtil_EndBufferProcessing( &(stream->bufferProcessor), &callbackResult ); PaUtil_AdvanceRingBufferReadIndex(&stream->inputRingBuffer, size1 ); } else if( ( size1 + size2 ) / ( flsz * inChan ) < frames ) { /*we underflowed. take what data we can, zero the rest.*/ unsigned char data[frames*inChan*flsz]; if( size1 ) memcpy( data, data1, size1 ); if( size2 ) memcpy( data+size1, data2, size2 ); bzero( data+size1+size2, frames*flsz*inChan - size1 - size2 ); PaUtil_SetInputFrameCount( &(stream->bufferProcessor), frames ); PaUtil_SetInterleavedInputChannels( &(stream->bufferProcessor), 0, data, inChan ); framesProcessed = PaUtil_EndBufferProcessing( &(stream->bufferProcessor), &callbackResult ); PaUtil_AdvanceRingBufferReadIndex( &stream->inputRingBuffer, size1+size2 ); /* flag underflow */ stream->xrunFlags |= paInputUnderflow; } else { /*we got all the data, but split between buffers*/ PaUtil_SetInputFrameCount( &(stream->bufferProcessor), size1 / ( flsz * inChan ) ); PaUtil_SetInterleavedInputChannels( &(stream->bufferProcessor), 0, data1, inChan ); PaUtil_Set2ndInputFrameCount( &(stream->bufferProcessor), size2 / ( flsz * inChan ) ); PaUtil_Set2ndInterleavedInputChannels( &(stream->bufferProcessor), 0, data2, inChan ); framesProcessed = PaUtil_EndBufferProcessing( &(stream->bufferProcessor), &callbackResult ); PaUtil_AdvanceRingBufferReadIndex(&stream->inputRingBuffer, size1+size2 ); } } } else { framesProcessed = PaUtil_EndBufferProcessing( &(stream->bufferProcessor), &callbackResult ); } } else { /* ------------------ Input * * First, we read off the audio data and put it in the ring buffer. * if this is an input-only stream, we need to process it more, * otherwise, we let the output case deal with it. */ OSStatus err = 0; int chan = stream->inputAudioBufferList.mBuffers[0].mNumberChannels ; /* FIXME: looping here may not actually be necessary, but it was something I tried in testing. */ do { err= AudioUnitRender(stream->inputUnit, ioActionFlags, inTimeStamp, INPUT_ELEMENT, inNumberFrames, &stream->inputAudioBufferList ); if( err == -10874 ) inNumberFrames /= 2; } while( err == -10874 && inNumberFrames > 1 ); /* FEEDBACK: I'm not sure what to do when this call fails */ ERR( err ); assert( !err ); if( stream->inputSRConverter || stream->outputUnit ) { /* If this is duplex or we use a converter, put the data into the ring buffer. */ long bytesIn, bytesOut; bytesIn = sizeof( float ) * inNumberFrames * chan; bytesOut = PaUtil_WriteRingBuffer( &stream->inputRingBuffer, stream->inputAudioBufferList.mBuffers[0].mData, bytesIn ); if( bytesIn != bytesOut ) stream->xrunFlags |= paInputOverflow ; } else { /* for simplex input w/o SR conversion, just pop the data into the buffer processor.*/ PaUtil_BeginBufferProcessing( &(stream->bufferProcessor), &timeInfo, stream->xrunFlags ); stream->xrunFlags = 0; PaUtil_SetInputFrameCount( &(stream->bufferProcessor), inNumberFrames); PaUtil_SetInterleavedInputChannels( &(stream->bufferProcessor), 0, stream->inputAudioBufferList.mBuffers[0].mData, chan ); framesProcessed = PaUtil_EndBufferProcessing( &(stream->bufferProcessor), &callbackResult ); } if( !stream->outputUnit && stream->inputSRConverter ) { /* ------------------ Simplex Input w/ SR Conversion * * if this is a simplex input stream, we need to read off the buffer, * do our sample rate conversion and pass the results to the buffer * processor. * The logic here is complicated somewhat by the fact that we don't * know how much data is available, so we loop on reasonably sized * chunks, and let the BufferProcessor deal with the rest. * */ /*This might be too big or small depending on SR conversion*/ float data[ chan * inNumberFrames ]; OSStatus err; do { /*Run the buffer processor until we are out of data*/ UInt32 size; long f; size = sizeof( data ); err = AudioConverterFillBuffer( stream->inputSRConverter, ringBufferIOProc, &stream->inputRingBuffer, &size, (void *)data ); if( err != RING_BUFFER_EMPTY ) ERR( err ); assert( err == 0 || err == RING_BUFFER_EMPTY ); f = size / ( chan * sizeof(float) ); PaUtil_SetInputFrameCount( &(stream->bufferProcessor), f ); if( f ) { PaUtil_BeginBufferProcessing( &(stream->bufferProcessor), &timeInfo, stream->xrunFlags ); stream->xrunFlags = 0; PaUtil_SetInterleavedInputChannels( &(stream->bufferProcessor), 0, data, chan ); framesProcessed = PaUtil_EndBufferProcessing( &(stream->bufferProcessor), &callbackResult ); } } while( callbackResult == paContinue && !err ); } } switch( callbackResult ) { case paContinue: break; case paComplete: case paAbort: stream->isTimeSet = FALSE; stream->state = CALLBACK_STOPPED ; if( stream->outputUnit ) AudioOutputUnitStop(stream->outputUnit); if( stream->inputUnit ) AudioOutputUnitStop(stream->inputUnit); break; } PaUtil_EndCpuLoadMeasurement( &stream->cpuLoadMeasurer, framesProcessed ); return noErr; } /* When CloseStream() is called, the multi-api layer ensures that the stream has already been stopped or aborted. */ static PaError CloseStream( PaStream* s ) { /* This may be called from a failed OpenStream. Therefore, each piece of info is treated seperately. */ PaError result = paNoError; PaMacCoreStream *stream = (PaMacCoreStream*)s; VVDBUG(("CloseStream()\n")); VDBUG( ( "Closing stream.\n" ) ); if( stream ) { if( stream->outputUnit ) AudioDeviceRemovePropertyListener( stream->outputDevice, 0, false, kAudioDeviceProcessorOverload, xrunCallback ); if( stream->inputUnit && stream->outputUnit != stream->inputUnit ) AudioDeviceRemovePropertyListener( stream->inputDevice, 0, true, kAudioDeviceProcessorOverload, xrunCallback ); if( stream->outputUnit && stream->outputUnit != stream->inputUnit ) { AudioUnitUninitialize( stream->outputUnit ); CloseComponent( stream->outputUnit ); } stream->outputUnit = NULL; if( stream->inputUnit ) { AudioUnitUninitialize( stream->inputUnit ); CloseComponent( stream->inputUnit ); stream->inputUnit = NULL; } if( stream->inputRingBuffer.buffer ) free( (void *) stream->inputRingBuffer.buffer ); stream->inputRingBuffer.buffer = NULL; /*TODO: is there more that needs to be done on error from AudioConverterDispose?*/ if( stream->inputSRConverter ) ERR( AudioConverterDispose( stream->inputSRConverter ) ); stream->inputSRConverter = NULL; if( stream->inputAudioBufferList.mBuffers[0].mData ) free( stream->inputAudioBufferList.mBuffers[0].mData ); stream->inputAudioBufferList.mBuffers[0].mData = NULL; result = destroyBlioRingBuffers( &stream->blio ); if( result ) return result; if( stream->bufferProcessorIsInitialized ) PaUtil_TerminateBufferProcessor( &stream->bufferProcessor ); PaUtil_TerminateStreamRepresentation( &stream->streamRepresentation ); PaUtil_FreeMemory( stream ); } return result; } static PaError StartStream( PaStream *s ) { PaMacCoreStream *stream = (PaMacCoreStream*)s; OSStatus result = noErr; VVDBUG(("StartStream()\n")); VDBUG( ( "Starting stream.\n" ) ); #define ERR_WRAP(mac_err) do { result = mac_err ; if ( result != noErr ) return ERR(result) ; } while(0) /*FIXME: maybe want to do this on close/abort for faster start? */ PaUtil_ResetBufferProcessor( &stream->bufferProcessor ); if( stream->inputSRConverter ) ERR_WRAP( AudioConverterReset( stream->inputSRConverter ) ); /* -- start -- */ stream->state = ACTIVE; if( stream->inputUnit ) { ERR_WRAP( AudioOutputUnitStart(stream->inputUnit) ); } if( stream->outputUnit && stream->outputUnit != stream->inputUnit ) { ERR_WRAP( AudioOutputUnitStart(stream->outputUnit) ); } //setStreamStartTime( stream ); //stream->isTimeSet = TRUE; return paNoError; #undef ERR_WRAP } // it's not clear from appl's docs that this really waits // until all data is flushed. static ComponentResult BlockWhileAudioUnitIsRunning( AudioUnit audioUnit, AudioUnitElement element ) { Boolean isRunning = 1; while( isRunning ) { UInt32 s = sizeof( isRunning ); ComponentResult err = AudioUnitGetProperty( audioUnit, kAudioOutputUnitProperty_IsRunning, kAudioUnitScope_Global, element, &isRunning, &s ); if( err ) return err; Pa_Sleep( 100 ); } return noErr; } static PaError StopStream( PaStream *s ) { PaMacCoreStream *stream = (PaMacCoreStream*)s; OSStatus result = noErr; PaError paErr; VVDBUG(("StopStream()\n")); VDBUG( ("Waiting for BLIO.\n") ); waitUntilBlioWriteBufferIsFlushed( &stream->blio ); VDBUG( ( "Stopping stream.\n" ) ); stream->isTimeSet = FALSE; stream->state = STOPPING; #define ERR_WRAP(mac_err) do { result = mac_err ; if ( result != noErr ) return ERR(result) ; } while(0) /* -- stop and reset -- */ if( stream->inputUnit == stream->outputUnit && stream->inputUnit ) { ERR_WRAP( AudioOutputUnitStop(stream->inputUnit) ); ERR_WRAP( BlockWhileAudioUnitIsRunning(stream->inputUnit,0) ); ERR_WRAP( BlockWhileAudioUnitIsRunning(stream->inputUnit,1) ); ERR_WRAP( AudioUnitReset(stream->inputUnit, kAudioUnitScope_Global, 1) ); ERR_WRAP( AudioUnitReset(stream->inputUnit, kAudioUnitScope_Global, 0) ); } else { if( stream->inputUnit ) { ERR_WRAP(AudioOutputUnitStop(stream->inputUnit) ); ERR_WRAP( BlockWhileAudioUnitIsRunning(stream->inputUnit,1) ); ERR_WRAP(AudioUnitReset(stream->inputUnit,kAudioUnitScope_Global,1)); } if( stream->outputUnit ) { ERR_WRAP(AudioOutputUnitStop(stream->outputUnit)); ERR_WRAP( BlockWhileAudioUnitIsRunning(stream->outputUnit,0) ); ERR_WRAP(AudioUnitReset(stream->outputUnit,kAudioUnitScope_Global,0)); } } if( stream->inputRingBuffer.buffer ) { PaUtil_FlushRingBuffer( &stream->inputRingBuffer ); bzero( (void *)stream->inputRingBuffer.buffer, stream->inputRingBuffer.bufferSize ); /* advance the write point a little, so we are reading from the middle of the buffer. We'll need extra at the end because testing has shown that this helps. */ if( stream->outputUnit ) PaUtil_AdvanceRingBufferWriteIndex( &stream->inputRingBuffer, stream->inputRingBuffer.bufferSize / RING_BUFFER_ADVANCE_DENOMINATOR ); } stream->xrunFlags = 0; stream->state = STOPPED; paErr = resetBlioRingBuffers( &stream->blio ); if( paErr ) return paErr; /* //stream->isTimeSet = FALSE; */ VDBUG( ( "Stream Stopped.\n" ) ); return paNoError; #undef ERR_WRAP } static PaError AbortStream( PaStream *s ) { VVDBUG(("AbortStream()->StopStream()\n")); VDBUG( ( "Aborting stream.\n" ) ); /* We have nothing faster than StopStream. */ return StopStream(s); } static PaError IsStreamStopped( PaStream *s ) { PaMacCoreStream *stream = (PaMacCoreStream*)s; VVDBUG(("IsStreamStopped()\n")); return stream->state == STOPPED ? 1 : 0; } static PaError IsStreamActive( PaStream *s ) { PaMacCoreStream *stream = (PaMacCoreStream*)s; VVDBUG(("IsStreamActive()\n")); return ( stream->state == ACTIVE || stream->state == STOPPING ); } static double GetStreamCpuLoad( PaStream* s ) { PaMacCoreStream *stream = (PaMacCoreStream*)s; VVDBUG(("GetStreamCpuLoad()\n")); return PaUtil_GetCpuLoad( &stream->cpuLoadMeasurer ); } sources_5316/external/portaudio/pa_allocation.h0000644000176700017670000000744410474003011020530 0ustar paulpaul#ifndef PA_ALLOCATION_H #define PA_ALLOCATION_H /* * $Id: pa_allocation.h 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library allocation context header * memory allocation context for tracking allocation groups * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Allocation Group prototypes. An Allocation Group makes it easy to allocate multiple blocks of memory and free them all simultanously. An allocation group is useful for keeping track of multiple blocks of memory which are allocated at the same time (such as during initialization) and need to be deallocated at the same time. The allocation group maintains a list of allocated blocks, and can deallocate them all simultaneously which can be usefull for cleaning up after a partially initialized object fails. The allocation group implementation is built on top of the lower level allocation functions defined in pa_util.h */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ typedef struct { long linkCount; struct PaUtilAllocationGroupLink *linkBlocks; struct PaUtilAllocationGroupLink *spareLinks; struct PaUtilAllocationGroupLink *allocations; }PaUtilAllocationGroup; /** Create an allocation group. */ PaUtilAllocationGroup* PaUtil_CreateAllocationGroup( void ); /** Destroy an allocation group, but not the memory allocated through the group. */ void PaUtil_DestroyAllocationGroup( PaUtilAllocationGroup* group ); /** Allocate a block of memory though an allocation group. */ void* PaUtil_GroupAllocateMemory( PaUtilAllocationGroup* group, long size ); /** Free a block of memory that was previously allocated though an allocation group. Calling this function is a relatively time consuming operation. Under normal circumstances clients should call PaUtil_FreeAllAllocations to free all allocated blocks simultaneously. @see PaUtil_FreeAllAllocations */ void PaUtil_GroupFreeMemory( PaUtilAllocationGroup* group, void *buffer ); /** Free all blocks of memory which have been allocated through the allocation group. This function doesn't destroy the group itself. */ void PaUtil_FreeAllAllocations( PaUtilAllocationGroup* group ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_ALLOCATION_H */ sources_5316/external/portaudio/pa_util.h0000644000176700017670000001257110634535037017375 0ustar paulpaul#ifndef PA_UTIL_H #define PA_UTIL_H /* * $Id: pa_util.h 1229 2007-06-15 16:11:11Z rossb $ * Portable Audio I/O Library implementation utilities header * common implementation utilities and interfaces * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Prototypes for utility functions used by PortAudio implementations. @todo Document and adhere to the alignment guarantees provided by PaUtil_AllocateMemory(). */ #include "portaudio.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ struct PaUtilHostApiRepresentation; /** Retrieve a specific host API representation. This function can be used by implementations to retrieve a pointer to their representation in host api specific extension functions which aren't passed a rep pointer by pa_front.c. @param hostApi A pointer to a host API represenation pointer. Apon success this will receive the requested representation pointer. @param type A valid host API type identifier. @returns An error code. If the result is PaNoError then a pointer to the requested host API representation will be stored in *hostApi. If the host API specified by type is not found, this function returns paHostApiNotFound. */ PaError PaUtil_GetHostApiRepresentation( struct PaUtilHostApiRepresentation **hostApi, PaHostApiTypeId type ); /** Convert a PortAudio device index into a host API specific device index. @param hostApiDevice Pointer to a device index, on success this will recieve the converted device index value. @param device The PortAudio device index to convert. @param hostApi The host api which the index should be converted for. @returns On success returns PaNoError and places the converted index in the hostApiDevice parameter. */ PaError PaUtil_DeviceIndexToHostApiDeviceIndex( PaDeviceIndex *hostApiDevice, PaDeviceIndex device, struct PaUtilHostApiRepresentation *hostApi ); /** Set the host error information returned by Pa_GetLastHostErrorInfo. This function and the paUnanticipatedHostError error code should be used as a last resort. Implementors should use existing PA error codes where possible, or nominate new ones. Note that at it is always better to use PaUtil_SetLastHostErrorInfo() and paUnanticipatedHostError than to return an ambiguous or inaccurate PaError code. @param hostApiType The host API which encountered the error (ie of the caller) @param errorCode The error code returned by the native API function. @param errorText A string describing the error. PaUtil_SetLastHostErrorInfo makes a copy of the string, so it is not necessary for the pointer to remain valid after the call to PaUtil_SetLastHostErrorInfo() returns. */ void PaUtil_SetLastHostErrorInfo( PaHostApiTypeId hostApiType, long errorCode, const char *errorText ); /* the following functions are implemented in a platform platform specific .c file */ /** Allocate size bytes, guaranteed to be aligned to a FIXME byte boundary */ void *PaUtil_AllocateMemory( long size ); /** Realease block if non-NULL. block may be NULL */ void PaUtil_FreeMemory( void *block ); /** Return the number of currently allocated blocks. This function can be used for detecting memory leaks. @note Allocations will only be tracked if PA_TRACK_MEMORY is #defined. If it isn't, this function will always return 0. */ int PaUtil_CountCurrentlyAllocatedBlocks( void ); /** Initialize the clock used by PaUtil_GetTime(). Call this before calling PaUtil_GetTime. @see PaUtil_GetTime */ void PaUtil_InitializeClock( void ); /** Return the system time in seconds. Used to implement CPU load functions @see PaUtil_InitializeClock */ double PaUtil_GetTime( void ); /* void Pa_Sleep( long msec ); must also be implemented in per-platform .c file */ #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_UTIL_H */ sources_5316/external/portaudio/pa_win_wmme.h0000644000176700017670000001472210657361725020250 0ustar paulpaul#ifndef PA_WIN_WMME_H #define PA_WIN_WMME_H /* * $Id: pa_win_wmme.h 1247 2007-08-11 16:29:09Z rossb $ * PortAudio Portable Real-Time Audio Library * MME specific extensions * * Copyright (c) 1999-2000 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @brief WMME-specific PortAudio API extension header file. */ #include "portaudio.h" #include "pa_win_waveformat.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ #define paWinMmeUseLowLevelLatencyParameters (0x01) #define paWinMmeUseMultipleDevices (0x02) /* use mme specific multiple device feature */ #define paWinMmeUseChannelMask (0x04) /* By default, the mme implementation drops the processing thread's priority to THREAD_PRIORITY_NORMAL and sleeps the thread if the CPU load exceeds 100% This flag disables any priority throttling. The processing thread will always run at THREAD_PRIORITY_TIME_CRITICAL. */ #define paWinMmeDontThrottleOverloadedProcessingThread (0x08) typedef struct PaWinMmeDeviceAndChannelCount{ PaDeviceIndex device; int channelCount; }PaWinMmeDeviceAndChannelCount; typedef struct PaWinMmeStreamInfo{ unsigned long size; /**< sizeof(PaWinMmeStreamInfo) */ PaHostApiTypeId hostApiType; /**< paMME */ unsigned long version; /**< 1 */ unsigned long flags; /* low-level latency setting support These settings control the number and size of host buffers in order to set latency. They will be used instead of the generic parameters to Pa_OpenStream() if flags contains the PaWinMmeUseLowLevelLatencyParameters flag. If PaWinMmeStreamInfo structures with PaWinMmeUseLowLevelLatencyParameters are supplied for both input and output in a full duplex stream, then the input and output framesPerBuffer must be the same, or the larger of the two must be a multiple of the smaller, otherwise a paIncompatibleHostApiSpecificStreamInfo error will be returned from Pa_OpenStream(). */ unsigned long framesPerBuffer; unsigned long bufferCount; /* formerly numBuffers */ /* multiple devices per direction support If flags contains the PaWinMmeUseMultipleDevices flag, this functionality will be used, otherwise the device parameter to Pa_OpenStream() will be used instead. If devices are specified here, the corresponding device parameter to Pa_OpenStream() should be set to paUseHostApiSpecificDeviceSpecification, otherwise an paInvalidDevice error will result. The total number of channels accross all specified devices must agree with the corresponding channelCount parameter to Pa_OpenStream() otherwise a paInvalidChannelCount error will result. */ PaWinMmeDeviceAndChannelCount *devices; unsigned long deviceCount; /* support for WAVEFORMATEXTENSIBLE channel masks. If flags contains paWinMmeUseChannelMask this allows you to specify which speakers to address in a multichannel stream. Constants for channelMask are specified in pa_win_waveformat.h */ PaWinWaveFormatChannelMask channelMask; }PaWinMmeStreamInfo; /** Retrieve the number of wave in handles used by a PortAudio WinMME stream. Returns zero if the stream is output only. @return A non-negative value indicating the number of wave in handles or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. @see PaWinMME_GetStreamInputHandle */ int PaWinMME_GetStreamInputHandleCount( PaStream* stream ); /** Retrieve a wave in handle used by a PortAudio WinMME stream. @param stream The stream to query. @param handleIndex The zero based index of the wave in handle to retrieve. This should be in the range [0, PaWinMME_GetStreamInputHandleCount(stream)-1]. @return A valid wave in handle, or NULL if an error occurred. @see PaWinMME_GetStreamInputHandle */ HWAVEIN PaWinMME_GetStreamInputHandle( PaStream* stream, int handleIndex ); /** Retrieve the number of wave out handles used by a PortAudio WinMME stream. Returns zero if the stream is input only. @return A non-negative value indicating the number of wave out handles or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. @see PaWinMME_GetStreamOutputHandle */ int PaWinMME_GetStreamOutputHandleCount( PaStream* stream ); /** Retrieve a wave out handle used by a PortAudio WinMME stream. @param stream The stream to query. @param handleIndex The zero based index of the wave out handle to retrieve. This should be in the range [0, PaWinMME_GetStreamOutputHandleCount(stream)-1]. @return A valid wave out handle, or NULL if an error occurred. @see PaWinMME_GetStreamOutputHandleCount */ HWAVEOUT PaWinMME_GetStreamOutputHandle( PaStream* stream, int handleIndex ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_WIN_WMME_H */ sources_5316/external/portaudio/pa_front.c0000644000176700017670000015203310634535037017541 0ustar paulpaul/* * $Id: pa_front.c 1229 2007-06-15 16:11:11Z rossb $ * Portable Audio I/O Library Multi-Host API front end * Validate function parameters and manage multiple host APIs. * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Implements public PortAudio API, checks some errors, forwards to host API implementations. Implements the functions defined in the PortAudio API, checks for some parameter and state inconsistencies and forwards API requests to specific Host API implementations (via the interface declared in pa_hostapi.h), and Streams (via the interface declared in pa_stream.h). This file handles initialization and termination of Host API implementations via initializers stored in the paHostApiInitializers global variable. Some utility functions declared in pa_util.h are implemented in this file. All PortAudio API functions can be conditionally compiled with logging code. To compile with logging, define the PA_LOG_API_CALLS precompiler symbol. @todo Consider adding host API specific error text in Pa_GetErrorText() for paUnanticipatedHostError @todo Consider adding a new error code for when (inputParameters == NULL) && (outputParameters == NULL) @todo review whether Pa_CloseStream() should call the interface's CloseStream function if aborting the stream returns an error code. @todo Create new error codes if a NULL buffer pointer, or a zero frame count is passed to Pa_ReadStream or Pa_WriteStream. */ #include #include #include #include /* needed by PA_VALIDATE_ENDIANNESS */ #include "portaudio.h" #include "pa_util.h" #include "pa_endianness.h" #include "pa_types.h" #include "pa_hostapi.h" #include "pa_stream.h" #include "pa_trace.h" /* still usefull?*/ #include "pa_debugprint.h" #define PA_VERSION_ 1899 #define PA_VERSION_TEXT_ "PortAudio V19-devel (built " __DATE__ ")" int Pa_GetVersion( void ) { return PA_VERSION_; } const char* Pa_GetVersionText( void ) { return PA_VERSION_TEXT_; } #define PA_LAST_HOST_ERROR_TEXT_LENGTH_ 1024 static char lastHostErrorText_[ PA_LAST_HOST_ERROR_TEXT_LENGTH_ + 1 ] = {0}; static PaHostErrorInfo lastHostErrorInfo_ = { (PaHostApiTypeId)-1, 0, lastHostErrorText_ }; void PaUtil_SetLastHostErrorInfo( PaHostApiTypeId hostApiType, long errorCode, const char *errorText ) { lastHostErrorInfo_.hostApiType = hostApiType; lastHostErrorInfo_.errorCode = errorCode; strncpy( lastHostErrorText_, errorText, PA_LAST_HOST_ERROR_TEXT_LENGTH_ ); } static PaUtilHostApiRepresentation **hostApis_ = 0; static int hostApisCount_ = 0; static int initializationCount_ = 0; static int deviceCount_ = 0; PaUtilStreamRepresentation *firstOpenStream_ = NULL; #define PA_IS_INITIALISED_ (initializationCount_ != 0) static int CountHostApiInitializers( void ) { int result = 0; while( paHostApiInitializers[ result ] != 0 ) ++result; return result; } static void TerminateHostApis( void ) { /* terminate in reverse order from initialization */ PA_DEBUG(("TerminateHostApis in \n")); while( hostApisCount_ > 0 ) { --hostApisCount_; hostApis_[hostApisCount_]->Terminate( hostApis_[hostApisCount_] ); } hostApisCount_ = 0; deviceCount_ = 0; if( hostApis_ != 0 ) PaUtil_FreeMemory( hostApis_ ); hostApis_ = 0; PA_DEBUG(("TerminateHostApis out\n")); } static PaError InitializeHostApis( void ) { PaError result = paNoError; int i, initializerCount, baseDeviceIndex; initializerCount = CountHostApiInitializers(); hostApis_ = (PaUtilHostApiRepresentation**)PaUtil_AllocateMemory( sizeof(PaUtilHostApiRepresentation*) * initializerCount ); if( !hostApis_ ) { result = paInsufficientMemory; goto error; } hostApisCount_ = 0; deviceCount_ = 0; baseDeviceIndex = 0; for( i=0; i< initializerCount; ++i ) { hostApis_[hostApisCount_] = NULL; PA_DEBUG(( "before paHostApiInitializers[%d].\n",i)); result = paHostApiInitializers[i]( &hostApis_[hostApisCount_], hostApisCount_ ); if( result != paNoError ) goto error; PA_DEBUG(( "after paHostApiInitializers[%d].\n",i)); if( hostApis_[hostApisCount_] ) { PaUtilHostApiRepresentation* hostApi = hostApis_[hostApisCount_]; assert( hostApi->info.defaultInputDevice < hostApi->info.deviceCount ); assert( hostApi->info.defaultOutputDevice < hostApi->info.deviceCount ); hostApi->privatePaFrontInfo.baseDeviceIndex = baseDeviceIndex; if( hostApi->info.defaultInputDevice != paNoDevice ) hostApi->info.defaultInputDevice += baseDeviceIndex; if( hostApi->info.defaultOutputDevice != paNoDevice ) hostApi->info.defaultOutputDevice += baseDeviceIndex; baseDeviceIndex += hostApi->info.deviceCount; deviceCount_ += hostApi->info.deviceCount; ++hostApisCount_; } } return result; error: TerminateHostApis(); return result; } /* FindHostApi() finds the index of the host api to which belongs and returns it. if is non-null, the host specific device index is returned in it. returns -1 if is out of range. */ static int FindHostApi( PaDeviceIndex device, int *hostSpecificDeviceIndex ) { int i=0; if( !PA_IS_INITIALISED_ ) return -1; if( device < 0 ) return -1; while( i < hostApisCount_ && device >= hostApis_[i]->info.deviceCount ) { device -= hostApis_[i]->info.deviceCount; ++i; } if( i >= hostApisCount_ ) return -1; if( hostSpecificDeviceIndex ) *hostSpecificDeviceIndex = device; return i; } static void AddOpenStream( PaStream* stream ) { ((PaUtilStreamRepresentation*)stream)->nextOpenStream = firstOpenStream_; firstOpenStream_ = (PaUtilStreamRepresentation*)stream; } static void RemoveOpenStream( PaStream* stream ) { PaUtilStreamRepresentation *previous = NULL; PaUtilStreamRepresentation *current = firstOpenStream_; while( current != NULL ) { if( ((PaStream*)current) == stream ) { if( previous == NULL ) { firstOpenStream_ = current->nextOpenStream; } else { previous->nextOpenStream = current->nextOpenStream; } return; } else { previous = current; current = current->nextOpenStream; } } } static void CloseOpenStreams( void ) { /* we call Pa_CloseStream() here to ensure that the same destruction logic is used for automatically closed streams */ while( firstOpenStream_ != NULL ) Pa_CloseStream( firstOpenStream_ ); } PaError Pa_Initialize( void ) { PaError result; PA_LOGAPI_ENTER( "Pa_Initialize" ); if( PA_IS_INITIALISED_ ) { ++initializationCount_; result = paNoError; } else { PA_VALIDATE_TYPE_SIZES; PA_VALIDATE_ENDIANNESS; PaUtil_InitializeClock(); PaUtil_ResetTraceMessages(); result = InitializeHostApis(); if( result == paNoError ) ++initializationCount_; } PA_LOGAPI_EXIT_PAERROR( "Pa_Initialize", result ); return result; } PaError Pa_Terminate( void ) { PaError result; PA_LOGAPI_ENTER( "Pa_Terminate" ); if( PA_IS_INITIALISED_ ) { if( --initializationCount_ == 0 ) { CloseOpenStreams(); TerminateHostApis(); PaUtil_DumpTraceMessages(); } result = paNoError; } else { result= paNotInitialized; } PA_LOGAPI_EXIT_PAERROR( "Pa_Terminate", result ); return result; } const PaHostErrorInfo* Pa_GetLastHostErrorInfo( void ) { return &lastHostErrorInfo_; } const char *Pa_GetErrorText( PaError errorCode ) { const char *result; switch( errorCode ) { case paNoError: result = "Success"; break; case paNotInitialized: result = "PortAudio not initialized"; break; /** @todo could catenate the last host error text to result in the case of paUnanticipatedHostError */ case paUnanticipatedHostError: result = "Unanticipated host error"; break; case paInvalidChannelCount: result = "Invalid number of channels"; break; case paInvalidSampleRate: result = "Invalid sample rate"; break; case paInvalidDevice: result = "Invalid device"; break; case paInvalidFlag: result = "Invalid flag"; break; case paSampleFormatNotSupported: result = "Sample format not supported"; break; case paBadIODeviceCombination: result = "Illegal combination of I/O devices"; break; case paInsufficientMemory: result = "Insufficient memory"; break; case paBufferTooBig: result = "Buffer too big"; break; case paBufferTooSmall: result = "Buffer too small"; break; case paNullCallback: result = "No callback routine specified"; break; case paBadStreamPtr: result = "Invalid stream pointer"; break; case paTimedOut: result = "Wait timed out"; break; case paInternalError: result = "Internal PortAudio error"; break; case paDeviceUnavailable: result = "Device unavailable"; break; case paIncompatibleHostApiSpecificStreamInfo: result = "Incompatible host API specific stream info"; break; case paStreamIsStopped: result = "Stream is stopped"; break; case paStreamIsNotStopped: result = "Stream is not stopped"; break; case paInputOverflowed: result = "Input overflowed"; break; case paOutputUnderflowed: result = "Output underflowed"; break; case paHostApiNotFound: result = "Host API not found"; break; case paInvalidHostApi: result = "Invalid host API"; break; case paCanNotReadFromACallbackStream: result = "Can't read from a callback stream"; break; case paCanNotWriteToACallbackStream: result = "Can't write to a callback stream"; break; case paCanNotReadFromAnOutputOnlyStream: result = "Can't read from an output only stream"; break; case paCanNotWriteToAnInputOnlyStream: result = "Can't write to an input only stream"; break; default: if( errorCode > 0 ) result = "Invalid error code (value greater than zero)"; else result = "Invalid error code"; break; } return result; } PaHostApiIndex Pa_HostApiTypeIdToHostApiIndex( PaHostApiTypeId type ) { PaHostApiIndex result; int i; PA_LOGAPI_ENTER_PARAMS( "Pa_HostApiTypeIdToHostApiIndex" ); PA_LOGAPI(("\tPaHostApiTypeId type: %d\n", type )); if( !PA_IS_INITIALISED_ ) { result = paNotInitialized; } else { result = paHostApiNotFound; for( i=0; i < hostApisCount_; ++i ) { if( hostApis_[i]->info.type == type ) { result = i; break; } } } PA_LOGAPI_EXIT_PAERROR_OR_T_RESULT( "Pa_HostApiTypeIdToHostApiIndex", "PaHostApiIndex: %d", result ); return result; } PaError PaUtil_GetHostApiRepresentation( struct PaUtilHostApiRepresentation **hostApi, PaHostApiTypeId type ) { PaError result; int i; if( !PA_IS_INITIALISED_ ) { result = paNotInitialized; } else { result = paHostApiNotFound; for( i=0; i < hostApisCount_; ++i ) { if( hostApis_[i]->info.type == type ) { *hostApi = hostApis_[i]; result = paNoError; break; } } } return result; } PaError PaUtil_DeviceIndexToHostApiDeviceIndex( PaDeviceIndex *hostApiDevice, PaDeviceIndex device, struct PaUtilHostApiRepresentation *hostApi ) { PaError result; PaDeviceIndex x; x = device - hostApi->privatePaFrontInfo.baseDeviceIndex; if( x < 0 || x >= hostApi->info.deviceCount ) { result = paInvalidDevice; } else { *hostApiDevice = x; result = paNoError; } return result; } PaHostApiIndex Pa_GetHostApiCount( void ) { int result; PA_LOGAPI_ENTER( "Pa_GetHostApiCount" ); if( !PA_IS_INITIALISED_ ) { result = paNotInitialized; } else { result = hostApisCount_; } PA_LOGAPI_EXIT_PAERROR_OR_T_RESULT( "Pa_GetHostApiCount", "PaHostApiIndex: %d", result ); return result; } PaHostApiIndex Pa_GetDefaultHostApi( void ) { int result; PA_LOGAPI_ENTER( "Pa_GetDefaultHostApi" ); if( !PA_IS_INITIALISED_ ) { result = paNotInitialized; } else { result = paDefaultHostApiIndex; /* internal consistency check: make sure that the default host api index is within range */ if( result < 0 || result >= hostApisCount_ ) { result = paInternalError; } } PA_LOGAPI_EXIT_PAERROR_OR_T_RESULT( "Pa_GetDefaultHostApi", "PaHostApiIndex: %d", result ); return result; } const PaHostApiInfo* Pa_GetHostApiInfo( PaHostApiIndex hostApi ) { PaHostApiInfo *info; PA_LOGAPI_ENTER_PARAMS( "Pa_GetHostApiInfo" ); PA_LOGAPI(("\tPaHostApiIndex hostApi: %d\n", hostApi )); if( !PA_IS_INITIALISED_ ) { info = NULL; PA_LOGAPI(("Pa_GetHostApiInfo returned:\n" )); PA_LOGAPI(("\tPaHostApiInfo*: NULL [ PortAudio not initialized ]\n" )); } else if( hostApi < 0 || hostApi >= hostApisCount_ ) { info = NULL; PA_LOGAPI(("Pa_GetHostApiInfo returned:\n" )); PA_LOGAPI(("\tPaHostApiInfo*: NULL [ hostApi out of range ]\n" )); } else { info = &hostApis_[hostApi]->info; PA_LOGAPI(("Pa_GetHostApiInfo returned:\n" )); PA_LOGAPI(("\tPaHostApiInfo*: 0x%p\n", info )); PA_LOGAPI(("\t{\n" )); PA_LOGAPI(("\t\tint structVersion: %d\n", info->structVersion )); PA_LOGAPI(("\t\tPaHostApiTypeId type: %d\n", info->type )); PA_LOGAPI(("\t\tconst char *name: %s\n", info->name )); PA_LOGAPI(("\t}\n" )); } return info; } PaDeviceIndex Pa_HostApiDeviceIndexToDeviceIndex( PaHostApiIndex hostApi, int hostApiDeviceIndex ) { PaDeviceIndex result; PA_LOGAPI_ENTER_PARAMS( "Pa_HostApiDeviceIndexToPaDeviceIndex" ); PA_LOGAPI(("\tPaHostApiIndex hostApi: %d\n", hostApi )); PA_LOGAPI(("\tint hostApiDeviceIndex: %d\n", hostApiDeviceIndex )); if( !PA_IS_INITIALISED_ ) { result = paNotInitialized; } else { if( hostApi < 0 || hostApi >= hostApisCount_ ) { result = paInvalidHostApi; } else { if( hostApiDeviceIndex < 0 || hostApiDeviceIndex >= hostApis_[hostApi]->info.deviceCount ) { result = paInvalidDevice; } else { result = hostApis_[hostApi]->privatePaFrontInfo.baseDeviceIndex + hostApiDeviceIndex; } } } PA_LOGAPI_EXIT_PAERROR_OR_T_RESULT( "Pa_HostApiDeviceIndexToPaDeviceIndex", "PaDeviceIndex: %d", result ); return result; } PaDeviceIndex Pa_GetDeviceCount( void ) { PaDeviceIndex result; PA_LOGAPI_ENTER( "Pa_GetDeviceCount" ); if( !PA_IS_INITIALISED_ ) { result = paNotInitialized; } else { result = deviceCount_; } PA_LOGAPI_EXIT_PAERROR_OR_T_RESULT( "Pa_GetDeviceCount", "PaDeviceIndex: %d", result ); return result; } PaDeviceIndex Pa_GetDefaultInputDevice( void ) { PaHostApiIndex hostApi; PaDeviceIndex result; PA_LOGAPI_ENTER( "Pa_GetDefaultInputDevice" ); hostApi = Pa_GetDefaultHostApi(); if( hostApi < 0 ) { result = paNoDevice; } else { result = hostApis_[hostApi]->info.defaultInputDevice; } PA_LOGAPI_EXIT_T( "Pa_GetDefaultInputDevice", "PaDeviceIndex: %d", result ); return result; } PaDeviceIndex Pa_GetDefaultOutputDevice( void ) { PaHostApiIndex hostApi; PaDeviceIndex result; PA_LOGAPI_ENTER( "Pa_GetDefaultOutputDevice" ); hostApi = Pa_GetDefaultHostApi(); if( hostApi < 0 ) { result = paNoDevice; } else { result = hostApis_[hostApi]->info.defaultOutputDevice; } PA_LOGAPI_EXIT_T( "Pa_GetDefaultOutputDevice", "PaDeviceIndex: %d", result ); return result; } const PaDeviceInfo* Pa_GetDeviceInfo( PaDeviceIndex device ) { int hostSpecificDeviceIndex; int hostApiIndex = FindHostApi( device, &hostSpecificDeviceIndex ); PaDeviceInfo *result; PA_LOGAPI_ENTER_PARAMS( "Pa_GetDeviceInfo" ); PA_LOGAPI(("\tPaDeviceIndex device: %d\n", device )); if( hostApiIndex < 0 ) { result = NULL; PA_LOGAPI(("Pa_GetDeviceInfo returned:\n" )); PA_LOGAPI(("\tPaDeviceInfo* NULL [ invalid device index ]\n" )); } else { result = hostApis_[hostApiIndex]->deviceInfos[ hostSpecificDeviceIndex ]; PA_LOGAPI(("Pa_GetDeviceInfo returned:\n" )); PA_LOGAPI(("\tPaDeviceInfo*: 0x%p:\n", result )); PA_LOGAPI(("\t{\n" )); PA_LOGAPI(("\t\tint structVersion: %d\n", result->structVersion )); PA_LOGAPI(("\t\tconst char *name: %s\n", result->name )); PA_LOGAPI(("\t\tPaHostApiIndex hostApi: %d\n", result->hostApi )); PA_LOGAPI(("\t\tint maxInputChannels: %d\n", result->maxInputChannels )); PA_LOGAPI(("\t\tint maxOutputChannels: %d\n", result->maxOutputChannels )); PA_LOGAPI(("\t}\n" )); } return result; } /* SampleFormatIsValid() returns 1 if sampleFormat is a sample format defined in portaudio.h, or 0 otherwise. */ static int SampleFormatIsValid( PaSampleFormat format ) { switch( format & ~paNonInterleaved ) { case paFloat32: return 1; case paInt16: return 1; case paInt32: return 1; case paInt24: return 1; case paInt8: return 1; case paUInt8: return 1; case paCustomFormat: return 1; default: return 0; } } /* NOTE: make sure this validation list is kept syncronised with the one in pa_hostapi.h ValidateOpenStreamParameters() checks that parameters to Pa_OpenStream() conform to the expected values as described below. This function is also designed to be used with the proposed Pa_IsFormatSupported() function. There are basically two types of validation that could be performed: Generic conformance validation, and device capability mismatch validation. This function performs only generic conformance validation. Validation that would require knowledge of device capabilities is not performed because of potentially complex relationships between combinations of parameters - for example, even if the sampleRate seems ok, it might not be for a duplex stream - we have no way of checking this in an API-neutral way, so we don't try. On success the function returns PaNoError and fills in hostApi, hostApiInputDeviceID, and hostApiOutputDeviceID fields. On failure the function returns an error code indicating the first encountered parameter error. If ValidateOpenStreamParameters() returns paNoError, the following assertions are guaranteed to be true. - at least one of inputParameters & outputParmeters is valid (not NULL) - if inputParameters & outputParameters are both valid, that inputParameters->device & outputParameters->device both use the same host api PaDeviceIndex inputParameters->device - is within range (0 to Pa_GetDeviceCount-1) Or: - is paUseHostApiSpecificDeviceSpecification and inputParameters->hostApiSpecificStreamInfo is non-NULL and refers to a valid host api int inputParameters->channelCount - if inputParameters->device is not paUseHostApiSpecificDeviceSpecification, channelCount is > 0 - upper bound is NOT validated against device capabilities PaSampleFormat inputParameters->sampleFormat - is one of the sample formats defined in portaudio.h void *inputParameters->hostApiSpecificStreamInfo - if supplied its hostApi field matches the input device's host Api PaDeviceIndex outputParmeters->device - is within range (0 to Pa_GetDeviceCount-1) int outputParmeters->channelCount - if inputDevice is valid, channelCount is > 0 - upper bound is NOT validated against device capabilities PaSampleFormat outputParmeters->sampleFormat - is one of the sample formats defined in portaudio.h void *outputParmeters->hostApiSpecificStreamInfo - if supplied its hostApi field matches the output device's host Api double sampleRate - is not an 'absurd' rate (less than 1000. or greater than 200000.) - sampleRate is NOT validated against device capabilities PaStreamFlags streamFlags - unused platform neutral flags are zero - paNeverDropInput is only used for full-duplex callback streams with variable buffer size (paFramesPerBufferUnspecified) */ static PaError ValidateOpenStreamParameters( const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, PaUtilHostApiRepresentation **hostApi, PaDeviceIndex *hostApiInputDevice, PaDeviceIndex *hostApiOutputDevice ) { int inputHostApiIndex = -1, /* Surpress uninitialised var warnings: compiler does */ outputHostApiIndex = -1; /* not see that if inputParameters and outputParame- */ /* ters are both nonzero, these indices are set. */ if( (inputParameters == NULL) && (outputParameters == NULL) ) { return paInvalidDevice; /** @todo should be a new error code "invalid device parameters" or something */ } else { if( inputParameters == NULL ) { *hostApiInputDevice = paNoDevice; } else if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) { if( inputParameters->hostApiSpecificStreamInfo ) { inputHostApiIndex = Pa_HostApiTypeIdToHostApiIndex( ((PaUtilHostApiSpecificStreamInfoHeader*)inputParameters->hostApiSpecificStreamInfo)->hostApiType ); if( inputHostApiIndex != -1 ) { *hostApiInputDevice = paUseHostApiSpecificDeviceSpecification; *hostApi = hostApis_[inputHostApiIndex]; } else { return paInvalidDevice; } } else { return paInvalidDevice; } } else { if( inputParameters->device < 0 || inputParameters->device >= deviceCount_ ) return paInvalidDevice; inputHostApiIndex = FindHostApi( inputParameters->device, hostApiInputDevice ); if( inputHostApiIndex < 0 ) return paInternalError; *hostApi = hostApis_[inputHostApiIndex]; if( inputParameters->channelCount <= 0 ) return paInvalidChannelCount; if( !SampleFormatIsValid( inputParameters->sampleFormat ) ) return paSampleFormatNotSupported; if( inputParameters->hostApiSpecificStreamInfo != NULL ) { if( ((PaUtilHostApiSpecificStreamInfoHeader*)inputParameters->hostApiSpecificStreamInfo)->hostApiType != (*hostApi)->info.type ) return paIncompatibleHostApiSpecificStreamInfo; } } if( outputParameters == NULL ) { *hostApiOutputDevice = paNoDevice; } else if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) { if( outputParameters->hostApiSpecificStreamInfo ) { outputHostApiIndex = Pa_HostApiTypeIdToHostApiIndex( ((PaUtilHostApiSpecificStreamInfoHeader*)outputParameters->hostApiSpecificStreamInfo)->hostApiType ); if( outputHostApiIndex != -1 ) { *hostApiOutputDevice = paUseHostApiSpecificDeviceSpecification; *hostApi = hostApis_[outputHostApiIndex]; } else { return paInvalidDevice; } } else { return paInvalidDevice; } } else { if( outputParameters->device < 0 || outputParameters->device >= deviceCount_ ) return paInvalidDevice; outputHostApiIndex = FindHostApi( outputParameters->device, hostApiOutputDevice ); if( outputHostApiIndex < 0 ) return paInternalError; *hostApi = hostApis_[outputHostApiIndex]; if( outputParameters->channelCount <= 0 ) return paInvalidChannelCount; if( !SampleFormatIsValid( outputParameters->sampleFormat ) ) return paSampleFormatNotSupported; if( outputParameters->hostApiSpecificStreamInfo != NULL ) { if( ((PaUtilHostApiSpecificStreamInfoHeader*)outputParameters->hostApiSpecificStreamInfo)->hostApiType != (*hostApi)->info.type ) return paIncompatibleHostApiSpecificStreamInfo; } } if( (inputParameters != NULL) && (outputParameters != NULL) ) { /* ensure that both devices use the same API */ if( inputHostApiIndex != outputHostApiIndex ) return paBadIODeviceCombination; } } /* Check for absurd sample rates. */ if( (sampleRate < 1000.0) || (sampleRate > 200000.0) ) return paInvalidSampleRate; if( ((streamFlags & ~paPlatformSpecificFlags) & ~(paClipOff | paDitherOff | paNeverDropInput | paPrimeOutputBuffersUsingStreamCallback ) ) != 0 ) return paInvalidFlag; if( streamFlags & paNeverDropInput ) { /* must be a callback stream */ if( !streamCallback ) return paInvalidFlag; /* must be a full duplex stream */ if( (inputParameters == NULL) || (outputParameters == NULL) ) return paInvalidFlag; /* must use paFramesPerBufferUnspecified */ if( framesPerBuffer != paFramesPerBufferUnspecified ) return paInvalidFlag; } return paNoError; } PaError Pa_IsFormatSupported( const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ) { PaError result; PaUtilHostApiRepresentation *hostApi = 0; PaDeviceIndex hostApiInputDevice = paNoDevice, hostApiOutputDevice = paNoDevice; PaStreamParameters hostApiInputParameters, hostApiOutputParameters; PaStreamParameters *hostApiInputParametersPtr, *hostApiOutputParametersPtr; #ifdef PA_LOG_API_CALLS PA_LOGAPI_ENTER_PARAMS( "Pa_IsFormatSupported" ); if( inputParameters == NULL ){ PA_LOGAPI(("\tPaStreamParameters *inputParameters: NULL\n" )); }else{ PA_LOGAPI(("\tPaStreamParameters *inputParameters: 0x%p\n", inputParameters )); PA_LOGAPI(("\tPaDeviceIndex inputParameters->device: %d\n", inputParameters->device )); PA_LOGAPI(("\tint inputParameters->channelCount: %d\n", inputParameters->channelCount )); PA_LOGAPI(("\tPaSampleFormat inputParameters->sampleFormat: %d\n", inputParameters->sampleFormat )); PA_LOGAPI(("\tPaTime inputParameters->suggestedLatency: %f\n", inputParameters->suggestedLatency )); PA_LOGAPI(("\tvoid *inputParameters->hostApiSpecificStreamInfo: 0x%p\n", inputParameters->hostApiSpecificStreamInfo )); } if( outputParameters == NULL ){ PA_LOGAPI(("\tPaStreamParameters *outputParameters: NULL\n" )); }else{ PA_LOGAPI(("\tPaStreamParameters *outputParameters: 0x%p\n", outputParameters )); PA_LOGAPI(("\tPaDeviceIndex outputParameters->device: %d\n", outputParameters->device )); PA_LOGAPI(("\tint outputParameters->channelCount: %d\n", outputParameters->channelCount )); PA_LOGAPI(("\tPaSampleFormat outputParameters->sampleFormat: %d\n", outputParameters->sampleFormat )); PA_LOGAPI(("\tPaTime outputParameters->suggestedLatency: %f\n", outputParameters->suggestedLatency )); PA_LOGAPI(("\tvoid *outputParameters->hostApiSpecificStreamInfo: 0x%p\n", outputParameters->hostApiSpecificStreamInfo )); } PA_LOGAPI(("\tdouble sampleRate: %g\n", sampleRate )); #endif if( !PA_IS_INITIALISED_ ) { result = paNotInitialized; PA_LOGAPI_EXIT_PAERROR( "Pa_IsFormatSupported", result ); return result; } result = ValidateOpenStreamParameters( inputParameters, outputParameters, sampleRate, 0, paNoFlag, 0, &hostApi, &hostApiInputDevice, &hostApiOutputDevice ); if( result != paNoError ) { PA_LOGAPI_EXIT_PAERROR( "Pa_IsFormatSupported", result ); return result; } if( inputParameters ) { hostApiInputParameters.device = hostApiInputDevice; hostApiInputParameters.channelCount = inputParameters->channelCount; hostApiInputParameters.sampleFormat = inputParameters->sampleFormat; hostApiInputParameters.suggestedLatency = inputParameters->suggestedLatency; hostApiInputParameters.hostApiSpecificStreamInfo = inputParameters->hostApiSpecificStreamInfo; hostApiInputParametersPtr = &hostApiInputParameters; } else { hostApiInputParametersPtr = NULL; } if( outputParameters ) { hostApiOutputParameters.device = hostApiOutputDevice; hostApiOutputParameters.channelCount = outputParameters->channelCount; hostApiOutputParameters.sampleFormat = outputParameters->sampleFormat; hostApiOutputParameters.suggestedLatency = outputParameters->suggestedLatency; hostApiOutputParameters.hostApiSpecificStreamInfo = outputParameters->hostApiSpecificStreamInfo; hostApiOutputParametersPtr = &hostApiOutputParameters; } else { hostApiOutputParametersPtr = NULL; } result = hostApi->IsFormatSupported( hostApi, hostApiInputParametersPtr, hostApiOutputParametersPtr, sampleRate ); #ifdef PA_LOG_API_CALLS PA_LOGAPI(("Pa_OpenStream returned:\n" )); if( result == paFormatIsSupported ) PA_LOGAPI(("\tPaError: 0 [ paFormatIsSupported ]\n" )); else PA_LOGAPI(("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) )); #endif return result; } PaError Pa_OpenStream( PaStream** stream, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ) { PaError result; PaUtilHostApiRepresentation *hostApi = 0; PaDeviceIndex hostApiInputDevice = paNoDevice, hostApiOutputDevice = paNoDevice; PaStreamParameters hostApiInputParameters, hostApiOutputParameters; PaStreamParameters *hostApiInputParametersPtr, *hostApiOutputParametersPtr; #ifdef PA_LOG_API_CALLS PA_LOGAPI_ENTER_PARAMS( "Pa_OpenStream" ); PA_LOGAPI(("\tPaStream** stream: 0x%p\n", stream )); if( inputParameters == NULL ){ PA_LOGAPI(("\tPaStreamParameters *inputParameters: NULL\n" )); }else{ PA_LOGAPI(("\tPaStreamParameters *inputParameters: 0x%p\n", inputParameters )); PA_LOGAPI(("\tPaDeviceIndex inputParameters->device: %d\n", inputParameters->device )); PA_LOGAPI(("\tint inputParameters->channelCount: %d\n", inputParameters->channelCount )); PA_LOGAPI(("\tPaSampleFormat inputParameters->sampleFormat: %d\n", inputParameters->sampleFormat )); PA_LOGAPI(("\tPaTime inputParameters->suggestedLatency: %f\n", inputParameters->suggestedLatency )); PA_LOGAPI(("\tvoid *inputParameters->hostApiSpecificStreamInfo: 0x%p\n", inputParameters->hostApiSpecificStreamInfo )); } if( outputParameters == NULL ){ PA_LOGAPI(("\tPaStreamParameters *outputParameters: NULL\n" )); }else{ PA_LOGAPI(("\tPaStreamParameters *outputParameters: 0x%p\n", outputParameters )); PA_LOGAPI(("\tPaDeviceIndex outputParameters->device: %d\n", outputParameters->device )); PA_LOGAPI(("\tint outputParameters->channelCount: %d\n", outputParameters->channelCount )); PA_LOGAPI(("\tPaSampleFormat outputParameters->sampleFormat: %d\n", outputParameters->sampleFormat )); PA_LOGAPI(("\tPaTime outputParameters->suggestedLatency: %f\n", outputParameters->suggestedLatency )); PA_LOGAPI(("\tvoid *outputParameters->hostApiSpecificStreamInfo: 0x%p\n", outputParameters->hostApiSpecificStreamInfo )); } PA_LOGAPI(("\tdouble sampleRate: %g\n", sampleRate )); PA_LOGAPI(("\tunsigned long framesPerBuffer: %d\n", framesPerBuffer )); PA_LOGAPI(("\tPaStreamFlags streamFlags: 0x%x\n", streamFlags )); PA_LOGAPI(("\tPaStreamCallback *streamCallback: 0x%p\n", streamCallback )); PA_LOGAPI(("\tvoid *userData: 0x%p\n", userData )); #endif if( !PA_IS_INITIALISED_ ) { result = paNotInitialized; PA_LOGAPI(("Pa_OpenStream returned:\n" )); PA_LOGAPI(("\t*(PaStream** stream): undefined\n" )); PA_LOGAPI(("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) )); return result; } /* Check for parameter errors. NOTE: make sure this validation list is kept syncronised with the one in pa_hostapi.h */ if( stream == NULL ) { result = paBadStreamPtr; PA_LOGAPI(("Pa_OpenStream returned:\n" )); PA_LOGAPI(("\t*(PaStream** stream): undefined\n" )); PA_LOGAPI(("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) )); return result; } result = ValidateOpenStreamParameters( inputParameters, outputParameters, sampleRate, framesPerBuffer, streamFlags, streamCallback, &hostApi, &hostApiInputDevice, &hostApiOutputDevice ); if( result != paNoError ) { PA_LOGAPI(("Pa_OpenStream returned:\n" )); PA_LOGAPI(("\t*(PaStream** stream): undefined\n" )); PA_LOGAPI(("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) )); return result; } if( inputParameters ) { hostApiInputParameters.device = hostApiInputDevice; hostApiInputParameters.channelCount = inputParameters->channelCount; hostApiInputParameters.sampleFormat = inputParameters->sampleFormat; hostApiInputParameters.suggestedLatency = inputParameters->suggestedLatency; hostApiInputParameters.hostApiSpecificStreamInfo = inputParameters->hostApiSpecificStreamInfo; hostApiInputParametersPtr = &hostApiInputParameters; } else { hostApiInputParametersPtr = NULL; } if( outputParameters ) { hostApiOutputParameters.device = hostApiOutputDevice; hostApiOutputParameters.channelCount = outputParameters->channelCount; hostApiOutputParameters.sampleFormat = outputParameters->sampleFormat; hostApiOutputParameters.suggestedLatency = outputParameters->suggestedLatency; hostApiOutputParameters.hostApiSpecificStreamInfo = outputParameters->hostApiSpecificStreamInfo; hostApiOutputParametersPtr = &hostApiOutputParameters; } else { hostApiOutputParametersPtr = NULL; } result = hostApi->OpenStream( hostApi, stream, hostApiInputParametersPtr, hostApiOutputParametersPtr, sampleRate, framesPerBuffer, streamFlags, streamCallback, userData ); if( result == paNoError ) AddOpenStream( *stream ); PA_LOGAPI(("Pa_OpenStream returned:\n" )); PA_LOGAPI(("\t*(PaStream** stream): 0x%p\n", *stream )); PA_LOGAPI(("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) )); return result; } PaError Pa_OpenDefaultStream( PaStream** stream, int inputChannelCount, int outputChannelCount, PaSampleFormat sampleFormat, double sampleRate, unsigned long framesPerBuffer, PaStreamCallback *streamCallback, void *userData ) { PaError result; PaStreamParameters hostApiInputParameters, hostApiOutputParameters; PaStreamParameters *hostApiInputParametersPtr, *hostApiOutputParametersPtr; PA_LOGAPI_ENTER_PARAMS( "Pa_OpenDefaultStream" ); PA_LOGAPI(("\tPaStream** stream: 0x%p\n", stream )); PA_LOGAPI(("\tint inputChannelCount: %d\n", inputChannelCount )); PA_LOGAPI(("\tint outputChannelCount: %d\n", outputChannelCount )); PA_LOGAPI(("\tPaSampleFormat sampleFormat: %d\n", sampleFormat )); PA_LOGAPI(("\tdouble sampleRate: %g\n", sampleRate )); PA_LOGAPI(("\tunsigned long framesPerBuffer: %d\n", framesPerBuffer )); PA_LOGAPI(("\tPaStreamCallback *streamCallback: 0x%p\n", streamCallback )); PA_LOGAPI(("\tvoid *userData: 0x%p\n", userData )); if( inputChannelCount > 0 ) { hostApiInputParameters.device = Pa_GetDefaultInputDevice(); if( hostApiInputParameters.device == paNoDevice ) return paDeviceUnavailable; hostApiInputParameters.channelCount = inputChannelCount; hostApiInputParameters.sampleFormat = sampleFormat; /* defaultHighInputLatency is used below instead of defaultLowInputLatency because it is more important for the default stream to work reliably than it is for it to work with the lowest latency. */ hostApiInputParameters.suggestedLatency = Pa_GetDeviceInfo( hostApiInputParameters.device )->defaultHighInputLatency; hostApiInputParameters.hostApiSpecificStreamInfo = NULL; hostApiInputParametersPtr = &hostApiInputParameters; } else { hostApiInputParametersPtr = NULL; } if( outputChannelCount > 0 ) { hostApiOutputParameters.device = Pa_GetDefaultOutputDevice(); if( hostApiOutputParameters.device == paNoDevice ) return paDeviceUnavailable; hostApiOutputParameters.channelCount = outputChannelCount; hostApiOutputParameters.sampleFormat = sampleFormat; /* defaultHighOutputLatency is used below instead of defaultLowOutputLatency because it is more important for the default stream to work reliably than it is for it to work with the lowest latency. */ hostApiOutputParameters.suggestedLatency = Pa_GetDeviceInfo( hostApiOutputParameters.device )->defaultHighOutputLatency; hostApiOutputParameters.hostApiSpecificStreamInfo = NULL; hostApiOutputParametersPtr = &hostApiOutputParameters; } else { hostApiOutputParametersPtr = NULL; } result = Pa_OpenStream( stream, hostApiInputParametersPtr, hostApiOutputParametersPtr, sampleRate, framesPerBuffer, paNoFlag, streamCallback, userData ); PA_LOGAPI(("Pa_OpenDefaultStream returned:\n" )); PA_LOGAPI(("\t*(PaStream** stream): 0x%p", *stream )); PA_LOGAPI(("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) )); return result; } PaError PaUtil_ValidateStreamPointer( PaStream* stream ) { if( !PA_IS_INITIALISED_ ) return paNotInitialized; if( stream == NULL ) return paBadStreamPtr; if( ((PaUtilStreamRepresentation*)stream)->magic != PA_STREAM_MAGIC ) return paBadStreamPtr; return paNoError; } PaError Pa_CloseStream( PaStream* stream ) { PaUtilStreamInterface *interface; PaError result = PaUtil_ValidateStreamPointer( stream ); PA_LOGAPI_ENTER_PARAMS( "Pa_CloseStream" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); /* always remove the open stream from our list, even if this function eventually returns an error. Otherwise CloseOpenStreams() will get stuck in an infinite loop */ RemoveOpenStream( stream ); /* be sure to call this _before_ closing the stream */ if( result == paNoError ) { interface = PA_STREAM_INTERFACE(stream); /* abort the stream if it isn't stopped */ result = interface->IsStopped( stream ); if( result == 1 ) result = paNoError; else if( result == 0 ) result = interface->Abort( stream ); if( result == paNoError ) /** @todo REVIEW: shouldn't we close anyway? */ result = interface->Close( stream ); } PA_LOGAPI_EXIT_PAERROR( "Pa_CloseStream", result ); return result; } PaError Pa_SetStreamFinishedCallback( PaStream *stream, PaStreamFinishedCallback* streamFinishedCallback ) { PaError result = PaUtil_ValidateStreamPointer( stream ); PA_LOGAPI_ENTER_PARAMS( "Pa_SetStreamFinishedCallback" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); PA_LOGAPI(("\tPaStreamFinishedCallback* streamFinishedCallback: 0x%p\n", streamFinishedCallback )); if( result == paNoError ) { result = PA_STREAM_INTERFACE(stream)->IsStopped( stream ); if( result == 0 ) { result = paStreamIsNotStopped ; } if( result == 1 ) { PA_STREAM_REP( stream )->streamFinishedCallback = streamFinishedCallback; result = paNoError; } } PA_LOGAPI_EXIT_PAERROR( "Pa_SetStreamFinishedCallback", result ); return result; } PaError Pa_StartStream( PaStream *stream ) { PaError result = PaUtil_ValidateStreamPointer( stream ); PA_LOGAPI_ENTER_PARAMS( "Pa_StartStream" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( result == paNoError ) { result = PA_STREAM_INTERFACE(stream)->IsStopped( stream ); if( result == 0 ) { result = paStreamIsNotStopped ; } else if( result == 1 ) { result = PA_STREAM_INTERFACE(stream)->Start( stream ); } } PA_LOGAPI_EXIT_PAERROR( "Pa_StartStream", result ); return result; } PaError Pa_StopStream( PaStream *stream ) { PaError result = PaUtil_ValidateStreamPointer( stream ); PA_LOGAPI_ENTER_PARAMS( "Pa_StopStream" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( result == paNoError ) { result = PA_STREAM_INTERFACE(stream)->IsStopped( stream ); if( result == 0 ) { result = PA_STREAM_INTERFACE(stream)->Stop( stream ); } else if( result == 1 ) { result = paStreamIsStopped; } } PA_LOGAPI_EXIT_PAERROR( "Pa_StopStream", result ); return result; } PaError Pa_AbortStream( PaStream *stream ) { PaError result = PaUtil_ValidateStreamPointer( stream ); PA_LOGAPI_ENTER_PARAMS( "Pa_AbortStream" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( result == paNoError ) { result = PA_STREAM_INTERFACE(stream)->IsStopped( stream ); if( result == 0 ) { result = PA_STREAM_INTERFACE(stream)->Abort( stream ); } else if( result == 1 ) { result = paStreamIsStopped; } } PA_LOGAPI_EXIT_PAERROR( "Pa_AbortStream", result ); return result; } PaError Pa_IsStreamStopped( PaStream *stream ) { PaError result = PaUtil_ValidateStreamPointer( stream ); PA_LOGAPI_ENTER_PARAMS( "Pa_IsStreamStopped" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( result == paNoError ) result = PA_STREAM_INTERFACE(stream)->IsStopped( stream ); PA_LOGAPI_EXIT_PAERROR( "Pa_IsStreamStopped", result ); return result; } PaError Pa_IsStreamActive( PaStream *stream ) { PaError result = PaUtil_ValidateStreamPointer( stream ); PA_LOGAPI_ENTER_PARAMS( "Pa_IsStreamActive" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( result == paNoError ) result = PA_STREAM_INTERFACE(stream)->IsActive( stream ); PA_LOGAPI_EXIT_PAERROR( "Pa_IsStreamActive", result ); return result; } const PaStreamInfo* Pa_GetStreamInfo( PaStream *stream ) { PaError error = PaUtil_ValidateStreamPointer( stream ); const PaStreamInfo *result; PA_LOGAPI_ENTER_PARAMS( "Pa_GetStreamInfo" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( error != paNoError ) { result = 0; PA_LOGAPI(("Pa_GetStreamInfo returned:\n" )); PA_LOGAPI(("\tconst PaStreamInfo*: 0 [PaError error:%d ( %s )]\n", result, error, Pa_GetErrorText( error ) )); } else { result = &PA_STREAM_REP( stream )->streamInfo; PA_LOGAPI(("Pa_GetStreamInfo returned:\n" )); PA_LOGAPI(("\tconst PaStreamInfo*: 0x%p:\n", result )); PA_LOGAPI(("\t{" )); PA_LOGAPI(("\t\tint structVersion: %d\n", result->structVersion )); PA_LOGAPI(("\t\tPaTime inputLatency: %f\n", result->inputLatency )); PA_LOGAPI(("\t\tPaTime outputLatency: %f\n", result->outputLatency )); PA_LOGAPI(("\t\tdouble sampleRate: %f\n", result->sampleRate )); PA_LOGAPI(("\t}\n" )); } return result; } PaTime Pa_GetStreamTime( PaStream *stream ) { PaError error = PaUtil_ValidateStreamPointer( stream ); PaTime result; PA_LOGAPI_ENTER_PARAMS( "Pa_GetStreamTime" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( error != paNoError ) { result = 0; PA_LOGAPI(("Pa_GetStreamTime returned:\n" )); PA_LOGAPI(("\tPaTime: 0 [PaError error:%d ( %s )]\n", result, error, Pa_GetErrorText( error ) )); } else { result = PA_STREAM_INTERFACE(stream)->GetTime( stream ); PA_LOGAPI(("Pa_GetStreamTime returned:\n" )); PA_LOGAPI(("\tPaTime: %g\n", result )); } return result; } double Pa_GetStreamCpuLoad( PaStream* stream ) { PaError error = PaUtil_ValidateStreamPointer( stream ); double result; PA_LOGAPI_ENTER_PARAMS( "Pa_GetStreamCpuLoad" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( error != paNoError ) { result = 0.0; PA_LOGAPI(("Pa_GetStreamCpuLoad returned:\n" )); PA_LOGAPI(("\tdouble: 0.0 [PaError error: %d ( %s )]\n", error, Pa_GetErrorText( error ) )); } else { result = PA_STREAM_INTERFACE(stream)->GetCpuLoad( stream ); PA_LOGAPI(("Pa_GetStreamCpuLoad returned:\n" )); PA_LOGAPI(("\tdouble: %g\n", result )); } return result; } PaError Pa_ReadStream( PaStream* stream, void *buffer, unsigned long frames ) { PaError result = PaUtil_ValidateStreamPointer( stream ); PA_LOGAPI_ENTER_PARAMS( "Pa_ReadStream" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( result == paNoError ) { if( frames == 0 ) { /* XXX: Should we not allow the implementation to signal any overflow condition? */ result = paNoError; } else if( buffer == 0 ) { result = paBadBufferPtr; } else { result = PA_STREAM_INTERFACE(stream)->IsStopped( stream ); if( result == 0 ) { result = PA_STREAM_INTERFACE(stream)->Read( stream, buffer, frames ); } else if( result == 1 ) { result = paStreamIsStopped; } } } PA_LOGAPI_EXIT_PAERROR( "Pa_ReadStream", result ); return result; } PaError Pa_WriteStream( PaStream* stream, const void *buffer, unsigned long frames ) { PaError result = PaUtil_ValidateStreamPointer( stream ); PA_LOGAPI_ENTER_PARAMS( "Pa_WriteStream" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( result == paNoError ) { if( frames == 0 ) { /* XXX: Should we not allow the implementation to signal any underflow condition? */ result = paNoError; } else if( buffer == 0 ) { result = paBadBufferPtr; } else { result = PA_STREAM_INTERFACE(stream)->IsStopped( stream ); if( result == 0 ) { result = PA_STREAM_INTERFACE(stream)->Write( stream, buffer, frames ); } else if( result == 1 ) { result = paStreamIsStopped; } } } PA_LOGAPI_EXIT_PAERROR( "Pa_WriteStream", result ); return result; } signed long Pa_GetStreamReadAvailable( PaStream* stream ) { PaError error = PaUtil_ValidateStreamPointer( stream ); signed long result; PA_LOGAPI_ENTER_PARAMS( "Pa_GetStreamReadAvailable" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( error != paNoError ) { result = 0; PA_LOGAPI(("Pa_GetStreamReadAvailable returned:\n" )); PA_LOGAPI(("\tunsigned long: 0 [ PaError error: %d ( %s ) ]\n", error, Pa_GetErrorText( error ) )); } else { result = PA_STREAM_INTERFACE(stream)->GetReadAvailable( stream ); PA_LOGAPI(("Pa_GetStreamReadAvailable returned:\n" )); PA_LOGAPI(("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) )); } return result; } signed long Pa_GetStreamWriteAvailable( PaStream* stream ) { PaError error = PaUtil_ValidateStreamPointer( stream ); signed long result; PA_LOGAPI_ENTER_PARAMS( "Pa_GetStreamWriteAvailable" ); PA_LOGAPI(("\tPaStream* stream: 0x%p\n", stream )); if( error != paNoError ) { result = 0; PA_LOGAPI(("Pa_GetStreamWriteAvailable returned:\n" )); PA_LOGAPI(("\tunsigned long: 0 [ PaError error: %d ( %s ) ]\n", error, Pa_GetErrorText( error ) )); } else { result = PA_STREAM_INTERFACE(stream)->GetWriteAvailable( stream ); PA_LOGAPI(("Pa_GetStreamWriteAvailable returned:\n" )); PA_LOGAPI(("\tPaError: %d ( %s )\n", result, Pa_GetErrorText( result ) )); } return result; } PaError Pa_GetSampleSize( PaSampleFormat format ) { int result; PA_LOGAPI_ENTER_PARAMS( "Pa_GetSampleSize" ); PA_LOGAPI(("\tPaSampleFormat format: %d\n", format )); switch( format & ~paNonInterleaved ) { case paUInt8: case paInt8: result = 1; break; case paInt16: result = 2; break; case paInt24: result = 3; break; case paFloat32: case paInt32: result = 4; break; default: result = paSampleFormatNotSupported; break; } PA_LOGAPI_EXIT_PAERROR_OR_T_RESULT( "Pa_GetSampleSize", "int: %d", result ); return (PaError) result; } sources_5316/external/portaudio/pa_mac_core_internal.h0000644000176700017670000001323310707754534022066 0ustar paulpaul/* * Internal interfaces for PortAudio Apple AUHAL implementation * * PortAudio Portable Real-Time Audio Library * Latest Version at: http://www.portaudio.com * * Written by Bjorn Roche of XO Audio LLC, from PA skeleton code. * Portions copied from code by Dominic Mazzoni (who wrote a HAL implementation) * * Dominic's code was based on code by Phil Burk, Darren Gibbs, * Gord Peters, Stephane Letz, and Greg Pfiel. * * The following people also deserve acknowledgements: * * Olivier Tristan for feedback and testing * Glenn Zelniker and Z-Systems engineering for sponsoring the Blocking I/O * interface. * * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file pa_mac_core @ingroup hostapi_src @author Bjorn Roche @brief AUHAL implementation of PortAudio */ #ifndef PA_MAC_CORE_INTERNAL_H__ #define PA_MAC_CORE_INTERNAL_H__ #include #include #include "portaudio.h" #include "pa_util.h" #include "pa_hostapi.h" #include "pa_stream.h" #include "pa_allocation.h" #include "pa_cpuload.h" #include "pa_process.h" #include "pa_ringbuffer.h" #include "pa_mac_core_blocking.h" /* function prototypes */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ PaError PaMacCore_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); #ifdef __cplusplus } #endif /* __cplusplus */ #define RING_BUFFER_ADVANCE_DENOMINATOR (4) PaError ReadStream( PaStream* stream, void *buffer, unsigned long frames ); PaError WriteStream( PaStream* stream, const void *buffer, unsigned long frames ); signed long GetStreamReadAvailable( PaStream* stream ); signed long GetStreamWriteAvailable( PaStream* stream ); /* PaMacAUHAL - host api datastructure specific to this implementation */ typedef struct { PaUtilHostApiRepresentation inheritedHostApiRep; PaUtilStreamInterface callbackStreamInterface; PaUtilStreamInterface blockingStreamInterface; PaUtilAllocationGroup *allocations; /* implementation specific data goes here */ long devCount; AudioDeviceID *devIds; /*array of all audio devices*/ AudioDeviceID defaultIn; AudioDeviceID defaultOut; } PaMacAUHAL; /* stream data structure specifically for this implementation */ typedef struct PaMacCoreStream { PaUtilStreamRepresentation streamRepresentation; PaUtilCpuLoadMeasurer cpuLoadMeasurer; PaUtilBufferProcessor bufferProcessor; /* implementation specific data goes here */ bool bufferProcessorIsInitialized; AudioUnit inputUnit; AudioUnit outputUnit; AudioDeviceID inputDevice; AudioDeviceID outputDevice; size_t userInChan; size_t userOutChan; size_t inputFramesPerBuffer; size_t outputFramesPerBuffer; PaMacBlio blio; /* We use this ring buffer when input and out devs are different. */ PaUtilRingBuffer inputRingBuffer; /* We may need to do SR conversion on input. */ AudioConverterRef inputSRConverter; /* We need to preallocate an inputBuffer for reading data. */ AudioBufferList inputAudioBufferList; AudioTimeStamp startTime; /* FIXME: instead of volatile, these should be properly memory barriered */ volatile PaStreamCallbackFlags xrunFlags; volatile bool isTimeSet; volatile enum { STOPPED = 0, /* playback is completely stopped, and the user has called StopStream(). */ CALLBACK_STOPPED = 1, /* callback has requested stop, but user has not yet called StopStream(). */ STOPPING = 2, /* The stream is in the process of closing because the user has called StopStream. This state is just used internally; externally it is indistinguishable from ACTIVE.*/ ACTIVE = 3 /* The stream is active and running. */ } state; double sampleRate; //these may be different from the stream sample rate due to SR conversion: double outDeviceSampleRate; double inDeviceSampleRate; } PaMacCoreStream; #endif /* PA_MAC_CORE_INTERNAL_H__ */ sources_5316/external/portaudio/pa_mac_core_utilities.c0000644000176700017670000005465510716412660022264 0ustar paulpaul/* * Helper and utility functions for pa_mac_core.c (Apple AUHAL implementation) * * PortAudio Portable Real-Time Audio Library * Latest Version at: http://www.portaudio.com * * Written by Bjorn Roche of XO Audio LLC, from PA skeleton code. * Portions copied from code by Dominic Mazzoni (who wrote a HAL implementation) * * Dominic's code was based on code by Phil Burk, Darren Gibbs, * Gord Peters, Stephane Letz, and Greg Pfiel. * * The following people also deserve acknowledgements: * * Olivier Tristan for feedback and testing * Glenn Zelniker and Z-Systems engineering for sponsoring the Blocking I/O * interface. * * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostapi_src */ #include "pa_mac_core_utilities.h" PaError PaMacCore_SetUnixError( int err, int line ) { PaError ret; const char *errorText; if( err == 0 ) { return paNoError; } ret = paNoError; errorText = strerror( err ); /** Map Unix error to PaError. Pretty much the only one that maps is ENOMEM. */ if( err == ENOMEM ) ret = paInsufficientMemory; else ret = paInternalError; DBUG(("%d on line %d: msg='%s'\n", err, line, errorText)); PaUtil_SetLastHostErrorInfo( paCoreAudio, err, errorText ); return ret; } /* * Translates MacOS generated errors into PaErrors */ PaError PaMacCore_SetError(OSStatus error, int line, int isError) { /*FIXME: still need to handle possible ComponentResult values.*/ /* unfortunately, they don't seem to be documented anywhere.*/ PaError result; const char *errorType; const char *errorText; switch (error) { case kAudioHardwareNoError: return paNoError; case kAudioHardwareNotRunningError: errorText = "Audio Hardware Not Running"; result = paInternalError; break; case kAudioHardwareUnspecifiedError: errorText = "Unspecified Audio Hardware Error"; result = paInternalError; break; case kAudioHardwareUnknownPropertyError: errorText = "Audio Hardware: Unknown Property"; result = paInternalError; break; case kAudioHardwareBadPropertySizeError: errorText = "Audio Hardware: Bad Property Size"; result = paInternalError; break; case kAudioHardwareIllegalOperationError: errorText = "Audio Hardware: Illegal Operation"; result = paInternalError; break; case kAudioHardwareBadDeviceError: errorText = "Audio Hardware: Bad Device"; result = paInvalidDevice; break; case kAudioHardwareBadStreamError: errorText = "Audio Hardware: BadStream"; result = paBadStreamPtr; break; case kAudioHardwareUnsupportedOperationError: errorText = "Audio Hardware: Unsupported Operation"; result = paInternalError; break; case kAudioDeviceUnsupportedFormatError: errorText = "Audio Device: Unsupported Format"; result = paSampleFormatNotSupported; break; case kAudioDevicePermissionsError: errorText = "Audio Device: Permissions Error"; result = paDeviceUnavailable; break; /* Audio Unit Errors: http://developer.apple.com/documentation/MusicAudio/Reference/CoreAudio/audio_units/chapter_5_section_3.html */ case kAudioUnitErr_InvalidProperty: errorText = "Audio Unit: Invalid Property"; result = paInternalError; break; case kAudioUnitErr_InvalidParameter: errorText = "Audio Unit: Invalid Parameter"; result = paInternalError; break; case kAudioUnitErr_NoConnection: errorText = "Audio Unit: No Connection"; result = paInternalError; break; case kAudioUnitErr_FailedInitialization: errorText = "Audio Unit: Initialization Failed"; result = paInternalError; break; case kAudioUnitErr_TooManyFramesToProcess: errorText = "Audio Unit: Too Many Frames"; result = paInternalError; break; case kAudioUnitErr_IllegalInstrument: errorText = "Audio Unit: Illegal Instrument"; result = paInternalError; break; case kAudioUnitErr_InstrumentTypeNotFound: errorText = "Audio Unit: Instrument Type Not Found"; result = paInternalError; break; case kAudioUnitErr_InvalidFile: errorText = "Audio Unit: Invalid File"; result = paInternalError; break; case kAudioUnitErr_UnknownFileType: errorText = "Audio Unit: Unknown File Type"; result = paInternalError; break; case kAudioUnitErr_FileNotSpecified: errorText = "Audio Unit: File Not Specified"; result = paInternalError; break; case kAudioUnitErr_FormatNotSupported: errorText = "Audio Unit: Format Not Supported"; result = paInternalError; break; case kAudioUnitErr_Uninitialized: errorText = "Audio Unit: Unitialized"; result = paInternalError; break; case kAudioUnitErr_InvalidScope: errorText = "Audio Unit: Invalid Scope"; result = paInternalError; break; case kAudioUnitErr_PropertyNotWritable: errorText = "Audio Unit: PropertyNotWritable"; result = paInternalError; break; case kAudioUnitErr_InvalidPropertyValue: errorText = "Audio Unit: Invalid Property Value"; result = paInternalError; break; case kAudioUnitErr_PropertyNotInUse: errorText = "Audio Unit: Property Not In Use"; result = paInternalError; break; case kAudioUnitErr_Initialized: errorText = "Audio Unit: Initialized"; result = paInternalError; break; case kAudioUnitErr_InvalidOfflineRender: errorText = "Audio Unit: Invalid Offline Render"; result = paInternalError; break; case kAudioUnitErr_Unauthorized: errorText = "Audio Unit: Unauthorized"; result = paInternalError; break; case kAudioUnitErr_CannotDoInCurrentContext: errorText = "Audio Unit: cannot do in current context"; result = paInternalError; break; default: errorText = "Unknown Error"; result = paInternalError; } if (isError) errorType = "Error"; else errorType = "Warning"; char str[20]; // see if it appears to be a 4-char-code *(UInt32 *)(str + 1) = CFSwapInt32HostToBig(error); if (isprint(str[1]) && isprint(str[2]) && isprint(str[3]) && isprint(str[4])) { str[0] = str[5] = '\''; str[6] = '\0'; } else { // no, format it as an integer sprintf(str, "%d", (int)error); } DBUG(("%s on line %d: err='%s', msg=%s\n", errorType, line, str, errorText)); PaUtil_SetLastHostErrorInfo( paCoreAudio, error, errorText ); return result; } /* * This function computes an appropriate ring buffer size given * a requested latency (in seconds), sample rate and framesPerBuffer. * * The returned ringBufferSize is computed using the following * constraints: * - it must be at least 4. * - it must be at least 3x framesPerBuffer. * - it must be at least 2x the suggestedLatency. * - it must be a power of 2. * This function attempts to compute the minimum such size. * * FEEDBACK: too liberal/conservative/another way? */ long computeRingBufferSize( const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, long inputFramesPerBuffer, long outputFramesPerBuffer, double sampleRate ) { long ringSize; int index; int i; double latencyTimesChannelCount ; long framesPerBufferTimesChannelCount ; VVDBUG(( "computeRingBufferSize()\n" )); assert( inputParameters || outputParameters ); if( outputParameters && inputParameters ) { latencyTimesChannelCount = MAX( inputParameters->suggestedLatency * inputParameters->channelCount, outputParameters->suggestedLatency * outputParameters->channelCount ); framesPerBufferTimesChannelCount = MAX( inputFramesPerBuffer * inputParameters->channelCount, outputFramesPerBuffer * outputParameters->channelCount ); } else if( outputParameters ) { latencyTimesChannelCount = outputParameters->suggestedLatency * outputParameters->channelCount; framesPerBufferTimesChannelCount = outputFramesPerBuffer * outputParameters->channelCount; } else /* we have inputParameters */ { latencyTimesChannelCount = inputParameters->suggestedLatency * inputParameters->channelCount; framesPerBufferTimesChannelCount = inputFramesPerBuffer * inputParameters->channelCount; } ringSize = (long) ( latencyTimesChannelCount * sampleRate * 2 + .5); VDBUG( ( "suggested latency * channelCount: %d\n", (int) (latencyTimesChannelCount*sampleRate) ) ); if( ringSize < framesPerBufferTimesChannelCount * 3 ) ringSize = framesPerBufferTimesChannelCount * 3 ; VDBUG(("framesPerBuffer*channelCount:%d\n",(int)framesPerBufferTimesChannelCount)); VDBUG(("Ringbuffer size (1): %d\n", (int)ringSize )); /* make sure it's at least 4 */ ringSize = MAX( ringSize, 4 ); /* round up to the next power of 2 */ index = -1; for( i=0; i> i & 0x01 ) index = i; assert( index > 0 ); if( ringSize <= ( 0x01 << index ) ) ringSize = 0x01 << index ; else ringSize = 0x01 << ( index + 1 ); VDBUG(( "Final Ringbuffer size (2): %d\n", (int)ringSize )); return ringSize; } /* * Durring testing of core audio, I found that serious crashes could occur * if properties such as sample rate were changed multiple times in rapid * succession. The function below has some fancy logic to make sure that changes * are acknowledged before another is requested. That seems to help a lot. */ OSStatus propertyProc( AudioDeviceID inDevice, UInt32 inChannel, Boolean isInput, AudioDevicePropertyID inPropertyID, void* inClientData ) { MutexAndBool *mab = (MutexAndBool *) inClientData; mab->once = TRUE; pthread_mutex_unlock( &(mab->mutex) ); return noErr; } /* sets the value of the given property and waits for the change to be acknowledged, and returns the final value, which is not guaranteed by this function to be the same as the desired value. Obviously, this function can only be used for data whose input and output are the same size and format, and their size and format are known in advance.*/ PaError AudioDeviceSetPropertyNowAndWaitForChange( AudioDeviceID inDevice, UInt32 inChannel, Boolean isInput, AudioDevicePropertyID inPropertyID, UInt32 inPropertyDataSize, const void *inPropertyData, void *outPropertyData ) { OSStatus macErr; int unixErr; MutexAndBool mab; UInt32 outPropertyDataSize = inPropertyDataSize; /* First, see if it already has that value. If so, return. */ macErr = AudioDeviceGetProperty( inDevice, inChannel, isInput, inPropertyID, &outPropertyDataSize, outPropertyData ); if( macErr ) goto failMac2; if( inPropertyDataSize!=outPropertyDataSize ) return paInternalError; if( 0==memcmp( outPropertyData, inPropertyData, outPropertyDataSize ) ) return paNoError; /* setup and lock mutex */ mab.once = FALSE; unixErr = pthread_mutex_init( &mab.mutex, NULL ); if( unixErr ) goto failUnix2; unixErr = pthread_mutex_lock( &mab.mutex ); if( unixErr ) goto failUnix; /* add property listener */ macErr = AudioDeviceAddPropertyListener( inDevice, inChannel, isInput, inPropertyID, propertyProc, &mab ); if( macErr ) goto failMac; /* set property */ macErr = AudioDeviceSetProperty( inDevice, NULL, inChannel, isInput, inPropertyID, inPropertyDataSize, inPropertyData ); if( macErr ) { /* we couldn't set the property, so we'll just unlock the mutex and move on. */ pthread_mutex_unlock( &mab.mutex ); } /* wait for property to change */ unixErr = pthread_mutex_lock( &mab.mutex ); if( unixErr ) goto failUnix; /* now read the property back out */ macErr = AudioDeviceGetProperty( inDevice, inChannel, isInput, inPropertyID, &outPropertyDataSize, outPropertyData ); if( macErr ) goto failMac; /* cleanup */ AudioDeviceRemovePropertyListener( inDevice, inChannel, isInput, inPropertyID, propertyProc ); unixErr = pthread_mutex_unlock( &mab.mutex ); if( unixErr ) goto failUnix2; unixErr = pthread_mutex_destroy( &mab.mutex ); if( unixErr ) goto failUnix2; return paNoError; failUnix: pthread_mutex_destroy( &mab.mutex ); AudioDeviceRemovePropertyListener( inDevice, inChannel, isInput, inPropertyID, propertyProc ); failUnix2: DBUG( ("Error #%d while setting a device property: %s\n", unixErr, strerror( unixErr ) ) ); return paUnanticipatedHostError; failMac: pthread_mutex_destroy( &mab.mutex ); AudioDeviceRemovePropertyListener( inDevice, inChannel, isInput, inPropertyID, propertyProc ); failMac2: return ERR( macErr ); } /* * Sets the sample rate the HAL device. * if requireExact: set the sample rate or fail. * * otherwise : set the exact sample rate. * If that fails, check for available sample rates, and choose one * higher than the requested rate. If there isn't a higher one, * just use the highest available. */ PaError setBestSampleRateForDevice( const AudioDeviceID device, const bool isOutput, const bool requireExact, const Float64 desiredSrate ) { /*FIXME: changing the sample rate is disruptive to other programs using the device, so it might be good to offer a custom flag to not change the sample rate and just do conversion. (in my casual tests, there is no disruption unless the sample rate really does need to change) */ const bool isInput = isOutput ? 0 : 1; Float64 srate; UInt32 propsize = sizeof( Float64 ); OSErr err; AudioValueRange *ranges; int i=0; Float64 max = -1; /*the maximum rate available*/ Float64 best = -1; /*the lowest sample rate still greater than desired rate*/ VDBUG(("Setting sample rate for device %ld to %g.\n",device,(float)desiredSrate)); /* -- try setting the sample rate -- */ err = AudioDeviceSetPropertyNowAndWaitForChange( device, 0, isInput, kAudioDevicePropertyNominalSampleRate, propsize, &desiredSrate, &srate ); if( err ) return err; /* -- if the rate agrees, and we got no errors, we are done -- */ if( !err && srate == desiredSrate ) return paNoError; /* -- we've failed if the rates disagree and we are setting input -- */ if( requireExact ) return paInvalidSampleRate; /* -- generate a list of available sample rates -- */ err = AudioDeviceGetPropertyInfo( device, 0, isInput, kAudioDevicePropertyAvailableNominalSampleRates, &propsize, NULL ); if( err ) return ERR( err ); ranges = (AudioValueRange *)calloc( 1, propsize ); if( !ranges ) return paInsufficientMemory; err = AudioDeviceGetProperty( device, 0, isInput, kAudioDevicePropertyAvailableNominalSampleRates, &propsize, ranges ); if( err ) { free( ranges ); return ERR( err ); } VDBUG(("Requested sample rate of %g was not available.\n", (float)desiredSrate)); VDBUG(("%lu Available Sample Rates are:\n",propsize/sizeof(AudioValueRange))); #ifdef MAC_CORE_VERBOSE_DEBUG for( i=0; i max ) max = ranges[i].mMaximum; if( ranges[i].mMinimum > desiredSrate ) { if( best < 0 ) best = ranges[i].mMinimum; else if( ranges[i].mMinimum < best ) best = ranges[i].mMinimum; } } if( best < 0 ) best = max; VDBUG( ("Maximum Rate %g. best is %g.\n", max, best ) ); free( ranges ); /* -- set the sample rate -- */ propsize = sizeof( best ); err = AudioDeviceSetPropertyNowAndWaitForChange( device, 0, isInput, kAudioDevicePropertyNominalSampleRate, propsize, &best, &srate ); if( err ) return err; if( err ) return ERR( err ); /* -- if the set rate matches, we are done -- */ if( srate == best ) return paNoError; /* -- otherwise, something wierd happened: we didn't set the rate, and we got no errors. Just bail. */ return paInternalError; } /* Attempts to set the requestedFramesPerBuffer. If it can't set the exact value, it settles for something smaller if available. If nothing smaller is available, it uses the smallest available size. actualFramesPerBuffer will be set to the actual value on successful return. OK to pass NULL to actualFramesPerBuffer. The logic is very simmilar too setBestSampleRate only failure here is not usually catastrophic. */ PaError setBestFramesPerBuffer( const AudioDeviceID device, const bool isOutput, UInt32 requestedFramesPerBuffer, UInt32 *actualFramesPerBuffer ) { UInt32 afpb; const bool isInput = !isOutput; UInt32 propsize = sizeof(UInt32); OSErr err; Float64 min = -1; /*the min blocksize*/ Float64 best = -1; /*the best blocksize*/ int i=0; AudioValueRange *ranges; if( actualFramesPerBuffer == NULL ) actualFramesPerBuffer = &afpb; /* -- try and set exact FPB -- */ err = AudioDeviceSetProperty( device, NULL, 0, isInput, kAudioDevicePropertyBufferFrameSize, propsize, &requestedFramesPerBuffer); err = AudioDeviceGetProperty( device, 0, isInput, kAudioDevicePropertyBufferFrameSize, &propsize, actualFramesPerBuffer); if( err ) return ERR( err ); if( *actualFramesPerBuffer == requestedFramesPerBuffer ) return paNoError; /* we are done */ /* -- fetch available block sizes -- */ err = AudioDeviceGetPropertyInfo( device, 0, isInput, kAudioDevicePropertyBufferSizeRange, &propsize, NULL ); if( err ) return ERR( err ); ranges = (AudioValueRange *)calloc( 1, propsize ); if( !ranges ) return paInsufficientMemory; err = AudioDeviceGetProperty( device, 0, isInput, kAudioDevicePropertyBufferSizeRange, &propsize, ranges ); if( err ) { free( ranges ); return ERR( err ); } VDBUG(("Requested block size of %lu was not available.\n", requestedFramesPerBuffer )); VDBUG(("%lu Available block sizes are:\n",propsize/sizeof(AudioValueRange))); #ifdef MAC_CORE_VERBOSE_DEBUG for( i=0; i best ) best = ranges[i].mMaximum; } } if( best == -1 ) best = min; VDBUG( ("Minimum FPB %g. best is %g.\n", min, best ) ); free( ranges ); /* --- set the buffer size (ignore errors) -- */ requestedFramesPerBuffer = (UInt32) best ; propsize = sizeof( UInt32 ); err = AudioDeviceSetProperty( device, NULL, 0, isInput, kAudioDevicePropertyBufferSize, propsize, &requestedFramesPerBuffer ); /* --- read the property to check that it was set -- */ err = AudioDeviceGetProperty( device, 0, isInput, kAudioDevicePropertyBufferSize, &propsize, actualFramesPerBuffer ); if( err ) return ERR( err ); return paNoError; } sources_5316/external/portaudio/pa_dither.h0000644000176700017670000000645210474003011017660 0ustar paulpaul#ifndef PA_DITHER_H #define PA_DITHER_H /* * $Id: pa_dither.h 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library triangular dither generator * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Phil Burk, Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Functions for generating dither noise */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ /** @brief State needed to generate a dither signal */ typedef struct PaUtilTriangularDitherGenerator{ unsigned long previous; unsigned long randSeed1; unsigned long randSeed2; } PaUtilTriangularDitherGenerator; /** @brief Initialize dither state */ void PaUtil_InitializeTriangularDitherState( PaUtilTriangularDitherGenerator *ditherState ); /** @brief Calculate 2 LSB dither signal with a triangular distribution. Ranged for adding to a 1 bit right-shifted 32 bit integer prior to >>15. eg:
    signed long in = *
    signed long dither = PaUtil_Generate16BitTriangularDither( ditherState );
    signed short out = (signed short)(((in>>1) + dither) >> 15);
@return A signed long with a range of +32767 to -32768 */ signed long PaUtil_Generate16BitTriangularDither( PaUtilTriangularDitherGenerator *ditherState ); /** @brief Calculate 2 LSB dither signal with a triangular distribution. Ranged for adding to a pre-scaled float.
    float in = *
    float dither = PaUtil_GenerateFloatTriangularDither( ditherState );
    // use smaller scaler to prevent overflow when we add the dither
    signed short out = (signed short)(in*(32766.0f) + dither );
@return A float with a range of -2.0 to +1.99999. */ float PaUtil_GenerateFloatTriangularDither( PaUtilTriangularDitherGenerator *ditherState ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_DITHER_H */ sources_5316/external/portaudio/pa_mac_hostapis.c0000644000176700017670000000511310541046274021054 0ustar paulpaul/* * $Id: pa_mac_hostapis.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library Macintosh initialization table * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup macosx_src Mac OS host API initialization function table. */ #include "pa_hostapi.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ PaError PaSkeleton_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaMacCore_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaMacSm_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaJack_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); PaError PaMacAsio_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); #ifdef __cplusplus } #endif /* __cplusplus */ PaUtilHostApiInitializer *paHostApiInitializers[] = { PaMacCore_Initialize, 0 /* NULL terminated array */ }; int paDefaultHostApiIndex = 0; sources_5316/external/portaudio/pa_stream.h0000644000176700017670000001611110474003011017665 0ustar paulpaul#ifndef PA_STREAM_H #define PA_STREAM_H /* * $Id: pa_stream.h 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library * stream interface * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Interface used by pa_front to virtualize functions which operate on streams. */ #include "portaudio.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ #define PA_STREAM_MAGIC (0x18273645) /** A structure representing an (abstract) interface to a host API. Contains pointers to functions which implement the interface. All PaStreamInterface functions are guaranteed to be called with a non-null, valid stream parameter. */ typedef struct { PaError (*Close)( PaStream* stream ); PaError (*Start)( PaStream *stream ); PaError (*Stop)( PaStream *stream ); PaError (*Abort)( PaStream *stream ); PaError (*IsStopped)( PaStream *stream ); PaError (*IsActive)( PaStream *stream ); PaTime (*GetTime)( PaStream *stream ); double (*GetCpuLoad)( PaStream* stream ); PaError (*Read)( PaStream* stream, void *buffer, unsigned long frames ); PaError (*Write)( PaStream* stream, const void *buffer, unsigned long frames ); signed long (*GetReadAvailable)( PaStream* stream ); signed long (*GetWriteAvailable)( PaStream* stream ); } PaUtilStreamInterface; /** Initialize the fields of a PaUtilStreamInterface structure. */ void PaUtil_InitializeStreamInterface( PaUtilStreamInterface *streamInterface, PaError (*Close)( PaStream* ), PaError (*Start)( PaStream* ), PaError (*Stop)( PaStream* ), PaError (*Abort)( PaStream* ), PaError (*IsStopped)( PaStream* ), PaError (*IsActive)( PaStream* ), PaTime (*GetTime)( PaStream* ), double (*GetCpuLoad)( PaStream* ), PaError (*Read)( PaStream* stream, void *buffer, unsigned long frames ), PaError (*Write)( PaStream* stream, const void *buffer, unsigned long frames ), signed long (*GetReadAvailable)( PaStream* stream ), signed long (*GetWriteAvailable)( PaStream* stream ) ); /** Dummy Read function for use in interfaces to a callback based streams. Pass to the Read parameter of PaUtil_InitializeStreamInterface. @return An error code indicating that the function has no effect because the stream is a callback stream. */ PaError PaUtil_DummyRead( PaStream* stream, void *buffer, unsigned long frames ); /** Dummy Write function for use in an interfaces to callback based streams. Pass to the Write parameter of PaUtil_InitializeStreamInterface. @return An error code indicating that the function has no effect because the stream is a callback stream. */ PaError PaUtil_DummyWrite( PaStream* stream, const void *buffer, unsigned long frames ); /** Dummy GetReadAvailable function for use in interfaces to callback based streams. Pass to the GetReadAvailable parameter of PaUtil_InitializeStreamInterface. @return An error code indicating that the function has no effect because the stream is a callback stream. */ signed long PaUtil_DummyGetReadAvailable( PaStream* stream ); /** Dummy GetWriteAvailable function for use in interfaces to callback based streams. Pass to the GetWriteAvailable parameter of PaUtil_InitializeStreamInterface. @return An error code indicating that the function has no effect because the stream is a callback stream. */ signed long PaUtil_DummyGetWriteAvailable( PaStream* stream ); /** Dummy GetCpuLoad function for use in an interface to a read/write stream. Pass to the GetCpuLoad parameter of PaUtil_InitializeStreamInterface. @return Returns 0. */ double PaUtil_DummyGetCpuLoad( PaStream* stream ); /** Non host specific data for a stream. This data is used by pa_front to forward to the appropriate functions in the streamInterface structure. */ typedef struct PaUtilStreamRepresentation { unsigned long magic; /**< set to PA_STREAM_MAGIC */ struct PaUtilStreamRepresentation *nextOpenStream; /**< field used by multi-api code */ PaUtilStreamInterface *streamInterface; PaStreamCallback *streamCallback; PaStreamFinishedCallback *streamFinishedCallback; void *userData; PaStreamInfo streamInfo; } PaUtilStreamRepresentation; /** Initialize a PaUtilStreamRepresentation structure. @see PaUtil_InitializeStreamRepresentation */ void PaUtil_InitializeStreamRepresentation( PaUtilStreamRepresentation *streamRepresentation, PaUtilStreamInterface *streamInterface, PaStreamCallback *streamCallback, void *userData ); /** Clean up a PaUtilStreamRepresentation structure previously initialized by a call to PaUtil_InitializeStreamRepresentation. @see PaUtil_InitializeStreamRepresentation */ void PaUtil_TerminateStreamRepresentation( PaUtilStreamRepresentation *streamRepresentation ); /** Check that the stream pointer is valid. @return Returns paNoError if the stream pointer appears to be OK, otherwise returns an error indicating the cause of failure. */ PaError PaUtil_ValidateStreamPointer( PaStream *stream ); /** Cast an opaque stream pointer into a pointer to a PaUtilStreamRepresentation. @see PaUtilStreamRepresentation */ #define PA_STREAM_REP( stream )\ ((PaUtilStreamRepresentation*) (stream) ) /** Cast an opaque stream pointer into a pointer to a PaUtilStreamInterface. @see PaUtilStreamRepresentation, PaUtilStreamInterface */ #define PA_STREAM_INTERFACE( stream )\ PA_STREAM_REP( (stream) )->streamInterface #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_STREAM_H */ sources_5316/external/portaudio/pa_allocation.c0000644000176700017670000001540510474003011020517 0ustar paulpaul/* * $Id: pa_allocation.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library allocation group implementation * memory allocation group for tracking allocation groups * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Allocation Group implementation. */ #include "pa_allocation.h" #include "pa_util.h" /* Maintain 3 singly linked lists... linkBlocks: the buffers used to allocate the links spareLinks: links available for use in the allocations list allocations: the buffers currently allocated using PaUtil_ContextAllocateMemory() Link block size is doubled every time new links are allocated. */ #define PA_INITIAL_LINK_COUNT_ 16 struct PaUtilAllocationGroupLink { struct PaUtilAllocationGroupLink *next; void *buffer; }; /* Allocate a block of links. The first link will have it's buffer member pointing to the block, and it's next member set to . The remaining links will have NULL buffer members, and each link will point to the next link except the last, which will point to */ static struct PaUtilAllocationGroupLink *AllocateLinks( long count, struct PaUtilAllocationGroupLink *nextBlock, struct PaUtilAllocationGroupLink *nextSpare ) { struct PaUtilAllocationGroupLink *result; int i; result = (struct PaUtilAllocationGroupLink *)PaUtil_AllocateMemory( sizeof(struct PaUtilAllocationGroupLink) * count ); if( result ) { /* the block link */ result[0].buffer = result; result[0].next = nextBlock; /* the spare links */ for( i=1; ilinkCount = PA_INITIAL_LINK_COUNT_; result->linkBlocks = &links[0]; result->spareLinks = &links[1]; result->allocations = 0; } else { PaUtil_FreeMemory( links ); } } return result; } void PaUtil_DestroyAllocationGroup( PaUtilAllocationGroup* group ) { struct PaUtilAllocationGroupLink *current = group->linkBlocks; struct PaUtilAllocationGroupLink *next; while( current ) { next = current->next; PaUtil_FreeMemory( current->buffer ); current = next; } PaUtil_FreeMemory( group ); } void* PaUtil_GroupAllocateMemory( PaUtilAllocationGroup* group, long size ) { struct PaUtilAllocationGroupLink *links, *link; void *result = 0; /* allocate more links if necessary */ if( !group->spareLinks ) { /* double the link count on each block allocation */ links = AllocateLinks( group->linkCount, group->linkBlocks, group->spareLinks ); if( links ) { group->linkCount += group->linkCount; group->linkBlocks = &links[0]; group->spareLinks = &links[1]; } } if( group->spareLinks ) { result = PaUtil_AllocateMemory( size ); if( result ) { link = group->spareLinks; group->spareLinks = link->next; link->buffer = result; link->next = group->allocations; group->allocations = link; } } return result; } void PaUtil_GroupFreeMemory( PaUtilAllocationGroup* group, void *buffer ) { struct PaUtilAllocationGroupLink *current = group->allocations; struct PaUtilAllocationGroupLink *previous = 0; if( buffer == 0 ) return; /* find the right link and remove it */ while( current ) { if( current->buffer == buffer ) { if( previous ) { previous->next = current->next; } else { group->allocations = current->next; } current->buffer = 0; current->next = group->spareLinks; group->spareLinks = current; break; } previous = current; current = current->next; } PaUtil_FreeMemory( buffer ); /* free the memory whether we found it in the list or not */ } void PaUtil_FreeAllAllocations( PaUtilAllocationGroup* group ) { struct PaUtilAllocationGroupLink *current = group->allocations; struct PaUtilAllocationGroupLink *previous = 0; /* free all buffers in the allocations list */ while( current ) { PaUtil_FreeMemory( current->buffer ); current->buffer = 0; previous = current; current = current->next; } /* link the former allocations list onto the front of the spareLinks list */ if( previous ) { previous->next = group->spareLinks; group->spareLinks = group->allocations; group->allocations = 0; } } sources_5316/external/portaudio/pa_converters.h0000644000176700017670000002376010474003011020574 0ustar paulpaul#ifndef PA_CONVERTERS_H #define PA_CONVERTERS_H /* * $Id: pa_converters.h 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library sample conversion mechanism * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Phil Burk, Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Conversion functions used to convert buffers of samples from one format to another. */ #include "portaudio.h" /* for PaSampleFormat */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ struct PaUtilTriangularDitherGenerator; /** Choose an available sample format which is most appropriate for representing the requested format. If the requested format is not available higher quality formats are considered before lower quality formates. @param availableFormats A variable containing the logical OR of all available formats. @param format The desired format. @return The most appropriate available format for representing the requested format. */ PaSampleFormat PaUtil_SelectClosestAvailableFormat( PaSampleFormat availableFormats, PaSampleFormat format ); /* high level conversions functions for use by implementations */ /** The generic sample converter prototype. Sample converters convert count samples from sourceBuffer to destinationBuffer. The actual type of the data pointed to by these parameters varys for different converter functions. @param destinationBuffer A pointer to the first sample of the destination. @param destinationStride An offset between successive destination samples expressed in samples (not bytes.) It may be negative. @param sourceBuffer A pointer to the first sample of the source. @param sourceStride An offset between successive source samples expressed in samples (not bytes.) It may be negative. @param count The number of samples to convert. @param ditherState State information used to calculate dither. Converters that do not perform dithering will ignore this parameter, in which case NULL or invalid dither state may be passed. */ typedef void PaUtilConverter( void *destinationBuffer, signed int destinationStride, void *sourceBuffer, signed int sourceStride, unsigned int count, struct PaUtilTriangularDitherGenerator *ditherGenerator ); /** Find a sample converter function for the given source and destinations formats and flags (clip and dither.) @return A pointer to a PaUtilConverter which will perform the requested conversion, or NULL if the given format conversion is not supported. For conversions where clipping or dithering is not necessary, the clip and dither flags are ignored and a non-clipping or dithering version is returned. If the source and destination formats are the same, a function which copies data of the appropriate size will be returned. */ PaUtilConverter* PaUtil_SelectConverter( PaSampleFormat sourceFormat, PaSampleFormat destinationFormat, PaStreamFlags flags ); /** The generic buffer zeroer prototype. Buffer zeroers copy count zeros to destinationBuffer. The actual type of the data pointed to varys for different zeroer functions. @param destinationBuffer A pointer to the first sample of the destination. @param destinationStride An offset between successive destination samples expressed in samples (not bytes.) It may be negative. @param count The number of samples to zero. */ typedef void PaUtilZeroer( void *destinationBuffer, signed int destinationStride, unsigned int count ); /** Find a buffer zeroer function for the given destination format. @return A pointer to a PaUtilZeroer which will perform the requested zeroing. */ PaUtilZeroer* PaUtil_SelectZeroer( PaSampleFormat destinationFormat ); /*----------------------------------------------------------------------------*/ /* low level functions and data structures which may be used for substituting conversion functions */ /** The type used to store all sample conversion functions. @see paConverters; */ typedef struct{ PaUtilConverter *Float32_To_Int32; PaUtilConverter *Float32_To_Int32_Dither; PaUtilConverter *Float32_To_Int32_Clip; PaUtilConverter *Float32_To_Int32_DitherClip; PaUtilConverter *Float32_To_Int24; PaUtilConverter *Float32_To_Int24_Dither; PaUtilConverter *Float32_To_Int24_Clip; PaUtilConverter *Float32_To_Int24_DitherClip; PaUtilConverter *Float32_To_Int16; PaUtilConverter *Float32_To_Int16_Dither; PaUtilConverter *Float32_To_Int16_Clip; PaUtilConverter *Float32_To_Int16_DitherClip; PaUtilConverter *Float32_To_Int8; PaUtilConverter *Float32_To_Int8_Dither; PaUtilConverter *Float32_To_Int8_Clip; PaUtilConverter *Float32_To_Int8_DitherClip; PaUtilConverter *Float32_To_UInt8; PaUtilConverter *Float32_To_UInt8_Dither; PaUtilConverter *Float32_To_UInt8_Clip; PaUtilConverter *Float32_To_UInt8_DitherClip; PaUtilConverter *Int32_To_Float32; PaUtilConverter *Int32_To_Int24; PaUtilConverter *Int32_To_Int24_Dither; PaUtilConverter *Int32_To_Int16; PaUtilConverter *Int32_To_Int16_Dither; PaUtilConverter *Int32_To_Int8; PaUtilConverter *Int32_To_Int8_Dither; PaUtilConverter *Int32_To_UInt8; PaUtilConverter *Int32_To_UInt8_Dither; PaUtilConverter *Int24_To_Float32; PaUtilConverter *Int24_To_Int32; PaUtilConverter *Int24_To_Int16; PaUtilConverter *Int24_To_Int16_Dither; PaUtilConverter *Int24_To_Int8; PaUtilConverter *Int24_To_Int8_Dither; PaUtilConverter *Int24_To_UInt8; PaUtilConverter *Int24_To_UInt8_Dither; PaUtilConverter *Int16_To_Float32; PaUtilConverter *Int16_To_Int32; PaUtilConverter *Int16_To_Int24; PaUtilConverter *Int16_To_Int8; PaUtilConverter *Int16_To_Int8_Dither; PaUtilConverter *Int16_To_UInt8; PaUtilConverter *Int16_To_UInt8_Dither; PaUtilConverter *Int8_To_Float32; PaUtilConverter *Int8_To_Int32; PaUtilConverter *Int8_To_Int24; PaUtilConverter *Int8_To_Int16; PaUtilConverter *Int8_To_UInt8; PaUtilConverter *UInt8_To_Float32; PaUtilConverter *UInt8_To_Int32; PaUtilConverter *UInt8_To_Int24; PaUtilConverter *UInt8_To_Int16; PaUtilConverter *UInt8_To_Int8; PaUtilConverter *Copy_8_To_8; /* copy without any conversion */ PaUtilConverter *Copy_16_To_16; /* copy without any conversion */ PaUtilConverter *Copy_24_To_24; /* copy without any conversion */ PaUtilConverter *Copy_32_To_32; /* copy without any conversion */ } PaUtilConverterTable; /** A table of pointers to all required converter functions. PaUtil_SelectConverter() uses this table to lookup the appropriate conversion functions. The fields of this structure are initialized with default conversion functions. Fields may be NULL, indicating that no conversion function is available. User code may substitue optimised conversion functions by assigning different function pointers to these fields. @note If the PA_NO_STANDARD_CONVERTERS preprocessor variable is defined, PortAudio's standard converters will not be compiled, and all fields of this structure will be initialized to NULL. In such cases, users should supply their own conversion functions if the require PortAudio to open a stream that requires sample conversion. @see PaUtilConverterTable, PaUtilConverter, PaUtil_SelectConverter */ extern PaUtilConverterTable paConverters; /** The type used to store all buffer zeroing functions. @see paZeroers; */ typedef struct{ PaUtilZeroer *ZeroU8; /* unsigned 8 bit, zero == 128 */ PaUtilZeroer *Zero8; PaUtilZeroer *Zero16; PaUtilZeroer *Zero24; PaUtilZeroer *Zero32; } PaUtilZeroerTable; /** A table of pointers to all required zeroer functions. PaUtil_SelectZeroer() uses this table to lookup the appropriate conversion functions. The fields of this structure are initialized with default conversion functions. User code may substitue optimised conversion functions by assigning different function pointers to these fields. @note If the PA_NO_STANDARD_ZEROERS preprocessor variable is defined, PortAudio's standard zeroers will not be compiled, and all fields of this structure will be initialized to NULL. In such cases, users should supply their own zeroing functions for the sample sizes which they intend to use. @see PaUtilZeroerTable, PaUtilZeroer, PaUtil_SelectZeroer */ extern PaUtilZeroerTable paZeroers; #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_CONVERTERS_H */ sources_5316/external/portaudio/pa_ringbuffer.h0000644000176700017670000001506610533166104020544 0ustar paulpaul#ifndef PA_RINGBUFFER_H #define PA_RINGBUFFER_H /* * $Id: pa_ringbuffer.h 1151 2006-11-29 02:11:16Z leland_lucius $ * Portable Audio I/O Library * Ring Buffer utility. * * Author: Phil Burk, http://www.softsynth.com * modified for SMP safety on OS X by Bjorn Roche. * also allowed for const where possible. * Note that this is safe only for a single-thread reader * and a single-thread writer. * * This program is distributed with the PortAudio Portable Audio Library. * For more information see: http://www.portaudio.com * Copyright (c) 1999-2000 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ typedef struct PaUtilRingBuffer { long bufferSize; /* Number of bytes in FIFO. Power of 2. Set by PaUtil_InitRingBuffer. */ long writeIndex; /* Index of next writable byte. Set by PaUtil_AdvanceRingBufferWriteIndex. */ long readIndex; /* Index of next readable byte. Set by PaUtil_AdvanceRingBufferReadIndex. */ long bigMask; /* Used for wrapping indices with extra bit to distinguish full/empty. */ long smallMask; /* Used for fitting indices to buffer. */ char *buffer; }PaUtilRingBuffer; /** Initialize Ring Buffer. @param rbuf The ring buffer. @param numBytes The number of bytes in the buffer and must be power of 2. @param dataPtr A pointer to a previously allocated area where the data will be maintained. It must be numBytes long. @return -1 if numBytes is not a power of 2, otherwise 0. */ long PaUtil_InitializeRingBuffer( PaUtilRingBuffer *rbuf, long numBytes, void *dataPtr ); /** Clear buffer. Should only be called when buffer is NOT being read. @param rbuf The ring buffer. */ void PaUtil_FlushRingBuffer( PaUtilRingBuffer *rbuf ); /** Retrieve the number of bytes available in the ring buffer for writing. @param rbuf The ring buffer. @return The number of bytes available for writing. */ long PaUtil_GetRingBufferWriteAvailable( PaUtilRingBuffer *rbuf ); /** Retrieve the number of bytes available in the ring buffer for reading. @param rbuf The ring buffer. @return The number of bytes available for reading. */ long PaUtil_GetRingBufferReadAvailable( PaUtilRingBuffer *rbuf ); /** Write data to the ring buffer. @param rbuf The ring buffer. @param data The address of new data to write to the buffer. @param numBytes The number of bytes to be written. @return The number of bytes written. */ long PaUtil_WriteRingBuffer( PaUtilRingBuffer *rbuf, const void *data, long numBytes ); /** Read data from the ring buffer. @param rbuf The ring buffer. @param data The address where the data should be stored. @param numBytes The number of bytes to be read. @return The number of bytes read. */ long PaUtil_ReadRingBuffer( PaUtilRingBuffer *rbuf, void *data, long numBytes ); /** Get address of region(s) to which we can write data. @param rbuf The ring buffer. @param numBytes The number of bytes desired. @param dataPtr1 The address where the first (or only) region pointer will be stored. @param sizePtr1 The address where the first (or only) region length will be stored. @param dataPtr2 The address where the second region pointer will be stored if the first region is too small to satisfy numBytes. @param sizePtr2 The address where the second region length will be stored if the first region is too small to satisfy numBytes. @return The room available to be written or numBytes, whichever is smaller. */ long PaUtil_GetRingBufferWriteRegions( PaUtilRingBuffer *rbuf, long numBytes, void **dataPtr1, long *sizePtr1, void **dataPtr2, long *sizePtr2 ); /** Advance the write index to the next location to be written. @param rbuf The ring buffer. @param numBytes The number of bytes to advance. @return The new position. */ long PaUtil_AdvanceRingBufferWriteIndex( PaUtilRingBuffer *rbuf, long numBytes ); /** Get address of region(s) from which we can write data. @param rbuf The ring buffer. @param numBytes The number of bytes desired. @param dataPtr1 The address where the first (or only) region pointer will be stored. @param sizePtr1 The address where the first (or only) region length will be stored. @param dataPtr2 The address where the second region pointer will be stored if the first region is too small to satisfy numBytes. @param sizePtr2 The address where the second region length will be stored if the first region is too small to satisfy numBytes. @return The number of bytes available for reading. */ long PaUtil_GetRingBufferReadRegions( PaUtilRingBuffer *rbuf, long numBytes, void **dataPtr1, long *sizePtr1, void **dataPtr2, long *sizePtr2 ); /** Advance the read index to the next location to be read. @param rbuf The ring buffer. @param numBytes The number of bytes to advance. @return The new position. */ long PaUtil_AdvanceRingBufferReadIndex( PaUtilRingBuffer *rbuf, long numBytes ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_RINGBUFFER_H */ sources_5316/external/portaudio/pa_cpuload.h0000644000176700017670000000523710474003011020030 0ustar paulpaul#ifndef PA_CPULOAD_H #define PA_CPULOAD_H /* * $Id: pa_cpuload.h 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library CPU Load measurement functions * Portable CPU load measurement facility. * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 2002 Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Functions to assist in measuring the CPU utilization of a callback stream. Used to implement the Pa_GetStreamCpuLoad() function. */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ typedef struct { double samplingPeriod; double measurementStartTime; double averageLoad; } PaUtilCpuLoadMeasurer; /**< @todo need better name than measurer */ void PaUtil_InitializeCpuLoadMeasurer( PaUtilCpuLoadMeasurer* measurer, double sampleRate ); void PaUtil_BeginCpuLoadMeasurement( PaUtilCpuLoadMeasurer* measurer ); void PaUtil_EndCpuLoadMeasurement( PaUtilCpuLoadMeasurer* measurer, unsigned long framesProcessed ); void PaUtil_ResetCpuLoadMeasurer( PaUtilCpuLoadMeasurer* measurer ); double PaUtil_GetCpuLoad( PaUtilCpuLoadMeasurer* measurer ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_CPULOAD_H */ sources_5316/external/portaudio/pa_ringbuffer.c0000644000176700017670000002575410647137203020550 0ustar paulpaul/* * $Id: pa_ringbuffer.c 1240 2007-07-17 13:05:07Z bjornroche $ * Portable Audio I/O Library * Ring Buffer utility. * * Author: Phil Burk, http://www.softsynth.com * modified for SMP safety on Mac OS X by Bjorn Roche * modified for SMP safety on Linux by Leland Lucius * also, allowed for const where possible * Note that this is safe only for a single-thread reader and a * single-thread writer. * * This program uses the PortAudio Portable Audio Library. * For more information see: http://www.portaudio.com * Copyright (c) 1999-2000 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src */ #include #include #include #include "pa_ringbuffer.h" #include /**************** * First, we'll define some memory barrier primitives based on the system. * right now only OS X, FreeBSD, and Linux are supported. In addition to providing * memory barriers, these functions should ensure that data cached in registers * is written out to cache where it can be snooped by other CPUs. (ie, the volatile * keyword should not be required) * * the primitives that must be defined are: * * PaUtil_FullMemoryBarrier() * PaUtil_ReadMemoryBarrier() * PaUtil_WriteMemoryBarrier() * ****************/ #if defined(__APPLE__) # include /* Here are the memory barrier functions. Mac OS X only provides full memory barriers, so the three types of barriers are the same, however, these barriers are superior to compiler-based ones. */ # define PaUtil_FullMemoryBarrier() OSMemoryBarrier() # define PaUtil_ReadMemoryBarrier() OSMemoryBarrier() # define PaUtil_WriteMemoryBarrier() OSMemoryBarrier() #elif defined(__GNUC__) /* GCC >= 4.1 has built-in intrinsics. We'll use those */ # if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 1) # define PaUtil_FullMemoryBarrier() __sync_synchronize() # define PaUtil_ReadMemoryBarrier() __sync_synchronize() # define PaUtil_WriteMemoryBarrier() __sync_synchronize() /* as a fallback, GCC understands volatile asm and "memory" to mean it * should not reorder memory read/writes */ # elif defined( __PPC__ ) # define PaUtil_FullMemoryBarrier() asm volatile("sync":::"memory") # define PaUtil_ReadMemoryBarrier() asm volatile("sync":::"memory") # define PaUtil_WriteMemoryBarrier() asm volatile("sync":::"memory") # elif defined( __i386__ ) || defined( __i486__ ) || defined( __i586__ ) || defined( __i686__ ) || defined( __x86_64__ ) # define PaUtil_FullMemoryBarrier() asm volatile("mfence":::"memory") # define PaUtil_ReadMemoryBarrier() asm volatile("lfence":::"memory") # define PaUtil_WriteMemoryBarrier() asm volatile("sfence":::"memory") # else # ifdef ALLOW_SMP_DANGERS # warning Memory barriers not defined on this system or system unknown # warning For SMP safety, you should fix this. # define PaUtil_FullMemoryBarrier() # define PaUtil_ReadMemoryBarrier() # define PaUtil_WriteMemoryBarrier() # else # error Memory barriers are not defined on this system. You can still compile by defining ALLOW_SMP_DANGERS, but SMP safety will not be guaranteed. # endif # endif #else # ifdef ALLOW_SMP_DANGERS # warning Memory barriers not defined on this system or system unknown # warning For SMP safety, you should fix this. # define PaUtil_FullMemoryBarrier() # define PaUtil_ReadMemoryBarrier() # define PaUtil_WriteMemoryBarrier() # else # error Memory barriers are not defined on this system. You can still compile by defining ALLOW_SMP_DANGERS, but SMP safety will not be guaranteed. # endif #endif /*************************************************************************** * Initialize FIFO. * numBytes must be power of 2, returns -1 if not. */ long PaUtil_InitializeRingBuffer( PaUtilRingBuffer *rbuf, long numBytes, void *dataPtr ) { if( ((numBytes-1) & numBytes) != 0) return -1; /* Not Power of two. */ rbuf->bufferSize = numBytes; rbuf->buffer = (char *)dataPtr; PaUtil_FlushRingBuffer( rbuf ); rbuf->bigMask = (numBytes*2)-1; rbuf->smallMask = (numBytes)-1; return 0; } /*************************************************************************** ** Return number of bytes available for reading. */ long PaUtil_GetRingBufferReadAvailable( PaUtilRingBuffer *rbuf ) { PaUtil_ReadMemoryBarrier(); return ( (rbuf->writeIndex - rbuf->readIndex) & rbuf->bigMask ); } /*************************************************************************** ** Return number of bytes available for writing. */ long PaUtil_GetRingBufferWriteAvailable( PaUtilRingBuffer *rbuf ) { /* Since we are calling PaUtil_GetRingBufferReadAvailable, we don't need an aditional MB */ return ( rbuf->bufferSize - PaUtil_GetRingBufferReadAvailable(rbuf)); } /*************************************************************************** ** Clear buffer. Should only be called when buffer is NOT being read. */ void PaUtil_FlushRingBuffer( PaUtilRingBuffer *rbuf ) { rbuf->writeIndex = rbuf->readIndex = 0; } /*************************************************************************** ** Get address of region(s) to which we can write data. ** If the region is contiguous, size2 will be zero. ** If non-contiguous, size2 will be the size of second region. ** Returns room available to be written or numBytes, whichever is smaller. */ long PaUtil_GetRingBufferWriteRegions( PaUtilRingBuffer *rbuf, long numBytes, void **dataPtr1, long *sizePtr1, void **dataPtr2, long *sizePtr2 ) { long index; long available = PaUtil_GetRingBufferWriteAvailable( rbuf ); if( numBytes > available ) numBytes = available; /* Check to see if write is not contiguous. */ index = rbuf->writeIndex & rbuf->smallMask; if( (index + numBytes) > rbuf->bufferSize ) { /* Write data in two blocks that wrap the buffer. */ long firstHalf = rbuf->bufferSize - index; *dataPtr1 = &rbuf->buffer[index]; *sizePtr1 = firstHalf; *dataPtr2 = &rbuf->buffer[0]; *sizePtr2 = numBytes - firstHalf; } else { *dataPtr1 = &rbuf->buffer[index]; *sizePtr1 = numBytes; *dataPtr2 = NULL; *sizePtr2 = 0; } return numBytes; } /*************************************************************************** */ long PaUtil_AdvanceRingBufferWriteIndex( PaUtilRingBuffer *rbuf, long numBytes ) { /* we need to ensure that previous writes are seen before we update the write index */ PaUtil_WriteMemoryBarrier(); return rbuf->writeIndex = (rbuf->writeIndex + numBytes) & rbuf->bigMask; } /*************************************************************************** ** Get address of region(s) from which we can read data. ** If the region is contiguous, size2 will be zero. ** If non-contiguous, size2 will be the size of second region. ** Returns room available to be written or numBytes, whichever is smaller. */ long PaUtil_GetRingBufferReadRegions( PaUtilRingBuffer *rbuf, long numBytes, void **dataPtr1, long *sizePtr1, void **dataPtr2, long *sizePtr2 ) { long index; long available = PaUtil_GetRingBufferReadAvailable( rbuf ); if( numBytes > available ) numBytes = available; /* Check to see if read is not contiguous. */ index = rbuf->readIndex & rbuf->smallMask; if( (index + numBytes) > rbuf->bufferSize ) { /* Write data in two blocks that wrap the buffer. */ long firstHalf = rbuf->bufferSize - index; *dataPtr1 = &rbuf->buffer[index]; *sizePtr1 = firstHalf; *dataPtr2 = &rbuf->buffer[0]; *sizePtr2 = numBytes - firstHalf; } else { *dataPtr1 = &rbuf->buffer[index]; *sizePtr1 = numBytes; *dataPtr2 = NULL; *sizePtr2 = 0; } return numBytes; } /*************************************************************************** */ long PaUtil_AdvanceRingBufferReadIndex( PaUtilRingBuffer *rbuf, long numBytes ) { /* we need to ensure that previous writes are always seen before updating the index. */ PaUtil_WriteMemoryBarrier(); return rbuf->readIndex = (rbuf->readIndex + numBytes) & rbuf->bigMask; } /*************************************************************************** ** Return bytes written. */ long PaUtil_WriteRingBuffer( PaUtilRingBuffer *rbuf, const void *data, long numBytes ) { long size1, size2, numWritten; void *data1, *data2; numWritten = PaUtil_GetRingBufferWriteRegions( rbuf, numBytes, &data1, &size1, &data2, &size2 ); if( size2 > 0 ) { memcpy( data1, data, size1 ); data = ((char *)data) + size1; memcpy( data2, data, size2 ); } else { memcpy( data1, data, size1 ); } PaUtil_AdvanceRingBufferWriteIndex( rbuf, numWritten ); return numWritten; } /*************************************************************************** ** Return bytes read. */ long PaUtil_ReadRingBuffer( PaUtilRingBuffer *rbuf, void *data, long numBytes ) { long size1, size2, numRead; void *data1, *data2; numRead = PaUtil_GetRingBufferReadRegions( rbuf, numBytes, &data1, &size1, &data2, &size2 ); if( size2 > 0 ) { memcpy( data, data1, size1 ); data = ((char *)data) + size1; memcpy( data, data2, size2 ); } else { memcpy( data, data1, size1 ); } PaUtil_AdvanceRingBufferReadIndex( rbuf, numRead ); return numRead; } sources_5316/external/portaudio/READ_ME.TXT0000644000176700017670000000102711704065576017263 0ustar paulpaulPraats/external/portaudio/READ_ME.TXT Paul Boersma, 4 January 2010 This file describes the adaptations to the PortAudio v19 sources (2007/11) that are needed to make them compatible with Praat. Deleted lines in pa_***_hostapis.c. At the top of pa_win_*.c: #undef UNICODE In pa_win_mme.c, remove the #ifndef/endif from: #ifndef __MWERKS__ #include #include #endif /* __MWERKS__ */ In pa_mac_core.c: #include Duplicate pa_unix_util.c to pa_mac_util.c, but only for allocation and time routines. sources_5316/external/portaudio/pa_mac_core_blocking.h0000644000176700017670000001104310665641056022034 0ustar paulpaul/* * Internal blocking interfaces for PortAudio Apple AUHAL implementation * * PortAudio Portable Real-Time Audio Library * Latest Version at: http://www.portaudio.com * * Written by Bjorn Roche of XO Audio LLC, from PA skeleton code. * Portions copied from code by Dominic Mazzoni (who wrote a HAL implementation) * * Dominic's code was based on code by Phil Burk, Darren Gibbs, * Gord Peters, Stephane Letz, and Greg Pfiel. * * The following people also deserve acknowledgements: * * Olivier Tristan for feedback and testing * Glenn Zelniker and Z-Systems engineering for sponsoring the Blocking I/O * interface. * * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostaip_src */ #ifndef PA_MAC_CORE_BLOCKING_H_ #define PA_MAC_CORE_BLOCKING_H_ #include "pa_ringbuffer.h" #include "portaudio.h" #include "pa_mac_core_utilities.h" /* * Number of miliseconds to busy wait whil waiting for data in blocking calls. */ #define PA_MAC_BLIO_BUSY_WAIT_SLEEP_INTERVAL (5) /* * Define exactly one of these blocking methods * PA_MAC_BLIO_MUTEX is not actively maintained. */ #define PA_MAC_BLIO_BUSY_WAIT /* #define PA_MAC_BLIO_MUTEX */ typedef struct { PaUtilRingBuffer inputRingBuffer; PaUtilRingBuffer outputRingBuffer; size_t ringBufferFrames; PaSampleFormat inputSampleFormat; size_t inputSampleSizeActual; size_t inputSampleSizePow2; PaSampleFormat outputSampleFormat; size_t outputSampleSizeActual; size_t outputSampleSizePow2; size_t framesPerBuffer; int inChan; int outChan; //PaStreamCallbackFlags statusFlags; uint32_t statusFlags; PaError errors; /* Here we handle blocking, using condition variables. */ #ifdef PA_MAC_BLIO_MUTEX volatile bool isInputEmpty; pthread_mutex_t inputMutex; pthread_cond_t inputCond; volatile bool isOutputFull; pthread_mutex_t outputMutex; pthread_cond_t outputCond; #endif } PaMacBlio; /* * These functions operate on condition and related variables. */ PaError initializeBlioRingBuffers( PaMacBlio *blio, PaSampleFormat inputSampleFormat, PaSampleFormat outputSampleFormat, size_t framesPerBuffer, long ringBufferSize, int inChan, int outChan ); PaError destroyBlioRingBuffers( PaMacBlio *blio ); PaError resetBlioRingBuffers( PaMacBlio *blio ); int BlioCallback( const void *input, void *output, unsigned long frameCount, const PaStreamCallbackTimeInfo* timeInfo, PaStreamCallbackFlags statusFlags, void *userData ); void waitUntilBlioWriteBufferIsFlushed( PaMacBlio *blio ); #endif /*PA_MAC_CORE_BLOCKING_H_*/ sources_5316/external/portaudio/pa_types.h0000644000176700017670000000733010474003011017541 0ustar paulpaul#ifndef PA_TYPES_H #define PA_TYPES_H /* * Portable Audio I/O Library * integer type definitions * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2006 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Definition of 16 and 32 bit integer types (PaInt16, PaInt32 etc) SIZEOF_SHORT, SIZEOF_INT and SIZEOF_LONG are set by the configure script when it is used. Otherwise we default to the common 32 bit values, if your platform doesn't use configure, and doesn't use the default values below you will need to explicitly define these symbols in your make file. A PA_VALIDATE_SIZES macro is provided to assert that the values set in this file are correct. */ #ifndef SIZEOF_SHORT #define SIZEOF_SHORT 2 #endif #ifndef SIZEOF_INT #define SIZEOF_INT 4 #endif #ifndef SIZEOF_LONG #define SIZEOF_LONG 4 #endif #if SIZEOF_SHORT == 2 typedef signed short PaInt16; typedef unsigned short PaUint16; #elif SIZEOF_INT == 2 typedef signed int PaInt16; typedef unsigned int PaUint16; #else #error pa_types.h was unable to determine which type to use for 16bit integers on the target platform #endif #if SIZEOF_SHORT == 4 typedef signed short PaInt32; typedef unsigned short PaUint32; #elif SIZEOF_INT == 4 typedef signed int PaInt32; typedef unsigned int PaUint32; #elif SIZEOF_LONG == 4 typedef signed long PaInt32; typedef unsigned long PaUint32; #else #error pa_types.h was unable to determine which type to use for 32bit integers on the target platform #endif /* PA_VALIDATE_TYPE_SIZES compares the size of the integer types at runtime to ensure that PortAudio was configured correctly, and raises an assertion if they don't match the expected values. must be included in the context in which this macro is used. */ #define PA_VALIDATE_TYPE_SIZES \ { \ assert( "PortAudio: type sizes are not correct in pa_types.h" && sizeof( PaUint16 ) == 2 ); \ assert( "PortAudio: type sizes are not correct in pa_types.h" && sizeof( PaInt16 ) == 2 ); \ assert( "PortAudio: type sizes are not correct in pa_types.h" && sizeof( PaUint32 ) == 4 ); \ assert( "PortAudio: type sizes are not correct in pa_types.h" && sizeof( PaInt32 ) == 4 ); \ } #endif /* PA_TYPES_H */ sources_5316/external/portaudio/pa_win_ds.h0000644000176700017670000000715610672511232017677 0ustar paulpaul#ifndef PA_WIN_DS_H #define PA_WIN_DS_H /* * $Id: $ * PortAudio Portable Real-Time Audio Library * DirectSound specific extensions * * Copyright (c) 1999-2007 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @brief DirectSound-specific PortAudio API extension header file. */ #include "portaudio.h" #include "pa_win_waveformat.h" #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ #define paWinDirectSoundUseLowLevelLatencyParameters (0x01) #define paWinDirectSoundUseChannelMask (0x04) typedef struct PaWinDirectSoundStreamInfo{ unsigned long size; /**< sizeof(PaWinDirectSoundStreamInfo) */ PaHostApiTypeId hostApiType; /**< paDirectSound */ unsigned long version; /**< 1 */ unsigned long flags; /* low-level latency setting support TODO ** NOT IMPLEMENTED ** These settings control the number and size of host buffers in order to set latency. They will be used instead of the generic parameters to Pa_OpenStream() if flags contains the paWinDirectSoundUseLowLevelLatencyParameters flag. If PaWinDirectSoundStreamInfo structures with paWinDirectSoundUseLowLevelLatencyParameters are supplied for both input and output in a full duplex stream, then the input and output framesPerBuffer must be the same, or the larger of the two must be a multiple of the smaller, otherwise a paIncompatibleHostApiSpecificStreamInfo error will be returned from Pa_OpenStream(). unsigned long framesPerBuffer; */ /* support for WAVEFORMATEXTENSIBLE channel masks. If flags contains paWinDirectSoundUseChannelMask this allows you to specify which speakers to address in a multichannel stream. Constants for channelMask are specified in pa_win_waveformat.h */ PaWinWaveFormatChannelMask channelMask; }PaWinDirectSoundStreamInfo; #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PA_WIN_DS_H */ sources_5316/external/portaudio/pa_trace.c0000644000176700017670000000624310474003011017470 0ustar paulpaul/* * $Id: pa_trace.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library Trace Facility * Store trace information in real-time for later printing. * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2000 Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Event trace mechanism for debugging. */ #include #include #include #include "pa_trace.h" #if PA_TRACE_REALTIME_EVENTS static char *traceTextArray[PA_MAX_TRACE_RECORDS]; static int traceIntArray[PA_MAX_TRACE_RECORDS]; static int traceIndex = 0; static int traceBlock = 0; /*********************************************************************/ void PaUtil_ResetTraceMessages() { traceIndex = 0; } /*********************************************************************/ void PaUtil_DumpTraceMessages() { int i; int messageCount = (traceIndex < PA_MAX_TRACE_RECORDS) ? traceIndex : PA_MAX_TRACE_RECORDS; printf("DumpTraceMessages: traceIndex = %d\n", traceIndex ); for( i=0; i #include "pa_util.h" /* for PaUtil_GetTime() */ void PaUtil_InitializeCpuLoadMeasurer( PaUtilCpuLoadMeasurer* measurer, double sampleRate ) { assert( sampleRate > 0 ); measurer->samplingPeriod = 1. / sampleRate; measurer->averageLoad = 0.; } void PaUtil_ResetCpuLoadMeasurer( PaUtilCpuLoadMeasurer* measurer ) { measurer->averageLoad = 0.; } void PaUtil_BeginCpuLoadMeasurement( PaUtilCpuLoadMeasurer* measurer ) { measurer->measurementStartTime = PaUtil_GetTime(); } void PaUtil_EndCpuLoadMeasurement( PaUtilCpuLoadMeasurer* measurer, unsigned long framesProcessed ) { double measurementEndTime, secondsFor100Percent, measuredLoad; if( framesProcessed > 0 ){ measurementEndTime = PaUtil_GetTime(); assert( framesProcessed > 0 ); secondsFor100Percent = framesProcessed * measurer->samplingPeriod; measuredLoad = (measurementEndTime - measurer->measurementStartTime) / secondsFor100Percent; /* Low pass filter the calculated CPU load to reduce jitter using a simple IIR low pass filter. */ /** FIXME @todo these coefficients shouldn't be hardwired */ #define LOWPASS_COEFFICIENT_0 (0.9) #define LOWPASS_COEFFICIENT_1 (0.99999 - LOWPASS_COEFFICIENT_0) measurer->averageLoad = (LOWPASS_COEFFICIENT_0 * measurer->averageLoad) + (LOWPASS_COEFFICIENT_1 * measuredLoad); } } double PaUtil_GetCpuLoad( PaUtilCpuLoadMeasurer* measurer ) { return measurer->averageLoad; } sources_5316/external/portaudio/pa_mac_util.c0000644000176700017670000000715711020567576020217 0ustar paulpaul/* * $Id: pa_unix_util.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library * UNIX platform-specific support functions * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2000 Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup unix_src */ #include #include #include #include #include #include #include /* For memset */ #include #include #include "pa_util.h" //#include "pa_mac_util.h" /* Track memory allocations to avoid leaks. */ #if PA_TRACK_MEMORY static int numAllocations_ = 0; #endif void *PaUtil_AllocateMemory( long size ) { void *result = malloc( size ); #if PA_TRACK_MEMORY if( result != NULL ) numAllocations_ += 1; #endif return result; } void PaUtil_FreeMemory( void *block ) { if( block != NULL ) { free( block ); #if PA_TRACK_MEMORY numAllocations_ -= 1; #endif } } int PaUtil_CountCurrentlyAllocatedBlocks( void ) { #if PA_TRACK_MEMORY return numAllocations_; #else return 0; #endif } void Pa_Sleep( long msec ) { #ifdef HAVE_NANOSLEEP struct timespec req = {0}, rem = {0}; PaTime time = msec / 1.e3; req.tv_sec = (time_t)time; assert(time - req.tv_sec < 1.0); req.tv_nsec = (long)((time - req.tv_sec) * 1.e9); nanosleep(&req, &rem); /* XXX: Try sleeping the remaining time (contained in rem) if interrupted by a signal? */ #else while( msec > 999 ) /* For OpenBSD and IRIX, argument */ { /* to usleep must be < 1000000. */ usleep( 999000 ); msec -= 999; } usleep( msec * 1000 ); #endif } /* *** NOT USED YET: *** static int usePerformanceCounter_; static double microsecondsPerTick_; */ void PaUtil_InitializeClock( void ) { /* TODO */ } PaTime PaUtil_GetTime( void ) { #ifdef HAVE_CLOCK_GETTIME struct timespec tp; clock_gettime(CLOCK_REALTIME, &tp); return (PaTime)(tp.tv_sec + tp.tv_nsec / 1.e9); #else struct timeval tv; gettimeofday( &tv, NULL ); return (PaTime) tv.tv_usec / 1000000. + tv.tv_sec; #endif } sources_5316/external/portaudio/pa_stream.c0000644000176700017670000001225410474003011017664 0ustar paulpaul/* * $Id: pa_stream.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library * * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 2002 Ross Bencina * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Interface used by pa_front to virtualize functions which operate on streams. */ #include "pa_stream.h" void PaUtil_InitializeStreamInterface( PaUtilStreamInterface *streamInterface, PaError (*Close)( PaStream* ), PaError (*Start)( PaStream* ), PaError (*Stop)( PaStream* ), PaError (*Abort)( PaStream* ), PaError (*IsStopped)( PaStream* ), PaError (*IsActive)( PaStream* ), PaTime (*GetTime)( PaStream* ), double (*GetCpuLoad)( PaStream* ), PaError (*Read)( PaStream*, void *, unsigned long ), PaError (*Write)( PaStream*, const void *, unsigned long ), signed long (*GetReadAvailable)( PaStream* ), signed long (*GetWriteAvailable)( PaStream* ) ) { streamInterface->Close = Close; streamInterface->Start = Start; streamInterface->Stop = Stop; streamInterface->Abort = Abort; streamInterface->IsStopped = IsStopped; streamInterface->IsActive = IsActive; streamInterface->GetTime = GetTime; streamInterface->GetCpuLoad = GetCpuLoad; streamInterface->Read = Read; streamInterface->Write = Write; streamInterface->GetReadAvailable = GetReadAvailable; streamInterface->GetWriteAvailable = GetWriteAvailable; } void PaUtil_InitializeStreamRepresentation( PaUtilStreamRepresentation *streamRepresentation, PaUtilStreamInterface *streamInterface, PaStreamCallback *streamCallback, void *userData ) { streamRepresentation->magic = PA_STREAM_MAGIC; streamRepresentation->nextOpenStream = 0; streamRepresentation->streamInterface = streamInterface; streamRepresentation->streamCallback = streamCallback; streamRepresentation->streamFinishedCallback = 0; streamRepresentation->userData = userData; streamRepresentation->streamInfo.inputLatency = 0.; streamRepresentation->streamInfo.outputLatency = 0.; streamRepresentation->streamInfo.sampleRate = 0.; } void PaUtil_TerminateStreamRepresentation( PaUtilStreamRepresentation *streamRepresentation ) { streamRepresentation->magic = 0; } PaError PaUtil_DummyRead( PaStream* stream, void *buffer, unsigned long frames ) { (void)stream; /* unused parameter */ (void)buffer; /* unused parameter */ (void)frames; /* unused parameter */ return paCanNotReadFromACallbackStream; } PaError PaUtil_DummyWrite( PaStream* stream, const void *buffer, unsigned long frames ) { (void)stream; /* unused parameter */ (void)buffer; /* unused parameter */ (void)frames; /* unused parameter */ return paCanNotWriteToACallbackStream; } signed long PaUtil_DummyGetReadAvailable( PaStream* stream ) { (void)stream; /* unused parameter */ return paCanNotReadFromACallbackStream; } signed long PaUtil_DummyGetWriteAvailable( PaStream* stream ) { (void)stream; /* unused parameter */ return paCanNotWriteToACallbackStream; } double PaUtil_DummyGetCpuLoad( PaStream* stream ) { (void)stream; /* unused parameter */ return 0.0; } sources_5316/external/portaudio/pa_mac_core_utilities.h0000644000176700017670000001611010716412660022251 0ustar paulpaul/* * Helper and utility functions for pa_mac_core.c (Apple AUHAL implementation) * * PortAudio Portable Real-Time Audio Library * Latest Version at: http://www.portaudio.com * * Written by Bjorn Roche of XO Audio LLC, from PA skeleton code. * Portions copied from code by Dominic Mazzoni (who wrote a HAL implementation) * * Dominic's code was based on code by Phil Burk, Darren Gibbs, * Gord Peters, Stephane Letz, and Greg Pfiel. * * The following people also deserve acknowledgements: * * Olivier Tristan for feedback and testing * Glenn Zelniker and Z-Systems engineering for sponsoring the Blocking I/O * interface. * * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup hostapi_src */ #ifndef PA_MAC_CORE_UTILITIES_H__ #define PA_MAC_CORE_UTILITIES_H__ #include #include "portaudio.h" #include "pa_util.h" #include #include #ifndef MIN #define MIN(a, b) (((a)<(b))?(a):(b)) #endif #ifndef MAX #define MAX(a, b) (((a)<(b))?(b):(a)) #endif #define ERR(mac_error) PaMacCore_SetError(mac_error, __LINE__, 1 ) #define WARNING(mac_error) PaMacCore_SetError(mac_error, __LINE__, 0 ) /* Help keep track of AUHAL element numbers */ #define INPUT_ELEMENT (1) #define OUTPUT_ELEMENT (0) /* Normal level of debugging: fine for most apps that don't mind the occational warning being printf'ed */ /* */ #define MAC_CORE_DEBUG #ifdef MAC_CORE_DEBUG # define DBUG(MSG) do { printf("||PaMacCore (AUHAL)|| "); printf MSG ; fflush(stdout); } while(0) #else # define DBUG(MSG) #endif /* Verbose Debugging: useful for developement */ /* #define MAC_CORE_VERBOSE_DEBUG */ #ifdef MAC_CORE_VERBOSE_DEBUG # define VDBUG(MSG) do { printf("||PaMacCore (v )|| "); printf MSG ; fflush(stdout); } while(0) #else # define VDBUG(MSG) #endif /* Very Verbose Debugging: Traces every call. */ /* #define MAC_CORE_VERY_VERBOSE_DEBUG */ #ifdef MAC_CORE_VERY_VERBOSE_DEBUG # define VVDBUG(MSG) do { printf("||PaMacCore (vv)|| "); printf MSG ; fflush(stdout); } while(0) #else # define VVDBUG(MSG) #endif #define UNIX_ERR(err) PaMacCore_SetUnixError( err, __LINE__ ) PaError PaMacCore_SetUnixError( int err, int line ); /* * Translates MacOS generated errors into PaErrors */ PaError PaMacCore_SetError(OSStatus error, int line, int isError); /* * This function computes an appropriate ring buffer size given * a requested latency (in seconds), sample rate and framesPerBuffer. * * The returned ringBufferSize is computed using the following * constraints: * - it must be at least 4. * - it must be at least 3x framesPerBuffer. * - it must be at least 2x the suggestedLatency. * - it must be a power of 2. * This function attempts to compute the minimum such size. * */ long computeRingBufferSize( const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, long inputFramesPerBuffer, long outputFramesPerBuffer, double sampleRate ); /* * Durring testing of core audio, I found that serious crashes could occur * if properties such as sample rate were changed multiple times in rapid * succession. The function below has some fancy logic to make sure that changes * are acknowledged before another is requested. That seems to help a lot. */ typedef struct { bool once; /* I didn't end up using this. bdr */ pthread_mutex_t mutex; } MutexAndBool ; OSStatus propertyProc( AudioDeviceID inDevice, UInt32 inChannel, Boolean isInput, AudioDevicePropertyID inPropertyID, void* inClientData ); /* sets the value of the given property and waits for the change to be acknowledged, and returns the final value, which is not guaranteed by this function to be the same as the desired value. Obviously, this function can only be used for data whose input and output are the same size and format, and their size and format are known in advance.*/ PaError AudioDeviceSetPropertyNowAndWaitForChange( AudioDeviceID inDevice, UInt32 inChannel, Boolean isInput, AudioDevicePropertyID inPropertyID, UInt32 inPropertyDataSize, const void *inPropertyData, void *outPropertyData ); /* * Sets the sample rate the HAL device. * if requireExact: set the sample rate or fail. * * otherwise : set the exact sample rate. * If that fails, check for available sample rates, and choose one * higher than the requested rate. If there isn't a higher one, * just use the highest available. */ PaError setBestSampleRateForDevice( const AudioDeviceID device, const bool isOutput, const bool requireExact, const Float64 desiredSrate ); /* Attempts to set the requestedFramesPerBuffer. If it can't set the exact value, it settles for something smaller if available. If nothing smaller is available, it uses the smallest available size. actualFramesPerBuffer will be set to the actual value on successful return. OK to pass NULL to actualFramesPerBuffer. The logic is very simmilar too setBestSampleRate only failure here is not usually catastrophic. */ PaError setBestFramesPerBuffer( const AudioDeviceID device, const bool isOutput, UInt32 requestedFramesPerBuffer, UInt32 *actualFramesPerBuffer ); #endif /* PA_MAC_CORE_UTILITIES_H__*/ sources_5316/external/portaudio/pa_skeleton.c0000644000176700017670000006671010474003011020223 0ustar paulpaul/* * $Id: pa_skeleton.c 1097 2006-08-26 08:27:53Z rossb $ * Portable Audio I/O Library skeleton implementation * demonstrates how to use the common functions to implement support * for a host API * * Based on the Open Source API proposed by Ross Bencina * Copyright (c) 1999-2002 Ross Bencina, Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /* * The text above constitutes the entire PortAudio license; however, * the PortAudio community also makes the following non-binding requests: * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. It is also * requested that these non-binding requests be included along with the * license above. */ /** @file @ingroup common_src @brief Skeleton implementation of support for a host API. @note This file is provided as a starting point for implementing support for a new host API. IMPLEMENT ME comments are used to indicate functionality which much be customised for each implementation. */ #include /* strlen() */ #include "pa_util.h" #include "pa_allocation.h" #include "pa_hostapi.h" #include "pa_stream.h" #include "pa_cpuload.h" #include "pa_process.h" /* prototypes for functions declared in this file */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ PaError PaSkeleton_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index ); #ifdef __cplusplus } #endif /* __cplusplus */ static void Terminate( struct PaUtilHostApiRepresentation *hostApi ); static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ); static PaError CloseStream( PaStream* stream ); static PaError StartStream( PaStream *stream ); static PaError StopStream( PaStream *stream ); static PaError AbortStream( PaStream *stream ); static PaError IsStreamStopped( PaStream *s ); static PaError IsStreamActive( PaStream *stream ); static PaTime GetStreamTime( PaStream *stream ); static double GetStreamCpuLoad( PaStream* stream ); static PaError ReadStream( PaStream* stream, void *buffer, unsigned long frames ); static PaError WriteStream( PaStream* stream, const void *buffer, unsigned long frames ); static signed long GetStreamReadAvailable( PaStream* stream ); static signed long GetStreamWriteAvailable( PaStream* stream ); /* IMPLEMENT ME: a macro like the following one should be used for reporting host errors */ #define PA_SKELETON_SET_LAST_HOST_ERROR( errorCode, errorText ) \ PaUtil_SetLastHostErrorInfo( paInDevelopment, errorCode, errorText ) /* PaSkeletonHostApiRepresentation - host api datastructure specific to this implementation */ typedef struct { PaUtilHostApiRepresentation inheritedHostApiRep; PaUtilStreamInterface callbackStreamInterface; PaUtilStreamInterface blockingStreamInterface; PaUtilAllocationGroup *allocations; /* implementation specific data goes here */ } PaSkeletonHostApiRepresentation; /* IMPLEMENT ME: rename this */ PaError PaSkeleton_Initialize( PaUtilHostApiRepresentation **hostApi, PaHostApiIndex hostApiIndex ) { PaError result = paNoError; int i, deviceCount; PaSkeletonHostApiRepresentation *skeletonHostApi; PaDeviceInfo *deviceInfoArray; skeletonHostApi = (PaSkeletonHostApiRepresentation*)PaUtil_AllocateMemory( sizeof(PaSkeletonHostApiRepresentation) ); if( !skeletonHostApi ) { result = paInsufficientMemory; goto error; } skeletonHostApi->allocations = PaUtil_CreateAllocationGroup(); if( !skeletonHostApi->allocations ) { result = paInsufficientMemory; goto error; } *hostApi = &skeletonHostApi->inheritedHostApiRep; (*hostApi)->info.structVersion = 1; (*hostApi)->info.type = paInDevelopment; /* IMPLEMENT ME: change to correct type id */ (*hostApi)->info.name = "skeleton implementation"; /* IMPLEMENT ME: change to correct name */ (*hostApi)->info.defaultInputDevice = paNoDevice; /* IMPLEMENT ME */ (*hostApi)->info.defaultOutputDevice = paNoDevice; /* IMPLEMENT ME */ (*hostApi)->info.deviceCount = 0; deviceCount = 0; /* IMPLEMENT ME */ if( deviceCount > 0 ) { (*hostApi)->deviceInfos = (PaDeviceInfo**)PaUtil_GroupAllocateMemory( skeletonHostApi->allocations, sizeof(PaDeviceInfo*) * deviceCount ); if( !(*hostApi)->deviceInfos ) { result = paInsufficientMemory; goto error; } /* allocate all device info structs in a contiguous block */ deviceInfoArray = (PaDeviceInfo*)PaUtil_GroupAllocateMemory( skeletonHostApi->allocations, sizeof(PaDeviceInfo) * deviceCount ); if( !deviceInfoArray ) { result = paInsufficientMemory; goto error; } for( i=0; i < deviceCount; ++i ) { PaDeviceInfo *deviceInfo = &deviceInfoArray[i]; deviceInfo->structVersion = 2; deviceInfo->hostApi = hostApiIndex; deviceInfo->name = 0; /* IMPLEMENT ME: allocate block and copy name eg: deviceName = (char*)PaUtil_GroupAllocateMemory( skeletonHostApi->allocations, strlen(srcName) + 1 ); if( !deviceName ) { result = paInsufficientMemory; goto error; } strcpy( deviceName, srcName ); deviceInfo->name = deviceName; */ deviceInfo->maxInputChannels = 0; /* IMPLEMENT ME */ deviceInfo->maxOutputChannels = 0; /* IMPLEMENT ME */ deviceInfo->defaultLowInputLatency = 0.; /* IMPLEMENT ME */ deviceInfo->defaultLowOutputLatency = 0.; /* IMPLEMENT ME */ deviceInfo->defaultHighInputLatency = 0.; /* IMPLEMENT ME */ deviceInfo->defaultHighOutputLatency = 0.; /* IMPLEMENT ME */ deviceInfo->defaultSampleRate = 0.; /* IMPLEMENT ME */ (*hostApi)->deviceInfos[i] = deviceInfo; ++(*hostApi)->info.deviceCount; } } (*hostApi)->Terminate = Terminate; (*hostApi)->OpenStream = OpenStream; (*hostApi)->IsFormatSupported = IsFormatSupported; PaUtil_InitializeStreamInterface( &skeletonHostApi->callbackStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, GetStreamCpuLoad, PaUtil_DummyRead, PaUtil_DummyWrite, PaUtil_DummyGetReadAvailable, PaUtil_DummyGetWriteAvailable ); PaUtil_InitializeStreamInterface( &skeletonHostApi->blockingStreamInterface, CloseStream, StartStream, StopStream, AbortStream, IsStreamStopped, IsStreamActive, GetStreamTime, PaUtil_DummyGetCpuLoad, ReadStream, WriteStream, GetStreamReadAvailable, GetStreamWriteAvailable ); return result; error: if( skeletonHostApi ) { if( skeletonHostApi->allocations ) { PaUtil_FreeAllAllocations( skeletonHostApi->allocations ); PaUtil_DestroyAllocationGroup( skeletonHostApi->allocations ); } PaUtil_FreeMemory( skeletonHostApi ); } return result; } static void Terminate( struct PaUtilHostApiRepresentation *hostApi ) { PaSkeletonHostApiRepresentation *skeletonHostApi = (PaSkeletonHostApiRepresentation*)hostApi; /* IMPLEMENT ME: - clean up any resources not handled by the allocation group */ if( skeletonHostApi->allocations ) { PaUtil_FreeAllAllocations( skeletonHostApi->allocations ); PaUtil_DestroyAllocationGroup( skeletonHostApi->allocations ); } PaUtil_FreeMemory( skeletonHostApi ); } static PaError IsFormatSupported( struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ) { int inputChannelCount, outputChannelCount; PaSampleFormat inputSampleFormat, outputSampleFormat; if( inputParameters ) { inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; /* all standard sample formats are supported by the buffer adapter, this implementation doesn't support any custom sample formats */ if( inputSampleFormat & paCustomFormat ) return paSampleFormatNotSupported; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that input device can support inputChannelCount */ if( inputChannelCount > hostApi->deviceInfos[ inputParameters->device ]->maxInputChannels ) return paInvalidChannelCount; /* validate inputStreamInfo */ if( inputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ } else { inputChannelCount = 0; } if( outputParameters ) { outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; /* all standard sample formats are supported by the buffer adapter, this implementation doesn't support any custom sample formats */ if( outputSampleFormat & paCustomFormat ) return paSampleFormatNotSupported; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that output device can support outputChannelCount */ if( outputChannelCount > hostApi->deviceInfos[ outputParameters->device ]->maxOutputChannels ) return paInvalidChannelCount; /* validate outputStreamInfo */ if( outputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ } else { outputChannelCount = 0; } /* IMPLEMENT ME: - if a full duplex stream is requested, check that the combination of input and output parameters is supported if necessary - check that the device supports sampleRate Because the buffer adapter handles conversion between all standard sample formats, the following checks are only required if paCustomFormat is implemented, or under some other unusual conditions. - check that input device can support inputSampleFormat, or that we have the capability to convert from inputSampleFormat to a native format - check that output device can support outputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format */ /* suppress unused variable warnings */ (void) sampleRate; return paFormatIsSupported; } /* PaSkeletonStream - a stream data structure specifically for this implementation */ typedef struct PaSkeletonStream { /* IMPLEMENT ME: rename this */ PaUtilStreamRepresentation streamRepresentation; PaUtilCpuLoadMeasurer cpuLoadMeasurer; PaUtilBufferProcessor bufferProcessor; /* IMPLEMENT ME: - implementation specific data goes here */ unsigned long framesPerHostCallback; /* just an example */ } PaSkeletonStream; /* see pa_hostapi.h for a list of validity guarantees made about OpenStream parameters */ static PaError OpenStream( struct PaUtilHostApiRepresentation *hostApi, PaStream** s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ) { PaError result = paNoError; PaSkeletonHostApiRepresentation *skeletonHostApi = (PaSkeletonHostApiRepresentation*)hostApi; PaSkeletonStream *stream = 0; unsigned long framesPerHostBuffer = framesPerBuffer; /* these may not be equivalent for all implementations */ int inputChannelCount, outputChannelCount; PaSampleFormat inputSampleFormat, outputSampleFormat; PaSampleFormat hostInputSampleFormat, hostOutputSampleFormat; if( inputParameters ) { inputChannelCount = inputParameters->channelCount; inputSampleFormat = inputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( inputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that input device can support inputChannelCount */ if( inputChannelCount > hostApi->deviceInfos[ inputParameters->device ]->maxInputChannels ) return paInvalidChannelCount; /* validate inputStreamInfo */ if( inputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ /* IMPLEMENT ME - establish which host formats are available */ hostInputSampleFormat = PaUtil_SelectClosestAvailableFormat( paInt16 /* native formats */, inputSampleFormat ); } else { inputChannelCount = 0; inputSampleFormat = hostInputSampleFormat = paInt16; /* Surpress 'uninitialised var' warnings. */ } if( outputParameters ) { outputChannelCount = outputParameters->channelCount; outputSampleFormat = outputParameters->sampleFormat; /* unless alternate device specification is supported, reject the use of paUseHostApiSpecificDeviceSpecification */ if( outputParameters->device == paUseHostApiSpecificDeviceSpecification ) return paInvalidDevice; /* check that output device can support inputChannelCount */ if( outputChannelCount > hostApi->deviceInfos[ outputParameters->device ]->maxOutputChannels ) return paInvalidChannelCount; /* validate outputStreamInfo */ if( outputParameters->hostApiSpecificStreamInfo ) return paIncompatibleHostApiSpecificStreamInfo; /* this implementation doesn't use custom stream info */ /* IMPLEMENT ME - establish which host formats are available */ hostOutputSampleFormat = PaUtil_SelectClosestAvailableFormat( paInt16 /* native formats */, outputSampleFormat ); } else { outputChannelCount = 0; outputSampleFormat = hostOutputSampleFormat = paInt16; /* Surpress 'uninitialized var' warnings. */ } /* IMPLEMENT ME: ( the following two checks are taken care of by PaUtil_InitializeBufferProcessor() FIXME - checks needed? ) - check that input device can support inputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format - check that output device can support outputSampleFormat, or that we have the capability to convert from outputSampleFormat to a native format - if a full duplex stream is requested, check that the combination of input and output parameters is supported - check that the device supports sampleRate - alter sampleRate to a close allowable rate if possible / necessary - validate suggestedInputLatency and suggestedOutputLatency parameters, use default values where necessary */ /* validate platform specific flags */ if( (streamFlags & paPlatformSpecificFlags) != 0 ) return paInvalidFlag; /* unexpected platform specific flag */ stream = (PaSkeletonStream*)PaUtil_AllocateMemory( sizeof(PaSkeletonStream) ); if( !stream ) { result = paInsufficientMemory; goto error; } if( streamCallback ) { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &skeletonHostApi->callbackStreamInterface, streamCallback, userData ); } else { PaUtil_InitializeStreamRepresentation( &stream->streamRepresentation, &skeletonHostApi->blockingStreamInterface, streamCallback, userData ); } PaUtil_InitializeCpuLoadMeasurer( &stream->cpuLoadMeasurer, sampleRate ); /* we assume a fixed host buffer size in this example, but the buffer processor can also support bounded and unknown host buffer sizes by passing paUtilBoundedHostBufferSize or paUtilUnknownHostBufferSize instead of paUtilFixedHostBufferSize below. */ result = PaUtil_InitializeBufferProcessor( &stream->bufferProcessor, inputChannelCount, inputSampleFormat, hostInputSampleFormat, outputChannelCount, outputSampleFormat, hostOutputSampleFormat, sampleRate, streamFlags, framesPerBuffer, framesPerHostBuffer, paUtilFixedHostBufferSize, streamCallback, userData ); if( result != paNoError ) goto error; /* IMPLEMENT ME: initialise the following fields with estimated or actual values. */ stream->streamRepresentation.streamInfo.inputLatency = PaUtil_GetBufferProcessorInputLatency(&stream->bufferProcessor); stream->streamRepresentation.streamInfo.outputLatency = PaUtil_GetBufferProcessorOutputLatency(&stream->bufferProcessor); stream->streamRepresentation.streamInfo.sampleRate = sampleRate; /* IMPLEMENT ME: - additional stream setup + opening */ stream->framesPerHostCallback = framesPerHostBuffer; *s = (PaStream*)stream; return result; error: if( stream ) PaUtil_FreeMemory( stream ); return result; } /* ExampleHostProcessingLoop() illustrates the kind of processing which may occur in a host implementation. */ static void ExampleHostProcessingLoop( void *inputBuffer, void *outputBuffer, void *userData ) { PaSkeletonStream *stream = (PaSkeletonStream*)userData; PaStreamCallbackTimeInfo timeInfo = {0,0,0}; /* IMPLEMENT ME */ int callbackResult; unsigned long framesProcessed; PaUtil_BeginCpuLoadMeasurement( &stream->cpuLoadMeasurer ); /* IMPLEMENT ME: - generate timing information - handle buffer slips */ /* If you need to byte swap or shift inputBuffer to convert it into a portaudio format, do it here. */ PaUtil_BeginBufferProcessing( &stream->bufferProcessor, &timeInfo, 0 /* IMPLEMENT ME: pass underflow/overflow flags when necessary */ ); /* depending on whether the host buffers are interleaved, non-interleaved or a mixture, you will want to call PaUtil_SetInterleaved*Channels(), PaUtil_SetNonInterleaved*Channel() or PaUtil_Set*Channel() here. */ PaUtil_SetInputFrameCount( &stream->bufferProcessor, 0 /* default to host buffer size */ ); PaUtil_SetInterleavedInputChannels( &stream->bufferProcessor, 0, /* first channel of inputBuffer is channel 0 */ inputBuffer, 0 ); /* 0 - use inputChannelCount passed to init buffer processor */ PaUtil_SetOutputFrameCount( &stream->bufferProcessor, 0 /* default to host buffer size */ ); PaUtil_SetInterleavedOutputChannels( &stream->bufferProcessor, 0, /* first channel of outputBuffer is channel 0 */ outputBuffer, 0 ); /* 0 - use outputChannelCount passed to init buffer processor */ /* you must pass a valid value of callback result to PaUtil_EndBufferProcessing() in general you would pass paContinue for normal operation, and paComplete to drain the buffer processor's internal output buffer. You can check whether the buffer processor's output buffer is empty using PaUtil_IsBufferProcessorOuputEmpty( bufferProcessor ) */ callbackResult = paContinue; framesProcessed = PaUtil_EndBufferProcessing( &stream->bufferProcessor, &callbackResult ); /* If you need to byte swap or shift outputBuffer to convert it to host format, do it here. */ PaUtil_EndCpuLoadMeasurement( &stream->cpuLoadMeasurer, framesProcessed ); if( callbackResult == paContinue ) { /* nothing special to do */ } else if( callbackResult == paAbort ) { /* IMPLEMENT ME - finish playback immediately */ /* once finished, call the finished callback */ if( stream->streamRepresentation.streamFinishedCallback != 0 ) stream->streamRepresentation.streamFinishedCallback( stream->streamRepresentation.userData ); } else { /* User callback has asked us to stop with paComplete or other non-zero value */ /* IMPLEMENT ME - finish playback once currently queued audio has completed */ /* once finished, call the finished callback */ if( stream->streamRepresentation.streamFinishedCallback != 0 ) stream->streamRepresentation.streamFinishedCallback( stream->streamRepresentation.userData ); } } /* When CloseStream() is called, the multi-api layer ensures that the stream has already been stopped or aborted. */ static PaError CloseStream( PaStream* s ) { PaError result = paNoError; PaSkeletonStream *stream = (PaSkeletonStream*)s; /* IMPLEMENT ME: - additional stream closing + cleanup */ PaUtil_TerminateBufferProcessor( &stream->bufferProcessor ); PaUtil_TerminateStreamRepresentation( &stream->streamRepresentation ); PaUtil_FreeMemory( stream ); return result; } static PaError StartStream( PaStream *s ) { PaError result = paNoError; PaSkeletonStream *stream = (PaSkeletonStream*)s; PaUtil_ResetBufferProcessor( &stream->bufferProcessor ); /* IMPLEMENT ME, see portaudio.h for required behavior */ /* suppress unused function warning. the code in ExampleHostProcessingLoop or something similar should be implemented to feed samples to and from the host after StartStream() is called. */ (void) ExampleHostProcessingLoop; return result; } static PaError StopStream( PaStream *s ) { PaError result = paNoError; PaSkeletonStream *stream = (PaSkeletonStream*)s; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior */ return result; } static PaError AbortStream( PaStream *s ) { PaError result = paNoError; PaSkeletonStream *stream = (PaSkeletonStream*)s; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior */ return result; } static PaError IsStreamStopped( PaStream *s ) { PaSkeletonStream *stream = (PaSkeletonStream*)s; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior */ return 0; } static PaError IsStreamActive( PaStream *s ) { PaSkeletonStream *stream = (PaSkeletonStream*)s; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior */ return 0; } static PaTime GetStreamTime( PaStream *s ) { PaSkeletonStream *stream = (PaSkeletonStream*)s; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ return 0; } static double GetStreamCpuLoad( PaStream* s ) { PaSkeletonStream *stream = (PaSkeletonStream*)s; return PaUtil_GetCpuLoad( &stream->cpuLoadMeasurer ); } /* As separate stream interfaces are used for blocking and callback streams, the following functions can be guaranteed to only be called for blocking streams. */ static PaError ReadStream( PaStream* s, void *buffer, unsigned long frames ) { PaSkeletonStream *stream = (PaSkeletonStream*)s; /* suppress unused variable warnings */ (void) buffer; (void) frames; (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ return paNoError; } static PaError WriteStream( PaStream* s, const void *buffer, unsigned long frames ) { PaSkeletonStream *stream = (PaSkeletonStream*)s; /* suppress unused variable warnings */ (void) buffer; (void) frames; (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ return paNoError; } static signed long GetStreamReadAvailable( PaStream* s ) { PaSkeletonStream *stream = (PaSkeletonStream*)s; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ return 0; } static signed long GetStreamWriteAvailable( PaStream* s ) { PaSkeletonStream *stream = (PaSkeletonStream*)s; /* suppress unused variable warnings */ (void) stream; /* IMPLEMENT ME, see portaudio.h for required behavior*/ return 0; } sources_5316/external/espeak/0000775000176700017670000000000011753205751015025 5ustar paulpaulsources_5316/external/espeak/wavegen.cpp0000775000176700017670000014567011723710247017203 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2007 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, see: * * . * ***************************************************************************/ #include "StdAfx.h" // this version keeps wavemult window as a constant fraction // of the cycle length - but that spreads out the HF peaks too much #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "sonic.h" //#undef INCLUDE_KLATT #ifdef USE_PORTAUDIO #include "portaudio.h" #undef USE_PORTAUDIO // determine portaudio version by looking for a #define which is not in V18 #ifdef paNeverDropInput #define USE_PORTAUDIO 19 #else #define USE_PORTAUDIO 18 #endif #endif #define N_SINTAB 2048 #include "sintab.h" #define PI 3.1415927 #define PI2 6.283185307 #define N_WAV_BUF 10 voice_t *wvoice; FILE *f_log = NULL; int option_waveout = 0; static int option_harmonic1 = 10; // 10 int option_log_frames = 0; static int flutter_amp = 64; static int general_amplitude = 60; static int consonant_amp = 26; // 24 int embedded_value[N_EMBEDDED_VALUES]; static int PHASE_INC_FACTOR; int samplerate = 0; // this is set by Wavegeninit() int samplerate_native=0; extern int option_device_number; extern int option_quiet; static wavegen_peaks_t peaks[N_PEAKS]; static int peak_harmonic[N_PEAKS]; static int peak_height[N_PEAKS]; int echo_head; int echo_tail; int echo_amp = 0; short echo_buf[N_ECHO_BUF]; static int echo_length = 0; // period (in sample\) to ensure completion of echo at the end of speech, set in WavegenSetEcho() static int voicing; static RESONATOR rbreath[N_PEAKS]; static int harm_sqrt_n = 0; #define N_LOWHARM 30 static int harm_inc[N_LOWHARM]; // only for these harmonics do we interpolate amplitude between steps static int *harmspect; static int hswitch=0; static int hspect[2][MAX_HARMONIC]; // 2 copies, we interpolate between then static int max_hval=0; static int nsamples=0; // number to do static int modulation_type = 0; static int glottal_flag = 0; static int glottal_reduce = 0; WGEN_DATA wdata; static int amp_ix; static int amp_inc; static unsigned char *amplitude_env = NULL; static int samplecount=0; // number done static int samplecount_start=0; // count at start of this segment static int end_wave=0; // continue to end of wave cycle static int wavephase; static int phaseinc; static int cycle_samples; // number of samples in a cycle at current pitch static int cbytes; static int hf_factor; static double minus_pi_t; static double two_pi_t; unsigned char *out_ptr; unsigned char *out_start; unsigned char *out_end; int outbuf_size = 0; // the queue of operations passed to wavegen from sythesize long64 wcmdq[N_WCMDQ][4]; int wcmdq_head=0; int wcmdq_tail=0; // pitch,speed, int embedded_default[N_EMBEDDED_VALUES] = {0, 50,175,100,50, 0, 0, 0,175,0,0,0,0,0,0}; static int embedded_max[N_EMBEDDED_VALUES] = {0,0x7fff,750,300,99,99,99, 0,750,0,0,0,0,4,0}; #define N_CALLBACK_IX N_WAV_BUF-2 // adjust this delay to match display with the currently spoken word int current_source_index=0; extern FILE *f_wave; #if (USE_PORTAUDIO == 18) static PortAudioStream *pa_stream=NULL; #endif #if (USE_PORTAUDIO == 19) static PaStream *pa_stream=NULL; #endif static sonicStream sonicSpeedupStream = NULL; double sonicSpeed = 1.0; // 1st index=roughness // 2nd index=modulation_type // value: bits 0-3 amplitude (16ths), bits 4-7 every n cycles #define N_ROUGHNESS 8 static unsigned char modulation_tab[N_ROUGHNESS][8] = { {0, 0x00, 0x00, 0x00, 0, 0x46, 0xf2, 0x29}, {0, 0x2f, 0x00, 0x2f, 0, 0x45, 0xf2, 0x29}, {0, 0x2f, 0x00, 0x2e, 0, 0x45, 0xf2, 0x28}, {0, 0x2e, 0x00, 0x2d, 0, 0x34, 0xf2, 0x28}, {0, 0x2d, 0x2d, 0x2c, 0, 0x34, 0xf2, 0x28}, {0, 0x2b, 0x2b, 0x2b, 0, 0x34, 0xf2, 0x28}, {0, 0x2a, 0x2a, 0x2a, 0, 0x34, 0xf2, 0x28}, {0, 0x29, 0x29, 0x29, 0, 0x34, 0xf2, 0x28}, }; // Flutter table, to add natural variations to the pitch #define N_FLUTTER 0x170 static int Flutter_inc; static const unsigned char Flutter_tab[N_FLUTTER] = { 0x80, 0x9b, 0xb5, 0xcb, 0xdc, 0xe8, 0xed, 0xec, 0xe6, 0xdc, 0xce, 0xbf, 0xb0, 0xa3, 0x98, 0x90, 0x8c, 0x8b, 0x8c, 0x8f, 0x92, 0x94, 0x95, 0x92, 0x8c, 0x83, 0x78, 0x69, 0x59, 0x49, 0x3c, 0x31, 0x2a, 0x29, 0x2d, 0x36, 0x44, 0x56, 0x69, 0x7d, 0x8f, 0x9f, 0xaa, 0xb1, 0xb2, 0xad, 0xa4, 0x96, 0x87, 0x78, 0x69, 0x5c, 0x53, 0x4f, 0x4f, 0x55, 0x5e, 0x6b, 0x7a, 0x88, 0x96, 0xa2, 0xab, 0xb0, 0xb1, 0xae, 0xa8, 0xa0, 0x98, 0x91, 0x8b, 0x88, 0x89, 0x8d, 0x94, 0x9d, 0xa8, 0xb2, 0xbb, 0xc0, 0xc1, 0xbd, 0xb4, 0xa5, 0x92, 0x7c, 0x63, 0x4a, 0x32, 0x1e, 0x0e, 0x05, 0x02, 0x05, 0x0f, 0x1e, 0x30, 0x44, 0x59, 0x6d, 0x7f, 0x8c, 0x96, 0x9c, 0x9f, 0x9f, 0x9d, 0x9b, 0x99, 0x99, 0x9c, 0xa1, 0xa9, 0xb3, 0xbf, 0xca, 0xd5, 0xdc, 0xe0, 0xde, 0xd8, 0xcc, 0xbb, 0xa6, 0x8f, 0x77, 0x60, 0x4b, 0x3a, 0x2e, 0x28, 0x29, 0x2f, 0x3a, 0x48, 0x59, 0x6a, 0x7a, 0x86, 0x90, 0x94, 0x95, 0x91, 0x89, 0x80, 0x75, 0x6b, 0x62, 0x5c, 0x5a, 0x5c, 0x61, 0x69, 0x74, 0x80, 0x8a, 0x94, 0x9a, 0x9e, 0x9d, 0x98, 0x90, 0x86, 0x7c, 0x71, 0x68, 0x62, 0x60, 0x63, 0x6b, 0x78, 0x88, 0x9b, 0xaf, 0xc2, 0xd2, 0xdf, 0xe6, 0xe7, 0xe2, 0xd7, 0xc6, 0xb2, 0x9c, 0x84, 0x6f, 0x5b, 0x4b, 0x40, 0x39, 0x37, 0x38, 0x3d, 0x43, 0x4a, 0x50, 0x54, 0x56, 0x55, 0x52, 0x4d, 0x48, 0x42, 0x3f, 0x3e, 0x41, 0x49, 0x56, 0x67, 0x7c, 0x93, 0xab, 0xc3, 0xd9, 0xea, 0xf6, 0xfc, 0xfb, 0xf4, 0xe7, 0xd5, 0xc0, 0xaa, 0x94, 0x80, 0x71, 0x64, 0x5d, 0x5a, 0x5c, 0x61, 0x68, 0x70, 0x77, 0x7d, 0x7f, 0x7f, 0x7b, 0x74, 0x6b, 0x61, 0x57, 0x4e, 0x48, 0x46, 0x48, 0x4e, 0x59, 0x66, 0x75, 0x84, 0x93, 0x9f, 0xa7, 0xab, 0xaa, 0xa4, 0x99, 0x8b, 0x7b, 0x6a, 0x5b, 0x4e, 0x46, 0x43, 0x45, 0x4d, 0x5a, 0x6b, 0x7f, 0x92, 0xa6, 0xb8, 0xc5, 0xcf, 0xd3, 0xd2, 0xcd, 0xc4, 0xb9, 0xad, 0xa1, 0x96, 0x8e, 0x89, 0x87, 0x87, 0x8a, 0x8d, 0x91, 0x92, 0x91, 0x8c, 0x84, 0x78, 0x68, 0x55, 0x41, 0x2e, 0x1c, 0x0e, 0x05, 0x01, 0x05, 0x0f, 0x1f, 0x34, 0x4d, 0x68, 0x81, 0x9a, 0xb0, 0xc1, 0xcd, 0xd3, 0xd3, 0xd0, 0xc8, 0xbf, 0xb5, 0xab, 0xa4, 0x9f, 0x9c, 0x9d, 0xa0, 0xa5, 0xaa, 0xae, 0xb1, 0xb0, 0xab, 0xa3, 0x96, 0x87, 0x76, 0x63, 0x51, 0x42, 0x36, 0x2f, 0x2d, 0x31, 0x3a, 0x48, 0x59, 0x6b, 0x7e, 0x8e, 0x9c, 0xa6, 0xaa, 0xa9, 0xa3, 0x98, 0x8a, 0x7b, 0x6c, 0x5d, 0x52, 0x4a, 0x48, 0x4a, 0x50, 0x5a, 0x67, 0x75, 0x82 }; // waveform shape table for HF peaks, formants 6,7,8 #define N_WAVEMULT 128 static int wavemult_offset=0; static int wavemult_max=0; // the presets are for 22050 Hz sample rate. // A different rate will need to recalculate the presets in WavegenInit() static unsigned char wavemult[N_WAVEMULT] = { 0, 0, 0, 2, 3, 5, 8, 11, 14, 18, 22, 27, 32, 37, 43, 49, 55, 62, 69, 76, 83, 90, 98,105,113,121,128,136,144,152,159,166, 174,181,188,194,201,207,213,218,224,228,233,237,240,244,246,249, 251,252,253,253,253,253,252,251,249,246,244,240,237,233,228,224, 218,213,207,201,194,188,181,174,166,159,152,144,136,128,121,113, 105, 98, 90, 83, 76, 69, 62, 55, 49, 43, 37, 32, 27, 22, 18, 14, 11, 8, 5, 3, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; // set from y = pow(2,x) * 128, x=-1 to 1 unsigned char pitch_adjust_tab[MAX_PITCH_VALUE+1] = { 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 86, 87, 88, 89, 91, 92, 93, 94, 96, 97, 98, 100,101,103,104,105,107,108,110, 111,113,115,116,118,119,121,123, 124,126,128,130,132,133,135,137, 139,141,143,145,147,149,151,153, 155,158,160,162,164,167,169,171, 174,176,179,181,184,186,189,191, 194,197,199,202,205,208,211,214, 217,220,223,226,229,232,236,239, 242,246,249,252, 254,255 }; #ifdef LOG_FRAMES static void LogMarker(int type, int value, int value2) {//=================================================== char buf[20]; int *p; if(option_log_frames == 0) return; if((type == espeakEVENT_PHONEME) || (type == espeakEVENT_SENTENCE)) { f_log=fopen("log-espeakedit","a"); if(f_log) { if(type == espeakEVENT_PHONEME) { p = (int *)buf; p[0] = value; p[1] = value2; buf[8] = 0; fprintf(f_log,"Phoneme [%s]\n", buf); } else fprintf(f_log,"\n"); fclose(f_log); f_log = NULL; } } } #endif void WcmdqStop() {//============= wcmdq_head = 0; wcmdq_tail = 0; if(sonicSpeedupStream != NULL) { sonicDestroyStream(sonicSpeedupStream); sonicSpeedupStream = NULL; } #ifdef USE_PORTAUDIO Pa_AbortStream(pa_stream); #endif if(mbrola_name[0] != 0) MbrolaReset(); } int WcmdqFree() {//============ int i; i = wcmdq_head - wcmdq_tail; if(i <= 0) i += N_WCMDQ; return(i); } int WcmdqUsed() {//============ return(N_WCMDQ - WcmdqFree()); } void WcmdqInc() {//============ wcmdq_tail++; if(wcmdq_tail >= N_WCMDQ) wcmdq_tail=0; } static void WcmdqIncHead() {//======================= wcmdq_head++; if(wcmdq_head >= N_WCMDQ) wcmdq_head=0; } // data points from which to make the presets for pk_shape1 and pk_shape2 #define PEAKSHAPEW 256 static const float pk_shape_x[2][8] = { {0,-0.6f, 0.0f, 0.6f, 1.4f, 2.5f, 4.5f, 5.5f}, {0,-0.6f, 0.0f, 0.6f, 1.4f, 2.0f, 4.5f, 5.5f }}; static const float pk_shape_y[2][8] = { {0, 67, 81, 67, 31, 14, 0, -6} , {0, 77, 81, 77, 31, 7, 0, -6 }}; unsigned char pk_shape1[PEAKSHAPEW+1] = { 255,254,254,254,254,254,253,253,252,251,251,250,249,248,247,246, 245,244,242,241,239,238,236,234,233,231,229,227,225,223,220,218, 216,213,211,209,207,205,203,201,199,197,195,193,191,189,187,185, 183,180,178,176,173,171,169,166,164,161,159,156,154,151,148,146, 143,140,138,135,132,129,126,123,120,118,115,112,108,105,102, 99, 96, 95, 93, 91, 90, 88, 86, 85, 83, 82, 80, 79, 77, 76, 74, 73, 72, 70, 69, 68, 67, 66, 64, 63, 62, 61, 60, 59, 58, 57, 56, 55, 55, 54, 53, 52, 52, 51, 50, 50, 49, 48, 48, 47, 47, 46, 46, 46, 45, 45, 45, 44, 44, 44, 44, 44, 44, 44, 43, 43, 43, 43, 44, 43, 42, 42, 41, 40, 40, 39, 38, 38, 37, 36, 36, 35, 35, 34, 33, 33, 32, 32, 31, 30, 30, 29, 29, 28, 28, 27, 26, 26, 25, 25, 24, 24, 23, 23, 22, 22, 21, 21, 20, 20, 19, 19, 18, 18, 18, 17, 17, 16, 16, 15, 15, 15, 14, 14, 13, 13, 13, 12, 12, 11, 11, 11, 10, 10, 10, 9, 9, 9, 8, 8, 8, 7, 7, 7, 7, 6, 6, 6, 5, 5, 5, 5, 4, 4, 4, 4, 4, 3, 3, 3, 3, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; static unsigned char pk_shape2[PEAKSHAPEW+1] = { 255,254,254,254,254,254,254,254,254,254,253,253,253,253,252,252, 252,251,251,251,250,250,249,249,248,248,247,247,246,245,245,244, 243,243,242,241,239,237,235,233,231,229,227,225,223,221,218,216, 213,211,208,205,203,200,197,194,191,187,184,181,178,174,171,167, 163,160,156,152,148,144,140,136,132,127,123,119,114,110,105,100, 96, 94, 91, 88, 86, 83, 81, 78, 76, 74, 71, 69, 66, 64, 62, 60, 57, 55, 53, 51, 49, 47, 44, 42, 40, 38, 36, 34, 32, 30, 29, 27, 25, 23, 21, 19, 18, 16, 14, 12, 11, 9, 7, 6, 4, 3, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; static unsigned char *pk_shape; static void WavegenInitPkData(int which) {//===================================== // this is only needed to set up the presets for pk_shape1 and pk_shape2 // These have already been pre-calculated and preset #ifdef deleted int ix; int p; float x; float y[PEAKSHAPEW]; float maxy=0; if(which==0) pk_shape = pk_shape1; else pk_shape = pk_shape2; p = 0; for(ix=0;ix= pk_shape_x[which][p+3]) p++; y[ix] = polint(&pk_shape_x[which][p],&pk_shape_y[which][p],3,x); if(y[ix] > maxy) maxy = y[ix]; } for(ix=0;ix= 0) ? p : 0; } pk_shape[PEAKSHAPEW]=0; #endif } // end of WavegenInitPkData #ifdef USE_PORTAUDIO // PortAudio interface static int userdata[4]; static PaError pa_init_err=0; static int out_channels=1; unsigned char *outbuffer = NULL; int outbuffer_size = 0; #if USE_PORTAUDIO == 18 static int WaveCallback(void *inputBuffer, void *outputBuffer, unsigned long framesPerBuffer, PaTimestamp outTime, void *userData ) #else static int WaveCallback(const void *inputBuffer, void *outputBuffer, long unsigned int framesPerBuffer, const PaStreamCallbackTimeInfo *outTime, PaStreamCallbackFlags flags, void *userData ) #endif { int ix; int result; unsigned char *p; unsigned char *out_buf; unsigned char *out_end2; int pa_size; pa_size = framesPerBuffer*2; // make a buffer 3x size of the portaudio output ix = pa_size*3; if(ix > outbuffer_size) { outbuffer = (unsigned char *)realloc(outbuffer, ix); if(outbuffer == NULL) { fprintf(stderr, "espeak: out of memory\n"); } outbuffer_size = ix; out_ptr = NULL; } if(out_ptr == NULL) { out_ptr = out_start = outbuffer; out_end = out_start + outbuffer_size; } out_end2 = &outbuffer[pa_size]; // top of data needed for the portaudio buffer #ifdef LIBRARY event_list_ix = 0; #endif result = WavegenFill(1); // copy from the outbut buffer into the portaudio buffer if(result && (out_ptr > out_end2)) { result = 0; // don't end yet, there is more data in the buffer than can fit in portaudio } while(out_ptr < out_end2) *out_ptr++ = 0; // fill with zeros up to the size of the portaudio buffer memcpy(outputBuffer, outbuffer, pa_size); // move the remaining contents of the start of the output buffer for(p = out_end2; p < out_end; p++) { p[-pa_size] = p[0]; } out_ptr -= pa_size; #ifdef LIBRARY count_samples += framesPerBuffer; if(synth_callback) { // synchronous-playback mode, allow the calling process to abort the speech event_list[event_list_ix].type = espeakEVENT_LIST_TERMINATED; // indicates end of event list event_list[event_list_ix].user_data = 0; if(synth_callback(NULL,0,event_list) == 1) { SpeakNextClause(NULL,NULL,2); // stop speaking result = 1; } } #endif #ifdef ARCH_BIG { // swap the order of bytes in each sound sample in the portaudio buffer int c; unsigned char *buf_end; out_buf = (unsigned char *)outputBuffer; buf_end = out_buf + framesPerBuffer*2; while(out_buf < buf_end) { c = out_buf[0]; out_buf[0] = out_buf[1]; out_buf[1] = c; out_buf += 2; } } #endif if(out_channels == 2) { // sound output can only do stereo, not mono. Duplicate each sound sample to // produce 2 channels. out_buf = (unsigned char *)outputBuffer; for(ix=framesPerBuffer-1; ix>=0; ix--) { p = &out_buf[ix*4]; p[3] = p[1] = out_buf[ix*2 + 1]; p[2] = p[0] = out_buf[ix*2]; } } #if USE_PORTAUDIO == 18 #ifdef PLATFORM_WINDOWS return(result); #endif if(result != 0) { static int end_timer = 0; if(end_timer == 0) end_timer = 4; if(end_timer > 0) { end_timer--; if(end_timer == 0) return(1); } } return(0); #else return(result); #endif } // end of WaveCallBack #if USE_PORTAUDIO == 19 /* This is a fixed version of Pa_OpenDefaultStream() for use if the version in portaudio V19 is broken */ static PaError Pa_OpenDefaultStream2( PaStream** stream, int inputChannelCount, int outputChannelCount, PaSampleFormat sampleFormat, double sampleRate, unsigned long framesPerBuffer, PaStreamCallback *streamCallback, void *userData ) { PaError result; PaStreamParameters hostApiOutputParameters; if(option_device_number >= 0) hostApiOutputParameters.device = option_device_number; else hostApiOutputParameters.device = Pa_GetDefaultOutputDevice(); if( hostApiOutputParameters.device == paNoDevice ) return paDeviceUnavailable; hostApiOutputParameters.channelCount = outputChannelCount; hostApiOutputParameters.sampleFormat = sampleFormat; /* defaultHighOutputLatency is used below instead of defaultLowOutputLatency because it is more important for the default stream to work reliably than it is for it to work with the lowest latency. */ hostApiOutputParameters.suggestedLatency = Pa_GetDeviceInfo( hostApiOutputParameters.device )->defaultHighOutputLatency; hostApiOutputParameters.hostApiSpecificStreamInfo = NULL; result = Pa_OpenStream( stream, NULL, &hostApiOutputParameters, sampleRate, framesPerBuffer, paNoFlag, streamCallback, userData ); return(result); } #endif int WavegenOpenSound() {//=================== PaError err, err2; PaError active; if(option_waveout || option_quiet) { // writing to WAV file, not to portaudio return(0); } #if USE_PORTAUDIO == 18 active = Pa_StreamActive(pa_stream); #else active = Pa_IsStreamActive(pa_stream); #endif if(active == 1) return(0); if(active < 0) { out_channels = 1; #if USE_PORTAUDIO == 18 err2 = Pa_OpenDefaultStream(&pa_stream,0,1,paInt16,samplerate,512,N_WAV_BUF,WaveCallback,(void *)userdata); if(err2 == paInvalidChannelCount) { // failed to open with mono, try stereo out_channels=2; err2 = Pa_OpenDefaultStream(&pa_stream,0,2,paInt16,samplerate,512,N_WAV_BUF,WaveCallback,(void *)userdata); } #else err2 = Pa_OpenDefaultStream2(&pa_stream,0,1,paInt16,(double)samplerate,512,WaveCallback,(void *)userdata); if(err2 == paInvalidChannelCount) { // failed to open with mono, try stereo out_channels=2; err2 = Pa_OpenDefaultStream(&pa_stream,0,2,paInt16,(double)samplerate,512,WaveCallback,(void *)userdata); } #endif } err = Pa_StartStream(pa_stream); #if USE_PORTAUDIO == 19 if(err == paStreamIsNotStopped) { // not sure why we need this, but PA v19 seems to need it err = Pa_StopStream(pa_stream); err = Pa_StartStream(pa_stream); } #endif if(err != paNoError) { // exit speak if we can't open the sound device - this is OK if speak is being run for each utterance exit(2); } return(0); } int WavegenCloseSound() {//==================== PaError active; // check whether speaking has finished, and close the stream if(pa_stream != NULL) { #if USE_PORTAUDIO == 18 active = Pa_StreamActive(pa_stream); #else active = Pa_IsStreamActive(pa_stream); #endif if(WcmdqUsed() == 0) // also check that the queue is empty { if(active == 0) { Pa_CloseStream(pa_stream); pa_stream = NULL; return(1); } } else { WavegenOpenSound(); // still items in the queue, shouldn't be closed } } return(0); } int WavegenInitSound() {//=================== PaError err; if(option_quiet) return(0); // PortAudio sound output library err = Pa_Initialize(); pa_init_err = err; if(err != paNoError) { fprintf(stderr,"Failed to initialise the PortAudio sound\n"); return(1); } return(0); } #else int WavegenOpenSound() {//=================== return(0); } int WavegenCloseSound() {//==================== return(0); } int WavegenInitSound() {//=================== return(0); } #endif void WavegenInit(int rate, int wavemult_fact) {//========================================== int ix; double x; if(wavemult_fact == 0) wavemult_fact=60; // default wvoice = NULL; samplerate = samplerate_native = rate; PHASE_INC_FACTOR = 0x8000000 / samplerate; // assumes pitch is Hz*32 Flutter_inc = (64 * samplerate)/rate; samplecount = 0; nsamples = 0; wavephase = 0x7fffffff; max_hval = 0; wdata.amplitude = 32; wdata.amplitude_fmt = 100; for(ix=0; ix N_WAVEMULT) wavemult_max = N_WAVEMULT; wavemult_offset = wavemult_max/2; if(samplerate != 22050) { // wavemult table has preset values for 22050 Hz, we only need to // recalculate them if we have a different sample rate for(ix=0; ixvoicing; delay = wvoice->echo_delay; amp = wvoice->echo_amp; if(delay >= N_ECHO_BUF) delay = N_ECHO_BUF-1; if(amp > 100) amp = 100; memset(echo_buf,0,sizeof(echo_buf)); echo_tail = 0; if(embedded_value[EMBED_H] > 0) { // set echo from an embedded command in the text amp = embedded_value[EMBED_H]; delay = 130; } #ifdef deleted if(embedded_value[EMBED_T] > 0) { // announcing punctuation, add a small echo // This seems unpopular amp = embedded_value[EMBED_T] * 8; delay = 60; } #endif if(delay == 0) amp = 0; echo_head = (delay * samplerate)/1000; echo_length = echo_head; // ensure completion of echo at the end of speech. Use 1 delay period? if(amp == 0) echo_length = 0; if(amp > 20) echo_length = echo_head * 2; // perhaps allow 2 echo periods if the echo is loud. // echo_amp units are 1/256ths of the amplitude of the original sound. echo_amp = amp; // compensate (partially) for increase in amplitude due to echo general_amplitude = GetAmplitude(); general_amplitude = ((general_amplitude * (500-amp))/500); } // end of WavegenSetEcho int PeaksToHarmspect(wavegen_peaks_t *peaks, int pitch, int *htab, int control) {//============================================================================ // Calculate the amplitude of each harmonics from the formants // Only for formants 0 to 5 // control 0=initial call, 1=every 64 cycles // pitch and freqs are Hz<<16 int f; wavegen_peaks_t *p; int fp; // centre freq of peak int fhi; // high freq of peak int h; // harmonic number int pk; int hmax; int hmax_samplerate; // highest harmonic allowed for the samplerate int x; int ix; int h1; #ifdef SPECT_EDITOR if(harm_sqrt_n > 0) return(HarmToHarmspect(pitch,htab)); #endif // initialise as much of *out as we will need if(wvoice == NULL) return(1); hmax = (peaks[wvoice->n_harmonic_peaks].freq + peaks[wvoice->n_harmonic_peaks].right)/pitch; if(hmax >= MAX_HARMONIC) hmax = MAX_HARMONIC-1; // restrict highest harmonic to half the samplerate hmax_samplerate = (((samplerate * 19)/40) << 16)/pitch; // only 95% of Nyquist freq // hmax_samplerate = (samplerate << 16)/(pitch*2); if(hmax > hmax_samplerate) hmax = hmax_samplerate; for(h=0;h<=hmax;h++) htab[h]=0; h=0; for(pk=0; pk<=wvoice->n_harmonic_peaks; pk++) { p = &peaks[pk]; if((p->height == 0) || (fp = p->freq)==0) continue; fhi = p->freq + p->right; h = ((p->freq - p->left) / pitch) + 1; if(h <= 0) h = 1; for(f=pitch*h; f < fp; f+=pitch) { htab[h++] += pk_shape[(fp-f)/(p->left>>8)] * p->height; } for(; f < fhi; f+=pitch) { htab[h++] += pk_shape[(f-fp)/(p->right>>8)] * p->height; } } { int y; int h2; // increase bass y = peaks[1].height * 10; // addition as a multiple of 1/256s h2 = (1000<<16)/pitch; // decrease until 1000Hz if(h2 > 0) { x = y/h2; h = 1; while(y > 0) { htab[h++] += y; y -= x; } } } // find the nearest harmonic for HF peaks where we don't use shape for(; pk> 14; peak_height[pk] = (x * x * 5)/2; // find the nearest harmonic for HF peaks where we don't use shape if(control == 0) { // set this initially, but make changes only at the quiet point peak_harmonic[pk] = peaks[pk].freq / pitch; } // only use harmonics up to half the samplerate if(peak_harmonic[pk] >= hmax_samplerate) peak_height[pk] = 0; } // convert from the square-rooted values f = 0; for(h=0; h<=hmax; h++, f+=pitch) { x = htab[h] >> 15; htab[h] = (x * x) >> 8; if((ix = (f >> 19)) < N_TONE_ADJUST) { htab[h] = (htab[h] * wvoice->tone_adjust[ix]) >> 13; // index tone_adjust with Hz/8 } } // adjust the amplitude of the first harmonic, affects tonal quality h1 = htab[1] * option_harmonic1; htab[1] = h1/8; // calc intermediate increments of LF harmonics if(control & 1) { for(h=1; h> 3; } } return(hmax); // highest harmonic number } // end of PeaksToHarmspect static void AdvanceParameters() {//============================ // Called every 64 samples to increment the formant freq, height, and widths int x; int ix; static int Flutter_ix = 0; // advance the pitch wdata.pitch_ix += wdata.pitch_inc; if((ix = wdata.pitch_ix>>8) > 127) ix = 127; x = wdata.pitch_env[ix] * wdata.pitch_range; wdata.pitch = (x>>8) + wdata.pitch_base; amp_ix += amp_inc; /* add pitch flutter */ if(Flutter_ix >= (N_FLUTTER*64)) Flutter_ix = 0; x = ((int)(Flutter_tab[Flutter_ix >> 6])-0x80) * flutter_amp; Flutter_ix += Flutter_inc; wdata.pitch += x; if(wdata.pitch < 102400) wdata.pitch = 102400; // min pitch, 25 Hz (25 << 12) if(samplecount == samplecount_start) return; for(ix=0; ix <= wvoice->n_harmonic_peaks; ix++) { peaks[ix].freq1 += peaks[ix].freq_inc; peaks[ix].freq = int(peaks[ix].freq1); peaks[ix].height1 += peaks[ix].height_inc; if((peaks[ix].height = int(peaks[ix].height1)) < 0) peaks[ix].height = 0; peaks[ix].left1 += peaks[ix].left_inc; peaks[ix].left = int(peaks[ix].left1); if(ix < 3) { peaks[ix].right1 += peaks[ix].right_inc; peaks[ix].right = int(peaks[ix].right1); } else { peaks[ix].right = peaks[ix].left; } } for(;ix < 8; ix++) { // formants 6,7,8 don't have a width parameter if(ix < 7) { peaks[ix].freq1 += peaks[ix].freq_inc; peaks[ix].freq = int(peaks[ix].freq1); } peaks[ix].height1 += peaks[ix].height_inc; if((peaks[ix].height = int(peaks[ix].height1)) < 0) peaks[ix].height = 0; } #ifdef SPECT_EDITOR if(harm_sqrt_n != 0) { // We are generating from a harmonic spectrum at a given pitch, not from formant peaks for(ix=0; ixa * input + r->b * r->x1 + r->c * r->x2; r->x2 = r->x1; r->x1 = x; return x; } static void setresonator(RESONATOR *rp, int freq, int bwidth, int init) {//==================================================================== // freq Frequency of resonator in Hz // bwidth Bandwidth of resonator in Hz // init Initialize internal data double x; double arg; if(init) { rp->x1 = 0; rp->x2 = 0; } // x = exp(-pi * bwidth * t) arg = minus_pi_t * bwidth; x = exp(arg); // c = -(x*x) rp->c = -(x * x); // b = x * 2*cos(2 pi * freq * t) arg = two_pi_t * freq; rp->b = x * cos(arg) * 2.0; // a = 1.0 - b - c rp->a = 1.0 - rp->b - rp->c; } // end if setresonator #endif void InitBreath(void) {//================== #ifndef PLATFORM_RISCOS int ix; minus_pi_t = -PI / samplerate; two_pi_t = -2.0 * minus_pi_t; for(ix=0; ixbreath[0] == 0) return; for(pk=1; pkbreath[pk] != 0) { // breath[0] indicates that some breath formants are needed // set the freq from the current ynthesis formant and the width from the voice data setresonator(&rbreath[pk], peaks[pk].freq >> 16, wvoice->breathw[pk],0); } } #endif } // end of SetBreath static int ApplyBreath(void) {//========================= int value = 0; #ifndef PLATFORM_RISCOS int noise; int ix; int amp; // use two random numbers, for alternate formants noise = (rand() & 0x3fff) - 0x2000; for(ix=1; ix < N_PEAKS; ix++) { if((amp = wvoice->breath[ix]) != 0) { amp *= (peaks[ix].height >> 14); value += int(resonator(&rbreath[ix],noise) * amp); } } #endif return (value); } int Wavegen() {//========== unsigned short waveph; unsigned short theta; int total; int h; int ix; int z, z1, z2; int echo; int ov; static int maxh, maxh2; int pk; signed char c; int sample; int amp; int modn_amp, modn_period; static int agc = 256; static int h_switch_sign = 0; static int cycle_count = 0; static int amplitude2 = 0; // adjusted for pitch // continue until the output buffer is full, or // the required number of samples have been produced for(;;) { if((end_wave==0) && (samplecount==nsamples)) return(0); if((samplecount & 0x3f) == 0) { // every 64 samples, adjust the parameters if(samplecount == 0) { hswitch = 0; harmspect = hspect[0]; maxh2 = PeaksToHarmspect(peaks, wdata.pitch<<4, hspect[0], 0); // adjust amplitude to compensate for fewer harmonics at higher pitch // amplitude2 = (wdata.amplitude * wdata.pitch)/(100 << 11); amplitude2 = (wdata.amplitude * (wdata.pitch >> 8) * wdata.amplitude_fmt)/(10000 << 3); // switch sign of harmonics above about 900Hz, to reduce max peak amplitude h_switch_sign = 890 / (wdata.pitch >> 12); } else AdvanceParameters(); // pitch is Hz<<12 phaseinc = (wdata.pitch>>7) * PHASE_INC_FACTOR; cycle_samples = samplerate/(wdata.pitch >> 12); // sr/(pitch*2) hf_factor = wdata.pitch >> 11; maxh = maxh2; harmspect = hspect[hswitch]; hswitch ^= 1; maxh2 = PeaksToHarmspect(peaks, wdata.pitch<<4, hspect[hswitch], 1); SetBreath(); } else if((samplecount & 0x07) == 0) { for(h=1; h 0) { wavephase += phaseinc; if(wavephase < 0) { // sign has changed, reached a quiet point in the waveform cbytes = wavemult_offset - (cycle_samples)/2; if(samplecount > nsamples) return(0); cycle_count++; for(pk=wvoice->n_harmonic_peaks+1; pk> 8) * wdata.amplitude_fmt)/(10000 << 3); if(glottal_flag > 0) { if(glottal_flag == 3) { if((nsamples-samplecount) < (cycle_samples*2)) { // Vowel before glottal-stop. // This is the start of the penultimate cycle, reduce its amplitude glottal_flag = 2; amplitude2 = (amplitude2 * glottal_reduce)/256; } } else if(glottal_flag == 4) { // Vowel following a glottal-stop. // This is the start of the second cycle, reduce its amplitude glottal_flag = 2; amplitude2 = (amplitude2 * glottal_reduce)/256; } else { glottal_flag--; } } if(amplitude_env != NULL) { // amplitude envelope is only used for creaky voice effect on certain vowels/tones if((ix = amp_ix>>8) > 127) ix = 127; amp = amplitude_env[ix]; amplitude2 = (amplitude2 * amp)/128; // if(amp < 255) // modulation_type = 7; } // introduce roughness into the sound by reducing the amplitude of modn_period = 0; if(voice->roughness < N_ROUGHNESS) { modn_period = modulation_tab[voice->roughness][modulation_type]; modn_amp = modn_period & 0xf; modn_period = modn_period >> 4; } if(modn_period != 0) { if(modn_period==0xf) { // just once */ amplitude2 = (amplitude2 * modn_amp)/16; modulation_type = 0; } else { // reduce amplitude every [modn_period} cycles if((cycle_count % modn_period)==0) amplitude2 = (amplitude2 * modn_amp)/16; } } } } else { wavephase += phaseinc; } waveph = (unsigned short)(wavephase >> 16); total = 0; // apply HF peaks, formants 6,7,8 // add a single harmonic and then spread this my multiplying by a // window. This is to reduce the processing power needed to add the // higher frequence harmonics. cbytes++; if(cbytes >=0 && cbytesn_harmonic_peaks+1; pk> 5] * peak_height[pk]; } // spread the peaks by multiplying by a window total = (long)(total / hf_factor) * wavemult[cbytes]; } // apply main peaks, formants 0 to 5 #ifdef USE_ASSEMBLER_1 // use an optimised routine for this loop, if available total += AddSineWaves(waveph, h_switch_sign, maxh, harmspect); // call an assembler code routine #else theta = waveph; for(h=1; h<=h_switch_sign; h++) { total += (int(sin_tab[theta >> 5]) * harmspect[h]); theta += waveph; } while(h<=maxh) { total -= (int(sin_tab[theta >> 5]) * harmspect[h]); theta += waveph; h++; } #endif if(voicing != 64) { total = (total >> 6) * voicing; } #ifndef PLATFORM_RISCOS if(wvoice->breath[0]) { total += ApplyBreath(); } #endif // mix with sampled wave if required z2 = 0; if(wdata.mix_wavefile_ix < wdata.n_mix_wavefile) { if(wdata.mix_wave_scale == 0) { // a 16 bit sample c = wdata.mix_wavefile[wdata.mix_wavefile_ix+wdata.mix_wavefile_offset+1]; sample = wdata.mix_wavefile[wdata.mix_wavefile_ix+wdata.mix_wavefile_offset] + (c * 256); wdata.mix_wavefile_ix += 2; } else { // a 8 bit sample, scaled sample = (signed char)wdata.mix_wavefile[wdata.mix_wavefile_offset+wdata.mix_wavefile_ix++] * wdata.mix_wave_scale; } z2 = (sample * wdata.amplitude_v) >> 10; z2 = (z2 * wdata.mix_wave_amp)/32; if((wdata.mix_wavefile_ix + wdata.mix_wavefile_offset) >= wdata.mix_wavefile_max) // reached the end of available WAV data wdata.mix_wavefile_offset -= (wdata.mix_wavefile_max*3)/4; } z1 = z2 + (((total>>8) * amplitude2) >> 13); echo = (echo_buf[echo_tail++] * echo_amp); z1 += echo >> 8; if(echo_tail >= N_ECHO_BUF) echo_tail=0; z = (z1 * agc) >> 8; // check for overflow, 16bit signed samples if(z >= 32768) { ov = 8388608/z1 - 1; // 8388608 is 2^23, i.e. max value * 256 if(ov < agc) agc = ov; // set agc to number of 1/256ths to multiply the sample by z = (z1 * agc) >> 8; // reduce sample by agc value to prevent overflow } else if(z <= -32768) { ov = -8388608/z1 - 1; if(ov < agc) agc = ov; z = (z1 * agc) >> 8; } *out_ptr++ = z; *out_ptr++ = z >> 8; echo_buf[echo_head++] = z; if(echo_head >= N_ECHO_BUF) echo_head = 0; if(out_ptr >= out_end) return(1); } return(0); } // end of Wavegen static int PlaySilence(int length, int resume) {//=========================================== static int n_samples; int value=0; nsamples = 0; samplecount = 0; wavephase = 0x7fffffff; if(length == 0) return(0); if(resume==0) n_samples = length; while(n_samples-- > 0) { value = (echo_buf[echo_tail++] * echo_amp) >> 8; if(echo_tail >= N_ECHO_BUF) echo_tail = 0; *out_ptr++ = value; *out_ptr++ = value >> 8; echo_buf[echo_head++] = value; if(echo_head >= N_ECHO_BUF) echo_head = 0; if(out_ptr >= out_end) return(1); } return(0); } // end of PlaySilence static int PlayWave(int length, int resume, unsigned char *data, int scale, int amp) {//================================================================================= static int n_samples; static int ix=0; int value; signed char c; if(resume==0) { n_samples = length; ix = 0; } nsamples = 0; samplecount = 0; while(n_samples-- > 0) { if(scale == 0) { // 16 bits data c = data[ix+1]; value = data[ix] + (c * 256); ix+=2; } else { // 8 bit data, shift by the specified scale factor value = (signed char)data[ix++] * scale; } value *= (consonant_amp * general_amplitude); // reduce strength of consonant value = value >> 10; value = (value * amp)/32; value += ((echo_buf[echo_tail++] * echo_amp) >> 8); if(value > 32767) value = 32768; else if(value < -32768) value = -32768; if(echo_tail >= N_ECHO_BUF) echo_tail = 0; out_ptr[0] = value; out_ptr[1] = value >> 8; out_ptr+=2; echo_buf[echo_head++] = (value*3)/4; if(echo_head >= N_ECHO_BUF) echo_head = 0; if(out_ptr >= out_end) return(1); } return(0); } static int SetWithRange0(int value, int max) {//========================================= if(value < 0) return(0); if(value > max) return(max); return(value); } static void SetPitchFormants() {//=========================== int ix; int factor; int pitch_value; // adjust formants to give better results for a different voice pitch if((pitch_value = embedded_value[EMBED_P]) > MAX_PITCH_VALUE) pitch_value = MAX_PITCH_VALUE; if(pitch_value > 50) { // only adjust if the pitch is higher than normal factor = 256 + (25 * (pitch_value - 50))/50; for(ix=0; ix<=5; ix++) { wvoice->freq[ix] = (wvoice->freq2[ix] * factor)/256; } } factor = embedded_value[EMBED_T]*3; wvoice->height[0] = (wvoice->height2[0] * (256 - factor*2))/256; wvoice->height[1] = (wvoice->height2[1] * (256 - factor))/256; } void SetEmbedded(int control, int value) {//===================================== // there was an embedded command in the text at this point int sign=0; int command; command = control & 0x1f; if((control & 0x60) == 0x60) sign = -1; else if((control & 0x60) == 0x40) sign = 1; if(command < N_EMBEDDED_VALUES) { if(sign == 0) embedded_value[command] = value; else embedded_value[command] += (value * sign); embedded_value[command] = SetWithRange0(embedded_value[command],embedded_max[command]); } switch(command) { case EMBED_T: WavegenSetEcho(); // and drop through to case P case EMBED_P: SetPitchFormants(); break; case EMBED_A: // amplitude general_amplitude = GetAmplitude(); break; case EMBED_F: // emphasis general_amplitude = GetAmplitude(); break; case EMBED_H: WavegenSetEcho(); break; } } void WavegenSetVoice(voice_t *v) {//============================= static voice_t v2; memcpy(&v2,v,sizeof(v2)); wvoice = &v2; if(v->peak_shape==0) pk_shape = pk_shape1; else pk_shape = pk_shape2; consonant_amp = (v->consonant_amp * 26) /100; if(samplerate <= 11000) { consonant_amp = consonant_amp*2; // emphasize consonants at low sample rates option_harmonic1 = 6; } WavegenSetEcho(); SetPitchFormants(); MarkerEvent(espeakEVENT_SAMPLERATE, 0, wvoice->samplerate, 0, out_ptr); // WVoiceChanged(wvoice); } static void SetAmplitude(int length, unsigned char *amp_env, int value) {//==================================================================== amp_ix = 0; if(length==0) amp_inc = 0; else amp_inc = (256 * ENV_LEN * STEPSIZE)/length; wdata.amplitude = (value * general_amplitude)/16; wdata.amplitude_v = (wdata.amplitude * wvoice->consonant_ampv * 15)/100; // for wave mixed with voiced sounds amplitude_env = amp_env; } void SetPitch2(voice_t *voice, int pitch1, int pitch2, int *pitch_base, int *pitch_range) {//====================================================================================== int x; int base; int range; int pitch_value; if(pitch1 > pitch2) { x = pitch1; // swap values pitch1 = pitch2; pitch2 = x; } if((pitch_value = embedded_value[EMBED_P]) > MAX_PITCH_VALUE) pitch_value = MAX_PITCH_VALUE; pitch_value -= embedded_value[EMBED_T]; // adjust tone for announcing punctuation if(pitch_value < 0) pitch_value = 0; base = (voice->pitch_base * pitch_adjust_tab[pitch_value])/128; range = (voice->pitch_range * embedded_value[EMBED_R])/50; // compensate for change in pitch when the range is narrowed or widened base -= (range - voice->pitch_range)*18; *pitch_base = base + (pitch1 * range)/2; *pitch_range = base + (pitch2 * range)/2 - *pitch_base; } void SetPitch(int length, unsigned char *env, int pitch1, int pitch2) {//================================================================== // length in samples #ifdef LOG_FRAMES if(option_log_frames) { f_log=fopen("log-espeakedit","a"); if(f_log != NULL) { fprintf(f_log," pitch %3d %3d %3dmS\n",pitch1,pitch2,(length*1000)/samplerate); fclose(f_log); f_log=NULL; } } #endif if((wdata.pitch_env = env)==NULL) wdata.pitch_env = env_fall; // default wdata.pitch_ix = 0; if(length==0) wdata.pitch_inc = 0; else wdata.pitch_inc = (256 * ENV_LEN * STEPSIZE)/length; SetPitch2(wvoice, pitch1, pitch2, &wdata.pitch_base, &wdata.pitch_range); // set initial pitch wdata.pitch = ((wdata.pitch_env[0] * wdata.pitch_range) >>8) + wdata.pitch_base; // Hz << 12 flutter_amp = wvoice->flutter; } // end of SetPitch void SetSynth(int length, int modn, frame_t *fr1, frame_t *fr2, voice_t *v) {//======================================================================== int ix; DOUBLEX next; int length2; int length4; int qix; int cmd; static int glottal_reduce_tab1[4] = {0x30, 0x30, 0x40, 0x50}; // vowel before [?], amp * 1/256 // static int glottal_reduce_tab1[4] = {0x30, 0x40, 0x50, 0x60}; // vowel before [?], amp * 1/256 static int glottal_reduce_tab2[4] = {0x90, 0xa0, 0xb0, 0xc0}; // vowel after [?], amp * 1/256 #ifdef LOG_FRAMES if(option_log_frames) { f_log=fopen("log-espeakedit","a"); if(f_log != NULL) { fprintf(f_log,"%3dmS %3d %3d %4d %4d (%3d %3d %3d %3d) to %3d %3d %4d %4d (%3d %3d %3d %3d)\n",length*1000/samplerate, fr1->ffreq[0],fr1->ffreq[1],fr1->ffreq[2],fr1->ffreq[3], fr1->fheight[0],fr1->fheight[1],fr1->fheight[2],fr1->fheight[3], fr2->ffreq[0],fr2->ffreq[1],fr2->ffreq[2],fr2->ffreq[3], fr2->fheight[0],fr2->fheight[1],fr2->fheight[2],fr2->fheight[3] ); fclose(f_log); f_log=NULL; } } #endif harm_sqrt_n = 0; end_wave = 1; // any additional information in the param1 ? modulation_type = modn & 0xff; glottal_flag = 0; if(modn & 0x400) { glottal_flag = 3; // before a glottal stop glottal_reduce = glottal_reduce_tab1[(modn >> 8) & 3]; } if(modn & 0x800) { glottal_flag = 4; // after a glottal stop glottal_reduce = glottal_reduce_tab2[(modn >> 8) & 3]; } for(qix=wcmdq_head+1;;qix++) { if(qix >= N_WCMDQ) qix = 0; if(qix == wcmdq_tail) break; cmd = wcmdq[qix][0]; if(cmd==WCMD_SPECT) { end_wave = 0; // next wave generation is from another spectrum break; } if((cmd==WCMD_WAVE) || (cmd==WCMD_PAUSE)) break; // next is not from spectrum, so continue until end of wave cycle } // round the length to a multiple of the stepsize length2 = (length + STEPSIZE/2) & ~0x3f; if(length2 == 0) length2 = STEPSIZE; // add this length to any left over from the previous synth samplecount_start = samplecount; nsamples += length2; length4 = length2/4; peaks[7].freq = (7800 * v->freq[7] + v->freqadd[7]*256) << 8; peaks[8].freq = (9000 * v->freq[8] + v->freqadd[8]*256) << 8; for(ix=0; ix < 8; ix++) { if(ix < 7) { peaks[ix].freq1 = (fr1->ffreq[ix] * v->freq[ix] + v->freqadd[ix]*256) << 8; peaks[ix].freq = int(peaks[ix].freq1); next = (fr2->ffreq[ix] * v->freq[ix] + v->freqadd[ix]*256) << 8; peaks[ix].freq_inc = ((next - peaks[ix].freq1) * (STEPSIZE/4)) / length4; // lower headroom for fixed point math } peaks[ix].height1 = (fr1->fheight[ix] * v->height[ix]) << 6; peaks[ix].height = int(peaks[ix].height1); next = (fr2->fheight[ix] * v->height[ix]) << 6; peaks[ix].height_inc = ((next - peaks[ix].height1) * STEPSIZE) / length2; if((ix <= 5) && (ix <= wvoice->n_harmonic_peaks)) { peaks[ix].left1 = (fr1->fwidth[ix] * v->width[ix]) << 10; peaks[ix].left = int(peaks[ix].left1); next = (fr2->fwidth[ix] * v->width[ix]) << 10; peaks[ix].left_inc = ((next - peaks[ix].left1) * STEPSIZE) / length2; if(ix < 3) { peaks[ix].right1 = (fr1->fright[ix] * v->width[ix]) << 10; peaks[ix].right = int(peaks[ix].right1); next = (fr2->fright[ix] * v->width[ix]) << 10; peaks[ix].right_inc = ((next - peaks[ix].right1) * STEPSIZE) / length2; } else { peaks[ix].right = peaks[ix].left; } } } } // end of SetSynth static int Wavegen2(int length, int modulation, int resume, frame_t *fr1, frame_t *fr2) {//==================================================================================== if(resume==0) SetSynth(length, modulation, fr1, fr2, wvoice); return(Wavegen()); } void Write4Bytes(FILE *f, int value) {//================================= // Write 4 bytes to a file, least significant first int ix; for(ix=0; ix<4; ix++) { fputc(value & 0xff,f); value = value >> 8; } } int WavegenFill2(int fill_zeros) {//============================ // Pick up next wavegen commands from the queue // return: 0 output buffer has been filled // return: 1 input command queue is now empty long64 *q; int length; int result; int marker_type; static int resume=0; static int echo_complete=0; while(out_ptr < out_end) { if(WcmdqUsed() <= 0) { if(echo_complete > 0) { // continue to play silence until echo is completed resume = PlaySilence(echo_complete,resume); if(resume == 1) return(0); // not yet finished } if(fill_zeros) { while(out_ptr < out_end) *out_ptr++ = 0; } return(1); // queue empty, close sound channel } result = 0; q = wcmdq[wcmdq_head]; length = q[1]; switch(q[0] & 0xff) { case WCMD_PITCH: SetPitch(length,(unsigned char *)q[2],q[3] >> 16,q[3] & 0xffff); break; case WCMD_PAUSE: if(resume==0) { echo_complete -= length; } wdata.n_mix_wavefile = 0; wdata.amplitude_fmt = 100; KlattReset(1); result = PlaySilence(length,resume); break; case WCMD_WAVE: echo_complete = echo_length; wdata.n_mix_wavefile = 0; KlattReset(1); result = PlayWave(length,resume,(unsigned char*)q[2], q[3] & 0xff, q[3] >> 8); break; case WCMD_WAVE2: // wave file to be played at the same time as synthesis wdata.mix_wave_amp = q[3] >> 8; wdata.mix_wave_scale = q[3] & 0xff; wdata.n_mix_wavefile = (length & 0xffff); wdata.mix_wavefile_max = (length >> 16) & 0xffff; if(wdata.mix_wave_scale == 0) { wdata.n_mix_wavefile *= 2; wdata.mix_wavefile_max *= 2; } wdata.mix_wavefile_ix = 0; wdata.mix_wavefile_offset = 0; wdata.mix_wavefile = (unsigned char *)q[2]; break; case WCMD_SPECT2: // as WCMD_SPECT but stop any concurrent wave file wdata.n_mix_wavefile = 0; // ... and drop through to WCMD_SPECT case case WCMD_SPECT: echo_complete = echo_length; result = Wavegen2(length & 0xffff,q[1] >> 16,resume,(frame_t *)q[2],(frame_t *)q[3]); break; #ifdef INCLUDE_KLATT case WCMD_KLATT2: // as WCMD_SPECT but stop any concurrent wave file wdata.n_mix_wavefile = 0; // ... and drop through to WCMD_SPECT case case WCMD_KLATT: echo_complete = echo_length; result = Wavegen_Klatt2(length & 0xffff,q[1] >> 16,resume,(frame_t *)q[2],(frame_t *)q[3]); break; #endif case WCMD_MARKER: marker_type = q[0] >> 8; MarkerEvent(marker_type, q[1],q[2],q[3],out_ptr); #ifdef LOG_FRAMES LogMarker(marker_type, q[2], q[3]); #endif if(marker_type == 1) // word marker { current_source_index = q[1] & 0xffffff; } break; case WCMD_AMPLITUDE: SetAmplitude(length,(unsigned char *)q[2],q[3]); break; case WCMD_VOICE: WavegenSetVoice((voice_t *)q[2]); free((voice_t *)q[2]); break; case WCMD_EMBEDDED: SetEmbedded(q[1],q[2]); break; case WCMD_MBROLA_DATA: result = MbrolaFill(length, resume, (general_amplitude * wvoice->voicing)/64); break; case WCMD_FMT_AMPLITUDE: if((wdata.amplitude_fmt = q[1]) == 0) wdata.amplitude_fmt = 100; // percentage, but value=0 means 100% break; case WCMD_SONIC_SPEED: sonicSpeed = (double)q[1] / 1024; break; } if(result==0) { WcmdqIncHead(); resume=0; } else { resume=1; } } return(0); } // end of WavegenFill2 /* Speed up the audio samples with libsonic. */ static int SpeedUp(short *outbuf, int length_in, int length_out, int end_of_text) {//============================================================================== if(length_in >0) { if(sonicSpeedupStream == NULL) { sonicSpeedupStream = sonicCreateStream(22050, 1); } if(sonicGetSpeed(sonicSpeedupStream) != sonicSpeed) { sonicSetSpeed(sonicSpeedupStream, sonicSpeed); } sonicWriteShortToStream(sonicSpeedupStream, outbuf, length_in); } if(sonicSpeedupStream == NULL) return(0); if(end_of_text) { sonicFlushStream(sonicSpeedupStream); } return sonicReadShortFromStream(sonicSpeedupStream, outbuf, length_out); } // end of SpeedUp /* Call WavegenFill2, and then speed up the output samples. */ int WavegenFill(int fill_zeros) {//============================ int finished; unsigned char *p_start; int length; int max_length; p_start = out_ptr; // fill_zeros is ignored. It is now done in the portaudio callback finished = WavegenFill2(0); if(sonicSpeed > 1.0) { max_length = (out_end - p_start); length = 2*SpeedUp((short *)p_start, (out_ptr-p_start)/2, max_length/2, finished); out_ptr = p_start + length; if(length >= max_length) finished = 0; // there may be more data to flush } return finished; } // end of WavegenFill sources_5316/external/espeak/voices.cpp0000775000176700017670000012453711725414617017042 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2010 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #include "StdAfx.h" #include "stdio.h" #include "ctype.h" #include "wctype.h" #include "string.h" #include "stdlib.h" #include "speech.h" #ifdef PLATFORM_WINDOWS #include "windows.h" #else #ifdef PLATFORM_RISCOS #include "kernel.h" #else #include "dirent.h" #endif #endif #include "speak_lib.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" MNEM_TAB genders [] = { {"unknown", 0}, {"male", 1}, {"female", 2}, {NULL, 0 }}; int tone_points[12] = {600,170, 1200,135, 2000,110, 3000,110, -1,0}; //int tone_points[12] = {250,200, 400,170, 600,170, 1200,135, 2000,110, -1,0}; // limit the rate of change for each formant number //static int formant_rate_22050[9] = {50, 104, 165, 230, 220, 220, 220, 220, 220}; // values for 22kHz sample rate //static int formant_rate_22050[9] = {240, 180, 180, 180, 180, 180, 180, 180, 180}; // values for 22kHz sample rate static int formant_rate_22050[9] = {240, 170, 170, 170, 170, 170, 170, 170, 170}; // values for 22kHz sample rate int formant_rate[9]; // values adjusted for actual sample rate #define DEFAULT_LANGUAGE_PRIORITY 5 #define N_VOICES_LIST 150 static int n_voices_list = 0; static espeak_VOICE *voices_list[N_VOICES_LIST]; static int len_path_voices; espeak_VOICE current_voice_selected; enum { V_NAME = 1, V_LANGUAGE, V_GENDER, V_TRANSLATOR, V_PHONEMES, V_DICTIONARY, // these affect voice quality, are independent of language V_FORMANT, V_PITCH, V_ECHO, V_FLUTTER, V_ROUGHNESS, V_CLARITY, V_TONE, V_VOICING, V_BREATH, V_BREATHW, // these override defaults set by the translator V_WORDGAP, V_INTONATION, V_TUNES, V_STRESSLENGTH, V_STRESSAMP, V_STRESSADD, V_DICTRULES, V_STRESSRULE, V_CHARSET, V_NUMBERS, V_OPTION, V_MBROLA, V_KLATT, V_FAST, V_SPEED, // these need a phoneme table to have been specified V_REPLACE, V_CONSONANTS }; static MNEM_TAB options_tab[] = { {"reduce_t", LOPT_REDUCE_T}, {"bracket", LOPT_BRACKET_PAUSE}, {NULL, -1} }; static MNEM_TAB keyword_tab[] = { {"name", V_NAME}, {"language", V_LANGUAGE}, {"gender", V_GENDER}, {"formant", V_FORMANT}, {"pitch", V_PITCH}, {"phonemes", V_PHONEMES}, {"translator", V_TRANSLATOR}, {"dictionary", V_DICTIONARY}, {"stressLength", V_STRESSLENGTH}, {"stressAmp", V_STRESSAMP}, {"stressAdd", V_STRESSADD}, {"intonation", V_INTONATION}, {"tunes", V_TUNES}, {"dictrules", V_DICTRULES}, {"stressrule", V_STRESSRULE}, {"charset", V_CHARSET}, {"replace", V_REPLACE}, {"words", V_WORDGAP}, {"echo", V_ECHO}, {"flutter", V_FLUTTER}, {"roughness", V_ROUGHNESS}, {"clarity", V_CLARITY}, {"tone", V_TONE}, {"voicing", V_VOICING}, {"breath", V_BREATH}, {"breathw", V_BREATHW}, {"numbers", V_NUMBERS}, {"option", V_OPTION}, {"mbrola", V_MBROLA}, {"consonants", V_CONSONANTS}, {"klatt", V_KLATT}, {"fast_test2", V_FAST}, {"speed", V_SPEED}, // these just set a value in langopts.param[] {"l_dieresis", 0x100+LOPT_DIERESES}, // {"l_lengthen", 0x100+LOPT_IT_LENGTHEN}, {"l_prefix", 0x100+LOPT_PREFIXES}, {"l_regressive_v", 0x100+LOPT_REGRESSIVE_VOICING}, {"l_unpronouncable", 0x100+LOPT_UNPRONOUNCABLE}, {"l_sonorant_min", 0x100+LOPT_SONORANT_MIN}, {"l_length_mods", 0x100+LOPT_LENGTH_MODS}, {NULL, 0} }; #define N_VOICE_VARIANTS 12 const char variants_either[N_VOICE_VARIANTS] = {1,2,12,3,13,4,14,5,11,0}; const char variants_male[N_VOICE_VARIANTS] = {1,2,3,4,5,0}; const char variants_female[N_VOICE_VARIANTS] = {11,12,13,14,0}; const char *variant_lists[3] = {variants_either, variants_male, variants_female}; static voice_t voicedata; voice_t *voice = &voicedata; static char *fgets_strip(char *buf, int size, FILE *f_in) {//====================================================== // strip trailing spaces, and truncate lines at // comment int len; char *p; if(fgets(buf,size,f_in) == NULL) return(NULL); len = strlen(buf); while((--len > 0) && isspace(buf[len])) buf[len] = 0; if((p = strstr(buf,"//")) != NULL) *p = 0; return(buf); } static int LookupTune(const char *name) {//==================================== int ix; for(ix=0; ix 0) tone_pts[pt+1] = tone_pts[pt-1]; } freq2 = tone_pts[pt] / 8; // 8Hz steps height2 = tone_pts[pt+1]; if((freq2 - freq1) > 0) { rate = double(height2-height1)/(freq2-freq1); for(ix=freq1; ix 255) y = 255; voice->tone_adjust[ix] = y; } } freq1 = freq2; height1 = height2; } } void ReadTonePoints(char *string, int *tone_pts) {//============================================= // tone_pts[] is int[12] int ix; for(ix=0; ix<12; ix++) tone_pts[ix] = -1; sscanf(string,"%d %d %d %d %d %d %d %d %d %d", &tone_pts[0],&tone_pts[1],&tone_pts[2],&tone_pts[3], &tone_pts[4],&tone_pts[5],&tone_pts[6],&tone_pts[7], &tone_pts[8],&tone_pts[9]); } static espeak_VOICE *ReadVoiceFile(FILE *f_in, const char *fname, const char*leafname) {//=================================================================================== // Read a Voice file, allocate a VOICE_DATA and set data from the // file's language, gender, name lines char linebuf[120]; char vname[80]; char vgender[80]; char vlanguage[80]; char languages[300]; // allow space for several alternate language names and priorities unsigned int len; int langix = 0; int n_languages = 0; char *p; espeak_VOICE *voice_data; int priority; int age; int n_variants = 3; // default, number of variants of this voice before using another voice int gender; #ifdef PLATFORM_WINDOWS char fname_buf[sizeof(path_home)+15]; if(memcmp(leafname,"mb-",3) == 0) { // check whether the mbrola speech data is present for this voice memcpy(vname,&leafname[3],3); vname[3] = 0; sprintf(fname_buf,"%s/mbrola/%s",path_home,vname); if(GetFileLength(fname_buf) <= 0) return(0); } #endif vname[0] = 0; vgender[0] = 0; age = 0; while(fgets_strip(linebuf,sizeof(linebuf),f_in) != NULL) { if(memcmp(linebuf,"name",4)==0) { p = &linebuf[4]; while(isspace(*p)) p++; strncpy0(vname,p,sizeof(vname)); } else if(memcmp(linebuf,"language",8)==0) { priority = DEFAULT_LANGUAGE_PRIORITY; vlanguage[0] = 0; sscanf(&linebuf[8],"%s %d",vlanguage,&priority); len = strlen(vlanguage) + 2; // check for space in languages[] if(len < (sizeof(languages)-langix-1)) { languages[langix] = priority; strcpy(&languages[langix+1],vlanguage); langix += len; n_languages++; } } else if(memcmp(linebuf,"gender",6)==0) { sscanf(&linebuf[6],"%s %d",vgender,&age); } else if(memcmp(linebuf,"variants",8)==0) { sscanf(&linebuf[8],"%d",&n_variants); } } languages[langix++] = 0; gender = LookupMnem(genders,vgender); if(n_languages == 0) { return(NULL); // no language lines in the voice file } p = (char *)calloc(sizeof(espeak_VOICE) + langix + strlen(fname) + strlen(vname) + 3, 1); voice_data = (espeak_VOICE *)p; p = &p[sizeof(espeak_VOICE)]; memcpy(p,languages,langix); voice_data->languages = p; strcpy(&p[langix],fname); voice_data->identifier = &p[langix]; voice_data->name = &p[langix]; if(vname[0] != 0) { langix += strlen(fname)+1; strcpy(&p[langix],vname); voice_data->name = &p[langix]; } voice_data->age = age; voice_data->gender = gender; voice_data->variant = 0; voice_data->xx1 = n_variants; return(voice_data); } // end of ReadVoiceFile void VoiceReset(int tone_only) {//=========================== // Set voice to the default values int pk; static unsigned char default_heights[N_PEAKS] = {128,128,120,120,110,110,128,128,128}; static unsigned char default_widths[N_PEAKS] = {128,128,128,160,171,171,128,128,128}; static int breath_widths[N_PEAKS] = {0,200,200,400,400,400,600,600,600}; // default is: pitch 80,118 voice->pitch_base = 0x47000; voice->pitch_range = 4104; // default is: pitch 80,117 // voice->pitch_base = 0x47000; // voice->pitch_range = 3996; voice->formant_factor = 256; voice->speed_percent = 100; voice->echo_delay = 0; voice->echo_amp = 0; voice->flutter = 64; voice->n_harmonic_peaks = 5; voice->peak_shape = 0; voice->voicing = 64; voice->consonant_amp = 100; voice->consonant_ampv = 100; voice->samplerate = 22050; memset(voice->klattv,0,sizeof(voice->klattv)); speed.fast_settings[0] = 450; speed.fast_settings[1] = 800; speed.fast_settings[2] = 175; #ifdef PLATFORM_RISCOS voice->roughness = 1; #else voice->roughness = 2; #endif InitBreath(); for(pk=0; pkfreq[pk] = 256; voice->height[pk] = default_heights[pk]*2; voice->width[pk] = default_widths[pk]*2; voice->breath[pk] = 0; voice->breathw[pk] = breath_widths[pk]; // default breath formant woidths voice->freqadd[pk] = 0; // adjust formant smoothing depending on sample rate formant_rate[pk] = (formant_rate_22050[pk] * 22050)/samplerate; } voice->height[2] = 240; // reduce F2 slightly // This table provides the opportunity for tone control. // Adjustment of harmonic amplitudes, steps of 8Hz // value of 128 means no change // memset(voice->tone_adjust,128,sizeof(voice->tone_adjust)); SetToneAdjust(voice,tone_points); // default values of speed factors voice->speedf1 = 256; voice->speedf2 = 238; voice->speedf3 = 232; if(tone_only == 0) { n_replace_phonemes = 0; option_quiet = 0; LoadMbrolaTable(NULL,NULL,0); } } // end of VoiceReset static void VoiceFormant(char *p) {//============================== // Set parameters for a formant int ix; int formant; int freq = 100; int height = 100; int width = 100; int freqadd = 0; ix = sscanf(p,"%d %d %d %d %d",&formant,&freq,&height,&width,&freqadd); if(ix < 2) return; if((formant < 0) || (formant > 8)) return; if(freq >= 0) voice->freq[formant] = int(freq * 2.56001); if(height >= 0) voice->height[formant] = int(height * 2.56001); if(width >= 0) voice->width[formant] = int(width * 2.56001); voice->freqadd[formant] = freqadd; } static void PhonemeReplacement(int type, char *p) {//============================================== int n; int phon; int flags = 0; char phon_string1[12]; char phon_string2[12]; strcpy(phon_string2,"NULL"); n = sscanf(p,"%d %s %s",&flags,phon_string1,phon_string2); if((n < 2) || (n_replace_phonemes >= N_REPLACE_PHONEMES)) return; if((phon = LookupPhonemeString(phon_string1)) == 0) return; // not recognised replace_phonemes[n_replace_phonemes].old_ph = phon; replace_phonemes[n_replace_phonemes].new_ph = LookupPhonemeString(phon_string2); replace_phonemes[n_replace_phonemes++].type = flags; } // end of PhonemeReplacement static int Read8Numbers(char *data_in,int *data) {//============================================= // Read 8 integer numbers memset(data, 0, 8+sizeof(int)); return(sscanf(data_in,"%d %d %d %d %d %d %d %d", &data[0],&data[1],&data[2],&data[3],&data[4],&data[5],&data[6],&data[7])); } voice_t *LoadVoice(const char *vname, int control) {//=============================================== // control, bit 0 1= no_default // bit 1 1 = change tone only, not language // bit 2 1 = don't report error on LoadDictionary // bit 4 1 = vname = full path FILE *f_voice = NULL; char *p; int key; int ix; int n; int value; int value2; int langix = 0; int tone_only = control & 2; int language_set = 0; int phonemes_set = 0; int stress_amps_set = 0; int stress_lengths_set = 0; int stress_add_set = 0; int conditional_rules = 0; LANGUAGE_OPTIONS *langopts = NULL; Translator *new_translator = NULL; char voicename[40]; char language_name[40]; char translator_name[40]; char new_dictionary[40]; char phonemes_name[40]; char option_name[40]; const char *language_type; char buf[200]; char path_voices[sizeof(path_home)+12]; char langname[4]; int stress_amps[8]; int stress_lengths[8]; int stress_add[8]; char names[8][40]; int pitch1; int pitch2; static char voice_identifier[40]; // file name for current_voice_selected static char voice_name[40]; // voice name for current_voice_selected static char voice_languages[100]; // list of languages and priorities for current_voice_selected strcpy(voicename,vname); if(voicename[0]==0) strcpy(voicename,"default"); #ifdef DATA_FROM_SOURCECODE_FILES long numberOfBytes; const char * data; if (tone_only) { data = espeakdata_get_voiceVariant (vname, &numberOfBytes); } else { language_type = "en"; data = espeakdata_get_voice (vname, &numberOfBytes); language_type = vname; } if (data == 0) { language_type = "en"; // default data = espeakdata_get_voice ("en/en", &numberOfBytes); } language_type = "en"; #else if(control & 0x10) { strcpy(buf,vname); if(GetFileLength(buf) <= 0) return(NULL); } else { sprintf(path_voices,"%s%cvoices%c",path_home,PATHSEP,PATHSEP); sprintf(buf,"%s%s",path_voices,voicename); if(GetFileLength(buf) <= 0) { // look for the voice in a sub-directory of the language name langname[0] = voicename[0]; langname[1] = voicename[1]; langname[2] = 0; sprintf(buf,"%s%s%c%s",path_voices,langname,PATHSEP,voicename); if(GetFileLength(buf) <= 0) { // look in "extra" sub-directory sprintf(buf,"%sextra%c%s",path_voices,PATHSEP,voicename); if(GetFileLength(buf) <= 0) { // look in "test" sub-directory sprintf(buf,"%stest%c%s",path_voices,PATHSEP,voicename); } } } } f_voice = fopen(buf,"r"); language_type = "en"; // default if(f_voice == NULL) { if(control & 3) return(NULL); // can't open file if(SelectPhonemeTableName(voicename) >= 0) language_type = voicename; } #endif if(!tone_only && (translator != NULL)) { DeleteTranslator(translator); translator = NULL; } strcpy(translator_name,language_type); strcpy(new_dictionary,language_type); strcpy(phonemes_name,language_type); if(!tone_only) { voice = &voicedata; strncpy0(voice_identifier,vname,sizeof(voice_identifier)); voice_name[0] = 0; voice_languages[0] = 0; current_voice_selected.identifier = voice_identifier; current_voice_selected.name = voice_name; current_voice_selected.languages = voice_languages; } else { // append the variant file name to the voice identifier if((p = strchr(voice_identifier,'+')) != NULL) *p = 0; // remove previous variant name sprintf(buf,"+%s",&vname[0]); // djmw was vname[3] omit !v/ from the variant filename strcat(voice_identifier,buf); langopts = &translator->langopts; } VoiceReset(tone_only); if(!tone_only) SelectPhonemeTableName(phonemes_name); // set up phoneme_tab #ifdef DATA_FROM_SOURCECODE_FILES long index = 0; const char *start = data; while (start = espeakdata_get_voicedata (start, numberOfBytes, buf, sizeof(buf), &index)) { #else while((f_voice != NULL) && (fgets_strip(buf,sizeof(buf),f_voice) != NULL)) { #endif // isolate the attribute name for(p=buf; (*p != 0) && !isspace(*p); p++); *p++ = 0; if(buf[0] == 0) continue; key = LookupMnem(keyword_tab, buf); switch(key) { case V_LANGUAGE: { unsigned int len; int priority; if(tone_only) break; priority = DEFAULT_LANGUAGE_PRIORITY; language_name[0] = 0; sscanf(p,"%s %d",language_name,&priority); if(strcmp(language_name,"variant") == 0) break; len = strlen(language_name) + 2; // check for space in languages[] if(len < (sizeof(voice_languages)-langix-1)) { voice_languages[langix] = priority; strcpy(&voice_languages[langix+1],language_name); langix += len; } // only act on the first language line if(language_set == 0) { language_type = strtok(language_name,"-"); language_set = 1; strcpy(translator_name,language_type); strcpy(new_dictionary,language_type); strcpy(phonemes_name,language_type); SelectPhonemeTableName(phonemes_name); if(new_translator != NULL) DeleteTranslator(new_translator); new_translator = SelectTranslator(translator_name); langopts = &new_translator->langopts; } } break; case V_NAME: if(tone_only == 0) { while(isspace(*p)) p++; strncpy0(voice_name,p,sizeof(voice_name)); } break; case V_GENDER: { int age = 0; char vgender[80]; sscanf(p,"%s %d",vgender,&age); current_voice_selected.gender = LookupMnem(genders,vgender); current_voice_selected.age = age; } break; case V_TRANSLATOR: if(tone_only) break; sscanf(p,"%s",translator_name); if(new_translator != NULL) DeleteTranslator(new_translator); new_translator = SelectTranslator(translator_name); langopts = &new_translator->langopts; break; case V_DICTIONARY: // dictionary sscanf(p,"%s",new_dictionary); break; case V_PHONEMES: // phoneme table sscanf(p,"%s",phonemes_name); break; case V_FORMANT: VoiceFormant(p); break; case V_PITCH: { double factor; // default is pitch 82 118 n = sscanf(p,"%d %d",&pitch1,&pitch2); voice->pitch_base = (pitch1 - 9) << 12; voice->pitch_range = (pitch2 - pitch1) * 108; factor = double(pitch1 - 82)/82; voice->formant_factor = (int)((1+factor/4) * 256); // nominal formant shift for a different voice pitch } break; case V_STRESSLENGTH: // stressLength stress_lengths_set = Read8Numbers(p,stress_lengths); break; case V_STRESSAMP: // stressAmp stress_amps_set = Read8Numbers(p,stress_amps); break; case V_STRESSADD: // stressAdd stress_add_set = Read8Numbers(p,stress_add); break; case V_INTONATION: // intonation sscanf(p,"%d %d",&option_tone_flags,&option_tone2); if((option_tone_flags & 0xff) != 0) langopts->intonation_group = option_tone_flags & 0xff; break; case V_TUNES: n = sscanf(p,"%s %s %s %s %s %s",names[0],names[1],names[2],names[3],names[4],names[5]); langopts->intonation_group = 0; for(ix=0; ixtunes[ix] = value; } break; case V_DICTRULES: // conditional dictionary rules and list entries while(*p != 0) { while(isspace(*p)) p++; n = -1; if(((n = atoi(p)) > 0) && (n < 32)) { p++; conditional_rules |= (1 << n); } while(isalnum(*p)) p++; } break; case V_REPLACE: if(phonemes_set == 0) { // must set up a phoneme table before we can lookup phoneme mnemonics SelectPhonemeTableName(phonemes_name); phonemes_set = 1; } PhonemeReplacement(key,p); break; case V_WORDGAP: // words sscanf(p,"%d %d",&langopts->word_gap, &langopts->vowel_pause); break; case V_STRESSRULE: sscanf(p,"%d %d %d %d",&langopts->stress_rule, &langopts->stress_flags, &langopts->unstressed_wd1, &langopts->unstressed_wd2); break; case V_CHARSET: if((sscanf(p,"%d",&value)==1) && (value < N_CHARSETS)) new_translator->charset_a0 = charsets[value]; break; case V_NUMBERS: sscanf(p,"%d %d",&langopts->numbers,&langopts->numbers2); break; case V_OPTION: value2 = 0; if((sscanf(p,"%s %d %d",option_name,&value,&value2) >= 2) && ((ix = LookupMnem(options_tab, option_name)) >= 0)) { langopts->param[ix] = value; langopts->param2[ix] = value2; } else { fprintf(stderr,"Bad voice option: %s %s\n",buf,p); } break; case V_ECHO: // echo. suggest: 135mS 11% value = 0; voice->echo_amp = 0; sscanf(p,"%d %d",&voice->echo_delay,&voice->echo_amp); break; case V_FLUTTER: // flutter if(sscanf(p,"%d",&value)==1) voice->flutter = value * 32; break; case V_ROUGHNESS: // roughness if(sscanf(p,"%d",&value)==1) voice->roughness = value; break; case V_CLARITY: // formantshape if(sscanf(p,"%d",&value)==1) { if(value > 4) { voice->peak_shape = 1; // squarer formant peaks value = 4; } voice->n_harmonic_peaks = 1+value; } break; case V_TONE: { int tone_data[12]; ReadTonePoints(p,tone_data); SetToneAdjust(voice,tone_data); } break; case V_VOICING: if(sscanf(p,"%d",&value)==1) voice->voicing = (value * 64)/100; break; case V_BREATH: voice->breath[0] = Read8Numbers(p,&voice->breath[1]); for(ix=1; ix<8; ix++) { if(ix % 2) voice->breath[ix] = -voice->breath[ix]; } break; case V_BREATHW: voice->breathw[0] = Read8Numbers(p,&voice->breathw[1]); break; case V_CONSONANTS: value = sscanf(p,"%d %d",&voice->consonant_amp, &voice->consonant_ampv); break; case V_SPEED: sscanf(p,"%d",&voice->speed_percent); break; case V_MBROLA: { int srate = 16000; char name[40]; char phtrans[40]; phtrans[0] = 0; sscanf(p,"%s %s %d",name,phtrans,&srate); if(LoadMbrolaTable(name,phtrans,srate) != EE_OK) { fprintf(stderr,"mbrola voice not found\n"); } voice->samplerate = srate; } break; case V_KLATT: voice->klattv[0] = 1; // default source: IMPULSIVE Read8Numbers(p,voice->klattv); voice->klattv[KLATT_Kopen] -= 40; break; case V_FAST: Read8Numbers(p,speed.fast_settings); SetSpeed(3); break; default: if((key & 0xff00) == 0x100) { sscanf(p,"%d",&langopts->param[key &0xff]); } else { fprintf(stderr,"Bad voice attribute: %s\n",buf); } break; } } if(f_voice != NULL) fclose(f_voice); if((new_translator == NULL) && (!tone_only)) { // not set by language attribute new_translator = SelectTranslator(translator_name); } SetSpeed(3); // for speed_percent for(ix=0; ixfreq2[ix] = voice->freq[ix]; voice->height2[ix] = voice->height[ix]; voice->width2[ix] = voice->width[ix]; } if(tone_only) { new_translator = translator; } else { if((ix = SelectPhonemeTableName(phonemes_name)) < 0) { Melder_throw ("Unknown phoneme table: ", phonemes_name); } voice->phoneme_tab_ix = ix; new_translator->phoneme_tab_ix = ix; LoadDictionary(new_translator, new_dictionary, control & 4); if(dictionary_name[0]==0) return(NULL); // no dictionary loaded new_translator->dict_condition = conditional_rules; voice_languages[langix] = 0; } langopts = &new_translator->langopts; if((value = langopts->param[LOPT_LENGTH_MODS]) != 0) { SetLengthMods(new_translator,value); } voice->width[0] = (voice->width[0] * 105)/100; if(!tone_only) { translator = new_translator; } // relative lengths of different stress syllables for(ix=0; ixstress_lengths[ix] = stress_lengths[ix]; } for(ix=0; ixstress_lengths[ix] += stress_add[ix]; } for(ix=0; ixstress_amps[ix] = stress_amps[ix]; translator->stress_amps_r[ix] = stress_amps[ix] -1; } return(voice); } // end of LoadVoice static char *ExtractVoiceVariantName(char *vname, int variant_num, int add_dir) {//=========================================================================== // Remove any voice variant suffix (name or number) from a voice name // Returns the voice variant name char *p; static char variant_name[40]; char variant_prefix[5]; variant_name[0] = 0; sprintf(variant_prefix,"!v%c",PATHSEP); if(add_dir == 0) variant_prefix[0] = 0; if(vname != NULL) { if((p = strchr(vname,'+')) != NULL) { // The voice name has a +variant suffix variant_num = 0; *p++ = 0; // delete the suffix from the voice name if(isdigit(*p)) { variant_num = atoi(p); // variant number } else { // voice variant name, not number sprintf(variant_name, "%s%s", variant_prefix, p); } } } if(variant_num > 0) { if(variant_num < 10) sprintf(variant_name,"%sm%d",variant_prefix, variant_num); // male else sprintf(variant_name,"%sf%d",variant_prefix, variant_num-10); // female } return(variant_name); } // end of ExtractVoiceVariantName voice_t *LoadVoiceVariant(const char *vname, int variant_num) {//========================================================== // Load a voice file. // Also apply a voice variant if specified by "variant", or by "+number" or "+name" in the "vname" voice_t *v; char *variant_name; char buf[60]; strncpy0(buf,vname,sizeof(buf)); variant_name = ExtractVoiceVariantName(buf,variant_num, 1); if((v = LoadVoice(buf,0)) == NULL) return(NULL); if(variant_name[0] != 0) { v = LoadVoice(variant_name,2); } return(v); } static int VoiceNameSorter(const void *p1, const void *p2) {//======================================================= int ix; espeak_VOICE *v1 = *(espeak_VOICE **)p1; espeak_VOICE *v2 = *(espeak_VOICE **)p2; if((ix = strcmp(&v1->languages[1],&v2->languages[1])) != 0) // primary language name return(ix); if((ix = v1->languages[0] - v2->languages[0]) != 0) // priority number return(ix); return(strcmp(v1->name,v2->name)); } static int VoiceScoreSorter(const void *p1, const void *p2) {//======================================================== int ix; espeak_VOICE *v1 = *(espeak_VOICE **)p1; espeak_VOICE *v2 = *(espeak_VOICE **)p2; if((ix = v2->score - v1->score) != 0) return(ix); return(strcmp(v1->name,v2->name)); } static int ScoreVoice(espeak_VOICE *voice_spec, const char *spec_language, int spec_n_parts, int spec_lang_len, espeak_VOICE *voice) {//========================================================================================================================= int ix; const char *p; int c1, c2; int language_priority; int n_parts; int matching; int matching_parts; int score = 0; int x; int ratio; int required_age; int diff; p = voice->languages; // list of languages+dialects for which this voice is suitable if(strcmp(spec_language,"mbrola")==0) { // only list mbrola voices if(memcmp(voice->identifier,"mb/",3) == 0) return(100); return(0); } if(spec_n_parts == 0) { score = 100; } else { if((*p == 0) && (strcmp(spec_language,"variants")==0)) { // match on a voice with no languages if the required language is "variants" score = 100; } // compare the required language with each of the languages of this voice while(*p != 0) { language_priority = *p++; matching = 1; matching_parts = 0; n_parts = 1; for(ix=0; ; ix++) { if((ix >= spec_lang_len) || ((c1 = spec_language[ix]) == '-')) c1 = 0; if((c2 = p[ix]) == '-') c2 = 0; if(c1 != c2) { matching = 0; } if(p[ix] == '-') { n_parts++; if(matching) matching_parts++; } if(p[ix] == 0) break; } p += (ix+1); matching_parts += matching; // number of parts which match if(matching_parts == 0) continue; // no matching parts for this language x = 5; // reduce the score if not all parts of the required language match if((diff = (spec_n_parts - matching_parts)) > 0) x -= diff; // reduce score if the language is more specific than required if((diff = (n_parts - matching_parts)) > 0) x -= diff; x = x*100 - (language_priority * 2); if(x > score) score = x; } } if(score == 0) return(0); if(voice_spec->name != NULL) { if(strcmp(voice_spec->name,voice->name)==0) { // match on voice name score += 500; } else if(strcmp(voice_spec->name,voice->identifier)==0) { score += 400; } } if(((voice_spec->gender == 1) || (voice_spec->gender == 2)) && ((voice->gender == 1) || (voice->gender == 2))) { if(voice_spec->gender == voice->gender) score += 50; else score -= 50; } if((voice_spec->age <= 12) && (voice->gender == 2) && (voice->age > 12)) { score += 5; // give some preference for non-child female voice if a child is requested } if(voice->age != 0) { if(voice_spec->age == 0) required_age = 30; else required_age = voice_spec->age; ratio = (required_age*100)/voice->age; if(ratio < 100) ratio = 10000/ratio; ratio = (ratio - 100)/10; // 0=exact match, 10=out by factor of 2 x = 5 - ratio; if(x > 0) x = 0; score = score + x; if(voice_spec->age > 0) score += 10; // required age specified, favour voices with a specified age (near it) } if(score < 1) score = 1; return(score); } // end of ScoreVoice static int SetVoiceScores(espeak_VOICE *voice_select, espeak_VOICE **voices, int control) {//====================================================================================== // control: bit0=1 include mbrola voices int ix; int score; int nv; // number of candidates int n_parts=0; int lang_len=0; espeak_VOICE *vp; char language[80]; // count number of parts in the specified language if((voice_select->languages != NULL) && (voice_select->languages[0] != 0)) { n_parts = 1; lang_len = strlen(voice_select->languages); for(ix=0; (ix<=lang_len) && ((unsigned)ix < sizeof(language)); ix++) { if((language[ix] = tolower(voice_select->languages[ix])) == '-') n_parts++; } } // select those voices which match the specified language nv = 0; for(ix=0; ixidentifier,"mb/",3) == 0)) continue; if((score = ScoreVoice(voice_select, language, n_parts, lang_len, voices_list[ix])) > 0) { voices[nv++] = vp; vp->score = score; } } voices[nv] = NULL; // list terminator if(nv==0) return(0); // sort the selected voices by their score qsort(voices,nv,sizeof(espeak_VOICE *),(int (*)(const void *,const void *))VoiceScoreSorter); return(nv); } // end of SetVoiceScores espeak_VOICE *SelectVoiceByName(espeak_VOICE **voices, const char *name2) {//====================================================================== int ix; int match_fname = -1; int match_fname2 = -1; int match_name = -1; const char *id; // this is the filename within espeak-data/voices char *variant_name; int last_part_len; char last_part[41]; char name[40]; if(voices == NULL) { if(n_voices_list == 0) espeak_ListVoices(NULL); // create the voices list voices = voices_list; } strncpy0(name, name2, sizeof(name)); if((variant_name = strchr(name, '+')) != NULL) { *variant_name = 0; variant_name++; } sprintf(last_part,"%c%s",PATHSEP,name); last_part_len = strlen(last_part); for(ix=0; voices[ix] != NULL; ix++) { if(strcmp(name,voices[ix]->name)==0) { match_name = ix; // found matching voice name break; } else { id = voices[ix]->identifier; if(strcmp(name, id)==0) { match_fname = ix; // matching identifier, use this if no matching name } else if(strcmp(last_part,&id[strlen(id)-last_part_len])==0) { match_fname2 = ix; } } } if(match_name < 0) { match_name = match_fname; // no matching name, try matching filename if(match_name < 0) match_name = match_fname2; // try matching just the last part of the filename } if(match_name < 0) return(NULL); return(voices[match_name]); } // end of SelectVoiceByName char const *SelectVoice(espeak_VOICE *voice_select, int *found) {//============================================================ // Returns a path within espeak-voices, with a possible +variant suffix // variant is an output-only parameter int nv; // number of candidates int ix, ix2; int j; int n_variants; int variant_number; int gender; int skip; int aged=1; char *variant_name; const char *p, *p_start; espeak_VOICE *vp = NULL; espeak_VOICE *vp2; espeak_VOICE voice_select2; espeak_VOICE *voices[N_VOICES_LIST]; // list of candidates espeak_VOICE *voices2[N_VOICES_LIST+N_VOICE_VARIANTS]; static espeak_VOICE voice_variants[N_VOICE_VARIANTS]; static char voice_id[50]; *found = 1; memcpy(&voice_select2,voice_select,sizeof(voice_select2)); if(n_voices_list == 0) espeak_ListVoices(NULL); // create the voices list if((voice_select2.languages == NULL) || (voice_select2.languages[0] == 0)) { // no language is specified. Get language from the named voice static char buf[60]; if(voice_select2.name == NULL) { if((voice_select2.name = voice_select2.identifier) == NULL) voice_select2.name = "default"; } strncpy0(buf,voice_select2.name,sizeof(buf)); variant_name = ExtractVoiceVariantName(buf,0,0); vp = SelectVoiceByName(voices_list,buf); if(vp != NULL) { voice_select2.languages = &(vp->languages[1]); if((voice_select2.gender==0) && (voice_select2.age==0) && (voice_select2.variant==0)) { if(variant_name[0] != 0) { sprintf(voice_id,"%s+%s", vp->identifier, variant_name); return(voice_id); } return(vp->identifier); } } } // select and sort voices for the required language nv = SetVoiceScores(&voice_select2,voices,0); if(nv == 0) { // no matching voice, choose the default *found = 0; if((voices[0] = SelectVoiceByName(voices_list,"default")) != NULL) nv = 1; } gender = 0; if((voice_select2.gender == 2) || ((voice_select2.age > 0) && (voice_select2.age < 13))) gender = 2; else if(voice_select2.gender == 1) gender = 1; #define AGE_OLD 60 if(voice_select2.age < AGE_OLD) aged = 0; p = p_start = variant_lists[gender]; if(aged == 0) p++; // the first voice in the variants list is older // add variants for the top voices n_variants = 0; for(ix=0, ix2=0; ixgender != gender)) { skip=1; } if((ix2==0) && aged && (vp->age < AGE_OLD)) { skip=1; } if(skip==0) { voices2[ix2++] = vp; } for(j=0; (j < vp->xx1) && (n_variants < N_VOICE_VARIANTS);) { if((variant_number = *p) == 0) { p = p_start; continue; } vp2 = &voice_variants[n_variants++]; // allocate space for voice variant memcpy(vp2,vp,sizeof(espeak_VOICE)); // copy from the original voice vp2->variant = variant_number; voices2[ix2++] = vp2; p++; j++; } } // add any more variants to the end of the list while((vp != NULL) && ((variant_number = *p++) != 0) && (n_variants < N_VOICE_VARIANTS)) { vp2 = &voice_variants[n_variants++]; // allocate space for voice variant memcpy(vp2,vp,sizeof(espeak_VOICE)); // copy from the original voice vp2->variant = variant_number; voices2[ix2++] = vp2; } // index the sorted list by the required variant number if(ix2 == 0) return(NULL); vp = voices2[voice_select2.variant % ix2]; if(vp->variant != 0) { variant_name = ExtractVoiceVariantName(NULL, vp->variant, 0); sprintf(voice_id,"%s+%s", vp->identifier, variant_name); return(voice_id); } return(vp->identifier); } // end of SelectVoice static void GetVoices(const char *path) {//==================================== FILE *f_voice; espeak_VOICE *voice_data; int ftype; char fname[sizeof(path_home)+100]; #ifdef PLATFORM_RISCOS int len; int *type; char *p; _kernel_swi_regs regs; _kernel_oserror *error; char buf[80]; char directory2[sizeof(path_home)+100]; regs.r[0] = 10; regs.r[1] = (int)path; regs.r[2] = (int)buf; regs.r[3] = 1; regs.r[4] = 0; regs.r[5] = sizeof(buf); regs.r[6] = 0; while(regs.r[3] > 0) { error = _kernel_swi(0x0c+0x20000,®s,®s); /* OS_GBPB 10, read directory entries */ if((error != NULL) || (regs.r[3] == 0)) { break; } type = (int *)(&buf[16]); len = strlen(&buf[20]); sprintf(fname,"%s.%s",path,&buf[20]); if(*type == 2) { // a sub-directory GetVoices(fname); } else { // a regular line, add it to the voices list if((f_voice = fopen(fname,"r")) == NULL) continue; // pass voice file name within the voices directory voice_data = ReadVoiceFile(f_voice, fname+len_path_voices, &buf[20]); fclose(f_voice); if(voice_data != NULL) { voices_list[n_voices_list++] = voice_data; } } } #else #ifdef PLATFORM_WINDOWS WIN32_FIND_DATAA FindFileData; HANDLE hFind = INVALID_HANDLE_VALUE; #undef UNICODE // we need FindFirstFileA() which takes an 8-bit c-string sprintf(fname,"%s\\*",path); hFind = FindFirstFileA(fname, &FindFileData); if(hFind == INVALID_HANDLE_VALUE) return; do { sprintf(fname,"%s%c%s",path,PATHSEP,FindFileData.cFileName); ftype = GetFileLength(fname); if((ftype == -2) && (FindFileData.cFileName[0] != '.')) { // a sub-sirectory GetVoices(fname); } else if(ftype > 0) { // a regular line, add it to the voices list if((f_voice = fopen(fname,"r")) == NULL) continue; // pass voice file name within the voices directory voice_data = ReadVoiceFile(f_voice, fname+len_path_voices, FindFileData.cFileName); fclose(f_voice); if(voice_data != NULL) { voices_list[n_voices_list++] = voice_data; } } } while(FindNextFileA(hFind, &FindFileData) != 0); FindClose(hFind); #else DIR *dir; struct dirent *ent; if((dir = opendir((char *)path)) == NULL) // note: (char *) is needed for WINCE return; while((ent = readdir(dir)) != NULL) { if(n_voices_list >= (N_VOICES_LIST-2)) break; // voices list is full sprintf(fname,"%s%c%s",path,PATHSEP,ent->d_name); ftype = GetFileLength(fname); if((ftype == -2) && (ent->d_name[0] != '.')) { // a sub-sirectory GetVoices(fname); } else if(ftype > 0) { // a regular line, add it to the voices list if((f_voice = fopen(fname,"r")) == NULL) continue; // pass voice file name within the voices directory voice_data = ReadVoiceFile(f_voice, fname+len_path_voices, ent->d_name); fclose(f_voice); if(voice_data != NULL) { voices_list[n_voices_list++] = voice_data; } } } closedir(dir); #endif #endif } // end of GetVoices espeak_ERROR SetVoiceByName(const char *name) {//========================================= espeak_VOICE *v; espeak_VOICE voice_selector; char *variant_name; static char buf[60]; strncpy0(buf,name,sizeof(buf)); variant_name = ExtractVoiceVariantName(buf, 0, 1); memset(&voice_selector,0,sizeof(voice_selector)); // voice_selector.name = buf; voice_selector.name = (char *)name; // include variant name in voice stack ?? // first check for a voice with this filename // This may avoid the need to call espeak_ListVoices(). if(LoadVoice(buf,1) != NULL) { if(variant_name[0] != 0) { LoadVoice(variant_name,2); } DoVoiceChange(voice); SetVoiceStack(&voice_selector, variant_name); return(EE_OK); } if(n_voices_list == 0) espeak_ListVoices(NULL); // create the voices list if((v = SelectVoiceByName(voices_list,buf)) != NULL) { if(LoadVoice(v->identifier,0) != NULL) { if(variant_name[0] != 0) { LoadVoice(variant_name,2); } DoVoiceChange(voice); SetVoiceStack(&voice_selector, variant_name); return(EE_OK); } } return(EE_INTERNAL_ERROR); // voice name not found } // end of SetVoiceByName espeak_ERROR SetVoiceByProperties(espeak_VOICE *voice_selector) {//============================================================ const char *voice_id; int voice_found; voice_id = SelectVoice(voice_selector, &voice_found); if(voice_found == 0) return(EE_NOT_FOUND); LoadVoiceVariant(voice_id,0); DoVoiceChange(voice); SetVoiceStack(voice_selector, ""); return(EE_OK); } // end of SetVoiceByProperties void FreeVoiceList() {//================= for(int ix=0; ixlanguages[0] != 0) && (strcmp(&v->languages[1],"variant") != 0) && (memcmp(v->identifier,"mb/",3) != 0)) { voices[j++] = v; } } voices[j] = NULL; } return((const espeak_VOICE **)voices); #endif return((const espeak_VOICE **)voices_list); } // end of espeak_ListVoices ESPEAK_API espeak_VOICE *espeak_GetCurrentVoice(void) {//================================================== return(¤t_voice_selected); } #pragma GCC visibility pop sources_5316/external/espeak/speak.cpp0000664000176700017670000005152411674622653016651 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2007 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #include "StdAfx.h" #include "speech.h" #include #include #include #ifndef PLATFORM_DOS #ifdef PLATFORM_WINDOWS #include #include #include #include #else #include #endif #endif #ifndef NEED_GETOPT #include #endif #include #include #include #include #include "speak_lib.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" extern void Write4Bytes(FILE *f, int value); char path_home[N_PATH_HOME]; // this is the espeak-data directory char filetype[5]; char wavefile[200]; int (* uri_callback)(int, const char *, const char *) = NULL; int (* phoneme_callback)(const char *) = NULL; FILE *f_wave = NULL; int quiet = 0; unsigned int samples_total = 0; unsigned int samples_split = 0; unsigned int wavefile_count = 0; int end_of_sentence = 0; static const char *help_text = "\nspeak [options] [\"\"]\n\n" "-f Text file to speak\n" "--stdin Read text input from stdin instead of a file\n\n" "If neither -f nor --stdin, then are spoken, or if none then text\n" "is spoken from stdin, each line separately.\n\n" "-a \n" "\t Amplitude, 0 to 200, default is 100\n" "-g \n" "\t Word gap. Pause between words, units of 10mS at the default speed\n" "-k \n" "\t Indicate capital letters with: 1=sound, 2=the word \"capitals\",\n" "\t higher values indicate a pitch increase (try -k20).\n" "-l \n" "\t Line length. If not zero (which is the default), consider\n" "\t lines less than this length as end-of-clause\n" "-p \n" "\t Pitch adjustment, 0 to 99, default is 50\n" "-s \n" "\t Speed in words per minute, 80 to 450, default is 175\n" "-v \n" "\t Use voice file of this name from espeak-data/voices\n" "-w \n" "\t Write speech to this WAV file, rather than speaking it directly\n" "-b\t Input text encoding, 1=UTF8, 2=8 bit, 4=16 bit \n" "-m\t Interpret SSML markup, and ignore other < > tags\n" "-q\t Quiet, don't produce any speech (may be useful with -x)\n" "-x\t Write phoneme mnemonics to stdout\n" "-X\t Write phonemes mnemonics and translation trace to stdout\n" "-z\t No final sentence pause at the end of the text\n" "--compile=\n" "\t Compile pronunciation rules and dictionary from the current\n" "\t directory. specifies the language\n" "--ipa Write phonemes to stdout using International Phonetic Alphabet\n" "--path=\"\"\n" "\t Specifies the directory containing the espeak-data directory\n" "--pho Write mbrola phoneme data (.pho) to stdout or to the file in --phonout\n" "--phonout=\"\"\n" "\t Write phoneme output from -x -X --ipa and --pho to this file\n" "--punct=\"\"\n" "\t Speak the names of punctuation characters during speaking. If\n" "\t = is omitted, all punctuation is spoken.\n" "--split=\"\"\n" "\t Starts a new WAV file every . Used with -w\n" "--stdout Write speech output to stdout\n" "--voices=\n" "\t List the available voices for the specified language.\n" "\t If is omitted, then list all voices.\n"; void DisplayVoices(FILE *f_out, char *language); USHORT voice_pcnt[N_PEAKS+1][3]; int GetFileLength(const char *filename) {//==================================== struct stat statbuf; if(stat(filename,&statbuf) != 0) return(0); if((statbuf.st_mode & S_IFMT) == S_IFDIR) // if(S_ISDIR(statbuf.st_mode)) return(-2); // a directory return(statbuf.st_size); } // end of GetFileLength char *Alloc(int size) {//================== char *p; if((p = (char *)malloc(size)) == NULL) fprintf(stderr,"Can't allocate memory\n"); return(p); } void Free(void *ptr) {//================= if(ptr != NULL) free(ptr); } void DisplayVoices(FILE *f_out, char *language) {//============================================ int ix; const char *p; int len; int count; const espeak_VOICE *v; const char *lang_name; char age_buf[12]; const espeak_VOICE **voices; espeak_VOICE voice_select; static char genders[4] = {' ','M','F',' '}; if((language != NULL) && (language[0] != 0)) { // display only voices for the specified language, in order of priority voice_select.languages = language; voice_select.age = 0; voice_select.gender = 0; voice_select.name = NULL; voices = espeak_ListVoices(&voice_select); } else { voices = espeak_ListVoices(NULL); } fprintf(f_out,"Pty Language Age/Gender VoiceName File Other Langs\n"); for(ix=0; (v = voices[ix]) != NULL; ix++) { count = 0; p = v->languages; while(*p != 0) { len = strlen(p+1); lang_name = p+1; if(v->age == 0) strcpy(age_buf," "); else sprintf(age_buf,"%3d",v->age); if(count==0) { fprintf(f_out,"%2d %-12s%s%c %-17s %-11s ", p[0],lang_name,age_buf,genders[v->gender],v->name,v->identifier); } else { fprintf(f_out,"(%s %d)",lang_name,p[0]); } count++; p += len+2; } fputc('\n',f_out); } } // end of DisplayVoices void WVoiceChanged(voice_t *wvoice) { } static int OpenWaveFile(const char *path, int rate) //================================================= { // Set the length of 0x7ffff000 for --stdout // This will be changed to the correct length for -w (write to file) static unsigned char wave_hdr[44] = { 'R','I','F','F',0x24,0xf0,0xff,0x7f,'W','A','V','E','f','m','t',' ', 0x10,0,0,0,1,0,1,0, 9,0x3d,0,0,0x12,0x7a,0,0, 2,0,0x10,0,'d','a','t','a', 0x00,0xf0,0xff,0x7f}; if(path == NULL) return(2); if(strcmp(path,"stdout")==0) { #ifdef PLATFORM_WINDOWS // prevent Windows adding 0x0d before 0x0a bytes _setmode(_fileno(stdout), _O_BINARY); #endif f_wave = stdout; } else f_wave = fopen(path,"wb"); if(f_wave != NULL) { fwrite(wave_hdr,1,24,f_wave); Write4Bytes(f_wave,rate); Write4Bytes(f_wave,rate * 2); fwrite(&wave_hdr[32],1,12,f_wave); return(0); } return(1); } // end of OpenWaveFile static void CloseWaveFile() //========================= { unsigned int pos; if((f_wave == NULL) || (f_wave == stdout)) return; fflush(f_wave); pos = ftell(f_wave); fseek(f_wave,4,SEEK_SET); Write4Bytes(f_wave,pos - 8); fseek(f_wave,40,SEEK_SET); Write4Bytes(f_wave,pos - 44); fclose(f_wave); f_wave = NULL; } // end of CloseWaveFile void MarkerEvent(int type, unsigned int char_position, int value, unsigned char *out_ptr) {//====================================================================================== // Do nothing in the command-line version. if(type == 2) end_of_sentence = 1; } // end of MarkerEvent static int WavegenFile(void) {//========================= int finished; unsigned char wav_outbuf[1024]; char fname[210]; out_ptr = out_start = wav_outbuf; out_end = wav_outbuf + sizeof(wav_outbuf); finished = WavegenFill(0); if(quiet) return(finished); if(f_wave == NULL) { sprintf(fname,"%s_%.2d%s",wavefile,++wavefile_count,filetype); if(OpenWaveFile(fname, samplerate) != 0) return(1); } if(end_of_sentence) { end_of_sentence = 0; if((samples_split > 0 ) && (samples_total > samples_split)) { CloseWaveFile(); samples_total = 0; } } if(f_wave != NULL) { samples_total += (out_ptr - wav_outbuf)/2; fwrite(wav_outbuf, 1, out_ptr - wav_outbuf, f_wave); } return(finished); } // end of WavegenFile static void init_path(char *argv0, char *path_specified) {//===================================================== if(path_specified) { sprintf(path_home,"%s/espeak-data",path_specified); return; } #ifdef PLATFORM_WINDOWS HKEY RegKey; unsigned long size; unsigned long var_type; char *p; char *env; unsigned char buf[sizeof(path_home)-12]; if(((env = getenv("ESPEAK_DATA_PATH")) != NULL) && ((strlen(env)+12) < sizeof(path_home))) { sprintf(path_home,"%s\\espeak-data",env); if(GetFileLength(path_home) == -2) return; // an espeak-data directory exists in the directory specified by environment variable } strcpy(path_home,argv0); if((p = strrchr(path_home,'\\')) != NULL) { strcpy(&p[1],"espeak-data"); if(GetFileLength(path_home) == -2) return; // an espeak-data directory exists in the same directory as the espeak program } // otherwise, look in the Windows Registry buf[0] = 0; RegOpenKeyEx(HKEY_LOCAL_MACHINE, "Software\\Microsoft\\Speech\\Voices\\Tokens\\eSpeak", 0, KEY_READ, &RegKey); size = sizeof(buf); var_type = REG_SZ; RegQueryValueEx(RegKey, "path", 0, &var_type, buf, &size); sprintf(path_home,"%s\\espeak-data",buf); #else #ifdef PLATFORM_DOS strcpy(path_home,PATH_ESPEAK_DATA); #else char *env; if((env = getenv("ESPEAK_DATA_PATH")) != NULL) { snprintf(path_home,sizeof(path_home),"%s/espeak-data",env); if(GetFileLength(path_home) == -2) return; // an espeak-data directory exists } snprintf(path_home,sizeof(path_home),"%s/espeak-data",getenv("HOME")); if(access(path_home,R_OK) != 0) { strcpy(path_home,PATH_ESPEAK_DATA); } #endif #endif } static int initialise(void) {//======================== int param; int result; // It seems that the wctype functions don't work until the locale has been set // to something other than the default "C". Then, not only Latin1 but also the // other characters give the correct results with iswalpha() etc. #ifdef PLATFORM_RISCOS setlocale(LC_CTYPE,"ISO8859-1"); #else if(setlocale(LC_CTYPE,"en_US.UTF-8") == NULL) { if(setlocale(LC_CTYPE,"UTF-8") == NULL) setlocale(LC_CTYPE,""); } #endif WavegenInit(22050,0); // 22050 if((result = LoadPhData()) != 1) { if(result == -1) { fprintf(stderr,"Failed to load espeak-data\n"); exit(1); } else fprintf(stderr,"Wrong version of espeak-data 0x%x (expects 0x%x) at %s\n",result,version_phdata,path_home); } LoadConfig(); SetVoiceStack(NULL, ""); SynthesizeInit(); for(param=0; param 99) pitch_adjustment = 99; break; case 'q': quiet = 1; break; case 'f': strncpy0(filename,optarg2,sizeof(filename)); break; case 'l': value = 0; value = atoi(optarg2); option_linelength = value; break; case 'a': amp = atoi(optarg2); break; case 's': speed = atoi(optarg2); break; case 'g': wordgap = atoi(optarg2); break; case 'v': strncpy0(voicename,optarg2,sizeof(voicename)); break; case 'w': option_waveout = 1; strncpy0(wavefile,optarg2,sizeof(wavefile)); break; case 'z': option_endpause = 0; break; case 0x100: // --stdin flag_stdin = 1; break; case 0x105: // --stdout option_waveout = 1; strcpy(wavefile,"stdout"); break; case 0x101: // --compile-debug case 0x102: // --compile if(optarg2 != NULL) strncpy0(voicename,optarg2,sizeof(voicename)); flag_compile = c; break; case 0x103: // --punct option_punctuation = 1; if(optarg2 != NULL) { ix = 0; while((ix < N_PUNCTLIST) && ((option_punctlist[ix] = optarg2[ix]) != 0)) ix++; option_punctlist[N_PUNCTLIST-1] = 0; option_punctuation = 2; } break; case 0x104: // --voices init_path(argv[0],data_path); DisplayVoices(stdout,optarg2); exit(0); case 0x106: // -- split if(optarg2 == NULL) samples_split = 30; // default 30 minutes else samples_split = atoi(optarg2); break; case 0x107: // --path data_path = optarg2; break; case 0x108: // --phonout if((f_trans = fopen(optarg2,"w")) == NULL) { fprintf(stderr,"Can't write to: %s\n",optarg2); f_trans = stderr; } break; case 0x109: // --pho option_mbrola_phonemes = 16; break; case 0x10a: // --ipa option_phonemes = 3; break; default: exit(0); } } init_path(argv[0],data_path); initialise(); if(flag_compile) { LoadVoice(voicename,5); #ifdef PLATFORM_DOS char path_dsource[sizeof(path_home)+20]; strcpy(path_dsource,path_home); path_dsource[strlen(path_home)-11] = 0; // remove "espeak-data" from the end strcat(path_dsource,"dictsource\\"); CompileDictionary(path_dsource,dictionary_name,NULL,NULL, flag_compile & 0x1); #else #ifdef PLATFORM_WINDOWS char path_dsource[sizeof(path_home)+20]; strcpy(path_dsource,path_home); path_dsource[strlen(path_home)-11] = 0; // remove "espeak-data" from the end strcat(path_dsource,"dictsource\\"); CompileDictionary(path_dsource,dictionary_name,NULL,NULL, flag_compile & 0x1); #else CompileDictionary(NULL,dictionary_name,NULL,NULL, flag_compile & 0x1); #endif #endif exit(0); } if(voicename[0] == 0) strcpy(voicename,"default"); if(SetVoiceByName(voicename) != EE_OK) { memset(&voice_select,0,sizeof(voice_select)); voice_select.languages = voicename; if(SetVoiceByProperties(&voice_select) != EE_OK) { fprintf(stderr,"%svoice '%s'\n",err_load,voicename); exit(2); } } SetParameter(espeakRATE,speed,0); SetParameter(espeakVOLUME,amp,0); SetParameter(espeakCAPITALS,option_capitals,0); SetParameter(espeakPUNCTUATION,option_punctuation,0); SetParameter(espeakWORDGAP,wordgap,0); if(pitch_adjustment != 50) { SetParameter(espeakPITCH,pitch_adjustment,0); } DoVoiceChange(voice); if(filename[0]==0) { if((optind < argc) && (flag_stdin == 0)) { // there's a non-option parameter, and no -f or --stdin // use it as text p_text = argv[optind]; } else { f_text = stdin; if(flag_stdin == 0) option_linelength = -1; // single input lines on stdin } } else { f_text = fopen(filename,"r"); } if((f_text == NULL) && (p_text == NULL)) { fprintf(stderr,"%sfile '%s'\n",err_load,filename); exit(1); } if(option_waveout || quiet) { if(quiet) { // no sound output OpenWaveFile(NULL,samplerate); option_waveout = 1; } else { // write sound output to a WAV file samples_split = (samplerate * samples_split) * 60; if(samples_split) { // don't open the wav file until we start generating speech char *extn; extn = strrchr(wavefile,'.'); if((extn != NULL) && ((wavefile + strlen(wavefile) - extn) <= 4)) { strcpy(filetype,extn); *extn = 0; } } else if(OpenWaveFile(wavefile,samplerate) != 0) { fprintf(stderr,"Can't write to output file '%s'\n'",wavefile); exit(3); } } InitText(0); SpeakNextClause(f_text,p_text,0); ix = 1; for(;;) { if(WavegenFile() != 0) { if(ix == 0) break; // finished, wavegen command queue is empty } if(Generate(phoneme_list,&n_phoneme_list,1)==0) { ix = SpeakNextClause(NULL,NULL,1); } } CloseWaveFile(); } else { // Silence on ^C or SIGINT // signal(SIGINT,StopSpeak); // output sound using portaudio WavegenInitSound(); InitText(0); SpeakNextClause(f_text,p_text,0); if(option_quiet) { while(SpeakNextClause(NULL,NULL,1) != 0); return(0); } #ifdef USE_PORTAUDIO speaking = 1; while(speaking) { // NOTE: if nanosleep() isn't recognised on your system, try replacing // this by sleep(1); #ifdef PLATFORM_WINDOWS Sleep(300); // 0.3s #else #ifdef USE_NANOSLEEP struct timespec period; struct timespec remaining; period.tv_sec = 0; period.tv_nsec = 300000000; // 0.3 sec nanosleep(&period,&remaining); #else sleep(1); #endif #endif if(SynthOnTimer() != 0) speaking = 0; } #else fprintf(stderr,"-w option must be used because the program was built without a sound interface\n"); #endif // USE_PORTAUDIO } if((f_trans != stdout) && (f_trans != stderr)) fclose(f_trans); // needed for WinCe return(0); } sources_5316/external/espeak/Makefile0000664000176700017670000000135311723710247016465 0ustar paulpaul# makefile for libespeak include ../../makefile.defs CPPFLAGS = -I ../../num -I ../../kar -I ../../stat -I ../../sys -I ../../dwsys OBJECTS = compiledict.o dictionary.o intonation.o klatt.o \ numbers.o phonemelist.o readclause.o setlengths.o \ sonic.o speak_lib.o synthdata.o synthesize.o \ synth_mbrola.o tr_languages.o translate.o voices.o wavegen.o \ espeakdata_phons.o espeakdata_dicts.o espeakdata_voices.o espeakdata_variants.o \ espeakdata_FileInMemory.o .PHONY: all clean all: libespeak.a clean: $(RM) $(OBJECTS) $(RM) libespeak.a libespeak.a: $(OBJECTS) touch libespeak.a rm libespeak.a ar cq libespeak.a $(OBJECTS) $(RANLIB) libespeak.a $(OBJECTS): *.h ../../num/NUM.h ../../kar/*.h ../../sys/*.h ../../stat/*.h sources_5316/external/espeak/translate.cpp0000664000176700017670000025574411723710247017545 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2011 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" #define WORD_STRESS_CHAR '*' Translator *translator = NULL; // the main translator Translator *translator2 = NULL; // secondary translator for certain words static char translator2_language[20] = {0}; FILE *f_trans = NULL; // phoneme output text int option_tone2 = 0; int option_tone_flags = 0; // bit 8=emphasize allcaps, bit 9=emphasize penultimate stress int option_phonemes = 0; int option_phoneme_events = 0; int option_quiet = 0; int option_endpause = 0; // suppress pause after end of text int option_capitals = 0; int option_punctuation = 0; int option_sayas = 0; static int option_sayas2 = 0; // used in translate_clause() static int option_emphasis = 0; // 0=normal, 1=normal, 2=weak, 3=moderate, 4=strong int option_ssml = 0; int option_phoneme_input = 0; // allow [[phonemes]] in input int option_phoneme_variants = 0; // 0= don't display phoneme variant mnemonics int option_wordgap = 0; static int count_sayas_digits; int skip_sentences; int skip_words; int skip_characters; char skip_marker[N_MARKER_LENGTH]; int skipping_text; // waiting until word count, sentence count, or named marker is reached int end_character_position; int count_sentences; int count_words; int clause_start_char; int clause_start_word; int new_sentence; static int word_emphasis = 0; // set if emphasis level 3 or 4 static int embedded_flag = 0; // there are embedded commands to be applied to the next phoneme, used in TranslateWord2() static int prev_clause_pause=0; static int max_clause_pause = 0; static int any_stressed_words; int pre_pause; // these were previously in translator class #ifdef PLATFORM_WINDOWS char word_phonemes[N_WORD_PHONEMES*2]; // longer, because snprint() is not available #else char word_phonemes[N_WORD_PHONEMES]; // a word translated into phoneme codes #endif int n_ph_list2; PHONEME_LIST2 ph_list2[N_PHONEME_LIST]; // first stage of text->phonemes wchar_t option_punctlist[N_PUNCTLIST]={0}; char ctrl_embedded = '\001'; // to allow an alternative CTRL for embedded commands int option_multibyte=espeakCHARS_AUTO; // 0=auto, 1=utf8, 2=8bit, 3=wchar, 4=16bit // these are overridden by defaults set in the "speak" file int option_linelength = 0; #define N_EMBEDDED_LIST 250 static int embedded_ix; static int embedded_read; unsigned int embedded_list[N_EMBEDDED_LIST]; // the source text of a single clause (UTF8 bytes) #define N_TR_SOURCE 800 static char source[N_TR_SOURCE+40]; // extra space for embedded command & voice change info at end int n_replace_phonemes; REPLACE_PHONEMES replace_phonemes[N_REPLACE_PHONEMES]; // brackets, also 0x2014 to 0x021f which don't need to be in this list static const unsigned short brackets[] = { '(',')','[',']','{','}','<','>','"','\'','`', 0xab,0xbb, // double angle brackets 0x300a,0x300b, // double angle brackets (ideograph) 0xe000+'<', // private usage area 0}; // other characters which break a word, but don't produce a pause static const unsigned short breaks[] = {'_', 0}; // treat these characters as spaces, in addition to iswspace() // static const wchar_t chars_space[] = {0x2500,0x2501,0}; // box drawing horiz // Translate character codes 0xA0 to 0xFF into their unicode values // ISO_8859_1 is set as default static const unsigned short ISO_8859_1[0x60] = { 0x00a0, 0x00a1, 0x00a2, 0x00a3, 0x00a4, 0x00a5, 0x00a6, 0x00a7, // a0 0x00a8, 0x00a9, 0x00aa, 0x00ab, 0x00ac, 0x00ad, 0x00ae, 0x00af, // a8 0x00b0, 0x00b1, 0x00b2, 0x00b3, 0x00b4, 0x00b5, 0x00b6, 0x00b7, // b0 0x00b8, 0x00b9, 0x00ba, 0x00bb, 0x00bc, 0x00bd, 0x00be, 0x00bf, // b8 0x00c0, 0x00c1, 0x00c2, 0x00c3, 0x00c4, 0x00c5, 0x00c6, 0x00c7, // c0 0x00c8, 0x00c9, 0x00ca, 0x00cb, 0x00cc, 0x00cd, 0x00ce, 0x00cf, // c8 0x00d0, 0x00d1, 0x00d2, 0x00d3, 0x00d4, 0x00d5, 0x00d6, 0x00d7, // d0 0x00d8, 0x00d9, 0x00da, 0x00db, 0x00dc, 0x00dd, 0x00de, 0x00df, // d8 0x00e0, 0x00e1, 0x00e2, 0x00e3, 0x00e4, 0x00e5, 0x00e6, 0x00e7, // e0 0x00e8, 0x00e9, 0x00ea, 0x00eb, 0x00ec, 0x00ed, 0x00ee, 0x00ef, // e8 0x00f0, 0x00f1, 0x00f2, 0x00f3, 0x00f4, 0x00f5, 0x00f6, 0x00f7, // f0 0x00f8, 0x00f9, 0x00fa, 0x00fb, 0x00fc, 0x00fd, 0x00fe, 0x00ff, // f8 }; static const unsigned short ISO_8859_2[0x60] = { 0x00a0, 0x0104, 0x02d8, 0x0141, 0x00a4, 0x013d, 0x015a, 0x00a7, // a0 0x00a8, 0x0160, 0x015e, 0x0164, 0x0179, 0x00ad, 0x017d, 0x017b, // a8 0x00b0, 0x0105, 0x02db, 0x0142, 0x00b4, 0x013e, 0x015b, 0x02c7, // b0 0x00b8, 0x0161, 0x015f, 0x0165, 0x017a, 0x02dd, 0x017e, 0x017c, // b8 0x0154, 0x00c1, 0x00c2, 0x0102, 0x00c4, 0x0139, 0x0106, 0x00c7, // c0 0x010c, 0x00c9, 0x0118, 0x00cb, 0x011a, 0x00cd, 0x00ce, 0x010e, // c8 0x0110, 0x0143, 0x0147, 0x00d3, 0x00d4, 0x0150, 0x00d6, 0x00d7, // d0 0x0158, 0x016e, 0x00da, 0x0170, 0x00dc, 0x00dd, 0x0162, 0x00df, // d8 0x0155, 0x00e1, 0x00e2, 0x0103, 0x00e4, 0x013a, 0x0107, 0x00e7, // e0 0x010d, 0x00e9, 0x0119, 0x00eb, 0x011b, 0x00ed, 0x00ee, 0x010f, // e8 0x0111, 0x0144, 0x0148, 0x00f3, 0x00f4, 0x0151, 0x00f6, 0x00f7, // f0 0x0159, 0x016f, 0x00fa, 0x0171, 0x00fc, 0x00fd, 0x0163, 0x02d9, // f8 }; static const unsigned short ISO_8859_3[0x60] = { 0x00a0, 0x0126, 0x02d8, 0x00a3, 0x00a4, 0x0000, 0x0124, 0x00a7, // a0 0x00a8, 0x0130, 0x015e, 0x011e, 0x0134, 0x00ad, 0x0000, 0x017b, // a8 0x00b0, 0x0127, 0x00b2, 0x00b3, 0x00b4, 0x00b5, 0x0125, 0x00b7, // b0 0x00b8, 0x0131, 0x015f, 0x011f, 0x0135, 0x00bd, 0x0000, 0x017c, // b8 0x00c0, 0x00c1, 0x00c2, 0x0000, 0x00c4, 0x010a, 0x0108, 0x00c7, // c0 0x00c8, 0x00c9, 0x00ca, 0x00cb, 0x00cc, 0x00cd, 0x00ce, 0x00cf, // c8 0x0000, 0x00d1, 0x00d2, 0x00d3, 0x00d4, 0x0120, 0x00d6, 0x00d7, // d0 0x011c, 0x00d9, 0x00da, 0x00db, 0x00dc, 0x016c, 0x015c, 0x00df, // d8 0x00e0, 0x00e1, 0x00e2, 0x0000, 0x00e4, 0x010b, 0x0109, 0x00e7, // e0 0x00e8, 0x00e9, 0x00ea, 0x00eb, 0x00ec, 0x00ed, 0x00ee, 0x00ef, // e8 0x0000, 0x00f1, 0x00f2, 0x00f3, 0x00f4, 0x0121, 0x00f6, 0x00f7, // f0 0x011d, 0x00f9, 0x00fa, 0x00fb, 0x00fc, 0x016d, 0x015d, 0x02d9, // f8 }; static const unsigned short ISO_8859_4[0x60] = { 0x00a0, 0x0104, 0x0138, 0x0156, 0x00a4, 0x0128, 0x013b, 0x00a7, // a0 0x00a8, 0x0160, 0x0112, 0x0122, 0x0166, 0x00ad, 0x017d, 0x00af, // a8 0x00b0, 0x0105, 0x02db, 0x0157, 0x00b4, 0x0129, 0x013c, 0x02c7, // b0 0x00b8, 0x0161, 0x0113, 0x0123, 0x0167, 0x014a, 0x017e, 0x014b, // b8 0x0100, 0x00c1, 0x00c2, 0x00c3, 0x00c4, 0x00c5, 0x00c6, 0x012e, // c0 0x010c, 0x00c9, 0x0118, 0x00cb, 0x0116, 0x00cd, 0x00ce, 0x012a, // c8 0x0110, 0x0145, 0x014c, 0x0136, 0x00d4, 0x00d5, 0x00d6, 0x00d7, // d0 0x00d8, 0x0172, 0x00da, 0x00db, 0x00dc, 0x0168, 0x016a, 0x00df, // d8 0x0101, 0x00e1, 0x00e2, 0x00e3, 0x00e4, 0x00e5, 0x00e6, 0x012f, // e0 0x010d, 0x00e9, 0x0119, 0x00eb, 0x0117, 0x00ed, 0x00ee, 0x012b, // e8 0x0111, 0x0146, 0x014d, 0x0137, 0x00f4, 0x00f5, 0x00f6, 0x00f7, // f0 0x00f8, 0x0173, 0x00fa, 0x00fb, 0x00fc, 0x0169, 0x016b, 0x02d9, // f8 }; static const unsigned short ISO_8859_5[0x60] = { 0x00a0, 0x0401, 0x0402, 0x0403, 0x0404, 0x0405, 0x0406, 0x0407, // a0 Cyrillic 0x0408, 0x0409, 0x040a, 0x040b, 0x040c, 0x00ad, 0x040e, 0x040f, // a8 0x0410, 0x0411, 0x0412, 0x0413, 0x0414, 0x0415, 0x0416, 0x0417, // b0 0x0418, 0x0419, 0x041a, 0x041b, 0x041c, 0x041d, 0x041e, 0x041f, // b8 0x0420, 0x0421, 0x0422, 0x0423, 0x0424, 0x0425, 0x0426, 0x0427, // c0 0x0428, 0x0429, 0x042a, 0x042b, 0x042c, 0x042d, 0x042e, 0x042f, // c8 0x0430, 0x0431, 0x0432, 0x0433, 0x0434, 0x0435, 0x0436, 0x0437, // d0 0x0438, 0x0439, 0x043a, 0x043b, 0x043c, 0x043d, 0x043e, 0x043f, // d8 0x0440, 0x0441, 0x0442, 0x0443, 0x0444, 0x0445, 0x0446, 0x0447, // e0 0x0448, 0x0449, 0x044a, 0x044b, 0x044c, 0x044d, 0x044e, 0x044f, // e8 0x2116, 0x0451, 0x0452, 0x0453, 0x0454, 0x0455, 0x0456, 0x0457, // f0 0x0458, 0x0459, 0x045a, 0x045b, 0x045c, 0x00a7, 0x045e, 0x045f, // f8 }; static const unsigned short ISO_8859_7[0x60] = { 0x00a0, 0x2018, 0x2019, 0x00a3, 0x20ac, 0x20af, 0x00a6, 0x00a7, // a0 Greek 0x00a8, 0x00a9, 0x037a, 0x00ab, 0x00ac, 0x00ad, 0x0000, 0x2015, // a8 0x00b0, 0x00b1, 0x00b2, 0x00b3, 0x0384, 0x0385, 0x0386, 0x00b7, // b0 0x0388, 0x0389, 0x038a, 0x00bb, 0x038c, 0x00bd, 0x038e, 0x038f, // b8 0x0390, 0x0391, 0x0392, 0x0393, 0x0394, 0x0395, 0x0396, 0x0397, // c0 0x0398, 0x0399, 0x039a, 0x039b, 0x039c, 0x039d, 0x039e, 0x039f, // c8 0x03a0, 0x03a1, 0x0000, 0x03a3, 0x03a4, 0x03a5, 0x03a6, 0x03a7, // d0 0x03a8, 0x03a9, 0x03aa, 0x03ab, 0x03ac, 0x03ad, 0x03ae, 0x03af, // d8 0x03b0, 0x03b1, 0x03b2, 0x03b3, 0x03b4, 0x03b5, 0x03b6, 0x03b7, // e0 0x03b8, 0x03b9, 0x03ba, 0x03bb, 0x03bc, 0x03bd, 0x03be, 0x03bf, // e8 0x03c0, 0x03c1, 0x03c2, 0x03c3, 0x03c4, 0x03c5, 0x03c6, 0x03c7, // f0 0x03c8, 0x03c9, 0x03ca, 0x03cb, 0x03cc, 0x03cd, 0x03ce, 0x0000, // f8 }; static const unsigned short ISO_8859_9[0x60] = { 0x00a0, 0x00a1, 0x00a2, 0x00a3, 0x00a4, 0x00a5, 0x00a6, 0x00a7, // a0 0x00a8, 0x00a9, 0x00aa, 0x00ab, 0x00ac, 0x00ad, 0x00ae, 0x00af, // a8 0x00b0, 0x00b1, 0x00b2, 0x00b3, 0x00b4, 0x00b5, 0x00b6, 0x00b7, // b0 0x00b8, 0x00b9, 0x00ba, 0x00bb, 0x00bc, 0x00bd, 0x00be, 0x00bf, // b8 0x00c0, 0x00c1, 0x00c2, 0x00c3, 0x00c4, 0x00c5, 0x00c6, 0x00c7, // c0 0x00c8, 0x00c9, 0x00ca, 0x00cb, 0x00cc, 0x00cd, 0x00ce, 0x00cf, // c8 0x011e, 0x00d1, 0x00d2, 0x00d3, 0x00d4, 0x00d5, 0x00d6, 0x00d7, // d0 0x00d8, 0x00d9, 0x00da, 0x00db, 0x00dc, 0x0130, 0x015e, 0x00df, // d8 0x00e0, 0x00e1, 0x00e2, 0x00e3, 0x00e4, 0x00e5, 0x00e6, 0x00e7, // e0 0x00e8, 0x00e9, 0x00ea, 0x00eb, 0x00ec, 0x00ed, 0x00ee, 0x00ef, // e8 0x011f, 0x00f1, 0x00f2, 0x00f3, 0x00f4, 0x00f5, 0x00f6, 0x00f7, // f0 0x00f8, 0x00f9, 0x00fa, 0x00fb, 0x00fc, 0x0131, 0x015f, 0x00ff, // f8 }; static const unsigned short ISO_8859_14[0x60] = { 0x00a0, 0x1e02, 0x1e03, 0x00a3, 0x010a, 0x010b, 0x1e0a, 0x00a7, // a0 Welsh 0x1e80, 0x00a9, 0x1e82, 0x1e0b, 0x1ef2, 0x00ad, 0x00ae, 0x0178, // a8 0x1e1e, 0x1e1f, 0x0120, 0x0121, 0x1e40, 0x1e41, 0x00b6, 0x1e56, // b0 0x1e81, 0x1e57, 0x1e83, 0x1e60, 0x1ef3, 0x1e84, 0x1e85, 0x1e61, // b8 0x00c0, 0x00c1, 0x00c2, 0x00c3, 0x00c4, 0x00c5, 0x00c6, 0x00c7, // c0 0x00c8, 0x00c9, 0x00ca, 0x00cb, 0x00cc, 0x00cd, 0x00ce, 0x00cf, // c8 0x0174, 0x00d1, 0x00d2, 0x00d3, 0x00d4, 0x00d5, 0x00d6, 0x1e6a, // d0 0x00d8, 0x00d9, 0x00da, 0x00db, 0x00dc, 0x00dd, 0x0176, 0x00df, // d8 0x00e0, 0x00e1, 0x00e2, 0x00e3, 0x00e4, 0x00e5, 0x00e6, 0x00e7, // e0 0x00e8, 0x00e9, 0x00ea, 0x00eb, 0x00ec, 0x00ed, 0x00ee, 0x00ef, // e8 0x0175, 0x00f1, 0x00f2, 0x00f3, 0x00f4, 0x00f5, 0x00f6, 0x1e6b, // f0 0x00f8, 0x00f9, 0x00fa, 0x00fb, 0x00fc, 0x00fd, 0x0177, 0x00ff, // f8 }; static const unsigned short KOI8_R[0x60] = { 0x2550, 0x2551, 0x2552, 0x0451, 0x2553, 0x2554, 0x2555, 0x2556, // a0 Russian 0x2557, 0x2558, 0x2559, 0x255a, 0x255b, 0x255c, 0x255d, 0x255e, // a8 0x255f, 0x2560, 0x2561, 0x0401, 0x2562, 0x2563, 0x2564, 0x2565, // b0 0x2566, 0x2567, 0x2568, 0x2569, 0x256a, 0x256b, 0x256c, 0x00a9, // b8 0x044e, 0x0430, 0x0431, 0x0446, 0x0434, 0x0435, 0x0444, 0x0433, // c0 0x0445, 0x0438, 0x0439, 0x043a, 0x043b, 0x043c, 0x043d, 0x043e, // c8 0x043f, 0x044f, 0x0440, 0x0441, 0x0442, 0x0443, 0x0436, 0x0432, // d0 0x044c, 0x044b, 0x0437, 0x0448, 0x044d, 0x0449, 0x0447, 0x044a, // d8 0x042e, 0x0410, 0x0411, 0x0426, 0x0414, 0x0415, 0x0424, 0x0413, // e0 0x0425, 0x0418, 0x0419, 0x041a, 0x041b, 0x041c, 0x041d, 0x041e, // e8 0x041f, 0x042f, 0x0420, 0x0421, 0x0422, 0x0423, 0x0416, 0x0412, // f0 0x042c, 0x042b, 0x0417, 0x0428, 0x042d, 0x0429, 0x0427, 0x042a, // f8 }; static const unsigned short ISCII[0x60] = { 0x0020, 0x0901, 0x0902, 0x0903, 0x0905, 0x0906, 0x0907, 0x0908, // a0 0x0909, 0x090a, 0x090b, 0x090e, 0x090f, 0x0910, 0x090d, 0x0912, // a8 0x0913, 0x0914, 0x0911, 0x0915, 0x0916, 0x0917, 0x0918, 0x0919, // b0 0x091a, 0x091b, 0x091c, 0x091d, 0x091e, 0x091f, 0x0920, 0x0921, // b8 0x0922, 0x0923, 0x0924, 0x0925, 0x0926, 0x0927, 0x0928, 0x0929, // c0 0x092a, 0x092b, 0x092c, 0x092d, 0x092e, 0x092f, 0x095f, 0x0930, // c8 0x0931, 0x0932, 0x0933, 0x0934, 0x0935, 0x0936, 0x0937, 0x0938, // d0 0x0939, 0x0020, 0x093e, 0x093f, 0x0940, 0x0941, 0x0942, 0x0943, // d8 0x0946, 0x0947, 0x0948, 0x0945, 0x094a, 0x094b, 0x094c, 0x0949, // e0 0x094d, 0x093c, 0x0964, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, // e8 0x0020, 0x0030, 0x0031, 0x0032, 0x0033, 0x0034, 0x0035, 0x0036, // f0 0x0037, 0x0038, 0x0039, 0x20, 0x20, 0x20, 0x20, 0x20, // f8 }; const unsigned short *charsets[N_CHARSETS] = { ISO_8859_1, ISO_8859_1, ISO_8859_2, ISO_8859_3, ISO_8859_4, ISO_8859_5, ISO_8859_1, ISO_8859_7, ISO_8859_1, ISO_8859_9, ISO_8859_1, ISO_8859_1, ISO_8859_1, ISO_8859_1, ISO_8859_14, ISO_8859_1, ISO_8859_1, ISO_8859_1, KOI8_R, // 18 ISCII }; // Tables of the relative lengths of vowels, depending on the // type of the two phonemes that follow // indexes are the "length_mod" value for the following phonemes // use this table if vowel is not the last in the word static unsigned char length_mods_en[100] = { /* a , t s n d z r N <- next */ 100,120,100,105,100,110,110,100, 95, 100, /* a <- next2 */ 105,120,105,110,125,130,135,115,125, 100, /* , */ 105,120, 75,100, 75,105,120, 85, 75, 100, /* t */ 105,120, 85,105, 95,115,120,100, 95, 100, /* s */ 110,120, 95,105,100,115,120,100,100, 100, /* n */ 105,120,100,105, 95,115,120,110, 95, 100, /* d */ 105,120,100,105,105,122,125,110,105, 100, /* z */ 105,120,100,105,105,122,125,110,105, 100, /* r */ 105,120, 95,105,100,115,120,110,100, 100, /* N */ 100,120,100,100,100,100,100,100,100, 100 }; // SPARE // as above, but for the last syllable in a word static unsigned char length_mods_en0[100] = { /* a , t s n d z r N <- next */ 100,150,100,105,110,115,110,110,110, 100, /* a <- next2 */ 105,150,105,110,125,135,140,115,135, 100, /* , */ 105,150, 90,105, 90,122,135,100, 90, 100, /* t */ 105,150,100,105,100,122,135,100,100, 100, /* s */ 105,150,100,105,105,115,135,110,105, 100, /* n */ 105,150,100,105,105,122,130,120,125, 100, /* d */ 105,150,100,105,110,122,125,115,110, 100, /* z */ 105,150,100,105,105,122,135,120,105, 100, /* r */ 105,150,100,105,105,115,135,110,105, 100, /* N */ 100,100,100,100,100,100,100,100,100, 100 }; // SPARE static unsigned char length_mods_equal[100] = { /* a , t s n d z r N <- next */ 110,120,100,110,110,110,110,110,110, 110, /* a <- next2 */ 110,120,100,110,110,110,110,110,110, 110, /* , */ 110,120,100,110,100,110,110,110,100, 110, /* t */ 110,120,100,110,110,110,110,110,110, 110, /* s */ 110,120,100,110,110,110,110,110,110, 110, /* n */ 110,120,100,110,110,110,110,110,110, 110, /* d */ 110,120,100,110,110,110,110,110,110, 110, /* z */ 110,120,100,110,110,110,110,110,110, 110, /* r */ 110,120,100,110,110,110,110,110,110, 110, /* N */ 110,120,100,110,110,110,110,110,110, 110 }; // SPARE static unsigned char *length_mod_tabs[6] = { length_mods_en, length_mods_en, // 1 length_mods_en0, // 2 length_mods_equal, // 3 length_mods_equal, // 4 length_mods_equal // 5 }; void SetLengthMods(Translator *tr, int value) {//========================================== int value2; tr->langopts.length_mods0 = tr->langopts.length_mods = length_mod_tabs[value % 100]; if((value2 = value / 100) != 0) { tr->langopts.length_mods0 = length_mod_tabs[value2]; } } int IsAlpha(unsigned int c) {//======================== // Replacement for iswalph() which also checks for some in-word symbols const unsigned short extra_indic_alphas[] = { 0xa70,0xa71, // Gurmukhi: tippi, addak 0 }; if(iswalpha(c)) return(1); if((c >= 0x901) && (c <= 0xdf7)) { // Indic scripts: Devanagari, Tamil, etc if((c & 0x7f) < 0x64) return(1); if(lookupwchar(extra_indic_alphas, c) != 0) return(1); if((c >= 0xd7a) && (c <= 0xd7f)) return(1); // malaytalam chillu characters return(0); } if((c >= 0x64b) && (c <= 0x65e)) return(1); // arabic vowel marks if((c >= 0x300) && (c <= 0x36f)) return(1); // combining accents if((c >= 0x780) && (c <= 0x7b1)) return(1); // taani/divehi (maldives) if((c >= 0xf40) && (c <= 0xfbc)) return(1); // tibetan if((c >= 0x1100) && (c <= 0x11ff)) return(1); //Korean jamo if((c > 0x3040) && (c <= 0xa700)) return(1); // Chinese/Japanese. Should never get here, but Mac OS 10.4's iswalpha seems to be broken, so just make sure return(0); } static int IsDigit09(unsigned int c) {//========================= if((c >= '0') && (c <= '9')) return(1); return(0); } int IsDigit(unsigned int c) {//======================== if(iswdigit(c)) return(1); if((c >= 0x966) && (c <= 0x96f)) return(1); return(0); } int IsSpace(unsigned int c) {//======================== if(c == 0) return(0); if((c >= 0x2500) && (c < 0x25a0)) return(1); // box drawing characters // if(wcschr(chars_space,c)) // return(1); return(iswspace(c)); } void DeleteTranslator(Translator *tr) {//================================== if(tr->data_dictlist != NULL) Free(tr->data_dictlist); tr->data_dictlist = 0; Free(tr); } int lookupwchar(const unsigned short *list,int c) {//============================================== // Is the character c in the list ? int ix; for(ix=0; list[ix] != 0; ix++) { if(list[ix] == c) return(ix+1); } return(0); } int IsBracket(int c) {//================= if((c >= 0x2014) && (c <= 0x201f)) return(1); return(lookupwchar(brackets,c)); } int utf8_out(unsigned int c, char *buf) {//==================================== // write a unicode character into a buffer as utf8 // returns the number of bytes written int n_bytes; int j; int shift; static char unsigned code[4] = {0,0xc0,0xe0,0xf0}; if(c < 0x80) { buf[0] = c; return(1); } if(c >= 0x110000) { buf[0] = ' '; // out of range character code return(1); } if(c < 0x0800) n_bytes = 1; else if(c < 0x10000) n_bytes = 2; else n_bytes = 3; shift = 6*n_bytes; buf[0] = code[n_bytes] | (c >> shift); for(j=0; j> shift) & 0x3f); } return(n_bytes+1); } // end of utf8_out int utf8_nbytes(const char *buf) {//============================= // Returns the number of bytes for the first UTF-8 character in buf unsigned char c = (unsigned char)buf[0]; if(c < 0x80) return(1); if(c < 0xe0) return(2); if(c < 0xf0) return(3); return(4); } int utf8_in2(int *c, const char *buf, int backwards) {//================================================= // Read a unicode characater from a UTF8 string // Returns the number of UTF8 bytes used. // backwards: set if we are moving backwards through the UTF8 string int c1; int n_bytes; int ix; static const unsigned char mask[4] = {0xff,0x1f,0x0f,0x07}; // find the start of the next/previous character while((*buf & 0xc0) == 0x80) { // skip over non-initial bytes of a multi-byte utf8 character if(backwards) buf--; else buf++; } n_bytes = 0; if((c1 = *buf++) & 0x80) { if((c1 & 0xe0) == 0xc0) n_bytes = 1; else if((c1 & 0xf0) == 0xe0) n_bytes = 2; else if((c1 & 0xf8) == 0xf0) n_bytes = 3; c1 &= mask[n_bytes]; for(ix=0; ix= 0x80) return(NULL); return(strchr((char *)s,c)); // (char *) is needed for Borland compiler } int IsAllUpper(const char *word) {//============================= int c; while((*word != 0) && !isspace2(*word)) { word += utf8_in(&c, word); if(!iswupper(c)) return(0); } return(1); } static char *SpeakIndividualLetters(Translator *tr, char *word, char *phonemes, int spell_word) {//============================================================================================ int posn = 0; int capitals = 0; int non_initial = 0; if (spell_word > 2) capitals = 2; while((*word != ' ') && (*word != 0)) { word += TranslateLetter(tr, word, phonemes, capitals | non_initial); posn++; non_initial = 1; if(phonemes[0] == phonSWITCH) { // change to another language in order to translate this word strcpy(word_phonemes,phonemes); return(NULL); } } SetSpellingStress(tr,phonemes,spell_word,posn); return(word); } // end of SpeakIndividualLetters static int CheckDottedAbbrev(char *word1, WORD_TAB *wtab) {//===================================================== int wc; int count = 0; int nbytes; int ok; int ix; char *word; char *wbuf; char word_buf[80]; word = word1; wbuf = word_buf; ix = 0; for(;;) { ok = 0; nbytes = utf8_in(&wc, word); if((word[nbytes] == ' ') && IsAlpha(wc)) { if(word[nbytes+1] == '.') { if(word[nbytes+2] == ' ') ok = 1; else if(word[nbytes+2] =='\'') { nbytes += 2; // delete the final dot (eg. u.s.a.'s) ok = 2; } } else if((count > 0) && (word[nbytes] == ' ')) ok = 2; } if(ok == 0) break; for(ix=0; ix < nbytes; ix++) *wbuf++ = word[ix]; count++; if(ok == 2) { word += nbytes; break; } word += (nbytes + 3); } if(count > 1) { ix = wbuf - word_buf; memcpy(word1, word_buf, ix); while(&word1[ix] < word) word1[ix++] = ' '; dictionary_skipwords = (count - 1)*2; } return(count); } // end of CheckDottedAbbrev extern char *phondata_ptr; int ChangeEquivalentPhonemes(Translator *tr, int lang2, char *phonemes) {//==================================================================== // tr: the original language // lang2: phoneme table number for the temporary language // phonemes: the phonemes to be replaced int ix; int len; char phon; char *p; unsigned char *pb; char *eqlist; char *p_out; char *p_in; int remove_stress = 0; char phonbuf[N_WORD_PHONEMES]; // has a phoneme equivalence table been specified for thus language pair? if((ix = phoneme_tab_list[tr->phoneme_tab_ix].equivalence_tables) == 0) return(0); pb = (unsigned char *)&phondata_ptr[ix]; for(;;) { if(pb[0] == 0) return(0); // table not found if(pb[0] == lang2) break; len = (pb[2] << 8) + pb[3]; // size of this table in words pb += (len * 4); } remove_stress = pb[1]; if(option_phonemes == 2) { DecodePhonemes(phonemes, phonbuf); fprintf(f_trans,"(%s) %s -> (%s) ", phoneme_tab_list[lang2].name, phonbuf, phoneme_tab_list[tr->phoneme_tab_ix].name); } p_in = phonemes; eqlist = (char *)&pb[8]; p_out = phonbuf; while((phon = *p_in++) != 0) { if(remove_stress && ((phon & 0xff) < phonSTRESS_PREV)) continue; // remove stress marks // is there a translation for this phoneme code? p = eqlist; while(*p != 0) { len = strlen(&p[1]); if(*p == phon) { strcpy(p_out, &p[1]); p_out += len; break; } p += (len + 2); } if(*p == 0) { // no translation found *p_out++ = phon; } } *p_out = 0; if(remove_stress) { SetWordStress(tr, phonbuf, NULL, -1, 0); } strcpy(phonemes, phonbuf); if(option_phonemes == 2) { SelectPhonemeTable(tr->phoneme_tab_ix); DecodePhonemes(phonemes, phonbuf); fprintf(f_trans,"%s\n\n", phonbuf); } return(1); } // end of ChangeEquivalentPhonemes int TranslateWord(Translator *tr, char *word_start, int next_pause, WORD_TAB *wtab) {//=========================================================================== // word1 is terminated by space (0x20) character char *word1; int word_length; int ix; char *p; int pfix; int n_chars; unsigned int dictionary_flags[2]; unsigned int dictionary_flags2[2]; int end_type=0; int prefix_type=0; int prefix_stress; char *wordx; char phonemes[N_WORD_PHONEMES]; char prefix_phonemes[N_WORD_PHONEMES]; char unpron_phonemes[N_WORD_PHONEMES]; char end_phonemes[N_WORD_PHONEMES]; char word_copy[N_WORD_BYTES]; char word_copy2[N_WORD_BYTES]; int word_copy_length; char prefix_chars[0x3f + 2]; int found=0; int end_flags; char c_temp; // save a character byte while we temporarily replace it with space int first_char; int last_char = 0; int add_plural_suffix = 0; int prefix_flags = 0; int confirm_prefix; int spell_word; int stress_bits; int emphasize_allcaps = 0; int wflags; int wmark; int was_unpronouncable = 0; WORD_TAB wtab_null[8]; // translate these to get pronunciations of plural 's' suffix (different forms depending on // the preceding letter static char word_zz[4] = {0,'z','z',0}; static char word_iz[4] = {0,'i','z',0}; static char word_ss[4] = {0,'s','s',0}; if(wtab == NULL) { memset(wtab_null, 0, sizeof(wtab_null)); wtab = wtab_null; } wflags = wtab->flags; wmark = wtab->wmark; dictionary_flags[0] = 0; dictionary_flags[1] = 0; dictionary_flags2[0] = 0; dictionary_flags2[1] = 0; dictionary_skipwords = 0; phonemes[0] = 0; unpron_phonemes[0] = 0; prefix_phonemes[0] = 0; end_phonemes[0] = 0; if(tr->data_dictlist == NULL) { // dictionary is not loaded word_phonemes[0] = 0; return(0); } // count the length of the word word1 = word_start; if(*word1 == ' ') word1++; // possibly a dot was replaced by space: $dot wordx = word1; utf8_in(&first_char,wordx); word_length = 0; while((*wordx != 0) && (*wordx != ' ')) { wordx += utf8_in(&last_char,wordx); word_length++; } word_copy_length = wordx - word_start; if(word_copy_length >= N_WORD_BYTES) word_copy_length = N_WORD_BYTES-1; memcpy(word_copy2, word_start, word_copy_length); spell_word = 0; if(option_sayas == SAYAS_KEY) { if(word_length == 1) spell_word = 4; else { // is there a translation for this keyname ? word1--; *word1 = '_'; // prefix keyname with '_' found = LookupDictList(tr, &word1, phonemes, dictionary_flags, 0, wtab); } } // try an initial lookup in the dictionary list, we may find a pronunciation specified, or // we may just find some flags if(option_sayas & 0x10) { // SAYAS_CHAR, SAYAS_GYLPH, or SAYAS_SINGLE_CHAR spell_word = option_sayas & 0xf; // 2,3,4 } else { if(!found) found = LookupDictList(tr, &word1, phonemes, dictionary_flags, FLAG_ALLOW_TEXTMODE, wtab); // the original word if((dictionary_flags[0] & (FLAG_ALLOW_DOT || FLAG_NEEDS_DOT)) && (wordx[1] == '.')) { wordx[1] = ' '; // remove a Dot after this word } if(dictionary_flags[0] & FLAG_TEXTMODE) { first_char = word1[0]; stress_bits = dictionary_flags[0] & 0x7f; found = LookupDictList(tr, &word1, phonemes, dictionary_flags2, 0, wtab); // the text replacement if(dictionary_flags2[0]!=0) { dictionary_flags[0] = dictionary_flags2[0]; dictionary_flags[1] = dictionary_flags2[1]; if(stress_bits != 0) { // keep any stress information from the original word dictionary_flags[0] = (dictionary_flags[0] & ~0x7f) | stress_bits; } } } else if((found==0) && (dictionary_flags[0] & FLAG_SKIPWORDS)) { // grouped words, but no translation. Join the words with hyphens. wordx = word1; ix = 0; while(ix < dictionary_skipwords) { if(*wordx == ' ') { *wordx = '-'; ix++; } wordx++; } } if((word_length == 1) && (dictionary_skipwords == 0)) { // is this a series of single letters separated by dots? if(CheckDottedAbbrev(word1, wtab)) { dictionary_flags[0] = 0; dictionary_flags[1] = 0; spell_word = 1; if(dictionary_skipwords) dictionary_flags[0] = FLAG_SKIPWORDS; } } // if textmode, LookupDictList() replaces word1 by the new text and returns found=0 if(phonemes[0] == phonSWITCH) { // change to another language in order to translate this word strcpy(word_phonemes,phonemes); return(0); } if((wmark > 0) && (wmark < 8)) { // the stressed syllable has been specified in the text (TESTING) dictionary_flags[0] = (dictionary_flags[0] & ~0xf) | wmark; } if(!found && (dictionary_flags[0] & FLAG_ABBREV)) { // the word has $abbrev flag, but no pronunciation specified. Speak as individual letters spell_word = 1; } if(!found && iswdigit(first_char)) { Lookup(tr,"_0lang",word_phonemes); if(word_phonemes[0] == phonSWITCH) return(0); found = TranslateNumber(tr, word1, phonemes, dictionary_flags, wtab, 0); } if(!found & ((wflags & FLAG_UPPERS) != FLAG_FIRST_UPPER)) { // either all upper or all lower case if((tr->langopts.numbers & NUM_ROMAN) || ((tr->langopts.numbers & NUM_ROMAN_CAPITALS) && (wflags & FLAG_ALL_UPPER))) { if((wflags & FLAG_LAST_WORD) || !(wtab[1].flags & FLAG_NOSPACE)) { // don't use Roman number if this word is not separated from the next word (eg. "XLTest") if((found = TranslateRoman(tr, word1, phonemes, wtab)) != 0) dictionary_flags[0] |= FLAG_ABBREV; // prevent emphasis if capitals } } } if((wflags & FLAG_ALL_UPPER) && (word_length > 1)&& iswalpha(first_char)) { if((option_tone_flags & OPTION_EMPHASIZE_ALLCAPS) && !(dictionary_flags[0] & FLAG_ABBREV)) { // emphasize words which are in capitals emphasize_allcaps = FLAG_EMPHASIZED; } else if(!found && !(dictionary_flags[0] & FLAG_SKIPWORDS) && (word_length<4) && (tr->clause_lower_count > 3) && (tr->clause_upper_count <= tr->clause_lower_count)) { // An upper case word in a lower case clause. This could be an abbreviation. spell_word = 1; } } } if(spell_word > 0) { // Speak as individual letters phonemes[0] = 0; end_type = 0; if(SpeakIndividualLetters(tr, word1, phonemes, spell_word) == NULL) { if(word_length > 1) return(FLAG_SPELLWORD); // a mixture of languages, retranslate as individual letters, separated by spaces return(0); } } else if(found == 0) { int posn; int non_initial; int length; // word's pronunciation is not given in the dictionary list, although // dictionary_flags may have ben set there posn = 0; non_initial = 0; length = 999; wordx = word1; while(((length < 3) && (length > 0))|| (word_length > 1 && Unpronouncable(tr, wordx, posn))) { // This word looks "unpronouncable", so speak letters individually until we // find a remainder that we can pronounce. was_unpronouncable = FLAG_WAS_UNPRONOUNCABLE; emphasize_allcaps = 0; if(wordx[0] == '\'') break; if(posn > 0) non_initial = 1; wordx += TranslateLetter(tr, wordx, unpron_phonemes, non_initial); posn++; if(unpron_phonemes[0] == phonSWITCH) { // change to another language in order to translate this word strcpy(word_phonemes,unpron_phonemes); if(strcmp(&unpron_phonemes[1],"en")==0) return(FLAG_SPELLWORD); // _^_en must have been set in TranslateLetter(), not *_rules return(0); } #ifdef deleted p = &wordx[word_length-3]; // this looks wrong. Doesn't consider multi-byte chars. if(memcmp(p,"'s ",3) == 0) { // remove a 's suffix and pronounce this separately (not as an individual letter) add_plural_suffix = 1; p[0] = ' '; p[1] = ' '; last_char = p[-1]; } #endif length=0; while(wordx[length] != ' ') length++; } SetSpellingStress(tr,unpron_phonemes,0,posn); // anything left ? if(*wordx != ' ') { if((unpron_phonemes[0] != 0) && (wordx[0] != '\'')) { // letters which have been spoken individually from affecting the pronunciation of the pronuncable part wordx[-1] = ' '; } // Translate the stem end_type = TranslateRules(tr, wordx, phonemes, N_WORD_PHONEMES, end_phonemes, wflags, dictionary_flags); if(phonemes[0] == phonSWITCH) { // change to another language in order to translate this word strcpy(word_phonemes,phonemes); return(0); } if((phonemes[0] == 0) && (end_phonemes[0] == 0)) { int wc; // characters not recognised, speak them individually utf8_in(&wc, wordx); if((word_length == 1) && IsAlpha(wc)) { if((wordx = SpeakIndividualLetters(tr, wordx, phonemes, spell_word)) == NULL) { return(0); } } } c_temp = wordx[-1]; found = 0; confirm_prefix = 1; for (int loopcount = 0; (loopcount < 50) && (end_type & SUFX_P); loopcount++) { // Found a standard prefix, remove it and retranslate // loopcount guards against an endless loop if(confirm_prefix && !(end_type & SUFX_B)) { int end2; char phonemes2[N_WORD_PHONEMES]; char end_phonemes2[N_WORD_PHONEMES]; // remove any standard suffix and confirm that the prefix is still recognised phonemes2[0] = 0; end2 = TranslateRules(tr, wordx, phonemes2, N_WORD_PHONEMES, end_phonemes2, wflags|FLAG_NO_PREFIX|FLAG_NO_TRACE, dictionary_flags); if(end2) { RemoveEnding(tr, wordx, end2, word_copy); end_type = TranslateRules(tr, wordx, phonemes, N_WORD_PHONEMES, end_phonemes, wflags|FLAG_NO_TRACE, dictionary_flags); memcpy(wordx,word_copy,strlen(word_copy)); if((end_type & SUFX_P) == 0) { // after removing the suffix, the prefix is no longer recognised. // Keep the suffix, but don't use the prefix end_type = end2; strcpy(phonemes,phonemes2); strcpy(end_phonemes,end_phonemes2); if(option_phonemes == 2) { DecodePhonemes(end_phonemes,end_phonemes2); fprintf(f_trans," suffix [%s]\n\n",end_phonemes2); } } confirm_prefix = 0; continue; } } prefix_type = end_type; if(prefix_type & SUFX_V) { tr->expect_verb = 1; // use the verb form of the word } wordx[-1] = c_temp; if((prefix_type & SUFX_B) == 0) { for(ix=(prefix_type & 0xf); ix>0; ix--) // num. of characters to remove { wordx++; while((*wordx & 0xc0) == 0x80) wordx++; // for multibyte characters } } else { pfix = 1; prefix_chars[0] = 0; n_chars = prefix_type & 0x3f; for(ix=0; ix < n_chars; ix++) // num. of bytes to remove { prefix_chars[pfix++] = *wordx++; if((prefix_type & SUFX_B) && (ix == (n_chars-1))) { prefix_chars[pfix-1] = 0; // discard the last character of the prefix, this is the separator character } } prefix_chars[pfix] = 0; } c_temp = wordx[-1]; wordx[-1] = ' '; confirm_prefix = 1; if(prefix_type & SUFX_B) { // SUFX_B is used for Turkish, tr_rules contains " ' (Pb" // examine the prefix part char *wordpf; char prefix_phonemes2[12]; strncpy0(prefix_phonemes2,end_phonemes,sizeof(prefix_phonemes2)); wordpf = &prefix_chars[1]; strcpy(prefix_phonemes, phonemes); // look for stress marker or $abbrev found = LookupDictList(tr, &wordpf, phonemes, dictionary_flags, 0, wtab); if(found) { strcpy(prefix_phonemes, phonemes); } if(dictionary_flags[0] & FLAG_ABBREV) { prefix_phonemes[0] = 0; SpeakIndividualLetters(tr, wordpf, prefix_phonemes, 1); } } else { strcat(prefix_phonemes,end_phonemes); } end_phonemes[0] = 0; end_type = 0; found = LookupDictList(tr, &wordx, phonemes, dictionary_flags2, SUFX_P, wtab); // without prefix if(dictionary_flags[0]==0) { dictionary_flags[0] = dictionary_flags2[0]; dictionary_flags[1] = dictionary_flags2[1]; } else prefix_flags = 1; if(found == 0) { end_type = TranslateRules(tr, wordx, phonemes, N_WORD_PHONEMES, end_phonemes, 0, dictionary_flags); if(phonemes[0] == phonSWITCH) { // change to another language in order to translate this word wordx[-1] = c_temp; strcpy(word_phonemes,phonemes); return(0); } } } if((end_type != 0) && !(end_type & SUFX_P)) { char phonemes2[N_WORD_PHONEMES]; strcpy(phonemes2,phonemes); // The word has a standard ending, re-translate without this ending end_flags = RemoveEnding(tr, wordx, end_type, word_copy); phonemes[0] = 0; if(prefix_phonemes[0] != 0) { // lookup the stem without the prefix removed wordx[-1] = c_temp; found = LookupDictList(tr, &word1, phonemes, dictionary_flags2, end_flags, wtab); // include prefix, but not suffix wordx[-1] = ' '; if(phonemes[0] == phonSWITCH) { // change to another language in order to translate this word memcpy(wordx,word_copy,strlen(word_copy)); strcpy(word_phonemes,phonemes); return(0); } if(dictionary_flags[0]==0) { dictionary_flags[0] = dictionary_flags2[0]; dictionary_flags[1] = dictionary_flags2[1]; } if(found) prefix_phonemes[0] = 0; // matched whole word, don't need prefix now if((found==0) && (dictionary_flags2[0] != 0)) prefix_flags = 1; } if(found == 0) { found = LookupDictList(tr, &wordx, phonemes, dictionary_flags2, end_flags, wtab); // without prefix and suffix if(phonemes[0] == phonSWITCH) { // change to another language in order to translate this word memcpy(wordx,word_copy,strlen(word_copy)); strcpy(word_phonemes,phonemes); return(0); } if(dictionary_flags2[0] & FLAG_ABBREV) { // Removing the suffix leaves a word which should be spoken as individual letters // Not yet implemented } if(dictionary_flags[0]==0) { dictionary_flags[0] = dictionary_flags2[0]; dictionary_flags[1] = dictionary_flags2[1]; } } if(found == 0) { if(end_type & SUFX_Q) { // don't retranslate, use the original lookup result strcpy(phonemes,phonemes2); // language specific changes ApplySpecialAttribute(tr,phonemes,dictionary_flags[0]); } else { if(end_flags & FLAG_SUFX) wflags |= FLAG_SUFFIX_REMOVED; if(end_type & SUFX_A) wflags |= FLAG_SUFFIX_VOWEL; TranslateRules(tr, wordx, phonemes, N_WORD_PHONEMES, NULL, wflags, dictionary_flags); if(phonemes[0] == phonSWITCH) { // change to another language in order to translate this word strcpy(word_phonemes,phonemes); memcpy(wordx,word_copy,strlen(word_copy)); wordx[-1] = c_temp; return(0); } } } if((end_type & SUFX_T) == 0) { // the default is to add the suffix and then determine the word's stress pattern AppendPhonemes(tr,phonemes, N_WORD_PHONEMES, end_phonemes); end_phonemes[0] = 0; } memcpy(wordx,word_copy,strlen(word_copy)); } wordx[-1] = c_temp; } } if((add_plural_suffix) || (wflags & FLAG_HAS_PLURAL)) { // s or 's suffix, append [s], [z] or [Iz] depending on previous letter if(last_char == 'f') TranslateRules(tr, &word_ss[1], phonemes, N_WORD_PHONEMES, NULL, 0, NULL); else if((last_char==0) || (strchr_w("hsx",last_char)==NULL)) TranslateRules(tr, &word_zz[1], phonemes, N_WORD_PHONEMES, NULL, 0, NULL); else TranslateRules(tr, &word_iz[1], phonemes, N_WORD_PHONEMES, NULL, 0, NULL); } wflags |= emphasize_allcaps; /* determine stress pattern for this word */ /******************************************/ prefix_stress = 0; for(p = prefix_phonemes; *p != 0; p++) { if((*p == phonSTRESS_P) || (*p == phonSTRESS_P2)) { prefix_stress = *p; } } if(prefix_flags || (prefix_stress != 0)) { if((tr->langopts.param[LOPT_PREFIXES]) || (prefix_type & SUFX_T)) { char *p; // German, keep a secondary stress on the stem SetWordStress(tr, phonemes, dictionary_flags, 3, 0); // reduce all but the first primary stress ix=0; for(p=prefix_phonemes; *p != 0; p++) { if(*p == phonSTRESS_P) { if(ix==0) ix=1; else *p = phonSTRESS_3; } } #ifdef PLATFORM_WINDOWS sprintf(word_phonemes, "%s%s%s", unpron_phonemes, prefix_phonemes, phonemes); #else snprintf(word_phonemes, sizeof(word_phonemes), "%s%s%s", unpron_phonemes, prefix_phonemes, phonemes); #endif word_phonemes[N_WORD_PHONEMES-1] = 0; SetWordStress(tr, word_phonemes, dictionary_flags, -1, 0); } else { // stress position affects the whole word, including prefix #ifdef PLATFORM_WINDOWS sprintf(word_phonemes, "%s%s%s", unpron_phonemes, prefix_phonemes, phonemes); #else snprintf(word_phonemes, sizeof(word_phonemes), "%s%s%s", unpron_phonemes, prefix_phonemes, phonemes); #endif word_phonemes[N_WORD_PHONEMES-1] = 0; SetWordStress(tr, word_phonemes, dictionary_flags, -1, 0); } } else { if(prefix_phonemes[0] == 0) SetWordStress(tr, phonemes, dictionary_flags, -1, 0); else SetWordStress(tr, phonemes, dictionary_flags, -1, 0); #ifdef PLATFORM_WINDOWS sprintf(word_phonemes, "%s%s%s", unpron_phonemes, prefix_phonemes, phonemes); #else snprintf(word_phonemes, sizeof(word_phonemes), "%s%s%s", unpron_phonemes, prefix_phonemes, phonemes); #endif word_phonemes[N_WORD_PHONEMES-1] = 0; } if(end_phonemes[0] != 0) { // a suffix had the SUFX_T option set, add the suffix after the stress pattern has been determined ix = strlen(word_phonemes); end_phonemes[N_WORD_PHONEMES-1-ix] = 0; // ensure no buffer overflow strcpy(&word_phonemes[ix], end_phonemes); } if(wflags & FLAG_LAST_WORD) { // don't use $brk pause before the last word of a sentence // (but allow it for emphasis, see below dictionary_flags[0] &= ~FLAG_PAUSE1; } #ifdef deleted // but it causes problems if these are not a person name if(tr->translator_name == L('h','u')) { // lang=hu, If the last two words of a clause have capital letters (eg. a person name), unstress the last word. if((wflags & (FLAG_LAST_WORD | FLAG_FIRST_UPPER | FLAG_ALL_UPPER | FLAG_FIRST_WORD)) == (FLAG_LAST_WORD | FLAG_FIRST_UPPER)) { if(((wtab[-1].flags & (FLAG_FIRST_UPPER | FLAG_ALL_UPPER)) == FLAG_FIRST_UPPER) && ((tr->clause_terminator != 0x90028) || (wflags & FLAG_HAS_DOT))) { ChangeWordStress(tr,word_phonemes,3); } } } #endif if((wflags & FLAG_HYPHEN) && (tr->langopts.stress_flags & S_HYPEN_UNSTRESS)) { ChangeWordStress(tr,word_phonemes,3); } else if(wflags & FLAG_EMPHASIZED2) { // A word is indicated in the source text as stressed // Give it stress level 6 (for the intonation module) ChangeWordStress(tr,word_phonemes,6); if(wflags & FLAG_EMPHASIZED) dictionary_flags[0] |= FLAG_PAUSE1; // precede by short pause } else if(wtab[dictionary_skipwords].flags & FLAG_LAST_WORD) { // the word has attribute to stress or unstress when at end of clause if(dictionary_flags[0] & (FLAG_STRESS_END | FLAG_STRESS_END2)) ChangeWordStress(tr,word_phonemes,4); else if((dictionary_flags[0] & FLAG_UNSTRESS_END) && (any_stressed_words)) ChangeWordStress(tr,word_phonemes,3); } // dictionary flags for this word give a clue about which alternative pronunciations of // following words to use. if(end_type & SUFX_F) { // expect a verb form, with or without -s suffix tr->expect_verb = 2; tr->expect_verb_s = 2; } if(dictionary_flags[1] & FLAG_PASTF) { /* expect perfect tense in next two words */ tr->expect_past = 3; tr->expect_verb = 0; tr->expect_noun = 0; } else if(dictionary_flags[1] & FLAG_VERBF) { /* expect a verb in the next word */ tr->expect_verb = 2; tr->expect_verb_s = 0; /* verb won't have -s suffix */ tr->expect_noun = 0; } else if(dictionary_flags[1] & FLAG_VERBSF) { // expect a verb, must have a -s suffix tr->expect_verb = 0; tr->expect_verb_s = 2; tr->expect_past = 0; tr->expect_noun = 0; } else if(dictionary_flags[1] & FLAG_NOUNF) { /* not expecting a verb next */ tr->expect_noun = 2; tr->expect_verb = 0; tr->expect_verb_s = 0; tr->expect_past = 0; } if((wordx[0] != 0) && (!(dictionary_flags[1] & FLAG_VERB_EXT))) { if(tr->expect_verb > 0) tr->expect_verb--; if(tr->expect_verb_s > 0) tr->expect_verb_s--; if(tr->expect_noun >0) tr->expect_noun--; if(tr->expect_past > 0) tr->expect_past--; } if((word_length == 1) && (tr->translator_name == L('e','n')) && iswalpha(first_char) && (first_char != 'i')) { // English Specific !!!! // any single letter before a dot is an abbreviation, except 'I' dictionary_flags[0] |= FLAG_ALLOW_DOT; } if((tr->langopts.param[LOPT_ALT] & 2) && ((dictionary_flags[0] & (FLAG_ALT_TRANS | FLAG_ALT2_TRANS)) != 0)) { ApplySpecialAttribute2(tr,word_phonemes,dictionary_flags[0]); } dictionary_flags[0] |= was_unpronouncable; memcpy(word_start, word_copy2, word_copy_length); return(dictionary_flags[0]); } // end of TranslateWord static void SetPlist2(PHONEME_LIST2 *p, unsigned char phcode) {//========================================================== p->phcode = phcode; p->stresslevel = 0; p->tone_ph = 0; p->synthflags = embedded_flag; p->sourceix = 0; embedded_flag = 0; } static int CountSyllables(unsigned char *phonemes) {//=============================================== int count = 0; int phon; while((phon = *phonemes++) != 0) { if(phoneme_tab[phon]->type == phVOWEL) count++; } return(count); } void Word_EmbeddedCmd() {//==================== // Process embedded commands for emphasis, sayas, and break int embedded_cmd; int value; do { embedded_cmd = embedded_list[embedded_read++]; value = embedded_cmd >> 8; switch(embedded_cmd & 0x1f) { case EMBED_Y: option_sayas = value; break; case EMBED_F: option_emphasis = value; break; case EMBED_B: // break command if(value == 0) pre_pause = 0; // break=none else pre_pause += value; break; } } while(((embedded_cmd & 0x80) == 0) && (embedded_read < embedded_ix)); } // end of Word_EmbeddedCmd int SetTranslator2(const char *new_language) {//========================================= // Set translator2 to a second language int new_phoneme_tab; if((new_phoneme_tab = SelectPhonemeTableName(new_language)) >= 0) { if((translator2 != NULL) && (strcmp(new_language,translator2_language) != 0)) { // we already have an alternative translator, but not for the required language, delete it DeleteTranslator(translator2); translator2 = NULL; } if(translator2 == NULL) { translator2 = SelectTranslator(new_language); strcpy(translator2_language,new_language); if(LoadDictionary(translator2, new_language, 0) != 0) { SelectPhonemeTable(voice->phoneme_tab_ix); // revert to original phoneme table new_phoneme_tab = -1; translator2_language[0] = 0; } } } return(new_phoneme_tab); } // end of SetTranslator2 static int TranslateWord2(Translator *tr, char *word, WORD_TAB *wtab, int pre_pause, int next_pause) {//================================================================================================= int flags=0; int stress; int next_stress; int next_tone=0; unsigned char *p; int srcix; int found_dict_flag; unsigned char ph_code; PHONEME_LIST2 *plist2; PHONEME_TAB *ph; int max_stress; int max_stress_ix=0; int prev_vowel = -1; int pitch_raised = 0; int switch_phonemes = -1; int first_phoneme = 1; int source_ix; int len; int ix; int sylimit; // max. number of syllables in a word to be combined with a preceding preposition const char *new_language; unsigned char bad_phoneme[4]; int word_flags; int word_copy_len; char word_copy[N_WORD_BYTES+1]; char old_dictionary_name[40]; if((f_logespeak != NULL) && (logging_type & 8)) { fprintf(f_logespeak,"WORD: flg=%.5x len=%d '",wtab->flags,wtab->length); for(ix=0; ix<40; ix++) { if(word[ix]==0) break; fputc(word[ix], f_logespeak); } fprintf(f_logespeak,"'\n"); } len = wtab->length; if(len > 31) len = 31; source_ix = (wtab->sourceix & 0x7ff) | (len << 11); // bits 0-10 sourceix, bits 11-15 word length word_flags = wtab[0].flags; if(word_flags & FLAG_EMBEDDED) { embedded_flag = SFLAG_EMBEDDED; Word_EmbeddedCmd(); } if((word[0] == 0) || (word_flags & FLAG_DELETE_WORD)) { // nothing to translate. Add a dummy phoneme to carry any embedded commands if(embedded_flag) { ph_list2[n_ph_list2].phcode = phonEND_WORD; ph_list2[n_ph_list2].stresslevel = 0; ph_list2[n_ph_list2].wordstress = 0; ph_list2[n_ph_list2].tone_ph = 0; ph_list2[n_ph_list2].synthflags = embedded_flag; ph_list2[n_ph_list2].sourceix = 0; n_ph_list2++; embedded_flag = 0; } word_phonemes[0] = 0; return(0); } // after a $pause word attribute, ignore a $pause attribute on the next two words if(tr->prepause_timeout > 0) tr->prepause_timeout--; if((option_sayas & 0xf0) == 0x10) { if(!(word_flags & FLAG_FIRST_WORD)) { // SAYAS_CHARS, SAYAS_GLYPHS, or SAYAS_SINGLECHARS. Pause between each word. pre_pause += 4; } } if(word_flags & FLAG_FIRST_UPPER) { if((option_capitals > 2) && (embedded_ix < N_EMBEDDED_LIST-6)) { // indicate capital letter by raising pitch if(embedded_flag) embedded_list[embedded_ix-1] &= ~0x80; // already embedded command before this word, remove terminator if((pitch_raised = option_capitals) == 3) pitch_raised = 20; // default pitch raise for capitals embedded_list[embedded_ix++] = EMBED_P+0x40+0x80 + (pitch_raised << 8); // raise pitch embedded_flag = SFLAG_EMBEDDED; } } p = (unsigned char *)word_phonemes; if(word_flags & FLAG_PHONEMES) { // The input is in phoneme mnemonics, not language text int c1; char lang_name[12]; if(memcmp(word,"_^_",3)==0) { // switch languages word+=3; for(ix=0;;) { c1 = *word++; if((c1==' ') || (c1==0)) break; lang_name[ix++] = tolower(c1); } lang_name[ix] = 0; if((ix = LookupPhonemeTable(lang_name)) > 0) { SelectPhonemeTable(ix); word_phonemes[0] = phonSWITCH; word_phonemes[1] = ix; word_phonemes[2] = 0; } } else { EncodePhonemes(word,word_phonemes,bad_phoneme); } flags = FLAG_FOUND; } else { int c2; ix = 0; while(((c2 = word_copy[ix] = word[ix]) != ' ') && (c2 != 0) && (ix < N_WORD_BYTES)) ix++; word_copy_len = ix; flags = TranslateWord(translator, word, next_pause, wtab); if(flags & FLAG_SPELLWORD) { // re-translate the word as individual letters, separated by spaces memcpy(word, word_copy, word_copy_len); return(flags); } if((flags & FLAG_COMBINE) && !(wtab[1].flags & FLAG_PHONEMES)) { char *p2; int ok = 1; unsigned int flags2[2]; int c_word2; char ph_buf[N_WORD_PHONEMES]; flags2[0] = 0; sylimit = tr->langopts.param[LOPT_COMBINE_WORDS]; // LANG=cs,sk // combine a preposition with the following word p2 = word; while(*p2 != ' ') p2++; utf8_in(&c_word2, p2+1); // first character of the next word; if(!iswalpha(c_word2)) { ok =0; } if(ok != 0) { strcpy(ph_buf,word_phonemes); flags2[0] = TranslateWord(translator, p2+1, 0, wtab+1); if((flags2[0] & FLAG_WAS_UNPRONOUNCABLE) || (word_phonemes[0] == phonSWITCH)) ok = 0; if(sylimit & 0x100) { // only if the second word has $alt attribute if((flags2[0] & FLAG_ALT_TRANS) == 0) { ok = 0; } } if((sylimit & 0x200) && ((wtab+1)->flags & FLAG_LAST_WORD)) { // not if the next word is end-of-sentence ok = 0; } if(ok == 0) { strcpy(word_phonemes,ph_buf); } } if(ok) { *p2 = '-'; // replace next space by hyphen flags = TranslateWord(translator, word, next_pause, wtab); // translate the combined word if((sylimit > 0) && (CountSyllables(p) > (sylimit & 0x1f))) { // revert to separate words *p2 = ' '; flags = TranslateWord(translator, word, next_pause, wtab); } else { if(flags == 0) flags = flags2[0]; // no flags for the combined word, so use flags from the second word eg. lang-hu "nem december 7-e" flags |= FLAG_SKIPWORDS; dictionary_skipwords = 1; } } } if(p[0] == phonSWITCH) { // this word uses a different language memcpy(word, word_copy, word_copy_len); new_language = (char *)(&p[1]); if(new_language[0]==0) new_language = "en"; strcpy(old_dictionary_name, dictionary_name); switch_phonemes = SetTranslator2(new_language); if(switch_phonemes >= 0) { // re-translate the word using the new translator flags = TranslateWord(translator2, word, next_pause, wtab); // strcpy((char *)p,translator2->word_phonemes); if(p[0] == phonSWITCH) { // the second translator doesn't want to process this word switch_phonemes = -1; } } if(switch_phonemes < 0) { // language code is not recognised or 2nd translator won't translate it p[0] = phonSCHWA; // just say something p[1] = phonSCHWA; p[2] = 0; } // ?? Option to convert from language2 phonemes to the equivalent language1 phonemes // ?? Option to set the word-stress according to language1 rules eg. lang=fr) if(ChangeEquivalentPhonemes(tr, switch_phonemes, (char *)p)) { // Phonemes have been converted from the foreign language to the native language switch_phonemes = -1; } if(switch_phonemes == -1) { strcpy(dictionary_name, old_dictionary_name); SelectPhonemeTable(voice->phoneme_tab_ix); // leave switch_phonemes set, but use the original phoneme table number. // This will suppress LOPT_REGRESSIVE_VOICING switch_phonemes = voice->phoneme_tab_ix; // original phoneme table } } if(!(word_flags & FLAG_HYPHEN)) { if(flags & FLAG_PAUSE1) { if(pre_pause < 1) pre_pause = 1; } if((flags & FLAG_PREPAUSE) && !(word_flags && (FLAG_LAST_WORD | FLAG_FIRST_WORD)) && !(wtab[-1].flags & FLAG_FIRST_WORD) && (tr->prepause_timeout == 0)) { // the word is marked in the dictionary list with $pause if(pre_pause < 4) pre_pause = 4; tr->prepause_timeout = 3; } } if((option_emphasis >= 3) && (pre_pause < 1)) pre_pause = 1; } plist2 = &ph_list2[n_ph_list2]; stress = 0; next_stress = 1; srcix = 0; max_stress = -1; found_dict_flag = 0; if((flags & FLAG_FOUND) && !(flags & FLAG_TEXTMODE)) found_dict_flag = SFLAG_DICTIONARY; while((pre_pause > 0) && (n_ph_list2 < N_PHONEME_LIST-4)) { // add pause phonemes here. Either because of punctuation (brackets or quotes) in the // text, or because the word is marked in the dictionary lookup as a conjunction if(pre_pause > 1) { SetPlist2(&ph_list2[n_ph_list2++],phonPAUSE); pre_pause -= 2; } else { SetPlist2(&ph_list2[n_ph_list2++],phonPAUSE_NOLINK); pre_pause--; } tr->end_stressed_vowel = 0; // forget about the previous word tr->prev_dict_flags = 0; } if((option_capitals==1) && (word_flags & FLAG_FIRST_UPPER)) { SetPlist2(&ph_list2[n_ph_list2++],phonPAUSE_SHORT); SetPlist2(&ph_list2[n_ph_list2++],phonCAPITAL); if((word_flags & FLAG_ALL_UPPER) && IsAlpha(word[1])) { // word > 1 letter and all capitals SetPlist2(&ph_list2[n_ph_list2++],phonPAUSE_SHORT); SetPlist2(&ph_list2[n_ph_list2++],phonCAPITAL); } } if(switch_phonemes >= 0) { // this word uses a different phoneme table SetPlist2(&ph_list2[n_ph_list2],phonSWITCH); ph_list2[n_ph_list2++].tone_ph = switch_phonemes; // temporary phoneme table number } // remove initial pause from a word if it follows a hyphen if((word_flags & FLAG_HYPHEN) && (phoneme_tab[*p]->type == phPAUSE)) p++; if((p[0] == 0) && (embedded_flag)) { // no phonemes. Insert a very short pause to carry an embedded command p[0] = phonPAUSE_VSHORT; p[1] = 0; } while(((ph_code = *p++) != 0) && (n_ph_list2 < N_PHONEME_LIST-4)) { if(ph_code == 255) continue; // unknown phoneme // Add the phonemes to the first stage phoneme list (ph_list2) ph = phoneme_tab[ph_code]; if(ph_code == phonSWITCH) { ph_list2[n_ph_list2].phcode = ph_code; ph_list2[n_ph_list2].sourceix = 0; ph_list2[n_ph_list2].synthflags = embedded_flag; ph_list2[n_ph_list2++].tone_ph = *p++; } else if(ph->type == phSTRESS) { // don't add stress phonemes codes to the list, but give their stress // value to the next vowel phoneme // std_length is used to hold stress number or (if >10) a tone number for a tone language if(ph->program == 0) next_stress = ph->std_length; else { // for tone languages, the tone number for a syllable follows the vowel if(prev_vowel >= 0) { ph_list2[prev_vowel].tone_ph = ph_code; } else { next_tone = ph_code; // no previous vowel, apply to the next vowel } } } else if(ph_code == phonSYLLABIC) { // mark the previous phoneme as a syllabic consonant prev_vowel = n_ph_list2-1; ph_list2[prev_vowel].synthflags |= SFLAG_SYLLABLE; ph_list2[prev_vowel].stresslevel = next_stress; } else if(ph_code == phonLENGTHEN) { ph_list2[n_ph_list2-1].synthflags |= SFLAG_LENGTHEN; } else if(ph_code == phonEND_WORD) { // a || symbol in a phoneme string was used to indicate a word boundary // Don't add this phoneme to the list, but make sure the next phoneme has // a newword indication srcix = source_ix+1; } else if(ph_code == phonX1) { // a language specific action if(tr->langopts.param[LOPT_IT_DOUBLING]) { flags |= FLAG_DOUBLING; } } else { ph_list2[n_ph_list2].phcode = ph_code; ph_list2[n_ph_list2].tone_ph = 0; ph_list2[n_ph_list2].synthflags = embedded_flag | found_dict_flag; embedded_flag = 0; ph_list2[n_ph_list2].sourceix = srcix; srcix = 0; if(ph->type == phVOWEL) { stress = next_stress; next_stress = 1; // default is 'unstressed' if(stress >= 4) { any_stressed_words = 1; } if((prev_vowel >= 0) && (n_ph_list2-1) != prev_vowel) ph_list2[n_ph_list2-1].stresslevel = stress; // set stress for previous consonant ph_list2[n_ph_list2].synthflags |= SFLAG_SYLLABLE; prev_vowel = n_ph_list2; if(stress > max_stress) { max_stress = stress; max_stress_ix = n_ph_list2; } if(next_tone != 0) { ph_list2[n_ph_list2].tone_ph = next_tone; next_tone=0; } } else { if(first_phoneme && tr->langopts.param[LOPT_IT_DOUBLING]) { if(((tr->prev_dict_flags & FLAG_DOUBLING) && (tr->langopts.param[LOPT_IT_DOUBLING] & 1)) || (tr->end_stressed_vowel && (tr->langopts.param[LOPT_IT_DOUBLING] & 2))) { // italian, double the initial consonant if the previous word ends with a // stressed vowel, or is marked with a flag ph_list2[n_ph_list2].synthflags |= SFLAG_LENGTHEN; } } } ph_list2[n_ph_list2].stresslevel = stress; n_ph_list2++; first_phoneme = 0; } } if(word_flags & FLAG_COMMA_AFTER) { SetPlist2(&ph_list2[n_ph_list2++],phonPAUSE_CLAUSE); } // don't set new-word if there is a hyphen before it if((word_flags & FLAG_HYPHEN) == 0) { plist2->sourceix = source_ix; } tr->end_stressed_vowel = 0; if((stress >= 4) && (phoneme_tab[ph_list2[n_ph_list2-1].phcode]->type == phVOWEL)) { tr->end_stressed_vowel = 1; // word ends with a stressed vowel } if(switch_phonemes >= 0) { // this word uses a different phoneme table, now switch back strcpy(dictionary_name, old_dictionary_name); SelectPhonemeTable(voice->phoneme_tab_ix); SetPlist2(&ph_list2[n_ph_list2],phonSWITCH); ph_list2[n_ph_list2++].tone_ph = voice->phoneme_tab_ix; // original phoneme table number } if(pitch_raised > 0) { embedded_list[embedded_ix++] = EMBED_P+0x60+0x80 + (pitch_raised << 8); // lower pitch SetPlist2(&ph_list2[n_ph_list2],phonPAUSE_SHORT); ph_list2[n_ph_list2++].synthflags = SFLAG_EMBEDDED; } if(flags & FLAG_STRESS_END2) { // this's word's stress could be increased later ph_list2[max_stress_ix].synthflags |= SFLAG_PROMOTE_STRESS; } tr->prev_dict_flags = flags; return(flags); } // end of TranslateWord2 static int EmbeddedCommand(unsigned int &source_index) {//=================================================== // An embedded command to change the pitch, volume, etc. // returns number of commands added to embedded_list // pitch,speed,amplitude,expression,reverb,tone,voice,sayas const char *commands = "PSARHTIVYMUBF"; int value = -1; int sign = 0; unsigned char c; char *p; int cmd; c = source[source_index]; if(c == '+') { sign = 0x40; source_index++; } else if(c == '-') { sign = 0x60; source_index++; } if(isdigit(source[source_index])) { value = atoi(&source[source_index]); while(isdigit(source[source_index])) source_index++; } c = source[source_index++]; if(embedded_ix >= (N_EMBEDDED_LIST - 2)) return(0); // list is full if((p = strchr_w(commands,c)) == NULL) return(0); cmd = (p - commands)+1; if(value == -1) { value = embedded_default[cmd]; sign = 0; } if(cmd == EMBED_Y) { option_sayas2 = value; count_sayas_digits = 0; } if(cmd == EMBED_F) { if(value >= 3) word_emphasis = FLAG_EMPHASIZED; else word_emphasis = 0; } embedded_list[embedded_ix++] = cmd + sign + (value << 8); return(1); } // end of EmbeddedCommand static int SubstituteChar(Translator *tr, unsigned int c, unsigned int next_in, int *insert) {//========================================================================================= int ix; unsigned int word; unsigned int new_c, c2, c_lower; int upper_case = 0; static int ignore_next = 0; const unsigned int *replace_chars; if(ignore_next) { ignore_next = 0; return(8); } if(c == 0) return(0); if((replace_chars = tr->langopts.replace_chars) == NULL) return(c); // there is a list of character codes to be substituted with alternative codes if(iswupper(c_lower = c)) { c_lower = towlower(c); upper_case = 1; } new_c = 0; for(ix=0; (word = replace_chars[ix]) != 0; ix+=2) { if(c_lower == (word & 0xffff)) { if((word >> 16) == 0) { new_c = replace_chars[ix+1]; break; } if((word >> 16) == (unsigned int)towlower(next_in)) { new_c = replace_chars[ix+1]; ignore_next = 1; break; } } } if(new_c == 0) return(c); // no substitution if(new_c & 0xffe00000) { // there is a second character to be inserted // don't convert the case of the second character unless the next letter is also upper case c2 = new_c >> 16; if(upper_case && iswupper(next_in)) c2 = towupper(c2); *insert = c2; new_c &= 0xffff; } if(upper_case) new_c = towupper(new_c); return(new_c); } static int TranslateChar(Translator *tr, char *ptr, int prev_in, unsigned int c, unsigned int next_in, int *insert) {//================================================================================================================ // To allow language specific examination and replacement of characters int code; int initial; int medial; int final; int next2; static const unsigned char hangul_compatibility[0x34] = { 0, 0x00,0x01,0xaa,0x02,0xac,0xad,0x03, 0x04,0x05,0xb0,0xb1,0xb2,0xb3,0xb4,0xb4, 0xb6,0x06,0x07,0x08,0xb9,0x09,0x0a,0xbc, 0x0c,0x0d,0x0e,0x0f,0x10,0x11,0x12,0x61, 0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69, 0x6a,0x6b,0x6c,0x6d,0x6e,0x6f,0x70,0x71, 0x72,0x73,0x74,0x75 }; switch(tr->translator_name) { case L('a','f'): case L('n','l'): // look for 'n and replace by a special character (unicode: schwa) if(!iswalpha(prev_in)) { utf8_in(&next2, &ptr[1]); if((c == '\'') && IsSpace(next2)) { if((next_in == 'n') && (tr->translator_name == L('a','f'))) { // n preceded by either apostrophe or U2019 "right single quotation mark" ptr[0] = ' '; // delete the n return(0x0259); // replace ' by unicode schwa character } if((next_in == 'n') || (next_in == 't')) { // Dutch, [@n] and [@t] return(0x0259); // replace ' by unicode schwa character } } } break; case L('k','o'): if(((code = c - 0xac00) >= 0) && (c <= 0xd7af)) { // break a syllable hangul into 2 or 3 individual jamo initial = (code/28)/21; medial = (code/28) % 21; final = code % 28; if(initial == 11) { // null initial c = medial + 0x1161; if(final > 0) *insert = final + 0x11a7; } else { // extact the initial and insert the remainder with a null initial c = initial + 0x1100; *insert = (11*28*21) + (medial*28) + final + 0xac00; } return(c); } else if(((code = c - 0x3130) >= 0) && (code < 0x34)) { // Hangul compatibility jamo return(hangul_compatibility[code] + 0x1100); } break; } return(SubstituteChar(tr,c,next_in,insert)); } void *TranslateClause(Translator *tr, FILE *f_text, const void *vp_input, int *tone_out, char **voice_change) {//========================================================================================================== int ix; int c; int cc; unsigned int source_index=0; unsigned int prev_source_index=0; int source_index_word=0; int prev_in; int prev_out=' '; int prev_out2; int prev_in_save=0; int next_in; int next_in_nbytes; int char_inserted=0; int clause_pause; int pre_pause_add=0; int word_mark = 0; int all_upper_case=FLAG_ALL_UPPER; int finished; int single_quoted; int phoneme_mode = 0; int dict_flags = 0; // returned from dictionary lookup int word_flags; // set here int next_word_flags; int embedded_count = 0; int letter_count = 0; int space_inserted = 0; int syllable_marked = 0; int decimal_sep_count = 0; char *word; char *p; int j, k; int n_digits; int charix_top=0; short charix[N_TR_SOURCE+4]; WORD_TAB words[N_CLAUSE_WORDS]; static char voice_change_name[40]; int word_count=0; // index into words char sbuf[N_TR_SOURCE]; int terminator; int tone; int tone2; if(tr==NULL) { return(NULL); } p_textinput = (unsigned char *)vp_input; p_wchar_input = (wchar_t *)vp_input; embedded_ix = 0; embedded_read = 0; pre_pause = 0; any_stressed_words = 0; if((clause_start_char = count_characters) < 0) clause_start_char = 0; clause_start_word = count_words + 1; for(ix=0; ix> 12) & 0x7; if(tone2 != 0) { // override the tone type tone = tone2; } for(p=source; *p != 0; p++) { if(!isspace2(*p)) { break; } } if(*p == 0) { // No characters except spaces. This is not a sentence. // Don't add this pause, just make up the previous pause to this value; clause_pause -= max_clause_pause; if(clause_pause < 0) clause_pause = 0; terminator &= ~CLAUSE_BIT_SENTENCE; // clear sentence bit max_clause_pause += clause_pause; } else { max_clause_pause = clause_pause; } tr->clause_terminator = terminator; if(new_sentence) { count_sentences++; if(skip_sentences > 0) { skip_sentences--; if(skip_sentences == 0) skipping_text = 0; } } memset(&ph_list2[0],0,sizeof(ph_list2[0])); ph_list2[0].phcode = phonPAUSE_SHORT; n_ph_list2 = 1; tr->prev_last_stress = 0; tr->prepause_timeout = 0; tr->expect_verb=0; tr->expect_noun=0; tr->expect_past=0; tr->expect_verb_s=0; tr->phonemes_repeat_count = 0; tr->end_stressed_vowel=0; tr->prev_dict_flags = 0; word_count = 0; single_quoted = 0; word_flags = 0; next_word_flags = 0; sbuf[0] = 0; sbuf[1] = ' '; sbuf[2] = ' '; ix = 3; prev_in = ' '; words[0].start = ix; words[0].flags = 0; finished = 0; for(j=0; charix[j]<=0; j++); words[0].sourceix = charix[j]; k = 0; while(charix[j] != 0) { // count the number of characters (excluding multibyte continuation bytes) if(charix[j++] != -1) k++; } words[0].length = k; while(!finished && (ix < (int)sizeof(sbuf))&& (n_ph_list2 < N_PHONEME_LIST-4)) { prev_out2 = prev_out; utf8_in2(&prev_out,&sbuf[ix-1],1); // prev_out = sbuf[ix-1]; if(tr->langopts.tone_numbers && IsDigit09(prev_out) && IsAlpha(prev_out2)) { // tone numbers can be part of a word, consider them as alphabetic prev_out = 'a'; } if(prev_in_save != 0) { prev_in = prev_in_save; prev_in_save = 0; } else if(source_index > 0) { utf8_in2(&prev_in,&source[source_index-1],1); // prev_in = source[source_index-1]; } prev_source_index = source_index; if(char_inserted) { c = char_inserted; char_inserted = 0; } else { source_index += utf8_in(&cc,&source[source_index]); // cc = source[source_index++]; c = cc; } next_in_nbytes = utf8_in(&next_in,&source[source_index]); if(c == 0) { finished = 1; c = ' '; } if((c == CTRL_EMBEDDED) || (c == ctrl_embedded)) { // start of embedded command in the text int srcix = source_index-1; if(prev_in != ' ') { c = ' '; prev_in_save = c; source_index--; } else { embedded_count += EmbeddedCommand(source_index); prev_in_save = prev_in; // replace the embedded command by spaces memset(&source[srcix],' ',source_index-srcix); source_index = srcix; continue; } } if((option_sayas2 == SAYAS_KEY) && (c != ' ')) { if((prev_in == ' ') && (next_in == ' ')) option_sayas2 = SAYAS_SINGLE_CHARS; // single character, speak its name c = towlower2(c); } if(phoneme_mode) { all_upper_case = FLAG_PHONEMES; if((c == ']') && (next_in == ']')) { phoneme_mode = 0; source_index++; c = ' '; } } else if((option_sayas2 & 0xf0) == SAYAS_DIGITS) { if(iswdigit(c)) { count_sayas_digits++; if(count_sayas_digits > (option_sayas2 & 0xf)) { // break after the specified number of digits c = ' '; space_inserted = 1; count_sayas_digits = 0; } } else { count_sayas_digits = 0; if(iswdigit(prev_out)) { c = ' '; space_inserted = 1; } } } else if((option_sayas2 & 0x10) == 0) { // speak as words #ifdef deleted if((c == '/') && (tr->langopts.testing & 2) && IsDigit09(next_in) && IsAlpha(prev_out)) { // TESTING, explicit indication of stressed syllable by /2 after the word word_mark = next_in-'0'; source_index++; c = ' '; } #endif if((c == 0x92) || (c == 0xb4) || (c == 0x2019) || (c == 0x2032)) c = '\''; // 'microsoft' quote or sexed closing single quote, or prime - possibly used as apostrophe if(((c == 0x2018) || (c == '?')) && IsAlpha(prev_out) && IsAlpha(next_in)) { // ? between two letters may be a smart-quote replaced by ? c = '\''; } if(c == CHAR_EMPHASIS) { // this character is a marker that the previous word is the focus of the clause c = ' '; word_flags |= FLAG_FOCUS; } if(c == CHAR_COMMA_BREAK) { c = ' '; word_flags |= FLAG_COMMA_AFTER; } c = TranslateChar(tr, &source[source_index], prev_in,c, next_in, &char_inserted); // optional language specific function if(c == 8) continue; // ignore this character if(char_inserted) next_in = char_inserted; // allow certain punctuation within a word (usually only apostrophe) if(!IsAlpha(c) && !IsSpace(c) && (wcschr(tr->punct_within_word,c) == 0)) { if(IsAlpha(prev_out)) { if(tr->langopts.tone_numbers && IsDigit09(c) && !IsDigit09(next_in)) { // allow a tone number as part of the word } else { c = ' '; // ensure we have an end-of-word terminator space_inserted = 1; } } } if(iswdigit(prev_out)) { if(!iswdigit(c) && (c != '.') && (c != ',') && (c != ' ')) { c = ' '; // terminate digit string with a space space_inserted = 1; } } else { if(prev_in != ',') { decimal_sep_count = 0; } } if(c == '[') { if((next_in == '\002') || ((next_in == '[') && option_phoneme_input)) { // "[\002" is used internally to start phoneme mode phoneme_mode = FLAG_PHONEMES; source_index++; continue; } } if(IsAlpha(c)) { if(!IsAlpha(prev_out) || (tr->langopts.ideographs && ((c > 0x3040) || (prev_out > 0x3040)))) { if(wcschr(tr->punct_within_word,prev_out) == 0) letter_count = 0; // don't reset count for an apostrophy within a word if((prev_out != ' ') && (wcschr(tr->punct_within_word,prev_out) == 0)) { // start of word, insert space if not one there already c = ' '; space_inserted = 1; if(!IsBracket(prev_out)) // ?? perhaps only set FLAG_NOSPACE for . - / (hyphenated words, URLs, etc) { next_word_flags |= FLAG_NOSPACE; } } else { if(iswupper(c)) word_flags |= FLAG_FIRST_UPPER; if((prev_out == ' ') && iswdigit(sbuf[ix-2]) && !iswdigit(prev_in)) { // word, following a number, but with a space between // Add an extra space, to distinguish "2 a" from "2a" sbuf[ix++] = ' '; words[word_count].start++; } } } letter_count++; if(iswupper(c)) { c = towlower2(c); if((j = tr->langopts.param[LOPT_CAPS_IN_WORD]) > 0) { if((j == 2) && (syllable_marked == 0)) { char_inserted = c; c = 0x2c8; // stress marker syllable_marked = 1; } } else { if(iswlower(prev_in)) { c = ' '; // lower case followed by upper case, treat as new word space_inserted = 1; prev_in_save = c; // next_word_flags |= FLAG_NOSPACE; // problem: prevents FLAG_HAS_DOT being set } else if((c != ' ') && iswupper(prev_in) && iswlower(next_in)) { int next2_in; utf8_in(&next2_in,&source[source_index + next_in_nbytes]); if(IsAlpha(next2_in)) { // changing from upper to lower case, start new word at the last uppercase, if 3 or more letters c = ' '; space_inserted = 1; prev_in_save = c; next_word_flags |= FLAG_NOSPACE; } } } } else { if((all_upper_case) && (letter_count > 2)) { if((c == 's') && (next_in==' ')) { c = ' '; all_upper_case |= FLAG_HAS_PLURAL; if(sbuf[ix-1] == '\'') sbuf[ix-1] = ' '; } else all_upper_case = 0; // current word contains lower case letters, not "'s" } else all_upper_case = 0; } } else if(c=='-') { if(!IsSpace(prev_in) && IsAlpha(next_in)) { if(prev_out != ' ') { // previous 'word' not yet ended (not alpha or numeric), start new word now. c = ' '; space_inserted = 1; } else { // '-' between two letters is a hyphen, treat as a space word_flags |= FLAG_HYPHEN; if(word_count > 0) words[word_count-1].flags |= FLAG_HYPHEN_AFTER; c = ' '; } } else if((prev_in==' ') && (next_in==' ')) { // ' - ' dash between two spaces, treat as pause c = ' '; pre_pause_add = 4; } else if(next_in=='-') { // double hyphen, treat as pause source_index++; c = ' '; pre_pause_add = 4; } else if((prev_out == ' ') && IsAlpha(sbuf[ix-2]) && !IsAlpha(prev_in)) { // insert extra space between a word + space + hyphen, to distinguish 'a -2' from 'a-2' sbuf[ix++] = ' '; words[word_count].start++; } } else if(c == '.') { if(prev_out == '.') { // multiple dots, separate by spaces. Note >3 dots has been replaced by elipsis c = ' '; space_inserted = 1; } else if((word_count > 0) && !(words[word_count-1].flags & FLAG_NOSPACE) && IsAlpha(prev_in)) { // dot after a word, with space following, probably an abbreviation words[word_count-1].flags |= FLAG_HAS_DOT; if(IsSpace(next_in) || (next_in == '-')) c = ' '; // remove the dot if it's followed by a space or hyphen, so that it's not pronounced } } else if(c == '\'') { if(((prev_in == '.') || iswalnum(prev_in)) && IsAlpha(next_in)) { // between two letters, or in an abbreviation (eg. u.s.a.'s). Consider the apostrophe as part of the word single_quoted = 0; } else if((wcschr(tr->char_plus_apostrophe,prev_in) != 0) && (prev_out2 == ' ')) { // consider single character plus apostrophe as a word single_quoted = 0; if(next_in == ' ') { source_index++; // skip following space } } else { if((prev_out == 's') && (single_quoted==0)) { // looks like apostrophe after an 's' c = ' '; } else { if(IsSpace(prev_out)) single_quoted = 1; else single_quoted = 0; pre_pause_add = 4; // single quote c = ' '; } } } else #ifdef deleted // Brackets are now recognised in TranslateRules() if(IsBracket(c)) { pre_pause_add = 4; c = ' '; } else #endif if(lookupwchar(breaks,c) != 0) { c = ' '; // various characters to treat as space } else if(iswdigit(c)) { if(tr->langopts.tone_numbers && IsAlpha(prev_out) && !IsDigit(next_in)) { } else if((prev_out != ' ') && !iswdigit(prev_out)) { if((prev_out != tr->langopts.decimal_sep) || ((decimal_sep_count > 0) && (tr->langopts.decimal_sep == ','))) { c = ' '; space_inserted = 1; } else { decimal_sep_count = 1; } } else if((prev_out == ' ') && IsAlpha(sbuf[ix-2]) && !IsAlpha(prev_in)) { // insert extra space between a word and a number, to distinguish 'a 2' from 'a2' sbuf[ix++] = ' '; words[word_count].start++; } } } if(IsSpace(c)) { if(prev_out == ' ') { word_flags |= FLAG_MULTIPLE_SPACES; continue; // multiple spaces } if((cc == 0x09) || (cc == 0x0a)) { next_word_flags |= FLAG_MULTIPLE_SPACES; // tab or newline, not a simple space } if(space_inserted) { // count the number of characters since the start of the word j = 0; k = source_index - 1; while((k >= source_index_word) && (charix[k] != 0)) { if(charix[k] > 0) // don't count initial bytes of multi-byte character j++; k--; } words[word_count].length = j; } source_index_word = source_index; // end of 'word' sbuf[ix++] = ' '; if((word_count < N_CLAUSE_WORDS-1) && (ix > words[word_count].start)) { if(embedded_count > 0) { // there are embedded commands before this word embedded_list[embedded_ix-1] |= 0x80; // terminate list of commands for this word words[word_count].flags |= FLAG_EMBEDDED; embedded_count = 0; } words[word_count].pre_pause = pre_pause; words[word_count].flags |= (all_upper_case | word_flags | word_emphasis); words[word_count].wmark = word_mark; if(pre_pause > 0) { // insert an extra space before the word, to prevent influence from previous word across the pause for(j=ix; j>words[word_count].start; j--) { sbuf[j] = sbuf[j-1]; } sbuf[j] = ' '; words[word_count].start++; ix++; } word_count++; words[word_count].start = ix; words[word_count].flags = 0; for(j=source_index; charix[j] <= 0; j++); // skip blanks words[word_count].sourceix = charix[j]; k = 0; while(charix[j] != 0) { // count the number of characters (excluding multibyte continuation bytes) if(charix[j++] != -1) k++; } words[word_count].length = k; word_flags = next_word_flags; next_word_flags = 0; pre_pause = 0; word_mark = 0; all_upper_case = FLAG_ALL_UPPER; syllable_marked = 0; } if(space_inserted) { source_index = prev_source_index; // rewind to the previous character char_inserted = 0; space_inserted = 0; } } else { if((ix < (N_TR_SOURCE - 4))) ix += utf8_out(c,&sbuf[ix]); // sbuf[ix++] = c; } if(pre_pause_add > pre_pause) pre_pause = pre_pause_add; pre_pause_add = 0; } if((word_count==0) && (embedded_count > 0)) { // add a null 'word' to carry the embedded command flag embedded_list[embedded_ix-1] |= 0x80; words[word_count].flags |= FLAG_EMBEDDED; word_count = 1; } tr->clause_end = &sbuf[ix-1]; sbuf[ix] = 0; words[0].pre_pause = 0; // don't add extra pause at beginning of clause words[word_count].pre_pause = 8; if(word_count > 0) { ix = word_count-1; while((ix > 0) && (IsBracket(sbuf[words[ix].start]))) ix--; // the last word is a bracket, mark the previous word as last words[ix].flags |= FLAG_LAST_WORD; // FLAG_NOSPACE check to avoid recognizing .mr -mr if((terminator & CLAUSE_DOT) && !(words[word_count-1].flags & FLAG_NOSPACE)) words[word_count-1].flags |= FLAG_HAS_DOT; } words[0].flags |= FLAG_FIRST_WORD; for(ix=0; ix < word_count; ix++) { int nx; int c_temp; char *pn; char *pw; int nw; char number_buf[150]; WORD_TAB num_wtab[50]; // copy of 'words', when splitting numbers into parts // start speaking at a specified word position in the text? count_words++; if(skip_words > 0) { skip_words--; if(skip_words == 0) skipping_text = 0; } if(skipping_text) continue; // digits should have been converted to Latin alphabet ('0' to '9') word = pw = &sbuf[words[ix].start]; if(iswdigit(word[0]) && (tr->langopts.break_numbers != BREAK_THOUSANDS)) { // Languages with 100000 numbers. Remove thousands separators so that we can insert them again later pn = number_buf; while(pn < &number_buf[sizeof(number_buf)-20]) { if(iswdigit(*pw)) { *pn++ = *pw++; } else if((*pw == tr->langopts.thousands_sep) && (pw[1] == ' ') && iswdigit(pw[2]) && (pw[3] != ' ') && (pw[4] != ' ')) // don't allow only 1 or 2 digits in the final part { pw += 2; ix++; // skip "word" } else { nx = pw - word; memset(word,' ',nx); nx = pn - number_buf; memcpy(word,number_buf,nx); break; } } pw = word; } for(n_digits=0; iswdigit(word[n_digits]); n_digits++); // count consecutive digits if(n_digits > 4) { // word is entirely digits, insert commas and break into 3 digit "words" number_buf[0] = ' '; pn = &number_buf[1]; nx = n_digits; nw = 0; if((n_digits > tr->langopts.max_digits) || (word[0] == '0')) words[ix].flags |= FLAG_INDIVIDUAL_DIGITS; while(pn < &number_buf[sizeof(number_buf)-20]) { if(!isdigit(c = *pw++) && (c != tr->langopts.decimal_sep)) break; *pn++ = c; if((--nx > 0) && (tr->langopts.break_numbers & (1 << nx))) { memcpy(&num_wtab[nw++], &words[ix], sizeof(WORD_TAB)); // copy the 'words' entry for each word of numbers if(tr->langopts.thousands_sep != ' ') { *pn++ = tr->langopts.thousands_sep; } *pn++ = ' '; if(tr->langopts.break_numbers & (1 << (nx-1))) { // the next group only has 1 digits (i.e. NUM2_10000), make it three *pn++ = '0'; *pn++ = '0'; } if(tr->langopts.break_numbers & (1 << (nx-2))) { // the next group only has 2 digits (i.e. NUM2_10000), make it three *pn++ = '0'; } } } pw--; memcpy(&num_wtab[nw], &words[ix], sizeof(WORD_TAB)*2); // the original number word, and the word after it for(j=1; j<=nw; j++) { num_wtab[j].flags &= ~(FLAG_MULTIPLE_SPACES | FLAG_EMBEDDED); // don't use these flags for subsequent parts when splitting a number } // include the next few characters, in case there are an ordinal indicator or other suffix memcpy(pn, pw, 16); pn[16] = 0; nw = 0; for(pw = &number_buf[1]; pw < pn;) { // keep wflags for each part, for FLAG_HYPHEN_AFTER dict_flags = TranslateWord2(tr, pw, &num_wtab[nw++], words[ix].pre_pause,0 ); while(*pw++ != ' '); words[ix].pre_pause = 0; } } else { pre_pause = 0; dict_flags = TranslateWord2(tr, word, &words[ix], words[ix].pre_pause, words[ix+1].pre_pause); if(pre_pause > words[ix+1].pre_pause) { words[ix+1].pre_pause = pre_pause; pre_pause = 0; } if(dict_flags & FLAG_SPELLWORD) { // redo the word, speaking single letters for(pw = word; *pw != ' ';) { memset(number_buf,' ',9); nx = utf8_in(&c_temp, pw); memcpy(&number_buf[2],pw,nx); TranslateWord2(tr, &number_buf[2], &words[ix], 0, 0 ); pw += nx; } } if((dict_flags & (FLAG_ALLOW_DOT | FLAG_NEEDS_DOT)) && (ix == word_count - 1 - dictionary_skipwords) && (terminator & CLAUSE_DOT)) { // probably an abbreviation such as Mr. or B. rather than end of sentence clause_pause = 10; tone = 4; } } if(dict_flags & FLAG_SKIPWORDS) { // dictionary indicates skip next word(s) while(dictionary_skipwords > 0) { words[ix+dictionary_skipwords].flags |= FLAG_DELETE_WORD; dictionary_skipwords--; } } } if(embedded_read < embedded_ix) { // any embedded commands not yet processed? Word_EmbeddedCmd(); } for(ix=0; ix<2; ix++) { // terminate the clause with 2 PAUSE phonemes PHONEME_LIST2 *p2; p2 = &ph_list2[n_ph_list2 + ix]; p2->phcode = phonPAUSE; p2->stresslevel = 0; p2->sourceix = source_index; p2->synthflags = 0; } n_ph_list2 += 2; if(count_words == 0) { clause_pause = 0; } if(Eof() && ((word_count == 0) || (option_endpause==0))) { clause_pause = 10; } MakePhonemeList(tr, clause_pause, new_sentence); if(embedded_count) // ???? is this needed { phoneme_list[n_phoneme_list-2].synthflags = SFLAG_EMBEDDED; embedded_list[embedded_ix-1] |= 0x80; embedded_list[embedded_ix] = 0x80; } prev_clause_pause = clause_pause; *tone_out = tone; new_sentence = 0; if(terminator & CLAUSE_BIT_SENTENCE) { new_sentence = 1; // next clause is a new sentence } if(voice_change != NULL) { // return new voice name if an embedded voice change command terminated the clause if(terminator & CLAUSE_BIT_VOICE) *voice_change = voice_change_name; else *voice_change = NULL; } if(Eof() || (vp_input==NULL)) return(NULL); if(option_multibyte == espeakCHARS_WCHAR) return((void *)p_wchar_input); else return((void *)p_textinput); } // end of TranslateClause void InitText(int control) {//======================= count_sentences = 0; count_words = 0; end_character_position = 0; skip_sentences = 0; skip_marker[0] = 0; skip_words = 0; skip_characters = 0; skipping_text = 0; new_sentence = 1; prev_clause_pause = 0; option_sayas = 0; option_sayas2 = 0; option_emphasis = 0; word_emphasis = 0; embedded_flag = 0; InitText2(); if((control & espeakKEEP_NAMEDATA) == 0) { InitNamedata(); } } sources_5316/external/espeak/wave.h0000644000176700017670000000252411721443315016134 0ustar paulpaul#ifndef WAVE_H #define WAVE_H #ifndef PLATFORM_DOS #include "stdint.h" #endif extern int option_device_number; extern void wave_init(int samplerate); // TBD: the arg could be "alsa", "oss",... extern void* wave_open(const char* the_api); extern size_t wave_write(void* theHandler, char* theMono16BitsWaveBuffer, size_t theSize); extern int wave_close(void* theHandler); extern void wave_flush(void* theHandler); extern int wave_is_busy(void* theHandler); extern void wave_terminate(); extern uint32_t wave_get_read_position(void* theHandler); extern uint32_t wave_get_write_position(void* theHandler); // Supply the remaining time in ms before the sample is played // (or 0 if the event has been already played). // sample: sample identifier // time: supplied value in ms // // return 0 if ok or -1 otherwise (stream not opened). extern int wave_get_remaining_time(uint32_t sample, uint32_t* time); // set the callback which informs if the output is still enabled. // Helpful if a new sample is waiting for free space whereas sound must be stopped. typedef int (t_wave_callback)(void); extern void wave_set_callback_is_output_enabled(t_wave_callback* cb); // general functions extern void clock_gettime2(struct timespec *ts); extern void add_time_in_ms(struct timespec *ts, int time_in_ms); // for tests extern void *wave_test_get_write_buffer(); #endif sources_5316/external/espeak/debug.cpp0000664000176700017670000000243311674622653016627 0ustar paulpaul#include #include #include "speech.h" #include "debug.h" #ifdef DEBUG_ENABLED #include #include static FILE* fd_log=NULL; static const char* FILENAME="/tmp/espeak.log"; void debug_init() { if((fd_log = fopen(FILENAME,"a")) != NULL) setvbuf(fd_log, NULL, _IONBF, 0); } void debug_enter(const char* text) { struct timeval tv; gettimeofday(&tv, NULL); // fd_log = fopen(FILENAME,"a"); if (!fd_log) { debug_init(); } if (fd_log) { fprintf(fd_log, "%03d.%03dms > ENTER %s\n",(int)(tv.tv_sec%1000), (int)(tv.tv_usec/1000), text); // fclose(fd_log); } } void debug_show(const char *format, ...) { va_list args; va_start(args, format); // fd_log = fopen(FILENAME,"a"); if (!fd_log) { debug_init(); } if (fd_log) { vfprintf(fd_log, format, args); // fclose(fd_log); } va_end(args); } void debug_time(const char* text) { struct timeval tv; gettimeofday(&tv, NULL); // fd_log = fopen(FILENAME,"a"); if (!fd_log) { debug_init(); } if (fd_log) { fprintf(fd_log, "%03d.%03dms > %s\n",(int)(tv.tv_sec%1000), (int)(tv.tv_usec/1000), text); // fclose(fd_log); } } #endif sources_5316/external/espeak/espeakdata_FileInMemory.h0000664000176700017670000000343311723710247021720 0ustar paulpaul#ifndef _espeakdata_FileInMemory_h_ #define _espeakdata_FileInMemory_h_ /* espeakdata_FileInMemory.h * Copyright (C) David Weenink 2012 * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "FileInMemory.h" #include "Table.h" extern FilesInMemory espeakdata_phons; extern FilesInMemory espeakdata_dicts; extern FilesInMemory espeakdata_voices; extern FilesInMemory espeakdata_variants; FilesInMemory create_espeakdata_phons (); FilesInMemory create_espeakdata_dicts (); FilesInMemory create_espeakdata_voices (); FilesInMemory create_espeakdata_variants (); extern Strings espeakdata_voices_names; extern Strings espeakdata_variants_names; void espeakdata_praat_init (); const char * espeakdata_get_voicedata (const char *data, long ndata, char *buf, long nbuf, long *index); Table espeakdata_voices_to_Table (FilesInMemory me); Strings espeakdata_voices_getNames (Table me, long column); // mask the char / wchar_t char * espeakdata_get_dict_data (const char *name, unsigned int *size); const char * espeakdata_get_voice (const char *vname, long *numberOfBytes); const char * espeakdata_get_voiceVariant (const char *vname, long *numberOfBytes); #endif sources_5316/external/espeak/voice.h0000644000176700017670000000712211721443315016276 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2007 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ typedef struct { char v_name[40]; int phoneme_tab_ix; // phoneme table number int pitch_base; // Hz<<12 int pitch_range; // standard = 0x1000 int speedf1; int speedf2; int speedf3; int speed_percent; // adjust the WPM speed by this percentage int flutter; int roughness; int echo_delay; int echo_amp; int n_harmonic_peaks; // highest formant which is formed from adding harmonics int peak_shape; // alternative shape for formant peaks (0=standard 1=squarer) int voicing; // 100% = 64, level of formant-synthesized sound int formant_factor; // adjust nominal formant frequencies by this because of the voice's pitch (256ths) int consonant_amp; // amplitude of unvoiced consonants int consonant_ampv; // amplitude of the noise component of voiced consonants int samplerate; int klattv[8]; // parameters used by Wavegen short freq[N_PEAKS]; // 100% = 256 short height[N_PEAKS]; // 100% = 256 short width[N_PEAKS]; // 100% = 256 short freqadd[N_PEAKS]; // Hz // copies without temporary adjustments from embedded commands short freq2[N_PEAKS]; // 100% = 256 short height2[N_PEAKS]; // 100% = 256 short width2[N_PEAKS]; // 100% = 256 int breath[N_PEAKS]; // amount of breath for each formant. breath[0] indicates whether any are set. int breathw[N_PEAKS]; // width of each breath formant // This table provides the opportunity for tone control. // Adjustment of harmonic amplitudes, steps of 8Hz // value of 128 means no change #define N_TONE_ADJUST 1000 unsigned char tone_adjust[N_TONE_ADJUST]; // 8Hz steps * 1000 = 8kHz } voice_t; // percentages shown to user, ix=N_PEAKS means ALL peaks extern USHORT voice_pcnt[N_PEAKS+1][3]; extern espeak_VOICE current_voice_selected; extern voice_t *voice; extern int tone_points[12]; const char *SelectVoice(espeak_VOICE *voice_select, int *found); espeak_VOICE *SelectVoiceByName(espeak_VOICE **voices, const char *name); voice_t *LoadVoice(const char *voice_name, int control); voice_t *LoadVoiceVariant(const char *voice_name, int variant); void DoVoiceChange(voice_t *v); void WVoiceChanged(voice_t *wvoice); void WavegenSetVoice(voice_t *v); void ReadTonePoints(char *string, int *tone_pts); void VoiceReset(int control); sources_5316/external/espeak/dictionary.cpp0000664000176700017670000025336711723710247017714 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2011 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "translate.h" int dictionary_skipwords; char dictionary_name[40]; extern char *print_dictionary_flags(unsigned int *flags); extern char *DecodeRule(const char *group_chars, int group_length, char *rule, int control); // accented characters which indicate (in some languages) the start of a separate syllable //static const unsigned short diereses_list[7] = {L'ä',L'ë',L'ï',L'ö',L'ü',L'ÿ',0}; static const unsigned short diereses_list[7] = {0xe4,0xeb,0xef,0xf6,0xfc,0xff,0}; // convert characters to an approximate 7 bit ascii equivalent // used for checking for vowels (up to 0x259=schwa) #define N_REMOVE_ACCENT 0x25e static unsigned char remove_accent[N_REMOVE_ACCENT] = { 'a','a','a','a','a','a','a','c','e','e','e','e','i','i','i','i', // 0c0 'd','n','o','o','o','o','o', 0, 'o','u','u','u','u','y','t','s', // 0d0 'a','a','a','a','a','a','a','c','e','e','e','e','i','i','i','i', // 0e0 'd','n','o','o','o','o','o', 0 ,'o','u','u','u','u','y','t','y', // 0f0 'a','a','a','a','a','a','c','c','c','c','c','c','c','c','d','d', // 100 'd','d','e','e','e','e','e','e','e','e','e','e','g','g','g','g', // 110 'g','g','g','g','h','h','h','h','i','i','i','i','i','i','i','i', // 120 'i','i','i','i','j','j','k','k','k','l','l','l','l','l','l','l', // 130 'l','l','l','n','n','n','n','n','n','n','n','n','o','o','o','o', // 140 'o','o','o','o','r','r','r','r','r','r','s','s','s','s','s','s', // 150 's','s','t','t','t','t','t','t','u','u','u','u','u','u','u','u', // 160 'u','u','u','u','w','w','y','y','y','z','z','z','z','z','z','s', // 170 'b','b','b','b', 0, 0, 'o','c','c','d','d','d','d','d','e','e', // 180 'e','f','f','g','g','h','i','i','k','k','l','l','m','n','n','o', // 190 'o','o','o','o','p','p','y', 0, 0, 's','s','t','t','t','t','u', // 1a0 'u','u','v','y','y','z','z','z','z','z','z','z', 0, 0, 0, 'w', // 1b0 't','t','t','k','d','d','d','l','l','l','n','n','n','a','a','i', // 1c0 'i','o','o','u','u','u','u','u','u','u','u','u','u','e','a','a', // 1d0 'a','a','a','a','g','g','g','g','k','k','o','o','o','o','z','z', // 1e0 'j','d','d','d','g','g','w','w','n','n','a','a','a','a','o','o', // 1f0 'a','a','a','a','e','e','e','e','i','i','i','i','o','o','o','o', // 200 'r','r','r','r','u','u','u','u','s','s','t','t','y','y','h','h', // 210 'n','d','o','o','z','z','a','a','e','e','o','o','o','o','o','o', // 220 'o','o','y','y','l','n','t','j','d','q','a','c','c','l','t','s', // 230 'z', 0, 0, 'b','u','v','e','e','j','j','q','q','r','r','y','y', // 240 'a','a','a','b','o','c','d','d','e','e','e','e','e','e' }; void strncpy0(char *to,const char *from, int size) {//=============================================== // strcpy with limit, ensures a zero terminator strncpy(to,from,size); to[size-1] = 0; } int Reverse4Bytes(int word) {//======================== // reverse the order of bytes from little-endian to big-endian #ifdef ARCH_BIG int ix; int word2 = 0; for(ix=0; ix<=24; ix+=8) { word2 = word2 << 8; word2 |= (word >> ix) & 0xff; } return(word2); #else return(word); #endif } int LookupMnem(MNEM_TAB *table, const char *string) {//================================================ while(table->mnem != NULL) { if(strcmp(string,table->mnem)==0) return(table->value); table++; } return(table->value); } //============================================================================================= // Read pronunciation rules and pronunciation lookup dictionary // //============================================================================================= static void InitGroups(Translator *tr) {//=================================== /* Called after dictionary 1 is loaded, to set up table of entry points for translation rule chains for single-letters and two-letter combinations */ int ix; char *p; char *p_name; unsigned int *pw; unsigned char c, c2; int len; tr->n_groups2 = 0; for(ix=0; ix<256; ix++) { tr->groups1[ix]=NULL; tr->groups2_count[ix]=0; tr->groups2_start[ix]=255; // indicates "not set" } memset(tr->letterGroups,0,sizeof(tr->letterGroups)); memset(tr->groups3,0,sizeof(tr->groups3)); p = tr->data_dictrules; while(*p != 0) { if(*p != RULE_GROUP_START) { fprintf(stderr,"Bad rules data in '%s_dict' at 0x%x\n",dictionary_name,(unsigned int)(p - tr->data_dictrules)); break; } p++; if(p[0] == RULE_REPLACEMENTS) { // pw = (unsigned int *)(((long64)p+4) & ~3); // advance to next word boundary pw = (unsigned int *) align_address <4, char> (p+4); // advance to next word boundary tr->langopts.replace_chars = pw; while(pw[0] != 0) { pw += 2; // find the end of the replacement list, each entry is 2 words. } p = (char *)(pw+1); #ifdef ARCH_BIG pw = (unsigned int *)(tr->langopts.replace_chars); while(*pw != 0) { *pw = Reverse4Bytes(*pw); pw++; *pw = Reverse4Bytes(*pw); pw++; } #endif continue; } if(p[0] == RULE_LETTERGP2) { ix = p[1] - 'A'; p += 2; if((ix >= 0) && (ix < N_LETTER_GROUPS)) { tr->letterGroups[ix] = p; } } else { len = strlen(p); p_name = p; c = p_name[0]; c2 = p_name[1]; p += (len+1); if(len == 1) { tr->groups1[c] = p; } else if(len == 0) { tr->groups1[0] = p; } else if(c == 1) { // index by offset from letter base tr->groups3[c2 - 1] = p; } else { if(tr->groups2_start[c] == 255) tr->groups2_start[c] = tr->n_groups2; tr->groups2_count[c]++; tr->groups2[tr->n_groups2] = p; tr->groups2_name[tr->n_groups2++] = (c + (c2 << 8)); } } // skip over all the rules in this group while(*p != RULE_GROUP_END) { p += (strlen(p) + 1); } p++; } } // end of InitGroups #ifdef DATA_FROM_SOURCECODE_FILES int LoadDictionary(Translator *tr, const char *name, int no_error) { strcpy (dictionary_name, name); // currently loaded dictionary name strcpy (tr -> dictionary_name, name); // Load a pronunciation data file into memory // bytes 0-3: offset to rules data // bytes 4-7: number of hash table entries if(tr -> data_dictlist != NULL) { Free (tr -> data_dictlist); tr -> data_dictlist = NULL; } unsigned int size; tr -> data_dictlist = (char *) espeakdata_get_dict_data (name, &size); if (tr -> data_dictlist == 0) { return 1; } int *pw = reinterpret_cast (tr -> data_dictlist); int length = Reverse4Bytes (pw[1]); // was int really written with 4 bytes? if (size <= (N_HASH_DICT + sizeof(int)*2)) { Melder_error_ (L"Empty _dict: ", Melder_utf8ToWcs(name), L"_dict."); return(2); } if((Reverse4Bytes(pw[0]) != N_HASH_DICT) || (length <= 0) || (length > 0x8000000)) { Melder_error_ (L"Bad data in dict: ", Melder_utf8ToWcs(name), L" ", Melder_integer (Reverse4Bytes(pw[0])), L" ", Melder_integer (length)); return (2); } tr -> data_dictrules = &(tr->data_dictlist[length]); // set up indices into data_dictrules InitGroups(tr); if (tr -> groups1[0] == NULL) { Melder_error_ (L"Error in ", Melder_peekUtf8ToWcs (name), L"_rules, no default rule group."); } // set up hash table for data_dictlist char *p = &(tr -> data_dictlist[8]); for (int hash = 0; hash < N_HASH_DICT; hash++) { tr -> dict_hashtab[hash] = p; while ((length = *p) != 0) { p += length; } p++; // skip over the zero which terminates the list for this hash value } return (0); } // end of LoadDictionary #else int LoadDictionary(Translator *tr, const char *name, int no_error) {//=============================================================== int hash; char *p; int *pw; int length; FILE *f; unsigned int size; char fname[sizeof(path_home)+20]; strcpy(dictionary_name,name); // currently loaded dictionary name strcpy(tr->dictionary_name, name); // Load a pronunciation data file into memory // bytes 0-3: offset to rules data // bytes 4-7: number of hash table entries sprintf(fname,"%s%c%s_dict",path_home,PATHSEP,name); size = GetFileLength(fname); if(tr->data_dictlist != NULL) { Free(tr->data_dictlist); tr->data_dictlist = NULL; } f = fopen(fname,"rb"); if((f == NULL) || (size <= 0)) { if(no_error == 0) { fprintf(stderr,"Can't read dictionary file: '%s'\n",fname); } return(1); } tr->data_dictlist = Alloc(size); size = fread(tr->data_dictlist,1,size,f); fclose(f); pw = (int *)(tr->data_dictlist); length = Reverse4Bytes(pw[1]); if(size <= (N_HASH_DICT + sizeof(int)*2)) { fprintf(stderr,"Empty _dict file: '%s\n",fname); return(2); } if((Reverse4Bytes(pw[0]) != N_HASH_DICT) || (length <= 0) || (length > 0x8000000)) { fprintf(stderr,"Bad data: '%s' (%x length=%x)\n",fname,Reverse4Bytes(pw[0]),length); return(2); } tr->data_dictrules = &(tr->data_dictlist[length]); // set up indices into data_dictrules InitGroups(tr); if(tr->groups1[0] == NULL) { fprintf(stderr,"Error in %s_rules, no default rule group\n",name); } // set up hash table for data_dictlist p = &(tr->data_dictlist[8]); for(hash=0; hashdict_hashtab[hash] = p; while((length = *p) != 0) { p += length; } p++; // skip over the zero which terminates the list for this hash value } return(0); } // end of LoadDictionary #endif int HashDictionary(const char *string) //==================================== /* Generate a hash code from the specified string This is used to access the dictionary_2 word-lookup dictionary */ { int c; int chars=0; int hash=0; while((c = (*string++ & 0xff)) != 0) { hash = hash * 8 + c; hash = (hash & 0x3ff) ^ (hash >> 8); /* exclusive or */ chars++; } return((hash+chars) & 0x3ff); // a 10 bit hash code } // end of HashDictionary //============================================================================================= // Translate between internal representation of phonemes and a mnemonic form for display // //============================================================================================= char *EncodePhonemes(char *p, char *outptr, unsigned char *bad_phoneme) /*********************************************************************/ /* Translate a phoneme string from ascii mnemonics to internal phoneme numbers, from 'p' up to next blank . Returns advanced 'p' outptr contains encoded phonemes, unrecognized phoneme stops the encoding bad_phoneme must point to char array of length 2 of more */ { int ix; unsigned char c; int count; /* num. of matching characters */ int max; /* highest num. of matching found so far */ int max_ph; /* corresponding phoneme with highest matching */ int consumed; unsigned int mnemonic_word; bad_phoneme[0] = 0; // skip initial blanks while(isspace(*p)) { p++; } while(((c = *p) != 0) && !isspace(c)) { consumed = 0; switch(c) { case '|': // used to separate phoneme mnemonics if needed, to prevent characters being treated // as a multi-letter mnemonic if((c = p[1]) == '|') { // treat double || as a word-break symbol, drop through // to the default case with c = '|' } else { p++; break; } default: // lookup the phoneme mnemonic, find the phoneme with the highest number of // matching characters max= -1; max_ph= 0; for(ix=1; ixtype == phINVALID) continue; // this phoneme is not defined for this language count = 0; mnemonic_word = phoneme_tab[ix]->mnemonic; while(((c = p[count]) > ' ') && (count < 4) && (c == ((mnemonic_word >> (count*8)) & 0xff))) count++; if((count > max) && ((count == 4) || (((mnemonic_word >> (count*8)) & 0xff)==0))) { max = count; max_ph = phoneme_tab[ix]->code; } } if(max_ph == 0) { // not recognised, report and ignore bad_phoneme[0] = *p; bad_phoneme[1] = 0; *outptr++ = 0; return(p+1); } if(max <= 0) max = 1; p += (consumed + max); *outptr++ = (char)(max_ph); if(max_ph == phonSWITCH) { // Switch Language: this phoneme is followed by a text string char *p_lang = outptr; while(!isspace(c = *p) && (c != 0)) { p++; *outptr++ = tolower(c); } *outptr = 0; if(c == 0) { if(strcmp(p_lang,"en")==0) { *p_lang = 0; // don't need "en", it's assumed by default return(p); } } else { *outptr++ = '|'; // more phonemes follow, terminate language string with separator } } break; } } /* terminate the encoded string */ *outptr = 0; return(p); } // end of EncodePhonemes void DecodePhonemes(const char *inptr, char *outptr) //================================================== // Translate from internal phoneme codes into phoneme mnemonics { unsigned char phcode; unsigned char c; unsigned int mnem; PHONEME_TAB *ph; static const char *stress_chars = "==,,'* "; sprintf(outptr,"* "); while((phcode = *inptr++) > 0) { if(phcode == 255) continue; /* indicates unrecognised phoneme */ if((ph = phoneme_tab[phcode]) == NULL) continue; if((ph->type == phSTRESS) && (ph->std_length <= 4) && (ph->program == 0)) { if(ph->std_length > 1) *outptr++ = stress_chars[ph->std_length]; } else { mnem = ph->mnemonic; while((c = (mnem & 0xff)) != 0) { *outptr++ = c; mnem = mnem >> 8; } if(phcode == phonSWITCH) { while(isalpha(*inptr)) { *outptr++ = *inptr++; } } } } *outptr = 0; /* string terminator */ } // end of DecodePhonemes // using Kirschenbaum to IPA translation, ascii 0x20 to 0x7f unsigned short ipa1[96] = { 0x20,0x21,0x22,0x2b0,0x24,0x25,0x0e6,0x2c8,0x28,0x27e,0x2a,0x2b,0x2cc,0x2d,0x2e,0x2f, 0x252,0x31,0x32,0x25c,0x34,0x35,0x36,0x37,0x275,0x39,0x2d0,0x2b2,0x3c,0x3d,0x3e,0x294, 0x259,0x251,0x3b2,0xe7,0xf0,0x25b,0x46,0x262,0x127,0x26a,0x25f,0x4b,0x4c,0x271,0x14b,0x254, 0x3a6,0x263,0x280,0x283,0x3b8,0x28a,0x28c,0x153,0x3c7,0xf8,0x292,0x32a,0x5c,0x5d,0x5e,0x5f, 0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x261,0x68,0x69,0x6a,0x6b,0x6c,0x6d,0x6e,0x6f, 0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0x7a,0x7b,0x7c,0x7d,0x303,0x7f }; char *WritePhMnemonic(char *phon_out, PHONEME_TAB *ph, PHONEME_LIST *plist, int use_ipa) {//===================================================================================== int c; int mnem; int len; int first; int ix = 0; char *p; unsigned int ipa_control=0; // first byte of ipa string may control the phoneme name interpretation. 0x20 = ignore this phoneme PHONEME_DATA phdata; if(ph->code == phonEND_WORD) { // ignore phon_out[0] = 0; return(phon_out); } if(ph->code == phonSWITCH) { // the tone_ph field contains a phoneme table number p = phoneme_tab_list[plist->tone_ph].name; sprintf(phon_out, "(%s)", p); return(phon_out + strlen(phon_out)); } if(use_ipa) { // has an ipa name been defined for this phoneme ? phdata.ipa_string[0] = 0; if(plist == NULL) { InterpretPhoneme2(ph->code, &phdata); } else { InterpretPhoneme(NULL, 0, plist, &phdata); } len = strlen(phdata.ipa_string); if(len > 0) { if((ipa_control = phdata.ipa_string[0]) > 0x20) { strcpy(&phon_out[ix], phdata.ipa_string); ix += len; } if(ipa_control >= 0x20) { phon_out = &phon_out[ix]; *phon_out = 0; return(phon_out); // 0x20 = ignore phoneme } } } first = 1; for(mnem = ph->mnemonic; (c = mnem & 0xff) != 0; mnem = mnem >> 8) { if((c == '/') && (option_phoneme_variants==0)) break; // discard phoneme variant indicator if(use_ipa) { // convert from ascii to ipa if(first && (c == '_')) break; // don't show pause phonemes if((c == '#') && (ph->type == phVOWEL)) break; // # is subscript-h, but only for consonants // ignore digits after the first character if(!first && isdigit(c)) continue; if((c >= 0x20) && (c < 128)) c = ipa1[c-0x20]; ix += utf8_out(c, &phon_out[ix]); } else { phon_out[ix++]= c; } first = 0; } phon_out = &phon_out[ix]; *phon_out = 0; return(phon_out); } // end of WritePhMnemonic void GetTranslatedPhonemeString(char *phon_out, int n_phon_out, int use_ipa) {//========================================================================= /* Can be called after a clause has been translated into phonemes, in order to display the clause in phoneme mnemonic form. */ int ix; unsigned int len; unsigned int max_len; int phon_out_ix=0; int stress; unsigned int c; char *buf; char phon_buf[30]; PHONEME_LIST *plist; static const char *stress_chars = "==,,''"; if(phon_out != NULL) { for(ix=1; ix<(n_phoneme_list-2); ix++) { buf = phon_buf; plist = &phoneme_list[ix]; if(plist->newword) *buf++ = ' '; if(plist->synthflags & SFLAG_SYLLABLE) { if((stress = plist->stresslevel) > 1) { c = 0; if(stress > 5) stress = 5; if(use_ipa) { c = 0x2cc; // ipa, secondary stress if(stress > 3) c = 0x02c8; // ipa, primary stress } else { c = stress_chars[stress]; } if(c != 0) { buf += utf8_out(c, buf); } } } buf = WritePhMnemonic(buf, plist->ph, plist, use_ipa); if(plist->ph->code != phonSWITCH) { if(plist->synthflags & SFLAG_LENGTHEN) { buf = WritePhMnemonic(buf, phoneme_tab[phonLENGTHEN], NULL, use_ipa); } if((plist->synthflags & SFLAG_SYLLABLE) && (plist->type != phVOWEL)) { // syllablic consonant buf = WritePhMnemonic(buf, phoneme_tab[phonSYLLABIC], NULL, use_ipa); } if(plist->tone_ph > 0) { buf = WritePhMnemonic(buf, phoneme_tab[plist->tone_ph], NULL, use_ipa); } } len = buf - phon_buf; max_len = (n_phon_out - phon_out_ix - 5); // allow for " ..." and zero byte terminator if(len > max_len) { strcpy(&phon_buf[max_len], " ..."); len = max_len + 4; } phon_buf[len] = 0; strcpy(&phon_out[phon_out_ix], phon_buf); phon_out_ix += len; if(len > max_len) { break; } } phon_out[phon_out_ix] = 0; } } // end of GetTranslatedPhonemeString //============================================================================================= // Is a word Unpronouncable - and so should be spoken as individual letters // //============================================================================================= static int IsLetterGroup(Translator *tr, char *word, int group, int pre) {//===================================================================== // match the word against a list of utf-8 strings char *p; char *w; int len=0; p = tr->letterGroups[group]; if(p == NULL) return(0); while(*p != RULE_GROUP_END) { if(pre) { len = strlen(p); w = word - len + 1; } else { w = word; } while(*p == *w) { w++; p++; } if(*p == 0) { if(pre) return(len); return(w-word); // matched a complete string } while(*p++ != 0); // skip to end of string } return(0); } static int IsLetter(Translator *tr, int letter, int group) {//======================================================= int letter2; if(tr->letter_groups[group] != NULL) { if(wcschr(tr->letter_groups[group],letter)) return(1); return(0); } if(group > 7) return(0); if(tr->letter_bits_offset > 0) { if(((letter2 = (letter - tr->letter_bits_offset)) > 0) && (letter2 < 0x100)) letter = letter2; else return(0); } else { if((letter >= 0xc0) && (letter < N_REMOVE_ACCENT)) return(tr->letter_bits[remove_accent[letter-0xc0]] & (1L << group)); } if((letter >= 0) && (letter < 0x100)) return(tr->letter_bits[letter] & (1L << group)); return(0); } int IsVowel(Translator *tr, int letter) {//==================================== return(IsLetter(tr, letter, LETTERGP_VOWEL2)); } static int Unpronouncable2(Translator *tr, char *word) {//=================================================== int c; int end_flags; char ph_buf[N_WORD_PHONEMES]; ph_buf[0] = 0; c = word[-1]; word[-1] = ' '; // ensure there is a space before the "word" end_flags = TranslateRules(tr, word, ph_buf, sizeof(ph_buf), NULL, FLAG_UNPRON_TEST, NULL); word[-1] = c; if((end_flags == 0) || (end_flags & SUFX_UNPRON)) return(1); return(0); } int Unpronouncable(Translator *tr, char *word, int posn) {//===================================================== /* Determines whether a word in 'unpronouncable', i.e. whether it should be spoken as individual letters. This function may be language specific. This is a generic version. */ int c; int c1=0; int vowel_posn=9; int index; int count; utf8_in(&c,word); if((tr->letter_bits_offset > 0) && (c < 0x241)) { // Latin characters for a language with a non-latin alphabet return(0); // so we can re-translate the word as English } if(tr->langopts.param[LOPT_UNPRONOUNCABLE] == 1) return(0); if(((c = *word) == ' ') || (c == 0) || (c == '\'')) return(0); index = 0; count = 0; for(;;) { index += utf8_in(&c,&word[index]); if((c==0) || (c==' ')) break; if((c=='\'') && ((count > 1) || (posn > 0))) break; // "tv'" but not "l'" if(count==0) c1 = c; count++; if(IsVowel(tr, c)) { vowel_posn = count; // position of the first vowel break; } if((c != '\'') && !iswalpha(c)) return(0); } if((vowel_posn > 2) && (tr->langopts.param[LOPT_UNPRONOUNCABLE] == 2)) { // Lookup unpronounable rules in *_rules return(Unpronouncable2(tr, word)); } if(c1 == tr->langopts.param[LOPT_UNPRONOUNCABLE]) vowel_posn--; // disregard this as the initial letter when counting if(vowel_posn > (tr->langopts.max_initial_consonants+1)) return(1); // no vowel, or no vowel in first few letters return(0); } /* end of Unpronounceable */ //============================================================================================= // Determine the stress pattern of a word // //============================================================================================= static int GetVowelStress(Translator *tr, unsigned char *phonemes, signed char *vowel_stress, int &vowel_count, int &stressed_syllable, int control) {//================================================================================================================================================= // control = 1, set stress to 1 for forced unstressed vowels unsigned char phcode; PHONEME_TAB *ph; unsigned char *ph_out = phonemes; int count = 1; int max_stress = -1; int ix; int j; int stress = -1; int primary_posn = 0; vowel_stress[0] = 1; while(((phcode = *phonemes++) != 0) && (count < (N_WORD_PHONEMES/2)-1)) { if((ph = phoneme_tab[phcode]) == NULL) continue; if((ph->type == phSTRESS) && (ph->program == 0)) { /* stress marker, use this for the following vowel */ if(phcode == phonSTRESS_PREV) { /* primary stress on preceeding vowel */ j = count - 1; while((j > 0) && (stressed_syllable == 0) && (vowel_stress[j] < 4)) { if((vowel_stress[j] != 0) && (vowel_stress[j] != 1)) { // don't promote a phoneme which must be unstressed vowel_stress[j] = 4; if(max_stress < 4) { max_stress = 4; primary_posn = j; } /* reduce any preceding primary stress markers */ for(ix=1; ixstd_length < 4) || (stressed_syllable == 0)) { stress = ph->std_length; if(stress > max_stress) max_stress = stress; } } continue; } if((ph->type == phVOWEL) && !(ph->phflags & phNONSYLLABIC)) { vowel_stress[count] = (char)stress; if((stress >= 4) && (stress >= max_stress)) { primary_posn = count; max_stress = stress; } if((stress < 0) && (control & 1) && (ph->phflags & phUNSTRESSED)) vowel_stress[count] = 1; /* weak vowel, must be unstressed */ count++; stress = -1; } else if(phcode == phonSYLLABIC) { // previous consonant phoneme is syllablic vowel_stress[count] = (char)stress; if((stress == 0) && (control & 1)) vowel_stress[count++] = 1; // syllabic consonant, usually unstressed } *ph_out++ = phcode; } vowel_stress[count] = 1; *ph_out = 0; /* has the position of the primary stress been specified by $1, $2, etc? */ if(stressed_syllable > 0) { if(stressed_syllable >= count) stressed_syllable = count-1; // the final syllable vowel_stress[stressed_syllable] = 4; max_stress = 4; primary_posn = stressed_syllable; } if(max_stress == 5) { // priority stress, replaces any other primary stress marker for(ix=1; ixlangopts.stress_flags & 0x20000) vowel_stress[ix] = 1; else vowel_stress[ix] = 3; } if(vowel_stress[ix] == 5) { vowel_stress[ix] = 4; primary_posn = ix; } } max_stress = 4; } stressed_syllable = primary_posn; vowel_count = count; return(max_stress); } // end of GetVowelStress static char stress_phonemes[] = {phonSTRESS_D, phonSTRESS_U, phonSTRESS_2, phonSTRESS_3, phonSTRESS_P, phonSTRESS_P2, phonSTRESS_TONIC}; void ChangeWordStress(Translator *tr, char *word, int new_stress) {//============================================================== int ix; unsigned char *p; int max_stress; int vowel_count; // num of vowels + 1 int stressed_syllable=0; // position of stressed syllable unsigned char phonetic[N_WORD_PHONEMES]; signed char vowel_stress[N_WORD_PHONEMES/2]; strcpy((char *)phonetic,word); max_stress = GetVowelStress(tr, phonetic, vowel_stress, vowel_count, stressed_syllable, 0); if(new_stress >= 4) { // promote to primary stress for(ix=1; ix= max_stress) { vowel_stress[ix] = new_stress; break; } } } else { // remove primary stress for(ix=1; ix new_stress) // >= allows for diminished stress (=1) vowel_stress[ix] = new_stress; } } // write out phonemes ix = 1; p = phonetic; while(*p != 0) { if((phoneme_tab[*p]->type == phVOWEL) && !(phoneme_tab[*p]->phflags & phNONSYLLABIC)) { if((vowel_stress[ix] == 0) || (vowel_stress[ix] > 1)) *word++ = stress_phonemes[(unsigned char)vowel_stress[ix]]; ix++; } *word++ = *p++; } *word = 0; } // end of ChangeWordStress void SetWordStress(Translator *tr, char *output, unsigned int *dictionary_flags, int tonic, int control) {//===================================================================================================== /* Guess stress pattern of word. This is language specific 'output' is used for input and output 'dictionary_flags' has bits 0-3 position of stressed vowel (if > 0) or unstressed (if == 7) or syllables 1 and 2 (if == 6) bits 8... dictionary flags If 'tonic' is set (>= 0), replace highest stress by this value. control: bit 0 This is an individual symbol, not a word */ unsigned char phcode; unsigned char *p; PHONEME_TAB *ph; int stress; int max_stress; int vowel_count; // num of vowels + 1 int ix; int v; int v_stress; int stressed_syllable; // position of stressed syllable int max_stress_posn; int unstressed_word = 0; char *max_output; int final_ph; int final_ph2; int mnem; int mnem2; int post_tonic; // currently not used int opt_length; int done; int stressflags; int dflags = 0; int first_primary; signed char vowel_stress[N_WORD_PHONEMES/2]; char syllable_weight[N_WORD_PHONEMES/2]; char vowel_length[N_WORD_PHONEMES/2]; unsigned char phonetic[N_WORD_PHONEMES]; static char consonant_types[16] = {0,0,0,1,1,1,1,1,1,1,0,0,0,0,0,0}; /* stress numbers STRESS_BASE + 0 diminished, unstressed within a word 1 unstressed, weak 2 3 secondary stress 4 main stress */ stressflags = tr->langopts.stress_flags; if(dictionary_flags != NULL) dflags = dictionary_flags[0]; /* copy input string into internal buffer */ for(ix=0; ix= n_phoneme_tab) phonetic[ix] = phonSCHWA; if(phonetic[ix] == 0) break; } if(ix == 0) return; final_ph = phonetic[ix-1]; final_ph2 = phonetic[ix-2]; max_output = output + (N_WORD_PHONEMES-3); /* check for overrun */ // any stress position marked in the xx_list dictionary ? stressed_syllable = dflags & 0x7; if(dflags & 0x8) { // this indicates a word without a primary stress stressed_syllable = dflags & 0x3; unstressed_word = 1; } max_stress = GetVowelStress(tr, phonetic, vowel_stress, vowel_count, stressed_syllable, 1); if((max_stress < 0) && dictionary_flags) { if((tr->langopts.stress_flags & 1) && (vowel_count == 2)) { // lang=fr: don't stress monosyllables except at end-of-clause vowel_stress[1] = 0; dictionary_flags[0] |= FLAG_STRESS_END2; } max_stress = 0; } // heavy or light syllables ix = 1; for(p = phonetic; *p != 0; p++) { if((phoneme_tab[p[0]]->type == phVOWEL) && !(phoneme_tab[p[0]]->phflags & phNONSYLLABIC)) { int weight = 0; int lengthened = 0; if(phoneme_tab[p[1]]->code == phonLENGTHEN) lengthened = 1; if(lengthened || (phoneme_tab[p[0]]->phflags & phLONG)) { // long vowel, increase syllable weight weight++; } vowel_length[ix] = weight; if(lengthened) p++; // advance over phonLENGTHEN if(consonant_types[phoneme_tab[p[1]]->type] && ((phoneme_tab[p[2]]->type != phVOWEL) || (phoneme_tab[p[1]]->phflags & phLONG))) { // followed by two consonants, a long consonant, or consonant and end-of-word weight++; } syllable_weight[ix] = weight; ix++; } } switch(tr->langopts.stress_rule) { case 8: // stress on first syllable, unless it is a light syllable followed by a heavy syllable if((syllable_weight[1] > 0) || (syllable_weight[2] == 0)) break; // else drop through to case 1 case 1: // stress on second syllable if((stressed_syllable == 0) && (vowel_count > 2)) { stressed_syllable = 2; if(max_stress == 0) { vowel_stress[stressed_syllable] = 4; } max_stress = 4; } break; case 10: // penultimate, but final if only 1 or 2 syllables if(stressed_syllable == 0) { if(vowel_count < 4) { vowel_stress[vowel_count - 1] = 4; max_stress = 4; break; } } // drop through to next case case 2: // a language with stress on penultimate vowel if(stressed_syllable == 0) { /* no explicit stress - stress the penultimate vowel */ max_stress = 4; if(vowel_count > 2) { stressed_syllable = vowel_count - 2; if(stressflags & 0x300) { // LANG=Spanish, stress on last vowel if the word ends in a consonant other than 'n' or 's' if(phoneme_tab[final_ph]->type != phVOWEL) { if(stressflags & 0x100) { stressed_syllable = vowel_count - 1; } else { mnem = phoneme_tab[final_ph]->mnemonic; mnem2 = phoneme_tab[final_ph2]->mnemonic; if((mnem == 's') && (mnem2 == 'n')) { // -ns stress remains on penultimate syllable } else if(((mnem != 'n') && (mnem != 's')) || (phoneme_tab[final_ph2]->type != phVOWEL)) { stressed_syllable = vowel_count - 1; } } } } if(stressflags & 0x80000) { // stress on last syllable if it has a long vowel, but previous syllable has a short vowel if(vowel_length[vowel_count - 1] > vowel_length[vowel_count - 2]) { stressed_syllable = vowel_count - 1; } } if((vowel_stress[stressed_syllable] == 0) || (vowel_stress[stressed_syllable] == 1)) { // but this vowel is explicitly marked as unstressed if(stressed_syllable > 1) stressed_syllable--; else stressed_syllable++; } } else { stressed_syllable = 1; } // only set the stress if it's not already marked explicitly if(vowel_stress[stressed_syllable] < 0) { // don't stress if next and prev syllables are stressed if((vowel_stress[stressed_syllable-1] < 4) || (vowel_stress[stressed_syllable+1] < 4)) vowel_stress[stressed_syllable] = max_stress; } } break; case 3: // stress on last vowel if(stressed_syllable == 0) { /* no explicit stress - stress the final vowel */ stressed_syllable = vowel_count - 1; while(stressed_syllable > 0) { // find the last vowel which is not unstressed if(vowel_stress[stressed_syllable] < 0) { vowel_stress[stressed_syllable] = 4; break; } else stressed_syllable--; } max_stress = 4; } break; case 4: // stress on antipenultimate vowel if(stressed_syllable == 0) { stressed_syllable = vowel_count - 3; if(stressed_syllable < 1) stressed_syllable = 1; if(max_stress == 0) { vowel_stress[stressed_syllable] = 4; } max_stress = 4; } break; case 5: // LANG=Russian if(stressed_syllable == 0) { /* no explicit stress - guess the stress from the number of syllables */ static char guess_ru[16] = {0,0,1,1,2,3,3,4,5,6,7,7,8,9,10,11}; static char guess_ru_v[16] = {0,0,1,1,2,2,3,3,4,5,6,7,7,8,9,10}; // for final phoneme is a vowel static char guess_ru_t[16] = {0,0,1,2,3,3,3,4,5,6,7,7,7,8,9,10}; // for final phoneme is an unvoiced stop stressed_syllable = vowel_count - 3; if(vowel_count < 16) { if(phoneme_tab[final_ph]->type == phVOWEL) stressed_syllable = guess_ru_v[vowel_count]; else if(phoneme_tab[final_ph]->type == phSTOP) stressed_syllable = guess_ru_t[vowel_count]; else stressed_syllable = guess_ru[vowel_count]; } vowel_stress[stressed_syllable] = 4; max_stress = 4; } break; case 6: // LANG=hi stress on the last heaviest syllable if(stressed_syllable == 0) { int wt; int max_weight = -1; // int prev_stressed; // find the heaviest syllable, excluding the final syllable for(ix = 1; ix < (vowel_count-1); ix++) { if(vowel_stress[ix] < 0) { if((wt = syllable_weight[ix]) >= max_weight) { max_weight = wt; // prev_stressed = stressed_syllable; stressed_syllable = ix; } } } if((syllable_weight[vowel_count-1] == 2) && (max_weight< 2)) { // the only double=heavy syllable is the final syllable, so stress this stressed_syllable = vowel_count-1; } else if(max_weight <= 0) { // all syllables, exclusing the last, are light. Stress the first syllable stressed_syllable = 1; } vowel_stress[stressed_syllable] = 4; max_stress = 4; } break; case 7: // LANG=tr, the last syllable for any vowel marked explicitly as unstressed if(stressed_syllable == 0) { stressed_syllable = vowel_count - 1; for(ix=1; ix < vowel_count; ix++) { if(vowel_stress[ix] == 1) { stressed_syllable = ix-1; break; } } vowel_stress[stressed_syllable] = 4; max_stress = 4; } break; case 9: // mark all as stressed for(ix=1; ix 2) && (vowel_stress[2] >= 4)) { vowel_stress[1] = 3; } } done = 0; first_primary = 0; for(v=1; v 1) && (stressflags & 0x40) && (syllable_weight[v]==0) && (syllable_weight[v+1]>0)) { // don't put secondary stress on a light syllable which is followed by a heavy syllable continue; } // should start with secondary stress on the first syllable, or should it count back from // the primary stress and put secondary stress on alternate syllables? vowel_stress[v] = (char)stress; done =1; stress = 3; /* use secondary stress for remaining syllables */ } } if(vowel_stress[v] >= 4) { if(first_primary == 0) first_primary = v; else if(stressflags & S_FIRST_PRIMARY) { // reduce primary stresses after the first to secondary vowel_stress[v] = 3; } } } if((unstressed_word) && (tonic < 0)) { if(vowel_count <= 2) tonic = tr->langopts.unstressed_wd1; /* monosyllable - unstressed */ else tonic = tr->langopts.unstressed_wd2; /* more than one syllable, used secondary stress as the main stress */ } max_stress = 0; max_stress_posn = 0; for(v=1; v= max_stress) { max_stress = vowel_stress[v]; max_stress_posn = v; } } if(tonic >= 0) { /* find position of highest stress, and replace it by 'tonic' */ /* don't disturb an explicitly set stress by 'unstress-at-end' flag */ if((tonic > max_stress) || (max_stress <= 4)) vowel_stress[max_stress_posn] = (char)tonic; max_stress = tonic; } /* produce output phoneme string */ p = phonetic; v = 1; if(!(control & 1) && ((ph = phoneme_tab[*p]) != NULL)) { if(ph->type == phSTRESS) ph = phoneme_tab[p[1]]; #ifdef deleted int gap = tr->langopts.word_gap & 0x700; if((gap) && (vowel_stress[1] >= 4) && (prev_stress >= 4)) { /* two primary stresses together, insert a short pause */ *output++ = pause_phonemes[gap >> 8]; } else #endif if((tr->langopts.vowel_pause & 0x30) && (ph->type == phVOWEL)) { // word starts with a vowel if((tr->langopts.vowel_pause & 0x20) && (vowel_stress[1] >= 4)) { *output++ = phonPAUSE_NOLINK; // not to be replaced by link } else { *output++ = phonPAUSE_VSHORT; // break, but no pause } } } p = phonetic; post_tonic = 0; while(((phcode = *p++) != 0) && (output < max_output)) { if((ph = phoneme_tab[phcode]) == NULL) continue; // if(ph->type == phSTRESS) // continue; if(ph->type == phPAUSE) { tr->prev_last_stress = 0; } else if(((ph->type == phVOWEL) && !(ph->phflags & phNONSYLLABIC)) || (*p == phonSYLLABIC)) { // a vowel, or a consonant followed by a syllabic consonant marker v_stress = vowel_stress[v]; tr->prev_last_stress = v_stress; if(vowel_stress[v-1] >= max_stress) post_tonic = 1; if(v_stress <= 1) { if((v > 1) && (max_stress >= 2) && (stressflags & 4) && (v == (vowel_count-1))) { // option: mark unstressed final syllable as diminished v_stress = 0; } else if((stressflags & 2) || (v == 1) || (v == (vowel_count-1))) { // first or last syllable, or option 'don't set diminished stress' v_stress = 1; } else if((v == (vowel_count-2)) && (vowel_stress[vowel_count-1] <= 1)) { // penultimate syllable, followed by an unstressed final syllable v_stress = 1; } else { // unstressed syllable within a word if((vowel_stress[v-1] < 0) || ((stressflags & 0x10000) == 0)) { v_stress = 0; /* change to 0 (diminished stress) */ vowel_stress[v] = v_stress; } } } if((v_stress == 0) || (v_stress > 1)) *output++ = stress_phonemes[v_stress]; // mark stress of all vowels except 1 (unstressed) if(vowel_stress[v] > max_stress) { max_stress = vowel_stress[v]; } if((*p == phonLENGTHEN) && ((opt_length = tr->langopts.param[LOPT_IT_LENGTHEN]) & 1)) { // remove lengthen indicator from non-stressed syllables int shorten=0; if(opt_length & 0x10) { // only allow lengthen indicator on the highest stress syllable in the word if(v != max_stress_posn) shorten = 1; } else if(v_stress < 4) { // only allow lengthen indicator if stress >= 4. shorten = 1; } if(shorten) p++; } if((v_stress >= 4) && (tr->langopts.param[LOPT_IT_LENGTHEN] == 2)) { // LANG=Italian, lengthen penultimate stressed vowels, unless followed by 2 consonants if((v == (vowel_count - 2)) && (syllable_weight[v] == 0)) { *output++ = phcode; phcode = phonLENGTHEN; } } v++; } if(phcode != 1) *output++ = phcode; } *output++ = 0; return; } /* end of SetWordStress */ //============================================================================================= // Look up a word in the pronunciation rules // //============================================================================================= void AppendPhonemes(Translator *tr, char *string, int size, const char *ph) {//======================================================================== /* Add new phoneme string "ph" to "string" Keeps count of the number of vowel phonemes in the word, and whether these can be stressed syllables. These values can be used in translation rules */ const char *p; unsigned char c; int unstress_mark; int length; length = strlen(ph) + strlen(string); if(length >= size) { return; } /* any stressable vowel ? */ unstress_mark = 0; p = ph; while((c = *p++) != 0) { if(c >= n_phoneme_tab) continue; if(phoneme_tab[c]->type == phSTRESS) { if(phoneme_tab[c]->std_length < 4) unstress_mark = 1; } else { if(phoneme_tab[c]->type == phVOWEL) { if(((phoneme_tab[c]->phflags & phUNSTRESSED) == 0) && (unstress_mark == 0)) { tr->word_stressed_count++; } unstress_mark = 0; tr->word_vowel_count++; } } } if(string != NULL) strcat(string,ph); } /* end of AppendPhonemes */ static void MatchRule(Translator *tr, char *word[], char *word_start, int group_length, char *rule, MatchRecord *match_out, int word_flags, int dict_flags) {//======================================================================================================================================================== /* Checks a specified word against dictionary rules. Returns with phoneme code string, or NULL if no match found. word (indirect) points to current character group within the input word This is advanced by this procedure as characters are consumed group: the initial characters used to choose the rules group rule: address of dictionary rule data for this character group match_out: returns best points score word_flags: indicates whether this is a retranslation after a suffix has been removed */ unsigned char rb; // current instuction from rule unsigned char letter; // current letter from input word, single byte int letter_w; // current letter, wide character int letter_xbytes; // number of extra bytes of multibyte character (num bytes - 1) unsigned char last_letter; char *pre_ptr; char *post_ptr; /* pointer to first character after group */ char *rule_start; /* start of current match template */ char *p; int ix; int match_type; /* left, right, or consume */ int failed; int unpron_ignore; int consumed; /* number of letters consumed from input */ int syllable_count; int vowel; int letter_group; int distance_right; int distance_left; int lg_pts; int n_bytes; int add_points; int command; int check_atstart; MatchRecord match; static MatchRecord best; int total_consumed; /* letters consumed for best match */ unsigned char condition_num; char *common_phonemes; /* common to a group of entries */ char *group_chars; char word_buf[N_WORD_BYTES]; group_chars = *word; if(rule == NULL) { match_out->points = 0; (*word)++; return; } total_consumed = 0; common_phonemes = NULL; match_type = 0; best.points = 0; best.phonemes = ""; best.end_type = 0; best.del_fwd = NULL; /* search through dictionary rules */ while(rule[0] != RULE_GROUP_END) { unpron_ignore = word_flags & FLAG_UNPRON_TEST; match_type=0; consumed = 0; letter = 0; distance_right= -6; /* used to reduce points for matches further away the current letter */ distance_left= -2; check_atstart = 0; match.points = 1; match.end_type = 0; match.del_fwd = NULL; pre_ptr = *word; post_ptr = *word + group_length; /* work through next rule until end, or until no-match proved */ rule_start = rule; failed = 0; while(!failed) { rb = *rule++; if(rb <= RULE_LINENUM) { switch(rb) { case 0: // no phoneme string for this rule, use previous common rule if(common_phonemes != NULL) { match.phonemes = common_phonemes; while(((rb = *match.phonemes++) != 0) && (rb != RULE_PHONEMES)) { if(rb == RULE_CONDITION) match.phonemes++; // skip over condition number if(rb == RULE_LINENUM) match.phonemes += 2; // skip over line number } } else { match.phonemes = ""; } rule--; // so we are still pointing at the 0 failed=2; // matched OK break; case RULE_PRE_ATSTART: // pre rule with implied 'start of word' check_atstart = 1; unpron_ignore = 0; match_type = RULE_PRE; break; case RULE_PRE: match_type = RULE_PRE; if(word_flags & FLAG_UNPRON_TEST) { // checking the start of the word for unpronouncable character sequences, only // consider rules which explicitly match the start of a word // Note: Those rules now use RULE_PRE_ATSTART failed = 1; } break; case RULE_POST: match_type = RULE_POST; break; case RULE_PHONEMES: match.phonemes = rule; failed=2; // matched OK break; case RULE_PH_COMMON: common_phonemes = rule; break; case RULE_CONDITION: /* conditional rule, next byte gives condition number */ condition_num = *rule++; if(condition_num >= 32) { // allow the rule only if the condition number is NOT set if((tr->dict_condition & (1L << (condition_num-32))) != 0) failed = 1; } else { // allow the rule only if the condition number is set if((tr->dict_condition & (1L << condition_num)) == 0) failed = 1; } if(!failed) match.points++; // add one point for a matched conditional rule break; case RULE_LINENUM: rule+=2; break; } continue; } add_points = 0; switch(match_type) { case 0: /* match and consume this letter */ last_letter = letter; letter = *post_ptr++; if((letter == rb) || ((letter==(unsigned char)REPLACED_E) && (rb=='e'))) { if((letter & 0xc0) != 0x80) add_points = 21; // don't add point for non-initial UTF-8 bytes consumed++; } else failed = 1; break; case RULE_POST: /* continue moving fowards */ distance_right += 6; if(distance_right > 18) distance_right = 19; last_letter = letter; letter_xbytes = utf8_in(&letter_w,post_ptr)-1; letter = *post_ptr++; switch(rb) { case RULE_LETTERGP: letter_group = *rule++ - 'A'; if(IsLetter(tr, letter_w, letter_group)) { lg_pts = 20; if(letter_group==2) lg_pts = 19; // fewer points for C, general consonant add_points = (lg_pts-distance_right); post_ptr += letter_xbytes; } else failed = 1; break; case RULE_LETTERGP2: // match against a list of utf-8 strings letter_group = *rule++ - 'A'; if((n_bytes = IsLetterGroup(tr, post_ptr-1,letter_group,0)) >0) { add_points = (20-distance_right); post_ptr += (n_bytes-1); } else failed =1; break; case RULE_NOTVOWEL: if(IsLetter(tr, letter_w, 0) || ((letter_w == ' ') && (word_flags & FLAG_SUFFIX_VOWEL))) { failed = 1; } else { add_points = (20-distance_right); post_ptr += letter_xbytes; } break; case RULE_DIGIT: if(IsDigit(letter_w)) { add_points = (20-distance_right); post_ptr += letter_xbytes; } else if(tr->langopts.tone_numbers) { // also match if there is no digit add_points = (20-distance_right); post_ptr--; } else failed = 1; break; case RULE_NONALPHA: if(!iswalpha(letter_w)) { add_points = (21-distance_right); post_ptr += letter_xbytes; } else failed = 1; break; case RULE_DOUBLE: if(letter == last_letter) add_points = (21-distance_right); else failed = 1; break; case RULE_DOLLAR: command = *rule++; if(command == 0x01) { match.end_type = SUFX_UNPRON; // $unpron } else if((command & 0xf0) == 0x10) { // $w_alt if(dict_flags & (1 << (BITNUM_FLAG_ALT + (command & 0xf)))) add_points = 23; else failed = 1; } else if((command & 0xf0) == 0x20) { // $p_alt // make a copy of the word up to the post-match characters ix = *word - word_start + consumed + group_length + 1; memcpy(word_buf, word_start-1, ix); word_buf[ix] = ' '; word_buf[ix+1] = 0; if(LookupFlags(tr, &word_buf[1]) & (1 << (BITNUM_FLAG_ALT + (command & 0xf)))) add_points = 23; else failed = 1; } break; case '-': if((letter == '-') || ((letter == ' ') && (word_flags & FLAG_HYPHEN_AFTER))) { add_points = (22-distance_right); // one point more than match against space } else failed = 1; break; case RULE_SYLLABLE: { /* more than specified number of vowel letters to the right */ char *p = post_ptr + letter_xbytes; int vowel_count=0; syllable_count = 1; while(*rule == RULE_SYLLABLE) { rule++; syllable_count+=1; /* number of syllables to match */ } vowel = 0; while(letter_w != RULE_SPACE) { if((vowel==0) && IsLetter(tr, letter_w,LETTERGP_VOWEL2)) { // this is counting vowels which are separated by non-vowel letters vowel_count++; } vowel = IsLetter(tr, letter_w,LETTERGP_VOWEL2); p += utf8_in(&letter_w,p); } if(syllable_count <= vowel_count) add_points = (18+syllable_count-distance_right); else failed = 1; } break; case RULE_NOVOWELS: { char *p = post_ptr + letter_xbytes; while(letter_w != RULE_SPACE) { if(IsLetter(tr, letter_w,LETTERGP_VOWEL2)) { failed = 1; break; } p += utf8_in(&letter_w,p); } if(!failed) add_points = (19-distance_right); } break; case RULE_SKIPCHARS: { // Used for lang=Tamil, used to match on the next word after an unknown word ending // only look until the end of the word (including the end-of-word marker) // Jx means 'skip characters until x', where 'x' may be '_' for 'end of word' char *p = post_ptr + letter_xbytes; char *p2 = p; int rule_w; // skip characters until this utf8_in(&rule_w,rule); while((letter_w != rule_w) && (letter_w != RULE_SPACE)) { p2 = p; p += utf8_in(&letter_w,p); } if(letter_w == rule_w) { post_ptr = p2; } } break; case RULE_INC_SCORE: add_points = 20; // force an increase in points break; case RULE_DEL_FWD: // find the next 'e' in the word and replace by 'E' for(p = *word + group_length; p < post_ptr; p++) { if(*p == 'e') { match.del_fwd = p; break; } } break; case RULE_ENDING: { int end_type; // next 3 bytes are a (non-zero) ending type. 2 bytes of flags + suffix length end_type = (rule[0] << 16) + ((rule[1] & 0x7f) << 8) + (rule[2] & 0x7f); if((tr->word_vowel_count == 0) && !(end_type & SUFX_P) && (tr->langopts.param[LOPT_SUFFIX] & 1)) failed = 1; // don't match a suffix rule if there are no previous syllables (needed for lang=tr). else { match.end_type = end_type; rule += 3; } } break; case RULE_NO_SUFFIX: if(word_flags & FLAG_SUFFIX_REMOVED) failed = 1; // a suffix has been removed else add_points = 1; break; default: if(letter == rb) { if((letter & 0xc0) != 0x80) { // not for non-initial UTF-8 bytes add_points = (21-distance_right); } } else failed = 1; break; } break; case RULE_PRE: /* match backwards from start of current group */ distance_left += 2; if(distance_left > 18) distance_left = 19; last_letter = *pre_ptr; pre_ptr--; letter_xbytes = utf8_in2(&letter_w,pre_ptr,1)-1; letter = *pre_ptr; switch(rb) { case RULE_LETTERGP: letter_group = *rule++ - 'A'; if(IsLetter(tr, letter_w,letter_group)) { lg_pts = 20; if(letter_group==2) lg_pts = 19; // fewer points for C, general consonant add_points = (lg_pts-distance_left); pre_ptr -= letter_xbytes; } else failed = 1; break; case RULE_LETTERGP2: // match against a list of utf-8 strings letter_group = *rule++ - 'A'; if((n_bytes = IsLetterGroup(tr, pre_ptr,letter_group,1)) >0) { add_points = (20-distance_right); pre_ptr -= (n_bytes-1); } else failed =1; break; case RULE_NOTVOWEL: if(!IsLetter(tr, letter_w,0)) { add_points = (20-distance_left); pre_ptr -= letter_xbytes; } else failed = 1; break; case RULE_DOUBLE: if(letter == last_letter) add_points = (21-distance_left); else failed = 1; break; case RULE_DIGIT: if(IsDigit(letter_w)) { add_points = (21-distance_left); pre_ptr -= letter_xbytes; } else failed = 1; break; case RULE_NONALPHA: if(!iswalpha(letter_w)) { add_points = (21-distance_right); pre_ptr -= letter_xbytes; } else failed = 1; break; case RULE_SYLLABLE: /* more than specified number of vowels to the left */ syllable_count = 1; while(*rule == RULE_SYLLABLE) { rule++; syllable_count++; /* number of syllables to match */ } if(syllable_count <= tr->word_vowel_count) add_points = (18+syllable_count-distance_left); else failed = 1; break; case RULE_STRESSED: if(tr->word_stressed_count > 0) add_points = 19; else failed = 1; break; case RULE_NOVOWELS: { char *p = pre_ptr - letter_xbytes - 1; while(letter_w != RULE_SPACE) { if(IsLetter(tr, letter_w,LETTERGP_VOWEL2)) { failed = 1; break; } p -= utf8_in2(&letter_w,p,1); } if(!failed) add_points = 3; } break; case RULE_IFVERB: if(tr->expect_verb) add_points = 1; else failed = 1; break; case RULE_CAPITAL: if(word_flags & FLAG_FIRST_UPPER) add_points = 1; else failed = 1; break; case '.': // dot in pre- section, match on any dot before this point in the word for(p=pre_ptr; *p != ' '; p--) { if(*p == '.') { add_points = 50; break; } } if(*p == ' ') failed = 1; break; case '-': if((letter == '-') || ((letter == ' ') && (word_flags & FLAG_HYPHEN))) { add_points = (22-distance_right); // one point more than match against space } else failed = 1; break; default: if(letter == rb) { if(letter == RULE_SPACE) add_points = 4; else { if((letter & 0xc0) != 0x80) { // not for non-initial UTF-8 bytes add_points = (21-distance_left); } } } else failed = 1; break; } break; } if(failed == 0) match.points += add_points; } if((failed == 2) && (unpron_ignore == 0)) { // do we also need to check for 'start of word' ? if((check_atstart==0) || (pre_ptr[-1] == ' ')) { if(check_atstart) match.points += 4; /* matched OK, is this better than the last best match ? */ if(match.points >= best.points) { memcpy(&best,&match,sizeof(match)); total_consumed = consumed; } if((option_phonemes == 2) && (match.points > 0) && ((word_flags & FLAG_NO_TRACE) == 0)) { // show each rule that matches, and it's points score int pts; char decoded_phonemes[80]; pts = match.points; if(group_length > 1) pts += 35; // to account for an extra letter matching DecodePhonemes(match.phonemes,decoded_phonemes); fprintf(f_trans,"%3d\t%s [%s]\n",pts,DecodeRule(group_chars, group_length, rule_start, word_flags), decoded_phonemes); } } } /* skip phoneme string to reach start of next template */ while(*rule++ != 0); } if((option_phonemes == 2) && ((word_flags & FLAG_NO_TRACE)==0)) { if(group_length <= 1) fprintf(f_trans,"\n"); } /* advance input data pointer */ total_consumed += group_length; if(total_consumed == 0) total_consumed = 1; /* always advance over 1st letter */ *word += total_consumed; if(best.points == 0) best.phonemes = ""; memcpy(match_out,&best,sizeof(MatchRecord)); } /* end of MatchRule */ int TranslateRules(Translator *tr, char *p_start, char *phonemes, int ph_size, char *end_phonemes, int word_flags, unsigned int *dict_flags) {//===================================================================================================================================== /* Translate a word bounded by space characters Append the result to 'phonemes' and any standard prefix/suffix in 'end_phonemes' */ unsigned char c, c2; unsigned int c12; int wc=0; int wc_bytes; char *p2; /* copy of p for use in double letter chain match */ int found; int g; /* group chain number */ int g1; /* first group for this letter */ int n; int letter; int any_alpha=0; int ix; unsigned int digit_count=0; char *p; int dict_flags0=0; MatchRecord match1; MatchRecord match2; char ph_buf[40]; char word_copy[N_WORD_BYTES]; static const char str_pause[2] = {phonPAUSE_NOLINK,0}; if(tr->data_dictrules == NULL) return(0); if(dict_flags != NULL) dict_flags0 = dict_flags[0]; for(ix=0; ix<(N_WORD_BYTES-1);) { c = p_start[ix]; word_copy[ix++] = c; if(c == 0) break; } word_copy[ix] = 0; if((option_phonemes == 2) && ((word_flags & FLAG_NO_TRACE)==0)) { char wordbuf[120]; unsigned int ix; for(ix=0; ((c = p_start[ix]) != ' ') && (c != 0) && (ix < (sizeof(wordbuf)-1)); ix++) { wordbuf[ix] = c; } wordbuf[ix] = 0; if(word_flags & FLAG_UNPRON_TEST) fprintf(f_trans,"Unpronouncable? '%s'\n",wordbuf); else fprintf(f_trans,"Translate '%s'\n",wordbuf); } p = p_start; tr->word_vowel_count = 0; tr->word_stressed_count = 0; if(end_phonemes != NULL) end_phonemes[0] = 0; while(((c = *p) != ' ') && (c != 0)) { wc_bytes = utf8_in(&wc,p); if(IsAlpha(wc)) any_alpha++; n = tr->groups2_count[c]; if(IsDigit(wc) && ((tr->langopts.tone_numbers == 0) || !any_alpha)) { // lookup the number in *_list not *_rules char string[8]; char buf[40]; string[0] = '_'; memcpy(&string[1],p,wc_bytes); string[1+wc_bytes] = 0; Lookup(tr, string,buf); if(++digit_count >= 2) { strcat(buf,str_pause); digit_count=0; } AppendPhonemes(tr,phonemes,ph_size,buf); p += wc_bytes; continue; } else { digit_count = 0; found = 0; if(((ix = wc - tr->letter_bits_offset) >= 0) && (ix < 128)) { if(tr->groups3[ix] != NULL) { MatchRule(tr, &p, p_start, wc_bytes, tr->groups3[ix], &match1, word_flags, dict_flags0); found = 1; } } if(!found && (n > 0)) { /* there are some 2 byte chains for this initial letter */ c2 = p[1]; c12 = c + (c2 << 8); /* 2 characters */ g1 = tr->groups2_start[c]; for(g=g1; g < (g1+n); g++) { if(tr->groups2_name[g] == c12) { found = 1; p2 = p; MatchRule(tr, &p2, p_start, 2, tr->groups2[g], &match2, word_flags, dict_flags0); if(match2.points > 0) match2.points += 35; /* to acount for 2 letters matching */ /* now see whether single letter chain gives a better match ? */ MatchRule(tr, &p, p_start, 1, tr->groups1[c], &match1, word_flags, dict_flags0); if(match2.points >= match1.points) { // use match from the 2-letter group memcpy(&match1,&match2,sizeof(MatchRecord)); p = p2; } } } } if(!found) { /* alphabetic, single letter chain */ if(tr->groups1[c] != NULL) MatchRule(tr, &p, p_start, 1, tr->groups1[c], &match1, word_flags, dict_flags0); else { // no group for this letter, use default group MatchRule(tr, &p, p_start, 0, tr->groups1[0], &match1, word_flags, dict_flags0); if((match1.points == 0) && ((option_sayas & 0x10) == 0)) { n = utf8_in(&letter,p-1)-1; if(tr->letter_bits_offset > 0) { // not a Latin alphabet, switch to the default Latin alphabet language if((letter <= 0x241) && iswalpha(letter)) { sprintf(phonemes,"%c%s",phonSWITCH,tr->langopts.ascii_language); return(0); } } #ifdef deleted // can't switch to a tone language, because the tone-phoneme numbers are not valid for the original language if((letter >= 0x4e00) && (letter < 0xa000) && (tr->langopts.ideographs != 1)) { // Chinese ideogram sprintf(phonemes,"%czh",phonSWITCH); return(0); } #endif // is it a bracket ? if(letter == 0xe000+'(') { if(pre_pause < tr->langopts.param2[LOPT_BRACKET_PAUSE]) pre_pause = tr->langopts.param2[LOPT_BRACKET_PAUSE]; // a bracket, aleady spoken by AnnouncePunctuation() } if(IsBracket(letter)) { if(pre_pause < tr->langopts.param[LOPT_BRACKET_PAUSE]) pre_pause = tr->langopts.param[LOPT_BRACKET_PAUSE]; } // no match, try removing the accent and re-translating the word if((letter >= 0xc0) && (letter < N_REMOVE_ACCENT) && ((ix = remove_accent[letter-0xc0]) != 0)) { // within range of the remove_accent table if((p[-2] != ' ') || (p[n] != ' ')) { // not the only letter in the word p2 = p-1; p[-1] = ix; while((p[0] = p[n]) != ' ') p++; while(n-- > 0) *p++ = ' '; // replacement character must be no longer than original if(tr->langopts.param[LOPT_DIERESES] && (lookupwchar(diereses_list,letter) > 0)) { // vowel with dieresis, replace and continue from this point p = p2; continue; } phonemes[0] = 0; // delete any phonemes which have been produced so far p = p_start; tr->word_vowel_count = 0; tr->word_stressed_count = 0; continue; // start again at the beginning of the word } } else if((letter >= 0x3200) && (letter < 0xa700) && (end_phonemes != NULL)) { // ideograms // outside the range of the accent table, speak the unknown symbol sound Lookup(tr, "_??", ph_buf); match1.phonemes = ph_buf; match1.points = 1; p += (wc_bytes-1); } } } if(match1.points == 0) { if((wc >= 0x300) && (wc <= 0x36f)) { // combining accent inside a word, ignore } else if(IsAlpha(wc)) { if((any_alpha > 1) || (p[wc_bytes-1] > ' ')) { // an unrecognised character in a word, abort and then spell the word phonemes[0] = 0; if(dict_flags != NULL) dict_flags[0] |= FLAG_SPELLWORD; break; } } else { LookupLetter(tr, wc, -1, ph_buf, 0); if(ph_buf[0]) { match1.phonemes = ph_buf; match1.points = 1; } } p += (wc_bytes-1); } else { tr->phonemes_repeat_count = 0; } } } if(match1.phonemes == NULL) match1.phonemes = ""; if(match1.points > 0) { if(word_flags & FLAG_UNPRON_TEST) return(match1.end_type | 1); if((match1.phonemes[0] == phonSWITCH) && ((word_flags & FLAG_DONT_SWITCH_TRANSLATOR)==0)) { // an instruction to switch language, return immediately so we can re-translate strcpy(phonemes,match1.phonemes); return(0); } match1.end_type &= ~SUFX_UNPRON; if((match1.end_type != 0) && (end_phonemes != NULL)) { /* a standard ending has been found, re-translate the word without it */ if((match1.end_type & SUFX_P) && (word_flags & FLAG_NO_PREFIX)) { // ignore the match on a prefix } else { if((match1.end_type & SUFX_P) && ((match1.end_type & 0x7f) == 0)) { // no prefix length specified match1.end_type |= p - p_start; } strcpy(end_phonemes,match1.phonemes); memcpy(p_start,word_copy,strlen(word_copy)); return(match1.end_type); } } if(match1.del_fwd != NULL) *match1.del_fwd = REPLACED_E; AppendPhonemes(tr,phonemes,ph_size,match1.phonemes); } } // any language specific changes ? ApplySpecialAttribute(tr,phonemes,dict_flags0); memcpy(p_start,word_copy,strlen(word_copy)); return(0); } /* end of TranslateRules */ void ApplySpecialAttribute2(Translator *tr, char *phonemes, int dict_flags) {//======================================================================== // apply after the translation is complete int ix; int len; char *p; len = strlen(phonemes); if(tr->langopts.param[LOPT_ALT] & 2) { for(ix=0; ix<(len-1); ix++) { if(phonemes[ix] == phonSTRESS_P) { p = &phonemes[ix+1]; if((dict_flags & FLAG_ALT2_TRANS) != 0) { if(*p == PhonemeCode('E')) *p = PhonemeCode('e'); if(*p == PhonemeCode('O')) *p = PhonemeCode('o'); } else { if(*p == PhonemeCode('e')) *p = PhonemeCode('E'); if(*p == PhonemeCode('o')) *p = PhonemeCode('O'); } break; } } } } // end of ApplySpecialAttribute2 void ApplySpecialAttribute(Translator *tr, char *phonemes, int dict_flags) {//======================================================================= // Amend the translated phonemes according to an attribute which is specific for the language. int len; char *p_end; if((dict_flags & (FLAG_ALT_TRANS | FLAG_ALT2_TRANS)) == 0) return; len = strlen(phonemes); p_end = &phonemes[len-1]; switch(tr->translator_name) { #ifdef deleted // this is now done in de_rules case L('d','e'): if(p_end[0] == PhonemeCode2('i',':')) { // words ends in ['i:], change to [=I@] p_end[-1] = phonSTRESS_PREV; p_end[0] = PhonemeCode('I'); p_end[1] = phonSCHWA; p_end[2] = 0; } break; #endif case L('r','o'): if(p_end[0] == PhonemeCode('j')) { // word end in [j], change to ['i] p_end[0] = phonSTRESS_P; p_end[1] = PhonemeCode('i'); p_end[2] = 0; } break; } } // end of ApplySpecialAttribute //============================================================================================= // Look up a word in the pronunciation dictionary list // - exceptions which override the usual pronunciation rules, or which give a word // special properties, such as pronounce as unstressed //============================================================================================= int TransposeAlphabet(Translator *tr, char *text) {//============================================== // transpose cyrillic alphabet (for example) into ascii (single byte) character codes // return: number of bytes, bit 6: 1=used compression int c; int c2; int ix; int offset; int min; int max; char *p = text; char *p2 = text; int all_alpha=1; int bits; int acc; int pairs_start; const short *pairs_list; offset = tr->transpose_min - 1; min = tr->transpose_min; max = tr->transpose_max; pairs_start = max - min + 2; do { p += utf8_in(&c,p); if((c >= min) && (c <= max)) { *p2++ = c - offset; } else if(c != 0) { p2 += utf8_out(c,p2); all_alpha=0; } } while (c != 0); *p2 = 0; if(all_alpha) { // compress to 6 bits per character acc=0; bits=0; p = text; p2 = text; while((c = *p++) != 0) { if((pairs_list = tr->frequent_pairs) != NULL) { c2 = c + (*p << 8); for(ix=0; c2 >= pairs_list[ix]; ix++) { if(c2 == pairs_list[ix]) { // found an encoding for a 2-character pair c = ix + pairs_start; // 2-character codes start after the single letter codes p++; break; } } } acc = (acc << 6) + (c & 0x3f); bits += 6; if(bits >= 8) { bits -= 8; *p2++ = (acc >> bits); } } if(bits > 0) { *p2++ = (acc << (8-bits)); } *p2 = 0; return((p2 - text) | 0x40); // bit 6 indicates compressed characters } return(p2 - text); } // end of TransposeAlphabet static const char *LookupDict2(Translator *tr, const char *word, const char *word2, char *phonetic, unsigned int *flags, int end_flags, WORD_TAB *wtab) //===================================================================================== /* Find an entry in the word_dict file for a specified word. Returns NULL if no match, else returns 'word_end' word zero terminated word to match word2 pointer to next word(s) in the input text (terminated by space) flags: returns dictionary flags which are associated with a matched word end_flags: indicates whether this is a retranslation after removing a suffix */ { char *p; char *next; int hash; int phoneme_len; int wlen; unsigned char flag; unsigned int dictionary_flags; unsigned int dictionary_flags2; int condition_failed=0; int n_chars; int no_phonemes; int skipwords; int ix; const char *word_end; const char *word1; int wflags = 0; // int wflags2; char word_buf[N_WORD_BYTES+1]; if(wtab != NULL) { wflags = wtab->flags; } word1 = word; if(tr->transpose_min > 0) { strncpy0(word_buf,word, N_WORD_BYTES); wlen = TransposeAlphabet(tr, word_buf); word = word_buf; } else { wlen = strlen(word); } hash = HashDictionary(word); p = tr->dict_hashtab[hash]; if(p == NULL) { if(flags != NULL) *flags = 0; return(0); } // Find the first entry in the list for this hash value which matches. // This corresponds to the last matching entry in the *_list file. while(*p != 0) { next = p + p[0]; if(((p[1] & 0x7f) != wlen) || (memcmp(word,&p[2],wlen & 0x3f) != 0)) { // bit 6 of wlen indicates whether the word has been compressed; so we need to match on this also. p = next; continue; } /* found matching entry. Decode the phonetic string */ word_end = word2; dictionary_flags = 0; dictionary_flags2 = 0; no_phonemes = p[1] & 0x80; p += ((p[1] & 0x3f) + 2); if(no_phonemes) { phonetic[0] = 0; phoneme_len = 0; } else { strcpy(phonetic,p); phoneme_len = strlen(p); p += (phoneme_len + 1); } while(p < next) { // examine the flags which follow the phoneme string flag = *p++; if(flag >= 100) { // conditional rule if(flag >= 132) { // fail if this condition is set if((tr->dict_condition & (1 << (flag-132))) != 0) condition_failed = 1; } else { // allow only if this condition is set if((tr->dict_condition & (1 << (flag-100))) == 0) condition_failed = 1; } } else if(flag > 80) { // flags 81 to 90 match more than one word // This comes after the other flags n_chars = next - p; skipwords = flag - 80; // don't use the contraction if any of the words are emphasized // or has an embedded command, such as MARK if(wtab != NULL) { for(ix=0; ix <= skipwords; ix++) { if(wtab[ix].flags & FLAG_EMPHASIZED2) // if(((wflags2 = wtab[ix].flags) & FLAG_EMPHASIZED2) || ((ix > 0) && (wflags2 & FLAG_EMBEDDED))) { condition_failed = 1; } } } if(memcmp(word2,p,n_chars) != 0) condition_failed = 1; if(condition_failed) { p = next; break; } dictionary_flags |= FLAG_SKIPWORDS; dictionary_skipwords = skipwords; p = next; word_end = word2 + n_chars; } else if(flag > 64) { // stressed syllable information, put in bits 0-3 dictionary_flags = (dictionary_flags & ~0xf) | (flag & 0xf); if((flag & 0xc) == 0xc) dictionary_flags |= FLAG_STRESS_END; } else if(flag >= 32) { dictionary_flags2 |= (1L << (flag-32)); } else { dictionary_flags |= (1L << flag); } } if(condition_failed) { condition_failed=0; continue; } if((end_flags & FLAG_SUFX)==0) { // no suffix has been removed if(dictionary_flags & FLAG_STEM) continue; // this word must have a suffix } if((end_flags & SUFX_P) && (dictionary_flags & (FLAG_ONLY | FLAG_ONLY_S))) continue; // $only or $onlys, don't match if a prefix has been removed if(end_flags & FLAG_SUFX) { // a suffix was removed from the word if(dictionary_flags & FLAG_ONLY) continue; // no match if any suffix if((dictionary_flags & FLAG_ONLY_S) && ((end_flags & FLAG_SUFX_S)==0)) { // only a 's' suffix allowed, but the suffix wasn't 's' continue; } } if(dictionary_flags2 & FLAG_HYPHENATED) { if(!(wflags & FLAG_HYPHEN_AFTER)) { continue; } } if(dictionary_flags2 & FLAG_CAPITAL) { if(!(wflags & FLAG_FIRST_UPPER)) { continue; } } if(dictionary_flags2 & FLAG_ALLCAPS) { if(!(wflags & FLAG_ALL_UPPER)) { continue; } } if(dictionary_flags & FLAG_NEEDS_DOT) { if(!(wflags & FLAG_HAS_DOT)) continue; } if((dictionary_flags & FLAG_ATEND) && (word_end < tr->clause_end)) { // only use this pronunciation if it's the last word of the clause continue; } if((dictionary_flags & FLAG_ATSTART) && !(wtab->flags & FLAG_FIRST_WORD)) { // only use this pronunciation if it's the first word of a clause continue; } if((dictionary_flags2 & FLAG_SENTENCE) && !(tr->clause_terminator & CLAUSE_BIT_SENTENCE)) { // only uis this clause is a sentence , i.e. terminator is {. ? !} not {, : :} continue; } if(dictionary_flags2 & FLAG_VERB) { // this is a verb-form pronunciation if(tr->expect_verb || (tr->expect_verb_s && (end_flags & FLAG_SUFX_S))) { // OK, we are expecting a verb } else { /* don't use the 'verb' pronunciation unless we are expecting a verb */ continue; } } if(dictionary_flags2 & FLAG_PAST) { if(!tr->expect_past) { /* don't use the 'past' pronunciation unless we are expecting past tense */ continue; } } if(dictionary_flags2 & FLAG_NOUN) { if((!tr->expect_noun) || (end_flags & SUFX_V)) { /* don't use the 'noun' pronunciation unless we are expecting a noun */ continue; } } if(dictionary_flags & FLAG_ALT2_TRANS) { // language specific if((tr->translator_name == L('h','u')) && !(tr->prev_dict_flags & FLAG_ALT_TRANS)) continue; } if(flags != NULL) { flags[0] = dictionary_flags | FLAG_FOUND_ATTRIBUTES; flags[1] = dictionary_flags2; } if(phoneme_len == 0) { if(option_phonemes == 2) { fprintf(f_trans,"Flags: %s %s\n",word1,print_dictionary_flags(flags)); } return(0); // no phoneme translation found here, only flags. So use rules } if(flags != NULL) flags[0] |= FLAG_FOUND; // this flag indicates word was found in dictionary if(option_phonemes == 2) { char ph_decoded[N_WORD_PHONEMES]; int textmode; DecodePhonemes(phonetic,ph_decoded); if((dictionary_flags & FLAG_TEXTMODE) == 0) textmode = 0; else textmode = 1; if(textmode == translator->langopts.textmode) { // only show this line if the word translates to phonemes, not replacement text if((dictionary_skipwords) && (wtab != NULL)) { // matched more than one word // (check for wtab prevents showing RULE_SPELLING byte when speaking individual letters) memcpy(word_buf,word2,word_end-word2); word_buf[word_end-word2-1] = 0; fprintf(f_trans,"Found: '%s %s",word1,word_buf); } else { fprintf(f_trans,"Found: '%s",word1); } fprintf(f_trans,"' [%s] %s\n",ph_decoded,print_dictionary_flags(flags)); } } return(word_end); } return(0); } // end of LookupDict2 int LookupDictList(Translator *tr, char **wordptr, char *ph_out, unsigned int *flags, int end_flags, WORD_TAB *wtab) //================================================================================================================== /* Lookup a specified word in the word dictionary. Returns phonetic data in 'phonetic' and bits in 'flags' end_flags: indicates if a suffix has been removed */ { int length; const char *found; const char *word1; const char *word2; unsigned char c; int nbytes; int len; char word[N_WORD_BYTES]; static char word_replacement[N_WORD_BYTES]; length = 0; word2 = word1 = *wordptr; while((word2[nbytes = utf8_nbytes(word2)]==' ') && (word2[nbytes+1]=='.')) { // look for an abbreviation of the form a.b.c // try removing the spaces between the dots and looking for a match memcpy(&word[length],word2,nbytes); length += nbytes; word[length++] = '.'; word2 += nbytes+3; } if(length > 0) { // found an abbreviation containing dots nbytes = 0; while(((c = word2[nbytes]) != 0) && (c != ' ')) { nbytes++; } memcpy(&word[length],word2,nbytes); word[length+nbytes] = 0; found = LookupDict2(tr, word, word2, ph_out, flags, end_flags, wtab); if(found) { // set the skip words flag flags[0] |= FLAG_SKIPWORDS; dictionary_skipwords = length; return(1); } } for(length=0; length<(N_WORD_BYTES-1); length++) { if(((c = *word1++)==0) || (c == ' ')) break; if((c=='.') && (length > 0) && (isdigit(word[length-1]))) break; // needed for lang=hu, eg. "december 2.-ig" word[length] = c; } word[length] = 0; found = LookupDict2(tr, word, word1, ph_out, flags, end_flags, wtab); if(flags[0] & FLAG_MAX3) { if(strcmp(ph_out, tr->phonemes_repeat) == 0) { tr->phonemes_repeat_count++; if(tr->phonemes_repeat_count > 3) { ph_out[0] = 0; } } else { strncpy0(tr->phonemes_repeat, ph_out, sizeof(tr->phonemes_repeat)); tr->phonemes_repeat_count = 1; } } else { tr->phonemes_repeat_count = 0; } if((found == 0) && (flags[1] & FLAG_ACCENT)) { int letter; word2 = word; if(*word2 == '_') word2++; len = utf8_in(&letter, word2); LookupAccentedLetter(tr,letter, ph_out); found = word2 + len; } if(found == 0) { ph_out[0] = 0; // try modifications to find a recognised word if((end_flags & FLAG_SUFX_E_ADDED) && (word[length-1] == 'e')) { // try removing an 'e' which has been added by RemoveEnding word[length-1] = 0; found = LookupDict2(tr, word, word1, ph_out, flags, end_flags, wtab); } else if((end_flags & SUFX_D) && (word[length-1] == word[length-2])) { // try removing a double letter word[length-1] = 0; found = LookupDict2(tr, word, word1, ph_out, flags, end_flags, wtab); } } if(found) { // if textmode is the default, then words which have phonemes are marked. if(tr->langopts.textmode) *flags ^= FLAG_TEXTMODE; if(*flags & FLAG_TEXTMODE) { // the word translates to replacement text, not to phonemes if(end_flags & FLAG_ALLOW_TEXTMODE) { // only use replacement text if this is the original word, not if a prefix or suffix has been removed word_replacement[0] = 0; word_replacement[1] = ' '; sprintf(&word_replacement[2],"%s ",ph_out); // replacement word, preceded by zerochar and space word1 = *wordptr; *wordptr = &word_replacement[2]; if(option_phonemes == 2) { len = found - word1; memcpy(word,word1,len); // include multiple matching words word[len] = 0; fprintf(f_trans,"Replace: %s %s\n",word,*wordptr); } } else { // flags[0] &= ~FLAG_SKIPWORDS; // check lang=hu január 21.-ig (error: suffix repeated ??) } ph_out[0] = 0; return(0); } return(1); } ph_out[0] = 0; return(0); } // end of LookupDictList int Lookup(Translator *tr, const char *word, char *ph_out) {//=================================================== unsigned int flags[2]; flags[0] = flags[1] = 0; char *word1 = (char *)word; return(LookupDictList(tr, &word1, ph_out, flags, 0, NULL)); } int LookupFlags(Translator *tr, const char *word) {//============================================== char buf[100]; static unsigned int flags[2]; flags[0] = flags[1] = 0; char *word1 = (char *)word; LookupDictList(tr, &word1, buf, flags, 0, NULL); return(flags[0]); } int RemoveEnding(Translator *tr, char *word, int end_type, char *word_copy) {//======================================================================== /* Removes a standard suffix from a word, once it has been indicated by the dictionary rules. end_type: bits 0-6 number of letters bits 8-14 suffix flags word_copy: make a copy of the original word This routine is language specific. In English it deals with reversing y->i and e-dropping that were done when the suffix was added to the original word. */ int i; char *word_end; int len_ending; int end_flags; const char *p; int len; static char ending[12]; // these lists are language specific, but are only relevent if the 'e' suffix flag is used static const char *add_e_exceptions[] = { "ion", NULL }; static const char *add_e_additions[] = { // "c", "rs", "ir", "ur", "ath", "ns", "lu", NULL }; "c", "rs", "ir", "ur", "ath", "ns", "u", NULL }; for(word_end = word; *word_end != ' '; word_end++) { /* replace discarded 'e's */ if(*word_end == REPLACED_E) *word_end = 'e'; } i = word_end - word; memcpy(word_copy,word,i); word_copy[i] = 0; // look for multibyte characters to increase the number of bytes to remove for(len_ending = i = (end_type & 0x3f); i>0 ;i--) // num.of characters of the suffix { word_end--; while((*word_end & 0xc0) == 0x80) { word_end--; // for multibyte characters len_ending++; } } // remove bytes from the end of the word and replace them by spaces for(i=0; itranslator_name == L('n','l')) { if(((word_end[0] & 0x80) == 0) && ((word_end[-1] & 0x80) == 0) && IsVowel(tr, word_end[-1]) && IsLetter(tr, word_end[0], LETTERGP_C) && !IsVowel(tr, word_end[-2])) { //double the vowel before the (ascii) final consonant word_end[1] = word_end[0]; word_end[0] = word_end[-1]; word_end[2] = ' '; } } else if(tr->translator_name == L('e','n')) { // add 'e' to end of stem if(IsLetter(tr, word_end[-1],LETTERGP_VOWEL2) && IsLetter(tr, word_end[0],1)) { // vowel(incl.'y') + hard.consonant for(i=0; (p = add_e_exceptions[i]) != NULL; i++) { len = strlen(p); if(memcmp(p,&word_end[1-len],len)==0) { break; } } if(p == NULL) end_flags |= FLAG_SUFX_E_ADDED; // no exception found } else { for(i=0; (p = add_e_additions[i]) != NULL; i++) { len = strlen(p); if(memcmp(p,&word_end[1-len],len)==0) { end_flags |= FLAG_SUFX_E_ADDED; break; } } } } else if(tr->langopts.suffix_add_e != 0) { end_flags |= FLAG_SUFX_E_ADDED; } if(end_flags & FLAG_SUFX_E_ADDED) { utf8_out(tr->langopts.suffix_add_e, &word_end[1]); if(option_phonemes == 2) { fprintf(f_trans,"add e\n"); } } } if((end_type & SUFX_V) && (tr->expect_verb==0)) tr->expect_verb = 1; // this suffix indicates the verb pronunciation if((strcmp(ending,"s")==0) || (strcmp(ending,"es")==0)) end_flags |= FLAG_SUFX_S; // if(strcmp(ending,"'s")==0) if(ending[0] == '\'') end_flags &= ~FLAG_SUFX; // don't consider 's as an added suffix return(end_flags); } /* end of RemoveEnding */ sources_5316/external/espeak/wave_sada.cpp0000664000176700017670000003647711674622653017512 0ustar paulpaul/*************************************************************************** * Copyright (C) 2008, Sun Microsystems, Inc. * * eSpeak driver for Solaris Audio Device Architecture (SADA) * * Written by Willie Walker, based on the eSpeak PulseAudio driver * * from Gilles Casse * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ #include "speech.h" #ifdef USE_ASYNC // This source file is only used for asynchronious modes #include #include #include #include #include #include #include #include #include "wave.h" #include "debug.h" enum {ONE_BILLION=1000000000}; #define SAMPLE_RATE 22050 #define SAMPLE_SIZE 16 #ifdef USE_SADA static t_wave_callback* my_callback_is_output_enabled=NULL; static const char *sun_audio_device = "/dev/audio"; static int sun_audio_fd = -1; // The total number of 16-bit samples sent to be played via the // wave_write method. // static uint32_t total_samples_sent; // The total number of samples sent to be played via the wave_write // method, but which were never played because of a call to // wave_close. // static uint32_t total_samples_skipped; // The last known playing index after a call to wave_close. // static uint32_t last_play_position=0; static uint32_t wave_samplerate; //> // wave_init // // DESCRIPTION: // // initializes the audio subsytem. // // GLOBALS USED/MODIFIED: // // sun_audio_fd: modified to hold the file descriptor of the opened // audio device. // // // wave_open // // DESCRIPTION: // // opens the audio subsystem given a specific API (e.g., "alsa", // "oss", ...). We ignore the_api and just return the sun_audio_fd we // opened in wave_init. This return value will be passed in as the // theHandler parameter in all other methods. // // PARAMETERS: // // the_api: "alsa", "oss" (ignored) // // GLOBALS USED/MODIFIED: // // sun_audio_fd: used as return value // // RETURNS: // // sun_audio_fd opened in wave_init, which is passed in as theHandler // parameter in all other methods // // // wave_write // // DESCRIPTION: // // Meant to be asynchronous, it supplies the wave sample to the lower // audio layer and returns. The sample is played later on. [[[WDW - // we purposely do not open the audio device as non-blocking because // managing that would be a pain. So, we rely a lot upon fifo.cpp and // event.cpp to not overload us, allowing us to get away with a // blocking write. event.cpp:polling_thread in particular appears to // use get_remaining_time to prevent flooding.]]] // // PARAMETERS: // // theHandler: the audio device file descriptor // theMono16BitsWaveBuffer: the audio data // theSize: the number of bytes (not 16-bit samples) // // GLOBALS USED/MODIFIED: // // total_samples_sent: modified based upon 16-bit samples sent // // RETURNS: // // the number of bytes (not 16-bit samples) sent // // my_callback_is_output_enabled: no!"); return 0; } #if defined(BYTE_ORDER) && BYTE_ORDER == BIG_ENDIAN { // BIG-ENDIAN, swap the order of bytes in each sound sample int c; char *out_ptr; char *out_end; out_ptr = (char *)theMono16BitsWaveBuffer; out_end = out_ptr + theSize; while(out_ptr < out_end) { c = out_ptr[0]; out_ptr[0] = out_ptr[1]; out_ptr[1] = c; out_ptr += 2; } } #endif num = write((int) theHandler, theMono16BitsWaveBuffer, theSize); // Keep track of the total number of samples sent -- we use this in // wave_get_read_position and also use it to help calculate the // total_samples_skipped in wave_close. // total_samples_sent += num / 2; if (num < theSize) { SHOW("ERROR: wave_write only wrote %d of %d bytes\n", num, theSize); } else { SHOW("wave_write wrote %d bytes\n", theSize); } SHOW_TIME("wave_write > LEAVE"); return num; } //> // wave_close // // DESCRIPTION: // // Does what SADA normally would call a flush, which means to cease // all audio production in progress and throw any remaining audio // away. [[[WDW - see comment in wave_flush.]]] // // PARAMETERS: // // theHandler: the audio device file descriptor // // GLOBALS USED/MODIFIED: // // last_play_position: modified to reflect play position the last time // this method was called // total_samples_sent: used to help calculate total_samples_skipped // total_samples_skipped: modified to hold the total number of 16-bit // samples sent to wave_write, but which were // never played // sun_audio_fd: used because some calls to wave_close seem to // pass a NULL for theHandler for some odd reason // // RETURNS: // // The result of the ioctl call (non-0 means failure) // // LEAVE"); return ret; } //> // wave_is_busy // // DESCRIPTION: // // Returns a non-0 value if audio is being played. // // PARAMETERS: // // theHandler: the audio device file descriptor // // GLOBALS USED/MODIFIED: // // sun_audio_fd: used because some calls to wave_is_busy seem to // pass a NULL for theHandler for some odd reason // // RETURNS: // // A non-0 value if audio is being played // //= 1) { wave_get_remaining_time(total_samples_sent - 1, &time); } else { time = 0; } return time != 0; } //> // wave_terminate // // DESCRIPTION: // // Used to end our session with eSpeak. // // GLOBALS USED/MODIFIED: // // sun_audio_fd: modified - closed and set to -1 // // LEAVE"); } //> // wave_flush // // DESCRIPTION: // // Appears to want to tell the audio subsystem to make sure it plays // the audio. In our case, the system is already doing this, so this // is basically a no-op. [[[WDW - if you do a drain, you block, so // don't do that. In addition the typical SADA notion of flush is // currently handled by wave_close. I think this is most likely just // terminology conflict between eSpeak and SADA.]]] // // PARAMETERS: // // theHandler: the audio device file descriptor // // LEAVE"); } //> // wave_set_callback_is_output_enabled // // DESCRIPTION: // // Sets the callback to call from wave_write before it sends data to // be played. It helps wave_write determine if the data should be // thrown away or not. // // PARAMETERS: // // cb: the callback to call from wave_write // // // wave_test_get_write_buffer // // DESCRIPTION: // // Unnecessary and is used for debug output from // speak_lib.cpp:dispatch_audio. // // RETURNS: // // NULL // // // wave_get_read_position // // DESCRIPTION: // // Concerns the sample which is currently played by the audio layer, // where 'sample' is a small buffer of synthesized wave data, // identified so that the user callback could be called when the // 'sample' is really played. The identifier is returned by // wave_get_write_position. This method is unused. // // PARAMETERS: // // theHandler: the audio device file descriptor // // RETURNS: // // The total number of 16-bit samples played by the audio system // so far. // // LEAVE"); return ainfo.play.samples; } //> // wave_get_write_position // // DESCRIPTION: // // Returns an identifier for a new sample, where 'sample' is a small // buffer of synthesized wave data, identified so that the user // callback could be called when the 'sample' is really played. This // implementation views the audio as one long continuous stream of // 16-bit samples. // // PARAMETERS: // // theHandler: the audio device file descriptor // // GLOBALS USED/MODIFIED: // // total_samples_sent: used as the return value // // RETURNS: // // total_samples_sent, which is the index for the end of this long // continuous stream. [[[WDW: with a unit32_t managing 16-bit // samples at 22050Hz, we have about 54 hours of play time before // the index wraps back to 0. We don't handle that wrapping, so // the behavior after 54 hours of play time is undefined.]]] // // LEAVE"); return total_samples_sent; } //> // wave_get_remaining_time // // DESCRIPTION: // // Returns the remaining time (in ms) before the sample is played. // The sample in this case is a return value from a previous call to // wave_get_write_position. // // PARAMETERS: // // sample: an index returned from wave_get_write_position representing // an index into the long continuous stream of 16-bit samples // time: a return value representing the delay in milliseconds until // sample is played. A value of 0 means the sample is either // currently being played or it has already been played. // // GLOBALS USED/MODIFIED: // // sun_audio_fd: used to determine total number of samples played by // the audio system // total_samples_skipped: used in remaining time calculation // // RETURNS: // // Time in milliseconds before the sample is played or 0 if the sample // is currently playing or has already been played. // // LEAVE"); } ioctl(sun_audio_fd, AUDIO_GETINFO, &ainfo); // See if this sample has already been played or is currently // playing. // actual_index = sample - total_samples_skipped; if ((sample < total_samples_skipped) || (actual_index <= ainfo.play.samples)) { *time = 0; } else { a_time = ((actual_index - ainfo.play.samples) * 1000) / wave_samplerate; *time = (uint32_t) a_time; } SHOW("wave_get_remaining_time for %d: %d\n", sample, *time); SHOW_TIME("wave_get_remaining_time > LEAVE"); return 0; } #else // notdef USE_SADA void wave_init() {} void* wave_open(const char* the_api) {return (void *)1;} size_t wave_write(void* theHandler, char* theMono16BitsWaveBuffer, size_t theSize) {return theSize;} int wave_close(void* theHandler) {return 0;} int wave_is_busy(void* theHandler) {return 0;} void wave_terminate() {} uint32_t wave_get_read_position(void* theHandler) {return 0;} uint32_t wave_get_write_position(void* theHandler) {return 0;} void wave_flush(void* theHandler) {} typedef int (t_wave_callback)(void); void wave_set_callback_is_output_enabled(t_wave_callback* cb) {} extern void* wave_test_get_write_buffer() {return NULL;} int wave_get_remaining_time(uint32_t sample, uint32_t* time) { if (!time) return(-1); *time = (uint32_t)0; return 0; } #endif // of USE_PORTAUDIO //> //tv_sec = tv.tv_sec; ts->tv_nsec = tv.tv_usec*1000; } void add_time_in_ms(struct timespec *ts, int time_in_ms) { if (!ts) { return; } uint64_t t_ns = (uint64_t)ts->tv_nsec + 1000000 * (uint64_t)time_in_ms; while(t_ns >= ONE_BILLION) { SHOW("event > add_time_in_ms ns: %d sec %Lu nsec \n", ts->tv_sec, t_ns); ts->tv_sec += 1; t_ns -= ONE_BILLION; } ts->tv_nsec = (long int)t_ns; } #endif // USE_ASYNC //> sources_5316/external/espeak/phonemelist.cpp0000664000176700017670000003677711723710247020102 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2011 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "translate.h" const unsigned char pause_phonemes[8] = {0, phonPAUSE_VSHORT, phonPAUSE_SHORT, phonPAUSE, phonPAUSE_LONG, phonGLOTTALSTOP, phonPAUSE_LONG, phonPAUSE_LONG}; extern int n_ph_list2; extern PHONEME_LIST2 ph_list2[N_PHONEME_LIST]; // first stage of text->phonemes static int SubstitutePhonemes(Translator *tr, PHONEME_LIST *plist_out) {//=================================================================== // Copy the phonemes list and perform any substitutions that are required for the // current voice int ix; int k; int replace_flags; int n_plist_out = 0; int word_end; int switched_language = 0; PHONEME_LIST2 *plist2; PHONEME_TAB *next=NULL; for(ix=0; (ix < n_ph_list2) && (n_plist_out < N_PHONEME_LIST); ix++) { plist2 = &ph_list2[ix]; if(plist2->phcode == phonSWITCH) switched_language ^= 1; // don't do any substitution if the language has been temporarily changed if(switched_language == 0) { if(ix < (n_ph_list2 -1)) next = phoneme_tab[ph_list2[ix+1].phcode]; word_end = 0; if((plist2+1)->sourceix || ((next != 0) && (next->type == phPAUSE))) word_end = 1; // this phoneme is the end of a word // check whether a Voice has specified that we should replace this phoneme for(k=0; kphcode == replace_phonemes[k].old_ph) { replace_flags = replace_phonemes[k].type; if((replace_flags & 1) && (word_end == 0)) continue; // this replacement only occurs at the end of a word if((replace_flags & 2) && ((plist2->stresslevel & 0x7) > 3)) continue; // this replacement doesn't occur in stressed syllables // substitute the replacement phoneme plist2->phcode = replace_phonemes[k].new_ph; if((plist2->stresslevel > 1) && (phoneme_tab[plist2->phcode]->phflags & phUNSTRESSED)) plist2->stresslevel = 0; // the replacement must be unstressed break; } } if(plist2->phcode == 0) { continue; // phoneme has been replaced by NULL, so don't copy it } } // copy phoneme into the output list memcpy(&plist_out[n_plist_out],plist2,sizeof(PHONEME_LIST2)); plist_out[n_plist_out].ph = phoneme_tab[plist2->phcode]; plist_out[n_plist_out].type = plist_out[n_plist_out].ph->type; n_plist_out++; } return(n_plist_out); } // end of SubstitutePhonemes void MakePhonemeList(Translator *tr, int post_pause, int start_sentence) {//===================================================================== int ix=0; int j; int insert_ph = 0; PHONEME_LIST *phlist; PHONEME_TAB *ph; PHONEME_TAB *next, *next2; int unstress_count = 0; int word_stress = 0; int switched_language = 0; int max_stress; int voicing; int regression; int end_sourceix; int alternative; PHONEME_DATA phdata; int n_ph_list3; PHONEME_LIST *plist3; PHONEME_LIST *plist3_inserted = NULL; PHONEME_LIST ph_list3[N_PHONEME_LIST]; PHONEME_LIST2 *plist2; plist2 = ph_list2; phlist = phoneme_list; end_sourceix = plist2[n_ph_list2-1].sourceix; // is the last word of the clause unstressed ? max_stress = 0; for(j = n_ph_list2-3; j>=0; j--) { // start with the last phoneme (before the terminating pauses) and move forwards if((plist2[j].stresslevel & 0x7f) > max_stress) max_stress = plist2[j].stresslevel & 0x7f; if(plist2[j].sourceix != 0) break; } if(max_stress < 4) { // the last word is unstressed, look for a previous word that can be stressed while(--j >= 0) { if(plist2[j].synthflags & SFLAG_PROMOTE_STRESS) // dictionary flags indicated that this stress can be promoted { plist2[j].stresslevel = 4; // promote to stressed break; } if(plist2[j].stresslevel >= 4) { // found a stressed syllable, so stop looking break; } } } if((regression = tr->langopts.param[LOPT_REGRESSIVE_VOICING]) != 0) { // set consonant clusters to all voiced or all unvoiced // Regressive int type; int stop_propagation = 0; voicing = 0; for(j=n_ph_list2-1; j>=0; j--) { ph = phoneme_tab[plist2[j].phcode]; if(ph == NULL) continue; if(ph->code == phonSWITCH) switched_language ^= 1; if(switched_language) continue; type = ph->type; if(regression & 0x2) { // [v] amd [v;] don't cause regression, or [R^] if(((ph->mnemonic & 0xff) == 'v') || ((ph->mnemonic & 0xff)== 'R')) { stop_propagation = 1; if(regression & 0x10) voicing = 0; } } if((type==phSTOP) || type==(phFRICATIVE)) { if((voicing==0) && (regression & 0xf)) { voicing = 1; } else if((voicing==2) && (ph->end_type != 0)) // use end_type field for voicing_switch for consonants { plist2[j].phcode = ph->end_type; // change to voiced equivalent } } else if((type==phVSTOP) || type==(phVFRICATIVE)) { if((voicing==0) && (regression & 0xf)) { voicing = 2; } else if((voicing==1) && (ph->end_type != 0)) { plist2[j].phcode = ph->end_type; // change to unvoiced equivalent } } else { if(regression & 0x8) { // LANG=Polish, propagate through liquids and nasals if((type == phPAUSE) || (type == phVOWEL)) voicing = 0; } else { voicing = 0; } } if(stop_propagation) { voicing = 0; stop_propagation = 0; } if(plist2[j].sourceix) { if(regression & 0x04) { // stop propagation at a word boundary voicing = 0; } if(regression & 0x100) { // devoice word-final consonants, unless propagating voiced if(voicing == 0) { voicing = 1; } } } } } n_ph_list3 = SubstitutePhonemes(tr,ph_list3) - 2; for(j=0; (j < n_ph_list3) && (ix < N_PHONEME_LIST-3);) { if(ph_list3[j].sourceix) { // start of a word int k; int nextw; word_stress = 0; // find the highest stress level in this word for(nextw=j; nextw < n_ph_list3;) { if(ph_list3[nextw].stresslevel > word_stress) word_stress = ph_list3[nextw].stresslevel; nextw++; if(ph_list3[nextw].sourceix) break; // start of the next word } for(k=j; kphcode]; // this phoneme, i.e. after the insert // re-use the previous entry for the inserted phoneme. // That's OK because we don't look backwards from plist3 *** but CountVowelPosiion() and isAfterStress does !!! j--; plist3 = plist3_inserted = &ph_list3[j]; if(j > 0) { memcpy(&plist3[-1], &plist3[0], sizeof(*plist3)); } memset(&plist3[0], 0, sizeof(*plist3)); plist3->phcode = insert_ph; ph = phoneme_tab[insert_ph]; plist3->ph = ph; insert_ph = 0; } else { // otherwise get the next phoneme from the list ph = phoneme_tab[plist3->phcode]; plist3[0].ph = ph; if(plist3->phcode == phonSWITCH) { // change phoneme table SelectPhonemeTable(plist3->tone_ph); switched_language ^= SFLAG_SWITCHED_LANG; } next = phoneme_tab[plist3[1].phcode]; // the phoneme after this one plist3[1].ph = next; } if(ph == NULL) continue; InterpretPhoneme(tr, 0x100, plist3, &phdata); if((alternative = phdata.pd_param[pd_INSERTPHONEME]) > 0) { // PROBLEM: if we insert a phoneme before a vowel then we loose the stress. PHONEME_TAB *ph2; ph2 = ph; insert_ph = plist3->phcode; ph = phoneme_tab[alternative]; plist3->ph = ph; plist3->phcode = alternative; if(ph->type == phVOWEL) { plist3->synthflags |= SFLAG_SYLLABLE; if(ph2->type != phVOWEL) plist3->stresslevel = 0; // change from non-vowel to vowel, make sure it's unstressed } else plist3->synthflags &= ~SFLAG_SYLLABLE; // re-interpret the changed phoneme // But it doesn't obey a second ChangePhoneme() InterpretPhoneme(tr, 0x100, plist3, &phdata); } if((alternative = phdata.pd_param[pd_CHANGEPHONEME]) > 0) { PHONEME_TAB *ph2; ph2 = ph; ph = phoneme_tab[alternative]; plist3->ph = ph; plist3->phcode = alternative; if(alternative == 1) continue; // NULL phoneme, discard if(ph->type == phVOWEL) { plist3->synthflags |= SFLAG_SYLLABLE; if(ph2->type != phVOWEL) plist3->stresslevel = 0; // change from non-vowel to vowel, make sure it's unstressed } else plist3->synthflags &= ~SFLAG_SYLLABLE; // re-interpret the changed phoneme // But it doesn't obey a second ChangePhoneme() InterpretPhoneme(tr, 0x100, plist3, &phdata); } if(ph->type == phVOWEL) { PHONEME_LIST *p; // Check for consecutive unstressed syllables, even across word boundaries. // Do this after changing phonemes according to stress level. if(plist3->stresslevel <= 1) { // an unstressed vowel unstress_count++; if(tr->langopts.stress_flags & 0x08) { // change sequences of consecutive unstressed vowels in unstressed words to diminished stress (TEST) for(p=plist3+1; p->type != phPAUSE; p++) { if(p->type == phVOWEL) { if(p->stresslevel <= 1) { if(plist3->wordstress < 4) plist3->stresslevel = 0; if(p->wordstress < 4) p->stresslevel = 0; } break; } } } else { if((unstress_count > 1) && ((unstress_count & 1)==0)) { // in a sequence of unstressed syllables, reduce alternate syllables to 'diminished' // stress. But not for the last phoneme of a stressed word if((tr->langopts.stress_flags & 0x2) || ((word_stress > 3) && ((plist3+1)->sourceix!=0))) { // An unstressed final vowel of a stressed word unstress_count=1; // try again for next syllable } else { plist3->stresslevel = 0; // change stress to 'diminished' } } } } else { unstress_count = 0; } } if((plist3+1)->synthflags & SFLAG_LENGTHEN) { static char types_double[] = {phFRICATIVE,phVFRICATIVE,phNASAL,phLIQUID,0}; if(strchr(types_double,next->type)) { // lengthen this consonant by doubling it insert_ph = next->code; (plist3+1)->synthflags ^= SFLAG_LENGTHEN; } } if((plist3+1)->sourceix != 0) { int x; if(tr->langopts.vowel_pause && (ph->type != phPAUSE)) { if((ph->type != phVOWEL) && (tr->langopts.vowel_pause & 0x200)) { // add a pause after a word which ends in a consonant insert_ph = phonPAUSE_NOLINK; } if(next->type == phVOWEL) { if((x = tr->langopts.vowel_pause & 0x0c) != 0) { // break before a word which starts with a vowel if(x == 0xc) insert_ph = phonPAUSE_NOLINK; else insert_ph = phonPAUSE_VSHORT; } if((ph->type == phVOWEL) && ((x = tr->langopts.vowel_pause & 0x03) != 0)) { // adjacent vowels over a word boundary if(x == 2) insert_ph = phonPAUSE_SHORT; else insert_ph = phonPAUSE_VSHORT; } if(((plist3+1)->stresslevel >= 4) && (tr->langopts.vowel_pause & 0x100)) { // pause before a words which starts with a stressed vowel insert_ph = phonPAUSE_SHORT; } } } if(plist3 != plist3_inserted) { if((x = (tr->langopts.word_gap & 0x7)) != 0) { if((x > 1) || ((insert_ph != phonPAUSE_SHORT) && (insert_ph != phonPAUSE_NOLINK))) { // don't reduce the pause insert_ph = pause_phonemes[x]; } } if(option_wordgap > 0) { insert_ph = phonPAUSE_LONG; } } } next2 = phoneme_tab[plist3[2].phcode]; plist3[2].ph = next2; if((insert_ph == 0) && (phdata.pd_param[pd_APPENDPHONEME] != 0)) { insert_ph = phdata.pd_param[pd_APPENDPHONEME]; } if(ph->phflags & phVOICED) { // check that a voiced consonant is preceded or followed by a vowel or liquid // and if not, add a short schwa // not yet implemented } phlist[ix].ph = ph; phlist[ix].type = ph->type; phlist[ix].env = PITCHfall; // default, can be changed in the "intonation" module phlist[ix].synthflags = plist3->synthflags | switched_language; phlist[ix].stresslevel = plist3->stresslevel & 0xf; phlist[ix].wordstress = plist3->wordstress; phlist[ix].tone_ph = plist3->tone_ph; phlist[ix].sourceix = 0; phlist[ix].phcode = ph->code; if(plist3->sourceix != 0) { phlist[ix].sourceix = plist3->sourceix; phlist[ix].newword = 1; // this phoneme is the start of a word if(start_sentence) { phlist[ix].newword = 5; // start of sentence + start of word start_sentence = 0; } } else { phlist[ix].newword = 0; } // phlist[ix].length = ph->std_length; phlist[ix].length = phdata.pd_param[i_SET_LENGTH]*2; if((ph->code == phonPAUSE_LONG) && (option_wordgap > 0)) { phlist[ix].ph = phoneme_tab[phonPAUSE_SHORT]; phlist[ix].length = option_wordgap*14; // 10mS per unit at the default speed } if(ph->type==phVOWEL || ph->type==phLIQUID || ph->type==phNASAL || ph->type==phVSTOP || ph->type==phVFRICATIVE) { phlist[ix].length = 128; // length_mod phlist[ix].env = PITCHfall; } phlist[ix].prepause = 0; phlist[ix].amp = 20; // default, will be changed later phlist[ix].pitch1 = 255; phlist[ix].pitch2 = 255; ix++; } phlist[ix].newword = 2; // end of clause phlist[ix].phcode = phonPAUSE; phlist[ix].type = phPAUSE; // terminate with 2 Pause phonemes phlist[ix].length = post_pause; // length of the pause, depends on the punctuation phlist[ix].sourceix = end_sourceix; phlist[ix].synthflags = 0; phlist[ix++].ph = phoneme_tab[phonPAUSE]; phlist[ix].phcode = phonPAUSE; phlist[ix].type = phPAUSE; phlist[ix].length = 0; phlist[ix].sourceix=0; phlist[ix].synthflags = 0; phlist[ix++].ph = phoneme_tab[phonPAUSE_SHORT]; n_phoneme_list = ix; } // end of MakePhonemeList sources_5316/external/espeak/debug.h0000644000176700017670000000102311721443315016251 0ustar paulpaul#ifndef DEBUG_H #define DEBUG_H //#define DEBUG_ENABLED #ifdef DEBUG_ENABLED #define ENTER(text) debug_enter(text) #define SHOW(format,...) debug_show(format,__VA_ARGS__); #define SHOW_TIME(text) debug_time(text); extern void debug_enter(const char* text); extern void debug_show(const char* format,...); extern void debug_time(const char* text); #else #ifdef NO_VARIADIC_MACROS #define SHOW(format) // VC6 doesn't allow "..." #else #define SHOW(format,...) #endif #define SHOW_TIME(text) #define ENTER(text) #endif #endif sources_5316/external/espeak/portaudio18.h0000664000176700017670000003700511674622653017370 0ustar paulpaul// NOTE: Copy this file to portaudio.h in order to compile with V18 portaudio #ifndef PORT_AUDIO_H #define PORT_AUDIO_H #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ /* * $Id: portaudio.h,v 1.5 2002/03/26 18:04:22 philburk Exp $ * PortAudio Portable Real-Time Audio Library * PortAudio API Header File * Latest version available at: http://www.audiomulch.com/portaudio/ * * Copyright (c) 1999-2000 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. * */ typedef int PaError; typedef enum { paNoError = 0, paHostError = -10000, paInvalidChannelCount, paInvalidSampleRate, paInvalidDeviceId, paInvalidFlag, paSampleFormatNotSupported, paBadIODeviceCombination, paInsufficientMemory, paBufferTooBig, paBufferTooSmall, paNullCallback, paBadStreamPtr, paTimedOut, paInternalError, paDeviceUnavailable } PaErrorNum; /* Pa_Initialize() is the library initialisation function - call this before using the library. */ PaError Pa_Initialize( void ); /* Pa_Terminate() is the library termination function - call this after using the library. */ PaError Pa_Terminate( void ); /* Pa_GetHostError() returns a host specific error code. This can be called after receiving a PortAudio error code of paHostError. */ long Pa_GetHostError( void ); /* Pa_GetErrorText() translates the supplied PortAudio error number into a human readable message. */ const char *Pa_GetErrorText( PaError errnum ); /* Sample formats These are formats used to pass sound data between the callback and the stream. Each device has a "native" format which may be used when optimum efficiency or control over conversion is required. Formats marked "always available" are supported (emulated) by all PortAudio implementations. The floating point representation (paFloat32) uses +1.0 and -1.0 as the maximum and minimum respectively. paUInt8 is an unsigned 8 bit format where 128 is considered "ground" */ typedef unsigned long PaSampleFormat; #define paFloat32 ((PaSampleFormat) (1<<0)) /*always available*/ #define paInt16 ((PaSampleFormat) (1<<1)) /*always available*/ #define paInt32 ((PaSampleFormat) (1<<2)) /*always available*/ #define paInt24 ((PaSampleFormat) (1<<3)) #define paPackedInt24 ((PaSampleFormat) (1<<4)) #define paInt8 ((PaSampleFormat) (1<<5)) #define paUInt8 ((PaSampleFormat) (1<<6)) #define paCustomFormat ((PaSampleFormat) (1<<16)) /* Device enumeration mechanism. Device ids range from 0 to Pa_CountDevices()-1. Devices may support input, output or both. */ typedef int PaDeviceID; #define paNoDevice -1 int Pa_CountDevices( void ); typedef struct { int structVersion; const char *name; int maxInputChannels; int maxOutputChannels; /* Number of discrete rates, or -1 if range supported. */ int numSampleRates; /* Array of supported sample rates, or {min,max} if range supported. */ const double *sampleRates; PaSampleFormat nativeSampleFormats; } PaDeviceInfo; /* Pa_GetDefaultInputDeviceID(), Pa_GetDefaultOutputDeviceID() return the default device ids for input and output respectively, or paNoDevice if no device is available. The result can be passed to Pa_OpenStream(). On the PC, the user can specify a default device by setting an environment variable. For example, to use device #1. set PA_RECOMMENDED_OUTPUT_DEVICE=1 The user should first determine the available device ids by using the supplied application "pa_devs". */ PaDeviceID Pa_GetDefaultInputDeviceID( void ); PaDeviceID Pa_GetDefaultOutputDeviceID( void ); /* Pa_GetDeviceInfo() returns a pointer to an immutable PaDeviceInfo structure for the device specified. If the device parameter is out of range the function returns NULL. PortAudio manages the memory referenced by the returned pointer, the client must not manipulate or free the memory. The pointer is only guaranteed to be valid between calls to Pa_Initialize() and Pa_Terminate(). */ const PaDeviceInfo* Pa_GetDeviceInfo( PaDeviceID device ); /* PaTimestamp is used to represent a continuous sample clock with arbitrary start time that can be used for syncronization. The type is used for the outTime argument to the PortAudioCallback and as the result of Pa_StreamTime() */ typedef double PaTimestamp; /* PortAudioCallback is implemented by PortAudio clients. inputBuffer and outputBuffer are arrays of interleaved samples, the format, packing and number of channels used by the buffers are determined by parameters to Pa_OpenStream() (see below). framesPerBuffer is the number of sample frames to be processed by the callback. outTime is the time in samples when the buffer(s) processed by this callback will begin being played at the audio output. See also Pa_StreamTime() userData is the value of a user supplied pointer passed to Pa_OpenStream() intended for storing synthesis data etc. return value: The callback can return a non-zero value to stop the stream. This may be useful in applications such as soundfile players where a specific duration of output is required. However, it is not necessary to utilise this mechanism as StopStream() will also terminate the stream. A callback returning a non-zero value must fill the entire outputBuffer. NOTE: None of the other stream functions may be called from within the callback function except for Pa_GetCPULoad(). */ typedef int (PortAudioCallback)( void *inputBuffer, void *outputBuffer, unsigned long framesPerBuffer, PaTimestamp outTime, void *userData ); /* Stream flags These flags may be supplied (ored together) in the streamFlags argument to the Pa_OpenStream() function. */ #define paNoFlag (0) #define paClipOff (1<<0) /* disable default clipping of out of range samples */ #define paDitherOff (1<<1) /* disable default dithering */ #define paPlatformSpecificFlags (0x00010000) typedef unsigned long PaStreamFlags; /* A single PortAudioStream provides multiple channels of real-time input and output audio streaming to a client application. Pointers to PortAudioStream objects are passed between PortAudio functions. */ typedef void PortAudioStream; #define PaStream PortAudioStream /* Pa_OpenStream() opens a stream for either input, output or both. stream is the address of a PortAudioStream pointer which will receive a pointer to the newly opened stream. inputDevice is the id of the device used for input (see PaDeviceID above.) inputDevice may be paNoDevice to indicate that an input device is not required. numInputChannels is the number of channels of sound to be delivered to the callback. It can range from 1 to the value of maxInputChannels in the PaDeviceInfo record for the device specified by the inputDevice parameter. If inputDevice is paNoDevice numInputChannels is ignored. inputSampleFormat is the sample format of inputBuffer provided to the callback function. inputSampleFormat may be any of the formats described by the PaSampleFormat enumeration (see above). PortAudio guarantees support for the device's native formats (nativeSampleFormats in the device info record) and additionally 16 and 32 bit integer and 32 bit floating point formats. Support for other formats is implementation defined. inputDriverInfo is a pointer to an optional driver specific data structure containing additional information for device setup or stream processing. inputDriverInfo is never required for correct operation. If not used inputDriverInfo should be NULL. outputDevice is the id of the device used for output (see PaDeviceID above.) outputDevice may be paNoDevice to indicate that an output device is not required. numOutputChannels is the number of channels of sound to be supplied by the callback. See the definition of numInputChannels above for more details. outputSampleFormat is the sample format of the outputBuffer filled by the callback function. See the definition of inputSampleFormat above for more details. outputDriverInfo is a pointer to an optional driver specific data structure containing additional information for device setup or stream processing. outputDriverInfo is never required for correct operation. If not used outputDriverInfo should be NULL. sampleRate is the desired sampleRate. For full-duplex streams it is the sample rate for both input and output framesPerBuffer is the length in sample frames of all internal sample buffers used for communication with platform specific audio routines. Wherever possible this corresponds to the framesPerBuffer parameter passed to the callback function. numberOfBuffers is the number of buffers used for multibuffered communication with the platform specific audio routines. If you pass zero, then an optimum value will be chosen for you internally. This parameter is provided only as a guide - and does not imply that an implementation must use multibuffered i/o when reliable double buffering is available (such as SndPlayDoubleBuffer() on the Macintosh.) streamFlags may contain a combination of flags ORed together. These flags modify the behaviour of the streaming process. Some flags may only be relevant to certain buffer formats. callback is a pointer to a client supplied function that is responsible for processing and filling input and output buffers (see above for details.) userData is a client supplied pointer which is passed to the callback function. It could for example, contain a pointer to instance data necessary for processing the audio buffers. return value: Upon success Pa_OpenStream() returns PaNoError and places a pointer to a valid PortAudioStream in the stream argument. The stream is inactive (stopped). If a call to Pa_OpenStream() fails a non-zero error code is returned (see PaError above) and the value of stream is invalid. */ PaError Pa_OpenStream( PortAudioStream** stream, PaDeviceID inputDevice, int numInputChannels, PaSampleFormat inputSampleFormat, void *inputDriverInfo, PaDeviceID outputDevice, int numOutputChannels, PaSampleFormat outputSampleFormat, void *outputDriverInfo, double sampleRate, unsigned long framesPerBuffer, unsigned long numberOfBuffers, PaStreamFlags streamFlags, PortAudioCallback *callback, void *userData ); /* Pa_OpenDefaultStream() is a simplified version of Pa_OpenStream() that opens the default input and/or output devices. Most parameters have identical meaning to their Pa_OpenStream() counterparts, with the following exceptions: If either numInputChannels or numOutputChannels is 0 the respective device is not opened. This has the same effect as passing paNoDevice in the device arguments to Pa_OpenStream(). sampleFormat applies to both the input and output buffers. */ PaError Pa_OpenDefaultStream( PortAudioStream** stream, int numInputChannels, int numOutputChannels, PaSampleFormat sampleFormat, double sampleRate, unsigned long framesPerBuffer, unsigned long numberOfBuffers, PortAudioCallback *callback, void *userData ); /* Pa_CloseStream() closes an audio stream, flushing any pending buffers. */ PaError Pa_CloseStream( PortAudioStream* ); /* Pa_StartStream() and Pa_StopStream() begin and terminate audio processing. Pa_StopStream() waits until all pending audio buffers have been played. Pa_AbortStream() stops playing immediately without waiting for pending buffers to complete. */ PaError Pa_StartStream( PortAudioStream *stream ); PaError Pa_StopStream( PortAudioStream *stream ); PaError Pa_AbortStream( PortAudioStream *stream ); /* Pa_StreamActive() returns one (1) when the stream is active (ie playing or recording audio), zero (0) when not playing, or a negative error number if the stream is invalid. The stream is active between calls to Pa_StartStream() and Pa_StopStream(), but may also become inactive if the callback returns a non-zero value. In the latter case, the stream is considered inactive after the last buffer has finished playing. */ PaError Pa_StreamActive( PortAudioStream *stream ); /* Pa_StreamTime() returns the current output time in samples for the stream. This time may be used as a time reference (for example synchronizing audio to MIDI). */ PaTimestamp Pa_StreamTime( PortAudioStream *stream ); /* Pa_GetCPULoad() returns the CPU Load for the stream. The "CPU Load" is a fraction of total CPU time consumed by the stream's audio processing routines including, but not limited to the client supplied callback. A value of 0.5 would imply that PortAudio and the sound generating callback was consuming roughly 50% of the available CPU time. This function may be called from the callback function or the application. */ double Pa_GetCPULoad( PortAudioStream* stream ); /* Pa_GetMinNumBuffers() returns the minimum number of buffers required by the current host based on minimum latency. On the PC, for the DirectSound implementation, latency can be optionally set by user by setting an environment variable. For example, to set latency to 200 msec, put: set PA_MIN_LATENCY_MSEC=200 in the AUTOEXEC.BAT file and reboot. If the environment variable is not set, then the latency will be determined based on the OS. Windows NT has higher latency than Win95. */ int Pa_GetMinNumBuffers( int framesPerBuffer, double sampleRate ); /* Pa_Sleep() puts the caller to sleep for at least 'msec' milliseconds. You may sleep longer than the requested time so don't rely on this for accurate musical timing. Pa_Sleep() is provided as a convenience for authors of portable code (such as the tests and examples in the PortAudio distribution.) */ void Pa_Sleep( long msec ); /* Pa_GetSampleSize() returns the size in bytes of a single sample in the supplied PaSampleFormat, or paSampleFormatNotSupported if the format is no supported. */ PaError Pa_GetSampleSize( PaSampleFormat format ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PORT_AUDIO_H */ sources_5316/external/espeak/espeakdata_dicts.cpp0000664000176700017670002036544111723710247021036 0ustar paulpaul/* File espeakdata_dicts.cpp was generated on Thu Feb 23 14:34:18 2012 from all espeak-data/*_dict files: */ #include "espeakdata_FileInMemory.h" #include "Collection.h" #include "FileInMemory.h" #include "melder.h" FilesInMemory create_espeakdata_dicts () { try { autoFilesInMemory me = FilesInMemory_create (); static unsigned char espeakdata_dicts1_data[81298] = { 0, 4, 0, 0, 213, 80, 0, 0, 14, 69, 80, 245, 9, 85, 48, 47, 115, 89, 37, 109, 87, 0, 0, 0, 0, 0, 0, 10, 198, 88, 243, 210, 44, 243, 64, 66, 9, 9, 198, 80, 244, 142, 4, 67, 192, 66, 24, 74, 44, 243, 134, 101, 69, 5, 73, 66, 137, 20, 49, 108, 50, 81, 6, 121, 47, 111, 34, 78, 37, 0, 23, 65, 4, 35, 15, 49, 35, 48, 6, 110, 55, 35, 0, 81, 99, 97, 112, 112, 101, 108, 108, 97, 32, 0, 18, 71, 32, 81, 76, 80, 83, 65, 48, 105, 114, 55, 47, 13, 63, 35, 55, 0, 10, 199, 5, 69, 18, 4, 180, 201, 20, 66, 9, 198, 80, 241, 82, 36, 83, 128, 66, 0, 20, 72, 88, 243, 210, 56, 83, 69, 57, 48, 81, 115, 34, 50, 114, 63, 13, 50, 87, 0, 6, 195, 92, 19, 148, 8, 0, 11, 68, 88, 19, 142, 20, 81, 35, 50, 13, 0, 13, 68, 61, 1, 78, 16, 108, 48, 10, 106, 50, 47, 0, 12, 4, 1, 19, 39, 20, 35, 87, 13, 47, 0, 72, 10, 67, 80, 243, 153, 47, 118, 50, 37, 0, 0, 6, 65, 8, 69, 114, 0, 0, 10, 198, 92, 19, 142, 20, 84, 128, 65, 8, 6, 195, 76, 16, 131, 17, 0, 6, 195, 89, 48, 64, 17, 14, 67, 52, 82, 128, 63, 13, 57, 109, 81, 34, 118, 0, 24, 0, 0, 6, 65, 12, 87, 114, 0, 0, 0, 17, 10, 2, 18, 195, 188, 14, 8, 9, 12, 4, 5, 21, 100, 101, 0, 10, 13, 4, 95, 8, 1, 3, 49, 6, 113, 34, 108, 50, 0, 0, 0, 13, 69, 56, 81, 197, 21, 32, 50, 13, 134, 114, 34, 0, 10, 69, 32, 85, 201, 81, 64, 21, 0, 10, 6, 65, 16, 70, 114, 0, 0, 0, 0, 11, 68, 88, 144, 203, 76, 82, 37, 49, 87, 0, 0, 5, 65, 20, 114, 0, 0, 12, 201, 16, 85, 82, 77, 68, 129, 4, 193, 5, 66, 15, 70, 92, 18, 204, 60, 241, 128, 82, 113, 49, 55, 115, 81, 0, 0, 10, 67, 64, 243, 132, 48, 133, 50, 47, 0, 17, 4, 95, 48, 67, 15, 105, 6, 108, 50, 13, 34, 47, 87, 47, 13, 0, 0, 26, 73, 52, 244, 133, 48, 85, 1, 64, 20, 139, 63, 108, 34, 13, 55, 4, 106, 47, 35, 48, 6, 35, 34, 49, 0, 0, 8, 197, 60, 244, 140, 20, 112, 66, 14, 69, 36, 225, 129, 52, 80, 13, 50, 81, 113, 63, 13, 0, 22, 73, 48, 19, 135, 20, 226, 15, 88, 83, 128, 55, 35, 66, 13, 50, 105, 115, 81, 13, 50, 0, 6, 65, 24, 106, 81, 0, 0, 6, 195, 76, 21, 75, 17, 0, 0, 0, 8, 197, 28, 83, 129, 16, 80, 66, 21, 10, 13, 1, 20, 20, 8, 195, 169, 195, 188, 19, 63, 35, 47, 6, 37, 12, 109, 87, 0, 14, 69, 8, 83, 129, 16, 80, 69, 13, 50, 113, 70, 37, 0, 15, 69, 52, 243, 129, 12, 240, 63, 108, 50, 6, 113, 49, 40, 0, 6, 65, 28, 134, 114, 0, 0, 0, 8, 195, 44, 19, 128, 72, 11, 32, 18, 71, 12, 243, 5, 76, 33, 82, 28, 49, 115, 55, 87, 69, 110, 34, 134, 0, 0, 19, 72, 80, 84, 130, 48, 19, 131, 32, 80, 47, 13, 34, 69, 55, 113, 50, 89, 0, 0, 6, 65, 32, 105, 113, 0, 0, 13, 70, 24, 192, 85, 8, 84, 148, 21, 102, 114, 0, 10, 0, 8, 67, 48, 244, 132, 21, 0, 10, 0, 15, 70, 60, 211, 69, 44, 81, 82, 108, 63, 13, 49, 114, 34, 0, 10, 198, 36, 229, 21, 77, 49, 78, 8, 32, 10, 1, 35, 50, 108, 63, 13, 34, 0, 27, 0, 10, 69, 28, 21, 19, 9, 144, 21, 0, 10, 5, 65, 36, 37, 0, 6, 195, 5, 66, 214, 17, 0, 13, 6, 4, 195, 169, 10, 195, 160, 21, 102, 114, 0, 10, 13, 1, 37, 48, 13, 34, 87, 6, 106, 50, 47, 0, 27, 0, 14, 1, 38, 23, 35, 63, 48, 110, 34, 87, 35, 50, 47, 0, 0, 0, 18, 70, 77, 68, 153, 17, 35, 211, 87, 47, 34, 121, 47, 10, 34, 108, 87, 0, 16, 69, 20, 180, 197, 48, 96, 2, 110, 49, 87, 6, 110, 55, 81, 0, 6, 65, 40, 57, 114, 0, 0, 16, 70, 44, 21, 137, 4, 20, 128, 49, 35, 82, 37, 6, 113, 34, 0, 0, 8, 67, 76, 148, 128, 21, 0, 10, 10, 67, 12, 20, 140, 49, 113, 34, 112, 0, 9, 1, 42, 87, 47, 110, 34, 0, 27, 0, 20, 72, 52, 84, 133, 28, 80, 137, 20, 64, 63, 114, 34, 13, 134, 13, 69, 37, 47, 0, 16, 70, 4, 50, 197, 72, 208, 78, 35, 49, 13, 34, 63, 35, 50, 0, 10, 1, 43, 48, 55, 6, 109, 87, 0, 27, 0, 6, 65, 44, 49, 113, 0, 0, 0, 12, 71, 28, 83, 148, 48, 83, 65, 56, 21, 0, 10, 9, 1, 46, 48, 109, 50, 47, 0, 27, 0, 12, 68, 80, 19, 137, 4, 47, 35, 50, 57, 35, 0, 10, 1, 47, 87, 47, 34, 114, 48, 0, 27, 0, 14, 69, 17, 84, 214, 21, 32, 70, 109, 87, 81, 110, 34, 0, 6, 65, 48, 110, 55, 0, 0, 0, 12, 67, 52, 85, 128, 63, 13, 81, 34, 118, 0, 24, 0, 0, 6, 65, 52, 106, 63, 0, 0, 24, 11, 22, 5, 18, 1, 6, 7, 5, 12, 5, 195, 171, 81, 110, 34, 35, 81, 134, 13, 55, 114, 13, 0, 9, 198, 60, 244, 140, 20, 81, 128, 66, 0, 17, 70, 12, 128, 82, 37, 51, 65, 49, 35, 34, 6, 107, 87, 63, 35, 0, 0, 22, 72, 65, 35, 205, 21, 66, 5, 85, 48, 48, 34, 40, 63, 6, 114, 47, 37, 38, 109, 87, 0, 21, 72, 52, 20, 135, 5, 33, 84, 32, 16, 63, 35, 34, 134, 35, 34, 6, 114, 47, 35, 0, 0, 8, 197, 64, 20, 139, 36, 80, 65, 14, 69, 80, 19, 139, 92, 16, 47, 35, 66, 49, 58, 35, 0, 11, 5, 95, 48, 1, 14, 4, 11, 106, 50, 0, 6, 65, 56, 106, 50, 0, 0, 9, 198, 60, 225, 5, 73, 118, 76, 67, 0, 10, 199, 4, 19, 135, 4, 19, 132, 20, 66, 0, 21, 72, 44, 243, 15, 77, 49, 78, 76, 80, 49, 108, 55, 13, 87, 6, 132, 50, 87, 13, 0, 0, 9, 198, 60, 225, 5, 73, 113, 71, 67, 9, 197, 16, 16, 82, 60, 208, 8, 32, 5, 65, 60, 115, 0, 0, 17, 70, 21, 113, 78, 81, 114, 76, 114, 82, 13, 50, 47, 82, 13, 55, 0, 6, 194, 61, 0, 72, 12, 15, 70, 48, 82, 80, 60, 193, 20, 55, 120, 48, 108, 55, 47, 0, 13, 1, 61, 10, 134, 13, 55, 6, 121, 49, 10, 0, 27, 0, 12, 71, 16, 243, 129, 48, 68, 207, 56, 21, 0, 10, 16, 70, 12, 128, 82, 48, 83, 133, 89, 113, 55, 6, 37, 12, 50, 0, 0, 12, 68, 61, 32, 65, 48, 115, 34, 6, 113, 55, 0, 20, 72, 36, 224, 71, 56, 83, 73, 56, 112, 13, 50, 35, 134, 50, 114, 63, 13, 66, 0, 0, 7, 1, 64, 69, 121, 9, 0, 6, 65, 64, 48, 114, 0, 0, 16, 70, 4, 227, 129, 48, 85, 0, 35, 50, 35, 55, 6, 106, 47, 0, 0, 0, 0, 6, 65, 68, 49, 116, 0, 0, 16, 70, 32, 244, 193, 56, 224, 64, 105, 40, 87, 6, 35, 50, 35, 0, 0, 10, 199, 5, 52, 197, 77, 51, 210, 20, 67, 12, 199, 28, 85, 143, 48, 115, 9, 44, 66, 8, 32, 0, 0, 8, 197, 60, 209, 197, 20, 96, 66, 0, 8, 67, 80, 129, 79, 47, 117, 0, 11, 70, 12, 128, 82, 48, 84, 192, 21, 0, 10, 0, 15, 6, 1, 14, 4, 18, 195, 169, 6, 35, 50, 70, 34, 121, 0, 0, 0, 17, 70, 28, 85, 197, 48, 198, 83, 134, 114, 82, 13, 55, 55, 121, 87, 0, 6, 65, 76, 106, 87, 0, 0, 19, 71, 77, 0, 71, 32, 85, 20, 36, 87, 48, 2, 35, 79, 106, 47, 2, 37, 0, 0, 11, 136, 20, 21, 14, 9, 19, 9, 195, 171, 66, 18, 71, 44, 147, 66, 21, 35, 5, 100, 49, 37, 63, 69, 13, 34, 55, 37, 0, 17, 70, 16, 160, 75, 5, 37, 1, 73, 35, 49, 6, 35, 34, 47, 35, 0, 0, 0, 6, 65, 80, 47, 114, 0, 0, 17, 70, 48, 20, 193, 28, 225, 64, 55, 35, 87, 6, 35, 50, 57, 13, 0, 16, 70, 4, 33, 21, 48, 192, 72, 35, 69, 70, 6, 40, 55, 35, 0, 0, 0, 7, 196, 88, 243, 20, 20, 65, 0, 9, 198, 60, 225, 197, 92, 83, 147, 65, 5, 193, 84, 72, 32, 14, 69, 76, 19, 132, 72, 16, 87, 35, 50, 70, 34, 35, 0, 9, 198, 52, 20, 148, 36, 83, 147, 66, 15, 69, 84, 112, 78, 16, 16, 40, 79, 6, 35, 50, 70, 35, 0, 0, 14, 70, 64, 85, 71, 20, 245, 0, 48, 109, 12, 88, 118, 0, 0, 0, 22, 72, 76, 244, 200, 4, 225, 213, 88, 80, 87, 108, 89, 35, 66, 79, 6, 40, 12, 82, 106, 0, 0, 24, 73, 48, 19, 66, 61, 33, 200, 36, 226, 64, 55, 35, 63, 69, 108, 34, 79, 6, 37, 12, 50, 37, 0, 6, 65, 88, 81, 114, 0, 0, 9, 66, 5, 48, 4, 35, 87, 0, 8, 0, 0, 9, 68, 52, 16, 133, 48, 21, 0, 10, 11, 200, 12, 243, 147, 80, 19, 148, 36, 16, 66, 0, 13, 69, 64, 85, 9, 80, 80, 48, 13, 47, 37, 47, 0, 14, 69, 64, 85, 18, 85, 48, 48, 114, 47, 34, 109, 87, 0, 12, 1, 92, 47, 34, 116, 87, 47, 34, 114, 48, 0, 6, 65, 92, 82, 114, 0, 0, 16, 70, 56, 85, 10, 36, 84, 192, 50, 106, 12, 37, 78, 37, 87, 0, 16, 70, 36, 66, 76, 48, 84, 192, 37, 70, 6, 107, 55, 13, 87, 0, 0, 11, 67, 64, 244, 148, 48, 108, 34, 47, 0, 65, 24, 73, 29, 35, 194, 48, 84, 147, 16, 19, 0, 134, 34, 108, 69, 55, 13, 34, 87, 70, 6, 35, 55, 0, 0, 12, 68, 44, 17, 133, 20, 49, 35, 81, 6, 114, 0, 0, 7, 65, 96, 106, 49, 87, 0, 0, 17, 70, 64, 19, 5, 72, 211, 192, 48, 35, 55, 6, 110, 34, 63, 40, 0, 0, 16, 70, 56, 85, 10, 36, 84, 197, 50, 106, 37, 78, 37, 87, 13, 0, 0, 12, 68, 49, 80, 193, 76, 55, 40, 49, 35, 87, 0, 0, 17, 70, 76, 243, 132, 20, 225, 83, 87, 108, 50, 70, 13, 50, 106, 87, 0, 5, 65, 100, 121, 0, 0, 11, 67, 4, 211, 211, 6, 113, 63, 108, 87, 0, 9, 67, 80, 134, 83, 47, 121, 87, 0, 17, 70, 56, 21, 1, 76, 128, 64, 50, 2, 35, 47, 6, 35, 89, 35, 0, 0, 10, 199, 48, 85, 137, 80, 146, 213, 76, 66, 12, 71, 72, 240, 133, 73, 68, 207, 56, 21, 0, 10, 28, 67, 48, 244, 192, 55, 108, 87, 10, 6, 35, 50, 73, 13, 55, 37, 12, 86, 0, 81, 97, 110, 103, 101, 108, 101, 115, 32, 0, 10, 67, 8, 197, 77, 69, 55, 40, 63, 0, 0, 10, 69, 44, 83, 22, 36, 224, 21, 0, 10, 7, 65, 104, 86, 106, 70, 0, 0, 16, 70, 56, 148, 150, 4, 224, 64, 50, 13, 34, 82, 113, 50, 35, 0, 16, 70, 28, 20, 129, 28, 84, 192, 79, 13, 34, 113, 73, 13, 87, 0, 9, 67, 21, 84, 143, 126, 34, 40, 0, 17, 70, 76, 16, 146, 36, 224, 64, 87, 35, 69, 34, 6, 37, 50, 35, 0, 0, 19, 71, 88, 84, 132, 21, 32, 65, 56, 81, 111, 34, 70, 13, 34, 10, 113, 50, 0, 0, 11, 68, 64, 147, 143, 80, 48, 37, 50, 40, 0, 9, 198, 60, 225, 197, 48, 243, 198, 65, 19, 72, 29, 32, 72, 4, 212, 212, 4, 64, 134, 34, 113, 63, 87, 47, 35, 47, 0, 0, 14, 69, 44, 244, 1, 5, 32, 49, 108, 48, 10, 113, 34, 0, 0, 0, 18, 71, 72, 147, 80, 20, 194, 78, 28, 34, 107, 63, 48, 13, 55, 13, 66, 0, 0, 0, 8, 197, 76, 81, 5, 73, 64, 8, 0, 14, 70, 21, 66, 69, 56, 225, 64, 106, 47, 37, 13, 50, 0, 0, 0, 13, 68, 61, 32, 76, 20, 115, 34, 6, 113, 55, 13, 0, 0, 14, 69, 16, 19, 5, 56, 80, 70, 35, 55, 6, 114, 50, 0, 10, 69, 12, 192, 73, 72, 80, 21, 0, 10, 0, 18, 70, 52, 20, 148, 36, 226, 64, 63, 35, 34, 47, 6, 37, 12, 50, 37, 0, 17, 70, 88, 149, 129, 48, 66, 64, 82, 37, 82, 6, 35, 55, 70, 37, 0, 0, 0, 16, 70, 40, 84, 197, 8, 83, 0, 57, 114, 87, 13, 69, 110, 55, 0, 0, 0, 17, 70, 40, 19, 148, 92, 18, 192, 57, 35, 50, 47, 58, 6, 35, 49, 0, 16, 70, 16, 17, 5, 48, 146, 192, 70, 113, 70, 13, 55, 107, 49, 0, 17, 66, 5, 80, 118, 15, 48, 6, 111, 34, 0, 81, 112, 97, 105, 114, 32, 0, 10, 199, 16, 85, 82, 77, 64, 65, 56, 66, 0, 7, 196, 76, 19, 146, 8, 17, 0, 8, 197, 60, 225, 213, 57, 48, 65, 14, 69, 56, 19, 69, 57, 48, 50, 113, 63, 13, 50, 87, 0, 8, 197, 20, 180, 205, 4, 224, 65, 13, 69, 17, 83, 142, 21, 48, 70, 109, 50, 13, 87, 0, 0, 9, 198, 60, 225, 197, 52, 18, 192, 65, 0, 10, 1, 126, 47, 107, 55, 70, 13, 0, 27, 0, 0, 0, 11, 70, 12, 130, 67, 4, 115, 192, 21, 0, 10, 0, 0, 12, 68, 21, 33, 197, 72, 110, 34, 79, 13, 34, 0, 0, 0, 0, 15, 70, 92, 243, 19, 20, 193, 89, 58, 40, 55, 87, 55, 37, 0, 0, 0, 18, 70, 20, 193, 15, 72, 17, 15, 110, 55, 70, 108, 34, 6, 113, 70, 118, 0, 0, 15, 70, 16, 145, 134, 85, 84, 192, 70, 13, 81, 116, 12, 87, 0, 15, 70, 85, 68, 133, 12, 133, 0, 116, 47, 34, 110, 134, 47, 0, 0, 0, 14, 7, 3, 18, 195, 168, 3, 8, 5, 49, 34, 106, 89, 0, 0, 8, 197, 92, 16, 82, 60, 208, 8, 0, 9, 198, 76, 82, 212, 61, 33, 64, 66, 9, 198, 16, 242, 212, 61, 33, 64, 66, 14, 70, 72, 83, 133, 81, 65, 64, 34, 13, 50, 106, 47, 0, 0, 0, 11, 200, 88, 243, 19, 92, 19, 135, 21, 32, 65, 0, 0, 21, 66, 16, 16, 70, 35, 15, 82, 6, 37, 50, 74, 37, 0, 81, 118, 105, 110, 99, 105, 32, 0, 11, 70, 20, 20, 212, 28, 21, 5, 21, 0, 10, 0, 0, 14, 69, 88, 244, 137, 28, 80, 81, 115, 34, 13, 134, 13, 0, 16, 69, 76, 145, 83, 80, 16, 87, 37, 38, 6, 106, 87, 47, 35, 0, 14, 69, 29, 32, 78, 28, 80, 134, 34, 113, 50, 87, 37, 0, 14, 69, 20, 196, 193, 8, 80, 110, 55, 87, 13, 69, 37, 0, 0, 0, 7, 195, 16, 21, 0, 72, 11, 0, 7, 196, 44, 243, 148, 20, 65, 23, 72, 53, 5, 77, 4, 192, 78, 28, 16, 63, 48, 40, 12, 63, 35, 55, 6, 35, 66, 79, 35, 0, 8, 67, 48, 17, 25, 21, 0, 10, 0, 14, 69, 16, 80, 143, 72, 16, 70, 13, 69, 115, 34, 35, 0, 0, 17, 70, 32, 16, 129, 45, 82, 192, 105, 6, 35, 69, 35, 49, 109, 49, 0, 0, 18, 7, 4, 1, 14, 9, 195, 171, 12, 70, 6, 113, 50, 37, 12, 13, 55, 0, 0, 22, 72, 88, 84, 147, 36, 225, 1, 8, 16, 81, 111, 34, 87, 10, 13, 50, 70, 113, 69, 35, 0, 11, 200, 52, 148, 194, 73, 82, 75, 80, 80, 66, 12, 68, 88, 243, 22, 60, 82, 108, 55, 82, 40, 0, 0, 0, 15, 70, 44, 194, 77, 20, 145, 0, 49, 55, 107, 63, 121, 47, 0, 0, 0, 0, 0, 16, 70, 64, 144, 193, 77, 51, 192, 48, 37, 49, 6, 35, 87, 40, 0, 11, 70, 52, 20, 135, 5, 33, 84, 21, 0, 10, 0, 0, 16, 7, 19, 195, 169, 1, 14, 3, 5, 87, 2, 114, 131, 50, 87, 0, 0, 16, 70, 80, 84, 207, 85, 37, 83, 47, 13, 87, 118, 34, 109, 87, 0, 0, 0, 13, 67, 52, 228, 128, 63, 107, 50, 6, 114, 34, 0, 24, 0, 9, 68, 60, 113, 5, 56, 21, 0, 10, 0, 9, 198, 77, 64, 67, 12, 21, 15, 66, 0, 17, 70, 48, 20, 193, 73, 84, 192, 55, 113, 87, 13, 34, 2, 109, 87, 0, 15, 70, 13, 84, 211, 60, 228, 192, 49, 35, 87, 13, 50, 87, 0, 13, 66, 17, 32, 70, 6, 108, 49, 47, 13, 34, 0, 24, 16, 66, 9, 96, 69, 121, 81, 6, 115, 34, 69, 114, 55, 47, 0, 24, 0, 0, 12, 200, 36, 229, 5, 20, 225, 5, 20, 192, 66, 8, 13, 68, 40, 244, 213, 4, 57, 6, 115, 89, 37, 35, 0, 12, 68, 45, 34, 71, 20, 49, 34, 37, 134, 13, 0, 0, 12, 69, 76, 50, 15, 61, 32, 87, 49, 115, 34, 0, 0, 17, 70, 52, 244, 212, 21, 37, 0, 63, 6, 108, 87, 47, 13, 34, 47, 0, 0, 0, 11, 67, 8, 85, 1, 69, 114, 47, 35, 0, 9, 13, 68, 44, 83, 137, 4, 49, 37, 12, 50, 37, 35, 0, 0, 0, 9, 198, 65, 34, 77, 5, 65, 64, 66, 0, 0, 8, 196, 60, 225, 5, 72, 72, 12, 0, 13, 69, 24, 245, 82, 36, 80, 81, 40, 34, 6, 37, 0, 0, 0, 17, 71, 81, 34, 67, 32, 20, 132, 80, 47, 34, 37, 134, 113, 34, 47, 0, 0, 16, 70, 76, 83, 133, 44, 19, 0, 87, 114, 50, 13, 49, 35, 55, 0, 0, 14, 69, 28, 195, 210, 36, 16, 79, 55, 129, 34, 37, 35, 0, 12, 201, 4, 208, 78, 104, 147, 84, 61, 66, 64, 68, 0, 0, 11, 70, 88, 144, 212, 61, 34, 65, 21, 0, 10, 0, 11, 200, 60, 225, 197, 92, 83, 147, 16, 80, 67, 0, 0, 0, 9, 198, 84, 226, 70, 61, 35, 69, 67, 0, 7, 196, 76, 241, 1, 80, 8, 7, 196, 60, 209, 1, 80, 8, 0, 0, 0, 6, 195, 4, 224, 192, 17, 0, 12, 68, 29, 34, 69, 28, 79, 34, 37, 12, 79, 0, 0, 0, 10, 198, 56, 241, 212, 4, 228, 192, 8, 32, 0, 17, 70, 48, 243, 132, 20, 228, 197, 55, 108, 50, 70, 13, 50, 87, 13, 0, 11, 67, 8, 80, 64, 69, 37, 12, 57, 35, 0, 0, 0, 0, 0, 6, 195, 16, 145, 64, 72, 0, 10, 67, 105, 83, 21, 86, 40, 55, 40, 0, 0, 14, 69, 72, 243, 132, 21, 32, 34, 108, 50, 70, 13, 34, 0, 14, 69, 17, 83, 131, 4, 224, 70, 35, 66, 49, 14, 50, 0, 12, 69, 8, 245, 87, 21, 32, 69, 118, 13, 34, 0, 0, 0, 19, 71, 28, 83, 4, 20, 194, 75, 20, 134, 110, 55, 70, 13, 55, 13, 49, 13, 0, 0, 10, 67, 73, 81, 1, 34, 40, 70, 35, 0, 0, 14, 69, 49, 82, 68, 61, 0, 55, 125, 47, 10, 108, 48, 0, 10, 69, 72, 240, 133, 73, 64, 21, 0, 10, 15, 69, 8, 84, 212, 21, 32, 69, 6, 106, 87, 47, 13, 34, 0, 0, 12, 201, 60, 244, 133, 20, 226, 207, 53, 53, 5, 66, 19, 8, 5, 6, 5, 19, 9, 195, 171, 18, 37, 81, 6, 114, 87, 37, 13, 34, 0, 17, 8, 3, 9, 20, 18, 15, 195, 170, 14, 87, 13, 47, 34, 40, 50, 0, 15, 66, 16, 80, 70, 13, 15, 55, 35, 0, 72, 81, 108, 97, 32, 8, 66, 16, 80, 70, 13, 0, 9, 16, 70, 28, 243, 149, 8, 145, 64, 79, 13, 50, 40, 12, 69, 37, 0, 0, 0, 12, 68, 32, 147, 4, 20, 105, 37, 55, 70, 13, 0, 0, 8, 195, 32, 16, 82, 72, 9, 32, 16, 69, 76, 243, 1, 56, 176, 87, 2, 115, 55, 35, 66, 49, 0, 8, 16, 7, 11, 1, 14, 1, 195, 164, 14, 49, 113, 50, 113, 35, 50, 0, 0, 0, 18, 71, 64, 148, 143, 84, 85, 20, 20, 48, 13, 34, 40, 12, 6, 106, 47, 0, 20, 71, 4, 112, 77, 20, 211, 143, 56, 35, 134, 35, 63, 6, 106, 63, 50, 108, 50, 0, 0, 13, 68, 92, 83, 1, 24, 82, 110, 55, 10, 35, 81, 0, 9, 68, 9, 34, 65, 56, 21, 0, 10, 12, 4, 95, 4, 16, 20, 6, 48, 109, 50, 47, 0, 0, 0, 5, 194, 9, 144, 72, 16, 66, 17, 80, 70, 13, 15, 47, 123, 0, 81, 116, 111, 105, 116, 32, 19, 66, 17, 80, 70, 13, 15, 48, 34, 6, 114, 0, 81, 112, 114, 101, 101, 122, 32, 18, 66, 17, 80, 70, 13, 15, 48, 55, 123, 0, 81, 112, 108, 111, 111, 121, 32, 23, 66, 17, 80, 70, 40, 15, 48, 55, 13, 87, 6, 37, 0, 81, 112, 108, 101, 115, 115, 105, 115, 32, 24, 66, 17, 80, 70, 40, 15, 48, 37, 87, 6, 113, 50, 37, 0, 81, 112, 105, 115, 97, 110, 105, 101, 32, 5, 194, 17, 80, 72, 0, 10, 199, 80, 83, 141, 36, 228, 212, 20, 66, 0, 13, 68, 32, 19, 12, 60, 105, 6, 107, 55, 4, 118, 0, 11, 200, 20, 65, 76, 4, 112, 129, 72, 80, 67, 15, 7, 5, 21, 7, 195, 168, 14, 5, 116, 88, 6, 106, 50, 0, 0, 10, 67, 40, 80, 78, 88, 131, 50, 0, 41, 0, 0, 8, 67, 56, 82, 76, 21, 0, 10, 0, 12, 68, 80, 19, 135, 4, 47, 35, 66, 79, 35, 0, 8, 196, 80, 83, 147, 100, 66, 8, 7, 196, 56, 17, 1, 80, 8, 0, 8, 197, 24, 195, 210, 37, 48, 65, 19, 70, 4, 229, 15, 56, 149, 83, 35, 50, 47, 6, 115, 50, 37, 57, 109, 87, 0, 0, 6, 194, 4, 192, 8, 32, 17, 70, 40, 240, 67, 32, 147, 64, 57, 40, 58, 6, 113, 134, 13, 63, 0, 0, 0, 12, 68, 49, 82, 193, 76, 55, 40, 49, 35, 87, 0, 12, 68, 29, 33, 84, 4, 79, 34, 114, 47, 35, 0, 13, 4, 95, 20, 12, 4, 47, 6, 107, 55, 70, 13, 0, 0, 10, 69, 92, 21, 19, 60, 224, 21, 0, 10, 14, 69, 37, 48, 66, 20, 192, 37, 87, 13, 69, 110, 55, 0, 0, 9, 198, 4, 196, 133, 20, 68, 192, 66, 0, 16, 67, 20, 228, 192, 106, 50, 87, 115, 81, 115, 34, 47, 87, 0, 24, 0, 12, 68, 88, 83, 132, 4, 82, 106, 50, 70, 35, 0, 9, 68, 12, 242, 5, 56, 21, 0, 10, 0, 13, 69, 12, 131, 208, 36, 224, 89, 2, 108, 48, 131, 0, 0, 17, 70, 60, 213, 18, 20, 229, 0, 108, 63, 47, 34, 6, 106, 50, 47, 0, 22, 66, 21, 64, 106, 47, 87, 6, 106, 47, 13, 34, 35, 0, 81, 99, 101, 116, 101, 114, 97, 32, 9, 198, 4, 194, 66, 4, 208, 64, 67, 0, 0, 9, 198, 92, 16, 82, 32, 81, 78, 8, 16, 70, 85, 2, 78, 29, 67, 206, 35, 48, 37, 66, 47, 13, 50, 0, 0, 0, 17, 70, 52, 242, 1, 52, 209, 68, 63, 40, 105, 6, 35, 63, 13, 47, 0, 0, 0, 12, 137, 1, 7, 20, 5, 18, 23, 5, 195, 171, 67, 0, 0, 16, 70, 8, 147, 208, 76, 145, 64, 69, 37, 6, 108, 48, 87, 37, 0, 16, 70, 52, 243, 148, 4, 117, 64, 63, 108, 50, 47, 13, 49, 116, 0, 0, 0, 0, 0, 9, 198, 60, 244, 151, 4, 18, 64, 65, 0, 0, 9, 198, 72, 243, 132, 20, 83, 0, 66, 9, 68, 48, 245, 73, 76, 55, 124, 0, 0, 8, 197, 60, 244, 139, 60, 208, 66, 14, 69, 20, 97, 129, 80, 16, 106, 81, 6, 113, 47, 35, 0, 0, 0, 10, 67, 52, 241, 84, 63, 40, 47, 0, 32, 0, 9, 198, 88, 243, 210, 92, 16, 82, 66, 13, 68, 76, 243, 143, 64, 87, 108, 50, 10, 108, 48, 0, 11, 200, 60, 225, 197, 72, 145, 70, 36, 80, 65, 0, 16, 70, 24, 85, 1, 44, 16, 83, 81, 106, 47, 35, 49, 113, 87, 0, 13, 69, 76, 128, 82, 60, 224, 89, 110, 34, 14, 50, 0, 10, 69, 8, 244, 212, 60, 224, 21, 0, 10, 0, 11, 70, 92, 147, 12, 36, 19, 64, 21, 0, 10, 0, 0, 24, 72, 16, 84, 207, 56, 64, 78, 45, 48, 70, 106, 87, 19, 108, 50, 70, 35, 66, 49, 87, 0, 8, 32, 16, 70, 20, 147, 147, 80, 82, 78, 119, 50, 87, 47, 119, 12, 50, 0, 20, 9, 23, 1, 12, 12, 15, 14, 9, 195, 171, 82, 35, 55, 6, 115, 50, 37, 13, 0, 0, 14, 69, 8, 84, 212, 21, 48, 69, 106, 87, 47, 13, 87, 0, 23, 73, 12, 192, 78, 92, 147, 12, 36, 19, 64, 49, 55, 111, 50, 58, 6, 37, 55, 37, 13, 63, 0, 0, 10, 67, 52, 241, 83, 63, 40, 87, 0, 32, 15, 70, 44, 128, 89, 100, 19, 64, 49, 35, 57, 6, 35, 63, 0, 18, 5, 19, 13, 19, 39, 5, 106, 87, 10, 106, 63, 10, 6, 106, 87, 13, 0, 0, 0, 0, 11, 68, 8, 245, 8, 4, 69, 115, 47, 35, 0, 0, 14, 6, 14, 1, 21, 4, 195, 169, 50, 108, 70, 6, 114, 0, 0, 0, 16, 71, 76, 50, 18, 20, 147, 133, 72, 89, 34, 119, 50, 13, 34, 0, 0, 12, 68, 80, 19, 135, 60, 47, 35, 66, 134, 40, 0, 12, 68, 12, 147, 132, 100, 87, 107, 50, 70, 37, 0, 9, 68, 4, 115, 133, 76, 21, 0, 10, 12, 68, 44, 243, 135, 60, 49, 108, 66, 79, 40, 0, 0, 0, 17, 70, 56, 85, 19, 61, 113, 76, 50, 106, 47, 87, 115, 82, 110, 55, 0, 11, 70, 12, 128, 85, 12, 84, 128, 21, 0, 10, 0, 18, 71, 9, 82, 84, 21, 1, 82, 16, 69, 125, 47, 13, 48, 111, 34, 47, 0, 23, 10, 13, 1, 3, 5, 4, 15, 14, 9, 195, 171, 63, 35, 87, 13, 70, 6, 115, 50, 37, 13, 0, 24, 10, 2, 1, 2, 9, 12, 15, 14, 9, 195, 171, 69, 35, 69, 37, 55, 6, 115, 50, 37, 38, 13, 0, 0, 11, 68, 4, 195, 1, 32, 2, 35, 55, 113, 0, 18, 7, 9, 20, 1, 12, 9, 195, 171, 37, 47, 6, 113, 55, 37, 38, 13, 0, 22, 72, 4, 97, 193, 56, 148, 212, 4, 224, 35, 81, 79, 6, 35, 50, 37, 87, 47, 35, 50, 0, 0, 18, 70, 12, 20, 193, 56, 245, 129, 49, 35, 87, 35, 50, 6, 115, 82, 35, 0, 0, 0, 0, 11, 68, 32, 19, 143, 84, 105, 113, 50, 118, 0, 0, 18, 70, 76, 241, 15, 20, 225, 5, 87, 6, 115, 70, 4, 40, 50, 70, 13, 0, 0, 17, 70, 52, 20, 140, 20, 225, 64, 63, 35, 34, 55, 6, 114, 12, 50, 0, 21, 9, 1, 2, 9, 13, 195, 169, 12, 5, 7, 35, 69, 37, 50, 6, 114, 55, 106, 134, 0, 0, 17, 67, 36, 228, 208, 107, 50, 87, 48, 106, 49, 47, 6, 126, 34, 0, 24, 0, 13, 68, 88, 84, 129, 24, 81, 110, 34, 10, 35, 81, 0, 12, 68, 88, 19, 129, 24, 81, 35, 50, 35, 81, 0, 15, 70, 76, 50, 15, 20, 208, 78, 87, 49, 40, 63, 35, 50, 0, 0, 14, 69, 64, 19, 1, 92, 16, 48, 13, 55, 113, 82, 35, 0, 16, 69, 21, 52, 5, 4, 176, 37, 12, 38, 87, 48, 37, 12, 49, 0, 7, 195, 16, 149, 0, 72, 32, 0, 0, 19, 71, 76, 181, 76, 16, 83, 1, 76, 87, 49, 109, 55, 70, 13, 55, 35, 87, 0, 20, 71, 56, 20, 193, 72, 83, 133, 72, 50, 35, 87, 35, 34, 6, 114, 50, 13, 34, 0, 16, 70, 48, 148, 19, 80, 145, 75, 55, 107, 48, 87, 47, 37, 49, 0, 15, 70, 12, 129, 67, 44, 84, 147, 74, 106, 49, 13, 34, 87, 0, 15, 70, 53, 144, 149, 72, 114, 0, 63, 121, 69, 109, 34, 134, 0, 0, 13, 68, 52, 19, 1, 56, 63, 35, 55, 6, 35, 50, 0, 0, 14, 69, 52, 17, 1, 52, 80, 63, 35, 70, 6, 113, 63, 0, 13, 69, 52, 20, 148, 32, 16, 63, 35, 34, 47, 35, 0, 13, 69, 8, 84, 148, 32, 16, 69, 110, 34, 47, 35, 0, 0, 6, 195, 20, 243, 133, 66, 10, 67, 8, 83, 133, 69, 114, 50, 13, 0, 0, 0, 11, 200, 44, 192, 65, 77, 96, 75, 36, 80, 66, 15, 6, 10, 21, 14, 195, 173, 14, 134, 40, 50, 6, 37, 50, 0, 0, 10, 67, 41, 80, 78, 134, 58, 35, 50, 0, 16, 70, 28, 83, 210, 28, 147, 129, 73, 129, 73, 6, 37, 50, 35, 0, 17, 70, 16, 19, 137, 20, 195, 5, 70, 35, 50, 37, 38, 6, 110, 55, 0, 0, 11, 67, 105, 83, 65, 86, 40, 12, 63, 35, 0, 16, 70, 48, 21, 5, 28, 19, 128, 55, 113, 47, 13, 134, 35, 50, 0, 11, 70, 12, 194, 70, 80, 243, 128, 21, 0, 10, 0, 16, 70, 72, 145, 83, 48, 147, 135, 34, 37, 12, 87, 55, 37, 66, 0, 7, 195, 16, 19, 128, 8, 32, 20, 71, 52, 85, 21, 76, 19, 5, 52, 63, 13, 47, 6, 116, 87, 35, 55, 106, 63, 0, 19, 71, 64, 146, 197, 80, 33, 82, 28, 48, 13, 49, 106, 47, 69, 110, 34, 134, 0, 0, 0, 9, 198, 4, 100, 137, 12, 19, 129, 67, 0, 10, 67, 88, 84, 129, 82, 114, 34, 35, 0, 11, 70, 77, 65, 80, 32, 83, 128, 21, 0, 10, 0, 10, 67, 88, 84, 128, 81, 6, 111, 34, 0, 10, 199, 16, 85, 82, 28, 16, 78, 76, 65, 0, 16, 73, 52, 17, 1, 52, 242, 83, 20, 195, 5, 21, 102, 114, 0, 10, 0, 13, 69, 80, 129, 82, 60, 224, 47, 34, 6, 108, 50, 0, 10, 69, 48, 147, 9, 4, 224, 21, 0, 10, 0, 17, 70, 56, 146, 211, 92, 84, 132, 50, 107, 49, 87, 82, 111, 34, 47, 0, 15, 70, 88, 149, 137, 21, 36, 192, 82, 13, 82, 13, 57, 114, 0, 0, 0, 10, 67, 88, 84, 135, 81, 110, 34, 134, 0, 9, 68, 32, 83, 5, 56, 21, 0, 10, 0, 14, 69, 52, 244, 139, 20, 192, 63, 108, 34, 49, 13, 55, 0, 0, 0, 0, 19, 72, 12, 132, 137, 77, 66, 65, 4, 224, 49, 34, 107, 87, 47, 37, 113, 50, 0, 0, 23, 73, 8, 83, 1, 56, 116, 137, 44, 84, 128, 69, 13, 55, 35, 66, 34, 13, 49, 4, 107, 34, 0, 0, 0, 0, 0, 14, 69, 77, 80, 137, 21, 64, 87, 109, 69, 6, 37, 47, 0, 9, 198, 4, 193, 193, 4, 225, 5, 66, 0, 6, 194, 8, 240, 72, 12, 0, 18, 71, 13, 33, 83, 12, 83, 132, 60, 49, 34, 13, 89, 106, 50, 70, 40, 0, 23, 73, 72, 16, 200, 52, 19, 137, 56, 241, 134, 34, 35, 134, 63, 6, 35, 50, 37, 50, 108, 81, 0, 19, 71, 16, 83, 133, 52, 20, 139, 20, 70, 114, 50, 13, 63, 35, 34, 49, 13, 0, 18, 71, 8, 241, 75, 5, 33, 83, 80, 69, 40, 49, 35, 34, 106, 87, 47, 0, 0, 0, 16, 69, 36, 225, 21, 56, 16, 37, 50, 70, 6, 40, 12, 50, 35, 0, 15, 6, 13, 15, 18, 14, 195, 169, 63, 108, 34, 50, 6, 121, 0, 14, 69, 52, 243, 137, 12, 16, 63, 108, 50, 37, 49, 35, 0, 15, 69, 32, 83, 5, 56, 16, 105, 37, 55, 6, 114, 50, 35, 0, 13, 69, 8, 85, 19, 36, 80, 69, 106, 47, 87, 37, 0, 0, 0, 0, 0, 15, 69, 80, 245, 1, 48, 80, 47, 40, 47, 6, 113, 55, 13, 0, 14, 69, 56, 17, 5, 48, 80, 50, 113, 70, 114, 55, 13, 0, 18, 70, 52, 16, 193, 72, 243, 137, 63, 35, 49, 35, 34, 6, 115, 50, 37, 0, 21, 73, 12, 132, 137, 77, 67, 198, 24, 83, 0, 49, 34, 13, 87, 47, 108, 81, 13, 55, 0, 17, 69, 4, 209, 76, 36, 16, 35, 63, 6, 37, 12, 55, 37, 57, 35, 0, 14, 69, 28, 17, 1, 72, 16, 134, 13, 70, 113, 34, 35, 0, 0, 0, 17, 3, 226, 133, 148, 47, 58, 4, 114, 70, 6, 111, 34, 70, 13, 87, 0, 0, 13, 68, 72, 243, 133, 48, 34, 40, 50, 6, 110, 55, 0, 0, 18, 70, 40, 18, 207, 52, 147, 129, 57, 35, 49, 40, 63, 6, 37, 50, 35, 0, 0, 9, 198, 20, 180, 212, 20, 83, 128, 65, 16, 70, 45, 84, 149, 52, 19, 128, 49, 40, 34, 40, 63, 35, 50, 0, 0, 16, 70, 21, 33, 197, 72, 147, 135, 110, 34, 79, 13, 34, 13, 66, 0, 0, 12, 68, 16, 20, 133, 52, 70, 35, 34, 13, 63, 0, 14, 70, 12, 147, 147, 5, 85, 0, 87, 13, 50, 87, 115, 0, 11, 3, 226, 133, 147, 70, 111, 34, 70, 13, 0, 0, 15, 69, 36, 229, 5, 57, 48, 13, 50, 47, 6, 106, 50, 87, 0, 14, 69, 20, 193, 5, 73, 48, 110, 55, 70, 13, 34, 87, 0, 14, 73, 77, 4, 137, 56, 116, 212, 20, 83, 128, 21, 0, 10, 0, 10, 198, 60, 100, 203, 60, 243, 128, 66, 8, 9, 198, 88, 147, 10, 60, 83, 128, 66, 13, 70, 5, 98, 71, 56, 243, 128, 21, 102, 114, 0, 10, 0, 0, 9, 68, 20, 197, 137, 76, 21, 0, 10, 0, 19, 70, 5, 3, 212, 20, 244, 197, 35, 48, 108, 47, 37, 38, 6, 115, 87, 13, 0, 14, 69, 52, 245, 84, 60, 224, 63, 40, 47, 6, 108, 50, 0, 0, 9, 198, 8, 244, 203, 4, 20, 192, 66, 11, 70, 8, 80, 84, 48, 84, 192, 21, 0, 10, 16, 70, 52, 84, 211, 36, 20, 192, 63, 13, 87, 37, 57, 35, 87, 0, 15, 70, 8, 244, 12, 4, 20, 192, 69, 115, 48, 55, 113, 87, 0, 0, 10, 67, 4, 128, 64, 113, 105, 26, 113, 0, 19, 71, 52, 21, 82, 37, 66, 85, 76, 63, 108, 34, 6, 37, 89, 57, 109, 87, 0, 0, 9, 68, 92, 83, 132, 100, 21, 0, 10, 10, 3, 95, 49, 15, 10, 6, 114, 34, 0, 0, 0, 10, 3, 95, 49, 1, 10, 6, 114, 50, 0, 0, 14, 71, 8, 245, 82, 28, 83, 201, 76, 21, 102, 114, 0, 10, 9, 3, 226, 130, 172, 126, 34, 40, 0, 0, 19, 8, 22, 15, 195, 171, 12, 5, 14, 20, 81, 115, 13, 55, 10, 106, 50, 47, 0, 0, 0, 17, 70, 56, 244, 141, 4, 193, 64, 50, 108, 34, 63, 6, 113, 55, 13, 0, 0, 0, 24, 67, 64, 144, 203, 48, 4, 37, 49, 15, 13, 50, 15, 48, 6, 121, 0, 82, 110, 32, 112, 97, 121, 32, 10, 3, 95, 50, 15, 47, 58, 6, 114, 0, 0, 0, 9, 66, 20, 176, 110, 49, 0, 72, 32, 0, 0, 10, 67, 88, 84, 147, 81, 111, 34, 87, 0, 12, 68, 28, 83, 133, 72, 134, 114, 50, 13, 34, 0, 13, 68, 5, 51, 207, 44, 2, 35, 87, 10, 115, 49, 0, 0, 15, 69, 76, 19, 1, 52, 144, 87, 35, 55, 6, 113, 63, 37, 0, 7, 195, 32, 85, 0, 72, 32, 16, 69, 17, 99, 210, 4, 176, 70, 14, 82, 6, 129, 88, 35, 49, 0, 0, 16, 70, 81, 32, 71, 36, 82, 192, 47, 34, 35, 134, 6, 37, 49, 0, 17, 70, 9, 33, 89, 4, 226, 64, 69, 34, 37, 57, 6, 113, 50, 37, 0, 16, 70, 65, 33, 83, 80, 146, 192, 48, 34, 106, 87, 47, 37, 49, 0, 24, 74, 64, 245, 3, 32, 81, 147, 81, 35, 207, 52, 48, 108, 74, 107, 81, 87, 47, 34, 6, 115, 63, 0, 0, 11, 199, 60, 225, 5, 73, 113, 82, 64, 67, 36, 10, 199, 28, 84, 136, 5, 33, 21, 76, 66, 0, 9, 68, 40, 243, 133, 76, 21, 0, 10, 10, 3, 95, 51, 15, 70, 6, 111, 34, 0, 0, 15, 69, 76, 243, 149, 72, 80, 87, 108, 50, 10, 116, 34, 13, 0, 0, 6, 194, 37, 48, 72, 32, 0, 12, 71, 92, 147, 66, 48, 81, 15, 56, 21, 0, 10, 0, 20, 72, 5, 36, 143, 28, 19, 147, 36, 80, 35, 34, 40, 134, 6, 35, 50, 87, 37, 0, 12, 68, 76, 245, 8, 60, 87, 40, 12, 47, 40, 0, 9, 67, 41, 83, 135, 57, 40, 66, 0, 0, 0, 0, 9, 198, 32, 84, 139, 84, 193, 83, 65, 17, 70, 44, 19, 1, 24, 243, 135, 49, 35, 55, 35, 81, 6, 108, 66, 0, 0, 0, 0, 20, 9, 6, 18, 1, 14, 195, 167, 15, 9, 19, 81, 34, 131, 50, 87, 58, 6, 113, 0, 0, 6, 195, 16, 148, 192, 72, 14, 71, 12, 129, 86, 72, 243, 5, 80, 21, 102, 114, 0, 10, 0, 0, 15, 70, 56, 245, 83, 20, 64, 69, 50, 118, 87, 13, 70, 113, 0, 0, 16, 70, 80, 84, 85, 36, 192, 64, 47, 13, 49, 37, 12, 55, 35, 0, 16, 70, 44, 19, 9, 20, 96, 64, 49, 35, 55, 6, 37, 81, 35, 0, 17, 70, 56, 21, 1, 76, 160, 64, 50, 2, 35, 47, 6, 35, 89, 35, 0, 18, 70, 52, 21, 8, 36, 20, 192, 63, 35, 47, 6, 37, 12, 57, 35, 87, 0, 9, 198, 8, 84, 141, 84, 64, 64, 66, 0, 19, 71, 65, 33, 84, 61, 34, 85, 76, 48, 34, 13, 47, 115, 34, 37, 109, 87, 0, 0, 20, 72, 29, 34, 69, 44, 83, 1, 56, 64, 134, 34, 37, 49, 13, 55, 35, 50, 47, 0, 0, 9, 197, 60, 244, 150, 4, 192, 66, 36, 10, 69, 56, 83, 19, 60, 224, 21, 0, 10, 0, 25, 74, 76, 225, 69, 84, 32, 76, 20, 97, 133, 44, 87, 50, 117, 69, 35, 55, 10, 37, 81, 4, 106, 49, 0, 10, 67, 8, 85, 197, 69, 114, 82, 13, 0, 17, 70, 76, 81, 129, 56, 160, 64, 87, 13, 81, 6, 35, 50, 57, 35, 0, 14, 4, 95, 13, 3, 14, 63, 6, 35, 49, 34, 108, 50, 0, 0, 20, 71, 28, 192, 68, 36, 21, 15, 72, 134, 55, 35, 70, 37, 6, 113, 47, 108, 34, 0, 0, 15, 70, 72, 145, 75, 21, 37, 0, 34, 37, 49, 13, 34, 47, 0, 0, 0, 0, 20, 71, 52, 20, 203, 21, 34, 78, 28, 63, 35, 87, 49, 6, 114, 34, 13, 66, 0, 9, 15, 69, 32, 20, 132, 61, 0, 105, 35, 34, 47, 19, 108, 48, 0, 16, 6, 11, 1, 195, 175, 18, 15, 49, 35, 10, 6, 37, 34, 40, 0, 0, 12, 68, 64, 20, 139, 20, 48, 35, 34, 49, 13, 0, 14, 70, 8, 83, 142, 21, 69, 0, 69, 106, 50, 13, 47, 0, 0, 17, 70, 76, 147, 129, 28, 241, 197, 87, 13, 50, 13, 134, 115, 134, 13, 0, 25, 73, 28, 241, 1, 48, 208, 71, 80, 145, 192, 134, 108, 47, 10, 35, 55, 63, 6, 35, 134, 47, 13, 134, 0, 10, 69, 77, 69, 65, 73, 64, 21, 0, 10, 14, 69, 29, 84, 212, 5, 96, 79, 40, 87, 47, 35, 81, 0, 0, 9, 198, 52, 20, 211, 4, 193, 64, 66, 15, 70, 12, 81, 9, 48, 193, 64, 87, 13, 70, 107, 55, 13, 0, 14, 70, 64, 244, 147, 12, 129, 64, 48, 108, 34, 89, 13, 0, 15, 70, 21, 53, 5, 48, 193, 64, 2, 37, 87, 47, 110, 55, 0, 0, 0, 7, 196, 76, 244, 1, 76, 66, 13, 68, 16, 149, 129, 56, 70, 37, 82, 6, 35, 50, 0, 9, 198, 4, 197, 5, 52, 149, 0, 67, 12, 5, 10, 15, 19, 195, 169, 21, 101, 115, 0, 10, 0, 18, 70, 36, 228, 207, 52, 226, 65, 13, 50, 87, 108, 63, 50, 37, 57, 35, 0, 16, 69, 32, 83, 5, 56, 80, 105, 37, 12, 55, 6, 37, 12, 50, 0, 0, 0, 20, 71, 92, 83, 9, 77, 112, 65, 72, 82, 6, 110, 55, 14, 87, 82, 113, 34, 0, 8, 11, 70, 56, 144, 200, 60, 192, 83, 21, 0, 10, 18, 71, 76, 147, 135, 5, 3, 197, 72, 87, 37, 66, 79, 35, 48, 40, 34, 0, 0, 21, 72, 88, 243, 210, 52, 19, 9, 28, 80, 81, 115, 34, 63, 6, 113, 55, 13, 134, 13, 0, 12, 68, 88, 84, 130, 100, 81, 13, 34, 69, 121, 0, 11, 68, 60, 244, 140, 20, 115, 34, 55, 13, 0, 27, 13, 19, 20, 15, 3, 11, 5, 14, 19, 20, 18, 195, 182, 13, 87, 47, 108, 49, 13, 50, 87, 47, 34, 115, 63, 0, 11, 68, 24, 20, 129, 60, 81, 113, 34, 115, 0, 12, 68, 12, 84, 133, 76, 87, 114, 34, 13, 87, 0, 12, 3, 95, 55, 15, 87, 6, 114, 82, 13, 50, 0, 0, 19, 70, 77, 80, 149, 72, 34, 65, 87, 109, 69, 6, 109, 34, 69, 37, 57, 35, 0, 12, 201, 32, 243, 198, 76, 16, 75, 48, 146, 192, 66, 0, 9, 198, 60, 224, 146, 84, 146, 192, 65, 0, 12, 71, 77, 83, 142, 101, 50, 68, 20, 21, 0, 10, 0, 11, 68, 4, 68, 137, 20, 113, 70, 34, 37, 0, 24, 73, 64, 130, 76, 4, 65, 76, 64, 130, 65, 81, 13, 55, 13, 70, 6, 110, 55, 81, 37, 38, 35, 0, 17, 6, 95, 18, 15, 13, 1, 14, 34, 40, 63, 6, 121, 50, 87, 13, 0, 0, 0, 0, 10, 199, 4, 113, 210, 21, 52, 201, 20, 66, 9, 198, 32, 84, 131, 84, 193, 83, 65, 0, 16, 70, 12, 132, 137, 76, 160, 78, 49, 34, 107, 87, 57, 35, 50, 0, 0, 0, 7, 194, 20, 224, 72, 8, 32, 0, 10, 199, 16, 148, 204, 20, 180, 201, 20, 66, 13, 3, 95, 51, 88, 6, 70, 110, 34, 47, 107, 134, 0, 0, 21, 9, 8, 5, 12, 12, 15, 195, 175, 19, 5, 105, 106, 55, 40, 58, 6, 37, 12, 86, 0, 13, 3, 95, 48, 67, 6, 105, 108, 50, 13, 34, 47, 0, 0, 8, 197, 60, 228, 129, 4, 64, 65, 27, 69, 29, 32, 65, 24, 96, 134, 34, 113, 81, 15, 34, 13, 50, 6, 106, 47, 0, 81, 114, 101, 105, 110, 101, 116, 32, 13, 69, 12, 86, 76, 60, 224, 87, 13, 55, 108, 50, 0, 0, 14, 70, 77, 68, 129, 85, 52, 192, 87, 47, 34, 127, 87, 0, 0, 19, 71, 52, 145, 23, 36, 229, 5, 72, 63, 107, 70, 82, 13, 50, 47, 13, 34, 0, 0, 13, 72, 92, 20, 200, 36, 225, 212, 60, 224, 21, 0, 10, 11, 3, 95, 57, 15, 50, 114, 134, 13, 50, 0, 0, 14, 69, 76, 19, 85, 20, 192, 87, 113, 63, 116, 13, 55, 0, 0, 17, 70, 29, 35, 206, 17, 148, 192, 134, 34, 129, 50, 47, 10, 121, 87, 0, 9, 198, 21, 32, 83, 53, 84, 192, 66, 0, 10, 199, 28, 84, 148, 73, 82, 68, 4, 66, 0, 9, 68, 12, 20, 143, 48, 21, 0, 10, 0, 0, 14, 70, 76, 50, 21, 81, 65, 64, 87, 49, 109, 47, 13, 0, 14, 70, 4, 227, 133, 81, 65, 64, 35, 50, 6, 106, 47, 0, 0, 0, 0, 0, 16, 70, 88, 84, 135, 21, 65, 64, 81, 13, 34, 134, 114, 47, 13, 0, 16, 70, 69, 82, 74, 61, 65, 64, 49, 37, 134, 6, 108, 47, 106, 0, 15, 3, 95, 49, 57, 6, 50, 114, 134, 13, 50, 47, 37, 50, 0, 0, 13, 3, 95, 49, 56, 10, 6, 35, 134, 47, 37, 50, 0, 0, 0, 14, 69, 57, 83, 69, 72, 144, 50, 109, 63, 13, 34, 37, 0, 13, 69, 20, 224, 207, 72, 80, 131, 66, 49, 129, 34, 0, 15, 69, 52, 18, 149, 8, 16, 63, 35, 57, 6, 40, 69, 35, 0, 0, 0, 0, 20, 72, 88, 84, 140, 4, 225, 211, 80, 80, 81, 13, 34, 55, 35, 66, 87, 47, 13, 0, 8, 196, 4, 117, 5, 72, 72, 12, 0, 15, 69, 4, 97, 193, 56, 80, 35, 81, 79, 6, 113, 50, 13, 0, 8, 197, 80, 246, 79, 80, 16, 66, 11, 3, 226, 136, 146, 63, 37, 50, 109, 87, 0, 0, 6, 194, 33, 144, 72, 32, 11, 70, 29, 33, 71, 61, 38, 64, 21, 0, 10, 11, 3, 95, 49, 49, 10, 6, 110, 55, 81, 0, 0, 10, 3, 95, 49, 48, 6, 47, 37, 50, 0, 0, 11, 200, 12, 19, 142, 20, 195, 15, 56, 144, 67, 13, 3, 95, 49, 51, 6, 70, 110, 34, 47, 37, 50, 0, 0, 13, 3, 95, 49, 50, 6, 47, 58, 6, 113, 55, 81, 0, 0, 13, 3, 95, 49, 53, 6, 81, 121, 81, 47, 37, 50, 0, 0, 9, 67, 40, 242, 12, 57, 115, 55, 0, 13, 3, 95, 49, 52, 6, 81, 114, 34, 47, 37, 50, 0, 0, 15, 3, 95, 49, 55, 6, 87, 114, 82, 13, 50, 47, 37, 50, 0, 0, 17, 70, 72, 81, 5, 16, 83, 5, 34, 114, 70, 13, 70, 114, 55, 13, 0, 13, 3, 95, 49, 54, 6, 87, 106, 87, 47, 37, 50, 0, 0, 0, 9, 198, 52, 84, 131, 20, 65, 83, 66, 15, 3, 95, 55, 88, 6, 87, 114, 82, 13, 50, 47, 107, 134, 0, 0, 12, 68, 76, 245, 133, 72, 87, 115, 81, 110, 34, 0, 11, 68, 12, 132, 137, 76, 49, 34, 107, 87, 0, 0, 0, 9, 198, 60, 224, 133, 29, 34, 80, 65, 0, 0, 0, 0, 16, 70, 89, 32, 80, 73, 148, 192, 81, 34, 113, 48, 34, 121, 87, 0, 0, 18, 71, 77, 65, 80, 32, 19, 149, 76, 87, 47, 13, 81, 113, 50, 109, 87, 0, 0, 0, 0, 17, 70, 76, 243, 66, 21, 33, 64, 87, 6, 108, 63, 69, 13, 34, 13, 0, 16, 70, 69, 82, 88, 61, 65, 64, 49, 37, 134, 6, 108, 47, 106, 0, 0, 20, 8, 3, 5, 19, 1, 18, 195, 169, 1, 87, 13, 87, 13, 34, 37, 12, 57, 35, 0, 0, 0, 0, 9, 198, 45, 83, 20, 85, 33, 64, 66, 0, 0, 22, 72, 48, 148, 197, 57, 50, 65, 5, 64, 55, 13, 87, 132, 50, 87, 37, 38, 6, 113, 47, 0, 0, 16, 70, 52, 148, 212, 21, 34, 69, 63, 13, 87, 47, 114, 34, 37, 0, 9, 198, 24, 16, 212, 61, 69, 77, 66, 15, 69, 84, 197, 78, 16, 144, 40, 55, 6, 40, 50, 70, 37, 0, 0, 17, 70, 64, 20, 16, 21, 33, 76, 48, 35, 48, 13, 34, 6, 110, 55, 0, 0, 17, 70, 60, 225, 5, 73, 34, 71, 108, 50, 13, 34, 6, 107, 134, 0, 36, 10, 199, 4, 19, 135, 21, 50, 69, 56, 8, 0, 12, 68, 24, 244, 148, 20, 81, 108, 34, 47, 13, 0, 24, 68, 12, 20, 144, 20, 49, 35, 34, 48, 106, 15, 70, 37, 12, 106, 63, 0, 81, 100, 105, 101, 109, 32, 7, 196, 40, 244, 137, 76, 65, 9, 68, 32, 83, 146, 100, 21, 0, 10, 0, 15, 69, 56, 17, 193, 56, 16, 50, 35, 79, 6, 113, 50, 35, 0, 0, 9, 198, 60, 225, 197, 49, 146, 192, 65, 17, 70, 44, 20, 9, 81, 65, 76, 49, 35, 48, 6, 107, 47, 13, 55, 0, 20, 9, 13, 1, 20, 20, 8, 5, 195, 188, 19, 63, 35, 47, 6, 37, 12, 109, 87, 0, 16, 7, 7, 5, 14, 195, 168, 22, 5, 88, 13, 50, 106, 12, 82, 0, 0, 14, 3, 95, 50, 88, 6, 47, 58, 107, 50, 47, 107, 134, 0, 0, 9, 68, 16, 21, 137, 16, 21, 0, 10, 17, 67, 65, 33, 83, 48, 34, 13, 87, 13, 70, 6, 106, 50, 47, 0, 24, 0, 0, 0, 0, 26, 12, 11, 14, 1, 16, 19, 5, 11, 195, 170, 18, 5, 12, 49, 50, 35, 48, 87, 13, 49, 111, 34, 13, 55, 0, 10, 3, 95, 56, 15, 10, 6, 35, 134, 0, 0, 14, 69, 48, 242, 193, 5, 48, 55, 108, 49, 10, 113, 87, 0, 9, 197, 4, 225, 5, 73, 48, 8, 32, 0, 0, 0, 0, 0, 0, 16, 70, 25, 32, 78, 12, 242, 83, 81, 34, 35, 50, 89, 58, 35, 0, 0, 14, 68, 37, 53, 90, 84, 37, 87, 6, 40, 12, 86, 40, 0, 13, 3, 95, 63, 63, 87, 13, 63, 69, 6, 115, 55, 0, 0, 19, 8, 9, 18, 15, 14, 9, 5, 195, 171, 37, 34, 40, 50, 6, 37, 12, 13, 0, 14, 69, 36, 225, 9, 20, 224, 107, 50, 70, 37, 50, 0, 36, 9, 67, 28, 81, 78, 134, 114, 50, 0, 17, 70, 4, 97, 193, 4, 228, 197, 35, 81, 79, 6, 113, 50, 87, 13, 0, 20, 8, 1, 12, 7, 5, 18, 9, 195, 171, 35, 55, 134, 6, 114, 34, 114, 12, 14, 0, 0, 11, 70, 13, 147, 148, 32, 144, 64, 21, 0, 10, 0, 8, 67, 28, 81, 64, 134, 114, 0, 18, 71, 12, 132, 137, 77, 66, 65, 56, 49, 34, 107, 87, 47, 37, 35, 50, 0, 20, 71, 48, 17, 25, 9, 32, 78, 16, 55, 121, 70, 37, 69, 34, 6, 35, 50, 47, 0, 13, 3, 95, 52, 88, 6, 81, 114, 34, 47, 107, 134, 0, 0, 0, 16, 69, 88, 84, 132, 21, 32, 81, 6, 110, 34, 70, 13, 34, 0, 8, 10, 69, 21, 35, 133, 77, 64, 21, 0, 10, 20, 70, 104, 147, 66, 4, 37, 197, 86, 107, 12, 63, 69, 6, 35, 69, 10, 58, 106, 0, 0, 15, 70, 77, 86, 133, 81, 65, 64, 87, 40, 86, 6, 106, 47, 0, 10, 67, 60, 193, 193, 108, 55, 79, 35, 0, 15, 70, 52, 83, 1, 56, 145, 64, 63, 13, 55, 113, 50, 37, 0, 0, 0, 0, 14, 69, 72, 82, 197, 57, 64, 34, 114, 49, 13, 50, 47, 0, 8, 67, 40, 240, 78, 21, 0, 10, 10, 69, 32, 19, 76, 21, 64, 21, 0, 10, 0, 25, 74, 64, 81, 1, 48, 81, 5, 53, 2, 78, 28, 48, 13, 70, 113, 55, 13, 70, 106, 63, 48, 13, 66, 0, 5, 194, 56, 16, 72, 8, 66, 48, 80, 55, 13, 0, 9, 17, 70, 64, 244, 148, 84, 112, 76, 48, 108, 34, 47, 116, 134, 35, 55, 0, 0, 10, 199, 60, 244, 147, 81, 35, 207, 52, 66, 13, 3, 95, 53, 88, 6, 81, 121, 81, 47, 107, 134, 0, 0, 13, 68, 76, 241, 18, 4, 87, 115, 70, 34, 6, 113, 0, 7, 196, 76, 241, 18, 4, 8, 9, 68, 72, 245, 133, 72, 21, 0, 10, 0, 16, 73, 8, 245, 82, 28, 83, 201, 76, 145, 64, 21, 102, 114, 0, 10, 12, 69, 64, 145, 82, 72, 80, 48, 6, 114, 34, 0, 14, 69, 21, 35, 69, 48, 240, 110, 34, 63, 13, 55, 115, 0, 0, 25, 74, 76, 19, 135, 20, 209, 69, 57, 50, 193, 64, 87, 35, 50, 134, 13, 63, 114, 50, 87, 49, 35, 48, 0, 0, 17, 71, 76, 86, 67, 32, 83, 12, 20, 87, 121, 89, 6, 110, 55, 13, 0, 0, 0, 8, 197, 60, 244, 147, 20, 80, 66, 0, 6, 194, 41, 144, 72, 32, 9, 198, 16, 241, 66, 4, 18, 64, 66, 0, 20, 71, 72, 245, 5, 72, 83, 132, 20, 34, 40, 47, 6, 114, 34, 13, 50, 70, 13, 0, 13, 3, 95, 54, 88, 6, 87, 106, 87, 47, 107, 134, 0, 0, 23, 73, 60, 33, 82, 4, 211, 69, 72, 112, 85, 115, 69, 13, 34, 6, 35, 63, 13, 34, 79, 127, 0, 0, 24, 73, 16, 244, 212, 60, 161, 87, 76, 178, 64, 70, 108, 87, 47, 108, 57, 6, 106, 82, 87, 49, 37, 0, 22, 73, 28, 244, 132, 60, 228, 194, 4, 18, 64, 79, 129, 34, 70, 13, 50, 87, 69, 6, 120, 0, 0, 16, 70, 44, 133, 77, 4, 195, 192, 49, 40, 63, 6, 113, 55, 40, 0, 17, 7, 2, 15, 7, 15, 20, 195, 161, 69, 108, 79, 108, 47, 6, 113, 0, 0, 19, 71, 16, 85, 82, 20, 229, 25, 16, 70, 116, 13, 34, 13, 50, 47, 121, 47, 0, 18, 71, 8, 85, 8, 48, 82, 5, 52, 69, 106, 47, 10, 55, 37, 106, 63, 0, 0, 13, 70, 52, 243, 147, 36, 85, 82, 21, 102, 114, 0, 10, 21, 72, 32, 84, 146, 101, 49, 78, 37, 48, 105, 110, 34, 6, 121, 87, 13, 50, 13, 87, 0, 17, 70, 32, 20, 148, 77, 65, 82, 105, 35, 34, 47, 87, 47, 110, 34, 0, 0, 14, 69, 73, 84, 208, 21, 48, 34, 109, 87, 48, 13, 87, 0, 8, 197, 5, 52, 18, 37, 48, 66, 0, 9, 67, 40, 241, 89, 73, 118, 37, 0, 0, 0, 0, 17, 70, 81, 51, 197, 56, 19, 73, 47, 87, 40, 50, 6, 113, 63, 37, 0, 17, 70, 52, 19, 8, 21, 32, 133, 63, 35, 55, 6, 110, 34, 69, 13, 0, 0, 16, 70, 16, 146, 215, 20, 196, 192, 70, 107, 49, 82, 13, 55, 87, 0, 17, 70, 76, 17, 193, 72, 144, 64, 87, 35, 134, 35, 34, 6, 37, 35, 0, 11, 70, 40, 84, 211, 36, 48, 64, 21, 0, 10, 18, 70, 28, 19, 9, 48, 80, 64, 134, 35, 55, 13, 55, 6, 37, 12, 35, 0, 0, 0, 0, 10, 69, 17, 84, 212, 36, 224, 21, 0, 10, 0, 0, 20, 71, 5, 48, 70, 77, 64, 78, 16, 35, 87, 10, 35, 81, 87, 47, 35, 50, 47, 0, 8, 195, 40, 245, 64, 72, 9, 32, 9, 67, 52, 21, 68, 63, 129, 70, 0, 13, 3, 95, 56, 88, 6, 47, 35, 134, 47, 107, 134, 0, 0, 0, 20, 8, 1, 12, 2, 1, 14, 9, 195, 171, 35, 55, 69, 6, 113, 50, 114, 12, 14, 0, 0, 0, 0, 21, 73, 72, 144, 200, 5, 33, 19, 8, 16, 73, 34, 37, 74, 13, 70, 87, 69, 6, 120, 0, 0, 23, 73, 44, 19, 69, 72, 17, 5, 72, 145, 64, 49, 35, 63, 13, 34, 113, 70, 13, 34, 6, 37, 0, 0, 13, 70, 12, 128, 82, 48, 145, 64, 74, 113, 55, 37, 0, 0, 15, 3, 95, 57, 88, 6, 50, 114, 134, 13, 50, 47, 107, 134, 0, 0, 0, 13, 69, 12, 241, 206, 4, 48, 49, 108, 65, 35, 49, 0, 6, 195, 52, 85, 0, 72, 0, 0, 15, 70, 64, 130, 76, 48, 148, 19, 81, 107, 55, 13, 48, 87, 0, 20, 71, 44, 193, 79, 64, 21, 18, 4, 49, 55, 117, 12, 48, 6, 113, 47, 34, 35, 0, 0, 19, 72, 4, 229, 15, 36, 225, 84, 80, 80, 35, 50, 47, 40, 50, 6, 106, 47, 0, 0, 14, 69, 12, 20, 9, 80, 16, 49, 35, 48, 37, 47, 35, 0, 13, 69, 4, 209, 76, 20, 80, 35, 63, 13, 55, 114, 0, 20, 8, 2, 15, 12, 9, 22, 9, 195, 171, 69, 40, 55, 6, 107, 82, 37, 12, 13, 0, 0, 9, 198, 52, 19, 5, 4, 114, 64, 67, 15, 70, 76, 50, 15, 49, 70, 128, 87, 49, 129, 55, 47, 87, 0, 12, 3, 95, 63, 65, 55, 6, 106, 47, 13, 34, 0, 0, 23, 73, 76, 197, 73, 80, 85, 197, 56, 16, 82, 87, 55, 125, 47, 10, 114, 82, 13, 50, 113, 34, 0, 10, 199, 60, 227, 205, 92, 243, 132, 20, 67, 19, 71, 76, 80, 129, 77, 66, 65, 56, 87, 13, 69, 35, 87, 47, 37, 35, 50, 0, 0, 17, 70, 44, 19, 69, 72, 241, 78, 49, 35, 63, 13, 34, 6, 40, 50, 0, 0, 0, 0, 0, 0, 18, 70, 77, 84, 137, 56, 19, 69, 87, 116, 34, 37, 50, 6, 113, 63, 13, 0, 0, 10, 3, 19, 39, 14, 87, 13, 50, 0, 72, 0, 5, 194, 36, 224, 72, 10, 3, 226, 153, 175, 49, 34, 125, 87, 0, 0, 0, 9, 68, 72, 240, 137, 56, 21, 0, 10, 9, 3, 226, 153, 173, 63, 108, 55, 0, 0, 0, 17, 70, 44, 21, 5, 80, 84, 128, 49, 35, 47, 6, 114, 47, 13, 34, 0, 0, 10, 199, 76, 48, 82, 48, 21, 20, 36, 66, 14, 4, 95, 15, 7, 15, 115, 134, 115, 50, 4, 110, 49, 0, 0, 0, 15, 69, 52, 20, 148, 36, 224, 63, 6, 113, 34, 47, 13, 50, 0, 10, 69, 8, 83, 147, 60, 224, 21, 0, 10, 8, 197, 8, 20, 211, 60, 224, 66, 0, 15, 70, 64, 85, 15, 61, 36, 192, 48, 13, 47, 115, 34, 87, 0, 15, 70, 48, 245, 66, 76, 84, 128, 55, 118, 48, 89, 13, 34, 0, 15, 70, 8, 244, 132, 20, 21, 88, 69, 108, 34, 70, 6, 118, 0, 0, 20, 71, 28, 84, 141, 60, 193, 78, 20, 73, 107, 12, 63, 13, 55, 6, 37, 12, 50, 0, 15, 70, 24, 84, 146, 20, 148, 129, 81, 13, 34, 111, 34, 13, 0, 0, 0, 17, 70, 77, 65, 82, 92, 83, 147, 87, 47, 110, 34, 82, 13, 50, 87, 0, 10, 198, 52, 148, 194, 73, 82, 75, 66, 36, 21, 73, 20, 225, 197, 48, 36, 133, 12, 133, 0, 106, 66, 13, 55, 69, 34, 110, 134, 47, 0, 0, 0, 18, 70, 64, 192, 83, 20, 229, 1, 48, 55, 35, 87, 6, 106, 50, 47, 35, 0, 10, 199, 36, 225, 197, 88, 243, 7, 20, 67, 0, 19, 8, 13, 1, 2, 1, 12, 195, 170, 12, 63, 35, 69, 35, 55, 6, 110, 55, 0, 0, 0, 0, 13, 6, 18, 5, 14, 195, 169, 5, 34, 13, 50, 121, 0, 17, 70, 52, 21, 8, 36, 193, 1, 63, 35, 47, 6, 107, 55, 70, 35, 0, 21, 67, 77, 84, 20, 87, 40, 48, 34, 106, 50, 47, 106, 50, 70, 6, 106, 50, 47, 0, 24, 0, 33, 68, 52, 241, 21, 76, 63, 4, 115, 70, 109, 87, 15, 115, 48, 13, 34, 6, 35, 50, 70, 37, 0, 81, 111, 112, 101, 114, 97, 110, 100, 105, 32, 0, 8, 197, 60, 212, 133, 16, 80, 66, 13, 69, 60, 85, 86, 72, 80, 109, 12, 82, 34, 13, 0, 15, 69, 56, 21, 21, 72, 80, 50, 35, 47, 6, 116, 34, 13, 0, 0, 0, 11, 199, 60, 225, 5, 73, 51, 197, 44, 67, 36, 10, 199, 16, 85, 82, 45, 37, 73, 76, 66, 20, 71, 52, 19, 148, 61, 96, 78, 36, 63, 35, 50, 47, 108, 82, 6, 113, 50, 37, 0, 13, 67, 28, 83, 140, 134, 13, 50, 13, 34, 113, 55, 0, 0, 9, 198, 52, 20, 211, 4, 19, 0, 66, 21, 72, 12, 20, 16, 84, 48, 201, 56, 240, 49, 35, 48, 40, 74, 6, 37, 12, 50, 40, 0, 22, 68, 80, 128, 66, 4, 47, 35, 69, 6, 113, 15, 50, 74, 40, 0, 81, 110, 99, 104, 117, 32, 13, 72, 8, 243, 142, 36, 85, 129, 48, 80, 21, 0, 10, 0, 16, 69, 12, 20, 201, 56, 240, 49, 35, 87, 6, 37, 12, 50, 118, 0, 14, 69, 48, 83, 206, 36, 80, 55, 37, 6, 115, 50, 37, 0, 0, 9, 198, 88, 243, 8, 20, 145, 0, 65, 0, 22, 73, 77, 112, 78, 28, 84, 147, 92, 16, 82, 87, 58, 35, 66, 13, 34, 87, 58, 113, 34, 0, 23, 67, 65, 35, 192, 48, 34, 115, 15, 81, 6, 108, 34, 63, 35, 0, 81, 102, 111, 114, 109, 97, 32, 19, 71, 8, 244, 212, 4, 19, 132, 20, 69, 6, 115, 87, 47, 113, 50, 70, 13, 0, 7, 195, 4, 19, 128, 72, 12, 20, 71, 64, 83, 9, 56, 64, 66, 4, 48, 110, 55, 13, 50, 70, 6, 113, 69, 35, 0, 0, 22, 72, 20, 193, 77, 20, 229, 1, 48, 80, 106, 55, 13, 63, 106, 50, 47, 6, 113, 55, 13, 0, 0, 13, 69, 16, 85, 82, 73, 144, 70, 126, 34, 34, 121, 0, 16, 67, 65, 35, 198, 48, 34, 40, 81, 6, 106, 87, 13, 34, 0, 24, 0, 21, 9, 13, 9, 12, 9, 20, 195, 170, 18, 5, 63, 107, 55, 13, 47, 6, 111, 34, 13, 0, 8, 3, 195, 161, 19, 35, 87, 0, 11, 70, 52, 21, 82, 20, 83, 128, 21, 0, 10, 9, 198, 40, 244, 132, 4, 19, 128, 66, 11, 70, 12, 19, 69, 72, 243, 128, 21, 0, 10, 14, 4, 95, 48, 77, 50, 63, 107, 55, 57, 6, 40, 50, 0, 0, 15, 4, 95, 48, 77, 51, 63, 107, 55, 57, 6, 35, 34, 47, 0, 0, 11, 68, 52, 20, 137, 20, 63, 113, 34, 37, 0, 0, 15, 4, 95, 48, 77, 49, 6, 70, 6, 125, 87, 13, 50, 47, 0, 0, 17, 70, 24, 147, 5, 52, 243, 128, 81, 6, 37, 55, 13, 63, 108, 50, 0, 16, 4, 95, 2, 18, 22, 49, 6, 108, 34, 47, 114, 49, 13, 50, 0, 0, 9, 198, 92, 19, 8, 4, 195, 1, 66, 0, 0, 0, 15, 70, 52, 83, 9, 77, 48, 64, 63, 13, 55, 107, 87, 35, 0, 14, 70, 24, 148, 195, 32, 84, 128, 81, 37, 89, 13, 34, 0, 11, 70, 8, 83, 3, 32, 84, 128, 21, 0, 10, 0, 18, 70, 76, 83, 129, 80, 244, 133, 87, 13, 50, 35, 47, 6, 115, 34, 13, 0, 14, 71, 13, 35, 201, 77, 48, 78, 80, 21, 102, 114, 0, 10, 0, 10, 67, 52, 20, 129, 63, 113, 34, 35, 0, 0, 9, 198, 45, 112, 78, 77, 82, 83, 66, 17, 70, 44, 21, 19, 92, 147, 139, 49, 35, 47, 87, 82, 13, 50, 49, 0, 13, 69, 72, 85, 9, 20, 96, 34, 13, 47, 37, 81, 0, 0, 9, 198, 20, 83, 139, 20, 84, 128, 65, 16, 70, 16, 17, 211, 80, 84, 128, 70, 35, 134, 87, 47, 110, 34, 0, 0, 19, 71, 8, 84, 206, 20, 65, 78, 20, 69, 13, 87, 50, 114, 70, 13, 50, 13, 0, 10, 199, 9, 34, 84, 80, 19, 138, 20, 66, 0, 0, 16, 70, 88, 84, 146, 21, 113, 71, 81, 110, 34, 13, 82, 110, 134, 0, 0, 11, 70, 28, 147, 2, 21, 37, 0, 21, 0, 10, 0, 18, 71, 64, 243, 137, 21, 1, 82, 76, 48, 115, 50, 37, 48, 110, 34, 87, 0, 0, 0, 0, 9, 198, 60, 244, 147, 21, 49, 64, 66, 0, 10, 67, 24, 244, 148, 81, 108, 34, 47, 0, 8, 67, 29, 86, 64, 21, 0, 10, 18, 71, 8, 241, 68, 5, 1, 83, 80, 69, 40, 70, 35, 48, 106, 87, 47, 0, 0, 21, 72, 8, 17, 5, 56, 131, 210, 77, 64, 69, 113, 70, 13, 50, 105, 108, 34, 87, 47, 0, 0, 8, 197, 40, 84, 193, 40, 16, 66, 10, 69, 8, 241, 73, 56, 112, 21, 0, 10, 0, 0, 0, 12, 68, 8, 244, 137, 76, 69, 108, 34, 13, 87, 0, 0, 21, 73, 88, 241, 76, 20, 229, 8, 20, 145, 0, 81, 40, 55, 13, 50, 47, 105, 121, 47, 0, 15, 70, 72, 243, 201, 64, 84, 147, 34, 123, 48, 111, 34, 87, 0, 8, 197, 44, 147, 79, 56, 240, 66, 13, 69, 76, 20, 16, 32, 240, 87, 35, 48, 81, 40, 0, 14, 69, 12, 80, 201, 48, 80, 87, 13, 87, 37, 12, 55, 0, 0, 6, 194, 53, 144, 72, 32, 0, 9, 198, 77, 66, 76, 77, 118, 69, 65, 20, 71, 76, 19, 136, 20, 68, 137, 56, 87, 35, 50, 105, 6, 114, 70, 34, 13, 50, 0, 0, 22, 72, 12, 132, 137, 77, 66, 65, 56, 16, 49, 34, 13, 87, 47, 37, 57, 6, 113, 50, 35, 0, 0, 16, 70, 56, 81, 197, 72, 147, 135, 50, 13, 134, 114, 34, 13, 66, 0, 16, 70, 8, 85, 197, 72, 147, 135, 69, 13, 82, 114, 34, 107, 66, 0, 18, 70, 88, 84, 213, 88, 149, 83, 82, 13, 87, 40, 12, 82, 37, 109, 87, 0, 0, 0, 17, 71, 76, 50, 5, 21, 1, 82, 76, 87, 49, 114, 48, 13, 34, 87, 0, 0, 19, 72, 52, 19, 13, 21, 48, 149, 73, 144, 63, 113, 63, 87, 69, 13, 34, 37, 0, 0, 15, 69, 29, 32, 84, 37, 48, 134, 34, 6, 113, 47, 13, 87, 0, 14, 69, 4, 226, 77, 85, 48, 35, 50, 37, 63, 40, 87, 0, 0, 6, 194, 60, 96, 72, 8, 16, 70, 8, 16, 137, 48, 243, 128, 69, 35, 69, 37, 55, 108, 50, 0, 0, 20, 71, 92, 81, 199, 21, 113, 78, 76, 82, 110, 134, 13, 82, 6, 106, 12, 50, 87, 0, 17, 70, 52, 17, 5, 48, 83, 133, 63, 35, 70, 13, 55, 6, 114, 50, 0, 17, 70, 52, 17, 5, 48, 83, 133, 63, 35, 70, 13, 55, 6, 114, 50, 0, 12, 71, 5, 35, 83, 81, 35, 206, 28, 21, 0, 10, 0, 0, 0, 11, 70, 72, 22, 77, 60, 225, 0, 21, 0, 10, 12, 70, 77, 4, 137, 56, 116, 192, 21, 0, 41, 10, 0, 16, 70, 28, 83, 133, 72, 193, 73, 134, 114, 50, 13, 34, 55, 121, 0, 20, 71, 56, 81, 133, 73, 66, 84, 36, 50, 106, 81, 13, 34, 47, 6, 37, 47, 37, 0, 0, 0, 9, 198, 88, 244, 133, 56, 64, 71, 67, 24, 73, 5, 34, 83, 80, 245, 5, 48, 84, 192, 35, 34, 37, 87, 47, 6, 115, 47, 13, 55, 106, 87, 0, 19, 70, 76, 19, 148, 36, 17, 207, 87, 35, 50, 47, 37, 38, 6, 113, 79, 40, 0, 0, 18, 70, 60, 225, 1, 56, 180, 192, 6, 108, 50, 70, 35, 66, 49, 87, 0, 8, 0, 11, 70, 88, 84, 143, 56, 144, 193, 21, 0, 10, 0, 11, 67, 52, 145, 193, 63, 6, 37, 134, 35, 0, 17, 7, 3, 18, 15, 14, 10, 195, 169, 49, 34, 108, 50, 57, 6, 114, 0, 0, 0, 13, 202, 44, 83, 142, 37, 53, 129, 5, 33, 9, 28, 65, 15, 70, 40, 21, 207, 61, 33, 0, 57, 113, 82, 115, 34, 47, 0, 16, 70, 8, 244, 135, 20, 225, 64, 69, 108, 34, 134, 13, 50, 13, 0, 0, 10, 67, 52, 17, 192, 63, 35, 134, 0, 32, 0, 8, 67, 52, 20, 153, 21, 0, 10, 0, 0, 15, 70, 28, 84, 136, 5, 33, 0, 134, 110, 34, 35, 34, 47, 0, 0, 14, 70, 72, 82, 78, 21, 69, 5, 34, 13, 50, 106, 47, 0, 19, 70, 16, 244, 143, 80, 129, 65, 70, 108, 34, 13, 47, 6, 37, 12, 57, 35, 0, 0, 21, 72, 28, 80, 146, 60, 177, 78, 21, 32, 134, 13, 69, 34, 115, 49, 13, 50, 13, 34, 0, 0, 13, 69, 80, 84, 193, 4, 208, 47, 13, 87, 113, 63, 0, 0, 0, 16, 70, 4, 229, 8, 60, 226, 69, 35, 50, 47, 6, 115, 50, 37, 0, 12, 5, 16, 5, 18, 195, 186, 48, 13, 34, 40, 0, 0, 8, 67, 52, 146, 197, 21, 0, 10, 0, 9, 197, 60, 225, 5, 84, 112, 65, 9, 22, 73, 56, 19, 1, 80, 145, 200, 20, 145, 0, 50, 113, 55, 6, 113, 47, 13, 134, 121, 47, 0, 10, 69, 32, 148, 16, 36, 80, 21, 0, 10, 0, 0, 10, 199, 88, 243, 210, 48, 83, 148, 20, 65, 11, 70, 88, 148, 135, 36, 226, 65, 21, 0, 10, 19, 71, 40, 244, 197, 64, 130, 78, 4, 57, 115, 87, 13, 81, 6, 37, 50, 35, 0, 17, 71, 8, 194, 71, 56, 21, 76, 80, 69, 55, 107, 134, 50, 118, 47, 0, 13, 6, 18, 8, 195, 180, 14, 5, 21, 102, 114, 0, 10, 0, 22, 72, 45, 83, 147, 52, 21, 9, 28, 80, 49, 109, 50, 87, 63, 6, 113, 47, 13, 134, 13, 0, 0, 21, 73, 25, 32, 78, 76, 50, 8, 60, 82, 192, 81, 34, 131, 50, 87, 105, 6, 40, 49, 0, 0, 12, 4, 95, 3, 9, 18, 49, 6, 35, 48, 37, 0, 0, 0, 20, 72, 76, 179, 204, 48, 145, 78, 21, 48, 87, 49, 108, 55, 37, 50, 4, 106, 87, 0, 16, 70, 12, 132, 153, 76, 193, 82, 49, 34, 119, 87, 55, 13, 34, 0, 13, 68, 52, 33, 75, 36, 63, 69, 106, 12, 49, 37, 0, 0, 13, 69, 56, 20, 211, 5, 80, 50, 35, 87, 6, 118, 0, 14, 69, 8, 82, 197, 73, 48, 69, 114, 49, 13, 34, 87, 0, 0, 6, 195, 36, 34, 83, 65, 0, 21, 71, 81, 32, 80, 21, 50, 85, 52, 47, 34, 35, 48, 6, 114, 87, 37, 12, 109, 63, 0, 0, 7, 196, 60, 227, 73, 56, 65, 0, 0, 9, 198, 36, 226, 204, 84, 148, 192, 66, 16, 70, 28, 83, 133, 76, 148, 192, 134, 114, 50, 13, 87, 13, 87, 0, 16, 70, 76, 80, 213, 56, 64, 64, 87, 13, 49, 40, 50, 70, 35, 0, 0, 19, 71, 12, 132, 137, 77, 66, 78, 20, 49, 34, 13, 87, 47, 6, 37, 12, 50, 0, 0, 0, 23, 73, 17, 34, 78, 44, 80, 146, 60, 84, 128, 70, 34, 107, 50, 49, 13, 69, 34, 40, 12, 34, 0, 0, 16, 70, 24, 195, 210, 36, 64, 64, 81, 55, 108, 34, 37, 70, 35, 0, 0, 13, 4, 95, 19, 20, 11, 87, 47, 34, 6, 114, 48, 0, 0, 20, 72, 48, 145, 70, 16, 84, 208, 20, 192, 55, 37, 81, 70, 13, 87, 48, 110, 55, 0, 0, 9, 198, 80, 245, 19, 36, 83, 147, 66, 20, 73, 52, 245, 73, 48, 193, 80, 84, 229, 0, 63, 40, 55, 37, 48, 109, 50, 47, 0, 12, 4, 95, 1, 3, 21, 35, 49, 6, 116, 47, 0, 0, 18, 70, 37, 50, 193, 72, 147, 212, 37, 87, 49, 6, 35, 34, 37, 108, 47, 0, 0, 12, 201, 4, 117, 5, 73, 53, 5, 88, 243, 210, 68, 17, 70, 17, 85, 133, 56, 17, 197, 70, 116, 82, 13, 50, 113, 134, 13, 0, 0, 0, 8, 197, 88, 19, 132, 5, 64, 65, 7, 195, 76, 19, 0, 72, 32, 0, 17, 70, 16, 17, 207, 72, 65, 64, 70, 35, 134, 10, 108, 34, 70, 13, 0, 0, 0, 0, 13, 69, 32, 81, 76, 8, 240, 105, 114, 55, 69, 115, 0, 15, 69, 60, 32, 68, 40, 16, 115, 69, 6, 35, 47, 57, 35, 0, 18, 70, 48, 83, 206, 5, 33, 15, 55, 117, 12, 50, 6, 35, 34, 70, 40, 0, 0, 0, 18, 71, 12, 132, 137, 77, 66, 78, 4, 49, 34, 13, 87, 47, 37, 50, 35, 0, 13, 4, 95, 18, 14, 7, 6, 113, 50, 69, 110, 55, 0, 0, 16, 70, 60, 101, 5, 92, 83, 0, 108, 81, 47, 13, 82, 110, 55, 0, 9, 198, 32, 241, 86, 20, 83, 0, 8, 0, 13, 69, 28, 84, 148, 36, 80, 79, 107, 12, 47, 37, 0, 0, 17, 70, 9, 84, 149, 56, 66, 64, 69, 40, 34, 6, 40, 50, 70, 37, 0, 0, 20, 71, 4, 229, 8, 60, 226, 85, 76, 35, 50, 47, 6, 115, 50, 37, 38, 109, 87, 0, 21, 67, 33, 69, 16, 105, 113, 47, 114, 47, 114, 48, 6, 114, 10, 0, 81, 58, 47, 47, 32, 0, 0, 0, 17, 70, 92, 147, 8, 20, 195, 64, 82, 13, 55, 105, 110, 55, 14, 63, 0, 0, 19, 71, 44, 243, 80, 84, 196, 201, 20, 49, 108, 63, 48, 6, 109, 55, 87, 37, 0, 0, 0, 14, 69, 32, 83, 1, 5, 48, 105, 114, 55, 6, 113, 87, 0, 0, 0, 0, 0, 8, 197, 32, 84, 141, 60, 224, 65, 0, 17, 70, 36, 227, 133, 77, 65, 76, 107, 50, 50, 106, 87, 47, 13, 55, 0, 0, 9, 67, 21, 32, 64, 114, 34, 35, 0, 9, 67, 72, 19, 12, 34, 113, 55, 0, 15, 6, 7, 18, 15, 22, 195, 169, 134, 34, 40, 82, 6, 114, 0, 0, 16, 7, 5, 12, 19, 1, 2, 195, 169, 110, 55, 87, 13, 69, 37, 0, 0, 0, 15, 70, 60, 81, 9, 65, 84, 192, 115, 70, 37, 48, 109, 87, 0, 15, 70, 8, 20, 130, 5, 32, 64, 69, 113, 69, 13, 34, 35, 0, 0, 19, 71, 52, 20, 148, 32, 147, 149, 76, 63, 35, 34, 47, 6, 37, 50, 109, 87, 0, 0, 9, 68, 52, 144, 77, 36, 21, 0, 10, 0, 0, 17, 70, 28, 195, 194, 4, 193, 64, 134, 55, 115, 69, 6, 113, 55, 13, 0, 17, 4, 95, 1, 3, 50, 70, 6, 109, 69, 13, 55, 35, 49, 116, 47, 0, 0, 0, 0, 24, 73, 64, 21, 18, 36, 245, 9, 76, 209, 64, 48, 35, 47, 34, 37, 40, 47, 6, 107, 87, 63, 13, 0, 13, 69, 8, 243, 65, 5, 64, 69, 115, 63, 113, 47, 0, 0, 16, 70, 88, 84, 132, 21, 33, 64, 81, 110, 34, 70, 13, 34, 13, 0, 9, 198, 24, 18, 212, 85, 33, 64, 66, 0, 0, 11, 68, 8, 82, 68, 20, 69, 121, 70, 13, 0, 8, 196, 41, 83, 12, 20, 72, 32, 11, 70, 52, 144, 200, 4, 83, 0, 21, 0, 10, 0, 0, 16, 70, 52, 245, 15, 73, 38, 64, 63, 115, 47, 13, 34, 34, 121, 0, 0, 17, 71, 72, 80, 133, 48, 193, 69, 72, 34, 13, 69, 13, 55, 114, 34, 0, 0, 16, 70, 44, 244, 147, 92, 83, 0, 49, 108, 34, 87, 82, 13, 55, 0, 0, 13, 69, 28, 19, 132, 32, 144, 79, 35, 50, 70, 37, 0, 0, 0, 0, 17, 70, 76, 243, 143, 56, 65, 82, 87, 108, 50, 10, 108, 50, 13, 34, 0, 19, 72, 48, 18, 78, 29, 48, 149, 72, 112, 55, 121, 50, 87, 69, 109, 34, 134, 0, 0, 14, 69, 52, 20, 129, 37, 48, 63, 35, 34, 6, 106, 12, 0, 0, 0, 16, 71, 84, 149, 4, 4, 114, 78, 28, 125, 70, 113, 134, 13, 66, 0, 18, 70, 4, 193, 197, 32, 83, 5, 35, 55, 134, 13, 105, 4, 114, 55, 13, 0, 13, 70, 76, 244, 130, 60, 227, 133, 21, 102, 114, 0, 10, 0, 0, 0, 0, 0, 12, 68, 92, 147, 80, 100, 58, 107, 63, 48, 37, 0, 11, 68, 72, 85, 8, 4, 34, 114, 47, 35, 0, 15, 70, 52, 16, 199, 36, 195, 0, 63, 13, 79, 57, 37, 55, 0, 0, 14, 69, 37, 52, 129, 20, 192, 107, 87, 34, 119, 12, 55, 0, 0, 15, 70, 28, 243, 79, 73, 32, 64, 134, 13, 63, 108, 34, 35, 0, 16, 70, 76, 145, 205, 84, 225, 0, 87, 37, 79, 63, 40, 50, 47, 0, 17, 70, 48, 80, 78, 17, 32, 64, 55, 37, 6, 35, 50, 70, 34, 35, 0, 0, 10, 199, 4, 195, 5, 72, 113, 78, 20, 67, 0, 11, 68, 88, 84, 146, 20, 81, 111, 34, 13, 0, 13, 72, 52, 16, 203, 36, 229, 15, 76, 128, 21, 0, 10, 11, 68, 80, 242, 201, 60, 47, 115, 49, 117, 0, 0, 14, 69, 8, 84, 215, 36, 192, 69, 106, 87, 82, 13, 55, 0, 8, 2, 195, 151, 63, 113, 55, 0, 0, 10, 66, 77, 64, 87, 13, 50, 47, 0, 24, 0, 0, 9, 68, 41, 83, 9, 4, 21, 0, 10, 0, 0, 0, 19, 71, 33, 83, 12, 21, 49, 76, 24, 105, 109, 55, 13, 87, 110, 55, 81, 0, 32, 0, 12, 68, 88, 84, 147, 20, 81, 111, 34, 87, 13, 0, 12, 68, 20, 226, 71, 20, 114, 50, 107, 134, 13, 0, 14, 68, 56, 19, 205, 36, 50, 35, 10, 6, 115, 63, 37, 0, 0, 12, 2, 194, 167, 35, 81, 70, 114, 55, 13, 66, 0, 0, 17, 70, 88, 18, 193, 57, 65, 64, 81, 2, 35, 49, 35, 50, 47, 13, 0, 10, 66, 76, 80, 106, 87, 13, 0, 41, 9, 6, 194, 60, 208, 72, 12, 13, 2, 194, 164, 63, 109, 50, 47, 114, 49, 13, 50, 0, 0, 10, 198, 60, 225, 5, 84, 113, 5, 65, 9, 8, 2, 194, 165, 57, 106, 50, 0, 0, 13, 68, 60, 225, 69, 72, 108, 50, 10, 114, 34, 0, 9, 12, 68, 8, 82, 193, 24, 69, 110, 49, 35, 81, 0, 16, 3, 5, 46, 1, 9, 106, 50, 10, 6, 35, 50, 70, 13, 34, 0, 0, 12, 69, 52, 81, 71, 20, 80, 63, 114, 134, 114, 0, 13, 69, 44, 230, 83, 56, 16, 50, 121, 87, 50, 35, 0, 9, 2, 194, 163, 48, 129, 50, 47, 0, 0, 0, 12, 201, 77, 113, 84, 80, 84, 138, 60, 83, 0, 67, 18, 71, 5, 52, 197, 8, 194, 69, 24, 35, 87, 13, 69, 55, 6, 37, 81, 0, 19, 70, 49, 80, 210, 21, 66, 65, 55, 40, 49, 34, 6, 37, 12, 89, 57, 35, 0, 20, 71, 8, 20, 131, 20, 195, 206, 4, 69, 35, 34, 87, 13, 55, 6, 115, 50, 35, 0, 0, 12, 68, 88, 84, 148, 20, 81, 110, 34, 47, 13, 0, 12, 68, 80, 84, 149, 28, 47, 14, 34, 109, 134, 0, 7, 196, 64, 20, 148, 20, 65, 17, 7, 3, 12, 9, 3, 8, 195, 169, 49, 55, 37, 89, 6, 121, 12, 0, 0, 0, 15, 70, 24, 84, 146, 5, 34, 64, 81, 13, 34, 113, 34, 37, 0, 5, 130, 195, 164, 43, 0, 19, 71, 16, 21, 201, 17, 53, 5, 72, 70, 113, 82, 13, 47, 87, 47, 110, 34, 0, 20, 71, 81, 32, 70, 4, 193, 193, 72, 47, 34, 35, 81, 6, 35, 55, 79, 35, 34, 0, 0, 21, 72, 64, 85, 18, 60, 225, 76, 48, 16, 48, 114, 47, 34, 40, 50, 6, 110, 55, 35, 0, 15, 7, 6, 15, 21, 3, 8, 195, 169, 81, 40, 89, 6, 114, 0, 12, 68, 12, 80, 201, 48, 87, 106, 87, 13, 55, 0, 9, 68, 56, 145, 197, 48, 21, 0, 10, 0, 0, 18, 70, 76, 192, 80, 5, 35, 64, 87, 55, 35, 48, 10, 35, 34, 14, 63, 0, 25, 2, 195, 160, 35, 15, 55, 35, 15, 49, 6, 35, 34, 47, 0, 82, 108, 97, 32, 99, 97, 114, 116, 101, 32, 6, 130, 195, 160, 43, 14, 0, 13, 2, 194, 169, 49, 40, 48, 6, 37, 34, 110, 134, 0, 5, 130, 195, 161, 43, 0, 18, 70, 32, 245, 1, 29, 65, 82, 105, 108, 47, 10, 35, 134, 47, 13, 34, 0, 18, 70, 16, 85, 133, 57, 65, 82, 70, 6, 114, 82, 13, 50, 47, 13, 34, 0, 13, 2, 194, 182, 48, 35, 34, 35, 134, 34, 113, 81, 0, 0, 5, 130, 195, 175, 43, 0, 5, 130, 195, 172, 43, 0, 9, 67, 88, 144, 64, 82, 37, 35, 0, 10, 2, 194, 181, 63, 37, 49, 34, 40, 0, 5, 130, 195, 173, 43, 0, 12, 68, 8, 82, 197, 72, 69, 114, 49, 13, 34, 0, 10, 68, 12, 128, 82, 48, 89, 113, 55, 0, 18, 72, 76, 86, 67, 32, 83, 12, 21, 48, 87, 121, 89, 6, 110, 55, 86, 0, 5, 130, 195, 170, 43, 0, 5, 130, 195, 171, 43, 0, 10, 2, 194, 176, 134, 34, 113, 70, 13, 0, 5, 130, 195, 168, 43, 0, 17, 2, 194, 177, 48, 55, 109, 87, 10, 108, 81, 63, 37, 50, 109, 87, 0, 5, 130, 195, 169, 43, 0, 13, 2, 194, 190, 70, 34, 37, 49, 58, 35, 34, 47, 0, 5, 130, 195, 182, 43, 0, 10, 69, 32, 245, 193, 72, 64, 21, 0, 10, 8, 197, 20, 195, 73, 20, 224, 66, 10, 69, 16, 20, 151, 36, 224, 21, 0, 10, 13, 2, 195, 183, 134, 13, 70, 114, 55, 70, 126, 34, 0, 0, 16, 70, 56, 241, 197, 20, 228, 192, 50, 108, 134, 10, 114, 50, 87, 0, 15, 70, 72, 80, 133, 44, 176, 64, 34, 13, 69, 106, 49, 35, 0, 11, 2, 194, 188, 13, 49, 58, 35, 34, 47, 0, 5, 130, 195, 180, 43, 0, 28, 67, 56, 145, 64, 50, 4, 37, 15, 82, 4, 113, 34, 15, 50, 6, 37, 0, 82, 119, 97, 97, 114, 32, 110, 105, 101, 32, 7, 195, 56, 145, 64, 13, 40, 11, 2, 194, 189, 13, 105, 35, 55, 82, 13, 0, 0, 11, 200, 76, 81, 5, 73, 65, 9, 20, 224, 67, 13, 4, 95, 3, 5, 4, 87, 13, 70, 107, 55, 35, 0, 5, 130, 195, 178, 43, 0, 13, 70, 28, 241, 66, 8, 83, 19, 21, 100, 101, 0, 10, 5, 130, 195, 179, 43, 0, 16, 70, 5, 97, 82, 76, 145, 64, 35, 82, 6, 110, 34, 87, 37, 0, 16, 70, 88, 148, 193, 28, 145, 64, 81, 37, 87, 6, 113, 134, 37, 0, 15, 70, 52, 20, 133, 48, 145, 64, 63, 35, 34, 13, 55, 37, 0, 0, 18, 4, 95, 12, 9, 7, 70, 6, 109, 69, 13, 55, 55, 106, 47, 13, 34, 0, 0, 9, 68, 12, 192, 82, 44, 21, 0, 10, 17, 70, 76, 19, 22, 4, 67, 210, 87, 35, 55, 82, 35, 70, 129, 34, 0, 0, 21, 67, 80, 83, 0, 47, 110, 55, 15, 35, 82, 6, 37, 82, 0, 81, 97, 118, 105, 118, 32, 0, 14, 70, 88, 243, 210, 28, 81, 64, 81, 115, 34, 134, 114, 0, 8, 66, 80, 80, 47, 13, 0, 32, 15, 70, 12, 241, 84, 104, 81, 64, 49, 40, 47, 87, 6, 114, 0, 21, 73, 40, 81, 134, 72, 86, 83, 8, 16, 73, 73, 106, 81, 34, 37, 87, 69, 6, 120, 0, 5, 130, 195, 188, 43, 0, 5, 130, 195, 189, 43, 0, 8, 196, 33, 83, 12, 20, 72, 32, 9, 68, 72, 241, 197, 72, 21, 0, 10, 13, 68, 48, 80, 78, 4, 55, 37, 6, 113, 50, 35, 0, 5, 130, 195, 186, 43, 0, 21, 73, 72, 83, 129, 37, 52, 193, 56, 49, 64, 34, 106, 50, 13, 87, 6, 131, 50, 87, 0, 8, 197, 60, 225, 197, 4, 112, 65, 14, 69, 32, 145, 82, 76, 240, 105, 37, 12, 34, 87, 108, 0, 15, 69, 12, 194, 86, 36, 16, 49, 55, 107, 82, 37, 57, 35, 0, 10, 69, 28, 83, 210, 28, 80, 21, 0, 10, 12, 69, 9, 32, 72, 4, 208, 69, 34, 113, 63, 0, 14, 69, 56, 147, 133, 88, 80, 50, 107, 50, 13, 81, 37, 0, 5, 130, 195, 187, 43, 0, 15, 70, 85, 37, 71, 84, 22, 64, 40, 34, 40, 79, 58, 119, 0, 0, 5, 130, 195, 185, 43, 0, 7, 196, 92, 18, 201, 76, 65, 12, 68, 12, 130, 78, 4, 89, 6, 37, 50, 35, 0, 0, 14, 69, 40, 19, 137, 56, 80, 73, 13, 50, 37, 12, 50, 0, 13, 69, 8, 85, 10, 36, 80, 69, 106, 37, 78, 37, 0, 15, 69, 4, 192, 83, 44, 16, 35, 55, 6, 35, 87, 49, 35, 0, 0, 9, 198, 72, 147, 139, 36, 226, 192, 66, 0, 18, 71, 17, 80, 130, 20, 194, 197, 56, 70, 109, 69, 13, 55, 49, 106, 50, 0, 0, 0, 16, 69, 21, 131, 196, 85, 48, 106, 49, 87, 6, 115, 70, 109, 87, 0, 0, 0, 18, 70, 60, 179, 1, 32, 243, 65, 118, 49, 55, 13, 105, 6, 118, 63, 35, 0, 0, 0, 18, 70, 64, 147, 143, 44, 178, 79, 48, 37, 50, 6, 108, 49, 37, 38, 40, 0, 0, 0, 0, 12, 68, 92, 21, 23, 60, 82, 35, 47, 82, 115, 0, 10, 67, 4, 36, 193, 35, 69, 87, 35, 0, 0, 9, 4, 95, 35, 4, 5, 70, 13, 0, 0, 0, 11, 67, 60, 228, 192, 133, 50, 87, 0, 72, 32, 0, 12, 68, 52, 245, 15, 72, 63, 115, 47, 13, 34, 0, 19, 72, 8, 18, 78, 76, 179, 15, 60, 96, 69, 121, 50, 87, 49, 55, 115, 81, 0, 0, 17, 70, 72, 85, 15, 72, 145, 75, 34, 13, 47, 40, 34, 6, 37, 49, 0, 25, 73, 52, 83, 79, 72, 16, 137, 48, 144, 64, 63, 106, 63, 108, 34, 35, 69, 6, 37, 55, 37, 57, 35, 0, 0, 10, 66, 81, 96, 47, 114, 81, 114, 10, 0, 0, 7, 195, 76, 245, 64, 72, 32, 0, 10, 67, 49, 83, 21, 55, 40, 55, 40, 0, 9, 68, 40, 147, 77, 100, 21, 0, 10, 0, 14, 69, 73, 84, 5, 73, 64, 34, 40, 48, 13, 34, 47, 0, 0, 9, 198, 88, 243, 19, 64, 241, 68, 65, 0, 7, 195, 92, 245, 64, 72, 32, 0, 9, 198, 60, 225, 197, 72, 145, 70, 65, 12, 68, 20, 97, 83, 20, 114, 81, 13, 87, 13, 0, 0, 20, 73, 32, 19, 132, 80, 84, 148, 40, 145, 64, 105, 35, 50, 47, 111, 34, 78, 37, 0, 11, 69, 88, 147, 204, 21, 64, 21, 0, 41, 10, 13, 69, 12, 17, 83, 5, 32, 87, 37, 86, 13, 34, 0, 0, 17, 70, 76, 147, 135, 20, 227, 212, 87, 107, 50, 134, 13, 50, 108, 47, 0, 9, 198, 56, 17, 5, 56, 177, 64, 65, 0, 0, 20, 9, 22, 18, 15, 5, 195, 171, 18, 9, 7, 81, 34, 40, 12, 13, 34, 13, 134, 0, 7, 196, 60, 228, 149, 76, 65, 12, 68, 32, 241, 82, 4, 105, 40, 34, 6, 113, 0, 14, 68, 16, 144, 78, 4, 70, 37, 57, 6, 113, 50, 35, 0, 0, 8, 197, 32, 241, 75, 60, 208, 8, 0, 0, 6, 195, 92, 21, 0, 8, 0, 20, 72, 64, 146, 193, 56, 145, 78, 36, 80, 48, 37, 49, 35, 50, 6, 37, 50, 37, 0, 13, 68, 4, 224, 76, 20, 35, 50, 6, 113, 55, 13, 0, 13, 68, 20, 192, 78, 4, 37, 55, 6, 113, 50, 35, 0, 0, 14, 69, 88, 84, 151, 20, 112, 81, 111, 34, 82, 110, 134, 0, 16, 70, 8, 16, 133, 48, 16, 83, 69, 35, 69, 13, 55, 113, 87, 0, 12, 69, 52, 84, 129, 4, 144, 63, 13, 34, 120, 0, 0, 23, 66, 77, 144, 87, 4, 121, 15, 35, 50, 15, 87, 6, 121, 0, 82, 97, 97, 110, 32, 115, 121, 32, 6, 194, 77, 144, 72, 32, 15, 70, 65, 33, 83, 48, 86, 64, 48, 34, 106, 87, 55, 37, 0, 0, 18, 71, 72, 17, 5, 52, 86, 69, 72, 34, 113, 70, 13, 63, 121, 13, 34, 0, 6, 2, 95, 1, 113, 0, 0, 9, 198, 88, 243, 210, 44, 81, 82, 65, 19, 72, 88, 84, 133, 17, 82, 70, 36, 80, 81, 114, 34, 13, 70, 125, 81, 37, 0, 11, 200, 77, 113, 76, 48, 83, 132, 4, 208, 67, 0, 23, 73, 28, 83, 5, 72, 83, 132, 32, 82, 68, 134, 13, 55, 114, 34, 13, 50, 47, 105, 121, 47, 0, 0, 0, 18, 71, 8, 244, 132, 20, 115, 197, 16, 69, 129, 34, 70, 13, 134, 40, 47, 0, 27, 12, 13, 5, 19, 15, 16, 15, 20, 1, 13, 9, 195, 171, 63, 106, 87, 40, 48, 40, 47, 6, 113, 63, 37, 13, 0, 0, 0, 13, 69, 8, 86, 69, 73, 48, 69, 121, 13, 34, 87, 0, 0, 9, 198, 60, 225, 197, 17, 83, 4, 65, 17, 70, 76, 84, 207, 80, 131, 192, 87, 13, 87, 6, 40, 12, 47, 40, 0, 0, 0, 0, 12, 68, 64, 21, 15, 76, 48, 113, 47, 108, 87, 0, 0, 9, 3, 7, 39, 14, 134, 107, 50, 0, 0, 9, 198, 60, 244, 130, 60, 244, 132, 66, 0, 19, 71, 20, 194, 83, 4, 33, 84, 32, 37, 55, 6, 37, 87, 35, 69, 106, 47, 0, 11, 67, 45, 112, 64, 49, 58, 35, 0, 72, 9, 0, 7, 196, 60, 227, 65, 28, 65, 0, 14, 69, 32, 241, 87, 20, 192, 105, 40, 82, 6, 110, 55, 0, 0, 21, 9, 22, 5, 18, 7, 5, 12, 5, 195, 171, 81, 111, 34, 134, 13, 55, 4, 114, 13, 0, 16, 70, 56, 20, 208, 21, 36, 192, 50, 35, 87, 48, 110, 34, 87, 0, 0, 19, 71, 80, 147, 79, 80, 129, 85, 76, 47, 13, 63, 6, 115, 47, 37, 109, 87, 0, 14, 71, 8, 240, 195, 4, 48, 201, 60, 21, 105, 116, 0, 10, 0, 0, 13, 69, 24, 145, 213, 85, 32, 81, 13, 134, 116, 34, 0, 6, 2, 95, 21, 116, 0, 0, 17, 70, 64, 83, 143, 72, 83, 148, 48, 106, 50, 115, 34, 106, 50, 47, 0, 17, 70, 44, 243, 139, 5, 113, 64, 49, 108, 50, 49, 6, 113, 82, 13, 0, 31, 76, 72, 149, 137, 21, 36, 207, 56, 65, 82, 20, 225, 0, 34, 13, 81, 37, 12, 34, 87, 108, 50, 13, 34, 10, 6, 106, 50, 47, 0, 0, 18, 70, 4, 48, 80, 84, 192, 207, 35, 49, 35, 48, 6, 40, 55, 49, 118, 0, 0, 0, 9, 198, 88, 243, 16, 84, 229, 5, 65, 0, 0, 9, 198, 32, 84, 139, 48, 16, 83, 65, 19, 70, 8, 80, 84, 72, 150, 0, 69, 37, 38, 6, 113, 47, 34, 13, 49, 87, 0, 12, 67, 9, 2, 192, 69, 13, 48, 110, 34, 49, 0, 0, 16, 70, 80, 241, 82, 20, 177, 78, 47, 40, 34, 114, 49, 13, 50, 0, 30, 76, 80, 129, 83, 76, 19, 15, 56, 144, 197, 57, 49, 64, 47, 106, 87, 35, 55, 115, 50, 37, 87, 6, 106, 12, 50, 87, 13, 0, 0, 15, 69, 64, 20, 129, 80, 80, 48, 35, 34, 6, 113, 47, 13, 0, 12, 69, 32, 242, 193, 4, 144, 105, 108, 49, 120, 0, 0, 17, 70, 16, 80, 149, 77, 54, 64, 70, 13, 69, 40, 87, 6, 37, 12, 0, 0, 0, 10, 135, 20, 5, 18, 4, 5, 195, 171, 66, 10, 68, 60, 244, 146, 100, 115, 34, 121, 0, 11, 2, 95, 34, 105, 113, 55, 23, 113, 50, 0, 0, 14, 69, 52, 147, 149, 80, 80, 63, 13, 50, 116, 47, 13, 0, 14, 69, 4, 98, 197, 72, 80, 35, 81, 49, 114, 34, 13, 0, 13, 69, 101, 99, 206, 56, 80, 37, 82, 6, 108, 50, 0, 13, 69, 64, 131, 197, 8, 80, 81, 37, 12, 69, 37, 0, 13, 69, 60, 229, 15, 56, 112, 108, 50, 47, 108, 66, 0, 24, 73, 88, 19, 146, 33, 147, 147, 16, 244, 144, 81, 35, 50, 34, 6, 121, 50, 87, 70, 108, 34, 48, 0, 0, 9, 66, 89, 80, 21, 102, 114, 0, 10, 0, 8, 195, 44, 243, 128, 72, 11, 32, 17, 70, 16, 19, 65, 76, 181, 83, 70, 13, 63, 35, 87, 49, 109, 87, 0, 8, 2, 95, 39, 47, 37, 49, 0, 0, 21, 72, 76, 19, 69, 48, 85, 201, 56, 112, 87, 113, 63, 13, 55, 4, 114, 82, 13, 66, 0, 20, 72, 64, 242, 78, 76, 85, 20, 36, 16, 48, 122, 50, 87, 6, 106, 47, 37, 35, 0, 20, 72, 52, 20, 135, 84, 84, 137, 80, 80, 63, 113, 79, 13, 34, 6, 37, 12, 47, 0, 0, 0, 15, 70, 77, 65, 80, 32, 19, 128, 87, 47, 114, 81, 35, 50, 0, 8, 67, 40, 19, 133, 21, 0, 10, 16, 70, 4, 68, 137, 4, 19, 128, 113, 70, 34, 37, 57, 35, 50, 0, 0, 6, 195, 88, 19, 128, 72, 0, 17, 70, 36, 115, 143, 72, 81, 82, 37, 134, 50, 115, 34, 6, 114, 34, 0, 6, 195, 37, 50, 83, 65, 16, 4, 95, 3, 1, 16, 105, 6, 115, 81, 55, 106, 47, 13, 34, 0, 0, 14, 69, 80, 19, 135, 5, 48, 47, 35, 66, 79, 35, 87, 0, 13, 69, 88, 84, 151, 21, 144, 81, 13, 34, 82, 121, 0, 27, 69, 9, 81, 78, 61, 48, 69, 58, 106, 50, 108, 87, 10, 6, 119, 34, 106, 87, 0, 81, 97, 105, 114, 101, 115, 32, 13, 2, 95, 41, 34, 110, 134, 87, 105, 35, 49, 37, 0, 0, 16, 70, 48, 147, 80, 61, 3, 192, 55, 13, 63, 48, 115, 48, 115, 0, 16, 70, 12, 19, 5, 16, 243, 128, 49, 35, 55, 37, 70, 108, 50, 0, 13, 2, 95, 40, 55, 107, 66, 87, 105, 35, 49, 37, 0, 0, 10, 67, 64, 84, 128, 48, 13, 34, 0, 9, 6, 195, 88, 148, 128, 72, 7, 195, 92, 244, 132, 72, 32, 0, 16, 70, 80, 83, 5, 52, 19, 142, 47, 114, 55, 13, 63, 35, 50, 0, 0, 24, 73, 64, 19, 132, 20, 211, 206, 37, 83, 64, 48, 35, 50, 70, 13, 63, 6, 115, 50, 37, 109, 63, 0, 15, 2, 95, 45, 49, 108, 48, 13, 55, 47, 114, 49, 13, 50, 0, 0, 10, 67, 32, 84, 133, 105, 114, 34, 13, 0, 10, 67, 48, 85, 137, 55, 114, 81, 37, 0, 9, 2, 95, 44, 49, 108, 63, 35, 0, 0, 19, 71, 12, 19, 69, 52, 33, 82, 80, 49, 35, 63, 13, 63, 69, 6, 111, 34, 0, 9, 67, 16, 84, 128, 70, 13, 34, 0, 9, 2, 95, 51, 6, 70, 34, 37, 0, 0, 12, 68, 80, 133, 76, 4, 47, 40, 12, 55, 35, 0, 12, 68, 76, 18, 78, 80, 87, 107, 50, 47, 0, 72, 9, 2, 95, 50, 6, 47, 58, 114, 0, 0, 13, 69, 44, 243, 65, 4, 224, 49, 108, 63, 113, 50, 0, 8, 197, 52, 147, 1, 4, 224, 66, 9, 2, 95, 49, 10, 6, 114, 50, 0, 0, 10, 67, 88, 149, 129, 82, 37, 82, 35, 0, 16, 70, 41, 84, 9, 80, 84, 128, 57, 40, 48, 37, 47, 13, 34, 0, 9, 2, 95, 48, 6, 50, 109, 55, 0, 0, 18, 71, 28, 85, 129, 48, 193, 78, 20, 134, 13, 81, 35, 55, 13, 50, 13, 0, 10, 2, 95, 55, 6, 87, 114, 82, 13, 0, 0, 21, 72, 8, 19, 135, 48, 17, 5, 76, 160, 69, 35, 66, 79, 55, 35, 70, 6, 106, 89, 0, 9, 2, 95, 54, 6, 87, 106, 87, 0, 0, 14, 69, 52, 84, 140, 61, 64, 63, 110, 34, 55, 6, 115, 0, 9, 2, 95, 53, 6, 81, 121, 81, 0, 0, 15, 70, 20, 97, 133, 57, 49, 64, 106, 81, 13, 50, 87, 13, 0, 17, 70, 52, 20, 140, 37, 49, 64, 63, 35, 34, 55, 6, 37, 12, 87, 0, 24, 11, 7, 5, 20, 19, 195, 169, 13, 1, 14, 195, 169, 134, 106, 47, 87, 6, 114, 63, 35, 50, 37, 0, 10, 2, 95, 52, 6, 81, 37, 12, 34, 0, 0, 13, 2, 95, 59, 49, 108, 63, 35, 48, 109, 50, 47, 0, 0, 15, 70, 40, 245, 66, 21, 37, 0, 57, 40, 69, 6, 111, 34, 0, 14, 2, 95, 58, 70, 109, 69, 13, 55, 48, 109, 50, 47, 0, 0, 13, 69, 52, 147, 149, 85, 64, 63, 13, 50, 116, 47, 0, 10, 2, 95, 57, 6, 50, 114, 134, 13, 0, 0, 10, 2, 95, 56, 10, 6, 35, 134, 47, 0, 0, 15, 70, 12, 147, 12, 36, 84, 147, 87, 107, 55, 57, 6, 114, 0, 15, 70, 12, 83, 12, 36, 84, 147, 87, 107, 55, 57, 6, 114, 0, 16, 70, 88, 147, 12, 36, 84, 147, 82, 107, 55, 37, 13, 34, 87, 0, 14, 2, 95, 63, 81, 34, 113, 134, 47, 114, 49, 13, 50, 0, 0, 14, 2, 95, 62, 134, 34, 115, 47, 13, 34, 23, 35, 87, 0, 0, 14, 69, 76, 19, 15, 52, 240, 87, 113, 55, 13, 63, 115, 0, 14, 69, 52, 148, 137, 4, 208, 63, 107, 34, 37, 13, 63, 0, 15, 69, 28, 64, 78, 76, 176, 79, 14, 70, 35, 50, 87, 49, 0, 0, 14, 2, 95, 60, 49, 55, 121, 50, 13, 34, 23, 35, 87, 0, 0, 18, 71, 9, 34, 69, 92, 83, 69, 76, 69, 34, 37, 82, 13, 63, 106, 87, 0, 0, 21, 72, 88, 84, 139, 20, 84, 132, 60, 208, 81, 13, 34, 49, 114, 34, 47, 10, 108, 63, 0, 9, 198, 88, 243, 210, 16, 21, 0, 8, 18, 8, 5, 19, 5, 7, 9, 195, 171, 12, 37, 87, 6, 114, 134, 37, 12, 0, 21, 72, 20, 211, 65, 72, 83, 148, 36, 16, 106, 63, 35, 34, 6, 132, 50, 89, 57, 35, 0, 0, 15, 69, 76, 19, 21, 80, 80, 87, 35, 55, 6, 116, 47, 13, 0, 14, 69, 48, 81, 193, 80, 80, 55, 13, 134, 113, 47, 13, 0, 15, 69, 16, 82, 193, 16, 80, 70, 106, 49, 6, 113, 70, 13, 0, 16, 69, 76, 244, 8, 36, 16, 87, 40, 81, 6, 37, 12, 57, 35, 0, 17, 70, 76, 19, 4, 4, 226, 1, 87, 35, 55, 70, 6, 35, 50, 35, 0, 0, 0, 17, 70, 17, 82, 84, 77, 113, 83, 70, 125, 47, 87, 82, 6, 106, 87, 0, 0, 21, 72, 16, 148, 12, 60, 208, 83, 36, 80, 70, 13, 48, 55, 115, 63, 35, 87, 6, 37, 0, 9, 68, 13, 148, 137, 48, 21, 0, 10, 0, 14, 69, 52, 20, 137, 85, 48, 63, 113, 34, 37, 109, 87, 0, 13, 69, 48, 85, 201, 21, 48, 55, 13, 82, 37, 87, 0, 0, 9, 198, 52, 148, 203, 36, 83, 128, 66, 15, 70, 12, 132, 137, 77, 67, 192, 49, 34, 107, 87, 47, 40, 0, 0, 0, 11, 68, 52, 16, 200, 60, 63, 35, 74, 118, 0, 16, 70, 12, 132, 137, 77, 67, 198, 49, 34, 107, 87, 47, 108, 81, 0, 0, 18, 70, 73, 147, 69, 48, 20, 153, 34, 121, 63, 13, 55, 35, 34, 6, 121, 0, 15, 70, 52, 144, 200, 20, 195, 5, 63, 37, 89, 6, 110, 55, 0, 18, 70, 12, 20, 143, 48, 147, 129, 49, 35, 34, 40, 55, 6, 37, 50, 35, 0, 0, 16, 70, 4, 195, 5, 29, 35, 192, 35, 55, 6, 106, 79, 34, 40, 0, 17, 70, 8, 244, 143, 16, 147, 128, 69, 108, 34, 40, 70, 6, 37, 50, 0, 16, 4, 194, 182, 194, 182, 48, 35, 34, 35, 134, 34, 113, 82, 13, 0, 0, 0, 11, 70, 88, 147, 131, 20, 229, 0, 21, 0, 10, 12, 5, 18, 5, 14, 195, 169, 34, 13, 50, 121, 0, 12, 68, 40, 244, 197, 24, 57, 115, 87, 13, 81, 0, 0, 15, 204, 92, 81, 82, 88, 243, 210, 77, 1, 76, 48, 147, 135, 65, 9, 198, 12, 243, 134, 21, 69, 9, 66, 10, 69, 28, 244, 132, 60, 224, 21, 0, 10, 0, 12, 137, 15, 14, 22, 5, 18, 13, 15, 195, 171, 65, 15, 70, 56, 146, 204, 4, 20, 192, 50, 37, 49, 55, 113, 87, 0, 0, 19, 71, 4, 229, 23, 21, 36, 5, 56, 35, 50, 47, 82, 110, 34, 48, 13, 50, 0, 0, 6, 195, 76, 243, 211, 72, 6, 195, 76, 243, 211, 8, 18, 8, 7, 1, 2, 18, 9, 195, 171, 12, 134, 113, 69, 34, 37, 13, 55, 0, 11, 5, 95, 35, 19, 20, 5, 87, 47, 13, 0, 0, 10, 69, 9, 84, 148, 60, 224, 21, 0, 10, 10, 69, 4, 193, 146, 20, 64, 21, 0, 10, 17, 70, 44, 147, 147, 32, 20, 193, 49, 37, 50, 89, 6, 113, 87, 35, 0, 0, 9, 198, 4, 229, 1, 72, 84, 192, 66, 15, 70, 76, 84, 150, 4, 20, 192, 87, 13, 34, 81, 113, 87, 0, 22, 73, 52, 243, 210, 72, 81, 83, 9, 84, 135, 63, 40, 34, 6, 114, 87, 69, 109, 34, 134, 0, 0, 0, 11, 70, 72, 144, 200, 5, 33, 0, 21, 0, 10, 12, 4, 95, 4, 15, 20, 48, 6, 109, 50, 47, 0, 0, 14, 69, 80, 245, 4, 5, 64, 47, 108, 70, 35, 47, 0, 8, 0, 9, 198, 60, 226, 213, 56, 65, 64, 65, 6, 195, 36, 65, 69, 66, 17, 70, 100, 243, 1, 56, 65, 64, 57, 40, 55, 6, 35, 50, 70, 13, 0, 10, 67, 4, 64, 77, 35, 70, 35, 63, 0, 0, 17, 71, 64, 192, 65, 76, 160, 65, 64, 48, 55, 113, 87, 57, 113, 48, 0, 18, 2, 95, 91, 55, 107, 66, 87, 15, 69, 55, 108, 49, 105, 35, 49, 37, 0, 0, 7, 196, 88, 84, 141, 100, 66, 11, 68, 32, 82, 203, 20, 105, 110, 49, 13, 0, 0, 17, 70, 64, 147, 143, 80, 17, 197, 48, 37, 50, 40, 47, 6, 113, 88, 0, 13, 69, 72, 82, 78, 21, 64, 34, 13, 50, 106, 47, 0, 15, 69, 52, 246, 129, 73, 64, 63, 115, 47, 87, 35, 34, 47, 0, 0, 17, 70, 45, 112, 90, 84, 197, 64, 49, 58, 35, 86, 6, 40, 55, 40, 0, 0, 9, 67, 32, 82, 192, 105, 110, 49, 0, 8, 2, 95, 95, 55, 121, 50, 0, 0, 9, 68, 40, 19, 69, 76, 21, 0, 10, 0, 22, 73, 88, 84, 146, 20, 112, 65, 56, 65, 64, 81, 110, 34, 13, 134, 6, 113, 50, 70, 13, 0, 15, 69, 76, 240, 133, 72, 80, 87, 6, 115, 69, 13, 34, 13, 0, 8, 197, 56, 19, 65, 80, 80, 66, 13, 69, 81, 37, 68, 36, 80, 47, 34, 40, 70, 37, 0, 9, 198, 12, 243, 146, 4, 66, 69, 66, 18, 2, 95, 93, 34, 110, 134, 87, 15, 69, 55, 108, 49, 105, 35, 49, 37, 0, 0, 16, 70, 45, 34, 84, 36, 82, 192, 49, 34, 107, 47, 6, 37, 49, 0, 8, 67, 28, 243, 201, 134, 122, 0, 18, 70, 4, 194, 15, 21, 113, 76, 35, 55, 105, 40, 82, 6, 110, 55, 0, 8, 0, 10, 199, 8, 20, 146, 36, 176, 68, 20, 67, 6, 195, 24, 18, 192, 17, 0, 12, 201, 92, 16, 82, 76, 182, 78, 48, 146, 197, 66, 13, 68, 20, 194, 84, 20, 37, 55, 6, 37, 12, 47, 0, 0, 8, 197, 81, 84, 139, 100, 80, 66, 0, 15, 70, 49, 146, 215, 4, 18, 192, 55, 121, 49, 82, 113, 49, 0, 9, 198, 28, 245, 68, 36, 226, 64, 66, 0, 12, 201, 36, 229, 5, 57, 50, 84, 20, 149, 0, 68, 18, 71, 28, 16, 78, 16, 85, 197, 28, 134, 113, 50, 70, 13, 82, 110, 134, 0, 0, 22, 72, 76, 241, 197, 56, 16, 77, 16, 80, 87, 6, 115, 134, 13, 50, 4, 113, 63, 70, 13, 0, 10, 67, 40, 16, 207, 57, 35, 49, 40, 0, 0, 12, 201, 92, 16, 82, 76, 182, 78, 48, 146, 192, 66, 6, 195, 37, 48, 142, 17, 0, 0, 20, 9, 195, 170, 18, 5, 14, 19, 20, 5, 18, 111, 34, 13, 50, 87, 47, 13, 34, 0, 0, 22, 72, 61, 32, 78, 40, 84, 5, 73, 48, 115, 34, 6, 35, 50, 57, 13, 48, 111, 34, 87, 0, 0, 0, 26, 74, 16, 85, 84, 21, 35, 206, 60, 210, 85, 52, 70, 126, 47, 13, 34, 115, 50, 6, 115, 63, 37, 109, 63, 0, 14, 4, 95, 7, 18, 22, 134, 34, 35, 81, 6, 107, 87, 0, 0, 9, 67, 20, 180, 192, 106, 49, 87, 0, 0, 0, 0, 16, 70, 36, 226, 193, 80, 128, 64, 37, 66, 49, 6, 113, 47, 35, 0, 9, 198, 24, 147, 129, 48, 148, 192, 67, 0, 0, 9, 68, 48, 85, 201, 76, 21, 0, 10, 12, 68, 36, 36, 197, 56, 37, 69, 87, 13, 50, 0, 0, 0, 0, 0, 13, 67, 20, 67, 83, 121, 13, 50, 70, 108, 63, 87, 0, 0, 0, 16, 70, 80, 85, 146, 20, 65, 64, 47, 13, 81, 34, 114, 70, 13, 0, 0, 9, 195, 92, 147, 0, 72, 11, 9, 32, 18, 2, 95, 123, 55, 107, 66, 87, 15, 49, 34, 109, 55, 105, 35, 49, 37, 0, 16, 4, 95, 4, 9, 1, 70, 6, 114, 55, 47, 114, 49, 13, 50, 0, 0, 7, 196, 4, 226, 77, 4, 65, 0, 15, 69, 9, 37, 87, 21, 32, 69, 34, 40, 58, 6, 111, 34, 0, 0, 16, 70, 77, 69, 75, 72, 17, 192, 87, 47, 116, 49, 34, 35, 134, 0, 15, 70, 77, 86, 129, 56, 225, 64, 87, 40, 86, 6, 113, 50, 0, 11, 70, 12, 20, 140, 100, 193, 64, 21, 0, 10, 0, 19, 71, 32, 148, 143, 76, 162, 77, 4, 105, 37, 34, 40, 89, 6, 37, 63, 35, 0, 0, 0, 23, 73, 48, 16, 149, 76, 50, 1, 28, 225, 64, 55, 35, 69, 109, 87, 49, 6, 35, 134, 50, 37, 0, 15, 69, 21, 81, 197, 56, 80, 57, 40, 73, 6, 37, 12, 50, 0, 18, 2, 95, 125, 34, 110, 134, 87, 15, 49, 34, 109, 55, 105, 35, 49, 37, 0, 0, 12, 2, 95, 124, 35, 81, 87, 47, 34, 114, 48, 0, 0, 0, 11, 200, 92, 83, 148, 4, 181, 9, 20, 176, 65, 0, 8, 197, 60, 225, 9, 56, 112, 65, 10, 69, 76, 244, 8, 36, 80, 21, 0, 10, 0, 11, 70, 64, 21, 18, 36, 50, 192, 21, 0, 10, 0, 0, 11, 70, 9, 35, 207, 44, 198, 78, 21, 0, 10, 0, 0, 0, 17, 71, 52, 245, 15, 73, 66, 137, 20, 63, 115, 47, 13, 34, 49, 37, 0, 12, 71, 48, 240, 203, 21, 32, 137, 20, 21, 0, 10, 0, 0, 13, 69, 92, 21, 23, 61, 80, 82, 35, 47, 82, 118, 0, 0, 17, 70, 12, 16, 133, 72, 225, 84, 49, 35, 69, 13, 34, 50, 6, 121, 0, 0, 18, 71, 16, 82, 210, 20, 194, 78, 28, 70, 106, 49, 34, 114, 55, 13, 66, 0, 0, 13, 70, 76, 50, 13, 36, 69, 0, 89, 63, 37, 47, 0, 0, 0, 18, 70, 52, 19, 132, 20, 192, 64, 63, 35, 50, 70, 6, 106, 12, 55, 35, 0, 0, 0, 0, 0, 17, 70, 52, 21, 20, 21, 84, 192, 63, 35, 47, 6, 37, 12, 109, 87, 0, 0, 17, 70, 44, 244, 9, 21, 33, 71, 49, 40, 48, 6, 37, 34, 110, 134, 0, 19, 8, 22, 9, 195, 171, 20, 14, 1, 13, 82, 57, 6, 106, 47, 50, 35, 63, 0, 12, 71, 52, 83, 2, 61, 84, 142, 20, 21, 0, 10, 0, 0, 14, 69, 88, 243, 21, 37, 64, 81, 108, 55, 10, 125, 47, 0, 13, 69, 32, 82, 77, 5, 64, 105, 119, 63, 35, 47, 0, 0, 16, 70, 93, 148, 199, 21, 33, 64, 82, 121, 87, 134, 114, 34, 13, 0, 0, 0, 0, 10, 69, 88, 144, 212, 61, 32, 21, 0, 10, 14, 73, 76, 128, 75, 21, 52, 5, 5, 33, 64, 21, 0, 10, 0, 13, 70, 72, 244, 211, 61, 85, 192, 34, 13, 87, 118, 0, 9, 198, 52, 144, 200, 36, 83, 0, 66, 0, 10, 199, 92, 81, 82, 44, 194, 78, 44, 66, 10, 199, 60, 225, 197, 92, 243, 206, 76, 65, 0, 11, 200, 60, 225, 5, 73, 118, 83, 21, 32, 67, 15, 70, 48, 145, 83, 8, 85, 0, 55, 37, 87, 69, 106, 47, 0, 13, 68, 20, 210, 76, 20, 106, 63, 6, 37, 12, 55, 0, 0, 15, 69, 32, 21, 129, 56, 16, 105, 35, 82, 6, 35, 50, 35, 0, 0, 0, 16, 70, 73, 82, 203, 21, 34, 71, 34, 109, 49, 13, 34, 13, 134, 0, 0, 11, 200, 4, 19, 147, 80, 16, 78, 16, 80, 66, 0, 15, 69, 52, 245, 15, 72, 80, 63, 115, 47, 6, 115, 34, 13, 0, 9, 197, 16, 16, 82, 56, 16, 8, 32, 14, 69, 76, 50, 1, 48, 176, 87, 49, 6, 35, 55, 49, 0, 0, 0, 16, 70, 72, 245, 20, 20, 225, 83, 34, 108, 47, 13, 50, 106, 87, 0, 13, 71, 32, 243, 199, 20, 65, 76, 20, 105, 115, 134, 0, 18, 71, 17, 35, 207, 53, 53, 5, 72, 70, 34, 115, 63, 87, 47, 110, 34, 0, 10, 199, 52, 17, 196, 4, 193, 78, 4, 67, 0, 11, 68, 16, 18, 83, 100, 70, 121, 86, 37, 0, 0, 10, 67, 5, 51, 198, 35, 87, 108, 81, 0, 0, 18, 70, 12, 243, 5, 57, 51, 192, 49, 40, 55, 6, 106, 12, 50, 87, 118, 0, 0, 13, 70, 21, 52, 18, 21, 52, 207, 21, 105, 116, 0, 10, 18, 70, 8, 195, 205, 21, 37, 83, 69, 55, 40, 63, 6, 114, 34, 109, 87, 0, 0, 0, 17, 70, 76, 177, 80, 76, 83, 5, 87, 49, 106, 48, 87, 13, 55, 13, 0, 11, 70, 44, 83, 148, 84, 50, 217, 21, 0, 10, 0, 25, 73, 52, 81, 137, 77, 67, 198, 20, 193, 83, 63, 106, 81, 37, 87, 47, 6, 115, 81, 13, 55, 13, 87, 0, 0, 0, 0, 0, 0, 7, 195, 17, 84, 192, 8, 32, 0, 0, 0, 11, 70, 76, 147, 129, 81, 32, 64, 21, 0, 10, 17, 70, 41, 80, 78, 37, 64, 64, 57, 40, 35, 50, 6, 37, 47, 35, 0, 0, 19, 71, 84, 149, 5, 72, 16, 82, 16, 125, 47, 13, 34, 10, 6, 113, 34, 47, 0, 14, 67, 4, 69, 128, 35, 47, 81, 40, 49, 6, 113, 47, 0, 0, 0, 13, 69, 48, 81, 193, 5, 64, 55, 13, 134, 113, 47, 0, 16, 70, 8, 83, 12, 21, 101, 69, 69, 110, 55, 82, 57, 40, 12, 0, 0, 0, 21, 71, 36, 225, 215, 5, 101, 77, 4, 37, 66, 79, 58, 35, 82, 6, 40, 12, 63, 35, 0, 0, 0, 8, 197, 92, 21, 20, 21, 32, 8, 0, 9, 198, 5, 53, 1, 73, 65, 64, 66, 0, 0, 10, 67, 89, 33, 75, 81, 34, 110, 49, 0, 0, 9, 198, 92, 81, 82, 28, 19, 13, 66, 12, 69, 80, 241, 71, 20, 80, 47, 40, 134, 114, 0, 14, 69, 48, 144, 137, 16, 240, 55, 13, 69, 37, 70, 40, 0, 0, 16, 70, 88, 16, 82, 92, 83, 0, 81, 113, 34, 82, 6, 110, 55, 0, 0, 10, 199, 84, 149, 5, 72, 208, 84, 20, 67, 14, 67, 44, 20, 20, 49, 35, 48, 47, 6, 121, 50, 0, 24, 0, 20, 72, 61, 85, 5, 56, 145, 75, 92, 16, 118, 47, 13, 50, 6, 37, 49, 58, 35, 0, 0, 14, 69, 88, 84, 147, 80, 80, 81, 110, 34, 87, 47, 13, 0, 17, 70, 56, 80, 146, 5, 50, 193, 50, 13, 69, 34, 35, 87, 49, 35, 0, 0, 0, 0, 17, 70, 56, 81, 197, 77, 65, 82, 50, 114, 134, 13, 87, 47, 110, 34, 0, 20, 72, 24, 147, 9, 65, 1, 78, 76, 80, 81, 13, 55, 13, 48, 106, 50, 87, 13, 0, 13, 68, 76, 245, 197, 48, 87, 115, 82, 6, 110, 55, 0, 21, 72, 25, 32, 83, 21, 32, 149, 72, 112, 81, 34, 121, 86, 13, 34, 69, 109, 34, 134, 0, 0, 0, 0, 0, 12, 68, 72, 81, 201, 20, 34, 13, 88, 37, 12, 0, 17, 70, 52, 147, 137, 77, 65, 82, 63, 13, 50, 107, 87, 47, 13, 34, 0, 21, 72, 65, 149, 8, 4, 115, 210, 5, 48, 48, 37, 47, 6, 113, 134, 115, 34, 35, 87, 0, 0, 8, 197, 61, 3, 1, 5, 48, 66, 0, 17, 70, 88, 84, 147, 24, 83, 4, 81, 110, 34, 87, 81, 110, 55, 47, 0, 0, 24, 73, 8, 85, 12, 20, 129, 77, 77, 65, 82, 69, 106, 47, 55, 37, 12, 106, 63, 87, 47, 110, 34, 0, 0, 9, 68, 92, 22, 78, 20, 21, 0, 10, 0, 14, 69, 8, 85, 197, 56, 64, 69, 114, 82, 13, 50, 47, 0, 14, 69, 12, 20, 141, 20, 224, 49, 35, 34, 63, 106, 50, 0, 0, 15, 70, 92, 147, 12, 20, 228, 192, 82, 107, 55, 13, 50, 87, 0, 18, 70, 40, 84, 133, 52, 144, 64, 57, 2, 114, 34, 13, 63, 6, 37, 35, 0, 0, 0, 13, 68, 20, 194, 90, 20, 37, 55, 6, 37, 12, 86, 0, 0, 8, 195, 28, 16, 78, 72, 9, 32, 14, 69, 36, 225, 210, 36, 64, 37, 66, 79, 34, 13, 70, 0, 0, 10, 67, 4, 193, 197, 35, 55, 134, 13, 0, 11, 70, 77, 65, 86, 20, 228, 192, 21, 0, 10, 11, 70, 12, 243, 12, 36, 228, 192, 21, 0, 10, 0, 6, 195, 92, 145, 64, 8, 7, 195, 80, 241, 64, 72, 32, 18, 71, 76, 50, 1, 48, 181, 217, 44, 87, 49, 35, 55, 49, 82, 121, 49, 0, 12, 71, 28, 84, 141, 37, 53, 15, 56, 21, 0, 10, 0, 19, 72, 92, 83, 12, 36, 225, 212, 60, 224, 58, 106, 55, 37, 66, 47, 13, 50, 0, 0, 0, 0, 6, 195, 32, 241, 64, 8, 0, 0, 16, 69, 88, 18, 193, 57, 64, 81, 2, 35, 49, 6, 35, 50, 47, 0, 10, 67, 4, 209, 78, 113, 63, 106, 50, 0, 10, 69, 5, 37, 8, 85, 32, 21, 0, 10, 0, 0, 0, 0, 9, 198, 4, 195, 73, 76, 178, 69, 67, 13, 69, 16, 84, 137, 12, 176, 70, 106, 34, 37, 49, 0, 0, 0, 9, 67, 105, 147, 0, 87, 121, 55, 0, 0, 0, 15, 69, 76, 243, 143, 72, 80, 87, 40, 50, 6, 115, 34, 13, 0, 17, 70, 29, 32, 70, 24, 149, 9, 79, 34, 35, 81, 6, 37, 47, 37, 0, 13, 70, 72, 245, 83, 76, 80, 85, 34, 13, 87, 118, 0, 16, 69, 76, 245, 197, 80, 240, 87, 40, 58, 6, 106, 12, 47, 40, 0, 16, 69, 52, 20, 21, 80, 240, 63, 35, 48, 6, 40, 12, 47, 40, 0, 15, 69, 44, 19, 129, 16, 16, 49, 35, 50, 35, 70, 2, 35, 0, 0, 0, 18, 70, 65, 35, 198, 21, 65, 83, 48, 34, 108, 81, 13, 47, 6, 106, 87, 0, 18, 71, 64, 245, 16, 61, 84, 146, 36, 48, 108, 47, 48, 40, 34, 6, 37, 0, 20, 71, 36, 212, 18, 60, 212, 20, 84, 37, 63, 48, 34, 6, 108, 63, 48, 47, 40, 0, 10, 199, 24, 147, 129, 48, 148, 212, 20, 67, 18, 70, 4, 192, 133, 73, 69, 83, 35, 55, 69, 6, 110, 34, 47, 109, 87, 0, 0, 11, 70, 29, 83, 12, 37, 97, 82, 21, 0, 10, 0, 10, 69, 8, 20, 139, 49, 144, 21, 0, 10, 0, 21, 72, 9, 33, 68, 20, 226, 193, 53, 0, 69, 34, 114, 70, 13, 50, 49, 35, 63, 48, 0, 14, 70, 4, 36, 129, 32, 19, 64, 113, 69, 34, 35, 63, 0, 0, 20, 71, 44, 245, 9, 48, 163, 206, 76, 49, 108, 47, 13, 55, 57, 6, 133, 50, 87, 0, 7, 195, 32, 243, 64, 72, 32, 9, 67, 44, 147, 64, 21, 0, 41, 10, 0, 12, 68, 32, 22, 68, 56, 105, 120, 70, 13, 50, 0, 17, 70, 8, 83, 138, 4, 210, 78, 69, 106, 50, 73, 13, 63, 13, 50, 0, 21, 72, 5, 32, 200, 36, 209, 68, 21, 48, 35, 34, 134, 37, 63, 6, 114, 70, 106, 87, 0, 0, 10, 69, 72, 131, 196, 21, 48, 21, 0, 10, 8, 197, 48, 17, 146, 5, 48, 66, 0, 12, 201, 81, 32, 80, 77, 85, 84, 40, 145, 83, 66, 12, 67, 4, 195, 205, 35, 55, 10, 6, 108, 63, 0, 11, 67, 36, 196, 197, 6, 37, 55, 86, 13, 0, 15, 70, 48, 84, 207, 80, 131, 192, 55, 13, 87, 40, 47, 40, 0, 0, 18, 71, 88, 243, 19, 12, 129, 78, 44, 81, 108, 55, 87, 49, 106, 66, 49, 0, 0, 0, 10, 69, 92, 147, 19, 60, 224, 21, 0, 10, 0, 15, 70, 61, 81, 19, 32, 84, 128, 118, 47, 87, 105, 110, 34, 0, 17, 70, 12, 80, 201, 48, 144, 64, 87, 13, 87, 37, 12, 55, 37, 35, 0, 0, 17, 71, 12, 128, 82, 52, 18, 78, 20, 89, 113, 63, 6, 121, 12, 50, 0, 0, 11, 68, 28, 86, 69, 72, 134, 121, 13, 34, 0, 0, 10, 69, 61, 129, 143, 72, 64, 21, 0, 10, 0, 16, 70, 32, 21, 133, 56, 112, 64, 105, 113, 81, 13, 66, 134, 35, 0, 0, 12, 71, 92, 147, 12, 37, 53, 15, 56, 21, 0, 10, 12, 71, 77, 65, 86, 20, 228, 207, 56, 21, 0, 10, 0, 0, 0, 14, 70, 52, 21, 20, 32, 81, 64, 63, 35, 47, 6, 114, 0, 0, 0, 18, 8, 2, 195, 170, 18, 5, 20, 25, 4, 69, 111, 34, 13, 47, 121, 47, 0, 14, 68, 32, 244, 197, 4, 105, 40, 87, 6, 37, 12, 35, 0, 0, 15, 69, 92, 83, 5, 21, 32, 82, 110, 55, 10, 6, 114, 34, 0, 0, 0, 20, 71, 88, 19, 141, 20, 193, 87, 20, 81, 35, 50, 63, 13, 55, 6, 114, 82, 13, 0, 11, 70, 16, 83, 9, 48, 18, 0, 21, 0, 10, 0, 11, 200, 56, 147, 77, 21, 35, 69, 21, 32, 65, 22, 72, 52, 17, 1, 28, 20, 203, 5, 32, 63, 35, 70, 35, 134, 6, 35, 87, 49, 35, 34, 0, 0, 16, 69, 32, 84, 133, 72, 240, 105, 106, 34, 6, 106, 12, 34, 40, 0, 17, 69, 4, 64, 71, 36, 240, 35, 70, 6, 113, 73, 37, 38, 2, 118, 0, 6, 195, 92, 16, 82, 8, 14, 69, 16, 83, 9, 48, 16, 70, 13, 55, 107, 55, 35, 0, 14, 69, 21, 84, 143, 64, 16, 126, 34, 6, 115, 48, 35, 0, 0, 0, 0, 13, 68, 16, 246, 69, 56, 70, 129, 57, 6, 106, 50, 0, 18, 72, 12, 132, 137, 77, 65, 76, 48, 80, 49, 34, 13, 87, 47, 110, 55, 0, 0, 13, 69, 76, 129, 73, 48, 16, 89, 37, 12, 55, 35, 0, 15, 69, 48, 245, 73, 76, 80, 55, 40, 58, 6, 37, 12, 86, 0, 14, 69, 5, 66, 5, 56, 80, 35, 47, 6, 114, 50, 13, 0, 0, 0, 0, 21, 72, 13, 34, 77, 64, 83, 5, 56, 80, 49, 34, 13, 63, 48, 13, 55, 37, 12, 50, 0, 20, 72, 12, 19, 79, 84, 99, 1, 28, 80, 49, 35, 63, 40, 81, 55, 6, 113, 88, 0, 0, 6, 97, 97, 0, 4, 110, 2, 98, 105, 100, 3, 2, 113, 50, 0, 110, 2, 103, 114, 101, 110, 115, 101, 110, 0, 110, 2, 103, 114, 121, 112, 101, 110, 100, 0, 110, 2, 104, 97, 110, 103, 105, 103, 0, 110, 2, 104, 97, 110, 107, 0, 110, 2, 104, 111, 117, 100, 101, 110, 0, 110, 2, 108, 111, 107, 0, 110, 2, 109, 101, 108, 100, 98, 97, 0, 110, 2, 112, 97, 115, 98, 97, 0, 110, 2, 115, 105, 101, 110, 0, 110, 2, 115, 112, 114, 101, 101, 107, 0, 110, 2, 115, 116, 17, 65, 17, 65, 17, 67, 0, 110, 2, 116, 97, 115, 98, 0, 110, 2, 118, 97, 97, 114, 0, 110, 2, 118, 97, 108, 108, 17, 65, 17, 67, 0, 110, 2, 118, 101, 103, 98, 97, 0, 110, 2, 118, 117, 108, 108, 101, 110, 100, 0, 110, 2, 119, 101, 115, 105, 103, 0, 110, 2, 119, 121, 115, 101, 110, 100, 101, 32, 118, 111, 111, 114, 110, 0, 110, 2, 101, 101, 110, 3, 2, 113, 50, 19, 0, 110, 116, 114, 101, 107, 108, 105, 107, 3, 2, 113, 50, 47, 34, 110, 49, 55, 13, 49, 0, 110, 100, 111, 101, 110, 108, 105, 107, 3, 2, 113, 50, 70, 40, 50, 55, 13, 49, 0, 110, 110, 101, 101, 109, 108, 105, 107, 3, 2, 113, 50, 114, 63, 55, 13, 49, 0, 109, 2, 98, 111, 114, 115, 3, 2, 113, 63, 0, 110, 2, 115, 105, 101, 110, 32, 24, 3, 6, 113, 50, 0, 4, 110, 119, 101, 110, 2, 32, 3, 6, 113, 50, 82, 106, 50, 0, 110, 119, 101, 110, 2, 100, 0, 110, 115, 116, 101, 114, 107, 3, 6, 113, 50, 87, 47, 110, 34, 49, 0, 110, 103, 101, 8, 2, 21, 14, 128, 132, 133, 3, 6, 113, 50, 134, 13, 0, 110, 103, 101, 101, 2, 12, 3, 6, 113, 50, 134, 114, 0, 110, 115, 2, 32, 3, 6, 131, 50, 87, 0, 110, 115, 101, 2, 32, 3, 6, 131, 50, 87, 13, 0, 3, 113, 0, 114, 100, 8, 2, 114, 3, 113, 34, 47, 0, 114, 100, 8, 2, 111, 3, 113, 34, 47, 10, 0, 4, 110, 2, 103, 3, 113, 50, 0, 110, 2, 108, 111, 107, 32, 24, 0, 110, 2, 115, 112, 114, 101, 101, 107, 32, 24, 0, 110, 2, 115, 116, 17, 65, 17, 65, 17, 67, 32, 24, 0, 110, 2, 116, 114, 101, 107, 32, 24, 0, 110, 2, 118, 97, 108, 108, 101, 114, 0, 4, 110, 2, 115, 107, 111, 117, 3, 113, 50, 6, 0, 110, 2, 118, 97, 110, 107, 0, 4, 110, 100, 2, 114, 111, 107, 3, 113, 50, 47, 10, 0, 110, 100, 2, 114, 117, 115, 0, 110, 116, 101, 108, 8, 3, 113, 50, 47, 110, 55, 0, 110, 100, 101, 108, 101, 3, 113, 50, 70, 114, 55, 13, 10, 0, 110, 115, 116, 101, 2, 108, 108, 101, 114, 105, 103, 3, 113, 50, 87, 47, 6, 110, 0, 110, 110, 101, 109, 2, 17, 65, 3, 113, 50, 114, 63, 0, 105, 3, 120, 0, 4, 110, 2, 100, 106, 105, 101, 3, 120, 66, 0, 110, 2, 116, 106, 105, 101, 0, 4, 100, 106, 105, 101, 3, 120, 78, 37, 0, 116, 106, 105, 101, 0, 7, 6, 97, 110, 0, 4, 1, 17, 67, 2, 107, 101, 101, 114, 3, 2, 35, 50, 0, 8, 2, 17, 65, 0, 8, 2, 101, 109, 105, 101, 0, 110, 8, 2, 97, 21, 0, 97, 116, 111, 2, 109, 105, 101, 3, 2, 35, 50, 2, 35, 47, 2, 40, 0, 97, 116, 111, 109, 105, 101, 115, 3, 2, 35, 50, 2, 35, 47, 115, 63, 2, 37, 87, 0, 111, 2, 114, 101, 107, 17, 67, 3, 2, 35, 50, 2, 40, 0, 111, 109, 97, 2, 108, 105, 101, 3, 2, 35, 50, 2, 40, 63, 2, 35, 0, 111, 109, 97, 108, 105, 101, 115, 3, 2, 35, 50, 2, 40, 63, 113, 55, 37, 87, 0, 101, 107, 2, 100, 111, 116, 3, 2, 35, 50, 2, 106, 49, 0, 101, 2, 109, 111, 3, 2, 35, 50, 13, 0, 116, 105, 8, 2, 17, 67, 14, 128, 132, 132, 3, 2, 35, 50, 47, 2, 37, 0, 116, 114, 97, 2, 115, 105, 101, 116, 3, 2, 35, 50, 47, 34, 2, 35, 0, 116, 101, 2, 110, 110, 17, 65, 3, 2, 35, 50, 47, 106, 0, 101, 116, 116, 101, 1, 17, 67, 2, 32, 3, 2, 35, 50, 106, 47, 0, 2, 103, 105, 110, 97, 3, 2, 35, 66, 0, 103, 101, 2, 108, 105, 101, 114, 3, 2, 35, 66, 13, 0, 103, 111, 114, 97, 3, 2, 35, 66, 79, 129, 34, 2, 35, 0, 103, 111, 108, 2, 101, 3, 2, 131, 66, 134, 2, 40, 55, 0, 103, 108, 8, 2, 17, 65, 3, 2, 131, 66, 134, 55, 2, 0, 97, 8, 2, 17, 67, 3, 4, 35, 50, 35, 0, 1, 103, 2, 32, 3, 21, 0, 111, 2, 114, 97, 107, 3, 35, 50, 2, 40, 0, 116, 114, 111, 111, 112, 1, 21, 3, 35, 50, 47, 34, 6, 115, 48, 0, 116, 114, 111, 112, 101, 1, 21, 2, 32, 3, 35, 50, 47, 34, 6, 115, 48, 13, 0, 116, 114, 111, 112, 105, 101, 1, 21, 3, 35, 50, 47, 34, 6, 115, 48, 37, 0, 116, 114, 111, 112, 105, 101, 1, 21, 2, 32, 24, 3, 35, 50, 47, 34, 40, 48, 6, 37, 0, 115, 106, 111, 118, 105, 3, 35, 50, 89, 7, 115, 81, 13, 0, 103, 108, 101, 101, 114, 3, 35, 66, 55, 114, 34, 0, 4, 2, 100, 106, 105, 101, 12, 3, 119, 66, 0, 2, 116, 106, 105, 101, 0, 4, 115, 1, 100, 3, 131, 50, 87, 0, 115, 1, 104, 0, 115, 1, 107, 0, 115, 1, 108, 0, 115, 1, 114, 102, 0, 115, 1, 114, 107, 0, 103, 111, 108, 97, 3, 131, 66, 134, 6, 115, 55, 35, 0, 7, 6, 98, 97, 0, 4, 2, 108, 97, 110, 115, 3, 69, 2, 35, 0, 2, 108, 100, 97, 100, 105, 103, 0, 2, 108, 106, 97, 97, 114, 0, 2, 108, 107, 111, 110, 0, 2, 108, 108, 111, 110, 0, 2, 110, 97, 108, 17, 65, 0, 2, 110, 105, 101, 114, 0, 2, 114, 101, 116, 25, 0, 2, 114, 111, 110, 0, 2, 115, 105, 101, 108, 105, 0, 2, 116, 105, 107, 0, 8, 2, 115, 97, 0, 114, 2, 98, 17, 65, 3, 69, 2, 35, 34, 0, 116, 97, 108, 2, 106, 111, 110, 3, 69, 2, 35, 47, 2, 35, 55, 0, 116, 116, 101, 2, 114, 121, 3, 69, 2, 35, 47, 13, 0, 107, 97, 116, 101, 2, 108, 3, 69, 2, 35, 49, 13, 47, 110, 0, 107, 116, 101, 2, 114, 105, 3, 69, 2, 35, 49, 47, 114, 0, 110, 100, 2, 105, 101, 116, 3, 69, 2, 35, 50, 70, 0, 4, 108, 97, 107, 108, 97, 118, 97, 3, 69, 2, 35, 55, 2, 35, 49, 55, 113, 82, 2, 35, 0, 108, 97, 107, 108, 97, 119, 97, 0, 108, 97, 110, 2, 115, 101, 101, 114, 3, 69, 2, 35, 55, 2, 35, 50, 0, 108, 108, 101, 114, 2, 105, 110, 17, 65, 3, 69, 2, 35, 55, 13, 34, 0, 108, 106, 117, 3, 69, 2, 35, 55, 57, 116, 0, 108, 104, 111, 114, 3, 69, 2, 35, 55, 105, 115, 34, 0, 108, 108, 101, 2, 116, 3, 69, 2, 35, 55, 106, 0, 108, 108, 97, 100, 101, 3, 69, 2, 35, 55, 113, 70, 13, 0, 106, 111, 110, 101, 2, 116, 3, 69, 2, 35, 57, 2, 40, 50, 106, 0, 109, 8, 2, 98, 111, 101, 115, 3, 69, 2, 35, 63, 0, 4, 110, 2, 107, 101, 116, 3, 69, 2, 35, 66, 0, 110, 2, 107, 105, 101, 114, 0, 110, 2, 107, 114, 111, 116, 0, 115, 105, 2, 108, 105, 115, 107, 3, 69, 2, 35, 87, 13, 0, 115, 111, 116, 104, 111, 3, 69, 2, 35, 87, 40, 47, 2, 40, 0, 115, 116, 105, 108, 108, 101, 3, 69, 2, 35, 87, 47, 37, 12, 55, 0, 104, 97, 109, 97, 3, 69, 2, 35, 105, 113, 63, 2, 35, 0, 110, 100, 2, 17, 65, 108, 105, 101, 114, 3, 69, 4, 35, 50, 70, 0, 108, 108, 111, 2, 116, 3, 69, 4, 35, 55, 108, 0, 1, 21, 2, 114, 101, 110, 3, 69, 6, 113, 0, 97, 114, 108, 105, 107, 1, 21, 3, 69, 6, 113, 34, 55, 13, 49, 0, 116, 101, 8, 3, 69, 7, 113, 47, 13, 0, 107, 108, 101, 105, 3, 69, 13, 49, 55, 121, 0, 103, 97, 115, 105, 101, 3, 69, 13, 134, 113, 87, 37, 0, 2, 114, 105, 116, 111, 110, 3, 69, 35, 0, 114, 111, 2, 109, 101, 116, 101, 114, 3, 69, 35, 34, 2, 40, 0, 114, 97, 2, 107, 3, 69, 35, 34, 6, 35, 0, 114, 111, 107, 3, 69, 35, 34, 7, 108, 49, 10, 0, 100, 2, 114, 3, 69, 35, 47, 0, 100, 8, 2, 17, 65, 3, 69, 35, 47, 10, 0, 107, 8, 2, 111, 3, 69, 35, 49, 10, 0, 110, 100, 2, 17, 65, 3, 69, 35, 50, 47, 0, 110, 100, 2, 101, 3, 69, 35, 50, 70, 0, 108, 108, 2, 101, 116, 106, 105, 101, 12, 3, 69, 35, 55, 0, 108, 115, 101, 109, 3, 69, 35, 55, 87, 13, 63, 0, 115, 116, 105, 111, 110, 3, 69, 35, 87, 47, 37, 108, 50, 0, 107, 101, 110, 3, 69, 113, 49, 13, 50, 0, 114, 98, 101, 114, 116, 111, 110, 3, 69, 113, 69, 13, 34, 47, 2, 108, 50, 0, 98, 97, 3, 69, 113, 69, 35, 0, 98, 97, 2, 116, 106, 105, 101, 3, 69, 113, 69, 119, 0, 115, 105, 2, 115, 3, 69, 113, 87, 13, 0, 100, 106, 105, 101, 3, 69, 119, 78, 37, 0, 7, 6, 98, 101, 0, 115, 101, 114, 105, 110, 103, 3, 8, 69, 13, 87, 114, 34, 13, 66, 0, 110, 8, 2, 17, 67, 105, 101, 110, 3, 69, 2, 106, 50, 0, 110, 8, 2, 103, 97, 3, 69, 2, 106, 66, 0, 114, 2, 108, 121, 110, 3, 69, 2, 110, 34, 0, 110, 101, 2, 100, 121, 3, 69, 2, 114, 50, 13, 0, 1, 17, 67, 2, 114, 115, 105, 101, 3, 69, 6, 111, 0, 101, 114, 1, 21, 2, 32, 3, 69, 6, 114, 34, 0, 4, 114, 105, 110, 103, 3, 69, 6, 114, 34, 13, 66, 0, 114, 105, 110, 103, 1, 98, 111, 114, 107, 115, 0, 116, 101, 114, 3, 69, 6, 114, 47, 13, 34, 0, 101, 108, 100, 105, 103, 1, 21, 3, 69, 6, 114, 55, 70, 13, 134, 0, 107, 101, 114, 8, 2, 17, 67, 21, 3, 69, 7, 114, 49, 13, 34, 0, 4, 1, 21, 2, 17, 67, 3, 69, 13, 0, 1, 98, 17, 65, 17, 67, 2, 108, 0, 1, 117, 106, 2, 108, 108, 17, 65, 0, 2, 100, 114, 21, 0, 2, 119, 101, 103, 105, 110, 103, 0, 8, 2, 17, 67, 121, 0, 8, 2, 21, 14, 128, 132, 130, 0, 8, 2, 32, 0, 2, 97, 109, 112, 3, 69, 13, 19, 0, 114, 2, 115, 101, 114, 107, 3, 69, 13, 34, 0, 4, 114, 105, 110, 103, 1, 17, 67, 3, 69, 13, 34, 13, 66, 0, 114, 105, 110, 103, 1, 111, 0, 107, 101, 110, 3, 69, 13, 49, 106, 50, 0, 110, 100, 101, 1, 98, 10, 3, 69, 13, 50, 70, 13, 0, 100, 119, 2, 21, 3, 69, 13, 70, 58, 0, 100, 101, 2, 17, 67, 102, 3, 69, 13, 70, 110, 0, 100, 101, 108, 105, 110, 103, 3, 69, 13, 70, 114, 55, 13, 66, 0, 119, 121, 115, 1, 21, 3, 69, 13, 82, 121, 87, 0, 115, 116, 101, 2, 107, 3, 69, 13, 87, 47, 110, 0, 115, 105, 103, 2, 116, 105, 103, 3, 69, 13, 87, 107, 134, 0, 104, 101, 112, 3, 69, 13, 105, 106, 48, 0, 103, 101, 114, 2, 17, 65, 3, 69, 13, 134, 114, 34, 0, 4, 2, 17, 67, 11, 12, 3, 69, 106, 0, 100, 2, 116, 0, 100, 106, 105, 101, 3, 69, 106, 12, 37, 78, 37, 0, 4, 100, 1, 21, 2, 32, 3, 69, 106, 47, 0, 100, 2, 17, 67, 0, 100, 2, 114, 97, 110, 100, 0, 100, 2, 119, 97, 114, 109, 0, 100, 2, 119, 111, 111, 114, 100, 0, 116, 108, 101, 104, 101, 2, 109, 3, 69, 106, 47, 55, 2, 37, 2, 106, 0, 100, 119, 2, 105, 101, 103, 3, 69, 106, 47, 82, 0, 110, 100, 101, 3, 69, 106, 50, 70, 13, 0, 110, 103, 101, 108, 3, 69, 106, 66, 13, 55, 0, 115, 115, 105, 101, 3, 69, 106, 87, 37, 0, 115, 116, 101, 2, 32, 3, 69, 106, 87, 47, 13, 0, 1, 101, 114, 2, 108, 25, 12, 3, 69, 110, 0, 114, 8, 2, 17, 67, 3, 69, 110, 34, 0, 114, 107, 101, 8, 3, 69, 110, 34, 49, 13, 0, 114, 103, 101, 3, 69, 110, 34, 79, 13, 0, 114, 103, 3, 69, 110, 34, 134, 0, 4, 107, 2, 32, 3, 69, 110, 49, 0, 107, 2, 100, 0, 107, 2, 102, 0, 107, 2, 104, 0, 107, 2, 109, 0, 107, 2, 115, 0, 107, 107, 2, 12, 0, 4, 1, 114, 2, 108, 25, 3, 69, 110, 55, 0, 108, 1, 17, 67, 2, 32, 0, 108, 8, 2, 17, 67, 0, 108, 108, 2, 12, 0, 4, 1, 110, 111, 115, 2, 115, 105, 101, 3, 69, 114, 0, 2, 100, 101, 32, 0, 101, 2, 12, 0, 4, 101, 114, 1, 97, 17, 67, 11, 3, 69, 114, 34, 0, 101, 114, 1, 101, 105, 100, 100, 101, 116, 0, 101, 114, 1, 115, 121, 0, 114, 101, 2, 32, 3, 69, 114, 34, 13, 0, 114, 105, 110, 103, 1, 116, 110, 111, 3, 69, 114, 34, 13, 66, 0, 116, 101, 2, 32, 3, 69, 114, 47, 13, 0, 116, 101, 115, 1, 97, 105, 100, 2, 21, 3, 69, 114, 47, 13, 87, 0, 116, 105, 101, 115, 3, 69, 114, 47, 37, 87, 0, 4, 107, 101, 114, 1, 21, 2, 32, 3, 69, 114, 49, 13, 34, 0, 107, 101, 114, 1, 21, 2, 116, 106, 105, 101, 0, 107, 101, 114, 2, 17, 67, 21, 0, 107, 101, 114, 2, 17, 65, 17, 65, 3, 69, 114, 49, 13, 34, 10, 0, 4, 110, 101, 1, 21, 2, 32, 3, 69, 114, 50, 13, 0, 110, 101, 2, 114, 0, 110, 105, 2, 103, 0, 100, 101, 2, 115, 116, 114, 3, 69, 114, 70, 13, 0, 100, 101, 108, 3, 69, 114, 70, 13, 55, 0, 100, 101, 118, 3, 69, 114, 70, 13, 81, 0, 100, 101, 115, 2, 32, 3, 69, 114, 70, 13, 87, 0, 4, 119, 101, 2, 107, 110, 105, 101, 3, 69, 114, 82, 13, 0, 119, 101, 2, 108, 105, 112, 0, 119, 101, 2, 114, 97, 115, 105, 101, 0, 119, 101, 2, 114, 105, 103, 0, 119, 101, 110, 100, 101, 3, 69, 114, 82, 13, 50, 70, 13, 0, 119, 105, 110, 103, 3, 69, 114, 82, 13, 66, 0, 4, 115, 2, 105, 101, 32, 3, 69, 114, 87, 0, 115, 2, 105, 101, 115, 32, 0, 115, 101, 109, 3, 69, 114, 87, 13, 63, 0, 115, 105, 103, 3, 69, 114, 87, 13, 134, 0, 97, 117, 3, 69, 118, 0, 105, 2, 12, 3, 69, 121, 0, 105, 103, 101, 3, 69, 121, 12, 88, 0, 117, 2, 17, 67, 3, 69, 126, 0, 117, 101, 108, 3, 69, 126, 13, 55, 0, 7, 6, 100, 101, 0, 1, 21, 2, 114, 111, 115, 105, 101, 3, 47, 10, 2, 114, 0, 4, 2, 109, 111, 111, 110, 3, 70, 2, 37, 0, 2, 112, 114, 101, 115, 115, 0, 111, 100, 111, 2, 114, 97, 110, 116, 3, 70, 2, 37, 2, 40, 70, 2, 40, 0, 116, 97, 105, 2, 108, 108, 101, 101, 114, 3, 70, 2, 37, 12, 47, 2, 121, 0, 109, 111, 110, 101, 3, 70, 2, 37, 63, 115, 50, 13, 0, 4, 2, 107, 108, 105, 110, 17, 65, 3, 70, 2, 106, 0, 2, 109, 111, 17, 67, 114, 0, 2, 112, 117, 116, 97, 0, 2, 115, 107, 117, 110, 0, 116, 111, 2, 110, 17, 65, 3, 70, 2, 106, 47, 2, 40, 0, 110, 8, 2, 100, 114, 105, 3, 70, 2, 106, 50, 0, 108, 105, 8, 2, 107, 97, 3, 70, 2, 106, 55, 2, 37, 0, 108, 105, 107, 97, 2, 116, 101, 115, 115, 3, 70, 2, 106, 55, 2, 37, 49, 2, 35, 0, 98, 105, 2, 116, 101, 3, 70, 2, 106, 69, 2, 37, 0, 4, 98, 117, 2, 116, 97, 3, 70, 2, 106, 69, 2, 116, 0, 98, 117, 2, 116, 101, 21, 0, 115, 8, 2, 112, 111, 3, 70, 2, 106, 87, 0, 114, 8, 2, 100, 117, 105, 17, 67, 3, 70, 2, 110, 34, 0, 108, 112, 104, 105, 110, 105, 117, 109, 3, 70, 2, 110, 55, 81, 37, 50, 37, 38, 109, 63, 0, 4, 2, 102, 108, 97, 115, 105, 3, 70, 2, 114, 0, 2, 104, 105, 100, 114, 0, 2, 107, 114, 105, 109, 105, 110, 97, 0, 2, 115, 116, 114, 117, 107, 116, 0, 101, 2, 109, 111, 101, 100, 105, 103, 0, 115, 116, 97, 98, 105, 108, 105, 8, 2, 115, 3, 70, 2, 114, 87, 47, 2, 35, 69, 2, 37, 55, 2, 37, 0, 115, 101, 109, 98, 101, 114, 3, 70, 2, 114, 87, 106, 63, 69, 13, 34, 0, 4, 117, 114, 2, 100, 114, 101, 110, 107, 3, 70, 2, 116, 13, 34, 0, 117, 114, 2, 100, 114, 105, 110, 103, 21, 0, 117, 114, 2, 103, 114, 111, 110, 100, 0, 117, 114, 2, 108, 101, 101, 102, 0, 117, 114, 2, 108, 111, 112, 21, 0, 117, 114, 2, 108, 117, 103, 116, 0, 117, 114, 2, 115, 105, 103, 116, 0, 117, 114, 2, 116, 114, 97, 112, 116, 0, 117, 114, 2, 119, 101, 101, 17, 67, 0, 117, 114, 2, 119, 105, 110, 116, 101, 114, 0, 117, 114, 2, 97, 97, 114, 3, 70, 2, 116, 13, 34, 10, 0, 117, 114, 115, 112, 101, 107, 3, 70, 2, 116, 13, 34, 87, 48, 106, 49, 0, 4, 117, 114, 2, 98, 111, 3, 70, 2, 126, 34, 0, 117, 114, 2, 100, 97, 103, 0, 117, 114, 2, 112, 114, 105, 101, 109, 0, 117, 114, 2, 114, 101, 105, 115, 0, 117, 114, 2, 115, 107, 121, 110, 17, 65, 0, 117, 114, 2, 115, 107, 121, 110, 100, 101, 0, 117, 114, 2, 115, 111, 101, 107, 0, 117, 114, 2, 119, 97, 97, 105, 100, 0, 2, 103, 114, 97, 100, 17, 65, 3, 70, 4, 114, 0, 116, 97, 105, 108, 3, 70, 6, 37, 12, 47, 121, 55, 0, 110, 105, 109, 8, 3, 70, 7, 106, 50, 13, 63, 0, 110, 107, 101, 110, 2, 100, 3, 70, 7, 106, 66, 49, 13, 50, 0, 4, 1, 10, 2, 110, 101, 32, 3, 70, 13, 0, 1, 21, 2, 107, 111, 110, 116, 114, 97, 107, 0, 1, 21, 2, 109, 101, 110, 116, 0, 2, 98, 17, 65, 0, 2, 107, 97, 97, 110, 0, 2, 107, 97, 110, 101, 0, 2, 107, 114, 101, 0, 2, 108, 97, 97, 110, 0, 114, 100, 1, 21, 2, 32, 3, 70, 13, 34, 47, 0, 112, 97, 114, 116, 101, 2, 109, 101, 110, 116, 3, 70, 13, 48, 2, 35, 34, 47, 13, 0, 112, 111, 115, 105, 116, 111, 3, 70, 13, 48, 115, 87, 37, 47, 40, 0, 107, 97, 110, 116, 2, 32, 3, 70, 13, 49, 35, 50, 47, 0, 110, 105, 115, 1, 10, 3, 70, 13, 50, 13, 87, 0, 110, 100, 1, 21, 2, 115, 116, 101, 3, 70, 13, 50, 47, 0, 110, 100, 1, 21, 2, 101, 114, 3, 70, 13, 50, 70, 0, 108, 101, 8, 2, 103, 17, 65, 3, 70, 13, 55, 13, 0, 108, 101, 1, 110, 117, 107, 2, 25, 3, 70, 13, 55, 106, 0, 108, 105, 2, 114, 105, 117, 109, 3, 70, 13, 55, 107, 0, 4, 108, 111, 111, 115, 3, 70, 13, 55, 115, 87, 0, 108, 111, 115, 0, 98, 97, 2, 116, 116, 101, 101, 114, 3, 70, 13, 69, 2, 35, 0, 98, 117, 117, 116, 3, 70, 13, 69, 116, 47, 0, 119, 101, 2, 116, 25, 3, 70, 13, 82, 106, 0, 112, 111, 116, 2, 32, 3, 70, 106, 48, 2, 40, 0, 107, 97, 100, 101, 2, 115, 3, 70, 106, 49, 6, 113, 70, 13, 0, 107, 97, 100, 101, 2, 110, 3, 70, 106, 49, 35, 70, 6, 106, 0, 110, 116, 101, 1, 21, 2, 21, 3, 70, 106, 50, 47, 13, 0, 110, 107, 3, 70, 106, 66, 49, 0, 115, 105, 98, 101, 108, 3, 70, 106, 87, 37, 69, 110, 55, 0, 114, 109, 1, 17, 67, 21, 2, 25, 3, 70, 110, 34, 14, 63, 0, 114, 103, 101, 8, 3, 70, 110, 34, 134, 13, 0, 4, 114, 100, 101, 1, 101, 101, 119, 116, 3, 70, 111, 34, 70, 13, 0, 114, 100, 101, 8, 2, 25, 0, 8, 2, 107, 108, 97, 115, 115, 3, 70, 114, 0, 4, 108, 101, 1, 114, 101, 100, 110, 111, 2, 21, 3, 70, 114, 55, 13, 10, 0, 108, 101, 1, 114, 111, 111, 118, 2, 21, 0, 7, 6, 101, 101, 0, 114, 98, 105, 101, 100, 119, 3, 2, 114, 34, 69, 2, 37, 47, 82, 0, 114, 119, 8, 3, 2, 114, 34, 82, 0, 4, 110, 2, 100, 114, 97, 103, 21, 3, 2, 114, 50, 0, 110, 2, 109, 97, 108, 105, 103, 0, 110, 2, 112, 97, 114, 105, 103, 0, 110, 2, 118, 111, 114, 109, 0, 110, 8, 2, 115, 116, 101, 109, 109, 0, 110, 8, 2, 115, 121, 0, 110, 8, 2, 116, 111, 110, 0, 110, 8, 2, 118, 111, 117, 100, 21, 0, 4, 114, 1, 21, 2, 24, 3, 6, 114, 34, 0, 114, 1, 107, 105, 0, 114, 1, 108, 111, 17, 65, 0, 114, 1, 109, 109, 0, 114, 1, 109, 114, 0, 114, 1, 115, 107, 0, 114, 1, 115, 115, 0, 114, 1, 117, 0, 114, 100, 104, 101, 105, 100, 1, 21, 3, 6, 114, 34, 47, 105, 121, 47, 0, 108, 1, 117, 3, 6, 114, 55, 0, 3, 114, 0, 2, 117, 117, 3, 114, 10, 0, 110, 2, 17, 67, 106, 105, 101, 3, 114, 12, 37, 66, 0, 4, 114, 1, 102, 115, 3, 114, 34, 0, 114, 1, 104, 0, 114, 1, 107, 21, 0, 114, 1, 107, 115, 0, 114, 1, 108, 17, 65, 17, 65, 0, 114, 1, 108, 17, 67, 17, 65, 17, 65, 0, 114, 1, 108, 17, 67, 21, 0, 114, 1, 108, 101, 103, 0, 114, 1, 108, 103, 0, 114, 1, 108, 107, 0, 114, 1, 108, 110, 0, 114, 1, 108, 114, 0, 114, 1, 108, 115, 0, 114, 1, 109, 17, 67, 0, 114, 1, 112, 101, 0, 114, 1, 115, 17, 67, 0, 114, 1, 116, 110, 171, 195, 105, 114, 111, 0, 114, 1, 118, 17, 65, 17, 65, 0, 114, 1, 118, 17, 67, 0, 114, 1, 118, 101, 17, 67, 0, 114, 1, 119, 0, 114, 98, 105, 101, 100, 2, 17, 65, 3, 114, 34, 69, 6, 37, 70, 0, 4, 100, 106, 105, 101, 3, 114, 37, 78, 37, 0, 116, 106, 105, 101, 0, 117, 3, 117, 12, 0, 117, 101, 3, 117, 12, 13, 0, 7, 6, 101, 110, 0, 101, 109, 109, 101, 108, 3, 2, 37, 50, 110, 63, 13, 55, 0, 4, 1, 17, 67, 17, 65, 17, 67, 2, 115, 105, 101, 101, 17, 67, 3, 2, 106, 50, 0, 1, 17, 67, 17, 65, 17, 67, 2, 115, 105, 195, 171, 17, 67, 0, 8, 2, 116, 111, 112, 116, 105, 101, 0, 101, 114, 2, 103, 105, 3, 2, 106, 50, 13, 34, 0, 116, 111, 101, 115, 105, 97, 3, 2, 106, 50, 47, 2, 40, 87, 2, 37, 35, 0, 107, 101, 108, 2, 118, 111, 117, 100, 105, 3, 2, 106, 50, 49, 13, 55, 0, 115, 105, 107, 108, 111, 112, 101, 3, 2, 106, 50, 87, 2, 37, 49, 55, 2, 40, 48, 13, 0, 105, 103, 8, 2, 109, 97, 3, 2, 106, 50, 107, 134, 0, 111, 114, 109, 8, 2, 17, 65, 3, 2, 114, 50, 108, 34, 63, 0, 116, 114, 101, 112, 114, 101, 2, 110, 101, 3, 2, 131, 50, 47, 34, 13, 48, 34, 13, 0, 4, 116, 1, 17, 67, 21, 2, 25, 3, 6, 106, 50, 47, 0, 116, 1, 17, 67, 21, 2, 101, 32, 0, 115, 105, 101, 1, 17, 67, 2, 25, 3, 6, 106, 50, 87, 37, 0, 115, 105, 101, 115, 1, 17, 67, 3, 6, 106, 50, 87, 37, 87, 0, 105, 8, 2, 103, 3, 6, 114, 50, 13, 0, 8, 107, 2, 100, 104, 3, 8, 106, 50, 0, 4, 115, 105, 101, 109, 2, 32, 3, 10, 2, 106, 50, 87, 37, 63, 0, 115, 105, 101, 109, 2, 101, 32, 0, 115, 101, 109, 98, 108, 101, 3, 10, 2, 131, 50, 87, 131, 63, 69, 112, 0, 4, 1, 10, 2, 17, 67, 32, 3, 13, 50, 0, 1, 10, 2, 32, 0, 1, 10, 2, 100, 101, 17, 67, 32, 0, 1, 10, 2, 100, 101, 32, 0, 1, 17, 67, 10, 2, 98, 17, 65, 114, 103, 0, 1, 100, 114, 111, 111, 98, 2, 115, 0, 1, 102, 21, 2, 105, 115, 0, 1, 103, 110, 2, 100, 0, 1, 105, 111, 111, 2, 115, 0, 1, 107, 17, 67, 97, 118, 2, 17, 67, 0, 1, 107, 21, 2, 115, 107, 97, 112, 0, 1, 109, 2, 105, 115, 0, 105, 101, 114, 1, 17, 67, 3, 13, 50, 6, 37, 12, 34, 0, 121, 1, 17, 67, 21, 2, 32, 3, 13, 50, 6, 121, 0, 4, 101, 1, 107, 10, 2, 32, 3, 13, 50, 13, 0, 101, 1, 115, 10, 2, 32, 0, 4, 115, 1, 108, 17, 65, 17, 65, 2, 32, 3, 13, 50, 87, 0, 115, 1, 108, 101, 118, 2, 32, 0, 115, 1, 108, 108, 117, 118, 2, 32, 0, 115, 1, 112, 112, 111, 17, 67, 0, 115, 119, 97, 97, 114, 1, 21, 2, 100, 105, 103, 3, 13, 50, 87, 82, 6, 113, 34, 0, 104, 101, 105, 100, 1, 17, 67, 3, 13, 50, 105, 121, 47, 0, 97, 97, 114, 1, 17, 67, 3, 13, 50, 113, 34, 0, 97, 114, 101, 1, 17, 67, 2, 32, 3, 13, 50, 113, 34, 13, 0, 99, 101, 2, 25, 12, 3, 21, 0, 116, 106, 105, 101, 1, 107, 10, 3, 37, 66, 78, 37, 0, 116, 106, 105, 101, 1, 114, 112, 3, 106, 12, 37, 66, 49, 2, 37, 0, 115, 1, 108, 2, 32, 3, 106, 12, 50, 87, 0, 115, 101, 1, 108, 2, 32, 3, 106, 12, 50, 87, 13, 0, 116, 106, 105, 101, 2, 12, 3, 106, 37, 66, 78, 37, 0, 4, 1, 107, 115, 2, 100, 3, 106, 50, 0, 1, 112, 17, 67, 21, 2, 32, 0, 1, 112, 105, 101, 114, 98, 0, 1, 116, 111, 112, 2, 17, 67, 0, 110, 1, 112, 17, 67, 21, 2, 101, 0, 4, 116, 1, 110, 101, 2, 12, 12, 3, 106, 50, 47, 0, 116, 1, 114, 112, 2, 12, 12, 0, 116, 1, 115, 21, 2, 114, 17, 65, 0, 106, 105, 110, 3, 106, 50, 57, 13, 50, 0, 100, 101, 108, 2, 32, 3, 106, 50, 70, 13, 55, 0, 115, 1, 112, 17, 67, 2, 12, 3, 106, 50, 87, 0, 115, 101, 1, 112, 17, 67, 2, 108, 101, 32, 3, 106, 50, 87, 114, 0, 4, 1, 10, 2, 107, 32, 3, 106, 66, 0, 103, 1, 10, 2, 32, 0, 103, 101, 2, 108, 3, 106, 66, 13, 0, 107, 101, 108, 8, 3, 106, 66, 49, 13, 55, 0, 111, 114, 109, 8, 3, 114, 50, 6, 108, 34, 13, 10, 63, 0, 101, 1, 107, 115, 2, 32, 3, 114, 50, 13, 0, 101, 114, 115, 3, 114, 50, 13, 34, 87, 0, 4, 115, 1, 109, 2, 12, 12, 3, 132, 50, 87, 0, 115, 1, 114, 103, 0, 115, 1, 119, 0, 115, 105, 101, 1, 109, 2, 25, 3, 132, 50, 87, 2, 37, 0, 7, 6, 103, 101, 0, 103, 101, 101, 1, 21, 3, 8, 134, 13, 134, 114, 0, 1, 17, 67, 2, 32, 3, 79, 13, 0, 114, 1, 114, 117, 98, 3, 79, 13, 34, 0, 110, 114, 101, 3, 88, 6, 131, 50, 34, 13, 0, 110, 105, 101, 2, 32, 3, 88, 13, 50, 37, 12, 0, 111, 8, 2, 115, 3, 134, 2, 37, 2, 40, 0, 114, 8, 2, 109, 97, 3, 134, 2, 110, 34, 0, 114, 117, 2, 98, 121, 110, 3, 134, 2, 114, 34, 2, 109, 0, 110, 101, 2, 97, 108, 111, 3, 134, 2, 114, 50, 2, 37, 0, 101, 115, 2, 100, 114, 105, 102, 116, 105, 3, 134, 2, 114, 87, 0, 109, 109, 101, 114, 3, 134, 6, 106, 63, 13, 34, 0, 1, 105, 110, 2, 114, 105, 3, 134, 6, 114, 0, 119, 101, 2, 32, 3, 134, 6, 114, 82, 13, 0, 4, 119, 101, 110, 100, 1, 21, 2, 32, 3, 134, 6, 114, 82, 13, 50, 47, 0, 119, 101, 110, 100, 1, 21, 2, 115, 116, 101, 0, 119, 101, 110, 100, 101, 1, 21, 2, 32, 3, 134, 6, 114, 82, 13, 50, 70, 13, 0, 115, 101, 2, 32, 3, 134, 6, 114, 87, 13, 0, 4, 3, 134, 13, 0, 8, 2, 21, 14, 128, 132, 130, 0, 8, 2, 111, 115, 115, 14, 128, 132, 130, 0, 107, 108, 101, 100, 101, 3, 134, 13, 49, 55, 114, 70, 13, 0, 110, 101, 2, 114, 17, 65, 3, 134, 13, 50, 13, 0, 110, 97, 100, 2, 101, 116, 106, 105, 101, 3, 134, 13, 50, 113, 70, 0, 110, 97, 100, 101, 3, 134, 13, 50, 113, 70, 13, 0, 110, 101, 2, 114, 105, 101, 25, 3, 134, 13, 50, 114, 0, 108, 121, 107, 101, 110, 105, 8, 2, 115, 3, 134, 13, 55, 6, 121, 49, 13, 50, 13, 0, 109, 101, 108, 2, 100, 3, 134, 13, 63, 110, 55, 0, 98, 101, 100, 101, 8, 3, 134, 13, 69, 114, 70, 13, 0, 118, 101, 115, 2, 32, 3, 134, 13, 81, 106, 87, 0, 119, 101, 108, 2, 119, 3, 134, 13, 82, 6, 110, 55, 0, 4, 119, 101, 108, 2, 100, 3, 134, 13, 82, 110, 55, 0, 119, 101, 108, 2, 102, 0, 119, 101, 101, 114, 3, 134, 13, 82, 114, 34, 0, 119, 101, 110, 115, 1, 17, 67, 21, 3, 134, 13, 82, 132, 50, 87, 0, 115, 101, 108, 2, 32, 3, 134, 13, 87, 110, 55, 0, 115, 101, 108, 108, 101, 2, 32, 3, 134, 13, 87, 110, 55, 13, 0, 115, 101, 108, 115, 3, 134, 13, 87, 110, 55, 87, 0, 103, 101, 119, 101, 110, 115, 3, 134, 13, 134, 114, 82, 13, 50, 87, 0, 4, 1, 17, 65, 2, 116, 106, 105, 101, 3, 134, 37, 0, 2, 111, 103, 114, 97, 0, 2, 111, 108, 111, 0, 2, 111, 109, 101, 0, 110, 115, 8, 2, 17, 67, 3, 134, 106, 12, 50, 87, 0, 109, 115, 3, 134, 106, 63, 87, 0, 115, 112, 101, 2, 32, 3, 134, 106, 87, 48, 13, 0, 115, 112, 101, 115, 2, 32, 3, 134, 106, 87, 48, 13, 87, 0, 4, 2, 107, 32, 3, 134, 110, 0, 2, 107, 103, 0, 2, 107, 104, 0, 2, 107, 107, 0, 2, 107, 115, 107, 101, 101, 114, 0, 2, 107, 116, 0, 8, 2, 114, 17, 67, 0, 114, 102, 1, 17, 67, 3, 134, 110, 34, 81, 0, 114, 119, 101, 1, 17, 67, 2, 32, 3, 134, 110, 34, 82, 13, 0, 107, 119, 2, 111, 114, 100, 3, 134, 110, 49, 82, 0, 108, 100, 3, 134, 110, 55, 47, 0, 108, 100, 2, 105, 110, 17, 67, 3, 134, 110, 55, 47, 10, 0, 108, 100, 2, 105, 110, 103, 3, 134, 110, 55, 70, 0, 4, 108, 100, 101, 2, 25, 3, 134, 110, 55, 70, 13, 0, 108, 100, 105, 0, 108, 100, 106, 105, 101, 3, 134, 110, 55, 78, 37, 0, 4, 1, 107, 114, 101, 119, 2, 119, 101, 114, 3, 134, 114, 0, 101, 2, 12, 0, 195, 171, 114, 2, 32, 3, 134, 114, 13, 34, 0, 110, 101, 2, 32, 3, 134, 114, 50, 13, 0, 110, 105, 116, 2, 105, 101, 17, 67, 3, 134, 114, 50, 13, 47, 0, 110, 117, 115, 3, 134, 114, 50, 109, 87, 0, 108, 101, 1, 25, 2, 32, 3, 134, 114, 55, 13, 0, 108, 101, 114, 8, 3, 134, 114, 55, 13, 34, 0, 4, 119, 101, 114, 1, 103, 97, 108, 115, 3, 134, 114, 82, 13, 34, 0, 119, 101, 114, 1, 116, 101, 119, 0, 119, 101, 114, 2, 32, 0, 119, 101, 114, 115, 2, 32, 3, 134, 114, 82, 13, 34, 87, 0, 119, 101, 110, 115, 2, 103, 3, 134, 114, 82, 13, 50, 87, 0, 119, 101, 108, 3, 134, 114, 82, 13, 55, 0, 119, 105, 110, 103, 3, 134, 114, 82, 13, 66, 0, 105, 2, 12, 3, 134, 121, 0, 117, 2, 17, 67, 3, 134, 126, 0, 7, 6, 104, 101, 0, 2, 98, 114, 101, 3, 105, 2, 37, 0, 116, 101, 114, 111, 2, 21, 21, 14, 128, 132, 134, 3, 105, 2, 106, 47, 14, 34, 2, 40, 0, 107, 8, 2, 116, 97, 3, 105, 2, 106, 49, 0, 114, 8, 2, 21, 14, 128, 132, 131, 3, 105, 2, 110, 34, 0, 114, 97, 108, 2, 100, 105, 101, 107, 3, 105, 2, 110, 34, 2, 35, 55, 0, 114, 2, 101, 110, 105, 3, 105, 2, 110, 34, 19, 0, 114, 97, 108, 2, 100, 3, 105, 2, 110, 34, 35, 55, 0, 114, 116, 111, 103, 2, 105, 110, 3, 105, 2, 110, 34, 47, 2, 108, 134, 0, 114, 109, 97, 102, 114, 111, 2, 100, 105, 3, 105, 2, 110, 34, 63, 2, 35, 81, 34, 2, 40, 0, 114, 109, 101, 2, 108, 121, 110, 3, 105, 2, 110, 34, 63, 13, 0, 114, 98, 101, 114, 103, 2, 105, 3, 105, 2, 110, 34, 69, 2, 110, 34, 134, 0, 114, 98, 101, 114, 103, 2, 115, 97, 21, 3, 105, 2, 110, 34, 69, 110, 34, 134, 0, 114, 105, 110, 110, 101, 114, 3, 105, 2, 110, 34, 107, 50, 13, 34, 0, 108, 2, 100, 105, 110, 3, 105, 2, 110, 55, 0, 108, 105, 2, 107, 111, 112, 3, 105, 2, 110, 55, 2, 37, 0, 108, 100, 2, 104, 97, 102, 116, 3, 105, 2, 110, 55, 47, 0, 2, 114, 111, 195, 175, 101, 3, 105, 2, 114, 0, 114, 111, 2, 195, 175, 101, 110, 3, 105, 2, 114, 34, 2, 40, 58, 0, 101, 116, 2, 104, 111, 111, 102, 100, 105, 3, 105, 2, 114, 47, 0, 4, 114, 8, 2, 98, 101, 17, 67, 14, 128, 132, 131, 3, 105, 6, 110, 34, 0, 114, 8, 2, 118, 101, 114, 14, 128, 132, 131, 0, 114, 100, 101, 114, 3, 105, 6, 110, 34, 70, 13, 34, 0, 108, 100, 101, 8, 3, 105, 6, 110, 55, 70, 13, 0, 114, 8, 2, 119, 97, 97, 3, 105, 7, 110, 34, 0, 4, 114, 2, 101, 107, 115, 97, 109, 17, 65, 3, 105, 7, 110, 34, 10, 0, 114, 8, 2, 117, 105, 116, 0, 1, 21, 2, 110, 25, 3, 105, 106, 0, 120, 2, 17, 67, 3, 105, 106, 49, 87, 0, 107, 115, 101, 2, 17, 67, 3, 105, 106, 49, 87, 13, 0, 109, 2, 17, 67, 3, 105, 106, 63, 0, 4, 2, 103, 3, 105, 110, 0, 2, 114, 114, 105, 101, 0, 4, 114, 2, 98, 101, 114, 103, 3, 105, 110, 34, 0, 114, 2, 107, 111, 109, 115, 0, 114, 8, 2, 109, 97, 110, 25, 0, 114, 8, 114, 111, 111, 2, 17, 67, 0, 114, 2, 101, 118, 97, 3, 105, 110, 34, 19, 0, 114, 116, 122, 111, 103, 3, 105, 110, 34, 47, 87, 108, 134, 0, 114, 116, 111, 103, 3, 105, 110, 34, 47, 108, 134, 0, 114, 102, 115, 3, 105, 110, 34, 81, 87, 0, 114, 115, 101, 110, 3, 105, 110, 34, 87, 13, 50, 0, 108, 3, 105, 110, 55, 0, 2, 108, 105, 3, 105, 114, 0, 114, 2, 101, 25, 3, 105, 114, 34, 0, 4, 114, 101, 2, 114, 101, 103, 3, 105, 114, 34, 13, 0, 114, 101, 2, 119, 0, 114, 101, 8, 2, 108, 0, 101, 114, 101, 110, 2, 103, 114, 97, 99, 3, 105, 114, 34, 13, 50, 0, 101, 114, 115, 101, 114, 3, 105, 114, 34, 87, 13, 34, 0, 108, 101, 8, 2, 25, 3, 105, 114, 55, 13, 0, 109, 101, 108, 3, 105, 114, 63, 13, 55, 0, 100, 101, 1, 10, 2, 32, 3, 105, 114, 70, 13, 0, 105, 100, 2, 32, 14, 128, 128, 132, 3, 105, 121, 47, 0, 105, 100, 101, 2, 17, 67, 3, 105, 121, 70, 13, 0, 7, 6, 105, 110, 0, 4, 105, 115, 105, 2, 17, 65, 3, 2, 37, 50, 2, 37, 89, 2, 37, 0, 105, 115, 105, 2, 101, 17, 65, 0, 2, 102, 111, 114, 109, 101, 14, 128, 132, 130, 3, 6, 107, 50, 0, 8, 2, 97, 17, 67, 101, 109, 14, 128, 132, 130, 3, 6, 107, 50, 10, 0, 103, 8, 2, 21, 3, 6, 107, 50, 134, 0, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 6, 107, 50, 134, 13, 0, 4, 103, 101, 2, 119, 105, 110, 103, 3, 6, 107, 50, 134, 114, 0, 103, 101, 101, 8, 2, 12, 0, 8, 2, 115, 116, 117, 100, 101, 14, 128, 132, 130, 3, 7, 107, 50, 0, 8, 2, 101, 110, 116, 3, 7, 107, 50, 10, 0, 4, 1, 17, 67, 2, 97, 115, 101, 109, 3, 10, 13, 50, 0, 1, 102, 108, 101, 115, 2, 17, 67, 21, 0, 103, 97, 110, 103, 3, 10, 107, 50, 134, 35, 66, 0, 4, 1, 21, 2, 103, 114, 121, 112, 3, 13, 50, 0, 2, 100, 105, 101, 110, 0, 2, 100, 111, 101, 110, 97, 0, 2, 101, 101, 110, 0, 2, 102, 101, 107, 0, 2, 104, 97, 108, 105, 103, 0, 2, 104, 101, 101, 109, 115, 0, 2, 104, 101, 103, 116, 101, 110, 0, 2, 107, 101, 110, 110, 0, 2, 115, 107, 105, 107, 0, 2, 115, 107, 114, 105, 112, 0, 2, 115, 112, 101, 107, 0, 2, 115, 116, 97, 110, 0, 2, 116, 105, 101, 109, 0, 2, 119, 101, 114, 107, 105, 110, 103, 17, 67, 17, 67, 0, 8, 2, 101, 114, 17, 67, 0, 105, 115, 105, 101, 3, 13, 50, 6, 37, 87, 2, 37, 0, 116, 117, 195, 175, 3, 13, 50, 47, 2, 40, 12, 37, 0, 116, 101, 2, 103, 114, 101, 3, 13, 50, 47, 13, 0, 4, 116, 101, 114, 2, 110, 97, 115, 105, 111, 3, 13, 50, 47, 13, 34, 0, 116, 101, 114, 2, 110, 101, 114, 105, 110, 0, 116, 101, 114, 2, 110, 105, 25, 0, 116, 105, 109, 105, 2, 100, 17, 65, 3, 13, 50, 47, 13, 63, 13, 0, 116, 114, 105, 103, 2, 101, 21, 3, 13, 50, 47, 34, 2, 37, 134, 0, 116, 114, 111, 8, 2, 17, 67, 3, 13, 50, 47, 34, 2, 40, 0, 116, 114, 105, 103, 101, 3, 13, 50, 47, 34, 37, 134, 13, 0, 116, 101, 103, 2, 114, 105, 3, 13, 50, 47, 110, 134, 0, 100, 105, 2, 97, 21, 3, 13, 50, 70, 2, 37, 0, 100, 111, 110, 101, 2, 115, 105, 3, 13, 50, 70, 2, 40, 50, 37, 12, 0, 100, 101, 114, 8, 2, 17, 67, 3, 13, 50, 70, 13, 34, 0, 4, 100, 105, 118, 105, 3, 13, 50, 70, 13, 82, 13, 0, 100, 105, 119, 105, 0, 100, 105, 115, 2, 107, 114, 3, 13, 50, 70, 13, 87, 0, 102, 97, 110, 2, 116, 105, 3, 13, 50, 81, 2, 35, 50, 0, 102, 111, 114, 2, 109, 97, 3, 13, 50, 81, 2, 108, 34, 0, 118, 97, 108, 105, 100, 101, 3, 13, 50, 82, 2, 35, 55, 37, 70, 13, 0, 118, 101, 115, 116, 2, 101, 101, 114, 3, 13, 50, 82, 2, 106, 87, 47, 0, 118, 101, 115, 116, 101, 2, 114, 21, 3, 13, 50, 82, 2, 106, 87, 47, 114, 0, 115, 105, 2, 100, 101, 110, 116, 3, 13, 50, 87, 13, 0, 115, 101, 107, 2, 117, 3, 13, 50, 87, 13, 49, 0, 115, 116, 105, 2, 116, 117, 3, 13, 50, 87, 47, 13, 0, 115, 116, 114, 117, 107, 116, 3, 13, 50, 87, 47, 34, 2, 109, 49, 47, 0, 115, 116, 114, 117, 107, 115, 3, 13, 50, 87, 47, 34, 6, 109, 49, 87, 0, 110, 101, 109, 101, 110, 3, 13, 50, 114, 63, 13, 50, 0, 110, 117, 101, 110, 100, 111, 3, 13, 50, 116, 12, 6, 106, 50, 70, 118, 0, 103, 114, 121, 112, 101, 110, 3, 13, 50, 134, 34, 121, 48, 13, 50, 0, 103, 1, 10, 2, 32, 3, 13, 66, 0, 103, 101, 1, 17, 67, 21, 2, 32, 3, 13, 66, 13, 0, 4, 100, 106, 105, 101, 3, 107, 37, 66, 78, 37, 0, 116, 106, 105, 101, 0, 8, 2, 97, 21, 14, 128, 132, 130, 3, 107, 50, 0, 8, 2, 111, 101, 3, 107, 50, 10, 0, 98, 101, 8, 2, 108, 17, 67, 3, 107, 50, 69, 2, 110, 0, 100, 119, 105, 110, 103, 3, 107, 50, 70, 58, 13, 66, 0, 100, 101, 108, 8, 2, 17, 67, 3, 107, 50, 70, 110, 55, 0, 115, 101, 107, 2, 17, 65, 3, 107, 50, 87, 106, 49, 10, 0, 103, 2, 115, 3, 107, 66, 0, 7, 6, 107, 97, 0, 116, 97, 8, 3, 4, 49, 35, 47, 35, 0, 4, 1, 21, 2, 110, 111, 110, 3, 49, 2, 35, 0, 2, 106, 97, 107, 0, 2, 109, 97, 115, 0, 2, 110, 97, 108, 101, 0, 2, 112, 97, 17, 67, 101, 17, 67, 0, 2, 114, 111, 115, 0, 2, 115, 97, 114, 109, 0, 2, 115, 116, 114, 111, 108, 0, 2, 115, 116, 121, 0, 2, 116, 97, 114, 115, 105, 0, 8, 2, 100, 21, 0, 8, 2, 108, 17, 65, 110, 17, 67, 0, 8, 2, 114, 105, 101, 110, 0, 8, 2, 115, 116, 97, 0, 8, 2, 115, 116, 101, 21, 0, 8, 2, 116, 111, 0, 8, 2, 116, 114, 0, 4, 114, 2, 100, 111, 101, 115, 3, 49, 2, 35, 34, 0, 114, 2, 110, 117, 102, 102, 101, 108, 0, 114, 2, 116, 111, 110, 0, 114, 2, 119, 97, 116, 115, 0, 114, 2, 119, 101, 105, 0, 114, 2, 119, 121, 0, 114, 8, 2, 98, 0, 114, 8, 2, 118, 101, 0, 4, 114, 97, 2, 98, 121, 110, 3, 49, 2, 35, 34, 2, 35, 0, 114, 97, 2, 107, 111, 101, 108, 0, 114, 97, 109, 101, 108, 3, 49, 2, 35, 34, 2, 35, 63, 110, 55, 0, 114, 105, 107, 97, 2, 116, 117, 3, 49, 2, 35, 34, 2, 37, 49, 2, 35, 0, 114, 97, 2, 118, 97, 3, 49, 2, 35, 34, 13, 0, 114, 116, 101, 116, 115, 3, 49, 2, 35, 34, 47, 106, 47, 87, 0, 114, 110, 97, 2, 118, 97, 108, 3, 49, 2, 35, 34, 50, 2, 35, 0, 114, 109, 111, 115, 121, 110, 3, 49, 2, 35, 34, 63, 2, 40, 87, 121, 50, 0, 114, 109, 101, 2, 110, 97, 97, 100, 106, 3, 49, 2, 35, 34, 63, 13, 0, 114, 97, 116, 101, 3, 49, 2, 35, 34, 113, 47, 2, 37, 0, 4, 116, 101, 2, 100, 114, 3, 49, 2, 35, 47, 13, 0, 116, 101, 2, 103, 17, 65, 0, 116, 97, 108, 111, 2, 103, 17, 65, 3, 49, 2, 35, 47, 35, 55, 2, 40, 0, 116, 107, 105, 2, 115, 17, 65, 3, 49, 2, 35, 47, 49, 13, 0, 112, 2, 116, 101, 105, 110, 3, 49, 2, 35, 48, 0, 112, 97, 2, 115, 105, 116, 101, 105, 116, 3, 49, 2, 35, 48, 2, 35, 0, 112, 105, 2, 116, 97, 3, 49, 2, 35, 48, 2, 37, 0, 112, 101, 2, 108, 97, 21, 3, 49, 2, 35, 48, 13, 0, 112, 101, 114, 2, 106, 111, 108, 3, 49, 2, 35, 48, 13, 34, 0, 112, 115, 117, 108, 101, 3, 49, 2, 35, 48, 87, 116, 55, 13, 0, 112, 111, 8, 2, 17, 67, 3, 49, 2, 35, 48, 108, 0, 112, 101, 2, 108, 3, 49, 2, 35, 48, 110, 0, 4, 110, 2, 116, 105, 101, 110, 3, 49, 2, 35, 50, 0, 110, 8, 2, 116, 111, 21, 0, 4, 110, 100, 105, 2, 100, 17, 65, 3, 49, 2, 35, 50, 2, 37, 0, 110, 110, 105, 2, 98, 97, 0, 110, 115, 101, 2, 108, 108, 101, 3, 49, 2, 35, 50, 87, 13, 0, 4, 110, 111, 2, 32, 3, 49, 2, 35, 50, 115, 0, 110, 111, 8, 2, 118, 97, 97, 114, 0, 4, 108, 2, 98, 97, 115, 3, 49, 2, 35, 55, 0, 108, 2, 107, 111, 101, 110, 0, 108, 105, 2, 98, 3, 49, 2, 35, 55, 37, 0, 108, 101, 110, 100, 101, 114, 3, 49, 2, 35, 55, 106, 50, 70, 13, 34, 0, 109, 111, 101, 2, 102, 108, 3, 49, 2, 35, 63, 2, 40, 0, 109, 111, 101, 102, 108, 97, 103, 101, 3, 49, 2, 35, 63, 2, 40, 81, 55, 113, 88, 0, 109, 101, 114, 97, 100, 101, 3, 49, 2, 35, 63, 13, 34, 113, 70, 13, 0, 98, 97, 114, 101, 2, 116, 3, 49, 2, 35, 69, 2, 35, 34, 106, 0, 98, 105, 110, 101, 2, 116, 3, 49, 2, 35, 69, 2, 37, 50, 106, 0, 102, 101, 2, 195, 175, 3, 49, 2, 35, 81, 2, 37, 0, 102, 101, 2, 116, 101, 3, 49, 2, 35, 81, 13, 0, 115, 116, 97, 2, 110, 106, 101, 116, 3, 49, 2, 35, 87, 47, 2, 35, 0, 115, 107, 101, 2, 110, 97, 100, 101, 3, 49, 2, 35, 87, 49, 13, 0, 115, 115, 101, 2, 116, 3, 49, 2, 35, 87, 106, 0, 115, 101, 114, 110, 101, 3, 49, 2, 35, 87, 110, 34, 50, 13, 0, 116, 106, 105, 101, 2, 112, 105, 101, 3, 49, 2, 119, 78, 2, 37, 0, 110, 102, 101, 114, 2, 102, 111, 101, 108, 3, 49, 2, 131, 50, 81, 13, 34, 0, 116, 101, 103, 111, 114, 105, 101, 115, 3, 49, 4, 35, 47, 13, 134, 6, 115, 34, 37, 87, 0, 116, 101, 103, 111, 114, 105, 101, 3, 49, 4, 35, 47, 13, 134, 40, 34, 6, 37, 0, 97, 1, 17, 65, 21, 2, 116, 3, 49, 6, 113, 0, 116, 101, 1, 21, 2, 32, 3, 49, 6, 113, 47, 13, 0, 110, 101, 114, 1, 17, 65, 21, 2, 32, 3, 49, 6, 113, 50, 13, 34, 0, 4, 114, 2, 98, 101, 3, 49, 35, 34, 0, 114, 2, 118, 101, 110, 0, 114, 2, 118, 101, 114, 0, 116, 101, 103, 111, 114, 2, 105, 115, 17, 65, 3, 49, 35, 47, 13, 134, 40, 34, 0, 110, 116, 2, 111, 110, 100, 101, 114, 3, 49, 35, 50, 47, 10, 0, 110, 115, 101, 2, 108, 25, 3, 49, 35, 50, 87, 13, 0, 108, 97, 104, 97, 114, 105, 3, 49, 35, 55, 35, 105, 6, 113, 34, 37, 0, 4, 108, 109, 101, 101, 114, 3, 49, 35, 55, 63, 6, 114, 34, 0, 108, 109, 101, 114, 2, 17, 65, 0, 108, 119, 101, 114, 3, 49, 35, 55, 82, 13, 34, 10, 0, 109, 101, 114, 2, 97, 116, 106, 105, 101, 3, 49, 35, 63, 13, 34, 0, 109, 101, 114, 97, 97, 3, 49, 35, 63, 13, 34, 6, 113, 0, 109, 101, 114, 97, 3, 49, 35, 63, 13, 34, 35, 0, 98, 101, 108, 106, 111, 117, 3, 49, 35, 69, 13, 55, 57, 6, 118, 0, 100, 2, 109, 105, 117, 109, 3, 49, 35, 70, 0, 115, 116, 101, 114, 2, 111, 108, 105, 101, 3, 49, 35, 87, 47, 13, 34, 10, 0, 2, 100, 101, 114, 3, 49, 113, 0, 116, 101, 108, 1, 25, 3, 49, 113, 47, 13, 55, 0, 107, 101, 2, 17, 67, 3, 49, 113, 49, 13, 0, 4, 109, 101, 114, 3, 49, 113, 63, 13, 34, 0, 109, 101, 114, 2, 17, 67, 0, 98, 101, 108, 3, 49, 113, 69, 13, 55, 0, 110, 102, 101, 114, 3, 49, 131, 50, 81, 13, 34, 10, 0, 7, 6, 107, 111, 0, 4, 2, 107, 101, 116, 25, 3, 49, 2, 40, 0, 2, 107, 111, 110, 0, 2, 108, 111, 109, 0, 2, 108, 111, 110, 105, 0, 2, 109, 101, 100, 105, 0, 2, 109, 101, 116, 101, 0, 2, 114, 97, 0, 2, 114, 105, 110, 116, 0, 2, 114, 114, 117, 112, 0, 2, 195, 182, 0, 8, 2, 109, 105, 101, 107, 0, 8, 2, 109, 109, 111, 0, 8, 2, 112, 105, 101, 21, 0, 101, 2, 106, 97, 119, 101, 108, 0, 101, 2, 112, 108, 101, 116, 0, 101, 2, 112, 111, 110, 0, 101, 2, 114, 17, 65, 0, 114, 114, 101, 107, 3, 49, 2, 40, 34, 106, 49, 0, 114, 101, 110, 2, 116, 3, 49, 2, 40, 34, 106, 50, 0, 117, 107, 97, 2, 115, 105, 195, 171, 3, 49, 2, 40, 49, 113, 0, 110, 110, 101, 107, 3, 49, 2, 40, 50, 106, 49, 0, 101, 108, 2, 98, 108, 111, 101, 3, 49, 2, 40, 55, 0, 108, 108, 101, 2, 107, 116, 17, 65, 3, 49, 2, 40, 55, 2, 106, 0, 108, 108, 101, 2, 107, 116, 101, 25, 3, 49, 2, 40, 55, 106, 0, 108, 108, 101, 107, 2, 115, 3, 49, 2, 40, 55, 106, 49, 0, 108, 111, 2, 115, 25, 3, 49, 2, 40, 55, 108, 0, 108, 111, 110, 110, 101, 3, 49, 2, 40, 55, 108, 50, 13, 0, 108, 108, 101, 103, 97, 3, 49, 2, 40, 55, 114, 134, 2, 35, 0, 109, 101, 100, 105, 2, 97, 110, 116, 3, 49, 2, 40, 63, 2, 37, 70, 2, 37, 0, 109, 109, 97, 110, 100, 111, 3, 49, 2, 40, 63, 35, 50, 70, 40, 0, 109, 109, 105, 115, 115, 105, 101, 3, 49, 2, 40, 63, 37, 87, 2, 37, 0, 109, 97, 116, 105, 2, 25, 3, 49, 2, 40, 63, 113, 47, 2, 37, 0, 101, 118, 101, 114, 2, 116, 3, 49, 2, 40, 81, 110, 34, 0, 4, 114, 2, 115, 101, 116, 3, 49, 2, 108, 34, 0, 114, 8, 2, 100, 17, 65, 0, 114, 114, 101, 107, 116, 105, 101, 119, 101, 3, 49, 2, 108, 34, 2, 106, 49, 47, 37, 82, 13, 0, 114, 114, 105, 103, 2, 101, 3, 49, 2, 108, 34, 13, 134, 0, 4, 114, 116, 2, 115, 105, 103, 116, 105, 103, 3, 49, 2, 108, 34, 47, 0, 114, 116, 2, 115, 116, 111, 110, 100, 0, 114, 112, 111, 2, 114, 97, 97, 108, 3, 49, 2, 108, 34, 48, 13, 0, 112, 117, 2, 108, 17, 65, 3, 49, 2, 108, 48, 2, 116, 0, 107, 107, 101, 8, 2, 17, 67, 3, 49, 2, 108, 49, 13, 0, 110, 8, 2, 17, 67, 21, 14, 128, 132, 131, 3, 49, 2, 108, 50, 0, 110, 116, 114, 97, 2, 100, 105, 107, 115, 3, 49, 2, 108, 50, 47, 34, 2, 35, 0, 110, 116, 114, 97, 115, 101, 112, 3, 49, 2, 108, 50, 47, 34, 2, 35, 87, 106, 48, 0, 110, 116, 114, 111, 118, 101, 114, 2, 115, 3, 49, 2, 108, 50, 47, 34, 2, 40, 82, 110, 34, 0, 110, 116, 114, 97, 112, 2, 115, 105, 101, 3, 49, 2, 108, 50, 47, 34, 35, 48, 0, 110, 116, 114, 97, 107, 8, 3, 49, 2, 108, 50, 47, 34, 35, 49, 0, 110, 116, 114, 97, 115, 8, 3, 49, 2, 108, 50, 47, 34, 35, 87, 0, 110, 116, 97, 107, 2, 17, 65, 3, 49, 2, 108, 50, 47, 35, 49, 10, 0, 110, 100, 101, 110, 2, 115, 101, 3, 49, 2, 108, 50, 70, 2, 106, 50, 0, 110, 102, 101, 114, 2, 101, 3, 49, 2, 108, 50, 81, 13, 34, 0, 110, 102, 101, 114, 101, 110, 3, 49, 2, 108, 50, 81, 13, 34, 106, 50, 0, 4, 110, 115, 117, 108, 2, 17, 65, 3, 49, 2, 108, 50, 87, 2, 109, 55, 0, 110, 115, 117, 108, 2, 116, 97, 110, 116, 0, 110, 115, 101, 110, 2, 116, 114, 105, 101, 3, 49, 2, 108, 50, 87, 7, 106, 50, 0, 110, 115, 101, 2, 107, 119, 101, 110, 3, 49, 2, 108, 50, 87, 13, 0, 110, 115, 101, 114, 116, 105, 110, 97, 3, 49, 2, 108, 50, 87, 13, 34, 47, 37, 50, 2, 35, 0, 110, 115, 101, 114, 118, 3, 49, 2, 108, 50, 87, 13, 34, 82, 0, 110, 115, 101, 110, 2, 116, 114, 3, 49, 2, 108, 50, 87, 13, 50, 0, 110, 115, 105, 100, 101, 2, 114, 17, 65, 3, 49, 2, 108, 50, 87, 13, 70, 13, 0, 110, 115, 105, 115, 116, 3, 49, 2, 108, 50, 87, 13, 87, 47, 0, 110, 115, 116, 105, 2, 116, 117, 115, 105, 3, 49, 2, 108, 50, 87, 47, 13, 0, 110, 115, 116, 97, 98, 101, 108, 3, 49, 2, 108, 50, 87, 47, 113, 69, 13, 55, 0, 110, 115, 101, 112, 2, 17, 65, 3, 49, 2, 108, 50, 87, 106, 48, 10, 0, 4, 108, 2, 106, 97, 110, 3, 49, 2, 108, 55, 0, 108, 2, 119, 121, 110, 0, 4, 109, 2, 112, 108, 17, 65, 3, 49, 2, 108, 63, 0, 109, 2, 112, 111, 115, 105, 115, 105, 101, 0, 109, 109, 97, 110, 2, 100, 17, 65, 3, 49, 2, 108, 63, 2, 35, 50, 0, 109, 109, 101, 114, 2, 115, 105, 3, 49, 2, 108, 63, 2, 110, 34, 0, 109, 109, 117, 2, 110, 97, 3, 49, 2, 108, 63, 2, 116, 0, 109, 105, 2, 116, 101, 101, 3, 49, 2, 108, 63, 13, 0, 109, 109, 101, 110, 2, 116, 97, 3, 49, 2, 108, 63, 13, 50, 0, 109, 109, 105, 115, 115, 97, 114, 105, 2, 97, 3, 49, 2, 108, 63, 13, 87, 2, 35, 34, 2, 37, 0, 109, 112, 97, 110, 2, 106, 105, 101, 3, 49, 2, 108, 63, 48, 2, 35, 50, 0, 109, 112, 114, 111, 2, 109, 105, 101, 3, 49, 2, 108, 63, 48, 34, 2, 40, 0, 109, 107, 111, 109, 109, 101, 114, 3, 49, 2, 108, 63, 49, 108, 63, 13, 34, 0, 109, 98, 101, 114, 115, 3, 49, 2, 108, 63, 69, 111, 34, 87, 0, 109, 98, 117, 105, 115, 3, 49, 2, 108, 63, 69, 125, 87, 0, 110, 103, 2, 111, 116, 111, 109, 105, 101, 3, 49, 2, 108, 66, 79, 0, 4, 115, 2, 109, 101, 116, 3, 49, 2, 108, 87, 0, 115, 2, 116, 117, 0, 115, 109, 111, 2, 112, 111, 108, 105, 3, 49, 2, 108, 87, 63, 2, 40, 0, 115, 109, 101, 2, 116, 105, 101, 107, 3, 49, 2, 108, 87, 63, 13, 0, 107, 97, 2, 195, 175, 3, 49, 2, 115, 49, 2, 35, 0, 110, 105, 110, 103, 2, 105, 110, 3, 49, 2, 115, 50, 13, 66, 0, 100, 101, 2, 114, 105, 110, 103, 3, 49, 2, 115, 70, 114, 0, 117, 2, 115, 97, 21, 3, 49, 2, 118, 0, 108, 111, 2, 115, 115, 97, 3, 49, 4, 108, 55, 40, 0, 110, 103, 111, 2, 25, 3, 49, 4, 108, 66, 79, 40, 0, 110, 8, 2, 100, 105, 103, 3, 49, 6, 108, 50, 0, 110, 116, 114, 97, 8, 2, 25, 14, 128, 132, 134, 3, 49, 6, 108, 50, 47, 34, 35, 0, 108, 108, 101, 103, 101, 115, 2, 32, 3, 49, 6, 108, 55, 37, 73, 13, 87, 0, 101, 2, 114, 101, 110, 100, 3, 49, 40, 0, 101, 195, 171, 108, 3, 49, 40, 12, 55, 0, 112, 2, 111, 3, 49, 108, 48, 19, 0, 110, 2, 115, 117, 108, 3, 49, 108, 50, 0, 110, 110, 101, 107, 116, 101, 101, 114, 3, 49, 108, 50, 106, 49, 47, 6, 114, 34, 0, 108, 111, 110, 101, 108, 3, 49, 108, 55, 13, 50, 6, 110, 55, 0, 108, 108, 101, 103, 101, 3, 49, 108, 55, 37, 73, 0, 110, 107, 101, 108, 3, 49, 108, 66, 49, 13, 55, 0, 110, 107, 97, 8, 2, 25, 3, 49, 108, 66, 49, 35, 0, 115, 2, 116, 101, 114, 109, 3, 49, 108, 87, 0, 115, 116, 101, 3, 49, 108, 87, 47, 13, 0, 98, 114, 97, 3, 49, 115, 69, 34, 35, 0, 7, 6, 109, 97, 0, 110, 117, 2, 115, 107, 3, 4, 63, 35, 50, 116, 0, 4, 2, 103, 105, 115, 116, 101, 114, 3, 63, 2, 35, 0, 2, 103, 114, 105, 101, 116, 0, 2, 104, 17, 65, 0, 2, 107, 97, 115, 115, 97, 114, 0, 2, 107, 105, 101, 116, 105, 101, 0, 2, 107, 114, 105, 101, 108, 0, 2, 116, 101, 115, 105, 115, 0, 2, 116, 114, 0, 8, 2, 100, 0, 8, 2, 114, 17, 65, 0, 2, 114, 105, 116, 122, 3, 63, 2, 35, 6, 0, 114, 2, 115, 106, 101, 3, 63, 2, 35, 34, 0, 114, 105, 111, 2, 110, 101, 116, 3, 63, 2, 35, 34, 2, 37, 2, 40, 0, 114, 105, 101, 1, 21, 2, 32, 3, 63, 2, 35, 34, 6, 37, 0, 114, 105, 2, 116, 105, 101, 109, 3, 63, 2, 35, 34, 13, 0, 114, 105, 110, 101, 2, 25, 3, 63, 2, 35, 34, 37, 50, 13, 0, 114, 109, 111, 2, 115, 101, 116, 3, 63, 2, 35, 34, 63, 2, 40, 0, 114, 109, 101, 108, 97, 100, 101, 3, 63, 2, 35, 34, 63, 13, 55, 113, 70, 13, 0, 114, 103, 97, 2, 114, 105, 3, 63, 2, 35, 34, 134, 2, 35, 0, 116, 101, 114, 105, 2, 17, 65, 21, 3, 63, 2, 35, 47, 2, 114, 34, 2, 37, 0, 116, 101, 2, 109, 97, 116, 105, 3, 63, 2, 35, 47, 13, 0, 116, 101, 114, 105, 101, 2, 12, 3, 63, 2, 35, 47, 114, 34, 2, 37, 0, 107, 97, 2, 112, 97, 97, 110, 3, 63, 2, 35, 49, 2, 35, 0, 99, 97, 100, 97, 109, 105, 97, 3, 63, 2, 35, 49, 2, 35, 70, 113, 63, 2, 37, 38, 2, 35, 0, 99, 104, 105, 97, 118, 101, 3, 63, 2, 35, 49, 2, 37, 2, 35, 82, 106, 0, 107, 115, 105, 2, 109, 97, 21, 3, 63, 2, 35, 49, 87, 2, 37, 0, 107, 97, 98, 101, 114, 3, 63, 2, 35, 49, 113, 69, 13, 34, 0, 4, 110, 2, 100, 97, 3, 63, 2, 35, 50, 0, 110, 2, 104, 97, 102, 116, 0, 110, 2, 109, 111, 101, 0, 110, 2, 115, 106, 101, 116, 0, 110, 105, 2, 107, 117, 3, 63, 2, 35, 50, 2, 37, 0, 110, 105, 112, 117, 3, 63, 2, 35, 50, 2, 37, 48, 2, 116, 0, 4, 110, 101, 2, 119, 97, 108, 101, 3, 63, 2, 35, 50, 13, 0, 110, 110, 101, 2, 107, 121, 110, 0, 110, 106, 105, 2, 102, 105, 101, 3, 63, 2, 35, 50, 57, 13, 0, 110, 100, 111, 2, 108, 105, 101, 110, 3, 63, 2, 35, 50, 70, 2, 40, 0, 110, 101, 2, 108, 3, 63, 2, 35, 50, 110, 0, 108, 2, 103, 97, 115, 3, 63, 2, 35, 55, 0, 108, 97, 2, 103, 105, 101, 116, 3, 63, 2, 35, 55, 2, 35, 0, 108, 116, 101, 8, 2, 115, 17, 65, 3, 63, 2, 35, 55, 47, 114, 0, 109, 2, 112, 111, 101, 114, 3, 63, 2, 35, 63, 0, 115, 111, 2, 99, 104, 105, 115, 3, 63, 2, 35, 87, 2, 40, 0, 99, 101, 100, 111, 2, 110, 17, 65, 3, 63, 2, 35, 87, 13, 70, 115, 0, 115, 116, 101, 107, 116, 111, 2, 109, 3, 63, 2, 35, 87, 47, 106, 49, 47, 2, 40, 0, 115, 107, 101, 114, 2, 97, 100, 101, 3, 63, 2, 35, 87, 49, 13, 34, 0, 115, 107, 97, 114, 97, 3, 63, 2, 35, 87, 49, 113, 34, 2, 35, 0, 115, 106, 105, 2, 110, 97, 21, 3, 63, 2, 35, 89, 2, 37, 0, 103, 2, 110, 17, 65, 21, 3, 63, 2, 35, 134, 0, 103, 97, 2, 115, 121, 110, 3, 63, 2, 35, 134, 2, 35, 0, 103, 105, 115, 2, 116, 114, 97, 3, 63, 2, 35, 134, 2, 37, 87, 0, 103, 97, 2, 108, 105, 101, 3, 63, 2, 35, 134, 35, 0, 110, 105, 97, 2, 107, 3, 63, 2, 113, 50, 2, 37, 38, 2, 35, 0, 106, 101, 115, 116, 117, 3, 63, 2, 113, 57, 13, 87, 47, 2, 116, 0, 106, 101, 115, 116, 101, 105, 116, 108, 105, 3, 63, 2, 113, 57, 13, 87, 47, 121, 47, 55, 13, 0, 100, 101, 2, 108, 105, 101, 3, 63, 2, 113, 70, 13, 0, 121, 111, 110, 110, 97, 105, 115, 101, 3, 63, 2, 121, 57, 2, 40, 50, 121, 12, 86, 0, 116, 105, 103, 1, 21, 3, 63, 6, 113, 47, 13, 134, 0, 116, 105, 101, 115, 3, 63, 6, 113, 47, 37, 87, 0, 110, 105, 101, 114, 3, 63, 13, 50, 37, 12, 34, 0, 115, 106, 105, 101, 110, 3, 63, 13, 89, 37, 50, 0, 114, 97, 116, 2, 111, 110, 3, 63, 35, 34, 2, 35, 47, 0, 114, 97, 116, 104, 111, 110, 3, 63, 35, 34, 2, 35, 47, 2, 108, 50, 10, 0, 114, 109, 101, 114, 3, 63, 35, 34, 63, 13, 34, 10, 0, 107, 105, 101, 1, 21, 2, 115, 105, 101, 3, 63, 35, 49, 6, 37, 0, 107, 114, 97, 110, 107, 97, 1, 21, 3, 63, 35, 49, 34, 6, 35, 50, 49, 35, 0, 110, 105, 102, 101, 115, 3, 63, 35, 50, 37, 81, 106, 87, 0, 108, 1, 10, 2, 32, 14, 128, 128, 131, 3, 63, 35, 55, 0, 108, 97, 114, 105, 97, 3, 63, 35, 55, 6, 113, 34, 37, 35, 0, 108, 108, 101, 115, 2, 32, 3, 63, 35, 55, 13, 87, 0, 108, 118, 97, 2, 25, 3, 63, 35, 55, 81, 2, 35, 0, 110, 103, 111, 8, 3, 63, 35, 66, 79, 2, 40, 0, 115, 107, 101, 114, 3, 63, 35, 87, 49, 13, 34, 0, 2, 116, 114, 105, 107, 25, 3, 63, 113, 0, 110, 105, 2, 97, 107, 25, 3, 63, 113, 50, 2, 37, 0, 2, 98, 105, 101, 107, 3, 87, 0, 7, 6, 109, 101, 0, 116, 101, 2, 111, 3, 63, 2, 37, 47, 2, 37, 0, 116, 101, 111, 2, 114, 105, 101, 116, 3, 63, 2, 37, 47, 2, 37, 2, 40, 0, 116, 97, 8, 2, 17, 67, 3, 63, 2, 106, 47, 2, 35, 0, 110, 2, 116, 97, 115, 105, 101, 3, 63, 2, 106, 50, 0, 110, 111, 112, 111, 117, 2, 115, 97, 3, 63, 2, 106, 50, 2, 40, 48, 2, 118, 0, 110, 117, 101, 2, 116, 3, 63, 2, 106, 50, 2, 116, 12, 38, 106, 0, 110, 116, 97, 108, 105, 2, 116, 101, 105, 116, 3, 63, 2, 106, 50, 47, 2, 35, 55, 2, 37, 0, 110, 115, 116, 114, 117, 3, 63, 2, 106, 50, 87, 47, 34, 2, 116, 0, 4, 108, 97, 110, 99, 104, 3, 63, 2, 106, 55, 2, 35, 66, 49, 0, 108, 97, 110, 107, 0, 4, 108, 97, 110, 99, 104, 111, 108, 105, 101, 2, 32, 24, 3, 63, 2, 106, 55, 2, 35, 66, 49, 2, 115, 55, 37, 0, 108, 97, 110, 107, 111, 108, 105, 101, 2, 32, 24, 0, 108, 111, 100, 105, 8, 2, 101, 117, 3, 63, 2, 106, 55, 2, 40, 70, 2, 37, 0, 109, 2, 98, 114, 97, 3, 63, 2, 106, 63, 0, 109, 111, 2, 114, 17, 65, 3, 63, 2, 106, 63, 2, 40, 0, 109, 111, 114, 97, 2, 98, 105, 108, 105, 3, 63, 2, 106, 63, 2, 108, 34, 2, 35, 0, 109, 111, 2, 114, 105, 17, 65, 3, 63, 2, 106, 63, 115, 0, 100, 105, 2, 116, 17, 65, 3, 63, 2, 106, 70, 2, 37, 0, 100, 105, 116, 101, 2, 114, 114, 101, 3, 63, 2, 106, 70, 2, 37, 47, 13, 0, 100, 105, 115, 105, 2, 110, 97, 21, 3, 63, 2, 106, 70, 13, 87, 2, 37, 0, 4, 101, 2, 100, 111, 195, 171, 3, 63, 2, 114, 0, 101, 2, 119, 97, 114, 0, 101, 114, 2, 118, 111, 117, 100, 105, 103, 3, 63, 2, 114, 34, 0, 101, 114, 100, 101, 114, 2, 106, 97, 114, 3, 63, 2, 114, 34, 70, 13, 34, 0, 4, 100, 101, 2, 100, 111, 195, 171, 3, 63, 2, 114, 70, 13, 0, 100, 101, 2, 112, 108, 105, 103, 0, 100, 101, 8, 2, 108, 121, 0, 101, 115, 116, 101, 114, 101, 3, 63, 2, 114, 87, 47, 13, 34, 106, 0, 110, 116, 106, 105, 101, 3, 63, 6, 106, 37, 66, 78, 37, 0, 110, 116, 3, 63, 6, 106, 50, 47, 0, 108, 111, 8, 2, 100, 114, 3, 63, 6, 106, 55, 40, 0, 110, 105, 110, 103, 3, 63, 6, 114, 50, 13, 66, 0, 100, 101, 8, 2, 21, 14, 128, 132, 132, 3, 63, 6, 114, 70, 13, 0, 101, 103, 101, 8, 2, 21, 14, 128, 132, 133, 3, 63, 6, 114, 134, 13, 0, 4, 2, 106, 117, 102, 3, 63, 13, 0, 2, 108, 97, 97, 116, 115, 0, 2, 114, 105, 101, 116, 101, 0, 2, 116, 111, 100, 0, 8, 2, 100, 117, 17, 67, 0, 114, 105, 110, 111, 3, 63, 13, 34, 37, 50, 2, 40, 0, 116, 97, 108, 101, 3, 63, 13, 47, 6, 113, 55, 13, 0, 116, 111, 100, 101, 3, 63, 13, 47, 6, 115, 70, 13, 0, 116, 97, 97, 2, 17, 67, 3, 63, 13, 47, 113, 0, 107, 97, 97, 114, 3, 63, 13, 49, 6, 113, 34, 0, 107, 97, 97, 114, 103, 101, 3, 63, 13, 49, 6, 113, 34, 134, 13, 0, 110, 101, 101, 114, 3, 63, 13, 50, 6, 114, 34, 0, 110, 101, 114, 101, 3, 63, 13, 50, 6, 114, 34, 13, 0, 108, 111, 100, 105, 101, 115, 8, 3, 63, 13, 55, 6, 115, 70, 37, 87, 0, 100, 97, 108, 2, 106, 111, 110, 3, 63, 13, 70, 2, 35, 55, 0, 100, 105, 115, 121, 110, 101, 3, 63, 13, 70, 13, 87, 121, 50, 13, 0, 100, 97, 108, 106, 101, 3, 63, 13, 70, 35, 55, 57, 13, 0, 118, 114, 111, 117, 3, 63, 13, 81, 34, 6, 118, 0, 103, 97, 110, 105, 101, 115, 3, 63, 13, 134, 6, 113, 50, 37, 87, 0, 2, 100, 105, 117, 109, 3, 63, 37, 12, 0, 100, 105, 97, 3, 63, 37, 12, 70, 37, 12, 57, 35, 4, 0, 2, 114, 114, 105, 101, 3, 63, 106, 0, 116, 101, 101, 110, 3, 63, 106, 47, 10, 6, 114, 50, 0, 116, 111, 100, 105, 115, 3, 63, 106, 47, 40, 70, 6, 107, 87, 0, 110, 105, 110, 103, 2, 105, 116, 105, 115, 3, 63, 106, 50, 13, 66, 134, 0, 110, 116, 101, 101, 2, 17, 67, 3, 63, 106, 50, 47, 6, 114, 0, 110, 116, 101, 114, 105, 110, 103, 3, 63, 106, 50, 47, 6, 114, 34, 13, 66, 0, 110, 116, 101, 108, 101, 2, 25, 3, 63, 106, 50, 47, 6, 114, 55, 13, 0, 108, 111, 100, 105, 101, 8, 3, 63, 106, 55, 40, 70, 6, 37, 0, 110, 103, 2, 115, 101, 108, 3, 63, 106, 66, 0, 4, 115, 1, 102, 101, 104, 2, 32, 3, 63, 106, 87, 0, 115, 1, 108, 101, 102, 97, 116, 2, 32, 0, 115, 1, 115, 17, 65, 17, 65, 2, 32, 0, 115, 1, 115, 17, 67, 2, 32, 0, 115, 1, 121, 110, 115, 2, 32, 0, 115, 8, 2, 97, 97, 110, 3, 63, 106, 87, 10, 0, 4, 114, 107, 1, 101, 116, 3, 63, 110, 34, 49, 0, 114, 107, 2, 32, 0, 114, 107, 101, 2, 32, 3, 63, 110, 34, 49, 13, 0, 2, 116, 114, 117, 109, 3, 63, 114, 0, 114, 101, 1, 17, 67, 21, 2, 32, 3, 63, 114, 12, 34, 13, 0, 116, 101, 108, 8, 3, 63, 114, 47, 13, 55, 0, 7, 6, 109, 105, 0, 2, 110, 101, 117, 114, 3, 63, 2, 37, 0, 114, 97, 107, 117, 2, 108, 101, 117, 115, 3, 63, 2, 37, 34, 2, 35, 49, 2, 116, 0, 107, 114, 111, 98, 101, 3, 63, 2, 37, 49, 34, 115, 69, 13, 0, 110, 105, 2, 109, 97, 21, 3, 63, 2, 37, 50, 2, 37, 0, 97, 97, 117, 3, 63, 2, 37, 127, 12, 0, 110, 97, 103, 3, 63, 6, 107, 50, 35, 134, 0, 100, 100, 97, 103, 101, 116, 101, 3, 63, 6, 107, 70, 35, 134, 10, 114, 47, 13, 0, 115, 2, 108, 105, 107, 3, 63, 6, 107, 87, 0, 4, 2, 109, 105, 101, 107, 3, 63, 13, 0, 2, 109, 111, 115, 97, 0, 2, 115, 115, 105, 101, 108, 0, 114, 97, 107, 101, 108, 3, 63, 13, 34, 113, 49, 13, 55, 0, 110, 97, 114, 101, 2, 116, 3, 63, 13, 50, 2, 35, 34, 106, 0, 110, 105, 115, 116, 101, 114, 115, 3, 63, 13, 50, 6, 107, 87, 47, 13, 34, 87, 0, 110, 117, 2, 115, 107, 117, 3, 63, 13, 50, 13, 0, 4, 110, 100, 101, 114, 2, 106, 97, 114, 3, 63, 13, 50, 13, 34, 0, 110, 101, 114, 2, 17, 65, 0, 110, 105, 115, 116, 101, 114, 105, 3, 63, 13, 50, 13, 87, 47, 2, 114, 34, 2, 37, 0, 110, 105, 115, 116, 101, 2, 114, 105, 101, 25, 3, 63, 13, 50, 13, 87, 47, 114, 0, 108, 2, 106, 17, 65, 3, 63, 13, 55, 0, 108, 105, 116, 3, 63, 13, 55, 13, 47, 0, 108, 105, 101, 117, 3, 63, 13, 55, 57, 116, 0, 108, 108, 101, 2, 110, 110, 105, 17, 65, 3, 63, 13, 55, 106, 0, 100, 100, 101, 108, 2, 106, 97, 114, 105, 3, 63, 13, 70, 13, 55, 0, 4, 115, 2, 103, 105, 115, 3, 63, 13, 87, 0, 115, 2, 103, 117, 110, 0, 115, 2, 104, 97, 0, 115, 2, 108, 0, 115, 2, 110, 111, 101, 103, 0, 115, 2, 112, 108, 97, 97, 115, 0, 115, 2, 114, 97, 98, 101, 108, 0, 115, 2, 114, 101, 107, 101, 110, 0, 115, 2, 116, 105, 101, 107, 0, 115, 2, 116, 114, 111, 111, 115, 0, 115, 2, 118, 111, 114, 109, 0, 115, 8, 2, 105, 110, 14, 128, 132, 131, 0, 115, 8, 2, 109, 0, 115, 101, 2, 114, 97, 0, 115, 116, 101, 114, 2, 105, 101, 117, 115, 3, 63, 13, 87, 47, 114, 34, 0, 115, 107, 101, 2, 110, 3, 63, 13, 87, 49, 106, 0, 2, 115, 115, 105, 101, 3, 63, 37, 0, 107, 114, 2, 111, 3, 63, 37, 49, 34, 0, 100, 100, 101, 2, 108, 3, 63, 107, 70, 13, 0, 100, 100, 101, 108, 108, 105, 2, 107, 3, 63, 107, 70, 13, 55, 13, 0, 4, 115, 2, 108, 97, 109, 112, 3, 63, 107, 87, 0, 115, 2, 108, 111, 111, 112, 0, 115, 2, 111, 0, 7, 6, 109, 111, 0, 4, 2, 112, 97, 110, 105, 3, 63, 2, 40, 0, 101, 2, 114, 97, 115, 0, 116, 111, 114, 2, 105, 101, 3, 63, 2, 40, 47, 115, 34, 0, 4, 108, 101, 115, 2, 25, 3, 63, 2, 40, 55, 106, 87, 0, 108, 101, 115, 2, 116, 101, 32, 0, 100, 101, 114, 110, 3, 63, 2, 40, 70, 110, 34, 14, 50, 0, 104, 97, 109, 109, 101, 100, 2, 97, 3, 63, 2, 40, 105, 2, 35, 63, 13, 70, 0, 4, 2, 100, 117, 108, 17, 65, 3, 63, 2, 108, 0, 2, 115, 107, 101, 101, 0, 4, 114, 2, 102, 111, 115, 101, 3, 63, 2, 108, 34, 0, 114, 8, 2, 17, 67, 21, 0, 114, 102, 2, 111, 116, 111, 109, 105, 101, 3, 63, 2, 108, 34, 81, 0, 122, 122, 97, 114, 101, 108, 108, 97, 3, 63, 2, 108, 47, 87, 2, 35, 34, 110, 55, 2, 35, 0, 110, 2, 116, 101, 117, 114, 3, 63, 2, 108, 50, 0, 110, 105, 116, 2, 101, 3, 63, 2, 108, 50, 2, 37, 47, 0, 110, 117, 2, 109, 101, 110, 116, 3, 63, 2, 108, 50, 2, 116, 0, 110, 101, 2, 116, 195, 170, 114, 3, 63, 2, 108, 50, 13, 0, 110, 100, 101, 114, 2, 17, 65, 3, 63, 2, 108, 50, 70, 114, 34, 0, 108, 101, 115, 2, 116, 17, 65, 3, 63, 2, 108, 55, 13, 87, 0, 110, 8, 2, 103, 111, 21, 3, 63, 2, 108, 66, 0, 100, 101, 2, 108, 108, 101, 21, 3, 63, 2, 108, 70, 13, 0, 100, 101, 114, 97, 2, 116, 17, 65, 3, 63, 2, 108, 70, 13, 34, 2, 35, 0, 100, 101, 114, 97, 2, 116, 111, 114, 25, 3, 63, 2, 108, 70, 13, 34, 113, 0, 2, 110, 97, 114, 103, 3, 63, 2, 115, 0, 116, 105, 101, 2, 17, 67, 3, 63, 2, 115, 47, 37, 0, 110, 97, 114, 103, 105, 101, 2, 32, 24, 3, 63, 2, 115, 50, 2, 35, 34, 134, 37, 0, 110, 111, 2, 103, 97, 3, 63, 2, 115, 50, 2, 115, 0, 110, 111, 112, 111, 2, 108, 105, 3, 63, 2, 115, 50, 2, 115, 48, 2, 40, 0, 100, 101, 2, 108, 3, 63, 2, 115, 70, 110, 0, 115, 97, 2, 195, 175, 101, 107, 3, 63, 2, 115, 87, 2, 35, 0, 115, 97, 109, 2, 98, 105, 101, 107, 3, 63, 2, 115, 87, 2, 35, 63, 0, 101, 105, 116, 101, 3, 63, 6, 124, 47, 13, 0, 100, 101, 8, 3, 63, 7, 115, 70, 13, 0, 101, 100, 115, 119, 105, 108, 108, 105, 103, 3, 63, 40, 47, 87, 82, 6, 107, 55, 13, 134, 0, 114, 114, 8, 2, 105, 3, 63, 108, 34, 0, 114, 115, 8, 2, 21, 3, 63, 108, 34, 87, 0, 110, 110, 105, 107, 101, 3, 63, 108, 50, 13, 49, 13, 0, 110, 105, 116, 111, 114, 2, 25, 3, 63, 108, 50, 37, 47, 108, 34, 0, 2, 98, 105, 101, 108, 3, 63, 115, 6, 0, 116, 111, 114, 3, 63, 115, 47, 13, 34, 0, 7, 6, 111, 110, 0, 4, 2, 114, 101, 103, 118, 12, 12, 3, 2, 108, 50, 0, 2, 116, 111, 101, 0, 2, 116, 117, 103, 116, 105, 103, 0, 2, 116, 119, 121, 102, 101, 108, 0, 8, 2, 21, 14, 128, 132, 130, 0, 8, 2, 116, 97, 97, 108, 0, 8, 2, 116, 97, 107, 116, 0, 8, 2, 116, 97, 115, 98, 97, 0, 8, 2, 116, 111, 111, 17, 67, 17, 67, 0, 8, 2, 116, 121, 100, 0, 8, 2, 119, 101, 115, 101, 110, 0, 116, 2, 100, 21, 0, 111, 109, 2, 115, 116, 111, 111, 116, 3, 2, 108, 50, 2, 108, 63, 0, 4, 97, 102, 8, 2, 115, 107, 101, 105, 17, 67, 3, 2, 108, 50, 10, 2, 35, 81, 0, 97, 102, 8, 2, 119, 101, 110, 100, 0, 4, 100, 101, 114, 2, 98, 114, 101, 3, 2, 108, 50, 13, 34, 0, 100, 101, 114, 2, 98, 114, 111, 107, 101, 0, 100, 101, 114, 2, 100, 97, 110, 105, 103, 0, 100, 101, 114, 2, 100, 114, 117, 107, 0, 100, 101, 114, 2, 100, 117, 105, 109, 0, 100, 101, 114, 2, 104, 97, 110, 100, 101, 0, 100, 101, 114, 2, 104, 101, 119, 0, 100, 101, 114, 2, 104, 111, 114, 0, 100, 101, 114, 2, 104, 111, 117, 0, 100, 101, 114, 2, 108, 101, 103, 0, 100, 101, 114, 2, 109, 121, 110, 0, 100, 101, 114, 2, 110, 101, 0, 100, 101, 114, 2, 115, 107, 114, 121, 17, 67, 0, 100, 101, 114, 2, 115, 111, 101, 107, 101, 110, 0, 100, 101, 114, 2, 115, 116, 101, 117, 0, 100, 101, 114, 2, 115, 116, 114, 101, 0, 100, 101, 114, 2, 116, 101, 107, 101, 110, 0, 100, 101, 114, 2, 116, 114, 111, 117, 0, 100, 101, 114, 2, 118, 97, 110, 103, 0, 100, 101, 114, 2, 118, 105, 110, 0, 100, 101, 114, 2, 118, 114, 97, 0, 100, 101, 114, 2, 119, 101, 114, 112, 105, 110, 103, 0, 100, 101, 114, 2, 119, 111, 114, 112, 0, 100, 101, 114, 8, 2, 115, 107, 17, 65, 0, 100, 101, 114, 111, 110, 115, 105, 101, 3, 2, 108, 50, 13, 34, 19, 133, 50, 87, 37, 0, 100, 101, 114, 115, 116, 101, 98, 111, 3, 2, 108, 50, 13, 34, 87, 47, 13, 69, 115, 0, 116, 8, 2, 21, 14, 128, 132, 131, 3, 2, 108, 50, 47, 0, 116, 101, 109, 2, 98, 97, 3, 2, 108, 50, 47, 106, 63, 0, 116, 101, 108, 8, 3, 2, 108, 50, 47, 110, 55, 0, 116, 101, 114, 105, 110, 103, 3, 2, 108, 50, 47, 114, 34, 13, 66, 0, 100, 101, 117, 114, 3, 2, 108, 50, 70, 2, 116, 13, 34, 0, 118, 111, 111, 114, 2, 115, 3, 2, 108, 50, 81, 2, 115, 34, 0, 4, 119, 101, 101, 114, 8, 2, 108, 3, 2, 108, 50, 82, 2, 114, 34, 0, 119, 101, 101, 114, 8, 2, 115, 112, 114, 0, 119, 101, 101, 114, 8, 2, 115, 116, 97, 97, 110, 0, 104, 101, 105, 108, 2, 115, 112, 101, 108, 3, 2, 108, 50, 105, 2, 121, 55, 0, 104, 101, 105, 108, 2, 105, 103, 3, 2, 108, 50, 105, 6, 121, 55, 0, 103, 101, 101, 115, 8, 3, 2, 108, 50, 134, 2, 114, 87, 0, 103, 101, 108, 2, 100, 105, 103, 3, 2, 108, 50, 134, 110, 55, 0, 103, 114, 101, 115, 1, 107, 3, 2, 108, 66, 134, 34, 106, 87, 0, 4, 2, 115, 107, 117, 108, 100, 32, 24, 3, 6, 108, 50, 0, 8, 2, 119, 17, 65, 115, 0, 100, 101, 114, 103, 101, 8, 2, 21, 14, 128, 132, 135, 3, 6, 108, 50, 13, 34, 134, 13, 0, 105, 101, 115, 1, 21, 3, 6, 115, 50, 37, 87, 0, 4, 100, 101, 114, 2, 115, 101, 107, 114, 3, 7, 108, 50, 13, 34, 0, 100, 101, 114, 2, 119, 121, 115, 17, 67, 21, 0, 100, 101, 114, 8, 2, 101, 110, 17, 67, 3, 7, 108, 50, 13, 34, 10, 0, 104, 101, 105, 108, 3, 7, 108, 50, 105, 121, 55, 0, 121, 1, 21, 2, 32, 3, 21, 0, 111, 111, 109, 3, 40, 50, 6, 115, 63, 0, 111, 109, 101, 3, 40, 50, 6, 115, 63, 13, 0, 111, 109, 105, 101, 115, 3, 40, 50, 6, 115, 63, 37, 87, 0, 111, 109, 105, 101, 3, 40, 50, 40, 63, 6, 37, 0, 4, 2, 100, 105, 101, 114, 3, 108, 50, 0, 2, 108, 97, 110, 103, 115, 0, 2, 115, 105, 110, 32, 24, 0, 2, 116, 117, 103, 0, 8, 2, 102, 105, 107, 115, 0, 8, 2, 107, 97, 110, 116, 0, 8, 2, 107, 111, 115, 116, 101, 0, 8, 2, 107, 114, 117, 105, 100, 0, 8, 2, 108, 117, 115, 0, 8, 2, 112, 97, 97, 114, 0, 8, 2, 116, 117, 105, 17, 67, 0, 8, 2, 117, 105, 116, 103, 101, 21, 12, 12, 14, 128, 132, 130, 3, 108, 50, 10, 0, 117, 105, 116, 8, 2, 21, 14, 128, 132, 133, 3, 108, 50, 10, 125, 47, 0, 4, 100, 101, 114, 3, 108, 50, 13, 34, 0, 100, 101, 114, 2, 104, 111, 117, 100, 25, 0, 100, 101, 114, 2, 104, 111, 117, 100, 101, 32, 0, 100, 101, 114, 2, 115, 107, 101, 105, 100, 32, 24, 0, 100, 101, 114, 119, 121, 115, 101, 114, 2, 97, 3, 108, 50, 13, 34, 82, 6, 121, 87, 13, 34, 10, 0, 114, 101, 103, 2, 25, 3, 108, 50, 34, 110, 134, 0, 110, 105, 101, 8, 3, 108, 50, 37, 0, 116, 101, 118, 114, 101, 100, 101, 3, 108, 50, 47, 13, 81, 34, 6, 114, 70, 13, 0, 116, 101, 101, 110, 115, 101, 103, 3, 108, 50, 47, 114, 50, 87, 6, 110, 134, 0, 119, 101, 101, 114, 8, 3, 108, 50, 82, 114, 34, 0, 4, 103, 101, 2, 100, 105, 101, 114, 116, 3, 108, 50, 134, 13, 0, 103, 101, 8, 2, 21, 14, 128, 132, 132, 0, 103, 101, 114, 105, 101, 102, 108, 105, 2, 107, 3, 108, 50, 134, 13, 34, 6, 37, 81, 55, 13, 0, 103, 101, 108, 111, 111, 102, 108, 105, 8, 2, 107, 3, 108, 50, 134, 13, 55, 6, 115, 81, 55, 13, 0, 103, 101, 109, 97, 107, 108, 105, 2, 107, 3, 108, 50, 134, 13, 63, 6, 35, 49, 55, 13, 0, 105, 107, 115, 3, 115, 50, 13, 49, 87, 0, 4, 105, 101, 1, 108, 111, 107, 3, 115, 50, 37, 0, 105, 101, 1, 109, 101, 114, 101, 115, 2, 25, 0, 105, 101, 115, 1, 112, 21, 3, 115, 50, 37, 87, 0, 117, 115, 8, 3, 115, 50, 109, 87, 0, 4, 100, 106, 105, 101, 3, 122, 66, 78, 37, 0, 116, 106, 105, 101, 0, 4, 115, 1, 98, 3, 133, 50, 87, 0, 115, 1, 100, 0, 115, 1, 103, 0, 115, 1, 114, 102, 0, 4, 103, 101, 1, 21, 2, 108, 117, 107, 21, 3, 133, 66, 134, 13, 0, 103, 101, 2, 108, 117, 107, 32, 0, 103, 101, 2, 108, 117, 107, 107, 101, 32, 0, 103, 101, 2, 108, 117, 107, 107, 105, 101, 0, 103, 101, 2, 108, 117, 107, 115, 0, 103, 101, 118, 97, 2, 108, 3, 133, 66, 134, 13, 81, 35, 0, 7, 6, 111, 111, 0, 4, 114, 2, 98, 108, 121, 119, 3, 2, 115, 34, 0, 114, 2, 98, 114, 117, 103, 0, 114, 2, 100, 105, 110, 107, 0, 114, 2, 100, 111, 110, 100, 101, 114, 0, 114, 2, 100, 114, 97, 97, 103, 0, 114, 2, 103, 97, 110, 107, 0, 114, 2, 104, 101, 101, 114, 115, 0, 114, 2, 107, 111, 111, 109, 0, 114, 2, 108, 97, 97, 105, 100, 0, 114, 2, 108, 97, 109, 115, 0, 114, 2, 109, 101, 101, 115, 116, 101, 114, 0, 114, 2, 114, 101, 101, 100, 0, 114, 2, 114, 111, 109, 112, 101, 108, 0, 114, 2, 115, 105, 103, 116, 0, 114, 2, 115, 107, 114, 121, 0, 114, 2, 115, 112, 114, 111, 110, 107, 0, 114, 2, 115, 116, 117, 114, 0, 114, 2, 116, 114, 0, 114, 2, 116, 117, 105, 103, 0, 114, 8, 2, 100, 97, 103, 0, 114, 8, 2, 100, 101, 110, 107, 0, 114, 8, 2, 100, 111, 101, 110, 0, 114, 8, 2, 100, 114, 121, 17, 67, 0, 114, 8, 2, 103, 114, 111, 101, 105, 0, 114, 8, 2, 104, 97, 97, 115, 0, 114, 8, 2, 104, 111, 111, 102, 115, 0, 114, 8, 2, 112, 101, 105, 110, 115, 0, 114, 8, 2, 115, 107, 97, 100, 117, 0, 114, 8, 2, 115, 107, 97, 116, 0, 114, 8, 2, 115, 116, 101, 108, 112, 0, 114, 8, 2, 115, 116, 114, 111, 109, 105, 0, 114, 8, 2, 118, 108, 101, 117, 101, 108, 0, 114, 8, 2, 118, 108, 111, 101, 100, 105, 103, 0, 114, 8, 2, 119, 0, 4, 114, 2, 101, 101, 110, 3, 2, 115, 34, 10, 0, 114, 2, 101, 101, 110, 103, 101, 0, 114, 2, 101, 101, 110, 115, 21, 0, 114, 2, 101, 101, 116, 0, 114, 2, 101, 105, 115, 0, 114, 101, 114, 102, 108, 105, 107, 3, 2, 115, 34, 10, 110, 34, 81, 55, 13, 49, 0, 114, 100, 119, 97, 114, 115, 8, 3, 2, 115, 34, 70, 58, 35, 34, 87, 0, 114, 100, 101, 8, 2, 107, 3, 2, 115, 34, 70, 110, 0, 114, 115, 116, 117, 117, 114, 115, 8, 3, 2, 115, 34, 87, 47, 116, 12, 34, 87, 0, 114, 115, 97, 97, 107, 108, 105, 107, 3, 2, 115, 34, 87, 113, 49, 55, 13, 49, 0, 114, 114, 101, 2, 100, 17, 65, 3, 2, 115, 34, 114, 0, 116, 2, 109, 111, 101, 100, 105, 103, 3, 2, 115, 47, 0, 4, 103, 2, 108, 111, 112, 3, 2, 115, 134, 0, 103, 2, 108, 117, 105, 107, 0, 114, 2, 101, 101, 110, 21, 21, 3, 4, 115, 34, 10, 0, 114, 2, 119, 105, 103, 3, 6, 115, 34, 0, 112, 103, 101, 8, 2, 21, 14, 128, 132, 133, 3, 6, 115, 48, 134, 13, 0, 3, 115, 0, 4, 114, 2, 115, 105, 103, 116, 121, 100, 3, 115, 34, 0, 114, 2, 116, 114, 101, 107, 0, 114, 8, 2, 116, 114, 111, 109, 0, 114, 8, 2, 104, 97, 110, 100, 21, 3, 115, 34, 6, 0, 114, 107, 111, 101, 112, 101, 108, 3, 115, 34, 49, 6, 40, 48, 13, 55, 0, 114, 108, 101, 100, 101, 8, 3, 115, 34, 55, 6, 114, 70, 13, 0, 114, 108, 101, 2, 119, 17, 65, 110, 3, 115, 34, 55, 7, 114, 0, 114, 108, 101, 2, 108, 25, 3, 115, 34, 55, 110, 0, 114, 98, 111, 100, 105, 103, 3, 115, 34, 69, 6, 115, 70, 13, 134, 0, 114, 98, 108, 117, 102, 3, 115, 34, 69, 55, 6, 109, 81, 0, 114, 100, 114, 101, 119, 101, 3, 115, 34, 70, 34, 6, 114, 82, 13, 0, 109, 98, 108, 105, 107, 108, 105, 107, 3, 115, 63, 69, 55, 6, 107, 49, 55, 13, 49, 0, 4, 105, 3, 123, 0, 121, 0, 4, 110, 100, 106, 105, 101, 3, 123, 66, 49, 37, 0, 110, 116, 106, 105, 101, 0, 4, 100, 106, 105, 101, 3, 123, 78, 37, 0, 116, 106, 105, 101, 0, 7, 6, 111, 112, 0, 4, 2, 104, 111, 117, 100, 101, 3, 2, 108, 48, 0, 2, 108, 101, 116, 116, 0, 2, 110, 117, 117, 116, 0, 2, 114, 111, 101, 114, 105, 103, 0, 2, 114, 117, 105, 101, 110, 0, 2, 115, 105, 101, 110, 98, 0, 2, 115, 105, 111, 110, 101, 21, 0, 2, 115, 116, 97, 110, 100, 105, 103, 0, 2, 119, 105, 110, 100, 101, 0, 8, 2, 114, 101, 103, 0, 8, 2, 115, 121, 0, 8, 2, 118, 97, 108, 108, 0, 8, 2, 118, 108, 105, 101, 195, 171, 0, 112, 111, 114, 2, 116, 117, 3, 2, 108, 48, 2, 108, 34, 0, 112, 101, 114, 2, 118, 108, 97, 107, 107, 105, 3, 2, 108, 48, 13, 34, 0, 112, 111, 110, 2, 17, 65, 3, 2, 108, 48, 13, 50, 0, 112, 111, 115, 2, 105, 115, 105, 101, 3, 2, 108, 48, 13, 86, 0, 116, 105, 2, 109, 17, 65, 3, 2, 108, 48, 47, 2, 37, 0, 109, 101, 114, 107, 108, 105, 8, 2, 107, 3, 2, 108, 48, 63, 110, 34, 49, 55, 13, 0, 115, 101, 116, 108, 105, 107, 3, 2, 108, 48, 87, 106, 47, 55, 13, 49, 0, 115, 105, 103, 116, 101, 108, 105, 8, 2, 107, 3, 2, 108, 48, 87, 107, 134, 47, 13, 55, 13, 0, 101, 114, 8, 2, 17, 65, 3, 2, 115, 48, 13, 34, 0, 101, 114, 97, 115, 105, 101, 3, 2, 115, 48, 13, 34, 113, 87, 37, 0, 101, 110, 2, 98, 3, 2, 115, 48, 13, 50, 0, 8, 2, 21, 14, 128, 132, 130, 3, 6, 108, 48, 0, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 6, 108, 48, 134, 13, 0, 103, 101, 101, 2, 12, 3, 6, 108, 48, 134, 114, 0, 1, 17, 67, 10, 2, 105, 103, 3, 6, 115, 48, 0, 101, 101, 110, 1, 25, 3, 10, 2, 108, 48, 10, 114, 50, 0, 97, 97, 116, 3, 40, 48, 6, 113, 47, 0, 4, 97, 116, 105, 101, 115, 3, 40, 48, 6, 113, 47, 37, 87, 0, 97, 116, 105, 101, 115, 0, 97, 116, 105, 101, 3, 40, 48, 35, 47, 6, 37, 0, 2, 111, 102, 102, 101, 114, 3, 108, 48, 0, 112, 101, 114, 3, 108, 48, 13, 34, 0, 116, 101, 108, 3, 108, 48, 47, 110, 55, 0, 115, 112, 114, 97, 97, 107, 3, 108, 48, 87, 48, 34, 113, 49, 0, 105, 110, 105, 101, 3, 115, 48, 6, 37, 50, 37, 0, 4, 101, 2, 108, 3, 115, 48, 13, 0, 101, 8, 2, 25, 0, 101, 8, 2, 114, 105, 103, 0, 101, 114, 97, 2, 25, 3, 115, 48, 13, 34, 2, 35, 0, 101, 110, 2, 12, 3, 115, 48, 13, 50, 0, 105, 117, 109, 3, 115, 48, 37, 109, 63, 0, 117, 8, 2, 115, 3, 115, 48, 109, 0, 7, 6, 112, 97, 0, 114, 97, 2, 17, 67, 3, 4, 48, 35, 34, 35, 0, 4, 2, 103, 111, 100, 17, 65, 3, 48, 2, 35, 0, 2, 110, 101, 108, 101, 0, 2, 110, 105, 101, 107, 0, 2, 112, 105, 101, 114, 0, 2, 112, 105, 114, 117, 115, 0, 2, 115, 105, 102, 105, 0, 2, 115, 116, 101, 108, 0, 2, 116, 114, 17, 65, 0, 8, 2, 107, 107, 97, 0, 8, 2, 115, 116, 101, 105, 0, 8, 2, 115, 116, 111, 0, 8, 2, 116, 17, 65, 0, 112, 2, 98, 114, 111, 101, 107, 17, 65, 17, 67, 0, 114, 8, 2, 17, 67, 17, 65, 3, 48, 2, 35, 34, 0, 114, 111, 2, 100, 105, 3, 48, 2, 35, 34, 2, 40, 0, 114, 116, 105, 2, 115, 97, 3, 48, 2, 35, 34, 47, 2, 37, 0, 114, 116, 105, 2, 116, 117, 3, 48, 2, 35, 34, 47, 13, 0, 114, 108, 101, 2, 109, 101, 110, 116, 3, 48, 2, 35, 34, 55, 13, 0, 114, 109, 101, 2, 115, 97, 97, 110, 3, 48, 2, 35, 34, 63, 13, 0, 116, 105, 101, 2, 25, 24, 3, 48, 2, 35, 47, 6, 37, 0, 116, 114, 105, 2, 21, 3, 48, 2, 35, 47, 34, 2, 37, 0, 116, 114, 105, 97, 114, 2, 103, 97, 3, 48, 2, 35, 47, 34, 2, 37, 2, 35, 34, 0, 116, 114, 111, 2, 108, 108, 101, 3, 48, 2, 35, 47, 34, 2, 40, 0, 116, 195, 169, 3, 48, 2, 35, 47, 114, 0, 112, 97, 106, 97, 3, 48, 2, 35, 48, 6, 113, 37, 35, 0, 4, 112, 101, 2, 103, 97, 97, 105, 3, 48, 2, 35, 48, 13, 0, 112, 112, 101, 2, 114, 121, 0, 112, 97, 119, 101, 114, 3, 48, 2, 35, 48, 113, 82, 13, 34, 0, 107, 105, 115, 116, 97, 110, 3, 48, 2, 35, 49, 2, 37, 87, 47, 35, 50, 0, 107, 107, 101, 2, 116, 3, 48, 2, 35, 49, 106, 0, 4, 110, 8, 2, 100, 111, 3, 48, 2, 35, 50, 0, 110, 8, 2, 116, 111, 0, 110, 111, 2, 114, 97, 109, 3, 48, 2, 35, 50, 2, 40, 0, 110, 100, 101, 2, 109, 105, 101, 3, 48, 2, 35, 50, 70, 114, 0, 108, 2, 109, 105, 101, 116, 3, 48, 2, 35, 55, 0, 108, 101, 2, 115, 116, 17, 65, 3, 48, 2, 35, 55, 13, 0, 108, 105, 110, 2, 100, 114, 111, 3, 48, 2, 35, 55, 13, 50, 0, 108, 101, 2, 116, 3, 48, 2, 35, 55, 106, 0, 109, 2, 17, 67, 3, 48, 2, 35, 63, 0, 109, 112, 101, 114, 2, 108, 3, 48, 2, 35, 63, 48, 13, 34, 0, 4, 118, 105, 108, 2, 106, 111, 101, 3, 48, 2, 35, 82, 13, 55, 0, 119, 105, 108, 2, 106, 111, 101, 0, 115, 2, 111, 112, 3, 48, 2, 35, 87, 0, 115, 115, 97, 2, 115, 105, 101, 114, 3, 48, 2, 35, 87, 2, 35, 0, 115, 116, 111, 8, 2, 114, 17, 65, 21, 3, 48, 2, 35, 87, 47, 2, 40, 0, 115, 101, 2, 108, 108, 97, 3, 48, 2, 35, 87, 110, 0, 116, 105, 101, 115, 1, 21, 3, 48, 6, 113, 47, 37, 87, 0, 100, 100, 97, 8, 2, 17, 67, 17, 65, 3, 48, 7, 35, 70, 35, 0, 2, 116, 97, 116, 3, 48, 13, 0, 114, 97, 100, 101, 2, 25, 3, 48, 13, 34, 113, 70, 13, 0, 110, 97, 100, 111, 3, 48, 13, 50, 113, 70, 118, 12, 0, 106, 97, 109, 97, 3, 48, 13, 73, 113, 63, 2, 35, 0, 114, 107, 97, 2, 98, 97, 97, 100, 106, 3, 48, 35, 34, 49, 2, 35, 0, 114, 107, 101, 2, 114, 97, 97, 100, 3, 48, 35, 34, 49, 13, 0, 107, 2, 17, 65, 3, 48, 35, 49, 19, 0, 110, 8, 2, 103, 101, 17, 67, 3, 48, 35, 50, 0, 110, 97, 109, 97, 3, 48, 35, 50, 13, 63, 35, 0, 110, 116, 115, 101, 114, 3, 48, 35, 50, 47, 87, 13, 34, 0, 108, 106, 97, 8, 2, 25, 3, 48, 35, 55, 57, 7, 35, 0, 109, 2, 112, 97, 3, 48, 35, 63, 0, 110, 107, 114, 101, 97, 3, 48, 35, 66, 49, 34, 2, 37, 2, 35, 0, 110, 103, 97, 3, 48, 35, 66, 79, 35, 0, 115, 8, 2, 17, 65, 17, 65, 3, 48, 35, 87, 0, 97, 114, 108, 8, 3, 48, 111, 34, 112, 0, 116, 105, 111, 3, 48, 113, 47, 37, 38, 40, 0, 7, 6, 112, 101, 0, 2, 110, 97, 108, 105, 3, 48, 2, 106, 0, 114, 105, 2, 115, 17, 67, 17, 65, 3, 48, 2, 106, 34, 13, 0, 114, 105, 102, 101, 2, 114, 17, 65, 21, 3, 48, 2, 106, 34, 13, 81, 13, 0, 110, 2, 100, 117, 108, 101, 3, 48, 2, 106, 50, 0, 110, 101, 2, 116, 114, 17, 65, 3, 48, 2, 106, 50, 13, 0, 110, 105, 115, 105, 2, 108, 108, 105, 3, 48, 2, 106, 50, 13, 87, 13, 0, 110, 115, 105, 2, 111, 101, 110, 3, 48, 2, 106, 50, 89, 2, 37, 0, 108, 105, 8, 2, 107, 97, 3, 48, 2, 106, 55, 2, 37, 0, 108, 111, 116, 111, 110, 3, 48, 2, 106, 55, 13, 47, 108, 50, 0, 100, 8, 2, 111, 102, 3, 48, 2, 106, 70, 0, 100, 97, 8, 2, 103, 3, 48, 2, 106, 70, 2, 35, 0, 100, 105, 8, 3, 48, 2, 106, 70, 2, 37, 0, 114, 2, 115, 101, 101, 108, 3, 48, 2, 110, 34, 0, 114, 108, 101, 2, 109, 111, 101, 3, 48, 2, 110, 34, 55, 13, 0, 114, 115, 111, 2, 110, 101, 101, 108, 3, 48, 2, 110, 34, 87, 2, 40, 0, 114, 103, 111, 108, 97, 3, 48, 2, 110, 34, 134, 115, 55, 2, 35, 0, 4, 108, 101, 2, 116, 111, 110, 3, 48, 2, 110, 55, 13, 0, 108, 101, 2, 116, 111, 110, 0, 114, 105, 2, 111, 3, 48, 2, 114, 34, 2, 37, 0, 114, 100, 101, 8, 3, 48, 6, 111, 34, 70, 13, 0, 4, 1, 17, 67, 21, 2, 100, 97, 3, 48, 13, 0, 2, 110, 97, 114, 105, 101, 0, 2, 114, 114, 111, 110, 0, 2, 116, 105, 101, 116, 101, 114, 0, 2, 116, 105, 115, 105, 0, 2, 116, 117, 110, 105, 97, 0, 8, 2, 100, 17, 65, 0, 4, 114, 2, 107, 117, 115, 115, 105, 101, 3, 48, 13, 34, 0, 114, 2, 115, 101, 112, 115, 105, 0, 114, 2, 115, 111, 0, 4, 114, 101, 1, 109, 97, 107, 115, 2, 32, 3, 48, 13, 34, 13, 0, 114, 101, 1, 112, 2, 32, 0, 114, 101, 1, 121, 114, 2, 32, 0, 114, 109, 105, 116, 3, 48, 13, 34, 63, 6, 107, 47, 0, 4, 114, 100, 101, 1, 101, 112, 2, 32, 3, 48, 13, 34, 70, 13, 0, 114, 100, 101, 1, 109, 101, 116, 2, 32, 0, 114, 100, 101, 1, 112, 105, 110, 115, 2, 32, 0, 114, 100, 101, 1, 114, 117, 112, 2, 32, 0, 114, 100, 101, 1, 115, 97, 114, 2, 32, 0, 114, 102, 101, 107, 3, 48, 13, 34, 81, 106, 49, 0, 114, 118, 101, 114, 116, 3, 48, 13, 34, 81, 110, 34, 47, 0, 114, 118, 101, 114, 115, 3, 48, 13, 34, 81, 110, 34, 87, 0, 114, 115, 101, 110, 116, 3, 48, 13, 34, 87, 106, 50, 47, 0, 114, 115, 101, 110, 116, 97, 1, 21, 2, 115, 105, 3, 48, 13, 34, 87, 106, 50, 47, 113, 0, 116, 114, 111, 108, 2, 101, 117, 109, 3, 48, 13, 47, 34, 115, 55, 0, 110, 101, 2, 32, 3, 48, 13, 50, 13, 0, 108, 105, 110, 103, 1, 114, 2, 32, 3, 48, 13, 55, 13, 66, 0, 114, 105, 112, 97, 2, 116, 3, 48, 106, 34, 37, 48, 35, 7, 0, 116, 114, 111, 108, 3, 48, 106, 47, 34, 13, 55, 10, 0, 100, 111, 8, 2, 109, 3, 48, 106, 70, 2, 40, 0, 115, 1, 114, 101, 100, 110, 117, 114, 3, 48, 106, 87, 0, 114, 107, 101, 1, 21, 2, 32, 3, 48, 110, 34, 49, 13, 0, 114, 107, 101, 114, 1, 21, 2, 25, 3, 48, 110, 34, 49, 13, 34, 0, 114, 107, 105, 110, 103, 1, 21, 3, 48, 110, 34, 49, 13, 66, 0, 114, 109, 97, 110, 101, 110, 3, 48, 110, 34, 63, 35, 50, 6, 106, 50, 0, 114, 115, 2, 111, 109, 3, 48, 110, 34, 87, 10, 0, 114, 115, 107, 101, 3, 48, 110, 34, 87, 49, 13, 0, 114, 1, 121, 114, 2, 100, 3, 48, 111, 34, 0, 114, 100, 8, 2, 114, 3, 48, 111, 34, 47, 0, 4, 114, 100, 101, 1, 21, 2, 32, 3, 48, 111, 34, 70, 13, 0, 114, 100, 101, 2, 107, 97, 114, 0, 8, 2, 116, 114, 17, 65, 32, 3, 48, 114, 0, 114, 101, 1, 21, 2, 32, 3, 48, 114, 34, 13, 0, 7, 6, 112, 114, 0, 111, 116, 101, 115, 116, 3, 4, 48, 34, 108, 47, 13, 87, 47, 0, 111, 112, 97, 103, 3, 4, 48, 34, 108, 48, 35, 134, 0, 97, 107, 8, 2, 116, 121, 107, 3, 48, 34, 2, 35, 49, 0, 97, 107, 116, 105, 2, 115, 121, 110, 3, 48, 34, 2, 35, 49, 47, 2, 37, 0, 105, 2, 109, 97, 97, 116, 3, 48, 34, 2, 37, 0, 101, 116, 111, 114, 105, 3, 48, 34, 2, 37, 47, 2, 115, 34, 2, 37, 0, 101, 116, 111, 114, 105, 97, 2, 110, 3, 48, 34, 2, 37, 47, 2, 115, 34, 2, 37, 6, 113, 0, 101, 116, 111, 114, 105, 97, 2, 32, 3, 48, 34, 2, 37, 47, 6, 115, 34, 37, 35, 0, 101, 109, 105, 195, 168, 114, 101, 3, 48, 34, 2, 37, 63, 57, 111, 34, 0, 105, 118, 2, 97, 21, 3, 48, 34, 2, 37, 81, 0, 105, 101, 115, 116, 101, 114, 101, 2, 25, 3, 48, 34, 2, 37, 87, 47, 13, 34, 106, 0, 4, 111, 2, 17, 67, 17, 65, 3, 48, 34, 2, 40, 0, 111, 2, 98, 108, 17, 65, 0, 111, 2, 103, 114, 97, 109, 0, 111, 116, 101, 115, 2, 116, 101, 32, 24, 3, 48, 34, 2, 40, 47, 106, 87, 0, 111, 106, 101, 107, 3, 48, 34, 2, 40, 57, 106, 49, 0, 111, 100, 117, 107, 2, 17, 65, 3, 48, 34, 2, 40, 70, 109, 49, 10, 0, 111, 102, 101, 115, 115, 105, 111, 2, 110, 3, 48, 34, 2, 40, 81, 2, 106, 89, 2, 37, 2, 40, 0, 111, 118, 105, 116, 97, 3, 48, 34, 2, 40, 82, 37, 47, 2, 35, 0, 111, 115, 101, 115, 3, 48, 34, 2, 40, 87, 106, 87, 0, 111, 103, 114, 97, 109, 109, 101, 2, 114, 105, 110, 103, 3, 48, 34, 2, 40, 134, 34, 2, 35, 63, 114, 0, 101, 112, 97, 2, 114, 97, 3, 48, 34, 2, 106, 48, 13, 0, 101, 115, 116, 105, 103, 101, 3, 48, 34, 2, 106, 87, 47, 37, 12, 88, 0, 101, 115, 98, 105, 116, 101, 114, 105, 2, 97, 3, 48, 34, 2, 106, 87, 69, 13, 47, 2, 114, 34, 2, 37, 0, 101, 103, 2, 110, 97, 110, 17, 67, 3, 48, 34, 2, 106, 134, 0, 111, 112, 111, 115, 105, 3, 48, 34, 2, 108, 48, 13, 86, 37, 0, 111, 107, 117, 2, 114, 17, 65, 3, 48, 34, 2, 108, 49, 2, 116, 0, 111, 108, 101, 116, 97, 114, 105, 2, 97, 3, 48, 34, 2, 108, 55, 13, 47, 2, 35, 34, 2, 37, 0, 111, 109, 117, 108, 103, 2, 101, 3, 48, 34, 2, 108, 63, 2, 109, 55, 134, 0, 111, 109, 101, 110, 97, 100, 101, 3, 48, 34, 2, 108, 63, 13, 50, 113, 70, 13, 0, 111, 109, 105, 115, 107, 117, 3, 48, 34, 2, 108, 63, 13, 87, 49, 116, 0, 111, 98, 108, 101, 2, 109, 97, 116, 105, 3, 48, 34, 2, 108, 69, 55, 13, 0, 111, 102, 105, 116, 2, 101, 3, 48, 34, 2, 108, 81, 13, 47, 0, 111, 115, 101, 2, 100, 117, 114, 101, 3, 48, 34, 2, 108, 87, 13, 0, 111, 115, 116, 105, 2, 116, 117, 3, 48, 34, 2, 108, 87, 47, 13, 0, 101, 100, 105, 2, 107, 97, 110, 116, 3, 48, 34, 2, 114, 70, 13, 0, 111, 2, 103, 114, 101, 115, 115, 3, 48, 34, 2, 115, 0, 111, 116, 101, 2, 195, 175, 3, 48, 34, 2, 115, 47, 13, 0, 111, 106, 101, 107, 2, 116, 105, 101, 108, 3, 48, 34, 2, 115, 57, 2, 106, 49, 0, 111, 118, 105, 2, 97, 110, 100, 3, 48, 34, 2, 115, 82, 2, 37, 0, 111, 115, 97, 2, 195, 175, 101, 3, 48, 34, 2, 115, 87, 113, 0, 111, 103, 101, 115, 116, 101, 114, 2, 111, 3, 48, 34, 2, 115, 134, 2, 106, 87, 47, 13, 34, 0, 101, 2, 110, 97, 116, 97, 3, 48, 34, 4, 114, 0, 4, 101, 2, 108, 117, 100, 3, 48, 34, 13, 0, 101, 2, 109, 105, 101, 114, 0, 101, 2, 115, 17, 65, 0, 101, 116, 101, 110, 2, 115, 105, 3, 48, 34, 13, 47, 132, 50, 0, 105, 110, 115, 105, 2, 112, 17, 65, 3, 48, 34, 13, 50, 87, 13, 0, 105, 110, 115, 105, 112, 101, 2, 25, 3, 48, 34, 13, 50, 87, 37, 48, 13, 0, 105, 110, 115, 101, 2, 115, 3, 48, 34, 13, 50, 87, 106, 0, 105, 110, 115, 101, 115, 1, 21, 2, 32, 3, 48, 34, 13, 50, 87, 106, 87, 0, 105, 109, 105, 2, 116, 3, 48, 34, 13, 63, 13, 0, 4, 101, 115, 101, 2, 100, 101, 110, 116, 3, 48, 34, 13, 87, 13, 0, 105, 115, 111, 2, 110, 105, 101, 114, 0, 101, 115, 105, 100, 101, 110, 2, 17, 67, 3, 48, 34, 13, 87, 13, 70, 106, 50, 0, 101, 115, 116, 97, 2, 115, 105, 101, 3, 48, 34, 13, 87, 47, 113, 0, 101, 115, 116, 101, 2, 114, 101, 110, 100, 3, 48, 34, 13, 87, 47, 114, 0, 101, 115, 116, 101, 101, 114, 3, 48, 34, 13, 87, 47, 114, 34, 0, 101, 115, 101, 110, 116, 1, 21, 3, 48, 34, 13, 87, 106, 50, 47, 0, 101, 116, 111, 114, 105, 97, 2, 17, 67, 3, 48, 34, 37, 47, 6, 115, 34, 37, 35, 0, 101, 102, 101, 107, 3, 48, 34, 37, 81, 106, 49, 0, 111, 116, 101, 115, 3, 48, 34, 40, 47, 6, 106, 87, 0, 111, 109, 105, 110, 101, 110, 3, 48, 34, 108, 63, 37, 50, 6, 106, 50, 0, 111, 110, 107, 101, 114, 2, 116, 106, 105, 3, 48, 34, 108, 66, 49, 10, 110, 34, 0, 111, 102, 101, 115, 105, 101, 3, 48, 34, 108, 81, 13, 87, 6, 37, 0, 4, 101, 2, 104, 105, 115, 116, 111, 3, 48, 34, 114, 0, 101, 2, 115, 101, 32, 0, 101, 100, 105, 107, 101, 114, 3, 48, 34, 114, 70, 13, 49, 13, 34, 0, 111, 116, 2, 111, 110, 12, 3, 48, 34, 115, 47, 0, 111, 116, 111, 2, 17, 67, 3, 48, 34, 115, 47, 40, 0, 111, 107, 105, 101, 3, 48, 34, 115, 49, 2, 37, 0, 111, 115, 97, 3, 48, 34, 115, 87, 2, 35, 0, 111, 115, 101, 1, 21, 2, 32, 3, 48, 34, 115, 87, 13, 0, 7, 6, 114, 101, 0, 2, 97, 103, 101, 114, 101, 110, 3, 34, 2, 37, 0, 97, 2, 17, 67, 3, 34, 2, 37, 2, 35, 0, 104, 97, 98, 105, 108, 105, 116, 3, 34, 2, 37, 2, 35, 69, 2, 37, 55, 2, 37, 47, 0, 2, 195, 188, 3, 34, 2, 37, 10, 0, 97, 2, 107, 115, 3, 34, 2, 37, 35, 0, 102, 108, 101, 107, 2, 17, 67, 3, 34, 2, 37, 81, 55, 106, 49, 0, 116, 114, 111, 8, 2, 21, 14, 128, 132, 133, 3, 34, 2, 106, 47, 34, 2, 40, 0, 112, 2, 116, 105, 101, 108, 3, 34, 2, 106, 48, 0, 112, 101, 114, 116, 111, 105, 114, 101, 3, 34, 2, 106, 48, 13, 34, 47, 58, 113, 34, 0, 112, 117, 2, 116, 3, 34, 2, 106, 48, 116, 0, 100, 105, 103, 8, 2, 17, 65, 3, 34, 2, 106, 70, 2, 37, 134, 0, 102, 101, 114, 2, 97, 3, 34, 2, 106, 81, 13, 34, 0, 119, 111, 108, 2, 117, 3, 34, 2, 106, 82, 2, 109, 55, 0, 115, 111, 2, 110, 17, 65, 3, 34, 2, 106, 87, 2, 40, 0, 115, 111, 2, 108, 117, 115, 105, 101, 3, 34, 2, 106, 87, 2, 108, 0, 115, 116, 97, 117, 114, 3, 34, 2, 106, 87, 47, 2, 40, 34, 0, 115, 116, 101, 8, 2, 114, 101, 110, 100, 3, 34, 2, 106, 87, 47, 114, 0, 103, 105, 109, 101, 110, 2, 116, 97, 21, 3, 34, 2, 106, 134, 2, 37, 63, 2, 106, 50, 0, 103, 117, 2, 108, 17, 65, 3, 34, 2, 106, 134, 2, 116, 0, 103, 2, 104, 111, 101, 107, 105, 103, 3, 34, 2, 110, 134, 0, 2, 112, 114, 111, 100, 117, 3, 34, 2, 114, 0, 112, 101, 114, 2, 107, 117, 115, 3, 34, 2, 114, 48, 13, 34, 0, 108, 105, 195, 171, 102, 3, 34, 2, 114, 55, 2, 37, 106, 81, 0, 100, 101, 2, 114, 121, 3, 34, 2, 114, 70, 13, 0, 101, 108, 1, 17, 65, 10, 2, 32, 3, 34, 6, 114, 55, 0, 108, 101, 1, 10, 2, 32, 3, 34, 6, 114, 55, 13, 0, 4, 1, 17, 67, 2, 103, 97, 116, 3, 34, 13, 0, 2, 98, 101, 108, 0, 2, 100, 97, 107, 17, 67, 0, 2, 102, 114, 101, 105, 110, 0, 2, 103, 101, 101, 114, 0, 2, 103, 114, 101, 115, 25, 0, 2, 103, 114, 111, 101, 112, 0, 2, 107, 114, 117, 0, 2, 108, 105, 101, 107, 0, 2, 110, 17, 65, 0, 2, 112, 108, 105, 101, 107, 0, 2, 115, 101, 110, 115, 17, 65, 0, 2, 115, 101, 115, 115, 105, 101, 0, 2, 115, 112, 111, 110, 0, 2, 116, 111, 0, 8, 2, 108, 97, 0, 8, 2, 115, 112, 121, 116, 0, 8, 2, 115, 116, 97, 110, 116, 0, 116, 105, 2, 114, 101, 3, 34, 13, 47, 13, 0, 112, 117, 98, 108, 105, 2, 107, 3, 34, 13, 48, 2, 109, 69, 55, 2, 37, 0, 112, 117, 98, 108, 105, 101, 107, 3, 34, 13, 48, 2, 109, 69, 55, 37, 49, 0, 4, 107, 108, 97, 2, 109, 17, 65, 3, 34, 13, 49, 55, 35, 0, 107, 108, 97, 2, 109, 101, 101, 114, 0, 107, 108, 97, 109, 101, 3, 34, 13, 49, 55, 113, 63, 13, 0, 110, 101, 1, 111, 3, 34, 13, 50, 13, 0, 110, 111, 110, 115, 3, 34, 13, 50, 133, 50, 87, 0, 4, 108, 101, 2, 103, 17, 65, 3, 34, 13, 55, 13, 0, 108, 101, 2, 118, 97, 110, 0, 108, 105, 2, 103, 105, 0, 108, 97, 115, 101, 3, 34, 13, 55, 113, 87, 13, 0, 100, 101, 110, 2, 17, 65, 17, 67, 17, 65, 3, 34, 13, 70, 13, 50, 6, 0, 100, 101, 110, 101, 101, 114, 3, 34, 13, 70, 13, 50, 6, 114, 34, 0, 102, 111, 114, 2, 109, 3, 34, 13, 81, 2, 108, 34, 0, 102, 101, 114, 101, 110, 2, 100, 17, 65, 3, 34, 13, 81, 13, 34, 106, 50, 0, 119, 111, 108, 119, 101, 114, 3, 34, 13, 82, 6, 108, 55, 82, 13, 34, 0, 115, 101, 114, 119, 101, 3, 34, 13, 86, 6, 110, 34, 82, 13, 0, 4, 115, 105, 2, 100, 101, 110, 3, 34, 13, 87, 13, 0, 115, 105, 2, 116, 17, 65, 0, 115, 101, 114, 2, 118, 3, 34, 13, 87, 13, 34, 0, 115, 112, 101, 107, 2, 116, 101, 101, 114, 3, 34, 13, 87, 48, 2, 106, 49, 0, 115, 112, 101, 107, 3, 34, 13, 87, 48, 106, 49, 0, 115, 101, 112, 3, 34, 13, 87, 106, 48, 0, 115, 101, 115, 2, 32, 3, 34, 13, 87, 106, 87, 0, 115, 117, 108, 2, 116, 17, 65, 3, 34, 13, 87, 109, 55, 6, 0, 103, 105, 109, 101, 2, 32, 3, 34, 13, 88, 37, 12, 63, 0, 103, 2, 105, 115, 116, 3, 34, 13, 134, 0, 4, 103, 105, 2, 109, 101, 110, 116, 3, 34, 13, 134, 13, 0, 103, 105, 2, 115, 115, 101, 117, 17, 67, 0, 103, 108, 101, 2, 109, 101, 110, 116, 3, 34, 13, 134, 55, 13, 0, 103, 101, 114, 2, 17, 65, 3, 34, 13, 134, 114, 34, 0, 4, 1, 17, 67, 2, 110, 32, 3, 34, 106, 0, 1, 17, 67, 2, 110, 110, 101, 32, 0, 1, 101, 100, 114, 101, 112, 2, 110, 0, 116, 105, 110, 97, 3, 34, 106, 47, 37, 50, 35, 0, 112, 101, 116, 3, 34, 106, 48, 13, 47, 0, 107, 111, 114, 100, 3, 34, 106, 49, 2, 108, 34, 47, 0, 99, 99, 101, 3, 34, 106, 49, 37, 0, 109, 2, 32, 3, 34, 106, 63, 0, 103, 103, 97, 101, 3, 34, 106, 79, 121, 0, 103, 3, 34, 110, 134, 0, 103, 118, 101, 114, 100, 105, 103, 3, 34, 110, 134, 81, 6, 110, 34, 70, 13, 134, 0, 114, 105, 110, 103, 1, 10, 2, 32, 3, 34, 114, 34, 13, 66, 0, 107, 101, 2, 110, 17, 65, 3, 34, 114, 49, 13, 0, 4, 100, 101, 1, 115, 3, 34, 114, 70, 13, 0, 100, 101, 8, 2, 17, 67, 0, 100, 101, 108, 8, 3, 34, 114, 70, 13, 55, 0, 7, 6, 115, 101, 0, 110, 105, 111, 114, 2, 105, 116, 101, 105, 3, 87, 2, 37, 12, 50, 2, 37, 2, 108, 34, 0, 4, 114, 101, 2, 109, 111, 110, 105, 3, 87, 2, 106, 34, 13, 0, 114, 101, 2, 110, 97, 100, 101, 0, 114, 111, 116, 111, 2, 110, 105, 3, 87, 2, 106, 34, 13, 47, 2, 40, 0, 107, 117, 2, 108, 3, 87, 2, 106, 49, 2, 116, 0, 107, 119, 101, 2, 115, 116, 114, 17, 65, 3, 87, 2, 106, 49, 58, 13, 0, 107, 115, 2, 116, 97, 110, 116, 3, 87, 2, 106, 49, 87, 0, 107, 115, 116, 101, 2, 116, 3, 87, 2, 106, 49, 87, 47, 106, 0, 4, 110, 2, 115, 111, 114, 105, 101, 3, 87, 2, 106, 50, 0, 110, 2, 115, 117, 117, 114, 0, 110, 8, 2, 116, 114, 97, 21, 0, 110, 116, 105, 2, 109, 101, 110, 116, 3, 87, 2, 106, 50, 47, 2, 37, 0, 108, 105, 2, 98, 97, 3, 87, 2, 106, 55, 2, 37, 0, 109, 105, 2, 110, 97, 3, 87, 2, 106, 63, 2, 37, 0, 2, 108, 108, 105, 110, 3, 87, 2, 110, 6, 0, 108, 108, 111, 2, 102, 97, 3, 87, 2, 110, 55, 13, 0, 108, 100, 101, 114, 2, 121, 3, 87, 2, 110, 55, 70, 13, 34, 0, 108, 102, 2, 115, 116, 97, 110, 3, 87, 2, 110, 55, 81, 0, 108, 97, 2, 107, 97, 110, 116, 3, 87, 2, 114, 55, 13, 0, 105, 2, 115, 111, 101, 110, 3, 87, 2, 121, 0, 108, 1, 21, 2, 119, 105, 103, 3, 87, 6, 110, 55, 0, 108, 108, 105, 103, 1, 21, 3, 87, 6, 110, 55, 13, 134, 0, 108, 101, 1, 10, 2, 32, 3, 87, 6, 114, 55, 13, 0, 110, 105, 111, 114, 8, 3, 87, 7, 37, 12, 50, 37, 13, 34, 0, 107, 111, 1, 21, 2, 110, 111, 21, 3, 87, 10, 2, 106, 49, 2, 40, 0, 4, 2, 32, 3, 87, 13, 0, 2, 100, 117, 107, 0, 2, 107, 111, 0, 2, 107, 117, 0, 2, 114, 111, 101, 116, 0, 8, 2, 100, 101, 110, 116, 0, 8, 2, 100, 111, 111, 115, 0, 8, 2, 107, 114, 101, 0, 8, 2, 110, 105, 21, 0, 8, 2, 114, 105, 110, 103, 0, 8, 32, 2, 32, 0, 4, 114, 2, 115, 97, 110, 116, 3, 87, 13, 34, 0, 114, 2, 118, 101, 116, 0, 114, 8, 2, 101, 21, 0, 107, 114, 101, 2, 116, 97, 3, 87, 13, 49, 34, 13, 0, 107, 114, 101, 116, 97, 114, 105, 2, 17, 65, 3, 87, 13, 49, 34, 13, 47, 2, 35, 34, 2, 37, 0, 108, 101, 1, 111, 110, 2, 32, 3, 87, 13, 55, 13, 0, 108, 101, 107, 2, 17, 67, 17, 65, 3, 87, 13, 55, 106, 49, 0, 108, 111, 110, 8, 2, 115, 17, 67, 3, 87, 13, 55, 133, 50, 0, 109, 101, 8, 2, 17, 67, 116, 3, 87, 13, 63, 106, 0, 100, 97, 110, 8, 3, 87, 13, 70, 35, 50, 0, 100, 101, 2, 114, 105, 110, 103, 3, 87, 13, 70, 114, 0, 100, 101, 101, 114, 3, 87, 13, 70, 114, 34, 0, 107, 115, 1, 21, 2, 32, 3, 87, 106, 49, 87, 0, 110, 116, 101, 114, 3, 87, 106, 50, 47, 13, 34, 0, 110, 100, 105, 110, 103, 2, 32, 3, 87, 106, 50, 70, 13, 66, 0, 4, 109, 105, 8, 2, 17, 67, 3, 87, 106, 63, 37, 0, 109, 105, 8, 2, 32, 0, 115, 2, 117, 117, 114, 3, 87, 106, 87, 10, 0, 4, 1, 100, 101, 111, 108, 98, 2, 108, 3, 87, 110, 0, 1, 101, 105, 115, 105, 108, 111, 112, 2, 108, 25, 0, 1, 101, 108, 108, 105, 97, 114, 98, 2, 108, 0, 1, 103, 110, 105, 110, 117, 101, 104, 2, 108, 25, 0, 1, 109, 97, 97, 103, 103, 105, 108, 2, 108, 25, 0, 1, 109, 97, 116, 115, 2, 108, 0, 2, 103, 103, 17, 65, 0, 108, 108, 101, 2, 116, 106, 105, 101, 3, 87, 110, 55, 37, 0, 1, 17, 67, 21, 2, 114, 101, 32, 3, 87, 114, 0, 116, 101, 2, 110, 101, 32, 3, 87, 114, 47, 13, 0, 116, 101, 108, 2, 25, 3, 87, 114, 47, 13, 55, 0, 107, 101, 114, 3, 87, 114, 49, 13, 34, 0, 110, 105, 110, 103, 3, 87, 114, 50, 13, 66, 0, 110, 117, 8, 2, 17, 67, 17, 67, 3, 87, 114, 50, 116, 0, 109, 101, 108, 2, 21, 3, 87, 114, 63, 13, 55, 0, 98, 114, 97, 8, 3, 87, 114, 69, 34, 35, 0, 100, 101, 8, 3, 87, 114, 70, 13, 0, 7, 6, 115, 116, 0, 105, 101, 115, 1, 21, 3, 8, 87, 47, 2, 37, 87, 0, 101, 109, 112, 101, 114, 97, 109, 101, 1, 21, 3, 87, 10, 47, 106, 63, 48, 14, 34, 2, 35, 63, 106, 0, 4, 97, 2, 116, 117, 116, 17, 65, 3, 87, 47, 2, 35, 0, 97, 8, 2, 98, 105, 21, 0, 97, 110, 2, 100, 97, 3, 87, 47, 2, 35, 50, 0, 4, 97, 110, 100, 2, 104, 111, 117, 100, 101, 3, 87, 47, 2, 35, 50, 47, 0, 97, 110, 100, 2, 118, 97, 115, 116, 105, 0, 97, 110, 100, 101, 114, 100, 2, 21, 3, 87, 47, 2, 35, 50, 70, 13, 34, 47, 0, 97, 108, 97, 103, 2, 17, 67, 105, 101, 116, 3, 87, 47, 2, 35, 55, 2, 35, 134, 0, 105, 101, 2, 98, 101, 117, 3, 87, 47, 2, 37, 0, 105, 108, 101, 2, 116, 3, 87, 47, 2, 37, 55, 106, 0, 101, 8, 2, 114, 105, 3, 87, 47, 2, 106, 0, 101, 108, 108, 101, 110, 2, 98, 111, 115, 3, 87, 47, 2, 110, 55, 13, 63, 0, 101, 114, 101, 111, 2, 116, 105, 3, 87, 47, 2, 114, 34, 2, 37, 2, 40, 0, 101, 114, 111, 2, 195, 175, 101, 100, 3, 87, 47, 2, 114, 34, 2, 40, 38, 0, 117, 2, 100, 101, 3, 87, 47, 2, 116, 0, 117, 100, 101, 110, 2, 116, 3, 87, 47, 2, 116, 70, 106, 50, 0, 111, 117, 116, 2, 109, 111, 101, 100, 105, 3, 87, 47, 2, 118, 47, 0, 105, 101, 107, 1, 26, 21, 3, 87, 47, 6, 37, 49, 0, 101, 1, 21, 2, 108, 108, 101, 110, 3, 87, 47, 6, 110, 0, 101, 114, 114, 101, 116, 106, 105, 101, 3, 87, 47, 6, 110, 34, 37, 78, 37, 0, 97, 116, 105, 101, 115, 3, 87, 47, 6, 113, 47, 37, 87, 0, 121, 102, 103, 101, 2, 21, 14, 128, 132, 134, 3, 87, 47, 6, 121, 81, 134, 13, 0, 97, 97, 116, 8, 2, 115, 3, 87, 47, 7, 113, 47, 0, 4, 101, 1, 17, 67, 21, 2, 109, 97, 110, 3, 87, 47, 13, 0, 101, 1, 21, 2, 108, 121, 25, 0, 101, 1, 32, 15, 0, 101, 1, 114, 170, 195, 2, 32, 14, 128, 128, 131, 0, 101, 2, 108, 97, 97, 110, 0, 101, 2, 108, 97, 110, 100, 0, 101, 2, 108, 108, 97, 115, 105, 101, 0, 101, 2, 109, 97, 97, 116, 0, 101, 2, 109, 97, 114, 107, 0, 101, 8, 2, 102, 97, 97, 110, 0, 105, 2, 112, 117, 108, 17, 65, 0, 101, 114, 114, 101, 105, 3, 87, 47, 13, 34, 6, 121, 0, 101, 110, 101, 1, 105, 114, 104, 99, 2, 32, 3, 87, 47, 13, 50, 13, 0, 4, 101, 108, 1, 21, 2, 105, 17, 67, 3, 87, 47, 13, 55, 0, 101, 108, 1, 21, 2, 111, 0, 101, 108, 1, 110, 117, 107, 2, 100, 0, 101, 108, 1, 111, 112, 97, 0, 101, 108, 1, 114, 111, 119, 0, 101, 108, 8, 101, 110, 0, 105, 108, 2, 115, 119, 121, 0, 101, 108, 105, 107, 1, 21, 3, 87, 47, 13, 55, 13, 49, 0, 105, 109, 117, 2, 108, 17, 65, 3, 87, 47, 13, 63, 2, 116, 0, 114, 97, 116, 101, 103, 105, 101, 3, 87, 47, 34, 2, 35, 47, 13, 134, 37, 0, 114, 97, 116, 101, 103, 105, 101, 115, 3, 87, 47, 34, 2, 35, 47, 114, 134, 37, 87, 0, 114, 97, 98, 2, 111, 116, 111, 109, 105, 3, 87, 47, 34, 2, 35, 69, 0, 114, 97, 102, 2, 114, 101, 103, 116, 101, 3, 87, 47, 34, 2, 35, 81, 0, 114, 117, 107, 116, 2, 117, 3, 87, 47, 34, 2, 109, 49, 47, 0, 114, 117, 107, 116, 117, 2, 114, 101, 114, 17, 65, 110, 3, 87, 47, 34, 2, 109, 49, 47, 2, 116, 0, 114, 105, 103, 2, 110, 105, 101, 110, 3, 87, 47, 34, 13, 134, 0, 4, 114, 97, 110, 100, 2, 111, 3, 87, 47, 34, 35, 50, 47, 10, 0, 114, 97, 110, 100, 8, 2, 101, 114, 17, 67, 0, 114, 101, 115, 2, 32, 3, 87, 47, 34, 106, 87, 0, 114, 97, 97, 116, 1, 21, 2, 32, 14, 129, 128, 134, 3, 87, 47, 34, 113, 47, 0, 114, 101, 107, 101, 3, 87, 47, 34, 114, 49, 13, 0, 97, 112, 8, 2, 17, 65, 3, 87, 47, 35, 48, 10, 0, 97, 109, 105, 110, 97, 3, 87, 47, 35, 63, 2, 37, 50, 2, 35, 0, 101, 2, 109, 3, 87, 47, 106, 0, 101, 110, 2, 115, 105, 108, 3, 87, 47, 106, 50, 0, 101, 109, 112, 101, 108, 3, 87, 47, 106, 63, 48, 13, 55, 0, 111, 114, 109, 3, 87, 47, 108, 34, 14, 63, 0, 111, 107, 2, 17, 65, 3, 87, 47, 108, 49, 19, 0, 111, 102, 2, 111, 3, 87, 47, 108, 81, 19, 0, 4, 101, 1, 100, 110, 2, 114, 3, 87, 47, 110, 0, 101, 1, 101, 101, 115, 2, 114, 0, 101, 1, 101, 105, 112, 101, 115, 2, 114, 0, 101, 1, 101, 105, 115, 105, 118, 2, 114, 0, 101, 1, 101, 114, 17, 65, 109, 2, 114, 0, 101, 1, 101, 119, 101, 115, 2, 114, 0, 101, 1, 103, 114, 101, 119, 100, 2, 114, 0, 101, 1, 107, 99, 111, 114, 2, 114, 0, 101, 1, 108, 97, 97, 119, 100, 2, 114, 0, 101, 1, 108, 101, 17, 67, 11, 2, 114, 0, 101, 1, 108, 111, 111, 112, 2, 114, 0, 101, 1, 109, 97, 97, 115, 2, 108, 108, 101, 110, 0, 101, 1, 109, 108, 105, 102, 2, 114, 0, 101, 1, 110, 101, 101, 116, 2, 108, 108, 101, 110, 0, 101, 1, 112, 111, 112, 2, 114, 0, 101, 1, 114, 101, 112, 117, 115, 2, 114, 0, 101, 1, 116, 101, 17, 67, 2, 114, 25, 0, 101, 1, 116, 110, 101, 114, 112, 2, 114, 0, 101, 2, 108, 0, 4, 101, 114, 1, 103, 101, 119, 2, 119, 101, 3, 87, 47, 110, 34, 0, 101, 114, 2, 45, 104, 111, 116, 101, 108, 0, 101, 114, 2, 104, 111, 116, 101, 108, 0, 101, 114, 2, 119, 101, 110, 100, 0, 101, 114, 8, 0, 101, 114, 114, 101, 3, 87, 47, 110, 34, 13, 0, 101, 114, 107, 2, 32, 3, 87, 47, 110, 34, 49, 0, 101, 114, 107, 116, 1, 21, 3, 87, 47, 110, 34, 49, 47, 0, 101, 114, 102, 2, 25, 3, 87, 47, 110, 34, 81, 0, 101, 114, 119, 101, 110, 115, 2, 21, 3, 87, 47, 110, 34, 82, 13, 50, 87, 10, 0, 101, 108, 101, 1, 10, 2, 102, 111, 3, 87, 47, 110, 55, 13, 0, 4, 101, 114, 1, 107, 105, 119, 107, 3, 87, 47, 111, 34, 0, 101, 114, 1, 107, 111, 98, 2, 116, 0, 101, 114, 1, 107, 114, 97, 118, 2, 116, 106, 105, 101, 0, 101, 114, 1, 112, 97, 97, 107, 115, 2, 116, 106, 105, 101, 0, 97, 2, 100, 105, 111, 110, 3, 87, 47, 113, 0, 97, 112, 101, 108, 3, 87, 47, 113, 48, 13, 55, 0, 101, 2, 107, 101, 32, 3, 87, 47, 114, 0, 101, 107, 101, 2, 108, 105, 103, 3, 87, 47, 114, 49, 13, 0, 101, 107, 101, 114, 1, 17, 67, 3, 87, 47, 114, 49, 13, 34, 0, 101, 110, 101, 2, 32, 3, 87, 47, 114, 50, 13, 0, 101, 108, 101, 2, 32, 3, 87, 47, 114, 55, 13, 0, 101, 108, 101, 114, 3, 87, 47, 114, 55, 13, 34, 0, 4, 101, 100, 101, 2, 17, 67, 3, 87, 47, 114, 70, 13, 0, 101, 100, 101, 2, 32, 0, 101, 100, 105, 110, 103, 3, 87, 47, 114, 70, 13, 66, 0, 101, 119, 101, 108, 3, 87, 47, 114, 82, 13, 55, 0, 111, 116, 101, 110, 101, 3, 87, 47, 115, 47, 13, 50, 13, 0, 111, 107, 2, 101, 3, 87, 47, 115, 49, 0, 7, 6, 116, 101, 0, 109, 112, 101, 114, 97, 3, 4, 47, 106, 63, 48, 14, 34, 2, 35, 0, 2, 111, 17, 67, 3, 47, 2, 37, 2, 0, 97, 2, 116, 114, 97, 3, 47, 2, 37, 2, 35, 0, 97, 116, 101, 114, 3, 47, 2, 37, 113, 47, 13, 34, 0, 114, 97, 2, 112, 17, 65, 3, 47, 2, 106, 34, 2, 35, 0, 114, 97, 1, 111, 2, 112, 17, 65, 3, 47, 2, 106, 34, 2, 35, 6, 0, 114, 114, 111, 114, 2, 105, 115, 3, 47, 2, 106, 34, 2, 40, 34, 0, 4, 107, 115, 2, 116, 105, 101, 108, 3, 47, 2, 106, 49, 87, 0, 107, 115, 8, 2, 116, 117, 0, 4, 110, 2, 111, 116, 111, 109, 105, 101, 3, 47, 2, 106, 50, 0, 110, 2, 116, 97, 107, 101, 108, 0, 110, 2, 116, 111, 111, 110, 0, 110, 100, 101, 110, 115, 3, 47, 2, 106, 50, 70, 132, 50, 87, 0, 115, 111, 117, 2, 114, 105, 101, 3, 47, 2, 106, 87, 2, 40, 0, 4, 114, 2, 109, 105, 101, 116, 3, 47, 2, 110, 34, 0, 114, 2, 109, 121, 110, 0, 114, 8, 2, 115, 0, 114, 97, 97, 114, 100, 101, 8, 3, 47, 2, 110, 34, 19, 113, 34, 70, 13, 0, 114, 112, 101, 110, 2, 116, 121, 110, 3, 47, 2, 110, 34, 48, 13, 50, 0, 114, 109, 105, 2, 110, 97, 21, 3, 47, 2, 110, 34, 63, 2, 37, 0, 108, 101, 8, 2, 17, 67, 3, 47, 2, 110, 55, 13, 0, 4, 101, 110, 2, 115, 116, 114, 121, 100, 3, 47, 2, 114, 50, 0, 101, 110, 2, 119, 111, 111, 114, 0, 101, 110, 2, 111, 111, 114, 103, 101, 115, 3, 47, 2, 114, 50, 10, 0, 101, 110, 115, 2, 119, 111, 111, 114, 3, 47, 2, 114, 50, 87, 0, 4, 1, 17, 67, 21, 2, 114, 103, 101, 110, 100, 3, 47, 6, 110, 0, 2, 114, 103, 101, 110, 100, 0, 114, 110, 2, 101, 32, 3, 47, 6, 110, 34, 50, 0, 114, 110, 2, 25, 3, 47, 6, 111, 34, 14, 50, 0, 4, 1, 97, 17, 67, 2, 114, 105, 110, 103, 3, 47, 6, 114, 0, 1, 107, 2, 114, 105, 110, 103, 0, 4, 114, 101, 110, 100, 101, 1, 101, 112, 2, 32, 3, 47, 6, 114, 34, 13, 50, 70, 13, 0, 114, 101, 110, 100, 101, 1, 105, 2, 32, 0, 114, 101, 110, 100, 101, 1, 107, 101, 2, 32, 0, 114, 101, 110, 100, 101, 1, 108, 117, 2, 32, 0, 114, 101, 110, 100, 101, 1, 114, 101, 118, 2, 32, 0, 114, 101, 110, 100, 101, 1, 115, 97, 2, 32, 0, 108, 101, 1, 21, 2, 32, 3, 47, 6, 114, 55, 13, 0, 115, 101, 2, 32, 3, 47, 6, 114, 87, 13, 0, 115, 101, 115, 2, 32, 3, 47, 6, 114, 87, 13, 87, 0, 4, 117, 114, 1, 17, 65, 3, 47, 6, 126, 34, 0, 117, 114, 1, 107, 0, 101, 110, 2, 97, 114, 103, 117, 3, 47, 7, 114, 50, 0, 4, 1, 17, 65, 2, 108, 105, 110, 103, 3, 47, 13, 0, 1, 17, 65, 10, 2, 108, 112, 0, 1, 17, 65, 17, 67, 2, 108, 101, 110, 100, 0, 1, 17, 65, 21, 2, 103, 101, 17, 67, 0, 1, 17, 67, 21, 2, 17, 67, 0, 1, 17, 67, 21, 2, 109, 97, 114, 107, 0, 1, 21, 2, 111, 112, 0, 1, 97, 119, 2, 114, 105, 110, 103, 0, 1, 101, 105, 110, 2, 109, 105, 110, 0, 2, 32, 0, 2, 97, 97, 0, 2, 100, 111, 109, 0, 2, 111, 110, 100, 101, 114, 0, 2, 111, 111, 0, 2, 114, 114, 17, 65, 0, 8, 2, 98, 111, 119, 101, 0, 8, 2, 110, 111, 0, 8, 2, 119, 101, 0, 4, 114, 1, 10, 2, 116, 17, 65, 21, 3, 47, 13, 34, 0, 114, 1, 21, 2, 116, 121, 100, 0, 114, 1, 97, 119, 2, 116, 0, 114, 8, 2, 108, 0, 114, 8, 2, 110, 17, 65, 0, 114, 8, 2, 119, 0, 114, 105, 101, 1, 110, 3, 47, 13, 34, 6, 37, 0, 114, 117, 103, 103, 101, 101, 2, 12, 3, 47, 13, 34, 6, 109, 134, 114, 0, 4, 114, 100, 1, 10, 2, 32, 3, 47, 13, 34, 47, 0, 114, 116, 1, 10, 2, 114, 0, 114, 116, 106, 105, 101, 1, 10, 3, 47, 13, 34, 49, 37, 0, 114, 109, 101, 115, 1, 10, 3, 47, 13, 34, 63, 106, 87, 0, 114, 101, 103, 8, 3, 47, 13, 34, 110, 134, 0, 107, 111, 114, 3, 47, 13, 49, 108, 34, 0, 107, 101, 114, 101, 8, 3, 47, 13, 49, 114, 34, 13, 0, 4, 110, 1, 21, 2, 98, 97, 99, 104, 3, 47, 13, 50, 0, 110, 1, 21, 2, 100, 101, 114, 119, 121, 25, 0, 110, 105, 115, 3, 47, 13, 50, 107, 87, 0, 110, 97, 97, 114, 3, 47, 13, 50, 113, 34, 0, 4, 108, 1, 10, 2, 32, 3, 47, 13, 55, 0, 108, 1, 21, 2, 111, 0, 108, 1, 117, 101, 108, 115, 0, 108, 116, 106, 105, 101, 3, 47, 13, 55, 49, 37, 0, 108, 115, 1, 10, 2, 32, 3, 47, 13, 55, 87, 0, 108, 101, 117, 114, 3, 47, 13, 55, 126, 34, 0, 118, 111, 114, 101, 3, 47, 13, 81, 6, 115, 34, 13, 0, 118, 101, 114, 8, 2, 21, 3, 47, 13, 81, 13, 34, 0, 115, 97, 109, 101, 3, 47, 13, 87, 113, 63, 13, 0, 103, 101, 8, 2, 17, 67, 17, 65, 3, 47, 13, 134, 13, 0, 114, 117, 103, 8, 2, 14, 128, 132, 133, 3, 47, 14, 34, 6, 109, 134, 0, 114, 117, 103, 103, 101, 8, 2, 21, 14, 128, 132, 135, 3, 47, 14, 34, 6, 109, 134, 13, 0, 1, 17, 67, 2, 116, 106, 105, 101, 3, 47, 37, 0, 2, 107, 107, 105, 101, 12, 3, 47, 106, 0, 114, 114, 105, 195, 171, 114, 3, 47, 106, 34, 37, 13, 34, 0, 107, 115, 2, 12, 3, 47, 106, 49, 87, 0, 110, 2, 100, 101, 114, 3, 47, 106, 50, 0, 110, 110, 105, 115, 3, 47, 106, 50, 13, 87, 0, 110, 116, 2, 32, 3, 47, 106, 50, 47, 0, 110, 116, 101, 2, 32, 3, 47, 106, 50, 47, 13, 0, 109, 112, 111, 2, 32, 3, 47, 106, 63, 48, 2, 40, 0, 109, 112, 101, 114, 3, 47, 106, 63, 48, 13, 34, 0, 109, 112, 101, 108, 3, 47, 106, 63, 48, 13, 55, 0, 4, 1, 17, 67, 21, 2, 103, 110, 3, 47, 110, 0, 1, 17, 67, 21, 2, 107, 32, 0, 1, 17, 67, 21, 2, 108, 98, 111, 114, 100, 0, 1, 17, 67, 21, 2, 108, 108, 0, 1, 17, 67, 21, 2, 110, 107, 0, 2, 108, 0, 114, 109, 1, 21, 2, 32, 3, 47, 110, 34, 13, 63, 0, 114, 114, 97, 2, 99, 3, 47, 110, 34, 35, 0, 114, 116, 1, 10, 3, 47, 110, 34, 47, 0, 114, 109, 101, 1, 21, 2, 32, 3, 47, 110, 34, 63, 13, 0, 114, 116, 105, 8, 2, 17, 65, 25, 3, 47, 110, 34, 89, 57, 0, 108, 1, 101, 103, 2, 32, 3, 47, 110, 55, 0, 4, 108, 101, 1, 21, 2, 102, 111, 3, 47, 110, 55, 13, 0, 108, 101, 1, 21, 2, 103, 114, 97, 0, 108, 101, 107, 115, 3, 47, 110, 55, 106, 49, 87, 0, 4, 114, 116, 1, 115, 10, 2, 97, 97, 110, 3, 47, 111, 34, 47, 0, 114, 116, 1, 115, 10, 2, 101, 32, 0, 4, 1, 21, 2, 102, 105, 101, 32, 3, 47, 114, 0, 1, 21, 2, 108, 101, 114, 0, 1, 110, 105, 115, 2, 116, 105, 0, 1, 110, 121, 109, 2, 114, 105, 110, 103, 0, 1, 115, 2, 107, 105, 110, 103, 0, 4, 114, 105, 110, 103, 1, 115, 101, 108, 111, 109, 3, 47, 114, 34, 13, 66, 0, 114, 105, 110, 103, 8, 0, 4, 107, 1, 21, 2, 101, 110, 3, 47, 114, 49, 0, 107, 1, 112, 97, 2, 17, 65, 0, 107, 101, 110, 2, 17, 65, 3, 47, 114, 49, 13, 50, 0, 108, 101, 114, 8, 3, 47, 114, 55, 13, 34, 0, 119, 101, 2, 32, 3, 47, 114, 82, 13, 0, 119, 101, 110, 115, 8, 3, 47, 114, 82, 13, 50, 87, 0, 115, 105, 2, 115, 3, 47, 114, 87, 13, 0, 105, 107, 101, 110, 3, 47, 121, 49, 13, 50, 0, 7, 6, 116, 114, 0, 101, 107, 101, 110, 3, 47, 10, 34, 114, 49, 13, 50, 0, 97, 2, 106, 101, 107, 3, 47, 34, 2, 35, 0, 97, 112, 2, 115, 111, 101, 3, 47, 34, 2, 35, 48, 0, 97, 107, 8, 2, 116, 97, 3, 47, 34, 2, 35, 49, 0, 4, 97, 110, 115, 8, 2, 21, 14, 128, 132, 133, 3, 47, 34, 2, 35, 50, 87, 0, 97, 110, 115, 8, 2, 97, 107, 115, 105, 101, 0, 97, 110, 115, 101, 110, 100, 101, 110, 116, 2, 17, 65, 3, 47, 34, 2, 35, 50, 87, 2, 106, 50, 70, 2, 106, 50, 47, 0, 97, 110, 115, 105, 116, 111, 3, 47, 34, 2, 35, 50, 87, 37, 47, 2, 40, 0, 97, 110, 115, 112, 97, 2, 114, 97, 110, 116, 3, 47, 34, 2, 35, 50, 87, 48, 13, 0, 97, 110, 115, 112, 111, 114, 116, 3, 47, 34, 2, 35, 50, 87, 48, 108, 34, 47, 0, 97, 110, 115, 105, 115, 116, 111, 114, 3, 47, 34, 2, 35, 50, 87, 107, 87, 47, 13, 34, 0, 97, 100, 105, 2, 115, 105, 3, 47, 34, 2, 35, 70, 37, 0, 97, 103, 2, 101, 100, 3, 47, 34, 2, 35, 134, 0, 105, 2, 111, 109, 102, 3, 47, 34, 2, 37, 0, 105, 111, 109, 102, 2, 97, 110, 116, 3, 47, 34, 2, 37, 2, 108, 63, 81, 0, 4, 111, 2, 116, 115, 101, 101, 114, 3, 47, 34, 2, 108, 0, 111, 2, 116, 115, 101, 114, 105, 110, 103, 0, 4, 111, 109, 8, 2, 98, 3, 47, 34, 2, 108, 63, 0, 111, 109, 8, 2, 112, 101, 116, 0, 111, 103, 108, 111, 2, 100, 105, 101, 3, 47, 34, 2, 108, 134, 55, 2, 40, 0, 117, 2, 115, 116, 101, 101, 3, 47, 34, 2, 109, 0, 97, 103, 101, 2, 111, 116, 111, 109, 105, 3, 47, 34, 2, 113, 134, 2, 37, 0, 105, 115, 101, 1, 21, 2, 32, 3, 47, 34, 6, 37, 87, 13, 0, 105, 115, 101, 115, 1, 21, 2, 32, 3, 47, 34, 6, 37, 87, 13, 87, 0, 101, 101, 114, 1, 21, 3, 47, 34, 6, 114, 34, 0, 111, 117, 115, 115, 101, 97, 117, 3, 47, 34, 7, 40, 12, 87, 118, 0, 105, 8, 2, 98, 117, 3, 47, 34, 13, 0, 105, 108, 2, 106, 111, 101, 110, 3, 47, 34, 13, 55, 0, 105, 98, 117, 8, 2, 110, 97, 3, 47, 34, 13, 69, 2, 116, 0, 97, 112, 2, 111, 114, 114, 3, 47, 34, 35, 48, 10, 0, 97, 119, 2, 97, 3, 47, 34, 35, 82, 6, 0, 105, 111, 2, 32, 3, 47, 34, 37, 12, 40, 0, 101, 102, 2, 97, 102, 115, 3, 47, 34, 106, 81, 10, 0, 105, 118, 105, 97, 3, 47, 34, 107, 82, 37, 57, 2, 35, 0, 101, 2, 107, 3, 47, 34, 110, 0, 101, 107, 107, 101, 114, 3, 47, 34, 110, 49, 13, 34, 0, 97, 110, 115, 8, 2, 100, 97, 110, 115, 3, 47, 34, 113, 50, 87, 0, 101, 101, 114, 1, 21, 2, 17, 65, 3, 47, 34, 114, 34, 0, 101, 100, 105, 110, 103, 1, 10, 3, 47, 34, 114, 70, 13, 66, 0, 4, 117, 2, 112, 114, 111, 106, 101, 107, 3, 47, 34, 116, 0, 117, 2, 115, 112, 105, 101, 195, 171, 0, 117, 107, 2, 97, 97, 116, 115, 3, 47, 34, 116, 49, 0, 101, 110, 115, 2, 32, 3, 47, 34, 132, 50, 87, 0, 7, 6, 117, 105, 0, 116, 2, 100, 97, 103, 101, 110, 3, 2, 125, 0, 4, 116, 2, 98, 117, 110, 100, 3, 2, 125, 47, 0, 116, 2, 100, 114, 117, 107, 0, 116, 2, 104, 117, 105, 115, 105, 103, 0, 116, 2, 109, 117, 110, 116, 101, 110, 0, 116, 2, 115, 108, 117, 105, 116, 101, 110, 0, 116, 2, 115, 112, 97, 116, 116, 0, 116, 2, 115, 116, 101, 107, 101, 110, 0, 116, 2, 118, 111, 101, 114, 98, 97, 0, 116, 2, 118, 111, 101, 114, 105, 103, 0, 116, 2, 119, 105, 115, 98, 97, 0, 116, 2, 101, 101, 110, 3, 2, 125, 47, 10, 0, 116, 101, 101, 110, 2, 108, 111, 112, 3, 2, 125, 47, 10, 2, 114, 50, 0, 116, 109, 101, 2, 107, 97, 97, 114, 3, 2, 125, 47, 63, 13, 0, 116, 115, 116, 97, 97, 110, 2, 17, 67, 3, 2, 125, 47, 87, 47, 113, 50, 0, 116, 115, 112, 114, 101, 101, 107, 108, 3, 2, 125, 47, 87, 48, 34, 114, 49, 55, 0, 116, 115, 112, 97, 116, 108, 105, 107, 3, 2, 125, 47, 87, 48, 35, 47, 55, 13, 49, 0, 116, 115, 108, 117, 105, 116, 108, 105, 107, 3, 2, 125, 47, 87, 55, 125, 47, 55, 13, 49, 0, 116, 115, 111, 110, 100, 101, 114, 108, 105, 2, 107, 3, 2, 125, 47, 87, 108, 50, 13, 34, 55, 13, 0, 116, 101, 105, 110, 100, 101, 108, 105, 3, 2, 125, 47, 121, 50, 70, 13, 55, 13, 0, 116, 8, 2, 21, 14, 128, 132, 131, 3, 6, 125, 47, 0, 116, 103, 101, 8, 2, 21, 14, 128, 132, 133, 3, 6, 125, 47, 134, 13, 0, 116, 103, 101, 101, 2, 12, 3, 6, 125, 47, 134, 114, 0, 4, 3, 125, 0, 2, 116, 106, 105, 101, 0, 101, 2, 17, 67, 3, 125, 13, 0, 4, 116, 2, 100, 114, 117, 107, 32, 24, 3, 125, 47, 0, 116, 2, 100, 114, 117, 107, 107, 105, 110, 103, 32, 0, 116, 2, 100, 114, 117, 107, 107, 105, 110, 103, 115, 0, 116, 2, 101, 101, 110, 108, 111, 111, 112, 3, 125, 47, 10, 0, 116, 101, 114, 3, 125, 47, 13, 34, 0, 116, 105, 110, 103, 3, 125, 47, 13, 66, 0, 116, 107, 101, 2, 110, 3, 125, 47, 49, 106, 0, 116, 115, 116, 97, 97, 110, 2, 114, 3, 125, 47, 87, 47, 113, 50, 0, 116, 103, 101, 119, 101, 114, 3, 125, 47, 134, 2, 114, 82, 13, 34, 0, 116, 103, 101, 119, 101, 114, 112, 3, 125, 47, 134, 13, 82, 110, 34, 48, 0, 116, 103, 101, 119, 101, 114, 107, 3, 125, 47, 134, 13, 82, 110, 34, 49, 0, 7, 6, 118, 101, 0, 4, 1, 21, 2, 32, 3, 21, 0, 115, 1, 17, 65, 2, 32, 0, 116, 101, 2, 114, 97, 3, 81, 2, 106, 47, 13, 0, 114, 116, 105, 2, 107, 97, 3, 81, 2, 110, 34, 47, 2, 37, 0, 4, 101, 108, 2, 100, 117, 105, 100, 3, 81, 2, 114, 55, 0, 101, 108, 2, 106, 97, 114, 0, 101, 108, 2, 115, 21, 21, 0, 114, 2, 107, 121, 107, 101, 114, 3, 81, 6, 111, 34, 0, 114, 103, 101, 115, 111, 103, 8, 3, 81, 6, 111, 34, 38, 134, 13, 87, 108, 134, 0, 114, 101, 110, 100, 2, 32, 3, 81, 6, 114, 34, 13, 50, 47, 0, 114, 101, 110, 100, 101, 3, 81, 6, 114, 34, 13, 50, 70, 13, 0, 114, 105, 110, 103, 3, 81, 6, 114, 34, 13, 66, 0, 108, 101, 3, 81, 6, 114, 55, 13, 0, 114, 115, 102, 8, 3, 81, 7, 110, 34, 87, 81, 0, 114, 2, 115, 112, 114, 105, 110, 103, 3, 81, 7, 111, 34, 0, 4, 114, 3, 81, 13, 34, 0, 114, 2, 102, 108, 101, 110, 17, 67, 0, 114, 2, 102, 114, 105, 115, 0, 114, 2, 118, 101, 108, 17, 65, 0, 114, 8, 2, 21, 14, 128, 132, 131, 0, 114, 97, 110, 116, 2, 119, 3, 81, 13, 34, 2, 35, 50, 47, 0, 114, 111, 110, 103, 101, 8, 2, 21, 14, 128, 132, 135, 3, 81, 13, 34, 6, 129, 66, 134, 13, 0, 4, 114, 97, 110, 116, 2, 119, 111, 111, 114, 100, 32, 3, 81, 13, 34, 10, 35, 50, 47, 0, 114, 97, 110, 116, 2, 119, 111, 111, 114, 100, 101, 32, 24, 0, 114, 101, 114, 2, 105, 110, 103, 3, 81, 13, 34, 10, 114, 34, 0, 114, 116, 101, 2, 108, 3, 81, 13, 34, 47, 110, 0, 114, 116, 101, 114, 2, 17, 65, 3, 81, 13, 34, 47, 114, 34, 0, 114, 108, 97, 110, 103, 115, 2, 97, 3, 81, 13, 34, 55, 6, 35, 66, 87, 0, 114, 98, 101, 116, 101, 3, 81, 13, 34, 69, 6, 114, 47, 13, 0, 114, 98, 121, 3, 81, 13, 34, 69, 121, 0, 4, 114, 102, 2, 105, 3, 81, 13, 34, 81, 0, 114, 102, 2, 114, 111, 109, 0, 114, 102, 8, 2, 108, 111, 117, 0, 114, 102, 8, 2, 111, 0, 114, 118, 101, 114, 115, 105, 110, 103, 3, 81, 13, 34, 81, 6, 110, 34, 87, 13, 66, 0, 114, 102, 121, 110, 3, 81, 13, 34, 81, 6, 121, 50, 0, 114, 115, 116, 101, 114, 1, 21, 2, 107, 3, 81, 13, 34, 87, 47, 110, 34, 0, 114, 111, 110, 100, 101, 114, 115, 116, 101, 2, 108, 3, 81, 13, 34, 108, 50, 13, 34, 87, 47, 6, 110, 0, 114, 103, 101, 116, 101, 3, 81, 13, 34, 134, 6, 114, 47, 13, 0, 114, 103, 101, 119, 101, 8, 3, 81, 13, 34, 134, 114, 82, 13, 0, 4, 110, 2, 100, 117, 115, 105, 101, 3, 81, 13, 50, 0, 110, 2, 121, 110, 0, 2, 115, 116, 3, 81, 106, 0, 116, 8, 2, 17, 65, 3, 81, 106, 47, 10, 0, 2, 108, 3, 81, 110, 0, 114, 2, 103, 101, 115, 105, 103, 3, 81, 110, 34, 0, 4, 114, 102, 3, 81, 110, 34, 81, 0, 114, 102, 2, 21, 0, 114, 119, 101, 2, 32, 3, 81, 110, 34, 82, 13, 0, 114, 119, 101, 114, 2, 32, 3, 81, 110, 34, 82, 13, 34, 0, 114, 119, 101, 114, 121, 3, 81, 110, 34, 82, 13, 34, 2, 121, 0, 114, 119, 101, 114, 115, 3, 81, 110, 34, 82, 13, 34, 87, 0, 4, 114, 115, 1, 21, 2, 32, 3, 81, 110, 34, 87, 0, 114, 115, 1, 21, 2, 101, 32, 0, 114, 115, 2, 100, 0, 114, 115, 2, 107, 117, 110, 115, 0, 114, 115, 2, 114, 0, 114, 115, 2, 118, 0, 114, 115, 8, 2, 98, 0, 114, 115, 101, 1, 17, 67, 2, 32, 3, 81, 110, 34, 87, 13, 0, 108, 100, 2, 17, 67, 3, 81, 110, 55, 47, 0, 4, 108, 100, 2, 101, 107, 115, 3, 81, 110, 55, 47, 10, 0, 108, 100, 2, 111, 0, 4, 103, 2, 101, 101, 110, 3, 81, 110, 134, 10, 0, 103, 2, 111, 0, 4, 114, 1, 17, 67, 21, 2, 32, 3, 81, 111, 34, 0, 114, 2, 114, 101, 105, 107, 0, 114, 2, 115, 105, 101, 32, 0, 114, 2, 115, 105, 101, 115, 32, 0, 114, 108, 97, 110, 103, 115, 8, 3, 81, 111, 34, 55, 35, 66, 87, 0, 4, 114, 115, 2, 107, 97, 108, 17, 67, 3, 81, 111, 34, 87, 0, 114, 115, 2, 112, 97, 110, 111, 114, 0, 114, 115, 2, 97, 108, 98, 117, 109, 3, 81, 111, 34, 87, 10, 0, 114, 115, 101, 2, 98, 3, 81, 111, 34, 87, 13, 0, 114, 103, 101, 2, 115, 116, 114, 101, 107, 3, 81, 111, 34, 134, 13, 0, 4, 114, 101, 2, 32, 3, 81, 114, 34, 13, 0, 114, 101, 2, 98, 0, 114, 101, 2, 100, 111, 0, 114, 101, 2, 104, 0, 114, 101, 2, 107, 0, 114, 101, 2, 109, 0, 114, 101, 2, 115, 116, 111, 0, 114, 101, 2, 118, 0, 4, 116, 111, 8, 2, 114, 101, 103, 3, 81, 114, 47, 2, 40, 0, 116, 111, 8, 2, 115, 116, 101, 109, 0, 116, 101, 2, 29, 3, 81, 114, 47, 13, 0, 116, 101, 114, 2, 25, 3, 81, 114, 47, 13, 34, 0, 108, 1, 21, 2, 17, 65, 3, 81, 114, 55, 0, 110, 2, 115, 116, 101, 114, 3, 81, 132, 50, 0, 114, 105, 102, 105, 2, 21, 3, 82, 2, 106, 34, 2, 37, 81, 2, 37, 0, 110, 2, 100, 101, 116, 116, 97, 3, 82, 2, 106, 50, 0, 4, 114, 2, 98, 97, 97, 108, 3, 82, 2, 110, 34, 0, 114, 2, 98, 97, 108, 17, 65, 0, 114, 115, 105, 102, 105, 2, 17, 67, 3, 82, 2, 110, 34, 87, 2, 37, 81, 2, 37, 0, 114, 115, 101, 1, 17, 65, 25, 2, 32, 3, 82, 6, 110, 34, 87, 13, 0, 114, 97, 110, 100, 97, 3, 82, 13, 34, 35, 50, 70, 35, 0, 114, 98, 101, 110, 97, 3, 82, 13, 34, 69, 114, 50, 2, 35, 0, 110, 101, 2, 115, 105, 17, 65, 3, 82, 13, 50, 37, 12, 0, 114, 1, 111, 114, 116, 2, 25, 3, 82, 110, 34, 0, 2, 110, 117, 115, 3, 82, 114, 0, 7, 6, 118, 111, 0, 114, 2, 32, 3, 21, 0, 4, 2, 107, 97, 3, 81, 2, 40, 0, 8, 2, 109, 101, 0, 2, 108, 17, 67, 3, 81, 2, 108, 0, 4, 108, 2, 98, 114, 105, 110, 103, 3, 81, 2, 108, 55, 0, 108, 2, 103, 114, 111, 101, 105, 0, 108, 2, 107, 111, 109, 101, 0, 108, 2, 101, 105, 110, 100, 105, 103, 3, 81, 2, 108, 55, 10, 0, 108, 108, 101, 2, 100, 105, 103, 3, 81, 2, 108, 55, 114, 0, 4, 111, 114, 2, 107, 111, 109, 98, 97, 3, 81, 2, 115, 34, 0, 111, 114, 2, 115, 105, 101, 0, 111, 114, 2, 115, 112, 111, 101, 100, 105, 0, 111, 114, 8, 2, 100, 101, 108, 105, 103, 0, 111, 114, 8, 2, 107, 111, 109, 17, 65, 0, 4, 111, 114, 2, 97, 102, 103, 97, 97, 110, 3, 81, 2, 115, 34, 10, 0, 111, 114, 116, 2, 100, 117, 114, 101, 110, 0, 111, 114, 116, 2, 118, 21, 21, 3, 81, 2, 115, 34, 47, 0, 111, 114, 119, 97, 97, 114, 100, 101, 2, 32, 3, 81, 2, 115, 34, 82, 113, 34, 70, 13, 0, 111, 114, 115, 116, 101, 100, 101, 108, 105, 2, 107, 3, 81, 2, 115, 34, 87, 47, 114, 70, 13, 55, 13, 0, 111, 114, 115, 107, 114, 105, 102, 116, 101, 108, 105, 2, 107, 3, 81, 2, 115, 34, 87, 49, 34, 107, 81, 47, 13, 55, 13, 0, 111, 103, 2, 100, 121, 3, 81, 2, 115, 134, 0, 101, 114, 105, 103, 1, 21, 3, 81, 6, 40, 34, 13, 134, 0, 108, 111, 112, 3, 81, 6, 108, 55, 10, 108, 48, 0, 114, 101, 110, 3, 81, 6, 115, 34, 13, 50, 0, 111, 114, 98, 101, 8, 2, 21, 14, 128, 132, 134, 3, 81, 6, 115, 34, 69, 13, 0, 111, 114, 103, 101, 8, 2, 21, 14, 128, 132, 134, 3, 81, 6, 115, 34, 134, 13, 0, 108, 2, 109, 97, 103, 3, 81, 7, 108, 55, 0, 4, 2, 108, 108, 17, 65, 32, 3, 81, 108, 0, 2, 108, 108, 101, 114, 0, 114, 109, 3, 81, 108, 34, 13, 63, 0, 114, 115, 116, 105, 2, 110, 3, 81, 108, 34, 87, 47, 6, 107, 0, 4, 108, 2, 98, 3, 81, 108, 55, 0, 108, 2, 103, 0, 108, 2, 104, 111, 117, 32, 0, 108, 2, 109, 97, 97, 110, 0, 108, 2, 109, 97, 110, 101, 0, 108, 2, 112, 114, 111, 112, 0, 108, 2, 114, 0, 108, 2, 115, 105, 17, 67, 0, 108, 2, 115, 116, 101, 32, 0, 108, 2, 115, 116, 111, 0, 108, 8, 2, 115, 107, 0, 108, 108, 101, 115, 2, 32, 3, 81, 108, 55, 13, 87, 0, 108, 116, 121, 100, 115, 3, 81, 108, 55, 47, 121, 47, 87, 0, 108, 107, 3, 81, 108, 55, 49, 0, 108, 107, 101, 3, 81, 108, 55, 49, 13, 0, 108, 119, 97, 115, 115, 101, 3, 81, 108, 55, 82, 6, 35, 87, 13, 0, 108, 108, 2, 101, 110, 103, 116, 101, 3, 81, 108, 55, 106, 0, 4, 111, 114, 2, 115, 107, 3, 81, 115, 34, 0, 111, 114, 2, 116, 114, 97, 112, 0, 111, 114, 2, 116, 114, 101, 107, 0, 111, 114, 8, 2, 98, 101, 101, 12, 0, 111, 114, 2, 17, 65, 3, 81, 115, 34, 10, 0, 111, 114, 117, 105, 116, 8, 3, 81, 115, 34, 10, 6, 125, 47, 0, 111, 114, 98, 97, 114, 3, 81, 115, 34, 69, 6, 113, 34, 0, 111, 114, 119, 97, 97, 114, 100, 101, 2, 32, 24, 3, 81, 115, 34, 82, 113, 34, 70, 13, 0, 111, 114, 115, 112, 101, 2, 108, 25, 3, 81, 115, 34, 87, 48, 6, 110, 0, 111, 114, 117, 105, 116, 2, 115, 116, 114, 101, 119, 3, 81, 115, 34, 125, 47, 6, 0, 108, 117, 109, 101, 3, 82, 2, 108, 55, 116, 63, 13, 0, 100, 107, 97, 3, 82, 108, 47, 49, 35, 0, 7, 6, 119, 101, 0, 8, 2, 108, 108, 21, 21, 3, 82, 2, 110, 0, 114, 107, 2, 115, 116, 101, 108, 108, 105, 3, 82, 2, 110, 34, 49, 0, 4, 108, 2, 115, 107, 97, 112, 101, 3, 82, 2, 110, 55, 0, 108, 2, 115, 112, 114, 101, 107, 101, 110, 0, 108, 2, 119, 105, 108, 0, 108, 8, 2, 114, 0, 108, 8, 2, 118, 0, 108, 8, 2, 101, 100, 101, 108, 3, 82, 2, 110, 55, 10, 0, 108, 98, 101, 104, 97, 97, 103, 108, 105, 107, 3, 82, 2, 110, 55, 69, 13, 105, 113, 134, 55, 13, 49, 0, 101, 2, 109, 111, 101, 100, 105, 3, 82, 2, 114, 0, 4, 101, 114, 2, 98, 97, 114, 115, 116, 3, 82, 2, 114, 34, 0, 101, 114, 2, 104, 111, 117, 0, 101, 114, 2, 107, 97, 97, 116, 115, 0, 101, 114, 2, 108, 101, 103, 0, 101, 114, 2, 108, 195, 170, 0, 101, 114, 2, 115, 116, 97, 97, 110, 0, 101, 114, 2, 115, 116, 114, 101, 119, 0, 101, 116, 2, 103, 105, 101, 114, 105, 103, 3, 82, 2, 114, 47, 0, 100, 101, 114, 2, 118, 97, 3, 82, 2, 114, 70, 13, 34, 0, 107, 107, 101, 110, 100, 1, 21, 3, 82, 6, 106, 49, 13, 50, 47, 0, 107, 107, 101, 110, 100, 101, 1, 21, 3, 82, 6, 106, 49, 13, 50, 70, 13, 0, 110, 100, 105, 103, 1, 21, 3, 82, 6, 106, 50, 70, 13, 134, 0, 103, 103, 101, 8, 2, 17, 67, 21, 14, 128, 132, 133, 3, 82, 6, 110, 134, 13, 0, 115, 105, 103, 104, 101, 105, 100, 1, 21, 3, 82, 6, 114, 87, 13, 134, 121, 47, 0, 114, 1, 17, 65, 2, 17, 65, 17, 65, 3, 82, 13, 34, 0, 110, 101, 1, 10, 2, 32, 3, 82, 13, 50, 13, 0, 110, 115, 1, 101, 110, 3, 82, 13, 50, 87, 0, 1, 17, 67, 21, 2, 116, 25, 3, 82, 106, 0, 4, 100, 1, 21, 2, 115, 116, 114, 3, 82, 106, 47, 0, 100, 1, 115, 2, 17, 67, 0, 100, 121, 119, 101, 114, 3, 82, 106, 47, 121, 82, 13, 34, 0, 110, 8, 2, 97, 17, 67, 3, 82, 106, 50, 19, 0, 98, 8, 3, 82, 106, 69, 0, 100, 100, 1, 115, 2, 21, 3, 82, 106, 70, 0, 114, 112, 3, 82, 110, 34, 48, 0, 114, 107, 1, 116, 3, 82, 110, 34, 49, 0, 114, 119, 101, 108, 3, 82, 110, 34, 82, 13, 55, 0, 108, 2, 118, 97, 97, 114, 116, 3, 82, 110, 55, 0, 108, 102, 2, 32, 3, 82, 110, 55, 81, 0, 4, 103, 1, 21, 2, 32, 3, 82, 110, 134, 0, 103, 1, 114, 111, 111, 112, 115, 0, 103, 1, 25, 2, 111, 3, 82, 110, 134, 10, 0, 101, 114, 1, 115, 17, 65, 2, 32, 3, 82, 114, 34, 0, 101, 114, 8, 2, 115, 112, 3, 82, 114, 34, 6, 0, 114, 101, 1, 101, 103, 3, 82, 114, 34, 13, 0, 114, 105, 110, 103, 1, 17, 67, 21, 2, 32, 3, 82, 114, 34, 13, 66, 0, 116, 101, 110, 2, 17, 67, 3, 82, 114, 47, 13, 50, 0, 107, 101, 8, 2, 17, 67, 3, 82, 114, 49, 13, 0, 101, 115, 1, 21, 2, 32, 3, 82, 114, 87, 0, 105, 102, 101, 2, 108, 3, 82, 121, 81, 13, 0, 110, 115, 1, 115, 101, 101, 102, 3, 82, 132, 50, 87, 0, 7, 6, 97, 0, 4, 1, 17, 67, 2, 17, 67, 115, 105, 101, 114, 3, 2, 35, 0, 1, 17, 67, 2, 114, 105, 110, 97, 0, 1, 17, 67, 2, 116, 101, 114, 105, 110, 103, 0, 1, 17, 67, 11, 2, 32, 0, 1, 17, 67, 17, 65, 2, 32, 0, 1, 17, 67, 21, 2, 116, 105, 101, 102, 0, 1, 17, 67, 21, 2, 116, 105, 101, 119, 101, 0, 1, 21, 2, 17, 67, 105, 115, 97, 115, 105, 101, 0, 1, 21, 2, 17, 67, 105, 115, 101, 101, 114, 0, 1, 21, 2, 17, 67, 105, 115, 101, 114, 105, 110, 103, 0, 1, 98, 10, 2, 32, 0, 1, 100, 2, 103, 111, 103, 103, 101, 110, 0, 1, 100, 10, 2, 32, 0, 1, 105, 2, 32, 0, 1, 105, 2, 116, 105, 101, 17, 67, 0, 1, 106, 2, 112, 97, 110, 0, 1, 109, 21, 2, 116, 105, 101, 107, 0, 1, 109, 114, 10, 2, 32, 0, 1, 114, 10, 2, 32, 0, 1, 116, 10, 2, 32, 24, 0, 2, 17, 67, 17, 65, 17, 65, 0, 2, 17, 67, 121, 0, 2, 102, 102, 108, 105, 107, 0, 2, 103, 105, 116, 17, 65, 0, 2, 103, 111, 110, 105, 101, 0, 2, 103, 117, 114, 107, 105, 101, 0, 2, 107, 107, 111, 111, 114, 100, 0, 2, 108, 97, 114, 109, 0, 2, 108, 105, 115, 109, 101, 0, 2, 108, 105, 116, 101, 105, 116, 0, 2, 109, 101, 110, 116, 0, 2, 114, 105, 115, 116, 111, 107, 114, 0, 2, 115, 105, 101, 108, 0, 2, 115, 112, 101, 114, 115, 105, 101, 0, 2, 116, 111, 109, 17, 65, 0, 8, 2, 98, 17, 67, 0, 8, 2, 102, 102, 17, 65, 0, 8, 2, 107, 117, 0, 8, 2, 107, 119, 97, 116, 0, 8, 2, 108, 17, 65, 0, 8, 2, 108, 108, 111, 111, 105, 0, 8, 2, 108, 108, 117, 0, 8, 2, 112, 17, 67, 0, 8, 2, 112, 111, 0, 8, 2, 115, 116, 114, 17, 65, 0, 8, 107, 2, 110, 17, 65, 0, 102, 2, 118, 97, 108, 108, 105, 103, 0, 4, 114, 1, 25, 2, 112, 117, 105, 115, 3, 2, 35, 34, 0, 114, 2, 103, 97, 195, 175, 0, 114, 2, 109, 111, 101, 100, 105, 103, 0, 114, 2, 115, 101, 101, 110, 0, 114, 2, 116, 105, 107, 101, 108, 0, 114, 8, 2, 103, 105, 0, 114, 8, 2, 111, 109, 0, 114, 97, 2, 98, 105, 101, 114, 3, 2, 35, 34, 2, 35, 0, 114, 97, 98, 101, 2, 115, 107, 3, 2, 35, 34, 2, 35, 69, 106, 0, 114, 101, 2, 111, 108, 17, 65, 3, 2, 35, 34, 2, 37, 0, 114, 114, 111, 2, 103, 3, 2, 35, 34, 2, 40, 0, 114, 121, 1, 108, 101, 107, 107, 111, 109, 115, 21, 21, 21, 3, 2, 35, 34, 2, 121, 0, 114, 114, 101, 2, 115, 116, 17, 65, 3, 2, 35, 34, 13, 0, 4, 114, 109, 2, 108, 97, 115, 116, 3, 2, 35, 34, 14, 63, 0, 114, 109, 2, 115, 97, 108, 105, 103, 0, 114, 116, 105, 107, 117, 3, 2, 35, 34, 47, 2, 37, 49, 2, 116, 0, 114, 116, 101, 2, 102, 97, 107, 3, 2, 35, 34, 47, 13, 0, 114, 116, 105, 108, 108, 101, 2, 114, 105, 101, 3, 2, 35, 34, 47, 13, 55, 13, 0, 114, 116, 101, 8, 2, 114, 105, 3, 2, 35, 34, 47, 114, 0, 114, 115, 101, 2, 110, 97, 3, 2, 35, 34, 87, 13, 0, 114, 114, 101, 115, 2, 32, 3, 2, 35, 34, 106, 87, 0, 114, 97, 2, 98, 105, 3, 2, 35, 34, 113, 0, 114, 101, 110, 97, 2, 25, 12, 3, 2, 35, 34, 114, 50, 2, 35, 0, 114, 103, 2, 108, 105, 115, 116, 3, 2, 35, 34, 134, 0, 114, 103, 105, 116, 101, 107, 3, 2, 35, 34, 134, 2, 37, 47, 106, 49, 0, 114, 103, 101, 2, 116, 105, 112, 3, 2, 35, 34, 134, 13, 0, 114, 103, 101, 110, 2, 116, 17, 65, 3, 2, 35, 34, 134, 13, 50, 0, 4, 100, 2, 118, 105, 101, 115, 3, 2, 35, 47, 0, 116, 2, 108, 97, 110, 116, 0, 116, 2, 108, 101, 0, 116, 116, 101, 115, 116, 2, 17, 65, 3, 2, 35, 47, 2, 106, 87, 47, 0, 116, 111, 114, 105, 101, 115, 1, 21, 3, 2, 35, 47, 6, 115, 34, 37, 87, 0, 4, 116, 101, 1, 115, 2, 108, 3, 2, 35, 47, 13, 0, 116, 104, 101, 1, 17, 67, 2, 114, 105, 110, 97, 0, 116, 114, 111, 2, 102, 105, 101, 3, 2, 35, 47, 34, 2, 40, 0, 116, 116, 114, 105, 98, 2, 117, 3, 2, 35, 47, 34, 13, 69, 0, 116, 108, 101, 2, 116, 105, 101, 107, 3, 2, 35, 47, 55, 13, 0, 100, 109, 105, 2, 114, 3, 2, 35, 47, 63, 2, 37, 0, 116, 109, 111, 2, 115, 102, 101, 3, 2, 35, 47, 63, 2, 108, 0, 100, 109, 105, 110, 105, 3, 2, 35, 47, 63, 13, 50, 13, 0, 100, 109, 105, 2, 115, 115, 105, 101, 3, 2, 35, 47, 63, 37, 0, 116, 101, 108, 2, 106, 101, 101, 3, 2, 35, 47, 112, 0, 112, 111, 2, 107, 114, 105, 101, 17, 67, 3, 2, 35, 48, 2, 40, 0, 112, 111, 107, 97, 2, 108, 3, 2, 35, 48, 2, 108, 49, 2, 35, 0, 112, 111, 108, 111, 103, 2, 17, 65, 3, 2, 35, 48, 2, 108, 55, 2, 40, 134, 0, 112, 112, 101, 2, 108, 108, 17, 65, 3, 2, 35, 48, 13, 0, 112, 112, 97, 114, 2, 17, 65, 3, 2, 35, 48, 13, 34, 0, 112, 112, 101, 108, 8, 2, 107, 111, 21, 3, 2, 35, 48, 13, 55, 0, 112, 111, 115, 116, 111, 2, 108, 105, 101, 3, 2, 35, 48, 13, 87, 47, 115, 0, 112, 112, 114, 111, 112, 114, 105, 2, 17, 65, 3, 2, 35, 48, 34, 2, 115, 48, 34, 2, 37, 0, 112, 97, 114, 116, 3, 2, 35, 48, 35, 34, 47, 0, 112, 112, 108, 105, 2, 107, 97, 110, 116, 3, 2, 35, 48, 55, 2, 37, 0, 98, 115, 111, 2, 108, 117, 3, 2, 35, 48, 87, 2, 40, 0, 98, 115, 101, 2, 115, 3, 2, 35, 48, 87, 106, 0, 112, 112, 101, 110, 2, 100, 105, 17, 67, 3, 2, 35, 48, 106, 50, 0, 107, 2, 115, 121, 110, 3, 2, 35, 49, 0, 107, 111, 2, 17, 67, 105, 101, 116, 3, 2, 35, 49, 2, 40, 0, 107, 107, 111, 109, 109, 111, 2, 100, 3, 2, 35, 49, 2, 108, 63, 13, 0, 107, 107, 117, 2, 114, 97, 3, 2, 35, 49, 2, 116, 0, 107, 97, 2, 100, 101, 21, 3, 2, 35, 49, 13, 0, 107, 107, 101, 100, 105, 3, 2, 35, 49, 13, 70, 107, 0, 107, 114, 111, 2, 98, 97, 3, 2, 35, 49, 34, 2, 40, 0, 107, 116, 117, 97, 114, 105, 2, 17, 65, 3, 2, 35, 49, 47, 2, 116, 2, 35, 34, 2, 37, 0, 107, 119, 97, 114, 101, 2, 108, 3, 2, 35, 49, 58, 2, 35, 34, 110, 0, 107, 119, 97, 109, 97, 2, 114, 121, 110, 3, 2, 35, 49, 58, 2, 35, 63, 2, 35, 0, 107, 97, 2, 115, 105, 97, 3, 2, 35, 49, 113, 0, 110, 111, 2, 110, 105, 21, 3, 2, 35, 50, 2, 40, 0, 110, 116, 101, 114, 105, 110, 103, 3, 2, 35, 50, 47, 114, 34, 13, 66, 0, 4, 108, 2, 98, 97, 115, 116, 101, 114, 3, 2, 35, 55, 0, 108, 2, 98, 105, 110, 111, 0, 108, 2, 106, 97, 110, 100, 101, 114, 0, 108, 8, 2, 119, 101, 0, 108, 117, 2, 109, 105, 110, 105, 117, 109, 3, 2, 35, 55, 2, 40, 0, 108, 101, 120, 2, 97, 3, 2, 35, 55, 2, 106, 49, 86, 0, 108, 101, 107, 115, 97, 110, 100, 2, 114, 121, 3, 2, 35, 55, 2, 106, 49, 87, 2, 35, 50, 70, 0, 4, 108, 105, 8, 17, 67, 2, 102, 111, 114, 110, 105, 3, 2, 35, 55, 13, 0, 108, 108, 101, 2, 109, 105, 110, 116, 0, 108, 108, 101, 114, 2, 103, 105, 101, 32, 24, 3, 2, 35, 55, 13, 34, 0, 108, 8, 2, 101, 119, 105, 103, 3, 2, 35, 55, 38, 0, 108, 107, 111, 104, 111, 108, 2, 105, 101, 25, 3, 2, 35, 55, 49, 2, 40, 105, 115, 55, 0, 108, 109, 97, 2, 110, 97, 107, 3, 2, 35, 55, 63, 2, 35, 0, 108, 102, 97, 98, 101, 2, 116, 17, 65, 3, 2, 35, 55, 81, 2, 35, 69, 114, 0, 108, 108, 101, 114, 2, 103, 105, 101, 3, 2, 35, 55, 110, 34, 0, 108, 108, 101, 2, 110, 17, 65, 3, 2, 35, 55, 114, 0, 108, 108, 101, 101, 110, 3, 2, 35, 55, 114, 50, 0, 108, 99, 104, 101, 2, 109, 105, 3, 2, 35, 55, 134, 2, 114, 0, 108, 103, 101, 2, 114, 121, 110, 3, 2, 35, 55, 134, 13, 0, 4, 109, 8, 2, 17, 65, 3, 2, 35, 63, 0, 109, 8, 2, 110, 17, 65, 0, 109, 97, 114, 117, 108, 97, 3, 2, 35, 63, 2, 35, 34, 40, 55, 2, 35, 0, 109, 97, 115, 111, 110, 101, 3, 2, 35, 63, 2, 35, 87, 115, 50, 13, 0, 109, 117, 2, 17, 67, 17, 65, 3, 2, 35, 63, 2, 116, 0, 109, 112, 105, 2, 111, 101, 110, 3, 2, 35, 63, 48, 2, 37, 0, 109, 98, 97, 115, 115, 2, 97, 100, 101, 3, 2, 35, 63, 69, 2, 35, 87, 0, 109, 98, 97, 115, 115, 97, 2, 100, 101, 117, 3, 2, 35, 63, 69, 2, 35, 87, 2, 35, 0, 109, 98, 117, 2, 108, 3, 2, 35, 63, 69, 2, 116, 0, 109, 101, 114, 2, 105, 107, 3, 2, 35, 63, 114, 34, 0, 109, 109, 111, 2, 110, 105, 17, 65, 3, 2, 35, 63, 115, 0, 98, 111, 8, 2, 17, 67, 3, 2, 35, 69, 108, 0, 4, 98, 101, 108, 1, 116, 3, 2, 35, 69, 110, 55, 0, 98, 101, 108, 108, 1, 116, 0, 100, 111, 108, 101, 115, 115, 101, 110, 3, 2, 35, 70, 2, 115, 55, 13, 87, 106, 50, 0, 100, 114, 101, 110, 97, 2, 108, 105, 3, 2, 35, 70, 34, 13, 50, 2, 35, 0, 100, 114, 101, 2, 25, 3, 2, 35, 70, 34, 106, 0, 103, 97, 2, 112, 97, 110, 116, 3, 2, 35, 79, 2, 35, 0, 4, 102, 2, 103, 117, 110, 115, 116, 105, 103, 3, 2, 35, 81, 0, 102, 2, 104, 97, 110, 107, 0, 102, 2, 115, 105, 103, 116, 101, 0, 102, 2, 115, 107, 117, 119, 0, 102, 2, 115, 121, 100, 105, 103, 0, 102, 2, 119, 97, 103, 116, 101, 110, 0, 102, 8, 2, 107, 101, 114, 105, 103, 0, 102, 8, 2, 107, 111, 109, 115, 116, 105, 103, 0, 102, 102, 111, 2, 100, 105, 108, 3, 2, 35, 81, 2, 40, 0, 118, 111, 107, 97, 100, 101, 3, 2, 35, 81, 2, 40, 49, 113, 70, 13, 0, 118, 111, 107, 97, 100, 111, 3, 2, 35, 81, 2, 40, 49, 113, 70, 40, 0, 102, 114, 105, 107, 2, 97, 97, 110, 3, 2, 35, 81, 34, 2, 37, 49, 0, 102, 114, 105, 107, 97, 110, 101, 2, 25, 3, 2, 35, 81, 34, 2, 37, 49, 113, 50, 13, 0, 4, 102, 114, 111, 2, 100, 105, 116, 3, 2, 35, 81, 34, 2, 40, 0, 112, 104, 114, 111, 2, 100, 105, 116, 0, 102, 102, 114, 111, 2, 110, 116, 3, 2, 35, 81, 34, 2, 108, 0, 102, 119, 101, 115, 105, 103, 3, 2, 35, 81, 82, 114, 87, 13, 134, 0, 102, 115, 116, 111, 111, 116, 108, 3, 2, 35, 81, 87, 47, 115, 47, 55, 0, 102, 115, 111, 110, 100, 101, 114, 108, 3, 2, 35, 81, 87, 108, 50, 13, 34, 55, 0, 102, 103, 114, 121, 115, 108, 105, 107, 3, 2, 35, 81, 134, 34, 121, 87, 55, 13, 49, 0, 118, 111, 110, 116, 117, 2, 114, 105, 101, 114, 3, 2, 35, 82, 2, 108, 50, 47, 2, 116, 0, 115, 8, 2, 107, 101, 3, 2, 35, 87, 0, 115, 115, 117, 2, 114, 97, 110, 3, 2, 35, 87, 2, 109, 0, 115, 115, 111, 115, 105, 2, 17, 65, 3, 2, 35, 87, 2, 115, 89, 2, 37, 0, 115, 115, 101, 2, 103, 97, 97, 105, 3, 2, 35, 87, 13, 0, 115, 115, 105, 115, 116, 3, 2, 35, 87, 13, 87, 47, 0, 115, 112, 105, 8, 2, 114, 17, 65, 3, 2, 35, 87, 48, 2, 37, 0, 115, 112, 101, 107, 3, 2, 35, 87, 48, 106, 49, 0, 115, 107, 105, 116, 101, 8, 3, 2, 35, 87, 49, 37, 47, 13, 0, 115, 107, 97, 114, 105, 3, 2, 35, 87, 49, 113, 34, 2, 37, 0, 115, 98, 101, 115, 8, 3, 2, 35, 87, 69, 106, 87, 0, 115, 115, 101, 2, 115, 115, 111, 114, 3, 2, 35, 87, 106, 0, 115, 115, 105, 115, 1, 114, 2, 25, 3, 2, 35, 87, 107, 87, 0, 103, 111, 110, 105, 101, 2, 32, 24, 3, 2, 35, 134, 2, 40, 50, 37, 0, 103, 116, 101, 2, 108, 111, 115, 105, 103, 3, 2, 35, 134, 47, 13, 0, 4, 103, 116, 101, 114, 2, 98, 97, 107, 3, 2, 35, 134, 47, 13, 34, 0, 103, 116, 101, 114, 2, 100, 111, 103, 116, 0, 103, 116, 101, 114, 2, 108, 111, 115, 105, 103, 0, 103, 116, 101, 114, 2, 109, 105, 100, 100, 97, 0, 103, 116, 101, 114, 2, 115, 116, 97, 108, 108, 0, 103, 116, 101, 114, 2, 118, 111, 108, 103, 0, 103, 116, 101, 114, 2, 111, 111, 114, 3, 2, 35, 134, 47, 13, 34, 10, 0, 103, 116, 101, 114, 101, 101, 110, 2, 118, 111, 108, 103, 3, 2, 35, 134, 47, 13, 34, 10, 2, 114, 50, 0, 103, 116, 101, 114, 2, 117, 105, 116, 3, 2, 35, 134, 47, 13, 34, 19, 0, 103, 101, 110, 116, 3, 2, 35, 134, 106, 50, 47, 0, 103, 101, 110, 100, 97, 3, 2, 35, 134, 106, 50, 70, 2, 35, 0, 103, 101, 2, 114, 101, 110, 100, 3, 2, 35, 134, 114, 0, 117, 103, 117, 115, 116, 117, 115, 3, 2, 108, 134, 109, 87, 47, 109, 87, 0, 2, 112, 111, 108, 105, 116, 105, 3, 2, 113, 0, 117, 115, 116, 114, 97, 3, 2, 115, 87, 47, 34, 113, 0, 195, 171, 2, 114, 111, 98, 105, 3, 2, 119, 0, 118, 111, 110, 2, 116, 3, 4, 35, 82, 108, 50, 0, 108, 103, 101, 109, 101, 101, 110, 3, 6, 35, 55, 134, 13, 63, 4, 114, 50, 0, 102, 8, 2, 21, 14, 128, 132, 130, 3, 6, 35, 81, 0, 102, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 6, 35, 81, 134, 13, 0, 102, 103, 101, 101, 2, 12, 3, 6, 35, 81, 134, 114, 0, 103, 116, 101, 114, 103, 101, 8, 2, 21, 14, 128, 132, 135, 3, 6, 35, 134, 47, 13, 34, 134, 13, 0, 103, 116, 105, 103, 1, 10, 3, 6, 35, 134, 47, 13, 134, 0, 4, 1, 105, 2, 116, 105, 101, 115, 3, 6, 113, 0, 2, 114, 105, 17, 65, 0, 8, 17, 67, 2, 17, 67, 105, 101, 32, 0, 116, 111, 114, 1, 21, 2, 25, 3, 6, 113, 47, 108, 34, 0, 98, 101, 108, 1, 116, 107, 101, 112, 115, 3, 6, 113, 69, 13, 55, 0, 98, 105, 101, 1, 17, 67, 3, 6, 113, 69, 37, 0, 100, 8, 17, 67, 114, 97, 2, 17, 65, 3, 6, 113, 70, 0, 100, 105, 103, 1, 21, 3, 6, 113, 70, 13, 134, 0, 100, 105, 101, 115, 1, 17, 67, 17, 65, 3, 6, 113, 70, 37, 87, 0, 115, 105, 101, 1, 17, 67, 3, 6, 113, 87, 37, 0, 103, 116, 101, 114, 8, 2, 101, 110, 3, 7, 35, 134, 47, 13, 34, 10, 0, 116, 116, 97, 99, 104, 195, 169, 3, 10, 2, 35, 47, 2, 35, 89, 114, 0, 4, 99, 107, 2, 32, 3, 21, 0, 121, 2, 32, 0, 121, 115, 2, 32, 0, 4, 105, 110, 101, 2, 32, 3, 21, 102, 114, 0, 105, 114, 101, 1, 21, 2, 32, 0, 4, 1, 17, 67, 2, 120, 17, 65, 12, 3, 35, 0, 1, 107, 10, 2, 32, 0, 1, 116, 115, 2, 116, 105, 115, 116, 0, 2, 17, 67, 0, 8, 2, 98, 98, 97, 0, 2, 100, 114, 101, 115, 3, 35, 6, 0, 114, 121, 1, 108, 101, 17, 67, 3, 35, 34, 6, 121, 0, 114, 109, 101, 115, 8, 3, 35, 34, 19, 63, 13, 87, 0, 100, 8, 112, 2, 17, 65, 3, 35, 47, 0, 116, 116, 101, 110, 2, 17, 67, 3, 35, 47, 6, 106, 50, 0, 116, 111, 114, 101, 1, 21, 2, 32, 3, 35, 47, 6, 115, 34, 13, 0, 116, 116, 101, 110, 2, 100, 3, 35, 47, 13, 50, 0, 112, 112, 8, 2, 17, 65, 3, 35, 48, 0, 112, 112, 195, 168, 108, 3, 35, 48, 6, 110, 55, 0, 4, 112, 1, 17, 67, 2, 111, 111, 114, 3, 35, 48, 10, 0, 112, 1, 17, 67, 2, 111, 114, 101, 32, 0, 108, 105, 8, 2, 107, 114, 17, 65, 3, 35, 55, 2, 37, 0, 108, 111, 195, 171, 3, 35, 55, 6, 40, 13, 0, 108, 111, 111, 103, 3, 35, 55, 6, 115, 134, 0, 108, 111, 103, 105, 101, 115, 3, 35, 55, 6, 115, 134, 37, 87, 0, 108, 108, 101, 8, 2, 17, 67, 3, 35, 55, 13, 0, 108, 111, 109, 8, 2, 21, 3, 35, 55, 19, 108, 63, 0, 108, 111, 103, 105, 101, 3, 35, 55, 40, 134, 6, 37, 0, 108, 107, 111, 104, 111, 108, 3, 35, 55, 49, 2, 40, 2, 108, 55, 0, 108, 109, 101, 2, 108, 101, 3, 35, 55, 63, 13, 0, 108, 102, 97, 98, 101, 2, 116, 25, 3, 35, 55, 81, 35, 69, 106, 0, 109, 97, 110, 100, 101, 108, 3, 35, 63, 6, 35, 50, 70, 13, 55, 0, 109, 112, 101, 114, 8, 3, 35, 63, 48, 13, 34, 0, 100, 106, 117, 110, 107, 3, 35, 70, 57, 6, 109, 66, 49, 0, 115, 1, 17, 67, 21, 2, 32, 3, 35, 87, 0, 103, 116, 8, 2, 117, 117, 114, 3, 35, 134, 47, 0, 103, 116, 101, 114, 110, 97, 3, 35, 134, 47, 13, 34, 50, 6, 113, 0, 4, 3, 113, 0, 1, 17, 67, 2, 17, 67, 105, 97, 32, 0, 1, 109, 97, 116, 2, 116, 105, 101, 107, 0, 1, 114, 98, 17, 67, 2, 32, 0, 1, 114, 100, 10, 2, 32, 0, 1, 114, 118, 10, 2, 32, 0, 1, 119, 2, 116, 101, 114, 105, 110, 103, 0, 2, 17, 67, 17, 65, 0, 2, 17, 67, 105, 101, 0, 2, 104, 108, 101, 32, 0, 8, 2, 115, 105, 195, 171, 0, 101, 0, 104, 2, 17, 67, 0, 114, 101, 1, 17, 67, 2, 17, 67, 17, 65, 3, 113, 34, 13, 0, 114, 101, 110, 100, 115, 3, 113, 34, 13, 50, 47, 87, 10, 0, 114, 101, 97, 3, 113, 34, 37, 35, 0, 116, 114, 105, 117, 109, 3, 113, 47, 34, 37, 109, 63, 0, 108, 105, 97, 3, 113, 55, 2, 37, 2, 35, 0, 100, 101, 109, 8, 3, 113, 70, 13, 63, 0, 100, 105, 117, 1, 17, 67, 2, 25, 3, 113, 70, 37, 109, 0, 102, 101, 108, 1, 17, 67, 2, 21, 3, 113, 81, 13, 55, 0, 102, 114, 105, 107, 97, 3, 113, 81, 34, 37, 49, 35, 0, 4, 115, 105, 101, 1, 21, 21, 21, 21, 3, 113, 87, 2, 37, 0, 115, 105, 101, 1, 108, 112, 0, 115, 105, 101, 1, 112, 115, 21, 0, 115, 101, 109, 3, 113, 87, 13, 63, 0, 4, 115, 105, 101, 1, 17, 67, 11, 17, 67, 3, 113, 87, 37, 0, 115, 105, 101, 1, 98, 117, 111, 0, 115, 105, 101, 1, 108, 103, 0, 115, 105, 101, 1, 109, 114, 111, 102, 21, 0, 115, 105, 101, 1, 116, 115, 17, 65, 17, 65, 0, 115, 105, 101, 1, 116, 115, 17, 67, 0, 103, 105, 101, 1, 17, 67, 3, 113, 134, 37, 0, 117, 1, 25, 3, 118, 0, 4, 2, 100, 106, 105, 101, 3, 119, 0, 105, 0, 116, 106, 105, 101, 3, 119, 78, 37, 0, 101, 110, 2, 116, 106, 105, 101, 3, 120, 66, 0, 100, 106, 105, 101, 3, 120, 78, 37, 0, 117, 3, 127, 0, 117, 101, 114, 3, 127, 13, 34, 0, 7, 6, 98, 0, 2, 98, 3, 0, 117, 114, 121, 1, 21, 2, 32, 3, 21, 0, 2, 32, 24, 3, 48, 0, 4, 3, 69, 0, 2, 101, 101, 110, 116, 106, 105, 101, 12, 12, 0, 4, 105, 2, 115, 97, 114, 3, 69, 2, 37, 0, 105, 2, 122, 97, 0, 105, 8, 2, 103, 97, 0, 105, 115, 97, 110, 2, 116, 121, 110, 3, 69, 2, 37, 87, 2, 35, 50, 0, 4, 111, 2, 98, 111, 116, 105, 101, 3, 69, 2, 40, 0, 111, 2, 104, 97, 97, 105, 0, 111, 2, 104, 101, 0, 111, 101, 2, 100, 100, 104, 105, 0, 111, 101, 2, 116, 115, 101, 101, 114, 0, 4, 111, 101, 114, 2, 103, 111, 110, 100, 3, 69, 2, 40, 34, 0, 111, 101, 114, 2, 105, 110, 0, 111, 101, 107, 101, 2, 116, 25, 3, 69, 2, 40, 49, 106, 0, 117, 108, 2, 103, 97, 3, 69, 2, 40, 55, 0, 117, 108, 108, 101, 2, 116, 105, 110, 3, 69, 2, 40, 55, 13, 0, 111, 114, 8, 2, 100, 17, 65, 21, 3, 69, 2, 108, 34, 0, 111, 107, 109, 97, 2, 107, 105, 101, 114, 3, 69, 2, 108, 49, 63, 2, 35, 0, 111, 110, 115, 109, 97, 114, 97, 3, 69, 2, 108, 50, 87, 63, 113, 34, 2, 35, 0, 111, 98, 98, 101, 2, 106, 3, 69, 2, 108, 69, 13, 0, 117, 114, 2, 108, 101, 115, 107, 3, 69, 2, 109, 34, 0, 117, 102, 102, 101, 2, 116, 3, 69, 2, 109, 81, 106, 0, 111, 2, 116, 97, 110, 105, 101, 3, 69, 2, 115, 0, 111, 116, 97, 2, 110, 105, 101, 32, 24, 3, 69, 2, 115, 47, 2, 35, 0, 111, 111, 115, 2, 97, 97, 114, 100, 105, 103, 3, 69, 2, 115, 87, 10, 0, 117, 114, 2, 111, 107, 114, 97, 3, 69, 2, 116, 34, 0, 117, 114, 111, 3, 69, 2, 116, 34, 115, 0, 4, 121, 2, 107, 111, 109, 21, 3, 69, 2, 121, 0, 121, 2, 118, 111, 111, 114, 98, 0, 121, 2, 101, 101, 110, 3, 69, 2, 121, 10, 0, 121, 100, 101, 114, 2, 17, 67, 21, 3, 69, 2, 121, 70, 13, 34, 0, 121, 119, 111, 111, 114, 100, 101, 108, 105, 3, 69, 2, 121, 82, 115, 34, 70, 13, 55, 13, 0, 121, 103, 101, 2, 108, 111, 119, 105, 3, 69, 2, 121, 134, 13, 0, 121, 8, 2, 116, 101, 108, 14, 128, 132, 130, 3, 69, 6, 121, 0, 121, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 69, 6, 121, 134, 13, 0, 117, 105, 116, 101, 110, 2, 103, 101, 3, 69, 6, 125, 47, 13, 50, 0, 111, 101, 112, 101, 110, 115, 3, 69, 7, 40, 48, 132, 50, 87, 0, 111, 119, 101, 8, 3, 69, 7, 115, 82, 13, 0, 98, 101, 2, 114, 114, 3, 69, 13, 0, 105, 107, 105, 110, 105, 3, 69, 13, 49, 37, 50, 37, 0, 105, 108, 2, 106, 3, 69, 13, 55, 0, 105, 98, 108, 105, 2, 111, 17, 67, 3, 69, 13, 69, 55, 2, 37, 12, 2, 0, 114, 97, 118, 2, 17, 65, 3, 69, 34, 2, 35, 82, 0, 114, 97, 115, 105, 2, 108, 105, 3, 69, 34, 2, 35, 87, 107, 0, 114, 111, 2, 115, 106, 117, 3, 69, 34, 2, 108, 0, 114, 111, 2, 109, 105, 3, 69, 34, 2, 115, 0, 114, 117, 2, 116, 97, 3, 69, 34, 2, 116, 0, 114, 105, 101, 119, 101, 8, 2, 17, 67, 3, 69, 34, 7, 37, 82, 13, 0, 114, 105, 108, 2, 106, 97, 110, 116, 3, 69, 34, 13, 55, 0, 114, 101, 100, 97, 8, 3, 69, 34, 13, 70, 113, 0, 114, 97, 110, 100, 2, 114, 3, 69, 34, 35, 50, 47, 0, 114, 97, 110, 100, 2, 97, 3, 69, 34, 35, 50, 47, 10, 0, 114, 97, 110, 100, 2, 111, 3, 69, 34, 35, 50, 47, 19, 0, 114, 111, 110, 2, 17, 65, 21, 3, 69, 34, 108, 50, 10, 0, 114, 97, 105, 108, 108, 101, 3, 69, 34, 121, 12, 55, 10, 0, 114, 101, 105, 100, 101, 108, 3, 69, 34, 121, 70, 13, 55, 0, 111, 101, 114, 101, 3, 69, 40, 12, 34, 13, 0, 111, 117, 108, 101, 118, 97, 114, 100, 3, 69, 40, 55, 13, 82, 35, 34, 70, 0, 4, 108, 97, 2, 116, 97, 110, 116, 3, 69, 55, 2, 35, 0, 108, 97, 8, 2, 109, 101, 0, 108, 111, 101, 2, 100, 100, 111, 114, 115, 21, 3, 69, 55, 2, 40, 0, 4, 108, 111, 101, 100, 2, 115, 107, 101, 110, 100, 105, 103, 3, 69, 55, 2, 40, 47, 0, 108, 111, 101, 100, 2, 115, 116, 111, 108, 0, 4, 108, 111, 8, 2, 107, 107, 97, 3, 69, 55, 2, 108, 0, 108, 111, 8, 2, 107, 107, 101, 101, 114, 0, 108, 111, 110, 2, 100, 105, 110, 101, 3, 69, 55, 2, 108, 50, 0, 108, 121, 2, 109, 111, 101, 100, 3, 69, 55, 2, 121, 0, 108, 97, 100, 2, 17, 65, 3, 69, 55, 35, 47, 10, 0, 108, 105, 107, 8, 2, 17, 65, 3, 69, 55, 107, 49, 10, 0, 108, 111, 109, 2, 97, 107, 107, 101, 114, 3, 69, 55, 108, 63, 10, 0, 105, 100, 8, 3, 69, 107, 47, 10, 0, 105, 110, 110, 101, 3, 69, 107, 50, 13, 0, 105, 108, 108, 105, 2, 107, 3, 69, 107, 55, 13, 0, 105, 100, 100, 3, 69, 107, 70, 0, 111, 114, 100, 101, 2, 114, 3, 69, 108, 34, 70, 13, 0, 111, 107, 2, 111, 111, 105, 3, 69, 108, 49, 10, 0, 111, 110, 100, 101, 2, 17, 67, 3, 69, 108, 50, 70, 13, 0, 111, 109, 2, 17, 65, 17, 65, 3, 69, 108, 63, 10, 0, 111, 110, 103, 111, 8, 3, 69, 108, 66, 79, 40, 0, 111, 115, 99, 104, 2, 32, 3, 69, 108, 87, 0, 111, 115, 2, 17, 65, 21, 3, 69, 108, 87, 19, 0, 4, 111, 2, 103, 114, 111, 110, 100, 3, 69, 115, 0, 111, 2, 115, 107, 114, 105, 102, 0, 111, 2, 118, 0, 111, 8, 2, 107, 108, 101, 0, 111, 116, 97, 8, 2, 110, 105, 17, 67, 17, 65, 3, 69, 115, 47, 7, 113, 0, 111, 109, 97, 97, 110, 115, 3, 69, 115, 63, 113, 50, 87, 0, 111, 119, 101, 110, 3, 69, 115, 82, 13, 50, 6, 0, 121, 98, 101, 108, 3, 69, 121, 69, 13, 55, 0, 117, 105, 116, 101, 3, 69, 125, 47, 13, 0, 4, 117, 105, 116, 101, 110, 2, 115, 116, 101, 3, 69, 125, 47, 13, 50, 0, 117, 105, 116, 101, 110, 2, 116, 0, 117, 105, 116, 101, 110, 3, 69, 125, 47, 13, 50, 6, 0, 7, 6, 99, 0, 2, 99, 3, 0, 4, 101, 2, 32, 3, 21, 0, 101, 108, 1, 21, 2, 32, 0, 104, 97, 116, 0, 108, 101, 1, 21, 2, 32, 0, 121, 2, 32, 0, 4, 3, 49, 0, 104, 2, 108, 0, 104, 2, 114, 111, 0, 107, 0, 104, 97, 2, 114, 105, 115, 109, 97, 3, 49, 2, 35, 0, 97, 108, 2, 118, 17, 65, 3, 49, 2, 35, 55, 0, 97, 108, 97, 109, 97, 114, 105, 3, 49, 2, 35, 55, 2, 35, 63, 113, 34, 2, 37, 0, 104, 111, 114, 101, 2, 111, 103, 114, 97, 3, 49, 2, 108, 34, 2, 37, 0, 111, 108, 111, 109, 98, 105, 2, 97, 21, 3, 49, 2, 108, 55, 2, 108, 63, 69, 2, 37, 0, 104, 111, 108, 101, 115, 116, 101, 114, 111, 108, 3, 49, 2, 108, 55, 106, 87, 47, 14, 34, 2, 108, 55, 0, 108, 105, 99, 104, 195, 169, 3, 49, 55, 2, 37, 89, 114, 0, 111, 114, 110, 101, 2, 108, 105, 3, 49, 108, 34, 50, 7, 114, 0, 104, 111, 108, 101, 114, 97, 3, 49, 115, 55, 13, 34, 35, 10, 0, 111, 107, 101, 3, 49, 118, 49, 0, 104, 101, 100, 100, 97, 114, 3, 74, 106, 70, 13, 34, 0, 4, 2, 101, 3, 87, 0, 2, 105, 0, 2, 121, 0, 101, 110, 2, 116, 97, 117, 114, 17, 65, 3, 87, 2, 106, 50, 0, 105, 1, 21, 2, 32, 3, 87, 6, 37, 0, 121, 2, 114, 105, 108, 108, 105, 101, 3, 87, 13, 0, 105, 8, 2, 112, 114, 17, 65, 3, 87, 37, 0, 104, 97, 108, 101, 116, 3, 89, 2, 35, 55, 121, 0, 104, 105, 110, 2, 101, 3, 89, 2, 37, 50, 0, 104, 97, 117, 2, 17, 67, 3, 89, 2, 118, 0, 104, 105, 114, 117, 114, 103, 2, 105, 101, 32, 24, 3, 89, 13, 34, 2, 109, 34, 134, 0, 104, 105, 114, 117, 114, 103, 3, 89, 13, 34, 109, 34, 134, 0, 4, 104, 3, 134, 0, 104, 8, 0, 104, 101, 109, 105, 107, 97, 2, 108, 105, 3, 134, 2, 114, 63, 2, 37, 49, 113, 0, 7, 6, 100, 0, 4, 1, 21, 2, 116, 3, 0, 4, 2, 32, 100, 24, 3, 0, 2, 100, 3, 0, 4, 103, 101, 1, 21, 2, 32, 3, 21, 0, 103, 101, 2, 32, 0, 4, 1, 21, 2, 17, 67, 3, 47, 0, 1, 21, 2, 101, 116, 101, 17, 67, 32, 0, 1, 21, 2, 114, 97, 97, 109, 0, 1, 21, 2, 114, 111, 111, 115, 0, 1, 21, 2, 114, 111, 115, 101, 32, 0, 1, 21, 2, 114, 111, 115, 105, 101, 0, 1, 21, 2, 114, 117, 105, 109, 0, 1, 101, 111, 2, 114, 0, 1, 110, 21, 2, 101, 116, 101, 32, 0, 1, 110, 97, 104, 2, 114, 0, 1, 110, 97, 115, 2, 114, 0, 1, 110, 105, 119, 2, 114, 0, 1, 110, 111, 104, 2, 17, 67, 0, 1, 111, 111, 2, 114, 0, 2, 32, 0, 2, 114, 105, 101, 109, 32, 0, 4, 1, 17, 65, 2, 97, 103, 116, 105, 103, 3, 47, 10, 0, 1, 21, 2, 101, 105, 101, 110, 0, 1, 21, 2, 101, 105, 110, 100, 101, 32, 0, 1, 21, 2, 101, 105, 115, 0, 1, 21, 2, 105, 110, 104, 111, 117, 0, 1, 110, 21, 2, 117, 105, 116, 0, 1, 111, 111, 2, 17, 65, 3, 47, 19, 0, 119, 101, 115, 1, 21, 3, 47, 82, 6, 106, 87, 0, 119, 105, 108, 108, 105, 103, 1, 21, 3, 47, 82, 6, 107, 55, 13, 134, 0, 119, 101, 115, 101, 1, 21, 3, 47, 82, 114, 87, 13, 0, 115, 1, 21, 2, 32, 3, 47, 87, 0, 4, 3, 70, 0, 1, 21, 2, 114, 0, 1, 101, 111, 116, 2, 114, 0, 1, 111, 111, 114, 97, 107, 0, 1, 112, 2, 17, 67, 0, 1, 114, 101, 118, 2, 17, 67, 0, 100, 0, 100, 1, 21, 0, 100, 104, 0, 105, 2, 110, 97, 109, 105, 101, 3, 70, 2, 37, 0, 105, 97, 2, 17, 67, 3, 70, 2, 37, 2, 35, 0, 105, 97, 107, 111, 2, 110, 105, 101, 3, 70, 2, 37, 2, 35, 49, 2, 40, 0, 105, 114, 101, 107, 3, 70, 2, 37, 34, 106, 49, 0, 4, 105, 110, 97, 2, 109, 105, 101, 107, 3, 70, 2, 37, 50, 2, 35, 0, 105, 110, 97, 2, 109, 105, 101, 116, 0, 105, 110, 97, 2, 115, 116, 105, 101, 0, 105, 110, 111, 2, 115, 111, 117, 3, 70, 2, 37, 50, 2, 40, 0, 105, 101, 110, 115, 2, 119, 105, 108, 108, 105, 3, 70, 2, 37, 50, 87, 0, 105, 97, 107, 101, 110, 3, 70, 2, 37, 113, 49, 13, 50, 0, 105, 103, 105, 2, 116, 97, 3, 70, 2, 37, 134, 2, 37, 0, 117, 2, 101, 116, 3, 70, 2, 40, 12, 58, 0, 111, 101, 108, 2, 116, 114, 101, 102, 3, 70, 2, 40, 55, 0, 117, 118, 101, 116, 3, 70, 2, 40, 82, 121, 12, 0, 111, 101, 97, 110, 101, 3, 70, 2, 40, 113, 50, 13, 0, 111, 2, 115, 115, 105, 101, 114, 3, 70, 2, 108, 0, 111, 108, 2, 102, 121, 110, 3, 70, 2, 108, 55, 0, 111, 108, 111, 2, 109, 105, 101, 116, 3, 70, 2, 108, 55, 13, 0, 111, 109, 105, 110, 2, 17, 65, 3, 70, 2, 108, 63, 2, 37, 50, 0, 111, 109, 105, 110, 105, 2, 107, 97, 3, 70, 2, 108, 63, 2, 37, 50, 2, 37, 0, 97, 97, 114, 111, 112, 2, 118, 3, 70, 2, 113, 34, 2, 108, 48, 0, 97, 97, 114, 101, 110, 2, 116, 101, 3, 70, 2, 113, 34, 13, 50, 0, 97, 97, 100, 2, 119, 101, 114, 107, 3, 70, 2, 113, 47, 0, 111, 112, 97, 2, 109, 105, 3, 70, 2, 115, 48, 2, 35, 0, 97, 110, 116, 1, 21, 3, 70, 6, 35, 50, 47, 0, 97, 103, 1, 110, 97, 97, 2, 116, 105, 103, 3, 70, 6, 35, 134, 0, 97, 110, 105, 2, 103, 104, 3, 70, 6, 113, 50, 13, 0, 97, 109, 101, 115, 8, 3, 70, 6, 113, 63, 13, 87, 0, 111, 109, 105, 110, 101, 101, 2, 32, 3, 70, 6, 115, 63, 13, 50, 37, 0, 111, 100, 101, 8, 3, 70, 6, 115, 70, 13, 0, 4, 105, 2, 110, 101, 101, 3, 70, 13, 0, 105, 2, 112, 108, 111, 109, 97, 0, 105, 2, 115, 115, 105, 0, 105, 2, 118, 105, 115, 105, 101, 0, 105, 114, 105, 103, 2, 101, 3, 70, 13, 34, 13, 134, 0, 100, 101, 114, 100, 1, 21, 2, 32, 3, 70, 13, 34, 47, 0, 105, 112, 108, 111, 2, 109, 97, 116, 3, 70, 13, 48, 55, 2, 40, 0, 105, 107, 2, 118, 101, 108, 108, 3, 70, 13, 49, 0, 105, 110, 97, 1, 110, 97, 107, 115, 3, 70, 13, 50, 6, 113, 0, 105, 108, 101, 109, 109, 97, 3, 70, 13, 55, 106, 63, 35, 0, 105, 109, 101, 110, 2, 115, 105, 3, 70, 13, 63, 106, 50, 0, 105, 110, 103, 97, 97, 110, 3, 70, 13, 66, 79, 113, 50, 0, 105, 118, 105, 100, 101, 2, 110, 100, 3, 70, 13, 82, 13, 70, 106, 0, 4, 105, 115, 2, 107, 111, 101, 114, 115, 3, 70, 13, 87, 0, 105, 115, 2, 108, 111, 106, 97, 0, 105, 115, 2, 112, 117, 0, 105, 115, 8, 2, 105, 110, 14, 128, 132, 131, 0, 105, 115, 8, 2, 107, 114, 101, 0, 105, 115, 8, 2, 107, 117, 115, 115, 17, 65, 0, 105, 115, 8, 2, 111, 14, 128, 132, 131, 0, 105, 115, 8, 2, 116, 0, 105, 115, 115, 105, 112, 101, 108, 2, 105, 110, 3, 70, 13, 87, 2, 37, 48, 13, 55, 0, 105, 115, 115, 105, 112, 108, 105, 110, 101, 2, 25, 3, 70, 13, 87, 13, 48, 55, 37, 50, 13, 0, 105, 115, 116, 114, 111, 2, 102, 105, 101, 3, 70, 13, 87, 47, 34, 2, 40, 0, 105, 115, 116, 114, 105, 2, 98, 117, 3, 70, 13, 87, 47, 34, 13, 0, 105, 115, 107, 114, 101, 2, 115, 3, 70, 13, 87, 49, 34, 106, 0, 105, 103, 101, 114, 115, 3, 70, 13, 134, 13, 34, 87, 0, 105, 103, 116, 101, 114, 101, 2, 25, 3, 70, 13, 134, 47, 13, 34, 106, 0, 114, 111, 101, 102, 2, 103, 101, 101, 115, 3, 70, 34, 2, 40, 81, 0, 114, 117, 107, 107, 101, 8, 2, 114, 121, 3, 70, 34, 2, 109, 49, 13, 0, 114, 97, 109, 97, 2, 116, 117, 114, 103, 3, 70, 34, 2, 113, 63, 2, 35, 0, 114, 97, 2, 115, 116, 105, 101, 3, 70, 34, 35, 0, 114, 105, 108, 2, 17, 65, 3, 70, 34, 107, 55, 0, 114, 97, 8, 2, 115, 116, 3, 70, 34, 113, 0, 105, 101, 112, 101, 114, 2, 21, 3, 70, 37, 48, 13, 34, 0, 117, 2, 112, 108, 105, 17, 67, 3, 70, 40, 0, 4, 119, 1, 101, 103, 3, 70, 58, 0, 119, 1, 109, 0, 119, 1, 121, 98, 114, 101, 118, 0, 119, 2, 101, 114, 103, 0, 119, 101, 108, 109, 2, 32, 3, 70, 58, 110, 55, 14, 63, 0, 105, 2, 103, 25, 3, 70, 107, 0, 105, 115, 116, 101, 108, 3, 70, 107, 87, 47, 13, 55, 0, 111, 107, 116, 111, 114, 2, 25, 3, 70, 108, 49, 47, 13, 34, 0, 111, 107, 117, 3, 70, 108, 49, 116, 0, 111, 108, 2, 111, 115, 3, 70, 108, 55, 0, 111, 109, 8, 2, 17, 65, 17, 67, 17, 67, 3, 70, 108, 63, 0, 111, 110, 103, 97, 3, 70, 108, 66, 79, 35, 0, 97, 116, 101, 1, 105, 100, 110, 97, 107, 2, 17, 67, 3, 70, 113, 47, 13, 0, 97, 110, 105, 195, 171, 108, 3, 70, 113, 50, 37, 13, 55, 0, 111, 115, 105, 2, 115, 3, 70, 115, 87, 13, 0, 106, 8, 3, 73, 0, 106, 3, 78, 0, 106, 105, 101, 3, 78, 37, 0, 7, 6, 101, 0, 1, 105, 111, 111, 2, 110, 116, 106, 105, 101, 3, 0, 4, 2, 102, 101, 115, 105, 3, 2, 37, 0, 2, 109, 111, 115, 105, 0, 8, 2, 108, 108, 105, 112, 25, 0, 8, 108, 101, 105, 115, 2, 116, 106, 105, 101, 0, 108, 101, 107, 2, 116, 114, 111, 100, 101, 3, 2, 37, 55, 2, 106, 49, 0, 108, 101, 107, 116, 114, 3, 2, 37, 55, 106, 49, 47, 34, 0, 102, 102, 101, 107, 2, 25, 3, 2, 37, 81, 106, 49, 0, 118, 2, 101, 110, 116, 117, 101, 3, 2, 37, 82, 0, 118, 97, 108, 2, 117, 3, 2, 37, 82, 2, 35, 55, 0, 115, 115, 101, 110, 2, 115, 105, 3, 2, 37, 87, 106, 50, 0, 4, 1, 108, 108, 101, 116, 110, 105, 2, 107, 3, 2, 106, 0, 2, 107, 111, 110, 111, 21, 0, 8, 2, 107, 115, 0, 8, 2, 109, 105, 0, 116, 105, 2, 107, 101, 116, 3, 2, 106, 47, 2, 37, 0, 116, 105, 107, 101, 116, 116, 101, 2, 114, 17, 65, 3, 2, 106, 47, 2, 37, 49, 2, 106, 47, 114, 0, 4, 112, 105, 2, 100, 101, 17, 67, 3, 2, 106, 48, 2, 37, 0, 112, 105, 8, 2, 17, 67, 0, 112, 111, 117, 2, 108, 101, 116, 3, 2, 106, 48, 2, 40, 0, 107, 117, 2, 109, 101, 110, 105, 101, 3, 2, 106, 49, 2, 116, 0, 107, 119, 105, 2, 108, 105, 98, 114, 105, 3, 2, 106, 49, 58, 2, 37, 0, 120, 1, 108, 97, 2, 97, 110, 100, 3, 2, 106, 49, 86, 0, 107, 115, 97, 109, 105, 110, 2, 17, 65, 3, 2, 106, 49, 87, 2, 35, 63, 2, 37, 50, 0, 107, 115, 101, 2, 108, 108, 101, 110, 17, 67, 3, 2, 106, 49, 87, 13, 0, 107, 115, 101, 103, 101, 2, 17, 67, 17, 65, 3, 2, 106, 49, 87, 13, 134, 114, 0, 107, 115, 116, 114, 111, 2, 118, 101, 114, 3, 2, 106, 49, 87, 47, 34, 2, 40, 0, 107, 115, 116, 114, 101, 2, 109, 105, 115, 3, 2, 106, 49, 87, 47, 34, 13, 0, 107, 115, 116, 101, 114, 110, 8, 3, 2, 106, 49, 87, 47, 110, 34, 14, 50, 0, 107, 115, 112, 108, 105, 2, 115, 105, 101, 116, 3, 2, 106, 49, 87, 48, 55, 13, 0, 4, 108, 101, 2, 103, 97, 110, 17, 67, 3, 2, 106, 55, 13, 0, 108, 101, 2, 103, 105, 101, 0, 108, 101, 109, 101, 110, 116, 3, 2, 106, 55, 13, 63, 106, 50, 47, 0, 4, 109, 2, 112, 105, 114, 3, 2, 106, 63, 0, 109, 8, 2, 98, 108, 101, 0, 109, 102, 105, 2, 115, 101, 101, 109, 3, 2, 106, 63, 81, 2, 37, 0, 119, 111, 2, 108, 117, 115, 105, 3, 2, 106, 82, 2, 108, 0, 115, 8, 2, 107, 97, 114, 112, 3, 2, 106, 87, 0, 115, 105, 1, 100, 21, 2, 109, 97, 3, 2, 106, 87, 2, 37, 0, 115, 116, 114, 111, 2, 103, 101, 3, 2, 106, 87, 47, 34, 2, 40, 0, 115, 116, 101, 8, 2, 116, 3, 2, 106, 87, 47, 114, 0, 115, 107, 97, 2, 112, 97, 100, 101, 3, 2, 106, 87, 49, 13, 0, 115, 107, 97, 100, 101, 114, 3, 2, 106, 87, 49, 113, 70, 13, 34, 0, 114, 107, 101, 2, 110, 12, 3, 2, 110, 34, 49, 106, 0, 4, 2, 107, 108, 105, 112, 25, 3, 2, 114, 0, 8, 2, 103, 105, 112, 116, 0, 8, 2, 114, 111, 115, 105, 101, 0, 114, 101, 2, 107, 115, 105, 17, 65, 3, 2, 114, 34, 106, 0, 109, 97, 108, 106, 101, 3, 2, 114, 63, 35, 55, 57, 13, 0, 119, 101, 8, 2, 114, 101, 100, 3, 2, 114, 82, 13, 0, 119, 101, 119, 105, 103, 2, 116, 105, 103, 3, 2, 114, 82, 13, 82, 107, 134, 0, 119, 105, 103, 2, 100, 117, 3, 2, 114, 82, 13, 134, 0, 115, 111, 116, 101, 2, 114, 105, 101, 3, 2, 114, 87, 2, 40, 47, 114, 0, 103, 111, 115, 101, 110, 116, 114, 105, 101, 3, 2, 114, 134, 2, 40, 87, 106, 50, 47, 34, 37, 0, 103, 97, 8, 2, 108, 3, 2, 114, 134, 113, 0, 105, 101, 110, 97, 97, 114, 100, 105, 103, 3, 2, 121, 13, 50, 113, 34, 70, 13, 134, 0, 117, 2, 102, 111, 114, 105, 101, 3, 2, 126, 0, 117, 114, 111, 8, 2, 112, 101, 3, 2, 126, 34, 2, 115, 0, 117, 102, 111, 2, 114, 105, 101, 32, 24, 3, 2, 126, 81, 2, 115, 0, 118, 97, 110, 103, 8, 3, 4, 114, 81, 35, 66, 134, 0, 8, 17, 67, 2, 111, 110, 32, 3, 6, 37, 0, 4, 1, 17, 67, 2, 115, 107, 32, 12, 12, 3, 6, 106, 0, 1, 17, 67, 2, 115, 107, 101, 32, 12, 12, 0, 1, 17, 67, 21, 2, 115, 107, 101, 114, 32, 0, 1, 114, 97, 2, 115, 115, 101, 32, 0, 100, 106, 105, 101, 3, 6, 106, 12, 37, 78, 37, 0, 107, 116, 111, 109, 105, 101, 1, 17, 67, 3, 6, 106, 49, 47, 40, 63, 37, 0, 1, 115, 21, 2, 108, 102, 100, 101, 3, 6, 110, 0, 4, 1, 100, 21, 2, 115, 101, 32, 12, 3, 6, 114, 0, 1, 112, 2, 114, 105, 110, 103, 0, 1, 112, 101, 111, 114, 2, 114, 105, 110, 103, 0, 4, 114, 1, 102, 102, 111, 116, 115, 2, 17, 65, 3, 6, 114, 34, 0, 114, 1, 110, 105, 2, 17, 65, 0, 114, 105, 110, 103, 1, 117, 3, 6, 114, 34, 13, 66, 0, 116, 101, 110, 115, 8, 3, 6, 114, 47, 13, 50, 87, 0, 108, 101, 1, 117, 17, 67, 2, 25, 12, 3, 6, 114, 55, 13, 0, 105, 1, 114, 2, 115, 101, 110, 3, 6, 121, 0, 105, 107, 101, 8, 3, 6, 121, 49, 13, 0, 105, 110, 1, 21, 2, 100, 105, 103, 3, 6, 121, 50, 0, 108, 119, 101, 114, 115, 1, 17, 67, 3, 7, 110, 55, 82, 13, 34, 87, 0, 1, 17, 67, 2, 110, 100, 104, 3, 8, 13, 0, 107, 111, 110, 1, 10, 2, 111, 21, 3, 10, 2, 106, 49, 2, 40, 50, 0, 105, 1, 17, 67, 21, 2, 108, 97, 110, 100, 3, 10, 4, 121, 0, 105, 1, 21, 2, 115, 101, 110, 3, 10, 6, 121, 0, 114, 116, 115, 1, 21, 2, 32, 3, 10, 110, 34, 47, 87, 0, 114, 107, 101, 1, 100, 108, 117, 107, 115, 3, 10, 110, 34, 49, 106, 0, 114, 103, 8, 114, 101, 108, 108, 97, 3, 10, 110, 34, 134, 0, 116, 101, 114, 1, 114, 101, 105, 109, 3, 10, 114, 47, 13, 34, 0, 4, 1, 10, 2, 32, 3, 13, 0, 1, 10, 2, 108, 17, 67, 32, 0, 1, 10, 2, 108, 32, 0, 1, 10, 2, 109, 32, 0, 1, 10, 2, 114, 32, 0, 1, 17, 67, 2, 104, 0, 1, 17, 67, 2, 107, 97, 109, 112, 12, 0, 1, 17, 67, 2, 107, 97, 110, 116, 12, 0, 1, 17, 67, 2, 108, 116, 106, 105, 101, 0, 1, 17, 67, 2, 109, 97, 97, 116, 0, 1, 17, 67, 2, 109, 97, 110, 0, 1, 17, 67, 2, 109, 97, 114, 105, 101, 0, 1, 17, 67, 2, 112, 97, 100, 0, 1, 17, 67, 2, 112, 97, 110, 0, 1, 17, 67, 2, 116, 111, 101, 32, 0, 1, 17, 67, 2, 118, 0, 1, 17, 67, 2, 119, 97, 97, 114, 0, 1, 17, 67, 2, 119, 105, 110, 107, 101, 108, 0, 1, 17, 67, 10, 2, 103, 97, 110, 103, 101, 114, 0, 1, 17, 67, 10, 2, 108, 114, 17, 65, 0, 1, 17, 67, 10, 2, 115, 107, 21, 0, 1, 17, 67, 11, 2, 17, 67, 0, 1, 17, 67, 17, 65, 2, 108, 104, 0, 1, 17, 67, 17, 65, 17, 67, 2, 17, 67, 17, 67, 0, 1, 17, 67, 17, 65, 17, 67, 2, 114, 114, 0, 1, 17, 67, 21, 2, 98, 111, 0, 1, 17, 67, 21, 2, 98, 117, 0, 1, 17, 67, 21, 2, 98, 121, 0, 1, 17, 67, 21, 2, 100, 105, 101, 110, 0, 1, 17, 67, 21, 2, 103, 101, 17, 67, 21, 0, 1, 17, 67, 21, 2, 103, 114, 111, 101, 112, 0, 1, 17, 67, 21, 2, 106, 0, 1, 17, 67, 21, 2, 107, 111, 100, 101, 25, 0, 1, 17, 67, 21, 2, 107, 111, 109, 21, 0, 1, 17, 67, 21, 2, 109, 97, 97, 108, 32, 0, 1, 17, 67, 21, 2, 109, 97, 108, 101, 32, 0, 1, 17, 67, 21, 2, 114, 101, 101, 107, 25, 0, 1, 17, 67, 21, 2, 114, 101, 195, 171, 0, 1, 17, 67, 21, 2, 114, 104, 0, 1, 17, 67, 21, 2, 116, 97, 97, 108, 0, 1, 17, 67, 21, 2, 119, 97, 32, 0, 1, 17, 67, 21, 2, 119, 97, 101, 110, 0, 1, 17, 67, 101, 111, 17, 67, 2, 17, 67, 12, 0, 1, 17, 67, 105, 117, 2, 25, 12, 0, 1, 17, 67, 117, 101, 25, 2, 108, 17, 67, 21, 0, 1, 21, 2, 115, 112, 101, 108, 32, 0, 1, 25, 2, 112, 111, 111, 114, 116, 0, 1, 98, 10, 2, 115, 21, 0, 1, 98, 17, 65, 2, 119, 97, 0, 1, 100, 10, 2, 114, 21, 12, 12, 0, 1, 100, 17, 67, 2, 116, 114, 0, 1, 100, 21, 2, 98, 108, 0, 1, 100, 21, 2, 107, 108, 97, 115, 0, 1, 100, 21, 2, 107, 114, 0, 1, 100, 21, 2, 115, 21, 0, 1, 100, 97, 114, 114, 111, 111, 118, 2, 17, 67, 0, 1, 100, 100, 17, 65, 2, 108, 101, 32, 0, 1, 100, 100, 105, 109, 2, 21, 0, 1, 100, 102, 101, 105, 108, 2, 17, 67, 0, 1, 100, 103, 117, 101, 114, 118, 2, 17, 67, 0, 1, 100, 108, 97, 97, 110, 2, 17, 67, 0, 1, 100, 108, 101, 101, 119, 2, 119, 17, 65, 0, 1, 100, 108, 101, 112, 115, 2, 17, 67, 0, 1, 100, 108, 105, 119, 0, 1, 100, 108, 105, 119, 2, 107, 17, 65, 0, 1, 100, 110, 2, 108, 105, 110, 103, 0, 1, 100, 110, 17, 65, 2, 108, 17, 67, 0, 1, 100, 110, 97, 17, 67, 2, 17, 67, 0, 1, 100, 110, 97, 97, 109, 2, 108, 17, 65, 0, 1, 100, 110, 101, 105, 114, 118, 2, 17, 67, 0, 1, 100, 110, 105, 108, 98, 2, 17, 67, 21, 0, 1, 100, 110, 105, 108, 98, 2, 108, 105, 110, 103, 0, 1, 100, 110, 111, 17, 67, 2, 17, 67, 17, 65, 0, 1, 100, 110, 117, 107, 2, 21, 0, 1, 100, 111, 107, 2, 17, 67, 0, 1, 100, 114, 111, 111, 110, 2, 17, 67, 0, 1, 100, 121, 2, 108, 0, 1, 102, 108, 105, 107, 115, 2, 114, 0, 1, 102, 121, 115, 2, 114, 0, 1, 103, 110, 97, 108, 115, 2, 17, 67, 0, 1, 103, 110, 105, 17, 67, 2, 108, 17, 65, 0, 1, 103, 110, 105, 17, 67, 2, 108, 17, 67, 21, 0, 1, 103, 110, 105, 110, 101, 107, 2, 21, 0, 1, 105, 97, 97, 2, 17, 67, 0, 1, 105, 101, 0, 1, 105, 111, 111, 2, 17, 67, 0, 1, 107, 21, 2, 108, 100, 101, 32, 0, 1, 107, 21, 2, 114, 97, 97, 100, 0, 1, 107, 97, 108, 98, 2, 114, 0, 1, 107, 101, 111, 2, 17, 67, 0, 1, 107, 110, 2, 108, 17, 67, 0, 1, 107, 110, 17, 65, 2, 114, 21, 0, 1, 107, 110, 105, 119, 2, 108, 0, 1, 107, 111, 112, 115, 2, 17, 67, 0, 1, 107, 114, 101, 119, 2, 114, 115, 0, 1, 107, 114, 105, 115, 2, 108, 0, 1, 108, 2, 109, 111, 101, 110, 0, 1, 108, 97, 104, 2, 114, 17, 67, 21, 0, 1, 108, 97, 109, 2, 100, 121, 0, 1, 108, 97, 114, 101, 110, 105, 109, 2, 17, 67, 0, 1, 108, 101, 119, 117, 106, 2, 17, 67, 0, 1, 108, 105, 101, 114, 116, 2, 114, 17, 67, 0, 1, 108, 108, 105, 119, 2, 17, 67, 0, 1, 108, 111, 114, 116, 2, 17, 67, 21, 0, 1, 109, 2, 108, 101, 110, 100, 0, 1, 109, 2, 108, 105, 110, 103, 0, 1, 109, 97, 115, 0, 1, 109, 97, 115, 21, 2, 110, 115, 32, 0, 1, 109, 101, 110, 21, 2, 110, 115, 32, 0, 1, 109, 108, 101, 17, 67, 2, 116, 25, 0, 1, 109, 111, 107, 21, 2, 110, 115, 32, 0, 1, 109, 111, 115, 2, 114, 0, 1, 109, 114, 2, 114, 116, 106, 105, 101, 0, 1, 110, 97, 17, 67, 17, 67, 2, 17, 67, 17, 65, 0, 1, 110, 101, 105, 17, 67, 2, 114, 17, 67, 21, 0, 1, 110, 110, 17, 65, 17, 67, 2, 17, 67, 17, 65, 0, 1, 110, 110, 97, 112, 2, 17, 67, 0, 1, 110, 117, 101, 2, 114, 21, 0, 1, 112, 2, 116, 97, 108, 106, 101, 0, 1, 112, 2, 116, 97, 108, 106, 101, 0, 1, 112, 17, 65, 2, 108, 105, 110, 103, 0, 1, 112, 17, 65, 17, 67, 2, 114, 107, 17, 67, 0, 1, 112, 17, 67, 17, 65, 17, 67, 2, 114, 108, 0, 1, 112, 21, 2, 108, 104, 0, 1, 112, 21, 2, 114, 116, 106, 105, 101, 0, 1, 112, 105, 104, 2, 114, 0, 1, 112, 109, 2, 108, 100, 101, 32, 0, 1, 112, 109, 21, 2, 108, 17, 67, 21, 0, 1, 112, 109, 111, 107, 2, 116, 21, 0, 1, 112, 112, 2, 17, 67, 21, 12, 0, 1, 112, 114, 2, 114, 17, 67, 17, 67, 0, 1, 112, 114, 101, 119, 2, 114, 115, 17, 65, 0, 1, 112, 114, 117, 112, 2, 114, 0, 1, 112, 115, 2, 100, 0, 1, 112, 115, 2, 108, 111, 110, 107, 0, 1, 114, 101, 100, 101, 111, 103, 2, 21, 0, 1, 114, 101, 105, 17, 67, 29, 2, 21, 0, 1, 114, 114, 111, 2, 108, 0, 1, 115, 10, 2, 108, 21, 0, 1, 115, 25, 2, 110, 97, 0, 1, 115, 100, 110, 97, 104, 101, 100, 2, 17, 67, 21, 0, 1, 115, 101, 105, 2, 98, 0, 1, 115, 101, 105, 2, 102, 0, 1, 115, 105, 101, 2, 98, 101, 0, 1, 115, 105, 101, 2, 115, 116, 0, 1, 115, 107, 21, 2, 109, 17, 67, 0, 1, 115, 107, 117, 117, 108, 0, 1, 115, 111, 107, 114, 97, 110, 2, 17, 67, 0, 1, 115, 111, 108, 2, 115, 0, 1, 115, 111, 114, 2, 17, 67, 17, 65, 0, 1, 115, 117, 101, 114, 2, 21, 0, 1, 115, 117, 111, 112, 2, 17, 67, 0, 1, 116, 10, 2, 114, 21, 0, 1, 116, 17, 65, 10, 2, 98, 17, 65, 21, 0, 1, 117, 111, 2, 17, 67, 0, 1, 118, 2, 110, 110, 111, 21, 12, 0, 1, 119, 2, 108, 105, 110, 103, 0, 1, 119, 10, 2, 102, 0, 1, 119, 17, 65, 2, 98, 17, 65, 0, 1, 119, 97, 2, 17, 67, 21, 0, 1, 119, 101, 107, 115, 2, 17, 67, 0, 1, 119, 101, 108, 2, 110, 115, 0, 1, 119, 108, 97, 104, 2, 25, 0, 1, 119, 108, 111, 17, 67, 2, 17, 67, 0, 1, 119, 114, 2, 115, 0, 1, 119, 117, 101, 17, 67, 2, 108, 0, 1, 119, 121, 2, 114, 17, 65, 0, 1, 119, 121, 116, 115, 2, 17, 67, 0, 1, 121, 17, 67, 2, 17, 67, 12, 0, 1, 121, 17, 67, 2, 17, 67, 17, 67, 0, 2, 17, 67, 111, 117, 120, 0, 2, 110, 97, 114, 101, 115, 32, 0, 8, 100, 97, 2, 108, 17, 67, 0, 8, 100, 105, 101, 109, 2, 17, 67, 0, 8, 100, 110, 101, 101, 2, 17, 67, 17, 65, 0, 8, 108, 101, 105, 115, 2, 21, 0, 8, 112, 111, 2, 110, 0, 8, 112, 115, 97, 114, 2, 114, 0, 8, 115, 110, 101, 109, 0, 8, 115, 110, 101, 109, 2, 107, 0, 8, 119, 101, 2, 12, 12, 0, 4, 1, 17, 67, 2, 114, 106, 3, 13, 6, 0, 1, 114, 112, 114, 101, 116, 110, 105, 2, 116, 17, 65, 0, 4, 1, 17, 67, 2, 117, 105, 116, 3, 13, 10, 0, 1, 17, 67, 10, 2, 117, 117, 0, 1, 17, 67, 21, 2, 97, 17, 67, 17, 67, 0, 1, 17, 67, 21, 2, 111, 111, 114, 0, 1, 100, 110, 111, 104, 2, 21, 0, 1, 110, 105, 101, 116, 110, 111, 102, 2, 17, 67, 0, 1, 117, 111, 2, 97, 0, 4, 114, 1, 17, 67, 21, 2, 116, 121, 100, 3, 13, 34, 0, 114, 1, 102, 102, 2, 21, 0, 114, 1, 105, 17, 65, 2, 17, 65, 0, 114, 1, 105, 101, 108, 2, 115, 0, 114, 105, 101, 1, 110, 2, 32, 3, 13, 34, 6, 37, 0, 4, 114, 101, 115, 1, 17, 67, 3, 13, 34, 6, 106, 87, 0, 114, 101, 115, 115, 1, 17, 67, 0, 114, 105, 1, 110, 117, 101, 2, 110, 3, 13, 34, 6, 107, 0, 114, 1, 112, 111, 108, 2, 17, 65, 3, 13, 34, 10, 0, 114, 101, 1, 10, 2, 32, 3, 13, 34, 13, 0, 114, 101, 115, 1, 116, 97, 108, 3, 13, 34, 13, 87, 0, 4, 114, 115, 1, 10, 2, 32, 3, 13, 34, 87, 0, 114, 115, 1, 112, 108, 101, 104, 2, 32, 0, 114, 115, 1, 112, 114, 101, 119, 2, 32, 0, 114, 115, 1, 112, 114, 111, 100, 2, 32, 0, 114, 115, 1, 119, 101, 105, 2, 116, 101, 114, 0, 114, 115, 121, 100, 115, 1, 17, 67, 3, 13, 34, 87, 121, 47, 87, 0, 114, 101, 1, 115, 110, 97, 100, 21, 2, 25, 3, 13, 34, 106, 0, 114, 105, 103, 1, 25, 10, 3, 13, 34, 107, 134, 0, 4, 114, 105, 103, 101, 1, 17, 65, 17, 65, 3, 13, 34, 107, 134, 13, 0, 114, 105, 103, 101, 1, 25, 10, 0, 4, 114, 101, 105, 1, 10, 2, 32, 3, 13, 34, 121, 0, 114, 121, 1, 21, 2, 32, 12, 0, 114, 121, 1, 21, 2, 101, 32, 0, 107, 101, 1, 110, 2, 32, 3, 13, 49, 13, 0, 108, 1, 102, 102, 2, 21, 3, 13, 55, 0, 108, 97, 103, 116, 105, 103, 3, 13, 55, 6, 35, 134, 47, 13, 134, 0, 108, 1, 103, 110, 97, 109, 2, 17, 65, 3, 13, 55, 10, 0, 108, 101, 1, 10, 2, 32, 3, 13, 55, 13, 0, 108, 105, 107, 1, 10, 2, 105, 110, 103, 3, 13, 55, 13, 49, 0, 108, 105, 107, 104, 101, 105, 100, 1, 10, 3, 13, 55, 13, 49, 121, 47, 0, 108, 105, 103, 97, 1, 21, 2, 32, 3, 13, 55, 37, 134, 35, 0, 108, 97, 97, 114, 3, 13, 55, 113, 34, 0, 108, 111, 111, 115, 1, 17, 67, 3, 13, 55, 115, 87, 0, 108, 111, 115, 101, 1, 17, 67, 3, 13, 55, 115, 87, 13, 0, 100, 101, 114, 109, 1, 17, 67, 21, 3, 13, 70, 110, 34, 14, 63, 10, 0, 100, 97, 110, 115, 1, 17, 67, 21, 3, 13, 70, 131, 50, 87, 0, 119, 101, 114, 107, 1, 17, 67, 21, 3, 13, 82, 110, 34, 49, 0, 119, 121, 1, 17, 67, 2, 17, 67, 3, 13, 82, 121, 0, 4, 115, 1, 17, 67, 17, 65, 17, 65, 17, 67, 29, 2, 32, 3, 13, 87, 0, 115, 1, 17, 67, 17, 65, 29, 2, 32, 0, 115, 1, 100, 17, 65, 17, 65, 17, 65, 17, 67, 29, 2, 32, 0, 115, 1, 100, 17, 67, 10, 2, 32, 0, 115, 1, 105, 17, 65, 17, 65, 2, 32, 0, 115, 1, 107, 2, 32, 0, 4, 115, 115, 1, 17, 67, 21, 2, 32, 3, 21, 0, 120, 2, 12, 0, 121, 2, 32, 0, 4, 1, 17, 67, 101, 111, 17, 67, 2, 116, 106, 105, 101, 3, 37, 0, 1, 110, 110, 97, 112, 2, 116, 106, 105, 101, 0, 116, 106, 105, 101, 1, 10, 2, 12, 3, 37, 78, 37, 0, 116, 106, 105, 101, 115, 1, 110, 110, 3, 37, 78, 37, 87, 0, 4, 1, 17, 67, 2, 107, 115, 12, 12, 3, 106, 0, 1, 17, 67, 2, 107, 116, 21, 12, 12, 0, 1, 17, 67, 2, 109, 109, 12, 12, 0, 1, 17, 67, 11, 2, 116, 116, 12, 0, 1, 17, 67, 17, 65, 17, 67, 2, 17, 67, 11, 0, 1, 100, 2, 102, 105, 0, 1, 100, 101, 114, 112, 2, 115, 116, 105, 0, 1, 106, 2, 107, 0, 1, 107, 21, 2, 116, 116, 21, 12, 0, 1, 108, 10, 2, 109, 32, 0, 1, 114, 2, 100, 105, 103, 101, 114, 105, 110, 103, 0, 2, 17, 67, 0, 8, 119, 2, 115, 107, 117, 115, 0, 1, 100, 2, 109, 111, 110, 115, 3, 106, 2, 0, 1, 17, 67, 2, 104, 108, 101, 32, 12, 3, 106, 12, 0, 116, 106, 105, 101, 115, 1, 110, 17, 67, 3, 106, 37, 78, 37, 87, 0, 112, 105, 108, 101, 112, 8, 3, 106, 48, 13, 55, 6, 106, 48, 0, 112, 115, 1, 17, 67, 21, 2, 12, 3, 106, 48, 87, 0, 120, 105, 107, 1, 109, 3, 106, 49, 87, 2, 37, 49, 0, 120, 97, 115, 1, 116, 3, 106, 49, 87, 13, 87, 0, 107, 115, 116, 97, 115, 101, 3, 106, 49, 87, 47, 6, 113, 87, 13, 0, 107, 115, 116, 101, 114, 8, 2, 25, 3, 106, 49, 87, 47, 13, 34, 0, 107, 115, 116, 114, 97, 2, 25, 3, 106, 49, 87, 47, 34, 35, 0, 118, 111, 108, 117, 115, 3, 106, 82, 108, 55, 6, 116, 87, 0, 4, 1, 17, 67, 2, 107, 3, 110, 0, 1, 17, 67, 2, 107, 107, 21, 12, 0, 1, 17, 67, 11, 2, 103, 103, 0, 1, 17, 67, 17, 65, 17, 67, 2, 103, 103, 0, 1, 17, 67, 21, 2, 103, 100, 12, 0, 1, 17, 67, 21, 2, 108, 107, 32, 12, 0, 1, 17, 67, 21, 2, 108, 107, 101, 32, 0, 1, 100, 21, 2, 114, 110, 115, 116, 12, 12, 0, 1, 100, 100, 108, 2, 108, 103, 17, 65, 17, 67, 0, 1, 107, 115, 21, 2, 108, 0, 1, 108, 108, 2, 108, 25, 0, 1, 109, 21, 2, 108, 100, 0, 1, 110, 107, 2, 108, 0, 1, 112, 115, 17, 67, 2, 108, 100, 0, 1, 112, 115, 17, 67, 2, 108, 115, 0, 1, 112, 115, 101, 103, 2, 108, 100, 0, 1, 112, 115, 117, 111, 107, 115, 2, 108, 32, 0, 1, 112, 115, 121, 108, 98, 2, 108, 25, 0, 1, 115, 17, 67, 2, 108, 102, 0, 1, 115, 17, 67, 2, 108, 108, 101, 32, 0, 1, 115, 107, 110, 111, 114, 116, 2, 108, 0, 1, 115, 114, 101, 105, 101, 2, 108, 0, 1, 116, 17, 65, 17, 67, 2, 103, 110, 0, 1, 118, 101, 17, 67, 2, 103, 25, 0, 1, 119, 17, 65, 17, 67, 2, 114, 107, 17, 65, 0, 1, 119, 17, 65, 17, 67, 2, 114, 107, 25, 0, 1, 119, 21, 2, 108, 115, 121, 110, 0, 1, 119, 108, 111, 98, 2, 114, 107, 32, 0, 2, 103, 25, 0, 2, 108, 25, 0, 2, 114, 0, 4, 114, 8, 2, 98, 3, 110, 34, 6, 0, 114, 8, 2, 118, 0, 114, 112, 1, 17, 67, 21, 2, 32, 3, 110, 34, 48, 0, 114, 112, 101, 1, 17, 67, 21, 2, 32, 3, 110, 34, 48, 13, 0, 114, 112, 105, 101, 1, 17, 67, 21, 2, 32, 3, 110, 34, 48, 37, 0, 4, 114, 107, 101, 1, 109, 2, 110, 100, 3, 110, 34, 49, 13, 0, 114, 107, 101, 1, 112, 2, 110, 100, 0, 114, 107, 101, 1, 119, 2, 110, 100, 0, 114, 100, 101, 8, 2, 17, 67, 3, 110, 34, 70, 13, 0, 114, 102, 1, 17, 67, 21, 2, 32, 3, 110, 34, 81, 0, 114, 119, 101, 1, 17, 67, 21, 2, 32, 3, 110, 34, 82, 13, 0, 4, 114, 115, 1, 112, 102, 2, 32, 3, 110, 34, 87, 0, 114, 115, 1, 112, 103, 2, 32, 0, 114, 115, 1, 112, 107, 2, 32, 0, 114, 115, 1, 112, 108, 2, 32, 0, 114, 115, 1, 112, 110, 2, 32, 0, 114, 115, 1, 112, 114, 2, 32, 0, 108, 112, 101, 8, 3, 110, 55, 48, 13, 0, 4, 114, 115, 1, 107, 103, 3, 111, 34, 87, 0, 114, 115, 1, 107, 116, 0, 114, 115, 1, 112, 117, 111, 108, 98, 0, 4, 3, 114, 0, 1, 17, 67, 2, 107, 17, 65, 12, 0, 1, 100, 17, 67, 17, 65, 2, 108, 101, 32, 0, 1, 100, 100, 17, 67, 2, 108, 101, 32, 0, 1, 100, 101, 111, 116, 2, 108, 105, 110, 103, 0, 1, 100, 110, 105, 2, 108, 105, 110, 103, 0, 1, 100, 115, 17, 67, 2, 108, 101, 32, 0, 1, 108, 108, 2, 115, 101, 114, 0, 1, 116, 105, 17, 67, 2, 114, 105, 110, 103, 0, 1, 116, 110, 171, 195, 105, 2, 114, 21, 110, 0, 1, 119, 21, 2, 103, 101, 110, 100, 101, 0, 1, 119, 114, 2, 115, 101, 32, 0, 2, 17, 67, 17, 65, 0, 8, 100, 110, 101, 101, 2, 108, 105, 103, 0, 195, 171, 0, 114, 101, 1, 119, 115, 2, 32, 3, 114, 12, 34, 13, 0, 4, 114, 101, 1, 108, 21, 2, 32, 3, 114, 34, 13, 0, 114, 101, 8, 0, 108, 108, 101, 110, 100, 101, 8, 3, 114, 55, 6, 106, 50, 70, 13, 0, 108, 108, 101, 110, 100, 105, 103, 8, 3, 114, 55, 6, 106, 50, 70, 13, 134, 0, 108, 97, 97, 114, 1, 100, 114, 111, 111, 3, 114, 55, 113, 34, 0, 109, 97, 1, 17, 67, 2, 32, 3, 114, 63, 35, 0, 100, 101, 1, 17, 67, 2, 32, 3, 114, 70, 13, 0, 100, 101, 108, 8, 3, 114, 70, 13, 55, 0, 100, 101, 115, 1, 17, 67, 2, 32, 3, 114, 70, 13, 87, 0, 119, 101, 108, 1, 17, 67, 2, 17, 65, 3, 114, 82, 13, 55, 0, 119, 105, 103, 104, 101, 105, 2, 100, 3, 114, 82, 13, 134, 4, 121, 0, 4, 105, 3, 121, 0, 121, 0, 105, 101, 114, 3, 121, 13, 34, 0, 105, 110, 100, 2, 101, 107, 115, 3, 121, 50, 47, 10, 0, 117, 3, 126, 0, 117, 101, 1, 17, 67, 3, 126, 13, 0, 117, 110, 116, 106, 105, 101, 3, 126, 37, 66, 78, 37, 0, 7, 6, 102, 0, 2, 102, 3, 0, 4, 105, 101, 108, 100, 3, 21, 0, 105, 116, 122, 8, 0, 117, 108, 1, 21, 2, 32, 0, 3, 81, 0, 4, 97, 2, 98, 114, 105, 101, 107, 3, 81, 2, 35, 0, 97, 2, 110, 97, 116, 105, 0, 97, 2, 116, 97, 21, 0, 97, 114, 105, 2, 115, 101, 195, 171, 114, 3, 81, 2, 35, 34, 2, 37, 0, 97, 114, 109, 97, 2, 115, 101, 117, 116, 3, 81, 2, 35, 34, 63, 2, 35, 0, 97, 116, 2, 115, 111, 101, 110, 3, 81, 2, 35, 47, 0, 97, 107, 2, 116, 111, 114, 101, 3, 81, 2, 35, 49, 0, 97, 107, 117, 108, 2, 116, 101, 105, 116, 3, 81, 2, 35, 49, 2, 109, 55, 0, 97, 107, 116, 117, 2, 114, 101, 114, 105, 3, 81, 2, 35, 49, 47, 2, 116, 0, 4, 97, 110, 2, 102, 97, 114, 101, 3, 81, 2, 35, 50, 0, 97, 110, 8, 2, 116, 111, 0, 97, 110, 116, 97, 2, 115, 17, 65, 3, 81, 2, 35, 50, 47, 2, 35, 0, 97, 109, 105, 2, 108, 105, 17, 65, 3, 81, 2, 35, 63, 37, 0, 97, 98, 114, 105, 2, 17, 67, 17, 65, 3, 81, 2, 35, 69, 34, 2, 37, 0, 97, 115, 105, 108, 105, 3, 81, 2, 35, 87, 13, 55, 2, 37, 0, 97, 115, 101, 2, 116, 25, 3, 81, 2, 35, 87, 106, 0, 97, 115, 97, 100, 101, 3, 81, 2, 35, 87, 113, 70, 13, 0, 4, 105, 2, 115, 97, 110, 116, 3, 81, 2, 37, 0, 105, 8, 2, 110, 97, 21, 0, 105, 97, 115, 107, 111, 3, 81, 2, 37, 35, 87, 49, 2, 40, 0, 111, 114, 101, 2, 108, 3, 81, 2, 40, 34, 110, 0, 111, 110, 101, 2, 116, 105, 101, 3, 81, 2, 40, 50, 114, 0, 101, 2, 109, 105, 110, 17, 65, 3, 81, 2, 106, 0, 101, 114, 111, 2, 109, 111, 3, 81, 2, 106, 34, 2, 40, 0, 101, 100, 101, 2, 114, 97, 3, 81, 2, 106, 70, 13, 0, 101, 115, 115, 111, 114, 2, 97, 21, 3, 81, 2, 106, 87, 13, 34, 0, 111, 2, 115, 115, 105, 101, 108, 3, 81, 2, 108, 0, 111, 114, 8, 2, 17, 67, 21, 3, 81, 2, 108, 34, 0, 111, 114, 109, 97, 2, 108, 105, 101, 110, 3, 81, 2, 108, 34, 63, 2, 35, 0, 111, 114, 109, 105, 2, 100, 97, 3, 81, 2, 108, 34, 63, 2, 37, 0, 111, 114, 109, 117, 2, 108, 105, 101, 114, 3, 81, 2, 108, 34, 63, 2, 116, 0, 111, 110, 2, 116, 101, 105, 110, 3, 81, 2, 108, 50, 0, 111, 110, 100, 117, 101, 3, 81, 2, 108, 50, 70, 116, 0, 111, 115, 2, 102, 97, 3, 81, 2, 108, 87, 0, 117, 110, 103, 2, 101, 3, 81, 2, 109, 66, 134, 0, 101, 8, 2, 116, 97, 21, 3, 81, 2, 114, 0, 111, 116, 111, 2, 115, 116, 97, 3, 81, 2, 115, 47, 2, 40, 0, 111, 116, 111, 103, 101, 2, 110, 105, 101, 3, 81, 2, 115, 47, 2, 40, 134, 114, 0, 111, 110, 101, 2, 116, 105, 101, 107, 3, 81, 2, 115, 50, 13, 0, 117, 8, 2, 116, 105, 3, 81, 2, 116, 0, 117, 115, 105, 2, 108, 108, 17, 65, 3, 81, 2, 116, 87, 13, 0, 121, 110, 103, 101, 2, 118, 111, 101, 108, 105, 3, 81, 2, 121, 50, 134, 13, 0, 111, 114, 8, 2, 115, 101, 32, 3, 81, 6, 108, 34, 0, 111, 110, 105, 101, 115, 1, 21, 3, 81, 6, 115, 50, 37, 87, 0, 4, 105, 2, 115, 105, 101, 107, 3, 81, 13, 0, 105, 2, 115, 107, 17, 65, 0, 101, 114, 2, 119, 101, 101, 108, 3, 81, 13, 34, 0, 101, 110, 111, 109, 2, 101, 3, 81, 13, 50, 2, 108, 63, 0, 101, 110, 111, 109, 101, 110, 2, 17, 65, 21, 3, 81, 13, 50, 2, 108, 63, 13, 50, 0, 4, 101, 108, 1, 21, 2, 101, 110, 100, 3, 81, 13, 55, 0, 101, 108, 1, 21, 2, 105, 110, 103, 0, 105, 108, 105, 2, 112, 112, 17, 65, 3, 81, 13, 55, 13, 0, 105, 108, 105, 115, 116, 121, 110, 3, 81, 13, 55, 13, 87, 47, 6, 121, 50, 0, 105, 108, 108, 101, 2, 116, 3, 81, 13, 55, 106, 0, 101, 115, 115, 111, 114, 101, 2, 32, 3, 81, 13, 87, 115, 34, 13, 0, 114, 97, 2, 103, 105, 101, 108, 3, 81, 34, 2, 35, 0, 4, 114, 97, 110, 2, 17, 67, 105, 110, 97, 3, 81, 34, 2, 35, 50, 0, 114, 97, 110, 8, 2, 17, 67, 105, 115, 17, 67, 17, 65, 0, 114, 97, 110, 103, 105, 2, 112, 97, 110, 105, 3, 81, 34, 2, 35, 66, 2, 37, 0, 114, 101, 2, 107, 119, 101, 110, 3, 81, 34, 2, 37, 0, 114, 111, 110, 116, 2, 17, 65, 21, 3, 81, 34, 2, 108, 50, 47, 0, 114, 117, 2, 115, 116, 114, 3, 81, 34, 2, 109, 0, 114, 105, 107, 107, 97, 100, 101, 2, 108, 3, 81, 34, 13, 49, 13, 70, 110, 0, 114, 101, 117, 100, 3, 81, 34, 122, 70, 0, 97, 2, 108, 97, 110, 107, 115, 3, 81, 35, 0, 105, 110, 101, 1, 114, 111, 109, 2, 21, 3, 81, 37, 50, 13, 10, 0, 4, 111, 110, 105, 101, 1, 21, 3, 81, 40, 50, 6, 37, 0, 111, 110, 105, 101, 1, 21, 2, 115, 21, 21, 0, 4, 108, 97, 2, 103, 114, 97, 110, 116, 3, 81, 55, 2, 35, 0, 108, 97, 2, 109, 105, 0, 108, 97, 109, 98, 111, 2, 106, 97, 110, 116, 3, 81, 55, 2, 35, 63, 69, 2, 40, 0, 108, 111, 2, 114, 101, 3, 81, 55, 2, 40, 0, 108, 101, 98, 2, 111, 116, 111, 109, 105, 101, 3, 81, 55, 2, 106, 69, 0, 108, 111, 114, 105, 2, 115, 115, 17, 65, 3, 81, 55, 2, 115, 34, 13, 0, 108, 117, 2, 119, 101, 3, 81, 55, 2, 116, 0, 108, 105, 107, 116, 8, 2, 101, 114, 17, 65, 3, 81, 55, 13, 49, 47, 0, 101, 115, 115, 111, 114, 3, 81, 106, 87, 13, 34, 0, 111, 107, 8, 2, 111, 3, 81, 108, 49, 10, 0, 117, 110, 103, 117, 115, 3, 81, 109, 66, 79, 109, 87, 10, 0, 101, 98, 114, 117, 97, 114, 105, 101, 3, 81, 114, 69, 34, 116, 4, 113, 34, 37, 0, 111, 2, 116, 111, 103, 114, 97, 3, 81, 115, 0, 111, 116, 111, 3, 81, 115, 47, 40, 0, 111, 108, 105, 111, 3, 81, 115, 55, 37, 10, 40, 0, 101, 105, 116, 101, 3, 81, 121, 47, 13, 0, 121, 110, 103, 101, 2, 17, 67, 3, 81, 121, 50, 134, 13, 0, 7, 6, 103, 0, 2, 103, 3, 0, 4, 104, 116, 3, 21, 0, 110, 1, 21, 2, 32, 0, 110, 111, 110, 1, 21, 2, 32, 3, 21, 102, 114, 0, 104, 2, 32, 3, 49, 0, 104, 8, 3, 79, 0, 104, 105, 2, 116, 97, 3, 79, 2, 37, 0, 117, 105, 108, 108, 111, 116, 105, 110, 101, 3, 79, 2, 37, 55, 2, 40, 47, 37, 50, 0, 111, 2, 114, 105, 108, 108, 97, 3, 79, 2, 40, 0, 117, 101, 114, 114, 105, 108, 108, 97, 3, 79, 13, 34, 6, 107, 55, 35, 0, 97, 114, 97, 103, 101, 3, 79, 13, 34, 6, 113, 73, 0, 108, 105, 115, 101, 2, 114, 105, 101, 110, 3, 79, 55, 13, 87, 13, 0, 97, 108, 97, 2, 32, 3, 79, 113, 55, 2, 35, 0, 111, 117, 114, 109, 101, 116, 3, 79, 115, 34, 63, 121, 12, 0, 3, 134, 0, 4, 97, 2, 108, 17, 65, 17, 67, 3, 134, 2, 35, 0, 97, 2, 114, 105, 101, 112, 0, 97, 114, 2, 110, 3, 134, 2, 35, 34, 0, 97, 114, 121, 101, 1, 17, 67, 21, 3, 134, 2, 35, 34, 6, 121, 13, 0, 97, 114, 110, 105, 2, 115, 111, 101, 110, 3, 134, 2, 35, 34, 50, 2, 37, 0, 97, 108, 2, 106, 111, 101, 110, 3, 134, 2, 35, 55, 0, 97, 108, 97, 2, 115, 105, 3, 134, 2, 35, 55, 113, 0, 111, 101, 100, 2, 103, 117, 110, 115, 116, 3, 134, 2, 40, 47, 0, 111, 101, 100, 101, 114, 2, 116, 105, 101, 3, 134, 2, 40, 70, 13, 34, 0, 111, 101, 119, 101, 114, 8, 3, 134, 2, 40, 82, 13, 34, 0, 111, 114, 2, 100, 121, 110, 3, 134, 2, 108, 34, 0, 4, 111, 100, 2, 115, 97, 108, 105, 103, 3, 134, 2, 108, 47, 0, 111, 100, 2, 118, 114, 0, 4, 111, 100, 115, 2, 100, 105, 101, 110, 115, 116, 105, 103, 3, 134, 2, 108, 47, 87, 0, 111, 100, 115, 2, 108, 97, 115, 116, 101, 114, 0, 111, 100, 100, 101, 2, 108, 111, 3, 134, 2, 108, 70, 13, 0, 117, 116, 116, 117, 2, 114, 97, 3, 134, 2, 109, 47, 2, 109, 0, 111, 2, 100, 105, 110, 3, 134, 2, 115, 0, 97, 117, 116, 101, 110, 103, 3, 134, 2, 127, 47, 106, 66, 0, 111, 195, 171, 1, 17, 65, 3, 134, 6, 40, 13, 0, 97, 109, 105, 101, 115, 3, 134, 6, 113, 63, 37, 87, 0, 111, 111, 103, 1, 17, 65, 2, 32, 3, 134, 6, 115, 134, 0, 111, 103, 105, 101, 115, 1, 17, 65, 3, 134, 6, 115, 134, 37, 87, 0, 97, 115, 8, 2, 17, 65, 3, 134, 7, 35, 87, 10, 0, 103, 101, 1, 21, 2, 32, 3, 134, 13, 0, 105, 109, 2, 110, 97, 25, 3, 134, 13, 63, 0, 105, 109, 110, 97, 2, 115, 105, 17, 65, 3, 134, 13, 63, 50, 113, 0, 4, 114, 97, 2, 102, 105, 101, 107, 3, 134, 34, 2, 35, 0, 114, 97, 2, 102, 105, 101, 116, 0, 114, 97, 2, 110, 105, 101, 116, 0, 114, 97, 2, 115, 105, 101, 117, 0, 114, 97, 8, 2, 118, 17, 65, 0, 114, 97, 110, 100, 105, 2, 111, 3, 134, 34, 2, 35, 50, 70, 2, 37, 0, 114, 97, 109, 97, 2, 100, 111, 101, 3, 134, 34, 2, 35, 63, 2, 35, 0, 114, 97, 109, 109, 97, 2, 116, 105, 107, 3, 134, 34, 2, 35, 63, 35, 0, 114, 97, 100, 101, 2, 114, 105, 110, 103, 3, 134, 34, 2, 35, 70, 114, 0, 114, 111, 110, 100, 119, 101, 116, 108, 105, 107, 3, 134, 34, 2, 108, 50, 47, 82, 106, 47, 55, 13, 49, 0, 114, 97, 97, 100, 8, 2, 116, 3, 134, 34, 2, 113, 0, 4, 114, 97, 97, 100, 8, 2, 110, 101, 103, 101, 3, 134, 34, 2, 113, 47, 0, 114, 97, 97, 100, 8, 2, 118, 121, 102, 0, 114, 97, 97, 100, 8, 2, 101, 3, 134, 34, 2, 113, 47, 10, 0, 114, 97, 97, 100, 115, 101, 8, 2, 115, 3, 134, 34, 2, 113, 47, 87, 106, 0, 114, 1, 97, 17, 67, 117, 111, 2, 111, 111, 116, 106, 105, 101, 3, 134, 34, 6, 0, 4, 114, 97, 8, 2, 110, 97, 3, 134, 34, 13, 0, 114, 105, 2, 102, 102, 105, 101, 114, 0, 114, 105, 8, 2, 109, 17, 65, 0, 114, 97, 115, 8, 2, 17, 65, 3, 134, 34, 35, 87, 10, 0, 114, 105, 101, 107, 119, 97, 3, 134, 34, 37, 49, 58, 35, 0, 114, 111, 110, 100, 119, 101, 2, 116, 25, 3, 134, 34, 108, 50, 47, 82, 106, 0, 114, 111, 110, 100, 119, 101, 116, 2, 97, 3, 134, 34, 108, 50, 47, 82, 106, 47, 10, 0, 114, 97, 8, 2, 115, 105, 101, 3, 134, 34, 113, 0, 114, 97, 100, 101, 2, 17, 67, 3, 134, 34, 113, 70, 13, 0, 114, 111, 116, 101, 114, 101, 3, 134, 34, 115, 47, 13, 34, 13, 0, 4, 114, 111, 110, 100, 1, 114, 101, 116, 103, 97, 2, 105, 3, 134, 34, 129, 50, 47, 10, 0, 114, 111, 110, 100, 2, 111, 0, 97, 116, 8, 2, 111, 3, 134, 35, 47, 10, 0, 97, 109, 105, 101, 2, 32, 3, 134, 35, 63, 6, 37, 0, 111, 103, 105, 101, 1, 17, 65, 2, 32, 3, 134, 40, 134, 6, 37, 0, 108, 101, 116, 115, 101, 114, 3, 134, 55, 7, 106, 47, 87, 13, 34, 0, 108, 97, 110, 115, 3, 134, 55, 35, 50, 87, 0, 4, 108, 97, 115, 2, 97, 3, 134, 55, 35, 87, 10, 0, 108, 97, 115, 2, 111, 0, 105, 102, 8, 2, 17, 65, 3, 134, 107, 81, 10, 0, 111, 109, 97, 103, 2, 116, 105, 103, 3, 134, 108, 63, 10, 2, 35, 134, 0, 117, 115, 2, 111, 111, 105, 3, 134, 109, 87, 10, 0, 97, 100, 101, 8, 3, 134, 113, 70, 13, 0, 4, 97, 115, 2, 101, 114, 105, 103, 3, 134, 113, 87, 0, 97, 115, 2, 105, 101, 0, 97, 115, 2, 105, 103, 0, 195, 169, 115, 101, 108, 3, 134, 114, 87, 13, 55, 0, 4, 111, 117, 100, 2, 97, 21, 3, 134, 118, 47, 10, 0, 111, 117, 100, 2, 111, 0, 104, 101, 105, 100, 1, 21, 3, 134, 121, 47, 0, 4, 97, 110, 115, 1, 21, 3, 134, 131, 50, 87, 0, 97, 110, 115, 2, 17, 67, 0, 7, 6, 104, 0, 4, 1, 17, 65, 21, 2, 32, 3, 0, 2, 104, 3, 0, 108, 101, 1, 17, 65, 2, 32, 3, 8, 103, 106, 0, 3, 105, 0, 97, 114, 2, 112, 111, 101, 110, 3, 105, 2, 35, 34, 0, 4, 97, 114, 100, 2, 17, 67, 21, 3, 105, 2, 35, 34, 47, 0, 97, 114, 116, 2, 114, 111, 101, 114, 0, 97, 114, 116, 2, 115, 116, 111, 103, 116, 101, 32, 0, 97, 114, 108, 101, 2, 107, 121, 110, 3, 105, 2, 35, 34, 55, 13, 0, 97, 114, 109, 111, 2, 110, 105, 101, 3, 105, 2, 35, 34, 63, 2, 40, 0, 4, 97, 108, 2, 115, 115, 116, 97, 114, 3, 105, 2, 35, 55, 0, 97, 108, 2, 118, 101, 21, 0, 97, 108, 102, 2, 118, 105, 101, 114, 0, 97, 108, 102, 2, 118, 121, 102, 0, 97, 108, 111, 2, 103, 101, 3, 105, 2, 35, 55, 2, 40, 0, 97, 108, 108, 101, 108, 117, 106, 97, 3, 105, 2, 35, 55, 13, 55, 116, 57, 2, 35, 0, 4, 97, 108, 102, 2, 100, 114, 105, 101, 3, 105, 2, 35, 55, 81, 0, 97, 108, 102, 2, 107, 114, 111, 21, 0, 97, 108, 102, 2, 110, 101, 103, 101, 0, 97, 108, 102, 2, 115, 101, 119, 101, 0, 97, 108, 102, 2, 116, 105, 101, 110, 0, 97, 108, 102, 2, 116, 119, 97, 97, 108, 102, 0, 97, 108, 102, 2, 116, 119, 101, 101, 0, 4, 97, 108, 102, 2, 101, 101, 110, 3, 105, 2, 35, 55, 81, 10, 0, 97, 108, 102, 2, 101, 108, 102, 0, 97, 108, 102, 8, 2, 97, 103, 25, 0, 97, 108, 102, 115, 101, 2, 115, 3, 105, 2, 35, 55, 81, 87, 106, 0, 4, 105, 2, 115, 116, 111, 3, 105, 2, 37, 0, 105, 8, 2, 98, 105, 115, 0, 105, 101, 114, 110, 97, 2, 109, 97, 97, 108, 3, 105, 2, 37, 12, 34, 50, 113, 0, 105, 195, 171, 114, 2, 97, 114, 103, 105, 101, 3, 105, 2, 37, 13, 34, 0, 105, 195, 171, 114, 97, 114, 2, 103, 105, 101, 32, 24, 3, 105, 2, 37, 13, 34, 2, 35, 34, 0, 105, 195, 171, 114, 111, 2, 103, 108, 105, 101, 3, 105, 2, 37, 13, 34, 2, 40, 0, 105, 112, 2, 110, 111, 17, 67, 17, 65, 3, 105, 2, 37, 48, 0, 105, 112, 101, 114, 2, 98, 111, 3, 105, 2, 37, 48, 13, 34, 0, 105, 97, 2, 115, 105, 110, 116, 3, 105, 2, 37, 57, 2, 35, 0, 105, 115, 116, 114, 105, 2, 111, 110, 3, 105, 2, 37, 87, 47, 34, 2, 37, 0, 105, 195, 171, 110, 97, 3, 105, 2, 37, 114, 12, 50, 35, 0, 105, 103, 105, 195, 171, 2, 110, 17, 65, 3, 105, 2, 37, 134, 2, 37, 114, 0, 111, 116, 101, 2, 108, 3, 105, 2, 40, 47, 110, 0, 111, 101, 118, 101, 2, 114, 3, 105, 2, 40, 81, 110, 0, 111, 101, 118, 101, 101, 108, 104, 2, 101, 3, 105, 2, 40, 81, 114, 55, 105, 0, 111, 2, 110, 110, 101, 117, 114, 3, 105, 2, 108, 0, 4, 111, 114, 2, 108, 111, 115, 3, 105, 2, 108, 34, 0, 111, 114, 2, 109, 111, 0, 111, 114, 114, 105, 2, 98, 17, 65, 3, 105, 2, 108, 34, 2, 37, 0, 111, 110, 103, 2, 97, 3, 105, 2, 108, 66, 134, 0, 111, 114, 105, 115, 111, 110, 2, 116, 97, 3, 105, 2, 115, 34, 2, 37, 87, 2, 108, 50, 0, 4, 111, 111, 103, 2, 100, 114, 97, 3, 105, 2, 115, 134, 0, 111, 111, 103, 2, 109, 111, 101, 100, 105, 103, 0, 117, 2, 109, 101, 117, 114, 3, 105, 2, 116, 0, 117, 105, 115, 2, 104, 111, 117, 100, 32, 3, 105, 2, 125, 87, 0, 97, 114, 116, 105, 103, 1, 21, 3, 105, 6, 35, 34, 47, 13, 134, 0, 97, 108, 1, 17, 67, 21, 2, 115, 17, 65, 3, 105, 6, 35, 55, 0, 97, 108, 102, 8, 2, 103, 101, 14, 128, 132, 132, 3, 105, 6, 35, 55, 81, 0, 105, 110, 107, 101, 2, 112, 105, 110, 107, 3, 105, 13, 66, 49, 13, 0, 4, 97, 114, 100, 2, 104, 101, 105, 100, 3, 105, 35, 34, 47, 0, 97, 114, 100, 2, 108, 111, 0, 97, 114, 100, 2, 115, 116, 101, 0, 97, 114, 116, 2, 115, 116, 111, 103, 116, 101, 32, 24, 0, 97, 114, 100, 103, 101, 2, 17, 67, 3, 105, 35, 34, 47, 134, 13, 0, 97, 114, 109, 111, 110, 105, 101, 115, 3, 105, 35, 34, 63, 6, 115, 50, 37, 87, 0, 97, 114, 100, 101, 3, 105, 35, 34, 70, 13, 0, 97, 110, 100, 2, 111, 3, 105, 35, 50, 47, 19, 0, 105, 116, 108, 101, 114, 3, 105, 37, 47, 55, 13, 34, 0, 105, 112, 111, 8, 2, 21, 14, 128, 132, 132, 3, 105, 37, 48, 40, 0, 105, 110, 2, 100, 111, 101, 3, 105, 37, 50, 0, 105, 109, 110, 101, 3, 105, 37, 63, 50, 13, 0, 105, 115, 116, 101, 114, 2, 105, 3, 105, 37, 87, 47, 6, 114, 34, 0, 105, 115, 116, 101, 114, 2, 101, 3, 105, 37, 87, 47, 13, 34, 0, 111, 101, 110, 100, 101, 114, 3, 105, 40, 50, 13, 34, 0, 111, 102, 2, 17, 65, 3, 105, 108, 81, 10, 0, 97, 2, 119, 101, 3, 105, 113, 0, 97, 112, 101, 114, 3, 105, 113, 48, 13, 34, 0, 97, 110, 101, 8, 2, 17, 67, 3, 105, 113, 50, 13, 0, 97, 109, 101, 114, 3, 105, 113, 63, 13, 34, 0, 111, 98, 111, 8, 3, 105, 115, 69, 40, 0, 111, 102, 2, 105, 101, 3, 105, 115, 81, 0, 7, 6, 105, 0, 4, 1, 17, 67, 2, 195, 171, 115, 116, 97, 3, 2, 37, 0, 1, 104, 2, 100, 114, 17, 65, 0, 1, 112, 115, 2, 111, 101, 110, 0, 1, 120, 97, 116, 2, 21, 0, 1, 180, 195, 2, 25, 0, 2, 114, 111, 110, 105, 101, 0, 2, 118, 111, 111, 114, 0, 8, 2, 107, 111, 0, 8, 2, 109, 109, 117, 0, 8, 2, 114, 114, 0, 195, 171, 116, 101, 105, 116, 3, 2, 37, 13, 47, 6, 121, 47, 0, 114, 97, 8, 2, 17, 67, 3, 2, 37, 34, 35, 0, 116, 97, 108, 105, 2, 97, 3, 2, 37, 47, 2, 35, 55, 2, 37, 0, 101, 116, 101, 114, 109, 97, 2, 103, 3, 2, 37, 47, 13, 34, 63, 2, 35, 0, 112, 101, 2, 107, 111, 110, 3, 2, 37, 48, 13, 0, 108, 108, 117, 109, 105, 2, 110, 17, 65, 3, 2, 37, 55, 2, 40, 63, 2, 37, 0, 108, 108, 117, 2, 115, 116, 114, 17, 65, 3, 2, 37, 55, 2, 109, 0, 108, 108, 117, 2, 115, 105, 3, 2, 37, 55, 116, 0, 109, 112, 97, 108, 97, 3, 2, 37, 63, 48, 113, 55, 35, 0, 98, 101, 114, 2, 105, 21, 3, 2, 37, 69, 114, 34, 0, 100, 8, 2, 17, 65, 3, 2, 37, 70, 0, 4, 100, 101, 2, 97, 3, 2, 37, 70, 2, 37, 0, 100, 101, 2, 195, 171, 0, 100, 105, 8, 2, 111, 0, 115, 108, 97, 109, 8, 2, 105, 3, 2, 37, 87, 55, 2, 35, 63, 0, 101, 115, 101, 8, 2, 17, 67, 3, 4, 37, 87, 13, 0, 101, 1, 114, 116, 2, 32, 24, 3, 6, 37, 0, 116, 105, 115, 1, 17, 67, 21, 2, 32, 3, 6, 37, 47, 13, 87, 0, 4, 101, 107, 1, 110, 21, 2, 32, 3, 6, 37, 49, 0, 101, 107, 1, 110, 21, 2, 101, 32, 0, 101, 107, 1, 114, 116, 21, 2, 32, 0, 101, 107, 1, 114, 116, 21, 2, 101, 25, 0, 101, 107, 1, 116, 21, 2, 32, 0, 101, 107, 1, 116, 21, 2, 101, 32, 0, 101, 102, 1, 115, 115, 2, 32, 3, 6, 37, 81, 0, 4, 101, 119, 101, 1, 115, 110, 2, 25, 3, 6, 37, 82, 13, 0, 101, 119, 101, 1, 115, 115, 2, 32, 0, 115, 105, 101, 1, 17, 67, 3, 6, 37, 87, 37, 0, 1, 17, 67, 114, 97, 110, 2, 115, 115, 117, 115, 3, 6, 107, 0, 109, 109, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 6, 107, 63, 13, 34, 10, 0, 4, 115, 1, 17, 67, 17, 65, 2, 32, 3, 6, 107, 87, 0, 115, 1, 109, 101, 111, 108, 98, 0, 115, 1, 114, 97, 116, 105, 108, 2, 12, 0, 115, 116, 101, 1, 17, 67, 17, 65, 2, 32, 3, 6, 107, 87, 47, 13, 0, 115, 116, 105, 101, 115, 1, 17, 67, 21, 3, 6, 107, 87, 47, 37, 87, 0, 4, 115, 107, 1, 17, 67, 2, 32, 3, 6, 107, 87, 49, 0, 115, 107, 1, 17, 67, 2, 101, 32, 0, 115, 109, 101, 1, 21, 2, 25, 3, 6, 107, 87, 63, 13, 0, 107, 97, 1, 21, 2, 32, 3, 8, 2, 37, 49, 2, 35, 0, 115, 1, 114, 97, 21, 2, 25, 3, 8, 13, 87, 0, 4, 1, 17, 67, 2, 103, 3, 13, 0, 1, 102, 101, 100, 2, 110, 0, 1, 109, 2, 110, 105, 115, 116, 101, 114, 0, 1, 115, 105, 114, 107, 2, 25, 0, 2, 110, 110, 101, 101, 109, 98, 97, 0, 2, 116, 105, 101, 102, 0, 2, 116, 105, 101, 119, 0, 8, 109, 101, 2, 114, 0, 103, 101, 114, 1, 10, 2, 32, 14, 128, 128, 130, 3, 13, 34, 0, 103, 101, 114, 115, 1, 10, 2, 32, 14, 128, 128, 131, 3, 13, 34, 87, 0, 107, 101, 1, 10, 2, 32, 14, 128, 128, 131, 3, 13, 49, 13, 0, 107, 101, 114, 1, 108, 10, 2, 17, 67, 3, 13, 49, 13, 34, 0, 107, 101, 110, 100, 1, 17, 67, 10, 3, 13, 49, 13, 50, 47, 0, 107, 101, 110, 100, 101, 1, 17, 67, 10, 3, 13, 49, 13, 50, 70, 13, 0, 107, 105, 110, 103, 1, 17, 67, 3, 13, 49, 13, 66, 0, 110, 2, 116, 117, 115, 115, 101, 110, 3, 13, 50, 0, 110, 116, 101, 110, 2, 115, 3, 13, 50, 47, 106, 50, 0, 110, 115, 117, 114, 103, 101, 110, 2, 17, 67, 3, 13, 50, 87, 2, 109, 34, 134, 106, 50, 0, 110, 103, 101, 110, 105, 101, 117, 114, 3, 13, 50, 134, 13, 50, 6, 116, 13, 34, 0, 109, 109, 105, 8, 2, 103, 114, 17, 65, 3, 13, 63, 13, 0, 4, 109, 112, 111, 2, 115, 97, 110, 116, 3, 13, 63, 48, 2, 40, 0, 109, 112, 111, 2, 116, 101, 0, 109, 112, 101, 114, 97, 2, 116, 17, 65, 21, 3, 13, 63, 48, 2, 106, 34, 2, 35, 0, 109, 98, 101, 2, 115, 3, 13, 63, 69, 13, 0, 4, 115, 1, 98, 117, 112, 2, 32, 3, 13, 87, 0, 115, 1, 108, 105, 117, 118, 0, 115, 1, 108, 111, 112, 2, 32, 0, 115, 1, 109, 17, 65, 17, 65, 2, 32, 0, 115, 1, 110, 101, 2, 25, 0, 4, 115, 1, 110, 102, 2, 17, 65, 3, 13, 87, 10, 0, 115, 1, 110, 110, 2, 17, 65, 0, 115, 114, 97, 101, 2, 108, 105, 21, 3, 13, 87, 34, 2, 119, 0, 115, 114, 97, 101, 2, 108, 105, 3, 13, 87, 34, 120, 0, 103, 101, 114, 1, 17, 67, 21, 2, 17, 67, 17, 65, 3, 13, 134, 13, 34, 0, 103, 101, 110, 100, 1, 17, 67, 21, 2, 32, 3, 13, 134, 13, 50, 47, 0, 103, 101, 110, 100, 101, 1, 17, 67, 21, 3, 13, 134, 13, 50, 70, 13, 0, 103, 105, 110, 103, 1, 17, 67, 3, 13, 134, 13, 66, 0, 103, 104, 101, 105, 2, 100, 3, 13, 134, 121, 0, 4, 99, 1, 21, 2, 32, 3, 21, 0, 108, 101, 115, 2, 32, 0, 116, 121, 2, 32, 24, 0, 195, 169, 3, 26, 37, 0, 4, 3, 37, 0, 1, 21, 2, 115, 101, 114, 105, 110, 103, 0, 1, 104, 2, 100, 114, 111, 0, 1, 115, 112, 2, 103, 17, 65, 0, 2, 17, 67, 17, 65, 0, 8, 116, 110, 97, 2, 17, 67, 0, 101, 0, 101, 1, 103, 2, 114, 105, 103, 0, 101, 1, 104, 2, 114, 100, 105, 101, 0, 101, 1, 107, 2, 114, 97, 110, 17, 67, 0, 101, 1, 107, 2, 114, 105, 101, 0, 101, 1, 107, 2, 114, 116, 115, 0, 101, 1, 107, 115, 2, 114, 105, 103, 0, 101, 1, 112, 2, 114, 101, 119, 0, 101, 1, 112, 2, 114, 105, 110, 103, 0, 101, 1, 119, 2, 114, 111, 111, 107, 0, 101, 2, 117, 117, 0, 195, 171, 110, 3, 37, 6, 106, 50, 0, 97, 116, 101, 114, 1, 17, 67, 3, 37, 6, 113, 47, 13, 34, 0, 97, 116, 114, 105, 101, 115, 1, 17, 67, 3, 37, 6, 113, 47, 34, 37, 87, 0, 97, 110, 97, 3, 37, 6, 113, 50, 35, 0, 97, 97, 108, 2, 32, 25, 3, 37, 6, 113, 55, 0, 97, 108, 101, 2, 32, 3, 37, 6, 113, 55, 13, 0, 101, 101, 2, 17, 67, 3, 37, 6, 114, 0, 195, 171, 114, 2, 17, 65, 3, 37, 6, 114, 34, 0, 195, 171, 108, 101, 3, 37, 6, 114, 55, 13, 0, 101, 117, 115, 3, 37, 6, 126, 87, 0, 101, 1, 17, 67, 2, 114, 3, 37, 12, 0, 101, 195, 171, 2, 25, 3, 37, 12, 13, 0, 114, 105, 8, 2, 115, 3, 37, 34, 13, 0, 114, 114, 105, 116, 101, 114, 2, 21, 3, 37, 34, 13, 47, 6, 114, 34, 0, 114, 111, 110, 105, 101, 2, 32, 24, 3, 37, 34, 40, 50, 6, 37, 0, 97, 116, 114, 105, 101, 1, 17, 67, 3, 37, 35, 47, 34, 6, 37, 0, 116, 101, 105, 116, 1, 21, 3, 37, 47, 6, 121, 47, 0, 116, 101, 109, 3, 37, 47, 106, 63, 0, 4, 101, 107, 1, 110, 107, 21, 2, 32, 3, 37, 49, 0, 101, 107, 1, 116, 105, 114, 107, 0, 109, 112, 105, 8, 2, 16, 3, 37, 63, 48, 37, 0, 103, 8, 2, 108, 111, 3, 37, 79, 0, 4, 118, 101, 101, 114, 1, 17, 67, 3, 37, 81, 6, 114, 34, 0, 118, 101, 114, 1, 17, 67, 2, 17, 65, 0, 115, 101, 101, 114, 1, 21, 3, 37, 87, 6, 114, 34, 0, 115, 101, 114, 101, 110, 1, 21, 2, 100, 3, 37, 87, 6, 114, 34, 13, 50, 0, 115, 101, 117, 114, 1, 21, 3, 37, 87, 6, 126, 34, 0, 115, 105, 101, 1, 17, 67, 21, 21, 21, 3, 37, 87, 37, 0, 115, 105, 101, 117, 115, 1, 17, 67, 3, 37, 87, 37, 6, 126, 87, 0, 115, 108, 97, 109, 8, 3, 37, 87, 55, 35, 63, 0, 103, 101, 114, 105, 110, 103, 1, 21, 3, 37, 134, 6, 114, 34, 13, 66, 0, 4, 1, 29, 2, 103, 25, 12, 3, 107, 0, 1, 115, 2, 103, 17, 67, 0, 1, 119, 115, 2, 103, 0, 2, 17, 67, 0, 4, 100, 106, 105, 101, 3, 107, 37, 78, 37, 0, 116, 106, 105, 101, 0, 116, 1, 119, 2, 17, 65, 3, 107, 47, 0, 115, 1, 109, 101, 17, 67, 21, 2, 32, 3, 107, 87, 0, 115, 112, 101, 108, 1, 17, 67, 3, 107, 87, 48, 13, 55, 0, 103, 101, 1, 10, 2, 32, 3, 107, 134, 13, 0, 103, 101, 115, 1, 10, 2, 32, 3, 107, 134, 13, 87, 0, 195, 171, 3, 114, 12, 14, 0, 101, 117, 3, 117, 0, 106, 2, 17, 67, 3, 121, 0, 7, 6, 106, 0, 2, 106, 3, 0, 4, 97, 99, 107, 8, 3, 21, 0, 101, 97, 110, 0, 101, 101, 112, 0, 111, 104, 110, 0, 4, 3, 57, 0, 8, 2, 97, 110, 116, 106, 105, 101, 25, 12, 12, 0, 97, 8, 2, 17, 67, 111, 98, 17, 65, 3, 57, 2, 35, 0, 97, 112, 111, 2, 110, 3, 57, 2, 35, 48, 108, 0, 4, 97, 99, 97, 114, 97, 110, 100, 97, 3, 57, 2, 35, 49, 2, 35, 34, 6, 35, 50, 70, 35, 0, 97, 107, 97, 114, 97, 110, 100, 97, 0, 97, 107, 111, 112, 101, 119, 101, 114, 3, 57, 2, 35, 49, 2, 108, 48, 114, 82, 13, 34, 10, 0, 97, 110, 8, 2, 17, 67, 21, 3, 57, 2, 35, 50, 0, 97, 108, 111, 101, 2, 115, 105, 101, 3, 57, 2, 35, 55, 2, 40, 0, 97, 115, 2, 109, 121, 110, 3, 57, 2, 35, 87, 0, 117, 2, 114, 105, 100, 3, 57, 2, 40, 0, 111, 101, 114, 2, 110, 97, 3, 57, 2, 40, 34, 0, 117, 114, 105, 115, 2, 100, 105, 107, 3, 57, 2, 40, 34, 13, 87, 0, 111, 104, 97, 2, 110, 3, 57, 2, 40, 105, 35, 0, 111, 114, 100, 97, 8, 2, 110, 105, 17, 65, 3, 57, 2, 108, 34, 70, 113, 0, 97, 107, 111, 98, 2, 114, 101, 103, 111, 112, 3, 57, 2, 113, 49, 2, 108, 48, 0, 117, 2, 119, 101, 3, 57, 2, 116, 0, 117, 119, 101, 2, 108, 105, 101, 114, 3, 57, 2, 116, 82, 13, 0, 117, 119, 101, 108, 101, 3, 57, 2, 116, 82, 114, 55, 13, 0, 117, 110, 103, 105, 8, 2, 97, 3, 57, 4, 40, 66, 2, 37, 0, 97, 103, 8, 2, 17, 65, 3, 57, 7, 35, 134, 10, 0, 101, 114, 117, 115, 97, 108, 101, 109, 3, 57, 13, 34, 116, 87, 2, 35, 55, 2, 106, 63, 0, 101, 110, 101, 119, 101, 114, 3, 57, 13, 50, 114, 82, 13, 34, 0, 97, 8, 2, 110, 110, 17, 65, 12, 3, 57, 35, 0, 97, 110, 8, 2, 115, 17, 65, 110, 25, 3, 57, 35, 50, 0, 97, 110, 117, 97, 114, 105, 101, 3, 57, 35, 50, 116, 4, 113, 34, 37, 0, 97, 103, 117, 97, 114, 3, 57, 35, 79, 58, 35, 34, 0, 101, 115, 117, 115, 3, 57, 37, 12, 87, 109, 87, 0, 117, 110, 105, 101, 3, 57, 40, 50, 37, 0, 117, 108, 105, 101, 3, 57, 40, 55, 37, 0, 111, 110, 103, 2, 101, 116, 106, 105, 101, 3, 57, 108, 66, 0, 111, 110, 103, 101, 3, 57, 108, 66, 13, 0, 97, 2, 98, 114, 111, 101, 114, 3, 57, 113, 0, 4, 97, 103, 2, 101, 110, 100, 3, 57, 113, 134, 0, 97, 103, 2, 101, 114, 0, 97, 103, 2, 105, 110, 103, 0, 101, 108, 108, 105, 101, 3, 73, 6, 106, 55, 37, 0, 111, 117, 108, 101, 3, 73, 40, 12, 55, 0, 97, 122, 122, 3, 73, 111, 86, 0, 7, 6, 107, 0, 2, 107, 3, 0, 107, 108, 101, 114, 101, 3, 8, 49, 55, 6, 114, 34, 13, 0, 3, 49, 0, 97, 114, 97, 107, 116, 101, 114, 3, 49, 2, 35, 34, 35, 49, 47, 13, 34, 0, 4, 105, 2, 110, 101, 116, 105, 101, 3, 49, 2, 37, 0, 105, 8, 2, 116, 97, 0, 105, 97, 97, 116, 3, 49, 2, 37, 38, 113, 47, 0, 105, 107, 111, 101, 2, 106, 111, 101, 3, 49, 2, 37, 49, 40, 12, 0, 105, 108, 105, 109, 97, 110, 100, 106, 97, 114, 111, 3, 49, 2, 37, 55, 13, 63, 2, 35, 50, 73, 113, 34, 40, 0, 101, 110, 2, 109, 101, 114, 107, 101, 110, 3, 49, 2, 106, 50, 0, 117, 108, 105, 110, 3, 49, 2, 109, 55, 2, 37, 50, 0, 101, 114, 97, 2, 109, 105, 101, 107, 3, 49, 2, 110, 34, 2, 35, 0, 101, 108, 107, 105, 101, 2, 119, 121, 110, 3, 49, 2, 110, 55, 49, 2, 37, 0, 101, 108, 110, 101, 114, 2, 105, 110, 3, 49, 2, 110, 55, 50, 13, 34, 0, 4, 117, 2, 98, 97, 21, 3, 49, 2, 116, 0, 117, 2, 98, 105, 101, 107, 0, 101, 105, 115, 101, 114, 2, 105, 110, 3, 49, 2, 121, 86, 13, 34, 0, 117, 110, 100, 105, 1, 21, 2, 103, 3, 49, 6, 109, 50, 70, 13, 0, 117, 115, 1, 105, 3, 49, 6, 109, 87, 0, 101, 114, 1, 114, 101, 100, 101, 119, 2, 17, 65, 3, 49, 6, 114, 34, 0, 101, 117, 114, 105, 103, 1, 21, 3, 49, 6, 126, 34, 13, 134, 0, 101, 117, 115, 101, 8, 3, 49, 7, 126, 87, 13, 0, 4, 101, 114, 1, 21, 2, 116, 106, 105, 101, 3, 49, 13, 34, 0, 107, 101, 114, 2, 17, 65, 0, 101, 114, 101, 110, 100, 1, 110, 2, 32, 3, 49, 13, 34, 13, 50, 47, 0, 101, 114, 101, 110, 100, 101, 1, 110, 2, 32, 3, 49, 13, 34, 13, 50, 70, 13, 0, 101, 114, 107, 101, 114, 115, 1, 107, 105, 108, 102, 3, 49, 13, 34, 49, 111, 34, 87, 0, 4, 101, 108, 101, 110, 100, 2, 32, 3, 49, 13, 55, 13, 50, 47, 0, 107, 101, 108, 101, 110, 100, 2, 32, 0, 4, 101, 108, 101, 110, 100, 101, 2, 32, 3, 49, 13, 55, 13, 50, 70, 13, 0, 107, 101, 108, 101, 110, 100, 101, 2, 32, 0, 4, 101, 108, 105, 110, 103, 3, 49, 13, 55, 13, 66, 0, 107, 101, 108, 105, 110, 103, 0, 114, 97, 2, 119, 97, 116, 3, 49, 34, 2, 35, 0, 4, 114, 101, 8, 2, 111, 3, 49, 34, 2, 37, 0, 114, 105, 2, 111, 101, 108, 0, 114, 101, 2, 100, 105, 116, 3, 49, 34, 2, 106, 0, 114, 111, 107, 111, 100, 105, 2, 108, 3, 49, 34, 2, 108, 49, 13, 70, 107, 0, 114, 117, 103, 101, 114, 3, 49, 34, 6, 126, 13, 34, 0, 114, 97, 103, 8, 2, 17, 65, 3, 49, 34, 7, 35, 134, 10, 0, 4, 114, 101, 2, 100, 105, 101, 116, 3, 49, 34, 13, 0, 114, 101, 8, 2, 112, 101, 21, 0, 114, 105, 2, 115, 97, 110, 116, 0, 114, 105, 116, 2, 17, 65, 3, 49, 34, 13, 47, 0, 114, 101, 109, 101, 2, 116, 97, 114, 116, 3, 49, 34, 13, 63, 13, 0, 114, 105, 109, 105, 2, 110, 17, 65, 3, 49, 34, 13, 63, 13, 6, 0, 114, 105, 115, 116, 97, 2, 108, 3, 49, 34, 13, 87, 47, 35, 0, 114, 105, 116, 105, 101, 115, 3, 49, 34, 37, 47, 37, 87, 0, 114, 105, 101, 107, 101, 116, 3, 49, 34, 37, 49, 13, 47, 0, 114, 105, 101, 107, 101, 116, 119, 3, 49, 34, 37, 49, 13, 47, 82, 0, 114, 105, 101, 119, 101, 2, 108, 3, 49, 34, 37, 82, 13, 0, 114, 97, 2, 103, 105, 101, 3, 49, 34, 113, 0, 97, 109, 101, 108, 101, 8, 3, 49, 35, 63, 6, 114, 55, 13, 0, 105, 108, 111, 8, 3, 49, 37, 55, 2, 40, 0, 105, 101, 115, 101, 114, 2, 21, 3, 49, 37, 87, 13, 34, 0, 110, 105, 112, 2, 17, 65, 3, 49, 50, 107, 48, 19, 0, 110, 101, 114, 115, 2, 32, 3, 49, 50, 110, 34, 87, 0, 4, 108, 97, 2, 115, 115, 105, 101, 107, 3, 49, 55, 2, 35, 0, 108, 97, 2, 118, 105, 101, 114, 0, 108, 97, 114, 105, 110, 101, 2, 116, 3, 49, 55, 2, 35, 34, 2, 37, 50, 106, 0, 108, 97, 110, 100, 101, 2, 115, 116, 105, 3, 49, 55, 2, 35, 50, 70, 13, 0, 4, 108, 97, 119, 101, 114, 2, 98, 111, 101, 114, 3, 49, 55, 2, 113, 82, 13, 34, 0, 108, 97, 119, 101, 114, 2, 100, 114, 0, 108, 97, 119, 101, 114, 2, 104, 101, 101, 114, 0, 108, 97, 119, 101, 114, 2, 106, 97, 115, 0, 108, 97, 119, 101, 114, 2, 110, 101, 103, 101, 0, 108, 97, 119, 101, 114, 2, 115, 101, 119, 0, 108, 97, 119, 101, 114, 2, 116, 0, 108, 97, 119, 101, 114, 2, 118, 0, 108, 97, 119, 101, 114, 2, 97, 3, 49, 55, 2, 113, 82, 13, 34, 10, 0, 108, 97, 119, 101, 114, 115, 101, 115, 3, 49, 55, 2, 113, 82, 13, 34, 87, 106, 87, 0, 108, 111, 117, 2, 115, 117, 108, 101, 3, 49, 55, 2, 118, 0, 108, 101, 105, 110, 2, 115, 105, 101, 108, 105, 3, 49, 55, 2, 121, 50, 0, 108, 101, 105, 110, 115, 101, 2, 114, 105, 103, 3, 49, 55, 2, 121, 50, 87, 114, 0, 4, 108, 105, 2, 109, 97, 97, 116, 3, 49, 55, 13, 0, 108, 105, 2, 110, 105, 101, 107, 0, 108, 97, 8, 2, 115, 17, 65, 21, 21, 3, 49, 55, 35, 0, 108, 105, 2, 109, 111, 112, 3, 49, 55, 107, 0, 108, 105, 112, 2, 17, 65, 3, 49, 55, 107, 48, 10, 0, 108, 105, 109, 1, 103, 114, 101, 98, 2, 17, 65, 3, 49, 55, 107, 63, 10, 0, 108, 97, 2, 107, 111, 117, 115, 3, 49, 55, 113, 0, 108, 97, 97, 114, 98, 108, 121, 107, 108, 105, 107, 3, 49, 55, 113, 34, 69, 55, 6, 121, 49, 55, 13, 49, 0, 4, 108, 97, 119, 101, 114, 3, 49, 55, 113, 82, 13, 34, 0, 108, 97, 119, 101, 114, 2, 118, 101, 108, 100, 0, 108, 97, 118, 101, 115, 105, 109, 98, 101, 108, 3, 49, 55, 113, 82, 13, 87, 13, 63, 69, 13, 55, 0, 108, 101, 114, 101, 3, 49, 55, 114, 34, 13, 0, 108, 101, 117, 114, 2, 101, 102, 102, 101, 107, 3, 49, 55, 126, 34, 0, 108, 101, 117, 114, 101, 3, 49, 55, 126, 34, 13, 0, 119, 8, 3, 49, 58, 0, 4, 119, 97, 2, 100, 114, 97, 3, 49, 58, 2, 35, 0, 119, 97, 2, 116, 114, 121, 110, 0, 119, 97, 114, 8, 2, 116, 17, 65, 3, 49, 58, 2, 35, 34, 0, 119, 97, 114, 97, 110, 2, 116, 3, 49, 58, 2, 35, 34, 13, 50, 0, 119, 97, 114, 116, 101, 2, 116, 3, 49, 58, 2, 35, 34, 47, 106, 0, 119, 97, 108, 105, 2, 17, 67, 21, 3, 49, 58, 2, 35, 55, 2, 37, 0, 119, 97, 97, 100, 2, 97, 97, 114, 100, 105, 3, 49, 58, 2, 113, 47, 10, 0, 119, 105, 2, 116, 97, 110, 115, 3, 49, 58, 13, 0, 119, 105, 110, 116, 101, 2, 116, 3, 49, 58, 13, 50, 47, 106, 0, 119, 97, 114, 116, 2, 101, 101, 117, 3, 49, 58, 35, 34, 47, 10, 0, 119, 97, 114, 116, 101, 105, 110, 100, 8, 3, 49, 58, 35, 34, 47, 10, 121, 50, 47, 0, 119, 97, 114, 116, 101, 108, 3, 49, 58, 35, 34, 47, 13, 55, 10, 0, 119, 101, 108, 97, 3, 49, 58, 106, 12, 55, 35, 0, 119, 105, 107, 8, 2, 17, 65, 3, 49, 58, 107, 49, 10, 0, 101, 2, 110, 110, 17, 65, 25, 3, 49, 106, 0, 117, 114, 119, 101, 3, 49, 109, 34, 82, 13, 0, 101, 114, 1, 21, 2, 115, 105, 101, 32, 3, 49, 110, 34, 0, 101, 114, 107, 2, 32, 3, 49, 110, 34, 49, 0, 101, 114, 107, 101, 2, 32, 3, 49, 110, 34, 49, 13, 0, 101, 114, 107, 101, 114, 3, 49, 110, 34, 49, 13, 34, 0, 101, 114, 107, 105, 101, 2, 25, 3, 49, 110, 34, 49, 37, 0, 101, 108, 110, 101, 114, 3, 49, 110, 55, 50, 13, 34, 0, 4, 101, 114, 115, 1, 108, 101, 116, 116, 111, 98, 3, 49, 111, 34, 87, 0, 101, 114, 115, 1, 115, 101, 101, 102, 0, 101, 116, 101, 2, 108, 3, 49, 114, 47, 13, 0, 101, 105, 115, 101, 114, 3, 49, 121, 86, 13, 34, 0, 7, 6, 108, 0, 2, 108, 3, 0, 111, 107, 111, 109, 111, 3, 4, 55, 40, 49, 40, 63, 40, 6, 0, 4, 97, 110, 100, 8, 2, 32, 114, 111, 118, 101, 114, 3, 21, 0, 101, 1, 17, 67, 2, 32, 0, 101, 115, 115, 1, 21, 2, 32, 0, 108, 1, 21, 2, 32, 24, 0, 3, 55, 0, 4, 97, 2, 116, 101, 110, 116, 3, 55, 2, 35, 0, 97, 8, 2, 107, 111, 110, 0, 97, 116, 114, 105, 110, 101, 3, 55, 2, 35, 47, 34, 37, 50, 13, 0, 97, 112, 97, 114, 2, 111, 116, 111, 109, 105, 3, 55, 2, 35, 48, 2, 35, 34, 0, 97, 112, 101, 108, 2, 32, 3, 55, 2, 35, 48, 6, 110, 55, 0, 97, 112, 101, 2, 108, 25, 3, 55, 2, 35, 48, 110, 0, 97, 110, 8, 2, 115, 17, 65, 3, 55, 2, 35, 50, 0, 97, 110, 111, 2, 108, 105, 101, 110, 3, 55, 2, 35, 50, 2, 40, 0, 97, 110, 100, 101, 2, 114, 121, 3, 55, 2, 35, 50, 70, 13, 0, 97, 109, 2, 108, 101, 110, 3, 55, 2, 35, 63, 0, 97, 109, 112, 101, 2, 116, 3, 55, 2, 35, 63, 48, 106, 0, 4, 97, 110, 103, 2, 119, 101, 114, 112, 3, 55, 2, 35, 66, 0, 97, 110, 103, 8, 2, 100, 21, 21, 0, 97, 110, 107, 2, 109, 111, 101, 3, 55, 2, 35, 66, 49, 0, 97, 98, 105, 2, 114, 105, 110, 116, 3, 55, 2, 35, 69, 13, 0, 97, 98, 111, 114, 97, 116, 111, 114, 3, 55, 2, 35, 69, 14, 34, 2, 35, 47, 6, 115, 34, 0, 97, 118, 101, 110, 116, 101, 108, 3, 55, 2, 35, 81, 106, 50, 47, 13, 55, 0, 97, 103, 117, 110, 101, 3, 55, 2, 35, 134, 116, 50, 13, 0, 105, 2, 107, 119, 105, 100, 3, 55, 2, 37, 0, 4, 105, 116, 2, 111, 116, 111, 109, 105, 101, 3, 55, 2, 37, 47, 0, 105, 116, 8, 2, 111, 103, 114, 97, 102, 0, 105, 116, 111, 8, 2, 17, 67, 3, 55, 2, 37, 47, 2, 40, 0, 105, 110, 103, 117, 2, 105, 3, 55, 2, 37, 66, 79, 58, 0, 105, 101, 102, 2, 116, 97, 108, 108, 3, 55, 2, 37, 81, 0, 4, 111, 2, 106, 97, 3, 55, 2, 40, 0, 111, 2, 107, 97, 108, 17, 65, 0, 117, 112, 105, 110, 101, 3, 55, 2, 40, 48, 37, 50, 13, 0, 111, 98, 111, 116, 111, 2, 109, 105, 101, 3, 55, 2, 40, 69, 2, 108, 47, 2, 40, 0, 111, 115, 105, 101, 115, 8, 3, 55, 2, 40, 87, 6, 37, 87, 0, 117, 115, 101, 114, 110, 3, 55, 2, 40, 87, 111, 34, 13, 50, 0, 101, 103, 105, 2, 111, 101, 110, 3, 55, 2, 106, 134, 2, 37, 0, 111, 109, 2, 98, 97, 114, 100, 17, 65, 3, 55, 2, 108, 63, 0, 111, 98, 111, 108, 97, 3, 55, 2, 108, 69, 129, 55, 35, 0, 111, 115, 98, 97, 110, 100, 105, 2, 103, 3, 55, 2, 108, 87, 69, 35, 50, 70, 13, 0, 117, 2, 109, 105, 101, 114, 3, 55, 2, 109, 0, 117, 107, 115, 97, 2, 108, 105, 103, 3, 55, 2, 109, 49, 87, 6, 113, 0, 101, 100, 101, 2, 107, 97, 110, 116, 3, 55, 2, 114, 70, 13, 0, 101, 118, 105, 2, 97, 116, 97, 110, 3, 55, 2, 114, 82, 2, 37, 0, 111, 117, 2, 114, 105, 101, 114, 3, 55, 2, 118, 0, 4, 121, 107, 2, 109, 111, 101, 100, 3, 55, 2, 121, 49, 0, 121, 107, 2, 110, 97, 109, 0, 117, 105, 116, 101, 2, 110, 97, 110, 116, 3, 55, 2, 125, 47, 13, 0, 117, 105, 100, 2, 114, 117, 103, 116, 3, 55, 2, 125, 70, 0, 111, 115, 103, 101, 8, 2, 21, 14, 128, 132, 133, 3, 55, 6, 108, 87, 134, 13, 0, 117, 115, 116, 105, 1, 21, 2, 103, 3, 55, 6, 109, 87, 47, 13, 0, 101, 101, 114, 1, 105, 17, 67, 3, 55, 6, 114, 34, 0, 101, 114, 105, 110, 103, 2, 32, 3, 55, 6, 114, 34, 13, 66, 0, 117, 103, 8, 2, 17, 67, 3, 55, 7, 109, 134, 0, 4, 101, 1, 108, 2, 32, 3, 55, 13, 0, 101, 1, 108, 21, 2, 115, 17, 67, 21, 0, 105, 2, 107, 101, 117, 114, 0, 105, 2, 114, 105, 101, 107, 0, 105, 2, 116, 117, 114, 103, 105, 101, 0, 105, 8, 2, 109, 105, 0, 105, 116, 101, 114, 2, 17, 65, 3, 55, 13, 47, 13, 34, 0, 105, 116, 101, 114, 97, 2, 116, 3, 55, 13, 47, 13, 34, 2, 35, 0, 105, 107, 1, 10, 2, 32, 14, 128, 128, 131, 3, 55, 13, 49, 0, 4, 105, 107, 101, 1, 10, 2, 17, 67, 21, 3, 55, 13, 49, 13, 0, 105, 107, 101, 1, 10, 2, 32, 14, 128, 128, 132, 0, 105, 107, 107, 101, 2, 119, 97, 0, 105, 107, 101, 114, 1, 10, 2, 32, 14, 128, 128, 133, 3, 55, 13, 49, 13, 34, 0, 105, 107, 101, 115, 1, 10, 2, 32, 14, 128, 128, 133, 3, 55, 13, 49, 13, 87, 0, 105, 107, 115, 116, 101, 1, 10, 2, 32, 14, 128, 128, 134, 3, 55, 13, 49, 87, 47, 13, 0, 105, 110, 105, 2, 97, 97, 108, 3, 55, 13, 50, 2, 37, 0, 105, 110, 111, 2, 108, 101, 117, 109, 3, 55, 13, 50, 115, 0, 105, 109, 111, 117, 115, 105, 110, 101, 3, 55, 13, 63, 2, 40, 86, 37, 12, 50, 0, 105, 98, 101, 2, 114, 17, 65, 3, 55, 13, 69, 13, 0, 105, 98, 101, 8, 2, 114, 105, 21, 3, 55, 13, 69, 114, 0, 101, 118, 8, 2, 105, 3, 55, 13, 81, 0, 101, 119, 101, 114, 107, 1, 17, 65, 3, 55, 13, 82, 110, 34, 49, 0, 105, 115, 101, 110, 115, 105, 2, 101, 101, 114, 3, 55, 13, 87, 2, 106, 50, 87, 2, 37, 0, 105, 115, 101, 110, 115, 105, 101, 3, 55, 13, 87, 106, 12, 50, 87, 2, 37, 0, 105, 103, 2, 104, 111, 111, 102, 100, 3, 55, 13, 134, 0, 105, 103, 101, 110, 3, 55, 13, 134, 6, 106, 50, 0, 101, 103, 101, 110, 2, 100, 97, 3, 55, 13, 134, 13, 50, 0, 101, 103, 101, 110, 100, 101, 3, 55, 13, 134, 106, 50, 70, 13, 0, 105, 103, 103, 97, 97, 109, 108, 105, 107, 3, 55, 13, 134, 113, 63, 55, 13, 49, 0, 109, 1, 10, 2, 25, 3, 55, 14, 63, 0, 97, 110, 103, 101, 8, 2, 17, 67, 17, 65, 3, 55, 35, 66, 13, 0, 97, 102, 2, 97, 97, 114, 3, 55, 35, 81, 0, 4, 105, 2, 103, 97, 32, 3, 55, 37, 0, 105, 8, 2, 103, 97, 17, 67, 0, 105, 101, 102, 100, 101, 115, 3, 55, 37, 81, 70, 13, 87, 0, 101, 110, 100, 101, 8, 3, 55, 106, 50, 70, 13, 0, 4, 101, 115, 1, 17, 67, 21, 2, 25, 3, 55, 106, 87, 0, 101, 115, 1, 101, 105, 2, 32, 0, 101, 115, 115, 101, 1, 17, 67, 21, 2, 32, 3, 55, 106, 87, 13, 0, 105, 8, 2, 103, 3, 55, 107, 0, 105, 110, 107, 101, 114, 3, 55, 107, 66, 49, 13, 34, 0, 117, 115, 2, 111, 3, 55, 109, 87, 10, 0, 117, 103, 2, 17, 65, 3, 55, 109, 134, 19, 0, 101, 2, 107, 107, 101, 114, 3, 55, 110, 0, 97, 112, 97, 8, 2, 25, 3, 55, 113, 48, 35, 0, 101, 112, 101, 2, 108, 108, 3, 55, 114, 48, 13, 0, 101, 110, 105, 110, 103, 3, 55, 114, 50, 13, 66, 0, 101, 108, 105, 2, 107, 3, 55, 114, 55, 13, 0, 4, 101, 100, 101, 1, 10, 2, 32, 14, 128, 128, 132, 3, 55, 114, 70, 13, 0, 101, 100, 101, 1, 114, 101, 118, 2, 25, 0, 101, 100, 101, 2, 17, 67, 0, 101, 100, 105, 110, 103, 2, 32, 3, 55, 114, 70, 13, 66, 0, 101, 119, 101, 2, 25, 3, 55, 114, 82, 13, 0, 101, 119, 101, 2, 116, 106, 105, 101, 3, 55, 114, 82, 37, 0, 111, 114, 101, 8, 2, 17, 67, 21, 3, 55, 115, 34, 13, 0, 117, 2, 107, 119, 97, 114, 116, 3, 55, 116, 0, 117, 116, 104, 101, 114, 3, 55, 116, 47, 13, 34, 0, 101, 117, 101, 110, 2, 116, 106, 105, 101, 3, 55, 126, 37, 66, 0, 4, 97, 109, 102, 101, 114, 3, 55, 131, 63, 81, 13, 34, 0, 97, 110, 102, 101, 114, 0, 7, 6, 109, 0, 2, 109, 3, 0, 110, 1, 21, 2, 32, 3, 21, 0, 3, 63, 0, 117, 115, 105, 101, 107, 3, 63, 2, 109, 87, 37, 49, 0, 117, 115, 107, 97, 100, 101, 108, 3, 63, 2, 109, 87, 49, 2, 35, 70, 110, 55, 0, 117, 115, 107, 101, 2, 116, 105, 101, 114, 3, 63, 2, 109, 87, 49, 13, 0, 117, 115, 107, 101, 108, 2, 106, 97, 97, 116, 3, 63, 2, 109, 87, 49, 13, 55, 0, 117, 115, 101, 117, 109, 3, 63, 2, 116, 87, 126, 63, 0, 109, 101, 1, 17, 65, 17, 67, 2, 17, 67, 3, 63, 13, 0, 109, 101, 1, 17, 65, 17, 67, 2, 116, 106, 105, 101, 3, 63, 37, 0, 112, 101, 108, 1, 21, 2, 17, 65, 3, 63, 48, 13, 55, 0, 117, 114, 109, 101, 108, 3, 63, 109, 34, 63, 13, 55, 0, 117, 115, 105, 2, 17, 67, 3, 63, 116, 87, 37, 6, 0, 121, 109, 101, 114, 3, 63, 121, 63, 13, 34, 0, 195, 180, 114, 101, 2, 21, 3, 63, 129, 34, 13, 0, 7, 6, 110, 0, 4, 2, 32, 110, 3, 0, 2, 110, 3, 0, 97, 2, 116, 97, 108, 3, 4, 50, 35, 6, 0, 4, 3, 50, 0, 1, 10, 2, 103, 97, 116, 0, 1, 97, 97, 2, 103, 97, 115, 0, 1, 101, 2, 103, 111, 101, 17, 67, 0, 1, 101, 101, 2, 103, 0, 1, 101, 111, 2, 103, 0, 1, 101, 119, 2, 103, 21, 12, 12, 0, 1, 105, 101, 2, 103, 0, 1, 105, 112, 115, 2, 103, 101, 0, 1, 105, 117, 17, 67, 2, 103, 0, 1, 111, 111, 2, 103, 0, 1, 117, 101, 2, 103, 0, 1, 121, 2, 103, 0, 1, 171, 195, 2, 103, 0, 2, 32, 110, 32, 0, 8, 2, 17, 65, 17, 65, 0, 4, 97, 1, 21, 2, 108, 105, 115, 3, 50, 2, 35, 0, 97, 2, 116, 117, 117, 114, 0, 97, 2, 118, 114, 97, 110, 116, 0, 97, 8, 2, 114, 107, 0, 97, 2, 195, 175, 3, 50, 2, 35, 10, 0, 97, 2, 195, 175, 3, 50, 2, 35, 19, 0, 97, 114, 101, 115, 2, 32, 3, 50, 2, 35, 34, 6, 106, 87, 0, 97, 116, 117, 114, 101, 2, 108, 25, 3, 50, 2, 35, 47, 2, 116, 34, 110, 0, 97, 112, 111, 108, 101, 2, 111, 110, 116, 3, 50, 2, 35, 48, 2, 115, 55, 2, 37, 0, 97, 112, 111, 2, 108, 101, 111, 110, 3, 50, 2, 35, 48, 115, 0, 97, 109, 97, 107, 119, 97, 3, 50, 2, 35, 63, 35, 49, 58, 2, 35, 0, 97, 109, 105, 2, 98, 105, 3, 50, 2, 35, 63, 107, 0, 97, 118, 105, 103, 3, 50, 2, 35, 82, 2, 37, 134, 0, 97, 115, 105, 111, 2, 110, 97, 3, 50, 2, 35, 89, 2, 37, 2, 40, 0, 101, 2, 97, 110, 100, 101, 114, 17, 67, 97, 3, 50, 2, 37, 0, 101, 111, 2, 108, 105, 3, 50, 2, 37, 2, 40, 0, 4, 105, 107, 111, 2, 116, 105, 3, 50, 2, 37, 49, 2, 40, 0, 105, 107, 111, 2, 116, 105, 101, 110, 0, 111, 116, 2, 101, 114, 105, 110, 103, 3, 50, 2, 40, 47, 0, 111, 116, 117, 108, 101, 2, 25, 3, 50, 2, 40, 47, 116, 55, 13, 0, 111, 118, 101, 108, 108, 101, 3, 50, 2, 40, 81, 110, 55, 13, 0, 101, 107, 116, 97, 2, 114, 105, 101, 110, 3, 50, 2, 106, 49, 47, 2, 35, 0, 111, 2, 115, 116, 97, 108, 103, 105, 101, 3, 50, 2, 108, 0, 111, 114, 2, 109, 97, 21, 3, 50, 2, 108, 34, 0, 111, 107, 116, 117, 114, 110, 101, 3, 50, 2, 108, 49, 47, 109, 34, 50, 13, 0, 111, 110, 99, 104, 97, 2, 108, 97, 3, 50, 2, 108, 50, 89, 2, 35, 0, 111, 109, 105, 2, 110, 17, 65, 3, 50, 2, 108, 63, 2, 37, 0, 111, 109, 109, 101, 114, 2, 101, 101, 110, 3, 50, 2, 108, 63, 13, 34, 19, 0, 111, 115, 116, 97, 108, 2, 103, 105, 101, 32, 24, 3, 50, 2, 108, 87, 47, 2, 35, 55, 0, 101, 114, 2, 118, 101, 117, 3, 50, 2, 110, 34, 0, 4, 97, 2, 98, 117, 114, 105, 103, 3, 50, 2, 113, 0, 97, 2, 98, 121, 103, 101, 0, 97, 8, 2, 98, 121, 21, 0, 97, 8, 2, 100, 101, 108, 105, 103, 0, 97, 8, 2, 108, 97, 116, 105, 103, 0, 97, 8, 2, 115, 112, 101, 117, 114, 0, 97, 2, 121, 119, 101, 114, 105, 103, 3, 50, 2, 113, 10, 0, 97, 97, 114, 115, 116, 105, 103, 116, 101, 3, 50, 2, 113, 34, 87, 47, 107, 134, 47, 13, 0, 97, 98, 121, 104, 2, 101, 3, 50, 2, 113, 69, 121, 105, 0, 4, 101, 101, 114, 2, 100, 114, 117, 107, 107, 3, 50, 2, 114, 34, 0, 101, 101, 114, 2, 104, 97, 108, 101, 110, 100, 0, 101, 103, 101, 114, 2, 105, 110, 3, 50, 2, 114, 134, 13, 34, 0, 111, 2, 109, 97, 100, 3, 50, 2, 115, 0, 111, 111, 114, 100, 2, 111, 111, 115, 3, 50, 2, 115, 34, 47, 10, 0, 4, 111, 111, 100, 2, 108, 111, 116, 116, 105, 3, 50, 2, 115, 47, 0, 111, 111, 100, 2, 115, 97, 97, 107, 0, 111, 116, 97, 114, 105, 2, 17, 65, 3, 50, 2, 115, 47, 2, 35, 34, 2, 37, 38, 0, 111, 98, 101, 108, 8, 3, 50, 2, 115, 69, 110, 55, 0, 111, 118, 101, 109, 98, 101, 114, 3, 50, 2, 115, 81, 106, 63, 69, 13, 34, 0, 117, 97, 110, 2, 115, 101, 101, 114, 3, 50, 2, 116, 2, 35, 50, 0, 117, 97, 110, 115, 101, 2, 114, 105, 110, 103, 3, 50, 2, 116, 2, 35, 50, 87, 114, 0, 117, 97, 110, 115, 101, 2, 25, 3, 50, 2, 116, 35, 50, 87, 13, 0, 117, 119, 101, 114, 2, 119, 101, 116, 3, 50, 2, 116, 82, 13, 34, 0, 117, 117, 115, 2, 107, 105, 101, 114, 105, 103, 3, 50, 2, 116, 87, 0, 101, 117, 2, 116, 114, 3, 50, 2, 126, 0, 101, 117, 114, 111, 2, 17, 67, 17, 65, 3, 50, 2, 126, 34, 115, 0, 97, 8, 2, 17, 67, 32, 3, 50, 6, 35, 0, 97, 103, 8, 2, 17, 67, 3, 50, 6, 35, 134, 0, 97, 8, 3, 50, 6, 113, 0, 97, 103, 8, 2, 114, 97, 97, 100, 3, 50, 6, 113, 134, 0, 97, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 50, 6, 113, 134, 13, 0, 101, 108, 101, 1, 10, 2, 32, 3, 50, 6, 114, 55, 13, 0, 101, 101, 115, 1, 21, 2, 32, 3, 50, 6, 114, 87, 0, 101, 115, 101, 2, 32, 3, 50, 6, 114, 87, 13, 0, 4, 121, 1, 114, 101, 17, 67, 21, 2, 32, 3, 50, 6, 121, 0, 121, 1, 114, 101, 17, 67, 21, 2, 101, 0, 97, 8, 2, 115, 107, 101, 101, 114, 3, 50, 7, 113, 0, 101, 101, 114, 103, 101, 8, 2, 17, 67, 21, 14, 128, 132, 134, 3, 50, 7, 114, 34, 134, 13, 0, 101, 2, 103, 111, 115, 105, 101, 3, 50, 13, 0, 110, 105, 110, 103, 3, 50, 13, 66, 0, 110, 101, 115, 1, 97, 104, 3, 50, 13, 87, 0, 4, 97, 1, 21, 2, 32, 3, 50, 35, 0, 97, 8, 2, 114, 17, 67, 0, 97, 8, 2, 116, 17, 67, 0, 97, 115, 116, 101, 114, 2, 103, 3, 50, 35, 87, 47, 13, 34, 0, 4, 97, 103, 2, 97, 100, 100, 101, 114, 3, 50, 35, 134, 10, 0, 97, 103, 2, 117, 105, 108, 0, 97, 103, 8, 2, 97, 97, 112, 0, 97, 103, 8, 2, 97, 112, 17, 65, 0, 105, 116, 114, 111, 3, 50, 37, 47, 34, 2, 40, 0, 116, 101, 114, 101, 2, 115, 115, 3, 50, 47, 34, 13, 6, 0, 101, 116, 2, 119, 101, 114, 107, 3, 50, 106, 47, 0, 101, 116, 116, 111, 8, 3, 50, 106, 47, 2, 40, 0, 4, 101, 116, 2, 97, 103, 116, 105, 103, 3, 50, 106, 47, 10, 0, 101, 116, 8, 2, 111, 0, 4, 101, 115, 1, 17, 67, 21, 2, 32, 3, 50, 106, 87, 0, 101, 115, 1, 101, 121, 98, 0, 101, 115, 1, 115, 2, 25, 0, 101, 115, 1, 121, 98, 0, 101, 115, 8, 2, 101, 105, 3, 50, 106, 87, 10, 0, 105, 2, 103, 103, 105, 101, 3, 50, 107, 0, 111, 103, 97, 108, 3, 50, 108, 134, 35, 55, 0, 101, 107, 2, 111, 109, 3, 50, 110, 49, 10, 0, 4, 97, 1, 114, 2, 32, 3, 50, 113, 0, 97, 2, 98, 111, 111, 116, 115, 0, 97, 2, 116, 114, 105, 117, 109, 0, 97, 2, 116, 114, 111, 115, 25, 0, 97, 2, 118, 114, 97, 0, 97, 8, 2, 103, 108, 111, 101, 0, 97, 8, 2, 115, 112, 101, 117, 114, 32, 24, 0, 97, 8, 2, 116, 114, 101, 107, 25, 0, 97, 1, 10, 2, 119, 101, 3, 50, 113, 2, 0, 97, 122, 105, 3, 50, 113, 47, 87, 37, 0, 97, 109, 101, 115, 3, 50, 113, 63, 13, 87, 0, 97, 100, 114, 117, 107, 108, 105, 107, 3, 50, 113, 70, 34, 6, 109, 49, 55, 13, 49, 0, 101, 116, 101, 108, 3, 50, 114, 47, 13, 55, 0, 111, 111, 100, 2, 115, 97, 97, 107, 32, 24, 3, 50, 115, 47, 0, 111, 116, 101, 2, 98, 3, 50, 115, 47, 13, 0, 121, 108, 111, 110, 3, 50, 120, 55, 108, 50, 0, 101, 117, 116, 101, 3, 50, 126, 47, 13, 0, 103, 101, 101, 115, 3, 50, 134, 114, 87, 0, 4, 2, 32, 103, 3, 66, 0, 2, 99, 0, 2, 107, 0, 2, 113, 0, 2, 116, 106, 105, 101, 0, 2, 120, 0, 103, 0, 103, 101, 114, 1, 17, 65, 17, 67, 3, 66, 13, 34, 0, 103, 101, 115, 1, 21, 2, 32, 3, 66, 13, 87, 0, 103, 117, 110, 105, 8, 3, 66, 79, 40, 12, 50, 37, 0, 4, 103, 1, 21, 2, 105, 116, 105, 115, 32, 3, 66, 134, 0, 103, 2, 101, 101, 82, 0, 103, 2, 101, 110, 116, 0, 7, 6, 111, 0, 4, 1, 17, 67, 2, 17, 67, 17, 65, 17, 65, 3, 2, 40, 0, 1, 17, 67, 2, 17, 67, 121, 0, 1, 17, 67, 10, 2, 32, 24, 0, 1, 107, 105, 115, 105, 114, 0, 2, 108, 105, 101, 110, 0, 97, 115, 101, 3, 2, 40, 10, 113, 87, 13, 0, 8, 105, 100, 117, 17, 65, 3, 2, 40, 12, 0, 114, 97, 110, 103, 2, 111, 101, 116, 3, 2, 40, 34, 2, 35, 66, 10, 0, 107, 114, 97, 116, 2, 105, 115, 17, 65, 3, 2, 40, 49, 34, 2, 35, 47, 0, 4, 2, 114, 97, 107, 101, 108, 3, 2, 108, 0, 2, 115, 111, 111, 110, 0, 8, 2, 109, 97, 114, 109, 0, 4, 114, 8, 2, 103, 97, 3, 2, 108, 34, 0, 114, 8, 2, 107, 97, 0, 4, 114, 116, 2, 111, 103, 114, 97, 3, 2, 108, 34, 47, 0, 114, 116, 2, 111, 108, 111, 0, 114, 116, 2, 111, 109, 101, 116, 114, 0, 114, 116, 2, 111, 115, 107, 111, 0, 114, 116, 111, 8, 2, 21, 3, 2, 108, 34, 47, 2, 40, 0, 114, 107, 101, 115, 3, 2, 108, 34, 49, 106, 87, 0, 114, 100, 111, 2, 110, 110, 97, 110, 3, 2, 108, 34, 70, 13, 0, 114, 100, 101, 110, 116, 8, 3, 2, 108, 34, 70, 106, 50, 47, 0, 114, 103, 97, 110, 105, 2, 115, 17, 65, 3, 2, 108, 34, 134, 2, 35, 50, 37, 0, 114, 103, 105, 2, 100, 101, 3, 2, 108, 34, 134, 13, 0, 98, 8, 2, 115, 3, 2, 108, 48, 0, 98, 115, 101, 114, 2, 118, 101, 101, 114, 3, 2, 108, 48, 87, 2, 110, 34, 0, 98, 115, 116, 105, 2, 110, 97, 3, 2, 108, 48, 87, 47, 13, 0, 107, 8, 2, 116, 17, 65, 3, 2, 108, 49, 0, 107, 107, 101, 114, 2, 110, 101, 117, 116, 3, 2, 108, 49, 13, 34, 0, 4, 109, 2, 108, 121, 3, 2, 108, 63, 0, 109, 2, 114, 105, 110, 103, 0, 109, 2, 115, 101, 105, 108, 0, 109, 2, 115, 105, 103, 0, 109, 2, 115, 119, 101, 114, 17, 67, 0, 109, 2, 118, 97, 116, 116, 0, 109, 2, 119, 101, 110, 116, 101, 108, 105, 0, 109, 8, 2, 103, 111, 114, 100, 0, 109, 8, 2, 104, 0, 109, 8, 2, 107, 108, 101, 109, 0, 109, 8, 2, 108, 97, 97, 103, 0, 109, 8, 2, 109, 117, 117, 114, 0, 109, 8, 2, 114, 97, 97, 109, 0, 109, 8, 2, 115, 105, 114, 107, 101, 108, 0, 109, 8, 2, 115, 107, 101, 112, 0, 109, 8, 2, 115, 107, 114, 0, 109, 8, 2, 115, 108, 117, 105, 101, 114, 0, 109, 8, 2, 115, 108, 117, 105, 116, 0, 109, 8, 2, 115, 116, 114, 101, 100, 101, 0, 109, 8, 2, 119, 97, 108, 0, 109, 8, 2, 119, 101, 108, 17, 67, 0, 109, 101, 108, 101, 2, 116, 3, 2, 108, 63, 13, 55, 106, 0, 109, 108, 105, 8, 2, 103, 103, 3, 2, 108, 63, 55, 107, 0, 109, 118, 101, 114, 8, 3, 2, 108, 63, 81, 110, 34, 0, 109, 115, 116, 97, 110, 100, 105, 103, 104, 3, 2, 108, 63, 87, 47, 35, 50, 70, 13, 134, 0, 109, 115, 107, 97, 110, 115, 8, 3, 2, 108, 63, 87, 49, 35, 50, 87, 0, 109, 115, 105, 110, 103, 101, 108, 3, 2, 108, 63, 87, 107, 66, 13, 55, 0, 109, 103, 101, 119, 105, 110, 103, 3, 2, 108, 63, 134, 114, 82, 13, 66, 0, 102, 102, 105, 115, 105, 3, 2, 108, 81, 2, 37, 89, 2, 37, 38, 0, 102, 102, 105, 2, 115, 105, 101, 114, 3, 2, 108, 81, 13, 0, 118, 117, 3, 2, 108, 82, 2, 116, 0, 115, 8, 2, 109, 111, 17, 67, 3, 2, 108, 87, 0, 115, 115, 105, 108, 108, 2, 101, 3, 2, 108, 87, 13, 55, 0, 115, 115, 105, 108, 108, 101, 2, 17, 67, 17, 65, 3, 2, 108, 87, 13, 55, 114, 0, 4, 1, 17, 67, 2, 17, 67, 105, 101, 101, 3, 2, 115, 0, 2, 108, 105, 109, 0, 2, 108, 121, 17, 67, 0, 2, 112, 97, 97, 108, 0, 2, 112, 97, 108, 101, 0, 8, 2, 118, 97, 21, 0, 114, 105, 195, 171, 110, 116, 2, 21, 3, 2, 115, 34, 2, 37, 57, 2, 106, 50, 47, 0, 114, 97, 110, 106, 101, 3, 2, 115, 34, 35, 50, 57, 13, 0, 114, 101, 110, 116, 2, 25, 3, 2, 115, 34, 106, 50, 47, 0, 116, 111, 109, 105, 101, 1, 21, 2, 32, 24, 3, 2, 115, 47, 2, 40, 63, 6, 37, 0, 116, 111, 109, 105, 101, 1, 21, 2, 195, 171, 3, 2, 115, 47, 2, 40, 63, 6, 37, 12, 0, 107, 97, 112, 105, 3, 2, 115, 49, 113, 48, 2, 37, 0, 108, 101, 2, 97, 110, 100, 101, 114, 3, 2, 115, 55, 2, 37, 0, 108, 121, 109, 2, 112, 3, 2, 115, 55, 107, 63, 0, 109, 105, 8, 2, 115, 115, 105, 101, 3, 2, 115, 63, 37, 0, 109, 101, 103, 97, 3, 2, 115, 63, 114, 134, 35, 0, 118, 97, 114, 105, 2, 111, 116, 111, 109, 105, 3, 2, 115, 82, 2, 113, 34, 2, 37, 0, 119, 101, 114, 2, 115, 112, 101, 108, 105, 103, 3, 2, 115, 82, 13, 34, 0, 115, 101, 2, 97, 3, 2, 115, 89, 2, 37, 0, 117, 116, 2, 111, 107, 114, 97, 3, 2, 118, 47, 0, 117, 100, 101, 114, 2, 119, 101, 116, 3, 2, 118, 70, 13, 34, 0, 1, 114, 117, 98, 2, 32, 3, 4, 115, 0, 117, 120, 3, 6, 40, 0, 109, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 6, 108, 63, 134, 13, 0, 109, 103, 101, 101, 2, 12, 3, 6, 108, 63, 134, 114, 0, 1, 98, 114, 2, 32, 3, 6, 115, 0, 114, 105, 117, 3, 6, 115, 34, 37, 109, 0, 116, 105, 101, 115, 1, 21, 3, 6, 115, 47, 37, 87, 0, 103, 105, 103, 1, 17, 67, 3, 10, 115, 134, 13, 134, 0, 4, 39, 8, 2, 17, 67, 3, 21, 0, 121, 1, 17, 67, 0, 105, 114, 1, 25, 2, 32, 3, 21, 102, 114, 0, 4, 1, 114, 107, 105, 109, 3, 40, 0, 2, 116, 101, 114, 97, 112, 0, 101, 0, 101, 1, 104, 2, 114, 0, 101, 1, 107, 2, 114, 0, 101, 1, 116, 2, 114, 17, 65, 0, 101, 1, 119, 2, 114, 0, 101, 8, 2, 114, 0, 1, 108, 105, 102, 2, 21, 3, 40, 2, 0, 4, 101, 2, 114, 3, 40, 12, 0, 101, 2, 195, 171, 0, 195, 171, 3, 40, 12, 13, 0, 101, 116, 101, 108, 1, 17, 67, 3, 40, 47, 13, 55, 0, 116, 114, 111, 111, 112, 3, 40, 47, 34, 6, 115, 48, 0, 116, 114, 111, 112, 101, 3, 40, 47, 34, 6, 115, 48, 13, 0, 116, 114, 111, 112, 105, 101, 115, 3, 40, 47, 34, 6, 115, 48, 37, 87, 0, 116, 114, 111, 112, 105, 101, 3, 40, 47, 34, 40, 48, 6, 37, 0, 101, 107, 101, 1, 116, 2, 110, 3, 40, 49, 2, 106, 0, 4, 107, 114, 97, 97, 116, 3, 40, 49, 34, 6, 113, 47, 0, 107, 114, 97, 116, 2, 17, 65, 0, 107, 114, 97, 115, 105, 101, 3, 40, 49, 34, 35, 87, 6, 37, 0, 4, 108, 105, 101, 107, 1, 25, 3, 40, 55, 6, 37, 49, 0, 108, 105, 101, 107, 2, 101, 32, 0, 108, 105, 101, 107, 105, 103, 3, 40, 55, 6, 37, 49, 13, 134, 0, 108, 111, 195, 171, 3, 40, 55, 6, 40, 13, 0, 108, 111, 111, 103, 3, 40, 55, 6, 115, 134, 0, 108, 111, 103, 105, 101, 115, 3, 40, 55, 6, 115, 134, 37, 87, 0, 108, 111, 103, 105, 101, 3, 40, 55, 40, 134, 6, 37, 0, 108, 111, 103, 105, 101, 2, 115, 116, 3, 40, 55, 40, 134, 7, 37, 0, 109, 101, 116, 114, 105, 101, 115, 3, 40, 63, 6, 114, 47, 34, 37, 87, 0, 109, 101, 116, 114, 105, 101, 3, 40, 63, 114, 47, 34, 6, 37, 0, 100, 105, 101, 107, 3, 40, 70, 6, 37, 49, 0, 102, 105, 101, 108, 3, 40, 81, 6, 37, 55, 0, 102, 111, 111, 110, 3, 40, 81, 6, 115, 50, 0, 102, 111, 110, 101, 3, 40, 81, 6, 115, 50, 13, 0, 102, 111, 98, 105, 101, 115, 3, 40, 81, 6, 115, 69, 37, 87, 0, 101, 102, 101, 110, 3, 40, 81, 13, 50, 0, 102, 105, 108, 105, 101, 3, 40, 81, 37, 55, 6, 37, 0, 102, 111, 98, 105, 101, 3, 40, 81, 115, 69, 6, 37, 0, 101, 119, 101, 114, 8, 3, 40, 82, 13, 34, 0, 115, 111, 111, 102, 3, 40, 87, 6, 115, 81, 0, 115, 111, 102, 105, 101, 115, 3, 40, 87, 6, 115, 81, 37, 87, 0, 115, 111, 119, 101, 3, 40, 87, 6, 115, 82, 13, 0, 115, 111, 102, 105, 101, 3, 40, 87, 40, 81, 6, 37, 0, 115, 107, 111, 111, 112, 3, 40, 87, 49, 6, 115, 48, 0, 115, 107, 111, 112, 101, 3, 40, 87, 49, 6, 115, 48, 13, 0, 115, 107, 111, 112, 105, 101, 115, 3, 40, 87, 49, 6, 115, 48, 37, 87, 0, 103, 114, 97, 97, 102, 3, 40, 134, 34, 6, 113, 81, 0, 103, 114, 97, 102, 105, 101, 115, 3, 40, 134, 34, 6, 113, 81, 37, 87, 0, 103, 114, 97, 119, 101, 3, 40, 134, 34, 6, 113, 82, 13, 0, 103, 114, 97, 102, 105, 101, 3, 40, 134, 34, 35, 81, 6, 37, 0, 4, 1, 119, 2, 114, 115, 116, 101, 108, 3, 108, 0, 2, 17, 67, 0, 114, 100, 101, 8, 3, 108, 34, 70, 13, 0, 107, 107, 101, 108, 1, 17, 67, 3, 108, 49, 13, 55, 0, 4, 109, 2, 104, 97, 3, 108, 63, 0, 109, 8, 2, 107, 114, 105, 110, 103, 14, 128, 132, 130, 0, 109, 1, 98, 2, 111, 3, 108, 63, 10, 0, 4, 109, 107, 101, 101, 114, 3, 108, 63, 49, 114, 34, 0, 109, 107, 101, 114, 8, 2, 17, 65, 0, 109, 103, 101, 119, 101, 2, 32, 3, 108, 63, 134, 6, 114, 82, 13, 0, 115, 115, 101, 119, 97, 2, 17, 67, 3, 108, 87, 13, 82, 113, 0, 103, 103, 101, 110, 100, 2, 21, 3, 108, 134, 13, 50, 47, 10, 0, 103, 103, 101, 110, 100, 101, 2, 32, 3, 108, 134, 13, 50, 70, 13, 0, 4, 3, 115, 0, 1, 17, 67, 2, 17, 67, 105, 101, 0, 1, 17, 67, 2, 100, 105, 117, 109, 0, 1, 17, 67, 2, 108, 105, 97, 0, 1, 98, 2, 17, 67, 17, 65, 17, 65, 0, 1, 98, 2, 108, 121, 17, 67, 0, 1, 115, 10, 2, 32, 0, 2, 17, 67, 17, 65, 0, 114, 105, 101, 3, 115, 34, 37, 0, 107, 101, 114, 8, 3, 115, 49, 13, 34, 0, 119, 101, 114, 2, 21, 3, 115, 82, 13, 34, 0, 4, 117, 3, 118, 0, 117, 119, 2, 25, 0, 117, 116, 111, 8, 2, 21, 14, 128, 132, 132, 3, 118, 47, 40, 0, 4, 105, 3, 122, 0, 121, 0, 4, 100, 106, 105, 101, 3, 122, 78, 37, 0, 116, 106, 105, 101, 0, 101, 105, 3, 124, 0, 101, 110, 116, 106, 105, 101, 3, 124, 66, 78, 37, 0, 4, 101, 100, 106, 105, 101, 3, 124, 78, 37, 0, 101, 116, 106, 105, 101, 0, 4, 1, 114, 103, 2, 110, 100, 3, 129, 0, 1, 119, 2, 114, 115, 0, 7, 6, 112, 0, 2, 112, 3, 0, 111, 114, 8, 2, 17, 67, 3, 2, 48, 108, 34, 0, 111, 112, 117, 3, 4, 48, 108, 48, 116, 0, 3, 48, 0, 4, 105, 2, 107, 97, 110, 116, 3, 48, 2, 37, 0, 105, 8, 2, 108, 97, 0, 105, 111, 2, 110, 105, 101, 114, 3, 48, 2, 37, 2, 40, 0, 105, 114, 97, 2, 109, 105, 3, 48, 2, 37, 34, 2, 35, 0, 105, 101, 116, 101, 114, 8, 2, 115, 17, 65, 21, 3, 48, 2, 37, 47, 13, 34, 0, 105, 111, 2, 110, 3, 48, 2, 37, 57, 108, 0, 4, 111, 2, 108, 101, 109, 105, 101, 3, 48, 2, 40, 0, 111, 2, 108, 105, 101, 112, 0, 111, 195, 171, 115, 105, 101, 3, 48, 2, 40, 12, 13, 86, 37, 0, 111, 195, 171, 2, 116, 17, 65, 3, 48, 2, 40, 12, 114, 0, 111, 116, 101, 110, 8, 2, 17, 67, 3, 48, 2, 40, 47, 106, 50, 0, 111, 108, 105, 115, 105, 2, 101, 101, 114, 3, 48, 2, 40, 55, 2, 37, 87, 2, 37, 0, 111, 108, 105, 115, 105, 195, 171, 3, 48, 2, 40, 55, 2, 37, 87, 2, 37, 114, 0, 111, 108, 105, 116, 105, 101, 115, 3, 48, 2, 40, 55, 37, 47, 2, 37, 87, 0, 111, 108, 105, 115, 105, 101, 3, 48, 2, 40, 55, 37, 87, 2, 37, 0, 111, 109, 101, 108, 111, 3, 48, 2, 40, 63, 114, 55, 2, 40, 0, 111, 115, 105, 115, 105, 101, 3, 48, 2, 40, 86, 37, 87, 2, 37, 0, 111, 114, 116, 117, 2, 103, 101, 3, 48, 2, 108, 34, 47, 2, 116, 0, 112, 111, 114, 116, 101, 1, 97, 114, 2, 114, 17, 65, 3, 48, 2, 108, 34, 47, 114, 0, 111, 114, 115, 101, 2, 108, 101, 105, 110, 3, 48, 2, 108, 34, 87, 13, 0, 111, 116, 2, 115, 105, 101, 114, 3, 48, 2, 108, 47, 0, 111, 110, 8, 2, 100, 111, 107, 3, 48, 2, 108, 50, 0, 4, 111, 108, 2, 102, 121, 110, 3, 48, 2, 108, 55, 0, 111, 108, 2, 118, 121, 0, 111, 108, 105, 195, 171, 115, 116, 101, 2, 114, 3, 48, 2, 108, 55, 2, 37, 38, 106, 87, 47, 13, 0, 4, 111, 108, 101, 2, 109, 105, 101, 107, 3, 48, 2, 108, 55, 13, 0, 111, 108, 105, 2, 116, 17, 65, 17, 65, 17, 67, 0, 111, 115, 116, 8, 2, 117, 3, 48, 2, 108, 87, 47, 0, 117, 110, 116, 101, 110, 101, 114, 3, 48, 2, 109, 50, 47, 13, 50, 114, 34, 0, 117, 98, 2, 108, 105, 3, 48, 2, 109, 69, 0, 111, 114, 2, 105, 101, 3, 48, 2, 115, 34, 0, 111, 114, 105, 2, 101, 117, 115, 3, 48, 2, 115, 34, 2, 37, 0, 111, 116, 101, 110, 2, 115, 105, 97, 3, 48, 2, 115, 47, 2, 106, 50, 0, 111, 108, 105, 8, 2, 17, 67, 3, 48, 2, 115, 55, 2, 37, 0, 117, 2, 112, 105, 108, 3, 48, 2, 116, 0, 117, 114, 105, 2, 116, 101, 105, 110, 3, 48, 2, 116, 34, 13, 0, 111, 115, 116, 8, 2, 25, 3, 48, 6, 118, 87, 47, 20, 0, 111, 115, 2, 97, 100, 118, 101, 114, 116, 3, 48, 7, 108, 87, 10, 0, 111, 108, 105, 115, 8, 2, 25, 3, 48, 7, 115, 55, 13, 87, 0, 105, 2, 115, 116, 111, 3, 48, 13, 0, 105, 107, 107, 101, 2, 119, 121, 110, 3, 48, 13, 49, 13, 0, 115, 97, 108, 109, 105, 115, 3, 48, 13, 87, 2, 35, 55, 13, 63, 107, 87, 0, 115, 97, 108, 109, 8, 3, 48, 13, 87, 35, 55, 13, 63, 0, 105, 103, 2, 109, 101, 17, 65, 3, 48, 13, 134, 0, 105, 122, 122, 97, 3, 48, 37, 47, 87, 35, 0, 111, 2, 108, 105, 101, 115, 109, 97, 110, 3, 48, 40, 0, 4, 108, 97, 2, 102, 111, 110, 3, 48, 55, 2, 35, 0, 108, 97, 2, 115, 116, 105, 101, 107, 0, 108, 97, 8, 2, 107, 107, 97, 0, 108, 97, 8, 2, 116, 97, 0, 108, 97, 110, 101, 2, 116, 17, 65, 3, 48, 55, 2, 35, 50, 13, 6, 0, 108, 97, 110, 116, 2, 97, 97, 114, 100, 105, 3, 48, 55, 2, 35, 50, 47, 10, 0, 108, 97, 110, 101, 116, 101, 3, 48, 55, 2, 35, 50, 114, 47, 13, 0, 108, 97, 103, 105, 2, 97, 3, 48, 55, 2, 35, 134, 2, 37, 0, 108, 101, 105, 2, 100, 111, 111, 105, 3, 48, 55, 2, 121, 0, 108, 105, 103, 116, 105, 103, 1, 21, 3, 48, 55, 6, 107, 134, 47, 13, 134, 0, 108, 101, 115, 105, 101, 114, 3, 48, 55, 13, 87, 6, 37, 12, 34, 0, 108, 105, 103, 3, 48, 55, 107, 134, 0, 108, 101, 2, 107, 3, 48, 55, 110, 0, 108, 97, 116, 105, 110, 117, 109, 2, 17, 65, 3, 48, 55, 113, 47, 37, 50, 109, 63, 10, 0, 115, 105, 103, 101, 8, 101, 105, 110, 3, 48, 87, 13, 134, 13, 0, 4, 111, 114, 2, 115, 105, 101, 3, 48, 108, 34, 0, 111, 114, 2, 115, 116, 111, 107, 0, 111, 116, 2, 121, 115, 116, 101, 114, 3, 48, 108, 47, 10, 0, 111, 102, 2, 97, 100, 100, 3, 48, 108, 81, 10, 0, 111, 115, 8, 2, 97, 3, 48, 108, 87, 0, 195, 170, 114, 101, 2, 17, 67, 3, 48, 111, 34, 13, 0, 111, 108, 105, 111, 3, 48, 115, 55, 117, 0, 104, 2, 32, 3, 81, 0, 104, 105, 2, 108, 105, 112, 112, 17, 65, 32, 3, 81, 13, 0, 104, 105, 2, 108, 105, 112, 3, 81, 107, 0, 115, 2, 105, 103, 17, 65, 3, 87, 0, 115, 105, 103, 101, 2, 100, 101, 108, 105, 101, 3, 87, 2, 37, 134, 13, 0, 115, 101, 117, 100, 111, 3, 87, 126, 70, 2, 40, 0, 7, 6, 113, 0, 2, 113, 3, 0, 117, 3, 21, 0, 3, 49, 58, 0, 117, 105, 120, 2, 111, 116, 105, 101, 3, 49, 58, 2, 37, 49, 87, 0, 7, 6, 114, 0, 2, 114, 3, 0, 4, 108, 2, 32, 3, 21, 0, 108, 115, 2, 32, 0, 3, 34, 0, 4, 97, 2, 98, 98, 121, 110, 3, 34, 2, 35, 0, 97, 2, 110, 116, 115, 111, 101, 110, 0, 97, 2, 112, 105, 101, 114, 0, 97, 8, 2, 112, 112, 111, 114, 116, 0, 97, 109, 2, 112, 111, 107, 107, 101, 114, 3, 34, 2, 35, 63, 0, 4, 97, 109, 112, 2, 115, 97, 108, 105, 103, 3, 34, 2, 35, 63, 48, 0, 97, 109, 112, 2, 115, 112, 111, 101, 100, 21, 0, 97, 110, 8, 2, 103, 101, 101, 114, 3, 34, 2, 35, 66, 0, 97, 102, 102, 105, 110, 97, 100, 101, 2, 114, 3, 34, 2, 35, 81, 2, 37, 50, 2, 35, 70, 13, 0, 105, 8, 2, 111, 3, 34, 2, 37, 0, 111, 2, 106, 97, 3, 34, 2, 40, 0, 111, 101, 116, 105, 110, 101, 3, 34, 2, 40, 47, 37, 50, 13, 0, 111, 117, 108, 101, 116, 116, 101, 3, 34, 2, 40, 55, 106, 47, 0, 111, 109, 97, 110, 3, 34, 2, 40, 63, 35, 50, 0, 111, 101, 109, 101, 2, 110, 105, 195, 171, 3, 34, 2, 40, 63, 37, 12, 0, 111, 110, 2, 100, 97, 119, 101, 108, 3, 34, 2, 108, 50, 0, 111, 110, 100, 2, 98, 111, 114, 115, 116, 3, 34, 2, 108, 50, 47, 0, 111, 110, 100, 111, 109, 2, 116, 97, 108, 105, 3, 34, 2, 108, 50, 47, 2, 108, 63, 0, 4, 117, 2, 98, 114, 105, 101, 107, 3, 34, 2, 109, 0, 117, 2, 109, 111, 101, 114, 0, 117, 109, 97, 2, 116, 105, 101, 107, 3, 34, 2, 109, 63, 13, 0, 97, 100, 105, 2, 111, 108, 111, 21, 3, 34, 2, 113, 70, 2, 37, 0, 111, 111, 115, 2, 107, 108, 101, 117, 114, 105, 3, 34, 2, 115, 87, 0, 117, 2, 195, 175, 110, 3, 34, 2, 116, 10, 0, 111, 111, 100, 101, 8, 3, 34, 6, 115, 70, 13, 0, 117, 103, 8, 2, 17, 65, 21, 3, 34, 7, 109, 134, 10, 0, 97, 2, 110, 111, 110, 107, 101, 108, 3, 34, 13, 0, 105, 116, 117, 2, 17, 65, 3, 34, 13, 47, 2, 116, 0, 105, 110, 110, 101, 2, 119, 3, 34, 13, 50, 13, 0, 4, 105, 110, 103, 1, 10, 2, 32, 3, 34, 13, 66, 0, 114, 105, 110, 103, 0, 105, 118, 105, 101, 114, 3, 34, 13, 81, 37, 12, 34, 0, 105, 115, 2, 107, 97, 110, 116, 3, 34, 13, 87, 0, 110, 1, 21, 2, 25, 3, 34, 14, 50, 0, 109, 1, 10, 2, 25, 3, 34, 14, 63, 0, 97, 107, 101, 2, 116, 3, 34, 35, 49, 6, 106, 0, 4, 8, 2, 32, 15, 15, 15, 3, 34, 35, 50, 47, 0, 8, 2, 32, 15, 15, 46, 0, 8, 2, 32, 15, 46, 0, 97, 110, 100, 8, 2, 17, 65, 21, 3, 34, 35, 50, 47, 10, 0, 4, 97, 100, 105, 107, 97, 2, 108, 101, 3, 34, 35, 70, 37, 49, 6, 113, 0, 97, 100, 105, 107, 97, 97, 0, 97, 100, 105, 107, 97, 2, 108, 105, 3, 34, 35, 70, 37, 49, 35, 0, 97, 115, 115, 101, 3, 34, 35, 87, 13, 0, 105, 101, 116, 101, 3, 34, 37, 47, 13, 0, 117, 2, 100, 111, 108, 17, 67, 3, 34, 40, 0, 111, 101, 114, 115, 101, 108, 3, 34, 40, 34, 87, 13, 55, 0, 105, 8, 2, 103, 3, 34, 107, 0, 105, 116, 109, 101, 3, 34, 107, 47, 63, 13, 0, 105, 110, 107, 104, 2, 97, 108, 115, 3, 34, 107, 66, 49, 0, 105, 98, 98, 101, 2, 116, 106, 3, 34, 107, 69, 2, 37, 0, 111, 110, 100, 2, 114, 3, 34, 108, 50, 47, 0, 111, 110, 100, 111, 109, 3, 34, 108, 50, 47, 10, 2, 108, 63, 0, 111, 108, 8, 2, 17, 65, 3, 34, 108, 55, 19, 0, 117, 103, 98, 121, 3, 34, 109, 79, 69, 37, 0, 117, 115, 112, 101, 114, 2, 17, 67, 3, 34, 109, 87, 48, 13, 34, 0, 97, 97, 100, 2, 17, 65, 3, 34, 113, 47, 10, 0, 97, 100, 105, 111, 3, 34, 113, 70, 117, 12, 10, 0, 97, 99, 104, 101, 108, 3, 34, 113, 134, 13, 55, 0, 111, 98, 111, 116, 2, 17, 65, 3, 34, 115, 69, 108, 47, 10, 0, 8, 2, 32, 3, 110, 34, 0, 7, 6, 115, 0, 2, 115, 3, 0, 4, 104, 2, 32, 3, 21, 0, 104, 105, 114, 101, 2, 32, 0, 4, 3, 87, 0, 1, 21, 2, 32, 14, 128, 192, 129, 0, 1, 21, 2, 106, 97, 115, 0, 1, 21, 2, 106, 111, 101, 114, 110, 0, 1, 21, 2, 106, 111, 110, 17, 67, 0, 1, 21, 21, 21, 2, 32, 14, 128, 128, 129, 0, 1, 105, 2, 32, 0, 1, 111, 2, 32, 0, 1, 117, 2, 32, 0, 2, 99, 104, 97, 111, 115, 0, 2, 99, 104, 101, 109, 105, 0, 2, 106, 97, 97, 112, 0, 2, 106, 97, 103, 0, 4, 97, 2, 114, 111, 110, 103, 3, 87, 2, 35, 0, 97, 2, 116, 105, 114, 0, 97, 2, 116, 117, 114, 110, 117, 0, 4, 97, 114, 2, 107, 17, 65, 3, 87, 2, 35, 34, 0, 97, 114, 8, 2, 100, 0, 97, 114, 97, 2, 115, 101, 3, 87, 2, 35, 34, 2, 35, 0, 97, 114, 107, 111, 2, 102, 97, 3, 87, 2, 35, 34, 49, 2, 40, 0, 4, 97, 110, 2, 17, 65, 116, 17, 65, 17, 67, 3, 87, 2, 35, 50, 0, 97, 110, 8, 2, 100, 97, 0, 4, 97, 108, 2, 109, 97, 110, 100, 101, 114, 3, 87, 2, 35, 55, 0, 97, 108, 2, 112, 101, 116, 101, 114, 0, 97, 108, 97, 2, 109, 97, 110, 100, 101, 114, 3, 87, 2, 35, 55, 2, 35, 0, 97, 108, 111, 2, 110, 3, 87, 2, 35, 55, 108, 0, 97, 109, 8, 2, 98, 3, 87, 2, 35, 63, 0, 97, 109, 97, 114, 105, 2, 116, 97, 3, 87, 2, 35, 63, 2, 35, 34, 2, 37, 0, 97, 110, 103, 101, 114, 101, 2, 25, 3, 87, 2, 35, 66, 13, 34, 106, 0, 97, 98, 111, 116, 2, 17, 65, 3, 87, 2, 35, 69, 2, 40, 47, 0, 97, 102, 97, 114, 105, 3, 87, 2, 35, 81, 113, 34, 2, 37, 0, 97, 118, 2, 97, 110, 110, 17, 65, 3, 87, 2, 35, 82, 0, 97, 103, 2, 109, 111, 101, 3, 87, 2, 35, 134, 0, 97, 103, 104, 101, 98, 98, 101, 2, 110, 3, 87, 2, 35, 134, 105, 106, 69, 13, 0, 105, 8, 2, 107, 108, 111, 3, 87, 2, 37, 0, 105, 112, 114, 101, 2, 25, 3, 87, 2, 37, 48, 34, 106, 0, 105, 101, 108, 107, 117, 110, 1, 21, 2, 100, 105, 103, 3, 87, 2, 37, 55, 49, 4, 109, 50, 0, 4, 111, 2, 110, 97, 116, 17, 65, 3, 87, 2, 40, 0, 111, 2, 112, 114, 97, 0, 111, 117, 2, 102, 102, 108, 101, 117, 0, 117, 2, 115, 97, 17, 67, 0, 117, 8, 2, 109, 101, 114, 105, 0, 111, 101, 116, 2, 115, 97, 112, 112, 105, 3, 87, 2, 40, 47, 0, 111, 110, 110, 101, 2, 116, 3, 87, 2, 40, 50, 106, 0, 111, 109, 97, 8, 2, 108, 105, 17, 65, 3, 87, 2, 40, 63, 113, 0, 111, 101, 100, 97, 8, 2, 110, 3, 87, 2, 40, 70, 35, 0, 111, 101, 119, 101, 2, 110, 105, 101, 114, 3, 87, 2, 40, 82, 13, 0, 111, 115, 97, 2, 116, 105, 3, 87, 2, 40, 87, 113, 0, 4, 111, 2, 108, 105, 100, 3, 87, 2, 108, 0, 111, 2, 108, 105, 101, 100, 0, 4, 111, 108, 2, 100, 121, 3, 87, 2, 108, 55, 0, 111, 108, 8, 2, 100, 97, 0, 117, 2, 109, 109, 105, 101, 114, 3, 87, 2, 109, 0, 117, 114, 114, 111, 2, 103, 97, 3, 87, 2, 109, 34, 2, 40, 0, 4, 117, 98, 2, 115, 116, 97, 110, 115, 105, 101, 3, 87, 2, 109, 48, 0, 117, 98, 2, 116, 105, 0, 117, 107, 115, 101, 115, 3, 87, 2, 109, 49, 87, 106, 87, 0, 117, 108, 116, 97, 110, 97, 3, 87, 2, 109, 55, 47, 113, 50, 2, 35, 0, 4, 117, 98, 2, 108, 105, 3, 87, 2, 109, 69, 0, 117, 98, 2, 115, 105, 100, 17, 65, 0, 117, 98, 2, 115, 107, 114, 105, 112, 0, 117, 98, 108, 105, 2, 109, 17, 65, 3, 87, 2, 109, 69, 55, 2, 37, 0, 117, 98, 108, 105, 109, 105, 2, 110, 97, 3, 87, 2, 109, 69, 55, 2, 37, 63, 2, 37, 0, 117, 98, 115, 116, 105, 2, 116, 117, 3, 87, 2, 109, 69, 87, 47, 13, 0, 117, 103, 103, 101, 115, 3, 87, 2, 109, 134, 106, 87, 0, 97, 2, 116, 97, 110, 105, 101, 3, 87, 2, 113, 0, 97, 109, 101, 8, 2, 104, 17, 65, 21, 3, 87, 2, 113, 63, 13, 0, 99, 101, 110, 97, 114, 105, 111, 3, 87, 2, 114, 50, 113, 34, 2, 37, 38, 2, 115, 0, 117, 105, 100, 2, 45, 97, 102, 114, 105, 107, 3, 87, 2, 125, 47, 0, 117, 105, 100, 2, 111, 111, 115, 3, 87, 2, 125, 47, 10, 0, 105, 110, 111, 2, 110, 105, 101, 109, 3, 87, 4, 37, 50, 2, 40, 0, 117, 112, 101, 114, 105, 110, 116, 101, 110, 100, 101, 110, 116, 3, 87, 4, 40, 48, 34, 13, 50, 47, 2, 106, 50, 70, 106, 50, 47, 0, 4, 111, 100, 111, 109, 2, 105, 101, 116, 3, 87, 4, 115, 70, 108, 63, 0, 111, 100, 111, 109, 2, 105, 101, 116, 0, 105, 116, 114, 117, 115, 3, 87, 6, 37, 47, 34, 2, 109, 87, 10, 0, 105, 101, 102, 1, 21, 2, 32, 3, 87, 6, 37, 81, 0, 105, 101, 119, 101, 1, 21, 2, 32, 3, 87, 6, 37, 82, 13, 0, 105, 101, 119, 101, 114, 1, 21, 2, 32, 3, 87, 6, 37, 82, 13, 34, 0, 105, 2, 110, 110, 105, 103, 3, 87, 6, 107, 0, 117, 103, 1, 21, 2, 116, 105, 103, 3, 87, 6, 109, 134, 0, 101, 108, 102, 2, 32, 3, 87, 6, 110, 55, 81, 0, 97, 97, 109, 8, 2, 14, 128, 132, 132, 3, 87, 6, 113, 63, 0, 97, 109, 101, 8, 2, 21, 14, 128, 132, 132, 3, 87, 6, 113, 63, 13, 0, 101, 114, 105, 110, 103, 1, 21, 3, 87, 6, 114, 34, 13, 66, 0, 101, 119, 101, 1, 25, 2, 17, 67, 3, 87, 6, 114, 82, 13, 0, 111, 110, 2, 111, 109, 3, 87, 7, 108, 50, 10, 0, 117, 112, 101, 114, 2, 17, 65, 3, 87, 7, 116, 48, 13, 34, 10, 0, 101, 119, 101, 1, 21, 2, 119, 105, 103, 3, 87, 10, 114, 82, 13, 0, 4, 105, 2, 108, 108, 97, 98, 17, 65, 3, 87, 13, 0, 105, 2, 108, 108, 97, 98, 17, 65, 0, 105, 2, 110, 97, 112, 25, 0, 105, 2, 112, 105, 101, 114, 0, 105, 2, 116, 114, 111, 101, 110, 0, 105, 2, 118, 105, 101, 108, 0, 105, 8, 2, 110, 111, 17, 67, 0, 105, 114, 101, 110, 101, 3, 87, 13, 34, 114, 50, 13, 0, 105, 116, 114, 111, 110, 101, 108, 108, 97, 3, 87, 13, 47, 34, 2, 40, 50, 110, 55, 2, 35, 0, 101, 112, 116, 101, 109, 98, 101, 114, 3, 87, 13, 48, 47, 106, 63, 69, 13, 34, 0, 4, 105, 110, 2, 106, 97, 3, 87, 13, 50, 0, 105, 110, 2, 116, 97, 107, 17, 67, 0, 105, 110, 8, 2, 100, 114, 111, 0, 105, 110, 116, 101, 116, 105, 101, 115, 3, 87, 13, 50, 47, 114, 47, 37, 87, 0, 105, 110, 105, 115, 116, 2, 17, 65, 114, 3, 87, 13, 50, 107, 87, 47, 0, 105, 108, 105, 107, 111, 111, 110, 3, 87, 13, 55, 2, 37, 49, 115, 50, 10, 0, 105, 108, 104, 111, 101, 2, 17, 65, 3, 87, 13, 55, 2, 40, 58, 0, 105, 108, 105, 2, 110, 100, 3, 87, 13, 55, 107, 0, 97, 108, 97, 114, 105, 115, 3, 87, 13, 55, 113, 34, 13, 87, 0, 4, 105, 109, 8, 2, 98, 17, 65, 3, 87, 13, 63, 0, 105, 109, 112, 2, 116, 111, 0, 105, 109, 109, 101, 2, 116, 114, 105, 101, 32, 24, 3, 87, 13, 63, 13, 0, 105, 109, 112, 111, 2, 115, 105, 17, 65, 3, 87, 13, 63, 48, 115, 0, 105, 109, 98, 105, 2, 111, 17, 67, 3, 87, 13, 63, 69, 2, 37, 0, 105, 109, 98, 111, 2, 108, 105, 101, 107, 3, 87, 13, 63, 69, 2, 40, 0, 105, 109, 109, 101, 2, 116, 114, 105, 101, 3, 87, 13, 63, 114, 0, 4, 101, 115, 1, 21, 2, 32, 3, 87, 13, 87, 0, 105, 115, 2, 116, 121, 110, 0, 105, 115, 116, 2, 101, 3, 87, 13, 87, 47, 0, 105, 115, 116, 101, 2, 109, 97, 116, 3, 87, 13, 87, 47, 13, 0, 105, 103, 2, 97, 21, 3, 87, 13, 134, 0, 105, 103, 97, 114, 101, 2, 116, 3, 87, 13, 134, 2, 35, 34, 106, 0, 97, 8, 2, 102, 102, 3, 87, 35, 7, 0, 97, 110, 100, 2, 97, 100, 100, 101, 114, 3, 87, 35, 50, 47, 10, 0, 97, 108, 118, 111, 2, 25, 3, 87, 35, 55, 82, 2, 40, 0, 97, 104, 97, 114, 97, 3, 87, 35, 105, 6, 113, 34, 35, 0, 105, 2, 107, 108, 105, 101, 3, 87, 37, 0, 105, 112, 97, 108, 101, 1, 21, 3, 87, 37, 48, 6, 113, 55, 13, 0, 105, 101, 107, 101, 8, 3, 87, 37, 49, 13, 0, 105, 107, 108, 117, 2, 115, 3, 87, 37, 49, 55, 109, 0, 111, 110, 97, 110, 116, 3, 87, 40, 50, 6, 35, 50, 47, 0, 112, 97, 2, 115, 105, 101, 101, 114, 3, 87, 48, 2, 35, 0, 112, 97, 114, 8, 2, 116, 97, 21, 3, 87, 48, 2, 35, 34, 0, 4, 112, 97, 110, 2, 100, 97, 98, 3, 87, 48, 2, 35, 50, 0, 112, 97, 110, 2, 106, 17, 65, 17, 65, 0, 112, 97, 110, 2, 115, 112, 101, 107, 0, 112, 97, 115, 2, 109, 111, 100, 3, 87, 48, 2, 35, 87, 0, 4, 112, 105, 2, 110, 97, 21, 3, 87, 48, 2, 37, 0, 112, 105, 8, 2, 114, 97, 0, 112, 105, 110, 101, 2, 116, 3, 87, 48, 2, 37, 50, 106, 0, 112, 101, 107, 2, 116, 97, 107, 101, 108, 3, 87, 48, 2, 106, 49, 0, 112, 101, 107, 117, 2, 108, 17, 65, 3, 87, 48, 2, 106, 49, 2, 116, 0, 112, 101, 115, 8, 2, 109, 97, 3, 87, 48, 2, 106, 87, 0, 112, 101, 115, 105, 2, 102, 3, 87, 48, 2, 106, 87, 2, 107, 0, 112, 101, 115, 105, 2, 97, 3, 87, 48, 2, 106, 89, 2, 37, 0, 112, 111, 110, 8, 2, 116, 97, 3, 87, 48, 2, 108, 50, 0, 112, 111, 114, 116, 8, 2, 21, 21, 21, 3, 87, 48, 7, 108, 34, 47, 10, 0, 112, 101, 114, 1, 21, 2, 97, 3, 87, 48, 13, 34, 6, 0, 112, 105, 116, 115, 2, 118, 111, 110, 3, 87, 48, 13, 47, 87, 0, 112, 101, 115, 101, 2, 114, 121, 3, 87, 48, 13, 87, 13, 0, 112, 114, 101, 101, 107, 119, 111, 111, 114, 100, 101, 108, 105, 3, 87, 48, 34, 2, 114, 49, 82, 115, 34, 70, 13, 55, 13, 0, 112, 114, 105, 110, 103, 98, 111, 2, 107, 3, 87, 48, 34, 7, 107, 66, 69, 108, 0, 112, 114, 111, 107, 101, 3, 87, 48, 34, 115, 49, 13, 0, 112, 97, 114, 116, 101, 108, 3, 87, 48, 35, 34, 47, 13, 55, 0, 112, 97, 116, 8, 2, 97, 3, 87, 48, 35, 47, 10, 0, 112, 111, 101, 100, 8, 2, 21, 3, 87, 48, 40, 47, 0, 112, 111, 101, 100, 2, 105, 103, 3, 87, 48, 40, 70, 0, 112, 101, 114, 1, 107, 101, 2, 105, 109, 3, 87, 48, 106, 34, 0, 112, 101, 115, 105, 97, 108, 105, 115, 3, 87, 48, 106, 89, 35, 55, 6, 107, 87, 0, 112, 101, 115, 105, 97, 108, 105, 115, 2, 17, 65, 3, 87, 48, 106, 89, 37, 35, 55, 37, 87, 0, 4, 112, 101, 108, 1, 17, 65, 17, 65, 2, 100, 3, 87, 48, 110, 55, 0, 112, 101, 108, 1, 17, 67, 2, 32, 0, 112, 101, 108, 1, 101, 2, 32, 0, 112, 101, 108, 8, 17, 65, 110, 2, 32, 0, 112, 101, 108, 97, 103, 116, 105, 103, 3, 87, 48, 110, 55, 6, 35, 134, 47, 13, 134, 0, 112, 101, 110, 101, 2, 32, 3, 87, 48, 114, 50, 13, 0, 112, 101, 108, 101, 1, 10, 2, 32, 3, 87, 48, 114, 55, 13, 0, 107, 97, 2, 118, 111, 116, 3, 87, 49, 2, 35, 0, 107, 97, 114, 8, 2, 17, 67, 3, 87, 49, 2, 35, 34, 0, 107, 97, 107, 101, 114, 2, 105, 110, 103, 3, 87, 49, 2, 35, 49, 114, 34, 0, 107, 97, 110, 2, 100, 97, 3, 87, 49, 2, 35, 50, 0, 107, 97, 110, 100, 101, 2, 114, 105, 110, 103, 3, 87, 49, 2, 35, 50, 70, 114, 0, 107, 105, 115, 111, 102, 114, 2, 101, 3, 87, 49, 2, 37, 87, 2, 40, 81, 34, 0, 107, 101, 2, 100, 117, 108, 101, 3, 87, 49, 2, 106, 0, 107, 111, 112, 112, 101, 108, 2, 109, 97, 97, 3, 87, 49, 2, 108, 48, 13, 55, 0, 107, 101, 114, 2, 109, 117, 116, 115, 3, 87, 49, 2, 110, 34, 0, 107, 101, 114, 112, 105, 2, 111, 101, 110, 3, 87, 49, 2, 110, 34, 48, 2, 37, 0, 107, 111, 2, 108, 105, 101, 114, 3, 87, 49, 2, 115, 0, 107, 121, 110, 2, 104, 101, 105, 3, 87, 49, 2, 121, 50, 0, 107, 97, 112, 108, 105, 107, 1, 21, 3, 87, 49, 6, 35, 48, 55, 13, 49, 0, 107, 121, 110, 108, 105, 107, 1, 21, 3, 87, 49, 6, 121, 50, 55, 13, 49, 0, 107, 111, 107, 8, 2, 17, 65, 14, 128, 132, 132, 3, 87, 49, 7, 108, 49, 10, 0, 107, 101, 2, 100, 111, 110, 107, 3, 87, 49, 13, 0, 107, 105, 108, 100, 101, 114, 2, 121, 3, 87, 49, 13, 55, 70, 13, 34, 0, 107, 101, 108, 101, 8, 2, 116, 3, 87, 49, 13, 55, 106, 0, 107, 114, 97, 112, 110, 101, 2, 108, 3, 87, 49, 34, 2, 35, 48, 50, 110, 0, 107, 114, 105, 102, 2, 17, 65, 3, 87, 49, 34, 107, 81, 10, 0, 107, 97, 114, 114, 101, 108, 3, 87, 49, 35, 34, 13, 55, 0, 107, 97, 112, 112, 121, 8, 17, 67, 17, 65, 17, 65, 17, 67, 3, 87, 49, 35, 48, 6, 121, 0, 4, 107, 97, 112, 1, 21, 2, 105, 110, 21, 3, 87, 49, 35, 48, 10, 0, 107, 97, 112, 1, 21, 2, 111, 0, 107, 108, 101, 2, 114, 111, 115, 101, 3, 87, 49, 55, 13, 0, 107, 117, 108, 100, 2, 101, 114, 107, 101, 110, 3, 87, 49, 109, 55, 47, 10, 0, 107, 101, 114, 112, 3, 87, 49, 110, 34, 48, 0, 107, 97, 100, 101, 3, 87, 49, 113, 70, 13, 0, 107, 97, 100, 117, 3, 87, 49, 113, 70, 116, 0, 107, 101, 109, 101, 114, 3, 87, 49, 114, 63, 13, 34, 0, 107, 111, 111, 110, 103, 101, 2, 17, 67, 3, 87, 49, 115, 50, 134, 13, 0, 107, 111, 108, 101, 3, 87, 49, 115, 55, 13, 0, 110, 101, 108, 8, 2, 17, 65, 3, 87, 50, 7, 110, 55, 10, 0, 110, 101, 108, 2, 32, 3, 87, 50, 110, 55, 0, 110, 97, 112, 101, 114, 2, 105, 110, 103, 3, 87, 50, 113, 48, 13, 34, 0, 108, 97, 2, 118, 105, 110, 3, 87, 55, 2, 35, 0, 108, 97, 103, 8, 3, 87, 55, 7, 35, 134, 10, 0, 108, 97, 103, 2, 111, 102, 102, 3, 87, 55, 35, 134, 10, 0, 108, 111, 112, 2, 101, 109, 109, 101, 114, 3, 87, 55, 108, 48, 10, 0, 108, 97, 2, 119, 101, 3, 87, 55, 113, 0, 4, 106, 1, 21, 2, 97, 17, 67, 17, 65, 3, 87, 57, 0, 106, 1, 21, 2, 97, 97, 114, 0, 4, 119, 2, 101, 114, 109, 3, 87, 58, 0, 119, 8, 0, 119, 97, 2, 104, 105, 108, 105, 3, 87, 58, 2, 35, 0, 119, 97, 114, 116, 2, 103, 97, 108, 3, 87, 58, 2, 35, 34, 47, 0, 4, 119, 97, 97, 114, 2, 108, 121, 119, 3, 87, 58, 2, 113, 34, 0, 119, 97, 97, 114, 2, 109, 111, 101, 100, 0, 119, 97, 109, 8, 2, 17, 65, 21, 3, 87, 58, 35, 63, 10, 0, 117, 105, 116, 101, 3, 87, 58, 37, 47, 13, 0, 119, 101, 110, 100, 101, 108, 3, 87, 58, 106, 50, 70, 13, 55, 0, 119, 101, 109, 1, 21, 2, 32, 3, 87, 58, 106, 63, 0, 119, 101, 109, 8, 2, 17, 65, 3, 87, 58, 106, 63, 10, 0, 119, 105, 116, 115, 101, 114, 3, 87, 58, 107, 47, 87, 13, 34, 0, 119, 101, 101, 112, 3, 87, 58, 114, 48, 0, 119, 101, 112, 101, 3, 87, 58, 114, 48, 13, 0, 109, 97, 2, 114, 97, 103, 3, 87, 63, 2, 35, 0, 109, 101, 108, 116, 3, 87, 63, 110, 55, 47, 0, 119, 97, 103, 2, 25, 3, 87, 82, 35, 134, 0, 119, 101, 114, 107, 1, 21, 3, 87, 82, 110, 34, 49, 0, 119, 101, 101, 1, 21, 2, 32, 3, 87, 82, 114, 0, 105, 108, 105, 107, 111, 2, 110, 3, 87, 107, 55, 2, 37, 49, 2, 108, 0, 105, 108, 119, 101, 114, 3, 87, 107, 55, 82, 13, 34, 0, 105, 116, 117, 97, 115, 105, 101, 3, 87, 107, 74, 40, 6, 113, 87, 37, 0, 111, 2, 110, 110, 101, 116, 106, 105, 101, 12, 12, 3, 87, 108, 0, 111, 110, 2, 103, 21, 3, 87, 108, 50, 0, 117, 98, 8, 2, 97, 3, 87, 109, 69, 10, 0, 97, 107, 101, 3, 87, 113, 49, 13, 0, 97, 109, 101, 110, 2, 12, 3, 87, 113, 63, 13, 50, 0, 97, 109, 101, 108, 2, 17, 67, 3, 87, 113, 63, 13, 55, 0, 97, 97, 109, 103, 101, 101, 3, 87, 113, 63, 134, 114, 0, 101, 119, 101, 2, 116, 106, 105, 101, 3, 87, 114, 82, 37, 0, 111, 2, 118, 3, 87, 115, 0, 111, 105, 101, 8, 3, 87, 115, 19, 37, 0, 111, 118, 101, 114, 114, 101, 3, 87, 115, 81, 6, 110, 34, 13, 0, 111, 115, 105, 97, 108, 2, 105, 3, 87, 115, 89, 37, 35, 55, 6, 0, 111, 115, 105, 111, 2, 45, 3, 87, 115, 89, 117, 12, 0, 97, 117, 110, 97, 3, 87, 129, 50, 35, 0, 4, 1, 17, 67, 2, 105, 101, 101, 17, 67, 3, 89, 0, 1, 17, 67, 2, 105, 195, 171, 108, 101, 0, 2, 105, 195, 171, 110, 0, 99, 104, 0, 104, 8, 0, 106, 0, 106, 97, 2, 109, 97, 3, 89, 2, 35, 0, 106, 97, 114, 2, 109, 97, 110, 116, 3, 89, 2, 35, 34, 0, 106, 97, 109, 112, 97, 110, 106, 101, 3, 89, 2, 35, 63, 48, 35, 50, 57, 13, 0, 106, 97, 109, 112, 111, 101, 3, 89, 2, 35, 63, 48, 40, 12, 0, 106, 111, 107, 111, 108, 97, 100, 101, 3, 89, 2, 108, 49, 13, 55, 113, 70, 13, 0, 106, 105, 109, 112, 97, 110, 2, 115, 101, 101, 3, 89, 13, 63, 48, 2, 35, 50, 0, 105, 1, 21, 2, 111, 3, 89, 37, 0, 105, 97, 97, 108, 3, 89, 37, 6, 113, 55, 0, 105, 97, 108, 101, 3, 89, 37, 6, 113, 55, 13, 0, 99, 104, 117, 8, 2, 17, 67, 3, 89, 40, 0, 106, 101, 114, 114, 105, 101, 3, 89, 106, 34, 37, 0, 105, 111, 1, 21, 2, 110, 101, 3, 89, 117, 6, 0, 7, 6, 116, 0, 4, 2, 32, 100, 24, 3, 0, 2, 116, 3, 0, 4, 99, 104, 1, 17, 65, 3, 21, 0, 104, 1, 21, 2, 32, 24, 0, 104, 8, 0, 104, 121, 1, 21, 2, 32, 0, 105, 111, 110, 1, 21, 2, 32, 0, 105, 111, 110, 115, 1, 21, 2, 32, 0, 108, 101, 1, 21, 2, 32, 0, 106, 105, 101, 1, 101, 114, 3, 37, 78, 37, 0, 4, 3, 47, 0, 1, 17, 67, 21, 2, 101, 110, 121, 0, 1, 21, 2, 101, 109, 97, 25, 12, 12, 0, 1, 97, 97, 114, 116, 115, 2, 106, 0, 104, 1, 21, 2, 17, 67, 0, 104, 8, 2, 21, 21, 0, 4, 97, 1, 21, 2, 108, 105, 115, 3, 47, 2, 35, 0, 97, 2, 98, 108, 101, 116, 0, 97, 2, 114, 105, 101, 102, 0, 97, 2, 114, 105, 101, 119, 101, 0, 97, 8, 2, 109, 98, 0, 97, 114, 8, 2, 116, 97, 21, 3, 47, 2, 35, 34, 0, 97, 114, 101, 110, 2, 116, 97, 3, 47, 2, 35, 34, 13, 50, 0, 97, 116, 111, 101, 2, 195, 171, 3, 47, 2, 35, 47, 2, 40, 0, 97, 112, 105, 115, 115, 101, 2, 114, 105, 3, 47, 2, 35, 48, 13, 87, 13, 0, 97, 107, 115, 105, 100, 101, 114, 2, 109, 3, 47, 2, 35, 49, 87, 2, 37, 70, 2, 110, 34, 0, 97, 110, 122, 97, 2, 110, 105, 3, 47, 2, 35, 50, 86, 113, 0, 97, 108, 101, 110, 2, 116, 106, 105, 101, 3, 47, 2, 35, 55, 106, 37, 66, 0, 97, 108, 101, 110, 116, 3, 47, 2, 35, 55, 106, 50, 47, 0, 97, 109, 97, 114, 105, 115, 107, 3, 47, 2, 35, 63, 2, 35, 34, 107, 87, 49, 0, 97, 109, 101, 108, 101, 2, 116, 106, 3, 47, 2, 35, 63, 13, 55, 106, 37, 0, 97, 109, 98, 111, 101, 2, 114, 121, 110, 3, 47, 2, 35, 63, 69, 2, 40, 0, 97, 109, 97, 2, 116, 105, 101, 3, 47, 2, 35, 63, 113, 0, 97, 98, 101, 114, 2, 110, 97, 107, 101, 108, 3, 47, 2, 35, 69, 13, 34, 0, 97, 98, 97, 107, 3, 47, 2, 35, 69, 35, 49, 0, 97, 98, 108, 111, 2, 16, 3, 47, 2, 35, 69, 55, 115, 0, 97, 102, 101, 2, 114, 101, 3, 47, 2, 35, 81, 13, 0, 97, 118, 101, 114, 2, 110, 105, 101, 114, 3, 47, 2, 35, 81, 13, 34, 0, 97, 118, 101, 114, 110, 101, 3, 47, 2, 35, 81, 110, 34, 50, 13, 0, 4, 105, 2, 112, 101, 114, 17, 65, 3, 47, 2, 37, 0, 105, 2, 114, 97, 0, 105, 101, 114, 108, 97, 110, 2, 116, 121, 3, 47, 2, 37, 12, 34, 55, 2, 35, 50, 0, 105, 114, 97, 2, 110, 110, 105, 101, 3, 47, 2, 37, 34, 2, 35, 0, 105, 110, 101, 110, 8, 2, 116, 97, 21, 3, 47, 2, 37, 50, 2, 106, 50, 0, 105, 98, 101, 116, 8, 3, 47, 2, 37, 69, 106, 47, 0, 105, 97, 114, 97, 3, 47, 2, 37, 113, 34, 35, 0, 4, 111, 101, 2, 107, 111, 109, 101, 3, 47, 2, 40, 0, 111, 101, 2, 107, 111, 109, 115, 116, 105, 0, 111, 101, 2, 108, 97, 97, 116, 98, 97, 0, 111, 101, 2, 114, 105, 115, 116, 101, 21, 0, 111, 101, 114, 2, 110, 3, 47, 2, 40, 34, 0, 111, 101, 114, 101, 107, 101, 110, 2, 98, 3, 47, 2, 40, 34, 6, 114, 49, 13, 50, 0, 111, 101, 114, 101, 105, 107, 101, 3, 47, 2, 40, 34, 121, 49, 13, 0, 4, 111, 112, 8, 2, 97, 97, 115, 3, 47, 2, 40, 48, 0, 111, 112, 8, 2, 97, 115, 101, 0, 111, 101, 112, 97, 115, 108, 105, 107, 3, 47, 2, 40, 48, 35, 87, 55, 13, 49, 0, 111, 110, 101, 101, 108, 3, 47, 2, 40, 50, 114, 55, 0, 111, 110, 101, 108, 101, 3, 47, 2, 40, 50, 114, 55, 13, 0, 111, 101, 103, 97, 110, 107, 3, 47, 2, 40, 134, 6, 35, 66, 49, 0, 111, 101, 103, 101, 101, 102, 3, 47, 2, 40, 134, 114, 81, 0, 111, 101, 103, 101, 119, 101, 110, 2, 100, 3, 47, 2, 40, 134, 114, 82, 13, 50, 0, 111, 114, 8, 2, 110, 121, 110, 3, 47, 2, 108, 34, 0, 111, 107, 2, 116, 111, 107, 107, 3, 47, 2, 108, 49, 0, 111, 107, 107, 101, 2, 108, 111, 3, 47, 2, 108, 49, 13, 0, 111, 109, 98, 111, 108, 97, 3, 47, 2, 108, 63, 69, 115, 55, 2, 35, 0, 111, 115, 8, 2, 107, 97, 3, 47, 2, 108, 87, 0, 111, 8, 2, 110, 97, 3, 47, 2, 115, 0, 4, 111, 112, 8, 2, 111, 103, 114, 97, 3, 47, 2, 115, 48, 0, 111, 112, 8, 2, 111, 108, 111, 0, 117, 98, 101, 114, 107, 117, 108, 111, 115, 101, 3, 47, 2, 116, 69, 13, 34, 49, 2, 116, 55, 115, 87, 13, 0, 97, 105, 119, 97, 2, 110, 3, 47, 2, 119, 58, 35, 0, 121, 100, 2, 114, 111, 119, 3, 47, 2, 121, 47, 0, 111, 105, 2, 108, 101, 116, 3, 47, 2, 122, 0, 117, 105, 110, 2, 105, 101, 114, 3, 47, 2, 125, 50, 0, 1, 114, 101, 118, 100, 97, 2, 101, 3, 47, 6, 0, 105, 101, 102, 1, 21, 2, 32, 3, 47, 6, 37, 81, 0, 4, 105, 101, 119, 101, 1, 21, 2, 32, 3, 47, 6, 37, 82, 13, 0, 105, 101, 119, 101, 1, 21, 2, 114, 32, 0, 111, 101, 8, 2, 119, 101, 110, 25, 14, 128, 132, 131, 3, 47, 6, 40, 0, 111, 101, 103, 101, 8, 2, 21, 14, 128, 132, 133, 3, 47, 6, 40, 134, 13, 0, 111, 101, 103, 101, 2, 119, 105, 110, 103, 3, 47, 6, 40, 134, 114, 0, 97, 108, 105, 103, 1, 21, 3, 47, 6, 113, 55, 13, 134, 0, 111, 114, 105, 115, 1, 21, 2, 32, 3, 47, 6, 115, 34, 13, 87, 0, 117, 117, 114, 3, 47, 6, 116, 34, 0, 121, 1, 21, 2, 100, 105, 103, 3, 47, 6, 121, 0, 117, 105, 103, 108, 105, 107, 3, 47, 6, 125, 134, 55, 13, 49, 0, 97, 110, 100, 101, 8, 2, 17, 67, 21, 3, 47, 7, 35, 50, 70, 13, 0, 111, 112, 8, 2, 17, 65, 3, 47, 7, 108, 48, 10, 0, 117, 114, 98, 111, 8, 2, 25, 3, 47, 7, 109, 34, 69, 115, 10, 0, 104, 101, 117, 8, 3, 47, 7, 126, 0, 116, 101, 108, 3, 47, 13, 55, 0, 105, 110, 107, 2, 116, 105, 110, 107, 3, 47, 13, 66, 49, 0, 4, 97, 110, 100, 2, 111, 3, 47, 35, 50, 47, 10, 0, 97, 110, 100, 8, 2, 97, 0, 105, 116, 101, 108, 3, 47, 37, 47, 13, 55, 0, 105, 115, 115, 117, 101, 3, 47, 37, 89, 2, 40, 0, 111, 101, 114, 101, 2, 32, 3, 47, 40, 12, 34, 13, 0, 111, 101, 110, 101, 109, 101, 110, 3, 47, 40, 50, 6, 114, 63, 13, 50, 0, 4, 106, 1, 21, 2, 97, 3, 47, 57, 0, 106, 1, 105, 117, 0, 106, 111, 101, 114, 110, 97, 108, 105, 1, 21, 3, 47, 57, 2, 40, 34, 50, 2, 35, 55, 13, 0, 119, 101, 101, 100, 2, 25, 3, 47, 58, 37, 12, 70, 0, 119, 105, 115, 2, 17, 65, 3, 47, 58, 107, 87, 10, 0, 119, 101, 101, 100, 2, 114, 97, 3, 47, 58, 114, 70, 0, 119, 121, 102, 101, 2, 108, 3, 47, 58, 121, 81, 13, 0, 111, 103, 1, 103, 114, 111, 98, 3, 47, 108, 134, 10, 0, 117, 114, 108, 105, 110, 103, 116, 111, 110, 3, 47, 109, 12, 55, 2, 37, 66, 47, 13, 50, 0, 117, 115, 115, 101, 110, 3, 47, 109, 87, 13, 50, 0, 117, 103, 2, 17, 65, 3, 47, 109, 134, 10, 0, 4, 117, 117, 114, 1, 105, 116, 114, 97, 112, 3, 47, 116, 12, 34, 0, 117, 117, 114, 1, 115, 0, 121, 100, 2, 114, 3, 47, 121, 47, 0, 97, 110, 116, 8, 2, 101, 3, 47, 131, 50, 47, 0, 97, 110, 116, 101, 115, 3, 47, 131, 50, 47, 13, 87, 0, 4, 106, 3, 74, 0, 106, 8, 2, 105, 101, 0, 106, 101, 2, 108, 108, 105, 115, 3, 74, 2, 106, 0, 106, 97, 110, 107, 1, 21, 3, 74, 35, 66, 49, 0, 106, 101, 108, 108, 111, 3, 74, 106, 55, 40, 0, 106, 2, 105, 101, 3, 78, 0, 106, 105, 101, 1, 105, 117, 3, 78, 37, 0, 105, 97, 2, 32, 3, 89, 57, 35, 0, 7, 6, 117, 0, 103, 97, 110, 2, 100, 101, 3, 2, 40, 79, 2, 35, 50, 0, 1, 109, 2, 115, 107, 105, 101, 116, 3, 2, 109, 0, 108, 116, 105, 2, 109, 97, 3, 2, 109, 55, 47, 2, 37, 0, 8, 2, 114, 97, 3, 2, 116, 0, 114, 105, 110, 101, 3, 2, 116, 34, 37, 50, 13, 0, 114, 105, 101, 110, 119, 101, 103, 3, 2, 116, 34, 37, 50, 82, 110, 134, 10, 0, 114, 101, 8, 2, 116, 3, 2, 116, 34, 114, 0, 116, 111, 2, 112, 105, 17, 65, 3, 2, 116, 47, 115, 0, 110, 105, 118, 101, 114, 115, 2, 17, 65, 21, 3, 2, 116, 50, 2, 37, 82, 2, 110, 34, 87, 0, 115, 8, 98, 2, 17, 65, 3, 7, 109, 87, 10, 0, 2, 104, 108, 101, 32, 3, 40, 12, 0, 2, 17, 67, 3, 109, 0, 4, 3, 116, 0, 2, 17, 67, 17, 65, 0, 117, 0, 114, 101, 8, 2, 17, 67, 3, 116, 12, 34, 13, 0, 114, 105, 110, 101, 101, 114, 3, 116, 34, 37, 50, 6, 114, 34, 0, 119, 1, 110, 3, 116, 82, 0, 4, 119, 101, 1, 110, 2, 17, 67, 3, 116, 82, 13, 0, 119, 101, 1, 114, 17, 67, 2, 17, 67, 0, 119, 101, 108, 105, 107, 1, 17, 67, 3, 116, 82, 13, 55, 13, 49, 0, 121, 3, 125, 0, 110, 116, 106, 105, 101, 1, 17, 67, 3, 125, 66, 78, 37, 0, 116, 106, 105, 101, 3, 125, 78, 37, 0, 7, 6, 118, 0, 2, 118, 3, 0, 105, 108, 108, 101, 3, 21, 0, 3, 81, 0, 97, 2, 108, 108, 101, 105, 3, 81, 2, 35, 0, 97, 116, 105, 2, 107, 97, 97, 110, 3, 81, 2, 35, 47, 2, 37, 0, 97, 107, 97, 2, 116, 117, 114, 101, 3, 81, 2, 35, 49, 13, 0, 97, 110, 8, 2, 21, 3, 81, 2, 35, 50, 0, 97, 110, 115, 101, 108, 102, 2, 115, 112, 114, 3, 81, 2, 35, 50, 87, 2, 110, 55, 81, 0, 105, 2, 111, 3, 81, 2, 37, 0, 105, 111, 2, 108, 101, 116, 25, 3, 81, 2, 37, 2, 40, 0, 105, 101, 114, 2, 107, 97, 110, 116, 105, 103, 3, 81, 2, 37, 12, 34, 0, 105, 116, 114, 105, 2, 111, 101, 108, 3, 81, 2, 37, 47, 34, 2, 37, 0, 4, 117, 108, 2, 107, 97, 3, 81, 2, 109, 55, 0, 117, 108, 8, 2, 103, 97, 97, 116, 0, 121, 2, 97, 110, 100, 105, 103, 3, 81, 2, 121, 0, 97, 108, 108, 105, 103, 3, 81, 6, 35, 55, 13, 134, 0, 97, 115, 103, 101, 8, 2, 21, 14, 128, 132, 133, 3, 81, 6, 35, 87, 134, 13, 0, 105, 115, 101, 2, 25, 3, 81, 6, 37, 87, 37, 0, 117, 108, 100, 105, 103, 3, 81, 6, 109, 55, 70, 13, 134, 0, 97, 97, 114, 100, 105, 103, 1, 21, 3, 81, 6, 113, 34, 70, 13, 134, 0, 97, 107, 97, 110, 115, 105, 101, 3, 81, 13, 49, 35, 50, 87, 37, 0, 4, 105, 115, 1, 25, 2, 105, 101, 114, 3, 81, 13, 87, 0, 105, 115, 1, 101, 105, 21, 2, 32, 0, 105, 115, 101, 110, 2, 116, 101, 3, 81, 13, 87, 13, 50, 0, 105, 115, 105, 116, 101, 3, 81, 13, 87, 37, 47, 13, 0, 114, 101, 100, 101, 2, 108, 105, 101, 119, 3, 81, 34, 2, 114, 70, 13, 0, 114, 101, 101, 115, 97, 97, 110, 2, 106, 97, 3, 81, 34, 2, 114, 87, 19, 2, 113, 50, 0, 4, 114, 121, 2, 109, 101, 115, 115, 101, 108, 3, 81, 34, 2, 121, 0, 114, 121, 2, 109, 111, 101, 100, 0, 114, 121, 2, 112, 111, 115, 116, 105, 0, 114, 121, 2, 119, 105, 108, 0, 114, 105, 101, 110, 100, 105, 2, 110, 3, 81, 34, 37, 50, 70, 6, 107, 0, 114, 111, 116, 2, 101, 105, 101, 114, 3, 81, 34, 108, 47, 10, 0, 114, 101, 101, 109, 100, 101, 3, 81, 34, 114, 63, 70, 13, 0, 114, 101, 100, 101, 3, 81, 34, 114, 70, 13, 0, 114, 121, 103, 101, 119, 105, 103, 3, 81, 34, 121, 134, 6, 114, 82, 13, 134, 0, 97, 2, 100, 111, 101, 107, 3, 81, 35, 0, 97, 116, 8, 2, 17, 65, 21, 3, 81, 35, 47, 10, 0, 97, 107, 2, 117, 110, 105, 101, 3, 81, 35, 49, 10, 0, 97, 110, 103, 8, 2, 21, 3, 81, 35, 66, 0, 97, 110, 103, 101, 110, 3, 81, 35, 66, 13, 50, 0, 97, 110, 107, 108, 105, 107, 8, 3, 81, 35, 66, 49, 55, 13, 49, 0, 97, 115, 115, 116, 101, 2, 108, 3, 81, 35, 87, 47, 110, 0, 105, 115, 1, 100, 97, 2, 101, 21, 3, 81, 37, 87, 6, 0, 108, 105, 101, 195, 171, 2, 110, 105, 101, 114, 3, 81, 55, 2, 37, 13, 0, 108, 97, 109, 2, 111, 111, 3, 81, 55, 35, 63, 10, 0, 108, 97, 2, 17, 67, 17, 65, 17, 65, 3, 81, 55, 113, 0, 105, 115, 2, 17, 65, 3, 81, 107, 87, 0, 195, 169, 114, 3, 81, 111, 34, 0, 4, 97, 97, 114, 100, 105, 103, 1, 114, 101, 118, 3, 81, 113, 34, 70, 13, 134, 0, 97, 97, 114, 100, 105, 103, 1, 116, 105, 117, 0, 97, 116, 101, 2, 17, 67, 3, 81, 113, 47, 13, 0, 1, 21, 2, 97, 108, 101, 110, 116, 3, 82, 0, 97, 2, 107, 117, 3, 82, 2, 35, 0, 97, 114, 105, 2, 17, 65, 3, 82, 2, 35, 34, 2, 37, 0, 97, 108, 117, 116, 97, 3, 82, 2, 35, 55, 116, 47, 2, 35, 0, 97, 115, 101, 108, 105, 110, 101, 3, 82, 2, 35, 87, 13, 55, 37, 50, 0, 97, 103, 105, 110, 2, 17, 65, 21, 3, 82, 2, 35, 134, 2, 37, 50, 0, 4, 105, 2, 98, 114, 17, 65, 3, 82, 2, 37, 0, 105, 2, 99, 116, 111, 21, 0, 105, 8, 2, 114, 97, 0, 105, 116, 97, 2, 109, 105, 3, 82, 2, 37, 47, 2, 35, 0, 105, 115, 105, 2, 111, 101, 110, 3, 82, 2, 37, 87, 2, 37, 0, 105, 115, 2, 117, 17, 65, 3, 82, 2, 37, 88, 0, 105, 8, 2, 114, 105, 3, 82, 13, 0, 105, 114, 116, 117, 3, 82, 13, 34, 74, 2, 116, 0, 97, 103, 105, 110, 97, 3, 82, 35, 134, 37, 50, 35, 0, 105, 114, 117, 2, 25, 3, 82, 37, 34, 109, 0, 105, 116, 114, 111, 8, 2, 32, 3, 82, 37, 47, 34, 2, 40, 0, 105, 107, 105, 110, 103, 3, 82, 37, 49, 37, 66, 0, 105, 100, 101, 111, 3, 82, 37, 70, 117, 0, 4, 105, 115, 1, 17, 65, 2, 97, 115, 105, 101, 3, 82, 37, 87, 0, 105, 115, 2, 105, 101, 0, 105, 115, 2, 117, 109, 0, 105, 115, 1, 17, 65, 2, 101, 21, 3, 82, 37, 87, 6, 0, 105, 195, 171, 116, 110, 97, 2, 109, 101, 3, 82, 57, 2, 106, 47, 50, 2, 35, 0, 105, 108, 108, 97, 3, 82, 107, 55, 35, 0, 7, 6, 119, 0, 2, 119, 3, 0, 4, 1, 21, 2, 17, 67, 32, 3, 21, 0, 1, 21, 2, 32, 24, 0, 104, 0, 110, 0, 111, 111, 100, 2, 12, 0, 111, 114, 116, 104, 0, 115, 1, 21, 2, 32, 24, 0, 4, 1, 100, 3, 58, 0, 1, 104, 103, 0, 1, 107, 0, 1, 115, 0, 1, 115, 2, 97, 114, 116, 0, 1, 115, 2, 101, 101, 114, 100, 101, 114, 0, 1, 115, 21, 2, 97, 108, 107, 32, 0, 1, 115, 101, 98, 2, 97, 97, 114, 100, 101, 0, 1, 115, 101, 105, 2, 97, 97, 110, 0, 1, 115, 114, 101, 2, 101, 101, 114, 32, 0, 1, 116, 0, 97, 103, 103, 97, 1, 107, 3, 58, 35, 134, 35, 0, 97, 114, 101, 1, 115, 101, 98, 3, 58, 113, 34, 13, 0, 121, 102, 101, 108, 1, 116, 21, 3, 58, 121, 81, 13, 55, 0, 4, 3, 82, 0, 1, 17, 67, 2, 101, 101, 114, 100, 101, 114, 0, 1, 17, 67, 2, 105, 116, 32, 0, 1, 17, 67, 2, 195, 170, 114, 101, 108, 100, 0, 1, 17, 67, 17, 65, 2, 97, 97, 105, 101, 114, 0, 1, 17, 67, 21, 2, 97, 97, 114, 100, 101, 32, 0, 1, 17, 67, 21, 2, 97, 114, 109, 0, 1, 17, 67, 21, 2, 101, 114, 107, 0, 1, 17, 67, 21, 2, 101, 195, 171, 0, 1, 17, 67, 21, 2, 105, 101, 108, 0, 1, 17, 67, 21, 2, 111, 17, 67, 25, 0, 1, 17, 67, 21, 2, 111, 111, 17, 67, 0, 1, 17, 67, 21, 2, 117, 114, 109, 0, 1, 17, 67, 21, 2, 121, 100, 0, 1, 17, 67, 111, 111, 0, 1, 21, 2, 97, 101, 110, 0, 1, 100, 17, 65, 17, 65, 0, 1, 100, 21, 2, 97, 97, 114, 0, 1, 100, 97, 0, 1, 100, 110, 0, 1, 100, 111, 17, 67, 0, 1, 100, 121, 0, 1, 107, 2, 17, 65, 110, 100, 0, 1, 107, 2, 101, 114, 17, 67, 0, 1, 107, 2, 111, 17, 65, 0, 1, 107, 21, 2, 97, 108, 109, 0, 1, 115, 2, 97, 116, 101, 114, 0, 1, 115, 2, 101, 101, 107, 0, 1, 115, 2, 105, 108, 0, 1, 115, 2, 111, 101, 100, 101, 0, 1, 115, 2, 111, 101, 108, 105, 110, 103, 0, 1, 115, 2, 111, 117, 0, 1, 115, 2, 114, 0, 1, 115, 2, 121, 102, 0, 1, 115, 10, 2, 101, 101, 102, 115, 0, 1, 115, 17, 65, 17, 65, 2, 101, 110, 107, 0, 1, 115, 21, 2, 17, 65, 110, 32, 0, 1, 115, 21, 2, 17, 65, 110, 100, 0, 1, 115, 21, 2, 97, 97, 110, 0, 1, 115, 21, 2, 97, 108, 0, 1, 115, 21, 2, 97, 110, 103, 32, 0, 1, 115, 21, 2, 97, 110, 103, 101, 32, 0, 1, 115, 21, 2, 101, 110, 110, 0, 1, 115, 97, 97, 108, 112, 2, 101, 114, 17, 67, 0, 1, 115, 97, 118, 0, 1, 115, 105, 101, 108, 118, 0, 1, 115, 105, 109, 0, 1, 115, 107, 108, 111, 118, 0, 1, 115, 107, 121, 108, 2, 97, 97, 17, 67, 0, 1, 115, 110, 101, 0, 1, 115, 111, 108, 0, 1, 115, 114, 101, 0, 1, 116, 2, 97, 97, 114, 0, 1, 116, 2, 97, 116, 0, 1, 116, 17, 65, 11, 0, 1, 116, 21, 2, 97, 110, 100, 0, 1, 116, 21, 2, 105, 101, 0, 1, 116, 21, 2, 121, 0, 1, 116, 101, 111, 0, 1, 116, 105, 0, 1, 116, 110, 2, 17, 65, 0, 1, 116, 114, 97, 119, 115, 0, 1, 116, 117, 17, 67, 0, 1, 116, 117, 111, 0, 2, 101, 115, 101, 32, 0, 2, 121, 115, 0, 97, 116, 2, 119, 111, 110, 100, 3, 82, 2, 35, 47, 0, 4, 97, 110, 2, 115, 116, 97, 108, 116, 3, 82, 2, 35, 50, 0, 97, 110, 2, 116, 114, 111, 117, 105, 103, 0, 97, 110, 111, 114, 100, 101, 108, 105, 2, 107, 3, 82, 2, 35, 50, 10, 108, 34, 70, 13, 55, 13, 0, 97, 108, 2, 107, 117, 114, 101, 3, 82, 2, 35, 55, 0, 97, 110, 107, 101, 108, 2, 109, 111, 101, 100, 3, 82, 2, 35, 66, 49, 13, 55, 0, 111, 101, 2, 115, 116, 121, 110, 3, 82, 2, 40, 0, 111, 108, 2, 118, 105, 110, 3, 82, 2, 108, 55, 0, 97, 97, 114, 2, 110, 101, 101, 109, 98, 97, 3, 82, 2, 113, 34, 0, 121, 115, 103, 101, 2, 114, 105, 103, 3, 82, 2, 121, 87, 134, 114, 0, 195, 170, 114, 101, 108, 100, 8, 2, 21, 14, 128, 132, 134, 3, 82, 6, 111, 34, 13, 55, 47, 10, 0, 97, 97, 114, 100, 105, 103, 1, 10, 3, 82, 6, 113, 34, 70, 13, 134, 0, 97, 110, 8, 2, 17, 65, 14, 128, 132, 131, 3, 82, 7, 35, 50, 10, 0, 105, 108, 108, 101, 2, 109, 105, 3, 82, 13, 55, 13, 0, 105, 108, 104, 101, 108, 2, 109, 105, 3, 82, 13, 55, 105, 2, 110, 55, 0, 105, 110, 107, 101, 2, 108, 105, 101, 114, 3, 82, 13, 66, 49, 13, 55, 0, 105, 115, 112, 101, 108, 2, 116, 117, 3, 82, 13, 87, 48, 13, 55, 0, 114, 101, 101, 100, 2, 97, 97, 114, 100, 105, 103, 3, 82, 34, 2, 114, 47, 10, 0, 114, 101, 101, 100, 2, 97, 3, 82, 34, 114, 47, 10, 0, 4, 97, 97, 114, 100, 101, 101, 114, 3, 82, 35, 34, 70, 6, 114, 34, 0, 97, 97, 114, 100, 101, 114, 2, 21, 0, 97, 110, 103, 101, 2, 100, 114, 97, 103, 3, 82, 35, 50, 134, 13, 0, 97, 115, 1, 115, 21, 2, 25, 3, 82, 35, 87, 0, 97, 115, 97, 103, 2, 116, 105, 103, 3, 82, 35, 87, 10, 4, 35, 134, 0, 97, 103, 1, 17, 67, 2, 25, 3, 82, 35, 134, 0, 105, 107, 105, 110, 103, 3, 82, 37, 49, 37, 66, 0, 111, 114, 99, 101, 115, 116, 101, 114, 3, 82, 40, 87, 47, 13, 34, 0, 101, 100, 2, 114, 101, 110, 3, 82, 106, 47, 0, 101, 114, 115, 116, 101, 1, 21, 2, 32, 3, 82, 107, 34, 87, 47, 13, 0, 4, 105, 110, 100, 8, 2, 97, 3, 82, 107, 50, 47, 10, 0, 105, 110, 100, 8, 2, 111, 0, 105, 108, 107, 101, 114, 3, 82, 107, 55, 49, 13, 34, 0, 105, 110, 107, 101, 108, 1, 17, 67, 3, 82, 107, 66, 49, 13, 55, 0, 105, 103, 8, 3, 82, 107, 134, 0, 111, 108, 8, 2, 17, 65, 3, 82, 108, 55, 10, 0, 111, 108, 107, 101, 3, 82, 108, 55, 49, 13, 0, 195, 170, 114, 101, 108, 2, 100, 106, 105, 101, 3, 82, 111, 34, 13, 55, 0, 195, 170, 114, 101, 108, 100, 119, 3, 82, 111, 34, 13, 55, 47, 82, 0, 195, 170, 114, 101, 108, 100, 101, 2, 32, 3, 82, 111, 34, 13, 55, 70, 13, 0, 4, 97, 1, 21, 2, 32, 24, 3, 82, 113, 0, 97, 2, 115, 112, 111, 114, 101, 0, 97, 2, 118, 111, 108, 0, 97, 2, 118, 114, 97, 103, 0, 97, 8, 2, 98, 111, 0, 97, 8, 2, 119, 121, 0, 97, 97, 114, 1, 107, 3, 82, 113, 34, 0, 4, 97, 114, 101, 1, 107, 21, 3, 82, 113, 34, 13, 0, 97, 114, 101, 1, 115, 21, 0, 97, 114, 101, 1, 116, 2, 25, 0, 97, 97, 114, 116, 115, 1, 17, 67, 3, 82, 113, 34, 47, 87, 0, 97, 116, 101, 114, 1, 107, 21, 3, 82, 113, 47, 13, 34, 0, 97, 112, 101, 110, 3, 82, 113, 48, 13, 50, 0, 111, 111, 114, 100, 2, 97, 3, 82, 115, 34, 47, 10, 0, 111, 111, 114, 100, 101, 3, 82, 115, 34, 70, 13, 0, 111, 110, 105, 110, 103, 1, 17, 67, 21, 3, 82, 115, 50, 13, 66, 0, 111, 111, 110, 103, 101, 119, 101, 115, 3, 82, 115, 50, 134, 13, 82, 106, 87, 0, 121, 107, 1, 115, 10, 3, 82, 121, 49, 0, 121, 110, 107, 101, 108, 2, 100, 101, 114, 3, 82, 121, 50, 49, 110, 55, 0, 101, 110, 115, 1, 107, 117, 108, 3, 82, 132, 50, 87, 0, 7, 6, 120, 0, 2, 120, 3, 0, 104, 111, 115, 97, 3, 49, 7, 129, 87, 35, 0, 3, 49, 87, 0, 101, 110, 2, 111, 3, 86, 2, 106, 50, 0, 7, 6, 121, 0, 1, 112, 112, 97, 107, 115, 2, 32, 3, 2, 121, 0, 1, 17, 67, 11, 2, 32, 3, 21, 0, 111, 114, 107, 3, 57, 6, 129, 49, 0, 3, 121, 0, 115, 116, 101, 114, 114, 101, 2, 108, 105, 110, 3, 121, 87, 47, 13, 34, 114, 0, 7, 6, 122, 0, 2, 122, 3, 0, 3, 86, 0, 97, 109, 98, 101, 115, 105, 3, 86, 2, 35, 63, 69, 114, 87, 2, 37, 0, 101, 98, 114, 97, 3, 86, 114, 69, 34, 35, 0, 1, 116, 3, 87, 0, 7, 6, 206, 0, 4, 172, 3, 6, 35, 55, 81, 35, 10, 0, 177, 0, 4, 173, 3, 6, 106, 48, 87, 37, 55, 108, 50, 10, 0, 181, 0, 191, 3, 6, 108, 63, 37, 49, 34, 108, 50, 10, 0, 4, 174, 3, 6, 114, 47, 35, 10, 0, 183, 0, 4, 175, 3, 37, 6, 115, 47, 35, 10, 0, 185, 0, 186, 3, 49, 6, 35, 48, 35, 10, 0, 190, 3, 49, 87, 6, 37, 10, 0, 189, 3, 50, 6, 116, 12, 10, 0, 187, 3, 55, 6, 35, 63, 69, 70, 35, 10, 0, 188, 3, 63, 6, 116, 12, 10, 0, 178, 3, 69, 6, 114, 47, 35, 10, 0, 180, 3, 70, 6, 110, 55, 47, 35, 10, 0, 179, 3, 79, 6, 35, 63, 35, 10, 0, 184, 3, 85, 6, 114, 47, 35, 10, 0, 182, 3, 86, 6, 114, 47, 35, 10, 0, 7, 6, 207, 0, 4, 133, 3, 6, 40, 48, 87, 37, 55, 108, 50, 10, 0, 141, 0, 140, 3, 6, 108, 63, 37, 49, 34, 108, 50, 10, 0, 129, 3, 34, 6, 115, 10, 0, 132, 3, 47, 6, 127, 10, 0, 128, 3, 48, 6, 37, 10, 0, 136, 3, 48, 87, 6, 37, 10, 0, 134, 3, 81, 6, 37, 10, 0, 4, 130, 3, 87, 6, 37, 79, 63, 35, 10, 0, 131, 0, 135, 3, 99, 6, 37, 10, 0, 4, 137, 3, 115, 63, 6, 114, 134, 35, 10, 0, 142, 0, 7, 6, 0, 33, 1, 19, 3, 0, 195, 175, 108, 108, 117, 2, 115, 116, 3, 2, 37, 55, 2, 109, 0, 39, 116, 106, 105, 101, 1, 21, 3, 2, 37, 78, 37, 0, 195, 175, 115, 111, 108, 3, 2, 37, 87, 2, 40, 55, 0, 195, 175, 2, 110, 17, 67, 3, 6, 107, 0, 195, 169, 107, 1, 25, 2, 32, 3, 6, 110, 49, 0, 195, 170, 114, 2, 32, 3, 7, 111, 34, 0, 195, 170, 114, 101, 2, 32, 3, 7, 111, 34, 13, 0, 195, 161, 1, 17, 67, 2, 17, 67, 17, 65, 3, 7, 113, 0, 33, 3, 9, 121, 47, 34, 40, 48, 9, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 4, 195, 171, 2, 116, 101, 105, 116, 3, 13, 0, 195, 175, 2, 110, 115, 112, 0, 195, 175, 2, 110, 116, 0, 201, 153, 0, 195, 175, 110, 107, 97, 114, 110, 2, 17, 65, 3, 13, 66, 49, 2, 35, 34, 50, 0, 195, 177, 3, 21, 101, 115, 0, 195, 161, 1, 25, 2, 17, 67, 25, 3, 26, 35, 0, 195, 161, 108, 108, 101, 2, 25, 3, 26, 35, 55, 13, 0, 195, 179, 195, 169, 3, 26, 40, 0, 195, 169, 1, 25, 2, 17, 67, 25, 3, 26, 106, 0, 195, 179, 1, 25, 2, 17, 67, 25, 3, 26, 108, 0, 195, 186, 1, 25, 2, 17, 67, 25, 3, 26, 109, 0, 195, 169, 107, 2, 32, 3, 26, 110, 49, 0, 195, 161, 195, 161, 3, 26, 113, 0, 195, 169, 195, 169, 3, 26, 114, 0, 195, 179, 195, 179, 3, 26, 115, 0, 195, 179, 195, 186, 3, 26, 118, 0, 195, 189, 3, 26, 121, 0, 195, 179, 195, 179, 105, 3, 26, 123, 0, 195, 169, 195, 186, 3, 26, 126, 0, 195, 175, 103, 110, 111, 114, 101, 101, 114, 3, 37, 134, 50, 40, 34, 6, 114, 34, 0, 45, 8, 32, 2, 32, 15, 3, 63, 37, 50, 109, 87, 0, 36, 3, 70, 108, 55, 13, 34, 0, 39, 115, 1, 21, 2, 14, 128, 128, 130, 3, 87, 0, 195, 168, 8, 17, 67, 2, 32, 3, 106, 0, 195, 187, 101, 3, 109, 12, 13, 0, 195, 171, 1, 101, 103, 2, 114, 102, 3, 110, 0, 195, 170, 2, 114, 3, 111, 0, 195, 170, 101, 114, 1, 108, 3, 111, 13, 34, 0, 195, 170, 114, 1, 107, 115, 2, 12, 3, 111, 34, 0, 195, 170, 114, 101, 1, 98, 2, 32, 3, 111, 34, 13, 0, 195, 170, 3, 128, 0, 195, 180, 3, 129, 0, 195, 174, 101, 3, 130, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts1 = FileInMemory_createWithData (81297, reinterpret_cast (&espeakdata_dicts1_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/af_dict", L"af"); Collection_addItem (me.peek(), espeakdata_dicts1.transfer()); static unsigned char espeakdata_dicts2_data[1351] = { 0, 4, 0, 0, 8, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 201, 148, 0, 3, 107, 0, 7, 6, 201, 155, 0, 3, 106, 0, 7, 6, 97, 0, 3, 35, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 49, 0, 4, 2, 101, 3, 87, 0, 2, 105, 0, 7, 6, 100, 0, 3, 70, 0, 119, 3, 73, 0, 119, 2, 105, 3, 75, 0, 7, 6, 101, 0, 3, 36, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 121, 3, 70, 92, 0, 3, 79, 0, 7, 6, 104, 0, 4, 2, 105, 3, 97, 0, 121, 0, 119, 2, 105, 3, 97, 58, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 7, 6, 106, 0, 3, 73, 0, 7, 6, 107, 0, 3, 49, 0, 121, 3, 76, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 4, 103, 2, 105, 3, 65, 0, 106, 0, 119, 2, 105, 0, 4, 110, 121, 2, 105, 3, 65, 12, 0, 121, 2, 105, 0, 2, 107, 3, 66, 0, 103, 3, 66, 12, 0, 119, 3, 66, 12, 58, 0, 7, 6, 111, 0, 3, 39, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 117, 3, 49, 58, 0, 7, 6, 114, 0, 3, 51, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 2, 105, 3, 47, 97, 0, 7, 6, 117, 0, 3, 40, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 49, 87, 0, 8, 3, 86, 0, 7, 6, 121, 0, 1, 25, 2, 25, 3, 37, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 36, 3, 70, 107, 55, 35, 51, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts2 = FileInMemory_createWithData (1350, reinterpret_cast (&espeakdata_dicts2_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ak_dict", L"ak"); Collection_addItem (me.peek(), espeakdata_dicts2.transfer()); static unsigned char espeakdata_dicts3_data[3335] = { 0, 4, 0, 0, 149, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 1, 37, 48, 13, 34, 87, 6, 13, 50, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 4, 16, 20, 10, 50, 6, 13, 108, 106, 69, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 225, 141, 164, 70, 6, 106, 34, 106, 80, 106, 87, 13, 34, 13, 86, 0, 0, 20, 3, 225, 141, 167, 108, 6, 106, 57, 35, 110, 36, 63, 106, 55, 106, 49, 106, 47, 0, 0, 0, 0, 0, 18, 3, 225, 141, 163, 50, 6, 13, 108, 13, 55, 35, 87, 13, 34, 13, 86, 0, 0, 18, 3, 225, 141, 162, 19, 6, 35, 34, 35, 47, 106, 50, 13, 108, 106, 69, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 51, 88, 87, 35, 55, 6, 35, 87, 35, 0, 0, 11, 3, 95, 48, 67, 63, 6, 13, 47, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 49, 48, 6, 19, 35, 87, 87, 106, 34, 0, 0, 0, 17, 3, 95, 49, 50, 6, 19, 35, 87, 34, 35, 6, 40, 55, 13, 47, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 55, 88, 87, 13, 69, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 49, 88, 19, 35, 87, 34, 6, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 50, 88, 105, 35, 57, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 52, 88, 19, 35, 34, 69, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 53, 88, 105, 35, 63, 87, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 54, 88, 87, 37, 55, 87, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 56, 88, 87, 13, 63, 6, 35, 50, 57, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 57, 88, 86, 13, 108, 6, 13, 50, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 48, 77, 50, 63, 6, 37, 55, 106, 39, 50, 0, 0, 14, 4, 95, 48, 77, 51, 69, 6, 37, 55, 106, 39, 50, 0, 0, 0, 11, 4, 95, 48, 77, 49, 89, 6, 37, 99, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 2, 95, 51, 87, 6, 39, 87, 47, 0, 0, 11, 2, 95, 50, 105, 6, 40, 55, 13, 47, 0, 0, 10, 2, 95, 49, 6, 19, 35, 50, 70, 0, 0, 10, 2, 95, 48, 86, 6, 36, 34, 39, 0, 0, 11, 2, 95, 55, 87, 6, 13, 69, 35, 47, 0, 0, 13, 2, 95, 54, 87, 6, 106, 70, 12, 106, 87, 47, 0, 0, 13, 2, 95, 53, 6, 19, 35, 63, 63, 106, 87, 47, 0, 0, 11, 2, 95, 52, 6, 19, 35, 34, 35, 47, 0, 0, 0, 0, 11, 2, 95, 57, 86, 6, 13, 108, 13, 65, 0, 0, 12, 2, 95, 56, 87, 6, 106, 63, 106, 50, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 225, 136, 0, 173, 1, 21, 2, 32, 3, 34, 0, 168, 3, 34, 13, 0, 171, 3, 34, 35, 0, 172, 3, 34, 36, 0, 170, 3, 34, 37, 0, 174, 3, 34, 39, 0, 169, 3, 34, 40, 0, 175, 3, 34, 58, 35, 0, 173, 3, 34, 106, 0, 141, 1, 21, 2, 32, 3, 55, 0, 136, 3, 55, 13, 0, 139, 3, 55, 35, 0, 140, 3, 55, 36, 0, 138, 3, 55, 37, 0, 142, 3, 55, 39, 0, 137, 3, 55, 40, 0, 143, 3, 55, 40, 35, 0, 141, 3, 55, 106, 0, 157, 1, 21, 2, 32, 3, 63, 0, 152, 3, 63, 13, 0, 155, 3, 63, 35, 0, 156, 3, 63, 36, 0, 154, 3, 63, 37, 0, 158, 3, 63, 39, 0, 153, 3, 63, 40, 0, 159, 3, 63, 58, 35, 0, 157, 3, 63, 106, 0, 4, 165, 1, 21, 2, 32, 3, 87, 0, 181, 1, 21, 2, 32, 0, 4, 160, 3, 87, 13, 0, 176, 0, 4, 163, 3, 87, 35, 0, 179, 0, 4, 164, 3, 87, 36, 0, 180, 0, 4, 162, 3, 87, 37, 0, 178, 0, 4, 166, 3, 87, 39, 0, 182, 0, 4, 161, 3, 87, 40, 0, 177, 0, 4, 167, 3, 87, 58, 35, 0, 183, 0, 4, 165, 3, 87, 106, 0, 181, 0, 189, 1, 21, 2, 32, 3, 89, 0, 184, 3, 89, 13, 0, 187, 3, 89, 35, 0, 188, 3, 89, 36, 0, 186, 3, 89, 37, 0, 190, 3, 89, 39, 0, 185, 3, 89, 40, 0, 191, 3, 89, 58, 35, 0, 189, 3, 89, 106, 0, 4, 133, 1, 21, 2, 32, 3, 99, 0, 149, 1, 21, 2, 32, 0, 4, 128, 3, 105, 35, 0, 131, 0, 144, 0, 147, 0, 4, 132, 3, 105, 36, 0, 148, 0, 4, 130, 3, 105, 37, 0, 146, 0, 4, 134, 3, 105, 39, 0, 150, 0, 4, 129, 3, 105, 40, 0, 145, 0, 151, 3, 105, 58, 35, 0, 4, 133, 3, 105, 106, 0, 149, 0, 7, 6, 225, 137, 0, 181, 1, 21, 2, 32, 3, 47, 0, 176, 3, 47, 13, 0, 179, 3, 47, 35, 0, 180, 3, 47, 36, 0, 178, 3, 47, 37, 0, 182, 3, 47, 39, 0, 177, 3, 47, 40, 0, 183, 3, 47, 58, 35, 0, 181, 3, 47, 106, 0, 165, 1, 21, 2, 32, 3, 69, 0, 160, 3, 69, 13, 0, 163, 3, 69, 35, 0, 164, 3, 69, 36, 0, 162, 3, 69, 37, 0, 166, 3, 69, 39, 0, 161, 3, 69, 40, 0, 167, 3, 69, 58, 35, 0, 165, 3, 69, 106, 0, 189, 1, 21, 2, 32, 3, 74, 0, 184, 3, 74, 13, 0, 187, 3, 74, 35, 0, 188, 3, 74, 36, 0, 186, 3, 74, 37, 0, 190, 3, 74, 39, 0, 185, 3, 74, 40, 0, 191, 3, 74, 58, 35, 0, 189, 3, 74, 106, 0, 173, 1, 21, 2, 32, 3, 82, 0, 168, 3, 82, 13, 0, 171, 3, 82, 35, 0, 172, 3, 82, 36, 0, 170, 3, 82, 37, 0, 174, 3, 82, 39, 0, 169, 3, 82, 40, 0, 175, 3, 82, 58, 35, 0, 173, 3, 82, 106, 0, 133, 1, 21, 2, 32, 3, 110, 0, 128, 3, 110, 13, 0, 131, 3, 110, 35, 0, 132, 3, 110, 36, 0, 130, 3, 110, 37, 0, 134, 3, 110, 39, 0, 129, 3, 110, 40, 0, 141, 1, 21, 2, 32, 3, 110, 58, 0, 136, 3, 110, 58, 13, 0, 139, 3, 110, 58, 35, 0, 140, 3, 110, 58, 36, 0, 138, 3, 110, 58, 37, 0, 141, 3, 110, 58, 106, 0, 133, 3, 110, 106, 0, 7, 6, 225, 138, 0, 167, 3, 19, 13, 0, 4, 160, 3, 19, 35, 0, 163, 0, 164, 3, 19, 36, 0, 162, 3, 19, 37, 0, 166, 3, 19, 39, 0, 161, 3, 19, 40, 0, 165, 3, 19, 106, 0, 173, 1, 21, 2, 32, 3, 49, 0, 168, 3, 49, 13, 0, 171, 3, 49, 35, 0, 172, 3, 49, 36, 0, 170, 3, 49, 37, 0, 174, 3, 49, 39, 0, 169, 3, 49, 40, 0, 181, 1, 21, 2, 32, 3, 49, 58, 0, 176, 3, 49, 58, 13, 0, 179, 3, 49, 58, 35, 0, 180, 3, 49, 58, 36, 0, 178, 3, 49, 58, 37, 0, 181, 3, 49, 58, 106, 0, 173, 3, 49, 106, 0, 149, 1, 21, 2, 32, 3, 50, 0, 144, 3, 50, 13, 0, 147, 3, 50, 35, 0, 148, 3, 50, 36, 0, 146, 3, 50, 37, 0, 150, 3, 50, 39, 0, 145, 3, 50, 40, 0, 151, 3, 50, 58, 35, 0, 149, 3, 50, 106, 0, 157, 1, 21, 2, 32, 3, 65, 0, 152, 3, 65, 13, 0, 155, 3, 65, 35, 0, 156, 3, 65, 36, 0, 154, 3, 65, 37, 0, 158, 3, 65, 39, 0, 153, 3, 65, 40, 0, 159, 3, 65, 58, 35, 0, 157, 3, 65, 106, 0, 4, 133, 1, 21, 2, 32, 3, 99, 0, 189, 1, 21, 2, 32, 0, 184, 3, 105, 13, 0, 4, 128, 3, 105, 35, 0, 131, 0, 187, 0, 4, 132, 3, 105, 36, 0, 188, 0, 4, 130, 3, 105, 37, 0, 186, 0, 4, 134, 3, 105, 39, 0, 190, 0, 4, 129, 3, 105, 40, 0, 185, 0, 141, 1, 21, 2, 32, 3, 105, 58, 0, 136, 3, 105, 58, 13, 0, 139, 3, 105, 58, 35, 0, 140, 3, 105, 58, 36, 0, 138, 3, 105, 58, 37, 0, 141, 3, 105, 58, 106, 0, 4, 133, 3, 105, 106, 0, 189, 0, 7, 6, 225, 139, 0, 4, 144, 3, 19, 35, 0, 147, 0, 148, 3, 19, 36, 0, 146, 3, 19, 37, 0, 150, 3, 19, 39, 0, 145, 3, 19, 40, 0, 149, 3, 19, 106, 0, 173, 1, 21, 2, 32, 3, 57, 0, 168, 3, 57, 13, 0, 171, 3, 57, 35, 0, 172, 3, 57, 36, 0, 170, 3, 57, 37, 0, 174, 3, 57, 39, 0, 169, 3, 57, 40, 0, 173, 3, 57, 106, 0, 141, 1, 21, 2, 32, 3, 58, 0, 136, 3, 58, 13, 0, 139, 3, 58, 35, 0, 140, 3, 58, 36, 0, 138, 3, 58, 37, 0, 142, 3, 58, 39, 0, 137, 3, 58, 40, 0, 141, 3, 58, 106, 0, 181, 1, 21, 2, 32, 3, 70, 0, 176, 3, 70, 13, 0, 179, 3, 70, 35, 0, 180, 3, 70, 36, 0, 178, 3, 70, 37, 0, 182, 3, 70, 39, 0, 177, 3, 70, 40, 0, 183, 3, 70, 58, 35, 0, 189, 1, 21, 2, 32, 3, 70, 70, 0, 184, 3, 70, 70, 13, 0, 187, 3, 70, 70, 35, 0, 188, 3, 70, 70, 36, 0, 186, 3, 70, 70, 37, 0, 190, 3, 70, 70, 39, 0, 185, 3, 70, 70, 40, 0, 191, 3, 70, 70, 58, 35, 0, 189, 3, 70, 70, 106, 0, 181, 3, 70, 106, 0, 157, 1, 21, 2, 32, 3, 86, 0, 152, 3, 86, 13, 0, 155, 3, 86, 35, 0, 156, 3, 86, 36, 0, 154, 3, 86, 37, 0, 158, 3, 86, 39, 0, 153, 3, 86, 40, 0, 159, 3, 86, 58, 35, 0, 157, 3, 86, 106, 0, 165, 1, 21, 2, 32, 3, 88, 0, 160, 3, 88, 13, 0, 163, 3, 88, 35, 0, 164, 3, 88, 36, 0, 162, 3, 88, 37, 0, 166, 3, 88, 39, 0, 161, 3, 88, 40, 0, 167, 3, 88, 58, 35, 0, 165, 3, 88, 106, 0, 133, 1, 21, 2, 32, 3, 105, 58, 0, 128, 3, 105, 58, 13, 0, 131, 3, 105, 58, 35, 0, 132, 3, 105, 58, 36, 0, 130, 3, 105, 58, 37, 0, 133, 3, 105, 58, 106, 0, 7, 6, 225, 140, 0, 189, 1, 21, 2, 32, 3, 47, 87, 0, 184, 3, 47, 87, 13, 0, 187, 3, 47, 87, 35, 0, 188, 3, 47, 87, 36, 0, 186, 3, 47, 87, 37, 0, 190, 3, 47, 87, 39, 0, 185, 3, 47, 87, 40, 0, 191, 3, 47, 87, 58, 35, 0, 189, 3, 47, 87, 106, 0, 157, 1, 21, 2, 32, 3, 66, 0, 152, 3, 66, 13, 0, 155, 3, 66, 35, 0, 156, 3, 66, 36, 0, 154, 3, 66, 37, 0, 158, 3, 66, 39, 0, 153, 3, 66, 40, 0, 157, 3, 66, 106, 0, 133, 1, 21, 2, 32, 3, 73, 0, 128, 3, 73, 13, 0, 131, 3, 73, 35, 0, 132, 3, 73, 36, 0, 130, 3, 73, 37, 0, 134, 3, 73, 39, 0, 129, 3, 73, 40, 0, 135, 3, 73, 58, 35, 0, 133, 3, 73, 106, 0, 141, 1, 21, 2, 32, 3, 79, 0, 136, 3, 79, 13, 0, 139, 3, 79, 35, 0, 140, 3, 79, 36, 0, 138, 3, 79, 37, 0, 142, 3, 79, 39, 0, 137, 3, 79, 40, 0, 149, 1, 21, 2, 32, 3, 79, 58, 0, 144, 3, 79, 58, 13, 0, 147, 3, 79, 58, 35, 0, 148, 3, 79, 58, 36, 0, 146, 3, 79, 58, 37, 0, 149, 3, 79, 58, 106, 0, 141, 3, 79, 106, 0, 181, 1, 21, 2, 32, 3, 107, 0, 176, 3, 107, 13, 0, 179, 3, 107, 35, 0, 180, 3, 107, 36, 0, 178, 3, 107, 37, 0, 182, 3, 107, 39, 0, 177, 3, 107, 40, 0, 183, 3, 107, 58, 35, 0, 181, 3, 107, 106, 0, 165, 1, 21, 2, 32, 3, 108, 0, 160, 3, 108, 13, 0, 163, 3, 108, 35, 0, 164, 3, 108, 36, 0, 162, 3, 108, 37, 0, 166, 3, 108, 39, 0, 161, 3, 108, 40, 0, 167, 3, 108, 58, 35, 0, 165, 3, 108, 106, 0, 173, 1, 21, 2, 32, 3, 109, 0, 168, 3, 109, 13, 0, 171, 3, 109, 35, 0, 172, 3, 109, 36, 0, 170, 3, 109, 37, 0, 174, 3, 109, 39, 0, 169, 3, 109, 40, 0, 175, 3, 109, 58, 35, 0, 173, 3, 109, 106, 0, 7, 6, 225, 141, 0, 152, 3, 34, 57, 13, 0, 133, 1, 21, 2, 32, 3, 47, 87, 0, 128, 3, 47, 87, 13, 0, 131, 3, 47, 87, 35, 0, 132, 3, 47, 87, 36, 0, 130, 3, 47, 87, 37, 0, 134, 3, 47, 87, 39, 0, 129, 3, 47, 87, 40, 0, 133, 3, 47, 87, 106, 0, 149, 1, 21, 2, 32, 3, 48, 0, 144, 3, 48, 13, 0, 147, 3, 48, 35, 0, 148, 3, 48, 36, 0, 146, 3, 48, 37, 0, 150, 3, 48, 39, 0, 145, 3, 48, 40, 0, 151, 3, 48, 58, 35, 0, 149, 3, 48, 106, 0, 153, 3, 63, 57, 13, 0, 141, 1, 21, 2, 32, 3, 81, 0, 136, 3, 81, 13, 0, 139, 3, 81, 35, 0, 140, 3, 81, 36, 0, 138, 3, 81, 37, 0, 142, 3, 81, 39, 0, 137, 3, 81, 40, 0, 154, 3, 81, 57, 13, 0, 143, 3, 81, 58, 35, 0, 141, 3, 81, 106, 0, 7, 6, 0, 36, 3, 70, 39, 55, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts3 = FileInMemory_createWithData (3334, reinterpret_cast (&espeakdata_dicts3_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/am_dict", L"am"); Collection_addItem (me.peek(), espeakdata_dicts3.transfer()); static unsigned char espeakdata_dicts4_data[1813] = { 0, 4, 0, 0, 15, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 8, 69, 36, 0, 0, 0, 0, 0, 6, 65, 12, 73, 36, 0, 0, 0, 0, 0, 6, 65, 16, 70, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 24, 81, 36, 0, 0, 0, 0, 0, 6, 65, 28, 77, 36, 0, 0, 0, 0, 0, 6, 65, 32, 105, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 40, 88, 36, 0, 0, 0, 0, 0, 6, 65, 44, 49, 35, 0, 0, 0, 0, 0, 6, 65, 48, 36, 55, 0, 0, 0, 0, 0, 6, 65, 52, 36, 63, 0, 0, 0, 0, 0, 6, 65, 56, 36, 50, 0, 0, 0, 6, 195, 76, 150, 128, 76, 0, 0, 4, 193, 60, 76, 0, 0, 0, 0, 6, 65, 64, 48, 36, 0, 0, 0, 0, 0, 6, 65, 68, 79, 36, 0, 0, 0, 0, 0, 6, 65, 72, 36, 51, 0, 0, 0, 0, 0, 6, 65, 76, 87, 36, 0, 0, 0, 0, 0, 6, 65, 80, 47, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 88, 82, 36, 0, 0, 0, 0, 0, 12, 65, 92, 70, 40, 69, 107, 55, 82, 6, 107, 0, 0, 0, 0, 0, 6, 65, 96, 99, 36, 0, 0, 0, 0, 0, 6, 65, 100, 57, 36, 0, 0, 0, 0, 0, 6, 65, 104, 86, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 19, 201, 153, 14, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 13, 201, 153, 14, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 4, 16, 20, 10, 82, 37, 51, 79, 4, 110, 55, 23, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 19, 201, 153, 14, 9, 14, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 60, 227, 1, 72, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 51, 88, 39, 47, 6, 40, 86, 0, 0, 10, 3, 95, 48, 67, 57, 6, 110, 86, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 55, 88, 57, 36, 47, 63, 6, 37, 89, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 95, 49, 88, 6, 39, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 50, 88, 37, 57, 37, 51, 63, 6, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 76, 150, 137, 56, 76, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 52, 88, 79, 6, 13, 51, 99, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 53, 88, 125, 55, 55, 6, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 54, 88, 35, 55, 47, 63, 6, 13, 89, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 13, 201, 153, 14, 9, 13, 76, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 88, 87, 125, 97, 87, 6, 125, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 57, 88, 70, 39, 99, 87, 6, 35, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 48, 77, 50, 63, 37, 55, 57, 6, 39, 50, 0, 0, 15, 4, 95, 48, 77, 51, 63, 37, 55, 57, 6, 35, 51, 70, 0, 0, 0, 11, 4, 95, 48, 77, 49, 63, 6, 37, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 8, 150, 137, 52, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 60, 229, 78, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 196, 159, 98, 36, 0, 7, 2, 195, 167, 74, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 197, 159, 89, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 15, 14, 12, 1, 18, 196, 177, 14, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 15, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 2, 95, 51, 6, 110, 74, 0, 0, 9, 2, 95, 50, 37, 78, 6, 37, 0, 0, 9, 2, 95, 49, 69, 6, 37, 51, 0, 0, 11, 2, 95, 48, 87, 13, 81, 6, 13, 51, 0, 0, 11, 2, 95, 55, 57, 36, 70, 70, 6, 37, 0, 0, 10, 2, 95, 54, 35, 55, 47, 6, 13, 0, 0, 9, 2, 95, 53, 69, 6, 36, 89, 0, 0, 10, 2, 95, 52, 70, 6, 123, 51, 70, 0, 0, 0, 0, 12, 2, 95, 57, 70, 39, 79, 79, 6, 40, 86, 0, 0, 12, 2, 95, 56, 87, 125, 97, 78, 6, 37, 86, 0, 0, 0, 0, 0, 0, 6, 195, 8, 150, 128, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 167, 0, 3, 74, 0, 7, 6, 195, 182, 0, 3, 123, 0, 7, 6, 195, 188, 0, 3, 110, 0, 7, 6, 196, 159, 0, 3, 98, 0, 7, 6, 196, 177, 0, 3, 13, 0, 7, 6, 197, 159, 0, 3, 89, 0, 7, 6, 201, 153, 0, 3, 125, 0, 7, 6, 97, 0, 3, 35, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 73, 0, 7, 6, 100, 0, 3, 70, 0, 7, 6, 101, 0, 3, 36, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 3, 77, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 7, 6, 106, 0, 3, 88, 0, 7, 6, 107, 0, 3, 78, 0, 2, 25, 3, 97, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 7, 6, 111, 0, 3, 39, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 79, 0, 7, 6, 114, 0, 1, 17, 65, 2, 17, 65, 3, 16, 0, 3, 51, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 7, 6, 117, 0, 3, 40, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 99, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 195, 164, 3, 125, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts4 = FileInMemory_createWithData (1812, reinterpret_cast (&espeakdata_dicts4_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/az_dict", L"az"); Collection_addItem (me.peek(), espeakdata_dicts4.transfer()); static unsigned char espeakdata_dicts5_data[26955] = { 0, 4, 0, 0, 170, 99, 0, 0, 8, 197, 64, 20, 144, 245, 48, 66, 8, 197, 55, 166, 81, 81, 48, 66, 8, 197, 50, 226, 80, 81, 48, 67, 8, 197, 47, 52, 209, 173, 48, 66, 0, 9, 198, 88, 148, 147, 60, 195, 196, 67, 9, 198, 87, 163, 107, 60, 195, 196, 68, 9, 198, 25, 50, 77, 60, 195, 196, 68, 9, 198, 168, 139, 211, 60, 195, 196, 68, 0, 8, 197, 52, 20, 203, 5, 0, 66, 0, 6, 195, 79, 128, 72, 66, 7, 196, 175, 99, 137, 52, 67, 0, 7, 196, 74, 49, 84, 68, 66, 7, 196, 67, 97, 139, 76, 66, 7, 196, 65, 27, 137, 12, 65, 8, 197, 66, 148, 58, 5, 48, 67, 7, 196, 8, 244, 212, 100, 66, 0, 5, 193, 4, 72, 23, 8, 197, 149, 18, 75, 5, 48, 67, 6, 195, 75, 160, 74, 66, 12, 201, 68, 17, 73, 60, 68, 65, 52, 245, 115, 70, 6, 195, 48, 98, 250, 65, 9, 198, 47, 161, 73, 60, 195, 196, 68, 9, 198, 17, 16, 85, 60, 195, 196, 67, 0, 17, 66, 5, 0, 35, 48, 35, 34, 47, 35, 63, 6, 36, 50, 47, 0, 24, 6, 195, 5, 0, 89, 66, 0, 6, 195, 148, 204, 192, 66, 10, 199, 197, 36, 6, 45, 63, 65, 76, 68, 0, 7, 196, 73, 67, 37, 56, 66, 7, 196, 20, 115, 227, 56, 66, 7, 196, 212, 81, 170, 48, 67, 0, 6, 65, 8, 69, 13, 0, 8, 197, 64, 193, 130, 24, 160, 66, 0, 9, 198, 77, 27, 210, 67, 212, 192, 66, 9, 198, 73, 52, 65, 76, 97, 0, 66, 9, 198, 197, 36, 201, 77, 68, 192, 67, 9, 198, 24, 50, 237, 37, 4, 192, 67, 0, 0, 11, 200, 84, 148, 248, 5, 51, 204, 60, 64, 69, 0, 7, 65, 12, 82, 13, 0, 14, 4, 193, 12, 23, 8, 197, 77, 18, 66, 60, 160, 66, 8, 197, 73, 94, 207, 36, 80, 67, 6, 195, 67, 211, 202, 66, 6, 195, 244, 99, 0, 66, 8, 197, 10, 188, 2, 232, 80, 67, 0, 9, 198, 73, 52, 73, 88, 236, 64, 66, 6, 195, 67, 100, 47, 66, 9, 198, 52, 193, 139, 60, 222, 192, 67, 9, 198, 44, 243, 80, 61, 36, 192, 66, 9, 198, 14, 52, 147, 24, 204, 64, 67, 0, 0, 6, 195, 14, 251, 177, 67, 0, 12, 65, 16, 79, 39, 70, 6, 37, 50, 35, 0, 25, 9, 198, 47, 19, 193, 67, 160, 83, 69, 8, 197, 22, 196, 209, 199, 176, 67, 8, 197, 168, 36, 65, 87, 48, 67, 0, 6, 195, 74, 170, 87, 66, 9, 198, 64, 17, 73, 100, 21, 128, 67, 0, 6, 195, 73, 179, 64, 72, 9, 198, 16, 20, 147, 216, 227, 205, 67, 0, 17, 4, 95, 100, 112, 116, 10, 115, 38, 6, 35, 119, 39, 10, 37, 15, 0, 6, 195, 75, 9, 237, 67, 7, 196, 20, 146, 229, 76, 66, 7, 196, 173, 114, 115, 236, 68, 0, 6, 65, 20, 70, 13, 0, 8, 197, 25, 99, 204, 61, 48, 67, 0, 9, 198, 77, 18, 80, 76, 149, 128, 66, 0, 9, 198, 188, 99, 79, 17, 16, 85, 68, 0, 7, 196, 74, 210, 219, 52, 66, 6, 195, 69, 64, 177, 66, 0, 4, 193, 24, 72, 9, 198, 32, 20, 207, 99, 2, 75, 66, 8, 197, 19, 3, 215, 36, 80, 67, 0, 9, 198, 73, 15, 19, 60, 222, 192, 67, 9, 198, 53, 67, 133, 105, 66, 192, 66, 9, 198, 140, 50, 193, 20, 114, 96, 65, 6, 195, 47, 138, 7, 66, 0, 6, 195, 79, 133, 8, 66, 0, 7, 196, 75, 22, 6, 92, 66, 6, 195, 75, 19, 197, 66, 12, 201, 64, 243, 9, 76, 99, 73, 17, 27, 211, 69, 0, 6, 65, 28, 88, 13, 0, 8, 197, 52, 105, 78, 60, 192, 67, 6, 195, 22, 180, 238, 66, 0, 6, 195, 24, 180, 111, 66, 0, 0, 0, 7, 195, 45, 16, 74, 72, 23, 6, 65, 32, 86, 13, 0, 8, 197, 45, 68, 82, 189, 48, 66, 9, 198, 45, 22, 196, 157, 16, 83, 67, 8, 197, 44, 243, 85, 245, 48, 66, 8, 197, 20, 98, 239, 5, 48, 67, 0, 9, 198, 72, 19, 79, 72, 59, 64, 67, 9, 198, 64, 244, 240, 92, 155, 64, 68, 6, 195, 4, 81, 147, 66, 0, 10, 199, 67, 100, 198, 45, 63, 65, 76, 68, 6, 195, 176, 107, 192, 67, 6, 195, 147, 97, 64, 66, 0, 11, 1, 35, 70, 6, 37, 38, 36, 93, 0, 27, 6, 195, 91, 161, 109, 66, 6, 195, 36, 81, 173, 67, 6, 195, 11, 19, 205, 66, 0, 5, 193, 36, 72, 8, 8, 197, 69, 77, 213, 60, 32, 67, 8, 197, 66, 145, 68, 159, 208, 65, 9, 198, 24, 179, 6, 45, 50, 75, 67, 9, 198, 20, 241, 13, 5, 50, 75, 67, 8, 197, 16, 197, 16, 25, 112, 66, 0, 13, 1, 37, 48, 34, 39, 115, 6, 36, 50, 47, 0, 27, 9, 198, 64, 243, 6, 13, 177, 64, 67, 6, 195, 44, 157, 83, 66, 0, 16, 67, 73, 52, 64, 87, 47, 34, 6, 35, 50, 37, 115, 35, 0, 24, 6, 1, 38, 21, 0, 10, 6, 195, 60, 140, 192, 66, 6, 195, 46, 252, 192, 66, 6, 195, 18, 220, 192, 66, 0, 6, 195, 129, 102, 209, 66, 7, 196, 197, 62, 228, 76, 67, 0, 6, 65, 40, 37, 0, 72, 8, 197, 160, 61, 140, 60, 64, 67, 6, 195, 4, 90, 82, 66, 0, 6, 195, 77, 18, 115, 66, 9, 198, 66, 148, 198, 45, 36, 192, 66, 6, 195, 44, 22, 115, 66, 0, 15, 1, 42, 86, 82, 36, 86, 70, 6, 37, 74, 49, 35, 0, 27, 0, 8, 196, 67, 208, 69, 36, 72, 23, 9, 1, 43, 48, 55, 40, 87, 0, 27, 9, 198, 84, 244, 221, 60, 163, 0, 66, 6, 195, 77, 18, 125, 66, 9, 198, 65, 62, 207, 22, 180, 238, 68, 0, 6, 65, 44, 49, 13, 0, 8, 197, 88, 207, 79, 86, 224, 67, 8, 197, 73, 60, 56, 37, 32, 67, 8, 197, 16, 194, 87, 239, 16, 67, 8, 197, 16, 16, 186, 23, 16, 67, 0, 4, 129, 45, 8, 9, 198, 52, 22, 113, 224, 148, 128, 68, 9, 198, 44, 20, 11, 60, 222, 192, 67, 9, 198, 189, 50, 68, 236, 242, 128, 68, 0, 6, 195, 221, 3, 204, 66, 6, 195, 157, 16, 68, 66, 0, 8, 196, 35, 160, 69, 36, 72, 23, 21, 1, 47, 50, 35, 49, 119, 6, 39, 50, 36, 50, 35, 15, 74, 36, 34, 47, 4, 35, 0, 7, 196, 165, 15, 83, 236, 67, 7, 196, 68, 17, 73, 188, 67, 6, 195, 60, 34, 61, 66, 7, 196, 54, 226, 115, 236, 68, 7, 196, 52, 100, 198, 244, 67, 6, 195, 5, 82, 89, 66, 0, 6, 65, 48, 55, 13, 0, 8, 197, 69, 178, 248, 37, 32, 67, 6, 195, 31, 2, 86, 66, 8, 197, 188, 177, 147, 119, 208, 67, 0, 9, 198, 24, 193, 139, 79, 97, 64, 67, 6, 195, 18, 219, 211, 66, 9, 198, 8, 241, 15, 72, 201, 192, 67, 0, 10, 199, 66, 209, 179, 76, 243, 15, 16, 69, 10, 199, 52, 100, 198, 244, 243, 15, 16, 69, 9, 198, 24, 66, 80, 78, 3, 177, 66, 0, 0, 6, 65, 52, 63, 13, 0, 8, 197, 11, 161, 140, 25, 80, 67, 8, 197, 5, 68, 144, 81, 96, 65, 0, 6, 195, 91, 163, 111, 66, 6, 195, 64, 241, 147, 66, 0, 9, 198, 91, 99, 143, 17, 16, 85, 67, 9, 198, 76, 148, 15, 17, 16, 85, 67, 9, 198, 65, 91, 87, 17, 16, 85, 66, 9, 198, 66, 209, 143, 17, 16, 85, 68, 9, 198, 48, 148, 207, 17, 16, 85, 67, 9, 198, 47, 164, 207, 17, 16, 85, 67, 9, 198, 25, 51, 143, 17, 16, 85, 67, 0, 7, 196, 83, 97, 193, 40, 67, 7, 196, 55, 0, 71, 236, 67, 0, 6, 65, 56, 50, 13, 0, 8, 197, 72, 19, 79, 80, 176, 67, 8, 197, 52, 18, 14, 36, 176, 66, 8, 197, 8, 241, 15, 54, 224, 67, 0, 6, 195, 176, 243, 123, 67, 6, 195, 46, 244, 243, 66, 0, 0, 6, 195, 244, 146, 0, 66, 0, 8, 197, 85, 180, 147, 108, 176, 66, 9, 198, 64, 197, 19, 177, 16, 83, 67, 8, 197, 32, 96, 200, 24, 176, 66, 9, 198, 232, 148, 147, 177, 16, 83, 68, 0, 16, 1, 61, 36, 15, 34, 6, 35, 82, 50, 39, 15, 50, 4, 35, 0, 9, 198, 68, 18, 13, 37, 38, 204, 65, 0, 0, 7, 196, 97, 65, 20, 56, 66, 9, 198, 73, 54, 203, 51, 130, 82, 67, 7, 196, 72, 98, 233, 76, 66, 6, 195, 75, 160, 85, 66, 7, 196, 67, 102, 9, 76, 65, 7, 196, 44, 245, 70, 196, 67, 7, 196, 236, 100, 201, 44, 67, 9, 198, 24, 81, 140, 12, 18, 146, 65, 6, 195, 23, 186, 153, 66, 0, 11, 1, 64, 49, 55, 6, 39, 63, 69, 35, 0, 6, 65, 64, 48, 13, 0, 6, 195, 76, 153, 78, 66, 9, 198, 60, 47, 79, 76, 243, 123, 69, 8, 197, 10, 242, 209, 81, 48, 66, 0, 10, 198, 64, 243, 70, 28, 85, 0, 72, 23, 6, 195, 92, 153, 83, 66, 6, 195, 54, 193, 147, 66, 6, 195, 28, 157, 83, 66, 0, 9, 198, 64, 243, 9, 17, 16, 85, 67, 10, 199, 189, 50, 80, 240, 100, 201, 44, 69, 0, 6, 195, 91, 161, 141, 66, 9, 198, 74, 48, 224, 56, 245, 110, 68, 7, 196, 145, 89, 76, 196, 67, 7, 196, 36, 131, 211, 224, 67, 0, 6, 65, 68, 34, 13, 0, 8, 197, 84, 243, 11, 51, 208, 66, 8, 197, 73, 69, 76, 119, 208, 66, 9, 198, 64, 98, 210, 36, 209, 147, 67, 0, 13, 202, 73, 179, 211, 25, 129, 146, 76, 60, 9, 44, 67, 6, 195, 66, 227, 211, 66, 0, 6, 195, 222, 132, 192, 66, 0, 7, 196, 88, 22, 73, 100, 66, 7, 196, 20, 105, 74, 48, 66, 0, 7, 65, 72, 87, 13, 0, 14, 4, 193, 72, 23, 6, 195, 79, 137, 78, 66, 8, 197, 47, 160, 77, 24, 192, 67, 0, 9, 198, 172, 49, 133, 80, 180, 192, 67, 0, 0, 6, 195, 75, 0, 83, 66, 7, 196, 67, 176, 193, 32, 66, 7, 196, 60, 35, 15, 16, 66, 6, 195, 12, 20, 173, 66, 0, 6, 65, 76, 47, 13, 0, 8, 197, 91, 179, 70, 51, 16, 67, 8, 197, 80, 94, 142, 36, 176, 65, 8, 197, 79, 192, 148, 103, 48, 67, 8, 197, 68, 19, 65, 34, 240, 67, 8, 197, 47, 19, 213, 184, 208, 67, 8, 197, 44, 21, 24, 80, 176, 65, 0, 9, 198, 67, 100, 201, 212, 64, 72, 68, 6, 195, 53, 72, 211, 66, 9, 198, 55, 50, 83, 247, 17, 0, 66, 9, 198, 22, 113, 133, 192, 146, 192, 66, 0, 6, 195, 73, 49, 128, 72, 0, 7, 196, 66, 147, 15, 52, 66, 7, 196, 44, 241, 212, 88, 66, 0, 5, 193, 80, 72, 23, 8, 197, 12, 100, 246, 19, 48, 67, 0, 9, 198, 73, 62, 198, 61, 34, 248, 68, 0, 9, 198, 128, 165, 198, 67, 109, 69, 68, 9, 198, 77, 22, 194, 227, 109, 69, 68, 0, 7, 196, 95, 21, 250, 196, 65, 6, 195, 85, 77, 145, 66, 11, 200, 73, 58, 80, 76, 243, 73, 95, 16, 68, 7, 196, 73, 51, 201, 44, 66, 7, 196, 212, 83, 205, 236, 67, 7, 196, 9, 67, 29, 204, 66, 0, 6, 65, 84, 81, 13, 0, 9, 198, 74, 84, 201, 73, 50, 75, 67, 9, 198, 47, 53, 198, 72, 156, 251, 69, 9, 198, 24, 180, 147, 238, 67, 147, 67, 0, 9, 198, 75, 162, 207, 84, 17, 0, 67, 9, 198, 64, 20, 209, 39, 165, 128, 67, 0, 10, 199, 84, 244, 253, 25, 15, 83, 236, 69, 9, 198, 84, 244, 207, 17, 16, 85, 67, 9, 198, 79, 179, 79, 17, 16, 85, 67, 9, 198, 20, 99, 79, 17, 16, 85, 67, 0, 9, 198, 77, 18, 66, 82, 67, 0, 67, 0, 6, 65, 88, 99, 13, 0, 6, 195, 34, 99, 202, 66, 0, 9, 198, 80, 194, 88, 56, 146, 192, 65, 9, 198, 76, 111, 70, 76, 146, 192, 68, 9, 198, 65, 16, 83, 192, 146, 192, 65, 0, 10, 199, 20, 99, 21, 199, 162, 84, 52, 67, 0, 7, 196, 80, 128, 134, 44, 66, 11, 200, 77, 18, 66, 4, 74, 78, 36, 176, 66, 11, 200, 73, 60, 3, 25, 36, 206, 36, 176, 65, 7, 196, 220, 53, 143, 32, 66, 7, 196, 44, 244, 204, 204, 66, 6, 195, 34, 99, 197, 66, 0, 30, 1, 92, 39, 69, 34, 6, 35, 47, 50, 35, 15, 50, 35, 49, 119, 6, 39, 50, 36, 50, 35, 15, 74, 36, 34, 47, 4, 35, 0, 6, 65, 92, 115, 13, 0, 8, 197, 76, 240, 143, 18, 240, 67, 8, 197, 216, 208, 143, 36, 80, 67, 12, 201, 68, 17, 73, 61, 49, 150, 56, 146, 192, 69, 12, 201, 65, 34, 86, 224, 20, 207, 48, 241, 0, 69, 8, 197, 64, 145, 147, 25, 48, 67, 8, 197, 64, 20, 139, 168, 192, 66, 8, 197, 140, 142, 142, 36, 176, 65, 8, 197, 140, 78, 206, 36, 176, 65, 8, 197, 44, 19, 66, 81, 16, 66, 8, 197, 19, 98, 14, 36, 176, 66, 8, 197, 8, 18, 179, 25, 48, 67, 8, 197, 4, 87, 229, 57, 48, 67, 0, 9, 198, 77, 27, 210, 67, 212, 252, 67, 9, 198, 44, 20, 207, 48, 146, 192, 67, 6, 195, 15, 1, 151, 66, 0, 12, 1, 94, 49, 39, 55, 6, 37, 69, 49, 35, 0, 0, 6, 195, 78, 146, 61, 66, 0, 14, 4, 95, 49, 77, 49, 97, 37, 55, 6, 35, 70, 35, 0, 6, 65, 96, 74, 13, 0, 8, 197, 76, 96, 134, 103, 192, 67, 8, 197, 69, 70, 67, 25, 48, 66, 6, 195, 55, 62, 150, 66, 8, 197, 44, 22, 109, 61, 48, 67, 6, 195, 8, 31, 0, 66, 0, 10, 198, 36, 131, 70, 28, 85, 0, 72, 23, 20, 4, 95, 49, 77, 50, 36, 70, 6, 37, 50, 15, 63, 37, 55, 37, 6, 39, 50, 0, 9, 198, 91, 99, 137, 45, 223, 64, 67, 9, 198, 72, 16, 143, 77, 223, 64, 67, 9, 198, 47, 19, 198, 45, 27, 192, 68, 9, 198, 17, 27, 197, 60, 219, 192, 67, 0, 21, 4, 95, 49, 77, 51, 36, 70, 6, 37, 50, 15, 63, 37, 55, 37, 6, 35, 34, 70, 0, 10, 199, 48, 109, 82, 24, 185, 78, 76, 68, 0, 7, 196, 91, 181, 42, 52, 67, 7, 196, 84, 146, 9, 44, 66, 7, 196, 76, 97, 6, 48, 66, 7, 196, 74, 81, 73, 204, 67, 7, 196, 64, 240, 143, 40, 66, 7, 196, 197, 37, 12, 196, 67, 0, 6, 65, 100, 89, 13, 0, 12, 201, 47, 53, 251, 76, 208, 74, 73, 63, 64, 66, 8, 197, 13, 178, 19, 244, 64, 66, 8, 197, 9, 67, 5, 60, 64, 66, 0, 6, 195, 18, 99, 211, 66, 0, 0, 7, 196, 61, 49, 39, 244, 65, 7, 196, 244, 145, 49, 180, 68, 0, 7, 65, 104, 89, 47, 13, 0, 8, 197, 21, 16, 68, 80, 224, 66, 8, 197, 212, 83, 204, 24, 160, 67, 8, 197, 189, 63, 15, 54, 240, 68, 0, 9, 198, 44, 48, 69, 68, 20, 192, 66, 9, 198, 20, 100, 15, 32, 148, 192, 66, 0, 7, 195, 73, 180, 128, 72, 23, 6, 195, 60, 35, 112, 66, 0, 7, 196, 30, 144, 134, 92, 66, 7, 196, 12, 19, 80, 240, 66, 0, 13, 65, 108, 6, 36, 34, 79, 4, 39, 55, 35, 63, 0, 8, 197, 92, 99, 15, 86, 240, 67, 8, 197, 88, 241, 65, 148, 160, 67, 8, 197, 76, 99, 6, 87, 48, 67, 8, 197, 176, 24, 14, 36, 176, 66, 8, 197, 57, 66, 204, 27, 16, 67, 8, 197, 36, 220, 14, 36, 176, 65, 0, 9, 198, 73, 62, 47, 156, 97, 64, 68, 9, 198, 72, 99, 112, 56, 146, 192, 65, 9, 198, 48, 145, 38, 56, 146, 192, 65, 0, 10, 199, 58, 115, 194, 60, 64, 101, 100, 69, 0, 7, 196, 91, 1, 70, 44, 66, 9, 198, 220, 217, 13, 9, 67, 0, 67, 7, 196, 44, 96, 129, 64, 66, 0, 8, 197, 84, 195, 211, 39, 176, 67, 9, 198, 73, 64, 146, 77, 16, 83, 66, 9, 198, 73, 52, 91, 12, 226, 75, 66, 8, 197, 44, 19, 123, 79, 48, 67, 0, 0, 0, 7, 196, 73, 180, 165, 12, 66, 7, 196, 75, 11, 15, 72, 67, 0, 13, 65, 116, 6, 36, 34, 63, 4, 35, 119, 13, 49, 0, 8, 197, 160, 35, 210, 212, 80, 67, 8, 197, 34, 188, 231, 24, 80, 68, 0, 6, 195, 67, 101, 111, 66, 6, 195, 36, 211, 211, 66, 0, 6, 1, 118, 21, 0, 10, 10, 199, 47, 49, 79, 55, 18, 84, 52, 67, 0, 11, 200, 64, 243, 20, 68, 18, 16, 4, 80, 68, 7, 196, 20, 243, 107, 196, 67, 7, 196, 17, 240, 198, 96, 66, 0, 6, 1, 120, 21, 0, 10, 8, 197, 68, 148, 206, 36, 176, 66, 9, 198, 44, 59, 211, 37, 49, 147, 67, 0, 9, 198, 88, 100, 211, 68, 146, 192, 66, 9, 198, 76, 146, 195, 192, 146, 192, 65, 9, 198, 45, 180, 69, 30, 210, 96, 65, 0, 6, 195, 79, 143, 64, 66, 10, 199, 161, 4, 102, 24, 83, 137, 44, 66, 6, 195, 140, 146, 192, 66, 9, 198, 5, 3, 211, 24, 242, 0, 68, 0, 9, 198, 47, 52, 209, 4, 32, 82, 67, 7, 196, 196, 149, 201, 180, 68, 0, 8, 197, 88, 18, 133, 80, 176, 66, 12, 201, 73, 182, 20, 13, 36, 195, 192, 146, 192, 66, 9, 198, 24, 193, 139, 79, 99, 123, 68, 0, 7, 195, 44, 20, 207, 72, 23, 9, 198, 88, 148, 56, 62, 83, 64, 68, 9, 198, 72, 177, 144, 76, 146, 192, 66, 9, 198, 52, 100, 207, 20, 146, 192, 67, 0, 6, 195, 79, 15, 64, 66, 9, 198, 52, 17, 5, 188, 242, 0, 67, 0, 9, 198, 79, 99, 6, 40, 37, 18, 67, 0, 8, 197, 79, 99, 80, 25, 48, 66, 8, 197, 56, 148, 209, 5, 48, 66, 6, 195, 53, 77, 206, 66, 0, 9, 198, 24, 193, 139, 79, 99, 128, 67, 0, 0, 6, 195, 224, 149, 13, 65, 7, 196, 44, 21, 101, 56, 66, 6, 195, 22, 200, 197, 66, 0, 8, 197, 85, 16, 72, 119, 208, 66, 0, 9, 198, 77, 16, 77, 64, 204, 64, 66, 9, 198, 68, 147, 76, 128, 236, 64, 65, 6, 195, 6, 83, 111, 67, 0, 6, 195, 66, 241, 140, 66, 6, 195, 188, 156, 192, 67, 0, 7, 196, 245, 62, 6, 20, 67, 7, 196, 52, 155, 58, 20, 67, 7, 196, 55, 162, 212, 96, 66, 7, 196, 20, 98, 233, 76, 66, 0, 8, 197, 80, 210, 82, 108, 192, 65, 8, 197, 67, 100, 236, 60, 192, 67, 8, 197, 66, 52, 147, 216, 224, 66, 8, 197, 161, 77, 135, 4, 160, 68, 8, 197, 44, 20, 9, 148, 192, 67, 8, 197, 23, 177, 130, 24, 160, 67, 0, 6, 195, 98, 113, 139, 66, 9, 198, 95, 18, 195, 4, 164, 128, 66, 9, 198, 60, 81, 139, 60, 204, 192, 68, 6, 195, 24, 193, 139, 66, 0, 0, 8, 196, 61, 50, 219, 52, 72, 23, 7, 196, 72, 148, 232, 28, 66, 7, 196, 12, 89, 198, 92, 66, 7, 196, 9, 179, 53, 96, 66, 0, 16, 67, 9, 67, 0, 69, 40, 55, 36, 82, 4, 35, 34, 47, 0, 24, 8, 197, 72, 20, 209, 5, 0, 66, 8, 197, 45, 28, 79, 51, 16, 67, 6, 195, 47, 131, 202, 66, 8, 197, 37, 36, 15, 51, 16, 67, 8, 197, 20, 144, 68, 206, 208, 68, 8, 197, 16, 18, 15, 51, 16, 67, 8, 197, 11, 1, 149, 37, 32, 67, 8, 197, 4, 77, 142, 60, 208, 67, 0, 6, 195, 95, 18, 75, 66, 9, 198, 89, 67, 111, 60, 145, 64, 68, 6, 195, 164, 220, 211, 66, 9, 198, 55, 195, 196, 48, 97, 64, 67, 9, 198, 19, 49, 79, 48, 158, 192, 68, 6, 195, 168, 188, 211, 66, 0, 10, 199, 76, 100, 142, 60, 68, 91, 20, 67, 6, 195, 66, 240, 124, 67, 6, 195, 61, 153, 128, 66, 9, 198, 52, 146, 246, 72, 190, 0, 67, 0, 7, 195, 72, 193, 133, 72, 23, 7, 196, 61, 48, 198, 72, 66, 7, 196, 46, 251, 73, 128, 66, 7, 196, 212, 95, 79, 20, 67, 0, 5, 193, 144, 72, 23, 8, 197, 85, 18, 72, 119, 208, 66, 8, 197, 79, 209, 129, 23, 208, 68, 8, 197, 64, 243, 9, 55, 176, 67, 8, 197, 52, 17, 1, 35, 16, 67, 8, 197, 10, 209, 65, 91, 16, 67, 0, 6, 195, 233, 54, 203, 66, 0, 6, 195, 25, 51, 192, 65, 10, 199, 52, 20, 140, 61, 32, 198, 76, 67, 0, 0, 8, 197, 93, 181, 83, 24, 112, 66, 8, 197, 48, 109, 195, 108, 80, 67, 8, 197, 17, 180, 77, 24, 112, 66, 0, 0, 8, 197, 77, 18, 88, 51, 0, 66, 6, 195, 236, 32, 80, 66, 0, 6, 195, 73, 176, 189, 66, 7, 196, 67, 189, 228, 48, 67, 6, 195, 52, 97, 109, 66, 7, 196, 45, 25, 129, 40, 66, 0, 0, 10, 66, 17, 16, 79, 34, 35, 47, 0, 24, 9, 198, 88, 17, 71, 185, 178, 192, 67, 6, 195, 55, 213, 11, 66, 6, 195, 34, 241, 111, 66, 6, 195, 5, 96, 83, 66, 0, 6, 195, 25, 59, 128, 66, 0, 7, 196, 18, 144, 134, 92, 66, 7, 196, 8, 243, 9, 20, 66, 0, 8, 197, 76, 96, 83, 70, 208, 67, 8, 197, 68, 18, 11, 61, 144, 66, 0, 0, 6, 195, 92, 155, 192, 66, 0, 5, 194, 159, 0, 66, 7, 196, 145, 156, 6, 92, 65, 7, 196, 52, 104, 206, 28, 66, 0, 5, 193, 160, 72, 11, 8, 197, 88, 145, 81, 189, 48, 66, 8, 197, 66, 49, 9, 5, 48, 67, 8, 197, 44, 244, 204, 25, 48, 66, 6, 195, 188, 29, 206, 67, 9, 198, 4, 128, 148, 96, 226, 75, 65, 0, 20, 4, 95, 50, 77, 50, 70, 82, 6, 35, 15, 63, 37, 55, 37, 6, 39, 50, 35, 0, 9, 198, 40, 241, 79, 87, 211, 64, 67, 6, 195, 20, 97, 151, 66, 0, 21, 4, 95, 50, 77, 51, 70, 82, 6, 35, 15, 63, 37, 55, 37, 6, 35, 34, 70, 35, 0, 10, 199, 88, 99, 79, 16, 195, 194, 196, 68, 0, 7, 195, 8, 98, 0, 72, 23, 7, 196, 61, 49, 70, 48, 66, 0, 11, 200, 45, 67, 133, 81, 17, 71, 38, 0, 65, 8, 197, 44, 19, 66, 80, 128, 66, 0, 9, 198, 36, 212, 6, 22, 244, 128, 67, 0, 0, 7, 196, 96, 99, 9, 44, 66, 7, 196, 80, 211, 137, 44, 66, 9, 198, 67, 212, 213, 24, 163, 0, 66, 7, 196, 46, 50, 221, 244, 66, 0, 4, 193, 168, 72, 9, 198, 73, 14, 205, 5, 113, 147, 67, 8, 197, 44, 243, 51, 38, 208, 68, 8, 197, 44, 20, 9, 148, 224, 67, 8, 197, 20, 149, 83, 204, 64, 66, 8, 197, 169, 113, 139, 70, 208, 67, 8, 197, 12, 99, 9, 46, 240, 67, 8, 197, 7, 179, 200, 60, 192, 68, 0, 0, 6, 195, 66, 236, 192, 66, 0, 6, 195, 67, 96, 237, 66, 7, 196, 49, 177, 198, 92, 66, 7, 196, 20, 155, 79, 16, 67, 7, 196, 18, 49, 15, 48, 66, 7, 196, 10, 182, 73, 100, 66, 0, 8, 197, 91, 166, 12, 108, 176, 66, 8, 197, 73, 51, 205, 5, 96, 66, 8, 197, 68, 18, 11, 51, 48, 66, 0, 9, 198, 48, 98, 147, 194, 244, 192, 65, 9, 198, 46, 208, 66, 181, 178, 192, 68, 0, 9, 198, 53, 66, 9, 46, 113, 133, 68, 10, 199, 40, 241, 103, 60, 95, 79, 20, 69, 0, 11, 200, 84, 244, 207, 52, 20, 251, 38, 208, 70, 7, 196, 64, 102, 75, 240, 66, 7, 196, 11, 209, 70, 40, 66, 0, 8, 197, 54, 226, 122, 23, 176, 68, 8, 197, 44, 148, 58, 37, 32, 67, 6, 195, 192, 150, 58, 66, 8, 197, 20, 243, 113, 39, 48, 68, 0, 6, 194, 20, 16, 72, 11, 6, 195, 55, 211, 115, 66, 0, 10, 199, 72, 98, 72, 52, 243, 15, 16, 68, 6, 195, 64, 244, 248, 66, 10, 199, 45, 18, 77, 196, 243, 15, 16, 68, 10, 199, 24, 66, 80, 76, 243, 15, 16, 68, 0, 7, 196, 140, 47, 49, 76, 67, 7, 196, 44, 20, 201, 204, 67, 0, 6, 195, 149, 15, 0, 66, 9, 198, 148, 180, 137, 20, 147, 211, 68, 9, 198, 73, 1, 139, 82, 51, 147, 67, 9, 198, 189, 50, 87, 36, 179, 51, 68, 0, 0, 6, 195, 64, 244, 252, 66, 6, 195, 52, 105, 76, 66, 0, 9, 198, 98, 113, 139, 61, 128, 82, 68, 7, 196, 216, 131, 194, 236, 67, 6, 195, 60, 33, 141, 66, 7, 196, 53, 68, 139, 180, 66, 7, 196, 54, 100, 84, 20, 66, 0, 8, 197, 76, 98, 210, 78, 224, 66, 6, 195, 52, 105, 78, 66, 8, 197, 52, 21, 167, 36, 176, 67, 8, 197, 37, 36, 251, 36, 176, 67, 0, 0, 10, 199, 73, 50, 80, 192, 82, 111, 76, 68, 6, 195, 60, 47, 64, 66, 0, 7, 196, 92, 155, 201, 20, 67, 7, 196, 91, 164, 20, 56, 66, 7, 196, 88, 18, 27, 68, 66, 7, 196, 73, 241, 198, 76, 66, 7, 196, 73, 176, 198, 76, 66, 9, 198, 46, 233, 193, 77, 128, 82, 68, 7, 196, 44, 20, 219, 68, 66, 7, 196, 7, 188, 230, 76, 68, 0, 8, 197, 96, 150, 56, 24, 160, 67, 8, 197, 90, 210, 85, 5, 48, 67, 8, 197, 84, 244, 248, 140, 224, 67, 8, 197, 65, 68, 73, 148, 224, 67, 8, 197, 9, 67, 4, 81, 16, 66, 0, 6, 195, 64, 244, 243, 66, 6, 195, 60, 33, 147, 66, 9, 198, 54, 180, 137, 53, 67, 64, 65, 0, 7, 195, 13, 22, 200, 72, 23, 0, 7, 196, 73, 68, 251, 192, 67, 7, 196, 44, 62, 165, 48, 66, 7, 196, 212, 83, 227, 32, 67, 6, 195, 4, 117, 17, 66, 0, 8, 197, 84, 244, 149, 5, 48, 66, 8, 197, 66, 149, 70, 45, 48, 66, 8, 197, 24, 180, 144, 237, 48, 66, 8, 197, 9, 241, 71, 25, 48, 66, 0, 6, 195, 52, 243, 35, 66, 6, 195, 50, 113, 151, 66, 9, 198, 17, 16, 85, 60, 219, 192, 67, 6, 195, 170, 49, 147, 67, 0, 6, 195, 60, 35, 200, 66, 0, 11, 200, 52, 109, 203, 60, 208, 177, 5, 48, 69, 7, 196, 47, 164, 20, 32, 66, 0, 8, 197, 68, 18, 11, 60, 192, 66, 6, 195, 60, 35, 202, 66, 0, 6, 195, 105, 74, 87, 66, 6, 195, 70, 106, 23, 66, 9, 198, 53, 66, 9, 46, 244, 192, 67, 9, 198, 17, 16, 77, 61, 92, 192, 67, 9, 198, 5, 92, 73, 76, 100, 192, 68, 9, 198, 153, 63, 73, 76, 100, 192, 68, 0, 10, 199, 52, 18, 146, 79, 211, 27, 44, 67, 6, 195, 46, 147, 204, 66, 0, 7, 196, 74, 81, 239, 76, 66, 9, 198, 67, 100, 201, 213, 65, 122, 68, 11, 200, 64, 243, 9, 76, 244, 197, 24, 192, 68, 7, 196, 67, 177, 65, 88, 66, 7, 196, 44, 242, 6, 48, 66, 0, 8, 197, 96, 20, 17, 4, 128, 66, 8, 197, 55, 30, 237, 60, 64, 68, 8, 197, 44, 243, 22, 60, 128, 66, 8, 197, 16, 20, 147, 216, 192, 66, 0, 10, 66, 13, 96, 82, 105, 39, 47, 0, 24, 9, 198, 17, 180, 76, 60, 35, 204, 67, 0, 7, 195, 32, 17, 64, 72, 23, 10, 199, 72, 49, 147, 60, 67, 6, 20, 67, 6, 195, 67, 100, 236, 65, 10, 199, 22, 209, 139, 60, 67, 6, 20, 68, 0, 7, 196, 65, 18, 83, 176, 65, 7, 196, 67, 178, 79, 20, 67, 7, 196, 47, 98, 198, 76, 66, 0, 8, 197, 67, 4, 137, 207, 176, 68, 8, 197, 44, 62, 147, 239, 48, 67, 8, 197, 32, 99, 70, 55, 176, 67, 6, 195, 15, 4, 238, 66, 0, 9, 198, 79, 131, 196, 68, 21, 64, 67, 9, 198, 65, 16, 79, 76, 101, 192, 67, 9, 198, 56, 146, 235, 12, 101, 192, 65, 9, 198, 53, 180, 83, 12, 101, 192, 66, 9, 198, 48, 97, 79, 88, 241, 64, 67, 9, 198, 25, 2, 68, 68, 21, 64, 67, 9, 198, 153, 51, 196, 68, 21, 64, 67, 0, 6, 195, 86, 226, 72, 66, 9, 198, 47, 52, 209, 5, 60, 61, 68, 0, 7, 196, 87, 3, 205, 192, 67, 7, 196, 81, 16, 68, 188, 67, 7, 196, 74, 84, 212, 76, 66, 7, 196, 11, 161, 84, 44, 66, 7, 196, 180, 37, 13, 196, 67, 0, 8, 197, 55, 18, 71, 81, 0, 67, 8, 197, 180, 32, 83, 217, 32, 67, 0, 9, 198, 68, 18, 16, 48, 241, 64, 66, 0, 6, 195, 24, 82, 64, 65, 10, 199, 72, 96, 251, 60, 146, 19, 176, 68, 0, 7, 195, 13, 42, 69, 72, 23, 6, 195, 96, 21, 25, 66, 7, 196, 216, 131, 122, 196, 67, 11, 200, 64, 243, 20, 66, 244, 137, 207, 176, 70, 6, 195, 22, 224, 85, 66, 7, 196, 16, 244, 231, 188, 67, 0, 8, 197, 72, 20, 252, 36, 176, 67, 8, 197, 52, 244, 248, 24, 80, 67, 6, 195, 9, 73, 78, 66, 0, 6, 194, 144, 80, 72, 23, 9, 198, 72, 197, 7, 8, 22, 64, 66, 0, 9, 198, 47, 61, 209, 92, 149, 13, 66, 10, 199, 13, 178, 16, 38, 83, 137, 44, 66, 10, 199, 15, 179, 184, 60, 91, 201, 44, 67, 0, 9, 198, 85, 27, 203, 52, 29, 206, 67, 9, 198, 68, 17, 73, 61, 128, 82, 68, 7, 196, 161, 33, 146, 236, 67, 7, 196, 55, 161, 58, 196, 67, 7, 196, 12, 100, 233, 92, 66, 0, 8, 197, 89, 27, 240, 36, 176, 65, 8, 197, 64, 243, 112, 36, 176, 67, 8, 197, 64, 241, 66, 36, 48, 65, 9, 198, 48, 98, 139, 226, 52, 147, 67, 0, 9, 198, 64, 97, 65, 16, 241, 0, 67, 6, 195, 45, 44, 51, 66, 0, 9, 198, 68, 18, 11, 68, 22, 0, 65, 10, 199, 45, 22, 245, 36, 131, 9, 12, 67, 0, 7, 196, 67, 162, 198, 76, 66, 0, 8, 197, 54, 49, 112, 25, 112, 67, 8, 197, 46, 49, 112, 25, 112, 65, 8, 197, 44, 20, 139, 25, 48, 66, 0, 9, 198, 221, 0, 69, 28, 152, 0, 65, 6, 195, 64, 17, 51, 66, 0, 6, 195, 55, 219, 64, 66, 0, 7, 196, 79, 211, 79, 32, 66, 7, 196, 67, 17, 42, 56, 66, 7, 196, 52, 20, 246, 72, 66, 7, 196, 47, 99, 73, 20, 66, 0, 8, 197, 86, 254, 137, 61, 48, 68, 8, 197, 164, 133, 12, 149, 48, 67, 8, 197, 66, 145, 77, 25, 48, 66, 8, 197, 35, 162, 38, 5, 48, 67, 12, 201, 24, 193, 139, 79, 99, 115, 77, 223, 64, 69, 8, 197, 20, 144, 77, 189, 48, 67, 8, 197, 8, 242, 139, 61, 48, 66, 0, 5, 194, 10, 144, 72, 9, 198, 24, 193, 139, 79, 97, 240, 68, 9, 198, 189, 61, 144, 60, 195, 196, 68, 0, 9, 198, 97, 66, 212, 56, 85, 17, 67, 10, 199, 73, 177, 17, 4, 113, 111, 196, 66, 6, 195, 73, 76, 68, 66, 6, 195, 11, 172, 192, 66, 0, 7, 196, 167, 83, 3, 236, 67, 7, 196, 64, 242, 9, 12, 65, 11, 200, 24, 180, 139, 81, 18, 9, 189, 48, 68, 11, 200, 153, 51, 211, 70, 244, 144, 245, 48, 68, 0, 8, 197, 77, 18, 66, 80, 224, 66, 8, 197, 65, 18, 72, 70, 176, 65, 0, 9, 198, 84, 244, 207, 74, 84, 192, 67, 9, 198, 80, 226, 67, 236, 208, 68, 68, 9, 198, 65, 64, 187, 76, 100, 192, 67, 9, 198, 52, 146, 246, 9, 68, 128, 67, 0, 0, 7, 196, 84, 18, 147, 204, 66, 6, 195, 150, 50, 0, 66, 7, 196, 48, 97, 9, 204, 67, 11, 200, 47, 52, 209, 4, 17, 77, 242, 208, 69, 7, 196, 44, 248, 196, 192, 67, 7, 196, 20, 240, 137, 12, 65, 7, 196, 4, 34, 1, 92, 66, 0, 8, 197, 21, 73, 16, 164, 224, 67, 8, 197, 20, 53, 2, 60, 160, 66, 0, 9, 198, 129, 100, 203, 49, 64, 128, 66, 9, 198, 77, 18, 87, 12, 100, 192, 66, 13, 202, 76, 99, 6, 84, 244, 207, 5, 14, 129, 76, 71, 6, 195, 23, 90, 87, 66, 9, 198, 19, 211, 215, 12, 100, 192, 67, 6, 195, 9, 70, 115, 66, 9, 198, 233, 0, 69, 28, 146, 192, 67, 0, 10, 199, 84, 244, 207, 5, 14, 129, 76, 69, 6, 195, 20, 106, 136, 66, 0, 6, 195, 86, 226, 109, 67, 7, 196, 81, 96, 71, 244, 67, 7, 196, 73, 51, 198, 28, 66, 7, 196, 66, 249, 76, 204, 67, 7, 196, 44, 243, 6, 28, 66, 7, 196, 32, 20, 245, 68, 66, 0, 8, 197, 66, 115, 6, 46, 240, 67, 0, 6, 195, 48, 147, 115, 66, 9, 198, 43, 179, 196, 48, 149, 64, 67, 0, 10, 199, 75, 185, 219, 16, 206, 207, 20, 69, 0, 7, 196, 86, 244, 207, 52, 66, 7, 196, 77, 18, 79, 20, 66, 6, 195, 67, 131, 49, 66, 7, 196, 55, 162, 201, 32, 66, 6, 195, 32, 20, 61, 66, 7, 196, 9, 66, 198, 76, 66, 7, 196, 7, 121, 14, 72, 67, 7, 196, 5, 34, 198, 76, 66, 7, 196, 232, 208, 68, 188, 67, 0, 12, 201, 47, 17, 141, 5, 51, 196, 68, 21, 64, 69, 0, 6, 195, 145, 1, 131, 66, 6, 195, 197, 91, 211, 66, 0, 0, 7, 196, 67, 97, 41, 72, 66, 7, 196, 64, 97, 111, 76, 66, 7, 196, 54, 241, 122, 196, 67, 0, 8, 197, 74, 170, 3, 108, 80, 67, 9, 198, 66, 148, 147, 69, 64, 239, 67, 8, 197, 65, 25, 142, 80, 176, 66, 8, 197, 17, 16, 69, 24, 112, 66, 8, 197, 8, 19, 66, 80, 176, 66, 0, 9, 198, 88, 145, 118, 48, 241, 0, 67, 9, 198, 85, 68, 100, 20, 114, 96, 65, 9, 198, 15, 14, 207, 48, 241, 0, 68, 0, 6, 195, 61, 33, 140, 66, 0, 6, 195, 47, 132, 253, 66, 0, 9, 198, 87, 163, 65, 92, 96, 211, 67, 8, 197, 74, 51, 112, 36, 176, 65, 0, 11, 66, 25, 48, 36, 47, 6, 35, 89, 0, 24, 6, 195, 67, 100, 243, 66, 6, 195, 11, 48, 179, 66, 0, 10, 199, 72, 98, 233, 149, 18, 65, 76, 69, 10, 199, 67, 99, 6, 149, 18, 65, 76, 69, 9, 198, 4, 223, 83, 37, 39, 125, 68, 0, 7, 196, 91, 197, 17, 16, 66, 9, 198, 8, 144, 140, 36, 245, 110, 68, 0, 8, 197, 17, 16, 69, 25, 112, 66, 0, 9, 198, 65, 34, 86, 60, 195, 196, 67, 9, 198, 52, 146, 246, 86, 227, 64, 67, 9, 198, 20, 98, 59, 77, 223, 64, 67, 0, 6, 195, 81, 15, 64, 66, 10, 199, 46, 209, 138, 20, 244, 139, 224, 68, 10, 199, 21, 16, 77, 5, 53, 17, 16, 67, 0, 11, 200, 73, 1, 151, 38, 210, 72, 189, 48, 69, 7, 196, 69, 179, 70, 28, 66, 6, 195, 55, 213, 113, 66, 0, 8, 197, 64, 197, 3, 25, 112, 66, 8, 197, 47, 160, 179, 5, 48, 67, 8, 197, 24, 180, 144, 245, 48, 66, 8, 197, 20, 148, 139, 189, 48, 66, 8, 197, 23, 178, 67, 5, 48, 67, 0, 9, 198, 76, 101, 142, 60, 195, 196, 67, 6, 195, 64, 148, 59, 66, 6, 195, 31, 161, 51, 66, 0, 10, 66, 8, 192, 69, 55, 39, 49, 0, 24, 6, 195, 145, 11, 77, 66, 6, 195, 10, 182, 209, 66, 0, 0, 0, 8, 197, 73, 180, 17, 80, 64, 66, 8, 197, 45, 68, 73, 60, 128, 67, 0, 9, 198, 72, 19, 108, 205, 61, 140, 68, 9, 198, 20, 101, 201, 8, 99, 0, 67, 9, 198, 18, 52, 144, 5, 15, 0, 67, 0, 6, 195, 96, 25, 76, 66, 9, 198, 44, 243, 80, 48, 98, 211, 66, 6, 195, 232, 76, 192, 66, 0, 7, 196, 77, 18, 83, 204, 66, 7, 196, 61, 82, 87, 236, 67, 9, 198, 44, 243, 80, 48, 98, 210, 66, 7, 196, 196, 82, 106, 20, 67, 7, 196, 180, 44, 79, 72, 67, 0, 8, 197, 93, 180, 67, 80, 192, 66, 0, 9, 198, 88, 19, 70, 48, 108, 192, 68, 6, 195, 164, 114, 77, 66, 9, 198, 56, 150, 65, 21, 180, 64, 67, 9, 198, 47, 52, 209, 5, 36, 192, 66, 9, 198, 20, 144, 80, 4, 140, 192, 68, 9, 198, 9, 180, 72, 224, 148, 128, 67, 0, 6, 195, 72, 209, 128, 72, 6, 195, 75, 186, 136, 66, 10, 199, 68, 18, 14, 60, 67, 6, 20, 67, 0, 7, 196, 150, 52, 155, 52, 67, 6, 195, 60, 40, 203, 65, 7, 196, 47, 162, 70, 72, 65, 7, 196, 25, 11, 143, 16, 67, 7, 196, 13, 180, 54, 72, 66, 6, 195, 11, 176, 187, 66, 0, 8, 197, 84, 18, 15, 55, 176, 67, 8, 197, 52, 97, 109, 119, 48, 67, 8, 197, 16, 18, 15, 55, 176, 67, 8, 197, 4, 208, 83, 119, 208, 67, 0, 8, 197, 204, 32, 89, 38, 0, 65, 0, 6, 195, 16, 19, 112, 66, 0, 7, 196, 91, 211, 210, 188, 67, 7, 196, 76, 99, 6, 92, 66, 7, 196, 47, 169, 3, 180, 67, 6, 195, 20, 98, 239, 66, 7, 196, 11, 160, 66, 188, 67, 0, 6, 195, 52, 100, 238, 66, 8, 197, 52, 21, 129, 19, 48, 67, 0, 6, 194, 32, 16, 72, 23, 9, 198, 8, 241, 73, 19, 161, 64, 67, 0, 7, 195, 65, 18, 64, 72, 23, 9, 198, 84, 206, 9, 20, 148, 139, 67, 10, 199, 79, 98, 139, 4, 81, 201, 128, 65, 10, 199, 23, 179, 65, 76, 243, 15, 16, 68, 10, 199, 22, 217, 187, 4, 81, 201, 128, 67, 10, 199, 9, 65, 75, 4, 81, 201, 128, 65, 0, 7, 196, 73, 67, 81, 172, 65, 7, 196, 37, 146, 65, 72, 67, 7, 196, 32, 16, 143, 40, 66, 7, 196, 20, 96, 137, 76, 65, 11, 200, 19, 14, 237, 37, 34, 77, 81, 32, 68, 7, 196, 11, 98, 193, 76, 66, 0, 9, 198, 91, 209, 143, 17, 16, 85, 68, 9, 198, 67, 211, 143, 17, 16, 85, 67, 8, 197, 181, 98, 77, 36, 176, 67, 0, 9, 198, 141, 62, 228, 20, 114, 96, 66, 0, 9, 198, 84, 16, 145, 36, 176, 83, 67, 0, 11, 200, 88, 148, 15, 91, 49, 81, 36, 176, 68, 11, 200, 65, 18, 67, 109, 17, 240, 36, 176, 66, 6, 195, 224, 144, 83, 67, 9, 198, 48, 100, 142, 37, 129, 138, 67, 7, 196, 47, 179, 210, 196, 67, 7, 196, 21, 66, 193, 76, 66, 0, 8, 197, 9, 67, 83, 24, 112, 66, 0, 12, 201, 64, 243, 20, 84, 16, 145, 36, 176, 83, 69, 9, 198, 52, 227, 199, 37, 49, 140, 65, 9, 198, 12, 100, 147, 156, 242, 128, 67, 0, 7, 195, 45, 179, 64, 72, 23, 6, 195, 61, 43, 128, 66, 9, 198, 47, 53, 240, 77, 16, 83, 67, 6, 195, 10, 203, 64, 66, 0, 7, 195, 13, 178, 0, 72, 23, 7, 196, 78, 147, 157, 244, 66, 7, 196, 72, 20, 219, 68, 66, 7, 196, 21, 65, 84, 44, 66, 0, 8, 197, 72, 49, 147, 25, 112, 66, 8, 197, 64, 245, 131, 5, 48, 66, 9, 198, 64, 20, 17, 36, 176, 89, 65, 8, 197, 54, 240, 82, 79, 192, 67, 8, 197, 20, 155, 70, 45, 48, 67, 6, 195, 20, 98, 250, 65, 8, 197, 4, 130, 77, 81, 48, 65, 0, 6, 195, 20, 98, 253, 66, 0, 0, 6, 195, 196, 124, 59, 67, 7, 196, 4, 40, 212, 76, 65, 0, 8, 197, 44, 243, 80, 61, 48, 66, 8, 197, 21, 177, 197, 25, 112, 66, 0, 6, 195, 47, 17, 237, 66, 0, 9, 198, 67, 98, 212, 23, 2, 75, 66, 10, 199, 48, 98, 231, 60, 83, 227, 32, 69, 9, 198, 17, 16, 77, 5, 50, 75, 67, 10, 199, 9, 66, 205, 24, 162, 219, 68, 65, 0, 0, 8, 197, 145, 18, 207, 54, 240, 67, 6, 195, 140, 177, 138, 66, 0, 5, 194, 144, 160, 65, 9, 198, 79, 179, 79, 74, 84, 192, 67, 9, 198, 47, 52, 198, 45, 36, 192, 66, 6, 195, 26, 84, 0, 66, 9, 198, 212, 95, 65, 32, 81, 140, 68, 0, 6, 195, 70, 108, 64, 66, 6, 195, 244, 99, 204, 67, 6, 195, 25, 95, 0, 66, 10, 199, 12, 99, 15, 72, 148, 6, 20, 68, 0, 6, 195, 72, 98, 51, 66, 7, 196, 52, 97, 5, 188, 66, 0, 8, 197, 64, 100, 205, 24, 128, 66, 8, 197, 64, 20, 147, 246, 208, 67, 8, 197, 55, 51, 204, 60, 64, 67, 6, 195, 43, 190, 150, 66, 8, 197, 32, 243, 204, 60, 64, 67, 9, 198, 13, 179, 14, 60, 195, 205, 67, 0, 9, 198, 73, 62, 198, 61, 50, 80, 68, 6, 195, 47, 163, 113, 66, 0, 9, 198, 8, 144, 140, 36, 243, 111, 68, 0, 7, 196, 91, 181, 207, 16, 66, 7, 196, 60, 211, 6, 76, 66, 7, 196, 52, 243, 6, 92, 66, 6, 195, 47, 162, 123, 67, 7, 196, 46, 213, 212, 56, 66, 7, 196, 34, 107, 73, 128, 65, 0, 8, 197, 79, 179, 79, 87, 208, 67, 8, 197, 148, 163, 184, 37, 32, 67, 8, 197, 65, 25, 184, 37, 32, 67, 8, 197, 53, 68, 134, 51, 16, 67, 0, 6, 195, 91, 179, 241, 67, 9, 198, 141, 28, 68, 61, 34, 248, 68, 9, 198, 18, 208, 239, 61, 34, 248, 68, 0, 9, 198, 20, 155, 70, 45, 50, 75, 68, 0, 7, 196, 84, 100, 201, 100, 66, 7, 196, 76, 251, 70, 76, 67, 7, 196, 25, 100, 198, 28, 66, 7, 196, 9, 16, 77, 196, 66, 7, 196, 4, 81, 144, 76, 66, 0, 8, 197, 52, 97, 1, 87, 48, 67, 8, 197, 45, 179, 139, 119, 208, 66, 0, 9, 198, 9, 67, 6, 15, 161, 64, 67, 0, 10, 199, 164, 184, 205, 4, 81, 201, 128, 66, 6, 195, 66, 254, 192, 66, 6, 195, 46, 148, 240, 66, 0, 9, 198, 92, 146, 204, 61, 36, 238, 67, 7, 196, 87, 211, 65, 76, 66, 7, 196, 81, 166, 209, 8, 66, 7, 196, 75, 20, 198, 32, 66, 7, 196, 52, 18, 4, 180, 66, 6, 195, 46, 148, 243, 66, 6, 195, 47, 160, 83, 66, 0, 12, 3, 226, 132, 150, 50, 6, 39, 63, 36, 34, 0, 0, 0, 9, 198, 20, 96, 134, 48, 243, 123, 68, 0, 9, 198, 221, 114, 79, 48, 241, 0, 68, 7, 196, 64, 153, 68, 244, 67, 7, 196, 61, 50, 207, 72, 66, 7, 196, 44, 99, 6, 100, 66, 7, 196, 232, 243, 65, 76, 67, 7, 196, 4, 83, 124, 180, 67, 0, 8, 197, 80, 226, 75, 80, 208, 65, 8, 197, 72, 222, 129, 16, 80, 66, 8, 197, 68, 18, 4, 216, 208, 66, 8, 197, 37, 36, 253, 36, 176, 67, 9, 198, 8, 98, 9, 73, 60, 0, 67, 8, 197, 232, 158, 196, 232, 80, 68, 0, 9, 198, 64, 243, 9, 92, 18, 128, 67, 0, 10, 199, 52, 243, 9, 76, 60, 9, 44, 66, 0, 7, 196, 88, 20, 219, 68, 66, 7, 196, 68, 18, 53, 20, 66, 7, 196, 45, 67, 70, 92, 66, 7, 196, 44, 243, 6, 76, 66, 7, 196, 46, 52, 104, 76, 66, 7, 196, 44, 148, 6, 28, 66, 7, 196, 44, 22, 77, 240, 66, 7, 196, 10, 212, 129, 52, 66, 0, 8, 197, 68, 18, 16, 37, 48, 65, 8, 197, 189, 242, 83, 25, 48, 68, 0, 9, 198, 84, 100, 147, 36, 59, 64, 67, 6, 195, 61, 52, 61, 66, 0, 9, 198, 68, 18, 146, 108, 49, 147, 67, 9, 198, 67, 98, 193, 31, 2, 75, 66, 9, 198, 24, 193, 139, 77, 18, 75, 67, 0, 7, 196, 99, 180, 198, 28, 66, 7, 196, 84, 197, 9, 20, 66, 9, 198, 67, 100, 201, 212, 49, 146, 68, 7, 196, 196, 59, 73, 20, 67, 0, 8, 197, 65, 18, 67, 25, 48, 66, 8, 197, 20, 101, 70, 45, 48, 66, 8, 197, 4, 74, 68, 5, 48, 67, 0, 6, 195, 90, 210, 85, 66, 6, 195, 173, 55, 125, 66, 0, 0, 7, 196, 197, 94, 139, 76, 66, 0, 6, 131, 226, 128, 166, 8, 8, 197, 53, 68, 165, 56, 64, 66, 0, 9, 198, 75, 17, 73, 44, 20, 192, 67, 9, 198, 46, 241, 73, 20, 20, 192, 67, 9, 198, 197, 49, 140, 24, 180, 192, 67, 0, 8, 197, 86, 235, 211, 217, 0, 67, 10, 199, 73, 59, 15, 60, 47, 79, 76, 69, 6, 195, 224, 148, 192, 65, 6, 195, 15, 161, 140, 66, 0, 7, 196, 88, 18, 131, 188, 66, 7, 196, 68, 18, 53, 40, 66, 7, 196, 60, 36, 134, 16, 66, 7, 196, 47, 160, 179, 184, 67, 7, 196, 4, 44, 193, 76, 67, 0, 12, 201, 221, 114, 109, 20, 99, 108, 68, 20, 192, 70, 12, 201, 47, 52, 209, 5, 10, 67, 68, 20, 192, 68, 8, 197, 12, 100, 246, 14, 208, 67, 0, 9, 198, 79, 176, 80, 24, 52, 192, 67, 9, 198, 67, 100, 144, 24, 180, 192, 66, 9, 198, 20, 97, 48, 236, 20, 192, 68, 0, 10, 199, 68, 18, 11, 6, 3, 137, 44, 66, 10, 199, 52, 17, 9, 73, 52, 65, 76, 67, 6, 195, 8, 98, 60, 66, 0, 6, 195, 26, 83, 51, 67, 7, 196, 25, 2, 68, 204, 67, 0, 8, 197, 72, 99, 32, 59, 16, 65, 8, 197, 47, 19, 210, 183, 48, 68, 0, 5, 194, 163, 48, 66, 0, 7, 195, 66, 145, 64, 72, 23, 9, 198, 220, 36, 147, 15, 2, 75, 65, 10, 199, 45, 190, 73, 44, 241, 212, 88, 68, 0, 11, 200, 77, 244, 76, 124, 71, 195, 25, 128, 68, 7, 196, 75, 17, 71, 240, 66, 7, 196, 177, 62, 15, 20, 67, 0, 8, 197, 75, 186, 147, 119, 208, 67, 8, 197, 48, 100, 248, 37, 32, 67, 0, 6, 195, 54, 241, 45, 66, 0, 7, 195, 61, 32, 240, 72, 23, 0, 8, 196, 72, 52, 91, 88, 72, 23, 7, 196, 68, 148, 212, 180, 67, 6, 195, 64, 150, 167, 66, 9, 198, 52, 146, 207, 48, 241, 0, 67, 6, 195, 54, 241, 47, 66, 0, 0, 12, 201, 65, 180, 198, 100, 100, 147, 15, 2, 75, 67, 9, 198, 65, 16, 70, 32, 146, 192, 67, 9, 198, 53, 22, 210, 56, 146, 192, 66, 9, 198, 47, 164, 194, 140, 230, 64, 66, 6, 195, 19, 188, 0, 66, 9, 198, 212, 193, 138, 8, 243, 0, 65, 0, 0, 6, 195, 60, 197, 11, 66, 9, 198, 52, 148, 207, 48, 241, 0, 67, 6, 195, 47, 161, 111, 66, 7, 196, 32, 20, 1, 72, 66, 6, 195, 9, 68, 243, 66, 7, 196, 8, 99, 15, 76, 66, 0, 9, 198, 88, 145, 118, 17, 16, 85, 67, 12, 201, 77, 180, 15, 108, 70, 204, 56, 146, 192, 67, 9, 198, 76, 99, 6, 17, 16, 85, 67, 6, 195, 164, 249, 78, 67, 12, 201, 65, 25, 143, 108, 70, 204, 56, 146, 192, 67, 12, 201, 24, 113, 141, 25, 33, 152, 56, 146, 192, 67, 8, 197, 188, 67, 15, 86, 224, 67, 0, 9, 198, 86, 197, 18, 56, 146, 192, 65, 9, 198, 77, 21, 7, 192, 146, 192, 65, 9, 198, 73, 181, 24, 192, 146, 192, 68, 9, 198, 64, 243, 9, 76, 146, 192, 67, 9, 198, 52, 17, 1, 35, 30, 192, 68, 9, 198, 44, 243, 119, 52, 243, 0, 67, 0, 7, 195, 88, 99, 64, 72, 23, 0, 11, 200, 77, 18, 91, 17, 179, 14, 36, 176, 66, 7, 196, 72, 187, 197, 180, 66, 7, 196, 64, 242, 29, 244, 66, 7, 196, 52, 18, 20, 76, 66, 7, 196, 7, 210, 82, 76, 66, 0, 8, 197, 72, 18, 131, 189, 48, 66, 12, 201, 64, 100, 207, 108, 70, 204, 56, 146, 192, 67, 8, 197, 144, 154, 147, 25, 48, 68, 8, 197, 44, 148, 27, 165, 112, 65, 8, 197, 47, 17, 146, 47, 128, 67, 8, 197, 44, 99, 6, 67, 192, 67, 0, 9, 198, 52, 97, 45, 60, 219, 192, 68, 9, 198, 8, 22, 137, 96, 179, 192, 65, 0, 0, 7, 196, 52, 25, 69, 244, 67, 7, 196, 47, 212, 198, 28, 66, 7, 196, 28, 104, 211, 196, 67, 7, 196, 23, 49, 212, 188, 67, 0, 8, 197, 74, 83, 133, 233, 48, 66, 8, 197, 66, 51, 153, 25, 48, 66, 8, 197, 64, 20, 147, 25, 48, 66, 8, 197, 31, 195, 210, 47, 128, 67, 8, 197, 7, 179, 210, 149, 48, 68, 0, 9, 198, 66, 241, 73, 101, 11, 192, 67, 0, 6, 195, 128, 137, 252, 67, 9, 198, 74, 144, 155, 68, 226, 75, 65, 9, 198, 72, 99, 18, 108, 49, 147, 67, 9, 198, 64, 19, 70, 76, 226, 75, 65, 0, 11, 200, 73, 51, 205, 5, 51, 210, 47, 128, 68, 7, 196, 67, 96, 227, 44, 65, 11, 200, 52, 17, 14, 37, 51, 210, 47, 128, 68, 0, 8, 197, 216, 188, 5, 216, 192, 67, 9, 198, 44, 243, 66, 4, 170, 17, 67, 8, 197, 44, 22, 75, 154, 208, 67, 8, 197, 46, 211, 194, 70, 240, 67, 8, 197, 233, 98, 123, 24, 160, 68, 8, 197, 5, 3, 196, 24, 160, 67, 0, 9, 198, 20, 146, 211, 61, 92, 192, 67, 9, 198, 20, 99, 6, 16, 20, 192, 67, 0, 10, 199, 73, 178, 195, 233, 63, 47, 76, 68, 9, 198, 45, 223, 85, 37, 145, 139, 65, 10, 199, 20, 100, 134, 76, 240, 143, 40, 68, 0, 7, 196, 72, 197, 4, 4, 66, 7, 196, 164, 244, 165, 76, 67, 11, 200, 68, 17, 73, 61, 34, 68, 144, 192, 69, 7, 196, 67, 165, 198, 48, 66, 7, 196, 47, 164, 198, 48, 66, 7, 196, 36, 212, 1, 72, 66, 7, 196, 8, 16, 148, 196, 67, 0, 8, 197, 44, 21, 2, 60, 160, 67, 8, 197, 44, 20, 147, 216, 224, 66, 9, 198, 36, 132, 27, 48, 179, 205, 67, 12, 201, 9, 241, 71, 25, 62, 54, 24, 180, 192, 69, 8, 197, 8, 98, 2, 216, 160, 66, 0, 9, 198, 76, 99, 6, 64, 20, 192, 67, 9, 198, 44, 244, 141, 206, 100, 192, 67, 9, 198, 24, 180, 144, 204, 20, 192, 67, 9, 198, 9, 27, 160, 57, 60, 64, 67, 0, 10, 199, 160, 52, 65, 73, 60, 9, 44, 68, 0, 7, 196, 79, 101, 70, 40, 66, 7, 196, 73, 61, 134, 28, 66, 0, 9, 198, 84, 99, 5, 55, 166, 109, 65, 9, 198, 73, 180, 134, 50, 3, 177, 66, 8, 197, 73, 68, 240, 119, 208, 67, 8, 197, 72, 191, 80, 39, 48, 67, 8, 197, 64, 20, 129, 31, 176, 67, 8, 197, 145, 3, 204, 27, 48, 68, 9, 198, 52, 21, 186, 4, 81, 193, 68, 8, 197, 44, 20, 9, 103, 48, 67, 12, 201, 24, 193, 139, 79, 97, 79, 8, 144, 192, 68, 8, 197, 20, 96, 137, 79, 208, 65, 0, 7, 195, 176, 17, 193, 72, 23, 0, 9, 198, 74, 84, 207, 72, 190, 0, 67, 9, 198, 64, 243, 9, 76, 146, 239, 68, 0, 6, 195, 54, 242, 123, 67, 6, 195, 18, 222, 0, 66, 7, 196, 232, 76, 230, 76, 67, 0, 8, 197, 88, 97, 6, 55, 48, 67, 8, 197, 86, 249, 72, 119, 208, 67, 8, 197, 31, 49, 12, 119, 208, 66, 8, 197, 19, 163, 137, 35, 48, 67, 0, 9, 198, 74, 49, 79, 48, 97, 64, 67, 6, 195, 54, 240, 85, 66, 0, 6, 195, 220, 179, 204, 66, 6, 195, 61, 36, 240, 66, 9, 198, 244, 177, 146, 77, 27, 211, 67, 9, 198, 212, 89, 219, 69, 49, 135, 68, 0, 8, 196, 67, 100, 201, 12, 72, 23, 7, 196, 44, 18, 6, 196, 67, 7, 196, 15, 180, 198, 64, 66, 7, 196, 4, 43, 207, 72, 67, 0, 9, 197, 144, 209, 146, 76, 240, 72, 23, 8, 197, 68, 18, 17, 36, 48, 65, 8, 197, 64, 241, 86, 60, 80, 66, 8, 197, 49, 73, 19, 36, 176, 67, 8, 197, 13, 180, 67, 24, 112, 66, 8, 197, 8, 149, 83, 24, 176, 66, 0, 7, 195, 66, 145, 73, 72, 23, 9, 198, 108, 70, 204, 56, 146, 192, 65, 9, 198, 85, 26, 215, 39, 62, 192, 68, 9, 198, 72, 209, 153, 56, 146, 192, 66, 0, 10, 199, 64, 243, 20, 60, 47, 79, 76, 69, 9, 198, 52, 20, 147, 60, 92, 211, 67, 6, 195, 47, 169, 76, 66, 0, 6, 195, 90, 208, 83, 66, 7, 196, 73, 66, 205, 188, 66, 7, 196, 75, 177, 239, 76, 66, 11, 200, 64, 241, 84, 96, 20, 147, 108, 176, 65, 7, 196, 44, 245, 203, 232, 65, 0, 9, 198, 76, 99, 6, 76, 148, 0, 67, 8, 197, 216, 219, 211, 36, 176, 67, 12, 201, 216, 142, 54, 36, 141, 69, 37, 49, 140, 69, 8, 197, 52, 20, 251, 36, 176, 67, 8, 197, 13, 180, 83, 24, 112, 66, 0, 0, 10, 199, 81, 36, 61, 24, 83, 137, 44, 65, 6, 195, 149, 107, 192, 66, 10, 199, 69, 65, 79, 20, 240, 137, 12, 67, 0, 11, 200, 73, 180, 12, 24, 220, 14, 36, 176, 66, 7, 196, 24, 51, 148, 88, 66, 0, 12, 201, 61, 35, 79, 108, 70, 204, 56, 146, 192, 67, 8, 197, 45, 16, 69, 25, 112, 66, 0, 6, 195, 74, 208, 77, 66, 9, 198, 9, 18, 68, 4, 95, 0, 67, 0, 6, 195, 130, 147, 64, 66, 9, 198, 73, 178, 77, 192, 226, 75, 66, 9, 198, 21, 177, 197, 60, 36, 111, 67, 0, 7, 196, 64, 148, 134, 92, 66, 6, 195, 61, 49, 151, 66, 7, 196, 47, 96, 82, 188, 67, 0, 8, 197, 91, 211, 210, 47, 128, 67, 6, 195, 64, 148, 186, 65, 8, 197, 197, 36, 241, 45, 48, 66, 0, 12, 201, 72, 97, 77, 61, 177, 27, 48, 226, 75, 67, 9, 198, 64, 243, 20, 73, 179, 128, 67, 9, 198, 20, 149, 84, 33, 223, 64, 67, 0, 15, 3, 95, 51, 88, 47, 34, 6, 37, 70, 36, 87, 36, 47, 0, 9, 198, 65, 18, 125, 37, 49, 147, 68, 10, 199, 65, 16, 80, 70, 99, 148, 44, 67, 9, 198, 66, 179, 210, 76, 226, 75, 65, 9, 198, 13, 22, 210, 76, 226, 75, 66, 9, 198, 180, 179, 214, 60, 194, 75, 68, 0, 13, 3, 95, 48, 67, 87, 47, 6, 39, 47, 37, 50, 0, 7, 196, 68, 18, 2, 244, 66, 7, 196, 60, 47, 79, 76, 67, 7, 196, 140, 212, 9, 204, 67, 7, 196, 46, 118, 6, 16, 66, 7, 196, 16, 240, 140, 192, 66, 7, 196, 16, 145, 47, 76, 66, 0, 8, 197, 54, 214, 20, 18, 240, 67, 8, 197, 32, 16, 145, 154, 240, 67, 0, 0, 6, 195, 167, 116, 64, 66, 0, 7, 196, 69, 77, 213, 184, 67, 6, 195, 54, 246, 115, 66, 7, 196, 12, 100, 251, 188, 67, 7, 196, 12, 99, 20, 68, 66, 7, 196, 8, 245, 134, 52, 66, 0, 0, 0, 0, 10, 3, 95, 49, 67, 87, 47, 6, 39, 0, 6, 195, 54, 241, 135, 66, 11, 200, 47, 19, 213, 25, 36, 201, 14, 208, 69, 7, 196, 10, 195, 20, 44, 66, 0, 0, 6, 195, 24, 204, 0, 66, 9, 198, 20, 124, 19, 108, 195, 112, 65, 9, 198, 16, 18, 56, 219, 81, 64, 68, 0, 10, 199, 67, 171, 79, 16, 146, 27, 52, 65, 0, 7, 196, 52, 18, 15, 48, 66, 7, 196, 180, 16, 129, 100, 67, 0, 0, 6, 194, 20, 240, 72, 23, 20, 3, 95, 49, 57, 70, 4, 36, 82, 36, 47, 50, 6, 35, 70, 36, 87, 36, 47, 0, 9, 198, 36, 133, 13, 69, 65, 64, 67, 9, 198, 24, 194, 80, 220, 145, 64, 68, 9, 198, 16, 18, 15, 60, 35, 112, 68, 0, 19, 3, 95, 49, 56, 4, 39, 87, 36, 63, 50, 6, 35, 70, 36, 87, 36, 47, 0, 9, 198, 76, 99, 6, 72, 190, 0, 67, 10, 199, 73, 1, 140, 24, 243, 15, 16, 68, 9, 198, 65, 26, 211, 36, 187, 211, 67, 0, 13, 3, 95, 50, 67, 70, 82, 6, 36, 87, 47, 35, 0, 7, 196, 189, 52, 107, 72, 66, 0, 9, 198, 67, 100, 207, 76, 148, 0, 67, 8, 197, 64, 241, 111, 36, 176, 65, 8, 197, 66, 51, 167, 36, 176, 67, 0, 6, 195, 20, 248, 209, 65, 0, 6, 195, 20, 248, 208, 66, 0, 7, 196, 88, 18, 131, 236, 66, 7, 196, 72, 145, 36, 48, 66, 6, 195, 45, 68, 51, 66, 7, 196, 47, 164, 198, 96, 66, 7, 196, 189, 52, 107, 76, 66, 0, 0, 18, 3, 95, 49, 49, 36, 70, 4, 37, 50, 6, 35, 70, 36, 87, 36, 47, 0, 9, 198, 65, 25, 174, 56, 146, 192, 65, 6, 195, 61, 61, 81, 66, 0, 12, 3, 95, 49, 48, 70, 6, 36, 87, 36, 47, 0, 6, 195, 77, 74, 12, 66, 9, 198, 47, 160, 68, 116, 242, 0, 67, 6, 195, 26, 83, 128, 66, 8, 197, 19, 3, 211, 37, 0, 67, 10, 199, 168, 81, 143, 72, 145, 36, 48, 69, 0, 13, 3, 95, 51, 67, 47, 34, 6, 37, 87, 47, 35, 0, 17, 3, 95, 49, 51, 47, 34, 37, 50, 6, 35, 70, 36, 87, 36, 47, 0, 7, 196, 68, 18, 5, 244, 66, 7, 196, 52, 17, 36, 76, 66, 6, 195, 10, 209, 147, 66, 0, 17, 3, 95, 49, 50, 70, 82, 35, 50, 6, 35, 70, 36, 87, 36, 47, 0, 8, 197, 17, 68, 66, 25, 48, 66, 0, 17, 3, 95, 49, 53, 48, 36, 47, 50, 6, 35, 70, 36, 87, 36, 47, 0, 0, 21, 3, 95, 49, 52, 74, 4, 36, 47, 37, 34, 37, 50, 6, 35, 70, 36, 87, 36, 47, 0, 8, 197, 51, 19, 211, 37, 0, 67, 6, 195, 24, 223, 0, 66, 10, 199, 215, 3, 143, 196, 59, 73, 20, 70, 0, 20, 3, 95, 49, 55, 87, 4, 36, 70, 36, 63, 50, 6, 35, 70, 36, 87, 36, 47, 0, 7, 196, 67, 101, 198, 72, 66, 12, 201, 66, 148, 139, 205, 94, 240, 92, 152, 0, 68, 7, 196, 55, 161, 49, 180, 67, 6, 195, 30, 177, 147, 66, 0, 18, 3, 95, 49, 54, 89, 36, 87, 47, 50, 6, 35, 70, 36, 87, 36, 47, 0, 8, 197, 77, 180, 78, 179, 128, 67, 8, 197, 66, 144, 209, 5, 48, 66, 9, 198, 24, 83, 143, 96, 204, 0, 67, 8, 197, 4, 213, 12, 25, 48, 67, 0, 6, 194, 36, 128, 72, 23, 9, 198, 52, 100, 246, 56, 243, 64, 67, 0, 17, 3, 95, 55, 88, 87, 36, 70, 36, 63, 70, 36, 87, 6, 36, 47, 0, 10, 199, 47, 31, 70, 28, 148, 157, 244, 69, 9, 198, 19, 14, 237, 37, 49, 147, 69, 0, 7, 196, 166, 129, 1, 76, 67, 6, 195, 52, 17, 47, 66, 7, 196, 48, 241, 9, 44, 66, 7, 196, 5, 36, 60, 196, 67, 0, 8, 197, 21, 180, 117, 140, 128, 67, 0, 0, 0, 7, 196, 44, 240, 173, 76, 66, 6, 195, 188, 184, 195, 66, 0, 8, 197, 89, 67, 9, 18, 240, 67, 9, 198, 88, 243, 6, 73, 62, 241, 68, 8, 197, 52, 20, 251, 38, 208, 68, 8, 197, 45, 16, 88, 60, 192, 66, 0, 0, 0, 7, 196, 67, 100, 147, 244, 66, 0, 8, 197, 56, 146, 207, 79, 16, 67, 0, 9, 198, 89, 27, 248, 219, 81, 64, 68, 9, 198, 79, 131, 56, 219, 81, 64, 68, 6, 195, 170, 83, 113, 67, 0, 9, 198, 32, 20, 27, 69, 54, 203, 65, 0, 6, 195, 91, 211, 115, 66, 7, 196, 79, 99, 66, 204, 66, 7, 196, 17, 244, 84, 44, 66, 0, 9, 198, 99, 179, 143, 16, 193, 133, 67, 8, 197, 79, 179, 73, 23, 208, 67, 8, 197, 76, 97, 12, 37, 128, 66, 8, 197, 75, 195, 205, 5, 96, 67, 6, 195, 216, 219, 210, 66, 8, 197, 4, 90, 100, 51, 16, 68, 0, 5, 194, 52, 16, 72, 11, 66, 48, 48, 55, 4, 36, 82, 35, 0, 24, 6, 195, 177, 34, 69, 66, 6, 195, 47, 49, 125, 66, 0, 10, 199, 85, 16, 72, 24, 243, 15, 16, 68, 10, 199, 24, 208, 145, 36, 243, 15, 16, 68, 0, 11, 200, 53, 67, 19, 36, 219, 137, 207, 176, 70, 7, 196, 16, 18, 165, 56, 66, 7, 196, 4, 74, 77, 188, 67, 0, 8, 197, 222, 52, 73, 80, 208, 66, 8, 197, 65, 18, 74, 60, 208, 66, 8, 197, 55, 163, 109, 4, 80, 67, 0, 6, 194, 180, 16, 72, 23, 9, 198, 55, 17, 123, 49, 178, 192, 67, 0, 9, 198, 4, 67, 15, 55, 176, 83, 68, 0, 6, 195, 84, 244, 243, 66, 11, 200, 72, 198, 206, 96, 241, 12, 24, 80, 67, 7, 196, 68, 21, 129, 76, 66, 6, 195, 64, 148, 243, 66, 6, 195, 47, 62, 0, 66, 6, 195, 232, 100, 147, 66, 0, 8, 197, 88, 144, 145, 36, 80, 66, 8, 197, 67, 160, 86, 60, 80, 67, 0, 6, 195, 52, 244, 253, 66, 0, 15, 3, 95, 50, 88, 70, 82, 6, 35, 70, 36, 87, 36, 47, 0, 9, 198, 8, 146, 250, 11, 48, 83, 68, 0, 7, 196, 88, 207, 73, 20, 66, 7, 196, 88, 18, 58, 76, 66, 6, 195, 84, 18, 47, 66, 7, 196, 74, 217, 100, 76, 67, 6, 195, 164, 129, 151, 66, 7, 196, 60, 220, 201, 52, 67, 7, 196, 47, 210, 69, 244, 67, 7, 196, 32, 54, 232, 92, 66, 7, 196, 15, 179, 84, 76, 66, 0, 8, 197, 91, 195, 205, 189, 48, 67, 8, 197, 77, 180, 68, 5, 144, 66, 8, 197, 52, 98, 51, 25, 48, 67, 8, 197, 52, 19, 122, 25, 112, 67, 8, 197, 44, 195, 200, 25, 48, 66, 0, 9, 198, 44, 243, 66, 4, 163, 128, 66, 0, 6, 195, 216, 219, 192, 66, 9, 198, 167, 83, 31, 92, 156, 251, 70, 6, 195, 232, 107, 64, 67, 9, 198, 5, 3, 204, 60, 65, 147, 68, 0, 7, 196, 96, 144, 148, 44, 66, 7, 196, 67, 21, 198, 76, 66, 7, 196, 25, 36, 198, 76, 66, 7, 196, 9, 245, 70, 76, 66, 0, 9, 198, 72, 99, 32, 56, 85, 17, 67, 8, 197, 52, 20, 145, 5, 80, 66, 8, 197, 25, 50, 75, 25, 48, 67, 8, 197, 8, 97, 239, 25, 112, 67, 8, 197, 8, 97, 12, 25, 112, 66, 8, 197, 153, 62, 46, 61, 48, 68, 0, 9, 198, 44, 243, 44, 169, 67, 64, 66, 9, 198, 7, 179, 197, 69, 67, 64, 68, 0, 6, 195, 45, 67, 124, 66, 6, 195, 191, 52, 128, 66, 0, 11, 200, 88, 147, 75, 60, 208, 177, 5, 48, 68, 7, 196, 84, 244, 132, 192, 66, 7, 196, 76, 101, 83, 236, 66, 11, 200, 73, 68, 59, 84, 244, 149, 5, 48, 68, 7, 196, 220, 195, 137, 44, 66, 7, 196, 68, 18, 13, 236, 66, 7, 196, 64, 100, 246, 48, 66, 7, 196, 55, 163, 197, 236, 67, 0, 8, 197, 64, 22, 75, 80, 192, 66, 8, 197, 64, 20, 1, 18, 208, 67, 0, 9, 198, 84, 98, 140, 25, 60, 192, 67, 9, 198, 72, 147, 84, 140, 228, 192, 67, 5, 194, 158, 208, 66, 9, 198, 53, 68, 65, 84, 100, 192, 67, 9, 198, 20, 144, 251, 74, 244, 192, 67, 9, 198, 168, 45, 130, 25, 60, 192, 68, 0, 10, 199, 52, 104, 206, 88, 243, 9, 44, 68, 10, 199, 47, 49, 12, 60, 222, 193, 76, 68, 0, 7, 196, 64, 102, 1, 76, 66, 7, 196, 52, 20, 148, 68, 66, 7, 196, 47, 52, 212, 68, 66, 0, 8, 197, 73, 15, 126, 55, 0, 66, 8, 197, 68, 17, 73, 46, 208, 67, 8, 197, 64, 145, 13, 24, 160, 66, 8, 197, 64, 20, 147, 24, 192, 66, 8, 197, 44, 20, 17, 36, 128, 66, 0, 0, 18, 3, 95, 52, 88, 74, 36, 47, 37, 34, 6, 37, 70, 36, 87, 36, 47, 0, 10, 199, 44, 243, 73, 75, 162, 65, 76, 69, 0, 7, 196, 74, 229, 6, 76, 67, 7, 196, 52, 18, 165, 64, 66, 7, 196, 47, 164, 207, 84, 66, 6, 195, 15, 177, 131, 66, 0, 8, 197, 165, 83, 6, 45, 32, 66, 9, 198, 9, 16, 83, 157, 129, 133, 67, 0, 9, 198, 87, 51, 196, 68, 21, 64, 67, 9, 198, 45, 22, 210, 76, 101, 192, 66, 0, 0, 7, 196, 48, 240, 148, 76, 66, 7, 196, 21, 246, 70, 44, 66, 0, 8, 197, 72, 149, 110, 37, 32, 65, 8, 197, 48, 149, 198, 55, 176, 67, 8, 197, 8, 198, 213, 119, 208, 66, 0, 9, 198, 65, 180, 117, 30, 149, 192, 67, 9, 198, 67, 98, 72, 88, 241, 64, 67, 9, 198, 44, 148, 140, 244, 241, 64, 67, 0, 15, 3, 95, 53, 88, 48, 36, 47, 70, 36, 87, 6, 36, 47, 0, 9, 198, 64, 243, 9, 16, 195, 211, 67, 10, 199, 64, 241, 82, 24, 186, 101, 68, 65, 0, 7, 196, 84, 17, 15, 76, 66, 11, 200, 68, 18, 3, 24, 164, 17, 5, 96, 67, 7, 196, 67, 100, 198, 196, 67, 7, 196, 52, 22, 129, 8, 66, 7, 196, 47, 160, 84, 48, 67, 7, 196, 212, 163, 137, 44, 66, 0, 9, 197, 12, 209, 146, 76, 240, 72, 23, 8, 197, 96, 149, 76, 36, 176, 66, 8, 197, 87, 49, 147, 36, 176, 67, 8, 197, 77, 16, 68, 36, 176, 66, 8, 197, 64, 241, 73, 80, 208, 65, 9, 198, 66, 254, 19, 36, 181, 13, 66, 8, 197, 53, 182, 48, 36, 176, 67, 8, 197, 48, 241, 56, 24, 80, 67, 0, 0, 6, 195, 5, 1, 140, 66, 0, 7, 196, 60, 46, 211, 204, 65, 0, 9, 197, 20, 241, 70, 76, 240, 72, 23, 8, 197, 49, 241, 79, 24, 80, 67, 6, 195, 45, 69, 122, 65, 8, 197, 8, 97, 12, 36, 176, 66, 0, 9, 198, 152, 147, 205, 60, 81, 140, 69, 0, 16, 3, 95, 54, 88, 89, 36, 87, 47, 70, 36, 87, 6, 36, 47, 0, 6, 195, 8, 240, 72, 66, 0, 7, 196, 88, 18, 163, 32, 66, 6, 195, 79, 178, 123, 67, 11, 200, 73, 189, 194, 73, 48, 240, 36, 176, 66, 11, 200, 60, 38, 134, 73, 48, 240, 36, 176, 66, 7, 196, 56, 246, 134, 72, 66, 9, 198, 47, 52, 209, 5, 65, 122, 67, 6, 195, 47, 49, 151, 66, 7, 196, 5, 93, 142, 76, 66, 0, 9, 198, 47, 48, 240, 92, 156, 237, 69, 8, 197, 232, 100, 165, 57, 48, 67, 8, 197, 4, 90, 82, 5, 48, 67, 0, 9, 198, 88, 207, 79, 87, 211, 64, 67, 9, 198, 55, 51, 196, 68, 19, 64, 67, 9, 198, 141, 28, 68, 60, 195, 196, 68, 9, 198, 8, 242, 5, 80, 75, 192, 67, 0, 6, 195, 22, 243, 192, 66, 6, 195, 91, 219, 64, 66, 6, 195, 81, 27, 192, 66, 0, 7, 196, 77, 244, 66, 188, 66, 6, 195, 11, 209, 151, 66, 6, 195, 173, 70, 123, 67, 0, 8, 197, 46, 52, 113, 25, 48, 67, 0, 6, 195, 51, 17, 173, 67, 0, 0, 7, 196, 73, 51, 194, 244, 66, 7, 196, 60, 33, 139, 76, 66, 7, 196, 48, 110, 58, 20, 67, 11, 200, 7, 179, 211, 70, 244, 144, 245, 48, 69, 0, 8, 197, 73, 254, 81, 36, 128, 66, 8, 197, 169, 52, 73, 60, 192, 67, 0, 9, 198, 73, 180, 87, 24, 35, 204, 67, 9, 198, 67, 97, 139, 148, 228, 192, 67, 6, 195, 46, 58, 145, 66, 9, 198, 44, 48, 69, 70, 244, 192, 66, 9, 198, 20, 96, 159, 148, 228, 192, 67, 9, 198, 153, 62, 61, 78, 148, 192, 68, 0, 6, 195, 160, 176, 64, 65, 9, 198, 44, 48, 69, 70, 226, 115, 68, 0, 7, 196, 68, 22, 6, 48, 66, 7, 196, 48, 149, 240, 32, 66, 7, 196, 47, 53, 84, 32, 66, 7, 196, 44, 240, 148, 68, 66, 0, 6, 195, 47, 61, 74, 66, 8, 197, 197, 49, 132, 70, 208, 67, 6, 195, 8, 241, 110, 66, 0, 5, 194, 53, 64, 72, 6, 195, 66, 144, 237, 66, 9, 198, 56, 249, 81, 37, 68, 128, 66, 9, 198, 15, 180, 207, 48, 100, 192, 67, 0, 16, 3, 95, 56, 88, 39, 87, 36, 63, 70, 36, 87, 6, 36, 47, 0, 0, 6, 195, 144, 179, 51, 66, 7, 196, 36, 188, 207, 52, 67, 0, 8, 197, 79, 131, 15, 55, 176, 67, 8, 197, 68, 18, 14, 61, 32, 66, 8, 197, 67, 203, 18, 187, 16, 68, 8, 197, 8, 25, 76, 119, 48, 67, 0, 9, 198, 67, 160, 68, 68, 21, 64, 67, 9, 198, 52, 20, 139, 232, 17, 64, 67, 9, 198, 32, 54, 206, 76, 97, 192, 66, 9, 198, 16, 99, 196, 68, 21, 64, 67, 0, 0, 8, 196, 36, 132, 15, 20, 72, 23, 7, 196, 55, 4, 207, 48, 66, 7, 196, 28, 20, 141, 196, 66, 7, 196, 8, 204, 197, 196, 66, 6, 195, 4, 131, 211, 66, 0, 12, 201, 84, 244, 236, 233, 51, 196, 68, 21, 64, 69, 8, 197, 67, 164, 206, 119, 208, 66, 8, 197, 12, 100, 246, 55, 176, 67, 8, 197, 5, 43, 210, 119, 208, 67, 8, 197, 172, 48, 77, 235, 16, 68, 0, 5, 194, 36, 208, 72, 7, 195, 145, 42, 69, 72, 23, 9, 198, 97, 65, 197, 192, 101, 192, 67, 9, 198, 74, 129, 39, 180, 97, 192, 68, 9, 198, 60, 36, 65, 32, 101, 192, 67, 0, 17, 3, 95, 57, 88, 70, 36, 82, 36, 47, 70, 36, 87, 6, 36, 47, 0, 0, 9, 198, 47, 52, 209, 5, 95, 82, 67, 6, 195, 47, 164, 243, 66, 0, 8, 197, 22, 126, 240, 36, 176, 66, 0, 9, 198, 84, 207, 37, 20, 114, 96, 65, 9, 198, 64, 145, 133, 25, 41, 76, 68, 9, 198, 14, 180, 129, 20, 114, 96, 65, 0, 9, 198, 20, 148, 12, 60, 208, 83, 67, 0, 7, 196, 67, 212, 201, 236, 67, 7, 196, 5, 14, 129, 76, 67, 0, 8, 197, 72, 201, 253, 24, 80, 67, 8, 197, 64, 195, 218, 4, 80, 66, 9, 198, 44, 20, 139, 4, 87, 125, 67, 8, 197, 18, 145, 125, 24, 80, 67, 0, 0, 6, 195, 79, 191, 64, 66, 0, 7, 196, 92, 145, 47, 196, 65, 7, 196, 85, 68, 68, 204, 66, 7, 196, 79, 179, 113, 180, 67, 6, 195, 74, 82, 239, 66, 7, 196, 161, 68, 246, 56, 67, 7, 196, 53, 69, 76, 204, 66, 7, 196, 45, 68, 66, 188, 66, 7, 196, 17, 25, 157, 244, 66, 0, 8, 197, 91, 210, 72, 205, 48, 67, 8, 197, 77, 18, 84, 53, 80, 66, 8, 197, 165, 36, 253, 189, 48, 67, 8, 197, 20, 100, 20, 149, 48, 67, 8, 197, 11, 177, 139, 25, 48, 67, 0, 6, 195, 46, 58, 153, 66, 9, 198, 153, 51, 205, 60, 43, 128, 68, 0, 6, 195, 164, 139, 128, 66, 0, 6, 195, 149, 1, 147, 66, 6, 195, 64, 156, 251, 67, 7, 196, 44, 21, 155, 68, 66, 6, 195, 10, 208, 239, 66, 0, 8, 197, 75, 18, 231, 25, 112, 65, 8, 197, 72, 98, 229, 57, 48, 66, 8, 197, 64, 241, 76, 25, 112, 66, 9, 198, 52, 146, 47, 79, 100, 0, 67, 8, 197, 47, 52, 148, 49, 48, 66, 8, 197, 20, 100, 144, 61, 48, 66, 8, 197, 8, 148, 141, 81, 48, 66, 8, 197, 5, 36, 60, 189, 48, 67, 0, 6, 195, 68, 17, 122, 65, 9, 198, 64, 243, 20, 87, 27, 64, 68, 9, 198, 66, 226, 68, 68, 147, 64, 67, 0, 6, 195, 144, 178, 83, 65, 9, 198, 52, 17, 40, 76, 245, 115, 68, 6, 195, 10, 226, 115, 67, 6, 195, 10, 210, 243, 66, 0, 6, 195, 20, 145, 136, 66, 0, 8, 196, 13, 180, 86, 80, 72, 23, 7, 196, 166, 132, 175, 72, 67, 7, 196, 164, 140, 239, 72, 67, 6, 195, 67, 160, 69, 66, 7, 196, 46, 52, 137, 44, 66, 6, 195, 180, 37, 13, 66, 0, 8, 197, 148, 194, 82, 54, 240, 67, 8, 197, 67, 160, 66, 24, 192, 67, 8, 197, 44, 243, 39, 60, 128, 67, 6, 195, 30, 193, 138, 66, 0, 6, 195, 8, 98, 243, 66, 0, 6, 195, 164, 140, 192, 66, 0, 7, 196, 88, 240, 143, 76, 66, 11, 200, 73, 51, 205, 5, 51, 204, 60, 64, 68, 11, 200, 160, 61, 144, 5, 51, 204, 60, 64, 69, 0, 8, 197, 84, 97, 123, 10, 208, 65, 8, 197, 70, 241, 70, 54, 240, 67, 8, 197, 44, 242, 60, 60, 64, 65, 8, 197, 20, 146, 1, 40, 224, 66, 0, 9, 198, 160, 35, 210, 44, 204, 192, 67, 9, 198, 44, 226, 68, 224, 148, 128, 67, 0, 0, 7, 196, 92, 145, 47, 244, 67, 7, 196, 195, 210, 65, 100, 68, 0, 6, 195, 72, 107, 210, 66, 8, 197, 64, 241, 82, 51, 48, 66, 9, 198, 20, 19, 65, 32, 198, 203, 67, 0, 6, 195, 52, 19, 115, 66, 9, 198, 24, 130, 75, 156, 97, 64, 68, 6, 195, 10, 210, 239, 66, 0, 10, 199, 88, 207, 103, 60, 95, 79, 20, 69, 0, 7, 196, 83, 99, 15, 16, 67, 7, 196, 77, 68, 203, 180, 66, 7, 196, 72, 191, 70, 92, 66, 12, 201, 67, 98, 72, 212, 84, 147, 15, 2, 75, 67, 0, 8, 197, 164, 114, 82, 119, 208, 67, 8, 197, 64, 243, 20, 79, 48, 67, 9, 198, 52, 148, 139, 196, 198, 203, 67, 8, 197, 44, 241, 207, 23, 176, 67, 8, 197, 20, 157, 228, 57, 32, 67, 0, 5, 194, 48, 144, 72, 9, 198, 49, 67, 143, 88, 241, 64, 67, 9, 198, 18, 113, 133, 157, 177, 64, 68, 9, 198, 12, 100, 246, 88, 241, 64, 67, 6, 195, 10, 212, 243, 66, 0, 10, 199, 10, 180, 251, 36, 243, 15, 16, 69, 0, 26, 4, 104, 116, 116, 112, 36, 57, 74, 47, 37, 12, 47, 37, 12, 6, 48, 37, 12, 10, 0, 81, 58, 47, 47, 32, 7, 196, 61, 51, 9, 12, 65, 6, 195, 46, 192, 113, 67, 6, 195, 31, 192, 85, 66, 0, 8, 197, 68, 18, 12, 60, 208, 66, 8, 197, 44, 19, 89, 36, 176, 66, 8, 197, 25, 2, 72, 60, 80, 67, 0, 9, 198, 128, 213, 17, 49, 66, 192, 67, 9, 198, 95, 194, 193, 20, 114, 96, 65, 6, 195, 164, 142, 195, 66, 9, 198, 45, 22, 195, 56, 146, 192, 66, 9, 198, 21, 22, 195, 56, 146, 192, 66, 6, 195, 8, 100, 243, 66, 0, 6, 195, 52, 18, 128, 72, 0, 7, 196, 79, 181, 201, 236, 67, 0, 8, 197, 77, 16, 85, 36, 176, 66, 8, 197, 73, 65, 71, 80, 176, 66, 8, 197, 68, 20, 147, 24, 112, 66, 8, 197, 67, 98, 1, 36, 176, 67, 8, 197, 157, 113, 131, 108, 80, 67, 0, 9, 198, 77, 16, 77, 12, 18, 128, 66, 9, 198, 52, 98, 15, 32, 242, 128, 67, 9, 198, 19, 98, 5, 60, 46, 192, 67, 6, 195, 10, 225, 147, 66, 0, 9, 198, 52, 146, 246, 17, 16, 85, 67, 6, 195, 36, 132, 236, 65, 10, 199, 9, 179, 4, 232, 245, 79, 8, 68, 0, 7, 196, 52, 21, 8, 236, 65, 6, 195, 19, 14, 237, 67, 0, 8, 197, 73, 64, 134, 45, 48, 66, 8, 197, 164, 92, 68, 61, 48, 65, 9, 198, 144, 33, 133, 164, 226, 75, 66, 8, 197, 44, 243, 111, 23, 192, 67, 9, 198, 20, 144, 66, 25, 50, 75, 68, 6, 195, 173, 179, 0, 66, 0, 15, 4, 95, 48, 77, 50, 63, 37, 55, 37, 6, 39, 50, 35, 0, 5, 194, 179, 128, 66, 9, 198, 44, 97, 6, 48, 43, 192, 65, 6, 195, 8, 241, 151, 66, 0, 16, 4, 95, 48, 77, 51, 63, 37, 55, 37, 6, 35, 34, 70, 35, 0, 10, 199, 168, 81, 143, 79, 179, 113, 180, 70, 0, 8, 196, 64, 244, 169, 20, 72, 23, 7, 196, 99, 166, 65, 84, 66, 0, 14, 4, 95, 48, 77, 49, 97, 6, 37, 55, 35, 70, 37, 0, 8, 197, 73, 178, 204, 25, 48, 66, 8, 197, 164, 142, 195, 5, 48, 67, 6, 195, 61, 59, 0, 65, 8, 197, 140, 179, 205, 25, 112, 65, 9, 198, 25, 11, 134, 65, 50, 75, 68, 8, 197, 4, 93, 75, 5, 48, 67, 0, 9, 198, 72, 98, 210, 5, 11, 128, 67, 6, 195, 68, 18, 179, 66, 9, 198, 46, 209, 91, 69, 179, 64, 67, 0, 9, 198, 75, 185, 207, 23, 211, 197, 69, 6, 195, 74, 220, 192, 66, 6, 195, 10, 220, 192, 66, 0, 9, 198, 91, 210, 72, 206, 83, 0, 68, 7, 196, 9, 66, 210, 240, 66, 0, 8, 197, 75, 19, 204, 60, 64, 67, 8, 197, 64, 99, 9, 46, 240, 67, 8, 197, 44, 25, 76, 60, 64, 67, 0, 9, 198, 88, 244, 240, 76, 244, 192, 67, 9, 198, 65, 180, 198, 64, 148, 128, 67, 0, 9, 198, 73, 62, 198, 61, 91, 141, 68, 10, 199, 66, 145, 82, 150, 164, 198, 48, 66, 0, 8, 196, 144, 180, 65, 40, 72, 23, 7, 196, 85, 68, 78, 240, 66, 11, 200, 52, 146, 246, 8, 147, 204, 60, 64, 69, 7, 196, 45, 68, 100, 32, 66, 7, 196, 36, 132, 9, 76, 65, 7, 196, 11, 162, 83, 204, 67, 0, 9, 198, 52, 146, 47, 73, 124, 0, 67, 9, 198, 45, 79, 148, 32, 197, 11, 67, 8, 197, 24, 179, 204, 60, 64, 67, 6, 195, 10, 219, 210, 66, 0, 9, 198, 95, 4, 212, 68, 156, 192, 68, 6, 195, 222, 67, 147, 66, 6, 195, 225, 50, 75, 66, 9, 198, 54, 242, 85, 25, 36, 192, 67, 0, 10, 199, 145, 4, 91, 73, 51, 137, 44, 65, 0, 7, 196, 73, 68, 201, 192, 67, 7, 196, 24, 180, 165, 32, 66, 7, 196, 232, 43, 70, 76, 67, 0, 8, 197, 92, 100, 6, 51, 16, 67, 9, 198, 84, 16, 145, 36, 187, 211, 67, 9, 198, 220, 80, 69, 28, 152, 0, 65, 8, 197, 44, 243, 80, 5, 32, 66, 9, 198, 16, 147, 100, 73, 50, 75, 67, 8, 197, 5, 66, 215, 39, 48, 68, 0, 6, 195, 160, 49, 135, 66, 6, 195, 47, 176, 239, 66, 0, 9, 198, 57, 242, 189, 45, 139, 241, 66, 0, 7, 196, 140, 212, 198, 28, 66, 7, 196, 47, 211, 137, 32, 66, 7, 196, 20, 99, 21, 196, 66, 0, 6, 195, 68, 25, 74, 66, 8, 197, 66, 149, 73, 45, 32, 66, 8, 197, 52, 240, 137, 87, 48, 65, 9, 198, 44, 194, 77, 5, 50, 75, 67, 8, 197, 8, 20, 147, 39, 48, 67, 0, 5, 194, 52, 144, 72, 0, 9, 198, 20, 149, 123, 193, 114, 109, 69, 10, 199, 4, 77, 130, 36, 243, 15, 16, 69, 0, 7, 196, 88, 148, 233, 92, 66, 11, 200, 73, 51, 205, 188, 240, 134, 79, 48, 69, 6, 195, 67, 160, 85, 66, 7, 196, 192, 150, 58, 196, 66, 7, 196, 9, 68, 75, 188, 66, 0, 0, 9, 198, 72, 19, 84, 68, 18, 128, 67, 6, 195, 66, 152, 211, 66, 9, 198, 60, 33, 140, 37, 34, 192, 67, 0, 10, 199, 72, 191, 79, 73, 51, 205, 236, 68, 10, 199, 64, 241, 80, 37, 35, 137, 44, 65, 0, 7, 196, 48, 244, 137, 204, 67, 0, 8, 197, 66, 208, 77, 80, 80, 67, 8, 197, 44, 17, 118, 168, 176, 67, 9, 198, 193, 53, 18, 36, 20, 147, 68, 0, 9, 198, 88, 244, 198, 48, 158, 192, 68, 9, 198, 64, 100, 207, 8, 242, 128, 67, 0, 10, 199, 99, 208, 129, 20, 123, 155, 44, 68, 10, 199, 20, 99, 115, 73, 52, 111, 76, 67, 0, 11, 200, 33, 176, 143, 76, 101, 142, 36, 176, 68, 7, 196, 175, 209, 70, 204, 68, 0, 8, 197, 20, 144, 66, 25, 48, 67, 8, 197, 12, 22, 112, 25, 112, 65, 0, 0, 9, 198, 66, 52, 206, 61, 99, 197, 67, 10, 199, 44, 16, 145, 36, 243, 6, 76, 68, 0, 6, 195, 84, 159, 69, 66, 11, 200, 67, 101, 75, 60, 210, 83, 25, 48, 68, 12, 201, 48, 147, 115, 4, 80, 69, 28, 152, 0, 67, 9, 198, 33, 176, 143, 48, 98, 250, 67, 0, 8, 197, 77, 16, 80, 25, 112, 66, 9, 198, 216, 84, 147, 15, 2, 75, 65, 8, 197, 65, 16, 82, 25, 112, 66, 8, 197, 44, 16, 177, 25, 48, 67, 8, 197, 9, 18, 75, 25, 48, 66, 0, 9, 198, 95, 177, 141, 204, 155, 64, 69, 0, 10, 199, 197, 33, 139, 76, 149, 201, 20, 68, 6, 195, 196, 20, 192, 66, 0, 9, 198, 216, 83, 197, 192, 93, 142, 68, 11, 200, 68, 17, 73, 60, 16, 179, 5, 48, 70, 0, 6, 195, 160, 61, 142, 66, 8, 197, 47, 178, 240, 24, 128, 67, 0, 9, 198, 64, 243, 6, 16, 20, 192, 67, 9, 198, 64, 20, 209, 36, 244, 192, 67, 9, 198, 47, 52, 144, 24, 180, 192, 66, 0, 0, 7, 196, 77, 68, 78, 240, 66, 7, 196, 61, 48, 137, 12, 65, 7, 196, 180, 219, 193, 88, 67, 0, 8, 197, 77, 18, 80, 140, 224, 66, 8, 197, 52, 17, 71, 80, 224, 66, 6, 195, 46, 208, 74, 66, 8, 197, 20, 240, 187, 54, 240, 65, 0, 9, 198, 44, 243, 80, 48, 244, 192, 66, 9, 198, 44, 243, 66, 196, 20, 192, 67, 0, 6, 195, 12, 98, 60, 66, 0, 7, 196, 87, 211, 109, 196, 67, 7, 196, 86, 249, 82, 76, 66, 7, 196, 20, 241, 39, 244, 65, 6, 195, 212, 18, 189, 67, 0, 9, 198, 64, 193, 141, 192, 226, 75, 65, 8, 197, 66, 51, 139, 79, 48, 66, 9, 198, 224, 242, 9, 92, 156, 251, 70, 9, 198, 160, 89, 207, 48, 226, 75, 68, 8, 197, 52, 148, 137, 207, 176, 68, 8, 197, 47, 50, 212, 69, 32, 66, 8, 197, 24, 180, 144, 165, 32, 66, 8, 197, 9, 243, 6, 79, 16, 67, 0, 9, 198, 52, 227, 196, 61, 131, 48, 67, 0, 0, 7, 195, 56, 146, 0, 72, 23, 7, 196, 66, 145, 39, 244, 65, 7, 196, 67, 160, 85, 196, 67, 7, 196, 36, 129, 39, 244, 65, 7, 196, 33, 176, 134, 92, 66, 0, 8, 197, 77, 16, 84, 51, 176, 65, 8, 197, 76, 105, 78, 81, 32, 65, 8, 197, 161, 68, 144, 25, 96, 67, 8, 197, 12, 18, 6, 51, 16, 67, 6, 195, 189, 80, 82, 66, 0, 5, 194, 72, 16, 72, 5, 194, 56, 144, 72, 6, 195, 4, 32, 83, 66, 0, 10, 199, 67, 100, 144, 236, 148, 198, 76, 68, 12, 201, 47, 164, 207, 86, 195, 205, 8, 18, 142, 69, 9, 198, 20, 147, 79, 61, 61, 69, 68, 0, 7, 196, 46, 144, 193, 76, 66, 7, 196, 44, 243, 73, 44, 66, 7, 196, 8, 18, 45, 76, 66, 0, 8, 197, 148, 35, 15, 36, 80, 67, 0, 6, 194, 184, 144, 72, 23, 6, 194, 172, 240, 72, 23, 9, 198, 81, 41, 66, 5, 146, 96, 66, 9, 198, 145, 18, 207, 76, 146, 192, 67, 0, 0, 7, 196, 75, 176, 134, 32, 66, 7, 196, 67, 212, 233, 76, 66, 7, 196, 45, 77, 145, 76, 66, 7, 196, 47, 170, 212, 48, 67, 7, 196, 29, 68, 100, 48, 66, 7, 196, 25, 81, 139, 76, 66, 0, 8, 197, 76, 101, 142, 36, 176, 66, 8, 197, 64, 243, 49, 60, 208, 67, 8, 197, 66, 217, 142, 36, 176, 65, 12, 201, 188, 100, 147, 24, 130, 79, 48, 241, 0, 70, 0, 9, 198, 64, 20, 207, 48, 241, 0, 67, 9, 198, 10, 218, 15, 48, 241, 0, 68, 0, 10, 199, 89, 64, 143, 73, 51, 137, 44, 67, 0, 6, 195, 52, 18, 189, 66, 7, 196, 44, 243, 24, 188, 66, 7, 196, 47, 176, 83, 196, 67, 0, 8, 197, 104, 145, 12, 25, 112, 66, 8, 197, 73, 77, 132, 5, 48, 67, 8, 197, 44, 62, 147, 25, 48, 66, 0, 0, 10, 199, 20, 99, 9, 44, 20, 198, 72, 68, 0, 7, 196, 164, 140, 221, 244, 67, 7, 196, 47, 160, 137, 20, 66, 6, 195, 20, 147, 197, 66, 0, 9, 198, 73, 3, 6, 76, 226, 75, 66, 8, 197, 52, 101, 240, 5, 48, 67, 9, 198, 52, 105, 85, 36, 130, 75, 68, 9, 198, 44, 243, 6, 72, 226, 75, 67, 9, 198, 36, 213, 14, 37, 49, 147, 68, 0, 0, 10, 199, 73, 64, 251, 192, 148, 198, 76, 69, 6, 195, 47, 193, 152, 66, 10, 199, 169, 34, 207, 32, 148, 198, 76, 68, 0, 12, 201, 65, 180, 117, 36, 132, 207, 96, 226, 75, 67, 7, 196, 64, 241, 70, 52, 66, 7, 196, 67, 177, 6, 48, 66, 7, 196, 140, 47, 111, 76, 67, 7, 196, 45, 79, 148, 32, 66, 7, 196, 16, 213, 41, 92, 66, 7, 196, 8, 244, 165, 56, 66, 7, 196, 189, 50, 68, 192, 67, 0, 8, 197, 87, 162, 82, 24, 160, 67, 12, 201, 80, 196, 209, 4, 210, 75, 217, 34, 248, 69, 0, 0, 0, 6, 195, 74, 241, 109, 66, 7, 196, 5, 60, 37, 76, 67, 0, 8, 197, 68, 18, 5, 24, 192, 66, 8, 197, 67, 98, 72, 212, 192, 67, 8, 197, 47, 165, 73, 60, 192, 67, 8, 197, 16, 243, 15, 18, 240, 67, 0, 9, 198, 65, 34, 86, 224, 20, 192, 67, 9, 198, 48, 98, 211, 244, 20, 192, 67, 9, 198, 47, 53, 76, 36, 180, 192, 66, 9, 198, 44, 243, 80, 189, 220, 192, 67, 6, 195, 24, 130, 75, 66, 6, 195, 9, 250, 75, 66, 0, 10, 199, 73, 179, 73, 100, 204, 9, 44, 66, 9, 198, 45, 66, 212, 69, 66, 0, 67, 0, 7, 196, 32, 17, 39, 244, 65, 0, 12, 201, 68, 17, 73, 61, 49, 140, 25, 92, 192, 70, 9, 198, 64, 243, 65, 34, 242, 75, 66, 8, 197, 66, 242, 233, 5, 32, 67, 0, 38, 3, 95, 194, 171, 55, 38, 4, 35, 82, 35, 15, 70, 82, 4, 39, 37, 50, 35, 15, 47, 34, 37, 4, 13, 79, 35, 55, 50, 35, 15, 87, 49, 6, 39, 69, 35, 0, 0, 10, 199, 52, 21, 141, 81, 19, 20, 44, 67, 0, 12, 201, 96, 100, 252, 37, 177, 27, 48, 226, 75, 68, 7, 196, 66, 144, 198, 72, 66, 7, 196, 55, 62, 15, 48, 67, 7, 196, 28, 144, 198, 92, 66, 11, 200, 168, 81, 143, 76, 99, 6, 87, 48, 70, 7, 196, 188, 20, 207, 52, 67, 0, 24, 3, 95, 194, 166, 48, 34, 36, 49, 4, 13, 87, 50, 35, 47, 35, 15, 74, 36, 34, 47, 6, 35, 0, 12, 201, 48, 148, 251, 5, 53, 54, 12, 97, 64, 70, 8, 197, 28, 145, 12, 119, 208, 66, 6, 195, 23, 17, 46, 66, 0, 9, 198, 73, 59, 15, 60, 35, 112, 68, 0, 0, 6, 195, 78, 196, 177, 66, 6, 195, 52, 17, 253, 66, 7, 196, 48, 145, 14, 196, 66, 7, 196, 47, 57, 75, 76, 66, 0, 8, 197, 75, 30, 19, 36, 176, 67, 0, 9, 198, 66, 209, 153, 56, 146, 192, 65, 9, 198, 20, 148, 144, 189, 46, 192, 67, 0, 9, 198, 65, 50, 87, 24, 54, 197, 67, 9, 198, 67, 168, 205, 193, 55, 125, 68, 8, 197, 20, 53, 24, 51, 0, 66, 9, 198, 169, 113, 129, 20, 223, 45, 69, 10, 199, 8, 146, 195, 4, 84, 65, 76, 67, 0, 7, 196, 77, 67, 20, 52, 66, 7, 196, 67, 96, 137, 12, 65, 7, 196, 25, 34, 253, 76, 66, 7, 196, 8, 148, 35, 56, 66, 6, 195, 4, 33, 109, 66, 0, 12, 201, 65, 34, 86, 62, 251, 73, 76, 146, 192, 70, 9, 198, 52, 109, 197, 60, 34, 67, 67, 8, 197, 44, 253, 208, 4, 80, 67, 8, 197, 44, 20, 24, 80, 176, 66, 12, 201, 20, 243, 79, 81, 4, 102, 37, 49, 140, 68, 8, 197, 18, 49, 78, 36, 176, 66, 8, 197, 212, 94, 54, 212, 80, 68, 0, 15, 66, 73, 48, 87, 47, 39, 47, 6, 37, 50, 49, 37, 0, 24, 9, 198, 96, 148, 147, 56, 146, 192, 66, 9, 198, 172, 17, 70, 52, 146, 192, 68, 0, 10, 199, 161, 13, 139, 225, 43, 201, 44, 67, 0, 9, 198, 60, 194, 68, 61, 90, 78, 68, 11, 200, 24, 180, 139, 81, 18, 39, 60, 80, 68, 7, 196, 13, 180, 83, 224, 66, 7, 196, 189, 60, 201, 52, 67, 0, 8, 197, 164, 180, 253, 5, 48, 67, 9, 198, 54, 249, 76, 37, 49, 147, 68, 8, 197, 22, 196, 253, 5, 48, 67, 8, 197, 5, 49, 146, 149, 48, 67, 0, 9, 198, 99, 179, 143, 32, 99, 64, 67, 6, 195, 141, 81, 147, 66, 6, 195, 20, 144, 239, 66, 0, 0, 7, 196, 220, 197, 70, 28, 66, 7, 196, 145, 55, 233, 48, 67, 12, 201, 52, 227, 196, 61, 177, 27, 48, 226, 75, 67, 7, 196, 54, 49, 70, 28, 66, 7, 196, 52, 101, 239, 196, 67, 7, 196, 54, 241, 139, 192, 67, 0, 9, 198, 74, 80, 174, 37, 49, 147, 68, 8, 197, 44, 244, 147, 81, 16, 66, 8, 197, 16, 102, 70, 85, 48, 66, 0, 0, 6, 195, 87, 3, 204, 66, 6, 195, 156, 100, 128, 66, 0, 7, 196, 67, 96, 143, 40, 66, 7, 196, 66, 145, 70, 48, 66, 7, 196, 52, 241, 70, 52, 66, 6, 195, 44, 101, 109, 66, 7, 196, 44, 17, 70, 52, 66, 6, 195, 168, 135, 125, 66, 7, 196, 8, 17, 70, 52, 66, 0, 8, 197, 64, 243, 46, 24, 160, 67, 8, 197, 60, 36, 147, 164, 192, 66, 8, 197, 20, 101, 201, 54, 208, 67, 8, 197, 16, 99, 204, 60, 64, 67, 0, 9, 198, 16, 244, 144, 60, 92, 64, 67, 0, 9, 198, 13, 67, 133, 236, 188, 69, 65, 6, 195, 154, 244, 128, 66, 0, 7, 196, 52, 241, 70, 48, 66, 0, 8, 197, 87, 163, 65, 220, 224, 67, 0, 9, 198, 46, 208, 77, 9, 68, 64, 67, 6, 195, 4, 164, 111, 66, 0, 10, 199, 52, 20, 209, 39, 165, 129, 76, 68, 10, 199, 189, 50, 66, 36, 244, 201, 44, 69, 0, 7, 196, 88, 19, 84, 76, 66, 7, 196, 86, 245, 122, 204, 67, 7, 196, 221, 84, 212, 236, 65, 9, 198, 67, 100, 212, 11, 187, 210, 68, 7, 196, 64, 19, 84, 44, 66, 7, 196, 64, 17, 70, 28, 66, 0, 9, 198, 67, 100, 198, 74, 83, 147, 67, 8, 197, 44, 240, 85, 119, 208, 67, 0, 6, 195, 14, 209, 135, 66, 0, 10, 199, 23, 82, 139, 4, 81, 201, 128, 65, 10, 199, 8, 20, 139, 25, 48, 143, 48, 65, 0, 7, 196, 79, 2, 20, 88, 66, 7, 196, 149, 16, 83, 244, 67, 7, 196, 244, 156, 19, 240, 68, 12, 201, 24, 113, 146, 24, 83, 73, 96, 226, 75, 67, 7, 196, 9, 70, 77, 192, 66, 0, 12, 201, 73, 14, 205, 5, 51, 200, 60, 145, 64, 69, 8, 197, 55, 52, 176, 119, 208, 67, 6, 195, 37, 160, 86, 66, 9, 198, 19, 161, 123, 60, 34, 123, 69, 0, 9, 198, 45, 66, 204, 156, 241, 64, 67, 0, 10, 199, 92, 155, 231, 60, 95, 79, 20, 70, 10, 199, 44, 20, 1, 92, 148, 198, 76, 68, 0, 7, 196, 61, 48, 143, 40, 66, 7, 196, 32, 21, 163, 72, 66, 0, 8, 197, 65, 26, 211, 36, 176, 66, 8, 197, 55, 6, 70, 168, 176, 67, 9, 198, 189, 50, 80, 5, 32, 83, 68, 0, 0, 7, 195, 65, 178, 192, 72, 23, 0, 0, 8, 197, 77, 68, 19, 24, 112, 66, 8, 197, 73, 180, 54, 212, 80, 67, 8, 197, 64, 100, 147, 36, 176, 66, 9, 198, 24, 178, 9, 73, 60, 23, 67, 0, 9, 198, 54, 98, 15, 48, 98, 128, 67, 0, 6, 195, 90, 107, 192, 66, 0, 7, 196, 64, 243, 39, 196, 67, 7, 196, 64, 96, 198, 92, 66, 7, 196, 160, 209, 165, 48, 67, 7, 196, 32, 101, 147, 196, 66, 7, 196, 16, 241, 70, 28, 66, 7, 196, 8, 241, 70, 28, 66, 0, 0, 38, 3, 95, 194, 187, 114, 4, 35, 87, 50, 35, 15, 70, 82, 4, 39, 37, 50, 35, 15, 47, 34, 37, 4, 13, 79, 35, 55, 50, 35, 15, 87, 49, 6, 39, 69, 35, 0, 0, 6, 195, 98, 187, 64, 66, 10, 199, 72, 52, 91, 89, 137, 198, 44, 67, 6, 195, 74, 107, 192, 66, 0, 7, 195, 66, 146, 0, 72, 23, 6, 195, 15, 188, 237, 67, 0, 8, 197, 88, 145, 81, 5, 48, 66, 8, 197, 72, 186, 237, 25, 112, 67, 6, 195, 52, 29, 206, 66, 0, 5, 194, 72, 96, 72, 9, 198, 88, 145, 118, 66, 51, 128, 67, 0, 10, 199, 88, 99, 9, 60, 68, 65, 84, 68, 10, 199, 68, 17, 73, 60, 68, 65, 84, 68, 10, 199, 47, 161, 73, 60, 68, 65, 84, 68, 10, 199, 44, 20, 9, 77, 72, 206, 76, 68, 10, 199, 17, 22, 205, 60, 244, 245, 20, 68, 0, 7, 196, 85, 65, 1, 72, 66, 7, 196, 72, 19, 84, 68, 66, 11, 200, 52, 100, 198, 244, 241, 17, 5, 80, 69, 7, 196, 47, 52, 246, 48, 66, 11, 200, 37, 36, 253, 36, 241, 17, 5, 80, 69, 7, 196, 13, 180, 72, 224, 66, 11, 200, 8, 144, 140, 36, 241, 17, 5, 80, 68, 0, 6, 195, 68, 149, 250, 65, 12, 201, 67, 97, 139, 76, 241, 79, 18, 127, 64, 68, 8, 197, 11, 101, 14, 196, 64, 65, 8, 197, 8, 147, 204, 60, 64, 67, 0, 9, 198, 76, 98, 232, 84, 100, 128, 67, 9, 198, 197, 62, 213, 24, 164, 128, 67, 6, 195, 19, 177, 111, 66, 9, 198, 233, 98, 80, 26, 49, 0, 68, 0, 10, 199, 64, 243, 20, 36, 82, 79, 76, 69, 9, 198, 19, 181, 14, 20, 149, 13, 66, 0, 7, 196, 99, 1, 6, 48, 66, 7, 196, 79, 179, 9, 44, 66, 7, 196, 72, 97, 70, 84, 66, 9, 198, 68, 17, 70, 76, 99, 0, 67, 9, 198, 64, 244, 140, 25, 2, 82, 67, 7, 196, 54, 241, 65, 76, 66, 7, 196, 45, 64, 251, 76, 66, 7, 196, 46, 244, 243, 236, 67, 7, 196, 21, 180, 77, 204, 66, 7, 196, 19, 177, 6, 84, 66, 7, 196, 154, 241, 58, 20, 67, 0, 8, 197, 86, 227, 204, 60, 64, 67, 8, 197, 66, 145, 76, 60, 64, 66, 8, 197, 20, 96, 134, 140, 224, 67, 8, 197, 180, 179, 214, 60, 192, 67, 6, 195, 180, 155, 210, 67, 0, 9, 198, 24, 180, 147, 70, 180, 192, 66, 0, 9, 198, 217, 51, 73, 73, 54, 209, 65, 6, 195, 175, 209, 64, 66, 0, 7, 196, 53, 66, 6, 40, 66, 7, 196, 47, 160, 143, 48, 66, 7, 196, 44, 17, 70, 76, 66, 7, 196, 172, 59, 111, 16, 67, 0, 6, 195, 72, 111, 0, 66, 8, 197, 66, 52, 147, 187, 16, 67, 8, 197, 140, 36, 65, 23, 208, 67, 8, 197, 45, 68, 139, 81, 32, 66, 8, 197, 22, 226, 71, 189, 32, 67, 0, 9, 198, 65, 180, 67, 192, 101, 192, 67, 6, 195, 66, 195, 51, 66, 0, 10, 199, 72, 184, 197, 4, 81, 201, 128, 65, 0, 7, 196, 91, 161, 84, 236, 65, 12, 201, 52, 242, 1, 40, 176, 69, 28, 152, 0, 66, 7, 196, 44, 20, 147, 244, 66, 0, 8, 197, 77, 27, 210, 87, 176, 66, 8, 197, 76, 243, 59, 189, 32, 67, 8, 197, 73, 69, 73, 45, 32, 66, 9, 198, 72, 100, 147, 71, 18, 75, 65, 9, 198, 44, 243, 70, 20, 155, 211, 68, 8, 197, 44, 243, 2, 5, 32, 66, 8, 197, 24, 208, 145, 39, 48, 67, 0, 6, 194, 56, 240, 72, 23, 0, 0, 0, 6, 195, 66, 57, 78, 66, 8, 197, 64, 99, 19, 24, 176, 66, 8, 197, 34, 110, 176, 36, 176, 66, 8, 197, 189, 50, 80, 60, 80, 67, 0, 6, 195, 55, 17, 123, 66, 9, 198, 183, 163, 65, 20, 114, 96, 66, 0, 0, 7, 196, 164, 62, 239, 72, 67, 7, 196, 66, 149, 163, 72, 66, 6, 195, 46, 209, 141, 66, 7, 196, 15, 162, 111, 76, 67, 7, 196, 8, 144, 187, 204, 67, 0, 8, 197, 67, 100, 176, 36, 176, 67, 16, 205, 61, 49, 152, 25, 36, 195, 192, 245, 118, 57, 57, 198, 92, 70, 8, 197, 52, 148, 147, 36, 176, 66, 8, 197, 55, 18, 77, 80, 208, 65, 8, 197, 52, 105, 76, 36, 176, 67, 8, 197, 168, 62, 137, 80, 208, 66, 8, 197, 172, 62, 137, 80, 208, 66, 0, 0, 9, 198, 76, 101, 142, 36, 181, 13, 65, 10, 199, 64, 193, 139, 72, 145, 35, 72, 67, 0, 7, 196, 165, 114, 101, 48, 67, 0, 6, 195, 84, 148, 238, 66, 8, 197, 73, 67, 21, 5, 48, 66, 8, 197, 67, 162, 83, 25, 48, 67, 9, 198, 16, 100, 165, 66, 113, 151, 66, 8, 197, 13, 16, 66, 25, 112, 66, 8, 197, 153, 59, 17, 5, 48, 67, 0, 9, 198, 73, 4, 113, 77, 223, 64, 66, 6, 195, 66, 177, 147, 66, 0, 0, 8, 196, 52, 97, 197, 80, 72, 23, 11, 200, 88, 145, 118, 73, 67, 21, 5, 48, 68, 7, 196, 74, 129, 198, 92, 66, 7, 196, 72, 19, 84, 56, 66, 6, 195, 68, 149, 241, 66, 7, 196, 32, 20, 140, 204, 66, 0, 8, 197, 73, 176, 145, 5, 48, 66, 9, 198, 73, 64, 147, 217, 2, 75, 67, 9, 198, 65, 18, 89, 24, 193, 151, 67, 0, 14, 66, 64, 192, 48, 55, 39, 89, 47, 6, 35, 47, 0, 24, 6, 195, 79, 90, 87, 66, 9, 198, 5, 36, 209, 4, 75, 192, 67, 0, 0, 7, 196, 45, 68, 73, 236, 67, 7, 196, 31, 164, 201, 236, 67, 11, 200, 24, 193, 139, 79, 97, 17, 5, 80, 68, 7, 196, 172, 62, 134, 48, 67, 0, 8, 197, 60, 34, 88, 4, 160, 67, 8, 197, 47, 210, 85, 24, 160, 67, 0, 9, 198, 92, 149, 123, 10, 52, 192, 65, 9, 198, 86, 181, 12, 76, 100, 192, 67, 9, 198, 64, 19, 85, 48, 100, 192, 66, 9, 198, 47, 52, 209, 6, 212, 192, 67, 6, 195, 8, 146, 51, 66, 0, 6, 195, 18, 61, 88, 66, 0, 11, 200, 66, 145, 80, 4, 130, 83, 24, 192, 66, 7, 196, 55, 62, 35, 56, 67, 7, 196, 7, 190, 35, 56, 68, 0, 8, 197, 67, 213, 198, 140, 224, 67, 8, 197, 58, 193, 65, 80, 224, 65, 8, 197, 32, 20, 147, 60, 160, 66, 9, 198, 34, 188, 248, 216, 98, 211, 69, 8, 197, 19, 161, 123, 60, 32, 67, 8, 197, 212, 83, 197, 24, 192, 67, 8, 197, 8, 19, 194, 4, 32, 67, 0, 9, 198, 197, 52, 73, 18, 244, 192, 67, 6, 195, 4, 47, 83, 66, 0, 10, 199, 73, 176, 233, 55, 3, 137, 44, 66, 0, 7, 196, 74, 129, 61, 196, 67, 7, 196, 60, 37, 143, 20, 66, 7, 196, 140, 142, 134, 76, 67, 7, 196, 11, 169, 198, 92, 65, 0, 6, 195, 57, 251, 210, 66, 8, 197, 52, 98, 44, 233, 0, 67, 8, 197, 46, 224, 193, 79, 176, 65, 8, 197, 17, 18, 77, 119, 208, 66, 9, 198, 212, 163, 137, 44, 198, 203, 67, 8, 197, 8, 99, 39, 141, 32, 67, 0, 9, 198, 72, 214, 209, 20, 97, 192, 66, 9, 198, 53, 16, 72, 156, 101, 192, 65, 9, 198, 140, 225, 68, 68, 21, 64, 66, 9, 198, 46, 210, 68, 68, 21, 64, 67, 9, 198, 13, 177, 12, 236, 241, 64, 67, 0, 10, 199, 17, 16, 83, 37, 38, 9, 128, 65, 0, 7, 196, 52, 97, 70, 92, 66, 7, 196, 18, 61, 105, 32, 67, 0, 6, 195, 84, 29, 206, 66, 8, 197, 36, 212, 20, 49, 32, 66, 8, 197, 4, 36, 151, 25, 32, 66, 0, 5, 194, 72, 144, 72, 9, 198, 72, 180, 73, 64, 101, 192, 66, 9, 198, 64, 148, 207, 52, 101, 192, 65, 6, 195, 67, 169, 175, 67, 9, 198, 16, 16, 182, 12, 101, 192, 65, 9, 198, 13, 16, 71, 180, 101, 192, 67, 0, 6, 195, 149, 53, 12, 66, 9, 198, 197, 62, 228, 92, 156, 237, 70, 0, 7, 196, 88, 243, 79, 76, 66, 7, 196, 88, 147, 73, 44, 66, 7, 196, 84, 20, 148, 48, 66, 7, 196, 221, 3, 227, 56, 67, 6, 195, 165, 53, 25, 66, 7, 196, 61, 50, 9, 12, 65, 0, 8, 197, 64, 22, 109, 108, 176, 67, 0, 9, 198, 84, 242, 187, 15, 178, 192, 65, 0, 10, 199, 67, 195, 211, 25, 99, 137, 44, 68, 0, 11, 200, 65, 180, 117, 53, 182, 48, 36, 176, 69, 7, 196, 67, 212, 236, 180, 67, 6, 195, 50, 197, 13, 66, 7, 196, 44, 20, 137, 236, 67, 0, 8, 197, 84, 197, 61, 36, 80, 67, 8, 197, 52, 101, 140, 24, 208, 66, 8, 197, 45, 68, 89, 80, 208, 66, 8, 197, 47, 160, 77, 86, 224, 67, 0, 6, 195, 47, 209, 115, 66, 6, 195, 37, 161, 151, 66, 0, 6, 195, 79, 203, 192, 66, 9, 198, 73, 67, 21, 4, 210, 69, 67, 10, 199, 68, 17, 73, 179, 53, 251, 76, 69, 10, 199, 64, 20, 209, 39, 165, 129, 76, 68, 6, 195, 47, 219, 64, 66, 0, 7, 196, 64, 98, 211, 196, 66, 7, 196, 212, 94, 1, 20, 67, 0, 8, 197, 65, 67, 139, 79, 192, 66, 8, 197, 56, 144, 198, 51, 192, 67, 8, 197, 52, 21, 73, 61, 48, 67, 8, 197, 25, 2, 83, 25, 48, 67, 0, 6, 195, 44, 246, 47, 66, 9, 198, 46, 227, 196, 68, 19, 64, 67, 9, 198, 193, 51, 205, 60, 195, 196, 68, 0, 6, 195, 87, 27, 64, 66, 10, 199, 54, 242, 85, 25, 41, 78, 76, 68, 0, 11, 200, 80, 226, 67, 237, 34, 83, 25, 48, 69, 11, 200, 73, 1, 151, 38, 210, 83, 25, 48, 69, 6, 195, 46, 226, 77, 66, 0, 8, 197, 88, 18, 163, 41, 80, 66, 9, 198, 52, 20, 139, 232, 198, 203, 67, 8, 197, 24, 194, 75, 75, 192, 67, 8, 197, 20, 144, 82, 47, 128, 67, 0, 9, 198, 36, 36, 73, 100, 147, 64, 67, 0, 6, 195, 46, 214, 208, 66, 0, 7, 196, 76, 99, 70, 48, 66, 7, 196, 64, 241, 54, 52, 66, 7, 196, 67, 171, 70, 48, 67, 7, 196, 64, 20, 20, 68, 66, 6, 195, 55, 23, 125, 66, 0, 0, 9, 198, 68, 146, 207, 100, 100, 192, 67, 9, 198, 141, 28, 68, 61, 92, 192, 68, 9, 198, 44, 25, 80, 80, 196, 192, 67, 0, 0, 7, 196, 96, 100, 9, 44, 66, 7, 196, 148, 180, 201, 44, 66, 7, 196, 47, 53, 251, 76, 66, 6, 195, 46, 214, 213, 66, 7, 196, 8, 98, 193, 72, 66, 7, 196, 153, 59, 35, 12, 67, 0, 8, 197, 45, 18, 82, 148, 192, 66, 0, 9, 198, 72, 19, 79, 48, 100, 192, 67, 9, 198, 60, 211, 137, 9, 68, 128, 65, 9, 198, 52, 146, 246, 128, 137, 252, 69, 6, 195, 19, 171, 211, 66, 0, 6, 195, 98, 182, 204, 66, 10, 199, 75, 180, 201, 84, 146, 193, 76, 68, 10, 199, 72, 98, 212, 56, 83, 205, 236, 68, 10, 199, 67, 99, 73, 100, 204, 9, 44, 66, 9, 198, 44, 243, 15, 21, 21, 13, 67, 10, 199, 44, 243, 6, 45, 114, 115, 236, 69, 10, 199, 24, 180, 151, 193, 52, 73, 44, 67, 0, 7, 196, 67, 2, 238, 236, 65, 6, 195, 144, 82, 61, 66, 6, 195, 44, 243, 113, 66, 0, 9, 198, 77, 27, 210, 67, 171, 211, 67, 6, 195, 44, 100, 186, 65, 0, 9, 198, 60, 211, 196, 68, 21, 64, 67, 9, 198, 52, 105, 76, 60, 145, 64, 68, 9, 198, 8, 147, 196, 68, 21, 64, 67, 0, 10, 199, 44, 226, 68, 60, 240, 141, 192, 68, 6, 195, 188, 241, 64, 66, 0, 7, 196, 64, 146, 198, 76, 66, 7, 196, 197, 62, 198, 72, 67, 7, 196, 10, 208, 82, 76, 66, 0, 9, 198, 85, 67, 139, 92, 156, 251, 68, 8, 197, 79, 180, 48, 79, 16, 67, 8, 197, 64, 241, 78, 61, 32, 66, 8, 197, 67, 162, 198, 79, 16, 67, 8, 197, 67, 160, 69, 177, 32, 67, 12, 201, 48, 98, 210, 36, 179, 196, 68, 21, 64, 68, 8, 197, 9, 179, 4, 235, 16, 65, 0, 5, 194, 76, 144, 72, 5, 194, 80, 112, 72, 6, 194, 64, 240, 72, 23, 9, 198, 5, 36, 251, 60, 145, 64, 68, 0, 9, 198, 22, 209, 139, 227, 109, 69, 69, 0, 7, 196, 81, 140, 9, 44, 67, 7, 196, 149, 2, 87, 236, 67, 7, 196, 165, 94, 193, 76, 67, 7, 196, 66, 50, 193, 76, 66, 6, 195, 67, 165, 237, 66, 7, 196, 47, 53, 251, 56, 66, 0, 8, 197, 85, 179, 133, 108, 176, 66, 8, 197, 77, 245, 76, 24, 176, 66, 8, 197, 77, 180, 77, 108, 176, 66, 8, 197, 65, 18, 75, 140, 80, 66, 8, 197, 66, 126, 240, 36, 176, 66, 9, 198, 44, 193, 144, 76, 243, 111, 67, 8, 197, 180, 81, 150, 36, 80, 67, 0, 0, 6, 195, 87, 14, 192, 66, 0, 7, 196, 66, 107, 137, 204, 68, 7, 196, 53, 177, 105, 92, 66, 6, 195, 47, 209, 141, 66, 11, 200, 13, 177, 12, 27, 81, 125, 60, 80, 69, 7, 196, 212, 94, 15, 40, 67, 7, 196, 8, 99, 44, 244, 67, 0, 26, 3, 95, 208, 142, 39, 69, 34, 4, 35, 47, 36, 50, 15, 40, 70, 37, 82, 6, 37, 47, 36, 55, 36, 50, 0, 7, 2, 95, 3, 82, 13, 0, 12, 201, 99, 179, 143, 11, 212, 129, 20, 114, 96, 67, 8, 197, 47, 49, 131, 108, 80, 67, 9, 198, 21, 64, 140, 36, 176, 83, 67, 0, 28, 3, 95, 209, 151, 39, 69, 34, 4, 35, 47, 36, 50, 15, 82, 13, 48, 34, 39, 87, 6, 37, 47, 36, 55, 36, 50, 0, 0, 6, 2, 95, 1, 35, 0, 10, 199, 52, 97, 79, 20, 240, 137, 12, 67, 6, 195, 190, 211, 196, 67, 0, 6, 2, 95, 6, 36, 0, 11, 200, 72, 49, 147, 157, 180, 83, 24, 112, 68, 6, 195, 166, 162, 61, 67, 7, 196, 56, 243, 65, 20, 66, 7, 196, 10, 242, 198, 76, 66, 0, 8, 197, 89, 64, 166, 25, 112, 67, 6, 195, 87, 17, 146, 66, 8, 197, 60, 37, 131, 5, 48, 66, 0, 12, 3, 95, 209, 147, 81, 55, 39, 34, 37, 50, 0, 7, 2, 95, 4, 79, 13, 0, 9, 198, 72, 147, 80, 76, 243, 64, 66, 6, 195, 46, 210, 239, 66, 9, 198, 19, 17, 139, 60, 195, 196, 68, 9, 198, 168, 81, 143, 86, 227, 64, 68, 6, 195, 8, 145, 115, 66, 0, 6, 195, 149, 27, 192, 66, 6, 195, 144, 195, 196, 66, 6, 195, 55, 31, 64, 66, 0, 8, 196, 73, 13, 147, 36, 72, 23, 7, 196, 79, 99, 6, 40, 66, 7, 196, 72, 20, 20, 56, 66, 0, 14, 2, 95, 10, 6, 37, 49, 34, 4, 35, 47, 49, 39, 0, 8, 197, 87, 178, 66, 61, 48, 65, 8, 197, 67, 98, 212, 217, 16, 67, 8, 197, 65, 16, 89, 25, 112, 66, 8, 197, 67, 160, 80, 25, 48, 67, 8, 197, 44, 24, 21, 25, 48, 67, 8, 197, 180, 19, 113, 81, 48, 68, 0, 6, 2, 95, 9, 37, 0, 9, 198, 88, 245, 77, 233, 155, 64, 65, 9, 198, 84, 146, 9, 60, 195, 196, 68, 9, 198, 244, 226, 83, 60, 195, 196, 68, 0, 6, 195, 11, 2, 49, 66, 0, 0, 7, 196, 75, 17, 118, 52, 66, 7, 196, 45, 64, 137, 44, 66, 0, 8, 197, 76, 99, 204, 60, 64, 67, 0, 9, 198, 45, 44, 15, 84, 240, 128, 67, 9, 198, 20, 99, 9, 76, 99, 0, 65, 0, 6, 195, 144, 76, 192, 66, 6, 195, 168, 140, 192, 66, 0, 7, 2, 95, 18, 87, 13, 0, 11, 200, 96, 100, 195, 109, 20, 213, 198, 208, 68, 7, 196, 66, 147, 73, 236, 67, 7, 196, 5, 81, 139, 76, 66, 0, 8, 197, 52, 245, 137, 46, 240, 67, 0, 9, 198, 25, 34, 201, 52, 244, 128, 67, 9, 198, 20, 148, 252, 4, 208, 128, 67, 0, 10, 199, 84, 193, 132, 52, 20, 201, 44, 67, 10, 199, 64, 241, 80, 245, 70, 9, 44, 65, 9, 198, 20, 98, 15, 23, 219, 211, 68, 0, 7, 196, 79, 180, 201, 64, 66, 7, 196, 44, 194, 82, 232, 65, 7, 196, 24, 195, 65, 32, 66, 0, 9, 198, 73, 180, 87, 24, 49, 133, 67, 0, 6, 2, 95, 20, 40, 0, 9, 198, 5, 3, 210, 79, 101, 64, 67, 0, 10, 199, 88, 193, 130, 60, 137, 143, 20, 68, 10, 199, 72, 49, 147, 60, 82, 79, 20, 68, 0, 7, 196, 92, 146, 204, 204, 66, 6, 195, 28, 100, 243, 66, 7, 196, 11, 2, 15, 48, 66, 0, 8, 197, 68, 17, 73, 81, 32, 65, 6, 195, 19, 179, 202, 66, 0, 9, 198, 52, 97, 1, 91, 181, 192, 67, 0, 6, 195, 55, 162, 64, 72, 9, 198, 76, 101, 142, 177, 16, 83, 67, 9, 198, 72, 49, 147, 48, 243, 123, 67, 9, 198, 140, 164, 205, 61, 50, 67, 65, 0, 7, 196, 74, 226, 75, 204, 67, 7, 196, 15, 160, 250, 196, 65, 7, 196, 5, 37, 109, 76, 66, 7, 196, 180, 146, 58, 196, 68, 0, 8, 197, 44, 243, 15, 36, 80, 67, 8, 197, 25, 129, 141, 36, 176, 67, 0, 9, 198, 73, 62, 1, 20, 114, 96, 65, 9, 198, 64, 246, 129, 20, 114, 96, 65, 9, 198, 53, 69, 101, 20, 114, 96, 65, 9, 198, 33, 176, 143, 8, 243, 0, 67, 9, 198, 31, 180, 195, 192, 146, 192, 65, 0, 0, 13, 2, 95, 34, 49, 35, 82, 6, 37, 74, 49, 37, 0, 7, 196, 87, 99, 147, 204, 66, 6, 195, 51, 194, 75, 66, 7, 196, 16, 96, 196, 240, 66, 7, 196, 14, 222, 201, 188, 68, 6, 195, 8, 25, 83, 66, 6, 195, 10, 242, 251, 66, 9, 198, 5, 36, 246, 48, 241, 0, 67, 0, 16, 2, 95, 33, 40, 70, 37, 82, 6, 37, 47, 36, 55, 36, 50, 0, 8, 197, 73, 244, 83, 80, 176, 66, 12, 201, 66, 145, 89, 25, 36, 195, 192, 146, 192, 66, 9, 198, 66, 244, 207, 17, 16, 85, 67, 8, 197, 49, 73, 16, 232, 176, 65, 0, 9, 198, 86, 196, 147, 236, 158, 192, 68, 6, 195, 164, 191, 69, 66, 9, 198, 44, 149, 99, 20, 114, 96, 65, 0, 14, 2, 95, 39, 35, 48, 39, 87, 47, 34, 6, 39, 81, 0, 10, 199, 74, 48, 224, 56, 245, 79, 8, 68, 10, 199, 72, 99, 6, 45, 114, 115, 236, 69, 6, 195, 50, 203, 64, 66, 10, 199, 21, 180, 117, 20, 240, 137, 12, 67, 6, 195, 10, 251, 192, 66, 0, 15, 2, 95, 38, 35, 63, 48, 36, 34, 87, 6, 35, 50, 47, 0, 6, 195, 56, 150, 111, 66, 7, 196, 11, 160, 148, 56, 66, 0, 8, 197, 73, 67, 37, 145, 48, 67, 8, 197, 74, 226, 75, 5, 48, 67, 8, 197, 67, 100, 198, 73, 48, 66, 8, 197, 67, 160, 89, 81, 48, 67, 0, 6, 195, 140, 133, 17, 66, 9, 198, 45, 22, 196, 60, 143, 64, 67, 0, 6, 195, 46, 107, 64, 66, 0, 7, 196, 96, 147, 89, 240, 66, 11, 200, 47, 52, 209, 5, 80, 68, 61, 48, 68, 7, 196, 25, 145, 140, 204, 67, 7, 196, 16, 235, 143, 96, 66, 0, 18, 2, 95, 41, 114, 4, 35, 87, 50, 35, 15, 87, 49, 6, 39, 69, 35, 0, 8, 197, 89, 16, 66, 165, 112, 66, 0, 18, 2, 95, 40, 55, 38, 6, 35, 82, 35, 15, 87, 49, 6, 39, 69, 35, 0, 9, 198, 87, 212, 141, 4, 127, 64, 67, 9, 198, 24, 180, 147, 236, 159, 64, 68, 9, 198, 5, 36, 246, 56, 243, 64, 67, 0, 0, 11, 2, 95, 46, 47, 6, 39, 74, 49, 35, 0, 7, 196, 92, 146, 204, 224, 66, 7, 196, 88, 244, 198, 48, 66, 6, 195, 75, 206, 0, 66, 7, 196, 70, 181, 17, 72, 66, 7, 196, 52, 101, 148, 68, 66, 0, 10, 2, 95, 45, 47, 37, 34, 4, 36, 0, 8, 197, 160, 189, 140, 60, 64, 67, 8, 197, 8, 20, 134, 40, 224, 66, 0, 14, 2, 95, 44, 86, 35, 48, 36, 47, 6, 35, 57, 35, 0, 9, 198, 48, 98, 210, 36, 188, 192, 67, 9, 198, 5, 52, 73, 9, 68, 192, 67, 9, 198, 188, 67, 15, 84, 240, 128, 67, 0, 9, 2, 95, 51, 47, 34, 6, 37, 0, 6, 195, 34, 188, 192, 66, 6, 195, 30, 220, 192, 66, 10, 199, 17, 27, 197, 88, 244, 198, 48, 67, 0, 9, 2, 95, 50, 70, 82, 6, 36, 0, 7, 196, 64, 100, 147, 184, 66, 9, 198, 45, 16, 82, 59, 130, 82, 67, 7, 196, 46, 242, 66, 180, 67, 7, 196, 32, 19, 65, 88, 66, 7, 196, 24, 208, 74, 48, 66, 7, 196, 8, 241, 212, 68, 66, 0, 10, 2, 95, 49, 36, 70, 50, 6, 39, 0, 8, 197, 81, 99, 194, 60, 192, 67, 8, 197, 64, 148, 139, 80, 224, 66, 8, 197, 8, 20, 147, 80, 224, 66, 0, 10, 2, 95, 48, 50, 6, 40, 119, 35, 0, 6, 195, 64, 99, 49, 66, 9, 198, 44, 25, 81, 32, 148, 128, 65, 0, 11, 2, 95, 55, 87, 6, 36, 70, 36, 63, 0, 9, 198, 73, 99, 227, 73, 50, 75, 67, 6, 195, 55, 171, 48, 67, 0, 10, 2, 95, 54, 89, 6, 36, 87, 47, 0, 7, 196, 76, 147, 80, 188, 66, 7, 196, 72, 19, 70, 92, 66, 7, 196, 66, 52, 198, 28, 66, 7, 196, 197, 62, 195, 180, 67, 7, 196, 172, 59, 230, 76, 67, 0, 9, 2, 95, 53, 48, 6, 36, 47, 0, 9, 198, 76, 96, 83, 216, 49, 133, 68, 8, 197, 68, 18, 4, 159, 208, 65, 8, 197, 64, 243, 9, 19, 48, 67, 8, 197, 21, 179, 4, 81, 128, 66, 0, 12, 2, 95, 52, 74, 6, 36, 47, 37, 34, 37, 0, 0, 23, 2, 95, 59, 47, 4, 39, 74, 49, 35, 15, 37, 15, 86, 35, 48, 36, 47, 6, 35, 57, 35, 0, 10, 199, 61, 89, 76, 52, 243, 15, 16, 68, 0, 15, 2, 95, 58, 70, 82, 40, 36, 47, 6, 39, 74, 37, 36, 0, 11, 200, 28, 99, 6, 32, 240, 134, 79, 48, 69, 0, 11, 2, 95, 57, 70, 6, 36, 82, 36, 47, 0, 8, 197, 66, 149, 123, 189, 32, 67, 8, 197, 67, 2, 87, 187, 16, 68, 8, 197, 66, 242, 75, 119, 208, 67, 8, 197, 44, 243, 80, 165, 32, 66, 8, 197, 14, 49, 15, 55, 176, 67, 0, 10, 2, 95, 56, 6, 39, 87, 36, 63, 0, 6, 195, 8, 22, 129, 66, 0, 18, 2, 95, 63, 82, 13, 48, 34, 39, 87, 6, 37, 47, 36, 55, 36, 50, 0, 10, 199, 52, 193, 139, 60, 137, 143, 20, 68, 10, 199, 8, 22, 73, 8, 242, 20, 44, 68, 0, 16, 2, 95, 62, 48, 39, 15, 79, 39, 55, 38, 6, 35, 63, 39, 0, 7, 196, 164, 228, 201, 236, 67, 6, 195, 67, 192, 83, 66, 7, 196, 176, 18, 9, 204, 68, 7, 196, 44, 243, 65, 76, 66, 7, 196, 44, 241, 70, 196, 67, 9, 198, 36, 81, 143, 48, 241, 0, 68, 7, 196, 20, 243, 65, 76, 66, 0, 6, 195, 78, 197, 0, 66, 8, 197, 65, 18, 72, 144, 176, 65, 8, 197, 47, 98, 207, 22, 224, 67, 8, 197, 17, 16, 66, 24, 112, 66, 8, 197, 180, 187, 79, 36, 80, 68, 0, 14, 2, 95, 60, 48, 39, 15, 63, 6, 35, 55, 49, 39, 0, 6, 195, 79, 188, 0, 66, 9, 198, 32, 99, 48, 97, 66, 192, 67, 0, 10, 199, 44, 243, 80, 192, 82, 84, 52, 66, 6, 195, 23, 30, 128, 65, 0, 11, 200, 24, 193, 139, 79, 100, 54, 212, 80, 69, 0, 9, 198, 95, 18, 207, 17, 16, 85, 67, 9, 198, 73, 124, 15, 17, 16, 85, 67, 9, 198, 73, 60, 15, 17, 16, 85, 67, 9, 198, 64, 100, 147, 37, 114, 69, 67, 0, 0, 6, 195, 212, 187, 64, 66, 0, 7, 196, 148, 165, 84, 56, 66, 6, 195, 72, 149, 115, 66, 7, 196, 52, 146, 246, 8, 66, 7, 196, 49, 67, 113, 180, 67, 7, 196, 48, 100, 198, 28, 66, 7, 196, 46, 52, 157, 244, 66, 7, 196, 5, 51, 6, 76, 66, 7, 196, 175, 209, 93, 244, 67, 0, 8, 197, 165, 36, 6, 45, 48, 66, 8, 197, 46, 163, 147, 25, 48, 66, 8, 197, 5, 36, 6, 45, 48, 66, 0, 0, 10, 199, 77, 16, 80, 24, 131, 201, 20, 68, 6, 195, 148, 43, 192, 66, 6, 195, 144, 75, 192, 66, 6, 195, 48, 97, 48, 66, 9, 198, 44, 20, 134, 76, 245, 115, 68, 0, 7, 196, 67, 9, 68, 204, 67, 0, 8, 197, 72, 191, 66, 81, 48, 66, 0, 11, 66, 80, 192, 40, 55, 37, 115, 35, 0, 24, 9, 198, 19, 179, 111, 61, 91, 128, 68, 0, 9, 4, 95, 226, 128, 161, 21, 0, 10, 6, 195, 4, 64, 64, 66, 0, 9, 4, 95, 226, 128, 160, 21, 0, 10, 7, 196, 80, 226, 119, 56, 67, 7, 196, 64, 241, 66, 244, 66, 7, 196, 52, 244, 198, 48, 66, 7, 196, 44, 244, 198, 48, 66, 7, 196, 44, 19, 73, 204, 67, 6, 195, 46, 107, 123, 67, 9, 198, 25, 2, 83, 68, 21, 174, 68, 7, 196, 20, 100, 175, 76, 66, 0, 8, 197, 74, 83, 137, 60, 192, 67, 0, 18, 4, 95, 226, 128, 166, 63, 50, 39, 79, 39, 47, 6, 39, 74, 37, 36, 0, 9, 198, 81, 4, 102, 37, 49, 140, 66, 9, 198, 66, 145, 73, 44, 20, 192, 67, 9, 198, 20, 99, 108, 68, 20, 192, 67, 9, 198, 8, 102, 65, 52, 99, 0, 67, 6, 195, 234, 241, 253, 67, 9, 198, 189, 50, 83, 177, 44, 64, 68, 0, 10, 199, 161, 34, 248, 61, 35, 137, 44, 66, 10, 199, 36, 132, 17, 152, 148, 198, 48, 66, 6, 195, 233, 156, 64, 66, 0, 7, 196, 76, 244, 198, 52, 66, 7, 196, 64, 100, 198, 48, 66, 6, 195, 47, 97, 135, 66, 7, 196, 44, 19, 204, 196, 67, 6, 195, 5, 34, 251, 66, 0, 8, 197, 88, 147, 73, 46, 208, 67, 8, 197, 64, 241, 77, 60, 192, 66, 8, 197, 55, 178, 69, 38, 240, 68, 12, 201, 13, 177, 12, 25, 98, 69, 68, 20, 192, 68, 0, 9, 198, 68, 18, 3, 68, 20, 192, 66, 13, 202, 64, 241, 80, 164, 84, 134, 20, 20, 198, 48, 65, 9, 198, 197, 91, 147, 68, 20, 192, 67, 0, 6, 195, 96, 98, 72, 66, 0, 7, 196, 65, 179, 40, 28, 66, 7, 196, 52, 146, 246, 56, 66, 7, 196, 52, 100, 198, 28, 66, 7, 196, 8, 99, 79, 48, 66, 7, 196, 232, 16, 137, 128, 66, 0, 8, 197, 147, 97, 120, 37, 32, 68, 8, 197, 52, 146, 246, 87, 48, 67, 8, 197, 188, 20, 236, 75, 16, 68, 0, 0, 7, 195, 74, 145, 64, 72, 23, 29, 2, 95, 91, 55, 38, 4, 35, 82, 35, 15, 49, 82, 35, 70, 34, 4, 35, 47, 50, 35, 15, 87, 49, 6, 39, 69, 35, 0, 9, 198, 72, 149, 110, 37, 50, 75, 68, 6, 195, 173, 114, 72, 66, 0, 6, 195, 87, 160, 115, 67, 11, 200, 10, 209, 147, 52, 18, 146, 79, 208, 66, 0, 18, 4, 95, 226, 128, 147, 49, 4, 13, 87, 39, 15, 47, 37, 34, 6, 36, 0, 9, 198, 52, 20, 140, 227, 109, 69, 68, 8, 197, 21, 64, 140, 119, 208, 66, 8, 197, 175, 100, 147, 37, 96, 67, 8, 197, 153, 51, 194, 81, 32, 67, 0, 13, 202, 65, 34, 86, 61, 82, 72, 36, 243, 15, 16, 70, 0, 18, 2, 95, 95, 70, 4, 39, 55, 50, 35, 15, 74, 36, 34, 47, 6, 35, 0, 10, 199, 164, 228, 196, 192, 243, 15, 16, 68, 0, 6, 195, 130, 81, 47, 67, 6, 195, 34, 210, 67, 65, 0, 29, 2, 95, 93, 114, 4, 35, 87, 50, 35, 15, 49, 82, 35, 70, 34, 4, 35, 47, 50, 35, 15, 87, 49, 6, 39, 69, 35, 0, 8, 197, 8, 249, 78, 36, 176, 67, 0, 9, 198, 78, 146, 3, 192, 146, 192, 65, 0, 9, 198, 77, 244, 75, 60, 18, 0, 67, 6, 195, 150, 54, 64, 66, 6, 195, 160, 86, 196, 66, 9, 198, 8, 148, 148, 49, 80, 83, 67, 0, 19, 4, 95, 226, 128, 148, 70, 4, 13, 55, 79, 39, 15, 47, 37, 34, 6, 36, 0, 9, 198, 91, 99, 143, 48, 241, 0, 67, 7, 196, 64, 100, 18, 196, 66, 7, 196, 60, 36, 73, 12, 65, 7, 196, 60, 36, 65, 76, 66, 7, 196, 32, 21, 186, 196, 67, 9, 198, 9, 180, 72, 204, 241, 0, 67, 0, 8, 197, 65, 18, 72, 36, 48, 65, 8, 197, 66, 148, 147, 36, 112, 66, 8, 197, 8, 99, 19, 108, 176, 66, 8, 197, 4, 36, 148, 68, 80, 66, 0, 9, 2, 95, 96, 79, 34, 35, 81, 0, 9, 198, 77, 68, 205, 188, 146, 192, 65, 9, 198, 23, 130, 82, 56, 146, 192, 65, 0, 10, 199, 72, 191, 79, 73, 51, 137, 44, 65, 10, 199, 65, 16, 66, 108, 193, 58, 196, 66, 10, 199, 46, 148, 15, 73, 51, 137, 44, 65, 6, 195, 47, 219, 192, 66, 0, 6, 195, 88, 16, 187, 66, 7, 196, 64, 243, 80, 204, 66, 6, 195, 145, 101, 19, 66, 0, 8, 197, 85, 68, 75, 25, 48, 66, 8, 197, 67, 178, 82, 47, 128, 67, 8, 197, 153, 51, 210, 79, 128, 67, 0, 6, 195, 97, 64, 237, 66, 6, 195, 64, 102, 45, 66, 6, 195, 55, 166, 109, 66, 6, 195, 17, 72, 217, 66, 0, 10, 199, 73, 1, 139, 79, 100, 139, 224, 67, 9, 198, 64, 100, 6, 48, 226, 75, 67, 10, 199, 24, 193, 139, 79, 100, 139, 224, 68, 9, 198, 23, 48, 66, 244, 226, 75, 66, 0, 7, 196, 48, 146, 221, 244, 66, 7, 196, 44, 20, 198, 76, 66, 7, 196, 10, 196, 157, 244, 66, 0, 8, 197, 73, 58, 76, 25, 112, 66, 8, 197, 72, 193, 144, 25, 112, 66, 8, 197, 68, 18, 19, 213, 16, 66, 8, 197, 8, 241, 1, 149, 144, 67, 8, 197, 188, 98, 197, 61, 48, 67, 0, 6, 194, 96, 96, 72, 23, 9, 198, 68, 17, 73, 61, 111, 64, 68, 9, 198, 47, 52, 246, 49, 223, 64, 67, 0, 10, 199, 161, 68, 209, 180, 148, 198, 76, 69, 0, 7, 196, 84, 100, 147, 204, 66, 7, 196, 47, 49, 41, 72, 66, 7, 196, 44, 147, 73, 204, 67, 6, 195, 4, 74, 23, 66, 0, 12, 201, 64, 241, 84, 65, 25, 137, 76, 99, 0, 65, 8, 197, 18, 54, 65, 148, 160, 67, 9, 198, 153, 51, 205, 205, 55, 125, 68, 0, 6, 195, 14, 241, 109, 66, 9, 198, 5, 36, 246, 144, 52, 192, 67, 0, 6, 195, 67, 188, 192, 66, 9, 198, 52, 244, 207, 77, 18, 115, 68, 9, 198, 44, 243, 66, 196, 98, 51, 68, 0, 7, 196, 89, 179, 2, 176, 65, 7, 196, 175, 96, 129, 76, 67, 0, 8, 197, 68, 18, 2, 60, 160, 66, 8, 197, 10, 241, 123, 60, 192, 67, 0, 9, 198, 20, 100, 147, 184, 20, 192, 67, 9, 198, 9, 253, 139, 68, 20, 192, 67, 9, 198, 233, 98, 83, 24, 180, 192, 67, 0, 6, 195, 86, 191, 0, 66, 10, 199, 72, 198, 206, 96, 240, 145, 188, 67, 0, 7, 196, 66, 52, 198, 92, 66, 0, 8, 197, 77, 180, 66, 81, 96, 66, 8, 197, 46, 48, 198, 75, 16, 67, 0, 6, 195, 148, 182, 205, 66, 0, 32, 2, 95, 123, 55, 38, 4, 35, 82, 35, 15, 82, 13, 55, 50, 39, 4, 39, 69, 34, 35, 86, 50, 35, 15, 87, 49, 6, 39, 69, 35, 0, 9, 198, 36, 132, 207, 96, 226, 75, 65, 0, 7, 196, 78, 153, 7, 244, 67, 6, 195, 67, 52, 243, 66, 7, 196, 224, 98, 212, 56, 67, 9, 198, 55, 162, 198, 79, 17, 0, 65, 0, 8, 197, 47, 160, 66, 199, 176, 68, 8, 197, 20, 243, 79, 87, 48, 67, 0, 6, 195, 233, 44, 0, 66, 0, 6, 195, 46, 240, 80, 66, 6, 195, 184, 146, 192, 66, 0, 14, 2, 95, 126, 82, 13, 55, 50, 6, 37, 74, 49, 35, 0, 11, 200, 24, 193, 139, 79, 108, 71, 195, 176, 70, 9, 198, 233, 97, 143, 48, 241, 0, 68, 0, 32, 2, 95, 125, 114, 4, 35, 87, 50, 35, 15, 82, 13, 55, 50, 39, 4, 39, 69, 34, 35, 86, 50, 35, 15, 87, 49, 6, 39, 69, 35, 0, 8, 197, 88, 243, 59, 36, 176, 67, 0, 23, 2, 95, 124, 82, 36, 34, 47, 37, 49, 4, 35, 55, 50, 35, 15, 74, 36, 34, 47, 6, 35, 0, 6, 195, 84, 197, 61, 66, 6, 195, 75, 7, 125, 66, 9, 198, 67, 171, 73, 76, 146, 192, 68, 9, 198, 54, 189, 134, 32, 146, 192, 68, 9, 198, 32, 16, 166, 37, 49, 140, 66, 12, 201, 24, 193, 139, 79, 96, 68, 164, 64, 83, 70, 0, 6, 195, 80, 94, 128, 65, 10, 199, 77, 18, 84, 54, 164, 65, 76, 68, 0, 8, 196, 66, 196, 65, 40, 72, 23, 7, 196, 66, 116, 65, 76, 66, 6, 195, 61, 113, 147, 66, 7, 196, 52, 147, 111, 72, 66, 7, 196, 52, 19, 84, 48, 66, 7, 196, 44, 17, 111, 72, 66, 0, 11, 5, 95, 48, 97, 110, 100, 10, 2, 37, 0, 0, 9, 198, 64, 100, 147, 56, 146, 192, 66, 9, 198, 145, 10, 88, 56, 146, 192, 65, 9, 198, 20, 198, 199, 56, 146, 192, 66, 0, 10, 199, 72, 147, 80, 60, 130, 84, 52, 66, 9, 198, 67, 98, 248, 74, 242, 75, 66, 9, 198, 64, 244, 140, 25, 35, 39, 67, 10, 199, 34, 147, 15, 73, 51, 137, 44, 65, 0, 7, 196, 81, 36, 6, 88, 66, 7, 196, 148, 229, 221, 244, 66, 11, 200, 68, 20, 147, 192, 145, 131, 108, 80, 69, 7, 196, 48, 100, 198, 92, 66, 7, 196, 47, 212, 134, 76, 66, 7, 196, 44, 19, 91, 100, 66, 7, 196, 22, 148, 157, 244, 66, 7, 196, 9, 23, 232, 76, 66, 7, 196, 11, 172, 198, 76, 67, 0, 11, 200, 72, 209, 147, 44, 17, 71, 38, 0, 65, 8, 197, 75, 186, 147, 81, 48, 67, 12, 201, 68, 16, 143, 76, 245, 143, 48, 146, 192, 69, 12, 201, 64, 241, 80, 60, 194, 231, 56, 146, 192, 65, 0, 8, 197, 142, 49, 71, 38, 0, 65, 9, 198, 32, 19, 73, 73, 179, 0, 65, 0, 9, 198, 65, 177, 80, 108, 86, 203, 67, 9, 198, 65, 25, 134, 20, 226, 75, 65, 0, 7, 196, 61, 84, 134, 76, 66, 6, 195, 51, 218, 19, 66, 7, 196, 47, 161, 113, 180, 67, 7, 196, 16, 194, 68, 188, 66, 0, 11, 200, 66, 144, 209, 6, 81, 71, 38, 0, 66, 8, 197, 53, 68, 139, 25, 48, 66, 0, 9, 198, 88, 99, 9, 61, 34, 248, 68, 0, 10, 199, 88, 98, 211, 60, 68, 65, 84, 67, 0, 7, 196, 47, 209, 163, 76, 67, 7, 196, 36, 212, 61, 76, 66, 7, 196, 16, 96, 233, 44, 66, 11, 200, 189, 50, 69, 25, 10, 82, 189, 48, 69, 0, 8, 197, 61, 51, 204, 60, 64, 67, 8, 197, 246, 241, 20, 148, 224, 66, 6, 195, 144, 83, 202, 66, 8, 197, 46, 196, 198, 40, 192, 66, 8, 197, 5, 3, 15, 52, 32, 66, 0, 9, 198, 72, 99, 70, 20, 99, 0, 67, 13, 202, 68, 17, 73, 61, 49, 140, 24, 68, 65, 84, 70, 5, 194, 214, 208, 66, 0, 9, 198, 78, 146, 133, 124, 226, 115, 68, 0, 7, 196, 148, 225, 70, 52, 66, 7, 196, 73, 180, 134, 20, 66, 7, 196, 74, 84, 73, 44, 66, 6, 195, 66, 209, 135, 66, 7, 196, 48, 99, 84, 68, 66, 6, 195, 46, 247, 115, 66, 7, 196, 8, 97, 84, 196, 67, 0, 8, 197, 65, 18, 66, 60, 160, 66, 6, 195, 44, 248, 202, 66, 8, 197, 153, 51, 196, 60, 192, 67, 0, 0, 9, 198, 95, 161, 170, 96, 226, 75, 65, 10, 199, 73, 98, 72, 52, 20, 201, 44, 67, 0, 7, 196, 76, 99, 247, 84, 67, 7, 196, 64, 20, 147, 240, 66, 7, 196, 36, 82, 79, 52, 67, 11, 200, 20, 155, 70, 45, 51, 204, 60, 64, 69, 0, 8, 197, 44, 243, 15, 87, 48, 67, 6, 195, 44, 248, 206, 66, 0, 0, 10, 199, 73, 177, 12, 24, 80, 193, 96, 66, 9, 198, 72, 98, 212, 56, 91, 211, 67, 10, 199, 19, 100, 141, 4, 164, 147, 244, 65, 6, 195, 182, 53, 128, 66, 0, 7, 196, 77, 28, 79, 52, 66, 7, 196, 48, 144, 187, 180, 67, 6, 195, 236, 128, 87, 66, 0, 9, 198, 65, 33, 131, 23, 50, 77, 67, 6, 195, 55, 48, 86, 66, 8, 197, 46, 249, 81, 39, 48, 68, 0, 0, 6, 195, 164, 62, 192, 66, 10, 199, 20, 146, 6, 48, 211, 211, 244, 68, 9, 198, 8, 100, 243, 156, 242, 0, 68, 0, 7, 196, 73, 64, 240, 240, 67, 6, 195, 67, 210, 67, 65, 7, 196, 66, 196, 73, 12, 65, 7, 196, 66, 244, 137, 204, 67, 6, 195, 48, 101, 123, 66, 0, 9, 197, 73, 4, 96, 52, 240, 72, 23, 8, 197, 246, 82, 204, 108, 176, 67, 8, 197, 45, 179, 147, 24, 112, 66, 8, 197, 45, 18, 83, 36, 176, 66, 8, 197, 20, 144, 85, 184, 208, 67, 6, 195, 8, 21, 238, 66, 6, 195, 190, 240, 82, 67, 0, 9, 198, 64, 243, 20, 45, 22, 196, 67, 6, 195, 64, 97, 109, 66, 9, 198, 21, 177, 197, 60, 222, 192, 67, 9, 198, 22, 209, 139, 60, 222, 192, 68, 0, 6, 195, 32, 101, 124, 66, 0, 6, 195, 164, 85, 19, 66, 7, 196, 67, 213, 201, 204, 67, 7, 196, 52, 100, 201, 72, 66, 7, 196, 44, 21, 70, 32, 66, 7, 196, 44, 17, 81, 184, 66, 9, 198, 44, 17, 65, 73, 61, 142, 67, 11, 200, 36, 130, 212, 73, 61, 67, 24, 80, 68, 11, 200, 25, 36, 198, 73, 61, 67, 24, 80, 68, 6, 195, 18, 213, 115, 66, 0, 8, 197, 99, 202, 204, 108, 176, 67, 8, 197, 73, 58, 77, 24, 112, 66, 0, 9, 198, 52, 241, 70, 48, 158, 192, 68, 6, 195, 25, 41, 21, 66, 9, 198, 22, 144, 143, 73, 178, 192, 67, 0, 6, 195, 67, 195, 196, 66, 6, 195, 46, 251, 64, 66, 0, 7, 196, 96, 100, 198, 92, 66, 7, 196, 84, 99, 197, 180, 67, 7, 196, 86, 213, 198, 76, 66, 7, 196, 67, 197, 6, 76, 67, 7, 196, 52, 19, 84, 76, 66, 0, 11, 200, 64, 241, 54, 52, 17, 71, 38, 0, 66, 12, 201, 52, 18, 141, 80, 225, 71, 185, 178, 192, 68, 12, 201, 168, 81, 143, 20, 148, 144, 48, 98, 128, 69, 8, 197, 5, 11, 17, 37, 80, 67, 8, 197, 153, 51, 205, 5, 48, 67, 0, 9, 198, 20, 99, 60, 37, 67, 64, 66, 0, 6, 195, 67, 204, 88, 66, 0, 7, 195, 98, 146, 0, 72, 23, 7, 196, 75, 28, 201, 52, 67, 11, 200, 52, 244, 207, 92, 146, 204, 25, 48, 68, 7, 196, 55, 52, 221, 244, 66, 0, 8, 197, 76, 99, 123, 81, 48, 67, 8, 197, 74, 49, 75, 37, 144, 66, 8, 197, 67, 97, 84, 45, 48, 66, 8, 197, 45, 68, 12, 25, 48, 66, 8, 197, 32, 241, 17, 5, 80, 66, 8, 197, 5, 113, 147, 187, 0, 68, 8, 197, 4, 90, 82, 189, 48, 67, 0, 5, 194, 104, 96, 72, 9, 198, 88, 99, 9, 61, 61, 144, 68, 6, 195, 46, 119, 125, 66, 0, 7, 195, 74, 150, 148, 72, 23, 9, 198, 45, 22, 210, 79, 134, 211, 67, 0, 7, 195, 176, 243, 15, 72, 23, 11, 200, 72, 98, 72, 52, 241, 17, 5, 80, 68, 7, 196, 20, 100, 187, 76, 66, 0, 0, 9, 198, 17, 16, 71, 22, 252, 64, 65, 0, 6, 195, 5, 51, 204, 66, 0, 8, 196, 36, 128, 219, 56, 72, 23, 6, 195, 221, 4, 111, 66, 7, 196, 220, 193, 65, 76, 66, 7, 196, 74, 241, 91, 44, 66, 7, 196, 74, 189, 213, 204, 67, 7, 196, 164, 186, 134, 52, 67, 7, 196, 67, 182, 6, 52, 66, 0, 8, 197, 66, 148, 147, 60, 160, 66, 8, 197, 64, 20, 209, 80, 192, 66, 8, 197, 204, 179, 204, 60, 64, 67, 6, 195, 181, 54, 206, 66, 0, 9, 198, 76, 100, 6, 17, 211, 200, 67, 9, 198, 64, 243, 20, 18, 52, 128, 67, 6, 195, 64, 242, 61, 66, 6, 195, 55, 30, 237, 67, 9, 198, 36, 188, 207, 74, 84, 128, 68, 6, 195, 236, 76, 0, 66, 9, 198, 20, 19, 65, 72, 188, 64, 67, 0, 0, 7, 196, 55, 5, 6, 76, 67, 7, 196, 48, 149, 198, 40, 66, 11, 200, 48, 98, 210, 36, 179, 204, 60, 64, 68, 7, 196, 28, 19, 66, 204, 66, 0, 8, 197, 44, 19, 123, 39, 176, 68, 8, 197, 9, 26, 243, 39, 176, 68, 9, 198, 154, 249, 69, 28, 152, 0, 66, 0, 9, 198, 212, 83, 207, 79, 81, 64, 68, 0, 0, 7, 196, 86, 227, 247, 84, 67, 6, 195, 148, 212, 51, 66, 7, 196, 47, 196, 9, 96, 66, 7, 196, 47, 193, 9, 32, 66, 11, 200, 5, 37, 109, 76, 240, 134, 79, 48, 69, 0, 6, 195, 69, 178, 230, 66, 8, 197, 166, 181, 201, 207, 176, 69, 8, 197, 68, 18, 13, 5, 96, 66, 8, 197, 45, 43, 143, 87, 48, 67, 0, 6, 195, 44, 21, 25, 66, 0, 6, 195, 75, 16, 80, 66, 6, 195, 46, 238, 192, 66, 0, 6, 195, 87, 179, 111, 66, 7, 196, 36, 82, 79, 76, 67, 0, 8, 197, 73, 180, 66, 24, 112, 66, 8, 197, 67, 96, 140, 24, 208, 66, 8, 197, 44, 148, 240, 36, 176, 65, 8, 197, 13, 178, 22, 60, 80, 66, 0, 9, 198, 9, 180, 251, 86, 50, 128, 65, 0, 6, 195, 99, 208, 80, 66, 0, 7, 196, 74, 227, 205, 236, 67, 7, 196, 52, 97, 73, 44, 66, 6, 195, 54, 177, 147, 66, 7, 196, 33, 67, 20, 52, 66, 7, 196, 20, 240, 74, 192, 67, 6, 195, 12, 17, 51, 66, 7, 196, 5, 113, 147, 204, 67, 0, 9, 197, 13, 180, 41, 44, 144, 72, 23, 8, 197, 88, 145, 81, 36, 80, 66, 8, 197, 86, 240, 83, 36, 176, 67, 9, 198, 77, 18, 75, 60, 199, 125, 67, 8, 197, 72, 21, 81, 36, 80, 66, 8, 197, 52, 97, 73, 80, 208, 65, 6, 195, 196, 85, 18, 66, 0, 6, 195, 164, 193, 149, 66, 9, 198, 64, 18, 58, 49, 178, 192, 67, 0, 10, 199, 65, 16, 68, 52, 20, 201, 44, 67, 10, 199, 52, 193, 139, 204, 17, 79, 40, 68, 9, 198, 44, 243, 73, 72, 156, 251, 69, 0, 7, 196, 67, 172, 201, 52, 67, 6, 195, 66, 209, 147, 66, 7, 196, 44, 204, 241, 16, 66, 7, 196, 44, 20, 212, 56, 66, 0, 8, 197, 52, 148, 139, 25, 48, 66, 9, 198, 44, 25, 69, 28, 152, 0, 65, 8, 197, 44, 17, 65, 37, 80, 67, 8, 197, 21, 64, 140, 25, 48, 66, 8, 197, 22, 225, 165, 57, 48, 67, 0, 9, 198, 24, 194, 72, 37, 67, 64, 66, 6, 195, 4, 213, 17, 66, 0, 6, 195, 148, 59, 192, 66, 6, 195, 72, 20, 252, 66, 6, 195, 214, 51, 128, 66, 0, 7, 196, 72, 20, 21, 240, 66, 9, 198, 52, 105, 76, 81, 17, 0, 67, 9, 198, 19, 179, 111, 61, 83, 194, 68, 0, 6, 195, 164, 74, 82, 66, 8, 197, 20, 148, 144, 81, 48, 66, 0, 10, 66, 96, 192, 74, 55, 36, 50, 0, 24, 6, 195, 164, 59, 217, 66, 0, 0, 7, 196, 73, 55, 250, 20, 66, 11, 200, 73, 1, 139, 79, 97, 17, 5, 80, 67, 7, 196, 45, 68, 148, 68, 66, 0, 9, 198, 79, 58, 71, 37, 39, 125, 68, 8, 197, 68, 144, 143, 50, 112, 67, 8, 197, 9, 67, 123, 188, 64, 67, 0, 9, 198, 44, 243, 112, 22, 244, 192, 67, 0, 7, 195, 4, 208, 64, 72, 23, 10, 199, 72, 97, 77, 37, 131, 137, 44, 65, 10, 199, 32, 243, 211, 25, 99, 137, 44, 68, 0, 7, 196, 246, 83, 27, 44, 67, 7, 196, 56, 253, 246, 16, 67, 7, 196, 30, 241, 122, 52, 66, 0, 8, 197, 99, 163, 197, 24, 160, 67, 6, 195, 79, 100, 238, 66, 8, 197, 66, 148, 147, 60, 192, 66, 8, 197, 32, 195, 197, 24, 160, 66, 8, 197, 169, 20, 212, 60, 128, 67, 0, 9, 198, 72, 98, 210, 148, 228, 192, 66, 9, 198, 36, 210, 68, 70, 244, 192, 67, 9, 198, 24, 210, 68, 70, 244, 192, 67, 0, 14, 67, 16, 241, 64, 79, 39, 70, 6, 37, 50, 35, 0, 24, 6, 195, 5, 56, 200, 66, 0, 6, 195, 150, 51, 147, 66, 7, 196, 58, 192, 84, 76, 65, 6, 195, 44, 18, 47, 66, 7, 196, 13, 178, 36, 44, 65, 0, 6, 195, 16, 241, 70, 65, 8, 197, 164, 191, 69, 119, 208, 67, 8, 197, 16, 244, 147, 195, 16, 65, 0, 0, 7, 195, 64, 241, 64, 72, 23, 9, 198, 47, 52, 148, 50, 83, 147, 67, 0, 6, 195, 76, 145, 47, 66, 7, 196, 149, 27, 70, 28, 67, 0, 8, 197, 64, 20, 137, 189, 32, 67, 6, 195, 5, 56, 210, 66, 0, 9, 198, 91, 176, 137, 92, 145, 64, 67, 9, 198, 48, 148, 147, 224, 17, 64, 67, 9, 198, 25, 33, 183, 12, 101, 192, 66, 9, 198, 9, 22, 211, 12, 97, 192, 66, 0, 9, 198, 61, 82, 87, 36, 242, 0, 68, 9, 198, 197, 84, 65, 32, 53, 11, 65, 6, 195, 21, 65, 140, 66, 0, 7, 196, 77, 26, 229, 76, 66, 0, 8, 197, 96, 98, 209, 108, 176, 66, 8, 197, 73, 177, 108, 140, 80, 67, 8, 197, 73, 67, 21, 36, 80, 66, 8, 197, 24, 212, 60, 36, 176, 67, 0, 9, 198, 72, 19, 79, 76, 98, 192, 67, 9, 198, 12, 99, 8, 24, 53, 12, 67, 0, 0, 7, 196, 52, 100, 207, 88, 66, 7, 196, 46, 145, 73, 76, 65, 12, 201, 197, 36, 209, 80, 220, 37, 68, 149, 13, 68, 9, 198, 20, 99, 65, 16, 241, 0, 67, 0, 8, 197, 73, 59, 39, 24, 80, 67, 8, 197, 29, 179, 19, 108, 176, 66, 8, 197, 16, 241, 112, 36, 176, 67, 0, 6, 195, 4, 80, 89, 66, 0, 9, 198, 68, 21, 129, 76, 198, 203, 67, 6, 195, 34, 211, 196, 66, 0, 7, 196, 96, 17, 91, 68, 66, 7, 196, 45, 246, 6, 44, 66, 6, 195, 44, 20, 47, 66, 7, 196, 197, 62, 201, 244, 68, 6, 195, 21, 65, 147, 66, 7, 196, 11, 212, 148, 44, 66, 0, 8, 197, 52, 97, 38, 5, 48, 67, 8, 197, 45, 180, 141, 25, 48, 66, 0, 6, 195, 233, 44, 45, 67, 0, 10, 199, 80, 196, 209, 4, 128, 212, 44, 67, 9, 198, 64, 148, 147, 60, 193, 147, 67, 0, 7, 196, 148, 34, 70, 76, 67, 11, 200, 68, 17, 73, 60, 20, 58, 5, 48, 70, 7, 196, 53, 67, 133, 240, 66, 7, 196, 45, 190, 70, 28, 66, 0, 9, 198, 77, 21, 2, 4, 85, 17, 67, 8, 197, 197, 60, 5, 189, 48, 67, 8, 197, 9, 22, 205, 11, 160, 65, 0, 9, 198, 68, 18, 18, 78, 147, 0, 66, 6, 195, 18, 211, 217, 66, 9, 198, 152, 147, 205, 61, 63, 64, 69, 0, 6, 195, 67, 213, 124, 66, 6, 195, 24, 178, 80, 66, 0, 8, 196, 73, 15, 70, 20, 72, 23, 6, 195, 86, 50, 243, 66, 7, 196, 141, 74, 65, 76, 68, 9, 198, 9, 179, 4, 232, 245, 110, 68, 0, 0, 9, 198, 64, 244, 147, 82, 52, 192, 67, 5, 194, 226, 208, 66, 9, 198, 44, 62, 147, 242, 244, 192, 67, 9, 198, 20, 100, 41, 74, 244, 192, 67, 0, 6, 195, 91, 28, 64, 66, 6, 195, 67, 204, 192, 66, 10, 199, 145, 145, 146, 76, 60, 9, 44, 66, 0, 7, 196, 36, 132, 73, 12, 65, 7, 196, 18, 220, 9, 44, 65, 7, 196, 13, 67, 11, 188, 66, 7, 196, 212, 83, 198, 52, 67, 0, 0, 6, 195, 98, 214, 205, 66, 9, 198, 84, 145, 20, 70, 244, 192, 67, 6, 195, 72, 178, 125, 66, 9, 198, 68, 18, 23, 12, 100, 192, 66, 9, 198, 44, 243, 73, 76, 100, 192, 67, 9, 198, 20, 98, 210, 77, 28, 64, 66, 9, 198, 8, 147, 205, 37, 124, 64, 68, 0, 10, 199, 86, 214, 73, 84, 146, 193, 76, 68, 9, 198, 75, 176, 134, 32, 198, 203, 67, 10, 199, 52, 20, 198, 52, 20, 201, 44, 68, 0, 7, 196, 84, 150, 70, 44, 66, 7, 196, 77, 180, 232, 28, 66, 6, 195, 216, 35, 211, 66, 0, 8, 197, 47, 53, 227, 19, 176, 65, 0, 9, 198, 47, 49, 136, 152, 241, 64, 68, 9, 198, 44, 148, 134, 48, 101, 192, 65, 9, 198, 16, 243, 6, 52, 101, 192, 67, 0, 0, 7, 196, 54, 246, 70, 76, 66, 7, 196, 44, 20, 207, 20, 66, 7, 196, 197, 37, 12, 76, 66, 11, 200, 24, 193, 139, 79, 99, 79, 79, 208, 69, 0, 6, 195, 87, 57, 78, 66, 8, 197, 48, 97, 9, 207, 176, 68, 8, 197, 44, 244, 177, 81, 32, 65, 0, 6, 195, 66, 224, 85, 66, 9, 198, 47, 160, 77, 8, 243, 0, 67, 9, 198, 153, 51, 200, 152, 241, 64, 68, 0, 6, 195, 67, 217, 76, 66, 9, 198, 189, 50, 85, 68, 146, 0, 67, 0, 7, 196, 141, 49, 139, 72, 66, 0, 8, 197, 36, 67, 48, 36, 176, 67, 8, 197, 32, 60, 39, 60, 80, 67, 9, 198, 28, 157, 83, 58, 118, 197, 68, 0, 6, 195, 75, 23, 125, 66, 0, 9, 198, 73, 64, 140, 36, 208, 83, 67, 0, 9, 198, 67, 100, 207, 43, 177, 138, 68, 9, 198, 52, 227, 196, 60, 35, 202, 67, 9, 198, 237, 117, 187, 92, 241, 0, 67, 9, 198, 23, 1, 118, 48, 241, 0, 67, 0, 9, 198, 92, 99, 20, 48, 242, 69, 68, 9, 198, 66, 146, 9, 20, 149, 13, 66, 8, 197, 25, 144, 85, 60, 80, 67, 0, 6, 195, 44, 18, 89, 66, 0, 9, 198, 67, 101, 82, 109, 242, 0, 67, 0, 7, 196, 72, 20, 29, 244, 66, 7, 196, 66, 52, 157, 244, 66, 7, 196, 66, 244, 198, 204, 67, 6, 195, 66, 98, 111, 67, 7, 196, 61, 54, 6, 76, 66, 11, 200, 13, 177, 12, 24, 83, 194, 36, 48, 67, 6, 195, 11, 165, 19, 66, 0, 6, 18, 66, 208, 181, 0, 209, 144, 0, 208, 184, 0, 209, 157, 0, 7, 6, 18, 67, 209, 128, 0, 208, 187, 0, 208, 188, 0, 208, 189, 0, 7, 6, 18, 68, 208, 180, 208, 183, 0, 208, 180, 208, 182, 0, 208, 177, 0, 208, 178, 0, 208, 179, 0, 208, 180, 0, 208, 183, 0, 208, 182, 0, 7, 6, 18, 69, 208, 191, 0, 209, 132, 0, 208, 186, 0, 209, 130, 0, 209, 129, 0, 209, 134, 0, 209, 136, 0, 209, 137, 0, 209, 135, 0, 209, 133, 0, 7, 6, 1, 17, 0, 209, 128, 1, 21, 2, 32, 3, 6, 35, 34, 0, 209, 130, 208, 181, 208, 187, 208, 181, 208, 189, 1, 21, 2, 32, 3, 6, 35, 47, 36, 55, 36, 50, 0, 209, 130, 208, 181, 208, 187, 209, 129, 209, 130, 208, 178, 208, 190, 1, 21, 2, 32, 3, 6, 35, 47, 36, 55, 87, 47, 82, 39, 0, 208, 186, 1, 21, 2, 32, 3, 6, 35, 49, 0, 208, 189, 208, 184, 208, 181, 1, 21, 2, 32, 3, 6, 35, 50, 37, 36, 0, 208, 189, 209, 129, 208, 186, 208, 184, 1, 21, 2, 32, 3, 6, 35, 50, 87, 49, 37, 0, 208, 187, 208, 181, 208, 189, 1, 21, 2, 32, 3, 6, 35, 55, 36, 50, 0, 208, 187, 208, 184, 209, 137, 208, 181, 1, 21, 2, 32, 3, 6, 35, 55, 37, 89, 47, 36, 0, 208, 187, 208, 189, 209, 143, 1, 21, 2, 32, 3, 6, 35, 55, 50, 38, 35, 0, 209, 135, 1, 21, 2, 32, 3, 6, 35, 74, 0, 208, 178, 208, 184, 209, 137, 208, 181, 1, 21, 2, 32, 3, 6, 35, 82, 37, 89, 47, 36, 0, 208, 182, 1, 21, 2, 32, 3, 6, 35, 88, 0, 209, 134, 208, 184, 209, 143, 1, 21, 2, 32, 3, 6, 35, 115, 37, 35, 0, 4, 3, 35, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 209, 128, 208, 184, 209, 143, 1, 21, 2, 32, 3, 35, 34, 37, 35, 0, 7, 6, 1, 18, 0, 3, 69, 0, 2, 17, 71, 3, 69, 38, 0, 7, 6, 1, 19, 0, 3, 82, 0, 2, 17, 71, 3, 82, 38, 0, 7, 6, 1, 20, 0, 3, 79, 0, 2, 17, 71, 3, 121, 0, 7, 6, 1, 21, 0, 3, 70, 0, 208, 182, 3, 73, 0, 2, 17, 71, 3, 114, 0, 208, 183, 3, 116, 0, 208, 183, 2, 17, 71, 3, 116, 38, 0, 7, 6, 1, 22, 0, 208, 181, 208, 189, 1, 21, 2, 32, 3, 6, 36, 36, 50, 0, 208, 189, 208, 184, 208, 181, 1, 21, 2, 32, 3, 6, 36, 50, 37, 36, 0, 208, 189, 209, 130, 1, 21, 2, 32, 3, 6, 36, 50, 47, 0, 208, 185, 209, 129, 208, 186, 208, 184, 1, 21, 2, 32, 3, 6, 36, 57, 87, 49, 37, 0, 208, 177, 208, 181, 208, 189, 1, 21, 2, 32, 3, 6, 36, 69, 36, 50, 0, 208, 178, 208, 181, 208, 189, 1, 21, 2, 32, 3, 6, 36, 82, 36, 50, 0, 3, 36, 0, 7, 6, 1, 23, 0, 3, 88, 0, 7, 6, 1, 24, 0, 3, 86, 0, 2, 17, 71, 3, 92, 0, 7, 6, 1, 25, 0, 4, 1, 130, 209, 190, 208, 2, 209, 143, 32, 3, 6, 37, 0, 1, 186, 208, 2, 208, 189, 209, 143, 32, 0, 209, 130, 1, 21, 2, 32, 3, 6, 37, 47, 0, 209, 130, 208, 181, 208, 187, 1, 21, 2, 32, 3, 6, 37, 47, 36, 55, 0, 209, 130, 208, 181, 208, 187, 208, 181, 208, 189, 1, 21, 2, 32, 3, 6, 37, 47, 36, 55, 36, 50, 0, 208, 180, 208, 177, 208, 176, 1, 21, 2, 32, 3, 6, 37, 47, 69, 35, 0, 208, 186, 208, 176, 208, 178, 1, 21, 2, 32, 3, 6, 37, 49, 35, 82, 0, 208, 189, 209, 129, 208, 186, 208, 184, 1, 21, 2, 32, 3, 6, 37, 50, 87, 49, 37, 0, 208, 187, 208, 181, 208, 189, 1, 21, 2, 32, 3, 6, 37, 55, 36, 50, 0, 208, 187, 208, 184, 209, 137, 208, 181, 1, 21, 2, 32, 3, 6, 37, 55, 37, 89, 47, 36, 0, 208, 188, 208, 176, 1, 21, 2, 32, 3, 6, 37, 63, 35, 0, 209, 135, 208, 181, 209, 129, 208, 186, 208, 184, 1, 21, 2, 32, 3, 6, 37, 74, 36, 87, 49, 37, 0, 208, 178, 1, 21, 2, 32, 3, 6, 37, 82, 0, 208, 178, 208, 181, 208, 189, 1, 21, 2, 32, 3, 6, 37, 82, 36, 50, 0, 208, 183, 209, 138, 208, 188, 1, 21, 2, 32, 3, 6, 37, 86, 13, 63, 0, 209, 129, 209, 130, 1, 21, 2, 32, 3, 6, 37, 87, 47, 0, 3, 37, 0, 2, 32, 24, 3, 37, 12, 0, 7, 6, 1, 26, 0, 3, 57, 0, 7, 6, 1, 27, 0, 3, 49, 0, 2, 17, 71, 3, 49, 38, 0, 208, 190, 1, 21, 2, 32, 14, 128, 128, 130, 3, 49, 39, 0, 7, 6, 1, 28, 0, 4, 2, 17, 71, 3, 55, 0, 2, 18, 66, 0, 2, 209, 140, 18, 66, 3, 61, 0, 3, 119, 0, 7, 6, 1, 29, 0, 3, 63, 0, 2, 17, 71, 3, 63, 38, 0, 7, 6, 1, 30, 0, 3, 50, 0, 208, 189, 3, 50, 12, 0, 2, 17, 71, 3, 65, 0, 7, 6, 1, 31, 0, 209, 128, 208, 184, 209, 131, 208, 188, 1, 21, 2, 32, 3, 6, 39, 34, 37, 40, 63, 0, 208, 186, 1, 21, 2, 32, 3, 6, 39, 49, 0, 208, 178, 208, 181, 208, 189, 1, 21, 2, 32, 3, 6, 39, 82, 36, 50, 0, 208, 178, 208, 184, 209, 137, 208, 181, 1, 21, 2, 32, 3, 6, 39, 82, 37, 89, 47, 36, 0, 208, 178, 208, 189, 208, 184, 208, 186, 1, 21, 2, 32, 3, 6, 39, 82, 50, 37, 49, 0, 208, 183, 208, 181, 208, 189, 2, 32, 3, 6, 39, 86, 36, 50, 0, 3, 39, 0, 208, 178, 208, 176, 2, 209, 130, 32, 3, 39, 82, 6, 35, 0, 208, 178, 208, 184, 2, 209, 130, 32, 3, 39, 82, 6, 37, 0, 7, 6, 1, 32, 0, 3, 48, 0, 2, 17, 71, 3, 48, 38, 0, 7, 6, 1, 33, 0, 3, 34, 0, 2, 17, 71, 3, 34, 38, 0, 7, 6, 1, 34, 0, 3, 87, 0, 2, 17, 71, 3, 93, 0, 7, 6, 1, 35, 0, 3, 47, 0, 209, 130, 3, 47, 12, 0, 208, 176, 1, 21, 2, 32, 14, 128, 128, 130, 3, 47, 35, 0, 208, 181, 1, 21, 2, 32, 14, 128, 128, 130, 3, 47, 36, 0, 2, 17, 71, 3, 113, 0, 7, 6, 1, 36, 0, 3, 40, 0, 7, 6, 1, 37, 0, 3, 81, 0, 2, 17, 71, 3, 81, 38, 0, 7, 6, 1, 38, 0, 4, 2, 17, 71, 3, 97, 0, 2, 208, 184, 0, 3, 99, 0, 7, 6, 1, 39, 0, 3, 115, 0, 2, 17, 71, 3, 115, 38, 0, 7, 6, 1, 40, 0, 208, 190, 1, 21, 2, 32, 3, 8, 74, 39, 0, 3, 74, 0, 7, 6, 1, 41, 0, 3, 89, 0, 7, 6, 1, 42, 0, 3, 89, 47, 0, 2, 17, 71, 3, 89, 113, 0, 7, 6, 1, 43, 0, 3, 13, 0, 209, 130, 1, 21, 2, 32, 14, 128, 128, 130, 3, 13, 47, 0, 7, 6, 1, 45, 0, 1, 17, 67, 3, 0, 3, 57, 0, 7, 6, 1, 47, 0, 1, 17, 67, 3, 40, 0, 3, 57, 40, 0, 7, 6, 1, 48, 0, 208, 189, 208, 184, 208, 181, 1, 21, 2, 32, 3, 6, 57, 35, 50, 37, 36, 0, 4, 1, 17, 67, 3, 35, 0, 1, 17, 67, 21, 2, 32, 14, 128, 192, 129, 0, 209, 130, 1, 17, 67, 21, 2, 32, 14, 128, 192, 130, 3, 35, 47, 0, 4, 3, 57, 35, 0, 1, 21, 2, 32, 14, 128, 192, 129, 0, 209, 130, 1, 21, 2, 32, 14, 128, 192, 130, 3, 57, 35, 47, 0, 7, 6, 0, 209, 144, 3, 7, 36, 0, 209, 157, 3, 7, 37, 0, 204, 128, 3, 8, 0, 36, 3, 70, 6, 39, 119, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts5 = FileInMemory_createWithData (26954, reinterpret_cast (&espeakdata_dicts5_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/bg_dict", L"bg"); Collection_addItem (me.peek(), espeakdata_dicts5.transfer()); static unsigned char espeakdata_dicts6_data[2830] = { 0, 4, 0, 0, 8, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 32, 15, 0, 0, 48, 0, 0, 0, 33, 15, 0, 0, 49, 0, 0, 0, 34, 15, 0, 0, 50, 0, 0, 0, 35, 15, 0, 0, 51, 0, 0, 0, 36, 15, 0, 0, 52, 0, 0, 0, 37, 15, 0, 0, 53, 0, 0, 0, 38, 15, 0, 0, 54, 0, 0, 0, 39, 15, 0, 0, 55, 0, 0, 0, 40, 15, 0, 0, 56, 0, 0, 0, 41, 15, 0, 0, 57, 0, 0, 0, 0, 0, 0, 0, 6, 1, 65, 0, 4, 1, 21, 2, 32, 3, 49, 0, 2, 17, 66, 0, 3, 49, 35, 0, 7, 6, 1, 66, 0, 4, 1, 21, 2, 32, 3, 144, 0, 2, 17, 66, 0, 3, 144, 35, 0, 7, 6, 1, 67, 0, 4, 1, 21, 2, 32, 3, 79, 0, 2, 17, 66, 0, 3, 79, 35, 0, 7, 6, 1, 68, 0, 4, 1, 21, 2, 32, 3, 145, 0, 2, 17, 66, 0, 3, 145, 35, 0, 7, 6, 1, 69, 0, 4, 1, 21, 2, 32, 3, 66, 0, 2, 17, 66, 0, 3, 66, 35, 0, 7, 6, 1, 70, 0, 4, 1, 21, 2, 32, 3, 78, 0, 2, 17, 66, 0, 3, 78, 35, 0, 7, 6, 1, 71, 0, 4, 1, 21, 2, 32, 3, 142, 0, 2, 17, 66, 0, 3, 142, 35, 0, 7, 6, 1, 72, 0, 4, 1, 21, 2, 32, 3, 77, 0, 2, 17, 66, 0, 3, 77, 35, 0, 7, 6, 1, 74, 0, 4, 1, 21, 2, 32, 3, 65, 0, 2, 17, 66, 0, 3, 65, 35, 0, 7, 6, 1, 75, 0, 4, 1, 21, 2, 32, 3, 138, 0, 2, 17, 66, 0, 3, 138, 35, 0, 7, 6, 1, 76, 0, 4, 1, 21, 2, 32, 3, 140, 0, 2, 17, 66, 0, 3, 140, 35, 0, 7, 6, 1, 77, 0, 4, 1, 21, 2, 32, 3, 139, 0, 2, 17, 66, 0, 3, 139, 35, 0, 7, 6, 1, 78, 0, 4, 1, 21, 2, 32, 3, 141, 0, 2, 17, 66, 0, 3, 141, 35, 0, 7, 6, 1, 79, 0, 4, 1, 21, 2, 32, 3, 64, 0, 2, 17, 66, 0, 3, 64, 35, 0, 7, 6, 1, 80, 0, 4, 1, 21, 2, 32, 3, 47, 0, 2, 17, 66, 0, 3, 47, 35, 0, 7, 6, 1, 81, 0, 4, 1, 21, 2, 32, 3, 136, 0, 2, 17, 66, 0, 3, 136, 35, 0, 7, 6, 1, 82, 0, 4, 1, 21, 2, 32, 3, 70, 0, 2, 17, 66, 0, 3, 70, 35, 0, 7, 6, 1, 83, 0, 4, 1, 21, 2, 32, 3, 137, 0, 2, 17, 66, 0, 3, 137, 35, 0, 7, 6, 1, 84, 0, 4, 1, 21, 2, 32, 3, 50, 0, 2, 17, 66, 0, 3, 50, 35, 0, 7, 6, 1, 85, 0, 4, 1, 21, 2, 32, 3, 48, 0, 2, 17, 66, 0, 3, 48, 35, 0, 7, 6, 1, 86, 0, 4, 1, 21, 2, 32, 3, 134, 0, 2, 17, 66, 0, 3, 134, 35, 0, 7, 6, 1, 87, 0, 4, 1, 21, 2, 32, 3, 69, 0, 2, 17, 66, 0, 3, 69, 35, 0, 7, 6, 1, 88, 0, 4, 1, 21, 2, 32, 3, 135, 0, 2, 17, 66, 0, 3, 135, 35, 0, 7, 6, 1, 89, 0, 4, 1, 21, 2, 32, 3, 63, 0, 2, 17, 66, 0, 3, 63, 35, 0, 7, 6, 1, 90, 0, 4, 1, 21, 2, 32, 3, 147, 0, 2, 17, 66, 0, 3, 147, 35, 0, 7, 6, 1, 91, 0, 4, 1, 21, 2, 32, 3, 149, 0, 2, 17, 66, 0, 3, 149, 35, 0, 7, 6, 1, 92, 0, 4, 1, 21, 2, 32, 3, 148, 0, 2, 17, 66, 0, 3, 148, 35, 0, 7, 6, 1, 93, 0, 4, 1, 21, 2, 32, 3, 150, 0, 2, 17, 66, 0, 3, 150, 35, 0, 7, 6, 1, 94, 0, 4, 1, 21, 2, 32, 3, 58, 0, 2, 17, 66, 0, 3, 58, 35, 0, 7, 6, 1, 95, 0, 4, 1, 21, 2, 32, 3, 88, 0, 2, 17, 66, 0, 3, 88, 35, 0, 7, 6, 1, 96, 0, 4, 1, 21, 2, 32, 3, 86, 0, 2, 17, 66, 0, 3, 86, 35, 0, 7, 6, 1, 97, 0, 4, 1, 21, 2, 32, 3, 19, 0, 2, 17, 66, 0, 3, 19, 35, 0, 7, 6, 1, 98, 0, 4, 1, 21, 2, 32, 3, 57, 0, 2, 17, 66, 0, 3, 57, 35, 0, 7, 6, 1, 99, 0, 4, 1, 21, 2, 32, 3, 34, 0, 2, 17, 66, 0, 3, 34, 35, 0, 7, 6, 1, 100, 0, 4, 1, 21, 2, 32, 3, 55, 0, 2, 17, 66, 0, 3, 55, 35, 0, 7, 6, 1, 101, 0, 4, 1, 21, 2, 32, 3, 89, 0, 2, 17, 66, 0, 3, 89, 35, 0, 7, 6, 1, 102, 0, 4, 1, 21, 2, 32, 3, 91, 0, 2, 17, 66, 0, 3, 91, 35, 0, 7, 6, 1, 103, 0, 4, 1, 21, 2, 32, 3, 87, 0, 2, 17, 66, 0, 3, 87, 35, 0, 7, 6, 1, 104, 0, 4, 1, 21, 2, 32, 3, 106, 0, 2, 17, 66, 0, 3, 106, 35, 0, 7, 6, 1, 105, 0, 4, 1, 21, 2, 32, 3, 19, 0, 2, 17, 66, 0, 3, 19, 35, 0, 7, 6, 1, 106, 0, 4, 1, 21, 2, 32, 3, 49, 91, 0, 2, 17, 66, 0, 3, 49, 91, 35, 0, 7, 6, 224, 189, 0, 186, 3, 36, 0, 178, 3, 37, 0, 188, 3, 39, 0, 180, 3, 40, 0, 182, 3, 44, 0, 183, 3, 44, 12, 0, 184, 3, 45, 0, 185, 3, 45, 12, 0, 179, 3, 110, 0, 187, 3, 112, 0, 177, 3, 116, 0, 189, 3, 117, 0, 181, 3, 121, 0, 7, 6, 224, 190, 0, 4, 176, 1, 21, 2, 32, 3, 19, 0, 176, 2, 17, 66, 0, 184, 1, 21, 2, 32, 0, 184, 2, 17, 66, 0, 4, 176, 3, 19, 35, 0, 184, 0, 4, 178, 1, 21, 2, 32, 3, 34, 0, 178, 2, 17, 66, 0, 178, 3, 34, 35, 0, 4, 159, 1, 21, 2, 32, 3, 47, 0, 159, 2, 17, 66, 0, 159, 3, 47, 35, 0, 4, 164, 1, 21, 2, 32, 3, 48, 0, 164, 2, 17, 66, 0, 164, 3, 48, 35, 0, 4, 144, 1, 21, 2, 32, 3, 49, 0, 144, 2, 17, 66, 0, 144, 3, 49, 35, 0, 4, 185, 1, 21, 2, 32, 3, 49, 91, 0, 185, 2, 17, 66, 0, 185, 3, 49, 91, 35, 0, 4, 163, 1, 21, 2, 32, 3, 50, 0, 163, 2, 17, 66, 0, 163, 3, 50, 35, 0, 4, 179, 1, 21, 2, 32, 3, 55, 0, 179, 2, 17, 66, 0, 179, 3, 55, 35, 0, 4, 177, 1, 21, 2, 32, 3, 57, 0, 177, 2, 17, 66, 0, 177, 3, 57, 35, 0, 4, 173, 1, 21, 2, 32, 3, 58, 0, 173, 2, 17, 66, 0, 173, 3, 58, 35, 0, 4, 168, 1, 21, 2, 32, 3, 63, 0, 168, 2, 17, 66, 0, 168, 3, 63, 35, 0, 4, 158, 1, 21, 2, 32, 3, 64, 0, 158, 2, 17, 66, 0, 158, 3, 64, 35, 0, 4, 153, 1, 21, 2, 32, 3, 65, 0, 153, 2, 17, 66, 0, 153, 3, 65, 35, 0, 4, 148, 1, 21, 2, 32, 3, 66, 0, 148, 2, 17, 66, 0, 148, 3, 66, 35, 0, 4, 166, 1, 21, 2, 32, 3, 69, 0, 166, 2, 17, 66, 0, 166, 3, 69, 35, 0, 4, 161, 1, 21, 2, 32, 3, 70, 0, 161, 2, 17, 66, 0, 161, 3, 70, 35, 0, 4, 151, 1, 21, 2, 32, 3, 77, 0, 151, 2, 17, 66, 0, 151, 3, 77, 35, 0, 4, 149, 1, 21, 2, 32, 3, 78, 0, 149, 2, 17, 66, 0, 149, 3, 78, 35, 0, 4, 146, 1, 21, 2, 32, 3, 79, 0, 146, 2, 17, 66, 0, 146, 3, 79, 35, 0, 4, 175, 1, 21, 2, 32, 3, 86, 0, 175, 2, 17, 66, 0, 175, 3, 86, 35, 0, 4, 182, 1, 21, 2, 32, 3, 87, 0, 182, 2, 17, 66, 0, 182, 3, 87, 35, 0, 4, 174, 1, 21, 2, 32, 3, 88, 0, 174, 2, 17, 66, 0, 174, 3, 88, 35, 0, 4, 180, 1, 21, 2, 32, 3, 89, 0, 180, 2, 17, 66, 0, 180, 3, 89, 35, 0, 4, 181, 1, 21, 2, 32, 3, 91, 0, 181, 2, 17, 66, 0, 181, 3, 91, 35, 0, 4, 183, 1, 21, 2, 32, 3, 106, 0, 183, 2, 17, 66, 0, 183, 3, 106, 35, 0, 4, 165, 1, 21, 2, 32, 3, 134, 0, 165, 2, 17, 66, 0, 165, 3, 134, 35, 0, 4, 167, 1, 21, 2, 32, 3, 135, 0, 167, 2, 17, 66, 0, 167, 3, 135, 35, 0, 4, 160, 1, 21, 2, 32, 3, 136, 0, 160, 2, 17, 66, 0, 160, 3, 136, 35, 0, 4, 162, 1, 21, 2, 32, 3, 137, 0, 162, 2, 17, 66, 0, 162, 3, 137, 35, 0, 4, 154, 1, 21, 2, 32, 3, 138, 0, 154, 2, 17, 66, 0, 154, 3, 138, 35, 0, 4, 156, 1, 21, 2, 32, 3, 139, 0, 156, 2, 17, 66, 0, 156, 3, 139, 35, 0, 4, 155, 1, 21, 2, 32, 3, 140, 0, 155, 2, 17, 66, 0, 155, 3, 140, 35, 0, 4, 157, 1, 21, 2, 32, 3, 141, 0, 157, 2, 17, 66, 0, 157, 3, 141, 35, 0, 4, 150, 1, 21, 2, 32, 3, 142, 0, 150, 2, 17, 66, 0, 150, 3, 142, 35, 0, 4, 145, 1, 21, 2, 32, 3, 144, 0, 145, 2, 17, 66, 0, 145, 3, 144, 35, 0, 147, 1, 21, 2, 32, 3, 145, 0, 147, 3, 145, 35, 0, 4, 169, 1, 21, 2, 32, 3, 147, 0, 169, 2, 17, 66, 0, 169, 3, 147, 35, 0, 4, 171, 1, 21, 2, 32, 3, 148, 0, 171, 2, 17, 66, 0, 171, 3, 148, 35, 0, 4, 170, 1, 21, 2, 32, 3, 149, 0, 170, 2, 17, 66, 0, 170, 3, 149, 35, 0, 4, 172, 1, 21, 2, 32, 3, 150, 0, 172, 2, 17, 66, 0, 172, 3, 150, 35, 0, 7, 6, 0, 36, 3, 70, 39, 55, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts6 = FileInMemory_createWithData (2829, reinterpret_cast (&espeakdata_dicts6_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/bo_dict", L"bo"); Collection_addItem (me.peek(), espeakdata_dicts6.transfer()); static unsigned char espeakdata_dicts7_data[4178] = { 0, 4, 0, 0, 46, 12, 0, 0, 0, 0, 0, 0, 0, 6, 65, 4, 35, 0, 14, 5, 193, 4, 72, 28, 0, 0, 0, 0, 6, 65, 8, 69, 36, 0, 0, 0, 6, 195, 4, 208, 128, 28, 0, 0, 6, 65, 12, 87, 36, 0, 0, 0, 13, 4, 95, 8, 1, 3, 49, 35, 67, 6, 108, 50, 0, 0, 0, 6, 65, 16, 70, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 65, 24, 107, 81, 122, 0, 0, 0, 0, 0, 6, 65, 28, 77, 36, 0, 9, 134, 19, 5, 18, 195, 160, 19, 76, 0, 0, 0, 0, 6, 65, 32, 35, 49, 0, 0, 0, 0, 14, 1, 35, 49, 109, 57, 95, 37, 50, 6, 107, 47, 0, 27, 0, 6, 65, 36, 37, 0, 14, 5, 193, 36, 72, 8, 0, 15, 1, 37, 48, 13, 51, 87, 13, 50, 47, 6, 35, 75, 13, 0, 0, 18, 1, 38, 9, 9, 6, 37, 38, 15, 9, 122, 66, 55, 6, 107, 86, 122, 0, 0, 0, 8, 65, 40, 94, 108, 47, 122, 0, 0, 0, 9, 67, 21, 68, 192, 36, 121, 0, 76, 14, 1, 42, 35, 87, 47, 36, 16, 6, 37, 87, 49, 0, 27, 0, 9, 1, 43, 63, 16, 36, 87, 0, 27, 0, 6, 65, 44, 49, 36, 0, 0, 9, 1, 45, 63, 6, 107, 65, 87, 0, 0, 0, 9, 1, 47, 69, 35, 16, 51, 35, 0, 0, 7, 65, 48, 107, 55, 122, 0, 0, 0, 0, 0, 7, 65, 52, 107, 63, 122, 0, 0, 0, 0, 0, 7, 65, 56, 107, 50, 122, 0, 0, 0, 0, 0, 6, 65, 60, 39, 0, 14, 5, 193, 60, 72, 8, 0, 11, 1, 61, 37, 98, 58, 6, 35, 55, 0, 27, 0, 0, 0, 6, 65, 64, 48, 36, 0, 11, 1, 64, 35, 16, 51, 6, 39, 80, 35, 0, 0, 0, 0, 0, 6, 65, 68, 49, 40, 0, 0, 0, 6, 195, 84, 224, 64, 72, 0, 0, 8, 65, 72, 107, 51, 52, 13, 0, 0, 0, 0, 0, 8, 65, 76, 107, 87, 87, 13, 0, 0, 0, 0, 0, 6, 65, 80, 47, 36, 0, 0, 0, 0, 0, 0, 11, 4, 19, 195, 179, 14, 87, 39, 50, 0, 76, 0, 0, 0, 13, 65, 88, 6, 83, 36, 15, 69, 6, 115, 95, 122, 0, 0, 0, 0, 10, 135, 19, 5, 18, 195, 173, 5, 13, 76, 0, 14, 65, 92, 6, 83, 36, 15, 70, 6, 39, 69, 55, 13, 0, 0, 0, 16, 1, 94, 87, 37, 51, 49, 40, 63, 81, 55, 6, 107, 49, 87, 0, 0, 0, 7, 65, 96, 37, 49, 87, 0, 0, 0, 11, 4, 19, 195, 179, 3, 87, 39, 49, 0, 76, 0, 10, 135, 19, 5, 18, 195, 173, 5, 21, 76, 0, 12, 65, 100, 6, 37, 15, 79, 67, 107, 98, 122, 0, 0, 0, 0, 0, 8, 65, 104, 86, 36, 47, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 84, 225, 83, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 16, 80, 72, 0, 0, 0, 6, 195, 16, 83, 0, 72, 0, 0, 0, 12, 4, 95, 4, 16, 20, 10, 49, 39, 63, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 4, 192, 72, 28, 0, 0, 13, 4, 95, 20, 12, 4, 47, 6, 37, 55, 70, 36, 0, 0, 0, 0, 6, 195, 84, 228, 192, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 32, 21, 137, 4, 76, 0, 0, 7, 66, 32, 16, 35, 0, 76, 0, 6, 195, 25, 82, 64, 76, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 32, 19, 128, 35, 50, 0, 76, 0, 0, 8, 197, 32, 21, 137, 21, 48, 76, 0, 0, 0, 0, 8, 197, 76, 84, 137, 21, 48, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 32, 21, 137, 21, 80, 76, 0, 0, 0, 0, 0, 0, 0, 7, 196, 24, 244, 133, 56, 76, 0, 0, 0, 0, 0, 0, 0, 11, 3, 226, 130, 172, 6, 107, 58, 16, 109, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 32, 80, 107, 0, 76, 0, 0, 8, 133, 6, 195, 179, 18, 1, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 76, 84, 133, 52, 76, 0, 0, 6, 194, 20, 192, 72, 28, 5, 194, 20, 192, 72, 0, 9, 67, 32, 20, 192, 35, 87, 0, 76, 10, 3, 95, 50, 48, 83, 6, 37, 50, 0, 0, 7, 196, 76, 84, 129, 56, 76, 0, 0, 0, 0, 0, 0, 14, 4, 95, 13, 3, 14, 63, 35, 49, 67, 6, 108, 50, 0, 0, 19, 3, 197, 128, 12, 107, 55, 122, 4, 88, 13, 63, 37, 50, 6, 35, 84, 122, 0, 0, 0, 0, 0, 0, 7, 196, 76, 84, 137, 4, 76, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 24, 244, 133, 76, 76, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 76, 84, 133, 84, 76, 0, 0, 6, 194, 20, 224, 72, 28, 0, 13, 3, 95, 51, 88, 47, 67, 6, 107, 50, 47, 122, 0, 0, 12, 3, 95, 48, 67, 87, 6, 107, 50, 47, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 67, 87, 6, 107, 50, 47, 0, 0, 0, 0, 0, 0, 0, 5, 194, 48, 16, 72, 12, 3, 95, 49, 57, 70, 37, 50, 6, 39, 40, 0, 0, 13, 3, 95, 49, 56, 70, 37, 80, 6, 40, 57, 47, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 49, 6, 108, 50, 86, 13, 0, 0, 10, 3, 95, 49, 48, 70, 6, 36, 58, 0, 0, 13, 3, 95, 49, 51, 47, 67, 6, 107, 70, 86, 13, 0, 0, 12, 3, 95, 49, 50, 70, 6, 39, 70, 86, 13, 0, 0, 12, 3, 95, 49, 53, 49, 6, 37, 50, 86, 13, 0, 0, 14, 3, 95, 49, 52, 49, 122, 47, 6, 39, 51, 86, 13, 0, 0, 12, 3, 95, 49, 55, 70, 37, 87, 6, 107, 47, 0, 0, 12, 3, 95, 49, 54, 87, 6, 107, 70, 86, 13, 0, 0, 0, 14, 3, 95, 55, 88, 87, 13, 47, 6, 35, 50, 47, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 53, 67, 87, 37, 50, 87, 6, 107, 50, 121, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 32, 21, 137, 20, 208, 76, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 88, 83, 4, 37, 50, 47, 37, 0, 0, 14, 3, 95, 55, 67, 87, 4, 36, 121, 6, 107, 50, 121, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 32, 21, 137, 20, 224, 76, 0, 0, 0, 13, 3, 95, 63, 63, 87, 6, 37, 63, 69, 108, 55, 0, 0, 8, 197, 76, 84, 137, 20, 224, 76, 0, 0, 15, 3, 95, 52, 88, 49, 58, 122, 67, 6, 35, 50, 47, 122, 0, 0, 15, 3, 95, 57, 67, 50, 4, 108, 40, 87, 6, 107, 50, 121, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 53, 88, 87, 37, 50, 49, 58, 6, 35, 50, 47, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 54, 88, 87, 13, 57, 95, 6, 35, 50, 47, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 56, 88, 83, 40, 57, 47, 6, 35, 50, 47, 122, 0, 0, 0, 0, 0, 6, 195, 24, 245, 64, 76, 0, 0, 0, 0, 14, 3, 95, 57, 88, 50, 109, 67, 6, 35, 50, 47, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 15, 7, 15, 49, 39, 55, 6, 37, 47, 35, 0, 0, 7, 196, 20, 229, 18, 20, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 48, 77, 50, 63, 37, 61, 6, 39, 50, 13, 87, 0, 0, 0, 0, 11, 4, 95, 48, 77, 49, 63, 6, 37, 55, 0, 0, 13, 4, 95, 2, 18, 22, 69, 67, 6, 36, 80, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 4, 12, 194, 183, 12, 107, 55, 122, 4, 88, 13, 63, 37, 50, 6, 35, 84, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 66, 48, 192, 6, 107, 37, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 64, 83, 0, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 195, 169, 19, 36, 87, 0, 76, 19, 4, 95, 3, 9, 18, 87, 37, 51, 49, 40, 63, 81, 55, 6, 107, 49, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 19, 20, 11, 69, 6, 35, 16, 51, 35, 0, 0, 0, 13, 4, 95, 1, 3, 21, 35, 98, 6, 40, 84, 39, 0, 0, 20, 3, 95, 194, 171, 6, 39, 69, 67, 13, 15, 49, 109, 63, 6, 107, 47, 13, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 18, 14, 7, 35, 50, 6, 37, 96, 39, 0, 0, 23, 3, 95, 194, 161, 35, 80, 67, 6, 37, 51, 35, 84, 63, 37, 67, 35, 85, 57, 6, 108, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 19, 5, 18, 195, 160, 76, 0, 0, 0, 0, 0, 0, 6, 195, 21, 32, 64, 76, 0, 0, 0, 8, 133, 19, 5, 18, 195, 169, 76, 7, 195, 64, 83, 19, 72, 28, 0, 0, 0, 0, 20, 4, 95, 1, 3, 50, 70, 6, 108, 69, 55, 36, 15, 35, 98, 6, 40, 84, 39, 0, 0, 0, 0, 6, 195, 21, 33, 78, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 27, 3, 95, 194, 191, 35, 80, 67, 6, 37, 51, 37, 50, 47, 107, 16, 51, 4, 39, 98, 35, 85, 57, 6, 108, 50, 0, 0, 0, 0, 0, 6, 195, 21, 33, 83, 76, 21, 3, 95, 194, 187, 47, 6, 35, 50, 49, 122, 15, 49, 109, 63, 6, 107, 47, 13, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 6, 195, 179, 18, 5, 13, 76, 0, 0, 0, 6, 195, 16, 83, 19, 72, 0, 0, 0, 13, 2, 194, 167, 122, 48, 122, 67, 47, 6, 35, 47, 0, 0, 0, 0, 0, 12, 2, 194, 163, 55, 55, 37, 40, 67, 13, 87, 0, 0, 0, 0, 0, 16, 2, 195, 167, 87, 36, 4, 47, 67, 13, 50, 49, 35, 84, 122, 0, 0, 0, 0, 0, 0, 0, 14, 2, 194, 169, 49, 39, 48, 37, 16, 51, 6, 115, 47, 0, 0, 14, 2, 194, 182, 48, 122, 67, 6, 35, 98, 67, 122, 81, 0, 0, 0, 0, 9, 134, 6, 195, 179, 18, 5, 21, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 3, 5, 4, 47, 67, 107, 50, 49, 6, 35, 84, 35, 0, 0, 0, 0, 8, 2, 195, 177, 107, 65, 13, 0, 16, 4, 95, 12, 9, 7, 55, 37, 98, 35, 84, 6, 40, 67, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 32, 83, 64, 107, 63, 0, 76, 6, 195, 76, 243, 64, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 32, 85, 64, 107, 58, 0, 76, 6, 195, 76, 245, 64, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 1, 35, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 9, 37, 0, 0, 0, 6, 2, 95, 15, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 2, 95, 34, 49, 109, 63, 6, 107, 47, 13, 87, 0, 0, 23, 2, 95, 33, 87, 6, 37, 79, 50, 13, 15, 70, 122, 70, 63, 37, 67, 122, 87, 57, 6, 39, 0, 0, 0, 15, 2, 95, 39, 122, 48, 6, 108, 87, 47, 67, 6, 109, 81, 0, 0, 0, 0, 0, 0, 13, 4, 95, 3, 1, 16, 63, 6, 35, 96, 40, 87, 0, 0, 23, 2, 95, 41, 47, 6, 35, 50, 49, 122, 15, 48, 122, 67, 6, 107, 50, 47, 13, 86, 37, 87, 0, 0, 22, 2, 95, 40, 6, 39, 69, 67, 13, 15, 48, 122, 67, 6, 107, 50, 47, 13, 86, 37, 87, 0, 0, 7, 195, 64, 84, 128, 72, 28, 10, 2, 95, 47, 69, 35, 16, 51, 35, 0, 0, 8, 2, 95, 46, 48, 40, 50, 0, 0, 0, 9, 2, 95, 44, 49, 39, 63, 35, 0, 0, 10, 2, 95, 51, 47, 67, 6, 36, 87, 0, 0, 9, 2, 95, 50, 70, 6, 108, 87, 0, 0, 7, 2, 95, 49, 6, 40, 0, 0, 10, 2, 95, 48, 86, 6, 36, 67, 109, 0, 0, 9, 2, 95, 55, 87, 6, 107, 47, 0, 0, 9, 2, 95, 54, 87, 6, 37, 87, 0, 0, 10, 2, 95, 53, 87, 6, 37, 66, 49, 0, 20, 4, 95, 4, 1, 3, 70, 6, 108, 69, 55, 36, 15, 35, 98, 6, 40, 84, 39, 0, 0, 12, 2, 95, 52, 49, 58, 6, 35, 47, 67, 13, 0, 0, 15, 2, 95, 59, 48, 4, 40, 50, 37, 49, 6, 39, 63, 35, 0, 0, 15, 2, 95, 58, 70, 6, 39, 87, 15, 48, 6, 40, 50, 87, 0, 0, 9, 2, 95, 57, 50, 6, 39, 58, 0, 0, 10, 2, 95, 56, 83, 6, 40, 57, 47, 0, 0, 26, 2, 95, 63, 87, 6, 37, 79, 50, 13, 15, 70, 37, 50, 47, 13, 51, 52, 109, 98, 122, 87, 57, 6, 39, 0, 0, 15, 2, 95, 62, 63, 122, 94, 6, 39, 15, 9, 9, 49, 13, 0, 0, 0, 15, 2, 95, 60, 63, 13, 50, 6, 39, 15, 9, 9, 49, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 4, 15, 20, 48, 6, 40, 50, 47, 0, 0, 0, 0, 22, 2, 95, 91, 6, 39, 69, 67, 13, 15, 49, 55, 122, 58, 84, 6, 35, 47, 4, 39, 16, 0, 0, 0, 0, 7, 66, 88, 144, 82, 37, 0, 0, 18, 2, 95, 95, 69, 6, 35, 51, 52, 122, 15, 80, 6, 35, 57, 95, 122, 0, 0, 0, 23, 2, 95, 93, 47, 6, 35, 50, 49, 122, 15, 49, 55, 122, 58, 84, 6, 35, 47, 4, 39, 16, 0, 0, 21, 2, 95, 92, 69, 6, 35, 16, 51, 35, 37, 63, 69, 107, 51, 47, 6, 37, 84, 35, 0, 0, 0, 0, 0, 19, 2, 95, 96, 122, 49, 87, 6, 107, 50, 47, 4, 109, 80, 6, 107, 67, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 7, 18, 22, 79, 67, 6, 35, 80, 36, 0, 0, 0, 0, 0, 0, 6, 195, 48, 84, 192, 72, 0, 0, 0, 0, 0, 0, 0, 0, 17, 2, 95, 123, 6, 39, 69, 67, 13, 15, 49, 55, 6, 35, 58, 87, 0, 16, 4, 95, 4, 9, 1, 70, 57, 6, 107, 67, 36, 87, 37, 87, 0, 0, 10, 4, 95, 35, 57, 96, 47, 35, 69, 0, 0, 0, 0, 0, 0, 18, 2, 95, 125, 47, 6, 35, 50, 49, 122, 15, 49, 55, 6, 35, 58, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 84, 224, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 35, 51, 50, 13, 87, 48, 6, 35, 57, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 195, 169, 18, 5, 13, 76, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 195, 169, 18, 5, 21, 76, 0, 0, 0, 0, 0, 0, 0, 6, 195, 20, 196, 192, 72, 0, 0, 0, 0, 7, 195, 4, 196, 192, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 102, 0, 104, 0, 108, 0, 114, 0, 115, 0, 118, 0, 119, 0, 121, 0, 122, 0, 7, 6, 18, 67, 104, 0, 108, 0, 114, 0, 115, 0, 118, 0, 119, 0, 121, 0, 122, 0, 7, 6, 18, 68, 102, 0, 104, 0, 114, 0, 115, 0, 118, 0, 119, 0, 121, 0, 122, 0, 7, 6, 18, 69, 195, 173, 0, 195, 169, 0, 195, 168, 0, 105, 0, 101, 0, 7, 6, 18, 70, 112, 0, 116, 0, 107, 0, 102, 0, 115, 0, 7, 6, 18, 74, 98, 0, 100, 0, 103, 0, 109, 0, 118, 0, 108, 0, 110, 0, 100, 0, 122, 0, 114, 0, 113, 0, 7, 6, 18, 75, 97, 0, 101, 0, 111, 0, 7, 6, 18, 76, 105, 0, 117, 0, 7, 6, 18, 86, 112, 0, 98, 0, 116, 0, 100, 0, 107, 0, 103, 0, 7, 6, 18, 87, 102, 0, 118, 0, 115, 0, 122, 0, 7, 6, 18, 88, 109, 0, 110, 0, 7, 6, 18, 89, 108, 108, 0, 108, 0, 7, 6, 18, 90, 114, 0, 7, 6, 195, 167, 0, 3, 87, 0, 7, 6, 97, 0, 101, 3, 4, 35, 123, 0, 3, 35, 0, 109, 98, 2, 32, 17, 65, 3, 35, 63, 0, 7, 6, 98, 0, 2, 32, 3, 48, 0, 3, 69, 0, 4, 1, 17, 65, 2, 17, 65, 3, 80, 0, 1, 18, 67, 2, 17, 65, 0, 1, 32, 17, 65, 2, 17, 65, 0, 1, 32, 18, 67, 2, 17, 65, 0, 7, 6, 99, 0, 3, 49, 0, 2, 18, 69, 3, 87, 0, 7, 6, 100, 0, 2, 32, 3, 47, 0, 118, 3, 69, 69, 0, 3, 70, 0, 106, 3, 75, 0, 4, 1, 17, 65, 2, 17, 65, 3, 84, 0, 1, 18, 68, 2, 17, 65, 0, 1, 32, 17, 65, 2, 17, 65, 0, 1, 32, 18, 68, 2, 17, 65, 0, 7, 6, 101, 0, 2, 110, 116, 32, 3, 36, 0, 3, 107, 0, 97, 3, 123, 4, 35, 0, 111, 3, 123, 4, 39, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 2, 32, 3, 49, 0, 117, 105, 3, 75, 37, 0, 4, 3, 79, 0, 117, 2, 18, 69, 0, 2, 18, 69, 3, 94, 0, 4, 1, 17, 65, 2, 17, 65, 3, 98, 0, 1, 17, 65, 2, 114, 17, 65, 0, 1, 18, 66, 2, 17, 65, 0, 1, 32, 17, 65, 2, 17, 65, 0, 1, 32, 18, 66, 2, 17, 65, 0, 7, 6, 104, 0, 3, 0, 105, 1, 45, 2, 32, 3, 6, 37, 0, 111, 1, 45, 2, 32, 3, 6, 109, 0, 7, 6, 105, 0, 4, 3, 37, 0, 1, 188, 195, 103, 2, 25, 0, 1, 188, 195, 113, 2, 25, 0, 2, 97, 32, 0, 2, 117, 0, 4, 1, 17, 65, 2, 25, 12, 3, 57, 0, 2, 17, 65, 0, 103, 1, 17, 65, 2, 32, 3, 76, 0, 120, 1, 17, 65, 3, 95, 0, 7, 6, 106, 0, 3, 94, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 4, 3, 55, 0, 39, 8, 2, 14, 128, 132, 130, 0, 97, 1, 45, 2, 32, 3, 55, 122, 0, 108, 3, 61, 0, 7, 6, 109, 0, 4, 3, 63, 0, 39, 8, 2, 14, 128, 132, 130, 0, 112, 2, 25, 0, 7, 6, 110, 0, 4, 2, 32, 3, 8, 50, 0, 116, 2, 32, 0, 4, 3, 50, 0, 1, 101, 2, 32, 0, 1, 105, 2, 32, 0, 39, 8, 2, 14, 128, 132, 130, 0, 116, 2, 25, 0, 4, 1, 21, 2, 98, 3, 63, 0, 1, 21, 2, 118, 0, 1, 98, 2, 21, 0, 1, 118, 2, 21, 0, 121, 3, 65, 0, 4, 2, 99, 25, 3, 66, 0, 103, 0, 7, 6, 111, 0, 114, 2, 32, 3, 6, 39, 16, 0, 3, 39, 0, 117, 3, 108, 58, 0, 7, 6, 112, 0, 3, 48, 0, 2, 116, 3, 48, 12, 0, 7, 6, 113, 0, 4, 3, 49, 0, 117, 2, 18, 69, 0, 195, 188, 3, 49, 58, 0, 117, 105, 3, 49, 58, 37, 0, 7, 6, 114, 0, 2, 32, 3, 8, 0, 4, 8, 3, 16, 51, 0, 114, 0, 4, 3, 51, 0, 1, 108, 2, 17, 65, 0, 1, 109, 2, 17, 65, 0, 1, 110, 2, 17, 65, 0, 1, 115, 2, 17, 65, 0, 4, 1, 17, 65, 2, 17, 65, 3, 67, 0, 1, 17, 67, 2, 17, 65, 0, 2, 116, 0, 7, 6, 115, 0, 1, 17, 65, 2, 17, 65, 3, 86, 0, 4, 3, 87, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 39, 8, 2, 14, 128, 132, 130, 0, 115, 0, 101, 1, 45, 2, 32, 3, 87, 13, 0, 7, 6, 116, 0, 4, 3, 47, 0, 39, 8, 2, 14, 128, 132, 130, 0, 109, 3, 63, 63, 0, 122, 3, 70, 86, 0, 4, 103, 2, 18, 69, 3, 75, 0, 106, 0, 4, 106, 2, 32, 3, 76, 0, 120, 0, 7, 6, 117, 0, 4, 3, 40, 0, 2, 105, 0, 117, 3, 40, 58, 0, 4, 1, 17, 65, 2, 25, 3, 58, 0, 2, 17, 65, 0, 7, 6, 118, 0, 3, 80, 0, 8, 3, 83, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 4, 3, 49, 87, 0, 8, 17, 65, 2, 18, 70, 0, 8, 17, 65, 3, 79, 86, 0, 4, 1, 25, 3, 95, 0, 1, 105, 17, 65, 0, 1, 117, 17, 65, 0, 7, 6, 121, 0, 3, 37, 0, 2, 17, 65, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 195, 160, 3, 7, 35, 0, 195, 169, 3, 7, 36, 0, 195, 173, 3, 7, 37, 0, 195, 179, 3, 7, 39, 0, 195, 186, 3, 7, 40, 0, 195, 168, 3, 7, 107, 0, 195, 178, 3, 7, 108, 0, 195, 175, 3, 37, 0, 195, 188, 3, 40, 0, 197, 128, 3, 55, 0, 195, 188, 1, 103, 3, 58, 0, 195, 177, 3, 65, 0, 36, 3, 70, 39, 55, 122, 16, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts7 = FileInMemory_createWithData (4177, reinterpret_cast (&espeakdata_dicts7_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ca_dict", L"ca"); Collection_addItem (me.peek(), espeakdata_dicts7.transfer()); static unsigned char espeakdata_dicts8_data[7615] = { 0, 4, 0, 0, 70, 17, 0, 0, 0, 0, 0, 0, 6, 195, 41, 49, 77, 72, 0, 6, 65, 4, 122, 0, 14, 6, 193, 4, 72, 28, 8, 0, 0, 6, 195, 12, 16, 128, 17, 9, 134, 2, 196, 155, 8, 5, 13, 8, 0, 0, 6, 65, 8, 69, 121, 0, 0, 0, 0, 0, 6, 65, 12, 115, 121, 0, 0, 0, 13, 4, 95, 8, 1, 3, 105, 6, 122, 74, 36, 49, 0, 0, 0, 6, 65, 16, 70, 121, 0, 0, 7, 132, 196, 141, 19, 18, 17, 0, 0, 0, 5, 65, 20, 121, 0, 0, 0, 6, 195, 41, 50, 64, 72, 0, 0, 14, 69, 4, 229, 15, 56, 144, 35, 50, 47, 39, 50, 37, 0, 6, 65, 24, 36, 81, 0, 0, 0, 0, 6, 195, 41, 51, 69, 72, 0, 6, 65, 28, 79, 121, 0, 0, 6, 195, 29, 0, 64, 17, 0, 11, 67, 64, 117, 80, 48, 129, 73, 35, 48, 0, 0, 0, 6, 65, 32, 105, 122, 0, 0, 14, 1, 33, 82, 37, 79, 131, 37, 74, 65, 119, 49, 0, 27, 0, 0, 10, 1, 35, 79, 131, 119, 88, 36, 49, 0, 0, 6, 65, 36, 119, 0, 14, 5, 193, 36, 72, 28, 0, 5, 194, 37, 0, 17, 13, 1, 37, 48, 51, 39, 115, 36, 50, 47, 39, 0, 27, 0, 12, 1, 38, 35, 63, 48, 44, 87, 36, 50, 47, 0, 0, 0, 7, 132, 12, 5, 196, 141, 8, 6, 65, 40, 57, 121, 0, 0, 0, 15, 1, 42, 105, 82, 57, 36, 86, 77, 37, 74, 49, 35, 0, 27, 15, 1, 42, 105, 82, 57, 36, 86, 77, 37, 74, 49, 35, 0, 27, 0, 9, 1, 43, 48, 55, 40, 87, 0, 27, 0, 7, 65, 44, 49, 122, 0, 14, 4, 193, 44, 28, 0, 6, 195, 45, 0, 64, 17, 0, 10, 1, 46, 47, 36, 74, 49, 35, 0, 27, 0, 10, 1, 47, 55, 39, 63, 36, 50, 39, 0, 0, 6, 65, 48, 36, 55, 0, 0, 0, 0, 7, 196, 88, 81, 12, 20, 8, 0, 6, 65, 52, 36, 63, 0, 0, 6, 195, 53, 0, 64, 17, 0, 9, 134, 2, 21, 4, 5, 197, 161, 72, 0, 0, 11, 136, 3, 8, 20, 196, 155, 10, 195, 173, 76, 8, 197, 9, 81, 5, 52, 80, 72, 6, 65, 56, 36, 50, 0, 0, 0, 0, 0, 6, 65, 60, 123, 0, 14, 6, 193, 60, 72, 8, 23, 0, 10, 1, 61, 51, 39, 82, 50, 39, 0, 27, 0, 0, 10, 67, 76, 150, 133, 87, 35, 57, 86, 0, 0, 11, 1, 64, 86, 35, 82, 37, 50, 122, 74, 0, 6, 65, 64, 48, 121, 0, 0, 0, 6, 195, 20, 81, 192, 17, 0, 0, 7, 65, 68, 49, 82, 121, 0, 0, 0, 0, 7, 132, 13, 196, 155, 12, 76, 0, 6, 65, 72, 36, 51, 0, 0, 0, 0, 0, 7, 65, 76, 36, 87, 0, 14, 7, 65, 76, 87, 10, 0, 8, 10, 133, 16, 197, 153, 5, 4, 72, 8, 23, 0, 0, 0, 6, 195, 76, 144, 197, 8, 0, 6, 65, 80, 47, 121, 0, 0, 0, 6, 195, 4, 226, 64, 8, 0, 11, 67, 84, 226, 69, 40, 50, 37, 57, 36, 0, 6, 195, 52, 86, 137, 8, 0, 0, 7, 66, 85, 0, 35, 48, 0, 8, 133, 4, 195, 173, 11, 25, 8, 0, 0, 0, 12, 69, 12, 128, 78, 28, 80, 74, 129, 50, 73, 0, 7, 65, 88, 82, 121, 0, 14, 8, 197, 12, 128, 197, 80, 80, 76, 7, 65, 88, 82, 10, 0, 28, 0, 0, 0, 14, 4, 95, 49, 77, 52, 69, 6, 37, 55, 37, 123, 50, 0, 0, 11, 1, 92, 69, 36, 49, 87, 55, 36, 89, 0, 11, 65, 92, 70, 82, 6, 39, 57, 82, 121, 0, 0, 0, 11, 1, 94, 86, 70, 131, 119, 89, 49, 35, 0, 0, 0, 13, 4, 95, 49, 77, 49, 78, 6, 37, 87, 119, 115, 0, 7, 65, 96, 37, 49, 87, 0, 0, 14, 4, 95, 49, 77, 50, 63, 6, 37, 55, 37, 123, 50, 0, 0, 16, 4, 95, 49, 77, 51, 63, 6, 37, 55, 37, 35, 51, 70, 35, 0, 0, 0, 9, 67, 16, 245, 206, 70, 125, 50, 0, 11, 65, 100, 37, 48, 87, 37, 55, 39, 50, 0, 0, 0, 0, 0, 8, 65, 104, 86, 36, 47, 0, 14, 7, 65, 104, 87, 10, 0, 28, 0, 0, 6, 195, 5, 65, 0, 17, 0, 11, 68, 5, 48, 201, 36, 35, 87, 49, 37, 0, 0, 0, 15, 70, 84, 229, 9, 80, 193, 68, 35, 50, 47, 37, 47, 45, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 57, 52, 128, 17, 0, 0, 0, 0, 19, 71, 8, 19, 9, 77, 66, 75, 4, 69, 35, 55, 37, 87, 47, 37, 49, 35, 0, 9, 1, 126, 47, 37, 55, 70, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 196, 65, 35, 212, 36, 72, 8, 0, 0, 0, 6, 195, 13, 33, 0, 17, 0, 0, 0, 0, 8, 133, 196, 141, 19, 19, 18, 17, 0, 0, 0, 7, 132, 3, 15, 197, 190, 8, 0, 6, 195, 93, 34, 64, 17, 0, 0, 0, 0, 6, 195, 17, 2, 64, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 72, 196, 128, 17, 6, 195, 56, 68, 128, 17, 6, 195, 8, 196, 128, 17, 0, 0, 0, 0, 6, 195, 73, 52, 192, 17, 0, 0, 0, 0, 0, 6, 195, 41, 51, 213, 72, 0, 0, 0, 0, 0, 0, 0, 6, 195, 84, 102, 128, 17, 0, 0, 14, 67, 16, 51, 0, 70, 36, 115, 37, 55, 37, 47, 44, 0, 0, 0, 0, 0, 0, 9, 198, 56, 20, 18, 61, 66, 64, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 72, 192, 192, 17, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 85, 97, 128, 17, 0, 6, 195, 9, 81, 5, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 4, 16, 20, 9, 74, 122, 51, 49, 35, 10, 0, 0, 0, 5, 194, 9, 144, 72, 5, 194, 9, 144, 72, 0, 0, 6, 195, 9, 81, 21, 72, 0, 6, 195, 9, 147, 0, 72, 0, 0, 0, 0, 0, 7, 66, 12, 128, 99, 122, 0, 0, 0, 13, 4, 95, 20, 12, 4, 78, 6, 37, 55, 70, 35, 0, 10, 3, 95, 35, 57, 47, 6, 35, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 61, 165, 128, 17, 0, 0, 0, 0, 16, 70, 21, 128, 200, 4, 225, 197, 37, 49, 87, 74, 129, 50, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 69, 76, 52, 143, 48, 192, 87, 49, 34, 123, 55, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 56, 80, 143, 72, 8, 0, 0, 6, 195, 45, 35, 205, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 57, 83, 64, 50, 35, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 60, 52, 128, 17, 0, 0, 13, 69, 12, 19, 131, 20, 192, 49, 36, 50, 87, 45, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 66, 12, 208, 115, 36, 50, 47, 37, 63, 36, 47, 44, 0, 6, 195, 8, 86, 133, 8, 0, 0, 0, 0, 0, 7, 195, 8, 86, 128, 8, 23, 0, 0, 0, 0, 0, 7, 196, 44, 243, 5, 52, 8, 0, 6, 195, 44, 193, 18, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 60, 65, 64, 72, 28, 9, 3, 226, 130, 172, 126, 51, 39, 0, 0, 0, 8, 195, 76, 180, 154, 72, 28, 23, 0, 9, 67, 64, 17, 197, 48, 129, 73, 0, 6, 131, 196, 141, 1, 17, 0, 0, 8, 133, 13, 195, 161, 197, 161, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 9, 81, 5, 80, 80, 72, 11, 3, 95, 50, 6, 70, 82, 57, 6, 36, 0, 0, 12, 66, 29, 112, 79, 37, 79, 35, 82, 35, 47, 0, 0, 6, 195, 61, 51, 128, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 77, 52, 128, 17, 6, 195, 8, 84, 192, 17, 0, 0, 0, 14, 4, 95, 13, 3, 14, 63, 6, 35, 49, 51, 39, 50, 0, 0, 0, 0, 0, 6, 195, 76, 52, 201, 17, 0, 0, 0, 0, 7, 194, 16, 240, 72, 28, 23, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 196, 141, 18, 17, 0, 13, 66, 44, 32, 49, 37, 55, 39, 69, 35, 57, 47, 0, 0, 13, 3, 95, 51, 88, 47, 132, 6, 37, 115, 36, 47, 0, 0, 10, 3, 95, 48, 67, 87, 6, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 84, 129, 128, 17, 0, 10, 3, 95, 49, 67, 87, 47, 6, 39, 0, 0, 0, 0, 0, 0, 0, 5, 194, 40, 80, 72, 17, 3, 95, 49, 57, 70, 6, 36, 82, 35, 47, 36, 50, 122, 115, 47, 0, 0, 15, 3, 95, 49, 56, 6, 39, 87, 40, 63, 50, 122, 115, 47, 0, 0, 15, 3, 95, 50, 67, 70, 82, 57, 6, 36, 87, 78, 6, 36, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 49, 49, 57, 6, 36, 70, 36, 50, 122, 115, 47, 0, 0, 6, 195, 65, 35, 64, 17, 12, 3, 95, 49, 48, 70, 6, 36, 87, 36, 47, 0, 0, 14, 3, 95, 51, 67, 47, 132, 6, 37, 87, 47, 6, 35, 0, 14, 3, 95, 49, 51, 47, 132, 6, 37, 50, 122, 115, 47, 0, 0, 14, 3, 95, 49, 50, 70, 82, 6, 35, 50, 122, 115, 47, 0, 0, 14, 3, 95, 49, 53, 48, 6, 35, 47, 50, 122, 115, 47, 0, 0, 6, 195, 81, 35, 64, 17, 14, 3, 95, 49, 52, 74, 47, 6, 44, 50, 122, 115, 47, 0, 0, 16, 3, 95, 49, 55, 87, 6, 36, 70, 40, 63, 50, 122, 115, 47, 0, 0, 15, 3, 95, 49, 54, 89, 6, 36, 87, 47, 50, 122, 115, 47, 0, 0, 0, 17, 3, 95, 55, 88, 87, 6, 36, 70, 40, 63, 70, 36, 87, 122, 47, 0, 0, 15, 3, 95, 52, 67, 74, 47, 37, 131, 37, 87, 47, 6, 35, 0, 0, 0, 0, 0, 0, 0, 9, 66, 33, 160, 105, 36, 51, 115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 67, 52, 134, 128, 63, 36, 79, 35, 105, 36, 51, 115, 0, 0, 7, 196, 9, 148, 212, 20, 72, 7, 196, 64, 241, 12, 20, 8, 0, 0, 0, 9, 132, 16, 197, 153, 9, 72, 8, 23, 0, 0, 0, 0, 13, 3, 95, 50, 88, 70, 82, 6, 35, 115, 36, 47, 0, 0, 15, 5, 95, 48, 77, 65, 49, 78, 6, 37, 87, 119, 115, 36, 0, 0, 0, 17, 5, 95, 48, 77, 65, 51, 63, 6, 37, 55, 37, 35, 51, 70, 37, 0, 0, 16, 5, 95, 48, 77, 65, 50, 63, 6, 37, 55, 37, 123, 50, 37, 0, 0, 0, 16, 5, 95, 48, 77, 65, 52, 69, 6, 37, 55, 37, 123, 50, 37, 0, 0, 13, 66, 28, 224, 79, 37, 79, 35, 65, 40, 47, 50, 0, 0, 6, 195, 88, 112, 64, 17, 0, 11, 68, 48, 22, 133, 72, 55, 129, 86, 44, 0, 0, 0, 0, 0, 6, 195, 52, 147, 79, 8, 12, 3, 95, 63, 63, 87, 37, 63, 69, 39, 55, 0, 0, 0, 0, 15, 3, 95, 52, 88, 74, 47, 6, 37, 131, 37, 115, 36, 47, 0, 0, 0, 0, 0, 0, 0, 8, 195, 56, 17, 0, 72, 8, 23, 0, 7, 194, 56, 16, 72, 28, 23, 0, 6, 195, 64, 50, 64, 17, 14, 3, 95, 53, 88, 48, 6, 35, 70, 36, 87, 122, 47, 0, 0, 0, 0, 0, 0, 0, 6, 195, 77, 52, 210, 17, 0, 12, 66, 45, 112, 49, 37, 55, 39, 82, 35, 47, 0, 0, 14, 3, 95, 54, 88, 89, 6, 36, 70, 36, 87, 122, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 60, 68, 192, 17, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 56, 88, 6, 39, 87, 40, 63, 70, 36, 87, 122, 47, 0, 0, 0, 0, 6, 195, 77, 69, 129, 17, 0, 6, 195, 17, 37, 128, 17, 0, 0, 0, 0, 16, 3, 95, 57, 88, 70, 6, 36, 82, 35, 70, 36, 87, 122, 47, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 13, 195, 161, 76, 10, 3, 95, 63, 65, 86, 50, 35, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 15, 7, 15, 6, 39, 79, 39, 50, 36, 49, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 13, 195, 161, 13, 5, 76, 0, 0, 0, 0, 0, 9, 134, 3, 8, 3, 5, 197, 161, 76, 0, 0, 0, 0, 0, 0, 8, 197, 9, 144, 200, 60, 208, 72, 0, 0, 8, 195, 65, 35, 192, 72, 8, 23, 0, 15, 4, 95, 48, 77, 52, 69, 6, 37, 55, 37, 123, 50, 124, 0, 0, 0, 15, 4, 95, 48, 77, 50, 63, 6, 37, 55, 37, 123, 50, 124, 0, 0, 15, 4, 95, 48, 77, 51, 63, 6, 37, 55, 37, 35, 51, 70, 0, 0, 0, 13, 4, 95, 48, 77, 49, 78, 6, 37, 87, 119, 115, 0, 0, 7, 194, 60, 64, 72, 28, 23, 15, 4, 95, 2, 18, 22, 6, 39, 69, 55, 127, 74, 36, 49, 0, 0, 0, 0, 12, 69, 56, 85, 212, 60, 224, 65, 124, 47, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 66, 44, 208, 49, 37, 55, 39, 63, 36, 47, 44, 0, 5, 194, 52, 144, 72, 0, 0, 0, 13, 69, 16, 83, 5, 80, 80, 70, 37, 55, 119, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 66, 44, 224, 49, 37, 55, 39, 65, 40, 47, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 195, 16, 193, 64, 72, 8, 23, 0, 0, 0, 0, 0, 7, 196, 60, 179, 204, 60, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 36, 35, 64, 17, 0, 0, 0, 15, 4, 95, 3, 9, 18, 87, 47, 131, 6, 119, 89, 49, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 196, 76, 180, 154, 20, 72, 8, 0, 0, 0, 19, 4, 95, 19, 20, 11, 89, 6, 37, 49, 63, 122, 74, 6, 122, 51, 49, 35, 0, 0, 0, 13, 4, 95, 1, 3, 21, 74, 6, 122, 51, 49, 35, 0, 0, 0, 0, 0, 0, 5, 194, 72, 48, 17, 0, 0, 0, 0, 0, 14, 4, 95, 18, 14, 7, 49, 51, 6, 127, 88, 36, 49, 0, 0, 0, 0, 5, 194, 73, 48, 17, 0, 19, 67, 33, 69, 16, 105, 122, 47, 36, 47, 36, 48, 121, 0, 81, 58, 47, 47, 32, 0, 0, 0, 7, 132, 196, 141, 1, 22, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 17, 64, 64, 17, 0, 0, 0, 5, 194, 77, 32, 17, 0, 0, 7, 195, 56, 17, 5, 72, 8, 0, 0, 18, 4, 95, 1, 3, 50, 70, 82, 57, 6, 36, 74, 6, 122, 51, 49, 37, 0, 0, 0, 0, 0, 0, 6, 195, 60, 177, 0, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 64, 68, 128, 17, 0, 0, 0, 0, 6, 195, 64, 196, 128, 17, 0, 0, 9, 2, 195, 151, 49, 51, 122, 47, 0, 7, 2, 196, 143, 77, 121, 0, 0, 0, 7, 2, 196, 141, 74, 121, 0, 0, 0, 0, 0, 0, 0, 13, 2, 194, 167, 48, 35, 51, 35, 79, 51, 35, 81, 0, 0, 5, 194, 60, 208, 17, 5, 194, 76, 80, 72, 0, 0, 0, 0, 10, 3, 5, 46, 7, 50, 35, 48, 131, 0, 7, 2, 197, 136, 36, 65, 0, 0, 0, 0, 0, 0, 0, 0, 8, 2, 196, 155, 37, 57, 36, 0, 0, 0, 14, 2, 194, 169, 49, 6, 39, 48, 37, 51, 35, 57, 47, 0, 13, 2, 195, 161, 70, 55, 6, 127, 105, 121, 4, 122, 0, 0, 7, 132, 2, 195, 189, 20, 72, 0, 0, 0, 13, 2, 195, 173, 70, 55, 6, 127, 105, 121, 4, 119, 0, 0, 0, 5, 130, 195, 171, 43, 0, 8, 133, 13, 195, 161, 20, 5, 76, 11, 2, 194, 176, 87, 47, 40, 48, 36, 65, 0, 0, 6, 195, 12, 112, 64, 17, 7, 2, 197, 153, 36, 131, 0, 13, 2, 195, 169, 70, 55, 6, 127, 105, 121, 4, 121, 0, 0, 5, 130, 195, 182, 43, 0, 12, 69, 76, 80, 82, 12, 128, 87, 36, 51, 74, 0, 11, 2, 195, 183, 77, 36, 55, 36, 50, 39, 0, 0, 5, 194, 73, 128, 17, 7, 2, 195, 180, 40, 123, 0, 0, 7, 2, 197, 165, 78, 121, 0, 0, 14, 4, 95, 3, 5, 4, 115, 6, 36, 77, 37, 55, 35, 0, 0, 13, 2, 195, 179, 70, 55, 6, 127, 105, 121, 4, 123, 0, 0, 0, 17, 4, 95, 12, 9, 7, 55, 6, 37, 79, 35, 47, 4, 40, 51, 35, 0, 7, 2, 197, 161, 36, 89, 0, 0, 0, 17, 2, 197, 175, 6, 124, 87, 10, 49, 51, 6, 127, 88, 49, 36, 63, 0, 0, 5, 130, 195, 188, 43, 0, 6, 195, 5, 34, 128, 17, 18, 2, 195, 189, 70, 55, 6, 127, 121, 4, 37, 48, 87, 37, 55, 39, 50, 0, 0, 13, 2, 195, 186, 70, 55, 6, 127, 105, 121, 4, 124, 0, 0, 0, 0, 0, 7, 2, 196, 190, 36, 61, 0, 0, 0, 0, 0, 14, 2, 196, 186, 70, 55, 6, 127, 105, 121, 4, 36, 55, 0, 0, 0, 6, 195, 92, 116, 15, 17, 0, 0, 6, 195, 9, 147, 1, 72, 8, 2, 197, 190, 88, 36, 47, 0, 0, 0, 6, 195, 9, 147, 15, 72, 0, 0, 0, 0, 0, 0, 6, 195, 9, 147, 9, 72, 0, 0, 0, 0, 7, 196, 9, 81, 15, 84, 72, 6, 131, 1, 196, 141, 8, 0, 0, 0, 0, 0, 0, 7, 194, 64, 240, 72, 8, 23, 5, 194, 76, 144, 72, 0, 8, 195, 64, 241, 0, 72, 8, 23, 0, 0, 0, 0, 0, 6, 195, 9, 147, 25, 72, 0, 0, 0, 6, 2, 95, 1, 122, 0, 0, 0, 0, 0, 0, 7, 2, 95, 11, 49, 122, 0, 0, 0, 6, 2, 95, 9, 119, 0, 0, 0, 6, 195, 5, 32, 192, 17, 6, 2, 95, 15, 123, 0, 0, 0, 0, 0, 6, 195, 85, 48, 64, 17, 7, 2, 95, 19, 36, 87, 0, 0, 0, 0, 0, 0, 7, 2, 95, 22, 82, 121, 0, 0, 6, 2, 95, 21, 124, 0, 0, 0, 0, 8, 2, 95, 26, 86, 36, 47, 0, 0, 0, 7, 131, 197, 190, 5, 72, 8, 5, 194, 80, 144, 72, 0, 0, 0, 0, 0, 0, 13, 2, 95, 34, 40, 82, 39, 86, 39, 82, 49, 37, 0, 0, 0, 0, 13, 2, 95, 39, 35, 48, 39, 87, 47, 51, 39, 81, 0, 0, 0, 0, 10, 2, 95, 36, 70, 39, 55, 122, 51, 0, 0, 0, 12, 4, 95, 3, 1, 16, 82, 36, 55, 49, 121, 0, 0, 18, 2, 95, 41, 86, 122, 82, 39, 34, 49, 35, 86, 35, 82, 131, 119, 47, 0, 0, 12, 2, 95, 40, 86, 122, 82, 39, 51, 49, 35, 0, 0, 6, 195, 52, 180, 128, 17, 0, 10, 2, 95, 46, 47, 36, 74, 49, 35, 0, 0, 10, 2, 95, 45, 63, 119, 50, 40, 87, 0, 0, 10, 2, 95, 44, 74, 122, 51, 49, 35, 0, 0, 8, 2, 95, 51, 47, 132, 37, 0, 0, 9, 2, 95, 50, 70, 82, 6, 35, 0, 0, 11, 2, 95, 49, 57, 6, 36, 70, 36, 50, 0, 0, 10, 2, 95, 48, 50, 6, 40, 55, 35, 0, 0, 6, 195, 84, 181, 128, 17, 11, 2, 95, 55, 87, 6, 36, 70, 40, 63, 0, 0, 10, 2, 95, 54, 89, 6, 36, 87, 47, 0, 0, 10, 2, 95, 53, 48, 6, 57, 36, 47, 0, 0, 11, 2, 95, 52, 74, 47, 6, 37, 131, 37, 0, 0, 13, 2, 95, 59, 86, 70, 131, 36, 70, 65, 119, 49, 0, 0, 15, 2, 95, 58, 70, 82, 6, 39, 57, 47, 36, 74, 49, 35, 0, 0, 12, 2, 95, 57, 70, 6, 36, 82, 57, 36, 47, 0, 0, 10, 2, 95, 56, 6, 39, 87, 40, 63, 0, 0, 12, 2, 95, 63, 39, 47, 35, 86, 65, 119, 49, 0, 0, 10, 2, 95, 62, 82, 57, 36, 74, 119, 0, 0, 8, 197, 12, 128, 197, 52, 80, 76, 0, 10, 2, 95, 60, 63, 36, 50, 89, 119, 0, 0, 0, 8, 133, 13, 1, 10, 195, 173, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 20, 177, 192, 17, 0, 13, 4, 95, 4, 15, 20, 47, 6, 36, 74, 49, 35, 0, 0, 0, 0, 6, 195, 4, 193, 64, 8, 22, 2, 95, 91, 105, 51, 6, 35, 50, 35, 47, 122, 15, 86, 6, 122, 82, 39, 51, 49, 35, 0, 0, 0, 0, 7, 194, 104, 16, 72, 8, 23, 0, 14, 2, 95, 95, 48, 39, 47, 47, 44, 88, 36, 65, 119, 0, 0, 0, 21, 2, 95, 93, 105, 51, 6, 35, 50, 35, 47, 122, 15, 86, 6, 35, 82, 131, 119, 47, 0, 0, 0, 0, 0, 0, 22, 2, 95, 96, 6, 39, 69, 51, 122, 115, 4, 36, 50, 122, 15, 74, 6, 122, 51, 49, 35, 0, 0, 9, 134, 13, 195, 173, 19, 20, 15, 8, 0, 0, 8, 133, 196, 141, 22, 21, 20, 17, 0, 0, 0, 0, 0, 21, 4, 95, 7, 18, 22, 78, 6, 36, 89, 49, 119, 38, 6, 35, 49, 115, 36, 50, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 22, 2, 95, 123, 87, 55, 6, 39, 88, 36, 50, 122, 15, 86, 6, 122, 82, 39, 51, 49, 35, 0, 13, 4, 95, 4, 9, 1, 47, 51, 6, 36, 63, 35, 0, 0, 0, 0, 8, 133, 22, 197, 161, 1, 11, 8, 0, 0, 10, 68, 64, 245, 197, 72, 48, 125, 44, 0, 0, 21, 2, 95, 125, 87, 55, 6, 39, 88, 36, 50, 122, 15, 86, 6, 35, 82, 131, 119, 47, 0, 0, 18, 2, 95, 124, 87, 82, 6, 37, 87, 55, 122, 15, 74, 6, 122, 51, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 196, 141, 12, 1, 17, 0, 0, 0, 0, 12, 67, 21, 48, 192, 37, 87, 49, 36, 37, 48, 0, 0, 0, 0, 7, 195, 64, 241, 5, 72, 8, 0, 0, 0, 0, 14, 4, 95, 35, 51, 50, 63, 6, 36, 86, 36, 51, 35, 0, 0, 6, 195, 9, 144, 200, 72, 0, 0, 0, 7, 132, 196, 141, 12, 18, 17, 7, 194, 104, 80, 72, 28, 23, 0, 0, 0, 0, 0, 0, 0, 0, 14, 70, 61, 85, 12, 60, 242, 192, 125, 47, 55, 124, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 196, 128, 17, 0, 0, 0, 0, 6, 195, 9, 148, 192, 72, 0, 0, 0, 0, 12, 67, 93, 117, 192, 82, 121, 82, 121, 82, 121, 0, 6, 195, 60, 133, 128, 17, 0, 0, 0, 0, 0, 19, 67, 12, 20, 19, 49, 35, 48, 87, 55, 39, 49, 0, 81, 108, 111, 99, 107, 32, 0, 0, 0, 14, 67, 28, 134, 128, 79, 37, 79, 35, 105, 36, 34, 115, 0, 0, 0, 12, 67, 64, 113, 14, 48, 129, 73, 70, 125, 50, 0, 0, 0, 14, 67, 44, 134, 128, 49, 37, 55, 39, 105, 36, 34, 115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 12, 128, 197, 76, 0, 6, 195, 60, 128, 192, 17, 7, 132, 13, 195, 161, 13, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 196, 141, 19, 1, 4, 17, 0, 6, 195, 12, 128, 201, 76, 0, 6, 195, 21, 65, 128, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 32, 243, 69, 105, 127, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 196, 141, 19, 6, 18, 17, 0, 0, 0, 0, 0, 0, 14, 69, 36, 228, 197, 73, 64, 37, 50, 86, 36, 51, 47, 0, 0, 6, 195, 41, 53, 5, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 100, 105, 0, 4, 1, 97, 2, 107, 3, 70, 37, 0, 1, 97, 108, 2, 115, 0, 1, 97, 114, 116, 2, 99, 0, 1, 101, 109, 0, 1, 101, 112, 111, 116, 2, 99, 0, 1, 101, 114, 107, 2, 116, 0, 1, 105, 109, 0, 1, 108, 97, 114, 0, 1, 110, 2, 99, 0, 1, 110, 97, 2, 100, 0, 1, 110, 97, 109, 2, 116, 0, 1, 110, 105, 0, 1, 111, 2, 99, 0, 1, 111, 105, 114, 2, 99, 0, 1, 111, 107, 2, 102, 105, 0, 1, 111, 116, 101, 0, 1, 114, 97, 100, 2, 122, 0, 1, 114, 111, 0, 1, 155, 196, 109, 0, 1, 169, 195, 109, 0, 2, 97, 0, 2, 97, 32, 0, 2, 101, 0, 2, 103, 105, 0, 2, 106, 0, 2, 107, 0, 2, 110, 105, 107, 0, 2, 111, 0, 2, 114, 0, 2, 115, 99, 105, 112, 0, 2, 115, 107, 0, 2, 115, 109, 0, 2, 115, 112, 0, 2, 115, 116, 0, 2, 115, 116, 0, 2, 116, 105, 107, 0, 2, 117, 0, 2, 117, 109, 32, 0, 8, 2, 99, 104, 0, 8, 2, 102, 0, 8, 2, 103, 0, 8, 2, 108, 101, 116, 0, 8, 2, 109, 101, 0, 8, 2, 109, 105, 0, 8, 2, 112, 0, 8, 2, 115, 0, 8, 2, 118, 97, 110, 0, 8, 2, 118, 101, 114, 0, 8, 2, 118, 105, 100, 0, 8, 2, 122, 0, 8, 2, 195, 161, 0, 8, 97, 108, 103, 0, 8, 97, 114, 116, 0, 8, 101, 0, 8, 101, 110, 2, 112, 0, 8, 101, 112, 120, 101, 0, 8, 108, 111, 112, 0, 8, 110, 97, 99, 115, 0, 8, 111, 2, 110, 115, 116, 0, 8, 111, 109, 0, 8, 114, 97, 107, 0, 8, 114, 97, 115, 0, 8, 117, 97, 0, 99, 107, 8, 3, 70, 37, 49, 0, 4, 2, 101, 32, 3, 70, 37, 57, 0, 2, 101, 32, 0, 2, 105, 32, 0, 2, 111, 32, 0, 2, 117, 32, 0, 8, 2, 97, 0, 115, 116, 105, 2, 99, 3, 70, 37, 87, 47, 37, 0, 115, 107, 114, 101, 100, 105, 3, 70, 37, 87, 49, 14, 16, 36, 70, 37, 0, 115, 99, 111, 8, 3, 70, 37, 87, 49, 39, 0, 4, 1, 101, 153, 197, 2, 115, 107, 3, 77, 37, 0, 1, 111, 104, 99, 2, 115, 0, 8, 2, 114, 99, 0, 8, 2, 114, 107, 0, 8, 2, 118, 105, 122, 110, 97, 0, 8, 2, 118, 105, 122, 110, 121, 0, 8, 101, 108, 104, 0, 7, 6, 110, 105, 0, 4, 1, 97, 2, 100, 3, 50, 37, 0, 1, 97, 2, 107, 0, 1, 97, 2, 107, 111, 118, 0, 1, 97, 2, 122, 0, 1, 97, 103, 114, 111, 110, 97, 0, 1, 97, 104, 99, 2, 99, 0, 1, 97, 104, 99, 2, 107, 0, 1, 97, 104, 99, 101, 2, 115, 0, 1, 97, 109, 2, 102, 0, 1, 97, 109, 2, 112, 0, 1, 97, 109, 114, 101, 0, 1, 97, 110, 2, 115, 0, 1, 101, 2, 107, 0, 1, 101, 2, 115, 0, 1, 101, 103, 0, 1, 101, 108, 97, 2, 116, 0, 1, 101, 108, 101, 2, 116, 0, 1, 101, 122, 2, 116, 0, 1, 103, 2, 116, 0, 1, 105, 2, 99, 105, 0, 1, 105, 2, 107, 0, 1, 105, 2, 116, 0, 1, 105, 102, 101, 0, 1, 105, 108, 107, 0, 1, 105, 109, 0, 1, 107, 2, 112, 0, 1, 111, 2, 100, 0, 1, 111, 2, 107, 0, 1, 111, 2, 115, 0, 1, 111, 100, 2, 99, 0, 1, 111, 102, 2, 99, 0, 1, 111, 103, 0, 1, 111, 103, 97, 116, 2, 115, 0, 1, 111, 109, 101, 114, 101, 0, 1, 111, 109, 114, 97, 104, 0, 1, 111, 110, 2, 109, 0, 1, 111, 114, 2, 99, 0, 1, 111, 114, 100, 110, 101, 0, 1, 111, 114, 104, 99, 110, 121, 115, 0, 1, 111, 114, 105, 0, 1, 111, 116, 107, 0, 1, 117, 2, 116, 0, 1, 117, 109, 2, 107, 0, 1, 117, 109, 2, 115, 0, 1, 117, 109, 111, 107, 0, 1, 117, 116, 2, 115, 0, 1, 169, 195, 103, 0, 2, 97, 32, 0, 2, 97, 107, 0, 2, 107, 108, 0, 2, 110, 105, 107, 0, 2, 115, 109, 0, 2, 115, 116, 0, 2, 116, 105, 107, 0, 2, 117, 109, 32, 0, 2, 122, 117, 106, 0, 8, 2, 108, 0, 8, 2, 116, 114, 111, 0, 8, 97, 2, 109, 0, 8, 97, 103, 114, 111, 0, 8, 97, 107, 2, 98, 0, 8, 97, 109, 117, 104, 0, 8, 97, 110, 2, 116, 114, 0, 8, 97, 112, 2, 99, 107, 0, 8, 97, 115, 2, 116, 0, 8, 97, 116, 111, 98, 0, 8, 97, 118, 108, 97, 103, 0, 8, 101, 105, 103, 121, 104, 0, 8, 101, 115, 2, 108, 0, 8, 101, 116, 2, 115, 0, 8, 111, 98, 101, 0, 8, 111, 108, 111, 107, 0, 8, 111, 109, 0, 8, 116, 101, 2, 99, 0, 8, 117, 0, 8, 117, 109, 0, 8, 117, 109, 105, 2, 116, 0, 8, 121, 99, 0, 8, 169, 195, 114, 116, 0, 116, 105, 1, 105, 102, 3, 50, 37, 47, 37, 0, 107, 111, 116, 105, 8, 3, 50, 37, 49, 39, 47, 37, 0, 4, 2, 101, 32, 3, 50, 37, 57, 0, 2, 105, 32, 0, 2, 111, 32, 0, 2, 117, 32, 0, 2, 195, 173, 0, 4, 1, 97, 122, 2, 107, 3, 65, 37, 0, 1, 100, 111, 112, 2, 107, 0, 1, 100, 117, 111, 108, 0, 1, 105, 118, 2, 116, 0, 1, 105, 141, 196, 2, 116, 0, 1, 106, 111, 116, 115, 0, 1, 111, 114, 112, 2, 107, 0, 1, 117, 2, 107, 0, 1, 118, 2, 107, 108, 0, 1, 122, 118, 2, 107, 0, 1, 153, 197, 111, 109, 161, 195, 110, 0, 8, 2, 116, 114, 111, 32, 0, 8, 97, 104, 99, 173, 195, 109, 0, 8, 105, 108, 104, 2, 116, 0, 8, 111, 114, 98, 0, 7, 6, 116, 105, 0, 4, 109, 101, 2, 32, 3, 47, 35, 57, 63, 0, 109, 101, 8, 0, 4, 1, 97, 2, 99, 3, 47, 37, 0, 1, 97, 2, 107, 0, 1, 97, 2, 110, 0, 1, 97, 2, 118, 0, 1, 97, 2, 122, 0, 1, 97, 109, 2, 99, 107, 0, 1, 97, 109, 2, 107, 97, 0, 1, 97, 109, 97, 2, 99, 0, 1, 97, 109, 97, 2, 107, 0, 1, 97, 109, 97, 114, 100, 0, 1, 97, 109, 101, 2, 99, 0, 1, 97, 109, 101, 2, 107, 0, 1, 97, 109, 111, 114, 97, 0, 1, 97, 109, 111, 116, 2, 99, 0, 1, 97, 109, 117, 2, 99, 0, 1, 97, 112, 97, 2, 99, 0, 1, 97, 112, 97, 2, 196, 141, 0, 1, 97, 112, 109, 111, 2, 98, 0, 1, 97, 112, 109, 121, 0, 1, 101, 2, 99, 0, 1, 101, 2, 107, 0, 1, 101, 2, 118, 0, 1, 101, 2, 122, 0, 1, 101, 107, 114, 97, 2, 110, 103, 0, 1, 101, 110, 2, 99, 0, 1, 101, 114, 111, 101, 2, 99, 0, 1, 105, 2, 107, 0, 1, 105, 103, 2, 109, 0, 1, 105, 108, 2, 99, 0, 1, 105, 109, 105, 114, 2, 118, 0, 1, 105, 110, 97, 118, 2, 116, 0, 1, 105, 114, 2, 99, 0, 1, 105, 114, 2, 107, 0, 1, 105, 114, 107, 0, 1, 105, 118, 114, 0, 1, 107, 2, 118, 0, 1, 107, 97, 0, 1, 107, 101, 0, 1, 107, 114, 0, 1, 108, 117, 107, 2, 118, 0, 1, 110, 2, 99, 0, 1, 110, 2, 110, 0, 1, 110, 97, 2, 107, 0, 1, 110, 97, 2, 108, 0, 1, 110, 97, 2, 115, 0, 1, 110, 101, 2, 110, 0, 1, 110, 101, 118, 2, 108, 0, 1, 110, 105, 2, 109, 0, 1, 110, 111, 107, 0, 1, 111, 2, 107, 0, 1, 111, 98, 2, 122, 0, 1, 111, 109, 2, 118, 0, 1, 111, 114, 2, 107, 0, 1, 111, 114, 101, 2, 99, 0, 1, 111, 120, 2, 107, 0, 1, 112, 101, 2, 107, 0, 1, 112, 111, 0, 1, 114, 2, 122, 0, 1, 114, 111, 2, 109, 0, 1, 115, 2, 107, 0, 1, 115, 2, 109, 117, 108, 0, 1, 115, 2, 112, 0, 1, 115, 101, 100, 2, 108, 0, 1, 115, 101, 103, 117, 115, 0, 1, 115, 101, 118, 110, 0, 1, 115, 111, 2, 99, 0, 1, 117, 2, 107, 0, 1, 117, 97, 0, 1, 120, 2, 108, 0, 1, 189, 195, 2, 99, 107, 0, 2, 97, 32, 0, 2, 99, 107, 0, 2, 102, 0, 2, 110, 105, 107, 0, 2, 115, 109, 0, 2, 115, 116, 0, 2, 116, 105, 107, 0, 2, 116, 117, 108, 0, 2, 117, 109, 32, 0, 8, 2, 98, 0, 8, 2, 99, 105, 0, 8, 2, 109, 98, 0, 8, 2, 110, 107, 0, 8, 2, 114, 97, 110, 0, 8, 2, 116, 97, 110, 0, 8, 2, 116, 117, 108, 0, 8, 2, 116, 195, 161, 110, 0, 8, 2, 120, 0, 8, 97, 108, 112, 2, 110, 0, 8, 97, 109, 103, 101, 108, 102, 0, 8, 97, 109, 169, 195, 116, 0, 8, 97, 115, 2, 114, 0, 8, 97, 115, 2, 197, 153, 0, 8, 101, 109, 115, 111, 107, 0, 8, 101, 112, 2, 196, 141, 0, 8, 105, 115, 111, 112, 0, 8, 108, 117, 2, 109, 0, 8, 108, 117, 109, 0, 8, 110, 97, 0, 8, 110, 97, 108, 116, 97, 0, 8, 110, 101, 99, 0, 8, 110, 101, 115, 0, 8, 110, 101, 118, 101, 114, 112, 0, 8, 110, 111, 107, 2, 110, 0, 8, 111, 108, 102, 0, 8, 112, 105, 108, 107, 101, 0, 8, 112, 111, 2, 99, 0, 8, 114, 101, 118, 2, 107, 0, 8, 115, 98, 97, 0, 8, 115, 101, 98, 0, 8, 115, 101, 108, 97, 112, 0, 8, 115, 101, 114, 2, 116, 0, 8, 115, 110, 105, 0, 8, 115, 110, 111, 107, 0, 8, 115, 117, 106, 0, 8, 117, 114, 0, 110, 105, 2, 117, 3, 47, 37, 50, 37, 57, 0, 4, 2, 101, 32, 3, 47, 37, 57, 0, 2, 105, 32, 0, 2, 111, 32, 0, 2, 117, 32, 0, 109, 111, 110, 105, 2, 116, 3, 47, 37, 63, 39, 50, 37, 0, 4, 115, 116, 105, 1, 97, 3, 47, 37, 87, 47, 37, 0, 115, 116, 105, 8, 97, 116, 115, 0, 4, 1, 97, 104, 99, 2, 99, 3, 78, 37, 0, 1, 97, 108, 2, 110, 0, 1, 97, 109, 2, 99, 0, 1, 99, 0, 1, 101, 99, 105, 153, 197, 0, 1, 101, 108, 112, 0, 1, 101, 153, 197, 2, 99, 0, 1, 104, 99, 101, 108, 0, 1, 111, 114, 2, 118, 0, 1, 112, 97, 2, 118, 0, 1, 114, 100, 0, 1, 115, 101, 161, 197, 0, 1, 115, 109, 0, 1, 115, 111, 100, 0, 1, 115, 111, 104, 0, 1, 115, 111, 107, 2, 99, 0, 1, 115, 161, 195, 2, 99, 0, 1, 155, 196, 2, 99, 0, 1, 155, 196, 112, 0, 1, 155, 196, 118, 2, 118, 0, 1, 161, 195, 115, 101, 100, 0, 1, 173, 195, 118, 101, 0, 8, 97, 109, 2, 110, 0, 8, 101, 99, 97, 118, 100, 0, 8, 101, 115, 101, 100, 0, 8, 111, 114, 112, 0, 8, 115, 97, 114, 116, 115, 0, 8, 121, 107, 2, 99, 0, 8, 155, 196, 116, 0, 7, 6, 195, 161, 0, 3, 122, 0, 7, 6, 195, 164, 0, 3, 36, 0, 7, 6, 195, 169, 0, 3, 121, 0, 7, 6, 195, 173, 0, 3, 119, 0, 7, 6, 195, 179, 0, 3, 123, 0, 7, 6, 195, 180, 0, 3, 40, 39, 0, 7, 6, 195, 186, 0, 3, 124, 0, 7, 6, 195, 189, 0, 3, 119, 0, 7, 6, 196, 141, 0, 3, 74, 0, 7, 6, 196, 143, 0, 4, 3, 77, 0, 2, 32, 17, 70, 0, 2, 32, 3, 78, 0, 7, 6, 196, 155, 0, 3, 36, 0, 7, 6, 196, 190, 0, 3, 61, 0, 7, 6, 197, 136, 0, 3, 65, 0, 7, 6, 197, 153, 0, 3, 131, 0, 4, 1, 102, 3, 132, 0, 1, 107, 0, 1, 112, 0, 1, 116, 0, 7, 6, 197, 161, 0, 3, 89, 0, 7, 6, 197, 165, 0, 3, 78, 0, 7, 6, 197, 175, 0, 3, 124, 0, 7, 6, 197, 190, 0, 4, 3, 88, 0, 2, 32, 17, 70, 0, 2, 32, 3, 89, 0, 7, 6, 97, 0, 3, 35, 0, 99, 107, 1, 114, 116, 3, 36, 49, 0, 117, 3, 125, 0, 105, 1, 109, 2, 108, 3, 129, 0, 103, 101, 1, 112, 3, 129, 73, 0, 115, 116, 101, 1, 112, 2, 32, 3, 129, 87, 47, 0, 7, 6, 98, 0, 2, 32, 3, 48, 0, 4, 3, 69, 0, 2, 32, 17, 70, 0, 97, 99, 107, 3, 69, 36, 49, 0, 196, 155, 3, 69, 57, 36, 0, 111, 97, 114, 100, 3, 69, 123, 34, 70, 0, 97, 115, 105, 99, 3, 69, 129, 86, 37, 49, 0, 7, 6, 99, 0, 4, 1, 101, 114, 2, 111, 3, 49, 0, 1, 115, 97, 112, 2, 97, 108, 0, 2, 117, 115, 0, 8, 2, 97, 108, 0, 8, 2, 108, 97, 117, 0, 8, 2, 111, 109, 0, 8, 2, 111, 114, 0, 8, 97, 109, 2, 114, 0, 8, 115, 2, 111, 0, 107, 1, 97, 112, 0, 107, 1, 111, 108, 0, 107, 8, 97, 112, 2, 97, 0, 114, 101, 97, 116, 105, 8, 3, 49, 34, 36, 35, 47, 37, 0, 111, 118, 101, 114, 3, 49, 35, 82, 44, 0, 97, 8, 115, 2, 110, 3, 49, 36, 0, 116, 114, 108, 3, 49, 39, 50, 47, 14, 16, 39, 55, 0, 111, 103, 110, 105, 1, 101, 114, 2, 116, 3, 49, 39, 79, 50, 37, 0, 104, 3, 99, 0, 3, 115, 0, 7, 6, 100, 0, 2, 32, 3, 47, 0, 4, 3, 70, 0, 2, 32, 17, 70, 0, 2, 105, 28, 17, 0, 2, 195, 173, 28, 17, 0, 4, 197, 190, 3, 73, 0, 197, 190, 2, 32, 17, 70, 0, 197, 190, 2, 32, 3, 74, 0, 4, 2, 105, 3, 77, 0, 2, 195, 173, 0, 2, 196, 155, 0, 122, 2, 32, 3, 115, 0, 4, 122, 3, 116, 0, 122, 2, 32, 17, 70, 0, 7, 6, 101, 0, 3, 36, 0, 121, 1, 107, 3, 119, 0, 117, 3, 126, 0, 106, 2, 25, 3, 129, 0, 7, 6, 102, 0, 3, 81, 0, 196, 155, 3, 81, 57, 36, 0, 7, 6, 103, 0, 2, 32, 3, 49, 0, 4, 3, 79, 0, 2, 32, 17, 70, 0, 7, 6, 104, 0, 2, 32, 3, 99, 0, 4, 3, 105, 0, 2, 32, 17, 70, 0, 7, 6, 105, 0, 97, 3, 2, 37, 35, 0, 101, 3, 2, 37, 36, 0, 117, 3, 2, 37, 40, 0, 103, 104, 116, 1, 17, 67, 3, 35, 57, 47, 0, 3, 37, 0, 97, 2, 32, 3, 37, 35, 0, 101, 2, 32, 3, 37, 57, 36, 0, 105, 2, 32, 3, 37, 57, 37, 0, 111, 2, 32, 3, 37, 57, 39, 0, 117, 2, 32, 3, 37, 57, 40, 0, 8, 2, 111, 110, 3, 57, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 4, 3, 49, 0, 107, 0, 7, 6, 108, 0, 1, 25, 2, 25, 3, 45, 0, 4, 3, 55, 0, 108, 0, 97, 115, 101, 114, 8, 3, 55, 129, 86, 34, 0, 7, 6, 109, 0, 3, 63, 0, 105, 99, 8, 2, 114, 111, 3, 63, 35, 57, 49, 0, 97, 110, 97, 103, 101, 114, 8, 3, 63, 36, 50, 36, 73, 44, 0, 101, 115, 115, 97, 103, 101, 8, 3, 63, 36, 87, 37, 73, 0, 196, 155, 3, 63, 65, 36, 0, 7, 6, 110, 0, 2, 110, 3, 0, 4, 3, 50, 0, 2, 105, 28, 17, 0, 2, 195, 173, 28, 17, 0, 4, 2, 105, 3, 65, 0, 2, 195, 173, 0, 2, 196, 155, 0, 101, 119, 3, 65, 124, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 7, 6, 111, 0, 3, 39, 0, 105, 99, 101, 1, 118, 3, 39, 57, 87, 0, 4, 111, 1, 116, 2, 108, 3, 124, 0, 117, 1, 114, 103, 2, 112, 0, 4, 117, 3, 127, 0, 119, 8, 100, 110, 105, 119, 0, 7, 6, 112, 0, 4, 3, 48, 0, 112, 2, 17, 65, 32, 0, 196, 155, 3, 48, 57, 36, 0, 7, 6, 113, 0, 4, 3, 49, 82, 0, 117, 0, 7, 6, 114, 0, 1, 25, 2, 25, 3, 44, 0, 4, 3, 51, 0, 114, 0, 105, 103, 104, 116, 3, 51, 35, 57, 47, 0, 7, 6, 115, 0, 4, 1, 101, 2, 105, 100, 3, 86, 0, 8, 101, 114, 112, 2, 105, 100, 0, 4, 3, 87, 0, 115, 2, 17, 65, 32, 0, 115, 2, 32, 0, 101, 108, 101, 99, 2, 116, 3, 87, 37, 55, 36, 49, 0, 112, 97, 99, 101, 3, 87, 48, 129, 87, 0, 99, 97, 112, 101, 3, 87, 49, 129, 48, 0, 104, 105, 102, 116, 3, 89, 37, 81, 47, 0, 7, 6, 116, 0, 4, 3, 47, 0, 2, 105, 28, 17, 0, 2, 195, 173, 28, 17, 0, 116, 2, 17, 65, 32, 0, 116, 2, 32, 0, 4, 2, 105, 3, 78, 0, 2, 195, 173, 0, 2, 196, 155, 0, 7, 6, 117, 0, 3, 40, 0, 7, 6, 118, 0, 3, 82, 0, 196, 155, 3, 82, 57, 36, 0, 7, 6, 119, 0, 3, 82, 0, 97, 118, 101, 3, 82, 129, 81, 0, 7, 6, 120, 0, 3, 49, 87, 0, 111, 116, 105, 1, 101, 2, 99, 3, 79, 86, 39, 47, 37, 0, 7, 6, 121, 0, 3, 37, 0, 2, 195, 173, 3, 37, 57, 0, 7, 6, 122, 0, 4, 3, 86, 0, 2, 32, 17, 70, 0, 2, 32, 3, 87, 0, 7, 6, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 195, 171, 3, 36, 0, 195, 188, 3, 37, 0, 197, 149, 3, 44, 0, 196, 186, 3, 45, 0, 45, 8, 32, 2, 32, 15, 3, 63, 119, 50, 40, 87, 0, 36, 3, 70, 39, 55, 122, 51, 0, 195, 182, 3, 121, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts8 = FileInMemory_createWithData (7614, reinterpret_cast (&espeakdata_dicts8_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/cs_dict", L"cs"); Collection_addItem (me.peek(), espeakdata_dicts8.transfer()); static unsigned char espeakdata_dicts9_data[3437] = { 0, 4, 0, 0, 31, 9, 0, 0, 0, 0, 0, 6, 195, 32, 243, 128, 76, 0, 0, 7, 65, 4, 2, 35, 0, 8, 0, 7, 66, 100, 224, 13, 50, 0, 9, 66, 5, 0, 10, 2, 35, 48, 0, 0, 0, 0, 0, 0, 6, 195, 64, 240, 128, 72, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 28, 19, 128, 76, 0, 0, 6, 65, 20, 106, 0, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 36, 107, 0, 76, 0, 0, 0, 0, 8, 197, 28, 19, 12, 92, 224, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 28, 84, 207, 56, 76, 0, 0, 0, 6, 195, 17, 118, 64, 72, 0, 0, 15, 65, 60, 116, 105, 6, 113, 70, 0, 8, 81, 104, 121, 100, 32, 7, 65, 60, 10, 2, 116, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 70, 13, 147, 82, 4, 81, 192, 49, 111, 63, 34, 6, 118, 79, 0, 0, 0, 0, 0, 9, 66, 5, 32, 10, 2, 35, 34, 0, 0, 0, 0, 14, 69, 8, 19, 135, 61, 32, 69, 35, 66, 79, 109, 34, 0, 0, 0, 0, 0, 0, 6, 194, 4, 48, 72, 8, 0, 8, 195, 13, 147, 128, 72, 8, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 33, 115, 128, 76, 0, 0, 12, 4, 95, 49, 77, 49, 63, 6, 112, 55, 10, 0, 0, 0, 6, 195, 100, 224, 64, 76, 8, 195, 93, 37, 8, 72, 8, 11, 0, 0, 5, 65, 100, 13, 0, 0, 0, 0, 0, 0, 9, 66, 5, 64, 10, 2, 35, 47, 0, 0, 6, 195, 28, 20, 192, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 32, 243, 142, 4, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 85, 206, 76, 0, 0, 0, 0, 8, 197, 28, 17, 143, 16, 64, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 72, 133, 206, 28, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 21, 32, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 196, 100, 210, 5, 56, 8, 11, 11, 4, 95, 4, 16, 20, 48, 130, 50, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 28, 19, 12, 4, 224, 72, 6, 195, 4, 195, 0, 72, 0, 0, 0, 0, 0, 0, 7, 67, 100, 225, 192, 13, 0, 6, 195, 56, 85, 64, 8, 0, 0, 0, 0, 6, 195, 56, 85, 68, 76, 0, 0, 0, 5, 194, 28, 16, 76, 9, 66, 4, 208, 10, 2, 35, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 21, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 28, 19, 12, 4, 72, 7, 196, 24, 83, 12, 100, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 24, 80, 76, 0, 6, 195, 24, 83, 0, 72, 0, 0, 0, 0, 0, 0, 0, 6, 195, 17, 147, 65, 72, 0, 0, 0, 0, 0, 6, 195, 16, 19, 128, 72, 6, 195, 16, 19, 128, 76, 7, 195, 16, 19, 128, 8, 11, 7, 195, 80, 19, 128, 8, 11, 0, 0, 0, 0, 0, 7, 196, 28, 19, 12, 36, 72, 7, 196, 4, 50, 15, 76, 8, 0, 0, 0, 6, 195, 52, 244, 128, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 8, 241, 0, 72, 0, 5, 194, 20, 144, 72, 0, 0, 7, 196, 4, 195, 1, 56, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 16, 16, 200, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 68, 40, 243, 133, 76, 73, 116, 50, 87, 0, 0, 0, 6, 195, 17, 147, 129, 72, 5, 194, 25, 144, 72, 0, 0, 0, 0, 0, 6, 195, 33, 147, 128, 76, 0, 0, 0, 0, 7, 195, 56, 84, 192, 8, 11, 0, 7, 196, 4, 195, 23, 56, 72, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 64, 85, 1, 36, 8, 0, 0, 0, 6, 195, 80, 21, 192, 76, 0, 12, 67, 4, 115, 211, 10, 117, 79, 109, 87, 0, 76, 0, 0, 0, 0, 7, 196, 28, 19, 12, 84, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 92, 81, 9, 72, 0, 14, 3, 95, 51, 88, 47, 34, 6, 112, 84, 4, 115, 79, 0, 0, 11, 3, 95, 48, 67, 49, 6, 35, 50, 47, 0, 0, 0, 0, 0, 7, 196, 100, 225, 4, 36, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 66, 32, 144, 105, 112, 0, 76, 0, 0, 14, 3, 95, 50, 67, 70, 6, 120, 79, 4, 35, 50, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 51, 67, 47, 34, 6, 112, 99, 4, 35, 50, 47, 0, 0, 0, 0, 0, 7, 196, 100, 225, 4, 60, 76, 0, 0, 0, 14, 3, 95, 55, 88, 87, 6, 119, 85, 84, 4, 115, 79, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 24, 241, 0, 72, 0, 0, 10, 3, 95, 49, 88, 70, 6, 115, 79, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 50, 88, 70, 6, 120, 84, 4, 115, 79, 0, 0, 0, 12, 69, 33, 81, 200, 21, 48, 105, 125, 12, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 17, 78, 72, 0, 0, 0, 0, 0, 0, 17, 3, 95, 52, 88, 48, 6, 106, 70, 58, 35, 34, 84, 4, 115, 79, 0, 0, 0, 0, 0, 6, 195, 52, 17, 64, 72, 6, 195, 52, 17, 64, 72, 0, 0, 0, 5, 194, 56, 16, 72, 0, 14, 3, 95, 53, 88, 48, 6, 108, 63, 84, 4, 115, 79, 0, 0, 0, 0, 9, 198, 72, 134, 87, 72, 18, 64, 72, 0, 6, 195, 52, 18, 64, 41, 6, 195, 52, 18, 64, 76, 0, 0, 0, 0, 14, 3, 95, 54, 88, 99, 58, 6, 115, 84, 4, 115, 79, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 56, 88, 58, 6, 108, 85, 84, 4, 115, 79, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 57, 88, 50, 6, 121, 84, 4, 115, 79, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 61, 48, 72, 8, 0, 6, 195, 20, 147, 128, 72, 0, 0, 0, 14, 4, 95, 48, 77, 50, 63, 6, 112, 55, 125, 50, 10, 0, 0, 14, 4, 95, 48, 77, 51, 69, 6, 112, 55, 125, 50, 10, 0, 0, 0, 12, 4, 95, 48, 77, 49, 63, 6, 112, 55, 10, 0, 0, 0, 6, 195, 73, 118, 84, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 39, 13, 1, 76, 0, 0, 6, 195, 17, 35, 211, 76, 0, 0, 0, 0, 0, 0, 6, 131, 39, 14, 1, 76, 0, 0, 0, 6, 195, 73, 118, 64, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 17, 37, 217, 76, 0, 0, 0, 11, 3, 195, 180, 12, 10, 2, 116, 55, 0, 11, 0, 0, 0, 0, 0, 0, 0, 8, 66, 56, 144, 50, 112, 0, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 60, 84, 192, 72, 0, 7, 196, 8, 192, 69, 56, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 72, 241, 68, 16, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 33, 115, 142, 4, 76, 0, 0, 0, 0, 0, 8, 197, 84, 228, 136, 101, 112, 72, 0, 0, 0, 0, 0, 0, 0, 7, 196, 72, 128, 73, 56, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 195, 77, 81, 0, 72, 8, 11, 0, 8, 2, 195, 162, 10, 2, 117, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 60, 225, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 60, 129, 82, 93, 145, 4, 8, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 81, 80, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 56, 133, 192, 50, 105, 114, 0, 76, 0, 0, 0, 0, 0, 7, 196, 33, 115, 142, 92, 76, 0, 0, 0, 0, 0, 0, 0, 9, 198, 28, 21, 211, 60, 50, 0, 76, 0, 7, 196, 33, 147, 142, 100, 76, 0, 0, 6, 195, 73, 145, 23, 72, 6, 194, 77, 144, 72, 8, 0, 6, 2, 95, 1, 117, 0, 0, 0, 0, 0, 6, 2, 95, 5, 115, 0, 0, 0, 0, 0, 0, 6, 195, 32, 80, 128, 72, 6, 2, 95, 15, 116, 0, 0, 0, 8, 197, 73, 145, 25, 12, 128, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 25, 111, 0, 0, 8, 66, 80, 144, 47, 112, 0, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 4, 195, 1, 72, 0, 0, 0, 0, 0, 0, 0, 8, 197, 29, 115, 133, 84, 64, 76, 8, 197, 4, 195, 23, 12, 128, 72, 0, 6, 195, 4, 195, 9, 72, 0, 8, 195, 21, 36, 192, 72, 8, 11, 9, 2, 95, 51, 47, 34, 6, 112, 0, 0, 7, 196, 21, 32, 153, 56, 76, 8, 2, 95, 50, 70, 6, 120, 0, 0, 8, 2, 95, 49, 6, 108, 50, 0, 0, 9, 2, 95, 48, 50, 6, 110, 55, 0, 0, 9, 2, 95, 55, 87, 6, 119, 85, 0, 0, 10, 2, 95, 54, 99, 58, 6, 115, 97, 0, 0, 10, 2, 95, 53, 48, 6, 108, 63, 48, 0, 0, 12, 2, 95, 52, 48, 6, 106, 70, 58, 35, 34, 0, 0, 0, 0, 8, 2, 95, 57, 50, 6, 121, 0, 0, 9, 2, 95, 56, 58, 6, 108, 85, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 72, 129, 73, 56, 16, 76, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 73, 112, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 101, 32, 13, 34, 0, 0, 0, 0, 0, 0, 6, 195, 56, 17, 192, 72, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 12, 130, 64, 99, 112, 0, 76, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 73, 147, 128, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 73, 145, 25, 56, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 28, 19, 12, 92, 50, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 28, 21, 211, 60, 224, 76, 0, 0, 0, 0, 0, 0, 6, 195, 73, 144, 200, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 101, 112, 2, 126, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 28, 19, 12, 72, 0, 0, 0, 0, 0, 0, 8, 197, 28, 84, 207, 12, 128, 76, 0, 0, 10, 199, 72, 134, 87, 24, 18, 78, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 72, 129, 73, 56, 144, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 100, 208, 64, 76, 0, 0, 0, 6, 195, 29, 145, 1, 76, 0, 7, 195, 77, 145, 4, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 12, 17, 76, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 101, 48, 146, 100, 64, 66, 0, 0, 8, 195, 76, 133, 196, 72, 8, 11, 0, 0, 0, 0, 0, 0, 0, 6, 66, 100, 208, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 97, 0, 4, 2, 17, 67, 3, 35, 0, 2, 17, 67, 17, 67, 0, 117, 1, 21, 2, 32, 0, 4, 3, 117, 0, 2, 98, 0, 2, 99, 104, 0, 2, 100, 0, 2, 100, 100, 0, 2, 102, 0, 2, 102, 102, 0, 2, 103, 0, 2, 115, 0, 2, 116, 104, 0, 8, 2, 32, 0, 97, 0, 101, 3, 118, 0, 105, 3, 119, 0, 117, 3, 120, 0, 119, 2, 12, 3, 121, 0, 7, 6, 98, 0, 3, 69, 0, 8, 2, 32, 3, 69, 112, 0, 7, 6, 99, 0, 3, 49, 0, 119, 110, 8, 3, 49, 110, 63, 0, 4, 104, 1, 101, 3, 97, 0, 104, 1, 105, 0, 104, 1, 117, 0, 104, 3, 99, 0, 8, 2, 32, 3, 106, 49, 0, 104, 8, 2, 32, 3, 106, 99, 0, 7, 6, 100, 0, 3, 70, 0, 8, 2, 32, 3, 70, 112, 0, 100, 3, 84, 0, 100, 8, 2, 32, 3, 106, 84, 0, 7, 6, 101, 0, 4, 2, 17, 67, 3, 106, 0, 2, 17, 67, 17, 67, 0, 2, 119, 17, 65, 0, 4, 3, 115, 0, 2, 98, 0, 2, 99, 104, 0, 2, 100, 0, 2, 100, 100, 0, 2, 102, 0, 2, 102, 102, 0, 2, 103, 0, 2, 115, 0, 2, 116, 104, 0, 8, 2, 32, 0, 101, 0, 4, 105, 3, 122, 0, 121, 0, 117, 3, 123, 0, 119, 2, 12, 3, 124, 0, 7, 6, 102, 0, 102, 3, 81, 0, 3, 82, 0, 102, 8, 2, 32, 3, 106, 81, 0, 8, 2, 32, 3, 106, 82, 0, 7, 6, 103, 0, 3, 79, 0, 119, 110, 3, 79, 58, 14, 50, 0, 119, 108, 3, 79, 58, 14, 55, 0, 8, 2, 32, 3, 106, 79, 0, 7, 6, 104, 0, 3, 105, 0, 8, 2, 32, 3, 105, 117, 0, 7, 6, 105, 0, 2, 17, 65, 3, 57, 0, 4, 2, 17, 67, 3, 107, 0, 2, 17, 67, 17, 67, 0, 4, 3, 112, 0, 2, 98, 0, 2, 99, 104, 0, 2, 100, 0, 2, 100, 100, 0, 2, 102, 0, 2, 102, 102, 0, 2, 103, 0, 2, 108, 0, 2, 110, 0, 2, 114, 0, 2, 115, 0, 2, 116, 104, 0, 8, 2, 32, 0, 105, 0, 119, 2, 12, 3, 125, 0, 7, 6, 106, 0, 3, 73, 0, 8, 2, 32, 3, 73, 111, 0, 7, 6, 107, 0, 3, 49, 0, 8, 2, 32, 3, 49, 111, 0, 7, 6, 108, 0, 3, 55, 0, 108, 3, 103, 0, 108, 97, 110, 8, 3, 103, 35, 50, 0, 8, 2, 32, 3, 106, 55, 0, 108, 8, 2, 32, 3, 106, 103, 0, 7, 6, 109, 0, 3, 63, 0, 8, 2, 32, 3, 106, 63, 0, 7, 6, 110, 0, 3, 50, 0, 103, 3, 66, 0, 8, 2, 32, 3, 106, 50, 0, 103, 8, 2, 32, 3, 106, 66, 0, 7, 6, 111, 0, 4, 2, 17, 67, 3, 109, 0, 2, 17, 67, 17, 67, 0, 4, 3, 116, 0, 2, 98, 0, 2, 99, 104, 0, 2, 100, 0, 2, 100, 100, 0, 2, 102, 0, 2, 102, 102, 0, 2, 103, 0, 2, 115, 0, 2, 116, 104, 0, 8, 2, 32, 0, 111, 0, 105, 3, 127, 0, 4, 101, 3, 128, 0, 117, 0, 7, 6, 112, 0, 3, 48, 0, 8, 2, 32, 3, 48, 112, 0, 104, 3, 81, 0, 104, 8, 2, 32, 3, 81, 112, 0, 7, 6, 113, 0, 3, 49, 0, 117, 3, 49, 58, 0, 8, 2, 32, 3, 49, 58, 117, 0, 7, 6, 114, 0, 3, 34, 0, 104, 3, 105, 34, 0, 104, 8, 2, 32, 3, 105, 34, 116, 0, 8, 2, 32, 3, 106, 34, 0, 7, 6, 115, 0, 3, 87, 0, 105, 2, 17, 65, 3, 89, 0, 8, 2, 32, 3, 106, 87, 0, 7, 6, 116, 0, 3, 47, 0, 8, 2, 32, 3, 47, 112, 0, 104, 3, 85, 0, 104, 8, 2, 32, 3, 106, 85, 0, 7, 6, 117, 0, 8, 2, 32, 3, 4, 107, 69, 6, 106, 70, 109, 55, 0, 4, 2, 17, 67, 3, 108, 0, 2, 17, 67, 17, 67, 0, 4, 3, 113, 0, 2, 98, 0, 2, 99, 104, 0, 2, 100, 0, 2, 100, 100, 0, 2, 102, 0, 2, 102, 102, 0, 2, 103, 0, 2, 108, 0, 2, 108, 108, 0, 2, 110, 0, 2, 114, 0, 2, 115, 0, 2, 116, 104, 0, 117, 0, 119, 2, 12, 3, 126, 0, 7, 6, 118, 0, 3, 82, 0, 8, 2, 32, 3, 82, 112, 0, 7, 6, 119, 0, 4, 1, 103, 3, 58, 0, 2, 17, 65, 0, 4, 1, 10, 2, 25, 12, 3, 110, 0, 2, 17, 67, 0, 2, 17, 67, 17, 67, 0, 4, 3, 114, 0, 2, 98, 0, 2, 99, 104, 0, 2, 100, 0, 2, 100, 100, 0, 2, 102, 0, 2, 102, 102, 0, 2, 103, 0, 2, 115, 0, 2, 116, 104, 0, 8, 2, 32, 0, 119, 0, 121, 3, 130, 0, 7, 6, 120, 0, 3, 49, 87, 0, 8, 2, 32, 3, 106, 49, 87, 0, 7, 6, 121, 0, 110, 8, 2, 32, 110, 3, 13, 0, 110, 8, 2, 32, 3, 13, 50, 0, 8, 2, 119, 3, 57, 0, 4, 2, 17, 67, 3, 108, 0, 2, 17, 67, 17, 67, 0, 4, 2, 21, 12, 3, 111, 0, 8, 2, 32, 0, 4, 3, 113, 0, 2, 99, 104, 0, 2, 100, 0, 2, 100, 100, 0, 2, 103, 0, 2, 115, 0, 2, 116, 104, 0, 119, 2, 12, 3, 126, 0, 7, 6, 122, 0, 3, 86, 0, 8, 2, 32, 3, 86, 114, 0, 7, 6, 0, 39, 114, 2, 32, 14, 128, 128, 130, 3, 34, 0, 195, 160, 3, 35, 0, 46, 3, 48, 130, 50, 47, 0, 39, 110, 2, 32, 14, 128, 128, 130, 3, 50, 0, 39, 99, 104, 2, 32, 14, 128, 128, 131, 3, 99, 0, 195, 168, 3, 106, 0, 195, 172, 3, 107, 0, 4, 195, 185, 3, 108, 0, 225, 187, 179, 0, 195, 178, 3, 109, 0, 225, 186, 129, 3, 110, 0, 4, 195, 174, 3, 112, 0, 195, 175, 0, 4, 195, 187, 3, 113, 0, 197, 183, 0, 197, 181, 3, 114, 0, 195, 170, 3, 115, 0, 195, 180, 3, 116, 0, 195, 162, 3, 117, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts9 = FileInMemory_createWithData (3436, reinterpret_cast (&espeakdata_dicts9_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/cy_dict", L"cy"); Collection_addItem (me.peek(), espeakdata_dicts9.transfer()); static unsigned char espeakdata_dicts10_data[192094] = { 0, 4, 0, 0, 230, 216, 1, 0, 12, 201, 60, 101, 1, 48, 211, 204, 60, 114, 64, 20, 12, 201, 48, 20, 153, 56, 115, 204, 60, 114, 64, 20, 12, 201, 24, 20, 141, 4, 179, 204, 60, 114, 64, 20, 13, 138, 1, 18, 11, 195, 166, 15, 12, 15, 7, 9, 20, 17, 142, 1, 14, 195, 166, 19, 20, 5, 19, 9, 15, 12, 15, 7, 9, 20, 15, 140, 6, 15, 18, 6, 195, 184, 18, 5, 18, 9, 19, 11, 20, 0, 26, 73, 8, 80, 200, 4, 209, 76, 76, 245, 147, 69, 36, 89, 35, 63, 6, 36, 12, 60, 87, 6, 112, 58, 87, 0, 0, 10, 199, 72, 17, 9, 60, 195, 199, 36, 20, 10, 199, 61, 53, 5, 60, 195, 199, 36, 20, 10, 199, 45, 35, 206, 60, 195, 199, 36, 20, 10, 199, 36, 181, 25, 60, 195, 199, 36, 20, 10, 199, 36, 179, 206, 60, 195, 199, 36, 20, 10, 199, 32, 148, 16, 60, 195, 199, 36, 20, 10, 199, 25, 33, 78, 60, 195, 199, 36, 20, 10, 199, 24, 147, 13, 60, 195, 199, 36, 20, 14, 203, 24, 147, 140, 4, 225, 9, 76, 84, 137, 56, 112, 20, 14, 203, 20, 180, 208, 72, 244, 18, 36, 84, 137, 56, 112, 20, 14, 203, 16, 81, 137, 9, 34, 76, 48, 84, 137, 56, 112, 20, 10, 199, 4, 69, 133, 72, 34, 69, 48, 20, 12, 201, 16, 144, 71, 56, 244, 212, 36, 49, 82, 20, 12, 201, 64, 243, 25, 80, 82, 206, 36, 177, 82, 20, 0, 17, 67, 52, 83, 128, 63, 36, 50, 15, 87, 112, 0, 81, 115, 195, 165, 32, 9, 198, 60, 224, 78, 37, 53, 0, 20, 9, 198, 9, 81, 134, 37, 53, 0, 20, 12, 201, 8, 81, 21, 36, 228, 212, 4, 211, 69, 67, 9, 198, 76, 84, 150, 36, 49, 82, 20, 9, 198, 16, 84, 193, 72, 209, 82, 20, 9, 198, 5, 4, 12, 36, 177, 82, 20, 12, 137, 19, 22, 195, 166, 18, 13, 5, 18, 9, 20, 12, 137, 4, 18, 195, 184, 13, 13, 5, 18, 9, 20, 9, 198, 4, 96, 84, 36, 177, 82, 20, 6, 195, 52, 83, 128, 8, 0, 9, 198, 36, 225, 21, 77, 68, 137, 20, 0, 13, 202, 64, 20, 143, 16, 243, 148, 60, 195, 199, 36, 20, 9, 198, 21, 33, 207, 56, 243, 64, 20, 9, 198, 4, 116, 143, 56, 243, 64, 20, 8, 197, 8, 192, 77, 21, 32, 20, 10, 135, 22, 195, 165, 19, 5, 18, 9, 20, 0, 9, 198, 65, 54, 75, 61, 49, 64, 20, 9, 198, 48, 22, 129, 72, 243, 128, 20, 9, 198, 80, 244, 147, 36, 243, 128, 20, 9, 198, 77, 64, 68, 36, 243, 128, 20, 9, 198, 8, 147, 12, 36, 243, 128, 20, 9, 198, 5, 82, 212, 36, 243, 128, 20, 12, 137, 7, 18, 195, 166, 3, 9, 19, 5, 18, 20, 11, 136, 6, 195, 166, 18, 7, 5, 18, 9, 20, 9, 198, 5, 0, 84, 37, 50, 192, 20, 12, 201, 52, 83, 1, 56, 179, 204, 36, 177, 82, 20, 12, 201, 16, 144, 71, 56, 244, 212, 36, 177, 82, 20, 10, 199, 52, 21, 83, 60, 193, 85, 52, 20, 9, 198, 4, 48, 197, 77, 50, 84, 20, 7, 196, 5, 0, 84, 36, 20, 9, 198, 56, 146, 207, 80, 147, 128, 20, 9, 198, 44, 20, 143, 80, 147, 128, 20, 10, 199, 33, 83, 65, 56, 148, 205, 20, 20, 10, 199, 4, 197, 18, 84, 148, 205, 20, 20, 9, 198, 76, 20, 129, 12, 83, 128, 20, 9, 198, 64, 19, 129, 52, 19, 128, 20, 9, 198, 44, 243, 150, 20, 229, 0, 20, 10, 199, 64, 84, 141, 4, 225, 78, 76, 20, 9, 198, 44, 243, 148, 4, 229, 0, 20, 9, 198, 5, 0, 78, 4, 113, 64, 20, 0, 17, 70, 72, 82, 137, 12, 84, 133, 34, 36, 57, 37, 87, 6, 36, 112, 0, 10, 199, 65, 35, 195, 20, 69, 82, 20, 20, 10, 199, 80, 19, 80, 60, 225, 82, 20, 20, 10, 199, 80, 16, 133, 48, 193, 82, 20, 20, 10, 199, 72, 80, 133, 48, 193, 82, 20, 20, 10, 199, 52, 241, 5, 48, 193, 82, 20, 20, 10, 199, 16, 84, 201, 28, 225, 82, 20, 20, 10, 199, 5, 4, 5, 48, 193, 82, 20, 20, 9, 198, 81, 38, 76, 48, 84, 137, 20, 9, 198, 49, 83, 83, 44, 84, 137, 20, 9, 198, 45, 82, 143, 56, 84, 137, 20, 9, 198, 45, 38, 68, 16, 84, 137, 20, 9, 198, 44, 192, 84, 80, 84, 137, 20, 9, 198, 17, 34, 76, 48, 84, 137, 20, 10, 199, 4, 224, 75, 60, 197, 84, 36, 20, 0, 11, 200, 77, 65, 82, 20, 244, 203, 61, 0, 20, 9, 198, 20, 193, 75, 81, 35, 206, 20, 7, 196, 52, 84, 193, 56, 21, 0, 12, 201, 81, 32, 78, 76, 101, 83, 36, 243, 128, 20, 12, 201, 77, 84, 16, 72, 84, 211, 36, 243, 128, 20, 12, 201, 72, 84, 1, 73, 66, 84, 36, 243, 128, 20, 12, 201, 45, 96, 68, 72, 147, 12, 36, 243, 128, 20, 12, 201, 44, 243, 80, 72, 84, 211, 36, 243, 128, 20, 12, 201, 36, 229, 5, 72, 18, 212, 36, 243, 128, 20, 12, 201, 20, 180, 208, 20, 66, 84, 36, 243, 128, 20, 12, 201, 24, 147, 15, 76, 241, 137, 45, 83, 64, 20, 12, 201, 80, 84, 146, 37, 67, 210, 37, 83, 64, 20, 12, 201, 60, 97, 133, 73, 67, 210, 37, 83, 64, 20, 8, 197, 16, 83, 148, 36, 224, 20, 8, 197, 8, 84, 140, 36, 224, 20, 13, 202, 88, 144, 212, 61, 34, 65, 56, 148, 205, 20, 20, 13, 202, 60, 36, 203, 85, 32, 78, 80, 148, 205, 20, 20, 13, 202, 16, 242, 212, 72, 147, 129, 72, 148, 205, 20, 20, 8, 197, 8, 84, 140, 36, 224, 20, 8, 197, 45, 83, 80, 4, 224, 21, 6, 65, 8, 69, 36, 0, 0, 18, 70, 52, 19, 129, 29, 80, 64, 63, 108, 50, 6, 108, 12, 79, 58, 108, 0, 9, 198, 72, 80, 75, 80, 244, 128, 20, 9, 198, 77, 1, 78, 16, 84, 128, 20, 9, 198, 76, 84, 15, 56, 84, 128, 20, 9, 198, 72, 84, 207, 56, 84, 128, 20, 9, 198, 72, 82, 137, 12, 84, 128, 20, 9, 198, 64, 245, 83, 76, 84, 128, 20, 9, 198, 61, 33, 9, 56, 84, 128, 20, 9, 198, 61, 4, 15, 56, 84, 128, 20, 9, 198, 44, 195, 193, 44, 84, 128, 20, 9, 198, 36, 212, 15, 56, 84, 128, 20, 9, 198, 25, 32, 80, 64, 84, 128, 20, 9, 198, 20, 225, 193, 28, 84, 128, 20, 9, 198, 5, 52, 213, 72, 84, 128, 20, 15, 140, 12, 195, 184, 19, 7, 195, 166, 14, 7, 5, 18, 9, 20, 8, 133, 195, 184, 4, 5, 13, 20, 9, 198, 5, 97, 79, 48, 20, 128, 20, 9, 198, 52, 147, 9, 80, 19, 148, 20, 9, 198, 4, 66, 149, 16, 19, 148, 20, 0, 10, 199, 32, 148, 212, 60, 195, 199, 36, 20, 9, 198, 52, 243, 143, 52, 19, 137, 20, 10, 199, 77, 82, 203, 84, 193, 78, 80, 20, 14, 203, 56, 21, 18, 37, 83, 66, 20, 230, 143, 5, 64, 20, 10, 199, 5, 48, 197, 56, 64, 78, 80, 20, 0, 15, 204, 44, 20, 129, 45, 65, 82, 37, 53, 9, 45, 83, 64, 20, 9, 198, 4, 224, 76, 101, 48, 66, 20, 7, 196, 21, 64, 71, 20, 20, 9, 68, 76, 208, 76, 48, 21, 0, 10, 0, 12, 201, 88, 149, 1, 52, 147, 137, 76, 84, 128, 20, 12, 201, 84, 225, 5, 73, 101, 82, 16, 84, 128, 20, 12, 201, 81, 32, 78, 77, 3, 210, 80, 84, 128, 20, 12, 201, 81, 32, 78, 76, 99, 210, 52, 84, 128, 20, 12, 201, 77, 68, 129, 80, 145, 137, 12, 84, 128, 20, 12, 201, 72, 83, 210, 28, 19, 137, 76, 84, 128, 20, 12, 201, 36, 229, 5, 72, 99, 204, 36, 84, 128, 20, 12, 201, 36, 212, 12, 20, 209, 78, 80, 84, 128, 20, 12, 201, 28, 192, 77, 61, 84, 137, 76, 84, 128, 20, 12, 201, 25, 32, 84, 21, 35, 137, 76, 84, 128, 20, 12, 201, 5, 85, 15, 56, 243, 73, 76, 84, 128, 20, 8, 197, 32, 245, 133, 72, 144, 20, 8, 197, 64, 85, 18, 60, 192, 20, 12, 201, 76, 178, 83, 52, 21, 9, 44, 84, 128, 20, 12, 201, 64, 20, 129, 49, 149, 9, 44, 84, 128, 20, 12, 201, 21, 128, 197, 57, 68, 137, 44, 84, 128, 20, 12, 201, 8, 192, 83, 24, 83, 73, 44, 84, 128, 20, 11, 136, 195, 184, 11, 15, 14, 15, 13, 9, 20, 6, 65, 12, 87, 36, 0, 0, 17, 70, 8, 83, 9, 104, 84, 128, 69, 36, 55, 37, 12, 87, 112, 0, 66, 12, 202, 65, 54, 75, 60, 96, 82, 52, 18, 207, 56, 9, 198, 72, 83, 133, 28, 84, 128, 20, 9, 198, 60, 97, 133, 72, 84, 128, 20, 9, 198, 52, 241, 5, 72, 84, 128, 20, 9, 198, 52, 148, 197, 72, 84, 128, 20, 9, 198, 36, 227, 143, 88, 84, 128, 20, 9, 198, 36, 225, 9, 12, 84, 128, 20, 9, 198, 24, 192, 77, 8, 84, 128, 20, 9, 198, 16, 148, 137, 28, 84, 128, 20, 9, 198, 16, 85, 15, 56, 84, 128, 20, 9, 198, 16, 84, 15, 56, 84, 128, 20, 9, 198, 16, 83, 9, 72, 84, 128, 20, 9, 198, 8, 147, 208, 80, 84, 128, 20, 12, 201, 45, 33, 65, 80, 147, 206, 37, 51, 69, 20, 9, 198, 45, 99, 212, 36, 83, 148, 20, 9, 198, 48, 81, 193, 80, 20, 128, 20, 9, 198, 76, 82, 211, 80, 19, 148, 20, 9, 198, 60, 178, 213, 64, 19, 148, 20, 9, 198, 45, 96, 68, 72, 19, 148, 20, 9, 198, 88, 84, 137, 80, 16, 128, 20, 0, 9, 198, 4, 116, 143, 56, 243, 73, 20, 9, 198, 4, 229, 9, 24, 243, 137, 20, 10, 199, 8, 144, 140, 36, 243, 65, 56, 21, 14, 4, 95, 8, 1, 3, 105, 6, 35, 74, 4, 107, 49, 0, 0, 14, 139, 7, 25, 14, 195, 166, 11, 15, 12, 15, 7, 9, 20, 11, 200, 77, 81, 199, 21, 53, 9, 60, 224, 20, 11, 200, 72, 84, 207, 73, 5, 9, 60, 224, 20, 9, 198, 44, 20, 142, 20, 243, 0, 20, 9, 198, 25, 33, 85, 16, 144, 78, 20, 0, 12, 201, 72, 81, 201, 77, 68, 129, 80, 244, 128, 20, 12, 201, 44, 243, 147, 21, 37, 129, 80, 244, 128, 20, 12, 201, 44, 243, 132, 20, 228, 193, 80, 244, 128, 20, 12, 201, 44, 243, 80, 20, 228, 193, 80, 244, 128, 20, 12, 201, 36, 195, 21, 77, 68, 129, 80, 244, 128, 20, 10, 135, 2, 5, 19, 22, 195, 166, 18, 20, 12, 201, 64, 243, 25, 52, 84, 137, 76, 84, 128, 20, 12, 201, 64, 192, 83, 80, 145, 137, 12, 84, 128, 20, 12, 201, 61, 3, 65, 28, 20, 201, 56, 84, 128, 20, 12, 201, 45, 96, 78, 80, 145, 137, 12, 84, 128, 20, 12, 201, 32, 145, 82, 5, 34, 201, 76, 84, 128, 20, 12, 201, 29, 147, 78, 5, 53, 9, 12, 84, 128, 20, 8, 197, 4, 226, 77, 21, 32, 20, 12, 201, 32, 243, 73, 48, 85, 9, 44, 84, 128, 20, 12, 201, 16, 144, 76, 20, 181, 9, 44, 84, 128, 20, 15, 204, 36, 229, 5, 73, 97, 78, 80, 147, 206, 37, 51, 69, 20, 6, 65, 16, 70, 36, 0, 0, 11, 136, 20, 5, 18, 20, 9, 195, 166, 18, 20, 11, 136, 8, 15, 14, 15, 18, 195, 166, 18, 20, 9, 198, 104, 243, 206, 61, 49, 64, 20, 9, 198, 56, 20, 139, 61, 49, 64, 20, 9, 198, 28, 197, 75, 61, 49, 64, 20, 16, 141, 6, 195, 166, 14, 15, 13, 5, 14, 15, 12, 15, 7, 9, 20, 9, 198, 76, 244, 130, 37, 67, 204, 20, 17, 70, 64, 83, 132, 4, 229, 0, 48, 110, 66, 70, 6, 110, 66, 0, 20, 0, 9, 198, 45, 82, 143, 56, 84, 133, 20, 9, 198, 44, 20, 146, 36, 84, 133, 20, 9, 198, 29, 34, 76, 48, 84, 133, 20, 10, 199, 61, 1, 143, 72, 209, 82, 20, 20, 9, 198, 48, 18, 197, 72, 84, 137, 20, 9, 198, 29, 37, 66, 48, 84, 137, 20, 10, 199, 21, 35, 212, 60, 208, 78, 36, 20, 9, 198, 33, 148, 132, 36, 225, 5, 20, 11, 67, 76, 147, 128, 87, 6, 37, 50, 0, 76, 0, 9, 198, 65, 35, 205, 61, 67, 210, 20, 11, 200, 12, 84, 148, 36, 98, 75, 5, 64, 20, 13, 138, 16, 18, 195, 166, 19, 5, 14, 20, 1, 2, 20, 0, 9, 198, 61, 67, 211, 44, 244, 0, 20, 12, 201, 45, 33, 65, 80, 149, 137, 80, 85, 0, 20, 12, 201, 88, 147, 132, 36, 49, 82, 36, 225, 192, 20, 12, 201, 77, 80, 147, 84, 209, 82, 36, 225, 192, 20, 12, 201, 76, 83, 5, 45, 65, 82, 36, 225, 192, 20, 12, 201, 64, 192, 84, 36, 225, 82, 36, 225, 192, 20, 12, 201, 64, 20, 211, 37, 97, 82, 36, 225, 192, 20, 12, 201, 64, 20, 208, 60, 193, 82, 36, 225, 192, 20, 12, 201, 61, 34, 69, 57, 65, 82, 36, 225, 192, 20, 12, 201, 52, 20, 141, 61, 33, 82, 36, 225, 192, 20, 12, 201, 48, 19, 69, 57, 65, 82, 36, 225, 192, 20, 12, 201, 45, 84, 147, 37, 97, 82, 36, 225, 192, 20, 12, 201, 44, 244, 212, 84, 209, 82, 36, 225, 192, 20, 12, 201, 44, 243, 134, 21, 33, 82, 36, 225, 192, 20, 12, 201, 44, 243, 66, 36, 225, 82, 36, 225, 192, 20, 12, 201, 44, 19, 11, 84, 193, 82, 36, 225, 192, 20, 12, 201, 36, 229, 5, 72, 225, 82, 36, 225, 192, 20, 12, 201, 36, 228, 212, 73, 81, 82, 36, 225, 192, 20, 12, 201, 36, 225, 143, 72, 209, 82, 36, 225, 192, 20, 12, 201, 36, 225, 12, 21, 97, 82, 36, 225, 192, 20, 12, 201, 24, 245, 82, 4, 113, 82, 36, 225, 192, 20, 12, 201, 20, 180, 208, 60, 225, 82, 36, 225, 192, 20, 12, 201, 16, 148, 208, 60, 225, 82, 36, 225, 192, 20, 12, 201, 16, 147, 73, 81, 65, 82, 36, 225, 192, 20, 12, 201, 16, 83, 69, 57, 65, 82, 36, 225, 192, 20, 12, 201, 16, 82, 204, 36, 225, 82, 36, 225, 192, 20, 12, 201, 16, 82, 204, 5, 33, 82, 36, 225, 192, 20, 12, 201, 12, 83, 5, 9, 33, 82, 36, 225, 192, 20, 12, 201, 8, 192, 78, 12, 129, 82, 36, 225, 192, 20, 12, 201, 8, 19, 1, 56, 49, 82, 36, 225, 192, 20, 12, 201, 5, 4, 18, 60, 33, 82, 36, 225, 192, 20, 12, 201, 48, 245, 134, 61, 35, 69, 48, 145, 192, 20, 0, 11, 136, 11, 22, 195, 166, 19, 20, 15, 18, 20, 9, 198, 21, 0, 85, 48, 85, 0, 20, 9, 198, 52, 147, 12, 36, 243, 128, 20, 9, 198, 20, 194, 83, 36, 243, 128, 20, 9, 198, 76, 19, 137, 80, 85, 0, 20, 9, 198, 44, 21, 137, 80, 85, 0, 20, 9, 198, 20, 229, 9, 80, 85, 0, 20, 9, 198, 44, 20, 146, 85, 49, 76, 20, 12, 201, 77, 80, 138, 20, 181, 9, 88, 84, 133, 20, 12, 201, 29, 82, 76, 48, 245, 9, 56, 84, 133, 20, 12, 201, 16, 147, 5, 81, 64, 78, 80, 84, 137, 20, 9, 198, 77, 147, 148, 21, 49, 64, 20, 9, 198, 16, 82, 207, 73, 83, 64, 20, 9, 198, 56, 144, 133, 56, 149, 0, 20, 9, 198, 16, 242, 212, 72, 147, 128, 20, 12, 137, 7, 18, 195, 166, 3, 9, 19, 13, 5, 20, 9, 198, 72, 81, 133, 72, 21, 0, 20, 9, 198, 36, 229, 18, 36, 176, 84, 20, 9, 198, 36, 226, 21, 52, 19, 128, 21, 9, 198, 17, 83, 3, 36, 19, 128, 21, 9, 198, 4, 116, 129, 52, 19, 128, 21, 0, 9, 198, 4, 84, 143, 17, 35, 205, 20, 10, 199, 24, 19, 19, 44, 225, 82, 36, 20, 10, 199, 77, 98, 71, 4, 117, 9, 28, 20, 9, 198, 52, 17, 206, 21, 50, 69, 20, 10, 199, 80, 84, 141, 60, 116, 129, 24, 20, 10, 199, 44, 244, 133, 60, 116, 129, 24, 20, 10, 199, 77, 98, 71, 4, 117, 9, 28, 20, 0, 9, 198, 48, 16, 146, 4, 67, 210, 20, 9, 198, 44, 244, 146, 36, 67, 210, 20, 9, 198, 20, 193, 86, 5, 67, 210, 20, 15, 204, 81, 32, 78, 77, 3, 1, 57, 65, 82, 36, 225, 192, 20, 15, 204, 80, 82, 206, 60, 195, 199, 37, 49, 82, 36, 225, 192, 20, 15, 204, 44, 243, 80, 72, 243, 73, 81, 65, 82, 36, 225, 192, 20, 15, 204, 36, 228, 212, 73, 83, 69, 57, 65, 82, 36, 225, 192, 20, 15, 204, 36, 211, 65, 81, 34, 75, 84, 193, 82, 36, 225, 192, 20, 15, 204, 8, 144, 140, 36, 241, 210, 4, 97, 82, 36, 225, 192, 20, 9, 198, 77, 147, 132, 36, 177, 82, 20, 9, 198, 73, 80, 146, 36, 49, 82, 20, 9, 198, 24, 84, 142, 37, 49, 82, 20, 15, 204, 20, 180, 200, 36, 34, 84, 36, 243, 137, 76, 209, 64, 20, 6, 195, 76, 147, 133, 76, 0, 12, 201, 81, 32, 78, 76, 18, 212, 36, 243, 128, 20, 12, 201, 72, 84, 212, 37, 69, 84, 36, 243, 128, 20, 12, 201, 64, 244, 201, 80, 149, 137, 80, 85, 0, 20, 12, 201, 56, 81, 193, 80, 149, 137, 80, 85, 0, 20, 12, 201, 52, 147, 137, 77, 65, 82, 37, 83, 64, 20, 8, 197, 80, 84, 141, 36, 176, 20, 8, 197, 80, 83, 210, 20, 208, 20, 8, 197, 8, 17, 193, 28, 80, 20, 6, 65, 24, 107, 81, 0, 0, 10, 135, 11, 21, 18, 9, 195, 184, 19, 20, 9, 198, 65, 83, 12, 36, 213, 84, 20, 9, 198, 28, 83, 204, 60, 114, 64, 20, 9, 198, 17, 35, 199, 37, 53, 0, 20, 13, 202, 25, 37, 71, 81, 51, 205, 52, 83, 9, 28, 20, 9, 198, 64, 19, 132, 20, 210, 64, 20, 9, 198, 60, 33, 21, 12, 83, 148, 20, 0, 10, 199, 48, 147, 78, 60, 195, 199, 36, 20, 10, 199, 29, 32, 70, 60, 195, 199, 36, 20, 10, 199, 28, 83, 77, 60, 195, 199, 36, 20, 10, 199, 5, 81, 9, 60, 195, 199, 36, 20, 12, 137, 16, 18, 195, 166, 3, 9, 19, 5, 18, 20, 12, 201, 64, 84, 147, 60, 226, 70, 36, 49, 82, 20, 12, 201, 52, 20, 203, 84, 194, 78, 37, 49, 82, 20, 10, 199, 36, 70, 76, 48, 146, 197, 72, 20, 10, 199, 8, 245, 1, 56, 146, 197, 72, 20, 13, 138, 16, 18, 195, 166, 12, 21, 4, 9, 21, 13, 20, 17, 70, 105, 80, 195, 32, 147, 137, 87, 40, 49, 6, 37, 50, 37, 0, 20, 9, 198, 49, 81, 15, 52, 19, 137, 20, 12, 201, 25, 83, 132, 4, 209, 78, 80, 19, 0, 20, 10, 199, 8, 20, 212, 60, 224, 68, 20, 20, 0, 9, 134, 22, 9, 7, 195, 184, 18, 20, 7, 196, 45, 84, 15, 56, 20, 11, 200, 80, 21, 15, 88, 84, 137, 56, 112, 20, 11, 200, 76, 242, 71, 56, 84, 137, 56, 112, 20, 11, 200, 20, 210, 71, 72, 84, 137, 56, 112, 20, 11, 200, 16, 81, 137, 48, 84, 137, 56, 112, 20, 11, 200, 8, 243, 137, 80, 84, 137, 56, 112, 20, 9, 198, 77, 1, 67, 36, 83, 0, 20, 11, 200, 16, 148, 212, 4, 224, 197, 72, 80, 20, 11, 200, 5, 52, 201, 77, 64, 78, 12, 80, 20, 9, 198, 61, 5, 9, 52, 19, 0, 20, 0, 13, 138, 13, 25, 19, 20, 5, 18, 9, 195, 184, 19, 20, 10, 135, 13, 1, 19, 19, 195, 184, 18, 20, 10, 135, 13, 1, 18, 11, 195, 184, 18, 20, 8, 197, 56, 147, 194, 36, 80, 20, 8, 197, 20, 228, 201, 4, 224, 21, 8, 197, 53, 84, 197, 4, 192, 20, 6, 65, 28, 79, 36, 0, 0, 9, 198, 72, 84, 1, 72, 84, 128, 20, 9, 198, 64, 17, 201, 56, 84, 128, 20, 9, 198, 45, 98, 84, 80, 84, 128, 20, 9, 198, 40, 243, 137, 76, 84, 128, 20, 9, 198, 36, 225, 9, 44, 84, 128, 20, 9, 198, 28, 195, 211, 76, 84, 128, 20, 13, 202, 20, 180, 203, 60, 211, 85, 56, 146, 197, 72, 20, 9, 198, 8, 20, 146, 36, 84, 128, 20, 9, 198, 4, 33, 9, 12, 84, 128, 20, 12, 201, 52, 20, 203, 84, 194, 78, 37, 51, 69, 20, 9, 198, 76, 192, 86, 60, 98, 76, 20, 9, 198, 88, 81, 197, 80, 20, 128, 20, 0, 12, 137, 18, 5, 7, 9, 19, 19, 195, 184, 18, 20, 9, 198, 25, 148, 201, 85, 33, 201, 20, 9, 198, 88, 20, 197, 48, 147, 133, 20, 9, 198, 28, 83, 1, 80, 147, 133, 20, 14, 203, 72, 83, 1, 80, 149, 137, 76, 84, 137, 56, 112, 20, 10, 199, 52, 19, 137, 65, 83, 5, 72, 20, 10, 199, 48, 81, 201, 80, 147, 69, 72, 20, 9, 198, 76, 18, 210, 37, 53, 9, 20, 9, 198, 88, 20, 197, 48, 147, 133, 20, 10, 199, 72, 145, 207, 72, 148, 205, 20, 20, 10, 199, 32, 147, 132, 84, 148, 205, 20, 20, 10, 199, 28, 21, 76, 48, 148, 205, 20, 20, 9, 198, 20, 194, 84, 37, 51, 69, 20, 10, 199, 16, 148, 137, 28, 148, 205, 20, 20, 10, 199, 88, 242, 193, 9, 83, 1, 72, 20, 6, 195, 44, 19, 128, 76, 14, 4, 95, 51, 88, 15, 47, 34, 6, 109, 81, 47, 13, 0, 0, 11, 200, 88, 145, 9, 52, 84, 137, 56, 112, 20, 11, 200, 56, 243, 73, 56, 84, 137, 56, 112, 20, 11, 200, 52, 84, 137, 80, 84, 137, 56, 112, 20, 11, 200, 5, 96, 78, 12, 84, 137, 56, 112, 20, 7, 196, 20, 180, 201, 48, 20, 0, 28, 67, 80, 245, 82, 47, 40, 12, 13, 70, 13, 15, 6, 81, 112, 12, 87, 0, 82, 100, 101, 32, 102, 111, 114, 99, 101, 32, 12, 201, 36, 225, 137, 49, 68, 129, 80, 244, 128, 20, 12, 201, 16, 83, 79, 17, 83, 1, 80, 244, 128, 20, 10, 135, 18, 1, 4, 9, 195, 166, 18, 20, 12, 201, 44, 243, 12, 5, 66, 79, 56, 84, 128, 20, 12, 201, 12, 83, 148, 72, 19, 9, 76, 84, 128, 20, 7, 65, 32, 105, 111, 12, 0, 0, 9, 198, 8, 243, 137, 80, 85, 0, 20, 9, 198, 4, 194, 193, 48, 242, 68, 20, 9, 198, 64, 84, 137, 45, 83, 64, 20, 9, 198, 16, 81, 137, 56, 149, 0, 20, 9, 198, 88, 20, 197, 48, 147, 128, 20, 9, 198, 48, 80, 201, 80, 147, 128, 20, 12, 201, 72, 21, 9, 60, 224, 76, 37, 51, 69, 20, 12, 201, 64, 21, 5, 72, 224, 76, 37, 51, 69, 20, 9, 198, 77, 147, 132, 36, 176, 84, 20, 9, 198, 52, 243, 143, 52, 19, 128, 21, 9, 198, 49, 81, 15, 52, 19, 128, 21, 9, 198, 5, 54, 76, 4, 229, 0, 20, 0, 25, 67, 28, 21, 128, 79, 108, 15, 87, 35, 57, 15, 47, 36, 55, 0, 82, 115, 105, 103, 32, 116, 105, 108, 32, 14, 203, 84, 68, 1, 72, 49, 76, 48, 84, 137, 56, 112, 20, 14, 203, 36, 225, 11, 4, 194, 213, 48, 84, 137, 56, 112, 20, 10, 199, 77, 68, 137, 44, 177, 82, 36, 20, 9, 198, 44, 21, 5, 28, 244, 137, 20, 6, 195, 5, 67, 204, 20, 0, 6, 195, 5, 67, 205, 20, 9, 198, 25, 84, 201, 60, 225, 82, 20, 9, 198, 8, 20, 212, 60, 225, 82, 20, 9, 1, 35, 50, 6, 111, 63, 112, 0, 0, 22, 65, 36, 37, 15, 49, 82, 6, 110, 12, 70, 112, 0, 81, 107, 118, 97, 114, 116, 101, 114, 32, 12, 201, 44, 20, 130, 61, 37, 78, 17, 83, 64, 20, 12, 201, 64, 20, 148, 36, 50, 80, 37, 83, 64, 20, 15, 204, 65, 35, 198, 21, 52, 201, 60, 224, 76, 37, 51, 69, 20, 12, 201, 4, 193, 75, 76, 19, 132, 72, 147, 128, 20, 7, 65, 36, 10, 37, 0, 76, 0, 9, 198, 77, 64, 84, 36, 243, 128, 20, 11, 136, 8, 195, 165, 14, 4, 20, 5, 18, 20, 13, 202, 44, 243, 147, 21, 37, 129, 80, 244, 137, 20, 20, 9, 198, 52, 17, 206, 21, 50, 84, 20, 9, 198, 28, 20, 207, 48, 147, 128, 20, 9, 198, 65, 84, 137, 80, 19, 128, 20, 13, 1, 37, 48, 51, 39, 87, 6, 36, 50, 70, 0, 27, 0, 10, 199, 53, 84, 201, 44, 243, 15, 28, 20, 10, 199, 25, 85, 21, 72, 243, 15, 28, 20, 10, 199, 21, 50, 201, 52, 243, 15, 28, 20, 10, 199, 16, 83, 132, 72, 243, 15, 28, 20, 9, 198, 77, 2, 79, 56, 84, 133, 20, 9, 198, 52, 20, 137, 56, 84, 133, 20, 9, 198, 29, 37, 78, 16, 84, 133, 20, 9, 198, 28, 20, 129, 28, 84, 133, 20, 9, 198, 24, 145, 213, 72, 84, 133, 20, 9, 198, 81, 38, 75, 44, 84, 137, 20, 9, 198, 76, 225, 82, 64, 84, 137, 20, 9, 198, 76, 180, 137, 88, 84, 137, 20, 10, 199, 48, 19, 135, 52, 241, 9, 28, 20, 10, 199, 24, 244, 133, 56, 83, 9, 28, 20, 10, 199, 32, 83, 22, 21, 66, 83, 44, 20, 10, 199, 20, 226, 204, 37, 66, 83, 44, 20, 10, 199, 20, 224, 217, 44, 194, 83, 44, 20, 10, 199, 8, 84, 130, 21, 34, 83, 44, 20, 12, 201, 81, 148, 15, 80, 82, 206, 36, 177, 82, 20, 15, 140, 16, 18, 15, 16, 195, 166, 4, 5, 21, 20, 9, 11, 20, 10, 199, 77, 65, 78, 60, 116, 129, 24, 20, 10, 199, 48, 19, 135, 4, 117, 9, 28, 20, 12, 137, 6, 195, 184, 4, 19, 5, 12, 1, 18, 20, 6, 1, 38, 112, 58, 0, 0, 9, 198, 36, 225, 21, 45, 67, 210, 20, 7, 196, 64, 241, 83, 36, 20, 13, 138, 195, 166, 11, 22, 9, 22, 1, 12, 5, 18, 20, 7, 196, 64, 19, 137, 44, 20, 11, 200, 64, 243, 148, 36, 98, 75, 5, 64, 20, 13, 1, 39, 35, 48, 39, 87, 47, 34, 6, 112, 81, 0, 0, 12, 201, 81, 33, 80, 4, 224, 84, 36, 243, 128, 20, 12, 201, 65, 35, 198, 4, 224, 84, 36, 243, 128, 20, 12, 201, 44, 243, 208, 21, 32, 84, 36, 243, 128, 20, 12, 201, 36, 228, 203, 72, 148, 20, 36, 243, 128, 20, 12, 201, 36, 226, 193, 72, 224, 84, 36, 243, 128, 20, 12, 201, 25, 37, 83, 81, 32, 84, 36, 243, 128, 20, 12, 201, 21, 96, 80, 61, 32, 84, 36, 243, 128, 20, 12, 201, 16, 84, 18, 5, 96, 84, 36, 243, 128, 20, 12, 201, 5, 36, 133, 77, 64, 84, 36, 243, 128, 20, 12, 201, 4, 97, 133, 45, 64, 84, 36, 243, 128, 20, 12, 201, 4, 48, 197, 65, 64, 84, 36, 243, 128, 20, 8, 197, 44, 20, 130, 60, 192, 20, 12, 201, 12, 19, 9, 24, 244, 142, 36, 83, 128, 20, 8, 197, 4, 180, 201, 4, 192, 20, 7, 65, 40, 57, 112, 84, 0, 0, 9, 198, 81, 148, 9, 76, 84, 128, 20, 9, 198, 80, 243, 5, 72, 84, 128, 20, 9, 198, 77, 81, 134, 48, 84, 128, 20, 9, 198, 77, 64, 71, 56, 84, 128, 20, 9, 198, 76, 84, 1, 72, 84, 128, 20, 15, 204, 65, 35, 198, 21, 52, 201, 60, 224, 76, 37, 49, 82, 20, 9, 198, 52, 83, 129, 28, 84, 128, 20, 9, 198, 44, 243, 15, 72, 84, 128, 20, 9, 198, 36, 243, 137, 76, 84, 128, 20, 9, 198, 28, 19, 15, 56, 84, 128, 20, 9, 198, 21, 64, 66, 48, 84, 128, 20, 9, 198, 16, 19, 137, 76, 84, 128, 20, 9, 198, 5, 97, 82, 80, 84, 128, 20, 9, 198, 4, 67, 213, 12, 84, 128, 20, 12, 201, 44, 148, 211, 20, 210, 83, 76, 84, 137, 20, 13, 202, 77, 147, 139, 72, 85, 9, 77, 66, 83, 44, 20, 13, 202, 76, 84, 1, 72, 21, 9, 77, 66, 83, 44, 20, 13, 202, 52, 147, 137, 52, 19, 9, 77, 66, 83, 44, 20, 13, 202, 25, 32, 71, 52, 83, 148, 5, 34, 83, 44, 20, 13, 202, 24, 147, 1, 80, 83, 9, 77, 66, 83, 44, 20, 13, 202, 16, 242, 213, 52, 83, 148, 5, 34, 83, 44, 20, 13, 202, 5, 34, 201, 80, 82, 212, 60, 226, 83, 44, 20, 9, 198, 16, 148, 137, 28, 83, 148, 20, 0, 12, 201, 44, 243, 131, 20, 229, 18, 5, 67, 210, 20, 10, 199, 44, 244, 205, 60, 195, 199, 36, 20, 12, 201, 4, 32, 146, 21, 98, 65, 80, 147, 206, 20, 10, 199, 36, 225, 22, 20, 225, 9, 28, 20, 10, 199, 104, 243, 204, 60, 114, 83, 44, 20, 10, 199, 24, 244, 133, 57, 50, 83, 44, 20, 10, 199, 9, 84, 141, 21, 50, 83, 44, 20, 9, 198, 53, 149, 15, 52, 19, 137, 20, 9, 198, 104, 147, 206, 37, 51, 69, 20, 10, 199, 36, 229, 5, 56, 64, 78, 80, 20, 10, 199, 5, 4, 5, 48, 192, 78, 80, 20, 15, 1, 42, 6, 35, 87, 70, 108, 34, 4, 37, 87, 79, 0, 27, 0, 19, 72, 8, 82, 71, 56, 85, 4, 20, 160, 69, 36, 66, 36, 70, 35, 57, 0, 66, 13, 138, 195, 166, 19, 20, 5, 20, 9, 19, 5, 18, 20, 7, 196, 49, 84, 9, 56, 20, 11, 200, 44, 243, 148, 72, 243, 12, 4, 32, 20, 11, 200, 36, 224, 67, 12, 84, 20, 4, 32, 20, 8, 1, 43, 48, 55, 40, 87, 0, 0, 12, 201, 52, 19, 137, 65, 83, 1, 80, 244, 128, 20, 12, 201, 44, 243, 80, 72, 147, 65, 80, 244, 128, 20, 12, 201, 44, 148, 143, 65, 32, 75, 80, 244, 128, 20, 8, 197, 8, 81, 21, 36, 224, 67, 12, 201, 81, 32, 78, 76, 101, 78, 16, 84, 128, 20, 12, 201, 77, 147, 139, 72, 243, 137, 76, 84, 128, 20, 8, 197, 76, 145, 206, 21, 32, 20, 12, 201, 52, 18, 193, 16, 19, 73, 76, 84, 128, 20, 12, 201, 44, 243, 132, 37, 66, 79, 56, 84, 128, 20, 12, 201, 44, 195, 210, 60, 99, 210, 52, 84, 128, 20, 12, 201, 44, 192, 83, 76, 145, 137, 12, 84, 128, 20, 8, 197, 33, 145, 18, 21, 32, 20, 8, 197, 25, 84, 142, 21, 32, 20, 12, 201, 20, 180, 212, 72, 21, 129, 28, 84, 128, 20, 12, 201, 77, 64, 84, 37, 53, 9, 44, 84, 128, 20, 12, 201, 76, 179, 204, 5, 53, 9, 44, 84, 128, 20, 12, 201, 76, 19, 135, 88, 147, 137, 44, 84, 128, 20, 12, 201, 60, 36, 212, 21, 68, 137, 44, 84, 128, 20, 12, 201, 4, 194, 207, 32, 243, 9, 44, 84, 128, 20, 8, 197, 8, 81, 21, 36, 224, 20, 11, 136, 13, 25, 24, 195, 184, 4, 5, 13, 20, 8, 197, 48, 147, 133, 4, 192, 20, 8, 197, 48, 16, 137, 4, 192, 20, 12, 201, 65, 35, 212, 84, 33, 82, 4, 228, 192, 20, 7, 65, 44, 49, 111, 12, 0, 0, 9, 198, 56, 21, 137, 28, 84, 128, 20, 9, 198, 16, 82, 207, 72, 84, 128, 20, 13, 202, 44, 147, 133, 76, 147, 204, 60, 114, 83, 44, 20, 12, 201, 72, 85, 137, 76, 147, 206, 37, 51, 69, 20, 9, 198, 76, 180, 137, 8, 83, 148, 20, 9, 198, 61, 4, 15, 56, 83, 148, 20, 9, 198, 25, 33, 75, 88, 83, 148, 20, 14, 139, 195, 166, 11, 22, 9, 22, 1, 12, 5, 14, 19, 20, 9, 198, 41, 80, 137, 48, 20, 128, 20, 0, 9, 67, 28, 149, 128, 79, 6, 37, 0, 10, 199, 44, 243, 132, 20, 228, 207, 72, 20, 16, 141, 7, 18, 195, 184, 14, 12, 1, 14, 4, 9, 19, 5, 18, 20, 9, 198, 32, 81, 197, 52, 243, 137, 20, 9, 198, 76, 192, 86, 36, 225, 5, 20, 14, 139, 195, 166, 11, 22, 9, 22, 1, 12, 5, 14, 20, 20, 10, 199, 81, 34, 75, 61, 64, 71, 20, 20, 0, 11, 200, 81, 32, 78, 77, 2, 82, 21, 32, 20, 11, 200, 81, 32, 78, 76, 97, 82, 21, 32, 20, 11, 200, 76, 19, 139, 80, 147, 206, 21, 32, 20, 11, 200, 64, 20, 129, 29, 32, 70, 21, 32, 20, 15, 204, 61, 1, 82, 5, 66, 79, 56, 19, 9, 76, 84, 128, 20, 11, 200, 60, 34, 133, 45, 66, 86, 21, 32, 20, 11, 200, 44, 147, 15, 52, 85, 18, 21, 32, 20, 11, 200, 36, 229, 5, 73, 97, 78, 21, 32, 20, 11, 200, 28, 20, 142, 37, 51, 206, 21, 32, 20, 11, 200, 77, 147, 66, 36, 245, 9, 76, 176, 20, 11, 200, 44, 148, 137, 8, 21, 9, 76, 176, 20, 11, 200, 20, 226, 71, 52, 21, 9, 76, 176, 20, 11, 200, 4, 193, 77, 4, 227, 137, 76, 176, 20, 15, 204, 64, 20, 140, 4, 209, 78, 80, 20, 137, 44, 84, 128, 20, 7, 196, 77, 67, 205, 36, 20, 11, 200, 65, 35, 214, 36, 228, 201, 4, 224, 20, 11, 200, 9, 32, 78, 16, 84, 201, 4, 224, 20, 9, 198, 64, 20, 148, 37, 48, 78, 21, 11, 200, 44, 21, 5, 28, 244, 137, 4, 192, 20, 14, 1, 47, 87, 79, 51, 112, 87, 70, 34, 35, 37, 0, 27, 0, 12, 201, 56, 243, 69, 56, 179, 1, 80, 244, 128, 20, 12, 201, 4, 178, 213, 53, 83, 1, 80, 244, 128, 20, 12, 201, 76, 243, 9, 16, 20, 137, 76, 84, 128, 20, 12, 201, 76, 82, 213, 48, 20, 137, 76, 84, 128, 20, 12, 201, 72, 82, 207, 28, 227, 211, 12, 84, 128, 20, 12, 201, 52, 147, 9, 80, 20, 137, 76, 84, 128, 20, 12, 201, 44, 243, 139, 72, 85, 9, 76, 84, 128, 20, 12, 201, 36, 65, 78, 80, 145, 137, 12, 84, 128, 20, 8, 197, 32, 19, 22, 21, 32, 20, 8, 197, 24, 195, 210, 21, 32, 20, 8, 197, 65, 35, 211, 37, 64, 20, 8, 197, 64, 192, 75, 5, 64, 20, 6, 65, 48, 107, 55, 0, 10, 67, 33, 99, 210, 82, 6, 112, 34, 0, 0, 9, 198, 52, 19, 20, 61, 49, 64, 20, 9, 198, 16, 144, 77, 4, 229, 0, 20, 11, 70, 92, 130, 80, 12, 244, 132, 21, 0, 10, 0, 9, 198, 77, 68, 153, 28, 84, 137, 20, 10, 199, 76, 179, 205, 4, 113, 82, 36, 20, 10, 199, 64, 20, 134, 84, 209, 82, 36, 20, 14, 203, 20, 193, 75, 81, 35, 211, 80, 21, 9, 76, 176, 20, 0, 9, 198, 44, 243, 132, 37, 67, 210, 20, 9, 198, 25, 83, 132, 5, 67, 210, 20, 9, 198, 16, 146, 212, 5, 67, 210, 20, 9, 198, 8, 85, 129, 81, 35, 206, 20, 11, 200, 77, 80, 147, 45, 34, 66, 21, 32, 20, 11, 200, 65, 35, 211, 45, 34, 66, 21, 32, 20, 12, 137, 1, 6, 8, 195, 166, 14, 7, 9, 7, 20, 11, 200, 52, 21, 18, 36, 20, 139, 5, 64, 20, 9, 68, 13, 148, 149, 76, 21, 0, 10, 0, 12, 201, 8, 84, 212, 36, 19, 9, 80, 85, 0, 69, 12, 201, 85, 53, 1, 8, 147, 9, 80, 85, 0, 20, 12, 201, 76, 83, 147, 84, 19, 9, 80, 85, 0, 20, 12, 201, 36, 229, 129, 48, 145, 9, 80, 85, 0, 20, 12, 201, 36, 211, 79, 8, 147, 9, 80, 85, 0, 20, 12, 201, 36, 195, 5, 28, 19, 9, 80, 85, 0, 20, 12, 201, 8, 84, 212, 36, 19, 9, 80, 85, 0, 20, 12, 201, 4, 224, 201, 20, 227, 137, 80, 85, 0, 20, 12, 201, 77, 65, 87, 5, 33, 5, 77, 49, 64, 20, 9, 198, 25, 33, 75, 88, 83, 147, 20, 9, 198, 77, 80, 147, 80, 19, 147, 20, 6, 65, 52, 107, 63, 0, 0, 9, 198, 60, 181, 1, 28, 243, 128, 20, 9, 198, 88, 84, 147, 36, 243, 128, 20, 9, 198, 61, 96, 84, 36, 243, 128, 20, 9, 198, 24, 148, 211, 36, 243, 128, 20, 6, 195, 52, 83, 147, 8, 0, 10, 199, 52, 147, 133, 72, 19, 15, 28, 20, 10, 199, 45, 33, 77, 48, 243, 15, 28, 20, 10, 199, 45, 83, 20, 85, 35, 9, 28, 20, 10, 199, 28, 83, 5, 4, 117, 9, 28, 20, 10, 199, 80, 83, 210, 21, 66, 83, 44, 20, 10, 199, 80, 19, 201, 77, 66, 83, 44, 20, 10, 199, 76, 241, 137, 77, 66, 83, 44, 20, 10, 199, 56, 83, 204, 37, 66, 83, 44, 20, 10, 199, 56, 82, 210, 61, 66, 83, 44, 20, 10, 199, 52, 243, 137, 77, 66, 83, 44, 20, 10, 199, 20, 193, 75, 81, 34, 83, 44, 20, 10, 199, 4, 224, 76, 101, 66, 83, 44, 20, 10, 199, 44, 20, 148, 60, 116, 129, 24, 20, 0, 11, 200, 20, 194, 77, 36, 224, 84, 61, 32, 20, 14, 68, 92, 17, 207, 56, 82, 108, 79, 6, 112, 66, 0, 20, 9, 198, 64, 192, 83, 81, 35, 206, 20, 15, 204, 29, 32, 77, 52, 21, 9, 44, 19, 9, 80, 85, 0, 20, 12, 201, 33, 145, 210, 61, 50, 207, 64, 148, 203, 20, 7, 196, 60, 35, 9, 44, 20, 11, 200, 64, 21, 18, 36, 20, 139, 5, 64, 20, 0, 8, 197, 104, 243, 204, 60, 112, 20, 12, 201, 81, 32, 78, 76, 192, 84, 36, 243, 128, 20, 12, 201, 77, 1, 75, 84, 192, 84, 36, 243, 128, 20, 12, 201, 72, 84, 197, 73, 96, 84, 36, 243, 128, 20, 12, 201, 65, 35, 199, 72, 84, 211, 36, 243, 128, 20, 12, 201, 64, 84, 134, 61, 32, 84, 36, 243, 128, 20, 12, 201, 60, 36, 197, 73, 96, 84, 36, 243, 128, 20, 12, 201, 48, 19, 69, 57, 64, 84, 36, 243, 128, 20, 12, 201, 45, 83, 13, 36, 224, 84, 36, 243, 128, 20, 12, 201, 44, 243, 147, 84, 212, 20, 36, 243, 128, 20, 12, 201, 44, 243, 142, 61, 64, 84, 36, 243, 128, 20, 12, 201, 44, 243, 80, 5, 32, 84, 36, 243, 128, 20, 12, 201, 44, 243, 77, 85, 64, 84, 36, 243, 128, 20, 12, 201, 44, 243, 66, 36, 224, 84, 36, 243, 128, 20, 12, 201, 44, 19, 11, 84, 192, 84, 36, 243, 128, 20, 12, 201, 36, 229, 5, 29, 32, 84, 36, 243, 128, 20, 12, 201, 36, 228, 208, 37, 32, 84, 36, 243, 128, 20, 12, 201, 36, 225, 9, 28, 224, 84, 36, 243, 128, 20, 12, 201, 29, 32, 84, 84, 192, 84, 36, 243, 128, 20, 12, 201, 20, 180, 193, 49, 64, 84, 36, 243, 128, 20, 12, 201, 16, 84, 212, 36, 224, 84, 36, 243, 128, 20, 12, 201, 16, 84, 203, 72, 148, 20, 36, 243, 128, 20, 12, 201, 16, 84, 197, 73, 64, 84, 36, 243, 128, 20, 12, 201, 16, 84, 15, 73, 64, 84, 36, 243, 128, 20, 12, 201, 16, 82, 204, 36, 224, 84, 36, 243, 128, 20, 12, 201, 8, 19, 12, 61, 64, 84, 36, 243, 128, 20, 12, 201, 5, 69, 5, 77, 64, 84, 36, 243, 128, 20, 12, 201, 5, 4, 18, 60, 32, 84, 36, 243, 128, 20, 12, 201, 4, 36, 197, 57, 64, 84, 36, 243, 128, 20, 12, 201, 84, 226, 70, 61, 35, 73, 80, 85, 0, 20, 12, 201, 72, 17, 9, 44, 19, 9, 80, 85, 0, 20, 12, 201, 44, 20, 1, 8, 147, 9, 80, 85, 0, 20, 12, 201, 32, 243, 79, 28, 83, 137, 80, 85, 0, 20, 12, 201, 72, 81, 133, 45, 67, 210, 37, 83, 64, 20, 12, 201, 65, 35, 214, 37, 51, 210, 37, 83, 64, 20, 12, 201, 45, 33, 77, 5, 67, 210, 37, 83, 64, 20, 8, 197, 44, 243, 15, 56, 144, 20, 12, 201, 81, 32, 78, 77, 3, 210, 80, 21, 0, 20, 9, 198, 36, 212, 5, 16, 19, 147, 20, 6, 65, 56, 107, 50, 0, 9, 5, 95, 48, 1, 14, 4, 112, 0, 0, 10, 135, 6, 21, 18, 9, 195, 184, 19, 20, 9, 198, 44, 193, 82, 21, 50, 64, 20, 9, 198, 40, 19, 15, 85, 50, 64, 20, 13, 202, 28, 20, 212, 72, 244, 203, 61, 2, 83, 44, 20, 13, 202, 20, 193, 75, 81, 35, 204, 101, 66, 83, 44, 20, 13, 202, 4, 229, 1, 28, 243, 137, 77, 66, 83, 44, 20, 13, 202, 4, 224, 75, 72, 243, 137, 77, 66, 83, 44, 20, 9, 198, 36, 225, 5, 12, 83, 148, 20, 9, 198, 20, 179, 1, 80, 19, 148, 20, 0, 11, 136, 16, 18, 5, 20, 9, 195, 184, 19, 20, 12, 137, 9, 14, 6, 5, 18, 9, 195, 184, 18, 20, 10, 199, 76, 213, 75, 44, 84, 197, 72, 20, 10, 199, 48, 85, 19, 36, 225, 9, 28, 20, 10, 199, 76, 195, 214, 4, 178, 83, 44, 20, 10, 199, 72, 148, 5, 57, 50, 83, 44, 20, 10, 199, 28, 83, 203, 20, 210, 83, 44, 20, 10, 199, 21, 2, 68, 20, 210, 83, 44, 20, 10, 199, 20, 196, 193, 77, 50, 83, 44, 20, 10, 199, 52, 83, 15, 16, 146, 197, 72, 20, 9, 198, 77, 97, 67, 37, 51, 69, 20, 9, 198, 76, 192, 86, 37, 51, 69, 20, 12, 201, 44, 243, 4, 36, 225, 197, 57, 49, 82, 20, 12, 201, 44, 243, 132, 37, 66, 79, 56, 19, 0, 20, 10, 199, 52, 20, 141, 20, 192, 68, 20, 20, 0, 12, 137, 13, 9, 14, 21, 20, 9, 195, 184, 19, 20, 12, 137, 13, 5, 12, 15, 4, 9, 195, 184, 19, 20, 13, 138, 5, 11, 19, 20, 5, 18, 9, 195, 184, 18, 20, 11, 200, 44, 147, 133, 76, 147, 204, 60, 112, 20, 15, 204, 81, 32, 78, 77, 3, 1, 57, 64, 84, 36, 243, 128, 20, 15, 204, 36, 228, 212, 73, 83, 69, 57, 64, 84, 36, 243, 128, 20, 15, 204, 36, 211, 65, 81, 34, 75, 84, 192, 84, 36, 243, 128, 20, 15, 204, 76, 83, 148, 36, 209, 78, 80, 19, 9, 80, 85, 0, 20, 15, 204, 72, 84, 208, 20, 181, 1, 8, 147, 9, 80, 85, 0, 20, 11, 200, 52, 241, 21, 48, 84, 137, 56, 112, 20, 11, 200, 4, 212, 21, 80, 84, 137, 56, 112, 20, 11, 200, 88, 148, 148, 84, 244, 197, 72, 144, 20, 11, 200, 65, 35, 212, 20, 147, 146, 36, 112, 20, 11, 200, 77, 80, 129, 72, 181, 9, 76, 176, 20, 11, 200, 65, 32, 71, 52, 21, 9, 76, 176, 20, 11, 200, 33, 148, 15, 80, 85, 9, 76, 176, 20, 11, 200, 21, 96, 78, 28, 83, 9, 76, 176, 20, 11, 200, 13, 148, 18, 36, 245, 9, 76, 176, 20, 9, 198, 41, 85, 133, 56, 147, 0, 20, 9, 198, 24, 241, 5, 72, 19, 0, 20, 0, 10, 135, 6, 1, 18, 3, 195, 184, 18, 20, 8, 197, 4, 211, 133, 76, 144, 20, 8, 197, 28, 226, 69, 72, 144, 20, 16, 205, 20, 180, 208, 72, 84, 211, 36, 243, 137, 77, 66, 83, 44, 20, 8, 197, 84, 224, 201, 4, 192, 20, 5, 65, 60, 39, 0, 0, 11, 136, 4, 18, 5, 19, 19, 195, 184, 18, 20, 9, 198, 61, 0, 67, 37, 65, 84, 20, 9, 198, 85, 53, 82, 64, 84, 128, 20, 9, 198, 72, 85, 83, 76, 84, 128, 20, 9, 198, 61, 0, 76, 37, 49, 82, 20, 9, 198, 60, 33, 21, 12, 84, 128, 20, 9, 198, 52, 245, 83, 76, 84, 128, 20, 9, 198, 44, 20, 21, 56, 84, 128, 20, 9, 198, 36, 229, 21, 8, 84, 128, 20, 9, 198, 36, 229, 15, 56, 84, 128, 20, 9, 198, 36, 225, 21, 12, 84, 128, 20, 9, 198, 8, 20, 213, 56, 84, 128, 20, 9, 198, 4, 195, 15, 44, 84, 128, 20, 11, 200, 61, 0, 153, 28, 113, 76, 36, 112, 20, 13, 202, 45, 34, 77, 36, 227, 204, 60, 114, 83, 44, 20, 13, 202, 32, 84, 144, 21, 67, 204, 60, 114, 83, 44, 20, 12, 201, 32, 148, 212, 61, 34, 67, 37, 51, 69, 20, 12, 201, 21, 81, 1, 36, 211, 206, 37, 51, 69, 20, 12, 201, 20, 179, 5, 45, 66, 67, 37, 51, 69, 20, 12, 201, 8, 82, 1, 88, 147, 210, 37, 51, 69, 20, 12, 201, 4, 115, 143, 77, 66, 67, 37, 51, 69, 20, 6, 195, 61, 0, 76, 20, 10, 1, 61, 55, 6, 37, 63, 36, 84, 0, 0, 19, 71, 48, 81, 197, 56, 65, 82, 76, 55, 36, 79, 6, 107, 50, 70, 112, 87, 0, 9, 198, 17, 85, 133, 80, 147, 133, 20, 10, 199, 13, 146, 204, 61, 68, 143, 56, 20, 10, 199, 77, 84, 16, 72, 147, 69, 72, 20, 10, 199, 44, 243, 80, 72, 147, 69, 72, 20, 10, 199, 36, 225, 140, 4, 211, 69, 72, 20, 10, 199, 5, 37, 9, 45, 83, 5, 72, 20, 14, 203, 44, 20, 146, 36, 84, 133, 52, 17, 197, 72, 144, 20, 10, 199, 52, 147, 12, 20, 227, 137, 20, 20, 10, 199, 8, 20, 201, 48, 146, 213, 52, 20, 10, 199, 44, 243, 147, 36, 194, 85, 52, 20, 9, 198, 80, 16, 200, 37, 51, 69, 20, 9, 198, 52, 20, 152, 37, 51, 69, 20, 9, 198, 16, 17, 1, 37, 51, 69, 20, 12, 201, 44, 243, 148, 36, 225, 78, 80, 19, 0, 20, 0, 11, 200, 76, 147, 143, 48, 241, 201, 76, 176, 20, 11, 200, 64, 21, 15, 48, 241, 201, 76, 176, 20, 11, 200, 60, 226, 207, 48, 241, 201, 76, 176, 20, 11, 200, 56, 244, 141, 4, 227, 137, 76, 176, 20, 11, 200, 44, 21, 5, 44, 85, 9, 76, 176, 20, 11, 200, 36, 66, 79, 52, 21, 9, 76, 176, 20, 11, 200, 24, 243, 143, 48, 241, 201, 76, 176, 20, 11, 200, 24, 193, 71, 52, 21, 9, 76, 176, 20, 9, 198, 36, 208, 133, 12, 147, 0, 20, 11, 200, 45, 38, 80, 80, 241, 210, 4, 96, 20, 0, 12, 201, 72, 146, 207, 12, 129, 84, 80, 84, 128, 20, 12, 201, 44, 21, 5, 28, 244, 137, 76, 84, 128, 20, 12, 201, 36, 229, 5, 73, 1, 76, 48, 84, 128, 20, 12, 201, 12, 130, 70, 24, 243, 142, 36, 84, 128, 20, 12, 201, 12, 83, 148, 72, 145, 149, 28, 84, 128, 20, 12, 201, 56, 244, 212, 4, 193, 201, 44, 84, 128, 20, 6, 65, 64, 48, 36, 0, 15, 1, 64, 87, 50, 4, 108, 12, 69, 36, 55, 6, 108, 12, 0, 0, 18, 70, 12, 128, 78, 76, 243, 128, 89, 57, 110, 50, 87, 6, 112, 66, 0, 20, 9, 198, 64, 243, 25, 28, 243, 128, 20, 9, 198, 61, 37, 15, 28, 243, 128, 20, 9, 198, 61, 2, 78, 36, 243, 128, 20, 9, 198, 61, 3, 211, 77, 83, 64, 20, 9, 198, 72, 82, 214, 37, 50, 84, 20, 9, 198, 65, 70, 65, 48, 147, 128, 20, 12, 201, 64, 20, 129, 48, 193, 76, 37, 51, 69, 20, 12, 201, 56, 21, 9, 60, 224, 76, 37, 51, 69, 20, 12, 201, 44, 19, 142, 36, 32, 76, 37, 51, 69, 20, 9, 198, 9, 33, 84, 4, 115, 128, 20, 9, 198, 65, 33, 83, 20, 229, 0, 20, 9, 198, 53, 149, 15, 52, 19, 128, 21, 11, 70, 64, 20, 211, 92, 244, 132, 21, 0, 10, 0, 11, 67, 76, 145, 192, 87, 35, 57, 0, 14, 45, 17, 67, 76, 145, 192, 87, 37, 15, 82, 108, 0, 81, 104, 118, 97, 100, 32, 17, 67, 76, 145, 192, 87, 37, 15, 63, 35, 57, 0, 81, 109, 105, 103, 32, 10, 199, 24, 195, 210, 4, 116, 129, 52, 20, 9, 198, 64, 193, 84, 80, 84, 133, 20, 9, 198, 9, 34, 76, 48, 84, 133, 20, 9, 198, 4, 64, 80, 80, 84, 133, 20, 9, 198, 77, 2, 78, 16, 84, 137, 20, 9, 198, 52, 83, 129, 28, 84, 137, 20, 10, 199, 65, 35, 211, 12, 83, 137, 20, 20, 6, 195, 84, 226, 84, 20, 14, 203, 12, 132, 137, 77, 66, 65, 57, 50, 1, 88, 224, 20, 6, 195, 76, 145, 192, 72, 0, 9, 198, 45, 84, 148, 37, 49, 82, 20, 0, 12, 201, 81, 34, 86, 36, 19, 9, 80, 85, 0, 20, 12, 201, 76, 82, 211, 84, 19, 9, 80, 85, 0, 20, 12, 201, 72, 83, 1, 80, 149, 137, 80, 85, 0, 20, 12, 201, 56, 245, 1, 8, 147, 9, 80, 85, 0, 20, 12, 201, 53, 84, 201, 44, 19, 9, 80, 85, 0, 20, 12, 201, 17, 84, 129, 8, 147, 9, 80, 85, 0, 20, 10, 135, 16, 12, 195, 166, 4, 5, 18, 20, 8, 197, 77, 69, 80, 36, 64, 20, 12, 201, 36, 229, 5, 73, 33, 71, 57, 83, 64, 20, 12, 201, 44, 20, 18, 36, 99, 204, 37, 83, 64, 20, 12, 201, 36, 229, 5, 72, 209, 68, 37, 83, 64, 20, 12, 201, 4, 229, 5, 64, 83, 132, 37, 83, 64, 20, 6, 65, 68, 49, 40, 0, 0, 12, 201, 65, 35, 212, 60, 179, 204, 48, 84, 133, 20, 12, 201, 16, 148, 195, 37, 3, 9, 56, 84, 133, 20, 12, 201, 52, 20, 139, 76, 180, 137, 28, 84, 137, 20, 9, 198, 88, 20, 137, 4, 229, 0, 20, 0, 10, 199, 76, 225, 68, 44, 84, 133, 72, 20, 12, 201, 72, 21, 9, 60, 224, 76, 37, 49, 82, 20, 12, 201, 64, 84, 147, 60, 224, 76, 37, 49, 82, 20, 12, 201, 64, 20, 129, 48, 193, 76, 37, 49, 82, 20, 12, 201, 52, 20, 135, 36, 224, 76, 37, 49, 82, 20, 12, 201, 45, 34, 77, 36, 224, 76, 37, 49, 82, 20, 12, 201, 36, 229, 5, 72, 224, 76, 37, 49, 82, 20, 10, 199, 20, 180, 208, 48, 244, 133, 72, 20, 10, 199, 76, 83, 73, 61, 66, 83, 44, 20, 10, 199, 61, 53, 9, 56, 66, 83, 44, 20, 10, 199, 20, 97, 77, 21, 34, 83, 44, 20, 10, 199, 17, 32, 86, 36, 66, 83, 44, 20, 10, 199, 16, 145, 1, 45, 66, 83, 44, 20, 10, 199, 9, 84, 149, 56, 66, 83, 44, 20, 10, 199, 4, 181, 129, 52, 20, 137, 56, 20, 12, 201, 32, 84, 142, 36, 225, 197, 57, 49, 82, 20, 10, 199, 72, 17, 9, 60, 116, 129, 24, 20, 10, 199, 44, 19, 12, 36, 116, 129, 24, 20, 10, 199, 72, 80, 197, 57, 49, 78, 80, 20, 10, 199, 44, 243, 135, 73, 81, 78, 80, 20, 0, 9, 198, 88, 144, 146, 5, 67, 210, 20, 15, 204, 36, 228, 212, 73, 83, 69, 57, 64, 76, 37, 53, 0, 20, 9, 198, 28, 197, 75, 4, 115, 206, 20, 15, 204, 77, 147, 139, 72, 240, 217, 44, 195, 212, 72, 243, 128, 20, 14, 68, 76, 19, 15, 56, 87, 108, 55, 6, 112, 66, 0, 20, 9, 198, 72, 83, 1, 80, 147, 206, 20, 10, 135, 13, 195, 166, 14, 1, 4, 5, 20, 6, 195, 28, 17, 197, 20, 0, 9, 198, 104, 83, 15, 80, 148, 203, 20, 9, 198, 77, 147, 143, 16, 148, 203, 20, 9, 198, 64, 192, 83, 80, 148, 203, 20, 9, 198, 52, 83, 15, 16, 148, 203, 20, 9, 198, 36, 66, 79, 80, 148, 203, 20, 9, 198, 20, 192, 83, 80, 148, 203, 20, 8, 197, 80, 84, 141, 36, 224, 20, 8, 197, 52, 244, 137, 4, 224, 21, 6, 65, 72, 107, 34, 0, 0, 13, 202, 84, 226, 70, 61, 35, 73, 77, 66, 83, 44, 20, 13, 202, 77, 65, 82, 20, 243, 69, 81, 34, 83, 44, 20, 13, 202, 44, 243, 134, 61, 35, 73, 77, 66, 83, 44, 20, 13, 202, 44, 20, 9, 80, 19, 9, 77, 66, 83, 44, 20, 13, 202, 36, 229, 5, 72, 147, 73, 77, 66, 83, 44, 20, 13, 202, 24, 83, 142, 61, 50, 193, 56, 66, 83, 44, 20, 13, 202, 12, 83, 148, 72, 19, 9, 77, 66, 83, 44, 20, 9, 198, 16, 84, 15, 56, 83, 148, 20, 13, 70, 13, 35, 209, 84, 148, 192, 21, 102, 114, 0, 10, 8, 67, 48, 243, 203, 21, 0, 10, 0, 10, 199, 80, 16, 149, 48, 21, 15, 72, 20, 10, 199, 36, 226, 1, 48, 21, 15, 72, 20, 12, 201, 16, 83, 79, 57, 53, 18, 5, 67, 210, 20, 9, 198, 80, 244, 15, 48, 241, 201, 20, 9, 198, 76, 86, 15, 48, 241, 201, 20, 9, 198, 9, 38, 79, 48, 241, 201, 20, 12, 201, 72, 21, 9, 32, 16, 137, 80, 147, 206, 20, 12, 201, 65, 35, 211, 80, 149, 21, 80, 147, 206, 20, 12, 201, 44, 243, 147, 80, 149, 21, 80, 147, 206, 20, 12, 201, 44, 243, 147, 36, 115, 129, 80, 147, 206, 20, 12, 201, 36, 226, 193, 52, 147, 129, 80, 147, 206, 20, 12, 201, 36, 195, 21, 52, 147, 129, 80, 147, 206, 20, 12, 201, 24, 144, 146, 36, 195, 1, 80, 147, 206, 20, 10, 199, 52, 19, 20, 21, 50, 83, 44, 20, 10, 199, 72, 82, 214, 37, 33, 78, 80, 20, 10, 199, 44, 243, 80, 21, 65, 78, 80, 20, 10, 199, 72, 84, 208, 20, 181, 1, 8, 20, 9, 198, 25, 84, 197, 48, 17, 197, 20, 9, 198, 4, 97, 149, 80, 17, 197, 20, 8, 67, 80, 129, 64, 21, 0, 10, 0, 7, 196, 53, 147, 211, 20, 20, 7, 196, 64, 147, 143, 48, 20, 12, 201, 64, 20, 129, 48, 192, 75, 80, 148, 203, 20, 12, 201, 56, 245, 133, 48, 194, 83, 80, 148, 203, 20, 12, 201, 52, 241, 5, 72, 226, 83, 80, 148, 203, 20, 12, 201, 52, 20, 207, 12, 130, 83, 80, 148, 203, 20, 12, 201, 44, 243, 77, 84, 226, 83, 80, 148, 203, 20, 12, 201, 32, 148, 212, 61, 34, 83, 80, 148, 203, 20, 12, 201, 25, 148, 201, 60, 115, 143, 52, 148, 203, 20, 11, 200, 65, 35, 206, 60, 210, 78, 4, 192, 20, 9, 198, 5, 4, 5, 48, 192, 66, 20, 0, 8, 197, 81, 34, 66, 85, 64, 20, 8, 197, 77, 64, 82, 85, 64, 20, 12, 201, 65, 35, 208, 61, 37, 9, 60, 225, 76, 20, 8, 197, 20, 229, 18, 21, 32, 20, 16, 205, 25, 83, 132, 4, 209, 78, 80, 19, 9, 77, 66, 83, 44, 20, 8, 197, 77, 2, 78, 4, 192, 20, 8, 197, 64, 197, 82, 4, 192, 20, 8, 197, 28, 195, 194, 4, 192, 20, 6, 65, 76, 36, 87, 0, 0, 13, 202, 53, 83, 20, 37, 3, 9, 44, 21, 15, 72, 20, 15, 140, 4, 9, 19, 3, 9, 16, 12, 9, 14, 195, 166, 18, 20, 12, 201, 77, 0, 83, 80, 144, 201, 80, 85, 0, 20, 11, 200, 77, 0, 84, 36, 84, 137, 56, 112, 20, 9, 198, 77, 0, 84, 36, 84, 128, 20, 10, 199, 77, 0, 78, 45, 83, 5, 72, 20, 9, 198, 77, 0, 76, 36, 84, 133, 20, 9, 198, 77, 0, 68, 76, 84, 128, 20, 13, 202, 76, 84, 137, 21, 4, 143, 17, 80, 197, 72, 20, 12, 201, 77, 0, 82, 76, 243, 77, 20, 194, 71, 20, 9, 198, 77, 0, 78, 36, 243, 0, 20, 11, 200, 77, 0, 83, 52, 241, 9, 76, 176, 20, 9, 198, 77, 0, 82, 80, 19, 128, 20, 8, 197, 77, 0, 71, 5, 64, 20, 0, 10, 199, 45, 99, 212, 21, 34, 78, 28, 20, 10, 199, 28, 20, 132, 21, 34, 78, 28, 20, 10, 199, 17, 80, 140, 21, 34, 78, 28, 20, 18, 67, 48, 241, 192, 55, 112, 49, 6, 36, 50, 0, 44, 20, 81, 105, 110, 32, 0, 11, 200, 44, 244, 205, 21, 67, 204, 60, 112, 20, 11, 200, 56, 20, 131, 37, 52, 201, 77, 64, 20, 11, 200, 44, 192, 83, 76, 144, 201, 77, 64, 20, 13, 138, 16, 18, 195, 166, 3, 9, 19, 9, 15, 14, 20, 11, 200, 16, 148, 212, 36, 225, 214, 21, 32, 20, 7, 196, 45, 33, 79, 48, 20, 11, 200, 81, 148, 15, 48, 241, 201, 76, 176, 20, 11, 200, 77, 145, 137, 48, 149, 9, 76, 176, 20, 11, 200, 76, 84, 143, 48, 241, 201, 76, 176, 20, 11, 200, 21, 67, 143, 48, 241, 201, 76, 176, 20, 11, 200, 21, 2, 76, 21, 5, 9, 76, 176, 20, 11, 200, 9, 84, 135, 84, 225, 9, 76, 176, 20, 11, 200, 13, 84, 146, 36, 53, 76, 84, 208, 20, 11, 200, 80, 83, 80, 21, 33, 82, 21, 64, 20, 11, 200, 72, 84, 201, 28, 225, 82, 21, 64, 20, 11, 200, 72, 17, 134, 36, 225, 82, 21, 64, 20, 11, 200, 48, 19, 69, 48, 193, 82, 21, 64, 20, 11, 200, 36, 226, 193, 72, 225, 82, 21, 64, 20, 11, 200, 16, 148, 12, 60, 209, 82, 21, 64, 20, 11, 200, 16, 85, 1, 48, 161, 82, 21, 64, 20, 12, 137, 9, 14, 8, 195, 166, 18, 5, 14, 19, 20, 0, 8, 197, 88, 144, 146, 21, 32, 20, 8, 197, 76, 84, 150, 21, 32, 20, 9, 198, 32, 84, 129, 48, 66, 75, 20, 12, 201, 25, 148, 201, 60, 115, 143, 52, 146, 192, 20, 8, 197, 60, 181, 76, 5, 32, 20, 8, 197, 28, 20, 129, 57, 64, 20, 10, 69, 76, 84, 150, 21, 32, 21, 0, 10, 0, 9, 198, 76, 86, 15, 48, 241, 192, 20, 9, 198, 21, 67, 143, 48, 241, 192, 20, 9, 198, 81, 84, 130, 36, 225, 64, 20, 9, 198, 80, 84, 154, 36, 225, 64, 20, 9, 198, 24, 244, 134, 36, 225, 64, 20, 9, 198, 21, 50, 193, 64, 148, 212, 20, 13, 202, 76, 81, 9, 52, 83, 148, 21, 34, 78, 28, 20, 13, 202, 65, 35, 214, 36, 19, 148, 21, 34, 78, 28, 20, 12, 201, 48, 81, 19, 4, 113, 82, 36, 225, 5, 20, 6, 195, 84, 226, 75, 20, 9, 198, 80, 19, 135, 20, 229, 0, 20, 9, 198, 44, 20, 132, 36, 224, 76, 20, 0, 9, 198, 52, 19, 137, 13, 84, 133, 20, 10, 199, 72, 84, 197, 73, 98, 83, 80, 20, 10, 199, 12, 19, 22, 36, 226, 83, 80, 20, 10, 199, 28, 20, 212, 72, 243, 143, 52, 20, 14, 203, 76, 83, 22, 8, 147, 199, 72, 17, 137, 76, 176, 20, 10, 199, 80, 18, 211, 60, 227, 205, 36, 20, 10, 199, 44, 243, 135, 73, 81, 78, 76, 20, 0, 7, 196, 81, 83, 79, 72, 20, 7, 196, 80, 83, 143, 72, 20, 9, 198, 25, 83, 139, 80, 147, 206, 20, 9, 198, 25, 34, 75, 80, 147, 206, 20, 9, 198, 21, 33, 75, 80, 147, 206, 20, 11, 200, 76, 181, 129, 17, 35, 206, 21, 32, 20, 7, 196, 44, 243, 9, 44, 20, 11, 200, 44, 243, 77, 37, 69, 5, 57, 64, 20, 11, 200, 65, 32, 75, 80, 146, 193, 57, 64, 20, 11, 200, 5, 84, 203, 84, 197, 1, 57, 64, 20, 0, 8, 197, 8, 240, 137, 56, 80, 20, 13, 138, 195, 166, 18, 22, 195, 166, 18, 4, 9, 7, 20, 12, 201, 76, 224, 75, 44, 84, 193, 48, 145, 192, 20, 13, 138, 18, 5, 20, 6, 195, 166, 18, 4, 9, 7, 20, 12, 201, 60, 212, 212, 36, 195, 5, 48, 145, 192, 20, 12, 201, 60, 36, 212, 21, 35, 129, 76, 145, 192, 20, 13, 138, 2, 15, 4, 6, 195, 166, 18, 4, 9, 7, 20, 12, 201, 8, 148, 203, 61, 4, 5, 48, 145, 192, 20, 9, 198, 64, 21, 5, 80, 148, 203, 20, 9, 198, 44, 84, 129, 52, 148, 203, 20, 9, 198, 20, 212, 1, 80, 148, 203, 20, 9, 198, 17, 37, 73, 16, 148, 203, 20, 10, 69, 92, 147, 132, 61, 112, 21, 0, 10, 6, 65, 84, 40, 19, 0, 0, 9, 198, 5, 85, 15, 65, 50, 64, 20, 9, 198, 88, 149, 1, 48, 148, 212, 20, 13, 202, 88, 83, 148, 72, 147, 15, 45, 98, 83, 80, 20, 13, 202, 64, 84, 139, 85, 52, 201, 60, 226, 83, 80, 20, 13, 202, 36, 225, 5, 80, 84, 141, 36, 226, 83, 80, 20, 9, 198, 36, 65, 65, 48, 148, 212, 20, 13, 202, 25, 83, 139, 80, 147, 206, 4, 194, 83, 80, 20, 13, 202, 16, 242, 213, 52, 83, 148, 5, 34, 83, 80, 20, 14, 139, 195, 184, 13, 20, 195, 165, 12, 5, 12, 9, 7, 20, 14, 139, 20, 18, 25, 11, 6, 195, 166, 18, 4, 9, 7, 20, 14, 139, 19, 16, 1, 7, 6, 195, 166, 18, 4, 9, 7, 20, 14, 139, 19, 12, 1, 7, 6, 195, 166, 18, 4, 9, 7, 20, 14, 139, 19, 1, 14, 4, 6, 195, 166, 18, 4, 9, 7, 20, 14, 139, 16, 18, 9, 19, 22, 195, 166, 18, 4, 9, 7, 20, 14, 139, 15, 16, 19, 195, 166, 20, 20, 5, 12, 9, 7, 20, 14, 139, 15, 13, 19, 195, 166, 20, 20, 5, 12, 9, 7, 20, 14, 139, 15, 13, 7, 195, 166, 14, 7, 5, 12, 9, 7, 20, 9, 198, 5, 35, 79, 16, 145, 192, 20, 14, 139, 1, 14, 20, 195, 166, 14, 4, 5, 12, 9, 7, 20, 14, 139, 1, 6, 19, 195, 166, 20, 20, 5, 12, 9, 7, 20, 0, 18, 71, 72, 82, 137, 12, 84, 133, 72, 34, 36, 57, 37, 87, 6, 36, 112, 0, 10, 199, 29, 32, 77, 52, 241, 143, 56, 20, 12, 201, 36, 229, 5, 72, 161, 75, 80, 147, 206, 20, 15, 140, 22, 9, 4, 5, 18, 22, 195, 166, 18, 4, 9, 7, 20, 15, 140, 19, 20, 18, 1, 6, 22, 195, 166, 18, 4, 9, 7, 20, 15, 140, 11, 21, 14, 19, 20, 6, 195, 166, 18, 4, 9, 7, 20, 15, 140, 6, 15, 18, 19, 195, 184, 13, 13, 5, 12, 9, 7, 20, 15, 140, 6, 15, 18, 19, 13, 195, 166, 4, 5, 12, 9, 7, 20, 15, 140, 6, 15, 18, 6, 195, 166, 18, 4, 5, 12, 9, 7, 20, 10, 199, 88, 19, 149, 5, 66, 83, 44, 20, 10, 199, 80, 83, 12, 85, 34, 83, 44, 20, 10, 199, 72, 17, 129, 20, 194, 83, 44, 20, 10, 199, 65, 35, 211, 60, 66, 83, 44, 20, 10, 199, 64, 84, 137, 60, 66, 83, 44, 20, 10, 199, 45, 80, 137, 77, 66, 83, 44, 20, 10, 199, 21, 51, 212, 21, 34, 83, 44, 20, 10, 199, 17, 32, 75, 60, 226, 83, 44, 20, 10, 199, 5, 4, 137, 61, 34, 83, 44, 20, 10, 199, 4, 192, 77, 60, 66, 83, 44, 20, 10, 199, 4, 115, 143, 77, 66, 83, 44, 20, 9, 198, 32, 20, 141, 60, 226, 69, 20, 9, 198, 8, 84, 153, 48, 194, 69, 20, 10, 199, 76, 49, 78, 60, 116, 129, 24, 20, 10, 199, 72, 84, 18, 60, 116, 129, 24, 20, 10, 199, 64, 19, 148, 60, 116, 129, 24, 20, 0, 9, 198, 32, 82, 211, 4, 115, 206, 20, 7, 196, 80, 19, 15, 56, 20, 9, 198, 64, 244, 201, 80, 147, 206, 20, 11, 200, 52, 81, 9, 12, 147, 133, 72, 80, 20, 16, 141, 22, 5, 12, 195, 166, 18, 22, 195, 166, 18, 4, 9, 7, 20, 15, 204, 76, 19, 77, 20, 226, 204, 5, 4, 5, 48, 145, 192, 20, 16, 141, 15, 22, 5, 18, 19, 195, 166, 20, 20, 5, 12, 9, 7, 20, 15, 204, 28, 83, 142, 20, 212, 203, 36, 227, 133, 48, 145, 192, 20, 12, 201, 5, 34, 83, 80, 245, 5, 48, 148, 203, 20, 9, 198, 48, 149, 15, 72, 19, 0, 20, 0, 8, 197, 65, 35, 204, 60, 112, 20, 8, 197, 61, 67, 204, 60, 112, 20, 8, 197, 48, 85, 133, 72, 80, 20, 9, 198, 49, 146, 211, 4, 194, 71, 20, 17, 142, 12, 5, 20, 1, 14, 20, 195, 166, 14, 4, 5, 12, 9, 7, 20, 17, 142, 8, 195, 184, 10, 195, 166, 18, 22, 195, 166, 18, 4, 9, 7, 20, 9, 198, 4, 228, 197, 20, 194, 71, 20, 8, 197, 5, 32, 76, 36, 80, 20, 12, 201, 61, 37, 15, 12, 84, 129, 80, 149, 0, 20, 8, 197, 36, 225, 129, 52, 144, 20, 6, 65, 88, 82, 36, 0, 0, 10, 135, 11, 1, 18, 9, 195, 184, 19, 20, 10, 135, 3, 1, 18, 9, 195, 184, 19, 20, 11, 136, 3, 8, 1, 18, 13, 195, 184, 18, 20, 13, 202, 64, 244, 201, 80, 149, 137, 77, 66, 83, 44, 20, 13, 202, 56, 81, 193, 80, 149, 137, 77, 66, 83, 44, 20, 13, 202, 52, 147, 9, 80, 20, 137, 77, 66, 83, 44, 20, 13, 202, 44, 19, 15, 72, 147, 69, 81, 34, 83, 44, 20, 13, 202, 33, 145, 18, 60, 209, 75, 4, 226, 83, 44, 20, 13, 202, 12, 128, 85, 88, 147, 137, 77, 66, 83, 44, 20, 9, 198, 76, 18, 203, 5, 34, 68, 20, 9, 198, 44, 243, 12, 60, 145, 0, 20, 9, 198, 32, 20, 141, 60, 226, 64, 20, 9, 198, 5, 67, 5, 80, 146, 192, 20, 9, 198, 24, 97, 82, 52, 21, 0, 20, 0, 10, 67, 64, 130, 76, 81, 37, 60, 0, 25, 19, 71, 72, 82, 137, 12, 84, 133, 76, 34, 36, 57, 37, 87, 6, 36, 112, 87, 0, 10, 199, 72, 81, 213, 48, 21, 15, 72, 20, 10, 199, 72, 80, 201, 80, 21, 15, 72, 20, 10, 199, 36, 225, 9, 44, 21, 15, 72, 20, 10, 199, 21, 50, 193, 48, 21, 15, 72, 20, 12, 201, 72, 21, 9, 24, 146, 193, 80, 147, 206, 20, 12, 201, 61, 33, 193, 56, 148, 193, 80, 147, 206, 20, 12, 201, 52, 241, 9, 24, 146, 193, 80, 147, 206, 20, 12, 201, 44, 243, 148, 72, 144, 149, 80, 147, 206, 20, 12, 201, 44, 243, 134, 37, 50, 193, 80, 147, 206, 20, 12, 201, 44, 243, 134, 37, 35, 65, 80, 147, 206, 20, 12, 201, 44, 241, 9, 24, 146, 193, 80, 147, 206, 20, 12, 201, 44, 19, 143, 56, 148, 193, 80, 147, 206, 20, 12, 201, 36, 228, 212, 4, 195, 1, 80, 147, 206, 20, 12, 201, 16, 84, 212, 36, 195, 1, 80, 147, 206, 20, 12, 201, 4, 229, 9, 12, 148, 1, 80, 147, 206, 20, 10, 199, 44, 21, 1, 49, 148, 197, 72, 20, 10, 199, 16, 82, 204, 5, 52, 197, 72, 20, 10, 199, 16, 80, 200, 36, 100, 133, 72, 20, 10, 199, 81, 80, 82, 20, 114, 83, 44, 20, 10, 199, 44, 20, 148, 4, 114, 83, 44, 20, 10, 199, 8, 148, 195, 5, 146, 83, 44, 20, 8, 133, 195, 166, 20, 1, 14, 21, 9, 198, 77, 64, 70, 24, 17, 197, 20, 0, 11, 200, 45, 34, 77, 36, 227, 204, 60, 112, 20, 9, 198, 44, 20, 129, 88, 83, 0, 20, 11, 200, 5, 81, 205, 20, 229, 5, 72, 80, 20, 12, 201, 61, 97, 82, 44, 243, 77, 20, 194, 71, 20, 12, 201, 25, 33, 68, 76, 243, 77, 20, 194, 71, 20, 12, 201, 20, 161, 78, 16, 243, 77, 20, 194, 71, 20, 16, 141, 2, 18, 195, 184, 19, 20, 6, 195, 166, 12, 4, 9, 7, 20, 11, 200, 88, 242, 193, 80, 149, 137, 76, 176, 20, 11, 200, 72, 80, 76, 37, 53, 9, 76, 176, 20, 11, 200, 65, 35, 195, 20, 229, 9, 76, 176, 20, 11, 200, 64, 145, 84, 37, 53, 9, 76, 176, 20, 11, 200, 61, 5, 1, 80, 149, 137, 76, 176, 20, 11, 200, 28, 83, 199, 72, 17, 137, 76, 176, 20, 11, 200, 17, 84, 129, 80, 149, 137, 76, 176, 20, 11, 200, 17, 80, 76, 37, 53, 9, 76, 176, 20, 11, 200, 16, 162, 66, 61, 85, 9, 76, 176, 20, 11, 200, 16, 144, 75, 72, 243, 137, 76, 176, 20, 11, 200, 5, 67, 205, 37, 53, 9, 76, 176, 20, 11, 200, 5, 34, 193, 37, 53, 9, 76, 176, 20, 11, 200, 64, 197, 84, 60, 180, 129, 80, 144, 20, 9, 198, 33, 96, 66, 20, 128, 82, 20, 9, 198, 12, 83, 148, 72, 19, 0, 20, 21, 4, 95, 49, 77, 52, 6, 36, 12, 50, 15, 69, 37, 55, 37, 57, 6, 39, 12, 50, 0, 0, 14, 139, 16, 18, 15, 7, 18, 1, 13, 13, 195, 184, 18, 20, 8, 197, 4, 193, 75, 76, 144, 20, 9, 198, 28, 82, 147, 80, 194, 71, 20, 8, 197, 44, 20, 141, 36, 224, 20, 16, 69, 72, 243, 65, 56, 144, 34, 39, 63, 6, 108, 50, 37, 0, 20, 12, 201, 32, 84, 141, 20, 225, 85, 80, 146, 192, 20, 12, 201, 13, 149, 15, 28, 83, 133, 80, 146, 192, 20, 8, 197, 28, 84, 141, 4, 224, 20, 8, 197, 88, 19, 5, 57, 48, 20, 8, 197, 76, 145, 206, 4, 192, 20, 8, 197, 56, 243, 65, 16, 80, 20, 14, 65, 92, 70, 6, 112, 69, 36, 55, 47, 82, 36, 12, 0, 22, 1, 92, 6, 112, 63, 82, 36, 50, 70, 87, 79, 34, 4, 112, 87, 70, 51, 35, 37, 0, 27, 0, 9, 198, 48, 19, 80, 37, 53, 0, 20, 9, 198, 28, 20, 132, 37, 53, 0, 20, 9, 198, 52, 85, 15, 16, 146, 192, 20, 9, 198, 44, 21, 15, 48, 146, 192, 20, 0, 10, 199, 5, 3, 208, 48, 82, 211, 36, 20, 14, 203, 20, 180, 208, 21, 34, 77, 20, 229, 5, 72, 80, 20, 14, 203, 77, 147, 132, 36, 176, 76, 37, 53, 9, 76, 176, 20, 14, 203, 52, 21, 5, 72, 144, 76, 37, 53, 9, 76, 176, 20, 14, 203, 36, 212, 5, 72, 144, 76, 37, 53, 9, 76, 176, 20, 14, 203, 16, 85, 5, 72, 210, 78, 37, 53, 9, 76, 176, 20, 10, 199, 13, 144, 78, 44, 19, 9, 20, 20, 10, 199, 44, 243, 12, 60, 66, 85, 52, 20, 10, 199, 28, 195, 211, 5, 34, 85, 52, 20, 10, 199, 44, 243, 80, 21, 65, 78, 76, 20, 6, 195, 4, 224, 76, 20, 0, 9, 198, 45, 32, 75, 20, 193, 82, 20, 9, 198, 16, 84, 212, 73, 81, 82, 20, 9, 198, 4, 113, 210, 5, 97, 82, 20, 12, 201, 20, 101, 5, 73, 98, 83, 20, 194, 71, 20, 11, 200, 100, 83, 69, 56, 149, 9, 76, 176, 20, 11, 200, 76, 19, 15, 52, 243, 137, 76, 176, 20, 11, 200, 65, 34, 83, 52, 21, 9, 76, 176, 20, 11, 200, 64, 19, 143, 72, 19, 73, 76, 176, 20, 11, 200, 61, 33, 201, 5, 53, 9, 76, 176, 20, 11, 200, 41, 81, 1, 37, 53, 9, 76, 176, 20, 11, 200, 36, 225, 15, 48, 241, 201, 76, 176, 20, 11, 200, 20, 194, 84, 37, 53, 9, 76, 176, 20, 11, 200, 8, 19, 12, 37, 53, 9, 76, 176, 20, 11, 200, 4, 225, 75, 16, 245, 9, 76, 176, 20, 11, 200, 4, 180, 143, 8, 21, 9, 76, 176, 20, 7, 196, 88, 19, 9, 16, 20, 9, 198, 77, 68, 153, 44, 226, 78, 20, 13, 68, 45, 32, 65, 48, 49, 34, 112, 12, 55, 0, 20, 0, 14, 139, 22, 21, 12, 11, 1, 14, 9, 19, 195, 184, 18, 20, 14, 139, 19, 25, 13, 16, 1, 20, 9, 19, 195, 184, 18, 20, 14, 139, 13, 1, 7, 14, 5, 20, 9, 19, 195, 184, 18, 20, 12, 201, 44, 243, 15, 56, 144, 76, 37, 53, 0, 20, 18, 70, 52, 17, 206, 36, 98, 75, 63, 108, 66, 37, 81, 6, 37, 49, 0, 20, 7, 65, 96, 107, 49, 87, 0, 17, 4, 95, 49, 77, 49, 36, 70, 15, 47, 6, 40, 12, 87, 14, 50, 0, 0, 17, 206, 36, 229, 5, 48, 193, 75, 81, 80, 76, 37, 53, 9, 76, 176, 20, 17, 206, 20, 180, 201, 77, 65, 78, 80, 144, 76, 37, 53, 9, 76, 176, 20, 13, 202, 77, 84, 16, 61, 50, 84, 61, 34, 85, 52, 20, 9, 66, 4, 64, 108, 84, 0, 14, 45, 7, 66, 4, 64, 108, 12, 0, 21, 4, 95, 49, 77, 50, 6, 36, 12, 50, 15, 63, 37, 55, 37, 57, 6, 39, 12, 50, 0, 0, 9, 198, 76, 147, 133, 13, 84, 133, 20, 10, 199, 88, 145, 5, 60, 116, 129, 52, 20, 10, 199, 77, 65, 78, 60, 116, 129, 52, 20, 14, 203, 48, 82, 211, 36, 179, 199, 72, 17, 137, 76, 176, 20, 14, 203, 45, 35, 205, 5, 67, 199, 72, 17, 137, 76, 176, 20, 14, 203, 44, 243, 15, 56, 144, 76, 37, 53, 9, 76, 176, 20, 10, 199, 77, 147, 80, 61, 50, 85, 52, 20, 12, 201, 5, 49, 82, 8, 18, 132, 76, 160, 78, 20, 12, 201, 5, 49, 82, 8, 18, 132, 76, 160, 78, 21, 21, 4, 95, 49, 77, 51, 6, 36, 12, 50, 15, 63, 37, 55, 37, 57, 6, 110, 12, 70, 0, 0, 9, 198, 77, 80, 195, 20, 65, 82, 20, 9, 198, 77, 66, 77, 84, 193, 82, 20, 9, 198, 72, 85, 21, 72, 225, 82, 20, 13, 138, 16, 18, 195, 166, 19, 5, 14, 20, 5, 18, 20, 9, 198, 32, 20, 141, 60, 225, 82, 20, 9, 198, 76, 18, 203, 5, 34, 78, 20, 9, 198, 52, 20, 203, 84, 194, 78, 20, 11, 200, 44, 243, 139, 61, 33, 1, 57, 48, 20, 11, 200, 44, 243, 132, 84, 181, 1, 57, 48, 20, 0, 12, 201, 61, 34, 69, 57, 64, 76, 37, 53, 0, 20, 9, 198, 64, 243, 9, 80, 148, 203, 20, 9, 198, 8, 20, 201, 48, 148, 203, 20, 12, 201, 16, 85, 5, 72, 210, 78, 4, 229, 0, 20, 6, 65, 100, 115, 19, 0, 0, 13, 202, 64, 20, 129, 48, 193, 76, 60, 116, 129, 52, 20, 15, 140, 18, 5, 16, 18, 195, 166, 19, 5, 14, 20, 5, 18, 20, 0, 9, 198, 81, 35, 205, 8, 244, 197, 20, 9, 198, 65, 35, 199, 56, 244, 197, 20, 12, 201, 56, 21, 9, 60, 224, 76, 37, 49, 82, 20, 10, 199, 44, 243, 147, 64, 148, 133, 72, 20, 12, 201, 44, 243, 77, 84, 224, 76, 37, 49, 82, 20, 12, 201, 44, 19, 142, 36, 32, 76, 37, 49, 82, 20, 10, 199, 36, 225, 11, 48, 20, 133, 72, 20, 9, 198, 44, 147, 133, 76, 84, 137, 20, 9, 198, 24, 20, 193, 56, 84, 137, 20, 10, 199, 80, 83, 211, 60, 98, 83, 44, 20, 10, 199, 24, 20, 129, 60, 226, 83, 44, 20, 10, 199, 17, 32, 77, 5, 66, 83, 44, 20, 10, 199, 4, 224, 70, 61, 34, 83, 44, 20, 9, 198, 4, 224, 77, 56, 84, 197, 20, 10, 199, 80, 84, 144, 20, 229, 9, 56, 20, 10, 199, 76, 84, 144, 20, 229, 9, 56, 20, 10, 199, 20, 225, 15, 77, 49, 78, 80, 20, 0, 9, 198, 56, 245, 1, 80, 147, 206, 20, 9, 198, 45, 33, 65, 80, 147, 206, 20, 9, 198, 16, 245, 1, 80, 147, 206, 20, 12, 201, 52, 146, 210, 61, 50, 207, 64, 148, 203, 20, 21, 68, 77, 64, 78, 16, 87, 47, 108, 50, 70, 6, 37, 50, 0, 44, 20, 81, 105, 110, 32, 9, 198, 44, 243, 150, 20, 224, 66, 20, 0, 8, 197, 28, 19, 9, 60, 224, 20, 9, 198, 60, 198, 77, 64, 148, 203, 20, 9, 198, 52, 85, 15, 16, 148, 203, 20, 9, 198, 44, 21, 15, 16, 148, 203, 20, 9, 198, 20, 180, 207, 80, 148, 203, 20, 9, 198, 9, 82, 207, 48, 148, 203, 20, 8, 197, 44, 195, 210, 36, 224, 20, 8, 197, 44, 243, 150, 4, 192, 20, 7, 65, 104, 87, 107, 47, 0, 0, 16, 66, 5, 64, 108, 15, 105, 108, 12, 0, 81, 104, 97, 118, 101, 32, 9, 198, 72, 149, 15, 72, 225, 76, 20, 12, 201, 12, 128, 82, 48, 21, 1, 56, 84, 137, 20, 13, 202, 77, 80, 147, 80, 19, 148, 37, 98, 83, 44, 20, 13, 202, 64, 84, 147, 64, 82, 212, 37, 98, 83, 44, 20, 13, 202, 52, 83, 15, 17, 32, 77, 5, 66, 83, 44, 20, 13, 202, 44, 243, 80, 61, 50, 84, 61, 34, 83, 44, 20, 13, 202, 36, 226, 214, 37, 50, 84, 61, 34, 83, 44, 20, 12, 201, 20, 180, 208, 20, 66, 84, 72, 144, 197, 20, 8, 66, 5, 64, 108, 12, 0, 72, 0, 10, 199, 72, 81, 140, 20, 181, 15, 72, 20, 10, 199, 65, 35, 212, 20, 181, 15, 72, 20, 10, 199, 36, 228, 208, 20, 181, 15, 72, 20, 12, 201, 52, 83, 147, 81, 37, 65, 80, 147, 206, 20, 12, 201, 36, 229, 9, 52, 145, 1, 80, 147, 206, 20, 10, 199, 36, 225, 11, 5, 52, 197, 72, 20, 10, 199, 52, 19, 1, 101, 50, 83, 44, 20, 10, 199, 44, 148, 143, 52, 19, 148, 36, 20, 0, 11, 200, 88, 148, 201, 80, 21, 9, 60, 224, 20, 11, 200, 88, 81, 197, 80, 21, 9, 60, 224, 20, 11, 200, 72, 80, 201, 80, 21, 9, 60, 224, 20, 11, 200, 52, 241, 21, 48, 21, 9, 60, 224, 20, 11, 200, 21, 50, 193, 48, 21, 9, 60, 224, 20, 11, 200, 16, 84, 21, 80, 21, 9, 60, 224, 20, 11, 200, 16, 84, 9, 48, 21, 9, 60, 224, 20, 11, 200, 4, 212, 21, 80, 21, 9, 60, 224, 20, 12, 201, 65, 35, 198, 100, 192, 75, 80, 148, 203, 20, 12, 201, 64, 197, 82, 4, 194, 83, 80, 148, 203, 20, 12, 201, 53, 148, 212, 36, 98, 83, 80, 148, 203, 20, 12, 201, 44, 16, 130, 4, 194, 83, 80, 148, 203, 20, 12, 201, 32, 83, 12, 20, 226, 83, 80, 148, 203, 20, 12, 201, 28, 20, 212, 72, 243, 143, 52, 148, 203, 20, 12, 201, 17, 32, 77, 5, 69, 82, 28, 148, 203, 20, 12, 201, 12, 19, 22, 36, 226, 83, 80, 148, 203, 20, 11, 200, 76, 19, 22, 4, 67, 210, 4, 224, 20, 11, 200, 16, 148, 133, 45, 67, 210, 4, 192, 20, 0, 12, 201, 36, 229, 5, 56, 64, 78, 81, 84, 128, 20, 8, 197, 88, 84, 137, 77, 64, 20, 8, 197, 4, 244, 137, 77, 64, 20, 12, 201, 44, 243, 150, 20, 229, 9, 60, 225, 76, 20, 8, 197, 37, 34, 83, 21, 32, 20, 8, 197, 9, 81, 211, 21, 32, 20, 8, 197, 8, 19, 132, 37, 64, 20, 8, 197, 16, 83, 6, 36, 224, 20, 8, 197, 88, 19, 5, 57, 64, 20, 8, 197, 80, 19, 5, 57, 64, 20, 8, 197, 64, 147, 69, 57, 64, 20, 8, 197, 52, 243, 69, 57, 64, 20, 8, 197, 16, 83, 69, 57, 64, 20, 8, 197, 48, 18, 212, 5, 64, 20, 8, 197, 49, 83, 66, 4, 192, 20, 0, 9, 198, 5, 81, 9, 80, 244, 128, 20, 12, 201, 64, 20, 129, 76, 149, 15, 48, 241, 201, 20, 12, 201, 16, 144, 76, 20, 181, 15, 48, 241, 201, 20, 9, 198, 80, 243, 148, 36, 225, 64, 20, 9, 198, 44, 19, 148, 36, 225, 64, 20, 9, 198, 65, 32, 75, 80, 146, 192, 20, 9, 198, 9, 34, 71, 4, 65, 64, 20, 9, 198, 8, 195, 203, 4, 65, 64, 20, 0, 10, 199, 81, 35, 212, 76, 178, 83, 80, 20, 10, 199, 64, 20, 139, 21, 34, 78, 28, 20, 15, 204, 25, 83, 139, 80, 147, 206, 4, 194, 83, 80, 148, 203, 20, 0, 22, 72, 9, 33, 65, 44, 64, 78, 12, 80, 69, 34, 107, 37, 79, 6, 70, 35, 12, 50, 87, 0, 11, 200, 44, 21, 129, 48, 84, 137, 77, 64, 20, 11, 200, 52, 81, 9, 80, 21, 9, 60, 224, 20, 11, 200, 48, 144, 201, 80, 21, 9, 60, 224, 20, 11, 200, 44, 244, 146, 20, 181, 9, 60, 224, 20, 11, 200, 80, 83, 210, 21, 66, 83, 21, 32, 20, 11, 200, 77, 147, 80, 5, 66, 83, 21, 32, 20, 11, 200, 56, 20, 139, 61, 66, 83, 21, 32, 20, 11, 200, 52, 20, 148, 101, 34, 83, 21, 32, 20, 11, 200, 52, 17, 206, 21, 66, 83, 21, 32, 20, 11, 200, 44, 20, 130, 60, 226, 83, 21, 32, 20, 11, 200, 33, 148, 14, 61, 66, 83, 21, 32, 20, 11, 200, 28, 195, 194, 4, 194, 83, 21, 32, 20, 11, 200, 20, 193, 75, 81, 34, 83, 21, 32, 20, 11, 200, 16, 144, 76, 60, 114, 83, 21, 32, 20, 11, 200, 4, 227, 206, 100, 210, 83, 21, 32, 20, 11, 200, 4, 224, 76, 60, 114, 83, 21, 32, 20, 11, 200, 4, 176, 68, 20, 210, 83, 21, 32, 20, 11, 200, 80, 131, 205, 37, 53, 9, 76, 176, 20, 11, 200, 64, 21, 18, 36, 245, 9, 76, 176, 20, 11, 200, 48, 19, 65, 37, 53, 9, 76, 176, 20, 11, 200, 32, 243, 73, 48, 85, 9, 76, 176, 20, 11, 200, 16, 146, 207, 80, 243, 73, 76, 176, 20, 11, 200, 16, 145, 148, 60, 225, 201, 76, 176, 20, 11, 200, 16, 144, 76, 20, 181, 9, 76, 176, 20, 11, 200, 72, 85, 77, 5, 66, 75, 21, 32, 20, 11, 200, 33, 148, 212, 21, 34, 75, 21, 32, 20, 11, 200, 32, 148, 212, 61, 34, 75, 21, 32, 20, 11, 200, 17, 32, 77, 5, 66, 75, 21, 32, 20, 11, 200, 16, 241, 205, 5, 66, 75, 21, 32, 20, 9, 198, 52, 86, 154, 4, 226, 78, 20, 11, 200, 4, 35, 206, 56, 83, 69, 57, 64, 20, 11, 200, 72, 85, 19, 36, 225, 82, 21, 64, 20, 11, 200, 44, 20, 9, 81, 83, 1, 57, 64, 20, 0, 8, 197, 72, 82, 210, 85, 64, 20, 12, 201, 9, 34, 76, 48, 19, 148, 36, 225, 64, 20, 8, 197, 72, 16, 201, 77, 64, 20, 8, 197, 65, 84, 137, 77, 64, 20, 8, 197, 44, 244, 137, 77, 64, 20, 8, 197, 44, 19, 11, 21, 32, 20, 8, 197, 21, 34, 71, 21, 32, 20, 8, 197, 48, 21, 5, 57, 64, 20, 8, 197, 64, 81, 1, 57, 64, 20, 0, 11, 66, 12, 16, 87, 37, 34, 49, 108, 0, 25, 9, 198, 32, 243, 79, 48, 241, 192, 20, 9, 198, 32, 21, 83, 76, 148, 212, 20, 9, 198, 84, 69, 69, 48, 145, 192, 20, 9, 198, 32, 244, 141, 60, 224, 76, 20, 9, 198, 33, 145, 18, 4, 229, 0, 20, 0, 9, 198, 76, 147, 9, 44, 244, 197, 20, 10, 199, 76, 84, 137, 4, 194, 83, 80, 20, 10, 199, 60, 178, 213, 49, 66, 83, 80, 20, 14, 203, 25, 83, 139, 80, 147, 206, 4, 194, 83, 21, 32, 20, 14, 203, 8, 243, 129, 64, 20, 148, 37, 53, 9, 76, 176, 20, 0, 11, 200, 24, 243, 11, 48, 244, 137, 77, 64, 20, 19, 70, 16, 148, 212, 36, 179, 206, 70, 37, 87, 47, 37, 49, 6, 112, 50, 0, 20, 9, 198, 41, 83, 139, 80, 147, 206, 20, 9, 198, 25, 32, 75, 80, 147, 206, 20, 11, 200, 44, 243, 77, 84, 226, 75, 21, 32, 20, 11, 200, 16, 243, 69, 77, 66, 67, 21, 32, 20, 12, 137, 195, 184, 13, 20, 195, 165, 12, 9, 7, 20, 12, 137, 22, 5, 12, 4, 195, 166, 4, 9, 7, 20, 12, 137, 7, 15, 4, 4, 195, 166, 4, 9, 7, 20, 11, 200, 5, 53, 13, 5, 66, 75, 21, 32, 20, 7, 196, 61, 33, 193, 56, 21, 11, 200, 72, 81, 140, 20, 181, 1, 57, 64, 20, 0, 12, 201, 16, 144, 76, 20, 181, 15, 48, 241, 192, 20, 12, 201, 48, 81, 201, 80, 147, 73, 80, 85, 0, 20, 12, 201, 25, 32, 84, 21, 35, 137, 80, 85, 0, 20, 8, 197, 64, 243, 5, 72, 80, 20, 8, 197, 52, 83, 5, 72, 80, 20, 12, 201, 80, 147, 19, 80, 81, 5, 48, 145, 192, 20, 13, 138, 15, 22, 5, 18, 19, 195, 166, 4, 9, 7, 20, 13, 138, 14, 195, 184, 4, 22, 5, 14, 4, 9, 7, 20, 12, 201, 32, 83, 2, 72, 81, 5, 48, 145, 192, 20, 12, 201, 32, 19, 19, 77, 64, 82, 72, 145, 192, 20, 12, 201, 28, 83, 130, 73, 81, 197, 48, 145, 192, 20, 12, 201, 24, 244, 132, 72, 17, 197, 48, 145, 192, 20, 9, 198, 72, 18, 201, 80, 148, 203, 20, 9, 198, 32, 20, 141, 60, 226, 75, 20, 12, 201, 80, 85, 18, 5, 96, 76, 20, 229, 0, 20, 0, 13, 202, 76, 17, 15, 52, 20, 207, 12, 130, 83, 80, 20, 9, 198, 56, 146, 9, 48, 148, 212, 20, 13, 202, 52, 19, 149, 24, 18, 212, 85, 34, 83, 80, 20, 9, 198, 37, 51, 1, 52, 148, 212, 20, 9, 198, 24, 21, 1, 48, 148, 212, 20, 9, 198, 4, 194, 217, 52, 148, 212, 20, 14, 139, 20, 9, 12, 2, 195, 184, 10, 5, 12, 9, 7, 20, 14, 139, 16, 195, 165, 18, 5, 7, 14, 5, 12, 9, 7, 20, 9, 198, 77, 64, 78, 56, 147, 204, 20, 9, 198, 5, 4, 5, 80, 149, 0, 20, 9, 198, 76, 225, 71, 48, 21, 0, 20, 9, 198, 72, 16, 130, 36, 224, 84, 20, 0, 12, 201, 44, 243, 147, 81, 37, 75, 80, 147, 206, 20, 12, 201, 36, 229, 18, 60, 69, 75, 80, 147, 206, 20, 12, 201, 16, 84, 201, 56, 97, 75, 80, 147, 206, 20, 12, 201, 12, 245, 133, 73, 97, 82, 76, 147, 206, 20, 10, 199, 52, 243, 137, 80, 244, 133, 72, 20, 10, 199, 52, 20, 211, 4, 180, 133, 72, 20, 15, 140, 20, 9, 12, 7, 195, 166, 14, 7, 5, 12, 9, 7, 20, 10, 199, 44, 21, 1, 52, 20, 129, 56, 21, 0, 22, 3, 7, 195, 165, 79, 111, 15, 48, 6, 111, 15, 108, 0, 82, 112, 195, 165, 32, 97, 102, 32, 12, 201, 48, 20, 153, 56, 115, 211, 44, 244, 0, 20, 6, 195, 48, 241, 201, 20, 9, 198, 76, 243, 21, 80, 147, 206, 20, 9, 198, 72, 245, 1, 80, 147, 206, 20, 9, 198, 56, 81, 193, 80, 147, 206, 20, 9, 198, 48, 81, 193, 80, 147, 206, 20, 9, 198, 20, 213, 76, 76, 147, 206, 20, 9, 198, 12, 149, 1, 80, 147, 206, 20, 11, 200, 64, 242, 213, 48, 84, 137, 56, 112, 20, 11, 200, 48, 144, 201, 80, 84, 137, 56, 112, 20, 11, 200, 12, 148, 197, 48, 84, 137, 56, 112, 20, 11, 200, 64, 83, 147, 36, 243, 133, 72, 80, 20, 16, 141, 15, 13, 11, 18, 9, 14, 7, 19, 195, 166, 4, 9, 7, 20, 11, 200, 45, 98, 78, 16, 17, 212, 36, 112, 20, 15, 204, 29, 81, 22, 20, 192, 133, 32, 17, 197, 48, 145, 192, 20, 15, 204, 29, 81, 19, 8, 84, 208, 61, 69, 5, 48, 145, 192, 20, 12, 137, 1, 6, 6, 195, 166, 12, 4, 9, 7, 20, 12, 201, 60, 229, 15, 28, 83, 133, 80, 148, 203, 20, 12, 201, 32, 84, 141, 20, 225, 85, 80, 148, 203, 20, 11, 200, 32, 83, 7, 20, 226, 78, 16, 80, 20, 11, 200, 45, 98, 78, 16, 17, 212, 36, 112, 20, 7, 196, 4, 97, 129, 8, 20, 11, 200, 44, 20, 148, 60, 227, 129, 28, 80, 20, 0, 33, 69, 65, 80, 140, 36, 48, 48, 112, 69, 55, 36, 49, 15, 87, 13, 12, 82, 37, 87, 14, 50, 0, 81, 115, 101, 114, 118, 105, 99, 101, 110, 32, 30, 69, 65, 80, 140, 36, 48, 48, 112, 69, 55, 36, 49, 15, 87, 13, 12, 82, 37, 87, 0, 81, 115, 101, 114, 118, 105, 99, 101, 32, 12, 201, 77, 2, 82, 37, 69, 65, 48, 148, 212, 20, 12, 201, 76, 243, 78, 4, 208, 149, 48, 148, 212, 20, 16, 205, 56, 21, 9, 60, 224, 76, 76, 240, 201, 4, 194, 83, 80, 20, 8, 197, 56, 245, 5, 72, 80, 20, 13, 138, 22, 195, 166, 18, 19, 1, 18, 20, 9, 7, 20, 12, 201, 56, 21, 21, 72, 96, 71, 48, 145, 192, 20, 13, 138, 7, 5, 19, 11, 195, 166, 6, 20, 9, 7, 20, 13, 138, 7, 5, 19, 10, 195, 166, 6, 20, 9, 7, 20, 12, 201, 24, 244, 132, 20, 192, 71, 80, 145, 192, 20, 8, 197, 20, 212, 1, 80, 144, 20, 31, 69, 65, 80, 140, 36, 48, 48, 112, 69, 55, 36, 49, 15, 70, 39, 63, 6, 108, 57, 50, 0, 20, 81, 100, 111, 109, 97, 105, 110, 32, 12, 201, 44, 244, 147, 21, 69, 5, 72, 85, 0, 20, 12, 201, 52, 81, 4, 20, 192, 71, 80, 145, 192, 20, 12, 201, 24, 244, 132, 20, 192, 71, 80, 145, 192, 20, 0, 9, 198, 32, 244, 141, 60, 225, 76, 20, 9, 198, 36, 229, 129, 48, 145, 0, 20, 9, 198, 21, 84, 143, 64, 145, 0, 20, 9, 198, 29, 80, 82, 4, 226, 64, 20, 9, 198, 64, 243, 9, 80, 146, 192, 20, 9, 198, 44, 84, 129, 52, 146, 192, 20, 9, 198, 52, 83, 5, 72, 85, 0, 20, 0, 9, 198, 21, 67, 143, 48, 241, 201, 20, 12, 201, 88, 19, 15, 72, 148, 193, 80, 147, 206, 20, 12, 201, 81, 148, 9, 24, 146, 193, 80, 147, 206, 20, 12, 201, 64, 243, 1, 72, 148, 193, 80, 147, 206, 20, 12, 201, 44, 243, 148, 36, 229, 65, 80, 147, 206, 20, 12, 201, 44, 243, 147, 80, 148, 1, 80, 147, 206, 20, 12, 201, 44, 243, 135, 72, 81, 193, 80, 147, 206, 20, 12, 201, 20, 208, 78, 12, 148, 1, 80, 147, 206, 20, 12, 201, 4, 211, 210, 80, 148, 193, 80, 147, 206, 20, 12, 201, 4, 194, 77, 20, 229, 1, 80, 147, 206, 20, 12, 201, 4, 48, 197, 57, 69, 65, 80, 147, 206, 20, 14, 203, 52, 146, 210, 61, 50, 207, 64, 84, 137, 56, 112, 20, 12, 201, 44, 243, 132, 37, 66, 79, 56, 83, 0, 20, 10, 199, 44, 244, 146, 84, 212, 5, 72, 20, 15, 140, 195, 165, 2, 5, 14, 8, 10, 5, 18, 20, 9, 7, 20, 15, 140, 22, 5, 4, 5, 18, 8, 195, 166, 6, 20, 9, 7, 20, 15, 140, 6, 15, 18, 18, 195, 165, 4, 14, 5, 12, 9, 7, 20, 15, 140, 6, 15, 18, 7, 195, 166, 14, 7, 5, 12, 9, 7, 20, 15, 140, 6, 15, 18, 6, 195, 166, 14, 7, 5, 12, 9, 7, 20, 9, 198, 44, 243, 12, 60, 66, 69, 20, 14, 203, 44, 243, 150, 20, 229, 21, 4, 194, 78, 16, 80, 20, 12, 201, 44, 243, 148, 84, 33, 82, 56, 19, 0, 20, 5, 195, 32, 244, 192, 0, 11, 200, 88, 148, 201, 80, 84, 137, 56, 112, 20, 11, 200, 88, 81, 197, 80, 84, 137, 56, 112, 20, 11, 200, 77, 64, 70, 24, 84, 137, 56, 112, 20, 11, 200, 72, 85, 137, 16, 84, 137, 56, 112, 20, 11, 200, 72, 83, 1, 80, 84, 137, 56, 112, 20, 11, 200, 56, 20, 193, 48, 84, 137, 56, 112, 20, 11, 200, 44, 194, 67, 32, 84, 137, 56, 112, 20, 11, 200, 72, 20, 16, 61, 37, 5, 72, 80, 20, 11, 200, 28, 20, 146, 61, 69, 5, 72, 80, 20, 12, 201, 81, 34, 75, 36, 226, 15, 48, 66, 71, 20, 12, 201, 48, 245, 141, 20, 66, 15, 48, 66, 71, 20, 12, 201, 48, 19, 135, 76, 243, 77, 20, 194, 71, 20, 12, 201, 25, 33, 77, 44, 243, 77, 20, 194, 71, 20, 16, 141, 6, 15, 18, 20, 18, 195, 166, 6, 6, 5, 12, 9, 7, 20, 11, 200, 80, 244, 15, 48, 241, 201, 76, 176, 20, 11, 200, 76, 86, 15, 48, 241, 201, 76, 176, 20, 11, 200, 53, 149, 15, 48, 241, 201, 76, 176, 20, 11, 200, 52, 243, 143, 48, 241, 201, 76, 176, 20, 11, 200, 9, 38, 79, 48, 241, 201, 76, 176, 20, 11, 200, 36, 229, 5, 72, 209, 68, 36, 80, 20, 11, 200, 44, 243, 147, 84, 194, 78, 16, 80, 20, 7, 196, 76, 83, 137, 48, 20, 7, 196, 72, 16, 129, 80, 20, 9, 198, 77, 147, 143, 16, 19, 0, 20, 0, 8, 197, 28, 83, 204, 60, 112, 20, 8, 197, 25, 84, 201, 60, 224, 20, 9, 198, 28, 85, 129, 48, 66, 71, 20, 8, 197, 65, 81, 82, 36, 192, 20, 8, 197, 80, 82, 206, 36, 176, 20, 8, 197, 77, 148, 212, 20, 208, 20, 8, 197, 16, 83, 69, 57, 48, 20, 0, 13, 202, 4, 67, 73, 56, 148, 212, 72, 21, 15, 72, 20, 9, 198, 80, 16, 200, 37, 53, 0, 20, 9, 198, 52, 20, 152, 37, 53, 0, 20, 9, 198, 16, 17, 1, 37, 53, 0, 20, 9, 198, 52, 83, 15, 16, 146, 192, 20, 9, 198, 20, 192, 83, 80, 146, 192, 20, 0, 10, 199, 44, 244, 9, 21, 34, 78, 28, 20, 14, 203, 20, 180, 208, 48, 144, 201, 80, 84, 137, 56, 112, 20, 10, 199, 12, 19, 80, 21, 34, 78, 28, 20, 19, 144, 7, 5, 14, 14, 5, 13, 20, 18, 195, 166, 14, 7, 5, 12, 9, 7, 20, 14, 203, 21, 2, 68, 20, 210, 79, 48, 241, 201, 76, 176, 20, 14, 203, 16, 144, 76, 20, 181, 15, 48, 241, 201, 76, 176, 20, 10, 199, 4, 69, 133, 72, 34, 85, 52, 20, 10, 199, 80, 244, 141, 20, 229, 9, 48, 20, 12, 137, 6, 195, 184, 14, 9, 11, 9, 5, 14, 20, 10, 199, 73, 85, 9, 56, 84, 133, 80, 20, 8, 67, 84, 226, 88, 21, 0, 10, 0, 11, 200, 60, 225, 21, 48, 21, 9, 60, 224, 20, 11, 200, 16, 148, 203, 72, 85, 9, 60, 224, 20, 11, 200, 16, 147, 1, 80, 21, 9, 60, 224, 20, 11, 200, 4, 100, 133, 4, 181, 9, 60, 224, 20, 11, 200, 4, 33, 82, 72, 21, 9, 60, 224, 20, 7, 196, 52, 241, 5, 48, 20, 9, 198, 44, 243, 150, 20, 225, 82, 20, 9, 198, 44, 240, 71, 84, 193, 82, 20, 9, 198, 36, 227, 203, 84, 193, 82, 20, 9, 198, 16, 85, 1, 12, 129, 82, 20, 11, 200, 17, 148, 208, 21, 5, 9, 76, 176, 20, 9, 198, 88, 19, 137, 48, 194, 78, 20, 11, 200, 56, 144, 193, 72, 17, 213, 4, 224, 20, 9, 198, 4, 84, 143, 64, 192, 78, 21, 11, 200, 77, 80, 140, 36, 210, 78, 4, 192, 20, 11, 200, 64, 84, 134, 61, 35, 65, 57, 48, 20, 0, 12, 201, 45, 34, 77, 36, 224, 76, 37, 53, 0, 20, 12, 201, 56, 245, 133, 48, 194, 83, 80, 146, 192, 20, 0, 9, 198, 52, 85, 15, 16, 148, 212, 20, 13, 202, 52, 19, 20, 72, 18, 212, 21, 34, 78, 28, 20, 13, 202, 24, 18, 211, 36, 210, 76, 21, 34, 78, 28, 20, 13, 202, 20, 180, 208, 5, 68, 137, 21, 34, 78, 28, 20, 13, 202, 20, 180, 208, 21, 34, 77, 20, 229, 5, 48, 20, 13, 202, 16, 242, 213, 52, 83, 148, 5, 34, 85, 52, 20, 9, 198, 8, 18, 197, 48, 149, 0, 20, 13, 202, 76, 83, 22, 12, 83, 148, 72, 84, 133, 80, 20, 6, 66, 4, 96, 108, 0, 0, 6, 195, 89, 51, 208, 17, 12, 201, 8, 83, 133, 16, 146, 212, 36, 225, 82, 68, 10, 199, 32, 148, 212, 60, 116, 129, 52, 20, 12, 201, 77, 80, 150, 20, 229, 9, 60, 225, 82, 20, 12, 201, 65, 35, 208, 61, 37, 9, 60, 225, 82, 20, 0, 7, 196, 85, 33, 197, 72, 20, 9, 198, 72, 84, 201, 28, 225, 82, 20, 9, 198, 72, 17, 134, 36, 225, 82, 20, 9, 198, 21, 128, 197, 48, 193, 82, 20, 9, 198, 20, 208, 129, 48, 193, 82, 20, 9, 198, 53, 84, 211, 20, 194, 78, 20, 7, 196, 44, 147, 137, 56, 20, 9, 68, 25, 33, 65, 44, 21, 0, 10, 0, 24, 73, 76, 176, 84, 20, 35, 193, 72, 65, 84, 87, 49, 6, 36, 37, 47, 69, 39, 13, 70, 106, 84, 0, 9, 198, 37, 51, 1, 52, 148, 203, 20, 9, 198, 36, 229, 73, 80, 148, 203, 20, 9, 198, 21, 66, 79, 64, 148, 203, 20, 9, 198, 16, 82, 193, 16, 148, 203, 20, 9, 198, 5, 50, 197, 80, 148, 203, 20, 12, 201, 65, 35, 208, 61, 37, 9, 60, 224, 76, 20, 0, 9, 198, 20, 193, 70, 4, 229, 0, 20, 0, 10, 199, 88, 83, 133, 72, 243, 15, 28, 20, 10, 199, 61, 35, 137, 80, 243, 15, 28, 20, 10, 199, 28, 192, 67, 36, 243, 15, 28, 20, 10, 199, 45, 34, 78, 60, 194, 78, 20, 20, 12, 201, 44, 243, 148, 72, 20, 201, 28, 225, 82, 20, 10, 199, 36, 212, 12, 4, 229, 5, 72, 20, 10, 199, 77, 81, 134, 37, 48, 78, 80, 20, 0, 15, 204, 65, 35, 198, 21, 52, 201, 60, 224, 76, 37, 53, 0, 20, 7, 196, 41, 81, 197, 72, 20, 12, 201, 77, 65, 84, 61, 50, 207, 64, 148, 203, 20, 12, 201, 64, 243, 25, 12, 83, 148, 72, 148, 203, 20, 12, 201, 64, 84, 137, 64, 21, 5, 80, 148, 203, 20, 12, 201, 52, 18, 210, 61, 50, 207, 64, 148, 203, 20, 12, 201, 44, 244, 205, 60, 224, 85, 80, 148, 203, 20, 12, 201, 13, 149, 15, 28, 83, 133, 80, 148, 203, 20, 7, 196, 21, 97, 78, 80, 20, 9, 198, 16, 82, 204, 36, 224, 66, 20, 9, 68, 21, 97, 78, 80, 21, 0, 10, 0, 13, 138, 7, 25, 14, 195, 166, 11, 15, 12, 15, 7, 20, 8, 197, 84, 226, 83, 60, 224, 20, 8, 197, 61, 5, 9, 60, 224, 20, 8, 197, 48, 81, 201, 60, 224, 20, 11, 136, 12, 195, 184, 22, 9, 14, 4, 5, 20, 0, 8, 67, 80, 19, 11, 21, 0, 10, 0, 10, 199, 76, 147, 85, 48, 21, 15, 72, 20, 10, 199, 36, 226, 9, 8, 149, 15, 72, 20, 15, 140, 6, 195, 166, 14, 15, 13, 5, 14, 15, 12, 15, 7, 20, 12, 201, 88, 242, 193, 48, 148, 193, 80, 147, 206, 20, 10, 199, 88, 20, 137, 5, 66, 79, 56, 20, 12, 201, 72, 84, 212, 5, 84, 129, 80, 147, 206, 20, 10, 199, 65, 35, 205, 61, 66, 79, 56, 20, 12, 201, 48, 81, 193, 48, 148, 193, 80, 147, 206, 20, 10, 199, 44, 243, 77, 84, 226, 79, 56, 20, 12, 201, 44, 243, 15, 56, 148, 193, 80, 147, 206, 20, 12, 201, 44, 21, 5, 44, 148, 193, 80, 147, 206, 20, 12, 201, 44, 19, 129, 48, 148, 193, 80, 147, 206, 20, 10, 199, 5, 52, 197, 73, 66, 79, 56, 20, 10, 199, 4, 226, 77, 5, 66, 79, 56, 20, 10, 199, 64, 244, 212, 16, 21, 5, 72, 20, 10, 199, 24, 197, 79, 72, 145, 5, 72, 20, 15, 204, 44, 243, 77, 84, 224, 76, 64, 243, 9, 80, 148, 203, 20, 10, 199, 28, 83, 198, 101, 50, 83, 44, 20, 10, 199, 5, 85, 1, 72, 178, 83, 44, 20, 0, 11, 200, 32, 84, 131, 20, 115, 214, 36, 224, 20, 9, 198, 16, 148, 203, 85, 64, 66, 20, 9, 198, 4, 48, 197, 65, 64, 66, 20, 0, 8, 197, 48, 19, 131, 21, 32, 20, 8, 197, 25, 83, 135, 21, 32, 20, 8, 197, 44, 197, 83, 36, 192, 20, 8, 197, 12, 130, 76, 20, 224, 20, 8, 197, 65, 35, 198, 4, 224, 21, 8, 197, 5, 67, 205, 5, 32, 20, 0, 9, 198, 12, 245, 84, 85, 33, 64, 20, 13, 202, 76, 81, 9, 52, 83, 148, 5, 66, 79, 56, 20, 13, 202, 44, 243, 134, 72, 243, 148, 5, 66, 79, 56, 20, 13, 202, 16, 242, 213, 52, 83, 148, 5, 66, 79, 56, 20, 13, 202, 5, 33, 213, 52, 83, 148, 5, 66, 79, 56, 20, 9, 198, 77, 83, 77, 21, 33, 64, 20, 9, 198, 37, 32, 75, 37, 50, 192, 20, 9, 198, 36, 33, 82, 37, 50, 192, 20, 9, 198, 20, 198, 83, 37, 50, 192, 20, 16, 141, 9, 19, 12, 195, 166, 14, 4, 5, 18, 9, 14, 4, 5, 20, 9, 198, 72, 82, 212, 61, 32, 76, 20, 0, 10, 199, 65, 80, 140, 36, 50, 83, 80, 20, 10, 199, 52, 18, 84, 72, 84, 211, 20, 20, 6, 195, 61, 32, 76, 20, 9, 198, 64, 19, 9, 76, 17, 5, 20, 20, 70, 45, 37, 83, 80, 17, 5, 49, 34, 114, 87, 70, 6, 108, 12, 84, 13, 0, 20, 10, 199, 36, 225, 21, 45, 64, 78, 76, 20, 0, 7, 196, 81, 34, 83, 80, 20, 11, 200, 65, 35, 214, 36, 228, 201, 20, 192, 20, 11, 200, 88, 84, 130, 4, 194, 83, 21, 32, 20, 11, 200, 81, 148, 129, 56, 226, 83, 21, 32, 20, 11, 200, 77, 65, 82, 36, 194, 83, 21, 32, 20, 11, 200, 77, 64, 66, 36, 194, 83, 21, 32, 20, 11, 200, 76, 145, 206, 4, 194, 83, 21, 32, 20, 11, 200, 28, 84, 141, 4, 226, 83, 21, 32, 20, 11, 200, 28, 19, 22, 4, 226, 83, 21, 32, 20, 0, 12, 201, 65, 54, 75, 60, 102, 83, 37, 50, 192, 20, 12, 201, 64, 243, 25, 4, 225, 18, 37, 50, 192, 20, 12, 201, 20, 115, 195, 20, 229, 18, 37, 50, 192, 20, 0, 9, 198, 64, 21, 15, 48, 241, 192, 20, 9, 198, 60, 226, 207, 48, 241, 192, 20, 9, 198, 4, 194, 207, 48, 241, 192, 20, 9, 198, 64, 20, 139, 21, 33, 64, 20, 9, 198, 24, 146, 211, 21, 33, 64, 20, 5, 194, 16, 16, 72, 0, 10, 199, 5, 48, 133, 77, 67, 211, 20, 20, 10, 199, 65, 35, 203, 85, 34, 83, 80, 20, 10, 199, 56, 245, 133, 48, 194, 83, 80, 20, 10, 199, 52, 241, 5, 72, 226, 83, 80, 20, 10, 199, 44, 243, 80, 60, 226, 83, 80, 20, 10, 199, 44, 243, 77, 84, 226, 83, 80, 20, 10, 199, 32, 20, 144, 20, 226, 83, 80, 20, 14, 203, 36, 225, 21, 77, 68, 137, 4, 194, 83, 21, 32, 20, 14, 203, 16, 149, 137, 76, 147, 206, 4, 194, 83, 21, 32, 20, 9, 198, 76, 84, 133, 56, 17, 5, 20, 0, 11, 200, 88, 84, 147, 36, 98, 67, 21, 32, 20, 11, 200, 72, 84, 18, 60, 69, 67, 21, 32, 20, 11, 200, 53, 148, 212, 36, 98, 67, 21, 32, 20, 11, 200, 45, 96, 76, 36, 98, 67, 21, 32, 20, 11, 200, 36, 229, 18, 60, 69, 67, 21, 32, 20, 15, 204, 80, 161, 75, 44, 244, 204, 61, 96, 75, 37, 50, 192, 20, 0, 16, 205, 84, 65, 9, 24, 97, 82, 20, 229, 9, 21, 34, 78, 28, 20, 12, 201, 72, 84, 197, 73, 97, 82, 36, 225, 192, 20, 12, 201, 72, 83, 73, 81, 65, 82, 36, 225, 192, 20, 12, 201, 64, 192, 75, 5, 65, 82, 36, 225, 192, 20, 12, 201, 64, 84, 134, 61, 33, 82, 36, 225, 192, 20, 12, 201, 64, 21, 5, 57, 65, 82, 36, 225, 192, 20, 12, 201, 60, 36, 197, 73, 97, 82, 36, 225, 192, 20, 12, 201, 57, 83, 77, 21, 33, 82, 36, 225, 192, 20, 12, 201, 45, 83, 20, 37, 97, 82, 36, 225, 192, 20, 12, 201, 45, 33, 68, 37, 65, 82, 36, 225, 192, 20, 12, 201, 44, 243, 77, 85, 65, 82, 36, 225, 192, 20, 12, 201, 44, 20, 130, 85, 33, 82, 36, 225, 192, 20, 12, 201, 44, 19, 9, 9, 33, 82, 36, 225, 192, 20, 12, 201, 36, 229, 133, 57, 65, 82, 36, 225, 192, 20, 12, 201, 36, 229, 5, 29, 33, 82, 36, 225, 192, 20, 12, 201, 32, 244, 208, 37, 65, 82, 36, 225, 192, 20, 12, 201, 24, 16, 197, 81, 65, 82, 36, 225, 192, 20, 12, 201, 16, 84, 197, 73, 65, 82, 36, 225, 192, 20, 12, 201, 16, 84, 15, 73, 65, 82, 36, 225, 192, 20, 12, 201, 8, 19, 12, 61, 65, 82, 36, 225, 192, 20, 12, 201, 5, 69, 5, 77, 65, 82, 36, 225, 192, 20, 12, 201, 5, 49, 129, 49, 65, 82, 36, 225, 192, 20, 12, 201, 5, 4, 18, 21, 65, 82, 36, 225, 192, 20, 12, 201, 4, 36, 197, 57, 65, 82, 36, 225, 192, 20, 0, 13, 202, 88, 147, 204, 60, 224, 197, 48, 194, 83, 80, 20, 9, 198, 65, 35, 211, 4, 148, 212, 20, 9, 198, 56, 144, 143, 56, 149, 0, 20, 0, 26, 73, 64, 21, 18, 60, 230, 77, 36, 179, 206, 48, 108, 47, 34, 39, 50, 6, 114, 63, 37, 49, 112, 50, 0, 20, 12, 201, 76, 21, 9, 76, 96, 75, 80, 147, 206, 20, 12, 201, 72, 84, 18, 60, 69, 75, 80, 147, 206, 20, 12, 201, 41, 84, 137, 76, 66, 75, 80, 147, 206, 20, 10, 199, 4, 48, 197, 77, 50, 79, 56, 20, 10, 199, 81, 32, 86, 21, 36, 197, 72, 20, 10, 199, 72, 80, 201, 16, 149, 133, 72, 20, 10, 199, 4, 48, 197, 48, 84, 133, 72, 20, 10, 199, 61, 3, 1, 16, 83, 9, 28, 20, 0, 12, 201, 44, 19, 5, 40, 67, 211, 44, 244, 0, 20, 12, 201, 28, 19, 22, 4, 227, 211, 44, 244, 0, 20, 11, 200, 88, 19, 9, 16, 84, 137, 56, 112, 20, 11, 200, 84, 68, 129, 16, 84, 137, 56, 112, 20, 11, 200, 81, 84, 195, 32, 84, 137, 56, 112, 20, 11, 200, 77, 3, 206, 76, 84, 137, 56, 112, 20, 11, 200, 76, 19, 21, 80, 84, 137, 56, 112, 20, 11, 200, 60, 225, 21, 48, 84, 137, 56, 112, 20, 11, 200, 52, 147, 137, 52, 84, 137, 56, 112, 20, 11, 200, 52, 18, 213, 48, 84, 137, 56, 112, 20, 15, 204, 44, 243, 148, 36, 225, 197, 57, 65, 82, 36, 225, 192, 20, 11, 200, 28, 19, 15, 64, 84, 137, 56, 112, 20, 11, 200, 24, 147, 5, 80, 84, 137, 56, 112, 20, 11, 200, 20, 180, 201, 48, 84, 137, 56, 112, 20, 11, 200, 16, 82, 193, 80, 84, 137, 56, 112, 20, 15, 204, 9, 35, 206, 44, 244, 203, 61, 1, 82, 36, 225, 192, 20, 7, 196, 45, 33, 69, 72, 20, 11, 200, 81, 83, 135, 76, 147, 132, 36, 112, 20, 11, 200, 80, 18, 211, 45, 147, 4, 36, 112, 20, 11, 200, 52, 19, 135, 24, 243, 4, 36, 112, 20, 11, 200, 44, 243, 4, 8, 195, 196, 36, 112, 20, 11, 200, 29, 81, 6, 73, 145, 212, 36, 112, 20, 11, 200, 4, 193, 129, 16, 84, 140, 36, 112, 20, 11, 200, 65, 35, 214, 77, 66, 78, 16, 80, 20, 7, 196, 76, 81, 1, 56, 21, 9, 68, 8, 246, 76, 20, 21, 0, 10, 0, 12, 201, 77, 65, 82, 20, 243, 69, 81, 34, 64, 20, 12, 201, 44, 243, 15, 72, 147, 69, 81, 34, 64, 20, 8, 197, 32, 21, 129, 72, 144, 20, 8, 197, 8, 20, 143, 56, 144, 20, 0, 9, 198, 64, 84, 147, 60, 225, 76, 20, 9, 198, 88, 20, 203, 21, 34, 64, 20, 9, 198, 64, 192, 71, 21, 34, 64, 20, 9, 198, 48, 147, 135, 21, 34, 64, 20, 9, 198, 32, 82, 211, 21, 34, 64, 20, 9, 198, 48, 19, 212, 37, 50, 192, 20, 9, 198, 44, 19, 212, 37, 50, 192, 20, 9, 198, 8, 147, 212, 37, 50, 192, 20, 9, 198, 52, 19, 1, 44, 149, 0, 20, 0, 10, 199, 65, 35, 195, 21, 52, 207, 72, 20, 14, 203, 77, 147, 80, 80, 243, 65, 80, 243, 15, 28, 144, 20, 9, 198, 64, 21, 15, 48, 241, 201, 20, 9, 198, 60, 226, 207, 48, 241, 201, 20, 9, 198, 32, 243, 79, 48, 241, 201, 20, 9, 198, 13, 149, 15, 48, 241, 201, 20, 10, 199, 64, 243, 12, 85, 66, 79, 56, 20, 10, 199, 4, 97, 133, 45, 66, 79, 56, 20, 14, 203, 72, 82, 1, 8, 147, 9, 80, 84, 137, 56, 112, 20, 14, 203, 52, 243, 143, 25, 67, 206, 28, 84, 137, 56, 112, 20, 0, 18, 7, 12, 39, 3, 8, 1, 9, 13, 55, 108, 49, 34, 6, 35, 57, 63, 0, 12, 137, 11, 1, 22, 5, 18, 14, 195, 184, 19, 20, 11, 200, 88, 83, 133, 72, 243, 15, 28, 144, 20, 11, 200, 61, 35, 137, 80, 243, 15, 28, 144, 20, 11, 200, 28, 192, 67, 36, 243, 15, 28, 144, 20, 16, 6, 18, 195, 166, 19, 15, 14, 51, 107, 87, 6, 112, 66, 0, 20, 11, 200, 21, 50, 193, 48, 84, 137, 56, 112, 20, 11, 200, 36, 225, 19, 81, 81, 5, 72, 80, 20, 11, 200, 48, 145, 66, 32, 21, 133, 72, 144, 20, 11, 200, 8, 241, 200, 60, 193, 5, 72, 144, 20, 11, 200, 36, 229, 5, 72, 197, 68, 36, 80, 20, 11, 200, 44, 243, 80, 61, 50, 84, 84, 208, 20, 11, 200, 64, 243, 25, 56, 243, 73, 84, 208, 20, 11, 200, 52, 147, 12, 20, 227, 137, 84, 208, 20, 11, 200, 21, 96, 78, 28, 83, 9, 84, 208, 20, 11, 200, 32, 84, 148, 84, 114, 78, 16, 80, 20, 7, 196, 52, 240, 137, 48, 20, 7, 196, 16, 80, 129, 80, 20, 9, 198, 45, 38, 83, 80, 19, 0, 20, 0, 12, 201, 64, 19, 132, 20, 176, 71, 21, 34, 64, 20, 12, 201, 81, 34, 78, 36, 64, 68, 37, 50, 192, 20, 12, 201, 80, 83, 5, 76, 179, 208, 37, 50, 192, 20, 12, 201, 64, 20, 129, 80, 18, 212, 37, 50, 192, 20, 12, 201, 48, 16, 153, 72, 147, 148, 37, 50, 192, 20, 12, 201, 37, 52, 129, 20, 194, 84, 37, 50, 192, 20, 12, 201, 33, 148, 15, 80, 18, 212, 37, 50, 192, 20, 12, 201, 33, 145, 18, 60, 198, 84, 37, 50, 192, 20, 12, 201, 4, 193, 207, 72, 149, 13, 37, 50, 192, 20, 12, 201, 16, 243, 73, 12, 147, 5, 72, 85, 0, 20, 8, 197, 76, 17, 146, 4, 224, 21, 0, 14, 139, 19, 5, 14, 20, 5, 14, 20, 9, 195, 184, 19, 20, 14, 139, 16, 18, 15, 13, 9, 19, 11, 21, 195, 184, 19, 20, 9, 198, 41, 81, 1, 37, 53, 0, 20, 9, 198, 4, 65, 78, 60, 145, 0, 20, 9, 198, 24, 244, 131, 21, 33, 84, 20, 9, 198, 72, 81, 201, 60, 224, 76, 20, 9, 198, 29, 85, 20, 85, 32, 76, 20, 0, 15, 140, 16, 18, 195, 166, 20, 5, 14, 20, 9, 195, 184, 19, 20, 12, 137, 7, 21, 22, 5, 18, 14, 195, 184, 18, 20, 10, 199, 44, 195, 210, 21, 34, 78, 28, 20, 12, 201, 72, 81, 133, 72, 83, 148, 36, 83, 0, 20, 10, 199, 16, 83, 5, 28, 84, 133, 80, 20, 10, 199, 16, 80, 201, 16, 84, 133, 80, 20, 10, 199, 4, 197, 5, 72, 84, 133, 80, 20, 12, 201, 16, 147, 69, 57, 50, 79, 56, 19, 0, 20, 0, 7, 196, 88, 243, 21, 80, 20, 9, 198, 77, 1, 75, 84, 193, 82, 20, 9, 198, 64, 192, 84, 36, 225, 82, 20, 9, 198, 64, 20, 208, 60, 193, 82, 20, 9, 198, 44, 242, 197, 81, 65, 82, 20, 9, 198, 44, 19, 11, 84, 193, 82, 20, 9, 198, 16, 148, 211, 60, 225, 82, 20, 9, 198, 16, 84, 212, 36, 225, 82, 20, 9, 198, 16, 82, 204, 36, 225, 82, 20, 9, 198, 5, 4, 18, 60, 33, 82, 20, 9, 198, 88, 149, 18, 36, 243, 0, 20, 11, 200, 9, 35, 205, 44, 19, 9, 84, 208, 20, 9, 198, 77, 80, 141, 5, 34, 78, 20, 9, 198, 16, 19, 13, 5, 66, 78, 20, 7, 196, 64, 81, 1, 48, 20, 7, 196, 52, 241, 1, 48, 20, 7, 196, 5, 33, 65, 48, 20, 0, 14, 139, 1, 13, 2, 1, 19, 19, 1, 4, 195, 184, 18, 20, 12, 201, 65, 35, 205, 37, 50, 213, 37, 65, 84, 20, 12, 201, 80, 83, 5, 80, 82, 206, 37, 50, 192, 20, 12, 201, 76, 147, 135, 4, 193, 83, 37, 50, 192, 20, 12, 201, 52, 17, 1, 28, 20, 203, 37, 50, 192, 20, 12, 201, 44, 244, 205, 60, 115, 206, 37, 50, 192, 20, 12, 201, 28, 84, 149, 56, 66, 86, 37, 50, 192, 20, 12, 201, 64, 84, 137, 4, 194, 83, 21, 33, 84, 20, 0, 9, 198, 48, 19, 65, 37, 53, 0, 20, 20, 66, 12, 64, 87, 36, 70, 36, 51, 6, 112, 63, 0, 44, 20, 81, 114, 111, 109, 32, 9, 198, 17, 147, 129, 52, 149, 0, 20, 13, 202, 20, 180, 208, 21, 34, 77, 20, 229, 1, 48, 20, 13, 202, 16, 84, 1, 73, 65, 77, 20, 229, 1, 48, 20, 0, 12, 137, 16, 18, 195, 166, 13, 1, 20, 21, 18, 20, 10, 199, 56, 21, 9, 88, 149, 5, 80, 20, 10, 199, 52, 18, 143, 72, 149, 5, 80, 20, 10, 199, 48, 246, 65, 48, 149, 5, 80, 20, 10, 199, 36, 229, 9, 52, 149, 5, 80, 20, 10, 199, 4, 97, 137, 56, 149, 5, 80, 20, 12, 201, 36, 211, 65, 81, 34, 75, 84, 193, 82, 20, 12, 201, 8, 144, 140, 36, 241, 210, 4, 97, 82, 20, 10, 199, 52, 244, 129, 80, 244, 137, 20, 20, 10, 199, 65, 148, 129, 52, 145, 1, 48, 20, 0, 21, 68, 77, 67, 210, 80, 87, 47, 39, 34, 70, 15, 105, 110, 40, 0, 81, 104, 97, 118, 32, 15, 204, 84, 225, 5, 72, 82, 211, 81, 33, 77, 37, 65, 84, 20, 9, 198, 81, 33, 77, 84, 193, 82, 20, 9, 198, 65, 35, 198, 4, 225, 82, 20, 9, 198, 56, 149, 133, 48, 193, 82, 20, 9, 198, 52, 245, 73, 48, 193, 82, 20, 9, 198, 44, 243, 77, 5, 65, 82, 20, 9, 198, 36, 226, 193, 72, 225, 82, 20, 9, 198, 25, 37, 83, 81, 33, 82, 20, 9, 198, 16, 148, 203, 85, 65, 82, 20, 7, 196, 4, 65, 5, 72, 20, 0, 9, 198, 76, 130, 73, 80, 148, 203, 20, 9, 198, 65, 35, 211, 4, 148, 203, 20, 9, 198, 49, 83, 129, 80, 148, 203, 20, 9, 198, 9, 83, 9, 52, 148, 203, 20, 9, 198, 5, 67, 5, 80, 148, 203, 20, 9, 198, 17, 32, 77, 5, 66, 75, 20, 0, 13, 202, 77, 80, 147, 36, 66, 65, 72, 149, 5, 80, 20, 13, 202, 64, 192, 85, 76, 144, 137, 48, 149, 5, 80, 20, 13, 202, 21, 128, 197, 57, 68, 137, 12, 149, 5, 80, 20, 13, 202, 4, 113, 210, 21, 52, 201, 88, 149, 5, 80, 20, 9, 198, 52, 20, 135, 21, 34, 84, 20, 9, 198, 24, 244, 198, 61, 34, 84, 20, 0, 10, 199, 20, 118, 80, 80, 243, 15, 28, 20, 10, 199, 72, 80, 75, 80, 149, 133, 72, 20, 12, 137, 13, 195, 166, 1, 14, 4, 18, 5, 18, 20, 10, 199, 44, 243, 150, 21, 33, 197, 72, 20, 10, 199, 44, 243, 147, 84, 197, 5, 72, 20, 12, 201, 44, 243, 80, 48, 83, 69, 57, 65, 82, 20, 10, 199, 44, 243, 77, 4, 225, 5, 72, 20, 10, 199, 77, 67, 210, 4, 117, 9, 28, 20, 10, 199, 8, 20, 142, 4, 117, 9, 28, 20, 10, 199, 52, 243, 143, 45, 32, 84, 36, 20, 10, 199, 77, 67, 210, 4, 117, 9, 28, 20, 10, 199, 8, 20, 142, 4, 117, 9, 28, 20, 10, 199, 36, 229, 18, 36, 112, 78, 80, 20, 0, 9, 198, 44, 244, 148, 37, 51, 206, 20, 7, 196, 52, 83, 15, 56, 20, 13, 138, 9, 13, 16, 18, 195, 166, 7, 14, 5, 18, 20, 7, 196, 49, 81, 193, 72, 20, 9, 198, 44, 243, 77, 85, 64, 66, 20, 0, 7, 197, 8, 19, 12, 60, 224, 12, 201, 20, 180, 208, 21, 34, 77, 20, 229, 0, 20, 12, 201, 44, 243, 77, 84, 226, 75, 4, 229, 0, 20, 10, 69, 64, 145, 7, 36, 224, 21, 0, 10, 0, 13, 202, 20, 101, 5, 73, 33, 84, 80, 83, 9, 28, 20, 12, 201, 64, 244, 212, 76, 52, 137, 65, 69, 77, 20, 0, 12, 201, 53, 83, 73, 24, 146, 193, 80, 147, 206, 20, 10, 199, 72, 84, 208, 20, 181, 5, 72, 20, 10, 199, 52, 83, 147, 81, 37, 69, 72, 20, 10, 199, 44, 243, 147, 81, 37, 69, 72, 20, 10, 199, 36, 228, 212, 37, 69, 69, 72, 20, 10, 199, 5, 53, 18, 36, 225, 197, 72, 20, 10, 199, 4, 225, 204, 37, 53, 9, 44, 20, 10, 199, 29, 32, 84, 84, 192, 78, 80, 20, 10, 199, 16, 83, 196, 61, 32, 78, 80, 20, 10, 199, 44, 243, 134, 37, 50, 193, 8, 20, 0, 10, 67, 16, 21, 5, 70, 36, 57, 47, 0, 12, 201, 88, 246, 69, 85, 34, 83, 80, 148, 203, 20, 12, 201, 80, 84, 146, 61, 34, 83, 80, 148, 203, 20, 12, 201, 77, 147, 66, 60, 194, 83, 80, 148, 203, 20, 12, 201, 77, 64, 76, 36, 226, 83, 80, 148, 203, 20, 12, 201, 77, 2, 82, 37, 66, 83, 80, 148, 203, 20, 12, 201, 76, 240, 201, 4, 194, 83, 80, 148, 203, 20, 12, 201, 72, 149, 21, 4, 194, 83, 80, 148, 203, 20, 12, 201, 65, 34, 86, 5, 66, 83, 80, 148, 203, 20, 12, 201, 28, 83, 197, 48, 82, 212, 72, 148, 203, 20, 12, 201, 24, 244, 141, 4, 194, 83, 80, 148, 203, 20, 12, 201, 24, 85, 68, 4, 194, 83, 80, 148, 203, 20, 12, 201, 24, 85, 9, 12, 130, 83, 80, 148, 203, 20, 12, 201, 16, 20, 151, 36, 226, 83, 80, 148, 203, 20, 12, 201, 9, 37, 84, 4, 194, 83, 80, 148, 203, 20, 12, 201, 4, 36, 213, 72, 66, 83, 80, 148, 203, 20, 0, 21, 73, 64, 20, 211, 21, 0, 82, 80, 245, 84, 48, 108, 35, 69, 110, 47, 6, 40, 0, 20, 8, 197, 76, 19, 4, 21, 32, 20, 8, 197, 4, 114, 84, 21, 32, 20, 8, 197, 64, 83, 131, 36, 192, 20, 8, 197, 44, 243, 131, 36, 192, 20, 12, 201, 81, 32, 78, 77, 0, 82, 20, 229, 0, 20, 12, 201, 81, 32, 78, 77, 0, 82, 20, 228, 192, 20, 0, 13, 202, 45, 96, 76, 36, 98, 75, 5, 66, 79, 56, 20, 9, 198, 80, 16, 149, 21, 33, 64, 20, 9, 198, 56, 244, 141, 21, 33, 64, 20, 9, 198, 24, 84, 137, 21, 33, 64, 20, 9, 198, 36, 179, 206, 37, 50, 192, 20, 9, 198, 77, 1, 75, 81, 32, 76, 20, 9, 198, 44, 244, 144, 61, 32, 76, 20, 9, 198, 24, 84, 212, 37, 96, 76, 20, 0, 15, 204, 76, 17, 15, 52, 20, 207, 12, 130, 83, 80, 148, 203, 20, 15, 204, 64, 84, 134, 20, 181, 9, 60, 226, 83, 80, 148, 203, 20, 15, 204, 44, 243, 77, 84, 226, 84, 5, 34, 83, 80, 148, 203, 20, 15, 204, 36, 225, 9, 88, 145, 21, 4, 194, 83, 80, 148, 203, 20, 15, 204, 36, 212, 18, 21, 52, 201, 60, 226, 83, 80, 148, 203, 20, 15, 204, 20, 180, 208, 4, 228, 201, 60, 226, 83, 80, 148, 203, 20, 13, 138, 12, 195, 166, 18, 5, 18, 9, 14, 4, 5, 20, 9, 198, 44, 19, 143, 56, 17, 5, 20, 0, 11, 200, 44, 19, 132, 36, 64, 84, 85, 32, 20, 11, 200, 61, 33, 193, 56, 241, 210, 4, 208, 20, 11, 200, 45, 38, 80, 80, 241, 210, 4, 208, 20, 11, 200, 20, 180, 208, 48, 242, 84, 21, 32, 20, 11, 200, 4, 178, 207, 52, 211, 196, 21, 32, 20, 16, 141, 16, 18, 15, 16, 195, 166, 4, 5, 21, 20, 9, 19, 11, 20, 11, 200, 77, 66, 80, 20, 225, 9, 84, 208, 20, 11, 200, 44, 243, 80, 20, 225, 9, 84, 208, 20, 0, 8, 197, 45, 83, 20, 85, 32, 20, 8, 197, 45, 34, 68, 21, 32, 20, 8, 197, 41, 84, 212, 21, 32, 20, 12, 201, 36, 225, 140, 5, 67, 210, 37, 50, 192, 20, 0, 9, 198, 80, 19, 135, 21, 33, 64, 20, 9, 198, 64, 21, 83, 21, 33, 64, 20, 9, 198, 52, 20, 211, 21, 33, 64, 20, 9, 198, 52, 20, 203, 21, 33, 64, 20, 9, 198, 52, 20, 139, 21, 33, 64, 20, 9, 198, 52, 19, 139, 21, 33, 64, 20, 9, 198, 45, 84, 147, 21, 33, 64, 20, 9, 198, 44, 20, 211, 21, 33, 64, 20, 9, 198, 24, 147, 135, 21, 33, 64, 20, 0, 10, 199, 88, 20, 197, 45, 67, 205, 36, 20, 9, 198, 72, 83, 85, 48, 17, 5, 20, 9, 198, 52, 84, 211, 36, 17, 5, 20, 10, 199, 61, 33, 15, 56, 224, 78, 76, 20, 0, 15, 204, 24, 244, 148, 36, 98, 75, 5, 67, 210, 37, 50, 192, 20, 7, 196, 88, 83, 137, 56, 20, 11, 200, 77, 66, 80, 20, 225, 9, 5, 64, 20, 7, 196, 61, 34, 193, 56, 21, 0, 8, 197, 21, 2, 76, 60, 112, 20, 8, 197, 52, 19, 5, 72, 144, 20, 9, 198, 88, 242, 193, 48, 148, 203, 20, 9, 198, 76, 177, 77, 5, 66, 75, 20, 12, 201, 44, 243, 147, 80, 149, 21, 20, 229, 0, 20, 0, 9, 198, 88, 242, 193, 48, 148, 212, 20, 9, 198, 4, 227, 129, 48, 148, 212, 20, 9, 198, 44, 19, 148, 61, 34, 64, 20, 9, 198, 76, 178, 90, 60, 145, 0, 20, 9, 198, 72, 82, 212, 61, 32, 84, 20, 9, 198, 52, 241, 5, 72, 21, 0, 20, 9, 198, 48, 82, 212, 61, 32, 84, 20, 0, 10, 199, 76, 81, 205, 20, 229, 5, 72, 20, 10, 199, 64, 145, 205, 20, 229, 5, 72, 20, 10, 199, 44, 243, 134, 84, 225, 5, 72, 20, 10, 199, 5, 84, 203, 84, 197, 5, 72, 20, 10, 199, 61, 4, 201, 28, 83, 9, 28, 20, 10, 199, 33, 83, 4, 76, 19, 9, 28, 20, 10, 199, 4, 229, 1, 28, 83, 9, 28, 20, 10, 199, 4, 228, 203, 84, 83, 9, 28, 20, 9, 198, 32, 148, 212, 61, 34, 69, 20, 0, 22, 72, 48, 81, 197, 56, 65, 82, 56, 80, 55, 36, 79, 6, 107, 50, 70, 112, 50, 106, 87, 0, 21, 72, 48, 81, 197, 56, 65, 82, 56, 80, 55, 36, 79, 6, 107, 50, 70, 112, 50, 106, 0, 11, 200, 16, 84, 212, 36, 195, 5, 72, 144, 20, 11, 200, 81, 98, 86, 48, 17, 212, 36, 112, 20, 11, 200, 76, 176, 76, 44, 17, 212, 36, 112, 20, 11, 200, 72, 81, 197, 16, 84, 140, 36, 112, 20, 11, 200, 52, 19, 132, 32, 17, 148, 36, 112, 20, 11, 200, 24, 244, 149, 17, 49, 76, 36, 112, 20, 11, 200, 24, 244, 147, 80, 19, 132, 36, 112, 20, 11, 200, 64, 20, 129, 16, 148, 201, 76, 176, 20, 11, 200, 52, 19, 131, 33, 84, 137, 76, 176, 20, 12, 201, 5, 66, 5, 56, 145, 78, 76, 148, 203, 20, 11, 200, 45, 144, 133, 72, 225, 84, 36, 176, 20, 11, 200, 81, 98, 86, 48, 17, 212, 36, 112, 20, 11, 200, 76, 176, 76, 44, 17, 212, 36, 112, 20, 9, 198, 4, 229, 9, 45, 96, 82, 20, 0, 8, 197, 73, 81, 197, 72, 144, 20, 12, 201, 72, 81, 213, 48, 17, 5, 81, 34, 64, 20, 8, 197, 48, 149, 1, 56, 144, 20, 8, 197, 57, 80, 78, 12, 80, 20, 12, 201, 36, 228, 212, 73, 82, 212, 61, 32, 84, 20, 0, 11, 136, 3, 9, 19, 5, 12, 195, 184, 18, 20, 9, 198, 80, 145, 199, 21, 34, 64, 20, 9, 198, 72, 83, 147, 21, 34, 64, 20, 9, 198, 64, 18, 203, 21, 34, 64, 20, 9, 198, 40, 20, 203, 21, 34, 64, 20, 9, 198, 24, 148, 203, 21, 34, 64, 20, 9, 198, 64, 20, 148, 37, 50, 192, 20, 18, 70, 60, 64, 76, 37, 50, 192, 39, 70, 35, 55, 6, 37, 87, 49, 0, 20, 9, 198, 4, 96, 84, 37, 50, 192, 20, 0, 12, 137, 9, 14, 7, 5, 14, 9, 195, 184, 18, 20, 10, 199, 65, 83, 19, 5, 66, 79, 56, 20, 12, 137, 1, 4, 8, 195, 166, 19, 9, 15, 14, 20, 10, 199, 81, 32, 78, 76, 149, 5, 72, 20, 10, 199, 20, 97, 133, 45, 69, 69, 72, 20, 10, 199, 45, 84, 141, 4, 113, 82, 36, 20, 10, 199, 56, 20, 15, 48, 149, 1, 56, 20, 10, 199, 8, 148, 135, 37, 69, 9, 56, 20, 0, 12, 137, 9, 14, 7, 5, 14, 9, 195, 184, 19, 20, 9, 134, 7, 5, 8, 195, 184, 18, 20, 11, 200, 72, 81, 213, 48, 84, 137, 56, 112, 20, 11, 200, 21, 53, 9, 52, 84, 137, 56, 112, 20, 11, 200, 9, 83, 148, 52, 17, 197, 72, 144, 20, 11, 200, 76, 19, 132, 77, 147, 140, 36, 112, 20, 11, 200, 4, 225, 1, 49, 84, 201, 76, 176, 20, 11, 200, 65, 35, 211, 12, 83, 137, 84, 208, 20, 9, 198, 16, 243, 73, 12, 147, 0, 20, 7, 196, 16, 80, 137, 48, 20, 9, 198, 48, 21, 5, 72, 19, 0, 20, 0, 10, 135, 12, 195, 166, 19, 9, 15, 14, 20, 9, 198, 49, 85, 135, 37, 34, 71, 20, 8, 197, 8, 83, 154, 60, 192, 20, 12, 201, 88, 149, 1, 48, 148, 212, 37, 50, 192, 20, 12, 201, 84, 226, 79, 56, 148, 212, 37, 50, 192, 20, 12, 201, 80, 245, 5, 52, 148, 212, 37, 50, 192, 20, 12, 201, 76, 227, 194, 8, 148, 212, 37, 50, 192, 20, 12, 201, 76, 21, 1, 56, 148, 212, 37, 50, 192, 20, 12, 201, 72, 246, 65, 48, 148, 212, 37, 50, 192, 20, 12, 201, 72, 145, 207, 72, 148, 212, 37, 50, 192, 20, 12, 201, 65, 54, 75, 60, 65, 76, 37, 50, 192, 20, 12, 201, 64, 244, 21, 48, 148, 212, 37, 50, 192, 20, 12, 201, 64, 193, 79, 56, 20, 212, 37, 50, 192, 20, 12, 201, 64, 19, 148, 20, 148, 212, 37, 50, 192, 20, 12, 201, 61, 5, 9, 52, 148, 212, 37, 50, 192, 20, 12, 201, 56, 146, 9, 48, 148, 212, 37, 50, 192, 20, 12, 201, 52, 244, 135, 4, 224, 84, 37, 50, 192, 20, 12, 201, 52, 82, 193, 56, 148, 212, 37, 50, 192, 20, 12, 201, 48, 246, 65, 48, 148, 212, 37, 50, 192, 20, 12, 201, 48, 241, 193, 72, 149, 13, 37, 50, 192, 20, 12, 201, 37, 51, 1, 52, 148, 212, 37, 50, 192, 20, 12, 201, 36, 65, 65, 48, 148, 212, 37, 50, 192, 20, 12, 201, 33, 83, 65, 56, 148, 212, 37, 50, 192, 20, 12, 201, 32, 147, 132, 84, 148, 212, 37, 50, 192, 20, 12, 201, 32, 81, 15, 56, 148, 212, 37, 50, 192, 20, 12, 201, 28, 21, 76, 48, 148, 212, 37, 50, 192, 20, 12, 201, 24, 83, 73, 56, 148, 212, 37, 50, 192, 20, 12, 201, 24, 21, 1, 48, 148, 212, 37, 50, 192, 20, 12, 201, 21, 52, 193, 100, 148, 212, 37, 50, 192, 20, 12, 201, 21, 50, 193, 64, 148, 212, 37, 50, 192, 20, 12, 201, 20, 212, 9, 72, 148, 212, 37, 50, 192, 20, 12, 201, 16, 148, 137, 28, 148, 212, 37, 50, 192, 20, 12, 201, 16, 144, 71, 56, 244, 212, 37, 50, 192, 20, 12, 201, 16, 83, 9, 72, 148, 212, 37, 50, 192, 20, 12, 201, 4, 224, 82, 44, 148, 212, 37, 50, 192, 20, 12, 201, 4, 197, 18, 84, 148, 212, 37, 50, 192, 20, 12, 201, 4, 194, 217, 52, 148, 212, 37, 50, 192, 20, 12, 201, 4, 181, 9, 88, 148, 212, 37, 50, 192, 20, 8, 197, 24, 147, 129, 57, 48, 20, 0, 19, 67, 80, 145, 19, 47, 37, 87, 15, 50, 6, 112, 49, 0, 81, 110, 111, 107, 32, 14, 139, 20, 5, 14, 4, 5, 14, 20, 9, 195, 184, 19, 20, 11, 136, 4, 15, 13, 16, 20, 195, 184, 18, 20, 9, 198, 72, 84, 207, 49, 85, 0, 20, 13, 202, 41, 84, 212, 36, 98, 75, 5, 66, 79, 56, 20, 13, 202, 24, 19, 19, 36, 98, 75, 5, 66, 79, 56, 20, 9, 198, 4, 227, 149, 37, 65, 84, 20, 9, 198, 24, 244, 148, 36, 227, 128, 20, 9, 198, 8, 192, 83, 21, 33, 84, 20, 0, 11, 136, 14, 15, 18, 13, 12, 195, 184, 19, 20, 12, 137, 3, 8, 9, 11, 1, 14, 195, 184, 18, 20, 12, 137, 1, 18, 18, 1, 14, 7, 195, 184, 18, 20, 10, 199, 44, 21, 1, 48, 84, 19, 36, 20, 10, 199, 9, 35, 205, 44, 19, 9, 20, 20, 0, 12, 137, 3, 8, 9, 11, 1, 14, 195, 184, 19, 20, 7, 196, 36, 130, 133, 48, 20, 9, 198, 72, 16, 129, 81, 65, 82, 20, 9, 198, 64, 84, 134, 61, 33, 82, 20, 9, 198, 60, 36, 197, 73, 97, 82, 20, 9, 198, 57, 83, 77, 21, 33, 82, 20, 9, 198, 44, 243, 77, 85, 65, 82, 20, 9, 198, 24, 16, 197, 81, 65, 82, 20, 9, 198, 16, 82, 25, 17, 33, 82, 20, 9, 198, 8, 19, 12, 61, 65, 82, 20, 9, 198, 5, 49, 129, 49, 65, 82, 20, 9, 198, 4, 67, 73, 81, 65, 82, 20, 15, 204, 80, 245, 1, 48, 149, 1, 72, 148, 212, 37, 50, 192, 20, 15, 204, 77, 80, 138, 20, 181, 9, 88, 148, 212, 37, 50, 192, 20, 15, 204, 77, 2, 82, 37, 69, 65, 48, 148, 212, 37, 50, 192, 20, 15, 204, 52, 84, 139, 4, 229, 9, 48, 148, 212, 37, 50, 192, 20, 15, 204, 37, 51, 204, 5, 66, 79, 56, 148, 212, 37, 50, 192, 20, 15, 204, 16, 80, 197, 57, 68, 129, 48, 148, 212, 37, 50, 192, 20, 15, 204, 5, 96, 78, 80, 112, 82, 16, 148, 212, 37, 50, 192, 20, 11, 200, 44, 243, 15, 24, 243, 137, 84, 208, 20, 11, 200, 44, 243, 12, 60, 181, 137, 84, 208, 20, 9, 198, 28, 198, 67, 21, 34, 78, 20, 0, 14, 69, 76, 128, 77, 65, 80, 89, 57, 35, 63, 69, 39, 0, 12, 201, 80, 16, 133, 48, 192, 82, 37, 50, 192, 20, 12, 201, 64, 243, 25, 80, 82, 206, 37, 50, 192, 20, 12, 201, 48, 81, 197, 56, 64, 82, 37, 50, 192, 20, 12, 201, 45, 81, 134, 21, 37, 6, 37, 50, 192, 20, 12, 201, 44, 19, 5, 56, 64, 82, 37, 50, 192, 20, 12, 201, 41, 81, 207, 76, 192, 86, 37, 50, 192, 20, 12, 201, 16, 81, 140, 5, 67, 210, 37, 50, 192, 20, 12, 201, 36, 229, 5, 72, 84, 211, 21, 33, 84, 20, 12, 201, 24, 147, 9, 64, 83, 147, 21, 33, 84, 20, 6, 195, 85, 96, 78, 21, 0, 5, 194, 8, 128, 17, 9, 198, 61, 1, 82, 37, 53, 0, 20, 9, 198, 37, 32, 78, 37, 53, 0, 20, 17, 142, 16, 18, 195, 166, 16, 15, 19, 9, 20, 9, 15, 14, 5, 12, 20, 9, 198, 44, 21, 5, 17, 32, 76, 20, 13, 4, 95, 20, 21, 18, 47, 6, 106, 12, 50, 70, 0, 0, 10, 199, 88, 82, 212, 61, 34, 69, 48, 20, 12, 201, 45, 35, 208, 77, 98, 83, 37, 65, 82, 20, 12, 201, 36, 229, 5, 73, 5, 78, 45, 65, 82, 20, 18, 207, 36, 229, 5, 72, 224, 84, 36, 243, 129, 48, 148, 212, 37, 50, 192, 20, 10, 199, 44, 243, 15, 24, 243, 137, 20, 20, 10, 199, 44, 243, 12, 60, 181, 137, 20, 20, 0, 14, 68, 5, 33, 207, 56, 6, 35, 34, 79, 112, 50, 0, 20, 13, 138, 16, 18, 195, 166, 19, 5, 18, 22, 5, 18, 20, 9, 198, 65, 35, 205, 61, 97, 82, 20, 9, 198, 21, 128, 197, 73, 1, 82, 20, 9, 198, 20, 180, 197, 45, 97, 82, 20, 9, 198, 12, 83, 147, 85, 33, 82, 20, 9, 198, 4, 48, 197, 65, 65, 82, 20, 11, 200, 44, 243, 147, 20, 181, 133, 57, 48, 20, 7, 196, 8, 242, 129, 56, 21, 0, 12, 201, 5, 37, 9, 48, 193, 82, 37, 53, 0, 20, 12, 201, 44, 243, 80, 48, 82, 211, 37, 65, 84, 20, 8, 197, 33, 145, 18, 36, 64, 20, 8, 197, 64, 244, 212, 36, 192, 20, 8, 67, 64, 18, 82, 21, 0, 10, 0, 13, 202, 77, 80, 138, 20, 181, 9, 88, 149, 5, 80, 20, 13, 202, 64, 84, 141, 37, 52, 201, 88, 149, 5, 80, 20, 13, 202, 32, 85, 5, 72, 241, 197, 56, 149, 5, 80, 20, 13, 202, 5, 69, 18, 4, 181, 9, 88, 149, 5, 80, 20, 15, 140, 16, 18, 195, 166, 4, 9, 19, 16, 15, 14, 5, 18, 20, 9, 198, 52, 244, 203, 61, 98, 84, 20, 9, 198, 36, 228, 212, 4, 228, 192, 20, 9, 198, 20, 193, 71, 4, 229, 0, 20, 17, 70, 16, 19, 147, 4, 229, 0, 70, 35, 50, 87, 6, 110, 50, 0, 20, 0, 10, 199, 65, 35, 203, 80, 243, 15, 28, 20, 10, 199, 16, 82, 210, 21, 65, 82, 20, 20, 10, 199, 4, 225, 201, 88, 83, 9, 28, 20, 6, 195, 60, 35, 204, 20, 9, 198, 72, 83, 69, 16, 149, 77, 20, 9, 198, 4, 181, 129, 72, 149, 77, 20, 10, 199, 16, 83, 79, 45, 32, 84, 36, 20, 10, 199, 80, 20, 148, 72, 22, 137, 56, 20, 12, 4, 95, 49, 49, 15, 107, 55, 81, 70, 106, 0, 0, 7, 196, 88, 83, 9, 56, 20, 14, 139, 16, 18, 195, 166, 6, 5, 18, 5, 14, 3, 5, 20, 0, 11, 67, 20, 113, 78, 35, 12, 57, 13, 50, 0, 12, 201, 60, 36, 212, 37, 0, 84, 36, 243, 128, 20, 12, 201, 36, 225, 9, 24, 97, 82, 20, 228, 192, 20, 0, 13, 202, 72, 85, 143, 49, 85, 9, 60, 225, 82, 20, 20, 13, 202, 36, 228, 212, 73, 83, 69, 57, 65, 82, 20, 20, 13, 202, 28, 83, 142, 20, 212, 203, 84, 83, 9, 28, 20, 12, 201, 72, 84, 208, 60, 228, 207, 72, 149, 77, 20, 9, 198, 76, 83, 148, 20, 228, 192, 20, 8, 66, 21, 32, 107, 34, 0, 72, 0, 10, 199, 76, 145, 206, 4, 193, 82, 20, 20, 10, 199, 72, 81, 143, 72, 209, 82, 20, 20, 10, 199, 44, 243, 134, 37, 50, 197, 72, 20, 10, 199, 20, 180, 212, 72, 18, 5, 72, 20, 10, 199, 24, 244, 147, 100, 227, 9, 28, 20, 9, 198, 4, 209, 137, 8, 149, 77, 20, 10, 199, 12, 19, 66, 60, 66, 129, 56, 20, 10, 199, 4, 36, 212, 36, 225, 78, 80, 20, 6, 195, 72, 80, 76, 20, 10, 199, 16, 147, 5, 81, 64, 78, 80, 20, 0, 9, 198, 76, 144, 137, 72, 145, 78, 20, 9, 198, 28, 83, 210, 28, 145, 78, 20, 11, 200, 25, 32, 78, 12, 148, 203, 4, 224, 20, 0, 10, 135, 22, 21, 12, 7, 195, 166, 18, 20, 8, 197, 21, 2, 84, 21, 64, 20, 8, 197, 64, 240, 200, 21, 32, 20, 15, 204, 20, 180, 208, 21, 34, 77, 20, 229, 1, 72, 149, 77, 20, 8, 197, 29, 32, 78, 37, 64, 20, 8, 197, 28, 19, 66, 37, 64, 20, 8, 197, 20, 210, 82, 5, 64, 20, 8, 197, 8, 20, 130, 5, 32, 20, 14, 69, 5, 81, 213, 77, 64, 111, 79, 111, 87, 70, 0, 41, 0, 13, 202, 16, 81, 137, 9, 34, 76, 48, 21, 15, 72, 20, 9, 198, 4, 50, 68, 61, 49, 64, 20, 9, 198, 24, 244, 141, 21, 33, 64, 20, 9, 198, 104, 20, 137, 76, 209, 64, 20, 9, 198, 88, 84, 137, 76, 209, 64, 20, 9, 198, 76, 130, 73, 76, 209, 64, 20, 13, 138, 11, 22, 195, 166, 18, 21, 12, 1, 14, 20, 20, 0, 10, 199, 80, 18, 212, 21, 34, 78, 28, 20, 10, 199, 77, 3, 204, 21, 34, 78, 28, 20, 10, 199, 76, 243, 132, 21, 34, 78, 28, 20, 10, 199, 52, 243, 148, 21, 34, 78, 28, 20, 10, 199, 8, 20, 132, 21, 34, 78, 28, 20, 10, 199, 65, 34, 78, 76, 84, 211, 20, 20, 12, 201, 76, 176, 78, 16, 147, 129, 88, 145, 78, 20, 10, 199, 4, 36, 212, 36, 225, 78, 76, 20, 0, 11, 200, 36, 212, 18, 36, 208, 84, 85, 32, 20, 11, 200, 77, 1, 67, 36, 19, 9, 77, 64, 20, 11, 200, 56, 85, 84, 72, 19, 9, 77, 64, 20, 11, 200, 56, 21, 21, 72, 19, 9, 77, 64, 20, 11, 200, 44, 243, 139, 72, 85, 9, 77, 64, 20, 11, 200, 4, 36, 207, 49, 85, 9, 77, 64, 20, 7, 196, 28, 83, 143, 52, 20, 11, 200, 52, 241, 5, 72, 226, 84, 21, 64, 20, 11, 200, 48, 147, 133, 5, 34, 84, 21, 64, 20, 11, 200, 44, 243, 77, 84, 226, 84, 21, 64, 20, 11, 200, 24, 84, 212, 37, 98, 84, 21, 64, 20, 11, 200, 36, 226, 207, 52, 211, 196, 21, 32, 20, 9, 198, 8, 19, 19, 4, 210, 78, 20, 9, 198, 88, 83, 133, 104, 144, 78, 20, 9, 198, 60, 65, 78, 76, 80, 78, 20, 11, 200, 81, 34, 85, 53, 98, 82, 5, 64, 20, 9, 198, 44, 195, 196, 72, 144, 78, 21, 13, 72, 76, 85, 20, 48, 83, 69, 57, 64, 21, 0, 10, 0, 8, 197, 80, 242, 76, 21, 64, 20, 8, 197, 60, 209, 76, 21, 64, 20, 8, 197, 36, 99, 204, 21, 64, 20, 8, 197, 64, 20, 9, 77, 64, 20, 8, 197, 8, 147, 9, 77, 64, 20, 8, 197, 80, 244, 148, 21, 32, 20, 8, 197, 60, 181, 76, 21, 32, 20, 8, 197, 44, 243, 148, 21, 32, 20, 8, 197, 44, 20, 148, 21, 32, 20, 8, 197, 53, 84, 214, 37, 64, 20, 12, 201, 76, 177, 80, 80, 144, 201, 76, 209, 64, 20, 12, 201, 52, 84, 211, 36, 19, 137, 76, 209, 64, 20, 12, 201, 4, 229, 1, 28, 243, 137, 76, 209, 64, 20, 8, 197, 45, 32, 86, 5, 64, 20, 8, 197, 17, 32, 86, 5, 64, 20, 6, 195, 48, 144, 78, 21, 0, 17, 66, 16, 80, 70, 6, 37, 15, 70, 36, 34, 0, 81, 100, 101, 114, 32, 17, 66, 16, 80, 70, 6, 37, 15, 105, 36, 34, 0, 81, 104, 101, 114, 32, 18, 66, 16, 80, 70, 37, 15, 87, 47, 6, 36, 0, 81, 115, 116, 101, 103, 32, 13, 202, 25, 33, 75, 88, 83, 148, 21, 34, 78, 28, 20, 13, 202, 25, 32, 71, 52, 83, 148, 21, 34, 78, 28, 20, 13, 202, 4, 178, 210, 20, 66, 84, 21, 34, 78, 28, 20, 18, 143, 16, 1, 12, 195, 166, 19, 20, 9, 14, 5, 14, 19, 9, 19, 11, 20, 9, 198, 44, 243, 69, 16, 145, 64, 20, 9, 198, 28, 84, 129, 56, 145, 64, 20, 9, 198, 76, 147, 9, 12, 145, 64, 20, 9, 198, 28, 84, 129, 56, 145, 64, 20, 9, 198, 52, 19, 201, 76, 209, 64, 20, 9, 198, 45, 80, 137, 76, 209, 64, 20, 9, 198, 24, 20, 153, 56, 112, 76, 20, 9, 198, 52, 243, 148, 4, 113, 64, 20, 5, 194, 16, 80, 72, 0, 14, 203, 72, 84, 212, 72, 146, 212, 37, 98, 84, 21, 64, 20, 14, 203, 72, 17, 9, 60, 18, 212, 37, 98, 84, 21, 64, 20, 15, 140, 16, 195, 166, 4, 5, 18, 1, 19, 20, 9, 19, 11, 20, 12, 201, 77, 68, 133, 65, 67, 205, 100, 50, 78, 20, 10, 199, 44, 243, 15, 77, 67, 205, 36, 20, 10, 199, 80, 243, 5, 72, 19, 131, 20, 20, 6, 195, 32, 144, 84, 20, 6, 195, 4, 112, 84, 20, 0, 21, 68, 44, 244, 212, 20, 49, 39, 87, 70, 13, 15, 63, 107, 84, 0, 81, 109, 101, 100, 32, 19, 68, 88, 147, 12, 20, 82, 37, 55, 106, 15, 87, 112, 0, 81, 115, 195, 165, 32, 11, 200, 4, 116, 137, 45, 83, 20, 85, 32, 20, 11, 200, 72, 82, 77, 64, 244, 148, 21, 32, 20, 11, 200, 61, 35, 129, 52, 83, 148, 21, 32, 20, 11, 200, 44, 243, 134, 72, 243, 148, 21, 32, 20, 11, 200, 36, 229, 5, 73, 3, 204, 21, 32, 20, 11, 200, 36, 225, 11, 88, 20, 148, 21, 32, 20, 11, 200, 72, 84, 208, 60, 225, 5, 57, 64, 20, 11, 200, 44, 243, 147, 20, 181, 133, 57, 64, 20, 11, 200, 16, 83, 9, 56, 181, 133, 57, 64, 20, 11, 200, 37, 36, 133, 48, 85, 129, 57, 64, 20, 0, 12, 201, 88, 146, 193, 72, 145, 82, 36, 225, 192, 20, 12, 201, 81, 83, 142, 20, 193, 82, 36, 225, 192, 20, 12, 201, 80, 16, 149, 37, 49, 82, 36, 225, 192, 20, 12, 201, 77, 148, 212, 20, 209, 82, 36, 225, 192, 20, 12, 201, 77, 83, 6, 60, 225, 82, 36, 225, 192, 20, 12, 201, 77, 66, 77, 84, 193, 82, 36, 225, 192, 20, 12, 201, 76, 81, 210, 20, 113, 82, 36, 225, 192, 20, 12, 201, 72, 85, 21, 72, 225, 82, 36, 225, 192, 20, 12, 201, 64, 245, 5, 57, 49, 82, 36, 225, 192, 20, 12, 201, 64, 241, 19, 60, 193, 82, 36, 225, 192, 20, 12, 201, 56, 81, 204, 36, 113, 82, 36, 225, 192, 20, 12, 201, 48, 144, 197, 57, 49, 82, 36, 225, 192, 20, 12, 201, 45, 84, 148, 37, 49, 82, 36, 225, 192, 20, 12, 201, 45, 33, 78, 20, 193, 82, 36, 225, 192, 20, 12, 201, 44, 244, 146, 84, 113, 82, 36, 225, 192, 20, 12, 201, 41, 81, 1, 37, 49, 82, 36, 225, 192, 20, 12, 201, 36, 226, 204, 84, 65, 82, 36, 225, 192, 20, 12, 201, 36, 226, 193, 77, 49, 82, 36, 225, 192, 20, 12, 201, 36, 225, 5, 45, 49, 82, 36, 225, 192, 20, 12, 201, 25, 84, 201, 60, 225, 82, 36, 225, 192, 20, 12, 201, 24, 197, 75, 81, 81, 82, 36, 225, 192, 20, 12, 201, 8, 19, 132, 4, 113, 82, 36, 225, 192, 20, 12, 201, 5, 67, 205, 37, 49, 82, 36, 225, 192, 20, 12, 201, 5, 34, 193, 37, 49, 82, 36, 225, 192, 20, 12, 201, 4, 227, 143, 56, 49, 82, 36, 225, 192, 20, 12, 201, 4, 178, 207, 72, 65, 82, 36, 225, 192, 20, 8, 197, 20, 212, 9, 72, 144, 20, 11, 136, 195, 184, 11, 21, 13, 5, 14, 9, 20, 12, 201, 44, 21, 15, 48, 144, 201, 76, 209, 64, 20, 12, 201, 76, 145, 206, 36, 98, 75, 4, 229, 0, 20, 0, 14, 139, 195, 166, 18, 5, 6, 18, 25, 7, 20, 9, 7, 20, 9, 198, 65, 54, 75, 37, 50, 192, 20, 9, 198, 4, 84, 143, 48, 149, 0, 20, 13, 202, 20, 180, 212, 72, 21, 129, 28, 19, 131, 20, 20, 9, 198, 16, 21, 1, 52, 21, 0, 20, 0, 18, 67, 16, 85, 0, 70, 6, 36, 15, 70, 36, 34, 0, 81, 100, 101, 114, 32, 18, 67, 16, 85, 0, 70, 6, 36, 15, 105, 36, 34, 0, 81, 104, 101, 114, 32, 25, 67, 16, 85, 0, 70, 36, 15, 49, 82, 110, 6, 47, 36, 34, 0, 81, 107, 118, 97, 114, 116, 101, 114, 32, 10, 199, 20, 180, 197, 45, 85, 15, 72, 20, 10, 199, 20, 229, 15, 52, 243, 15, 28, 20, 9, 198, 52, 84, 139, 60, 227, 205, 20, 15, 140, 15, 13, 19, 20, 195, 166, 14, 4, 5, 12, 9, 7, 20, 9, 198, 88, 149, 129, 72, 149, 77, 20, 9, 67, 16, 85, 0, 70, 36, 0, 72, 0, 10, 135, 12, 195, 184, 10, 2, 15, 13, 20, 15, 204, 72, 21, 9, 60, 224, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 65, 35, 204, 21, 64, 82, 37, 49, 82, 36, 225, 192, 20, 15, 204, 65, 34, 77, 37, 66, 86, 37, 49, 82, 36, 225, 192, 20, 15, 204, 64, 84, 147, 60, 224, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 64, 20, 129, 48, 193, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 60, 34, 133, 45, 66, 86, 37, 49, 82, 36, 225, 192, 20, 15, 204, 56, 21, 9, 60, 224, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 52, 20, 135, 36, 224, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 45, 34, 77, 36, 224, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 44, 243, 77, 84, 224, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 44, 20, 129, 45, 65, 82, 37, 49, 82, 36, 225, 192, 20, 15, 204, 44, 19, 142, 36, 32, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 36, 229, 5, 72, 224, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 24, 19, 73, 48, 144, 82, 37, 49, 82, 36, 225, 192, 20, 15, 204, 20, 193, 75, 81, 34, 70, 36, 49, 82, 36, 225, 192, 20, 15, 204, 20, 97, 133, 45, 66, 86, 37, 49, 82, 36, 225, 192, 20, 15, 204, 16, 149, 133, 73, 50, 70, 36, 49, 82, 36, 225, 192, 20, 15, 204, 16, 145, 134, 21, 33, 78, 80, 145, 82, 36, 225, 192, 20, 15, 204, 12, 243, 80, 85, 65, 82, 37, 49, 82, 36, 225, 192, 20, 15, 204, 4, 209, 82, 36, 176, 78, 37, 49, 82, 36, 225, 192, 20, 7, 196, 72, 17, 5, 72, 20, 11, 200, 45, 35, 206, 60, 209, 84, 72, 144, 20, 11, 200, 5, 81, 9, 60, 209, 84, 72, 144, 20, 11, 200, 36, 195, 21, 76, 244, 137, 76, 176, 20, 11, 200, 21, 128, 197, 57, 68, 137, 76, 176, 20, 11, 200, 4, 195, 21, 76, 244, 137, 76, 176, 20, 11, 200, 56, 82, 210, 60, 208, 78, 80, 144, 20, 7, 196, 37, 35, 206, 36, 20, 11, 200, 8, 144, 140, 36, 243, 65, 56, 144, 20, 15, 204, 44, 243, 147, 81, 37, 75, 80, 149, 137, 76, 209, 64, 20, 9, 198, 52, 19, 132, 72, 147, 0, 20, 14, 4, 95, 4, 16, 20, 10, 49, 4, 112, 63, 108, 12, 0, 0, 10, 135, 16, 1, 18, 12, 195, 184, 18, 20, 12, 201, 52, 146, 210, 60, 225, 83, 37, 50, 192, 20, 8, 197, 64, 245, 1, 28, 80, 20, 0, 29, 4, 7, 195, 184, 18, 79, 4, 116, 34, 15, 87, 35, 57, 15, 47, 6, 36, 55, 0, 82, 115, 105, 103, 32, 116, 105, 108, 32, 17, 66, 17, 80, 70, 40, 15, 105, 108, 12, 0, 81, 104, 97, 118, 101, 32, 10, 135, 6, 9, 2, 18, 195, 184, 19, 20, 11, 136, 19, 15, 9, 7, 14, 195, 184, 18, 20, 9, 198, 44, 20, 129, 52, 35, 204, 20, 9, 198, 76, 19, 65, 72, 149, 0, 20, 9, 198, 32, 16, 137, 80, 21, 0, 20, 8, 66, 17, 80, 70, 40, 0, 72, 0, 11, 136, 19, 11, 1, 2, 18, 195, 184, 19, 20, 11, 136, 7, 18, 1, 3, 9, 195, 184, 19, 20, 10, 199, 36, 227, 143, 88, 21, 15, 72, 20, 18, 207, 65, 35, 198, 21, 52, 201, 60, 224, 76, 37, 49, 82, 36, 225, 192, 20, 10, 199, 72, 84, 212, 37, 69, 69, 72, 20, 10, 199, 72, 81, 140, 20, 181, 5, 72, 20, 10, 199, 65, 35, 199, 72, 81, 5, 72, 20, 10, 199, 44, 243, 147, 80, 21, 5, 72, 20, 15, 140, 6, 15, 18, 20, 18, 195, 166, 4, 5, 12, 9, 7, 20, 11, 136, 19, 6, 195, 166, 18, 9, 19, 11, 20, 10, 199, 4, 68, 133, 56, 19, 9, 56, 20, 6, 195, 4, 114, 76, 20, 10, 199, 8, 19, 12, 37, 53, 9, 44, 20, 6, 195, 32, 19, 64, 72, 0, 13, 138, 14, 1, 22, 9, 7, 1, 20, 195, 184, 18, 20, 7, 196, 52, 147, 149, 80, 20, 11, 200, 8, 241, 211, 80, 21, 133, 72, 80, 20, 11, 200, 77, 147, 77, 21, 68, 137, 76, 176, 20, 11, 200, 8, 147, 205, 21, 68, 137, 76, 176, 20, 11, 200, 44, 243, 147, 61, 37, 9, 84, 208, 20, 11, 200, 56, 85, 82, 5, 53, 5, 56, 144, 20, 9, 198, 32, 243, 79, 24, 147, 0, 20, 0, 9, 134, 19, 5, 18, 195, 184, 19, 20, 10, 135, 11, 15, 18, 19, 195, 184, 18, 20, 10, 135, 11, 12, 1, 11, 195, 184, 18, 20, 8, 197, 32, 83, 132, 21, 48, 76, 0, 9, 198, 4, 36, 207, 49, 85, 0, 20, 9, 198, 24, 195, 210, 37, 53, 0, 20, 9, 198, 76, 22, 15, 24, 243, 128, 20, 9, 198, 65, 35, 199, 72, 19, 64, 20, 9, 198, 56, 147, 194, 37, 83, 64, 20, 9, 198, 52, 20, 139, 21, 33, 84, 20, 0, 22, 9, 6, 195, 184, 12, 10, 5, 20, 15, 14, 81, 116, 55, 57, 36, 47, 6, 112, 50, 0, 20, 10, 199, 24, 147, 129, 57, 50, 69, 48, 20, 14, 203, 80, 84, 212, 4, 209, 78, 80, 20, 137, 76, 176, 20, 14, 203, 64, 20, 140, 4, 209, 78, 80, 20, 137, 76, 176, 20, 10, 199, 8, 83, 133, 24, 144, 201, 20, 20, 10, 199, 21, 81, 133, 52, 148, 205, 20, 20, 10, 199, 64, 84, 212, 36, 193, 78, 76, 20, 10, 199, 36, 212, 12, 4, 229, 1, 80, 20, 12, 201, 44, 21, 1, 77, 68, 143, 24, 19, 0, 20, 6, 195, 20, 112, 76, 20, 12, 4, 95, 49, 48, 15, 47, 37, 13, 50, 106, 0, 0, 7, 196, 76, 19, 21, 80, 20, 9, 198, 60, 36, 212, 73, 81, 82, 20, 9, 198, 36, 228, 213, 49, 65, 82, 20, 9, 198, 36, 228, 212, 73, 81, 82, 20, 9, 198, 36, 225, 143, 72, 209, 82, 20, 9, 198, 36, 225, 12, 21, 97, 82, 20, 9, 198, 5, 32, 137, 81, 33, 82, 20, 12, 137, 11, 9, 13, 195, 166, 18, 9, 19, 11, 20, 11, 200, 44, 83, 143, 80, 17, 137, 84, 208, 20, 7, 196, 36, 229, 73, 80, 20, 9, 198, 12, 20, 132, 36, 112, 78, 21, 0, 9, 198, 52, 85, 18, 60, 195, 199, 20, 12, 201, 16, 243, 79, 72, 112, 78, 37, 53, 0, 20, 12, 201, 5, 69, 18, 36, 37, 84, 36, 243, 128, 20, 17, 142, 19, 20, 18, 1, 20, 15, 19, 6, 195, 166, 18, 9, 19, 11, 20, 8, 197, 64, 245, 5, 57, 48, 20, 0, 21, 66, 4, 192, 35, 55, 15, 49, 6, 35, 57, 70, 35, 0, 81, 113, 97, 101, 100, 97, 32, 14, 139, 7, 1, 14, 7, 18, 195, 166, 14, 195, 184, 19, 20, 9, 198, 28, 19, 66, 37, 53, 0, 20, 9, 198, 52, 83, 1, 56, 243, 64, 20, 12, 137, 22, 18, 195, 184, 22, 12, 5, 18, 9, 20, 14, 139, 13, 9, 12, 9, 20, 195, 166, 18, 9, 19, 11, 20, 9, 198, 24, 84, 141, 20, 229, 0, 20, 9, 198, 52, 19, 137, 21, 33, 84, 20, 9, 198, 52, 20, 139, 4, 229, 0, 20, 0, 10, 199, 88, 149, 1, 48, 149, 5, 80, 20, 10, 199, 80, 245, 1, 48, 149, 5, 80, 20, 10, 199, 76, 243, 9, 16, 149, 5, 80, 20, 10, 199, 76, 83, 137, 48, 149, 5, 80, 20, 10, 199, 72, 149, 129, 48, 149, 5, 80, 20, 10, 199, 72, 145, 201, 16, 149, 5, 80, 20, 10, 199, 72, 20, 9, 16, 149, 5, 80, 20, 10, 199, 56, 240, 137, 48, 149, 5, 80, 20, 10, 199, 56, 21, 1, 48, 149, 5, 80, 20, 10, 199, 56, 20, 193, 48, 149, 5, 80, 20, 10, 199, 52, 241, 1, 48, 149, 5, 80, 20, 10, 199, 52, 240, 137, 48, 149, 5, 80, 20, 10, 199, 48, 242, 193, 48, 149, 5, 80, 20, 10, 199, 48, 81, 193, 48, 149, 5, 80, 20, 10, 199, 36, 211, 85, 56, 149, 5, 80, 20, 10, 199, 36, 65, 65, 48, 149, 5, 80, 20, 10, 199, 24, 145, 5, 48, 149, 5, 80, 20, 10, 199, 24, 21, 1, 48, 149, 5, 80, 20, 10, 199, 24, 16, 201, 48, 149, 5, 80, 20, 10, 199, 16, 80, 137, 48, 149, 5, 80, 20, 10, 199, 76, 82, 212, 61, 34, 69, 48, 20, 10, 199, 21, 52, 197, 57, 66, 69, 48, 20, 10, 199, 8, 18, 212, 21, 34, 69, 48, 20, 12, 201, 80, 82, 206, 60, 195, 199, 37, 49, 82, 20, 12, 201, 44, 243, 80, 72, 243, 73, 81, 65, 82, 20, 13, 138, 19, 11, 18, 195, 166, 4, 4, 5, 18, 9, 20, 15, 140, 1, 20, 13, 15, 19, 6, 195, 166, 18, 9, 19, 11, 20, 10, 199, 44, 243, 135, 20, 226, 65, 48, 20, 0, 9, 198, 72, 80, 197, 65, 69, 82, 20, 7, 196, 16, 243, 143, 72, 20, 9, 198, 44, 242, 203, 21, 33, 82, 20, 9, 198, 24, 147, 135, 21, 33, 82, 20, 9, 198, 16, 81, 140, 61, 33, 82, 20, 14, 139, 15, 16, 20, 18, 195, 166, 11, 11, 5, 18, 9, 20, 16, 141, 11, 22, 195, 166, 18, 21, 12, 1, 14, 20, 9, 19, 11, 20, 16, 141, 1, 13, 1, 20, 195, 184, 18, 9, 19, 20, 9, 19, 11, 20, 7, 196, 45, 33, 84, 36, 20, 7, 196, 44, 19, 137, 56, 20, 11, 136, 13, 195, 166, 3, 5, 14, 1, 20, 20, 9, 198, 56, 20, 139, 60, 208, 78, 21, 9, 3, 95, 35, 57, 47, 35, 69, 0, 12, 4, 95, 20, 12, 4, 47, 37, 55, 70, 13, 0, 0, 12, 201, 61, 5, 15, 52, 85, 18, 37, 53, 0, 20, 12, 201, 32, 148, 212, 61, 34, 67, 37, 65, 84, 20, 12, 201, 20, 193, 75, 81, 34, 67, 37, 65, 84, 20, 12, 201, 5, 85, 5, 57, 66, 67, 37, 65, 84, 20, 11, 136, 20, 195, 184, 18, 18, 5, 18, 9, 20, 8, 197, 52, 243, 135, 60, 192, 20, 8, 197, 104, 80, 200, 36, 224, 20, 0, 13, 202, 77, 2, 82, 37, 69, 65, 48, 149, 5, 80, 20, 13, 202, 65, 49, 85, 16, 243, 153, 52, 149, 5, 80, 20, 13, 202, 44, 243, 135, 20, 226, 65, 48, 149, 5, 80, 20, 13, 202, 36, 195, 5, 28, 149, 9, 52, 149, 5, 80, 20, 13, 202, 24, 193, 75, 76, 144, 137, 48, 149, 5, 80, 20, 9, 198, 72, 81, 213, 48, 84, 128, 20, 9, 198, 21, 53, 9, 52, 84, 128, 20, 12, 137, 19, 11, 195, 166, 12, 13, 5, 18, 9, 20, 15, 140, 195, 165, 12, 2, 15, 18, 7, 5, 14, 19, 5, 18, 20, 15, 140, 6, 195, 165, 2, 15, 18, 7, 5, 14, 19, 5, 18, 20, 9, 198, 76, 82, 214, 20, 228, 192, 20, 9, 198, 72, 84, 212, 4, 229, 0, 20, 0, 12, 201, 81, 32, 78, 76, 98, 71, 85, 33, 82, 20, 10, 199, 72, 21, 9, 60, 225, 82, 20, 20, 10, 199, 64, 19, 12, 21, 65, 82, 20, 20, 10, 199, 45, 83, 13, 36, 225, 82, 20, 20, 10, 199, 24, 244, 198, 5, 65, 82, 20, 20, 10, 199, 4, 181, 9, 60, 225, 82, 20, 20, 9, 198, 48, 147, 143, 48, 85, 77, 20, 9, 198, 76, 147, 9, 12, 149, 77, 20, 10, 199, 32, 82, 212, 60, 116, 129, 24, 20, 0, 23, 72, 4, 180, 143, 77, 66, 75, 60, 224, 35, 49, 34, 112, 87, 70, 37, 49, 6, 112, 50, 0, 20, 9, 198, 64, 21, 137, 48, 195, 206, 20, 9, 198, 52, 81, 1, 48, 163, 206, 20, 11, 200, 20, 180, 208, 4, 228, 201, 60, 224, 20, 11, 200, 16, 84, 18, 21, 52, 201, 60, 224, 20, 12, 201, 88, 84, 147, 36, 243, 133, 72, 147, 135, 20, 11, 200, 76, 145, 82, 72, 19, 5, 60, 224, 20, 0, 8, 197, 88, 83, 148, 36, 192, 20, 8, 197, 28, 83, 148, 36, 192, 20, 12, 201, 88, 144, 143, 72, 113, 78, 76, 84, 128, 20, 8, 197, 76, 195, 214, 20, 224, 20, 12, 201, 77, 80, 147, 45, 34, 66, 20, 229, 0, 20, 12, 201, 44, 243, 148, 72, 243, 12, 4, 229, 0, 20, 8, 197, 64, 20, 211, 4, 32, 20, 0, 23, 66, 21, 64, 36, 70, 15, 81, 6, 112, 34, 87, 114, 50, 0, 81, 102, 111, 114, 115, 121, 110, 32, 17, 66, 21, 64, 36, 70, 15, 105, 6, 110, 40, 0, 81, 104, 97, 118, 32, 17, 66, 21, 64, 36, 70, 15, 6, 81, 39, 34, 0, 81, 102, 111, 114, 32, 16, 66, 21, 64, 36, 70, 15, 105, 110, 40, 0, 81, 104, 97, 118, 32, 24, 66, 21, 64, 36, 47, 15, 49, 82, 110, 6, 47, 36, 34, 0, 81, 107, 118, 97, 114, 116, 101, 114, 32, 13, 202, 76, 83, 22, 24, 147, 129, 57, 50, 69, 72, 20, 9, 198, 60, 213, 18, 20, 229, 0, 20, 9, 198, 44, 243, 132, 20, 228, 192, 20, 11, 70, 76, 178, 78, 32, 80, 68, 21, 0, 10, 8, 66, 21, 64, 36, 47, 0, 72, 0, 12, 137, 6, 1, 13, 9, 12, 9, 195, 166, 18, 20, 10, 199, 60, 33, 21, 45, 66, 79, 56, 20, 10, 199, 36, 225, 21, 45, 66, 79, 56, 20, 10, 199, 72, 82, 204, 4, 209, 82, 20, 20, 10, 199, 12, 128, 77, 9, 34, 69, 72, 20, 10, 199, 4, 227, 143, 56, 49, 82, 20, 20, 9, 198, 64, 243, 25, 28, 19, 73, 20, 10, 199, 21, 128, 197, 57, 68, 137, 44, 20, 10, 199, 32, 84, 140, 61, 98, 65, 56, 20, 10, 199, 44, 244, 144, 84, 193, 78, 80, 20, 0, 13, 138, 19, 21, 2, 19, 9, 4, 9, 195, 166, 18, 20, 9, 134, 2, 5, 7, 195, 166, 18, 20, 11, 200, 72, 81, 210, 21, 52, 201, 60, 224, 20, 11, 200, 60, 178, 193, 76, 147, 206, 20, 192, 20, 11, 200, 25, 83, 139, 80, 147, 206, 20, 192, 20, 7, 196, 24, 83, 143, 48, 20, 12, 137, 6, 195, 184, 14, 9, 11, 9, 19, 11, 20, 0, 10, 135, 16, 18, 5, 11, 195, 166, 18, 20, 8, 197, 52, 19, 201, 77, 64, 20, 8, 197, 45, 33, 77, 21, 32, 20, 8, 197, 65, 35, 198, 37, 64, 20, 8, 197, 52, 17, 206, 5, 64, 20, 8, 197, 24, 244, 198, 5, 64, 20, 8, 197, 88, 243, 1, 57, 64, 20, 12, 201, 64, 20, 148, 36, 50, 80, 4, 229, 0, 20, 8, 197, 45, 83, 1, 57, 64, 20, 0, 13, 202, 44, 243, 147, 80, 84, 142, 5, 66, 79, 56, 20, 13, 202, 36, 226, 207, 73, 3, 210, 5, 66, 79, 56, 20, 9, 198, 4, 209, 137, 8, 145, 64, 20, 8, 133, 195, 165, 18, 20, 9, 20, 9, 198, 81, 84, 137, 76, 209, 64, 20, 9, 198, 80, 19, 201, 76, 209, 64, 20, 9, 198, 72, 16, 201, 76, 209, 64, 20, 9, 198, 65, 84, 137, 76, 209, 64, 20, 9, 198, 56, 22, 137, 76, 209, 64, 20, 9, 198, 49, 148, 137, 76, 209, 64, 20, 9, 198, 20, 115, 201, 76, 209, 64, 20, 13, 202, 48, 145, 67, 33, 65, 78, 77, 65, 73, 56, 20, 9, 198, 80, 243, 142, 4, 113, 64, 20, 9, 198, 12, 245, 82, 4, 113, 64, 20, 0, 10, 135, 6, 195, 166, 18, 9, 19, 20, 20, 10, 199, 81, 84, 142, 21, 34, 78, 28, 20, 10, 199, 80, 18, 211, 21, 34, 78, 28, 20, 10, 199, 64, 192, 78, 21, 34, 78, 28, 20, 10, 199, 48, 19, 131, 21, 34, 78, 28, 20, 10, 199, 28, 20, 142, 21, 34, 78, 28, 20, 10, 199, 24, 146, 211, 21, 34, 78, 28, 20, 10, 199, 8, 20, 130, 21, 34, 78, 28, 20, 13, 4, 95, 49, 50, 15, 47, 112, 55, 81, 70, 106, 0, 0, 11, 200, 64, 243, 25, 32, 148, 212, 61, 32, 20, 13, 138, 11, 15, 13, 13, 9, 19, 19, 195, 166, 18, 20, 11, 200, 65, 81, 82, 36, 194, 84, 21, 64, 20, 11, 200, 65, 80, 140, 36, 50, 84, 21, 64, 20, 11, 200, 64, 21, 5, 72, 226, 84, 21, 64, 20, 11, 200, 44, 21, 83, 4, 194, 84, 21, 64, 20, 11, 200, 25, 37, 71, 4, 194, 84, 21, 64, 20, 11, 200, 25, 34, 86, 60, 194, 84, 21, 64, 20, 11, 200, 25, 32, 71, 36, 194, 84, 21, 64, 20, 11, 200, 4, 226, 77, 61, 50, 84, 21, 64, 20, 11, 200, 4, 208, 137, 29, 82, 84, 21, 64, 20, 9, 198, 8, 20, 148, 32, 144, 78, 20, 9, 198, 4, 100, 137, 44, 16, 78, 20, 9, 198, 4, 100, 137, 44, 16, 78, 20, 11, 200, 20, 180, 203, 72, 83, 69, 57, 64, 20, 11, 200, 5, 34, 83, 80, 242, 210, 5, 64, 20, 0, 8, 197, 80, 21, 140, 21, 64, 20, 8, 197, 76, 242, 204, 21, 64, 20, 11, 136, 12, 195, 166, 11, 11, 5, 18, 9, 20, 11, 136, 8, 195, 184, 14, 19, 5, 18, 9, 20, 13, 138, 7, 5, 15, 4, 195, 166, 20, 9, 19, 11, 20, 13, 138, 5, 21, 18, 15, 16, 195, 166, 9, 19, 11, 20, 8, 197, 76, 241, 134, 37, 64, 20, 12, 201, 28, 227, 211, 80, 144, 201, 76, 209, 64, 20, 12, 201, 9, 32, 72, 52, 19, 137, 76, 209, 64, 20, 8, 197, 64, 245, 5, 57, 64, 20, 8, 197, 64, 84, 211, 5, 32, 20, 0, 13, 202, 88, 84, 130, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 81, 148, 129, 56, 226, 83, 21, 34, 78, 28, 20, 13, 202, 77, 65, 82, 36, 194, 83, 21, 34, 78, 28, 20, 13, 202, 77, 64, 66, 36, 194, 83, 21, 34, 78, 28, 20, 13, 202, 76, 145, 206, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 52, 85, 1, 48, 194, 83, 21, 34, 78, 28, 20, 13, 202, 52, 20, 203, 36, 226, 83, 21, 34, 78, 28, 20, 13, 202, 32, 20, 141, 60, 226, 83, 21, 34, 78, 28, 20, 13, 202, 28, 84, 141, 4, 226, 83, 21, 34, 78, 28, 20, 13, 202, 28, 19, 22, 4, 226, 83, 21, 34, 78, 28, 20, 13, 202, 16, 149, 137, 76, 147, 206, 21, 34, 78, 28, 20, 13, 202, 8, 19, 11, 4, 226, 83, 21, 34, 78, 28, 20, 13, 202, 4, 32, 78, 16, 243, 142, 21, 34, 78, 28, 20, 12, 201, 81, 34, 71, 60, 227, 205, 21, 68, 137, 20, 14, 139, 16, 20, 15, 12, 5, 13, 195, 166, 9, 19, 11, 20, 9, 198, 24, 19, 73, 48, 145, 64, 20, 9, 198, 20, 225, 9, 88, 145, 64, 20, 9, 198, 88, 149, 129, 72, 145, 64, 20, 9, 198, 72, 83, 69, 16, 145, 64, 20, 9, 198, 4, 181, 129, 72, 145, 64, 20, 9, 198, 45, 147, 137, 76, 209, 64, 20, 9, 198, 60, 97, 137, 12, 144, 76, 20, 9, 198, 4, 195, 21, 88, 144, 76, 20, 17, 70, 8, 243, 132, 4, 113, 64, 69, 6, 112, 50, 70, 37, 73, 0, 20, 9, 198, 8, 19, 132, 4, 113, 64, 20, 11, 70, 8, 243, 132, 4, 113, 64, 21, 0, 10, 0, 14, 203, 44, 243, 147, 81, 37, 75, 80, 149, 137, 77, 64, 20, 14, 203, 64, 20, 129, 16, 242, 211, 4, 194, 84, 21, 64, 20, 15, 140, 8, 5, 13, 9, 19, 6, 195, 166, 18, 9, 19, 11, 20, 10, 199, 44, 243, 134, 49, 81, 78, 76, 20, 10, 199, 4, 208, 149, 48, 19, 131, 20, 20, 0, 7, 196, 76, 243, 143, 72, 20, 11, 200, 97, 147, 15, 24, 243, 137, 77, 64, 20, 11, 200, 88, 84, 147, 36, 243, 137, 77, 64, 20, 11, 200, 44, 195, 203, 44, 83, 137, 77, 64, 20, 16, 141, 11, 1, 13, 195, 166, 12, 5, 15, 14, 20, 9, 19, 11, 20, 9, 198, 32, 21, 193, 36, 144, 78, 20, 7, 196, 61, 51, 65, 56, 21, 7, 196, 8, 242, 129, 72, 20, 0, 12, 137, 6, 12, 195, 184, 10, 20, 9, 19, 20, 20, 16, 205, 84, 66, 210, 101, 53, 1, 48, 194, 83, 21, 34, 78, 28, 20, 12, 201, 73, 80, 146, 36, 49, 82, 36, 225, 192, 20, 16, 205, 36, 225, 21, 77, 68, 137, 4, 194, 83, 21, 34, 78, 28, 20, 12, 201, 24, 84, 142, 37, 49, 82, 36, 225, 192, 20, 16, 205, 16, 149, 137, 76, 147, 206, 4, 194, 83, 21, 34, 78, 28, 20, 11, 136, 19, 20, 195, 184, 2, 5, 18, 9, 20, 13, 138, 15, 16, 12, 195, 184, 19, 5, 12, 9, 7, 20, 13, 138, 7, 5, 12, 195, 169, 1, 7, 20, 9, 7, 20, 17, 142, 9, 14, 4, 15, 5, 21, 18, 15, 16, 195, 166, 9, 19, 11, 20, 12, 201, 72, 84, 208, 60, 228, 207, 72, 145, 64, 20, 12, 201, 48, 19, 65, 72, 50, 201, 76, 209, 64, 20, 12, 201, 12, 128, 85, 88, 147, 137, 76, 209, 64, 20, 12, 201, 44, 20, 129, 52, 35, 204, 4, 113, 64, 20, 10, 69, 72, 83, 65, 44, 80, 21, 0, 10, 0, 9, 198, 48, 85, 1, 72, 114, 64, 20, 14, 139, 9, 14, 4, 12, 195, 184, 19, 5, 12, 9, 7, 20, 9, 198, 4, 225, 18, 60, 145, 0, 20, 13, 202, 64, 20, 148, 20, 227, 199, 20, 225, 83, 20, 20, 13, 202, 25, 33, 68, 21, 34, 75, 76, 128, 86, 56, 20, 8, 198, 4, 35, 210, 36, 114, 64, 0, 10, 199, 24, 147, 129, 57, 50, 69, 72, 20, 10, 199, 24, 147, 15, 76, 241, 133, 72, 20, 10, 199, 61, 33, 7, 100, 65, 82, 36, 20, 10, 199, 45, 83, 147, 80, 193, 82, 36, 20, 10, 199, 44, 242, 197, 81, 65, 82, 36, 20, 10, 199, 44, 194, 77, 65, 33, 82, 36, 20, 10, 199, 41, 84, 137, 77, 65, 82, 36, 20, 13, 138, 7, 5, 14, 4, 195, 184, 2, 5, 18, 9, 20, 10, 199, 16, 21, 1, 52, 21, 9, 44, 20, 10, 199, 72, 81, 197, 57, 50, 65, 56, 20, 10, 199, 24, 195, 210, 20, 229, 9, 56, 20, 10, 199, 44, 243, 132, 20, 211, 129, 8, 20, 0, 11, 200, 17, 32, 77, 5, 69, 82, 28, 144, 20, 11, 200, 76, 147, 85, 48, 84, 137, 56, 112, 20, 15, 204, 64, 84, 147, 60, 226, 70, 36, 49, 82, 36, 225, 192, 20, 15, 204, 52, 20, 203, 84, 194, 78, 37, 49, 82, 36, 225, 192, 20, 16, 141, 12, 5, 20, 15, 16, 12, 195, 184, 19, 5, 12, 9, 7, 20, 9, 198, 64, 20, 129, 8, 243, 0, 20, 11, 200, 77, 81, 1, 56, 84, 201, 76, 176, 20, 11, 200, 52, 147, 137, 77, 65, 82, 36, 80, 20, 15, 204, 20, 180, 208, 21, 34, 77, 20, 229, 1, 72, 145, 64, 20, 7, 196, 81, 82, 193, 56, 21, 9, 198, 64, 19, 1, 80, 19, 0, 20, 0, 8, 197, 8, 84, 204, 60, 112, 20, 15, 69, 8, 83, 9, 104, 80, 69, 36, 55, 37, 12, 87, 0, 66, 17, 142, 20, 9, 12, 19, 20, 18, 195, 166, 11, 11, 5, 12, 9, 7, 20, 13, 138, 20, 9, 12, 6, 195, 166, 12, 4, 9, 7, 20, 12, 201, 44, 243, 77, 37, 69, 5, 72, 85, 0, 20, 0, 5, 194, 21, 80, 17, 18, 70, 8, 80, 200, 4, 209, 76, 69, 36, 89, 35, 63, 6, 36, 12, 60, 0, 9, 198, 80, 16, 140, 60, 145, 0, 20, 9, 198, 64, 243, 25, 4, 210, 68, 20, 18, 70, 61, 34, 71, 4, 210, 64, 39, 34, 36, 79, 6, 35, 63, 37, 0, 20, 9, 198, 77, 80, 140, 36, 208, 84, 20, 0, 14, 203, 4, 195, 5, 28, 244, 137, 76, 84, 137, 56, 112, 20, 12, 201, 52, 147, 137, 77, 65, 82, 36, 83, 0, 20, 10, 199, 4, 99, 65, 72, 50, 5, 72, 20, 19, 144, 19, 1, 13, 13, 5, 14, 20, 18, 195, 166, 11, 11, 5, 12, 9, 7, 20, 15, 140, 14, 195, 184, 4, 20, 195, 184, 18, 6, 20, 9, 7, 20, 14, 203, 72, 81, 204, 20, 209, 78, 80, 20, 137, 76, 176, 20, 10, 199, 52, 19, 5, 72, 147, 132, 20, 20, 10, 199, 8, 243, 19, 40, 85, 137, 44, 20, 0, 9, 198, 88, 144, 146, 4, 99, 206, 20, 11, 200, 80, 245, 67, 32, 84, 137, 56, 112, 20, 11, 200, 76, 176, 78, 16, 84, 137, 56, 112, 20, 11, 200, 76, 176, 77, 24, 84, 137, 56, 112, 20, 11, 200, 73, 83, 83, 80, 84, 137, 56, 112, 20, 11, 200, 72, 81, 149, 76, 84, 137, 56, 112, 20, 11, 200, 72, 81, 133, 72, 84, 137, 56, 112, 20, 11, 200, 72, 81, 9, 28, 84, 137, 56, 112, 20, 11, 200, 64, 242, 78, 80, 84, 137, 56, 112, 20, 11, 200, 64, 192, 71, 36, 84, 137, 56, 112, 20, 11, 200, 64, 21, 9, 56, 84, 137, 56, 112, 20, 11, 200, 61, 5, 9, 52, 84, 137, 56, 112, 20, 11, 200, 52, 245, 9, 88, 84, 137, 56, 112, 20, 11, 200, 44, 17, 13, 36, 84, 137, 56, 112, 20, 11, 200, 40, 243, 135, 48, 84, 137, 56, 112, 20, 11, 200, 36, 226, 84, 36, 84, 137, 56, 112, 20, 11, 200, 32, 243, 143, 72, 84, 137, 56, 112, 20, 11, 200, 29, 37, 80, 64, 84, 137, 56, 112, 20, 11, 200, 20, 208, 76, 40, 84, 137, 56, 112, 20, 11, 200, 20, 181, 137, 64, 84, 137, 56, 112, 20, 11, 200, 16, 85, 143, 88, 84, 137, 56, 112, 20, 11, 200, 16, 80, 201, 52, 84, 137, 56, 112, 20, 11, 200, 12, 83, 148, 72, 84, 137, 56, 112, 20, 11, 200, 12, 17, 13, 36, 84, 137, 56, 112, 20, 11, 200, 9, 32, 73, 76, 84, 137, 56, 112, 20, 11, 200, 4, 192, 82, 52, 84, 137, 56, 112, 20, 11, 200, 4, 181, 9, 88, 84, 137, 56, 112, 20, 11, 200, 4, 69, 137, 76, 84, 137, 56, 112, 20, 11, 200, 4, 35, 210, 80, 84, 137, 56, 112, 20, 14, 68, 44, 19, 133, 48, 49, 108, 50, 6, 36, 55, 0, 20, 11, 200, 81, 35, 205, 64, 85, 5, 72, 80, 20, 11, 200, 44, 243, 131, 21, 37, 5, 72, 80, 20, 11, 200, 21, 66, 75, 21, 69, 5, 72, 80, 20, 11, 200, 9, 81, 7, 21, 69, 5, 72, 80, 20, 11, 200, 9, 34, 75, 21, 69, 5, 72, 80, 20, 12, 137, 16, 25, 7, 13, 195, 166, 9, 19, 11, 20, 11, 200, 60, 194, 71, 5, 34, 201, 76, 176, 20, 11, 200, 72, 81, 133, 45, 67, 210, 36, 80, 20, 11, 200, 65, 35, 214, 37, 51, 210, 36, 80, 20, 11, 200, 45, 33, 77, 5, 67, 210, 36, 80, 20, 7, 196, 24, 147, 137, 80, 20, 7, 196, 32, 16, 137, 48, 20, 11, 200, 61, 35, 129, 52, 83, 148, 36, 176, 20, 12, 137, 4, 9, 195, 166, 20, 5, 20, 9, 11, 20, 9, 198, 12, 20, 137, 8, 145, 78, 20, 7, 196, 5, 50, 65, 80, 20, 11, 200, 77, 4, 153, 17, 53, 1, 28, 80, 20, 0, 6, 195, 48, 145, 82, 20, 10, 69, 8, 244, 212, 60, 224, 21, 0, 10, 0, 13, 202, 81, 32, 78, 76, 99, 210, 52, 21, 15, 72, 20, 9, 198, 16, 21, 1, 56, 243, 64, 20, 0, 14, 203, 80, 84, 212, 4, 209, 78, 80, 84, 137, 56, 112, 20, 14, 203, 77, 147, 139, 72, 85, 9, 76, 84, 137, 56, 112, 20, 10, 199, 77, 69, 68, 21, 34, 78, 28, 20, 14, 203, 76, 147, 80, 48, 145, 137, 12, 84, 137, 56, 112, 20, 10, 199, 76, 19, 4, 21, 34, 78, 28, 20, 14, 203, 64, 244, 21, 48, 20, 137, 76, 84, 137, 56, 112, 20, 14, 203, 64, 20, 140, 4, 209, 78, 80, 84, 137, 56, 112, 20, 10, 199, 64, 19, 16, 21, 34, 78, 28, 20, 10, 199, 45, 33, 77, 21, 34, 78, 28, 20, 14, 203, 44, 19, 12, 36, 116, 129, 24, 84, 137, 56, 112, 20, 14, 203, 36, 65, 79, 48, 241, 201, 76, 84, 137, 56, 112, 20, 14, 203, 25, 83, 132, 4, 209, 78, 80, 84, 137, 56, 112, 20, 14, 203, 24, 244, 198, 61, 33, 83, 12, 84, 137, 56, 112, 20, 10, 199, 20, 213, 76, 21, 34, 78, 28, 20, 14, 203, 5, 85, 15, 52, 21, 9, 76, 84, 137, 56, 112, 20, 14, 203, 4, 193, 129, 8, 85, 9, 76, 84, 137, 56, 112, 20, 12, 201, 61, 1, 82, 5, 66, 79, 56, 83, 0, 20, 9, 198, 37, 51, 205, 21, 68, 137, 20, 10, 199, 16, 84, 15, 76, 149, 21, 52, 20, 10, 199, 52, 20, 137, 8, 243, 137, 80, 20, 10, 199, 45, 98, 82, 72, 85, 137, 80, 20, 10, 199, 85, 32, 129, 56, 148, 205, 20, 20, 10, 199, 48, 21, 9, 56, 148, 205, 20, 20, 10, 199, 44, 243, 15, 72, 148, 205, 20, 20, 10, 199, 28, 83, 210, 28, 148, 205, 20, 20, 10, 199, 9, 81, 4, 32, 148, 205, 20, 20, 10, 199, 20, 180, 201, 77, 65, 78, 76, 20, 6, 195, 76, 176, 76, 76, 0, 9, 198, 77, 80, 140, 36, 209, 82, 20, 9, 198, 65, 35, 214, 60, 177, 82, 20, 9, 198, 65, 35, 212, 20, 113, 82, 20, 9, 198, 5, 52, 207, 12, 145, 82, 20, 9, 198, 4, 66, 149, 56, 113, 82, 20, 9, 198, 4, 194, 207, 32, 243, 0, 20, 16, 141, 195, 184, 11, 15, 14, 15, 13, 5, 20, 18, 9, 19, 11, 20, 12, 137, 195, 166, 7, 25, 16, 20, 9, 19, 11, 20, 7, 196, 20, 243, 9, 80, 20, 9, 198, 48, 144, 133, 72, 144, 78, 20, 9, 198, 60, 36, 201, 16, 144, 78, 21, 7, 196, 4, 227, 129, 48, 20, 8, 67, 60, 176, 89, 21, 0, 10, 0, 9, 198, 32, 148, 16, 60, 195, 199, 20, 9, 198, 25, 33, 78, 60, 195, 199, 20, 12, 201, 88, 19, 4, 32, 244, 142, 37, 53, 0, 20, 12, 201, 8, 82, 1, 88, 147, 210, 37, 53, 0, 20, 11, 136, 19, 12, 195, 184, 19, 5, 18, 9, 20, 17, 142, 19, 20, 195, 184, 11, 9, 15, 13, 5, 20, 18, 9, 19, 11, 20, 13, 138, 19, 16, 15, 14, 4, 195, 166, 9, 19, 11, 20, 17, 142, 6, 195, 184, 4, 5, 18, 1, 12, 9, 19, 20, 9, 19, 11, 20, 17, 142, 5, 14, 3, 25, 11, 12, 15, 16, 195, 166, 4, 9, 19, 11, 20, 0, 13, 202, 52, 21, 18, 36, 181, 76, 21, 34, 78, 28, 20, 13, 202, 36, 225, 18, 20, 117, 76, 21, 34, 78, 28, 20, 13, 202, 20, 180, 208, 48, 242, 84, 21, 34, 78, 28, 20, 13, 202, 8, 20, 146, 36, 176, 68, 21, 34, 78, 28, 20, 14, 139, 16, 195, 166, 4, 1, 7, 15, 7, 9, 19, 11, 20, 13, 202, 81, 32, 78, 77, 97, 83, 80, 148, 205, 20, 20, 13, 202, 76, 176, 78, 16, 147, 129, 88, 148, 205, 20, 20, 13, 202, 21, 99, 204, 85, 66, 79, 56, 148, 205, 20, 20, 13, 202, 21, 67, 143, 12, 83, 148, 72, 148, 205, 20, 20, 9, 198, 48, 20, 153, 56, 112, 76, 20, 13, 202, 44, 243, 138, 84, 226, 212, 36, 243, 129, 48, 20, 11, 70, 52, 243, 148, 72, 80, 76, 21, 0, 10, 0, 10, 199, 24, 83, 142, 60, 195, 199, 36, 20, 10, 199, 32, 82, 212, 60, 116, 129, 52, 20, 15, 140, 16, 18, 195, 166, 16, 1, 18, 5, 18, 9, 14, 7, 20, 14, 139, 16, 18, 195, 166, 10, 21, 4, 9, 11, 1, 20, 20, 10, 199, 20, 229, 18, 20, 50, 1, 80, 20, 0, 9, 198, 65, 35, 208, 4, 113, 82, 20, 9, 198, 44, 243, 138, 84, 113, 82, 20, 9, 198, 21, 52, 1, 48, 145, 82, 20, 9, 198, 8, 19, 19, 4, 209, 82, 20, 14, 139, 6, 18, 9, 20, 195, 166, 14, 11, 5, 18, 9, 20, 9, 198, 4, 35, 210, 36, 114, 78, 20, 11, 200, 77, 80, 147, 37, 53, 5, 57, 48, 20, 9, 198, 64, 83, 77, 36, 176, 78, 21, 0, 13, 138, 195, 166, 7, 25, 16, 20, 15, 12, 15, 7, 20, 9, 198, 29, 32, 70, 60, 195, 199, 20, 17, 142, 5, 21, 18, 15, 16, 195, 166, 9, 19, 5, 18, 9, 14, 7, 20, 16, 205, 16, 82, 207, 57, 53, 18, 84, 181, 9, 88, 148, 205, 20, 20, 10, 135, 19, 9, 7, 195, 184, 10, 14, 20, 7, 196, 16, 147, 129, 72, 20, 7, 196, 64, 20, 129, 8, 20, 0, 8, 197, 104, 148, 139, 60, 224, 20, 9, 198, 4, 192, 82, 52, 84, 133, 20, 9, 198, 4, 35, 210, 80, 84, 133, 20, 0, 9, 198, 80, 16, 149, 48, 84, 128, 20, 9, 198, 76, 21, 9, 56, 84, 128, 20, 9, 198, 72, 84, 213, 52, 84, 128, 20, 12, 201, 25, 33, 77, 65, 35, 214, 60, 177, 82, 20, 9, 198, 52, 243, 137, 80, 84, 128, 20, 9, 198, 52, 83, 79, 72, 84, 128, 20, 9, 198, 45, 83, 85, 48, 84, 128, 20, 9, 198, 36, 228, 197, 72, 84, 128, 20, 9, 198, 36, 226, 1, 48, 84, 128, 20, 9, 198, 36, 195, 21, 16, 84, 128, 20, 9, 198, 28, 83, 73, 56, 84, 128, 20, 9, 198, 24, 242, 213, 76, 84, 128, 20, 9, 198, 24, 16, 149, 48, 84, 128, 20, 9, 198, 20, 210, 84, 80, 84, 128, 20, 9, 198, 16, 243, 73, 56, 84, 128, 20, 9, 198, 16, 80, 137, 80, 84, 128, 20, 9, 198, 5, 52, 9, 72, 84, 128, 20, 9, 198, 4, 195, 21, 16, 84, 128, 20, 9, 198, 4, 67, 208, 80, 84, 128, 20, 17, 142, 19, 11, 18, 21, 5, 2, 18, 195, 166, 11, 11, 5, 18, 9, 20, 9, 198, 32, 243, 143, 72, 20, 128, 20, 9, 198, 88, 83, 133, 72, 16, 128, 20, 0, 10, 199, 36, 212, 12, 61, 50, 79, 56, 20, 10, 199, 44, 243, 150, 60, 161, 82, 20, 20, 10, 199, 44, 21, 84, 36, 243, 133, 72, 20, 10, 199, 32, 20, 144, 84, 225, 82, 20, 20, 10, 199, 20, 180, 193, 52, 147, 133, 72, 20, 10, 199, 16, 85, 1, 48, 161, 82, 20, 20, 10, 199, 12, 19, 79, 84, 99, 5, 72, 20, 10, 199, 25, 83, 132, 4, 209, 78, 80, 20, 10, 199, 16, 85, 5, 72, 113, 78, 80, 20, 10, 199, 77, 84, 16, 48, 80, 78, 80, 20, 10, 199, 44, 243, 150, 21, 36, 193, 8, 20, 0, 11, 200, 52, 85, 1, 48, 195, 198, 60, 224, 20, 7, 196, 77, 2, 79, 56, 20, 12, 201, 80, 84, 212, 4, 209, 78, 80, 84, 133, 20, 11, 200, 44, 243, 5, 77, 65, 82, 60, 192, 20, 14, 139, 4, 9, 195, 166, 20, 5, 20, 9, 11, 5, 18, 20, 7, 196, 72, 244, 201, 56, 20, 11, 200, 56, 80, 80, 60, 194, 84, 4, 224, 20, 7, 196, 88, 83, 1, 56, 21, 7, 196, 44, 20, 1, 8, 20, 7, 196, 16, 83, 142, 20, 76, 0, 12, 201, 81, 32, 78, 76, 210, 84, 80, 84, 128, 20, 9, 198, 64, 148, 129, 80, 84, 133, 20, 12, 201, 53, 149, 15, 48, 241, 201, 76, 84, 128, 20, 12, 201, 53, 83, 20, 37, 3, 9, 12, 84, 128, 20, 9, 198, 45, 38, 80, 80, 84, 133, 20, 12, 201, 36, 229, 5, 72, 210, 84, 80, 84, 128, 20, 12, 201, 32, 243, 79, 28, 83, 137, 76, 84, 128, 20, 12, 201, 20, 180, 208, 72, 244, 18, 36, 84, 128, 20, 12, 201, 16, 148, 203, 72, 147, 73, 56, 84, 128, 20, 9, 198, 9, 35, 206, 104, 84, 133, 20, 12, 201, 8, 20, 212, 5, 33, 9, 76, 84, 128, 20, 9, 198, 8, 18, 129, 16, 84, 133, 20, 12, 201, 77, 145, 137, 48, 149, 9, 44, 84, 128, 20, 12, 201, 21, 2, 76, 21, 5, 9, 44, 84, 128, 20, 8, 197, 28, 20, 132, 36, 224, 20, 8, 197, 4, 226, 76, 36, 224, 20, 9, 198, 44, 243, 80, 4, 115, 137, 20, 8, 197, 80, 20, 148, 4, 224, 21, 8, 197, 64, 192, 84, 4, 224, 21, 8, 197, 72, 17, 9, 4, 192, 20, 8, 197, 24, 147, 9, 4, 192, 20, 0, 9, 198, 52, 85, 1, 24, 244, 128, 20, 9, 198, 76, 16, 143, 80, 84, 128, 20, 9, 198, 73, 83, 83, 80, 84, 128, 20, 9, 198, 72, 148, 201, 44, 84, 128, 20, 9, 198, 65, 33, 77, 36, 84, 128, 20, 9, 198, 64, 21, 9, 56, 84, 128, 20, 9, 198, 52, 20, 143, 16, 84, 128, 20, 9, 198, 48, 19, 73, 56, 84, 128, 20, 13, 202, 44, 243, 80, 48, 147, 69, 57, 65, 82, 20, 20, 9, 198, 12, 128, 82, 52, 84, 128, 20, 9, 198, 12, 83, 148, 72, 84, 128, 20, 9, 198, 12, 17, 13, 36, 84, 128, 20, 9, 198, 5, 36, 137, 88, 84, 128, 20, 9, 198, 57, 82, 204, 20, 20, 128, 20, 9, 198, 37, 36, 137, 80, 16, 128, 20, 0, 10, 199, 44, 244, 146, 20, 181, 21, 72, 20, 10, 199, 48, 18, 212, 5, 66, 79, 56, 20, 10, 199, 44, 243, 132, 37, 66, 79, 56, 20, 10, 199, 36, 229, 21, 37, 66, 79, 56, 20, 10, 199, 16, 148, 133, 45, 66, 79, 56, 20, 10, 199, 8, 19, 132, 4, 113, 82, 20, 20, 10, 199, 44, 148, 149, 72, 114, 83, 44, 20, 10, 199, 52, 85, 1, 24, 244, 137, 44, 20, 10, 199, 24, 148, 141, 4, 209, 78, 80, 20, 10, 199, 16, 148, 211, 36, 65, 78, 80, 20, 12, 201, 20, 180, 207, 72, 34, 84, 4, 229, 0, 20, 0, 10, 135, 195, 166, 15, 12, 9, 19, 11, 20, 11, 200, 85, 48, 133, 44, 148, 212, 4, 224, 21, 11, 200, 45, 35, 205, 61, 51, 205, 4, 192, 20, 0, 12, 201, 76, 147, 80, 48, 145, 137, 12, 84, 128, 20, 12, 201, 72, 82, 207, 53, 1, 78, 76, 84, 128, 20, 12, 201, 72, 82, 207, 52, 208, 78, 16, 84, 128, 20, 12, 201, 4, 195, 5, 28, 244, 137, 76, 84, 128, 20, 9, 198, 76, 209, 76, 80, 84, 137, 20, 9, 198, 76, 194, 75, 44, 84, 137, 20, 9, 198, 76, 178, 76, 16, 84, 137, 20, 9, 198, 64, 148, 129, 80, 84, 137, 20, 12, 201, 17, 148, 204, 20, 181, 9, 44, 84, 128, 20, 8, 197, 53, 84, 203, 5, 64, 20, 12, 201, 8, 144, 140, 36, 245, 5, 44, 20, 128, 20, 10, 69, 77, 68, 133, 21, 64, 21, 0, 10, 0, 9, 198, 56, 85, 82, 61, 49, 64, 20, 13, 202, 25, 32, 71, 52, 83, 148, 5, 66, 79, 56, 20, 13, 202, 16, 148, 208, 72, 244, 15, 73, 66, 79, 56, 20, 9, 198, 44, 20, 203, 4, 65, 64, 20, 0, 10, 199, 77, 83, 77, 21, 34, 78, 28, 20, 9, 198, 36, 211, 65, 56, 83, 147, 20, 0, 11, 200, 44, 20, 129, 8, 147, 137, 21, 32, 20, 12, 137, 16, 10, 195, 166, 11, 11, 5, 18, 9, 20, 12, 201, 44, 192, 77, 64, 133, 71, 28, 84, 137, 20, 7, 196, 81, 34, 79, 48, 20, 18, 143, 195, 166, 11, 22, 9, 12, 9, 2, 18, 9, 19, 20, 9, 19, 11, 20, 14, 139, 16, 195, 166, 4, 9, 1, 20, 18, 9, 19, 11, 20, 14, 139, 15, 18, 20, 15, 16, 195, 166, 4, 9, 19, 11, 20, 14, 139, 12, 15, 7, 15, 16, 195, 166, 4, 9, 19, 11, 20, 13, 72, 77, 113, 65, 81, 50, 9, 73, 64, 21, 0, 10, 0, 9, 198, 21, 2, 76, 21, 4, 201, 20, 9, 198, 17, 148, 208, 21, 4, 201, 20, 12, 201, 45, 38, 83, 80, 19, 12, 61, 49, 64, 20, 8, 197, 88, 20, 137, 21, 32, 20, 9, 198, 76, 160, 83, 44, 84, 137, 20, 9, 198, 61, 32, 78, 28, 84, 137, 20, 12, 201, 24, 244, 130, 36, 225, 20, 48, 145, 192, 20, 12, 201, 76, 19, 77, 20, 228, 213, 72, 145, 64, 20, 8, 197, 77, 64, 75, 37, 64, 20, 14, 139, 8, 9, 12, 12, 5, 18, 195, 184, 4, 1, 14, 20, 8, 197, 64, 20, 211, 5, 64, 20, 8, 197, 44, 244, 147, 5, 32, 20, 0, 9, 198, 36, 211, 65, 56, 83, 148, 20, 0, 14, 139, 15, 18, 20, 15, 16, 195, 166, 4, 9, 19, 20, 20, 0, 9, 198, 72, 80, 197, 65, 67, 210, 20, 9, 198, 44, 243, 80, 48, 85, 0, 20, 9, 198, 44, 21, 129, 48, 85, 0, 20, 9, 198, 12, 243, 80, 48, 85, 0, 20, 9, 198, 64, 20, 137, 80, 85, 0, 20, 7, 196, 76, 19, 133, 72, 20, 7, 196, 16, 243, 133, 72, 20, 9, 198, 45, 38, 79, 48, 149, 0, 20, 9, 198, 32, 148, 212, 4, 210, 78, 20, 9, 198, 5, 4, 5, 49, 50, 78, 20, 7, 196, 33, 83, 65, 56, 21, 7, 196, 8, 19, 129, 56, 21, 0, 12, 201, 52, 85, 1, 52, 244, 134, 61, 49, 64, 20, 8, 197, 20, 225, 82, 28, 144, 20, 12, 201, 77, 66, 76, 37, 49, 82, 36, 225, 192, 20, 12, 201, 76, 145, 206, 4, 193, 82, 36, 225, 192, 20, 12, 201, 76, 50, 1, 81, 65, 82, 36, 225, 192, 20, 12, 201, 72, 82, 204, 4, 209, 82, 36, 225, 192, 20, 12, 201, 72, 81, 143, 72, 209, 82, 36, 225, 192, 20, 12, 201, 65, 35, 198, 36, 193, 82, 36, 225, 192, 20, 12, 201, 64, 241, 84, 37, 49, 82, 36, 225, 192, 20, 12, 201, 45, 32, 75, 20, 193, 82, 36, 225, 192, 20, 12, 201, 44, 19, 132, 37, 49, 82, 36, 225, 192, 20, 12, 201, 36, 225, 12, 60, 113, 82, 36, 225, 192, 20, 12, 201, 36, 67, 204, 37, 49, 82, 36, 225, 192, 20, 12, 201, 32, 84, 143, 37, 49, 82, 36, 225, 192, 20, 12, 201, 24, 16, 146, 36, 177, 82, 36, 225, 192, 20, 12, 201, 20, 112, 76, 37, 49, 82, 36, 225, 192, 20, 12, 201, 16, 148, 211, 20, 177, 82, 36, 225, 192, 20, 12, 201, 16, 85, 129, 49, 81, 82, 36, 225, 192, 20, 12, 201, 16, 84, 212, 73, 81, 82, 36, 225, 192, 20, 12, 201, 16, 82, 204, 4, 209, 82, 36, 225, 192, 20, 12, 201, 16, 81, 143, 72, 209, 82, 36, 225, 192, 20, 12, 201, 8, 149, 149, 4, 177, 82, 36, 225, 192, 20, 12, 201, 4, 227, 196, 37, 49, 82, 36, 225, 192, 20, 12, 201, 4, 113, 210, 5, 97, 82, 36, 225, 192, 20, 13, 138, 19, 195, 184, 18, 195, 184, 22, 5, 18, 9, 20, 9, 198, 28, 84, 129, 56, 149, 77, 20, 12, 201, 72, 83, 1, 80, 149, 137, 76, 209, 64, 20, 8, 197, 80, 148, 129, 16, 80, 20, 8, 197, 64, 20, 129, 16, 80, 20, 11, 67, 16, 149, 0, 70, 6, 37, 47, 0, 72, 0, 9, 198, 77, 147, 133, 72, 114, 64, 20, 0, 10, 199, 72, 80, 197, 77, 50, 79, 56, 20, 10, 199, 4, 227, 133, 45, 50, 79, 56, 20, 10, 199, 4, 67, 73, 77, 50, 79, 56, 20, 12, 201, 64, 21, 15, 28, 83, 137, 80, 85, 0, 20, 12, 201, 24, 83, 73, 56, 147, 137, 80, 85, 0, 20, 10, 199, 44, 243, 132, 20, 211, 133, 72, 20, 10, 199, 36, 228, 197, 52, 147, 133, 72, 20, 10, 199, 28, 83, 1, 80, 147, 133, 72, 20, 15, 140, 195, 184, 10, 5, 14, 20, 10, 5, 14, 5, 18, 9, 20, 10, 199, 77, 98, 78, 16, 193, 82, 36, 20, 10, 199, 77, 84, 141, 84, 193, 82, 36, 20, 10, 199, 76, 180, 137, 8, 193, 82, 36, 20, 10, 199, 65, 34, 86, 5, 65, 82, 36, 20, 10, 199, 28, 19, 1, 57, 65, 82, 36, 20, 10, 199, 25, 34, 77, 85, 33, 82, 36, 20, 10, 199, 21, 2, 71, 60, 225, 82, 36, 20, 10, 199, 12, 130, 75, 4, 225, 82, 36, 20, 10, 199, 8, 146, 143, 85, 65, 82, 36, 20, 10, 199, 5, 37, 9, 48, 193, 82, 36, 20, 12, 201, 4, 229, 9, 32, 148, 212, 4, 210, 78, 20, 10, 199, 52, 85, 1, 25, 148, 201, 44, 20, 10, 199, 52, 20, 203, 21, 32, 68, 20, 20, 0, 12, 201, 61, 48, 201, 48, 195, 211, 44, 244, 0, 20, 9, 198, 64, 18, 76, 48, 85, 0, 20, 11, 200, 80, 149, 21, 48, 84, 137, 56, 112, 20, 11, 200, 76, 176, 76, 64, 84, 137, 56, 112, 20, 11, 200, 72, 83, 143, 88, 84, 137, 56, 112, 20, 11, 200, 72, 83, 5, 28, 84, 137, 56, 112, 20, 15, 204, 72, 81, 201, 60, 224, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 65, 54, 75, 60, 195, 199, 37, 49, 82, 36, 225, 192, 20, 11, 200, 64, 194, 83, 76, 84, 137, 56, 112, 20, 15, 204, 48, 82, 211, 36, 176, 76, 37, 49, 82, 36, 225, 192, 20, 11, 200, 48, 19, 73, 56, 84, 137, 56, 112, 20, 15, 204, 45, 38, 83, 80, 19, 12, 37, 49, 82, 36, 225, 192, 20, 15, 204, 45, 38, 80, 80, 241, 210, 4, 97, 82, 36, 225, 192, 20, 15, 204, 32, 244, 208, 37, 64, 76, 37, 49, 82, 36, 225, 192, 20, 11, 200, 25, 32, 78, 44, 84, 137, 56, 112, 20, 11, 200, 21, 96, 75, 84, 84, 137, 56, 112, 20, 15, 204, 16, 84, 212, 4, 34, 76, 37, 49, 82, 36, 225, 192, 20, 15, 204, 16, 84, 207, 72, 112, 78, 37, 49, 82, 36, 225, 192, 20, 15, 204, 16, 83, 79, 45, 32, 84, 37, 49, 82, 36, 225, 192, 20, 11, 200, 16, 83, 5, 28, 84, 137, 56, 112, 20, 11, 200, 5, 69, 1, 44, 84, 137, 56, 112, 20, 15, 204, 4, 178, 204, 36, 208, 84, 37, 49, 82, 36, 225, 192, 20, 11, 200, 84, 226, 70, 61, 35, 69, 72, 80, 20, 11, 200, 44, 192, 85, 77, 83, 5, 72, 80, 20, 11, 200, 64, 21, 18, 60, 225, 83, 76, 80, 20, 11, 200, 56, 83, 204, 37, 66, 75, 84, 208, 20, 11, 200, 56, 20, 139, 61, 66, 75, 84, 208, 20, 9, 198, 64, 243, 70, 72, 149, 0, 20, 11, 200, 44, 243, 80, 21, 65, 78, 12, 80, 20, 7, 196, 88, 83, 1, 72, 20, 7, 196, 32, 83, 132, 20, 72, 0, 11, 136, 12, 21, 11, 19, 21, 195, 184, 19, 20, 12, 201, 76, 149, 21, 5, 66, 79, 56, 83, 0, 20, 12, 201, 72, 81, 1, 45, 66, 79, 56, 83, 0, 20, 9, 198, 44, 193, 78, 60, 66, 69, 20, 9, 198, 77, 147, 80, 61, 50, 69, 20, 9, 198, 21, 81, 143, 52, 19, 137, 20, 12, 69, 52, 17, 1, 52, 80, 21, 102, 114, 0, 10, 0, 17, 142, 5, 14, 3, 25, 11, 12, 15, 16, 195, 166, 4, 9, 19, 20, 20, 9, 198, 60, 97, 137, 12, 145, 76, 20, 9, 198, 77, 84, 146, 20, 19, 0, 20, 0, 20, 67, 32, 19, 128, 105, 108, 50, 15, 87, 47, 6, 36, 0, 81, 115, 116, 101, 103, 32, 10, 199, 72, 80, 197, 65, 66, 79, 56, 20, 10, 199, 45, 33, 77, 5, 66, 79, 56, 20, 10, 199, 16, 81, 21, 45, 66, 79, 56, 20, 12, 201, 36, 224, 75, 80, 149, 137, 80, 85, 0, 20, 14, 203, 77, 65, 78, 60, 116, 129, 24, 84, 137, 56, 112, 20, 14, 203, 72, 85, 137, 80, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 64, 20, 212, 21, 84, 137, 76, 84, 137, 56, 112, 20, 14, 203, 64, 19, 1, 80, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 52, 243, 143, 64, 243, 9, 76, 84, 137, 56, 112, 20, 14, 203, 44, 21, 1, 48, 241, 201, 76, 84, 137, 56, 112, 20, 18, 207, 36, 228, 212, 73, 83, 69, 57, 64, 76, 37, 49, 82, 36, 225, 192, 20, 14, 203, 36, 225, 15, 45, 68, 137, 56, 84, 137, 56, 112, 20, 14, 203, 32, 82, 212, 60, 116, 129, 24, 84, 137, 56, 112, 20, 14, 203, 24, 81, 5, 72, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 20, 180, 212, 20, 212, 15, 72, 84, 137, 56, 112, 20, 14, 203, 16, 145, 201, 80, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 12, 128, 80, 80, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 4, 100, 137, 44, 19, 137, 76, 84, 137, 56, 112, 20, 10, 199, 44, 20, 143, 77, 49, 82, 36, 20, 10, 199, 36, 225, 137, 72, 209, 82, 36, 20, 10, 199, 80, 19, 65, 72, 147, 132, 20, 20, 10, 199, 65, 34, 79, 72, 147, 132, 20, 20, 11, 67, 16, 147, 128, 70, 6, 37, 50, 0, 76, 6, 195, 32, 19, 128, 72, 0, 11, 200, 24, 192, 78, 44, 84, 137, 56, 112, 20, 11, 200, 5, 81, 9, 80, 84, 137, 56, 112, 20, 11, 200, 44, 243, 80, 5, 36, 197, 72, 144, 20, 11, 68, 24, 147, 129, 48, 20, 36, 87, 36, 0, 7, 196, 32, 16, 137, 80, 20, 7, 196, 48, 16, 137, 48, 20, 7, 196, 60, 35, 1, 80, 20, 7, 196, 80, 243, 129, 48, 20, 7, 196, 44, 19, 129, 48, 20, 7, 196, 24, 147, 129, 48, 20, 7, 196, 8, 19, 129, 48, 20, 11, 200, 44, 243, 16, 61, 37, 1, 28, 80, 20, 0, 9, 198, 76, 182, 76, 48, 84, 137, 20, 9, 198, 44, 21, 129, 48, 84, 137, 20, 6, 195, 73, 82, 78, 20, 9, 198, 48, 19, 65, 37, 51, 69, 20, 9, 198, 5, 67, 205, 37, 51, 69, 20, 25, 4, 95, 55, 88, 15, 105, 108, 55, 81, 57, 6, 108, 34, 87, 36, 50, 87, 47, 114, 82, 13, 50, 13, 0, 0, 11, 67, 20, 115, 133, 35, 12, 37, 50, 13, 0, 11, 136, 20, 18, 1, 11, 20, 195, 184, 18, 20, 13, 202, 81, 32, 78, 77, 2, 82, 5, 66, 79, 56, 20, 13, 202, 44, 243, 148, 4, 210, 78, 5, 66, 79, 56, 20, 13, 202, 44, 243, 12, 4, 35, 210, 5, 66, 79, 56, 20, 13, 202, 32, 19, 12, 84, 50, 78, 5, 66, 79, 56, 20, 13, 202, 20, 180, 208, 5, 68, 137, 5, 66, 79, 56, 20, 9, 198, 25, 85, 21, 73, 83, 64, 20, 9, 198, 20, 198, 83, 37, 83, 64, 20, 9, 198, 44, 20, 129, 8, 147, 128, 20, 9, 198, 8, 18, 18, 4, 147, 128, 20, 9, 198, 77, 3, 206, 80, 19, 128, 21, 11, 67, 16, 147, 133, 70, 6, 37, 50, 36, 0, 0, 10, 199, 44, 20, 132, 36, 19, 7, 36, 20, 10, 199, 5, 53, 18, 60, 195, 199, 36, 20, 9, 198, 80, 20, 133, 72, 147, 135, 20, 10, 199, 80, 19, 10, 21, 34, 78, 28, 20, 10, 199, 76, 145, 206, 21, 34, 78, 28, 20, 10, 199, 65, 83, 19, 21, 34, 78, 28, 20, 9, 198, 64, 20, 133, 72, 147, 135, 20, 9, 198, 64, 19, 133, 72, 147, 135, 20, 10, 199, 37, 34, 83, 21, 34, 78, 28, 20, 10, 199, 33, 145, 18, 21, 34, 78, 28, 20, 10, 199, 25, 84, 142, 21, 34, 78, 28, 20, 9, 198, 24, 147, 133, 72, 147, 135, 20, 10, 199, 9, 81, 211, 21, 34, 78, 28, 20, 10, 199, 44, 83, 73, 44, 19, 9, 20, 20, 10, 199, 64, 85, 18, 60, 193, 85, 52, 20, 10, 199, 77, 67, 201, 12, 148, 205, 20, 20, 10, 199, 64, 16, 201, 24, 148, 205, 20, 20, 10, 199, 52, 244, 129, 48, 148, 205, 20, 20, 10, 199, 24, 19, 129, 80, 148, 205, 20, 20, 10, 199, 48, 242, 207, 52, 240, 137, 48, 20, 10, 199, 24, 192, 71, 20, 195, 1, 80, 20, 10, 199, 52, 81, 9, 12, 147, 129, 48, 20, 10, 199, 20, 208, 146, 100, 243, 129, 48, 20, 0, 9, 198, 16, 82, 204, 4, 209, 82, 20, 9, 198, 8, 149, 149, 4, 177, 82, 20, 12, 201, 16, 85, 5, 72, 210, 78, 37, 51, 69, 20, 7, 196, 24, 243, 133, 52, 20, 9, 198, 40, 19, 65, 36, 48, 78, 20, 7, 196, 77, 82, 193, 80, 20, 7, 196, 61, 2, 65, 80, 20, 7, 196, 17, 82, 193, 80, 20, 11, 70, 16, 80, 149, 28, 113, 82, 21, 0, 10, 0, 14, 139, 9, 14, 19, 20, 18, 21, 11, 20, 195, 184, 18, 20, 9, 198, 52, 147, 129, 72, 147, 133, 20, 9, 198, 28, 83, 210, 28, 147, 133, 20, 9, 198, 4, 35, 206, 56, 147, 133, 20, 12, 201, 77, 84, 16, 61, 50, 84, 36, 243, 128, 20, 12, 201, 52, 19, 149, 17, 82, 212, 36, 243, 128, 20, 12, 201, 45, 98, 78, 80, 147, 12, 36, 243, 128, 20, 12, 201, 44, 243, 138, 84, 226, 212, 36, 243, 128, 20, 12, 201, 36, 228, 212, 37, 69, 84, 36, 243, 128, 20, 12, 201, 36, 226, 214, 37, 50, 84, 36, 243, 128, 20, 12, 201, 20, 180, 212, 36, 226, 212, 36, 243, 128, 20, 12, 201, 20, 180, 208, 61, 50, 84, 36, 243, 128, 20, 12, 201, 16, 148, 212, 36, 226, 212, 36, 243, 128, 20, 12, 201, 16, 148, 208, 61, 50, 84, 36, 243, 128, 20, 12, 201, 16, 84, 212, 73, 82, 212, 36, 243, 128, 20, 0, 15, 140, 11, 15, 14, 19, 20, 18, 21, 11, 20, 195, 184, 18, 20, 9, 198, 44, 243, 15, 24, 243, 128, 20, 13, 202, 89, 83, 11, 4, 226, 83, 21, 34, 78, 28, 20, 13, 202, 81, 32, 78, 77, 2, 82, 21, 34, 78, 28, 20, 13, 202, 81, 32, 78, 76, 97, 82, 21, 34, 78, 28, 20, 13, 202, 80, 83, 210, 21, 66, 83, 21, 34, 78, 28, 20, 13, 202, 80, 83, 5, 29, 32, 70, 21, 34, 78, 28, 20, 13, 202, 77, 84, 5, 73, 98, 83, 21, 34, 78, 28, 20, 12, 201, 77, 3, 206, 76, 244, 133, 72, 147, 135, 20, 13, 202, 76, 177, 77, 5, 66, 83, 21, 34, 78, 28, 20, 13, 202, 76, 19, 139, 80, 147, 206, 21, 34, 78, 28, 20, 12, 201, 72, 21, 9, 32, 16, 133, 72, 147, 135, 20, 13, 202, 64, 20, 129, 29, 32, 70, 21, 34, 78, 28, 20, 13, 202, 60, 34, 133, 45, 66, 86, 21, 34, 78, 28, 20, 13, 202, 56, 20, 139, 61, 66, 83, 21, 34, 78, 28, 20, 13, 202, 52, 241, 5, 72, 226, 83, 21, 34, 78, 28, 20, 13, 202, 52, 84, 131, 21, 34, 83, 21, 34, 78, 28, 20, 12, 201, 52, 81, 9, 12, 147, 133, 72, 147, 135, 20, 13, 202, 52, 17, 206, 21, 66, 83, 21, 34, 78, 28, 20, 13, 202, 44, 243, 148, 4, 210, 78, 21, 34, 78, 28, 20, 13, 202, 44, 194, 77, 5, 66, 83, 21, 34, 78, 28, 20, 13, 202, 44, 147, 15, 52, 85, 18, 21, 34, 78, 28, 20, 12, 201, 44, 21, 84, 36, 243, 133, 72, 147, 135, 20, 13, 202, 44, 20, 130, 60, 226, 83, 21, 34, 78, 28, 20, 12, 201, 36, 225, 18, 84, 195, 5, 72, 147, 135, 20, 12, 201, 36, 225, 11, 48, 20, 133, 72, 147, 135, 20, 13, 202, 33, 148, 14, 61, 66, 83, 21, 34, 78, 28, 20, 13, 202, 32, 148, 212, 61, 34, 83, 21, 34, 78, 28, 20, 13, 202, 28, 195, 194, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 28, 129, 84, 80, 242, 83, 21, 34, 78, 28, 20, 13, 202, 28, 20, 142, 37, 51, 206, 21, 34, 78, 28, 20, 13, 202, 24, 245, 15, 29, 32, 70, 21, 34, 78, 28, 20, 13, 202, 24, 147, 13, 5, 66, 83, 21, 34, 78, 28, 20, 13, 202, 17, 32, 77, 5, 66, 83, 21, 34, 78, 28, 20, 13, 202, 16, 241, 205, 5, 66, 83, 21, 34, 78, 28, 20, 13, 202, 16, 83, 196, 61, 34, 83, 21, 34, 78, 28, 20, 12, 201, 12, 149, 137, 48, 148, 197, 72, 147, 135, 20, 12, 201, 12, 19, 79, 84, 99, 5, 72, 147, 135, 20, 13, 202, 5, 35, 205, 5, 66, 83, 21, 34, 78, 28, 20, 13, 202, 4, 227, 206, 100, 210, 83, 21, 34, 78, 28, 20, 13, 202, 4, 224, 76, 60, 114, 83, 21, 34, 78, 28, 20, 13, 202, 4, 176, 68, 20, 210, 83, 21, 34, 78, 28, 20, 13, 202, 36, 228, 212, 37, 69, 84, 36, 243, 133, 48, 20, 9, 198, 64, 147, 135, 88, 147, 128, 20, 9, 198, 52, 81, 9, 12, 147, 128, 20, 13, 202, 84, 226, 86, 21, 36, 193, 48, 148, 205, 20, 20, 13, 202, 44, 243, 12, 20, 181, 9, 88, 148, 205, 20, 20, 9, 198, 52, 242, 9, 44, 19, 128, 20, 9, 198, 52, 81, 9, 12, 147, 128, 20, 9, 198, 4, 225, 207, 48, 19, 128, 20, 9, 198, 81, 83, 9, 64, 19, 128, 21, 9, 198, 64, 83, 9, 44, 19, 128, 21, 9, 198, 52, 83, 66, 72, 19, 128, 21, 9, 198, 21, 81, 143, 52, 19, 128, 21, 7, 66, 16, 160, 21, 0, 10, 0, 31, 67, 64, 20, 128, 48, 35, 12, 36, 79, 87, 13, 6, 55, 35, 12, 66, 87, 0, 81, 101, 120, 99, 101, 108, 108, 101, 110, 99, 101, 32, 10, 199, 77, 65, 84, 61, 50, 207, 64, 20, 10, 199, 80, 85, 18, 4, 195, 199, 36, 20, 10, 199, 64, 85, 18, 60, 195, 199, 36, 20, 10, 199, 28, 83, 133, 4, 195, 199, 36, 20, 9, 198, 76, 19, 133, 72, 147, 135, 20, 9, 198, 52, 147, 133, 72, 147, 135, 20, 9, 198, 28, 148, 133, 72, 147, 135, 20, 12, 201, 65, 54, 75, 60, 195, 199, 37, 49, 82, 20, 12, 201, 21, 70, 77, 60, 195, 199, 37, 49, 82, 20, 10, 199, 45, 84, 129, 80, 244, 137, 20, 20, 10, 199, 28, 195, 211, 76, 20, 137, 20, 20, 10, 199, 48, 144, 197, 57, 66, 65, 80, 20, 10, 67, 32, 20, 128, 105, 110, 34, 0, 76, 0, 40, 68, 16, 147, 133, 72, 70, 37, 50, 6, 36, 47, 34, 110, 66, 87, 48, 112, 47, 6, 35, 69, 55, 13, 0, 81, 116, 114, 97, 110, 115, 112, 111, 114, 116, 97, 98, 108, 101, 32, 7, 196, 64, 19, 133, 72, 20, 9, 198, 61, 34, 71, 4, 209, 82, 20, 7, 196, 16, 147, 133, 72, 20, 9, 198, 5, 67, 205, 37, 49, 82, 20, 12, 201, 65, 54, 75, 60, 195, 199, 37, 51, 69, 20, 7, 196, 16, 83, 129, 72, 20, 16, 73, 52, 17, 5, 52, 242, 83, 20, 195, 5, 21, 102, 114, 0, 10, 6, 196, 20, 195, 5, 72, 0, 8, 197, 64, 21, 18, 60, 224, 20, 17, 69, 56, 21, 18, 60, 224, 50, 6, 108, 12, 47, 51, 112, 50, 0, 20, 16, 205, 81, 32, 78, 76, 148, 212, 61, 34, 83, 21, 34, 78, 28, 20, 16, 205, 25, 83, 139, 80, 147, 206, 4, 194, 83, 21, 34, 78, 28, 20, 9, 198, 76, 176, 78, 16, 84, 133, 20, 9, 198, 64, 242, 78, 80, 84, 133, 20, 9, 198, 52, 245, 9, 88, 84, 133, 20, 9, 198, 29, 37, 80, 64, 84, 133, 20, 9, 198, 4, 181, 9, 88, 84, 133, 20, 8, 197, 28, 243, 132, 60, 192, 20, 8, 197, 8, 147, 195, 36, 64, 20, 8, 197, 40, 20, 205, 36, 224, 20, 9, 198, 77, 147, 139, 72, 243, 137, 20, 12, 201, 72, 85, 19, 52, 81, 9, 12, 147, 128, 20, 0, 9, 198, 16, 149, 137, 76, 244, 128, 20, 9, 198, 45, 96, 78, 80, 244, 128, 20, 12, 201, 76, 82, 212, 36, 243, 133, 72, 147, 135, 20, 12, 201, 44, 243, 210, 16, 147, 133, 72, 147, 135, 20, 12, 201, 44, 243, 132, 20, 211, 133, 72, 147, 135, 20, 12, 201, 36, 228, 197, 52, 147, 133, 72, 147, 135, 20, 12, 201, 28, 83, 1, 80, 147, 133, 72, 147, 135, 20, 12, 201, 5, 85, 15, 72, 148, 197, 72, 147, 135, 20, 9, 198, 88, 145, 9, 52, 84, 128, 20, 9, 198, 72, 18, 76, 48, 84, 128, 20, 9, 198, 56, 243, 73, 56, 84, 128, 20, 9, 198, 52, 84, 137, 80, 84, 128, 20, 9, 198, 44, 20, 137, 44, 84, 128, 20, 9, 198, 21, 128, 201, 80, 84, 128, 20, 9, 198, 16, 149, 137, 16, 84, 128, 20, 9, 198, 4, 208, 149, 48, 84, 128, 20, 9, 198, 28, 198, 67, 21, 35, 204, 20, 0, 10, 199, 77, 147, 80, 61, 50, 79, 56, 20, 10, 199, 64, 20, 131, 20, 195, 5, 72, 20, 12, 201, 52, 85, 1, 52, 244, 134, 61, 49, 82, 20, 10, 199, 76, 176, 66, 4, 117, 9, 28, 20, 10, 199, 84, 226, 84, 5, 34, 83, 44, 20, 10, 199, 77, 147, 70, 60, 226, 83, 44, 20, 10, 199, 76, 86, 9, 77, 66, 83, 44, 20, 10, 199, 76, 17, 9, 77, 66, 83, 44, 20, 10, 199, 52, 20, 148, 101, 34, 83, 44, 20, 10, 199, 32, 243, 9, 77, 66, 83, 44, 20, 10, 199, 32, 149, 20, 37, 66, 83, 44, 20, 10, 199, 28, 19, 1, 45, 66, 83, 44, 20, 10, 199, 16, 243, 69, 77, 66, 83, 44, 20, 10, 199, 16, 149, 82, 21, 66, 83, 44, 20, 10, 199, 16, 144, 66, 21, 66, 83, 44, 20, 10, 199, 5, 85, 9, 77, 66, 83, 44, 20, 10, 199, 5, 65, 73, 77, 66, 83, 44, 20, 10, 199, 76, 176, 66, 4, 117, 9, 28, 20, 10, 199, 24, 16, 146, 36, 176, 78, 80, 20, 6, 195, 40, 84, 128, 72, 0, 11, 200, 77, 147, 139, 72, 245, 18, 60, 224, 20, 7, 196, 65, 34, 79, 56, 20, 7, 196, 28, 83, 5, 72, 20, 7, 196, 28, 19, 1, 72, 20, 7, 196, 64, 243, 1, 72, 20, 13, 68, 24, 244, 132, 36, 81, 112, 70, 6, 37, 0, 8, 0, 9, 198, 64, 195, 205, 8, 84, 133, 20, 9, 198, 64, 20, 129, 16, 84, 133, 20, 9, 198, 64, 19, 133, 48, 84, 133, 20, 9, 198, 52, 20, 131, 32, 84, 133, 20, 12, 201, 36, 225, 11, 4, 194, 213, 48, 84, 128, 20, 9, 198, 9, 35, 195, 32, 84, 133, 20, 9, 198, 5, 96, 78, 12, 84, 133, 20, 8, 197, 9, 32, 77, 36, 224, 20, 8, 197, 40, 245, 137, 4, 192, 20, 8, 197, 28, 83, 137, 4, 192, 20, 0, 9, 66, 33, 32, 105, 108, 34, 0, 25, 9, 198, 76, 176, 77, 24, 84, 128, 20, 9, 198, 76, 176, 76, 64, 84, 128, 20, 9, 198, 72, 82, 210, 20, 84, 128, 20, 9, 198, 72, 81, 149, 76, 84, 128, 20, 15, 140, 16, 18, 195, 166, 6, 1, 2, 18, 9, 11, 5, 18, 20, 9, 198, 64, 244, 148, 36, 84, 128, 20, 9, 198, 64, 194, 83, 76, 84, 128, 20, 9, 198, 44, 17, 13, 36, 84, 128, 20, 9, 198, 40, 243, 135, 48, 84, 128, 20, 9, 198, 36, 226, 84, 36, 84, 128, 20, 9, 198, 25, 32, 78, 44, 84, 128, 20, 9, 198, 21, 96, 75, 84, 84, 128, 20, 9, 198, 20, 209, 78, 16, 84, 128, 20, 9, 198, 20, 181, 137, 64, 84, 128, 20, 9, 198, 16, 83, 143, 80, 84, 128, 20, 9, 198, 5, 69, 1, 44, 84, 128, 20, 13, 202, 80, 84, 141, 61, 3, 1, 77, 66, 83, 44, 20, 13, 202, 76, 83, 147, 84, 19, 9, 77, 66, 83, 44, 20, 13, 202, 72, 85, 129, 56, 50, 9, 77, 66, 83, 44, 20, 13, 202, 56, 20, 131, 37, 52, 201, 77, 66, 83, 44, 20, 13, 202, 52, 243, 143, 64, 243, 9, 77, 66, 83, 44, 20, 13, 202, 48, 81, 201, 80, 147, 73, 77, 66, 83, 44, 20, 13, 202, 44, 192, 83, 76, 144, 201, 77, 66, 83, 44, 20, 13, 202, 24, 81, 5, 72, 19, 9, 77, 66, 83, 44, 20, 13, 202, 20, 180, 212, 72, 83, 73, 77, 66, 83, 44, 20, 9, 198, 80, 83, 132, 20, 228, 192, 20, 9, 198, 9, 33, 86, 36, 20, 128, 20, 9, 198, 5, 34, 201, 88, 20, 128, 20, 9, 198, 24, 21, 143, 72, 16, 128, 20, 0, 10, 67, 32, 21, 128, 105, 110, 40, 0, 14, 10, 199, 80, 18, 211, 5, 66, 79, 56, 20, 10, 199, 44, 148, 135, 37, 50, 83, 44, 20, 10, 199, 81, 33, 77, 84, 192, 78, 80, 20, 0, 9, 198, 8, 85, 1, 81, 35, 206, 20, 6, 195, 32, 19, 147, 76, 0, 12, 201, 81, 32, 78, 76, 49, 78, 16, 84, 128, 20, 12, 201, 76, 19, 69, 45, 50, 83, 80, 84, 128, 20, 12, 201, 65, 35, 208, 4, 112, 78, 16, 84, 128, 20, 12, 201, 64, 244, 21, 48, 20, 137, 76, 84, 128, 20, 12, 201, 64, 20, 212, 21, 84, 137, 76, 84, 128, 20, 12, 201, 64, 20, 140, 4, 209, 78, 80, 84, 128, 20, 8, 197, 49, 82, 210, 21, 32, 20, 12, 201, 44, 21, 1, 48, 241, 201, 76, 84, 128, 20, 12, 201, 36, 229, 5, 73, 5, 78, 28, 84, 128, 20, 12, 201, 36, 225, 15, 45, 68, 137, 56, 84, 128, 20, 12, 201, 36, 65, 79, 48, 241, 201, 76, 84, 128, 20, 12, 201, 20, 180, 212, 20, 228, 201, 88, 84, 128, 20, 12, 201, 20, 180, 212, 20, 212, 15, 72, 84, 128, 20, 12, 201, 4, 100, 137, 44, 19, 137, 76, 84, 128, 20, 12, 201, 44, 243, 77, 20, 228, 213, 72, 16, 128, 20, 0, 9, 198, 44, 195, 210, 61, 49, 64, 20, 9, 198, 24, 144, 146, 61, 49, 64, 20, 9, 198, 12, 243, 80, 61, 49, 64, 20, 13, 202, 24, 84, 148, 36, 194, 83, 5, 66, 79, 56, 20, 13, 202, 76, 19, 141, 5, 34, 78, 21, 50, 83, 44, 20, 13, 202, 45, 38, 80, 80, 241, 210, 4, 98, 83, 44, 20, 13, 138, 16, 18, 195, 166, 19, 9, 4, 5, 14, 20, 20, 9, 198, 36, 225, 15, 48, 83, 148, 20, 9, 198, 25, 32, 71, 52, 83, 148, 20, 9, 198, 20, 195, 203, 88, 83, 148, 20, 9, 198, 53, 84, 201, 44, 19, 148, 20, 9, 198, 48, 16, 143, 72, 19, 148, 20, 9, 198, 36, 115, 143, 72, 19, 148, 20, 9, 198, 17, 81, 76, 48, 19, 148, 20, 0, 14, 139, 16, 18, 195, 166, 20, 5, 14, 4, 5, 14, 20, 20, 10, 199, 72, 84, 15, 73, 64, 71, 20, 20, 10, 199, 21, 33, 77, 37, 64, 71, 20, 20, 0, 30, 68, 24, 244, 131, 20, 81, 112, 34, 87, 15, 4, 63, 35, 6, 87, 57, 116, 12, 34, 0, 81, 109, 97, 106, 101, 117, 114, 101, 32, 11, 200, 97, 147, 15, 29, 32, 70, 21, 32, 20, 11, 200, 96, 84, 143, 29, 32, 70, 21, 32, 20, 11, 200, 81, 148, 15, 29, 32, 70, 21, 32, 20, 11, 200, 64, 85, 9, 80, 147, 206, 21, 32, 20, 11, 200, 48, 149, 15, 29, 32, 70, 21, 32, 20, 7, 196, 81, 148, 143, 48, 20, 0, 16, 205, 84, 66, 210, 101, 53, 1, 48, 194, 83, 5, 66, 79, 56, 20, 9, 198, 45, 32, 68, 76, 84, 137, 20, 12, 201, 81, 32, 78, 76, 49, 78, 16, 83, 148, 20, 0, 9, 198, 24, 147, 1, 52, 83, 148, 20, 13, 202, 76, 50, 1, 48, 37, 82, 29, 64, 71, 20, 20, 0, 12, 201, 36, 212, 18, 61, 98, 83, 5, 67, 210, 20, 9, 198, 72, 83, 65, 56, 83, 147, 20, 9, 198, 36, 225, 15, 48, 83, 147, 20, 9, 198, 20, 195, 203, 88, 83, 147, 20, 9, 198, 49, 83, 73, 56, 19, 147, 20, 0, 7, 196, 77, 85, 21, 72, 20, 11, 200, 5, 85, 15, 44, 192, 86, 21, 32, 20, 9, 198, 77, 144, 129, 72, 149, 0, 20, 9, 198, 52, 81, 193, 8, 149, 0, 20, 9, 198, 44, 147, 15, 8, 149, 0, 20, 7, 196, 53, 84, 201, 44, 20, 7, 196, 4, 116, 129, 24, 20, 0, 12, 201, 81, 80, 133, 72, 181, 76, 61, 49, 64, 20, 12, 201, 64, 20, 129, 16, 83, 148, 61, 49, 64, 20, 12, 201, 5, 98, 84, 4, 210, 78, 61, 49, 64, 20, 0, 11, 200, 77, 68, 143, 8, 244, 203, 61, 0, 20, 9, 198, 8, 243, 77, 21, 50, 64, 20, 12, 201, 81, 32, 78, 76, 49, 78, 16, 83, 147, 20, 9, 198, 44, 20, 132, 36, 19, 0, 20, 0, 9, 134, 6, 1, 13, 195, 184, 19, 20, 11, 136, 4, 18, 195, 166, 19, 9, 14, 5, 20, 10, 199, 44, 243, 12, 37, 50, 79, 56, 20, 12, 201, 36, 211, 79, 72, 19, 9, 80, 85, 0, 20, 10, 199, 72, 81, 197, 56, 84, 133, 72, 20, 10, 199, 72, 81, 5, 24, 147, 133, 72, 20, 10, 199, 72, 80, 83, 77, 83, 69, 72, 20, 10, 199, 44, 243, 210, 16, 147, 133, 72, 20, 10, 199, 104, 20, 137, 77, 66, 83, 44, 20, 10, 199, 88, 84, 137, 77, 66, 83, 44, 20, 10, 199, 77, 147, 80, 5, 66, 83, 44, 20, 10, 199, 76, 245, 138, 21, 66, 83, 44, 20, 10, 199, 65, 35, 198, 21, 66, 83, 44, 20, 10, 199, 64, 20, 211, 37, 98, 83, 44, 20, 10, 199, 61, 51, 65, 56, 226, 83, 44, 20, 10, 199, 56, 85, 82, 61, 66, 83, 44, 20, 10, 199, 56, 20, 139, 61, 66, 83, 44, 20, 10, 199, 52, 19, 4, 37, 98, 83, 44, 20, 10, 199, 52, 17, 206, 21, 66, 83, 44, 20, 10, 199, 33, 148, 14, 61, 66, 83, 44, 20, 10, 199, 32, 84, 141, 21, 66, 83, 44, 20, 10, 199, 20, 115, 201, 77, 66, 83, 44, 20, 10, 199, 17, 147, 129, 77, 66, 83, 44, 20, 10, 199, 8, 19, 5, 5, 34, 83, 44, 20, 0, 7, 196, 65, 34, 79, 72, 20, 11, 200, 16, 21, 1, 52, 21, 9, 76, 176, 20, 9, 198, 52, 20, 207, 56, 149, 0, 20, 7, 196, 5, 67, 206, 36, 20, 7, 196, 4, 229, 9, 44, 20, 9, 198, 60, 35, 9, 28, 21, 0, 20, 7, 196, 28, 19, 1, 56, 21, 0, 8, 197, 24, 19, 148, 60, 208, 20, 8, 197, 72, 81, 5, 72, 144, 20, 8, 197, 44, 243, 147, 84, 208, 20, 9, 198, 64, 243, 25, 24, 243, 137, 20, 19, 70, 64, 84, 5, 72, 243, 137, 48, 36, 48, 13, 34, 6, 39, 50, 37, 0, 20, 8, 197, 16, 84, 15, 56, 144, 20, 0, 13, 202, 56, 85, 82, 61, 4, 217, 44, 243, 15, 28, 20, 9, 198, 8, 20, 213, 56, 148, 212, 20, 9, 198, 45, 84, 129, 80, 83, 0, 20, 13, 202, 81, 32, 78, 76, 194, 84, 80, 84, 133, 72, 20, 13, 202, 77, 3, 206, 80, 19, 137, 77, 66, 83, 44, 20, 13, 202, 72, 84, 208, 37, 32, 84, 61, 34, 83, 44, 20, 13, 202, 44, 243, 66, 36, 224, 84, 61, 34, 83, 44, 20, 13, 202, 32, 83, 9, 60, 49, 78, 81, 34, 83, 44, 20, 0, 29, 75, 44, 243, 134, 37, 35, 65, 56, 65, 82, 56, 80, 49, 112, 50, 81, 36, 34, 63, 6, 108, 50, 70, 106, 20, 50, 13, 0, 13, 138, 7, 12, 1, 13, 15, 21, 18, 195, 184, 19, 20, 12, 137, 19, 15, 21, 20, 5, 14, 195, 184, 18, 20, 12, 137, 13, 5, 4, 1, 12, 10, 195, 184, 18, 20, 10, 199, 49, 82, 211, 5, 66, 79, 56, 20, 10, 199, 36, 210, 84, 5, 66, 79, 56, 20, 10, 199, 24, 195, 212, 5, 66, 79, 56, 20, 10, 199, 16, 84, 197, 73, 66, 79, 56, 20, 10, 199, 4, 114, 84, 5, 66, 79, 56, 20, 12, 201, 77, 1, 67, 36, 19, 9, 80, 85, 0, 20, 12, 201, 64, 244, 21, 48, 20, 137, 80, 85, 0, 20, 12, 201, 56, 85, 84, 72, 19, 9, 80, 85, 0, 20, 12, 201, 53, 85, 1, 8, 147, 9, 80, 85, 0, 20, 10, 199, 81, 32, 75, 5, 52, 197, 72, 20, 10, 199, 44, 243, 134, 61, 35, 69, 72, 20, 10, 199, 44, 243, 134, 37, 35, 69, 72, 20, 10, 199, 8, 81, 18, 4, 113, 82, 36, 20, 10, 199, 52, 148, 212, 72, 242, 83, 44, 20, 10, 199, 44, 21, 75, 5, 50, 83, 44, 20, 10, 199, 4, 34, 200, 5, 50, 83, 44, 20, 10, 199, 4, 208, 129, 77, 48, 68, 20, 20, 0, 9, 134, 16, 15, 19, 195, 184, 18, 20, 9, 134, 13, 1, 12, 195, 184, 18, 20, 9, 198, 77, 64, 84, 37, 53, 0, 20, 9, 198, 21, 50, 193, 17, 35, 206, 20, 11, 200, 81, 32, 85, 52, 21, 9, 76, 176, 20, 11, 200, 65, 35, 203, 48, 149, 9, 76, 176, 20, 11, 200, 52, 21, 5, 52, 21, 9, 76, 176, 20, 11, 200, 16, 144, 75, 72, 149, 9, 76, 176, 20, 11, 200, 5, 34, 84, 52, 85, 9, 76, 176, 20, 11, 200, 4, 227, 210, 20, 181, 9, 76, 176, 20, 12, 201, 76, 19, 77, 20, 228, 213, 72, 149, 77, 20, 11, 200, 56, 81, 204, 36, 113, 78, 12, 80, 20, 7, 196, 45, 35, 193, 80, 20, 7, 196, 4, 115, 129, 80, 20, 0, 10, 135, 6, 15, 18, 8, 195, 184, 18, 20, 10, 135, 1, 13, 1, 20, 195, 184, 18, 20, 9, 198, 77, 69, 84, 80, 84, 137, 20, 9, 198, 8, 84, 133, 16, 84, 137, 20, 9, 198, 80, 131, 205, 37, 51, 69, 20, 9, 198, 41, 81, 1, 37, 51, 69, 20, 9, 198, 5, 34, 193, 37, 51, 69, 20, 10, 69, 8, 18, 76, 21, 144, 21, 0, 10, 0, 8, 198, 64, 84, 137, 44, 243, 128, 9, 198, 77, 147, 139, 72, 243, 128, 20, 9, 198, 52, 81, 193, 24, 243, 128, 20, 13, 202, 64, 20, 148, 36, 50, 80, 5, 66, 79, 56, 20, 13, 202, 44, 243, 147, 80, 83, 12, 5, 66, 79, 56, 20, 13, 202, 36, 229, 5, 73, 5, 78, 45, 66, 79, 56, 20, 15, 204, 44, 243, 147, 81, 37, 75, 80, 149, 137, 80, 85, 0, 20, 9, 198, 77, 84, 9, 57, 83, 64, 20, 17, 70, 60, 147, 19, 44, 147, 128, 112, 57, 55, 87, 49, 107, 50, 0, 20, 9, 198, 60, 97, 137, 12, 147, 128, 20, 13, 202, 88, 147, 204, 36, 226, 83, 80, 147, 132, 20, 20, 9, 198, 64, 84, 147, 36, 19, 128, 20, 16, 70, 33, 99, 210, 16, 19, 128, 82, 112, 70, 6, 108, 50, 0, 20, 0, 12, 137, 19, 16, 5, 4, 9, 20, 195, 184, 18, 20, 12, 137, 1, 14, 14, 15, 14, 3, 195, 184, 18, 20, 9, 198, 48, 85, 133, 72, 147, 135, 20, 9, 198, 48, 21, 133, 72, 147, 135, 20, 9, 198, 4, 65, 5, 72, 147, 135, 20, 10, 199, 64, 243, 25, 56, 243, 73, 20, 20, 10, 199, 21, 96, 78, 28, 83, 9, 20, 20, 10, 199, 53, 148, 212, 21, 34, 85, 52, 20, 10, 199, 45, 34, 84, 21, 34, 85, 52, 20, 10, 199, 44, 243, 131, 36, 194, 85, 52, 20, 10, 199, 16, 85, 84, 21, 34, 85, 52, 20, 10, 199, 88, 81, 197, 80, 16, 137, 48, 20, 0, 13, 138, 18, 5, 20, 15, 21, 3, 8, 195, 184, 18, 20, 13, 138, 16, 1, 19, 20, 9, 3, 8, 195, 184, 18, 20, 13, 138, 8, 5, 12, 19, 9, 14, 7, 195, 184, 18, 20, 7, 196, 64, 243, 5, 80, 20, 7, 196, 64, 19, 5, 80, 20, 9, 198, 12, 83, 12, 37, 53, 0, 20, 9, 198, 80, 20, 5, 81, 49, 82, 20, 9, 198, 72, 85, 129, 49, 81, 82, 20, 7, 196, 88, 148, 201, 80, 20, 7, 196, 76, 19, 1, 80, 20, 13, 72, 64, 144, 195, 4, 66, 76, 49, 144, 21, 0, 10, 0, 14, 139, 22, 5, 14, 20, 9, 12, 1, 20, 195, 184, 18, 20, 14, 139, 8, 25, 16, 14, 15, 20, 9, 19, 195, 184, 18, 20, 12, 201, 88, 147, 132, 36, 176, 84, 36, 243, 128, 20, 12, 201, 77, 80, 140, 36, 208, 84, 36, 243, 128, 20, 12, 201, 76, 81, 210, 20, 112, 84, 36, 243, 128, 20, 12, 201, 72, 84, 208, 37, 32, 84, 36, 243, 128, 20, 12, 201, 72, 83, 1, 45, 48, 84, 36, 243, 128, 20, 12, 201, 72, 82, 204, 4, 208, 84, 36, 243, 128, 20, 12, 201, 72, 82, 70, 36, 176, 84, 36, 243, 128, 20, 12, 201, 72, 81, 143, 72, 208, 84, 36, 243, 128, 20, 12, 201, 72, 80, 76, 37, 48, 84, 36, 243, 128, 20, 12, 201, 65, 80, 140, 36, 176, 84, 36, 243, 128, 20, 12, 201, 65, 35, 214, 60, 176, 84, 36, 243, 128, 20, 12, 201, 64, 84, 141, 85, 64, 84, 36, 243, 128, 20, 12, 201, 44, 244, 144, 61, 32, 84, 36, 243, 128, 20, 12, 201, 44, 243, 138, 84, 112, 84, 36, 243, 128, 20, 12, 201, 44, 243, 12, 60, 176, 84, 36, 243, 128, 20, 12, 201, 36, 228, 201, 57, 80, 84, 36, 243, 128, 20, 12, 201, 36, 225, 143, 72, 208, 84, 36, 243, 128, 20, 12, 201, 36, 212, 12, 36, 176, 84, 36, 243, 128, 20, 12, 201, 36, 211, 73, 29, 32, 84, 36, 243, 128, 20, 12, 201, 32, 16, 137, 81, 80, 84, 36, 243, 128, 20, 12, 201, 29, 32, 86, 37, 64, 84, 36, 243, 128, 20, 12, 201, 24, 197, 75, 81, 80, 84, 36, 243, 128, 20, 12, 201, 24, 16, 146, 36, 176, 84, 36, 243, 128, 20, 12, 201, 17, 148, 198, 84, 226, 212, 36, 243, 128, 20, 12, 201, 17, 84, 12, 36, 176, 84, 36, 243, 128, 20, 12, 201, 16, 84, 208, 21, 32, 84, 36, 243, 128, 20, 12, 201, 16, 84, 18, 37, 96, 84, 36, 243, 128, 20, 12, 201, 16, 83, 65, 72, 176, 84, 36, 243, 128, 20, 12, 201, 16, 82, 204, 5, 32, 84, 36, 243, 128, 20, 12, 201, 16, 82, 204, 4, 208, 84, 36, 243, 128, 20, 12, 201, 16, 81, 143, 72, 208, 84, 36, 243, 128, 20, 12, 201, 16, 81, 140, 61, 32, 84, 36, 243, 128, 20, 12, 201, 5, 52, 207, 12, 144, 84, 36, 243, 128, 20, 12, 201, 5, 4, 12, 36, 176, 84, 36, 243, 128, 20, 12, 201, 4, 178, 204, 4, 208, 84, 36, 243, 128, 20, 12, 201, 4, 97, 137, 72, 208, 84, 36, 243, 128, 20, 16, 205, 16, 83, 132, 72, 242, 210, 60, 227, 204, 60, 114, 83, 44, 20, 12, 201, 16, 84, 201, 16, 84, 129, 81, 83, 64, 20, 12, 201, 80, 84, 212, 36, 211, 206, 37, 83, 64, 20, 12, 201, 44, 243, 21, 52, 32, 82, 37, 83, 64, 20, 12, 201, 44, 19, 5, 56, 64, 82, 37, 83, 64, 20, 12, 201, 41, 81, 207, 76, 192, 86, 36, 83, 128, 20, 8, 197, 36, 229, 5, 57, 48, 20, 0, 15, 140, 4, 9, 19, 20, 18, 9, 2, 21, 20, 195, 184, 18, 20, 17, 70, 48, 144, 73, 76, 243, 128, 55, 37, 108, 87, 6, 112, 66, 0, 20, 17, 70, 8, 195, 213, 76, 243, 128, 69, 55, 40, 87, 6, 112, 66, 0, 20, 9, 198, 60, 181, 15, 28, 243, 128, 20, 9, 198, 64, 243, 25, 24, 243, 128, 20, 12, 201, 77, 84, 208, 20, 225, 5, 72, 147, 135, 20, 12, 201, 72, 80, 75, 80, 149, 133, 72, 147, 135, 20, 12, 201, 44, 243, 77, 20, 229, 5, 72, 147, 135, 20, 12, 201, 36, 225, 7, 72, 21, 133, 72, 147, 135, 20, 12, 201, 16, 148, 208, 21, 33, 197, 72, 147, 135, 20, 12, 201, 16, 148, 203, 60, 229, 5, 72, 147, 135, 20, 13, 202, 44, 243, 80, 61, 50, 84, 36, 243, 133, 48, 20, 9, 198, 64, 85, 9, 16, 147, 128, 20, 9, 198, 5, 68, 143, 64, 147, 128, 20, 9, 198, 44, 20, 21, 12, 147, 128, 20, 9, 198, 4, 100, 137, 44, 19, 128, 20, 9, 198, 65, 148, 143, 52, 19, 128, 21, 9, 198, 9, 32, 72, 52, 19, 128, 21, 0, 12, 201, 64, 242, 78, 80, 147, 12, 37, 53, 0, 20, 12, 137, 11, 22, 195, 166, 18, 21, 12, 5, 18, 20, 6, 195, 72, 83, 204, 20, 10, 199, 52, 17, 206, 21, 50, 85, 52, 20, 10, 199, 20, 180, 208, 48, 144, 201, 80, 20, 10, 199, 16, 144, 77, 21, 68, 129, 48, 20, 0, 15, 204, 81, 32, 78, 76, 98, 71, 85, 32, 84, 36, 243, 128, 20, 15, 204, 64, 84, 147, 60, 226, 70, 36, 176, 84, 36, 243, 128, 20, 15, 204, 52, 21, 5, 72, 144, 76, 37, 48, 84, 36, 243, 128, 20, 15, 204, 45, 38, 83, 80, 19, 12, 37, 48, 84, 36, 243, 128, 20, 15, 204, 16, 149, 133, 73, 50, 70, 36, 176, 84, 36, 243, 128, 20, 15, 204, 16, 145, 134, 21, 33, 78, 80, 144, 84, 36, 243, 128, 20, 15, 204, 5, 85, 5, 57, 66, 70, 36, 176, 84, 36, 243, 128, 20, 15, 140, 19, 21, 22, 5, 18, 195, 166, 14, 9, 20, 5, 20, 20, 7, 196, 80, 20, 133, 72, 20, 9, 198, 80, 16, 149, 37, 49, 82, 20, 9, 198, 73, 149, 13, 37, 49, 82, 20, 9, 198, 36, 228, 201, 57, 81, 82, 20, 9, 198, 5, 34, 193, 37, 49, 82, 20, 0, 9, 198, 77, 147, 66, 36, 244, 197, 20, 9, 198, 5, 3, 212, 20, 244, 197, 20, 9, 198, 16, 83, 65, 28, 241, 201, 20, 12, 201, 36, 229, 5, 72, 197, 68, 37, 83, 64, 20, 9, 198, 4, 229, 15, 57, 147, 73, 20, 8, 197, 77, 65, 82, 36, 192, 20, 6, 195, 64, 147, 206, 20, 8, 197, 52, 84, 137, 4, 224, 21, 8, 197, 77, 2, 82, 4, 192, 20, 0, 12, 201, 81, 32, 86, 21, 36, 197, 72, 147, 135, 20, 12, 201, 77, 64, 84, 36, 243, 133, 72, 147, 135, 20, 12, 201, 76, 81, 205, 20, 229, 5, 72, 147, 135, 20, 12, 201, 72, 83, 1, 80, 149, 133, 72, 147, 135, 20, 12, 201, 64, 145, 205, 20, 229, 5, 72, 147, 135, 20, 12, 201, 52, 243, 137, 80, 244, 133, 72, 147, 135, 20, 12, 201, 44, 243, 134, 84, 225, 5, 72, 147, 135, 20, 12, 201, 16, 81, 197, 56, 84, 133, 72, 147, 135, 20, 12, 201, 8, 241, 211, 80, 21, 133, 72, 147, 135, 20, 12, 201, 8, 147, 199, 72, 17, 133, 72, 147, 135, 20, 12, 201, 4, 48, 197, 48, 84, 133, 72, 147, 135, 20, 9, 198, 52, 20, 203, 36, 225, 76, 20, 9, 198, 37, 52, 129, 20, 194, 84, 20, 0, 27, 67, 73, 80, 128, 51, 6, 111, 69, 15, 112, 15, 87, 70, 6, 111, 69, 0, 82, 111, 103, 32, 115, 116, 117, 98, 32, 18, 207, 81, 32, 78, 77, 53, 66, 77, 64, 78, 80, 144, 84, 36, 243, 128, 20, 10, 199, 72, 21, 9, 32, 16, 133, 72, 20, 10, 199, 24, 82, 140, 4, 117, 9, 28, 20, 10, 199, 80, 244, 142, 37, 34, 83, 44, 20, 10, 199, 77, 147, 143, 65, 66, 83, 44, 20, 10, 199, 76, 243, 9, 77, 66, 83, 44, 20, 10, 199, 76, 82, 212, 21, 34, 83, 44, 20, 10, 199, 57, 81, 9, 77, 66, 83, 44, 20, 10, 199, 45, 84, 147, 61, 34, 83, 44, 20, 10, 199, 20, 179, 5, 45, 66, 83, 44, 20, 10, 199, 17, 148, 198, 5, 66, 83, 44, 20, 10, 199, 8, 20, 130, 5, 34, 83, 44, 20, 10, 199, 5, 67, 1, 57, 66, 83, 44, 20, 10, 199, 49, 83, 132, 20, 228, 197, 72, 20, 10, 199, 24, 82, 140, 4, 117, 9, 28, 20, 10, 199, 52, 19, 135, 20, 176, 78, 80, 20, 0, 28, 68, 16, 84, 133, 76, 70, 36, 13, 87, 15, 49, 82, 110, 6, 47, 36, 34, 0, 81, 107, 118, 97, 114, 116, 101, 114, 32, 9, 198, 72, 83, 9, 28, 147, 206, 20, 13, 138, 16, 18, 195, 166, 20, 5, 14, 4, 5, 18, 20, 7, 196, 4, 212, 5, 72, 20, 11, 200, 88, 81, 197, 80, 20, 137, 4, 224, 20, 7, 196, 40, 20, 1, 56, 20, 11, 200, 20, 53, 65, 16, 244, 137, 4, 224, 20, 9, 198, 76, 84, 135, 20, 229, 0, 20, 7, 196, 33, 84, 193, 72, 20, 11, 200, 37, 36, 129, 80, 147, 206, 4, 192, 20, 7, 196, 40, 84, 133, 76, 76, 13, 68, 16, 84, 133, 76, 70, 107, 12, 112, 87, 0, 72, 12, 3, 95, 49, 15, 81, 116, 34, 87, 70, 106, 0, 0, 8, 197, 28, 83, 149, 36, 224, 20, 9, 198, 65, 148, 143, 52, 19, 137, 20, 9, 198, 44, 18, 207, 24, 243, 137, 20, 8, 197, 36, 225, 9, 4, 224, 20, 8, 197, 8, 21, 137, 4, 224, 21, 12, 137, 16, 18, 195, 166, 7, 14, 1, 14, 20, 20, 0, 15, 66, 25, 128, 81, 112, 36, 79, 87, 36, 63, 48, 13, 55, 0, 9, 198, 80, 147, 139, 81, 84, 128, 20, 9, 198, 4, 113, 78, 81, 84, 128, 20, 13, 202, 76, 179, 204, 20, 209, 83, 80, 84, 133, 72, 20, 13, 202, 77, 84, 146, 20, 19, 9, 77, 66, 83, 44, 20, 13, 202, 77, 65, 82, 20, 244, 203, 61, 2, 83, 44, 20, 13, 202, 56, 85, 84, 72, 19, 9, 77, 66, 83, 44, 20, 13, 202, 56, 21, 21, 72, 19, 9, 77, 66, 83, 44, 20, 13, 202, 48, 144, 133, 72, 19, 9, 77, 66, 83, 44, 20, 13, 202, 44, 243, 139, 72, 85, 9, 77, 66, 83, 44, 20, 13, 202, 44, 243, 80, 36, 192, 84, 61, 34, 83, 44, 20, 13, 202, 44, 243, 15, 72, 147, 69, 81, 34, 83, 44, 20, 13, 202, 40, 245, 82, 56, 19, 9, 77, 66, 83, 44, 20, 13, 202, 24, 192, 71, 20, 195, 1, 57, 66, 83, 44, 20, 13, 202, 9, 84, 133, 5, 82, 210, 5, 66, 83, 44, 20, 13, 202, 8, 83, 12, 21, 68, 137, 77, 66, 83, 44, 20, 13, 202, 4, 36, 207, 49, 85, 9, 77, 66, 83, 44, 20, 9, 198, 52, 146, 210, 60, 194, 84, 20, 9, 198, 44, 243, 80, 61, 50, 84, 20, 0, 10, 199, 44, 243, 150, 20, 181, 15, 72, 20, 10, 199, 44, 243, 148, 4, 181, 15, 72, 20, 12, 201, 77, 80, 147, 80, 149, 21, 80, 147, 206, 20, 12, 201, 65, 35, 203, 48, 19, 65, 80, 147, 206, 20, 12, 201, 44, 20, 9, 81, 83, 1, 80, 147, 206, 20, 12, 201, 5, 52, 201, 52, 147, 1, 80, 147, 206, 20, 12, 201, 4, 208, 76, 28, 19, 65, 80, 147, 206, 20, 12, 201, 4, 178, 213, 53, 83, 1, 80, 147, 206, 20, 10, 199, 56, 243, 65, 16, 148, 197, 72, 20, 10, 199, 4, 194, 193, 48, 148, 197, 72, 20, 10, 199, 77, 80, 147, 60, 226, 83, 44, 20, 10, 199, 77, 1, 75, 84, 192, 78, 80, 20, 10, 67, 16, 145, 192, 70, 35, 57, 0, 76, 10, 3, 226, 130, 172, 36, 40, 34, 39, 0, 0, 17, 142, 14, 195, 166, 19, 20, 11, 15, 13, 13, 1, 14, 4, 5, 18, 20, 11, 200, 64, 20, 129, 29, 80, 89, 4, 224, 20, 0, 8, 197, 76, 86, 9, 77, 64, 20, 8, 197, 41, 84, 137, 77, 64, 20, 8, 197, 64, 147, 206, 21, 32, 20, 16, 205, 76, 83, 147, 5, 66, 79, 56, 19, 9, 77, 66, 83, 44, 20, 8, 197, 24, 19, 12, 37, 64, 20, 8, 197, 36, 226, 84, 5, 32, 20, 8, 197, 32, 82, 212, 5, 32, 20, 9, 198, 20, 228, 201, 48, 17, 197, 20, 11, 70, 32, 243, 69, 64, 17, 197, 21, 0, 10, 0, 22, 67, 48, 145, 197, 55, 37, 13, 15, 49, 39, 87, 70, 13, 0, 81, 107, 111, 115, 116, 101, 32, 17, 67, 48, 145, 197, 55, 37, 13, 15, 87, 112, 0, 81, 115, 195, 165, 32, 9, 198, 9, 35, 203, 4, 65, 64, 20, 12, 137, 16, 18, 195, 166, 7, 14, 1, 14, 19, 20, 6, 195, 64, 17, 197, 20, 0, 10, 199, 28, 84, 141, 4, 226, 83, 80, 20, 12, 201, 52, 19, 137, 65, 83, 1, 80, 147, 206, 20, 10, 199, 89, 84, 132, 21, 34, 78, 28, 20, 10, 199, 80, 245, 80, 21, 34, 78, 28, 20, 10, 199, 53, 83, 132, 21, 34, 78, 28, 20, 10, 199, 44, 16, 200, 21, 34, 78, 28, 20, 10, 199, 25, 83, 132, 21, 34, 78, 28, 20, 10, 199, 21, 35, 196, 21, 34, 78, 28, 20, 10, 199, 20, 66, 84, 21, 34, 78, 28, 20, 10, 199, 16, 146, 212, 21, 34, 78, 28, 20, 9, 198, 80, 82, 83, 80, 148, 203, 20, 9, 198, 61, 33, 193, 56, 148, 203, 20, 9, 198, 44, 84, 149, 8, 148, 203, 20, 9, 198, 16, 82, 83, 80, 148, 203, 20, 9, 198, 12, 20, 137, 8, 148, 203, 20, 10, 199, 5, 53, 18, 60, 227, 205, 36, 20, 10, 199, 5, 32, 137, 81, 32, 71, 20, 20, 10, 67, 40, 81, 192, 57, 35, 37, 0, 76, 0, 29, 68, 12, 243, 133, 100, 6, 49, 39, 40, 50, 37, 15, 6, 35, 57, 55, 106, 50, 70, 0, 81, 105, 115, 108, 97, 110, 100, 32, 11, 200, 72, 85, 129, 56, 50, 9, 77, 64, 20, 11, 200, 9, 32, 84, 76, 50, 9, 77, 64, 20, 11, 200, 36, 229, 5, 57, 50, 86, 21, 32, 20, 11, 200, 52, 20, 147, 44, 19, 12, 5, 64, 20, 9, 198, 12, 83, 12, 60, 96, 78, 21, 10, 3, 95, 50, 15, 108, 50, 13, 50, 0, 0, 12, 201, 60, 213, 133, 45, 51, 5, 48, 145, 192, 20, 12, 201, 48, 19, 132, 24, 198, 71, 80, 145, 192, 20, 8, 197, 76, 179, 204, 5, 32, 20, 8, 197, 28, 145, 193, 57, 64, 20, 0, 6, 194, 12, 240, 17, 42, 9, 198, 52, 20, 203, 36, 225, 64, 20, 13, 202, 77, 68, 149, 45, 69, 82, 4, 194, 83, 80, 20, 13, 202, 36, 225, 21, 77, 68, 137, 4, 194, 83, 80, 20, 13, 202, 88, 17, 193, 8, 243, 132, 21, 34, 78, 28, 20, 13, 202, 8, 19, 132, 21, 35, 204, 21, 34, 78, 28, 20, 12, 137, 19, 1, 13, 8, 195, 184, 18, 9, 7, 20, 9, 198, 4, 228, 197, 48, 145, 192, 20, 12, 201, 77, 147, 12, 60, 114, 83, 80, 148, 203, 20, 12, 201, 64, 243, 9, 80, 243, 15, 28, 148, 203, 20, 12, 201, 21, 50, 193, 80, 243, 15, 28, 148, 203, 20, 9, 198, 4, 225, 204, 60, 98, 76, 20, 9, 198, 20, 210, 84, 80, 83, 148, 20, 9, 198, 53, 148, 137, 4, 65, 64, 20, 9, 198, 76, 147, 85, 48, 19, 148, 20, 13, 70, 41, 81, 197, 52, 83, 148, 21, 102, 114, 0, 10, 0, 12, 201, 44, 243, 77, 84, 226, 75, 5, 67, 210, 20, 10, 199, 64, 197, 82, 4, 194, 83, 80, 20, 10, 199, 29, 82, 84, 5, 34, 83, 80, 20, 10, 199, 12, 83, 66, 4, 194, 83, 80, 20, 13, 138, 25, 14, 11, 22, 195, 166, 18, 4, 9, 7, 20, 13, 138, 20, 18, 15, 22, 195, 166, 18, 4, 9, 7, 20, 13, 138, 16, 195, 165, 12, 9, 4, 5, 12, 9, 7, 20, 13, 138, 12, 5, 20, 6, 195, 166, 18, 4, 9, 7, 20, 9, 198, 76, 83, 73, 80, 148, 203, 20, 9, 198, 4, 224, 82, 44, 148, 203, 20, 9, 198, 16, 146, 203, 20, 66, 75, 20, 0, 9, 198, 72, 17, 9, 5, 67, 210, 20, 11, 200, 81, 32, 78, 77, 3, 206, 21, 32, 20, 11, 200, 72, 83, 79, 57, 53, 18, 21, 32, 20, 7, 196, 28, 148, 133, 72, 20, 11, 200, 16, 83, 79, 57, 53, 18, 21, 32, 20, 14, 139, 19, 20, 9, 12, 6, 195, 166, 18, 4, 9, 7, 20, 14, 139, 15, 13, 19, 20, 195, 184, 4, 5, 12, 9, 7, 20, 14, 139, 8, 21, 19, 11, 22, 195, 166, 18, 4, 9, 7, 20, 14, 139, 7, 12, 15, 18, 22, 195, 166, 18, 4, 9, 7, 20, 14, 139, 5, 12, 19, 11, 22, 195, 166, 18, 4, 9, 7, 20, 14, 139, 1, 14, 19, 20, 195, 184, 4, 5, 12, 9, 7, 20, 9, 198, 56, 81, 210, 60, 145, 0, 20, 9, 198, 81, 84, 141, 4, 194, 78, 20, 7, 196, 76, 244, 129, 56, 20, 7, 196, 8, 83, 137, 56, 20, 11, 200, 16, 84, 195, 20, 225, 5, 57, 64, 20, 7, 196, 44, 244, 129, 56, 21, 11, 200, 44, 243, 131, 21, 37, 1, 57, 64, 20, 11, 200, 44, 243, 66, 5, 69, 1, 57, 64, 20, 11, 200, 4, 194, 77, 20, 229, 1, 57, 64, 20, 0, 8, 197, 16, 144, 76, 60, 112, 20, 8, 197, 44, 16, 137, 56, 80, 20, 8, 197, 41, 83, 5, 72, 144, 20, 15, 140, 13, 195, 166, 18, 11, 22, 195, 166, 18, 4, 9, 7, 20, 12, 201, 44, 81, 19, 60, 211, 69, 48, 145, 192, 20, 12, 201, 29, 81, 4, 60, 211, 69, 48, 145, 192, 20, 12, 201, 24, 244, 142, 20, 211, 69, 48, 145, 192, 20, 15, 204, 64, 20, 148, 36, 181, 76, 5, 34, 83, 80, 148, 203, 20, 15, 204, 56, 243, 139, 60, 225, 143, 72, 210, 83, 80, 148, 203, 20, 8, 197, 52, 19, 137, 76, 176, 20, 9, 198, 64, 197, 84, 60, 226, 69, 20, 16, 69, 76, 19, 1, 52, 144, 87, 108, 55, 6, 108, 63, 37, 0, 20, 8, 197, 52, 85, 18, 36, 176, 20, 8, 197, 64, 243, 9, 12, 80, 20, 8, 197, 64, 243, 65, 16, 80, 20, 0, 9, 198, 61, 5, 9, 52, 148, 212, 20, 9, 198, 32, 21, 129, 72, 148, 212, 20, 9, 198, 4, 181, 129, 72, 148, 212, 20, 12, 137, 195, 166, 4, 18, 21, 5, 12, 9, 7, 20, 16, 141, 22, 5, 12, 1, 14, 19, 20, 195, 166, 14, 4, 9, 7, 20, 12, 201, 88, 83, 133, 72, 243, 15, 28, 148, 203, 20, 12, 201, 61, 35, 137, 80, 243, 15, 28, 148, 203, 20, 12, 201, 60, 67, 206, 80, 243, 15, 28, 148, 203, 20, 12, 201, 60, 49, 65, 56, 243, 15, 28, 148, 203, 20, 12, 201, 52, 148, 193, 57, 68, 143, 64, 148, 203, 20, 12, 201, 33, 145, 18, 61, 53, 1, 80, 148, 203, 20, 12, 201, 28, 192, 67, 36, 243, 15, 28, 148, 203, 20, 12, 201, 24, 147, 1, 57, 68, 143, 64, 148, 203, 20, 12, 201, 24, 83, 73, 56, 243, 15, 28, 148, 203, 20, 9, 198, 5, 49, 80, 80, 146, 192, 20, 0, 22, 71, 64, 244, 212, 36, 195, 15, 56, 48, 4, 112, 87, 70, 37, 55, 57, 6, 112, 66, 0, 20, 10, 199, 76, 82, 212, 36, 243, 133, 72, 20, 10, 199, 5, 85, 15, 72, 148, 197, 72, 20, 10, 199, 29, 34, 78, 4, 117, 9, 28, 20, 9, 198, 28, 83, 89, 80, 194, 71, 20, 9, 198, 20, 225, 143, 48, 66, 71, 20, 10, 199, 77, 147, 148, 21, 66, 83, 44, 20, 10, 199, 77, 83, 142, 37, 66, 83, 44, 20, 10, 199, 76, 242, 210, 5, 66, 83, 44, 20, 10, 199, 76, 83, 65, 57, 66, 83, 44, 20, 10, 199, 72, 243, 65, 57, 66, 83, 44, 20, 10, 199, 65, 54, 75, 61, 66, 83, 44, 20, 10, 199, 61, 32, 84, 61, 34, 83, 44, 20, 10, 199, 52, 21, 82, 37, 66, 83, 44, 20, 10, 199, 52, 19, 201, 77, 66, 83, 44, 20, 10, 199, 49, 147, 70, 5, 66, 83, 44, 20, 10, 199, 48, 241, 201, 77, 66, 83, 44, 20, 10, 199, 44, 194, 77, 5, 66, 83, 44, 20, 10, 199, 21, 96, 83, 61, 34, 83, 44, 20, 10, 199, 20, 179, 9, 65, 66, 83, 44, 20, 10, 199, 16, 241, 205, 5, 66, 83, 44, 20, 10, 199, 16, 84, 208, 61, 66, 83, 44, 20, 10, 199, 5, 37, 9, 77, 66, 83, 44, 20, 10, 199, 5, 35, 205, 5, 66, 83, 44, 20, 12, 201, 28, 19, 12, 37, 83, 79, 96, 145, 0, 20, 10, 199, 65, 32, 71, 52, 21, 9, 44, 20, 10, 199, 64, 244, 142, 60, 116, 129, 24, 20, 10, 199, 29, 34, 78, 4, 117, 9, 28, 20, 0, 9, 134, 20, 18, 9, 195, 184, 18, 20, 11, 200, 52, 85, 1, 48, 197, 82, 28, 144, 20, 9, 198, 64, 83, 148, 4, 115, 206, 20, 7, 196, 5, 35, 69, 72, 20, 14, 139, 22, 9, 4, 20, 12, 195, 184, 6, 20, 9, 7, 20, 18, 143, 16, 5, 20, 5, 18, 1, 14, 19, 20, 195, 166, 14, 4, 9, 7, 20, 14, 139, 1, 14, 6, 195, 166, 7, 20, 5, 12, 9, 7, 20, 11, 200, 80, 83, 5, 52, 21, 9, 76, 176, 20, 11, 200, 76, 241, 15, 52, 149, 9, 76, 176, 20, 11, 200, 64, 225, 85, 52, 21, 9, 76, 176, 20, 11, 200, 52, 243, 143, 48, 149, 9, 76, 176, 20, 11, 200, 52, 85, 15, 57, 147, 73, 76, 176, 20, 11, 200, 29, 147, 78, 5, 53, 9, 76, 176, 20, 11, 200, 29, 32, 77, 52, 21, 9, 76, 176, 20, 11, 200, 25, 148, 201, 85, 33, 201, 76, 176, 20, 11, 200, 24, 195, 210, 37, 53, 9, 76, 176, 20, 11, 200, 24, 147, 15, 76, 241, 137, 76, 176, 20, 11, 200, 20, 225, 82, 28, 85, 9, 76, 176, 20, 11, 200, 8, 147, 199, 72, 17, 137, 76, 176, 20, 11, 200, 8, 16, 153, 48, 243, 137, 76, 176, 20, 11, 200, 4, 99, 210, 37, 53, 9, 76, 176, 20, 12, 3, 95, 51, 15, 47, 34, 107, 70, 57, 106, 0, 8, 4, 95, 15, 18, 4, 106, 0, 0, 11, 136, 1, 13, 15, 21, 18, 195, 184, 19, 20, 15, 140, 14, 5, 4, 6, 195, 166, 12, 4, 5, 12, 9, 7, 20, 15, 140, 6, 15, 18, 14, 195, 166, 18, 13, 5, 12, 9, 7, 20, 12, 201, 80, 83, 5, 60, 195, 199, 37, 50, 192, 20, 12, 201, 80, 82, 206, 60, 195, 199, 37, 50, 192, 20, 12, 201, 56, 85, 82, 60, 195, 199, 37, 50, 192, 20, 12, 201, 52, 244, 134, 60, 195, 199, 37, 50, 192, 20, 12, 201, 52, 85, 18, 60, 195, 199, 37, 50, 192, 20, 16, 69, 52, 83, 137, 76, 176, 63, 36, 50, 6, 37, 87, 49, 0, 20, 9, 198, 52, 17, 206, 60, 194, 69, 20, 12, 201, 65, 35, 194, 48, 83, 65, 80, 146, 192, 20, 12, 201, 44, 148, 143, 65, 32, 75, 80, 146, 192, 20, 8, 197, 52, 19, 9, 12, 80, 20, 12, 201, 20, 180, 212, 20, 212, 15, 72, 19, 0, 20, 0, 9, 198, 61, 33, 193, 56, 148, 212, 20, 18, 70, 4, 181, 129, 72, 83, 0, 110, 49, 82, 110, 51, 6, 109, 55, 0, 20, 13, 202, 72, 83, 1, 80, 149, 137, 77, 66, 83, 44, 20, 13, 202, 65, 35, 214, 60, 176, 84, 61, 34, 83, 44, 20, 13, 202, 64, 20, 129, 16, 145, 205, 5, 66, 83, 44, 20, 13, 202, 48, 147, 12, 20, 20, 201, 5, 66, 83, 44, 20, 13, 202, 44, 19, 11, 84, 192, 84, 61, 34, 83, 44, 20, 13, 202, 36, 228, 208, 37, 32, 84, 61, 34, 83, 44, 20, 13, 202, 36, 225, 143, 72, 208, 84, 61, 34, 83, 44, 20, 13, 202, 32, 245, 20, 20, 229, 15, 81, 66, 83, 44, 20, 13, 202, 16, 144, 71, 72, 19, 77, 5, 66, 83, 44, 20, 13, 202, 16, 82, 204, 5, 32, 84, 61, 34, 83, 44, 20, 13, 202, 8, 243, 19, 40, 85, 137, 77, 66, 83, 44, 20, 13, 202, 5, 34, 83, 80, 242, 210, 5, 66, 83, 44, 20, 13, 202, 4, 180, 207, 56, 243, 69, 81, 34, 83, 44, 20, 9, 198, 80, 83, 65, 80, 146, 192, 20, 9, 198, 4, 181, 83, 80, 146, 192, 20, 9, 198, 64, 21, 18, 60, 224, 84, 20, 0, 10, 199, 4, 66, 149, 56, 181, 21, 72, 20, 10, 199, 88, 148, 201, 80, 21, 15, 72, 20, 10, 199, 85, 53, 82, 64, 21, 15, 72, 20, 12, 201, 36, 225, 137, 49, 68, 129, 80, 147, 206, 20, 12, 201, 36, 225, 15, 64, 84, 129, 80, 147, 206, 20, 12, 201, 16, 148, 212, 72, 144, 149, 80, 147, 206, 20, 12, 201, 16, 83, 149, 57, 66, 65, 80, 147, 206, 20, 12, 201, 36, 195, 15, 100, 19, 9, 80, 85, 0, 20, 12, 201, 5, 51, 195, 36, 19, 9, 80, 85, 0, 20, 10, 199, 88, 242, 193, 48, 148, 197, 72, 20, 14, 203, 8, 244, 148, 5, 82, 212, 36, 243, 133, 72, 80, 20, 21, 146, 13, 9, 19, 21, 14, 4, 5, 12, 19, 5, 19, 22, 195, 166, 18, 4, 9, 7, 20, 14, 203, 44, 243, 148, 72, 20, 21, 56, 181, 9, 76, 176, 20, 10, 199, 4, 208, 146, 61, 50, 83, 44, 20, 10, 199, 77, 147, 143, 57, 147, 73, 44, 20, 12, 201, 44, 243, 135, 48, 243, 69, 72, 21, 0, 20, 0, 11, 200, 32, 84, 144, 21, 67, 204, 60, 112, 20, 9, 198, 32, 20, 144, 37, 53, 0, 20, 11, 200, 76, 20, 129, 12, 83, 137, 76, 176, 20, 11, 200, 64, 144, 78, 37, 53, 9, 76, 176, 20, 11, 200, 56, 18, 86, 37, 53, 9, 76, 176, 20, 11, 200, 52, 243, 143, 24, 243, 137, 76, 176, 20, 15, 204, 44, 20, 129, 45, 65, 82, 60, 195, 199, 37, 50, 192, 20, 11, 200, 32, 85, 82, 37, 53, 9, 76, 176, 20, 11, 200, 32, 81, 197, 52, 243, 137, 76, 176, 20, 11, 200, 24, 21, 86, 37, 53, 9, 76, 176, 20, 11, 200, 8, 18, 203, 4, 229, 9, 76, 176, 20, 11, 200, 4, 116, 143, 56, 243, 73, 76, 176, 20, 11, 200, 65, 34, 86, 36, 193, 71, 36, 80, 20, 7, 196, 52, 84, 137, 80, 20, 11, 200, 80, 82, 206, 60, 180, 129, 80, 144, 20, 11, 200, 21, 128, 197, 48, 193, 78, 12, 80, 20, 7, 196, 76, 83, 129, 80, 20, 7, 196, 64, 20, 129, 80, 20, 7, 196, 52, 244, 129, 48, 20, 7, 196, 44, 244, 129, 48, 20, 0, 16, 205, 44, 243, 147, 81, 37, 75, 80, 149, 137, 77, 66, 83, 44, 20, 16, 205, 20, 180, 200, 36, 34, 84, 36, 243, 137, 77, 66, 83, 44, 20, 0, 9, 198, 80, 83, 5, 24, 243, 128, 20, 15, 204, 36, 229, 5, 57, 66, 79, 56, 19, 9, 80, 85, 0, 20, 12, 201, 88, 83, 2, 20, 128, 71, 20, 194, 71, 20, 12, 201, 77, 68, 129, 25, 50, 217, 48, 66, 71, 20, 12, 201, 32, 245, 133, 17, 48, 71, 20, 194, 71, 20, 9, 198, 41, 83, 135, 36, 19, 128, 20, 9, 198, 72, 19, 65, 16, 19, 128, 21, 0, 12, 137, 9, 13, 16, 15, 18, 20, 195, 184, 18, 20, 12, 201, 44, 243, 147, 81, 34, 75, 80, 147, 206, 20, 12, 201, 36, 225, 140, 4, 211, 65, 80, 147, 206, 20, 12, 201, 5, 37, 9, 45, 83, 1, 80, 147, 206, 20, 14, 203, 85, 66, 76, 37, 64, 82, 37, 53, 9, 76, 176, 20, 14, 203, 81, 34, 71, 60, 227, 205, 21, 68, 137, 76, 176, 20, 14, 203, 44, 192, 85, 77, 68, 143, 24, 240, 137, 76, 176, 20, 14, 203, 20, 181, 137, 48, 144, 146, 37, 53, 9, 76, 176, 20, 15, 140, 16, 195, 166, 4, 1, 7, 15, 7, 9, 11, 21, 13, 20, 10, 199, 76, 147, 5, 57, 66, 85, 52, 20, 10, 199, 61, 32, 84, 61, 34, 85, 52, 20, 10, 199, 32, 84, 130, 5, 34, 85, 52, 20, 10, 199, 88, 242, 193, 48, 148, 205, 20, 20, 10, 199, 56, 243, 65, 16, 148, 205, 20, 20, 10, 199, 45, 98, 69, 80, 148, 205, 20, 20, 10, 199, 32, 85, 5, 72, 241, 137, 48, 20, 12, 137, 195, 165, 18, 8, 21, 19, 9, 1, 14, 20, 10, 199, 44, 243, 210, 16, 147, 129, 80, 20, 9, 198, 52, 20, 131, 37, 0, 78, 21, 10, 199, 84, 226, 86, 21, 36, 193, 48, 20, 10, 199, 28, 19, 15, 65, 0, 68, 20, 20, 8, 67, 73, 83, 128, 21, 0, 10, 0, 13, 138, 19, 11, 195, 166, 12, 19, 11, 195, 184, 18, 20, 7, 196, 8, 17, 21, 80, 20, 7, 196, 76, 243, 5, 80, 20, 9, 198, 85, 67, 208, 37, 53, 0, 20, 9, 198, 56, 244, 132, 37, 53, 0, 20, 9, 198, 76, 50, 1, 81, 65, 82, 20, 9, 198, 44, 243, 12, 4, 33, 82, 20, 9, 198, 20, 160, 75, 84, 193, 82, 20, 9, 198, 16, 85, 129, 49, 81, 82, 20, 11, 200, 4, 208, 137, 88, 19, 5, 57, 48, 20, 0, 9, 198, 4, 225, 201, 88, 84, 137, 20, 0, 5, 194, 36, 64, 17, 12, 201, 64, 84, 211, 36, 210, 83, 80, 148, 203, 20, 12, 201, 52, 243, 143, 80, 82, 83, 80, 148, 203, 20, 12, 201, 52, 243, 129, 72, 178, 83, 80, 148, 203, 20, 12, 201, 24, 19, 1, 56, 114, 83, 80, 148, 203, 20, 12, 201, 16, 81, 129, 37, 66, 83, 80, 148, 203, 20, 13, 202, 60, 36, 197, 73, 96, 84, 61, 34, 85, 52, 20, 13, 202, 72, 81, 204, 20, 209, 78, 80, 84, 133, 80, 20, 13, 202, 4, 194, 207, 32, 243, 9, 76, 84, 133, 80, 20, 0, 19, 71, 12, 129, 86, 72, 243, 5, 80, 87, 57, 107, 82, 34, 39, 55, 6, 36, 0, 10, 199, 24, 192, 71, 20, 243, 5, 80, 20, 10, 199, 64, 83, 148, 4, 116, 129, 52, 20, 10, 199, 32, 82, 211, 4, 116, 129, 52, 20, 12, 201, 45, 35, 206, 60, 195, 199, 37, 49, 82, 20, 9, 198, 21, 36, 129, 80, 148, 203, 20, 9, 198, 9, 37, 78, 20, 148, 203, 20, 10, 199, 64, 193, 66, 37, 48, 201, 80, 20, 10, 199, 21, 2, 83, 44, 244, 1, 48, 20, 0, 9, 198, 77, 83, 6, 60, 225, 82, 20, 7, 196, 64, 20, 133, 72, 20, 9, 198, 33, 145, 18, 5, 162, 78, 20, 7, 196, 4, 116, 129, 72, 20, 13, 72, 8, 80, 67, 32, 37, 71, 29, 144, 21, 0, 10, 0, 9, 198, 80, 245, 82, 57, 84, 133, 20, 9, 198, 76, 179, 5, 72, 244, 197, 20, 9, 198, 76, 176, 66, 36, 244, 197, 20, 8, 197, 16, 144, 75, 60, 224, 20, 8, 197, 88, 148, 201, 60, 224, 20, 8, 197, 16, 147, 216, 36, 64, 20, 8, 197, 48, 21, 18, 36, 224, 20, 8, 197, 12, 149, 18, 36, 224, 20, 9, 198, 80, 83, 5, 24, 243, 137, 20, 8, 197, 65, 35, 198, 36, 192, 20, 8, 197, 88, 84, 130, 4, 192, 20, 0, 12, 201, 24, 147, 129, 57, 50, 69, 72, 147, 135, 20, 12, 201, 24, 147, 15, 76, 241, 133, 72, 147, 135, 20, 9, 198, 80, 21, 15, 88, 84, 128, 20, 9, 198, 76, 242, 71, 56, 84, 128, 20, 9, 198, 72, 85, 9, 72, 84, 128, 20, 9, 198, 20, 210, 71, 72, 84, 128, 20, 9, 198, 16, 81, 137, 48, 84, 128, 20, 9, 198, 16, 80, 149, 80, 84, 128, 20, 9, 198, 12, 128, 83, 76, 84, 128, 20, 9, 198, 8, 243, 137, 80, 84, 128, 20, 9, 198, 65, 35, 212, 60, 179, 204, 20, 12, 201, 36, 211, 85, 56, 243, 15, 28, 148, 203, 20, 12, 201, 32, 84, 143, 77, 68, 129, 80, 148, 203, 20, 12, 201, 20, 118, 80, 80, 243, 15, 28, 148, 203, 20, 9, 198, 76, 21, 5, 48, 194, 84, 20, 0, 10, 199, 72, 80, 197, 57, 50, 79, 56, 20, 10, 199, 36, 226, 204, 85, 50, 79, 56, 20, 10, 199, 44, 243, 150, 21, 36, 197, 72, 20, 10, 199, 44, 243, 147, 20, 180, 133, 72, 20, 10, 199, 12, 149, 137, 48, 148, 197, 72, 20, 10, 199, 77, 83, 77, 5, 34, 83, 44, 20, 10, 199, 76, 177, 77, 5, 66, 83, 44, 20, 10, 199, 32, 148, 212, 61, 34, 83, 44, 20, 10, 199, 20, 195, 9, 65, 66, 83, 44, 20, 10, 199, 52, 19, 12, 61, 32, 193, 56, 20, 0, 22, 72, 44, 243, 134, 37, 35, 65, 56, 64, 49, 112, 50, 81, 36, 34, 63, 6, 108, 50, 70, 0, 10, 200, 64, 19, 143, 65, 66, 75, 60, 224, 11, 200, 65, 35, 198, 21, 52, 201, 60, 224, 20, 11, 200, 44, 243, 139, 49, 84, 201, 60, 224, 20, 11, 200, 44, 243, 134, 21, 52, 201, 60, 224, 20, 11, 200, 20, 180, 208, 48, 244, 201, 60, 224, 20, 7, 196, 44, 20, 5, 72, 20, 7, 196, 48, 21, 9, 56, 20, 7, 196, 48, 21, 9, 56, 20, 9, 198, 77, 2, 82, 4, 229, 0, 20, 7, 196, 56, 245, 1, 8, 20, 11, 3, 95, 53, 15, 81, 107, 63, 47, 106, 0, 0, 9, 198, 9, 35, 195, 33, 84, 133, 20, 9, 198, 8, 83, 133, 24, 144, 197, 67, 8, 197, 44, 20, 212, 20, 192, 20, 8, 197, 44, 20, 148, 20, 192, 20, 8, 197, 44, 20, 212, 20, 192, 20, 8, 197, 44, 20, 148, 20, 192, 20, 12, 201, 72, 83, 1, 80, 149, 137, 76, 84, 128, 20, 12, 201, 21, 2, 71, 72, 17, 137, 44, 84, 128, 20, 9, 198, 20, 180, 197, 28, 84, 197, 20, 8, 197, 24, 195, 210, 36, 224, 20, 9, 198, 8, 83, 133, 24, 144, 197, 20, 8, 197, 76, 244, 18, 4, 224, 21, 0, 5, 194, 37, 64, 17, 13, 202, 77, 68, 143, 8, 244, 203, 61, 2, 83, 44, 20, 13, 202, 72, 81, 143, 72, 208, 84, 61, 34, 83, 44, 20, 13, 202, 21, 2, 71, 72, 19, 77, 5, 66, 83, 44, 20, 13, 202, 16, 82, 204, 4, 208, 84, 61, 34, 83, 44, 20, 9, 198, 80, 83, 196, 60, 194, 84, 20, 9, 198, 76, 178, 66, 60, 226, 84, 20, 15, 4, 95, 13, 3, 14, 63, 6, 35, 49, 34, 4, 113, 50, 0, 0, 10, 199, 44, 243, 132, 84, 181, 15, 72, 20, 10, 199, 28, 192, 68, 36, 21, 15, 72, 20, 10, 199, 21, 96, 76, 84, 21, 15, 72, 20, 12, 201, 48, 81, 201, 80, 147, 65, 80, 147, 206, 20, 10, 199, 21, 99, 204, 85, 66, 79, 56, 20, 10, 199, 20, 193, 86, 5, 66, 79, 56, 20, 10, 199, 72, 243, 65, 56, 148, 197, 72, 20, 10, 199, 72, 81, 18, 21, 52, 197, 72, 20, 10, 199, 64, 20, 129, 49, 148, 197, 72, 20, 10, 199, 52, 19, 149, 17, 80, 197, 72, 20, 10, 199, 4, 229, 9, 12, 148, 5, 72, 20, 10, 199, 77, 148, 212, 20, 210, 83, 44, 20, 10, 199, 64, 19, 132, 20, 210, 83, 44, 20, 10, 199, 28, 128, 78, 21, 50, 83, 44, 20, 10, 199, 28, 83, 204, 60, 114, 83, 44, 20, 10, 199, 72, 84, 201, 77, 65, 78, 80, 20, 13, 67, 56, 85, 192, 21, 0, 10, 81, 97, 103, 101, 32, 0, 11, 200, 72, 84, 18, 21, 52, 201, 60, 224, 20, 11, 200, 65, 35, 195, 21, 52, 201, 60, 224, 20, 11, 200, 64, 84, 141, 37, 52, 201, 60, 224, 20, 11, 200, 64, 84, 139, 85, 52, 201, 60, 224, 20, 11, 200, 44, 243, 131, 21, 52, 201, 60, 224, 20, 11, 200, 44, 243, 77, 37, 52, 201, 60, 224, 20, 11, 200, 64, 84, 141, 37, 52, 201, 60, 224, 20, 11, 200, 64, 83, 148, 4, 115, 206, 4, 192, 20, 11, 200, 32, 82, 211, 4, 115, 206, 4, 192, 20, 9, 198, 24, 244, 141, 36, 64, 66, 20, 0, 8, 197, 72, 80, 71, 21, 32, 20, 8, 197, 12, 131, 203, 21, 32, 20, 9, 198, 76, 210, 71, 72, 84, 137, 20, 9, 198, 76, 178, 68, 80, 84, 137, 20, 9, 198, 24, 163, 204, 48, 84, 137, 20, 8, 197, 8, 21, 88, 37, 64, 20, 8, 197, 16, 146, 212, 5, 64, 20, 0, 11, 67, 76, 52, 201, 87, 49, 112, 87, 37, 0, 9, 198, 21, 64, 77, 36, 225, 64, 20, 13, 202, 77, 80, 143, 72, 66, 78, 5, 66, 79, 56, 20, 9, 198, 88, 83, 79, 16, 145, 192, 20, 13, 202, 64, 83, 15, 64, 243, 142, 21, 50, 83, 44, 20, 9, 198, 33, 145, 18, 60, 98, 76, 20, 9, 198, 45, 35, 203, 4, 65, 64, 20, 0, 10, 199, 80, 19, 135, 21, 34, 78, 28, 20, 10, 199, 73, 82, 78, 21, 34, 78, 28, 20, 10, 199, 72, 19, 135, 21, 34, 78, 28, 20, 10, 199, 64, 192, 67, 21, 34, 78, 28, 20, 10, 199, 64, 21, 83, 21, 34, 78, 28, 20, 10, 199, 52, 20, 203, 21, 34, 78, 28, 20, 10, 199, 52, 20, 139, 21, 34, 78, 28, 20, 10, 199, 48, 243, 135, 21, 34, 78, 28, 20, 10, 199, 48, 147, 138, 21, 34, 78, 28, 20, 10, 199, 24, 244, 131, 21, 34, 78, 28, 20, 9, 198, 77, 83, 69, 72, 148, 203, 20, 9, 198, 52, 19, 1, 92, 148, 203, 20, 9, 198, 44, 19, 129, 72, 148, 203, 20, 9, 198, 16, 82, 75, 80, 148, 203, 20, 9, 198, 77, 147, 66, 60, 194, 75, 20, 10, 199, 72, 84, 201, 77, 65, 78, 76, 20, 0, 12, 201, 24, 20, 141, 4, 179, 199, 56, 244, 201, 20, 11, 200, 89, 83, 7, 5, 34, 83, 21, 32, 20, 11, 200, 77, 147, 148, 21, 66, 83, 21, 32, 20, 11, 200, 76, 82, 212, 61, 34, 83, 21, 32, 20, 11, 200, 72, 243, 65, 57, 66, 83, 21, 32, 20, 11, 200, 65, 83, 22, 21, 34, 83, 21, 32, 20, 11, 200, 65, 34, 86, 5, 66, 83, 21, 32, 20, 11, 200, 64, 84, 137, 60, 66, 83, 21, 32, 20, 11, 200, 64, 20, 211, 37, 98, 83, 21, 32, 20, 11, 200, 56, 85, 82, 61, 66, 83, 21, 32, 20, 11, 200, 48, 16, 137, 4, 194, 83, 21, 32, 20, 11, 200, 44, 19, 148, 60, 226, 83, 21, 32, 20, 11, 200, 36, 212, 18, 61, 98, 83, 21, 32, 20, 11, 200, 32, 84, 130, 5, 34, 83, 21, 32, 20, 11, 200, 28, 116, 149, 8, 194, 83, 21, 32, 20, 11, 200, 8, 20, 130, 5, 34, 83, 21, 32, 20, 9, 198, 52, 84, 203, 4, 194, 78, 20, 9, 198, 52, 19, 132, 60, 194, 78, 20, 9, 198, 32, 84, 141, 20, 194, 78, 20, 11, 200, 52, 81, 9, 44, 19, 69, 57, 64, 20, 11, 200, 36, 228, 212, 73, 83, 69, 57, 64, 20, 9, 198, 44, 20, 5, 48, 192, 78, 21, 21, 72, 56, 243, 131, 32, 19, 1, 57, 64, 50, 112, 50, 89, 13, 55, 6, 110, 66, 0, 20, 11, 3, 95, 54, 15, 87, 57, 107, 70, 106, 0, 0, 30, 69, 76, 80, 210, 21, 64, 87, 37, 79, 34, 36, 70, 15, 87, 6, 116, 82, 37, 87, 0, 81, 115, 101, 114, 118, 105, 99, 101, 32, 16, 70, 8, 17, 213, 21, 69, 5, 69, 2, 35, 6, 79, 36, 47, 0, 8, 197, 81, 84, 137, 77, 64, 20, 8, 197, 56, 22, 137, 77, 64, 20, 16, 205, 36, 228, 212, 37, 69, 84, 36, 243, 129, 48, 148, 197, 72, 20, 8, 197, 8, 195, 203, 21, 32, 20, 9, 198, 4, 195, 5, 28, 244, 137, 20, 12, 201, 45, 32, 77, 64, 80, 71, 80, 145, 192, 20, 8, 197, 104, 83, 204, 37, 64, 20, 16, 141, 7, 195, 165, 19, 5, 16, 15, 20, 5, 14, 20, 9, 12, 20, 8, 197, 64, 21, 5, 57, 64, 20, 12, 201, 45, 32, 77, 64, 80, 71, 80, 145, 192, 20, 8, 197, 60, 181, 1, 57, 64, 20, 8, 197, 4, 181, 1, 57, 64, 20, 10, 69, 80, 80, 83, 21, 32, 21, 0, 10, 0, 25, 70, 88, 148, 139, 20, 65, 64, 82, 6, 37, 34, 49, 36, 84, 13, 15, 87, 112, 0, 81, 115, 195, 165, 32, 13, 202, 88, 148, 213, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 88, 19, 132, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 80, 84, 146, 61, 34, 83, 21, 34, 78, 28, 20, 13, 202, 77, 147, 66, 60, 194, 83, 21, 34, 78, 28, 20, 13, 202, 76, 240, 201, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 72, 149, 21, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 64, 21, 18, 60, 226, 83, 21, 34, 78, 28, 20, 13, 202, 56, 244, 141, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 53, 84, 197, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 36, 229, 5, 57, 50, 86, 21, 34, 78, 28, 20, 13, 202, 24, 244, 141, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 24, 84, 148, 36, 194, 83, 21, 34, 78, 28, 20, 13, 202, 16, 85, 18, 60, 226, 83, 21, 34, 78, 28, 20, 13, 202, 9, 37, 84, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 4, 181, 21, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 4, 68, 212, 72, 147, 135, 21, 34, 78, 28, 20, 9, 198, 45, 34, 77, 36, 224, 76, 20, 9, 198, 29, 81, 5, 48, 145, 192, 20, 12, 201, 76, 21, 68, 36, 20, 129, 8, 148, 203, 20, 12, 201, 65, 35, 194, 48, 83, 65, 80, 148, 203, 20, 12, 201, 52, 147, 133, 72, 19, 15, 28, 148, 203, 20, 12, 201, 45, 33, 77, 48, 243, 15, 28, 148, 203, 20, 12, 201, 44, 148, 143, 65, 32, 75, 80, 148, 203, 20, 12, 201, 44, 20, 148, 60, 116, 129, 24, 148, 203, 20, 0, 10, 199, 77, 2, 82, 37, 66, 83, 80, 20, 10, 199, 76, 82, 212, 21, 34, 83, 80, 20, 10, 199, 65, 34, 86, 5, 66, 83, 80, 20, 10, 199, 53, 149, 20, 21, 34, 83, 80, 20, 10, 199, 52, 19, 137, 21, 34, 83, 80, 20, 10, 199, 44, 243, 131, 37, 2, 83, 80, 20, 14, 203, 48, 21, 144, 5, 53, 5, 85, 34, 83, 21, 32, 20, 14, 203, 9, 84, 133, 5, 82, 210, 5, 66, 83, 21, 32, 20, 13, 138, 16, 195, 165, 20, 1, 7, 5, 12, 9, 7, 20, 13, 138, 15, 13, 2, 195, 184, 10, 5, 12, 9, 7, 20, 9, 198, 76, 243, 65, 80, 148, 203, 20, 9, 198, 76, 84, 129, 24, 148, 203, 20, 9, 198, 16, 144, 84, 60, 226, 75, 20, 0, 11, 200, 76, 83, 73, 56, 20, 137, 77, 64, 20, 11, 200, 52, 243, 133, 80, 20, 137, 77, 64, 20, 11, 200, 80, 82, 206, 36, 98, 67, 21, 32, 20, 11, 200, 52, 85, 18, 61, 3, 204, 37, 64, 20, 11, 200, 44, 244, 205, 61, 3, 204, 37, 64, 20, 7, 196, 28, 245, 9, 44, 20, 11, 200, 44, 243, 148, 36, 225, 197, 57, 64, 20, 11, 200, 44, 243, 147, 37, 53, 5, 57, 64, 20, 9, 198, 24, 147, 20, 72, 21, 0, 20, 7, 196, 88, 20, 129, 56, 21, 11, 200, 65, 35, 212, 21, 53, 1, 57, 64, 20, 9, 68, 9, 35, 206, 96, 21, 0, 10, 0, 8, 197, 4, 224, 76, 60, 112, 20, 8, 197, 52, 20, 137, 56, 80, 20, 16, 205, 44, 243, 77, 21, 32, 201, 4, 194, 83, 21, 34, 78, 28, 20, 16, 205, 36, 225, 9, 88, 145, 21, 4, 194, 83, 21, 34, 78, 28, 20, 12, 201, 76, 176, 82, 65, 50, 78, 16, 145, 192, 20, 12, 201, 61, 97, 82, 76, 181, 69, 48, 145, 192, 20, 12, 201, 60, 213, 22, 37, 53, 5, 48, 145, 192, 20, 12, 201, 56, 81, 2, 73, 145, 5, 48, 145, 192, 20, 12, 201, 24, 244, 148, 73, 145, 5, 48, 145, 192, 20, 12, 201, 24, 244, 148, 60, 194, 197, 48, 145, 192, 20, 12, 201, 24, 244, 147, 45, 145, 5, 48, 145, 192, 20, 12, 201, 24, 244, 141, 5, 53, 5, 48, 145, 192, 20, 15, 140, 6, 15, 18, 4, 195, 166, 18, 22, 5, 12, 9, 7, 20, 15, 204, 45, 38, 83, 80, 19, 12, 60, 116, 129, 24, 148, 203, 20, 9, 198, 44, 243, 139, 100, 194, 69, 20, 9, 198, 44, 243, 147, 36, 194, 69, 20, 8, 197, 44, 194, 78, 36, 176, 20, 8, 197, 52, 83, 129, 28, 80, 20, 0, 6, 195, 20, 212, 0, 17, 6, 195, 72, 81, 201, 20, 9, 198, 72, 246, 65, 48, 148, 212, 20, 9, 198, 64, 244, 21, 48, 148, 212, 20, 9, 198, 48, 246, 65, 48, 148, 212, 20, 13, 202, 44, 243, 77, 84, 226, 84, 5, 34, 83, 80, 20, 9, 198, 8, 145, 193, 52, 148, 212, 20, 9, 198, 4, 224, 82, 44, 148, 212, 20, 16, 141, 195, 184, 10, 5, 2, 12, 9, 11, 11, 5, 12, 9, 7, 20, 12, 137, 195, 166, 18, 2, 195, 184, 4, 9, 7, 20, 16, 141, 8, 195, 165, 14, 4, 7, 18, 9, 2, 5, 12, 9, 7, 20, 12, 201, 77, 147, 148, 4, 115, 65, 80, 148, 203, 20, 12, 201, 77, 147, 80, 80, 243, 65, 80, 148, 203, 20, 12, 201, 64, 19, 139, 72, 243, 65, 80, 148, 203, 20, 12, 201, 45, 96, 68, 72, 241, 143, 56, 148, 203, 20, 12, 201, 44, 19, 12, 36, 116, 129, 24, 148, 203, 20, 12, 201, 36, 179, 206, 60, 116, 129, 24, 148, 203, 20, 12, 201, 25, 32, 83, 20, 243, 15, 28, 148, 203, 20, 12, 201, 16, 148, 203, 60, 116, 129, 24, 148, 203, 20, 9, 198, 5, 36, 197, 56, 146, 192, 20, 0, 10, 199, 4, 194, 214, 4, 229, 15, 72, 20, 9, 198, 48, 149, 147, 4, 194, 71, 20, 10, 199, 52, 21, 5, 52, 21, 9, 44, 20, 10, 199, 5, 34, 84, 52, 85, 9, 44, 20, 12, 201, 20, 50, 1, 84, 97, 133, 72, 85, 0, 20, 0, 28, 68, 88, 244, 133, 76, 82, 112, 12, 87, 15, 49, 82, 110, 6, 47, 36, 34, 0, 81, 107, 118, 97, 114, 116, 101, 114, 32, 9, 198, 72, 83, 5, 28, 147, 206, 20, 9, 198, 53, 85, 1, 80, 147, 206, 20, 11, 200, 24, 147, 20, 72, 84, 137, 56, 112, 20, 11, 200, 80, 83, 5, 24, 243, 133, 72, 80, 20, 11, 200, 52, 17, 193, 76, 147, 133, 72, 80, 20, 14, 139, 16, 195, 165, 16, 1, 19, 19, 5, 12, 9, 7, 20, 14, 139, 6, 15, 18, 14, 195, 184, 10, 5, 12, 9, 7, 20, 11, 200, 21, 2, 71, 72, 17, 137, 76, 176, 20, 11, 200, 64, 20, 148, 36, 50, 80, 36, 80, 20, 9, 198, 37, 51, 1, 52, 149, 0, 20, 9, 198, 12, 240, 203, 64, 149, 0, 20, 7, 196, 44, 149, 9, 56, 20, 9, 198, 52, 147, 12, 36, 32, 82, 20, 9, 198, 17, 35, 205, 20, 64, 82, 20, 13, 68, 32, 21, 132, 20, 105, 108, 12, 84, 13, 0, 76, 7, 196, 88, 244, 133, 76, 72, 11, 3, 95, 55, 15, 87, 114, 82, 50, 106, 0, 0, 8, 197, 56, 81, 197, 72, 80, 20, 15, 140, 7, 5, 2, 18, 195, 166, 11, 11, 5, 12, 9, 7, 20, 15, 140, 1, 6, 7, 18, 195, 166, 14, 19, 5, 12, 9, 7, 20, 8, 197, 64, 243, 9, 80, 144, 20, 0, 9, 198, 52, 82, 133, 72, 148, 212, 20, 9, 198, 33, 83, 65, 56, 148, 212, 20, 9, 198, 4, 196, 9, 56, 148, 212, 20, 9, 198, 45, 34, 77, 36, 225, 76, 20, 16, 141, 195, 166, 7, 20, 5, 19, 11, 1, 2, 5, 12, 9, 7, 20, 9, 198, 4, 225, 197, 48, 146, 192, 20, 9, 198, 44, 243, 147, 84, 192, 84, 20, 9, 198, 25, 32, 75, 80, 19, 0, 20, 0, 10, 199, 76, 84, 1, 72, 21, 15, 72, 20, 12, 201, 65, 35, 204, 60, 225, 193, 80, 147, 206, 20, 12, 201, 64, 84, 148, 85, 32, 129, 80, 147, 206, 20, 12, 201, 52, 20, 212, 85, 32, 129, 80, 147, 206, 20, 12, 201, 24, 84, 141, 20, 229, 1, 80, 147, 206, 20, 14, 203, 77, 68, 129, 80, 145, 137, 12, 84, 137, 56, 112, 20, 0, 9, 198, 72, 80, 75, 80, 147, 206, 20, 9, 198, 36, 229, 129, 76, 147, 206, 20, 11, 200, 81, 148, 9, 76, 84, 137, 56, 112, 20, 11, 200, 81, 37, 78, 44, 84, 137, 56, 112, 20, 11, 200, 81, 32, 75, 80, 84, 137, 56, 112, 20, 11, 200, 77, 64, 71, 56, 84, 137, 56, 112, 20, 11, 200, 65, 83, 139, 80, 84, 137, 56, 112, 20, 11, 200, 61, 33, 9, 56, 84, 137, 56, 112, 20, 11, 200, 60, 178, 213, 64, 84, 137, 56, 112, 20, 11, 200, 57, 80, 78, 12, 84, 137, 56, 112, 20, 11, 200, 45, 96, 68, 72, 84, 137, 56, 112, 20, 11, 200, 44, 20, 212, 72, 84, 137, 56, 112, 20, 11, 200, 36, 243, 137, 76, 84, 137, 56, 112, 20, 11, 200, 29, 83, 77, 36, 84, 137, 56, 112, 20, 11, 200, 29, 37, 78, 16, 84, 137, 56, 112, 20, 11, 200, 21, 64, 66, 48, 84, 137, 56, 112, 20, 11, 200, 20, 225, 193, 28, 84, 137, 56, 112, 20, 11, 200, 20, 213, 76, 28, 84, 137, 56, 112, 20, 11, 200, 16, 82, 213, 64, 84, 137, 56, 112, 20, 11, 200, 12, 130, 70, 72, 84, 137, 56, 112, 20, 11, 200, 5, 97, 82, 80, 84, 137, 56, 112, 20, 11, 200, 4, 227, 143, 80, 84, 137, 56, 112, 20, 11, 200, 72, 82, 210, 85, 69, 5, 72, 80, 20, 11, 200, 36, 229, 129, 48, 145, 5, 72, 80, 20, 11, 200, 52, 241, 2, 100, 65, 76, 36, 112, 20, 11, 200, 44, 20, 18, 36, 99, 204, 36, 80, 20, 11, 200, 44, 20, 18, 36, 99, 204, 36, 80, 20, 11, 200, 64, 243, 25, 80, 82, 206, 36, 176, 20, 7, 196, 64, 148, 129, 80, 20, 7, 196, 44, 20, 129, 80, 20, 9, 198, 24, 244, 141, 84, 192, 82, 20, 0, 0, 9, 198, 44, 243, 150, 60, 197, 84, 20, 13, 202, 72, 82, 207, 57, 96, 76, 21, 48, 197, 72, 20, 12, 201, 24, 244, 149, 17, 50, 71, 20, 194, 71, 20, 9, 198, 44, 243, 77, 84, 224, 76, 20, 0, 14, 203, 88, 149, 1, 52, 147, 137, 76, 84, 137, 56, 112, 20, 10, 199, 88, 21, 20, 21, 34, 78, 28, 20, 14, 203, 81, 32, 78, 77, 3, 210, 80, 84, 137, 56, 112, 20, 14, 203, 81, 32, 78, 76, 99, 210, 52, 84, 137, 56, 112, 20, 14, 203, 77, 147, 139, 72, 243, 137, 76, 84, 137, 56, 112, 20, 14, 203, 77, 65, 82, 20, 245, 25, 64, 84, 137, 56, 112, 20, 14, 203, 72, 82, 207, 57, 53, 18, 84, 84, 137, 56, 112, 20, 10, 199, 64, 244, 212, 21, 34, 78, 28, 20, 14, 203, 44, 243, 132, 37, 66, 79, 56, 84, 137, 56, 112, 20, 14, 203, 44, 192, 83, 76, 145, 137, 12, 84, 137, 56, 112, 20, 10, 199, 29, 32, 68, 21, 34, 78, 28, 20, 14, 203, 28, 192, 77, 61, 84, 137, 76, 84, 137, 56, 112, 20, 10, 199, 25, 34, 84, 21, 34, 78, 28, 20, 10, 199, 20, 195, 216, 21, 34, 78, 28, 20, 14, 203, 16, 84, 201, 56, 99, 210, 52, 84, 137, 56, 112, 20, 14, 203, 5, 85, 15, 56, 243, 73, 76, 84, 137, 56, 112, 20, 14, 203, 76, 19, 77, 20, 227, 9, 28, 225, 76, 36, 112, 20, 9, 198, 48, 149, 15, 80, 148, 203, 20, 9, 198, 44, 19, 143, 56, 148, 203, 20, 9, 198, 20, 225, 82, 28, 148, 203, 20, 9, 198, 4, 209, 137, 8, 148, 203, 20, 10, 199, 56, 84, 20, 84, 226, 85, 52, 20, 10, 199, 52, 20, 148, 101, 34, 85, 52, 20, 10, 199, 48, 83, 137, 56, 148, 205, 20, 20, 10, 199, 52, 84, 139, 4, 229, 9, 48, 20, 9, 198, 77, 1, 67, 36, 98, 75, 20, 10, 199, 5, 96, 78, 12, 84, 133, 80, 20, 10, 199, 44, 243, 134, 21, 33, 78, 76, 20, 10, 199, 64, 197, 84, 60, 180, 129, 80, 20, 0, 7, 196, 52, 245, 5, 48, 20, 9, 198, 44, 243, 132, 60, 193, 82, 20, 9, 198, 32, 20, 131, 20, 193, 82, 20, 9, 198, 12, 148, 139, 84, 193, 82, 20, 7, 196, 72, 20, 9, 16, 20, 7, 196, 64, 20, 9, 48, 20, 0, 9, 198, 45, 84, 148, 60, 148, 201, 20, 0, 25, 66, 20, 224, 36, 50, 15, 49, 108, 50, 39, 50, 6, 36, 34, 0, 81, 107, 97, 110, 111, 110, 101, 114, 32, 16, 66, 20, 224, 36, 50, 15, 87, 6, 112, 0, 81, 115, 195, 165, 32, 25, 66, 20, 224, 36, 50, 15, 55, 36, 79, 6, 107, 50, 70, 13, 0, 81, 108, 101, 103, 101, 110, 100, 101, 32, 23, 66, 20, 224, 110, 66, 15, 48, 108, 87, 6, 110, 66, 0, 81, 112, 97, 115, 115, 97, 110, 116, 32, 19, 66, 20, 224, 35, 66, 15, 6, 69, 55, 112, 49, 0, 81, 98, 108, 111, 99, 32, 18, 66, 20, 224, 35, 66, 15, 81, 6, 35, 87, 0, 81, 102, 97, 99, 101, 32, 9, 198, 44, 244, 147, 20, 193, 84, 20, 13, 202, 81, 34, 65, 56, 117, 76, 21, 34, 78, 28, 20, 13, 202, 77, 80, 147, 80, 149, 21, 21, 34, 78, 28, 20, 13, 202, 77, 68, 129, 56, 117, 76, 21, 34, 78, 28, 20, 13, 202, 72, 80, 201, 72, 181, 76, 21, 34, 78, 28, 20, 13, 202, 65, 35, 211, 64, 82, 212, 21, 34, 78, 28, 20, 13, 202, 64, 20, 148, 36, 50, 80, 21, 34, 78, 28, 20, 13, 202, 44, 243, 147, 80, 149, 21, 21, 34, 78, 28, 20, 13, 202, 44, 243, 80, 48, 85, 20, 21, 34, 78, 28, 20, 12, 201, 80, 84, 141, 60, 116, 129, 24, 148, 203, 20, 12, 201, 52, 85, 15, 16, 243, 15, 28, 148, 203, 20, 12, 201, 45, 34, 83, 80, 243, 15, 28, 148, 203, 20, 12, 201, 44, 244, 133, 60, 116, 129, 24, 148, 203, 20, 12, 201, 32, 82, 211, 4, 209, 84, 72, 148, 203, 20, 12, 201, 24, 20, 141, 4, 49, 85, 80, 148, 203, 20, 12, 201, 20, 229, 21, 76, 144, 83, 80, 148, 203, 20, 12, 201, 20, 229, 15, 52, 243, 15, 28, 148, 203, 20, 5, 194, 20, 224, 72, 0, 10, 199, 64, 146, 212, 60, 116, 129, 52, 20, 9, 198, 88, 83, 133, 72, 148, 203, 20, 9, 198, 76, 243, 65, 48, 148, 203, 20, 9, 198, 64, 83, 1, 28, 148, 203, 20, 9, 198, 57, 83, 69, 72, 148, 203, 20, 9, 198, 32, 19, 73, 80, 148, 203, 20, 9, 198, 4, 181, 83, 80, 148, 203, 20, 10, 199, 36, 225, 149, 76, 244, 137, 20, 20, 10, 199, 28, 84, 141, 4, 226, 85, 52, 20, 10, 199, 21, 2, 83, 44, 244, 1, 80, 20, 13, 3, 95, 51, 88, 47, 51, 6, 109, 84, 82, 13, 0, 0, 7, 196, 8, 20, 143, 56, 20, 9, 198, 72, 84, 207, 72, 33, 82, 20, 9, 198, 72, 19, 80, 60, 225, 82, 20, 9, 198, 61, 48, 201, 48, 193, 82, 20, 7, 196, 52, 245, 133, 72, 20, 9, 198, 44, 243, 80, 60, 225, 82, 20, 9, 198, 24, 244, 141, 84, 193, 82, 20, 9, 198, 5, 69, 1, 12, 129, 82, 20, 9, 198, 4, 227, 149, 48, 193, 82, 20, 11, 200, 44, 243, 148, 36, 225, 197, 57, 48, 20, 11, 200, 44, 243, 147, 37, 53, 5, 57, 48, 20, 14, 3, 95, 48, 67, 105, 6, 40, 50, 16, 13, 12, 84, 0, 0, 0, 12, 201, 80, 84, 141, 61, 53, 1, 80, 148, 203, 20, 12, 201, 77, 65, 78, 60, 116, 129, 24, 148, 203, 20, 12, 201, 25, 85, 21, 72, 243, 15, 28, 148, 203, 20, 12, 201, 21, 50, 201, 52, 243, 15, 28, 148, 203, 20, 12, 201, 16, 83, 132, 72, 243, 15, 28, 148, 203, 20, 0, 10, 199, 52, 20, 135, 5, 34, 78, 20, 20, 10, 199, 44, 243, 134, 85, 50, 79, 56, 20, 10, 199, 36, 211, 73, 77, 50, 79, 56, 20, 12, 201, 81, 32, 78, 77, 50, 210, 36, 33, 82, 20, 10, 199, 44, 243, 77, 20, 229, 5, 72, 20, 10, 199, 16, 148, 208, 21, 33, 197, 72, 20, 12, 201, 16, 83, 79, 57, 53, 18, 4, 229, 0, 20, 8, 67, 81, 34, 80, 21, 0, 10, 0, 11, 200, 72, 81, 140, 20, 180, 201, 60, 224, 20, 11, 200, 64, 84, 150, 21, 36, 201, 60, 224, 20, 11, 200, 44, 243, 150, 21, 36, 201, 60, 224, 20, 11, 200, 5, 37, 9, 24, 144, 201, 20, 192, 20, 7, 196, 88, 245, 5, 72, 20, 7, 196, 12, 149, 5, 72, 20, 9, 198, 16, 83, 79, 29, 32, 70, 20, 9, 198, 52, 244, 132, 20, 229, 0, 20, 7, 196, 80, 149, 1, 56, 21, 7, 196, 68, 21, 1, 72, 20, 7, 196, 44, 21, 1, 72, 20, 9, 198, 44, 243, 80, 5, 32, 66, 20, 11, 3, 95, 57, 15, 50, 37, 13, 50, 106, 0, 0, 15, 140, 16, 1, 12, 195, 166, 15, 14, 20, 15, 12, 15, 7, 20, 13, 138, 16, 18, 195, 166, 19, 20, 9, 14, 4, 5, 20, 0, 16, 141, 1, 14, 195, 166, 19, 20, 5, 19, 9, 15, 12, 15, 7, 20, 13, 202, 72, 85, 18, 60, 99, 5, 45, 50, 79, 56, 20, 0, 10, 199, 65, 35, 211, 20, 181, 15, 72, 20, 10, 199, 76, 82, 210, 21, 66, 79, 56, 20, 12, 201, 44, 243, 132, 20, 228, 193, 80, 147, 206, 20, 12, 201, 44, 243, 80, 20, 228, 193, 80, 147, 206, 20, 12, 201, 36, 195, 21, 77, 68, 129, 80, 147, 206, 20, 10, 199, 25, 83, 132, 5, 66, 79, 56, 20, 12, 201, 16, 148, 208, 20, 228, 193, 80, 147, 206, 20, 10, 199, 16, 147, 206, 101, 50, 83, 44, 20, 10, 199, 61, 37, 15, 16, 243, 148, 36, 20, 10, 199, 5, 36, 133, 77, 64, 78, 80, 20, 0, 12, 67, 77, 65, 71, 87, 70, 35, 57, 0, 14, 45, 11, 200, 65, 34, 78, 12, 148, 9, 20, 192, 20, 7, 196, 64, 148, 143, 48, 20, 12, 137, 22, 195, 166, 18, 20, 9, 14, 4, 5, 20, 9, 198, 24, 245, 15, 29, 32, 70, 20, 9, 198, 21, 67, 143, 29, 32, 70, 20, 11, 200, 52, 81, 9, 80, 84, 146, 4, 224, 21, 17, 3, 95, 49, 67, 36, 70, 15, 105, 6, 40, 50, 51, 13, 12, 84, 0, 0, 8, 197, 44, 243, 132, 61, 32, 20, 8, 197, 64, 192, 67, 21, 32, 20, 8, 197, 24, 244, 131, 21, 32, 20, 12, 137, 16, 195, 184, 14, 9, 20, 5, 14, 20, 20, 0, 9, 198, 29, 32, 86, 85, 33, 64, 20, 9, 198, 80, 19, 10, 21, 33, 64, 20, 9, 198, 24, 245, 82, 4, 113, 64, 20, 0, 10, 67, 81, 33, 64, 47, 34, 6, 36, 0, 10, 199, 64, 19, 9, 56, 68, 143, 52, 20, 10, 199, 16, 85, 137, 21, 34, 78, 28, 20, 10, 199, 64, 85, 9, 80, 84, 211, 20, 20, 0, 11, 200, 88, 148, 213, 4, 194, 83, 21, 32, 20, 11, 200, 88, 19, 132, 4, 194, 83, 21, 32, 20, 11, 200, 80, 84, 146, 61, 34, 83, 21, 32, 20, 11, 200, 77, 147, 66, 60, 194, 83, 21, 32, 20, 11, 200, 76, 240, 201, 4, 194, 83, 21, 32, 20, 11, 200, 72, 149, 21, 4, 194, 83, 21, 32, 20, 11, 200, 64, 21, 18, 60, 226, 83, 21, 32, 20, 11, 200, 56, 244, 141, 4, 194, 83, 21, 32, 20, 11, 200, 33, 145, 18, 60, 198, 83, 21, 32, 20, 11, 200, 24, 244, 141, 4, 194, 83, 21, 32, 20, 11, 200, 24, 84, 148, 36, 194, 83, 21, 32, 20, 11, 200, 16, 85, 18, 60, 226, 83, 21, 32, 20, 11, 200, 9, 37, 84, 4, 194, 83, 21, 32, 20, 11, 200, 4, 181, 21, 4, 194, 83, 21, 32, 20, 11, 200, 4, 178, 214, 36, 84, 195, 21, 32, 20, 9, 198, 49, 85, 8, 21, 32, 78, 20, 11, 200, 36, 224, 201, 80, 19, 69, 57, 64, 20, 0, 8, 197, 88, 84, 147, 21, 32, 20, 12, 201, 80, 83, 5, 29, 32, 70, 21, 33, 64, 20, 12, 201, 24, 245, 15, 29, 32, 70, 21, 33, 64, 20, 8, 197, 24, 20, 147, 21, 32, 20, 12, 201, 5, 85, 15, 29, 32, 70, 21, 33, 64, 20, 8, 197, 21, 33, 77, 37, 64, 20, 8, 197, 52, 17, 217, 5, 32, 20, 9, 198, 52, 20, 137, 56, 17, 5, 20, 0, 17, 70, 52, 150, 20, 85, 33, 64, 63, 36, 79, 87, 47, 57, 112, 0, 20, 9, 198, 25, 34, 84, 85, 33, 64, 20, 9, 198, 77, 69, 68, 21, 33, 64, 20, 9, 198, 29, 32, 68, 21, 33, 64, 20, 12, 137, 15, 16, 19, 195, 166, 20, 19, 9, 7, 20, 18, 143, 11, 1, 18, 18, 5, 2, 195, 166, 11, 19, 13, 9, 14, 4, 5, 20, 12, 3, 95, 49, 57, 50, 6, 36, 70, 14, 50, 0, 0, 10, 199, 76, 243, 4, 21, 34, 83, 80, 20, 10, 199, 32, 148, 212, 61, 34, 83, 80, 20, 10, 199, 24, 17, 207, 81, 66, 83, 80, 20, 14, 203, 44, 243, 77, 21, 32, 201, 4, 194, 83, 21, 32, 20, 14, 203, 36, 225, 9, 88, 145, 21, 4, 194, 83, 21, 32, 20, 16, 75, 84, 225, 5, 73, 53, 1, 80, 83, 69, 57, 64, 21, 0, 10, 11, 3, 95, 49, 56, 6, 108, 70, 14, 50, 0, 0, 10, 68, 28, 149, 133, 72, 79, 37, 34, 0, 11, 68, 20, 229, 5, 72, 36, 50, 47, 112, 0, 11, 200, 77, 1, 67, 36, 98, 67, 21, 32, 20, 11, 200, 73, 84, 211, 36, 98, 67, 21, 32, 20, 11, 200, 72, 83, 66, 61, 84, 147, 21, 32, 20, 11, 200, 44, 192, 82, 36, 98, 67, 21, 32, 20, 7, 196, 44, 21, 133, 72, 20, 11, 200, 36, 229, 5, 72, 84, 211, 21, 32, 20, 11, 200, 28, 195, 210, 36, 98, 67, 21, 32, 20, 7, 196, 28, 84, 133, 72, 20, 11, 200, 24, 19, 19, 36, 98, 67, 21, 32, 20, 11, 200, 16, 84, 201, 56, 98, 67, 21, 32, 20, 7, 196, 40, 21, 129, 56, 20, 9, 198, 61, 53, 9, 56, 21, 0, 20, 12, 201, 44, 243, 148, 4, 181, 6, 48, 17, 5, 20, 0, 8, 197, 45, 84, 201, 56, 80, 20, 12, 201, 80, 20, 5, 81, 49, 82, 36, 225, 192, 20, 12, 201, 72, 85, 133, 73, 49, 82, 36, 225, 192, 20, 12, 201, 72, 85, 129, 49, 81, 82, 36, 225, 192, 20, 12, 201, 72, 80, 76, 37, 49, 82, 36, 225, 192, 20, 12, 201, 24, 19, 148, 5, 49, 82, 36, 225, 192, 20, 12, 201, 21, 35, 212, 37, 49, 82, 36, 225, 192, 20, 12, 201, 20, 225, 15, 77, 49, 82, 36, 225, 192, 20, 12, 201, 16, 84, 12, 61, 145, 82, 36, 225, 192, 20, 12, 201, 4, 225, 204, 37, 49, 82, 36, 225, 192, 20, 12, 201, 4, 68, 133, 77, 49, 82, 36, 225, 192, 20, 9, 198, 45, 34, 84, 21, 34, 69, 20, 9, 198, 44, 243, 131, 36, 194, 69, 20, 0, 9, 198, 48, 147, 135, 88, 148, 212, 20, 9, 198, 76, 176, 66, 21, 34, 64, 20, 9, 198, 17, 34, 86, 21, 34, 64, 20, 9, 198, 52, 147, 143, 37, 50, 192, 20, 9, 198, 17, 37, 83, 37, 50, 192, 20, 9, 198, 81, 34, 86, 36, 19, 0, 20, 0, 10, 199, 72, 85, 15, 73, 50, 79, 56, 20, 10, 199, 16, 147, 69, 57, 50, 79, 56, 20, 10, 199, 72, 83, 66, 85, 36, 197, 72, 20, 10, 199, 72, 83, 1, 80, 149, 133, 72, 20, 10, 199, 20, 180, 212, 20, 225, 5, 72, 20, 10, 199, 16, 80, 197, 48, 84, 133, 72, 20, 9, 198, 61, 4, 137, 29, 66, 71, 20, 10, 199, 24, 244, 148, 72, 243, 9, 28, 20, 10, 199, 4, 100, 203, 100, 83, 9, 28, 20, 14, 203, 44, 20, 148, 4, 114, 78, 36, 83, 147, 21, 32, 20, 12, 201, 76, 82, 210, 21, 64, 82, 36, 21, 0, 20, 12, 201, 4, 229, 9, 45, 96, 82, 36, 21, 0, 20, 0, 21, 72, 72, 82, 137, 12, 84, 137, 56, 112, 34, 36, 57, 37, 87, 6, 36, 51, 37, 66, 0, 12, 201, 77, 1, 75, 81, 35, 211, 44, 244, 0, 20, 10, 135, 13, 1, 6, 9, 195, 184, 19, 20, 11, 200, 40, 84, 137, 44, 244, 143, 76, 80, 20, 11, 200, 25, 85, 21, 72, 243, 15, 28, 144, 20, 11, 200, 21, 50, 201, 52, 243, 15, 28, 144, 20, 11, 200, 16, 83, 132, 72, 243, 15, 28, 144, 20, 9, 198, 64, 19, 70, 48, 85, 0, 20, 11, 200, 8, 83, 133, 24, 144, 201, 84, 208, 67, 15, 204, 77, 148, 212, 20, 208, 84, 37, 49, 82, 36, 225, 192, 20, 11, 200, 77, 81, 134, 48, 84, 137, 56, 112, 20, 15, 204, 77, 64, 78, 16, 20, 132, 37, 49, 82, 36, 225, 192, 20, 11, 200, 76, 178, 84, 76, 84, 137, 56, 112, 20, 11, 200, 76, 84, 1, 72, 84, 137, 56, 112, 20, 15, 204, 76, 83, 147, 36, 34, 76, 37, 49, 82, 36, 225, 192, 20, 11, 200, 72, 82, 137, 12, 84, 137, 56, 112, 20, 11, 200, 64, 147, 15, 80, 84, 137, 56, 112, 20, 15, 204, 52, 21, 5, 72, 144, 76, 37, 49, 82, 36, 225, 192, 20, 11, 200, 52, 20, 137, 56, 84, 137, 56, 112, 20, 11, 200, 44, 243, 15, 72, 84, 137, 56, 112, 20, 11, 200, 44, 195, 193, 44, 84, 137, 56, 112, 20, 11, 200, 28, 20, 129, 28, 84, 137, 56, 112, 20, 11, 200, 24, 145, 213, 72, 84, 137, 56, 112, 20, 11, 200, 16, 19, 137, 76, 84, 137, 56, 112, 20, 15, 204, 8, 17, 193, 80, 83, 12, 37, 49, 82, 36, 225, 192, 20, 11, 200, 5, 52, 213, 72, 84, 137, 56, 112, 20, 7, 196, 16, 21, 5, 72, 20, 7, 196, 33, 99, 210, 36, 20, 11, 200, 64, 84, 148, 20, 229, 12, 36, 112, 20, 11, 200, 61, 3, 21, 44, 177, 76, 36, 112, 20, 11, 200, 60, 210, 25, 28, 113, 76, 36, 112, 20, 11, 200, 28, 83, 148, 4, 113, 76, 36, 112, 20, 11, 200, 24, 244, 148, 72, 147, 140, 36, 112, 20, 11, 200, 24, 244, 140, 36, 113, 76, 36, 112, 20, 11, 200, 81, 48, 82, 37, 53, 9, 76, 176, 20, 11, 200, 56, 244, 212, 4, 193, 201, 76, 176, 20, 11, 200, 37, 51, 205, 21, 68, 137, 76, 176, 20, 11, 200, 28, 83, 205, 21, 68, 137, 76, 176, 20, 11, 200, 8, 243, 66, 5, 53, 9, 76, 176, 20, 11, 200, 60, 229, 15, 28, 83, 133, 76, 80, 20, 11, 200, 8, 83, 133, 24, 144, 201, 84, 208, 20, 11, 200, 84, 226, 84, 5, 34, 83, 52, 80, 20, 11, 200, 64, 197, 82, 4, 194, 83, 52, 80, 20, 11, 200, 52, 17, 206, 21, 66, 83, 52, 80, 20, 11, 200, 33, 148, 14, 61, 66, 83, 52, 80, 20, 11, 200, 12, 19, 22, 36, 226, 83, 52, 80, 20, 0, 11, 136, 7, 12, 15, 18, 9, 195, 184, 19, 20, 12, 201, 76, 83, 147, 5, 66, 79, 56, 83, 0, 20, 12, 201, 80, 21, 84, 60, 195, 199, 37, 50, 192, 20, 12, 201, 76, 240, 201, 60, 195, 199, 37, 50, 192, 20, 12, 201, 76, 83, 73, 60, 195, 199, 37, 50, 192, 20, 12, 201, 65, 54, 75, 60, 195, 199, 37, 50, 192, 20, 12, 201, 64, 244, 148, 84, 114, 83, 37, 50, 192, 20, 12, 201, 33, 145, 18, 60, 195, 199, 37, 50, 192, 20, 12, 201, 28, 83, 133, 4, 195, 199, 37, 50, 192, 20, 12, 201, 25, 148, 201, 60, 195, 199, 37, 50, 192, 20, 12, 201, 21, 70, 77, 60, 195, 199, 37, 50, 192, 20, 0, 9, 198, 80, 83, 143, 72, 148, 212, 20, 9, 198, 28, 83, 210, 28, 148, 212, 20, 9, 198, 76, 243, 4, 21, 34, 64, 20, 9, 198, 65, 32, 76, 21, 34, 64, 20, 9, 198, 64, 147, 80, 21, 34, 64, 20, 9, 198, 64, 147, 12, 21, 34, 64, 20, 9, 198, 64, 19, 80, 21, 34, 64, 20, 9, 198, 52, 19, 20, 21, 34, 64, 20, 9, 198, 48, 245, 20, 21, 34, 64, 20, 9, 198, 33, 146, 204, 21, 34, 64, 20, 9, 198, 28, 19, 12, 21, 34, 64, 20, 9, 198, 9, 83, 20, 21, 34, 64, 20, 9, 198, 8, 21, 20, 21, 34, 64, 20, 9, 198, 5, 67, 205, 37, 50, 192, 20, 9, 198, 17, 147, 129, 52, 146, 192, 20, 9, 198, 16, 83, 79, 45, 32, 84, 20, 9, 198, 8, 148, 213, 48, 96, 84, 20, 9, 198, 8, 145, 78, 56, 19, 0, 20, 11, 3, 95, 49, 49, 6, 107, 55, 82, 13, 0, 0, 10, 199, 72, 81, 21, 45, 66, 79, 56, 20, 10, 199, 61, 1, 82, 5, 66, 79, 56, 20, 10, 199, 20, 208, 78, 5, 66, 79, 56, 20, 14, 203, 52, 18, 193, 16, 19, 73, 76, 84, 137, 56, 112, 20, 14, 203, 44, 195, 210, 60, 99, 210, 52, 84, 137, 56, 112, 20, 18, 207, 36, 229, 5, 48, 193, 75, 81, 80, 76, 37, 49, 82, 36, 225, 192, 20, 14, 203, 36, 225, 5, 45, 49, 82, 12, 84, 137, 56, 112, 20, 14, 203, 36, 212, 12, 20, 209, 78, 80, 84, 137, 56, 112, 20, 14, 203, 25, 32, 84, 21, 35, 137, 76, 84, 137, 56, 112, 20, 14, 203, 20, 180, 212, 72, 20, 15, 48, 84, 137, 56, 112, 20, 14, 203, 4, 194, 207, 32, 243, 9, 76, 84, 137, 56, 112, 20, 14, 203, 4, 67, 73, 56, 148, 212, 72, 84, 137, 56, 112, 20, 10, 199, 36, 229, 9, 52, 145, 5, 72, 20, 10, 199, 20, 180, 208, 48, 241, 5, 72, 20, 10, 199, 16, 83, 9, 44, 21, 5, 72, 20, 10, 199, 44, 243, 132, 37, 67, 210, 36, 20, 14, 203, 44, 20, 129, 45, 65, 82, 37, 53, 9, 76, 176, 20, 14, 203, 16, 83, 147, 37, 67, 205, 21, 68, 137, 76, 176, 20, 14, 203, 36, 225, 5, 80, 84, 141, 36, 226, 83, 52, 80, 20, 14, 203, 25, 83, 139, 80, 147, 206, 4, 194, 83, 52, 80, 20, 14, 203, 16, 242, 213, 52, 83, 148, 5, 34, 83, 52, 80, 20, 10, 199, 64, 19, 133, 29, 148, 137, 44, 20, 9, 3, 95, 49, 48, 47, 6, 37, 0, 0, 7, 196, 44, 19, 149, 80, 20, 11, 200, 36, 211, 85, 56, 243, 15, 28, 144, 20, 11, 200, 20, 118, 80, 80, 243, 15, 28, 144, 20, 11, 200, 60, 213, 18, 20, 229, 12, 36, 112, 20, 11, 200, 52, 241, 20, 4, 113, 76, 36, 112, 20, 11, 200, 40, 243, 70, 73, 81, 76, 36, 112, 20, 11, 200, 24, 244, 141, 20, 229, 12, 36, 112, 20, 11, 200, 24, 244, 129, 72, 113, 76, 36, 112, 20, 16, 141, 16, 1, 12, 195, 166, 15, 12, 9, 20, 9, 11, 21, 13, 20, 11, 200, 13, 144, 78, 44, 19, 9, 84, 208, 20, 7, 196, 48, 85, 137, 80, 20, 22, 72, 12, 19, 142, 20, 195, 15, 56, 144, 49, 108, 50, 13, 55, 6, 39, 12, 50, 37, 0, 20, 11, 200, 44, 244, 144, 84, 193, 78, 12, 80, 20, 7, 196, 76, 148, 129, 80, 20, 9, 68, 48, 85, 133, 48, 21, 0, 10, 13, 3, 95, 49, 51, 47, 51, 6, 109, 70, 14, 50, 0, 0, 12, 201, 76, 176, 78, 16, 147, 129, 88, 148, 212, 20, 12, 201, 28, 83, 146, 20, 208, 76, 21, 34, 64, 20, 12, 201, 4, 180, 207, 56, 243, 69, 81, 34, 64, 20, 12, 201, 80, 18, 211, 60, 227, 205, 37, 50, 192, 20, 12, 201, 65, 54, 75, 60, 177, 77, 37, 50, 192, 20, 12, 201, 64, 243, 25, 73, 149, 13, 37, 50, 192, 20, 12, 201, 29, 32, 70, 60, 227, 205, 37, 50, 192, 20, 12, 201, 16, 149, 25, 72, 19, 66, 37, 50, 192, 20, 12, 201, 5, 3, 204, 60, 113, 84, 37, 50, 192, 20, 12, 201, 8, 20, 137, 84, 212, 213, 48, 96, 84, 20, 10, 3, 95, 49, 50, 47, 6, 112, 55, 0, 0, 13, 202, 72, 85, 18, 61, 52, 5, 45, 66, 79, 56, 20, 13, 202, 64, 84, 147, 21, 97, 82, 5, 66, 79, 56, 20, 13, 202, 16, 85, 5, 72, 210, 78, 5, 66, 79, 56, 20, 17, 206, 61, 1, 82, 5, 66, 79, 56, 19, 9, 76, 84, 137, 56, 112, 20, 9, 198, 24, 19, 12, 21, 33, 84, 20, 9, 198, 20, 195, 216, 21, 33, 84, 20, 9, 198, 61, 34, 71, 36, 224, 76, 20, 9, 198, 12, 84, 133, 9, 32, 76, 20, 13, 3, 95, 49, 53, 81, 6, 36, 63, 47, 13, 50, 0, 0, 12, 137, 11, 1, 13, 195, 166, 12, 5, 15, 14, 20, 10, 199, 80, 149, 18, 21, 34, 78, 28, 20, 10, 199, 48, 149, 18, 21, 34, 78, 28, 20, 10, 199, 25, 34, 83, 21, 34, 78, 28, 20, 10, 199, 17, 32, 71, 21, 34, 78, 28, 20, 14, 203, 88, 81, 5, 73, 53, 25, 28, 113, 76, 36, 112, 20, 9, 198, 76, 144, 137, 72, 148, 203, 20, 9, 198, 28, 83, 210, 28, 148, 203, 20, 9, 198, 28, 83, 133, 72, 148, 203, 20, 9, 198, 20, 118, 80, 80, 148, 203, 20, 10, 199, 56, 18, 211, 44, 245, 137, 80, 20, 10, 199, 80, 82, 206, 60, 180, 129, 80, 20, 10, 199, 77, 3, 206, 76, 244, 129, 80, 20, 14, 3, 95, 49, 52, 81, 57, 6, 39, 34, 70, 14, 50, 0, 0, 9, 198, 5, 67, 205, 37, 53, 0, 20, 7, 196, 32, 245, 5, 48, 20, 9, 198, 52, 147, 135, 20, 193, 82, 20, 9, 198, 44, 244, 146, 60, 65, 82, 20, 9, 198, 24, 245, 82, 4, 113, 82, 20, 9, 198, 16, 148, 211, 36, 65, 82, 20, 9, 198, 5, 69, 18, 4, 129, 82, 20, 6, 195, 21, 2, 75, 20, 7, 196, 88, 149, 1, 48, 20, 7, 196, 80, 245, 1, 48, 20, 10, 3, 95, 52, 15, 81, 57, 36, 112, 0, 12, 3, 95, 49, 55, 87, 6, 116, 70, 14, 50, 0, 0, 14, 139, 1, 18, 2, 9, 20, 18, 1, 7, 195, 184, 18, 20, 9, 198, 56, 243, 79, 29, 32, 77, 20, 9, 198, 24, 245, 15, 29, 32, 77, 20, 14, 3, 95, 49, 54, 87, 6, 35, 57, 87, 70, 14, 50, 0, 0, 13, 202, 81, 148, 15, 29, 32, 70, 21, 34, 78, 28, 20, 13, 202, 77, 147, 148, 21, 66, 83, 21, 34, 78, 28, 20, 13, 202, 77, 68, 149, 45, 69, 82, 21, 34, 78, 28, 20, 13, 202, 72, 243, 65, 57, 66, 83, 21, 34, 78, 28, 20, 13, 202, 65, 83, 22, 21, 34, 83, 21, 34, 78, 28, 20, 13, 202, 65, 34, 86, 5, 66, 83, 21, 34, 78, 28, 20, 13, 202, 64, 84, 137, 60, 66, 83, 21, 34, 78, 28, 20, 13, 202, 64, 20, 211, 37, 98, 83, 21, 34, 78, 28, 20, 13, 202, 48, 149, 15, 29, 32, 70, 21, 34, 78, 28, 20, 13, 202, 48, 16, 137, 4, 194, 83, 21, 34, 78, 28, 20, 13, 202, 44, 19, 148, 60, 226, 83, 21, 34, 78, 28, 20, 13, 202, 36, 226, 210, 36, 210, 78, 21, 34, 78, 28, 20, 13, 202, 36, 212, 18, 61, 98, 83, 21, 34, 78, 28, 20, 13, 202, 16, 85, 5, 72, 210, 78, 21, 34, 78, 28, 20, 13, 202, 8, 20, 130, 5, 34, 83, 21, 34, 78, 28, 20, 12, 201, 76, 176, 78, 16, 147, 129, 88, 148, 203, 20, 12, 201, 76, 49, 78, 60, 116, 129, 24, 148, 203, 20, 12, 201, 72, 84, 18, 60, 116, 129, 24, 148, 203, 20, 12, 201, 72, 81, 143, 72, 210, 83, 80, 148, 203, 20, 12, 201, 64, 244, 142, 60, 116, 129, 24, 148, 203, 20, 12, 201, 64, 243, 25, 80, 82, 83, 80, 148, 203, 20, 12, 201, 44, 20, 132, 36, 243, 15, 28, 148, 203, 20, 12, 201, 33, 145, 18, 60, 116, 129, 24, 148, 203, 20, 14, 139, 11, 22, 195, 166, 18, 21, 12, 1, 14, 3, 5, 20, 0, 10, 199, 52, 146, 210, 61, 50, 207, 64, 20, 12, 201, 16, 85, 5, 72, 210, 78, 37, 53, 0, 20, 10, 199, 88, 149, 129, 12, 149, 5, 80, 20, 10, 199, 64, 243, 1, 72, 149, 5, 80, 20, 10, 199, 52, 147, 143, 72, 149, 5, 80, 20, 10, 199, 48, 21, 9, 56, 149, 5, 80, 20, 10, 199, 45, 96, 78, 80, 149, 5, 80, 20, 10, 199, 44, 243, 137, 12, 149, 5, 80, 20, 10, 199, 44, 20, 1, 12, 149, 5, 80, 20, 10, 199, 36, 65, 78, 80, 149, 5, 80, 20, 10, 199, 25, 85, 9, 48, 149, 5, 80, 20, 10, 199, 21, 67, 137, 12, 149, 5, 80, 20, 9, 198, 92, 19, 9, 76, 148, 203, 20, 9, 198, 80, 83, 65, 80, 148, 203, 20, 9, 198, 48, 144, 133, 72, 148, 203, 20, 9, 198, 4, 116, 129, 72, 148, 203, 20, 10, 199, 76, 83, 73, 56, 20, 137, 20, 20, 10, 199, 76, 19, 129, 80, 244, 137, 20, 20, 9, 198, 16, 241, 205, 5, 66, 75, 20, 15, 3, 95, 55, 88, 105, 108, 55, 81, 57, 6, 108, 34, 87, 0, 0, 9, 198, 65, 35, 195, 20, 65, 82, 20, 11, 136, 19, 195, 166, 2, 25, 14, 9, 20, 20, 9, 198, 80, 19, 66, 85, 34, 78, 20, 9, 198, 64, 21, 9, 20, 229, 0, 20, 9, 198, 64, 20, 211, 4, 229, 0, 20, 0, 12, 201, 72, 80, 201, 65, 35, 195, 37, 65, 84, 20, 16, 205, 9, 84, 133, 5, 82, 210, 5, 66, 83, 21, 34, 78, 28, 20, 15, 204, 65, 54, 75, 60, 194, 78, 29, 98, 83, 80, 148, 203, 20, 8, 197, 9, 35, 205, 36, 64, 20, 9, 198, 48, 20, 135, 21, 52, 197, 20, 8, 197, 81, 34, 75, 36, 224, 20, 8, 197, 80, 18, 87, 4, 224, 20, 8, 197, 80, 18, 87, 4, 224, 21, 8, 197, 64, 20, 195, 4, 192, 20, 0, 13, 202, 77, 81, 199, 21, 53, 9, 88, 149, 5, 80, 20, 13, 202, 65, 35, 196, 84, 181, 9, 88, 149, 5, 80, 20, 13, 202, 44, 243, 132, 84, 181, 9, 88, 149, 5, 80, 20, 13, 202, 16, 84, 18, 21, 52, 201, 88, 149, 5, 80, 20, 12, 201, 80, 84, 141, 60, 209, 84, 72, 148, 203, 20, 12, 201, 77, 65, 82, 20, 241, 143, 56, 148, 203, 20, 12, 201, 52, 246, 129, 52, 34, 81, 84, 148, 203, 20, 12, 201, 52, 240, 193, 52, 34, 81, 84, 148, 203, 20, 13, 202, 20, 180, 193, 52, 147, 129, 80, 244, 137, 20, 20, 0, 10, 199, 36, 211, 85, 56, 243, 15, 28, 20, 10, 199, 77, 84, 208, 20, 225, 5, 72, 20, 11, 136, 10, 195, 184, 4, 9, 14, 4, 5, 20, 10, 199, 5, 85, 15, 52, 21, 9, 44, 20, 10, 199, 52, 19, 12, 61, 32, 201, 56, 20, 10, 199, 44, 243, 77, 20, 229, 1, 72, 20, 10, 199, 36, 228, 201, 57, 80, 78, 80, 20, 0, 9, 198, 64, 85, 9, 80, 147, 206, 20, 9, 198, 5, 81, 9, 80, 147, 206, 20, 11, 200, 76, 82, 214, 20, 229, 9, 20, 192, 20, 11, 200, 44, 243, 77, 21, 32, 201, 20, 192, 20, 7, 196, 72, 245, 5, 72, 20, 7, 196, 16, 245, 5, 72, 20, 11, 200, 36, 225, 15, 56, 84, 201, 20, 224, 20, 9, 198, 97, 147, 15, 29, 32, 70, 20, 9, 198, 48, 149, 15, 29, 32, 70, 20, 9, 198, 44, 83, 73, 29, 32, 70, 20, 7, 196, 60, 181, 1, 56, 21, 7, 196, 56, 245, 1, 72, 20, 7, 196, 12, 149, 1, 72, 20, 9, 198, 9, 34, 83, 4, 229, 0, 20, 9, 198, 89, 83, 14, 21, 32, 66, 20, 0, 12, 201, 4, 32, 146, 21, 98, 65, 81, 84, 128, 20, 8, 197, 80, 19, 80, 60, 224, 20, 9, 198, 5, 53, 18, 60, 227, 205, 20, 8, 197, 76, 84, 137, 20, 192, 20, 9, 198, 80, 83, 203, 72, 21, 9, 20, 8, 197, 80, 243, 147, 36, 192, 20, 8, 197, 89, 83, 11, 4, 224, 21, 8, 197, 88, 84, 147, 4, 192, 20, 0, 0, 10, 199, 4, 113, 210, 21, 52, 207, 72, 20, 10, 199, 65, 34, 79, 72, 149, 5, 72, 20, 10, 199, 88, 19, 139, 84, 225, 9, 28, 20, 10, 199, 52, 83, 147, 40, 85, 137, 44, 20, 10, 199, 76, 19, 65, 72, 149, 1, 56, 20, 12, 201, 32, 148, 212, 61, 34, 79, 29, 32, 70, 20, 10, 199, 76, 19, 65, 72, 149, 1, 56, 21, 10, 199, 36, 211, 73, 29, 32, 78, 80, 20, 10, 199, 12, 83, 5, 9, 32, 78, 80, 20, 0, 11, 200, 12, 244, 212, 5, 34, 67, 4, 224, 20, 9, 198, 80, 244, 15, 29, 32, 70, 20, 9, 198, 80, 83, 5, 29, 32, 70, 20, 9, 198, 32, 243, 79, 29, 32, 70, 20, 9, 198, 5, 85, 15, 29, 32, 70, 20, 0, 8, 197, 72, 245, 76, 21, 32, 20, 8, 197, 36, 210, 84, 21, 32, 20, 8, 197, 25, 34, 84, 21, 32, 20, 12, 137, 13, 5, 4, 9, 195, 166, 22, 1, 12, 20, 0, 13, 202, 88, 84, 147, 36, 98, 75, 5, 66, 79, 56, 20, 13, 202, 77, 65, 82, 36, 194, 83, 5, 66, 79, 56, 20, 13, 202, 77, 1, 67, 36, 98, 75, 5, 66, 79, 56, 20, 13, 202, 76, 240, 201, 4, 194, 83, 5, 66, 79, 56, 20, 13, 202, 53, 148, 212, 36, 98, 75, 5, 66, 79, 56, 20, 13, 202, 36, 229, 5, 73, 35, 199, 5, 66, 79, 56, 20, 13, 202, 29, 32, 84, 36, 98, 75, 5, 66, 79, 56, 20, 9, 198, 29, 32, 86, 21, 33, 64, 20, 9, 198, 9, 37, 78, 21, 33, 64, 20, 8, 67, 76, 86, 25, 21, 0, 10, 0, 9, 198, 44, 144, 83, 80, 148, 203, 20, 9, 198, 32, 84, 141, 21, 66, 75, 20, 12, 201, 44, 147, 133, 52, 21, 15, 29, 32, 70, 20, 10, 199, 52, 243, 147, 81, 32, 78, 76, 20, 0, 12, 201, 20, 224, 197, 24, 19, 15, 29, 32, 77, 20, 11, 200, 81, 34, 65, 56, 117, 76, 21, 32, 20, 11, 200, 77, 68, 129, 56, 117, 76, 21, 32, 20, 11, 200, 72, 80, 201, 72, 181, 76, 21, 32, 20, 11, 200, 65, 35, 211, 64, 82, 212, 21, 32, 20, 11, 200, 64, 20, 148, 36, 50, 80, 21, 32, 20, 0, 9, 198, 44, 147, 15, 29, 32, 77, 20, 9, 198, 32, 243, 15, 29, 32, 77, 20, 12, 201, 77, 68, 149, 45, 69, 82, 21, 33, 64, 20, 12, 201, 76, 181, 76, 65, 69, 82, 21, 33, 64, 20, 8, 197, 17, 32, 80, 21, 32, 20, 8, 197, 40, 84, 213, 37, 64, 20, 0, 9, 198, 80, 84, 212, 21, 33, 64, 20, 9, 198, 72, 84, 212, 21, 33, 64, 20, 9, 198, 64, 244, 212, 21, 33, 64, 20, 9, 198, 16, 243, 12, 21, 33, 64, 20, 0, 11, 4, 9, 4, 195, 169, 37, 70, 6, 36, 0, 9, 198, 56, 243, 65, 16, 148, 203, 20, 9, 198, 17, 147, 129, 52, 148, 203, 20, 9, 198, 4, 194, 193, 48, 148, 203, 20, 0, 11, 200, 44, 20, 129, 52, 35, 204, 21, 32, 20, 11, 200, 28, 84, 212, 36, 181, 76, 21, 32, 20, 11, 200, 60, 209, 143, 72, 213, 76, 21, 32, 20, 7, 196, 12, 148, 133, 72, 20, 9, 198, 16, 81, 137, 12, 149, 0, 20, 7, 196, 24, 20, 137, 56, 20, 7, 196, 4, 196, 9, 56, 20, 9, 198, 4, 225, 15, 73, 32, 78, 20, 9, 198, 44, 19, 9, 24, 21, 0, 20, 7, 196, 4, 197, 1, 56, 21, 0, 8, 197, 16, 148, 12, 60, 208, 20, 12, 201, 44, 243, 148, 72, 243, 12, 21, 33, 64, 20, 9, 198, 76, 49, 78, 5, 34, 69, 20, 9, 198, 76, 49, 78, 5, 34, 69, 20, 9, 198, 53, 148, 212, 21, 34, 69, 20, 9, 198, 16, 85, 84, 21, 34, 69, 20, 8, 197, 36, 225, 82, 80, 144, 20, 8, 197, 45, 34, 84, 36, 176, 20, 9, 198, 72, 85, 129, 56, 50, 5, 20, 0, 9, 198, 45, 83, 20, 85, 33, 76, 20, 9, 198, 77, 98, 78, 21, 34, 64, 20, 9, 198, 76, 49, 78, 21, 34, 64, 20, 9, 198, 17, 33, 74, 21, 34, 64, 20, 9, 198, 65, 35, 214, 77, 66, 64, 20, 0, 10, 199, 64, 243, 9, 80, 243, 15, 28, 20, 10, 199, 32, 85, 5, 72, 243, 15, 28, 20, 10, 199, 44, 244, 146, 61, 50, 79, 56, 20, 10, 199, 20, 180, 208, 4, 225, 5, 72, 20, 10, 199, 16, 145, 134, 84, 225, 5, 72, 20, 10, 199, 17, 34, 76, 4, 117, 9, 28, 20, 10, 199, 24, 243, 129, 77, 65, 78, 36, 20, 10, 199, 17, 34, 76, 4, 117, 9, 28, 20, 0, 23, 72, 4, 98, 67, 36, 243, 129, 16, 240, 35, 81, 37, 87, 57, 39, 6, 50, 35, 12, 70, 39, 0, 10, 135, 11, 15, 16, 9, 195, 184, 19, 20, 10, 135, 4, 21, 2, 9, 195, 184, 19, 20, 9, 134, 8, 21, 13, 195, 184, 18, 20, 7, 196, 24, 85, 5, 72, 20, 11, 200, 4, 225, 210, 36, 33, 76, 36, 112, 20, 11, 200, 4, 195, 73, 56, 65, 76, 36, 112, 20, 11, 200, 48, 144, 129, 56, 84, 201, 76, 176, 20, 11, 200, 36, 225, 15, 56, 84, 201, 76, 176, 20, 11, 200, 28, 16, 143, 56, 84, 201, 76, 176, 20, 11, 200, 64, 244, 212, 49, 81, 9, 84, 208, 20, 9, 198, 64, 20, 129, 44, 149, 0, 20, 9, 198, 16, 243, 5, 72, 149, 0, 20, 7, 196, 17, 84, 201, 56, 20, 11, 200, 72, 81, 143, 72, 210, 83, 52, 80, 20, 11, 200, 64, 243, 25, 80, 82, 83, 52, 80, 20, 11, 200, 61, 53, 18, 4, 178, 83, 52, 80, 20, 11, 200, 56, 244, 150, 4, 114, 83, 52, 80, 20, 11, 200, 53, 148, 212, 36, 50, 83, 52, 80, 20, 11, 200, 28, 145, 193, 57, 66, 83, 52, 80, 20, 11, 200, 28, 84, 141, 4, 226, 83, 52, 80, 20, 11, 200, 4, 225, 204, 36, 50, 83, 52, 80, 20, 11, 200, 4, 176, 68, 20, 210, 83, 52, 80, 20, 9, 198, 65, 34, 79, 72, 21, 0, 20, 7, 196, 52, 85, 1, 56, 21, 7, 196, 80, 21, 1, 72, 20, 8, 67, 24, 246, 0, 21, 0, 10, 0, 8, 197, 81, 149, 133, 72, 144, 20, 8, 197, 72, 241, 5, 72, 144, 20, 12, 201, 45, 96, 75, 76, 19, 22, 21, 34, 64, 20, 8, 197, 44, 241, 197, 72, 144, 20, 8, 197, 40, 17, 197, 72, 144, 20, 8, 197, 8, 17, 197, 72, 144, 20, 12, 201, 44, 20, 143, 48, 147, 135, 37, 50, 192, 20, 9, 198, 8, 50, 75, 61, 34, 69, 20, 9, 198, 21, 2, 90, 60, 245, 9, 20, 9, 198, 16, 144, 84, 21, 35, 73, 20, 8, 197, 77, 64, 84, 36, 176, 20, 12, 201, 80, 84, 146, 37, 67, 210, 36, 19, 0, 20, 0, 12, 137, 15, 6, 6, 9, 3, 9, 195, 184, 19, 20, 9, 198, 48, 83, 137, 56, 148, 212, 20, 9, 198, 33, 83, 79, 72, 148, 212, 20, 9, 198, 80, 20, 16, 21, 34, 64, 20, 9, 198, 76, 182, 68, 21, 34, 64, 20, 9, 198, 76, 182, 68, 21, 34, 64, 20, 9, 198, 76, 19, 20, 21, 34, 64, 20, 9, 198, 72, 148, 212, 21, 34, 64, 20, 9, 198, 52, 244, 212, 21, 34, 64, 20, 9, 198, 48, 20, 16, 21, 34, 64, 20, 9, 198, 40, 20, 16, 21, 34, 64, 20, 9, 198, 33, 148, 212, 21, 34, 64, 20, 9, 198, 24, 81, 20, 21, 34, 64, 20, 9, 198, 17, 32, 80, 21, 34, 64, 20, 9, 198, 9, 38, 68, 21, 34, 64, 20, 9, 198, 8, 85, 12, 21, 34, 64, 20, 13, 202, 28, 83, 129, 57, 97, 78, 16, 83, 9, 28, 20, 9, 198, 5, 34, 193, 37, 50, 192, 20, 9, 198, 16, 84, 208, 61, 66, 64, 20, 9, 198, 64, 20, 203, 88, 147, 0, 20, 13, 138, 6, 195, 166, 14, 15, 13, 5, 14, 1, 12, 20, 9, 198, 24, 81, 5, 72, 19, 0, 20, 0, 13, 138, 11, 15, 14, 20, 1, 7, 9, 195, 184, 19, 20, 13, 138, 11, 1, 16, 18, 9, 3, 9, 195, 184, 19, 20, 13, 138, 9, 14, 3, 5, 19, 20, 21, 195, 184, 19, 20, 10, 199, 81, 32, 68, 37, 66, 79, 56, 20, 10, 199, 76, 83, 5, 45, 66, 79, 56, 20, 10, 199, 44, 243, 12, 5, 66, 79, 56, 20, 10, 199, 29, 32, 68, 5, 66, 79, 56, 20, 10, 199, 44, 243, 142, 20, 181, 5, 72, 20, 10, 199, 4, 48, 197, 57, 69, 69, 72, 20, 14, 203, 48, 245, 141, 20, 66, 15, 48, 65, 76, 36, 112, 20, 14, 203, 77, 68, 149, 45, 69, 82, 4, 194, 83, 52, 80, 20, 14, 203, 65, 35, 212, 21, 53, 1, 57, 66, 83, 52, 80, 20, 14, 203, 44, 244, 205, 61, 3, 204, 37, 66, 83, 52, 80, 20, 14, 203, 44, 244, 144, 61, 32, 84, 37, 98, 83, 52, 80, 20, 14, 203, 36, 225, 21, 77, 68, 137, 4, 194, 83, 52, 80, 20, 10, 199, 25, 148, 147, 80, 147, 132, 20, 20, 12, 201, 65, 35, 212, 60, 179, 204, 48, 21, 0, 20, 10, 69, 48, 20, 20, 61, 0, 21, 0, 10, 11, 3, 95, 50, 88, 47, 6, 114, 12, 58, 0, 0, 14, 139, 11, 15, 13, 16, 5, 14, 4, 9, 195, 184, 19, 20, 9, 134, 4, 21, 19, 195, 184, 18, 20, 9, 198, 44, 20, 213, 37, 53, 0, 20, 11, 200, 48, 145, 197, 52, 17, 197, 72, 144, 20, 11, 200, 61, 4, 137, 56, 65, 76, 36, 112, 20, 15, 204, 44, 20, 148, 4, 114, 78, 36, 83, 147, 37, 50, 192, 20, 12, 201, 16, 148, 12, 60, 208, 84, 5, 34, 69, 20, 11, 200, 48, 147, 135, 88, 148, 212, 36, 176, 20, 7, 196, 88, 149, 129, 80, 20, 7, 196, 72, 149, 129, 48, 20, 0, 12, 201, 45, 96, 78, 80, 85, 5, 61, 34, 64, 20, 12, 201, 44, 19, 77, 21, 32, 84, 21, 34, 64, 20, 12, 201, 76, 243, 129, 72, 20, 16, 5, 32, 84, 20, 12, 201, 44, 20, 132, 36, 224, 76, 80, 19, 0, 20, 0, 13, 202, 81, 34, 65, 56, 117, 76, 5, 66, 79, 56, 20, 13, 202, 81, 32, 78, 76, 195, 203, 5, 66, 79, 56, 20, 13, 202, 77, 68, 129, 56, 117, 76, 5, 66, 79, 56, 20, 13, 202, 44, 243, 148, 20, 212, 12, 5, 66, 79, 56, 20, 13, 202, 36, 229, 18, 61, 52, 5, 45, 66, 79, 56, 20, 13, 202, 36, 212, 18, 61, 98, 83, 5, 66, 79, 56, 20, 13, 202, 4, 178, 207, 52, 211, 196, 5, 66, 79, 56, 20, 0, 12, 201, 61, 4, 15, 73, 69, 78, 37, 53, 0, 20, 14, 203, 64, 192, 84, 80, 83, 147, 48, 17, 197, 72, 144, 20, 14, 203, 76, 19, 77, 20, 225, 143, 48, 65, 76, 36, 112, 20, 10, 199, 8, 144, 140, 36, 241, 137, 48, 20, 10, 199, 60, 36, 197, 73, 96, 78, 76, 20, 0, 9, 198, 80, 19, 66, 85, 33, 82, 20, 9, 198, 72, 83, 73, 81, 65, 82, 20, 9, 198, 72, 82, 213, 73, 33, 82, 20, 9, 198, 64, 148, 5, 81, 65, 82, 20, 9, 198, 44, 243, 142, 61, 65, 82, 20, 9, 198, 44, 243, 80, 5, 33, 82, 20, 9, 198, 45, 35, 205, 5, 66, 78, 20, 7, 196, 56, 245, 1, 80, 20, 7, 196, 8, 21, 1, 80, 20, 9, 198, 77, 80, 139, 85, 64, 78, 21, 7, 196, 52, 85, 1, 48, 20, 7, 196, 48, 85, 1, 48, 20, 7, 196, 24, 21, 1, 48, 20, 10, 3, 95, 56, 15, 112, 47, 50, 106, 0, 0, 13, 138, 1, 4, 8, 195, 166, 18, 5, 14, 3, 5, 20, 0, 9, 198, 16, 83, 147, 37, 65, 84, 20, 11, 136, 11, 15, 8, 195, 166, 18, 5, 18, 20, 11, 136, 1, 4, 8, 195, 166, 18, 5, 18, 20, 9, 198, 80, 19, 10, 21, 33, 84, 20, 14, 139, 18, 5, 14, 195, 166, 19, 19, 1, 14, 3, 5, 20, 0, 12, 201, 65, 34, 77, 37, 66, 86, 37, 53, 0, 20, 12, 201, 36, 195, 21, 76, 147, 206, 37, 53, 0, 20, 10, 199, 85, 32, 129, 56, 149, 5, 80, 20, 10, 199, 65, 34, 79, 72, 149, 5, 80, 20, 10, 199, 33, 83, 65, 56, 149, 5, 80, 20, 10, 199, 4, 181, 9, 88, 149, 5, 80, 20, 12, 201, 45, 96, 75, 76, 19, 22, 21, 33, 82, 20, 12, 201, 9, 35, 206, 44, 244, 203, 61, 1, 82, 20, 10, 199, 77, 66, 80, 20, 225, 9, 20, 20, 10, 199, 44, 243, 80, 20, 225, 9, 20, 20, 9, 198, 45, 35, 205, 5, 66, 75, 20, 0, 9, 198, 80, 83, 80, 21, 33, 82, 20, 9, 198, 77, 147, 139, 61, 1, 82, 20, 9, 198, 72, 84, 207, 49, 97, 82, 20, 9, 198, 36, 226, 214, 37, 33, 82, 20, 7, 196, 29, 86, 65, 56, 20, 11, 200, 44, 243, 150, 21, 33, 197, 57, 48, 20, 9, 198, 76, 147, 85, 49, 64, 78, 21, 9, 198, 24, 147, 9, 29, 32, 78, 21, 0, 8, 197, 56, 85, 82, 60, 224, 20, 9, 198, 52, 85, 18, 60, 227, 205, 20, 12, 201, 64, 84, 144, 48, 82, 211, 37, 65, 84, 20, 12, 201, 29, 32, 78, 16, 147, 211, 37, 65, 84, 20, 9, 198, 81, 32, 86, 21, 53, 9, 20, 8, 197, 32, 84, 143, 36, 224, 20, 8, 197, 17, 82, 212, 36, 192, 20, 8, 197, 12, 242, 84, 4, 192, 20, 0, 13, 202, 72, 81, 140, 20, 180, 201, 88, 149, 5, 80, 20, 13, 202, 44, 243, 12, 20, 181, 9, 88, 149, 5, 80, 20, 13, 202, 37, 36, 133, 29, 83, 1, 72, 149, 5, 80, 20, 13, 202, 20, 180, 203, 49, 84, 201, 88, 149, 5, 80, 20, 9, 198, 52, 85, 5, 61, 34, 84, 20, 11, 70, 24, 148, 133, 92, 19, 12, 21, 0, 10, 0, 10, 199, 60, 67, 206, 80, 243, 15, 28, 20, 10, 199, 60, 49, 65, 56, 243, 15, 28, 20, 12, 201, 60, 212, 212, 73, 82, 212, 85, 33, 82, 20, 12, 201, 72, 84, 212, 73, 82, 212, 85, 33, 82, 20, 10, 199, 72, 84, 197, 73, 97, 82, 20, 20, 10, 199, 72, 84, 15, 73, 65, 82, 20, 20, 10, 199, 64, 21, 5, 57, 65, 82, 20, 20, 10, 199, 16, 84, 197, 73, 65, 82, 20, 20, 10, 199, 5, 69, 5, 77, 65, 82, 20, 20, 0, 12, 137, 1, 14, 195, 166, 19, 20, 5, 19, 9, 20, 9, 198, 8, 245, 73, 48, 195, 206, 20, 12, 201, 48, 16, 143, 72, 21, 15, 72, 149, 77, 20, 11, 200, 64, 243, 25, 56, 84, 201, 20, 224, 20, 11, 200, 52, 83, 1, 56, 84, 201, 20, 224, 20, 9, 198, 5, 35, 69, 56, 145, 78, 20, 9, 198, 4, 208, 137, 20, 229, 0, 20, 9, 198, 81, 32, 70, 36, 176, 66, 20, 9, 68, 77, 21, 65, 92, 21, 0, 10, 12, 3, 95, 63, 63, 87, 114, 63, 69, 39, 55, 0, 0, 13, 138, 19, 25, 14, 195, 166, 19, 20, 5, 19, 9, 20, 13, 138, 11, 9, 14, 195, 166, 19, 20, 5, 19, 9, 20, 12, 201, 20, 180, 208, 60, 225, 78, 80, 145, 76, 20, 8, 197, 24, 195, 206, 20, 192, 20, 8, 197, 28, 198, 75, 60, 192, 20, 9, 198, 72, 81, 149, 28, 149, 77, 20, 9, 198, 36, 225, 9, 12, 149, 77, 20, 9, 198, 16, 83, 9, 72, 149, 77, 20, 8, 197, 72, 84, 20, 36, 192, 20, 8, 197, 64, 148, 212, 36, 192, 20, 8, 197, 9, 84, 139, 36, 224, 20, 12, 137, 11, 15, 8, 195, 166, 18, 5, 14, 20, 20, 0, 11, 66, 53, 32, 63, 36, 87, 47, 112, 0, 25, 19, 144, 11, 195, 184, 14, 19, 4, 9, 19, 11, 18, 9, 13, 9, 14, 5, 18, 20, 13, 202, 76, 83, 22, 8, 82, 1, 28, 83, 9, 28, 20, 9, 198, 64, 21, 9, 20, 228, 192, 20, 9, 198, 5, 81, 9, 20, 228, 192, 20, 0, 10, 199, 65, 35, 202, 20, 181, 15, 72, 20, 12, 137, 12, 9, 20, 20, 5, 18, 195, 166, 18, 20, 10, 199, 72, 85, 129, 56, 50, 5, 72, 20, 10, 199, 36, 225, 11, 61, 2, 69, 72, 20, 10, 199, 16, 148, 212, 72, 18, 5, 72, 20, 10, 199, 4, 68, 133, 77, 49, 82, 20, 20, 10, 199, 24, 244, 142, 84, 101, 9, 28, 20, 10, 199, 81, 32, 77, 64, 243, 9, 56, 20, 10, 199, 72, 84, 213, 49, 64, 78, 80, 20, 10, 199, 60, 36, 197, 73, 96, 78, 80, 20, 11, 3, 95, 52, 88, 81, 6, 116, 12, 112, 0, 0, 13, 138, 16, 5, 14, 19, 9, 15, 14, 195, 166, 18, 20, 12, 201, 76, 181, 70, 24, 81, 1, 72, 149, 77, 20, 12, 201, 44, 243, 77, 37, 52, 207, 72, 149, 77, 20, 0, 14, 139, 6, 21, 14, 11, 20, 9, 15, 14, 195, 166, 18, 20, 8, 197, 76, 177, 76, 21, 64, 20, 8, 197, 72, 245, 76, 21, 64, 20, 8, 197, 8, 147, 12, 21, 64, 20, 8, 197, 89, 84, 132, 21, 32, 20, 8, 197, 20, 66, 84, 21, 32, 20, 8, 197, 16, 146, 212, 21, 32, 20, 9, 198, 77, 147, 77, 21, 68, 137, 20, 8, 197, 45, 98, 86, 37, 64, 20, 8, 197, 20, 35, 206, 37, 64, 20, 6, 195, 60, 208, 78, 20, 8, 197, 72, 80, 197, 57, 64, 20, 8, 197, 65, 34, 86, 5, 64, 20, 8, 197, 45, 32, 66, 5, 64, 20, 6, 195, 60, 208, 78, 21, 10, 69, 77, 2, 82, 37, 64, 21, 0, 10, 0, 11, 136, 19, 5, 11, 21, 12, 195, 166, 18, 20, 11, 136, 18, 5, 7, 21, 12, 195, 166, 18, 20, 15, 140, 16, 18, 195, 166, 12, 9, 13, 9, 14, 195, 166, 18, 20, 15, 140, 9, 14, 6, 12, 1, 20, 9, 15, 14, 195, 166, 18, 20, 15, 140, 5, 22, 15, 12, 21, 20, 9, 15, 14, 195, 166, 18, 20, 10, 135, 6, 195, 184, 12, 5, 18, 9, 20, 9, 198, 76, 243, 1, 72, 145, 64, 20, 9, 198, 41, 81, 9, 12, 145, 64, 20, 12, 137, 11, 15, 8, 195, 166, 18, 5, 14, 19, 20, 12, 137, 1, 4, 8, 195, 166, 18, 5, 14, 19, 20, 9, 198, 72, 83, 143, 56, 49, 64, 20, 9, 198, 36, 212, 5, 72, 144, 76, 20, 0, 16, 141, 18, 5, 22, 15, 12, 21, 20, 9, 15, 14, 195, 166, 18, 20, 12, 137, 11, 15, 14, 19, 21, 12, 195, 166, 18, 20, 12, 137, 7, 18, 1, 14, 21, 12, 195, 166, 18, 20, 16, 141, 4, 9, 19, 11, 18, 5, 20, 9, 15, 14, 195, 166, 18, 20, 12, 137, 3, 9, 18, 11, 21, 12, 195, 166, 18, 20, 10, 199, 76, 244, 148, 21, 34, 78, 28, 20, 10, 199, 76, 21, 84, 21, 34, 78, 28, 20, 10, 199, 73, 83, 132, 21, 34, 78, 28, 20, 10, 199, 60, 181, 76, 21, 34, 78, 28, 20, 10, 199, 44, 243, 148, 21, 34, 78, 28, 20, 10, 199, 44, 20, 148, 21, 34, 78, 28, 20, 10, 199, 9, 35, 196, 21, 34, 78, 28, 20, 11, 136, 19, 13, 195, 184, 12, 5, 18, 9, 20, 9, 198, 44, 244, 205, 21, 66, 75, 20, 0, 13, 138, 13, 15, 12, 5, 11, 25, 12, 195, 166, 18, 20, 13, 138, 5, 12, 5, 13, 5, 14, 20, 195, 166, 18, 20, 11, 200, 89, 83, 7, 5, 34, 84, 21, 64, 20, 11, 200, 80, 242, 211, 36, 50, 84, 21, 64, 20, 11, 200, 77, 80, 148, 36, 194, 84, 21, 64, 20, 11, 200, 64, 20, 211, 37, 98, 84, 21, 64, 20, 11, 200, 52, 244, 148, 4, 194, 84, 21, 64, 20, 11, 200, 52, 83, 148, 4, 194, 84, 21, 64, 20, 11, 200, 52, 21, 5, 72, 226, 84, 21, 64, 20, 11, 200, 40, 245, 137, 4, 194, 84, 21, 64, 20, 11, 200, 36, 225, 5, 52, 226, 84, 21, 64, 20, 11, 200, 28, 83, 137, 4, 194, 84, 21, 64, 20, 11, 200, 4, 229, 9, 45, 98, 84, 21, 64, 20, 11, 200, 4, 35, 143, 72, 210, 84, 21, 64, 20, 11, 200, 9, 84, 133, 5, 82, 210, 5, 64, 20, 9, 198, 57, 147, 70, 60, 208, 78, 21, 0, 8, 197, 76, 83, 147, 61, 32, 20, 8, 197, 12, 83, 147, 61, 32, 20, 14, 139, 19, 5, 4, 9, 13, 5, 14, 20, 195, 166, 18, 20, 8, 197, 4, 213, 76, 21, 64, 20, 8, 197, 44, 244, 9, 77, 64, 20, 8, 197, 21, 99, 204, 21, 32, 20, 9, 198, 28, 84, 137, 5, 68, 137, 20, 11, 136, 9, 8, 195, 166, 18, 4, 9, 7, 20, 12, 201, 36, 229, 15, 48, 84, 129, 56, 49, 64, 20, 8, 197, 88, 17, 193, 57, 64, 20, 16, 141, 18, 5, 16, 18, 195, 166, 19, 5, 14, 20, 1, 14, 20, 20, 8, 197, 61, 5, 1, 57, 64, 20, 0, 10, 66, 52, 48, 63, 35, 49, 6, 0, 41, 15, 140, 16, 1, 18, 12, 1, 13, 5, 14, 20, 195, 166, 18, 20, 13, 202, 61, 35, 129, 52, 83, 148, 21, 34, 78, 28, 20, 13, 202, 52, 19, 137, 24, 84, 212, 21, 34, 78, 28, 20, 13, 202, 44, 243, 150, 60, 197, 84, 21, 34, 78, 28, 20, 13, 202, 44, 243, 134, 72, 243, 148, 21, 34, 78, 28, 20, 13, 202, 36, 229, 5, 73, 3, 204, 21, 34, 78, 28, 20, 13, 202, 36, 225, 11, 88, 20, 148, 21, 34, 78, 28, 20, 13, 202, 16, 242, 213, 52, 83, 148, 21, 34, 78, 28, 20, 13, 202, 5, 33, 213, 52, 83, 148, 21, 34, 78, 28, 20, 12, 137, 19, 5, 22, 195, 166, 18, 4, 9, 7, 20, 9, 198, 72, 240, 137, 56, 145, 64, 20, 9, 198, 64, 243, 15, 56, 145, 64, 20, 9, 198, 36, 212, 5, 72, 145, 64, 20, 9, 198, 81, 32, 70, 36, 176, 76, 20, 9, 198, 76, 194, 84, 4, 113, 64, 20, 0, 16, 141, 11, 15, 13, 16, 12, 5, 13, 5, 14, 20, 195, 166, 18, 20, 10, 199, 32, 85, 5, 72, 243, 143, 52, 20, 14, 203, 65, 35, 214, 36, 228, 201, 4, 194, 84, 21, 64, 20, 14, 203, 20, 115, 195, 20, 229, 18, 36, 50, 84, 21, 64, 20, 13, 138, 15, 22, 5, 18, 8, 195, 184, 18, 9, 7, 20, 13, 138, 1, 7, 20, 22, 195, 166, 18, 4, 9, 7, 20, 10, 199, 72, 81, 133, 72, 83, 131, 20, 20, 10, 199, 16, 147, 9, 28, 83, 131, 20, 20, 10, 199, 16, 82, 193, 16, 83, 131, 20, 20, 10, 199, 5, 52, 213, 72, 19, 131, 20, 20, 14, 3, 95, 53, 88, 105, 108, 55, 6, 47, 16, 36, 87, 0, 0, 17, 142, 16, 5, 18, 16, 5, 14, 4, 9, 11, 21, 12, 195, 166, 18, 20, 9, 198, 60, 36, 207, 48, 85, 0, 20, 11, 200, 72, 82, 78, 88, 84, 212, 21, 32, 20, 11, 200, 44, 243, 147, 60, 194, 68, 21, 32, 20, 11, 200, 44, 241, 75, 76, 148, 212, 21, 32, 20, 11, 200, 20, 101, 5, 72, 64, 84, 21, 32, 20, 14, 139, 12, 1, 19, 20, 22, 195, 166, 18, 4, 9, 7, 20, 9, 198, 81, 32, 78, 76, 149, 0, 20, 7, 196, 8, 21, 9, 44, 20, 11, 200, 44, 243, 150, 21, 33, 197, 57, 64, 20, 11, 200, 8, 146, 193, 72, 35, 206, 5, 64, 20, 9, 198, 88, 19, 5, 72, 144, 78, 21, 0, 15, 140, 195, 184, 14, 19, 11, 22, 195, 166, 18, 4, 9, 7, 20, 15, 140, 12, 195, 166, 19, 5, 22, 195, 166, 18, 4, 9, 7, 20, 15, 140, 6, 15, 18, 4, 195, 184, 13, 13, 5, 12, 9, 7, 20, 9, 198, 24, 18, 212, 61, 69, 77, 20, 9, 198, 80, 149, 1, 56, 149, 77, 20, 9, 198, 52, 243, 143, 28, 19, 73, 20, 8, 197, 76, 147, 79, 56, 144, 20, 0, 9, 198, 48, 149, 21, 72, 114, 64, 20, 9, 198, 81, 34, 86, 36, 83, 0, 20, 12, 137, 15, 16, 14, 195, 165, 5, 12, 9, 7, 20, 16, 141, 6, 15, 18, 11, 18, 195, 166, 14, 11, 5, 12, 9, 7, 20, 6, 195, 44, 83, 73, 20, 9, 198, 48, 149, 20, 21, 32, 84, 20, 9, 198, 16, 148, 12, 60, 208, 84, 20, 9, 198, 5, 85, 15, 45, 32, 84, 20, 9, 198, 4, 113, 210, 20, 112, 84, 20, 9, 198, 56, 85, 84, 72, 19, 0, 20, 0, 17, 142, 6, 15, 18, 19, 11, 18, 195, 166, 11, 11, 5, 12, 9, 7, 20, 10, 199, 77, 98, 78, 4, 117, 9, 28, 20, 0, 7, 196, 8, 85, 15, 56, 20, 9, 198, 33, 145, 18, 60, 99, 206, 20, 9, 198, 29, 32, 70, 60, 99, 206, 20, 16, 141, 11, 195, 184, 2, 5, 14, 8, 1, 22, 14, 5, 18, 9, 20, 14, 139, 16, 195, 165, 19, 20, 195, 165, 5, 12, 9, 7, 20, 14, 139, 15, 22, 5, 18, 6, 12, 195, 184, 4, 9, 7, 20, 14, 139, 6, 15, 18, 19, 20, 195, 165, 5, 12, 9, 7, 20, 14, 139, 4, 18, 9, 11, 6, 195, 166, 12, 4, 9, 7, 20, 11, 200, 60, 36, 212, 21, 68, 137, 76, 176, 20, 11, 200, 52, 85, 1, 24, 244, 137, 76, 176, 20, 11, 200, 13, 147, 9, 56, 68, 137, 76, 176, 20, 11, 200, 44, 193, 80, 80, 243, 65, 56, 144, 20, 11, 200, 76, 128, 77, 4, 226, 83, 52, 80, 20, 11, 200, 64, 83, 142, 4, 194, 83, 52, 80, 20, 11, 200, 44, 242, 193, 36, 226, 83, 52, 80, 20, 11, 200, 32, 83, 12, 20, 226, 83, 52, 80, 20, 0, 11, 136, 16, 18, 5, 3, 9, 195, 184, 19, 20, 13, 138, 13, 1, 14, 195, 184, 22, 18, 5, 18, 5, 20, 15, 140, 13, 195, 184, 10, 19, 15, 13, 13, 5, 12, 9, 7, 20, 12, 201, 72, 17, 9, 60, 195, 199, 37, 50, 192, 20, 12, 201, 45, 35, 206, 60, 195, 199, 37, 50, 192, 20, 12, 201, 32, 148, 16, 60, 195, 199, 37, 50, 192, 20, 12, 201, 25, 33, 78, 60, 195, 199, 37, 50, 192, 20, 12, 201, 24, 147, 13, 60, 195, 199, 37, 50, 192, 20, 8, 197, 61, 96, 82, 36, 80, 20, 8, 197, 61, 96, 82, 36, 80, 20, 8, 197, 21, 85, 15, 56, 144, 20, 8, 197, 5, 53, 5, 56, 144, 20, 8, 197, 73, 84, 212, 36, 176, 20, 12, 201, 65, 35, 198, 21, 52, 207, 72, 19, 0, 20, 12, 201, 44, 243, 138, 20, 181, 21, 72, 19, 0, 20, 10, 69, 77, 21, 65, 72, 80, 21, 0, 10, 0, 10, 135, 8, 195, 166, 18, 5, 19, 9, 20, 9, 198, 81, 34, 76, 60, 114, 64, 20, 9, 198, 25, 83, 135, 36, 50, 68, 20, 9, 198, 72, 84, 213, 49, 64, 84, 20, 0, 6, 195, 32, 35, 192, 17, 10, 199, 16, 85, 15, 56, 21, 15, 72, 20, 10, 199, 8, 80, 82, 8, 82, 132, 20, 67, 10, 199, 72, 85, 129, 48, 145, 5, 72, 20, 10, 199, 72, 85, 15, 84, 50, 5, 72, 20, 10, 199, 4, 36, 212, 72, 18, 5, 72, 20, 14, 203, 20, 208, 78, 12, 148, 1, 80, 244, 137, 76, 176, 20, 10, 199, 24, 83, 129, 12, 85, 9, 56, 20, 14, 203, 88, 81, 197, 80, 20, 137, 4, 226, 83, 52, 80, 20, 14, 203, 37, 36, 129, 80, 147, 206, 4, 194, 83, 52, 80, 20, 10, 199, 9, 83, 7, 5, 34, 69, 56, 20, 12, 201, 65, 35, 198, 21, 52, 207, 72, 21, 0, 20, 11, 3, 95, 54, 88, 47, 16, 6, 36, 87, 0, 0, 11, 200, 77, 84, 16, 61, 37, 5, 72, 80, 20, 12, 137, 16, 18, 195, 166, 19, 20, 5, 18, 5, 20, 11, 200, 8, 147, 199, 72, 17, 133, 72, 80, 20, 11, 200, 77, 64, 84, 84, 20, 137, 76, 176, 20, 11, 200, 49, 83, 132, 20, 228, 201, 76, 176, 20, 11, 200, 45, 83, 9, 56, 20, 137, 76, 176, 20, 11, 200, 29, 148, 129, 80, 244, 137, 76, 176, 20, 11, 200, 28, 84, 137, 5, 68, 137, 76, 176, 20, 11, 200, 64, 192, 78, 21, 64, 82, 36, 80, 20, 11, 200, 16, 83, 6, 36, 224, 82, 36, 80, 20, 11, 200, 77, 148, 212, 20, 208, 84, 36, 176, 20, 11, 200, 57, 83, 73, 76, 208, 84, 36, 176, 20, 11, 200, 20, 208, 140, 20, 208, 84, 36, 176, 20, 11, 200, 16, 148, 12, 60, 208, 84, 36, 176, 20, 0, 10, 135, 2, 1, 14, 11, 195, 184, 18, 20, 14, 4, 95, 50, 88, 15, 47, 6, 114, 82, 13, 50, 13, 0, 0, 10, 135, 11, 195, 166, 12, 5, 18, 9, 20, 9, 198, 20, 180, 212, 72, 83, 64, 20, 15, 204, 56, 21, 18, 37, 83, 75, 5, 32, 143, 56, 21, 0, 20, 9, 198, 25, 85, 20, 21, 32, 76, 20, 0, 12, 137, 11, 18, 15, 14, 9, 11, 195, 184, 18, 20, 9, 198, 80, 82, 206, 60, 195, 199, 20, 9, 198, 56, 85, 82, 60, 195, 199, 20, 9, 198, 56, 82, 210, 60, 195, 199, 20, 12, 201, 85, 66, 76, 37, 64, 82, 37, 53, 0, 20, 12, 201, 20, 181, 137, 48, 144, 146, 37, 53, 0, 20, 14, 203, 8, 144, 140, 36, 245, 5, 44, 20, 137, 76, 176, 20, 14, 203, 36, 228, 212, 73, 83, 69, 57, 64, 82, 36, 80, 20, 10, 199, 52, 20, 135, 84, 84, 137, 80, 20, 10, 199, 25, 32, 78, 44, 241, 137, 48, 20, 9, 198, 48, 149, 21, 72, 114, 75, 20, 0, 9, 198, 56, 18, 86, 37, 53, 0, 20, 9, 198, 72, 84, 213, 49, 65, 82, 20, 9, 198, 72, 84, 208, 37, 33, 82, 20, 9, 198, 64, 84, 141, 85, 65, 82, 20, 9, 198, 64, 20, 211, 37, 97, 82, 20, 9, 198, 60, 36, 212, 37, 1, 82, 20, 9, 198, 16, 147, 73, 81, 65, 82, 20, 7, 196, 12, 149, 1, 80, 20, 13, 70, 52, 243, 147, 36, 85, 82, 21, 102, 114, 0, 10, 0, 9, 198, 80, 83, 5, 29, 32, 77, 20, 13, 138, 11, 195, 166, 18, 5, 19, 20, 5, 18, 9, 20, 9, 198, 24, 243, 137, 5, 68, 137, 20, 0, 21, 66, 36, 192, 37, 55, 15, 70, 6, 40, 12, 74, 57, 13, 0, 81, 100, 117, 99, 101, 32, 13, 202, 44, 243, 148, 72, 245, 133, 73, 50, 69, 48, 20, 9, 198, 8, 243, 66, 21, 33, 84, 20, 0, 10, 199, 88, 148, 137, 48, 149, 5, 80, 20, 10, 199, 88, 19, 9, 16, 149, 5, 80, 20, 10, 199, 80, 243, 129, 48, 149, 5, 80, 20, 10, 199, 52, 244, 129, 48, 149, 5, 80, 20, 10, 199, 48, 16, 137, 48, 149, 5, 80, 20, 10, 199, 44, 19, 1, 52, 149, 5, 80, 20, 10, 199, 8, 19, 129, 48, 149, 5, 80, 20, 10, 199, 64, 245, 5, 57, 66, 69, 48, 20, 12, 201, 4, 229, 9, 12, 128, 77, 9, 33, 82, 20, 0, 22, 68, 32, 20, 16, 100, 105, 108, 48, 37, 15, 6, 110, 40, 112, 0, 81, 104, 111, 117, 114, 32, 9, 198, 8, 82, 203, 5, 50, 78, 67, 9, 198, 4, 100, 133, 4, 113, 82, 20, 9, 198, 36, 211, 73, 29, 33, 82, 20, 9, 198, 5, 69, 18, 5, 1, 82, 20, 9, 198, 4, 113, 210, 20, 113, 82, 20, 9, 198, 52, 242, 203, 5, 50, 78, 20, 9, 198, 8, 82, 203, 5, 50, 78, 20, 7, 196, 25, 148, 201, 44, 20, 7, 196, 8, 150, 129, 72, 20, 0, 12, 201, 77, 1, 67, 36, 98, 67, 37, 65, 84, 20, 12, 201, 64, 84, 137, 60, 66, 67, 37, 65, 84, 20, 12, 201, 77, 1, 75, 81, 35, 199, 72, 19, 64, 20, 14, 139, 16, 195, 165, 15, 11, 20, 18, 15, 10, 5, 18, 20, 9, 198, 64, 243, 15, 56, 149, 77, 20, 8, 197, 80, 18, 212, 36, 192, 20, 14, 139, 7, 18, 5, 14, 195, 165, 5, 14, 19, 5, 18, 20, 12, 201, 44, 243, 134, 20, 65, 82, 21, 33, 84, 20, 12, 201, 16, 148, 211, 20, 210, 78, 21, 33, 84, 20, 12, 201, 16, 85, 5, 72, 210, 78, 21, 33, 84, 20, 0, 13, 202, 88, 82, 147, 80, 16, 137, 48, 149, 5, 80, 20, 13, 202, 84, 226, 86, 21, 36, 193, 48, 149, 5, 80, 20, 13, 202, 37, 36, 137, 80, 16, 137, 48, 149, 5, 80, 20, 13, 202, 20, 211, 212, 36, 243, 129, 48, 149, 5, 80, 20, 12, 201, 44, 243, 148, 72, 18, 5, 72, 147, 135, 20, 9, 198, 56, 245, 1, 72, 145, 76, 20, 9, 198, 16, 84, 21, 80, 84, 128, 20, 9, 198, 4, 212, 21, 80, 84, 128, 20, 15, 140, 7, 18, 5, 14, 195, 165, 7, 5, 14, 19, 5, 18, 20, 9, 198, 72, 80, 71, 20, 228, 192, 20, 0, 19, 5, 4, 10, 39, 5, 14, 70, 37, 12, 6, 70, 57, 36, 12, 57, 106, 50, 0, 10, 199, 61, 85, 133, 73, 69, 82, 20, 20, 10, 199, 44, 243, 134, 37, 69, 82, 20, 20, 10, 199, 24, 147, 9, 65, 2, 78, 20, 20, 10, 199, 16, 241, 5, 44, 17, 143, 56, 20, 10, 199, 65, 35, 214, 37, 50, 79, 56, 20, 10, 199, 44, 243, 148, 85, 50, 79, 56, 20, 10, 199, 16, 147, 73, 77, 50, 79, 56, 20, 10, 199, 16, 83, 73, 77, 50, 79, 56, 20, 10, 199, 64, 192, 75, 5, 65, 82, 20, 20, 10, 199, 45, 85, 133, 73, 65, 82, 20, 20, 10, 199, 16, 242, 212, 61, 33, 82, 20, 20, 10, 199, 16, 80, 129, 81, 65, 82, 20, 20, 10, 199, 5, 4, 15, 73, 65, 82, 20, 20, 10, 135, 195, 166, 20, 1, 14, 15, 12, 20, 12, 201, 5, 3, 208, 48, 82, 212, 36, 177, 82, 20, 10, 199, 44, 193, 77, 20, 229, 9, 56, 20, 0, 14, 204, 44, 20, 129, 45, 65, 82, 37, 53, 9, 44, 243, 128, 11, 200, 80, 83, 5, 88, 148, 201, 60, 224, 20, 11, 200, 77, 80, 195, 21, 52, 201, 60, 224, 20, 11, 200, 20, 180, 203, 49, 84, 201, 60, 224, 20, 11, 200, 16, 148, 203, 85, 52, 201, 60, 224, 20, 11, 200, 16, 145, 210, 21, 52, 201, 60, 224, 20, 11, 200, 16, 81, 210, 21, 52, 201, 60, 224, 20, 11, 200, 36, 225, 21, 77, 68, 137, 20, 192, 20, 11, 200, 72, 83, 1, 80, 147, 206, 20, 192, 20, 11, 200, 64, 83, 137, 12, 147, 12, 36, 224, 20, 7, 196, 80, 86, 1, 56, 20, 11, 200, 65, 4, 137, 56, 50, 80, 4, 192, 20, 0, 10, 135, 20, 5, 18, 14, 195, 166, 18, 20, 16, 205, 44, 243, 77, 20, 228, 213, 72, 16, 137, 48, 149, 5, 80, 20, 12, 201, 20, 180, 201, 77, 65, 78, 80, 145, 76, 20, 12, 201, 16, 145, 134, 21, 33, 78, 80, 145, 76, 20, 9, 198, 52, 241, 21, 48, 84, 133, 20, 8, 197, 77, 80, 148, 36, 192, 20, 8, 197, 4, 97, 200, 4, 224, 20, 8, 197, 52, 83, 148, 4, 192, 20, 10, 69, 5, 84, 212, 36, 224, 21, 0, 10, 0, 11, 136, 11, 15, 14, 20, 18, 195, 166, 18, 20, 9, 198, 5, 37, 5, 72, 145, 76, 20, 15, 140, 16, 18, 195, 166, 4, 5, 19, 20, 9, 14, 5, 18, 20, 0, 10, 199, 48, 16, 143, 72, 21, 15, 72, 20, 10, 199, 16, 81, 140, 20, 181, 15, 72, 20, 12, 137, 12, 5, 7, 9, 15, 14, 195, 166, 18, 20, 12, 137, 12, 1, 20, 18, 9, 14, 195, 166, 18, 20, 12, 137, 1, 11, 20, 9, 15, 14, 195, 166, 18, 20, 21, 71, 48, 147, 79, 85, 50, 78, 20, 55, 37, 63, 111, 87, 6, 37, 12, 50, 13, 0, 20, 10, 199, 88, 144, 146, 5, 66, 79, 56, 20, 10, 199, 52, 145, 210, 5, 66, 79, 56, 20, 10, 199, 44, 241, 206, 37, 66, 79, 56, 20, 10, 199, 44, 20, 142, 5, 66, 79, 56, 20, 14, 203, 44, 243, 147, 80, 149, 21, 80, 147, 206, 20, 192, 20, 10, 199, 77, 80, 148, 72, 18, 5, 72, 20, 10, 199, 64, 245, 5, 57, 49, 82, 20, 20, 10, 199, 64, 20, 212, 36, 50, 5, 72, 20, 10, 199, 4, 32, 146, 21, 98, 69, 72, 20, 13, 138, 195, 184, 11, 15, 14, 15, 13, 9, 19, 11, 20, 10, 199, 88, 144, 212, 61, 34, 65, 56, 20, 10, 199, 5, 52, 201, 77, 65, 78, 80, 20, 11, 3, 95, 56, 88, 81, 6, 37, 34, 87, 0, 0, 11, 200, 4, 113, 210, 21, 52, 201, 60, 224, 20, 11, 200, 64, 244, 201, 80, 147, 206, 20, 192, 20, 0, 10, 135, 21, 22, 21, 12, 195, 166, 18, 20, 10, 135, 5, 12, 9, 20, 195, 166, 18, 20, 9, 198, 8, 147, 205, 21, 68, 137, 20, 8, 197, 77, 83, 142, 37, 64, 20, 8, 197, 28, 19, 1, 57, 64, 20, 0, 13, 202, 64, 244, 21, 48, 20, 137, 76, 21, 15, 72, 20, 11, 136, 19, 1, 14, 9, 20, 195, 166, 18, 20, 13, 202, 72, 83, 79, 57, 53, 18, 5, 66, 79, 56, 20, 13, 202, 44, 243, 131, 20, 229, 18, 5, 66, 79, 56, 20, 13, 202, 16, 83, 79, 57, 53, 18, 5, 66, 79, 56, 20, 16, 141, 7, 25, 14, 195, 166, 11, 15, 12, 15, 7, 9, 19, 11, 20, 9, 198, 36, 226, 149, 72, 145, 64, 20, 9, 198, 8, 85, 15, 56, 145, 64, 20, 9, 198, 5, 37, 5, 72, 145, 64, 20, 9, 198, 72, 81, 149, 28, 145, 64, 20, 9, 198, 36, 225, 9, 12, 145, 64, 20, 9, 198, 16, 83, 9, 72, 145, 64, 20, 9, 198, 44, 240, 75, 76, 144, 76, 20, 9, 198, 16, 147, 21, 88, 144, 76, 20, 9, 198, 64, 20, 211, 4, 113, 64, 20, 0, 12, 137, 1, 12, 22, 5, 15, 12, 195, 166, 18, 20, 10, 199, 88, 144, 146, 21, 34, 78, 28, 20, 10, 199, 76, 84, 150, 21, 34, 78, 28, 20, 10, 199, 45, 35, 203, 21, 34, 78, 28, 20, 10, 199, 44, 20, 211, 21, 34, 78, 28, 20, 10, 199, 28, 192, 83, 21, 34, 78, 28, 20, 10, 199, 16, 244, 211, 21, 34, 78, 28, 20, 11, 136, 11, 195, 166, 22, 12, 5, 18, 9, 20, 10, 199, 44, 21, 1, 45, 33, 83, 20, 20, 12, 201, 16, 145, 134, 21, 33, 78, 80, 144, 66, 20, 0, 13, 138, 20, 15, 20, 1, 12, 9, 20, 195, 166, 18, 20, 11, 200, 76, 240, 201, 4, 194, 84, 21, 64, 20, 11, 200, 64, 84, 134, 36, 66, 84, 21, 64, 20, 11, 200, 56, 244, 141, 4, 194, 84, 21, 64, 20, 11, 200, 52, 244, 130, 36, 66, 84, 21, 64, 20, 11, 200, 48, 146, 214, 36, 66, 84, 21, 64, 20, 11, 200, 29, 32, 86, 36, 66, 84, 21, 64, 20, 11, 200, 25, 34, 71, 36, 66, 84, 21, 64, 20, 11, 200, 24, 244, 141, 4, 194, 84, 21, 64, 20, 11, 200, 24, 84, 148, 36, 194, 84, 21, 64, 20, 11, 200, 17, 82, 212, 36, 194, 84, 21, 64, 20, 11, 200, 9, 37, 84, 4, 194, 84, 21, 64, 20, 11, 200, 4, 181, 21, 4, 194, 84, 21, 64, 20, 11, 200, 4, 36, 213, 72, 66, 84, 21, 64, 20, 11, 200, 65, 35, 199, 72, 81, 9, 21, 32, 20, 12, 201, 64, 192, 78, 28, 83, 205, 21, 68, 137, 20, 12, 137, 4, 10, 195, 166, 22, 12, 5, 18, 9, 20, 14, 139, 195, 166, 20, 9, 15, 12, 15, 7, 9, 19, 11, 20, 18, 143, 6, 195, 166, 14, 15, 13, 5, 14, 15, 12, 15, 7, 9, 19, 11, 20, 9, 198, 8, 19, 4, 4, 178, 78, 20, 9, 198, 72, 245, 1, 72, 144, 78, 20, 9, 198, 44, 244, 147, 36, 176, 78, 20, 13, 72, 52, 19, 129, 28, 83, 69, 57, 64, 21, 0, 10, 11, 70, 32, 243, 204, 36, 112, 78, 21, 0, 10, 0, 14, 139, 16, 18, 15, 16, 18, 9, 5, 20, 195, 166, 18, 20, 14, 139, 11, 15, 13, 13, 21, 14, 9, 20, 195, 166, 18, 20, 8, 197, 72, 17, 9, 21, 32, 20, 8, 197, 24, 243, 9, 21, 32, 20, 12, 201, 76, 181, 70, 24, 81, 1, 72, 145, 64, 20, 12, 201, 44, 243, 77, 37, 52, 207, 72, 145, 64, 20, 8, 197, 24, 84, 146, 37, 64, 20, 12, 201, 52, 84, 193, 48, 194, 65, 56, 49, 64, 20, 8, 197, 44, 241, 206, 5, 64, 20, 8, 197, 53, 85, 1, 57, 64, 20, 6, 195, 52, 81, 0, 76, 0, 13, 202, 88, 84, 147, 36, 98, 67, 21, 34, 78, 28, 20, 13, 202, 72, 82, 212, 36, 98, 67, 21, 34, 78, 28, 20, 13, 202, 64, 20, 129, 24, 98, 78, 21, 34, 78, 28, 20, 13, 202, 52, 244, 148, 36, 98, 67, 21, 34, 78, 28, 20, 13, 202, 45, 96, 76, 36, 98, 67, 21, 34, 78, 28, 20, 13, 202, 44, 243, 131, 20, 229, 18, 21, 34, 78, 28, 20, 13, 202, 25, 32, 75, 80, 147, 206, 21, 34, 78, 28, 20, 13, 202, 12, 84, 148, 36, 98, 67, 21, 34, 78, 28, 20, 10, 135, 22, 195, 166, 22, 5, 18, 9, 20, 10, 135, 20, 195, 184, 10, 5, 18, 9, 20, 9, 198, 52, 21, 5, 72, 145, 64, 20, 9, 198, 52, 18, 15, 56, 145, 64, 20, 9, 198, 8, 81, 207, 56, 145, 64, 20, 9, 198, 80, 149, 1, 56, 145, 64, 20, 9, 198, 44, 20, 18, 36, 49, 64, 20, 9, 198, 24, 18, 129, 56, 49, 64, 20, 9, 198, 44, 243, 15, 56, 144, 76, 20, 9, 198, 45, 84, 148, 4, 113, 64, 20, 0, 14, 203, 52, 243, 149, 52, 83, 148, 4, 194, 84, 21, 64, 20, 14, 203, 36, 225, 9, 88, 145, 21, 4, 194, 84, 21, 64, 20, 13, 138, 16, 195, 165, 22, 9, 19, 5, 12, 9, 7, 20, 13, 138, 1, 14, 19, 20, 195, 166, 14, 4, 9, 7, 20, 13, 138, 1, 6, 12, 195, 165, 19, 5, 12, 9, 7, 20, 12, 201, 29, 37, 78, 17, 69, 137, 28, 144, 78, 20, 10, 199, 48, 85, 133, 72, 19, 131, 20, 20, 10, 199, 5, 36, 143, 28, 19, 131, 20, 20, 8, 67, 8, 246, 64, 21, 0, 10, 14, 3, 95, 57, 88, 105, 108, 55, 81, 6, 107, 63, 87, 0, 0, 9, 198, 33, 145, 18, 60, 99, 210, 20, 9, 198, 80, 244, 133, 4, 67, 210, 20, 11, 200, 65, 35, 203, 85, 32, 84, 61, 32, 20, 7, 196, 32, 245, 133, 72, 20, 16, 141, 11, 22, 195, 166, 18, 21, 12, 1, 14, 20, 5, 18, 9, 20, 14, 139, 9, 14, 4, 19, 20, 195, 166, 14, 4, 9, 7, 20, 11, 200, 77, 84, 16, 48, 146, 193, 57, 64, 20, 7, 196, 16, 85, 20, 20, 76, 0, 9, 198, 44, 243, 77, 84, 227, 205, 20, 15, 140, 13, 9, 19, 20, 195, 166, 14, 11, 5, 12, 9, 7, 20, 12, 201, 48, 16, 143, 72, 21, 15, 72, 145, 64, 20, 12, 201, 4, 208, 149, 48, 21, 15, 72, 145, 64, 20, 9, 198, 5, 85, 15, 56, 243, 73, 20, 8, 197, 80, 18, 212, 36, 176, 20, 8, 197, 52, 244, 134, 20, 208, 20, 12, 201, 36, 228, 208, 20, 181, 18, 36, 49, 64, 20, 0, 9, 198, 104, 243, 204, 60, 114, 64, 20, 17, 206, 20, 180, 212, 21, 36, 137, 80, 244, 137, 4, 194, 84, 21, 64, 20, 9, 198, 52, 21, 5, 72, 145, 76, 20, 14, 139, 20, 9, 12, 19, 11, 195, 166, 18, 5, 18, 9, 20, 14, 139, 15, 22, 5, 18, 12, 195, 184, 2, 5, 18, 9, 20, 9, 198, 9, 32, 75, 80, 80, 84, 20, 0, 10, 199, 25, 32, 78, 44, 241, 143, 56, 20, 10, 199, 80, 83, 5, 52, 85, 18, 36, 20, 10, 199, 76, 241, 137, 77, 65, 82, 36, 20, 10, 199, 72, 85, 8, 5, 97, 82, 36, 20, 10, 199, 64, 81, 1, 57, 65, 82, 36, 20, 10, 199, 36, 225, 129, 57, 65, 82, 36, 20, 13, 138, 12, 5, 13, 6, 195, 166, 12, 4, 9, 7, 20, 13, 138, 1, 6, 12, 195, 166, 19, 5, 12, 9, 7, 20, 10, 199, 80, 83, 5, 52, 21, 9, 44, 20, 10, 199, 64, 225, 85, 52, 21, 9, 44, 20, 10, 199, 29, 32, 77, 52, 21, 9, 44, 20, 10, 199, 20, 225, 82, 28, 85, 9, 44, 20, 10, 199, 4, 34, 200, 5, 50, 69, 56, 20, 10, 199, 24, 20, 200, 36, 243, 129, 8, 20, 0, 11, 200, 80, 84, 146, 5, 52, 197, 72, 80, 20, 14, 139, 16, 195, 165, 22, 9, 18, 11, 5, 12, 9, 7, 20, 14, 139, 6, 15, 18, 4, 195, 184, 10, 5, 12, 9, 7, 20, 11, 200, 64, 84, 137, 24, 84, 137, 76, 176, 20, 11, 200, 64, 83, 135, 20, 116, 137, 76, 176, 20, 11, 200, 4, 193, 65, 80, 244, 137, 76, 176, 20, 11, 200, 80, 84, 146, 37, 67, 210, 36, 80, 20, 11, 200, 60, 97, 133, 73, 67, 210, 36, 80, 20, 12, 201, 4, 208, 149, 48, 21, 15, 72, 149, 77, 20, 0, 12, 201, 44, 147, 133, 76, 147, 204, 60, 114, 64, 20, 12, 201, 80, 84, 146, 37, 67, 210, 36, 83, 0, 20, 8, 197, 64, 244, 197, 72, 80, 20, 8, 197, 4, 181, 5, 72, 80, 20, 9, 198, 64, 148, 212, 4, 50, 69, 20, 9, 198, 5, 84, 208, 36, 50, 69, 20, 8, 197, 36, 66, 79, 80, 144, 20, 8, 197, 52, 20, 212, 36, 176, 20, 8, 197, 8, 84, 212, 36, 176, 20, 12, 201, 44, 243, 77, 37, 52, 193, 72, 144, 84, 20, 0, 9, 198, 41, 81, 9, 12, 145, 76, 20, 10, 135, 12, 195, 166, 4, 5, 18, 5, 20, 16, 141, 19, 5, 12, 22, 6, 195, 184, 12, 7, 5, 12, 9, 7, 20, 9, 198, 64, 84, 212, 36, 50, 68, 20, 9, 198, 21, 84, 153, 80, 210, 64, 20, 9, 198, 25, 32, 75, 80, 147, 0, 20, 9, 198, 8, 84, 212, 40, 19, 0, 20, 13, 3, 95, 63, 65, 69, 39, 40, 87, 47, 35, 58, 0, 0, 16, 5, 3, 4, 39, 5, 14, 87, 36, 12, 70, 36, 12, 106, 50, 0, 10, 199, 61, 33, 9, 56, 21, 15, 72, 20, 10, 199, 72, 84, 1, 81, 34, 69, 72, 20, 11, 136, 13, 195, 184, 2, 12, 5, 18, 5, 20, 10, 199, 44, 243, 148, 72, 18, 5, 72, 20, 10, 199, 16, 83, 149, 57, 66, 69, 72, 20, 10, 199, 72, 245, 9, 77, 49, 82, 36, 20, 10, 199, 4, 193, 143, 57, 49, 82, 36, 20, 17, 142, 12, 5, 20, 16, 195, 165, 22, 9, 18, 11, 5, 12, 9, 7, 20, 14, 203, 61, 33, 193, 56, 148, 193, 80, 244, 137, 76, 176, 20, 14, 203, 44, 243, 134, 37, 50, 193, 80, 244, 137, 76, 176, 20, 12, 201, 64, 20, 211, 36, 243, 133, 72, 85, 0, 20, 0, 7, 196, 12, 84, 149, 80, 20, 9, 198, 104, 147, 206, 37, 53, 0, 20, 11, 200, 77, 64, 84, 84, 84, 137, 56, 112, 20, 11, 200, 76, 180, 129, 88, 84, 137, 56, 112, 20, 11, 200, 72, 81, 21, 12, 84, 137, 56, 112, 20, 11, 200, 64, 20, 129, 24, 84, 137, 56, 112, 20, 11, 200, 44, 19, 143, 56, 84, 137, 56, 112, 20, 11, 200, 36, 225, 137, 12, 84, 137, 56, 112, 20, 11, 200, 36, 115, 143, 72, 84, 137, 56, 112, 20, 11, 200, 28, 83, 133, 72, 84, 137, 56, 112, 20, 11, 200, 20, 228, 201, 48, 84, 137, 56, 112, 20, 11, 200, 17, 81, 76, 48, 84, 137, 56, 112, 20, 11, 200, 16, 84, 137, 88, 84, 137, 56, 112, 20, 11, 200, 4, 35, 206, 56, 84, 137, 56, 112, 20, 11, 200, 76, 177, 76, 21, 69, 5, 72, 80, 20, 11, 200, 72, 245, 76, 21, 69, 5, 72, 80, 20, 11, 200, 65, 35, 202, 20, 181, 5, 72, 80, 20, 11, 200, 8, 147, 12, 21, 69, 5, 72, 80, 20, 11, 200, 80, 17, 19, 40, 146, 201, 76, 176, 20, 11, 200, 40, 21, 129, 56, 84, 201, 76, 176, 20, 11, 200, 4, 195, 5, 28, 244, 137, 76, 176, 20, 11, 200, 9, 32, 86, 85, 32, 82, 36, 80, 20, 7, 196, 12, 149, 137, 48, 20, 11, 200, 16, 144, 71, 56, 244, 212, 36, 176, 20, 9, 198, 4, 192, 129, 56, 145, 78, 20, 0, 12, 201, 81, 32, 68, 37, 66, 79, 56, 83, 0, 20, 9, 198, 28, 83, 205, 21, 68, 137, 20, 0, 20, 3, 13, 195, 165, 63, 6, 111, 12, 15, 105, 108, 12, 0, 81, 104, 97, 118, 101, 32, 14, 70, 48, 145, 197, 76, 243, 64, 55, 37, 87, 112, 63, 0, 17, 70, 77, 98, 78, 28, 243, 64, 87, 82, 36, 66, 6, 112, 63, 0, 20, 9, 198, 5, 85, 15, 56, 243, 64, 20, 9, 198, 4, 224, 71, 72, 19, 64, 20, 10, 135, 8, 195, 166, 12, 5, 18, 9, 20, 13, 202, 24, 244, 134, 5, 69, 5, 72, 147, 132, 20, 20, 9, 198, 48, 82, 211, 36, 176, 76, 20, 6, 131, 13, 195, 165, 76, 0, 17, 5, 2, 8, 39, 5, 18, 69, 4, 36, 12, 105, 6, 111, 12, 112, 0, 15, 5, 3, 4, 39, 5, 18, 87, 36, 12, 70, 36, 12, 112, 0, 12, 201, 72, 85, 137, 76, 147, 206, 37, 53, 0, 20, 14, 203, 84, 66, 207, 56, 181, 82, 72, 84, 137, 56, 112, 20, 14, 203, 81, 32, 85, 52, 21, 9, 76, 84, 137, 56, 112, 20, 14, 203, 80, 84, 141, 60, 116, 129, 24, 84, 137, 56, 112, 20, 14, 203, 77, 1, 67, 36, 19, 9, 76, 84, 137, 56, 112, 20, 10, 199, 61, 134, 68, 21, 34, 78, 28, 20, 10, 199, 61, 130, 68, 21, 34, 78, 28, 20, 14, 203, 56, 243, 73, 56, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 56, 85, 84, 72, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 56, 21, 21, 72, 19, 9, 76, 84, 137, 56, 112, 20, 10, 199, 52, 21, 20, 21, 34, 78, 28, 20, 14, 203, 48, 144, 133, 72, 19, 9, 76, 84, 137, 56, 112, 20, 10, 199, 45, 34, 68, 21, 34, 78, 28, 20, 14, 203, 44, 20, 9, 80, 19, 9, 76, 84, 137, 56, 112, 20, 10, 199, 41, 84, 212, 21, 34, 78, 28, 20, 10, 199, 37, 51, 204, 21, 34, 78, 28, 20, 10, 199, 16, 243, 12, 21, 34, 78, 28, 20, 14, 203, 16, 147, 69, 57, 50, 79, 56, 84, 137, 56, 112, 20, 14, 203, 16, 21, 1, 52, 21, 9, 76, 84, 137, 56, 112, 20, 14, 203, 4, 48, 197, 77, 50, 79, 56, 84, 137, 56, 112, 20, 15, 140, 16, 15, 18, 20, 18, 195, 166, 20, 20, 5, 18, 5, 20, 12, 201, 12, 83, 148, 72, 19, 1, 76, 145, 78, 20, 10, 199, 16, 145, 134, 21, 33, 78, 76, 20, 10, 199, 64, 84, 147, 21, 34, 193, 80, 20, 10, 199, 29, 147, 78, 5, 50, 65, 48, 20, 0, 9, 198, 17, 32, 71, 37, 53, 0, 20, 9, 198, 81, 32, 70, 36, 177, 82, 20, 9, 198, 77, 81, 134, 36, 113, 82, 20, 9, 198, 72, 84, 12, 36, 49, 82, 20, 9, 198, 72, 83, 143, 56, 49, 82, 20, 9, 198, 44, 243, 147, 84, 209, 82, 20, 9, 198, 36, 226, 149, 72, 145, 82, 20, 9, 198, 16, 84, 12, 4, 49, 82, 20, 12, 137, 19, 11, 195, 166, 20, 20, 5, 18, 9, 20, 12, 201, 16, 83, 147, 37, 67, 205, 21, 68, 137, 20, 9, 198, 56, 145, 197, 72, 144, 78, 20, 9, 198, 4, 225, 204, 60, 208, 78, 21, 0, 0, 9, 198, 21, 2, 71, 72, 19, 64, 20, 13, 202, 16, 148, 212, 72, 144, 149, 21, 34, 78, 28, 20, 11, 70, 92, 84, 212, 21, 35, 128, 21, 0, 10, 0, 9, 198, 32, 148, 212, 60, 195, 199, 20, 12, 201, 45, 33, 65, 80, 147, 206, 37, 53, 0, 20, 12, 201, 72, 17, 9, 60, 66, 82, 36, 113, 82, 20, 12, 201, 65, 35, 199, 56, 244, 212, 36, 49, 82, 20, 11, 136, 19, 13, 195, 184, 18, 5, 18, 9, 20, 10, 199, 72, 84, 208, 60, 228, 213, 52, 20, 10, 199, 29, 32, 80, 80, 243, 9, 80, 20, 10, 199, 65, 35, 202, 20, 181, 9, 48, 20, 12, 137, 11, 195, 184, 7, 5, 14, 19, 5, 18, 20, 10, 199, 64, 245, 5, 57, 66, 65, 48, 20, 0, 9, 198, 5, 36, 129, 56, 113, 82, 20, 16, 141, 195, 166, 18, 5, 19, 11, 195, 166, 14, 4, 5, 18, 9, 20, 18, 143, 16, 1, 12, 195, 166, 15, 14, 20, 15, 12, 15, 7, 9, 19, 11, 20, 13, 138, 8, 195, 166, 18, 5, 20, 9, 11, 5, 18, 20, 9, 198, 20, 193, 71, 36, 177, 82, 20, 18, 70, 52, 20, 143, 12, 18, 78, 63, 110, 34, 39, 6, 49, 107, 66, 0, 20, 11, 200, 44, 242, 78, 12, 145, 5, 57, 48, 20, 9, 198, 21, 35, 212, 60, 208, 78, 21, 11, 4, 95, 8, 15, 11, 105, 6, 40, 49, 0, 0, 19, 144, 1, 14, 195, 166, 19, 20, 5, 19, 9, 15, 12, 15, 7, 9, 19, 11, 20, 12, 137, 16, 18, 195, 166, 4, 9, 11, 1, 20, 20, 9, 198, 45, 34, 84, 37, 48, 66, 20, 0, 12, 137, 1, 18, 11, 195, 166, 15, 12, 15, 7, 20, 14, 139, 15, 18, 4, 11, 12, 195, 184, 22, 5, 18, 9, 20, 11, 136, 6, 195, 184, 14, 9, 11, 5, 18, 20, 13, 202, 44, 243, 15, 72, 21, 21, 72, 20, 137, 20, 20, 8, 197, 76, 20, 132, 36, 224, 20, 8, 197, 16, 147, 216, 36, 224, 20, 8, 197, 40, 244, 132, 4, 224, 20, 8, 197, 8, 192, 68, 4, 224, 21, 8, 197, 37, 36, 133, 4, 192, 20, 0, 9, 198, 16, 80, 201, 76, 244, 128, 20, 9, 198, 88, 81, 197, 80, 84, 128, 20, 9, 198, 88, 19, 21, 80, 84, 128, 20, 9, 198, 76, 19, 21, 80, 84, 128, 20, 9, 198, 72, 85, 137, 16, 84, 128, 20, 9, 198, 72, 84, 201, 16, 84, 128, 20, 9, 198, 72, 82, 217, 48, 84, 128, 20, 9, 198, 72, 81, 193, 48, 84, 128, 20, 9, 198, 72, 80, 201, 80, 84, 128, 20, 9, 198, 64, 242, 213, 48, 84, 128, 20, 9, 198, 61, 1, 1, 80, 84, 128, 20, 9, 198, 52, 81, 9, 80, 84, 128, 20, 9, 198, 48, 144, 201, 80, 84, 128, 20, 9, 198, 44, 194, 67, 32, 84, 128, 20, 9, 198, 16, 84, 9, 48, 84, 128, 20, 9, 198, 16, 80, 201, 16, 84, 128, 20, 9, 198, 12, 148, 197, 48, 84, 128, 20, 12, 201, 5, 85, 5, 57, 66, 70, 36, 49, 82, 20, 12, 201, 65, 35, 199, 56, 244, 212, 36, 177, 82, 20, 9, 198, 53, 144, 78, 52, 20, 128, 20, 9, 198, 16, 148, 212, 4, 229, 0, 20, 9, 198, 8, 20, 212, 4, 229, 0, 20, 9, 198, 80, 243, 5, 72, 16, 128, 20, 14, 70, 33, 99, 210, 24, 244, 128, 82, 112, 81, 6, 112, 0, 0, 10, 199, 52, 147, 137, 5, 69, 82, 20, 20, 10, 199, 52, 147, 137, 5, 69, 82, 20, 20, 16, 6, 11, 195, 184, 18, 15, 13, 49, 116, 51, 6, 112, 63, 0, 20, 10, 199, 16, 145, 134, 85, 50, 79, 56, 20, 9, 198, 57, 80, 78, 12, 84, 133, 20, 10, 199, 36, 228, 212, 4, 195, 5, 72, 20, 9, 198, 29, 83, 77, 36, 84, 133, 20, 10, 199, 16, 84, 212, 36, 195, 5, 72, 20, 9, 198, 16, 144, 75, 72, 243, 137, 20, 17, 142, 16, 1, 12, 195, 166, 19, 20, 9, 14, 5, 14, 19, 5, 18, 20, 17, 142, 14, 25, 11, 195, 184, 2, 9, 14, 7, 5, 14, 19, 5, 18, 20, 17, 142, 8, 10, 195, 184, 18, 18, 9, 14, 7, 5, 14, 19, 5, 18, 20, 10, 135, 195, 184, 4, 9, 16, 1, 12, 20, 15, 4, 95, 15, 7, 15, 6, 113, 79, 113, 50, 4, 107, 49, 0, 0, 18, 143, 18, 21, 4, 11, 195, 184, 2, 9, 14, 7, 5, 14, 19, 5, 18, 20, 0, 8, 197, 64, 84, 147, 60, 224, 20, 12, 201, 52, 243, 143, 25, 67, 206, 28, 84, 128, 20, 12, 201, 52, 146, 210, 61, 50, 207, 64, 84, 128, 20, 8, 197, 17, 83, 208, 60, 192, 20, 8, 197, 25, 34, 71, 36, 64, 20, 8, 197, 64, 192, 84, 36, 224, 20, 8, 197, 44, 19, 204, 36, 224, 20, 19, 144, 19, 195, 184, 14, 4, 5, 18, 2, 15, 18, 7, 5, 14, 19, 5, 18, 20, 19, 144, 19, 1, 11, 19, 11, 195, 184, 2, 9, 14, 7, 5, 14, 19, 5, 18, 20, 19, 144, 18, 9, 14, 7, 11, 195, 184, 2, 9, 14, 7, 5, 14, 19, 5, 18, 20, 12, 201, 32, 240, 146, 60, 113, 78, 76, 84, 128, 20, 8, 197, 64, 192, 84, 36, 224, 20, 8, 197, 44, 20, 211, 4, 32, 20, 0, 9, 198, 81, 37, 78, 44, 84, 128, 20, 9, 198, 81, 32, 75, 80, 84, 128, 20, 13, 202, 77, 80, 147, 80, 19, 148, 37, 97, 82, 20, 20, 9, 198, 64, 149, 143, 80, 84, 128, 20, 13, 202, 64, 84, 147, 64, 82, 212, 37, 97, 82, 20, 20, 9, 198, 44, 20, 212, 72, 84, 128, 20, 9, 198, 24, 147, 20, 72, 84, 128, 20, 9, 198, 21, 50, 193, 64, 84, 128, 20, 9, 198, 12, 130, 70, 72, 84, 128, 20, 9, 198, 4, 178, 207, 48, 84, 128, 20, 12, 137, 10, 21, 2, 9, 12, 195, 166, 21, 13, 20, 18, 143, 14, 195, 184, 18, 18, 5, 19, 21, 14, 4, 2, 25, 14, 9, 20, 20, 11, 136, 7, 18, 195, 165, 19, 20, 5, 14, 20, 9, 198, 77, 65, 76, 48, 20, 128, 20, 9, 198, 28, 195, 211, 76, 20, 128, 20, 9, 198, 72, 84, 1, 72, 16, 128, 20, 9, 198, 56, 21, 137, 28, 16, 128, 20, 0, 10, 199, 77, 69, 75, 44, 21, 21, 72, 20, 9, 198, 29, 32, 70, 60, 227, 205, 20, 10, 199, 72, 85, 5, 57, 66, 79, 56, 20, 10, 199, 60, 181, 76, 5, 66, 79, 56, 20, 10, 199, 24, 244, 141, 5, 66, 79, 56, 20, 10, 199, 16, 85, 5, 57, 66, 79, 56, 20, 10, 199, 16, 81, 140, 5, 66, 79, 56, 20, 9, 198, 56, 20, 193, 48, 84, 133, 20, 10, 199, 4, 224, 76, 101, 49, 82, 20, 20, 10, 199, 8, 147, 198, 101, 50, 83, 44, 20, 10, 199, 29, 35, 211, 29, 32, 73, 56, 20, 10, 199, 4, 193, 65, 80, 244, 137, 44, 20, 21, 146, 19, 20, 21, 2, 2, 5, 11, 195, 184, 2, 9, 14, 7, 5, 14, 19, 5, 18, 20, 10, 199, 44, 243, 208, 21, 32, 78, 80, 20, 0, 9, 198, 80, 18, 211, 5, 67, 210, 20, 11, 200, 20, 180, 203, 85, 36, 201, 60, 224, 20, 15, 204, 65, 34, 86, 5, 65, 137, 56, 19, 147, 36, 84, 128, 20, 11, 200, 72, 129, 85, 52, 21, 15, 36, 64, 20, 11, 200, 81, 80, 133, 72, 181, 76, 36, 224, 20, 11, 200, 88, 83, 133, 105, 81, 76, 4, 224, 20, 11, 200, 44, 20, 193, 44, 132, 212, 4, 224, 21, 7, 196, 36, 208, 71, 20, 20, 9, 68, 36, 208, 71, 20, 21, 0, 10, 0, 8, 197, 5, 162, 77, 85, 64, 20, 12, 201, 44, 243, 147, 64, 148, 129, 80, 244, 128, 20, 12, 201, 44, 243, 77, 20, 229, 1, 80, 244, 128, 20, 12, 201, 4, 48, 197, 48, 84, 129, 80, 244, 128, 20, 12, 201, 77, 65, 82, 20, 245, 25, 64, 84, 128, 20, 12, 201, 36, 225, 5, 45, 49, 82, 12, 84, 128, 20, 12, 201, 4, 67, 73, 56, 148, 212, 72, 84, 128, 20, 0, 15, 140, 16, 18, 15, 20, 15, 11, 15, 12, 12, 195, 166, 18, 20, 9, 198, 56, 82, 210, 61, 49, 64, 20, 9, 198, 36, 225, 15, 48, 241, 192, 20, 13, 202, 36, 229, 5, 73, 3, 204, 5, 66, 79, 56, 20, 9, 198, 4, 68, 133, 77, 49, 64, 20, 9, 198, 44, 19, 15, 72, 145, 64, 20, 9, 198, 28, 83, 199, 72, 17, 128, 20, 0, 10, 199, 56, 244, 141, 21, 34, 78, 28, 20, 10, 199, 4, 226, 77, 21, 34, 78, 28, 20, 0, 9, 198, 72, 243, 139, 20, 67, 210, 20, 15, 204, 20, 180, 208, 21, 34, 77, 20, 229, 1, 80, 244, 128, 20, 9, 198, 4, 226, 77, 5, 67, 210, 20, 11, 200, 44, 243, 132, 61, 69, 9, 21, 32, 20, 15, 204, 44, 19, 21, 56, 64, 143, 72, 113, 78, 76, 84, 128, 20, 0, 11, 136, 11, 195, 166, 20, 20, 5, 18, 9, 20, 11, 136, 8, 195, 166, 18, 4, 5, 18, 9, 20, 12, 201, 48, 82, 211, 36, 179, 199, 72, 17, 128, 20, 8, 197, 77, 6, 71, 5, 64, 20, 0, 9, 198, 48, 18, 212, 61, 49, 64, 20, 9, 198, 12, 148, 146, 61, 49, 64, 20, 13, 202, 16, 148, 211, 20, 229, 9, 21, 34, 78, 28, 20, 12, 137, 19, 13, 195, 165, 20, 20, 5, 18, 9, 20, 9, 198, 8, 147, 199, 72, 17, 128, 20, 9, 198, 60, 48, 201, 16, 83, 148, 20, 9, 198, 24, 192, 71, 72, 19, 148, 20, 0, 18, 207, 8, 83, 133, 16, 146, 212, 36, 225, 82, 44, 195, 211, 80, 84, 128, 68, 9, 198, 76, 192, 71, 80, 84, 137, 20, 13, 138, 6, 15, 18, 18, 195, 166, 4, 5, 18, 9, 20, 10, 199, 72, 84, 211, 61, 84, 131, 20, 20, 10, 199, 36, 115, 143, 72, 19, 131, 20, 20, 0, 11, 200, 77, 66, 77, 84, 192, 84, 61, 32, 20, 11, 200, 4, 224, 76, 101, 48, 84, 61, 32, 20, 11, 200, 16, 148, 211, 20, 229, 9, 21, 32, 20, 10, 135, 18, 195, 184, 22, 5, 18, 9, 20, 6, 195, 28, 83, 137, 20, 9, 198, 44, 20, 9, 80, 19, 0, 20, 0, 12, 201, 84, 225, 196, 60, 211, 69, 48, 145, 192, 20, 8, 197, 20, 198, 83, 36, 80, 20, 8, 197, 8, 82, 214, 20, 208, 20, 12, 201, 77, 1, 75, 81, 35, 199, 72, 17, 128, 20, 8, 197, 44, 20, 129, 16, 80, 20, 0, 11, 136, 20, 1, 20, 15, 22, 195, 184, 18, 20, 9, 198, 72, 20, 137, 80, 85, 0, 20, 18, 70, 8, 148, 203, 84, 149, 0, 69, 37, 87, 49, 82, 6, 37, 47, 0, 20, 9, 198, 88, 146, 193, 72, 144, 84, 20, 9, 198, 77, 84, 146, 60, 112, 84, 20, 0, 9, 198, 36, 225, 15, 48, 241, 201, 20, 9, 198, 52, 146, 210, 61, 67, 205, 20, 10, 199, 36, 226, 193, 52, 147, 133, 72, 20, 10, 199, 36, 195, 21, 52, 147, 133, 72, 20, 10, 199, 65, 54, 75, 36, 21, 18, 36, 20, 10, 199, 64, 20, 9, 77, 65, 82, 36, 20, 10, 199, 61, 5, 15, 52, 85, 18, 36, 20, 10, 199, 17, 148, 197, 57, 65, 82, 36, 20, 9, 198, 36, 212, 5, 72, 149, 77, 20, 28, 67, 48, 149, 0, 55, 37, 70, 106, 48, 108, 34, 6, 110, 70, 0, 20, 82, 100, 101, 32, 112, 97, 114, 97, 100, 101, 32, 0, 11, 200, 44, 243, 134, 20, 181, 21, 72, 80, 20, 12, 201, 80, 18, 201, 77, 67, 211, 44, 244, 0, 20, 12, 201, 20, 193, 75, 81, 35, 211, 44, 244, 0, 20, 11, 200, 52, 147, 133, 72, 19, 15, 28, 144, 20, 11, 200, 45, 33, 77, 48, 243, 15, 28, 144, 20, 11, 200, 84, 67, 5, 88, 84, 137, 56, 112, 20, 11, 200, 81, 32, 83, 76, 84, 137, 56, 112, 20, 11, 200, 80, 20, 137, 24, 84, 137, 56, 112, 20, 11, 200, 77, 84, 16, 48, 84, 137, 56, 112, 20, 11, 200, 64, 19, 143, 72, 84, 137, 56, 112, 20, 11, 200, 53, 83, 11, 80, 84, 137, 56, 112, 20, 12, 137, 12, 195, 166, 4, 5, 18, 9, 14, 7, 20, 11, 200, 29, 32, 68, 84, 84, 137, 56, 112, 20, 11, 200, 25, 35, 212, 80, 84, 137, 56, 112, 20, 11, 200, 21, 96, 76, 84, 84, 137, 56, 112, 20, 11, 200, 17, 33, 83, 76, 84, 137, 56, 112, 20, 11, 200, 16, 83, 79, 48, 84, 137, 56, 112, 20, 11, 200, 16, 81, 137, 56, 84, 137, 56, 112, 20, 11, 200, 5, 34, 201, 88, 84, 137, 56, 112, 20, 11, 200, 24, 19, 148, 5, 50, 82, 36, 112, 20, 9, 198, 4, 84, 143, 76, 243, 0, 20, 11, 200, 64, 84, 137, 60, 66, 75, 84, 208, 20, 11, 200, 21, 2, 67, 20, 229, 18, 84, 208, 20, 6, 195, 52, 19, 137, 20, 9, 198, 44, 241, 9, 12, 147, 0, 20, 9, 198, 12, 19, 69, 72, 245, 78, 20, 11, 200, 44, 243, 134, 21, 33, 78, 12, 80, 20, 9, 198, 25, 35, 206, 80, 19, 0, 20, 9, 198, 16, 80, 201, 52, 19, 0, 20, 0, 12, 201, 32, 85, 5, 72, 241, 15, 45, 50, 64, 20, 12, 201, 44, 243, 134, 36, 65, 78, 80, 145, 76, 20, 8, 197, 52, 82, 133, 72, 144, 20, 8, 197, 4, 225, 5, 72, 144, 20, 15, 204, 65, 54, 75, 61, 0, 84, 60, 195, 199, 37, 50, 192, 20, 12, 201, 65, 54, 75, 61, 0, 84, 37, 50, 192, 20, 10, 199, 65, 54, 75, 61, 0, 84, 36, 20, 8, 197, 73, 149, 13, 36, 176, 20, 9, 198, 65, 54, 75, 61, 0, 84, 20, 8, 197, 5, 34, 193, 16, 80, 20, 0, 10, 135, 16, 1, 19, 20, 195, 184, 19, 20, 11, 136, 19, 1, 2, 15, 20, 195, 184, 18, 20, 9, 198, 17, 148, 198, 5, 50, 64, 20, 9, 198, 76, 147, 9, 44, 21, 0, 20, 9, 198, 64, 192, 71, 36, 21, 0, 20, 9, 198, 44, 20, 197, 52, 21, 0, 20, 8, 66, 61, 48, 112, 87, 0, 76, 11, 4, 14, 195, 165, 18, 50, 112, 34, 0, 8, 0, 10, 199, 4, 69, 143, 44, 21, 21, 72, 20, 12, 137, 18, 5, 4, 1, 11, 20, 195, 184, 18, 20, 12, 137, 16, 18, 15, 3, 5, 4, 195, 184, 18, 20, 14, 203, 8, 84, 212, 36, 19, 9, 76, 84, 137, 56, 112, 69, 10, 199, 76, 149, 21, 5, 66, 79, 56, 20, 10, 199, 72, 81, 1, 45, 66, 79, 56, 20, 10, 199, 72, 17, 9, 5, 66, 79, 56, 20, 10, 199, 36, 226, 133, 45, 66, 79, 56, 20, 10, 199, 36, 225, 133, 45, 66, 79, 56, 20, 14, 203, 81, 34, 86, 36, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 77, 66, 71, 52, 21, 9, 76, 84, 137, 56, 112, 20, 14, 203, 76, 176, 78, 16, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 76, 82, 211, 84, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 72, 17, 9, 44, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 53, 84, 201, 44, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 40, 245, 82, 56, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 36, 211, 79, 8, 147, 9, 76, 84, 137, 56, 112, 20, 14, 203, 32, 243, 79, 48, 241, 201, 76, 84, 137, 56, 112, 20, 14, 203, 28, 83, 133, 72, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 16, 83, 79, 72, 19, 9, 76, 84, 137, 56, 112, 20, 14, 203, 8, 84, 212, 36, 19, 9, 76, 84, 137, 56, 112, 20, 12, 201, 36, 229, 5, 57, 66, 79, 56, 83, 0, 20, 9, 198, 76, 243, 1, 72, 149, 77, 20, 9, 198, 41, 81, 9, 12, 149, 77, 20, 9, 198, 52, 85, 15, 57, 147, 73, 20, 9, 198, 64, 225, 85, 52, 243, 137, 20, 10, 199, 72, 149, 129, 48, 147, 132, 20, 20, 10, 67, 52, 147, 128, 63, 37, 50, 0, 72, 0, 7, 196, 32, 84, 149, 80, 20, 11, 200, 64, 243, 9, 80, 243, 15, 28, 144, 20, 11, 200, 21, 50, 193, 80, 243, 15, 28, 144, 20, 11, 200, 20, 208, 146, 100, 243, 15, 28, 144, 20, 11, 200, 65, 35, 212, 21, 53, 5, 72, 80, 20, 9, 198, 45, 34, 84, 37, 49, 82, 20, 9, 198, 44, 244, 146, 36, 113, 82, 20, 9, 198, 36, 229, 18, 36, 113, 82, 20, 9, 198, 36, 212, 12, 36, 49, 82, 20, 9, 198, 32, 84, 143, 37, 49, 82, 20, 9, 198, 16, 148, 211, 20, 177, 82, 20, 11, 200, 80, 84, 212, 36, 211, 206, 36, 80, 20, 11, 200, 16, 145, 134, 21, 33, 78, 12, 80, 20, 17, 4, 95, 48, 77, 52, 69, 37, 55, 37, 57, 6, 39, 12, 50, 106, 0, 0, 14, 139, 13, 1, 14, 21, 4, 21, 11, 20, 195, 184, 18, 20, 12, 201, 64, 84, 150, 21, 36, 201, 80, 85, 0, 20, 9, 198, 88, 148, 197, 72, 147, 135, 20, 9, 198, 72, 20, 197, 72, 147, 135, 20, 9, 198, 65, 84, 133, 72, 147, 135, 20, 17, 142, 16, 15, 18, 20, 18, 195, 166, 20, 20, 5, 18, 9, 14, 7, 20, 9, 198, 64, 243, 5, 72, 147, 135, 20, 13, 138, 13, 195, 184, 2, 12, 5, 18, 9, 14, 7, 20, 9, 198, 48, 20, 197, 72, 147, 135, 20, 9, 198, 28, 83, 5, 72, 147, 135, 20, 9, 198, 8, 20, 197, 72, 147, 135, 20, 12, 137, 16, 18, 195, 166, 19, 5, 14, 9, 12, 20, 0, 15, 140, 4, 5, 19, 9, 14, 6, 5, 11, 20, 195, 184, 18, 20, 9, 198, 64, 21, 75, 37, 53, 0, 20, 9, 198, 16, 144, 75, 72, 243, 128, 20, 9, 198, 76, 82, 212, 36, 243, 128, 20, 9, 198, 72, 82, 212, 36, 243, 128, 20, 9, 198, 64, 244, 148, 36, 243, 128, 20, 9, 198, 48, 82, 212, 36, 243, 128, 20, 13, 202, 44, 243, 134, 36, 117, 82, 5, 66, 79, 56, 20, 13, 202, 44, 243, 134, 20, 65, 82, 5, 66, 79, 56, 20, 13, 202, 36, 225, 9, 88, 145, 21, 5, 66, 79, 56, 20, 9, 198, 24, 146, 212, 36, 243, 128, 20, 9, 198, 24, 18, 212, 36, 243, 128, 20, 9, 198, 20, 66, 84, 36, 243, 128, 20, 9, 198, 16, 146, 212, 36, 243, 128, 20, 13, 202, 4, 195, 9, 81, 65, 82, 5, 66, 79, 56, 20, 13, 202, 4, 113, 204, 85, 66, 78, 5, 66, 79, 56, 20, 9, 198, 52, 83, 1, 56, 147, 128, 20, 9, 198, 52, 22, 129, 72, 147, 128, 20, 17, 70, 12, 128, 71, 72, 147, 128, 89, 35, 79, 34, 6, 107, 66, 0, 20, 9, 198, 52, 86, 9, 12, 19, 128, 20, 9, 198, 44, 19, 148, 36, 19, 128, 20, 9, 198, 32, 18, 84, 36, 19, 128, 20, 9, 198, 29, 82, 78, 20, 19, 128, 20, 9, 198, 8, 245, 19, 92, 19, 128, 20, 17, 4, 95, 48, 77, 50, 63, 37, 55, 37, 57, 6, 39, 12, 50, 112, 0, 0, 18, 5, 4, 10, 39, 5, 18, 70, 37, 12, 6, 70, 57, 36, 12, 57, 112, 0, 16, 141, 16, 18, 195, 166, 19, 5, 14, 20, 1, 20, 9, 15, 14, 20, 10, 199, 56, 149, 18, 21, 34, 78, 28, 20, 10, 199, 44, 19, 11, 21, 34, 78, 28, 20, 10, 199, 32, 19, 22, 21, 34, 78, 28, 20, 10, 199, 29, 32, 86, 21, 34, 78, 28, 20, 10, 199, 28, 195, 211, 21, 34, 78, 28, 20, 10, 199, 60, 97, 137, 12, 147, 133, 48, 20, 12, 137, 16, 18, 195, 166, 12, 21, 4, 5, 18, 20, 12, 201, 45, 38, 80, 80, 241, 210, 4, 97, 82, 20, 10, 199, 64, 84, 134, 20, 181, 21, 52, 20, 10, 199, 64, 243, 25, 28, 243, 129, 48, 20, 10, 199, 61, 37, 15, 28, 243, 129, 48, 20, 10, 199, 72, 83, 21, 45, 64, 78, 76, 20, 17, 4, 95, 48, 77, 51, 63, 37, 55, 37, 57, 6, 110, 12, 70, 106, 0, 0, 7, 196, 44, 20, 21, 80, 20, 12, 201, 85, 32, 129, 56, 148, 197, 72, 147, 135, 20, 12, 201, 84, 64, 129, 77, 83, 133, 72, 147, 135, 20, 12, 201, 81, 148, 9, 24, 144, 197, 72, 147, 135, 20, 12, 201, 80, 149, 143, 48, 148, 197, 72, 147, 135, 20, 12, 201, 80, 83, 65, 80, 148, 197, 72, 147, 135, 20, 12, 201, 80, 83, 5, 24, 243, 133, 72, 147, 135, 20, 12, 201, 76, 128, 77, 64, 243, 133, 72, 147, 135, 20, 12, 201, 76, 21, 9, 72, 148, 197, 72, 147, 135, 20, 12, 201, 72, 243, 65, 56, 148, 197, 72, 147, 135, 20, 12, 201, 72, 149, 129, 48, 148, 197, 72, 147, 135, 20, 12, 201, 72, 84, 212, 5, 84, 133, 72, 147, 135, 20, 12, 201, 72, 83, 80, 48, 16, 197, 72, 147, 135, 20, 12, 201, 72, 81, 84, 4, 35, 5, 72, 147, 135, 20, 12, 201, 72, 81, 18, 21, 52, 197, 72, 147, 135, 20, 12, 201, 72, 21, 9, 24, 144, 197, 72, 147, 135, 20, 12, 201, 64, 243, 65, 16, 148, 197, 72, 147, 135, 20, 12, 201, 64, 243, 5, 52, 148, 197, 72, 147, 135, 20, 12, 201, 64, 83, 147, 36, 243, 133, 72, 147, 135, 20, 12, 201, 64, 20, 129, 49, 148, 197, 72, 147, 135, 20, 12, 201, 61, 33, 193, 56, 148, 197, 72, 147, 135, 20, 12, 201, 53, 83, 73, 24, 144, 197, 72, 147, 135, 20, 12, 201, 52, 245, 15, 72, 148, 197, 72, 147, 135, 20, 12, 201, 52, 244, 129, 48, 148, 197, 72, 147, 135, 20, 12, 201, 52, 240, 137, 48, 148, 197, 72, 147, 135, 20, 12, 201, 52, 18, 143, 72, 148, 197, 72, 147, 135, 20, 12, 201, 52, 17, 193, 76, 147, 133, 72, 147, 135, 20, 12, 201, 44, 21, 5, 44, 148, 197, 72, 147, 135, 20, 12, 201, 44, 19, 143, 56, 148, 197, 72, 147, 135, 20, 12, 201, 44, 19, 129, 48, 148, 197, 72, 147, 135, 20, 12, 201, 36, 228, 212, 4, 195, 5, 72, 147, 135, 20, 12, 201, 36, 225, 16, 48, 16, 197, 72, 147, 135, 20, 12, 201, 36, 225, 11, 5, 52, 197, 72, 147, 135, 20, 12, 201, 36, 211, 85, 56, 148, 197, 72, 147, 135, 20, 12, 201, 33, 83, 65, 56, 148, 197, 72, 147, 135, 20, 12, 201, 24, 83, 73, 56, 148, 197, 72, 147, 135, 20, 12, 201, 24, 21, 143, 72, 148, 197, 72, 147, 135, 20, 12, 201, 24, 19, 129, 80, 148, 197, 72, 147, 135, 20, 12, 201, 20, 208, 78, 12, 148, 5, 72, 147, 135, 20, 12, 201, 16, 84, 212, 36, 195, 5, 72, 147, 135, 20, 12, 201, 16, 83, 129, 81, 84, 133, 72, 147, 135, 20, 12, 201, 8, 19, 129, 48, 148, 197, 72, 147, 135, 20, 12, 201, 4, 181, 9, 88, 148, 197, 72, 147, 135, 20, 9, 198, 88, 146, 193, 72, 145, 82, 20, 9, 198, 76, 81, 210, 20, 113, 82, 20, 9, 198, 72, 83, 1, 45, 49, 82, 20, 9, 198, 56, 81, 204, 36, 113, 82, 20, 9, 198, 44, 244, 146, 84, 113, 82, 20, 9, 198, 8, 243, 9, 88, 144, 78, 20, 11, 67, 52, 147, 133, 63, 6, 37, 50, 13, 0, 0, 9, 198, 28, 83, 133, 4, 195, 199, 20, 12, 201, 88, 149, 137, 76, 82, 212, 36, 243, 128, 20, 12, 201, 77, 80, 148, 72, 18, 212, 36, 243, 128, 20, 12, 201, 72, 84, 212, 72, 146, 212, 36, 243, 128, 20, 18, 143, 18, 5, 16, 18, 195, 166, 19, 5, 14, 20, 1, 20, 9, 15, 14, 20, 12, 201, 72, 82, 214, 37, 50, 84, 36, 243, 128, 20, 12, 201, 65, 83, 139, 80, 18, 212, 36, 243, 128, 20, 12, 201, 65, 35, 208, 61, 50, 84, 36, 243, 128, 20, 12, 201, 60, 36, 212, 73, 82, 212, 36, 243, 128, 20, 12, 201, 44, 243, 148, 72, 18, 212, 36, 243, 128, 20, 12, 201, 44, 243, 80, 61, 50, 84, 36, 243, 128, 20, 12, 201, 36, 228, 212, 73, 82, 212, 36, 243, 128, 20, 12, 201, 16, 148, 212, 72, 18, 212, 36, 243, 128, 20, 12, 201, 16, 145, 134, 72, 18, 212, 36, 243, 128, 20, 12, 201, 8, 83, 133, 16, 146, 212, 36, 243, 128, 20, 12, 201, 4, 178, 214, 37, 50, 84, 36, 243, 128, 20, 12, 201, 4, 36, 212, 72, 18, 212, 36, 243, 128, 20, 9, 198, 72, 242, 197, 72, 147, 135, 20, 9, 198, 24, 147, 5, 72, 147, 135, 20, 9, 198, 16, 244, 197, 72, 147, 135, 20, 9, 198, 5, 35, 69, 72, 147, 135, 20, 14, 139, 11, 195, 184, 14, 19, 11, 22, 15, 20, 5, 18, 20, 14, 4, 95, 48, 77, 49, 47, 6, 40, 12, 87, 14, 50, 0, 0, 9, 198, 56, 85, 84, 72, 243, 128, 20, 13, 138, 16, 15, 18, 195, 184, 19, 9, 20, 5, 20, 20, 13, 202, 77, 68, 129, 8, 17, 19, 21, 34, 78, 28, 20, 13, 202, 64, 20, 129, 25, 32, 83, 21, 34, 78, 28, 20, 13, 202, 33, 148, 15, 77, 64, 83, 21, 34, 78, 28, 20, 13, 202, 16, 243, 69, 77, 66, 67, 21, 34, 78, 28, 20, 15, 204, 36, 228, 212, 73, 83, 69, 57, 64, 76, 37, 49, 82, 20, 11, 66, 64, 32, 81, 37, 50, 35, 55, 0, 42, 9, 198, 44, 241, 134, 20, 147, 128, 20, 12, 201, 65, 34, 77, 37, 66, 86, 37, 51, 69, 20, 12, 201, 60, 34, 133, 45, 66, 86, 37, 51, 69, 20, 12, 201, 49, 85, 8, 21, 32, 78, 37, 51, 69, 20, 13, 4, 95, 2, 18, 22, 69, 34, 6, 37, 12, 82, 0, 0, 9, 198, 64, 83, 5, 72, 147, 133, 20, 9, 198, 44, 243, 5, 72, 147, 133, 20, 10, 199, 12, 16, 146, 36, 243, 5, 80, 20, 14, 139, 13, 15, 14, 4, 195, 166, 14, 9, 20, 5, 20, 20, 15, 204, 80, 82, 206, 60, 180, 129, 80, 148, 197, 72, 147, 135, 20, 15, 204, 76, 176, 78, 16, 147, 129, 88, 148, 197, 72, 147, 135, 20, 15, 204, 65, 35, 194, 48, 83, 65, 80, 148, 197, 72, 147, 135, 20, 15, 204, 52, 84, 139, 4, 229, 9, 48, 148, 197, 72, 147, 135, 20, 15, 204, 24, 146, 212, 36, 243, 129, 48, 148, 197, 72, 147, 135, 20, 15, 204, 16, 83, 73, 56, 84, 129, 48, 148, 197, 72, 147, 135, 20, 15, 204, 16, 80, 197, 57, 68, 129, 48, 148, 197, 72, 147, 135, 20, 15, 204, 12, 243, 148, 4, 147, 133, 72, 148, 197, 72, 147, 135, 20, 12, 201, 65, 34, 77, 37, 66, 86, 37, 49, 82, 20, 12, 201, 60, 34, 133, 45, 66, 86, 37, 49, 82, 20, 12, 201, 20, 193, 75, 81, 34, 70, 36, 49, 82, 20, 12, 201, 16, 145, 134, 21, 33, 78, 80, 145, 82, 20, 13, 138, 8, 15, 13, 195, 184, 15, 16, 1, 20, 9, 20, 9, 198, 32, 84, 143, 37, 51, 69, 20, 9, 198, 24, 20, 195, 37, 51, 69, 20, 0, 11, 136, 19, 20, 195, 184, 22, 12, 5, 20, 20, 12, 201, 88, 242, 193, 48, 148, 197, 72, 147, 135, 20, 12, 201, 88, 148, 137, 48, 148, 197, 72, 147, 135, 20, 12, 201, 80, 84, 146, 5, 52, 197, 72, 147, 135, 20, 12, 201, 76, 213, 75, 44, 84, 197, 72, 147, 135, 20, 12, 201, 64, 243, 9, 80, 148, 197, 72, 147, 135, 20, 12, 201, 48, 242, 193, 48, 148, 197, 72, 147, 135, 20, 12, 201, 48, 81, 193, 48, 148, 197, 72, 147, 135, 20, 12, 201, 44, 243, 134, 61, 35, 69, 72, 147, 135, 20, 12, 201, 44, 243, 134, 37, 35, 69, 72, 147, 135, 20, 12, 201, 37, 51, 1, 52, 148, 197, 72, 147, 135, 20, 12, 201, 36, 195, 21, 52, 147, 133, 72, 147, 135, 20, 12, 201, 36, 65, 65, 48, 148, 197, 72, 147, 135, 20, 12, 201, 29, 34, 77, 5, 52, 197, 72, 147, 135, 20, 12, 201, 24, 197, 73, 16, 148, 197, 72, 147, 135, 20, 12, 201, 24, 20, 200, 36, 243, 133, 72, 147, 135, 20, 12, 201, 16, 82, 204, 5, 52, 197, 72, 147, 135, 20, 12, 201, 16, 80, 200, 36, 100, 133, 72, 147, 135, 20, 13, 138, 195, 166, 19, 20, 5, 20, 9, 11, 5, 18, 20, 7, 196, 52, 20, 137, 56, 20, 7, 196, 52, 147, 73, 44, 20, 7, 196, 52, 20, 137, 56, 20, 6, 195, 88, 244, 133, 72, 0, 12, 201, 77, 84, 5, 73, 98, 83, 36, 243, 128, 20, 16, 141, 18, 5, 12, 9, 7, 9, 195, 184, 19, 9, 20, 5, 20, 20, 16, 141, 13, 15, 14, 19, 20, 18, 195, 184, 19, 9, 20, 5, 20, 20, 8, 197, 44, 21, 84, 20, 192, 20, 8, 197, 44, 21, 84, 20, 192, 20, 14, 139, 195, 184, 11, 21, 13, 5, 14, 9, 11, 5, 18, 20, 8, 197, 9, 33, 84, 60, 224, 20, 8, 197, 52, 81, 9, 4, 224, 21, 0, 18, 207, 36, 229, 5, 72, 224, 84, 36, 243, 129, 48, 148, 197, 72, 147, 135, 20, 18, 207, 36, 228, 212, 37, 69, 84, 36, 243, 129, 48, 148, 197, 72, 147, 135, 20, 9, 198, 88, 148, 201, 80, 84, 128, 20, 9, 198, 88, 19, 9, 16, 84, 128, 20, 9, 198, 81, 84, 195, 32, 84, 128, 20, 9, 198, 77, 64, 70, 24, 84, 128, 20, 9, 198, 77, 3, 206, 76, 84, 128, 20, 9, 198, 72, 84, 5, 80, 84, 128, 20, 9, 198, 72, 83, 1, 80, 84, 128, 20, 9, 198, 60, 225, 21, 48, 84, 128, 20, 9, 198, 52, 147, 137, 52, 84, 128, 20, 9, 198, 52, 18, 213, 48, 84, 128, 20, 9, 198, 41, 80, 137, 48, 84, 128, 20, 9, 198, 36, 229, 129, 16, 84, 128, 20, 9, 198, 28, 19, 15, 64, 84, 128, 20, 9, 198, 16, 82, 193, 80, 84, 128, 20, 12, 201, 64, 242, 78, 80, 147, 12, 37, 51, 69, 20, 9, 198, 24, 243, 9, 4, 229, 0, 20, 9, 198, 77, 1, 78, 16, 16, 128, 20, 0, 12, 201, 16, 148, 211, 60, 50, 65, 80, 147, 206, 20, 18, 143, 9, 18, 18, 5, 12, 9, 7, 9, 195, 184, 19, 9, 20, 5, 20, 20, 9, 198, 76, 178, 84, 76, 84, 133, 20, 10, 199, 76, 128, 77, 64, 243, 133, 72, 20, 9, 198, 65, 83, 139, 80, 84, 133, 20, 9, 198, 64, 147, 15, 80, 84, 133, 20, 10, 199, 44, 243, 147, 36, 115, 133, 72, 20, 10, 199, 48, 21, 129, 16, 83, 9, 28, 20, 10, 199, 28, 145, 193, 57, 66, 83, 44, 20, 10, 199, 25, 33, 78, 21, 66, 83, 44, 20, 9, 198, 77, 147, 143, 57, 147, 73, 20, 10, 199, 77, 66, 76, 37, 53, 9, 44, 20, 10, 199, 77, 64, 84, 37, 53, 9, 44, 20, 10, 199, 76, 179, 204, 5, 53, 9, 44, 20, 6, 195, 88, 244, 128, 72, 5, 195, 24, 244, 128, 0, 19, 70, 21, 53, 18, 4, 115, 206, 36, 87, 47, 51, 35, 79, 6, 112, 66, 0, 20, 7, 196, 48, 20, 9, 56, 20, 11, 200, 76, 192, 71, 20, 196, 197, 4, 224, 20, 0, 8, 197, 64, 243, 80, 60, 224, 20, 12, 201, 80, 18, 212, 72, 81, 213, 48, 84, 128, 20, 12, 201, 77, 65, 84, 61, 50, 207, 64, 84, 128, 20, 12, 201, 72, 82, 212, 61, 50, 207, 64, 84, 128, 20, 12, 201, 72, 82, 1, 8, 147, 9, 80, 84, 128, 20, 12, 201, 4, 100, 1, 81, 37, 76, 40, 84, 128, 20, 12, 201, 44, 243, 147, 81, 34, 78, 28, 84, 128, 20, 12, 201, 20, 180, 208, 48, 144, 201, 80, 84, 128, 20, 15, 204, 77, 84, 18, 4, 224, 84, 85, 32, 76, 37, 51, 69, 20, 8, 197, 64, 20, 21, 4, 224, 20, 12, 201, 81, 32, 78, 77, 3, 210, 80, 16, 128, 20, 0, 9, 198, 76, 83, 129, 80, 244, 128, 20, 9, 198, 16, 243, 129, 80, 244, 128, 20, 18, 207, 8, 83, 133, 24, 144, 197, 24, 244, 133, 77, 66, 76, 48, 147, 135, 67, 9, 198, 60, 178, 213, 64, 84, 128, 20, 9, 198, 45, 96, 68, 72, 84, 128, 20, 9, 198, 20, 213, 76, 28, 84, 128, 20, 9, 198, 16, 82, 213, 64, 84, 128, 20, 9, 198, 4, 227, 143, 80, 84, 128, 20, 13, 202, 33, 145, 18, 60, 70, 78, 4, 210, 83, 44, 20, 13, 202, 16, 84, 141, 5, 67, 204, 60, 114, 83, 44, 20, 13, 202, 9, 35, 205, 5, 67, 204, 60, 114, 83, 44, 20, 13, 202, 4, 229, 18, 61, 3, 204, 60, 114, 83, 44, 20, 9, 198, 72, 80, 71, 20, 229, 0, 20, 9, 198, 52, 148, 197, 72, 16, 128, 20, 0, 10, 199, 77, 80, 195, 21, 52, 207, 72, 20, 9, 198, 64, 243, 25, 45, 35, 205, 20, 10, 199, 76, 83, 147, 5, 66, 79, 56, 20, 10, 199, 44, 20, 211, 5, 66, 79, 56, 20, 10, 199, 44, 20, 18, 36, 243, 5, 72, 20, 9, 198, 24, 147, 5, 80, 84, 133, 20, 9, 198, 20, 180, 201, 48, 84, 133, 20, 10, 199, 8, 19, 19, 81, 148, 137, 28, 20, 10, 199, 80, 82, 212, 60, 226, 83, 44, 20, 10, 199, 21, 2, 83, 60, 66, 83, 44, 20, 9, 198, 45, 84, 137, 61, 53, 77, 20, 10, 199, 60, 36, 203, 85, 32, 78, 80, 20, 10, 199, 32, 244, 208, 37, 64, 78, 80, 20, 10, 199, 5, 69, 5, 77, 64, 78, 80, 20, 10, 199, 4, 48, 197, 65, 64, 78, 80, 20, 0, 11, 200, 44, 243, 147, 20, 228, 213, 4, 192, 20, 0, 12, 201, 72, 81, 197, 56, 84, 129, 80, 244, 128, 20, 12, 201, 44, 243, 210, 16, 147, 129, 80, 244, 128, 20, 12, 201, 36, 228, 197, 52, 147, 129, 80, 244, 128, 20, 12, 201, 20, 180, 193, 52, 147, 129, 80, 244, 128, 20, 12, 201, 20, 180, 212, 72, 20, 15, 48, 84, 128, 20, 12, 201, 57, 144, 143, 72, 113, 78, 76, 84, 128, 20, 9, 198, 80, 243, 5, 72, 19, 147, 20, 9, 198, 72, 83, 5, 88, 19, 147, 20, 0, 9, 198, 88, 148, 203, 61, 49, 64, 20, 13, 202, 81, 32, 78, 77, 3, 211, 37, 66, 79, 56, 20, 13, 202, 72, 82, 212, 36, 98, 75, 5, 66, 79, 56, 20, 9, 198, 77, 146, 207, 24, 19, 148, 20, 9, 198, 36, 212, 15, 76, 19, 148, 20, 9, 198, 9, 34, 76, 48, 19, 148, 20, 0, 12, 201, 88, 84, 147, 36, 98, 75, 5, 67, 210, 20, 12, 201, 77, 64, 66, 36, 194, 83, 5, 67, 210, 20, 9, 198, 17, 148, 204, 20, 180, 201, 20, 10, 199, 32, 148, 16, 60, 68, 143, 52, 20, 9, 198, 76, 19, 1, 80, 84, 137, 20, 10, 199, 72, 84, 201, 77, 64, 78, 76, 20, 0, 11, 200, 44, 243, 148, 4, 210, 78, 21, 32, 20, 12, 201, 36, 225, 137, 56, 149, 9, 88, 148, 203, 20, 9, 198, 81, 85, 129, 49, 80, 78, 20, 0, 12, 201, 64, 20, 143, 16, 243, 148, 61, 49, 64, 20, 8, 197, 85, 34, 78, 21, 32, 20, 8, 197, 56, 149, 18, 21, 32, 20, 12, 201, 4, 178, 213, 72, 21, 5, 77, 49, 64, 20, 9, 198, 24, 147, 9, 64, 83, 147, 20, 9, 198, 9, 34, 76, 48, 19, 147, 20, 12, 201, 36, 229, 5, 73, 1, 76, 48, 19, 148, 20, 0, 18, 70, 20, 180, 208, 61, 49, 64, 36, 79, 87, 48, 39, 87, 6, 36, 0, 20, 9, 198, 21, 2, 71, 72, 17, 128, 20, 9, 198, 73, 81, 9, 52, 83, 148, 20, 9, 198, 16, 82, 193, 16, 83, 148, 20, 9, 198, 72, 85, 133, 73, 48, 76, 20, 9, 198, 80, 243, 5, 72, 19, 148, 20, 9, 198, 72, 83, 5, 88, 19, 148, 20, 9, 198, 61, 33, 9, 56, 19, 148, 20, 9, 198, 25, 32, 80, 64, 19, 148, 20, 9, 198, 24, 145, 213, 72, 19, 148, 20, 0, 9, 198, 76, 181, 76, 44, 84, 137, 20, 10, 199, 20, 208, 129, 48, 192, 71, 20, 20, 0, 7, 196, 76, 145, 143, 56, 20, 9, 198, 21, 65, 82, 56, 83, 0, 20, 9, 198, 44, 244, 132, 36, 19, 0, 20, 9, 198, 4, 67, 73, 72, 19, 0, 20, 0, 9, 134, 22, 9, 14, 195, 184, 19, 20, 8, 197, 44, 243, 132, 60, 208, 20, 12, 201, 16, 83, 9, 44, 21, 5, 77, 49, 64, 20, 8, 197, 8, 146, 201, 56, 144, 20, 8, 197, 81, 32, 70, 36, 176, 20, 12, 201, 20, 180, 212, 72, 21, 129, 28, 19, 148, 20, 0, 10, 135, 14, 9, 20, 18, 195, 184, 19, 20, 11, 136, 5, 13, 1, 12, 10, 195, 184, 18, 20, 9, 198, 25, 33, 78, 21, 50, 64, 20, 9, 198, 44, 245, 5, 48, 85, 0, 20, 9, 198, 61, 33, 9, 56, 21, 0, 20, 9, 198, 4, 181, 15, 72, 21, 0, 20, 0, 26, 67, 52, 149, 0, 63, 37, 47, 15, 49, 82, 110, 6, 47, 36, 34, 0, 81, 107, 118, 97, 114, 116, 101, 114, 32, 10, 199, 32, 21, 130, 36, 243, 15, 28, 20, 10, 199, 52, 148, 211, 36, 243, 133, 72, 20, 10, 199, 21, 98, 78, 16, 83, 9, 28, 20, 10, 199, 4, 101, 1, 28, 83, 9, 28, 20, 10, 199, 81, 84, 137, 77, 66, 83, 44, 20, 10, 199, 77, 64, 84, 5, 34, 83, 44, 20, 10, 199, 72, 16, 201, 77, 66, 83, 44, 20, 10, 199, 65, 84, 137, 77, 66, 83, 44, 20, 10, 199, 64, 81, 1, 57, 66, 83, 44, 20, 10, 199, 61, 33, 193, 77, 66, 83, 44, 20, 10, 199, 56, 22, 137, 77, 66, 83, 44, 20, 10, 199, 48, 149, 21, 72, 114, 83, 44, 20, 10, 199, 45, 34, 71, 21, 34, 83, 44, 20, 10, 199, 44, 244, 205, 21, 66, 83, 44, 20, 10, 199, 20, 180, 212, 5, 66, 83, 44, 20, 10, 199, 4, 176, 68, 20, 210, 83, 44, 20, 10, 199, 81, 32, 86, 21, 37, 9, 56, 20, 9, 198, 32, 243, 79, 24, 243, 137, 20, 10, 199, 60, 198, 77, 64, 144, 68, 20, 20, 10, 67, 52, 149, 0, 63, 37, 47, 0, 72, 0, 7, 196, 56, 21, 21, 72, 20, 11, 200, 76, 83, 5, 56, 243, 15, 28, 144, 20, 9, 198, 8, 17, 193, 80, 83, 0, 20, 11, 200, 81, 32, 75, 5, 52, 197, 72, 144, 20, 11, 200, 52, 85, 1, 25, 148, 201, 76, 176, 20, 11, 200, 77, 81, 134, 37, 48, 78, 12, 80, 20, 9, 198, 52, 20, 147, 44, 19, 0, 20, 0, 13, 138, 1, 12, 2, 21, 13, 9, 14, 195, 184, 19, 20, 12, 201, 76, 147, 80, 48, 144, 201, 80, 85, 0, 20, 8, 197, 81, 34, 65, 16, 80, 20, 8, 197, 72, 242, 193, 16, 80, 20, 8, 197, 17, 38, 65, 16, 80, 20, 0, 10, 135, 16, 15, 13, 16, 195, 184, 19, 20, 11, 136, 19, 1, 14, 9, 20, 195, 184, 18, 20, 11, 136, 4, 5, 11, 1, 20, 195, 184, 18, 20, 13, 202, 20, 180, 212, 72, 245, 133, 73, 50, 79, 56, 20, 13, 202, 88, 145, 5, 57, 50, 193, 8, 83, 9, 28, 20, 13, 202, 48, 145, 5, 57, 50, 193, 8, 83, 9, 28, 20, 13, 202, 76, 83, 73, 56, 20, 137, 77, 66, 83, 44, 20, 13, 202, 72, 85, 77, 5, 67, 204, 60, 114, 83, 44, 20, 13, 202, 65, 35, 212, 21, 53, 1, 57, 66, 83, 44, 20, 13, 202, 52, 243, 133, 80, 20, 137, 77, 66, 83, 44, 20, 13, 202, 52, 85, 5, 61, 35, 204, 60, 114, 83, 44, 20, 13, 202, 45, 96, 75, 76, 19, 22, 21, 34, 83, 44, 20, 13, 202, 44, 244, 205, 61, 3, 204, 37, 66, 83, 44, 20, 13, 202, 44, 243, 148, 72, 17, 129, 45, 66, 83, 44, 20, 13, 202, 24, 243, 11, 48, 244, 137, 77, 66, 83, 44, 20, 13, 202, 16, 148, 12, 60, 208, 84, 5, 34, 83, 44, 20, 13, 202, 4, 195, 5, 72, 115, 204, 60, 114, 83, 44, 20, 9, 198, 28, 198, 75, 61, 50, 68, 20, 9, 198, 5, 4, 1, 72, 21, 0, 20, 9, 198, 4, 68, 133, 77, 48, 84, 20, 0, 10, 199, 80, 149, 21, 48, 21, 21, 72, 20, 10, 199, 44, 243, 138, 20, 181, 21, 72, 20, 10, 199, 44, 192, 86, 36, 21, 21, 72, 20, 10, 199, 44, 20, 137, 44, 21, 21, 72, 20, 12, 137, 9, 19, 15, 12, 1, 20, 195, 184, 18, 20, 12, 137, 4, 5, 2, 1, 20, 20, 195, 184, 18, 20, 10, 199, 65, 35, 198, 21, 52, 207, 72, 20, 10, 199, 80, 84, 212, 5, 66, 79, 56, 20, 10, 199, 77, 1, 68, 37, 66, 79, 56, 20, 10, 199, 44, 240, 76, 37, 66, 79, 56, 20, 10, 199, 77, 65, 78, 12, 147, 5, 72, 20, 10, 199, 45, 98, 78, 44, 83, 5, 72, 20, 10, 199, 44, 20, 148, 60, 227, 133, 72, 20, 10, 199, 44, 19, 148, 60, 227, 133, 72, 20, 10, 199, 88, 83, 2, 101, 33, 9, 28, 20, 10, 199, 81, 148, 129, 56, 226, 83, 44, 20, 10, 199, 76, 144, 77, 21, 50, 83, 44, 20, 10, 199, 44, 20, 193, 44, 130, 83, 44, 20, 10, 199, 28, 19, 22, 4, 226, 83, 44, 20, 10, 199, 64, 197, 86, 37, 84, 201, 56, 20, 12, 201, 48, 16, 137, 60, 65, 78, 80, 19, 0, 20, 10, 199, 21, 52, 12, 4, 224, 68, 20, 20, 10, 199, 12, 131, 203, 60, 192, 68, 20, 20, 0, 13, 138, 19, 20, 21, 11, 11, 1, 20, 195, 184, 18, 20, 13, 138, 18, 5, 16, 5, 20, 9, 20, 195, 184, 18, 20, 13, 138, 18, 5, 14, 15, 22, 1, 20, 195, 184, 18, 20, 13, 138, 9, 14, 14, 15, 22, 1, 20, 195, 184, 18, 20, 13, 138, 4, 5, 11, 15, 18, 1, 20, 195, 184, 18, 20, 13, 138, 2, 9, 12, 12, 5, 20, 20, 195, 184, 18, 20, 16, 141, 195, 166, 19, 20, 5, 20, 9, 19, 5, 18, 9, 14, 7, 20, 9, 198, 72, 85, 133, 73, 49, 82, 20, 11, 200, 88, 147, 132, 52, 17, 197, 72, 144, 20, 11, 200, 25, 34, 66, 101, 69, 5, 72, 144, 20, 11, 200, 8, 84, 141, 84, 64, 82, 36, 112, 20, 11, 200, 4, 193, 197, 9, 32, 73, 76, 176, 20, 0, 14, 139, 20, 18, 1, 14, 19, 12, 1, 20, 195, 184, 18, 20, 14, 139, 16, 18, 15, 22, 15, 11, 1, 20, 195, 184, 18, 20, 14, 139, 15, 2, 19, 5, 18, 22, 1, 20, 195, 184, 18, 20, 14, 139, 12, 5, 22, 5, 18, 1, 14, 4, 195, 184, 18, 20, 14, 139, 11, 15, 14, 20, 18, 15, 12, 12, 195, 184, 18, 20, 14, 139, 5, 11, 19, 16, 5, 4, 9, 20, 195, 184, 18, 20, 14, 139, 1, 19, 19, 21, 18, 1, 14, 4, 195, 184, 18, 20, 12, 201, 84, 226, 86, 21, 36, 201, 80, 85, 0, 20, 12, 201, 44, 192, 83, 76, 144, 201, 80, 85, 0, 20, 12, 201, 28, 83, 133, 72, 244, 201, 80, 85, 0, 20, 12, 201, 8, 148, 15, 48, 20, 137, 80, 85, 0, 20, 9, 198, 88, 245, 5, 72, 147, 135, 20, 9, 198, 72, 81, 197, 72, 147, 135, 20, 9, 198, 61, 5, 5, 72, 147, 135, 20, 9, 198, 60, 194, 69, 72, 147, 135, 20, 9, 198, 56, 245, 5, 72, 147, 135, 20, 9, 198, 56, 81, 197, 72, 147, 135, 20, 9, 198, 48, 81, 197, 72, 147, 135, 20, 9, 198, 48, 18, 197, 72, 147, 135, 20, 9, 198, 41, 81, 197, 72, 147, 135, 20, 9, 198, 16, 245, 5, 72, 147, 135, 20, 9, 198, 12, 149, 5, 72, 147, 135, 20, 9, 198, 5, 5, 5, 72, 147, 135, 20, 0, 15, 140, 18, 5, 11, 15, 13, 13, 1, 14, 4, 195, 184, 18, 20, 9, 198, 29, 32, 84, 37, 53, 0, 20, 9, 198, 13, 146, 204, 37, 53, 0, 20, 9, 198, 8, 20, 211, 37, 53, 0, 20, 9, 198, 8, 20, 20, 37, 53, 0, 20, 9, 198, 32, 243, 79, 24, 243, 128, 20, 13, 202, 52, 244, 148, 36, 98, 75, 5, 66, 79, 56, 20, 13, 202, 44, 243, 77, 84, 226, 75, 5, 66, 79, 56, 20, 13, 202, 28, 84, 212, 36, 181, 76, 5, 66, 79, 56, 20, 13, 202, 24, 244, 148, 36, 98, 75, 5, 66, 79, 56, 20, 9, 198, 20, 211, 212, 36, 243, 128, 20, 13, 202, 16, 148, 211, 36, 210, 76, 5, 66, 79, 56, 20, 9, 198, 8, 20, 212, 36, 243, 128, 20, 14, 139, 16, 18, 195, 166, 13, 9, 5, 18, 9, 14, 7, 20, 13, 202, 72, 244, 203, 36, 193, 5, 57, 50, 83, 44, 20, 9, 198, 65, 35, 212, 20, 147, 128, 20, 9, 198, 40, 18, 207, 8, 147, 128, 20, 0, 16, 141, 11, 15, 13, 13, 21, 14, 9, 11, 1, 20, 195, 184, 18, 20, 19, 144, 7, 18, 195, 184, 14, 12, 1, 14, 4, 9, 19, 5, 18, 9, 14, 7, 20, 10, 199, 20, 211, 212, 36, 243, 133, 48, 20, 12, 201, 76, 83, 147, 36, 34, 76, 37, 49, 82, 20, 12, 201, 8, 17, 193, 80, 83, 12, 37, 49, 82, 20, 9, 198, 28, 20, 148, 56, 84, 137, 20, 14, 203, 44, 19, 5, 40, 67, 211, 44, 244, 9, 76, 176, 20, 10, 199, 76, 49, 78, 5, 34, 85, 52, 20, 9, 198, 5, 64, 86, 37, 51, 69, 20, 9, 198, 4, 226, 77, 37, 51, 69, 20, 8, 67, 61, 85, 0, 21, 0, 10, 0, 9, 3, 14, 195, 165, 50, 112, 0, 15, 12, 201, 84, 67, 9, 12, 149, 5, 72, 147, 135, 20, 12, 201, 84, 65, 5, 48, 81, 197, 72, 147, 135, 20, 12, 201, 77, 80, 148, 72, 18, 5, 72, 147, 135, 20, 12, 201, 77, 80, 147, 36, 66, 69, 72, 147, 135, 20, 12, 201, 72, 82, 210, 85, 69, 5, 72, 147, 135, 20, 12, 201, 72, 20, 16, 61, 37, 5, 72, 147, 135, 20, 12, 201, 65, 34, 79, 72, 149, 5, 72, 147, 135, 20, 12, 201, 64, 84, 141, 37, 69, 5, 72, 147, 135, 20, 12, 201, 44, 244, 147, 21, 69, 5, 72, 147, 135, 20, 12, 201, 44, 243, 147, 81, 37, 69, 72, 147, 135, 20, 12, 201, 44, 243, 134, 37, 50, 197, 72, 147, 135, 20, 12, 201, 44, 243, 16, 61, 37, 5, 72, 147, 135, 20, 12, 201, 36, 229, 129, 48, 145, 5, 72, 147, 135, 20, 12, 201, 36, 228, 212, 37, 69, 69, 72, 147, 135, 20, 12, 201, 36, 225, 11, 61, 2, 69, 72, 147, 135, 20, 12, 201, 28, 20, 146, 61, 69, 5, 72, 147, 135, 20, 12, 201, 24, 197, 79, 72, 145, 5, 72, 147, 135, 20, 12, 201, 16, 148, 212, 72, 18, 5, 72, 147, 135, 20, 12, 201, 8, 243, 66, 5, 33, 5, 72, 147, 135, 20, 12, 201, 5, 53, 18, 36, 225, 197, 72, 147, 135, 20, 9, 198, 77, 67, 204, 81, 49, 82, 20, 9, 198, 24, 197, 75, 81, 81, 82, 20, 9, 68, 48, 84, 143, 100, 21, 0, 10, 9, 68, 12, 240, 67, 32, 21, 0, 10, 0, 12, 201, 44, 243, 80, 5, 32, 84, 37, 53, 0, 20, 12, 201, 80, 84, 212, 61, 53, 5, 72, 243, 128, 20, 12, 201, 88, 83, 148, 36, 192, 84, 36, 243, 128, 20, 12, 201, 88, 16, 195, 36, 224, 84, 36, 243, 128, 20, 12, 201, 77, 80, 147, 84, 212, 20, 36, 243, 128, 20, 12, 201, 77, 66, 80, 84, 192, 84, 36, 243, 128, 20, 12, 201, 77, 66, 77, 84, 192, 84, 36, 243, 128, 20, 12, 201, 77, 64, 71, 24, 192, 84, 36, 243, 128, 20, 12, 201, 72, 85, 1, 72, 64, 84, 36, 243, 128, 20, 12, 201, 72, 84, 201, 28, 224, 84, 36, 243, 128, 20, 12, 201, 61, 48, 201, 48, 192, 84, 36, 243, 128, 20, 12, 201, 60, 36, 212, 73, 80, 212, 36, 243, 128, 20, 12, 201, 48, 146, 214, 36, 64, 84, 36, 243, 128, 20, 12, 201, 44, 244, 146, 20, 192, 84, 36, 243, 128, 20, 12, 201, 44, 243, 132, 60, 192, 84, 36, 243, 128, 20, 12, 201, 44, 243, 80, 36, 192, 84, 36, 243, 128, 20, 12, 201, 44, 240, 71, 84, 192, 84, 36, 243, 128, 20, 12, 201, 36, 227, 203, 84, 192, 84, 36, 243, 128, 20, 12, 201, 36, 226, 204, 36, 224, 84, 36, 243, 128, 20, 12, 201, 36, 226, 193, 77, 48, 84, 36, 243, 128, 20, 12, 201, 29, 32, 78, 84, 192, 84, 36, 243, 128, 20, 12, 201, 24, 20, 195, 36, 224, 84, 36, 243, 128, 20, 12, 201, 20, 194, 77, 36, 224, 84, 36, 243, 128, 20, 12, 201, 20, 180, 212, 72, 18, 212, 36, 243, 128, 20, 12, 201, 20, 160, 75, 84, 192, 84, 36, 243, 128, 20, 12, 201, 16, 84, 201, 28, 224, 84, 36, 243, 128, 20, 12, 201, 12, 148, 139, 84, 192, 84, 36, 243, 128, 20, 12, 201, 4, 197, 5, 72, 224, 84, 36, 243, 128, 20, 12, 201, 4, 113, 210, 5, 96, 84, 36, 243, 128, 20, 12, 137, 7, 18, 195, 166, 3, 9, 20, 5, 20, 20, 9, 198, 72, 17, 5, 72, 147, 135, 20, 9, 198, 45, 33, 69, 72, 147, 135, 20, 9, 198, 28, 17, 197, 72, 147, 135, 20, 9, 198, 24, 85, 5, 72, 147, 135, 20, 9, 198, 16, 21, 5, 72, 147, 135, 20, 9, 198, 4, 181, 5, 72, 147, 135, 20, 12, 201, 65, 81, 82, 80, 244, 137, 12, 19, 128, 20, 0, 9, 198, 97, 147, 15, 24, 243, 128, 20, 9, 198, 76, 84, 211, 36, 243, 128, 20, 9, 198, 64, 20, 211, 36, 243, 128, 20, 9, 198, 52, 148, 211, 36, 243, 128, 20, 9, 198, 21, 96, 83, 36, 243, 128, 20, 9, 198, 77, 65, 65, 72, 147, 128, 20, 12, 201, 61, 4, 15, 73, 69, 78, 37, 51, 69, 20, 12, 201, 52, 48, 193, 73, 66, 25, 37, 51, 69, 20, 15, 204, 88, 244, 132, 36, 225, 194, 61, 33, 197, 57, 49, 82, 20, 9, 198, 37, 99, 210, 36, 19, 128, 20, 9, 198, 88, 85, 5, 72, 19, 128, 21, 9, 198, 44, 243, 15, 77, 48, 76, 20, 13, 202, 20, 225, 9, 52, 83, 147, 36, 243, 129, 48, 20, 13, 70, 13, 35, 213, 80, 243, 128, 21, 102, 114, 0, 10, 0, 10, 199, 77, 80, 147, 80, 149, 21, 80, 20, 14, 139, 19, 5, 18, 9, 195, 184, 19, 9, 20, 5, 20, 20, 14, 139, 16, 15, 13, 16, 195, 184, 19, 9, 20, 5, 20, 20, 14, 139, 14, 5, 18, 22, 195, 184, 19, 9, 20, 5, 20, 20, 12, 137, 15, 13, 13, 195, 184, 2, 12, 5, 18, 20, 9, 198, 77, 66, 75, 48, 84, 137, 20, 10, 199, 56, 84, 15, 80, 148, 205, 20, 20, 10, 199, 36, 66, 79, 80, 148, 205, 20, 20, 10, 199, 21, 50, 193, 64, 148, 205, 20, 20, 9, 198, 13, 146, 204, 37, 51, 69, 20, 9, 198, 8, 20, 20, 37, 51, 69, 20, 12, 201, 21, 48, 138, 21, 33, 197, 57, 49, 82, 20, 0, 15, 204, 36, 228, 213, 8, 244, 132, 36, 224, 84, 36, 243, 128, 20, 9, 198, 16, 149, 137, 76, 147, 206, 20, 15, 204, 4, 178, 204, 36, 208, 84, 37, 48, 84, 36, 243, 128, 20, 15, 140, 16, 18, 5, 20, 9, 195, 184, 19, 9, 20, 5, 20, 20, 15, 140, 16, 18, 5, 3, 9, 195, 184, 19, 9, 20, 5, 20, 20, 15, 140, 7, 5, 14, 5, 18, 195, 184, 19, 9, 20, 5, 20, 20, 12, 201, 88, 84, 137, 24, 144, 197, 72, 147, 135, 20, 12, 201, 88, 19, 15, 72, 148, 197, 72, 147, 135, 20, 12, 201, 81, 32, 78, 76, 149, 5, 72, 147, 135, 20, 12, 201, 80, 83, 5, 88, 148, 197, 72, 147, 135, 20, 12, 201, 80, 82, 211, 81, 84, 133, 72, 147, 135, 20, 12, 201, 76, 177, 76, 21, 69, 5, 72, 147, 135, 20, 12, 201, 72, 85, 129, 48, 145, 5, 72, 147, 135, 20, 12, 201, 72, 85, 15, 84, 50, 5, 72, 147, 135, 20, 12, 201, 72, 84, 212, 37, 69, 69, 72, 147, 135, 20, 12, 201, 72, 81, 140, 20, 181, 5, 72, 147, 135, 20, 12, 201, 72, 81, 86, 4, 197, 69, 72, 147, 135, 20, 12, 201, 65, 35, 202, 20, 181, 5, 72, 147, 135, 20, 12, 201, 64, 243, 1, 72, 148, 197, 72, 147, 135, 20, 12, 201, 64, 84, 150, 21, 37, 5, 72, 147, 135, 20, 12, 201, 64, 16, 201, 24, 144, 197, 72, 147, 135, 20, 12, 201, 56, 22, 137, 24, 144, 197, 72, 147, 135, 20, 12, 201, 52, 241, 9, 24, 144, 197, 72, 147, 135, 20, 12, 201, 52, 82, 193, 56, 148, 197, 72, 147, 135, 20, 12, 201, 48, 21, 9, 56, 148, 197, 72, 147, 135, 20, 12, 201, 44, 244, 146, 84, 212, 5, 72, 147, 135, 20, 12, 201, 44, 243, 150, 21, 37, 5, 72, 147, 135, 20, 12, 201, 44, 243, 147, 80, 21, 5, 72, 147, 135, 20, 12, 201, 44, 243, 77, 37, 69, 5, 72, 147, 135, 20, 12, 201, 44, 243, 15, 56, 148, 197, 72, 147, 135, 20, 12, 201, 44, 241, 9, 24, 144, 197, 72, 147, 135, 20, 12, 201, 36, 229, 9, 52, 145, 5, 72, 147, 135, 20, 12, 201, 36, 70, 76, 48, 148, 197, 72, 147, 135, 20, 12, 201, 29, 37, 66, 48, 148, 197, 72, 147, 135, 20, 12, 201, 21, 85, 18, 60, 98, 69, 72, 147, 135, 20, 12, 201, 21, 81, 143, 72, 148, 197, 72, 147, 135, 20, 12, 201, 21, 66, 75, 21, 69, 5, 72, 147, 135, 20, 12, 201, 20, 97, 133, 45, 69, 69, 72, 147, 135, 20, 12, 201, 9, 81, 7, 21, 69, 5, 72, 147, 135, 20, 12, 201, 9, 34, 75, 21, 69, 5, 72, 147, 135, 20, 12, 201, 8, 245, 1, 56, 148, 197, 72, 147, 135, 20, 12, 201, 8, 147, 12, 21, 69, 5, 72, 147, 135, 20, 12, 201, 8, 20, 212, 5, 33, 5, 72, 147, 135, 20, 12, 201, 4, 229, 9, 44, 148, 197, 72, 147, 135, 20, 12, 201, 4, 229, 5, 16, 21, 5, 72, 147, 135, 20, 12, 201, 4, 211, 210, 80, 148, 197, 72, 147, 135, 20, 12, 201, 4, 48, 197, 57, 69, 69, 72, 147, 135, 20, 12, 201, 4, 36, 212, 72, 18, 5, 72, 147, 135, 20, 0, 12, 201, 65, 35, 199, 21, 53, 5, 72, 243, 128, 20, 16, 141, 16, 18, 195, 166, 13, 1, 20, 21, 18, 9, 20, 5, 20, 20, 8, 197, 45, 33, 83, 60, 192, 20, 8, 197, 44, 20, 197, 36, 224, 20, 8, 197, 84, 180, 129, 36, 224, 20, 12, 201, 52, 243, 148, 20, 225, 71, 72, 147, 128, 20, 8, 197, 44, 244, 133, 4, 224, 20, 8, 197, 44, 83, 153, 4, 224, 20, 16, 205, 56, 21, 18, 37, 83, 66, 36, 176, 82, 8, 243, 129, 80, 20, 8, 197, 72, 83, 148, 4, 32, 20, 0, 9, 198, 64, 243, 9, 81, 84, 128, 20, 9, 198, 48, 145, 193, 81, 84, 128, 20, 9, 198, 45, 33, 65, 81, 84, 128, 20, 12, 201, 25, 84, 197, 57, 64, 83, 80, 84, 137, 20, 12, 201, 72, 81, 201, 60, 224, 76, 37, 51, 69, 20, 12, 201, 44, 243, 80, 5, 32, 84, 37, 51, 69, 20, 12, 201, 44, 193, 82, 36, 176, 76, 37, 51, 69, 20, 12, 201, 16, 83, 79, 45, 32, 84, 37, 51, 69, 20, 15, 204, 76, 176, 78, 16, 84, 130, 61, 33, 197, 57, 49, 82, 20, 0, 9, 198, 16, 144, 71, 56, 244, 197, 20, 12, 201, 36, 229, 5, 73, 97, 78, 80, 147, 206, 20, 15, 204, 44, 243, 12, 20, 181, 9, 88, 148, 197, 72, 147, 135, 20, 15, 204, 20, 180, 197, 53, 3, 9, 24, 144, 197, 72, 147, 135, 20, 15, 204, 16, 148, 203, 88, 19, 9, 24, 144, 197, 72, 147, 135, 20, 15, 204, 16, 83, 73, 48, 149, 1, 72, 148, 197, 72, 147, 135, 20, 10, 199, 76, 21, 9, 72, 148, 197, 72, 20, 10, 199, 53, 83, 73, 24, 144, 197, 72, 20, 10, 199, 52, 245, 15, 72, 148, 197, 72, 20, 10, 199, 52, 18, 143, 72, 148, 197, 72, 20, 10, 199, 44, 21, 5, 44, 148, 197, 72, 20, 10, 199, 36, 224, 85, 29, 84, 133, 72, 20, 10, 199, 24, 83, 73, 56, 148, 197, 72, 20, 10, 199, 85, 35, 204, 60, 114, 83, 44, 20, 10, 199, 76, 83, 147, 61, 34, 83, 44, 20, 10, 199, 64, 20, 9, 77, 66, 83, 44, 20, 10, 199, 48, 85, 129, 57, 66, 83, 44, 20, 10, 199, 44, 244, 137, 57, 66, 83, 44, 20, 9, 198, 52, 243, 143, 80, 243, 137, 20, 10, 199, 44, 20, 213, 37, 53, 9, 44, 20, 10, 199, 81, 84, 130, 84, 193, 78, 80, 20, 10, 199, 5, 48, 197, 56, 65, 78, 80, 20, 0, 13, 138, 13, 9, 19, 19, 9, 15, 14, 195, 166, 18, 20, 6, 195, 52, 17, 201, 20, 11, 200, 77, 84, 208, 20, 228, 201, 60, 224, 20, 9, 198, 76, 176, 78, 76, 147, 206, 20, 9, 198, 36, 225, 149, 76, 147, 206, 20, 9, 198, 21, 128, 201, 76, 147, 206, 20, 11, 200, 20, 180, 212, 20, 228, 201, 60, 224, 20, 11, 136, 16, 18, 195, 166, 19, 5, 14, 20, 20, 0, 8, 197, 64, 20, 212, 20, 192, 20, 8, 197, 44, 242, 193, 36, 224, 20, 8, 197, 64, 84, 149, 4, 224, 20, 12, 201, 36, 229, 5, 72, 84, 211, 20, 229, 0, 20, 12, 201, 36, 229, 5, 48, 194, 71, 20, 229, 0, 20, 8, 197, 76, 17, 137, 4, 224, 21, 12, 201, 12, 192, 73, 73, 99, 217, 4, 229, 0, 20, 0, 9, 198, 25, 32, 75, 81, 84, 128, 20, 13, 202, 80, 84, 141, 36, 227, 204, 60, 114, 83, 44, 20, 13, 202, 76, 83, 147, 60, 211, 212, 61, 34, 83, 44, 20, 13, 138, 16, 18, 195, 166, 4, 9, 11, 1, 14, 20, 20, 0, 17, 67, 52, 145, 192, 63, 35, 57, 15, 87, 112, 0, 81, 115, 195, 165, 32, 16, 141, 11, 15, 13, 13, 9, 19, 19, 9, 15, 14, 195, 166, 18, 20, 10, 199, 64, 144, 195, 60, 194, 78, 20, 20, 10, 199, 4, 68, 203, 36, 195, 9, 28, 20, 10, 199, 80, 19, 13, 84, 66, 83, 44, 20, 10, 199, 76, 20, 132, 60, 226, 83, 44, 20, 10, 199, 64, 193, 66, 20, 162, 83, 44, 20, 10, 199, 32, 84, 129, 48, 66, 83, 44, 20, 20, 71, 8, 243, 150, 37, 96, 78, 80, 69, 112, 66, 82, 37, 82, 6, 110, 66, 0, 20, 10, 67, 52, 145, 192, 63, 35, 57, 0, 72, 0, 7, 196, 36, 209, 78, 76, 20, 7, 196, 56, 145, 67, 20, 20, 0, 12, 69, 8, 194, 86, 21, 32, 69, 55, 37, 34, 0, 8, 197, 81, 84, 142, 21, 32, 20, 8, 197, 60, 224, 78, 21, 32, 20, 9, 198, 80, 21, 1, 72, 148, 203, 20, 9, 198, 44, 147, 133, 76, 148, 203, 20, 9, 198, 36, 70, 76, 48, 148, 203, 20, 16, 205, 24, 145, 5, 36, 179, 205, 52, 148, 211, 5, 34, 83, 44, 20, 9, 198, 8, 245, 1, 56, 148, 203, 20, 9, 198, 80, 82, 212, 60, 226, 75, 20, 8, 197, 16, 240, 197, 57, 64, 20, 9, 198, 72, 84, 201, 16, 83, 147, 20, 0, 9, 198, 80, 83, 5, 76, 179, 208, 20, 9, 198, 52, 243, 143, 48, 241, 192, 20, 9, 198, 84, 180, 129, 36, 225, 64, 20, 15, 140, 8, 9, 12, 12, 5, 18, 195, 184, 4, 9, 1, 14, 20, 9, 198, 52, 20, 135, 36, 224, 76, 20, 9, 198, 72, 245, 76, 4, 65, 64, 20, 9, 198, 8, 19, 12, 4, 65, 64, 20, 9, 198, 65, 35, 214, 36, 19, 148, 20, 9, 198, 5, 36, 143, 28, 19, 148, 20, 0, 10, 199, 12, 83, 12, 84, 195, 211, 20, 20, 10, 199, 44, 16, 130, 4, 194, 83, 80, 20, 10, 199, 64, 20, 148, 21, 34, 78, 28, 20, 10, 199, 21, 99, 204, 21, 34, 78, 28, 20, 14, 139, 195, 166, 11, 22, 1, 20, 15, 18, 9, 1, 12, 20, 0, 11, 200, 76, 84, 1, 72, 21, 9, 77, 64, 20, 11, 200, 24, 147, 1, 80, 83, 9, 77, 64, 20, 11, 200, 4, 32, 78, 16, 243, 142, 21, 32, 20, 12, 137, 20, 195, 165, 12, 13, 15, 4, 9, 7, 20, 12, 201, 60, 35, 9, 28, 21, 15, 72, 148, 203, 20, 12, 201, 36, 225, 9, 44, 21, 9, 88, 148, 203, 20, 12, 201, 33, 145, 18, 61, 65, 75, 56, 148, 203, 20, 12, 201, 5, 3, 203, 4, 198, 80, 80, 148, 203, 20, 0, 8, 197, 76, 17, 9, 77, 64, 20, 8, 197, 5, 85, 9, 77, 64, 20, 8, 197, 5, 65, 73, 77, 64, 20, 8, 197, 65, 35, 194, 21, 32, 20, 8, 197, 52, 145, 210, 21, 32, 20, 13, 138, 19, 195, 184, 18, 7, 13, 15, 4, 9, 7, 20, 12, 201, 44, 243, 148, 72, 18, 212, 48, 145, 192, 20, 13, 138, 6, 15, 18, 19, 195, 166, 20, 12, 9, 7, 20, 9, 198, 80, 149, 1, 56, 148, 203, 20, 9, 198, 76, 145, 5, 72, 148, 203, 20, 9, 198, 64, 20, 137, 76, 148, 203, 20, 9, 198, 52, 82, 193, 56, 148, 203, 20, 9, 198, 48, 18, 207, 56, 148, 203, 20, 9, 198, 41, 83, 143, 56, 148, 203, 20, 11, 136, 19, 195, 166, 12, 1, 18, 9, 5, 20, 8, 197, 72, 84, 208, 37, 64, 20, 12, 201, 32, 84, 147, 44, 84, 137, 56, 65, 64, 20, 12, 201, 25, 34, 83, 80, 84, 137, 56, 65, 64, 20, 12, 201, 8, 18, 203, 4, 229, 9, 56, 65, 64, 20, 0, 9, 198, 88, 16, 195, 36, 225, 64, 20, 27, 74, 8, 80, 200, 4, 209, 76, 76, 21, 67, 20, 69, 36, 89, 35, 63, 6, 36, 12, 60, 87, 6, 111, 12, 87, 0, 13, 202, 44, 243, 148, 72, 20, 212, 21, 34, 78, 28, 20, 13, 202, 44, 243, 147, 60, 194, 68, 21, 34, 78, 28, 20, 9, 198, 20, 193, 78, 16, 145, 192, 20, 9, 198, 56, 82, 210, 60, 98, 76, 20, 9, 198, 72, 84, 201, 16, 83, 148, 20, 9, 198, 52, 243, 149, 52, 83, 148, 20, 8, 66, 60, 112, 112, 0, 76, 8, 0, 15, 204, 44, 192, 83, 76, 145, 137, 44, 21, 15, 72, 148, 203, 20, 10, 199, 81, 84, 130, 84, 193, 78, 76, 20, 10, 199, 5, 48, 197, 56, 65, 78, 76, 20, 10, 199, 80, 18, 203, 20, 192, 71, 20, 20, 9, 198, 77, 2, 79, 56, 17, 197, 20, 6, 195, 88, 244, 148, 72, 0, 11, 200, 44, 243, 80, 72, 84, 211, 61, 32, 20, 11, 200, 76, 83, 147, 84, 19, 9, 77, 64, 20, 11, 200, 48, 81, 201, 80, 147, 73, 77, 64, 20, 11, 200, 20, 180, 212, 72, 83, 73, 77, 64, 20, 8, 198, 48, 82, 211, 36, 179, 206, 11, 200, 64, 20, 129, 24, 98, 78, 21, 32, 20, 11, 200, 44, 243, 131, 20, 229, 18, 21, 32, 20, 7, 196, 16, 240, 197, 72, 20, 12, 137, 14, 195, 184, 10, 1, 7, 20, 9, 7, 20, 12, 137, 12, 195, 184, 19, 1, 7, 20, 9, 7, 20, 12, 201, 48, 19, 135, 60, 32, 82, 16, 148, 203, 20, 12, 201, 44, 243, 147, 60, 224, 78, 80, 148, 203, 20, 12, 201, 36, 226, 9, 8, 149, 15, 72, 148, 203, 20, 12, 201, 16, 147, 5, 81, 64, 78, 80, 148, 203, 20, 12, 201, 4, 208, 149, 48, 21, 15, 72, 148, 203, 20, 7, 196, 44, 243, 73, 44, 20, 11, 200, 72, 84, 197, 73, 97, 82, 21, 64, 20, 11, 200, 45, 83, 20, 37, 97, 82, 21, 64, 20, 11, 200, 8, 19, 1, 56, 49, 82, 21, 64, 20, 12, 137, 14, 195, 184, 10, 1, 7, 20, 9, 7, 20, 12, 137, 12, 195, 184, 19, 1, 7, 20, 9, 7, 20, 7, 196, 12, 145, 193, 72, 20, 9, 198, 36, 226, 84, 36, 19, 0, 20, 0, 12, 201, 77, 64, 78, 16, 128, 70, 80, 145, 192, 20, 9, 198, 48, 80, 133, 56, 66, 71, 20, 12, 201, 33, 84, 205, 60, 65, 82, 48, 145, 192, 20, 9, 198, 25, 34, 77, 60, 66, 71, 20, 9, 198, 24, 145, 213, 72, 194, 71, 20, 12, 201, 8, 20, 141, 32, 161, 82, 80, 145, 192, 20, 12, 201, 72, 240, 137, 57, 51, 206, 4, 65, 64, 20, 0, 10, 135, 21, 18, 9, 14, 195, 184, 19, 20, 9, 198, 48, 17, 197, 72, 148, 212, 20, 14, 139, 4, 22, 195, 166, 18, 7, 1, 7, 20, 9, 7, 20, 9, 198, 77, 3, 5, 56, 66, 68, 20, 0, 11, 136, 12, 21, 13, 9, 14, 195, 184, 19, 20, 11, 136, 4, 5, 12, 9, 18, 195, 184, 19, 20, 12, 201, 81, 32, 78, 76, 210, 83, 76, 147, 206, 20, 10, 199, 88, 149, 1, 48, 148, 197, 72, 20, 10, 199, 72, 20, 16, 20, 195, 5, 72, 20, 10, 199, 64, 243, 9, 80, 148, 197, 72, 20, 10, 199, 64, 84, 147, 36, 99, 5, 72, 20, 10, 199, 48, 242, 193, 48, 148, 197, 72, 20, 10, 199, 48, 81, 193, 48, 148, 197, 72, 20, 10, 199, 36, 65, 65, 48, 148, 197, 72, 20, 15, 140, 11, 18, 1, 19, 2, 195, 184, 18, 19, 20, 9, 7, 20, 15, 140, 1, 13, 1, 20, 195, 184, 18, 1, 7, 20, 9, 7, 20, 10, 199, 80, 83, 204, 60, 114, 83, 44, 20, 10, 199, 76, 49, 78, 5, 34, 83, 44, 20, 10, 199, 72, 85, 77, 5, 66, 83, 44, 20, 10, 199, 52, 85, 5, 61, 34, 83, 44, 20, 10, 199, 45, 35, 205, 5, 66, 83, 44, 20, 10, 199, 44, 241, 206, 5, 66, 83, 44, 20, 10, 199, 40, 84, 213, 37, 66, 83, 44, 20, 10, 199, 33, 148, 212, 21, 34, 83, 44, 20, 10, 199, 21, 50, 201, 52, 242, 83, 44, 20, 10, 199, 21, 34, 84, 72, 82, 83, 44, 20, 10, 199, 8, 147, 204, 60, 114, 83, 44, 20, 10, 199, 5, 85, 5, 57, 66, 83, 44, 20, 12, 201, 76, 83, 148, 36, 209, 78, 80, 19, 0, 20, 10, 199, 40, 84, 133, 52, 144, 68, 20, 20, 0, 12, 137, 7, 12, 21, 20, 9, 14, 195, 184, 19, 20, 11, 200, 4, 229, 18, 61, 3, 204, 60, 112, 20, 11, 200, 8, 20, 139, 20, 229, 9, 56, 80, 20, 9, 198, 65, 33, 83, 76, 147, 206, 20, 9, 198, 20, 210, 83, 76, 147, 206, 20, 9, 198, 77, 3, 210, 80, 83, 0, 20, 11, 200, 77, 3, 206, 76, 244, 133, 72, 80, 20, 12, 201, 48, 19, 132, 76, 176, 66, 20, 194, 71, 20, 16, 141, 11, 18, 1, 4, 19, 2, 195, 184, 18, 19, 20, 9, 7, 20, 12, 201, 36, 225, 19, 45, 34, 86, 20, 194, 71, 20, 15, 204, 16, 148, 203, 60, 229, 9, 57, 81, 82, 48, 145, 192, 20, 11, 200, 77, 80, 148, 72, 244, 9, 76, 176, 20, 11, 200, 44, 21, 5, 28, 244, 137, 76, 176, 20, 15, 204, 76, 181, 69, 77, 2, 76, 48, 84, 137, 56, 65, 64, 20, 15, 204, 33, 84, 194, 21, 53, 25, 72, 84, 137, 56, 65, 64, 20, 11, 200, 20, 193, 75, 81, 35, 206, 36, 176, 20, 9, 68, 92, 130, 84, 20, 21, 0, 10, 0, 13, 138, 22, 15, 12, 21, 13, 9, 14, 195, 184, 19, 20, 13, 138, 11, 1, 4, 1, 22, 5, 18, 195, 184, 19, 20, 13, 138, 2, 9, 20, 21, 13, 9, 14, 195, 184, 19, 20, 14, 139, 19, 11, 22, 1, 4, 18, 15, 14, 195, 184, 18, 20, 10, 135, 13, 15, 14, 20, 195, 184, 18, 20, 8, 197, 61, 53, 5, 72, 144, 20, 9, 198, 52, 19, 133, 72, 194, 71, 20, 9, 198, 28, 241, 13, 60, 66, 71, 20, 8, 197, 37, 34, 68, 36, 80, 20, 8, 197, 45, 35, 206, 36, 176, 20, 0, 7, 66, 57, 144, 50, 114, 0, 9, 198, 84, 226, 79, 56, 148, 212, 20, 9, 198, 76, 21, 1, 56, 148, 212, 20, 9, 198, 64, 19, 148, 20, 148, 212, 20, 9, 198, 48, 240, 130, 100, 148, 212, 20, 9, 198, 44, 243, 15, 56, 148, 212, 20, 9, 198, 32, 81, 15, 56, 148, 212, 20, 9, 198, 29, 35, 211, 76, 148, 212, 20, 9, 198, 16, 83, 9, 72, 148, 212, 20, 13, 202, 76, 19, 147, 20, 211, 212, 61, 34, 83, 44, 20, 13, 202, 64, 20, 129, 80, 17, 205, 5, 66, 83, 44, 20, 13, 202, 52, 243, 143, 45, 35, 205, 5, 66, 83, 44, 20, 13, 202, 32, 81, 197, 52, 243, 137, 77, 66, 83, 44, 20, 9, 198, 100, 83, 69, 56, 149, 0, 20, 9, 198, 16, 83, 132, 72, 149, 0, 20, 9, 198, 21, 81, 197, 56, 146, 192, 20, 0, 6, 195, 56, 115, 192, 17, 12, 137, 4, 5, 19, 5, 18, 20, 195, 184, 18, 20, 10, 199, 64, 20, 132, 60, 227, 133, 72, 20, 10, 199, 16, 148, 208, 20, 228, 197, 72, 20, 10, 199, 5, 52, 201, 52, 147, 5, 72, 20, 10, 199, 80, 19, 148, 4, 194, 83, 44, 20, 10, 199, 77, 3, 210, 4, 66, 83, 44, 20, 10, 199, 49, 82, 213, 48, 194, 83, 44, 20, 10, 199, 37, 35, 203, 21, 50, 83, 44, 20, 10, 199, 16, 18, 212, 100, 194, 83, 44, 20, 9, 198, 64, 19, 12, 4, 66, 69, 20, 10, 199, 88, 82, 140, 20, 228, 197, 72, 20, 10, 199, 16, 148, 208, 20, 228, 197, 72, 20, 17, 4, 95, 52, 88, 15, 81, 116, 112, 6, 47, 114, 82, 13, 50, 13, 0, 0, 9, 198, 77, 66, 76, 37, 49, 82, 20, 9, 198, 72, 85, 149, 72, 65, 82, 20, 9, 198, 72, 81, 210, 20, 65, 82, 20, 11, 200, 12, 128, 82, 13, 85, 5, 72, 144, 20, 12, 201, 28, 83, 143, 64, 192, 68, 20, 194, 71, 20, 11, 200, 88, 82, 140, 20, 228, 201, 76, 176, 20, 11, 200, 88, 20, 132, 20, 228, 201, 76, 176, 20, 11, 200, 64, 19, 133, 29, 148, 137, 76, 176, 20, 11, 200, 8, 84, 135, 20, 228, 201, 76, 176, 20, 7, 196, 28, 17, 193, 80, 20, 9, 4, 4, 195, 169, 20, 70, 36, 0, 0, 13, 138, 19, 11, 18, 15, 6, 21, 12, 195, 184, 19, 20, 19, 70, 8, 83, 9, 104, 148, 203, 69, 36, 55, 37, 12, 87, 37, 87, 79, 0, 66, 9, 198, 76, 21, 1, 56, 148, 203, 20, 9, 198, 32, 80, 146, 4, 148, 203, 20, 9, 198, 16, 83, 9, 72, 148, 203, 20, 9, 198, 8, 83, 9, 104, 148, 203, 20, 11, 136, 12, 5, 21, 11, 195, 166, 13, 9, 20, 0, 27, 70, 24, 244, 147, 100, 225, 84, 81, 6, 112, 34, 87, 114, 50, 13, 70, 15, 105, 110, 34, 0, 81, 104, 97, 114, 32, 9, 198, 16, 148, 16, 20, 69, 84, 20, 20, 4, 95, 3, 9, 18, 87, 6, 106, 12, 49, 112, 63, 81, 55, 4, 107, 49, 87, 0, 0, 12, 201, 72, 81, 201, 60, 224, 76, 37, 49, 82, 20, 12, 201, 44, 20, 129, 52, 83, 12, 37, 49, 82, 20, 12, 201, 16, 83, 79, 45, 32, 84, 37, 49, 82, 20, 14, 203, 52, 19, 137, 65, 83, 1, 80, 244, 137, 76, 176, 20, 10, 199, 80, 84, 146, 5, 34, 85, 52, 20, 10, 199, 44, 243, 12, 20, 114, 85, 52, 20, 10, 199, 64, 83, 147, 36, 243, 129, 80, 20, 10, 199, 16, 84, 212, 36, 195, 1, 80, 20, 6, 195, 45, 83, 128, 72, 0, 7, 196, 80, 18, 211, 36, 20, 9, 198, 36, 226, 204, 84, 65, 82, 20, 12, 201, 81, 83, 85, 49, 69, 65, 72, 148, 203, 20, 12, 201, 77, 80, 138, 20, 181, 9, 88, 148, 203, 20, 12, 201, 72, 80, 201, 80, 21, 9, 88, 148, 203, 20, 7, 196, 48, 147, 73, 80, 20, 7, 196, 80, 19, 73, 48, 20, 0, 0, 9, 198, 4, 225, 204, 37, 53, 0, 20, 13, 202, 16, 148, 12, 60, 208, 84, 5, 34, 85, 52, 20, 0, 10, 199, 24, 245, 15, 80, 18, 211, 36, 20, 10, 199, 76, 130, 66, 8, 243, 5, 80, 20, 12, 201, 65, 35, 204, 21, 64, 82, 37, 49, 82, 20, 12, 201, 45, 38, 68, 77, 33, 86, 36, 65, 82, 20, 10, 199, 56, 20, 212, 85, 37, 9, 20, 20, 10, 199, 29, 147, 78, 5, 50, 85, 52, 20, 10, 199, 72, 246, 65, 48, 148, 205, 20, 20, 10, 199, 61, 5, 9, 52, 148, 205, 20, 20, 10, 199, 24, 21, 1, 48, 148, 205, 20, 20, 10, 199, 4, 224, 82, 44, 148, 205, 20, 20, 14, 203, 72, 82, 207, 57, 96, 76, 21, 48, 197, 57, 48, 20, 10, 199, 61, 34, 197, 77, 68, 129, 48, 20, 0, 6, 195, 44, 101, 77, 17, 7, 196, 24, 16, 207, 56, 20, 7, 196, 81, 145, 143, 56, 20, 12, 201, 64, 21, 18, 84, 194, 133, 72, 147, 135, 20, 12, 201, 52, 83, 147, 40, 85, 137, 44, 148, 203, 20, 12, 201, 48, 243, 135, 60, 32, 82, 16, 148, 203, 20, 7, 196, 13, 80, 129, 56, 20, 0, 8, 197, 76, 18, 210, 4, 192, 20, 0, 7, 195, 44, 101, 75, 17, 42, 9, 198, 64, 244, 201, 81, 84, 128, 20, 9, 198, 5, 35, 65, 81, 84, 128, 20, 9, 198, 72, 85, 137, 76, 244, 128, 20, 9, 198, 21, 50, 193, 48, 84, 128, 20, 9, 198, 17, 84, 16, 20, 66, 84, 20, 13, 202, 77, 2, 82, 37, 69, 65, 48, 148, 205, 20, 20, 13, 202, 76, 243, 78, 4, 208, 149, 48, 148, 205, 20, 20, 13, 202, 44, 243, 147, 21, 37, 129, 80, 148, 205, 20, 20, 13, 202, 16, 80, 197, 57, 68, 129, 48, 148, 205, 20, 20, 9, 198, 21, 98, 68, 20, 229, 0, 20, 9, 198, 4, 208, 82, 4, 229, 0, 20, 0, 9, 198, 53, 149, 15, 48, 241, 201, 20, 10, 199, 36, 229, 133, 73, 50, 79, 56, 20, 10, 199, 72, 149, 129, 48, 148, 197, 72, 20, 10, 199, 72, 84, 212, 5, 84, 133, 72, 20, 10, 199, 61, 33, 193, 56, 148, 197, 72, 20, 10, 199, 52, 240, 137, 48, 148, 197, 72, 20, 10, 199, 44, 19, 143, 56, 148, 197, 72, 20, 10, 199, 36, 211, 85, 56, 148, 197, 72, 20, 10, 199, 24, 21, 143, 72, 148, 197, 72, 20, 10, 199, 52, 17, 217, 5, 34, 83, 44, 20, 10, 199, 45, 85, 193, 37, 66, 83, 44, 20, 10, 199, 21, 33, 77, 37, 66, 83, 44, 20, 10, 199, 8, 19, 19, 4, 210, 83, 44, 20, 10, 199, 5, 53, 13, 5, 66, 83, 44, 20, 10, 199, 81, 34, 86, 4, 193, 78, 80, 20, 10, 199, 65, 35, 205, 36, 225, 78, 80, 20, 13, 138, 16, 18, 195, 166, 10, 21, 4, 9, 3, 5, 20, 0, 11, 200, 76, 84, 1, 72, 21, 9, 60, 224, 20, 11, 200, 60, 35, 9, 28, 21, 9, 60, 224, 20, 11, 200, 44, 243, 150, 84, 196, 201, 60, 224, 20, 11, 200, 44, 243, 147, 84, 213, 9, 60, 224, 20, 11, 200, 44, 243, 142, 20, 180, 201, 60, 224, 20, 11, 200, 44, 243, 12, 20, 181, 9, 60, 224, 20, 11, 200, 24, 145, 213, 72, 21, 9, 60, 224, 20, 7, 196, 85, 32, 129, 56, 21, 0, 8, 197, 76, 84, 150, 36, 192, 20, 8, 197, 24, 80, 146, 36, 192, 20, 12, 201, 5, 66, 5, 56, 145, 78, 76, 84, 128, 20, 10, 69, 61, 33, 71, 60, 224, 21, 0, 10, 0, 9, 198, 80, 82, 211, 81, 84, 128, 20, 9, 198, 76, 82, 211, 81, 84, 128, 20, 9, 198, 65, 83, 139, 81, 84, 128, 20, 9, 198, 52, 146, 211, 81, 84, 128, 20, 9, 198, 41, 83, 139, 81, 84, 128, 20, 12, 201, 21, 2, 68, 20, 210, 79, 48, 241, 201, 20, 21, 146, 18, 5, 16, 18, 195, 166, 19, 5, 14, 20, 1, 20, 9, 22, 9, 20, 5, 20, 20, 13, 202, 80, 82, 206, 60, 180, 129, 80, 148, 197, 72, 20, 13, 202, 52, 84, 139, 4, 229, 9, 48, 148, 197, 72, 20, 13, 202, 77, 84, 5, 72, 192, 84, 37, 98, 83, 44, 20, 13, 202, 65, 35, 199, 72, 19, 77, 5, 66, 83, 44, 20, 13, 202, 5, 4, 5, 48, 192, 84, 37, 98, 83, 44, 20, 9, 198, 61, 5, 76, 20, 229, 0, 20, 9, 198, 24, 19, 12, 20, 229, 0, 20, 9, 198, 17, 32, 66, 4, 229, 0, 20, 11, 70, 92, 20, 146, 36, 244, 128, 21, 0, 10, 0, 14, 203, 44, 192, 83, 76, 145, 137, 44, 21, 9, 60, 224, 20, 10, 199, 72, 81, 201, 77, 68, 133, 72, 20, 10, 199, 61, 34, 197, 77, 68, 133, 72, 20, 10, 199, 44, 243, 80, 20, 228, 197, 72, 20, 10, 199, 36, 225, 137, 49, 68, 133, 72, 20, 10, 199, 36, 195, 21, 77, 68, 133, 72, 20, 10, 199, 45, 148, 137, 48, 194, 83, 44, 20, 10, 199, 37, 50, 201, 4, 66, 83, 44, 20, 10, 199, 77, 65, 71, 20, 228, 197, 72, 20, 10, 199, 45, 33, 84, 20, 228, 197, 72, 20, 14, 4, 95, 19, 20, 11, 87, 47, 34, 6, 39, 40, 49, 0, 0, 31, 76, 44, 243, 134, 37, 35, 65, 56, 65, 82, 56, 84, 192, 49, 112, 50, 81, 36, 34, 63, 6, 108, 50, 70, 106, 20, 50, 13, 87, 0, 11, 200, 77, 64, 71, 56, 21, 9, 60, 224, 20, 11, 200, 61, 33, 9, 56, 21, 9, 60, 224, 20, 11, 200, 36, 243, 137, 76, 21, 9, 60, 224, 20, 11, 200, 16, 148, 211, 20, 181, 9, 60, 224, 20, 12, 4, 95, 3, 18, 12, 49, 6, 106, 12, 55, 0, 0, 8, 197, 76, 241, 137, 77, 64, 20, 16, 141, 16, 18, 195, 166, 19, 9, 4, 5, 14, 20, 9, 5, 12, 20, 8, 197, 81, 32, 67, 21, 32, 20, 8, 197, 85, 33, 71, 21, 32, 20, 16, 205, 36, 229, 5, 72, 224, 84, 36, 243, 129, 48, 148, 197, 72, 20, 9, 198, 88, 148, 149, 48, 83, 147, 20, 8, 197, 88, 19, 21, 5, 32, 20, 14, 4, 95, 1, 3, 21, 35, 49, 57, 6, 40, 12, 47, 0, 0, 9, 198, 76, 147, 143, 48, 241, 192, 20, 9, 198, 53, 149, 15, 48, 241, 192, 20, 9, 198, 81, 33, 69, 56, 145, 192, 20, 9, 198, 44, 19, 148, 60, 224, 76, 20, 9, 198, 33, 148, 212, 4, 65, 64, 20, 0, 10, 199, 80, 19, 13, 84, 66, 83, 80, 20, 10, 199, 77, 64, 76, 36, 226, 83, 80, 20, 14, 203, 81, 32, 78, 76, 99, 210, 52, 21, 9, 60, 224, 20, 14, 203, 77, 68, 129, 80, 145, 137, 44, 21, 9, 60, 224, 20, 10, 199, 44, 192, 82, 21, 34, 78, 28, 20, 10, 199, 24, 20, 147, 21, 34, 78, 28, 20, 0, 11, 200, 80, 83, 5, 24, 243, 137, 77, 64, 20, 7, 196, 80, 82, 83, 80, 20, 11, 200, 64, 20, 131, 20, 195, 9, 77, 64, 20, 11, 200, 48, 144, 146, 21, 69, 9, 77, 64, 20, 11, 200, 44, 244, 142, 21, 69, 9, 77, 64, 20, 11, 200, 4, 229, 1, 28, 243, 137, 77, 64, 20, 11, 200, 89, 83, 11, 4, 226, 83, 21, 32, 20, 11, 200, 77, 84, 5, 73, 98, 83, 21, 32, 20, 11, 200, 76, 177, 77, 5, 66, 83, 21, 32, 20, 11, 200, 52, 241, 5, 72, 226, 83, 21, 32, 20, 11, 200, 52, 84, 131, 21, 34, 83, 21, 32, 20, 11, 200, 44, 194, 77, 5, 66, 83, 21, 32, 20, 11, 200, 32, 148, 212, 61, 34, 83, 21, 32, 20, 11, 200, 28, 129, 84, 80, 242, 83, 21, 32, 20, 11, 200, 24, 147, 13, 5, 66, 83, 21, 32, 20, 11, 200, 17, 32, 77, 5, 66, 83, 21, 32, 20, 11, 200, 16, 241, 205, 5, 66, 83, 21, 32, 20, 11, 200, 16, 83, 196, 61, 34, 83, 21, 32, 20, 11, 200, 5, 35, 205, 5, 66, 83, 21, 32, 20, 11, 200, 80, 83, 210, 21, 66, 75, 21, 32, 20, 11, 200, 16, 144, 66, 21, 66, 75, 21, 32, 20, 11, 200, 44, 243, 139, 85, 36, 133, 57, 64, 20, 0, 8, 197, 20, 115, 201, 77, 64, 20, 8, 197, 12, 21, 83, 21, 32, 20, 13, 138, 19, 195, 166, 4, 22, 1, 14, 12, 9, 7, 20, 12, 201, 56, 244, 132, 88, 84, 212, 48, 145, 192, 20, 13, 138, 13, 5, 4, 7, 195, 184, 18, 12, 9, 7, 20, 9, 198, 52, 19, 1, 40, 148, 203, 20, 9, 198, 44, 131, 69, 72, 148, 203, 20, 9, 198, 21, 81, 143, 72, 148, 203, 20, 12, 201, 45, 33, 79, 48, 84, 137, 56, 65, 64, 20, 8, 197, 52, 19, 132, 5, 64, 20, 8, 197, 4, 181, 21, 5, 32, 20, 0, 9, 198, 29, 148, 143, 76, 179, 208, 20, 9, 198, 24, 20, 203, 36, 225, 64, 20, 13, 202, 65, 35, 212, 20, 181, 9, 60, 226, 83, 80, 20, 13, 202, 64, 84, 134, 20, 181, 9, 60, 226, 83, 80, 20, 13, 202, 16, 242, 213, 52, 83, 148, 4, 194, 83, 80, 20, 13, 202, 81, 32, 78, 77, 3, 206, 21, 34, 78, 28, 20, 13, 202, 77, 1, 67, 36, 98, 67, 21, 34, 78, 28, 20, 13, 202, 73, 84, 211, 36, 98, 67, 21, 34, 78, 28, 20, 13, 202, 64, 244, 201, 80, 147, 206, 21, 34, 78, 28, 20, 13, 202, 44, 192, 82, 36, 98, 67, 21, 34, 78, 28, 20, 13, 202, 28, 195, 210, 36, 98, 67, 21, 34, 78, 28, 20, 13, 202, 24, 19, 19, 36, 98, 67, 21, 34, 78, 28, 20, 13, 202, 16, 84, 201, 56, 98, 67, 21, 34, 78, 28, 20, 13, 202, 16, 83, 79, 57, 53, 18, 21, 34, 78, 28, 20, 13, 202, 4, 96, 129, 48, 19, 131, 21, 34, 78, 28, 20, 14, 139, 195, 184, 13, 6, 9, 14, 4, 20, 12, 9, 7, 20, 9, 198, 88, 83, 137, 56, 65, 64, 20, 9, 198, 16, 84, 137, 56, 65, 64, 20, 9, 198, 88, 148, 149, 48, 83, 148, 20, 9, 198, 80, 84, 141, 36, 224, 76, 20, 9, 198, 21, 53, 18, 4, 65, 64, 20, 9, 198, 9, 32, 86, 4, 65, 64, 20, 0, 10, 199, 4, 69, 133, 57, 66, 83, 80, 20, 14, 203, 81, 32, 78, 76, 148, 212, 61, 34, 83, 21, 32, 20, 10, 199, 16, 82, 193, 56, 84, 211, 20, 20, 14, 203, 72, 82, 207, 57, 96, 76, 21, 48, 197, 57, 64, 20, 9, 198, 64, 192, 78, 80, 17, 197, 20, 0, 18, 70, 48, 81, 197, 56, 65, 78, 55, 36, 79, 6, 107, 50, 70, 13, 50, 0, 10, 68, 76, 145, 197, 72, 87, 37, 34, 0, 11, 200, 21, 96, 80, 61, 32, 84, 61, 32, 20, 11, 200, 5, 4, 12, 36, 176, 84, 61, 32, 20, 11, 200, 77, 3, 206, 80, 19, 137, 77, 64, 20, 11, 200, 44, 19, 131, 20, 195, 9, 77, 64, 20, 11, 200, 33, 148, 15, 77, 64, 83, 21, 32, 20, 12, 137, 1, 6, 13, 195, 166, 7, 20, 9, 7, 20, 12, 201, 32, 145, 82, 60, 115, 25, 24, 148, 203, 20, 11, 200, 77, 147, 70, 60, 226, 75, 21, 32, 20, 11, 200, 20, 193, 75, 81, 34, 75, 21, 32, 20, 11, 200, 4, 224, 76, 101, 66, 75, 21, 32, 20, 11, 200, 4, 195, 5, 72, 114, 75, 21, 32, 20, 11, 200, 4, 176, 68, 20, 210, 75, 21, 32, 20, 7, 196, 88, 81, 193, 56, 20, 11, 200, 44, 243, 148, 72, 18, 5, 57, 64, 20, 11, 200, 32, 20, 193, 72, 65, 82, 21, 64, 20, 11, 200, 16, 84, 18, 36, 209, 82, 21, 64, 20, 0, 12, 201, 88, 145, 21, 56, 65, 82, 48, 145, 192, 20, 12, 201, 88, 81, 5, 72, 129, 70, 80, 145, 192, 20, 13, 138, 20, 9, 12, 2, 195, 184, 18, 12, 9, 7, 20, 12, 201, 77, 2, 68, 76, 98, 78, 16, 145, 192, 20, 13, 138, 15, 22, 5, 18, 4, 195, 165, 4, 9, 7, 20, 13, 138, 12, 195, 184, 7, 14, 1, 7, 20, 9, 7, 20, 13, 138, 6, 195, 184, 12, 7, 1, 7, 20, 9, 7, 20, 12, 201, 24, 244, 149, 56, 65, 82, 48, 145, 192, 20, 12, 201, 24, 244, 129, 56, 65, 82, 48, 145, 192, 20, 9, 198, 24, 147, 149, 72, 194, 71, 20, 13, 138, 5, 14, 4, 18, 195, 166, 7, 20, 9, 7, 20, 9, 198, 4, 101, 5, 56, 194, 71, 20, 8, 197, 81, 32, 71, 36, 176, 20, 8, 197, 8, 147, 206, 36, 176, 20, 8, 197, 16, 144, 68, 20, 208, 20, 13, 138, 12, 195, 184, 7, 14, 1, 7, 20, 9, 7, 20, 13, 138, 6, 195, 184, 12, 7, 1, 7, 20, 9, 7, 20, 12, 201, 32, 20, 140, 20, 178, 78, 4, 65, 64, 20, 10, 69, 72, 240, 68, 36, 80, 21, 0, 10, 0, 9, 198, 81, 32, 80, 64, 148, 212, 20, 13, 202, 64, 20, 148, 36, 181, 76, 5, 34, 83, 80, 20, 14, 139, 19, 5, 14, 4, 18, 195, 166, 7, 20, 9, 7, 20, 14, 139, 19, 1, 13, 4, 18, 195, 166, 7, 20, 9, 7, 20, 9, 198, 77, 65, 82, 60, 145, 0, 20, 12, 137, 16, 18, 195, 166, 12, 21, 4, 9, 5, 20, 9, 198, 52, 81, 193, 48, 149, 0, 20, 9, 198, 80, 84, 141, 36, 226, 64, 20, 9, 198, 28, 198, 80, 80, 146, 192, 20, 9, 198, 8, 245, 1, 56, 146, 192, 20, 9, 198, 64, 146, 197, 72, 85, 0, 20, 9, 198, 81, 32, 75, 80, 21, 0, 20, 9, 198, 72, 83, 211, 80, 21, 0, 20, 9, 198, 29, 32, 78, 84, 192, 84, 20, 9, 198, 5, 85, 15, 52, 21, 0, 20, 0, 9, 198, 81, 148, 15, 48, 241, 201, 20, 9, 198, 76, 84, 143, 48, 241, 201, 20, 9, 198, 4, 229, 15, 48, 241, 201, 20, 10, 199, 52, 82, 193, 56, 148, 197, 72, 20, 10, 199, 45, 85, 20, 21, 36, 137, 28, 20, 15, 204, 16, 148, 203, 72, 147, 73, 56, 21, 15, 72, 148, 203, 20, 10, 199, 57, 147, 70, 60, 208, 78, 36, 20, 10, 199, 32, 85, 82, 37, 53, 9, 44, 20, 12, 201, 81, 32, 78, 77, 97, 82, 76, 19, 0, 20, 11, 4, 95, 18, 14, 7, 34, 37, 50, 79, 0, 0, 11, 200, 4, 195, 5, 72, 115, 204, 60, 112, 20, 9, 198, 76, 179, 210, 64, 147, 206, 20, 11, 200, 64, 193, 84, 80, 84, 137, 56, 112, 20, 11, 200, 64, 17, 201, 56, 84, 137, 56, 112, 20, 11, 200, 60, 33, 21, 12, 84, 137, 56, 112, 20, 11, 200, 56, 21, 137, 28, 84, 137, 56, 112, 20, 11, 200, 45, 82, 143, 56, 84, 137, 56, 112, 20, 11, 200, 44, 20, 21, 56, 84, 137, 56, 112, 20, 11, 200, 36, 229, 15, 56, 84, 137, 56, 112, 20, 11, 200, 36, 225, 9, 44, 84, 137, 56, 112, 20, 11, 200, 36, 225, 9, 12, 84, 137, 56, 112, 20, 11, 200, 29, 34, 76, 48, 84, 137, 56, 112, 20, 11, 200, 28, 195, 211, 76, 84, 137, 56, 112, 20, 11, 200, 24, 192, 77, 8, 84, 137, 56, 112, 20, 11, 200, 16, 148, 137, 28, 84, 137, 56, 112, 20, 11, 200, 16, 85, 15, 56, 84, 137, 56, 112, 20, 11, 200, 16, 84, 15, 56, 84, 137, 56, 112, 20, 11, 200, 16, 82, 207, 72, 84, 137, 56, 112, 20, 11, 200, 4, 195, 15, 44, 84, 137, 56, 112, 20, 11, 200, 4, 33, 9, 12, 84, 137, 56, 112, 20, 12, 201, 88, 147, 132, 76, 178, 66, 20, 194, 71, 20, 11, 200, 80, 147, 7, 37, 97, 76, 36, 112, 20, 11, 200, 61, 1, 129, 81, 65, 76, 36, 112, 20, 11, 200, 61, 1, 18, 37, 97, 76, 36, 112, 20, 11, 200, 60, 208, 153, 81, 65, 76, 36, 112, 20, 16, 141, 14, 5, 4, 5, 18, 4, 18, 195, 166, 7, 20, 9, 7, 20, 16, 141, 7, 5, 14, 14, 5, 13, 6, 195, 184, 18, 12, 9, 7, 20, 12, 201, 24, 244, 141, 60, 65, 78, 80, 194, 71, 20, 9, 198, 44, 20, 18, 36, 243, 0, 20, 11, 200, 52, 19, 1, 8, 20, 137, 76, 176, 20, 7, 196, 60, 224, 78, 36, 20, 11, 200, 88, 84, 212, 4, 194, 78, 16, 80, 20, 11, 200, 16, 145, 212, 21, 34, 78, 16, 80, 20, 11, 200, 16, 148, 133, 45, 68, 137, 12, 80, 20, 0, 12, 201, 32, 83, 12, 20, 32, 82, 16, 148, 212, 20, 8, 197, 76, 20, 139, 60, 208, 20, 8, 197, 60, 194, 69, 72, 80, 20, 9, 198, 4, 68, 212, 4, 66, 71, 20, 12, 201, 45, 38, 83, 80, 19, 12, 60, 145, 0, 20, 8, 197, 4, 194, 217, 52, 144, 20, 12, 201, 28, 145, 193, 57, 67, 205, 4, 226, 64, 20, 12, 201, 64, 84, 137, 77, 64, 76, 80, 146, 192, 20, 12, 201, 16, 148, 212, 72, 18, 5, 72, 85, 0, 20, 0, 9, 198, 72, 145, 207, 72, 148, 212, 20, 9, 198, 32, 147, 132, 84, 148, 212, 20, 9, 198, 16, 148, 137, 28, 148, 212, 20, 9, 198, 21, 65, 82, 56, 149, 0, 20, 9, 198, 9, 35, 206, 44, 149, 0, 20, 9, 198, 52, 82, 193, 56, 146, 192, 20, 9, 198, 76, 178, 86, 28, 21, 0, 20, 9, 198, 64, 244, 212, 84, 192, 84, 20, 9, 198, 45, 96, 68, 72, 21, 0, 20, 9, 198, 44, 20, 130, 60, 224, 84, 20, 0, 14, 203, 77, 80, 138, 20, 181, 9, 88, 84, 137, 56, 112, 20, 14, 203, 76, 243, 9, 16, 20, 137, 76, 84, 137, 56, 112, 20, 14, 203, 76, 82, 213, 48, 20, 137, 76, 84, 137, 56, 112, 20, 14, 203, 72, 146, 207, 12, 129, 84, 80, 84, 137, 56, 112, 20, 14, 203, 72, 82, 207, 28, 227, 211, 12, 84, 137, 56, 112, 20, 14, 203, 65, 35, 212, 60, 179, 204, 48, 84, 137, 56, 112, 20, 14, 203, 64, 243, 25, 52, 84, 137, 76, 84, 137, 56, 112, 20, 14, 203, 64, 192, 83, 80, 145, 137, 12, 84, 137, 56, 112, 20, 14, 203, 45, 96, 78, 80, 145, 137, 12, 84, 137, 56, 112, 20, 14, 203, 44, 243, 139, 72, 85, 9, 76, 84, 137, 56, 112, 20, 14, 203, 44, 243, 12, 5, 66, 79, 56, 84, 137, 56, 112, 20, 14, 203, 44, 21, 5, 28, 244, 137, 76, 84, 137, 56, 112, 20, 14, 203, 36, 229, 5, 73, 1, 76, 48, 84, 137, 56, 112, 20, 14, 203, 36, 65, 78, 80, 145, 137, 12, 84, 137, 56, 112, 20, 14, 203, 32, 145, 82, 5, 34, 201, 76, 84, 137, 56, 112, 20, 14, 203, 29, 82, 76, 48, 245, 9, 56, 84, 137, 56, 112, 20, 14, 203, 16, 148, 195, 37, 3, 9, 56, 84, 137, 56, 112, 20, 14, 203, 12, 83, 148, 72, 145, 149, 28, 84, 137, 56, 112, 20, 10, 199, 64, 84, 148, 85, 32, 133, 72, 20, 14, 203, 36, 225, 140, 4, 211, 65, 80, 244, 137, 76, 176, 20, 14, 203, 5, 37, 9, 45, 83, 1, 80, 244, 137, 76, 176, 20, 9, 198, 28, 84, 149, 56, 66, 69, 20, 9, 198, 4, 197, 77, 36, 226, 69, 20, 9, 198, 4, 69, 133, 72, 34, 69, 20, 10, 199, 53, 82, 1, 52, 81, 1, 56, 20, 0, 23, 72, 88, 194, 69, 76, 83, 9, 56, 80, 81, 55, 37, 87, 13, 55, 6, 37, 12, 50, 13, 0, 20, 9, 198, 77, 66, 80, 84, 193, 82, 20, 9, 198, 64, 244, 212, 84, 193, 82, 20, 9, 198, 44, 243, 12, 36, 65, 82, 20, 9, 198, 36, 229, 5, 56, 65, 82, 20, 9, 198, 20, 194, 77, 36, 225, 82, 20, 9, 198, 4, 36, 207, 72, 33, 82, 20, 12, 201, 44, 243, 148, 36, 229, 69, 72, 194, 71, 20, 12, 201, 36, 225, 19, 80, 147, 12, 20, 194, 71, 20, 11, 200, 28, 83, 147, 81, 34, 68, 36, 112, 20, 11, 200, 24, 244, 129, 29, 65, 76, 36, 112, 20, 11, 200, 17, 83, 68, 72, 148, 212, 36, 112, 20, 11, 200, 5, 4, 5, 80, 149, 12, 36, 112, 20, 11, 200, 56, 84, 1, 48, 84, 201, 76, 176, 20, 12, 137, 195, 184, 11, 21, 13, 5, 14, 9, 11, 20, 19, 70, 48, 19, 147, 20, 225, 82, 55, 108, 50, 87, 13, 50, 6, 36, 34, 0, 20, 0, 12, 201, 72, 80, 197, 65, 66, 79, 56, 148, 212, 20, 12, 201, 44, 192, 82, 36, 225, 84, 80, 148, 212, 20, 9, 198, 32, 147, 132, 84, 148, 203, 20, 12, 201, 20, 208, 78, 12, 148, 5, 72, 85, 0, 20, 0, 9, 198, 5, 69, 18, 36, 37, 84, 20, 9, 198, 88, 148, 135, 36, 224, 76, 20, 9, 198, 44, 19, 142, 36, 32, 76, 20, 0, 10, 199, 24, 243, 9, 21, 34, 78, 28, 20, 10, 199, 17, 32, 80, 21, 34, 78, 28, 20, 10, 199, 32, 244, 148, 20, 228, 201, 20, 20, 14, 203, 24, 244, 147, 80, 19, 132, 21, 34, 78, 16, 80, 20, 0, 17, 70, 48, 81, 197, 56, 65, 82, 55, 36, 79, 6, 107, 50, 70, 112, 0, 9, 198, 88, 16, 195, 36, 225, 82, 20, 9, 198, 81, 32, 78, 12, 129, 82, 20, 9, 198, 65, 35, 208, 60, 225, 82, 20, 9, 198, 65, 35, 205, 20, 225, 82, 20, 9, 198, 44, 243, 80, 36, 193, 82, 20, 9, 198, 29, 32, 78, 84, 193, 82, 20, 9, 198, 24, 20, 195, 36, 225, 82, 20, 9, 198, 4, 68, 207, 72, 33, 82, 20, 12, 201, 88, 145, 84, 56, 19, 69, 76, 148, 203, 20, 12, 201, 64, 84, 137, 77, 64, 76, 80, 148, 203, 20, 7, 196, 76, 83, 73, 80, 20, 10, 135, 12, 195, 166, 11, 1, 7, 5, 20, 0, 16, 141, 16, 18, 195, 166, 6, 5, 18, 5, 14, 20, 9, 5, 12, 20, 9, 198, 4, 196, 193, 12, 148, 203, 20, 0, 11, 5, 15, 7, 19, 195, 165, 112, 87, 13, 0, 9, 198, 76, 19, 13, 37, 53, 0, 20, 9, 198, 20, 194, 84, 37, 53, 0, 20, 13, 202, 65, 35, 199, 72, 19, 77, 21, 34, 78, 28, 20, 0, 10, 199, 16, 80, 197, 56, 226, 85, 52, 20, 10, 199, 77, 64, 76, 4, 115, 73, 80, 20, 10, 199, 61, 33, 193, 56, 148, 205, 20, 20, 10, 199, 52, 82, 193, 56, 148, 205, 20, 20, 10, 199, 48, 18, 207, 56, 148, 205, 20, 20, 10, 199, 24, 83, 73, 56, 148, 205, 20, 20, 10, 199, 4, 196, 9, 56, 148, 205, 20, 20, 10, 199, 16, 148, 208, 20, 228, 193, 80, 20, 10, 199, 52, 17, 201, 77, 68, 129, 48, 20, 0, 13, 68, 56, 241, 197, 56, 50, 6, 39, 12, 14, 50, 0, 9, 198, 36, 195, 21, 76, 147, 206, 20, 9, 198, 4, 195, 21, 76, 147, 206, 20, 7, 196, 72, 81, 197, 72, 20, 7, 196, 48, 81, 197, 72, 20, 12, 201, 76, 83, 133, 28, 19, 5, 76, 148, 203, 20, 12, 201, 20, 180, 197, 53, 3, 1, 72, 148, 203, 20, 12, 201, 4, 69, 143, 44, 21, 15, 72, 148, 203, 20, 9, 198, 64, 20, 129, 29, 32, 70, 20, 7, 196, 88, 81, 193, 72, 20, 0, 16, 69, 24, 192, 75, 60, 224, 81, 55, 108, 49, 6, 112, 66, 0, 20, 16, 205, 20, 226, 5, 17, 50, 207, 52, 208, 84, 21, 34, 78, 28, 20, 12, 137, 18, 195, 184, 4, 2, 25, 14, 9, 20, 20, 8, 197, 80, 19, 142, 36, 224, 20, 8, 197, 52, 244, 134, 36, 224, 20, 8, 197, 4, 211, 210, 36, 224, 20, 8, 197, 29, 32, 67, 36, 192, 20, 8, 197, 25, 32, 71, 36, 192, 20, 8, 197, 81, 35, 202, 4, 224, 20, 8, 197, 72, 16, 130, 36, 224, 20, 0, 13, 202, 80, 245, 1, 48, 149, 1, 72, 148, 205, 20, 20, 13, 202, 44, 243, 147, 60, 224, 78, 80, 148, 205, 20, 20, 13, 202, 44, 243, 134, 84, 50, 65, 56, 148, 205, 20, 20, 13, 202, 16, 147, 5, 81, 64, 78, 80, 148, 205, 20, 20, 13, 202, 5, 96, 78, 80, 112, 82, 16, 148, 205, 20, 20, 0, 21, 71, 5, 80, 133, 72, 114, 78, 20, 39, 69, 36, 34, 89, 6, 37, 12, 50, 13, 0, 20, 10, 199, 64, 84, 141, 37, 69, 5, 72, 20, 10, 199, 44, 243, 16, 61, 37, 5, 72, 20, 9, 198, 17, 80, 200, 21, 52, 197, 20, 0, 13, 68, 4, 193, 78, 20, 108, 55, 6, 36, 50, 13, 0, 11, 200, 4, 36, 207, 73, 5, 9, 60, 224, 20, 9, 198, 81, 148, 15, 29, 32, 70, 20, 9, 198, 8, 20, 143, 29, 32, 70, 20, 7, 196, 60, 49, 65, 56, 21, 11, 136, 6, 195, 184, 4, 5, 18, 1, 12, 20, 0, 8, 197, 52, 148, 211, 36, 192, 20, 0, 9, 198, 45, 38, 83, 60, 194, 84, 20, 0, 12, 201, 77, 80, 147, 45, 34, 80, 80, 147, 206, 20, 10, 199, 72, 82, 133, 45, 66, 79, 56, 20, 12, 201, 65, 35, 211, 45, 34, 80, 80, 147, 206, 20, 10, 199, 36, 229, 133, 57, 66, 79, 56, 20, 10, 199, 16, 145, 197, 77, 66, 79, 56, 20, 10, 199, 16, 85, 137, 5, 66, 79, 56, 20, 10, 199, 88, 147, 132, 36, 176, 78, 80, 20, 0, 11, 200, 8, 144, 140, 36, 244, 203, 61, 0, 20, 9, 198, 5, 52, 197, 77, 51, 210, 20, 11, 200, 44, 244, 146, 85, 5, 9, 60, 224, 20, 11, 200, 16, 148, 208, 21, 36, 201, 60, 224, 20, 11, 200, 4, 229, 9, 24, 80, 146, 36, 224, 20, 0, 8, 197, 72, 82, 212, 61, 32, 20, 8, 197, 24, 18, 212, 61, 32, 20, 8, 197, 80, 18, 211, 21, 32, 20, 8, 197, 48, 18, 211, 21, 32, 20, 0, 13, 202, 52, 19, 137, 24, 84, 212, 5, 66, 79, 56, 20, 9, 198, 64, 192, 78, 21, 33, 64, 20, 9, 198, 48, 147, 138, 21, 33, 64, 20, 9, 198, 28, 20, 142, 21, 33, 64, 20, 9, 198, 8, 20, 130, 21, 33, 64, 20, 18, 4, 95, 1, 3, 50, 70, 112, 13, 55, 35, 49, 57, 6, 40, 12, 47, 0, 0, 10, 199, 52, 244, 134, 36, 226, 83, 80, 20, 10, 199, 80, 16, 149, 21, 34, 78, 28, 20, 6, 195, 61, 96, 76, 20, 9, 198, 48, 147, 79, 56, 17, 5, 20, 0, 11, 200, 36, 226, 214, 37, 50, 84, 61, 32, 20, 11, 200, 52, 85, 1, 48, 194, 83, 21, 32, 20, 11, 200, 52, 20, 203, 36, 226, 83, 21, 32, 20, 11, 200, 32, 20, 141, 60, 226, 83, 21, 32, 20, 11, 200, 24, 197, 79, 72, 84, 195, 21, 32, 20, 11, 200, 8, 19, 11, 4, 226, 83, 21, 32, 20, 9, 198, 48, 144, 133, 73, 66, 78, 20, 0, 8, 197, 45, 35, 203, 21, 32, 20, 8, 197, 28, 192, 83, 21, 32, 20, 8, 197, 16, 244, 211, 21, 32, 20, 12, 201, 16, 149, 137, 76, 147, 206, 21, 33, 64, 20, 12, 201, 61, 97, 82, 76, 145, 212, 48, 145, 192, 20, 8, 197, 36, 228, 85, 37, 64, 20, 12, 201, 64, 21, 18, 36, 245, 9, 76, 209, 64, 20, 9, 198, 16, 145, 1, 45, 66, 75, 20, 0, 9, 198, 48, 82, 212, 85, 33, 64, 20, 9, 198, 80, 18, 212, 21, 33, 64, 20, 9, 198, 77, 3, 204, 21, 33, 64, 20, 9, 198, 76, 243, 132, 21, 33, 64, 20, 9, 198, 45, 99, 212, 21, 33, 64, 20, 9, 198, 28, 20, 132, 21, 33, 64, 20, 9, 198, 8, 20, 132, 21, 33, 64, 20, 9, 198, 44, 193, 82, 36, 176, 76, 20, 0, 10, 199, 64, 241, 1, 29, 34, 83, 80, 20, 10, 199, 52, 243, 143, 80, 82, 83, 80, 20, 10, 199, 45, 83, 20, 85, 34, 83, 80, 20, 10, 199, 44, 243, 148, 61, 34, 83, 80, 20, 10, 199, 21, 128, 197, 73, 2, 83, 80, 20, 10, 199, 16, 81, 129, 37, 66, 83, 80, 20, 10, 199, 8, 20, 143, 56, 84, 211, 20, 20, 14, 203, 77, 97, 78, 16, 35, 210, 28, 83, 147, 21, 32, 20, 14, 203, 76, 147, 11, 20, 35, 210, 28, 83, 147, 21, 32, 20, 14, 203, 52, 20, 137, 4, 113, 82, 28, 83, 147, 21, 32, 20, 0, 31, 68, 84, 226, 79, 56, 57, 40, 50, 57, 106, 50, 15, 87, 47, 36, 37, 87, 57, 13, 50, 0, 81, 115, 116, 97, 116, 105, 111, 110, 32, 11, 200, 88, 83, 148, 36, 192, 84, 61, 32, 20, 11, 200, 81, 32, 78, 76, 148, 212, 61, 32, 20, 11, 200, 61, 48, 201, 48, 192, 84, 61, 32, 20, 11, 200, 48, 146, 214, 36, 64, 84, 61, 32, 20, 11, 200, 36, 226, 193, 77, 48, 84, 61, 32, 20, 7, 196, 84, 226, 79, 56, 20, 11, 200, 72, 82, 212, 36, 98, 67, 21, 32, 20, 11, 200, 52, 244, 148, 36, 98, 67, 21, 32, 20, 7, 196, 48, 241, 197, 72, 20, 11, 200, 44, 243, 77, 84, 226, 67, 21, 32, 20, 11, 200, 24, 244, 148, 36, 98, 67, 21, 32, 20, 11, 200, 12, 84, 148, 36, 98, 67, 21, 32, 20, 7, 196, 73, 80, 137, 56, 20, 15, 204, 4, 229, 18, 61, 3, 205, 61, 33, 137, 76, 209, 64, 20, 9, 198, 52, 147, 133, 72, 19, 0, 20, 9, 198, 28, 83, 133, 72, 19, 0, 20, 0, 12, 201, 81, 34, 85, 52, 97, 82, 36, 225, 192, 20, 12, 201, 77, 66, 80, 84, 193, 82, 36, 225, 192, 20, 12, 201, 76, 82, 213, 56, 65, 82, 36, 225, 192, 20, 12, 201, 76, 80, 197, 72, 225, 82, 36, 225, 192, 20, 12, 201, 72, 85, 1, 8, 193, 82, 36, 225, 192, 20, 12, 201, 64, 83, 132, 84, 193, 82, 36, 225, 192, 20, 12, 201, 44, 240, 71, 84, 193, 82, 36, 225, 192, 20, 12, 201, 44, 20, 197, 72, 225, 82, 36, 225, 192, 20, 12, 201, 44, 19, 85, 24, 193, 82, 36, 225, 192, 20, 12, 201, 36, 227, 203, 84, 193, 82, 36, 225, 192, 20, 12, 201, 32, 20, 131, 20, 193, 82, 36, 225, 192, 20, 12, 201, 20, 194, 77, 36, 225, 82, 36, 225, 192, 20, 12, 201, 16, 85, 1, 12, 129, 82, 36, 225, 192, 20, 12, 201, 12, 148, 139, 84, 193, 82, 36, 225, 192, 20, 12, 201, 4, 36, 207, 72, 33, 82, 36, 225, 192, 20, 12, 201, 44, 21, 1, 65, 83, 20, 21, 33, 64, 20, 12, 201, 25, 32, 71, 52, 83, 148, 21, 33, 64, 20, 12, 201, 8, 19, 132, 21, 35, 204, 21, 33, 64, 20, 15, 140, 195, 166, 19, 20, 5, 20, 9, 3, 9, 19, 13, 5, 20, 8, 197, 45, 84, 129, 28, 80, 20, 0, 9, 198, 48, 21, 9, 56, 148, 212, 20, 9, 198, 44, 243, 15, 72, 148, 212, 20, 9, 198, 8, 18, 83, 76, 148, 212, 20, 9, 198, 73, 81, 134, 21, 34, 64, 20, 9, 198, 40, 240, 130, 21, 34, 64, 20, 9, 198, 28, 20, 150, 21, 34, 64, 20, 9, 198, 76, 18, 211, 37, 50, 192, 20, 9, 198, 37, 64, 76, 37, 50, 192, 20, 9, 198, 32, 84, 143, 37, 50, 192, 20, 9, 198, 33, 145, 18, 61, 130, 68, 20, 9, 198, 77, 147, 70, 60, 226, 64, 20, 9, 198, 16, 84, 137, 88, 21, 0, 20, 9, 198, 4, 69, 143, 44, 21, 0, 20, 5, 131, 239, 187, 191, 0, 6, 195, 53, 34, 64, 17, 11, 136, 19, 16, 1, 20, 9, 195, 184, 19, 20, 12, 137, 9, 14, 20, 5, 18, 9, 195, 184, 18, 20, 9, 198, 76, 147, 143, 48, 241, 201, 20, 9, 198, 24, 243, 143, 48, 241, 201, 20, 10, 199, 64, 16, 201, 24, 144, 197, 72, 20, 10, 199, 44, 243, 15, 56, 148, 197, 72, 20, 10, 199, 36, 70, 76, 48, 148, 197, 72, 20, 10, 199, 20, 180, 208, 61, 37, 5, 72, 20, 10, 199, 8, 245, 1, 56, 148, 197, 72, 20, 9, 198, 8, 18, 212, 21, 34, 69, 20, 9, 198, 32, 84, 130, 5, 34, 69, 20, 0, 12, 137, 1, 13, 2, 9, 20, 9, 195, 184, 19, 20, 11, 200, 25, 32, 83, 20, 243, 15, 28, 144, 20, 15, 204, 84, 67, 65, 81, 34, 75, 84, 193, 82, 36, 225, 192, 20, 15, 204, 77, 80, 150, 20, 229, 9, 60, 225, 82, 36, 225, 192, 20, 15, 204, 65, 35, 208, 61, 37, 9, 60, 225, 82, 36, 225, 192, 20, 11, 200, 45, 98, 84, 80, 84, 137, 56, 112, 20, 11, 200, 40, 243, 137, 76, 84, 137, 56, 112, 20, 9, 198, 64, 20, 148, 36, 83, 0, 20, 7, 196, 80, 83, 210, 36, 20, 11, 200, 32, 84, 148, 84, 113, 76, 36, 112, 20, 9, 198, 52, 85, 1, 56, 243, 0, 20, 11, 200, 45, 33, 84, 20, 228, 201, 76, 176, 20, 11, 200, 52, 83, 79, 72, 19, 132, 84, 208, 20, 11, 200, 45, 33, 83, 80, 243, 65, 80, 144, 20, 20, 68, 12, 129, 67, 44, 47, 57, 107, 49, 6, 37, 50, 0, 44, 20, 81, 105, 110, 32, 11, 200, 45, 96, 68, 72, 241, 143, 56, 144, 20, 11, 200, 89, 83, 7, 5, 34, 83, 52, 80, 20, 11, 200, 88, 246, 69, 85, 34, 83, 52, 80, 20, 11, 200, 77, 2, 82, 37, 66, 83, 52, 80, 20, 11, 200, 76, 84, 137, 4, 194, 83, 52, 80, 20, 11, 200, 76, 82, 212, 21, 34, 83, 52, 80, 20, 11, 200, 72, 243, 65, 57, 66, 83, 52, 80, 20, 11, 200, 65, 34, 86, 5, 66, 83, 52, 80, 20, 11, 200, 60, 178, 213, 49, 66, 83, 52, 80, 20, 11, 200, 52, 19, 137, 21, 34, 83, 52, 80, 20, 11, 200, 8, 20, 130, 5, 34, 83, 52, 80, 20, 11, 200, 77, 147, 132, 21, 34, 78, 16, 80, 20, 7, 196, 77, 81, 1, 56, 20, 7, 196, 77, 81, 1, 56, 21, 9, 198, 72, 17, 9, 44, 19, 0, 20, 0, 12, 201, 44, 244, 205, 21, 67, 204, 60, 114, 64, 20, 12, 201, 21, 99, 204, 85, 66, 79, 56, 148, 212, 20, 8, 197, 4, 180, 201, 60, 208, 20, 14, 139, 4, 5, 6, 195, 166, 11, 1, 20, 9, 15, 14, 20, 9, 198, 16, 83, 1, 29, 66, 71, 20, 12, 201, 77, 147, 80, 5, 65, 84, 37, 50, 192, 20, 12, 201, 65, 35, 212, 61, 70, 80, 37, 50, 192, 20, 12, 201, 56, 84, 15, 80, 148, 212, 37, 50, 192, 20, 12, 201, 52, 85, 15, 16, 148, 212, 37, 50, 192, 20, 12, 201, 52, 84, 143, 88, 147, 135, 37, 50, 192, 20, 12, 201, 45, 144, 133, 72, 225, 84, 37, 50, 192, 20, 12, 201, 32, 84, 146, 56, 133, 84, 37, 50, 192, 20, 12, 201, 12, 243, 135, 60, 193, 83, 37, 50, 192, 20, 12, 201, 12, 86, 76, 60, 225, 83, 37, 50, 192, 20, 12, 201, 5, 3, 208, 48, 82, 212, 37, 50, 192, 20, 12, 201, 4, 224, 75, 60, 197, 84, 37, 50, 192, 20, 8, 197, 80, 81, 5, 84, 208, 20, 6, 195, 85, 34, 78, 20, 8, 197, 8, 145, 193, 52, 144, 20, 12, 201, 65, 35, 204, 21, 64, 82, 36, 21, 0, 20, 9, 198, 16, 83, 1, 29, 66, 71, 20, 0, 9, 198, 64, 16, 201, 24, 148, 212, 20, 14, 139, 8, 195, 165, 14, 4, 20, 5, 18, 9, 14, 7, 20, 9, 198, 53, 149, 20, 21, 34, 64, 20, 9, 198, 53, 148, 132, 21, 34, 64, 20, 9, 198, 48, 81, 140, 21, 34, 64, 20, 9, 198, 44, 243, 9, 9, 34, 64, 20, 9, 198, 24, 145, 140, 21, 34, 64, 20, 9, 198, 8, 20, 130, 5, 34, 64, 20, 9, 198, 76, 20, 6, 37, 50, 192, 20, 9, 198, 52, 244, 193, 37, 50, 192, 20, 9, 198, 5, 32, 66, 37, 50, 192, 20, 9, 198, 45, 84, 5, 72, 85, 0, 20, 9, 198, 4, 180, 143, 8, 21, 0, 20, 0, 10, 199, 12, 83, 148, 85, 34, 79, 56, 20, 15, 140, 16, 18, 195, 166, 3, 9, 19, 5, 18, 9, 14, 7, 20, 14, 203, 12, 83, 148, 72, 19, 9, 76, 84, 137, 56, 112, 20, 10, 199, 44, 243, 139, 49, 81, 5, 72, 20, 10, 199, 5, 4, 12, 5, 81, 5, 72, 20, 14, 203, 33, 145, 18, 60, 83, 5, 45, 68, 137, 76, 176, 20, 9, 198, 56, 82, 212, 5, 34, 69, 20, 14, 203, 76, 17, 15, 52, 20, 207, 12, 130, 83, 52, 80, 20, 14, 203, 65, 35, 214, 36, 228, 201, 4, 194, 83, 52, 80, 20, 14, 203, 52, 19, 20, 33, 84, 201, 4, 226, 83, 52, 80, 20, 14, 203, 44, 243, 77, 84, 226, 84, 5, 34, 83, 52, 80, 20, 14, 203, 24, 192, 71, 20, 195, 1, 57, 66, 83, 52, 80, 20, 14, 203, 9, 84, 133, 5, 82, 210, 5, 66, 83, 52, 80, 20, 14, 203, 9, 32, 78, 16, 84, 201, 4, 226, 83, 52, 80, 20, 14, 203, 5, 34, 83, 80, 242, 210, 5, 66, 83, 52, 80, 20, 24, 4, 95, 53, 88, 15, 105, 108, 55, 47, 16, 6, 107, 87, 36, 50, 87, 47, 114, 82, 13, 50, 13, 0, 0, 9, 198, 80, 20, 212, 5, 69, 82, 20, 9, 198, 77, 68, 137, 45, 69, 82, 20, 13, 138, 16, 18, 15, 10, 5, 11, 20, 195, 184, 18, 20, 13, 138, 11, 15, 14, 4, 21, 11, 20, 195, 184, 18, 20, 11, 200, 60, 67, 206, 80, 243, 15, 28, 144, 20, 11, 200, 60, 49, 65, 56, 243, 15, 28, 144, 20, 11, 200, 24, 83, 73, 56, 243, 15, 28, 144, 20, 16, 141, 195, 166, 11, 22, 9, 22, 1, 12, 5, 18, 9, 14, 7, 20, 9, 198, 52, 20, 141, 61, 33, 82, 20, 9, 198, 29, 32, 84, 84, 193, 82, 20, 9, 198, 20, 180, 208, 60, 225, 82, 20, 9, 198, 20, 180, 201, 77, 65, 82, 20, 9, 198, 16, 148, 208, 60, 225, 82, 20, 11, 200, 77, 145, 22, 21, 53, 12, 36, 112, 20, 11, 200, 61, 4, 21, 77, 65, 76, 36, 112, 20, 18, 70, 9, 83, 12, 21, 66, 78, 69, 114, 55, 13, 47, 6, 107, 66, 0, 20, 11, 200, 45, 38, 80, 80, 241, 193, 52, 144, 20, 9, 198, 5, 81, 213, 77, 66, 78, 20, 7, 196, 72, 81, 193, 48, 20, 7, 196, 36, 65, 65, 48, 20, 0, 12, 201, 44, 243, 12, 20, 181, 9, 88, 148, 212, 20, 14, 139, 16, 18, 195, 166, 19, 20, 1, 20, 9, 15, 14, 20, 12, 201, 72, 17, 134, 36, 224, 68, 21, 34, 64, 20, 12, 201, 97, 147, 15, 29, 32, 70, 37, 50, 192, 20, 12, 201, 96, 84, 143, 29, 32, 70, 37, 50, 192, 20, 12, 201, 81, 148, 15, 29, 32, 70, 37, 50, 192, 20, 12, 201, 80, 244, 15, 29, 32, 70, 37, 50, 192, 20, 12, 201, 80, 243, 79, 29, 32, 70, 37, 50, 192, 20, 12, 201, 80, 83, 5, 29, 32, 70, 37, 50, 192, 20, 12, 201, 77, 84, 5, 73, 51, 206, 37, 50, 192, 20, 12, 201, 65, 148, 143, 80, 82, 206, 37, 50, 192, 20, 12, 201, 61, 37, 15, 29, 32, 70, 37, 50, 192, 20, 12, 201, 56, 243, 79, 29, 32, 70, 37, 50, 192, 20, 12, 201, 53, 83, 20, 36, 85, 14, 37, 50, 192, 20, 12, 201, 52, 243, 143, 29, 32, 70, 37, 50, 192, 20, 12, 201, 48, 149, 15, 29, 32, 70, 37, 50, 192, 20, 12, 201, 45, 38, 79, 80, 82, 206, 37, 50, 192, 20, 9, 198, 44, 243, 5, 72, 148, 203, 20, 12, 201, 44, 83, 73, 29, 32, 70, 37, 50, 192, 20, 12, 201, 36, 65, 79, 29, 32, 70, 37, 50, 192, 20, 12, 201, 32, 243, 15, 29, 32, 70, 37, 50, 192, 20, 12, 201, 24, 245, 15, 29, 32, 70, 37, 50, 192, 20, 12, 201, 24, 243, 143, 29, 32, 70, 37, 50, 192, 20, 12, 201, 21, 67, 143, 29, 32, 70, 37, 50, 192, 20, 12, 201, 16, 83, 79, 29, 32, 70, 37, 50, 192, 20, 12, 201, 8, 20, 143, 52, 85, 18, 37, 50, 192, 20, 12, 201, 5, 85, 15, 29, 32, 70, 37, 50, 192, 20, 12, 201, 9, 84, 133, 5, 82, 210, 5, 66, 64, 20, 9, 198, 77, 147, 70, 60, 226, 75, 20, 6, 195, 37, 32, 78, 20, 0, 9, 198, 80, 131, 205, 37, 53, 0, 20, 9, 198, 56, 18, 86, 37, 65, 84, 20, 12, 201, 16, 242, 213, 52, 83, 148, 5, 34, 69, 20, 9, 198, 56, 244, 141, 4, 227, 128, 20, 9, 198, 8, 18, 203, 4, 224, 76, 20, 0, 10, 199, 64, 20, 211, 21, 34, 78, 28, 20, 10, 199, 25, 32, 83, 21, 34, 78, 28, 20, 10, 199, 9, 37, 78, 21, 34, 78, 28, 20, 10, 199, 8, 195, 203, 21, 34, 78, 28, 20, 14, 203, 20, 101, 5, 73, 68, 153, 44, 177, 76, 36, 112, 20, 12, 201, 20, 115, 195, 20, 229, 18, 36, 177, 82, 20, 16, 141, 19, 11, 195, 166, 12, 19, 11, 195, 184, 18, 9, 1, 14, 20, 0, 9, 198, 81, 37, 66, 4, 69, 82, 20, 7, 196, 20, 193, 71, 36, 20, 9, 198, 77, 84, 16, 60, 225, 82, 20, 9, 198, 72, 82, 214, 37, 33, 82, 20, 9, 198, 72, 81, 149, 56, 65, 82, 20, 9, 198, 52, 243, 5, 77, 65, 82, 20, 9, 198, 12, 130, 75, 4, 225, 82, 20, 9, 198, 4, 227, 133, 45, 65, 82, 20, 9, 198, 4, 178, 214, 37, 33, 82, 20, 12, 201, 85, 53, 82, 64, 21, 15, 72, 148, 203, 20, 12, 201, 76, 82, 83, 52, 243, 15, 28, 148, 203, 20, 12, 201, 52, 243, 9, 56, 243, 15, 28, 148, 203, 20, 15, 204, 44, 147, 133, 52, 21, 15, 29, 32, 70, 37, 50, 192, 20, 15, 204, 32, 148, 212, 61, 34, 79, 29, 32, 70, 37, 50, 192, 20, 7, 196, 80, 147, 73, 16, 20, 9, 198, 64, 244, 212, 20, 194, 78, 20, 9, 198, 32, 20, 140, 20, 178, 78, 20, 9, 198, 20, 225, 15, 45, 34, 78, 20, 11, 70, 72, 80, 197, 37, 97, 82, 21, 0, 10, 0, 9, 198, 5, 53, 18, 60, 195, 199, 20, 12, 201, 76, 147, 85, 49, 64, 78, 37, 65, 84, 20, 12, 201, 72, 80, 197, 65, 66, 86, 37, 65, 84, 20, 12, 201, 65, 34, 77, 37, 66, 86, 37, 65, 84, 20, 12, 201, 60, 34, 133, 45, 66, 86, 37, 65, 84, 20, 12, 201, 20, 97, 133, 45, 66, 86, 37, 65, 84, 20, 9, 198, 36, 65, 78, 80, 148, 203, 20, 9, 198, 21, 81, 197, 56, 148, 203, 20, 9, 198, 76, 83, 73, 61, 66, 75, 20, 0, 9, 198, 20, 112, 76, 37, 65, 84, 20, 13, 202, 80, 82, 206, 36, 98, 67, 21, 34, 78, 28, 20, 18, 143, 6, 195, 184, 4, 5, 18, 1, 12, 9, 19, 5, 18, 9, 14, 7, 20, 13, 202, 5, 85, 15, 44, 192, 86, 21, 34, 78, 28, 20, 0, 9, 198, 52, 243, 143, 29, 32, 77, 20, 9, 198, 36, 65, 79, 29, 32, 77, 20, 12, 137, 18, 195, 166, 19, 15, 14, 14, 5, 18, 20, 10, 199, 80, 245, 5, 52, 148, 205, 20, 20, 10, 199, 64, 19, 148, 20, 148, 205, 20, 20, 10, 199, 32, 81, 15, 56, 148, 205, 20, 20, 10, 199, 4, 192, 137, 56, 148, 205, 20, 20, 10, 199, 52, 17, 201, 77, 68, 129, 80, 20, 0, 12, 201, 72, 81, 140, 20, 181, 15, 72, 148, 203, 20, 12, 201, 44, 243, 77, 37, 52, 193, 72, 148, 203, 20, 12, 201, 16, 149, 137, 56, 21, 15, 72, 148, 203, 20, 7, 196, 44, 19, 73, 44, 20, 9, 198, 24, 243, 143, 29, 32, 70, 20, 0, 8, 197, 12, 149, 18, 60, 224, 20, 12, 201, 36, 225, 129, 57, 66, 76, 37, 65, 84, 20, 8, 197, 76, 19, 79, 4, 224, 20, 12, 201, 16, 148, 212, 36, 225, 214, 21, 33, 84, 20, 0, 13, 202, 53, 82, 1, 52, 81, 1, 56, 148, 205, 20, 20, 13, 202, 52, 84, 139, 4, 229, 9, 48, 148, 205, 20, 20, 13, 202, 37, 51, 204, 5, 66, 79, 56, 148, 205, 20, 20, 0, 17, 70, 8, 84, 131, 21, 84, 197, 69, 107, 34, 87, 116, 12, 87, 0, 66, 10, 199, 72, 84, 208, 60, 225, 5, 72, 20, 10, 199, 64, 148, 149, 21, 69, 5, 72, 20, 10, 199, 16, 148, 12, 60, 208, 84, 36, 20, 10, 199, 5, 85, 15, 45, 32, 84, 36, 20, 12, 201, 24, 195, 206, 20, 195, 15, 29, 32, 70, 20, 10, 199, 76, 82, 213, 56, 64, 78, 80, 20, 10, 199, 72, 81, 21, 56, 64, 78, 80, 20, 0, 11, 200, 36, 229, 5, 72, 97, 82, 60, 224, 20, 9, 198, 81, 34, 76, 48, 147, 206, 20, 9, 198, 4, 64, 80, 80, 147, 206, 20, 15, 204, 65, 35, 208, 61, 37, 9, 60, 224, 76, 37, 65, 84, 20, 11, 200, 5, 84, 212, 72, 19, 9, 20, 224, 20, 9, 198, 76, 84, 137, 29, 32, 70, 20, 11, 200, 64, 20, 129, 16, 242, 211, 4, 192, 20, 0, 15, 140, 19, 20, 195, 184, 11, 9, 15, 13, 5, 20, 18, 9, 20, 8, 197, 64, 84, 19, 36, 224, 20, 16, 205, 36, 229, 5, 72, 224, 84, 36, 243, 129, 48, 148, 205, 20, 20, 8, 197, 24, 148, 211, 36, 192, 20, 12, 201, 36, 229, 5, 72, 97, 82, 20, 228, 192, 20, 10, 2, 195, 151, 79, 6, 35, 66, 36, 0, 0, 13, 202, 45, 34, 77, 36, 224, 76, 37, 53, 9, 44, 20, 0, 10, 199, 81, 32, 86, 21, 53, 5, 72, 20, 10, 199, 64, 84, 147, 37, 53, 5, 72, 20, 10, 199, 44, 242, 78, 12, 145, 5, 72, 20, 10, 199, 20, 180, 212, 73, 81, 5, 72, 20, 17, 4, 95, 19, 13, 3, 87, 63, 6, 111, 12, 55, 49, 4, 35, 48, 0, 5, 130, 196, 141, 43, 0, 11, 200, 80, 83, 132, 20, 229, 9, 20, 192, 20, 11, 200, 80, 19, 135, 20, 229, 9, 20, 192, 20, 0, 8, 197, 88, 243, 20, 21, 32, 20, 8, 197, 64, 19, 16, 21, 32, 20, 8, 197, 20, 213, 76, 21, 32, 20, 9, 198, 16, 243, 69, 77, 66, 75, 20, 8, 197, 72, 16, 137, 5, 64, 20, 0, 13, 202, 36, 225, 9, 77, 3, 211, 37, 66, 79, 56, 20, 9, 198, 73, 82, 78, 21, 33, 64, 20, 9, 198, 20, 193, 86, 21, 33, 64, 20, 0, 9, 198, 72, 85, 9, 72, 17, 5, 20, 9, 198, 48, 83, 79, 56, 17, 5, 20, 0, 19, 5, 6, 46, 5, 11, 19, 81, 112, 36, 79, 87, 36, 63, 48, 13, 55, 0, 25, 11, 200, 52, 21, 18, 36, 181, 76, 21, 32, 20, 11, 200, 8, 20, 146, 36, 176, 68, 21, 32, 20, 12, 201, 88, 20, 207, 52, 245, 15, 72, 148, 203, 20, 12, 201, 8, 243, 19, 40, 85, 137, 44, 148, 203, 20, 9, 198, 56, 82, 212, 5, 34, 78, 20, 9, 198, 48, 148, 9, 105, 160, 78, 20, 15, 140, 195, 166, 11, 22, 9, 4, 9, 19, 20, 1, 14, 20, 20, 0, 8, 197, 77, 64, 84, 85, 32, 20, 12, 201, 64, 244, 201, 80, 147, 206, 21, 33, 64, 20, 8, 197, 61, 134, 68, 21, 32, 20, 8, 197, 61, 130, 68, 21, 32, 20, 8, 197, 52, 21, 20, 21, 32, 20, 8, 197, 37, 51, 204, 21, 32, 20, 12, 201, 25, 83, 139, 80, 147, 206, 21, 33, 64, 20, 12, 201, 25, 32, 75, 80, 147, 206, 21, 33, 64, 20, 8, 197, 21, 2, 76, 21, 32, 20, 12, 201, 4, 208, 137, 80, 147, 206, 21, 33, 64, 20, 8, 197, 24, 244, 141, 5, 64, 20, 8, 197, 37, 51, 194, 5, 32, 20, 14, 2, 194, 167, 48, 35, 34, 35, 79, 34, 6, 35, 81, 0, 0, 15, 66, 76, 80, 87, 36, 15, 87, 112, 0, 81, 115, 195, 165, 32, 9, 198, 8, 244, 132, 85, 33, 64, 20, 9, 198, 76, 245, 80, 21, 33, 64, 20, 9, 198, 76, 244, 148, 21, 33, 64, 20, 9, 198, 64, 20, 148, 21, 33, 64, 20, 9, 198, 9, 35, 196, 21, 33, 64, 20, 9, 198, 84, 49, 78, 81, 32, 76, 20, 9, 198, 36, 229, 5, 29, 32, 76, 20, 11, 70, 88, 83, 148, 85, 33, 64, 21, 0, 10, 6, 194, 60, 208, 76, 28, 0, 9, 198, 56, 19, 143, 29, 32, 77, 20, 10, 199, 81, 34, 83, 80, 84, 211, 20, 20, 10, 199, 36, 229, 5, 72, 84, 211, 20, 20, 10, 199, 72, 81, 21, 56, 64, 78, 76, 20, 12, 137, 18, 195, 166, 19, 15, 14, 14, 1, 2, 20, 10, 2, 194, 165, 57, 6, 36, 50, 12, 0, 0, 11, 200, 80, 83, 80, 21, 32, 84, 85, 32, 20, 11, 200, 48, 149, 20, 21, 32, 84, 85, 32, 20, 12, 201, 40, 245, 82, 56, 19, 9, 77, 66, 75, 20, 11, 2, 194, 162, 87, 6, 36, 50, 47, 87, 0, 0, 9, 134, 15, 4, 9, 195, 184, 19, 20, 10, 135, 8, 15, 14, 14, 195, 184, 18, 20, 10, 135, 6, 18, 9, 19, 195, 184, 18, 20, 12, 201, 88, 17, 193, 8, 243, 132, 21, 33, 64, 20, 12, 201, 44, 243, 150, 60, 197, 84, 21, 33, 64, 20, 12, 201, 44, 243, 148, 72, 20, 212, 21, 33, 64, 20, 12, 201, 16, 242, 213, 52, 83, 148, 21, 33, 64, 20, 12, 201, 5, 33, 213, 52, 83, 148, 21, 33, 64, 20, 8, 197, 21, 81, 143, 72, 144, 20, 8, 197, 53, 84, 197, 84, 208, 20, 8, 197, 80, 82, 83, 52, 80, 20, 8, 197, 16, 82, 83, 52, 80, 20, 8, 197, 85, 48, 78, 12, 80, 20, 9, 2, 194, 163, 48, 40, 50, 19, 0, 0, 10, 135, 22, 9, 19, 11, 195, 184, 19, 20, 10, 135, 19, 5, 18, 9, 195, 184, 19, 20, 9, 198, 80, 20, 129, 57, 65, 76, 20, 9, 198, 76, 194, 66, 21, 34, 64, 20, 9, 198, 76, 192, 86, 21, 34, 64, 20, 9, 198, 56, 20, 146, 21, 34, 64, 20, 9, 198, 44, 226, 66, 21, 34, 64, 20, 9, 198, 28, 224, 86, 21, 34, 64, 20, 9, 198, 24, 20, 150, 21, 34, 64, 20, 9, 198, 48, 20, 16, 37, 50, 192, 20, 9, 198, 20, 193, 71, 37, 50, 192, 20, 9, 198, 28, 20, 129, 57, 66, 64, 20, 9, 198, 72, 83, 133, 28, 21, 0, 20, 9, 198, 24, 245, 15, 77, 64, 84, 20, 9, 198, 12, 83, 147, 61, 32, 84, 20, 9, 198, 5, 69, 5, 57, 64, 84, 20, 9, 198, 4, 197, 77, 56, 21, 0, 20, 0, 12, 137, 11, 15, 8, 195, 166, 19, 9, 15, 14, 20, 10, 199, 36, 229, 5, 57, 50, 79, 56, 20, 10, 199, 16, 149, 133, 73, 50, 79, 56, 20, 10, 199, 52, 19, 137, 13, 84, 133, 72, 20, 10, 199, 44, 243, 148, 36, 229, 69, 72, 20, 10, 199, 44, 21, 15, 48, 144, 197, 72, 20, 10, 199, 5, 69, 18, 36, 37, 69, 72, 20, 12, 201, 77, 83, 6, 5, 66, 65, 104, 243, 0, 20, 9, 198, 80, 84, 146, 5, 34, 69, 20, 10, 199, 44, 20, 140, 40, 242, 1, 56, 21, 0, 11, 200, 8, 245, 82, 28, 83, 201, 76, 144, 20, 11, 200, 44, 20, 146, 61, 52, 197, 72, 144, 20, 11, 200, 80, 147, 12, 4, 65, 76, 36, 112, 20, 11, 200, 77, 3, 9, 16, 17, 212, 36, 112, 20, 11, 200, 52, 148, 213, 56, 65, 76, 36, 112, 20, 11, 200, 4, 229, 133, 56, 65, 76, 36, 112, 20, 11, 200, 77, 144, 129, 72, 149, 9, 76, 176, 20, 11, 200, 37, 51, 1, 52, 149, 9, 76, 176, 20, 11, 200, 33, 145, 201, 20, 163, 137, 76, 176, 20, 11, 200, 32, 19, 147, 20, 21, 9, 76, 176, 20, 11, 200, 5, 34, 201, 52, 81, 9, 76, 176, 20, 11, 200, 4, 229, 1, 72, 181, 9, 76, 176, 20, 11, 200, 4, 193, 129, 8, 85, 9, 76, 176, 20, 11, 200, 4, 180, 143, 52, 21, 9, 76, 176, 20, 11, 200, 76, 178, 90, 60, 100, 133, 56, 144, 20, 11, 200, 81, 35, 212, 76, 178, 83, 52, 80, 20, 11, 200, 77, 147, 12, 60, 114, 83, 52, 80, 20, 11, 200, 76, 130, 78, 80, 242, 83, 52, 80, 20, 11, 200, 56, 83, 204, 60, 114, 83, 52, 80, 20, 11, 200, 28, 19, 12, 36, 50, 83, 52, 80, 20, 11, 200, 20, 180, 207, 72, 50, 83, 52, 80, 20, 11, 200, 77, 3, 9, 16, 17, 212, 36, 112, 20, 27, 2, 194, 174, 34, 36, 79, 37, 87, 47, 34, 6, 36, 34, 36, 47, 15, 82, 35, 34, 36, 63, 36, 34, 49, 36, 0, 0, 13, 138, 19, 16, 9, 18, 9, 20, 21, 195, 184, 19, 20, 14, 139, 7, 1, 12, 22, 1, 14, 9, 19, 195, 184, 18, 20, 8, 197, 25, 34, 69, 72, 144, 20, 12, 201, 76, 86, 67, 32, 83, 12, 37, 50, 192, 20, 12, 201, 65, 54, 75, 20, 65, 76, 37, 50, 192, 20, 12, 201, 65, 35, 199, 56, 244, 212, 37, 50, 192, 20, 12, 201, 64, 20, 133, 57, 65, 84, 37, 50, 192, 20, 12, 201, 64, 16, 201, 24, 148, 212, 37, 50, 192, 20, 12, 201, 52, 244, 129, 48, 148, 212, 37, 50, 192, 20, 12, 201, 52, 243, 133, 28, 20, 203, 37, 50, 192, 20, 12, 201, 52, 85, 1, 77, 64, 84, 37, 50, 192, 20, 12, 201, 48, 147, 135, 88, 148, 212, 37, 50, 192, 20, 12, 201, 48, 83, 137, 56, 148, 212, 37, 50, 192, 20, 12, 201, 44, 243, 15, 72, 148, 212, 37, 50, 192, 20, 12, 201, 44, 21, 1, 48, 84, 20, 37, 50, 192, 20, 12, 201, 33, 83, 79, 72, 148, 212, 37, 50, 192, 20, 12, 201, 28, 83, 210, 28, 148, 212, 37, 50, 192, 20, 12, 201, 25, 85, 21, 72, 148, 212, 37, 50, 192, 20, 12, 201, 21, 81, 133, 52, 148, 212, 37, 50, 192, 20, 12, 201, 16, 83, 79, 45, 32, 84, 37, 50, 192, 20, 12, 201, 9, 81, 4, 32, 148, 212, 37, 50, 192, 20, 12, 201, 4, 227, 129, 48, 148, 212, 37, 50, 192, 20, 12, 201, 12, 132, 137, 77, 66, 65, 56, 149, 0, 20, 10, 69, 76, 245, 82, 12, 80, 21, 0, 10, 5, 130, 195, 167, 43, 0, 9, 198, 76, 230, 68, 21, 34, 64, 20, 9, 198, 73, 149, 20, 21, 34, 64, 20, 9, 198, 64, 147, 132, 21, 34, 64, 20, 9, 198, 44, 241, 204, 21, 34, 64, 20, 9, 198, 44, 240, 140, 21, 34, 64, 20, 9, 198, 44, 20, 148, 21, 34, 64, 20, 9, 198, 28, 226, 68, 21, 34, 64, 20, 9, 198, 16, 145, 148, 21, 34, 64, 20, 9, 198, 9, 35, 196, 21, 34, 64, 20, 9, 198, 8, 147, 132, 21, 34, 64, 20, 9, 198, 64, 20, 129, 76, 149, 0, 20, 9, 198, 24, 81, 5, 77, 66, 64, 20, 9, 198, 12, 130, 65, 57, 66, 64, 20, 9, 198, 76, 83, 137, 61, 32, 84, 20, 9, 198, 72, 85, 19, 77, 64, 84, 20, 9, 198, 16, 148, 208, 5, 32, 84, 20, 5, 130, 195, 164, 43, 0, 12, 137, 13, 15, 4, 5, 12, 12, 195, 184, 18, 20, 10, 199, 61, 130, 68, 5, 66, 79, 56, 20, 10, 199, 61, 101, 76, 5, 66, 79, 56, 20, 10, 199, 37, 51, 204, 5, 66, 79, 56, 20, 10, 199, 36, 229, 5, 57, 66, 79, 56, 20, 10, 199, 36, 225, 140, 5, 66, 79, 56, 20, 10, 199, 44, 243, 80, 61, 53, 5, 72, 20, 9, 198, 52, 20, 148, 101, 34, 69, 20, 14, 203, 64, 21, 18, 36, 20, 139, 4, 194, 83, 52, 80, 20, 14, 203, 64, 20, 148, 36, 181, 76, 5, 34, 83, 52, 80, 20, 0, 13, 138, 11, 15, 13, 13, 1, 14, 4, 195, 184, 18, 20, 9, 198, 72, 148, 15, 77, 65, 82, 20, 9, 198, 45, 33, 68, 37, 65, 82, 20, 9, 198, 44, 20, 130, 85, 33, 82, 20, 9, 198, 44, 19, 9, 9, 33, 82, 20, 9, 198, 36, 229, 5, 29, 33, 82, 20, 9, 198, 36, 228, 208, 37, 33, 82, 20, 9, 198, 28, 20, 129, 57, 65, 82, 20, 9, 198, 16, 149, 133, 73, 65, 82, 20, 9, 198, 16, 145, 134, 21, 33, 82, 20, 9, 198, 5, 52, 201, 77, 65, 82, 20, 12, 201, 76, 198, 78, 28, 83, 1, 29, 66, 71, 20, 15, 204, 84, 226, 86, 21, 36, 193, 48, 148, 212, 37, 50, 192, 20, 11, 200, 80, 83, 5, 64, 21, 9, 76, 176, 20, 15, 204, 76, 176, 78, 16, 147, 129, 88, 148, 212, 37, 50, 192, 20, 15, 204, 65, 35, 208, 4, 112, 78, 16, 148, 212, 37, 50, 192, 20, 11, 200, 60, 229, 15, 48, 241, 201, 76, 176, 20, 15, 204, 44, 243, 12, 20, 181, 9, 88, 148, 212, 37, 50, 192, 20, 15, 204, 24, 20, 141, 4, 179, 199, 56, 244, 212, 37, 50, 192, 20, 15, 204, 21, 99, 204, 85, 66, 79, 56, 148, 212, 37, 50, 192, 20, 11, 200, 5, 85, 15, 52, 21, 9, 76, 176, 20, 11, 200, 5, 3, 211, 80, 243, 9, 76, 176, 20, 7, 196, 24, 16, 201, 48, 20, 11, 200, 72, 243, 65, 56, 148, 212, 36, 176, 20, 9, 198, 32, 243, 132, 85, 32, 78, 20, 15, 204, 24, 194, 80, 65, 35, 204, 21, 64, 82, 36, 21, 0, 20, 7, 196, 48, 81, 193, 48, 20, 20, 2, 194, 170, 81, 36, 63, 37, 50, 37, 50, 15, 116, 70, 37, 50, 6, 35, 55, 0, 0, 13, 138, 12, 21, 11, 19, 21, 18, 9, 195, 184, 19, 20, 12, 201, 72, 16, 149, 48, 148, 212, 21, 34, 64, 20, 12, 201, 56, 21, 20, 21, 35, 196, 21, 34, 64, 20, 12, 201, 81, 83, 85, 49, 64, 82, 37, 50, 192, 20, 12, 201, 80, 83, 5, 52, 85, 18, 37, 50, 192, 20, 12, 201, 72, 85, 8, 5, 97, 82, 37, 50, 192, 20, 12, 201, 65, 35, 204, 21, 64, 82, 37, 50, 192, 20, 12, 201, 64, 192, 78, 21, 64, 82, 37, 50, 192, 20, 12, 201, 4, 229, 9, 45, 96, 82, 37, 50, 192, 20, 12, 201, 4, 48, 197, 77, 51, 210, 37, 50, 192, 20, 0, 15, 140, 16, 15, 18, 20, 18, 195, 166, 20, 20, 195, 184, 18, 20, 15, 140, 13, 1, 14, 9, 16, 21, 12, 1, 20, 195, 184, 18, 20, 15, 140, 9, 14, 19, 20, 1, 12, 12, 1, 20, 195, 184, 18, 20, 15, 140, 4, 5, 19, 20, 9, 12, 12, 1, 20, 195, 184, 18, 20, 6, 195, 16, 85, 19, 72, 15, 4, 95, 18, 5, 22, 34, 37, 82, 6, 106, 12, 87, 70, 0, 6, 130, 195, 160, 43, 14, 0, 9, 198, 24, 243, 143, 29, 32, 77, 20, 9, 198, 4, 84, 143, 29, 32, 77, 20, 10, 199, 52, 146, 210, 60, 34, 69, 48, 20, 9, 198, 29, 147, 129, 56, 68, 137, 20, 14, 203, 8, 18, 212, 21, 34, 79, 48, 241, 201, 76, 176, 20, 10, 199, 44, 243, 139, 61, 33, 1, 80, 20, 13, 2, 194, 169, 49, 39, 48, 114, 34, 35, 57, 47, 0, 0, 9, 198, 64, 83, 12, 21, 65, 82, 20, 9, 198, 44, 243, 208, 21, 33, 82, 20, 9, 198, 36, 229, 133, 77, 65, 82, 20, 9, 198, 36, 228, 201, 77, 65, 82, 20, 9, 198, 24, 18, 212, 85, 33, 82, 20, 9, 198, 16, 85, 5, 45, 65, 82, 20, 9, 198, 5, 36, 133, 77, 65, 82, 20, 9, 198, 4, 36, 207, 49, 97, 82, 20, 15, 204, 24, 245, 15, 29, 32, 77, 52, 85, 18, 37, 50, 192, 20, 9, 198, 52, 19, 132, 5, 34, 78, 20, 9, 198, 44, 244, 147, 61, 32, 78, 20, 9, 3, 16, 195, 165, 48, 111, 0, 72, 0, 12, 201, 76, 83, 147, 37, 66, 86, 37, 65, 84, 20, 12, 201, 76, 83, 5, 45, 66, 86, 37, 65, 84, 20, 12, 201, 61, 4, 15, 73, 69, 78, 37, 65, 84, 20, 12, 201, 5, 52, 197, 73, 66, 86, 37, 65, 84, 20, 12, 137, 16, 18, 195, 166, 16, 1, 18, 1, 20, 20, 5, 130, 197, 159, 43, 5, 130, 195, 175, 43, 0, 9, 198, 81, 80, 129, 37, 53, 0, 20, 9, 198, 72, 80, 76, 37, 65, 84, 20, 9, 198, 57, 83, 12, 37, 65, 84, 20, 0, 20, 8, 23, 3, 39, 5, 18, 14, 5, 19, 82, 6, 36, 87, 36, 112, 50, 13, 87, 0, 9, 198, 8, 20, 143, 29, 32, 77, 20, 9, 198, 5, 69, 15, 29, 32, 77, 20, 12, 137, 7, 195, 166, 19, 20, 5, 18, 5, 18, 20, 10, 199, 12, 83, 12, 84, 195, 201, 16, 20, 10, 199, 44, 83, 143, 80, 17, 137, 20, 20, 7, 2, 194, 181, 63, 114, 0, 0, 7, 196, 64, 146, 197, 72, 20, 7, 196, 48, 18, 197, 72, 20, 7, 196, 80, 244, 20, 36, 20, 9, 198, 16, 19, 65, 76, 49, 78, 20, 7, 196, 88, 146, 193, 72, 20, 5, 130, 195, 170, 43, 0, 12, 201, 80, 83, 5, 29, 32, 70, 37, 53, 0, 20, 12, 201, 76, 83, 147, 36, 34, 76, 37, 65, 84, 20, 12, 201, 60, 97, 137, 12, 144, 76, 37, 65, 84, 20, 12, 201, 52, 21, 5, 72, 144, 76, 37, 65, 84, 20, 12, 201, 36, 211, 79, 73, 64, 76, 37, 65, 84, 20, 12, 201, 36, 195, 9, 45, 98, 68, 37, 65, 84, 20, 14, 139, 19, 11, 18, 195, 166, 4, 4, 5, 18, 5, 18, 20, 14, 139, 11, 195, 166, 18, 5, 19, 20, 5, 18, 5, 18, 20, 8, 197, 52, 20, 135, 36, 224, 20, 12, 201, 44, 243, 147, 80, 84, 142, 21, 33, 84, 20, 5, 130, 195, 171, 43, 0, 9, 198, 16, 148, 211, 20, 228, 192, 20, 17, 142, 19, 21, 12, 6, 1, 16, 18, 195, 166, 16, 1, 18, 1, 20, 20, 9, 198, 88, 20, 137, 4, 228, 192, 20, 0, 10, 199, 65, 35, 198, 21, 65, 82, 20, 20, 10, 199, 44, 244, 212, 84, 209, 82, 20, 20, 10, 199, 8, 19, 1, 56, 49, 82, 20, 20, 10, 199, 20, 212, 9, 72, 146, 197, 72, 20, 10, 199, 4, 181, 83, 80, 146, 197, 72, 20, 9, 198, 36, 225, 197, 56, 149, 77, 20, 10, 199, 80, 147, 79, 45, 32, 84, 36, 20, 5, 130, 195, 169, 43, 0, 13, 138, 19, 20, 1, 20, 9, 15, 14, 195, 166, 18, 20, 9, 134, 16, 15, 12, 195, 166, 18, 20, 9, 134, 13, 15, 12, 195, 166, 18, 20, 13, 138, 13, 9, 12, 12, 9, 15, 14, 195, 166, 18, 20, 7, 196, 64, 20, 148, 36, 20, 7, 196, 8, 81, 201, 44, 20, 5, 130, 195, 182, 43, 0, 10, 135, 19, 11, 1, 12, 195, 166, 18, 20, 8, 197, 29, 32, 86, 36, 64, 20, 8, 197, 8, 20, 211, 36, 224, 20, 8, 197, 64, 20, 212, 36, 192, 20, 8, 197, 56, 244, 208, 36, 192, 20, 12, 201, 45, 98, 78, 80, 84, 211, 20, 228, 192, 20, 12, 201, 36, 229, 5, 48, 194, 71, 20, 228, 192, 20, 12, 201, 36, 229, 5, 72, 84, 211, 4, 229, 0, 20, 19, 2, 195, 183, 70, 37, 82, 37, 70, 6, 36, 51, 36, 84, 15, 63, 36, 84, 0, 0, 13, 202, 56, 82, 210, 60, 208, 78, 80, 146, 197, 72, 20, 13, 202, 24, 147, 8, 5, 35, 79, 56, 146, 197, 72, 20, 12, 201, 44, 194, 77, 4, 181, 5, 72, 149, 77, 20, 13, 2, 194, 188, 36, 50, 15, 49, 82, 35, 34, 47, 0, 0, 12, 137, 16, 21, 2, 5, 18, 20, 195, 166, 18, 20, 12, 137, 3, 5, 12, 12, 21, 12, 195, 166, 18, 20, 10, 199, 65, 35, 198, 36, 193, 82, 20, 20, 10, 199, 76, 19, 86, 37, 69, 9, 28, 20, 10, 199, 76, 17, 212, 52, 241, 9, 28, 20, 10, 199, 17, 144, 147, 36, 225, 9, 28, 20, 14, 203, 20, 180, 202, 84, 115, 211, 48, 21, 137, 20, 224, 20, 10, 199, 85, 37, 71, 84, 22, 65, 56, 20, 9, 198, 4, 195, 9, 4, 224, 197, 20, 10, 199, 81, 32, 70, 36, 176, 78, 80, 20, 11, 2, 194, 189, 36, 50, 6, 105, 35, 55, 0, 0, 9, 198, 48, 85, 129, 57, 66, 78, 20, 9, 198, 5, 33, 197, 57, 66, 78, 20, 9, 198, 4, 225, 204, 36, 176, 78, 20, 9, 198, 17, 32, 71, 60, 208, 78, 21, 22, 2, 194, 186, 63, 6, 35, 87, 49, 40, 55, 37, 50, 15, 116, 70, 37, 50, 6, 35, 55, 0, 16, 4, 95, 18, 6, 24, 34, 47, 34, 39, 81, 55, 107, 49, 87, 0, 14, 4, 95, 3, 5, 4, 87, 13, 70, 6, 37, 55, 35, 0, 0, 14, 139, 18, 21, 4, 9, 13, 5, 14, 20, 195, 166, 18, 20, 8, 197, 64, 83, 12, 21, 64, 20, 8, 197, 8, 19, 12, 21, 64, 20, 8, 197, 60, 35, 201, 77, 64, 20, 8, 197, 52, 243, 148, 21, 32, 20, 15, 204, 44, 83, 79, 80, 84, 129, 64, 85, 84, 36, 181, 77, 20, 8, 197, 36, 226, 214, 37, 64, 20, 8, 197, 29, 32, 70, 37, 64, 20, 8, 197, 16, 80, 197, 57, 64, 20, 8, 197, 44, 195, 210, 5, 64, 20, 0, 9, 198, 48, 240, 133, 48, 145, 64, 20, 9, 198, 88, 19, 129, 16, 145, 64, 20, 9, 198, 56, 240, 133, 48, 145, 64, 20, 9, 198, 8, 19, 1, 56, 49, 64, 20, 0, 9, 67, 36, 177, 64, 35, 57, 49, 0, 10, 199, 76, 240, 201, 60, 227, 205, 36, 20, 14, 4, 95, 12, 9, 7, 55, 37, 79, 35, 47, 40, 34, 0, 5, 130, 195, 177, 43, 5, 130, 197, 161, 43, 0, 9, 198, 16, 81, 133, 57, 51, 210, 20, 11, 200, 76, 22, 15, 24, 243, 137, 77, 64, 20, 11, 200, 44, 243, 134, 61, 35, 73, 77, 64, 20, 11, 200, 44, 20, 9, 80, 19, 9, 77, 64, 20, 11, 200, 84, 211, 210, 4, 194, 84, 21, 64, 20, 11, 200, 64, 197, 82, 4, 194, 84, 21, 64, 20, 11, 200, 52, 20, 211, 37, 98, 84, 21, 64, 20, 11, 200, 48, 20, 195, 37, 98, 84, 21, 64, 20, 11, 200, 44, 243, 139, 5, 98, 84, 21, 64, 20, 11, 200, 36, 229, 5, 29, 34, 84, 21, 64, 20, 11, 200, 24, 18, 212, 36, 50, 84, 21, 64, 20, 11, 200, 16, 81, 143, 72, 210, 84, 21, 64, 20, 11, 200, 12, 83, 5, 9, 34, 84, 21, 64, 20, 11, 200, 4, 227, 206, 100, 210, 84, 21, 64, 20, 11, 200, 25, 33, 75, 88, 83, 148, 21, 32, 20, 11, 200, 4, 178, 210, 20, 66, 84, 21, 32, 20, 9, 198, 88, 83, 133, 80, 144, 78, 20, 11, 200, 72, 84, 212, 5, 84, 129, 57, 64, 20, 0, 8, 197, 80, 244, 148, 85, 32, 20, 8, 197, 73, 84, 20, 85, 32, 20, 8, 197, 44, 243, 148, 85, 32, 20, 8, 197, 77, 64, 84, 85, 64, 20, 8, 197, 41, 83, 137, 61, 32, 20, 8, 197, 77, 66, 76, 21, 64, 20, 8, 197, 57, 81, 9, 77, 64, 20, 12, 201, 76, 84, 150, 36, 49, 82, 36, 225, 192, 20, 12, 201, 64, 20, 134, 84, 209, 82, 36, 225, 192, 20, 12, 201, 16, 84, 193, 72, 209, 82, 36, 225, 192, 20, 12, 201, 5, 36, 129, 56, 113, 82, 36, 225, 192, 20, 8, 197, 76, 21, 84, 21, 32, 20, 8, 197, 20, 194, 68, 21, 32, 20, 8, 197, 16, 19, 132, 21, 32, 20, 11, 136, 13, 195, 184, 12, 12, 5, 18, 9, 20, 13, 138, 8, 195, 184, 10, 1, 4, 5, 12, 9, 7, 20, 12, 201, 88, 242, 193, 9, 83, 1, 72, 145, 64, 20, 8, 197, 21, 52, 18, 37, 64, 20, 12, 201, 56, 85, 84, 72, 19, 9, 76, 209, 64, 20, 12, 201, 56, 21, 21, 72, 19, 9, 76, 209, 64, 20, 12, 201, 44, 243, 134, 61, 35, 73, 76, 209, 64, 20, 12, 201, 44, 20, 9, 80, 19, 9, 76, 209, 64, 20, 8, 197, 44, 194, 69, 57, 64, 20, 12, 201, 56, 243, 131, 32, 19, 1, 56, 49, 64, 20, 8, 197, 77, 83, 6, 5, 64, 20, 8, 197, 56, 149, 18, 5, 64, 20, 12, 201, 44, 243, 147, 37, 53, 15, 72, 144, 76, 20, 8, 197, 64, 146, 193, 57, 64, 20, 0, 14, 139, 14, 15, 18, 4, 195, 184, 19, 20, 12, 9, 7, 20, 14, 139, 8, 195, 184, 10, 20, 9, 4, 5, 12, 9, 7, 20, 9, 198, 76, 19, 65, 72, 145, 64, 20, 9, 198, 4, 211, 79, 56, 145, 64, 20, 9, 198, 52, 21, 18, 36, 49, 64, 20, 9, 198, 4, 181, 18, 36, 49, 64, 20, 9, 198, 25, 35, 205, 4, 113, 64, 20, 7, 132, 2, 195, 184, 18, 76, 5, 130, 195, 188, 43, 0, 14, 203, 25, 83, 132, 4, 209, 78, 80, 19, 9, 77, 64, 20, 14, 203, 65, 35, 199, 72, 84, 211, 37, 98, 84, 21, 64, 20, 14, 203, 36, 225, 70, 24, 82, 212, 37, 98, 84, 21, 64, 20, 14, 203, 25, 83, 139, 80, 147, 206, 4, 194, 84, 21, 64, 20, 14, 203, 16, 148, 212, 36, 226, 212, 37, 98, 84, 21, 64, 20, 14, 203, 16, 84, 212, 73, 82, 212, 37, 98, 84, 21, 64, 20, 13, 138, 4, 195, 184, 4, 2, 9, 4, 5, 18, 9, 20, 10, 199, 53, 84, 203, 20, 67, 206, 56, 20, 0, 11, 200, 77, 84, 146, 20, 19, 9, 77, 64, 20, 11, 200, 48, 144, 133, 72, 19, 9, 77, 64, 20, 11, 136, 4, 9, 195, 166, 20, 9, 19, 20, 20, 11, 200, 8, 83, 12, 21, 68, 137, 77, 64, 20, 11, 200, 8, 80, 82, 8, 82, 132, 21, 32, 67, 9, 198, 76, 176, 66, 20, 195, 206, 20, 9, 198, 52, 146, 210, 60, 99, 206, 20, 15, 204, 5, 85, 5, 57, 66, 70, 36, 49, 82, 36, 225, 192, 20, 11, 200, 52, 19, 137, 24, 84, 212, 21, 32, 20, 12, 137, 195, 166, 18, 7, 5, 18, 18, 9, 7, 20, 16, 141, 6, 15, 18, 8, 195, 165, 2, 5, 14, 20, 12, 9, 7, 20, 15, 204, 81, 32, 78, 77, 97, 83, 80, 149, 9, 76, 209, 64, 20, 15, 204, 25, 83, 132, 4, 209, 78, 80, 19, 9, 76, 209, 64, 20, 9, 198, 81, 83, 133, 76, 145, 78, 20, 9, 198, 5, 52, 217, 72, 145, 78, 20, 11, 200, 20, 180, 208, 20, 66, 69, 57, 64, 20, 9, 198, 56, 243, 73, 56, 19, 0, 20, 0, 10, 135, 6, 12, 1, 14, 195, 184, 18, 20, 10, 135, 3, 1, 21, 19, 195, 184, 18, 20, 8, 197, 48, 21, 137, 56, 80, 20, 12, 201, 72, 82, 70, 36, 49, 82, 36, 225, 192, 20, 12, 201, 64, 20, 143, 16, 145, 82, 36, 225, 192, 20, 12, 201, 52, 18, 211, 36, 209, 82, 36, 225, 192, 20, 12, 201, 17, 84, 12, 36, 177, 82, 36, 225, 192, 20, 12, 201, 8, 19, 19, 4, 209, 82, 36, 225, 192, 20, 12, 201, 5, 68, 143, 24, 145, 82, 36, 225, 192, 20, 8, 197, 52, 147, 133, 72, 80, 20, 8, 197, 28, 83, 133, 72, 80, 20, 13, 138, 19, 25, 4, 195, 184, 19, 20, 12, 9, 7, 20, 12, 201, 77, 84, 208, 20, 228, 207, 72, 145, 64, 20, 12, 201, 44, 243, 147, 37, 53, 15, 72, 145, 64, 20, 8, 197, 76, 241, 15, 52, 144, 20, 12, 201, 77, 147, 139, 72, 85, 9, 76, 209, 64, 20, 12, 201, 76, 84, 1, 72, 21, 9, 76, 209, 64, 20, 12, 201, 52, 147, 137, 52, 19, 9, 76, 209, 64, 20, 12, 201, 44, 192, 83, 76, 144, 201, 76, 209, 64, 20, 8, 197, 29, 32, 70, 20, 208, 20, 0, 9, 198, 17, 80, 84, 48, 85, 0, 20, 9, 198, 44, 194, 69, 57, 65, 76, 20, 9, 198, 44, 194, 69, 57, 65, 76, 20, 14, 139, 20, 9, 12, 18, 195, 165, 4, 5, 12, 9, 7, 20, 9, 198, 32, 84, 130, 36, 50, 68, 20, 9, 198, 16, 243, 15, 52, 149, 0, 20, 9, 198, 64, 244, 212, 21, 64, 84, 20, 9, 198, 16, 84, 208, 21, 32, 84, 20, 6, 2, 195, 184, 116, 0, 0, 9, 198, 80, 82, 206, 60, 227, 205, 20, 9, 198, 44, 20, 131, 36, 227, 205, 20, 10, 199, 88, 149, 137, 76, 82, 197, 72, 20, 10, 199, 64, 84, 150, 21, 37, 5, 72, 20, 10, 199, 44, 19, 15, 72, 145, 133, 72, 20, 10, 199, 65, 35, 211, 4, 146, 197, 72, 20, 10, 199, 9, 83, 9, 52, 146, 197, 72, 20, 9, 198, 65, 35, 208, 72, 149, 77, 20, 10, 199, 4, 180, 143, 8, 21, 9, 44, 20, 10, 199, 65, 32, 75, 80, 148, 193, 8, 20, 0, 12, 137, 20, 18, 9, 11, 9, 14, 195, 184, 19, 20, 11, 200, 53, 150, 15, 52, 21, 15, 76, 80, 20, 11, 200, 77, 147, 139, 72, 243, 137, 76, 176, 20, 11, 200, 77, 66, 76, 37, 53, 9, 76, 176, 20, 11, 200, 77, 64, 84, 37, 53, 9, 76, 176, 20, 11, 200, 77, 2, 82, 4, 229, 9, 76, 176, 20, 11, 200, 76, 179, 204, 5, 53, 9, 76, 176, 20, 11, 200, 56, 85, 82, 4, 193, 201, 76, 176, 20, 11, 200, 44, 21, 1, 49, 149, 9, 76, 176, 20, 11, 200, 24, 20, 195, 37, 53, 9, 76, 176, 20, 11, 200, 16, 144, 83, 80, 243, 9, 76, 176, 20, 7, 196, 76, 21, 9, 56, 20, 7, 196, 44, 19, 73, 56, 20, 11, 200, 88, 19, 132, 4, 194, 83, 52, 80, 20, 11, 200, 80, 84, 146, 61, 34, 83, 52, 80, 20, 11, 200, 77, 147, 66, 60, 194, 83, 52, 80, 20, 11, 200, 77, 64, 76, 36, 226, 83, 52, 80, 20, 11, 200, 76, 240, 201, 4, 194, 83, 52, 80, 20, 11, 200, 64, 192, 84, 60, 226, 83, 52, 80, 20, 11, 200, 52, 243, 135, 60, 194, 83, 52, 80, 20, 11, 200, 45, 33, 84, 36, 226, 83, 52, 80, 20, 11, 200, 24, 244, 141, 4, 194, 83, 52, 80, 20, 11, 200, 24, 85, 68, 4, 194, 83, 52, 80, 20, 11, 200, 24, 85, 9, 12, 130, 83, 52, 80, 20, 11, 200, 16, 20, 151, 36, 226, 83, 52, 80, 20, 11, 200, 9, 37, 84, 4, 194, 83, 52, 80, 20, 11, 200, 4, 36, 213, 72, 66, 83, 52, 80, 20, 0, 12, 201, 16, 84, 141, 5, 67, 204, 60, 114, 64, 20, 12, 201, 9, 35, 205, 5, 67, 204, 60, 114, 64, 20, 12, 201, 4, 229, 18, 61, 3, 204, 60, 114, 64, 20, 8, 197, 73, 85, 9, 56, 80, 20, 8, 197, 53, 148, 212, 36, 176, 20, 8, 67, 76, 227, 194, 21, 0, 10, 0, 12, 137, 195, 166, 20, 9, 15, 12, 15, 7, 9, 20, 9, 198, 85, 35, 204, 60, 114, 64, 20, 13, 202, 32, 84, 141, 20, 225, 85, 80, 146, 197, 72, 20, 9, 198, 76, 241, 15, 52, 149, 0, 20, 9, 198, 52, 243, 143, 48, 149, 0, 20, 0, 17, 67, 44, 243, 64, 49, 112, 63, 15, 87, 112, 0, 81, 115, 195, 165, 32, 12, 137, 22, 15, 12, 15, 14, 20, 195, 184, 18, 20, 10, 199, 52, 18, 213, 48, 21, 15, 72, 20, 10, 199, 4, 195, 9, 28, 21, 15, 72, 20, 10, 199, 24, 147, 138, 85, 53, 5, 72, 20, 14, 203, 72, 81, 201, 60, 224, 76, 37, 53, 9, 76, 176, 20, 14, 203, 72, 21, 9, 60, 224, 76, 37, 53, 9, 76, 176, 20, 14, 203, 64, 242, 78, 80, 147, 12, 37, 53, 9, 76, 176, 20, 14, 203, 64, 21, 5, 72, 224, 76, 37, 53, 9, 76, 176, 20, 14, 203, 56, 21, 9, 60, 224, 76, 37, 53, 9, 76, 176, 20, 14, 203, 44, 19, 142, 36, 32, 76, 37, 53, 9, 76, 176, 20, 14, 203, 65, 35, 212, 20, 181, 9, 60, 226, 83, 52, 80, 20, 14, 203, 64, 84, 134, 20, 181, 9, 60, 226, 83, 52, 80, 20, 14, 203, 44, 243, 77, 21, 32, 201, 4, 194, 83, 52, 80, 20, 14, 203, 36, 225, 9, 88, 145, 21, 4, 194, 83, 52, 80, 20, 14, 203, 36, 212, 18, 21, 52, 201, 60, 226, 83, 52, 80, 20, 14, 203, 20, 180, 208, 4, 228, 201, 60, 226, 83, 52, 80, 20, 10, 199, 28, 83, 65, 48, 147, 132, 20, 20, 10, 67, 76, 243, 64, 87, 112, 63, 0, 72, 21, 4, 95, 54, 88, 15, 47, 34, 6, 107, 87, 36, 50, 87, 47, 114, 82, 13, 50, 13, 0, 0, 9, 198, 65, 83, 16, 37, 69, 82, 20, 9, 198, 16, 240, 197, 57, 69, 82, 20, 12, 137, 7, 18, 1, 14, 21, 12, 195, 184, 19, 20, 13, 138, 5, 11, 19, 16, 15, 18, 20, 195, 184, 18, 20, 13, 138, 4, 9, 19, 16, 1, 3, 8, 195, 184, 18, 20, 11, 200, 89, 83, 11, 4, 227, 204, 60, 112, 20, 11, 200, 28, 84, 143, 57, 67, 204, 60, 112, 20, 11, 200, 9, 34, 71, 4, 229, 9, 56, 80, 20, 9, 198, 88, 147, 132, 36, 49, 82, 20, 9, 198, 76, 83, 5, 45, 65, 82, 20, 9, 198, 72, 83, 1, 56, 49, 82, 20, 9, 198, 45, 84, 147, 37, 97, 82, 20, 9, 198, 44, 243, 134, 21, 33, 82, 20, 9, 198, 16, 82, 204, 5, 33, 82, 20, 9, 198, 12, 83, 5, 9, 33, 82, 20, 11, 200, 80, 16, 200, 37, 53, 9, 76, 176, 20, 11, 200, 77, 67, 203, 5, 53, 9, 76, 176, 20, 11, 200, 76, 178, 83, 52, 21, 9, 76, 176, 20, 11, 200, 64, 20, 129, 49, 149, 9, 76, 176, 20, 11, 200, 52, 20, 152, 37, 53, 9, 76, 176, 20, 11, 200, 45, 96, 68, 72, 21, 9, 76, 176, 20, 11, 200, 24, 19, 148, 5, 53, 9, 76, 176, 20, 12, 137, 4, 195, 166, 13, 15, 14, 9, 19, 11, 20, 11, 200, 16, 17, 1, 37, 53, 9, 76, 176, 20, 11, 200, 8, 20, 20, 37, 53, 9, 76, 176, 20, 11, 200, 5, 1, 82, 36, 241, 9, 76, 176, 20, 9, 198, 52, 85, 18, 36, 177, 82, 20, 7, 196, 24, 16, 201, 80, 20, 11, 200, 36, 225, 143, 72, 208, 84, 36, 176, 20, 7, 196, 4, 113, 78, 76, 20, 11, 200, 44, 243, 132, 60, 193, 78, 12, 80, 20, 7, 196, 48, 81, 193, 80, 20, 7, 196, 48, 242, 193, 48, 20, 0, 13, 138, 19, 11, 1, 14, 4, 1, 12, 195, 184, 19, 20, 13, 138, 13, 9, 18, 1, 11, 21, 12, 195, 184, 19, 20, 12, 201, 80, 84, 141, 36, 227, 204, 60, 114, 64, 20, 13, 138, 11, 195, 184, 7, 5, 14, 19, 9, 19, 11, 20, 8, 197, 48, 144, 197, 57, 48, 20, 8, 197, 21, 52, 197, 57, 48, 20, 14, 73, 8, 80, 67, 33, 99, 204, 48, 86, 64, 21, 0, 10, 0, 10, 67, 36, 177, 83, 35, 57, 49, 87, 0, 15, 140, 20, 18, 1, 14, 19, 16, 15, 18, 20, 195, 184, 18, 20, 9, 198, 29, 32, 86, 37, 65, 84, 20, 17, 206, 77, 84, 18, 4, 224, 84, 85, 32, 76, 37, 53, 9, 76, 176, 20, 14, 139, 1, 14, 1, 16, 195, 166, 19, 20, 9, 19, 11, 20, 9, 198, 64, 85, 9, 81, 83, 64, 20, 12, 4, 95, 2, 1, 18, 10, 69, 6, 110, 13, 0, 0, 19, 67, 16, 83, 64, 70, 6, 107, 63, 15, 70, 36, 34, 0, 81, 100, 101, 114, 32, 19, 67, 16, 83, 64, 70, 6, 107, 63, 15, 105, 36, 34, 0, 81, 104, 101, 114, 32, 12, 201, 88, 20, 133, 16, 82, 204, 5, 33, 82, 20, 9, 198, 36, 67, 204, 5, 68, 137, 20, 14, 203, 65, 54, 75, 60, 19, 129, 49, 149, 9, 76, 176, 20, 14, 203, 52, 85, 1, 48, 195, 199, 72, 17, 137, 76, 176, 20, 14, 203, 45, 34, 77, 36, 224, 76, 37, 53, 9, 76, 176, 20, 12, 201, 64, 19, 148, 60, 210, 77, 36, 177, 82, 20, 10, 199, 64, 244, 212, 49, 81, 9, 20, 20, 6, 195, 16, 83, 64, 72, 0, 13, 138, 16, 18, 195, 166, 6, 5, 11, 20, 21, 18, 20, 7, 196, 4, 96, 83, 36, 20, 9, 198, 80, 244, 148, 85, 33, 82, 20, 9, 198, 65, 35, 202, 36, 49, 82, 20, 9, 198, 36, 229, 143, 49, 97, 82, 20, 9, 198, 29, 32, 86, 37, 65, 82, 20, 9, 198, 16, 82, 193, 57, 65, 82, 20, 9, 198, 16, 19, 65, 76, 49, 82, 20, 7, 196, 32, 19, 73, 80, 20, 9, 198, 4, 209, 82, 36, 176, 78, 20, 9, 198, 52, 84, 137, 16, 144, 78, 21, 5, 130, 197, 190, 43, 0, 9, 198, 76, 240, 201, 60, 195, 199, 20, 9, 198, 25, 148, 201, 60, 195, 199, 20, 12, 201, 88, 144, 146, 4, 99, 206, 37, 53, 0, 20, 12, 201, 24, 19, 73, 48, 144, 82, 37, 65, 84, 20, 0, 16, 141, 18, 195, 184, 14, 20, 7, 5, 14, 15, 12, 15, 7, 9, 20, 9, 198, 80, 244, 130, 37, 53, 0, 20, 9, 198, 32, 244, 142, 37, 53, 0, 20, 9, 198, 45, 96, 76, 37, 65, 84, 20, 9, 198, 4, 114, 76, 37, 65, 84, 20, 9, 198, 61, 85, 18, 21, 33, 84, 20, 0, 27, 67, 24, 18, 84, 81, 107, 47, 35, 49, 112, 63, 48, 55, 6, 37, 0, 81, 97, 99, 99, 111, 109, 112, 108, 105, 32, 12, 201, 44, 243, 77, 4, 225, 1, 57, 69, 82, 20, 12, 137, 16, 18, 195, 166, 16, 1, 18, 5, 18, 20, 10, 199, 88, 149, 1, 48, 148, 205, 20, 20, 10, 199, 36, 65, 65, 48, 148, 205, 20, 20, 21, 71, 33, 145, 18, 60, 99, 201, 48, 105, 114, 70, 34, 39, 81, 6, 112, 37, 55, 0, 20, 10, 199, 80, 84, 141, 61, 53, 1, 80, 20, 0, 9, 134, 2, 9, 14, 195, 166, 18, 20, 15, 204, 44, 243, 80, 48, 83, 69, 57, 64, 82, 37, 65, 84, 20, 9, 68, 12, 128, 82, 80, 21, 0, 10, 0, 8, 197, 17, 32, 71, 60, 224, 20, 12, 201, 84, 213, 83, 36, 176, 76, 37, 65, 84, 20, 12, 201, 61, 34, 71, 36, 224, 76, 37, 65, 84, 20, 14, 139, 16, 18, 195, 166, 14, 21, 13, 5, 18, 5, 18, 20, 14, 139, 5, 21, 18, 15, 16, 195, 166, 9, 19, 5, 18, 20, 11, 136, 19, 16, 195, 184, 7, 5, 18, 9, 20, 11, 136, 13, 195, 166, 12, 11, 5, 18, 9, 20, 8, 197, 64, 84, 134, 36, 64, 20, 8, 197, 52, 244, 130, 36, 64, 20, 8, 197, 48, 146, 214, 36, 64, 20, 8, 197, 44, 20, 130, 36, 64, 20, 8, 197, 13, 144, 78, 36, 64, 20, 8, 197, 80, 19, 148, 4, 192, 20, 8, 197, 16, 83, 148, 4, 192, 20, 0, 11, 136, 15, 18, 4, 9, 14, 195, 166, 18, 20, 9, 198, 4, 229, 18, 4, 50, 84, 20, 9, 198, 8, 85, 10, 20, 229, 0, 20, 9, 198, 44, 243, 147, 20, 228, 192, 20, 13, 138, 9, 14, 1, 4, 195, 166, 11, 22, 1, 20, 20, 9, 134, 6, 195, 166, 11, 1, 12, 20, 0, 10, 199, 28, 20, 142, 37, 69, 82, 20, 20, 12, 137, 22, 9, 19, 9, 15, 14, 195, 166, 18, 20, 12, 137, 9, 13, 1, 7, 9, 14, 195, 166, 18, 20, 12, 137, 1, 18, 2, 9, 20, 18, 195, 166, 18, 20, 10, 199, 44, 243, 148, 85, 33, 82, 20, 20, 10, 199, 28, 243, 132, 60, 194, 69, 72, 20, 10, 199, 76, 177, 80, 80, 146, 197, 72, 20, 10, 199, 64, 243, 5, 52, 146, 197, 72, 20, 10, 199, 28, 83, 133, 80, 146, 197, 72, 20, 10, 199, 24, 243, 133, 80, 146, 197, 72, 20, 10, 199, 24, 19, 129, 80, 146, 197, 72, 20, 9, 198, 4, 211, 79, 56, 149, 77, 20, 10, 199, 76, 20, 132, 36, 226, 69, 56, 20, 9, 198, 20, 193, 71, 4, 224, 197, 20, 0, 7, 196, 52, 245, 15, 72, 20, 13, 138, 22, 5, 20, 5, 18, 9, 14, 195, 166, 18, 20, 9, 134, 22, 5, 12, 195, 166, 18, 20, 9, 134, 19, 1, 12, 195, 166, 18, 20, 13, 138, 4, 15, 11, 20, 18, 9, 14, 195, 166, 18, 20, 11, 200, 88, 83, 133, 72, 21, 9, 60, 224, 20, 11, 200, 76, 147, 85, 48, 21, 9, 60, 224, 20, 11, 200, 72, 84, 21, 80, 21, 9, 60, 224, 20, 11, 200, 72, 83, 143, 88, 21, 9, 60, 224, 20, 11, 200, 72, 83, 5, 28, 21, 9, 60, 224, 20, 11, 200, 65, 35, 212, 20, 181, 9, 60, 224, 20, 11, 200, 65, 35, 196, 84, 181, 9, 60, 224, 20, 11, 200, 64, 244, 21, 48, 21, 9, 60, 224, 20, 11, 200, 61, 4, 15, 76, 149, 9, 60, 224, 20, 11, 200, 36, 229, 137, 80, 21, 9, 60, 224, 20, 11, 200, 36, 228, 208, 20, 181, 9, 60, 224, 20, 11, 200, 36, 226, 9, 8, 149, 9, 60, 224, 20, 11, 200, 36, 224, 201, 80, 21, 9, 60, 224, 20, 11, 200, 28, 192, 67, 36, 21, 9, 60, 224, 20, 11, 200, 20, 209, 78, 16, 21, 9, 60, 224, 20, 11, 200, 16, 83, 5, 28, 21, 9, 60, 224, 20, 11, 200, 4, 211, 85, 56, 149, 9, 60, 224, 20, 12, 137, 8, 5, 2, 18, 195, 166, 9, 19, 11, 20, 9, 198, 21, 84, 129, 76, 145, 78, 20, 7, 196, 4, 113, 78, 80, 20, 11, 200, 32, 244, 137, 76, 243, 148, 4, 192, 20, 7, 196, 4, 147, 65, 8, 20, 0, 15, 69, 76, 18, 71, 60, 224, 87, 35, 57, 79, 106, 20, 50, 0, 14, 139, 18, 5, 1, 11, 20, 9, 15, 14, 195, 166, 18, 20, 8, 197, 21, 2, 71, 60, 224, 20, 8, 197, 72, 21, 9, 60, 224, 20, 12, 201, 44, 194, 77, 4, 181, 5, 72, 145, 76, 20, 13, 138, 195, 184, 11, 15, 12, 15, 7, 9, 19, 11, 20, 8, 197, 33, 144, 146, 36, 64, 20, 16, 69, 29, 32, 84, 36, 224, 79, 34, 110, 47, 6, 107, 66, 0, 20, 8, 197, 24, 84, 148, 36, 192, 20, 12, 201, 72, 83, 73, 56, 148, 195, 20, 228, 192, 20, 12, 201, 49, 83, 73, 56, 84, 195, 20, 228, 192, 20, 12, 201, 24, 197, 79, 72, 84, 195, 20, 228, 192, 20, 8, 197, 85, 33, 84, 4, 224, 21, 8, 197, 88, 19, 132, 4, 192, 20, 8, 197, 76, 19, 132, 4, 192, 20, 0, 11, 136, 20, 9, 20, 21, 12, 195, 166, 18, 20, 11, 136, 16, 15, 16, 21, 12, 195, 166, 18, 20, 11, 136, 13, 15, 14, 5, 20, 195, 166, 18, 20, 11, 136, 13, 15, 4, 21, 12, 195, 166, 18, 20, 11, 136, 9, 14, 19, 21, 12, 195, 166, 18, 20, 14, 139, 11, 1, 14, 1, 1, 14, 195, 166, 9, 19, 11, 20, 14, 139, 11, 1, 14, 1, 1, 14, 195, 166, 9, 19, 11, 20, 13, 202, 44, 148, 143, 65, 32, 75, 80, 146, 197, 72, 20, 0, 25, 73, 77, 21, 65, 72, 81, 1, 56, 49, 78, 87, 49, 58, 6, 36, 13, 70, 35, 12, 50, 87, 14, 50, 0, 10, 199, 44, 19, 142, 20, 197, 82, 20, 20, 10, 199, 28, 83, 133, 72, 21, 15, 72, 20, 12, 137, 19, 5, 11, 18, 5, 20, 195, 166, 18, 20, 12, 137, 13, 21, 19, 11, 21, 12, 195, 166, 18, 20, 10, 199, 44, 243, 139, 84, 34, 78, 20, 20, 14, 203, 76, 147, 80, 48, 145, 137, 44, 21, 9, 60, 224, 20, 14, 203, 72, 82, 207, 53, 1, 78, 76, 21, 9, 60, 224, 20, 14, 203, 72, 82, 207, 52, 208, 78, 16, 21, 9, 60, 224, 20, 14, 203, 72, 82, 193, 64, 149, 21, 48, 21, 9, 60, 224, 20, 14, 203, 36, 229, 5, 73, 4, 133, 80, 21, 9, 60, 224, 20, 14, 203, 20, 180, 212, 72, 20, 15, 76, 149, 9, 60, 224, 20, 10, 199, 81, 83, 142, 20, 193, 82, 20, 20, 10, 199, 4, 178, 207, 72, 65, 82, 20, 20, 11, 136, 195, 166, 20, 5, 18, 9, 19, 11, 20, 15, 140, 16, 1, 12, 195, 166, 15, 12, 9, 20, 9, 19, 11, 20, 15, 140, 13, 1, 10, 5, 19, 20, 195, 166, 20, 9, 19, 11, 20, 9, 198, 88, 19, 129, 16, 149, 77, 20, 9, 198, 56, 240, 133, 48, 149, 77, 20, 10, 199, 4, 209, 133, 80, 19, 73, 56, 20, 9, 134, 1, 14, 195, 166, 13, 9, 20, 14, 203, 81, 32, 78, 76, 49, 78, 16, 83, 148, 4, 192, 20, 0, 13, 138, 16, 1, 18, 1, 19, 9, 20, 195, 166, 18, 20, 13, 138, 8, 21, 13, 1, 14, 9, 20, 195, 166, 18, 20, 13, 138, 8, 5, 18, 5, 4, 9, 20, 195, 166, 18, 20, 13, 138, 2, 9, 14, 15, 11, 21, 12, 195, 166, 18, 20, 13, 138, 1, 21, 20, 15, 18, 9, 20, 195, 166, 18, 20, 11, 200, 72, 82, 210, 20, 21, 9, 60, 224, 20, 11, 200, 52, 245, 9, 88, 21, 9, 60, 224, 20, 11, 200, 44, 244, 21, 48, 21, 9, 60, 224, 20, 11, 200, 36, 226, 84, 36, 21, 9, 60, 224, 20, 11, 200, 16, 83, 143, 80, 21, 9, 60, 224, 20, 11, 200, 16, 81, 137, 56, 149, 9, 60, 224, 20, 11, 200, 5, 4, 15, 76, 149, 9, 60, 224, 20, 11, 200, 4, 197, 5, 72, 21, 9, 60, 224, 20, 12, 137, 16, 18, 195, 184, 10, 19, 9, 19, 11, 20, 11, 200, 64, 243, 25, 85, 33, 84, 4, 224, 21, 0, 14, 139, 16, 1, 18, 20, 9, 11, 21, 12, 195, 166, 18, 20, 14, 139, 13, 9, 12, 12, 9, 1, 18, 4, 195, 166, 18, 20, 14, 139, 13, 1, 20, 18, 9, 11, 21, 12, 195, 166, 18, 20, 8, 197, 80, 16, 140, 21, 64, 20, 8, 197, 45, 80, 137, 77, 64, 20, 8, 197, 52, 81, 9, 21, 32, 20, 8, 197, 80, 17, 198, 5, 64, 20, 8, 197, 65, 83, 19, 5, 32, 20, 0, 15, 140, 21, 14, 9, 22, 5, 18, 19, 9, 20, 195, 166, 18, 20, 15, 140, 19, 16, 5, 11, 20, 1, 11, 21, 12, 195, 166, 18, 20, 12, 201, 88, 242, 193, 9, 83, 1, 72, 149, 77, 20, 9, 198, 64, 20, 9, 76, 209, 64, 20, 9, 198, 8, 147, 9, 76, 209, 64, 20, 12, 201, 12, 192, 73, 73, 99, 217, 4, 224, 197, 20, 9, 198, 12, 244, 147, 4, 113, 64, 20, 0, 13, 138, 16, 18, 195, 166, 19, 9, 4, 9, 21, 13, 20, 12, 71, 64, 83, 148, 32, 245, 83, 20, 21, 0, 10, 0, 11, 200, 52, 147, 9, 80, 20, 137, 77, 64, 20, 11, 200, 52, 19, 137, 13, 84, 137, 77, 64, 20, 11, 200, 88, 148, 203, 61, 50, 84, 21, 64, 20, 11, 200, 77, 69, 80, 36, 66, 84, 21, 64, 20, 11, 200, 77, 65, 82, 36, 194, 84, 21, 64, 20, 11, 200, 77, 64, 66, 36, 194, 84, 21, 64, 20, 11, 200, 76, 84, 150, 36, 194, 84, 21, 64, 20, 11, 200, 45, 84, 137, 61, 50, 84, 21, 64, 20, 11, 200, 36, 229, 5, 57, 50, 84, 21, 64, 20, 11, 200, 16, 149, 133, 73, 50, 84, 21, 64, 20, 11, 200, 5, 67, 206, 4, 194, 84, 21, 64, 20, 11, 200, 4, 211, 210, 4, 194, 84, 21, 64, 20, 9, 198, 80, 19, 9, 76, 208, 78, 21, 11, 200, 72, 81, 201, 77, 68, 129, 57, 64, 20, 0, 23, 73, 77, 21, 65, 72, 81, 1, 56, 49, 64, 87, 49, 58, 6, 36, 13, 70, 35, 12, 50, 87, 0, 16, 69, 16, 148, 208, 85, 64, 70, 37, 87, 69, 6, 114, 47, 0, 20, 8, 197, 61, 32, 84, 61, 32, 20, 8, 197, 88, 147, 204, 21, 64, 20, 12, 201, 4, 178, 207, 53, 0, 71, 56, 84, 128, 20, 12, 201, 84, 226, 70, 61, 35, 73, 76, 209, 64, 20, 12, 201, 77, 84, 146, 20, 19, 9, 76, 209, 64, 20, 12, 201, 72, 17, 9, 44, 19, 9, 76, 209, 64, 20, 12, 201, 65, 32, 71, 52, 21, 9, 76, 209, 64, 20, 12, 201, 48, 144, 133, 72, 19, 9, 76, 209, 64, 20, 8, 197, 65, 35, 194, 5, 64, 20, 0, 9, 198, 65, 35, 208, 72, 145, 64, 20, 9, 198, 36, 225, 197, 56, 145, 64, 20, 9, 198, 76, 17, 9, 76, 209, 64, 20, 9, 198, 32, 243, 9, 76, 209, 64, 20, 9, 198, 5, 65, 73, 76, 209, 64, 20, 9, 198, 88, 18, 193, 56, 49, 64, 20, 9, 198, 64, 21, 18, 36, 49, 64, 20, 9, 198, 44, 17, 5, 56, 49, 64, 20, 9, 198, 4, 227, 143, 56, 49, 64, 20, 0, 14, 139, 6, 12, 195, 184, 10, 20, 5, 14, 9, 19, 20, 20, 14, 203, 72, 85, 133, 73, 50, 66, 36, 194, 84, 21, 64, 20, 14, 203, 65, 35, 198, 37, 64, 66, 36, 194, 84, 21, 64, 20, 14, 203, 44, 243, 80, 5, 66, 66, 36, 194, 84, 21, 64, 20, 14, 203, 37, 36, 129, 80, 147, 206, 4, 194, 84, 21, 64, 20, 14, 203, 4, 48, 197, 65, 64, 66, 36, 194, 84, 21, 64, 20, 0, 11, 200, 64, 84, 134, 61, 32, 84, 61, 32, 20, 11, 200, 60, 36, 197, 73, 96, 84, 61, 32, 20, 11, 200, 44, 243, 77, 85, 64, 84, 61, 32, 20, 11, 200, 44, 19, 11, 84, 192, 84, 61, 32, 20, 11, 200, 36, 225, 143, 72, 208, 84, 61, 32, 20, 11, 200, 17, 84, 12, 36, 176, 84, 61, 32, 20, 11, 200, 16, 85, 1, 36, 195, 9, 77, 64, 20, 11, 200, 16, 148, 212, 72, 144, 149, 21, 32, 20, 12, 137, 13, 1, 14, 195, 169, 18, 12, 9, 7, 20, 15, 204, 76, 83, 148, 36, 209, 78, 80, 19, 9, 76, 209, 64, 20, 9, 198, 60, 49, 65, 56, 145, 78, 20, 13, 138, 11, 195, 184, 2, 5, 14, 8, 1, 22, 14, 20, 7, 196, 5, 66, 5, 56, 20, 11, 200, 77, 81, 134, 36, 50, 69, 57, 64, 20, 11, 200, 44, 243, 139, 84, 34, 78, 5, 64, 20, 11, 200, 44, 243, 131, 20, 229, 18, 5, 64, 20, 11, 200, 4, 113, 204, 60, 209, 82, 5, 64, 20, 7, 196, 16, 82, 193, 56, 21, 9, 198, 52, 147, 137, 52, 19, 0, 20, 9, 198, 16, 145, 201, 80, 19, 0, 20, 0, 8, 197, 80, 83, 204, 60, 112, 20, 8, 197, 8, 147, 204, 60, 112, 20, 8, 197, 24, 147, 5, 72, 80, 20, 8, 197, 16, 244, 197, 72, 80, 20, 8, 197, 28, 83, 133, 76, 80, 20, 12, 201, 44, 194, 77, 4, 181, 5, 72, 145, 64, 20, 12, 201, 76, 83, 147, 84, 19, 9, 76, 209, 64, 20, 12, 201, 52, 243, 143, 64, 243, 9, 76, 209, 64, 20, 12, 201, 24, 81, 5, 72, 19, 9, 76, 209, 64, 20, 12, 201, 44, 243, 12, 20, 181, 18, 36, 49, 64, 20, 0, 9, 198, 84, 99, 204, 60, 114, 64, 20, 9, 198, 61, 67, 204, 60, 114, 64, 20, 9, 198, 21, 67, 204, 60, 114, 64, 20, 9, 198, 5, 3, 204, 60, 114, 64, 20, 13, 138, 8, 195, 184, 14, 19, 5, 18, 9, 19, 20, 20, 17, 206, 16, 145, 134, 21, 33, 78, 80, 144, 66, 36, 194, 84, 21, 64, 20, 14, 139, 15, 16, 20, 195, 166, 14, 11, 5, 12, 9, 7, 20, 9, 198, 21, 2, 68, 20, 210, 64, 20, 9, 198, 17, 84, 12, 36, 176, 84, 20, 9, 198, 13, 146, 204, 4, 208, 84, 20, 0, 9, 198, 32, 244, 148, 60, 227, 205, 20, 10, 199, 8, 150, 129, 73, 33, 82, 36, 20, 11, 136, 1, 14, 195, 166, 13, 9, 19, 11, 20, 10, 199, 16, 148, 195, 37, 3, 9, 56, 20, 9, 198, 16, 146, 207, 80, 243, 73, 20, 10, 199, 29, 147, 78, 5, 53, 9, 44, 20, 11, 67, 76, 149, 0, 87, 6, 37, 47, 0, 72, 0, 11, 200, 20, 208, 143, 84, 50, 21, 72, 80, 20, 11, 200, 5, 52, 217, 72, 147, 204, 60, 112, 20, 9, 198, 76, 245, 83, 4, 99, 206, 20, 11, 200, 29, 34, 77, 5, 52, 197, 72, 80, 20, 11, 200, 88, 148, 143, 48, 241, 201, 76, 176, 20, 11, 200, 80, 83, 5, 24, 243, 137, 76, 176, 20, 11, 200, 73, 83, 143, 48, 241, 201, 76, 176, 20, 11, 200, 53, 146, 207, 48, 241, 201, 76, 176, 20, 11, 200, 44, 20, 22, 21, 33, 9, 76, 176, 20, 11, 200, 36, 65, 79, 48, 241, 201, 76, 176, 20, 11, 200, 24, 147, 15, 48, 241, 201, 76, 176, 20, 11, 200, 16, 83, 65, 28, 241, 201, 76, 176, 20, 12, 137, 3, 195, 166, 19, 1, 18, 9, 19, 11, 20, 12, 137, 1, 18, 1, 13, 195, 166, 9, 19, 11, 20, 11, 200, 28, 20, 212, 72, 243, 143, 52, 144, 20, 15, 204, 81, 32, 68, 37, 66, 79, 56, 19, 9, 76, 209, 64, 20, 15, 204, 32, 84, 141, 4, 100, 143, 16, 149, 9, 76, 209, 64, 20, 9, 198, 45, 35, 193, 80, 145, 78, 20, 7, 196, 72, 243, 65, 56, 21, 0, 12, 201, 45, 34, 77, 36, 227, 204, 60, 114, 64, 20, 12, 201, 44, 194, 77, 5, 67, 204, 60, 114, 64, 20, 12, 201, 32, 84, 144, 21, 67, 204, 60, 114, 64, 20, 8, 197, 72, 21, 137, 56, 80, 20, 17, 142, 16, 21, 4, 19, 5, 12, 195, 184, 10, 5, 18, 12, 9, 7, 20, 13, 138, 6, 15, 18, 6, 195, 184, 18, 9, 19, 11, 20, 12, 201, 32, 84, 141, 4, 100, 143, 16, 149, 0, 20, 8, 197, 28, 84, 212, 36, 176, 20, 12, 201, 72, 81, 140, 20, 181, 5, 72, 85, 0, 20, 0, 14, 139, 1, 14, 195, 166, 19, 20, 5, 20, 9, 19, 11, 20, 12, 201, 77, 84, 208, 20, 228, 207, 72, 149, 77, 20, 12, 201, 44, 243, 147, 37, 53, 15, 72, 149, 77, 20, 9, 198, 4, 224, 84, 60, 210, 64, 20, 0, 6, 195, 4, 181, 84, 20, 10, 199, 36, 212, 5, 72, 21, 15, 72, 20, 10, 199, 20, 213, 76, 28, 21, 15, 72, 20, 9, 198, 56, 244, 212, 4, 193, 201, 20, 10, 199, 64, 243, 25, 4, 225, 18, 36, 20, 15, 140, 19, 25, 14, 195, 166, 19, 20, 5, 20, 9, 19, 11, 20, 15, 140, 11, 9, 14, 195, 166, 19, 20, 5, 20, 9, 19, 11, 20, 14, 203, 33, 83, 65, 56, 34, 79, 48, 241, 201, 76, 176, 20, 10, 199, 44, 243, 12, 20, 114, 65, 56, 20, 0, 11, 200, 60, 101, 1, 48, 211, 204, 60, 112, 20, 9, 198, 64, 150, 154, 36, 177, 82, 20, 9, 198, 36, 228, 208, 36, 49, 82, 20, 9, 198, 20, 180, 197, 72, 49, 82, 20, 9, 198, 17, 84, 12, 36, 49, 82, 20, 11, 200, 8, 20, 212, 5, 33, 5, 72, 80, 20, 16, 141, 195, 166, 7, 25, 16, 20, 15, 12, 15, 7, 9, 19, 11, 20, 11, 200, 77, 68, 129, 80, 81, 201, 76, 176, 20, 11, 200, 28, 83, 137, 80, 149, 137, 76, 176, 20, 11, 200, 17, 148, 204, 20, 181, 9, 76, 176, 20, 11, 200, 32, 85, 5, 72, 243, 143, 52, 144, 20, 7, 196, 88, 242, 193, 48, 20, 7, 196, 64, 242, 193, 48, 20, 7, 196, 24, 242, 193, 48, 20, 11, 200, 64, 192, 84, 52, 83, 129, 28, 80, 20, 0, 15, 5, 23, 3, 39, 5, 20, 82, 6, 36, 87, 36, 13, 70, 0, 12, 201, 89, 83, 11, 4, 227, 204, 60, 114, 64, 20, 12, 201, 28, 84, 143, 57, 67, 204, 60, 114, 64, 20, 9, 198, 72, 17, 9, 60, 195, 199, 20, 9, 198, 24, 147, 13, 60, 195, 199, 20, 13, 138, 1, 20, 8, 5, 14, 195, 166, 9, 19, 11, 20, 12, 201, 24, 20, 200, 36, 243, 133, 72, 85, 0, 20, 0, 10, 135, 195, 184, 11, 15, 12, 15, 7, 20, 9, 198, 76, 192, 86, 37, 53, 0, 20, 9, 198, 16, 144, 71, 72, 19, 64, 20, 12, 137, 16, 18, 195, 166, 13, 9, 5, 18, 5, 20, 9, 198, 65, 35, 194, 48, 83, 64, 20, 9, 198, 52, 18, 211, 36, 208, 76, 20, 0, 14, 5, 23, 3, 39, 5, 18, 82, 6, 36, 87, 36, 112, 0, 24, 73, 77, 21, 65, 72, 81, 1, 56, 49, 82, 87, 49, 58, 6, 36, 13, 70, 35, 12, 50, 87, 112, 0, 10, 199, 80, 83, 5, 60, 195, 199, 36, 20, 10, 199, 80, 82, 206, 60, 195, 199, 36, 20, 10, 199, 56, 85, 82, 60, 195, 199, 36, 20, 10, 199, 52, 244, 134, 60, 195, 199, 36, 20, 10, 199, 52, 85, 18, 60, 195, 199, 36, 20, 10, 199, 32, 20, 12, 60, 195, 199, 36, 20, 15, 140, 1, 18, 11, 195, 166, 15, 12, 15, 7, 9, 19, 11, 20, 12, 201, 20, 193, 75, 81, 35, 206, 36, 177, 82, 20, 12, 201, 65, 33, 83, 9, 149, 5, 72, 144, 78, 20, 7, 2, 95, 5, 36, 12, 0, 0, 7, 196, 48, 19, 69, 48, 20, 9, 198, 72, 82, 70, 36, 49, 82, 20, 9, 198, 52, 18, 211, 36, 209, 82, 20, 9, 198, 17, 84, 12, 36, 177, 82, 20, 9, 198, 5, 68, 143, 24, 145, 82, 20, 9, 198, 21, 35, 212, 36, 177, 82, 20, 7, 196, 64, 85, 9, 80, 20, 7, 196, 5, 81, 9, 80, 20, 7, 196, 28, 83, 65, 48, 20, 0, 9, 198, 28, 83, 77, 60, 195, 199, 20, 11, 136, 19, 195, 166, 20, 20, 5, 18, 9, 20, 11, 136, 14, 195, 165, 4, 12, 5, 18, 9, 20, 0, 13, 202, 44, 20, 129, 45, 65, 82, 60, 195, 199, 36, 20, 12, 137, 19, 11, 195, 166, 14, 4, 5, 18, 9, 20, 12, 137, 2, 18, 195, 166, 14, 4, 5, 18, 9, 20, 7, 2, 95, 9, 37, 12, 0, 0, 12, 201, 77, 148, 212, 20, 208, 84, 36, 177, 82, 20, 12, 201, 57, 83, 73, 76, 208, 84, 36, 177, 82, 20, 12, 201, 44, 148, 143, 52, 19, 148, 36, 177, 82, 20, 12, 201, 44, 20, 137, 76, 208, 84, 36, 177, 82, 20, 12, 201, 5, 53, 9, 28, 208, 84, 36, 177, 82, 20, 10, 199, 77, 64, 76, 4, 181, 9, 80, 20, 10, 199, 44, 243, 12, 20, 114, 65, 48, 20, 0, 13, 138, 4, 195, 166, 13, 15, 14, 9, 19, 5, 18, 20, 11, 200, 77, 81, 134, 36, 50, 69, 57, 48, 20, 0, 14, 139, 195, 184, 11, 15, 14, 15, 13, 9, 19, 5, 18, 20, 7, 196, 4, 113, 82, 20, 20, 17, 70, 24, 243, 132, 4, 229, 0, 81, 112, 66, 70, 6, 110, 66, 0, 20, 9, 198, 72, 80, 76, 37, 48, 66, 20, 9, 68, 81, 83, 133, 72, 21, 0, 10, 0, 17, 69, 40, 20, 135, 60, 224, 89, 57, 110, 34, 79, 6, 112, 66, 0, 20, 9, 198, 77, 64, 84, 84, 84, 133, 20, 9, 198, 44, 19, 143, 56, 84, 133, 20, 8, 197, 76, 244, 132, 36, 224, 20, 8, 197, 64, 82, 212, 36, 224, 20, 13, 202, 24, 244, 130, 73, 81, 197, 72, 148, 205, 20, 20, 8, 197, 65, 35, 208, 4, 224, 21, 0, 9, 198, 80, 245, 67, 32, 84, 128, 20, 9, 198, 76, 147, 85, 48, 84, 128, 20, 9, 198, 72, 83, 5, 28, 84, 128, 20, 9, 198, 72, 81, 133, 72, 84, 128, 20, 9, 198, 72, 81, 9, 28, 84, 128, 20, 9, 198, 61, 5, 9, 52, 84, 128, 20, 9, 198, 36, 229, 137, 80, 84, 128, 20, 9, 198, 36, 224, 201, 80, 84, 128, 20, 9, 198, 32, 243, 143, 72, 84, 128, 20, 9, 198, 32, 21, 129, 72, 84, 128, 20, 9, 198, 29, 32, 83, 76, 84, 128, 20, 9, 198, 16, 85, 143, 88, 84, 128, 20, 9, 198, 16, 83, 5, 28, 84, 128, 20, 9, 198, 16, 80, 201, 52, 84, 128, 20, 9, 198, 12, 128, 82, 28, 84, 128, 20, 9, 198, 12, 128, 78, 28, 84, 128, 20, 9, 198, 9, 32, 73, 76, 84, 128, 20, 9, 198, 4, 197, 5, 72, 84, 128, 20, 9, 198, 4, 69, 137, 76, 84, 128, 20, 9, 198, 48, 19, 73, 56, 20, 128, 20, 0, 6, 195, 85, 48, 64, 17, 10, 199, 72, 85, 143, 49, 65, 82, 20, 20, 10, 199, 24, 244, 141, 5, 65, 82, 20, 20, 10, 199, 60, 36, 212, 21, 68, 137, 44, 20, 12, 201, 36, 225, 9, 24, 97, 82, 20, 229, 0, 20, 0, 11, 200, 77, 80, 150, 20, 229, 9, 60, 224, 20, 11, 200, 65, 35, 208, 61, 37, 9, 60, 224, 20, 7, 196, 88, 243, 69, 72, 20, 12, 201, 16, 147, 69, 57, 50, 79, 56, 84, 133, 20, 11, 200, 24, 20, 195, 37, 53, 15, 36, 64, 20, 11, 200, 8, 83, 133, 16, 146, 212, 36, 224, 20, 9, 198, 17, 80, 140, 4, 229, 0, 20, 0, 12, 201, 81, 32, 78, 76, 69, 75, 80, 244, 128, 20, 12, 201, 72, 85, 137, 80, 19, 9, 76, 84, 128, 20, 12, 201, 52, 243, 143, 64, 243, 9, 76, 84, 128, 20, 12, 201, 32, 82, 212, 60, 116, 129, 24, 84, 128, 20, 12, 201, 16, 83, 73, 77, 50, 79, 56, 84, 128, 20, 12, 201, 5, 85, 15, 52, 21, 9, 76, 84, 128, 20, 8, 197, 64, 148, 212, 60, 192, 20, 11, 136, 21, 18, 195, 166, 13, 9, 19, 11, 20, 8, 197, 88, 147, 204, 36, 224, 20, 8, 197, 8, 133, 84, 4, 224, 20, 8, 197, 8, 133, 84, 4, 224, 21, 8, 197, 72, 149, 21, 4, 192, 20, 0, 11, 200, 21, 2, 68, 36, 20, 203, 61, 0, 20, 9, 198, 52, 21, 1, 16, 244, 128, 20, 9, 198, 45, 84, 129, 80, 244, 128, 20, 9, 198, 81, 32, 83, 76, 84, 128, 20, 9, 198, 77, 84, 16, 48, 84, 128, 20, 9, 198, 72, 81, 21, 12, 84, 128, 20, 9, 198, 53, 83, 11, 80, 84, 128, 20, 9, 198, 36, 226, 137, 12, 84, 128, 20, 9, 198, 36, 226, 9, 8, 84, 128, 20, 9, 198, 36, 225, 140, 84, 84, 128, 20, 9, 198, 36, 225, 137, 12, 84, 128, 20, 9, 198, 36, 115, 143, 72, 84, 128, 20, 9, 198, 17, 81, 76, 48, 84, 128, 20, 9, 198, 16, 84, 137, 88, 84, 128, 20, 9, 198, 16, 81, 137, 56, 84, 128, 20, 9, 198, 16, 81, 21, 12, 84, 128, 20, 9, 198, 16, 81, 9, 44, 84, 128, 20, 9, 198, 16, 81, 9, 12, 84, 128, 20, 9, 198, 4, 97, 137, 12, 84, 128, 20, 9, 198, 4, 69, 143, 44, 84, 128, 20, 9, 198, 8, 145, 137, 48, 20, 128, 20, 11, 70, 76, 48, 78, 56, 84, 128, 21, 0, 10, 0, 10, 199, 52, 18, 213, 48, 21, 21, 72, 20, 10, 199, 64, 192, 71, 36, 21, 15, 72, 20, 10, 199, 16, 84, 133, 29, 83, 5, 72, 20, 0, 11, 200, 72, 81, 146, 4, 181, 9, 60, 224, 20, 11, 200, 44, 243, 150, 20, 229, 9, 60, 224, 20, 11, 200, 36, 228, 197, 45, 66, 67, 36, 64, 20, 11, 200, 8, 18, 212, 21, 34, 67, 36, 64, 20, 11, 200, 29, 80, 84, 20, 208, 76, 4, 224, 20, 11, 200, 76, 82, 83, 52, 241, 210, 4, 96, 20, 11, 200, 60, 49, 65, 56, 241, 210, 4, 96, 20, 11, 200, 44, 20, 132, 36, 241, 210, 4, 96, 20, 11, 200, 8, 144, 140, 36, 241, 210, 4, 96, 20, 0, 8, 197, 76, 82, 212, 61, 32, 20, 12, 201, 80, 245, 1, 48, 148, 193, 80, 244, 128, 20, 12, 201, 72, 84, 212, 5, 84, 129, 80, 244, 128, 20, 12, 201, 44, 243, 15, 56, 148, 193, 80, 244, 128, 20, 12, 201, 44, 21, 1, 49, 148, 193, 80, 244, 128, 20, 12, 201, 81, 34, 86, 36, 19, 9, 76, 84, 128, 20, 12, 201, 81, 32, 85, 52, 21, 9, 76, 84, 128, 20, 12, 201, 77, 66, 71, 52, 21, 9, 76, 84, 128, 20, 12, 201, 76, 82, 211, 84, 19, 9, 76, 84, 128, 20, 12, 201, 56, 243, 73, 56, 19, 9, 76, 84, 128, 20, 12, 201, 53, 84, 201, 44, 19, 9, 76, 84, 128, 20, 12, 201, 48, 144, 133, 72, 19, 9, 76, 84, 128, 20, 12, 201, 40, 245, 82, 56, 19, 9, 76, 84, 128, 20, 12, 201, 36, 211, 79, 8, 147, 9, 76, 84, 128, 20, 12, 201, 32, 245, 141, 21, 53, 5, 72, 84, 128, 20, 12, 201, 32, 243, 79, 48, 241, 201, 76, 84, 128, 20, 12, 201, 8, 84, 212, 36, 19, 9, 76, 84, 128, 20, 8, 197, 4, 195, 9, 21, 32, 20, 12, 201, 8, 244, 148, 4, 67, 208, 80, 84, 128, 20, 9, 198, 44, 195, 214, 56, 84, 137, 20, 12, 201, 29, 32, 77, 52, 21, 9, 44, 84, 128, 20, 12, 201, 24, 193, 71, 52, 21, 9, 44, 84, 128, 20, 12, 201, 16, 21, 1, 52, 21, 9, 44, 84, 128, 20, 8, 197, 25, 33, 71, 5, 64, 20, 0, 9, 198, 33, 148, 14, 61, 49, 64, 20, 15, 140, 16, 18, 195, 166, 16, 1, 18, 1, 20, 9, 15, 14, 20, 9, 198, 24, 147, 133, 77, 49, 64, 20, 9, 198, 4, 35, 206, 56, 83, 148, 20, 9, 198, 17, 80, 140, 20, 19, 148, 20, 0, 10, 199, 24, 244, 141, 21, 34, 78, 28, 20, 6, 195, 80, 147, 0, 76, 6, 195, 88, 83, 0, 76, 0, 11, 136, 7, 18, 195, 166, 3, 9, 19, 20, 20, 17, 142, 16, 18, 195, 166, 14, 21, 13, 5, 18, 1, 20, 9, 15, 14, 20, 11, 200, 24, 19, 19, 36, 98, 75, 5, 64, 20, 0, 8, 197, 16, 85, 137, 21, 32, 20, 9, 198, 76, 225, 68, 44, 84, 137, 20, 12, 201, 4, 68, 203, 36, 195, 5, 48, 145, 192, 20, 12, 201, 76, 82, 211, 84, 19, 9, 76, 209, 64, 20, 9, 198, 29, 33, 86, 36, 225, 5, 20, 12, 201, 61, 48, 201, 48, 195, 199, 72, 17, 128, 20, 12, 201, 20, 229, 18, 21, 4, 133, 56, 19, 148, 20, 6, 195, 88, 81, 0, 76, 0, 10, 66, 92, 48, 82, 6, 36, 87, 36, 0, 9, 198, 56, 243, 73, 56, 83, 0, 20, 9, 198, 64, 20, 129, 76, 243, 0, 20, 9, 198, 72, 147, 69, 77, 49, 64, 20, 14, 139, 6, 1, 18, 9, 19, 195, 166, 9, 19, 13, 5, 20, 9, 198, 36, 224, 201, 16, 83, 148, 20, 9, 198, 29, 32, 68, 36, 83, 148, 20, 9, 198, 16, 242, 213, 52, 83, 148, 20, 9, 198, 48, 144, 133, 72, 19, 0, 20, 9, 198, 28, 192, 67, 36, 19, 0, 20, 0, 0, 11, 200, 44, 243, 80, 36, 192, 84, 61, 32, 20, 14, 70, 8, 82, 71, 56, 85, 0, 69, 36, 66, 36, 0, 66, 7, 196, 72, 242, 197, 72, 20, 11, 200, 44, 243, 148, 72, 144, 149, 21, 32, 20, 9, 198, 24, 18, 212, 60, 145, 0, 20, 9, 198, 24, 21, 143, 72, 149, 0, 20, 9, 198, 4, 181, 129, 88, 149, 0, 20, 16, 141, 195, 166, 11, 22, 9, 12, 9, 2, 18, 9, 19, 13, 5, 20, 15, 204, 76, 83, 147, 5, 66, 79, 56, 19, 9, 76, 209, 64, 20, 9, 198, 21, 68, 149, 72, 145, 78, 20, 9, 198, 29, 32, 83, 76, 21, 0, 20, 9, 198, 16, 83, 5, 28, 21, 0, 20, 0, 9, 198, 16, 144, 83, 44, 244, 0, 20, 8, 197, 5, 96, 78, 12, 80, 20, 8, 197, 76, 181, 76, 48, 80, 76, 0, 20, 67, 16, 82, 129, 70, 36, 89, 57, 35, 15, 6, 82, 114, 0, 44, 81, 118, 117, 32, 9, 198, 24, 19, 148, 5, 50, 64, 20, 14, 139, 13, 1, 12, 20, 7, 195, 184, 18, 5, 18, 9, 20, 9, 198, 52, 85, 18, 61, 3, 204, 20, 0, 12, 137, 22, 15, 12, 20, 9, 7, 195, 184, 18, 20, 10, 199, 72, 80, 133, 48, 194, 79, 56, 20, 12, 201, 77, 3, 206, 80, 19, 137, 80, 85, 0, 20, 10, 199, 72, 81, 210, 20, 66, 69, 72, 20, 10, 199, 64, 146, 193, 57, 65, 82, 36, 20, 10, 199, 24, 245, 15, 52, 85, 18, 36, 20, 10, 199, 24, 147, 9, 77, 65, 82, 36, 20, 10, 199, 8, 145, 207, 81, 65, 82, 36, 20, 10, 199, 5, 37, 9, 77, 65, 82, 36, 20, 10, 199, 44, 243, 5, 72, 146, 197, 72, 20, 10, 199, 56, 20, 139, 60, 208, 78, 36, 20, 10, 199, 61, 32, 78, 28, 80, 68, 20, 20, 0, 7, 196, 72, 85, 21, 72, 20, 11, 200, 44, 20, 132, 36, 243, 15, 28, 144, 20, 11, 200, 64, 83, 1, 72, 115, 206, 36, 80, 20, 20, 145, 1, 6, 22, 195, 166, 18, 7, 5, 13, 5, 11, 1, 14, 9, 19, 13, 5, 20, 11, 136, 16, 195, 166, 4, 15, 6, 9, 12, 20, 0, 30, 69, 69, 82, 67, 32, 80, 49, 37, 89, 15, 55, 39, 34, 6, 107, 12, 50, 12, 0, 81, 108, 111, 114, 114, 97, 105, 110, 101, 32, 10, 135, 12, 5, 11, 20, 195, 184, 18, 20, 15, 140, 13, 1, 14, 195, 184, 22, 18, 5, 18, 9, 14, 7, 20, 9, 198, 28, 84, 141, 4, 226, 69, 20, 9, 198, 12, 84, 133, 52, 243, 137, 20, 8, 197, 56, 245, 137, 12, 80, 20, 8, 197, 64, 19, 129, 16, 80, 20, 8, 197, 56, 18, 129, 16, 80, 20, 15, 2, 95, 33, 40, 70, 51, 112, 69, 87, 47, 36, 57, 50, 0, 0, 20, 67, 4, 195, 5, 108, 55, 106, 15, 87, 47, 6, 36, 0, 81, 115, 116, 101, 103, 32, 16, 141, 16, 18, 195, 166, 19, 5, 18, 22, 5, 18, 9, 14, 7, 20, 16, 141, 4, 195, 166, 13, 15, 14, 9, 19, 5, 18, 9, 14, 7, 20, 13, 202, 80, 147, 6, 61, 35, 1, 16, 83, 9, 28, 20, 9, 198, 56, 245, 137, 12, 144, 84, 20, 9, 198, 24, 16, 146, 36, 176, 84, 20, 0, 13, 138, 9, 14, 6, 5, 11, 20, 9, 195, 184, 19, 20, 12, 201, 76, 243, 9, 16, 20, 137, 80, 85, 0, 20, 12, 201, 72, 81, 213, 48, 20, 137, 80, 85, 0, 20, 17, 142, 195, 184, 11, 15, 14, 15, 13, 9, 19, 5, 18, 9, 14, 7, 20, 13, 138, 20, 18, 195, 166, 14, 5, 18, 9, 14, 7, 20, 9, 198, 45, 84, 5, 72, 147, 135, 20, 10, 199, 44, 244, 212, 84, 210, 69, 72, 20, 10, 199, 60, 208, 146, 100, 65, 82, 36, 20, 10, 199, 52, 20, 203, 36, 225, 82, 36, 20, 10, 199, 45, 32, 75, 36, 193, 82, 36, 20, 12, 201, 81, 32, 78, 77, 97, 83, 80, 149, 0, 20, 12, 201, 52, 84, 207, 64, 245, 1, 52, 145, 78, 20, 10, 199, 80, 19, 80, 60, 224, 68, 20, 20, 10, 199, 44, 243, 15, 56, 224, 68, 20, 20, 0, 13, 138, 9, 14, 19, 16, 5, 11, 20, 195, 184, 18, 20, 11, 200, 52, 85, 15, 16, 243, 15, 28, 144, 20, 11, 200, 45, 34, 83, 80, 243, 15, 28, 144, 20, 11, 200, 20, 229, 15, 52, 243, 15, 28, 144, 20, 15, 204, 16, 83, 132, 72, 242, 210, 60, 227, 204, 60, 114, 64, 20, 9, 198, 36, 225, 12, 60, 113, 82, 20, 9, 198, 24, 16, 146, 36, 177, 82, 20, 9, 198, 20, 112, 76, 37, 49, 82, 20, 11, 200, 16, 145, 148, 60, 225, 197, 72, 80, 20, 9, 198, 16, 84, 18, 36, 209, 82, 20, 9, 198, 16, 81, 143, 72, 209, 82, 20, 9, 198, 4, 227, 196, 37, 49, 82, 20, 11, 200, 24, 244, 141, 100, 225, 5, 72, 144, 20, 9, 198, 37, 35, 206, 36, 177, 82, 20, 11, 200, 44, 243, 21, 52, 32, 82, 36, 80, 20, 11, 200, 44, 19, 5, 56, 64, 82, 36, 80, 20, 21, 72, 80, 244, 148, 20, 195, 9, 56, 144, 47, 112, 47, 13, 55, 6, 37, 50, 37, 0, 20, 7, 196, 88, 148, 137, 48, 20, 9, 198, 52, 20, 143, 44, 176, 78, 20, 8, 67, 76, 243, 135, 21, 0, 10, 0, 14, 139, 1, 11, 21, 16, 21, 14, 11, 20, 195, 184, 18, 20, 15, 140, 7, 18, 195, 166, 3, 9, 19, 5, 18, 9, 14, 7, 20, 9, 198, 44, 192, 77, 52, 84, 137, 20, 9, 198, 9, 38, 71, 28, 84, 137, 20, 9, 198, 56, 18, 86, 37, 51, 69, 20, 13, 70, 20, 228, 197, 52, 35, 5, 21, 102, 114, 0, 10, 0, 9, 198, 77, 147, 132, 72, 243, 64, 20, 12, 201, 72, 81, 201, 77, 68, 133, 72, 147, 135, 20, 12, 201, 61, 34, 197, 77, 68, 133, 72, 147, 135, 20, 12, 201, 44, 243, 80, 20, 228, 197, 72, 147, 135, 20, 12, 201, 36, 225, 137, 49, 68, 133, 72, 147, 135, 20, 12, 201, 36, 195, 21, 77, 68, 133, 72, 147, 135, 20, 12, 201, 4, 208, 76, 28, 19, 69, 72, 147, 135, 20, 9, 198, 88, 19, 129, 16, 147, 128, 20, 9, 198, 52, 83, 1, 52, 147, 128, 20, 9, 198, 37, 64, 76, 36, 83, 128, 20, 0, 19, 67, 16, 83, 128, 70, 6, 107, 50, 15, 105, 36, 34, 0, 81, 104, 101, 114, 32, 19, 67, 16, 83, 128, 70, 6, 107, 50, 15, 70, 36, 34, 0, 81, 100, 101, 114, 32, 16, 141, 3, 8, 5, 6, 18, 5, 4, 1, 11, 20, 195, 184, 18, 20, 10, 199, 80, 21, 84, 60, 195, 199, 36, 20, 10, 199, 76, 240, 201, 60, 195, 199, 36, 20, 10, 199, 76, 83, 73, 60, 195, 199, 36, 20, 10, 199, 65, 54, 75, 60, 195, 199, 36, 20, 10, 199, 33, 145, 18, 60, 195, 199, 36, 20, 10, 199, 25, 148, 201, 60, 195, 199, 36, 20, 10, 199, 21, 70, 77, 60, 195, 199, 36, 20, 12, 201, 45, 38, 83, 80, 19, 12, 37, 49, 82, 20, 12, 201, 32, 244, 208, 37, 64, 76, 37, 49, 82, 20, 10, 199, 84, 197, 9, 52, 21, 21, 52, 20, 10, 199, 5, 85, 15, 52, 240, 137, 48, 20, 10, 135, 13, 195, 166, 18, 11, 1, 20, 20, 11, 70, 72, 86, 78, 60, 193, 19, 21, 0, 10, 10, 67, 16, 83, 128, 70, 107, 50, 0, 72, 0, 9, 198, 72, 80, 197, 57, 49, 82, 20, 9, 198, 44, 243, 135, 73, 81, 82, 20, 12, 201, 77, 6, 84, 76, 194, 75, 44, 84, 137, 20, 12, 201, 32, 243, 204, 36, 112, 78, 37, 51, 69, 20, 12, 201, 25, 33, 85, 16, 144, 78, 37, 51, 69, 20, 12, 201, 8, 20, 148, 32, 144, 78, 37, 51, 69, 20, 12, 201, 4, 209, 82, 36, 176, 78, 37, 51, 69, 20, 7, 196, 61, 35, 129, 80, 20, 9, 198, 5, 53, 18, 4, 176, 78, 21, 20, 4, 95, 3, 1, 16, 87, 47, 39, 112, 47, 15, 69, 39, 40, 87, 47, 35, 58, 0, 0, 9, 198, 104, 144, 133, 48, 147, 133, 20, 9, 198, 76, 243, 129, 80, 147, 133, 20, 14, 139, 16, 18, 195, 166, 10, 21, 4, 9, 3, 5, 18, 20, 9, 198, 76, 213, 71, 48, 84, 137, 20, 12, 201, 44, 20, 130, 60, 194, 78, 21, 83, 64, 20, 9, 198, 85, 67, 208, 37, 51, 69, 20, 9, 198, 72, 80, 76, 37, 51, 69, 20, 9, 198, 56, 244, 132, 37, 51, 69, 20, 9, 198, 21, 35, 212, 37, 51, 69, 20, 9, 198, 17, 80, 76, 37, 51, 69, 20, 11, 70, 16, 80, 68, 48, 147, 133, 21, 0, 10, 0, 9, 198, 44, 21, 84, 36, 243, 128, 20, 12, 201, 84, 226, 70, 61, 35, 69, 72, 147, 135, 20, 12, 201, 77, 65, 78, 12, 147, 5, 72, 147, 135, 20, 12, 201, 52, 19, 137, 65, 83, 5, 72, 147, 135, 20, 12, 201, 48, 81, 201, 80, 147, 69, 72, 147, 135, 20, 12, 201, 44, 243, 132, 20, 228, 197, 72, 147, 135, 20, 12, 201, 44, 243, 80, 72, 147, 69, 72, 147, 135, 20, 12, 201, 44, 192, 85, 77, 83, 5, 72, 147, 135, 20, 12, 201, 44, 20, 148, 60, 227, 133, 72, 147, 135, 20, 12, 201, 44, 19, 148, 60, 227, 133, 72, 147, 135, 20, 12, 201, 16, 148, 208, 20, 228, 197, 72, 147, 135, 20, 12, 201, 13, 84, 20, 85, 35, 133, 72, 147, 135, 20, 12, 201, 5, 52, 201, 52, 147, 5, 72, 147, 135, 20, 12, 201, 4, 178, 213, 53, 83, 5, 72, 147, 135, 20, 9, 198, 5, 68, 129, 104, 147, 128, 20, 9, 198, 5, 32, 66, 36, 83, 128, 20, 9, 198, 80, 144, 133, 80, 19, 128, 20, 9, 198, 4, 33, 83, 76, 147, 128, 20, 9, 198, 52, 83, 79, 72, 144, 76, 20, 0, 12, 201, 44, 20, 129, 45, 65, 82, 37, 49, 82, 20, 12, 201, 20, 97, 133, 45, 66, 86, 37, 49, 82, 20, 12, 201, 12, 243, 80, 85, 65, 82, 37, 49, 82, 20, 12, 201, 4, 209, 82, 36, 176, 78, 37, 49, 82, 20, 10, 199, 5, 81, 9, 80, 244, 137, 20, 20, 10, 199, 84, 226, 79, 56, 148, 205, 20, 20, 10, 199, 76, 21, 1, 56, 148, 205, 20, 20, 10, 199, 48, 240, 130, 100, 148, 205, 20, 20, 15, 204, 29, 37, 78, 17, 69, 137, 28, 144, 78, 37, 51, 69, 20, 10, 199, 77, 66, 77, 84, 192, 78, 76, 20, 8, 67, 92, 244, 132, 21, 0, 10, 6, 195, 32, 84, 128, 72, 0, 17, 142, 16, 18, 195, 166, 11, 22, 1, 12, 9, 6, 9, 3, 5, 18, 20, 12, 201, 77, 147, 132, 36, 176, 76, 37, 51, 69, 20, 12, 201, 52, 21, 5, 72, 144, 76, 37, 51, 69, 20, 12, 201, 36, 225, 129, 57, 66, 76, 37, 51, 69, 20, 12, 201, 36, 212, 5, 72, 144, 76, 37, 51, 69, 20, 7, 196, 17, 84, 129, 8, 20, 11, 2, 95, 46, 48, 111, 66, 47, 111, 63, 0, 0, 9, 198, 28, 83, 133, 72, 84, 133, 20, 9, 198, 5, 34, 201, 88, 84, 133, 20, 8, 197, 4, 224, 66, 60, 192, 20, 8, 197, 81, 145, 143, 36, 64, 20, 8, 197, 64, 19, 13, 36, 224, 20, 15, 69, 76, 84, 129, 36, 192, 87, 36, 34, 6, 35, 57, 0, 20, 12, 201, 52, 21, 82, 21, 64, 78, 36, 83, 128, 20, 8, 197, 64, 84, 137, 4, 192, 20, 8, 197, 56, 244, 141, 4, 192, 20, 8, 197, 52, 19, 149, 4, 192, 20, 15, 2, 95, 45, 69, 37, 50, 50, 36, 87, 70, 34, 35, 37, 0, 0, 9, 198, 20, 161, 75, 80, 244, 128, 20, 9, 198, 80, 149, 21, 48, 84, 128, 20, 9, 198, 72, 83, 143, 88, 84, 128, 20, 9, 198, 64, 192, 71, 36, 84, 128, 20, 9, 198, 48, 147, 73, 80, 84, 128, 20, 9, 198, 20, 208, 76, 40, 84, 128, 20, 9, 198, 4, 99, 5, 88, 84, 128, 20, 13, 202, 77, 80, 138, 20, 181, 9, 88, 148, 205, 20, 20, 13, 202, 64, 20, 139, 36, 228, 207, 56, 148, 205, 20, 20, 9, 198, 80, 19, 135, 20, 228, 192, 20, 9, 198, 76, 19, 79, 88, 20, 128, 20, 9, 198, 72, 148, 201, 44, 16, 128, 20, 9, 198, 44, 243, 147, 80, 16, 128, 20, 11, 2, 95, 44, 49, 6, 39, 63, 35, 12, 0, 0, 12, 67, 53, 36, 192, 63, 36, 87, 36, 87, 0, 25, 10, 199, 28, 83, 194, 36, 243, 15, 28, 20, 10, 199, 80, 18, 206, 20, 211, 9, 28, 20, 10, 199, 16, 144, 76, 60, 114, 83, 44, 20, 15, 204, 36, 229, 5, 48, 193, 75, 81, 80, 76, 37, 51, 69, 20, 10, 199, 20, 180, 197, 53, 3, 1, 72, 20, 10, 67, 88, 20, 128, 82, 110, 34, 0, 76, 11, 67, 16, 84, 128, 70, 107, 34, 0, 76, 72, 9, 2, 95, 51, 47, 51, 6, 36, 0, 0, 11, 200, 32, 244, 147, 20, 228, 201, 4, 224, 20, 8, 2, 95, 50, 47, 6, 39, 0, 0, 9, 198, 25, 37, 75, 80, 244, 197, 20, 12, 201, 77, 147, 139, 72, 85, 9, 76, 84, 128, 20, 12, 201, 77, 65, 78, 60, 116, 129, 24, 84, 128, 20, 12, 201, 72, 82, 193, 64, 149, 21, 48, 84, 128, 20, 12, 201, 64, 19, 1, 80, 19, 9, 76, 84, 128, 20, 12, 201, 44, 19, 12, 36, 116, 129, 24, 84, 128, 20, 12, 201, 36, 229, 5, 73, 4, 133, 80, 84, 128, 20, 12, 201, 24, 244, 198, 61, 33, 83, 12, 84, 128, 20, 12, 201, 16, 145, 201, 80, 19, 9, 76, 84, 128, 20, 12, 201, 12, 128, 80, 80, 19, 9, 76, 84, 128, 20, 12, 201, 4, 193, 129, 8, 85, 9, 76, 84, 128, 20, 8, 197, 77, 147, 66, 60, 192, 20, 8, 197, 12, 128, 84, 60, 192, 20, 9, 198, 44, 21, 1, 80, 243, 137, 20, 8, 197, 76, 240, 201, 4, 192, 20, 8, 197, 24, 244, 141, 4, 192, 20, 9, 2, 95, 49, 6, 36, 12, 50, 0, 0, 9, 198, 64, 144, 193, 16, 244, 128, 20, 9, 198, 77, 3, 206, 76, 244, 128, 20, 9, 198, 80, 20, 137, 24, 84, 128, 20, 9, 198, 76, 180, 129, 88, 84, 128, 20, 9, 198, 64, 20, 129, 24, 84, 128, 20, 9, 198, 64, 19, 143, 72, 84, 128, 20, 9, 198, 53, 84, 201, 12, 84, 128, 20, 9, 198, 48, 16, 143, 72, 84, 128, 20, 9, 198, 37, 36, 137, 80, 84, 128, 20, 9, 198, 29, 32, 68, 84, 84, 128, 20, 9, 198, 25, 35, 212, 80, 84, 128, 20, 9, 198, 21, 96, 76, 84, 84, 128, 20, 9, 198, 20, 228, 201, 48, 84, 128, 20, 9, 198, 17, 81, 84, 80, 84, 128, 20, 9, 198, 17, 33, 83, 76, 84, 128, 20, 9, 198, 16, 83, 79, 48, 84, 128, 20, 9, 198, 4, 35, 206, 56, 84, 128, 20, 13, 202, 44, 194, 77, 5, 67, 204, 60, 114, 83, 44, 20, 9, 198, 45, 96, 82, 81, 50, 84, 20, 9, 198, 76, 83, 73, 56, 20, 128, 20, 9, 2, 95, 48, 6, 50, 111, 55, 0, 0, 10, 199, 45, 96, 68, 72, 21, 21, 72, 20, 10, 199, 44, 243, 15, 72, 21, 21, 72, 20, 10, 199, 5, 4, 1, 72, 21, 21, 72, 20, 11, 136, 7, 5, 15, 4, 195, 166, 19, 9, 20, 12, 201, 88, 84, 137, 24, 146, 193, 80, 147, 206, 20, 12, 201, 56, 245, 9, 24, 146, 193, 80, 147, 206, 20, 12, 201, 44, 243, 80, 48, 146, 193, 80, 147, 206, 20, 12, 201, 20, 180, 208, 48, 146, 193, 80, 147, 206, 20, 10, 199, 4, 208, 76, 28, 19, 69, 72, 20, 10, 199, 28, 241, 22, 36, 195, 9, 28, 20, 10, 199, 80, 85, 84, 60, 226, 83, 44, 20, 9, 198, 41, 84, 137, 16, 148, 203, 20, 10, 199, 21, 82, 204, 36, 66, 83, 44, 20, 10, 199, 44, 193, 80, 80, 243, 65, 56, 21, 9, 198, 64, 243, 69, 72, 19, 147, 20, 10, 199, 44, 243, 69, 16, 144, 78, 80, 20, 9, 2, 95, 55, 87, 6, 114, 58, 0, 0, 9, 198, 36, 210, 84, 5, 67, 210, 20, 9, 198, 4, 114, 84, 5, 67, 210, 20, 12, 201, 25, 83, 132, 4, 209, 78, 80, 84, 133, 20, 9, 198, 16, 19, 65, 77, 50, 78, 20, 11, 200, 72, 19, 132, 73, 84, 201, 4, 224, 20, 6, 195, 16, 83, 147, 76, 10, 2, 95, 54, 87, 6, 107, 79, 87, 0, 0, 12, 201, 61, 33, 193, 56, 148, 193, 80, 244, 128, 20, 12, 201, 16, 84, 212, 36, 195, 1, 80, 244, 128, 20, 12, 201, 80, 84, 141, 60, 116, 129, 24, 84, 128, 20, 12, 201, 80, 80, 84, 72, 19, 9, 76, 84, 128, 20, 12, 201, 77, 1, 67, 36, 19, 9, 76, 84, 128, 20, 12, 201, 76, 176, 78, 16, 19, 9, 76, 84, 128, 20, 12, 201, 76, 49, 78, 60, 116, 129, 24, 84, 128, 20, 12, 201, 72, 17, 9, 44, 19, 9, 76, 84, 128, 20, 12, 201, 56, 85, 84, 72, 19, 9, 76, 84, 128, 20, 12, 201, 56, 21, 21, 72, 19, 9, 76, 84, 128, 20, 12, 201, 44, 244, 133, 60, 116, 129, 24, 84, 128, 20, 8, 197, 44, 195, 210, 21, 32, 20, 12, 201, 44, 20, 9, 80, 19, 9, 76, 84, 128, 20, 12, 201, 28, 83, 137, 57, 97, 83, 80, 84, 128, 20, 12, 201, 36, 226, 84, 36, 19, 9, 76, 84, 128, 20, 12, 201, 28, 83, 133, 72, 19, 9, 76, 84, 128, 20, 12, 201, 24, 195, 210, 4, 116, 129, 24, 84, 128, 20, 12, 201, 16, 21, 1, 52, 21, 9, 76, 84, 128, 20, 9, 198, 76, 165, 83, 44, 84, 137, 20, 9, 198, 44, 226, 82, 44, 84, 137, 20, 12, 201, 65, 32, 71, 52, 21, 9, 44, 84, 128, 20, 12, 201, 52, 85, 1, 25, 148, 201, 44, 84, 128, 20, 12, 201, 52, 21, 5, 52, 21, 9, 44, 84, 128, 20, 12, 201, 5, 34, 84, 52, 85, 9, 44, 84, 128, 20, 12, 201, 4, 227, 210, 20, 181, 9, 44, 84, 128, 20, 9, 198, 32, 83, 20, 36, 225, 5, 20, 12, 201, 76, 145, 206, 36, 98, 75, 4, 228, 192, 20, 9, 2, 95, 53, 81, 6, 107, 63, 0, 0, 15, 204, 20, 180, 203, 60, 211, 85, 56, 146, 193, 80, 147, 206, 20, 15, 204, 20, 180, 197, 53, 3, 9, 24, 146, 193, 80, 147, 206, 20, 12, 201, 25, 147, 15, 28, 83, 133, 80, 148, 203, 20, 9, 198, 16, 149, 82, 21, 49, 64, 20, 9, 198, 81, 32, 83, 76, 83, 148, 20, 9, 198, 36, 212, 15, 80, 83, 148, 20, 12, 201, 24, 244, 198, 61, 33, 83, 12, 83, 147, 20, 9, 198, 24, 16, 149, 48, 19, 148, 20, 9, 198, 20, 210, 71, 72, 19, 148, 20, 9, 198, 16, 243, 73, 56, 19, 148, 20, 9, 198, 16, 80, 149, 80, 19, 148, 20, 9, 198, 4, 208, 149, 48, 19, 148, 20, 10, 2, 95, 52, 81, 6, 37, 12, 112, 0, 0, 9, 198, 36, 225, 140, 84, 83, 147, 20, 9, 198, 16, 243, 73, 56, 19, 147, 20, 17, 2, 95, 59, 87, 36, 12, 63, 37, 12, 49, 39, 12, 55, 112, 50, 0, 0, 9, 198, 61, 1, 82, 5, 67, 210, 20, 9, 198, 36, 226, 133, 45, 67, 210, 20, 15, 204, 76, 83, 148, 36, 209, 78, 80, 19, 9, 76, 84, 128, 20, 11, 200, 72, 85, 129, 12, 50, 78, 21, 32, 20, 11, 200, 44, 243, 12, 4, 35, 210, 21, 32, 20, 11, 200, 32, 19, 12, 84, 50, 78, 21, 32, 20, 18, 70, 52, 20, 143, 69, 82, 78, 63, 110, 34, 39, 6, 49, 107, 66, 0, 20, 12, 2, 95, 58, 49, 6, 39, 12, 55, 112, 50, 0, 0, 12, 201, 8, 147, 8, 5, 38, 137, 61, 49, 64, 20, 8, 197, 80, 149, 18, 21, 32, 20, 8, 197, 61, 1, 82, 21, 32, 20, 8, 197, 48, 149, 18, 21, 32, 20, 8, 197, 20, 208, 78, 21, 32, 20, 9, 198, 77, 66, 75, 44, 84, 137, 20, 9, 198, 17, 34, 75, 44, 84, 137, 20, 12, 201, 36, 229, 5, 73, 97, 78, 36, 83, 148, 20, 8, 2, 95, 57, 50, 6, 37, 0, 0, 9, 198, 44, 20, 129, 52, 83, 0, 20, 9, 198, 65, 35, 212, 21, 49, 64, 20, 9, 198, 16, 144, 84, 21, 49, 64, 20, 14, 139, 1, 13, 1, 20, 195, 184, 18, 9, 19, 13, 5, 20, 9, 198, 12, 128, 82, 52, 19, 148, 20, 10, 2, 95, 56, 6, 111, 12, 70, 13, 0, 0, 9, 134, 16, 15, 18, 195, 184, 19, 20, 15, 140, 6, 195, 184, 4, 5, 18, 1, 12, 9, 19, 13, 5, 20, 10, 199, 44, 19, 85, 24, 192, 71, 20, 20, 12, 71, 36, 229, 5, 72, 96, 67, 20, 21, 0, 10, 19, 2, 95, 63, 87, 48, 116, 34, 79, 87, 63, 112, 55, 87, 47, 35, 57, 50, 0, 0, 9, 134, 13, 9, 14, 195, 184, 18, 20, 9, 134, 12, 9, 11, 195, 184, 18, 20, 11, 200, 64, 84, 147, 21, 97, 82, 21, 32, 20, 11, 200, 44, 243, 134, 36, 117, 82, 21, 32, 20, 11, 200, 36, 226, 210, 36, 210, 78, 21, 32, 20, 11, 200, 16, 85, 5, 72, 210, 78, 21, 32, 20, 11, 200, 4, 195, 9, 81, 65, 82, 21, 32, 20, 11, 200, 5, 4, 5, 56, 66, 67, 37, 64, 20, 7, 196, 81, 148, 129, 56, 21, 0, 9, 198, 29, 147, 78, 5, 50, 69, 20, 8, 197, 4, 176, 67, 36, 80, 20, 9, 198, 29, 147, 78, 5, 50, 69, 20, 8, 197, 52, 244, 193, 36, 176, 20, 8, 197, 29, 32, 70, 36, 176, 20, 12, 201, 36, 228, 213, 24, 98, 67, 36, 83, 148, 20, 8, 197, 24, 16, 193, 16, 80, 20, 0, 11, 136, 19, 13, 9, 14, 11, 195, 184, 18, 20, 9, 198, 52, 243, 132, 36, 19, 0, 20, 9, 198, 45, 96, 82, 80, 19, 0, 20, 0, 12, 201, 84, 227, 210, 52, 19, 9, 80, 85, 0, 20, 12, 201, 48, 144, 133, 72, 19, 9, 80, 85, 0, 20, 10, 199, 65, 32, 75, 80, 148, 197, 72, 20, 10, 199, 25, 34, 80, 61, 53, 9, 28, 20, 10, 199, 44, 19, 13, 84, 178, 83, 44, 20, 10, 199, 4, 224, 76, 60, 114, 83, 44, 20, 10, 199, 4, 195, 5, 72, 114, 83, 44, 20, 10, 199, 52, 85, 15, 16, 146, 197, 72, 20, 0, 9, 134, 22, 1, 12, 195, 184, 18, 20, 11, 200, 76, 82, 83, 52, 243, 15, 28, 144, 20, 11, 200, 52, 243, 9, 56, 243, 15, 28, 144, 20, 7, 196, 61, 35, 133, 72, 20, 11, 200, 76, 19, 79, 40, 81, 9, 76, 176, 20, 11, 200, 64, 20, 137, 80, 85, 9, 76, 176, 20, 11, 200, 20, 180, 197, 28, 85, 9, 76, 176, 20, 11, 200, 4, 229, 9, 80, 85, 9, 76, 176, 20, 7, 196, 4, 115, 206, 36, 20, 7, 196, 45, 80, 137, 44, 20, 9, 198, 76, 84, 1, 72, 21, 0, 20, 0, 14, 139, 14, 1, 18, 11, 15, 20, 9, 19, 195, 184, 18, 20, 10, 135, 12, 25, 4, 8, 195, 184, 18, 20, 8, 197, 44, 245, 5, 72, 144, 20, 9, 198, 32, 243, 79, 57, 147, 73, 20, 8, 197, 16, 82, 193, 16, 80, 20, 8, 197, 12, 146, 193, 16, 80, 20, 0, 11, 136, 1, 21, 4, 9, 20, 195, 184, 18, 20, 9, 198, 72, 16, 149, 48, 148, 212, 20, 9, 198, 12, 149, 137, 48, 148, 212, 20, 15, 204, 64, 84, 134, 20, 181, 9, 8, 147, 9, 80, 85, 0, 20, 13, 202, 80, 242, 211, 36, 179, 204, 60, 114, 83, 44, 20, 0, 10, 199, 44, 243, 148, 4, 181, 21, 72, 20, 12, 137, 15, 16, 5, 18, 1, 20, 195, 184, 18, 20, 12, 201, 88, 148, 148, 84, 244, 201, 80, 85, 0, 20, 12, 201, 64, 192, 83, 80, 144, 201, 80, 85, 0, 20, 12, 201, 44, 244, 132, 36, 19, 9, 80, 85, 0, 20, 12, 201, 44, 243, 150, 20, 180, 201, 80, 85, 0, 20, 12, 201, 44, 243, 148, 36, 229, 73, 80, 85, 0, 20, 12, 201, 44, 243, 142, 20, 180, 201, 80, 85, 0, 20, 12, 201, 44, 243, 134, 61, 35, 73, 80, 85, 0, 20, 12, 201, 25, 35, 206, 80, 19, 9, 80, 85, 0, 20, 12, 201, 20, 192, 83, 80, 144, 201, 80, 85, 0, 20, 12, 201, 4, 67, 73, 72, 19, 9, 80, 85, 0, 20, 10, 199, 65, 81, 19, 21, 35, 9, 28, 20, 14, 203, 81, 32, 78, 77, 97, 83, 80, 149, 9, 76, 176, 20, 10, 199, 77, 147, 12, 4, 34, 83, 44, 20, 10, 199, 52, 243, 4, 61, 98, 83, 44, 20, 10, 199, 32, 84, 139, 84, 194, 83, 44, 20, 12, 201, 65, 35, 212, 20, 181, 15, 72, 21, 0, 20, 12, 201, 36, 228, 208, 20, 181, 15, 72, 21, 0, 20, 10, 199, 72, 83, 79, 84, 192, 68, 20, 20, 10, 199, 24, 20, 150, 20, 192, 68, 20, 20, 12, 71, 52, 19, 147, 24, 145, 76, 16, 21, 0, 10, 0, 13, 138, 18, 5, 16, 1, 18, 1, 20, 195, 184, 18, 20, 9, 198, 77, 70, 76, 37, 53, 0, 20, 9, 198, 77, 66, 76, 37, 53, 0, 20, 9, 198, 45, 84, 147, 37, 53, 0, 20, 9, 198, 72, 80, 76, 37, 49, 82, 20, 9, 198, 24, 19, 148, 5, 49, 82, 20, 9, 198, 21, 35, 212, 37, 49, 82, 20, 9, 198, 20, 225, 15, 77, 49, 82, 20, 9, 198, 16, 144, 76, 101, 49, 82, 20, 9, 198, 16, 84, 12, 61, 145, 82, 20, 9, 198, 4, 225, 204, 37, 49, 82, 20, 7, 196, 24, 197, 73, 16, 20, 9, 198, 72, 148, 5, 57, 49, 82, 20, 9, 198, 8, 241, 197, 57, 49, 82, 20, 0, 14, 139, 11, 15, 15, 16, 5, 18, 1, 20, 195, 184, 18, 20, 9, 198, 8, 195, 206, 16, 147, 133, 20, 9, 198, 76, 227, 194, 8, 84, 137, 20, 9, 198, 81, 48, 82, 37, 51, 69, 20, 9, 198, 24, 21, 86, 37, 51, 69, 20, 9, 198, 4, 99, 210, 37, 51, 69, 20, 0, 15, 140, 18, 5, 19, 20, 1, 21, 18, 1, 20, 195, 184, 18, 20, 12, 201, 8, 80, 82, 8, 82, 132, 56, 147, 135, 67, 13, 202, 28, 195, 210, 36, 98, 75, 5, 66, 79, 56, 20, 15, 204, 77, 81, 199, 21, 53, 9, 8, 147, 9, 80, 85, 0, 20, 15, 204, 44, 243, 150, 21, 37, 9, 8, 147, 9, 80, 85, 0, 20, 15, 204, 21, 67, 143, 12, 83, 148, 72, 144, 201, 80, 85, 0, 20, 12, 201, 81, 32, 86, 21, 53, 5, 72, 147, 135, 20, 12, 201, 36, 225, 19, 81, 81, 5, 72, 147, 135, 20, 12, 201, 21, 50, 193, 52, 245, 5, 72, 147, 135, 20, 12, 201, 20, 180, 203, 49, 81, 5, 72, 147, 135, 20, 12, 201, 16, 84, 18, 20, 50, 69, 72, 147, 135, 20, 12, 201, 8, 19, 12, 5, 53, 5, 72, 147, 135, 20, 13, 202, 76, 84, 130, 60, 180, 143, 5, 66, 83, 44, 20, 9, 198, 21, 36, 129, 81, 83, 64, 20, 9, 198, 37, 34, 68, 37, 83, 64, 20, 9, 198, 88, 149, 1, 52, 147, 128, 20, 9, 198, 72, 21, 133, 48, 147, 128, 20, 9, 198, 53, 81, 90, 104, 147, 128, 20, 9, 198, 52, 17, 193, 76, 147, 128, 20, 9, 198, 44, 84, 129, 80, 147, 128, 20, 9, 198, 36, 228, 213, 48, 147, 128, 20, 9, 198, 4, 192, 149, 52, 147, 128, 20, 9, 198, 61, 69, 15, 52, 19, 128, 21, 0, 12, 201, 72, 81, 201, 60, 224, 76, 37, 53, 0, 20, 9, 198, 17, 84, 5, 72, 147, 135, 20, 12, 201, 77, 148, 212, 20, 208, 84, 37, 49, 82, 20, 12, 201, 77, 64, 78, 16, 20, 132, 37, 49, 82, 20, 12, 137, 16, 18, 195, 166, 19, 9, 4, 5, 18, 20, 12, 201, 52, 21, 5, 72, 144, 76, 37, 49, 82, 20, 12, 201, 72, 244, 203, 36, 193, 5, 57, 49, 82, 20, 0, 9, 198, 24, 20, 195, 37, 53, 0, 20, 9, 198, 48, 144, 197, 57, 49, 82, 20, 9, 198, 44, 20, 133, 77, 49, 82, 20, 9, 198, 36, 225, 5, 45, 49, 82, 20, 12, 201, 85, 66, 76, 37, 64, 82, 37, 51, 69, 20, 12, 201, 20, 181, 137, 48, 144, 146, 37, 51, 69, 20, 7, 196, 25, 85, 9, 48, 20, 7, 196, 80, 243, 65, 80, 20, 9, 68, 52, 16, 200, 60, 21, 0, 10, 0, 9, 198, 44, 21, 129, 80, 147, 133, 20, 9, 198, 81, 35, 204, 16, 84, 137, 20, 12, 201, 65, 34, 86, 36, 193, 71, 37, 83, 64, 20, 9, 198, 81, 35, 208, 37, 51, 69, 20, 9, 198, 64, 145, 84, 37, 51, 69, 20, 12, 201, 76, 147, 135, 5, 3, 210, 20, 19, 128, 20, 0, 9, 198, 12, 130, 70, 24, 243, 128, 20, 9, 198, 80, 83, 147, 36, 243, 128, 20, 9, 198, 64, 83, 147, 36, 243, 128, 20, 9, 198, 21, 35, 211, 36, 243, 128, 20, 12, 201, 76, 82, 214, 20, 228, 197, 72, 147, 135, 20, 12, 201, 65, 35, 204, 60, 225, 197, 72, 147, 135, 20, 12, 201, 44, 243, 147, 21, 37, 133, 72, 147, 135, 20, 12, 201, 44, 243, 80, 61, 53, 5, 72, 147, 135, 20, 12, 201, 36, 225, 18, 4, 225, 197, 72, 147, 135, 20, 12, 201, 24, 84, 141, 20, 229, 5, 72, 147, 135, 20, 12, 201, 16, 148, 212, 4, 224, 197, 72, 147, 135, 20, 12, 201, 16, 145, 148, 60, 225, 197, 72, 147, 135, 20, 12, 201, 16, 84, 193, 88, 245, 69, 72, 147, 135, 20, 12, 201, 16, 80, 197, 57, 68, 133, 72, 147, 135, 20, 11, 136, 16, 195, 184, 14, 9, 20, 5, 18, 20, 15, 204, 36, 229, 5, 48, 193, 75, 81, 80, 76, 37, 49, 82, 20, 9, 198, 61, 96, 82, 37, 83, 64, 20, 9, 198, 48, 19, 143, 48, 147, 128, 20, 9, 198, 24, 83, 73, 56, 147, 128, 20, 9, 198, 81, 84, 139, 52, 83, 128, 20, 9, 198, 52, 18, 197, 16, 243, 128, 20, 9, 198, 24, 244, 149, 72, 83, 128, 20, 9, 198, 8, 18, 1, 52, 19, 128, 20, 9, 198, 72, 82, 142, 24, 19, 128, 21, 0, 6, 195, 16, 224, 64, 17, 10, 199, 61, 37, 15, 16, 242, 211, 36, 20, 14, 139, 15, 2, 19, 11, 195, 184, 14, 9, 20, 5, 20, 20, 10, 199, 52, 85, 1, 48, 195, 201, 16, 20, 10, 199, 44, 243, 147, 61, 37, 9, 20, 20, 10, 199, 64, 197, 84, 60, 226, 85, 52, 20, 10, 199, 32, 20, 141, 60, 226, 85, 52, 20, 10, 199, 8, 84, 153, 48, 194, 85, 52, 20, 10, 199, 52, 85, 15, 16, 148, 205, 20, 20, 15, 204, 52, 20, 139, 20, 68, 205, 20, 176, 78, 37, 51, 69, 20, 10, 199, 20, 180, 207, 80, 148, 205, 20, 20, 0, 15, 68, 32, 18, 84, 36, 105, 108, 6, 37, 12, 47, 37, 0, 20, 12, 201, 104, 83, 130, 84, 65, 8, 37, 51, 69, 20, 12, 201, 44, 244, 144, 61, 32, 84, 37, 51, 69, 20, 12, 201, 44, 243, 15, 56, 144, 76, 37, 51, 69, 20, 12, 201, 8, 243, 129, 64, 20, 148, 37, 51, 69, 20, 12, 201, 5, 53, 9, 28, 208, 84, 37, 51, 69, 20, 9, 198, 65, 35, 195, 20, 229, 0, 20, 7, 196, 8, 20, 193, 72, 20, 0, 9, 198, 64, 81, 9, 13, 84, 133, 20, 9, 198, 88, 148, 143, 48, 241, 201, 20, 9, 198, 73, 83, 143, 48, 241, 201, 20, 9, 198, 53, 146, 207, 48, 241, 201, 20, 9, 198, 36, 65, 79, 48, 241, 201, 20, 8, 197, 52, 18, 210, 60, 224, 20, 8, 197, 24, 195, 212, 20, 192, 20, 12, 201, 64, 192, 78, 21, 64, 82, 37, 83, 64, 20, 12, 201, 16, 83, 6, 36, 224, 82, 37, 83, 64, 20, 8, 197, 77, 64, 66, 36, 192, 20, 12, 201, 32, 83, 19, 36, 225, 207, 72, 19, 128, 20, 12, 201, 25, 33, 68, 21, 34, 67, 36, 19, 128, 20, 8, 197, 24, 146, 137, 4, 224, 20, 8, 197, 9, 84, 141, 4, 224, 20, 12, 137, 8, 15, 13, 195, 184, 15, 16, 1, 20, 20, 8, 197, 76, 128, 77, 4, 224, 21, 0, 0, 10, 199, 85, 32, 129, 56, 148, 197, 72, 20, 10, 199, 80, 149, 143, 48, 148, 197, 72, 20, 10, 199, 80, 83, 65, 80, 148, 197, 72, 20, 10, 199, 72, 83, 80, 48, 16, 197, 72, 20, 10, 199, 72, 21, 9, 24, 144, 197, 72, 20, 10, 199, 64, 243, 65, 16, 148, 197, 72, 20, 10, 199, 4, 181, 9, 88, 148, 197, 72, 20, 10, 199, 24, 244, 147, 60, 227, 9, 28, 20, 10, 199, 64, 21, 18, 36, 50, 83, 44, 20, 10, 199, 52, 84, 207, 104, 242, 83, 44, 20, 10, 199, 48, 85, 1, 72, 114, 83, 44, 20, 10, 199, 21, 68, 149, 76, 178, 83, 44, 20, 10, 199, 4, 224, 84, 60, 210, 83, 44, 20, 15, 204, 20, 180, 201, 77, 65, 78, 80, 144, 76, 37, 51, 69, 20, 10, 199, 65, 35, 208, 60, 225, 78, 80, 20, 10, 199, 44, 243, 70, 61, 37, 1, 8, 20, 0, 9, 198, 16, 243, 129, 80, 147, 206, 20, 9, 198, 5, 97, 82, 76, 147, 206, 20, 7, 196, 45, 84, 5, 72, 20, 15, 204, 36, 228, 212, 73, 83, 69, 57, 64, 82, 37, 83, 64, 20, 7, 196, 25, 149, 9, 56, 20, 7, 196, 61, 5, 9, 44, 20, 0, 12, 201, 72, 81, 201, 77, 68, 129, 81, 84, 128, 20, 9, 198, 81, 32, 75, 80, 244, 197, 20, 8, 197, 48, 81, 213, 4, 224, 21, 8, 197, 85, 34, 78, 4, 192, 20, 8, 197, 5, 53, 18, 4, 192, 20, 8, 197, 64, 244, 148, 4, 32, 20, 0, 13, 202, 28, 84, 143, 57, 67, 204, 60, 114, 83, 44, 20, 0, 6, 195, 20, 177, 192, 17, 10, 67, 36, 65, 64, 37, 70, 6, 36, 0, 10, 199, 29, 33, 78, 4, 66, 78, 20, 20, 12, 201, 44, 243, 132, 20, 211, 129, 80, 147, 206, 20, 12, 201, 36, 229, 18, 61, 97, 82, 76, 147, 206, 20, 12, 201, 36, 228, 197, 52, 147, 129, 80, 147, 206, 20, 12, 201, 20, 180, 193, 52, 147, 129, 80, 147, 206, 20, 10, 199, 52, 147, 137, 77, 68, 133, 72, 20, 10, 199, 44, 244, 144, 61, 35, 9, 28, 20, 10, 199, 72, 20, 19, 60, 66, 83, 44, 20, 10, 199, 64, 192, 84, 60, 226, 83, 44, 20, 9, 198, 44, 147, 133, 80, 148, 203, 20, 10, 199, 29, 33, 78, 4, 66, 83, 44, 20, 9, 198, 20, 209, 129, 80, 148, 203, 20, 9, 198, 5, 34, 193, 16, 148, 203, 20, 10, 199, 81, 32, 78, 76, 145, 78, 80, 20, 10, 199, 72, 80, 201, 64, 145, 78, 80, 20, 9, 198, 72, 85, 133, 72, 83, 147, 20, 9, 198, 44, 243, 147, 80, 19, 147, 20, 10, 199, 36, 225, 143, 72, 208, 78, 80, 20, 0, 9, 198, 80, 84, 212, 5, 67, 210, 20, 9, 198, 72, 243, 12, 5, 67, 210, 20, 9, 198, 37, 51, 204, 5, 67, 210, 20, 18, 4, 95, 4, 15, 20, 58, 37, 84, 70, 6, 113, 47, 35, 69, 112, 82, 0, 0, 8, 197, 76, 83, 137, 61, 32, 20, 18, 143, 16, 18, 195, 166, 19, 21, 16, 16, 15, 19, 9, 20, 9, 15, 14, 20, 12, 201, 65, 35, 198, 21, 52, 201, 60, 225, 76, 20, 12, 201, 44, 243, 134, 21, 52, 201, 60, 225, 76, 20, 8, 197, 45, 33, 68, 37, 64, 20, 8, 197, 45, 84, 129, 57, 64, 20, 0, 9, 198, 88, 148, 143, 48, 241, 192, 20, 9, 198, 73, 83, 143, 48, 241, 192, 20, 9, 198, 53, 146, 207, 48, 241, 192, 20, 9, 198, 36, 65, 79, 48, 241, 192, 20, 13, 202, 76, 82, 83, 52, 241, 210, 4, 98, 83, 44, 20, 12, 201, 64, 197, 84, 60, 180, 129, 80, 148, 203, 20, 13, 202, 60, 49, 65, 56, 241, 210, 4, 98, 83, 44, 20, 12, 201, 52, 84, 207, 64, 245, 1, 52, 148, 203, 20, 13, 202, 44, 20, 132, 36, 241, 210, 4, 98, 83, 44, 20, 13, 202, 8, 144, 140, 36, 241, 210, 4, 98, 83, 44, 20, 13, 202, 8, 19, 135, 48, 17, 5, 76, 130, 83, 44, 20, 9, 198, 81, 34, 66, 84, 224, 76, 20, 9, 198, 5, 52, 9, 72, 19, 148, 20, 9, 198, 4, 67, 208, 80, 19, 148, 20, 0, 20, 67, 88, 147, 0, 82, 36, 55, 15, 105, 6, 108, 12, 0, 81, 104, 97, 118, 101, 32, 10, 199, 44, 242, 193, 36, 226, 83, 80, 20, 10, 199, 32, 83, 12, 20, 226, 83, 80, 20, 9, 198, 76, 21, 9, 72, 148, 203, 20, 9, 198, 64, 20, 143, 16, 148, 203, 20, 9, 198, 61, 51, 79, 80, 148, 203, 20, 9, 198, 60, 49, 65, 56, 148, 203, 20, 9, 198, 4, 193, 197, 72, 148, 203, 20, 8, 67, 80, 80, 200, 21, 0, 10, 6, 195, 88, 147, 0, 76, 0, 31, 76, 77, 21, 65, 72, 81, 1, 56, 49, 82, 56, 84, 192, 87, 49, 58, 6, 36, 13, 70, 35, 12, 50, 87, 112, 20, 50, 13, 87, 0, 9, 198, 36, 229, 133, 77, 67, 210, 20, 9, 198, 16, 85, 5, 45, 67, 210, 20, 11, 200, 52, 147, 137, 52, 19, 9, 77, 64, 20, 11, 200, 4, 194, 207, 32, 243, 9, 77, 64, 20, 9, 198, 20, 225, 15, 72, 98, 78, 20, 11, 200, 16, 242, 213, 52, 83, 148, 5, 32, 20, 11, 200, 36, 229, 15, 48, 84, 129, 57, 64, 20, 0, 6, 195, 36, 179, 206, 20, 8, 197, 24, 192, 78, 21, 32, 20, 12, 201, 88, 83, 147, 44, 16, 133, 48, 145, 192, 20, 12, 201, 80, 18, 206, 20, 211, 69, 48, 145, 192, 20, 12, 201, 76, 83, 19, 44, 16, 133, 48, 145, 192, 20, 12, 201, 32, 84, 147, 44, 16, 133, 48, 145, 192, 20, 8, 197, 32, 149, 20, 37, 64, 20, 12, 201, 64, 144, 78, 37, 53, 9, 56, 65, 64, 20, 8, 197, 76, 243, 4, 5, 64, 20, 8, 197, 25, 64, 76, 5, 64, 20, 8, 197, 4, 49, 84, 5, 64, 20, 8, 197, 76, 82, 193, 57, 64, 20, 9, 198, 20, 181, 137, 64, 17, 197, 20, 0, 18, 66, 88, 144, 82, 37, 15, 87, 47, 6, 36, 0, 81, 115, 116, 101, 103, 32, 18, 67, 36, 178, 197, 36, 79, 36, 15, 105, 108, 0, 81, 104, 97, 118, 101, 32, 9, 198, 20, 225, 15, 76, 179, 208, 20, 9, 198, 77, 69, 68, 36, 225, 64, 20, 12, 201, 65, 80, 140, 36, 50, 83, 80, 148, 203, 20, 12, 201, 56, 85, 82, 5, 53, 5, 56, 148, 203, 20, 12, 201, 52, 81, 9, 84, 210, 83, 80, 148, 203, 20, 9, 198, 84, 197, 137, 56, 65, 64, 20, 9, 198, 29, 81, 9, 56, 65, 64, 20, 9, 198, 72, 81, 133, 72, 83, 148, 20, 9, 198, 44, 243, 147, 80, 19, 148, 20, 8, 66, 88, 144, 82, 37, 0, 72, 0, 10, 199, 72, 81, 143, 72, 210, 83, 80, 20, 10, 199, 64, 243, 25, 80, 82, 83, 80, 20, 10, 199, 64, 84, 147, 60, 224, 71, 20, 20, 14, 2, 95, 95, 69, 6, 111, 50, 87, 70, 34, 35, 37, 0, 0, 9, 134, 6, 1, 22, 195, 184, 18, 20, 11, 200, 52, 243, 143, 64, 243, 9, 77, 64, 20, 11, 200, 24, 81, 5, 72, 19, 9, 77, 64, 20, 12, 201, 8, 84, 212, 101, 33, 82, 36, 225, 5, 68, 11, 200, 77, 80, 143, 72, 66, 78, 21, 32, 20, 11, 200, 36, 229, 5, 72, 97, 82, 21, 32, 20, 11, 200, 5, 3, 211, 81, 35, 198, 21, 32, 20, 12, 137, 16, 18, 195, 166, 19, 9, 4, 9, 5, 20, 12, 201, 45, 83, 147, 80, 225, 82, 36, 225, 5, 20, 12, 201, 8, 84, 212, 101, 33, 82, 36, 225, 5, 20, 11, 200, 72, 83, 143, 52, 209, 82, 21, 64, 20, 11, 200, 52, 19, 137, 21, 33, 82, 21, 64, 20, 11, 200, 36, 225, 9, 28, 225, 82, 21, 64, 20, 11, 200, 24, 16, 197, 81, 65, 82, 21, 64, 20, 11, 200, 20, 180, 193, 49, 65, 82, 21, 64, 20, 11, 200, 16, 84, 129, 56, 113, 82, 21, 64, 20, 11, 200, 16, 84, 18, 37, 97, 82, 21, 64, 20, 11, 200, 5, 52, 207, 73, 65, 82, 21, 64, 20, 11, 200, 4, 229, 9, 45, 97, 82, 21, 64, 20, 11, 200, 4, 97, 133, 45, 65, 82, 21, 64, 20, 9, 198, 48, 19, 73, 56, 21, 0, 20, 7, 196, 45, 84, 129, 8, 20, 0, 8, 197, 84, 225, 9, 56, 80, 20, 12, 201, 28, 80, 143, 52, 209, 82, 48, 145, 192, 20, 13, 138, 16, 195, 166, 4, 5, 18, 1, 19, 20, 9, 20, 12, 201, 4, 67, 73, 72, 19, 9, 56, 65, 64, 20, 10, 69, 60, 227, 9, 56, 80, 21, 0, 10, 0, 9, 198, 64, 20, 143, 16, 148, 212, 20, 9, 198, 49, 85, 5, 56, 148, 212, 20, 9, 198, 21, 52, 193, 100, 148, 212, 20, 9, 198, 52, 243, 135, 60, 194, 68, 20, 9, 198, 81, 148, 129, 56, 226, 64, 20, 9, 198, 16, 144, 75, 60, 226, 64, 20, 9, 198, 64, 243, 5, 52, 146, 192, 20, 9, 198, 28, 83, 133, 80, 146, 192, 20, 9, 198, 24, 243, 133, 80, 146, 192, 20, 9, 198, 81, 34, 66, 84, 224, 84, 20, 9, 198, 40, 245, 82, 56, 19, 0, 20, 8, 67, 12, 242, 197, 21, 0, 10, 0, 14, 203, 81, 32, 68, 37, 66, 79, 56, 19, 9, 77, 64, 20, 12, 201, 20, 180, 212, 72, 83, 73, 80, 85, 0, 20, 10, 199, 88, 148, 137, 48, 148, 197, 72, 20, 10, 199, 37, 51, 1, 52, 148, 197, 72, 20, 10, 199, 24, 197, 73, 16, 148, 197, 72, 20, 9, 198, 32, 245, 141, 60, 66, 71, 20, 9, 198, 28, 83, 69, 56, 194, 71, 20, 6, 195, 88, 147, 204, 20, 6, 195, 24, 147, 204, 20, 10, 199, 52, 243, 129, 72, 178, 83, 44, 20, 10, 199, 44, 19, 13, 100, 178, 83, 44, 20, 10, 199, 21, 84, 212, 4, 178, 83, 44, 20, 10, 199, 72, 17, 9, 60, 99, 206, 36, 20, 10, 199, 16, 243, 73, 56, 144, 193, 56, 20, 10, 199, 44, 21, 129, 48, 176, 68, 20, 20, 10, 199, 8, 20, 146, 36, 176, 68, 20, 20, 10, 199, 65, 32, 75, 80, 146, 193, 8, 20, 10, 199, 4, 211, 210, 80, 148, 193, 8, 20, 8, 67, 12, 243, 204, 21, 0, 10, 0, 13, 138, 9, 14, 19, 5, 13, 9, 14, 195, 184, 18, 20, 11, 200, 16, 84, 141, 5, 67, 204, 60, 112, 20, 11, 200, 9, 35, 205, 5, 67, 204, 60, 112, 20, 11, 200, 76, 84, 144, 20, 229, 9, 56, 80, 20, 9, 198, 21, 37, 80, 80, 147, 206, 20, 9, 198, 4, 208, 137, 80, 147, 206, 20, 11, 200, 33, 148, 15, 44, 243, 132, 72, 144, 20, 11, 200, 28, 83, 132, 5, 35, 69, 72, 144, 20, 11, 200, 96, 83, 143, 24, 240, 137, 76, 176, 20, 11, 200, 88, 81, 197, 80, 20, 137, 76, 176, 20, 11, 200, 88, 19, 21, 80, 20, 137, 76, 176, 20, 11, 200, 76, 243, 9, 16, 20, 137, 76, 176, 20, 11, 200, 52, 85, 1, 8, 243, 9, 76, 176, 20, 11, 200, 48, 20, 9, 16, 20, 137, 76, 176, 20, 11, 200, 8, 19, 21, 77, 68, 129, 16, 80, 20, 11, 200, 24, 84, 142, 37, 52, 193, 28, 80, 20, 0, 8, 197, 84, 99, 204, 60, 112, 20, 8, 197, 64, 241, 210, 60, 208, 20, 8, 197, 61, 34, 197, 72, 80, 20, 8, 197, 5, 50, 197, 76, 80, 20, 9, 198, 21, 2, 84, 4, 98, 69, 20, 9, 198, 16, 80, 197, 56, 226, 69, 20, 8, 197, 24, 16, 146, 36, 176, 20, 12, 201, 76, 18, 210, 4, 209, 78, 80, 19, 0, 20, 11, 70, 25, 34, 69, 56, 67, 25, 21, 0, 10, 20, 4, 95, 56, 88, 15, 81, 37, 34, 87, 36, 50, 87, 47, 114, 82, 13, 50, 13, 0, 0, 11, 67, 81, 83, 133, 47, 40, 50, 106, 0, 41, 12, 137, 18, 5, 12, 9, 7, 9, 195, 184, 19, 20, 12, 137, 13, 1, 12, 9, 3, 9, 195, 184, 19, 20, 11, 136, 16, 12, 1, 14, 20, 195, 184, 18, 20, 13, 202, 60, 101, 1, 48, 211, 204, 60, 114, 83, 44, 20, 13, 202, 48, 20, 153, 56, 115, 204, 60, 114, 83, 44, 20, 13, 202, 24, 20, 141, 4, 179, 204, 60, 114, 83, 44, 20, 9, 198, 16, 144, 75, 60, 224, 84, 20, 13, 202, 36, 226, 207, 52, 209, 78, 77, 84, 129, 8, 20, 0, 20, 67, 33, 83, 128, 105, 111, 50, 15, 87, 47, 6, 36, 0, 81, 115, 116, 101, 103, 32, 13, 138, 16, 5, 18, 14, 9, 3, 9, 195, 184, 19, 20, 12, 201, 44, 243, 210, 16, 147, 129, 80, 147, 206, 20, 12, 201, 44, 243, 147, 20, 180, 129, 80, 147, 206, 20, 12, 201, 24, 192, 71, 20, 195, 1, 80, 147, 206, 20, 12, 201, 36, 208, 133, 12, 147, 9, 80, 85, 0, 20, 12, 201, 4, 227, 210, 52, 19, 9, 80, 85, 0, 20, 10, 199, 65, 35, 203, 48, 19, 69, 72, 20, 10, 199, 44, 243, 139, 85, 36, 133, 72, 20, 10, 199, 44, 243, 132, 20, 228, 197, 72, 20, 10, 199, 44, 20, 9, 81, 83, 5, 72, 20, 10, 199, 4, 178, 213, 53, 83, 5, 72, 20, 10, 199, 64, 197, 84, 60, 226, 83, 44, 20, 14, 203, 56, 243, 69, 56, 179, 1, 80, 244, 137, 76, 176, 20, 10, 199, 52, 85, 1, 48, 194, 83, 44, 20, 9, 198, 48, 85, 137, 80, 148, 203, 20, 10, 199, 48, 84, 207, 80, 130, 83, 44, 20, 14, 203, 44, 243, 80, 20, 228, 193, 80, 244, 137, 76, 176, 20, 9, 198, 21, 84, 129, 76, 148, 203, 20, 10, 199, 16, 144, 84, 60, 226, 83, 44, 20, 10, 199, 8, 20, 130, 4, 66, 83, 44, 20, 9, 198, 5, 165, 5, 44, 148, 203, 20, 10, 199, 44, 244, 205, 60, 115, 206, 36, 20, 10, 199, 88, 20, 132, 20, 228, 197, 72, 20, 12, 201, 12, 149, 137, 48, 148, 197, 72, 85, 0, 20, 10, 199, 44, 20, 130, 60, 224, 68, 20, 20, 6, 195, 33, 83, 128, 72, 0, 14, 139, 16, 18, 5, 19, 20, 9, 7, 9, 195, 184, 19, 20, 11, 200, 44, 194, 77, 5, 67, 204, 60, 112, 20, 7, 196, 5, 67, 5, 80, 20, 9, 198, 64, 145, 84, 37, 53, 0, 20, 7, 196, 5, 4, 5, 48, 20, 9, 198, 64, 241, 84, 37, 49, 82, 20, 9, 198, 44, 19, 132, 37, 49, 82, 20, 9, 198, 36, 67, 204, 37, 49, 82, 20, 11, 200, 48, 19, 80, 37, 53, 5, 72, 144, 20, 11, 200, 24, 19, 148, 5, 53, 5, 72, 144, 20, 11, 200, 76, 20, 139, 5, 53, 9, 76, 176, 20, 11, 200, 32, 145, 82, 5, 34, 201, 76, 176, 20, 7, 196, 76, 130, 73, 80, 20, 9, 198, 64, 20, 129, 24, 98, 78, 20, 11, 200, 44, 243, 148, 20, 224, 78, 12, 80, 20, 7, 196, 73, 84, 129, 48, 20, 7, 196, 8, 20, 193, 48, 20, 0, 12, 201, 52, 84, 139, 4, 229, 9, 48, 148, 212, 20, 9, 198, 76, 181, 77, 48, 84, 137, 20, 9, 198, 45, 37, 75, 44, 84, 137, 20, 12, 201, 28, 84, 141, 4, 226, 83, 80, 146, 192, 20, 11, 67, 20, 192, 78, 36, 55, 35, 50, 0, 21, 8, 197, 45, 84, 129, 57, 48, 20, 0, 15, 204, 81, 32, 78, 76, 194, 84, 80, 84, 129, 80, 147, 206, 20, 15, 204, 36, 225, 140, 20, 180, 201, 8, 147, 9, 80, 85, 0, 20, 12, 201, 80, 82, 206, 60, 180, 129, 80, 148, 203, 20, 13, 202, 52, 81, 137, 77, 67, 198, 20, 194, 83, 44, 20, 12, 201, 33, 81, 213, 20, 227, 212, 80, 148, 203, 20, 0, 24, 73, 44, 243, 134, 37, 35, 65, 56, 65, 82, 49, 112, 50, 81, 36, 34, 63, 6, 108, 50, 70, 106, 0, 10, 67, 36, 65, 84, 37, 70, 6, 36, 0, 12, 201, 48, 82, 211, 36, 176, 76, 37, 49, 82, 20, 12, 201, 4, 178, 204, 36, 208, 84, 37, 49, 82, 20, 14, 203, 44, 243, 147, 64, 148, 129, 80, 244, 137, 76, 176, 20, 14, 203, 20, 180, 193, 52, 147, 129, 80, 244, 137, 76, 176, 20, 14, 203, 12, 149, 137, 48, 148, 193, 80, 244, 137, 76, 176, 20, 9, 198, 5, 53, 5, 56, 148, 203, 20, 10, 199, 5, 84, 208, 36, 50, 85, 52, 20, 0, 9, 198, 72, 80, 76, 37, 53, 0, 20, 9, 198, 17, 80, 76, 37, 53, 0, 20, 9, 198, 16, 83, 148, 37, 53, 0, 20, 9, 198, 12, 19, 80, 37, 53, 0, 20, 9, 198, 60, 181, 18, 60, 161, 82, 20, 9, 198, 37, 35, 206, 37, 49, 82, 20, 9, 198, 36, 226, 204, 36, 225, 82, 20, 9, 198, 36, 226, 193, 77, 49, 82, 20, 7, 196, 53, 83, 1, 80, 20, 0, 9, 198, 21, 85, 1, 56, 20, 201, 20, 9, 198, 64, 84, 137, 24, 84, 137, 20, 0, 15, 204, 20, 180, 201, 77, 65, 78, 80, 144, 76, 37, 53, 0, 20, 12, 201, 52, 225, 77, 61, 65, 75, 56, 148, 203, 20, 9, 198, 16, 148, 203, 60, 98, 76, 20, 9, 198, 16, 144, 75, 60, 224, 76, 20, 13, 4, 95, 7, 18, 22, 35, 49, 87, 6, 35, 66, 0, 0, 6, 195, 76, 244, 192, 17, 30, 75, 9, 33, 65, 44, 64, 78, 12, 84, 142, 21, 48, 69, 34, 107, 37, 79, 6, 70, 35, 12, 50, 87, 112, 20, 50, 13, 87, 0, 10, 199, 44, 83, 79, 80, 18, 211, 36, 20, 12, 201, 77, 147, 132, 36, 176, 76, 37, 53, 0, 20, 12, 201, 52, 21, 5, 72, 144, 76, 37, 53, 0, 20, 12, 201, 36, 212, 5, 72, 144, 76, 37, 53, 0, 20, 12, 201, 21, 52, 5, 72, 19, 148, 37, 53, 0, 20, 12, 201, 24, 19, 73, 48, 144, 82, 37, 49, 82, 20, 10, 199, 52, 243, 135, 60, 195, 201, 16, 20, 10, 135, 16, 18, 195, 166, 12, 1, 20, 20, 0, 14, 68, 8, 148, 207, 56, 69, 6, 37, 87, 112, 50, 0, 20, 9, 198, 72, 81, 149, 76, 147, 206, 20, 9, 198, 16, 85, 143, 80, 147, 206, 20, 7, 196, 65, 84, 133, 72, 20, 11, 200, 65, 35, 214, 20, 226, 69, 57, 48, 20, 11, 200, 44, 243, 150, 20, 226, 69, 57, 48, 20, 11, 200, 36, 225, 210, 20, 66, 69, 57, 48, 20, 0, 9, 198, 24, 147, 15, 48, 241, 201, 20, 8, 197, 44, 21, 9, 60, 224, 20, 8, 197, 44, 244, 132, 20, 192, 20, 8, 197, 8, 244, 132, 20, 192, 20, 12, 201, 65, 35, 198, 21, 52, 201, 60, 224, 76, 20, 0, 15, 204, 36, 229, 5, 48, 193, 75, 81, 80, 76, 37, 53, 0, 20, 9, 198, 44, 244, 21, 48, 84, 128, 20, 9, 198, 5, 81, 9, 80, 84, 128, 20, 9, 198, 44, 242, 203, 60, 194, 84, 20, 0, 10, 199, 81, 148, 9, 24, 144, 197, 72, 20, 10, 199, 64, 243, 5, 52, 148, 197, 72, 20, 10, 199, 56, 245, 9, 24, 144, 197, 72, 20, 10, 199, 52, 244, 129, 48, 148, 197, 72, 20, 10, 199, 44, 243, 80, 48, 144, 197, 72, 20, 10, 199, 44, 19, 129, 48, 148, 197, 72, 20, 10, 199, 33, 83, 65, 56, 148, 197, 72, 20, 10, 199, 24, 19, 129, 80, 148, 197, 72, 20, 10, 199, 16, 83, 129, 81, 84, 133, 72, 20, 10, 199, 8, 83, 133, 16, 144, 197, 72, 20, 10, 199, 8, 19, 129, 48, 148, 197, 72, 20, 10, 199, 44, 243, 80, 60, 225, 78, 80, 20, 10, 199, 20, 180, 208, 60, 225, 78, 80, 20, 10, 199, 16, 148, 208, 60, 225, 78, 80, 20, 0, 11, 200, 85, 53, 82, 64, 21, 9, 60, 224, 20, 11, 200, 72, 84, 5, 80, 149, 9, 60, 224, 20, 11, 200, 72, 84, 1, 72, 21, 9, 60, 224, 20, 11, 200, 40, 243, 137, 76, 21, 9, 60, 224, 20, 11, 200, 36, 229, 15, 56, 21, 9, 60, 224, 20, 11, 200, 36, 225, 9, 44, 21, 9, 60, 224, 20, 11, 200, 24, 81, 5, 72, 21, 9, 60, 224, 20, 11, 200, 5, 69, 18, 4, 181, 9, 60, 224, 20, 11, 200, 4, 195, 15, 44, 21, 9, 60, 224, 20, 9, 198, 4, 67, 208, 80, 147, 206, 20, 11, 200, 4, 67, 143, 80, 21, 9, 60, 224, 20, 11, 200, 4, 64, 80, 80, 21, 9, 60, 224, 20, 18, 207, 20, 180, 212, 72, 20, 1, 72, 192, 77, 20, 229, 1, 72, 148, 203, 20, 7, 196, 49, 148, 137, 44, 20, 13, 138, 11, 15, 18, 19, 195, 184, 18, 9, 1, 14, 20, 9, 198, 77, 69, 68, 20, 229, 0, 20, 7, 196, 53, 85, 1, 8, 20, 0, 12, 201, 56, 243, 69, 56, 179, 1, 81, 84, 128, 20, 12, 201, 24, 195, 211, 45, 83, 1, 81, 84, 128, 20, 9, 198, 16, 21, 1, 48, 241, 201, 20, 9, 198, 24, 192, 78, 44, 84, 133, 20, 9, 198, 33, 148, 15, 80, 84, 197, 20, 8, 197, 32, 83, 12, 20, 224, 20, 9, 198, 72, 83, 148, 72, 144, 197, 20, 9, 198, 52, 243, 148, 72, 144, 197, 20, 8, 197, 56, 85, 82, 4, 192, 20, 0, 28, 74, 9, 33, 65, 44, 64, 78, 12, 84, 142, 20, 69, 34, 107, 37, 79, 6, 70, 35, 12, 50, 87, 112, 20, 50, 13, 0, 11, 200, 44, 21, 15, 16, 244, 203, 61, 0, 20, 11, 200, 28, 20, 212, 72, 244, 203, 61, 0, 20, 13, 202, 76, 176, 78, 16, 147, 129, 88, 148, 197, 72, 20, 13, 202, 65, 35, 194, 48, 83, 65, 80, 148, 197, 72, 20, 13, 202, 24, 146, 212, 36, 243, 129, 48, 148, 197, 72, 20, 13, 202, 12, 243, 148, 4, 147, 133, 72, 148, 197, 72, 20, 13, 202, 80, 84, 141, 60, 70, 78, 4, 210, 83, 44, 20, 0, 10, 199, 80, 84, 141, 37, 53, 15, 72, 20, 14, 203, 36, 229, 5, 73, 1, 76, 48, 21, 9, 60, 224, 20, 14, 203, 36, 65, 78, 80, 145, 137, 44, 21, 9, 60, 224, 20, 14, 203, 20, 180, 212, 72, 20, 15, 48, 21, 9, 60, 224, 20, 14, 203, 12, 83, 148, 72, 19, 9, 76, 21, 9, 60, 224, 20, 12, 201, 5, 81, 205, 20, 229, 1, 80, 147, 206, 20, 14, 203, 4, 67, 73, 56, 148, 212, 72, 21, 9, 60, 224, 20, 10, 199, 80, 19, 154, 4, 226, 83, 44, 20, 9, 198, 80, 19, 65, 72, 148, 203, 20, 10, 199, 77, 148, 212, 60, 194, 83, 44, 20, 9, 198, 45, 35, 193, 80, 148, 203, 20, 10, 199, 32, 20, 141, 60, 226, 83, 44, 20, 9, 198, 25, 85, 21, 72, 148, 203, 20, 9, 198, 24, 243, 133, 80, 148, 203, 20, 9, 198, 4, 115, 129, 80, 148, 203, 20, 10, 199, 16, 149, 133, 72, 113, 78, 80, 20, 12, 201, 77, 80, 132, 60, 210, 78, 4, 229, 0, 20, 10, 199, 56, 81, 204, 36, 113, 65, 8, 20, 12, 71, 77, 64, 84, 20, 209, 78, 80, 21, 0, 10, 0, 11, 200, 72, 85, 143, 49, 85, 9, 60, 224, 20, 11, 200, 72, 84, 207, 49, 85, 9, 60, 224, 20, 11, 200, 60, 178, 213, 64, 21, 9, 60, 224, 20, 11, 200, 56, 21, 137, 28, 21, 9, 60, 224, 20, 11, 200, 52, 241, 5, 72, 21, 9, 60, 224, 20, 11, 200, 45, 96, 68, 72, 21, 9, 60, 224, 20, 11, 200, 44, 20, 212, 72, 21, 9, 60, 224, 20, 11, 200, 36, 227, 143, 88, 21, 9, 60, 224, 20, 11, 200, 16, 85, 15, 56, 21, 9, 60, 224, 20, 11, 200, 16, 82, 207, 72, 21, 9, 60, 224, 20, 11, 200, 5, 85, 15, 52, 21, 9, 60, 224, 20, 11, 200, 5, 4, 1, 72, 149, 9, 60, 224, 20, 11, 200, 4, 227, 143, 80, 21, 9, 60, 224, 20, 11, 200, 4, 33, 9, 44, 21, 9, 60, 224, 20, 0, 8, 197, 80, 19, 201, 77, 64, 20, 8, 197, 52, 243, 137, 77, 64, 20, 8, 197, 8, 147, 208, 5, 64, 20, 0, 9, 198, 24, 147, 15, 48, 241, 192, 20, 12, 201, 80, 83, 5, 44, 147, 133, 80, 148, 203, 20, 12, 201, 56, 81, 5, 73, 48, 75, 76, 148, 203, 20, 12, 201, 36, 225, 15, 44, 147, 133, 76, 148, 203, 20, 15, 140, 12, 195, 184, 7, 19, 20, 195, 184, 18, 9, 1, 14, 20, 9, 198, 72, 21, 9, 60, 224, 76, 20, 9, 198, 24, 244, 140, 4, 65, 64, 20, 0, 10, 199, 76, 18, 203, 5, 35, 211, 20, 20, 10, 199, 88, 147, 204, 36, 226, 83, 80, 20, 10, 199, 80, 84, 146, 61, 34, 83, 80, 20, 10, 199, 77, 147, 66, 60, 194, 83, 80, 20, 10, 199, 76, 240, 201, 4, 194, 83, 80, 20, 10, 199, 76, 163, 198, 20, 194, 83, 80, 20, 10, 199, 52, 245, 9, 60, 226, 83, 80, 20, 10, 199, 24, 244, 141, 4, 194, 83, 80, 20, 10, 199, 24, 85, 9, 12, 130, 83, 80, 20, 10, 199, 16, 20, 151, 36, 226, 83, 80, 20, 10, 199, 4, 181, 9, 60, 226, 83, 80, 20, 10, 199, 4, 36, 213, 72, 66, 83, 80, 20, 14, 203, 64, 243, 25, 52, 84, 137, 76, 21, 9, 60, 224, 20, 9, 198, 84, 112, 78, 16, 148, 203, 20, 9, 198, 81, 83, 133, 76, 148, 203, 20, 9, 198, 76, 21, 25, 72, 148, 203, 20, 9, 198, 52, 245, 9, 88, 148, 203, 20, 9, 198, 32, 243, 69, 72, 148, 203, 20, 9, 198, 20, 212, 9, 72, 148, 203, 20, 9, 198, 5, 52, 217, 72, 148, 203, 20, 9, 198, 4, 181, 9, 88, 148, 203, 20, 10, 199, 16, 149, 133, 72, 113, 78, 76, 20, 12, 71, 76, 178, 78, 32, 80, 68, 76, 21, 0, 10, 13, 4, 95, 4, 9, 1, 6, 39, 63, 55, 114, 70, 0, 0, 11, 200, 64, 83, 147, 36, 243, 137, 77, 64, 20, 11, 200, 44, 21, 84, 36, 243, 137, 77, 64, 20, 7, 196, 16, 82, 83, 80, 20, 14, 139, 8, 195, 165, 14, 4, 20, 5, 18, 12, 9, 7, 20, 11, 200, 76, 82, 212, 21, 34, 75, 21, 32, 20, 11, 200, 72, 243, 65, 57, 66, 75, 21, 32, 20, 11, 200, 56, 85, 82, 61, 66, 75, 21, 32, 20, 11, 200, 48, 241, 201, 77, 66, 75, 21, 32, 20, 11, 200, 20, 179, 5, 45, 66, 75, 21, 32, 20, 11, 200, 17, 148, 198, 5, 66, 75, 21, 32, 20, 11, 200, 16, 145, 1, 45, 66, 75, 21, 32, 20, 9, 198, 32, 244, 148, 84, 192, 78, 21, 0, 12, 201, 60, 212, 203, 72, 149, 133, 48, 145, 192, 20, 12, 201, 60, 212, 203, 36, 101, 5, 48, 145, 192, 20, 12, 201, 44, 19, 77, 21, 32, 84, 48, 145, 192, 20, 12, 201, 29, 32, 78, 28, 149, 133, 48, 145, 192, 20, 12, 201, 28, 83, 139, 20, 225, 5, 48, 145, 192, 20, 12, 201, 24, 244, 150, 20, 229, 5, 48, 145, 192, 20, 12, 201, 24, 244, 149, 17, 49, 69, 48, 145, 192, 20, 12, 201, 24, 244, 139, 5, 53, 5, 48, 145, 192, 20, 12, 201, 8, 241, 211, 80, 21, 133, 48, 145, 192, 20, 8, 197, 61, 34, 69, 57, 64, 20, 9, 198, 76, 16, 143, 80, 17, 197, 20, 0, 11, 136, 195, 166, 11, 22, 1, 20, 15, 18, 20, 9, 198, 44, 21, 1, 48, 241, 192, 20, 9, 198, 16, 21, 1, 48, 241, 192, 20, 13, 202, 36, 225, 9, 88, 145, 21, 4, 194, 83, 80, 20, 13, 202, 36, 212, 18, 21, 52, 201, 60, 226, 83, 80, 20, 9, 198, 16, 80, 201, 8, 83, 0, 20, 12, 201, 45, 35, 206, 60, 209, 84, 72, 148, 203, 20, 12, 201, 44, 244, 21, 48, 21, 15, 72, 148, 203, 20, 12, 201, 28, 84, 141, 4, 226, 83, 80, 148, 203, 20, 12, 201, 16, 81, 137, 56, 149, 15, 72, 148, 203, 20, 12, 201, 4, 225, 197, 49, 48, 75, 76, 148, 203, 20, 18, 70, 28, 83, 9, 56, 65, 64, 79, 36, 55, 6, 36, 50, 70, 13, 0, 20, 9, 198, 16, 144, 71, 60, 224, 76, 20, 9, 198, 64, 193, 74, 4, 65, 64, 20, 11, 70, 60, 97, 140, 36, 225, 64, 21, 0, 10, 0, 10, 199, 4, 229, 9, 8, 147, 211, 20, 20, 14, 203, 20, 180, 208, 72, 84, 211, 36, 243, 137, 77, 64, 20, 10, 199, 20, 180, 207, 72, 50, 83, 80, 20, 10, 199, 24, 192, 84, 84, 193, 78, 76, 20, 13, 138, 2, 12, 195, 184, 4, 1, 7, 20, 9, 7, 20, 0, 11, 200, 72, 84, 208, 37, 32, 84, 61, 32, 20, 11, 200, 45, 83, 20, 37, 96, 84, 61, 32, 20, 15, 204, 28, 84, 212, 4, 197, 16, 77, 146, 207, 48, 241, 192, 20, 11, 200, 4, 224, 66, 5, 5, 9, 77, 64, 20, 7, 196, 52, 84, 207, 56, 20, 9, 198, 72, 85, 137, 76, 147, 206, 20, 9, 198, 16, 80, 201, 76, 147, 206, 20, 7, 196, 45, 84, 133, 72, 20, 14, 139, 20, 22, 9, 22, 12, 18, 195, 165, 4, 9, 7, 20, 11, 200, 76, 83, 73, 61, 66, 75, 21, 32, 20, 11, 200, 76, 83, 65, 57, 66, 75, 21, 32, 20, 11, 200, 5, 67, 1, 57, 66, 75, 21, 32, 20, 11, 200, 4, 115, 143, 77, 66, 75, 21, 32, 20, 11, 200, 76, 244, 132, 36, 225, 82, 21, 64, 20, 11, 200, 72, 85, 1, 72, 65, 82, 21, 64, 20, 11, 200, 45, 33, 78, 20, 193, 82, 21, 64, 20, 11, 200, 24, 16, 207, 56, 225, 82, 21, 64, 20, 11, 200, 24, 192, 77, 8, 246, 65, 57, 64, 20, 0, 9, 198, 77, 68, 129, 80, 81, 201, 20, 12, 201, 77, 80, 147, 80, 19, 148, 36, 83, 0, 20, 8, 197, 72, 20, 197, 72, 80, 20, 8, 197, 33, 84, 197, 72, 80, 20, 8, 197, 8, 20, 197, 72, 80, 20, 15, 204, 77, 68, 149, 45, 69, 82, 4, 194, 83, 80, 148, 203, 20, 8, 197, 64, 20, 133, 76, 80, 20, 8, 197, 9, 83, 9, 52, 144, 20, 9, 198, 52, 148, 207, 29, 147, 137, 20, 8, 197, 28, 20, 129, 28, 80, 20, 0, 9, 198, 24, 83, 73, 56, 148, 212, 20, 9, 198, 20, 212, 9, 72, 148, 212, 20, 9, 198, 4, 197, 18, 84, 148, 212, 20, 9, 198, 4, 181, 9, 88, 148, 212, 20, 9, 198, 44, 147, 133, 80, 146, 192, 20, 9, 198, 77, 83, 20, 4, 224, 84, 20, 9, 198, 44, 244, 146, 20, 192, 84, 20, 9, 198, 52, 148, 212, 72, 19, 0, 20, 0, 10, 199, 88, 19, 15, 72, 148, 197, 72, 20, 10, 199, 80, 83, 5, 88, 148, 197, 72, 20, 10, 199, 72, 80, 83, 77, 84, 133, 72, 20, 10, 199, 64, 243, 1, 72, 148, 197, 72, 20, 10, 199, 52, 241, 9, 24, 144, 197, 72, 20, 10, 199, 48, 21, 9, 56, 148, 197, 72, 20, 10, 199, 44, 241, 9, 24, 144, 197, 72, 20, 10, 199, 21, 81, 143, 72, 148, 197, 72, 20, 10, 199, 4, 211, 210, 80, 148, 197, 72, 20, 9, 198, 44, 244, 148, 20, 194, 71, 20, 9, 198, 4, 197, 143, 72, 194, 71, 20, 9, 198, 4, 117, 5, 72, 194, 71, 20, 9, 198, 4, 100, 201, 56, 66, 71, 20, 14, 203, 44, 243, 135, 21, 53, 9, 60, 225, 82, 21, 64, 20, 0, 11, 200, 52, 85, 5, 61, 35, 204, 60, 112, 20, 11, 200, 8, 83, 133, 16, 144, 197, 72, 80, 68, 7, 196, 25, 85, 15, 56, 20, 9, 198, 56, 245, 129, 80, 147, 206, 20, 7, 196, 17, 84, 5, 72, 20, 11, 200, 64, 243, 25, 56, 84, 201, 76, 176, 20, 11, 200, 52, 147, 1, 56, 84, 201, 76, 176, 20, 11, 200, 52, 83, 1, 56, 84, 201, 76, 176, 20, 11, 200, 20, 180, 207, 80, 84, 137, 76, 176, 20, 11, 200, 8, 19, 19, 81, 148, 137, 76, 176, 20, 14, 68, 28, 19, 73, 56, 79, 108, 63, 6, 107, 66, 0, 20, 11, 200, 76, 19, 135, 21, 34, 78, 16, 80, 20, 11, 200, 64, 20, 212, 61, 34, 78, 16, 80, 20, 11, 200, 44, 82, 147, 21, 34, 78, 16, 80, 20, 15, 204, 44, 19, 77, 21, 34, 5, 73, 33, 73, 56, 65, 64, 20, 9, 68, 5, 4, 12, 20, 21, 0, 10, 0, 9, 198, 21, 2, 83, 44, 244, 0, 20, 12, 201, 60, 36, 203, 85, 32, 78, 80, 148, 212, 20, 12, 201, 5, 96, 78, 80, 112, 82, 16, 148, 212, 20, 12, 201, 61, 4, 15, 76, 149, 9, 60, 225, 76, 20, 14, 139, 8, 195, 166, 13, 15, 7, 12, 15, 2, 9, 14, 20, 11, 136, 195, 166, 19, 20, 5, 20, 9, 11, 20, 8, 197, 73, 80, 146, 36, 176, 20, 8, 197, 20, 208, 140, 20, 208, 20, 0, 9, 198, 64, 19, 133, 48, 148, 212, 20, 9, 198, 28, 21, 76, 48, 148, 212, 20, 9, 198, 24, 147, 129, 48, 148, 212, 20, 9, 198, 5, 33, 197, 48, 148, 212, 20, 12, 201, 8, 80, 82, 8, 82, 132, 20, 194, 71, 67, 14, 204, 60, 227, 205, 5, 67, 208, 60, 145, 84, 36, 179, 206, 6, 195, 33, 84, 137, 20, 12, 201, 45, 84, 134, 101, 36, 212, 20, 194, 71, 20, 12, 201, 24, 244, 150, 20, 180, 204, 20, 194, 71, 20, 12, 201, 8, 80, 82, 8, 82, 132, 20, 194, 71, 20, 9, 198, 72, 85, 15, 72, 146, 192, 20, 9, 198, 52, 245, 15, 72, 146, 192, 20, 0, 12, 201, 8, 83, 133, 24, 144, 197, 72, 85, 0, 68, 12, 201, 44, 243, 147, 84, 197, 1, 80, 147, 206, 20, 12, 201, 36, 225, 9, 76, 180, 133, 80, 147, 206, 20, 12, 201, 36, 212, 12, 4, 229, 1, 80, 147, 206, 20, 12, 201, 5, 84, 203, 84, 197, 1, 80, 147, 206, 20, 10, 199, 76, 82, 214, 20, 228, 197, 72, 20, 10, 199, 52, 20, 212, 85, 32, 133, 72, 20, 14, 203, 65, 54, 75, 60, 19, 129, 49, 148, 197, 72, 80, 20, 14, 203, 77, 84, 5, 72, 83, 12, 37, 5, 9, 76, 176, 20, 9, 198, 64, 243, 5, 52, 148, 203, 20, 9, 198, 56, 245, 15, 72, 148, 203, 20, 9, 198, 56, 19, 73, 8, 148, 203, 20, 9, 198, 5, 53, 5, 72, 148, 203, 20, 9, 198, 5, 37, 5, 76, 148, 203, 20, 10, 199, 44, 20, 5, 48, 192, 78, 36, 20, 14, 203, 44, 243, 134, 37, 35, 65, 56, 66, 78, 16, 80, 20, 12, 137, 18, 21, 13, 195, 166, 14, 9, 5, 14, 20, 12, 201, 44, 243, 80, 48, 144, 197, 72, 85, 0, 20, 12, 201, 8, 83, 133, 24, 144, 197, 72, 85, 0, 20, 0, 11, 200, 80, 242, 211, 36, 179, 204, 60, 112, 20, 9, 198, 76, 80, 197, 72, 225, 82, 20, 9, 198, 72, 85, 1, 8, 193, 82, 20, 9, 198, 44, 19, 85, 24, 193, 82, 20, 11, 200, 64, 243, 25, 12, 83, 148, 72, 144, 20, 11, 200, 25, 38, 71, 80, 17, 212, 36, 112, 20, 11, 200, 80, 241, 207, 48, 84, 201, 76, 176, 20, 11, 200, 4, 229, 5, 64, 83, 132, 36, 80, 20, 9, 198, 56, 17, 148, 4, 194, 78, 20, 11, 200, 80, 161, 78, 21, 34, 78, 16, 80, 20, 11, 200, 77, 98, 71, 21, 34, 78, 16, 80, 20, 11, 200, 36, 225, 129, 57, 66, 78, 16, 80, 20, 11, 200, 20, 196, 203, 21, 34, 78, 16, 80, 20, 11, 200, 16, 19, 147, 21, 34, 78, 16, 80, 20, 19, 70, 24, 19, 11, 60, 225, 82, 81, 108, 55, 49, 39, 50, 6, 36, 34, 0, 20, 11, 200, 76, 84, 150, 37, 68, 137, 12, 80, 20, 7, 196, 8, 84, 193, 80, 20, 11, 200, 25, 38, 71, 80, 17, 212, 36, 112, 20, 7, 196, 88, 20, 193, 48, 20, 7, 196, 56, 20, 193, 48, 20, 11, 200, 64, 84, 147, 36, 99, 1, 28, 80, 20, 0, 12, 201, 44, 243, 77, 4, 225, 9, 80, 148, 212, 20, 12, 201, 37, 51, 204, 5, 66, 79, 56, 148, 212, 20, 12, 201, 52, 225, 77, 61, 65, 75, 56, 146, 192, 20, 0, 19, 3, 19, 195, 165, 87, 112, 15, 87, 36, 50, 47, 0, 81, 115, 101, 110, 116, 32, 17, 3, 19, 195, 165, 87, 112, 15, 105, 35, 34, 0, 81, 104, 97, 114, 32, 27, 3, 19, 195, 165, 87, 6, 111, 15, 63, 6, 111, 87, 6, 37, 13, 0, 82, 109, 195, 165, 32, 115, 105, 103, 101, 32, 17, 3, 19, 195, 165, 87, 112, 15, 63, 6, 111, 0, 81, 109, 195, 165, 32, 20, 3, 19, 195, 165, 87, 112, 15, 82, 6, 107, 112, 0, 81, 118, 195, 166, 114, 101, 32, 22, 3, 19, 195, 165, 87, 112, 15, 55, 6, 107, 66, 106, 0, 81, 108, 195, 166, 110, 103, 101, 32, 18, 3, 19, 195, 165, 87, 112, 15, 82, 6, 110, 34, 0, 81, 118, 97, 114, 32, 21, 3, 19, 195, 165, 87, 112, 15, 105, 6, 112, 57, 47, 0, 81, 104, 195, 184, 106, 116, 32, 18, 3, 19, 195, 165, 87, 112, 15, 82, 6, 36, 55, 0, 81, 118, 105, 108, 32, 21, 3, 19, 195, 165, 87, 112, 15, 55, 6, 110, 66, 47, 0, 81, 108, 97, 110, 103, 116, 32, 19, 3, 19, 195, 165, 87, 112, 15, 79, 6, 116, 34, 0, 81, 103, 195, 184, 114, 32, 16, 3, 19, 195, 165, 87, 112, 15, 6, 107, 34, 0, 81, 101, 114, 32, 21, 3, 19, 195, 165, 87, 112, 15, 63, 6, 35, 66, 106, 0, 81, 109, 97, 110, 103, 101, 32, 23, 3, 19, 195, 165, 87, 112, 15, 63, 6, 35, 12, 57, 13, 84, 0, 81, 109, 101, 103, 101, 116, 32, 12, 201, 56, 21, 137, 28, 21, 15, 72, 148, 203, 20, 12, 201, 52, 85, 1, 48, 197, 82, 28, 148, 203, 20, 12, 201, 52, 20, 212, 60, 67, 206, 80, 148, 203, 20, 12, 201, 36, 212, 5, 72, 21, 9, 88, 148, 203, 20, 12, 201, 24, 244, 130, 73, 145, 5, 72, 148, 203, 20, 13, 202, 12, 148, 212, 21, 32, 201, 20, 228, 197, 72, 20, 15, 204, 16, 83, 73, 56, 84, 129, 48, 148, 197, 72, 85, 0, 20, 9, 198, 56, 21, 9, 60, 224, 76, 20, 0, 12, 201, 56, 21, 9, 60, 224, 76, 37, 53, 0, 20, 12, 201, 44, 244, 146, 21, 52, 15, 56, 65, 82, 20, 12, 201, 44, 243, 131, 21, 52, 201, 60, 225, 82, 20, 12, 201, 44, 243, 77, 37, 52, 201, 60, 225, 82, 20, 9, 198, 85, 48, 133, 44, 148, 203, 20, 9, 198, 72, 85, 15, 72, 148, 203, 20, 9, 198, 52, 245, 15, 72, 148, 203, 20, 9, 198, 44, 244, 193, 44, 148, 203, 20, 9, 198, 12, 243, 79, 72, 148, 203, 20, 10, 199, 44, 243, 150, 21, 37, 9, 80, 20, 9, 198, 65, 35, 211, 60, 66, 75, 20, 10, 199, 72, 85, 137, 76, 244, 129, 80, 20, 11, 136, 2, 18, 195, 166, 11, 1, 7, 5, 20, 0, 15, 204, 36, 229, 5, 72, 224, 84, 36, 243, 129, 48, 148, 212, 20, 9, 198, 80, 244, 144, 20, 65, 82, 20, 9, 198, 72, 85, 1, 72, 65, 82, 20, 9, 198, 48, 146, 214, 36, 65, 82, 20, 9, 198, 44, 244, 146, 20, 193, 82, 20, 9, 198, 44, 19, 142, 20, 193, 82, 20, 9, 198, 20, 180, 208, 20, 65, 82, 20, 9, 198, 4, 197, 5, 72, 225, 82, 20, 7, 196, 5, 4, 137, 48, 20, 7, 196, 20, 180, 197, 52, 20, 9, 68, 12, 245, 67, 32, 21, 0, 10, 0, 13, 69, 12, 19, 1, 37, 48, 49, 35, 55, 6, 107, 0, 0, 9, 198, 80, 20, 148, 20, 193, 84, 20, 12, 201, 60, 36, 203, 85, 32, 78, 80, 148, 203, 20, 12, 201, 13, 149, 15, 64, 192, 83, 52, 148, 203, 20, 12, 201, 4, 178, 213, 76, 21, 9, 88, 148, 203, 20, 0, 12, 201, 72, 21, 9, 60, 224, 76, 37, 53, 0, 20, 12, 201, 64, 84, 134, 20, 181, 9, 60, 225, 82, 20, 12, 201, 44, 243, 134, 20, 181, 9, 60, 225, 82, 20, 10, 199, 64, 19, 12, 4, 66, 85, 52, 20, 10, 199, 28, 84, 149, 56, 66, 85, 52, 20, 10, 199, 21, 2, 84, 4, 98, 85, 52, 20, 10, 199, 4, 197, 77, 36, 226, 85, 52, 20, 10, 199, 20, 212, 9, 72, 148, 205, 20, 20, 10, 199, 4, 181, 9, 88, 148, 205, 20, 20, 10, 199, 16, 84, 21, 80, 84, 133, 80, 20, 10, 199, 44, 243, 132, 20, 228, 193, 80, 20, 0, 9, 198, 28, 20, 142, 37, 51, 206, 20, 9, 198, 76, 19, 139, 80, 147, 206, 20, 9, 198, 24, 193, 75, 76, 147, 206, 20, 7, 196, 61, 5, 5, 72, 20, 9, 198, 52, 145, 210, 4, 229, 0, 20, 0, 8, 197, 25, 34, 86, 60, 192, 20, 9, 198, 44, 243, 84, 21, 52, 197, 20, 8, 197, 25, 37, 71, 4, 192, 20, 8, 197, 88, 20, 137, 4, 32, 20, 0, 13, 202, 65, 54, 75, 60, 96, 82, 52, 18, 213, 52, 20, 9, 198, 20, 180, 208, 20, 66, 84, 20, 0, 17, 67, 33, 96, 68, 82, 108, 15, 87, 112, 0, 14, 81, 115, 195, 165, 32, 6, 195, 20, 64, 128, 17, 10, 199, 48, 243, 66, 5, 33, 5, 72, 20, 10, 199, 36, 229, 5, 72, 17, 197, 72, 20, 10, 199, 8, 243, 66, 5, 33, 5, 72, 20, 10, 199, 49, 85, 135, 21, 36, 137, 28, 20, 10, 199, 44, 243, 148, 36, 225, 78, 80, 20, 10, 199, 44, 243, 147, 84, 193, 78, 80, 20, 6, 195, 25, 32, 64, 76, 0, 11, 200, 4, 68, 207, 73, 5, 9, 60, 224, 20, 7, 196, 53, 85, 5, 72, 20, 9, 198, 65, 35, 198, 37, 64, 66, 20, 9, 198, 16, 83, 79, 57, 64, 66, 20, 0, 8, 197, 72, 81, 201, 60, 224, 20, 8, 197, 80, 84, 146, 36, 224, 20, 8, 197, 8, 83, 154, 36, 224, 20, 8, 197, 44, 21, 83, 4, 192, 20, 0, 11, 200, 9, 35, 206, 44, 244, 203, 61, 0, 20, 13, 202, 72, 85, 18, 4, 228, 205, 37, 69, 5, 72, 20, 13, 202, 64, 84, 147, 64, 82, 212, 37, 100, 137, 28, 20, 0, 12, 201, 44, 243, 150, 21, 36, 193, 80, 147, 206, 20, 12, 201, 44, 243, 147, 64, 148, 129, 80, 147, 206, 20, 12, 201, 20, 180, 211, 64, 148, 129, 80, 147, 206, 20, 12, 201, 20, 180, 208, 48, 244, 129, 80, 147, 206, 20, 12, 201, 12, 149, 137, 48, 148, 193, 80, 147, 206, 20, 12, 201, 5, 85, 15, 72, 148, 193, 80, 147, 206, 20, 12, 201, 4, 48, 197, 48, 84, 129, 80, 147, 206, 20, 10, 199, 21, 50, 193, 52, 245, 5, 72, 20, 10, 199, 20, 180, 203, 49, 81, 5, 72, 20, 9, 198, 72, 84, 21, 8, 194, 75, 20, 13, 138, 16, 195, 166, 4, 1, 7, 15, 7, 9, 11, 20, 9, 198, 53, 82, 203, 20, 34, 75, 20, 10, 199, 77, 68, 137, 56, 113, 78, 80, 20, 10, 199, 44, 243, 147, 84, 209, 78, 80, 20, 0, 11, 200, 77, 80, 147, 84, 213, 9, 60, 224, 20, 11, 200, 64, 84, 131, 21, 5, 9, 60, 224, 20, 11, 200, 44, 243, 131, 21, 5, 9, 60, 224, 20, 11, 200, 20, 180, 197, 45, 85, 9, 60, 224, 20, 11, 200, 84, 197, 18, 4, 208, 82, 36, 224, 20, 0, 13, 69, 77, 65, 71, 21, 64, 87, 47, 36, 13, 70, 0, 8, 197, 4, 224, 70, 61, 32, 20, 14, 139, 6, 195, 184, 4, 5, 18, 1, 20, 9, 15, 14, 20, 12, 201, 52, 81, 9, 44, 19, 69, 57, 65, 76, 20, 12, 201, 36, 228, 212, 73, 83, 69, 57, 65, 76, 20, 9, 198, 28, 19, 15, 64, 17, 5, 20, 0, 9, 198, 25, 34, 83, 85, 33, 64, 20, 9, 198, 88, 149, 18, 36, 225, 64, 20, 9, 198, 48, 145, 82, 36, 225, 192, 20, 9, 198, 65, 83, 19, 21, 33, 64, 20, 9, 198, 25, 34, 83, 21, 33, 64, 20, 9, 198, 21, 64, 71, 21, 33, 64, 20, 9, 198, 17, 32, 71, 21, 33, 64, 20, 9, 198, 88, 83, 133, 16, 145, 192, 20, 12, 4, 95, 35, 51, 50, 69, 55, 35, 50, 49, 0, 0, 33, 67, 76, 19, 20, 87, 6, 112, 55, 47, 15, 55, 107, 57, 49, 15, 87, 6, 37, 47, 37, 0, 82, 108, 97, 107, 101, 32, 99, 105, 116, 121, 32, 10, 199, 52, 20, 207, 12, 130, 83, 80, 20, 10, 199, 52, 20, 203, 36, 226, 83, 80, 20, 10, 199, 12, 243, 21, 52, 226, 83, 80, 20, 14, 203, 4, 229, 9, 44, 243, 131, 21, 5, 9, 60, 224, 20, 10, 199, 77, 68, 137, 56, 113, 78, 76, 20, 0, 11, 200, 36, 228, 212, 73, 82, 212, 61, 32, 20, 7, 196, 36, 66, 79, 52, 20, 7, 196, 28, 194, 79, 52, 20, 17, 142, 19, 20, 195, 166, 18, 15, 16, 5, 18, 1, 20, 9, 15, 14, 20, 17, 142, 11, 15, 14, 6, 195, 184, 4, 5, 18, 1, 20, 9, 15, 14, 20, 11, 200, 65, 34, 86, 36, 193, 71, 21, 32, 20, 11, 200, 64, 192, 84, 60, 226, 75, 21, 32, 20, 11, 200, 32, 84, 129, 48, 66, 75, 21, 32, 20, 9, 198, 16, 82, 211, 81, 34, 78, 20, 9, 198, 64, 18, 201, 77, 64, 78, 20, 9, 198, 80, 20, 140, 5, 64, 78, 21, 9, 198, 52, 243, 69, 57, 64, 78, 21, 0, 12, 201, 8, 18, 212, 21, 34, 79, 48, 241, 192, 20, 12, 201, 88, 243, 20, 36, 113, 82, 36, 225, 192, 20, 12, 201, 84, 68, 129, 56, 113, 82, 36, 225, 192, 20, 12, 201, 84, 68, 12, 4, 49, 82, 36, 225, 192, 20, 12, 201, 81, 32, 70, 36, 177, 82, 36, 225, 192, 20, 12, 201, 77, 80, 140, 36, 209, 82, 36, 225, 192, 20, 12, 201, 65, 80, 140, 36, 49, 82, 36, 225, 192, 20, 12, 201, 65, 35, 212, 20, 113, 82, 36, 225, 192, 20, 12, 201, 44, 243, 147, 84, 209, 82, 36, 225, 192, 20, 12, 201, 36, 228, 208, 36, 49, 82, 36, 225, 192, 20, 12, 201, 17, 84, 12, 36, 49, 82, 36, 225, 192, 20, 12, 201, 16, 84, 12, 4, 49, 82, 36, 225, 192, 20, 12, 201, 16, 83, 65, 76, 177, 82, 36, 225, 192, 20, 12, 201, 16, 83, 65, 72, 177, 82, 36, 225, 192, 20, 12, 201, 5, 52, 207, 12, 145, 82, 36, 225, 192, 20, 12, 201, 5, 4, 12, 36, 49, 82, 36, 225, 192, 20, 8, 197, 72, 19, 135, 21, 32, 20, 8, 197, 48, 243, 135, 21, 32, 20, 12, 201, 80, 147, 18, 20, 115, 133, 48, 145, 192, 20, 8, 197, 65, 34, 77, 5, 64, 20, 8, 197, 48, 147, 133, 5, 32, 20, 8, 197, 40, 17, 213, 5, 32, 20, 8, 197, 48, 147, 133, 5, 32, 20, 12, 201, 20, 180, 203, 72, 83, 69, 57, 64, 76, 20, 10, 69, 72, 19, 135, 21, 32, 21, 0, 10, 0, 9, 198, 64, 84, 137, 76, 179, 208, 20, 9, 198, 32, 244, 143, 76, 179, 208, 20, 9, 198, 44, 244, 9, 21, 33, 64, 20, 18, 70, 9, 37, 89, 21, 33, 64, 69, 34, 114, 57, 6, 107, 12, 34, 0, 20, 9, 198, 5, 36, 197, 56, 19, 0, 20, 8, 67, 49, 82, 197, 21, 0, 10, 0, 10, 199, 64, 84, 211, 36, 210, 83, 80, 20, 10, 199, 52, 243, 129, 72, 178, 83, 80, 20, 10, 199, 24, 19, 1, 56, 114, 83, 80, 20, 10, 199, 8, 19, 132, 4, 114, 83, 80, 20, 9, 198, 81, 149, 129, 29, 66, 71, 20, 9, 198, 56, 20, 129, 29, 66, 71, 20, 9, 198, 48, 149, 129, 29, 66, 71, 20, 6, 195, 21, 64, 84, 20, 9, 198, 81, 149, 129, 29, 66, 71, 20, 9, 198, 56, 20, 129, 29, 66, 71, 20, 9, 198, 48, 149, 129, 29, 66, 71, 20, 0, 11, 200, 81, 34, 85, 52, 96, 84, 61, 32, 20, 11, 200, 72, 81, 143, 72, 208, 84, 61, 32, 20, 11, 200, 16, 82, 204, 4, 208, 84, 61, 32, 20, 15, 204, 72, 17, 9, 60, 66, 82, 36, 113, 82, 36, 225, 192, 20, 15, 204, 65, 35, 199, 56, 244, 212, 36, 49, 82, 36, 225, 192, 20, 15, 204, 16, 144, 71, 56, 244, 212, 36, 49, 82, 36, 225, 192, 20, 11, 200, 72, 84, 212, 72, 147, 135, 21, 32, 20, 7, 196, 52, 148, 197, 72, 20, 11, 200, 4, 68, 212, 72, 147, 135, 21, 32, 20, 12, 137, 16, 195, 166, 4, 9, 1, 20, 18, 9, 20, 9, 198, 81, 32, 83, 76, 21, 0, 20, 0, 9, 198, 60, 229, 15, 48, 241, 201, 20, 12, 201, 24, 245, 15, 44, 244, 9, 21, 33, 64, 20, 24, 73, 8, 243, 130, 60, 227, 137, 21, 33, 64, 69, 112, 66, 69, 112, 66, 57, 6, 107, 12, 34, 0, 20, 8, 197, 48, 144, 133, 72, 144, 20, 9, 198, 72, 83, 9, 45, 98, 69, 20, 9, 198, 76, 147, 5, 57, 66, 69, 20, 9, 198, 28, 195, 211, 5, 34, 69, 20, 8, 197, 29, 84, 129, 52, 144, 20, 0, 9, 198, 9, 81, 4, 32, 148, 212, 20, 9, 198, 88, 19, 11, 21, 34, 64, 20, 9, 198, 29, 34, 83, 21, 34, 64, 20, 9, 198, 9, 145, 199, 21, 34, 64, 20, 9, 198, 44, 20, 146, 36, 243, 0, 20, 9, 198, 85, 67, 208, 37, 50, 192, 20, 9, 198, 32, 18, 84, 37, 50, 192, 20, 9, 198, 21, 35, 212, 37, 50, 192, 20, 9, 198, 77, 147, 80, 5, 66, 64, 20, 9, 198, 24, 20, 133, 77, 66, 64, 20, 9, 198, 17, 147, 129, 77, 66, 64, 20, 9, 198, 16, 83, 69, 57, 66, 64, 20, 0, 10, 199, 88, 84, 137, 24, 144, 197, 72, 20, 10, 199, 56, 22, 137, 24, 144, 197, 72, 20, 10, 199, 44, 243, 77, 37, 69, 5, 72, 20, 10, 199, 20, 180, 208, 48, 144, 197, 72, 20, 10, 199, 4, 229, 9, 44, 148, 197, 72, 20, 6, 195, 61, 130, 68, 20, 16, 141, 18, 195, 184, 14, 20, 7, 5, 14, 15, 7, 18, 1, 6, 20, 0, 10, 135, 2, 9, 12, 12, 195, 184, 19, 20, 9, 134, 1, 11, 20, 195, 184, 18, 20, 12, 201, 8, 18, 212, 21, 34, 79, 48, 241, 201, 20, 11, 200, 24, 244, 147, 88, 20, 140, 36, 112, 20, 11, 200, 24, 244, 139, 48, 20, 140, 36, 112, 20, 11, 200, 4, 195, 79, 16, 84, 140, 36, 112, 20, 9, 198, 36, 225, 9, 88, 145, 0, 20, 12, 201, 77, 84, 16, 61, 50, 84, 61, 34, 69, 20, 11, 200, 72, 81, 133, 72, 83, 132, 84, 208, 20, 11, 200, 77, 65, 82, 20, 241, 143, 56, 144, 20, 11, 200, 89, 83, 11, 4, 226, 83, 52, 80, 20, 11, 200, 52, 244, 141, 60, 226, 83, 52, 80, 20, 11, 200, 52, 241, 5, 72, 226, 83, 52, 80, 20, 11, 200, 44, 243, 77, 84, 226, 83, 52, 80, 20, 11, 200, 32, 148, 212, 61, 34, 83, 52, 80, 20, 11, 200, 16, 241, 205, 5, 66, 83, 52, 80, 20, 11, 200, 16, 84, 208, 61, 66, 83, 52, 80, 20, 11, 200, 41, 81, 76, 76, 210, 78, 16, 80, 20, 9, 198, 16, 83, 9, 44, 21, 0, 20, 0, 8, 197, 8, 147, 208, 76, 144, 20, 12, 201, 65, 35, 208, 4, 112, 78, 16, 148, 212, 20, 12, 201, 5, 4, 15, 76, 149, 9, 60, 225, 76, 20, 12, 201, 77, 147, 133, 72, 113, 84, 37, 50, 192, 20, 12, 201, 53, 84, 201, 44, 19, 148, 37, 50, 192, 20, 12, 201, 52, 244, 203, 61, 98, 84, 37, 50, 192, 20, 12, 201, 45, 38, 83, 80, 19, 12, 37, 50, 192, 20, 12, 201, 44, 244, 205, 60, 195, 199, 37, 50, 192, 20, 12, 201, 44, 148, 143, 52, 19, 148, 37, 50, 192, 20, 12, 201, 44, 21, 1, 65, 83, 20, 37, 50, 192, 20, 12, 201, 32, 148, 212, 60, 195, 199, 37, 50, 192, 20, 12, 201, 32, 83, 73, 13, 146, 204, 37, 50, 192, 20, 9, 198, 56, 84, 20, 84, 226, 69, 20, 9, 134, 21, 18, 195, 166, 13, 9, 20, 10, 69, 76, 147, 135, 48, 80, 21, 0, 10, 24, 4, 95, 57, 88, 15, 105, 108, 55, 81, 6, 107, 63, 87, 36, 50, 87, 47, 114, 82, 13, 50, 13, 0, 0, 25, 67, 32, 243, 5, 105, 6, 39, 40, 55, 37, 50, 58, 4, 113, 50, 0, 82, 105, 110, 32, 111, 110, 101, 32, 11, 136, 19, 21, 6, 6, 12, 195, 184, 18, 20, 9, 198, 56, 21, 21, 72, 148, 212, 20, 9, 198, 52, 244, 129, 48, 148, 212, 20, 9, 198, 25, 85, 21, 72, 148, 212, 20, 16, 141, 9, 13, 16, 18, 195, 166, 7, 14, 5, 18, 9, 14, 7, 20, 13, 202, 44, 243, 12, 20, 181, 9, 88, 148, 197, 72, 20, 13, 202, 20, 180, 203, 60, 211, 85, 56, 144, 197, 72, 20, 13, 202, 20, 180, 197, 53, 3, 9, 24, 144, 197, 72, 20, 12, 201, 61, 97, 82, 88, 147, 132, 20, 194, 71, 20, 12, 201, 28, 83, 142, 20, 212, 201, 29, 66, 71, 20, 9, 198, 104, 18, 82, 37, 50, 192, 20, 9, 198, 76, 244, 130, 37, 50, 192, 20, 9, 198, 76, 84, 130, 37, 50, 192, 20, 9, 198, 44, 243, 66, 36, 224, 84, 20, 9, 198, 44, 19, 132, 36, 64, 84, 20, 9, 198, 36, 229, 5, 72, 224, 84, 20, 0, 12, 137, 12, 195, 184, 7, 19, 20, 195, 184, 18, 20, 12, 137, 4, 9, 18, 5, 11, 20, 195, 184, 18, 20, 10, 199, 44, 243, 147, 21, 37, 133, 72, 20, 9, 198, 28, 83, 133, 80, 148, 203, 20, 9, 198, 24, 19, 129, 80, 148, 203, 20, 14, 203, 64, 84, 147, 64, 82, 212, 37, 98, 83, 52, 80, 20, 10, 199, 8, 84, 135, 20, 228, 197, 72, 20, 0, 9, 198, 5, 4, 18, 21, 69, 82, 20, 13, 138, 11, 15, 18, 18, 5, 11, 20, 195, 184, 18, 20, 13, 138, 11, 15, 12, 12, 5, 11, 20, 195, 184, 18, 20, 11, 200, 77, 65, 82, 20, 241, 210, 4, 208, 20, 11, 200, 76, 82, 83, 52, 241, 210, 4, 208, 20, 11, 200, 61, 33, 193, 56, 145, 210, 4, 208, 20, 11, 200, 44, 20, 132, 36, 241, 210, 4, 208, 20, 9, 198, 77, 80, 147, 84, 209, 82, 20, 9, 198, 48, 19, 69, 57, 65, 82, 20, 9, 198, 44, 243, 66, 36, 225, 82, 20, 9, 198, 44, 19, 132, 36, 65, 82, 20, 9, 198, 36, 229, 5, 72, 225, 82, 20, 9, 198, 16, 83, 69, 57, 65, 82, 20, 9, 198, 8, 192, 78, 12, 129, 82, 20, 11, 200, 81, 35, 211, 45, 147, 4, 36, 112, 20, 11, 200, 44, 243, 4, 76, 147, 132, 36, 112, 20, 11, 200, 16, 81, 137, 56, 84, 140, 36, 112, 20, 11, 200, 16, 241, 5, 44, 17, 143, 56, 144, 20, 11, 200, 44, 84, 148, 20, 210, 78, 16, 80, 20, 6, 195, 21, 66, 75, 20, 9, 198, 64, 243, 77, 21, 32, 78, 20, 0, 12, 201, 84, 226, 86, 21, 36, 193, 48, 148, 212, 20, 12, 201, 72, 17, 9, 60, 99, 206, 37, 50, 192, 20, 12, 201, 65, 54, 75, 36, 21, 18, 37, 50, 192, 20, 12, 201, 64, 19, 148, 60, 210, 77, 37, 50, 192, 20, 12, 201, 52, 85, 1, 52, 244, 134, 37, 50, 192, 20, 12, 201, 29, 32, 70, 60, 195, 199, 37, 50, 192, 20, 12, 201, 28, 83, 77, 60, 195, 199, 37, 50, 192, 20, 12, 201, 20, 193, 75, 81, 35, 206, 37, 50, 192, 20, 12, 201, 16, 85, 5, 45, 66, 86, 37, 50, 192, 20, 12, 201, 12, 19, 9, 24, 244, 142, 37, 50, 192, 20, 12, 201, 8, 81, 18, 4, 113, 82, 37, 50, 192, 20, 12, 201, 5, 81, 9, 60, 195, 199, 37, 50, 192, 20, 12, 201, 4, 114, 84, 5, 67, 210, 37, 50, 192, 20, 12, 201, 52, 84, 137, 80, 242, 210, 5, 66, 64, 20, 12, 201, 5, 34, 83, 80, 242, 210, 5, 66, 64, 20, 12, 201, 81, 32, 78, 77, 3, 1, 57, 64, 84, 20, 0, 9, 198, 76, 84, 150, 37, 69, 84, 20, 12, 201, 44, 243, 150, 84, 196, 201, 88, 148, 203, 20, 12, 201, 33, 148, 15, 44, 243, 132, 72, 148, 203, 20, 0, 17, 142, 21, 4, 13, 1, 14, 195, 184, 22, 18, 5, 18, 9, 14, 7, 20, 12, 201, 81, 32, 78, 77, 3, 1, 57, 65, 82, 20, 9, 198, 77, 68, 143, 24, 148, 203, 20, 9, 198, 5, 68, 143, 24, 148, 203, 20, 9, 198, 5, 32, 77, 4, 148, 203, 20, 10, 199, 77, 83, 132, 9, 147, 137, 80, 20, 9, 198, 76, 83, 65, 57, 66, 75, 20, 10, 199, 77, 147, 129, 28, 241, 193, 48, 20, 0, 9, 198, 45, 84, 150, 5, 69, 82, 20, 9, 198, 81, 33, 80, 4, 225, 82, 20, 9, 198, 65, 35, 198, 37, 65, 82, 20, 9, 198, 64, 84, 131, 37, 1, 82, 20, 9, 198, 52, 245, 9, 60, 225, 82, 20, 9, 198, 36, 212, 15, 73, 65, 82, 20, 9, 198, 29, 32, 84, 36, 225, 82, 20, 9, 198, 21, 50, 207, 73, 65, 82, 20, 9, 198, 16, 81, 210, 4, 65, 82, 20, 9, 198, 4, 36, 212, 36, 225, 82, 20, 15, 204, 88, 84, 147, 36, 98, 75, 5, 67, 210, 37, 50, 192, 20, 15, 204, 36, 212, 18, 61, 98, 83, 5, 67, 210, 37, 50, 192, 20, 7, 196, 65, 84, 9, 48, 20, 10, 67, 33, 98, 83, 82, 36, 87, 0, 76, 0, 9, 198, 4, 227, 210, 20, 180, 201, 20, 12, 201, 52, 20, 203, 84, 194, 78, 37, 65, 84, 20, 0, 12, 201, 81, 35, 212, 76, 178, 83, 80, 148, 203, 20, 12, 201, 24, 147, 8, 5, 35, 79, 56, 148, 203, 20, 12, 201, 21, 67, 143, 12, 83, 148, 72, 148, 203, 20, 13, 138, 11, 195, 166, 6, 5, 18, 5, 18, 5, 20, 20, 0, 12, 137, 16, 18, 195, 166, 6, 5, 18, 5, 18, 20, 10, 199, 56, 21, 21, 72, 148, 205, 20, 20, 10, 199, 25, 85, 21, 72, 148, 205, 20, 20, 10, 199, 16, 144, 76, 20, 181, 1, 48, 20, 0, 7, 196, 5, 5, 5, 72, 20, 0, 12, 201, 72, 83, 148, 4, 34, 76, 37, 65, 84, 20, 9, 198, 56, 240, 140, 21, 52, 197, 20, 8, 197, 5, 82, 211, 36, 224, 20, 16, 141, 11, 15, 14, 6, 195, 184, 4, 5, 18, 5, 18, 5, 20, 20, 12, 201, 36, 228, 212, 73, 83, 69, 57, 64, 76, 20, 0, 13, 202, 44, 243, 12, 20, 114, 65, 48, 149, 5, 80, 20, 14, 139, 195, 184, 11, 15, 14, 15, 13, 5, 20, 18, 9, 20, 13, 202, 4, 224, 76, 24, 16, 133, 80, 148, 205, 20, 20, 13, 202, 44, 19, 3, 37, 83, 78, 37, 68, 129, 80, 20, 13, 202, 12, 19, 3, 37, 83, 78, 37, 68, 129, 80, 20, 0, 10, 199, 77, 84, 18, 20, 208, 84, 36, 20, 0, 9, 198, 4, 65, 9, 80, 147, 206, 20, 15, 204, 65, 35, 198, 21, 52, 201, 60, 224, 76, 37, 65, 84, 20, 11, 200, 4, 225, 1, 49, 84, 201, 20, 224, 20, 11, 200, 72, 84, 21, 8, 194, 75, 4, 224, 20, 7, 196, 9, 85, 1, 56, 21, 9, 198, 16, 148, 208, 85, 64, 66, 20, 0, 14, 139, 16, 18, 195, 166, 4, 9, 11, 20, 9, 15, 14, 20, 8, 197, 52, 83, 148, 60, 192, 20, 8, 197, 24, 244, 211, 36, 192, 20, 8, 197, 76, 160, 75, 4, 192, 20, 8, 197, 24, 148, 203, 4, 192, 20, 8, 197, 61, 1, 82, 4, 32, 20, 0, 9, 198, 56, 243, 142, 21, 66, 84, 20, 0, 9, 198, 12, 19, 129, 16, 148, 203, 20, 9, 198, 5, 50, 65, 80, 148, 203, 20, 10, 199, 12, 128, 78, 28, 80, 78, 80, 20, 0, 27, 68, 36, 66, 79, 80, 37, 70, 37, 6, 39, 15, 87, 108, 82, 6, 110, 66, 0, 81, 115, 97, 118, 97, 110, 116, 32, 11, 200, 12, 84, 133, 52, 243, 137, 20, 192, 20, 0, 8, 197, 12, 19, 80, 21, 32, 20, 8, 197, 80, 84, 141, 37, 64, 20, 0, 18, 70, 40, 19, 66, 61, 33, 64, 70, 57, 35, 63, 69, 39, 51, 6, 107, 0, 9, 198, 64, 20, 211, 21, 33, 64, 20, 9, 198, 28, 195, 211, 21, 33, 64, 20, 9, 198, 25, 32, 83, 21, 33, 64, 20, 12, 201, 36, 212, 5, 72, 21, 15, 72, 148, 203, 20, 12, 201, 44, 243, 66, 36, 224, 84, 61, 34, 75, 20, 9, 198, 12, 85, 1, 57, 64, 76, 20, 13, 202, 12, 128, 84, 20, 21, 66, 72, 144, 78, 80, 20, 0, 9, 198, 72, 243, 65, 57, 66, 75, 20, 9, 198, 48, 241, 201, 77, 66, 75, 20, 0, 11, 200, 44, 243, 138, 84, 226, 212, 85, 32, 20, 11, 200, 36, 229, 133, 77, 66, 84, 85, 32, 20, 11, 200, 4, 181, 80, 84, 226, 212, 85, 32, 20, 9, 198, 16, 147, 73, 77, 51, 210, 20, 11, 200, 52, 19, 20, 72, 18, 212, 21, 32, 20, 11, 200, 24, 18, 211, 36, 210, 76, 21, 32, 20, 9, 198, 72, 244, 205, 5, 34, 78, 20, 7, 196, 16, 148, 211, 20, 76, 0, 8, 197, 88, 21, 20, 21, 32, 20, 12, 201, 77, 68, 129, 8, 17, 19, 21, 33, 64, 20, 8, 197, 76, 176, 76, 21, 32, 20, 12, 201, 64, 20, 129, 25, 32, 83, 21, 33, 64, 20, 12, 201, 52, 85, 1, 77, 64, 83, 21, 33, 64, 20, 8, 197, 45, 33, 80, 21, 32, 20, 8, 197, 28, 245, 84, 21, 32, 20, 8, 197, 52, 20, 141, 37, 64, 20, 13, 138, 3, 195, 166, 19, 1, 18, 9, 19, 13, 5, 20, 9, 198, 21, 50, 193, 64, 17, 5, 20, 0, 18, 70, 29, 37, 89, 21, 33, 64, 79, 34, 114, 57, 6, 107, 12, 34, 0, 20, 9, 198, 52, 243, 143, 64, 243, 0, 20, 0, 9, 134, 22, 5, 14, 195, 184, 19, 20, 9, 198, 64, 147, 129, 29, 66, 71, 20, 15, 140, 5, 16, 9, 11, 21, 18, 195, 166, 9, 19, 13, 5, 20, 9, 198, 64, 147, 129, 29, 66, 71, 20, 0, 11, 200, 16, 83, 79, 45, 32, 84, 85, 32, 20, 10, 135, 15, 13, 9, 14, 195, 184, 19, 20, 7, 196, 4, 226, 79, 56, 20, 11, 200, 48, 244, 135, 56, 85, 20, 21, 32, 20, 11, 200, 44, 243, 80, 48, 85, 20, 21, 32, 20, 11, 200, 16, 148, 211, 36, 210, 76, 21, 32, 20, 9, 198, 24, 197, 79, 72, 145, 0, 20, 13, 138, 16, 1, 12, 195, 166, 15, 7, 18, 1, 6, 20, 9, 198, 16, 82, 193, 56, 21, 0, 20, 9, 198, 36, 229, 133, 57, 64, 82, 20, 0, 9, 198, 45, 35, 205, 61, 51, 205, 20, 12, 201, 65, 35, 199, 72, 19, 77, 21, 33, 64, 20, 8, 197, 72, 20, 197, 72, 144, 20, 16, 69, 64, 243, 9, 76, 176, 48, 39, 55, 6, 37, 87, 49, 0, 20, 9, 198, 88, 19, 11, 101, 34, 69, 20, 9, 198, 61, 32, 84, 61, 34, 69, 20, 9, 198, 80, 83, 5, 64, 21, 9, 20, 8, 197, 72, 84, 12, 36, 176, 20, 8, 197, 76, 80, 78, 12, 80, 20, 0, 12, 137, 13, 15, 14, 19, 20, 18, 195, 184, 19, 20, 9, 198, 80, 244, 211, 21, 34, 64, 20, 9, 198, 72, 20, 19, 21, 34, 64, 20, 9, 198, 49, 84, 203, 21, 34, 64, 20, 9, 198, 48, 241, 19, 21, 34, 64, 20, 9, 198, 48, 20, 19, 21, 34, 64, 20, 9, 198, 25, 84, 203, 21, 34, 64, 20, 9, 198, 12, 21, 83, 21, 34, 64, 20, 9, 198, 44, 243, 148, 72, 243, 0, 20, 9, 198, 76, 21, 68, 37, 50, 192, 20, 9, 198, 64, 241, 84, 37, 50, 192, 20, 9, 198, 65, 35, 198, 21, 66, 64, 20, 9, 198, 45, 96, 82, 80, 147, 0, 20, 9, 198, 64, 245, 5, 57, 64, 84, 20, 9, 198, 88, 17, 201, 56, 19, 0, 20, 9, 198, 72, 85, 137, 88, 19, 0, 20, 9, 198, 36, 195, 5, 28, 19, 0, 20, 0, 13, 138, 12, 9, 2, 9, 4, 9, 14, 195, 184, 19, 20, 13, 138, 6, 9, 12, 9, 19, 20, 18, 195, 184, 19, 20, 8, 133, 15, 4, 195, 184, 18, 20, 12, 137, 3, 8, 1, 21, 6, 6, 195, 184, 18, 20, 9, 198, 44, 149, 129, 29, 66, 71, 20, 10, 199, 44, 20, 141, 60, 148, 201, 56, 20, 10, 199, 4, 229, 9, 65, 148, 137, 56, 20, 10, 199, 4, 224, 84, 60, 194, 69, 56, 20, 9, 198, 44, 149, 129, 29, 66, 71, 20, 0, 13, 68, 56, 241, 204, 20, 50, 6, 39, 12, 14, 50, 0, 13, 138, 18, 195, 166, 19, 15, 14, 14, 195, 184, 18, 20, 9, 134, 11, 21, 12, 195, 184, 18, 20, 11, 200, 21, 97, 78, 81, 148, 140, 36, 112, 20, 11, 200, 80, 83, 203, 72, 21, 9, 76, 176, 20, 11, 200, 77, 147, 148, 4, 181, 9, 76, 176, 20, 11, 200, 64, 20, 129, 8, 243, 9, 76, 176, 20, 11, 200, 8, 147, 210, 101, 67, 73, 76, 176, 20, 12, 201, 60, 36, 197, 73, 96, 84, 61, 34, 69, 20, 11, 200, 45, 84, 129, 80, 244, 137, 84, 208, 20, 11, 200, 28, 195, 211, 76, 20, 137, 84, 208, 20, 9, 198, 44, 243, 15, 72, 149, 0, 20, 11, 200, 76, 243, 9, 65, 50, 83, 52, 80, 20, 11, 200, 72, 85, 77, 5, 66, 83, 52, 80, 20, 11, 200, 64, 84, 211, 36, 210, 83, 52, 80, 20, 11, 200, 52, 243, 143, 80, 82, 83, 52, 80, 20, 11, 200, 52, 243, 129, 72, 178, 83, 52, 80, 20, 11, 200, 45, 83, 20, 85, 34, 83, 52, 80, 20, 11, 200, 40, 84, 213, 37, 66, 83, 52, 80, 20, 11, 200, 16, 81, 129, 37, 66, 83, 52, 80, 20, 9, 198, 80, 83, 203, 72, 21, 0, 20, 9, 198, 16, 145, 206, 37, 64, 82, 20, 9, 198, 65, 35, 204, 21, 64, 82, 20, 0, 15, 140, 19, 11, 1, 18, 12, 1, 20, 9, 14, 195, 184, 19, 20, 8, 197, 24, 144, 146, 60, 208, 20, 12, 201, 80, 147, 79, 45, 32, 84, 37, 50, 192, 20, 12, 201, 80, 84, 129, 64, 85, 84, 37, 50, 192, 20, 12, 201, 77, 148, 212, 20, 208, 84, 37, 50, 192, 20, 12, 201, 72, 16, 149, 48, 148, 212, 37, 50, 192, 20, 12, 201, 61, 37, 15, 16, 243, 148, 37, 50, 192, 20, 12, 201, 57, 83, 73, 76, 208, 84, 37, 50, 192, 20, 12, 201, 52, 244, 134, 20, 208, 84, 37, 50, 192, 20, 12, 201, 44, 20, 137, 76, 208, 84, 37, 50, 192, 20, 12, 201, 29, 32, 86, 37, 65, 84, 37, 50, 192, 20, 12, 201, 24, 144, 133, 72, 244, 20, 37, 50, 192, 20, 12, 201, 20, 208, 140, 20, 208, 84, 37, 50, 192, 20, 12, 201, 16, 148, 12, 60, 208, 84, 37, 50, 192, 20, 12, 201, 5, 85, 15, 45, 32, 84, 37, 50, 192, 20, 12, 201, 5, 53, 9, 28, 208, 84, 37, 50, 192, 20, 12, 201, 4, 229, 9, 76, 84, 20, 37, 50, 192, 20, 12, 201, 4, 180, 201, 60, 208, 84, 37, 50, 192, 20, 12, 201, 4, 84, 143, 56, 21, 84, 37, 50, 192, 20, 9, 198, 52, 243, 69, 57, 69, 77, 20, 12, 201, 12, 83, 148, 72, 145, 149, 28, 19, 0, 20, 0, 12, 137, 13, 21, 19, 11, 21, 12, 195, 184, 19, 20, 11, 136, 13, 1, 18, 15, 4, 195, 184, 18, 20, 11, 136, 11, 18, 5, 1, 20, 195, 184, 18, 20, 11, 136, 4, 5, 11, 21, 16, 195, 184, 18, 20, 9, 198, 72, 243, 65, 56, 148, 212, 20, 9, 198, 76, 49, 78, 37, 50, 192, 20, 9, 198, 72, 243, 66, 37, 50, 192, 20, 9, 198, 37, 35, 206, 37, 50, 192, 20, 9, 198, 36, 176, 82, 37, 50, 192, 20, 9, 198, 5, 85, 5, 57, 66, 64, 20, 9, 198, 4, 211, 133, 77, 66, 64, 20, 9, 198, 72, 84, 197, 73, 96, 84, 20, 0, 12, 137, 19, 11, 21, 12, 16, 20, 195, 184, 18, 20, 12, 137, 19, 9, 7, 14, 1, 12, 195, 184, 18, 20, 12, 137, 14, 9, 22, 5, 12, 12, 195, 184, 18, 20, 12, 137, 4, 5, 20, 1, 3, 8, 195, 184, 18, 20, 10, 199, 65, 35, 204, 60, 225, 197, 72, 20, 10, 199, 24, 84, 141, 20, 229, 5, 72, 20, 10, 199, 45, 33, 80, 21, 35, 9, 28, 20, 10, 199, 4, 228, 214, 5, 35, 9, 28, 20, 14, 203, 44, 243, 147, 21, 37, 129, 80, 244, 137, 84, 208, 20, 10, 199, 76, 18, 210, 37, 53, 1, 56, 21, 0, 9, 198, 64, 20, 148, 37, 69, 82, 20, 9, 198, 16, 146, 212, 5, 69, 82, 20, 14, 139, 20, 21, 2, 5, 18, 11, 21, 12, 195, 184, 19, 20, 9, 198, 77, 81, 199, 21, 33, 82, 20, 9, 198, 76, 181, 76, 65, 65, 82, 20, 9, 198, 45, 83, 20, 37, 97, 82, 20, 9, 198, 36, 229, 133, 57, 65, 82, 20, 9, 198, 36, 225, 4, 5, 65, 82, 20, 9, 198, 32, 244, 208, 37, 65, 82, 20, 9, 198, 16, 84, 15, 73, 65, 82, 20, 9, 198, 5, 4, 18, 21, 65, 82, 20, 9, 198, 4, 36, 197, 57, 65, 82, 20, 11, 200, 76, 181, 82, 44, 17, 212, 36, 112, 20, 11, 200, 61, 34, 193, 56, 17, 212, 36, 112, 20, 11, 200, 56, 21, 142, 45, 83, 132, 36, 112, 20, 11, 200, 45, 32, 77, 64, 17, 212, 36, 112, 20, 11, 200, 44, 193, 74, 56, 211, 196, 36, 112, 20, 15, 204, 60, 227, 205, 5, 67, 208, 60, 145, 84, 37, 50, 192, 20, 11, 200, 48, 243, 66, 5, 33, 9, 76, 176, 20, 11, 200, 24, 243, 133, 52, 21, 9, 76, 176, 20, 11, 200, 20, 230, 153, 52, 21, 9, 76, 176, 20, 11, 200, 76, 83, 73, 56, 20, 137, 84, 208, 20, 11, 200, 76, 19, 129, 80, 244, 137, 84, 208, 20, 11, 200, 52, 244, 129, 80, 244, 137, 84, 208, 20, 7, 196, 24, 197, 65, 80, 20, 11, 200, 76, 181, 82, 44, 17, 212, 36, 112, 20, 11, 200, 45, 32, 77, 64, 17, 212, 36, 112, 20, 0, 14, 139, 18, 5, 11, 22, 9, 19, 9, 20, 195, 184, 18, 20, 14, 139, 16, 5, 18, 6, 15, 18, 1, 20, 195, 184, 18, 20, 14, 139, 14, 21, 13, 13, 5, 18, 1, 20, 195, 184, 18, 20, 14, 139, 9, 14, 6, 15, 18, 13, 1, 20, 195, 184, 18, 20, 14, 139, 1, 11, 11, 22, 9, 19, 9, 20, 195, 184, 18, 20, 14, 139, 16, 18, 195, 166, 20, 5, 14, 20, 9, 15, 14, 20, 12, 201, 80, 84, 146, 21, 53, 18, 37, 50, 192, 20, 12, 201, 76, 83, 22, 37, 35, 206, 37, 50, 192, 20, 12, 201, 65, 35, 214, 37, 51, 210, 37, 50, 192, 20, 12, 201, 52, 146, 210, 60, 99, 206, 37, 50, 192, 20, 12, 201, 44, 243, 131, 20, 229, 18, 37, 50, 192, 20, 12, 201, 28, 83, 195, 20, 229, 18, 37, 50, 192, 20, 12, 201, 16, 146, 212, 5, 67, 210, 37, 50, 192, 20, 0, 11, 136, 11, 22, 195, 166, 19, 20, 21, 18, 20, 15, 140, 19, 20, 5, 18, 5, 15, 20, 25, 16, 195, 184, 18, 20, 9, 198, 64, 245, 5, 57, 66, 76, 20, 12, 201, 24, 243, 11, 48, 244, 137, 77, 66, 75, 20, 9, 198, 80, 83, 80, 61, 32, 76, 20, 9, 198, 36, 229, 5, 73, 96, 76, 20, 0, 16, 141, 11, 15, 12, 12, 1, 2, 15, 18, 1, 20, 195, 184, 18, 20, 16, 141, 4, 5, 13, 15, 14, 19, 20, 18, 1, 20, 195, 184, 18, 20, 12, 201, 36, 225, 129, 57, 65, 82, 37, 53, 0, 20, 12, 201, 44, 243, 148, 36, 225, 197, 57, 65, 82, 20, 14, 203, 32, 84, 141, 4, 100, 143, 16, 149, 9, 76, 176, 20, 14, 203, 20, 180, 193, 52, 147, 129, 80, 244, 137, 84, 208, 20, 9, 198, 65, 35, 212, 21, 66, 75, 20, 0, 9, 198, 77, 68, 149, 45, 69, 82, 20, 9, 198, 76, 145, 206, 5, 69, 82, 20, 17, 142, 1, 11, 11, 15, 13, 16, 1, 7, 14, 1, 20, 195, 184, 18, 20, 9, 198, 72, 83, 79, 57, 65, 82, 20, 9, 198, 36, 229, 133, 73, 65, 82, 20, 9, 198, 28, 19, 15, 65, 1, 82, 20, 9, 198, 21, 96, 80, 61, 33, 82, 20, 9, 198, 16, 84, 18, 5, 97, 82, 20, 15, 204, 44, 243, 148, 72, 17, 9, 45, 67, 210, 37, 50, 192, 20, 15, 204, 32, 19, 12, 84, 50, 78, 5, 67, 210, 37, 50, 192, 20, 15, 204, 5, 33, 213, 52, 83, 148, 5, 67, 210, 37, 50, 192, 20, 9, 198, 24, 147, 9, 65, 2, 78, 20, 7, 196, 72, 246, 65, 48, 20, 0, 12, 201, 60, 97, 133, 57, 50, 86, 37, 65, 84, 20, 12, 201, 36, 229, 5, 57, 50, 86, 37, 65, 84, 20, 12, 201, 36, 225, 133, 72, 147, 210, 37, 65, 84, 20, 12, 201, 36, 212, 21, 49, 50, 86, 37, 65, 84, 20, 12, 201, 12, 148, 139, 84, 192, 82, 37, 65, 84, 20, 0, 9, 198, 36, 228, 212, 37, 69, 84, 20, 9, 198, 17, 80, 76, 37, 65, 84, 20, 9, 198, 36, 225, 129, 57, 66, 76, 20, 9, 198, 32, 244, 208, 37, 64, 76, 20, 0, 18, 67, 64, 112, 64, 48, 111, 15, 79, 51, 6, 111, 19, 50, 15, 108, 0, 25, 10, 199, 76, 243, 143, 72, 149, 5, 80, 20, 12, 201, 81, 84, 139, 52, 83, 137, 77, 64, 78, 21, 12, 201, 80, 17, 19, 40, 146, 201, 77, 64, 78, 21, 10, 199, 64, 145, 68, 21, 53, 1, 48, 20, 10, 199, 44, 243, 147, 60, 224, 78, 76, 20, 8, 67, 8, 32, 192, 21, 0, 10, 0, 11, 136, 3, 195, 184, 12, 9, 2, 1, 20, 20, 11, 136, 1, 4, 195, 166, 11, 22, 1, 20, 20, 9, 198, 16, 148, 203, 4, 229, 0, 20, 9, 198, 8, 18, 203, 4, 229, 0, 20, 9, 198, 72, 83, 65, 72, 176, 66, 20, 0, 11, 67, 92, 145, 78, 82, 6, 37, 12, 50, 0, 9, 198, 44, 243, 132, 100, 195, 205, 20, 12, 201, 88, 20, 137, 4, 34, 76, 37, 65, 84, 20, 12, 201, 80, 82, 206, 36, 176, 76, 37, 65, 84, 20, 12, 201, 72, 21, 9, 60, 224, 76, 37, 65, 84, 20, 12, 201, 64, 20, 129, 48, 193, 76, 37, 65, 84, 20, 12, 201, 45, 34, 77, 36, 224, 76, 37, 65, 84, 20, 12, 201, 21, 97, 78, 81, 80, 76, 37, 65, 84, 20, 8, 197, 44, 195, 210, 36, 64, 20, 8, 197, 80, 242, 211, 36, 224, 20, 9, 198, 20, 210, 78, 20, 224, 197, 20, 8, 197, 24, 85, 68, 4, 192, 20, 0, 9, 198, 21, 98, 68, 20, 228, 192, 20, 0, 10, 199, 76, 21, 9, 72, 146, 197, 72, 20, 10, 199, 72, 85, 15, 72, 146, 197, 72, 20, 10, 199, 5, 53, 5, 56, 146, 197, 72, 20, 10, 199, 76, 192, 86, 37, 53, 9, 44, 20, 10, 199, 33, 145, 18, 5, 83, 9, 44, 20, 10, 199, 61, 53, 9, 56, 66, 69, 56, 20, 10, 199, 9, 32, 83, 36, 194, 69, 56, 20, 10, 199, 44, 243, 147, 60, 224, 78, 80, 20, 8, 67, 12, 144, 64, 21, 0, 10, 0, 15, 204, 37, 36, 133, 88, 84, 147, 36, 34, 76, 37, 65, 84, 20, 15, 204, 36, 229, 5, 48, 193, 75, 81, 80, 76, 37, 65, 84, 20, 11, 200, 4, 229, 9, 80, 242, 211, 36, 224, 20, 11, 200, 52, 18, 197, 16, 243, 137, 20, 224, 20, 9, 198, 21, 66, 79, 64, 145, 78, 20, 11, 200, 4, 33, 83, 76, 147, 137, 20, 224, 20, 9, 198, 20, 193, 77, 20, 229, 0, 20, 9, 198, 64, 20, 139, 4, 229, 0, 20, 9, 198, 56, 81, 207, 80, 144, 66, 20, 0, 7, 197, 64, 84, 146, 60, 224, 8, 197, 77, 83, 6, 36, 64, 20, 8, 197, 56, 19, 139, 36, 224, 20, 15, 69, 16, 84, 211, 36, 224, 70, 36, 87, 6, 107, 66, 0, 20, 9, 198, 4, 229, 9, 56, 243, 73, 20, 8, 197, 56, 21, 84, 36, 192, 20, 8, 197, 80, 243, 135, 4, 224, 20, 8, 197, 52, 19, 135, 4, 224, 21, 8, 197, 64, 244, 212, 4, 192, 20, 8, 197, 9, 37, 84, 4, 192, 20, 0, 26, 74, 77, 21, 65, 72, 81, 1, 56, 49, 82, 20, 87, 49, 58, 6, 36, 13, 70, 35, 12, 50, 87, 112, 106, 0, 15, 140, 16, 18, 195, 166, 16, 15, 19, 9, 20, 9, 15, 14, 20, 13, 202, 56, 85, 82, 5, 53, 5, 56, 146, 197, 72, 20, 0, 11, 136, 195, 184, 11, 15, 12, 15, 7, 9, 20, 10, 199, 28, 16, 129, 72, 66, 78, 20, 20, 10, 199, 76, 82, 213, 56, 65, 82, 20, 20, 10, 199, 72, 84, 18, 20, 210, 69, 72, 20, 10, 199, 64, 83, 132, 84, 193, 82, 20, 20, 10, 199, 44, 20, 197, 72, 225, 82, 20, 20, 10, 199, 21, 82, 193, 72, 148, 212, 36, 20, 14, 203, 81, 32, 78, 77, 54, 76, 88, 19, 137, 20, 224, 20, 14, 203, 81, 32, 78, 77, 50, 76, 88, 19, 137, 20, 224, 20, 10, 199, 65, 35, 196, 84, 49, 78, 80, 20, 12, 201, 44, 241, 70, 24, 144, 201, 20, 229, 0, 20, 12, 201, 29, 85, 133, 72, 225, 77, 20, 229, 0, 20, 10, 199, 60, 97, 137, 12, 144, 78, 80, 20, 10, 199, 36, 226, 149, 72, 144, 78, 80, 20, 0, 12, 201, 8, 80, 82, 8, 82, 132, 20, 196, 197, 67, 11, 200, 12, 21, 1, 48, 243, 137, 20, 224, 20, 0, 14, 139, 16, 18, 195, 166, 22, 5, 14, 20, 9, 15, 14, 20, 8, 197, 64, 20, 140, 21, 32, 20, 8, 197, 17, 80, 140, 21, 32, 20, 8, 197, 88, 148, 197, 57, 64, 20, 8, 197, 72, 81, 197, 57, 64, 20, 8, 197, 4, 48, 197, 57, 64, 20, 0, 13, 202, 61, 97, 82, 61, 33, 5, 57, 67, 9, 28, 20, 9, 198, 32, 244, 208, 36, 49, 64, 20, 9, 198, 4, 36, 197, 56, 49, 64, 20, 9, 198, 52, 17, 18, 36, 112, 76, 20, 9, 198, 44, 243, 12, 4, 113, 64, 20, 11, 70, 52, 84, 211, 4, 113, 64, 21, 0, 10, 0, 0, 11, 200, 52, 19, 149, 24, 18, 212, 85, 32, 20, 11, 200, 5, 34, 201, 80, 82, 212, 85, 32, 20, 11, 200, 4, 66, 149, 16, 19, 148, 85, 32, 20, 9, 198, 65, 35, 214, 37, 51, 210, 20, 11, 200, 72, 17, 9, 44, 19, 9, 77, 64, 20, 11, 200, 64, 243, 25, 28, 19, 73, 77, 64, 20, 11, 200, 64, 19, 70, 48, 85, 9, 77, 64, 20, 11, 200, 28, 83, 133, 72, 19, 9, 77, 64, 20, 11, 200, 21, 96, 78, 28, 83, 9, 77, 64, 20, 11, 200, 76, 81, 9, 52, 83, 148, 21, 32, 20, 11, 200, 65, 35, 214, 36, 19, 148, 21, 32, 20, 9, 198, 44, 195, 210, 4, 210, 78, 20, 9, 198, 76, 144, 201, 48, 144, 78, 20, 11, 200, 16, 81, 133, 57, 51, 210, 5, 64, 20, 11, 200, 12, 128, 77, 64, 147, 206, 5, 64, 20, 11, 200, 44, 243, 77, 4, 225, 1, 57, 64, 20, 0, 14, 69, 40, 19, 15, 85, 128, 87, 57, 108, 6, 55, 40, 0, 8, 197, 76, 243, 9, 77, 64, 20, 8, 197, 52, 241, 9, 77, 64, 20, 8, 197, 8, 21, 9, 77, 64, 20, 12, 201, 88, 83, 148, 36, 193, 82, 36, 225, 192, 20, 12, 201, 88, 16, 195, 36, 225, 82, 36, 225, 192, 20, 12, 201, 84, 68, 207, 73, 65, 82, 36, 225, 192, 20, 12, 201, 81, 33, 80, 4, 225, 82, 36, 225, 192, 20, 12, 201, 81, 32, 78, 12, 129, 82, 36, 225, 192, 20, 12, 201, 80, 244, 144, 20, 65, 82, 36, 225, 192, 20, 12, 201, 80, 83, 80, 21, 33, 82, 36, 225, 192, 20, 12, 201, 80, 19, 80, 60, 225, 82, 36, 225, 192, 20, 12, 201, 80, 16, 133, 48, 193, 82, 36, 225, 192, 20, 12, 201, 77, 147, 139, 61, 1, 82, 36, 225, 192, 20, 12, 201, 72, 85, 1, 72, 65, 82, 36, 225, 192, 20, 12, 201, 72, 82, 214, 37, 33, 82, 36, 225, 192, 20, 12, 201, 72, 81, 149, 56, 65, 82, 36, 225, 192, 20, 12, 201, 72, 21, 9, 60, 225, 82, 36, 225, 192, 20, 12, 201, 72, 19, 80, 60, 225, 82, 36, 225, 192, 20, 12, 201, 72, 17, 134, 36, 225, 82, 36, 225, 192, 20, 12, 201, 65, 35, 205, 61, 97, 82, 36, 225, 192, 20, 12, 201, 65, 35, 202, 36, 49, 82, 36, 225, 192, 20, 12, 201, 65, 35, 198, 4, 225, 82, 36, 225, 192, 20, 12, 201, 64, 83, 12, 21, 65, 82, 36, 225, 192, 20, 12, 201, 64, 19, 12, 21, 65, 82, 36, 225, 192, 20, 12, 201, 52, 245, 73, 48, 193, 82, 36, 225, 192, 20, 12, 201, 52, 245, 9, 60, 225, 82, 36, 225, 192, 20, 12, 201, 52, 243, 5, 77, 65, 82, 36, 225, 192, 20, 12, 201, 52, 241, 5, 48, 193, 82, 36, 225, 192, 20, 12, 201, 52, 20, 135, 36, 225, 82, 36, 225, 192, 20, 12, 201, 48, 146, 214, 36, 65, 82, 36, 225, 192, 20, 12, 201, 45, 85, 133, 73, 65, 82, 36, 225, 192, 20, 12, 201, 44, 243, 150, 60, 161, 82, 36, 225, 192, 20, 12, 201, 44, 243, 148, 85, 33, 82, 36, 225, 192, 20, 12, 201, 44, 243, 80, 60, 225, 82, 36, 225, 192, 20, 12, 201, 44, 243, 80, 36, 193, 82, 36, 225, 192, 20, 12, 201, 44, 243, 77, 5, 65, 82, 36, 225, 192, 20, 12, 201, 44, 242, 203, 21, 33, 82, 36, 225, 192, 20, 12, 201, 44, 19, 142, 20, 193, 82, 36, 225, 192, 20, 12, 201, 36, 229, 143, 49, 97, 82, 36, 225, 192, 20, 12, 201, 36, 229, 133, 77, 65, 82, 36, 225, 192, 20, 12, 201, 36, 229, 133, 73, 65, 82, 36, 225, 192, 20, 12, 201, 32, 20, 144, 84, 225, 82, 36, 225, 192, 20, 12, 201, 29, 32, 86, 37, 65, 82, 36, 225, 192, 20, 12, 201, 29, 32, 84, 36, 225, 82, 36, 225, 192, 20, 12, 201, 29, 32, 78, 84, 193, 82, 36, 225, 192, 20, 12, 201, 28, 19, 15, 65, 1, 82, 36, 225, 192, 20, 12, 201, 25, 37, 83, 81, 33, 82, 36, 225, 192, 20, 12, 201, 24, 244, 198, 5, 65, 82, 36, 225, 192, 20, 12, 201, 24, 244, 141, 84, 193, 82, 36, 225, 192, 20, 12, 201, 24, 244, 141, 5, 65, 82, 36, 225, 192, 20, 12, 201, 24, 18, 212, 85, 33, 82, 36, 225, 192, 20, 12, 201, 21, 128, 197, 73, 1, 82, 36, 225, 192, 20, 12, 201, 21, 96, 80, 61, 33, 82, 36, 225, 192, 20, 12, 201, 21, 50, 207, 73, 65, 82, 36, 225, 192, 20, 12, 201, 20, 208, 129, 48, 193, 82, 36, 225, 192, 20, 12, 201, 20, 180, 208, 20, 65, 82, 36, 225, 192, 20, 12, 201, 20, 180, 197, 45, 97, 82, 36, 225, 192, 20, 12, 201, 16, 85, 5, 45, 65, 82, 36, 225, 192, 20, 12, 201, 16, 85, 1, 48, 161, 82, 36, 225, 192, 20, 12, 201, 16, 84, 201, 28, 225, 82, 36, 225, 192, 20, 12, 201, 16, 84, 18, 5, 97, 82, 36, 225, 192, 20, 12, 201, 16, 83, 79, 57, 65, 82, 36, 225, 192, 20, 12, 201, 16, 82, 193, 57, 65, 82, 36, 225, 192, 20, 12, 201, 16, 81, 210, 4, 65, 82, 36, 225, 192, 20, 12, 201, 16, 81, 140, 61, 33, 82, 36, 225, 192, 20, 12, 201, 16, 19, 65, 76, 49, 82, 36, 225, 192, 20, 12, 201, 12, 83, 147, 85, 33, 82, 36, 225, 192, 20, 12, 201, 12, 83, 69, 57, 65, 82, 36, 225, 192, 20, 12, 201, 5, 69, 18, 5, 1, 82, 36, 225, 192, 20, 12, 201, 5, 69, 1, 12, 129, 82, 36, 225, 192, 20, 12, 201, 5, 52, 207, 73, 65, 82, 36, 225, 192, 20, 12, 201, 5, 4, 15, 73, 65, 82, 36, 225, 192, 20, 12, 201, 4, 227, 149, 48, 193, 82, 36, 225, 192, 20, 12, 201, 4, 227, 133, 45, 65, 82, 36, 225, 192, 20, 12, 201, 4, 197, 5, 72, 225, 82, 36, 225, 192, 20, 12, 201, 4, 181, 9, 60, 225, 82, 36, 225, 192, 20, 12, 201, 4, 113, 210, 20, 113, 82, 36, 225, 192, 20, 12, 201, 4, 68, 207, 72, 33, 82, 36, 225, 192, 20, 12, 201, 4, 48, 197, 65, 65, 82, 36, 225, 192, 20, 12, 201, 4, 36, 207, 49, 97, 82, 36, 225, 192, 20, 8, 197, 80, 245, 80, 21, 32, 20, 8, 197, 80, 83, 132, 21, 32, 20, 8, 197, 44, 16, 200, 21, 32, 20, 8, 197, 25, 83, 132, 21, 32, 20, 8, 197, 21, 35, 196, 21, 32, 20, 12, 201, 72, 84, 18, 21, 52, 193, 48, 145, 64, 20, 8, 197, 77, 83, 6, 37, 64, 20, 8, 197, 56, 149, 18, 37, 64, 20, 12, 201, 88, 81, 197, 80, 20, 137, 76, 209, 64, 20, 12, 201, 76, 82, 213, 48, 20, 137, 76, 209, 64, 20, 12, 201, 52, 147, 9, 80, 20, 137, 76, 209, 64, 20, 12, 201, 52, 85, 1, 8, 243, 9, 76, 209, 64, 20, 12, 201, 44, 243, 139, 72, 85, 9, 76, 209, 64, 20, 12, 201, 8, 243, 19, 40, 85, 137, 76, 209, 64, 20, 12, 201, 4, 36, 207, 49, 85, 9, 76, 209, 64, 20, 12, 201, 44, 243, 139, 85, 36, 133, 56, 49, 64, 20, 8, 197, 77, 2, 78, 5, 64, 20, 8, 197, 33, 145, 18, 5, 64, 20, 8, 197, 29, 32, 78, 5, 64, 20, 8, 197, 12, 149, 18, 5, 64, 20, 8, 197, 88, 18, 193, 57, 64, 20, 10, 69, 13, 84, 147, 61, 32, 21, 0, 10, 0, 16, 141, 22, 9, 4, 5, 2, 5, 7, 195, 166, 18, 12, 9, 7, 20, 9, 198, 76, 241, 137, 76, 209, 64, 20, 9, 198, 76, 86, 9, 76, 209, 64, 20, 9, 198, 53, 85, 9, 76, 209, 64, 20, 9, 198, 52, 243, 137, 76, 209, 64, 20, 9, 198, 16, 19, 137, 76, 209, 64, 20, 9, 198, 72, 83, 79, 56, 49, 64, 20, 9, 198, 45, 83, 1, 56, 49, 64, 20, 9, 198, 77, 1, 67, 36, 19, 0, 20, 9, 198, 9, 35, 206, 44, 144, 76, 20, 9, 198, 64, 192, 77, 4, 113, 64, 20, 0, 6, 195, 4, 210, 68, 20, 13, 138, 19, 11, 195, 166, 12, 1, 7, 20, 9, 7, 20, 0, 11, 200, 53, 84, 203, 84, 192, 84, 85, 32, 20, 10, 135, 14, 5, 18, 22, 195, 184, 19, 20, 11, 200, 81, 35, 205, 64, 85, 9, 77, 64, 20, 11, 200, 40, 245, 82, 56, 19, 9, 77, 64, 20, 15, 204, 81, 32, 78, 77, 50, 210, 36, 33, 82, 36, 225, 192, 20, 15, 204, 77, 80, 147, 80, 19, 148, 37, 97, 82, 36, 225, 192, 20, 15, 204, 72, 148, 201, 44, 245, 149, 72, 65, 82, 36, 225, 192, 20, 15, 204, 64, 84, 147, 64, 82, 212, 37, 97, 82, 36, 225, 192, 20, 15, 204, 64, 84, 134, 20, 181, 9, 60, 225, 82, 36, 225, 192, 20, 15, 204, 44, 243, 134, 20, 181, 9, 60, 225, 82, 36, 225, 192, 20, 15, 204, 36, 225, 18, 20, 114, 83, 81, 33, 82, 36, 225, 192, 20, 11, 200, 36, 225, 13, 5, 32, 200, 21, 32, 20, 12, 201, 8, 85, 78, 17, 33, 82, 36, 225, 5, 20, 7, 196, 9, 85, 9, 44, 20, 18, 70, 84, 225, 21, 48, 21, 0, 112, 50, 70, 40, 55, 6, 108, 47, 0, 20, 11, 200, 8, 20, 130, 37, 69, 82, 5, 64, 20, 9, 198, 52, 19, 132, 5, 64, 82, 20, 11, 200, 24, 192, 71, 20, 195, 1, 57, 64, 20, 0, 7, 195, 85, 52, 210, 17, 42, 11, 136, 7, 5, 14, 5, 18, 195, 184, 19, 20, 10, 135, 7, 18, 1, 22, 195, 184, 18, 20, 9, 198, 44, 243, 12, 20, 114, 69, 20, 12, 201, 77, 147, 139, 72, 243, 137, 76, 209, 64, 20, 12, 201, 72, 85, 129, 56, 50, 9, 76, 209, 64, 20, 12, 201, 56, 20, 131, 37, 52, 201, 76, 209, 64, 20, 12, 201, 48, 84, 194, 36, 19, 137, 76, 209, 64, 20, 12, 201, 37, 51, 205, 61, 33, 137, 76, 209, 64, 20, 12, 201, 4, 224, 75, 72, 243, 137, 76, 209, 64, 20, 12, 201, 4, 194, 207, 32, 243, 9, 76, 209, 64, 20, 8, 197, 21, 35, 212, 36, 176, 20, 8, 197, 17, 84, 12, 36, 176, 20, 0, 18, 7, 23, 3, 39, 5, 18, 14, 5, 82, 6, 36, 87, 36, 112, 50, 13, 0, 9, 198, 4, 224, 76, 60, 114, 64, 20, 9, 198, 4, 195, 5, 72, 114, 64, 20, 9, 198, 36, 211, 79, 73, 65, 76, 20, 9, 198, 36, 211, 79, 73, 65, 76, 20, 9, 198, 4, 176, 68, 20, 210, 64, 20, 9, 198, 44, 19, 77, 21, 32, 84, 20, 9, 198, 28, 83, 137, 80, 19, 0, 20, 9, 198, 24, 197, 86, 36, 19, 0, 20, 9, 198, 5, 51, 195, 36, 19, 0, 20, 11, 70, 52, 18, 15, 56, 86, 64, 21, 0, 10, 0, 10, 199, 44, 243, 150, 21, 37, 5, 72, 20, 10, 199, 24, 147, 147, 61, 37, 5, 72, 20, 6, 195, 36, 67, 204, 20, 10, 199, 64, 243, 9, 80, 146, 197, 72, 20, 10, 199, 44, 84, 129, 52, 146, 197, 72, 20, 10, 199, 32, 243, 73, 48, 85, 9, 44, 20, 10, 199, 16, 144, 76, 20, 181, 9, 44, 20, 10, 199, 76, 195, 214, 20, 226, 69, 56, 20, 10, 199, 12, 20, 212, 36, 194, 69, 56, 20, 10, 199, 16, 243, 73, 56, 146, 193, 56, 20, 10, 199, 12, 243, 15, 52, 34, 65, 56, 20, 0, 14, 139, 9, 14, 20, 18, 1, 22, 5, 14, 195, 184, 19, 20, 11, 200, 80, 84, 141, 36, 227, 204, 60, 112, 20, 11, 200, 77, 64, 84, 36, 243, 133, 72, 80, 20, 11, 200, 5, 82, 212, 36, 243, 133, 72, 80, 20, 11, 200, 104, 147, 206, 37, 53, 9, 76, 176, 20, 11, 200, 104, 147, 66, 4, 37, 201, 76, 176, 20, 11, 200, 52, 18, 197, 16, 243, 137, 76, 176, 20, 11, 200, 44, 20, 213, 37, 53, 9, 76, 176, 20, 11, 200, 37, 51, 212, 21, 35, 73, 76, 176, 20, 11, 200, 4, 194, 207, 32, 243, 9, 76, 176, 20, 11, 200, 5, 81, 9, 80, 244, 137, 84, 208, 20, 11, 200, 81, 32, 75, 20, 245, 15, 52, 144, 20, 11, 200, 24, 147, 8, 5, 35, 79, 56, 144, 20, 11, 200, 52, 244, 134, 36, 226, 83, 52, 80, 20, 11, 200, 52, 20, 207, 12, 130, 83, 52, 80, 20, 15, 204, 20, 180, 208, 72, 84, 211, 36, 243, 137, 76, 209, 64, 20, 7, 196, 48, 241, 201, 44, 20, 9, 198, 36, 228, 197, 72, 21, 0, 20, 0, 10, 135, 16, 15, 18, 20, 195, 184, 18, 20, 12, 201, 72, 85, 77, 5, 67, 204, 60, 114, 64, 20, 12, 201, 52, 85, 5, 61, 35, 204, 60, 114, 64, 20, 12, 201, 4, 195, 5, 72, 115, 204, 60, 114, 64, 20, 9, 198, 76, 240, 201, 60, 227, 205, 20, 8, 197, 4, 224, 84, 60, 208, 20, 9, 198, 53, 144, 197, 48, 149, 77, 20, 8, 197, 64, 241, 84, 36, 176, 20, 8, 197, 56, 21, 84, 36, 176, 20, 12, 201, 17, 32, 77, 5, 69, 82, 28, 144, 84, 20, 0, 11, 136, 10, 15, 14, 7, 12, 195, 184, 18, 20, 15, 140, 5, 14, 20, 18, 5, 16, 18, 5, 14, 195, 184, 18, 20, 9, 198, 80, 83, 204, 60, 114, 64, 20, 9, 198, 72, 83, 204, 60, 114, 64, 20, 9, 198, 8, 147, 204, 60, 114, 64, 20, 16, 141, 16, 1, 12, 195, 166, 15, 7, 18, 1, 6, 9, 19, 11, 20, 13, 202, 64, 84, 137, 64, 21, 5, 80, 146, 197, 72, 20, 9, 198, 64, 20, 129, 56, 242, 68, 20, 14, 139, 16, 18, 195, 166, 20, 5, 18, 9, 20, 21, 13, 20, 9, 198, 77, 80, 147, 81, 32, 84, 20, 9, 198, 64, 20, 212, 61, 32, 84, 20, 0, 7, 195, 92, 131, 192, 17, 42, 13, 138, 7, 12, 1, 14, 4, 21, 12, 195, 184, 19, 20, 10, 199, 32, 16, 137, 48, 149, 5, 72, 20, 10, 199, 64, 245, 16, 61, 84, 146, 36, 20, 14, 203, 81, 32, 78, 76, 21, 12, 4, 229, 9, 76, 176, 20, 14, 203, 72, 85, 137, 76, 147, 206, 37, 53, 9, 76, 176, 20, 14, 203, 61, 4, 15, 73, 69, 78, 37, 53, 9, 76, 176, 20, 14, 203, 45, 33, 65, 80, 147, 206, 37, 53, 9, 76, 176, 20, 14, 203, 36, 195, 21, 76, 147, 206, 37, 53, 9, 76, 176, 20, 14, 203, 44, 194, 84, 61, 34, 68, 20, 181, 15, 52, 144, 20, 10, 199, 21, 81, 1, 36, 211, 206, 36, 20, 14, 203, 52, 16, 200, 36, 21, 133, 48, 194, 83, 52, 80, 20, 14, 203, 44, 244, 146, 21, 52, 15, 56, 64, 78, 12, 80, 20, 0, 9, 198, 76, 181, 76, 65, 69, 82, 20, 13, 138, 18, 1, 16, 16, 15, 18, 20, 195, 184, 18, 20, 13, 138, 11, 15, 12, 16, 15, 18, 20, 195, 184, 18, 20, 15, 70, 64, 20, 148, 61, 85, 0, 48, 110, 47, 6, 40, 0, 20, 9, 198, 24, 21, 86, 37, 53, 0, 20, 11, 200, 88, 84, 147, 36, 243, 133, 72, 80, 20, 9, 198, 61, 34, 69, 57, 65, 82, 20, 11, 200, 64, 20, 129, 76, 149, 9, 76, 176, 20, 11, 200, 52, 18, 193, 72, 243, 137, 76, 176, 20, 11, 200, 33, 145, 18, 5, 83, 9, 76, 176, 20, 11, 200, 21, 33, 207, 56, 243, 73, 76, 176, 20, 11, 200, 20, 208, 146, 100, 243, 137, 76, 176, 20, 11, 200, 8, 192, 83, 24, 83, 73, 76, 176, 20, 11, 200, 5, 64, 86, 37, 53, 9, 76, 176, 20, 11, 200, 4, 226, 77, 37, 53, 9, 76, 176, 20, 7, 196, 72, 145, 201, 16, 20, 11, 200, 80, 84, 129, 64, 85, 84, 36, 176, 20, 0, 12, 201, 5, 52, 217, 72, 147, 204, 60, 114, 64, 20, 0, 9, 198, 77, 147, 80, 80, 243, 64, 20, 13, 202, 29, 81, 19, 40, 19, 77, 21, 35, 9, 28, 20, 17, 206, 4, 224, 82, 44, 244, 217, 56, 66, 75, 4, 194, 83, 52, 80, 20, 9, 198, 76, 149, 21, 21, 33, 84, 20, 0, 29, 75, 77, 21, 65, 72, 81, 1, 56, 49, 82, 56, 80, 87, 49, 58, 6, 36, 13, 70, 35, 12, 50, 87, 112, 20, 50, 13, 0, 9, 198, 65, 54, 75, 60, 195, 199, 20, 10, 199, 5, 85, 15, 72, 149, 5, 80, 20, 14, 203, 36, 66, 79, 77, 147, 139, 72, 21, 9, 76, 176, 20, 14, 203, 32, 148, 212, 61, 34, 67, 37, 53, 9, 76, 176, 20, 14, 203, 8, 82, 1, 88, 147, 210, 37, 53, 9, 76, 176, 20, 10, 199, 20, 180, 203, 88, 148, 201, 80, 20, 10, 199, 44, 19, 143, 56, 146, 193, 80, 20, 10, 199, 4, 69, 133, 72, 34, 65, 48, 20, 0, 9, 198, 64, 144, 78, 37, 53, 0, 20, 9, 198, 44, 243, 131, 37, 1, 82, 20, 9, 198, 16, 148, 208, 85, 65, 82, 20, 9, 198, 12, 83, 69, 57, 65, 82, 20, 9, 198, 4, 211, 133, 77, 65, 82, 20, 7, 196, 48, 246, 65, 48, 20, 11, 200, 16, 148, 203, 72, 84, 1, 57, 48, 20, 0, 25, 73, 9, 33, 65, 44, 64, 78, 12, 83, 128, 69, 34, 107, 37, 79, 6, 70, 35, 12, 50, 87, 14, 50, 0, 12, 201, 44, 20, 9, 48, 192, 82, 37, 65, 84, 20, 12, 201, 52, 146, 210, 60, 225, 83, 36, 83, 128, 20, 12, 201, 65, 35, 211, 80, 149, 21, 21, 33, 84, 20, 0, 13, 202, 64, 245, 5, 57, 66, 65, 48, 149, 5, 80, 20, 9, 198, 64, 20, 212, 61, 32, 76, 20, 0, 8, 133, 9, 19, 195, 166, 18, 20, 10, 199, 32, 16, 137, 48, 149, 5, 80, 20, 10, 199, 88, 17, 5, 52, 80, 213, 52, 20, 10, 199, 76, 227, 194, 8, 148, 205, 20, 20, 10, 199, 64, 244, 21, 48, 148, 205, 20, 20, 10, 199, 56, 146, 9, 48, 148, 205, 20, 20, 10, 199, 37, 51, 1, 52, 148, 205, 20, 20, 10, 199, 8, 245, 21, 48, 148, 205, 20, 20, 10, 199, 21, 128, 197, 48, 193, 78, 76, 20, 0, 9, 68, 48, 241, 201, 56, 21, 0, 10, 0, 9, 198, 56, 85, 82, 4, 193, 201, 20, 8, 197, 56, 21, 9, 60, 224, 20, 12, 201, 56, 21, 9, 60, 224, 76, 37, 65, 84, 20, 8, 197, 44, 244, 142, 20, 192, 20, 8, 197, 44, 244, 142, 20, 192, 20, 8, 197, 44, 243, 147, 60, 192, 20, 16, 69, 64, 244, 12, 36, 224, 48, 112, 48, 55, 6, 107, 66, 0, 20, 8, 197, 52, 244, 140, 36, 192, 20, 12, 201, 76, 241, 137, 77, 66, 75, 21, 33, 84, 20, 9, 198, 72, 84, 212, 4, 224, 197, 20, 0, 15, 140, 16, 195, 166, 4, 1, 7, 15, 7, 9, 19, 5, 18, 20, 12, 137, 15, 18, 11, 14, 195, 184, 9, 19, 11, 20, 13, 202, 29, 83, 77, 36, 20, 129, 8, 144, 213, 52, 20, 13, 202, 64, 243, 25, 12, 83, 148, 72, 148, 205, 20, 20, 0, 10, 199, 72, 81, 146, 4, 181, 15, 72, 20, 12, 137, 20, 5, 13, 16, 15, 18, 195, 166, 18, 20, 10, 199, 77, 80, 147, 36, 66, 69, 72, 20, 10, 199, 65, 35, 196, 84, 49, 82, 20, 20, 10, 199, 64, 20, 143, 16, 145, 82, 20, 20, 10, 199, 64, 20, 134, 84, 209, 82, 20, 20, 13, 138, 195, 184, 11, 21, 13, 5, 14, 9, 19, 11, 20, 10, 199, 28, 227, 211, 80, 146, 197, 72, 20, 10, 199, 9, 32, 83, 36, 194, 65, 56, 20, 10, 199, 72, 84, 5, 48, 193, 78, 80, 20, 10, 199, 64, 84, 141, 4, 225, 78, 80, 20, 12, 201, 36, 212, 5, 73, 66, 78, 20, 229, 0, 20, 10, 199, 21, 128, 197, 48, 193, 78, 80, 20, 0, 14, 68, 64, 128, 82, 52, 81, 110, 12, 34, 63, 19, 0, 25, 13, 138, 11, 22, 1, 20, 5, 18, 14, 195, 166, 18, 20, 9, 134, 7, 5, 22, 195, 166, 18, 20, 11, 200, 81, 32, 78, 76, 149, 9, 60, 224, 20, 11, 200, 64, 84, 134, 20, 181, 9, 60, 224, 20, 11, 200, 44, 243, 150, 20, 181, 9, 60, 224, 20, 11, 200, 44, 243, 135, 21, 53, 9, 60, 224, 20, 11, 200, 44, 243, 134, 20, 181, 9, 60, 224, 20, 11, 200, 44, 21, 137, 80, 21, 9, 60, 224, 20, 11, 200, 37, 36, 137, 80, 21, 9, 60, 224, 20, 11, 200, 36, 226, 213, 8, 21, 9, 60, 224, 20, 11, 200, 36, 226, 1, 48, 21, 9, 60, 224, 20, 11, 200, 29, 32, 68, 84, 21, 9, 60, 224, 20, 11, 200, 28, 83, 73, 56, 21, 9, 60, 224, 20, 11, 200, 20, 210, 71, 72, 21, 9, 60, 224, 20, 11, 200, 16, 149, 137, 56, 21, 9, 60, 224, 20, 11, 200, 16, 81, 9, 44, 21, 9, 60, 224, 20, 11, 200, 5, 52, 9, 72, 21, 9, 60, 224, 20, 14, 139, 16, 18, 195, 166, 19, 5, 14, 20, 9, 19, 11, 20, 7, 196, 64, 193, 84, 36, 20, 9, 198, 76, 243, 22, 20, 229, 0, 20, 9, 198, 20, 210, 78, 20, 229, 0, 20, 11, 200, 61, 35, 129, 52, 83, 148, 4, 192, 20, 11, 200, 60, 48, 201, 16, 83, 148, 4, 192, 20, 11, 200, 52, 243, 149, 52, 83, 148, 4, 192, 20, 9, 198, 5, 4, 12, 36, 176, 66, 20, 0, 24, 73, 9, 33, 65, 44, 64, 78, 12, 84, 128, 69, 34, 107, 37, 79, 6, 70, 35, 12, 50, 87, 112, 0, 8, 197, 52, 245, 9, 60, 224, 20, 8, 197, 4, 181, 9, 60, 224, 20, 15, 140, 6, 15, 18, 18, 195, 166, 4, 5, 18, 9, 19, 11, 20, 8, 197, 56, 81, 210, 36, 64, 20, 8, 197, 45, 33, 84, 36, 224, 20, 8, 197, 64, 244, 148, 4, 192, 20, 0, 11, 136, 19, 15, 12, 9, 20, 195, 166, 18, 20, 11, 136, 13, 9, 12, 9, 20, 195, 166, 18, 20, 12, 137, 20, 18, 15, 11, 195, 166, 9, 19, 11, 20, 16, 141, 16, 25, 20, 8, 1, 7, 15, 18, 195, 166, 9, 19, 11, 20, 12, 137, 5, 12, 25, 19, 195, 166, 9, 19, 11, 20, 13, 202, 44, 244, 146, 21, 52, 15, 56, 65, 78, 80, 20, 9, 198, 76, 243, 22, 20, 228, 192, 20, 0, 12, 137, 16, 5, 11, 21, 14, 9, 195, 166, 18, 20, 14, 203, 77, 66, 71, 52, 21, 9, 76, 21, 9, 60, 224, 20, 14, 203, 53, 83, 20, 37, 3, 9, 44, 21, 9, 60, 224, 20, 14, 203, 36, 211, 79, 8, 147, 9, 76, 21, 9, 60, 224, 20, 14, 203, 28, 83, 133, 72, 19, 9, 76, 21, 9, 60, 224, 20, 14, 203, 16, 148, 203, 72, 147, 73, 56, 21, 9, 60, 224, 20, 14, 203, 5, 4, 18, 60, 180, 201, 52, 21, 9, 60, 224, 20, 10, 199, 88, 83, 148, 36, 193, 82, 20, 20, 10, 199, 81, 34, 85, 52, 97, 82, 20, 20, 10, 199, 52, 20, 135, 36, 225, 82, 20, 20, 10, 199, 44, 243, 147, 84, 193, 82, 20, 20, 10, 199, 16, 148, 211, 60, 50, 69, 72, 20, 10, 199, 16, 84, 18, 20, 50, 69, 72, 20, 13, 138, 6, 1, 18, 9, 19, 195, 166, 9, 19, 11, 20, 13, 138, 4, 9, 195, 166, 20, 5, 20, 9, 19, 11, 20, 10, 199, 40, 19, 137, 81, 50, 1, 72, 20, 0, 25, 73, 9, 33, 65, 44, 64, 78, 12, 84, 133, 69, 34, 107, 37, 79, 6, 70, 35, 12, 50, 87, 112, 106, 0, 11, 200, 88, 145, 9, 52, 21, 9, 60, 224, 20, 11, 200, 65, 35, 202, 20, 181, 9, 60, 224, 20, 11, 200, 56, 243, 73, 56, 21, 9, 60, 224, 20, 11, 200, 45, 83, 85, 48, 21, 9, 60, 224, 20, 11, 200, 44, 243, 139, 72, 85, 9, 60, 224, 20, 11, 200, 28, 83, 133, 72, 21, 9, 60, 224, 20, 11, 200, 24, 16, 149, 48, 21, 9, 60, 224, 20, 11, 200, 16, 84, 137, 88, 21, 9, 60, 224, 20, 11, 200, 4, 36, 207, 49, 85, 9, 60, 224, 20, 0, 8, 197, 17, 80, 140, 21, 64, 20, 15, 140, 8, 15, 13, 195, 184, 15, 16, 1, 20, 9, 19, 11, 20, 8, 197, 28, 195, 211, 5, 32, 20, 0, 14, 139, 195, 166, 7, 25, 16, 20, 15, 12, 15, 7, 9, 20, 12, 137, 8, 195, 184, 10, 13, 15, 4, 9, 7, 20, 9, 198, 53, 144, 197, 48, 145, 64, 20, 9, 198, 57, 81, 9, 76, 209, 64, 20, 9, 198, 88, 84, 148, 36, 176, 76, 20, 9, 198, 52, 20, 211, 4, 113, 64, 20, 9, 198, 44, 244, 147, 4, 113, 64, 20, 9, 198, 25, 84, 212, 4, 113, 64, 20, 9, 198, 12, 243, 12, 4, 113, 64, 20, 11, 70, 76, 50, 69, 56, 49, 64, 21, 0, 10, 0, 14, 203, 81, 32, 78, 77, 50, 210, 37, 5, 9, 60, 224, 20, 14, 203, 56, 85, 84, 72, 19, 9, 76, 21, 9, 60, 224, 20, 14, 203, 56, 21, 21, 72, 19, 9, 76, 21, 9, 60, 224, 20, 14, 203, 20, 180, 208, 72, 244, 18, 36, 21, 9, 60, 224, 20, 14, 203, 16, 81, 137, 9, 34, 76, 48, 21, 9, 60, 224, 20, 13, 138, 22, 9, 12, 11, 195, 165, 18, 12, 9, 7, 20, 0, 11, 200, 81, 35, 205, 8, 243, 137, 77, 64, 20, 11, 200, 64, 244, 201, 80, 149, 137, 77, 64, 20, 11, 200, 56, 81, 193, 80, 149, 137, 77, 64, 20, 11, 200, 12, 128, 85, 88, 147, 137, 77, 64, 20, 11, 200, 20, 180, 208, 5, 68, 137, 21, 32, 20, 11, 200, 16, 148, 133, 45, 67, 210, 5, 64, 20, 11, 200, 52, 147, 137, 77, 68, 129, 57, 64, 20, 11, 200, 24, 195, 210, 37, 52, 193, 57, 64, 20, 0, 24, 69, 88, 19, 132, 21, 64, 82, 108, 50, 13, 84, 15, 87, 47, 6, 36, 0, 81, 115, 116, 101, 103, 32, 8, 197, 5, 37, 9, 77, 64, 20, 8, 197, 4, 229, 18, 37, 64, 20, 12, 201, 65, 84, 137, 80, 19, 137, 76, 209, 64, 20, 12, 201, 64, 244, 201, 80, 149, 137, 76, 209, 64, 20, 12, 201, 56, 81, 193, 80, 149, 137, 76, 209, 64, 20, 12, 201, 32, 81, 197, 52, 243, 137, 76, 209, 64, 20, 12, 201, 12, 83, 148, 72, 19, 9, 76, 209, 64, 20, 8, 197, 12, 83, 69, 57, 64, 20, 8, 197, 9, 82, 203, 5, 32, 20, 12, 201, 16, 82, 207, 48, 193, 84, 4, 113, 64, 20, 0, 10, 135, 18, 195, 184, 7, 5, 18, 9, 20, 12, 137, 1, 14, 4, 195, 166, 7, 20, 9, 7, 20, 12, 137, 1, 12, 13, 195, 166, 7, 20, 9, 7, 20, 9, 198, 81, 37, 73, 76, 209, 64, 20, 9, 198, 5, 85, 9, 76, 209, 64, 20, 9, 198, 80, 82, 211, 80, 147, 0, 20, 6, 195, 64, 241, 77, 20, 9, 198, 76, 84, 150, 36, 49, 64, 20, 9, 198, 72, 243, 65, 56, 49, 64, 20, 9, 198, 8, 192, 77, 4, 113, 64, 20, 0, 14, 203, 88, 149, 137, 76, 82, 212, 36, 243, 137, 77, 64, 20, 13, 138, 22, 9, 12, 4, 18, 195, 165, 4, 9, 7, 20, 13, 138, 6, 15, 18, 4, 195, 166, 7, 20, 9, 7, 20, 10, 199, 16, 84, 5, 56, 65, 78, 76, 20, 0, 27, 68, 32, 21, 84, 20, 2, 39, 12, 47, 49, 40, 6, 47, 114, 12, 34, 0, 81, 99, 111, 117, 116, 117, 114, 101, 32, 11, 200, 44, 20, 130, 85, 32, 84, 61, 32, 20, 11, 200, 36, 228, 208, 37, 32, 84, 61, 32, 20, 15, 140, 195, 166, 11, 22, 9, 12, 9, 2, 18, 9, 19, 20, 20, 11, 200, 72, 83, 1, 80, 149, 137, 77, 64, 20, 11, 200, 72, 80, 201, 16, 149, 137, 77, 64, 20, 11, 200, 77, 80, 147, 80, 149, 21, 21, 32, 20, 11, 200, 65, 35, 211, 80, 149, 21, 21, 32, 20, 11, 200, 44, 243, 147, 80, 149, 21, 21, 32, 20, 14, 139, 19, 20, 15, 18, 13, 195, 166, 7, 20, 9, 7, 20, 14, 139, 15, 22, 5, 18, 13, 195, 166, 7, 20, 9, 7, 20, 14, 139, 13, 9, 19, 20, 18, 195, 184, 19, 20, 9, 7, 20, 9, 198, 21, 53, 9, 52, 21, 0, 20, 9, 68, 56, 145, 200, 80, 21, 0, 10, 0, 8, 197, 61, 51, 79, 76, 80, 20, 8, 197, 52, 147, 79, 76, 80, 20, 8, 197, 45, 80, 133, 72, 80, 20, 8, 197, 28, 17, 197, 72, 80, 20, 11, 136, 195, 166, 7, 195, 166, 9, 19, 11, 20, 8, 197, 44, 147, 133, 76, 80, 20, 12, 201, 77, 3, 206, 80, 19, 137, 76, 209, 64, 20, 12, 201, 76, 83, 73, 56, 20, 137, 76, 209, 64, 20, 12, 201, 52, 243, 133, 80, 20, 137, 76, 209, 64, 20, 12, 201, 20, 180, 212, 72, 83, 73, 76, 209, 64, 20, 12, 201, 12, 83, 148, 72, 148, 5, 80, 19, 0, 20, 8, 197, 72, 21, 129, 28, 80, 20, 0, 14, 139, 6, 25, 18, 22, 195, 166, 18, 11, 5, 18, 9, 20, 12, 137, 195, 166, 19, 20, 5, 20, 9, 19, 11, 20, 13, 202, 44, 244, 146, 21, 52, 15, 56, 65, 78, 76, 20, 9, 198, 64, 20, 139, 60, 208, 84, 20, 9, 198, 36, 195, 15, 100, 19, 0, 20, 0, 14, 139, 6, 195, 184, 4, 5, 18, 1, 12, 9, 19, 20, 20, 14, 203, 20, 180, 200, 36, 34, 84, 36, 243, 137, 77, 64, 20, 10, 199, 44, 243, 132, 60, 209, 82, 36, 20, 13, 138, 16, 25, 18, 5, 14, 195, 166, 9, 19, 11, 20, 10, 199, 52, 82, 193, 56, 146, 197, 72, 20, 10, 199, 4, 225, 18, 60, 118, 78, 36, 20, 10, 199, 5, 32, 71, 60, 226, 69, 56, 20, 10, 199, 56, 85, 82, 85, 4, 9, 56, 20, 10, 199, 12, 20, 212, 36, 194, 65, 56, 20, 0, 11, 200, 76, 180, 143, 25, 83, 15, 76, 80, 20, 9, 198, 88, 145, 5, 60, 99, 206, 20, 11, 200, 84, 68, 193, 56, 84, 137, 56, 112, 20, 11, 200, 80, 16, 149, 48, 84, 137, 56, 112, 20, 11, 200, 72, 84, 213, 52, 84, 137, 56, 112, 20, 11, 200, 64, 195, 205, 8, 84, 137, 56, 112, 20, 11, 200, 52, 243, 137, 80, 84, 137, 56, 112, 20, 11, 200, 45, 38, 80, 80, 84, 137, 56, 112, 20, 11, 200, 36, 226, 1, 48, 84, 137, 56, 112, 20, 11, 200, 28, 83, 73, 56, 84, 137, 56, 112, 20, 11, 200, 24, 242, 213, 76, 84, 137, 56, 112, 20, 11, 200, 9, 35, 206, 104, 84, 137, 56, 112, 20, 11, 200, 4, 67, 208, 80, 84, 137, 56, 112, 20, 11, 200, 60, 209, 210, 85, 4, 5, 72, 80, 20, 14, 139, 19, 1, 4, 4, 21, 11, 195, 166, 9, 19, 11, 20, 11, 200, 44, 18, 207, 24, 243, 137, 76, 176, 20, 14, 139, 5, 16, 9, 11, 21, 18, 195, 166, 9, 19, 11, 20, 11, 200, 16, 21, 1, 48, 241, 201, 76, 176, 20, 15, 204, 64, 20, 140, 4, 209, 78, 80, 20, 137, 76, 209, 64, 20, 9, 198, 76, 144, 201, 48, 145, 78, 20, 0, 8, 197, 52, 149, 15, 76, 80, 20, 12, 201, 80, 242, 211, 36, 179, 204, 60, 114, 64, 20, 9, 198, 21, 33, 207, 56, 243, 73, 20, 9, 198, 8, 192, 83, 24, 83, 73, 20, 0, 9, 198, 44, 148, 149, 72, 114, 64, 20, 17, 142, 16, 18, 195, 166, 12, 9, 13, 9, 14, 1, 18, 9, 19, 20, 20, 12, 137, 8, 195, 166, 18, 5, 20, 9, 19, 11, 20, 13, 202, 44, 20, 129, 45, 65, 82, 37, 53, 9, 44, 20, 0, 14, 203, 81, 32, 78, 76, 210, 84, 80, 84, 137, 56, 112, 20, 14, 203, 53, 149, 15, 48, 241, 201, 76, 84, 137, 56, 112, 20, 14, 203, 32, 243, 79, 28, 83, 137, 76, 84, 137, 56, 112, 20, 14, 203, 16, 148, 203, 72, 147, 73, 56, 84, 137, 56, 112, 20, 14, 203, 8, 20, 212, 5, 33, 9, 76, 84, 137, 56, 112, 20, 10, 199, 20, 115, 195, 20, 229, 18, 36, 20, 13, 138, 7, 1, 12, 9, 12, 195, 166, 9, 19, 11, 20, 18, 207, 17, 32, 77, 4, 67, 203, 84, 209, 78, 80, 20, 137, 76, 209, 64, 20, 10, 199, 77, 34, 76, 4, 226, 193, 56, 20, 12, 201, 80, 82, 211, 81, 84, 133, 72, 85, 0, 20, 0, 7, 196, 52, 20, 213, 80, 20, 16, 141, 16, 1, 12, 195, 166, 15, 14, 20, 15, 12, 15, 7, 9, 20, 11, 200, 48, 20, 153, 56, 115, 204, 60, 112, 20, 9, 198, 48, 149, 146, 37, 53, 0, 20, 11, 200, 64, 20, 129, 16, 84, 137, 56, 112, 20, 11, 200, 64, 19, 133, 48, 84, 137, 56, 112, 20, 11, 200, 45, 83, 85, 48, 84, 137, 56, 112, 20, 11, 200, 44, 20, 137, 44, 84, 137, 56, 112, 20, 11, 200, 24, 16, 149, 48, 84, 137, 56, 112, 20, 11, 200, 16, 243, 73, 56, 84, 137, 56, 112, 20, 11, 200, 16, 80, 137, 80, 84, 137, 56, 112, 20, 11, 200, 9, 35, 195, 32, 84, 137, 56, 112, 20, 9, 198, 88, 243, 20, 36, 113, 82, 20, 9, 198, 65, 80, 140, 36, 49, 82, 20, 11, 200, 64, 21, 18, 84, 194, 133, 72, 80, 20, 9, 198, 16, 149, 133, 72, 113, 82, 20, 9, 198, 16, 83, 65, 72, 177, 82, 20, 9, 198, 5, 4, 12, 36, 49, 82, 20, 11, 200, 5, 3, 203, 73, 145, 137, 76, 176, 20, 11, 200, 64, 21, 15, 28, 83, 133, 76, 80, 20, 11, 200, 25, 147, 15, 28, 83, 133, 76, 80, 20, 12, 137, 19, 195, 166, 12, 1, 18, 9, 21, 13, 20, 11, 200, 25, 148, 201, 60, 115, 143, 52, 144, 20, 9, 134, 18, 21, 13, 195, 166, 14, 20, 11, 200, 16, 81, 133, 45, 68, 137, 12, 80, 20, 11, 200, 12, 19, 79, 84, 99, 1, 28, 80, 20, 0, 6, 20, 252, 0, 0, 0, 121, 0, 0, 0, 246, 0, 0, 0, 248, 0, 0, 0, 228, 0, 0, 0, 230, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 99, 107, 0, 110, 107, 0, 110, 103, 0, 107, 0, 103, 0, 113, 0, 106, 0, 7, 6, 18, 67, 112, 0, 98, 0, 102, 0, 118, 0, 109, 0, 7, 6, 18, 68, 108, 0, 100, 0, 7, 6, 18, 69, 195, 184, 0, 117, 0, 121, 0, 105, 0, 111, 0, 7, 6, 18, 70, 195, 166, 0, 195, 165, 0, 97, 0, 7, 6, 18, 71, 112, 0, 98, 0, 7, 6, 18, 72, 116, 0, 107, 0, 118, 0, 7, 6, 18, 73, 115, 112, 0, 115, 116, 0, 115, 107, 0, 7, 6, 18, 74, 109, 0, 110, 0, 7, 6, 18, 75, 99, 0, 107, 0, 7, 6, 18, 76, 97, 0, 101, 0, 7, 6, 97, 102, 0, 1, 114, 103, 10, 2, 28, 33, 3, 6, 110, 81, 0, 4, 8, 112, 3, 35, 81, 0, 102, 1, 107, 2, 101, 0, 102, 1, 108, 2, 101, 0, 102, 1, 116, 2, 101, 0, 102, 1, 116, 115, 2, 101, 3, 108, 81, 0, 1, 114, 103, 10, 2, 105, 28, 33, 3, 110, 81, 6, 0, 7, 6, 97, 103, 0, 1, 108, 114, 111, 102, 3, 2, 108, 57, 0, 1, 98, 108, 105, 116, 2, 101, 3, 6, 108, 12, 0, 101, 1, 10, 2, 28, 33, 12, 12, 12, 3, 6, 108, 12, 89, 13, 0, 101, 1, 10, 2, 114, 28, 33, 12, 12, 3, 6, 108, 12, 89, 112, 0, 4, 110, 1, 115, 97, 108, 2, 101, 3, 6, 108, 50, 57, 0, 110, 1, 116, 101, 114, 98, 2, 101, 0, 101, 1, 114, 10, 2, 28, 33, 12, 12, 3, 6, 110, 12, 89, 13, 0, 1, 116, 2, 108, 105, 97, 116, 101, 108, 108, 101, 3, 21, 105, 116, 0, 4, 1, 102, 2, 21, 3, 35, 40, 0, 1, 108, 2, 17, 67, 0, 1, 108, 102, 2, 114, 101, 0, 1, 108, 115, 2, 17, 67, 21, 0, 1, 108, 115, 2, 115, 118, 195, 166, 114, 100, 0, 103, 1, 108, 115, 2, 101, 3, 35, 49, 0, 1, 116, 2, 17, 67, 3, 35, 58, 0, 4, 1, 102, 2, 116, 101, 114, 3, 35, 79, 0, 1, 106, 2, 116, 0, 1, 106, 2, 117, 97, 114, 0, 1, 108, 115, 2, 116, 101, 12, 0, 1, 108, 115, 2, 116, 110, 12, 0, 1, 109, 2, 116, 0, 1, 115, 2, 116, 12, 0, 1, 118, 115, 100, 101, 104, 114, 101, 107, 107, 105, 115, 2, 116, 0, 1, 118, 115, 101, 114, 166, 195, 2, 116, 0, 1, 118, 115, 103, 110, 105, 114, 101, 107, 114, 97, 112, 2, 116, 0, 1, 118, 115, 107, 105, 116, 117, 98, 2, 116, 0, 1, 118, 115, 108, 97, 116, 105, 112, 115, 111, 104, 2, 116, 0, 2, 116, 105, 103, 0, 8, 108, 115, 2, 115, 32, 0, 8, 108, 115, 2, 115, 101, 110, 0, 8, 98, 2, 101, 108, 12, 3, 107, 57, 79, 0, 4, 1, 100, 21, 2, 32, 12, 12, 3, 108, 0, 1, 100, 115, 0, 1, 116, 2, 102, 97, 116, 0, 4, 1, 98, 2, 102, 114, 3, 108, 4, 0, 1, 98, 2, 105, 0, 1, 98, 2, 112, 195, 165, 0, 1, 98, 2, 116, 105, 108, 0, 1, 116, 2, 115, 101, 108, 118, 3, 108, 6, 0, 4, 1, 98, 2, 111, 118, 101, 114, 3, 108, 9, 0, 1, 98, 2, 117, 100, 0, 1, 98, 2, 118, 101, 100, 0, 4, 1, 106, 2, 101, 12, 3, 108, 12, 0, 100, 1, 115, 2, 101, 12, 0, 100, 1, 108, 2, 101, 3, 108, 12, 57, 0, 101, 1, 17, 67, 2, 12, 3, 108, 12, 57, 13, 0, 101, 114, 1, 17, 67, 2, 12, 3, 108, 12, 57, 112, 0, 4, 101, 1, 100, 110, 97, 98, 3, 108, 12, 89, 13, 0, 101, 1, 103, 2, 32, 12, 0, 101, 1, 112, 2, 12, 12, 0, 101, 1, 115, 115, 97, 109, 101, 116, 114, 101, 106, 104, 0, 101, 1, 116, 117, 102, 102, 97, 0, 101, 1, 103, 97, 98, 3, 108, 12, 89, 106, 0, 110, 1, 116, 115, 97, 107, 2, 101, 116, 3, 108, 50, 57, 6, 0, 4, 1, 17, 67, 115, 2, 12, 3, 108, 57, 0, 1, 98, 2, 101, 102, 116, 101, 114, 0, 1, 98, 2, 101, 114, 105, 12, 0, 1, 98, 101, 109, 109, 101, 106, 104, 2, 32, 0, 1, 100, 2, 32, 0, 1, 100, 2, 101, 12, 0, 1, 100, 2, 115, 32, 0, 1, 108, 2, 32, 0, 1, 108, 2, 110, 0, 1, 108, 2, 114, 101, 0, 1, 108, 2, 114, 101, 12, 0, 1, 108, 112, 0, 1, 108, 115, 2, 110, 101, 0, 1, 108, 115, 2, 110, 105, 12, 0, 1, 108, 115, 109, 101, 110, 110, 101, 103, 2, 12, 0, 1, 108, 115, 112, 111, 0, 1, 115, 110, 97, 114, 2, 110, 0, 1, 116, 2, 32, 0, 1, 116, 2, 110, 101, 0, 1, 118, 115, 2, 116, 0, 1, 118, 115, 101, 110, 118, 101, 0, 1, 118, 115, 115, 100, 110, 165, 195, 0, 2, 110, 105, 110, 103, 0, 8, 18, 71, 2, 32, 0, 8, 106, 2, 32, 0, 8, 115, 2, 116, 101, 32, 0, 4, 101, 1, 108, 115, 115, 108, 101, 115, 100, 166, 195, 114, 2, 110, 3, 108, 57, 13, 0, 101, 1, 116, 2, 108, 115, 101, 0, 101, 1, 116, 101, 98, 0, 101, 1, 116, 101, 114, 97, 118, 0, 101, 1, 116, 101, 114, 111, 102, 0, 101, 8, 2, 32, 3, 108, 57, 106, 0, 4, 101, 110, 100, 1, 98, 2, 101, 32, 104, 101, 100, 3, 108, 57, 106, 50, 0, 101, 110, 100, 1, 98, 2, 101, 32, 115, 111, 108, 0, 101, 110, 100, 1, 98, 2, 101, 32, 118, 97, 114, 109, 0, 4, 101, 2, 114, 110, 3, 108, 57, 112, 0, 101, 114, 1, 116, 116, 103, 97, 105, 2, 32, 0, 101, 114, 2, 104, 195, 184, 110, 0, 101, 114, 8, 2, 32, 0, 110, 97, 110, 1, 116, 114, 97, 3, 108, 66, 110, 66, 0, 4, 1, 100, 2, 111, 103, 12, 3, 108, 79, 0, 1, 108, 112, 2, 105, 0, 103, 1, 116, 2, 101, 0, 4, 1, 112, 115, 2, 101, 116, 116, 3, 108, 79, 6, 0, 104, 1, 112, 115, 2, 101, 116, 116, 0, 101, 1, 116, 117, 109, 2, 110, 3, 108, 79, 6, 36, 0, 101, 116, 101, 115, 1, 116, 3, 108, 79, 6, 36, 47, 106, 87, 0, 101, 8, 2, 110, 116, 12, 12, 3, 108, 79, 6, 107, 0, 101, 2, 110, 116, 12, 12, 3, 108, 79, 107, 0, 101, 114, 1, 103, 2, 101, 12, 3, 108, 89, 6, 36, 0, 101, 1, 10, 2, 114, 101, 28, 33, 12, 3, 108, 89, 6, 36, 13, 0, 4, 101, 1, 110, 111, 3, 108, 89, 13, 0, 101, 1, 115, 115, 97, 0, 101, 1, 116, 110, 97, 108, 112, 0, 101, 1, 116, 101, 3, 108, 89, 106, 0, 101, 114, 1, 116, 101, 3, 108, 89, 112, 0, 4, 101, 114, 1, 116, 101, 114, 111, 102, 3, 110, 34, 0, 101, 114, 8, 116, 2, 32, 0, 4, 1, 98, 2, 17, 65, 110, 3, 110, 40, 0, 1, 98, 2, 18, 66, 0, 1, 98, 2, 98, 0, 1, 98, 2, 100, 0, 1, 98, 2, 102, 0, 1, 98, 2, 104, 12, 0, 1, 98, 2, 107, 0, 1, 98, 2, 108, 0, 1, 98, 2, 109, 0, 1, 98, 2, 112, 0, 1, 98, 2, 114, 117, 100, 0, 1, 98, 2, 115, 0, 1, 98, 2, 116, 21, 0, 1, 98, 2, 117, 100, 103, 97, 110, 103, 0, 1, 98, 2, 118, 0, 1, 100, 2, 105, 110, 115, 116, 105, 0, 1, 100, 2, 108, 21, 12, 0, 1, 108, 115, 2, 115, 105, 100, 101, 0, 1, 108, 115, 2, 115, 109, 195, 165, 108, 0, 1, 108, 115, 2, 116, 105, 108, 102, 0, 1, 108, 115, 101, 2, 108, 17, 65, 0, 1, 112, 115, 2, 110, 117, 109, 0, 1, 114, 2, 101, 12, 0, 1, 115, 2, 110, 0, 1, 115, 2, 115, 195, 184, 0, 110, 1, 116, 115, 3, 110, 40, 66, 0, 101, 110, 100, 1, 98, 2, 101, 3, 110, 40, 107, 50, 0, 101, 114, 1, 108, 102, 2, 109, 117, 115, 3, 110, 40, 112, 0, 1, 107, 115, 2, 108, 101, 114, 3, 110, 58, 0, 101, 1, 114, 2, 12, 12, 3, 110, 58, 13, 0, 101, 114, 1, 114, 2, 12, 12, 3, 110, 58, 112, 0, 1, 98, 2, 116, 101, 3, 110, 79, 0, 101, 100, 105, 101, 1, 114, 116, 3, 110, 79, 6, 36, 84, 57, 13, 0, 101, 1, 114, 102, 102, 117, 115, 2, 116, 116, 101, 3, 110, 89, 6, 107, 0, 7, 6, 97, 108, 0, 4, 8, 98, 97, 107, 2, 101, 3, 6, 108, 12, 55, 0, 8, 98, 109, 105, 116, 2, 101, 0, 8, 100, 110, 97, 107, 115, 2, 101, 0, 8, 103, 101, 114, 2, 101, 0, 8, 104, 114, 111, 102, 2, 101, 0, 8, 105, 114, 101, 116, 97, 109, 2, 101, 0, 8, 105, 116, 97, 114, 103, 2, 101, 0, 8, 105, 116, 110, 101, 116, 111, 112, 2, 101, 0, 8, 107, 111, 108, 2, 101, 0, 8, 109, 114, 111, 102, 2, 101, 0, 8, 110, 105, 102, 2, 101, 0, 8, 110, 110, 101, 105, 98, 0, 8, 110, 110, 101, 105, 114, 116, 2, 101, 0, 8, 115, 115, 105, 109, 2, 101, 0, 8, 116, 114, 111, 102, 2, 101, 0, 8, 116, 114, 111, 109, 111, 116, 108, 97, 115, 2, 101, 0, 8, 117, 100, 97, 114, 103, 2, 101, 0, 8, 117, 110, 97, 109, 2, 101, 0, 4, 101, 8, 105, 99, 101, 112, 115, 2, 32, 3, 6, 108, 12, 55, 13, 0, 101, 8, 105, 116, 110, 101, 114, 101, 102, 102, 105, 100, 0, 4, 1, 100, 101, 112, 115, 2, 115, 107, 3, 6, 108, 55, 0, 1, 117, 115, 107, 101, 115, 0, 4, 8, 114, 101, 109, 117, 110, 2, 101, 3, 6, 110, 12, 55, 0, 8, 114, 111, 109, 2, 101, 0, 8, 114, 111, 116, 115, 97, 112, 2, 101, 0, 4, 8, 110, 105, 114, 117, 3, 7, 108, 12, 55, 0, 8, 110, 111, 105, 116, 97, 114, 2, 101, 0, 8, 110, 111, 115, 114, 101, 112, 2, 101, 0, 7, 6, 98, 101, 0, 97, 117, 8, 3, 2, 69, 39, 0, 8, 2, 21, 3, 69, 2, 36, 0, 8, 2, 106, 108, 101, 3, 69, 35, 0, 4, 103, 8, 2, 98, 108, 101, 110, 100, 101, 3, 69, 35, 57, 0, 103, 8, 2, 109, 97, 110, 100, 0, 103, 8, 2, 110, 105, 110, 103, 0, 4, 8, 2, 100, 100, 105, 110, 103, 3, 69, 36, 0, 8, 2, 100, 101, 0, 8, 2, 101, 116, 97, 32, 0, 8, 2, 110, 97, 114, 98, 101, 106, 100, 101, 0, 8, 2, 110, 98, 98, 117, 107, 0, 8, 2, 110, 98, 114, 117, 100, 0, 8, 2, 110, 101, 100, 100, 101, 114, 0, 8, 2, 110, 101, 116, 0, 8, 2, 110, 102, 101, 100, 116, 0, 8, 2, 110, 102, 105, 115, 107, 0, 8, 2, 110, 102, 114, 105, 0, 8, 2, 110, 107, 108, 0, 8, 2, 110, 109, 101, 108, 0, 8, 2, 110, 109, 101, 108, 0, 8, 2, 110, 112, 105, 98, 101, 0, 8, 2, 110, 112, 108, 97, 100, 115, 0, 8, 2, 110, 114, 97, 100, 0, 8, 2, 110, 115, 107, 105, 110, 110, 101, 0, 8, 2, 110, 115, 112, 195, 166, 110, 100, 0, 8, 2, 110, 116, 195, 184, 106, 0, 8, 2, 116, 97, 115, 116, 114, 195, 165, 108, 0, 8, 2, 116, 97, 116, 114, 111, 110, 0, 8, 2, 116, 97, 118, 101, 114, 115, 105, 111, 110, 0, 8, 2, 116, 101, 108, 0, 8, 2, 116, 108, 0, 101, 116, 104, 111, 118, 101, 110, 3, 69, 36, 47, 39, 82, 106, 50, 0, 101, 99, 104, 8, 3, 69, 37, 74, 0, 4, 8, 2, 100, 114, 101, 3, 69, 107, 0, 8, 2, 100, 114, 105, 110, 103, 0, 8, 2, 100, 115, 116, 101, 0, 8, 2, 103, 103, 101, 0, 8, 2, 106, 100, 115, 0, 8, 2, 108, 103, 105, 0, 8, 2, 108, 108, 97, 0, 8, 2, 110, 98, 114, 195, 166, 107, 0, 8, 2, 110, 99, 104, 109, 97, 114, 107, 0, 8, 2, 110, 101, 110, 100, 101, 0, 8, 2, 110, 103, 101, 108, 0, 8, 2, 110, 103, 110, 97, 0, 8, 2, 110, 104, 0, 8, 2, 110, 106, 97, 109, 105, 110, 0, 8, 2, 110, 108, 0, 8, 2, 110, 118, 0, 8, 2, 114, 98, 0, 8, 2, 114, 103, 101, 110, 32, 0, 105, 103, 101, 8, 3, 69, 107, 12, 89, 0, 114, 107, 101, 108, 101, 121, 3, 69, 116, 49, 59, 37, 0, 7, 6, 101, 100, 0, 4, 1, 112, 105, 99, 111, 108, 101, 118, 2, 101, 3, 6, 36, 84, 0, 1, 116, 115, 102, 97, 2, 107, 111, 109, 0, 1, 114, 100, 110, 117, 104, 2, 12, 3, 13, 12, 84, 0, 1, 118, 111, 104, 3, 13, 84, 0, 101, 1, 21, 2, 32, 3, 13, 84, 13, 0, 4, 1, 110, 114, 101, 100, 2, 101, 3, 36, 84, 0, 1, 110, 114, 101, 104, 2, 101, 0, 4, 101, 1, 98, 108, 105, 116, 3, 36, 84, 13, 0, 101, 1, 98, 109, 101, 2, 32, 12, 0, 101, 1, 98, 109, 101, 2, 116, 32, 12, 0, 101, 1, 102, 2, 12, 12, 0, 101, 1, 104, 2, 12, 0, 101, 1, 107, 10, 2, 12, 0, 101, 1, 108, 100, 108, 105, 118, 2, 12, 0, 101, 1, 108, 100, 110, 105, 2, 12, 0, 101, 1, 108, 100, 117, 2, 12, 0, 101, 1, 108, 102, 97, 2, 12, 0, 101, 1, 108, 106, 101, 118, 2, 12, 0, 101, 1, 108, 110, 101, 104, 2, 12, 0, 101, 1, 108, 112, 111, 2, 12, 0, 101, 1, 108, 114, 111, 102, 2, 12, 0, 101, 1, 108, 115, 105, 109, 2, 12, 0, 101, 1, 108, 115, 118, 105, 108, 2, 12, 0, 101, 1, 108, 116, 114, 111, 98, 2, 12, 0, 101, 1, 116, 101, 114, 2, 12, 0, 101, 1, 109, 115, 3, 36, 84, 106, 0, 4, 101, 114, 1, 98, 108, 105, 116, 3, 36, 84, 112, 0, 101, 114, 1, 102, 2, 32, 12, 0, 101, 114, 1, 104, 2, 12, 0, 101, 114, 1, 108, 100, 108, 105, 118, 2, 12, 0, 101, 114, 1, 108, 100, 110, 105, 2, 12, 0, 101, 114, 1, 108, 100, 117, 2, 12, 0, 101, 114, 1, 108, 102, 97, 2, 12, 0, 101, 114, 1, 108, 106, 101, 118, 2, 12, 0, 101, 114, 1, 108, 110, 101, 104, 2, 12, 0, 101, 114, 1, 108, 112, 111, 2, 12, 0, 101, 114, 1, 108, 114, 111, 102, 2, 12, 0, 101, 114, 1, 108, 115, 105, 109, 2, 12, 0, 101, 114, 1, 108, 115, 118, 105, 108, 2, 12, 0, 101, 114, 1, 108, 116, 114, 111, 98, 2, 12, 0, 101, 114, 1, 116, 101, 114, 2, 12, 0, 101, 1, 114, 10, 2, 32, 3, 106, 84, 13, 0, 4, 101, 1, 108, 116, 114, 111, 98, 3, 107, 84, 13, 0, 101, 1, 114, 98, 108, 101, 104, 0, 101, 1, 114, 100, 108, 105, 118, 2, 32, 12, 0, 101, 1, 114, 101, 98, 2, 32, 12, 0, 101, 1, 114, 101, 108, 2, 32, 12, 0, 101, 1, 114, 101, 110, 114, 184, 195, 0, 101, 1, 114, 101, 115, 112, 101, 118, 104, 2, 32, 12, 0, 101, 1, 114, 101, 116, 116, 111, 114, 2, 32, 12, 0, 101, 1, 114, 112, 115, 2, 32, 12, 0, 101, 1, 114, 114, 101, 2, 12, 0, 101, 1, 114, 115, 118, 111, 107, 115, 108, 101, 0, 101, 1, 114, 118, 2, 32, 12, 0, 101, 8, 114, 98, 2, 32, 12, 0, 101, 8, 114, 102, 2, 32, 12, 0, 7, 6, 101, 108, 0, 4, 1, 98, 101, 114, 3, 6, 36, 55, 0, 1, 98, 111, 108, 2, 105, 97, 0, 1, 100, 97, 116, 105, 99, 0, 1, 100, 105, 102, 0, 1, 100, 110, 111, 114, 0, 1, 100, 114, 166, 195, 115, 2, 101, 115, 0, 1, 101, 114, 0, 1, 105, 98, 114, 101, 118, 0, 1, 108, 108, 97, 104, 2, 117, 106, 97, 0, 1, 109, 97, 107, 0, 1, 109, 109, 97, 114, 103, 111, 114, 112, 0, 1, 112, 111, 114, 112, 0, 1, 115, 100, 110, 117, 2, 105, 103, 0, 1, 115, 114, 101, 118, 105, 110, 117, 0, 1, 116, 110, 97, 114, 97, 116, 0, 1, 116, 114, 111, 112, 115, 0, 1, 117, 2, 32, 12, 0, 1, 117, 2, 116, 12, 0, 1, 117, 122, 101, 110, 101, 118, 2, 97, 0, 1, 118, 97, 106, 0, 1, 118, 117, 106, 0, 1, 118, 165, 195, 115, 0, 8, 98, 97, 116, 0, 8, 105, 99, 105, 102, 102, 111, 2, 12, 0, 8, 110, 97, 112, 0, 8, 112, 108, 97, 107, 115, 0, 105, 103, 1, 115, 10, 2, 28, 33, 3, 6, 36, 55, 37, 0, 4, 1, 99, 114, 97, 112, 3, 6, 107, 55, 0, 1, 100, 97, 116, 114, 111, 109, 0, 1, 100, 101, 112, 2, 12, 0, 1, 100, 114, 97, 115, 0, 1, 105, 114, 101, 116, 97, 109, 0, 1, 108, 108, 97, 114, 97, 112, 0, 1, 109, 114, 111, 102, 2, 108, 0, 1, 109, 114, 111, 102, 2, 116, 0, 1, 112, 97, 107, 0, 1, 114, 111, 102, 2, 115, 0, 1, 116, 110, 101, 109, 97, 107, 105, 100, 101, 109, 0, 1, 116, 111, 109, 0, 1, 116, 115, 97, 112, 0, 1, 118, 114, 97, 102, 0, 1, 118, 117, 110, 0, 8, 100, 97, 107, 105, 114, 102, 2, 108, 0, 103, 1, 104, 101, 108, 108, 97, 2, 101, 110, 115, 3, 6, 107, 55, 57, 0, 4, 8, 114, 107, 97, 109, 2, 12, 3, 6, 109, 55, 0, 8, 114, 111, 102, 0, 1, 10, 2, 108, 28, 33, 12, 12, 12, 3, 7, 107, 0, 4, 1, 10, 2, 28, 33, 12, 12, 12, 3, 7, 107, 55, 0, 1, 10, 2, 116, 28, 33, 0, 1, 116, 97, 107, 115, 117, 109, 0, 1, 114, 10, 2, 108, 28, 33, 12, 12, 12, 3, 7, 109, 0, 1, 114, 10, 2, 28, 33, 12, 12, 3, 7, 109, 55, 0, 105, 103, 1, 10, 2, 28, 33, 3, 8, 13, 55, 37, 0, 1, 117, 107, 115, 109, 101, 110, 110, 101, 103, 2, 105, 103, 3, 8, 36, 55, 0, 4, 1, 21, 2, 17, 65, 114, 3, 13, 55, 0, 1, 21, 2, 32, 0, 1, 21, 2, 115, 0, 1, 21, 2, 116, 32, 0, 1, 98, 97, 116, 107, 101, 112, 115, 101, 114, 0, 1, 100, 101, 107, 2, 12, 0, 1, 100, 101, 108, 2, 115, 101, 0, 1, 100, 110, 97, 2, 115, 101, 0, 1, 100, 110, 97, 104, 0, 1, 105, 110, 97, 112, 115, 0, 1, 107, 115, 114, 0, 8, 114, 111, 102, 2, 105, 103, 0, 101, 116, 1, 10, 2, 28, 33, 3, 13, 55, 6, 107, 47, 0, 101, 103, 1, 108, 117, 106, 3, 13, 55, 35, 57, 0, 4, 1, 10, 2, 101, 118, 3, 36, 55, 0, 1, 21, 2, 195, 184, 115, 0, 1, 98, 97, 116, 0, 1, 100, 2, 101, 12, 0, 1, 100, 2, 105, 110, 103, 0, 1, 100, 2, 116, 12, 0, 1, 100, 100, 101, 109, 0, 1, 100, 100, 110, 97, 116, 115, 101, 98, 0, 1, 100, 100, 110, 117, 114, 0, 1, 100, 101, 2, 12, 0, 1, 100, 101, 100, 0, 1, 100, 101, 107, 107, 105, 116, 115, 0, 1, 100, 101, 118, 114, 101, 115, 101, 114, 0, 1, 100, 103, 97, 98, 0, 1, 100, 107, 184, 195, 114, 98, 0, 1, 100, 110, 97, 0, 1, 100, 110, 101, 106, 101, 0, 1, 100, 110, 101, 118, 111, 0, 1, 100, 110, 111, 0, 1, 100, 111, 109, 0, 1, 100, 114, 101, 100, 101, 110, 0, 1, 100, 114, 111, 102, 0, 1, 100, 115, 109, 101, 103, 101, 108, 0, 1, 100, 115, 110, 101, 100, 114, 101, 118, 0, 1, 100, 115, 184, 195, 108, 0, 1, 100, 116, 110, 101, 99, 111, 114, 112, 0, 1, 100, 118, 108, 97, 104, 0, 1, 100, 121, 98, 0, 1, 103, 110, 97, 118, 101, 0, 1, 104, 2, 116, 12, 0, 1, 105, 110, 97, 100, 0, 1, 107, 115, 101, 115, 110, 166, 195, 114, 103, 0, 1, 107, 115, 107, 114, 97, 109, 0, 1, 107, 115, 114, 111, 0, 1, 109, 2, 111, 110, 0, 1, 109, 101, 100, 101, 118, 104, 0, 1, 109, 101, 116, 103, 105, 115, 0, 1, 109, 103, 117, 114, 0, 1, 109, 110, 101, 98, 0, 1, 109, 111, 103, 97, 115, 0, 1, 109, 114, 111, 102, 117, 0, 1, 109, 115, 105, 114, 0, 1, 110, 97, 112, 0, 1, 110, 114, 111, 107, 2, 101, 118, 97, 116, 111, 114, 0, 1, 114, 2, 97, 116, 0, 1, 115, 2, 101, 32, 0, 1, 115, 2, 101, 114, 32, 0, 1, 115, 2, 101, 114, 115, 32, 0, 1, 116, 2, 101, 0, 1, 116, 2, 101, 102, 0, 1, 116, 2, 116, 32, 0, 1, 116, 110, 0, 1, 116, 115, 101, 108, 108, 105, 114, 98, 0, 1, 116, 115, 101, 115, 105, 112, 115, 0, 1, 116, 115, 101, 116, 110, 97, 118, 114, 101, 115, 0, 1, 116, 115, 114, 101, 100, 110, 117, 2, 12, 0, 1, 116, 115, 115, 103, 110, 105, 100, 110, 97, 108, 0, 1, 117, 116, 107, 101, 108, 108, 101, 116, 110, 105, 0, 2, 105, 107, 115, 105, 114, 0, 2, 115, 107, 12, 0, 8, 116, 115, 2, 32, 0, 101, 114, 1, 100, 2, 12, 3, 36, 55, 112, 0, 4, 1, 97, 104, 99, 105, 3, 55, 0, 1, 97, 107, 105, 0, 1, 100, 100, 101, 115, 0, 4, 1, 100, 110, 105, 118, 107, 2, 17, 65, 3, 106, 55, 0, 8, 114, 111, 102, 2, 195, 166, 103, 0, 101, 1, 100, 110, 105, 98, 2, 100, 3, 106, 55, 36, 0, 4, 1, 98, 97, 115, 105, 3, 107, 55, 0, 1, 100, 97, 107, 105, 114, 102, 2, 108, 0, 1, 102, 21, 2, 116, 0, 1, 104, 2, 105, 107, 111, 112, 116, 0, 1, 104, 2, 115, 116, 0, 1, 105, 116, 0, 1, 107, 115, 2, 32, 0, 1, 110, 105, 109, 105, 114, 107, 0, 1, 110, 111, 105, 116, 97, 114, 0, 1, 110, 111, 115, 114, 101, 112, 0, 1, 112, 10, 2, 115, 32, 0, 1, 115, 2, 115, 0, 1, 116, 111, 104, 0, 1, 118, 0, 8, 0, 8, 112, 112, 97, 2, 115, 105, 110, 0, 8, 117, 109, 97, 115, 0, 108, 105, 111, 116, 3, 107, 55, 57, 112, 47, 0, 1, 114, 21, 2, 32, 12, 3, 109, 55, 0, 1, 114, 100, 2, 12, 3, 112, 55, 0, 7, 6, 101, 110, 0, 4, 1, 99, 166, 195, 109, 3, 6, 36, 50, 0, 1, 109, 111, 110, 166, 195, 102, 0, 1, 114, 121, 115, 2, 101, 110, 32, 0, 1, 114, 121, 115, 2, 101, 114, 32, 0, 1, 116, 115, 105, 115, 107, 101, 2, 115, 0, 8, 100, 97, 2, 32, 0, 8, 100, 105, 115, 101, 114, 2, 115, 0, 8, 100, 105, 115, 166, 195, 114, 112, 2, 116, 0, 8, 103, 97, 2, 116, 0, 8, 108, 121, 116, 101, 99, 97, 0, 8, 109, 101, 103, 0, 8, 114, 121, 115, 32, 110, 101, 0, 116, 1, 10, 2, 28, 33, 12, 3, 6, 36, 50, 47, 0, 115, 1, 10, 2, 28, 33, 3, 6, 36, 50, 87, 0, 4, 1, 112, 112, 97, 2, 100, 105, 107, 115, 3, 6, 107, 50, 0, 1, 114, 102, 111, 122, 105, 107, 115, 0, 8, 108, 111, 112, 2, 116, 97, 0, 8, 117, 108, 102, 110, 105, 2, 122, 97, 0, 100, 1, 108, 105, 116, 2, 101, 98, 114, 0, 110, 8, 105, 115, 114, 101, 112, 0, 4, 99, 101, 1, 108, 108, 101, 99, 120, 101, 2, 28, 33, 3, 6, 107, 50, 87, 13, 0, 99, 101, 1, 110, 105, 109, 101, 2, 28, 33, 0, 100, 101, 114, 8, 108, 97, 107, 3, 6, 107, 50, 112, 0, 116, 1, 114, 10, 2, 28, 33, 12, 3, 6, 109, 50, 47, 0, 115, 1, 114, 10, 2, 28, 33, 3, 6, 109, 50, 87, 0, 8, 118, 101, 114, 2, 99, 104, 101, 3, 6, 110, 50, 0, 116, 1, 115, 101, 10, 2, 28, 33, 12, 3, 6, 110, 66, 0, 115, 101, 114, 1, 10, 2, 28, 33, 3, 7, 107, 50, 87, 112, 0, 99, 101, 1, 10, 2, 28, 33, 3, 7, 110, 66, 87, 13, 0, 4, 1, 10, 2, 32, 24, 3, 13, 50, 0, 1, 98, 98, 2, 32, 12, 12, 0, 1, 98, 109, 111, 98, 2, 12, 0, 1, 98, 165, 195, 118, 2, 12, 12, 0, 1, 100, 105, 115, 0, 1, 100, 114, 111, 0, 1, 102, 102, 97, 107, 115, 116, 101, 114, 0, 1, 114, 101, 105, 10, 2, 32, 24, 0, 1, 116, 2, 195, 165, 0, 1, 116, 102, 97, 0, 8, 98, 165, 195, 2, 32, 12, 0, 8, 98, 165, 195, 2, 116, 32, 12, 0, 1, 98, 97, 107, 115, 2, 12, 3, 14, 50, 0, 115, 1, 10, 2, 32, 3, 14, 50, 87, 0, 100, 101, 114, 1, 114, 10, 2, 32, 3, 35, 50, 112, 0, 4, 1, 98, 10, 2, 32, 12, 3, 36, 50, 0, 1, 98, 98, 105, 114, 2, 12, 12, 0, 1, 100, 105, 115, 101, 114, 2, 115, 0, 1, 100, 105, 115, 166, 195, 114, 112, 2, 116, 0, 1, 103, 2, 115, 107, 0, 1, 103, 2, 115, 116, 0, 1, 103, 10, 2, 107, 101, 110, 100, 0, 1, 103, 10, 2, 115, 116, 0, 1, 103, 97, 2, 116, 0, 1, 112, 115, 117, 115, 2, 115, 105, 111, 110, 0, 1, 114, 115, 100, 108, 121, 107, 115, 0, 1, 116, 115, 2, 17, 65, 0, 1, 116, 115, 97, 116, 117, 97, 98, 0, 1, 116, 115, 100, 110, 97, 115, 0, 1, 116, 115, 100, 110, 97, 116, 0, 1, 116, 115, 100, 110, 117, 114, 103, 0, 1, 116, 115, 101, 98, 105, 108, 115, 0, 1, 116, 115, 101, 100, 108, 97, 103, 0, 1, 116, 115, 101, 100, 110, 101, 114, 0, 1, 116, 115, 101, 100, 110, 105, 109, 0, 1, 116, 115, 101, 100, 166, 195, 114, 116, 0, 1, 116, 115, 101, 103, 103, 121, 98, 0, 1, 116, 115, 101, 106, 184, 195, 0, 1, 116, 115, 101, 107, 107, 111, 114, 0, 1, 116, 115, 101, 107, 107, 121, 109, 115, 0, 1, 116, 115, 101, 107, 110, 105, 104, 0, 1, 116, 115, 101, 107, 110, 117, 109, 0, 1, 116, 115, 101, 107, 115, 101, 118, 115, 0, 1, 116, 115, 101, 108, 103, 110, 97, 114, 0, 1, 116, 115, 101, 108, 108, 117, 114, 0, 1, 116, 115, 101, 108, 108, 184, 195, 109, 0, 1, 116, 115, 101, 110, 114, 184, 195, 106, 104, 0, 1, 116, 115, 101, 110, 117, 114, 0, 1, 116, 115, 101, 110, 165, 195, 109, 0, 1, 116, 115, 101, 112, 109, 97, 107, 0, 1, 116, 115, 101, 112, 112, 97, 114, 116, 0, 1, 116, 115, 101, 114, 121, 110, 0, 1, 116, 115, 101, 116, 110, 105, 108, 102, 0, 1, 116, 115, 101, 118, 184, 195, 114, 112, 0, 1, 116, 115, 102, 117, 116, 0, 1, 116, 115, 103, 97, 116, 0, 1, 116, 115, 103, 110, 117, 116, 0, 1, 116, 115, 107, 108, 97, 107, 0, 1, 116, 115, 107, 166, 195, 100, 0, 1, 116, 115, 108, 101, 100, 101, 107, 0, 1, 116, 115, 108, 101, 100, 166, 195, 0, 1, 116, 115, 108, 101, 100, 166, 195, 0, 1, 116, 115, 108, 103, 101, 116, 0, 1, 116, 115, 108, 111, 104, 0, 1, 116, 115, 109, 105, 108, 0, 1, 116, 115, 110, 105, 104, 114, 0, 1, 116, 115, 110, 105, 118, 0, 1, 116, 115, 110, 114, 166, 195, 118, 107, 0, 1, 116, 115, 111, 114, 98, 0, 1, 116, 115, 112, 109, 105, 112, 0, 1, 116, 115, 112, 121, 114, 100, 0, 1, 116, 115, 114, 101, 100, 97, 118, 107, 0, 1, 116, 115, 114, 101, 108, 111, 109, 0, 1, 116, 115, 114, 111, 101, 116, 101, 109, 0, 1, 116, 115, 114, 111, 107, 115, 0, 1, 116, 115, 114, 111, 109, 114, 97, 109, 0, 1, 116, 115, 114, 117, 109, 0, 1, 116, 115, 116, 100, 101, 102, 0, 1, 116, 115, 116, 110, 97, 107, 0, 1, 116, 115, 116, 110, 105, 108, 102, 0, 1, 116, 115, 116, 117, 108, 115, 0, 1, 116, 115, 116, 117, 109, 115, 0, 1, 116, 115, 118, 97, 114, 103, 0, 1, 116, 115, 165, 195, 109, 115, 0, 1, 116, 115, 165, 195, 109, 115, 0, 1, 116, 115, 165, 195, 114, 103, 0, 1, 118, 2, 115, 107, 12, 0, 1, 118, 115, 21, 2, 32, 0, 8, 114, 117, 2, 32, 0, 110, 1, 103, 10, 2, 101, 109, 0, 116, 1, 118, 101, 2, 17, 65, 12, 3, 36, 50, 47, 0, 4, 116, 1, 10, 2, 97, 108, 115, 107, 28, 33, 12, 3, 36, 50, 47, 6, 0, 116, 1, 10, 2, 117, 114, 28, 33, 12, 0, 115, 1, 118, 107, 3, 36, 50, 87, 0, 116, 105, 1, 118, 2, 111, 110, 3, 36, 50, 89, 57, 0, 115, 101, 1, 103, 10, 2, 28, 33, 3, 79, 7, 107, 50, 87, 112, 0, 1, 114, 121, 115, 2, 101, 100, 115, 195, 166, 116, 116, 101, 110, 100, 101, 3, 106, 50, 0, 4, 1, 106, 116, 2, 115, 116, 3, 107, 50, 0, 1, 109, 2, 115, 12, 0, 1, 112, 101, 100, 0, 1, 112, 101, 108, 103, 117, 107, 0, 1, 112, 116, 108, 105, 102, 0, 1, 114, 103, 101, 105, 108, 111, 0, 1, 114, 103, 115, 116, 114, 111, 112, 115, 0, 1, 118, 101, 114, 121, 100, 0, 1, 118, 101, 115, 115, 184, 195, 98, 0, 100, 101, 114, 1, 116, 114, 97, 98, 3, 107, 50, 70, 112, 0, 4, 115, 101, 114, 1, 10, 2, 101, 28, 33, 3, 107, 50, 87, 6, 36, 34, 0, 115, 101, 114, 1, 112, 10, 2, 32, 28, 33, 0, 100, 101, 114, 1, 10, 2, 32, 3, 107, 50, 112, 0, 110, 1, 105, 99, 110, 97, 3, 107, 66, 0, 1, 114, 115, 98, 184, 195, 108, 102, 97, 2, 115, 3, 109, 50, 0, 1, 118, 101, 114, 2, 99, 104, 101, 3, 110, 50, 0, 4, 1, 115, 2, 115, 105, 98, 3, 110, 66, 0, 2, 32, 103, 114, 111, 115, 0, 2, 100, 111, 115, 0, 2, 116, 117, 115, 105, 97, 115, 0, 116, 1, 99, 99, 97, 2, 12, 0, 103, 114, 111, 115, 3, 110, 66, 79, 34, 6, 39, 0, 115, 1, 114, 10, 2, 32, 3, 112, 20, 50, 87, 0, 1, 114, 10, 2, 32, 24, 3, 112, 50, 0, 7, 6, 101, 114, 0, 105, 110, 103, 1, 17, 67, 21, 2, 12, 12, 3, 4, 36, 34, 36, 66, 0, 1, 105, 118, 97, 120, 3, 6, 36, 0, 4, 1, 99, 105, 102, 102, 111, 3, 6, 36, 34, 0, 1, 107, 114, 97, 112, 2, 32, 98, 105, 108, 0, 1, 108, 101, 118, 117, 106, 2, 101, 110, 0, 1, 109, 97, 2, 105, 107, 97, 32, 0, 1, 110, 97, 109, 2, 32, 0, 1, 115, 115, 97, 112, 2, 32, 103, 97, 100, 101, 110, 0, 1, 115, 115, 97, 112, 2, 115, 101, 100, 0, 1, 116, 101, 102, 97, 99, 2, 105, 0, 1, 116, 114, 111, 109, 0, 1, 116, 115, 21, 2, 105, 101, 0, 1, 116, 116, 97, 108, 102, 2, 101, 110, 100, 101, 0, 1, 118, 104, 110, 101, 0, 8, 98, 114, 97, 98, 2, 12, 0, 8, 102, 105, 114, 101, 112, 0, 8, 105, 118, 105, 114, 2, 97, 0, 8, 108, 97, 118, 97, 107, 0, 8, 108, 108, 97, 102, 2, 12, 0, 8, 110, 105, 102, 0, 8, 115, 115, 97, 107, 2, 101, 114, 0, 8, 116, 107, 97, 114, 97, 107, 0, 8, 116, 111, 110, 2, 32, 100, 101, 110, 0, 8, 116, 111, 110, 2, 32, 100, 101, 116, 0, 8, 116, 114, 97, 118, 107, 0, 8, 116, 115, 121, 109, 2, 105, 117, 0, 8, 118, 97, 108, 107, 2, 12, 12, 0, 105, 1, 116, 115, 2, 115, 107, 28, 33, 3, 6, 36, 34, 37, 0, 4, 116, 1, 107, 114, 111, 102, 3, 6, 36, 34, 47, 0, 116, 1, 109, 114, 111, 102, 101, 114, 0, 116, 1, 110, 101, 103, 0, 116, 1, 110, 105, 0, 116, 1, 110, 114, 111, 98, 0, 116, 1, 115, 97, 108, 98, 0, 116, 1, 116, 107, 101, 102, 102, 97, 0, 116, 1, 117, 110, 105, 116, 110, 111, 107, 0, 116, 1, 117, 110, 105, 116, 110, 111, 107, 115, 105, 100, 0, 116, 1, 118, 114, 101, 115, 101, 114, 0, 110, 101, 8, 116, 117, 97, 115, 2, 12, 3, 6, 36, 34, 50, 0, 4, 110, 101, 8, 99, 117, 108, 2, 12, 3, 6, 36, 34, 50, 13, 0, 110, 101, 8, 100, 111, 109, 2, 12, 12, 0, 110, 101, 8, 115, 97, 107, 2, 12, 0, 110, 101, 8, 116, 115, 105, 99, 2, 12, 0, 110, 101, 8, 118, 97, 116, 2, 12, 0, 110, 101, 114, 8, 115, 97, 107, 2, 12, 3, 6, 36, 34, 50, 112, 0, 101, 8, 103, 97, 101, 114, 2, 32, 3, 6, 36, 34, 106, 0, 4, 101, 114, 8, 110, 97, 109, 3, 6, 36, 112, 0, 101, 114, 8, 110, 97, 109, 0, 4, 1, 98, 108, 97, 2, 116, 17, 65, 3, 6, 107, 34, 0, 1, 102, 110, 105, 2, 110, 111, 0, 1, 116, 110, 105, 2, 110, 32, 12, 12, 0, 1, 116, 111, 115, 105, 2, 109, 0, 1, 118, 114, 101, 112, 2, 115, 12, 0, 8, 108, 108, 97, 116, 2, 107, 0, 8, 115, 110, 111, 107, 2, 118, 97, 116, 105, 118, 0, 8, 115, 110, 111, 107, 2, 118, 101, 115, 0, 8, 116, 110, 105, 2, 110, 32, 12, 12, 0, 8, 116, 110, 105, 2, 110, 101, 32, 12, 12, 0, 8, 118, 105, 110, 117, 2, 115, 12, 0, 8, 118, 111, 114, 116, 110, 111, 107, 2, 115, 0, 4, 116, 1, 99, 110, 111, 107, 3, 6, 107, 34, 47, 0, 116, 1, 112, 115, 107, 101, 0, 116, 1, 115, 115, 101, 100, 0, 116, 1, 118, 104, 116, 101, 0, 116, 1, 118, 111, 114, 116, 110, 105, 0, 116, 1, 118, 117, 107, 2, 12, 12, 0, 110, 101, 8, 116, 110, 97, 108, 2, 12, 3, 6, 107, 34, 50, 13, 0, 1, 116, 108, 97, 2, 110, 97, 116, 105, 118, 3, 6, 107, 51, 0, 4, 101, 1, 21, 2, 32, 28, 33, 12, 12, 3, 7, 36, 12, 112, 0, 101, 1, 21, 2, 100, 101, 28, 33, 12, 12, 0, 101, 1, 21, 2, 114, 28, 33, 12, 12, 0, 101, 1, 21, 2, 114, 101, 28, 33, 12, 12, 12, 0, 101, 1, 21, 2, 114, 101, 110, 28, 33, 12, 12, 0, 101, 1, 21, 2, 115, 32, 28, 33, 12, 12, 0, 101, 1, 21, 2, 116, 28, 33, 12, 12, 0, 101, 1, 105, 21, 2, 110, 32, 28, 33, 12, 12, 0, 4, 1, 21, 2, 28, 33, 12, 12, 12, 3, 7, 36, 34, 0, 1, 21, 2, 32, 28, 33, 12, 12, 0, 1, 21, 2, 101, 32, 28, 33, 12, 12, 12, 0, 1, 21, 2, 101, 116, 28, 33, 12, 12, 12, 12, 0, 105, 110, 103, 1, 10, 2, 28, 33, 12, 12, 3, 7, 36, 34, 36, 66, 0, 101, 116, 1, 10, 2, 28, 33, 12, 12, 3, 7, 36, 34, 106, 84, 0, 101, 114, 1, 108, 101, 118, 117, 106, 3, 7, 36, 112, 0, 1, 100, 110, 97, 120, 101, 108, 97, 3, 8, 70, 112, 0, 4, 1, 107, 105, 10, 2, 32, 28, 33, 12, 12, 3, 8, 112, 0, 1, 107, 105, 10, 2, 115, 32, 28, 33, 12, 12, 0, 105, 1, 21, 2, 115, 107, 28, 33, 3, 8, 112, 34, 37, 0, 4, 1, 102, 110, 10, 2, 101, 114, 21, 3, 13, 34, 0, 1, 118, 101, 108, 2, 101, 103, 12, 0, 101, 100, 101, 8, 108, 108, 97, 2, 32, 3, 13, 34, 36, 84, 13, 0, 101, 116, 1, 116, 108, 97, 3, 13, 34, 106, 84, 0, 101, 110, 1, 102, 110, 10, 2, 99, 3, 13, 34, 110, 66, 0, 1, 116, 2, 114, 97, 115, 115, 3, 35, 0, 4, 1, 99, 2, 101, 12, 3, 36, 34, 0, 1, 100, 2, 102, 114, 97, 0, 1, 100, 114, 117, 2, 101, 116, 0, 1, 102, 97, 114, 103, 111, 116, 111, 102, 110, 101, 103, 2, 101, 0, 1, 102, 105, 114, 101, 112, 0, 1, 103, 2, 97, 110, 105, 0, 1, 103, 2, 101, 12, 0, 1, 103, 2, 109, 97, 110, 115, 0, 1, 103, 115, 121, 110, 2, 114, 105, 0, 1, 106, 102, 2, 32, 0, 1, 107, 114, 111, 102, 2, 116, 12, 0, 1, 108, 98, 2, 101, 0, 1, 108, 108, 97, 2, 103, 0, 1, 109, 109, 111, 107, 2, 99, 105, 101, 108, 0, 1, 110, 105, 102, 0, 1, 112, 101, 116, 114, 111, 115, 0, 1, 112, 103, 105, 116, 103, 105, 118, 0, 1, 116, 2, 97, 12, 0, 1, 116, 2, 110, 105, 12, 0, 1, 116, 2, 114, 111, 114, 0, 1, 116, 105, 99, 21, 2, 101, 0, 1, 116, 107, 97, 114, 97, 107, 0, 1, 116, 114, 97, 118, 107, 0, 1, 116, 115, 2, 101, 111, 0, 1, 116, 115, 2, 105, 0, 1, 116, 115, 2, 108, 105, 110, 103, 0, 1, 116, 115, 117, 104, 2, 105, 0, 1, 118, 2, 101, 116, 0, 1, 118, 2, 114, 32, 0, 1, 118, 97, 108, 107, 2, 12, 12, 0, 1, 118, 97, 114, 103, 21, 2, 101, 0, 1, 118, 104, 2, 12, 0, 8, 2, 103, 111, 0, 8, 103, 2, 116, 97, 12, 0, 8, 104, 2, 32, 0, 8, 107, 115, 2, 32, 0, 8, 108, 2, 32, 12, 12, 0, 8, 115, 2, 32, 0, 8, 115, 114, 101, 118, 111, 0, 8, 116, 2, 32, 0, 8, 2, 17, 67, 3, 36, 34, 6, 0, 110, 101, 1, 116, 117, 97, 115, 2, 12, 3, 36, 34, 50, 0, 4, 110, 101, 1, 99, 117, 108, 2, 12, 3, 36, 34, 50, 13, 0, 110, 101, 1, 100, 111, 109, 2, 12, 12, 0, 110, 101, 1, 115, 97, 107, 2, 12, 0, 110, 101, 1, 116, 115, 105, 99, 2, 12, 0, 110, 101, 1, 118, 97, 116, 2, 12, 0, 4, 101, 1, 100, 114, 117, 118, 2, 32, 3, 36, 34, 106, 0, 101, 1, 103, 97, 101, 114, 2, 32, 0, 101, 1, 109, 109, 117, 115, 112, 111, 0, 101, 1, 114, 116, 2, 12, 0, 101, 1, 115, 105, 116, 97, 109, 97, 114, 100, 21, 0, 101, 1, 116, 97, 108, 101, 114, 0, 101, 116, 1, 116, 110, 101, 105, 114, 111, 3, 36, 34, 106, 84, 0, 4, 101, 1, 115, 97, 98, 3, 36, 112, 0, 101, 114, 1, 110, 97, 109, 0, 4, 1, 100, 110, 117, 104, 3, 106, 34, 0, 1, 109, 109, 17, 65, 2, 97, 0, 1, 116, 114, 111, 112, 101, 114, 2, 101, 12, 0, 1, 116, 114, 111, 112, 101, 114, 2, 101, 110, 12, 0, 1, 118, 121, 108, 102, 2, 117, 116, 101, 0, 101, 1, 21, 2, 114, 101, 28, 33, 12, 12, 3, 106, 34, 6, 36, 0, 4, 105, 1, 107, 115, 97, 118, 2, 28, 33, 3, 106, 34, 7, 37, 0, 105, 1, 116, 110, 97, 102, 110, 105, 2, 28, 33, 0, 1, 112, 115, 101, 100, 2, 97, 116, 3, 106, 51, 0, 4, 101, 1, 21, 2, 32, 3, 106, 112, 0, 101, 1, 114, 2, 32, 0, 1, 116, 2, 114, 3, 107, 0, 4, 1, 102, 2, 110, 105, 3, 107, 34, 0, 1, 103, 2, 100, 97, 0, 1, 103, 2, 110, 12, 12, 0, 1, 103, 2, 114, 105, 103, 0, 1, 104, 2, 108, 105, 12, 0, 1, 104, 101, 98, 2, 115, 107, 0, 1, 106, 2, 103, 0, 1, 106, 2, 110, 12, 12, 12, 12, 0, 1, 110, 2, 118, 0, 1, 115, 2, 116, 12, 0, 1, 115, 2, 118, 12, 0, 1, 116, 2, 109, 105, 110, 0, 1, 116, 2, 109, 111, 0, 1, 116, 2, 112, 0, 1, 116, 2, 114, 105, 101, 114, 0, 1, 116, 115, 2, 111, 108, 0, 1, 118, 2, 17, 67, 12, 12, 12, 0, 1, 118, 105, 110, 117, 0, 1, 118, 115, 2, 105, 103, 101, 0, 2, 102, 97, 114, 105, 0, 8, 103, 2, 110, 101, 32, 12, 0, 8, 110, 101, 103, 2, 116, 0, 114, 1, 103, 114, 166, 195, 0, 110, 1, 100, 111, 109, 2, 105, 12, 3, 107, 34, 50, 0, 110, 101, 1, 116, 110, 97, 108, 112, 111, 116, 2, 12, 12, 3, 107, 34, 50, 13, 0, 4, 115, 1, 21, 2, 116, 97, 116, 3, 107, 34, 87, 0, 115, 1, 102, 2, 107, 0, 4, 8, 2, 32, 3, 108, 34, 0, 8, 18, 71, 2, 32, 0, 114, 195, 166, 110, 1, 116, 3, 108, 34, 6, 109, 66, 0, 98, 121, 1, 100, 3, 110, 12, 69, 37, 0, 4, 1, 18, 71, 18, 71, 3, 112, 0, 1, 18, 74, 2, 110, 101, 32, 0, 1, 21, 2, 32, 24, 0, 1, 21, 2, 115, 17, 67, 0, 1, 98, 111, 2, 115, 116, 0, 1, 100, 2, 98, 121, 103, 0, 1, 100, 21, 2, 17, 67, 0, 1, 100, 100, 117, 0, 1, 100, 101, 108, 2, 21, 0, 1, 100, 110, 117, 0, 1, 102, 102, 2, 17, 65, 116, 0, 1, 102, 102, 117, 107, 2, 116, 0, 1, 103, 2, 12, 0, 1, 103, 2, 32, 12, 12, 0, 1, 103, 110, 166, 195, 108, 2, 101, 0, 1, 103, 114, 111, 98, 2, 101, 0, 1, 106, 101, 108, 0, 1, 106, 108, 97, 116, 2, 25, 12, 12, 0, 1, 106, 110, 105, 108, 2, 12, 12, 12, 0, 1, 107, 105, 17, 67, 2, 12, 0, 1, 107, 107, 2, 12, 0, 1, 107, 110, 117, 98, 0, 1, 107, 111, 112, 0, 1, 107, 115, 0, 1, 108, 103, 117, 109, 115, 0, 1, 108, 108, 105, 112, 0, 1, 108, 184, 195, 0, 1, 109, 21, 2, 115, 107, 0, 1, 109, 109, 2, 101, 116, 0, 1, 109, 109, 17, 65, 2, 17, 67, 0, 1, 109, 109, 117, 0, 1, 109, 111, 114, 0, 1, 110, 2, 32, 12, 0, 1, 110, 97, 109, 32, 114, 101, 100, 2, 32, 0, 1, 110, 97, 109, 109, 101, 114, 102, 0, 1, 110, 97, 109, 111, 2, 12, 0, 1, 110, 97, 109, 114, 111, 2, 32, 0, 1, 110, 105, 102, 108, 101, 100, 0, 1, 110, 116, 0, 1, 112, 117, 2, 17, 67, 0, 1, 114, 2, 17, 67, 0, 1, 114, 2, 32, 0, 1, 115, 110, 97, 100, 0, 1, 115, 110, 97, 112, 0, 1, 115, 117, 114, 98, 0, 1, 115, 121, 0, 1, 116, 2, 32, 0, 1, 116, 2, 101, 116, 32, 0, 1, 116, 10, 2, 17, 67, 0, 1, 116, 101, 109, 2, 12, 0, 1, 116, 102, 101, 0, 1, 116, 103, 0, 1, 116, 108, 97, 0, 1, 116, 108, 111, 112, 2, 97, 98, 0, 1, 116, 110, 101, 100, 0, 1, 116, 110, 105, 2, 21, 0, 1, 116, 110, 105, 2, 110, 97, 116, 0, 1, 116, 112, 101, 99, 115, 0, 1, 116, 114, 111, 112, 101, 114, 2, 12, 0, 1, 116, 115, 105, 0, 1, 116, 115, 110, 184, 195, 2, 12, 0, 1, 116, 115, 121, 114, 107, 2, 21, 0, 1, 116, 116, 2, 17, 67, 0, 1, 118, 97, 17, 67, 2, 32, 12, 0, 1, 118, 97, 114, 103, 100, 108, 117, 103, 2, 101, 0, 1, 118, 101, 108, 2, 17, 67, 12, 12, 0, 1, 118, 108, 111, 118, 101, 114, 2, 12, 0, 1, 118, 111, 2, 12, 12, 12, 0, 1, 118, 114, 97, 102, 2, 115, 12, 0, 1, 118, 121, 2, 12, 0, 1, 118, 184, 195, 2, 115, 116, 12, 12, 0, 8, 108, 108, 97, 0, 8, 112, 97, 107, 2, 115, 12, 12, 0, 95, 1, 104, 116, 0, 101, 1, 118, 111, 2, 110, 115, 12, 3, 112, 6, 36, 0, 4, 1, 100, 105, 107, 115, 3, 112, 34, 0, 1, 100, 111, 114, 98, 2, 101, 110, 0, 1, 118, 101, 108, 2, 101, 110, 12, 0, 105, 1, 21, 2, 28, 33, 12, 12, 3, 112, 34, 6, 37, 0, 105, 1, 118, 184, 195, 114, 21, 3, 112, 34, 37, 0, 101, 110, 1, 21, 2, 32, 3, 112, 34, 106, 50, 0, 101, 110, 115, 1, 21, 2, 32, 3, 112, 34, 106, 50, 87, 0, 4, 116, 1, 21, 2, 32, 3, 112, 47, 0, 116, 1, 21, 2, 115, 32, 0, 116, 1, 98, 109, 97, 108, 115, 0, 4, 110, 101, 1, 21, 2, 32, 12, 3, 112, 50, 13, 0, 110, 101, 1, 100, 21, 2, 12, 12, 0, 110, 101, 1, 116, 110, 97, 108, 112, 2, 12, 12, 0, 110, 101, 1, 116, 115, 105, 99, 115, 97, 102, 2, 12, 0, 110, 101, 1, 118, 97, 116, 115, 2, 12, 0, 110, 101, 115, 1, 21, 2, 32, 3, 112, 50, 13, 87, 0, 110, 101, 1, 103, 110, 105, 102, 2, 109, 3, 112, 50, 36, 0, 110, 101, 1, 116, 110, 105, 2, 116, 12, 3, 112, 50, 107, 0, 1, 103, 110, 105, 102, 2, 101, 110, 3, 112, 51, 0, 115, 1, 21, 2, 32, 3, 112, 87, 0, 115, 116, 101, 1, 21, 2, 32, 3, 112, 87, 47, 13, 0, 4, 1, 115, 2, 118, 105, 99, 101, 109, 101, 100, 3, 116, 0, 1, 115, 2, 118, 105, 99, 101, 110, 0, 1, 115, 2, 118, 105, 99, 101, 115, 116, 97, 116, 105, 111, 110, 0, 110, 105, 101, 8, 3, 116, 12, 50, 37, 0, 103, 105, 101, 1, 102, 3, 116, 12, 79, 37, 0, 110, 111, 110, 1, 118, 2, 12, 12, 3, 116, 50, 106, 50, 0, 4, 118, 105, 99, 101, 1, 115, 101, 100, 110, 117, 107, 3, 116, 82, 37, 87, 0, 118, 105, 99, 101, 1, 115, 109, 111, 111, 114, 0, 118, 105, 99, 101, 109, 105, 110, 100, 101, 116, 1, 115, 3, 116, 82, 37, 87, 63, 35, 57, 50, 70, 13, 84, 0, 7, 6, 101, 116, 0, 4, 1, 114, 107, 101, 100, 2, 12, 3, 6, 36, 47, 0, 1, 116, 105, 2, 32, 12, 0, 1, 116, 105, 2, 115, 32, 12, 0, 8, 98, 97, 102, 108, 97, 0, 8, 98, 101, 103, 2, 12, 0, 8, 98, 105, 116, 0, 8, 102, 111, 114, 112, 0, 8, 105, 118, 114, 101, 115, 0, 8, 107, 115, 97, 0, 8, 107, 115, 97, 107, 0, 8, 110, 97, 108, 112, 0, 8, 110, 105, 114, 97, 108, 107, 0, 8, 112, 97, 116, 0, 8, 112, 109, 111, 114, 116, 0, 8, 116, 114, 101, 98, 117, 112, 0, 116, 8, 105, 118, 114, 101, 115, 0, 116, 8, 107, 115, 97, 107, 0, 101, 114, 1, 109, 10, 3, 6, 36, 47, 112, 0, 1, 98, 114, 111, 115, 3, 6, 107, 0, 4, 1, 99, 110, 105, 112, 3, 6, 107, 47, 0, 1, 102, 97, 116, 115, 0, 1, 107, 110, 97, 108, 98, 32, 110, 101, 0, 1, 108, 117, 109, 97, 0, 1, 110, 111, 105, 114, 97, 109, 0, 1, 110, 111, 115, 32, 110, 101, 0, 1, 114, 97, 107, 2, 12, 12, 0, 1, 114, 107, 110, 111, 107, 0, 1, 117, 100, 21, 2, 32, 0, 1, 117, 100, 32, 101, 103, 110, 121, 115, 2, 32, 0, 1, 117, 100, 32, 103, 110, 97, 115, 2, 32, 0, 1, 117, 100, 32, 110, 101, 2, 32, 0, 1, 117, 100, 32, 114, 101, 103, 110, 121, 115, 2, 32, 0, 1, 117, 100, 32, 116, 101, 103, 110, 117, 115, 2, 32, 0, 1, 117, 114, 105, 112, 0, 8, 100, 97, 107, 2, 12, 0, 8, 103, 100, 117, 98, 0, 8, 107, 105, 114, 98, 0, 8, 107, 111, 107, 0, 8, 107, 114, 97, 112, 0, 8, 108, 105, 111, 116, 0, 8, 108, 105, 111, 116, 0, 8, 108, 108, 105, 98, 0, 8, 110, 111, 106, 97, 98, 0, 8, 114, 107, 101, 115, 2, 12, 0, 8, 115, 108, 97, 102, 0, 8, 115, 114, 111, 107, 32, 116, 101, 0, 8, 116, 110, 105, 118, 107, 0, 8, 116, 114, 97, 118, 107, 0, 116, 1, 110, 111, 105, 114, 97, 109, 0, 116, 1, 110, 111, 115, 2, 101, 0, 116, 8, 108, 108, 105, 98, 0, 116, 8, 110, 111, 106, 97, 98, 0, 116, 101, 8, 103, 114, 111, 101, 103, 0, 116, 101, 8, 117, 103, 97, 98, 0, 4, 116, 101, 8, 103, 97, 114, 102, 102, 117, 115, 3, 6, 107, 47, 13, 0, 116, 101, 8, 103, 114, 117, 111, 99, 0, 116, 101, 8, 107, 97, 108, 112, 0, 116, 101, 8, 107, 111, 107, 0, 116, 101, 8, 107, 115, 105, 100, 0, 116, 101, 8, 108, 105, 111, 116, 0, 116, 101, 8, 108, 108, 101, 118, 111, 110, 0, 116, 101, 8, 108, 111, 18, 75, 105, 110, 0, 116, 101, 8, 108, 117, 111, 114, 0, 116, 101, 8, 108, 121, 0, 116, 101, 8, 109, 108, 97, 112, 0, 116, 101, 8, 110, 97, 105, 112, 0, 116, 101, 8, 110, 105, 101, 114, 0, 116, 101, 8, 110, 117, 114, 98, 0, 116, 101, 8, 112, 105, 112, 0, 116, 101, 8, 114, 111, 98, 109, 97, 106, 0, 116, 101, 8, 114, 117, 98, 0, 116, 101, 8, 115, 105, 109, 101, 104, 99, 0, 116, 101, 8, 115, 105, 117, 113, 114, 97, 109, 0, 116, 101, 8, 115, 117, 109, 0, 116, 101, 8, 117, 116, 97, 116, 115, 0, 116, 101, 8, 118, 117, 99, 0, 116, 101, 114, 8, 117, 116, 97, 116, 115, 3, 6, 107, 47, 112, 0, 4, 116, 101, 8, 114, 98, 117, 111, 115, 3, 6, 108, 47, 13, 0, 116, 101, 8, 114, 103, 105, 97, 110, 105, 118, 0, 8, 114, 117, 98, 97, 116, 2, 12, 3, 6, 109, 47, 0, 1, 116, 105, 10, 2, 28, 33, 12, 3, 7, 36, 47, 0, 4, 8, 107, 105, 116, 101, 3, 7, 107, 47, 0, 8, 108, 111, 105, 118, 2, 12, 0, 116, 101, 8, 107, 105, 116, 101, 3, 7, 107, 47, 13, 0, 1, 114, 2, 195, 184, 106, 12, 3, 13, 47, 0, 4, 1, 21, 2, 32, 12, 3, 13, 84, 0, 1, 103, 97, 116, 0, 1, 114, 117, 2, 32, 12, 12, 0, 1, 117, 100, 110, 105, 118, 2, 32, 0, 1, 118, 97, 2, 12, 0, 115, 1, 21, 2, 32, 12, 3, 13, 84, 87, 0, 4, 1, 98, 97, 102, 108, 97, 3, 36, 47, 0, 1, 98, 105, 116, 0, 1, 102, 111, 114, 112, 0, 1, 103, 101, 109, 2, 12, 0, 1, 105, 118, 114, 101, 115, 0, 1, 110, 105, 114, 97, 108, 107, 0, 1, 112, 97, 116, 0, 1, 112, 109, 111, 114, 116, 0, 1, 115, 108, 105, 116, 0, 1, 115, 114, 101, 118, 111, 0, 8, 107, 115, 0, 8, 115, 2, 32, 12, 0, 8, 115, 100, 110, 105, 2, 32, 0, 8, 115, 101, 100, 108, 105, 0, 8, 115, 117, 2, 32, 0, 95, 1, 114, 111, 102, 3, 47, 0, 4, 1, 102, 111, 114, 112, 2, 105, 3, 106, 47, 0, 1, 105, 114, 114, 97, 104, 0, 1, 114, 107, 101, 115, 2, 195, 166, 114, 0, 1, 114, 21, 2, 32, 12, 3, 106, 84, 0, 4, 1, 107, 105, 114, 98, 3, 107, 47, 0, 1, 108, 98, 97, 116, 0, 1, 108, 101, 109, 111, 0, 1, 108, 101, 114, 166, 195, 112, 2, 12, 0, 1, 108, 105, 111, 116, 0, 1, 108, 108, 97, 98, 122, 122, 97, 106, 0, 1, 108, 108, 105, 98, 0, 1, 108, 111, 105, 118, 0, 1, 108, 112, 2, 12, 0, 1, 108, 112, 100, 108, 117, 103, 0, 1, 108, 112, 109, 97, 107, 115, 0, 1, 108, 112, 114, 101, 118, 101, 108, 0, 1, 108, 112, 115, 2, 12, 0, 1, 108, 112, 118, 108, 184, 195, 115, 0, 1, 110, 101, 103, 97, 108, 102, 117, 109, 97, 107, 0, 1, 110, 101, 107, 115, 105, 102, 0, 1, 110, 108, 101, 2, 12, 0, 1, 110, 111, 106, 97, 98, 0, 1, 110, 114, 165, 195, 104, 0, 1, 116, 110, 105, 118, 107, 0, 1, 116, 114, 97, 118, 107, 0, 8, 115, 115, 97, 98, 0, 116, 1, 108, 105, 111, 116, 0, 116, 1, 108, 108, 105, 98, 0, 116, 1, 108, 112, 2, 12, 0, 4, 1, 114, 97, 103, 114, 97, 109, 3, 109, 47, 0, 1, 114, 100, 110, 105, 2, 12, 0, 1, 114, 101, 98, 184, 195, 107, 2, 12, 0, 1, 114, 101, 100, 121, 114, 103, 2, 12, 0, 1, 114, 101, 100, 165, 195, 114, 2, 12, 0, 1, 114, 101, 100, 184, 195, 109, 2, 12, 0, 1, 114, 101, 102, 102, 97, 114, 116, 115, 2, 12, 0, 1, 114, 101, 103, 97, 108, 107, 2, 12, 0, 1, 114, 101, 103, 103, 121, 98, 2, 12, 0, 1, 114, 101, 103, 105, 108, 2, 12, 0, 1, 114, 101, 103, 110, 101, 112, 103, 97, 100, 2, 12, 0, 1, 114, 101, 105, 108, 105, 109, 97, 102, 2, 12, 0, 1, 114, 101, 107, 115, 101, 110, 110, 101, 109, 2, 12, 0, 1, 114, 101, 107, 115, 105, 102, 2, 12, 0, 1, 114, 101, 108, 97, 116, 2, 12, 0, 1, 114, 101, 108, 97, 116, 165, 195, 112, 2, 12, 0, 1, 114, 101, 108, 111, 107, 115, 2, 12, 0, 1, 114, 101, 109, 109, 101, 116, 115, 2, 12, 0, 1, 114, 101, 110, 97, 118, 100, 166, 195, 115, 2, 12, 0, 1, 114, 101, 110, 101, 2, 12, 12, 0, 1, 114, 101, 116, 115, 101, 106, 184, 195, 104, 0, 1, 114, 101, 116, 115, 114, 184, 195, 102, 2, 12, 0, 1, 114, 101, 116, 116, 97, 107, 115, 2, 12, 0, 1, 114, 101, 116, 116, 121, 98, 2, 12, 0, 1, 114, 101, 117, 107, 115, 2, 12, 0, 1, 114, 101, 118, 114, 97, 2, 12, 0, 1, 114, 103, 105, 100, 114, 166, 195, 102, 2, 12, 0, 1, 114, 108, 101, 103, 101, 114, 2, 12, 0, 1, 114, 110, 101, 104, 2, 32, 0, 1, 114, 114, 101, 100, 110, 117, 2, 12, 0, 1, 114, 114, 101, 103, 114, 111, 98, 0, 1, 114, 115, 2, 12, 12, 0, 1, 114, 117, 32, 101, 114, 184, 195, 103, 2, 12, 12, 0, 1, 114, 117, 32, 103, 105, 100, 2, 12, 12, 0, 1, 114, 117, 32, 103, 105, 100, 32, 101, 2, 12, 12, 0, 1, 114, 117, 32, 103, 105, 100, 32, 116, 2, 12, 12, 0, 1, 114, 117, 32, 103, 105, 109, 32, 101, 2, 12, 12, 0, 1, 114, 117, 32, 103, 105, 109, 32, 116, 2, 12, 12, 0, 1, 114, 117, 32, 103, 111, 32, 116, 101, 114, 2, 12, 0, 1, 114, 117, 32, 109, 101, 100, 32, 116, 2, 12, 12, 0, 1, 114, 117, 32, 110, 101, 2, 12, 12, 0, 1, 114, 117, 32, 114, 101, 106, 32, 116, 2, 12, 12, 0, 1, 114, 117, 32, 114, 184, 195, 103, 2, 12, 12, 0, 1, 114, 118, 105, 108, 2, 12, 0, 8, 114, 100, 114, 111, 2, 12, 0, 8, 114, 117, 2, 32, 109, 111, 100, 32, 12, 12, 0, 43, 8, 114, 0, 116, 1, 114, 2, 12, 12, 0, 1, 114, 100, 110, 166, 195, 2, 12, 3, 112, 84, 0, 7, 6, 103, 101, 0, 2, 110, 105, 117, 115, 3, 0, 4, 8, 101, 110, 97, 109, 3, 8, 89, 106, 0, 8, 101, 116, 114, 111, 107, 0, 1, 108, 184, 195, 102, 3, 57, 106, 0, 4, 1, 111, 108, 97, 104, 2, 110, 3, 79, 6, 36, 0, 8, 97, 2, 114, 101, 0, 4, 2, 110, 105, 97, 108, 3, 79, 36, 0, 2, 110, 105, 116, 97, 108, 0, 2, 110, 105, 116, 105, 118, 0, 8, 2, 110, 101, 114, 101, 114, 101, 32, 0, 4, 2, 98, 101, 116, 3, 79, 36, 6, 0, 2, 98, 105, 115, 0, 2, 98, 111, 109, 109, 101, 114, 108, 105, 103, 0, 2, 98, 114, 111, 107, 107, 101, 110, 0, 2, 98, 114, 195, 166, 107, 107, 101, 108, 105, 103, 0, 2, 98, 121, 114, 0, 2, 98, 195, 166, 114, 100, 101, 0, 2, 100, 105, 103, 101, 110, 0, 2, 100, 117, 108, 103, 116, 0, 2, 104, 97, 108, 116, 0, 2, 104, 101, 106, 109, 101, 114, 195, 165, 100, 0, 2, 104, 101, 110, 110, 97, 0, 2, 104, 195, 166, 110, 103, 0, 2, 104, 195, 184, 114, 0, 2, 108, 97, 115, 115, 101, 110, 0, 2, 108, 101, 100, 0, 2, 108, 101, 106, 100, 101, 0, 2, 108, 105, 110, 100, 101, 0, 2, 108, 195, 166, 110, 100, 101, 114, 0, 2, 109, 97, 107, 0, 2, 109, 97, 108, 0, 2, 109, 101, 110, 0, 2, 109, 121, 115, 101, 0, 2, 109, 121, 116, 0, 2, 109, 121, 116, 108, 105, 103, 0, 2, 110, 111, 109, 0, 2, 110, 116, 105, 108, 0, 2, 110, 117, 105, 110, 0, 2, 112, 97, 114, 100, 0, 2, 114, 97, 110, 105, 101, 0, 2, 114, 97, 110, 105, 117, 109, 0, 2, 114, 195, 165, 100, 101, 0, 2, 115, 97, 110, 100, 116, 0, 2, 115, 105, 109, 115, 0, 2, 115, 106, 195, 166, 102, 116, 0, 2, 115, 107, 195, 166, 102, 116, 105, 103, 0, 2, 115, 112, 101, 110, 115, 116, 0, 2, 115, 116, 97, 103, 101, 110, 0, 2, 115, 116, 97, 108, 116, 0, 2, 115, 116, 105, 107, 0, 2, 115, 118, 101, 106, 115, 110, 105, 110, 103, 0, 2, 115, 118, 105, 110, 100, 116, 0, 2, 118, 97, 108, 100, 105, 103, 0, 2, 118, 97, 108, 116, 0, 2, 118, 97, 110, 100, 116, 0, 2, 118, 105, 110, 100, 0, 2, 118, 105, 110, 115, 116, 0, 2, 118, 105, 114, 0, 2, 118, 195, 166, 107, 115, 116, 0, 2, 118, 195, 166, 114, 0, 110, 101, 114, 101, 108, 8, 3, 79, 36, 50, 13, 34, 6, 109, 55, 0, 110, 105, 2, 110, 100, 3, 79, 36, 50, 36, 0, 2, 110, 105, 110, 118, 101, 115, 116, 3, 79, 107, 0, 114, 2, 110, 105, 110, 103, 3, 79, 107, 34, 0, 114, 109, 97, 105, 110, 3, 88, 107, 34, 63, 6, 108, 66, 0, 4, 1, 97, 100, 110, 97, 98, 2, 114, 101, 3, 89, 6, 36, 0, 1, 97, 103, 2, 114, 101, 0, 1, 97, 103, 110, 101, 2, 114, 101, 0, 1, 97, 110, 101, 109, 2, 114, 101, 0, 1, 97, 114, 97, 103, 2, 114, 101, 0, 1, 97, 114, 117, 111, 102, 2, 114, 101, 0, 1, 101, 116, 111, 114, 112, 2, 114, 101, 0, 1, 105, 108, 103, 101, 110, 2, 114, 101, 0, 1, 110, 97, 104, 99, 2, 114, 101, 0, 1, 110, 97, 114, 2, 114, 101, 0, 1, 110, 97, 114, 100, 110, 105, 2, 114, 101, 0, 1, 110, 97, 114, 100, 117, 2, 114, 101, 0, 1, 110, 97, 114, 114, 97, 2, 114, 101, 0, 1, 111, 108, 2, 114, 101, 0, 1, 111, 108, 100, 110, 105, 2, 114, 101, 0, 1, 114, 97, 104, 99, 2, 114, 101, 0, 1, 114, 117, 2, 114, 101, 0, 1, 117, 106, 2, 114, 101, 0, 1, 100, 117, 98, 2, 116, 3, 89, 6, 107, 0, 4, 1, 111, 108, 2, 109, 195, 184, 3, 89, 36, 0, 2, 110, 101, 114, 116, 0, 2, 110, 101, 114, 195, 184, 115, 0, 2, 110, 105, 0, 8, 2, 110, 101, 32, 0, 8, 2, 110, 101, 114, 101, 0, 8, 2, 110, 101, 118, 101, 114, 0, 4, 110, 101, 114, 2, 32, 109, 105, 103, 3, 89, 36, 50, 6, 36, 34, 0, 110, 101, 114, 2, 101, 32, 109, 105, 103, 0, 4, 1, 101, 110, 97, 109, 3, 89, 106, 0, 1, 101, 116, 114, 111, 107, 0, 1, 111, 108, 2, 98, 114, 111, 0, 1, 111, 108, 2, 110, 0, 1, 111, 108, 114, 101, 114, 117, 109, 105, 114, 102, 0, 8, 111, 108, 2, 32, 0, 114, 8, 111, 108, 2, 32, 3, 89, 112, 0, 4, 1, 111, 108, 111, 107, 121, 2, 110, 3, 106, 0, 1, 111, 108, 111, 116, 107, 111, 114, 112, 2, 110, 0, 7, 6, 105, 103, 0, 1, 114, 116, 110, 105, 3, 6, 37, 0, 1, 100, 114, 166, 195, 118, 2, 101, 110, 115, 116, 97, 110, 100, 3, 6, 37, 79, 0, 1, 10, 2, 28, 33, 12, 12, 3, 8, 37, 0, 104, 116, 1, 108, 3, 35, 57, 47, 0, 104, 116, 121, 1, 109, 3, 35, 57, 47, 37, 0, 4, 8, 108, 2, 32, 103, 111, 100, 116, 3, 36, 49, 0, 8, 108, 2, 32, 111, 114, 100, 101, 110, 116, 108, 105, 103, 116, 0, 8, 108, 2, 32, 112, 195, 166, 110, 116, 0, 8, 108, 2, 32, 114, 111, 108, 105, 103, 116, 0, 8, 108, 2, 32, 115, 116, 105, 108, 108, 101, 0, 4, 1, 100, 97, 100, 100, 101, 2, 116, 3, 36, 79, 0, 1, 100, 97, 115, 111, 114, 112, 2, 116, 0, 1, 100, 101, 100, 166, 195, 109, 115, 2, 116, 0, 1, 100, 101, 116, 108, 101, 104, 2, 116, 0, 1, 100, 101, 116, 109, 166, 195, 107, 115, 2, 116, 0, 1, 100, 112, 111, 2, 116, 0, 1, 100, 117, 107, 105, 97, 104, 2, 116, 0, 1, 108, 112, 2, 116, 12, 0, 1, 115, 100, 2, 116, 12, 0, 1, 115, 110, 2, 116, 12, 0, 1, 115, 112, 111, 2, 116, 12, 0, 1, 118, 115, 2, 116, 12, 0, 8, 98, 2, 32, 0, 8, 100, 2, 116, 0, 103, 1, 108, 2, 101, 12, 12, 0, 103, 101, 114, 1, 110, 3, 36, 79, 112, 0, 4, 1, 100, 97, 116, 115, 3, 37, 0, 1, 100, 108, 0, 1, 100, 110, 166, 195, 104, 101, 98, 0, 1, 108, 111, 98, 2, 12, 0, 1, 115, 100, 105, 104, 0, 1, 115, 100, 111, 114, 116, 0, 1, 115, 100, 117, 109, 115, 0, 1, 115, 100, 117, 112, 0, 1, 115, 100, 117, 112, 2, 116, 0, 1, 116, 116, 97, 102, 0, 2, 32, 0, 2, 104, 101, 100, 12, 0, 2, 115, 0, 4, 101, 1, 114, 107, 2, 110, 3, 37, 12, 13, 0, 101, 1, 115, 2, 12, 12, 0, 101, 2, 12, 12, 0, 101, 110, 1, 112, 3, 37, 12, 106, 50, 0, 101, 114, 2, 12, 3, 37, 12, 112, 0, 116, 1, 21, 2, 32, 3, 37, 47, 0, 1, 112, 2, 32, 3, 37, 49, 0, 116, 1, 110, 101, 103, 184, 195, 100, 3, 37, 49, 47, 0, 4, 1, 100, 101, 110, 115, 3, 37, 57, 0, 1, 100, 105, 115, 110, 101, 103, 0, 1, 100, 121, 0, 1, 108, 2, 101, 110, 101, 0, 1, 110, 115, 0, 1, 116, 115, 2, 101, 12, 0, 101, 1, 100, 2, 110, 100, 101, 3, 37, 57, 13, 0, 4, 101, 1, 110, 115, 2, 12, 3, 37, 57, 106, 0, 101, 1, 118, 2, 110, 0, 4, 1, 107, 100, 117, 3, 37, 79, 0, 1, 108, 2, 97, 12, 12, 0, 1, 108, 2, 114, 97, 109, 0, 1, 114, 105, 100, 2, 101, 110, 116, 0, 8, 107, 2, 32, 0, 4, 101, 1, 100, 101, 114, 2, 114, 3, 37, 79, 6, 36, 0, 101, 1, 108, 105, 118, 105, 114, 112, 0, 101, 1, 108, 108, 101, 116, 110, 105, 2, 110, 0, 101, 1, 114, 101, 2, 114, 101, 0, 101, 1, 114, 105, 100, 2, 114, 0, 101, 1, 114, 114, 2, 114, 0, 101, 1, 118, 97, 110, 2, 114, 0, 101, 114, 105, 97, 1, 110, 3, 37, 79, 6, 36, 51, 37, 108, 0, 101, 2, 110, 12, 3, 37, 79, 6, 107, 0, 101, 1, 110, 2, 114, 105, 3, 37, 79, 36, 0, 101, 97, 1, 114, 102, 2, 114, 3, 37, 79, 37, 0, 101, 114, 8, 110, 2, 32, 3, 37, 79, 112, 0, 115, 1, 114, 107, 3, 37, 87, 0, 101, 110, 1, 108, 105, 100, 2, 99, 101, 3, 37, 89, 6, 110, 66, 0, 101, 1, 108, 111, 114, 3, 37, 107, 0, 7, 6, 105, 110, 0, 4, 1, 10, 2, 28, 33, 3, 6, 37, 50, 0, 1, 116, 97, 108, 10, 2, 28, 33, 0, 1, 116, 110, 97, 122, 121, 98, 0, 101, 1, 10, 2, 116, 114, 121, 107, 28, 33, 3, 6, 37, 50, 13, 0, 101, 1, 10, 2, 28, 33, 3, 6, 37, 50, 106, 0, 101, 1, 10, 2, 114, 28, 33, 3, 6, 37, 50, 112, 0, 4, 1, 115, 115, 97, 10, 2, 28, 33, 3, 6, 107, 66, 0, 1, 116, 97, 10, 2, 28, 33, 0, 4, 1, 108, 101, 118, 2, 102, 111, 114, 109, 101, 114, 101, 116, 3, 36, 50, 0, 100, 2, 104, 111, 108, 100, 0, 1, 10, 2, 97, 114, 28, 33, 3, 37, 50, 6, 0, 101, 1, 10, 2, 114, 101, 28, 33, 3, 37, 50, 6, 36, 0, 101, 1, 98, 97, 107, 2, 116, 3, 37, 50, 6, 107, 0, 7, 6, 105, 115, 0, 116, 1, 10, 2, 28, 33, 3, 7, 37, 87, 47, 0, 116, 1, 10, 2, 105, 107, 28, 33, 3, 37, 87, 47, 6, 0, 116, 105, 107, 101, 1, 10, 2, 114, 101, 3, 37, 87, 47, 37, 49, 6, 36, 0, 7, 6, 105, 116, 0, 1, 10, 2, 116, 28, 33, 3, 6, 37, 0, 1, 10, 2, 28, 33, 3, 6, 37, 47, 0, 1, 10, 2, 97, 110, 28, 33, 3, 37, 47, 6, 0, 105, 111, 110, 1, 10, 2, 28, 33, 3, 37, 89, 6, 39, 50, 0, 7, 6, 105, 118, 0, 4, 8, 116, 97, 116, 115, 3, 6, 37, 58, 0, 8, 116, 107, 97, 114, 116, 110, 111, 107, 0, 4, 8, 97, 110, 3, 6, 37, 82, 0, 8, 99, 115, 97, 108, 0, 8, 100, 110, 117, 114, 101, 103, 0, 8, 107, 114, 97, 0, 8, 115, 105, 99, 101, 100, 0, 8, 115, 114, 117, 107, 0, 8, 115, 115, 97, 109, 0, 8, 115, 166, 195, 104, 100, 97, 0, 8, 116, 97, 105, 116, 105, 110, 105, 0, 8, 116, 97, 108, 117, 103, 101, 114, 0, 8, 116, 107, 101, 112, 115, 114, 101, 112, 0, 8, 116, 107, 101, 114, 105, 100, 0, 8, 116, 107, 101, 116, 101, 100, 0, 8, 116, 111, 109, 0, 8, 116, 111, 109, 111, 107, 111, 108, 0, 8, 116, 112, 97, 100, 97, 0, 8, 116, 112, 117, 114, 101, 0, 8, 116, 114, 101, 115, 115, 97, 0, 8, 116, 114, 111, 98, 97, 0, 8, 116, 114, 111, 112, 115, 0, 8, 116, 115, 97, 114, 116, 110, 111, 107, 0, 8, 116, 115, 101, 103, 105, 100, 0, 8, 116, 117, 107, 101, 115, 107, 101, 0, 7, 6, 109, 101, 0, 116, 8, 114, 117, 111, 103, 3, 63, 6, 36, 0, 110, 116, 1, 10, 3, 63, 6, 36, 50, 47, 0, 4, 110, 116, 1, 101, 115, 115, 111, 100, 110, 101, 3, 63, 6, 110, 66, 0, 110, 116, 8, 97, 114, 101, 112, 109, 101, 116, 0, 110, 116, 8, 101, 98, 109, 97, 106, 110, 101, 0, 110, 116, 8, 101, 99, 97, 108, 112, 101, 100, 0, 110, 116, 8, 101, 99, 110, 97, 118, 97, 0, 110, 116, 8, 101, 100, 114, 97, 98, 109, 111, 98, 0, 110, 116, 8, 101, 103, 97, 103, 110, 101, 0, 110, 116, 8, 101, 103, 110, 97, 104, 99, 0, 110, 116, 8, 101, 103, 110, 97, 114, 114, 97, 0, 110, 116, 8, 101, 104, 99, 97, 116, 101, 100, 0, 110, 116, 8, 101, 108, 98, 184, 195, 109, 0, 110, 116, 8, 101, 108, 103, 101, 114, 0, 110, 116, 8, 101, 108, 108, 101, 118, 105, 110, 0, 110, 116, 8, 101, 108, 112, 112, 117, 115, 0, 110, 116, 8, 101, 110, 105, 102, 102, 97, 114, 0, 110, 116, 8, 101, 110, 110, 111, 98, 97, 0, 110, 116, 8, 101, 110, 110, 111, 116, 97, 107, 0, 110, 116, 8, 101, 110, 114, 101, 118, 117, 103, 0, 110, 116, 8, 101, 115, 115, 97, 108, 107, 0, 110, 116, 8, 101, 115, 115, 105, 108, 98, 97, 116, 101, 0, 110, 116, 8, 101, 115, 115, 105, 116, 114, 101, 118, 97, 0, 110, 116, 8, 101, 115, 115, 105, 116, 114, 101, 118, 105, 100, 0, 110, 116, 8, 101, 115, 115, 111, 110, 97, 107, 0, 110, 116, 8, 101, 115, 115, 111, 112, 0, 110, 116, 8, 101, 116, 107, 97, 114, 116, 0, 110, 116, 8, 101, 116, 114, 97, 112, 101, 100, 0, 110, 116, 8, 101, 118, 97, 108, 0, 110, 116, 8, 105, 108, 112, 109, 111, 107, 0, 110, 116, 8, 105, 116, 110, 101, 115, 115, 101, 114, 0, 110, 116, 8, 105, 116, 114, 111, 115, 0, 4, 110, 116, 8, 101, 108, 97, 110, 103, 105, 115, 3, 63, 7, 110, 66, 0, 110, 116, 8, 101, 110, 110, 111, 115, 166, 195, 114, 0, 116, 1, 114, 117, 111, 103, 3, 63, 36, 0, 4, 110, 116, 101, 1, 101, 108, 103, 101, 114, 2, 114, 101, 116, 3, 63, 36, 50, 47, 6, 36, 0, 110, 116, 101, 8, 101, 108, 103, 101, 114, 2, 114, 101, 0, 110, 116, 101, 108, 8, 117, 114, 116, 115, 110, 105, 3, 63, 36, 50, 47, 6, 36, 55, 0, 110, 116, 101, 108, 1, 117, 114, 116, 115, 110, 105, 3, 63, 36, 50, 47, 36, 55, 0, 4, 110, 2, 116, 117, 115, 105, 97, 115, 3, 63, 110, 66, 0, 110, 116, 1, 97, 114, 101, 112, 109, 101, 116, 0, 110, 116, 1, 101, 98, 109, 97, 106, 110, 101, 0, 110, 116, 1, 101, 99, 97, 108, 112, 101, 100, 0, 110, 116, 1, 101, 99, 110, 97, 118, 97, 0, 110, 116, 1, 101, 100, 114, 97, 98, 109, 111, 98, 0, 110, 116, 1, 101, 103, 97, 103, 110, 101, 0, 110, 116, 1, 101, 103, 110, 97, 104, 99, 0, 110, 116, 1, 101, 103, 110, 97, 114, 114, 97, 0, 110, 116, 1, 101, 104, 99, 97, 116, 101, 100, 0, 110, 116, 1, 101, 108, 97, 110, 103, 105, 115, 0, 110, 116, 1, 101, 108, 98, 184, 195, 109, 0, 110, 116, 1, 101, 108, 103, 101, 114, 0, 110, 116, 1, 101, 108, 108, 101, 118, 105, 110, 0, 110, 116, 1, 101, 108, 112, 112, 117, 115, 0, 110, 116, 1, 101, 110, 105, 102, 102, 97, 114, 0, 110, 116, 1, 101, 110, 110, 111, 98, 97, 0, 110, 116, 1, 101, 110, 110, 111, 115, 166, 195, 114, 0, 110, 116, 1, 101, 110, 110, 111, 116, 97, 107, 0, 110, 116, 1, 101, 110, 114, 101, 118, 117, 103, 0, 110, 116, 1, 101, 115, 115, 97, 108, 107, 0, 110, 116, 1, 101, 115, 115, 105, 108, 98, 97, 116, 101, 0, 110, 116, 1, 101, 115, 115, 105, 116, 114, 101, 118, 97, 0, 110, 116, 1, 101, 115, 115, 105, 116, 114, 101, 118, 105, 100, 0, 110, 116, 1, 101, 115, 115, 111, 110, 110, 111, 107, 0, 110, 116, 1, 101, 115, 115, 111, 112, 0, 110, 116, 1, 101, 116, 107, 97, 114, 116, 0, 110, 116, 1, 101, 116, 114, 97, 112, 101, 100, 0, 110, 116, 1, 101, 118, 97, 108, 0, 110, 116, 1, 105, 108, 112, 109, 111, 107, 0, 110, 116, 1, 105, 116, 110, 101, 115, 115, 101, 114, 0, 110, 116, 1, 105, 116, 114, 111, 115, 0, 7, 6, 110, 100, 0, 4, 1, 97, 101, 110, 2, 101, 114, 3, 8, 50, 70, 0, 1, 97, 109, 97, 2, 97, 0, 1, 97, 110, 114, 101, 102, 2, 111, 0, 4, 1, 17, 65, 3, 50, 0, 1, 97, 98, 2, 101, 108, 0, 1, 97, 98, 32, 103, 101, 106, 2, 101, 114, 0, 1, 97, 98, 32, 117, 100, 2, 101, 114, 0, 1, 97, 98, 114, 111, 102, 2, 101, 114, 0, 1, 97, 104, 2, 101, 108, 0, 1, 97, 108, 0, 1, 97, 108, 2, 97, 114, 0, 1, 97, 112, 2, 101, 108, 111, 107, 0, 1, 97, 116, 115, 2, 12, 0, 1, 97, 118, 2, 97, 102, 0, 1, 101, 2, 101, 12, 0, 1, 101, 2, 101, 108, 105, 103, 0, 1, 101, 107, 2, 101, 108, 0, 1, 105, 2, 101, 114, 107, 114, 101, 100, 115, 12, 0, 1, 105, 2, 101, 114, 108, 12, 0, 1, 105, 2, 101, 114, 115, 116, 12, 0, 1, 105, 2, 105, 109, 101, 108, 108, 101, 109, 0, 1, 105, 98, 2, 101, 0, 1, 105, 98, 2, 105, 110, 0, 1, 105, 102, 2, 12, 0, 1, 105, 102, 2, 101, 108, 195, 184, 110, 0, 1, 105, 109, 2, 101, 0, 1, 105, 116, 2, 105, 110, 0, 1, 105, 118, 2, 101, 0, 1, 105, 118, 2, 105, 110, 0, 1, 105, 118, 107, 0, 1, 105, 118, 115, 2, 101, 108, 0, 1, 117, 100, 2, 114, 101, 0, 1, 117, 104, 2, 12, 0, 1, 121, 2, 101, 108, 0, 1, 121, 108, 112, 2, 114, 0, 1, 165, 195, 2, 101, 108, 105, 0, 1, 165, 195, 104, 2, 97, 114, 0, 2, 101, 108, 115, 101, 0, 8, 97, 98, 32, 101, 100, 2, 101, 114, 0, 8, 97, 98, 32, 105, 2, 101, 114, 0, 8, 97, 98, 32, 105, 118, 2, 101, 114, 0, 8, 97, 98, 32, 110, 97, 109, 2, 101, 114, 0, 8, 105, 2, 114, 101, 116, 0, 101, 1, 101, 118, 2, 108, 0, 101, 1, 105, 109, 2, 108, 105, 0, 101, 1, 117, 115, 105, 109, 2, 108, 105, 103, 0, 110, 1, 17, 65, 0, 101, 1, 105, 118, 101, 2, 108, 105, 3, 50, 13, 0, 101, 108, 1, 97, 109, 3, 50, 13, 55, 0, 1, 97, 98, 2, 101, 114, 3, 50, 19, 0, 4, 1, 17, 65, 2, 97, 116, 3, 50, 70, 0, 1, 17, 65, 2, 114, 101, 0, 1, 17, 65, 2, 114, 105, 110, 0, 1, 97, 2, 97, 108, 117, 115, 0, 1, 97, 2, 101, 108, 0, 1, 97, 2, 114, 101, 0, 1, 97, 2, 121, 0, 1, 97, 98, 2, 97, 103, 101, 0, 1, 97, 98, 2, 101, 107, 114, 105, 0, 1, 97, 98, 2, 101, 109, 101, 100, 108, 101, 109, 0, 1, 97, 98, 2, 101, 110, 115, 0, 1, 97, 98, 2, 101, 114, 110, 101, 0, 1, 97, 98, 2, 101, 114, 111, 0, 1, 97, 98, 2, 101, 117, 118, 195, 166, 115, 101, 110, 0, 1, 97, 98, 2, 105, 116, 0, 1, 97, 103, 2, 97, 0, 1, 97, 103, 2, 101, 114, 101, 0, 1, 97, 104, 2, 105, 0, 1, 97, 107, 115, 2, 97, 0, 1, 97, 107, 115, 2, 105, 110, 97, 118, 0, 1, 97, 107, 115, 114, 97, 109, 0, 1, 97, 109, 2, 97, 103, 0, 1, 97, 109, 2, 97, 114, 105, 110, 0, 1, 97, 109, 109, 2, 101, 114, 0, 1, 97, 109, 109, 2, 111, 0, 1, 97, 109, 109, 111, 107, 0, 1, 97, 112, 2, 97, 0, 1, 97, 114, 101, 118, 2, 97, 0, 1, 97, 114, 105, 109, 2, 97, 0, 1, 97, 115, 2, 97, 108, 0, 1, 97, 116, 115, 2, 97, 114, 0, 1, 97, 118, 2, 97, 108, 0, 1, 97, 118, 2, 101, 114, 98, 105, 108, 116, 0, 1, 97, 118, 2, 114, 101, 0, 1, 101, 2, 111, 103, 101, 110, 0, 1, 101, 2, 111, 107, 114, 105, 0, 1, 101, 2, 111, 115, 0, 1, 101, 2, 111, 115, 107, 111, 112, 0, 1, 101, 32, 121, 112, 112, 97, 104, 2, 32, 0, 1, 101, 100, 100, 97, 0, 1, 101, 100, 105, 108, 97, 118, 101, 114, 0, 1, 101, 100, 105, 118, 105, 100, 0, 1, 101, 102, 2, 101, 114, 0, 1, 101, 103, 2, 97, 110, 0, 1, 101, 103, 101, 108, 2, 97, 114, 105, 115, 107, 0, 1, 101, 103, 117, 106, 0, 1, 101, 104, 2, 101, 114, 115, 111, 110, 0, 1, 101, 104, 97, 114, 116, 98, 117, 115, 0, 1, 101, 106, 101, 2, 101, 108, 0, 1, 101, 107, 2, 105, 115, 0, 1, 101, 108, 98, 2, 101, 0, 1, 101, 108, 101, 2, 105, 103, 0, 1, 101, 112, 2, 101, 114, 103, 97, 115, 116, 0, 1, 101, 112, 2, 105, 0, 1, 101, 112, 115, 2, 101, 114, 0, 1, 101, 116, 2, 101, 110, 0, 1, 101, 116, 2, 101, 110, 115, 0, 1, 101, 116, 115, 0, 1, 101, 116, 116, 105, 109, 105, 100, 0, 1, 101, 117, 110, 105, 109, 0, 1, 101, 118, 100, 184, 195, 110, 2, 105, 103, 0, 1, 101, 119, 2, 101, 108, 0, 1, 101, 119, 2, 121, 0, 1, 101, 119, 103, 2, 97, 0, 1, 105, 2, 101, 107, 115, 0, 1, 105, 2, 101, 117, 0, 1, 105, 2, 105, 0, 1, 105, 2, 105, 103, 12, 0, 1, 105, 2, 111, 107, 105, 0, 1, 105, 2, 111, 110, 101, 0, 1, 105, 2, 117, 0, 1, 105, 99, 2, 121, 0, 1, 105, 102, 2, 101, 108, 0, 1, 105, 108, 2, 97, 0, 1, 105, 108, 2, 121, 0, 1, 105, 118, 2, 114, 105, 107, 0, 1, 105, 118, 2, 117, 0, 1, 111, 2, 105, 0, 1, 111, 98, 32, 115, 101, 109, 97, 106, 0, 1, 111, 107, 2, 101, 109, 110, 101, 114, 101, 0, 1, 111, 107, 2, 101, 110, 115, 0, 1, 111, 107, 2, 105, 0, 1, 111, 107, 2, 111, 108, 0, 1, 111, 107, 2, 111, 108, 101, 114, 101, 0, 1, 111, 114, 2, 101, 108, 0, 1, 117, 2, 110, 101, 0, 1, 117, 2, 114, 101, 0, 1, 117, 102, 2, 97, 0, 1, 117, 102, 2, 101, 114, 0, 1, 117, 104, 2, 106, 195, 166, 118, 101, 108, 0, 1, 117, 104, 2, 121, 114, 0, 1, 117, 107, 101, 115, 0, 1, 117, 109, 2, 101, 114, 105, 110, 103, 0, 1, 117, 114, 32, 110, 101, 2, 101, 0, 1, 117, 114, 115, 2, 101, 0, 1, 184, 195, 115, 2, 97, 103, 0, 2, 97, 103, 0, 2, 101, 110, 116, 0, 2, 105, 100, 97, 0, 2, 105, 103, 0, 2, 111, 109, 0, 2, 121, 114, 0, 2, 195, 165, 115, 101, 0, 2, 195, 184, 100, 0, 2, 195, 184, 114, 0, 8, 97, 98, 32, 110, 101, 2, 101, 0, 8, 97, 98, 32, 110, 101, 100, 2, 101, 0, 8, 105, 2, 101, 114, 32, 12, 0, 8, 105, 2, 121, 0, 8, 105, 103, 97, 98, 0, 8, 111, 98, 2, 32, 0, 4, 1, 97, 109, 114, 111, 110, 2, 105, 3, 50, 70, 6, 0, 1, 97, 112, 2, 111, 114, 97, 0, 1, 101, 109, 2, 111, 122, 97, 0, 1, 101, 112, 2, 117, 108, 0, 101, 8, 97, 109, 2, 108, 97, 3, 50, 70, 6, 36, 0, 4, 105, 103, 1, 101, 118, 3, 50, 70, 37, 0, 105, 103, 1, 117, 114, 103, 0, 105, 103, 1, 121, 0, 105, 103, 1, 121, 109, 0, 4, 101, 1, 97, 98, 2, 108, 101, 100, 101, 114, 12, 3, 50, 70, 106, 0, 101, 1, 97, 98, 2, 109, 101, 100, 108, 101, 109, 0, 101, 1, 97, 98, 2, 111, 112, 103, 195, 184, 114, 0, 101, 1, 97, 98, 32, 101, 108, 101, 104, 0, 101, 1, 97, 98, 32, 110, 105, 100, 0, 101, 1, 97, 98, 32, 110, 105, 109, 0, 101, 1, 97, 98, 32, 115, 101, 114, 0, 101, 1, 97, 98, 101, 110, 114, 184, 195, 106, 98, 0, 101, 1, 97, 98, 101, 118, 121, 116, 0, 101, 1, 97, 98, 114, 101, 118, 184, 195, 114, 0, 97, 108, 101, 1, 101, 112, 112, 105, 104, 99, 3, 50, 70, 107, 57, 55, 0, 101, 1, 97, 115, 2, 108, 105, 103, 3, 50, 106, 0, 7, 6, 110, 103, 0, 1, 105, 109, 97, 108, 102, 2, 111, 3, 8, 50, 79, 0, 1, 105, 102, 2, 114, 101, 3, 8, 66, 0, 1, 97, 114, 111, 2, 101, 3, 8, 66, 87, 57, 0, 2, 117, 100, 3, 50, 70, 0, 1, 105, 114, 114, 101, 100, 2, 101, 114, 3, 50, 73, 0, 4, 1, 17, 65, 2, 111, 3, 50, 79, 0, 1, 97, 2, 105, 118, 0, 1, 97, 116, 2, 101, 110, 116, 0, 1, 97, 118, 101, 2, 101, 108, 0, 1, 101, 103, 2, 105, 118, 12, 0, 1, 101, 103, 114, 111, 109, 2, 114, 121, 0, 1, 101, 104, 2, 101, 109, 0, 1, 101, 104, 2, 105, 118, 0, 1, 101, 114, 2, 195, 184, 114, 0, 1, 105, 118, 2, 195, 165, 114, 100, 0, 1, 118, 97, 110, 2, 105, 118, 0, 1, 166, 195, 107, 2, 117, 114, 117, 0, 2, 97, 0, 2, 101, 118, 195, 166, 114, 0, 2, 108, 97, 115, 0, 2, 114, 97, 100, 0, 2, 117, 108, 118, 0, 2, 121, 109, 110, 97, 115, 116, 0, 2, 195, 166, 108, 100, 0, 8, 97, 2, 17, 65, 0, 8, 105, 102, 2, 101, 114, 101, 0, 1, 97, 112, 2, 195, 166, 97, 3, 50, 79, 6, 0, 117, 1, 97, 108, 2, 115, 116, 3, 50, 79, 6, 40, 0, 101, 114, 2, 114, 105, 103, 3, 50, 79, 107, 34, 0, 101, 110, 105, 1, 105, 2, 195, 184, 3, 50, 89, 37, 50, 0, 4, 3, 66, 0, 1, 97, 102, 2, 97, 114, 109, 0, 1, 105, 102, 2, 101, 114, 101, 110, 12, 0, 4, 1, 105, 116, 2, 101, 110, 116, 3, 66, 79, 0, 1, 117, 102, 2, 101, 114, 0, 4, 1, 97, 104, 99, 2, 101, 109, 101, 110, 116, 3, 66, 87, 57, 0, 8, 97, 114, 2, 101, 114, 0, 101, 97, 1, 97, 114, 111, 2, 100, 101, 3, 66, 87, 57, 6, 108, 0, 4, 1, 97, 114, 2, 101, 114, 101, 3, 66, 89, 0, 1, 97, 114, 114, 97, 0, 1, 111, 108, 108, 97, 2, 101, 0, 101, 114, 1, 105, 102, 3, 66, 112, 0, 7, 6, 111, 110, 0, 1, 10, 2, 110, 28, 33, 3, 6, 39, 0, 4, 1, 10, 2, 28, 33, 3, 6, 39, 50, 0, 1, 102, 101, 108, 10, 2, 28, 33, 0, 1, 102, 111, 10, 2, 28, 33, 0, 1, 108, 101, 10, 2, 28, 33, 0, 1, 116, 111, 102, 0, 1, 116, 111, 110, 111, 109, 0, 8, 100, 101, 107, 97, 109, 0, 110, 1, 108, 111, 107, 3, 6, 112, 50, 0, 4, 1, 98, 114, 97, 107, 3, 6, 112, 66, 0, 1, 99, 10, 2, 28, 33, 0, 1, 102, 105, 10, 2, 28, 33, 0, 1, 102, 108, 97, 2, 115, 0, 1, 106, 10, 2, 28, 33, 0, 1, 108, 10, 2, 28, 33, 0, 1, 112, 10, 2, 28, 33, 0, 1, 114, 114, 101, 112, 0, 1, 116, 10, 2, 28, 33, 0, 1, 116, 114, 97, 107, 0, 8, 108, 97, 115, 0, 8, 108, 108, 97, 98, 0, 8, 108, 108, 105, 118, 97, 112, 0, 8, 115, 166, 195, 115, 0, 4, 1, 108, 116, 97, 105, 114, 116, 3, 8, 112, 50, 0, 1, 108, 116, 97, 117, 100, 0, 1, 10, 2, 101, 108, 28, 33, 3, 39, 50, 0, 1, 116, 111, 110, 111, 109, 2, 105, 3, 39, 50, 6, 0, 4, 1, 98, 98, 105, 103, 3, 112, 50, 0, 1, 98, 101, 100, 101, 114, 0, 1, 101, 110, 0, 1, 101, 114, 102, 0, 1, 103, 114, 97, 0, 1, 104, 2, 100, 0, 1, 105, 100, 97, 116, 115, 0, 1, 107, 105, 115, 107, 101, 108, 0, 1, 108, 97, 114, 100, 0, 1, 108, 102, 101, 116, 0, 1, 108, 108, 97, 103, 0, 1, 108, 111, 107, 2, 32, 0, 1, 108, 114, 101, 112, 0, 1, 108, 114, 111, 0, 1, 110, 97, 98, 105, 108, 0, 1, 112, 2, 116, 0, 1, 115, 2, 100, 0, 1, 115, 105, 98, 0, 1, 115, 105, 108, 97, 0, 1, 115, 110, 105, 98, 111, 114, 0, 1, 116, 2, 32, 0, 1, 116, 2, 105, 99, 0, 1, 116, 2, 115, 32, 0, 1, 116, 2, 115, 118, 0, 1, 116, 97, 103, 101, 109, 0, 1, 116, 97, 114, 97, 109, 0, 1, 116, 116, 103, 166, 195, 118, 100, 184, 195, 100, 0, 1, 121, 114, 98, 109, 101, 0, 2, 100, 18, 69, 0, 2, 116, 111, 108, 0, 8, 109, 2, 116, 101, 32, 0, 110, 1, 114, 100, 2, 105, 110, 103, 0, 116, 121, 1, 109, 3, 112, 50, 47, 37, 0, 100, 1, 102, 3, 112, 50, 70, 0, 100, 1, 112, 115, 3, 112, 50, 70, 6, 0, 4, 1, 98, 2, 32, 3, 112, 66, 0, 1, 98, 2, 101, 110, 32, 0, 1, 108, 97, 115, 0, 1, 108, 97, 116, 0, 1, 108, 108, 105, 118, 97, 112, 0, 1, 110, 103, 0, 1, 114, 98, 0, 1, 115, 166, 195, 115, 0, 103, 1, 107, 0, 98, 111, 110, 1, 98, 3, 112, 66, 69, 112, 50, 0, 106, 111, 117, 114, 1, 98, 3, 112, 66, 88, 6, 40, 34, 0, 7, 6, 111, 114, 0, 8, 102, 2, 32, 118, 105, 108, 100, 3, 2, 39, 34, 0, 4, 1, 102, 2, 104, 97, 108, 17, 65, 12, 12, 3, 2, 112, 0, 8, 102, 2, 21, 12, 12, 0, 8, 102, 2, 104, 111, 108, 100, 101, 0, 8, 102, 2, 115, 107, 101, 108, 108, 105, 12, 3, 2, 112, 34, 0, 101, 116, 97, 103, 8, 102, 2, 115, 111, 109, 3, 2, 112, 106, 6, 47, 108, 12, 0, 1, 116, 111, 109, 2, 101, 114, 3, 6, 39, 0, 4, 1, 100, 2, 28, 33, 12, 3, 6, 39, 34, 0, 1, 100, 97, 101, 10, 2, 28, 33, 0, 1, 102, 10, 2, 28, 33, 0, 1, 110, 101, 10, 2, 28, 33, 0, 1, 116, 10, 2, 105, 101, 28, 33, 0, 105, 117, 109, 1, 116, 10, 2, 28, 33, 12, 3, 6, 39, 34, 37, 111, 63, 0, 8, 102, 2, 101, 116, 32, 12, 3, 6, 39, 106, 0, 8, 102, 2, 116, 105, 100, 12, 3, 6, 111, 12, 0, 8, 102, 2, 100, 195, 184, 114, 12, 3, 6, 111, 51, 0, 4, 1, 102, 103, 110, 105, 115, 108, 101, 104, 2, 115, 3, 6, 112, 0, 1, 112, 101, 114, 2, 116, 101, 114, 0, 8, 102, 2, 97, 32, 12, 0, 8, 102, 2, 97, 110, 32, 12, 0, 8, 102, 2, 97, 110, 107, 195, 184, 114, 101, 110, 100, 101, 12, 0, 8, 102, 2, 97, 110, 110, 195, 166, 118, 110, 116, 12, 0, 8, 102, 2, 97, 110, 115, 97, 116, 12, 0, 8, 102, 2, 97, 110, 115, 116, 105, 108, 108, 101, 12, 0, 8, 102, 2, 97, 110, 115, 116, 195, 165, 101, 110, 100, 101, 12, 0, 8, 102, 2, 98, 101, 104, 97, 110, 100, 12, 0, 8, 102, 2, 98, 101, 104, 111, 12, 0, 8, 102, 2, 98, 101, 110, 32, 12, 0, 8, 102, 2, 98, 101, 110, 101, 110, 101, 12, 0, 8, 102, 2, 98, 101, 110, 115, 12, 0, 8, 102, 2, 98, 101, 114, 101, 100, 12, 0, 8, 102, 2, 98, 105, 108, 12, 0, 8, 102, 2, 98, 106, 101, 114, 103, 12, 0, 8, 102, 2, 98, 111, 103, 115, 116, 97, 118, 12, 0, 8, 102, 2, 98, 117, 100, 32, 12, 0, 8, 102, 2, 98, 117, 100, 115, 12, 0, 8, 102, 2, 98, 117, 110, 100, 12, 0, 8, 102, 2, 98, 195, 184, 110, 12, 0, 8, 102, 2, 99, 101, 110, 115, 117, 114, 12, 0, 8, 102, 2, 100, 97, 110, 115, 101, 114, 12, 0, 8, 102, 2, 100, 101, 108, 32, 12, 0, 8, 102, 2, 100, 111, 109, 12, 0, 8, 102, 2, 100, 114, 105, 110, 103, 12, 0, 8, 102, 2, 100, 195, 166, 107, 32, 12, 0, 8, 102, 2, 100, 195, 166, 107, 107, 101, 110, 101, 12, 0, 8, 102, 2, 100, 195, 166, 107, 115, 12, 0, 8, 102, 2, 102, 97, 100, 101, 114, 12, 0, 8, 102, 2, 102, 97, 114, 12, 0, 8, 102, 2, 102, 114, 97, 12, 0, 8, 102, 2, 102, 195, 166, 100, 114, 12, 0, 8, 102, 2, 103, 97, 110, 103, 12, 0, 8, 102, 2, 103, 101, 109, 97, 107, 12, 0, 8, 102, 2, 103, 114, 117, 110, 100, 12, 0, 8, 102, 2, 103, 195, 165, 114, 100, 12, 0, 8, 102, 2, 103, 195, 166, 110, 103, 101, 114, 12, 0, 8, 102, 2, 103, 195, 166, 114, 101, 12, 0, 8, 102, 2, 104, 97, 108, 12, 0, 8, 102, 2, 104, 97, 109, 12, 0, 8, 102, 2, 104, 97, 118, 101, 12, 0, 8, 102, 2, 104, 101, 110, 12, 0, 8, 102, 2, 104, 105, 115, 116, 111, 12, 0, 8, 102, 2, 104, 106, 117, 108, 12, 0, 8, 102, 2, 104, 111, 108, 100, 0, 8, 102, 2, 104, 111, 108, 100, 101, 116, 12, 0, 8, 102, 2, 104, 117, 100, 12, 0, 8, 102, 2, 104, 117, 115, 12, 0, 8, 102, 2, 104, 195, 165, 110, 100, 12, 0, 8, 102, 2, 104, 195, 165, 110, 100, 115, 12, 0, 8, 102, 2, 104, 195, 166, 110, 103, 12, 0, 8, 102, 2, 107, 97, 109, 109, 101, 114, 0, 8, 102, 2, 107, 97, 114, 108, 12, 0, 8, 102, 2, 107, 108, 111, 103, 12, 0, 8, 102, 2, 107, 111, 110, 116, 111, 114, 12, 0, 8, 102, 2, 107, 114, 111, 112, 12, 0, 8, 102, 2, 107, 118, 105, 110, 100, 101, 12, 0, 8, 102, 2, 107, 195, 166, 109, 112, 101, 114, 12, 0, 8, 102, 2, 107, 195, 166, 114, 108, 105, 103, 104, 101, 100, 0, 8, 102, 2, 107, 195, 184, 98, 12, 0, 8, 102, 2, 108, 97, 103, 12, 0, 8, 102, 2, 108, 97, 103, 115, 12, 0, 8, 102, 2, 108, 97, 110, 100, 12, 0, 8, 102, 2, 108, 101, 109, 12, 0, 8, 102, 2, 108, 111, 118, 101, 114, 12, 0, 8, 102, 2, 108, 121, 100, 12, 0, 8, 102, 2, 108, 121, 115, 12, 0, 8, 102, 2, 108, 195, 166, 103, 103, 101, 114, 0, 8, 102, 2, 108, 195, 166, 110, 115, 12, 0, 8, 102, 2, 108, 195, 166, 115, 101, 12, 0, 8, 102, 2, 109, 97, 108, 100, 101, 104, 121, 100, 12, 0, 8, 102, 2, 109, 97, 110, 100, 12, 0, 8, 102, 2, 109, 98, 97, 114, 12, 0, 8, 102, 2, 109, 98, 114, 195, 184, 100, 12, 0, 8, 102, 2, 109, 101, 12, 12, 0, 8, 102, 2, 109, 101, 108, 105, 103, 12, 0, 8, 102, 2, 109, 108, 101, 12, 0, 8, 102, 2, 109, 195, 166, 110, 100, 12, 0, 8, 102, 2, 117, 100, 101, 32, 12, 0, 101, 110, 100, 8, 102, 2, 101, 12, 3, 6, 112, 4, 36, 50, 0, 4, 1, 107, 97, 2, 100, 3, 6, 112, 12, 0, 1, 107, 101, 114, 2, 100, 0, 1, 112, 112, 97, 114, 2, 116, 0, 1, 112, 115, 107, 101, 2, 116, 0, 8, 107, 115, 101, 2, 116, 101, 0, 8, 112, 115, 110, 97, 114, 116, 2, 116, 0, 8, 102, 109, 111, 107, 2, 116, 3, 6, 112, 12, 19, 0, 100, 8, 107, 107, 97, 3, 6, 112, 12, 19, 70, 0, 1, 107, 101, 100, 2, 32, 3, 6, 112, 12, 34, 0, 100, 1, 99, 110, 111, 99, 2, 101, 3, 6, 112, 12, 70, 0, 4, 1, 102, 111, 114, 112, 2, 109, 97, 3, 6, 112, 34, 0, 8, 98, 97, 2, 116, 0, 8, 102, 2, 102, 117, 108, 100, 101, 110, 100, 116, 12, 0, 8, 102, 2, 108, 121, 103, 116, 101, 12, 0, 8, 102, 2, 108, 195, 166, 98, 101, 12, 0, 8, 102, 2, 109, 102, 97, 115, 116, 12, 0, 8, 102, 2, 109, 102, 114, 105, 12, 0, 8, 102, 2, 109, 103, 105, 118, 12, 0, 8, 102, 2, 109, 105, 100, 100, 97, 103, 12, 0, 8, 102, 2, 109, 107, 97, 103, 101, 12, 0, 8, 102, 2, 109, 108, 195, 166, 114, 101, 12, 0, 8, 102, 2, 109, 108, 195, 184, 115, 12, 0, 8, 102, 2, 109, 110, 105, 110, 103, 12, 0, 8, 102, 2, 109, 111, 114, 12, 0, 8, 102, 2, 109, 112, 114, 101, 115, 115, 101, 12, 0, 8, 102, 2, 109, 115, 12, 0, 8, 102, 2, 109, 116, 12, 0, 8, 102, 2, 109, 117, 101, 12, 0, 8, 102, 2, 109, 121, 110, 100, 101, 114, 12, 0, 8, 102, 2, 109, 195, 165, 108, 12, 0, 8, 102, 2, 109, 195, 184, 100, 114, 101, 12, 0, 8, 102, 2, 110, 97, 118, 110, 12, 0, 8, 102, 2, 110, 101, 109, 32, 12, 0, 8, 102, 2, 111, 109, 116, 97, 108, 101, 12, 0, 8, 102, 2, 111, 114, 100, 12, 0, 8, 102, 2, 111, 118, 101, 114, 12, 0, 8, 102, 2, 112, 97, 110, 116, 104, 97, 118, 101, 114, 12, 0, 8, 102, 2, 112, 97, 114, 116, 105, 12, 0, 8, 102, 2, 112, 111, 115, 116, 12, 0, 8, 102, 2, 112, 114, 97, 107, 116, 105, 107, 12, 0, 8, 102, 2, 112, 114, 101, 109, 105, 101, 114, 101, 12, 0, 8, 102, 2, 112, 114, 111, 103, 114, 97, 109, 109, 101, 114, 101, 12, 0, 8, 102, 2, 112, 114, 195, 184, 118, 101, 12, 0, 8, 102, 2, 112, 195, 165, 12, 0, 8, 102, 2, 114, 97, 110, 103, 12, 0, 8, 102, 2, 114, 101, 115, 116, 12, 0, 8, 102, 2, 114, 101, 116, 12, 0, 8, 102, 2, 114, 105, 100, 101, 114, 12, 0, 8, 102, 2, 114, 105, 103, 101, 12, 0, 8, 102, 2, 114, 117, 100, 101, 12, 0, 8, 102, 2, 114, 195, 165, 100, 32, 12, 0, 8, 102, 2, 115, 97, 110, 103, 101, 114, 12, 0, 8, 102, 2, 115, 97, 116, 115, 12, 0, 8, 102, 2, 115, 105, 100, 101, 12, 0, 8, 102, 2, 115, 107, 101, 12, 0, 8, 102, 2, 115, 107, 101, 108, 32, 12, 0, 8, 102, 2, 115, 107, 101, 108, 115, 98, 101, 104, 97, 110, 100, 108, 12, 0, 8, 102, 2, 115, 107, 101, 108, 115, 108, 195, 184, 115, 12, 0, 8, 102, 2, 115, 107, 101, 114, 12, 0, 8, 102, 2, 115, 107, 110, 12, 0, 8, 102, 2, 115, 107, 111, 108, 12, 0, 8, 102, 2, 115, 107, 114, 105, 102, 116, 12, 0, 8, 102, 2, 115, 107, 117, 100, 12, 0, 8, 102, 2, 115, 107, 121, 108, 12, 0, 8, 102, 2, 115, 107, 195, 166, 114, 101, 12, 0, 8, 102, 2, 115, 107, 195, 166, 114, 109, 12, 0, 8, 102, 2, 115, 108, 97, 103, 12, 0, 8, 102, 2, 115, 108, 97, 103, 32, 12, 0, 8, 102, 2, 115, 108, 97, 103, 115, 12, 0, 8, 102, 2, 115, 109, 97, 103, 12, 0, 8, 102, 2, 115, 111, 109, 109, 101, 114, 12, 0, 8, 102, 2, 115, 111, 114, 103, 12, 0, 8, 102, 2, 115, 112, 97, 110, 100, 12, 0, 8, 102, 2, 115, 112, 105, 108, 32, 12, 0, 8, 102, 2, 115, 112, 105, 108, 108, 101, 110, 101, 12, 0, 8, 102, 2, 115, 112, 105, 108, 108, 101, 116, 12, 0, 8, 102, 2, 115, 112, 105, 114, 12, 0, 8, 102, 2, 115, 112, 114, 105, 110, 103, 12, 0, 8, 102, 2, 115, 112, 195, 166, 110, 100, 116, 12, 0, 8, 102, 2, 115, 116, 97, 100, 12, 0, 8, 102, 2, 115, 116, 97, 110, 100, 101, 114, 12, 0, 8, 102, 2, 115, 116, 97, 118, 101, 108, 115, 101, 12, 0, 8, 102, 2, 115, 116, 97, 118, 110, 12, 0, 8, 102, 2, 115, 116, 98, 111, 116, 97, 110, 105, 107, 12, 0, 8, 102, 2, 115, 116, 107, 97, 110, 100, 105, 100, 97, 116, 12, 0, 8, 102, 2, 115, 116, 108, 105, 103, 12, 0, 8, 102, 2, 115, 116, 109, 97, 110, 100, 12, 0, 8, 102, 2, 115, 116, 109, 195, 166, 115, 115, 105, 103, 12, 0, 8, 102, 2, 115, 116, 117, 100, 105, 101, 12, 0, 8, 102, 2, 115, 116, 117, 100, 105, 117, 109, 12, 0, 8, 102, 2, 115, 116, 117, 101, 12, 0, 8, 102, 2, 115, 116, 118, 195, 166, 115, 101, 110, 12, 0, 8, 102, 2, 115, 116, 122, 111, 111, 108, 111, 103, 105, 12, 0, 8, 102, 2, 115, 116, 195, 166, 100, 101, 114, 12, 0, 8, 102, 2, 115, 116, 195, 166, 118, 110, 12, 0, 8, 102, 2, 115, 118, 97, 114, 32, 12, 0, 8, 102, 2, 115, 118, 97, 114, 101, 114, 12, 0, 8, 102, 2, 115, 118, 97, 114, 115, 12, 0, 8, 102, 2, 115, 195, 165, 32, 12, 0, 8, 102, 2, 115, 195, 166, 100, 101, 12, 0, 8, 102, 2, 115, 195, 166, 116, 12, 0, 8, 102, 2, 116, 97, 110, 100, 12, 0, 8, 102, 2, 116, 97, 110, 100, 115, 12, 0, 8, 102, 2, 116, 101, 103, 110, 32, 12, 0, 8, 102, 2, 116, 101, 103, 110, 105, 110, 103, 115, 114, 101, 116, 12, 0, 8, 102, 2, 116, 101, 107, 115, 116, 12, 0, 8, 102, 2, 116, 101, 108, 116, 12, 0, 8, 102, 2, 116, 102, 97, 114, 101, 110, 100, 101, 12, 0, 8, 102, 2, 116, 105, 108, 12, 0, 8, 102, 2, 116, 108, 195, 184, 98, 101, 110, 100, 101, 12, 0, 8, 102, 2, 116, 111, 103, 12, 0, 8, 102, 2, 116, 111, 118, 12, 0, 8, 102, 2, 116, 114, 97, 112, 112, 101, 12, 0, 8, 102, 2, 116, 114, 105, 110, 32, 12, 0, 8, 102, 2, 116, 114, 105, 110, 115, 12, 0, 8, 102, 2, 116, 114, 111, 112, 12, 0, 8, 102, 2, 116, 114, 121, 107, 12, 0, 8, 102, 2, 116, 115, 195, 166, 116, 116, 101, 12, 0, 8, 102, 2, 116, 117, 110, 103, 101, 12, 0, 8, 102, 2, 116, 195, 166, 110, 100, 101, 114, 12, 0, 8, 102, 2, 116, 195, 166, 112, 112, 101, 12, 0, 8, 102, 2, 117, 100, 12, 0, 8, 102, 2, 118, 97, 108, 103, 12, 0, 8, 102, 2, 118, 97, 114, 109, 12, 0, 8, 102, 2, 118, 97, 114, 115, 12, 0, 8, 102, 2, 118, 97, 115, 107, 32, 12, 0, 8, 102, 2, 118, 101, 106, 101, 110, 12, 0, 8, 102, 2, 118, 195, 166, 114, 101, 108, 115, 101, 12, 0, 8, 102, 2, 195, 165, 100, 12, 0, 8, 102, 2, 195, 165, 114, 12, 0, 116, 97, 108, 101, 114, 43, 8, 102, 3, 6, 112, 34, 47, 108, 55, 112, 0, 109, 115, 115, 97, 103, 43, 8, 102, 2, 25, 3, 6, 112, 34, 63, 19, 87, 4, 87, 35, 0, 109, 101, 114, 8, 102, 2, 32, 12, 3, 6, 112, 34, 63, 112, 0, 4, 100, 1, 118, 2, 105, 3, 6, 112, 34, 70, 0, 100, 2, 101, 110, 116, 108, 105, 103, 12, 0, 100, 2, 110, 105, 110, 0, 101, 8, 102, 2, 12, 12, 3, 6, 113, 12, 106, 0, 1, 10, 2, 105, 115, 107, 28, 33, 3, 7, 39, 0, 1, 10, 2, 101, 114, 28, 33, 3, 7, 39, 12, 0, 1, 21, 2, 28, 33, 12, 3, 8, 8, 112, 0, 101, 1, 17, 67, 2, 32, 3, 39, 12, 112, 0, 4, 1, 115, 2, 116, 3, 39, 34, 0, 1, 115, 2, 116, 101, 0, 1, 116, 115, 2, 116, 0, 1, 118, 2, 18, 76, 12, 0, 1, 118, 115, 2, 101, 12, 0, 8, 2, 97, 0, 8, 102, 2, 101, 108, 32, 12, 0, 8, 102, 2, 111, 114, 100, 110, 0, 8, 110, 2, 100, 0, 100, 8, 2, 114, 101, 116, 12, 0, 117, 100, 101, 110, 8, 102, 2, 32, 12, 3, 39, 34, 6, 40, 84, 20, 50, 0, 101, 110, 115, 105, 115, 8, 102, 2, 107, 3, 39, 34, 6, 109, 50, 87, 37, 87, 0, 101, 108, 1, 109, 3, 39, 34, 6, 109, 55, 0, 109, 3, 39, 34, 63, 0, 4, 100, 1, 107, 2, 114, 101, 110, 103, 3, 39, 34, 70, 0, 100, 1, 109, 2, 101, 114, 0, 100, 1, 116, 2, 101, 110, 101, 110, 12, 0, 100, 8, 116, 2, 12, 12, 0, 100, 114, 117, 112, 3, 39, 34, 70, 34, 113, 69, 0, 100, 101, 1, 98, 2, 110, 100, 101, 3, 39, 34, 107, 0, 4, 2, 97, 108, 3, 39, 51, 0, 100, 1, 109, 2, 101, 116, 0, 100, 2, 12, 12, 0, 100, 2, 101, 110, 101, 12, 0, 4, 100, 1, 106, 2, 97, 110, 3, 39, 51, 70, 0, 100, 1, 106, 2, 105, 0, 100, 101, 97, 117, 120, 1, 98, 3, 39, 51, 70, 6, 39, 0, 100, 105, 1, 110, 2, 115, 107, 3, 39, 51, 70, 37, 0, 100, 1, 106, 2, 101, 110, 3, 39, 112, 0, 4, 1, 98, 2, 116, 3, 111, 0, 1, 115, 2, 116, 17, 65, 0, 1, 118, 2, 116, 0, 4, 1, 107, 2, 116, 3, 111, 12, 0, 1, 107, 2, 116, 17, 65, 0, 1, 116, 115, 2, 109, 0, 100, 1, 104, 2, 101, 3, 111, 12, 70, 0, 2, 100, 101, 110, 3, 111, 34, 0, 4, 1, 102, 3, 112, 0, 1, 102, 2, 101, 110, 0, 1, 102, 2, 116, 101, 114, 12, 0, 1, 109, 117, 104, 0, 1, 116, 107, 101, 114, 0, 1, 116, 107, 101, 115, 0, 1, 118, 108, 97, 0, 8, 2, 105, 0, 8, 102, 2, 102, 97, 110, 103, 12, 0, 8, 102, 2, 102, 101, 108, 116, 12, 0, 8, 102, 2, 102, 105, 108, 109, 12, 0, 8, 102, 2, 102, 106, 111, 114, 12, 0, 8, 102, 2, 102, 111, 114, 100, 12, 0, 8, 102, 2, 102, 111, 114, 102, 111, 100, 12, 0, 8, 102, 2, 102, 111, 114, 115, 116, 195, 166, 114, 107, 12, 0, 8, 102, 2, 102, 111, 114, 115, 195, 184, 103, 12, 0, 8, 102, 2, 102, 111, 114, 121, 115, 101, 114, 117, 109, 12, 0, 8, 102, 2, 102, 195, 184, 100, 100, 101, 114, 12, 0, 8, 102, 2, 103, 97, 115, 116, 12, 0, 8, 102, 2, 107, 97, 110, 116, 0, 8, 102, 2, 107, 195, 184, 114, 115, 101, 108, 115, 114, 101, 116, 0, 1, 102, 2, 21, 3, 112, 4, 0, 4, 1, 10, 2, 105, 28, 33, 12, 3, 112, 6, 0, 8, 102, 2, 101, 108, 115, 107, 12, 0, 8, 102, 2, 108, 121, 100, 101, 110, 100, 101, 12, 0, 101, 8, 102, 2, 110, 12, 3, 112, 6, 36, 12, 0, 101, 118, 8, 102, 2, 105, 103, 101, 3, 112, 6, 36, 12, 82, 0, 4, 101, 110, 107, 108, 8, 102, 2, 101, 12, 3, 112, 6, 36, 50, 49, 55, 0, 101, 110, 107, 108, 8, 102, 2, 105, 110, 103, 0, 4, 1, 109, 2, 102, 3, 112, 12, 0, 1, 109, 2, 109, 0, 1, 109, 2, 115, 101, 0, 1, 112, 115, 2, 116, 0, 1, 118, 2, 101, 12, 0, 8, 102, 2, 114, 105, 110, 103, 32, 0, 8, 102, 2, 114, 105, 110, 103, 101, 110, 0, 1, 102, 2, 116, 3, 112, 12, 19, 0, 108, 101, 97, 110, 115, 8, 3, 112, 12, 55, 36, 50, 87, 0, 4, 100, 1, 102, 2, 12, 3, 112, 12, 70, 0, 100, 1, 103, 2, 111, 110, 0, 100, 8, 108, 2, 32, 0, 116, 104, 1, 110, 3, 112, 12, 85, 0, 103, 101, 1, 109, 3, 112, 12, 106, 0, 4, 1, 110, 2, 109, 3, 112, 34, 0, 1, 110, 2, 115, 107, 0, 2, 100, 114, 101, 12, 0, 2, 105, 101, 110, 116, 0, 2, 116, 111, 0, 8, 102, 2, 103, 195, 165, 114, 115, 12, 0, 8, 102, 2, 114, 101, 116, 110, 105, 12, 0, 109, 111, 110, 8, 104, 3, 112, 34, 63, 6, 39, 50, 0, 4, 100, 1, 107, 2, 101, 108, 3, 112, 34, 70, 0, 100, 1, 118, 2, 101, 0, 100, 1, 118, 104, 2, 97, 110, 0, 100, 2, 101, 110, 12, 0, 100, 2, 101, 110, 101, 110, 12, 0, 100, 2, 105, 110, 12, 0, 100, 2, 110, 101, 12, 0, 100, 2, 114, 101, 116, 105, 108, 12, 0, 100, 8, 108, 2, 101, 114, 32, 0, 4, 100, 1, 98, 2, 101, 108, 3, 112, 34, 70, 6, 0, 100, 2, 114, 117, 107, 0, 100, 111, 110, 110, 97, 110, 115, 3, 112, 34, 70, 39, 50, 6, 108, 50, 87, 0, 101, 1, 102, 110, 101, 103, 2, 110, 12, 3, 112, 36, 12, 0, 108, 121, 115, 116, 8, 102, 3, 112, 55, 6, 116, 87, 70, 0, 4, 100, 1, 102, 2, 195, 166, 3, 112, 70, 6, 0, 100, 1, 102, 2, 195, 184, 0, 101, 1, 102, 2, 115, 17, 67, 3, 113, 12, 106, 0, 7, 6, 112, 104, 0, 2, 105, 108, 3, 81, 0, 111, 101, 3, 81, 37, 0, 105, 108, 108, 105, 112, 112, 101, 3, 81, 37, 55, 6, 37, 12, 48, 0, 105, 108, 97, 100, 101, 108, 112, 104, 105, 97, 3, 81, 37, 55, 108, 70, 6, 107, 55, 81, 37, 108, 0, 7, 6, 116, 105, 0, 4, 1, 105, 99, 105, 100, 110, 101, 112, 112, 97, 2, 115, 3, 8, 47, 37, 0, 1, 105, 103, 110, 105, 110, 101, 109, 2, 115, 0, 1, 105, 103, 110, 121, 114, 97, 108, 2, 115, 0, 1, 105, 107, 97, 114, 2, 115, 0, 1, 105, 107, 110, 111, 114, 98, 2, 115, 0, 1, 105, 108, 117, 108, 108, 101, 99, 2, 115, 0, 1, 105, 114, 101, 116, 102, 105, 100, 2, 115, 0, 1, 105, 114, 116, 115, 97, 103, 2, 115, 0, 1, 105, 116, 97, 112, 101, 104, 2, 115, 0, 1, 110, 97, 114, 101, 2, 115, 0, 115, 1, 115, 97, 112, 3, 47, 6, 37, 87, 0, 108, 1, 114, 2, 32, 3, 47, 36, 55, 0, 4, 108, 2, 98, 97, 103, 101, 3, 47, 36, 55, 6, 0, 108, 2, 102, 111, 114, 110, 0, 108, 2, 102, 114, 101, 100, 115, 0, 108, 2, 102, 195, 166, 108, 100, 105, 103, 0, 108, 2, 102, 195, 166, 108, 108, 101, 115, 0, 108, 2, 103, 111, 100, 101, 104, 97, 118, 101, 110, 100, 101, 0, 108, 2, 103, 111, 100, 101, 115, 101, 0, 108, 2, 103, 111, 100, 101, 115, 101, 100, 100, 101, 108, 0, 108, 2, 103, 111, 100, 101, 115, 107, 114, 105, 118, 101, 0, 108, 2, 103, 114, 117, 110, 100, 108, 105, 103, 103, 101, 110, 100, 101, 0, 108, 2, 103, 195, 166, 110, 103, 101, 108, 105, 103, 0, 108, 2, 105, 110, 116, 101, 116, 103, 195, 184, 114, 101, 0, 108, 2, 105, 110, 116, 101, 116, 103, 195, 184, 114, 101, 108, 115, 101, 0, 108, 2, 107, 101, 110, 100, 101, 103, 105, 118, 101, 0, 108, 2, 107, 101, 110, 100, 101, 103, 105, 118, 101, 108, 115, 101, 0, 108, 2, 108, 97, 100, 101, 108, 105, 103, 0, 108, 2, 108, 105, 103, 101, 0, 108, 2, 108, 105, 103, 101, 109, 101, 100, 0, 108, 2, 108, 121, 107, 107, 101, 0, 108, 2, 111, 118, 101, 114, 115, 0, 108, 2, 112, 97, 115, 0, 108, 2, 114, 101, 116, 116, 101, 108, 195, 166, 103, 103, 101, 0, 108, 2, 114, 101, 116, 116, 101, 118, 105, 115, 101, 0, 108, 2, 114, 101, 116, 116, 101, 118, 105, 115, 110, 105, 110, 103, 0, 108, 2, 115, 97, 109, 109, 101, 110, 0, 108, 2, 115, 107, 97, 100, 101, 107, 111, 109, 109, 101, 110, 0, 108, 2, 115, 107, 97, 100, 101, 107, 111, 109, 109, 101, 116, 0, 108, 2, 115, 107, 97, 100, 101, 107, 111, 109, 115, 116, 0, 108, 2, 115, 116, 101, 100, 101, 107, 111, 109, 115, 116, 0, 108, 2, 115, 116, 101, 100, 101, 108, 105, 103, 0, 108, 2, 115, 116, 101, 100, 101, 118, 195, 166, 114, 0, 108, 2, 115, 116, 101, 100, 101, 118, 195, 166, 114, 101, 108, 115, 101, 0, 108, 2, 115, 116, 101, 100, 101, 118, 195, 166, 114, 101, 110, 100, 101, 0, 108, 2, 115, 116, 114, 195, 166, 107, 107, 101, 108, 105, 103, 0, 108, 2, 115, 121, 110, 101, 107, 111, 109, 115, 116, 0, 108, 2, 115, 121, 110, 101, 108, 97, 100, 101, 110, 100, 101, 0, 1, 115, 97, 98, 2, 111, 110, 3, 47, 37, 0, 4, 1, 10, 2, 111, 110, 12, 3, 89, 0, 1, 97, 112, 2, 101, 110, 116, 0, 1, 107, 97, 2, 101, 0, 1, 107, 101, 108, 2, 101, 0, 1, 111, 118, 107, 2, 101, 110, 0, 2, 195, 184, 115, 12, 0, 7, 6, 195, 165, 0, 4, 1, 112, 110, 101, 118, 111, 2, 32, 3, 6, 111, 0, 1, 112, 165, 195, 103, 2, 109, 111, 100, 0, 1, 116, 115, 100, 111, 109, 105, 117, 2, 101, 108, 105, 103, 0, 114, 1, 110, 114, 111, 118, 104, 3, 6, 111, 19, 0, 98, 101, 110, 116, 108, 105, 103, 1, 104, 114, 111, 102, 3, 6, 111, 69, 107, 50, 47, 55, 37, 0, 1, 115, 97, 106, 2, 32, 3, 6, 112, 0, 4, 3, 111, 0, 1, 108, 115, 110, 97, 0, 1, 109, 2, 100, 101, 12, 12, 0, 1, 109, 2, 108, 105, 110, 103, 12, 12, 0, 1, 109, 115, 103, 97, 108, 115, 2, 108, 0, 1, 109, 115, 103, 114, 184, 195, 112, 115, 2, 108, 0, 1, 109, 115, 114, 101, 100, 111, 109, 2, 108, 0, 1, 112, 2, 115, 107, 101, 0, 1, 114, 2, 100, 12, 0, 1, 114, 103, 2, 100, 0, 1, 114, 103, 2, 110, 101, 0, 1, 115, 0, 114, 100, 1, 103, 3, 111, 12, 0, 114, 100, 101, 1, 103, 3, 111, 12, 20, 106, 0, 100, 1, 98, 2, 12, 3, 111, 84, 0, 100, 110, 101, 1, 114, 116, 2, 116, 3, 111, 84, 50, 107, 0, 114, 100, 101, 110, 3, 111, 112, 50, 0, 4, 1, 100, 2, 100, 121, 114, 3, 112, 0, 1, 106, 116, 115, 0, 1, 108, 2, 114, 0, 1, 108, 98, 2, 21, 0, 1, 108, 115, 2, 98, 114, 111, 107, 0, 1, 108, 115, 2, 115, 0, 1, 109, 2, 108, 108, 195, 184, 115, 12, 0, 1, 109, 2, 108, 116, 105, 100, 12, 0, 1, 109, 2, 116, 0, 1, 109, 115, 2, 17, 67, 21, 12, 0, 1, 112, 2, 115, 0, 1, 112, 115, 2, 100, 111, 109, 0, 1, 112, 115, 2, 107, 111, 110, 101, 0, 1, 112, 115, 2, 107, 118, 105, 110, 100, 101, 0, 1, 112, 115, 2, 109, 97, 110, 100, 0, 1, 112, 115, 2, 109, 195, 166, 110, 100, 0, 1, 114, 2, 98, 116, 0, 1, 114, 2, 100, 100, 12, 0, 1, 114, 2, 100, 102, 12, 0, 1, 114, 2, 100, 103, 12, 0, 1, 114, 2, 100, 104, 12, 0, 1, 114, 2, 100, 108, 195, 184, 115, 0, 1, 114, 2, 100, 109, 97, 110, 100, 0, 1, 114, 2, 100, 110, 12, 0, 1, 114, 2, 100, 115, 108, 0, 1, 114, 2, 100, 115, 110, 97, 114, 0, 1, 114, 2, 100, 115, 112, 0, 1, 114, 2, 100, 118, 105, 108, 100, 0, 1, 114, 2, 108, 97, 109, 0, 1, 114, 2, 109, 97, 116, 101, 114, 105, 97, 108, 0, 1, 114, 2, 115, 101, 106, 108, 0, 1, 114, 2, 116, 0, 1, 114, 18, 73, 2, 116, 0, 1, 114, 103, 2, 21, 0, 1, 114, 107, 115, 2, 112, 0, 1, 114, 116, 2, 100, 116, 0, 1, 114, 116, 115, 2, 100, 195, 184, 100, 0, 1, 114, 116, 115, 2, 102, 111, 114, 107, 111, 114, 116, 0, 1, 114, 116, 115, 2, 104, 97, 116, 0, 1, 114, 116, 115, 2, 109, 97, 110, 100, 0, 1, 114, 116, 115, 2, 109, 97, 110, 100, 0, 1, 115, 2, 32, 102, 195, 165, 0, 1, 115, 2, 32, 115, 110, 97, 114, 116, 0, 1, 115, 2, 100, 0, 1, 115, 2, 107, 97, 108, 100, 0, 1, 115, 2, 109, 195, 166, 110, 100, 0, 1, 115, 2, 116, 0, 1, 115, 2, 118, 101, 108, 0, 1, 115, 116, 108, 97, 0, 1, 116, 2, 108, 109, 111, 0, 1, 118, 2, 100, 116, 0, 2, 108, 116, 105, 0, 2, 110, 100, 0, 2, 116, 0, 8, 112, 0, 8, 115, 32, 114, 97, 118, 2, 32, 0, 114, 3, 112, 12, 0, 114, 1, 104, 3, 112, 12, 19, 0, 114, 100, 101, 1, 104, 3, 112, 12, 20, 106, 0, 114, 100, 101, 115, 116, 1, 104, 3, 112, 12, 34, 13, 87, 47, 0, 114, 101, 3, 112, 12, 106, 0, 100, 2, 115, 3, 112, 84, 0, 115, 101, 8, 112, 3, 112, 87, 36, 0, 7, 6, 195, 166, 0, 4, 1, 100, 101, 108, 166, 195, 107, 2, 103, 103, 101, 3, 6, 107, 0, 1, 102, 111, 114, 116, 0, 1, 116, 115, 101, 106, 97, 109, 2, 116, 0, 1, 118, 101, 103, 2, 114, 0, 1, 118, 115, 101, 98, 2, 114, 32, 0, 8, 100, 97, 102, 2, 115, 101, 0, 8, 108, 97, 112, 0, 8, 108, 101, 99, 114, 111, 112, 2, 110, 0, 8, 108, 105, 98, 117, 106, 0, 8, 108, 105, 108, 97, 103, 2, 101, 114, 0, 8, 108, 121, 112, 111, 114, 112, 2, 101, 114, 0, 8, 109, 97, 114, 97, 2, 101, 114, 0, 8, 109, 103, 121, 112, 0, 8, 109, 111, 100, 2, 110, 101, 0, 8, 110, 97, 97, 110, 97, 107, 2, 101, 114, 0, 8, 110, 97, 97, 110, 97, 107, 2, 101, 114, 0, 8, 110, 101, 104, 116, 97, 2, 101, 114, 0, 8, 112, 111, 114, 117, 101, 2, 101, 114, 0, 8, 114, 97, 122, 97, 110, 2, 101, 114, 0, 8, 114, 98, 101, 104, 2, 101, 114, 0, 8, 114, 103, 105, 109, 2, 110, 101, 0, 8, 114, 105, 115, 97, 110, 2, 101, 114, 0, 8, 114, 111, 103, 97, 104, 116, 121, 112, 2, 101, 114, 0, 8, 114, 111, 109, 2, 110, 101, 12, 0, 8, 114, 117, 107, 105, 112, 101, 2, 101, 114, 0, 8, 115, 105, 114, 97, 102, 2, 101, 114, 0, 8, 116, 110, 97, 114, 97, 107, 2, 110, 101, 0, 8, 116, 110, 111, 102, 2, 110, 101, 0, 4, 1, 102, 2, 114, 101, 3, 6, 107, 12, 0, 1, 104, 102, 97, 2, 110, 103, 105, 103, 0, 114, 114, 101, 1, 118, 115, 101, 100, 3, 6, 108, 34, 106, 0, 110, 1, 114, 102, 101, 114, 3, 6, 108, 66, 0, 8, 114, 116, 114, 111, 112, 2, 116, 3, 6, 109, 0, 8, 116, 115, 109, 111, 2, 110, 100, 3, 7, 107, 0, 114, 1, 10, 2, 28, 33, 3, 7, 107, 34, 0, 4, 3, 107, 0, 1, 114, 2, 17, 67, 18, 69, 0, 1, 114, 2, 18, 67, 0, 1, 114, 2, 115, 0, 1, 114, 100, 2, 98, 101, 114, 0, 1, 114, 100, 2, 110, 12, 0, 1, 114, 107, 2, 32, 0, 1, 114, 111, 102, 2, 100, 108, 101, 0, 1, 114, 112, 2, 103, 110, 0, 1, 114, 112, 2, 107, 0, 1, 114, 112, 2, 115, 116, 97, 0, 1, 114, 112, 2, 115, 116, 101, 114, 101, 0, 1, 114, 116, 0, 1, 114, 116, 2, 110, 12, 0, 2, 17, 67, 11, 17, 65, 0, 2, 108, 12, 0, 101, 1, 116, 2, 114, 0, 2, 103, 121, 112, 116, 3, 107, 6, 0, 4, 1, 112, 115, 2, 110, 101, 3, 107, 12, 0, 1, 114, 2, 17, 67, 17, 65, 0, 1, 114, 116, 2, 17, 67, 101, 12, 12, 0, 2, 17, 67, 17, 65, 0, 114, 103, 101, 1, 17, 67, 3, 107, 12, 34, 40, 13, 0, 114, 103, 101, 114, 1, 118, 3, 107, 12, 34, 40, 112, 0, 103, 101, 1, 116, 3, 107, 12, 57, 13, 0, 118, 108, 3, 107, 40, 55, 0, 114, 105, 110, 100, 101, 3, 107, 51, 50, 13, 0, 108, 100, 1, 107, 2, 114, 3, 107, 55, 0, 108, 100, 2, 114, 12, 3, 107, 55, 70, 0, 103, 1, 114, 116, 2, 104, 101, 100, 3, 107, 57, 0, 100, 105, 1, 114, 112, 2, 107, 97, 110, 116, 3, 107, 70, 37, 0, 103, 1, 114, 184, 195, 114, 3, 107, 79, 0, 100, 105, 1, 114, 112, 3, 107, 84, 0, 114, 114, 101, 3, 108, 34, 106, 0, 4, 1, 114, 3, 109, 0, 1, 114, 2, 17, 67, 11, 17, 65, 0, 1, 114, 2, 18, 67, 11, 0, 1, 114, 2, 18, 67, 116, 0, 1, 114, 2, 100, 101, 12, 12, 0, 1, 114, 2, 109, 0, 1, 114, 2, 116, 12, 0, 1, 114, 18, 73, 2, 17, 67, 0, 1, 114, 103, 2, 115, 0, 1, 114, 112, 2, 115, 116, 0, 1, 114, 112, 115, 2, 107, 107, 0, 1, 114, 114, 2, 17, 67, 101, 114, 12, 0, 1, 114, 116, 2, 17, 67, 0, 1, 114, 116, 2, 110, 103, 12, 0, 8, 114, 116, 2, 98, 101, 110, 12, 12, 0, 7, 6, 195, 169, 0, 3, 6, 36, 0, 7, 6, 195, 184, 0, 103, 1, 108, 3, 6, 112, 57, 0, 4, 1, 100, 114, 111, 110, 2, 115, 116, 3, 6, 116, 0, 1, 100, 121, 115, 2, 115, 116, 0, 1, 103, 108, 101, 118, 2, 114, 101, 110, 104, 101, 100, 0, 8, 102, 102, 117, 97, 104, 99, 2, 114, 0, 8, 106, 108, 105, 109, 0, 8, 109, 97, 2, 98, 101, 0, 8, 110, 97, 109, 2, 118, 114, 101, 0, 8, 118, 101, 110, 0, 4, 1, 107, 115, 98, 111, 2, 110, 3, 6, 116, 12, 0, 1, 109, 105, 2, 100, 101, 107, 111, 109, 0, 8, 110, 2, 100, 21, 0, 114, 101, 1, 105, 2, 102, 97, 108, 100, 101, 110, 100, 101, 3, 6, 116, 12, 112, 0, 4, 1, 103, 114, 117, 98, 2, 106, 115, 3, 6, 117, 0, 1, 108, 116, 115, 114, 101, 98, 111, 2, 106, 116, 110, 97, 110, 116, 0, 4, 1, 18, 74, 2, 103, 3, 112, 0, 1, 104, 2, 106, 0, 2, 106, 101, 0, 106, 43, 3, 112, 12, 57, 0, 4, 103, 1, 100, 2, 110, 3, 112, 57, 0, 103, 1, 103, 2, 108, 0, 103, 1, 112, 115, 2, 32, 0, 103, 1, 112, 115, 2, 101, 110, 0, 4, 3, 116, 0, 1, 18, 73, 2, 103, 0, 1, 108, 2, 115, 0, 1, 114, 2, 12, 0, 1, 114, 2, 18, 74, 101, 0, 1, 114, 2, 103, 101, 108, 115, 101, 0, 1, 114, 2, 103, 116, 101, 0, 1, 114, 2, 118, 101, 114, 0, 1, 114, 100, 2, 110, 0, 1, 114, 100, 2, 118, 101, 116, 0, 1, 114, 100, 101, 98, 2, 118, 0, 1, 114, 101, 98, 2, 118, 101, 0, 1, 114, 111, 102, 2, 103, 0, 1, 114, 112, 2, 118, 0, 1, 115, 2, 103, 0, 2, 100, 100, 0, 4, 1, 114, 2, 109, 101, 114, 3, 116, 12, 0, 2, 100, 101, 0, 95, 1, 115, 0, 103, 1, 114, 111, 102, 2, 32, 3, 116, 12, 19, 0, 114, 1, 112, 115, 2, 103, 3, 116, 12, 34, 0, 4, 114, 101, 3, 116, 12, 112, 0, 114, 101, 95, 0, 114, 1, 112, 115, 2, 103, 115, 3, 116, 34, 0, 114, 101, 2, 106, 115, 101, 3, 116, 34, 35, 0, 114, 101, 1, 115, 2, 100, 110, 105, 3, 116, 34, 107, 0, 4, 103, 1, 109, 115, 2, 32, 115, 105, 103, 3, 116, 57, 0, 103, 8, 2, 32, 0, 100, 116, 8, 110, 2, 32, 3, 116, 70, 0, 4, 103, 1, 108, 107, 2, 116, 3, 116, 79, 0, 103, 1, 110, 2, 116, 101, 114, 110, 0, 103, 103, 1, 108, 103, 0, 100, 1, 107, 3, 116, 84, 0, 4, 1, 17, 67, 2, 106, 12, 3, 117, 0, 1, 114, 2, 18, 74, 0, 1, 114, 2, 103, 0, 1, 114, 2, 118, 0, 1, 114, 101, 100, 110, 111, 98, 2, 118, 0, 1, 114, 114, 97, 110, 2, 118, 0, 2, 106, 110, 0, 8, 114, 2, 118, 101, 110, 0, 106, 101, 114, 3, 117, 57, 112, 0, 115, 1, 10, 2, 28, 33, 3, 6, 116, 12, 87, 0, 114, 1, 10, 2, 28, 33, 3, 7, 116, 34, 0, 7, 6, 39, 0, 101, 114, 2, 32, 14, 128, 128, 131, 3, 2, 112, 0, 101, 114, 110, 101, 2, 32, 14, 128, 128, 133, 3, 2, 112, 50, 13, 0, 101, 114, 110, 101, 115, 2, 32, 14, 128, 128, 134, 3, 2, 112, 50, 13, 87, 0, 101, 110, 2, 32, 14, 128, 128, 131, 3, 13, 50, 0, 101, 116, 2, 32, 14, 128, 128, 131, 3, 13, 84, 0, 115, 2, 32, 14, 128, 128, 130, 3, 87, 0, 101, 114, 101, 2, 32, 14, 128, 128, 132, 3, 112, 34, 112, 0, 7, 6, 97, 0, 103, 2, 110, 111, 115, 3, 2, 35, 79, 0, 4, 117, 2, 32, 112, 97, 105, 114, 3, 2, 39, 0, 117, 2, 32, 114, 101, 118, 111, 105, 114, 0, 1, 108, 2, 107, 114, 3, 2, 108, 0, 2, 109, 112, 3, 2, 110, 0, 102, 8, 114, 101, 100, 2, 32, 3, 4, 108, 0, 4, 1, 100, 114, 101, 116, 115, 109, 97, 2, 109, 3, 6, 35, 0, 1, 102, 108, 105, 116, 2, 110, 103, 101, 0, 1, 103, 110, 101, 2, 110, 103, 0, 1, 103, 110, 101, 2, 110, 103, 0, 1, 114, 107, 115, 110, 101, 112, 112, 97, 114, 2, 108, 100, 101, 0, 1, 116, 115, 101, 103, 2, 112, 111, 0, 8, 108, 97, 103, 2, 107, 115, 101, 0, 8, 108, 111, 112, 2, 107, 0, 8, 112, 109, 111, 107, 2, 107, 116, 0, 8, 114, 97, 116, 97, 107, 2, 107, 116, 0, 8, 114, 116, 110, 111, 107, 2, 107, 116, 0, 8, 114, 116, 115, 98, 97, 2, 107, 116, 0, 8, 114, 116, 115, 107, 101, 2, 107, 116, 0, 8, 115, 107, 101, 2, 107, 116, 0, 8, 115, 111, 107, 2, 107, 0, 8, 115, 115, 97, 109, 2, 107, 114, 101, 0, 8, 116, 101, 2, 112, 101, 0, 8, 116, 110, 105, 2, 107, 116, 0, 8, 116, 110, 111, 107, 2, 107, 116, 0, 8, 116, 112, 97, 107, 2, 106, 110, 0, 109, 1, 114, 103, 10, 2, 109, 28, 33, 12, 0, 1, 108, 115, 105, 2, 109, 3, 6, 35, 12, 0, 117, 8, 115, 115, 105, 98, 3, 6, 35, 12, 58, 0, 117, 114, 101, 114, 8, 115, 111, 110, 105, 100, 3, 6, 35, 40, 34, 112, 0, 117, 114, 8, 115, 111, 110, 105, 100, 3, 6, 35, 40, 112, 0, 110, 103, 101, 108, 111, 1, 108, 101, 104, 99, 105, 109, 3, 6, 35, 50, 73, 106, 55, 39, 0, 105, 1, 116, 101, 100, 2, 108, 3, 6, 35, 57, 0, 117, 1, 110, 111, 114, 116, 115, 97, 2, 116, 3, 6, 35, 58, 0, 109, 1, 114, 103, 10, 2, 28, 33, 12, 3, 6, 35, 63, 0, 103, 116, 105, 103, 1, 10, 2, 28, 33, 12, 3, 6, 35, 79, 47, 37, 0, 117, 120, 1, 103, 3, 6, 39, 0, 105, 115, 101, 3, 6, 107, 12, 87, 13, 0, 105, 1, 116, 110, 111, 99, 2, 110, 3, 6, 107, 57, 0, 105, 99, 104, 101, 1, 114, 102, 3, 6, 107, 89, 0, 4, 1, 98, 97, 108, 97, 2, 109, 3, 6, 108, 0, 1, 98, 101, 108, 97, 116, 2, 110, 0, 1, 98, 101, 115, 2, 115, 116, 105, 97, 110, 0, 1, 98, 109, 117, 108, 2, 103, 111, 0, 1, 99, 97, 100, 2, 112, 111, 0, 1, 99, 105, 112, 2, 115, 115, 111, 0, 1, 100, 97, 107, 2, 118, 101, 114, 0, 1, 100, 101, 112, 112, 117, 115, 2, 115, 0, 1, 100, 114, 101, 100, 110, 117, 2, 110, 105, 103, 0, 1, 100, 114, 111, 118, 104, 2, 110, 0, 1, 100, 117, 97, 108, 2, 110, 117, 109, 0, 1, 102, 110, 105, 2, 109, 0, 1, 103, 114, 111, 2, 115, 0, 1, 104, 97, 98, 2, 109, 97, 0, 1, 106, 121, 112, 2, 109, 97, 0, 1, 107, 115, 108, 105, 116, 2, 100, 101, 0, 1, 108, 97, 2, 115, 107, 0, 1, 108, 97, 112, 2, 118, 101, 114, 12, 0, 1, 108, 105, 112, 2, 116, 117, 115, 0, 1, 108, 115, 111, 103, 117, 106, 2, 118, 0, 1, 109, 97, 108, 97, 115, 2, 110, 100, 101, 114, 0, 1, 109, 101, 116, 97, 117, 103, 2, 108, 0, 1, 109, 105, 114, 103, 2, 115, 115, 101, 0, 1, 109, 109, 111, 107, 2, 110, 100, 0, 1, 110, 97, 98, 2, 110, 0, 1, 110, 105, 100, 110, 97, 107, 115, 2, 118, 0, 1, 110, 105, 104, 2, 110, 0, 1, 112, 111, 116, 2, 115, 0, 1, 114, 101, 118, 111, 2, 108, 116, 0, 1, 115, 101, 109, 114, 97, 112, 2, 110, 0, 1, 115, 108, 97, 98, 2, 109, 105, 0, 1, 116, 111, 103, 111, 98, 0, 1, 116, 115, 97, 107, 2, 110, 106, 101, 0, 1, 116, 115, 97, 116, 101, 109, 2, 115, 101, 0, 1, 116, 115, 107, 101, 2, 115, 0, 1, 116, 115, 110, 97, 114, 111, 102, 2, 108, 116, 0, 1, 116, 115, 112, 111, 2, 110, 100, 101, 108, 115, 101, 0, 1, 116, 115, 114, 101, 2, 116, 110, 105, 110, 103, 0, 1, 116, 117, 112, 115, 105, 100, 2, 116, 115, 0, 1, 118, 2, 110, 108, 105, 103, 0, 1, 118, 97, 104, 2, 110, 97, 0, 1, 118, 97, 104, 2, 110, 110, 97, 0, 1, 122, 121, 98, 2, 110, 115, 32, 0, 2, 115, 109, 101, 0, 8, 100, 100, 110, 101, 2, 32, 0, 8, 100, 101, 109, 2, 108, 106, 101, 0, 8, 101, 116, 2, 116, 101, 114, 0, 8, 103, 97, 112, 111, 114, 112, 2, 110, 100, 0, 8, 105, 100, 110, 105, 2, 110, 97, 0, 8, 105, 115, 117, 116, 110, 101, 2, 115, 0, 8, 107, 97, 107, 2, 111, 0, 8, 107, 97, 109, 2, 98, 0, 8, 107, 105, 104, 99, 2, 110, 101, 0, 8, 107, 105, 116, 97, 118, 2, 110, 0, 8, 107, 108, 97, 2, 108, 105, 0, 8, 107, 110, 111, 107, 2, 118, 0, 8, 108, 107, 101, 114, 2, 109, 101, 0, 8, 108, 107, 110, 101, 2, 118, 101, 12, 0, 8, 108, 115, 105, 116, 97, 114, 98, 2, 118, 0, 8, 109, 105, 114, 112, 2, 108, 0, 8, 110, 97, 99, 2, 100, 105, 101, 114, 0, 8, 110, 105, 109, 111, 100, 2, 110, 0, 8, 110, 121, 100, 2, 109, 111, 0, 8, 111, 2, 115, 101, 0, 8, 112, 97, 2, 99, 104, 0, 8, 112, 109, 105, 104, 99, 2, 110, 0, 8, 115, 97, 102, 2, 110, 0, 8, 115, 107, 101, 2, 109, 12, 0, 8, 116, 97, 98, 2, 108, 106, 101, 0, 8, 116, 101, 100, 2, 108, 106, 101, 0, 8, 116, 107, 111, 2, 118, 0, 8, 118, 97, 114, 97, 107, 2, 110, 101, 0, 100, 1, 107, 115, 117, 98, 2, 115, 0, 100, 1, 108, 97, 112, 2, 115, 0, 100, 8, 108, 106, 101, 115, 2, 115, 0, 103, 1, 115, 101, 107, 107, 97, 110, 115, 2, 108, 105, 103, 0, 4, 1, 103, 101, 114, 111, 2, 110, 111, 3, 6, 108, 12, 0, 1, 108, 105, 109, 2, 110, 111, 0, 1, 116, 114, 97, 107, 2, 103, 111, 0, 100, 101, 1, 10, 2, 28, 33, 3, 6, 108, 12, 84, 13, 0, 100, 101, 1, 10, 2, 114, 28, 33, 3, 6, 108, 12, 84, 112, 0, 116, 1, 10, 2, 28, 33, 3, 6, 108, 47, 0, 103, 110, 101, 1, 112, 3, 6, 108, 50, 57, 13, 0, 110, 100, 101, 1, 98, 97, 114, 116, 110, 111, 107, 3, 6, 108, 50, 70, 106, 0, 110, 115, 1, 10, 2, 28, 33, 3, 6, 108, 50, 87, 0, 4, 98, 1, 10, 2, 101, 108, 28, 33, 3, 6, 108, 69, 0, 98, 1, 10, 2, 108, 101, 28, 33, 0, 4, 100, 1, 110, 114, 111, 116, 2, 111, 3, 6, 108, 70, 0, 100, 1, 118, 101, 110, 2, 97, 0, 118, 101, 114, 97, 108, 1, 110, 97, 99, 3, 6, 108, 82, 106, 34, 106, 55, 0, 118, 101, 114, 8, 108, 107, 110, 101, 3, 6, 108, 82, 112, 0, 4, 1, 98, 110, 101, 98, 165, 195, 2, 114, 105, 110, 103, 3, 6, 110, 0, 1, 102, 97, 115, 2, 114, 105, 0, 1, 102, 114, 101, 2, 114, 0, 1, 112, 115, 101, 98, 2, 114, 105, 110, 103, 0, 1, 114, 98, 105, 118, 2, 116, 111, 0, 1, 114, 101, 109, 111, 111, 98, 2, 110, 103, 0, 1, 114, 105, 103, 2, 102, 0, 1, 114, 105, 109, 2, 107, 0, 1, 114, 108, 165, 195, 107, 2, 98, 105, 0, 1, 114, 116, 115, 97, 112, 2, 109, 105, 0, 1, 118, 97, 104, 2, 114, 116, 105, 0, 1, 118, 97, 107, 115, 2, 110, 107, 0, 1, 118, 114, 111, 102, 2, 114, 105, 110, 103, 0, 8, 98, 101, 108, 108, 101, 104, 2, 114, 100, 0, 8, 98, 109, 111, 108, 2, 114, 100, 0, 8, 98, 111, 103, 110, 111, 108, 2, 114, 100, 0, 8, 103, 108, 117, 98, 2, 114, 0, 8, 104, 97, 115, 2, 114, 97, 0, 8, 105, 108, 108, 105, 109, 2, 114, 0, 8, 105, 108, 108, 105, 114, 116, 2, 114, 0, 8, 108, 97, 2, 114, 109, 0, 8, 108, 97, 109, 2, 114, 105, 97, 0, 8, 108, 117, 111, 102, 2, 114, 100, 0, 8, 108, 117, 111, 112, 2, 114, 100, 0, 8, 110, 111, 109, 2, 114, 107, 0, 8, 111, 105, 100, 97, 114, 2, 107, 116, 105, 0, 8, 114, 97, 2, 98, 101, 114, 0, 8, 114, 97, 98, 2, 107, 0, 8, 114, 100, 97, 109, 2, 115, 0, 8, 114, 114, 117, 104, 0, 8, 115, 97, 104, 2, 114, 100, 0, 8, 115, 101, 114, 112, 109, 105, 2, 114, 105, 111, 0, 8, 115, 110, 97, 109, 2, 114, 100, 0, 8, 116, 115, 97, 98, 2, 114, 100, 0, 110, 1, 114, 10, 2, 110, 101, 28, 34, 12, 0, 8, 111, 108, 107, 2, 107, 12, 3, 6, 110, 12, 0, 100, 101, 1, 114, 10, 2, 28, 33, 3, 6, 110, 12, 84, 13, 0, 100, 101, 1, 114, 10, 2, 114, 28, 33, 3, 6, 110, 12, 84, 112, 0, 116, 1, 114, 10, 2, 28, 33, 3, 6, 110, 47, 0, 110, 1, 114, 10, 2, 28, 34, 12, 3, 6, 110, 50, 0, 110, 116, 1, 114, 10, 2, 28, 33, 3, 6, 110, 50, 47, 0, 110, 115, 1, 114, 10, 2, 28, 33, 3, 6, 110, 50, 87, 0, 4, 108, 1, 114, 2, 28, 33, 12, 12, 3, 6, 110, 55, 0, 108, 1, 114, 10, 2, 101, 32, 28, 33, 12, 0, 118, 1, 104, 110, 101, 98, 184, 195, 107, 2, 110, 3, 6, 110, 58, 0, 110, 116, 1, 114, 117, 97, 116, 115, 101, 114, 3, 6, 110, 66, 0, 4, 110, 99, 101, 1, 10, 2, 28, 33, 3, 6, 110, 66, 87, 13, 0, 110, 99, 104, 101, 1, 10, 2, 28, 33, 0, 110, 99, 101, 1, 10, 2, 114, 28, 33, 3, 6, 110, 66, 87, 112, 0, 98, 1, 114, 10, 2, 101, 108, 28, 33, 3, 6, 110, 69, 0, 114, 98, 101, 114, 8, 98, 97, 114, 3, 6, 110, 69, 112, 0, 100, 111, 1, 114, 111, 108, 111, 99, 3, 6, 110, 70, 39, 0, 4, 8, 105, 107, 121, 115, 112, 2, 116, 3, 7, 108, 0, 116, 1, 10, 2, 116, 28, 33, 0, 110, 1, 10, 2, 28, 34, 12, 3, 7, 108, 50, 0, 110, 116, 1, 10, 2, 28, 33, 3, 7, 108, 50, 47, 0, 4, 108, 1, 10, 2, 28, 33, 12, 3, 7, 108, 55, 0, 108, 1, 10, 2, 101, 32, 28, 33, 12, 0, 1, 108, 114, 111, 102, 2, 103, 116, 32, 3, 7, 110, 0, 114, 1, 10, 2, 28, 33, 3, 7, 110, 34, 0, 110, 99, 101, 1, 121, 111, 118, 2, 28, 33, 3, 7, 110, 66, 87, 0, 102, 1, 114, 111, 118, 104, 3, 8, 4, 108, 0, 4, 8, 110, 97, 98, 101, 107, 105, 3, 8, 108, 0, 8, 110, 97, 100, 110, 97, 98, 0, 8, 110, 97, 103, 114, 111, 109, 97, 116, 97, 102, 0, 8, 110, 97, 107, 114, 97, 0, 8, 110, 97, 117, 104, 105, 114, 97, 109, 0, 8, 110, 97, 118, 114, 105, 110, 0, 8, 110, 97, 119, 115, 116, 111, 17, 66, 0, 8, 110, 97, 121, 117, 103, 0, 8, 110, 101, 114, 97, 0, 8, 110, 101, 122, 105, 97, 109, 0, 8, 110, 105, 103, 110, 97, 0, 8, 110, 105, 108, 117, 107, 115, 97, 109, 0, 8, 110, 105, 110, 105, 109, 101, 102, 0, 8, 110, 105, 114, 97, 107, 111, 0, 8, 110, 105, 114, 97, 109, 0, 8, 110, 105, 114, 97, 115, 116, 0, 8, 110, 105, 114, 97, 122, 0, 8, 110, 105, 114, 101, 108, 108, 97, 98, 0, 8, 110, 105, 115, 116, 101, 114, 0, 8, 110, 105, 116, 110, 101, 103, 114, 97, 0, 8, 110, 105, 116, 114, 101, 99, 110, 111, 107, 0, 8, 110, 105, 116, 115, 166, 195, 108, 97, 112, 0, 8, 110, 105, 118, 111, 103, 101, 99, 114, 101, 104, 0, 8, 110, 110, 97, 105, 115, 111, 104, 0, 8, 110, 110, 111, 100, 97, 109, 0, 8, 110, 110, 111, 100, 97, 109, 105, 114, 112, 0, 8, 110, 111, 109, 111, 112, 120, 111, 99, 0, 8, 110, 111, 114, 111, 107, 0, 108, 1, 110, 97, 2, 102, 97, 98, 101, 116, 3, 8, 108, 55, 0, 1, 102, 101, 98, 2, 114, 105, 110, 103, 3, 16, 110, 0, 118, 101, 8, 100, 3, 21, 0, 4, 1, 104, 2, 99, 105, 101, 110, 100, 97, 3, 21, 101, 115, 0, 108, 101, 106, 97, 110, 100, 114, 111, 0, 4, 1, 17, 67, 2, 18, 71, 11, 3, 35, 0, 1, 17, 67, 2, 18, 75, 0, 1, 17, 67, 2, 18, 75, 101, 0, 1, 17, 67, 2, 99, 107, 0, 1, 17, 67, 2, 109, 12, 0, 1, 17, 67, 2, 110, 18, 75, 18, 69, 12, 12, 0, 1, 17, 67, 2, 114, 18, 76, 0, 1, 17, 67, 2, 114, 114, 0, 1, 17, 67, 2, 120, 12, 0, 1, 18, 73, 2, 109, 0, 1, 18, 74, 2, 106, 0, 1, 18, 75, 2, 112, 12, 0, 1, 98, 2, 106, 101, 114, 0, 1, 100, 2, 102, 110, 0, 1, 100, 2, 103, 21, 12, 0, 1, 100, 2, 103, 115, 21, 0, 1, 102, 2, 118, 111, 12, 0, 1, 104, 2, 18, 66, 0, 1, 104, 2, 106, 0, 1, 104, 2, 106, 12, 12, 0, 1, 104, 2, 112, 0, 1, 104, 99, 2, 110, 0, 1, 105, 108, 108, 105, 119, 2, 109, 0, 1, 106, 2, 112, 112, 0, 1, 106, 2, 112, 115, 0, 1, 107, 2, 106, 0, 1, 107, 2, 109, 0, 1, 107, 2, 112, 115, 0, 1, 107, 115, 2, 102, 12, 0, 1, 108, 2, 98, 32, 12, 0, 1, 108, 2, 98, 98, 0, 1, 108, 2, 112, 12, 0, 1, 108, 107, 2, 18, 71, 0, 1, 108, 115, 2, 18, 71, 0, 1, 108, 115, 2, 110, 103, 101, 12, 0, 1, 108, 115, 118, 105, 108, 2, 110, 103, 12, 0, 1, 109, 105, 108, 107, 2, 107, 115, 0, 1, 112, 2, 112, 114, 105, 12, 0, 1, 112, 115, 2, 110, 107, 117, 108, 101, 114, 0, 1, 114, 2, 18, 73, 0, 1, 114, 2, 115, 101, 0, 1, 114, 2, 116, 0, 1, 114, 2, 118, 0, 1, 114, 107, 115, 2, 108, 0, 1, 115, 2, 110, 103, 12, 0, 1, 115, 2, 120, 0, 1, 116, 2, 98, 116, 0, 1, 116, 2, 112, 0, 1, 118, 2, 99, 99, 0, 1, 118, 2, 102, 12, 12, 0, 1, 118, 2, 106, 0, 2, 18, 66, 12, 12, 0, 2, 18, 66, 101, 12, 12, 0, 2, 98, 110, 111, 114, 109, 0, 2, 102, 17, 67, 12, 0, 2, 109, 101, 114, 105, 107, 97, 110, 0, 2, 109, 109, 12, 0, 2, 109, 115, 0, 2, 112, 111, 116, 101, 0, 2, 112, 112, 97, 114, 0, 2, 112, 112, 101, 108, 115, 105, 110, 0, 2, 112, 112, 101, 116, 105, 116, 0, 2, 114, 114, 101, 115, 116, 0, 8, 2, 108, 100, 114, 105, 103, 0, 8, 2, 110, 100, 101, 114, 0, 8, 100, 2, 109, 32, 0, 8, 100, 2, 109, 109, 0, 114, 101, 8, 98, 2, 116, 3, 35, 34, 6, 109, 0, 114, 97, 103, 100, 1, 109, 115, 3, 35, 34, 6, 110, 58, 70, 0, 4, 118, 1, 103, 2, 116, 121, 118, 3, 35, 40, 0, 118, 1, 104, 32, 101, 100, 184, 195, 0, 118, 101, 114, 116, 1, 106, 3, 35, 40, 34, 47, 0, 116, 116, 101, 110, 116, 105, 111, 110, 3, 35, 47, 6, 107, 50, 89, 13, 50, 0, 112, 101, 103, 195, 184, 106, 101, 1, 112, 3, 35, 48, 13, 79, 6, 112, 57, 106, 0, 103, 1, 18, 74, 2, 116, 3, 35, 49, 0, 99, 99, 97, 114, 97, 116, 1, 98, 3, 35, 49, 35, 34, 6, 35, 0, 110, 100, 97, 1, 114, 2, 108, 3, 35, 50, 70, 20, 113, 0, 4, 110, 103, 1, 109, 2, 111, 3, 35, 50, 79, 0, 110, 103, 2, 117, 108, 12, 12, 0, 110, 103, 8, 2, 111, 108, 0, 4, 105, 1, 99, 2, 114, 111, 3, 35, 57, 0, 105, 8, 110, 105, 115, 0, 121, 1, 98, 0, 121, 1, 109, 2, 97, 0, 121, 1, 117, 103, 0, 105, 1, 110, 2, 114, 111, 98, 105, 3, 35, 57, 6, 0, 105, 114, 111, 8, 107, 3, 35, 57, 34, 39, 0, 121, 114, 101, 117, 116, 104, 1, 98, 3, 35, 57, 51, 6, 112, 57, 47, 0, 121, 97, 116, 111, 108, 108, 97, 104, 3, 35, 57, 108, 47, 6, 112, 55, 108, 0, 4, 117, 2, 12, 12, 3, 35, 58, 0, 119, 2, 25, 0, 118, 102, 108, 97, 98, 1, 103, 3, 35, 58, 81, 55, 108, 69, 0, 4, 110, 1, 114, 98, 2, 99, 104, 101, 3, 35, 66, 0, 110, 2, 99, 105, 101, 110, 0, 110, 103, 2, 114, 101, 0, 110, 103, 8, 2, 101, 17, 67, 0, 98, 97, 114, 101, 116, 1, 107, 3, 35, 69, 35, 34, 6, 107, 0, 98, 101, 114, 110, 97, 107, 1, 116, 3, 35, 69, 112, 50, 6, 35, 49, 0, 103, 103, 105, 111, 114, 101, 1, 109, 3, 35, 73, 6, 39, 12, 53, 36, 0, 103, 1, 109, 2, 97, 115, 105, 3, 35, 79, 0, 103, 97, 115, 97, 107, 105, 1, 110, 3, 35, 79, 108, 87, 6, 35, 49, 37, 0, 102, 116, 101, 114, 115, 104, 97, 118, 101, 3, 35, 81, 47, 112, 89, 107, 57, 82, 0, 122, 122, 105, 1, 114, 3, 35, 89, 57, 0, 99, 104, 1, 98, 3, 35, 99, 0, 104, 97, 8, 2, 32, 3, 35, 105, 6, 35, 0, 105, 1, 116, 110, 117, 111, 109, 2, 110, 3, 36, 0, 4, 1, 102, 114, 101, 116, 110, 105, 2, 99, 101, 3, 36, 37, 0, 1, 109, 101, 99, 97, 112, 2, 107, 0, 98, 121, 1, 98, 2, 12, 3, 36, 37, 69, 37, 0, 99, 101, 1, 112, 3, 36, 37, 87, 0, 4, 117, 1, 104, 99, 2, 102, 3, 39, 0, 117, 1, 104, 99, 2, 118, 105, 110, 0, 117, 1, 115, 2, 116, 101, 114, 110, 101, 0, 117, 1, 116, 115, 101, 114, 2, 114, 0, 117, 2, 32, 110, 97, 116, 117, 114, 101, 108, 0, 117, 120, 8, 102, 0, 117, 103, 117, 105, 110, 1, 103, 3, 39, 79, 6, 108, 66, 0, 4, 1, 114, 2, 99, 101, 114, 98, 97, 110, 101, 3, 107, 0, 1, 114, 2, 99, 101, 114, 98, 105, 108, 0, 1, 114, 2, 99, 101, 114, 99, 121, 107, 0, 1, 114, 2, 99, 101, 114, 107, 195, 184, 114, 0, 1, 114, 2, 99, 101, 114, 118, 111, 103, 110, 0, 101, 2, 114, 111, 0, 105, 2, 109, 97, 98, 101, 108, 0, 105, 114, 101, 1, 108, 99, 3, 107, 12, 34, 0, 105, 114, 99, 111, 110, 100, 105, 116, 105, 111, 110, 3, 107, 12, 34, 49, 112, 50, 70, 37, 12, 89, 13, 50, 0, 105, 114, 3, 107, 34, 0, 105, 100, 115, 3, 107, 37, 70, 87, 0, 4, 1, 104, 2, 115, 116, 105, 110, 103, 3, 107, 57, 0, 1, 108, 2, 115, 101, 114, 101, 110, 0, 1, 108, 2, 115, 101, 114, 110, 101, 115, 0, 1, 108, 2, 115, 101, 114, 112, 114, 0, 1, 108, 2, 115, 101, 114, 115, 116, 0, 1, 108, 32, 110, 101, 2, 115, 101, 114, 0, 1, 109, 107, 111, 111, 98, 2, 107, 101, 114, 0, 1, 114, 2, 116, 105, 110, 103, 0, 121, 1, 100, 0, 121, 2, 25, 0, 121, 8, 98, 2, 32, 0, 116, 101, 1, 109, 121, 97, 108, 112, 3, 107, 57, 47, 0, 116, 105, 101, 1, 107, 3, 107, 57, 47, 37, 0, 98, 101, 8, 98, 2, 32, 3, 107, 57, 48, 0, 99, 111, 8, 119, 3, 107, 57, 49, 39, 58, 0, 99, 111, 110, 1, 98, 3, 107, 57, 49, 112, 50, 0, 121, 110, 101, 1, 112, 3, 107, 57, 50, 0, 4, 105, 108, 1, 116, 107, 99, 111, 99, 3, 107, 57, 55, 0, 108, 101, 1, 32, 114, 101, 103, 110, 105, 103, 0, 109, 121, 8, 3, 107, 57, 63, 37, 0, 103, 101, 110, 99, 121, 3, 107, 57, 73, 13, 50, 87, 37, 0, 103, 97, 115, 8, 118, 3, 107, 57, 79, 13, 87, 0, 107, 101, 115, 1, 108, 102, 110, 114, 111, 99, 3, 107, 57, 79, 87, 0, 118, 101, 114, 121, 3, 107, 57, 82, 34, 37, 0, 121, 101, 115, 1, 17, 67, 3, 107, 57, 87, 0, 116, 105, 111, 110, 1, 116, 115, 2, 99, 97, 114, 3, 107, 57, 89, 106, 50, 0, 104, 97, 98, 8, 3, 107, 57, 105, 108, 69, 0, 112, 101, 1, 114, 103, 3, 107, 69, 0, 4, 3, 108, 0, 1, 17, 67, 2, 17, 67, 11, 0, 1, 17, 67, 2, 18, 75, 18, 69, 0, 1, 17, 67, 2, 109, 18, 69, 12, 0, 1, 17, 67, 2, 109, 105, 0, 1, 17, 67, 2, 109, 195, 166, 12, 0, 1, 18, 67, 2, 18, 67, 101, 0, 1, 18, 67, 2, 18, 67, 108, 101, 0, 1, 18, 71, 2, 110, 0, 1, 18, 73, 2, 18, 75, 18, 69, 0, 1, 18, 73, 2, 118, 0, 1, 18, 74, 2, 108, 100, 0, 1, 18, 75, 2, 109, 101, 12, 0, 1, 18, 75, 2, 112, 18, 69, 12, 0, 1, 21, 2, 107, 114, 18, 69, 12, 0, 1, 98, 2, 103, 97, 103, 101, 12, 12, 0, 1, 98, 2, 118, 105, 97, 110, 12, 0, 1, 98, 32, 103, 105, 98, 2, 110, 103, 0, 1, 98, 114, 105, 97, 2, 103, 0, 1, 99, 2, 109, 112, 12, 0, 1, 100, 2, 109, 18, 76, 12, 0, 1, 100, 100, 2, 103, 12, 0, 1, 100, 108, 2, 107, 0, 1, 100, 108, 101, 109, 109, 97, 103, 2, 103, 115, 0, 1, 101, 0, 1, 101, 2, 114, 18, 69, 12, 0, 1, 101, 114, 2, 103, 12, 0, 1, 102, 2, 18, 67, 114, 18, 69, 0, 1, 102, 2, 18, 74, 0, 1, 102, 2, 99, 18, 76, 0, 1, 102, 2, 110, 107, 108, 117, 98, 12, 0, 1, 102, 111, 115, 0, 1, 103, 2, 110, 103, 115, 116, 101, 114, 12, 0, 1, 103, 105, 108, 0, 1, 104, 2, 99, 107, 12, 0, 1, 104, 2, 109, 98, 117, 114, 103, 101, 114, 0, 1, 104, 2, 110, 0, 1, 104, 2, 110, 107, 97, 116, 0, 1, 104, 2, 110, 107, 195, 184, 110, 12, 12, 0, 1, 104, 2, 112, 112, 17, 65, 0, 1, 104, 101, 98, 2, 103, 0, 1, 104, 115, 2, 109, 18, 76, 0, 1, 104, 116, 2, 110, 107, 115, 0, 1, 105, 100, 2, 18, 66, 12, 0, 1, 106, 2, 109, 101, 110, 0, 1, 107, 2, 12, 0, 1, 107, 2, 112, 18, 76, 12, 0, 1, 107, 2, 112, 114, 101, 12, 0, 1, 107, 2, 112, 114, 105, 110, 103, 0, 1, 107, 115, 2, 18, 71, 12, 0, 1, 108, 2, 98, 101, 0, 1, 108, 2, 109, 17, 65, 12, 0, 1, 108, 2, 110, 0, 1, 108, 2, 118, 101, 110, 100, 101, 108, 0, 1, 108, 97, 109, 2, 18, 66, 97, 0, 1, 108, 98, 2, 99, 107, 0, 1, 108, 98, 2, 100, 0, 1, 108, 102, 2, 98, 32, 12, 0, 1, 108, 111, 99, 0, 1, 108, 112, 2, 99, 101, 0, 1, 108, 112, 2, 107, 97, 0, 1, 108, 115, 2, 110, 103, 12, 0, 1, 108, 115, 105, 2, 109, 105, 0, 1, 109, 2, 106, 111, 12, 0, 1, 109, 2, 107, 97, 0, 1, 109, 105, 108, 107, 0, 1, 109, 105, 114, 112, 0, 1, 109, 114, 105, 102, 0, 1, 109, 114, 105, 102, 2, 12, 0, 1, 109, 115, 2, 99, 107, 0, 1, 110, 2, 112, 97, 108, 109, 0, 1, 110, 97, 112, 2, 109, 97, 0, 1, 110, 103, 2, 118, 110, 101, 0, 1, 110, 105, 103, 97, 118, 0, 1, 110, 115, 2, 99, 107, 0, 1, 112, 2, 103, 18, 76, 12, 0, 1, 112, 2, 103, 110, 12, 0, 1, 112, 2, 112, 105, 0, 1, 112, 2, 118, 12, 0, 1, 114, 2, 110, 99, 104, 0, 1, 114, 2, 110, 115, 105, 103, 116, 0, 1, 114, 99, 2, 99, 107, 12, 0, 1, 114, 101, 116, 102, 101, 2, 98, 0, 1, 114, 111, 102, 2, 110, 0, 1, 115, 2, 98, 98, 97, 116, 0, 1, 115, 2, 103, 12, 0, 1, 115, 2, 103, 115, 97, 110, 12, 12, 0, 1, 115, 2, 103, 115, 98, 101, 104, 97, 110, 100, 108, 12, 12, 0, 1, 115, 2, 103, 115, 109, 97, 12, 12, 0, 1, 115, 2, 103, 115, 111, 109, 12, 12, 0, 1, 115, 2, 109, 97, 110, 116, 0, 1, 115, 107, 101, 10, 2, 109, 0, 1, 116, 2, 112, 18, 76, 0, 1, 116, 2, 112, 105, 0, 1, 116, 115, 2, 99, 99, 97, 116, 111, 0, 1, 116, 115, 2, 102, 102, 97, 103, 101, 0, 1, 116, 115, 2, 107, 97, 0, 1, 116, 115, 101, 116, 2, 109, 0, 1, 118, 2, 110, 100, 114, 195, 184, 114, 0, 1, 118, 108, 101, 115, 2, 110, 103, 105, 118, 0, 1, 118, 115, 2, 98, 0, 1, 120, 97, 116, 0, 2, 18, 66, 18, 69, 12, 12, 0, 2, 100, 118, 97, 114, 0, 2, 102, 102, 117, 116, 97, 103, 101, 0, 2, 102, 102, 195, 166, 114, 101, 12, 0, 2, 102, 115, 116, 101, 100, 12, 0, 2, 103, 103, 114, 101, 115, 12, 12, 0, 2, 107, 0, 2, 107, 97, 12, 12, 0, 2, 107, 97, 100, 101, 109, 12, 12, 0, 2, 107, 118, 17, 65, 12, 0, 2, 108, 100, 101, 0, 2, 108, 116, 0, 2, 110, 103, 97, 118, 12, 12, 0, 2, 110, 103, 195, 165, 12, 12, 0, 2, 110, 104, 111, 12, 12, 0, 2, 110, 107, 108, 97, 103, 12, 12, 0, 2, 110, 108, 195, 166, 103, 12, 0, 2, 110, 115, 116, 0, 2, 110, 115, 116, 114, 101, 110, 103, 12, 0, 2, 110, 116, 97, 108, 12, 0, 2, 110, 118, 101, 110, 100, 12, 0, 2, 116, 116, 97, 99, 104, 12, 0, 8, 2, 18, 66, 18, 69, 12, 12, 0, 8, 2, 102, 102, 101, 107, 116, 12, 0, 8, 2, 110, 100, 101, 110, 0, 8, 2, 110, 100, 101, 116, 0, 100, 1, 108, 106, 101, 115, 2, 115, 0, 103, 1, 100, 101, 114, 102, 2, 115, 0, 103, 1, 100, 110, 97, 109, 2, 115, 0, 103, 1, 100, 110, 184, 195, 115, 2, 115, 0, 103, 1, 100, 114, 101, 118, 104, 0, 103, 1, 100, 114, 184, 195, 108, 2, 115, 0, 103, 1, 100, 115, 110, 111, 2, 115, 0, 103, 1, 100, 115, 114, 105, 116, 2, 115, 0, 103, 1, 100, 115, 114, 111, 116, 2, 115, 0, 103, 2, 103, 114, 101, 103, 97, 116, 0, 104, 1, 104, 115, 0, 114, 1, 107, 2, 108, 101, 110, 101, 0, 114, 1, 107, 21, 2, 108, 0, 114, 1, 108, 110, 101, 118, 111, 100, 2, 115, 0, 118, 1, 104, 2, 32, 0, 4, 1, 107, 2, 106, 97, 107, 3, 108, 6, 0, 1, 116, 97, 107, 2, 112, 117, 108, 116, 0, 105, 1, 107, 2, 110, 3, 108, 6, 37, 12, 0, 4, 1, 17, 67, 2, 17, 67, 101, 3, 108, 12, 0, 1, 17, 67, 2, 110, 101, 0, 1, 18, 73, 2, 98, 18, 76, 0, 1, 18, 73, 2, 100, 0, 1, 18, 74, 2, 18, 67, 101, 0, 1, 18, 74, 2, 108, 0, 1, 103, 2, 118, 0, 1, 106, 116, 2, 32, 0, 1, 108, 115, 2, 118, 0, 1, 112, 115, 2, 109, 0, 1, 112, 115, 2, 110, 107, 105, 110, 103, 0, 1, 116, 2, 108, 17, 65, 0, 8, 2, 101, 32, 0, 110, 110, 101, 115, 8, 99, 3, 108, 12, 50, 12, 0, 118, 1, 108, 2, 101, 116, 3, 108, 12, 82, 0, 118, 101, 1, 108, 2, 109, 101, 110, 116, 3, 108, 13, 0, 114, 97, 112, 97, 104, 111, 101, 3, 108, 34, 6, 108, 48, 108, 105, 111, 58, 0, 4, 114, 114, 121, 1, 98, 3, 108, 34, 37, 0, 114, 121, 1, 109, 32, 121, 100, 111, 111, 108, 98, 0, 116, 104, 101, 110, 3, 108, 47, 6, 36, 50, 0, 116, 116, 114, 105, 98, 117, 116, 105, 111, 110, 8, 3, 108, 47, 51, 37, 69, 40, 89, 6, 39, 50, 0, 116, 116, 114, 105, 98, 117, 116, 105, 111, 110, 3, 108, 47, 51, 37, 69, 40, 89, 39, 50, 0, 116, 97, 107, 111, 109, 98, 1, 107, 3, 108, 47, 108, 49, 6, 39, 63, 69, 0, 4, 112, 101, 1, 110, 97, 107, 3, 108, 48, 6, 36, 0, 112, 195, 169, 1, 110, 97, 107, 0, 112, 112, 101, 97, 108, 3, 108, 48, 6, 37, 55, 0, 112, 111, 108, 101, 111, 110, 1, 110, 3, 108, 48, 6, 39, 55, 57, 112, 50, 0, 107, 107, 111, 114, 100, 101, 111, 110, 3, 108, 49, 6, 112, 12, 70, 36, 112, 50, 0, 107, 114, 121, 108, 3, 108, 49, 34, 6, 114, 55, 0, 107, 117, 108, 116, 101, 116, 8, 102, 3, 108, 49, 40, 55, 47, 6, 36, 47, 0, 99, 116, 105, 111, 110, 3, 108, 49, 89, 57, 13, 50, 0, 110, 100, 114, 101, 97, 8, 3, 108, 50, 70, 34, 6, 36, 108, 0, 110, 100, 114, 101, 119, 3, 108, 50, 70, 34, 40, 0, 110, 100, 114, 101, 119, 115, 3, 108, 50, 70, 51, 40, 12, 87, 0, 110, 100, 111, 8, 114, 98, 3, 108, 50, 70, 111, 58, 0, 110, 100, 111, 108, 112, 104, 1, 114, 3, 108, 50, 70, 112, 55, 81, 0, 110, 100, 101, 114, 115, 111, 110, 8, 3, 108, 50, 70, 112, 87, 112, 50, 0, 110, 103, 101, 108, 97, 8, 3, 108, 50, 73, 13, 55, 108, 0, 110, 103, 105, 101, 8, 3, 108, 50, 73, 37, 0, 110, 103, 101, 108, 101, 115, 3, 108, 50, 73, 106, 55, 107, 87, 0, 4, 110, 103, 2, 114, 101, 98, 3, 108, 50, 79, 0, 110, 103, 2, 114, 105, 12, 0, 110, 103, 111, 111, 110, 1, 114, 3, 108, 50, 79, 6, 40, 12, 50, 0, 110, 104, 97, 116, 116, 97, 110, 1, 109, 3, 108, 50, 105, 6, 108, 47, 13, 50, 0, 114, 114, 111, 119, 3, 108, 51, 39, 40, 0, 4, 108, 1, 10, 2, 105, 115, 109, 28, 33, 12, 3, 108, 55, 6, 0, 108, 1, 110, 97, 2, 121, 12, 0, 108, 97, 106, 1, 109, 3, 108, 55, 6, 35, 57, 0, 4, 108, 108, 105, 101, 8, 2, 32, 3, 108, 55, 37, 0, 108, 108, 121, 1, 115, 0, 108, 100, 101, 116, 104, 97, 3, 108, 55, 70, 6, 37, 85, 108, 0, 108, 100, 101, 104, 121, 100, 1, 109, 114, 111, 102, 3, 108, 55, 70, 106, 105, 6, 114, 84, 0, 108, 97, 107, 108, 97, 118, 1, 98, 2, 97, 3, 108, 55, 108, 49, 55, 6, 108, 12, 82, 0, 108, 97, 99, 101, 8, 112, 3, 108, 55, 108, 87, 0, 4, 1, 108, 21, 2, 103, 3, 108, 57, 0, 103, 1, 100, 101, 109, 109, 111, 100, 0, 103, 1, 102, 2, 32, 0, 103, 1, 109, 2, 114, 101, 0, 103, 1, 115, 2, 115, 32, 12, 0, 103, 1, 118, 32, 116, 100, 105, 108, 2, 116, 0, 103, 8, 109, 2, 32, 12, 0, 103, 8, 118, 2, 32, 0, 103, 8, 118, 2, 101, 32, 0, 108, 98, 117, 113, 117, 101, 114, 113, 117, 101, 3, 108, 59, 69, 106, 49, 116, 49, 37, 0, 109, 97, 114, 111, 1, 99, 3, 108, 63, 6, 107, 34, 39, 0, 109, 97, 1, 103, 2, 99, 104, 3, 108, 63, 6, 108, 0, 109, 98, 114, 111, 115, 101, 3, 108, 63, 69, 51, 113, 40, 87, 0, 103, 110, 97, 1, 109, 114, 97, 2, 99, 3, 108, 66, 6, 110, 0, 98, 98, 121, 8, 3, 108, 69, 37, 0, 98, 105, 108, 101, 110, 101, 3, 108, 69, 37, 55, 37, 12, 50, 0, 100, 101, 114, 1, 10, 2, 101, 28, 33, 3, 108, 70, 6, 36, 34, 0, 100, 101, 110, 116, 1, 10, 2, 28, 33, 3, 108, 70, 6, 36, 50, 47, 0, 4, 103, 1, 109, 2, 105, 12, 3, 108, 79, 0, 103, 1, 110, 97, 108, 102, 2, 97, 110, 0, 103, 1, 110, 121, 115, 2, 111, 103, 101, 0, 103, 2, 110, 101, 119, 0, 103, 103, 105, 101, 3, 108, 79, 37, 0, 103, 97, 122, 105, 110, 101, 1, 109, 3, 108, 79, 108, 87, 6, 37, 12, 50, 0, 4, 118, 1, 108, 2, 97, 17, 67, 3, 108, 82, 0, 118, 1, 108, 2, 97, 32, 0, 118, 1, 108, 2, 97, 101, 0, 118, 1, 108, 2, 101, 100, 0, 118, 1, 108, 2, 101, 114, 0, 118, 1, 108, 2, 101, 115, 0, 118, 1, 108, 2, 105, 110, 101, 0, 118, 1, 108, 2, 110, 105, 0, 118, 1, 108, 2, 116, 32, 0, 118, 1, 116, 115, 2, 110, 105, 110, 0, 118, 1, 116, 115, 103, 111, 98, 0, 118, 8, 108, 2, 32, 0, 118, 101, 114, 1, 108, 107, 2, 32, 3, 108, 82, 6, 36, 34, 0, 118, 101, 1, 108, 2, 32, 3, 108, 82, 13, 0, 118, 101, 116, 1, 108, 110, 111, 110, 97, 107, 3, 108, 82, 36, 47, 0, 118, 97, 110, 116, 103, 97, 114, 100, 101, 3, 108, 82, 110, 66, 79, 6, 35, 34, 70, 106, 0, 118, 101, 114, 1, 108, 2, 32, 3, 108, 82, 112, 0, 115, 116, 97, 105, 114, 101, 3, 108, 87, 70, 6, 107, 12, 34, 0, 115, 101, 114, 98, 97, 106, 100, 115, 106, 97, 110, 3, 108, 87, 112, 69, 108, 89, 6, 108, 50, 0, 99, 104, 101, 1, 116, 116, 97, 3, 108, 89, 6, 36, 0, 4, 116, 105, 111, 1, 103, 105, 108, 98, 111, 2, 110, 3, 108, 89, 6, 39, 0, 116, 105, 111, 8, 103, 105, 108, 98, 111, 2, 110, 0, 116, 105, 111, 110, 1, 10, 2, 28, 33, 3, 108, 89, 7, 39, 50, 0, 116, 105, 111, 1, 110, 114, 101, 116, 110, 105, 2, 110, 97, 108, 3, 108, 89, 39, 0, 104, 101, 110, 1, 104, 115, 3, 108, 106, 50, 0, 1, 114, 114, 101, 116, 2, 115, 3, 109, 0, 4, 1, 17, 67, 2, 102, 116, 3, 110, 0, 1, 17, 67, 2, 114, 18, 69, 0, 1, 18, 66, 2, 18, 71, 116, 12, 0, 1, 18, 67, 2, 18, 67, 0, 1, 18, 67, 2, 18, 67, 115, 101, 114, 0, 1, 18, 71, 2, 110, 107, 0, 1, 100, 2, 109, 112, 0, 1, 100, 97, 2, 109, 0, 1, 102, 2, 109, 108, 101, 12, 0, 1, 106, 2, 18, 75, 111, 12, 0, 1, 106, 109, 2, 118, 0, 1, 107, 2, 103, 0, 1, 107, 115, 2, 107, 0, 1, 108, 2, 103, 116, 12, 0, 1, 110, 2, 112, 0, 1, 110, 115, 2, 118, 115, 0, 1, 114, 2, 17, 67, 12, 0, 1, 114, 2, 17, 67, 18, 69, 0, 1, 114, 2, 18, 66, 12, 12, 0, 1, 114, 2, 18, 67, 18, 69, 12, 0, 1, 114, 2, 18, 71, 0, 1, 114, 2, 32, 0, 1, 114, 2, 100, 0, 1, 114, 2, 101, 110, 0, 1, 114, 2, 108, 0, 1, 114, 2, 108, 21, 21, 12, 0, 1, 114, 2, 110, 0, 1, 114, 2, 110, 101, 0, 1, 114, 17, 67, 2, 110, 0, 1, 114, 18, 66, 0, 1, 114, 98, 2, 17, 67, 0, 1, 114, 101, 109, 97, 107, 0, 1, 114, 102, 0, 1, 114, 111, 102, 2, 110, 100, 0, 1, 114, 111, 102, 2, 110, 107, 0, 1, 114, 116, 0, 1, 114, 116, 2, 17, 67, 0, 1, 114, 116, 115, 0, 1, 114, 117, 97, 108, 0, 1, 114, 118, 2, 108, 116, 0, 1, 116, 2, 110, 107, 0, 1, 118, 2, 110, 100, 114, 0, 2, 18, 66, 116, 12, 0, 2, 98, 99, 0, 2, 99, 99, 0, 2, 102, 98, 114, 121, 100, 0, 2, 102, 118, 105, 0, 2, 103, 116, 0, 2, 107, 116, 0, 2, 109, 102, 0, 2, 109, 116, 0, 2, 110, 100, 114, 101, 0, 2, 114, 12, 0, 2, 118, 108, 0, 2, 118, 110, 12, 0, 8, 2, 98, 115, 0, 8, 2, 109, 98, 0, 8, 2, 109, 101, 110, 32, 0, 8, 114, 98, 2, 110, 99, 104, 0, 104, 1, 114, 97, 115, 0, 4, 1, 114, 2, 111, 117, 108, 3, 110, 6, 0, 8, 110, 111, 109, 2, 114, 107, 105, 0, 97, 1, 107, 105, 114, 102, 97, 2, 110, 3, 110, 12, 0, 110, 99, 101, 1, 108, 101, 101, 114, 102, 3, 110, 12, 66, 87, 0, 114, 1, 10, 2, 105, 97, 116, 28, 33, 3, 110, 34, 0, 97, 114, 111, 110, 3, 110, 34, 112, 50, 0, 4, 102, 2, 115, 3, 110, 40, 0, 103, 1, 18, 74, 2, 12, 0, 103, 1, 104, 2, 108, 0, 103, 1, 114, 2, 110, 97, 12, 0, 103, 1, 115, 2, 17, 67, 12, 0, 103, 1, 115, 2, 115, 195, 184, 0, 103, 2, 110, 0, 118, 1, 18, 73, 2, 17, 67, 0, 118, 1, 98, 2, 12, 12, 0, 118, 1, 103, 2, 109, 105, 0, 118, 1, 104, 2, 17, 67, 0, 118, 1, 104, 2, 97, 98, 111, 114, 114, 0, 118, 1, 104, 2, 105, 115, 0, 118, 1, 104, 2, 111, 118, 101, 114, 0, 118, 1, 104, 2, 117, 100, 0, 118, 1, 104, 21, 2, 32, 0, 118, 1, 104, 32, 103, 111, 32, 108, 101, 109, 109, 105, 104, 0, 118, 1, 115, 2, 17, 67, 0, 118, 1, 116, 2, 115, 0, 118, 2, 108, 0, 118, 8, 2, 32, 0, 118, 8, 108, 0, 118, 8, 116, 2, 32, 0, 118, 95, 1, 104, 21, 0, 103, 110, 101, 1, 109, 2, 116, 3, 110, 40, 50, 6, 36, 0, 116, 1, 114, 10, 2, 105, 28, 33, 3, 110, 47, 0, 116, 1, 114, 10, 2, 117, 114, 28, 33, 3, 110, 47, 6, 0, 114, 107, 97, 110, 115, 97, 115, 3, 110, 49, 13, 50, 87, 111, 12, 0, 4, 102, 2, 116, 97, 108, 3, 110, 58, 0, 103, 1, 114, 112, 115, 2, 108, 101, 116, 0, 118, 1, 110, 103, 2, 112, 111, 116, 0, 109, 101, 108, 117, 1, 109, 2, 107, 3, 110, 63, 106, 55, 6, 40, 0, 109, 97, 103, 101, 114, 8, 3, 110, 63, 110, 34, 0, 4, 110, 1, 108, 2, 99, 101, 3, 110, 66, 0, 110, 1, 108, 112, 2, 99, 104, 0, 110, 99, 101, 1, 10, 2, 114, 101, 28, 33, 3, 110, 66, 87, 6, 36, 0, 110, 99, 101, 1, 10, 2, 12, 3, 110, 66, 87, 13, 0, 110, 99, 101, 1, 10, 2, 114, 101, 12, 3, 110, 66, 87, 36, 0, 110, 99, 104, 101, 116, 1, 109, 3, 110, 66, 89, 6, 107, 70, 0, 98, 101, 108, 1, 114, 105, 109, 3, 110, 69, 6, 107, 55, 0, 98, 97, 100, 115, 1, 114, 116, 115, 3, 110, 69, 6, 108, 87, 0, 98, 100, 111, 2, 109, 3, 110, 69, 70, 6, 39, 0, 98, 115, 111, 108, 117, 116, 105, 111, 110, 8, 3, 110, 69, 87, 39, 55, 40, 89, 6, 39, 50, 0, 98, 115, 111, 108, 117, 116, 105, 111, 110, 3, 110, 69, 87, 39, 55, 40, 89, 39, 50, 0, 100, 101, 114, 1, 114, 10, 2, 101, 28, 33, 3, 110, 70, 6, 36, 34, 0, 100, 97, 114, 1, 114, 3, 110, 70, 110, 34, 0, 114, 103, 101, 1, 108, 3, 110, 73, 0, 103, 103, 101, 114, 1, 100, 2, 116, 3, 110, 79, 112, 0, 102, 97, 101, 1, 114, 3, 110, 81, 108, 6, 36, 0, 116, 105, 111, 110, 1, 114, 10, 2, 28, 33, 3, 110, 89, 6, 39, 50, 0, 101, 114, 1, 114, 2, 32, 3, 110, 112, 0, 4, 1, 119, 2, 116, 101, 114, 3, 111, 0, 8, 116, 115, 2, 108, 108, 0, 117, 1, 115, 2, 116, 101, 114, 101, 0, 117, 8, 112, 2, 108, 0, 119, 1, 114, 0, 117, 1, 115, 2, 99, 101, 3, 111, 12, 0, 108, 108, 1, 98, 121, 101, 108, 108, 111, 118, 3, 111, 12, 55, 0, 117, 98, 114, 101, 121, 3, 111, 12, 69, 34, 37, 0, 117, 100, 114, 101, 121, 3, 111, 12, 70, 51, 37, 0, 117, 114, 105, 101, 1, 108, 3, 111, 34, 37, 0, 97, 103, 101, 8, 3, 111, 40, 106, 0, 108, 107, 1, 116, 2, 115, 104, 111, 119, 3, 111, 49, 0, 117, 114, 101, 101, 110, 1, 109, 3, 111, 51, 6, 37, 12, 50, 0, 108, 108, 2, 32, 114, 105, 103, 104, 116, 3, 111, 55, 0, 108, 100, 105, 110, 103, 1, 112, 115, 3, 111, 55, 70, 4, 36, 66, 0, 119, 1, 114, 99, 3, 112, 0, 108, 1, 119, 2, 107, 3, 112, 12, 0, 108, 108, 1, 119, 3, 112, 12, 55, 0, 119, 114, 101, 110, 99, 101, 1, 108, 3, 113, 34, 13, 50, 87, 0, 7, 6, 98, 0, 4, 1, 184, 195, 107, 2, 109, 97, 3, 0, 1, 184, 195, 107, 2, 109, 195, 166, 3, 0, 114, 111, 119, 110, 3, 21, 0, 2, 32, 3, 48, 0, 4, 1, 101, 112, 2, 101, 114, 3, 58, 0, 1, 101, 112, 2, 114, 101, 0, 98, 1, 111, 107, 2, 101, 114, 0, 4, 3, 69, 0, 98, 0, 101, 97, 116, 8, 3, 69, 6, 37, 12, 47, 0, 111, 110, 107, 97, 109, 109, 101, 114, 97, 116, 3, 69, 6, 112, 66, 49, 35, 63, 13, 34, 110, 47, 0, 114, 97, 105, 108, 108, 101, 3, 69, 34, 35, 57, 12, 0, 114, 105, 110, 116, 105, 111, 110, 3, 69, 34, 36, 50, 70, 57, 39, 12, 50, 0, 114, 111, 97, 100, 3, 69, 34, 111, 70, 0, 97, 114, 121, 116, 111, 110, 3, 69, 35, 37, 47, 112, 50, 0, 101, 105, 2, 114, 117, 116, 3, 69, 35, 57, 0, 105, 107, 101, 3, 69, 35, 57, 49, 0, 117, 105, 2, 108, 100, 105, 110, 103, 3, 69, 36, 0, 97, 115, 101, 98, 97, 108, 108, 3, 69, 36, 57, 87, 80, 111, 12, 59, 0, 105, 110, 103, 104, 97, 109, 3, 69, 36, 66, 106, 63, 0, 117, 115, 105, 110, 101, 115, 115, 3, 69, 36, 87, 50, 107, 87, 0, 101, 97, 2, 116, 114, 105, 3, 69, 36, 108, 6, 0, 101, 101, 1, 115, 105, 114, 102, 3, 69, 37, 0, 101, 98, 111, 112, 3, 69, 37, 12, 69, 112, 48, 0, 101, 97, 99, 104, 3, 69, 37, 12, 74, 0, 101, 97, 103, 108, 101, 3, 69, 37, 12, 79, 13, 55, 0, 105, 108, 108, 105, 101, 3, 69, 37, 59, 37, 0, 101, 97, 117, 106, 111, 108, 97, 105, 115, 3, 69, 39, 89, 57, 39, 55, 6, 107, 0, 111, 117, 114, 103, 111, 103, 110, 101, 3, 69, 40, 34, 79, 6, 112, 50, 57, 13, 0, 111, 117, 105, 108, 108, 2, 111, 110, 3, 69, 40, 55, 57, 0, 111, 117, 105, 108, 108, 97, 98, 97, 105, 115, 115, 101, 3, 69, 40, 57, 35, 69, 6, 107, 87, 0, 111, 117, 100, 111, 105, 114, 3, 69, 40, 70, 58, 6, 110, 12, 0, 114, 117, 99, 101, 8, 3, 69, 51, 40, 12, 87, 0, 114, 111, 119, 115, 101, 114, 3, 69, 51, 110, 58, 87, 112, 0, 108, 97, 107, 101, 8, 3, 69, 55, 107, 57, 49, 0, 108, 105, 103, 104, 8, 3, 69, 55, 110, 57, 0, 108, 111, 111, 100, 121, 3, 69, 55, 112, 70, 37, 0, 117, 116, 116, 101, 8, 2, 32, 3, 69, 57, 40, 12, 47, 0, 117, 105, 99, 8, 3, 69, 57, 40, 37, 49, 0, 101, 108, 108, 101, 118, 117, 101, 3, 69, 107, 55, 13, 82, 6, 114, 0, 101, 105, 106, 105, 110, 103, 3, 69, 107, 57, 73, 6, 36, 66, 0, 101, 118, 101, 114, 108, 121, 3, 69, 107, 82, 112, 55, 37, 0, 97, 99, 107, 117, 112, 8, 3, 69, 108, 49, 6, 112, 69, 0, 97, 108, 107, 111, 110, 8, 3, 69, 108, 55, 49, 6, 112, 66, 0, 97, 108, 107, 111, 110, 3, 69, 108, 55, 49, 112, 66, 0, 97, 98, 121, 108, 111, 110, 2, 101, 114, 3, 69, 108, 69, 114, 55, 6, 39, 50, 0, 97, 98, 121, 108, 111, 110, 2, 105, 115, 107, 3, 69, 108, 69, 114, 55, 39, 50, 0, 97, 98, 121, 108, 111, 110, 3, 69, 108, 69, 114, 55, 112, 50, 0, 97, 99, 107, 103, 97, 109, 109, 111, 110, 3, 69, 108, 79, 6, 108, 63, 106, 50, 0, 97, 115, 115, 105, 110, 1, 10, 3, 69, 108, 87, 6, 107, 66, 0, 97, 114, 98, 105, 101, 3, 69, 110, 34, 69, 37, 0, 97, 115, 107, 101, 116, 98, 97, 108, 108, 3, 69, 110, 87, 79, 36, 47, 69, 111, 12, 55, 0, 111, 97, 114, 100, 3, 69, 111, 12, 70, 0, 97, 108, 116, 105, 109, 111, 114, 101, 3, 69, 111, 55, 47, 37, 63, 112, 12, 0, 111, 110, 101, 1, 32, 116, 3, 69, 111, 58, 50, 0, 111, 114, 111, 117, 103, 104, 3, 69, 112, 34, 112, 0, 117, 116, 116, 101, 114, 102, 108, 121, 3, 69, 112, 47, 112, 81, 55, 35, 57, 0, 111, 100, 121, 103, 117, 97, 114, 100, 3, 69, 112, 70, 37, 79, 110, 12, 70, 0, 111, 100, 121, 115, 116, 111, 99, 107, 105, 110, 103, 3, 69, 112, 70, 37, 87, 47, 112, 49, 36, 66, 0, 117, 103, 115, 121, 3, 69, 112, 79, 87, 37, 0, 117, 102, 102, 97, 108, 111, 3, 69, 112, 81, 106, 55, 111, 58, 0, 4, 117, 102, 102, 101, 116, 1, 21, 3, 69, 114, 81, 6, 36, 0, 117, 102, 102, 101, 116, 8, 0, 117, 114, 103, 104, 3, 69, 116, 12, 79, 0, 117, 114, 116, 111, 110, 3, 69, 116, 47, 112, 50, 0, 101, 114, 110, 105, 101, 3, 69, 116, 50, 37, 0, 105, 114, 109, 105, 110, 103, 104, 97, 109, 3, 69, 116, 63, 37, 66, 13, 63, 0, 117, 114, 103, 101, 115, 115, 3, 69, 116, 73, 36, 87, 0, 7, 6, 99, 0, 4, 1, 115, 2, 104, 97, 3, 0, 2, 107, 3, 0, 99, 1, 101, 98, 101, 114, 2, 97, 3, 8, 49, 0, 1, 105, 114, 101, 100, 101, 114, 102, 2, 105, 97, 3, 8, 49, 87, 0, 101, 114, 1, 10, 2, 28, 33, 3, 8, 87, 7, 36, 34, 0, 101, 114, 101, 1, 10, 2, 28, 33, 3, 8, 87, 7, 36, 34, 106, 0, 4, 101, 1, 10, 2, 32, 28, 33, 3, 8, 87, 13, 0, 101, 1, 10, 2, 110, 28, 33, 0, 101, 1, 10, 2, 114, 28, 33, 3, 8, 87, 112, 0, 101, 114, 101, 110, 1, 117, 100, 111, 114, 112, 3, 8, 87, 112, 106, 50, 0, 101, 110, 101, 1, 115, 3, 36, 50, 106, 0, 101, 110, 101, 114, 1, 115, 3, 36, 50, 112, 0, 104, 105, 110, 97, 3, 47, 57, 35, 57, 50, 108, 0, 104, 97, 2, 116, 3, 47, 57, 108, 0, 4, 3, 49, 0, 1, 97, 108, 108, 105, 100, 97, 99, 0, 99, 1, 105, 112, 2, 111, 0, 99, 1, 111, 114, 2, 111, 0, 99, 1, 111, 115, 2, 101, 114, 0, 104, 1, 101, 116, 2, 110, 111, 0, 104, 1, 105, 109, 2, 97, 0, 104, 1, 105, 110, 2, 111, 108, 0, 104, 1, 111, 115, 97, 109, 2, 105, 115, 0, 104, 2, 108, 111, 101, 0, 104, 2, 114, 0, 104, 8, 97, 109, 2, 32, 0, 115, 1, 110, 97, 114, 102, 0, 99, 1, 97, 116, 115, 2, 97, 116, 111, 3, 49, 6, 0, 114, 101, 101, 107, 3, 49, 34, 37, 12, 49, 0, 114, 101, 97, 115, 121, 3, 49, 34, 37, 87, 37, 0, 114, 111, 105, 115, 115, 97, 110, 116, 3, 49, 34, 39, 35, 87, 6, 110, 66, 0, 114, 101, 109, 101, 3, 49, 34, 107, 12, 63, 0, 97, 114, 116, 105, 101, 114, 8, 3, 49, 35, 34, 47, 57, 6, 36, 0, 111, 119, 98, 111, 121, 3, 49, 35, 40, 69, 111, 57, 0, 97, 109, 101, 109, 98, 101, 114, 116, 3, 49, 35, 63, 110, 66, 69, 6, 107, 34, 0, 97, 109, 98, 114, 105, 100, 103, 101, 3, 49, 36, 57, 63, 69, 51, 37, 73, 0, 111, 108, 97, 100, 97, 3, 49, 39, 55, 6, 110, 84, 108, 0, 114, 97, 122, 121, 3, 49, 51, 107, 57, 87, 37, 0, 108, 101, 118, 101, 108, 97, 110, 100, 3, 49, 55, 37, 12, 82, 55, 108, 50, 0, 108, 97, 105, 114, 2, 118, 111, 121, 3, 49, 55, 107, 34, 0, 108, 97, 114, 101, 110, 99, 101, 3, 49, 55, 108, 51, 13, 50, 87, 0, 108, 101, 114, 107, 3, 49, 55, 110, 12, 49, 0, 108, 97, 117, 100, 101, 3, 49, 55, 111, 12, 70, 0, 104, 105, 97, 110, 116, 105, 3, 49, 57, 6, 108, 50, 47, 37, 0, 99, 3, 49, 87, 0, 97, 116, 101, 114, 105, 110, 103, 3, 49, 107, 37, 47, 13, 34, 37, 66, 0, 97, 106, 117, 110, 3, 49, 107, 73, 106, 50, 0, 97, 114, 111, 108, 105, 110, 97, 1, 32, 104, 116, 114, 111, 110, 3, 49, 108, 34, 39, 55, 6, 35, 57, 50, 108, 0, 97, 110, 116, 101, 114, 98, 117, 114, 121, 3, 49, 108, 50, 47, 112, 69, 34, 37, 0, 97, 103, 110, 101, 121, 8, 3, 49, 108, 79, 50, 37, 0, 97, 116, 104, 121, 8, 3, 49, 108, 85, 37, 0, 97, 114, 100, 105, 110, 8, 3, 49, 110, 34, 70, 6, 108, 66, 0, 97, 114, 108, 105, 115, 108, 101, 3, 49, 110, 55, 35, 57, 55, 0, 111, 117, 114, 116, 110, 101, 121, 3, 49, 111, 12, 47, 50, 37, 0, 111, 104, 101, 110, 3, 49, 111, 40, 13, 50, 0, 111, 108, 101, 114, 105, 100, 103, 101, 3, 49, 111, 58, 55, 34, 37, 73, 0, 111, 2, 110, 114, 97, 100, 3, 49, 112, 0, 111, 114, 110, 2, 102, 3, 49, 112, 12, 50, 0, 111, 114, 110, 105, 99, 104, 111, 110, 3, 49, 112, 34, 50, 37, 89, 6, 112, 66, 0, 111, 116, 116, 97, 103, 101, 3, 49, 112, 47, 37, 73, 0, 117, 116, 108, 101, 114, 3, 49, 112, 47, 55, 112, 0, 111, 99, 107, 110, 101, 121, 3, 49, 112, 49, 50, 37, 0, 111, 110, 110, 101, 99, 116, 105, 99, 117, 116, 3, 49, 112, 50, 6, 36, 47, 37, 49, 112, 70, 0, 111, 110, 110, 105, 101, 3, 49, 112, 50, 37, 0, 111, 117, 110, 116, 114, 121, 3, 49, 112, 50, 47, 34, 37, 0, 111, 110, 110, 111, 114, 3, 49, 112, 50, 112, 0, 97, 108, 108, 103, 105, 114, 108, 3, 49, 112, 55, 79, 116, 12, 55, 0, 111, 109, 112, 117, 116, 101, 114, 3, 49, 112, 63, 48, 57, 6, 40, 12, 47, 112, 0, 111, 114, 100, 101, 108, 105, 97, 3, 49, 112, 70, 6, 37, 55, 37, 20, 108, 0, 117, 115, 116, 101, 114, 8, 3, 49, 112, 87, 47, 112, 0, 121, 112, 101, 114, 3, 49, 114, 48, 112, 0, 117, 114, 108, 101, 114, 3, 49, 116, 55, 112, 0, 4, 104, 1, 105, 119, 3, 74, 0, 104, 2, 105, 0, 4, 1, 114, 111, 99, 115, 2, 101, 115, 101, 3, 74, 6, 0, 8, 97, 112, 2, 105, 110, 111, 0, 104, 105, 108, 100, 3, 74, 35, 57, 55, 70, 0, 104, 105, 104, 117, 97, 104, 117, 97, 3, 74, 37, 58, 6, 35, 58, 35, 0, 104, 2, 105, 112, 3, 74, 57, 0, 99, 1, 117, 112, 112, 97, 99, 2, 105, 110, 111, 3, 74, 57, 6, 0, 105, 97, 111, 8, 2, 32, 3, 74, 57, 110, 58, 0, 104, 101, 108, 115, 101, 97, 3, 74, 107, 55, 87, 37, 0, 104, 97, 112, 108, 105, 110, 3, 74, 108, 48, 55, 37, 50, 0, 104, 97, 108, 108, 101, 110, 103, 101, 3, 74, 108, 55, 36, 50, 73, 0, 104, 97, 114, 108, 101, 115, 3, 74, 110, 12, 55, 87, 0, 104, 97, 114, 108, 105, 101, 3, 74, 110, 55, 37, 0, 104, 97, 117, 99, 101, 114, 3, 74, 111, 12, 87, 112, 0, 104, 117, 99, 107, 8, 3, 74, 112, 49, 0, 104, 117, 114, 99, 104, 105, 108, 108, 3, 74, 116, 12, 89, 37, 55, 0, 4, 1, 17, 65, 2, 101, 3, 87, 0, 1, 97, 102, 2, 97, 100, 0, 1, 97, 102, 2, 111, 110, 0, 2, 101, 0, 2, 101, 108, 108, 111, 102, 97, 110, 0, 2, 105, 0, 2, 121, 0, 2, 195, 166, 115, 97, 114, 0, 2, 195, 184, 108, 105, 98, 97, 116, 0, 101, 8, 105, 108, 97, 0, 101, 8, 105, 102, 102, 111, 2, 114, 3, 87, 6, 36, 0, 195, 169, 114, 1, 10, 2, 32, 3, 87, 6, 36, 34, 0, 101, 2, 114, 116, 3, 87, 6, 107, 0, 195, 184, 114, 1, 10, 2, 32, 3, 87, 6, 116, 34, 0, 101, 121, 108, 111, 110, 3, 87, 35, 57, 59, 112, 50, 0, 101, 1, 105, 102, 102, 111, 2, 114, 3, 87, 36, 0, 101, 114, 1, 105, 102, 105, 108, 97, 118, 107, 115, 105, 100, 3, 87, 36, 34, 0, 121, 110, 116, 104, 105, 97, 3, 87, 36, 50, 85, 37, 108, 0, 105, 110, 99, 105, 110, 110, 97, 116, 105, 3, 87, 36, 50, 87, 37, 50, 6, 108, 47, 37, 0, 195, 169, 122, 97, 110, 110, 101, 3, 87, 36, 87, 6, 108, 50, 0, 195, 169, 122, 97, 110, 110, 101, 110, 3, 87, 36, 87, 6, 108, 50, 106, 50, 0, 4, 105, 103, 97, 114, 101, 116, 3, 87, 37, 79, 106, 34, 6, 109, 47, 0, 105, 103, 97, 114, 101, 116, 116, 0, 105, 101, 117, 120, 3, 87, 57, 6, 116, 0, 105, 114, 99, 117, 115, 1, 32, 121, 108, 108, 105, 100, 97, 99, 99, 105, 112, 3, 87, 116, 49, 13, 87, 0, 4, 2, 104, 97, 3, 89, 0, 104, 1, 114, 0, 104, 2, 12, 0, 104, 2, 97, 116, 101, 97, 117, 0, 99, 105, 110, 105, 1, 117, 112, 3, 89, 6, 37, 50, 37, 0, 104, 101, 121, 101, 110, 110, 101, 3, 89, 35, 57, 6, 107, 50, 0, 104, 105, 99, 97, 103, 111, 3, 89, 37, 49, 6, 110, 79, 111, 58, 0, 104, 111, 112, 105, 110, 3, 89, 39, 48, 107, 66, 0, 2, 101, 108, 108, 111, 3, 89, 57, 0, 104, 101, 114, 121, 108, 3, 89, 107, 34, 36, 59, 0, 104, 97, 98, 108, 105, 115, 3, 89, 108, 69, 55, 6, 37, 0, 104, 97, 103, 97, 108, 108, 3, 89, 108, 79, 6, 108, 55, 0, 104, 111, 107, 101, 114, 101, 110, 2, 32, 3, 89, 111, 58, 49, 112, 34, 13, 50, 0, 7, 6, 100, 0, 4, 1, 17, 65, 2, 116, 32, 12, 12, 3, 0, 4, 1, 17, 65, 2, 116, 101, 32, 12, 12, 3, 0, 4, 1, 17, 65, 2, 116, 101, 114, 32, 12, 12, 3, 0, 4, 1, 97, 118, 104, 3, 0, 4, 1, 101, 114, 107, 2, 115, 3, 0, 4, 1, 105, 2, 116, 3, 0, 4, 1, 105, 98, 2, 115, 107, 3, 0, 4, 1, 105, 103, 2, 115, 12, 3, 0, 4, 1, 105, 116, 2, 115, 101, 108, 3, 0, 4, 1, 108, 3, 0, 4, 1, 108, 101, 109, 2, 105, 110, 103, 3, 0, 4, 1, 108, 117, 103, 3, 0, 4, 1, 110, 97, 2, 101, 3, 0, 4, 1, 110, 105, 2, 17, 67, 3, 0, 4, 1, 114, 101, 106, 102, 2, 101, 3, 0, 4, 1, 114, 111, 2, 101, 3, 0, 4, 1, 114, 111, 107, 105, 116, 115, 3, 0, 4, 1, 114, 165, 195, 104, 3, 0, 4, 1, 114, 166, 195, 2, 32, 3, 0, 4, 1, 114, 166, 195, 102, 3, 0, 4, 1, 114, 166, 195, 118, 2, 115, 3, 0, 4, 1, 114, 166, 195, 118, 115, 3, 0, 4, 1, 114, 166, 195, 118, 115, 2, 101, 116, 3, 0, 4, 1, 117, 98, 2, 103, 101, 116, 3, 0, 4, 1, 184, 195, 2, 116, 3, 0, 4, 1, 184, 195, 102, 2, 115, 12, 12, 3, 0, 4, 2, 115, 116, 12, 12, 3, 0, 4, 8, 97, 109, 2, 115, 101, 110, 3, 0, 4, 8, 114, 117, 116, 2, 101, 3, 0, 101, 8, 110, 97, 102, 2, 109, 101, 3, 0, 4, 1, 105, 100, 110, 97, 107, 2, 97, 116, 3, 6, 70, 0, 1, 111, 109, 2, 97, 108, 0, 1, 108, 101, 109, 105, 2, 97, 3, 8, 70, 0, 4, 111, 114, 111, 116, 104, 121, 3, 21, 0, 114, 105, 115, 99, 111, 0, 105, 1, 114, 101, 106, 102, 2, 110, 103, 3, 36, 0, 4, 116, 1, 101, 102, 2, 21, 3, 47, 0, 116, 1, 101, 114, 112, 115, 0, 116, 1, 105, 107, 115, 0, 116, 1, 117, 2, 12, 0, 101, 1, 108, 97, 98, 3, 55, 106, 0, 4, 3, 70, 0, 1, 17, 67, 2, 101, 116, 17, 65, 0, 1, 21, 2, 101, 108, 116, 0, 1, 21, 2, 121, 114, 0, 1, 97, 2, 97, 109, 0, 1, 97, 2, 111, 112, 116, 101, 114, 0, 1, 97, 109, 2, 114, 97, 115, 0, 1, 101, 2, 103, 97, 114, 0, 1, 101, 109, 2, 97, 108, 106, 0, 1, 101, 109, 111, 114, 100, 2, 97, 114, 0, 1, 101, 110, 101, 118, 2, 105, 103, 0, 1, 101, 112, 2, 114, 111, 0, 1, 101, 114, 2, 97, 0, 1, 105, 2, 111, 108, 0, 1, 105, 99, 97, 2, 111, 115, 101, 0, 1, 105, 115, 2, 101, 110, 116, 0, 1, 105, 118, 101, 2, 101, 110, 0, 1, 108, 2, 97, 107, 105, 110, 0, 1, 108, 2, 105, 103, 0, 1, 108, 2, 117, 103, 0, 1, 108, 97, 2, 114, 105, 103, 0, 1, 108, 97, 109, 114, 111, 102, 2, 101, 0, 1, 108, 97, 115, 2, 111, 0, 1, 108, 101, 104, 2, 105, 0, 1, 108, 101, 116, 114, 117, 116, 2, 117, 101, 0, 1, 108, 101, 118, 2, 114, 101, 106, 0, 1, 108, 105, 2, 114, 105, 110, 103, 0, 1, 108, 105, 98, 2, 195, 166, 107, 0, 1, 108, 105, 100, 2, 111, 0, 1, 108, 105, 107, 2, 114, 101, 0, 1, 108, 108, 117, 98, 2, 111, 0, 1, 108, 111, 2, 105, 110, 103, 0, 1, 108, 111, 98, 0, 1, 108, 111, 115, 2, 195, 166, 107, 0, 1, 110, 17, 65, 2, 114, 17, 65, 0, 1, 110, 17, 65, 2, 114, 101, 0, 1, 110, 105, 2, 117, 0, 1, 110, 105, 2, 117, 17, 67, 0, 1, 110, 111, 104, 2, 117, 114, 97, 0, 1, 111, 98, 2, 101, 103, 97, 0, 1, 111, 109, 2, 101, 108, 0, 1, 111, 109, 2, 101, 109, 0, 1, 111, 109, 2, 101, 114, 110, 0, 1, 111, 111, 119, 0, 1, 114, 101, 118, 2, 101, 110, 0, 1, 114, 105, 2, 32, 0, 1, 114, 111, 2, 101, 108, 0, 1, 114, 111, 2, 101, 110, 0, 1, 114, 111, 2, 101, 114, 0, 1, 114, 111, 106, 104, 0, 1, 114, 111, 107, 97, 0, 1, 114, 111, 107, 101, 114, 0, 1, 114, 166, 195, 102, 2, 101, 17, 67, 0, 1, 114, 166, 195, 108, 2, 32, 0, 1, 114, 166, 195, 118, 2, 105, 0, 1, 117, 98, 2, 97, 112, 101, 115, 116, 0, 1, 117, 108, 107, 2, 101, 114, 101, 0, 1, 117, 109, 114, 101, 98, 2, 97, 0, 1, 121, 111, 108, 102, 0, 1, 165, 195, 2, 97, 110, 0, 1, 166, 195, 2, 114, 117, 0, 1, 166, 195, 112, 2, 97, 0, 2, 97, 103, 0, 2, 101, 108, 101, 0, 2, 101, 109, 101, 110, 115, 0, 2, 105, 0, 2, 111, 107, 0, 2, 111, 108, 108, 0, 2, 111, 109, 0, 2, 111, 110, 110, 97, 0, 2, 114, 97, 109, 97, 0, 2, 114, 101, 118, 0, 2, 114, 121, 115, 0, 2, 117, 102, 116, 101, 0, 2, 117, 115, 0, 2, 195, 165, 115, 101, 0, 2, 195, 184, 109, 0, 2, 195, 184, 114, 0, 8, 97, 2, 114, 0, 8, 105, 2, 101, 0, 8, 105, 2, 195, 169, 0, 8, 108, 105, 104, 2, 97, 0, 39, 0, 100, 1, 105, 109, 2, 97, 0, 100, 104, 1, 117, 98, 0, 100, 104, 1, 117, 98, 2, 105, 115, 116, 0, 4, 1, 110, 101, 112, 2, 117, 108, 3, 70, 6, 0, 1, 111, 109, 2, 117, 108, 0, 101, 1, 105, 107, 114, 111, 3, 70, 6, 36, 0, 101, 110, 100, 114, 111, 110, 3, 70, 6, 36, 50, 70, 34, 112, 50, 0, 105, 1, 117, 111, 104, 2, 110, 105, 3, 70, 6, 37, 0, 111, 115, 1, 101, 110, 114, 117, 111, 116, 3, 70, 6, 39, 0, 4, 117, 1, 97, 105, 118, 2, 107, 116, 3, 70, 6, 111, 0, 117, 8, 111, 114, 112, 2, 107, 116, 0, 111, 114, 1, 97, 118, 108, 97, 115, 3, 70, 6, 111, 12, 0, 114, 101, 100, 8, 108, 105, 109, 3, 70, 34, 107, 70, 0, 111, 119, 110, 108, 111, 97, 100, 3, 70, 35, 58, 50, 55, 39, 58, 70, 0, 111, 117, 98, 116, 102, 105, 114, 101, 3, 70, 35, 58, 70, 81, 35, 57, 112, 0, 4, 101, 1, 105, 117, 103, 2, 110, 3, 70, 36, 0, 101, 1, 121, 98, 2, 108, 0, 101, 116, 101, 110, 116, 101, 3, 70, 36, 47, 6, 110, 12, 66, 47, 0, 101, 116, 114, 111, 105, 116, 3, 70, 36, 47, 34, 6, 112, 57, 47, 0, 4, 105, 99, 107, 105, 101, 3, 70, 36, 49, 37, 0, 105, 99, 107, 121, 0, 105, 103, 1, 114, 166, 195, 102, 3, 70, 37, 0, 101, 97, 110, 8, 3, 70, 37, 12, 50, 0, 111, 114, 97, 100, 111, 1, 108, 101, 3, 70, 39, 34, 6, 110, 70, 39, 0, 111, 117, 103, 104, 110, 117, 116, 3, 70, 39, 58, 50, 112, 70, 0, 117, 8, 111, 114, 112, 2, 107, 116, 105, 118, 3, 70, 40, 0, 114, 105, 118, 101, 8, 2, 45, 3, 70, 51, 110, 57, 82, 0, 4, 117, 99, 101, 114, 1, 111, 114, 112, 2, 32, 3, 70, 57, 6, 40, 87, 112, 0, 117, 99, 101, 114, 1, 111, 114, 112, 2, 97, 115, 115, 105, 115, 116, 101, 110, 116, 0, 101, 119, 101, 121, 3, 70, 57, 40, 37, 0, 119, 105, 103, 104, 116, 3, 70, 58, 35, 57, 47, 0, 100, 115, 1, 111, 3, 70, 87, 0, 101, 98, 98, 105, 101, 3, 70, 107, 69, 37, 0, 97, 114, 121, 108, 3, 70, 108, 34, 106, 59, 0, 97, 105, 113, 117, 105, 114, 105, 3, 70, 108, 49, 13, 34, 37, 0, 97, 114, 108, 101, 110, 101, 3, 70, 110, 55, 6, 37, 50, 0, 97, 118, 8, 2, 32, 3, 70, 110, 58, 0, 97, 118, 115, 8, 2, 32, 3, 70, 110, 58, 87, 0, 117, 110, 100, 1, 101, 114, 2, 97, 110, 116, 3, 70, 111, 50, 70, 0, 101, 114, 1, 105, 117, 103, 3, 70, 112, 0, 97, 119, 115, 111, 110, 3, 70, 112, 12, 87, 106, 50, 0, 111, 99, 8, 2, 32, 3, 70, 112, 49, 0, 111, 117, 98, 108, 101, 3, 70, 112, 69, 13, 55, 0, 111, 117, 98, 108, 101, 116, 111, 110, 3, 70, 112, 69, 13, 55, 47, 112, 50, 0, 111, 100, 103, 101, 3, 70, 112, 73, 0, 117, 116, 99, 104, 3, 70, 112, 74, 0, 117, 98, 111, 105, 115, 3, 70, 114, 69, 58, 6, 110, 0, 117, 107, 101, 8, 3, 73, 40, 12, 49, 0, 101, 117, 99, 101, 3, 73, 40, 12, 87, 0, 4, 1, 17, 65, 3, 84, 0, 1, 17, 65, 2, 17, 67, 0, 1, 17, 65, 2, 101, 115, 0, 1, 17, 65, 2, 105, 103, 0, 1, 17, 65, 18, 74, 2, 116, 97, 0, 1, 97, 98, 2, 101, 0, 1, 100, 101, 110, 2, 115, 0, 1, 101, 110, 2, 115, 116, 0, 1, 101, 114, 102, 2, 115, 0, 1, 105, 2, 116, 105, 12, 0, 1, 105, 98, 2, 101, 0, 1, 105, 112, 115, 2, 115, 116, 101, 103, 0, 1, 105, 114, 2, 101, 0, 1, 105, 114, 116, 115, 2, 115, 0, 1, 105, 116, 2, 101, 0, 1, 105, 116, 2, 115, 12, 0, 1, 105, 118, 2, 101, 114, 0, 1, 111, 102, 2, 17, 67, 12, 12, 0, 1, 111, 109, 2, 115, 116, 12, 0, 1, 117, 2, 105, 0, 1, 117, 2, 115, 116, 121, 114, 12, 0, 1, 117, 98, 2, 115, 12, 12, 0, 1, 121, 2, 115, 116, 97, 116, 12, 0, 1, 121, 98, 2, 101, 108, 105, 103, 0, 1, 121, 108, 0, 1, 166, 195, 114, 2, 115, 101, 108, 0, 1, 184, 195, 2, 115, 12, 12, 0, 1, 184, 195, 100, 2, 12, 0, 8, 117, 2, 12, 12, 0, 100, 1, 17, 65, 0, 100, 1, 17, 65, 2, 17, 65, 12, 0, 101, 1, 97, 2, 108, 3, 84, 13, 0, 105, 1, 17, 65, 2, 115, 107, 3, 84, 37, 0, 4, 100, 1, 101, 109, 2, 101, 108, 101, 3, 84, 70, 0, 100, 1, 117, 2, 97, 110, 110, 0, 100, 1, 117, 2, 195, 184, 12, 0, 100, 1, 117, 103, 2, 12, 12, 0, 100, 1, 117, 107, 115, 2, 117, 12, 0, 100, 1, 117, 108, 2, 111, 118, 0, 100, 1, 121, 108, 2, 195, 166, 109, 112, 0, 115, 1, 17, 65, 2, 195, 166, 116, 3, 84, 87, 0, 4, 101, 1, 17, 65, 2, 32, 3, 84, 106, 0, 101, 1, 97, 2, 17, 67, 114, 0, 101, 1, 121, 0, 101, 1, 121, 98, 100, 110, 105, 0, 101, 1, 166, 195, 2, 108, 12, 0, 101, 1, 121, 115, 2, 110, 103, 3, 84, 107, 0, 101, 114, 1, 121, 2, 32, 3, 84, 112, 0, 4, 115, 1, 17, 65, 2, 101, 108, 3, 87, 0, 115, 1, 97, 108, 112, 0, 115, 1, 97, 112, 115, 2, 101, 114, 0, 115, 1, 97, 114, 107, 0, 115, 1, 97, 116, 115, 0, 115, 1, 101, 114, 102, 108, 0, 115, 1, 105, 104, 0, 115, 1, 105, 104, 2, 101, 0, 115, 1, 105, 112, 0, 115, 1, 105, 114, 0, 115, 1, 117, 109, 115, 0, 115, 1, 117, 112, 0, 115, 1, 117, 114, 116, 115, 0, 115, 1, 117, 116, 2, 101, 0, 115, 1, 117, 116, 115, 0, 115, 1, 121, 0, 115, 1, 105, 116, 2, 110, 111, 107, 3, 87, 6, 0, 115, 101, 108, 1, 117, 108, 112, 3, 87, 59, 0, 101, 1, 114, 166, 195, 103, 3, 112, 0, 7, 6, 101, 0, 4, 1, 99, 97, 102, 114, 101, 116, 110, 105, 3, 0, 4, 1, 99, 97, 112, 2, 109, 97, 107, 101, 114, 3, 0, 4, 1, 99, 97, 112, 114, 111, 116, 111, 109, 3, 0, 4, 1, 99, 101, 101, 108, 102, 3, 0, 4, 1, 99, 105, 112, 115, 111, 104, 2, 32, 3, 0, 4, 1, 99, 105, 116, 102, 111, 115, 3, 0, 4, 1, 99, 105, 117, 106, 3, 0, 4, 1, 99, 105, 118, 114, 101, 115, 2, 102, 97, 103, 3, 0, 4, 1, 99, 105, 118, 114, 101, 115, 2, 109, 101, 100, 3, 0, 4, 1, 99, 105, 118, 114, 101, 115, 2, 115, 101, 107, 116, 111, 114, 3, 0, 4, 1, 99, 105, 118, 114, 101, 115, 2, 115, 116, 97, 116, 105, 111, 110, 3, 0, 4, 1, 99, 105, 118, 114, 101, 115, 2, 121, 100, 101, 108, 115, 101, 3, 0, 4, 1, 99, 110, 97, 108, 101, 101, 114, 102, 3, 0, 4, 1, 99, 110, 101, 112, 3, 0, 4, 1, 99, 110, 101, 118, 111, 114, 112, 3, 0, 4, 1, 99, 117, 97, 115, 3, 0, 4, 1, 99, 121, 111, 106, 3, 0, 4, 1, 105, 112, 117, 111, 114, 103, 3, 0, 4, 1, 105, 114, 98, 2, 102, 3, 0, 4, 1, 108, 108, 2, 100, 101, 3, 0, 4, 1, 116, 115, 97, 116, 117, 97, 98, 2, 110, 3, 0, 4, 8, 99, 105, 102, 102, 111, 2, 32, 3, 0, 4, 8, 105, 110, 3, 0, 4, 8, 105, 110, 97, 106, 3, 0, 8, 105, 116, 114, 97, 3, 0, 1, 110, 114, 2, 100, 12, 3, 4, 36, 0, 1, 115, 2, 114, 118, 105, 99, 101, 101, 102, 116, 101, 114, 115, 121, 110, 3, 6, 13, 0, 8, 114, 114, 97, 2, 115, 116, 3, 6, 35, 0, 4, 106, 1, 105, 103, 121, 104, 2, 110, 101, 3, 6, 35, 57, 0, 106, 1, 108, 97, 103, 0, 106, 8, 98, 101, 108, 112, 2, 101, 114, 0, 4, 1, 99, 101, 100, 2, 109, 98, 101, 114, 3, 6, 36, 0, 1, 99, 114, 101, 109, 2, 100, 101, 115, 0, 1, 100, 111, 98, 2, 103, 97, 0, 1, 100, 117, 116, 115, 2, 114, 101, 0, 1, 107, 115, 111, 109, 0, 1, 107, 115, 165, 195, 109, 2, 32, 0, 1, 108, 97, 100, 103, 97, 109, 2, 110, 0, 1, 108, 108, 97, 2, 103, 114, 111, 0, 1, 109, 97, 110, 116, 101, 105, 118, 2, 115, 101, 114, 0, 1, 109, 103, 114, 111, 98, 2, 115, 116, 101, 114, 0, 1, 109, 105, 107, 114, 97, 2, 100, 101, 115, 0, 1, 109, 114, 117, 111, 103, 0, 1, 110, 97, 118, 105, 100, 2, 115, 101, 114, 0, 1, 110, 101, 118, 2, 100, 105, 103, 0, 1, 110, 105, 107, 2, 115, 0, 1, 110, 110, 97, 118, 97, 104, 2, 115, 101, 114, 0, 1, 110, 114, 117, 116, 0, 1, 112, 117, 111, 116, 0, 1, 114, 97, 108, 2, 100, 111, 0, 1, 114, 107, 115, 105, 100, 2, 116, 12, 0, 1, 114, 116, 115, 107, 101, 2, 109, 0, 1, 114, 117, 114, 111, 102, 2, 110, 101, 0, 1, 114, 121, 116, 115, 2, 110, 0, 1, 115, 101, 114, 2, 114, 118, 101, 0, 1, 116, 101, 105, 114, 97, 118, 0, 1, 116, 105, 109, 111, 107, 0, 1, 116, 111, 114, 112, 2, 115, 101, 0, 1, 116, 112, 101, 115, 2, 109, 98, 101, 114, 0, 1, 116, 115, 107, 101, 2, 114, 110, 0, 1, 118, 111, 110, 2, 109, 98, 101, 114, 0, 8, 98, 100, 184, 195, 114, 2, 100, 101, 0, 8, 98, 115, 97, 2, 115, 116, 0, 8, 100, 105, 0, 8, 100, 105, 118, 105, 100, 2, 110, 116, 101, 0, 8, 100, 111, 114, 2, 111, 0, 8, 102, 105, 110, 97, 109, 2, 115, 116, 0, 8, 103, 101, 114, 2, 115, 116, 0, 8, 108, 101, 2, 118, 0, 8, 108, 101, 99, 2, 98, 101, 114, 0, 8, 108, 108, 111, 107, 2, 103, 97, 0, 8, 108, 111, 109, 2, 115, 116, 0, 8, 109, 97, 114, 107, 97, 115, 2, 110, 116, 101, 0, 8, 109, 97, 116, 115, 101, 116, 2, 110, 116, 101, 0, 8, 109, 105, 2, 110, 115, 12, 0, 8, 109, 105, 103, 101, 114, 2, 110, 116, 101, 0, 8, 110, 103, 97, 109, 2, 116, 0, 8, 112, 114, 111, 116, 2, 100, 111, 0, 8, 114, 105, 2, 110, 101, 0, 8, 115, 121, 102, 109, 101, 2, 109, 0, 8, 116, 97, 107, 2, 100, 101, 114, 0, 8, 116, 110, 101, 114, 97, 112, 2, 115, 0, 8, 116, 111, 114, 112, 2, 115, 116, 0, 8, 116, 116, 97, 2, 115, 116, 0, 103, 1, 116, 115, 101, 98, 2, 32, 0, 103, 1, 116, 115, 101, 98, 2, 101, 116, 32, 0, 115, 1, 99, 99, 117, 0, 101, 2, 114, 3, 6, 36, 12, 0, 101, 1, 116, 105, 109, 111, 107, 2, 110, 3, 6, 36, 13, 0, 114, 1, 98, 105, 2, 105, 97, 12, 3, 6, 36, 34, 0, 4, 110, 101, 1, 108, 114, 111, 102, 3, 6, 36, 50, 13, 0, 110, 101, 1, 114, 117, 2, 32, 116, 97, 110, 107, 101, 114, 0, 4, 110, 101, 1, 108, 114, 97, 109, 3, 6, 36, 50, 106, 0, 110, 101, 1, 109, 114, 111, 102, 32, 116, 97, 0, 110, 101, 8, 108, 101, 104, 0, 103, 8, 108, 108, 111, 107, 2, 101, 3, 6, 36, 57, 0, 4, 109, 1, 10, 2, 32, 28, 33, 12, 3, 6, 36, 63, 0, 109, 1, 10, 2, 101, 114, 28, 33, 12, 0, 109, 1, 10, 2, 101, 116, 28, 33, 12, 0, 109, 1, 10, 2, 115, 28, 33, 12, 0, 100, 1, 108, 111, 116, 2, 111, 3, 6, 36, 70, 0, 100, 105, 101, 1, 109, 3, 6, 36, 70, 57, 106, 0, 100, 105, 101, 114, 1, 109, 3, 6, 36, 70, 57, 112, 0, 100, 101, 110, 1, 110, 114, 111, 102, 3, 6, 36, 84, 106, 50, 0, 115, 116, 101, 114, 1, 107, 114, 111, 3, 6, 36, 87, 47, 112, 0, 115, 101, 1, 10, 2, 28, 33, 3, 6, 36, 87, 106, 0, 115, 101, 1, 10, 2, 114, 28, 33, 3, 6, 36, 87, 112, 0, 115, 115, 105, 111, 110, 101, 108, 1, 102, 111, 114, 112, 3, 6, 36, 89, 39, 50, 36, 55, 0, 101, 1, 108, 104, 116, 97, 107, 2, 110, 3, 6, 37, 12, 0, 101, 102, 101, 1, 107, 3, 6, 37, 12, 81, 0, 97, 117, 3, 6, 39, 0, 4, 1, 98, 101, 108, 2, 110, 100, 105, 103, 3, 6, 107, 0, 1, 98, 101, 114, 2, 107, 107, 97, 0, 1, 99, 98, 97, 2, 115, 0, 1, 99, 101, 114, 2, 115, 0, 1, 99, 111, 114, 112, 2, 115, 0, 1, 99, 120, 101, 2, 115, 0, 1, 100, 114, 97, 2, 110, 110, 101, 114, 0, 1, 107, 115, 117, 109, 2, 116, 12, 0, 1, 108, 97, 112, 2, 114, 109, 111, 0, 1, 108, 97, 118, 2, 110, 99, 105, 97, 0, 1, 110, 97, 118, 2, 115, 115, 97, 0, 1, 112, 97, 100, 117, 98, 2, 115, 116, 0, 1, 115, 115, 97, 107, 2, 116, 116, 101, 0, 1, 115, 117, 109, 2, 101, 116, 0, 1, 115, 117, 109, 2, 117, 109, 0, 1, 116, 107, 110, 97, 115, 2, 108, 109, 115, 105, 108, 100, 0, 1, 118, 100, 114, 111, 110, 2, 115, 116, 0, 1, 118, 100, 121, 115, 2, 115, 116, 0, 1, 118, 108, 121, 115, 2, 115, 116, 101, 114, 0, 1, 122, 97, 103, 2, 108, 108, 101, 0, 8, 99, 99, 97, 2, 112, 116, 0, 8, 99, 101, 114, 2, 112, 116, 0, 8, 99, 110, 105, 2, 115, 116, 0, 8, 99, 110, 111, 107, 2, 112, 116, 0, 8, 99, 110, 111, 107, 2, 114, 110, 0, 8, 102, 101, 100, 2, 107, 116, 0, 8, 102, 102, 97, 2, 107, 116, 0, 8, 102, 102, 101, 2, 107, 116, 32, 0, 8, 102, 110, 111, 107, 2, 107, 116, 0, 8, 102, 110, 111, 107, 2, 116, 116, 105, 0, 8, 102, 114, 101, 112, 2, 107, 116, 0, 8, 102, 166, 195, 114, 112, 2, 107, 116, 0, 8, 106, 98, 111, 2, 107, 116, 0, 8, 106, 98, 117, 115, 2, 107, 116, 0, 8, 106, 111, 114, 112, 2, 107, 116, 0, 8, 107, 97, 114, 2, 116, 12, 0, 8, 108, 97, 105, 100, 2, 107, 116, 0, 8, 108, 102, 101, 114, 2, 107, 115, 0, 8, 108, 105, 100, 2, 109, 109, 97, 0, 8, 108, 108, 97, 98, 2, 116, 21, 0, 8, 108, 108, 97, 98, 32, 110, 101, 2, 116, 0, 8, 108, 108, 97, 98, 32, 114, 111, 118, 2, 116, 0, 8, 108, 108, 97, 98, 32, 115, 101, 100, 110, 101, 104, 2, 116, 0, 8, 108, 108, 97, 98, 32, 115, 101, 114, 101, 100, 2, 116, 0, 8, 108, 108, 97, 98, 32, 115, 101, 114, 101, 106, 2, 116, 0, 8, 108, 108, 97, 98, 32, 115, 101, 114, 111, 118, 2, 116, 0, 8, 108, 108, 97, 98, 32, 115, 110, 97, 104, 2, 116, 0, 8, 108, 108, 101, 116, 110, 105, 2, 107, 116, 0, 8, 108, 108, 111, 107, 2, 107, 116, 32, 0, 8, 108, 108, 111, 107, 2, 107, 116, 101, 0, 8, 108, 111, 105, 99, 111, 115, 2, 107, 116, 0, 8, 108, 111, 105, 100, 105, 2, 107, 116, 0, 8, 108, 112, 109, 111, 107, 2, 107, 115, 0, 8, 109, 101, 115, 2, 115, 116, 101, 114, 0, 8, 109, 103, 114, 111, 98, 2, 115, 116, 0, 8, 112, 115, 97, 2, 107, 116, 0, 8, 112, 115, 101, 100, 2, 107, 116, 0, 8, 112, 115, 101, 114, 2, 107, 116, 0, 8, 112, 115, 111, 114, 112, 2, 107, 116, 0, 8, 112, 115, 117, 115, 2, 107, 116, 0, 8, 114, 105, 2, 110, 101, 12, 0, 8, 115, 101, 114, 112, 2, 110, 110, 105, 110, 103, 0, 8, 115, 107, 101, 2, 109, 112, 101, 108, 0, 8, 115, 110, 105, 2, 107, 116, 0, 8, 116, 105, 107, 114, 97, 2, 107, 116, 0, 8, 116, 110, 97, 2, 110, 110, 101, 0, 8, 116, 111, 114, 103, 2, 115, 0, 8, 105, 110, 2, 99, 101, 3, 6, 107, 12, 0, 4, 114, 1, 98, 111, 114, 2, 116, 97, 3, 6, 107, 34, 0, 114, 1, 112, 117, 115, 2, 108, 97, 116, 105, 118, 0, 122, 1, 112, 97, 114, 116, 3, 6, 107, 47, 87, 0, 110, 100, 1, 107, 114, 101, 2, 101, 32, 3, 6, 107, 50, 0, 110, 101, 1, 114, 105, 115, 2, 12, 3, 6, 107, 50, 13, 0, 110, 100, 101, 1, 118, 97, 108, 2, 108, 3, 6, 107, 50, 106, 0, 105, 108, 108, 1, 118, 101, 114, 2, 101, 3, 6, 107, 55, 57, 0, 108, 112, 104, 105, 1, 100, 97, 108, 105, 104, 112, 2, 97, 3, 6, 107, 55, 81, 57, 0, 115, 101, 1, 114, 10, 2, 28, 33, 3, 6, 107, 87, 106, 0, 115, 101, 1, 114, 10, 2, 114, 28, 33, 3, 6, 107, 87, 112, 0, 115, 104, 1, 100, 97, 108, 103, 110, 97, 98, 3, 6, 107, 89, 0, 1, 106, 102, 118, 108, 97, 104, 2, 114, 100, 115, 3, 6, 108, 0, 4, 1, 114, 97, 109, 2, 110, 103, 3, 6, 109, 0, 1, 114, 105, 107, 105, 116, 115, 2, 110, 100, 100, 114, 101, 110, 103, 0, 1, 114, 112, 121, 99, 2, 115, 0, 1, 114, 114, 111, 102, 2, 116, 110, 105, 110, 103, 12, 0, 8, 114, 103, 101, 114, 2, 115, 0, 8, 114, 103, 110, 111, 107, 2, 115, 0, 8, 114, 114, 111, 107, 2, 107, 116, 0, 115, 115, 101, 1, 114, 10, 2, 28, 33, 3, 6, 109, 87, 106, 0, 115, 115, 101, 1, 114, 10, 2, 114, 28, 33, 3, 6, 109, 87, 112, 0, 1, 118, 111, 114, 112, 2, 110, 99, 101, 3, 6, 110, 12, 0, 117, 116, 8, 112, 97, 114, 101, 116, 3, 6, 116, 58, 70, 0, 115, 115, 101, 1, 104, 99, 10, 2, 28, 33, 3, 7, 107, 87, 0, 115, 115, 101, 1, 10, 2, 28, 33, 3, 7, 107, 87, 106, 0, 115, 115, 101, 1, 10, 2, 114, 28, 33, 3, 7, 107, 87, 112, 0, 8, 108, 108, 105, 116, 115, 2, 98, 101, 110, 3, 8, 6, 36, 0, 4, 1, 18, 73, 2, 32, 3, 13, 0, 1, 98, 98, 111, 100, 2, 108, 0, 1, 99, 2, 32, 0, 1, 99, 97, 112, 114, 111, 116, 111, 109, 2, 110, 0, 1, 100, 2, 115, 32, 0, 1, 100, 101, 2, 45, 0, 1, 100, 101, 2, 114, 0, 1, 100, 111, 103, 0, 1, 100, 111, 107, 0, 1, 103, 121, 115, 2, 12, 0, 1, 108, 97, 118, 2, 114, 105, 12, 12, 0, 1, 108, 109, 97, 0, 1, 108, 111, 107, 2, 17, 67, 0, 1, 108, 114, 101, 112, 0, 1, 110, 97, 2, 114, 0, 1, 114, 2, 115, 32, 0, 1, 114, 117, 2, 110, 101, 0, 1, 114, 121, 2, 12, 0, 1, 115, 2, 32, 0, 1, 115, 110, 111, 107, 2, 107, 118, 0, 1, 115, 117, 108, 2, 12, 12, 0, 1, 116, 2, 32, 0, 1, 116, 114, 111, 108, 0, 1, 116, 115, 101, 104, 2, 110, 12, 0, 1, 116, 115, 114, 97, 99, 2, 110, 0, 1, 116, 115, 114, 97, 107, 2, 110, 0, 1, 118, 114, 101, 115, 0, 2, 106, 117, 108, 12, 0, 8, 110, 101, 0, 101, 2, 106, 101, 114, 3, 13, 35, 0, 4, 97, 117, 2, 107, 116, 105, 3, 13, 35, 40, 0, 97, 117, 2, 116, 111, 0, 4, 110, 100, 101, 1, 10, 2, 32, 3, 13, 50, 13, 0, 110, 101, 1, 21, 2, 32, 0, 110, 101, 1, 103, 103, 21, 2, 32, 14, 128, 128, 132, 0, 110, 101, 115, 1, 21, 2, 32, 3, 13, 50, 13, 87, 0, 106, 2, 97, 103, 116, 3, 13, 57, 0, 100, 1, 114, 114, 2, 17, 65, 3, 13, 70, 0, 4, 103, 1, 108, 2, 97, 110, 12, 12, 3, 13, 79, 0, 103, 1, 108, 101, 100, 2, 17, 65, 0, 103, 1, 116, 115, 2, 195, 165, 0, 103, 2, 97, 102, 102, 101, 108, 0, 100, 1, 114, 114, 3, 13, 84, 0, 100, 101, 116, 1, 118, 111, 2, 32, 3, 13, 84, 106, 70, 0, 110, 1, 100, 17, 65, 2, 21, 3, 14, 50, 0, 103, 1, 108, 101, 114, 2, 105, 111, 110, 3, 20, 13, 79, 0, 120, 99, 104, 97, 110, 103, 101, 3, 21, 0, 4, 1, 114, 2, 110, 100, 116, 3, 35, 0, 2, 103, 102, 105, 0, 2, 103, 115, 111, 116, 0, 8, 114, 116, 2, 116, 116, 101, 110, 0, 103, 101, 116, 8, 2, 32, 3, 35, 12, 57, 13, 84, 0, 110, 100, 101, 1, 114, 118, 184, 195, 114, 2, 32, 3, 35, 20, 50, 13, 0, 110, 100, 101, 114, 1, 114, 118, 184, 195, 114, 2, 32, 3, 35, 20, 50, 112, 0, 4, 1, 103, 2, 106, 115, 3, 35, 57, 0, 103, 1, 18, 71, 2, 101, 0, 103, 1, 18, 73, 0, 103, 1, 104, 2, 108, 101, 0, 103, 1, 107, 2, 108, 101, 0, 103, 1, 108, 2, 101, 12, 0, 103, 1, 108, 98, 0, 103, 1, 108, 101, 2, 12, 0, 103, 1, 108, 115, 98, 97, 107, 115, 108, 101, 115, 0, 103, 1, 110, 115, 2, 108, 0, 103, 1, 112, 0, 103, 1, 114, 107, 115, 0, 103, 1, 114, 116, 2, 101, 32, 0, 103, 1, 114, 116, 2, 101, 100, 101, 32, 0, 103, 1, 114, 116, 2, 101, 110, 32, 0, 103, 1, 114, 116, 2, 101, 114, 32, 0, 103, 1, 114, 116, 2, 101, 115, 32, 0, 103, 1, 114, 116, 115, 0, 103, 1, 115, 2, 108, 0, 103, 1, 116, 2, 108, 0, 103, 2, 110, 0, 103, 2, 114, 195, 184, 100, 0, 103, 8, 98, 2, 32, 0, 105, 1, 104, 2, 100, 101, 108, 0, 105, 1, 115, 2, 115, 0, 105, 1, 115, 2, 115, 109, 111, 108, 0, 105, 1, 116, 115, 2, 110, 25, 0, 105, 8, 104, 2, 100, 105, 0, 105, 8, 104, 2, 108, 32, 0, 106, 1, 114, 2, 115, 0, 106, 1, 114, 100, 2, 12, 0, 106, 1, 118, 109, 101, 106, 104, 0, 106, 2, 12, 12, 0, 107, 1, 115, 2, 115, 116, 101, 110, 0, 121, 1, 109, 2, 101, 114, 0, 4, 103, 101, 110, 100, 101, 1, 108, 2, 32, 98, 195, 184, 114, 110, 3, 35, 57, 13, 50, 13, 0, 103, 101, 110, 100, 101, 1, 108, 2, 32, 108, 101, 116, 0, 103, 101, 109, 1, 108, 98, 2, 105, 100, 3, 35, 57, 13, 63, 0, 105, 110, 115, 116, 101, 105, 110, 3, 35, 57, 50, 87, 47, 35, 57, 50, 0, 105, 110, 100, 104, 111, 118, 101, 110, 3, 35, 57, 50, 105, 6, 39, 12, 81, 13, 50, 0, 4, 106, 114, 1, 118, 2, 101, 32, 3, 35, 57, 51, 0, 106, 114, 1, 118, 2, 101, 114, 32, 0, 103, 108, 1, 110, 3, 35, 57, 55, 0, 105, 108, 101, 101, 110, 3, 35, 57, 55, 6, 37, 12, 50, 0, 121, 101, 108, 105, 110, 101, 114, 3, 35, 57, 55, 35, 57, 50, 112, 0, 105, 103, 101, 114, 3, 35, 57, 79, 112, 0, 105, 102, 102, 101, 108, 3, 35, 57, 81, 106, 55, 0, 105, 115, 101, 110, 104, 111, 119, 101, 114, 3, 35, 57, 87, 13, 50, 105, 110, 40, 112, 0, 106, 101, 114, 2, 17, 67, 3, 35, 57, 112, 0, 4, 110, 1, 112, 2, 115, 105, 111, 110, 3, 35, 66, 0, 110, 1, 115, 115, 101, 114, 2, 116, 105, 109, 101, 110, 116, 0, 110, 1, 116, 101, 112, 109, 111, 2, 99, 101, 0, 110, 2, 116, 114, 195, 169, 0, 110, 8, 2, 116, 114, 101, 0, 110, 103, 97, 103, 2, 101, 3, 35, 66, 79, 108, 89, 0, 4, 3, 36, 0, 1, 17, 67, 2, 18, 67, 18, 76, 0, 1, 17, 67, 2, 100, 17, 65, 0, 1, 18, 68, 2, 18, 67, 18, 69, 0, 1, 18, 73, 2, 103, 116, 0, 1, 18, 74, 2, 100, 101, 0, 1, 18, 74, 2, 116, 0, 1, 98, 2, 114, 101, 116, 12, 0, 1, 98, 2, 114, 105, 103, 0, 1, 98, 114, 111, 102, 0, 1, 104, 2, 100, 100, 0, 1, 104, 2, 110, 32, 12, 0, 1, 104, 99, 97, 109, 112, 97, 112, 0, 1, 107, 115, 100, 184, 195, 114, 103, 0, 1, 107, 115, 101, 98, 184, 195, 116, 115, 0, 1, 107, 115, 101, 100, 121, 114, 103, 0, 1, 107, 115, 101, 103, 117, 102, 0, 1, 107, 115, 101, 108, 165, 195, 109, 0, 1, 107, 115, 101, 115, 105, 112, 115, 0, 1, 107, 115, 101, 116, 0, 1, 107, 115, 108, 117, 104, 0, 1, 107, 115, 110, 97, 107, 0, 1, 107, 115, 114, 117, 109, 0, 1, 107, 115, 116, 114, 101, 115, 115, 101, 100, 0, 1, 107, 115, 184, 195, 114, 116, 115, 0, 1, 108, 2, 118, 101, 0, 1, 108, 101, 2, 118, 0, 1, 108, 102, 2, 100, 101, 12, 0, 1, 108, 111, 112, 2, 114, 101, 12, 0, 1, 109, 2, 100, 105, 12, 0, 1, 110, 2, 100, 103, 97, 110, 103, 0, 1, 110, 2, 100, 115, 108, 97, 103, 0, 1, 110, 2, 100, 115, 116, 105, 103, 0, 1, 110, 2, 100, 115, 195, 166, 116, 0, 1, 110, 101, 109, 2, 100, 0, 1, 110, 107, 2, 98, 0, 1, 110, 115, 2, 25, 12, 0, 1, 114, 2, 104, 97, 98, 105, 108, 0, 1, 114, 2, 109, 18, 69, 0, 1, 114, 2, 115, 116, 18, 76, 0, 1, 114, 2, 116, 97, 98, 0, 1, 114, 2, 116, 97, 114, 100, 0, 1, 114, 2, 116, 101, 110, 116, 105, 111, 110, 0, 1, 114, 2, 116, 105, 0, 1, 114, 2, 116, 111, 114, 0, 1, 114, 2, 116, 111, 117, 0, 1, 114, 2, 116, 114, 97, 110, 0, 1, 114, 2, 116, 114, 111, 0, 1, 114, 2, 116, 114, 195, 166, 0, 1, 114, 2, 116, 115, 105, 110, 97, 0, 1, 114, 2, 116, 117, 114, 0, 1, 114, 107, 115, 2, 118, 0, 1, 114, 111, 101, 116, 2, 116, 0, 1, 114, 116, 2, 109, 105, 108, 101, 0, 1, 115, 100, 110, 105, 0, 1, 115, 100, 110, 105, 2, 114, 32, 0, 1, 115, 100, 117, 114, 111, 102, 0, 1, 115, 101, 100, 111, 103, 0, 1, 115, 102, 97, 2, 32, 0, 1, 115, 102, 97, 2, 116, 32, 12, 0, 1, 115, 108, 105, 116, 0, 1, 115, 110, 97, 108, 101, 118, 2, 116, 0, 1, 115, 114, 101, 116, 102, 101, 0, 1, 115, 114, 101, 118, 111, 2, 32, 0, 1, 115, 116, 114, 111, 98, 2, 12, 0, 1, 116, 101, 108, 108, 105, 109, 97, 107, 0, 1, 116, 101, 116, 114, 117, 0, 1, 116, 110, 101, 103, 114, 111, 109, 0, 1, 116, 115, 101, 106, 184, 195, 2, 110, 12, 0, 1, 116, 115, 103, 97, 100, 100, 105, 109, 0, 1, 116, 115, 114, 101, 116, 101, 109, 2, 110, 0, 1, 116, 115, 114, 111, 107, 115, 2, 110, 0, 1, 116, 115, 114, 117, 109, 2, 110, 0, 1, 118, 109, 101, 106, 104, 0, 2, 100, 116, 0, 8, 100, 2, 115, 32, 0, 8, 107, 115, 2, 32, 0, 8, 107, 115, 2, 101, 114, 0, 8, 109, 2, 108, 32, 0, 8, 110, 115, 2, 114, 32, 0, 8, 112, 115, 2, 32, 0, 8, 114, 2, 110, 100, 121, 114, 12, 0, 8, 114, 116, 2, 12, 0, 8, 114, 116, 2, 116, 0, 8, 115, 100, 117, 2, 32, 12, 0, 8, 115, 100, 117, 2, 114, 32, 12, 0, 8, 115, 110, 97, 2, 12, 12, 0, 8, 116, 2, 32, 0, 8, 116, 115, 105, 0, 100, 1, 116, 115, 2, 100, 97, 0, 100, 1, 116, 115, 2, 102, 97, 0, 100, 1, 116, 115, 2, 109, 111, 0, 100, 1, 116, 115, 2, 115, 195, 184, 0, 103, 8, 116, 115, 2, 32, 0, 1, 98, 10, 2, 115, 21, 3, 36, 4, 0, 101, 1, 100, 105, 2, 108, 3, 36, 6, 107, 0, 1, 114, 2, 100, 17, 65, 3, 36, 12, 0, 4, 103, 101, 8, 2, 32, 3, 36, 12, 57, 13, 0, 103, 101, 8, 2, 98, 108, 97, 100, 0, 103, 101, 8, 2, 108, 195, 184, 118, 0, 103, 101, 8, 2, 116, 114, 195, 166, 0, 101, 8, 110, 115, 2, 100, 101, 32, 3, 36, 13, 0, 8, 115, 2, 32, 3, 36, 19, 0, 110, 100, 101, 1, 106, 102, 3, 36, 20, 50, 13, 0, 110, 100, 101, 114, 1, 106, 102, 3, 36, 20, 50, 112, 0, 114, 114, 105, 101, 114, 8, 112, 3, 36, 34, 37, 6, 36, 0, 101, 1, 98, 2, 100, 3, 36, 36, 0, 116, 97, 103, 101, 114, 101, 3, 36, 47, 108, 89, 6, 107, 12, 51, 0, 100, 107, 101, 114, 1, 110, 115, 3, 36, 49, 112, 0, 4, 110, 1, 99, 2, 116, 17, 67, 3, 36, 50, 0, 110, 1, 100, 17, 65, 2, 116, 0, 108, 108, 101, 118, 101, 3, 36, 55, 82, 13, 0, 4, 103, 1, 108, 114, 101, 100, 110, 117, 3, 36, 57, 0, 103, 1, 116, 115, 114, 101, 118, 111, 0, 103, 8, 118, 2, 32, 0, 103, 8, 118, 2, 101, 116, 32, 0, 106, 2, 97, 107, 117, 0, 103, 101, 110, 8, 2, 21, 3, 36, 57, 13, 50, 0, 4, 103, 1, 108, 2, 101, 110, 100, 97, 3, 36, 79, 0, 103, 1, 108, 2, 101, 114, 0, 103, 1, 108, 2, 101, 114, 101, 0, 103, 1, 108, 2, 105, 116, 105, 0, 103, 1, 109, 2, 97, 0, 103, 1, 112, 2, 97, 115, 117, 115, 0, 103, 2, 101, 118, 105, 110, 115, 116, 12, 0, 103, 101, 110, 100, 101, 8, 108, 2, 32, 3, 36, 79, 6, 107, 50, 70, 106, 0, 100, 101, 116, 1, 108, 2, 12, 3, 36, 84, 13, 47, 0, 101, 1, 114, 2, 108, 3, 36, 107, 0, 4, 1, 115, 115, 101, 106, 3, 37, 0, 8, 2, 32, 109, 97, 105, 108, 0, 8, 2, 32, 115, 112, 101, 97, 107, 0, 8, 100, 2, 32, 0, 97, 1, 108, 2, 115, 101, 0, 97, 1, 108, 2, 115, 105, 110, 103, 0, 121, 1, 17, 67, 2, 32, 0, 121, 1, 107, 0, 121, 1, 108, 108, 0, 121, 1, 110, 115, 105, 100, 0, 121, 1, 115, 100, 110, 105, 108, 0, 121, 1, 118, 114, 97, 104, 0, 121, 8, 110, 114, 97, 98, 0, 4, 97, 1, 104, 2, 108, 3, 37, 12, 0, 97, 1, 107, 2, 116, 111, 110, 0, 97, 1, 112, 2, 99, 111, 0, 97, 1, 116, 2, 109, 0, 97, 8, 112, 2, 107, 32, 0, 101, 1, 104, 115, 2, 108, 97, 0, 101, 1, 107, 2, 112, 101, 114, 0, 101, 1, 114, 102, 0, 101, 1, 114, 102, 2, 108, 97, 110, 0, 101, 1, 114, 103, 2, 110, 0, 101, 1, 119, 0, 101, 1, 119, 2, 107, 0, 101, 8, 108, 102, 2, 99, 101, 12, 0, 116, 111, 110, 8, 3, 37, 12, 47, 13, 50, 0, 97, 108, 8, 110, 3, 37, 12, 59, 0, 4, 101, 100, 1, 112, 115, 3, 37, 12, 70, 0, 101, 100, 1, 119, 116, 0, 101, 100, 8, 114, 2, 25, 0, 97, 99, 104, 8, 112, 3, 37, 12, 74, 0, 97, 103, 108, 101, 3, 37, 12, 79, 13, 55, 0, 4, 97, 115, 101, 1, 116, 112, 105, 114, 116, 115, 3, 37, 12, 87, 0, 101, 115, 101, 1, 104, 99, 0, 97, 115, 116, 8, 3, 37, 12, 87, 70, 0, 98, 97, 121, 3, 37, 69, 107, 57, 0, 97, 98, 111, 100, 121, 1, 112, 3, 37, 69, 112, 70, 37, 0, 100, 105, 101, 8, 2, 32, 3, 37, 70, 37, 0, 103, 101, 1, 108, 108, 111, 99, 3, 37, 73, 0, 118, 105, 101, 8, 116, 115, 3, 37, 82, 37, 0, 97, 115, 121, 3, 37, 87, 37, 0, 115, 112, 101, 97, 107, 3, 37, 87, 48, 37, 12, 49, 0, 97, 117, 1, 114, 3, 39, 0, 119, 1, 108, 2, 105, 115, 3, 40, 12, 0, 119, 1, 116, 115, 3, 57, 40, 0, 117, 103, 101, 110, 101, 3, 57, 40, 73, 6, 37, 12, 50, 0, 116, 1, 103, 111, 110, 2, 32, 3, 84, 0, 4, 1, 21, 2, 32, 12, 3, 106, 0, 1, 98, 97, 118, 104, 2, 104, 97, 114, 32, 0, 1, 98, 109, 111, 98, 2, 114, 21, 0, 1, 99, 121, 111, 106, 2, 115, 0, 1, 100, 101, 98, 0, 1, 100, 117, 0, 1, 100, 184, 195, 0, 1, 105, 114, 0, 1, 107, 107, 121, 2, 17, 67, 0, 1, 108, 98, 111, 98, 0, 1, 108, 98, 166, 195, 2, 103, 114, 195, 184, 100, 0, 1, 108, 98, 184, 195, 2, 109, 0, 1, 108, 101, 2, 118, 97, 116, 0, 1, 108, 101, 116, 0, 1, 108, 102, 97, 2, 118, 0, 1, 108, 112, 2, 109, 101, 110, 0, 1, 108, 117, 0, 1, 110, 2, 117, 110, 103, 101, 0, 1, 110, 21, 2, 100, 0, 1, 110, 115, 17, 65, 108, 2, 12, 0, 1, 110, 115, 105, 103, 2, 12, 0, 1, 110, 115, 105, 118, 2, 12, 0, 1, 110, 115, 107, 111, 118, 0, 1, 114, 2, 104, 0, 1, 114, 97, 112, 115, 0, 1, 114, 97, 118, 0, 1, 114, 100, 108, 166, 195, 2, 12, 0, 1, 114, 100, 114, 111, 0, 1, 114, 116, 110, 101, 2, 112, 114, 0, 1, 114, 166, 195, 2, 12, 0, 1, 116, 114, 184, 195, 107, 115, 2, 17, 67, 0, 1, 118, 97, 104, 0, 2, 106, 111, 98, 12, 0, 8, 97, 2, 32, 0, 8, 100, 2, 32, 103, 97, 117, 108, 108, 101, 0, 8, 100, 2, 32, 108, 97, 32, 0, 8, 110, 115, 105, 2, 12, 0, 1, 114, 17, 65, 2, 115, 32, 3, 106, 9, 0, 4, 106, 101, 114, 110, 1, 109, 3, 106, 57, 107, 34, 50, 0, 106, 101, 114, 110, 1, 118, 0, 4, 106, 1, 100, 110, 2, 111, 98, 3, 106, 73, 0, 106, 1, 109, 2, 111, 98, 0, 4, 103, 1, 107, 115, 105, 102, 3, 106, 79, 0, 103, 1, 108, 101, 116, 2, 114, 0, 103, 2, 97, 110, 103, 115, 0, 116, 1, 99, 105, 112, 115, 111, 104, 3, 106, 84, 0, 115, 1, 21, 2, 32, 24, 3, 106, 87, 0, 4, 1, 17, 67, 2, 17, 67, 11, 3, 107, 0, 1, 17, 67, 2, 18, 67, 0, 1, 18, 71, 2, 114, 0, 1, 18, 74, 2, 108, 0, 1, 98, 2, 114, 103, 12, 0, 1, 98, 117, 116, 2, 114, 107, 117, 0, 1, 106, 98, 111, 2, 107, 116, 105, 118, 0, 1, 107, 97, 114, 2, 116, 12, 0, 1, 108, 2, 18, 72, 0, 1, 108, 101, 2, 110, 100, 105, 103, 0, 1, 108, 101, 116, 2, 120, 0, 1, 108, 111, 107, 2, 115, 116, 0, 1, 108, 115, 2, 116, 12, 12, 0, 1, 110, 101, 2, 109, 0, 1, 110, 101, 2, 114, 103, 105, 0, 1, 110, 115, 2, 114, 112, 0, 1, 112, 115, 101, 114, 2, 107, 116, 97, 98, 101, 108, 0, 1, 114, 2, 17, 67, 11, 0, 1, 114, 2, 110, 103, 195, 184, 0, 1, 114, 2, 110, 115, 107, 114, 0, 1, 114, 2, 110, 115, 107, 117, 0, 1, 114, 2, 115, 116, 97, 117, 114, 97, 110, 116, 0, 1, 114, 98, 2, 118, 0, 1, 114, 100, 2, 118, 110, 0, 1, 114, 101, 100, 101, 108, 2, 118, 110, 101, 0, 1, 114, 103, 2, 116, 0, 1, 114, 112, 2, 109, 0, 1, 114, 112, 111, 2, 118, 0, 1, 114, 112, 115, 2, 100, 0, 1, 115, 2, 100, 100, 0, 1, 116, 2, 100, 0, 8, 106, 111, 114, 112, 2, 107, 116, 105, 108, 0, 8, 114, 101, 108, 108, 97, 2, 100, 101, 32, 0, 8, 114, 116, 2, 100, 0, 8, 114, 116, 2, 115, 0, 97, 1, 119, 115, 2, 116, 101, 114, 0, 97, 1, 119, 115, 2, 116, 114, 101, 0, 106, 1, 118, 2, 114, 0, 4, 1, 114, 112, 2, 115, 115, 101, 114, 101, 110, 100, 101, 3, 107, 6, 0, 1, 114, 116, 2, 109, 97, 0, 110, 100, 101, 1, 115, 112, 111, 3, 107, 10, 50, 13, 0, 110, 100, 1, 107, 2, 101, 32, 12, 3, 107, 20, 50, 0, 4, 110, 100, 101, 1, 118, 2, 12, 3, 107, 20, 50, 13, 0, 110, 100, 101, 1, 118, 110, 97, 2, 32, 0, 110, 100, 101, 1, 118, 110, 101, 104, 2, 32, 0, 110, 100, 101, 1, 118, 115, 2, 32, 0, 110, 100, 101, 1, 100, 108, 117, 102, 3, 107, 20, 50, 106, 0, 4, 110, 100, 101, 114, 1, 107, 2, 32, 3, 107, 20, 50, 112, 0, 110, 100, 101, 114, 1, 118, 2, 12, 0, 110, 100, 101, 114, 1, 118, 110, 97, 2, 32, 0, 110, 100, 101, 114, 1, 118, 110, 101, 104, 2, 32, 0, 114, 118, 101, 114, 1, 115, 101, 114, 2, 32, 101, 110, 3, 107, 34, 82, 6, 36, 34, 0, 116, 97, 108, 1, 109, 32, 121, 118, 97, 101, 104, 3, 107, 47, 106, 55, 0, 99, 104, 1, 116, 3, 107, 49, 0, 4, 110, 1, 99, 2, 116, 3, 107, 50, 0, 110, 1, 99, 2, 116, 17, 65, 0, 4, 110, 101, 1, 106, 116, 2, 12, 12, 3, 107, 50, 13, 0, 110, 101, 1, 114, 103, 2, 12, 0, 110, 100, 101, 1, 118, 2, 116, 116, 97, 3, 107, 50, 70, 6, 107, 0, 110, 100, 97, 1, 114, 98, 3, 107, 50, 70, 108, 0, 110, 103, 101, 1, 104, 101, 110, 111, 116, 115, 3, 107, 50, 73, 0, 110, 101, 114, 1, 106, 116, 3, 107, 50, 112, 0, 4, 97, 1, 114, 98, 2, 107, 3, 107, 57, 0, 97, 1, 114, 103, 2, 116, 0, 103, 1, 108, 114, 101, 118, 111, 0, 121, 1, 114, 0, 103, 101, 1, 108, 2, 109, 101, 3, 107, 57, 20, 13, 0, 4, 103, 101, 108, 1, 114, 3, 107, 57, 55, 0, 103, 108, 1, 114, 0, 109, 112, 105, 114, 101, 2, 32, 115, 116, 97, 116, 101, 3, 107, 63, 48, 35, 57, 106, 0, 105, 110, 116, 1, 116, 3, 107, 66, 0, 4, 97, 100, 1, 104, 3, 107, 70, 0, 100, 100, 1, 114, 98, 0, 4, 100, 100, 105, 101, 1, 114, 102, 3, 107, 70, 37, 0, 100, 100, 105, 101, 8, 0, 100, 100, 121, 1, 114, 102, 0, 100, 100, 105, 107, 101, 3, 107, 70, 49, 106, 0, 100, 97, 103, 1, 114, 102, 3, 107, 70, 108, 0, 4, 103, 1, 114, 2, 101, 114, 3, 107, 79, 0, 103, 1, 114, 97, 117, 116, 0, 103, 103, 121, 1, 112, 3, 107, 79, 37, 0, 103, 109, 97, 116, 105, 116, 1, 112, 3, 107, 79, 63, 108, 47, 6, 37, 47, 0, 100, 100, 1, 114, 3, 107, 84, 0, 100, 101, 116, 1, 116, 115, 2, 32, 3, 107, 84, 106, 47, 0, 100, 101, 116, 1, 114, 2, 32, 3, 107, 84, 106, 70, 0, 4, 99, 115, 116, 97, 99, 121, 3, 107, 87, 47, 108, 87, 37, 0, 99, 115, 116, 97, 115, 121, 0, 4, 1, 110, 115, 2, 114, 114, 101, 3, 109, 0, 1, 114, 2, 18, 67, 115, 0, 1, 114, 2, 18, 74, 115, 0, 1, 114, 2, 107, 116, 111, 0, 1, 114, 2, 109, 0, 1, 114, 2, 110, 100, 32, 0, 1, 114, 2, 110, 100, 101, 0, 1, 114, 2, 110, 103, 0, 1, 114, 2, 110, 115, 101, 0, 1, 114, 2, 110, 116, 101, 0, 1, 114, 2, 115, 116, 0, 1, 114, 2, 115, 116, 101, 0, 1, 114, 2, 116, 0, 1, 114, 2, 118, 108, 0, 1, 114, 2, 118, 110, 0, 1, 114, 18, 67, 2, 17, 67, 11, 0, 1, 114, 18, 72, 2, 109, 0, 1, 114, 98, 2, 18, 74, 0, 1, 114, 101, 98, 2, 116, 12, 12, 0, 1, 114, 102, 2, 108, 0, 1, 114, 102, 2, 109, 0, 1, 114, 102, 2, 109, 111, 118, 0, 1, 114, 103, 2, 108, 0, 1, 114, 103, 103, 97, 2, 115, 115, 111, 114, 0, 1, 114, 103, 110, 111, 107, 2, 115, 0, 1, 114, 105, 100, 2, 107, 116, 0, 1, 114, 112, 2, 17, 67, 11, 12, 0, 1, 114, 112, 2, 115, 12, 0, 1, 114, 112, 111, 2, 116, 12, 12, 0, 1, 114, 114, 111, 102, 2, 116, 12, 12, 0, 1, 114, 121, 114, 114, 97, 107, 2, 116, 12, 0, 2, 103, 97, 110, 115, 105, 103, 116, 0, 8, 114, 103, 101, 114, 2, 115, 115, 105, 118, 0, 100, 105, 118, 101, 1, 114, 116, 3, 109, 84, 82, 13, 0, 115, 115, 101, 1, 114, 21, 2, 114, 101, 28, 33, 3, 109, 87, 6, 36, 0, 2, 109, 98, 97, 108, 108, 3, 110, 0, 97, 114, 116, 1, 104, 3, 110, 12, 70, 0, 110, 1, 114, 2, 99, 101, 3, 110, 66, 0, 110, 116, 101, 110, 116, 101, 3, 110, 66, 47, 6, 110, 66, 47, 0, 97, 117, 120, 1, 114, 3, 111, 0, 4, 1, 99, 110, 97, 108, 101, 101, 114, 102, 2, 114, 3, 112, 0, 1, 108, 97, 109, 2, 114, 105, 0, 1, 114, 100, 2, 100, 101, 115, 32, 0, 1, 114, 100, 110, 2, 17, 65, 0, 1, 114, 100, 110, 97, 0, 1, 114, 111, 10, 2, 112, 108, 0, 1, 114, 111, 104, 0, 1, 114, 111, 116, 115, 0, 1, 114, 116, 97, 108, 107, 0, 1, 114, 116, 115, 110, 101, 118, 0, 1, 114, 121, 110, 2, 12, 0, 114, 1, 98, 17, 65, 10, 0, 114, 1, 108, 97, 109, 0, 114, 1, 108, 100, 105, 109, 0, 114, 1, 108, 108, 101, 0, 114, 1, 108, 165, 195, 109, 0, 114, 1, 110, 115, 17, 65, 108, 2, 12, 0, 114, 1, 110, 115, 105, 103, 2, 12, 0, 114, 1, 110, 115, 105, 118, 2, 12, 0, 114, 1, 112, 117, 115, 0, 114, 1, 115, 100, 117, 112, 2, 12, 0, 114, 1, 115, 117, 108, 2, 12, 0, 114, 8, 110, 115, 105, 2, 12, 0, 4, 110, 101, 1, 114, 21, 2, 32, 3, 112, 50, 13, 0, 110, 101, 1, 114, 103, 110, 105, 102, 0, 110, 101, 115, 1, 114, 21, 2, 32, 14, 128, 128, 132, 3, 112, 50, 13, 87, 0, 117, 1, 102, 101, 3, 112, 57, 0, 97, 114, 108, 8, 3, 116, 12, 59, 0, 97, 114, 112, 8, 3, 116, 12, 69, 0, 117, 1, 110, 3, 116, 40, 0, 117, 2, 114, 111, 3, 116, 58, 0, 117, 116, 1, 112, 97, 114, 101, 116, 3, 116, 58, 70, 0, 117, 115, 3, 116, 58, 87, 0, 7, 6, 102, 0, 1, 97, 2, 115, 116, 101, 100, 3, 0, 4, 1, 97, 2, 17, 65, 3, 58, 0, 1, 97, 2, 17, 67, 0, 4, 3, 81, 0, 1, 21, 2, 108, 97, 115, 107, 101, 0, 1, 97, 2, 97, 115, 105, 0, 1, 97, 2, 97, 116, 105, 115, 107, 0, 1, 97, 2, 105, 116, 0, 1, 97, 2, 111, 110, 0, 1, 97, 2, 111, 114, 0, 1, 97, 2, 114, 105, 107, 0, 1, 97, 2, 114, 111, 0, 1, 97, 2, 116, 101, 110, 0, 1, 97, 2, 116, 101, 115, 32, 0, 1, 97, 17, 67, 2, 17, 65, 0, 1, 97, 17, 67, 2, 116, 0, 1, 97, 100, 2, 110, 0, 1, 97, 103, 2, 108, 0, 1, 97, 107, 115, 0, 1, 97, 108, 2, 114, 101, 0, 1, 97, 114, 2, 102, 111, 114, 0, 1, 97, 114, 2, 102, 114, 0, 1, 97, 114, 2, 105, 107, 0, 1, 97, 114, 2, 108, 101, 0, 1, 97, 114, 103, 2, 17, 65, 0, 1, 97, 114, 105, 103, 0, 1, 97, 114, 116, 115, 0, 1, 97, 115, 2, 97, 114, 0, 1, 97, 116, 115, 2, 101, 0, 1, 97, 118, 2, 108, 0, 2, 106, 101, 100, 101, 114, 0, 2, 111, 108, 107, 0, 102, 0, 102, 1, 97, 2, 97, 98, 101, 108, 0, 102, 1, 97, 2, 97, 103, 101, 0, 102, 1, 97, 2, 101, 107, 116, 0, 102, 1, 97, 2, 101, 108, 0, 102, 1, 97, 2, 105, 99, 101, 114, 101, 0, 102, 1, 97, 2, 105, 110, 101, 0, 102, 1, 97, 2, 105, 110, 105, 116, 101, 116, 0, 102, 1, 97, 2, 105, 114, 109, 0, 102, 1, 97, 2, 117, 116, 97, 103, 101, 0, 102, 1, 97, 2, 195, 166, 114, 101, 0, 102, 1, 97, 106, 2, 97, 0, 102, 1, 97, 114, 2, 101, 0, 111, 114, 101, 8, 2, 100, 101, 32, 3, 81, 2, 6, 39, 34, 112, 0, 111, 114, 8, 2, 101, 32, 3, 81, 2, 39, 0, 4, 101, 1, 97, 99, 3, 81, 6, 36, 0, 195, 169, 1, 97, 99, 0, 111, 114, 8, 2, 117, 109, 3, 81, 6, 39, 34, 0, 195, 166, 114, 100, 105, 103, 1, 21, 3, 81, 6, 107, 34, 70, 37, 0, 114, 105, 116, 101, 115, 1, 32, 115, 101, 3, 81, 34, 37, 47, 0, 114, 97, 110, 107, 105, 101, 3, 81, 34, 108, 50, 49, 37, 0, 114, 97, 110, 195, 167, 111, 105, 115, 3, 81, 34, 110, 66, 87, 6, 58, 35, 0, 114, 101, 117, 100, 3, 81, 34, 112, 57, 47, 0, 101, 8, 2, 32, 3, 81, 36, 0, 101, 116, 116, 117, 99, 99, 105, 110, 101, 3, 81, 36, 47, 40, 85, 89, 6, 37, 12, 50, 13, 0, 105, 110, 108, 97, 121, 3, 81, 36, 50, 55, 37, 0, 105, 101, 108, 100, 3, 81, 37, 12, 59, 70, 0, 4, 105, 114, 101, 3, 81, 37, 12, 112, 0, 105, 114, 101, 111, 103, 0, 105, 114, 101, 110, 122, 101, 3, 81, 37, 51, 6, 108, 50, 87, 13, 0, 111, 98, 105, 1, 21, 3, 81, 39, 69, 6, 37, 0, 111, 117, 113, 117, 101, 116, 3, 81, 40, 49, 6, 36, 0, 114, 97, 110, 99, 101, 115, 99, 97, 3, 81, 51, 35, 50, 89, 6, 107, 87, 49, 108, 0, 108, 117, 115, 104, 3, 81, 55, 112, 89, 0, 195, 166, 114, 100, 105, 103, 1, 21, 21, 3, 81, 107, 34, 70, 37, 0, 97, 114, 97, 111, 3, 81, 110, 34, 110, 39, 0, 111, 117, 114, 8, 2, 32, 3, 81, 111, 12, 0, 111, 110, 116, 97, 105, 110, 101, 3, 81, 111, 66, 47, 6, 107, 12, 50, 0, 98, 105, 8, 3, 107, 81, 69, 37, 6, 35, 57, 0, 7, 6, 103, 0, 4, 1, 105, 100, 184, 195, 2, 116, 32, 3, 0, 4, 1, 105, 107, 2, 104, 111, 115, 116, 3, 0, 4, 1, 105, 116, 103, 2, 101, 114, 101, 3, 0, 4, 1, 108, 2, 17, 67, 3, 0, 4, 1, 108, 2, 116, 101, 32, 3, 0, 4, 1, 108, 97, 118, 2, 116, 3, 0, 4, 1, 111, 2, 101, 114, 110, 17, 65, 3, 0, 4, 1, 114, 117, 103, 2, 108, 101, 3, 0, 4, 1, 114, 184, 195, 2, 115, 3, 0, 4, 1, 117, 2, 108, 3, 0, 4, 1, 117, 100, 32, 110, 101, 3, 0, 4, 1, 117, 100, 101, 100, 101, 118, 115, 3, 0, 4, 1, 117, 100, 101, 115, 121, 108, 3, 0, 4, 1, 117, 100, 103, 97, 108, 102, 3, 0, 4, 1, 117, 100, 107, 115, 97, 109, 97, 100, 3, 0, 4, 1, 117, 100, 108, 106, 101, 115, 3, 0, 4, 1, 117, 100, 114, 101, 109, 108, 111, 3, 0, 4, 1, 117, 100, 114, 101, 109, 109, 97, 107, 3, 0, 4, 1, 117, 100, 115, 107, 111, 118, 3, 0, 4, 1, 117, 100, 116, 108, 101, 116, 3, 0, 4, 1, 117, 114, 3, 0, 4, 1, 117, 116, 114, 101, 104, 3, 0, 1, 121, 115, 3, 0, 4, 1, 97, 2, 97, 118, 101, 3, 6, 79, 0, 8, 97, 2, 97, 114, 0, 101, 110, 116, 1, 114, 101, 115, 3, 6, 87, 57, 108, 50, 47, 0, 4, 1, 111, 103, 3, 8, 0, 1, 111, 108, 0, 4, 1, 111, 108, 2, 111, 3, 8, 79, 0, 1, 111, 108, 98, 2, 115, 0, 105, 1, 10, 2, 115, 107, 28, 33, 3, 8, 79, 37, 0, 101, 115, 1, 114, 97, 112, 115, 97, 3, 8, 87, 0, 4, 1, 97, 114, 2, 101, 3, 12, 0, 1, 97, 115, 2, 115, 0, 1, 117, 2, 101, 0, 1, 117, 115, 0, 1, 97, 100, 100, 2, 115, 3, 12, 19, 0, 101, 1, 184, 195, 2, 12, 12, 12, 3, 12, 57, 13, 0, 101, 1, 184, 195, 109, 2, 108, 101, 110, 3, 12, 57, 36, 0, 4, 1, 97, 98, 2, 101, 3, 13, 0, 1, 97, 107, 2, 101, 0, 4, 101, 110, 1, 114, 2, 32, 3, 13, 50, 0, 101, 110, 1, 114, 2, 115, 32, 0, 1, 97, 98, 2, 105, 3, 15, 0, 4, 101, 111, 114, 103, 101, 3, 21, 0, 114, 97, 99, 101, 0, 114, 97, 104, 97, 109, 2, 32, 0, 114, 97, 104, 97, 109, 115, 2, 32, 0, 111, 110, 122, 97, 108, 101, 115, 3, 21, 101, 115, 0, 4, 1, 97, 98, 2, 116, 97, 108, 3, 40, 0, 1, 97, 104, 2, 108, 0, 1, 114, 2, 101, 114, 32, 0, 1, 114, 184, 195, 0, 1, 165, 195, 0, 1, 165, 195, 2, 101, 0, 1, 165, 195, 118, 2, 110, 0, 116, 1, 114, 117, 112, 115, 3, 47, 0, 116, 101, 1, 114, 117, 112, 115, 3, 47, 13, 0, 4, 1, 105, 107, 3, 49, 0, 1, 111, 98, 2, 115, 116, 0, 110, 1, 97, 112, 2, 105, 3, 50, 6, 0, 4, 110, 1, 97, 112, 2, 111, 110, 3, 50, 57, 0, 110, 1, 105, 2, 111, 0, 110, 1, 166, 195, 114, 112, 109, 105, 2, 101, 0, 4, 1, 17, 65, 2, 110, 3, 57, 0, 1, 97, 100, 2, 115, 32, 0, 1, 97, 104, 101, 98, 0, 1, 97, 108, 2, 110, 0, 1, 97, 115, 0, 1, 101, 2, 101, 110, 115, 107, 97, 98, 0, 1, 101, 2, 101, 110, 116, 108, 0, 1, 101, 18, 73, 0, 1, 101, 108, 98, 2, 97, 110, 115, 105, 103, 116, 0, 1, 101, 108, 98, 2, 102, 105, 0, 1, 101, 108, 98, 2, 115, 111, 116, 0, 1, 101, 110, 2, 32, 0, 1, 101, 110, 115, 0, 1, 101, 118, 2, 101, 110, 0, 1, 105, 109, 115, 0, 1, 108, 2, 32, 0, 1, 108, 2, 101, 110, 32, 0, 1, 108, 2, 101, 116, 32, 0, 1, 108, 2, 115, 0, 1, 108, 97, 2, 101, 0, 1, 108, 97, 118, 0, 1, 108, 97, 118, 2, 195, 165, 114, 0, 1, 108, 101, 2, 101, 32, 0, 1, 108, 101, 2, 101, 110, 101, 32, 0, 1, 108, 101, 2, 101, 110, 101, 115, 32, 0, 1, 108, 166, 195, 2, 101, 0, 1, 108, 184, 195, 2, 101, 0, 1, 121, 2, 101, 0, 1, 166, 195, 2, 101, 0, 1, 166, 195, 2, 101, 114, 110, 17, 65, 0, 1, 166, 195, 108, 2, 100, 111, 109, 0, 1, 166, 195, 108, 2, 102, 111, 108, 107, 0, 1, 166, 195, 108, 2, 109, 0, 1, 166, 195, 108, 2, 115, 195, 184, 115, 0, 1, 166, 195, 114, 112, 0, 1, 166, 195, 118, 107, 0, 1, 184, 195, 0, 1, 184, 195, 2, 110, 0, 2, 108, 101, 0, 8, 101, 2, 32, 0, 110, 1, 105, 115, 108, 101, 118, 3, 57, 50, 0, 114, 1, 97, 108, 2, 101, 3, 57, 51, 0, 101, 1, 101, 2, 114, 3, 57, 112, 0, 4, 1, 97, 98, 2, 105, 110, 3, 58, 0, 1, 97, 100, 2, 17, 67, 0, 1, 97, 114, 98, 0, 1, 97, 114, 100, 0, 1, 97, 114, 100, 2, 101, 110, 0, 1, 97, 114, 118, 0, 1, 97, 118, 2, 110, 0, 1, 111, 17, 67, 0, 1, 111, 108, 114, 111, 0, 1, 114, 2, 32, 0, 1, 114, 2, 101, 116, 32, 0, 1, 114, 101, 106, 2, 17, 65, 0, 1, 114, 101, 106, 2, 17, 67, 0, 1, 114, 166, 195, 106, 2, 101, 0, 8, 97, 114, 112, 0, 101, 114, 1, 114, 166, 195, 2, 108, 105, 103, 3, 58, 13, 0, 101, 114, 110, 101, 1, 114, 2, 32, 3, 58, 112, 50, 106, 0, 101, 114, 110, 101, 115, 1, 114, 2, 32, 3, 58, 112, 50, 106, 87, 0, 110, 1, 105, 115, 2, 101, 114, 3, 66, 0, 101, 110, 116, 108, 101, 109, 101, 110, 3, 70, 57, 107, 50, 47, 13, 55, 63, 107, 50, 0, 101, 110, 116, 108, 101, 109, 97, 110, 3, 70, 57, 107, 50, 47, 13, 55, 63, 108, 50, 0, 2, 105, 103, 111, 108, 111, 3, 73, 0, 101, 114, 97, 108, 100, 1, 122, 116, 105, 102, 3, 73, 6, 107, 34, 106, 59, 0, 105, 97, 110, 116, 115, 8, 3, 73, 35, 57, 108, 50, 47, 87, 0, 105, 8, 2, 110, 3, 73, 36, 0, 101, 114, 111, 110, 105, 109, 111, 3, 73, 36, 34, 6, 112, 50, 37, 63, 111, 12, 40, 0, 105, 110, 103, 101, 114, 8, 3, 73, 36, 50, 73, 112, 0, 4, 105, 8, 2, 110, 18, 69, 3, 73, 37, 0, 105, 8, 2, 110, 97, 0, 105, 117, 115, 101, 112, 112, 101, 3, 73, 37, 87, 6, 107, 48, 13, 0, 101, 114, 114, 121, 3, 73, 107, 34, 37, 0, 101, 114, 97, 108, 100, 3, 73, 107, 34, 106, 59, 0, 101, 114, 97, 108, 100, 105, 110, 101, 3, 73, 107, 34, 106, 59, 70, 37, 12, 50, 0, 101, 111, 102, 102, 3, 73, 107, 81, 0, 101, 111, 114, 103, 105, 97, 3, 73, 112, 12, 73, 57, 108, 0, 4, 3, 79, 0, 1, 17, 65, 2, 116, 32, 0, 1, 17, 65, 108, 2, 97, 0, 1, 97, 2, 110, 111, 115, 0, 1, 97, 100, 110, 97, 2, 116, 0, 1, 97, 108, 2, 116, 0, 1, 97, 114, 98, 2, 116, 0, 1, 97, 114, 100, 2, 111, 110, 0, 1, 97, 114, 100, 2, 116, 0, 1, 97, 114, 112, 2, 116, 0, 1, 97, 115, 2, 111, 0, 1, 101, 18, 73, 2, 116, 0, 1, 101, 114, 2, 105, 17, 65, 0, 1, 101, 114, 2, 105, 109, 101, 110, 116, 0, 1, 101, 116, 2, 111, 114, 105, 0, 1, 105, 2, 105, 0, 1, 108, 105, 112, 2, 114, 105, 109, 0, 1, 111, 2, 114, 97, 102, 0, 1, 111, 2, 114, 97, 109, 0, 1, 111, 98, 2, 111, 116, 97, 0, 1, 111, 108, 2, 97, 0, 1, 111, 108, 2, 102, 105, 108, 0, 1, 111, 114, 2, 97, 110, 0, 1, 111, 114, 2, 101, 115, 0, 1, 111, 114, 112, 2, 114, 0, 1, 111, 114, 114, 117, 115, 2, 97, 116, 0, 1, 111, 116, 2, 97, 0, 1, 111, 116, 2, 111, 0, 1, 111, 116, 2, 116, 0, 1, 111, 118, 2, 116, 0, 1, 111, 118, 2, 116, 101, 0, 1, 117, 2, 101, 110, 18, 66, 0, 1, 117, 2, 101, 110, 110, 0, 1, 117, 104, 2, 110, 105, 110, 103, 0, 1, 117, 109, 2, 110, 0, 1, 117, 114, 102, 2, 116, 0, 1, 121, 98, 2, 110, 0, 1, 121, 107, 115, 2, 110, 105, 0, 1, 121, 116, 2, 110, 105, 110, 103, 0, 1, 166, 195, 2, 110, 12, 0, 1, 166, 195, 114, 112, 2, 110, 97, 0, 1, 166, 195, 114, 112, 2, 116, 105, 103, 0, 1, 184, 195, 114, 2, 116, 101, 114, 0, 1, 184, 195, 115, 2, 97, 110, 103, 0, 2, 101, 110, 115, 116, 97, 110, 100, 12, 0, 2, 105, 118, 12, 0, 2, 108, 97, 115, 0, 2, 108, 101, 109, 0, 2, 114, 97, 110, 0, 2, 114, 111, 115, 115, 0, 2, 114, 117, 18, 71, 0, 2, 114, 195, 184, 110, 0, 2, 116, 101, 32, 0, 2, 121, 114, 111, 0, 2, 195, 165, 114, 100, 12, 12, 0, 8, 2, 108, 101, 100, 0, 8, 111, 98, 2, 97, 114, 116, 0, 8, 111, 98, 2, 101, 121, 0, 8, 111, 108, 2, 32, 0, 8, 111, 108, 2, 103, 0, 103, 1, 97, 2, 114, 101, 115, 0, 103, 1, 105, 0, 103, 1, 111, 0, 103, 1, 111, 108, 2, 101, 0, 103, 2, 101, 0, 104, 1, 102, 97, 2, 97, 0, 104, 2, 97, 110, 97, 0, 104, 2, 101, 116, 116, 111, 0, 4, 1, 97, 2, 117, 114, 107, 3, 79, 6, 0, 1, 111, 108, 2, 105, 0, 8, 101, 114, 2, 105, 115, 116, 0, 101, 114, 1, 21, 2, 28, 33, 3, 79, 6, 36, 34, 0, 4, 101, 110, 1, 111, 114, 101, 3, 79, 6, 36, 50, 0, 101, 110, 1, 111, 114, 116, 105, 110, 0, 101, 110, 1, 111, 114, 116, 115, 184, 195, 0, 105, 1, 101, 114, 2, 115, 116, 101, 114, 3, 79, 6, 37, 0, 97, 1, 111, 110, 111, 109, 2, 109, 3, 79, 6, 108, 0, 105, 1, 10, 2, 28, 33, 3, 79, 7, 37, 0, 114, 97, 110, 100, 101, 8, 2, 32, 3, 79, 34, 35, 50, 70, 106, 0, 114, 111, 115, 1, 32, 110, 101, 3, 79, 34, 39, 0, 114, 97, 100, 121, 3, 79, 34, 107, 57, 70, 37, 0, 114, 97, 110, 100, 112, 114, 105, 120, 3, 79, 34, 110, 66, 48, 34, 6, 37, 0, 114, 97, 102, 102, 105, 116, 105, 3, 79, 34, 110, 81, 6, 37, 47, 37, 0, 114, 117, 110, 103, 101, 8, 2, 32, 3, 79, 34, 112, 50, 73, 0, 114, 195, 184, 100, 1, 101, 108, 98, 166, 195, 3, 79, 34, 116, 84, 0, 4, 117, 121, 8, 2, 32, 3, 79, 35, 12, 57, 0, 117, 121, 8, 2, 115, 32, 0, 117, 105, 2, 110, 110, 101, 115, 3, 79, 36, 0, 105, 110, 115, 98, 101, 114, 103, 3, 79, 36, 50, 87, 69, 116, 12, 79, 0, 4, 105, 1, 101, 114, 2, 109, 101, 110, 28, 33, 12, 3, 79, 37, 0, 105, 1, 101, 114, 2, 111, 110, 12, 0, 105, 1, 101, 114, 2, 115, 116, 114, 101, 28, 33, 12, 0, 101, 97, 114, 3, 79, 37, 34, 0, 117, 105, 114, 108, 97, 110, 100, 3, 79, 37, 34, 55, 6, 108, 50, 70, 0, 117, 105, 110, 101, 97, 3, 79, 37, 50, 6, 36, 108, 0, 117, 105, 108, 108, 111, 116, 105, 110, 101, 3, 79, 37, 57, 40, 47, 6, 37, 12, 50, 13, 0, 111, 100, 97, 102, 116, 101, 110, 3, 79, 39, 6, 35, 81, 47, 50, 0, 111, 100, 110, 97, 116, 3, 79, 39, 50, 6, 108, 47, 0, 111, 100, 109, 111, 114, 103, 101, 110, 3, 79, 39, 63, 6, 112, 12, 50, 0, 111, 98, 101, 108, 105, 110, 3, 79, 39, 69, 13, 55, 6, 107, 66, 0, 111, 100, 100, 97, 103, 3, 79, 39, 70, 6, 108, 0, 117, 100, 115, 107, 101, 108, 111, 118, 8, 2, 32, 3, 79, 40, 87, 79, 13, 55, 112, 40, 0, 108, 111, 117, 99, 101, 115, 116, 101, 114, 3, 79, 55, 112, 87, 47, 112, 0, 106, 111, 114, 100, 101, 3, 79, 57, 39, 12, 112, 0, 117, 105, 114, 101, 3, 79, 58, 6, 118, 112, 0, 109, 97, 116, 97, 1, 105, 116, 115, 3, 79, 63, 6, 108, 12, 47, 108, 0, 195, 166, 1, 110, 3, 79, 107, 0, 97, 116, 101, 115, 8, 2, 32, 3, 79, 107, 57, 47, 87, 0, 97, 98, 108, 101, 8, 3, 79, 107, 57, 69, 13, 55, 0, 97, 114, 121, 8, 3, 79, 108, 34, 37, 0, 117, 97, 114, 100, 3, 79, 110, 12, 70, 0, 111, 117, 100, 97, 3, 79, 110, 58, 70, 108, 0, 97, 117, 108, 108, 101, 3, 79, 111, 12, 55, 0, 111, 103, 111, 3, 79, 111, 58, 79, 6, 111, 58, 0, 117, 108, 102, 115, 116, 114, 101, 97, 109, 3, 79, 112, 55, 81, 87, 47, 34, 37, 12, 63, 0, 117, 116, 104, 114, 105, 101, 3, 79, 112, 85, 51, 37, 0, 117, 101, 114, 110, 115, 101, 121, 3, 79, 116, 12, 50, 87, 37, 0, 101, 114, 116, 105, 101, 3, 79, 116, 47, 37, 0, 4, 101, 108, 101, 3, 87, 57, 36, 55, 6, 36, 0, 101, 108, 195, 169, 0, 101, 111, 105, 115, 1, 114, 117, 111, 98, 3, 88, 58, 6, 110, 0, 101, 111, 105, 115, 105, 1, 114, 117, 111, 98, 3, 88, 58, 110, 87, 6, 37, 0, 4, 1, 101, 114, 2, 105, 109, 101, 3, 89, 0, 1, 117, 2, 101, 110, 101, 0, 2, 105, 114, 111, 0, 4, 105, 1, 101, 114, 2, 28, 33, 12, 3, 89, 6, 37, 0, 105, 8, 111, 108, 2, 32, 0, 105, 8, 111, 108, 2, 101, 0, 105, 101, 114, 1, 108, 97, 3, 89, 6, 37, 34, 0, 101, 1, 110, 105, 2, 110, 105, 195, 184, 114, 3, 89, 36, 0, 4, 101, 110, 101, 114, 2, 32, 100, 101, 109, 3, 89, 36, 50, 6, 36, 34, 0, 101, 110, 101, 114, 2, 32, 100, 101, 114, 101, 115, 0, 101, 110, 101, 114, 2, 32, 104, 97, 109, 0, 101, 110, 101, 114, 2, 32, 104, 101, 110, 100, 101, 0, 4, 101, 110, 101, 118, 101, 3, 89, 36, 50, 6, 107, 12, 82, 0, 101, 110, 195, 168, 118, 101, 0, 101, 114, 97, 114, 100, 8, 3, 89, 36, 51, 6, 110, 12, 0, 105, 1, 111, 108, 116, 97, 110, 3, 89, 37, 0, 105, 98, 114, 97, 108, 116, 97, 114, 3, 89, 37, 69, 51, 35, 55, 47, 6, 110, 0, 101, 114, 105, 115, 107, 1, 108, 97, 3, 89, 57, 6, 37, 12, 34, 87, 79, 0, 101, 114, 105, 101, 114, 1, 108, 97, 3, 89, 57, 6, 37, 112, 0, 101, 114, 105, 101, 116, 1, 108, 97, 3, 89, 57, 106, 34, 6, 37, 13, 70, 0, 101, 110, 100, 97, 114, 109, 3, 89, 108, 50, 70, 6, 35, 34, 63, 0, 4, 101, 114, 1, 101, 110, 2, 12, 12, 3, 112, 0, 114, 101, 1, 101, 110, 0, 7, 6, 104, 0, 4, 1, 17, 65, 2, 25, 3, 0, 4, 1, 119, 2, 105, 115, 107, 121, 3, 0, 4, 1, 119, 2, 105, 116, 3, 0, 4, 2, 106, 3, 0, 8, 114, 2, 105, 110, 3, 0, 4, 101, 109, 1, 111, 98, 2, 101, 3, 6, 107, 12, 63, 0, 101, 109, 101, 1, 111, 98, 2, 32, 0, 111, 1, 103, 2, 115, 116, 3, 39, 58, 0, 117, 101, 1, 108, 105, 115, 2, 116, 3, 40, 6, 107, 0, 118, 3, 82, 0, 4, 3, 105, 0, 1, 116, 2, 101, 110, 0, 105, 116, 101, 99, 104, 3, 105, 35, 57, 47, 36, 49, 0, 121, 100, 101, 8, 3, 105, 35, 57, 70, 0, 111, 119, 97, 114, 100, 3, 105, 35, 58, 112, 70, 0, 105, 108, 108, 97, 114, 121, 3, 105, 36, 55, 13, 16, 36, 0, 101, 97, 116, 3, 105, 37, 12, 47, 0, 105, 101, 114, 111, 103, 108, 121, 2, 102, 3, 105, 37, 34, 39, 81, 55, 6, 114, 0, 105, 112, 111, 107, 114, 97, 116, 101, 115, 3, 105, 37, 48, 6, 39, 49, 34, 35, 47, 107, 87, 0, 111, 109, 101, 114, 3, 105, 39, 63, 6, 36, 34, 0, 117, 103, 104, 3, 105, 57, 40, 12, 0, 117, 103, 101, 115, 8, 2, 32, 3, 105, 57, 40, 12, 87, 0, 111, 117, 115, 116, 111, 110, 3, 105, 57, 40, 12, 87, 70, 112, 50, 0, 97, 105, 103, 8, 3, 105, 107, 57, 79, 0, 101, 97, 118, 121, 3, 105, 107, 82, 37, 0, 101, 97, 116, 104, 101, 114, 3, 105, 107, 84, 112, 0, 97, 119, 97, 105, 105, 3, 105, 108, 58, 6, 35, 12, 57, 37, 0, 105, 103, 104, 104, 97, 116, 3, 105, 110, 12, 57, 105, 108, 70, 0, 111, 117, 115, 101, 99, 111, 97, 116, 3, 105, 110, 40, 87, 49, 39, 58, 70, 0, 97, 119, 116, 104, 111, 114, 110, 101, 3, 105, 111, 12, 85, 39, 50, 0, 111, 109, 101, 3, 105, 111, 58, 63, 0, 97, 119, 107, 3, 105, 112, 12, 49, 0, 111, 116, 108, 105, 110, 101, 3, 105, 112, 47, 55, 35, 12, 57, 50, 0, 117, 99, 107, 108, 101, 98, 101, 114, 114, 121, 3, 105, 112, 49, 13, 55, 69, 107, 34, 37, 0, 111, 110, 101, 121, 3, 105, 112, 50, 37, 0, 117, 110, 116, 8, 2, 32, 3, 105, 112, 50, 47, 0, 111, 108, 108, 121, 3, 105, 112, 55, 37, 0, 117, 109, 118, 101, 101, 3, 105, 112, 63, 82, 37, 12, 0, 117, 109, 118, 101, 101, 114, 3, 105, 112, 63, 82, 37, 12, 112, 0, 117, 100, 115, 111, 110, 3, 105, 112, 70, 87, 112, 50, 0, 101, 114, 98, 8, 2, 32, 3, 105, 116, 12, 69, 0, 101, 97, 114, 115, 116, 8, 3, 105, 116, 87, 47, 0, 101, 105, 109, 3, 105, 118, 63, 0, 101, 114, 99, 117, 108, 101, 8, 3, 107, 34, 49, 6, 114, 55, 0, 7, 6, 105, 0, 4, 1, 110, 101, 103, 110, 105, 2, 195, 184, 114, 3, 0, 4, 1, 116, 2, 195, 184, 115, 3, 0, 4, 1, 117, 106, 2, 99, 101, 3, 0, 1, 118, 2, 110, 100, 114, 105, 107, 12, 3, 0, 107, 1, 21, 2, 101, 114, 28, 33, 12, 12, 3, 2, 37, 49, 0, 4, 1, 103, 101, 114, 116, 115, 109, 105, 104, 2, 109, 115, 3, 6, 36, 0, 1, 107, 121, 114, 2, 110, 100, 0, 1, 114, 101, 2, 110, 100, 114, 0, 1, 114, 121, 98, 97, 108, 2, 110, 116, 0, 1, 115, 116, 101, 108, 2, 110, 100, 105, 103, 0, 8, 108, 121, 99, 2, 110, 100, 0, 8, 114, 116, 115, 105, 100, 2, 107, 116, 0, 8, 115, 98, 97, 2, 110, 116, 0, 8, 116, 115, 101, 118, 2, 110, 100, 105, 0, 8, 116, 115, 110, 105, 2, 110, 107, 116, 0, 110, 100, 101, 1, 10, 2, 28, 33, 3, 6, 36, 50, 13, 0, 110, 103, 1, 109, 111, 100, 2, 111, 3, 6, 36, 50, 79, 0, 110, 100, 101, 1, 10, 2, 114, 28, 33, 3, 6, 36, 50, 112, 0, 108, 1, 116, 115, 97, 112, 10, 2, 28, 33, 12, 12, 12, 12, 3, 6, 36, 55, 0, 4, 1, 100, 111, 115, 111, 114, 112, 3, 6, 37, 0, 1, 100, 114, 166, 195, 118, 0, 1, 100, 117, 111, 104, 2, 110, 105, 0, 1, 102, 108, 121, 115, 2, 100, 101, 0, 1, 103, 105, 115, 107, 101, 2, 98, 101, 108, 0, 1, 103, 110, 117, 102, 2, 98, 101, 108, 0, 1, 104, 97, 116, 2, 116, 105, 0, 1, 104, 97, 119, 115, 2, 108, 105, 0, 1, 107, 2, 101, 116, 12, 0, 1, 108, 101, 98, 111, 2, 115, 107, 0, 1, 108, 105, 102, 2, 115, 116, 0, 1, 108, 108, 105, 99, 105, 112, 109, 97, 2, 110, 0, 1, 108, 111, 98, 2, 118, 105, 97, 0, 1, 108, 111, 115, 115, 117, 109, 2, 110, 105, 0, 1, 109, 10, 2, 28, 33, 0, 1, 109, 97, 2, 103, 111, 0, 1, 109, 97, 18, 75, 2, 108, 108, 97, 0, 1, 109, 97, 107, 2, 108, 108, 101, 0, 1, 109, 105, 2, 100, 108, 101, 114, 116, 105, 100, 0, 1, 110, 97, 112, 109, 97, 107, 2, 108, 101, 0, 1, 110, 101, 112, 2, 98, 101, 108, 0, 1, 110, 111, 112, 115, 105, 100, 2, 98, 101, 108, 0, 1, 112, 115, 97, 2, 99, 0, 1, 114, 10, 2, 101, 116, 28, 33, 0, 1, 114, 97, 109, 2, 97, 0, 1, 114, 97, 112, 2, 115, 0, 1, 114, 97, 116, 2, 102, 0, 1, 114, 100, 97, 109, 2, 100, 0, 1, 114, 100, 101, 122, 110, 101, 98, 2, 110, 0, 1, 114, 101, 104, 115, 2, 102, 0, 1, 114, 101, 118, 111, 116, 110, 105, 114, 98, 2, 108, 116, 101, 0, 1, 114, 105, 112, 115, 97, 2, 110, 0, 1, 114, 110, 101, 104, 2, 118, 101, 110, 100, 101, 0, 1, 114, 114, 111, 104, 2, 98, 101, 108, 0, 1, 115, 10, 2, 28, 33, 0, 1, 115, 97, 103, 97, 109, 0, 1, 115, 97, 107, 2, 110, 111, 0, 1, 115, 105, 118, 2, 98, 101, 108, 0, 1, 115, 107, 101, 108, 102, 2, 98, 101, 108, 0, 1, 115, 110, 101, 115, 2, 98, 101, 108, 0, 1, 115, 114, 101, 118, 101, 114, 2, 98, 101, 108, 0, 1, 115, 114, 101, 118, 101, 114, 114, 105, 2, 98, 101, 108, 0, 1, 115, 115, 105, 115, 115, 105, 109, 2, 112, 112, 105, 0, 1, 115, 117, 97, 108, 112, 2, 98, 101, 108, 0, 1, 116, 97, 112, 109, 111, 107, 2, 98, 101, 108, 0, 1, 116, 107, 101, 102, 114, 101, 112, 2, 98, 101, 108, 0, 1, 116, 114, 101, 118, 110, 111, 107, 2, 98, 101, 108, 0, 1, 116, 114, 111, 115, 2, 101, 0, 1, 116, 115, 101, 103, 103, 117, 115, 2, 98, 101, 108, 0, 1, 116, 120, 105, 115, 2, 110, 115, 107, 0, 1, 118, 101, 114, 114, 105, 112, 115, 2, 112, 0, 8, 98, 105, 108, 97, 0, 8, 98, 108, 97, 2, 110, 111, 0, 8, 98, 111, 102, 0, 8, 99, 110, 97, 114, 102, 2, 115, 99, 111, 0, 8, 99, 110, 105, 114, 112, 2, 112, 0, 8, 99, 110, 111, 107, 2, 115, 0, 8, 99, 114, 101, 115, 107, 101, 2, 116, 115, 0, 8, 99, 166, 195, 114, 112, 2, 115, 0, 8, 100, 97, 114, 2, 115, 101, 0, 8, 100, 101, 98, 98, 97, 0, 8, 100, 101, 102, 102, 117, 109, 2, 115, 101, 0, 8, 100, 105, 102, 114, 101, 112, 0, 8, 100, 110, 97, 98, 2, 116, 0, 8, 100, 110, 97, 107, 115, 114, 97, 109, 2, 115, 0, 8, 100, 111, 107, 111, 114, 107, 2, 108, 108, 0, 8, 100, 111, 108, 101, 109, 0, 8, 100, 111, 114, 97, 112, 0, 8, 100, 111, 115, 112, 97, 114, 0, 8, 100, 166, 195, 112, 111, 116, 114, 111, 0, 8, 101, 114, 2, 115, 116, 101, 114, 0, 8, 102, 105, 99, 117, 114, 107, 2, 107, 115, 0, 8, 103, 97, 109, 2, 32, 0, 8, 103, 97, 109, 2, 101, 110, 32, 0, 8, 103, 97, 109, 2, 115, 116, 101, 114, 0, 8, 107, 114, 97, 109, 2, 115, 101, 0, 8, 107, 115, 97, 109, 2, 110, 0, 8, 108, 97, 103, 101, 109, 111, 114, 107, 97, 0, 8, 108, 97, 107, 2, 98, 101, 114, 0, 8, 108, 97, 109, 111, 110, 97, 0, 8, 108, 100, 101, 109, 2, 100, 101, 110, 104, 101, 100, 0, 8, 108, 101, 102, 102, 97, 116, 115, 0, 8, 108, 101, 116, 97, 108, 105, 102, 0, 8, 108, 102, 102, 117, 115, 0, 8, 108, 102, 110, 111, 107, 2, 107, 116, 0, 8, 108, 105, 102, 111, 100, 166, 195, 112, 0, 8, 108, 105, 102, 111, 105, 108, 98, 105, 98, 0, 8, 108, 105, 102, 111, 109, 111, 104, 0, 8, 108, 105, 102, 111, 111, 122, 0, 8, 108, 105, 102, 111, 114, 101, 116, 101, 104, 0, 8, 108, 105, 102, 111, 114, 107, 101, 110, 0, 8, 108, 105, 109, 2, 116, 115, 0, 8, 108, 108, 101, 99, 110, 97, 107, 0, 8, 108, 111, 2, 118, 101, 110, 0, 8, 108, 111, 2, 118, 105, 97, 0, 8, 108, 111, 107, 110, 97, 108, 101, 109, 0, 8, 108, 111, 115, 2, 100, 0, 8, 108, 115, 117, 109, 2, 109, 0, 8, 108, 117, 107, 2, 115, 115, 0, 8, 109, 97, 114, 121, 112, 2, 100, 0, 8, 109, 101, 114, 2, 115, 0, 8, 110, 105, 109, 2, 115, 116, 101, 114, 0, 8, 111, 114, 101, 116, 115, 97, 2, 100, 101, 0, 8, 112, 97, 107, 2, 116, 101, 108, 0, 8, 112, 97, 107, 2, 116, 108, 0, 8, 112, 97, 112, 2, 114, 0, 8, 112, 97, 114, 101, 116, 0, 8, 112, 97, 116, 2, 114, 0, 8, 112, 101, 107, 115, 97, 109, 0, 8, 112, 111, 107, 0, 8, 112, 111, 107, 115, 101, 108, 101, 116, 0, 8, 112, 111, 107, 115, 111, 107, 110, 111, 114, 98, 0, 8, 112, 111, 107, 115, 111, 108, 121, 116, 107, 97, 100, 0, 8, 112, 111, 107, 115, 111, 114, 116, 115, 97, 103, 0, 8, 112, 111, 107, 115, 111, 116, 101, 116, 115, 0, 8, 112, 111, 107, 115, 111, 116, 107, 101, 114, 0, 8, 112, 111, 107, 115, 111, 116, 111, 0, 8, 112, 111, 114, 116, 110, 97, 108, 105, 102, 0, 8, 112, 111, 114, 116, 110, 97, 115, 105, 109, 0, 8, 112, 111, 114, 116, 110, 101, 0, 8, 112, 111, 116, 111, 115, 105, 0, 8, 112, 111, 116, 117, 0, 8, 112, 111, 116, 117, 0, 8, 112, 121, 116, 111, 101, 114, 101, 116, 115, 0, 8, 112, 121, 116, 111, 101, 114, 114, 101, 117, 103, 97, 100, 0, 8, 112, 121, 116, 111, 110, 97, 118, 108, 97, 103, 0, 8, 112, 121, 116, 111, 110, 111, 109, 0, 8, 112, 121, 116, 111, 116, 105, 108, 0, 8, 112, 121, 116, 111, 116, 117, 97, 0, 8, 114, 101, 118, 121, 116, 0, 8, 114, 111, 103, 101, 116, 97, 107, 0, 8, 114, 111, 103, 108, 97, 2, 116, 109, 101, 0, 8, 114, 111, 109, 166, 195, 104, 2, 100, 0, 8, 114, 112, 101, 114, 2, 115, 101, 0, 8, 114, 112, 101, 114, 116, 110, 101, 2, 115, 101, 0, 8, 114, 116, 110, 101, 118, 2, 107, 0, 8, 115, 108, 101, 118, 2, 103, 110, 0, 8, 115, 115, 101, 109, 2, 97, 115, 0, 8, 116, 105, 103, 101, 108, 2, 109, 0, 8, 116, 105, 108, 111, 112, 0, 8, 116, 105, 108, 111, 112, 0, 8, 116, 110, 105, 2, 109, 0, 8, 116, 114, 97, 2, 107, 0, 8, 116, 114, 97, 109, 2, 110, 105, 0, 8, 116, 114, 97, 112, 2, 115, 107, 0, 8, 116, 115, 101, 116, 2, 107, 101, 108, 0, 8, 116, 115, 101, 116, 2, 107, 108, 0, 8, 116, 115, 117, 106, 2, 116, 115, 0, 8, 118, 97, 2, 115, 0, 8, 118, 97, 114, 103, 2, 100, 0, 8, 118, 101, 108, 111, 109, 2, 116, 0, 8, 118, 105, 99, 2, 108, 0, 101, 1, 116, 114, 111, 115, 2, 32, 0, 115, 1, 109, 101, 114, 2, 32, 0, 101, 8, 118, 108, 97, 115, 3, 6, 37, 12, 0, 103, 101, 8, 108, 100, 101, 118, 3, 6, 37, 13, 0, 103, 101, 118, 101, 108, 1, 108, 108, 97, 3, 6, 37, 13, 82, 107, 55, 0, 108, 1, 10, 2, 28, 33, 12, 12, 12, 12, 3, 6, 37, 55, 0, 4, 108, 108, 101, 1, 114, 100, 97, 107, 115, 101, 3, 6, 37, 55, 57, 106, 0, 108, 108, 101, 1, 114, 100, 97, 112, 115, 101, 0, 108, 108, 101, 1, 114, 100, 97, 118, 107, 0, 108, 108, 101, 1, 116, 115, 97, 98, 0, 103, 111, 110, 101, 1, 116, 110, 97, 3, 6, 37, 79, 39, 50, 13, 0, 115, 1, 117, 111, 108, 2, 101, 3, 6, 37, 87, 0, 115, 109, 101, 1, 10, 2, 114, 28, 33, 3, 6, 37, 87, 63, 112, 0, 111, 110, 1, 114, 111, 3, 6, 37, 112, 50, 0, 114, 116, 117, 97, 108, 1, 118, 2, 32, 114, 101, 97, 108, 105, 116, 121, 3, 6, 106, 74, 40, 20, 13, 59, 0, 1, 114, 107, 115, 10, 2, 112, 116, 3, 6, 107, 0, 4, 8, 114, 107, 109, 111, 2, 110, 103, 3, 7, 36, 0, 107, 1, 114, 10, 2, 107, 28, 33, 0, 107, 1, 114, 21, 2, 107, 28, 33, 12, 12, 12, 12, 0, 107, 1, 116, 115, 101, 21, 2, 107, 28, 33, 12, 12, 12, 0, 107, 1, 114, 10, 2, 28, 33, 12, 12, 3, 7, 36, 49, 0, 4, 1, 116, 10, 2, 28, 33, 12, 3, 7, 37, 0, 1, 116, 110, 101, 108, 97, 118, 2, 110, 111, 0, 8, 108, 101, 2, 116, 101, 0, 8, 116, 114, 101, 112, 115, 107, 101, 2, 115, 101, 0, 107, 1, 10, 2, 107, 28, 33, 12, 0, 107, 1, 21, 2, 107, 28, 33, 12, 12, 12, 0, 107, 1, 116, 115, 97, 21, 2, 107, 28, 33, 12, 12, 12, 0, 4, 107, 1, 21, 2, 28, 33, 12, 12, 12, 3, 7, 37, 49, 0, 107, 1, 114, 111, 10, 2, 28, 33, 12, 12, 0, 100, 1, 10, 2, 28, 33, 3, 7, 37, 84, 0, 115, 109, 101, 1, 10, 2, 28, 33, 3, 7, 37, 87, 63, 13, 0, 1, 114, 10, 2, 117, 109, 28, 33, 3, 8, 8, 37, 0, 103, 1, 109, 101, 112, 108, 166, 195, 106, 104, 100, 117, 103, 3, 8, 35, 57, 0, 1, 109, 10, 2, 115, 107, 28, 33, 3, 8, 37, 0, 101, 1, 10, 2, 114, 101, 28, 33, 3, 8, 37, 7, 36, 0, 101, 1, 10, 2, 108, 105, 118, 28, 33, 3, 8, 37, 13, 0, 101, 110, 1, 10, 2, 28, 33, 3, 8, 37, 13, 50, 0, 116, 117, 109, 1, 21, 2, 109, 28, 33, 3, 8, 37, 47, 111, 0, 116, 117, 109, 1, 21, 2, 28, 33, 3, 8, 37, 47, 111, 63, 0, 107, 1, 21, 2, 101, 114, 101, 110, 28, 33, 12, 12, 3, 8, 37, 49, 0, 4, 107, 101, 114, 1, 10, 2, 28, 33, 12, 3, 8, 37, 49, 112, 0, 107, 101, 114, 1, 109, 10, 2, 101, 28, 33, 12, 12, 0, 107, 101, 114, 1, 110, 97, 107, 21, 2, 101, 32, 28, 33, 12, 12, 12, 0, 107, 101, 114, 1, 114, 116, 10, 2, 101, 28, 33, 12, 0, 107, 101, 114, 1, 116, 10, 2, 101, 28, 33, 12, 0, 4, 115, 107, 1, 10, 2, 32, 28, 33, 3, 8, 37, 87, 79, 0, 115, 107, 1, 10, 2, 101, 28, 33, 0, 115, 107, 1, 10, 2, 116, 28, 33, 0, 101, 1, 10, 2, 28, 33, 3, 8, 37, 106, 0, 117, 109, 1, 10, 2, 109, 28, 33, 3, 8, 37, 111, 0, 117, 109, 1, 10, 2, 28, 33, 3, 8, 37, 111, 63, 0, 101, 1, 115, 10, 2, 28, 33, 3, 8, 57, 106, 0, 4, 101, 1, 10, 2, 114, 28, 33, 3, 8, 57, 112, 0, 101, 114, 1, 108, 97, 114, 116, 115, 117, 97, 0, 116, 104, 101, 1, 108, 98, 3, 35, 12, 57, 84, 0, 103, 110, 1, 115, 101, 100, 3, 35, 37, 50, 0, 4, 1, 108, 115, 117, 115, 107, 117, 108, 2, 110, 101, 114, 3, 35, 57, 0, 1, 114, 2, 108, 101, 121, 0, 1, 116, 2, 109, 105, 110, 103, 0, 1, 116, 102, 111, 115, 2, 99, 101, 0, 2, 111, 119, 97, 0, 103, 104, 1, 104, 0, 103, 104, 1, 108, 2, 116, 101, 114, 0, 106, 1, 110, 2, 109, 101, 103, 101, 110, 0, 107, 101, 8, 112, 115, 3, 35, 57, 49, 0, 115, 108, 97, 110, 100, 1, 32, 103, 110, 111, 108, 3, 35, 57, 55, 13, 50, 70, 0, 109, 101, 1, 116, 2, 111, 117, 116, 3, 35, 57, 63, 0, 4, 109, 101, 115, 1, 114, 103, 3, 35, 57, 63, 87, 0, 109, 101, 115, 1, 116, 32, 107, 114, 111, 121, 32, 119, 101, 110, 0, 100, 97, 104, 111, 3, 35, 57, 70, 108, 105, 6, 39, 58, 0, 118, 101, 1, 108, 99, 3, 35, 57, 82, 0, 118, 97, 110, 104, 111, 101, 3, 35, 57, 82, 13, 50, 105, 6, 39, 58, 0, 114, 101, 1, 119, 3, 35, 57, 112, 0, 114, 111, 110, 8, 2, 32, 3, 35, 57, 112, 50, 0, 4, 1, 17, 67, 2, 109, 17, 67, 3, 36, 0, 1, 17, 67, 2, 109, 18, 71, 0, 1, 17, 67, 2, 110, 103, 12, 0, 1, 17, 67, 2, 110, 107, 0, 1, 18, 67, 2, 112, 0, 1, 18, 67, 2, 112, 112, 0, 1, 18, 68, 2, 18, 66, 11, 12, 0, 1, 18, 68, 2, 107, 0, 1, 18, 71, 2, 107, 0, 1, 18, 71, 2, 108, 108, 101, 0, 1, 18, 72, 2, 102, 116, 101, 0, 1, 18, 73, 2, 108, 108, 0, 1, 18, 74, 2, 18, 68, 11, 97, 12, 0, 1, 18, 74, 2, 107, 115, 0, 1, 18, 74, 2, 112, 112, 0, 1, 18, 74, 2, 120, 0, 1, 98, 2, 116, 114, 101, 0, 1, 98, 2, 116, 116, 101, 114, 0, 1, 100, 2, 110, 103, 111, 0, 1, 100, 2, 115, 107, 0, 1, 102, 2, 18, 73, 12, 0, 1, 102, 2, 107, 115, 0, 1, 102, 2, 110, 108, 97, 110, 100, 0, 1, 102, 2, 110, 116, 101, 32, 0, 1, 102, 2, 120, 0, 1, 104, 2, 109, 12, 0, 1, 104, 2, 110, 100, 0, 1, 107, 2, 18, 74, 12, 12, 0, 1, 107, 2, 109, 115, 101, 0, 1, 107, 111, 109, 115, 2, 110, 103, 0, 1, 107, 115, 2, 108, 12, 12, 0, 1, 107, 115, 2, 110, 0, 1, 108, 2, 18, 66, 0, 1, 108, 2, 18, 73, 0, 1, 108, 2, 108, 108, 97, 0, 1, 108, 2, 110, 110, 101, 100, 0, 1, 108, 2, 110, 115, 0, 1, 108, 2, 110, 116, 0, 1, 108, 17, 67, 2, 112, 0, 1, 108, 18, 73, 2, 18, 72, 0, 1, 108, 103, 2, 109, 0, 1, 108, 107, 2, 107, 32, 0, 1, 108, 112, 2, 103, 116, 12, 0, 1, 108, 115, 2, 107, 0, 1, 109, 2, 107, 108, 101, 114, 0, 1, 109, 2, 115, 116, 101, 0, 1, 110, 2, 112, 0, 1, 110, 2, 115, 115, 101, 0, 1, 110, 2, 116, 116, 101, 110, 0, 1, 110, 107, 2, 112, 0, 1, 112, 2, 108, 114, 0, 1, 112, 2, 115, 115, 101, 0, 1, 112, 115, 2, 100, 115, 0, 1, 112, 115, 2, 108, 0, 1, 114, 2, 18, 66, 11, 0, 1, 114, 2, 18, 73, 12, 0, 1, 114, 2, 18, 75, 0, 1, 114, 2, 102, 0, 1, 114, 2, 103, 116, 105, 0, 1, 114, 17, 67, 2, 108, 108, 0, 1, 114, 17, 67, 2, 109, 17, 67, 0, 1, 114, 18, 71, 2, 110, 116, 0, 1, 114, 100, 2, 115, 116, 105, 103, 0, 1, 114, 103, 2, 109, 0, 1, 114, 107, 2, 99, 107, 101, 116, 0, 1, 114, 107, 2, 115, 116, 105, 32, 0, 1, 114, 107, 2, 115, 116, 117, 115, 0, 1, 114, 112, 2, 110, 0, 1, 114, 118, 2, 115, 115, 0, 1, 115, 2, 18, 66, 18, 72, 0, 1, 115, 2, 100, 32, 0, 1, 115, 2, 100, 100, 101, 0, 1, 115, 2, 100, 110, 105, 110, 103, 0, 1, 115, 2, 107, 17, 67, 0, 1, 115, 2, 108, 107, 0, 1, 115, 2, 110, 107, 12, 12, 0, 1, 115, 2, 112, 112, 0, 1, 116, 2, 18, 66, 12, 0, 1, 116, 2, 103, 103, 12, 0, 1, 116, 2, 108, 0, 1, 116, 115, 2, 108, 32, 104, 97, 109, 0, 1, 116, 115, 2, 108, 32, 111, 112, 32, 0, 1, 116, 115, 2, 108, 108, 105, 110, 103, 12, 12, 0, 1, 116, 115, 100, 110, 166, 195, 116, 2, 107, 12, 0, 1, 116, 115, 101, 98, 2, 107, 12, 12, 0, 1, 116, 115, 101, 98, 2, 108, 0, 1, 116, 115, 101, 98, 166, 195, 108, 2, 102, 116, 0, 1, 116, 115, 101, 100, 97, 112, 115, 2, 107, 0, 1, 116, 115, 101, 103, 103, 121, 109, 2, 107, 0, 1, 116, 115, 101, 108, 165, 195, 110, 2, 107, 12, 0, 1, 116, 115, 101, 110, 103, 101, 116, 2, 102, 116, 0, 1, 116, 115, 101, 114, 111, 102, 2, 108, 0, 1, 116, 115, 103, 97, 108, 115, 2, 102, 116, 0, 1, 116, 115, 105, 98, 2, 107, 12, 12, 0, 1, 116, 115, 107, 166, 195, 108, 98, 2, 102, 116, 0, 1, 116, 115, 109, 105, 108, 2, 102, 116, 0, 1, 116, 115, 115, 116, 110, 97, 121, 108, 98, 2, 102, 116, 0, 1, 116, 115, 116, 110, 97, 121, 108, 98, 2, 102, 116, 0, 1, 116, 115, 118, 105, 110, 107, 2, 107, 0, 1, 118, 2, 18, 66, 0, 1, 118, 2, 18, 66, 17, 67, 12, 12, 0, 1, 118, 2, 108, 32, 12, 0, 1, 118, 2, 110, 116, 101, 114, 0, 1, 118, 2, 110, 116, 114, 101, 0, 1, 118, 2, 115, 32, 103, 114, 97, 100, 0, 1, 118, 2, 115, 104, 0, 1, 118, 2, 115, 107, 12, 0, 1, 118, 2, 115, 110, 101, 0, 1, 118, 2, 115, 115, 0, 1, 118, 2, 115, 116, 32, 105, 107, 107, 101, 0, 1, 118, 18, 72, 2, 115, 116, 12, 0, 1, 118, 32, 101, 107, 115, 110, 97, 103, 2, 115, 116, 32, 0, 1, 118, 97, 106, 2, 115, 116, 0, 1, 118, 101, 103, 2, 110, 115, 116, 0, 1, 118, 104, 2, 108, 107, 12, 0, 1, 118, 111, 106, 2, 115, 116, 0, 1, 118, 115, 2, 18, 74, 17, 67, 0, 1, 119, 116, 2, 115, 116, 0, 2, 107, 107, 101, 0, 2, 109, 112, 0, 2, 109, 112, 111, 0, 2, 110, 99, 0, 2, 110, 100, 0, 2, 110, 102, 97, 110, 116, 0, 2, 110, 110, 0, 2, 110, 110, 101, 0, 2, 110, 115, 0, 8, 2, 110, 0, 8, 102, 2, 107, 32, 0, 8, 108, 2, 100, 116, 32, 0, 8, 109, 2, 115, 116, 32, 0, 8, 110, 2, 18, 75, 0, 8, 114, 100, 2, 108, 0, 8, 116, 2, 103, 32, 12, 0, 8, 116, 2, 110, 0, 8, 116, 2, 115, 107, 101, 32, 0, 8, 118, 2, 102, 116, 32, 0, 8, 118, 2, 115, 116, 32, 0, 100, 1, 118, 2, 115, 116, 0, 100, 8, 109, 2, 116, 0, 1, 118, 2, 115, 116, 110, 111, 107, 3, 36, 4, 0, 107, 97, 100, 101, 108, 108, 101, 1, 114, 102, 3, 36, 49, 108, 70, 6, 107, 55, 106, 0, 4, 110, 100, 1, 102, 2, 101, 108, 195, 184, 110, 3, 36, 50, 0, 110, 100, 2, 101, 108, 115, 101, 12, 0, 110, 117, 112, 1, 112, 3, 36, 50, 6, 112, 48, 0, 110, 103, 111, 1, 98, 3, 36, 50, 79, 39, 0, 110, 115, 105, 100, 101, 8, 2, 105, 110, 102, 111, 114, 109, 97, 116, 105, 111, 110, 3, 36, 50, 87, 35, 57, 70, 0, 110, 115, 105, 100, 101, 114, 8, 3, 36, 50, 87, 35, 57, 70, 112, 0, 110, 115, 116, 105, 116, 117, 116, 105, 111, 110, 8, 3, 36, 50, 87, 47, 37, 47, 40, 89, 6, 39, 50, 0, 110, 115, 116, 105, 116, 117, 116, 105, 111, 110, 3, 36, 50, 87, 47, 37, 47, 40, 89, 39, 50, 0, 109, 112, 111, 116, 101, 110, 3, 36, 63, 48, 39, 47, 107, 50, 0, 109, 97, 108, 97, 121, 97, 1, 104, 3, 36, 63, 108, 55, 6, 35, 57, 108, 0, 103, 1, 114, 2, 110, 105, 110, 103, 3, 36, 79, 0, 107, 115, 101, 116, 1, 107, 2, 32, 3, 36, 79, 87, 13, 84, 0, 115, 1, 112, 2, 32, 3, 36, 87, 0, 115, 105, 107, 1, 114, 2, 101, 3, 36, 87, 37, 49, 0, 4, 3, 37, 0, 1, 18, 67, 2, 18, 71, 101, 0, 1, 18, 67, 2, 18, 71, 114, 101, 0, 1, 18, 68, 2, 18, 75, 97, 0, 1, 18, 68, 2, 107, 18, 69, 0, 1, 18, 68, 2, 107, 101, 0, 1, 18, 71, 2, 107, 101, 0, 1, 98, 2, 107, 105, 110, 105, 0, 1, 98, 2, 107, 117, 98, 101, 0, 1, 98, 2, 108, 108, 101, 32, 12, 0, 1, 98, 2, 108, 108, 101, 110, 32, 12, 0, 1, 98, 2, 108, 108, 101, 114, 32, 12, 0, 1, 98, 2, 108, 108, 101, 116, 12, 0, 1, 98, 2, 112, 12, 0, 1, 99, 2, 110, 110, 0, 1, 100, 2, 107, 116, 0, 1, 100, 2, 115, 18, 75, 97, 0, 1, 100, 2, 115, 107, 101, 116, 116, 0, 1, 100, 2, 115, 107, 111, 0, 1, 100, 2, 115, 107, 114, 101, 112, 97, 110, 115, 0, 1, 100, 2, 115, 107, 114, 101, 116, 0, 1, 100, 2, 115, 107, 114, 105, 109, 105, 0, 1, 100, 2, 115, 107, 117, 0, 1, 100, 2, 115, 107, 118, 97, 0, 1, 100, 110, 105, 2, 115, 107, 0, 1, 100, 114, 111, 106, 2, 115, 107, 0, 1, 102, 2, 107, 17, 67, 18, 69, 0, 1, 102, 2, 110, 107, 117, 108, 0, 1, 102, 2, 110, 107, 195, 166, 109, 0, 1, 102, 2, 110, 115, 107, 121, 0, 1, 102, 97, 114, 103, 2, 115, 107, 0, 1, 102, 97, 114, 116, 2, 107, 0, 1, 102, 110, 111, 107, 2, 115, 107, 101, 114, 0, 1, 102, 110, 111, 107, 2, 115, 107, 101, 114, 101, 0, 1, 104, 2, 110, 0, 1, 104, 99, 2, 107, 12, 0, 1, 107, 2, 12, 12, 0, 1, 107, 2, 18, 74, 18, 76, 12, 12, 0, 1, 107, 2, 109, 110, 105, 110, 103, 12, 0, 1, 107, 2, 115, 116, 101, 12, 0, 1, 107, 105, 98, 2, 110, 105, 0, 1, 107, 115, 2, 17, 67, 116, 0, 1, 107, 115, 2, 107, 12, 0, 1, 107, 115, 2, 108, 105, 102, 116, 12, 0, 1, 107, 115, 2, 108, 195, 184, 98, 12, 12, 0, 1, 107, 115, 2, 109, 111, 12, 0, 1, 107, 115, 21, 2, 108, 100, 12, 12, 0, 1, 108, 2, 107, 118, 12, 0, 1, 108, 2, 109, 110, 105, 12, 0, 1, 108, 2, 115, 107, 0, 1, 108, 97, 105, 99, 101, 112, 115, 2, 115, 116, 0, 1, 108, 98, 117, 112, 0, 1, 108, 105, 98, 2, 115, 0, 1, 108, 112, 2, 18, 66, 18, 76, 12, 0, 1, 108, 112, 2, 107, 0, 1, 108, 114, 111, 102, 2, 115, 0, 1, 108, 115, 2, 109, 0, 1, 109, 2, 107, 115, 116, 117, 114, 0, 1, 109, 2, 115, 116, 97, 110, 107, 101, 0, 1, 110, 2, 99, 104, 101, 0, 1, 110, 2, 107, 18, 69, 0, 1, 110, 100, 108, 105, 118, 2, 115, 0, 1, 110, 101, 108, 2, 110, 0, 1, 110, 101, 112, 2, 115, 0, 1, 110, 105, 108, 107, 2, 107, 0, 1, 110, 107, 2, 118, 0, 1, 110, 107, 101, 116, 2, 107, 0, 1, 112, 2, 110, 115, 101, 108, 0, 1, 112, 2, 110, 115, 108, 101, 114, 0, 1, 112, 2, 112, 12, 0, 1, 112, 114, 97, 104, 2, 107, 115, 0, 1, 112, 115, 2, 108, 100, 0, 1, 114, 2, 18, 73, 18, 69, 12, 0, 1, 114, 2, 18, 75, 17, 67, 18, 69, 0, 1, 114, 2, 18, 75, 18, 69, 0, 1, 114, 2, 18, 75, 18, 76, 0, 1, 114, 2, 99, 101, 0, 1, 114, 2, 115, 116, 105, 107, 12, 0, 1, 114, 10, 2, 115, 107, 0, 1, 114, 18, 66, 2, 108, 108, 0, 1, 114, 101, 116, 110, 97, 102, 110, 105, 0, 1, 114, 102, 2, 102, 12, 0, 1, 114, 102, 2, 103, 0, 1, 114, 102, 2, 107, 101, 110, 0, 1, 114, 102, 2, 107, 118, 97, 114, 116, 101, 114, 0, 1, 114, 102, 2, 115, 116, 97, 100, 0, 1, 114, 102, 2, 115, 116, 101, 100, 0, 1, 114, 103, 2, 18, 73, 12, 0, 1, 114, 112, 2, 109, 12, 0, 1, 114, 112, 2, 115, 0, 1, 114, 116, 2, 18, 73, 12, 0, 1, 114, 116, 2, 108, 108, 0, 1, 115, 101, 98, 2, 100, 100, 101, 0, 1, 115, 117, 109, 2, 107, 0, 1, 116, 2, 100, 12, 0, 1, 116, 2, 107, 97, 12, 0, 1, 116, 2, 110, 18, 76, 0, 1, 116, 2, 110, 110, 105, 116, 117, 115, 0, 1, 116, 21, 2, 107, 32, 12, 12, 0, 1, 116, 105, 108, 111, 112, 2, 107, 0, 1, 116, 107, 101, 106, 111, 114, 112, 2, 108, 0, 1, 116, 110, 97, 0, 1, 116, 110, 101, 118, 2, 108, 0, 1, 116, 114, 97, 112, 0, 1, 116, 115, 2, 108, 32, 111, 118, 101, 114, 0, 1, 116, 115, 2, 108, 97, 114, 116, 0, 1, 116, 115, 2, 108, 102, 117, 108, 100, 0, 1, 116, 115, 17, 65, 2, 108, 32, 0, 1, 116, 115, 32, 101, 100, 118, 97, 104, 2, 108, 32, 0, 1, 116, 115, 32, 101, 114, 101, 109, 2, 108, 32, 111, 118, 101, 114, 32, 0, 1, 116, 115, 32, 110, 101, 2, 108, 32, 0, 1, 116, 115, 32, 114, 97, 104, 2, 108, 32, 0, 1, 116, 115, 32, 114, 97, 118, 2, 108, 32, 111, 118, 101, 114, 32, 0, 1, 116, 115, 32, 114, 101, 2, 108, 32, 111, 118, 101, 114, 32, 0, 1, 116, 115, 97, 108, 112, 2, 18, 75, 0, 1, 116, 115, 115, 118, 105, 108, 2, 108, 0, 1, 116, 117, 98, 2, 107, 0, 1, 118, 2, 18, 66, 97, 0, 1, 118, 2, 18, 75, 105, 0, 1, 118, 2, 98, 12, 0, 1, 118, 2, 99, 107, 0, 1, 118, 2, 107, 116, 18, 69, 12, 12, 0, 1, 118, 2, 110, 103, 108, 97, 115, 12, 12, 0, 1, 118, 2, 110, 103, 195, 165, 114, 100, 12, 0, 1, 118, 2, 110, 107, 111, 114, 116, 0, 1, 118, 2, 110, 107, 195, 166, 108, 100, 12, 0, 1, 118, 2, 115, 116, 101, 12, 0, 1, 118, 101, 98, 2, 115, 0, 1, 118, 104, 2, 108, 12, 0, 1, 118, 107, 2, 18, 72, 12, 12, 0, 1, 118, 115, 2, 110, 115, 0, 1, 118, 116, 114, 111, 98, 2, 115, 0, 1, 118, 184, 195, 104, 2, 115, 107, 0, 2, 103, 103, 106, 111, 12, 12, 0, 2, 103, 103, 195, 184, 114, 12, 12, 0, 2, 110, 117, 0, 8, 2, 110, 105, 0, 8, 108, 2, 100, 116, 32, 110, 101, 100, 101, 114, 108, 97, 103, 0, 8, 108, 2, 100, 116, 32, 111, 118, 101, 114, 108, 97, 115, 116, 0, 8, 108, 2, 100, 116, 32, 115, 107, 97, 100, 101, 0, 8, 108, 2, 100, 116, 32, 117, 110, 100, 101, 114, 0, 8, 108, 107, 2, 115, 116, 101, 114, 0, 8, 116, 115, 2, 108, 32, 111, 118, 101, 114, 32, 100, 101, 17, 67, 0, 8, 116, 115, 2, 108, 32, 111, 118, 101, 114, 32, 104, 97, 109, 0, 8, 116, 115, 2, 108, 32, 111, 118, 101, 114, 32, 104, 101, 110, 100, 101, 0, 8, 116, 115, 32, 100, 101, 109, 2, 108, 32, 0, 8, 116, 115, 32, 110, 105, 100, 2, 108, 32, 0, 8, 116, 115, 32, 110, 105, 109, 2, 108, 32, 0, 8, 116, 115, 32, 115, 101, 100, 110, 101, 104, 2, 108, 32, 0, 8, 116, 115, 32, 115, 101, 114, 101, 100, 2, 108, 32, 0, 8, 116, 115, 32, 115, 101, 114, 101, 106, 2, 108, 32, 0, 8, 116, 115, 32, 115, 110, 97, 104, 2, 108, 32, 0, 8, 116, 115, 32, 121, 110, 2, 108, 32, 0, 8, 118, 2, 115, 116, 32, 115, 105, 103, 0, 101, 1, 100, 2, 115, 101, 108, 0, 101, 1, 100, 2, 116, 114, 105, 99, 104, 0, 101, 1, 108, 115, 101, 108, 0, 101, 1, 110, 110, 111, 114, 0, 101, 1, 112, 2, 100, 101, 115, 116, 97, 108, 0, 101, 1, 112, 112, 105, 104, 0, 101, 1, 117, 111, 108, 0, 101, 8, 98, 98, 111, 114, 0, 101, 8, 110, 97, 108, 101, 109, 0, 101, 8, 110, 110, 97, 0, 101, 8, 115, 117, 115, 0, 101, 8, 122, 117, 115, 0, 103, 1, 100, 114, 166, 195, 118, 0, 103, 1, 108, 116, 110, 101, 102, 102, 111, 0, 103, 1, 114, 2, 17, 67, 0, 103, 1, 116, 2, 12, 0, 115, 1, 117, 111, 108, 0, 4, 1, 102, 2, 107, 115, 101, 114, 98, 97, 100, 3, 37, 6, 0, 1, 102, 2, 107, 115, 101, 114, 98, 105, 108, 108, 101, 100, 0, 1, 102, 2, 107, 115, 101, 114, 101, 0, 1, 102, 2, 107, 115, 101, 114, 105, 110, 103, 0, 1, 102, 2, 107, 115, 101, 114, 118, 195, 166, 115, 107, 101, 0, 1, 114, 18, 75, 2, 115, 116, 105, 110, 0, 101, 1, 114, 10, 2, 108, 28, 33, 3, 37, 6, 107, 0, 4, 101, 110, 1, 10, 2, 101, 114, 28, 33, 3, 37, 6, 107, 50, 0, 101, 110, 1, 10, 2, 115, 107, 28, 33, 0, 4, 1, 18, 73, 2, 108, 101, 12, 12, 3, 37, 12, 0, 1, 114, 103, 2, 109, 18, 76, 0, 1, 116, 115, 2, 108, 101, 0, 100, 101, 108, 8, 2, 32, 3, 37, 12, 84, 13, 55, 0, 114, 111, 115, 104, 105, 1, 104, 2, 109, 97, 3, 37, 34, 39, 89, 6, 37, 0, 116, 101, 115, 8, 114, 102, 2, 32, 3, 37, 47, 0, 4, 107, 1, 17, 67, 2, 97, 110, 101, 114, 12, 12, 3, 37, 49, 0, 107, 1, 17, 67, 2, 101, 114, 12, 0, 107, 1, 21, 2, 97, 116, 28, 33, 12, 12, 0, 107, 1, 21, 2, 101, 116, 28, 33, 12, 12, 12, 0, 4, 107, 1, 10, 2, 97, 108, 115, 107, 28, 33, 3, 37, 49, 6, 0, 107, 1, 21, 2, 97, 110, 116, 28, 33, 12, 0, 107, 101, 114, 1, 10, 2, 101, 114, 28, 33, 12, 3, 37, 49, 6, 36, 0, 4, 107, 101, 114, 1, 110, 10, 2, 101, 32, 28, 33, 12, 3, 37, 49, 6, 36, 34, 0, 107, 101, 114, 1, 110, 10, 2, 101, 116, 32, 28, 33, 12, 0, 107, 101, 114, 1, 114, 97, 107, 10, 2, 101, 28, 33, 12, 0, 103, 110, 1, 115, 2, 97, 108, 3, 37, 50, 0, 110, 116, 101, 114, 110, 97, 116, 105, 111, 110, 97, 108, 1, 32, 121, 116, 115, 101, 110, 109, 97, 3, 37, 50, 47, 112, 50, 6, 108, 89, 39, 50, 108, 55, 0, 4, 110, 100, 1, 102, 2, 101, 108, 3, 37, 50, 70, 0, 110, 100, 1, 102, 2, 121, 114, 107, 0, 110, 100, 1, 118, 2, 114, 117, 101, 0, 110, 103, 1, 118, 2, 117, 109, 109, 105, 3, 37, 50, 79, 0, 108, 108, 97, 100, 115, 1, 116, 115, 3, 37, 55, 6, 108, 87, 0, 108, 111, 112, 1, 112, 115, 3, 37, 55, 6, 112, 48, 0, 108, 108, 101, 1, 116, 114, 97, 2, 114, 105, 3, 37, 55, 13, 0, 108, 108, 1, 118, 97, 112, 2, 111, 3, 37, 55, 57, 0, 4, 103, 1, 108, 2, 17, 67, 3, 37, 57, 0, 103, 1, 108, 108, 101, 104, 0, 4, 98, 101, 1, 112, 2, 116, 195, 184, 106, 3, 37, 58, 0, 112, 1, 110, 107, 2, 116, 97, 110, 103, 0, 109, 97, 103, 101, 3, 37, 63, 37, 73, 0, 100, 103, 101, 1, 114, 3, 37, 73, 0, 100, 103, 101, 116, 1, 114, 98, 3, 37, 73, 37, 47, 0, 4, 103, 1, 108, 2, 105, 3, 37, 79, 0, 103, 1, 108, 105, 102, 2, 114, 97, 110, 0, 103, 1, 114, 102, 2, 106, 111, 0, 103, 1, 116, 115, 2, 109, 97, 0, 103, 2, 114, 117, 112, 112, 101, 0, 115, 1, 18, 73, 2, 12, 3, 37, 87, 0, 115, 114, 97, 101, 108, 8, 100, 2, 105, 3, 37, 87, 34, 110, 6, 36, 55, 0, 115, 114, 97, 101, 108, 115, 107, 3, 37, 87, 34, 110, 6, 36, 55, 87, 49, 0, 115, 114, 97, 101, 108, 101, 114, 3, 37, 87, 34, 110, 6, 36, 55, 112, 0, 115, 114, 97, 101, 108, 3, 37, 87, 34, 110, 12, 55, 0, 115, 105, 107, 111, 1, 114, 3, 37, 87, 37, 49, 39, 0, 115, 116, 101, 108, 116, 101, 110, 1, 109, 3, 37, 87, 47, 107, 55, 47, 36, 50, 0, 115, 105, 97, 110, 97, 1, 117, 111, 108, 3, 37, 87, 57, 6, 108, 50, 108, 0, 110, 103, 101, 1, 108, 2, 114, 105, 3, 55, 108, 66, 89, 36, 0, 4, 1, 99, 2, 97, 3, 57, 0, 1, 108, 2, 101, 0, 1, 110, 117, 106, 2, 111, 114, 0, 1, 115, 2, 111, 110, 0, 1, 115, 97, 2, 101, 0, 1, 115, 2, 97, 114, 3, 57, 6, 0, 4, 101, 114, 1, 99, 110, 97, 108, 3, 57, 6, 36, 0, 101, 114, 1, 99, 110, 97, 110, 105, 102, 0, 101, 114, 1, 99, 110, 101, 114, 101, 102, 110, 111, 107, 0, 101, 114, 1, 100, 97, 98, 114, 97, 98, 0, 101, 114, 1, 100, 97, 110, 101, 114, 103, 0, 101, 114, 1, 107, 110, 97, 98, 0, 101, 114, 1, 108, 97, 112, 115, 0, 101, 114, 1, 108, 97, 112, 115, 101, 0, 101, 114, 1, 108, 101, 116, 97, 0, 101, 114, 1, 108, 108, 111, 99, 0, 101, 114, 1, 108, 117, 99, 105, 116, 114, 97, 112, 0, 101, 114, 1, 109, 117, 116, 115, 111, 107, 0, 101, 114, 1, 110, 101, 100, 0, 101, 114, 1, 112, 117, 111, 114, 99, 0, 101, 114, 1, 115, 110, 97, 110, 105, 102, 0, 101, 114, 1, 115, 115, 111, 100, 0, 101, 114, 1, 116, 101, 109, 0, 101, 114, 1, 116, 110, 97, 103, 101, 108, 101, 0, 101, 114, 1, 116, 110, 101, 114, 0, 101, 114, 1, 116, 114, 111, 112, 0, 101, 119, 3, 57, 6, 40, 0, 97, 118, 1, 109, 3, 57, 35, 58, 0, 4, 101, 1, 118, 2, 116, 32, 99, 111, 110, 103, 3, 57, 107, 0, 101, 1, 118, 2, 116, 110, 97, 109, 0, 4, 111, 1, 107, 2, 115, 107, 3, 57, 112, 0, 111, 114, 1, 110, 101, 115, 0, 110, 1, 108, 101, 104, 99, 105, 109, 3, 107, 66, 0, 114, 1, 108, 102, 2, 116, 3, 116, 12, 0, 114, 118, 105, 110, 103, 3, 116, 82, 36, 66, 0, 7, 6, 106, 0, 101, 97, 110, 110, 101, 2, 32, 100, 39, 3, 2, 89, 108, 12, 50, 0, 1, 104, 114, 101, 100, 2, 101, 109, 109, 101, 3, 6, 57, 0, 4, 3, 57, 0, 1, 184, 195, 2, 101, 116, 0, 2, 117, 110, 107, 116, 0, 1, 97, 109, 2, 111, 114, 3, 57, 6, 0, 101, 104, 111, 118, 97, 3, 57, 36, 105, 6, 39, 82, 108, 0, 101, 114, 8, 2, 32, 3, 57, 107, 34, 0, 101, 114, 115, 101, 121, 2, 107, 3, 57, 107, 34, 87, 37, 0, 97, 107, 101, 108, 8, 3, 57, 108, 49, 20, 13, 55, 0, 97, 109, 115, 101, 115, 115, 105, 111, 110, 3, 70, 57, 108, 12, 63, 87, 6, 36, 89, 57, 13, 50, 0, 4, 1, 105, 102, 2, 105, 3, 73, 0, 1, 110, 105, 110, 2, 97, 0, 2, 97, 119, 0, 2, 97, 122, 122, 0, 2, 101, 110, 110, 105, 102, 101, 114, 0, 2, 111, 98, 0, 2, 117, 105, 99, 101, 0, 2, 117, 110, 103, 108, 0, 2, 117, 110, 107, 0, 8, 2, 101, 102, 102, 0, 8, 2, 105, 109, 32, 0, 101, 114, 114, 121, 3, 73, 36, 34, 37, 0, 101, 107, 121, 108, 108, 3, 73, 36, 49, 14, 55, 0, 105, 110, 103, 108, 101, 3, 73, 36, 50, 79, 106, 55, 0, 4, 105, 109, 109, 105, 101, 3, 73, 36, 63, 37, 0, 105, 109, 109, 121, 0, 4, 101, 97, 110, 3, 73, 37, 12, 50, 0, 101, 97, 110, 110, 101, 0, 101, 101, 112, 3, 73, 37, 12, 69, 0, 105, 108, 108, 8, 3, 73, 37, 55, 0, 105, 116, 116, 101, 114, 98, 117, 103, 3, 73, 37, 70, 112, 69, 112, 79, 0, 105, 104, 97, 100, 3, 73, 37, 105, 6, 108, 47, 0, 117, 107, 101, 2, 98, 111, 107, 115, 3, 73, 40, 12, 49, 0, 4, 101, 119, 101, 108, 3, 73, 40, 12, 55, 0, 111, 117, 108, 101, 0, 4, 101, 1, 97, 109, 114, 105, 102, 2, 116, 3, 73, 107, 0, 101, 1, 111, 98, 109, 117, 106, 2, 116, 0, 101, 8, 2, 116, 0, 4, 101, 110, 110, 105, 101, 3, 73, 107, 50, 37, 0, 101, 110, 110, 121, 0, 97, 121, 3, 73, 107, 57, 0, 97, 107, 101, 8, 3, 73, 107, 57, 49, 0, 97, 110, 101, 121, 3, 73, 107, 57, 50, 37, 0, 97, 109, 105, 101, 3, 73, 107, 57, 63, 37, 0, 97, 109, 101, 115, 8, 3, 73, 107, 57, 63, 87, 0, 101, 115, 115, 3, 73, 107, 87, 0, 101, 115, 115, 105, 101, 3, 73, 107, 87, 37, 0, 4, 97, 2, 99, 107, 3, 73, 108, 0, 97, 2, 109, 97, 108, 0, 97, 99, 107, 105, 101, 3, 73, 108, 49, 37, 0, 97, 114, 118, 105, 115, 8, 3, 73, 110, 12, 82, 36, 87, 0, 97, 109, 98, 97, 108, 97, 121, 97, 3, 73, 110, 63, 69, 108, 55, 6, 35, 57, 108, 0, 111, 108, 101, 110, 101, 8, 3, 73, 111, 58, 55, 6, 37, 12, 50, 0, 111, 2, 99, 107, 101, 121, 3, 73, 112, 0, 111, 104, 110, 3, 73, 112, 50, 0, 111, 104, 110, 110, 121, 3, 73, 112, 50, 37, 0, 117, 110, 107, 105, 101, 3, 73, 112, 50, 49, 37, 0, 117, 110, 99, 116, 105, 111, 110, 3, 73, 112, 50, 49, 89, 13, 50, 0, 111, 121, 3, 73, 112, 57, 0, 111, 105, 110, 116, 3, 73, 112, 57, 50, 47, 0, 111, 115, 104, 8, 3, 73, 112, 89, 0, 111, 101, 3, 73, 113, 58, 0, 111, 110, 101, 115, 3, 73, 113, 58, 50, 87, 0, 4, 101, 114, 115, 101, 121, 8, 2, 32, 3, 73, 116, 12, 87, 37, 0, 101, 114, 115, 101, 121, 8, 2, 115, 32, 0, 111, 107, 101, 3, 73, 116, 58, 49, 0, 97, 99, 113, 117, 101, 115, 3, 88, 35, 49, 0, 4, 1, 110, 101, 2, 97, 109, 98, 101, 3, 89, 0, 1, 111, 114, 2, 101, 107, 116, 0, 2, 97, 115, 109, 105, 110, 0, 2, 111, 110, 103, 108, 0, 2, 111, 117, 114, 110, 97, 108, 0, 1, 97, 2, 111, 117, 3, 89, 6, 0, 101, 114, 111, 109, 101, 3, 89, 36, 34, 6, 39, 63, 0, 97, 110, 101, 105, 114, 111, 3, 89, 36, 50, 6, 107, 34, 39, 0, 97, 117, 98, 101, 114, 116, 3, 89, 39, 69, 6, 107, 34, 0, 117, 97, 110, 8, 3, 89, 40, 6, 110, 66, 0, 101, 116, 111, 110, 3, 89, 57, 36, 47, 6, 112, 66, 0, 97, 114, 100, 105, 110, 105, 101, 114, 101, 3, 89, 57, 110, 34, 70, 37, 50, 57, 6, 107, 12, 34, 0, 101, 97, 2, 110, 101, 116, 116, 101, 3, 89, 108, 6, 0, 97, 108, 111, 117, 115, 105, 8, 3, 89, 108, 55, 40, 87, 6, 37, 0, 97, 108, 111, 117, 115, 105, 1, 21, 3, 89, 108, 55, 40, 87, 37, 0, 97, 109, 97, 105, 99, 97, 3, 89, 108, 63, 6, 35, 57, 49, 108, 0, 117, 103, 101, 114, 101, 3, 89, 114, 89, 6, 36, 112, 0, 1, 97, 118, 97, 110, 2, 111, 3, 105, 0, 7, 6, 107, 0, 4, 1, 101, 112, 115, 2, 116, 97, 107, 107, 3, 0, 1, 101, 112, 115, 2, 116, 97, 107, 108, 3, 0, 4, 8, 101, 112, 115, 2, 116, 97, 107, 107, 3, 6, 0, 8, 101, 112, 115, 2, 116, 97, 107, 108, 0, 4, 3, 49, 0, 1, 10, 0, 107, 0, 114, 121, 115, 97, 110, 116, 101, 109, 117, 109, 3, 49, 34, 115, 87, 6, 108, 50, 47, 13, 63, 111, 63, 0, 97, 107, 101, 114, 108, 97, 2, 107, 3, 49, 35, 49, 13, 55, 6, 35, 0, 97, 110, 116, 101, 114, 101, 108, 3, 49, 35, 50, 47, 13, 34, 6, 109, 55, 0, 105, 100, 1, 32, 101, 104, 116, 3, 49, 36, 70, 0, 101, 105, 116, 104, 3, 49, 37, 12, 85, 0, 105, 108, 105, 109, 97, 110, 106, 97, 114, 111, 3, 49, 37, 55, 37, 63, 108, 50, 73, 6, 110, 34, 39, 0, 108, 111, 115, 2, 32, 104, 111, 108, 100, 3, 49, 55, 112, 87, 0, 118, 97, 114, 116, 101, 114, 1, 10, 3, 49, 82, 35, 34, 47, 36, 34, 0, 97, 116, 101, 8, 2, 32, 3, 49, 107, 57, 47, 0, 97, 114, 97, 111, 107, 101, 3, 49, 108, 34, 108, 6, 39, 40, 49, 37, 0, 111, 110, 116, 105, 110, 117, 117, 109, 3, 49, 112, 50, 47, 6, 37, 50, 40, 111, 63, 0, 117, 109, 113, 117, 97, 116, 3, 49, 112, 63, 49, 58, 112, 70, 0, 101, 114, 109, 105, 116, 8, 3, 49, 116, 12, 63, 36, 47, 0, 110, 105, 103, 104, 116, 3, 50, 110, 57, 47, 0, 110, 111, 99, 107, 3, 50, 112, 49, 0, 110, 111, 120, 3, 50, 112, 79, 87, 0, 7, 6, 108, 0, 4, 101, 1, 102, 102, 105, 107, 115, 3, 13, 55, 0, 101, 8, 112, 114, 97, 109, 0, 4, 3, 55, 0, 100, 1, 10, 2, 101, 114, 0, 108, 0, 118, 1, 101, 115, 0, 118, 1, 111, 116, 0, 118, 1, 184, 195, 115, 0, 101, 111, 100, 1, 32, 99, 97, 109, 3, 55, 6, 35, 58, 70, 0, 111, 103, 1, 10, 2, 28, 33, 3, 55, 6, 39, 0, 4, 101, 116, 1, 10, 2, 116, 28, 33, 3, 55, 6, 107, 0, 101, 116, 1, 111, 105, 114, 98, 97, 99, 0, 101, 116, 1, 10, 2, 28, 33, 3, 55, 6, 107, 47, 0, 101, 103, 2, 32, 3, 55, 35, 57, 0, 101, 103, 101, 114, 2, 32, 3, 55, 35, 57, 112, 0, 111, 117, 110, 103, 101, 3, 55, 35, 58, 50, 73, 0, 4, 101, 116, 1, 105, 102, 101, 98, 98, 117, 114, 107, 115, 3, 55, 36, 0, 101, 116, 1, 105, 102, 101, 103, 110, 117, 116, 184, 195, 115, 0, 101, 116, 1, 105, 102, 101, 107, 115, 105, 102, 0, 101, 116, 1, 105, 102, 101, 109, 109, 97, 108, 0, 101, 116, 1, 105, 102, 101, 110, 105, 118, 115, 0, 101, 116, 1, 105, 102, 101, 114, 121, 100, 0, 101, 116, 1, 105, 102, 101, 115, 107, 111, 0, 101, 116, 1, 105, 102, 101, 116, 114, 111, 106, 104, 0, 101, 116, 1, 105, 102, 101, 116, 115, 101, 104, 0, 101, 116, 1, 105, 102, 101, 116, 116, 166, 195, 112, 115, 0, 101, 116, 1, 105, 102, 115, 103, 101, 116, 115, 0, 105, 110, 99, 111, 108, 110, 3, 55, 36, 50, 49, 112, 59, 50, 0, 105, 116, 116, 108, 101, 3, 55, 36, 70, 13, 55, 0, 101, 103, 101, 2, 114, 105, 110, 103, 3, 55, 36, 79, 6, 36, 0, 105, 118, 105, 110, 103, 115, 116, 111, 110, 101, 3, 55, 36, 82, 36, 66, 87, 47, 4, 106, 12, 58, 50, 0, 101, 118, 101, 114, 101, 1, 21, 3, 55, 36, 82, 36, 112, 0, 101, 121, 3, 55, 37, 0, 101, 101, 8, 2, 32, 3, 55, 37, 12, 0, 101, 101, 100, 8, 2, 115, 3, 55, 37, 12, 70, 0, 108, 97, 114, 100, 1, 105, 98, 3, 55, 37, 35, 70, 0, 105, 109, 111, 103, 101, 115, 3, 55, 37, 63, 6, 39, 12, 88, 0, 105, 122, 122, 105, 101, 3, 55, 37, 87, 37, 0, 97, 117, 116, 114, 101, 99, 3, 55, 39, 47, 34, 6, 107, 49, 0, 111, 114, 114, 97, 105, 110, 101, 3, 55, 39, 51, 107, 12, 50, 0, 111, 103, 1, 10, 2, 105, 28, 33, 3, 55, 39, 79, 6, 0, 103, 1, 101, 104, 2, 101, 3, 55, 57, 0, 108, 101, 110, 100, 101, 8, 97, 3, 55, 57, 6, 107, 50, 70, 106, 0, 4, 100, 1, 111, 98, 3, 55, 70, 0, 100, 1, 111, 115, 2, 97, 116, 0, 118, 101, 1, 101, 115, 3, 55, 82, 106, 0, 111, 116, 105, 111, 110, 3, 55, 106, 40, 89, 57, 50, 0, 101, 103, 101, 109, 2, 17, 67, 3, 55, 107, 57, 13, 63, 0, 97, 107, 101, 8, 2, 32, 3, 55, 107, 57, 49, 0, 97, 98, 111, 117, 114, 3, 55, 107, 57, 69, 112, 0, 4, 97, 100, 121, 1, 110, 114, 101, 106, 3, 55, 107, 57, 70, 37, 0, 97, 100, 121, 8, 0, 101, 97, 118, 101, 110, 119, 111, 114, 116, 104, 3, 55, 107, 82, 13, 50, 58, 116, 12, 106, 85, 0, 101, 105, 99, 101, 115, 116, 101, 114, 3, 55, 107, 87, 47, 112, 0, 97, 100, 121, 115, 1, 103, 3, 55, 108, 70, 37, 87, 0, 117, 99, 107, 121, 3, 55, 112, 49, 37, 0, 108, 111, 121, 100, 3, 55, 112, 57, 70, 0, 111, 110, 103, 2, 32, 105, 115, 108, 97, 110, 100, 3, 55, 112, 66, 0, 117, 100, 108, 111, 119, 3, 55, 112, 70, 55, 39, 58, 0, 4, 1, 98, 3, 59, 0, 1, 102, 0, 1, 115, 0, 97, 114, 114, 121, 3, 59, 108, 16, 37, 0, 7, 6, 109, 0, 97, 105, 108, 1, 32, 101, 3, 2, 63, 107, 57, 55, 0, 97, 110, 100, 1, 114, 117, 111, 103, 3, 2, 63, 110, 66, 0, 4, 97, 100, 101, 114, 111, 3, 21, 101, 115, 0, 105, 103, 117, 101, 108, 0, 111, 110, 116, 112, 101, 108, 108, 105, 101, 114, 3, 21, 102, 114, 0, 4, 3, 63, 0, 109, 0, 97, 110, 100, 8, 114, 117, 111, 103, 3, 63, 7, 110, 66, 0, 109, 1, 111, 2, 195, 184, 98, 108, 101, 3, 63, 15, 63, 0, 101, 103, 101, 110, 8, 2, 32, 3, 63, 35, 12, 57, 13, 50, 0, 101, 103, 101, 116, 8, 2, 32, 3, 63, 35, 12, 57, 13, 84, 0, 97, 107, 97, 114, 111, 110, 105, 3, 63, 35, 49, 106, 34, 6, 112, 50, 37, 0, 97, 114, 115, 101, 105, 108, 108, 101, 3, 63, 35, 51, 87, 6, 107, 12, 57, 0, 4, 105, 107, 101, 8, 2, 32, 3, 63, 35, 57, 49, 0, 105, 107, 101, 8, 2, 115, 32, 0, 111, 117, 115, 101, 8, 3, 63, 35, 58, 87, 0, 101, 114, 101, 8, 2, 32, 3, 63, 36, 34, 0, 105, 108, 107, 115, 104, 97, 107, 101, 3, 63, 36, 55, 49, 89, 107, 57, 49, 0, 105, 108, 119, 97, 117, 107, 101, 101, 3, 63, 36, 55, 58, 6, 111, 49, 37, 0, 101, 100, 101, 97, 8, 3, 63, 36, 70, 6, 107, 12, 108, 0, 105, 100, 110, 105, 103, 104, 116, 3, 63, 36, 70, 50, 35, 57, 47, 0, 105, 99, 104, 101, 108, 108, 101, 3, 63, 37, 89, 6, 107, 55, 0, 97, 117, 114, 105, 99, 101, 3, 63, 39, 34, 6, 37, 87, 0, 97, 117, 112, 97, 115, 115, 97, 110, 116, 3, 63, 39, 48, 108, 87, 6, 110, 66, 0, 111, 117, 108, 105, 110, 3, 63, 40, 55, 6, 108, 66, 0, 117, 115, 107, 101, 116, 101, 114, 3, 63, 40, 87, 79, 36, 47, 6, 36, 34, 0, 117, 115, 105, 99, 97, 108, 3, 63, 57, 40, 12, 87, 37, 49, 106, 55, 0, 4, 109, 1, 101, 108, 108, 101, 109, 3, 63, 63, 0, 109, 2, 97, 115, 115, 97, 103, 101, 0, 112, 115, 111, 110, 3, 63, 87, 112, 50, 0, 97, 107, 101, 117, 2, 112, 3, 63, 107, 57, 49, 6, 112, 0, 97, 105, 110, 101, 8, 3, 63, 107, 57, 50, 0, 97, 105, 108, 3, 63, 107, 57, 55, 0, 97, 121, 100, 97, 121, 3, 63, 107, 57, 70, 107, 12, 57, 0, 101, 108, 98, 111, 117, 114, 110, 101, 3, 63, 107, 59, 69, 116, 50, 0, 97, 114, 105, 108, 121, 110, 3, 63, 108, 34, 37, 55, 36, 50, 0, 97, 116, 105, 108, 100, 8, 3, 63, 108, 47, 6, 37, 55, 70, 0, 97, 116, 105, 110, 101, 3, 63, 108, 47, 37, 50, 6, 36, 0, 99, 8, 2, 17, 67, 21, 3, 63, 108, 49, 0, 97, 110, 110, 101, 113, 117, 105, 110, 8, 3, 63, 108, 50, 13, 49, 6, 107, 66, 0, 97, 110, 110, 101, 113, 117, 105, 110, 3, 63, 108, 50, 13, 49, 107, 66, 0, 97, 110, 97, 103, 101, 114, 3, 63, 108, 50, 36, 73, 112, 0, 105, 97, 109, 105, 3, 63, 108, 57, 6, 108, 12, 63, 37, 0, 97, 100, 97, 103, 97, 115, 107, 97, 114, 3, 63, 108, 70, 108, 79, 6, 108, 87, 49, 108, 0, 97, 116, 116, 104, 101, 119, 3, 63, 108, 85, 57, 40, 0, 97, 115, 115, 97, 99, 104, 117, 115, 101, 116, 116, 115, 3, 63, 108, 87, 108, 47, 57, 6, 40, 87, 107, 47, 87, 0, 97, 99, 104, 101, 116, 101, 3, 63, 108, 89, 6, 107, 70, 0, 97, 104, 111, 103, 110, 105, 3, 63, 108, 105, 6, 39, 50, 37, 0, 97, 114, 101, 114, 105, 100, 116, 3, 63, 110, 12, 13, 34, 37, 47, 0, 97, 114, 106, 111, 114, 105, 101, 3, 63, 110, 73, 111, 34, 37, 0, 111, 110, 116, 114, 101, 3, 63, 111, 12, 50, 47, 34, 112, 0, 97, 108, 116, 1, 32, 101, 108, 103, 110, 105, 115, 3, 63, 111, 55, 47, 0, 117, 114, 114, 97, 121, 3, 63, 112, 34, 37, 0, 117, 112, 112, 101, 116, 8, 3, 63, 112, 48, 36, 47, 0, 111, 110, 114, 111, 101, 3, 63, 112, 50, 34, 6, 111, 58, 0, 111, 110, 101, 121, 3, 63, 112, 50, 37, 0, 111, 110, 116, 103, 111, 109, 101, 114, 121, 3, 63, 112, 50, 70, 79, 6, 112, 63, 34, 37, 0, 111, 108, 121, 110, 101, 117, 120, 3, 63, 112, 55, 37, 50, 57, 40, 12, 0, 111, 116, 104, 101, 114, 3, 63, 112, 84, 112, 0, 117, 114, 100, 111, 99, 104, 3, 63, 116, 70, 112, 49, 0, 117, 114, 112, 104, 3, 63, 116, 81, 0, 4, 117, 114, 112, 104, 101, 121, 3, 63, 116, 81, 37, 0, 117, 114, 112, 104, 121, 0, 7, 6, 110, 0, 95, 1, 97, 107, 3, 0, 105, 1, 10, 2, 28, 33, 12, 3, 6, 50, 37, 0, 105, 1, 110, 10, 2, 28, 33, 12, 3, 7, 37, 0, 4, 1, 10, 2, 101, 114, 28, 33, 12, 3, 8, 50, 0, 1, 10, 2, 105, 115, 116, 97, 110, 28, 33, 0, 1, 10, 2, 115, 107, 28, 33, 0, 4, 105, 1, 10, 2, 115, 107, 28, 33, 12, 3, 8, 50, 37, 0, 105, 1, 105, 107, 105, 98, 0, 105, 107, 97, 8, 111, 109, 114, 97, 104, 3, 8, 50, 37, 49, 108, 0, 105, 101, 110, 1, 21, 3, 8, 50, 37, 106, 20, 50, 0, 105, 101, 114, 1, 21, 3, 8, 50, 37, 112, 0, 105, 103, 104, 116, 105, 110, 103, 97, 108, 101, 3, 21, 0, 4, 3, 50, 0, 110, 1, 17, 65, 0, 110, 1, 111, 115, 166, 195, 114, 0, 105, 97, 103, 97, 114, 97, 8, 3, 50, 35, 57, 6, 108, 79, 106, 34, 35, 0, 105, 103, 104, 116, 101, 110, 103, 97, 108, 101, 8, 3, 50, 35, 57, 47, 14, 50, 79, 107, 57, 55, 0, 121, 108, 111, 110, 3, 50, 35, 57, 55, 112, 50, 0, 105, 103, 101, 108, 8, 3, 50, 35, 57, 73, 106, 55, 0, 101, 103, 108, 105, 103, 101, 3, 50, 36, 79, 55, 37, 89, 6, 36, 0, 101, 105, 108, 3, 50, 37, 12, 55, 0, 105, 99, 111, 108, 101, 8, 3, 50, 37, 49, 6, 112, 55, 0, 105, 99, 111, 108, 8, 2, 101, 116, 116, 101, 3, 50, 37, 49, 39, 55, 0, 111, 117, 103, 97, 116, 3, 50, 40, 79, 6, 108, 0, 101, 119, 116, 111, 110, 3, 50, 57, 6, 40, 12, 47, 13, 50, 0, 101, 119, 3, 50, 57, 40, 0, 101, 119, 122, 101, 97, 108, 97, 110, 100, 3, 50, 57, 40, 87, 6, 36, 55, 108, 50, 0, 101, 108, 108, 105, 101, 8, 3, 50, 107, 55, 37, 0, 101, 118, 105, 108, 108, 101, 8, 3, 50, 107, 82, 36, 59, 0, 97, 105, 118, 8, 3, 50, 108, 6, 37, 82, 0, 97, 103, 8, 2, 32, 3, 50, 108, 12, 57, 0, 97, 105, 118, 1, 21, 3, 50, 108, 37, 82, 0, 111, 114, 101, 101, 110, 8, 3, 50, 111, 58, 34, 6, 37, 12, 50, 0, 111, 114, 119, 105, 99, 104, 8, 3, 50, 112, 34, 37, 74, 0, 111, 115, 116, 114, 97, 100, 97, 109, 117, 115, 3, 50, 112, 87, 47, 34, 110, 70, 6, 108, 63, 40, 87, 0, 107, 2, 116, 3, 66, 0, 7, 6, 111, 0, 1, 108, 32, 107, 97, 114, 116, 2, 100, 3, 0, 4, 1, 112, 2, 115, 116, 101, 106, 3, 2, 39, 0, 2, 107, 116, 111, 98, 0, 1, 114, 116, 110, 111, 107, 2, 108, 108, 101, 114, 3, 2, 111, 0, 4, 109, 109, 101, 8, 112, 2, 32, 3, 2, 112, 63, 0, 109, 109, 101, 115, 8, 112, 2, 32, 0, 119, 1, 108, 98, 3, 6, 13, 58, 0, 4, 117, 116, 8, 101, 109, 105, 116, 3, 6, 35, 58, 70, 0, 117, 116, 8, 107, 99, 97, 108, 98, 0, 117, 116, 8, 107, 99, 111, 108, 0, 117, 116, 8, 107, 99, 111, 110, 107, 0, 117, 116, 8, 107, 114, 111, 119, 0, 117, 116, 8, 121, 97, 108, 0, 4, 1, 98, 109, 97, 99, 2, 100, 106, 3, 6, 39, 0, 1, 99, 101, 100, 32, 116, 114, 97, 0, 1, 100, 97, 116, 97, 109, 2, 114, 0, 1, 100, 105, 114, 114, 111, 107, 2, 114, 0, 1, 101, 108, 99, 2, 112, 97, 116, 114, 97, 0, 1, 101, 116, 101, 109, 2, 114, 0, 1, 103, 97, 112, 2, 100, 101, 0, 1, 103, 110, 97, 2, 108, 97, 0, 1, 105, 98, 105, 116, 110, 97, 2, 116, 105, 107, 0, 1, 105, 100, 2, 100, 101, 0, 1, 105, 114, 101, 112, 2, 100, 101, 0, 1, 105, 118, 97, 114, 2, 108, 105, 0, 1, 106, 97, 103, 2, 108, 0, 1, 107, 97, 108, 2, 116, 97, 0, 1, 107, 110, 97, 108, 101, 109, 2, 108, 115, 107, 0, 1, 108, 97, 2, 104, 97, 0, 1, 108, 97, 104, 115, 2, 109, 0, 1, 108, 107, 121, 99, 2, 110, 0, 1, 108, 107, 121, 107, 2, 112, 0, 1, 108, 108, 97, 104, 0, 1, 109, 97, 115, 2, 97, 0, 1, 109, 109, 111, 107, 2, 100, 101, 0, 1, 112, 101, 2, 107, 101, 0, 1, 114, 97, 2, 109, 97, 0, 1, 114, 101, 2, 98, 0, 1, 114, 101, 112, 112, 101, 112, 2, 110, 105, 0, 1, 114, 116, 107, 101, 108, 101, 2, 100, 101, 0, 1, 114, 116, 115, 105, 98, 0, 1, 115, 105, 112, 101, 2, 100, 101, 0, 1, 116, 97, 107, 2, 100, 101, 0, 1, 116, 97, 107, 2, 108, 115, 107, 0, 1, 116, 97, 109, 166, 195, 104, 2, 109, 0, 1, 116, 101, 98, 2, 110, 105, 110, 103, 0, 1, 116, 101, 109, 2, 100, 101, 0, 1, 116, 110, 111, 107, 2, 114, 0, 1, 116, 115, 117, 107, 2, 100, 101, 0, 1, 121, 107, 2, 116, 111, 0, 8, 100, 97, 116, 101, 109, 2, 110, 0, 8, 100, 107, 101, 110, 97, 2, 116, 0, 8, 105, 100, 105, 2, 116, 0, 8, 105, 114, 112, 121, 99, 2, 116, 0, 8, 105, 114, 116, 97, 112, 2, 116, 0, 8, 106, 108, 97, 116, 97, 98, 2, 110, 0, 8, 106, 115, 110, 97, 2, 115, 0, 8, 106, 117, 107, 2, 110, 0, 8, 108, 105, 112, 2, 116, 0, 8, 108, 105, 116, 110, 97, 2, 112, 101, 0, 8, 109, 97, 114, 2, 110, 97, 0, 8, 109, 101, 110, 97, 2, 110, 101, 0, 8, 109, 105, 2, 100, 0, 8, 109, 105, 107, 115, 101, 0, 8, 109, 114, 111, 109, 2, 110, 0, 8, 109, 166, 195, 100, 2, 110, 0, 8, 110, 97, 107, 2, 110, 0, 8, 110, 103, 105, 115, 2, 114, 0, 8, 110, 111, 107, 184, 195, 2, 109, 32, 0, 8, 112, 101, 100, 2, 116, 0, 8, 114, 101, 2, 116, 0, 8, 114, 116, 97, 109, 2, 110, 101, 0, 8, 114, 116, 97, 109, 2, 115, 0, 8, 114, 117, 101, 2, 112, 97, 0, 8, 115, 111, 108, 105, 102, 2, 102, 105, 115, 107, 0, 8, 116, 111, 105, 98, 2, 112, 0, 8, 116, 111, 115, 105, 2, 112, 0, 108, 1, 114, 116, 10, 2, 108, 108, 101, 28, 33, 0, 116, 1, 100, 114, 97, 98, 0, 116, 1, 107, 105, 114, 116, 0, 116, 1, 108, 114, 101, 109, 0, 1, 116, 105, 108, 2, 116, 101, 3, 6, 39, 12, 0, 102, 101, 1, 114, 116, 115, 97, 116, 97, 107, 3, 6, 39, 12, 81, 106, 0, 115, 101, 1, 10, 2, 28, 33, 12, 3, 6, 39, 12, 87, 13, 0, 115, 101, 43, 1, 10, 2, 114, 28, 33, 3, 6, 39, 12, 87, 112, 0, 116, 105, 1, 107, 114, 97, 110, 2, 107, 3, 6, 39, 47, 37, 0, 112, 1, 107, 115, 10, 2, 28, 33, 12, 12, 3, 6, 39, 48, 0, 110, 100, 1, 107, 101, 115, 2, 108, 195, 184, 106, 116, 110, 97, 110, 116, 3, 6, 39, 50, 70, 0, 4, 108, 1, 10, 2, 28, 33, 12, 12, 3, 6, 39, 55, 0, 108, 1, 104, 10, 2, 105, 28, 33, 12, 0, 108, 1, 114, 116, 10, 2, 101, 28, 33, 0, 108, 1, 115, 10, 2, 18, 69, 28, 33, 12, 0, 108, 1, 116, 110, 10, 2, 28, 33, 12, 0, 108, 1, 116, 115, 10, 2, 12, 28, 33, 0, 109, 1, 10, 2, 28, 33, 12, 3, 6, 39, 63, 0, 4, 111, 1, 122, 97, 107, 3, 6, 40, 0, 117, 1, 108, 101, 118, 2, 114, 0, 117, 116, 1, 103, 97, 114, 0, 4, 111, 1, 122, 97, 98, 3, 6, 40, 12, 0, 117, 1, 115, 115, 105, 109, 2, 114, 105, 0, 117, 105, 108, 108, 101, 1, 116, 97, 116, 97, 114, 3, 6, 40, 12, 57, 0, 117, 110, 1, 104, 108, 97, 99, 3, 6, 40, 50, 0, 105, 114, 101, 1, 116, 114, 101, 112, 101, 114, 3, 6, 58, 110, 12, 0, 110, 100, 1, 98, 97, 103, 97, 118, 3, 6, 111, 50, 70, 0, 4, 1, 98, 111, 114, 2, 116, 12, 12, 3, 6, 112, 0, 1, 100, 97, 114, 97, 112, 2, 107, 115, 0, 1, 100, 97, 114, 98, 97, 108, 2, 114, 0, 1, 100, 111, 116, 114, 111, 2, 107, 115, 0, 1, 102, 101, 100, 2, 114, 109, 0, 1, 102, 101, 114, 2, 114, 109, 0, 1, 102, 105, 110, 117, 2, 114, 109, 0, 1, 102, 110, 111, 107, 2, 114, 109, 0, 1, 102, 111, 114, 111, 108, 107, 2, 114, 109, 0, 1, 104, 99, 97, 107, 2, 116, 0, 1, 104, 110, 114, 111, 98, 2, 108, 109, 0, 1, 107, 115, 105, 116, 114, 97, 2, 107, 0, 1, 108, 97, 103, 2, 17, 67, 0, 1, 108, 117, 2, 118, 0, 1, 109, 97, 2, 107, 0, 1, 110, 98, 97, 2, 114, 109, 0, 1, 110, 101, 2, 114, 109, 12, 0, 1, 110, 111, 109, 2, 107, 0, 1, 112, 97, 2, 108, 108, 111, 12, 12, 0, 1, 112, 109, 111, 107, 2, 115, 116, 0, 1, 114, 111, 116, 2, 110, 116, 111, 0, 1, 114, 116, 115, 101, 114, 101, 112, 2, 106, 107, 97, 0, 1, 115, 111, 108, 105, 102, 2, 102, 32, 0, 8, 107, 115, 97, 109, 2, 116, 0, 8, 107, 117, 104, 2, 109, 109, 101, 0, 8, 108, 111, 107, 2, 115, 0, 8, 112, 115, 101, 114, 2, 110, 115, 0, 8, 115, 105, 114, 111, 104, 2, 110, 0, 8, 116, 114, 97, 107, 2, 102, 0, 8, 118, 101, 114, 2, 108, 118, 0, 108, 1, 114, 116, 10, 2, 108, 101, 110, 28, 33, 0, 112, 116, 101, 114, 1, 107, 105, 108, 101, 104, 3, 6, 112, 48, 47, 112, 0, 103, 1, 107, 110, 105, 2, 110, 105, 116, 111, 3, 6, 112, 49, 0, 110, 100, 1, 107, 111, 112, 121, 104, 2, 101, 114, 3, 6, 112, 50, 70, 0, 4, 108, 1, 104, 10, 2, 28, 33, 12, 3, 6, 112, 55, 0, 108, 1, 107, 111, 10, 2, 28, 33, 12, 0, 108, 1, 114, 116, 10, 2, 28, 33, 12, 0, 108, 1, 115, 10, 2, 28, 33, 12, 0, 108, 1, 116, 10, 2, 28, 33, 12, 0, 108, 100, 101, 1, 115, 105, 3, 6, 112, 55, 70, 106, 0, 4, 106, 1, 118, 110, 111, 107, 3, 6, 112, 57, 0, 121, 2, 12, 0, 105, 97, 8, 110, 97, 114, 97, 112, 3, 6, 112, 57, 108, 0, 4, 103, 110, 101, 1, 99, 115, 97, 103, 3, 6, 112, 66, 57, 106, 0, 103, 110, 101, 1, 116, 115, 97, 98, 0, 114, 101, 114, 1, 115, 3, 7, 39, 12, 112, 0, 8, 2, 109, 17, 67, 3, 7, 112, 0, 103, 110, 1, 108, 117, 111, 98, 2, 101, 3, 7, 112, 66, 57, 0, 1, 114, 116, 107, 101, 108, 101, 3, 8, 39, 0, 114, 1, 115, 3, 8, 112, 0, 98, 108, 105, 103, 101, 1, 32, 101, 115, 115, 101, 108, 98, 111, 110, 3, 21, 102, 114, 0, 1, 100, 2, 119, 110, 105, 110, 103, 3, 35, 0, 117, 110, 3, 35, 40, 50, 0, 117, 116, 104, 1, 115, 3, 35, 40, 85, 0, 117, 116, 108, 97, 119, 3, 35, 58, 47, 55, 111, 12, 0, 4, 117, 116, 8, 100, 110, 97, 104, 3, 35, 58, 70, 0, 117, 116, 8, 110, 111, 114, 116, 115, 97, 0, 117, 116, 8, 112, 111, 114, 100, 0, 117, 116, 115, 105, 100, 101, 114, 3, 35, 58, 70, 87, 35, 57, 70, 112, 0, 4, 3, 39, 0, 1, 17, 67, 2, 18, 66, 97, 12, 0, 1, 17, 67, 2, 18, 66, 114, 18, 76, 12, 0, 1, 17, 67, 2, 18, 68, 11, 97, 0, 1, 17, 67, 2, 18, 71, 18, 69, 12, 12, 0, 1, 17, 67, 2, 103, 12, 0, 1, 17, 67, 2, 107, 18, 69, 12, 0, 1, 17, 67, 2, 109, 18, 76, 0, 1, 17, 67, 102, 2, 116, 18, 69, 0, 1, 18, 66, 2, 109, 18, 69, 0, 1, 18, 66, 2, 109, 101, 0, 1, 18, 66, 2, 109, 109, 97, 110, 12, 0, 1, 18, 68, 2, 18, 74, 18, 69, 0, 1, 18, 68, 2, 18, 74, 18, 76, 0, 1, 18, 71, 2, 116, 18, 76, 0, 1, 18, 73, 2, 108, 0, 1, 18, 73, 2, 116, 18, 69, 0, 1, 18, 74, 2, 100, 0, 1, 18, 75, 2, 18, 71, 114, 18, 76, 0, 1, 97, 109, 2, 12, 0, 1, 98, 2, 100, 0, 1, 98, 2, 103, 111, 114, 109, 0, 1, 98, 2, 109, 0, 1, 98, 2, 109, 109, 12, 12, 0, 1, 98, 2, 112, 195, 166, 108, 0, 1, 98, 97, 110, 2, 12, 0, 1, 98, 109, 117, 106, 0, 1, 98, 109, 121, 115, 2, 108, 0, 1, 100, 2, 18, 66, 114, 18, 69, 0, 1, 101, 100, 105, 118, 0, 1, 102, 2, 98, 0, 1, 102, 2, 100, 12, 0, 1, 102, 2, 114, 18, 69, 12, 0, 1, 103, 2, 100, 0, 1, 103, 2, 115, 108, 97, 118, 0, 1, 103, 97, 100, 2, 103, 0, 1, 104, 2, 18, 74, 18, 69, 12, 0, 1, 104, 2, 98, 12, 0, 1, 104, 2, 115, 112, 105, 116, 0, 1, 104, 2, 115, 116, 12, 0, 1, 104, 2, 118, 101, 114, 101, 0, 1, 104, 99, 2, 107, 111, 12, 0, 1, 105, 100, 97, 114, 0, 1, 106, 2, 100, 0, 1, 106, 103, 2, 114, 116, 0, 1, 106, 107, 2, 114, 116, 0, 1, 106, 115, 2, 102, 0, 1, 107, 2, 17, 67, 11, 18, 69, 12, 12, 0, 1, 107, 2, 100, 0, 1, 107, 2, 100, 101, 12, 0, 1, 107, 2, 107, 97, 0, 1, 107, 2, 108, 108, 101, 103, 12, 12, 12, 0, 1, 107, 2, 108, 108, 101, 107, 116, 32, 0, 1, 107, 2, 109, 109, 101, 110, 116, 17, 65, 12, 12, 12, 0, 1, 107, 2, 109, 109, 101, 114, 99, 105, 101, 108, 12, 12, 0, 1, 107, 2, 109, 112, 97, 103, 0, 1, 107, 2, 110, 116, 111, 114, 0, 1, 107, 2, 115, 107, 111, 0, 1, 107, 2, 115, 116, 18, 69, 0, 1, 107, 2, 115, 116, 32, 0, 1, 107, 2, 115, 116, 101, 115, 107, 97, 98, 0, 1, 107, 2, 115, 116, 101, 115, 107, 97, 102, 116, 0, 1, 107, 110, 97, 98, 2, 115, 112, 0, 1, 107, 111, 107, 2, 115, 0, 1, 107, 114, 97, 110, 0, 1, 107, 114, 97, 110, 2, 17, 67, 0, 1, 107, 115, 2, 115, 118, 195, 166, 114, 116, 101, 0, 1, 107, 115, 97, 107, 0, 1, 107, 115, 105, 100, 0, 1, 107, 115, 111, 114, 107, 105, 109, 2, 112, 0, 1, 108, 2, 18, 68, 0, 1, 108, 2, 18, 74, 17, 67, 18, 69, 0, 1, 108, 2, 107, 17, 65, 0, 1, 108, 2, 107, 117, 109, 0, 1, 108, 97, 103, 2, 112, 112, 101, 114, 101, 0, 1, 108, 101, 109, 21, 2, 110, 0, 1, 108, 105, 107, 0, 1, 108, 105, 112, 2, 116, 0, 1, 108, 107, 2, 110, 0, 1, 108, 111, 107, 2, 115, 115, 97, 0, 1, 108, 111, 107, 2, 115, 116, 0, 1, 108, 112, 2, 109, 12, 0, 1, 108, 115, 2, 103, 0, 1, 109, 2, 115, 107, 101, 0, 1, 109, 2, 115, 115, 101, 116, 12, 12, 0, 1, 109, 101, 2, 12, 0, 1, 109, 114, 101, 116, 0, 1, 110, 2, 109, 105, 0, 1, 110, 17, 67, 2, 18, 71, 12, 12, 0, 1, 110, 97, 107, 2, 110, 0, 1, 110, 103, 2, 109, 0, 1, 110, 103, 111, 107, 101, 114, 2, 115, 99, 101, 114, 101, 0, 1, 110, 107, 2, 106, 0, 1, 110, 111, 2, 109, 0, 1, 112, 2, 107, 101, 114, 12, 12, 0, 1, 112, 2, 108, 0, 1, 112, 2, 108, 115, 107, 0, 1, 112, 2, 115, 116, 116, 114, 97, 117, 0, 1, 112, 101, 100, 2, 116, 0, 1, 114, 2, 18, 71, 18, 70, 12, 0, 1, 114, 2, 100, 0, 1, 114, 2, 107, 18, 76, 12, 0, 1, 114, 2, 109, 17, 67, 18, 70, 0, 1, 114, 2, 115, 116, 12, 0, 1, 114, 17, 67, 2, 109, 18, 69, 0, 1, 114, 17, 67, 2, 115, 107, 0, 1, 114, 18, 71, 2, 106, 0, 1, 114, 18, 73, 2, 18, 66, 101, 110, 0, 1, 114, 18, 73, 2, 116, 18, 69, 0, 1, 114, 98, 2, 100, 101, 114, 0, 1, 114, 98, 2, 115, 116, 101, 110, 0, 1, 114, 100, 121, 104, 0, 1, 114, 102, 2, 109, 97, 0, 1, 114, 102, 2, 115, 115, 12, 12, 0, 1, 114, 103, 2, 115, 115, 105, 12, 0, 1, 114, 107, 2, 109, 0, 1, 114, 107, 2, 115, 0, 1, 114, 107, 2, 118, 195, 166, 0, 1, 114, 107, 105, 109, 0, 1, 114, 112, 2, 98, 108, 101, 0, 1, 114, 112, 2, 115, 12, 0, 1, 114, 112, 2, 115, 116, 105, 0, 1, 114, 112, 2, 118, 17, 65, 12, 0, 1, 114, 116, 2, 17, 67, 18, 69, 0, 1, 114, 116, 2, 106, 97, 110, 0, 1, 114, 116, 2, 109, 0, 1, 114, 116, 2, 109, 109, 101, 12, 0, 1, 114, 116, 2, 118, 12, 0, 1, 114, 116, 101, 109, 0, 1, 114, 116, 110, 111, 107, 2, 108, 108, 195, 184, 114, 0, 1, 115, 2, 108, 0, 1, 115, 2, 108, 108, 121, 115, 12, 12, 0, 1, 115, 2, 112, 114, 97, 0, 1, 116, 2, 116, 17, 65, 0, 1, 116, 97, 2, 109, 0, 1, 116, 101, 98, 2, 110, 101, 116, 0, 1, 116, 110, 111, 107, 0, 1, 116, 115, 2, 100, 32, 0, 1, 116, 115, 2, 109, 18, 69, 0, 1, 116, 115, 101, 116, 2, 115, 116, 101, 114, 111, 110, 0, 1, 116, 117, 97, 2, 12, 0, 1, 118, 2, 107, 18, 76, 12, 0, 1, 122, 105, 107, 115, 2, 102, 114, 101, 110, 0, 2, 18, 66, 18, 69, 0, 2, 18, 71, 18, 69, 12, 0, 2, 18, 71, 18, 76, 12, 0, 2, 98, 108, 18, 69, 0, 2, 98, 108, 97, 12, 0, 2, 107, 97, 17, 67, 0, 2, 108, 115, 101, 110, 0, 2, 112, 112, 111, 115, 105, 116, 0, 2, 115, 107, 111, 12, 0, 2, 115, 116, 105, 110, 100, 105, 0, 2, 118, 101, 106, 12, 0, 2, 118, 105, 12, 0, 8, 17, 67, 2, 32, 0, 8, 116, 115, 2, 114, 32, 0, 100, 1, 103, 2, 115, 0, 111, 1, 112, 109, 97, 104, 115, 0, 4, 1, 101, 108, 2, 112, 97, 114, 3, 39, 6, 0, 1, 115, 2, 109, 97, 108, 0, 8, 107, 2, 109, 112, 97, 115, 0, 8, 114, 107, 2, 107, 101, 116, 116, 0, 8, 115, 111, 108, 105, 102, 2, 102, 105, 32, 0, 8, 116, 2, 98, 97, 107, 0, 105, 114, 101, 1, 109, 101, 109, 3, 39, 6, 110, 12, 0, 4, 1, 107, 2, 109, 97, 3, 39, 12, 0, 1, 108, 2, 116, 117, 115, 0, 1, 109, 115, 2, 107, 105, 110, 103, 0, 2, 115, 18, 76, 0, 101, 1, 17, 67, 2, 100, 101, 0, 111, 1, 122, 0, 4, 103, 101, 100, 1, 102, 3, 39, 12, 13, 84, 0, 118, 101, 100, 1, 104, 0, 4, 101, 1, 107, 115, 2, 100, 101, 3, 39, 13, 0, 101, 1, 114, 116, 101, 98, 2, 100, 101, 0, 4, 114, 1, 107, 2, 107, 195, 165, 98, 101, 3, 39, 34, 0, 114, 1, 107, 2, 112, 105, 0, 114, 1, 107, 2, 112, 114, 195, 184, 118, 101, 0, 114, 1, 116, 115, 2, 12, 0, 118, 1, 108, 2, 101, 12, 3, 39, 40, 0, 39, 8, 3, 39, 40, 6, 0, 108, 108, 8, 114, 2, 105, 110, 103, 32, 115, 116, 111, 110, 101, 3, 39, 40, 55, 0, 4, 97, 109, 101, 115, 1, 115, 3, 39, 40, 63, 87, 0, 108, 109, 101, 115, 8, 104, 2, 32, 0, 104, 105, 111, 3, 39, 40, 105, 6, 35, 57, 39, 0, 116, 116, 101, 1, 114, 102, 2, 12, 12, 3, 39, 47, 6, 36, 0, 112, 1, 107, 115, 10, 2, 105, 28, 33, 3, 39, 48, 6, 0, 112, 111, 115, 1, 114, 112, 97, 3, 39, 48, 6, 39, 0, 107, 111, 1, 103, 110, 105, 110, 101, 109, 2, 107, 3, 39, 49, 6, 112, 0, 107, 111, 110, 1, 107, 3, 39, 49, 6, 112, 66, 0, 107, 108, 97, 104, 111, 109, 97, 3, 39, 49, 55, 108, 105, 6, 39, 63, 108, 0, 114, 1, 114, 2, 103, 3, 39, 51, 0, 108, 1, 100, 105, 21, 3, 39, 55, 0, 108, 105, 101, 116, 1, 103, 110, 111, 109, 3, 39, 55, 6, 37, 13, 84, 0, 4, 103, 1, 108, 107, 3, 39, 58, 0, 103, 1, 114, 112, 115, 0, 103, 1, 116, 2, 116, 117, 114, 0, 103, 8, 118, 2, 32, 0, 118, 1, 108, 2, 32, 109, 105, 103, 32, 0, 103, 101, 1, 108, 107, 3, 39, 58, 4, 13, 0, 103, 1, 104, 2, 97, 110, 3, 39, 58, 79, 0, 109, 1, 107, 114, 97, 115, 3, 39, 63, 0, 4, 109, 109, 101, 1, 110, 101, 114, 2, 12, 3, 39, 63, 6, 36, 0, 109, 109, 195, 169, 1, 110, 101, 114, 2, 12, 0, 109, 101, 116, 1, 107, 3, 39, 63, 6, 36, 47, 0, 109, 109, 101, 114, 115, 1, 107, 2, 32, 3, 39, 63, 6, 107, 34, 87, 0, 109, 97, 110, 8, 3, 39, 63, 6, 108, 50, 0, 98, 111, 8, 3, 39, 69, 6, 39, 0, 114, 103, 1, 101, 103, 2, 105, 110, 101, 3, 39, 79, 0, 103, 101, 1, 116, 111, 102, 2, 110, 3, 39, 79, 6, 36, 0, 103, 110, 1, 114, 112, 2, 111, 3, 39, 79, 50, 0, 112, 104, 105, 97, 1, 115, 3, 39, 81, 6, 37, 108, 0, 4, 118, 1, 107, 2, 101, 110, 100, 3, 39, 82, 0, 118, 1, 107, 117, 118, 2, 97, 114, 0, 118, 1, 110, 2, 97, 12, 12, 0, 118, 1, 110, 2, 101, 108, 108, 0, 118, 1, 110, 2, 101, 109, 12, 0, 118, 1, 110, 2, 105, 99, 17, 65, 0, 118, 1, 110, 101, 114, 2, 101, 114, 0, 118, 1, 116, 2, 195, 184, 114, 0, 118, 1, 116, 97, 2, 101, 114, 0, 118, 2, 195, 166, 114, 110, 12, 0, 118, 1, 108, 115, 2, 97, 107, 3, 39, 82, 6, 0, 118, 105, 8, 114, 112, 2, 110, 115, 3, 39, 82, 6, 36, 0, 4, 100, 1, 103, 2, 116, 17, 65, 103, 3, 39, 84, 0, 100, 1, 103, 2, 116, 114, 0, 100, 1, 108, 98, 0, 115, 1, 114, 116, 2, 115, 97, 109, 102, 117, 110, 100, 3, 39, 87, 0, 115, 104, 1, 104, 115, 2, 111, 110, 101, 3, 39, 89, 6, 0, 105, 1, 116, 2, 108, 3, 39, 108, 0, 111, 114, 1, 107, 2, 100, 3, 39, 112, 12, 19, 0, 111, 118, 110, 1, 114, 107, 105, 109, 3, 39, 112, 58, 50, 0, 4, 111, 1, 119, 3, 40, 0, 117, 0, 117, 1, 108, 0, 4, 111, 3, 40, 12, 0, 111, 1, 122, 2, 109, 0, 4, 111, 100, 1, 102, 3, 40, 12, 70, 0, 111, 100, 1, 104, 0, 117, 99, 104, 101, 1, 100, 3, 40, 12, 89, 0, 111, 107, 101, 1, 114, 98, 3, 40, 49, 0, 111, 110, 97, 103, 104, 3, 40, 50, 108, 0, 4, 111, 103, 105, 101, 1, 98, 3, 40, 79, 37, 0, 111, 103, 105, 101, 1, 119, 0, 103, 110, 1, 108, 111, 99, 2, 101, 3, 55, 6, 112, 66, 57, 0, 105, 120, 1, 114, 99, 3, 58, 6, 35, 0, 105, 115, 1, 110, 97, 100, 3, 58, 6, 110, 0, 105, 110, 116, 1, 112, 2, 32, 3, 58, 107, 66, 0, 105, 110, 116, 101, 110, 101, 1, 112, 3, 58, 107, 66, 13, 50, 106, 0, 105, 110, 116, 101, 1, 112, 3, 58, 107, 66, 47, 13, 0, 105, 110, 116, 101, 114, 1, 112, 3, 58, 107, 66, 47, 112, 0, 119, 1, 116, 2, 101, 114, 3, 110, 40, 0, 117, 1, 114, 103, 2, 99, 104, 111, 3, 110, 58, 0, 117, 115, 101, 1, 104, 3, 110, 58, 87, 0, 4, 1, 107, 2, 98, 98, 101, 114, 3, 111, 0, 1, 112, 2, 114, 0, 1, 112, 2, 115, 116, 109, 111, 100, 0, 1, 114, 17, 67, 2, 18, 66, 18, 69, 0, 1, 118, 115, 2, 103, 101, 114, 0, 4, 97, 114, 1, 98, 2, 100, 105, 110, 103, 3, 111, 12, 0, 114, 2, 108, 0, 117, 114, 110, 101, 1, 98, 3, 111, 12, 50, 0, 114, 103, 2, 101, 108, 3, 111, 12, 58, 0, 121, 101, 114, 8, 102, 3, 111, 13, 57, 6, 36, 0, 121, 101, 114, 101, 110, 8, 102, 3, 111, 13, 57, 6, 36, 106, 50, 0, 121, 101, 114, 1, 102, 3, 111, 13, 57, 36, 0, 114, 108, 121, 8, 2, 32, 3, 111, 16, 55, 6, 37, 0, 1, 104, 2, 108, 100, 105, 110, 103, 3, 111, 40, 0, 118, 2, 101, 114, 104, 101, 97, 100, 3, 111, 40, 82, 0, 97, 115, 116, 98, 101, 101, 102, 1, 114, 3, 111, 40, 87, 70, 69, 37, 81, 0, 116, 105, 111, 110, 1, 109, 119, 111, 108, 115, 3, 111, 40, 89, 20, 13, 50, 0, 4, 1, 103, 2, 107, 97, 114, 116, 12, 3, 111, 58, 0, 117, 1, 115, 2, 108, 0, 112, 114, 97, 104, 3, 111, 58, 48, 34, 35, 0, 4, 108, 101, 1, 112, 109, 105, 119, 3, 111, 58, 55, 0, 108, 108, 8, 114, 2, 32, 12, 0, 108, 108, 115, 8, 114, 2, 32, 3, 111, 58, 55, 87, 0, 4, 118, 1, 108, 2, 101, 110, 12, 12, 3, 111, 82, 0, 118, 1, 118, 2, 101, 0, 4, 1, 17, 67, 2, 17, 67, 11, 101, 116, 32, 12, 12, 3, 112, 0, 1, 17, 67, 2, 18, 66, 12, 0, 1, 17, 67, 2, 18, 66, 116, 0, 1, 17, 67, 2, 18, 68, 11, 0, 1, 17, 67, 2, 18, 74, 110, 0, 1, 17, 67, 2, 98, 98, 101, 114, 32, 12, 12, 0, 1, 17, 67, 2, 103, 103, 12, 0, 1, 17, 67, 2, 109, 0, 1, 17, 67, 2, 109, 18, 69, 0, 1, 17, 67, 2, 114, 114, 0, 1, 17, 67, 2, 115, 17, 67, 18, 76, 0, 1, 17, 67, 102, 2, 116, 0, 1, 18, 66, 2, 108, 100, 0, 1, 18, 66, 2, 109, 0, 1, 18, 67, 2, 18, 71, 11, 101, 12, 12, 0, 1, 18, 67, 2, 18, 71, 108, 101, 12, 0, 1, 18, 67, 2, 115, 116, 0, 1, 18, 68, 2, 18, 74, 0, 1, 18, 71, 2, 116, 0, 1, 18, 73, 2, 102, 0, 1, 18, 73, 2, 108, 112, 0, 1, 18, 73, 2, 108, 116, 0, 1, 18, 73, 2, 116, 0, 1, 18, 73, 2, 116, 116, 0, 1, 18, 75, 2, 110, 17, 67, 0, 1, 97, 17, 67, 2, 115, 0, 1, 98, 2, 18, 66, 18, 69, 0, 1, 98, 2, 115, 115, 0, 1, 99, 2, 99, 107, 0, 1, 99, 2, 114, 115, 0, 1, 100, 2, 103, 32, 12, 0, 1, 100, 2, 110, 97, 108, 100, 0, 1, 102, 2, 110, 116, 0, 1, 103, 2, 100, 116, 0, 1, 104, 2, 99, 107, 12, 0, 1, 104, 2, 102, 0, 1, 104, 2, 108, 108, 12, 0, 1, 104, 2, 110, 103, 0, 1, 104, 2, 115, 112, 105, 99, 101, 0, 1, 104, 99, 2, 107, 12, 0, 1, 104, 116, 2, 109, 97, 115, 32, 0, 1, 106, 2, 18, 66, 11, 18, 76, 0, 1, 106, 2, 98, 21, 0, 1, 106, 2, 114, 116, 0, 1, 107, 2, 98, 108, 105, 110, 103, 0, 1, 107, 2, 103, 108, 12, 0, 1, 107, 2, 103, 116, 12, 0, 1, 107, 2, 110, 17, 67, 0, 1, 107, 2, 112, 97, 114, 0, 1, 107, 2, 115, 116, 32, 111, 103, 32, 108, 111, 103, 105, 0, 1, 107, 2, 115, 116, 98, 97, 114, 0, 1, 107, 2, 115, 116, 112, 108, 97, 110, 0, 1, 107, 2, 115, 116, 112, 114, 105, 115, 0, 1, 107, 2, 115, 116, 114, 195, 165, 100, 0, 1, 107, 2, 115, 116, 115, 107, 111, 108, 101, 0, 1, 107, 2, 115, 116, 116, 105, 108, 115, 107, 117, 100, 0, 1, 107, 2, 115, 116, 118, 97, 110, 101, 0, 1, 107, 101, 98, 2, 115, 116, 0, 1, 107, 101, 115, 108, 101, 104, 2, 115, 116, 0, 1, 107, 111, 114, 102, 2, 115, 116, 0, 1, 107, 115, 2, 100, 0, 1, 107, 115, 103, 97, 100, 114, 101, 118, 104, 2, 115, 116, 0, 1, 107, 121, 111, 98, 2, 116, 0, 1, 108, 2, 18, 66, 11, 18, 76, 0, 1, 108, 2, 100, 116, 114, 195, 166, 107, 0, 1, 108, 2, 103, 102, 105, 108, 0, 1, 108, 2, 116, 0, 1, 108, 18, 71, 2, 18, 74, 0, 1, 108, 32, 101, 107, 107, 166, 195, 114, 116, 2, 100, 0, 1, 108, 32, 107, 166, 195, 114, 116, 2, 100, 0, 1, 108, 32, 114, 101, 107, 107, 166, 195, 114, 116, 2, 100, 0, 1, 108, 32, 115, 101, 107, 107, 166, 195, 114, 116, 2, 100, 0, 1, 108, 32, 116, 101, 107, 107, 117, 114, 116, 2, 100, 0, 1, 108, 98, 2, 107, 12, 0, 1, 108, 100, 114, 111, 106, 2, 100, 0, 1, 108, 107, 2, 115, 116, 114, 101, 0, 1, 108, 108, 97, 102, 2, 115, 0, 1, 108, 114, 111, 102, 2, 100, 115, 0, 1, 109, 2, 110, 105, 116, 111, 114, 0, 1, 110, 2, 110, 17, 67, 0, 1, 110, 2, 115, 32, 0, 1, 110, 107, 2, 116, 110, 0, 1, 110, 107, 2, 116, 116, 0, 1, 110, 115, 2, 116, 0, 1, 112, 2, 108, 116, 0, 1, 112, 2, 112, 105, 100, 111, 108, 12, 12, 0, 1, 112, 107, 99, 97, 106, 2, 116, 0, 1, 112, 115, 2, 110, 115, 111, 114, 0, 1, 114, 2, 17, 67, 11, 12, 12, 0, 1, 114, 2, 99, 107, 0, 1, 114, 2, 109, 107, 97, 103, 101, 0, 1, 114, 18, 73, 2, 18, 66, 0, 1, 114, 18, 73, 2, 116, 0, 1, 114, 98, 2, 100, 0, 1, 114, 100, 2, 115, 99, 104, 101, 0, 1, 114, 102, 2, 109, 0, 1, 114, 102, 2, 110, 116, 0, 1, 114, 102, 2, 115, 116, 12, 0, 1, 114, 107, 2, 107, 101, 116, 17, 67, 0, 1, 114, 108, 97, 118, 104, 2, 115, 0, 1, 114, 116, 2, 106, 12, 0, 1, 114, 116, 2, 107, 108, 0, 1, 114, 116, 2, 108, 100, 0, 1, 114, 116, 2, 116, 115, 0, 1, 114, 116, 110, 111, 107, 2, 108, 0, 1, 114, 116, 120, 111, 102, 2, 116, 0, 1, 115, 2, 106, 97, 12, 0, 1, 115, 21, 2, 110, 32, 0, 1, 115, 21, 2, 110, 115, 32, 0, 1, 116, 2, 103, 116, 12, 0, 1, 116, 2, 108, 107, 0, 1, 116, 2, 109, 97, 115, 32, 0, 1, 116, 2, 116, 0, 1, 116, 115, 2, 112, 12, 12, 0, 1, 118, 2, 103, 0, 1, 118, 2, 103, 116, 12, 0, 1, 118, 108, 101, 115, 2, 112, 0, 2, 18, 68, 25, 0, 2, 18, 71, 12, 0, 2, 98, 98, 17, 65, 12, 12, 12, 0, 2, 99, 104, 101, 0, 2, 102, 17, 67, 0, 2, 107, 0, 2, 108, 100, 32, 0, 2, 108, 100, 101, 0, 2, 108, 100, 101, 32, 0, 2, 109, 32, 0, 2, 109, 101, 103, 110, 0, 2, 109, 107, 0, 2, 109, 114, 195, 165, 100, 0, 2, 109, 115, 0, 2, 109, 116, 97, 108, 101, 0, 2, 112, 97, 100, 12, 0, 2, 112, 101, 102, 116, 101, 114, 12, 0, 2, 112, 105, 108, 100, 110, 101, 12, 0, 2, 112, 111, 102, 114, 101, 0, 2, 112, 111, 102, 114, 101, 12, 0, 2, 114, 103, 97, 12, 0, 2, 115, 17, 67, 18, 69, 0, 2, 116, 116, 97, 119, 97, 0, 2, 116, 116, 101, 110, 100, 101, 0, 2, 116, 116, 111, 0, 2, 120, 0, 8, 2, 108, 105, 118, 101, 114, 0, 8, 2, 109, 97, 0, 8, 98, 2, 110, 100, 32, 0, 8, 98, 2, 110, 110, 32, 0, 8, 100, 2, 110, 32, 0, 8, 104, 2, 108, 105, 100, 97, 121, 0, 8, 104, 2, 116, 32, 0, 8, 108, 2, 103, 32, 0, 8, 108, 2, 115, 0, 8, 109, 2, 114, 116, 0, 8, 112, 2, 116, 32, 0, 8, 114, 2, 98, 105, 110, 12, 12, 0, 100, 1, 108, 107, 2, 115, 0, 100, 1, 114, 116, 2, 115, 0, 103, 1, 107, 101, 114, 2, 110, 111, 115, 99, 101, 114, 101, 0, 103, 2, 102, 105, 114, 115, 0, 103, 2, 116, 114, 101, 100, 105, 118, 101, 0, 114, 1, 110, 111, 100, 0, 114, 1, 116, 2, 32, 0, 114, 1, 116, 2, 101, 110, 0, 114, 1, 116, 2, 110, 121, 0, 114, 1, 116, 2, 115, 0, 114, 1, 116, 111, 109, 0, 114, 1, 116, 115, 97, 112, 0, 117, 114, 1, 98, 114, 97, 104, 0, 1, 112, 2, 115, 116, 121, 114, 12, 3, 112, 6, 0, 4, 111, 114, 1, 108, 102, 3, 112, 12, 0, 111, 114, 101, 1, 109, 0, 114, 1, 107, 2, 112, 0, 114, 1, 116, 2, 116, 3, 112, 12, 19, 0, 105, 108, 8, 2, 32, 3, 112, 12, 37, 59, 0, 105, 115, 1, 110, 105, 108, 108, 105, 3, 112, 12, 57, 0, 114, 103, 2, 12, 3, 112, 12, 58, 0, 4, 103, 1, 100, 108, 108, 117, 98, 3, 112, 12, 79, 0, 114, 103, 2, 105, 0, 114, 115, 1, 107, 3, 112, 12, 87, 0, 4, 114, 1, 114, 114, 101, 116, 3, 112, 34, 0, 114, 2, 107, 12, 12, 0, 114, 101, 103, 111, 110, 112, 105, 110, 101, 3, 112, 34, 36, 79, 112, 50, 15, 48, 35, 57, 50, 0, 4, 103, 1, 110, 107, 3, 112, 40, 0, 118, 2, 101, 12, 0, 118, 2, 114, 101, 0, 116, 101, 108, 101, 1, 107, 2, 116, 3, 112, 47, 13, 55, 6, 107, 0, 116, 100, 111, 103, 1, 104, 3, 112, 47, 70, 112, 79, 0, 4, 99, 99, 1, 114, 98, 2, 111, 108, 105, 3, 112, 49, 0, 103, 104, 1, 103, 32, 110, 97, 118, 0, 110, 110, 121, 1, 115, 3, 112, 50, 37, 0, 110, 116, 97, 110, 97, 1, 109, 3, 112, 50, 47, 6, 108, 50, 108, 0, 110, 100, 1, 108, 98, 3, 112, 50, 70, 0, 110, 100, 111, 110, 1, 108, 3, 112, 50, 70, 112, 50, 0, 110, 103, 1, 107, 2, 114, 101, 115, 3, 112, 50, 79, 0, 110, 111, 1, 100, 2, 118, 97, 110, 3, 112, 50, 106, 0, 108, 105, 115, 104, 1, 112, 3, 112, 55, 37, 89, 0, 108, 103, 116, 1, 115, 3, 112, 55, 47, 0, 108, 108, 97, 114, 1, 100, 3, 112, 55, 112, 0, 105, 1, 110, 97, 104, 3, 112, 57, 0, 4, 105, 110, 116, 1, 112, 2, 101, 114, 101, 3, 112, 57, 50, 47, 0, 105, 110, 116, 1, 112, 32, 116, 115, 101, 119, 0, 121, 99, 101, 1, 114, 3, 112, 57, 87, 0, 121, 101, 117, 114, 1, 118, 3, 112, 57, 116, 12, 34, 0, 4, 118, 1, 17, 67, 2, 12, 3, 112, 58, 0, 118, 1, 108, 112, 2, 12, 12, 0, 118, 2, 101, 114, 115, 12, 12, 0, 118, 2, 110, 0, 103, 114, 101, 1, 108, 3, 112, 58, 34, 112, 0, 103, 110, 1, 17, 67, 3, 112, 58, 50, 0, 118, 106, 101, 116, 1, 115, 3, 112, 58, 57, 6, 107, 47, 0, 109, 107, 111, 2, 115, 116, 3, 112, 63, 49, 112, 0, 109, 98, 97, 121, 1, 98, 3, 112, 63, 69, 4, 107, 57, 0, 109, 101, 98, 97, 99, 107, 1, 99, 3, 112, 63, 69, 6, 108, 49, 0, 4, 110, 1, 108, 108, 97, 98, 3, 112, 66, 0, 110, 1, 110, 110, 97, 2, 99, 17, 65, 0, 110, 1, 112, 109, 97, 116, 0, 110, 1, 112, 109, 111, 112, 0, 110, 1, 112, 117, 107, 0, 110, 1, 116, 101, 98, 0, 103, 110, 97, 99, 1, 99, 3, 112, 66, 35, 49, 0, 98, 121, 8, 114, 2, 110, 12, 12, 3, 112, 69, 36, 0, 4, 100, 1, 118, 2, 107, 97, 3, 112, 70, 0, 111, 100, 1, 108, 98, 0, 111, 100, 1, 108, 102, 0, 100, 121, 1, 98, 3, 112, 70, 37, 0, 100, 121, 98, 117, 105, 108, 100, 101, 114, 1, 98, 3, 112, 70, 37, 69, 37, 55, 70, 112, 0, 100, 108, 101, 1, 106, 3, 112, 70, 55, 106, 0, 100, 102, 97, 116, 104, 101, 114, 1, 103, 3, 112, 70, 81, 110, 84, 112, 0, 4, 1, 108, 2, 103, 98, 111, 103, 3, 112, 79, 0, 103, 1, 107, 2, 110, 105, 116, 0, 103, 1, 109, 115, 2, 32, 0, 103, 1, 114, 103, 0, 103, 103, 1, 114, 103, 0, 114, 103, 2, 105, 101, 0, 117, 103, 1, 100, 0, 103, 103, 121, 1, 114, 103, 3, 112, 79, 37, 0, 120, 102, 111, 114, 100, 3, 112, 79, 87, 81, 112, 12, 70, 0, 117, 103, 104, 3, 112, 81, 0, 102, 102, 115, 105, 100, 101, 3, 112, 81, 87, 6, 35, 57, 70, 0, 116, 104, 1, 114, 98, 2, 101, 114, 3, 112, 84, 0, 100, 114, 101, 116, 1, 108, 2, 12, 3, 112, 84, 34, 109, 47, 0, 4, 114, 115, 101, 116, 1, 107, 32, 116, 101, 3, 112, 87, 6, 107, 47, 0, 114, 115, 101, 116, 116, 1, 107, 0, 115, 107, 118, 97, 1, 109, 3, 112, 87, 49, 82, 6, 108, 0, 115, 99, 97, 114, 3, 112, 87, 49, 110, 0, 115, 99, 111, 101, 1, 114, 3, 112, 87, 49, 111, 58, 0, 115, 98, 111, 114, 110, 101, 3, 112, 87, 69, 4, 111, 50, 0, 8, 114, 98, 2, 100, 121, 3, 113, 58, 0, 117, 114, 98, 111, 110, 1, 98, 3, 116, 12, 69, 13, 50, 0, 97, 107, 108, 97, 110, 100, 3, 116, 58, 49, 55, 13, 50, 70, 0, 101, 98, 98, 101, 108, 115, 1, 103, 3, 116, 69, 13, 55, 87, 0, 7, 6, 112, 0, 4, 1, 109, 121, 115, 2, 116, 111, 109, 3, 0, 2, 115, 121, 107, 3, 0, 4, 3, 48, 0, 1, 10, 2, 32, 0, 112, 0, 117, 114, 118, 105, 115, 8, 3, 48, 6, 106, 12, 82, 36, 87, 0, 195, 165, 8, 2, 115, 107, 101, 3, 48, 6, 111, 0, 195, 165, 8, 2, 14, 128, 132, 130, 3, 48, 6, 112, 0, 4, 114, 111, 116, 101, 103, 101, 3, 48, 34, 39, 70, 13, 89, 6, 36, 0, 114, 111, 116, 101, 103, 195, 169, 0, 114, 101, 115, 98, 121, 116, 101, 114, 105, 97, 110, 3, 48, 34, 107, 87, 69, 114, 47, 107, 34, 37, 6, 108, 50, 0, 105, 110, 99, 101, 110, 101, 122, 3, 48, 35, 12, 66, 87, 50, 6, 36, 0, 105, 112, 101, 108, 105, 110, 101, 3, 48, 35, 57, 48, 55, 35, 57, 50, 0, 195, 169, 116, 97, 105, 110, 8, 3, 48, 36, 47, 6, 108, 66, 0, 101, 110, 101, 108, 111, 112, 101, 3, 48, 36, 50, 6, 107, 55, 39, 48, 37, 0, 105, 116, 99, 104, 112, 105, 110, 101, 3, 48, 36, 85, 89, 48, 35, 12, 57, 50, 0, 105, 115, 115, 111, 105, 114, 3, 48, 36, 87, 58, 6, 110, 12, 0, 101, 116, 101, 8, 2, 32, 3, 48, 37, 12, 47, 0, 101, 116, 101, 121, 8, 3, 48, 37, 12, 47, 37, 0, 101, 97, 110, 117, 116, 3, 48, 37, 12, 50, 112, 70, 0, 101, 97, 99, 101, 3, 48, 37, 12, 87, 0, 105, 99, 107, 117, 2, 112, 3, 48, 37, 49, 6, 112, 0, 105, 103, 103, 121, 8, 3, 48, 37, 79, 37, 0, 112, 1, 111, 116, 2, 111, 115, 116, 3, 48, 48, 0, 114, 97, 108, 105, 110, 101, 3, 48, 51, 110, 55, 37, 50, 6, 36, 0, 105, 101, 114, 114, 101, 3, 48, 57, 107, 12, 34, 0, 105, 97, 102, 8, 3, 48, 57, 110, 81, 0, 111, 105, 114, 111, 116, 8, 3, 48, 58, 110, 34, 6, 39, 0, 111, 105, 116, 105, 101, 114, 8, 3, 48, 58, 110, 47, 57, 6, 36, 0, 97, 105, 103, 101, 3, 48, 107, 12, 57, 73, 0, 101, 105, 103, 110, 111, 105, 114, 3, 48, 107, 50, 57, 58, 6, 110, 12, 0, 97, 105, 110, 116, 98, 97, 108, 108, 3, 48, 107, 57, 50, 47, 69, 111, 12, 55, 0, 97, 105, 108, 108, 101, 2, 116, 3, 48, 108, 57, 6, 107, 0, 97, 115, 97, 100, 101, 110, 97, 3, 48, 108, 87, 108, 70, 6, 37, 50, 108, 0, 97, 115, 115, 97, 103, 101, 114, 8, 3, 48, 108, 87, 108, 87, 57, 6, 36, 34, 0, 97, 108, 109, 2, 32, 98, 101, 97, 99, 104, 3, 48, 110, 12, 63, 0, 97, 114, 102, 97, 105, 116, 3, 48, 110, 81, 6, 107, 0, 111, 115, 116, 104, 117, 109, 3, 48, 111, 87, 47, 105, 6, 40, 63, 0, 4, 195, 165, 2, 102, 117, 110, 100, 3, 48, 112, 0, 195, 165, 2, 108, 195, 166, 103, 0, 195, 165, 2, 118, 105, 114, 107, 0, 195, 165, 8, 2, 108, 105, 100, 101, 0, 195, 165, 8, 2, 118, 105, 115, 0, 111, 110, 121, 3, 48, 112, 50, 37, 0, 117, 110, 99, 104, 108, 105, 110, 101, 3, 48, 112, 50, 89, 55, 35, 57, 50, 0, 101, 97, 114, 108, 8, 2, 32, 3, 48, 116, 12, 55, 0, 101, 114, 116, 104, 3, 48, 116, 12, 85, 0, 101, 114, 107, 105, 110, 115, 3, 48, 116, 49, 36, 50, 87, 0, 101, 114, 99, 121, 3, 48, 116, 87, 37, 0, 101, 117, 103, 101, 111, 116, 3, 48, 116, 89, 6, 39, 0, 98, 1, 109, 97, 99, 2, 101, 108, 3, 69, 0, 4, 104, 1, 101, 115, 111, 106, 3, 81, 0, 104, 1, 108, 97, 114, 0, 104, 97, 101, 108, 1, 97, 114, 3, 81, 108, 6, 107, 55, 0, 115, 101, 117, 3, 87, 116, 58, 0, 7, 6, 113, 0, 117, 1, 101, 116, 2, 105, 108, 97, 3, 6, 49, 0, 117, 101, 1, 21, 3, 8, 49, 0, 3, 49, 0, 117, 101, 116, 1, 117, 111, 98, 3, 49, 7, 36, 0, 117, 105, 99, 104, 101, 3, 49, 37, 89, 0, 4, 117, 105, 106, 111, 116, 101, 3, 49, 37, 89, 6, 112, 47, 0, 117, 105, 120, 111, 116, 101, 0, 117, 101, 101, 110, 3, 49, 58, 37, 12, 50, 0, 117, 97, 114, 116, 101, 114, 3, 49, 58, 111, 47, 112, 0, 117, 2, 105, 115, 108, 105, 110, 103, 3, 49, 82, 0, 117, 105, 2, 122, 3, 49, 82, 37, 0, 117, 101, 98, 101, 99, 3, 49, 82, 37, 69, 6, 107, 49, 0, 117, 101, 122, 3, 49, 107, 12, 87, 0, 7, 6, 114, 0, 4, 1, 101, 2, 101, 32, 24, 3, 0, 4, 1, 111, 112, 115, 110, 97, 114, 116, 2, 116, 3, 0, 4, 1, 166, 195, 2, 101, 114, 32, 24, 3, 0, 100, 1, 165, 195, 104, 3, 0, 105, 1, 10, 2, 115, 107, 28, 33, 3, 8, 51, 37, 0, 100, 1, 165, 195, 104, 2, 101, 3, 12, 0, 97, 109, 105, 114, 101, 122, 3, 21, 101, 115, 0, 4, 1, 98, 3, 34, 0, 1, 101, 104, 2, 32, 0, 1, 101, 115, 2, 32, 0, 1, 101, 118, 104, 0, 2, 25, 0, 4, 101, 1, 97, 105, 100, 3, 34, 6, 36, 0, 101, 1, 114, 97, 105, 100, 0, 101, 110, 111, 105, 114, 3, 34, 13, 50, 58, 6, 110, 12, 0, 101, 118, 111, 105, 114, 1, 32, 117, 97, 3, 34, 13, 58, 6, 35, 12, 34, 0, 105, 99, 107, 115, 104, 97, 119, 3, 34, 36, 49, 89, 112, 12, 0, 105, 99, 107, 115, 104, 97, 119, 101, 114, 3, 34, 36, 49, 89, 112, 12, 112, 0, 101, 103, 1, 166, 195, 115, 2, 101, 110, 3, 34, 36, 57, 0, 101, 115, 101, 114, 118, 111, 105, 114, 8, 3, 34, 36, 87, 107, 34, 82, 39, 6, 35, 12, 0, 101, 115, 101, 114, 118, 111, 105, 114, 3, 34, 36, 87, 107, 34, 82, 39, 35, 12, 0, 4, 101, 97, 108, 105, 116, 121, 3, 34, 37, 6, 108, 55, 37, 47, 37, 0, 101, 97, 108, 105, 116, 121, 1, 32, 108, 97, 117, 116, 114, 105, 118, 0, 105, 111, 106, 97, 3, 34, 37, 6, 112, 49, 108, 0, 101, 101, 99, 101, 3, 34, 37, 12, 87, 0, 101, 99, 117, 116, 3, 34, 37, 49, 112, 70, 0, 101, 115, 101, 97, 114, 99, 104, 3, 34, 37, 87, 6, 116, 12, 74, 0, 105, 99, 104, 101, 108, 105, 101, 117, 3, 34, 37, 89, 55, 57, 6, 116, 0, 111, 117, 103, 101, 3, 34, 40, 12, 89, 0, 4, 100, 1, 97, 103, 2, 101, 3, 34, 70, 0, 100, 1, 97, 115, 2, 101, 108, 0, 100, 1, 101, 118, 2, 101, 25, 25, 0, 100, 1, 111, 2, 101, 108, 12, 12, 0, 100, 1, 111, 2, 101, 110, 12, 12, 0, 100, 1, 117, 98, 2, 101, 25, 0, 100, 1, 121, 2, 101, 32, 0, 97, 106, 97, 104, 3, 34, 110, 73, 108, 0, 4, 101, 1, 21, 2, 32, 3, 34, 112, 0, 101, 1, 103, 2, 32, 0, 101, 1, 118, 97, 104, 0, 111, 113, 117, 101, 102, 111, 114, 116, 3, 34, 112, 49, 81, 6, 112, 12, 0, 111, 98, 105, 101, 8, 3, 34, 112, 69, 37, 0, 111, 100, 110, 101, 121, 3, 34, 112, 70, 50, 37, 0, 111, 103, 101, 114, 3, 34, 112, 73, 112, 0, 117, 115, 115, 101, 108, 108, 3, 34, 112, 87, 14, 55, 0, 117, 115, 104, 109, 111, 114, 101, 3, 34, 112, 89, 63, 111, 12, 0, 111, 97, 100, 8, 2, 32, 3, 34, 116, 58, 70, 0, 4, 3, 51, 0, 114, 0, 105, 103, 104, 116, 3, 51, 6, 35, 57, 47, 0, 101, 8, 116, 110, 101, 2, 32, 3, 51, 6, 36, 0, 105, 1, 10, 2, 28, 33, 3, 51, 7, 37, 0, 105, 99, 104, 105, 101, 3, 51, 37, 74, 37, 0, 101, 103, 103, 97, 101, 3, 51, 107, 79, 107, 57, 0, 101, 97, 103, 97, 110, 3, 51, 107, 79, 108, 50, 0, 101, 115, 111, 108, 117, 116, 105, 111, 110, 3, 51, 107, 87, 39, 55, 40, 89, 6, 39, 50, 0, 117, 110, 1, 32, 101, 109, 111, 104, 3, 51, 112, 50, 0, 104, 101, 117, 2, 109, 97, 3, 51, 112, 57, 0, 117, 103, 98, 121, 3, 51, 112, 79, 69, 37, 0, 104, 111, 100, 101, 8, 3, 51, 116, 58, 70, 0, 100, 1, 111, 2, 114, 105, 110, 3, 70, 0, 4, 101, 1, 101, 100, 2, 115, 3, 112, 0, 101, 1, 101, 106, 2, 115, 0, 101, 1, 166, 195, 2, 32, 24, 0, 101, 1, 166, 195, 108, 0, 7, 6, 115, 0, 1, 105, 109, 109, 111, 107, 2, 101, 3, 0, 4, 1, 101, 99, 99, 117, 115, 3, 6, 0, 1, 105, 109, 111, 114, 112, 109, 111, 107, 0, 97, 99, 101, 1, 108, 97, 3, 6, 87, 108, 87, 0, 1, 105, 109, 109, 111, 107, 2, 32, 3, 8, 0, 4, 99, 1, 97, 98, 97, 116, 2, 111, 3, 8, 87, 49, 0, 99, 1, 105, 115, 110, 97, 114, 102, 2, 111, 0, 111, 109, 1, 21, 21, 3, 8, 87, 112, 63, 0, 105, 101, 103, 102, 114, 105, 101, 100, 3, 21, 100, 101, 0, 97, 105, 110, 116, 101, 3, 21, 102, 114, 0, 105, 103, 110, 111, 114, 101, 3, 21, 105, 116, 0, 4, 3, 87, 0, 1, 10, 2, 32, 28, 33, 14, 128, 128, 129, 0, 1, 101, 99, 98, 97, 0, 1, 101, 99, 101, 114, 0, 1, 101, 99, 120, 101, 0, 1, 101, 100, 101, 108, 114, 101, 100, 110, 97, 0, 1, 110, 101, 100, 105, 115, 101, 114, 0, 1, 110, 101, 114, 101, 102, 114, 101, 116, 110, 105, 0, 1, 110, 101, 116, 115, 105, 115, 107, 101, 0, 1, 121, 107, 0, 2, 17, 65, 0, 2, 99, 105, 103, 97, 114, 0, 2, 105, 101, 0, 2, 106, 0, 2, 111, 109, 107, 111, 115, 116, 12, 0, 2, 115, 104, 0, 99, 2, 101, 0, 115, 0, 99, 1, 105, 100, 2, 105, 112, 3, 87, 6, 0, 99, 101, 110, 101, 1, 105, 2, 115, 3, 87, 6, 36, 50, 13, 0, 111, 109, 1, 111, 109, 111, 114, 107, 3, 87, 6, 39, 63, 0, 97, 105, 110, 116, 3, 87, 6, 107, 57, 50, 70, 0, 4, 105, 103, 1, 32, 97, 114, 102, 2, 32, 3, 87, 35, 57, 0, 105, 103, 1, 32, 100, 101, 114, 2, 32, 0, 105, 103, 1, 32, 100, 111, 108, 2, 32, 0, 105, 103, 1, 32, 100, 184, 195, 107, 115, 2, 32, 0, 105, 103, 1, 32, 100, 184, 195, 114, 98, 2, 32, 0, 105, 103, 1, 32, 101, 2, 32, 12, 0, 105, 103, 1, 32, 101, 2, 32, 116, 105, 108, 0, 105, 103, 1, 32, 101, 100, 2, 32, 0, 105, 103, 1, 32, 101, 100, 110, 101, 118, 2, 32, 0, 105, 103, 1, 32, 101, 103, 103, 121, 104, 2, 32, 0, 105, 103, 1, 32, 101, 108, 184, 195, 102, 2, 32, 0, 105, 103, 1, 32, 101, 114, 166, 195, 108, 107, 114, 101, 2, 32, 0, 105, 103, 1, 32, 101, 114, 184, 195, 103, 2, 32, 100, 101, 116, 0, 105, 103, 1, 32, 103, 101, 110, 115, 2, 32, 0, 105, 103, 1, 32, 103, 110, 97, 118, 116, 2, 32, 0, 105, 103, 1, 32, 103, 111, 108, 115, 2, 32, 0, 105, 103, 1, 32, 103, 111, 116, 2, 32, 0, 105, 103, 1, 32, 107, 97, 2, 32, 0, 105, 103, 1, 32, 107, 105, 103, 2, 32, 0, 105, 103, 1, 32, 108, 105, 116, 2, 32, 0, 105, 103, 1, 32, 109, 111, 107, 2, 32, 0, 105, 103, 1, 32, 110, 17, 65, 2, 32, 116, 105, 108, 0, 105, 103, 1, 32, 110, 97, 104, 2, 32, 0, 105, 103, 1, 32, 110, 97, 109, 2, 32, 0, 105, 103, 1, 32, 110, 101, 100, 2, 32, 0, 105, 103, 1, 32, 110, 117, 104, 2, 32, 0, 105, 103, 1, 32, 111, 114, 116, 101, 98, 2, 32, 0, 105, 103, 1, 32, 114, 101, 2, 32, 0, 105, 103, 1, 32, 114, 101, 2, 32, 116, 105, 108, 0, 105, 103, 1, 32, 114, 101, 115, 2, 32, 111, 109, 0, 105, 103, 1, 32, 114, 111, 102, 2, 32, 0, 105, 103, 1, 32, 114, 111, 114, 116, 101, 98, 2, 32, 0, 105, 103, 1, 32, 114, 165, 195, 102, 2, 32, 0, 105, 103, 1, 32, 114, 165, 195, 108, 115, 2, 32, 0, 105, 103, 1, 32, 114, 184, 195, 2, 32, 0, 105, 103, 1, 32, 116, 2, 32, 0, 105, 103, 1, 32, 116, 97, 115, 2, 32, 0, 105, 103, 1, 32, 116, 101, 2, 32, 0, 105, 103, 1, 32, 116, 101, 2, 32, 116, 105, 108, 0, 105, 103, 1, 32, 118, 97, 103, 2, 32, 0, 105, 103, 1, 32, 118, 97, 103, 2, 32, 116, 105, 108, 0, 105, 103, 1, 32, 165, 195, 108, 115, 2, 32, 0, 105, 103, 1, 32, 165, 195, 112, 2, 32, 0, 105, 103, 1, 32, 165, 195, 115, 2, 32, 111, 109, 0, 105, 103, 1, 32, 165, 195, 116, 115, 2, 32, 0, 105, 103, 8, 2, 32, 97, 102, 32, 0, 105, 103, 8, 2, 32, 97, 108, 101, 110, 101, 0, 105, 103, 8, 2, 32, 102, 111, 114, 0, 105, 103, 8, 2, 32, 105, 32, 100, 101, 17, 67, 0, 105, 103, 8, 2, 32, 105, 110, 100, 32, 0, 105, 103, 8, 2, 32, 109, 101, 100, 0, 105, 103, 8, 2, 32, 111, 109, 0, 105, 103, 8, 2, 32, 111, 118, 101, 114, 0, 105, 103, 8, 2, 32, 112, 195, 165, 32, 0, 105, 103, 8, 2, 32, 115, 101, 108, 118, 0, 105, 103, 8, 2, 32, 117, 100, 32, 0, 105, 103, 8, 32, 101, 100, 2, 32, 116, 105, 108, 0, 105, 103, 8, 32, 102, 97, 2, 32, 0, 105, 103, 8, 32, 105, 2, 32, 0, 105, 103, 8, 32, 110, 97, 104, 2, 32, 0, 105, 103, 104, 116, 115, 101, 101, 105, 110, 103, 3, 87, 35, 57, 47, 87, 37, 12, 36, 66, 0, 99, 101, 110, 101, 3, 87, 36, 50, 106, 0, 99, 101, 110, 101, 114, 3, 87, 36, 50, 112, 0, 4, 105, 103, 1, 32, 101, 114, 97, 98, 2, 32, 3, 87, 37, 0, 105, 103, 1, 32, 101, 114, 97, 98, 2, 32, 116, 105, 108, 0, 105, 103, 2, 32, 100, 101, 116, 0, 105, 103, 2, 32, 117, 110, 100, 115, 107, 121, 108, 100, 12, 0, 101, 97, 116, 116, 108, 101, 3, 87, 37, 6, 108, 47, 13, 55, 0, 101, 121, 109, 111, 117, 114, 8, 3, 87, 37, 12, 63, 111, 12, 0, 105, 111, 110, 8, 3, 87, 37, 12, 112, 50, 0, 4, 105, 100, 110, 101, 121, 3, 87, 37, 70, 50, 37, 0, 121, 100, 110, 101, 121, 0, 105, 99, 105, 108, 105, 101, 110, 3, 87, 37, 87, 6, 37, 55, 37, 13, 50, 0, 101, 97, 115, 111, 110, 8, 3, 87, 37, 87, 13, 50, 0, 111, 105, 103, 110, 3, 87, 39, 108, 66, 0, 105, 111, 117, 120, 3, 87, 40, 12, 0, 117, 114, 1, 97, 108, 3, 87, 40, 34, 0, 117, 98, 115, 116, 105, 116, 117, 116, 105, 111, 110, 8, 3, 87, 40, 69, 87, 47, 37, 47, 40, 89, 6, 39, 50, 0, 117, 98, 115, 116, 105, 116, 117, 116, 105, 111, 110, 3, 87, 40, 69, 87, 47, 37, 47, 40, 89, 39, 50, 0, 116, 101, 118, 101, 8, 3, 87, 47, 37, 12, 82, 0, 116, 101, 118, 101, 110, 8, 3, 87, 47, 37, 12, 82, 13, 50, 0, 116, 101, 112, 104, 101, 110, 3, 87, 47, 37, 82, 13, 50, 0, 116, 114, 105, 107, 101, 3, 87, 47, 51, 35, 57, 49, 0, 116, 101, 97, 108, 116, 104, 3, 87, 47, 107, 55, 85, 0, 116, 97, 116, 101, 1, 32, 101, 114, 105, 112, 109, 101, 2, 32, 3, 87, 47, 107, 57, 47, 0, 116, 101, 97, 107, 3, 87, 47, 107, 57, 49, 0, 116, 97, 99, 121, 8, 3, 87, 47, 107, 57, 87, 37, 0, 112, 105, 116, 102, 105, 114, 101, 3, 87, 48, 36, 47, 81, 35, 57, 112, 0, 112, 101, 97, 107, 3, 87, 48, 37, 12, 49, 0, 112, 105, 101, 108, 98, 101, 114, 103, 3, 87, 48, 37, 55, 69, 116, 12, 79, 0, 112, 101, 99, 105, 97, 108, 2, 32, 98, 114, 97, 110, 99, 104, 3, 87, 48, 107, 87, 57, 106, 55, 0, 4, 99, 1, 101, 2, 111, 98, 97, 114, 3, 87, 49, 0, 99, 1, 101, 109, 2, 97, 108, 0, 99, 1, 105, 99, 110, 97, 114, 102, 2, 111, 0, 99, 2, 111, 111, 0, 99, 2, 111, 114, 0, 99, 2, 114, 97, 112, 0, 99, 104, 2, 111, 111, 108, 0, 4, 99, 1, 97, 109, 2, 97, 114, 97, 3, 87, 49, 6, 0, 99, 1, 105, 100, 2, 111, 117, 110, 116, 0, 99, 111, 114, 116, 1, 101, 3, 87, 49, 6, 112, 12, 47, 0, 107, 121, 108, 105, 110, 101, 3, 87, 49, 35, 57, 55, 35, 57, 50, 0, 99, 114, 101, 119, 100, 114, 105, 118, 101, 114, 3, 87, 49, 51, 40, 70, 34, 35, 57, 82, 112, 0, 107, 97, 116, 101, 98, 111, 97, 114, 100, 3, 87, 49, 107, 57, 47, 69, 111, 12, 70, 0, 99, 111, 2, 116, 3, 87, 49, 112, 0, 99, 111, 110, 101, 3, 87, 49, 112, 50, 0, 108, 105, 109, 108, 105, 110, 101, 3, 87, 55, 36, 63, 55, 35, 57, 50, 0, 108, 111, 118, 97, 107, 105, 101, 116, 3, 87, 55, 39, 82, 108, 49, 6, 37, 13, 84, 0, 108, 111, 97, 110, 101, 3, 87, 55, 111, 58, 50, 0, 104, 105, 110, 101, 3, 87, 57, 35, 57, 50, 13, 0, 119, 101, 101, 116, 3, 87, 58, 37, 12, 47, 0, 119, 97, 110, 101, 101, 3, 87, 58, 112, 50, 37, 0, 109, 105, 108, 101, 121, 3, 87, 63, 35, 57, 55, 37, 0, 109, 105, 116, 104, 3, 87, 63, 36, 47, 0, 109, 121, 116, 104, 101, 3, 87, 63, 110, 12, 57, 84, 0, 116, 114, 97, 105, 103, 104, 116, 3, 87, 70, 34, 107, 12, 57, 47, 0, 116, 111, 110, 101, 8, 3, 87, 70, 39, 40, 50, 0, 113, 117, 97, 115, 104, 3, 87, 79, 58, 112, 89, 0, 99, 104, 119, 101, 105, 122, 3, 87, 82, 35, 57, 47, 87, 0, 97, 105, 100, 1, 32, 116, 114, 111, 112, 3, 87, 108, 6, 37, 70, 0, 97, 108, 111, 111, 110, 3, 87, 108, 55, 6, 40, 12, 50, 0, 97, 118, 111, 105, 114, 3, 87, 108, 82, 39, 35, 12, 0, 111, 112, 104, 105, 101, 3, 87, 111, 40, 81, 37, 0, 117, 112, 112, 111, 114, 116, 3, 87, 111, 48, 6, 112, 34, 70, 0, 4, 195, 165, 1, 32, 100, 101, 109, 2, 32, 3, 87, 112, 0, 195, 165, 1, 32, 100, 108, 111, 104, 2, 32, 0, 195, 165, 1, 32, 101, 100, 32, 108, 105, 118, 2, 32, 0, 195, 165, 1, 32, 101, 114, 2, 32, 0, 195, 165, 1, 32, 101, 118, 105, 108, 98, 2, 32, 0, 195, 165, 1, 32, 103, 111, 2, 32, 118, 105, 100, 101, 114, 101, 0, 195, 165, 1, 32, 105, 32, 108, 105, 118, 2, 32, 0, 195, 165, 1, 32, 108, 105, 118, 2, 32, 0, 195, 165, 1, 32, 114, 2, 32, 98, 97, 110, 103, 101, 0, 195, 165, 1, 32, 114, 101, 2, 32, 0, 195, 165, 1, 32, 115, 101, 2, 32, 0, 195, 165, 1, 32, 117, 100, 32, 108, 105, 118, 2, 32, 0, 195, 165, 1, 32, 118, 101, 108, 98, 2, 32, 0, 195, 165, 8, 2, 32, 17, 67, 17, 65, 17, 67, 101, 114, 32, 0, 195, 165, 8, 2, 32, 98, 101, 115, 118, 195, 166, 114, 108, 105, 103, 0, 195, 165, 8, 2, 32, 98, 108, 101, 118, 32, 0, 195, 165, 8, 2, 32, 98, 108, 105, 118, 101, 114, 32, 0, 195, 165, 8, 2, 32, 100, 101, 32, 109, 195, 165, 0, 195, 165, 8, 2, 32, 100, 101, 110, 32, 109, 195, 165, 0, 195, 165, 8, 2, 32, 102, 105, 107, 32, 0, 195, 165, 8, 2, 32, 103, 105, 107, 32, 0, 195, 165, 8, 2, 32, 103, 111, 100, 32, 0, 195, 165, 8, 2, 32, 103, 195, 165, 32, 0, 195, 165, 8, 2, 32, 103, 195, 165, 114, 32, 0, 195, 165, 8, 2, 32, 103, 195, 184, 114, 101, 32, 0, 195, 165, 8, 2, 32, 104, 17, 65, 110, 32, 109, 195, 165, 0, 195, 165, 8, 2, 32, 104, 97, 118, 100, 101, 32, 0, 195, 165, 8, 2, 32, 104, 97, 118, 101, 32, 0, 195, 165, 8, 2, 32, 104, 101, 114, 32, 0, 195, 165, 8, 2, 32, 104, 111, 108, 100, 32, 0, 195, 165, 8, 2, 32, 105, 32, 109, 195, 165, 0, 195, 165, 8, 2, 32, 107, 97, 110, 32, 0, 195, 165, 8, 2, 32, 107, 111, 109, 32, 0, 195, 165, 8, 2, 32, 107, 111, 109, 109, 101, 114, 32, 0, 195, 165, 8, 2, 32, 108, 97, 100, 32, 0, 195, 165, 8, 2, 32, 110, 195, 166, 114, 32, 0, 195, 165, 8, 2, 32, 115, 105, 107, 107, 101, 114, 32, 0, 195, 165, 8, 2, 32, 115, 107, 97, 108, 32, 0, 195, 165, 8, 2, 32, 115, 107, 101, 116, 101, 32, 0, 195, 165, 8, 2, 32, 116, 97, 103, 101, 114, 32, 0, 195, 165, 8, 2, 32, 118, 101, 100, 32, 0, 195, 165, 8, 2, 32, 118, 105, 32, 107, 97, 110, 32, 0, 195, 165, 8, 2, 32, 118, 105, 32, 109, 195, 165, 0, 195, 165, 8, 2, 32, 118, 105, 108, 108, 101, 32, 0, 195, 165, 8, 32, 101, 100, 32, 101, 108, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 101, 100, 32, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 105, 32, 101, 108, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 105, 32, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 110, 97, 104, 32, 101, 108, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 110, 97, 104, 32, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 110, 97, 104, 32, 114, 184, 195, 103, 2, 32, 0, 195, 165, 8, 32, 110, 117, 104, 32, 101, 108, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 110, 117, 104, 32, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 117, 100, 32, 101, 108, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 117, 100, 32, 101, 108, 108, 105, 118, 2, 32, 0, 195, 165, 8, 32, 117, 100, 32, 114, 101, 2, 32, 0, 111, 110, 121, 97, 3, 87, 112, 50, 57, 108, 0, 117, 110, 100, 97, 121, 3, 87, 112, 50, 70, 37, 0, 117, 110, 115, 101, 116, 8, 3, 87, 112, 50, 87, 107, 47, 0, 117, 108, 108, 121, 3, 87, 112, 55, 37, 0, 117, 108, 108, 105, 118, 97, 110, 3, 87, 112, 55, 37, 82, 106, 50, 0, 111, 108, 115, 106, 101, 110, 105, 116, 115, 121, 110, 3, 87, 112, 55, 87, 57, 13, 50, 6, 37, 47, 87, 37, 50, 0, 117, 102, 102, 111, 108, 107, 3, 87, 112, 81, 112, 49, 0, 111, 116, 104, 101, 98, 121, 3, 87, 112, 84, 106, 69, 37, 0, 117, 116, 104, 101, 114, 3, 87, 112, 84, 112, 0, 117, 115, 115, 101, 120, 3, 87, 112, 87, 107, 79, 87, 0, 105, 114, 8, 2, 32, 3, 87, 116, 12, 0, 117, 114, 102, 3, 87, 116, 81, 0, 4, 99, 104, 3, 89, 0, 104, 1, 97, 104, 0, 104, 1, 97, 110, 0, 104, 1, 97, 112, 2, 97, 0, 104, 1, 105, 98, 2, 111, 112, 0, 104, 1, 105, 102, 2, 101, 114, 0, 104, 1, 105, 114, 116, 0, 104, 1, 111, 109, 2, 101, 0, 104, 1, 114, 97, 109, 0, 104, 1, 117, 112, 0, 104, 1, 117, 115, 2, 105, 0, 104, 2, 101, 114, 105, 102, 0, 104, 8, 0, 105, 2, 111, 110, 0, 104, 105, 114, 101, 3, 89, 13, 0, 104, 101, 105, 107, 3, 89, 35, 57, 49, 0, 104, 101, 105, 108, 97, 3, 89, 37, 12, 55, 108, 0, 104, 111, 119, 3, 89, 39, 40, 0, 117, 103, 97, 114, 8, 2, 32, 3, 89, 40, 79, 112, 0, 104, 105, 114, 116, 3, 89, 106, 12, 47, 0, 104, 97, 107, 101, 115, 112, 101, 97, 114, 101, 3, 89, 107, 37, 49, 87, 69, 37, 12, 34, 0, 101, 97, 109, 117, 115, 3, 89, 107, 37, 63, 13, 87, 0, 104, 101, 112, 104, 101, 114, 100, 3, 89, 107, 48, 20, 112, 70, 0, 104, 97, 119, 3, 89, 111, 12, 0, 101, 97, 110, 8, 2, 32, 3, 89, 111, 12, 50, 0, 101, 97, 110, 115, 8, 2, 32, 3, 89, 111, 12, 50, 87, 0, 104, 97, 117, 103, 104, 110, 101, 115, 115, 121, 3, 89, 111, 50, 107, 87, 37, 0, 104, 111, 114, 2, 116, 3, 89, 112, 0, 104, 111, 116, 3, 89, 112, 47, 0, 104, 101, 114, 2, 119, 111, 111, 100, 3, 89, 116, 0, 104, 101, 114, 109, 97, 110, 3, 89, 116, 12, 63, 108, 50, 0, 104, 105, 114, 108, 101, 121, 8, 3, 89, 116, 55, 37, 0, 104, 101, 114, 108, 111, 99, 107, 3, 89, 116, 55, 112, 49, 0, 7, 6, 116, 0, 8, 114, 97, 2, 32, 100, 101, 99, 111, 3, 0, 104, 1, 110, 97, 109, 97, 115, 2, 97, 3, 8, 85, 0, 4, 3, 47, 0, 116, 0, 4, 101, 107, 8, 97, 105, 100, 101, 109, 3, 47, 6, 36, 49, 0, 101, 107, 8, 101, 103, 101, 108, 0, 101, 107, 8, 111, 101, 100, 105, 118, 0, 101, 107, 8, 111, 105, 108, 98, 105, 98, 0, 101, 107, 8, 111, 107, 97, 110, 105, 112, 0, 101, 107, 8, 111, 107, 115, 105, 100, 0, 101, 107, 8, 111, 110, 111, 102, 0, 101, 107, 8, 111, 112, 97, 0, 101, 107, 8, 111, 112, 121, 104, 0, 101, 107, 8, 111, 116, 111, 102, 0, 101, 107, 8, 111, 116, 112, 121, 108, 103, 0, 101, 107, 8, 111, 116, 114, 97, 107, 0, 101, 107, 8, 114, 97, 104, 99, 0, 4, 8, 2, 32, 98, 111, 110, 101, 3, 47, 6, 37, 12, 2, 0, 8, 2, 32, 115, 104, 105, 114, 116, 0, 114, 101, 118, 111, 114, 8, 3, 47, 16, 107, 82, 112, 0, 114, 101, 110, 99, 104, 99, 111, 97, 116, 3, 47, 34, 6, 107, 50, 89, 49, 4, 39, 40, 70, 0, 101, 114, 101, 115, 115, 2, 97, 110, 116, 3, 47, 34, 106, 87, 0, 101, 114, 101, 115, 115, 101, 114, 101, 116, 1, 110, 105, 3, 47, 34, 106, 87, 6, 36, 34, 106, 84, 0, 4, 101, 114, 101, 115, 115, 101, 114, 101, 1, 110, 105, 3, 47, 34, 106, 87, 6, 36, 34, 112, 0, 101, 114, 101, 115, 115, 101, 114, 101, 114, 1, 110, 105, 0, 114, 195, 168, 115, 8, 2, 32, 3, 47, 34, 107, 0, 114, 97, 100, 101, 1, 32, 100, 108, 114, 111, 119, 3, 47, 34, 107, 57, 70, 0, 4, 114, 97, 99, 101, 121, 8, 3, 47, 34, 107, 57, 87, 37, 0, 114, 97, 99, 121, 8, 0, 4, 114, 101, 100, 105, 118, 116, 101, 100, 101, 108, 3, 47, 34, 108, 81, 70, 13, 70, 36, 55, 0, 114, 101, 100, 118, 116, 101, 100, 101, 108, 0, 104, 97, 105, 3, 47, 35, 57, 0, 105, 116, 97, 110, 105, 99, 3, 47, 35, 57, 47, 6, 108, 50, 37, 49, 0, 105, 109, 101, 115, 1, 32, 101, 104, 116, 3, 47, 35, 57, 63, 87, 0, 105, 109, 101, 115, 104, 97, 114, 101, 3, 47, 35, 57, 63, 89, 107, 12, 34, 0, 8, 2, 32, 3, 47, 36, 12, 0, 101, 114, 114, 121, 3, 47, 36, 34, 37, 0, 105, 109, 111, 116, 104, 121, 3, 47, 36, 63, 113, 85, 37, 0, 101, 97, 107, 3, 47, 37, 12, 49, 0, 101, 101, 110, 97, 103, 101, 3, 47, 37, 12, 50, 107, 73, 0, 101, 101, 110, 97, 103, 101, 114, 3, 47, 37, 12, 50, 107, 73, 112, 0, 101, 97, 99, 104, 8, 3, 47, 37, 12, 74, 0, 111, 109, 98, 115, 3, 47, 40, 12, 63, 87, 0, 111, 109, 98, 115, 116, 111, 110, 101, 3, 47, 40, 12, 63, 87, 70, 39, 40, 50, 0, 117, 99, 115, 111, 110, 8, 3, 47, 40, 12, 87, 112, 50, 0, 4, 116, 1, 101, 2, 97, 108, 3, 47, 47, 0, 116, 1, 101, 2, 105, 100, 0, 116, 2, 195, 184, 106, 0, 116, 1, 97, 110, 2, 195, 184, 106, 3, 47, 47, 4, 0, 104, 3, 47, 105, 0, 101, 114, 101, 115, 115, 101, 1, 110, 105, 3, 47, 106, 34, 6, 35, 87, 13, 0, 101, 114, 101, 115, 115, 101, 114, 1, 110, 105, 3, 47, 106, 34, 6, 35, 87, 112, 0, 101, 110, 110, 101, 115, 115, 101, 101, 3, 47, 107, 50, 13, 87, 37, 0, 97, 112, 101, 8, 2, 32, 3, 47, 107, 57, 48, 0, 97, 112, 101, 8, 2, 110, 32, 3, 47, 107, 57, 48, 106, 0, 97, 106, 8, 2, 32, 109, 97, 104, 97, 108, 3, 47, 108, 89, 0, 111, 119, 110, 3, 47, 110, 58, 50, 0, 111, 114, 113, 117, 97, 121, 3, 47, 111, 12, 49, 37, 0, 111, 97, 115, 116, 3, 47, 111, 58, 87, 47, 0, 111, 97, 115, 116, 109, 97, 115, 116, 101, 114, 3, 47, 111, 58, 87, 47, 63, 4, 110, 12, 87, 47, 112, 0, 111, 107, 121, 111, 3, 47, 112, 49, 57, 39, 0, 111, 117, 99, 104, 100, 111, 119, 110, 3, 47, 112, 74, 70, 35, 58, 50, 0, 106, 8, 3, 74, 0, 104, 1, 114, 97, 109, 2, 97, 3, 85, 0, 104, 101, 114, 105, 110, 101, 1, 97, 99, 3, 85, 34, 36, 50, 0, 104, 97, 99, 107, 101, 114, 121, 3, 85, 108, 49, 106, 34, 37, 0, 104, 117, 110, 100, 101, 114, 3, 85, 112, 50, 70, 112, 0, 104, 105, 114, 100, 3, 85, 116, 12, 70, 0, 115, 104, 1, 105, 110, 97, 106, 2, 97, 114, 3, 89, 0, 7, 6, 117, 0, 1, 115, 2, 98, 108, 105, 3, 2, 40, 0, 4, 1, 100, 101, 115, 117, 114, 107, 2, 108, 108, 101, 3, 6, 40, 0, 1, 102, 105, 114, 116, 110, 101, 99, 2, 103, 0, 1, 107, 109, 111, 2, 108, 100, 0, 1, 107, 111, 114, 112, 2, 114, 97, 0, 1, 108, 97, 100, 110, 97, 2, 115, 0, 1, 108, 97, 118, 2, 116, 97, 0, 1, 111, 115, 115, 101, 114, 2, 114, 115, 0, 1, 112, 97, 99, 97, 2, 108, 99, 111, 0, 1, 112, 108, 97, 118, 2, 114, 103, 105, 115, 0, 1, 112, 109, 105, 2, 108, 115, 0, 1, 114, 101, 106, 2, 115, 97, 108, 101, 109, 0, 1, 115, 101, 114, 2, 114, 115, 0, 1, 116, 107, 97, 102, 2, 114, 97, 0, 1, 116, 115, 111, 103, 110, 97, 2, 114, 97, 0, 2, 108, 106, 101, 0, 8, 98, 98, 105, 107, 2, 116, 122, 0, 8, 98, 111, 114, 2, 115, 116, 0, 8, 100, 105, 102, 2, 115, 0, 8, 102, 110, 111, 107, 2, 115, 0, 8, 103, 105, 102, 2, 114, 0, 8, 104, 114, 165, 195, 2, 110, 100, 114, 101, 100, 101, 0, 8, 107, 108, 97, 107, 2, 110, 0, 8, 107, 110, 111, 107, 2, 114, 115, 0, 8, 108, 111, 118, 110, 111, 107, 2, 116, 0, 8, 112, 114, 97, 104, 2, 110, 0, 8, 114, 101, 100, 2, 100, 0, 8, 114, 116, 115, 110, 105, 2, 107, 115, 0, 8, 115, 97, 98, 2, 110, 0, 8, 115, 97, 108, 103, 2, 114, 0, 8, 115, 98, 97, 2, 114, 100, 0, 8, 115, 117, 97, 108, 107, 2, 108, 0, 116, 1, 10, 2, 116, 28, 33, 0, 1, 103, 110, 166, 195, 107, 2, 114, 117, 3, 6, 40, 10, 0, 4, 1, 100, 110, 111, 104, 2, 114, 97, 3, 6, 40, 12, 0, 1, 109, 117, 2, 108, 105, 103, 0, 8, 17, 67, 97, 108, 2, 110, 101, 0, 8, 109, 109, 111, 107, 2, 110, 101, 0, 4, 114, 1, 115, 97, 108, 3, 6, 40, 34, 0, 114, 1, 115, 97, 108, 103, 0, 114, 1, 115, 97, 114, 0, 114, 1, 115, 110, 101, 99, 0, 114, 1, 115, 110, 101, 109, 0, 114, 1, 115, 110, 111, 116, 0, 114, 1, 115, 115, 101, 114, 100, 0, 114, 1, 115, 115, 105, 102, 0, 114, 1, 115, 166, 195, 99, 0, 114, 8, 102, 109, 111, 107, 0, 116, 1, 10, 2, 28, 33, 3, 6, 40, 47, 0, 4, 100, 8, 2, 97, 116, 12, 14, 128, 132, 130, 3, 6, 40, 70, 0, 100, 8, 2, 101, 108, 116, 12, 14, 128, 132, 130, 0, 100, 8, 2, 114, 195, 184, 106, 12, 14, 128, 132, 130, 0, 100, 8, 2, 121, 12, 14, 128, 132, 130, 0, 100, 8, 2, 195, 165, 100, 12, 14, 128, 132, 130, 0, 100, 8, 2, 195, 184, 98, 116, 12, 14, 128, 132, 130, 0, 116, 97, 104, 3, 6, 57, 40, 12, 47, 110, 0, 114, 102, 101, 114, 1, 115, 3, 6, 106, 12, 81, 112, 0, 4, 1, 103, 117, 97, 2, 115, 116, 3, 6, 111, 0, 1, 108, 97, 104, 2, 110, 107, 0, 1, 108, 111, 99, 2, 109, 98, 0, 8, 107, 101, 115, 2, 110, 100, 0, 110, 100, 1, 98, 97, 114, 2, 117, 115, 3, 6, 111, 50, 70, 0, 1, 99, 108, 97, 99, 2, 116, 116, 97, 3, 6, 112, 0, 99, 107, 121, 1, 116, 110, 101, 107, 3, 6, 112, 49, 37, 0, 4, 1, 98, 105, 116, 115, 101, 118, 2, 108, 3, 6, 114, 0, 1, 100, 101, 99, 111, 114, 112, 2, 114, 101, 0, 1, 102, 114, 97, 112, 2, 109, 101, 0, 1, 110, 101, 118, 111, 114, 112, 0, 8, 98, 105, 114, 116, 2, 110, 101, 0, 8, 110, 101, 109, 0, 8, 116, 115, 111, 107, 2, 109, 101, 0, 101, 1, 100, 110, 111, 102, 0, 101, 1, 110, 101, 118, 97, 0, 116, 8, 98, 101, 100, 0, 114, 101, 1, 116, 117, 111, 10, 2, 28, 33, 3, 6, 114, 12, 34, 0, 4, 114, 1, 100, 10, 2, 28, 33, 3, 7, 40, 34, 0, 114, 1, 116, 10, 2, 28, 33, 0, 100, 8, 2, 21, 21, 12, 14, 128, 132, 130, 3, 7, 40, 84, 0, 100, 101, 8, 2, 21, 21, 12, 14, 128, 132, 131, 3, 7, 40, 84, 13, 0, 114, 101, 1, 10, 2, 12, 12, 12, 28, 33, 3, 7, 114, 12, 112, 0, 101, 122, 1, 103, 3, 8, 36, 87, 0, 1, 112, 109, 105, 2, 108, 115, 105, 118, 3, 8, 40, 0, 109, 1, 10, 2, 28, 33, 3, 8, 111, 63, 0, 4, 105, 100, 1, 103, 32, 108, 105, 118, 2, 101, 3, 35, 57, 70, 0, 105, 100, 1, 103, 32, 116, 97, 2, 101, 0, 105, 100, 8, 103, 2, 101, 116, 0, 105, 100, 101, 1, 103, 0, 105, 100, 101, 114, 1, 103, 3, 35, 57, 70, 112, 0, 105, 1, 103, 2, 116, 97, 114, 3, 37, 0, 4, 3, 40, 0, 1, 17, 67, 2, 18, 66, 18, 69, 0, 1, 17, 67, 2, 18, 66, 18, 76, 0, 1, 18, 74, 115, 2, 17, 67, 18, 76, 0, 1, 18, 74, 115, 2, 116, 0, 1, 98, 2, 103, 115, 101, 0, 1, 100, 2, 107, 116, 105, 0, 1, 104, 2, 106, 101, 12, 0, 1, 104, 2, 108, 17, 67, 0, 1, 104, 2, 108, 18, 76, 0, 1, 104, 2, 108, 116, 0, 1, 104, 2, 110, 0, 1, 107, 2, 107, 0, 1, 107, 2, 108, 18, 69, 0, 1, 107, 2, 108, 18, 70, 0, 1, 107, 2, 108, 100, 0, 1, 107, 2, 108, 100, 101, 0, 1, 107, 2, 108, 108, 101, 114, 0, 1, 107, 2, 108, 116, 0, 1, 107, 100, 101, 118, 111, 104, 2, 108, 115, 0, 1, 107, 115, 2, 108, 107, 0, 1, 107, 115, 2, 108, 108, 0, 1, 107, 115, 2, 108, 112, 0, 1, 108, 2, 107, 97, 115, 0, 1, 108, 2, 107, 114, 18, 76, 0, 1, 108, 2, 107, 114, 101, 114, 101, 0, 1, 108, 2, 110, 32, 0, 1, 108, 2, 110, 101, 0, 1, 108, 98, 2, 102, 195, 166, 0, 1, 108, 103, 2, 103, 0, 1, 108, 115, 2, 103, 116, 0, 1, 109, 2, 102, 116, 0, 1, 109, 2, 115, 105, 107, 0, 1, 109, 115, 2, 18, 68, 12, 0, 1, 109, 115, 2, 103, 108, 0, 1, 110, 102, 2, 103, 0, 1, 110, 115, 2, 98, 108, 101, 0, 1, 112, 2, 99, 107, 12, 0, 1, 112, 2, 110, 100, 0, 1, 114, 2, 18, 71, 18, 69, 0, 1, 114, 2, 103, 0, 1, 114, 2, 109, 101, 0, 1, 114, 98, 2, 103, 0, 1, 114, 102, 2, 115, 0, 1, 114, 103, 2, 18, 71, 0, 1, 114, 103, 2, 112, 0, 1, 114, 107, 115, 2, 112, 108, 101, 0, 1, 114, 116, 2, 18, 71, 0, 1, 114, 116, 2, 107, 116, 18, 69, 0, 1, 114, 116, 2, 109, 97, 110, 0, 1, 115, 2, 98, 115, 0, 1, 115, 2, 103, 0, 1, 115, 2, 112, 112, 108, 101, 0, 1, 115, 2, 112, 114, 97, 0, 1, 116, 2, 110, 21, 0, 1, 116, 115, 2, 98, 12, 0, 2, 100, 101, 12, 12, 0, 2, 100, 101, 110, 0, 2, 100, 101, 110, 102, 111, 114, 12, 0, 2, 100, 103, 114, 117, 110, 100, 101, 108, 105, 103, 12, 0, 2, 103, 101, 12, 12, 0, 2, 103, 108, 12, 0, 2, 103, 108, 101, 12, 0, 2, 104, 121, 114, 101, 12, 0, 2, 105, 109, 111, 100, 115, 116, 195, 165, 101, 108, 105, 103, 0, 2, 108, 116, 105, 109, 97, 0, 2, 108, 116, 114, 97, 0, 2, 110, 105, 12, 12, 0, 2, 115, 117, 114, 112, 0, 2, 116, 111, 112, 105, 0, 8, 2, 21, 21, 12, 14, 128, 132, 129, 0, 8, 2, 100, 115, 12, 0, 8, 2, 114, 12, 12, 0, 8, 2, 114, 101, 116, 102, 195, 166, 12, 12, 14, 128, 132, 129, 0, 8, 107, 2, 108, 108, 101, 100, 101, 0, 8, 114, 112, 2, 115, 116, 0, 103, 1, 98, 2, 116, 97, 0, 103, 1, 108, 115, 0, 103, 1, 109, 2, 32, 117, 100, 0, 103, 1, 109, 2, 101, 32, 117, 100, 0, 2, 101, 110, 105, 103, 12, 3, 40, 6, 0, 101, 1, 108, 102, 110, 105, 2, 110, 122, 97, 3, 40, 6, 107, 0, 101, 116, 1, 110, 101, 109, 3, 40, 6, 107, 47, 0, 4, 1, 104, 2, 108, 101, 3, 40, 12, 0, 1, 106, 2, 105, 99, 101, 0, 1, 107, 2, 17, 67, 101, 0, 101, 1, 98, 108, 97, 0, 101, 1, 100, 2, 115, 0, 101, 1, 116, 115, 0, 101, 2, 32, 0, 103, 1, 108, 2, 101, 0, 115, 97, 8, 2, 32, 3, 40, 12, 36, 87, 6, 108, 0, 115, 97, 39, 115, 8, 2, 32, 3, 40, 12, 36, 87, 6, 108, 87, 0, 4, 101, 1, 116, 115, 2, 32, 3, 40, 13, 0, 101, 1, 116, 115, 2, 110, 32, 0, 114, 1, 98, 109, 97, 116, 3, 40, 34, 0, 114, 1, 116, 10, 2, 101, 108, 28, 33, 3, 40, 34, 6, 0, 114, 101, 1, 115, 10, 2, 114, 101, 12, 12, 12, 3, 40, 34, 7, 36, 0, 107, 101, 116, 8, 98, 3, 40, 49, 6, 107, 47, 0, 107, 117, 108, 101, 108, 101, 3, 40, 49, 40, 55, 6, 36, 55, 106, 0, 99, 99, 101, 115, 115, 111, 114, 1, 115, 3, 40, 49, 87, 6, 107, 87, 112, 0, 99, 99, 101, 115, 115, 111, 114, 101, 114, 1, 115, 3, 40, 49, 87, 107, 87, 6, 39, 112, 0, 108, 114, 101, 116, 1, 107, 3, 40, 55, 51, 112, 84, 0, 103, 1, 109, 115, 3, 40, 58, 0, 4, 100, 8, 2, 114, 105, 107, 107, 101, 108, 105, 103, 12, 14, 128, 132, 130, 3, 40, 70, 0, 100, 8, 2, 117, 101, 108, 105, 103, 12, 0, 100, 8, 2, 195, 184, 100, 12, 14, 128, 132, 130, 0, 102, 111, 114, 109, 101, 108, 3, 40, 81, 112, 63, 6, 36, 55, 0, 4, 100, 8, 2, 101, 110, 12, 3, 40, 84, 0, 100, 8, 2, 107, 105, 103, 0, 115, 107, 121, 108, 100, 105, 103, 3, 40, 87, 79, 6, 114, 55, 70, 37, 0, 103, 97, 102, 1, 108, 3, 55, 111, 79, 6, 108, 0, 4, 1, 112, 109, 111, 99, 2, 116, 101, 114, 3, 57, 40, 0, 1, 116, 2, 110, 101, 0, 1, 116, 2, 110, 105, 110, 103, 12, 0, 1, 116, 2, 116, 111, 114, 0, 8, 116, 115, 2, 97, 114, 116, 0, 110, 105, 116, 101, 100, 3, 57, 40, 50, 6, 35, 57, 47, 36, 70, 0, 114, 101, 1, 116, 120, 105, 109, 3, 57, 112, 0, 105, 1, 115, 2, 116, 101, 3, 58, 37, 0, 4, 114, 1, 115, 2, 102, 98, 3, 106, 12, 0, 114, 1, 115, 2, 102, 101, 0, 101, 114, 105, 1, 103, 2, 108, 108, 97, 3, 107, 51, 6, 37, 0, 4, 1, 17, 67, 2, 18, 66, 101, 12, 3, 111, 0, 1, 17, 67, 2, 18, 66, 116, 0, 1, 18, 68, 2, 102, 0, 1, 18, 71, 2, 110, 107, 116, 0, 1, 18, 73, 2, 102, 0, 1, 18, 74, 2, 102, 0, 1, 18, 74, 2, 114, 114, 101, 0, 1, 98, 2, 107, 0, 1, 98, 2, 110, 116, 0, 1, 100, 2, 107, 0, 1, 103, 2, 102, 0, 1, 104, 2, 103, 0, 1, 104, 2, 108, 0, 1, 104, 2, 108, 98, 195, 165, 110, 100, 0, 1, 104, 2, 108, 106, 101, 114, 110, 0, 1, 104, 2, 108, 108, 101, 0, 1, 104, 2, 108, 115, 107, 101, 0, 1, 104, 2, 108, 115, 195, 184, 109, 0, 1, 104, 2, 108, 116, 97, 110, 103, 0, 1, 104, 2, 114, 116, 105, 103, 0, 1, 104, 112, 97, 110, 107, 2, 108, 0, 1, 104, 114, 101, 100, 100, 117, 109, 2, 108, 0, 1, 104, 116, 117, 109, 115, 2, 108, 0, 1, 106, 2, 110, 107, 116, 117, 114, 12, 12, 0, 1, 106, 104, 2, 108, 112, 0, 1, 107, 2, 102, 102, 101, 114, 116, 0, 1, 107, 2, 108, 0, 1, 107, 2, 108, 100, 105, 111, 0, 1, 107, 2, 108, 105, 108, 116, 0, 1, 107, 101, 115, 2, 110, 100, 195, 166, 0, 1, 107, 115, 2, 98, 0, 1, 108, 2, 107, 0, 1, 108, 103, 184, 195, 114, 2, 103, 116, 0, 1, 108, 115, 2, 98, 0, 1, 108, 115, 2, 112, 0, 1, 109, 115, 2, 17, 67, 0, 1, 110, 18, 66, 2, 18, 71, 0, 1, 112, 2, 102, 0, 1, 112, 2, 107, 107, 101, 0, 1, 112, 2, 107, 108, 0, 1, 112, 2, 110, 99, 104, 0, 1, 112, 115, 2, 110, 100, 101, 0, 1, 114, 2, 18, 71, 0, 1, 114, 2, 102, 0, 1, 114, 2, 109, 0, 1, 114, 2, 115, 116, 0, 1, 114, 17, 67, 2, 18, 71, 0, 1, 114, 17, 67, 2, 107, 0, 1, 114, 98, 2, 103, 116, 0, 1, 114, 116, 2, 102, 102, 0, 1, 116, 115, 2, 107, 107, 101, 116, 0, 1, 118, 115, 2, 112, 0, 2, 107, 115, 0, 2, 109, 25, 0, 2, 110, 18, 73, 0, 2, 110, 100, 0, 2, 110, 103, 12, 0, 2, 110, 107, 0, 8, 2, 110, 100, 12, 0, 8, 2, 110, 103, 12, 0, 8, 114, 2, 98, 32, 0, 8, 114, 2, 98, 98, 101, 0, 108, 118, 1, 103, 3, 111, 55, 0, 108, 118, 1, 103, 2, 101, 3, 111, 55, 82, 0, 109, 98, 117, 103, 1, 104, 3, 111, 63, 69, 111, 79, 0, 107, 97, 102, 1, 108, 3, 111, 79, 6, 108, 0, 4, 1, 32, 100, 110, 97, 116, 115, 2, 112, 3, 112, 0, 1, 98, 2, 99, 107, 0, 1, 98, 2, 102, 102, 101, 114, 0, 1, 98, 2, 116, 108, 101, 114, 0, 1, 100, 2, 98, 98, 101, 0, 1, 100, 2, 98, 98, 105, 110, 103, 0, 1, 100, 2, 98, 108, 105, 110, 0, 1, 100, 2, 100, 108, 101, 121, 0, 1, 100, 2, 110, 99, 97, 110, 0, 1, 102, 2, 99, 107, 12, 12, 0, 1, 104, 2, 110, 116, 101, 114, 0, 1, 104, 99, 116, 101, 107, 2, 112, 0, 1, 104, 100, 97, 101, 104, 2, 110, 116, 0, 1, 106, 2, 110, 107, 0, 1, 108, 2, 98, 98, 111, 99, 107, 0, 1, 108, 99, 2, 98, 0, 1, 108, 108, 2, 112, 0, 1, 109, 2, 112, 112, 101, 114, 110, 101, 0, 1, 112, 2, 98, 98, 0, 1, 114, 116, 2, 99, 107, 0, 1, 116, 115, 2, 110, 116, 0, 8, 100, 2, 115, 116, 105, 110, 0, 8, 102, 2, 110, 107, 0, 8, 109, 2, 108, 108, 105, 110, 0, 8, 112, 2, 98, 32, 0, 8, 112, 2, 110, 107, 0, 112, 112, 101, 114, 99, 117, 116, 3, 112, 48, 112, 49, 112, 47, 0, 99, 107, 101, 114, 1, 116, 3, 112, 49, 112, 0, 110, 99, 104, 1, 114, 98, 3, 112, 50, 89, 0, 109, 112, 104, 114, 101, 121, 1, 104, 3, 112, 63, 81, 34, 37, 0, 100, 100, 1, 98, 2, 121, 3, 112, 70, 0, 102, 102, 105, 110, 1, 109, 3, 112, 81, 36, 50, 0, 115, 116, 121, 1, 114, 3, 112, 87, 47, 37, 0, 4, 1, 18, 68, 2, 110, 115, 3, 113, 0, 1, 98, 2, 110, 107, 101, 114, 0, 1, 102, 2, 18, 71, 0, 1, 102, 2, 110, 12, 0, 1, 106, 2, 110, 116, 0, 1, 108, 2, 110, 116, 101, 0, 1, 108, 107, 2, 110, 115, 0, 1, 109, 2, 18, 66, 0, 1, 109, 2, 110, 116, 0, 1, 110, 115, 2, 18, 71, 0, 1, 112, 2, 108, 118, 0, 1, 115, 2, 18, 71, 11, 0, 1, 115, 2, 107, 0, 1, 116, 2, 110, 110, 0, 1, 118, 2, 103, 0, 8, 107, 2, 110, 32, 0, 8, 110, 2, 108, 0, 4, 1, 98, 2, 100, 103, 101, 116, 3, 114, 0, 1, 98, 105, 114, 116, 2, 110, 101, 0, 1, 100, 2, 99, 104, 101, 115, 115, 101, 0, 1, 102, 101, 114, 2, 115, 101, 114, 0, 1, 108, 103, 2, 107, 111, 115, 101, 0, 1, 110, 2, 97, 110, 99, 101, 0, 1, 110, 101, 109, 0, 1, 112, 2, 114, 195, 169, 0, 1, 115, 2, 99, 99, 0, 1, 115, 2, 114, 114, 101, 97, 0, 1, 116, 115, 111, 107, 2, 109, 101, 0, 8, 98, 2, 115, 116, 101, 32, 0, 8, 112, 2, 114, 101, 114, 101, 0, 116, 1, 98, 101, 100, 0, 8, 116, 97, 110, 2, 114, 101, 108, 32, 12, 3, 114, 6, 0, 114, 101, 1, 116, 117, 111, 99, 3, 114, 12, 34, 0, 4, 114, 101, 1, 99, 101, 110, 105, 115, 3, 114, 12, 112, 0, 114, 101, 1, 99, 105, 100, 101, 112, 0, 114, 101, 1, 99, 105, 110, 97, 109, 0, 114, 101, 1, 100, 101, 99, 111, 114, 112, 0, 114, 101, 1, 100, 114, 111, 98, 0, 114, 101, 1, 104, 99, 111, 114, 98, 0, 114, 101, 1, 104, 99, 117, 111, 98, 109, 101, 0, 114, 101, 1, 108, 101, 110, 110, 97, 107, 0, 114, 101, 1, 110, 114, 117, 111, 116, 0, 114, 101, 1, 115, 105, 114, 102, 0, 114, 101, 1, 116, 97, 105, 110, 105, 109, 0, 114, 101, 1, 116, 97, 105, 110, 105, 109, 0, 114, 101, 1, 116, 105, 102, 110, 111, 107, 0, 114, 101, 1, 116, 105, 110, 114, 97, 103, 0, 114, 101, 1, 116, 105, 114, 102, 0, 114, 101, 1, 116, 107, 101, 102, 110, 111, 107, 0, 114, 101, 1, 116, 107, 101, 108, 0, 114, 101, 1, 116, 114, 101, 118, 117, 111, 0, 114, 101, 1, 118, 97, 114, 103, 0, 114, 101, 1, 10, 2, 114, 101, 28, 33, 12, 12, 12, 3, 114, 34, 7, 36, 0, 4, 114, 101, 1, 112, 116, 97, 109, 111, 116, 3, 114, 34, 36, 0, 114, 195, 169, 1, 112, 116, 97, 109, 111, 116, 0, 116, 101, 1, 108, 102, 3, 114, 47, 0, 114, 101, 97, 117, 1, 98, 3, 114, 51, 6, 39, 0, 4, 109, 101, 1, 115, 101, 114, 3, 114, 63, 6, 36, 0, 109, 195, 169, 1, 115, 101, 114, 0, 120, 101, 108, 108, 101, 115, 1, 114, 98, 3, 114, 87, 6, 107, 55, 0, 1, 115, 2, 114, 114, 101, 108, 3, 115, 0, 114, 1, 98, 2, 109, 101, 115, 3, 116, 0, 4, 114, 1, 98, 2, 109, 97, 3, 116, 12, 0, 114, 1, 112, 2, 115, 101, 114, 0, 114, 8, 98, 2, 116, 0, 114, 112, 108, 101, 1, 112, 3, 116, 12, 48, 20, 13, 55, 0, 114, 110, 1, 98, 121, 97, 114, 3, 116, 12, 50, 0, 114, 100, 108, 101, 1, 104, 3, 116, 70, 13, 55, 0, 114, 100, 108, 101, 110, 1, 104, 3, 116, 70, 55, 106, 50, 0, 114, 103, 105, 115, 8, 116, 115, 3, 116, 73, 37, 87, 0, 114, 103, 1, 98, 2, 101, 114, 3, 116, 79, 0, 7, 6, 118, 0, 4, 1, 101, 108, 98, 3, 0, 4, 1, 108, 97, 104, 3, 0, 1, 108, 101, 2, 17, 67, 3, 0, 1, 97, 108, 2, 101, 109, 101, 110, 116, 3, 13, 0, 108, 101, 103, 1, 108, 97, 104, 3, 35, 57, 0, 4, 1, 97, 104, 2, 17, 67, 3, 40, 0, 1, 97, 104, 2, 111, 118, 101, 114, 102, 0, 4, 1, 97, 2, 110, 3, 58, 0, 1, 101, 108, 98, 101, 100, 117, 0, 1, 184, 195, 2, 101, 110, 0, 2, 110, 0, 2, 97, 110, 32, 103, 111, 103, 104, 3, 81, 0, 111, 110, 8, 2, 32, 3, 81, 112, 50, 0, 4, 3, 82, 0, 1, 17, 65, 10, 2, 17, 65, 0, 1, 17, 65, 10, 2, 32, 17, 65, 0, 1, 97, 108, 115, 2, 12, 0, 1, 108, 97, 2, 101, 0, 1, 108, 105, 2, 17, 65, 0, 1, 111, 18, 74, 2, 17, 65, 0, 1, 111, 114, 112, 2, 101, 110, 99, 101, 0, 1, 114, 10, 0, 1, 114, 117, 0, 118, 0, 105, 114, 103, 105, 110, 105, 97, 3, 82, 13, 73, 6, 37, 66, 57, 108, 0, 105, 110, 99, 101, 3, 82, 36, 50, 87, 0, 105, 108, 108, 97, 103, 101, 3, 82, 36, 55, 36, 73, 0, 111, 105, 108, 97, 3, 82, 58, 35, 55, 6, 35, 0, 101, 2, 108, 115, 101, 3, 82, 106, 0, 101, 114, 100, 117, 110, 3, 82, 107, 34, 70, 6, 106, 66, 0, 97, 117, 103, 104, 110, 3, 82, 111, 12, 50, 0, 111, 108, 105, 101, 114, 101, 3, 82, 112, 55, 37, 6, 107, 12, 34, 0, 7, 6, 119, 0, 114, 105, 103, 104, 116, 3, 21, 0, 3, 58, 0, 121, 111, 109, 105, 110, 103, 3, 58, 35, 57, 6, 111, 58, 63, 36, 66, 0, 105, 100, 101, 115, 99, 114, 101, 101, 110, 3, 58, 35, 57, 70, 87, 49, 34, 37, 12, 50, 0, 105, 110, 110, 105, 112, 101, 103, 3, 58, 36, 50, 37, 48, 107, 79, 0, 105, 115, 99, 111, 110, 115, 105, 110, 3, 58, 36, 87, 49, 6, 112, 50, 87, 36, 50, 0, 101, 101, 107, 101, 110, 100, 3, 58, 37, 12, 79, 107, 50, 70, 0, 101, 97, 118, 101, 114, 3, 58, 37, 12, 82, 112, 0, 104, 101, 101, 108, 3, 58, 37, 55, 0, 4, 105, 108, 108, 105, 101, 3, 58, 37, 55, 37, 0, 105, 108, 108, 121, 0, 97, 121, 110, 101, 3, 58, 107, 57, 50, 0, 97, 108, 101, 115, 3, 58, 107, 57, 55, 87, 0, 101, 97, 116, 104, 101, 114, 3, 58, 107, 84, 112, 0, 97, 114, 101, 3, 58, 108, 12, 34, 0, 105, 108, 100, 8, 3, 58, 110, 57, 55, 70, 0, 97, 116, 101, 114, 103, 97, 116, 101, 3, 58, 111, 47, 112, 79, 107, 57, 47, 0, 97, 108, 100, 111, 114, 102, 8, 3, 58, 111, 70, 112, 81, 0, 97, 116, 115, 111, 110, 3, 58, 112, 47, 87, 14, 50, 0, 97, 110, 100, 97, 3, 58, 112, 50, 70, 108, 0, 111, 110, 100, 101, 114, 8, 3, 58, 112, 50, 70, 112, 0, 97, 110, 115, 101, 97, 1, 115, 3, 58, 112, 50, 87, 4, 37, 0, 97, 108, 108, 97, 99, 101, 3, 58, 112, 55, 36, 87, 0, 97, 115, 104, 105, 110, 103, 116, 111, 110, 3, 58, 112, 89, 36, 66, 47, 112, 50, 0, 111, 114, 107, 3, 58, 116, 12, 49, 0, 111, 114, 116, 104, 3, 58, 116, 12, 85, 0, 111, 114, 108, 100, 8, 3, 58, 116, 55, 70, 0, 111, 114, 100, 3, 58, 116, 70, 0, 4, 1, 116, 110, 97, 2, 101, 114, 112, 101, 110, 3, 82, 0, 2, 97, 100, 101, 114, 115, 0, 2, 97, 100, 105, 0, 2, 97, 108, 105, 115, 0, 2, 97, 115, 115, 101, 114, 109, 97, 110, 110, 112, 114, 195, 184, 118, 101, 0, 2, 97, 116, 116, 0, 2, 101, 108, 116, 101, 114, 118, 195, 166, 103, 116, 0, 2, 101, 108, 116, 115, 99, 104, 109, 101, 114, 122, 0, 2, 101, 114, 110, 101, 114, 0, 2, 101, 115, 115, 101, 108, 0, 2, 104, 105, 115, 116, 0, 2, 105, 101, 110, 101, 114, 115, 99, 104, 110, 105, 116, 122, 101, 108, 0, 2, 111, 108, 102, 103, 97, 110, 103, 0, 2, 111, 108, 102, 114, 97, 109, 0, 97, 105, 1, 117, 107, 2, 116, 3, 82, 6, 35, 57, 0, 97, 114, 115, 122, 97, 119, 97, 3, 82, 35, 34, 89, 6, 108, 12, 82, 108, 0, 97, 108, 100, 3, 82, 35, 55, 70, 0, 97, 102, 102, 101, 3, 82, 35, 81, 106, 0, 105, 101, 110, 3, 82, 37, 50, 0, 105, 101, 115, 101, 110, 116, 104, 97, 108, 3, 82, 37, 87, 13, 50, 47, 110, 55, 0, 7, 6, 120, 0, 4, 3, 79, 87, 0, 99, 0, 4, 105, 100, 8, 111, 2, 32, 3, 79, 87, 6, 37, 84, 0, 121, 100, 8, 111, 2, 32, 0, 97, 108, 1, 111, 3, 79, 87, 6, 108, 55, 0, 4, 105, 100, 101, 8, 111, 2, 114, 101, 3, 79, 87, 37, 70, 6, 36, 0, 105, 100, 101, 8, 111, 2, 114, 105, 0, 121, 100, 101, 8, 111, 2, 114, 101, 0, 121, 100, 101, 8, 111, 2, 114, 105, 0, 121, 103, 101, 110, 1, 111, 3, 79, 87, 37, 79, 6, 36, 50, 0, 111, 110, 3, 79, 87, 112, 50, 0, 4, 1, 110, 3, 87, 0, 8, 0, 7, 6, 121, 0, 1, 98, 100, 110, 97, 116, 115, 3, 6, 35, 57, 0, 4, 1, 110, 111, 100, 117, 101, 115, 112, 2, 109, 3, 6, 114, 0, 8, 107, 101, 108, 111, 109, 2, 108, 101, 0, 8, 108, 112, 97, 114, 97, 112, 0, 8, 115, 97, 2, 108, 0, 8, 116, 97, 108, 2, 114, 117, 115, 0, 8, 116, 111, 101, 114, 101, 116, 115, 2, 112, 0, 8, 118, 101, 114, 0, 8, 122, 110, 101, 2, 109, 0, 4, 1, 110, 97, 107, 2, 108, 101, 3, 6, 115, 0, 8, 98, 97, 107, 2, 115, 0, 8, 104, 97, 107, 2, 116, 0, 4, 1, 109, 2, 110, 116, 101, 3, 6, 116, 0, 8, 114, 97, 112, 2, 107, 0, 111, 114, 107, 115, 104, 105, 114, 101, 3, 10, 57, 111, 49, 89, 13, 0, 103, 1, 114, 2, 32, 3, 13, 49, 0, 4, 1, 99, 2, 98, 101, 114, 3, 35, 57, 0, 1, 107, 115, 2, 108, 105, 103, 104, 116, 0, 1, 116, 115, 2, 108, 105, 115, 116, 0, 116, 101, 1, 98, 3, 35, 57, 47, 0, 112, 97, 115, 115, 1, 98, 3, 35, 57, 48, 35, 12, 87, 0, 4, 108, 101, 1, 108, 114, 97, 99, 3, 35, 57, 55, 0, 108, 101, 8, 108, 0, 100, 101, 1, 108, 99, 3, 35, 57, 70, 0, 100, 101, 108, 108, 1, 114, 3, 35, 57, 70, 6, 107, 59, 0, 107, 101, 115, 8, 115, 3, 35, 57, 79, 87, 0, 97, 8, 119, 2, 116, 116, 3, 35, 57, 106, 0, 110, 100, 111, 110, 8, 108, 3, 36, 50, 70, 112, 50, 0, 110, 116, 104, 101, 115, 105, 122, 101, 114, 1, 115, 3, 36, 50, 85, 36, 87, 35, 57, 87, 112, 0, 108, 118, 97, 110, 105, 97, 1, 115, 110, 110, 101, 112, 3, 36, 55, 82, 6, 107, 57, 50, 57, 108, 0, 4, 1, 98, 98, 111, 3, 37, 0, 1, 98, 105, 108, 0, 1, 99, 110, 97, 110, 0, 1, 99, 117, 108, 0, 1, 100, 2, 32, 0, 1, 100, 2, 108, 97, 110, 0, 1, 100, 2, 115, 32, 0, 1, 107, 99, 101, 98, 0, 1, 107, 115, 105, 104, 119, 0, 1, 108, 105, 109, 101, 0, 1, 108, 107, 111, 111, 114, 98, 2, 110, 0, 1, 108, 108, 101, 107, 0, 1, 108, 108, 105, 98, 0, 1, 108, 108, 105, 108, 0, 1, 108, 111, 114, 97, 99, 2, 110, 0, 1, 110, 110, 101, 112, 0, 1, 110, 110, 111, 100, 0, 1, 110, 110, 111, 114, 0, 1, 112, 112, 97, 104, 0, 1, 114, 97, 109, 2, 115, 0, 1, 114, 111, 103, 101, 114, 103, 0, 1, 114, 114, 97, 107, 2, 12, 0, 1, 114, 114, 101, 104, 115, 0, 1, 116, 102, 105, 102, 0, 1, 116, 105, 99, 0, 1, 116, 105, 110, 105, 114, 116, 0, 1, 116, 110, 117, 111, 99, 0, 1, 116, 114, 97, 112, 0, 1, 116, 115, 101, 110, 109, 97, 0, 1, 116, 116, 101, 98, 0, 1, 116, 116, 105, 107, 0, 1, 118, 108, 101, 109, 2, 110, 0, 8, 98, 97, 110, 114, 97, 98, 0, 8, 114, 114, 97, 104, 0, 1, 108, 111, 112, 2, 101, 115, 116, 3, 37, 6, 0, 112, 114, 101, 115, 8, 3, 37, 12, 48, 51, 20, 106, 0, 118, 101, 115, 8, 3, 37, 12, 82, 0, 102, 108, 111, 115, 115, 1, 100, 110, 97, 99, 3, 37, 81, 55, 112, 87, 0, 4, 1, 110, 2, 97, 3, 57, 0, 2, 97, 109, 115, 0, 2, 101, 109, 101, 110, 0, 2, 111, 103, 97, 0, 2, 111, 110, 110, 0, 97, 114, 100, 3, 57, 35, 34, 70, 0, 97, 99, 104, 116, 3, 57, 35, 79, 70, 0, 111, 107, 111, 104, 97, 109, 97, 3, 57, 39, 49, 39, 105, 6, 108, 63, 108, 0, 111, 121, 111, 3, 57, 39, 57, 6, 39, 0, 117, 112, 112, 105, 101, 3, 57, 40, 48, 37, 0, 111, 110, 1, 110, 97, 99, 3, 57, 106, 50, 0, 101, 110, 8, 3, 57, 107, 50, 0, 97, 116, 101, 115, 8, 3, 57, 107, 57, 47, 87, 0, 97, 108, 101, 3, 57, 107, 57, 59, 0, 101, 97, 103, 101, 114, 3, 57, 107, 79, 112, 0, 97, 116, 122, 121, 3, 57, 108, 47, 87, 37, 0, 97, 110, 107, 101, 101, 3, 57, 108, 50, 49, 37, 0, 111, 117, 110, 103, 3, 57, 112, 66, 0, 111, 114, 107, 3, 77, 112, 12, 49, 0, 2, 97, 115, 109, 105, 110, 3, 89, 0, 4, 3, 114, 0, 1, 17, 67, 2, 18, 73, 12, 0, 1, 98, 2, 17, 65, 0, 1, 107, 2, 108, 108, 105, 110, 103, 12, 0, 1, 107, 2, 115, 107, 12, 0, 1, 107, 115, 2, 115, 12, 0, 1, 107, 115, 2, 116, 101, 114, 0, 1, 107, 115, 2, 116, 105, 0, 1, 108, 2, 110, 32, 0, 1, 108, 102, 97, 2, 116, 0, 1, 108, 102, 97, 2, 116, 116, 0, 1, 110, 107, 2, 116, 0, 1, 114, 2, 17, 67, 17, 65, 12, 0, 1, 114, 2, 18, 71, 12, 0, 1, 114, 2, 100, 12, 0, 1, 114, 2, 103, 101, 12, 0, 1, 114, 2, 108, 108, 101, 0, 1, 114, 2, 115, 107, 12, 0, 1, 114, 2, 116, 12, 0, 1, 114, 98, 2, 110, 0, 1, 114, 102, 2, 115, 12, 0, 1, 114, 103, 2, 110, 0, 1, 114, 107, 2, 98, 98, 12, 0, 1, 114, 107, 2, 115, 12, 0, 1, 115, 2, 110, 100, 114, 111, 109, 0, 1, 115, 2, 110, 107, 114, 0, 1, 115, 2, 110, 116, 0, 1, 116, 2, 18, 66, 11, 101, 0, 8, 108, 2, 110, 0, 103, 1, 114, 2, 32, 101, 110, 0, 103, 1, 114, 2, 110, 105, 110, 103, 0, 103, 1, 114, 112, 2, 108, 0, 103, 1, 114, 116, 2, 108, 101, 0, 1, 107, 2, 115, 101, 12, 3, 114, 12, 0, 103, 101, 1, 114, 116, 115, 3, 114, 12, 13, 0, 110, 103, 1, 108, 2, 108, 105, 109, 116, 3, 114, 50, 79, 0, 4, 103, 1, 109, 100, 121, 3, 114, 57, 0, 103, 1, 114, 116, 115, 0, 118, 1, 115, 3, 114, 58, 0, 103, 101, 108, 107, 110, 97, 98, 101, 1, 114, 112, 3, 114, 79, 107, 55, 49, 50, 110, 69, 106, 0, 4, 1, 110, 2, 116, 3, 115, 0, 1, 114, 17, 67, 2, 18, 73, 0, 4, 114, 114, 101, 1, 102, 2, 107, 3, 115, 12, 112, 0, 114, 114, 101, 1, 102, 2, 116, 114, 0, 4, 1, 18, 73, 2, 116, 3, 116, 0, 1, 100, 2, 18, 66, 116, 0, 1, 100, 2, 107, 0, 1, 100, 2, 112, 0, 1, 107, 2, 109, 25, 0, 1, 107, 2, 115, 12, 0, 1, 107, 115, 2, 108, 32, 0, 1, 107, 115, 2, 108, 108, 0, 1, 107, 115, 2, 108, 110, 105, 0, 1, 108, 2, 103, 116, 0, 1, 108, 2, 107, 115, 97, 108, 105, 103, 0, 1, 108, 2, 107, 195, 184, 0, 1, 108, 2, 109, 17, 67, 0, 1, 108, 2, 110, 99, 104, 0, 1, 108, 2, 115, 116, 32, 116, 105, 108, 32, 0, 1, 108, 2, 115, 116, 98, 0, 1, 108, 2, 115, 116, 101, 108, 105, 103, 0, 1, 108, 2, 115, 116, 101, 110, 0, 1, 108, 2, 115, 116, 101, 114, 0, 1, 108, 2, 115, 116, 102, 105, 115, 107, 0, 1, 108, 2, 115, 116, 103, 195, 165, 114, 100, 0, 1, 108, 2, 115, 116, 104, 117, 115, 0, 1, 108, 2, 115, 116, 105, 103, 0, 1, 108, 2, 115, 116, 108, 195, 184, 103, 110, 0, 1, 108, 2, 115, 116, 109, 111, 114, 100, 0, 1, 108, 2, 115, 116, 110, 101, 0, 1, 108, 2, 115, 116, 115, 101, 106, 108, 0, 1, 108, 2, 115, 116, 115, 112, 105, 108, 0, 1, 108, 2, 115, 116, 121, 97, 99, 104, 116, 0, 1, 108, 32, 101, 107, 107, 105, 2, 115, 116, 0, 1, 108, 32, 114, 97, 104, 2, 115, 116, 0, 1, 108, 32, 114, 111, 116, 115, 2, 115, 116, 0, 1, 108, 32, 114, 165, 195, 102, 2, 115, 116, 0, 1, 108, 100, 97, 109, 2, 115, 116, 0, 1, 108, 101, 100, 105, 118, 2, 115, 116, 0, 1, 108, 101, 100, 166, 195, 2, 115, 116, 0, 1, 108, 101, 103, 114, 184, 195, 112, 115, 2, 115, 116, 0, 1, 108, 101, 107, 114, 105, 118, 2, 115, 116, 0, 1, 108, 101, 112, 112, 97, 107, 2, 115, 116, 0, 1, 108, 101, 114, 100, 110, 97, 118, 2, 115, 116, 0, 1, 108, 101, 114, 166, 195, 108, 2, 115, 116, 0, 1, 108, 101, 118, 105, 114, 107, 115, 2, 115, 116, 0, 1, 108, 102, 2, 116, 32, 0, 1, 108, 102, 2, 116, 98, 97, 114, 0, 1, 108, 102, 2, 116, 110, 0, 1, 108, 102, 2, 116, 116, 0, 1, 108, 108, 101, 118, 2, 115, 116, 0, 1, 108, 110, 101, 106, 184, 195, 2, 115, 116, 0, 1, 108, 110, 118, 166, 195, 104, 2, 115, 116, 0, 1, 108, 115, 110, 101, 106, 184, 195, 2, 115, 116, 0, 1, 108, 115, 110, 101, 114, 184, 195, 2, 115, 116, 0, 1, 108, 115, 118, 105, 108, 2, 115, 116, 0, 1, 108, 117, 2, 115, 116, 0, 1, 109, 115, 2, 107, 110, 0, 1, 110, 2, 107, 32, 0, 1, 110, 2, 107, 101, 114, 0, 1, 110, 2, 109, 102, 0, 1, 110, 2, 110, 110, 101, 0, 1, 110, 2, 116, 116, 0, 1, 110, 100, 117, 2, 116, 0, 1, 110, 101, 98, 2, 116, 0, 1, 112, 2, 110, 116, 0, 1, 114, 2, 17, 67, 12, 0, 1, 114, 100, 2, 112, 0, 1, 114, 103, 2, 110, 116, 0, 1, 114, 107, 2, 18, 66, 11, 12, 0, 1, 115, 2, 110, 107, 114, 111, 99, 0, 1, 115, 2, 116, 116, 101, 110, 0, 1, 116, 115, 2, 107, 12, 0, 1, 116, 115, 2, 109, 112, 101, 114, 0, 2, 107, 107, 12, 0, 2, 110, 100, 12, 0, 2, 110, 107, 0, 8, 110, 2, 110, 32, 0, 1, 110, 107, 2, 116, 116, 3, 116, 12, 0, 114, 114, 101, 1, 102, 3, 116, 12, 112, 0, 110, 100, 105, 1, 115, 2, 107, 3, 116, 50, 70, 37, 0, 110, 103, 2, 97, 3, 116, 50, 79, 0, 4, 110, 103, 3, 116, 66, 0, 110, 103, 1, 108, 0, 115, 115, 1, 107, 3, 116, 87, 0, 114, 111, 110, 101, 1, 116, 3, 118, 34, 6, 111, 58, 50, 0, 7, 6, 122, 0, 1, 101, 104, 99, 2, 32, 3, 0, 122, 1, 105, 112, 2, 97, 3, 47, 87, 0, 4, 3, 87, 0, 122, 0, 101, 97, 2, 108, 97, 110, 3, 87, 36, 0, 4, 111, 109, 98, 105, 3, 87, 112, 63, 69, 37, 0, 111, 109, 98, 105, 101, 0, 7, 6, 0, 195, 177, 3, 21, 101, 115, 0, 195, 175, 3, 37, 12, 0, 36, 3, 70, 112, 55, 112, 0, 195, 167, 3, 87, 0, 195, 160, 3, 108, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts10 = FileInMemory_createWithData (192093, reinterpret_cast (&espeakdata_dicts10_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/da_dict", L"da"); Collection_addItem (me.peek(), espeakdata_dicts10.transfer()); static unsigned char espeakdata_dicts11_data[21520] = { 0, 4, 0, 0, 79, 33, 0, 0, 0, 0, 0, 0, 0, 21, 65, 4, 114, 15, 114, 15, 10, 125, 0, 85, 46, 32, 97, 32, 46, 32, 111, 32, 46, 32, 0, 0, 0, 0, 0, 12, 201, 36, 228, 194, 21, 51, 206, 16, 84, 133, 67, 11, 70, 9, 35, 215, 76, 84, 128, 21, 0, 10, 0, 0, 9, 68, 76, 208, 76, 48, 21, 0, 10, 0, 0, 10, 135, 26, 21, 18, 195, 188, 3, 11, 66, 0, 13, 4, 95, 8, 1, 3, 105, 6, 35, 74, 107, 49, 0, 0, 0, 8, 67, 69, 82, 90, 21, 0, 10, 0, 0, 0, 0, 11, 67, 44, 19, 142, 4, 49, 35, 50, 0, 9, 0, 16, 70, 76, 243, 12, 80, 83, 128, 4, 86, 111, 55, 47, 13, 50, 0, 0, 11, 67, 76, 147, 132, 86, 109, 50, 47, 0, 72, 16, 4, 95, 48, 67, 15, 6, 105, 112, 50, 70, 106, 130, 47, 13, 0, 0, 0, 17, 7, 8, 195, 164, 20, 20, 5, 14, 105, 4, 107, 47, 13, 50, 0, 9, 0, 0, 0, 7, 196, 48, 147, 9, 20, 20, 7, 196, 45, 84, 137, 20, 20, 0, 0, 0, 8, 67, 28, 147, 128, 21, 0, 10, 17, 7, 8, 195, 164, 20, 20, 5, 20, 105, 4, 107, 47, 13, 47, 0, 9, 0, 0, 0, 0, 11, 67, 92, 148, 132, 82, 4, 109, 34, 70, 0, 17, 67, 9, 165, 192, 69, 13, 130, 116, 112, 66, 87, 82, 120, 86, 13, 0, 0, 6, 195, 21, 69, 193, 72, 9, 1, 35, 50, 112, 63, 106, 0, 27, 0, 0, 13, 1, 37, 48, 34, 125, 130, 6, 107, 50, 47, 0, 27, 0, 11, 67, 92, 148, 128, 82, 116, 34, 0, 72, 9, 7, 1, 38, 112, 50, 47, 0, 0, 0, 0, 0, 20, 71, 5, 97, 78, 81, 84, 137, 56, 35, 82, 107, 50, 47, 118, 34, 6, 116, 50, 0, 11, 67, 92, 20, 128, 2, 82, 114, 34, 0, 9, 22, 67, 28, 20, 128, 79, 4, 114, 34, 50, 6, 109, 97, 47, 0, 81, 110, 105, 99, 104, 116, 32, 10, 1, 42, 89, 47, 107, 34, 50, 0, 27, 0, 9, 1, 43, 48, 55, 112, 87, 0, 27, 0, 12, 201, 52, 149, 5, 36, 224, 78, 16, 84, 128, 65, 16, 69, 21, 133, 18, 20, 208, 107, 49, 87, 47, 34, 6, 124, 63, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 8, 80, 133, 56, 69, 124, 69, 13, 50, 0, 0, 0, 0, 0, 9, 68, 77, 82, 84, 20, 21, 0, 10, 0, 13, 5, 95, 48, 1, 14, 4, 15, 23, 112, 50, 47, 0, 0, 20, 9, 1, 21, 195, 159, 5, 18, 4, 5, 13, 6, 119, 87, 106, 70, 4, 124, 63, 0, 0, 0, 0, 12, 67, 28, 19, 154, 79, 4, 35, 50, 130, 0, 9, 0, 21, 73, 77, 2, 78, 61, 160, 73, 76, 50, 0, 87, 48, 116, 50, 6, 125, 130, 120, 89, 0, 9, 1, 61, 79, 55, 120, 97, 0, 27, 0, 19, 71, 21, 38, 135, 20, 34, 82, 28, 124, 34, 130, 79, 13, 69, 109, 34, 79, 0, 0, 7, 196, 64, 147, 137, 20, 20, 0, 15, 1, 64, 49, 55, 6, 35, 63, 106, 10, 4, 35, 81, 13, 0, 0, 9, 66, 4, 32, 35, 48, 0, 76, 28, 0, 11, 67, 76, 144, 200, 86, 109, 97, 0, 72, 9, 0, 0, 0, 0, 0, 0, 0, 16, 70, 20, 147, 137, 28, 84, 192, 120, 50, 109, 79, 13, 87, 0, 76, 8, 67, 48, 243, 203, 21, 0, 10, 0, 8, 67, 80, 129, 64, 84, 13, 0, 0, 0, 8, 197, 4, 195, 5, 36, 224, 66, 0, 16, 70, 77, 0, 82, 76, 19, 64, 89, 48, 114, 34, 86, 114, 63, 0, 8, 67, 77, 0, 77, 21, 0, 10, 0, 17, 70, 16, 160, 75, 5, 37, 1, 73, 35, 49, 6, 35, 34, 47, 114, 0, 9, 67, 5, 37, 0, 114, 34, 47, 0, 10, 67, 5, 81, 128, 119, 81, 0, 76, 28, 11, 67, 8, 65, 64, 69, 107, 50, 70, 13, 0, 0, 0, 10, 69, 76, 84, 150, 21, 32, 21, 0, 10, 0, 12, 137, 20, 18, 1, 7, 195, 182, 4, 9, 5, 20, 0, 0, 15, 68, 32, 16, 133, 56, 105, 4, 114, 69, 13, 50, 0, 9, 12, 8, 196, 56, 80, 133, 56, 76, 28, 0, 10, 69, 92, 147, 132, 61, 112, 21, 0, 10, 0, 0, 0, 0, 10, 69, 12, 128, 78, 28, 80, 21, 0, 10, 6, 65, 88, 81, 119, 0, 0, 0, 16, 67, 4, 227, 64, 6, 35, 50, 63, 4, 107, 34, 49, 112, 66, 0, 0, 0, 11, 1, 92, 69, 35, 49, 87, 55, 35, 89, 0, 0, 0, 17, 71, 92, 20, 211, 21, 37, 78, 28, 82, 35, 87, 13, 34, 112, 66, 0, 19, 71, 36, 195, 9, 8, 84, 129, 48, 109, 55, 116, 69, 13, 34, 6, 114, 55, 0, 12, 67, 92, 20, 148, 2, 82, 114, 34, 47, 0, 9, 10, 67, 16, 240, 200, 70, 111, 99, 0, 76, 0, 7, 196, 53, 83, 73, 20, 20, 0, 7, 65, 96, 109, 49, 87, 0, 0, 20, 4, 95, 49, 77, 50, 10, 6, 120, 50, 13, 15, 63, 109, 55, 109, 6, 125, 50, 0, 0, 22, 4, 95, 49, 77, 51, 10, 6, 120, 50, 13, 15, 63, 109, 55, 109, 6, 35, 34, 70, 13, 0, 0, 12, 68, 28, 80, 133, 56, 79, 124, 69, 13, 50, 0, 13, 68, 44, 243, 142, 80, 4, 49, 111, 50, 47, 0, 9, 0, 0, 0, 15, 67, 21, 101, 12, 124, 82, 107, 50, 47, 118, 6, 107, 55, 0, 0, 0, 21, 65, 104, 130, 112, 63, 69, 6, 120, 89, 48, 116, 55, 0, 83, 46, 32, 98, 32, 46, 32, 0, 0, 9, 67, 92, 20, 192, 82, 35, 87, 0, 0, 0, 8, 197, 105, 147, 66, 4, 192, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 69, 92, 82, 84, 84, 208, 82, 120, 47, 23, 6, 112, 63, 0, 0, 0, 10, 67, 76, 17, 212, 86, 114, 79, 47, 0, 9, 198, 44, 20, 212, 4, 226, 69, 20, 9, 198, 4, 227, 205, 4, 194, 69, 66, 0, 9, 68, 25, 32, 77, 20, 21, 0, 10, 0, 15, 69, 32, 21, 20, 20, 224, 105, 4, 35, 47, 13, 50, 0, 9, 0, 0, 8, 67, 84, 226, 88, 21, 0, 10, 9, 1, 126, 47, 109, 55, 70, 13, 0, 0, 0, 8, 197, 76, 19, 15, 65, 0, 66, 0, 9, 66, 8, 64, 69, 35, 50, 70, 0, 0, 7, 195, 21, 80, 200, 76, 9, 0, 9, 68, 25, 33, 65, 44, 21, 0, 10, 0, 0, 0, 15, 6, 8, 195, 164, 20, 20, 5, 105, 4, 107, 47, 13, 0, 9, 0, 9, 68, 21, 97, 78, 80, 21, 0, 10, 0, 0, 8, 67, 80, 19, 11, 21, 0, 10, 0, 0, 0, 0, 0, 9, 67, 5, 97, 64, 114, 82, 107, 0, 9, 67, 5, 80, 200, 4, 119, 99, 0, 0, 0, 0, 5, 194, 16, 16, 76, 0, 0, 0, 0, 0, 10, 67, 77, 34, 64, 87, 34, 4, 116, 0, 0, 11, 68, 81, 32, 73, 56, 47, 34, 124, 50, 0, 13, 68, 84, 210, 9, 56, 112, 63, 105, 6, 109, 50, 0, 0, 8, 197, 32, 244, 212, 36, 80, 20, 0, 0, 0, 0, 0, 0, 0, 13, 68, 36, 225, 5, 52, 109, 50, 70, 6, 124, 63, 0, 9, 198, 16, 86, 133, 52, 33, 82, 66, 0, 0, 0, 0, 13, 68, 36, 225, 5, 56, 109, 50, 70, 6, 124, 50, 0, 0, 0, 9, 198, 16, 83, 83, 20, 192, 128, 66, 0, 11, 67, 5, 84, 192, 4, 119, 87, 0, 28, 11, 0, 12, 68, 20, 147, 137, 28, 120, 50, 109, 97, 0, 9, 0, 14, 69, 52, 241, 5, 48, 192, 63, 125, 70, 6, 107, 55, 0, 10, 69, 64, 145, 7, 36, 224, 21, 0, 10, 0, 12, 66, 17, 32, 70, 111, 49, 47, 6, 125, 34, 0, 0, 0, 0, 0, 13, 138, 16, 18, 195, 164, 19, 9, 4, 5, 14, 20, 67, 9, 198, 16, 80, 129, 81, 65, 64, 66, 0, 0, 12, 68, 44, 19, 143, 20, 49, 35, 50, 6, 118, 0, 0, 8, 197, 76, 245, 197, 37, 64, 66, 0, 0, 8, 67, 4, 145, 0, 21, 0, 10, 0, 11, 68, 36, 225, 5, 72, 109, 50, 70, 106, 0, 0, 0, 0, 9, 198, 32, 148, 212, 61, 34, 69, 20, 0, 13, 68, 36, 225, 5, 76, 109, 50, 70, 6, 107, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 22, 10, 7, 5, 7, 5, 14, 195, 188, 2, 5, 18, 79, 124, 79, 13, 50, 6, 126, 69, 106, 0, 0, 8, 67, 64, 18, 82, 21, 0, 10, 0, 9, 198, 16, 145, 83, 20, 192, 128, 66, 0, 20, 71, 56, 81, 204, 36, 113, 78, 80, 50, 124, 79, 55, 116, 73, 6, 107, 50, 47, 0, 0, 12, 68, 104, 195, 212, 100, 87, 55, 111, 47, 116, 0, 13, 68, 84, 228, 210, 20, 112, 50, 86, 34, 13, 0, 72, 0, 0, 10, 66, 21, 32, 107, 34, 0, 72, 28, 9, 0, 10, 199, 4, 36, 212, 36, 225, 78, 80, 67, 9, 67, 16, 145, 64, 2, 70, 116, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 44, 19, 69, 48, 145, 64, 20, 17, 70, 28, 84, 129, 56, 145, 64, 79, 124, 34, 6, 114, 50, 109, 13, 0, 0, 9, 67, 8, 80, 84, 21, 0, 9, 10, 0, 10, 67, 36, 226, 193, 109, 66, 49, 114, 0, 0, 0, 0, 16, 70, 16, 17, 21, 72, 50, 0, 70, 114, 70, 6, 112, 34, 97, 0, 11, 67, 8, 82, 64, 69, 120, 0, 76, 28, 9, 0, 12, 4, 95, 4, 16, 20, 10, 49, 111, 63, 35, 0, 0, 0, 17, 66, 21, 48, 2, 107, 87, 2, 109, 87, 47, 0, 81, 105, 115, 116, 32, 9, 66, 21, 48, 107, 87, 0, 72, 9, 6, 194, 17, 80, 72, 9, 0, 9, 67, 80, 147, 64, 47, 109, 63, 0, 0, 7, 196, 52, 147, 149, 80, 66, 11, 67, 8, 82, 77, 69, 120, 63, 0, 76, 28, 0, 8, 67, 40, 80, 78, 21, 0, 10, 0, 10, 67, 16, 145, 83, 70, 116, 86, 0, 72, 17, 70, 84, 228, 197, 72, 83, 64, 112, 50, 87, 13, 34, 13, 63, 0, 72, 0, 16, 67, 36, 226, 204, 109, 50, 49, 55, 118, 86, 6, 116, 82, 13, 0, 0, 11, 67, 60, 35, 197, 125, 69, 6, 125, 13, 0, 0, 0, 0, 11, 67, 36, 228, 192, 109, 50, 87, 0, 76, 28, 0, 13, 4, 95, 20, 12, 4, 47, 6, 109, 55, 70, 13, 0, 17, 3, 95, 35, 57, 47, 4, 35, 69, 118, 55, 6, 114, 47, 125, 106, 0, 0, 0, 15, 70, 32, 21, 83, 36, 84, 128, 105, 119, 86, 6, 116, 34, 0, 0, 7, 195, 84, 228, 192, 76, 9, 0, 11, 200, 56, 85, 83, 20, 83, 1, 56, 64, 66, 12, 68, 4, 225, 18, 20, 35, 50, 70, 34, 13, 0, 13, 68, 84, 210, 5, 72, 112, 63, 105, 6, 107, 34, 0, 0, 0, 8, 66, 25, 32, 81, 34, 119, 0, 0, 19, 71, 4, 36, 197, 57, 66, 69, 72, 35, 48, 86, 107, 50, 47, 6, 116, 34, 0, 0, 0, 12, 67, 25, 35, 0, 81, 34, 122, 55, 120, 50, 0, 0, 9, 198, 80, 243, 142, 4, 113, 64, 20, 0, 0, 0, 0, 9, 198, 20, 225, 9, 88, 145, 64, 20, 9, 66, 4, 208, 35, 63, 0, 76, 28, 0, 0, 0, 8, 197, 4, 176, 90, 36, 80, 20, 10, 69, 72, 83, 65, 44, 80, 21, 0, 10, 14, 69, 76, 243, 12, 80, 80, 4, 86, 111, 55, 47, 13, 0, 0, 0, 0, 13, 68, 92, 242, 5, 72, 82, 125, 105, 6, 124, 34, 0, 12, 68, 92, 243, 12, 80, 2, 82, 111, 55, 47, 0, 8, 196, 36, 131, 133, 56, 76, 9, 0, 8, 197, 28, 195, 210, 36, 80, 20, 0, 17, 70, 81, 53, 78, 4, 210, 64, 130, 118, 50, 6, 35, 12, 63, 116, 0, 0, 18, 71, 28, 81, 204, 36, 50, 5, 56, 79, 13, 79, 55, 109, 97, 13, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 66, 4, 224, 35, 50, 0, 76, 28, 0, 16, 70, 12, 128, 78, 28, 145, 82, 89, 35, 66, 88, 6, 116, 34, 0, 0, 0, 0, 12, 67, 32, 16, 133, 2, 105, 114, 69, 13, 0, 9, 0, 0, 0, 13, 69, 16, 85, 1, 36, 192, 70, 124, 47, 6, 120, 0, 0, 0, 0, 0, 15, 69, 92, 147, 12, 77, 64, 2, 82, 109, 55, 87, 47, 0, 9, 0, 0, 0, 13, 72, 77, 113, 65, 81, 50, 9, 73, 64, 21, 0, 10, 0, 0, 11, 70, 72, 84, 197, 5, 32, 200, 21, 0, 10, 0, 0, 19, 8, 8, 195, 164, 20, 20, 5, 19, 20, 105, 4, 107, 47, 107, 87, 47, 0, 9, 0, 9, 198, 72, 83, 9, 69, 82, 69, 20, 12, 201, 44, 243, 147, 21, 37, 129, 80, 149, 128, 65, 11, 67, 32, 21, 0, 2, 105, 35, 47, 0, 9, 0, 12, 5, 11, 23, 1, 195, 159, 49, 82, 35, 87, 0, 0, 0, 11, 136, 23, 195, 164, 8, 18, 5, 14, 4, 72, 12, 68, 76, 50, 15, 56, 89, 4, 125, 50, 0, 12, 11, 136, 23, 195, 164, 8, 18, 5, 14, 4, 8, 0, 0, 0, 0, 0, 12, 67, 25, 81, 82, 81, 126, 34, 0, 76, 8, 9, 0, 9, 198, 16, 17, 197, 28, 83, 128, 66, 0, 11, 67, 105, 83, 64, 130, 112, 63, 0, 76, 8, 9, 67, 32, 147, 128, 105, 109, 50, 0, 0, 11, 70, 16, 80, 149, 28, 113, 82, 21, 0, 10, 0, 8, 197, 92, 244, 129, 85, 48, 66, 0, 18, 70, 16, 149, 137, 16, 83, 132, 70, 116, 82, 116, 70, 6, 107, 50, 47, 0, 7, 66, 16, 160, 21, 0, 10, 0, 7, 195, 16, 148, 128, 76, 9, 0, 12, 68, 20, 147, 133, 56, 120, 50, 13, 50, 0, 72, 0, 13, 69, 28, 83, 69, 36, 224, 79, 13, 63, 120, 50, 0, 6, 195, 16, 19, 142, 72, 0, 16, 70, 17, 32, 71, 36, 84, 128, 70, 34, 35, 88, 6, 116, 34, 0, 0, 0, 0, 23, 73, 65, 34, 86, 5, 66, 83, 36, 84, 128, 48, 34, 116, 82, 35, 47, 116, 86, 6, 116, 34, 0, 8, 197, 44, 243, 147, 84, 192, 65, 15, 69, 28, 83, 137, 4, 192, 79, 124, 50, 109, 6, 35, 55, 0, 0, 16, 70, 92, 82, 84, 32, 84, 128, 82, 120, 47, 105, 6, 107, 34, 0, 15, 70, 64, 240, 200, 36, 84, 128, 48, 111, 89, 6, 116, 34, 0, 8, 66, 33, 32, 105, 107, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 17, 81, 84, 80, 70, 118, 6, 107, 47, 0, 0, 0, 0, 0, 13, 68, 4, 229, 9, 44, 35, 50, 47, 6, 116, 49, 0, 0, 0, 0, 0, 12, 68, 36, 132, 133, 52, 116, 34, 13, 63, 0, 72, 0, 0, 0, 17, 71, 92, 82, 84, 21, 37, 78, 28, 82, 120, 47, 13, 34, 112, 66, 0, 0, 12, 68, 20, 147, 133, 52, 120, 50, 13, 63, 0, 72, 0, 14, 73, 5, 52, 207, 12, 144, 84, 36, 243, 128, 21, 0, 10, 0, 0, 9, 67, 80, 160, 64, 47, 57, 114, 0, 8, 67, 76, 194, 80, 21, 0, 10, 0, 0, 0, 0, 0, 12, 68, 32, 19, 132, 100, 105, 107, 50, 70, 116, 0, 11, 68, 36, 132, 133, 72, 116, 34, 106, 0, 72, 13, 3, 95, 49, 15, 10, 6, 124, 34, 87, 47, 13, 0, 0, 13, 69, 28, 84, 211, 20, 224, 79, 107, 87, 13, 50, 0, 8, 197, 92, 244, 129, 84, 96, 66, 0, 10, 3, 95, 49, 1, 10, 6, 120, 50, 0, 0, 9, 3, 226, 130, 172, 122, 34, 125, 0, 0, 0, 11, 70, 32, 243, 69, 64, 17, 197, 21, 0, 10, 0, 0, 9, 67, 80, 17, 192, 47, 114, 79, 0, 0, 0, 16, 70, 52, 83, 149, 21, 69, 5, 63, 107, 50, 118, 6, 107, 47, 0, 0, 0, 0, 12, 68, 4, 50, 19, 60, 35, 99, 86, 6, 125, 0, 11, 68, 20, 147, 133, 72, 120, 50, 106, 0, 72, 7, 195, 36, 50, 0, 72, 9, 14, 68, 16, 84, 133, 56, 70, 124, 34, 13, 50, 0, 76, 28, 0, 0, 0, 15, 70, 20, 225, 12, 36, 50, 0, 107, 50, 47, 55, 109, 97, 0, 0, 10, 67, 52, 244, 147, 63, 111, 34, 87, 0, 13, 68, 92, 84, 132, 20, 82, 4, 107, 34, 70, 13, 0, 12, 68, 20, 147, 133, 76, 120, 50, 13, 87, 0, 72, 12, 3, 95, 51, 15, 70, 34, 6, 109, 47, 13, 0, 9, 4, 95, 15, 18, 4, 47, 13, 0, 0, 0, 0, 7, 195, 16, 144, 200, 76, 9, 0, 0, 10, 67, 37, 53, 0, 109, 87, 47, 0, 72, 0, 0, 8, 67, 73, 83, 128, 21, 0, 10, 7, 195, 36, 131, 64, 76, 9, 0, 0, 0, 0, 20, 71, 21, 2, 83, 44, 244, 1, 48, 124, 48, 109, 87, 49, 125, 48, 6, 114, 55, 0, 6, 195, 57, 84, 128, 28, 0, 0, 12, 67, 33, 34, 18, 105, 35, 34, 105, 35, 34, 0, 0, 8, 67, 76, 197, 77, 21, 0, 10, 0, 11, 67, 105, 84, 128, 130, 118, 34, 0, 76, 8, 10, 67, 16, 20, 192, 2, 70, 35, 87, 0, 0, 0, 0, 14, 4, 95, 13, 3, 14, 63, 6, 114, 49, 34, 111, 50, 0, 0, 0, 0, 0, 0, 11, 70, 40, 246, 83, 80, 144, 203, 21, 0, 10, 0, 0, 10, 69, 80, 80, 83, 21, 32, 21, 0, 10, 0, 0, 10, 67, 8, 84, 212, 69, 107, 87, 47, 0, 0, 13, 68, 92, 244, 129, 56, 82, 125, 34, 6, 35, 50, 0, 0, 0, 0, 19, 71, 25, 34, 69, 17, 99, 204, 48, 81, 34, 6, 116, 47, 81, 4, 111, 55, 0, 12, 67, 32, 20, 212, 2, 105, 35, 87, 47, 0, 9, 0, 10, 67, 16, 20, 211, 70, 35, 87, 0, 76, 12, 3, 95, 55, 15, 86, 6, 116, 69, 47, 13, 0, 0, 14, 69, 20, 147, 137, 28, 80, 120, 50, 109, 79, 13, 0, 76, 0, 0, 0, 0, 11, 67, 60, 65, 82, 125, 70, 106, 0, 76, 8, 0, 0, 0, 0, 0, 0, 13, 3, 95, 51, 88, 6, 70, 34, 120, 87, 109, 97, 0, 0, 12, 68, 84, 229, 5, 56, 112, 50, 47, 13, 50, 0, 13, 3, 95, 48, 67, 6, 105, 112, 50, 70, 106, 47, 0, 0, 13, 69, 52, 16, 200, 20, 224, 63, 35, 99, 13, 50, 0, 0, 0, 8, 67, 81, 34, 80, 21, 0, 10, 0, 12, 68, 8, 85, 5, 56, 69, 124, 47, 13, 50, 0, 0, 0, 0, 14, 203, 88, 145, 76, 8, 84, 208, 72, 240, 200, 20, 224, 67, 0, 12, 68, 20, 147, 147, 80, 6, 120, 50, 87, 47, 0, 0, 0, 0, 0, 0, 0, 5, 194, 40, 80, 72, 13, 3, 95, 49, 57, 6, 50, 122, 50, 130, 124, 50, 0, 0, 13, 3, 95, 49, 56, 6, 10, 35, 99, 130, 124, 50, 0, 0, 15, 68, 84, 229, 5, 72, 4, 112, 50, 47, 106, 0, 8, 11, 9, 0, 8, 67, 40, 85, 0, 21, 0, 10, 0, 8, 67, 32, 148, 0, 21, 0, 10, 0, 0, 0, 14, 69, 8, 84, 212, 36, 80, 69, 107, 87, 47, 109, 13, 0, 0, 11, 70, 8, 20, 197, 8, 19, 12, 21, 0, 10, 11, 3, 95, 49, 49, 6, 10, 107, 55, 81, 0, 0, 10, 3, 95, 49, 48, 6, 130, 124, 50, 0, 0, 9, 68, 48, 85, 133, 48, 21, 0, 10, 13, 3, 95, 49, 51, 6, 70, 34, 120, 130, 124, 50, 0, 0, 12, 3, 95, 49, 50, 6, 130, 82, 129, 55, 81, 0, 0, 14, 3, 95, 49, 53, 6, 81, 127, 50, 81, 130, 124, 50, 0, 0, 7, 195, 36, 131, 128, 76, 9, 14, 5, 195, 188, 2, 5, 18, 4, 127, 69, 106, 0, 8, 11, 13, 3, 95, 49, 52, 6, 81, 109, 34, 130, 124, 50, 0, 0, 13, 68, 76, 84, 137, 20, 87, 124, 34, 109, 38, 13, 0, 7, 196, 61, 33, 201, 20, 20, 13, 3, 95, 49, 55, 6, 86, 116, 48, 130, 124, 50, 0, 0, 13, 3, 95, 49, 54, 6, 86, 107, 97, 130, 124, 50, 0, 0, 10, 67, 36, 132, 133, 116, 34, 13, 0, 72, 0, 13, 3, 95, 55, 88, 6, 86, 116, 48, 130, 109, 97, 0, 0, 13, 68, 92, 20, 133, 56, 2, 82, 114, 34, 13, 50, 0, 0, 8, 197, 8, 19, 11, 4, 224, 65, 0, 9, 198, 16, 83, 147, 20, 192, 128, 66, 17, 70, 16, 20, 211, 20, 192, 128, 70, 35, 87, 86, 6, 107, 55, 69, 0, 17, 70, 16, 84, 211, 20, 192, 128, 70, 107, 87, 86, 6, 107, 55, 69, 0, 9, 198, 16, 84, 147, 20, 192, 128, 66, 0, 9, 67, 36, 132, 128, 116, 34, 0, 72, 0, 0, 0, 0, 0, 0, 0, 8, 67, 76, 86, 25, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 69, 48, 20, 20, 61, 0, 21, 0, 10, 14, 3, 95, 50, 88, 6, 130, 82, 35, 50, 130, 109, 97, 0, 0, 0, 0, 0, 10, 199, 36, 211, 79, 8, 147, 9, 20, 20, 0, 12, 3, 95, 56, 15, 10, 6, 35, 99, 47, 13, 0, 0, 0, 15, 70, 36, 226, 193, 37, 48, 200, 109, 66, 49, 114, 109, 89, 0, 0, 11, 67, 76, 82, 84, 86, 120, 47, 0, 72, 9, 0, 0, 0, 11, 70, 24, 148, 133, 92, 19, 12, 21, 0, 10, 0, 0, 9, 68, 77, 21, 65, 92, 21, 0, 10, 13, 3, 95, 63, 63, 86, 127, 63, 69, 6, 125, 55, 0, 0, 0, 0, 13, 3, 95, 52, 88, 6, 81, 109, 34, 130, 109, 97, 0, 0, 0, 10, 69, 77, 2, 82, 37, 64, 21, 0, 10, 0, 0, 11, 136, 11, 15, 13, 195, 182, 4, 9, 5, 20, 6, 195, 92, 82, 76, 8, 0, 0, 14, 69, 20, 147, 136, 21, 32, 120, 50, 105, 6, 124, 34, 0, 0, 8, 66, 52, 48, 63, 14, 49, 0, 8, 66, 32, 208, 105, 13, 63, 0, 0, 14, 3, 95, 53, 88, 6, 81, 127, 50, 81, 130, 109, 97, 0, 0, 14, 68, 8, 85, 143, 72, 69, 13, 81, 125, 34, 0, 66, 8, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 54, 88, 6, 86, 107, 97, 130, 109, 97, 0, 0, 0, 6, 195, 76, 82, 78, 72, 0, 0, 11, 67, 88, 243, 64, 81, 111, 63, 0, 76, 28, 0, 0, 0, 0, 8, 67, 24, 245, 76, 21, 0, 10, 0, 0, 0, 0, 10, 199, 56, 85, 77, 21, 130, 75, 60, 66, 0, 0, 0, 9, 66, 57, 32, 50, 112, 63, 106, 0, 0, 20, 71, 20, 33, 78, 16, 18, 5, 72, 124, 69, 13, 50, 70, 35, 105, 6, 124, 34, 0, 8, 67, 52, 18, 76, 21, 0, 10, 13, 3, 95, 56, 88, 6, 10, 35, 99, 130, 109, 97, 0, 0, 0, 13, 69, 76, 16, 130, 5, 64, 86, 35, 69, 35, 47, 0, 0, 16, 70, 64, 20, 211, 4, 113, 64, 48, 35, 87, 6, 35, 88, 13, 0, 9, 198, 36, 226, 149, 72, 145, 64, 20, 9, 198, 5, 37, 5, 72, 145, 64, 20, 0, 0, 11, 70, 32, 243, 204, 36, 112, 78, 21, 0, 10, 0, 9, 67, 44, 145, 0, 49, 109, 70, 0, 12, 137, 1, 20, 15, 13, 13, 195, 188, 12, 12, 65, 0, 9, 198, 52, 21, 5, 72, 145, 64, 20, 9, 66, 36, 208, 109, 63, 0, 76, 28, 0, 13, 3, 95, 57, 88, 6, 50, 122, 50, 130, 109, 97, 0, 0, 11, 200, 36, 226, 207, 57, 53, 1, 57, 64, 65, 13, 68, 32, 21, 20, 20, 105, 4, 35, 47, 13, 0, 9, 0, 8, 197, 57, 83, 69, 72, 240, 65, 0, 0, 0, 0, 0, 15, 3, 95, 63, 65, 69, 6, 118, 99, 87, 47, 114, 69, 13, 0, 0, 20, 71, 20, 33, 78, 16, 18, 9, 56, 124, 69, 13, 50, 70, 35, 105, 6, 109, 50, 0, 0, 13, 72, 20, 229, 5, 73, 4, 137, 76, 80, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 11, 66, 60, 32, 4, 111, 69, 0, 8, 11, 9, 9, 66, 36, 224, 109, 50, 0, 76, 28, 0, 17, 70, 20, 225, 193, 28, 145, 82, 35, 66, 79, 35, 88, 6, 116, 34, 0, 8, 67, 40, 240, 128, 21, 0, 10, 0, 0, 0, 15, 70, 80, 129, 65, 80, 84, 128, 47, 124, 6, 114, 47, 106, 0, 0, 15, 4, 95, 15, 7, 15, 6, 125, 79, 111, 50, 4, 107, 49, 0, 0, 13, 68, 40, 85, 26, 80, 57, 4, 107, 130, 47, 0, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 69, 48, 241, 201, 21, 32, 55, 125, 88, 6, 116, 34, 0, 0, 0, 0, 0, 15, 69, 73, 112, 78, 16, 16, 34, 112, 6, 35, 50, 70, 114, 0, 12, 67, 92, 83, 142, 4, 82, 107, 50, 0, 8, 11, 0, 0, 10, 67, 28, 80, 148, 79, 124, 69, 47, 0, 0, 0, 0, 0, 9, 67, 20, 147, 128, 120, 50, 0, 76, 11, 67, 65, 35, 192, 4, 48, 34, 125, 0, 8, 0, 14, 4, 95, 48, 77, 52, 69, 109, 55, 109, 6, 125, 50, 0, 0, 0, 15, 70, 25, 84, 131, 32, 83, 128, 81, 112, 34, 97, 13, 50, 0, 17, 4, 95, 48, 77, 50, 15, 63, 109, 55, 109, 6, 125, 50, 13, 50, 0, 0, 11, 67, 52, 19, 128, 63, 35, 50, 0, 72, 9, 11, 67, 88, 243, 128, 81, 111, 50, 0, 76, 28, 18, 4, 95, 48, 77, 51, 15, 63, 109, 55, 109, 6, 35, 34, 70, 13, 50, 0, 0, 10, 67, 20, 147, 133, 120, 50, 13, 0, 72, 0, 14, 4, 95, 48, 77, 49, 6, 47, 119, 86, 13, 50, 47, 0, 0, 9, 66, 60, 64, 125, 70, 106, 0, 9, 14, 4, 95, 2, 18, 22, 69, 14, 16, 6, 123, 82, 13, 0, 0, 7, 195, 52, 148, 128, 76, 9, 0, 0, 10, 69, 5, 4, 5, 4, 192, 21, 0, 10, 0, 16, 67, 33, 36, 199, 105, 107, 34, 6, 119, 87, 79, 124, 69, 106, 0, 0, 11, 67, 88, 244, 128, 4, 81, 111, 34, 0, 11, 0, 0, 0, 0, 0, 0, 12, 69, 76, 50, 21, 49, 64, 89, 118, 55, 47, 0, 0, 0, 0, 0, 0, 13, 66, 44, 208, 49, 116, 55, 125, 63, 124, 47, 106, 0, 0, 0, 11, 200, 88, 145, 76, 48, 82, 67, 33, 64, 66, 0, 12, 67, 105, 112, 82, 130, 82, 4, 35, 12, 34, 0, 0, 0, 11, 67, 52, 149, 0, 63, 109, 47, 0, 76, 8, 0, 0, 0, 7, 66, 53, 144, 21, 0, 10, 0, 18, 9, 8, 195, 164, 21, 19, 3, 8, 5, 14, 105, 122, 87, 97, 13, 50, 0, 0, 0, 0, 9, 198, 52, 243, 143, 80, 243, 128, 67, 0, 8, 67, 61, 85, 0, 21, 0, 10, 0, 9, 68, 12, 240, 67, 32, 21, 0, 10, 0, 0, 0, 0, 0, 0, 11, 70, 4, 48, 207, 84, 229, 0, 21, 0, 10, 0, 15, 70, 20, 147, 133, 72, 193, 73, 120, 50, 13, 34, 55, 120, 0, 0, 0, 0, 9, 198, 56, 80, 149, 48, 244, 192, 67, 0, 7, 195, 52, 144, 200, 72, 9, 0, 10, 67, 21, 33, 5, 124, 34, 70, 13, 0, 0, 0, 0, 24, 67, 56, 240, 200, 50, 6, 111, 99, 15, 50, 6, 109, 97, 47, 0, 28, 81, 110, 105, 99, 104, 116, 32, 6, 195, 56, 240, 200, 8, 0, 11, 68, 64, 240, 200, 76, 48, 111, 99, 87, 0, 0, 0, 0, 9, 198, 77, 2, 79, 56, 17, 197, 20, 0, 0, 0, 0, 0, 8, 67, 40, 242, 197, 21, 0, 10, 0, 11, 67, 4, 33, 82, 114, 69, 106, 0, 76, 8, 0, 16, 70, 5, 32, 200, 4, 146, 192, 35, 34, 97, 6, 114, 109, 49, 0, 0, 0, 16, 70, 20, 147, 129, 56, 65, 82, 120, 50, 6, 35, 50, 70, 106, 0, 0, 0, 19, 4, 95, 3, 9, 18, 130, 6, 109, 34, 49, 112, 63, 81, 55, 107, 49, 87, 0, 0, 0, 0, 0, 0, 0, 9, 68, 76, 130, 82, 80, 21, 0, 10, 0, 0, 0, 0, 0, 15, 69, 36, 229, 5, 72, 224, 109, 50, 47, 6, 107, 34, 50, 0, 15, 69, 92, 243, 12, 20, 224, 2, 82, 111, 55, 13, 50, 0, 9, 0, 0, 17, 4, 95, 19, 20, 11, 89, 34, 6, 124, 79, 87, 47, 34, 109, 97, 0, 0, 0, 15, 69, 64, 192, 78, 21, 64, 48, 55, 35, 50, 6, 124, 47, 0, 12, 4, 95, 1, 3, 21, 35, 49, 6, 118, 47, 0, 0, 10, 198, 60, 33, 204, 20, 144, 200, 66, 8, 21, 3, 95, 194, 171, 6, 35, 50, 81, 126, 51, 112, 66, 87, 130, 4, 120, 97, 13, 50, 0, 0, 0, 0, 0, 11, 70, 80, 84, 141, 36, 224, 76, 21, 0, 10, 0, 0, 0, 15, 69, 16, 144, 68, 20, 208, 70, 116, 35, 70, 6, 124, 63, 0, 10, 69, 72, 240, 68, 36, 80, 21, 0, 10, 0, 0, 9, 198, 48, 20, 16, 4, 194, 69, 20, 15, 4, 95, 18, 14, 7, 49, 34, 6, 125, 58, 88, 107, 49, 0, 0, 0, 0, 0, 0, 13, 68, 105, 81, 5, 52, 130, 118, 6, 70, 124, 63, 0, 0, 0, 0, 0, 0, 0, 0, 20, 71, 77, 64, 76, 4, 115, 73, 80, 87, 47, 35, 55, 35, 79, 63, 6, 109, 47, 0, 16, 67, 4, 32, 128, 6, 35, 69, 69, 4, 109, 55, 70, 112, 66, 0, 0, 7, 196, 76, 241, 193, 72, 66, 0, 0, 0, 0, 9, 67, 104, 243, 205, 86, 118, 63, 0, 11, 68, 16, 145, 78, 80, 70, 116, 50, 47, 0, 0, 14, 69, 21, 36, 212, 20, 224, 124, 34, 87, 47, 13, 50, 0, 0, 0, 0, 0, 14, 69, 76, 83, 2, 77, 64, 86, 107, 55, 48, 87, 47, 0, 0, 18, 4, 95, 1, 3, 50, 70, 6, 111, 48, 13, 55, 35, 49, 4, 118, 47, 0, 0, 0, 0, 0, 9, 66, 60, 176, 125, 49, 6, 124, 0, 0, 0, 0, 18, 70, 88, 244, 136, 21, 34, 71, 81, 125, 34, 105, 6, 124, 34, 109, 132, 0, 14, 69, 52, 243, 148, 4, 112, 63, 125, 50, 47, 114, 49, 0, 0, 0, 10, 67, 76, 243, 12, 4, 86, 111, 55, 0, 0, 6, 195, 5, 34, 69, 20, 0, 0, 0, 0, 0, 0, 25, 3, 95, 194, 187, 6, 35, 50, 81, 126, 51, 112, 66, 87, 130, 4, 120, 97, 13, 50, 15, 130, 6, 118, 0, 0, 10, 199, 20, 33, 78, 24, 19, 12, 76, 8, 0, 11, 70, 72, 80, 197, 37, 97, 82, 21, 0, 10, 0, 0, 0, 0, 14, 68, 28, 81, 197, 56, 79, 124, 79, 13, 50, 0, 76, 8, 0, 0, 0, 0, 0, 0, 10, 66, 77, 64, 6, 107, 87, 47, 124, 0, 12, 6, 95, 15, 18, 4, 50, 48, 87, 47, 13, 0, 0, 5, 130, 196, 141, 43, 0, 0, 12, 201, 21, 133, 18, 5, 96, 71, 4, 229, 0, 65, 0, 0, 0, 0, 0, 11, 70, 88, 83, 148, 85, 33, 64, 21, 0, 10, 0, 0, 8, 67, 76, 86, 0, 21, 0, 10, 23, 68, 56, 144, 200, 80, 50, 6, 109, 97, 47, 15, 50, 6, 118, 34, 0, 8, 81, 110, 117, 114, 32, 24, 68, 56, 144, 200, 80, 50, 4, 109, 97, 47, 15, 63, 6, 124, 34, 0, 14, 81, 109, 101, 104, 114, 32, 23, 68, 56, 144, 200, 80, 50, 6, 109, 97, 47, 15, 4, 63, 124, 34, 0, 81, 109, 101, 104, 114, 32, 0, 9, 2, 194, 163, 48, 119, 50, 70, 0, 0, 0, 0, 17, 70, 21, 36, 212, 52, 19, 0, 124, 34, 87, 47, 63, 35, 12, 55, 0, 5, 130, 195, 166, 43, 0, 10, 69, 76, 245, 82, 12, 80, 21, 0, 10, 5, 130, 195, 167, 43, 0, 0, 0, 0, 0, 0, 0, 11, 70, 12, 243, 80, 85, 65, 82, 21, 0, 10, 0, 0, 0, 0, 7, 196, 16, 82, 78, 20, 76, 0, 0, 9, 2, 194, 176, 79, 34, 114, 47, 0, 0, 16, 70, 16, 162, 66, 61, 85, 9, 73, 37, 69, 6, 118, 47, 116, 0, 5, 130, 195, 169, 43, 17, 2, 194, 177, 48, 55, 6, 112, 87, 15, 63, 6, 116, 50, 112, 87, 0, 0, 0, 0, 9, 198, 5, 52, 8, 4, 197, 0, 66, 0, 18, 71, 5, 36, 129, 56, 114, 69, 72, 35, 34, 35, 66, 88, 6, 116, 13, 0, 18, 71, 5, 36, 5, 28, 114, 69, 72, 35, 34, 48, 107, 73, 6, 116, 34, 0, 8, 67, 64, 195, 212, 21, 0, 10, 0, 13, 4, 95, 3, 5, 4, 87, 124, 70, 6, 116, 57, 0, 0, 0, 0, 5, 130, 197, 161, 43, 16, 4, 95, 12, 9, 7, 55, 6, 116, 79, 35, 47, 4, 118, 106, 0, 0, 0, 0, 0, 0, 0, 13, 69, 28, 83, 210, 28, 80, 73, 111, 12, 34, 73, 0, 18, 7, 11, 195, 182, 14, 14, 5, 14, 4, 49, 129, 50, 13, 50, 0, 9, 12, 0, 0, 0, 0, 8, 67, 76, 227, 194, 21, 0, 10, 6, 195, 16, 82, 78, 76, 0, 0, 0, 0, 9, 198, 64, 20, 129, 16, 145, 83, 67, 0, 0, 10, 67, 16, 83, 64, 2, 70, 124, 63, 0, 0, 9, 68, 53, 148, 209, 48, 21, 0, 10, 5, 130, 197, 190, 43, 0, 0, 9, 198, 76, 243, 132, 21, 35, 128, 8, 0, 11, 4, 4, 1, 195, 159, 70, 35, 87, 0, 76, 0, 9, 68, 12, 128, 82, 80, 21, 0, 10, 7, 196, 76, 82, 78, 20, 76, 0, 16, 69, 76, 241, 66, 20, 224, 86, 125, 10, 6, 124, 69, 13, 50, 0, 0, 0, 0, 0, 0, 15, 6, 11, 195, 182, 14, 14, 20, 4, 49, 129, 50, 47, 0, 9, 0, 0, 8, 67, 9, 149, 5, 21, 0, 10, 12, 68, 16, 145, 83, 20, 70, 116, 86, 13, 0, 72, 0, 14, 69, 49, 80, 197, 57, 64, 55, 118, 87, 107, 50, 47, 0, 15, 69, 93, 84, 132, 21, 64, 82, 4, 112, 34, 70, 13, 47, 0, 15, 69, 92, 84, 132, 21, 64, 82, 4, 107, 34, 70, 13, 47, 0, 0, 0, 12, 71, 64, 83, 148, 32, 245, 83, 20, 21, 0, 10, 0, 0, 0, 11, 70, 29, 35, 213, 64, 145, 64, 21, 0, 10, 13, 4, 6, 195, 188, 18, 81, 126, 34, 0, 76, 8, 9, 0, 9, 198, 64, 84, 144, 48, 86, 0, 66, 0, 0, 13, 69, 17, 34, 84, 80, 80, 70, 34, 109, 47, 13, 0, 0, 0, 0, 0, 0, 0, 8, 67, 12, 245, 80, 49, 118, 0, 0, 0, 0, 0, 0, 0, 0, 15, 70, 28, 84, 212, 21, 35, 128, 79, 107, 87, 47, 106, 50, 0, 17, 70, 93, 84, 132, 21, 53, 0, 82, 4, 112, 34, 70, 107, 87, 47, 0, 0, 0, 0, 11, 68, 44, 131, 69, 72, 49, 63, 124, 34, 0, 11, 68, 8, 81, 82, 20, 69, 124, 34, 13, 0, 9, 68, 81, 83, 133, 72, 21, 0, 10, 0, 0, 0, 0, 12, 68, 88, 244, 137, 28, 81, 125, 34, 109, 132, 0, 0, 0, 11, 70, 76, 48, 78, 56, 84, 128, 21, 0, 10, 0, 0, 13, 68, 92, 148, 147, 80, 82, 4, 109, 34, 87, 47, 0, 0, 0, 10, 135, 16, 18, 195, 164, 13, 9, 5, 20, 16, 70, 32, 84, 130, 21, 33, 192, 105, 107, 34, 69, 107, 34, 79, 0, 0, 0, 0, 0, 0, 29, 75, 65, 35, 194, 48, 83, 65, 80, 148, 201, 21, 32, 48, 34, 125, 69, 55, 124, 63, 6, 35, 12, 47, 109, 86, 116, 34, 0, 10, 199, 44, 20, 148, 60, 224, 71, 20, 20, 0, 0, 14, 69, 84, 228, 197, 72, 80, 112, 50, 86, 34, 13, 0, 72, 0, 0, 0, 14, 67, 4, 195, 7, 6, 35, 55, 79, 13, 63, 120, 50, 0, 11, 2, 95, 34, 130, 116, 47, 6, 114, 47, 0, 0, 20, 2, 95, 33, 6, 119, 87, 23, 34, 4, 118, 81, 13, 130, 4, 120, 97, 13, 50, 0, 0, 0, 15, 2, 95, 39, 4, 35, 48, 125, 87, 47, 34, 6, 111, 81, 0, 0, 8, 67, 76, 243, 135, 21, 0, 10, 0, 18, 70, 20, 228, 197, 52, 35, 5, 111, 50, 87, 6, 111, 63, 69, 13, 55, 0, 0, 0, 10, 67, 8, 147, 128, 69, 109, 50, 0, 72, 10, 67, 16, 83, 128, 2, 70, 124, 50, 0, 0, 13, 68, 92, 20, 149, 52, 82, 114, 34, 6, 112, 63, 0, 9, 68, 20, 208, 73, 48, 21, 0, 10, 12, 4, 95, 3, 1, 16, 79, 34, 6, 125, 87, 0, 0, 11, 67, 16, 83, 142, 70, 107, 50, 0, 76, 8, 15, 2, 95, 41, 49, 55, 6, 35, 63, 106, 15, 130, 6, 118, 0, 0, 17, 70, 105, 81, 197, 28, 83, 128, 130, 118, 79, 6, 124, 79, 13, 50, 0, 17, 70, 105, 81, 197, 28, 83, 128, 130, 118, 79, 6, 124, 79, 13, 50, 0, 16, 2, 95, 40, 49, 55, 6, 35, 63, 106, 15, 23, 6, 119, 81, 0, 0, 8, 67, 92, 244, 132, 21, 0, 10, 11, 67, 64, 84, 128, 48, 107, 34, 0, 76, 28, 15, 2, 95, 47, 89, 34, 6, 124, 79, 89, 47, 34, 109, 97, 0, 0, 17, 70, 36, 225, 5, 77, 49, 78, 109, 50, 70, 6, 107, 87, 13, 50, 0, 10, 2, 95, 46, 48, 112, 50, 49, 47, 0, 0, 17, 2, 95, 45, 69, 6, 109, 50, 70, 13, 87, 47, 34, 4, 109, 97, 0, 0, 9, 2, 95, 44, 49, 111, 63, 35, 0, 0, 10, 67, 16, 84, 128, 2, 70, 107, 34, 0, 9, 2, 95, 51, 6, 70, 34, 120, 0, 0, 9, 2, 95, 50, 6, 130, 82, 120, 0, 0, 10, 2, 95, 49, 10, 6, 120, 50, 87, 0, 0, 9, 2, 95, 48, 6, 50, 112, 55, 0, 0, 11, 2, 95, 55, 6, 86, 116, 69, 13, 50, 0, 0, 14, 68, 92, 20, 147, 80, 2, 82, 114, 34, 87, 47, 0, 9, 10, 2, 95, 54, 6, 86, 107, 49, 87, 0, 0, 10, 2, 95, 53, 6, 81, 127, 50, 81, 0, 0, 9, 2, 95, 52, 6, 81, 116, 34, 0, 0, 15, 67, 88, 115, 0, 81, 107, 34, 79, 55, 6, 120, 97, 13, 0, 16, 2, 95, 59, 89, 47, 34, 6, 109, 97, 48, 112, 66, 49, 47, 0, 0, 17, 2, 95, 58, 70, 6, 111, 48, 13, 55, 48, 4, 112, 66, 49, 47, 0, 0, 8, 197, 8, 150, 129, 73, 32, 66, 15, 69, 44, 19, 142, 77, 64, 4, 49, 35, 50, 87, 47, 0, 9, 9, 2, 95, 57, 6, 50, 122, 50, 0, 0, 10, 2, 95, 56, 6, 10, 35, 99, 47, 0, 0, 10, 67, 21, 36, 212, 124, 34, 87, 47, 0, 12, 71, 36, 229, 5, 72, 96, 67, 20, 21, 0, 10, 17, 2, 95, 63, 81, 34, 6, 115, 79, 13, 130, 4, 120, 97, 13, 50, 0, 0, 13, 68, 92, 244, 137, 56, 82, 125, 34, 6, 109, 50, 0, 10, 2, 95, 62, 79, 34, 128, 87, 106, 0, 0, 0, 10, 2, 95, 60, 49, 55, 120, 50, 106, 0, 0, 0, 0, 0, 0, 0, 10, 68, 56, 148, 195, 32, 50, 116, 89, 0, 19, 72, 52, 146, 210, 60, 98, 67, 32, 80, 63, 116, 49, 34, 125, 81, 116, 89, 0, 0, 0, 17, 70, 80, 83, 5, 28, 83, 128, 47, 124, 55, 124, 79, 6, 124, 50, 0, 0, 0, 9, 68, 52, 16, 200, 60, 21, 0, 10, 8, 196, 76, 245, 201, 20, 66, 8, 0, 0, 0, 0, 9, 68, 48, 20, 197, 72, 21, 0, 10, 7, 196, 52, 82, 78, 20, 76, 0, 14, 69, 88, 84, 133, 36, 224, 81, 107, 34, 6, 120, 50, 0, 0, 0, 0, 9, 68, 40, 242, 78, 80, 21, 0, 10, 0, 8, 197, 52, 243, 147, 84, 224, 66, 0, 6, 195, 56, 17, 197, 20, 0, 0, 13, 4, 95, 4, 15, 20, 48, 6, 112, 50, 49, 47, 0, 0, 0, 9, 198, 24, 85, 69, 73, 35, 212, 67, 0, 8, 67, 80, 80, 200, 21, 0, 10, 17, 67, 85, 49, 128, 2, 112, 50, 47, 86, 125, 81, 6, 111, 34, 47, 0, 22, 2, 95, 91, 6, 107, 49, 109, 79, 13, 49, 55, 6, 35, 63, 106, 15, 23, 6, 119, 81, 0, 0, 13, 68, 28, 83, 210, 28, 79, 124, 111, 34, 49, 0, 9, 0, 0, 8, 66, 76, 240, 86, 125, 0, 76, 0, 8, 67, 12, 128, 84, 21, 0, 10, 16, 2, 95, 95, 4, 112, 50, 47, 106, 89, 47, 34, 6, 109, 97, 0, 0, 16, 2, 95, 94, 130, 109, 34, 49, 112, 63, 81, 55, 107, 49, 87, 0, 0, 13, 69, 12, 194, 81, 84, 80, 49, 55, 109, 49, 13, 0, 10, 69, 60, 227, 9, 56, 80, 21, 0, 10, 21, 2, 95, 93, 6, 107, 49, 109, 79, 13, 49, 55, 6, 35, 63, 106, 15, 130, 6, 118, 0, 0, 8, 67, 12, 242, 197, 21, 0, 10, 0, 17, 70, 36, 229, 5, 72, 84, 211, 109, 50, 47, 13, 34, 6, 107, 87, 0, 8, 67, 12, 243, 204, 21, 0, 10, 0, 13, 68, 93, 84, 132, 20, 82, 4, 112, 34, 70, 13, 0, 12, 68, 84, 228, 197, 72, 112, 50, 86, 106, 0, 72, 22, 4, 95, 226, 128, 148, 79, 13, 70, 6, 35, 66, 49, 13, 50, 89, 47, 34, 4, 109, 97, 0, 0, 8, 197, 16, 18, 12, 36, 80, 20, 9, 198, 9, 35, 206, 12, 130, 69, 20, 10, 69, 41, 83, 139, 36, 80, 21, 0, 10, 0, 9, 2, 95, 96, 79, 34, 114, 82, 0, 0, 0, 8, 196, 17, 84, 131, 32, 76, 8, 0, 0, 0, 11, 67, 56, 16, 200, 50, 114, 99, 0, 76, 28, 0, 0, 0, 14, 4, 95, 7, 18, 22, 79, 34, 6, 114, 82, 109, 87, 0, 0, 0, 0, 8, 197, 8, 19, 11, 60, 224, 66, 0, 0, 12, 71, 72, 240, 83, 80, 33, 69, 24, 21, 0, 10, 11, 67, 8, 148, 192, 69, 109, 87, 0, 76, 8, 10, 67, 16, 84, 192, 2, 70, 107, 87, 0, 0, 7, 196, 84, 213, 197, 28, 65, 0, 14, 69, 76, 243, 12, 20, 224, 4, 86, 111, 55, 13, 50, 0, 0, 0, 0, 0, 16, 69, 32, 16, 133, 77, 64, 105, 114, 69, 107, 87, 47, 0, 9, 72, 0, 0, 13, 4, 95, 4, 9, 1, 6, 112, 63, 55, 119, 47, 0, 25, 2, 95, 123, 79, 13, 89, 82, 6, 120, 81, 47, 13, 49, 55, 6, 35, 63, 106, 15, 23, 6, 119, 81, 0, 0, 0, 0, 11, 70, 60, 97, 140, 36, 225, 64, 21, 0, 10, 9, 66, 84, 208, 112, 63, 0, 76, 28, 0, 11, 67, 8, 148, 212, 69, 109, 87, 47, 0, 72, 0, 0, 24, 2, 95, 125, 79, 13, 89, 82, 6, 120, 81, 47, 13, 49, 55, 6, 35, 63, 106, 15, 130, 6, 118, 0, 0, 8, 2, 95, 124, 48, 120, 48, 0, 0, 0, 9, 68, 5, 4, 12, 20, 21, 0, 10, 0, 0, 0, 0, 7, 196, 73, 84, 9, 20, 20, 11, 200, 64, 85, 5, 73, 50, 76, 36, 80, 20, 0, 10, 69, 4, 48, 197, 77, 48, 21, 0, 10, 0, 0, 0, 9, 68, 12, 245, 67, 32, 21, 0, 10, 13, 68, 16, 19, 73, 80, 70, 114, 63, 6, 109, 47, 0, 0, 11, 67, 84, 225, 0, 112, 50, 47, 0, 76, 8, 0, 0, 0, 0, 8, 197, 76, 245, 207, 32, 192, 66, 15, 69, 93, 84, 132, 20, 224, 82, 4, 112, 34, 70, 13, 50, 0, 16, 69, 92, 84, 132, 20, 224, 82, 4, 107, 34, 70, 13, 50, 0, 12, 0, 0, 0, 7, 196, 72, 148, 201, 44, 65, 13, 68, 4, 35, 210, 80, 35, 69, 6, 111, 34, 47, 0, 0, 9, 197, 60, 37, 207, 32, 192, 66, 8, 0, 9, 198, 16, 84, 200, 4, 192, 128, 66, 0, 0, 0, 14, 69, 40, 19, 149, 5, 32, 57, 35, 50, 118, 114, 34, 0, 8, 197, 32, 82, 77, 5, 64, 65, 0, 17, 4, 95, 35, 51, 50, 55, 6, 124, 34, 130, 6, 120, 97, 13, 50, 0, 0, 0, 0, 14, 69, 76, 243, 12, 77, 64, 4, 86, 111, 55, 87, 47, 0, 0, 0, 0, 0, 14, 69, 84, 228, 197, 72, 208, 112, 50, 87, 106, 63, 0, 72, 0, 0, 11, 67, 92, 147, 12, 2, 82, 109, 55, 0, 9, 0, 11, 200, 52, 20, 135, 36, 224, 76, 36, 80, 20, 0, 10, 69, 76, 147, 135, 48, 80, 21, 0, 10, 0, 9, 66, 105, 80, 130, 118, 0, 76, 28, 0, 0, 0, 0, 0, 0, 0, 0, 17, 70, 36, 229, 5, 72, 225, 84, 109, 50, 47, 13, 34, 50, 107, 47, 0, 0, 0, 0, 0, 0, 12, 71, 12, 19, 67, 61, 33, 5, 72, 21, 0, 10, 14, 67, 12, 132, 128, 49, 13, 34, 109, 87, 47, 112, 87, 0, 0, 0, 8, 197, 16, 19, 129, 12, 128, 66, 0, 0, 0, 0, 0, 0, 18, 67, 85, 53, 192, 2, 112, 50, 47, 86, 125, 82, 6, 120, 47, 106, 0, 8, 0, 0, 10, 69, 64, 244, 212, 21, 32, 21, 0, 10, 0, 0, 0, 7, 196, 81, 84, 137, 56, 66, 0, 14, 69, 32, 244, 147, 4, 208, 105, 111, 106, 86, 114, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 71, 36, 195, 5, 28, 149, 9, 52, 109, 55, 124, 79, 116, 47, 6, 116, 63, 0, 0, 0, 0, 0, 8, 67, 8, 32, 192, 21, 0, 10, 0, 0, 0, 0, 0, 8, 67, 12, 144, 79, 74, 119, 0, 8, 67, 76, 131, 215, 21, 0, 10, 9, 68, 24, 246, 69, 72, 21, 0, 10, 0, 0, 0, 7, 195, 92, 145, 64, 72, 8, 0, 0, 8, 197, 76, 241, 143, 73, 64, 66, 0, 11, 70, 52, 84, 211, 4, 113, 64, 21, 0, 10, 0, 10, 67, 76, 145, 64, 86, 116, 0, 72, 9, 0, 0, 10, 69, 13, 84, 147, 61, 32, 21, 0, 10, 0, 8, 66, 92, 240, 82, 4, 125, 0, 0, 0, 0, 8, 197, 29, 32, 90, 36, 80, 20, 0, 0, 20, 73, 5, 84, 199, 21, 48, 200, 4, 213, 0, 119, 87, 79, 13, 89, 114, 63, 47, 0, 0, 12, 68, 28, 84, 212, 20, 79, 124, 87, 47, 13, 0, 0, 0, 0, 9, 67, 80, 243, 64, 47, 111, 63, 0, 19, 71, 8, 19, 132, 4, 114, 69, 72, 69, 35, 50, 70, 35, 88, 6, 116, 13, 0, 10, 67, 44, 19, 64, 4, 49, 114, 63, 0, 0, 0, 0, 16, 70, 49, 81, 84, 37, 48, 200, 55, 118, 6, 124, 47, 109, 89, 0, 0, 0, 7, 196, 25, 84, 137, 20, 20, 0, 0, 16, 70, 56, 16, 200, 16, 83, 64, 50, 35, 99, 70, 6, 124, 63, 0, 0, 0, 9, 68, 48, 241, 201, 56, 21, 0, 10, 0, 0, 0, 11, 67, 4, 196, 192, 35, 55, 87, 0, 76, 28, 0, 6, 195, 4, 196, 207, 8, 0, 6, 195, 52, 82, 78, 76, 0, 0, 0, 0, 0, 11, 70, 76, 50, 69, 56, 49, 64, 21, 0, 10, 0, 0, 0, 0, 15, 70, 76, 84, 150, 36, 49, 64, 87, 107, 34, 82, 109, 87, 0, 9, 198, 8, 192, 77, 4, 113, 64, 20, 0, 0, 0, 0, 16, 70, 36, 195, 15, 100, 19, 0, 109, 55, 111, 35, 57, 114, 55, 0, 0, 0, 9, 198, 77, 80, 138, 20, 181, 0, 65, 0, 8, 197, 20, 33, 78, 76, 240, 65, 0, 0, 0, 0, 6, 18, 66, 108, 0, 114, 0, 7, 6, 18, 67, 99, 0, 102, 0, 104, 0, 107, 0, 112, 0, 113, 0, 115, 0, 116, 0, 122, 0, 7, 6, 18, 68, 195, 164, 0, 97, 0, 7, 6, 18, 69, 195, 182, 0, 111, 0, 7, 6, 99, 104, 0, 4, 1, 117, 102, 2, 115, 3, 49, 0, 2, 111, 114, 32, 0, 2, 111, 114, 100, 0, 2, 195, 182, 114, 0, 8, 2, 18, 66, 17, 65, 0, 8, 2, 111, 0, 97, 114, 97, 2, 107, 116, 3, 49, 2, 35, 34, 35, 0, 114, 111, 3, 49, 34, 125, 0, 115, 2, 32, 3, 49, 87, 0, 115, 116, 117, 1, 97, 119, 2, 109, 3, 49, 87, 47, 118, 0, 105, 112, 2, 32, 3, 74, 109, 48, 0, 4, 8, 2, 97, 3, 89, 0, 8, 2, 105, 99, 0, 8, 2, 105, 102, 0, 8, 2, 105, 108, 0, 97, 110, 99, 101, 3, 89, 136, 87, 13, 0, 4, 3, 97, 0, 1, 117, 101, 0, 1, 117, 164, 195, 0, 8, 2, 17, 65, 0, 4, 101, 110, 1, 17, 67, 2, 32, 14, 128, 128, 132, 3, 97, 13, 50, 0, 101, 110, 1, 101, 2, 32, 0, 101, 110, 1, 164, 195, 2, 32, 0, 101, 110, 1, 188, 195, 2, 32, 0, 115, 1, 164, 195, 110, 2, 116, 3, 97, 87, 0, 4, 1, 97, 3, 99, 0, 1, 101, 114, 98, 2, 101, 110, 0, 1, 111, 0, 1, 117, 0, 7, 6, 103, 101, 0, 8, 2, 111, 114, 103, 3, 79, 2, 124, 0, 111, 8, 3, 79, 4, 124, 125, 0, 4, 1, 115, 103, 110, 117, 2, 17, 67, 21, 3, 79, 13, 0, 2, 109, 97, 99, 104, 0, 2, 109, 97, 108, 0, 2, 114, 195, 164, 116, 0, 2, 116, 114, 0, 8, 2, 21, 14, 128, 132, 130, 0, 8, 2, 105, 109, 112, 0, 8, 2, 111, 114, 14, 128, 132, 130, 0, 98, 105, 114, 103, 101, 2, 32, 14, 128, 128, 135, 3, 79, 13, 69, 109, 34, 79, 13, 0, 4, 2, 114, 109, 97, 110, 3, 79, 107, 0, 2, 115, 116, 114, 105, 103, 0, 8, 2, 109, 25, 0, 8, 2, 110, 25, 0, 8, 2, 110, 101, 114, 0, 105, 2, 12, 3, 79, 120, 0, 4, 8, 2, 98, 101, 29, 3, 79, 124, 0, 104, 8, 2, 101, 29, 0, 104, 101, 110, 3, 79, 124, 13, 50, 0, 110, 101, 114, 97, 108, 2, 105, 115, 3, 79, 124, 50, 13, 34, 35, 55, 0, 110, 101, 114, 97, 108, 3, 79, 124, 50, 107, 34, 6, 35, 55, 0, 98, 101, 110, 3, 79, 124, 69, 13, 50, 0, 4, 103, 101, 110, 3, 79, 124, 79, 13, 50, 0, 103, 101, 110, 8, 2, 21, 14, 128, 132, 133, 0, 103, 110, 3, 79, 124, 79, 50, 0, 7, 6, 105, 101, 0, 4, 1, 10, 2, 114, 32, 3, 6, 116, 0, 1, 10, 2, 114, 108, 105, 99, 104, 0, 1, 21, 2, 32, 0, 1, 21, 2, 114, 101, 29, 0, 2, 114, 115, 21, 0, 4, 110, 1, 103, 21, 2, 32, 3, 6, 116, 13, 50, 0, 110, 1, 104, 112, 2, 32, 0, 110, 1, 109, 21, 2, 32, 0, 110, 1, 112, 21, 2, 32, 0, 110, 1, 114, 101, 115, 2, 32, 0, 110, 1, 114, 101, 116, 116, 2, 32, 0, 110, 1, 114, 111, 101, 2, 32, 0, 110, 1, 114, 111, 103, 2, 32, 0, 110, 1, 114, 116, 101, 2, 32, 0, 110, 1, 114, 116, 115, 117, 100, 2, 32, 0, 110, 1, 115, 21, 2, 32, 0, 110, 1, 116, 21, 2, 32, 0, 114, 117, 110, 103, 3, 6, 116, 34, 112, 66, 0, 114, 117, 110, 103, 115, 3, 6, 116, 34, 112, 66, 87, 0, 4, 1, 21, 2, 32, 28, 17, 3, 8, 109, 13, 0, 1, 100, 117, 116, 115, 2, 32, 0, 1, 108, 97, 109, 114, 111, 102, 0, 1, 108, 105, 109, 97, 102, 0, 1, 108, 111, 102, 2, 32, 0, 1, 114, 101, 102, 2, 110, 0, 1, 114, 101, 116, 107, 97, 98, 0, 110, 1, 10, 2, 32, 3, 8, 109, 13, 50, 0, 110, 115, 1, 10, 2, 32, 3, 8, 109, 38, 13, 50, 87, 0, 4, 110, 1, 98, 10, 2, 32, 3, 8, 116, 13, 50, 0, 110, 1, 114, 10, 2, 32, 0, 1, 117, 2, 114, 32, 3, 23, 6, 116, 0, 1, 10, 2, 108, 108, 32, 3, 109, 6, 107, 0, 110, 116, 2, 32, 3, 109, 6, 107, 50, 47, 0, 110, 122, 1, 10, 2, 32, 3, 109, 6, 107, 50, 130, 0, 4, 1, 99, 110, 97, 110, 105, 102, 2, 114, 3, 109, 6, 124, 0, 1, 103, 121, 104, 2, 110, 0, 1, 107, 110, 97, 98, 2, 114, 0, 1, 108, 97, 116, 105, 2, 110, 0, 1, 108, 101, 116, 111, 104, 2, 114, 0, 1, 109, 101, 114, 112, 2, 114, 0, 1, 114, 114, 97, 2, 114, 0, 1, 114, 114, 97, 98, 2, 114, 0, 1, 110, 105, 2, 32, 3, 109, 13, 0, 110, 1, 110, 10, 2, 32, 3, 109, 13, 50, 0, 110, 1, 114, 2, 21, 3, 109, 107, 50, 0, 4, 3, 116, 0, 1, 104, 99, 115, 2, 110, 0, 104, 0, 110, 115, 116, 1, 100, 3, 116, 50, 87, 47, 0, 7, 6, 195, 159, 0, 3, 87, 0, 8, 2, 32, 3, 107, 87, 130, 107, 47, 0, 7, 6, 195, 164, 0, 2, 117, 109, 32, 24, 3, 6, 123, 0, 116, 1, 116, 2, 32, 3, 6, 123, 47, 0, 4, 2, 17, 67, 11, 3, 107, 0, 2, 17, 67, 17, 67, 0, 2, 115, 99, 104, 0, 117, 3, 122, 0, 4, 3, 123, 0, 104, 2, 12, 0, 98, 2, 116, 32, 3, 123, 48, 0, 103, 2, 116, 32, 3, 123, 49, 0, 7, 6, 195, 182, 0, 2, 32, 3, 6, 128, 0, 4, 3, 128, 0, 104, 2, 12, 0, 4, 2, 17, 67, 11, 3, 129, 0, 2, 17, 67, 17, 67, 0, 2, 115, 99, 104, 0, 7, 6, 195, 188, 0, 98, 101, 114, 8, 2, 98, 101, 21, 14, 128, 132, 132, 3, 11, 6, 126, 69, 106, 0, 98, 101, 114, 8, 2, 21, 14, 128, 132, 132, 3, 23, 4, 126, 69, 106, 0, 4, 3, 126, 0, 104, 2, 12, 0, 98, 2, 116, 32, 3, 126, 48, 0, 103, 2, 116, 32, 3, 126, 49, 0, 98, 101, 114, 8, 2, 103, 97, 110, 103, 115, 3, 126, 69, 106, 0, 4, 2, 17, 67, 11, 3, 127, 0, 2, 17, 67, 17, 67, 0, 2, 115, 99, 104, 0, 2, 120, 0, 7, 6, 97, 0, 114, 99, 104, 97, 8, 2, 105, 3, 2, 35, 34, 97, 115, 0, 116, 111, 8, 2, 109, 3, 2, 35, 47, 125, 0, 4, 98, 8, 2, 110, 111, 114, 3, 2, 35, 48, 0, 98, 8, 2, 115, 111, 0, 98, 8, 2, 115, 111, 114, 0, 98, 8, 2, 115, 116, 114, 0, 98, 8, 2, 115, 117, 114, 0, 107, 113, 117, 3, 2, 35, 49, 82, 0, 110, 8, 2, 97, 3, 2, 35, 50, 0, 110, 105, 8, 2, 115, 3, 2, 35, 50, 116, 0, 98, 98, 8, 2, 97, 3, 2, 35, 69, 0, 117, 115, 116, 114, 97, 2, 108, 3, 2, 119, 87, 47, 34, 115, 0, 112, 112, 101, 8, 2, 108, 108, 21, 3, 4, 35, 48, 107, 0, 110, 116, 104, 114, 111, 112, 111, 8, 3, 4, 35, 50, 47, 34, 125, 48, 2, 125, 0, 110, 116, 105, 8, 2, 21, 14, 128, 132, 132, 3, 4, 35, 50, 47, 109, 0, 110, 116, 105, 8, 2, 21, 14, 128, 132, 132, 3, 4, 35, 50, 47, 116, 0, 110, 105, 109, 8, 3, 4, 35, 50, 116, 63, 0, 110, 105, 109, 97, 108, 8, 3, 4, 35, 50, 116, 63, 114, 55, 0, 110, 103, 108, 111, 8, 2, 21, 3, 4, 35, 66, 79, 55, 125, 0, 4, 108, 1, 110, 97, 107, 10, 2, 32, 3, 4, 114, 55, 0, 108, 1, 110, 103, 105, 115, 10, 2, 32, 0, 1, 114, 103, 2, 109, 109, 32, 3, 6, 35, 0, 98, 8, 2, 101, 114, 21, 14, 128, 132, 130, 3, 6, 35, 48, 0, 98, 122, 117, 8, 2, 21, 14, 128, 132, 132, 3, 6, 35, 48, 130, 118, 0, 4, 99, 104, 115, 8, 2, 21, 14, 128, 132, 132, 3, 6, 35, 49, 87, 0, 99, 104, 115, 8, 2, 101, 108, 0, 4, 110, 1, 110, 105, 101, 2, 100, 101, 114, 3, 6, 35, 50, 0, 110, 8, 2, 21, 14, 128, 132, 130, 0, 110, 8, 2, 110, 18, 68, 104, 14, 128, 132, 130, 0, 110, 8, 2, 110, 97, 100, 14, 128, 132, 130, 0, 110, 116, 1, 21, 2, 32, 3, 6, 35, 50, 47, 0, 108, 108, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 6, 35, 55, 13, 34, 0, 4, 1, 21, 2, 98, 101, 108, 32, 3, 6, 114, 0, 1, 21, 2, 98, 108, 32, 0, 2, 17, 67, 111, 32, 0, 2, 114, 99, 104, 32, 0, 8, 2, 110, 97, 116, 105, 111, 14, 128, 132, 129, 0, 4, 114, 1, 108, 21, 2, 32, 3, 6, 114, 34, 0, 114, 1, 116, 21, 2, 32, 0, 114, 105, 101, 114, 2, 32, 24, 3, 6, 114, 34, 116, 106, 0, 116, 1, 21, 2, 32, 3, 6, 114, 47, 0, 116, 105, 115, 99, 104, 1, 21, 2, 32, 14, 128, 128, 134, 3, 6, 114, 47, 109, 89, 0, 110, 1, 21, 2, 32, 3, 6, 114, 50, 0, 110, 105, 101, 114, 2, 32, 24, 3, 6, 114, 50, 116, 106, 0, 4, 108, 1, 17, 65, 21, 2, 32, 3, 6, 114, 55, 0, 108, 1, 98, 2, 32, 0, 108, 1, 103, 2, 32, 0, 108, 1, 107, 2, 32, 0, 108, 1, 110, 2, 32, 0, 108, 1, 114, 2, 32, 0, 108, 1, 116, 2, 32, 0, 109, 1, 114, 101, 107, 2, 105, 107, 3, 6, 114, 63, 0, 4, 103, 101, 2, 32, 28, 17, 3, 6, 114, 88, 13, 0, 103, 101, 2, 110, 32, 28, 33, 0, 110, 99, 101, 1, 115, 2, 32, 3, 6, 136, 87, 0, 110, 99, 101, 1, 114, 102, 2, 32, 3, 6, 136, 87, 13, 0, 110, 99, 101, 110, 1, 115, 2, 32, 3, 6, 136, 87, 13, 50, 0, 1, 17, 67, 17, 67, 10, 2, 32, 3, 8, 114, 0, 4, 98, 8, 2, 17, 67, 21, 14, 128, 132, 130, 3, 11, 6, 35, 48, 0, 98, 8, 2, 17, 67, 21, 14, 128, 132, 130, 0, 98, 8, 2, 195, 164, 14, 128, 132, 130, 0, 117, 102, 8, 2, 21, 14, 128, 132, 131, 3, 11, 6, 119, 81, 0, 117, 115, 8, 2, 21, 14, 128, 132, 131, 3, 11, 6, 119, 87, 0, 105, 114, 8, 3, 21, 0, 4, 2, 17, 67, 11, 3, 35, 0, 2, 17, 67, 17, 67, 0, 2, 105, 115, 105, 101, 114, 0, 2, 115, 99, 104, 0, 2, 116, 105, 111, 110, 0, 2, 120, 0, 100, 8, 2, 106, 117, 3, 35, 47, 0, 4, 98, 8, 2, 105, 3, 35, 48, 0, 98, 8, 2, 106, 0, 98, 8, 2, 115, 101, 0, 98, 8, 2, 115, 122, 0, 98, 8, 2, 111, 114, 3, 35, 48, 23, 0, 98, 100, 8, 2, 12, 3, 35, 48, 70, 0, 4, 110, 8, 2, 100, 101, 114, 3, 35, 50, 0, 110, 8, 2, 116, 101, 110, 0, 110, 8, 2, 116, 104, 0, 110, 8, 2, 116, 119, 0, 110, 110, 8, 0, 110, 97, 116, 104, 8, 3, 35, 50, 35, 47, 0, 110, 104, 101, 105, 109, 8, 2, 17, 67, 21, 14, 128, 132, 134, 3, 35, 50, 105, 6, 120, 63, 0, 110, 103, 108, 105, 8, 2, 17, 67, 3, 35, 66, 79, 55, 116, 0, 98, 98, 8, 2, 114, 101, 118, 3, 35, 69, 0, 98, 101, 114, 114, 8, 3, 35, 69, 23, 107, 34, 0, 99, 8, 2, 101, 116, 3, 35, 130, 0, 101, 2, 17, 67, 17, 67, 3, 107, 0, 105, 110, 1, 114, 116, 3, 107, 50, 0, 4, 1, 108, 21, 2, 103, 3, 114, 0, 1, 108, 99, 115, 2, 103, 0, 1, 114, 112, 115, 2, 99, 104, 0, 1, 115, 2, 103, 0, 1, 115, 2, 109, 32, 0, 1, 115, 2, 109, 107, 101, 105, 116, 0, 2, 17, 67, 32, 0, 2, 32, 0, 2, 112, 104, 0, 8, 2, 32, 0, 97, 0, 104, 2, 12, 0, 116, 105, 115, 105, 101, 114, 101, 110, 1, 21, 2, 32, 14, 128, 128, 137, 3, 114, 47, 109, 87, 6, 116, 34, 13, 50, 0, 98, 2, 116, 32, 3, 114, 48, 0, 4, 103, 1, 106, 2, 100, 3, 114, 49, 0, 103, 1, 108, 104, 99, 115, 2, 103, 101, 0, 103, 2, 116, 32, 0, 1, 109, 2, 108, 116, 32, 3, 114, 55, 0, 98, 101, 110, 8, 2, 100, 3, 114, 69, 13, 50, 0, 101, 108, 3, 114, 107, 55, 0, 105, 2, 115, 99, 104, 3, 114, 109, 0, 3, 115, 0, 4, 117, 3, 119, 0, 117, 8, 2, 17, 67, 101, 105, 110, 97, 110, 100, 0, 117, 104, 2, 32, 0, 117, 116, 104, 101, 110, 8, 3, 119, 47, 107, 50, 0, 117, 102, 101, 110, 116, 8, 3, 119, 81, 13, 50, 47, 0, 117, 115, 8, 2, 107, 117, 3, 119, 87, 0, 4, 105, 3, 120, 0, 121, 0, 4, 105, 114, 1, 109, 2, 32, 3, 120, 106, 0, 121, 114, 1, 109, 2, 32, 0, 4, 121, 1, 112, 3, 121, 0, 121, 2, 32, 24, 0, 101, 3, 123, 0, 105, 114, 2, 32, 3, 123, 34, 0, 7, 6, 98, 0, 1, 98, 3, 0, 4, 97, 98, 121, 3, 21, 0, 105, 107, 101, 8, 0, 108, 117, 101, 8, 0, 111, 97, 114, 100, 0, 111, 111, 109, 8, 0, 4, 2, 18, 67, 3, 48, 0, 2, 32, 24, 0, 8, 111, 2, 17, 67, 0, 116, 2, 32, 24, 3, 48, 47, 0, 4, 3, 69, 0, 2, 115, 17, 65, 0, 8, 2, 18, 66, 17, 65, 0, 8, 2, 101, 17, 68, 17, 67, 0, 8, 2, 101, 98, 17, 67, 0, 8, 2, 101, 99, 17, 67, 0, 8, 2, 101, 101, 116, 0, 8, 2, 101, 110, 122, 105, 110, 0, 8, 2, 101, 114, 17, 67, 0, 8, 2, 101, 115, 101, 110, 0, 8, 2, 101, 115, 115, 0, 8, 2, 101, 115, 116, 101, 110, 0, 8, 2, 101, 117, 103, 0, 8, 2, 101, 117, 108, 0, 8, 2, 101, 117, 116, 0, 8, 2, 106, 17, 65, 0, 4, 97, 8, 2, 108, 17, 65, 3, 69, 2, 35, 0, 97, 8, 2, 108, 108, 21, 0, 105, 115, 8, 2, 104, 14, 128, 132, 131, 3, 69, 2, 109, 87, 0, 101, 111, 8, 2, 98, 3, 69, 4, 13, 125, 0, 117, 110, 100, 101, 115, 8, 3, 69, 6, 112, 50, 70, 13, 87, 0, 101, 105, 8, 3, 69, 6, 120, 0, 4, 101, 1, 110, 101, 17, 67, 10, 2, 17, 67, 21, 3, 69, 13, 0, 101, 1, 115, 103, 110, 117, 2, 17, 67, 21, 0, 101, 2, 114, 101, 105, 99, 104, 0, 101, 8, 2, 21, 14, 128, 132, 130, 0, 101, 8, 2, 105, 110, 104, 14, 128, 132, 130, 0, 101, 8, 2, 17, 67, 11, 3, 69, 107, 0, 101, 115, 116, 105, 97, 3, 69, 107, 87, 47, 116, 6, 114, 0, 97, 114, 1, 10, 2, 32, 14, 128, 128, 131, 3, 69, 114, 34, 0, 97, 114, 101, 1, 10, 2, 32, 14, 128, 128, 132, 3, 69, 114, 34, 13, 0, 97, 114, 101, 110, 1, 10, 2, 32, 14, 128, 128, 133, 3, 69, 114, 34, 13, 50, 0, 97, 114, 101, 109, 1, 10, 2, 32, 14, 128, 128, 133, 3, 69, 114, 34, 13, 63, 0, 97, 114, 101, 115, 1, 10, 2, 32, 14, 128, 128, 133, 3, 69, 114, 34, 13, 87, 0, 97, 114, 101, 114, 1, 10, 2, 32, 14, 128, 128, 133, 3, 69, 114, 34, 106, 0, 101, 105, 103, 101, 8, 2, 21, 3, 69, 120, 79, 13, 0, 8, 2, 32, 3, 69, 124, 0, 101, 116, 101, 110, 3, 69, 124, 47, 13, 50, 0, 101, 105, 103, 101, 8, 2, 32, 3, 69, 124, 89, 0, 111, 2, 115, 104, 3, 69, 125, 0, 7, 6, 99, 0, 1, 99, 3, 0, 4, 111, 97, 116, 2, 32, 3, 21, 0, 111, 119, 8, 0, 114, 101, 119, 0, 117, 112, 0, 4, 3, 49, 0, 8, 2, 18, 66, 17, 65, 0, 107, 0, 111, 109, 112, 117, 116, 101, 114, 8, 2, 21, 14, 128, 132, 128, 3, 49, 111, 63, 48, 57, 6, 118, 47, 106, 0, 111, 100, 101, 8, 3, 49, 125, 47, 0, 2, 105, 101, 3, 87, 0, 121, 98, 101, 114, 8, 3, 87, 120, 69, 106, 0, 8, 2, 32, 3, 87, 124, 0, 104, 101, 102, 2, 32, 3, 89, 107, 81, 0, 4, 1, 97, 102, 2, 101, 116, 3, 130, 0, 1, 97, 108, 112, 2, 105, 101, 0, 8, 2, 101, 108, 0, 8, 2, 101, 110, 116, 0, 101, 121, 8, 3, 130, 120, 0, 7, 6, 100, 0, 1, 100, 3, 0, 4, 101, 97, 108, 8, 3, 21, 0, 101, 115, 105, 103, 110, 0, 103, 101, 2, 32, 0, 114, 105, 118, 101, 0, 114, 117, 103, 8, 0, 4, 2, 18, 67, 3, 47, 0, 2, 32, 24, 0, 100, 116, 0, 116, 0, 4, 3, 70, 0, 1, 110, 117, 111, 115, 0, 2, 115, 17, 65, 0, 8, 2, 114, 17, 65, 0, 8, 2, 115, 99, 104, 17, 65, 0, 8, 2, 115, 104, 17, 65, 0, 4, 117, 114, 99, 104, 8, 2, 98, 3, 70, 2, 112, 34, 97, 0, 117, 114, 99, 104, 8, 2, 102, 0, 117, 114, 99, 104, 8, 2, 107, 114, 0, 117, 114, 99, 104, 8, 2, 108, 97, 0, 117, 114, 99, 104, 8, 2, 115, 99, 104, 97, 117, 0, 117, 114, 99, 104, 8, 2, 115, 116, 0, 117, 114, 99, 104, 8, 2, 115, 117, 0, 117, 114, 99, 104, 8, 2, 116, 114, 101, 0, 117, 114, 99, 104, 8, 2, 119, 0, 117, 114, 99, 104, 113, 117, 101, 8, 3, 70, 2, 112, 34, 97, 49, 82, 124, 0, 105, 118, 101, 114, 8, 3, 70, 2, 116, 82, 107, 34, 0, 4, 101, 8, 2, 105, 107, 14, 128, 132, 130, 3, 70, 2, 124, 0, 101, 8, 2, 105, 110, 115, 116, 97, 14, 128, 132, 130, 0, 105, 97, 8, 3, 70, 4, 116, 35, 0, 97, 116, 101, 110, 8, 2, 21, 14, 128, 132, 133, 3, 70, 6, 35, 47, 13, 50, 0, 111, 114, 116, 8, 2, 17, 67, 21, 14, 128, 132, 132, 3, 70, 6, 111, 34, 47, 0, 4, 117, 114, 99, 104, 8, 2, 21, 14, 128, 132, 133, 3, 70, 6, 112, 34, 97, 0, 117, 114, 99, 104, 8, 2, 119, 97, 99, 104, 14, 128, 132, 133, 0, 117, 114, 99, 104, 119, 101, 103, 8, 3, 70, 112, 34, 97, 82, 124, 49, 0, 97, 98, 101, 105, 8, 2, 14, 128, 132, 133, 3, 70, 114, 6, 69, 120, 0, 97, 114, 97, 110, 8, 2, 14, 128, 132, 133, 3, 70, 114, 34, 6, 35, 50, 0, 97, 114, 105, 110, 8, 2, 14, 128, 132, 133, 3, 70, 114, 34, 6, 109, 50, 0, 97, 114, 117, 110, 116, 101, 114, 8, 2, 14, 128, 132, 136, 3, 70, 114, 34, 6, 112, 50, 47, 13, 34, 0, 97, 114, 117, 109, 8, 2, 14, 128, 132, 133, 3, 70, 114, 34, 6, 112, 63, 0, 97, 114, 97, 117, 102, 8, 2, 14, 128, 132, 134, 3, 70, 114, 34, 6, 119, 81, 0, 97, 114, 97, 117, 115, 8, 2, 14, 128, 132, 134, 3, 70, 114, 34, 6, 119, 87, 0, 97, 114, 101, 105, 110, 8, 2, 14, 128, 132, 134, 3, 70, 114, 34, 6, 120, 50, 0, 97, 114, 195, 188, 98, 101, 114, 8, 2, 14, 128, 132, 135, 3, 70, 114, 34, 6, 126, 69, 13, 34, 0, 97, 110, 101, 98, 101, 110, 8, 2, 14, 128, 132, 135, 3, 70, 114, 50, 6, 124, 69, 13, 50, 0, 97, 118, 111, 110, 8, 2, 14, 128, 132, 133, 3, 70, 114, 81, 6, 111, 50, 0, 97, 118, 111, 114, 8, 2, 14, 128, 132, 133, 3, 70, 114, 81, 6, 125, 34, 0, 97, 102, 195, 188, 114, 8, 2, 14, 128, 132, 133, 3, 70, 114, 81, 6, 127, 34, 0, 97, 104, 101, 114, 8, 2, 14, 128, 132, 133, 3, 70, 114, 105, 6, 107, 34, 0, 97, 104, 105, 110, 8, 2, 14, 128, 132, 133, 3, 70, 114, 105, 6, 109, 50, 0, 97, 104, 105, 110, 116, 101, 114, 8, 2, 14, 128, 132, 136, 3, 70, 114, 105, 6, 109, 50, 47, 106, 0, 97, 122, 117, 8, 2, 14, 128, 132, 132, 3, 70, 114, 130, 6, 118, 0, 4, 8, 2, 32, 3, 70, 124, 0, 101, 8, 2, 105, 102, 0, 101, 109, 101, 8, 3, 70, 124, 63, 107, 0, 4, 101, 109, 111, 2, 103, 3, 70, 124, 63, 125, 0, 101, 109, 111, 2, 107, 0, 115, 2, 32, 3, 130, 0, 7, 6, 101, 0, 8, 2, 102, 102, 3, 2, 107, 0, 114, 111, 98, 8, 2, 101, 114, 3, 2, 107, 34, 125, 69, 0, 109, 112, 8, 2, 105, 114, 3, 2, 107, 63, 48, 0, 109, 112, 104, 8, 2, 21, 3, 2, 107, 63, 81, 0, 117, 114, 8, 2, 111, 112, 3, 2, 122, 0, 8, 2, 108, 101, 107, 3, 2, 124, 0, 110, 101, 8, 2, 114, 103, 3, 2, 124, 50, 107, 0, 110, 100, 111, 8, 2, 21, 3, 4, 107, 50, 70, 125, 0, 105, 1, 114, 102, 10, 2, 32, 3, 4, 120, 0, 112, 105, 8, 2, 21, 3, 4, 124, 48, 116, 0, 4, 1, 10, 2, 110, 122, 25, 3, 6, 107, 0, 1, 21, 2, 107, 116, 32, 0, 1, 21, 2, 112, 116, 32, 0, 114, 115, 116, 8, 2, 17, 67, 14, 128, 132, 132, 3, 6, 107, 34, 87, 47, 0, 116, 116, 1, 21, 2, 32, 3, 6, 107, 47, 0, 4, 110, 100, 8, 2, 17, 67, 21, 14, 128, 132, 131, 3, 6, 107, 50, 47, 0, 110, 116, 1, 21, 2, 32, 0, 110, 116, 1, 109, 21, 2, 32, 0, 110, 116, 1, 116, 97, 112, 0, 110, 116, 101, 1, 109, 21, 2, 32, 3, 6, 107, 50, 47, 13, 0, 108, 108, 2, 32, 3, 6, 107, 55, 0, 105, 1, 21, 2, 32, 3, 6, 120, 0, 4, 105, 108, 8, 2, 97, 14, 128, 132, 131, 3, 6, 120, 55, 0, 105, 108, 8, 2, 102, 14, 128, 132, 131, 0, 105, 115, 101, 110, 8, 2, 21, 14, 128, 132, 133, 3, 6, 120, 86, 13, 50, 0, 4, 1, 108, 2, 103, 32, 3, 6, 124, 0, 101, 1, 104, 2, 32, 0, 114, 2, 111, 32, 3, 6, 124, 34, 0, 101, 110, 2, 32, 3, 6, 124, 42, 0, 109, 1, 10, 2, 32, 3, 6, 124, 63, 0, 117, 109, 2, 32, 3, 6, 124, 112, 63, 0, 117, 114, 1, 21, 2, 32, 3, 6, 128, 34, 0, 117, 115, 101, 2, 32, 3, 6, 128, 86, 13, 0, 117, 115, 101, 110, 2, 32, 3, 6, 128, 86, 13, 50, 0, 114, 117, 110, 103, 1, 10, 2, 32, 3, 8, 13, 34, 112, 66, 0, 110, 104, 97, 102, 116, 1, 21, 2, 32, 3, 8, 13, 50, 105, 35, 81, 47, 0, 117, 109, 1, 21, 21, 2, 32, 3, 8, 124, 112, 63, 0, 105, 110, 8, 2, 21, 14, 128, 132, 131, 3, 11, 6, 120, 50, 0, 4, 1, 10, 2, 32, 14, 128, 128, 129, 3, 13, 0, 1, 10, 2, 108, 116, 32, 0, 1, 116, 21, 2, 32, 14, 128, 128, 129, 0, 4, 114, 1, 10, 2, 105, 103, 32, 3, 13, 34, 0, 114, 1, 10, 2, 105, 103, 115, 116, 0, 114, 1, 21, 2, 32, 14, 128, 128, 130, 0, 114, 101, 1, 10, 2, 32, 14, 128, 128, 131, 3, 13, 34, 13, 0, 114, 101, 110, 1, 10, 2, 32, 14, 128, 128, 132, 3, 13, 34, 13, 50, 0, 114, 101, 109, 1, 10, 2, 32, 14, 128, 128, 132, 3, 13, 34, 13, 63, 0, 114, 101, 115, 1, 10, 2, 32, 14, 128, 128, 132, 3, 13, 34, 13, 87, 0, 114, 101, 114, 1, 10, 2, 32, 14, 128, 128, 132, 3, 13, 34, 106, 0, 114, 105, 110, 1, 10, 2, 32, 3, 13, 34, 109, 50, 0, 4, 114, 105, 115, 99, 104, 1, 10, 2, 32, 3, 13, 34, 109, 89, 0, 114, 105, 115, 99, 104, 1, 21, 21, 0, 116, 1, 10, 2, 32, 14, 128, 128, 130, 3, 13, 47, 0, 4, 110, 1, 10, 2, 116, 117, 109, 3, 13, 50, 0, 110, 1, 21, 2, 32, 14, 128, 128, 130, 0, 4, 110, 100, 1, 10, 2, 32, 24, 14, 128, 128, 131, 3, 13, 50, 47, 0, 110, 100, 1, 114, 101, 105, 2, 32, 24, 14, 128, 128, 131, 0, 110, 116, 108, 105, 99, 104, 1, 21, 3, 13, 50, 47, 55, 2, 109, 97, 0, 4, 110, 100, 1, 10, 2, 32, 3, 13, 50, 70, 0, 110, 100, 1, 114, 101, 105, 2, 32, 0, 110, 100, 101, 1, 10, 2, 32, 14, 128, 128, 132, 3, 13, 50, 70, 13, 0, 110, 100, 101, 110, 1, 10, 2, 32, 14, 128, 128, 133, 3, 13, 50, 70, 13, 50, 0, 110, 100, 101, 109, 1, 10, 2, 32, 14, 128, 128, 133, 3, 13, 50, 70, 13, 63, 0, 110, 100, 101, 115, 1, 10, 2, 32, 14, 128, 128, 133, 3, 13, 50, 70, 13, 87, 0, 110, 100, 101, 114, 1, 10, 2, 32, 14, 128, 128, 133, 3, 13, 50, 70, 106, 0, 108, 1, 10, 2, 32, 3, 13, 55, 0, 108, 110, 100, 1, 10, 2, 32, 3, 13, 55, 50, 70, 0, 109, 1, 10, 2, 32, 24, 14, 128, 128, 130, 3, 13, 63, 0, 115, 1, 21, 2, 32, 14, 128, 128, 130, 3, 13, 87, 0, 115, 116, 1, 10, 2, 32, 14, 128, 128, 131, 3, 13, 87, 47, 0, 115, 116, 101, 1, 10, 2, 32, 14, 128, 128, 132, 3, 13, 87, 47, 13, 0, 115, 116, 101, 110, 1, 10, 2, 32, 14, 128, 128, 133, 3, 13, 87, 47, 13, 50, 0, 115, 116, 101, 109, 1, 10, 2, 32, 14, 128, 128, 133, 3, 13, 87, 47, 13, 63, 0, 115, 116, 101, 115, 1, 10, 2, 32, 14, 128, 128, 133, 3, 13, 87, 47, 13, 87, 0, 115, 116, 101, 114, 1, 10, 2, 32, 14, 128, 128, 133, 3, 13, 87, 47, 106, 0, 110, 116, 101, 114, 116, 8, 3, 21, 0, 114, 8, 2, 21, 14, 128, 132, 130, 3, 23, 2, 107, 34, 0, 114, 115, 8, 2, 116, 114, 12, 3, 23, 2, 107, 34, 89, 0, 110, 116, 8, 2, 21, 14, 128, 132, 131, 3, 23, 2, 107, 50, 47, 0, 109, 112, 8, 2, 21, 14, 128, 132, 131, 3, 23, 2, 107, 63, 48, 0, 105, 110, 2, 97, 110, 100, 3, 23, 2, 120, 50, 0, 108, 110, 1, 10, 2, 32, 24, 14, 128, 128, 129, 3, 50, 0, 114, 1, 21, 2, 17, 67, 3, 106, 0, 4, 1, 21, 2, 110, 115, 105, 3, 107, 0, 1, 21, 2, 114, 110, 17, 67, 0, 1, 21, 2, 114, 114, 0, 1, 21, 2, 114, 116, 105, 0, 1, 21, 21, 2, 107, 116, 32, 0, 1, 100, 111, 109, 2, 108, 21, 0, 1, 109, 2, 110, 116, 0, 2, 17, 67, 11, 0, 2, 17, 67, 17, 67, 0, 2, 115, 99, 104, 0, 2, 120, 0, 114, 1, 10, 2, 114, 32, 0, 4, 114, 1, 21, 2, 118, 3, 107, 34, 0, 114, 1, 100, 111, 109, 2, 110, 0, 114, 1, 112, 120, 101, 2, 116, 0, 114, 1, 119, 2, 107, 32, 0, 114, 8, 2, 17, 68, 17, 67, 0, 114, 8, 2, 98, 101, 25, 0, 114, 8, 2, 103, 105, 101, 0, 114, 103, 101, 98, 8, 2, 110, 105, 115, 3, 107, 34, 79, 6, 124, 69, 0, 4, 110, 1, 116, 2, 116, 3, 107, 50, 0, 110, 1, 117, 113, 2, 116, 17, 65, 0, 110, 116, 8, 2, 101, 114, 3, 107, 50, 47, 0, 110, 116, 101, 110, 8, 3, 107, 50, 47, 13, 50, 0, 109, 115, 1, 114, 98, 3, 107, 63, 87, 0, 99, 104, 111, 3, 107, 97, 125, 0, 1, 10, 2, 17, 66, 17, 66, 32, 3, 108, 0, 110, 1, 10, 2, 21, 3, 108, 50, 0, 108, 1, 10, 2, 21, 3, 108, 55, 0, 4, 105, 3, 120, 0, 105, 1, 108, 114, 2, 32, 0, 105, 104, 2, 32, 0, 121, 0, 105, 110, 101, 8, 2, 114, 21, 3, 120, 50, 13, 0, 105, 110, 105, 103, 8, 3, 120, 50, 109, 79, 0, 105, 114, 1, 109, 2, 32, 3, 120, 106, 0, 4, 117, 3, 122, 0, 117, 1, 104, 2, 115, 101, 12, 12, 0, 117, 1, 108, 104, 99, 115, 2, 115, 0, 4, 3, 124, 0, 1, 108, 108, 2, 108, 0, 1, 114, 107, 2, 105, 101, 114, 0, 1, 115, 2, 108, 105, 103, 0, 2, 103, 116, 32, 12, 0, 2, 112, 104, 0, 8, 2, 32, 0, 101, 0, 104, 2, 12, 0, 121, 2, 32, 0, 4, 114, 2, 100, 32, 3, 124, 34, 0, 114, 2, 100, 105, 103, 0, 98, 2, 116, 32, 3, 124, 48, 0, 112, 105, 8, 2, 115, 107, 3, 124, 48, 109, 0, 103, 2, 116, 32, 3, 124, 49, 0, 110, 1, 21, 2, 105, 3, 124, 50, 0, 110, 101, 114, 103, 105, 101, 8, 3, 124, 50, 107, 34, 79, 6, 116, 0, 108, 101, 107, 116, 114, 111, 8, 2, 21, 14, 128, 132, 135, 3, 124, 55, 6, 107, 49, 47, 34, 125, 0, 108, 101, 110, 8, 3, 124, 55, 107, 50, 0, 115, 101, 110, 1, 21, 2, 32, 3, 124, 86, 13, 50, 0, 7, 6, 102, 0, 1, 102, 3, 0, 114, 101, 101, 8, 3, 21, 0, 4, 3, 81, 0, 8, 2, 18, 66, 17, 65, 0, 8, 2, 106, 111, 114, 100, 0, 97, 107, 115, 8, 2, 105, 3, 81, 2, 35, 49, 86, 0, 101, 117, 100, 97, 108, 8, 3, 81, 2, 122, 70, 114, 55, 0, 97, 114, 98, 8, 2, 17, 67, 21, 14, 128, 132, 132, 3, 81, 6, 35, 34, 48, 0, 97, 114, 98, 8, 2, 108, 21, 14, 128, 132, 132, 3, 81, 6, 35, 34, 69, 0, 101, 114, 116, 105, 103, 8, 2, 17, 67, 21, 14, 128, 132, 134, 3, 81, 6, 107, 34, 47, 37, 97, 0, 101, 115, 116, 8, 2, 21, 14, 128, 132, 132, 3, 81, 6, 107, 87, 47, 0, 101, 105, 110, 8, 2, 21, 14, 128, 132, 132, 3, 81, 6, 120, 50, 0, 114, 111, 104, 8, 2, 21, 14, 128, 132, 132, 3, 81, 34, 6, 125, 0, 114, 101, 118, 8, 3, 81, 34, 124, 81, 0, 114, 111, 104, 108, 111, 99, 107, 8, 3, 81, 34, 125, 55, 6, 111, 49, 0, 97, 114, 99, 8, 3, 81, 35, 34, 87, 0, 108, 117, 103, 8, 3, 81, 55, 6, 118, 79, 0, 117, 110, 103, 8, 2, 17, 65, 3, 81, 112, 66, 79, 0, 101, 117, 101, 114, 8, 2, 21, 3, 81, 122, 13, 34, 0, 111, 116, 111, 3, 81, 125, 47, 125, 0, 8, 2, 32, 3, 107, 81, 0, 7, 6, 103, 0, 2, 103, 3, 0, 4, 104, 116, 1, 21, 2, 32, 3, 21, 0, 114, 101, 101, 110, 0, 117, 105, 100, 101, 0, 4, 2, 18, 67, 3, 49, 0, 2, 32, 24, 0, 117, 101, 2, 32, 0, 4, 100, 2, 32, 24, 3, 49, 47, 0, 116, 1, 105, 101, 2, 32, 0, 116, 101, 116, 2, 32, 3, 49, 47, 13, 47, 0, 116, 101, 115, 116, 3, 49, 47, 13, 87, 47, 0, 4, 3, 79, 0, 2, 115, 17, 65, 0, 8, 2, 18, 66, 17, 65, 0, 8, 2, 101, 17, 68, 17, 67, 0, 104, 8, 2, 17, 65, 0, 195, 188, 116, 101, 8, 2, 21, 14, 128, 132, 132, 3, 79, 6, 126, 47, 13, 0, 8, 2, 110, 17, 65, 3, 79, 14, 0, 110, 1, 17, 66, 2, 17, 65, 3, 79, 14, 50, 0, 114, 97, 112, 104, 2, 32, 3, 79, 34, 6, 114, 81, 0, 114, 97, 112, 104, 3, 79, 34, 115, 81, 0, 8, 2, 32, 3, 79, 124, 0, 1, 97, 115, 115, 97, 109, 3, 88, 0, 116, 1, 105, 2, 32, 3, 97, 47, 0, 7, 6, 104, 0, 1, 104, 3, 0, 105, 103, 104, 8, 3, 21, 0, 4, 3, 105, 0, 1, 104, 99, 0, 105, 101, 114, 8, 2, 21, 3, 105, 2, 116, 34, 0, 101, 114, 111, 8, 3, 105, 2, 124, 34, 125, 0, 4, 105, 110, 116, 101, 114, 8, 2, 21, 3, 105, 4, 109, 50, 47, 106, 0, 105, 110, 116, 101, 114, 8, 2, 21, 14, 128, 132, 134, 0, 111, 109, 111, 103, 101, 110, 3, 105, 4, 125, 63, 125, 79, 124, 50, 0, 97, 110, 100, 8, 2, 17, 67, 14, 128, 132, 132, 3, 105, 6, 35, 50, 47, 0, 101, 114, 122, 8, 2, 101, 114, 21, 14, 128, 132, 132, 3, 105, 6, 107, 34, 130, 0, 105, 110, 103, 101, 8, 2, 21, 14, 128, 132, 133, 3, 105, 6, 109, 50, 79, 13, 0, 105, 108, 102, 8, 2, 21, 14, 128, 132, 132, 3, 105, 6, 109, 55, 81, 0, 105, 108, 102, 101, 8, 2, 21, 14, 128, 132, 133, 3, 105, 6, 109, 55, 81, 13, 0, 105, 108, 102, 115, 8, 2, 21, 14, 128, 132, 133, 3, 105, 6, 109, 55, 81, 87, 0, 97, 117, 112, 116, 8, 2, 21, 21, 14, 128, 132, 133, 3, 105, 6, 119, 48, 47, 0, 97, 117, 115, 8, 2, 21, 14, 128, 132, 132, 3, 105, 6, 119, 87, 0, 111, 99, 104, 8, 2, 21, 14, 128, 132, 132, 3, 105, 6, 125, 99, 0, 121, 112, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 105, 6, 126, 48, 106, 0, 97, 110, 100, 8, 2, 108, 117, 110, 103, 3, 105, 35, 50, 70, 0, 101, 114, 97, 110, 8, 2, 14, 128, 132, 133, 3, 105, 107, 34, 6, 35, 50, 0, 101, 114, 97, 98, 8, 2, 14, 128, 132, 133, 3, 105, 107, 34, 6, 35, 69, 0, 101, 114, 98, 101, 105, 8, 2, 14, 128, 132, 134, 3, 105, 107, 34, 6, 69, 120, 0, 101, 114, 117, 110, 116, 101, 114, 8, 2, 14, 128, 132, 136, 3, 105, 107, 34, 6, 112, 50, 47, 106, 0, 101, 114, 117, 109, 8, 2, 14, 128, 132, 133, 3, 105, 107, 34, 6, 112, 63, 0, 101, 114, 97, 117, 102, 8, 2, 14, 128, 132, 134, 3, 105, 107, 34, 6, 119, 81, 0, 101, 114, 97, 117, 115, 8, 2, 14, 128, 132, 134, 3, 105, 107, 34, 6, 119, 87, 0, 101, 114, 101, 105, 110, 8, 2, 14, 128, 132, 134, 3, 105, 107, 34, 6, 120, 50, 0, 101, 114, 195, 188, 98, 101, 114, 8, 2, 14, 128, 132, 135, 3, 105, 107, 34, 6, 126, 69, 106, 0, 101, 114, 118, 111, 114, 8, 2, 14, 128, 132, 134, 3, 105, 107, 34, 81, 6, 125, 34, 0, 105, 110, 97, 110, 8, 2, 14, 128, 132, 133, 3, 105, 109, 50, 6, 35, 50, 0, 105, 110, 97, 98, 8, 2, 14, 128, 132, 133, 3, 105, 109, 50, 6, 35, 69, 0, 105, 110, 117, 110, 116, 101, 114, 8, 2, 14, 128, 132, 136, 3, 105, 109, 50, 6, 112, 50, 47, 106, 0, 105, 110, 117, 109, 8, 2, 14, 128, 132, 133, 3, 105, 109, 50, 6, 112, 63, 0, 105, 110, 97, 117, 102, 8, 2, 14, 128, 132, 134, 3, 105, 109, 50, 6, 119, 81, 0, 105, 110, 97, 117, 115, 8, 2, 14, 128, 132, 134, 3, 105, 109, 50, 6, 119, 87, 0, 105, 110, 101, 105, 110, 8, 2, 14, 128, 132, 134, 3, 105, 109, 50, 6, 120, 50, 0, 105, 110, 195, 188, 98, 101, 114, 8, 2, 14, 128, 132, 135, 3, 105, 109, 50, 6, 126, 69, 106, 0, 105, 110, 103, 101, 103, 101, 110, 8, 3, 105, 109, 50, 79, 6, 124, 79, 13, 50, 0, 105, 110, 119, 101, 103, 8, 2, 14, 128, 132, 134, 3, 105, 109, 50, 82, 6, 124, 79, 0, 105, 110, 122, 117, 8, 2, 14, 128, 132, 133, 3, 105, 109, 50, 130, 6, 118, 0, 8, 2, 32, 3, 105, 114, 0, 111, 99, 104, 3, 105, 125, 99, 0, 7, 6, 105, 0, 8, 2, 108, 108, 117, 3, 2, 109, 0, 110, 8, 2, 107, 3, 2, 109, 50, 0, 2, 100, 101, 101, 3, 2, 116, 0, 108, 108, 101, 103, 8, 3, 4, 109, 55, 124, 79, 0, 116, 1, 21, 2, 32, 24, 3, 6, 109, 47, 0, 115, 2, 109, 117, 115, 32, 3, 6, 109, 87, 0, 115, 116, 1, 21, 2, 32, 3, 6, 109, 87, 47, 0, 4, 1, 21, 2, 98, 101, 108, 32, 3, 6, 116, 0, 1, 21, 2, 98, 108, 32, 0, 1, 114, 2, 110, 97, 32, 0, 1, 115, 21, 2, 118, 32, 0, 1, 116, 21, 2, 118, 32, 0, 2, 17, 67, 111, 32, 0, 2, 100, 32, 0, 2, 108, 32, 0, 116, 101, 1, 21, 2, 32, 3, 6, 116, 47, 13, 0, 4, 107, 1, 21, 2, 101, 108, 32, 3, 6, 116, 49, 0, 107, 1, 114, 98, 2, 32, 0, 107, 1, 115, 2, 32, 0, 107, 1, 116, 105, 108, 111, 112, 0, 4, 110, 1, 21, 2, 111, 32, 3, 6, 116, 50, 0, 110, 1, 108, 2, 32, 0, 110, 1, 109, 2, 32, 0, 110, 1, 115, 2, 32, 0, 110, 1, 122, 2, 32, 0, 115, 99, 104, 1, 10, 2, 32, 3, 8, 109, 89, 0, 4, 1, 17, 67, 17, 67, 10, 2, 32, 3, 8, 116, 0, 2, 101, 114, 105, 110, 0, 107, 1, 116, 21, 2, 32, 3, 8, 116, 49, 0, 109, 1, 10, 2, 111, 32, 3, 8, 116, 63, 0, 117, 109, 1, 10, 2, 32, 3, 8, 116, 112, 63, 0, 103, 104, 2, 25, 3, 21, 0, 111, 110, 1, 103, 2, 32, 3, 37, 6, 125, 50, 0, 111, 110, 1, 21, 2, 32, 3, 57, 6, 125, 50, 0, 4, 1, 21, 2, 97, 116, 32, 3, 109, 0, 1, 21, 2, 110, 103, 0, 1, 107, 2, 108, 32, 0, 2, 17, 67, 11, 0, 2, 17, 67, 17, 67, 0, 2, 115, 99, 104, 0, 2, 120, 0, 8, 2, 109, 97, 103, 0, 107, 1, 114, 21, 2, 32, 3, 109, 49, 0, 110, 116, 101, 114, 8, 3, 109, 50, 47, 13, 34, 0, 115, 1, 21, 2, 32, 3, 109, 87, 0, 4, 111, 3, 109, 125, 0, 111, 1, 21, 2, 110, 0, 103, 1, 21, 2, 12, 3, 109, 132, 0, 4, 3, 116, 0, 2, 112, 104, 0, 8, 2, 32, 0, 104, 2, 12, 0, 2, 105, 3, 116, 11, 0, 116, 195, 164, 116, 1, 21, 2, 32, 14, 128, 128, 132, 3, 116, 47, 6, 123, 47, 0, 98, 2, 116, 32, 3, 116, 48, 0, 107, 2, 111, 32, 3, 116, 49, 0, 110, 1, 10, 2, 32, 3, 117, 50, 0, 7, 6, 106, 0, 3, 57, 0, 8, 2, 32, 3, 57, 111, 47, 0, 7, 6, 107, 0, 1, 107, 3, 0, 4, 3, 49, 0, 8, 2, 18, 66, 17, 65, 0, 8, 2, 104, 97, 0, 8, 2, 110, 17, 65, 0, 97, 2, 114, 116, 111, 102, 102, 3, 49, 2, 35, 0, 4, 111, 8, 2, 109, 112, 3, 49, 2, 111, 0, 111, 8, 2, 110, 21, 0, 111, 108, 108, 101, 103, 3, 49, 2, 111, 55, 124, 79, 0, 111, 109, 109, 101, 8, 2, 17, 67, 21, 3, 49, 2, 111, 63, 107, 0, 4, 111, 8, 2, 109, 112, 111, 115, 116, 3, 49, 111, 0, 111, 8, 2, 110, 116, 101, 114, 0, 8, 2, 32, 3, 49, 114, 0, 111, 2, 101, 21, 3, 49, 125, 0, 7, 6, 108, 0, 1, 108, 3, 0, 101, 98, 8, 2, 17, 67, 21, 21, 14, 128, 132, 131, 3, 6, 55, 124, 48, 0, 97, 100, 121, 3, 21, 0, 3, 55, 0, 97, 110, 100, 8, 2, 17, 67, 21, 14, 128, 132, 132, 3, 55, 6, 35, 50, 47, 0, 97, 110, 100, 101, 115, 8, 2, 21, 14, 128, 132, 134, 3, 55, 6, 35, 50, 70, 13, 87, 0, 4, 97, 110, 103, 8, 2, 17, 67, 21, 14, 128, 132, 132, 3, 55, 6, 35, 66, 0, 97, 110, 103, 8, 2, 116, 21, 0, 97, 110, 103, 115, 97, 109, 3, 55, 6, 35, 66, 86, 114, 63, 0, 101, 114, 110, 8, 2, 21, 21, 14, 128, 132, 132, 3, 55, 6, 107, 34, 50, 0, 117, 102, 116, 8, 2, 17, 67, 14, 128, 132, 132, 3, 55, 6, 112, 81, 47, 0, 101, 105, 116, 8, 2, 21, 14, 128, 132, 132, 3, 55, 6, 120, 47, 0, 101, 104, 114, 8, 2, 17, 67, 21, 14, 128, 132, 132, 3, 55, 6, 124, 34, 0, 111, 1, 21, 2, 103, 105, 115, 99, 104, 3, 55, 6, 125, 0, 101, 120, 105, 8, 2, 21, 3, 55, 107, 49, 87, 116, 0, 101, 98, 8, 2, 17, 67, 3, 55, 124, 48, 0, 101, 98, 101, 110, 8, 2, 100, 105, 103, 3, 55, 124, 69, 6, 107, 50, 0, 8, 2, 32, 3, 107, 55, 0, 105, 99, 104, 1, 10, 2, 32, 14, 128, 128, 132, 3, 137, 109, 97, 0, 105, 99, 104, 117, 110, 103, 1, 10, 2, 32, 14, 128, 128, 135, 3, 137, 109, 97, 2, 112, 66, 0, 105, 99, 104, 101, 1, 10, 2, 32, 14, 128, 128, 133, 3, 137, 109, 97, 13, 0, 105, 99, 104, 101, 114, 101, 1, 10, 2, 32, 14, 128, 128, 135, 3, 137, 109, 97, 13, 34, 13, 0, 105, 99, 104, 101, 114, 101, 110, 1, 10, 2, 32, 14, 128, 128, 136, 3, 137, 109, 97, 13, 34, 13, 50, 0, 105, 99, 104, 101, 114, 101, 109, 1, 10, 2, 32, 14, 128, 128, 136, 3, 137, 109, 97, 13, 34, 13, 63, 0, 105, 99, 104, 101, 114, 101, 115, 1, 10, 2, 32, 14, 128, 128, 136, 3, 137, 109, 97, 13, 34, 13, 87, 0, 105, 99, 104, 101, 114, 101, 114, 1, 10, 2, 32, 14, 128, 128, 136, 3, 137, 109, 97, 13, 34, 13, 106, 0, 105, 99, 104, 101, 110, 1, 10, 2, 32, 14, 128, 128, 134, 3, 137, 109, 97, 13, 50, 0, 105, 99, 104, 101, 109, 1, 10, 2, 32, 14, 128, 128, 134, 3, 137, 109, 97, 13, 63, 0, 105, 99, 104, 101, 115, 1, 10, 2, 32, 14, 128, 128, 134, 3, 137, 109, 97, 13, 87, 0, 105, 99, 104, 107, 101, 105, 116, 1, 10, 2, 32, 14, 128, 128, 136, 3, 137, 109, 97, 49, 120, 47, 0, 105, 99, 104, 115, 116, 101, 1, 10, 2, 32, 14, 128, 128, 135, 3, 137, 109, 97, 87, 47, 13, 0, 105, 99, 104, 115, 116, 101, 114, 1, 10, 2, 32, 14, 128, 128, 136, 3, 137, 109, 97, 87, 47, 13, 34, 0, 105, 99, 104, 115, 116, 101, 110, 1, 10, 2, 32, 14, 128, 128, 136, 3, 137, 109, 97, 87, 47, 13, 50, 0, 105, 99, 104, 115, 116, 101, 109, 1, 10, 2, 32, 14, 128, 128, 136, 3, 137, 109, 97, 87, 47, 13, 63, 0, 105, 99, 104, 115, 116, 101, 115, 1, 10, 2, 32, 14, 128, 128, 136, 3, 137, 109, 97, 87, 47, 13, 87, 0, 105, 99, 104, 101, 114, 1, 10, 2, 32, 14, 128, 128, 134, 3, 137, 109, 97, 106, 0, 7, 6, 109, 0, 1, 109, 3, 0, 4, 105, 99, 114, 111, 8, 3, 21, 0, 115, 8, 0, 4, 3, 63, 0, 8, 2, 110, 101, 109, 0, 111, 8, 2, 114, 98, 3, 63, 2, 111, 0, 117, 115, 105, 107, 3, 63, 2, 118, 86, 116, 49, 0, 4, 101, 116, 8, 2, 97, 108, 108, 3, 63, 2, 124, 47, 0, 101, 116, 104, 8, 0, 101, 110, 97, 103, 8, 3, 63, 2, 124, 50, 114, 88, 0, 105, 107, 114, 111, 8, 2, 21, 14, 128, 132, 133, 3, 63, 4, 116, 49, 34, 125, 0, 101, 116, 114, 111, 8, 2, 21, 14, 128, 132, 133, 3, 63, 4, 124, 47, 34, 125, 0, 111, 110, 111, 8, 2, 21, 3, 63, 4, 125, 50, 125, 0, 101, 195, 159, 8, 2, 21, 14, 128, 132, 131, 3, 63, 6, 107, 87, 0, 105, 116, 8, 2, 14, 128, 132, 131, 3, 63, 6, 109, 47, 0, 105, 101, 116, 8, 2, 17, 67, 21, 14, 128, 132, 132, 3, 63, 6, 116, 47, 0, 101, 116, 101, 114, 3, 63, 6, 124, 47, 106, 0, 111, 116, 111, 114, 8, 3, 63, 6, 125, 47, 125, 34, 0, 97, 110, 99, 104, 8, 3, 63, 35, 50, 97, 0, 97, 110, 97, 103, 101, 114, 3, 63, 35, 50, 107, 73, 106, 34, 0, 105, 116, 116, 3, 63, 109, 47, 0, 105, 116, 116, 2, 101, 105, 108, 3, 63, 109, 47, 47, 0, 97, 114, 105, 110, 101, 3, 63, 114, 34, 6, 116, 50, 13, 0, 8, 2, 32, 3, 107, 63, 0, 7, 6, 110, 0, 1, 110, 3, 0, 4, 99, 101, 2, 32, 3, 21, 0, 99, 101, 115, 2, 32, 0, 101, 115, 115, 1, 10, 2, 32, 24, 0, 101, 119, 115, 0, 3, 50, 0, 4, 111, 114, 100, 2, 18, 69, 115, 116, 3, 50, 2, 111, 34, 47, 0, 111, 114, 100, 2, 119, 101, 115, 116, 0, 97, 8, 2, 116, 195, 188, 114, 3, 50, 2, 114, 0, 101, 98, 101, 110, 101, 105, 110, 97, 2, 110, 100, 3, 50, 4, 124, 69, 13, 50, 23, 120, 50, 6, 35, 0, 101, 98, 101, 110, 8, 2, 21, 14, 128, 132, 133, 3, 50, 6, 124, 69, 13, 50, 0, 107, 2, 17, 65, 3, 50, 49, 0, 103, 1, 111, 2, 101, 3, 50, 79, 0, 97, 116, 117, 114, 8, 2, 17, 67, 21, 14, 128, 132, 133, 3, 50, 114, 47, 6, 118, 34, 0, 105, 101, 100, 101, 114, 3, 50, 116, 70, 106, 0, 4, 101, 8, 2, 98, 3, 50, 124, 0, 101, 8, 2, 103, 0, 4, 101, 103, 108, 105, 103, 3, 50, 124, 79, 55, 116, 88, 0, 101, 103, 108, 105, 103, 101, 0, 103, 3, 66, 0, 4, 107, 3, 66, 49, 0, 107, 1, 117, 102, 0, 4, 103, 1, 111, 2, 17, 65, 3, 66, 79, 0, 103, 1, 117, 2, 105, 0, 103, 2, 114, 0, 8, 2, 32, 3, 107, 50, 0, 7, 6, 111, 0, 98, 8, 2, 106, 101, 107, 3, 2, 111, 48, 0, 110, 1, 114, 116, 105, 122, 3, 6, 39, 50, 0, 114, 116, 115, 8, 2, 21, 14, 128, 132, 132, 3, 6, 111, 34, 130, 0, 4, 1, 17, 65, 21, 2, 110, 32, 3, 6, 125, 0, 1, 21, 2, 103, 32, 0, 1, 21, 2, 103, 105, 110, 32, 0, 2, 17, 67, 111, 32, 0, 2, 108, 32, 0, 2, 109, 32, 0, 114, 101, 110, 1, 10, 2, 32, 3, 6, 125, 34, 13, 50, 0, 98, 115, 116, 8, 2, 114, 101, 14, 128, 132, 132, 3, 6, 125, 48, 87, 47, 0, 110, 101, 2, 32, 3, 6, 125, 50, 13, 0, 110, 101, 110, 2, 32, 3, 6, 125, 50, 13, 50, 0, 115, 111, 2, 32, 3, 6, 125, 86, 125, 0, 115, 116, 101, 114, 8, 3, 6, 125, 87, 47, 13, 34, 0, 1, 17, 67, 17, 67, 10, 2, 32, 3, 8, 125, 0, 114, 1, 116, 10, 2, 32, 3, 8, 125, 34, 0, 98, 101, 114, 8, 2, 21, 14, 128, 132, 132, 3, 23, 4, 125, 69, 106, 0, 101, 110, 1, 21, 2, 32, 14, 128, 128, 129, 3, 50, 0, 4, 2, 17, 67, 11, 3, 111, 0, 2, 17, 67, 17, 67, 0, 2, 115, 99, 104, 0, 2, 120, 0, 114, 99, 104, 101, 115, 3, 111, 34, 49, 107, 87, 0, 4, 111, 1, 21, 2, 32, 3, 118, 0, 111, 1, 114, 2, 109, 0, 111, 1, 122, 2, 109, 0, 117, 0, 121, 2, 25, 3, 122, 0, 4, 3, 125, 0, 1, 116, 115, 2, 115, 115, 0, 2, 108, 111, 32, 0, 2, 108, 115, 97, 109, 0, 2, 112, 104, 0, 8, 2, 32, 0, 8, 110, 2, 101, 0, 104, 2, 12, 0, 111, 0, 101, 2, 32, 3, 125, 13, 0, 98, 2, 116, 32, 3, 125, 48, 0, 103, 2, 116, 32, 3, 125, 49, 0, 98, 101, 114, 8, 2, 101, 29, 3, 125, 69, 13, 34, 0, 98, 101, 114, 8, 2, 115, 116, 101, 3, 125, 69, 106, 0, 103, 101, 110, 1, 116, 2, 32, 3, 125, 79, 6, 124, 50, 0, 101, 3, 128, 0, 101, 2, 17, 67, 17, 67, 3, 129, 0, 7, 6, 112, 0, 1, 112, 3, 0, 114, 111, 8, 2, 21, 3, 2, 48, 34, 125, 0, 111, 111, 108, 3, 21, 0, 4, 3, 48, 0, 8, 2, 18, 66, 17, 65, 0, 8, 2, 110, 101, 117, 0, 8, 2, 115, 17, 65, 0, 8, 2, 116, 111, 108, 0, 97, 114, 116, 101, 105, 3, 48, 2, 35, 34, 47, 120, 0, 97, 107, 101, 2, 116, 3, 48, 2, 35, 49, 124, 0, 101, 114, 102, 101, 8, 2, 107, 3, 48, 2, 107, 34, 81, 107, 0, 101, 114, 115, 111, 110, 3, 48, 2, 107, 34, 86, 125, 50, 0, 117, 8, 2, 101, 3, 48, 2, 118, 0, 4, 111, 2, 101, 109, 3, 48, 2, 125, 0, 111, 2, 101, 116, 0, 111, 8, 2, 108, 105, 116, 0, 97, 114, 97, 8, 2, 21, 3, 48, 4, 35, 34, 35, 0, 101, 114, 105, 111, 8, 3, 48, 4, 124, 34, 109, 125, 0, 101, 114, 105, 8, 3, 48, 4, 124, 34, 116, 0, 101, 114, 105, 112, 104, 101, 8, 3, 48, 4, 124, 34, 116, 81, 124, 0, 111, 108, 121, 8, 2, 21, 14, 128, 132, 132, 3, 48, 4, 125, 55, 126, 0, 111, 108, 105, 107, 8, 3, 48, 6, 125, 55, 116, 49, 0, 114, 111, 98, 108, 101, 109, 3, 48, 34, 2, 125, 69, 55, 124, 63, 0, 114, 101, 195, 159, 8, 2, 21, 14, 128, 132, 132, 3, 48, 34, 6, 107, 87, 0, 114, 105, 110, 122, 105, 112, 105, 101, 110, 8, 2, 21, 14, 128, 132, 137, 3, 48, 34, 109, 50, 130, 6, 116, 48, 109, 13, 0, 114, 105, 109, 195, 164, 114, 8, 2, 14, 128, 132, 134, 3, 48, 34, 116, 63, 6, 123, 34, 0, 114, 105, 118, 97, 116, 8, 2, 21, 14, 128, 132, 134, 3, 48, 34, 116, 82, 6, 114, 47, 0, 114, 111, 98, 101, 8, 3, 48, 34, 125, 69, 13, 0, 97, 115, 115, 97, 103, 105, 101, 3, 48, 35, 87, 35, 88, 6, 116, 0, 115, 121, 99, 104, 111, 8, 2, 21, 14, 128, 132, 134, 3, 48, 87, 4, 126, 97, 125, 0, 115, 121, 99, 104, 111, 8, 2, 116, 105, 3, 48, 87, 126, 97, 6, 125, 0, 101, 114, 115, 111, 110, 101, 110, 8, 2, 21, 14, 128, 132, 136, 3, 48, 107, 34, 86, 6, 125, 50, 13, 50, 0, 111, 119, 101, 114, 3, 48, 119, 13, 34, 0, 8, 2, 32, 3, 48, 124, 0, 111, 108, 121, 103, 111, 110, 8, 2, 21, 14, 128, 132, 135, 3, 48, 125, 55, 126, 79, 6, 125, 50, 0, 111, 101, 115, 105, 101, 3, 48, 125, 124, 86, 6, 116, 0, 4, 104, 3, 81, 0, 104, 8, 2, 17, 65, 0, 104, 8, 2, 18, 66, 17, 65, 0, 104, 111, 116, 111, 8, 3, 81, 4, 125, 47, 125, 0, 104, 105, 108, 105, 101, 3, 81, 6, 116, 55, 116, 0, 104, 116, 104, 8, 2, 17, 65, 3, 81, 47, 0, 4, 102, 8, 2, 17, 65, 3, 131, 0, 102, 8, 2, 18, 66, 17, 65, 0, 7, 6, 113, 0, 117, 101, 1, 21, 2, 32, 3, 8, 49, 0, 117, 101, 110, 1, 21, 2, 32, 3, 8, 49, 13, 50, 0, 3, 49, 0, 117, 3, 49, 82, 0, 8, 2, 32, 3, 49, 118, 0, 7, 6, 114, 0, 2, 114, 3, 0, 4, 3, 34, 0, 1, 98, 0, 104, 8, 2, 17, 65, 0, 101, 118, 101, 114, 115, 3, 34, 2, 124, 82, 107, 34, 87, 0, 101, 115, 115, 111, 117, 114, 99, 3, 34, 107, 87, 6, 112, 34, 87, 0, 97, 110, 103, 105, 101, 114, 3, 34, 114, 66, 88, 6, 116, 34, 0, 101, 8, 2, 100, 3, 34, 124, 0, 8, 2, 32, 3, 107, 34, 0, 7, 6, 115, 0, 4, 97, 102, 101, 8, 3, 21, 0, 104, 111, 112, 0, 107, 121, 8, 0, 112, 101, 101, 100, 0, 116, 114, 101, 101, 116, 8, 0, 116, 121, 108, 101, 0, 121, 110, 116, 104, 101, 115, 105, 0, 4, 1, 17, 65, 2, 32, 3, 86, 0, 2, 17, 65, 0, 2, 32, 0, 101, 114, 118, 105, 99, 101, 2, 32, 14, 128, 128, 135, 3, 86, 2, 107, 34, 82, 116, 87, 0, 111, 108, 100, 97, 116, 3, 86, 2, 111, 55, 70, 114, 47, 0, 4, 195, 188, 100, 2, 18, 69, 115, 116, 3, 86, 2, 126, 47, 0, 195, 188, 100, 2, 119, 101, 115, 116, 0, 121, 115, 116, 101, 109, 3, 86, 2, 127, 87, 47, 124, 63, 0, 101, 99, 104, 115, 8, 2, 14, 128, 132, 133, 3, 86, 6, 107, 49, 87, 0, 101, 108, 98, 115, 116, 8, 2, 21, 21, 14, 128, 132, 134, 3, 86, 6, 107, 55, 48, 87, 47, 0, 101, 107, 117, 2, 110, 100, 101, 110, 3, 86, 124, 49, 6, 112, 0, 4, 3, 87, 0, 1, 17, 65, 2, 32, 24, 0, 1, 107, 2, 105, 0, 1, 112, 2, 97, 0, 1, 112, 2, 105, 0, 1, 116, 2, 105, 0, 2, 32, 24, 14, 128, 128, 129, 0, 2, 115, 121, 115, 116, 101, 109, 0, 8, 2, 99, 17, 65, 0, 8, 2, 99, 114, 0, 8, 2, 107, 17, 65, 0, 8, 2, 107, 18, 66, 17, 65, 0, 8, 2, 108, 17, 65, 0, 8, 2, 109, 17, 65, 0, 8, 2, 110, 17, 65, 0, 8, 2, 112, 104, 17, 65, 0, 8, 2, 112, 108, 101, 110, 100, 0, 8, 2, 113, 117, 17, 65, 0, 8, 2, 118, 101, 0, 8, 2, 119, 17, 65, 0, 8, 2, 122, 17, 65, 0, 115, 0, 115, 1, 117, 97, 116, 115, 0, 111, 2, 114, 116, 32, 3, 87, 23, 111, 0, 4, 116, 1, 17, 67, 10, 2, 32, 14, 128, 128, 130, 3, 87, 47, 0, 116, 1, 110, 10, 2, 32, 0, 116, 8, 2, 105, 108, 17, 65, 0, 116, 101, 1, 17, 67, 10, 2, 32, 14, 128, 128, 131, 3, 87, 47, 13, 0, 116, 101, 110, 1, 17, 67, 10, 2, 32, 14, 128, 128, 132, 3, 87, 47, 13, 50, 0, 116, 101, 109, 1, 17, 67, 10, 2, 32, 14, 128, 128, 132, 3, 87, 47, 13, 63, 0, 116, 101, 115, 1, 17, 67, 10, 2, 32, 14, 128, 128, 132, 3, 87, 47, 13, 87, 0, 116, 114, 97, 195, 159, 101, 1, 21, 2, 32, 14, 128, 128, 134, 3, 87, 47, 34, 4, 114, 87, 13, 0, 116, 101, 114, 1, 17, 67, 10, 2, 32, 14, 128, 128, 132, 3, 87, 47, 106, 0, 116, 101, 1, 97, 2, 108, 108, 3, 87, 47, 107, 0, 112, 104, 3, 87, 81, 0, 115, 116, 2, 21, 3, 87, 89, 47, 0, 4, 99, 104, 101, 110, 1, 101, 102, 3, 87, 97, 13, 50, 0, 99, 104, 101, 110, 1, 101, 105, 0, 99, 104, 101, 110, 1, 104, 0, 99, 104, 101, 110, 1, 117, 164, 195, 0, 99, 104, 101, 110, 1, 164, 195, 0, 99, 104, 101, 110, 1, 182, 195, 0, 111, 117, 2, 110, 100, 3, 87, 119, 0, 4, 8, 2, 112, 17, 65, 3, 89, 0, 8, 2, 112, 108, 17, 65, 0, 8, 2, 112, 114, 17, 65, 0, 8, 2, 116, 17, 65, 0, 8, 2, 116, 114, 17, 65, 0, 99, 104, 0, 99, 104, 8, 2, 17, 65, 0, 99, 104, 8, 2, 18, 66, 17, 65, 0, 99, 104, 8, 2, 109, 17, 65, 0, 99, 104, 8, 2, 110, 17, 65, 0, 99, 104, 8, 2, 119, 0, 104, 2, 25, 0, 104, 8, 2, 17, 65, 0, 104, 8, 2, 114, 17, 65, 0, 99, 104, 117, 108, 8, 2, 100, 3, 89, 6, 112, 55, 0, 99, 104, 117, 108, 8, 2, 21, 14, 128, 132, 133, 3, 89, 6, 118, 55, 0, 99, 104, 101, 105, 110, 2, 108, 105, 99, 104, 3, 89, 6, 120, 50, 0, 4, 99, 104, 101, 110, 1, 117, 164, 195, 116, 3, 89, 13, 50, 0, 99, 104, 101, 110, 1, 164, 195, 119, 0, 99, 104, 101, 110, 1, 182, 195, 108, 0, 99, 104, 101, 110, 1, 182, 195, 114, 0, 99, 104, 97, 102, 116, 1, 10, 2, 32, 14, 128, 128, 134, 3, 89, 35, 81, 47, 0, 4, 116, 8, 101, 98, 3, 89, 47, 0, 116, 8, 101, 103, 0, 116, 8, 114, 101, 118, 0, 116, 101, 2, 108, 108, 3, 89, 47, 107, 0, 4, 112, 2, 97, 110, 3, 89, 48, 0, 112, 2, 101, 105, 99, 104, 0, 112, 2, 101, 114, 114, 0, 112, 2, 105, 101, 108, 0, 112, 2, 114, 0, 112, 8, 101, 98, 0, 112, 8, 101, 103, 0, 112, 8, 114, 101, 118, 0, 99, 104, 119, 101, 114, 3, 89, 82, 124, 34, 0, 8, 2, 32, 3, 107, 87, 0, 7, 6, 116, 0, 1, 116, 3, 0, 101, 1, 116, 10, 2, 32, 3, 13, 0, 4, 101, 101, 110, 8, 3, 21, 0, 104, 114, 105, 108, 108, 0, 114, 97, 105, 108, 8, 0, 114, 97, 110, 113, 117, 8, 0, 119, 8, 0, 4, 3, 47, 0, 1, 114, 101, 105, 2, 32, 14, 128, 128, 129, 0, 2, 99, 104, 101, 110, 32, 0, 8, 2, 114, 17, 65, 0, 8, 2, 115, 101, 116, 115, 101, 0, 104, 1, 25, 0, 104, 2, 25, 0, 104, 8, 2, 17, 65, 0, 104, 8, 2, 114, 17, 65, 0, 104, 8, 97, 112, 0, 101, 108, 101, 8, 2, 21, 3, 47, 4, 124, 55, 124, 0, 105, 101, 102, 8, 2, 21, 14, 128, 132, 132, 3, 47, 6, 116, 81, 0, 101, 1, 114, 101, 105, 2, 32, 14, 128, 128, 130, 3, 47, 13, 0, 101, 114, 101, 1, 114, 101, 105, 2, 32, 14, 128, 128, 132, 3, 47, 13, 34, 13, 0, 101, 114, 101, 110, 1, 114, 101, 105, 2, 32, 14, 128, 128, 133, 3, 47, 13, 34, 13, 50, 0, 101, 114, 101, 109, 1, 114, 101, 105, 2, 32, 14, 128, 128, 133, 3, 47, 13, 34, 13, 63, 0, 101, 114, 101, 115, 1, 114, 101, 105, 2, 32, 14, 128, 128, 133, 3, 47, 13, 34, 13, 87, 0, 101, 114, 101, 114, 1, 114, 101, 105, 2, 32, 14, 128, 128, 133, 3, 47, 13, 34, 106, 0, 101, 116, 1, 114, 101, 105, 2, 32, 14, 128, 128, 131, 3, 47, 13, 47, 0, 101, 110, 1, 114, 101, 105, 2, 32, 14, 128, 128, 131, 3, 47, 13, 50, 0, 101, 109, 1, 114, 101, 105, 2, 32, 14, 128, 128, 131, 3, 47, 13, 63, 0, 101, 115, 1, 114, 101, 105, 2, 32, 14, 128, 128, 131, 3, 47, 13, 87, 0, 101, 115, 116, 1, 114, 101, 105, 2, 32, 14, 128, 128, 132, 3, 47, 13, 87, 47, 0, 101, 115, 116, 101, 1, 114, 101, 105, 2, 32, 14, 128, 128, 133, 3, 47, 13, 87, 47, 13, 0, 101, 115, 116, 101, 110, 1, 114, 101, 105, 2, 32, 14, 128, 128, 134, 3, 47, 13, 87, 47, 13, 50, 0, 101, 115, 116, 101, 109, 1, 114, 101, 105, 2, 32, 14, 128, 128, 134, 3, 47, 13, 87, 47, 13, 63, 0, 101, 115, 116, 101, 115, 1, 114, 101, 105, 2, 32, 14, 128, 128, 134, 3, 47, 13, 87, 47, 13, 87, 0, 101, 115, 116, 101, 114, 1, 114, 101, 105, 2, 32, 14, 128, 128, 134, 3, 47, 13, 87, 47, 106, 0, 114, 97, 118, 101, 114, 3, 47, 34, 2, 35, 82, 107, 34, 0, 97, 108, 101, 110, 116, 8, 3, 47, 35, 55, 6, 107, 50, 47, 0, 119, 8, 2, 17, 65, 3, 47, 58, 0, 101, 114, 1, 114, 101, 105, 2, 32, 14, 128, 128, 131, 3, 47, 106, 0, 104, 101, 114, 109, 111, 8, 3, 47, 107, 34, 63, 125, 0, 117, 101, 114, 101, 105, 2, 32, 3, 47, 118, 13, 34, 6, 120, 0, 4, 8, 2, 32, 3, 47, 124, 0, 104, 101, 2, 101, 114, 97, 0, 4, 99, 104, 3, 74, 0, 115, 99, 104, 8, 2, 17, 65, 0, 122, 3, 130, 0, 115, 116, 1, 114, 101, 105, 2, 32, 14, 128, 128, 131, 3, 130, 47, 0, 115, 116, 101, 1, 114, 101, 105, 2, 32, 14, 128, 128, 132, 3, 130, 47, 13, 0, 115, 116, 101, 110, 1, 114, 101, 105, 2, 32, 14, 128, 128, 133, 3, 130, 47, 13, 50, 0, 115, 116, 101, 109, 1, 114, 101, 105, 2, 32, 14, 128, 128, 133, 3, 130, 47, 13, 63, 0, 115, 116, 101, 115, 1, 114, 101, 105, 2, 32, 14, 128, 128, 133, 3, 130, 47, 13, 87, 0, 115, 116, 101, 114, 1, 114, 101, 105, 2, 32, 14, 128, 128, 133, 3, 130, 47, 106, 0, 105, 111, 110, 1, 21, 3, 130, 109, 4, 125, 50, 0, 105, 101, 110, 116, 1, 21, 2, 32, 3, 130, 109, 6, 107, 50, 47, 0, 105, 111, 110, 1, 21, 2, 32, 3, 130, 109, 6, 125, 50, 0, 7, 6, 117, 0, 110, 103, 115, 1, 10, 2, 17, 65, 3, 2, 112, 66, 87, 23, 0, 108, 116, 114, 97, 8, 2, 21, 14, 128, 132, 133, 3, 4, 112, 55, 47, 34, 35, 0, 110, 105, 118, 101, 114, 2, 115, 3, 4, 118, 50, 116, 82, 107, 34, 0, 2, 112, 116, 32, 3, 6, 112, 0, 4, 109, 8, 2, 111, 114, 103, 14, 128, 132, 130, 3, 6, 112, 63, 0, 109, 8, 2, 115, 116, 17, 65, 14, 128, 132, 130, 0, 109, 98, 101, 8, 2, 21, 14, 128, 132, 132, 3, 6, 112, 63, 69, 13, 0, 109, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 6, 112, 63, 79, 13, 0, 101, 114, 105, 115, 99, 104, 1, 21, 2, 32, 3, 6, 118, 34, 109, 89, 0, 101, 2, 32, 3, 6, 126, 0, 4, 110, 100, 101, 114, 8, 3, 21, 0, 115, 101, 114, 8, 0, 110, 97, 98, 8, 2, 21, 14, 128, 132, 132, 3, 23, 4, 112, 50, 23, 35, 48, 0, 110, 116, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 23, 4, 112, 50, 47, 106, 0, 101, 98, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 23, 4, 126, 69, 106, 0, 4, 110, 8, 2, 21, 14, 128, 132, 130, 3, 23, 6, 112, 50, 0, 110, 8, 2, 105, 110, 21, 14, 128, 132, 130, 0, 110, 97, 110, 8, 2, 21, 14, 128, 132, 132, 3, 23, 6, 112, 50, 23, 35, 50, 0, 110, 117, 109, 8, 2, 21, 14, 128, 132, 132, 3, 23, 6, 112, 50, 23, 112, 63, 0, 110, 97, 117, 102, 8, 2, 21, 14, 128, 132, 133, 3, 23, 6, 112, 50, 23, 119, 81, 0, 110, 97, 117, 115, 8, 2, 21, 14, 128, 132, 133, 3, 23, 6, 112, 50, 23, 119, 87, 0, 110, 101, 105, 110, 8, 2, 21, 14, 128, 132, 133, 3, 23, 6, 112, 50, 23, 120, 50, 0, 110, 98, 101, 8, 2, 21, 14, 128, 132, 132, 3, 23, 6, 112, 50, 69, 13, 0, 110, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 23, 6, 112, 50, 79, 13, 0, 110, 118, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 23, 6, 112, 50, 81, 107, 34, 0, 4, 1, 21, 2, 109, 32, 3, 112, 0, 1, 21, 2, 110, 103, 0, 2, 17, 67, 11, 0, 2, 17, 67, 17, 67, 0, 2, 115, 99, 104, 0, 2, 120, 0, 110, 8, 3, 112, 50, 0, 110, 116, 101, 114, 8, 2, 101, 29, 3, 112, 50, 47, 13, 34, 0, 4, 109, 2, 32, 3, 112, 63, 0, 109, 8, 2, 21, 14, 128, 132, 130, 0, 109, 103, 101, 8, 2, 98, 3, 112, 63, 79, 6, 124, 0, 115, 2, 32, 3, 112, 87, 0, 4, 3, 118, 0, 1, 108, 17, 65, 2, 116, 32, 0, 1, 112, 101, 114, 2, 98, 108, 0, 1, 115, 2, 99, 104, 0, 1, 116, 114, 2, 109, 32, 0, 2, 101, 0, 8, 2, 32, 0, 8, 2, 114, 107, 0, 8, 2, 114, 108, 0, 8, 2, 114, 118, 0, 8, 100, 2, 115, 99, 104, 0, 104, 2, 12, 0, 101, 108, 97, 1, 10, 2, 32, 3, 118, 4, 124, 55, 35, 0, 101, 108, 108, 3, 118, 6, 107, 55, 0, 4, 101, 1, 114, 2, 32, 3, 118, 13, 0, 101, 1, 116, 2, 32, 0, 98, 2, 116, 32, 3, 118, 48, 0, 103, 2, 116, 32, 3, 118, 49, 0, 110, 8, 2, 105, 3, 118, 50, 0, 110, 105, 118, 101, 114, 115, 105, 116, 195, 164, 116, 115, 8, 2, 14, 128, 132, 140, 3, 118, 50, 116, 82, 107, 34, 86, 116, 47, 6, 123, 130, 0, 109, 1, 116, 2, 32, 3, 118, 63, 0, 7, 6, 118, 0, 1, 118, 3, 0, 4, 111, 114, 8, 2, 21, 14, 128, 132, 131, 3, 6, 81, 125, 34, 0, 111, 114, 8, 2, 110, 101, 0, 4, 2, 32, 24, 3, 81, 0, 2, 101, 114, 0, 2, 111, 103, 0, 2, 111, 108, 107, 0, 2, 111, 108, 108, 0, 2, 195, 182, 108, 17, 67, 0, 8, 2, 97, 116, 105, 32, 0, 8, 2, 105, 101, 0, 8, 2, 105, 122, 0, 8, 2, 108, 105, 101, 115, 0, 8, 2, 111, 110, 0, 8, 2, 114, 105, 0, 8, 2, 195, 164, 116, 0, 4, 101, 114, 2, 98, 105, 110, 100, 3, 81, 2, 107, 34, 0, 101, 114, 2, 100, 105, 101, 110, 0, 101, 114, 2, 115, 105, 99, 104, 116, 0, 101, 114, 2, 116, 105, 101, 102, 0, 101, 114, 8, 2, 21, 14, 128, 132, 131, 0, 4, 111, 108, 108, 8, 2, 98, 114, 3, 81, 2, 111, 55, 0, 111, 108, 108, 8, 2, 107, 111, 0, 111, 108, 108, 8, 2, 115, 116, 114, 101, 0, 111, 108, 108, 8, 2, 122, 0, 111, 108, 108, 8, 2, 101, 110, 100, 3, 81, 2, 111, 55, 23, 0, 111, 108, 108, 8, 2, 17, 67, 21, 14, 128, 132, 132, 3, 81, 6, 111, 55, 0, 105, 101, 114, 8, 2, 103, 21, 14, 128, 132, 132, 3, 81, 6, 116, 34, 0, 105, 101, 108, 8, 2, 21, 14, 128, 132, 132, 3, 81, 6, 116, 55, 0, 101, 114, 103, 101, 115, 115, 1, 21, 3, 81, 107, 34, 79, 4, 107, 87, 0, 101, 114, 102, 97, 104, 114, 101, 110, 1, 21, 2, 32, 14, 128, 128, 137, 3, 81, 107, 34, 81, 4, 114, 34, 13, 50, 0, 101, 114, 115, 105, 99, 104, 1, 21, 3, 81, 107, 34, 86, 4, 109, 97, 0, 111, 114, 8, 2, 110, 3, 81, 111, 34, 0, 111, 114, 100, 101, 114, 3, 81, 111, 34, 70, 106, 0, 97, 116, 101, 114, 3, 81, 114, 47, 106, 0, 105, 101, 8, 3, 81, 116, 0, 8, 2, 32, 3, 81, 119, 0, 195, 164, 116, 101, 114, 3, 81, 123, 47, 106, 0, 111, 114, 1, 17, 67, 3, 81, 125, 34, 0, 111, 114, 98, 101, 105, 8, 2, 14, 128, 132, 134, 3, 81, 125, 34, 6, 69, 120, 0, 111, 114, 97, 117, 115, 8, 2, 14, 128, 132, 134, 3, 81, 125, 34, 6, 119, 87, 0, 111, 114, 195, 188, 98, 101, 114, 8, 2, 14, 128, 132, 135, 3, 81, 125, 34, 6, 127, 69, 106, 0, 111, 114, 104, 97, 1, 45, 2, 110, 100, 3, 81, 125, 34, 105, 6, 35, 0, 111, 114, 104, 101, 114, 8, 2, 14, 128, 132, 134, 3, 81, 125, 34, 105, 6, 124, 34, 0, 4, 3, 82, 0, 1, 97, 2, 101, 114, 0, 1, 101, 114, 2, 101, 114, 0, 1, 105, 2, 101, 114, 0, 1, 111, 2, 101, 114, 0, 1, 117, 2, 101, 114, 0, 8, 2, 17, 65, 0, 8, 2, 105, 101, 116, 0, 8, 2, 108, 97, 100, 0, 8, 17, 65, 2, 101, 114, 0, 101, 8, 2, 114, 98, 111, 115, 3, 82, 2, 107, 0, 4, 101, 1, 98, 117, 115, 2, 114, 3, 82, 107, 0, 101, 1, 100, 97, 2, 114, 0, 101, 1, 110, 111, 107, 2, 114, 0, 101, 1, 114, 101, 112, 2, 114, 0, 101, 1, 115, 110, 97, 114, 116, 2, 114, 0, 101, 2, 114, 116, 105, 0, 101, 8, 2, 114, 98, 97, 108, 0, 101, 8, 2, 114, 115, 97, 116, 0, 101, 8, 2, 114, 115, 105, 101, 0, 101, 8, 2, 114, 115, 105, 102, 0, 101, 8, 2, 114, 115, 105, 111, 110, 0, 101, 8, 2, 114, 116, 101, 98, 0, 101, 108, 118, 2, 101, 114, 3, 82, 107, 55, 82, 0, 105, 8, 2, 17, 67, 17, 67, 3, 82, 109, 0, 105, 101, 116, 8, 3, 82, 109, 107, 47, 0, 105, 8, 3, 82, 116, 0, 101, 104, 101, 8, 3, 82, 124, 105, 124, 0, 7, 6, 119, 0, 4, 97, 114, 101, 1, 10, 2, 32, 3, 21, 0, 104, 8, 0, 111, 114, 107, 0, 4, 3, 82, 0, 8, 2, 108, 97, 100, 0, 8, 2, 114, 17, 65, 0, 104, 8, 2, 17, 65, 0, 111, 8, 2, 104, 105, 110, 3, 82, 2, 125, 0, 97, 115, 115, 101, 114, 8, 2, 21, 14, 128, 132, 134, 3, 82, 6, 35, 87, 13, 34, 0, 97, 115, 99, 104, 8, 2, 21, 14, 128, 132, 133, 3, 82, 6, 35, 89, 0, 101, 105, 116, 8, 2, 17, 67, 21, 14, 128, 132, 132, 3, 82, 6, 120, 47, 0, 101, 105, 116, 101, 114, 8, 2, 21, 14, 128, 132, 134, 3, 82, 6, 120, 47, 13, 34, 0, 101, 103, 8, 2, 17, 67, 21, 14, 128, 132, 131, 3, 82, 6, 124, 49, 0, 111, 104, 108, 8, 2, 21, 14, 128, 132, 132, 3, 82, 6, 125, 55, 0, 105, 101, 100, 101, 114, 8, 2, 21, 14, 128, 132, 134, 3, 82, 116, 70, 106, 0, 101, 105, 116, 104, 101, 114, 8, 3, 82, 120, 47, 105, 124, 34, 0, 8, 2, 32, 3, 82, 124, 0, 101, 114, 116, 1, 21, 2, 32, 3, 82, 124, 34, 47, 0, 111, 118, 111, 114, 8, 3, 82, 125, 81, 6, 125, 34, 0, 7, 6, 120, 0, 3, 49, 87, 0, 8, 2, 32, 3, 109, 49, 87, 0, 7, 6, 121, 0, 1, 116, 2, 32, 3, 21, 0, 4, 1, 17, 65, 2, 17, 65, 3, 57, 0, 8, 2, 17, 65, 0, 1, 21, 2, 32, 3, 109, 0, 3, 126, 0, 4, 2, 17, 67, 17, 67, 3, 127, 0, 2, 120, 0, 8, 2, 32, 3, 127, 48, 87, 109, 55, 111, 50, 0, 7, 6, 122, 0, 2, 122, 3, 0, 121, 107, 108, 111, 8, 2, 21, 14, 128, 132, 133, 3, 4, 130, 126, 49, 55, 125, 0, 8, 2, 100, 101, 110, 3, 86, 0, 4, 3, 130, 0, 8, 2, 119, 17, 65, 0, 121, 108, 105, 110, 3, 130, 2, 116, 55, 109, 50, 0, 4, 117, 8, 2, 17, 67, 21, 14, 128, 132, 130, 3, 130, 2, 118, 0, 117, 8, 2, 101, 14, 128, 132, 130, 0, 117, 8, 2, 103, 117, 21, 14, 128, 132, 130, 0, 105, 101, 8, 2, 103, 101, 21, 14, 128, 132, 131, 3, 130, 6, 116, 0, 105, 101, 114, 8, 2, 21, 14, 128, 132, 132, 3, 130, 6, 116, 34, 0, 105, 101, 108, 8, 2, 21, 14, 128, 132, 132, 3, 130, 6, 116, 55, 0, 101, 105, 116, 8, 2, 21, 14, 128, 132, 132, 3, 130, 6, 120, 47, 0, 105, 101, 108, 108, 3, 130, 57, 6, 107, 55, 0, 101, 114, 8, 2, 21, 14, 128, 132, 131, 3, 130, 107, 34, 0, 8, 2, 32, 3, 130, 107, 47, 0, 101, 110, 116, 114, 97, 108, 8, 2, 21, 14, 128, 132, 135, 3, 130, 107, 50, 47, 34, 6, 114, 55, 0, 101, 110, 116, 114, 97, 108, 8, 2, 105, 3, 130, 107, 50, 47, 34, 35, 55, 0, 4, 117, 8, 2, 99, 107, 3, 130, 112, 0, 117, 8, 2, 110, 17, 67, 0, 105, 103, 101, 117, 8, 3, 130, 116, 79, 6, 122, 0, 105, 103, 97, 114, 101, 116, 116, 101, 110, 8, 2, 21, 14, 128, 132, 138, 3, 130, 116, 79, 35, 34, 6, 107, 47, 13, 50, 0, 117, 8, 2, 103, 21, 3, 130, 118, 0, 117, 114, 195, 188, 99, 107, 8, 2, 21, 14, 128, 132, 134, 3, 130, 118, 34, 6, 127, 49, 0, 117, 115, 97, 109, 109, 101, 110, 8, 2, 21, 14, 128, 132, 136, 3, 130, 118, 86, 6, 35, 63, 13, 50, 0, 4, 101, 114, 101, 8, 2, 98, 3, 130, 124, 34, 124, 0, 101, 114, 101, 8, 2, 109, 0, 7, 6, 0, 4, 195, 169, 2, 32, 3, 6, 124, 0, 195, 169, 101, 0, 45, 8, 2, 32, 15, 3, 10, 0, 44, 2, 15, 3, 49, 111, 63, 35, 0, 45, 8, 32, 2, 32, 15, 3, 63, 116, 50, 112, 87, 0, 36, 3, 70, 111, 55, 6, 114, 0, 196, 141, 3, 74, 0, 195, 167, 3, 87, 0, 197, 190, 3, 88, 0, 197, 161, 3, 89, 0, 45, 1, 32, 15, 2, 32, 15, 3, 89, 47, 34, 109, 97, 0, 195, 166, 3, 107, 0, 195, 169, 3, 124, 0, 195, 184, 3, 129, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts11 = FileInMemory_createWithData (21519, reinterpret_cast (&espeakdata_dicts11_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/de_dict", L"de"); Collection_addItem (me.peek(), espeakdata_dicts11.transfer()); static unsigned char espeakdata_dicts12_data[3607] = { 0, 4, 0, 0, 154, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 51, 57, 120, 50, 47, 116, 55, 6, 111, 87, 0, 12, 3, 95, 50, 49, 111, 49, 12, 6, 111, 87, 0, 0, 12, 3, 95, 51, 56, 35, 34, 47, 6, 111, 87, 0, 10, 3, 95, 50, 48, 69, 6, 110, 87, 0, 0, 11, 3, 95, 50, 51, 47, 6, 112, 111, 87, 0, 0, 11, 3, 95, 50, 50, 69, 6, 116, 111, 87, 0, 0, 13, 3, 95, 50, 53, 48, 13, 78, 12, 6, 111, 87, 0, 0, 12, 3, 95, 50, 52, 78, 6, 118, 69, 111, 87, 0, 0, 14, 3, 95, 50, 55, 87, 13, 47, 12, 6, 116, 111, 87, 0, 0, 14, 3, 95, 50, 54, 142, 13, 69, 69, 6, 110, 34, 87, 0, 0, 14, 3, 95, 51, 49, 111, 49, 13, 47, 12, 6, 111, 87, 0, 0, 10, 3, 95, 51, 48, 47, 6, 110, 87, 0, 0, 12, 3, 95, 51, 51, 47, 125, 47, 6, 111, 87, 0, 0, 13, 3, 95, 51, 50, 69, 35, 47, 12, 6, 111, 87, 0, 0, 12, 3, 95, 51, 53, 48, 125, 47, 6, 111, 87, 0, 0, 12, 3, 95, 51, 52, 78, 128, 47, 6, 111, 87, 0, 0, 12, 3, 95, 51, 55, 87, 125, 47, 6, 111, 87, 0, 0, 13, 3, 95, 51, 54, 142, 35, 85, 6, 47, 111, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 55, 57, 4, 120, 65, 111, 116, 87, 6, 110, 0, 12, 3, 95, 54, 49, 6, 111, 49, 87, 13, 140, 0, 0, 16, 3, 95, 55, 56, 35, 136, 105, 35, 47, 12, 6, 107, 34, 12, 0, 10, 3, 95, 54, 48, 87, 6, 116, 140, 0, 0, 14, 3, 95, 48, 67, 87, 35, 6, 136, 36, 111, 49, 35, 0, 13, 3, 95, 54, 51, 47, 6, 111, 34, 87, 13, 140, 0, 0, 12, 3, 95, 54, 50, 69, 6, 116, 87, 13, 140, 0, 0, 12, 3, 95, 54, 53, 48, 132, 50, 87, 13, 140, 0, 0, 12, 3, 95, 54, 52, 78, 6, 128, 87, 13, 140, 0, 0, 13, 3, 95, 54, 55, 87, 6, 107, 34, 87, 13, 140, 0, 0, 14, 3, 95, 54, 54, 142, 6, 111, 57, 116, 87, 13, 140, 0, 0, 15, 3, 95, 55, 49, 111, 144, 35, 47, 12, 6, 107, 34, 12, 0, 0, 14, 3, 95, 55, 48, 87, 35, 47, 12, 6, 107, 34, 12, 0, 0, 16, 3, 95, 55, 51, 47, 111, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 16, 3, 95, 55, 50, 69, 13, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 17, 3, 95, 55, 53, 48, 35, 142, 4, 35, 47, 12, 6, 107, 34, 12, 0, 0, 16, 3, 95, 55, 52, 78, 118, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 18, 3, 95, 55, 55, 87, 13, 47, 13, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 16, 3, 95, 55, 54, 142, 111, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 12, 3, 95, 49, 57, 120, 50, 50, 6, 111, 87, 0, 0, 13, 3, 95, 49, 56, 107, 140, 12, 6, 116, 34, 109, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 57, 120, 50, 47, 6, 111, 87, 0, 15, 3, 95, 49, 49, 36, 6, 79, 57, 6, 116, 34, 13, 17, 0, 0, 13, 3, 95, 50, 56, 35, 136, 12, 6, 116, 111, 87, 0, 13, 3, 95, 49, 48, 70, 6, 37, 105, 35, 36, 111, 0, 0, 11, 3, 95, 49, 51, 47, 6, 113, 34, 109, 0, 0, 11, 3, 95, 49, 50, 69, 6, 35, 34, 109, 0, 0, 13, 3, 95, 49, 53, 48, 6, 107, 50, 70, 34, 109, 0, 0, 11, 3, 95, 49, 52, 142, 6, 118, 70, 109, 0, 0, 13, 3, 95, 49, 55, 87, 6, 107, 47, 12, 34, 109, 0, 0, 11, 3, 95, 49, 54, 87, 6, 117, 55, 109, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 52, 57, 6, 120, 65, 78, 116, 87, 0, 0, 14, 3, 95, 52, 56, 35, 34, 47, 116, 55, 6, 111, 87, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 53, 57, 120, 50, 87, 6, 107, 136, 0, 14, 3, 95, 52, 49, 111, 49, 47, 116, 55, 6, 111, 87, 0, 0, 14, 3, 95, 53, 56, 35, 136, 12, 6, 116, 58, 13, 50, 0, 12, 3, 95, 52, 48, 78, 116, 55, 6, 111, 87, 0, 0, 14, 3, 95, 52, 51, 47, 125, 47, 116, 55, 6, 111, 87, 0, 0, 13, 3, 95, 52, 50, 69, 132, 116, 55, 6, 111, 87, 0, 0, 16, 3, 95, 52, 53, 48, 132, 6, 50, 47, 116, 55, 6, 111, 87, 0, 0, 14, 3, 95, 52, 52, 78, 118, 58, 116, 55, 6, 111, 87, 0, 0, 14, 3, 95, 52, 55, 87, 125, 47, 116, 55, 6, 111, 87, 0, 0, 15, 3, 95, 52, 54, 142, 105, 111, 57, 116, 55, 6, 111, 87, 0, 0, 18, 3, 95, 54, 57, 120, 50, 13, 105, 4, 35, 47, 12, 6, 107, 34, 12, 0, 14, 3, 95, 53, 49, 111, 49, 57, 6, 116, 58, 107, 50, 0, 0, 11, 3, 95, 54, 56, 35, 34, 87, 13, 140, 0, 12, 3, 95, 53, 48, 48, 13, 78, 6, 116, 87, 0, 0, 13, 3, 95, 53, 51, 47, 6, 111, 34, 48, 107, 50, 0, 0, 12, 3, 95, 53, 50, 69, 6, 116, 58, 107, 50, 0, 0, 13, 3, 95, 53, 53, 48, 6, 35, 142, 48, 107, 50, 0, 0, 13, 3, 95, 53, 52, 78, 6, 119, 121, 58, 107, 50, 0, 0, 15, 3, 95, 53, 55, 87, 107, 47, 12, 6, 116, 58, 13, 50, 0, 0, 14, 3, 95, 53, 54, 142, 105, 13, 48, 12, 6, 107, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 57, 50, 107, 58, 116, 87, 6, 110, 0, 0, 13, 3, 95, 56, 56, 35, 136, 12, 116, 87, 6, 110, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 57, 57, 50, 111, 65, 57, 6, 116, 50, 13, 58, 112, 0, 13, 3, 95, 56, 49, 111, 49, 57, 116, 87, 6, 110, 0, 0, 15, 3, 95, 57, 56, 35, 136, 12, 6, 116, 50, 13, 58, 112, 0, 12, 3, 95, 56, 48, 4, 107, 87, 87, 6, 110, 0, 0, 13, 3, 95, 56, 51, 47, 111, 34, 116, 87, 6, 110, 0, 0, 12, 3, 95, 56, 50, 69, 132, 116, 87, 6, 110, 0, 0, 14, 3, 95, 56, 53, 48, 111, 6, 78, 116, 87, 6, 110, 0, 0, 13, 3, 95, 56, 52, 78, 118, 34, 116, 87, 6, 110, 0, 0, 14, 3, 95, 56, 55, 87, 107, 47, 12, 116, 87, 6, 110, 0, 0, 13, 3, 95, 56, 54, 142, 111, 57, 116, 87, 6, 110, 0, 0, 15, 3, 95, 57, 49, 111, 49, 57, 6, 116, 50, 13, 58, 112, 0, 0, 12, 3, 95, 57, 48, 50, 107, 69, 12, 6, 112, 0, 0, 15, 3, 95, 57, 51, 47, 111, 34, 6, 116, 50, 13, 58, 112, 0, 0, 13, 3, 95, 57, 50, 69, 6, 116, 50, 13, 58, 112, 0, 0, 15, 3, 95, 57, 53, 48, 13, 78, 6, 116, 50, 13, 58, 112, 0, 0, 15, 3, 95, 57, 52, 78, 118, 34, 6, 116, 63, 13, 58, 112, 0, 0, 16, 3, 95, 57, 55, 87, 13, 47, 12, 6, 116, 50, 13, 58, 112, 0, 0, 15, 3, 95, 57, 54, 142, 111, 57, 6, 116, 50, 13, 58, 112, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 4, 95, 48, 77, 50, 55, 6, 116, 144, 0, 0, 13, 4, 95, 48, 77, 51, 78, 34, 6, 39, 34, 36, 0, 0, 0, 13, 4, 95, 48, 77, 49, 105, 13, 86, 6, 116, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 131, 239, 187, 191, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 2, 95, 51, 47, 37, 50, 36, 111, 0, 0, 9, 2, 95, 50, 70, 6, 36, 111, 0, 0, 10, 2, 95, 49, 36, 6, 49, 36, 111, 0, 0, 11, 2, 95, 48, 87, 6, 40, 63, 36, 111, 0, 0, 11, 2, 95, 55, 105, 35, 6, 136, 36, 111, 0, 0, 10, 2, 95, 54, 105, 35, 6, 36, 111, 0, 0, 11, 2, 95, 53, 81, 35, 6, 105, 36, 111, 0, 0, 14, 2, 95, 52, 105, 35, 6, 136, 35, 6, 34, 36, 111, 0, 0, 0, 0, 11, 2, 95, 57, 50, 6, 40, 35, 36, 111, 0, 0, 10, 2, 95, 56, 35, 6, 89, 36, 111, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 2, 222, 135, 6, 35, 55, 37, 81, 40, 0, 0, 10, 2, 222, 134, 49, 6, 116, 81, 40, 0, 0, 15, 2, 222, 133, 62, 6, 35, 82, 4, 37, 57, 35, 50, 37, 0, 0, 8, 2, 222, 132, 69, 6, 116, 0, 0, 8, 2, 222, 131, 51, 6, 116, 0, 0, 10, 2, 222, 130, 50, 6, 121, 50, 40, 0, 0, 14, 2, 222, 129, 91, 6, 35, 82, 37, 57, 35, 50, 37, 0, 0, 8, 2, 222, 128, 105, 6, 116, 0, 0, 14, 2, 222, 143, 65, 6, 35, 82, 37, 57, 35, 50, 37, 0, 0, 10, 2, 222, 142, 79, 6, 116, 81, 40, 0, 0, 10, 2, 222, 141, 55, 6, 116, 63, 40, 0, 0, 8, 2, 222, 140, 47, 6, 116, 0, 0, 10, 2, 222, 139, 70, 6, 116, 55, 40, 0, 0, 10, 2, 222, 138, 81, 6, 116, 81, 40, 0, 0, 10, 2, 222, 137, 63, 6, 110, 63, 40, 0, 0, 10, 2, 222, 136, 82, 6, 116, 82, 40, 0, 0, 14, 2, 222, 151, 74, 6, 35, 82, 37, 57, 35, 50, 37, 0, 0, 14, 2, 222, 150, 73, 6, 35, 82, 37, 57, 35, 50, 37, 0, 0, 14, 2, 222, 149, 48, 6, 35, 82, 37, 57, 35, 50, 37, 0, 0, 8, 2, 222, 148, 57, 6, 116, 0, 0, 14, 2, 222, 147, 138, 6, 35, 82, 37, 57, 35, 50, 37, 0, 0, 14, 2, 222, 146, 86, 6, 35, 82, 37, 57, 35, 50, 37, 0, 0, 14, 2, 222, 145, 139, 6, 35, 82, 37, 57, 35, 50, 37, 0, 0, 10, 2, 222, 144, 87, 6, 110, 50, 40, 0, 0, 10, 2, 222, 159, 70, 6, 116, 70, 40, 0, 0, 10, 2, 222, 158, 87, 6, 116, 70, 40, 0, 0, 10, 2, 222, 157, 89, 6, 110, 50, 40, 0, 0, 8, 2, 222, 156, 86, 6, 116, 0, 0, 10, 2, 222, 155, 84, 6, 116, 55, 40, 0, 0, 8, 2, 222, 154, 99, 6, 116, 0, 0, 9, 2, 222, 153, 105, 105, 6, 116, 0, 0, 8, 2, 222, 152, 85, 6, 116, 0, 0, 15, 2, 222, 167, 6, 116, 69, 116, 15, 81, 4, 37, 55, 37, 0, 0, 15, 2, 222, 166, 6, 35, 69, 35, 15, 81, 4, 37, 55, 37, 0, 0, 10, 2, 222, 165, 58, 6, 116, 82, 40, 0, 0, 10, 2, 222, 164, 102, 6, 116, 81, 40, 0, 0, 11, 2, 222, 163, 98, 35, 6, 37, 50, 40, 0, 0, 10, 2, 222, 162, 35, 6, 37, 50, 40, 0, 0, 8, 2, 222, 161, 86, 6, 39, 0, 0, 8, 2, 222, 160, 47, 6, 39, 0, 0, 15, 2, 222, 175, 6, 117, 69, 117, 15, 81, 4, 37, 55, 37, 0, 0, 15, 2, 222, 174, 6, 39, 69, 39, 15, 81, 4, 37, 55, 37, 0, 0, 15, 2, 222, 173, 6, 112, 69, 112, 15, 81, 4, 37, 55, 37, 0, 0, 15, 2, 222, 172, 6, 36, 69, 36, 15, 81, 4, 37, 55, 37, 0, 0, 15, 2, 222, 171, 6, 121, 69, 121, 15, 81, 4, 37, 55, 37, 0, 0, 15, 2, 222, 170, 6, 40, 69, 40, 15, 81, 4, 37, 55, 37, 0, 0, 15, 2, 222, 169, 6, 110, 69, 110, 15, 81, 4, 37, 55, 37, 0, 0, 15, 2, 222, 168, 6, 37, 69, 37, 15, 81, 4, 37, 55, 37, 0, 0, 0, 0, 0, 0, 0, 0, 15, 2, 222, 177, 50, 6, 35, 15, 82, 37, 57, 35, 50, 37, 0, 0, 11, 2, 222, 176, 87, 6, 40, 49, 40, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 1, 1, 0, 3, 105, 0, 7, 6, 1, 2, 0, 3, 91, 0, 7, 6, 1, 3, 0, 3, 50, 0, 222, 176, 2, 222, 130, 3, 50, 50, 0, 222, 176, 2, 222, 137, 3, 63, 63, 0, 222, 176, 2, 222, 143, 3, 65, 65, 0, 7, 6, 1, 4, 0, 3, 51, 0, 7, 6, 1, 5, 0, 3, 69, 0, 7, 6, 1, 6, 0, 3, 62, 0, 7, 6, 1, 7, 0, 3, 49, 0, 7, 6, 1, 8, 0, 3, 0, 222, 176, 2, 32, 3, 36, 105, 0, 222, 176, 2, 222, 140, 3, 47, 0, 222, 176, 2, 222, 149, 3, 48, 0, 222, 176, 2, 222, 134, 3, 49, 0, 222, 176, 2, 222, 130, 3, 50, 0, 222, 176, 2, 222, 131, 3, 51, 0, 222, 176, 2, 222, 141, 3, 55, 0, 222, 176, 2, 222, 148, 3, 57, 0, 222, 176, 2, 222, 133, 3, 62, 0, 222, 176, 2, 222, 137, 3, 63, 0, 222, 176, 2, 222, 143, 3, 66, 0, 222, 176, 2, 222, 132, 3, 69, 0, 222, 176, 2, 222, 139, 3, 70, 0, 222, 176, 2, 222, 150, 3, 73, 0, 222, 176, 2, 222, 151, 3, 74, 0, 222, 176, 2, 222, 142, 3, 79, 0, 222, 176, 2, 222, 134, 3, 82, 0, 222, 176, 2, 222, 146, 3, 86, 0, 222, 176, 2, 222, 144, 3, 87, 0, 222, 176, 2, 222, 156, 3, 88, 0, 222, 176, 2, 222, 128, 3, 91, 0, 4, 222, 176, 2, 222, 128, 3, 105, 0, 222, 176, 2, 222, 129, 0, 222, 176, 2, 222, 147, 3, 138, 0, 222, 176, 2, 222, 145, 3, 139, 0, 7, 6, 1, 9, 0, 3, 82, 0, 7, 6, 1, 10, 0, 3, 63, 0, 7, 6, 1, 11, 0, 3, 81, 0, 7, 6, 1, 12, 0, 3, 70, 0, 7, 6, 1, 13, 0, 3, 47, 0, 7, 6, 1, 14, 0, 3, 55, 0, 7, 6, 1, 15, 0, 3, 79, 0, 7, 6, 1, 16, 0, 3, 65, 0, 7, 6, 1, 17, 0, 3, 87, 0, 7, 6, 1, 18, 0, 3, 139, 0, 7, 6, 1, 19, 0, 3, 86, 0, 7, 6, 1, 20, 0, 3, 138, 0, 7, 6, 1, 21, 0, 3, 57, 0, 7, 6, 1, 22, 0, 3, 48, 0, 7, 6, 1, 23, 0, 3, 73, 0, 7, 6, 1, 24, 0, 3, 74, 0, 7, 6, 1, 25, 0, 3, 85, 0, 7, 6, 1, 26, 0, 3, 105, 0, 7, 6, 1, 27, 0, 3, 99, 0, 7, 6, 1, 28, 0, 3, 84, 0, 7, 6, 1, 29, 0, 3, 88, 0, 7, 6, 1, 30, 0, 3, 89, 0, 7, 6, 1, 31, 0, 3, 87, 0, 7, 6, 1, 32, 0, 3, 70, 0, 7, 6, 1, 33, 0, 3, 47, 0, 7, 6, 1, 34, 0, 3, 86, 0, 7, 6, 1, 35, 0, 3, 19, 0, 7, 6, 1, 36, 0, 3, 98, 0, 7, 6, 1, 37, 0, 3, 102, 0, 7, 6, 1, 38, 0, 3, 58, 0, 7, 6, 1, 39, 0, 3, 35, 0, 7, 6, 1, 40, 0, 3, 116, 0, 7, 6, 1, 41, 0, 3, 37, 0, 7, 6, 1, 42, 0, 3, 110, 0, 7, 6, 1, 43, 0, 3, 40, 0, 7, 6, 1, 44, 0, 3, 121, 0, 7, 6, 1, 45, 0, 3, 36, 0, 7, 6, 1, 46, 0, 3, 112, 0, 7, 6, 1, 47, 0, 3, 39, 0, 7, 6, 1, 48, 0, 3, 117, 0, 7, 6, 1, 49, 0, 3, 0, 7, 6, 1, 50, 0, 3, 64, 0, 7, 6, 0, 36, 3, 70, 39, 55, 35, 51, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts12 = FileInMemory_createWithData (3606, reinterpret_cast (&espeakdata_dicts12_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/dv_dict", L"dv"); Collection_addItem (me.peek(), espeakdata_dicts12.transfer()); static unsigned char espeakdata_dicts13_data[5352] = { 0, 4, 0, 0, 19, 16, 0, 0, 0, 0, 0, 0, 13, 138, 206, 181, 206, 175, 207, 135, 206, 177, 206, 189, 72, 0, 0, 0, 0, 17, 142, 206, 174, 207, 131, 206, 177, 207, 131, 207, 132, 206, 177, 206, 189, 72, 17, 142, 206, 174, 206, 188, 206, 177, 207, 131, 207, 132, 206, 177, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 207, 140, 207, 132, 206, 185, 8, 10, 134, 207, 140, 207, 132, 206, 185, 72, 8, 0, 0, 0, 0, 0, 9, 134, 206, 188, 206, 177, 207, 130, 72, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 51, 88, 15, 47, 34, 37, 35, 49, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 12, 1, 36, 84, 39, 55, 6, 35, 34, 37, 35, 0, 0, 14, 1, 37, 47, 37, 87, 36, 49, 35, 47, 6, 39, 0, 27, 0, 0, 0, 0, 0, 9, 134, 207, 132, 207, 137, 206, 189, 72, 9, 1, 42, 36, 48, 37, 0, 72, 27, 0, 9, 1, 43, 87, 37, 50, 0, 72, 27, 0, 11, 136, 207, 131, 207, 132, 207, 137, 206, 189, 72, 0, 9, 1, 45, 63, 6, 37, 39, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 206, 188, 206, 185, 206, 177, 207, 130, 72, 0, 0, 0, 0, 9, 1, 61, 37, 87, 39, 50, 0, 27, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 206, 181, 206, 175, 206, 188, 206, 177, 206, 185, 72, 0, 0, 0, 0, 17, 142, 206, 189, 206, 177, 206, 181, 206, 175, 206, 188, 206, 177, 206, 185, 72, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 49, 67, 15, 36, 49, 35, 47, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 49, 77, 49, 97, 6, 37, 61, 35, 0, 0, 22, 4, 95, 49, 77, 50, 6, 36, 50, 35, 36, 49, 35, 47, 39, 63, 6, 37, 34, 37, 39, 0, 0, 25, 4, 95, 49, 77, 51, 6, 36, 50, 35, 84, 37, 87, 36, 49, 35, 47, 39, 63, 6, 37, 34, 37, 39, 0, 0, 0, 0, 0, 12, 6, 206, 186, 206, 177, 206, 185, 49, 36, 0, 72, 0, 0, 0, 0, 0, 0, 11, 136, 206, 174, 207, 132, 206, 177, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 49, 67, 48, 36, 49, 35, 47, 6, 39, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 50, 67, 15, 84, 38, 35, 49, 39, 93, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 206, 184, 206, 177, 206, 173, 207, 135, 207, 137, 72, 0, 0, 0, 15, 140, 206, 181, 207, 128, 206, 181, 206, 185, 206, 180, 206, 174, 8, 0, 9, 134, 207, 131, 206, 191, 207, 133, 72, 0, 0, 7, 132, 206, 189, 206, 177, 72, 7, 132, 206, 189, 206, 177, 72, 0, 0, 15, 4, 95, 49, 49, 15, 36, 50, 84, 6, 36, 49, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 4, 95, 51, 67, 15, 47, 34, 38, 35, 49, 39, 93, 39, 87, 47, 6, 0, 0, 13, 4, 95, 4, 16, 20, 10, 49, 6, 39, 63, 35, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 49, 48, 15, 84, 6, 36, 49, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 207, 132, 206, 183, 72, 0, 0, 9, 134, 207, 131, 207, 132, 206, 183, 72, 7, 132, 207, 132, 206, 177, 72, 0, 0, 9, 134, 207, 131, 207, 132, 206, 177, 72, 13, 138, 206, 181, 206, 175, 207, 131, 207, 132, 206, 181, 72, 0, 0, 15, 140, 206, 181, 206, 175, 207, 135, 206, 177, 206, 188, 206, 181, 72, 15, 140, 206, 173, 207, 135, 206, 191, 207, 133, 206, 188, 206, 181, 72, 0, 0, 17, 142, 206, 189, 206, 177, 206, 181, 206, 175, 207, 131, 207, 132, 206, 181, 72, 7, 132, 207, 132, 206, 191, 72, 15, 4, 95, 49, 50, 15, 84, 39, 84, 6, 36, 49, 35, 47, 0, 0, 0, 9, 134, 207, 131, 207, 132, 206, 191, 72, 19, 144, 206, 189, 206, 177, 206, 173, 207, 135, 206, 191, 207, 133, 206, 188, 206, 181, 72, 0, 0, 10, 134, 206, 181, 206, 172, 206, 189, 72, 8, 0, 0, 0, 0, 0, 18, 5, 95, 50, 77, 49, 15, 84, 37, 87, 97, 37, 61, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 206, 186, 206, 191, 206, 189, 207, 132, 206, 172, 28, 0, 9, 134, 207, 128, 206, 191, 207, 133, 72, 0, 0, 0, 0, 0, 0, 0, 13, 138, 206, 173, 207, 135, 206, 181, 207, 132, 206, 181, 72, 0, 0, 0, 0, 17, 142, 206, 189, 206, 177, 206, 173, 207, 135, 206, 181, 207, 132, 206, 181, 72, 17, 142, 206, 184, 206, 177, 206, 181, 206, 175, 207, 131, 207, 132, 206, 181, 72, 0, 0, 0, 0, 21, 146, 206, 184, 206, 177, 206, 181, 206, 175, 206, 188, 206, 177, 207, 131, 207, 132, 206, 181, 72, 0, 0, 0, 0, 13, 138, 206, 180, 206, 185, 207, 140, 207, 132, 206, 185, 8, 19, 4, 95, 52, 67, 15, 47, 36, 47, 34, 35, 49, 39, 93, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 15, 5, 95, 48, 77, 49, 15, 97, 37, 61, 39, 87, 47, 6, 0, 0, 0, 0, 18, 4, 95, 55, 88, 15, 36, 82, 84, 39, 63, 37, 49, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 11, 136, 207, 128, 207, 129, 206, 191, 207, 130, 28, 0, 0, 11, 6, 95, 35, 206, 191, 207, 130, 39, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 142, 206, 184, 206, 177, 206, 181, 206, 175, 207, 131, 206, 177, 206, 185, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 207, 131, 206, 177, 207, 130, 72, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 15, 48, 34, 6, 39, 47, 0, 0, 0, 0, 7, 132, 206, 191, 206, 185, 72, 11, 3, 226, 130, 172, 36, 82, 34, 6, 39, 0, 0, 0, 0, 0, 0, 13, 3, 95, 50, 15, 84, 6, 36, 81, 47, 36, 34, 0, 0, 13, 138, 206, 181, 206, 175, 207, 131, 206, 177, 206, 185, 72, 0, 0, 0, 0, 17, 142, 206, 189, 206, 177, 206, 181, 206, 175, 207, 131, 206, 177, 206, 185, 72, 18, 4, 95, 53, 67, 15, 48, 36, 70, 35, 49, 39, 93, 39, 87, 47, 6, 0, 0, 0, 0, 11, 3, 95, 51, 15, 47, 34, 6, 37, 47, 0, 9, 4, 95, 15, 18, 4, 39, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 51, 6, 47, 34, 6, 37, 87, 0, 0, 0, 0, 0, 15, 140, 207, 128, 206, 177, 207, 129, 207, 140, 206, 187, 206, 191, 8, 8, 4, 95, 35, 206, 183, 37, 0, 0, 0, 0, 12, 3, 95, 53, 15, 48, 6, 36, 63, 48, 47, 0, 0, 14, 3, 95, 52, 6, 47, 6, 36, 87, 36, 34, 37, 87, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 54, 15, 6, 36, 49, 47, 0, 0, 0, 0, 19, 144, 206, 184, 206, 177, 206, 173, 207, 135, 206, 191, 207, 133, 206, 188, 206, 181, 72, 0, 0, 0, 0, 0, 12, 3, 95, 55, 15, 6, 36, 82, 84, 39, 63, 0, 0, 0, 0, 0, 0, 8, 4, 95, 35, 206, 191, 39, 0, 0, 0, 0, 14, 3, 95, 48, 15, 63, 37, 84, 36, 50, 37, 49, 6, 0, 0, 0, 0, 14, 3, 95, 51, 88, 47, 34, 37, 6, 35, 50, 70, 35, 0, 0, 14, 3, 95, 48, 67, 36, 49, 35, 47, 6, 39, 50, 10, 0, 0, 0, 0, 0, 11, 3, 95, 57, 15, 6, 36, 50, 35, 47, 0, 0, 9, 134, 206, 173, 207, 135, 207, 137, 72, 0, 0, 0, 14, 3, 95, 49, 67, 36, 49, 35, 47, 6, 39, 50, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 50, 67, 84, 38, 35, 49, 6, 39, 93, 35, 10, 0, 0, 18, 4, 95, 54, 67, 15, 36, 49, 87, 35, 49, 39, 93, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 13, 3, 95, 49, 49, 6, 36, 50, 84, 36, 49, 35, 0, 0, 0, 16, 3, 95, 51, 67, 47, 34, 37, 35, 49, 6, 39, 93, 35, 10, 0, 0, 13, 4, 95, 49, 88, 15, 84, 6, 36, 49, 35, 47, 0, 13, 3, 95, 49, 50, 84, 6, 39, 84, 36, 49, 35, 0, 0, 0, 0, 13, 3, 95, 52, 15, 47, 6, 36, 47, 35, 34, 47, 0, 0, 9, 134, 206, 188, 206, 191, 207, 133, 72, 0, 0, 16, 3, 95, 55, 88, 36, 69, 70, 39, 63, 6, 37, 50, 70, 35, 0, 0, 17, 3, 95, 52, 67, 47, 36, 47, 34, 35, 49, 6, 39, 93, 35, 10, 0, 0, 13, 6, 207, 129, 206, 185, 206, 177, 34, 98, 38, 35, 0, 0, 0, 0, 0, 9, 134, 206, 173, 206, 189, 206, 177, 72, 0, 0, 0, 17, 3, 95, 53, 67, 48, 36, 50, 70, 35, 49, 6, 39, 93, 35, 10, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 88, 84, 6, 36, 49, 35, 0, 0, 16, 3, 95, 54, 67, 36, 49, 87, 35, 49, 6, 39, 93, 35, 10, 0, 0, 17, 142, 206, 184, 206, 177, 206, 173, 207, 135, 206, 191, 207, 133, 206, 189, 72, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 88, 6, 37, 49, 39, 87, 37, 0, 0, 16, 3, 95, 55, 67, 36, 48, 47, 35, 49, 6, 39, 93, 35, 10, 0, 0, 0, 0, 0, 11, 3, 95, 56, 15, 6, 39, 98, 84, 39, 0, 0, 0, 0, 0, 16, 3, 95, 56, 67, 39, 49, 47, 35, 49, 6, 39, 93, 35, 10, 0, 0, 0, 0, 0, 0, 9, 134, 206, 188, 206, 175, 206, 177, 72, 0, 0, 14, 3, 95, 52, 88, 87, 35, 34, 6, 35, 50, 70, 35, 0, 0, 17, 142, 206, 184, 206, 177, 206, 173, 207, 135, 206, 181, 206, 185, 207, 130, 72, 15, 3, 95, 57, 67, 36, 65, 35, 49, 6, 39, 93, 35, 10, 0, 0, 0, 0, 0, 12, 136, 207, 128, 206, 177, 207, 129, 206, 172, 72, 28, 0, 13, 138, 206, 174, 207, 131, 206, 191, 207, 133, 206, 189, 72, 0, 0, 14, 3, 95, 53, 88, 48, 36, 50, 6, 37, 50, 70, 35, 0, 0, 0, 13, 138, 206, 188, 206, 173, 207, 135, 207, 129, 206, 185, 28, 18, 4, 95, 55, 67, 15, 36, 48, 47, 35, 49, 39, 93, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 54, 88, 36, 49, 87, 6, 37, 50, 70, 35, 0, 0, 0, 13, 4, 95, 50, 88, 15, 37, 49, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 56, 88, 39, 79, 70, 6, 39, 50, 70, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 57, 88, 36, 50, 36, 50, 6, 37, 50, 70, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 206, 181, 207, 128, 206, 175, 72, 0, 0, 9, 134, 207, 132, 206, 191, 207, 133, 72, 13, 138, 206, 173, 207, 135, 206, 191, 207, 133, 206, 189, 72, 13, 138, 206, 174, 206, 188, 206, 191, 207, 133, 206, 189, 72, 9, 134, 207, 132, 206, 191, 207, 133, 72, 0, 0, 11, 136, 207, 131, 207, 132, 206, 191, 207, 133, 72, 0, 0, 17, 142, 206, 189, 206, 177, 206, 173, 207, 135, 206, 191, 207, 133, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 4, 95, 56, 67, 15, 39, 49, 47, 35, 49, 39, 93, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 4, 95, 48, 77, 50, 36, 49, 35, 47, 39, 63, 6, 37, 34, 37, 35, 0, 0, 21, 4, 95, 48, 77, 51, 84, 37, 87, 36, 49, 35, 47, 39, 63, 6, 37, 34, 37, 35, 0, 0, 0, 15, 4, 95, 48, 77, 49, 97, 37, 61, 6, 35, 84, 36, 87, 0, 0, 0, 0, 0, 7, 132, 207, 131, 206, 181, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 207, 132, 206, 191, 206, 189, 72, 0, 0, 11, 136, 207, 131, 207, 132, 206, 191, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 6, 206, 188, 206, 185, 206, 177, 63, 65, 35, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 4, 95, 57, 67, 15, 36, 50, 36, 35, 49, 39, 93, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 4, 95, 52, 88, 15, 47, 36, 87, 87, 35, 34, 35, 49, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 136, 206, 177, 206, 187, 206, 187, 206, 172, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 136, 206, 188, 206, 173, 207, 131, 206, 177, 72, 28, 15, 140, 206, 181, 206, 175, 207, 135, 206, 177, 207, 132, 206, 181, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 207, 132, 206, 185, 207, 130, 72, 0, 0, 11, 136, 207, 131, 207, 132, 206, 185, 207, 130, 72, 0, 0, 0, 13, 138, 206, 179, 206, 185, 206, 177, 207, 132, 206, 175, 8, 0, 11, 136, 207, 132, 206, 191, 207, 133, 207, 130, 72, 11, 136, 207, 132, 206, 191, 207, 133, 207, 130, 72, 0, 0, 13, 138, 207, 131, 207, 132, 206, 191, 207, 133, 207, 130, 72, 0, 0, 0, 0, 0, 8, 132, 206, 188, 206, 181, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 136, 206, 188, 206, 177, 206, 182, 206, 175, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 53, 88, 15, 48, 36, 70, 37, 49, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 142, 206, 184, 206, 177, 206, 173, 207, 135, 206, 181, 207, 132, 206, 181, 72, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 206, 181, 206, 175, 206, 189, 206, 177, 206, 185, 72, 0, 0, 0, 0, 17, 142, 206, 189, 206, 177, 206, 181, 206, 175, 206, 189, 206, 177, 206, 185, 72, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 206, 183, 6, 37, 47, 35, 0, 0, 0, 13, 138, 206, 181, 206, 175, 207, 135, 206, 181, 207, 130, 72, 0, 0, 0, 0, 0, 16, 3, 95, 206, 174, 4, 37, 47, 35, 47, 6, 39, 50, 39, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 54, 88, 15, 36, 49, 87, 37, 49, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 206, 181, 206, 189, 207, 140, 207, 130, 72, 0, 0, 32, 10, 206, 181, 206, 186, 207, 132, 207, 140, 207, 130, 36, 49, 47, 6, 39, 87, 36, 4, 35, 50, 0, 8, 81, 206, 181, 206, 172, 206, 189, 32, 0, 11, 136, 206, 173, 207, 135, 206, 181, 206, 185, 72, 0, 22, 12, 206, 188, 206, 185, 206, 181, 207, 129, 207, 140, 207, 130, 63, 37, 36, 34, 6, 39, 87, 0, 0, 0, 0, 15, 140, 206, 189, 206, 177, 206, 173, 207, 135, 206, 181, 206, 185, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 5, 95, 51, 77, 49, 15, 47, 34, 37, 87, 97, 37, 61, 39, 87, 47, 6, 0, 0, 0, 0, 0, 7, 2, 207, 134, 81, 37, 0, 15, 5, 95, 49, 77, 49, 15, 97, 37, 61, 39, 87, 47, 6, 0, 0, 7, 2, 207, 135, 97, 37, 0, 0, 8, 2, 207, 132, 47, 35, 81, 0, 14, 3, 95, 206, 191, 6, 39, 63, 37, 49, 34, 39, 50, 0, 0, 13, 2, 207, 133, 6, 37, 48, 87, 37, 55, 39, 50, 0, 0, 11, 2, 207, 130, 87, 6, 37, 98, 63, 35, 0, 0, 11, 2, 207, 131, 87, 6, 37, 98, 63, 35, 0, 0, 7, 2, 207, 128, 48, 37, 0, 7, 132, 206, 181, 206, 186, 72, 0, 7, 2, 207, 129, 51, 39, 0, 0, 0, 17, 2, 207, 142, 39, 63, 4, 36, 98, 35, 47, 6, 39, 50, 39, 87, 0, 0, 19, 2, 207, 141, 4, 37, 48, 87, 37, 55, 39, 50, 47, 6, 39, 50, 39, 87, 0, 0, 19, 2, 207, 140, 4, 39, 63, 37, 49, 34, 39, 50, 47, 6, 39, 50, 39, 87, 0, 0, 13, 2, 207, 139, 6, 37, 48, 87, 37, 55, 39, 50, 0, 0, 10, 2, 207, 138, 37, 6, 39, 47, 35, 0, 0, 11, 2, 207, 137, 39, 63, 6, 36, 98, 35, 0, 0, 8, 2, 207, 136, 48, 87, 37, 0, 0, 0, 0, 0, 17, 142, 206, 184, 206, 177, 206, 181, 206, 175, 206, 189, 206, 177, 206, 185, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 2, 206, 175, 37, 4, 39, 47, 35, 47, 6, 39, 50, 39, 87, 0, 0, 16, 2, 206, 174, 4, 37, 47, 35, 47, 6, 39, 50, 39, 87, 0, 14, 6, 130, 206, 174, 72, 8, 0, 19, 2, 206, 173, 4, 36, 48, 87, 37, 55, 39, 50, 47, 6, 39, 50, 39, 87, 0, 0, 16, 2, 206, 172, 4, 35, 55, 81, 35, 47, 6, 39, 50, 39, 87, 0, 0, 0, 0, 0, 0, 10, 2, 206, 183, 6, 37, 47, 35, 0, 14, 7, 2, 206, 183, 37, 0, 72, 0, 9, 2, 206, 182, 86, 37, 47, 35, 0, 0, 13, 2, 206, 181, 6, 36, 48, 87, 37, 55, 39, 50, 0, 0, 10, 2, 206, 180, 84, 36, 55, 47, 35, 0, 0, 9, 2, 206, 179, 98, 35, 63, 35, 0, 0, 11, 2, 95, 46, 47, 36, 55, 6, 37, 35, 0, 9, 2, 206, 178, 82, 37, 47, 35, 0, 13, 138, 206, 173, 207, 135, 206, 181, 206, 185, 207, 130, 72, 11, 2, 95, 46, 47, 36, 55, 6, 37, 35, 0, 0, 9, 2, 206, 177, 35, 55, 81, 35, 0, 0, 10, 2, 95, 44, 49, 6, 39, 63, 35, 0, 19, 2, 206, 176, 4, 37, 48, 87, 37, 55, 39, 50, 47, 6, 39, 50, 39, 87, 0, 0, 14, 2, 206, 191, 6, 39, 63, 37, 49, 34, 39, 50, 0, 14, 11, 136, 206, 181, 206, 175, 207, 135, 206, 181, 72, 7, 2, 206, 191, 39, 0, 72, 10, 2, 95, 51, 47, 34, 6, 37, 35, 0, 0, 8, 2, 206, 190, 49, 87, 37, 0, 17, 142, 206, 189, 206, 177, 206, 173, 207, 135, 206, 181, 206, 185, 207, 130, 72, 9, 2, 95, 50, 84, 6, 37, 39, 0, 0, 7, 2, 206, 189, 50, 37, 0, 9, 2, 95, 49, 6, 36, 50, 35, 0, 0, 7, 2, 206, 188, 63, 37, 0, 11, 2, 95, 48, 63, 37, 84, 6, 36, 50, 0, 0, 10, 2, 206, 187, 55, 35, 63, 84, 35, 0, 11, 136, 206, 181, 206, 175, 207, 135, 206, 177, 72, 10, 2, 95, 55, 36, 48, 47, 6, 35, 0, 0, 9, 2, 206, 186, 49, 35, 48, 35, 0, 10, 2, 95, 54, 6, 36, 49, 87, 37, 0, 0, 10, 2, 206, 185, 37, 6, 39, 47, 35, 0, 11, 2, 95, 53, 48, 6, 36, 50, 47, 36, 0, 0, 9, 2, 206, 184, 85, 37, 47, 35, 0, 12, 2, 95, 52, 47, 6, 36, 87, 36, 34, 35, 0, 0, 0, 0, 10, 2, 95, 57, 36, 50, 6, 36, 35, 0, 0, 10, 2, 95, 56, 39, 49, 47, 6, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 206, 177, 207, 128, 207, 140, 72, 0, 0, 0, 21, 6, 206, 179, 206, 185, 206, 177, 57, 35, 50, 6, 35, 0, 72, 81, 206, 189, 206, 177, 32, 9, 134, 206, 179, 206, 185, 206, 177, 8, 0, 0, 0, 0, 11, 136, 207, 128, 206, 181, 207, 129, 206, 175, 28, 0, 10, 134, 206, 180, 206, 185, 206, 172, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 56, 88, 15, 39, 98, 84, 118, 49, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 206, 184, 206, 177, 206, 173, 207, 135, 206, 181, 206, 185, 72, 0, 0, 17, 142, 206, 184, 206, 177, 206, 181, 206, 175, 206, 188, 206, 177, 206, 185, 72, 0, 0, 0, 0, 17, 142, 206, 181, 206, 175, 206, 188, 206, 177, 207, 131, 207, 132, 206, 181, 72, 0, 0, 0, 0, 21, 146, 206, 189, 206, 177, 206, 181, 206, 175, 206, 188, 206, 177, 207, 131, 207, 132, 206, 181, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 134, 206, 181, 206, 185, 207, 130, 72, 28, 0, 0, 0, 7, 132, 206, 184, 206, 177, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 57, 88, 15, 36, 50, 36, 50, 37, 49, 39, 87, 47, 6, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 207, 132, 206, 183, 207, 130, 72, 0, 0, 11, 136, 207, 131, 207, 132, 206, 183, 207, 130, 72, 11, 136, 206, 188, 206, 175, 206, 177, 207, 130, 72, 11, 136, 206, 173, 206, 189, 206, 177, 207, 130, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 207, 132, 206, 183, 206, 189, 72, 0, 0, 11, 136, 207, 131, 207, 132, 206, 183, 206, 189, 72, 11, 136, 206, 173, 206, 189, 206, 177, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 132, 206, 177, 206, 189, 72, 8, 0, 0, 6, 18, 66, 206, 177, 206, 185, 0, 206, 191, 206, 185, 0, 206, 181, 206, 185, 0, 206, 177, 206, 175, 0, 206, 191, 206, 175, 0, 206, 181, 206, 175, 0, 206, 181, 0, 206, 185, 0, 206, 183, 0, 207, 133, 0, 206, 173, 0, 206, 175, 0, 206, 174, 0, 207, 141, 0, 7, 6, 1, 61, 0, 3, 69, 0, 7, 6, 1, 50, 0, 207, 141, 2, 17, 66, 3, 6, 35, 81, 0, 207, 141, 3, 6, 35, 82, 0, 206, 175, 3, 6, 36, 0, 3, 35, 0, 207, 133, 2, 17, 66, 3, 35, 81, 0, 207, 133, 3, 35, 82, 0, 206, 185, 3, 36, 0, 4, 206, 183, 3, 115, 0, 207, 138, 0, 7, 6, 1, 51, 0, 2, 206, 178, 3, 0, 3, 82, 0, 7, 6, 1, 52, 0, 4, 2, 18, 66, 3, 57, 0, 206, 177, 206, 185, 2, 17, 65, 0, 206, 181, 2, 17, 65, 0, 206, 181, 206, 185, 2, 17, 65, 0, 206, 183, 2, 17, 65, 0, 206, 185, 2, 17, 65, 0, 206, 191, 206, 185, 2, 17, 65, 0, 207, 133, 2, 17, 65, 0, 2, 207, 135, 3, 66, 0, 4, 206, 179, 1, 17, 65, 3, 66, 79, 0, 206, 186, 1, 17, 65, 0, 4, 206, 179, 3, 79, 0, 206, 186, 0, 3, 98, 0, 7, 6, 1, 53, 0, 2, 206, 180, 3, 0, 3, 84, 0, 7, 6, 1, 54, 0, 4, 207, 141, 2, 206, 178, 3, 6, 36, 0, 207, 141, 2, 207, 134, 0, 207, 141, 2, 17, 66, 3, 6, 36, 81, 0, 207, 141, 3, 6, 36, 82, 0, 206, 175, 3, 6, 37, 0, 4, 3, 36, 0, 207, 133, 2, 206, 178, 0, 207, 133, 2, 207, 134, 0, 207, 133, 2, 17, 66, 3, 36, 81, 0, 207, 133, 3, 36, 82, 0, 206, 185, 3, 37, 0, 206, 185, 1, 17, 67, 2, 17, 65, 3, 97, 0, 7, 6, 1, 55, 0, 2, 206, 182, 3, 0, 3, 86, 0, 4, 206, 181, 206, 185, 2, 17, 65, 3, 86, 57, 0, 206, 183, 2, 17, 65, 0, 206, 185, 2, 17, 65, 0, 206, 191, 206, 185, 2, 17, 65, 0, 207, 133, 2, 17, 65, 0, 7, 6, 1, 56, 0, 3, 37, 0, 207, 133, 2, 17, 66, 3, 37, 81, 0, 207, 133, 3, 37, 82, 0, 7, 6, 1, 57, 0, 2, 206, 184, 3, 0, 3, 85, 0, 7, 6, 1, 58, 0, 4, 3, 37, 0, 1, 129, 207, 2, 17, 65, 0, 2, 206, 181, 0, 1, 180, 206, 2, 206, 177, 32, 3, 57, 0, 4, 1, 128, 207, 2, 17, 65, 3, 97, 0, 1, 132, 207, 2, 206, 145, 0, 1, 132, 207, 2, 206, 145, 0, 1, 186, 206, 2, 206, 145, 0, 7, 6, 1, 59, 0, 2, 206, 186, 3, 0, 3, 49, 0, 4, 2, 17, 71, 3, 78, 0, 2, 206, 177, 206, 175, 0, 2, 206, 177, 206, 185, 0, 2, 206, 191, 206, 175, 0, 2, 206, 191, 206, 185, 0, 206, 181, 206, 185, 2, 17, 65, 0, 206, 183, 2, 17, 65, 0, 206, 185, 2, 17, 65, 0, 206, 191, 206, 185, 2, 17, 65, 0, 207, 133, 2, 17, 65, 0, 1, 32, 189, 206, 3, 79, 0, 7, 6, 1, 60, 0, 2, 206, 187, 3, 0, 3, 55, 0, 4, 206, 181, 206, 185, 2, 17, 65, 3, 61, 0, 206, 183, 2, 17, 65, 0, 206, 185, 2, 17, 65, 0, 206, 191, 206, 185, 2, 17, 65, 0, 207, 133, 2, 17, 65, 0, 7, 6, 1, 61, 0, 4, 1, 17, 65, 2, 206, 188, 3, 0, 2, 207, 128, 3, 0, 3, 63, 0, 7, 6, 1, 62, 0, 2, 206, 189, 3, 0, 4, 3, 50, 0, 2, 32, 206, 186, 206, 177, 206, 185, 32, 0, 4, 2, 32, 207, 128, 3, 63, 0, 2, 32, 207, 136, 0, 4, 206, 181, 206, 185, 2, 17, 65, 3, 65, 0, 206, 183, 2, 17, 65, 0, 206, 185, 2, 17, 65, 0, 206, 191, 206, 185, 2, 17, 65, 0, 207, 133, 2, 17, 65, 0, 4, 2, 32, 206, 186, 3, 66, 0, 2, 32, 206, 190, 0, 207, 132, 3, 70, 0, 7, 6, 1, 63, 0, 2, 206, 190, 3, 0, 3, 49, 87, 0, 1, 32, 189, 206, 3, 79, 86, 0, 7, 6, 1, 64, 0, 206, 175, 3, 6, 37, 0, 207, 141, 3, 6, 40, 0, 206, 185, 3, 37, 0, 3, 39, 0, 207, 133, 3, 40, 0, 4, 206, 183, 3, 118, 0, 207, 138, 0, 7, 6, 1, 65, 0, 2, 207, 128, 3, 0, 3, 48, 0, 4, 1, 32, 189, 206, 3, 69, 0, 1, 188, 206, 0, 7, 6, 1, 66, 0, 4, 3, 34, 0, 1, 17, 65, 2, 17, 65, 0, 1, 17, 67, 0, 1, 133, 207, 177, 206, 0, 1, 133, 207, 181, 206, 0, 1, 133, 207, 183, 206, 0, 1, 141, 207, 177, 206, 0, 1, 141, 207, 181, 206, 0, 1, 141, 207, 183, 206, 0, 207, 129, 0, 7, 6, 1, 67, 0, 2, 32, 17, 67, 3, 86, 0, 4, 3, 87, 0, 2, 32, 17, 66, 0, 7, 6, 1, 68, 0, 3, 87, 0, 4, 206, 181, 206, 185, 2, 17, 65, 3, 87, 57, 0, 206, 183, 2, 17, 65, 0, 206, 185, 2, 17, 65, 0, 206, 191, 206, 185, 2, 17, 65, 0, 207, 133, 2, 17, 65, 0, 7, 6, 1, 69, 0, 2, 207, 132, 3, 0, 3, 47, 0, 1, 32, 189, 206, 3, 70, 0, 4, 206, 182, 3, 70, 86, 0, 207, 131, 1, 32, 189, 206, 0, 207, 131, 3, 121, 0, 7, 6, 1, 70, 0, 206, 175, 3, 6, 37, 0, 4, 3, 37, 0, 206, 185, 0, 7, 6, 1, 71, 0, 2, 207, 134, 3, 0, 3, 81, 0, 7, 6, 1, 72, 0, 4, 2, 17, 71, 3, 97, 0, 2, 206, 177, 206, 175, 0, 2, 206, 177, 206, 185, 0, 2, 206, 191, 206, 175, 0, 2, 206, 191, 206, 185, 0, 206, 181, 206, 185, 2, 17, 65, 0, 206, 183, 2, 17, 65, 0, 206, 185, 2, 17, 65, 0, 206, 191, 206, 185, 2, 17, 65, 0, 207, 133, 2, 17, 65, 0, 3, 99, 0, 7, 6, 1, 73, 0, 2, 207, 136, 3, 0, 3, 48, 87, 0, 1, 32, 189, 206, 3, 69, 86, 0, 7, 6, 1, 74, 0, 3, 39, 0, 7, 6, 0, 33, 1, 19, 3, 0, 206, 172, 3, 6, 35, 0, 206, 173, 3, 6, 36, 0, 4, 206, 174, 3, 6, 37, 0, 206, 175, 0, 206, 176, 0, 207, 141, 0, 4, 207, 140, 3, 6, 39, 0, 207, 142, 0, 4, 206, 172, 206, 183, 3, 6, 115, 0, 206, 172, 206, 185, 0, 4, 207, 140, 206, 183, 3, 6, 118, 0, 207, 140, 206, 185, 0, 4, 207, 138, 3, 37, 0, 207, 139, 0, 46, 3, 47, 36, 55, 6, 37, 35, 0, 44, 2, 15, 3, 49, 6, 39, 63, 35, 0, 33, 3, 85, 35, 82, 63, 35, 87, 47, 37, 49, 6, 39, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts13 = FileInMemory_createWithData (5351, reinterpret_cast (&espeakdata_dicts13_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/el_dict", L"el"); Collection_addItem (me.peek(), espeakdata_dicts13.transfer()); static unsigned char espeakdata_dicts14_data[93423] = { 0, 4, 0, 0, 131, 188, 0, 0, 13, 69, 65, 33, 67, 37, 48, 48, 34, 136, 87, 127, 0, 0, 14, 70, 56, 21, 83, 20, 19, 64, 50, 128, 86, 139, 63, 0, 0, 17, 71, 52, 16, 203, 20, 230, 137, 20, 63, 13, 49, 119, 50, 86, 37, 0, 0, 12, 68, 76, 81, 213, 20, 87, 119, 79, 58, 136, 0, 21, 72, 52, 83, 1, 56, 50, 15, 49, 144, 63, 119, 55, 117, 50, 49, 122, 55, 37, 0, 103, 20, 72, 52, 83, 1, 56, 50, 15, 49, 144, 63, 119, 55, 117, 50, 49, 13, 55, 37, 0, 11, 200, 24, 244, 133, 76, 128, 68, 61, 112, 66, 10, 68, 21, 148, 137, 20, 139, 34, 37, 0, 0, 14, 69, 52, 147, 4, 21, 112, 63, 120, 55, 70, 57, 132, 0, 12, 68, 32, 20, 212, 100, 105, 136, 87, 47, 120, 0, 0, 11, 65, 4, 35, 55, 35, 0, 81, 108, 97, 32, 16, 65, 4, 117, 15, 58, 135, 55, 0, 81, 119, 104, 105, 108, 101, 32, 12, 69, 12, 243, 142, 61, 32, 49, 122, 50, 112, 0, 16, 70, 80, 244, 142, 4, 67, 192, 47, 130, 50, 6, 136, 70, 134, 0, 13, 69, 80, 129, 83, 37, 48, 85, 127, 87, 120, 87, 0, 19, 65, 4, 35, 49, 117, 11, 0, 85, 46, 32, 107, 32, 46, 32, 97, 32, 46, 32, 6, 65, 4, 136, 0, 14, 4, 193, 4, 34, 0, 11, 67, 84, 225, 15, 123, 50, 70, 6, 132, 0, 14, 70, 61, 85, 23, 5, 33, 0, 133, 47, 58, 112, 70, 0, 19, 71, 52, 21, 83, 60, 193, 85, 52, 63, 128, 87, 13, 6, 55, 127, 13, 63, 0, 16, 70, 12, 243, 150, 20, 229, 0, 49, 122, 50, 82, 13, 50, 47, 0, 13, 69, 5, 0, 67, 32, 80, 117, 48, 35, 74, 37, 0, 0, 0, 10, 68, 72, 81, 83, 20, 34, 127, 87, 0, 11, 68, 37, 48, 65, 12, 135, 87, 13, 49, 0, 13, 68, 9, 86, 15, 52, 69, 123, 49, 87, 13, 63, 0, 21, 72, 4, 229, 9, 80, 129, 83, 37, 48, 35, 50, 47, 6, 120, 85, 13, 87, 120, 87, 0, 0, 14, 69, 8, 84, 140, 36, 224, 69, 126, 55, 6, 120, 50, 0, 13, 69, 72, 83, 9, 76, 128, 34, 119, 55, 111, 89, 0, 11, 67, 13, 144, 78, 87, 135, 6, 35, 50, 0, 15, 69, 12, 243, 150, 20, 224, 49, 122, 50, 82, 6, 127, 50, 0, 23, 73, 12, 243, 80, 21, 66, 84, 36, 243, 128, 49, 122, 63, 48, 13, 47, 6, 120, 89, 13, 50, 0, 6, 65, 8, 69, 127, 0, 0, 16, 70, 4, 229, 9, 29, 80, 64, 35, 50, 47, 6, 127, 79, 13, 0, 15, 70, 88, 17, 213, 21, 53, 0, 82, 136, 79, 13, 87, 47, 0, 14, 70, 76, 227, 207, 44, 84, 128, 87, 50, 132, 49, 112, 0, 15, 70, 61, 85, 12, 36, 84, 128, 6, 133, 47, 55, 4, 143, 0, 15, 70, 36, 51, 206, 8, 20, 128, 135, 49, 122, 50, 69, 125, 0, 15, 70, 12, 21, 5, 72, 84, 128, 49, 136, 47, 112, 34, 112, 0, 0, 6, 195, 85, 64, 192, 17, 14, 67, 21, 64, 192, 119, 47, 6, 87, 119, 47, 34, 13, 0, 0, 10, 67, 12, 17, 133, 49, 35, 81, 136, 0, 0, 12, 69, 16, 145, 83, 20, 192, 70, 127, 86, 116, 0, 17, 70, 4, 224, 76, 101, 50, 83, 117, 50, 35, 55, 13, 87, 120, 87, 0, 6, 65, 12, 87, 127, 0, 0, 9, 198, 4, 193, 201, 21, 36, 192, 66, 16, 70, 76, 83, 148, 36, 83, 148, 87, 119, 50, 47, 139, 50, 47, 0, 0, 19, 71, 21, 132, 5, 73, 66, 83, 20, 119, 49, 87, 48, 112, 47, 6, 127, 86, 0, 14, 4, 95, 8, 1, 3, 105, 6, 35, 74, 4, 119, 49, 0, 0, 12, 68, 85, 48, 71, 20, 57, 132, 87, 111, 73, 0, 0, 13, 69, 53, 84, 141, 85, 32, 63, 146, 63, 112, 0, 105, 12, 69, 53, 84, 141, 85, 32, 63, 126, 63, 112, 0, 13, 69, 8, 19, 12, 61, 64, 69, 35, 55, 13, 47, 0, 6, 65, 16, 70, 127, 0, 0, 15, 70, 65, 81, 82, 36, 193, 64, 48, 57, 141, 34, 116, 0, 103, 14, 70, 72, 82, 78, 36, 225, 192, 34, 136, 50, 120, 66, 0, 17, 70, 36, 224, 197, 57, 49, 64, 120, 50, 87, 6, 119, 50, 87, 0, 36, 0, 16, 70, 64, 20, 211, 21, 32, 153, 48, 35, 87, 112, 69, 6, 135, 0, 19, 71, 36, 212, 18, 20, 50, 83, 20, 120, 63, 48, 34, 120, 87, 6, 135, 87, 0, 20, 71, 4, 35, 210, 36, 114, 78, 20, 35, 69, 13, 34, 6, 120, 73, 13, 50, 37, 0, 0, 12, 68, 29, 84, 149, 76, 79, 132, 34, 132, 86, 0, 12, 68, 24, 198, 66, 100, 81, 55, 135, 69, 135, 0, 0, 8, 197, 52, 81, 21, 76, 16, 66, 15, 69, 37, 64, 76, 36, 16, 120, 47, 6, 35, 55, 111, 13, 0, 18, 70, 5, 48, 133, 77, 67, 211, 35, 87, 69, 6, 119, 87, 47, 13, 87, 0, 21, 65, 20, 81, 130, 119, 79, 86, 6, 118, 63, 48, 116, 0, 83, 46, 32, 103, 32, 46, 32, 5, 65, 20, 127, 0, 0, 14, 70, 52, 147, 12, 36, 243, 128, 63, 120, 55, 139, 50, 0, 15, 70, 8, 148, 195, 84, 149, 0, 69, 120, 87, 49, 120, 47, 0, 0, 17, 70, 36, 225, 21, 77, 68, 153, 120, 50, 70, 123, 87, 47, 34, 120, 0, 0, 12, 68, 56, 147, 138, 4, 50, 120, 50, 73, 13, 0, 15, 70, 52, 85, 1, 64, 131, 210, 63, 119, 47, 13, 81, 130, 0, 13, 68, 4, 69, 76, 80, 35, 70, 123, 55, 47, 0, 135, 0, 15, 69, 16, 210, 84, 72, 144, 70, 13, 63, 127, 47, 34, 37, 0, 8, 197, 52, 86, 9, 12, 240, 65, 14, 69, 32, 21, 193, 36, 144, 105, 13, 58, 6, 135, 127, 0, 13, 69, 17, 84, 136, 4, 208, 70, 123, 34, 13, 63, 0, 13, 69, 72, 80, 129, 80, 80, 34, 127, 69, 136, 47, 0, 13, 69, 64, 148, 129, 80, 80, 48, 135, 34, 13, 47, 0, 14, 69, 52, 18, 143, 72, 16, 63, 117, 73, 131, 34, 13, 0, 14, 69, 44, 20, 129, 80, 80, 49, 13, 34, 124, 47, 37, 0, 13, 69, 4, 84, 129, 80, 80, 138, 34, 6, 136, 47, 0, 6, 65, 24, 119, 81, 0, 0, 17, 70, 65, 33, 84, 21, 133, 0, 48, 34, 127, 106, 119, 49, 87, 47, 0, 0, 17, 71, 5, 32, 200, 36, 32, 76, 16, 125, 74, 120, 69, 128, 55, 70, 0, 19, 67, 92, 147, 132, 58, 6, 135, 50, 70, 15, 6, 123, 48, 0, 81, 117, 112, 32, 23, 67, 92, 147, 132, 58, 6, 120, 50, 70, 15, 48, 6, 133, 112, 0, 81, 112, 111, 119, 101, 114, 32, 11, 67, 92, 147, 132, 58, 135, 50, 70, 0, 36, 0, 9, 67, 16, 243, 133, 70, 123, 50, 0, 18, 72, 64, 130, 76, 48, 148, 9, 56, 80, 81, 120, 55, 111, 48, 127, 50, 0, 9, 67, 80, 243, 133, 47, 134, 50, 0, 13, 68, 20, 208, 133, 16, 119, 63, 69, 6, 119, 70, 0, 0, 14, 69, 52, 243, 129, 12, 240, 63, 122, 50, 13, 49, 134, 0, 13, 69, 72, 17, 9, 76, 128, 34, 35, 70, 120, 89, 0, 13, 69, 24, 147, 137, 80, 80, 81, 135, 50, 135, 47, 0, 14, 69, 16, 148, 205, 4, 192, 70, 120, 86, 63, 13, 55, 0, 6, 65, 28, 73, 127, 0, 0, 14, 70, 64, 197, 77, 8, 84, 128, 48, 55, 123, 63, 112, 0, 0, 17, 70, 21, 97, 82, 100, 243, 133, 119, 82, 34, 120, 58, 123, 50, 0, 106, 16, 70, 21, 97, 82, 100, 243, 133, 119, 82, 34, 120, 58, 122, 50, 0, 15, 7, 20, 8, 5, 25, 39, 12, 12, 84, 136, 55, 0, 72, 32, 13, 67, 12, 19, 128, 2, 49, 35, 50, 0, 32, 9, 12, 16, 70, 88, 20, 197, 48, 147, 133, 82, 35, 87, 13, 55, 127, 50, 0, 10, 67, 80, 243, 128, 47, 123, 50, 0, 10, 11, 67, 76, 19, 128, 4, 87, 35, 50, 0, 9, 14, 4, 95, 54, 48, 15, 87, 6, 120, 49, 87, 47, 139, 0, 0, 0, 14, 69, 44, 19, 147, 5, 48, 49, 35, 50, 86, 13, 87, 0, 13, 69, 24, 82, 83, 81, 144, 81, 135, 87, 47, 37, 0, 6, 65, 32, 136, 74, 0, 0, 16, 70, 32, 245, 83, 80, 243, 128, 105, 57, 132, 87, 47, 13, 50, 0, 17, 70, 36, 226, 5, 72, 149, 0, 120, 50, 105, 6, 119, 34, 120, 47, 0, 14, 70, 13, 84, 2, 60, 20, 132, 49, 123, 69, 13, 70, 0, 9, 198, 4, 229, 9, 28, 83, 128, 65, 0, 20, 71, 65, 33, 83, 20, 229, 12, 100, 48, 34, 119, 86, 13, 50, 47, 55, 120, 0, 32, 0, 11, 67, 4, 229, 9, 35, 50, 47, 135, 0, 103, 11, 68, 37, 33, 78, 20, 135, 34, 127, 50, 0, 12, 68, 80, 242, 217, 60, 47, 134, 49, 120, 134, 0, 10, 68, 60, 50, 18, 20, 134, 49, 112, 0, 10, 67, 36, 225, 25, 120, 50, 70, 37, 0, 8, 1, 35, 105, 35, 89, 0, 27, 0, 14, 65, 36, 2, 135, 35, 63, 0, 14, 42, 81, 97, 109, 32, 13, 65, 36, 2, 135, 117, 63, 0, 42, 81, 97, 109, 32, 9, 65, 36, 135, 0, 76, 32, 9, 42, 16, 70, 88, 84, 148, 36, 49, 83, 82, 126, 47, 120, 87, 127, 86, 0, 5, 65, 36, 135, 0, 0, 12, 67, 84, 229, 15, 4, 123, 50, 106, 115, 0, 103, 11, 67, 84, 229, 15, 4, 123, 50, 47, 115, 0, 17, 70, 37, 0, 78, 20, 208, 64, 120, 48, 117, 50, 6, 127, 63, 13, 0, 15, 70, 88, 147, 133, 100, 20, 132, 82, 120, 50, 57, 112, 70, 0, 14, 70, 76, 129, 80, 32, 84, 132, 89, 119, 48, 13, 70, 0, 16, 70, 16, 80, 146, 36, 81, 128, 70, 127, 69, 34, 6, 127, 81, 0, 13, 1, 37, 48, 146, 87, 6, 119, 50, 47, 0, 105, 27, 11, 1, 37, 48, 112, 87, 119, 50, 47, 0, 27, 0, 11, 67, 37, 68, 192, 120, 47, 87, 0, 72, 34, 13, 70, 12, 129, 83, 32, 148, 133, 74, 119, 89, 112, 0, 8, 67, 100, 84, 128, 57, 112, 0, 9, 1, 38, 10, 35, 50, 70, 0, 76, 0, 16, 70, 60, 48, 213, 64, 145, 82, 122, 49, 57, 132, 48, 135, 112, 0, 0, 24, 73, 92, 244, 139, 77, 64, 84, 36, 243, 128, 58, 6, 146, 49, 87, 47, 4, 136, 89, 13, 50, 0, 105, 23, 73, 92, 244, 139, 77, 64, 84, 36, 243, 128, 58, 6, 126, 49, 87, 47, 4, 136, 89, 13, 50, 0, 13, 69, 61, 33, 5, 4, 192, 130, 70, 6, 139, 55, 0, 16, 70, 52, 16, 200, 37, 51, 79, 63, 117, 74, 120, 86, 63, 134, 0, 18, 8, 4, 195, 169, 20, 5, 14, 20, 5, 70, 136, 47, 6, 122, 50, 47, 0, 23, 73, 12, 243, 148, 72, 20, 20, 36, 243, 128, 49, 13, 50, 47, 34, 6, 35, 48, 89, 13, 50, 0, 6, 65, 40, 73, 136, 0, 0, 15, 70, 80, 129, 82, 21, 48, 64, 47, 13, 34, 127, 86, 13, 0, 16, 70, 84, 229, 207, 84, 225, 0, 123, 50, 58, 6, 133, 50, 70, 0, 9, 198, 32, 245, 197, 88, 84, 128, 66, 0, 11, 67, 76, 148, 128, 87, 4, 146, 0, 105, 9, 10, 67, 76, 148, 128, 87, 4, 126, 0, 9, 11, 67, 16, 243, 148, 70, 134, 50, 47, 0, 9, 15, 70, 8, 245, 84, 37, 21, 69, 69, 132, 47, 6, 127, 49, 0, 17, 71, 4, 116, 133, 77, 50, 86, 20, 117, 79, 34, 119, 87, 120, 82, 0, 13, 1, 42, 35, 87, 47, 13, 34, 120, 87, 49, 0, 27, 0, 12, 68, 56, 17, 9, 4, 50, 124, 70, 57, 13, 0, 9, 1, 43, 48, 55, 123, 87, 0, 27, 0, 15, 70, 36, 195, 9, 56, 242, 83, 120, 55, 13, 50, 6, 137, 0, 12, 69, 76, 145, 206, 21, 32, 87, 135, 50, 112, 0, 16, 70, 36, 224, 207, 52, 147, 135, 120, 50, 49, 123, 63, 120, 66, 0, 16, 69, 21, 133, 18, 20, 208, 119, 49, 87, 47, 34, 6, 127, 63, 0, 6, 65, 44, 49, 136, 0, 0, 15, 70, 76, 84, 135, 20, 19, 148, 87, 125, 73, 13, 50, 47, 0, 16, 70, 61, 4, 15, 56, 83, 148, 13, 48, 134, 50, 13, 50, 47, 0, 14, 70, 16, 145, 72, 5, 33, 0, 70, 135, 105, 125, 70, 0, 0, 16, 70, 72, 83, 1, 80, 149, 133, 34, 119, 55, 13, 47, 120, 82, 0, 17, 70, 65, 83, 129, 80, 149, 133, 48, 57, 132, 50, 13, 47, 120, 82, 0, 15, 70, 56, 244, 197, 16, 149, 133, 50, 134, 86, 70, 135, 82, 0, 17, 71, 20, 229, 15, 85, 32, 71, 20, 122, 50, 106, 115, 34, 124, 88, 0, 10, 67, 5, 67, 208, 117, 47, 122, 48, 0, 0, 24, 67, 25, 35, 205, 2, 81, 34, 122, 63, 15, 58, 6, 120, 74, 0, 8, 81, 119, 104, 105, 99, 104, 32, 23, 67, 25, 35, 205, 2, 81, 34, 122, 63, 15, 58, 6, 138, 0, 8, 81, 119, 104, 101, 114, 101, 32, 12, 67, 25, 35, 205, 81, 34, 123, 63, 0, 103, 72, 11, 67, 25, 35, 205, 81, 34, 122, 63, 0, 72, 11, 68, 56, 21, 82, 84, 50, 133, 34, 132, 0, 9, 198, 20, 229, 18, 4, 147, 0, 65, 10, 67, 4, 229, 5, 35, 50, 47, 127, 0, 9, 1, 47, 87, 55, 35, 89, 0, 27, 0, 6, 65, 48, 119, 55, 0, 0, 14, 70, 80, 129, 82, 21, 49, 64, 47, 13, 34, 127, 86, 0, 9, 198, 12, 130, 78, 21, 49, 64, 66, 9, 198, 77, 81, 134, 85, 49, 64, 66, 0, 19, 71, 80, 20, 203, 24, 244, 131, 20, 47, 6, 35, 87, 49, 81, 4, 131, 87, 0, 19, 71, 36, 212, 5, 16, 19, 131, 20, 120, 63, 48, 6, 127, 70, 13, 50, 87, 0, 0, 12, 68, 56, 17, 10, 4, 50, 124, 70, 57, 13, 0, 10, 67, 28, 20, 153, 79, 35, 34, 37, 0, 12, 68, 72, 83, 9, 12, 34, 119, 55, 120, 49, 0, 13, 68, 60, 20, 197, 76, 134, 6, 136, 87, 127, 86, 0, 15, 70, 12, 130, 70, 25, 35, 206, 89, 120, 81, 34, 122, 50, 0, 0, 22, 73, 92, 129, 69, 48, 32, 82, 72, 245, 192, 58, 6, 127, 55, 10, 69, 4, 35, 34, 134, 0, 13, 69, 5, 98, 65, 73, 144, 136, 82, 139, 34, 37, 0, 6, 65, 52, 119, 63, 0, 0, 15, 70, 65, 33, 67, 37, 49, 64, 48, 34, 111, 87, 135, 87, 0, 0, 10, 199, 56, 240, 212, 85, 35, 129, 48, 66, 0, 11, 68, 100, 17, 83, 84, 57, 136, 87, 132, 0, 21, 72, 81, 32, 74, 20, 53, 15, 73, 144, 47, 34, 13, 73, 119, 49, 47, 13, 34, 120, 0, 12, 68, 77, 82, 84, 20, 87, 58, 127, 47, 0, 10, 0, 15, 69, 8, 84, 201, 16, 80, 69, 120, 87, 135, 70, 0, 74, 12, 14, 69, 32, 80, 193, 80, 80, 105, 119, 49, 13, 47, 136, 0, 11, 67, 49, 99, 214, 55, 14, 82, 122, 82, 0, 22, 73, 72, 84, 197, 73, 96, 84, 36, 243, 128, 34, 119, 86, 112, 82, 6, 136, 89, 13, 50, 0, 15, 69, 24, 81, 15, 72, 16, 81, 111, 70, 6, 131, 34, 13, 0, 23, 73, 16, 80, 204, 5, 32, 84, 36, 243, 128, 70, 119, 49, 55, 13, 6, 34, 136, 89, 13, 50, 0, 11, 5, 95, 48, 1, 14, 4, 13, 50, 0, 135, 6, 65, 56, 119, 50, 0, 0, 10, 67, 36, 225, 15, 120, 50, 70, 134, 0, 0, 20, 71, 88, 145, 201, 48, 19, 148, 20, 82, 120, 73, 111, 55, 6, 35, 50, 47, 37, 0, 9, 198, 76, 83, 73, 80, 243, 133, 65, 19, 71, 52, 20, 137, 41, 80, 78, 4, 63, 35, 34, 111, 58, 6, 124, 50, 13, 0, 17, 71, 21, 98, 76, 16, 241, 82, 76, 127, 82, 116, 70, 132, 112, 86, 0, 16, 70, 16, 240, 212, 72, 147, 133, 70, 122, 49, 47, 34, 111, 50, 0, 0, 13, 68, 72, 80, 133, 48, 34, 111, 69, 119, 55, 0, 36, 18, 72, 8, 192, 78, 12, 208, 78, 28, 80, 69, 55, 13, 63, 122, 50, 88, 0, 18, 72, 4, 195, 5, 28, 144, 78, 12, 80, 117, 55, 127, 73, 13, 50, 87, 0, 0, 14, 69, 32, 82, 193, 80, 80, 105, 119, 49, 13, 47, 136, 0, 13, 69, 8, 160, 82, 56, 80, 69, 57, 125, 50, 13, 0, 13, 69, 16, 19, 12, 5, 48, 70, 35, 55, 13, 87, 0, 5, 65, 60, 134, 0, 0, 14, 6, 19, 8, 5, 39, 12, 12, 89, 127, 55, 0, 72, 32, 10, 67, 81, 112, 83, 47, 58, 122, 86, 0, 13, 69, 61, 0, 81, 84, 80, 134, 48, 6, 136, 49, 0, 12, 1, 61, 9, 127, 49, 58, 116, 86, 9, 0, 27, 0, 16, 70, 52, 17, 5, 48, 147, 133, 63, 35, 70, 13, 55, 111, 50, 0, 10, 199, 36, 212, 5, 72, 49, 80, 80, 67, 18, 70, 16, 144, 83, 64, 244, 129, 70, 135, 6, 35, 87, 48, 13, 34, 13, 0, 0, 12, 4, 9, 20, 39, 4, 2, 120, 47, 13, 70, 0, 0, 12, 201, 16, 148, 212, 72, 144, 149, 80, 244, 128, 66, 14, 69, 16, 84, 195, 73, 144, 70, 111, 87, 49, 34, 136, 0, 9, 1, 64, 10, 35, 47, 10, 0, 76, 6, 65, 64, 48, 127, 0, 0, 15, 6, 20, 8, 1, 20, 39, 4, 2, 84, 35, 47, 13, 70, 0, 15, 70, 80, 129, 82, 21, 67, 192, 4, 84, 138, 6, 47, 132, 0, 9, 198, 65, 33, 83, 20, 229, 0, 36, 17, 70, 65, 33, 83, 20, 229, 0, 48, 34, 119, 86, 13, 50, 47, 0, 9, 15, 70, 61, 3, 211, 77, 83, 64, 13, 48, 122, 87, 13, 63, 0, 0, 10, 67, 8, 193, 72, 69, 55, 119, 105, 0, 0, 0, 13, 69, 76, 145, 206, 85, 0, 87, 135, 50, 123, 48, 0, 18, 70, 4, 224, 76, 101, 49, 83, 35, 50, 13, 55, 135, 86, 121, 86, 0, 36, 17, 70, 4, 224, 76, 101, 49, 83, 117, 50, 35, 55, 13, 87, 127, 86, 0, 7, 65, 68, 49, 57, 132, 0, 0, 20, 67, 80, 130, 83, 84, 6, 120, 87, 58, 4, 122, 50, 0, 33, 81, 111, 110, 101, 32, 12, 67, 80, 130, 83, 84, 120, 87, 0, 76, 34, 33, 17, 70, 52, 243, 148, 4, 224, 64, 63, 122, 50, 47, 6, 35, 50, 13, 0, 15, 70, 64, 148, 129, 56, 128, 64, 48, 13, 34, 124, 50, 13, 0, 15, 70, 64, 17, 197, 4, 229, 0, 48, 35, 73, 13, 50, 47, 0, 16, 70, 12, 130, 77, 21, 32, 64, 49, 135, 63, 6, 139, 34, 13, 0, 16, 70, 4, 64, 77, 4, 229, 0, 35, 70, 13, 63, 13, 50, 47, 0, 0, 15, 70, 81, 33, 65, 80, 148, 197, 47, 34, 127, 47, 120, 86, 0, 0, 11, 67, 80, 129, 77, 4, 84, 119, 63, 0, 9, 26, 68, 76, 19, 148, 4, 87, 6, 35, 50, 47, 13, 15, 49, 55, 6, 128, 86, 0, 81, 99, 108, 97, 117, 115, 32, 11, 68, 61, 48, 193, 72, 122, 87, 49, 112, 0, 11, 68, 17, 80, 78, 20, 70, 58, 136, 50, 0, 10, 68, 93, 34, 84, 32, 34, 135, 84, 0, 13, 68, 76, 19, 15, 56, 87, 117, 55, 122, 50, 0, 103, 12, 68, 64, 83, 137, 76, 48, 127, 50, 111, 87, 0, 17, 70, 20, 193, 67, 81, 35, 206, 111, 55, 119, 49, 47, 34, 122, 50, 0, 0, 10, 67, 80, 129, 78, 84, 119, 50, 0, 32, 13, 69, 28, 144, 130, 60, 224, 79, 120, 69, 13, 50, 0, 5, 65, 72, 125, 0, 0, 14, 70, 80, 80, 82, 28, 20, 192, 47, 140, 79, 35, 87, 0, 15, 70, 52, 246, 137, 48, 192, 64, 63, 13, 86, 120, 55, 13, 0, 16, 70, 49, 83, 129, 80, 144, 192, 55, 132, 50, 13, 47, 120, 49, 0, 17, 70, 48, 20, 193, 28, 224, 64, 55, 13, 86, 124, 50, 57, 13, 0, 103, 16, 70, 48, 20, 193, 28, 224, 64, 55, 13, 86, 35, 50, 57, 13, 0, 0, 19, 67, 80, 129, 64, 84, 113, 15, 58, 135, 55, 0, 81, 119, 104, 105, 108, 101, 32, 10, 67, 80, 129, 64, 84, 113, 0, 9, 34, 17, 70, 25, 84, 197, 48, 17, 197, 81, 57, 132, 86, 13, 55, 124, 88, 0, 0, 0, 14, 69, 9, 32, 90, 36, 192, 69, 34, 117, 86, 120, 55, 0, 13, 69, 77, 2, 78, 4, 192, 87, 48, 135, 50, 116, 0, 12, 69, 76, 130, 86, 21, 32, 89, 120, 82, 112, 0, 13, 69, 65, 149, 8, 60, 224, 48, 135, 85, 13, 50, 0, 14, 69, 8, 243, 130, 60, 224, 69, 122, 50, 69, 122, 50, 0, 0, 9, 198, 85, 4, 212, 5, 37, 0, 65, 13, 68, 77, 0, 83, 52, 87, 48, 35, 87, 13, 63, 0, 17, 71, 77, 0, 71, 32, 85, 20, 36, 87, 48, 117, 79, 119, 47, 37, 0, 9, 198, 76, 20, 132, 36, 225, 64, 66, 9, 198, 72, 245, 84, 36, 225, 64, 66, 15, 70, 72, 80, 193, 48, 193, 68, 34, 111, 49, 128, 55, 70, 0, 9, 198, 53, 83, 132, 4, 225, 64, 66, 16, 70, 36, 225, 9, 12, 84, 192, 120, 50, 70, 111, 87, 127, 86, 0, 0, 9, 67, 48, 240, 200, 55, 122, 99, 0, 9, 67, 28, 145, 192, 79, 120, 79, 0, 19, 71, 12, 243, 80, 21, 66, 78, 28, 49, 13, 63, 48, 6, 127, 47, 120, 66, 0, 9, 67, 12, 16, 200, 49, 35, 89, 0, 0, 9, 67, 80, 129, 69, 4, 84, 127, 0, 10, 67, 76, 17, 193, 87, 124, 79, 13, 0, 11, 200, 4, 229, 9, 12, 132, 137, 77, 64, 65, 0, 14, 69, 8, 82, 82, 85, 64, 69, 136, 34, 6, 132, 47, 0, 8, 197, 85, 4, 143, 61, 64, 66, 14, 69, 81, 37, 69, 77, 64, 47, 34, 132, 13, 87, 47, 0, 6, 65, 80, 47, 127, 0, 0, 15, 70, 25, 32, 71, 36, 193, 64, 81, 34, 35, 73, 116, 0, 103, 14, 70, 52, 21, 20, 32, 85, 192, 63, 35, 85, 57, 132, 0, 17, 70, 48, 20, 193, 28, 225, 64, 108, 97, 115, 97, 103, 110, 97, 0, 29, 5, 194, 4, 48, 17, 0, 9, 67, 76, 146, 200, 87, 127, 49, 0, 13, 70, 12, 21, 1, 73, 34, 0, 49, 13, 47, 125, 0, 6, 195, 12, 147, 192, 17, 0, 16, 70, 69, 81, 83, 80, 147, 206, 49, 58, 119, 87, 74, 13, 50, 0, 13, 68, 44, 80, 129, 8, 49, 13, 69, 124, 69, 0, 103, 12, 68, 44, 80, 129, 8, 49, 13, 69, 35, 69, 0, 11, 68, 20, 208, 133, 72, 119, 63, 69, 112, 0, 0, 14, 69, 8, 245, 212, 36, 80, 69, 4, 134, 47, 6, 135, 0, 6, 65, 84, 57, 132, 0, 0, 9, 66, 85, 0, 4, 123, 48, 0, 12, 10, 67, 77, 147, 131, 87, 120, 66, 49, 0, 16, 70, 16, 83, 9, 52, 149, 0, 70, 111, 55, 120, 63, 120, 47, 0, 16, 70, 12, 195, 211, 20, 198, 64, 49, 55, 134, 87, 55, 120, 0, 32, 0, 10, 67, 84, 226, 64, 57, 132, 50, 37, 0, 28, 75, 77, 84, 5, 72, 147, 148, 20, 225, 5, 57, 64, 87, 132, 48, 112, 120, 50, 47, 6, 119, 50, 70, 13, 50, 47, 0, 0, 15, 7, 20, 8, 5, 25, 39, 22, 5, 84, 136, 82, 0, 72, 35, 13, 68, 17, 80, 78, 4, 70, 58, 6, 124, 50, 13, 0, 12, 68, 52, 243, 148, 20, 63, 122, 50, 106, 37, 0, 11, 67, 84, 229, 25, 123, 50, 47, 6, 135, 0, 0, 12, 69, 72, 81, 199, 36, 80, 34, 119, 73, 37, 0, 14, 69, 76, 195, 214, 4, 176, 87, 55, 134, 82, 35, 49, 0, 14, 69, 69, 81, 66, 20, 48, 49, 58, 111, 69, 119, 49, 0, 13, 69, 80, 245, 67, 32, 80, 47, 132, 89, 136, 0, 9, 14, 69, 76, 84, 193, 52, 80, 87, 119, 87, 117, 63, 37, 0, 9, 67, 4, 96, 82, 117, 81, 125, 0, 6, 65, 88, 82, 127, 0, 0, 21, 66, 5, 48, 4, 35, 86, 120, 47, 4, 120, 86, 0, 76, 82, 105, 116, 32, 105, 115, 32, 16, 66, 5, 48, 4, 35, 86, 4, 120, 86, 0, 8, 81, 105, 115, 32, 9, 66, 5, 48, 2, 35, 86, 0, 9, 12, 67, 36, 229, 15, 4, 120, 50, 106, 115, 0, 103, 11, 67, 36, 229, 15, 4, 120, 50, 47, 115, 0, 9, 198, 65, 35, 202, 20, 53, 0, 36, 17, 70, 65, 35, 202, 20, 53, 0, 48, 34, 122, 73, 119, 49, 47, 0, 10, 0, 23, 73, 36, 228, 212, 4, 195, 1, 80, 147, 206, 120, 50, 87, 47, 13, 55, 6, 136, 89, 13, 50, 0, 17, 71, 12, 128, 77, 60, 210, 76, 20, 49, 35, 63, 13, 63, 135, 55, 0, 0, 11, 4, 9, 39, 12, 12, 135, 55, 0, 72, 32, 12, 68, 88, 147, 153, 48, 82, 135, 50, 111, 55, 0, 12, 200, 77, 64, 76, 4, 115, 73, 80, 80, 103, 66, 20, 72, 12, 243, 77, 84, 226, 81, 84, 80, 49, 13, 63, 57, 132, 50, 111, 49, 136, 0, 0, 13, 69, 52, 20, 137, 4, 224, 63, 35, 34, 139, 50, 0, 14, 69, 76, 145, 206, 4, 192, 87, 120, 79, 50, 13, 55, 0, 22, 73, 65, 84, 144, 61, 37, 5, 16, 198, 64, 48, 112, 48, 6, 131, 47, 111, 70, 55, 120, 0, 13, 69, 64, 85, 9, 80, 80, 48, 13, 47, 127, 47, 0, 12, 1, 92, 69, 35, 49, 87, 55, 35, 89, 0, 27, 11, 65, 92, 70, 6, 123, 69, 116, 57, 132, 0, 0, 14, 70, 32, 145, 5, 61, 85, 0, 105, 135, 70, 133, 47, 0, 0, 20, 67, 80, 243, 192, 47, 6, 132, 15, 63, 4, 123, 74, 0, 81, 109, 117, 99, 104, 32, 21, 67, 80, 243, 192, 47, 6, 132, 15, 63, 4, 119, 50, 37, 0, 81, 109, 97, 110, 121, 32, 19, 67, 80, 243, 192, 47, 6, 132, 15, 81, 4, 57, 132, 0, 81, 102, 101, 119, 32, 15, 70, 5, 1, 78, 56, 147, 133, 35, 48, 13, 50, 135, 50, 0, 9, 67, 4, 224, 76, 136, 50, 116, 0, 15, 4, 95, 55, 48, 15, 87, 6, 119, 82, 13, 50, 47, 139, 0, 0, 12, 4, 23, 5, 39, 4, 58, 127, 70, 0, 72, 35, 19, 72, 92, 147, 4, 21, 35, 133, 77, 48, 58, 120, 55, 70, 112, 50, 119, 87, 0, 13, 68, 84, 225, 133, 16, 123, 50, 81, 6, 119, 70, 0, 17, 70, 16, 144, 77, 21, 65, 82, 70, 135, 6, 35, 63, 111, 47, 112, 0, 0, 13, 69, 72, 80, 76, 49, 144, 34, 139, 55, 120, 0, 32, 7, 65, 96, 119, 49, 87, 0, 0, 16, 70, 52, 20, 137, 49, 147, 128, 63, 35, 34, 13, 55, 111, 50, 0, 10, 67, 4, 225, 87, 117, 50, 132, 0, 103, 10, 67, 4, 225, 87, 117, 50, 57, 132, 0, 0, 16, 70, 76, 130, 73, 80, 18, 197, 89, 127, 47, 6, 124, 49, 150, 0, 16, 70, 65, 32, 67, 80, 148, 197, 48, 34, 35, 49, 47, 111, 87, 0, 8, 67, 4, 65, 0, 35, 70, 0, 0, 11, 68, 92, 19, 12, 100, 58, 122, 55, 37, 0, 12, 68, 17, 32, 67, 60, 70, 34, 136, 49, 134, 0, 21, 72, 81, 32, 78, 77, 3, 210, 81, 48, 47, 34, 35, 50, 87, 48, 131, 47, 87, 0, 34, 10, 67, 60, 33, 89, 134, 69, 6, 136, 0, 9, 67, 16, 244, 197, 70, 134, 87, 0, 0, 12, 67, 16, 245, 206, 4, 70, 133, 50, 0, 9, 12, 0, 9, 198, 56, 21, 1, 76, 128, 64, 66, 10, 67, 4, 211, 211, 136, 63, 122, 87, 0, 16, 70, 64, 84, 147, 60, 224, 64, 48, 126, 87, 6, 134, 50, 13, 0, 16, 70, 8, 83, 9, 76, 128, 64, 69, 13, 55, 6, 127, 89, 13, 0, 0, 18, 70, 77, 83, 1, 92, 84, 201, 87, 132, 55, 117, 58, 6, 136, 87, 37, 0, 15, 70, 56, 80, 203, 48, 16, 197, 50, 119, 49, 55, 13, 87, 0, 11, 67, 48, 244, 192, 4, 55, 122, 87, 0, 9, 0, 13, 68, 84, 225, 15, 76, 123, 50, 70, 6, 132, 86, 0, 0, 12, 69, 72, 16, 200, 20, 192, 34, 136, 74, 116, 0, 13, 69, 76, 19, 13, 60, 224, 87, 35, 63, 13, 50, 0, 7, 65, 104, 86, 127, 0, 103, 7, 65, 104, 86, 119, 70, 0, 0, 18, 66, 5, 64, 117, 47, 10, 58, 6, 120, 55, 0, 81, 119, 105, 108, 108, 32, 18, 66, 5, 64, 117, 47, 10, 58, 122, 50, 87, 0, 81, 111, 110, 99, 101, 32, 13, 66, 5, 64, 2, 35, 47, 13, 0, 34, 81, 97, 32, 10, 66, 5, 64, 35, 47, 0, 34, 9, 72, 16, 70, 9, 34, 65, 56, 224, 64, 69, 34, 120, 6, 35, 50, 13, 0, 16, 70, 64, 245, 15, 52, 16, 192, 48, 13, 47, 134, 63, 13, 49, 0, 17, 70, 64, 243, 9, 80, 144, 192, 48, 122, 55, 13, 47, 120, 49, 0, 10, 0, 17, 67, 92, 20, 192, 58, 2, 122, 86, 84, 113, 0, 81, 116, 104, 101, 32, 14, 67, 92, 20, 192, 58, 2, 122, 86, 117, 0, 81, 97, 32, 13, 67, 92, 20, 192, 2, 58, 123, 86, 0, 103, 35, 9, 12, 67, 92, 20, 192, 2, 58, 122, 86, 0, 35, 9, 9, 67, 80, 133, 64, 85, 145, 0, 105, 8, 67, 80, 133, 64, 85, 126, 0, 9, 67, 21, 84, 128, 57, 141, 0, 9, 0, 12, 201, 40, 242, 1, 56, 225, 83, 9, 84, 135, 66, 0, 13, 69, 44, 145, 82, 4, 224, 49, 139, 34, 13, 50, 0, 14, 69, 80, 19, 5, 57, 64, 47, 35, 55, 13, 50, 47, 0, 12, 69, 76, 244, 130, 21, 64, 87, 130, 69, 136, 0, 0, 16, 70, 72, 19, 69, 76, 84, 192, 34, 35, 63, 13, 87, 127, 86, 0, 14, 70, 80, 129, 82, 52, 244, 192, 85, 126, 63, 13, 87, 0, 9, 198, 61, 85, 12, 36, 225, 64, 65, 9, 198, 9, 34, 71, 4, 65, 64, 66, 14, 70, 5, 3, 211, 80, 193, 64, 117, 48, 122, 87, 116, 0, 16, 70, 4, 225, 77, 60, 225, 64, 117, 50, 119, 63, 13, 50, 37, 0, 10, 67, 4, 211, 203, 117, 63, 122, 49, 0, 0, 10, 199, 84, 225, 5, 72, 194, 78, 28, 65, 8, 67, 16, 245, 192, 70, 133, 0, 0, 12, 68, 64, 147, 15, 80, 48, 135, 55, 13, 47, 0, 19, 72, 4, 69, 133, 73, 66, 83, 21, 32, 35, 70, 82, 112, 47, 135, 86, 112, 0, 0, 15, 69, 65, 84, 137, 77, 64, 48, 57, 132, 44, 120, 87, 47, 0, 14, 69, 4, 65, 9, 13, 64, 35, 70, 120, 49, 47, 0, 10, 0, 14, 70, 52, 148, 211, 36, 193, 64, 63, 120, 87, 116, 0, 103, 14, 70, 56, 85, 137, 48, 193, 64, 50, 119, 82, 120, 55, 0, 15, 70, 21, 66, 69, 56, 225, 64, 119, 47, 120, 6, 119, 50, 0, 13, 70, 12, 129, 65, 16, 193, 64, 74, 127, 70, 116, 0, 0, 11, 67, 32, 245, 192, 4, 105, 133, 0, 12, 10, 12, 67, 4, 230, 64, 4, 119, 50, 37, 0, 34, 9, 9, 67, 80, 134, 64, 4, 84, 135, 0, 9, 198, 12, 19, 3, 85, 69, 1, 66, 16, 70, 16, 17, 197, 56, 128, 77, 70, 35, 79, 13, 50, 13, 63, 0, 0, 10, 67, 80, 129, 89, 84, 136, 0, 72, 32, 0, 11, 4, 9, 39, 22, 5, 135, 82, 0, 72, 35, 13, 69, 80, 243, 129, 28, 80, 47, 123, 50, 120, 73, 0, 13, 69, 76, 242, 82, 20, 80, 87, 58, 124, 34, 136, 0, 14, 69, 64, 20, 212, 73, 144, 48, 136, 87, 47, 34, 37, 0, 0, 16, 70, 81, 34, 80, 60, 194, 64, 47, 34, 120, 48, 13, 55, 37, 0, 15, 70, 5, 85, 15, 65, 54, 64, 128, 106, 122, 48, 87, 37, 0, 0, 17, 67, 80, 128, 84, 2, 84, 35, 47, 84, 113, 0, 81, 116, 104, 101, 32, 19, 67, 80, 128, 84, 84, 6, 35, 47, 58, 4, 122, 50, 0, 81, 111, 110, 101, 32, 17, 67, 80, 128, 84, 4, 84, 117, 47, 120, 47, 0, 33, 81, 105, 116, 32, 17, 67, 80, 128, 84, 4, 84, 35, 47, 13, 50, 0, 34, 81, 97, 110, 32, 15, 67, 80, 128, 84, 4, 84, 35, 47, 13, 0, 34, 81, 97, 32, 13, 67, 80, 128, 84, 84, 35, 47, 0, 72, 34, 12, 33, 17, 71, 72, 84, 197, 73, 99, 201, 72, 34, 119, 86, 112, 82, 58, 125, 0, 18, 71, 20, 229, 133, 48, 244, 5, 76, 119, 50, 82, 13, 55, 134, 48, 87, 0, 0, 14, 7, 20, 8, 5, 25, 39, 18, 5, 2, 84, 136, 112, 0, 20, 72, 64, 84, 147, 21, 2, 15, 56, 80, 48, 112, 87, 6, 119, 81, 13, 50, 37, 0, 13, 70, 12, 18, 83, 20, 19, 0, 49, 35, 89, 116, 0, 11, 68, 77, 81, 68, 20, 87, 58, 136, 70, 0, 16, 70, 76, 243, 21, 80, 147, 206, 87, 13, 55, 132, 89, 13, 50, 0, 12, 68, 76, 147, 149, 76, 87, 135, 50, 13, 87, 0, 20, 72, 48, 149, 5, 72, 21, 21, 72, 80, 55, 120, 47, 112, 34, 13, 74, 112, 0, 103, 18, 72, 48, 149, 5, 72, 21, 21, 72, 80, 55, 120, 47, 34, 121, 74, 112, 0, 11, 68, 8, 144, 140, 20, 69, 135, 69, 116, 0, 0, 14, 69, 56, 144, 207, 48, 16, 50, 120, 49, 13, 55, 13, 0, 17, 70, 12, 243, 131, 21, 37, 15, 49, 13, 50, 74, 6, 138, 47, 134, 0, 15, 70, 12, 21, 8, 60, 194, 67, 49, 35, 85, 55, 120, 49, 0, 0, 18, 70, 4, 196, 133, 4, 70, 64, 128, 55, 34, 119, 70, 37, 0, 74, 32, 12, 10, 67, 52, 83, 215, 63, 37, 6, 133, 0, 16, 70, 12, 244, 143, 56, 85, 0, 49, 122, 34, 13, 50, 119, 47, 0, 14, 70, 8, 245, 81, 84, 85, 0, 69, 132, 49, 6, 136, 0, 7, 66, 5, 80, 4, 134, 0, 0, 20, 71, 48, 245, 73, 76, 144, 78, 4, 55, 132, 4, 127, 86, 127, 6, 35, 50, 13, 0, 17, 71, 80, 147, 69, 80, 16, 140, 20, 47, 135, 63, 47, 136, 69, 116, 0, 20, 71, 76, 83, 73, 12, 243, 15, 56, 87, 119, 63, 120, 49, 6, 134, 55, 13, 50, 0, 17, 71, 12, 128, 82, 48, 21, 1, 56, 89, 125, 55, 13, 47, 13, 50, 0, 0, 12, 68, 72, 16, 137, 16, 34, 136, 69, 120, 70, 0, 20, 72, 64, 82, 143, 72, 21, 9, 88, 80, 48, 13, 73, 122, 34, 13, 47, 120, 82, 0, 13, 68, 52, 241, 5, 52, 63, 134, 70, 13, 63, 0, 103, 12, 68, 52, 241, 5, 52, 63, 134, 70, 119, 63, 0, 10, 67, 44, 149, 201, 49, 127, 58, 127, 0, 0, 0, 10, 67, 4, 229, 83, 136, 50, 123, 87, 0, 0, 10, 1, 126, 47, 120, 55, 70, 13, 0, 27, 0, 11, 68, 28, 144, 130, 76, 79, 120, 69, 86, 0, 11, 68, 80, 145, 1, 48, 47, 135, 70, 116, 0, 0, 17, 67, 80, 128, 78, 4, 84, 35, 50, 13, 50, 0, 34, 81, 97, 110, 32, 15, 67, 80, 128, 78, 4, 84, 35, 50, 13, 0, 34, 81, 97, 32, 11, 67, 80, 128, 78, 84, 117, 50, 0, 72, 9, 14, 69, 81, 37, 69, 49, 144, 47, 34, 132, 55, 120, 0, 32, 13, 69, 52, 148, 211, 21, 48, 63, 120, 87, 111, 86, 0, 0, 16, 70, 12, 240, 207, 57, 85, 0, 49, 134, 49, 13, 50, 123, 47, 0, 0, 9, 67, 21, 96, 64, 127, 82, 13, 0, 0, 0, 17, 70, 4, 229, 9, 48, 193, 83, 35, 50, 47, 6, 120, 55, 127, 86, 0, 13, 69, 92, 144, 203, 20, 64, 58, 120, 49, 121, 70, 0, 15, 69, 84, 228, 133, 4, 64, 123, 50, 34, 6, 119, 70, 0, 9, 0, 15, 70, 72, 146, 1, 56, 224, 64, 34, 120, 6, 124, 50, 13, 0, 9, 67, 81, 115, 211, 47, 132, 86, 0, 0, 17, 71, 92, 129, 82, 20, 85, 133, 72, 58, 2, 138, 44, 119, 82, 112, 0, 0, 7, 196, 80, 16, 143, 60, 66, 10, 67, 40, 81, 9, 73, 119, 70, 135, 0, 11, 68, 21, 113, 69, 44, 127, 58, 127, 49, 0, 16, 70, 12, 147, 142, 4, 211, 206, 87, 120, 50, 13, 63, 13, 50, 0, 0, 11, 69, 80, 131, 213, 28, 128, 4, 84, 134, 0, 12, 69, 52, 148, 211, 20, 64, 63, 120, 87, 47, 0, 0, 9, 198, 64, 19, 132, 61, 32, 64, 66, 16, 70, 85, 68, 133, 12, 133, 0, 57, 132, 47, 34, 119, 97, 47, 0, 0, 18, 71, 8, 20, 143, 52, 85, 5, 72, 69, 13, 34, 122, 63, 111, 47, 112, 0, 0, 9, 67, 8, 81, 5, 69, 127, 70, 0, 13, 70, 16, 245, 71, 4, 195, 0, 70, 132, 79, 116, 0, 15, 70, 92, 19, 19, 4, 195, 0, 58, 128, 55, 87, 128, 55, 0, 10, 68, 4, 32, 133, 100, 35, 69, 37, 0, 7, 196, 57, 148, 19, 16, 17, 0, 14, 69, 28, 144, 147, 60, 224, 79, 120, 69, 87, 13, 50, 0, 22, 73, 77, 84, 5, 72, 99, 21, 61, 84, 192, 87, 132, 48, 6, 126, 81, 55, 132, 13, 87, 0, 13, 69, 28, 86, 83, 21, 32, 79, 135, 86, 112, 0, 103, 12, 69, 28, 86, 83, 21, 32, 79, 127, 86, 112, 0, 13, 69, 24, 21, 8, 60, 208, 81, 35, 84, 13, 63, 0, 21, 73, 12, 193, 65, 56, 194, 78, 21, 52, 192, 49, 55, 119, 50, 55, 120, 50, 13, 87, 0, 0, 14, 70, 76, 145, 206, 4, 113, 64, 87, 135, 50, 111, 73, 0, 16, 70, 64, 244, 148, 20, 225, 0, 48, 131, 47, 6, 119, 50, 70, 0, 0, 17, 71, 12, 19, 66, 72, 145, 7, 20, 49, 136, 63, 69, 34, 120, 73, 0, 0, 12, 68, 76, 243, 137, 4, 87, 122, 50, 57, 13, 0, 11, 200, 80, 132, 143, 84, 114, 15, 85, 64, 66, 0, 21, 73, 56, 243, 133, 80, 129, 76, 21, 52, 192, 50, 123, 50, 84, 13, 55, 6, 119, 87, 0, 12, 69, 48, 243, 211, 21, 32, 55, 132, 86, 112, 0, 12, 69, 8, 22, 129, 5, 32, 69, 117, 86, 125, 0, 0, 10, 66, 8, 80, 69, 127, 0, 35, 9, 76, 14, 70, 76, 85, 137, 48, 193, 64, 87, 13, 82, 120, 55, 0, 15, 70, 20, 228, 143, 85, 65, 64, 122, 50, 34, 6, 132, 47, 0, 0, 11, 67, 48, 244, 212, 55, 129, 87, 47, 0, 103, 17, 70, 76, 84, 133, 56, 17, 5, 87, 119, 34, 111, 50, 6, 136, 70, 0, 16, 70, 24, 21, 143, 72, 149, 5, 81, 136, 82, 14, 34, 111, 47, 0, 10, 199, 12, 243, 147, 81, 37, 67, 80, 36, 20, 71, 12, 243, 147, 81, 37, 67, 80, 49, 122, 50, 87, 47, 34, 123, 49, 47, 0, 10, 0, 14, 68, 84, 225, 5, 72, 123, 50, 70, 112, 0, 72, 12, 9, 16, 70, 80, 240, 143, 28, 112, 78, 47, 13, 69, 122, 79, 13, 50, 0, 12, 68, 65, 34, 86, 100, 48, 34, 120, 82, 37, 0, 11, 68, 44, 81, 137, 72, 49, 127, 81, 112, 0, 11, 67, 32, 18, 1, 105, 124, 105, 6, 124, 0, 0, 15, 69, 8, 19, 129, 56, 16, 69, 117, 50, 35, 50, 13, 0, 103, 17, 70, 52, 147, 132, 4, 224, 79, 63, 120, 50, 70, 13, 50, 6, 133, 0, 14, 69, 20, 198, 83, 20, 80, 136, 55, 6, 127, 86, 136, 0, 14, 69, 76, 145, 82, 72, 16, 87, 127, 6, 138, 34, 13, 0, 13, 69, 20, 229, 18, 20, 80, 122, 50, 47, 34, 136, 0, 8, 197, 20, 212, 9, 72, 80, 65, 13, 69, 12, 18, 143, 48, 80, 49, 117, 73, 134, 55, 0, 14, 69, 8, 19, 129, 56, 16, 69, 13, 50, 124, 50, 13, 0, 23, 73, 5, 4, 18, 61, 130, 77, 5, 65, 64, 117, 48, 34, 122, 49, 87, 120, 63, 136, 47, 0, 36, 23, 73, 5, 4, 18, 61, 130, 77, 5, 65, 64, 117, 48, 34, 122, 49, 87, 120, 63, 13, 47, 0, 9, 12, 69, 4, 50, 9, 56, 112, 136, 49, 120, 66, 0, 0, 15, 70, 92, 245, 78, 16, 81, 0, 58, 132, 50, 70, 121, 70, 0, 0, 10, 67, 77, 34, 64, 87, 34, 4, 127, 0, 18, 70, 48, 147, 135, 21, 34, 69, 55, 122, 50, 88, 13, 34, 6, 136, 0, 103, 16, 70, 48, 147, 135, 21, 34, 69, 55, 122, 50, 88, 13, 34, 37, 0, 10, 199, 25, 37, 83, 81, 32, 84, 20, 66, 16, 70, 9, 35, 195, 12, 243, 9, 69, 34, 122, 49, 13, 55, 37, 0, 0, 12, 68, 76, 81, 1, 56, 87, 111, 70, 35, 50, 0, 12, 68, 28, 243, 142, 4, 79, 4, 13, 50, 13, 0, 12, 68, 12, 240, 146, 4, 49, 134, 69, 34, 13, 0, 10, 68, 5, 81, 197, 72, 128, 79, 112, 0, 0, 12, 69, 65, 32, 71, 84, 80, 48, 34, 124, 79, 0, 13, 69, 61, 32, 78, 28, 80, 122, 34, 111, 50, 73, 0, 24, 73, 20, 193, 67, 81, 34, 67, 37, 70, 64, 111, 55, 119, 49, 47, 34, 6, 120, 87, 111, 47, 37, 0, 22, 73, 4, 227, 137, 88, 84, 147, 5, 38, 64, 35, 50, 120, 82, 6, 126, 87, 13, 34, 37, 0, 14, 69, 4, 69, 193, 72, 80, 6, 35, 70, 58, 4, 138, 0, 0, 0, 16, 70, 28, 147, 214, 4, 227, 137, 73, 13, 82, 6, 124, 50, 37, 0, 18, 71, 64, 20, 211, 21, 36, 194, 100, 48, 35, 87, 112, 86, 69, 6, 135, 0, 19, 71, 44, 147, 15, 52, 85, 5, 72, 49, 120, 55, 6, 122, 63, 111, 47, 112, 0, 17, 71, 24, 244, 148, 84, 224, 84, 20, 81, 130, 74, 13, 50, 13, 47, 0, 18, 71, 4, 67, 73, 72, 16, 140, 20, 35, 70, 63, 13, 34, 13, 69, 116, 0, 0, 12, 68, 81, 32, 67, 100, 47, 34, 136, 87, 37, 0, 15, 70, 76, 48, 76, 64, 83, 0, 87, 49, 35, 55, 48, 116, 0, 0, 13, 69, 16, 148, 206, 21, 144, 70, 120, 86, 50, 37, 0, 13, 69, 32, 83, 9, 84, 208, 105, 127, 55, 139, 63, 0, 17, 70, 17, 32, 77, 5, 66, 67, 70, 34, 13, 63, 35, 47, 120, 49, 0, 14, 69, 4, 194, 193, 48, 144, 35, 55, 49, 13, 55, 135, 0, 0, 10, 67, 80, 133, 83, 84, 123, 87, 0, 8, 13, 202, 92, 244, 132, 65, 35, 195, 21, 52, 207, 72, 66, 15, 70, 32, 244, 212, 21, 52, 192, 105, 134, 87, 47, 119, 87, 0, 18, 70, 12, 192, 82, 36, 225, 84, 49, 55, 35, 34, 13, 50, 6, 119, 47, 0, 0, 12, 67, 9, 85, 0, 4, 69, 123, 47, 0, 8, 9, 14, 67, 92, 20, 212, 2, 58, 122, 87, 47, 0, 9, 35, 9, 10, 67, 92, 20, 212, 58, 136, 87, 47, 0, 0, 11, 68, 28, 198, 78, 56, 79, 55, 120, 50, 0, 21, 72, 72, 130, 78, 60, 49, 82, 61, 48, 34, 135, 50, 6, 122, 87, 13, 34, 13, 87, 0, 0, 10, 67, 21, 96, 78, 119, 82, 13, 50, 0, 13, 69, 32, 80, 146, 21, 112, 105, 127, 69, 34, 132, 0, 15, 69, 84, 225, 5, 57, 144, 123, 50, 70, 120, 50, 6, 135, 0, 13, 69, 81, 35, 208, 33, 144, 47, 34, 134, 81, 37, 0, 8, 197, 77, 84, 150, 21, 144, 36, 14, 69, 77, 84, 150, 21, 144, 87, 146, 82, 136, 0, 105, 10, 13, 69, 77, 84, 150, 21, 144, 87, 126, 82, 136, 0, 10, 0, 15, 70, 52, 20, 135, 5, 33, 84, 63, 125, 79, 34, 13, 47, 0, 9, 198, 52, 20, 148, 36, 225, 84, 67, 0, 12, 67, 32, 21, 8, 2, 105, 35, 85, 0, 35, 9, 19, 71, 65, 148, 129, 52, 145, 1, 48, 48, 111, 34, 6, 35, 63, 120, 70, 116, 0, 18, 71, 24, 192, 71, 20, 195, 21, 52, 81, 55, 117, 73, 119, 55, 13, 63, 0, 19, 71, 4, 225, 67, 16, 245, 1, 48, 35, 50, 120, 49, 70, 6, 134, 47, 116, 0, 0, 13, 68, 64, 20, 212, 4, 48, 124, 87, 47, 13, 0, 103, 17, 70, 92, 129, 78, 21, 97, 82, 58, 119, 50, 119, 82, 112, 0, 74, 8, 11, 67, 64, 20, 1, 48, 124, 48, 13, 0, 103, 11, 67, 64, 20, 1, 48, 117, 48, 6, 124, 0, 12, 68, 52, 19, 9, 12, 63, 35, 55, 120, 49, 0, 0, 12, 69, 32, 19, 135, 20, 64, 105, 35, 66, 70, 0, 0, 15, 70, 81, 114, 76, 36, 114, 20, 47, 58, 135, 55, 135, 47, 0, 0, 17, 70, 65, 33, 84, 20, 228, 197, 48, 34, 127, 47, 119, 50, 87, 0, 103, 10, 67, 21, 98, 84, 119, 82, 111, 47, 0, 10, 199, 4, 229, 9, 25, 33, 90, 20, 65, 0, 12, 68, 88, 83, 149, 76, 82, 127, 50, 13, 87, 0, 10, 68, 80, 243, 142, 20, 47, 123, 50, 0, 16, 70, 76, 245, 86, 20, 226, 82, 87, 132, 82, 13, 50, 6, 140, 0, 13, 68, 56, 240, 140, 100, 50, 134, 69, 55, 120, 0, 32, 12, 68, 52, 83, 15, 56, 63, 119, 55, 13, 50, 0, 11, 68, 12, 81, 1, 72, 87, 127, 70, 112, 0, 0, 0, 14, 70, 32, 20, 142, 21, 52, 192, 105, 125, 50, 121, 87, 0, 11, 66, 17, 32, 70, 122, 49, 47, 112, 0, 24, 0, 18, 71, 64, 84, 137, 52, 85, 5, 72, 48, 13, 34, 120, 63, 111, 47, 112, 0, 17, 71, 52, 147, 5, 77, 67, 206, 20, 63, 135, 55, 87, 47, 134, 50, 0, 17, 70, 52, 18, 143, 72, 149, 25, 63, 13, 73, 122, 34, 111, 47, 37, 0, 19, 70, 21, 48, 193, 64, 148, 205, 119, 87, 49, 6, 136, 48, 111, 86, 13, 63, 0, 0, 11, 68, 37, 50, 65, 32, 135, 86, 6, 142, 0, 11, 68, 80, 241, 1, 100, 47, 13, 70, 136, 0, 11, 68, 72, 18, 129, 32, 34, 124, 73, 124, 0, 12, 68, 21, 32, 83, 20, 111, 34, 136, 87, 0, 103, 11, 68, 21, 32, 83, 20, 111, 34, 136, 86, 0, 0, 13, 69, 76, 243, 4, 21, 32, 87, 124, 70, 112, 0, 103, 13, 69, 76, 243, 4, 21, 32, 87, 122, 55, 70, 112, 0, 20, 73, 52, 148, 195, 32, 145, 86, 61, 84, 192, 63, 120, 87, 74, 111, 82, 13, 87, 0, 0, 16, 6, 8, 1, 4, 14, 39, 20, 105, 35, 70, 13, 50, 47, 0, 35, 15, 70, 84, 224, 87, 5, 33, 64, 123, 50, 13, 58, 6, 138, 0, 10, 67, 72, 84, 15, 34, 127, 48, 134, 0, 15, 70, 25, 34, 71, 5, 65, 64, 81, 34, 120, 79, 13, 47, 0, 14, 70, 12, 244, 144, 61, 32, 76, 49, 130, 48, 34, 116, 0, 0, 25, 67, 53, 84, 212, 63, 4, 123, 87, 47, 35, 82, 47, 114, 0, 35, 82, 104, 97, 118, 101, 32, 116, 111, 32, 21, 67, 53, 84, 212, 63, 123, 87, 47, 105, 35, 82, 0, 35, 14, 81, 104, 97, 118, 101, 32, 20, 67, 53, 84, 212, 63, 123, 87, 47, 117, 82, 0, 35, 65, 81, 104, 97, 118, 101, 32, 6, 195, 53, 84, 212, 32, 18, 71, 65, 33, 67, 37, 2, 67, 20, 48, 34, 119, 87, 111, 48, 120, 87, 0, 18, 70, 29, 32, 68, 84, 21, 5, 79, 34, 35, 70, 57, 132, 136, 47, 0, 36, 17, 70, 29, 32, 68, 84, 21, 5, 79, 34, 35, 70, 57, 132, 13, 47, 0, 16, 70, 16, 83, 9, 12, 21, 5, 70, 119, 55, 111, 49, 13, 47, 0, 0, 11, 67, 8, 85, 1, 69, 136, 47, 13, 0, 103, 12, 68, 76, 147, 131, 20, 87, 120, 50, 87, 0, 8, 11, 67, 80, 22, 25, 47, 35, 49, 87, 37, 0, 10, 67, 64, 21, 5, 48, 35, 106, 136, 0, 9, 67, 24, 85, 5, 81, 136, 47, 0, 10, 67, 8, 85, 1, 69, 127, 47, 13, 0, 0, 14, 69, 64, 84, 141, 37, 64, 48, 112, 63, 120, 47, 0, 36, 14, 69, 64, 84, 141, 37, 64, 48, 126, 63, 120, 47, 0, 10, 12, 69, 16, 144, 80, 21, 32, 70, 135, 48, 112, 0, 0, 15, 6, 4, 9, 4, 14, 39, 20, 70, 120, 70, 50, 47, 0, 32, 15, 70, 61, 85, 12, 37, 97, 64, 133, 47, 55, 6, 120, 82, 0, 17, 70, 21, 129, 67, 85, 65, 64, 119, 49, 87, 111, 49, 57, 132, 47, 0, 16, 70, 13, 33, 77, 5, 65, 64, 49, 34, 127, 63, 136, 47, 0, 103, 14, 70, 12, 83, 147, 85, 33, 64, 87, 119, 50, 89, 112, 0, 14, 70, 12, 21, 137, 5, 33, 64, 49, 35, 82, 120, 125, 0, 5, 194, 4, 144, 17, 0, 17, 70, 17, 83, 135, 5, 33, 69, 70, 123, 66, 79, 117, 34, 6, 127, 0, 0, 33, 8, 3, 15, 21, 12, 4, 14, 39, 20, 6, 49, 115, 70, 13, 50, 47, 35, 82, 47, 114, 0, 32, 12, 82, 104, 97, 118, 101, 32, 116, 111, 32, 27, 8, 3, 15, 21, 12, 4, 14, 39, 20, 49, 115, 70, 13, 50, 47, 13, 82, 0, 35, 77, 81, 104, 97, 118, 101, 32, 20, 8, 3, 15, 21, 12, 4, 14, 39, 20, 4, 49, 115, 70, 13, 50, 47, 0, 32, 12, 18, 8, 19, 8, 1, 12, 12, 14, 39, 20, 4, 89, 124, 50, 47, 0, 32, 12, 12, 68, 32, 17, 5, 76, 105, 136, 70, 127, 86, 0, 10, 67, 80, 145, 25, 47, 135, 70, 37, 0, 10, 67, 48, 147, 25, 55, 120, 55, 37, 0, 12, 68, 5, 33, 78, 4, 117, 34, 127, 50, 13, 0, 0, 13, 69, 76, 51, 5, 72, 16, 87, 49, 55, 139, 34, 0, 12, 201, 36, 228, 212, 36, 224, 212, 37, 97, 64, 66, 13, 69, 16, 83, 135, 84, 80, 70, 119, 50, 79, 37, 0, 22, 73, 4, 197, 5, 72, 224, 84, 37, 97, 64, 128, 55, 47, 6, 126, 50, 13, 47, 120, 82, 0, 0, 10, 67, 72, 81, 15, 34, 127, 70, 132, 0, 0, 13, 70, 72, 19, 5, 36, 114, 0, 34, 124, 55, 37, 0, 19, 71, 21, 84, 8, 72, 21, 5, 76, 57, 132, 81, 34, 6, 136, 47, 127, 86, 0, 18, 71, 24, 21, 143, 72, 149, 5, 76, 81, 136, 82, 14, 34, 111, 47, 87, 0, 0, 12, 68, 4, 225, 5, 76, 35, 50, 70, 127, 86, 0, 15, 70, 72, 85, 18, 36, 19, 0, 34, 127, 47, 34, 142, 55, 0, 10, 67, 72, 83, 25, 34, 111, 55, 135, 0, 11, 68, 72, 17, 1, 72, 34, 136, 70, 125, 0, 10, 68, 53, 148, 146, 32, 63, 146, 0, 105, 9, 68, 53, 148, 146, 32, 63, 126, 0, 12, 68, 36, 225, 133, 72, 120, 50, 81, 6, 126, 0, 10, 67, 8, 83, 25, 69, 111, 55, 135, 0, 0, 0, 16, 70, 60, 33, 76, 37, 50, 192, 122, 69, 13, 55, 111, 87, 49, 0, 13, 70, 28, 245, 82, 52, 85, 0, 79, 141, 63, 136, 0, 15, 70, 24, 148, 200, 56, 85, 0, 81, 120, 89, 50, 119, 47, 0, 0, 17, 71, 77, 84, 146, 60, 112, 84, 20, 87, 126, 13, 79, 13, 47, 0, 103, 17, 71, 77, 84, 146, 60, 112, 84, 20, 87, 123, 34, 13, 79, 136, 47, 0, 17, 71, 4, 195, 5, 52, 19, 132, 20, 35, 55, 13, 63, 35, 50, 70, 0, 0, 21, 72, 49, 86, 5, 52, 35, 213, 72, 112, 55, 123, 49, 87, 13, 63, 69, 146, 79, 0, 105, 20, 72, 49, 86, 5, 52, 35, 213, 72, 112, 55, 123, 49, 87, 13, 63, 69, 126, 79, 0, 10, 68, 32, 243, 13, 20, 105, 134, 63, 0, 0, 0, 17, 70, 4, 211, 206, 29, 53, 0, 117, 63, 123, 66, 87, 47, 0, 74, 12, 15, 70, 77, 84, 144, 49, 84, 192, 87, 126, 48, 55, 13, 87, 0, 0, 0, 13, 68, 49, 82, 71, 36, 55, 132, 6, 127, 73, 37, 0, 20, 72, 72, 80, 201, 65, 35, 195, 4, 192, 34, 111, 87, 120, 48, 34, 13, 49, 116, 0, 19, 72, 24, 21, 143, 85, 34, 84, 21, 48, 81, 136, 82, 14, 34, 111, 47, 87, 0, 11, 68, 8, 145, 5, 80, 69, 127, 70, 136, 0, 0, 14, 69, 16, 81, 133, 57, 48, 70, 111, 81, 119, 50, 87, 0, 0, 8, 67, 101, 97, 83, 127, 82, 0, 16, 70, 24, 243, 212, 32, 243, 4, 81, 115, 47, 105, 134, 55, 70, 0, 12, 4, 95, 20, 21, 18, 47, 6, 126, 50, 70, 0, 0, 11, 67, 72, 80, 68, 34, 119, 70, 0, 38, 9, 9, 67, 72, 80, 68, 34, 127, 70, 0, 0, 11, 68, 88, 147, 12, 36, 82, 120, 55, 135, 0, 12, 68, 85, 34, 78, 20, 57, 141, 34, 120, 50, 0, 11, 68, 12, 17, 18, 20, 49, 124, 70, 112, 0, 11, 68, 5, 33, 207, 56, 125, 79, 122, 50, 0, 11, 68, 4, 65, 15, 56, 35, 70, 122, 50, 0, 0, 14, 69, 52, 17, 18, 36, 64, 63, 13, 70, 34, 120, 70, 0, 13, 69, 64, 22, 80, 4, 192, 48, 136, 48, 35, 55, 0, 0, 17, 70, 33, 148, 15, 96, 144, 64, 105, 135, 48, 6, 122, 49, 87, 139, 0, 0, 0, 12, 68, 45, 80, 76, 4, 49, 58, 124, 55, 117, 0, 11, 68, 4, 65, 9, 76, 35, 70, 120, 87, 0, 10, 68, 17, 34, 69, 72, 70, 34, 143, 0, 20, 72, 5, 35, 83, 48, 83, 135, 80, 128, 4, 125, 63, 86, 55, 6, 119, 66, 85, 0, 0, 10, 67, 13, 37, 90, 49, 34, 132, 86, 0, 8, 197, 72, 80, 207, 72, 64, 36, 15, 69, 72, 80, 207, 72, 64, 34, 119, 49, 112, 70, 0, 103, 10, 14, 69, 72, 80, 207, 72, 64, 34, 119, 49, 130, 70, 0, 10, 14, 69, 12, 19, 148, 60, 224, 49, 35, 50, 47, 122, 50, 0, 0, 17, 70, 48, 144, 133, 72, 144, 64, 55, 135, 69, 6, 139, 34, 127, 13, 0, 10, 67, 48, 147, 79, 55, 120, 63, 134, 0, 15, 70, 24, 244, 133, 80, 83, 12, 81, 131, 47, 6, 119, 55, 0, 17, 70, 16, 147, 5, 52, 208, 64, 70, 121, 55, 6, 119, 63, 13, 0, 103, 16, 70, 16, 147, 5, 52, 208, 64, 70, 135, 55, 6, 119, 63, 13, 0, 0, 10, 67, 100, 245, 64, 57, 132, 0, 72, 32, 9, 67, 4, 113, 68, 136, 73, 70, 0, 0, 12, 68, 16, 243, 3, 20, 70, 122, 55, 74, 136, 0, 0, 14, 69, 17, 83, 131, 4, 224, 70, 123, 50, 49, 13, 50, 0, 14, 69, 48, 243, 132, 60, 224, 55, 123, 50, 70, 13, 50, 0, 0, 14, 70, 65, 85, 20, 36, 225, 192, 48, 115, 47, 120, 66, 0, 15, 70, 80, 129, 82, 20, 241, 128, 4, 84, 138, 6, 122, 82, 0, 9, 198, 77, 84, 16, 61, 49, 64, 66, 17, 70, 65, 33, 84, 72, 144, 76, 48, 34, 127, 47, 34, 6, 135, 116, 0, 16, 70, 21, 2, 84, 60, 209, 64, 111, 48, 120, 47, 13, 63, 120, 0, 16, 70, 12, 243, 131, 37, 49, 64, 49, 122, 50, 87, 6, 135, 87, 0, 0, 10, 199, 16, 148, 195, 61, 84, 147, 20, 65, 0, 8, 67, 80, 131, 213, 84, 133, 0, 10, 67, 48, 144, 77, 55, 127, 13, 63, 0, 10, 68, 72, 245, 83, 20, 34, 133, 86, 0, 0, 8, 197, 61, 85, 6, 37, 64, 65, 13, 69, 60, 209, 76, 21, 64, 122, 63, 55, 13, 47, 0, 0, 18, 66, 16, 80, 70, 136, 73, 6, 141, 34, 37, 0, 81, 106, 117, 114, 101, 32, 14, 70, 52, 21, 82, 36, 49, 64, 63, 122, 34, 120, 87, 0, 14, 70, 48, 83, 206, 5, 33, 0, 55, 119, 50, 13, 70, 0, 8, 66, 16, 80, 70, 13, 0, 9, 0, 9, 67, 72, 82, 68, 34, 127, 70, 0, 9, 67, 76, 178, 64, 87, 49, 127, 0, 17, 71, 56, 84, 195, 36, 83, 131, 20, 50, 119, 87, 120, 13, 50, 87, 0, 0, 12, 68, 81, 34, 78, 4, 47, 34, 127, 50, 13, 0, 13, 68, 17, 98, 78, 4, 70, 13, 82, 127, 50, 13, 0, 15, 204, 56, 245, 23, 37, 66, 19, 80, 19, 132, 36, 225, 192, 67, 12, 68, 48, 147, 1, 12, 55, 135, 55, 13, 49, 0, 12, 68, 37, 32, 84, 20, 135, 34, 6, 136, 47, 0, 12, 68, 33, 86, 154, 4, 105, 13, 86, 6, 124, 0, 0, 13, 67, 8, 81, 78, 4, 69, 120, 50, 0, 103, 35, 9, 12, 67, 8, 81, 78, 4, 69, 127, 50, 0, 35, 9, 13, 69, 8, 20, 129, 12, 176, 69, 117, 34, 124, 49, 0, 12, 69, 61, 4, 15, 76, 80, 13, 48, 134, 86, 0, 8, 197, 33, 83, 65, 56, 80, 66, 0, 14, 70, 48, 16, 143, 72, 81, 0, 55, 136, 69, 13, 70, 0, 9, 198, 12, 243, 150, 36, 53, 0, 36, 17, 70, 12, 243, 150, 36, 53, 0, 49, 122, 50, 82, 120, 49, 47, 0, 10, 0, 15, 70, 12, 20, 142, 20, 114, 69, 49, 125, 50, 13, 79, 37, 0, 10, 199, 92, 130, 67, 32, 85, 133, 72, 66, 0, 10, 67, 41, 81, 25, 73, 132, 70, 37, 0, 11, 68, 76, 21, 84, 20, 87, 128, 47, 136, 0, 10, 68, 60, 97, 133, 72, 122, 81, 112, 0, 12, 68, 52, 147, 149, 76, 63, 135, 50, 13, 87, 0, 21, 72, 16, 145, 76, 20, 53, 18, 36, 48, 70, 142, 55, 6, 119, 49, 47, 34, 120, 49, 0, 11, 4, 95, 4, 16, 20, 48, 137, 50, 47, 0, 0, 15, 69, 8, 80, 207, 52, 80, 69, 120, 49, 123, 63, 0, 74, 12, 13, 69, 61, 69, 1, 92, 16, 122, 47, 117, 58, 13, 0, 13, 69, 88, 19, 9, 76, 80, 82, 117, 55, 127, 87, 0, 14, 69, 76, 145, 67, 48, 80, 87, 57, 119, 49, 55, 14, 0, 15, 69, 21, 84, 133, 44, 16, 57, 132, 6, 34, 127, 49, 117, 0, 13, 69, 8, 85, 1, 44, 80, 69, 111, 47, 136, 49, 0, 10, 67, 4, 227, 206, 117, 50, 122, 50, 0, 9, 67, 4, 112, 82, 136, 79, 125, 0, 0, 8, 66, 9, 144, 69, 135, 0, 76, 0, 10, 199, 92, 244, 139, 80, 16, 140, 20, 20, 9, 67, 80, 131, 192, 84, 134, 0, 9, 15, 70, 64, 131, 197, 56, 150, 0, 81, 127, 50, 120, 49, 87, 0, 6, 195, 84, 99, 192, 17, 0, 11, 68, 4, 193, 137, 20, 35, 55, 81, 37, 0, 10, 67, 48, 147, 65, 55, 127, 63, 117, 0, 12, 68, 52, 147, 149, 80, 63, 120, 50, 120, 47, 0, 19, 72, 12, 132, 143, 52, 244, 207, 52, 80, 49, 34, 134, 63, 13, 87, 134, 63, 0, 0, 12, 67, 100, 245, 82, 57, 141, 0, 106, 72, 34, 9, 11, 67, 100, 245, 82, 57, 130, 0, 72, 34, 9, 18, 8, 6, 195, 173, 18, 9, 14, 14, 5, 81, 127, 34, 120, 50, 38, 13, 0, 14, 69, 84, 227, 5, 77, 48, 123, 50, 55, 6, 119, 87, 0, 9, 67, 72, 82, 78, 34, 136, 50, 0, 14, 69, 32, 147, 132, 85, 48, 105, 120, 50, 70, 132, 86, 0, 10, 67, 4, 114, 78, 117, 79, 120, 50, 0, 0, 15, 70, 4, 195, 25, 76, 243, 128, 35, 55, 120, 87, 13, 50, 0, 15, 70, 80, 129, 82, 20, 243, 128, 4, 84, 138, 6, 122, 50, 0, 9, 198, 65, 35, 212, 21, 53, 0, 36, 17, 70, 65, 35, 212, 21, 53, 0, 48, 34, 134, 47, 119, 87, 47, 0, 10, 9, 198, 12, 243, 148, 21, 53, 0, 36, 17, 70, 12, 243, 148, 21, 53, 0, 49, 122, 50, 106, 119, 87, 47, 0, 10, 0, 11, 67, 32, 147, 64, 4, 105, 120, 63, 0, 9, 6, 195, 21, 53, 0, 17, 6, 195, 4, 115, 64, 17, 0, 18, 70, 92, 128, 84, 21, 97, 82, 58, 123, 47, 119, 82, 112, 0, 103, 66, 8, 17, 70, 92, 128, 84, 21, 97, 82, 58, 122, 47, 119, 82, 112, 0, 66, 8, 12, 68, 32, 19, 143, 36, 105, 35, 50, 6, 137, 0, 12, 68, 12, 17, 5, 80, 49, 117, 70, 119, 47, 0, 0, 0, 10, 67, 100, 246, 79, 57, 134, 57, 134, 0, 16, 70, 80, 19, 12, 100, 131, 192, 47, 35, 55, 120, 6, 105, 134, 0, 0, 0, 16, 70, 92, 129, 82, 21, 97, 82, 58, 2, 138, 44, 119, 82, 112, 0, 17, 70, 76, 16, 143, 80, 85, 82, 87, 35, 69, 13, 47, 6, 146, 0, 105, 16, 70, 76, 16, 143, 80, 85, 82, 87, 35, 69, 13, 47, 6, 126, 0, 11, 68, 16, 243, 143, 72, 70, 134, 50, 112, 0, 12, 68, 4, 66, 5, 72, 35, 70, 105, 6, 140, 0, 9, 3, 95, 35, 57, 47, 35, 69, 0, 13, 4, 95, 20, 12, 4, 47, 6, 120, 55, 70, 13, 0, 0, 14, 69, 37, 48, 66, 20, 192, 120, 86, 13, 69, 119, 55, 0, 12, 69, 76, 130, 76, 60, 128, 89, 135, 55, 134, 0, 14, 69, 92, 21, 19, 60, 224, 58, 122, 47, 87, 13, 50, 0, 12, 69, 36, 227, 129, 72, 64, 120, 50, 112, 70, 0, 9, 67, 4, 195, 0, 128, 55, 0, 42, 0, 14, 70, 72, 86, 78, 60, 193, 0, 34, 119, 50, 116, 70, 0, 17, 70, 52, 242, 1, 52, 208, 68, 63, 134, 105, 6, 35, 63, 111, 70, 0, 0, 18, 71, 88, 19, 5, 57, 66, 78, 20, 82, 35, 55, 13, 50, 47, 135, 50, 0, 12, 6, 19, 195, 173, 4, 8, 5, 89, 127, 13, 0, 10, 199, 76, 83, 73, 9, 33, 86, 20, 65, 6, 195, 20, 69, 0, 17, 0, 11, 68, 12, 242, 5, 56, 49, 134, 13, 50, 0, 12, 68, 4, 225, 18, 20, 122, 50, 70, 34, 136, 0, 7, 196, 12, 17, 9, 104, 66, 11, 67, 41, 83, 25, 73, 132, 55, 6, 135, 0, 11, 68, 12, 243, 15, 72, 49, 123, 55, 112, 0, 0, 13, 69, 85, 49, 70, 84, 192, 57, 132, 87, 81, 116, 0, 15, 69, 52, 148, 204, 20, 64, 63, 120, 87, 55, 6, 119, 70, 0, 0, 9, 198, 61, 97, 82, 48, 244, 132, 65, 16, 70, 24, 244, 141, 36, 48, 64, 81, 130, 63, 6, 135, 49, 13, 0, 10, 67, 16, 18, 83, 70, 136, 120, 87, 0, 0, 18, 71, 20, 194, 90, 4, 33, 84, 32, 111, 55, 120, 86, 13, 69, 13, 85, 0, 16, 70, 65, 35, 214, 20, 224, 197, 48, 34, 122, 82, 6, 148, 87, 0, 0, 11, 68, 40, 243, 129, 32, 73, 134, 50, 13, 0, 11, 68, 16, 147, 129, 32, 70, 135, 50, 13, 0, 10, 67, 76, 181, 65, 87, 49, 132, 13, 0, 11, 68, 64, 244, 211, 20, 48, 122, 87, 37, 0, 20, 72, 32, 19, 12, 20, 197, 73, 4, 128, 105, 35, 55, 111, 6, 55, 132, 57, 13, 0, 10, 67, 4, 117, 69, 136, 79, 57, 132, 0, 0, 15, 69, 72, 240, 149, 77, 64, 34, 134, 69, 6, 123, 87, 47, 0, 14, 69, 16, 148, 212, 72, 240, 70, 120, 87, 47, 34, 134, 0, 0, 15, 70, 32, 20, 212, 36, 225, 192, 105, 136, 87, 47, 120, 66, 0, 9, 198, 77, 80, 140, 36, 209, 64, 66, 17, 70, 65, 35, 212, 20, 113, 64, 48, 34, 134, 47, 13, 88, 136, 0, 103, 16, 70, 65, 35, 212, 20, 113, 64, 48, 34, 122, 47, 13, 88, 136, 0, 9, 198, 61, 85, 18, 4, 113, 64, 65, 15, 70, 8, 20, 146, 4, 113, 64, 69, 112, 34, 124, 88, 0, 103, 14, 70, 8, 20, 146, 4, 113, 64, 69, 35, 34, 124, 88, 0, 0, 17, 70, 52, 243, 148, 4, 117, 69, 63, 122, 50, 106, 13, 79, 57, 132, 0, 10, 199, 52, 19, 135, 4, 225, 83, 20, 65, 18, 71, 8, 243, 15, 28, 225, 83, 20, 69, 122, 55, 13, 50, 6, 136, 86, 0, 0, 13, 68, 32, 83, 9, 96, 105, 127, 55, 120, 49, 87, 0, 0, 14, 69, 36, 225, 9, 13, 64, 120, 50, 70, 6, 135, 47, 0, 13, 69, 33, 84, 211, 5, 32, 105, 123, 86, 6, 125, 0, 15, 69, 21, 48, 207, 73, 64, 119, 87, 49, 6, 130, 47, 0, 36, 0, 15, 70, 92, 21, 6, 61, 33, 0, 58, 122, 47, 81, 13, 70, 0, 15, 70, 92, 80, 144, 4, 113, 64, 58, 119, 69, 48, 136, 73, 0, 13, 70, 76, 51, 213, 72, 113, 64, 87, 49, 126, 73, 0, 15, 70, 72, 85, 133, 72, 145, 64, 34, 119, 82, 13, 34, 37, 0, 16, 70, 16, 85, 143, 80, 81, 64, 70, 119, 82, 134, 47, 6, 127, 0, 0, 13, 6, 3, 18, 195, 168, 13, 5, 49, 34, 119, 63, 0, 6, 195, 16, 150, 64, 17, 0, 15, 70, 32, 21, 193, 36, 144, 78, 105, 13, 58, 6, 142, 50, 0, 12, 68, 80, 147, 4, 20, 47, 120, 55, 70, 13, 0, 15, 70, 76, 246, 65, 8, 80, 78, 87, 137, 13, 69, 127, 50, 0, 11, 68, 13, 33, 80, 20, 49, 34, 136, 48, 0, 22, 72, 4, 229, 5, 12, 81, 5, 57, 64, 35, 50, 47, 120, 87, 6, 127, 70, 13, 50, 47, 0, 0, 10, 67, 56, 80, 82, 4, 50, 140, 0, 12, 0, 17, 70, 60, 33, 83, 37, 70, 64, 134, 69, 6, 127, 87, 13, 47, 37, 0, 0, 20, 71, 52, 243, 69, 57, 64, 82, 100, 63, 134, 63, 13, 50, 106, 138, 34, 37, 0, 103, 19, 71, 52, 243, 69, 57, 64, 82, 100, 63, 134, 63, 13, 50, 47, 13, 34, 37, 0, 17, 71, 21, 66, 81, 84, 85, 20, 20, 119, 47, 121, 49, 13, 47, 0, 103, 10, 199, 21, 66, 81, 84, 85, 20, 20, 65, 0, 7, 196, 77, 66, 76, 48, 32, 10, 68, 48, 245, 73, 76, 55, 132, 37, 0, 11, 68, 9, 34, 69, 56, 69, 34, 142, 50, 0, 7, 196, 52, 147, 1, 56, 66, 17, 70, 77, 1, 67, 36, 209, 78, 87, 48, 119, 87, 111, 63, 13, 50, 0, 19, 72, 76, 147, 8, 61, 81, 84, 80, 80, 87, 111, 55, 115, 58, 6, 119, 47, 0, 9, 67, 32, 150, 65, 105, 135, 117, 0, 12, 68, 12, 243, 15, 56, 49, 134, 55, 13, 50, 0, 0, 14, 69, 8, 83, 9, 104, 80, 69, 119, 55, 6, 127, 86, 0, 13, 69, 85, 49, 65, 28, 80, 57, 132, 87, 111, 73, 0, 14, 69, 52, 244, 143, 76, 80, 63, 13, 34, 6, 134, 87, 0, 10, 67, 48, 145, 78, 55, 127, 13, 50, 0, 0, 9, 198, 16, 18, 15, 52, 86, 64, 66, 5, 194, 21, 80, 17, 0, 11, 67, 52, 241, 84, 63, 134, 6, 119, 47, 0, 19, 71, 4, 208, 82, 100, 195, 9, 76, 35, 63, 13, 34, 6, 120, 55, 120, 87, 0, 0, 12, 68, 52, 83, 5, 20, 63, 136, 55, 136, 0, 103, 11, 68, 52, 83, 5, 20, 63, 119, 55, 136, 0, 11, 68, 32, 83, 12, 60, 105, 13, 55, 134, 0, 15, 70, 24, 19, 73, 48, 144, 82, 81, 13, 63, 120, 55, 140, 0, 14, 68, 16, 80, 149, 80, 70, 136, 69, 6, 57, 132, 0, 103, 12, 68, 16, 80, 149, 80, 70, 136, 69, 57, 132, 0, 19, 72, 5, 4, 18, 20, 229, 9, 12, 80, 117, 48, 34, 119, 50, 106, 120, 87, 0, 0, 15, 69, 8, 244, 212, 60, 224, 69, 129, 87, 47, 13, 50, 0, 103, 8, 67, 48, 145, 82, 55, 143, 0, 8, 197, 17, 147, 129, 52, 240, 65, 0, 9, 198, 36, 229, 5, 72, 147, 64, 65, 16, 70, 8, 84, 212, 21, 53, 0, 69, 119, 87, 47, 13, 87, 47, 0, 0, 17, 71, 25, 34, 67, 5, 52, 197, 20, 81, 34, 120, 49, 117, 87, 136, 0, 0, 12, 68, 29, 82, 68, 60, 79, 58, 127, 70, 134, 0, 13, 68, 76, 18, 5, 48, 87, 124, 105, 6, 119, 55, 0, 12, 68, 85, 50, 78, 28, 57, 132, 86, 120, 66, 0, 16, 70, 77, 4, 129, 100, 48, 78, 87, 48, 34, 136, 49, 35, 50, 0, 12, 68, 76, 19, 1, 16, 87, 35, 55, 13, 70, 0, 10, 67, 60, 176, 89, 134, 49, 6, 136, 0, 0, 8, 67, 64, 145, 82, 48, 140, 0, 15, 70, 12, 245, 83, 12, 245, 83, 49, 132, 87, 49, 132, 87, 0, 0, 12, 67, 4, 225, 0, 35, 50, 70, 0, 72, 8, 9, 9, 67, 72, 81, 83, 34, 127, 87, 0, 18, 70, 52, 243, 148, 72, 80, 76, 63, 122, 50, 47, 34, 120, 6, 128, 55, 0, 14, 70, 76, 242, 143, 85, 35, 128, 87, 134, 73, 126, 50, 0, 0, 9, 66, 4, 224, 117, 50, 0, 34, 9, 10, 67, 80, 147, 153, 47, 135, 50, 37, 0, 16, 71, 21, 52, 197, 57, 66, 65, 48, 111, 87, 119, 50, 89, 116, 0, 0, 17, 70, 20, 118, 80, 80, 144, 78, 120, 73, 6, 120, 48, 89, 13, 50, 0, 16, 70, 77, 84, 5, 72, 208, 78, 87, 132, 48, 112, 63, 35, 50, 0, 12, 201, 76, 147, 85, 49, 64, 78, 20, 245, 83, 67, 0, 10, 67, 72, 83, 143, 34, 127, 50, 134, 0, 11, 68, 76, 243, 129, 72, 87, 134, 50, 125, 0, 7, 196, 84, 226, 3, 72, 17, 0, 16, 69, 8, 86, 79, 56, 64, 69, 120, 57, 122, 50, 70, 0, 74, 12, 13, 69, 12, 240, 207, 60, 224, 49, 13, 49, 132, 50, 0, 0, 0, 19, 71, 65, 35, 193, 13, 66, 86, 20, 48, 34, 134, 6, 35, 49, 47, 120, 82, 0, 0, 12, 68, 4, 115, 133, 76, 35, 79, 50, 13, 87, 0, 12, 68, 12, 243, 135, 60, 49, 122, 66, 79, 134, 0, 12, 68, 76, 147, 133, 92, 87, 120, 50, 57, 132, 0, 19, 72, 76, 130, 76, 48, 83, 1, 28, 128, 89, 4, 111, 55, 6, 136, 55, 13, 0, 0, 9, 197, 16, 85, 1, 36, 192, 103, 66, 15, 70, 12, 20, 200, 52, 84, 133, 49, 35, 88, 63, 140, 0, 103, 14, 70, 12, 20, 200, 52, 84, 133, 49, 35, 89, 63, 140, 0, 0, 16, 70, 8, 145, 5, 24, 244, 132, 69, 120, 70, 120, 81, 13, 70, 0, 15, 70, 65, 33, 77, 36, 84, 128, 48, 34, 13, 63, 140, 0, 103, 15, 70, 65, 33, 77, 36, 84, 128, 48, 34, 119, 63, 120, 112, 0, 9, 198, 60, 53, 15, 8, 84, 128, 66, 14, 70, 12, 20, 200, 36, 84, 128, 49, 35, 89, 6, 140, 0, 14, 70, 4, 227, 212, 32, 84, 128, 117, 50, 123, 84, 112, 0, 0, 10, 67, 64, 147, 148, 48, 135, 50, 47, 0, 8, 67, 21, 113, 64, 57, 132, 0, 0, 21, 72, 8, 19, 135, 48, 81, 5, 76, 128, 69, 35, 66, 79, 55, 13, 70, 6, 119, 89, 0, 12, 68, 12, 240, 143, 48, 49, 134, 69, 122, 55, 0, 11, 68, 5, 34, 83, 20, 117, 34, 135, 86, 0, 0, 17, 70, 80, 83, 133, 72, 145, 133, 47, 119, 50, 112, 34, 6, 127, 81, 0, 13, 69, 12, 20, 133, 21, 32, 49, 13, 34, 6, 140, 0, 0, 15, 70, 92, 147, 132, 36, 225, 192, 58, 135, 50, 70, 120, 66, 0, 0, 0, 11, 68, 12, 131, 15, 20, 49, 55, 134, 37, 0, 21, 68, 92, 147, 132, 76, 58, 6, 135, 50, 70, 86, 15, 6, 123, 48, 0, 81, 117, 112, 32, 24, 68, 92, 147, 132, 76, 58, 6, 135, 50, 70, 86, 15, 70, 6, 133, 50, 0, 81, 100, 111, 119, 110, 32, 13, 68, 72, 85, 83, 20, 34, 127, 6, 57, 132, 86, 0, 11, 68, 8, 146, 143, 84, 69, 127, 88, 132, 0, 0, 19, 67, 16, 145, 0, 70, 120, 70, 50, 122, 47, 0, 32, 78, 81, 110, 111, 116, 32, 10, 67, 16, 145, 0, 70, 120, 70, 0, 32, 17, 67, 32, 17, 0, 105, 4, 35, 70, 111, 47, 0, 14, 81, 105, 116, 32, 21, 67, 32, 17, 0, 2, 105, 117, 70, 2, 69, 120, 50, 0, 35, 81, 98, 101, 101, 110, 32, 16, 67, 32, 17, 0, 105, 35, 70, 47, 132, 0, 14, 81, 116, 111, 32, 16, 67, 32, 17, 0, 105, 2, 35, 70, 47, 114, 0, 81, 116, 111, 32, 11, 67, 32, 17, 0, 4, 105, 35, 70, 0, 14, 13, 67, 32, 17, 0, 2, 105, 117, 70, 0, 35, 12, 9, 20, 73, 4, 192, 149, 69, 81, 82, 69, 81, 64, 35, 55, 69, 13, 49, 126, 49, 37, 0, 14, 69, 17, 33, 65, 53, 64, 70, 34, 119, 63, 48, 47, 0, 0, 15, 70, 24, 244, 148, 84, 225, 64, 81, 130, 74, 13, 50, 0, 103, 8, 66, 16, 144, 70, 135, 0, 41, 14, 70, 92, 20, 146, 36, 225, 192, 58, 130, 34, 120, 66, 0, 18, 70, 25, 33, 81, 84, 83, 148, 81, 34, 111, 49, 58, 119, 50, 47, 0, 36, 14, 70, 24, 244, 148, 84, 225, 64, 81, 130, 74, 132, 50, 0, 9, 66, 16, 144, 70, 4, 120, 0, 9, 16, 66, 20, 112, 81, 130, 119, 79, 86, 6, 118, 63, 48, 116, 0, 9, 0, 17, 71, 88, 83, 135, 20, 19, 131, 20, 82, 119, 50, 73, 13, 50, 87, 0, 18, 71, 20, 51, 205, 52, 84, 131, 20, 6, 127, 49, 4, 122, 63, 126, 87, 0, 0, 11, 68, 4, 195, 5, 56, 35, 55, 13, 50, 0, 12, 68, 48, 147, 133, 56, 55, 120, 50, 111, 50, 0, 11, 68, 48, 16, 143, 72, 55, 136, 69, 112, 0, 12, 68, 5, 50, 197, 92, 117, 87, 49, 57, 132, 0, 11, 68, 5, 34, 69, 76, 138, 34, 127, 86, 0, 0, 14, 69, 64, 19, 69, 48, 16, 48, 35, 63, 13, 55, 13, 0, 13, 69, 12, 129, 82, 36, 80, 89, 138, 34, 6, 127, 0, 14, 69, 64, 82, 201, 56, 112, 48, 127, 49, 6, 120, 66, 0, 14, 69, 80, 148, 129, 16, 80, 47, 135, 34, 6, 136, 70, 0, 20, 73, 72, 21, 1, 80, 245, 73, 48, 193, 64, 34, 35, 47, 13, 47, 6, 132, 120, 0, 14, 69, 24, 147, 129, 48, 80, 81, 111, 50, 124, 55, 37, 0, 17, 70, 4, 195, 5, 49, 82, 65, 35, 55, 111, 55, 6, 132, 57, 13, 0, 12, 69, 4, 195, 5, 48, 80, 117, 55, 127, 55, 0, 0, 0, 16, 70, 41, 82, 197, 8, 246, 0, 73, 132, 49, 69, 122, 49, 87, 0, 17, 71, 24, 21, 143, 85, 34, 84, 20, 81, 136, 82, 14, 34, 111, 47, 0, 0, 11, 68, 76, 243, 142, 100, 87, 123, 50, 120, 0, 12, 68, 37, 35, 206, 100, 135, 34, 13, 50, 120, 0, 0, 13, 69, 52, 240, 137, 48, 80, 63, 134, 69, 116, 0, 103, 14, 69, 76, 16, 137, 56, 16, 87, 117, 69, 127, 50, 13, 0, 15, 69, 24, 144, 83, 12, 240, 81, 127, 6, 35, 87, 49, 134, 0, 0, 10, 67, 80, 147, 129, 47, 127, 50, 13, 0, 0, 13, 69, 64, 147, 5, 85, 0, 48, 135, 55, 123, 48, 0, 0, 11, 200, 4, 229, 1, 72, 53, 9, 12, 16, 66, 11, 68, 72, 83, 129, 48, 34, 127, 50, 116, 0, 11, 68, 64, 83, 129, 48, 48, 127, 50, 116, 0, 20, 72, 16, 83, 9, 8, 84, 129, 80, 80, 70, 111, 55, 120, 69, 13, 34, 13, 47, 0, 12, 68, 12, 19, 129, 48, 49, 13, 50, 35, 55, 0, 11, 68, 8, 19, 129, 48, 69, 136, 50, 116, 0, 0, 13, 69, 77, 64, 82, 73, 144, 87, 47, 124, 34, 120, 0, 10, 67, 73, 82, 78, 34, 132, 111, 50, 0, 17, 70, 52, 81, 9, 12, 147, 133, 63, 119, 70, 13, 87, 13, 50, 0, 103, 15, 70, 52, 81, 9, 12, 147, 133, 63, 119, 70, 87, 13, 50, 0, 0, 10, 67, 16, 19, 129, 70, 136, 50, 13, 0, 9, 198, 8, 18, 18, 4, 147, 128, 66, 17, 70, 32, 243, 73, 56, 83, 64, 105, 122, 63, 13, 50, 13, 63, 0, 103, 16, 70, 32, 243, 73, 56, 83, 64, 105, 122, 63, 120, 50, 119, 63, 0, 0, 19, 71, 64, 85, 18, 60, 193, 85, 52, 48, 13, 47, 34, 134, 55, 127, 13, 63, 0, 16, 71, 12, 245, 78, 80, 84, 133, 16, 49, 133, 50, 47, 112, 70, 0, 19, 71, 4, 97, 137, 16, 21, 137, 80, 35, 81, 120, 70, 6, 136, 82, 120, 47, 0, 0, 10, 67, 104, 85, 83, 86, 57, 132, 87, 0, 10, 67, 81, 148, 15, 47, 135, 48, 134, 0, 14, 70, 77, 84, 16, 48, 145, 82, 87, 13, 48, 55, 143, 0, 15, 70, 61, 85, 16, 61, 53, 0, 133, 47, 48, 134, 87, 47, 0, 12, 68, 52, 244, 5, 16, 63, 134, 48, 119, 70, 0, 11, 68, 5, 33, 213, 20, 125, 79, 57, 132, 0, 0, 13, 69, 76, 80, 77, 85, 48, 89, 136, 63, 13, 87, 0, 15, 70, 93, 34, 84, 4, 35, 5, 34, 135, 47, 13, 69, 116, 0, 13, 69, 76, 84, 137, 21, 48, 87, 127, 34, 127, 86, 0, 15, 70, 24, 19, 12, 36, 35, 5, 81, 35, 55, 13, 69, 116, 0, 0, 15, 70, 77, 65, 80, 32, 83, 128, 87, 47, 127, 82, 13, 50, 0, 17, 70, 4, 225, 207, 48, 19, 128, 35, 66, 79, 6, 134, 55, 13, 50, 0, 6, 66, 20, 128, 136, 0, 0, 15, 70, 64, 192, 71, 84, 147, 135, 48, 55, 136, 79, 120, 66, 0, 17, 71, 20, 21, 133, 76, 68, 143, 64, 127, 82, 86, 70, 34, 122, 48, 0, 0, 14, 70, 72, 82, 78, 16, 81, 82, 34, 136, 50, 70, 140, 0, 21, 73, 52, 17, 5, 52, 242, 83, 20, 195, 5, 63, 35, 70, 13, 63, 13, 86, 119, 55, 0, 17, 70, 13, 84, 212, 60, 209, 82, 49, 6, 123, 87, 47, 13, 63, 112, 0, 11, 68, 4, 34, 15, 72, 117, 69, 105, 131, 0, 0, 14, 69, 5, 34, 83, 20, 224, 13, 34, 120, 86, 13, 50, 0, 0, 15, 70, 92, 131, 197, 88, 84, 128, 105, 132, 119, 82, 112, 0, 66, 14, 70, 76, 49, 80, 80, 84, 128, 87, 119, 48, 47, 112, 0, 0, 0, 12, 68, 16, 84, 133, 44, 70, 119, 34, 120, 49, 0, 0, 28, 69, 76, 131, 213, 48, 64, 89, 115, 70, 105, 35, 82, 47, 114, 0, 74, 32, 12, 82, 104, 97, 118, 101, 32, 116, 111, 32, 21, 69, 76, 131, 213, 48, 64, 89, 115, 70, 13, 82, 0, 35, 77, 81, 104, 97, 118, 101, 32, 15, 69, 76, 131, 213, 48, 64, 4, 89, 115, 70, 0, 32, 9, 12, 13, 69, 52, 20, 129, 84, 64, 63, 13, 34, 128, 70, 0, 13, 69, 33, 84, 146, 4, 128, 105, 123, 34, 6, 136, 0, 13, 69, 33, 84, 146, 4, 128, 105, 13, 34, 6, 124, 0, 13, 3, 226, 132, 162, 47, 34, 136, 70, 63, 125, 49, 0, 0, 13, 70, 48, 242, 78, 56, 148, 128, 55, 123, 50, 139, 0, 14, 70, 64, 147, 206, 20, 84, 128, 48, 142, 50, 6, 140, 0, 13, 202, 12, 243, 148, 20, 212, 12, 5, 66, 86, 20, 66, 25, 74, 5, 85, 8, 61, 34, 84, 5, 66, 86, 20, 117, 85, 6, 129, 34, 13, 106, 136, 106, 120, 82, 0, 103, 24, 74, 5, 85, 8, 61, 34, 84, 5, 66, 86, 20, 128, 85, 6, 122, 34, 111, 47, 13, 47, 120, 82, 0, 0, 0, 20, 72, 32, 19, 12, 20, 197, 74, 4, 128, 105, 35, 55, 111, 6, 55, 132, 57, 13, 0, 0, 0, 19, 67, 32, 21, 133, 105, 117, 82, 50, 122, 47, 0, 35, 14, 81, 110, 111, 116, 32, 19, 67, 32, 21, 133, 105, 117, 82, 50, 4, 122, 47, 0, 35, 81, 110, 111, 116, 32, 21, 67, 32, 21, 133, 2, 105, 117, 82, 2, 69, 120, 50, 0, 35, 81, 98, 101, 101, 110, 32, 13, 67, 32, 21, 133, 105, 35, 82, 0, 35, 9, 72, 12, 10, 67, 48, 149, 133, 55, 120, 82, 0, 36, 10, 67, 48, 149, 133, 55, 135, 82, 0, 10, 10, 67, 48, 21, 129, 55, 124, 82, 13, 0, 13, 70, 12, 240, 203, 21, 145, 64, 49, 122, 49, 135, 0, 0, 6, 195, 72, 85, 128, 24, 6, 195, 32, 149, 128, 17, 0, 14, 68, 44, 244, 133, 4, 49, 112, 34, 6, 127, 13, 0, 103, 13, 68, 44, 244, 133, 4, 49, 129, 34, 6, 127, 13, 0, 10, 68, 24, 244, 131, 20, 81, 131, 87, 0, 11, 68, 12, 19, 143, 20, 49, 13, 50, 132, 0, 12, 68, 5, 35, 205, 4, 117, 34, 134, 63, 13, 0, 0, 15, 69, 72, 81, 140, 21, 128, 34, 127, 81, 55, 119, 49, 87, 0, 16, 69, 52, 147, 149, 21, 64, 63, 120, 50, 57, 132, 6, 119, 47, 0, 12, 69, 32, 82, 70, 21, 32, 105, 119, 81, 112, 0, 8, 67, 20, 145, 0, 127, 70, 0, 0, 10, 67, 80, 16, 149, 47, 35, 69, 132, 0, 0, 18, 71, 36, 225, 133, 72, 83, 131, 20, 120, 50, 81, 13, 34, 13, 50, 87, 0, 0, 0, 13, 69, 88, 148, 137, 48, 80, 82, 120, 34, 116, 0, 103, 13, 69, 16, 240, 201, 48, 80, 70, 134, 87, 116, 0, 103, 13, 67, 28, 85, 0, 2, 79, 119, 47, 0, 12, 35, 9, 14, 69, 32, 84, 143, 36, 48, 105, 111, 34, 134, 120, 49, 0, 18, 73, 4, 48, 207, 84, 50, 5, 52, 83, 148, 117, 49, 132, 89, 63, 149, 0, 13, 3, 226, 132, 150, 50, 57, 132, 63, 13, 34, 134, 0, 0, 15, 70, 76, 19, 131, 32, 86, 128, 87, 35, 50, 74, 119, 86, 0, 10, 67, 52, 243, 153, 63, 123, 50, 120, 0, 0, 17, 71, 76, 19, 9, 76, 37, 82, 100, 87, 128, 55, 87, 69, 34, 37, 0, 19, 71, 37, 51, 211, 12, 83, 5, 76, 135, 87, 6, 122, 87, 13, 55, 127, 86, 0, 0, 12, 68, 61, 34, 79, 56, 122, 34, 6, 142, 50, 0, 10, 68, 36, 227, 133, 72, 120, 50, 112, 0, 12, 68, 32, 21, 143, 12, 105, 35, 82, 13, 49, 0, 14, 68, 21, 128, 76, 80, 119, 79, 86, 6, 122, 55, 47, 0, 19, 72, 5, 85, 15, 52, 240, 137, 48, 80, 128, 47, 13, 63, 13, 69, 139, 55, 0, 0, 13, 69, 16, 20, 8, 56, 80, 70, 35, 81, 50, 37, 0, 8, 197, 72, 245, 1, 80, 80, 66, 18, 70, 72, 80, 68, 60, 227, 25, 4, 34, 127, 70, 6, 134, 50, 55, 120, 0, 13, 69, 56, 81, 193, 80, 80, 50, 111, 79, 136, 47, 0, 13, 69, 48, 145, 193, 80, 80, 55, 127, 79, 136, 47, 0, 14, 69, 13, 84, 129, 80, 80, 49, 57, 141, 34, 136, 47, 0, 8, 197, 5, 84, 143, 72, 16, 66, 0, 16, 70, 12, 149, 1, 16, 83, 0, 87, 120, 47, 13, 70, 119, 55, 0, 0, 18, 71, 88, 81, 197, 80, 16, 140, 20, 82, 119, 73, 111, 47, 13, 69, 116, 0, 11, 199, 36, 229, 5, 73, 37, 80, 80, 67, 36, 11, 199, 36, 229, 5, 73, 37, 80, 80, 65, 10, 20, 71, 36, 225, 140, 84, 83, 154, 4, 120, 50, 81, 55, 132, 6, 119, 50, 86, 13, 0, 13, 3, 226, 133, 148, 47, 132, 85, 6, 126, 70, 86, 0, 0, 11, 68, 44, 21, 9, 20, 49, 136, 47, 37, 0, 0, 15, 70, 49, 82, 197, 92, 20, 141, 55, 132, 49, 58, 130, 63, 0, 13, 69, 32, 84, 141, 21, 48, 105, 126, 63, 127, 86, 0, 13, 69, 4, 66, 69, 85, 48, 117, 70, 57, 132, 86, 0, 0, 15, 70, 28, 147, 12, 36, 19, 128, 73, 120, 55, 127, 13, 50, 0, 14, 70, 76, 80, 76, 36, 243, 128, 87, 127, 55, 142, 50, 0, 16, 70, 12, 20, 129, 88, 19, 128, 49, 35, 34, 13, 82, 35, 50, 0, 0, 9, 198, 4, 229, 9, 32, 84, 143, 65, 0, 13, 68, 56, 84, 1, 48, 50, 119, 48, 6, 128, 55, 0, 12, 68, 88, 148, 201, 80, 82, 120, 86, 111, 47, 0, 13, 68, 88, 19, 5, 80, 82, 35, 55, 6, 136, 0, 103, 11, 68, 88, 19, 5, 80, 82, 35, 55, 136, 0, 12, 68, 84, 229, 9, 20, 123, 50, 47, 6, 135, 0, 12, 68, 72, 84, 5, 48, 34, 111, 48, 119, 55, 0, 11, 68, 64, 20, 1, 48, 48, 136, 48, 116, 0, 12, 68, 8, 148, 5, 16, 69, 135, 48, 119, 70, 0, 15, 70, 8, 19, 12, 5, 53, 0, 69, 35, 55, 13, 87, 47, 0, 13, 3, 226, 133, 147, 58, 122, 50, 85, 6, 126, 70, 0, 0, 23, 73, 72, 84, 212, 61, 32, 84, 36, 243, 128, 34, 119, 87, 47, 13, 34, 6, 136, 89, 13, 50, 0, 23, 73, 72, 84, 208, 37, 32, 84, 36, 243, 128, 34, 119, 87, 48, 111, 34, 6, 136, 89, 13, 50, 0, 23, 73, 65, 33, 80, 5, 32, 84, 36, 243, 128, 48, 34, 119, 48, 13, 34, 6, 136, 89, 13, 50, 0, 14, 69, 52, 148, 197, 73, 144, 63, 120, 86, 13, 34, 120, 0, 13, 69, 32, 17, 199, 37, 48, 105, 35, 79, 120, 87, 0, 21, 73, 4, 97, 137, 72, 208, 84, 36, 243, 128, 35, 81, 112, 63, 6, 136, 89, 13, 50, 0, 0, 17, 70, 8, 85, 23, 20, 83, 128, 69, 120, 47, 58, 127, 50, 0, 74, 12, 16, 70, 32, 17, 18, 36, 19, 128, 105, 136, 70, 34, 127, 13, 50, 0, 16, 70, 76, 52, 143, 81, 83, 64, 87, 49, 34, 134, 47, 13, 63, 0, 16, 70, 48, 144, 73, 76, 243, 128, 55, 127, 6, 136, 86, 122, 50, 0, 0, 0, 12, 68, 44, 20, 133, 56, 49, 35, 34, 13, 50, 0, 11, 68, 16, 83, 8, 36, 70, 119, 55, 37, 0, 15, 70, 64, 148, 85, 4, 229, 0, 48, 127, 49, 13, 50, 47, 0, 12, 68, 61, 2, 78, 20, 134, 48, 6, 135, 50, 0, 11, 68, 44, 244, 10, 20, 49, 122, 48, 37, 0, 12, 201, 16, 148, 210, 21, 5, 84, 4, 35, 5, 66, 12, 68, 12, 18, 149, 56, 49, 136, 73, 13, 50, 0, 12, 68, 9, 84, 197, 76, 69, 123, 87, 121, 86, 0, 0, 13, 69, 48, 21, 78, 12, 128, 55, 124, 50, 74, 0, 103, 14, 69, 8, 147, 141, 4, 224, 69, 120, 50, 63, 35, 50, 0, 13, 69, 8, 19, 12, 4, 64, 69, 35, 55, 13, 70, 0, 0, 16, 70, 52, 21, 9, 48, 64, 64, 63, 117, 47, 120, 55, 70, 13, 0, 0, 18, 71, 64, 19, 5, 77, 66, 78, 20, 48, 35, 55, 13, 87, 47, 135, 50, 0, 17, 71, 44, 148, 139, 12, 19, 4, 100, 49, 145, 49, 6, 122, 70, 37, 0, 18, 71, 36, 229, 133, 72, 225, 83, 76, 120, 50, 82, 112, 50, 6, 119, 87, 0, 9, 67, 4, 128, 64, 124, 105, 124, 0, 0, 12, 68, 52, 147, 132, 100, 63, 120, 50, 70, 37, 0, 10, 67, 12, 193, 79, 49, 55, 127, 134, 0, 12, 68, 40, 20, 1, 56, 73, 13, 48, 35, 50, 0, 12, 68, 28, 83, 146, 20, 88, 122, 50, 34, 13, 0, 20, 72, 4, 229, 9, 64, 131, 206, 4, 192, 35, 50, 47, 6, 120, 81, 13, 50, 116, 0, 9, 3, 95, 49, 15, 81, 6, 126, 0, 0, 10, 67, 4, 128, 66, 136, 105, 35, 69, 0, 10, 67, 56, 83, 206, 50, 127, 122, 50, 0, 0, 0, 9, 67, 88, 81, 192, 82, 119, 73, 0, 10, 67, 60, 193, 68, 134, 55, 119, 70, 0, 8, 67, 20, 113, 192, 119, 79, 0, 15, 71, 8, 245, 82, 28, 83, 201, 76, 69, 141, 88, 58, 124, 0, 11, 3, 226, 130, 172, 57, 141, 34, 134, 86, 0, 0, 11, 68, 76, 20, 129, 32, 87, 138, 34, 13, 0, 12, 5, 16, 9, 195, 177, 1, 48, 127, 65, 117, 0, 12, 68, 60, 244, 129, 32, 6, 132, 34, 6, 124, 0, 0, 13, 5, 13, 15, 195, 171, 20, 63, 134, 6, 119, 47, 0, 13, 69, 69, 82, 86, 21, 32, 49, 58, 120, 82, 112, 0, 15, 70, 32, 243, 69, 64, 17, 197, 105, 134, 63, 48, 136, 73, 0, 14, 70, 12, 20, 211, 21, 69, 5, 49, 117, 87, 119, 47, 0, 0, 15, 70, 40, 20, 205, 36, 225, 64, 73, 35, 86, 63, 120, 50, 0, 16, 70, 21, 48, 193, 72, 115, 212, 111, 87, 49, 6, 125, 79, 134, 0, 9, 198, 12, 20, 195, 4, 65, 64, 66, 9, 3, 226, 130, 169, 58, 122, 50, 0, 0, 9, 67, 72, 81, 192, 34, 119, 73, 0, 10, 3, 226, 130, 168, 34, 132, 48, 127, 0, 0, 10, 68, 4, 195, 1, 100, 117, 55, 136, 0, 10, 3, 95, 50, 15, 87, 6, 119, 49, 0, 0, 16, 69, 72, 84, 15, 77, 64, 34, 4, 127, 48, 6, 134, 87, 47, 0, 17, 70, 65, 33, 83, 80, 145, 197, 48, 34, 119, 87, 47, 6, 127, 88, 0, 14, 69, 12, 245, 133, 73, 64, 49, 134, 82, 6, 126, 47, 0, 0, 9, 66, 32, 80, 105, 127, 0, 72, 33, 13, 70, 76, 128, 76, 48, 245, 192, 89, 35, 55, 134, 0, 17, 70, 65, 34, 77, 21, 96, 76, 48, 34, 135, 63, 6, 127, 82, 116, 0, 7, 66, 40, 16, 57, 124, 0, 15, 70, 36, 208, 71, 36, 225, 64, 111, 63, 35, 73, 111, 50, 0, 8, 66, 24, 144, 81, 4, 135, 0, 16, 70, 5, 69, 1, 12, 129, 64, 35, 106, 35, 6, 89, 136, 0, 103, 16, 70, 5, 69, 1, 12, 129, 64, 35, 47, 6, 35, 89, 136, 0, 9, 11, 67, 4, 129, 77, 117, 105, 6, 119, 63, 0, 14, 70, 4, 50, 9, 48, 193, 64, 117, 49, 120, 55, 127, 0, 0, 0, 12, 68, 8, 83, 137, 56, 69, 119, 50, 120, 50, 0, 12, 68, 64, 20, 133, 56, 48, 117, 34, 119, 50, 0, 13, 68, 44, 244, 129, 56, 49, 130, 34, 6, 124, 50, 0, 10, 67, 32, 82, 0, 105, 119, 105, 0, 9, 21, 72, 12, 148, 131, 84, 213, 133, 57, 64, 87, 145, 49, 13, 63, 82, 119, 50, 47, 0, 105, 20, 72, 12, 148, 131, 84, 213, 133, 57, 64, 87, 126, 49, 13, 63, 82, 119, 50, 47, 0, 16, 70, 12, 16, 137, 56, 85, 0, 49, 35, 69, 121, 50, 13, 47, 0, 11, 68, 4, 35, 5, 72, 136, 69, 55, 112, 0, 0, 15, 69, 16, 144, 76, 60, 112, 70, 135, 13, 55, 128, 79, 0, 103, 15, 69, 17, 99, 210, 4, 176, 70, 14, 82, 131, 88, 35, 49, 0, 13, 69, 8, 243, 199, 36, 80, 69, 115, 79, 37, 0, 103, 12, 69, 8, 243, 199, 36, 80, 69, 132, 79, 37, 0, 0, 10, 67, 48, 146, 197, 55, 135, 49, 0, 12, 15, 70, 44, 20, 129, 12, 130, 64, 49, 117, 34, 125, 74, 37, 0, 15, 70, 49, 83, 12, 4, 38, 64, 55, 123, 55, 13, 69, 135, 0, 9, 198, 12, 243, 134, 48, 144, 212, 36, 18, 70, 12, 243, 134, 48, 144, 212, 49, 122, 50, 81, 55, 120, 49, 47, 0, 10, 0, 0, 12, 68, 16, 19, 148, 20, 70, 124, 50, 47, 136, 0, 20, 72, 65, 33, 67, 20, 65, 78, 12, 80, 48, 34, 119, 87, 111, 70, 13, 50, 87, 0, 16, 70, 64, 84, 134, 20, 53, 0, 48, 112, 81, 119, 49, 47, 0, 36, 16, 70, 64, 84, 134, 20, 53, 0, 48, 126, 81, 119, 49, 47, 0, 10, 17, 70, 25, 37, 73, 80, 147, 206, 81, 34, 132, 6, 120, 89, 13, 50, 0, 10, 67, 24, 150, 0, 81, 120, 49, 87, 0, 19, 72, 12, 243, 12, 20, 114, 65, 80, 80, 49, 13, 55, 127, 73, 120, 13, 47, 0, 9, 3, 95, 51, 15, 85, 6, 126, 0, 8, 4, 95, 15, 18, 4, 85, 0, 0, 14, 69, 76, 16, 137, 56, 80, 87, 117, 69, 6, 127, 50, 0, 13, 69, 52, 19, 9, 12, 80, 63, 35, 55, 111, 87, 0, 11, 69, 28, 21, 67, 32, 80, 79, 134, 89, 0, 0, 10, 66, 37, 48, 2, 120, 86, 0, 35, 9, 16, 70, 37, 52, 129, 20, 194, 64, 120, 86, 34, 6, 136, 55, 37, 0, 16, 70, 76, 132, 137, 48, 198, 64, 89, 34, 120, 55, 55, 120, 0, 32, 0, 14, 70, 29, 82, 78, 56, 84, 211, 79, 120, 50, 120, 87, 0, 0, 12, 68, 40, 20, 133, 16, 73, 35, 34, 119, 70, 0, 11, 68, 88, 148, 129, 48, 82, 143, 34, 116, 0, 11, 68, 28, 21, 133, 48, 79, 35, 82, 116, 0, 11, 68, 12, 244, 129, 48, 49, 122, 34, 116, 0, 10, 67, 4, 115, 199, 117, 79, 122, 79, 0, 0, 13, 69, 24, 147, 133, 77, 48, 81, 111, 50, 119, 87, 0, 13, 69, 16, 147, 135, 33, 144, 70, 120, 66, 79, 37, 0, 0, 0, 17, 71, 80, 83, 142, 21, 52, 197, 20, 47, 119, 50, 13, 87, 6, 127, 0, 0, 19, 72, 65, 54, 67, 32, 144, 84, 73, 144, 87, 135, 49, 6, 142, 47, 34, 120, 0, 13, 68, 32, 20, 133, 52, 105, 124, 34, 6, 127, 63, 0, 12, 68, 16, 147, 135, 100, 70, 120, 50, 73, 120, 0, 0, 13, 69, 76, 17, 133, 81, 144, 87, 136, 81, 47, 37, 0, 8, 197, 61, 85, 3, 73, 144, 65, 13, 69, 48, 149, 133, 49, 144, 55, 135, 82, 55, 120, 0, 0, 9, 66, 20, 192, 4, 119, 55, 0, 9, 5, 194, 36, 64, 17, 0, 10, 67, 32, 20, 192, 105, 35, 86, 0, 42, 17, 67, 32, 20, 192, 105, 4, 35, 86, 111, 47, 0, 14, 81, 105, 116, 32, 19, 67, 32, 20, 192, 105, 117, 86, 50, 122, 47, 0, 35, 14, 81, 110, 111, 116, 32, 19, 67, 32, 20, 192, 105, 13, 86, 50, 2, 122, 47, 0, 35, 81, 110, 111, 116, 32, 16, 67, 32, 20, 192, 105, 35, 86, 47, 132, 0, 14, 81, 116, 111, 32, 21, 67, 32, 20, 192, 2, 105, 117, 86, 2, 69, 120, 50, 0, 35, 81, 98, 101, 101, 110, 32, 11, 67, 32, 20, 192, 105, 35, 86, 0, 9, 14, 12, 67, 32, 20, 192, 2, 105, 117, 86, 0, 35, 9, 8, 67, 81, 148, 128, 47, 143, 0, 10, 67, 80, 148, 192, 47, 120, 86, 0, 9, 18, 71, 12, 129, 86, 72, 243, 5, 80, 89, 119, 82, 34, 13, 55, 6, 136, 0, 0, 10, 67, 16, 148, 195, 70, 120, 87, 49, 0, 11, 68, 12, 19, 22, 20, 49, 35, 82, 0, 103, 10, 68, 12, 19, 22, 20, 49, 124, 82, 0, 0, 16, 69, 8, 82, 9, 56, 64, 69, 120, 105, 135, 50, 70, 0, 74, 12, 12, 69, 16, 20, 146, 100, 192, 70, 35, 34, 116, 0, 9, 198, 61, 97, 82, 81, 84, 133, 65, 14, 69, 4, 211, 210, 4, 192, 136, 63, 6, 122, 34, 116, 0, 0, 15, 70, 80, 84, 85, 36, 192, 64, 47, 13, 49, 127, 55, 13, 0, 15, 70, 25, 34, 78, 28, 84, 128, 81, 34, 120, 50, 73, 112, 0, 14, 70, 5, 36, 197, 56, 144, 192, 125, 87, 50, 120, 49, 0, 0, 13, 67, 32, 148, 192, 105, 120, 86, 0, 72, 34, 9, 12, 16, 71, 44, 21, 8, 21, 34, 78, 20, 49, 35, 85, 34, 111, 50, 0, 19, 71, 80, 19, 135, 21, 34, 78, 20, 47, 35, 50, 73, 13, 34, 6, 127, 50, 0, 12, 67, 48, 20, 192, 4, 55, 124, 87, 0, 103, 9, 11, 67, 48, 20, 192, 4, 55, 35, 87, 0, 9, 0, 16, 70, 72, 83, 78, 4, 229, 0, 34, 119, 63, 50, 13, 50, 47, 0, 12, 68, 13, 147, 82, 84, 49, 123, 63, 34, 37, 0, 10, 3, 95, 53, 15, 81, 6, 120, 81, 0, 0, 23, 73, 52, 147, 142, 20, 20, 15, 48, 148, 192, 63, 120, 50, 127, 6, 35, 48, 13, 55, 111, 87, 0, 14, 69, 12, 244, 146, 4, 192, 49, 13, 34, 6, 35, 55, 0, 16, 70, 12, 240, 203, 77, 84, 133, 4, 49, 122, 49, 89, 6, 141, 0, 17, 70, 9, 35, 195, 33, 84, 133, 69, 34, 134, 6, 89, 141, 34, 0, 103, 14, 70, 9, 35, 195, 33, 84, 133, 69, 34, 134, 89, 112, 0, 0, 6, 194, 37, 64, 42, 17, 18, 66, 37, 64, 2, 120, 47, 15, 58, 122, 86, 0, 14, 81, 119, 97, 115, 32, 16, 66, 37, 64, 2, 120, 47, 15, 120, 86, 0, 14, 81, 105, 115, 32, 18, 66, 37, 64, 2, 120, 47, 15, 105, 35, 86, 0, 14, 81, 104, 97, 115, 32, 9, 66, 37, 64, 120, 47, 0, 72, 33, 10, 67, 36, 245, 193, 135, 13, 58, 13, 0, 17, 70, 65, 35, 212, 60, 51, 204, 48, 34, 134, 47, 13, 49, 122, 55, 0, 15, 70, 52, 17, 208, 36, 84, 192, 63, 35, 79, 48, 135, 86, 0, 15, 4, 95, 13, 3, 14, 63, 6, 35, 49, 34, 4, 122, 50, 0, 0, 19, 67, 24, 85, 192, 81, 6, 57, 132, 63, 4, 131, 0, 81, 109, 111, 114, 101, 32, 0, 0, 13, 69, 4, 66, 69, 85, 128, 117, 70, 57, 132, 86, 0, 0, 15, 70, 77, 80, 147, 36, 65, 64, 87, 13, 69, 87, 135, 70, 0, 14, 70, 76, 245, 70, 24, 193, 64, 87, 132, 81, 55, 136, 0, 14, 70, 21, 2, 83, 80, 193, 64, 111, 48, 120, 87, 116, 0, 16, 70, 16, 83, 79, 48, 148, 200, 70, 111, 63, 122, 55, 120, 89, 0, 11, 67, 76, 52, 201, 87, 49, 123, 86, 37, 0, 0, 16, 71, 21, 66, 5, 72, 145, 7, 20, 119, 85, 14, 34, 120, 73, 0, 0, 11, 68, 12, 148, 131, 20, 87, 126, 87, 37, 0, 13, 68, 12, 19, 9, 96, 49, 136, 55, 120, 49, 87, 0, 0, 15, 69, 64, 21, 5, 57, 64, 48, 35, 47, 13, 50, 47, 0, 103, 14, 69, 77, 69, 65, 73, 64, 87, 47, 132, 112, 47, 0, 103, 14, 69, 77, 69, 65, 73, 64, 87, 47, 57, 132, 112, 47, 0, 9, 67, 36, 115, 210, 127, 79, 131, 0, 14, 69, 76, 80, 210, 21, 64, 87, 127, 49, 34, 13, 47, 0, 13, 69, 72, 21, 197, 77, 64, 34, 128, 13, 87, 47, 0, 14, 69, 21, 32, 83, 21, 32, 111, 34, 136, 87, 112, 0, 103, 13, 69, 21, 32, 83, 21, 32, 111, 34, 136, 86, 112, 0, 11, 69, 17, 32, 87, 21, 32, 70, 34, 130, 0, 15, 69, 16, 145, 197, 77, 64, 70, 135, 73, 119, 87, 47, 0, 37, 16, 70, 8, 85, 133, 72, 17, 197, 69, 119, 82, 13, 34, 111, 73, 0, 14, 69, 4, 69, 133, 73, 64, 117, 70, 82, 126, 47, 0, 36, 0, 15, 66, 16, 240, 70, 132, 15, 87, 134, 0, 14, 81, 115, 111, 32, 17, 66, 16, 240, 70, 132, 50, 122, 47, 0, 32, 78, 81, 110, 111, 116, 32, 8, 66, 16, 240, 70, 132, 0, 32, 9, 198, 64, 19, 129, 12, 129, 64, 66, 10, 66, 36, 80, 135, 127, 11, 0, 8, 9, 0, 21, 71, 21, 133, 18, 20, 210, 83, 80, 119, 49, 87, 47, 34, 6, 127, 63, 120, 87, 47, 0, 10, 67, 8, 84, 212, 69, 119, 87, 47, 0, 0, 13, 68, 8, 83, 15, 92, 69, 120, 55, 134, 0, 74, 12, 13, 5, 10, 15, 19, 195, 169, 105, 134, 87, 6, 136, 0, 12, 68, 4, 229, 15, 56, 35, 50, 47, 122, 50, 0, 7, 196, 21, 130, 76, 20, 65, 12, 68, 16, 149, 129, 56, 70, 111, 82, 35, 50, 0, 0, 14, 69, 16, 18, 207, 80, 16, 70, 117, 49, 134, 47, 13, 0, 14, 69, 52, 148, 129, 28, 80, 63, 112, 34, 124, 88, 0, 103, 13, 69, 52, 148, 129, 28, 80, 63, 120, 34, 124, 88, 0, 13, 69, 5, 32, 66, 48, 80, 35, 34, 117, 69, 116, 0, 14, 69, 4, 224, 76, 60, 112, 35, 50, 13, 55, 122, 79, 0, 0, 14, 70, 8, 84, 151, 36, 50, 192, 69, 119, 34, 120, 49, 0, 14, 70, 92, 244, 139, 76, 134, 64, 58, 126, 49, 89, 135, 0, 0, 16, 70, 56, 144, 200, 60, 192, 83, 50, 120, 49, 13, 55, 13, 87, 0, 17, 70, 77, 1, 67, 36, 98, 67, 87, 48, 13, 87, 120, 81, 120, 49, 0, 9, 198, 72, 81, 3, 72, 244, 211, 66, 0, 11, 68, 4, 148, 133, 76, 135, 34, 120, 86, 0, 11, 200, 52, 85, 1, 77, 64, 66, 48, 80, 20, 21, 72, 32, 244, 208, 37, 64, 66, 48, 80, 105, 122, 87, 48, 6, 120, 47, 13, 69, 116, 0, 12, 68, 12, 84, 133, 76, 87, 139, 34, 127, 86, 0, 0, 14, 6, 14, 1, 195, 175, 22, 5, 50, 135, 6, 127, 82, 0, 13, 69, 52, 22, 72, 20, 208, 63, 136, 105, 119, 63, 0, 12, 69, 5, 35, 213, 76, 80, 117, 34, 133, 86, 0, 0, 13, 70, 44, 82, 71, 32, 194, 64, 49, 136, 55, 37, 0, 15, 70, 16, 243, 129, 28, 134, 64, 70, 122, 50, 6, 105, 127, 0, 0, 17, 70, 52, 85, 1, 48, 194, 67, 63, 13, 47, 6, 35, 55, 120, 49, 0, 10, 199, 21, 133, 18, 36, 48, 84, 20, 65, 0, 15, 70, 4, 112, 73, 57, 53, 0, 117, 79, 119, 50, 87, 47, 0, 19, 72, 64, 244, 148, 84, 117, 69, 76, 80, 48, 131, 74, 13, 79, 6, 127, 86, 0, 14, 68, 85, 4, 197, 80, 123, 48, 87, 6, 119, 47, 0, 38, 8, 196, 85, 4, 197, 80, 65, 10, 11, 68, 48, 149, 133, 16, 55, 120, 82, 70, 0, 15, 6, 95, 18, 15, 13, 1, 14, 34, 134, 63, 13, 50, 10, 0, 0, 14, 69, 8, 197, 82, 73, 144, 69, 55, 146, 34, 120, 0, 105, 13, 69, 8, 197, 82, 73, 144, 69, 55, 126, 34, 120, 0, 0, 10, 67, 73, 80, 153, 34, 132, 69, 37, 0, 9, 67, 5, 116, 153, 117, 34, 135, 0, 0, 17, 70, 32, 84, 131, 84, 193, 83, 105, 126, 49, 57, 115, 55, 127, 86, 0, 0, 14, 70, 76, 131, 213, 48, 65, 82, 89, 134, 55, 70, 112, 0, 13, 68, 52, 245, 5, 48, 63, 134, 47, 6, 119, 55, 0, 15, 70, 52, 20, 129, 84, 65, 82, 63, 13, 34, 128, 70, 112, 0, 6, 195, 21, 132, 15, 65, 0, 14, 69, 56, 144, 197, 81, 144, 50, 135, 87, 13, 47, 37, 0, 15, 69, 9, 84, 201, 49, 144, 69, 120, 86, 111, 55, 120, 0, 32, 0, 7, 194, 36, 96, 72, 8, 9, 20, 66, 20, 224, 4, 122, 50, 15, 34, 6, 132, 47, 0, 81, 114, 111, 117, 116, 101, 32, 20, 66, 20, 224, 4, 122, 50, 15, 63, 6, 35, 87, 0, 81, 109, 97, 115, 115, 101, 32, 15, 70, 72, 144, 207, 12, 129, 84, 34, 120, 49, 13, 89, 136, 0, 0, 15, 70, 5, 69, 1, 12, 129, 83, 117, 47, 35, 74, 121, 86, 0, 12, 3, 95, 51, 88, 85, 6, 145, 47, 37, 0, 105, 11, 3, 95, 51, 88, 85, 6, 126, 47, 37, 0, 0, 17, 70, 48, 198, 87, 20, 198, 78, 103, 13, 58, 6, 119, 55, 120, 50, 0, 9, 198, 81, 32, 78, 76, 97, 82, 36, 10, 198, 81, 32, 78, 76, 97, 82, 65, 10, 11, 68, 72, 85, 133, 72, 34, 111, 82, 140, 0, 10, 198, 12, 243, 148, 20, 229, 0, 36, 38, 17, 70, 12, 243, 148, 20, 229, 0, 49, 122, 50, 47, 119, 50, 47, 0, 10, 14, 3, 95, 48, 67, 105, 6, 123, 50, 70, 34, 13, 70, 0, 0, 14, 69, 52, 145, 213, 20, 192, 63, 127, 98, 6, 119, 55, 0, 8, 197, 12, 86, 76, 60, 224, 66, 18, 70, 20, 229, 18, 4, 224, 197, 119, 50, 47, 34, 6, 118, 50, 87, 0, 36, 10, 198, 20, 229, 18, 4, 224, 197, 65, 10, 13, 69, 12, 245, 80, 60, 224, 49, 132, 48, 122, 50, 0, 0, 0, 17, 71, 64, 130, 76, 37, 2, 78, 20, 81, 120, 55, 111, 48, 127, 50, 0, 18, 71, 64, 84, 134, 20, 53, 12, 100, 48, 126, 81, 119, 49, 47, 55, 120, 0, 19, 71, 64, 20, 129, 49, 148, 201, 76, 48, 13, 34, 35, 55, 13, 87, 120, 87, 0, 18, 71, 52, 20, 135, 5, 34, 78, 20, 63, 125, 73, 112, 34, 13, 50, 0, 103, 17, 71, 52, 20, 135, 5, 34, 78, 20, 63, 125, 73, 112, 34, 127, 50, 0, 17, 71, 5, 85, 8, 61, 34, 84, 100, 117, 85, 122, 34, 111, 47, 37, 0, 0, 9, 198, 88, 84, 141, 60, 229, 0, 66, 11, 68, 68, 21, 1, 72, 49, 35, 47, 125, 0, 12, 68, 64, 20, 137, 76, 48, 35, 34, 120, 87, 0, 12, 68, 80, 149, 1, 56, 47, 135, 47, 13, 50, 0, 11, 68, 77, 80, 86, 20, 87, 58, 124, 82, 0, 0, 13, 69, 13, 85, 15, 24, 96, 49, 123, 47, 122, 81, 0, 12, 69, 8, 144, 83, 20, 64, 69, 142, 87, 47, 0, 0, 11, 67, 52, 17, 5, 63, 4, 136, 70, 0, 12, 13, 67, 52, 17, 5, 63, 4, 136, 70, 0, 12, 9, 76, 16, 70, 77, 67, 205, 5, 64, 64, 87, 47, 134, 63, 13, 47, 13, 0, 15, 70, 12, 131, 204, 21, 32, 64, 49, 122, 55, 13, 34, 13, 0, 17, 70, 12, 19, 4, 21, 32, 64, 49, 122, 55, 70, 6, 138, 34, 13, 0, 14, 70, 4, 230, 9, 61, 84, 192, 35, 66, 89, 13, 87, 0, 0, 9, 67, 65, 34, 88, 48, 34, 127, 0, 0, 12, 68, 12, 20, 143, 48, 49, 35, 34, 13, 55, 0, 0, 12, 201, 92, 244, 132, 65, 35, 195, 21, 52, 192, 66, 17, 70, 52, 241, 5, 72, 21, 5, 63, 122, 70, 13, 34, 136, 47, 0, 36, 9, 198, 48, 149, 5, 72, 21, 5, 21, 15, 69, 4, 192, 133, 37, 64, 128, 55, 69, 6, 127, 120, 47, 0, 15, 3, 226, 136, 158, 120, 50, 81, 6, 120, 50, 111, 47, 111, 0, 0, 13, 5, 19, 8, 5, 39, 19, 89, 127, 86, 0, 72, 35, 17, 6, 23, 1, 19, 14, 39, 20, 58, 123, 86, 50, 47, 0, 103, 35, 9, 15, 70, 64, 148, 5, 81, 65, 64, 48, 120, 48, 6, 119, 47, 0, 0, 17, 7, 4, 15, 5, 19, 14, 39, 20, 70, 123, 86, 13, 50, 47, 0, 32, 10, 199, 28, 83, 204, 60, 114, 83, 80, 66, 16, 3, 226, 137, 160, 50, 122, 47, 6, 127, 49, 58, 116, 47, 115, 0, 0, 12, 68, 16, 84, 15, 80, 70, 127, 48, 134, 0, 103, 12, 68, 81, 38, 83, 80, 47, 34, 120, 87, 47, 0, 12, 200, 81, 32, 78, 76, 52, 137, 65, 64, 65, 10, 11, 68, 16, 84, 15, 80, 70, 119, 48, 134, 0, 0, 9, 198, 8, 83, 7, 72, 17, 5, 66, 13, 69, 12, 21, 137, 5, 32, 49, 35, 82, 120, 125, 0, 9, 198, 8, 195, 195, 44, 17, 5, 66, 16, 70, 4, 48, 213, 72, 21, 5, 35, 49, 57, 115, 34, 13, 47, 0, 15, 3, 226, 136, 154, 87, 49, 58, 4, 138, 34, 6, 132, 47, 0, 0, 16, 70, 52, 16, 193, 9, 33, 64, 63, 13, 49, 124, 69, 34, 13, 0, 9, 66, 48, 16, 4, 55, 35, 0, 9, 13, 3, 95, 49, 57, 50, 6, 135, 50, 47, 127, 50, 0, 0, 17, 67, 52, 244, 212, 63, 134, 87, 47, 15, 13, 82, 0, 81, 111, 102, 32, 10, 67, 72, 84, 212, 34, 119, 87, 47, 0, 10, 67, 52, 19, 12, 63, 128, 55, 0, 103, 9, 67, 52, 19, 12, 63, 35, 55, 0, 6, 195, 5, 2, 64, 17, 11, 3, 95, 49, 56, 6, 136, 47, 127, 50, 0, 0, 12, 68, 48, 85, 133, 56, 55, 127, 82, 13, 50, 0, 11, 68, 16, 245, 133, 72, 70, 134, 82, 112, 0, 22, 73, 36, 229, 5, 72, 209, 68, 36, 21, 5, 120, 50, 47, 112, 63, 6, 127, 70, 139, 47, 0, 16, 3, 226, 151, 143, 69, 55, 4, 35, 49, 87, 6, 126, 49, 116, 0, 0, 12, 201, 20, 193, 67, 81, 35, 195, 85, 65, 64, 66, 13, 69, 16, 240, 66, 48, 80, 70, 132, 13, 69, 116, 0, 0, 10, 67, 52, 19, 9, 63, 124, 55, 37, 0, 15, 70, 88, 20, 137, 21, 70, 64, 82, 13, 34, 142, 47, 37, 0, 19, 70, 4, 36, 212, 72, 16, 212, 117, 69, 87, 47, 34, 6, 35, 49, 47, 0, 36, 18, 70, 4, 36, 212, 72, 16, 212, 35, 69, 87, 47, 34, 35, 49, 47, 0, 9, 0, 10, 199, 53, 83, 20, 37, 69, 68, 20, 65, 16, 70, 16, 83, 79, 56, 84, 211, 70, 127, 63, 13, 50, 119, 87, 0, 0, 12, 68, 52, 21, 137, 76, 63, 136, 82, 120, 87, 0, 12, 68, 76, 21, 1, 56, 87, 136, 47, 13, 50, 0, 0, 14, 69, 72, 81, 5, 100, 80, 34, 6, 119, 70, 4, 135, 0, 14, 69, 64, 20, 143, 48, 80, 48, 117, 34, 6, 134, 55, 0, 13, 69, 48, 244, 201, 56, 112, 55, 132, 86, 120, 66, 0, 14, 69, 12, 246, 79, 80, 80, 49, 135, 6, 134, 47, 37, 0, 11, 3, 226, 136, 146, 63, 135, 50, 13, 87, 0, 0, 14, 70, 76, 85, 133, 72, 19, 0, 87, 119, 82, 34, 116, 0, 13, 3, 95, 49, 49, 120, 55, 6, 119, 82, 13, 50, 0, 0, 17, 71, 81, 84, 142, 80, 16, 140, 20, 47, 126, 50, 106, 136, 69, 116, 0, 19, 71, 65, 34, 86, 5, 66, 79, 56, 48, 34, 135, 82, 6, 136, 89, 13, 50, 0, 10, 3, 95, 49, 48, 47, 6, 119, 50, 0, 0, 10, 67, 81, 34, 79, 47, 34, 127, 134, 0, 12, 68, 36, 229, 5, 48, 120, 50, 106, 119, 55, 0, 18, 72, 21, 97, 82, 101, 66, 9, 56, 112, 119, 82, 34, 111, 85, 120, 66, 0, 12, 68, 16, 243, 149, 80, 70, 134, 50, 123, 47, 0, 13, 3, 95, 49, 51, 85, 6, 145, 47, 127, 50, 0, 105, 12, 3, 95, 49, 51, 85, 6, 126, 47, 127, 50, 0, 0, 13, 69, 12, 19, 143, 21, 48, 49, 13, 50, 132, 86, 0, 12, 4, 95, 52, 48, 15, 81, 6, 131, 47, 139, 0, 12, 3, 95, 49, 50, 47, 58, 6, 119, 55, 82, 0, 0, 13, 3, 95, 49, 53, 81, 6, 120, 81, 47, 127, 50, 0, 0, 18, 71, 52, 81, 9, 4, 85, 129, 48, 63, 119, 70, 120, 6, 127, 82, 116, 0, 20, 71, 12, 243, 148, 72, 19, 20, 60, 49, 13, 50, 47, 34, 6, 35, 55, 47, 134, 0, 19, 71, 5, 85, 15, 13, 32, 67, 100, 128, 47, 6, 122, 49, 34, 13, 87, 37, 0, 12, 3, 95, 49, 52, 81, 6, 131, 47, 127, 50, 0, 0, 12, 68, 64, 21, 5, 48, 48, 117, 47, 119, 55, 0, 11, 68, 36, 225, 9, 20, 120, 50, 70, 37, 0, 13, 68, 32, 245, 5, 48, 105, 134, 47, 6, 119, 55, 0, 11, 67, 5, 129, 83, 35, 49, 87, 121, 86, 0, 16, 3, 95, 49, 55, 87, 6, 13, 82, 13, 50, 47, 127, 50, 0, 107, 15, 3, 95, 49, 55, 87, 6, 119, 82, 13, 50, 47, 127, 50, 0, 0, 13, 69, 80, 131, 205, 5, 48, 47, 122, 63, 13, 87, 0, 8, 197, 61, 85, 12, 5, 112, 65, 9, 197, 56, 80, 82, 9, 144, 66, 14, 14, 3, 95, 49, 54, 87, 6, 120, 49, 87, 47, 127, 50, 0, 0, 0, 17, 70, 52, 84, 131, 20, 65, 83, 63, 126, 87, 6, 136, 70, 127, 86, 0, 10, 67, 5, 115, 204, 136, 58, 122, 55, 0, 15, 3, 95, 55, 88, 87, 6, 13, 82, 13, 50, 47, 37, 0, 107, 14, 3, 95, 55, 88, 87, 6, 119, 82, 13, 50, 47, 37, 0, 0, 21, 72, 12, 243, 77, 20, 229, 1, 73, 144, 49, 122, 63, 13, 50, 47, 119, 34, 37, 0, 103, 7, 196, 56, 85, 133, 72, 32, 11, 68, 12, 132, 137, 76, 49, 34, 120, 87, 0, 13, 6, 2, 10, 195, 184, 18, 14, 69, 57, 126, 50, 0, 12, 68, 16, 85, 143, 56, 70, 119, 82, 13, 50, 0, 12, 68, 72, 84, 12, 100, 34, 111, 48, 55, 135, 0, 19, 72, 12, 243, 77, 20, 229, 1, 73, 144, 49, 122, 63, 13, 50, 47, 34, 120, 0, 13, 68, 4, 212, 12, 100, 35, 63, 48, 55, 120, 0, 32, 20, 72, 4, 36, 212, 20, 210, 79, 85, 48, 117, 69, 87, 47, 6, 127, 63, 139, 87, 0, 12, 200, 4, 36, 207, 49, 85, 5, 49, 144, 67, 32, 0, 13, 69, 72, 80, 71, 4, 224, 34, 136, 79, 13, 50, 0, 17, 70, 64, 83, 133, 48, 244, 5, 48, 13, 50, 119, 55, 13, 48, 37, 0, 14, 69, 80, 18, 87, 4, 224, 47, 135, 6, 58, 124, 50, 0, 13, 69, 72, 20, 195, 4, 192, 34, 118, 87, 49, 116, 0, 12, 69, 9, 35, 207, 12, 128, 69, 34, 134, 74, 0, 0, 15, 70, 77, 21, 73, 73, 33, 76, 87, 49, 58, 120, 34, 116, 0, 15, 70, 12, 243, 131, 32, 84, 192, 49, 122, 50, 74, 121, 86, 0, 0, 18, 71, 65, 54, 67, 32, 245, 9, 12, 87, 135, 49, 6, 122, 47, 120, 49, 0, 11, 67, 21, 130, 84, 119, 79, 86, 120, 47, 0, 9, 67, 9, 84, 192, 69, 123, 87, 0, 0, 11, 68, 32, 21, 133, 76, 105, 35, 82, 86, 0, 15, 70, 72, 18, 77, 20, 229, 0, 34, 136, 63, 13, 50, 47, 0, 12, 68, 48, 144, 146, 20, 55, 127, 69, 34, 13, 0, 10, 68, 20, 20, 140, 100, 126, 55, 120, 0, 0, 13, 69, 76, 147, 133, 4, 64, 89, 111, 50, 136, 70, 0, 14, 69, 80, 19, 80, 60, 224, 47, 35, 63, 48, 122, 50, 0, 9, 198, 56, 21, 9, 88, 149, 25, 66, 0, 0, 9, 67, 81, 165, 64, 47, 87, 132, 0, 17, 71, 72, 83, 132, 21, 99, 213, 76, 34, 122, 50, 70, 111, 82, 132, 0, 18, 71, 64, 20, 129, 52, 85, 5, 72, 48, 13, 34, 35, 63, 111, 47, 112, 0, 17, 71, 5, 85, 15, 29, 32, 80, 32, 128, 47, 13, 79, 34, 35, 81, 0, 11, 3, 224, 165, 164, 70, 123, 50, 70, 117, 0, 0, 18, 72, 32, 83, 131, 20, 99, 210, 80, 128, 105, 119, 50, 87, 81, 131, 85, 0, 0, 12, 69, 92, 149, 8, 21, 32, 58, 120, 84, 112, 0, 9, 198, 77, 64, 77, 64, 81, 5, 66, 16, 70, 72, 83, 133, 28, 17, 5, 34, 119, 50, 13, 79, 136, 70, 0, 16, 70, 64, 20, 129, 76, 149, 5, 48, 35, 34, 13, 87, 135, 47, 0, 9, 198, 4, 229, 9, 16, 245, 5, 65, 0, 15, 6, 1, 18, 5, 14, 39, 20, 4, 125, 50, 47, 0, 35, 12, 15, 70, 92, 80, 147, 37, 65, 64, 58, 119, 69, 87, 135, 47, 0, 9, 198, 64, 194, 67, 5, 65, 64, 66, 14, 70, 8, 150, 129, 73, 33, 64, 69, 120, 86, 6, 125, 0, 9, 198, 4, 230, 77, 61, 33, 64, 67, 0, 17, 7, 8, 1, 22, 5, 14, 39, 20, 105, 35, 82, 13, 50, 47, 0, 35, 16, 70, 92, 147, 142, 37, 1, 71, 58, 120, 50, 111, 48, 119, 79, 0, 0, 0, 28, 5, 23, 15, 14, 39, 20, 58, 6, 134, 50, 47, 35, 82, 47, 114, 0, 32, 12, 82, 104, 97, 118, 101, 32, 116, 111, 32, 23, 5, 23, 15, 14, 39, 20, 58, 134, 50, 47, 105, 35, 82, 0, 35, 14, 81, 104, 97, 118, 101, 32, 22, 5, 23, 15, 14, 39, 20, 58, 134, 50, 47, 117, 82, 0, 35, 73, 81, 104, 97, 118, 101, 32, 16, 5, 23, 15, 14, 39, 20, 58, 134, 50, 47, 0, 76, 32, 12, 9, 9, 198, 77, 64, 71, 56, 21, 5, 66, 17, 70, 76, 84, 1, 72, 21, 5, 87, 119, 48, 112, 34, 136, 47, 0, 36, 16, 70, 76, 84, 1, 72, 21, 5, 87, 119, 48, 14, 34, 13, 47, 0, 13, 69, 72, 21, 8, 21, 32, 34, 124, 84, 112, 0, 135, 10, 67, 21, 5, 66, 127, 48, 123, 69, 0, 21, 73, 12, 84, 148, 36, 98, 67, 5, 65, 64, 87, 112, 47, 120, 81, 120, 49, 13, 47, 0, 11, 69, 4, 85, 8, 21, 32, 127, 85, 13, 0, 0, 15, 70, 72, 81, 133, 73, 32, 76, 34, 111, 81, 126, 34, 116, 0, 13, 70, 56, 245, 200, 21, 33, 64, 50, 134, 58, 138, 0, 14, 70, 5, 84, 212, 21, 33, 64, 128, 87, 47, 6, 140, 0, 0, 6, 195, 41, 84, 212, 32, 17, 7, 23, 5, 18, 5, 14, 39, 20, 4, 58, 126, 50, 47, 0, 35, 12, 18, 71, 49, 83, 131, 33, 35, 207, 52, 55, 123, 50, 74, 15, 34, 132, 63, 0, 17, 71, 25, 33, 69, 48, 19, 131, 20, 81, 34, 127, 55, 118, 50, 87, 0, 0, 11, 68, 4, 20, 143, 56, 138, 34, 13, 50, 0, 19, 72, 24, 18, 18, 20, 226, 5, 37, 64, 81, 35, 34, 13, 50, 105, 135, 47, 0, 16, 70, 16, 81, 137, 12, 149, 0, 70, 119, 81, 111, 87, 120, 47, 0, 20, 72, 4, 197, 15, 28, 85, 8, 21, 32, 4, 128, 55, 47, 13, 79, 119, 84, 112, 0, 0, 20, 73, 80, 83, 80, 21, 32, 84, 85, 33, 64, 47, 119, 63, 48, 34, 111, 74, 112, 0, 9, 198, 61, 85, 3, 72, 244, 0, 65, 8, 197, 5, 32, 66, 36, 48, 65, 0, 16, 70, 4, 230, 9, 21, 70, 64, 35, 66, 86, 6, 142, 47, 37, 0, 0, 12, 201, 84, 197, 18, 5, 98, 79, 48, 85, 0, 67, 16, 3, 226, 150, 160, 69, 55, 6, 35, 49, 87, 49, 58, 6, 138, 0, 0, 13, 68, 104, 80, 146, 4, 86, 127, 69, 34, 13, 0, 103, 9, 198, 36, 228, 212, 20, 17, 0, 8, 11, 68, 80, 21, 1, 72, 47, 124, 47, 112, 0, 11, 68, 48, 149, 5, 72, 55, 127, 47, 112, 0, 0, 14, 69, 72, 80, 201, 64, 80, 34, 119, 87, 111, 48, 127, 0, 13, 69, 32, 84, 133, 80, 240, 105, 140, 6, 47, 132, 0, 0, 0, 13, 3, 95, 50, 88, 47, 58, 6, 119, 50, 106, 37, 0, 0, 11, 68, 21, 21, 65, 48, 127, 49, 58, 116, 0, 0, 14, 69, 64, 148, 129, 13, 144, 48, 143, 34, 13, 87, 37, 0, 15, 69, 12, 244, 205, 61, 48, 49, 122, 86, 63, 134, 87, 0, 103, 14, 69, 12, 244, 205, 61, 48, 49, 122, 86, 63, 122, 87, 0, 14, 69, 12, 241, 9, 25, 144, 49, 134, 70, 111, 81, 135, 0, 0, 13, 202, 36, 229, 5, 73, 35, 199, 5, 67, 210, 100, 67, 0, 17, 70, 76, 49, 78, 5, 34, 79, 87, 13, 50, 35, 34, 37, 134, 0, 103, 16, 70, 76, 49, 78, 5, 34, 79, 87, 13, 50, 125, 34, 37, 134, 0, 17, 71, 52, 19, 135, 21, 67, 213, 80, 63, 122, 50, 88, 47, 6, 132, 0, 19, 71, 16, 240, 212, 72, 147, 129, 48, 70, 122, 49, 47, 34, 6, 135, 50, 116, 0, 0, 11, 68, 16, 21, 137, 20, 70, 136, 82, 37, 0, 0, 14, 69, 88, 17, 193, 73, 144, 82, 136, 79, 13, 34, 120, 0, 14, 69, 80, 84, 212, 21, 48, 47, 119, 87, 47, 127, 86, 0, 8, 197, 61, 85, 12, 5, 144, 65, 0, 15, 70, 72, 84, 212, 25, 83, 0, 34, 119, 87, 47, 81, 116, 0, 17, 70, 52, 145, 20, 21, 35, 64, 63, 6, 120, 70, 47, 4, 126, 63, 0, 0, 20, 71, 25, 35, 206, 81, 0, 71, 20, 81, 34, 6, 123, 50, 47, 48, 4, 136, 73, 0, 0, 22, 72, 28, 193, 78, 72, 245, 8, 21, 48, 79, 55, 4, 119, 50, 34, 6, 122, 85, 121, 87, 0, 0, 12, 69, 48, 85, 8, 4, 192, 55, 127, 85, 116, 0, 14, 69, 32, 84, 143, 36, 224, 105, 119, 34, 134, 120, 50, 0, 0, 11, 67, 76, 83, 73, 87, 119, 63, 135, 0, 103, 0, 0, 11, 68, 76, 16, 146, 20, 87, 136, 69, 112, 0, 11, 3, 95, 63, 63, 87, 120, 63, 69, 116, 0, 0, 13, 69, 5, 35, 213, 56, 64, 117, 34, 133, 50, 70, 0, 14, 69, 80, 245, 193, 72, 64, 47, 115, 58, 130, 70, 0, 66, 14, 69, 64, 20, 212, 20, 64, 48, 136, 87, 47, 121, 70, 0, 13, 69, 9, 34, 68, 4, 192, 69, 34, 135, 70, 116, 0, 13, 67, 49, 65, 0, 55, 120, 63, 111, 47, 111, 70, 0, 0, 5, 194, 49, 64, 24, 11, 66, 53, 32, 63, 120, 87, 47, 112, 0, 24, 0, 19, 71, 5, 85, 15, 52, 21, 15, 56, 128, 47, 6, 122, 63, 13, 47, 13, 50, 0, 11, 3, 95, 52, 88, 81, 6, 131, 47, 37, 0, 0, 26, 68, 24, 148, 147, 80, 81, 6, 145, 87, 47, 10, 48, 55, 4, 136, 87, 0, 105, 81, 112, 108, 97, 99, 101, 32, 25, 68, 24, 148, 147, 80, 81, 6, 126, 87, 47, 10, 48, 55, 4, 136, 87, 0, 81, 112, 108, 97, 99, 101, 32, 0, 9, 67, 76, 80, 78, 89, 128, 50, 0, 17, 70, 104, 147, 66, 4, 37, 197, 86, 111, 63, 69, 124, 69, 58, 37, 0, 11, 67, 60, 208, 78, 134, 63, 6, 35, 50, 0, 8, 197, 85, 3, 9, 25, 64, 66, 8, 197, 36, 228, 197, 13, 64, 65, 0, 0, 9, 67, 56, 240, 72, 50, 134, 123, 0, 0, 0, 13, 69, 8, 241, 193, 73, 64, 69, 134, 79, 125, 47, 0, 8, 197, 60, 34, 133, 13, 64, 36, 9, 197, 60, 34, 133, 13, 64, 65, 10, 0, 10, 66, 28, 240, 4, 79, 134, 0, 12, 9, 15, 66, 48, 80, 55, 127, 6, 35, 50, 0, 81, 97, 110, 110, 32, 15, 70, 64, 244, 148, 84, 112, 76, 48, 131, 74, 13, 79, 116, 0, 15, 70, 65, 33, 70, 4, 49, 64, 48, 34, 119, 81, 13, 87, 0, 9, 66, 48, 80, 55, 13, 23, 0, 9, 15, 70, 32, 244, 212, 4, 113, 64, 105, 122, 87, 47, 111, 73, 0, 9, 198, 24, 147, 129, 56, 49, 64, 36, 16, 70, 24, 147, 129, 56, 49, 64, 81, 135, 50, 35, 50, 87, 0, 9, 0, 17, 71, 72, 81, 133, 72, 83, 131, 20, 34, 119, 81, 34, 13, 50, 87, 0, 14, 70, 52, 19, 77, 61, 66, 0, 63, 35, 63, 13, 85, 0, 12, 3, 95, 53, 88, 81, 6, 120, 81, 47, 37, 0, 0, 10, 68, 76, 145, 8, 20, 89, 127, 13, 0, 11, 68, 48, 21, 20, 20, 55, 124, 106, 136, 0, 0, 13, 67, 28, 245, 0, 2, 79, 122, 47, 0, 12, 35, 9, 15, 69, 28, 243, 69, 72, 16, 79, 134, 63, 6, 138, 34, 13, 0, 17, 70, 81, 32, 86, 21, 53, 25, 47, 34, 35, 82, 13, 87, 47, 37, 0, 13, 69, 25, 84, 195, 36, 16, 81, 57, 132, 89, 13, 0, 13, 69, 16, 148, 15, 48, 80, 70, 135, 48, 134, 55, 0, 20, 73, 8, 245, 82, 28, 83, 201, 76, 145, 64, 69, 141, 88, 58, 124, 86, 6, 127, 0, 0, 16, 70, 52, 148, 129, 8, 83, 0, 63, 120, 34, 13, 69, 119, 55, 0, 14, 70, 56, 244, 134, 60, 194, 192, 50, 130, 81, 13, 49, 0, 15, 70, 56, 21, 21, 72, 19, 0, 50, 35, 74, 13, 34, 116, 0, 0, 16, 71, 76, 86, 67, 32, 83, 12, 20, 87, 136, 89, 6, 119, 55, 0, 20, 71, 21, 131, 206, 21, 32, 84, 20, 119, 79, 86, 6, 122, 50, 13, 34, 136, 47, 0, 18, 71, 16, 148, 208, 5, 32, 84, 20, 70, 120, 87, 48, 13, 34, 13, 47, 0, 0, 9, 198, 21, 132, 12, 60, 149, 0, 36, 10, 198, 21, 132, 12, 60, 149, 0, 65, 10, 0, 13, 69, 81, 34, 65, 28, 80, 47, 34, 127, 124, 88, 0, 14, 69, 76, 85, 133, 72, 80, 87, 111, 82, 6, 140, 0, 9, 13, 69, 76, 49, 78, 36, 48, 87, 127, 50, 120, 49, 0, 14, 69, 64, 81, 1, 48, 240, 48, 119, 70, 13, 55, 134, 0, 13, 69, 52, 19, 149, 72, 80, 63, 13, 50, 57, 141, 0, 0, 9, 198, 28, 243, 196, 16, 22, 64, 66, 15, 70, 13, 85, 1, 92, 22, 64, 49, 123, 47, 13, 58, 136, 0, 0, 9, 67, 56, 245, 20, 50, 122, 47, 0, 18, 71, 20, 193, 67, 81, 35, 196, 20, 111, 55, 119, 49, 47, 34, 134, 70, 0, 6, 195, 60, 83, 64, 17, 13, 3, 95, 54, 88, 87, 6, 120, 49, 87, 47, 37, 0, 0, 11, 68, 69, 80, 83, 32, 49, 58, 122, 89, 0, 0, 13, 69, 72, 16, 130, 37, 48, 34, 35, 69, 135, 86, 0, 13, 69, 32, 245, 11, 21, 144, 105, 122, 47, 49, 127, 0, 22, 73, 9, 84, 133, 5, 80, 210, 4, 54, 64, 69, 57, 141, 6, 122, 49, 34, 13, 87, 37, 0, 13, 4, 95, 53, 48, 15, 81, 6, 120, 81, 47, 139, 0, 0, 10, 67, 12, 195, 197, 49, 55, 134, 37, 0, 17, 7, 2, 15, 7, 15, 20, 195, 161, 98, 111, 103, 111, 116, 97, 0, 29, 15, 70, 52, 19, 22, 21, 35, 128, 63, 128, 55, 82, 112, 50, 0, 0, 16, 71, 29, 33, 69, 57, 114, 67, 32, 79, 34, 119, 50, 120, 74, 0, 0, 10, 67, 56, 245, 19, 50, 122, 47, 87, 0, 15, 70, 52, 243, 147, 36, 85, 82, 63, 13, 87, 57, 146, 0, 105, 14, 70, 52, 243, 147, 36, 85, 82, 63, 13, 87, 57, 126, 0, 0, 15, 69, 4, 52, 143, 77, 48, 13, 49, 34, 122, 87, 0, 74, 12, 13, 69, 32, 84, 144, 21, 48, 105, 126, 48, 127, 86, 0, 14, 69, 12, 19, 80, 85, 48, 49, 35, 63, 48, 13, 87, 0, 0, 0, 21, 73, 12, 243, 142, 20, 53, 9, 13, 85, 0, 49, 13, 50, 119, 47, 111, 49, 13, 47, 0, 16, 70, 36, 225, 129, 52, 245, 83, 120, 50, 81, 13, 63, 13, 87, 0, 0, 12, 68, 64, 17, 18, 20, 48, 124, 70, 34, 136, 0, 0, 16, 69, 92, 149, 8, 36, 224, 58, 120, 84, 120, 50, 0, 74, 12, 28, 13, 69, 56, 21, 8, 4, 224, 50, 136, 85, 13, 50, 0, 15, 70, 12, 243, 77, 20, 224, 197, 49, 13, 63, 119, 50, 87, 0, 0, 0, 7, 195, 48, 36, 192, 17, 42, 11, 67, 48, 36, 192, 48, 133, 50, 70, 86, 0, 0, 12, 68, 16, 21, 137, 76, 70, 136, 82, 120, 87, 0, 12, 68, 52, 150, 5, 72, 63, 120, 49, 87, 112, 0, 0, 13, 69, 4, 97, 200, 4, 224, 35, 81, 79, 35, 50, 0, 15, 69, 36, 228, 212, 4, 192, 120, 50, 87, 47, 6, 128, 55, 0, 0, 14, 70, 12, 243, 142, 20, 195, 0, 49, 122, 50, 13, 55, 0, 0, 9, 67, 104, 241, 64, 86, 134, 37, 0, 17, 71, 48, 147, 79, 85, 50, 78, 20, 55, 120, 63, 13, 86, 127, 50, 0, 13, 67, 13, 68, 140, 49, 13, 50, 47, 34, 134, 55, 0, 10, 3, 95, 56, 88, 6, 136, 47, 37, 0, 0, 11, 200, 36, 228, 201, 28, 133, 6, 84, 192, 66, 12, 68, 32, 84, 143, 16, 105, 119, 34, 13, 70, 0, 0, 8, 197, 61, 85, 16, 85, 64, 65, 16, 70, 56, 81, 204, 36, 113, 69, 50, 119, 79, 55, 120, 88, 136, 0, 14, 69, 52, 84, 133, 77, 64, 63, 139, 34, 13, 87, 47, 0, 20, 67, 52, 18, 78, 63, 6, 136, 50, 87, 47, 34, 4, 127, 47, 0, 81, 115, 116, 32, 8, 197, 21, 132, 15, 73, 64, 36, 9, 197, 21, 132, 15, 73, 64, 65, 10, 0, 16, 70, 93, 147, 205, 36, 225, 192, 58, 135, 6, 134, 63, 120, 66, 0, 0, 0, 12, 68, 52, 20, 137, 4, 63, 117, 34, 127, 13, 0, 11, 68, 32, 84, 143, 20, 105, 139, 34, 134, 0, 19, 72, 12, 128, 78, 16, 83, 9, 21, 32, 89, 35, 50, 70, 13, 55, 6, 140, 0, 20, 72, 12, 20, 130, 85, 33, 84, 61, 32, 49, 125, 69, 13, 34, 136, 47, 112, 0, 103, 20, 72, 12, 20, 130, 85, 33, 84, 61, 32, 49, 125, 69, 13, 34, 6, 119, 47, 112, 0, 0, 9, 67, 36, 18, 78, 127, 13, 50, 0, 14, 69, 8, 197, 69, 77, 64, 69, 55, 132, 13, 87, 47, 0, 0, 9, 66, 52, 80, 63, 127, 0, 15, 14, 9, 66, 52, 80, 4, 63, 127, 0, 9, 14, 70, 80, 16, 140, 20, 21, 64, 47, 35, 69, 55, 134, 0, 14, 70, 52, 147, 5, 4, 113, 64, 63, 135, 55, 111, 73, 0, 16, 70, 12, 20, 18, 36, 49, 64, 49, 117, 48, 34, 6, 127, 87, 0, 0, 12, 3, 95, 57, 88, 50, 6, 135, 50, 47, 37, 0, 0, 14, 70, 32, 20, 146, 36, 85, 0, 105, 35, 34, 139, 47, 0, 16, 70, 56, 81, 204, 20, 53, 0, 50, 111, 79, 55, 119, 49, 47, 0, 15, 70, 13, 35, 207, 44, 81, 0, 49, 34, 115, 49, 120, 70, 0, 19, 72, 9, 81, 7, 21, 34, 71, 5, 32, 69, 123, 73, 13, 34, 120, 79, 125, 0, 0, 17, 69, 32, 21, 137, 56, 112, 4, 105, 35, 82, 120, 66, 0, 12, 35, 9, 13, 69, 72, 80, 68, 52, 80, 34, 127, 70, 63, 127, 0, 16, 69, 25, 84, 143, 72, 80, 81, 57, 132, 34, 6, 128, 34, 37, 0, 14, 69, 12, 241, 206, 4, 48, 49, 122, 50, 57, 35, 49, 0, 15, 70, 8, 243, 136, 60, 210, 69, 69, 122, 50, 13, 63, 127, 0, 0, 14, 70, 48, 147, 132, 76, 86, 64, 55, 120, 50, 86, 37, 0, 8, 67, 52, 22, 65, 63, 142, 0, 14, 70, 77, 81, 134, 60, 194, 192, 87, 123, 81, 13, 49, 0, 13, 202, 12, 148, 131, 84, 209, 133, 72, 83, 131, 20, 66, 16, 70, 8, 148, 5, 16, 19, 0, 69, 135, 48, 6, 127, 70, 116, 0, 9, 67, 4, 131, 217, 117, 105, 137, 0, 0, 26, 67, 52, 22, 64, 4, 63, 136, 105, 6, 35, 82, 47, 114, 0, 32, 14, 82, 104, 97, 118, 101, 32, 116, 111, 32, 19, 67, 52, 22, 64, 63, 136, 105, 117, 82, 0, 35, 77, 81, 104, 97, 118, 101, 32, 10, 67, 52, 22, 64, 63, 136, 0, 32, 12, 15, 71, 12, 128, 82, 48, 245, 20, 20, 89, 125, 55, 13, 47, 0, 18, 71, 76, 80, 210, 21, 64, 82, 100, 87, 119, 49, 34, 13, 47, 34, 120, 0, 20, 71, 37, 66, 78, 21, 32, 82, 100, 135, 47, 6, 120, 50, 13, 34, 13, 34, 120, 0, 17, 71, 29, 35, 211, 88, 83, 143, 72, 79, 34, 134, 82, 13, 50, 112, 0, 0, 13, 68, 52, 83, 149, 76, 63, 119, 50, 57, 132, 86, 0, 16, 70, 12, 244, 9, 48, 245, 0, 49, 134, 48, 135, 55, 13, 47, 0, 0, 15, 69, 4, 230, 79, 56, 80, 119, 50, 120, 58, 123, 50, 0, 106, 14, 69, 4, 230, 79, 56, 80, 119, 50, 120, 58, 122, 50, 0, 9, 67, 60, 208, 82, 134, 63, 125, 0, 14, 69, 56, 245, 77, 20, 16, 50, 132, 63, 6, 136, 13, 0, 14, 69, 12, 20, 9, 80, 16, 49, 35, 48, 120, 47, 13, 0, 12, 69, 8, 195, 213, 76, 80, 69, 55, 133, 86, 0, 0, 17, 70, 65, 34, 86, 4, 54, 64, 48, 34, 135, 82, 13, 87, 37, 0, 103, 16, 70, 81, 34, 76, 60, 118, 64, 47, 34, 120, 55, 13, 73, 37, 0, 15, 70, 72, 80, 201, 80, 19, 0, 34, 111, 87, 135, 47, 116, 0, 11, 3, 95, 63, 65, 55, 4, 119, 47, 112, 0, 0, 10, 199, 76, 80, 129, 77, 66, 65, 56, 66, 18, 71, 4, 69, 133, 73, 48, 82, 100, 35, 70, 82, 112, 87, 13, 34, 37, 0, 0, 20, 72, 77, 68, 153, 12, 131, 137, 56, 80, 87, 47, 34, 6, 120, 49, 50, 127, 50, 0, 12, 68, 72, 81, 137, 80, 34, 127, 81, 120, 47, 0, 0, 0, 0, 0, 9, 198, 92, 245, 76, 17, 53, 0, 76, 16, 70, 52, 144, 200, 36, 112, 78, 63, 120, 89, 120, 79, 13, 50, 0, 10, 68, 12, 244, 144, 76, 49, 130, 0, 9, 0, 17, 70, 77, 84, 137, 56, 19, 69, 87, 141, 34, 120, 50, 6, 35, 63, 0, 14, 69, 64, 19, 20, 73, 144, 48, 128, 55, 47, 34, 120, 0, 14, 69, 33, 80, 146, 37, 48, 105, 132, 69, 34, 120, 87, 0, 0, 11, 67, 85, 3, 206, 13, 48, 122, 50, 0, 74, 16, 70, 72, 84, 85, 36, 83, 64, 34, 119, 49, 58, 111, 119, 63, 0, 17, 70, 61, 33, 71, 4, 227, 192, 122, 34, 120, 79, 6, 124, 50, 134, 0, 0, 19, 66, 36, 224, 120, 50, 117, 15, 34, 6, 134, 0, 82, 97, 32, 114, 111, 119, 32, 20, 66, 36, 224, 120, 50, 15, 58, 120, 74, 0, 74, 8, 81, 119, 104, 105, 99, 104, 32, 15, 66, 36, 224, 2, 120, 50, 84, 113, 0, 81, 116, 104, 101, 32, 11, 66, 36, 224, 2, 120, 50, 0, 11, 9, 34, 20, 71, 52, 83, 129, 28, 84, 137, 20, 63, 13, 50, 6, 35, 73, 57, 13, 34, 37, 0, 5, 194, 56, 64, 9, 9, 3, 226, 153, 175, 89, 125, 48, 0, 0, 15, 70, 16, 147, 143, 76, 21, 82, 70, 135, 50, 13, 87, 130, 0, 6, 195, 61, 67, 200, 17, 6, 195, 53, 144, 64, 17, 11, 4, 95, 8, 15, 11, 105, 6, 115, 49, 0, 0, 11, 68, 104, 18, 82, 20, 86, 135, 6, 140, 0, 10, 68, 76, 131, 206, 20, 89, 122, 50, 0, 12, 68, 32, 84, 143, 56, 105, 119, 34, 13, 50, 0, 10, 3, 226, 153, 173, 81, 55, 35, 47, 0, 0, 0, 16, 70, 13, 84, 146, 20, 229, 0, 49, 6, 112, 13, 50, 47, 0, 103, 18, 70, 53, 82, 1, 52, 208, 68, 109, 111, 104, 97, 109, 109, 97, 100, 0, 29, 9, 198, 85, 5, 9, 28, 133, 0, 66, 16, 70, 64, 243, 9, 80, 84, 128, 48, 13, 55, 6, 135, 47, 112, 0, 0, 19, 71, 33, 148, 5, 72, 35, 204, 4, 105, 135, 48, 6, 126, 69, 13, 55, 13, 0, 15, 4, 95, 15, 7, 15, 6, 122, 79, 122, 50, 4, 119, 49, 0, 0, 13, 68, 56, 243, 206, 20, 50, 134, 58, 123, 50, 0, 106, 12, 68, 56, 243, 206, 20, 50, 134, 58, 122, 50, 0, 12, 68, 61, 97, 82, 80, 134, 82, 6, 126, 47, 0, 0, 13, 69, 72, 81, 9, 4, 192, 34, 127, 70, 142, 55, 0, 0, 9, 66, 61, 32, 130, 0, 72, 8, 9, 10, 67, 65, 35, 211, 48, 34, 134, 86, 0, 15, 70, 32, 243, 19, 80, 84, 128, 105, 134, 55, 87, 47, 112, 0, 13, 202, 16, 83, 79, 57, 53, 18, 5, 66, 86, 20, 66, 0, 0, 0, 0, 10, 67, 76, 83, 147, 87, 119, 50, 87, 0, 0, 13, 67, 92, 83, 148, 2, 58, 119, 50, 47, 0, 12, 9, 17, 71, 4, 69, 133, 73, 66, 83, 20, 35, 70, 82, 112, 47, 135, 86, 0, 0, 21, 72, 52, 17, 1, 28, 20, 195, 5, 32, 63, 35, 70, 13, 79, 6, 35, 87, 49, 112, 0, 0, 11, 69, 48, 21, 217, 21, 32, 55, 137, 112, 0, 12, 69, 9, 84, 147, 5, 32, 69, 126, 87, 112, 0, 0, 15, 70, 16, 148, 197, 5, 49, 64, 70, 120, 86, 6, 127, 86, 0, 17, 70, 12, 243, 134, 72, 243, 148, 49, 13, 50, 81, 34, 123, 50, 47, 0, 15, 70, 4, 229, 9, 69, 81, 64, 35, 50, 47, 6, 127, 49, 0, 0, 10, 67, 29, 82, 64, 79, 132, 37, 0, 10, 0, 16, 8, 20, 8, 5, 18, 5, 39, 12, 12, 84, 138, 55, 0, 72, 32, 10, 67, 72, 243, 137, 34, 122, 50, 37, 0, 13, 68, 80, 86, 1, 76, 47, 119, 49, 87, 13, 87, 0, 9, 198, 61, 134, 77, 61, 35, 206, 67, 10, 67, 28, 83, 137, 73, 127, 50, 37, 0, 0, 14, 69, 52, 19, 1, 92, 144, 63, 117, 55, 124, 58, 37, 0, 14, 69, 28, 83, 133, 88, 16, 73, 13, 50, 127, 82, 13, 0, 13, 69, 60, 85, 86, 72, 80, 146, 82, 34, 13, 0, 105, 12, 69, 60, 85, 86, 72, 80, 126, 82, 34, 13, 0, 17, 70, 24, 244, 133, 57, 50, 67, 81, 13, 34, 119, 50, 87, 120, 49, 0, 8, 197, 5, 32, 193, 16, 80, 66, 0, 16, 70, 76, 243, 9, 12, 149, 0, 87, 13, 55, 120, 87, 111, 47, 0, 0, 18, 71, 80, 83, 80, 61, 32, 82, 100, 47, 119, 63, 48, 34, 13, 34, 120, 0, 20, 71, 52, 85, 1, 8, 243, 9, 12, 63, 119, 47, 13, 69, 6, 122, 55, 120, 49, 0, 0, 12, 68, 4, 32, 66, 4, 35, 69, 117, 69, 13, 0, 12, 68, 72, 80, 68, 16, 34, 127, 6, 35, 70, 0, 0, 12, 69, 64, 84, 147, 36, 16, 48, 126, 88, 13, 0, 14, 69, 44, 244, 207, 88, 240, 49, 122, 87, 13, 82, 134, 0, 12, 69, 65, 54, 67, 32, 80, 87, 135, 49, 127, 0, 8, 67, 40, 245, 82, 88, 141, 0, 0, 13, 70, 65, 54, 67, 32, 81, 0, 87, 135, 49, 70, 0, 9, 198, 61, 85, 2, 85, 36, 212, 65, 5, 194, 61, 48, 17, 0, 9, 67, 36, 19, 128, 127, 13, 50, 0, 14, 203, 36, 225, 146, 5, 53, 18, 84, 53, 21, 72, 80, 65, 17, 71, 24, 244, 133, 77, 64, 76, 48, 81, 131, 87, 47, 6, 128, 55, 0, 16, 71, 5, 48, 197, 73, 64, 73, 56, 35, 87, 112, 47, 136, 50, 0, 0, 9, 67, 56, 243, 133, 50, 123, 50, 0, 11, 68, 8, 84, 153, 48, 69, 119, 34, 116, 0, 0, 12, 201, 12, 243, 148, 72, 245, 133, 73, 54, 64, 65, 14, 69, 12, 19, 129, 73, 144, 49, 13, 50, 138, 34, 37, 0, 15, 70, 4, 230, 84, 32, 147, 135, 119, 50, 111, 85, 120, 66, 0, 6, 195, 65, 35, 198, 24, 0, 17, 70, 32, 84, 143, 37, 51, 64, 105, 119, 34, 134, 120, 86, 13, 63, 0, 15, 70, 20, 66, 84, 36, 243, 128, 111, 70, 120, 89, 13, 50, 0, 13, 4, 95, 48, 77, 50, 63, 6, 120, 55, 139, 50, 0, 0, 10, 198, 12, 17, 134, 20, 147, 133, 103, 66, 19, 71, 40, 84, 149, 76, 19, 5, 52, 73, 13, 34, 132, 87, 13, 55, 13, 63, 0, 9, 67, 72, 245, 84, 34, 133, 47, 0, 17, 71, 72, 81, 133, 73, 34, 78, 28, 34, 111, 81, 126, 34, 120, 66, 0, 13, 4, 95, 48, 77, 51, 69, 6, 120, 55, 139, 50, 0, 0, 11, 68, 52, 20, 137, 20, 63, 117, 34, 127, 0, 12, 68, 44, 20, 21, 80, 49, 117, 48, 115, 47, 0, 0, 23, 73, 56, 85, 198, 61, 83, 132, 48, 19, 132, 50, 57, 132, 81, 13, 50, 70, 55, 117, 50, 70, 0, 14, 69, 77, 68, 137, 65, 144, 87, 47, 34, 135, 48, 120, 0, 13, 69, 64, 21, 8, 61, 48, 48, 136, 85, 122, 87, 0, 14, 4, 95, 48, 77, 49, 85, 6, 133, 86, 13, 50, 70, 0, 0, 17, 70, 88, 243, 3, 4, 227, 192, 82, 122, 55, 49, 6, 136, 50, 134, 0, 12, 4, 95, 2, 18, 22, 69, 34, 6, 127, 82, 0, 0, 0, 12, 68, 8, 85, 23, 76, 69, 119, 47, 115, 87, 0, 0, 10, 67, 77, 81, 90, 87, 132, 111, 86, 0, 12, 201, 77, 84, 5, 73, 98, 83, 36, 243, 128, 67, 14, 69, 52, 20, 131, 20, 192, 63, 125, 87, 6, 119, 55, 0, 17, 70, 20, 212, 8, 5, 50, 83, 119, 63, 81, 13, 87, 120, 87, 0, 9, 12, 69, 12, 130, 83, 20, 192, 74, 120, 86, 116, 0, 0, 15, 70, 52, 83, 9, 77, 48, 64, 63, 13, 55, 120, 87, 13, 0, 9, 198, 52, 83, 12, 37, 48, 64, 66, 9, 198, 92, 81, 75, 20, 225, 0, 66, 13, 70, 52, 19, 136, 61, 84, 128, 63, 35, 50, 144, 0, 0, 10, 67, 56, 244, 128, 50, 130, 0, 8, 9, 18, 67, 24, 244, 128, 81, 130, 58, 122, 50, 0, 66, 14, 81, 111, 110, 101, 32, 23, 67, 24, 244, 128, 81, 13, 13, 15, 58, 6, 135, 55, 0, 82, 97, 32, 119, 104, 105, 108, 101, 32, 16, 67, 24, 244, 128, 81, 112, 84, 113, 0, 34, 81, 116, 104, 101, 32, 15, 67, 24, 244, 128, 81, 13, 13, 50, 0, 34, 81, 97, 110, 32, 13, 67, 24, 244, 128, 81, 13, 13, 0, 34, 81, 97, 32, 9, 67, 24, 244, 128, 81, 130, 0, 72, 18, 71, 76, 80, 210, 21, 66, 86, 20, 87, 127, 49, 34, 13, 47, 120, 82, 0, 15, 71, 13, 35, 201, 77, 48, 78, 80, 49, 58, 124, 87, 148, 0, 0, 16, 67, 52, 19, 153, 63, 119, 50, 120, 13, 82, 0, 81, 111, 102, 32, 11, 67, 52, 19, 153, 63, 119, 50, 37, 0, 34, 11, 67, 92, 84, 133, 2, 58, 126, 0, 35, 9, 15, 70, 8, 244, 215, 20, 195, 0, 69, 122, 86, 58, 119, 55, 0, 12, 68, 76, 147, 79, 56, 87, 135, 63, 13, 50, 0, 9, 67, 20, 148, 133, 138, 34, 13, 0, 0, 14, 69, 8, 21, 13, 4, 224, 69, 35, 47, 63, 35, 50, 0, 0, 15, 70, 76, 83, 129, 80, 244, 128, 87, 119, 50, 13, 47, 112, 0, 0, 10, 199, 64, 243, 25, 80, 129, 78, 20, 65, 0, 12, 68, 32, 243, 193, 32, 105, 6, 132, 6, 124, 0, 0, 14, 69, 8, 83, 143, 37, 64, 69, 119, 50, 58, 6, 124, 0, 12, 201, 53, 83, 20, 37, 3, 5, 96, 84, 128, 65, 13, 69, 4, 35, 1, 85, 64, 35, 69, 55, 133, 47, 0, 0, 16, 70, 8, 80, 193, 85, 49, 64, 69, 120, 49, 123, 86, 0, 66, 8, 0, 0, 0, 13, 5, 23, 5, 39, 12, 12, 58, 127, 55, 0, 72, 32, 14, 69, 20, 194, 67, 37, 64, 111, 55, 120, 87, 111, 47, 0, 0, 14, 70, 12, 129, 77, 37, 49, 64, 89, 13, 63, 127, 86, 0, 24, 66, 44, 208, 87, 49, 58, 4, 138, 49, 120, 55, 6, 122, 63, 120, 47, 112, 86, 0, 81, 194, 178, 32, 0, 19, 71, 9, 80, 200, 5, 33, 83, 80, 69, 132, 49, 117, 34, 6, 119, 87, 47, 0, 16, 70, 8, 20, 130, 21, 21, 69, 69, 125, 69, 13, 49, 57, 132, 0, 0, 11, 68, 52, 242, 82, 4, 63, 137, 34, 13, 0, 13, 68, 80, 22, 9, 76, 47, 35, 49, 87, 37, 86, 0, 12, 68, 24, 85, 21, 76, 81, 127, 47, 13, 87, 0, 0, 14, 69, 80, 18, 80, 20, 144, 47, 4, 135, 48, 6, 136, 0, 15, 69, 8, 146, 201, 56, 144, 69, 120, 49, 6, 127, 50, 37, 0, 0, 16, 70, 52, 147, 4, 72, 81, 0, 63, 120, 55, 70, 34, 111, 70, 0, 9, 198, 61, 85, 19, 44, 148, 148, 65, 16, 70, 8, 19, 145, 84, 85, 0, 69, 35, 66, 49, 58, 111, 47, 0, 0, 14, 70, 56, 244, 151, 36, 50, 0, 50, 122, 34, 111, 74, 0, 19, 71, 80, 83, 5, 52, 85, 18, 100, 47, 13, 55, 119, 63, 13, 47, 34, 37, 0, 19, 71, 33, 148, 5, 72, 35, 204, 20, 105, 135, 48, 6, 126, 69, 13, 55, 37, 0, 16, 70, 21, 2, 80, 32, 19, 153, 111, 48, 120, 81, 13, 50, 120, 0, 17, 71, 12, 132, 137, 77, 67, 65, 76, 49, 34, 120, 87, 63, 13, 87, 0, 0, 11, 67, 60, 227, 25, 134, 50, 55, 37, 0, 40, 12, 68, 16, 244, 137, 76, 70, 122, 34, 120, 87, 0, 15, 70, 13, 34, 67, 33, 67, 206, 49, 34, 135, 47, 13, 50, 0, 12, 68, 8, 244, 137, 76, 69, 122, 34, 120, 87, 0, 11, 68, 16, 128, 66, 36, 70, 124, 69, 37, 0, 18, 72, 65, 33, 83, 12, 145, 78, 12, 80, 48, 34, 127, 87, 139, 50, 87, 0, 0, 13, 69, 24, 16, 201, 48, 80, 81, 35, 87, 116, 0, 103, 13, 69, 12, 80, 201, 48, 80, 87, 119, 87, 127, 55, 0, 8, 197, 85, 1, 1, 80, 80, 36, 9, 197, 85, 1, 1, 80, 80, 65, 10, 13, 69, 76, 81, 1, 80, 80, 87, 111, 70, 136, 47, 0, 15, 69, 12, 194, 67, 32, 80, 49, 55, 127, 89, 6, 136, 0, 103, 13, 69, 12, 194, 67, 32, 80, 49, 55, 127, 89, 136, 0, 0, 10, 66, 53, 144, 63, 135, 0, 72, 34, 12, 0, 10, 67, 77, 81, 84, 87, 132, 111, 47, 0, 19, 71, 65, 35, 205, 20, 224, 68, 20, 48, 34, 122, 63, 13, 50, 6, 124, 70, 0, 28, 75, 36, 225, 9, 76, 52, 137, 52, 147, 129, 80, 80, 120, 50, 70, 111, 87, 49, 34, 6, 120, 63, 111, 50, 13, 47, 0, 0, 18, 72, 93, 35, 206, 28, 67, 201, 56, 112, 34, 122, 66, 70, 132, 120, 66, 0, 0, 0, 15, 70, 80, 131, 213, 76, 19, 132, 85, 133, 86, 13, 50, 70, 0, 13, 202, 32, 84, 141, 5, 2, 18, 60, 66, 84, 20, 66, 16, 70, 12, 131, 210, 37, 163, 192, 74, 129, 34, 6, 127, 86, 134, 0, 15, 70, 8, 20, 212, 36, 243, 128, 69, 35, 87, 47, 139, 50, 0, 0, 15, 67, 61, 85, 0, 4, 133, 47, 13, 82, 0, 81, 111, 102, 32, 19, 71, 20, 66, 78, 9, 84, 135, 32, 119, 70, 120, 50, 69, 2, 123, 34, 13, 0, 18, 71, 21, 21, 73, 88, 240, 193, 48, 111, 49, 58, 120, 82, 13, 49, 116, 0, 0, 11, 68, 48, 84, 143, 100, 55, 127, 34, 137, 0, 0, 13, 69, 52, 245, 137, 21, 48, 63, 132, 82, 120, 86, 0, 0, 20, 66, 60, 96, 123, 82, 58, 120, 74, 0, 106, 66, 8, 81, 119, 104, 105, 99, 104, 32, 16, 66, 60, 96, 2, 123, 84, 113, 0, 106, 34, 81, 116, 104, 101, 32, 16, 66, 60, 96, 3, 122, 82, 84, 113, 0, 34, 81, 116, 104, 101, 32, 19, 66, 60, 96, 122, 82, 58, 120, 74, 0, 66, 8, 81, 119, 104, 105, 99, 104, 32, 14, 66, 60, 96, 13, 82, 13, 50, 0, 34, 81, 97, 110, 32, 12, 66, 60, 96, 13, 82, 13, 0, 34, 81, 97, 32, 10, 66, 60, 96, 123, 82, 0, 106, 72, 9, 9, 66, 60, 96, 122, 82, 0, 72, 9, 14, 70, 76, 147, 194, 32, 19, 128, 89, 13, 82, 128, 50, 0, 14, 70, 8, 19, 12, 60, 243, 128, 69, 13, 55, 132, 50, 0, 16, 70, 4, 33, 15, 52, 83, 128, 35, 69, 70, 13, 63, 13, 50, 0, 0, 16, 70, 52, 243, 143, 80, 243, 133, 63, 122, 50, 13, 47, 134, 50, 0, 9, 67, 52, 144, 192, 63, 135, 49, 0, 17, 70, 24, 193, 88, 36, 35, 5, 81, 55, 119, 49, 87, 120, 69, 116, 0, 0, 9, 68, 92, 131, 210, 20, 105, 131, 0, 13, 68, 88, 242, 76, 4, 82, 58, 35, 55, 6, 35, 0, 11, 68, 88, 144, 193, 72, 82, 120, 49, 112, 0, 10, 67, 52, 144, 193, 63, 135, 49, 13, 0, 0, 16, 69, 44, 244, 133, 4, 224, 49, 112, 34, 6, 127, 13, 50, 0, 103, 15, 69, 44, 244, 133, 4, 224, 49, 129, 34, 6, 127, 13, 50, 0, 14, 69, 77, 84, 5, 72, 32, 87, 132, 48, 6, 126, 69, 0, 13, 69, 76, 80, 66, 20, 64, 87, 127, 69, 119, 70, 0, 0, 16, 70, 64, 16, 201, 24, 144, 192, 48, 117, 87, 120, 81, 120, 49, 0, 12, 201, 80, 129, 82, 52, 244, 212, 4, 35, 5, 20, 17, 70, 65, 148, 137, 80, 84, 192, 48, 135, 34, 6, 135, 47, 127, 86, 0, 14, 70, 48, 148, 85, 21, 84, 128, 55, 111, 49, 126, 0, 103, 14, 70, 48, 148, 85, 21, 84, 128, 55, 111, 49, 57, 141, 0, 0, 0, 22, 72, 12, 244, 5, 56, 128, 71, 20, 224, 49, 134, 48, 13, 50, 105, 6, 136, 79, 13, 50, 0, 10, 67, 52, 17, 201, 63, 136, 73, 135, 0, 0, 14, 69, 4, 198, 67, 20, 224, 35, 55, 120, 87, 13, 50, 0, 18, 70, 76, 19, 148, 36, 17, 207, 87, 35, 50, 47, 120, 6, 124, 79, 134, 0, 12, 69, 76, 48, 82, 20, 64, 87, 49, 138, 70, 0, 0, 28, 74, 36, 229, 133, 77, 66, 71, 5, 66, 86, 20, 120, 50, 82, 4, 119, 87, 47, 111, 79, 6, 136, 47, 120, 82, 0, 103, 15, 70, 28, 84, 129, 36, 229, 0, 79, 119, 34, 135, 50, 47, 0, 15, 70, 56, 20, 195, 20, 229, 0, 50, 136, 87, 13, 50, 47, 0, 15, 70, 8, 243, 138, 61, 84, 128, 69, 128, 50, 88, 6, 141, 0, 15, 70, 4, 116, 143, 84, 225, 0, 117, 79, 34, 133, 50, 70, 0, 0, 8, 67, 4, 33, 64, 136, 69, 0, 19, 71, 65, 33, 68, 20, 98, 78, 20, 48, 34, 127, 70, 111, 81, 6, 135, 50, 0, 17, 70, 36, 224, 210, 20, 20, 197, 120, 50, 49, 34, 6, 127, 87, 0, 36, 14, 70, 13, 33, 65, 81, 84, 133, 49, 34, 127, 74, 112, 0, 0, 13, 68, 92, 131, 211, 20, 4, 105, 132, 86, 0, 8, 9, 16, 7, 8, 1, 23, 1, 9, 39, 9, 105, 13, 58, 6, 135, 127, 0, 0, 14, 69, 16, 84, 197, 73, 64, 70, 111, 86, 126, 47, 0, 36, 14, 69, 16, 84, 197, 73, 64, 70, 119, 87, 112, 47, 0, 9, 13, 69, 16, 84, 197, 73, 64, 70, 111, 86, 126, 47, 0, 14, 69, 12, 243, 80, 5, 64, 49, 13, 63, 48, 35, 47, 0, 0, 15, 70, 77, 65, 82, 36, 193, 64, 87, 47, 119, 34, 116, 0, 103, 15, 70, 36, 211, 199, 20, 225, 64, 120, 63, 13, 73, 13, 50, 0, 16, 70, 84, 180, 129, 36, 225, 64, 57, 132, 49, 34, 6, 136, 50, 0, 15, 70, 28, 192, 83, 28, 245, 192, 79, 55, 118, 86, 79, 134, 0, 13, 70, 88, 82, 9, 12, 193, 64, 82, 139, 49, 116, 0, 18, 70, 84, 181, 76, 20, 193, 64, 57, 132, 49, 13, 55, 6, 136, 55, 37, 0, 15, 70, 77, 65, 82, 36, 193, 64, 87, 47, 119, 34, 135, 55, 0, 14, 70, 52, 244, 129, 36, 225, 64, 63, 13, 34, 136, 50, 0, 15, 70, 12, 240, 193, 36, 225, 64, 49, 134, 49, 6, 136, 50, 0, 0, 13, 67, 60, 225, 64, 58, 123, 50, 0, 106, 34, 10, 13, 12, 67, 60, 225, 64, 58, 122, 50, 0, 34, 10, 13, 16, 67, 20, 16, 200, 127, 74, 15, 13, 82, 0, 8, 81, 111, 102, 32, 14, 70, 60, 209, 76, 21, 69, 5, 122, 63, 55, 13, 47, 0, 10, 67, 4, 33, 68, 117, 69, 119, 70, 0, 6, 195, 60, 209, 192, 17, 0, 0, 14, 69, 17, 34, 69, 77, 64, 70, 34, 135, 13, 87, 47, 0, 0, 16, 70, 12, 243, 82, 4, 65, 64, 49, 122, 63, 34, 35, 70, 0, 103, 13, 67, 60, 229, 15, 4, 122, 50, 106, 115, 0, 103, 12, 12, 67, 60, 229, 15, 4, 122, 50, 47, 115, 0, 12, 16, 70, 77, 3, 203, 4, 225, 64, 87, 48, 134, 49, 6, 35, 50, 0, 15, 70, 92, 19, 142, 4, 33, 64, 58, 122, 50, 117, 69, 127, 0, 15, 70, 32, 84, 143, 36, 225, 64, 105, 119, 34, 134, 120, 50, 0, 15, 70, 29, 33, 78, 4, 65, 64, 79, 34, 13, 50, 136, 70, 0, 9, 198, 4, 229, 9, 48, 241, 192, 65, 0, 20, 71, 76, 147, 131, 21, 33, 83, 80, 87, 120, 50, 87, 6, 139, 34, 13, 87, 47, 0, 15, 70, 4, 229, 9, 60, 50, 0, 35, 50, 106, 127, 122, 49, 0, 0, 12, 68, 80, 129, 73, 72, 84, 138, 0, 72, 34, 9, 11, 67, 52, 18, 197, 63, 4, 136, 49, 0, 12, 12, 67, 52, 18, 197, 63, 4, 136, 49, 0, 12, 9, 12, 68, 64, 80, 193, 56, 48, 127, 49, 13, 50, 0, 11, 68, 12, 145, 193, 72, 87, 111, 79, 125, 0, 8, 4, 95, 35, 18, 4, 70, 0, 0, 14, 69, 25, 85, 9, 48, 80, 81, 57, 132, 47, 116, 0, 103, 12, 69, 80, 129, 78, 12, 80, 84, 119, 50, 87, 0, 13, 69, 44, 20, 133, 56, 80, 49, 117, 34, 127, 50, 0, 8, 197, 4, 208, 78, 16, 16, 66, 14, 69, 32, 20, 129, 72, 80, 105, 117, 34, 124, 34, 37, 0, 14, 69, 85, 48, 66, 48, 80, 57, 132, 86, 13, 69, 116, 0, 13, 69, 76, 84, 133, 56, 80, 87, 13, 34, 127, 50, 0, 13, 69, 12, 20, 129, 24, 80, 49, 117, 34, 35, 81, 0, 9, 67, 4, 160, 82, 117, 73, 125, 0, 0, 0, 0, 12, 68, 4, 192, 78, 4, 117, 55, 35, 50, 13, 0, 12, 68, 48, 17, 207, 76, 55, 136, 79, 122, 87, 0, 12, 68, 76, 48, 76, 16, 87, 49, 122, 55, 70, 0, 0, 15, 70, 5, 34, 193, 57, 48, 83, 125, 49, 13, 50, 87, 128, 0, 13, 69, 84, 228, 213, 72, 80, 123, 50, 89, 6, 141, 0, 14, 69, 76, 81, 21, 12, 80, 87, 111, 70, 57, 132, 87, 0, 14, 69, 28, 83, 73, 56, 144, 73, 119, 63, 111, 50, 135, 0, 0, 11, 5, 23, 5, 39, 18, 5, 2, 58, 140, 0, 17, 70, 65, 83, 138, 4, 34, 64, 48, 123, 50, 73, 6, 124, 69, 37, 0, 20, 70, 37, 53, 1, 56, 37, 76, 4, 120, 87, 47, 4, 35, 50, 69, 6, 115, 55, 0, 17, 70, 76, 21, 1, 56, 148, 212, 87, 136, 47, 13, 50, 120, 87, 47, 0, 5, 194, 57, 144, 17, 0, 13, 6, 25, 15, 21, 39, 18, 5, 2, 57, 141, 0, 106, 12, 6, 25, 15, 21, 39, 18, 5, 2, 57, 130, 0, 9, 67, 65, 81, 0, 48, 115, 70, 0, 6, 195, 36, 35, 64, 17, 0, 12, 68, 8, 85, 19, 100, 69, 119, 47, 87, 37, 0, 21, 72, 77, 67, 206, 20, 129, 78, 28, 80, 87, 47, 4, 134, 50, 105, 6, 119, 50, 73, 0, 13, 68, 60, 209, 71, 4, 134, 63, 6, 136, 79, 13, 0, 14, 70, 4, 148, 144, 61, 113, 82, 6, 138, 48, 4, 144, 0, 0, 15, 69, 84, 229, 9, 17, 144, 123, 50, 47, 6, 135, 70, 37, 0, 13, 69, 65, 33, 84, 81, 144, 48, 34, 120, 47, 37, 0, 0, 15, 70, 104, 130, 86, 4, 115, 192, 88, 111, 82, 124, 79, 134, 0, 19, 4, 95, 3, 9, 18, 87, 6, 126, 49, 123, 63, 81, 55, 4, 119, 49, 87, 0, 0, 14, 7, 20, 8, 5, 18, 5, 39, 4, 2, 84, 138, 70, 0, 12, 67, 65, 85, 0, 4, 48, 115, 47, 0, 10, 12, 11, 67, 4, 160, 88, 136, 73, 35, 49, 87, 0, 10, 67, 4, 33, 84, 117, 69, 119, 47, 0, 6, 195, 57, 149, 0, 17, 6, 195, 12, 83, 192, 17, 0, 16, 70, 12, 132, 153, 76, 193, 82, 49, 34, 135, 87, 55, 112, 0, 103, 15, 70, 12, 132, 153, 76, 193, 82, 49, 34, 135, 86, 55, 112, 0, 11, 68, 80, 146, 203, 4, 47, 127, 49, 13, 0, 12, 68, 48, 147, 73, 80, 55, 120, 63, 111, 47, 0, 9, 198, 24, 244, 133, 92, 20, 142, 66, 9, 67, 20, 32, 89, 127, 69, 136, 0, 0, 14, 69, 72, 20, 137, 81, 144, 34, 138, 34, 13, 47, 37, 0, 0, 14, 6, 25, 15, 21, 39, 12, 12, 57, 132, 55, 0, 72, 32, 15, 70, 52, 19, 3, 60, 195, 64, 63, 35, 55, 49, 13, 63, 0, 15, 70, 65, 35, 206, 61, 83, 128, 48, 34, 134, 50, 133, 50, 0, 13, 3, 95, 194, 183, 63, 120, 70, 116, 70, 122, 47, 0, 0, 12, 67, 61, 84, 128, 133, 112, 0, 103, 72, 34, 9, 10, 67, 61, 84, 128, 144, 0, 72, 34, 9, 15, 71, 80, 19, 201, 76, 80, 67, 32, 47, 127, 89, 13, 99, 0, 9, 198, 52, 17, 193, 104, 147, 133, 67, 16, 71, 12, 243, 77, 37, 69, 5, 20, 49, 13, 63, 120, 47, 37, 0, 17, 3, 95, 194, 180, 117, 49, 57, 132, 47, 35, 49, 87, 119, 50, 47, 0, 0, 12, 68, 60, 208, 72, 4, 134, 63, 117, 105, 124, 0, 13, 68, 44, 240, 76, 4, 49, 134, 6, 124, 55, 13, 0, 19, 72, 4, 195, 8, 4, 195, 15, 93, 48, 128, 55, 105, 6, 35, 55, 134, 86, 0, 0, 13, 69, 48, 84, 201, 60, 224, 55, 127, 88, 13, 50, 0, 12, 69, 12, 83, 9, 16, 128, 49, 136, 55, 37, 0, 19, 3, 95, 194, 178, 87, 132, 48, 13, 87, 49, 34, 120, 48, 47, 47, 6, 132, 0, 0, 9, 67, 72, 134, 83, 34, 127, 87, 0, 17, 70, 4, 193, 129, 48, 96, 64, 35, 55, 81, 6, 35, 55, 81, 13, 0, 20, 3, 95, 194, 179, 87, 132, 48, 13, 87, 49, 34, 120, 48, 47, 85, 6, 34, 127, 0, 0, 20, 71, 4, 225, 18, 60, 209, 68, 4, 35, 50, 70, 34, 6, 122, 63, 120, 70, 13, 0, 16, 71, 12, 21, 8, 21, 34, 78, 20, 49, 35, 85, 34, 111, 50, 0, 19, 71, 65, 33, 67, 20, 65, 78, 80, 48, 34, 119, 87, 111, 70, 13, 50, 47, 0, 0, 11, 67, 40, 244, 197, 105, 134, 87, 6, 136, 0, 11, 200, 84, 225, 5, 73, 115, 210, 48, 64, 65, 0, 14, 69, 61, 33, 71, 60, 224, 122, 34, 111, 79, 13, 50, 0, 12, 69, 92, 148, 146, 4, 192, 58, 120, 34, 116, 0, 14, 69, 76, 16, 210, 20, 64, 87, 136, 49, 34, 13, 70, 0, 9, 197, 36, 229, 5, 72, 224, 65, 10, 14, 69, 36, 229, 5, 72, 224, 120, 50, 47, 126, 50, 0, 37, 13, 69, 12, 20, 144, 20, 192, 49, 125, 48, 13, 55, 0, 14, 69, 9, 33, 65, 80, 128, 69, 34, 127, 84, 0, 36, 10, 13, 69, 9, 33, 65, 80, 128, 69, 34, 119, 85, 0, 10, 0, 0, 12, 4, 8, 5, 39, 19, 105, 127, 86, 0, 72, 35, 9, 67, 4, 37, 64, 35, 69, 132, 0, 9, 67, 72, 245, 192, 34, 133, 0, 37, 8, 67, 72, 245, 192, 34, 134, 0, 21, 71, 36, 225, 197, 57, 82, 84, 100, 120, 50, 73, 111, 50, 6, 57, 132, 111, 47, 37, 0, 9, 67, 8, 245, 192, 69, 133, 0, 36, 8, 67, 8, 245, 192, 69, 134, 0, 13, 4, 95, 19, 20, 11, 87, 47, 34, 6, 134, 49, 0, 0, 14, 68, 80, 131, 211, 20, 84, 134, 86, 0, 72, 34, 12, 9, 9, 4, 95, 35, 19, 20, 87, 47, 0, 12, 3, 95, 194, 173, 63, 35, 49, 34, 122, 50, 0, 11, 4, 95, 3, 18, 12, 49, 6, 126, 55, 0, 0, 14, 69, 16, 81, 133, 13, 64, 70, 127, 81, 119, 49, 47, 0, 19, 3, 95, 194, 170, 81, 119, 63, 111, 50, 120, 50, 6, 130, 70, 111, 50, 116, 0, 13, 4, 95, 1, 3, 21, 117, 49, 57, 6, 132, 47, 0, 0, 15, 70, 13, 66, 21, 48, 133, 64, 49, 14, 85, 132, 103, 132, 0, 14, 70, 93, 33, 84, 12, 129, 68, 34, 119, 74, 121, 70, 0, 15, 70, 76, 84, 85, 36, 225, 64, 87, 127, 49, 58, 111, 50, 0, 18, 70, 76, 80, 207, 56, 65, 68, 87, 119, 49, 6, 122, 50, 70, 121, 70, 0, 15, 70, 65, 84, 144, 61, 37, 0, 48, 126, 48, 6, 131, 47, 0, 16, 70, 28, 83, 149, 36, 225, 64, 73, 119, 50, 57, 132, 121, 50, 0, 18, 3, 95, 194, 171, 55, 119, 81, 47, 6, 79, 120, 55, 13, 63, 119, 47, 0, 0, 10, 67, 56, 245, 192, 50, 133, 0, 32, 42, 6, 195, 56, 245, 192, 32, 9, 67, 16, 69, 64, 84, 120, 0, 9, 15, 3, 95, 194, 168, 70, 135, 117, 34, 6, 127, 87, 120, 87, 0, 0, 10, 67, 77, 86, 153, 87, 132, 86, 37, 0, 13, 68, 81, 83, 9, 64, 47, 57, 132, 55, 120, 48, 0, 11, 68, 48, 192, 77, 4, 55, 124, 63, 13, 0, 8, 4, 95, 35, 20, 8, 85, 0, 0, 15, 3, 95, 194, 166, 69, 34, 134, 49, 13, 50, 69, 6, 125, 0, 0, 13, 202, 88, 83, 148, 72, 147, 15, 69, 82, 83, 80, 66, 16, 70, 65, 33, 76, 84, 65, 64, 48, 34, 119, 55, 57, 132, 70, 0, 0, 18, 71, 65, 34, 86, 36, 193, 71, 20, 48, 34, 120, 82, 111, 55, 111, 73, 0, 0, 12, 68, 64, 17, 193, 56, 48, 136, 79, 13, 50, 0, 11, 68, 48, 80, 70, 100, 55, 127, 81, 37, 0, 0, 16, 70, 77, 66, 76, 21, 69, 15, 87, 47, 111, 55, 119, 47, 134, 0, 13, 69, 52, 147, 137, 56, 112, 63, 135, 50, 120, 66, 0, 13, 69, 24, 244, 129, 28, 80, 81, 122, 34, 111, 73, 0, 0, 15, 70, 80, 84, 141, 36, 226, 64, 47, 126, 63, 120, 50, 135, 0, 16, 70, 77, 64, 78, 16, 38, 64, 87, 47, 35, 50, 70, 69, 135, 0, 0, 13, 3, 95, 194, 160, 105, 125, 70, 87, 48, 136, 87, 0, 12, 4, 95, 18, 14, 7, 34, 6, 120, 66, 79, 0, 0, 18, 72, 44, 19, 7, 60, 244, 140, 36, 80, 49, 35, 55, 79, 141, 55, 37, 0, 10, 68, 56, 144, 200, 20, 50, 127, 89, 0, 17, 72, 8, 245, 82, 28, 83, 201, 76, 80, 69, 141, 88, 58, 124, 86, 0, 27, 3, 95, 194, 161, 2, 120, 50, 82, 4, 126, 47, 111, 70, 119, 49, 87, 49, 55, 13, 63, 6, 136, 89, 13, 50, 0, 0, 19, 8, 16, 18, 15, 20, 5, 7, 195, 169, 112, 114, 111, 116, 101, 103, 101, 0, 29, 8, 197, 61, 85, 9, 56, 112, 65, 13, 69, 24, 83, 9, 56, 80, 81, 127, 55, 135, 50, 0, 12, 69, 13, 80, 203, 60, 240, 49, 115, 49, 132, 0, 0, 13, 5, 23, 5, 39, 22, 5, 58, 127, 82, 0, 72, 35, 15, 70, 16, 244, 143, 80, 134, 64, 70, 122, 34, 13, 85, 37, 0, 15, 70, 4, 229, 8, 60, 230, 64, 35, 50, 47, 13, 50, 37, 0, 17, 70, 9, 84, 149, 56, 66, 64, 69, 115, 34, 6, 115, 50, 70, 37, 0, 20, 9, 16, 18, 15, 20, 195, 169, 7, 195, 169, 112, 114, 111, 116, 101, 103, 101, 0, 29, 0, 14, 6, 25, 15, 21, 39, 22, 5, 57, 132, 82, 0, 72, 35, 9, 67, 72, 134, 76, 34, 120, 55, 0, 14, 70, 92, 130, 84, 37, 50, 0, 58, 135, 47, 120, 89, 0, 17, 71, 52, 245, 83, 80, 16, 200, 20, 63, 13, 87, 47, 6, 118, 89, 0, 18, 71, 8, 16, 203, 77, 67, 210, 100, 69, 35, 49, 87, 47, 131, 34, 37, 0, 21, 67, 33, 69, 16, 136, 74, 106, 127, 106, 127, 6, 48, 127, 10, 0, 81, 58, 47, 47, 32, 0, 17, 70, 80, 241, 197, 80, 129, 82, 47, 13, 79, 119, 84, 112, 0, 74, 12, 11, 68, 4, 129, 65, 16, 117, 105, 119, 70, 0, 11, 68, 96, 131, 211, 4, 49, 128, 87, 13, 0, 13, 68, 17, 145, 133, 16, 70, 6, 123, 82, 120, 70, 0, 20, 72, 12, 243, 80, 72, 243, 73, 76, 80, 49, 122, 63, 48, 34, 13, 63, 135, 86, 0, 11, 200, 12, 130, 77, 64, 19, 154, 20, 80, 67, 0, 14, 69, 76, 144, 201, 49, 144, 87, 120, 87, 111, 55, 37, 0, 13, 69, 72, 80, 197, 77, 48, 34, 127, 87, 119, 87, 0, 22, 73, 64, 131, 212, 60, 116, 129, 64, 134, 64, 81, 13, 47, 6, 122, 79, 34, 13, 81, 37, 0, 14, 69, 13, 34, 83, 21, 48, 49, 34, 135, 87, 127, 86, 0, 15, 69, 72, 148, 195, 61, 48, 34, 120, 87, 49, 134, 119, 87, 0, 0, 13, 67, 60, 225, 83, 58, 123, 50, 86, 0, 106, 9, 13, 12, 67, 60, 225, 83, 58, 122, 50, 86, 0, 9, 13, 17, 70, 72, 244, 193, 72, 147, 192, 34, 134, 86, 6, 125, 34, 120, 134, 0, 17, 70, 28, 19, 9, 48, 83, 192, 79, 35, 55, 111, 55, 6, 136, 134, 0, 0, 0, 22, 72, 84, 226, 86, 21, 36, 201, 81, 144, 57, 132, 50, 120, 82, 6, 126, 87, 111, 47, 37, 0, 14, 68, 72, 83, 73, 80, 34, 127, 63, 6, 120, 47, 0, 36, 12, 68, 72, 83, 73, 80, 34, 127, 63, 120, 47, 0, 11, 68, 12, 128, 78, 28, 74, 35, 66, 0, 10, 11, 68, 12, 128, 78, 28, 74, 136, 50, 73, 0, 0, 15, 69, 84, 37, 78, 81, 80, 132, 69, 6, 132, 50, 106, 132, 0, 15, 70, 72, 241, 5, 72, 144, 203, 34, 122, 70, 34, 120, 49, 0, 10, 67, 5, 32, 66, 35, 34, 13, 69, 0, 0, 10, 198, 12, 243, 80, 61, 83, 132, 66, 36, 5, 194, 72, 64, 9, 0, 22, 73, 64, 131, 212, 60, 116, 129, 64, 129, 82, 81, 13, 47, 6, 122, 79, 34, 13, 81, 13, 0, 0, 10, 68, 76, 243, 212, 32, 87, 132, 84, 0, 11, 68, 48, 17, 197, 72, 55, 124, 79, 112, 0, 0, 14, 69, 81, 35, 202, 4, 224, 47, 34, 134, 73, 13, 50, 0, 0, 15, 70, 92, 144, 200, 37, 64, 64, 58, 120, 74, 111, 47, 125, 0, 9, 198, 20, 225, 137, 20, 193, 0, 65, 0, 17, 70, 20, 229, 133, 48, 244, 5, 124, 50, 82, 13, 55, 134, 48, 0, 103, 10, 199, 81, 32, 78, 77, 3, 210, 80, 36, 19, 71, 81, 32, 78, 77, 3, 210, 80, 47, 34, 35, 50, 87, 48, 131, 47, 0, 9, 20, 71, 80, 20, 129, 57, 69, 76, 4, 47, 13, 34, 35, 50, 47, 57, 115, 55, 13, 0, 9, 198, 20, 229, 133, 48, 244, 5, 36, 17, 70, 20, 229, 133, 48, 244, 5, 119, 50, 82, 13, 55, 134, 48, 0, 9, 15, 70, 13, 33, 86, 5, 52, 197, 49, 34, 13, 82, 35, 87, 0, 16, 71, 5, 80, 133, 72, 114, 78, 20, 134, 69, 112, 88, 127, 50, 0, 0, 11, 68, 80, 130, 78, 20, 4, 84, 135, 50, 0, 12, 68, 88, 81, 193, 76, 82, 136, 79, 13, 87, 0, 12, 68, 48, 83, 206, 20, 55, 127, 6, 134, 50, 0, 10, 68, 64, 147, 213, 76, 48, 142, 87, 0, 11, 68, 60, 49, 65, 56, 134, 89, 13, 50, 0, 0, 16, 70, 77, 148, 8, 36, 194, 83, 87, 120, 81, 13, 55, 121, 87, 0, 13, 69, 24, 20, 212, 20, 224, 81, 118, 87, 13, 50, 0, 0, 15, 70, 8, 20, 130, 5, 32, 64, 69, 125, 69, 13, 34, 13, 0, 0, 10, 67, 5, 33, 64, 2, 125, 0, 35, 9, 11, 67, 85, 32, 76, 57, 132, 13, 34, 116, 0, 21, 71, 64, 83, 137, 57, 53, 76, 4, 48, 13, 50, 6, 120, 50, 87, 57, 115, 55, 13, 0, 9, 198, 61, 85, 8, 61, 84, 197, 65, 0, 13, 68, 52, 144, 77, 36, 63, 135, 6, 35, 63, 37, 0, 13, 68, 64, 144, 78, 60, 48, 120, 6, 35, 50, 134, 0, 0, 30, 5, 3, 1, 14, 39, 20, 4, 49, 35, 50, 47, 6, 35, 82, 47, 114, 0, 103, 32, 14, 82, 104, 97, 118, 101, 32, 116, 111, 32, 22, 5, 3, 1, 14, 39, 20, 49, 35, 50, 47, 117, 82, 0, 103, 35, 81, 104, 97, 118, 101, 32, 16, 5, 3, 1, 14, 39, 20, 49, 35, 50, 47, 0, 103, 32, 9, 12, 29, 5, 3, 1, 14, 39, 20, 4, 49, 124, 50, 47, 6, 35, 82, 47, 114, 0, 32, 14, 82, 104, 97, 118, 101, 32, 116, 111, 32, 21, 5, 3, 1, 14, 39, 20, 49, 124, 50, 47, 117, 82, 0, 35, 81, 104, 97, 118, 101, 32, 15, 5, 3, 1, 14, 39, 20, 49, 124, 50, 47, 0, 32, 9, 12, 24, 73, 4, 36, 129, 12, 17, 1, 9, 32, 64, 35, 69, 34, 13, 49, 13, 70, 6, 35, 69, 34, 13, 0, 0, 17, 70, 56, 18, 86, 21, 65, 64, 50, 135, 6, 127, 82, 13, 47, 136, 0, 9, 198, 12, 243, 131, 21, 37, 0, 36, 16, 70, 12, 243, 131, 21, 37, 0, 49, 122, 50, 87, 112, 47, 0, 10, 18, 70, 12, 243, 80, 21, 65, 68, 49, 13, 63, 48, 6, 127, 47, 120, 70, 0, 14, 202, 4, 69, 133, 73, 66, 83, 20, 209, 78, 80, 103, 67, 24, 74, 4, 69, 133, 73, 66, 83, 20, 209, 78, 80, 117, 70, 82, 126, 47, 120, 87, 63, 13, 50, 47, 0, 18, 4, 95, 1, 3, 50, 70, 123, 69, 13, 55, 117, 49, 57, 6, 132, 47, 0, 0, 17, 70, 80, 83, 80, 48, 21, 5, 47, 119, 63, 48, 55, 13, 47, 0, 103, 18, 67, 77, 80, 200, 87, 123, 74, 15, 10, 117, 86, 0, 8, 81, 97, 115, 32, 16, 70, 60, 36, 207, 48, 85, 5, 122, 69, 87, 13, 55, 127, 47, 0, 8, 67, 21, 33, 64, 138, 0, 9, 0, 19, 72, 4, 208, 129, 77, 48, 68, 61, 32, 117, 63, 69, 35, 87, 13, 70, 112, 0, 0, 16, 5, 9, 19, 14, 39, 20, 4, 120, 86, 13, 50, 47, 0, 35, 12, 13, 69, 52, 19, 135, 21, 32, 63, 136, 50, 73, 112, 0, 10, 4, 4, 39, 25, 5, 70, 57, 13, 0, 13, 69, 17, 81, 207, 85, 64, 70, 123, 79, 133, 47, 0, 0, 16, 6, 8, 1, 19, 14, 39, 20, 105, 35, 86, 13, 50, 47, 0, 35, 16, 70, 93, 148, 201, 93, 145, 192, 58, 120, 86, 127, 58, 120, 79, 0, 9, 66, 72, 80, 34, 4, 127, 0, 9, 14, 70, 8, 150, 154, 5, 33, 64, 69, 120, 86, 6, 125, 0, 5, 194, 60, 176, 17, 0, 17, 70, 12, 243, 148, 72, 149, 5, 49, 122, 50, 47, 34, 6, 135, 47, 0, 16, 70, 4, 225, 67, 16, 245, 5, 35, 50, 120, 49, 70, 134, 47, 0, 0, 14, 68, 76, 128, 76, 48, 4, 89, 35, 55, 0, 32, 9, 12, 12, 68, 72, 83, 85, 76, 34, 127, 63, 13, 87, 0, 13, 70, 72, 16, 200, 4, 83, 0, 34, 136, 74, 116, 0, 9, 67, 21, 34, 69, 139, 34, 37, 0, 12, 68, 105, 83, 21, 76, 86, 132, 55, 132, 86, 0, 17, 70, 64, 80, 213, 48, 144, 82, 48, 111, 49, 57, 132, 55, 120, 112, 0, 11, 68, 16, 80, 207, 72, 70, 136, 49, 130, 0, 0, 14, 69, 88, 145, 78, 56, 16, 82, 120, 6, 119, 50, 13, 0, 15, 69, 72, 144, 133, 56, 16, 34, 135, 69, 6, 127, 50, 13, 0, 13, 69, 16, 244, 193, 28, 80, 70, 134, 87, 111, 73, 0, 0, 0, 18, 71, 12, 20, 137, 8, 33, 65, 56, 49, 35, 34, 13, 69, 6, 139, 50, 0, 16, 71, 92, 82, 18, 52, 16, 200, 80, 82, 138, 63, 35, 99, 47, 0, 17, 71, 12, 244, 144, 61, 32, 84, 20, 49, 130, 48, 13, 34, 13, 47, 0, 17, 71, 5, 96, 76, 4, 224, 200, 20, 35, 82, 13, 55, 118, 50, 89, 0, 0, 13, 68, 92, 130, 76, 20, 58, 4, 135, 55, 0, 8, 11, 13, 6, 5, 9, 14, 195, 173, 14, 119, 50, 127, 50, 0, 13, 68, 77, 81, 1, 56, 87, 132, 70, 6, 35, 50, 0, 12, 68, 4, 192, 77, 60, 35, 55, 13, 63, 134, 0, 11, 68, 4, 48, 210, 4, 35, 49, 34, 117, 0, 11, 200, 76, 83, 73, 12, 148, 131, 48, 80, 65, 11, 67, 32, 82, 5, 105, 127, 105, 6, 127, 0, 16, 70, 9, 33, 84, 33, 33, 78, 69, 34, 119, 84, 34, 13, 50, 0, 0, 13, 69, 77, 83, 132, 4, 80, 87, 123, 50, 70, 136, 0, 0, 10, 67, 5, 33, 83, 138, 34, 127, 86, 0, 16, 70, 64, 192, 89, 80, 84, 212, 48, 55, 136, 47, 119, 87, 47, 0, 23, 3, 95, 194, 191, 2, 120, 50, 82, 4, 126, 47, 111, 70, 49, 58, 6, 119, 87, 74, 13, 50, 0, 0, 17, 71, 64, 147, 133, 5, 4, 12, 20, 48, 6, 135, 50, 35, 48, 116, 0, 11, 4, 95, 56, 48, 15, 6, 136, 47, 139, 0, 0, 10, 68, 76, 83, 213, 48, 87, 134, 55, 0, 18, 72, 24, 243, 11, 21, 53, 15, 56, 80, 81, 134, 49, 87, 47, 134, 50, 0, 11, 68, 72, 81, 193, 48, 34, 127, 79, 116, 0, 0, 13, 69, 72, 84, 12, 5, 144, 34, 127, 48, 55, 136, 0, 17, 70, 16, 144, 66, 21, 65, 83, 70, 142, 69, 6, 127, 47, 127, 86, 0, 13, 69, 12, 243, 69, 49, 144, 49, 123, 63, 55, 120, 0, 13, 3, 95, 194, 186, 70, 111, 79, 34, 6, 127, 86, 0, 0, 10, 67, 64, 197, 83, 48, 55, 123, 87, 0, 17, 3, 95, 194, 187, 34, 135, 47, 6, 79, 120, 55, 13, 63, 119, 47, 0, 0, 14, 70, 12, 129, 89, 20, 227, 133, 89, 135, 6, 35, 50, 0, 20, 71, 16, 148, 12, 60, 208, 67, 100, 70, 120, 48, 55, 6, 134, 63, 13, 87, 37, 0, 13, 3, 95, 194, 184, 87, 119, 70, 6, 120, 55, 13, 0, 0, 11, 200, 72, 145, 9, 13, 83, 15, 85, 48, 66, 11, 68, 4, 225, 197, 48, 136, 50, 73, 116, 0, 6, 195, 84, 51, 1, 17, 20, 3, 95, 194, 185, 87, 132, 48, 13, 87, 49, 34, 120, 48, 47, 58, 6, 122, 50, 0, 0, 12, 67, 32, 212, 6, 105, 6, 13, 63, 48, 81, 0, 13, 69, 4, 197, 193, 101, 48, 128, 55, 58, 136, 86, 0, 0, 16, 70, 92, 149, 8, 61, 85, 0, 58, 120, 84, 133, 47, 0, 74, 12, 9, 198, 92, 149, 8, 61, 85, 0, 66, 10, 67, 37, 34, 83, 135, 34, 120, 87, 0, 10, 67, 28, 245, 15, 79, 134, 47, 132, 0, 10, 67, 56, 21, 15, 50, 136, 47, 134, 0, 0, 16, 71, 76, 243, 69, 80, 130, 78, 28, 87, 123, 63, 85, 120, 66, 0, 0, 10, 67, 77, 84, 197, 87, 132, 87, 13, 0, 12, 68, 76, 48, 76, 100, 87, 49, 136, 55, 120, 0, 0, 13, 69, 76, 243, 5, 52, 224, 87, 122, 55, 13, 63, 0, 14, 69, 53, 148, 137, 4, 64, 63, 120, 34, 120, 35, 70, 0, 0, 9, 198, 40, 18, 193, 73, 64, 64, 66, 14, 70, 80, 243, 137, 28, 133, 0, 47, 13, 50, 135, 47, 0, 13, 70, 52, 20, 147, 32, 19, 12, 63, 125, 89, 116, 0, 0, 15, 70, 80, 245, 76, 61, 84, 197, 47, 132, 55, 6, 132, 86, 0, 0, 13, 68, 88, 147, 204, 4, 82, 135, 6, 134, 55, 13, 0, 10, 67, 16, 83, 9, 70, 119, 55, 120, 0, 12, 68, 12, 16, 212, 36, 49, 35, 49, 47, 135, 0, 11, 68, 4, 112, 73, 56, 117, 79, 119, 50, 0, 0, 18, 70, 5, 67, 1, 57, 66, 83, 35, 47, 55, 6, 35, 50, 47, 120, 87, 0, 9, 2, 195, 151, 47, 135, 63, 86, 0, 0, 15, 70, 4, 197, 8, 61, 81, 200, 129, 55, 84, 6, 134, 0, 8, 5, 194, 77, 64, 24, 5, 194, 77, 64, 9, 9, 66, 77, 64, 87, 13, 50, 47, 0, 0, 20, 71, 92, 148, 195, 60, 228, 201, 56, 58, 111, 87, 49, 6, 122, 50, 87, 111, 50, 0, 18, 71, 52, 148, 195, 72, 80, 78, 80, 63, 120, 87, 49, 34, 139, 50, 47, 0, 16, 4, 95, 19, 13, 3, 87, 63, 6, 128, 55, 49, 4, 35, 48, 0, 5, 130, 196, 141, 43, 0, 20, 72, 5, 35, 65, 28, 81, 4, 60, 224, 125, 63, 117, 79, 6, 119, 70, 13, 50, 0, 9, 67, 4, 50, 25, 136, 49, 37, 0, 0, 12, 197, 12, 19, 142, 61, 64, 103, 66, 32, 9, 12, 15, 69, 48, 244, 133, 57, 160, 55, 122, 34, 13, 50, 47, 87, 0, 15, 69, 12, 21, 133, 5, 64, 49, 35, 82, 120, 124, 47, 0, 103, 14, 69, 12, 21, 133, 5, 64, 49, 35, 82, 120, 35, 47, 0, 0, 16, 70, 72, 84, 208, 37, 65, 64, 34, 119, 87, 48, 111, 47, 0, 103, 15, 70, 72, 148, 15, 77, 65, 64, 34, 111, 48, 122, 87, 47, 0, 15, 70, 72, 84, 208, 37, 65, 64, 34, 119, 87, 48, 135, 47, 0, 15, 70, 36, 228, 208, 37, 33, 64, 120, 50, 87, 48, 6, 143, 0, 16, 70, 20, 229, 5, 57, 65, 64, 122, 50, 47, 6, 122, 50, 47, 0, 17, 70, 12, 83, 5, 9, 33, 64, 87, 119, 55, 6, 119, 69, 34, 13, 0, 0, 16, 70, 8, 83, 133, 5, 66, 0, 69, 111, 50, 127, 85, 0, 74, 12, 15, 70, 4, 65, 76, 4, 145, 5, 35, 70, 13, 55, 136, 70, 0, 9, 198, 48, 83, 79, 56, 17, 5, 67, 0, 11, 68, 4, 194, 67, 20, 35, 55, 120, 87, 0, 12, 68, 8, 192, 83, 20, 69, 55, 124, 86, 136, 0, 0, 13, 5, 4, 15, 14, 39, 20, 70, 134, 50, 47, 0, 32, 8, 197, 61, 85, 19, 21, 64, 65, 13, 69, 52, 148, 212, 21, 32, 63, 120, 87, 47, 112, 0, 21, 73, 25, 84, 148, 32, 84, 141, 61, 33, 64, 81, 146, 84, 112, 63, 6, 131, 0, 105, 8, 20, 73, 25, 84, 148, 32, 84, 141, 61, 33, 64, 81, 126, 84, 112, 63, 6, 131, 0, 8, 12, 2, 195, 159, 89, 4, 125, 48, 6, 119, 87, 0, 11, 2, 194, 167, 87, 119, 49, 89, 13, 50, 0, 0, 17, 66, 56, 240, 50, 6, 134, 4, 63, 131, 0, 81, 109, 111, 114, 101, 32, 23, 66, 56, 240, 50, 4, 134, 15, 55, 6, 122, 66, 79, 112, 0, 81, 108, 111, 110, 103, 101, 114, 32, 17, 66, 56, 240, 6, 50, 134, 6, 58, 122, 50, 0, 81, 111, 110, 101, 32, 9, 198, 8, 243, 66, 5, 33, 0, 66, 8, 66, 56, 240, 50, 134, 0, 42, 15, 2, 194, 164, 49, 123, 34, 13, 50, 87, 120, 87, 135, 50, 0, 0, 15, 67, 16, 84, 20, 70, 111, 48, 125, 47, 63, 13, 50, 47, 0, 8, 2, 194, 165, 57, 119, 50, 0, 0, 14, 68, 76, 128, 76, 80, 4, 89, 35, 55, 47, 0, 32, 9, 10, 67, 76, 86, 0, 87, 119, 49, 87, 0, 11, 68, 4, 112, 80, 20, 117, 79, 136, 48, 0, 10, 4, 95, 35, 14, 4, 13, 50, 70, 0, 10, 2, 194, 162, 87, 119, 50, 47, 87, 0, 0, 15, 69, 53, 84, 197, 84, 208, 63, 57, 132, 86, 6, 139, 63, 0, 15, 69, 52, 242, 137, 80, 240, 63, 134, 105, 6, 127, 47, 134, 0, 18, 70, 28, 145, 193, 57, 66, 67, 73, 135, 79, 6, 35, 50, 47, 120, 49, 0, 8, 2, 197, 139, 119, 66, 79, 0, 9, 2, 194, 163, 48, 133, 50, 70, 0, 0, 16, 70, 65, 35, 199, 20, 230, 64, 48, 34, 122, 73, 13, 50, 37, 0, 24, 73, 16, 148, 195, 60, 228, 207, 48, 21, 5, 70, 120, 87, 49, 6, 122, 50, 87, 13, 55, 13, 47, 0, 0, 11, 67, 56, 245, 0, 50, 122, 47, 0, 42, 40, 15, 67, 56, 245, 0, 4, 50, 122, 47, 13, 0, 34, 81, 97, 32, 26, 67, 56, 245, 0, 4, 50, 122, 47, 105, 35, 82, 47, 114, 0, 35, 11, 82, 104, 97, 118, 101, 32, 116, 111, 32, 20, 67, 56, 245, 0, 50, 122, 47, 105, 35, 82, 0, 35, 14, 81, 104, 97, 118, 101, 32, 19, 67, 56, 245, 0, 50, 122, 47, 117, 82, 0, 35, 73, 81, 104, 97, 118, 101, 32, 13, 67, 56, 245, 0, 4, 50, 122, 47, 0, 40, 9, 11, 10, 199, 52, 19, 136, 5, 69, 5, 56, 66, 17, 70, 64, 150, 154, 21, 34, 65, 48, 127, 47, 87, 13, 34, 6, 139, 0, 13, 70, 64, 128, 82, 4, 242, 0, 81, 138, 34, 134, 0, 9, 67, 56, 245, 0, 50, 134, 47, 0, 18, 71, 16, 84, 208, 21, 32, 84, 20, 70, 119, 87, 48, 13, 34, 13, 47, 0, 0, 18, 72, 12, 243, 147, 12, 145, 78, 12, 80, 49, 122, 50, 89, 13, 50, 87, 0, 13, 2, 194, 174, 34, 119, 73, 120, 87, 47, 112, 70, 0, 0, 12, 67, 61, 97, 82, 134, 82, 112, 0, 72, 12, 9, 19, 70, 32, 243, 132, 85, 32, 83, 105, 122, 50, 70, 6, 57, 141, 34, 13, 87, 0, 13, 69, 28, 83, 143, 52, 80, 73, 127, 50, 134, 63, 0, 12, 69, 12, 243, 77, 36, 80, 49, 122, 63, 120, 0, 5, 130, 195, 167, 43, 0, 13, 66, 77, 80, 87, 132, 87, 13, 0, 81, 115, 101, 32, 9, 198, 65, 35, 195, 20, 81, 0, 9, 9, 198, 65, 35, 195, 20, 81, 0, 36, 16, 70, 65, 35, 195, 20, 81, 0, 48, 34, 134, 87, 127, 70, 0, 10, 12, 2, 194, 172, 50, 122, 47, 23, 87, 135, 50, 0, 5, 130, 195, 164, 43, 0, 10, 199, 76, 84, 85, 21, 53, 5, 72, 66, 20, 71, 29, 80, 67, 4, 211, 204, 20, 79, 58, 124, 49, 117, 63, 6, 134, 55, 127, 0, 22, 73, 12, 131, 204, 21, 53, 5, 72, 243, 0, 49, 13, 55, 119, 87, 47, 13, 34, 122, 55, 0, 16, 71, 12, 131, 195, 60, 192, 84, 20, 74, 122, 49, 55, 13, 47, 0, 0, 15, 68, 92, 130, 67, 32, 4, 58, 120, 74, 0, 8, 12, 9, 32, 23, 73, 52, 144, 200, 20, 192, 78, 28, 83, 15, 63, 135, 49, 116, 6, 35, 50, 73, 13, 55, 134, 0, 11, 68, 56, 145, 197, 48, 50, 135, 73, 116, 0, 11, 68, 40, 19, 73, 20, 73, 136, 63, 37, 0, 11, 68, 12, 80, 201, 48, 87, 119, 87, 116, 0, 12, 68, 56, 18, 197, 16, 50, 136, 49, 121, 70, 0, 15, 70, 52, 19, 149, 21, 97, 82, 63, 13, 50, 132, 82, 112, 0, 15, 70, 52, 19, 133, 85, 97, 82, 63, 13, 50, 132, 82, 112, 0, 11, 68, 48, 83, 77, 20, 55, 119, 63, 37, 0, 11, 68, 8, 17, 197, 48, 69, 136, 79, 116, 0, 0, 13, 69, 64, 148, 195, 21, 48, 48, 135, 87, 127, 86, 0, 0, 14, 4, 95, 18, 5, 22, 34, 120, 82, 6, 126, 87, 70, 0, 6, 130, 195, 160, 43, 14, 0, 12, 2, 194, 169, 49, 122, 48, 120, 34, 135, 47, 0, 0, 10, 68, 4, 113, 201, 20, 35, 79, 37, 0, 11, 68, 76, 178, 69, 16, 87, 49, 127, 70, 0, 22, 72, 65, 33, 70, 21, 32, 66, 49, 144, 48, 34, 119, 81, 14, 34, 13, 69, 55, 120, 0, 32, 11, 68, 16, 80, 207, 100, 70, 127, 49, 137, 0, 13, 2, 194, 182, 48, 35, 34, 13, 79, 34, 35, 81, 0, 0, 15, 69, 77, 64, 84, 85, 48, 87, 47, 35, 47, 13, 87, 0, 103, 13, 69, 52, 243, 132, 5, 144, 63, 123, 50, 70, 136, 0, 17, 70, 16, 85, 18, 37, 69, 83, 70, 111, 47, 34, 135, 47, 13, 87, 0, 5, 130, 197, 159, 43, 5, 130, 195, 175, 43, 0, 15, 66, 60, 224, 2, 122, 50, 84, 113, 0, 81, 116, 104, 101, 32, 9, 66, 60, 224, 4, 122, 50, 0, 12, 0, 16, 70, 60, 36, 212, 4, 51, 5, 122, 69, 87, 47, 13, 49, 116, 0, 9, 67, 48, 80, 68, 55, 127, 70, 0, 6, 195, 4, 32, 192, 17, 10, 2, 194, 181, 63, 135, 49, 34, 134, 0, 0, 6, 195, 60, 224, 197, 8, 12, 68, 52, 81, 193, 56, 63, 119, 79, 13, 50, 0, 11, 68, 32, 82, 68, 36, 105, 135, 70, 37, 0, 10, 68, 4, 242, 70, 20, 127, 81, 13, 0, 12, 68, 92, 131, 201, 76, 105, 132, 6, 120, 86, 0, 12, 68, 72, 21, 9, 60, 34, 136, 89, 120, 134, 0, 11, 68, 52, 144, 79, 92, 63, 127, 6, 133, 0, 21, 72, 4, 229, 9, 80, 129, 83, 21, 48, 35, 50, 47, 6, 120, 85, 13, 87, 127, 86, 0, 12, 68, 4, 67, 194, 20, 117, 70, 134, 69, 37, 0, 5, 130, 195, 170, 43, 0, 13, 69, 56, 117, 89, 20, 224, 50, 132, 57, 119, 50, 0, 5, 130, 195, 171, 43, 0, 14, 70, 25, 80, 200, 76, 144, 64, 81, 57, 132, 89, 13, 0, 12, 2, 194, 176, 70, 120, 79, 34, 6, 127, 86, 0, 0, 16, 70, 16, 162, 66, 61, 85, 9, 73, 120, 69, 6, 132, 47, 37, 0, 13, 5, 3, 39, 13, 15, 14, 49, 13, 63, 122, 50, 0, 9, 67, 4, 176, 64, 35, 49, 117, 0, 17, 71, 4, 69, 133, 73, 66, 90, 20, 35, 70, 82, 112, 47, 135, 86, 0, 16, 2, 194, 177, 48, 55, 123, 87, 130, 63, 6, 135, 50, 13, 87, 0, 5, 130, 195, 169, 43, 0, 13, 68, 52, 245, 9, 24, 63, 134, 47, 6, 127, 81, 0, 13, 2, 194, 190, 85, 34, 127, 49, 58, 130, 47, 112, 0, 5, 130, 195, 182, 43, 0, 14, 69, 52, 148, 212, 20, 64, 63, 120, 87, 47, 121, 70, 0, 6, 195, 85, 35, 0, 17, 13, 2, 195, 183, 70, 111, 82, 6, 135, 70, 69, 135, 0, 0, 15, 70, 12, 19, 80, 8, 83, 12, 49, 35, 63, 69, 13, 55, 0, 17, 70, 81, 83, 137, 76, 144, 64, 47, 132, 50, 6, 127, 88, 13, 0, 103, 11, 2, 194, 188, 117, 49, 58, 130, 47, 112, 0, 0, 15, 70, 48, 21, 82, 20, 224, 197, 55, 122, 34, 13, 50, 87, 0, 17, 70, 76, 85, 133, 72, 83, 25, 87, 111, 82, 6, 140, 55, 120, 0, 32, 16, 70, 56, 243, 147, 20, 228, 197, 50, 122, 50, 87, 13, 50, 87, 0, 9, 2, 194, 189, 117, 105, 124, 81, 0, 0, 16, 70, 52, 244, 143, 12, 48, 78, 63, 13, 34, 122, 49, 13, 50, 0, 11, 68, 52, 144, 79, 84, 63, 127, 6, 133, 0, 18, 4, 95, 18, 6, 24, 34, 6, 119, 47, 34, 13, 81, 55, 119, 49, 87, 0, 14, 4, 95, 3, 5, 4, 87, 13, 70, 6, 120, 55, 117, 0, 0, 10, 67, 44, 240, 78, 49, 134, 124, 50, 0, 14, 69, 16, 80, 197, 57, 64, 70, 127, 87, 13, 50, 47, 0, 14, 69, 8, 19, 12, 21, 64, 69, 35, 55, 6, 136, 0, 103, 12, 69, 8, 19, 12, 21, 64, 69, 35, 55, 136, 0, 0, 15, 70, 100, 241, 200, 85, 37, 0, 57, 134, 79, 112, 47, 0, 103, 14, 70, 100, 241, 200, 85, 37, 0, 57, 122, 79, 112, 47, 0, 14, 70, 52, 20, 145, 84, 81, 64, 63, 125, 49, 6, 127, 0, 7, 2, 195, 176, 119, 84, 0, 0, 10, 67, 12, 241, 68, 49, 134, 119, 70, 0, 14, 4, 95, 12, 9, 7, 55, 4, 120, 79, 117, 74, 13, 0, 5, 130, 195, 177, 43, 5, 130, 197, 161, 43, 0, 19, 72, 72, 84, 212, 5, 84, 129, 57, 64, 34, 119, 87, 47, 34, 122, 50, 47, 0, 8, 2, 195, 190, 85, 130, 50, 0, 0, 12, 69, 72, 85, 84, 21, 32, 34, 137, 47, 112, 0, 22, 67, 80, 83, 0, 47, 4, 119, 55, 15, 117, 82, 6, 127, 82, 0, 81, 97, 118, 105, 118, 32, 11, 67, 56, 18, 70, 50, 135, 6, 127, 81, 0, 14, 69, 12, 243, 66, 5, 64, 49, 122, 63, 69, 35, 47, 0, 0, 16, 6, 19, 8, 1, 14, 39, 20, 4, 89, 124, 50, 47, 0, 32, 12, 9, 67, 93, 84, 211, 58, 115, 87, 0, 17, 70, 65, 35, 196, 84, 49, 64, 48, 34, 122, 70, 57, 132, 87, 0, 37, 13, 70, 12, 128, 84, 20, 21, 64, 89, 35, 47, 134, 0, 5, 130, 195, 188, 43, 0, 14, 70, 80, 132, 143, 84, 114, 0, 85, 34, 132, 0, 72, 12, 0, 11, 68, 4, 114, 76, 20, 35, 73, 116, 0, 103, 10, 67, 32, 211, 77, 105, 6, 13, 63, 0, 10, 68, 24, 194, 69, 72, 81, 55, 143, 0, 0, 15, 69, 56, 85, 129, 16, 16, 50, 111, 82, 35, 70, 13, 0, 103, 14, 69, 56, 85, 129, 16, 16, 50, 111, 82, 124, 70, 13, 0, 21, 73, 72, 83, 129, 37, 52, 193, 56, 49, 64, 34, 119, 50, 13, 87, 122, 50, 87, 0, 103, 12, 69, 49, 144, 200, 20, 80, 55, 127, 74, 127, 0, 14, 69, 24, 18, 137, 80, 16, 81, 117, 105, 127, 47, 13, 0, 7, 2, 202, 131, 119, 89, 0, 0, 9, 198, 77, 84, 208, 20, 53, 0, 36, 17, 70, 77, 84, 208, 20, 53, 0, 87, 123, 87, 48, 119, 49, 47, 0, 10, 15, 70, 24, 192, 67, 12, 145, 0, 81, 55, 35, 87, 120, 70, 0, 9, 67, 8, 144, 83, 69, 142, 87, 0, 0, 10, 67, 65, 52, 212, 48, 87, 87, 47, 0, 10, 67, 24, 144, 84, 81, 127, 13, 47, 0, 0, 17, 70, 85, 65, 78, 76, 147, 0, 57, 132, 47, 6, 119, 50, 87, 116, 0, 10, 68, 72, 82, 71, 56, 34, 136, 50, 0, 15, 70, 12, 20, 9, 80, 243, 0, 49, 35, 48, 120, 47, 116, 0, 12, 68, 4, 194, 66, 36, 35, 55, 13, 69, 135, 0, 0, 14, 69, 8, 81, 143, 72, 80, 69, 120, 81, 131, 0, 74, 12, 13, 69, 81, 34, 67, 36, 16, 47, 34, 120, 89, 13, 0, 13, 69, 48, 83, 143, 72, 80, 55, 119, 50, 6, 131, 0, 13, 69, 29, 32, 72, 4, 208, 79, 34, 136, 13, 63, 0, 11, 69, 4, 242, 70, 24, 80, 127, 81, 13, 0, 8, 197, 4, 226, 193, 72, 16, 65, 16, 70, 64, 19, 131, 72, 80, 83, 48, 35, 50, 49, 34, 139, 87, 0, 14, 69, 64, 17, 76, 48, 16, 48, 135, 6, 119, 55, 13, 0, 6, 195, 4, 178, 78, 66, 9, 67, 4, 49, 82, 136, 87, 112, 0, 0, 6, 194, 85, 48, 17, 42, 9, 66, 85, 48, 4, 123, 86, 0, 9, 9, 198, 12, 243, 132, 84, 53, 0, 36, 16, 70, 12, 243, 132, 84, 53, 0, 49, 122, 50, 70, 123, 49, 47, 0, 12, 2, 201, 148, 134, 48, 13, 50, 6, 128, 10, 0, 0, 18, 71, 77, 67, 210, 101, 65, 76, 48, 87, 47, 128, 34, 120, 47, 119, 55, 0, 18, 71, 65, 54, 67, 32, 244, 201, 76, 87, 135, 49, 6, 134, 87, 120, 87, 0, 18, 71, 36, 229, 133, 57, 67, 210, 100, 120, 50, 82, 13, 50, 47, 34, 120, 0, 18, 71, 20, 116, 133, 28, 147, 213, 76, 120, 79, 34, 6, 127, 73, 13, 87, 0, 13, 4, 95, 57, 48, 15, 50, 6, 135, 50, 47, 139, 0, 0, 9, 67, 37, 51, 1, 135, 55, 13, 0, 12, 68, 4, 131, 69, 16, 35, 99, 63, 119, 70, 0, 11, 68, 28, 147, 77, 20, 79, 120, 63, 37, 0, 0, 11, 69, 80, 129, 73, 73, 48, 84, 138, 86, 0, 16, 70, 76, 144, 133, 48, 149, 83, 87, 111, 69, 136, 55, 139, 87, 0, 15, 69, 56, 240, 143, 17, 144, 6, 50, 134, 69, 122, 70, 37, 0, 12, 69, 52, 80, 68, 61, 112, 63, 119, 70, 134, 0, 15, 69, 21, 131, 196, 85, 48, 119, 49, 87, 13, 70, 13, 87, 0, 13, 69, 12, 20, 133, 77, 48, 49, 13, 34, 119, 87, 0, 14, 69, 12, 19, 150, 5, 48, 49, 35, 50, 82, 13, 87, 0, 0, 12, 67, 28, 241, 83, 2, 79, 134, 86, 0, 12, 9, 8, 2, 196, 184, 49, 34, 124, 0, 11, 4, 95, 2, 1, 18, 10, 69, 6, 125, 0, 0, 15, 70, 52, 16, 203, 20, 227, 129, 63, 13, 49, 119, 50, 13, 0, 18, 70, 60, 179, 1, 32, 243, 65, 134, 49, 55, 117, 105, 6, 134, 63, 13, 0, 9, 198, 61, 97, 82, 80, 147, 69, 65, 9, 67, 32, 211, 64, 105, 13, 63, 0, 0, 18, 67, 76, 243, 69, 87, 123, 63, 58, 122, 50, 0, 106, 81, 111, 110, 101, 32, 17, 67, 76, 243, 69, 87, 123, 63, 58, 122, 50, 0, 81, 111, 110, 101, 32, 13, 67, 76, 243, 69, 4, 87, 123, 63, 0, 34, 13, 9, 11, 68, 88, 81, 199, 100, 82, 119, 73, 120, 0, 10, 2, 204, 134, 69, 34, 119, 82, 10, 0, 5, 130, 197, 190, 43, 0, 11, 67, 8, 17, 90, 69, 135, 6, 119, 86, 0, 17, 70, 17, 83, 70, 72, 145, 83, 70, 123, 63, 81, 34, 6, 127, 87, 0, 12, 69, 60, 97, 133, 73, 48, 122, 81, 112, 86, 0, 15, 69, 32, 144, 84, 85, 48, 105, 135, 6, 136, 47, 13, 87, 0, 14, 69, 16, 80, 146, 37, 48, 70, 13, 69, 34, 127, 0, 103, 13, 69, 16, 80, 146, 37, 48, 70, 119, 69, 34, 127, 0, 0, 10, 67, 16, 83, 79, 70, 119, 63, 134, 0, 12, 2, 204, 132, 63, 35, 49, 34, 122, 50, 10, 0, 20, 2, 203, 140, 87, 6, 119, 49, 13, 50, 70, 34, 120, 87, 47, 34, 4, 119, 87, 0, 15, 2, 202, 148, 79, 55, 6, 122, 19, 116, 87, 47, 122, 48, 0, 0, 0, 10, 68, 52, 17, 86, 20, 63, 136, 82, 0, 10, 67, 49, 84, 5, 55, 132, 48, 136, 0, 11, 68, 52, 149, 18, 20, 63, 135, 47, 112, 0, 16, 2, 204, 130, 87, 126, 49, 123, 63, 81, 55, 119, 49, 87, 10, 0, 7, 2, 202, 146, 119, 88, 0, 0, 8, 197, 12, 243, 146, 4, 64, 65, 13, 69, 76, 19, 15, 60, 224, 87, 117, 55, 132, 50, 0, 12, 69, 64, 20, 137, 4, 128, 48, 13, 34, 142, 0, 11, 2, 204, 131, 47, 120, 55, 70, 13, 10, 0, 13, 2, 201, 155, 134, 48, 13, 50, 6, 119, 12, 10, 0, 0, 16, 8, 19, 9, 15, 2, 8, 195, 161, 14, 89, 13, 82, 128, 50, 0, 17, 70, 56, 144, 207, 76, 144, 64, 50, 120, 49, 13, 87, 6, 127, 13, 0, 10, 2, 204, 128, 79, 34, 124, 82, 10, 0, 10, 2, 203, 136, 87, 47, 34, 119, 87, 0, 0, 8, 67, 21, 36, 128, 138, 0, 103, 16, 70, 12, 19, 130, 21, 36, 129, 49, 35, 50, 69, 13, 34, 13, 0, 15, 71, 52, 244, 133, 12, 19, 66, 20, 63, 131, 49, 13, 63, 0, 7, 67, 21, 36, 128, 126, 0, 19, 71, 4, 229, 9, 64, 21, 8, 100, 35, 50, 47, 6, 120, 48, 13, 85, 37, 0, 6, 195, 57, 148, 4, 17, 11, 2, 204, 129, 117, 49, 57, 132, 47, 10, 0, 8, 2, 201, 153, 89, 58, 124, 0, 0, 22, 72, 72, 84, 21, 80, 21, 9, 60, 224, 34, 119, 48, 57, 132, 47, 6, 136, 89, 13, 50, 0, 17, 7, 16, 9, 195, 177, 1, 20, 1, 48, 127, 65, 6, 35, 47, 117, 0, 12, 68, 64, 84, 149, 76, 48, 13, 34, 132, 86, 0, 11, 200, 32, 244, 137, 104, 243, 148, 4, 192, 67, 11, 200, 16, 148, 195, 61, 83, 148, 20, 64, 66, 11, 68, 4, 194, 65, 76, 136, 55, 139, 87, 0, 0, 14, 69, 76, 18, 71, 60, 224, 87, 135, 79, 6, 122, 50, 0, 14, 69, 92, 147, 132, 20, 64, 58, 120, 50, 70, 121, 70, 0, 12, 67, 28, 242, 78, 4, 79, 134, 111, 50, 0, 9, 0, 12, 2, 201, 164, 34, 35, 63, 87, 105, 130, 50, 0, 0, 27, 75, 72, 80, 207, 52, 209, 78, 16, 21, 9, 60, 224, 34, 119, 49, 13, 63, 119, 50, 70, 6, 136, 89, 13, 50, 0, 0, 15, 68, 8, 82, 78, 28, 4, 69, 127, 120, 66, 0, 35, 9, 12, 12, 68, 8, 16, 213, 64, 69, 136, 49, 13, 48, 0, 10, 68, 28, 81, 83, 20, 79, 127, 87, 0, 12, 68, 20, 66, 67, 80, 127, 70, 120, 49, 47, 0, 12, 68, 12, 243, 66, 60, 49, 122, 63, 69, 134, 0, 11, 68, 4, 114, 78, 28, 136, 73, 120, 66, 0, 10, 2, 204, 138, 34, 120, 66, 79, 10, 0, 0, 14, 69, 80, 16, 140, 21, 64, 47, 35, 69, 55, 13, 47, 0, 14, 69, 4, 195, 79, 77, 64, 128, 55, 63, 134, 87, 47, 0, 14, 69, 4, 35, 5, 77, 64, 136, 69, 55, 13, 87, 47, 0, 0, 15, 70, 77, 65, 87, 5, 37, 0, 87, 47, 132, 112, 47, 0, 103, 15, 70, 77, 65, 87, 5, 37, 0, 87, 47, 57, 132, 112, 47, 0, 15, 70, 12, 19, 132, 4, 49, 64, 49, 35, 50, 70, 120, 87, 0, 16, 70, 72, 81, 133, 72, 81, 64, 34, 119, 81, 13, 34, 6, 127, 0, 14, 70, 72, 20, 16, 61, 37, 0, 34, 35, 48, 6, 131, 0, 12, 2, 204, 136, 70, 143, 34, 127, 87, 111, 87, 0, 13, 2, 203, 144, 55, 119, 66, 85, 13, 50, 70, 10, 0, 0, 0, 12, 68, 48, 80, 78, 56, 55, 127, 6, 35, 50, 0, 22, 72, 84, 226, 78, 80, 84, 133, 77, 64, 123, 50, 6, 120, 50, 47, 13, 34, 13, 87, 47, 0, 13, 68, 72, 82, 197, 100, 34, 4, 127, 49, 6, 127, 0, 22, 72, 72, 18, 78, 24, 244, 133, 77, 64, 34, 6, 136, 50, 81, 4, 122, 34, 111, 87, 47, 0, 0, 13, 69, 100, 84, 211, 37, 32, 57, 119, 87, 87, 126, 0, 11, 69, 65, 32, 89, 21, 32, 48, 34, 138, 0, 8, 67, 64, 80, 82, 48, 138, 0, 8, 197, 61, 85, 12, 21, 64, 65, 13, 69, 12, 128, 82, 37, 64, 74, 35, 34, 120, 47, 0, 12, 69, 12, 17, 83, 5, 32, 87, 127, 86, 112, 0, 8, 2, 202, 167, 74, 119, 89, 0, 0, 7, 66, 76, 144, 87, 127, 0, 14, 70, 29, 35, 213, 64, 145, 64, 79, 34, 132, 48, 37, 0, 15, 70, 5, 50, 193, 56, 49, 64, 117, 87, 49, 118, 50, 87, 0, 8, 2, 202, 164, 73, 119, 88, 0, 0, 0, 12, 68, 40, 16, 207, 8, 73, 136, 49, 13, 69, 0, 12, 68, 8, 19, 66, 36, 69, 35, 63, 69, 127, 0, 11, 68, 76, 178, 69, 76, 87, 49, 135, 86, 0, 11, 68, 4, 208, 83, 76, 117, 63, 35, 87, 0, 0, 15, 69, 80, 243, 65, 80, 240, 47, 13, 63, 136, 47, 134, 0, 103, 18, 67, 80, 80, 82, 47, 4, 138, 15, 6, 122, 81, 0, 81, 111, 102, 102, 32, 9, 67, 80, 80, 82, 47, 138, 0, 36, 9, 67, 80, 80, 82, 47, 140, 0, 10, 13, 69, 76, 19, 9, 56, 80, 87, 136, 55, 135, 50, 0, 8, 197, 61, 85, 1, 28, 80, 65, 12, 69, 28, 19, 15, 72, 80, 79, 117, 55, 131, 0, 0, 15, 70, 64, 198, 77, 61, 85, 8, 48, 55, 120, 63, 13, 85, 0, 12, 67, 96, 208, 83, 119, 49, 87, 63, 117, 87, 0, 10, 198, 21, 133, 18, 4, 53, 0, 66, 36, 10, 198, 21, 133, 18, 4, 53, 0, 65, 9, 10, 198, 21, 133, 18, 4, 53, 0, 65, 10, 0, 20, 71, 65, 34, 77, 5, 97, 82, 4, 48, 34, 127, 63, 13, 82, 6, 138, 34, 13, 0, 18, 71, 12, 145, 193, 72, 85, 20, 20, 87, 120, 79, 13, 6, 34, 119, 47, 0, 0, 11, 68, 12, 130, 76, 20, 74, 120, 55, 37, 0, 12, 68, 76, 83, 69, 56, 87, 127, 63, 13, 50, 0, 17, 70, 52, 20, 129, 80, 131, 206, 63, 35, 34, 13, 85, 122, 50, 0, 103, 12, 68, 24, 240, 213, 76, 81, 134, 49, 13, 87, 0, 11, 68, 16, 147, 196, 20, 70, 135, 134, 70, 0, 11, 68, 4, 81, 201, 76, 127, 73, 120, 87, 0, 18, 2, 204, 158, 117, 48, 34, 6, 122, 49, 87, 120, 63, 13, 50, 47, 10, 0, 0, 12, 69, 12, 243, 142, 36, 80, 49, 122, 50, 37, 0, 8, 197, 76, 85, 20, 20, 80, 66, 14, 69, 72, 81, 15, 56, 80, 34, 127, 70, 6, 123, 50, 0, 13, 69, 72, 21, 137, 56, 80, 34, 13, 82, 127, 50, 0, 17, 70, 52, 244, 209, 84, 149, 15, 63, 13, 87, 49, 6, 127, 47, 134, 0, 0, 15, 70, 81, 84, 142, 44, 86, 64, 47, 146, 50, 49, 127, 0, 105, 14, 70, 81, 84, 142, 44, 86, 64, 47, 126, 50, 49, 127, 0, 0, 16, 70, 64, 21, 18, 36, 50, 65, 48, 117, 47, 34, 120, 89, 13, 0, 18, 71, 12, 20, 211, 4, 225, 18, 4, 49, 13, 87, 35, 50, 70, 34, 13, 0, 19, 71, 72, 84, 21, 80, 16, 140, 20, 34, 119, 48, 57, 132, 47, 13, 69, 116, 0, 10, 199, 12, 244, 143, 48, 192, 82, 100, 66, 6, 2, 95, 1, 136, 0, 0, 15, 70, 12, 245, 207, 72, 177, 82, 49, 134, 58, 126, 49, 112, 0, 9, 198, 12, 21, 129, 48, 145, 82, 67, 7, 2, 201, 178, 65, 119, 0, 0, 14, 69, 64, 145, 211, 81, 144, 48, 120, 79, 87, 47, 135, 0, 15, 69, 28, 19, 1, 97, 144, 79, 35, 55, 117, 49, 87, 37, 0, 14, 69, 13, 34, 83, 37, 48, 49, 34, 135, 87, 120, 87, 0, 0, 10, 67, 16, 85, 83, 70, 136, 115, 87, 0, 0, 15, 70, 76, 192, 86, 37, 50, 0, 87, 55, 136, 82, 120, 89, 0, 14, 70, 44, 224, 86, 37, 50, 0, 50, 136, 82, 120, 89, 0, 0, 11, 200, 72, 81, 193, 72, 67, 5, 77, 48, 8, 11, 68, 76, 21, 143, 100, 87, 117, 82, 137, 0, 17, 70, 36, 229, 5, 72, 210, 78, 120, 50, 47, 6, 126, 63, 120, 50, 0, 11, 68, 12, 240, 207, 4, 49, 134, 49, 134, 0, 0, 17, 70, 16, 19, 65, 76, 53, 83, 70, 117, 63, 35, 87, 49, 13, 87, 0, 9, 198, 61, 85, 2, 72, 80, 75, 65, 13, 69, 16, 148, 200, 21, 48, 70, 120, 89, 121, 86, 0, 14, 69, 4, 194, 66, 37, 48, 35, 55, 13, 69, 135, 86, 0, 11, 2, 201, 190, 10, 6, 125, 47, 35, 48, 0, 0, 10, 2, 204, 165, 34, 120, 66, 79, 10, 0, 0, 5, 194, 80, 128, 9, 6, 66, 80, 128, 85, 0, 0, 8, 67, 5, 32, 192, 125, 49, 0, 6, 195, 37, 32, 192, 17, 0, 10, 68, 44, 131, 69, 72, 49, 63, 140, 0, 12, 2, 202, 178, 63, 4, 122, 70, 73, 6, 136, 0, 0, 14, 69, 16, 80, 204, 4, 224, 70, 119, 49, 55, 117, 50, 0, 14, 69, 4, 194, 83, 60, 224, 35, 55, 120, 87, 13, 50, 0, 17, 70, 4, 117, 73, 48, 84, 129, 35, 79, 127, 55, 6, 138, 34, 13, 0, 14, 69, 77, 83, 148, 4, 224, 87, 123, 50, 47, 35, 50, 0, 12, 69, 61, 36, 8, 4, 224, 130, 81, 13, 50, 0, 0, 15, 70, 88, 19, 133, 77, 48, 64, 82, 117, 50, 119, 87, 13, 0, 13, 70, 73, 84, 211, 20, 195, 0, 34, 123, 87, 116, 0, 15, 70, 80, 147, 73, 16, 84, 128, 47, 120, 63, 120, 70, 112, 0, 15, 2, 202, 176, 35, 87, 48, 111, 34, 136, 47, 111, 70, 10, 0, 0, 18, 71, 20, 194, 83, 4, 33, 84, 32, 111, 55, 120, 86, 13, 69, 13, 85, 0, 19, 71, 48, 19, 132, 61, 115, 133, 72, 55, 6, 35, 50, 70, 4, 134, 50, 112, 0, 18, 67, 24, 21, 88, 81, 6, 134, 15, 48, 6, 124, 0, 81, 112, 97, 115, 32, 6, 195, 85, 48, 64, 17, 17, 2, 204, 175, 50, 4, 122, 50, 87, 111, 55, 6, 35, 69, 111, 49, 0, 7, 2, 95, 19, 119, 87, 0, 0, 10, 68, 21, 83, 5, 72, 137, 55, 112, 0, 12, 68, 17, 147, 1, 56, 70, 120, 55, 13, 50, 0, 11, 68, 80, 147, 79, 72, 47, 127, 63, 131, 0, 20, 68, 92, 245, 78, 16, 58, 4, 133, 50, 70, 15, 6, 123, 48, 0, 81, 117, 112, 32, 23, 68, 92, 245, 78, 16, 58, 4, 133, 50, 70, 15, 6, 70, 133, 50, 0, 81, 100, 111, 119, 110, 32, 12, 68, 92, 245, 78, 16, 58, 133, 50, 70, 0, 38, 11, 68, 92, 245, 78, 16, 58, 132, 50, 70, 0, 11, 68, 52, 80, 78, 80, 63, 119, 50, 47, 0, 11, 68, 48, 80, 78, 80, 55, 119, 50, 47, 0, 12, 68, 5, 67, 1, 76, 35, 47, 55, 13, 87, 0, 0, 13, 69, 32, 19, 73, 76, 128, 105, 136, 63, 120, 89, 0, 14, 69, 8, 133, 84, 4, 224, 69, 132, 47, 6, 35, 50, 0, 8, 197, 88, 147, 204, 36, 224, 66, 13, 69, 33, 86, 154, 4, 128, 105, 13, 86, 6, 124, 0, 0, 10, 67, 76, 241, 129, 87, 134, 81, 13, 0, 21, 67, 93, 114, 73, 70, 123, 69, 116, 57, 132, 70, 123, 69, 116, 57, 132, 47, 6, 132, 0, 13, 2, 202, 188, 111, 73, 119, 49, 47, 111, 82, 10, 0, 0, 8, 67, 5, 32, 200, 125, 74, 0, 0, 11, 2, 204, 170, 70, 119, 50, 47, 116, 10, 0, 0, 12, 69, 16, 83, 137, 21, 32, 70, 111, 50, 143, 0, 0, 14, 70, 24, 147, 133, 77, 49, 64, 81, 111, 50, 119, 87, 0, 0, 10, 67, 85, 49, 64, 57, 132, 86, 0, 36, 9, 67, 85, 49, 64, 57, 132, 87, 0, 10, 199, 32, 80, 68, 24, 148, 147, 80, 66, 0, 11, 68, 20, 194, 83, 20, 111, 55, 127, 86, 0, 7, 196, 36, 64, 72, 60, 65, 9, 198, 52, 18, 78, 80, 18, 78, 66, 7, 196, 36, 229, 18, 60, 65, 12, 68, 12, 193, 82, 44, 49, 55, 125, 49, 0, 135, 0, 14, 69, 60, 49, 76, 61, 64, 122, 87, 13, 55, 122, 47, 0, 9, 197, 36, 228, 213, 49, 64, 65, 10, 8, 197, 36, 228, 213, 49, 64, 66, 23, 73, 36, 212, 18, 20, 115, 129, 8, 193, 64, 120, 63, 48, 34, 6, 119, 79, 50, 13, 69, 116, 0, 14, 69, 4, 97, 140, 85, 128, 117, 81, 55, 123, 49, 87, 0, 0, 13, 70, 76, 19, 201, 73, 49, 64, 87, 139, 89, 13, 0, 14, 70, 12, 193, 65, 57, 49, 64, 49, 55, 119, 50, 86, 0, 0, 18, 71, 21, 52, 9, 60, 224, 71, 20, 119, 87, 48, 120, 13, 50, 124, 88, 0, 6, 195, 5, 48, 80, 17, 0, 11, 68, 25, 147, 4, 20, 81, 135, 55, 70, 0, 10, 67, 88, 86, 0, 82, 119, 49, 87, 0, 0, 13, 69, 29, 32, 69, 52, 80, 79, 34, 136, 13, 63, 0, 13, 69, 5, 33, 217, 48, 80, 125, 79, 6, 135, 55, 0, 13, 69, 52, 244, 129, 48, 80, 63, 13, 34, 35, 55, 0, 8, 67, 37, 35, 206, 143, 50, 0, 0, 11, 67, 16, 82, 129, 70, 136, 88, 124, 0, 9, 0, 11, 67, 72, 21, 76, 34, 133, 6, 132, 55, 0, 14, 70, 32, 20, 151, 36, 50, 0, 105, 35, 34, 120, 73, 0, 10, 199, 64, 149, 21, 37, 64, 82, 100, 66, 10, 199, 28, 243, 196, 56, 145, 200, 80, 66, 0, 18, 70, 52, 242, 1, 52, 81, 0, 109, 111, 104, 97, 109, 109, 97, 100, 0, 29, 12, 68, 12, 129, 82, 36, 89, 138, 34, 6, 127, 0, 19, 72, 64, 130, 76, 37, 53, 9, 56, 80, 81, 120, 55, 111, 87, 47, 135, 50, 0, 11, 200, 52, 243, 25, 8, 65, 78, 84, 208, 66, 11, 68, 48, 80, 80, 80, 55, 119, 48, 47, 0, 11, 200, 36, 195, 9, 80, 84, 129, 80, 80, 21, 11, 68, 28, 83, 196, 20, 73, 127, 134, 70, 0, 12, 68, 16, 80, 210, 100, 70, 111, 49, 34, 135, 0, 21, 72, 12, 243, 210, 16, 147, 129, 80, 80, 49, 134, 6, 128, 70, 111, 50, 136, 47, 0, 36, 10, 2, 95, 34, 49, 58, 134, 47, 87, 0, 0, 8, 197, 101, 99, 206, 56, 80, 66, 12, 69, 64, 131, 197, 8, 80, 81, 127, 69, 127, 0, 15, 70, 4, 225, 204, 21, 49, 89, 35, 66, 79, 116, 87, 37, 0, 14, 69, 76, 145, 78, 56, 16, 87, 127, 6, 119, 50, 13, 0, 11, 69, 69, 82, 67, 32, 80, 49, 127, 89, 0, 14, 69, 65, 146, 129, 52, 16, 48, 13, 73, 124, 63, 13, 0, 14, 69, 52, 147, 149, 80, 80, 63, 120, 50, 120, 47, 0, 10, 13, 69, 16, 18, 12, 36, 16, 70, 136, 55, 127, 13, 0, 11, 69, 5, 84, 211, 36, 80, 122, 86, 37, 0, 17, 2, 95, 33, 119, 49, 87, 49, 55, 13, 63, 6, 136, 89, 13, 50, 0, 0, 13, 67, 28, 243, 133, 2, 79, 129, 50, 0, 103, 12, 9, 12, 67, 28, 243, 133, 2, 79, 122, 50, 0, 12, 9, 0, 9, 67, 76, 243, 128, 87, 123, 50, 0, 17, 70, 24, 192, 77, 20, 224, 207, 81, 55, 117, 63, 119, 66, 49, 134, 0, 12, 67, 17, 81, 84, 70, 57, 132, 6, 119, 47, 0, 9, 67, 12, 243, 128, 49, 122, 50, 0, 9, 2, 95, 39, 49, 58, 134, 47, 0, 0, 11, 68, 72, 82, 75, 36, 34, 136, 49, 127, 0, 21, 72, 36, 212, 5, 72, 21, 9, 88, 80, 120, 63, 48, 6, 119, 34, 13, 47, 120, 82, 0, 13, 2, 95, 38, 35, 63, 48, 13, 87, 35, 50, 70, 0, 0, 17, 70, 20, 228, 197, 52, 35, 5, 122, 50, 87, 6, 122, 63, 69, 116, 0, 14, 4, 95, 50, 48, 15, 47, 58, 6, 119, 50, 47, 139, 0, 13, 2, 95, 37, 48, 146, 87, 6, 119, 50, 47, 0, 105, 12, 2, 95, 37, 48, 112, 87, 6, 119, 50, 47, 0, 0, 9, 67, 12, 243, 133, 49, 134, 50, 0, 9, 2, 95, 36, 70, 122, 55, 112, 0, 0, 16, 67, 88, 19, 128, 82, 35, 50, 70, 126, 0, 81, 100, 101, 114, 32, 17, 67, 88, 19, 128, 82, 35, 50, 70, 119, 50, 0, 81, 100, 101, 110, 32, 9, 67, 80, 83, 128, 47, 119, 50, 0, 19, 71, 36, 212, 9, 56, 114, 78, 28, 120, 63, 48, 6, 120, 50, 73, 120, 66, 0, 0, 9, 198, 61, 85, 3, 5, 53, 0, 65, 11, 68, 4, 66, 69, 84, 117, 70, 57, 132, 0, 13, 2, 95, 42, 35, 87, 47, 13, 34, 120, 87, 49, 0, 14, 4, 95, 3, 1, 16, 49, 4, 35, 48, 14, 47, 116, 0, 0, 9, 67, 32, 84, 130, 126, 69, 0, 103, 12, 69, 12, 20, 211, 21, 144, 49, 136, 87, 37, 0, 14, 69, 9, 81, 78, 61, 48, 69, 58, 136, 50, 122, 87, 0, 17, 70, 80, 20, 5, 77, 68, 153, 47, 35, 48, 13, 87, 47, 34, 120, 0, 13, 2, 95, 41, 34, 135, 47, 48, 117, 34, 119, 50, 0, 0, 16, 70, 80, 244, 143, 57, 67, 192, 47, 13, 34, 122, 50, 47, 134, 0, 18, 70, 36, 66, 84, 5, 35, 196, 135, 70, 6, 120, 47, 13, 34, 122, 70, 0, 16, 70, 76, 245, 84, 32, 83, 132, 87, 124, 81, 6, 119, 50, 70, 0, 10, 67, 36, 67, 25, 135, 70, 55, 120, 0, 14, 2, 95, 40, 55, 119, 81, 47, 48, 117, 34, 119, 50, 0, 0, 11, 67, 32, 84, 128, 105, 126, 0, 72, 34, 9, 17, 67, 64, 84, 128, 48, 4, 126, 15, 87, 6, 136, 0, 81, 115, 101, 32, 20, 67, 64, 84, 128, 48, 112, 15, 87, 6, 119, 50, 47, 0, 81, 99, 101, 110, 116, 32, 9, 67, 64, 84, 128, 48, 126, 0, 72, 19, 71, 16, 243, 7, 20, 195, 1, 84, 70, 122, 55, 79, 6, 119, 97, 55, 135, 0, 0, 10, 67, 49, 82, 83, 55, 132, 120, 87, 0, 13, 68, 44, 80, 78, 84, 49, 120, 6, 124, 50, 132, 0, 11, 68, 20, 66, 84, 32, 127, 70, 120, 85, 0, 11, 68, 20, 35, 207, 44, 127, 69, 115, 49, 0, 8, 2, 95, 46, 70, 122, 47, 0, 0, 13, 69, 4, 68, 137, 4, 224, 136, 70, 34, 139, 50, 0, 14, 69, 53, 83, 137, 12, 128, 63, 57, 132, 50, 120, 49, 0, 15, 70, 5, 69, 15, 72, 225, 89, 117, 47, 146, 50, 37, 0, 105, 14, 70, 5, 69, 15, 72, 225, 89, 117, 47, 126, 50, 37, 0, 12, 69, 4, 195, 9, 20, 64, 35, 55, 135, 70, 0, 9, 2, 95, 45, 70, 35, 89, 0, 103, 11, 2, 95, 45, 105, 4, 135, 81, 13, 50, 0, 0, 28, 67, 32, 84, 133, 105, 6, 140, 15, 13, 50, 70, 15, 84, 6, 138, 0, 82, 97, 110, 100, 32, 116, 104, 101, 114, 101, 32, 14, 70, 76, 243, 4, 36, 84, 128, 87, 134, 55, 73, 112, 0, 9, 198, 24, 244, 133, 88, 84, 128, 66, 15, 70, 4, 195, 15, 88, 84, 128, 128, 55, 6, 134, 82, 112, 0, 9, 2, 95, 44, 49, 122, 63, 13, 0, 0, 19, 67, 24, 20, 128, 81, 6, 125, 10, 63, 4, 131, 0, 81, 109, 111, 114, 101, 32, 16, 71, 32, 243, 69, 61, 115, 133, 72, 105, 134, 63, 134, 50, 112, 0, 20, 71, 5, 4, 1, 72, 21, 21, 76, 35, 48, 13, 34, 6, 35, 47, 13, 87, 0, 103, 19, 71, 5, 4, 1, 72, 21, 21, 76, 35, 48, 13, 34, 6, 136, 47, 13, 87, 0, 12, 67, 53, 36, 192, 63, 120, 87, 111, 86, 0, 24, 9, 2, 95, 51, 85, 34, 6, 127, 0, 0, 12, 68, 4, 226, 84, 4, 117, 50, 127, 47, 13, 0, 21, 72, 104, 147, 66, 4, 37, 197, 4, 224, 86, 111, 63, 69, 124, 69, 58, 120, 13, 50, 0, 8, 2, 95, 50, 47, 6, 132, 0, 0, 13, 69, 77, 147, 66, 60, 192, 87, 120, 63, 69, 116, 0, 9, 198, 12, 243, 150, 21, 36, 197, 36, 10, 198, 12, 243, 150, 21, 36, 197, 65, 9, 10, 2, 95, 49, 58, 6, 123, 50, 0, 106, 9, 2, 95, 49, 58, 6, 122, 50, 0, 0, 16, 70, 8, 20, 133, 57, 68, 192, 69, 35, 34, 13, 50, 47, 87, 0, 14, 70, 61, 4, 15, 76, 84, 128, 13, 48, 134, 86, 112, 0, 15, 70, 48, 16, 143, 72, 84, 128, 55, 136, 69, 13, 34, 112, 0, 10, 2, 95, 48, 86, 6, 139, 34, 134, 0, 0, 19, 71, 72, 80, 207, 52, 209, 78, 16, 34, 4, 119, 49, 13, 63, 119, 50, 70, 0, 12, 2, 95, 55, 87, 6, 13, 82, 13, 50, 0, 107, 11, 2, 95, 55, 87, 6, 119, 82, 13, 50, 0, 0, 10, 67, 56, 148, 143, 50, 139, 34, 134, 0, 10, 67, 21, 35, 211, 139, 34, 122, 87, 0, 10, 2, 95, 54, 87, 6, 120, 49, 87, 0, 0, 9, 2, 95, 53, 81, 6, 135, 82, 0, 0, 16, 70, 72, 84, 18, 37, 48, 76, 34, 111, 48, 34, 135, 86, 116, 0, 17, 70, 64, 83, 131, 32, 19, 148, 48, 119, 50, 89, 13, 50, 47, 0, 103, 15, 70, 64, 83, 131, 32, 19, 148, 48, 122, 50, 89, 122, 50, 0, 14, 70, 24, 21, 9, 29, 81, 64, 81, 117, 47, 127, 79, 0, 8, 2, 95, 52, 81, 6, 131, 0, 0, 15, 2, 95, 59, 87, 119, 63, 120, 49, 6, 134, 55, 13, 50, 0, 0, 11, 67, 32, 84, 147, 105, 126, 86, 0, 72, 12, 11, 68, 4, 226, 83, 20, 35, 50, 120, 87, 0, 10, 2, 95, 58, 49, 134, 55, 13, 50, 0, 0, 15, 69, 92, 130, 76, 77, 64, 58, 4, 135, 55, 87, 47, 0, 8, 13, 5, 8, 5, 39, 12, 12, 105, 127, 55, 0, 72, 32, 13, 69, 21, 131, 79, 61, 32, 119, 49, 87, 63, 141, 0, 15, 69, 72, 81, 140, 85, 128, 34, 127, 81, 55, 123, 49, 87, 0, 9, 2, 95, 57, 50, 6, 135, 50, 0, 0, 10, 66, 92, 80, 58, 127, 0, 72, 32, 9, 13, 202, 52, 20, 211, 4, 50, 21, 76, 85, 20, 76, 67, 8, 66, 100, 16, 57, 117, 0, 9, 9, 198, 77, 84, 18, 37, 49, 64, 66, 18, 70, 12, 240, 88, 36, 19, 0, 49, 134, 6, 35, 49, 87, 120, 13, 55, 0, 16, 70, 12, 20, 129, 52, 83, 0, 49, 35, 34, 13, 63, 119, 55, 0, 16, 70, 4, 48, 213, 73, 49, 68, 117, 49, 146, 87, 121, 70, 0, 105, 15, 70, 4, 48, 213, 73, 49, 68, 117, 49, 126, 87, 121, 70, 0, 5, 194, 84, 144, 17, 8, 2, 95, 56, 6, 136, 47, 0, 0, 16, 70, 64, 84, 147, 64, 86, 0, 48, 126, 87, 48, 119, 49, 87, 0, 10, 199, 36, 229, 5, 72, 96, 67, 20, 65, 18, 71, 12, 243, 131, 36, 84, 135, 20, 49, 122, 50, 87, 120, 6, 138, 88, 0, 12, 2, 95, 63, 49, 58, 119, 87, 74, 13, 50, 0, 0, 11, 68, 24, 145, 82, 100, 81, 143, 34, 120, 0, 12, 68, 12, 19, 69, 60, 49, 35, 63, 120, 134, 0, 13, 2, 95, 62, 79, 34, 136, 47, 13, 84, 35, 50, 0, 0, 15, 69, 28, 64, 78, 76, 176, 79, 14, 70, 35, 50, 87, 49, 0, 14, 69, 48, 240, 193, 48, 80, 55, 134, 49, 6, 118, 55, 0, 12, 69, 29, 82, 78, 20, 16, 79, 120, 50, 37, 0, 13, 69, 24, 16, 193, 16, 80, 81, 13, 87, 124, 70, 0, 13, 69, 16, 80, 193, 16, 80, 70, 119, 49, 136, 70, 0, 10, 2, 95, 61, 127, 49, 58, 116, 86, 0, 0, 17, 70, 16, 243, 133, 28, 19, 0, 70, 122, 50, 111, 79, 6, 128, 55, 0, 10, 67, 16, 83, 153, 70, 111, 50, 135, 0, 11, 2, 95, 60, 55, 119, 87, 84, 35, 50, 0, 0, 0, 27, 68, 92, 245, 76, 16, 58, 115, 70, 105, 35, 82, 47, 114, 0, 74, 32, 12, 82, 104, 97, 118, 101, 32, 116, 111, 32, 21, 68, 92, 245, 76, 16, 58, 115, 70, 105, 35, 82, 0, 35, 14, 81, 104, 97, 118, 101, 32, 22, 68, 92, 245, 76, 16, 58, 2, 115, 70, 105, 2, 117, 82, 0, 35, 81, 104, 97, 118, 101, 32, 10, 196, 92, 245, 76, 16, 76, 32, 9, 12, 12, 68, 4, 211, 65, 56, 117, 63, 6, 124, 50, 0, 10, 67, 5, 53, 83, 136, 87, 13, 87, 0, 13, 68, 4, 66, 79, 76, 35, 84, 57, 6, 147, 87, 0, 0, 15, 69, 81, 34, 65, 56, 144, 47, 34, 127, 6, 35, 50, 37, 0, 14, 69, 76, 243, 21, 80, 80, 87, 122, 55, 57, 132, 47, 0, 15, 69, 16, 80, 149, 56, 176, 70, 127, 69, 6, 123, 50, 49, 0, 9, 198, 4, 229, 9, 52, 243, 153, 66, 0, 10, 2, 95, 64, 35, 47, 87, 135, 50, 0, 0, 19, 71, 21, 133, 18, 4, 66, 84, 20, 119, 49, 87, 47, 34, 13, 70, 135, 47, 0, 0, 20, 72, 65, 35, 202, 20, 53, 9, 48, 80, 48, 34, 13, 73, 119, 49, 47, 116, 0, 103, 11, 68, 5, 4, 1, 48, 117, 48, 128, 55, 0, 0, 16, 70, 12, 20, 143, 48, 147, 133, 49, 35, 34, 13, 55, 135, 50, 0, 16, 70, 24, 83, 73, 56, 147, 133, 81, 119, 63, 13, 50, 120, 50, 0, 12, 69, 5, 52, 197, 77, 48, 117, 87, 119, 87, 0, 0, 17, 70, 88, 149, 1, 52, 147, 128, 82, 135, 47, 13, 63, 120, 50, 0, 103, 17, 70, 88, 149, 1, 52, 147, 128, 82, 135, 47, 13, 63, 121, 50, 0, 103, 16, 70, 88, 149, 1, 52, 147, 128, 82, 120, 47, 13, 63, 121, 50, 0, 14, 70, 80, 84, 146, 4, 147, 128, 47, 13, 34, 136, 50, 0, 15, 70, 29, 34, 70, 24, 243, 128, 79, 34, 120, 81, 13, 50, 0, 0, 24, 75, 72, 80, 207, 56, 224, 73, 77, 48, 78, 12, 80, 34, 111, 49, 122, 50, 120, 87, 13, 50, 87, 0, 0, 10, 67, 48, 81, 207, 55, 119, 79, 134, 0, 11, 68, 4, 113, 210, 60, 35, 79, 34, 134, 0, 0, 14, 70, 52, 144, 200, 20, 195, 5, 63, 111, 89, 119, 55, 0, 13, 69, 5, 53, 12, 21, 144, 35, 87, 47, 55, 37, 0, 18, 70, 12, 20, 143, 48, 147, 129, 49, 35, 34, 13, 55, 6, 135, 50, 13, 0, 9, 198, 84, 208, 146, 20, 195, 1, 66, 15, 70, 80, 244, 148, 36, 195, 1, 47, 130, 47, 6, 127, 117, 0, 15, 69, 77, 80, 148, 49, 144, 87, 123, 47, 13, 55, 120, 0, 32, 17, 70, 72, 81, 137, 56, 84, 153, 34, 111, 81, 135, 50, 13, 34, 120, 0, 19, 8, 16, 9, 195, 177, 1, 20, 1, 19, 48, 127, 65, 6, 35, 47, 117, 86, 0, 13, 69, 52, 245, 84, 33, 48, 63, 133, 84, 86, 0, 9, 12, 201, 24, 244, 133, 76, 131, 210, 80, 83, 128, 66, 18, 70, 12, 243, 148, 72, 20, 153, 49, 122, 50, 47, 34, 138, 34, 37, 0, 103, 17, 70, 12, 243, 148, 72, 20, 153, 49, 122, 50, 47, 34, 13, 34, 120, 0, 12, 4, 95, 226, 128, 163, 69, 115, 55, 111, 47, 0, 0, 9, 198, 12, 243, 12, 20, 83, 128, 66, 19, 70, 25, 35, 206, 80, 83, 132, 81, 34, 6, 123, 50, 47, 4, 119, 50, 70, 0, 16, 4, 194, 182, 194, 182, 48, 35, 34, 13, 79, 34, 35, 81, 87, 0, 12, 4, 95, 226, 128, 162, 69, 115, 55, 111, 47, 0, 0, 10, 67, 4, 64, 64, 136, 70, 13, 0, 10, 18, 71, 12, 243, 15, 77, 49, 85, 52, 49, 122, 55, 13, 87, 6, 139, 63, 0, 15, 4, 95, 226, 128, 161, 70, 123, 69, 116, 70, 35, 79, 112, 0, 0, 11, 68, 48, 20, 197, 72, 55, 136, 86, 112, 0, 11, 68, 24, 147, 210, 16, 81, 127, 130, 70, 0, 16, 70, 8, 16, 203, 20, 225, 0, 69, 35, 49, 6, 119, 50, 70, 0, 11, 4, 95, 226, 128, 160, 70, 35, 79, 112, 0, 0, 12, 67, 92, 129, 78, 4, 58, 119, 50, 0, 15, 10, 12, 67, 92, 129, 78, 58, 2, 119, 50, 0, 12, 10, 16, 70, 65, 33, 78, 80, 144, 197, 48, 34, 119, 50, 47, 120, 87, 0, 14, 69, 36, 211, 199, 20, 224, 120, 63, 13, 73, 13, 50, 0, 8, 197, 4, 81, 197, 4, 224, 66, 0, 16, 70, 4, 225, 197, 48, 84, 192, 35, 50, 73, 13, 55, 127, 86, 0, 15, 7, 6, 1, 195, 167, 1, 4, 5, 81, 13, 87, 124, 70, 0, 15, 4, 95, 226, 128, 166, 120, 55, 6, 120, 48, 87, 120, 87, 0, 0, 13, 70, 12, 82, 76, 36, 66, 0, 49, 136, 55, 37, 0, 6, 195, 85, 48, 128, 17, 13, 4, 95, 226, 128, 165, 47, 132, 70, 122, 47, 87, 0, 0, 11, 68, 52, 148, 200, 4, 63, 127, 89, 13, 0, 10, 4, 95, 226, 128, 164, 70, 122, 47, 0, 0, 14, 69, 4, 193, 146, 20, 64, 35, 55, 81, 34, 111, 70, 0, 10, 67, 4, 192, 78, 35, 55, 13, 50, 0, 12, 69, 72, 82, 78, 20, 64, 34, 136, 50, 70, 0, 14, 69, 32, 21, 18, 20, 64, 105, 136, 47, 34, 121, 70, 0, 15, 4, 95, 226, 128, 155, 55, 119, 81, 47, 49, 58, 134, 47, 0, 0, 15, 70, 52, 83, 80, 32, 148, 192, 63, 119, 63, 81, 111, 87, 0, 13, 4, 95, 226, 128, 154, 55, 134, 49, 58, 134, 47, 0, 0, 15, 70, 76, 21, 67, 21, 0, 78, 87, 128, 87, 48, 13, 50, 0, 14, 4, 95, 226, 128, 153, 34, 135, 47, 49, 58, 134, 47, 0, 0, 14, 68, 28, 242, 78, 28, 4, 79, 134, 120, 66, 0, 12, 9, 10, 67, 4, 193, 67, 35, 55, 120, 49, 0, 14, 70, 48, 83, 208, 5, 33, 0, 55, 119, 48, 112, 70, 0, 10, 68, 28, 21, 71, 20, 79, 136, 73, 0, 15, 4, 95, 226, 128, 152, 55, 119, 81, 47, 49, 58, 134, 47, 0, 18, 4, 95, 4, 15, 20, 58, 120, 84, 70, 6, 122, 47, 117, 69, 123, 82, 0, 0, 14, 69, 76, 80, 193, 57, 64, 87, 127, 49, 13, 50, 47, 0, 14, 69, 21, 132, 5, 73, 64, 119, 49, 87, 48, 126, 47, 0, 13, 69, 4, 211, 213, 57, 64, 117, 63, 133, 50, 47, 0, 16, 4, 95, 226, 128, 159, 55, 119, 81, 47, 49, 58, 134, 47, 87, 0, 0, 18, 70, 81, 34, 66, 84, 224, 76, 47, 34, 135, 69, 6, 57, 132, 50, 116, 0, 16, 70, 77, 3, 207, 56, 97, 68, 87, 48, 132, 50, 81, 119, 70, 0, 11, 67, 56, 22, 137, 50, 124, 47, 87, 120, 0, 14, 70, 28, 148, 129, 24, 97, 64, 73, 111, 34, 118, 81, 0, 10, 67, 4, 64, 77, 35, 70, 13, 63, 0, 14, 4, 95, 226, 128, 158, 55, 134, 49, 58, 134, 47, 87, 0, 0, 11, 67, 76, 129, 64, 89, 127, 0, 72, 9, 33, 15, 4, 95, 226, 128, 157, 34, 135, 47, 49, 58, 134, 47, 87, 0, 15, 2, 95, 91, 55, 119, 81, 47, 69, 34, 35, 49, 111, 47, 0, 0, 16, 70, 65, 33, 67, 21, 5, 0, 48, 34, 127, 87, 119, 48, 47, 0, 11, 200, 52, 18, 78, 80, 18, 78, 21, 32, 66, 11, 68, 32, 82, 83, 80, 105, 135, 87, 47, 0, 16, 4, 95, 226, 128, 156, 55, 119, 81, 47, 49, 58, 134, 47, 87, 0, 0, 10, 67, 48, 83, 206, 55, 127, 122, 50, 0, 16, 70, 52, 148, 211, 61, 84, 137, 63, 120, 86, 6, 141, 34, 37, 0, 18, 70, 60, 34, 84, 84, 20, 153, 122, 69, 6, 120, 74, 115, 138, 37, 0, 103, 16, 70, 60, 34, 84, 84, 20, 153, 122, 69, 6, 120, 74, 141, 37, 0, 10, 67, 20, 65, 78, 127, 70, 13, 50, 0, 18, 70, 16, 147, 1, 80, 244, 153, 70, 120, 55, 35, 47, 147, 34, 120, 0, 103, 17, 70, 16, 147, 1, 80, 244, 153, 70, 120, 55, 13, 47, 13, 34, 120, 0, 14, 69, 12, 21, 143, 73, 64, 49, 117, 82, 6, 130, 47, 0, 10, 4, 95, 226, 128, 147, 70, 35, 89, 0, 0, 16, 70, 76, 243, 69, 60, 225, 64, 87, 123, 63, 58, 123, 50, 0, 106, 15, 70, 76, 243, 69, 60, 225, 64, 87, 123, 63, 58, 122, 50, 0, 19, 66, 76, 240, 87, 6, 134, 15, 63, 4, 123, 74, 0, 81, 109, 117, 99, 104, 32, 20, 66, 76, 240, 87, 4, 134, 15, 63, 6, 119, 50, 37, 0, 81, 109, 97, 110, 121, 32, 18, 66, 76, 240, 87, 6, 134, 15, 81, 4, 125, 0, 12, 81, 102, 97, 114, 32, 9, 66, 76, 240, 4, 87, 134, 0, 12, 16, 70, 29, 33, 68, 36, 83, 148, 79, 34, 127, 70, 139, 50, 47, 0, 16, 70, 16, 80, 129, 12, 193, 64, 70, 136, 69, 6, 124, 49, 116, 0, 6, 194, 88, 144, 17, 42, 5, 194, 84, 176, 17, 10, 4, 95, 226, 128, 146, 70, 35, 89, 0, 0, 13, 70, 4, 19, 9, 100, 18, 0, 13, 55, 127, 13, 0, 12, 4, 95, 226, 128, 145, 105, 135, 81, 13, 50, 0, 14, 2, 95, 95, 6, 123, 50, 70, 112, 87, 49, 4, 131, 0, 0, 12, 68, 72, 148, 197, 56, 34, 120, 86, 13, 50, 0, 12, 68, 72, 85, 18, 100, 34, 127, 47, 34, 135, 0, 9, 67, 12, 130, 67, 89, 127, 49, 0, 11, 67, 4, 192, 83, 117, 55, 6, 35, 87, 0, 11, 4, 95, 226, 130, 160, 57, 141, 34, 134, 0, 12, 4, 95, 226, 128, 144, 105, 135, 81, 13, 50, 0, 17, 2, 95, 94, 87, 145, 49, 123, 63, 81, 55, 4, 119, 49, 87, 0, 105, 16, 2, 95, 94, 87, 126, 49, 123, 63, 81, 55, 4, 119, 49, 87, 0, 0, 6, 195, 76, 243, 206, 32, 15, 69, 8, 80, 193, 52, 80, 69, 120, 49, 136, 63, 0, 74, 12, 10, 67, 4, 65, 78, 136, 70, 13, 50, 0, 14, 69, 64, 20, 1, 100, 16, 48, 117, 48, 135, 38, 13, 0, 10, 67, 36, 51, 206, 135, 49, 122, 50, 0, 13, 69, 12, 19, 137, 56, 80, 49, 136, 50, 135, 50, 0, 14, 2, 95, 93, 34, 135, 47, 69, 34, 35, 49, 111, 47, 0, 0, 10, 67, 64, 84, 149, 48, 13, 34, 132, 0, 16, 70, 56, 18, 82, 60, 34, 64, 50, 135, 34, 6, 134, 69, 37, 0, 18, 70, 9, 81, 1, 64, 84, 212, 69, 132, 70, 13, 48, 6, 119, 87, 47, 0, 15, 70, 77, 83, 132, 36, 19, 0, 87, 123, 50, 70, 142, 55, 0, 9, 67, 76, 130, 65, 89, 127, 13, 0, 27, 74, 52, 144, 210, 60, 244, 135, 4, 226, 83, 52, 63, 135, 49, 34, 134, 6, 130, 79, 13, 50, 120, 86, 13, 63, 0, 15, 4, 95, 226, 128, 150, 70, 4, 123, 69, 116, 69, 6, 125, 0, 0, 20, 4, 95, 226, 128, 149, 105, 122, 34, 111, 86, 4, 122, 50, 47, 116, 69, 6, 125, 0, 0, 27, 68, 12, 245, 76, 16, 49, 115, 70, 105, 35, 82, 47, 114, 0, 74, 32, 12, 82, 104, 97, 118, 101, 32, 116, 111, 32, 21, 68, 12, 245, 76, 16, 49, 115, 70, 105, 35, 82, 0, 35, 14, 81, 104, 97, 118, 101, 32, 20, 68, 12, 245, 76, 16, 4, 49, 115, 70, 117, 82, 0, 35, 81, 104, 97, 118, 101, 32, 14, 68, 12, 245, 76, 16, 2, 49, 115, 70, 0, 32, 12, 9, 13, 68, 60, 20, 201, 76, 134, 6, 136, 87, 111, 87, 0, 12, 68, 16, 83, 79, 56, 70, 127, 63, 13, 50, 0, 11, 68, 12, 243, 69, 72, 49, 123, 63, 112, 0, 9, 68, 12, 241, 85, 72, 49, 126, 0, 12, 4, 95, 226, 128, 148, 119, 63, 70, 35, 89, 0, 0, 16, 70, 76, 19, 65, 57, 66, 1, 87, 13, 63, 35, 50, 85, 13, 0, 14, 69, 72, 85, 9, 56, 16, 34, 119, 47, 120, 50, 13, 0, 14, 69, 72, 81, 201, 52, 80, 34, 136, 88, 6, 127, 63, 0, 16, 70, 56, 84, 5, 57, 66, 5, 50, 111, 48, 119, 50, 85, 37, 0, 15, 69, 53, 85, 1, 80, 80, 63, 57, 132, 47, 6, 136, 47, 0, 23, 73, 4, 197, 5, 72, 224, 84, 20, 198, 64, 128, 55, 47, 6, 126, 50, 13, 47, 55, 120, 0, 32, 0, 9, 198, 61, 85, 2, 4, 50, 192, 65, 12, 2, 95, 96, 69, 35, 49, 48, 34, 135, 63, 0, 0, 20, 71, 48, 165, 66, 48, 160, 78, 4, 55, 57, 132, 69, 55, 57, 6, 124, 50, 13, 0, 17, 71, 76, 245, 78, 16, 34, 84, 20, 87, 133, 50, 70, 69, 135, 47, 0, 0, 11, 67, 60, 130, 79, 134, 105, 6, 135, 134, 0, 11, 68, 12, 18, 82, 60, 49, 135, 34, 134, 0, 9, 198, 61, 85, 13, 61, 53, 0, 65, 11, 68, 8, 20, 193, 48, 69, 136, 87, 116, 0, 20, 72, 5, 34, 84, 32, 209, 84, 36, 48, 117, 34, 120, 85, 63, 13, 47, 120, 49, 0, 0, 8, 67, 12, 129, 82, 89, 138, 0, 14, 69, 52, 244, 129, 77, 48, 63, 122, 34, 6, 35, 87, 0, 16, 70, 16, 148, 195, 37, 3, 5, 70, 120, 87, 6, 135, 48, 116, 0, 12, 69, 4, 148, 130, 85, 48, 138, 69, 123, 87, 0, 12, 4, 95, 51, 48, 15, 85, 6, 126, 47, 139, 0, 0, 11, 67, 81, 83, 129, 47, 57, 132, 50, 13, 0, 15, 70, 24, 195, 213, 72, 148, 200, 81, 55, 126, 111, 89, 0, 103, 15, 70, 24, 195, 213, 72, 148, 200, 81, 55, 123, 34, 111, 89, 0, 0, 9, 67, 72, 147, 192, 34, 127, 134, 0, 9, 198, 12, 243, 21, 52, 37, 83, 66, 9, 67, 48, 83, 192, 55, 127, 134, 0, 18, 71, 32, 84, 133, 80, 144, 193, 48, 105, 111, 34, 119, 47, 111, 49, 116, 0, 16, 70, 25, 34, 78, 28, 147, 135, 81, 34, 120, 50, 73, 120, 66, 0, 12, 201, 12, 131, 15, 72, 244, 12, 5, 53, 0, 65, 8, 67, 4, 195, 64, 124, 63, 0, 0, 20, 72, 69, 80, 84, 21, 35, 129, 73, 144, 49, 58, 13, 47, 126, 50, 13, 34, 120, 0, 11, 68, 32, 245, 212, 60, 105, 133, 47, 132, 0, 12, 68, 12, 243, 69, 80, 49, 122, 63, 111, 47, 0, 0, 14, 69, 13, 148, 18, 85, 48, 87, 135, 48, 34, 13, 87, 0, 13, 69, 36, 229, 18, 5, 144, 120, 50, 47, 34, 136, 0, 0, 15, 70, 52, 244, 143, 12, 51, 192, 63, 13, 34, 122, 49, 134, 0, 10, 67, 88, 148, 193, 82, 127, 86, 13, 0, 10, 67, 88, 20, 197, 82, 124, 86, 0, 135, 9, 198, 80, 240, 129, 12, 51, 192, 66, 5, 194, 100, 64, 17, 12, 4, 95, 7, 18, 22, 79, 34, 6, 124, 82, 0, 0, 10, 67, 20, 66, 84, 119, 70, 120, 47, 0, 0, 13, 68, 53, 83, 20, 36, 63, 123, 55, 47, 135, 0, 103, 13, 68, 4, 35, 214, 20, 13, 69, 123, 82, 0, 74, 12, 12, 68, 48, 18, 84, 100, 55, 136, 13, 47, 37, 0, 13, 68, 16, 82, 84, 100, 70, 127, 13, 106, 37, 0, 103, 12, 68, 16, 82, 84, 100, 70, 136, 13, 47, 37, 0, 12, 68, 8, 148, 207, 56, 69, 135, 87, 13, 50, 0, 0, 12, 69, 12, 129, 82, 100, 192, 89, 119, 34, 116, 0, 15, 69, 84, 229, 201, 56, 64, 123, 50, 58, 6, 135, 50, 70, 0, 17, 69, 48, 149, 133, 12, 64, 55, 6, 135, 82, 87, 127, 70, 6, 127, 0, 13, 69, 21, 36, 129, 56, 64, 119, 34, 13, 50, 70, 0, 0, 16, 70, 16, 243, 73, 56, 144, 192, 70, 122, 63, 111, 50, 120, 49, 0, 10, 67, 56, 20, 193, 50, 35, 87, 117, 0, 0, 11, 67, 4, 193, 88, 35, 55, 120, 49, 87, 0, 19, 67, 16, 84, 192, 70, 13, 63, 137, 50, 0, 81, 109, 111, 105, 110, 101, 115, 32, 12, 201, 4, 99, 210, 20, 209, 78, 80, 147, 206, 66, 0, 0, 13, 69, 28, 244, 208, 20, 192, 79, 122, 87, 48, 116, 0, 23, 73, 12, 128, 82, 37, 51, 65, 80, 144, 192, 49, 35, 34, 120, 87, 63, 6, 35, 47, 120, 49, 0, 12, 69, 12, 128, 80, 20, 192, 74, 35, 48, 116, 0, 9, 198, 4, 195, 19, 64, 144, 197, 65, 0, 15, 70, 52, 18, 197, 56, 224, 64, 63, 13, 49, 119, 50, 13, 0, 15, 70, 44, 19, 142, 4, 64, 64, 49, 124, 50, 13, 70, 13, 0, 16, 70, 8, 243, 15, 28, 224, 64, 69, 13, 55, 134, 50, 38, 13, 0, 17, 70, 60, 49, 65, 56, 144, 192, 134, 89, 120, 6, 35, 50, 120, 49, 0, 0, 9, 67, 12, 243, 208, 49, 132, 48, 0, 19, 71, 12, 243, 77, 84, 226, 84, 100, 49, 13, 63, 57, 132, 50, 111, 47, 37, 0, 23, 73, 5, 81, 205, 20, 229, 1, 80, 147, 206, 128, 79, 63, 119, 50, 47, 6, 136, 89, 13, 50, 0, 10, 199, 4, 229, 9, 12, 194, 78, 20, 65, 0, 22, 73, 56, 243, 69, 56, 51, 1, 81, 84, 133, 50, 13, 63, 119, 66, 49, 55, 13, 74, 112, 0, 12, 68, 12, 195, 211, 20, 49, 55, 134, 86, 0, 36, 12, 68, 12, 195, 211, 20, 49, 55, 134, 87, 0, 9, 21, 72, 4, 67, 79, 56, 149, 9, 60, 224, 35, 70, 63, 13, 50, 6, 120, 89, 13, 50, 0, 0, 9, 198, 76, 128, 78, 28, 128, 73, 66, 13, 69, 12, 195, 211, 21, 32, 49, 55, 134, 87, 112, 0, 12, 69, 9, 81, 134, 21, 64, 69, 123, 81, 136, 0, 16, 69, 4, 36, 197, 57, 64, 35, 69, 87, 6, 119, 50, 47, 0, 36, 15, 69, 4, 36, 197, 57, 64, 35, 69, 87, 13, 50, 47, 0, 10, 15, 69, 4, 36, 197, 57, 64, 35, 69, 87, 6, 119, 50, 47, 0, 0, 14, 70, 52, 144, 200, 20, 193, 64, 63, 111, 89, 119, 55, 0, 15, 70, 76, 80, 84, 80, 193, 64, 87, 127, 6, 35, 47, 116, 0, 14, 70, 12, 243, 15, 28, 225, 64, 49, 13, 55, 134, 50, 0, 0, 13, 2, 95, 123, 55, 119, 81, 47, 69, 34, 136, 87, 0, 13, 4, 95, 4, 9, 1, 6, 115, 63, 55, 133, 47, 0, 0, 18, 72, 81, 35, 213, 8, 17, 15, 85, 32, 47, 34, 132, 69, 13, 70, 131, 0, 12, 68, 20, 69, 67, 20, 111, 70, 57, 132, 87, 0, 9, 67, 8, 20, 211, 69, 136, 87, 0, 20, 4, 95, 226, 128, 188, 119, 49, 87, 49, 55, 117, 63, 6, 136, 89, 13, 50, 86, 0, 0, 15, 69, 16, 241, 83, 57, 64, 70, 123, 86, 13, 50, 47, 0, 32, 13, 69, 24, 243, 7, 21, 32, 81, 134, 55, 73, 112, 0, 16, 70, 88, 145, 206, 21, 69, 5, 82, 120, 50, 57, 6, 119, 47, 0, 16, 70, 76, 16, 143, 80, 17, 197, 87, 35, 69, 13, 47, 124, 88, 0, 16, 70, 36, 229, 5, 72, 225, 69, 120, 50, 47, 6, 126, 50, 127, 0, 23, 73, 12, 21, 1, 77, 68, 143, 64, 129, 64, 49, 117, 47, 35, 87, 47, 34, 13, 81, 2, 37, 0, 15, 4, 95, 226, 128, 179, 70, 123, 69, 116, 48, 34, 135, 63, 0, 0, 15, 70, 32, 244, 212, 36, 193, 64, 105, 122, 87, 47, 116, 0, 103, 14, 70, 24, 84, 148, 36, 193, 64, 81, 126, 47, 116, 0, 103, 9, 66, 80, 240, 47, 132, 0, 72, 42, 9, 66, 80, 240, 47, 132, 0, 72, 14, 23, 66, 80, 240, 47, 132, 13, 50, 70, 81, 34, 6, 134, 0, 82, 97, 110, 100, 32, 102, 114, 111, 32, 16, 66, 80, 240, 2, 47, 115, 10, 47, 114, 0, 32, 81, 116, 111, 32, 16, 66, 80, 240, 47, 13, 15, 6, 69, 127, 0, 14, 81, 98, 101, 32, 15, 66, 80, 240, 47, 13, 69, 2, 37, 0, 35, 81, 98, 101, 32, 8, 66, 80, 240, 47, 114, 0, 32, 7, 66, 100, 80, 57, 127, 0, 9, 198, 85, 1, 210, 4, 65, 64, 36, 10, 198, 85, 1, 210, 4, 65, 64, 65, 10, 11, 67, 65, 83, 153, 48, 57, 132, 50, 37, 0, 14, 70, 12, 128, 82, 4, 65, 64, 89, 117, 34, 124, 70, 0, 11, 4, 95, 226, 128, 178, 48, 34, 135, 63, 0, 0, 11, 67, 92, 134, 64, 4, 58, 135, 0, 12, 10, 9, 67, 20, 198, 64, 127, 55, 37, 0, 9, 198, 65, 35, 199, 72, 84, 211, 36, 18, 70, 65, 35, 199, 72, 84, 211, 48, 34, 122, 79, 34, 119, 87, 0, 103, 9, 17, 70, 65, 35, 199, 72, 84, 211, 48, 34, 134, 79, 34, 119, 87, 0, 9, 0, 13, 4, 95, 226, 128, 176, 48, 126, 63, 6, 127, 55, 0, 0, 14, 69, 28, 20, 129, 28, 80, 79, 117, 34, 124, 88, 0, 103, 13, 69, 16, 83, 137, 76, 80, 70, 13, 50, 127, 87, 0, 11, 69, 5, 32, 200, 36, 80, 125, 74, 37, 0, 16, 70, 12, 243, 15, 52, 34, 65, 49, 13, 55, 123, 63, 69, 139, 0, 16, 69, 8, 241, 207, 80, 16, 69, 134, 79, 13, 47, 6, 124, 0, 103, 15, 69, 8, 241, 207, 80, 16, 69, 122, 79, 13, 47, 6, 124, 0, 14, 69, 84, 224, 66, 48, 80, 123, 50, 6, 136, 69, 116, 0, 12, 2, 95, 125, 34, 135, 47, 69, 34, 136, 87, 0, 0, 8, 3, 19, 195, 173, 89, 127, 0, 19, 70, 12, 243, 148, 72, 20, 212, 49, 122, 50, 47, 34, 6, 35, 87, 47, 0, 36, 10, 2, 95, 124, 82, 127, 69, 6, 125, 0, 0, 13, 67, 92, 128, 84, 4, 58, 123, 47, 0, 103, 12, 10, 12, 67, 92, 128, 84, 4, 58, 122, 47, 0, 15, 10, 12, 67, 92, 128, 84, 58, 2, 122, 47, 0, 12, 10, 19, 71, 80, 83, 5, 64, 131, 206, 100, 47, 119, 55, 6, 119, 81, 13, 50, 37, 0, 0, 18, 70, 77, 80, 138, 20, 53, 0, 87, 123, 69, 73, 6, 119, 49, 47, 0, 36, 8, 67, 76, 129, 87, 89, 134, 0, 12, 68, 25, 85, 15, 56, 81, 132, 47, 122, 50, 0, 16, 70, 21, 21, 65, 80, 147, 206, 111, 49, 58, 136, 88, 13, 50, 0, 11, 68, 20, 98, 76, 20, 127, 81, 135, 55, 0, 14, 70, 12, 243, 15, 72, 81, 0, 49, 123, 55, 112, 70, 0, 9, 68, 4, 148, 204, 20, 142, 55, 0, 16, 4, 95, 226, 128, 180, 47, 34, 120, 48, 116, 48, 34, 135, 63, 0, 0, 12, 69, 76, 244, 8, 36, 80, 87, 134, 81, 37, 0, 15, 70, 4, 36, 201, 57, 66, 5, 35, 69, 87, 120, 50, 85, 0, 0, 16, 70, 61, 97, 82, 80, 198, 64, 134, 82, 6, 126, 47, 55, 120, 0, 0, 15, 71, 72, 145, 200, 80, 83, 213, 76, 34, 135, 74, 13, 87, 0, 18, 71, 72, 21, 9, 60, 224, 76, 20, 34, 35, 89, 13, 50, 6, 35, 55, 0, 0, 18, 70, 9, 80, 200, 4, 224, 78, 69, 57, 132, 49, 6, 35, 50, 13, 50, 0, 9, 67, 92, 129, 87, 81, 57, 132, 0, 0, 14, 69, 28, 192, 68, 101, 48, 79, 55, 35, 70, 120, 87, 0, 22, 73, 65, 54, 67, 32, 144, 84, 72, 148, 212, 87, 135, 49, 6, 142, 47, 34, 120, 87, 47, 0, 14, 69, 4, 48, 197, 77, 48, 35, 49, 87, 119, 87, 0, 36, 14, 69, 4, 48, 197, 77, 48, 35, 49, 87, 119, 87, 0, 10, 0, 9, 198, 76, 128, 77, 64, 243, 192, 66, 16, 70, 48, 243, 135, 4, 115, 192, 55, 122, 66, 79, 13, 79, 134, 0, 0, 17, 70, 32, 80, 146, 36, 65, 83, 105, 119, 69, 34, 13, 70, 127, 86, 0, 14, 70, 12, 130, 83, 92, 144, 203, 74, 120, 86, 120, 49, 0, 0, 10, 67, 76, 147, 15, 87, 135, 55, 134, 0, 11, 68, 61, 85, 5, 16, 133, 47, 121, 70, 0, 16, 70, 52, 145, 5, 5, 53, 0, 63, 120, 70, 6, 127, 87, 47, 0, 12, 68, 4, 226, 77, 20, 35, 50, 120, 63, 136, 0, 0, 0, 9, 198, 76, 21, 129, 56, 224, 72, 66, 16, 70, 12, 16, 133, 72, 225, 84, 49, 35, 69, 112, 50, 6, 136, 0, 6, 194, 84, 224, 17, 42, 0, 20, 67, 92, 19, 12, 58, 6, 128, 55, 87, 47, 34, 4, 127, 47, 0, 81, 115, 116, 32, 9, 67, 64, 243, 12, 48, 134, 55, 0, 18, 71, 64, 145, 67, 20, 209, 65, 48, 48, 6, 127, 87, 63, 4, 127, 55, 0, 20, 71, 4, 197, 77, 36, 226, 85, 52, 35, 55, 57, 115, 63, 6, 120, 50, 139, 63, 0, 0, 10, 67, 80, 241, 15, 47, 13, 70, 132, 0, 11, 68, 76, 21, 68, 36, 87, 133, 70, 37, 0, 0, 15, 69, 64, 243, 9, 76, 128, 48, 134, 55, 120, 89, 0, 41, 9, 13, 69, 5, 33, 217, 48, 192, 125, 79, 38, 135, 55, 0, 13, 69, 73, 81, 199, 20, 64, 34, 123, 79, 121, 70, 0, 9, 197, 72, 80, 193, 48, 192, 66, 36, 13, 69, 72, 80, 193, 48, 192, 34, 127, 49, 128, 55, 0, 13, 69, 48, 144, 200, 20, 224, 55, 135, 49, 13, 50, 0, 14, 69, 9, 83, 137, 60, 224, 69, 123, 50, 111, 13, 50, 0, 0, 14, 70, 64, 149, 5, 61, 84, 192, 48, 120, 47, 139, 87, 0, 17, 70, 5, 50, 65, 80, 144, 192, 136, 89, 120, 6, 35, 47, 120, 49, 0, 0, 18, 71, 80, 81, 4, 100, 33, 65, 72, 47, 6, 119, 70, 120, 69, 4, 138, 0, 18, 71, 16, 19, 132, 20, 194, 79, 56, 70, 35, 50, 70, 111, 55, 142, 50, 0, 0, 12, 68, 12, 195, 212, 32, 49, 55, 134, 84, 0, 36, 12, 68, 8, 20, 201, 76, 69, 136, 87, 120, 87, 0, 0, 14, 69, 105, 84, 137, 12, 128, 86, 57, 115, 34, 120, 49, 0, 11, 67, 85, 64, 78, 132, 47, 6, 35, 50, 0, 13, 69, 72, 81, 201, 60, 224, 34, 127, 73, 13, 50, 0, 15, 69, 28, 147, 5, 4, 64, 79, 6, 120, 55, 120, 35, 70, 0, 0, 15, 70, 52, 147, 133, 73, 96, 64, 63, 111, 50, 126, 82, 13, 0, 0, 16, 71, 52, 83, 2, 61, 84, 142, 20, 63, 119, 55, 69, 112, 50, 0, 11, 67, 61, 1, 68, 122, 48, 6, 119, 70, 0, 18, 71, 4, 49, 84, 100, 193, 78, 20, 117, 87, 119, 47, 13, 55, 127, 50, 0, 0, 6, 195, 97, 134, 0, 17, 0, 17, 70, 21, 53, 9, 52, 21, 5, 119, 87, 47, 111, 63, 136, 47, 0, 36, 14, 69, 12, 195, 211, 21, 64, 49, 55, 122, 86, 111, 47, 0, 0, 14, 70, 48, 82, 83, 85, 33, 64, 55, 127, 88, 112, 0, 103, 13, 70, 48, 82, 83, 85, 33, 64, 55, 119, 88, 112, 0, 11, 4, 95, 35, 51, 50, 87, 48, 136, 87, 0, 0, 11, 67, 85, 64, 72, 57, 132, 106, 129, 0, 103, 10, 67, 85, 64, 72, 57, 132, 106, 124, 0, 0, 13, 68, 4, 211, 206, 28, 117, 63, 123, 66, 0, 74, 12, 10, 67, 44, 147, 15, 49, 127, 55, 134, 0, 12, 68, 4, 114, 83, 80, 136, 73, 120, 87, 47, 0, 0, 14, 69, 65, 33, 83, 21, 64, 48, 34, 127, 87, 119, 47, 0, 13, 69, 33, 83, 135, 21, 32, 105, 123, 66, 79, 112, 0, 9, 198, 21, 53, 18, 4, 225, 197, 66, 13, 69, 13, 85, 15, 85, 64, 49, 123, 47, 133, 47, 0, 13, 69, 12, 243, 135, 21, 32, 49, 122, 66, 79, 112, 0, 12, 69, 8, 243, 199, 21, 32, 69, 115, 79, 112, 0, 0, 15, 70, 76, 129, 82, 36, 97, 128, 89, 6, 119, 34, 111, 81, 0, 14, 70, 76, 49, 80, 81, 33, 64, 87, 119, 48, 47, 112, 0, 15, 70, 52, 16, 200, 21, 65, 64, 63, 117, 89, 119, 47, 37, 0, 14, 70, 5, 36, 197, 56, 19, 0, 125, 87, 13, 50, 116, 0, 0, 0, 12, 68, 72, 84, 201, 56, 34, 119, 86, 120, 50, 0, 0, 13, 69, 24, 19, 73, 56, 80, 81, 35, 63, 120, 50, 0, 9, 198, 4, 229, 9, 8, 241, 25, 65, 18, 70, 4, 36, 197, 57, 66, 65, 35, 69, 87, 6, 119, 50, 106, 127, 13, 0, 0, 17, 70, 36, 228, 85, 37, 38, 64, 120, 50, 49, 58, 13, 34, 37, 0, 103, 19, 70, 36, 225, 9, 72, 80, 212, 120, 50, 70, 112, 34, 6, 119, 49, 47, 0, 103, 9, 198, 36, 225, 9, 72, 80, 212, 67, 9, 198, 24, 20, 133, 92, 83, 12, 66, 9, 198, 12, 243, 148, 72, 16, 212, 36, 10, 198, 12, 243, 148, 72, 16, 212, 65, 10, 9, 67, 9, 34, 69, 69, 34, 127, 0, 0, 15, 67, 92, 147, 12, 58, 120, 55, 47, 114, 0, 81, 116, 111, 32, 9, 195, 92, 147, 12, 76, 9, 32, 12, 10, 199, 88, 19, 131, 61, 85, 133, 72, 66, 17, 70, 72, 129, 84, 61, 34, 67, 34, 119, 47, 13, 34, 120, 49, 0, 10, 19, 71, 36, 224, 78, 36, 208, 84, 20, 120, 50, 6, 35, 50, 120, 63, 13, 47, 0, 20, 71, 36, 115, 143, 72, 19, 85, 76, 120, 79, 50, 131, 34, 6, 136, 63, 13, 87, 0, 0, 22, 72, 64, 19, 5, 77, 66, 78, 36, 16, 48, 35, 55, 13, 87, 47, 6, 120, 50, 127, 13, 0, 21, 72, 12, 147, 131, 36, 227, 129, 80, 144, 87, 120, 50, 87, 120, 50, 6, 35, 47, 37, 0, 17, 70, 16, 148, 213, 76, 81, 0, 70, 120, 87, 6, 57, 132, 86, 70, 0, 6, 195, 4, 65, 147, 17, 0, 14, 69, 100, 19, 65, 32, 16, 57, 35, 63, 13, 105, 124, 0, 23, 73, 72, 85, 1, 48, 144, 84, 61, 38, 64, 34, 111, 47, 35, 55, 127, 13, 47, 13, 34, 120, 0, 23, 73, 72, 84, 208, 37, 32, 84, 61, 38, 64, 34, 119, 87, 48, 34, 13, 47, 147, 34, 37, 0, 103, 23, 73, 72, 84, 208, 37, 32, 84, 61, 38, 64, 34, 111, 87, 48, 120, 34, 13, 47, 13, 34, 120, 0, 13, 69, 64, 84, 149, 76, 80, 48, 13, 34, 132, 86, 0, 15, 69, 16, 148, 213, 76, 80, 70, 120, 87, 6, 57, 132, 87, 0, 0, 9, 198, 61, 85, 12, 60, 242, 192, 65, 5, 194, 97, 144, 17, 0, 18, 71, 4, 227, 206, 100, 211, 213, 76, 117, 50, 122, 50, 13, 63, 13, 87, 0, 6, 195, 5, 67, 64, 17, 0, 14, 68, 16, 242, 78, 28, 4, 70, 132, 120, 66, 0, 12, 9, 20, 72, 72, 80, 207, 53, 1, 78, 76, 80, 34, 119, 49, 13, 63, 48, 119, 50, 87, 0, 20, 72, 16, 81, 137, 56, 149, 9, 88, 80, 70, 111, 81, 120, 50, 111, 47, 120, 82, 0, 10, 68, 8, 242, 78, 28, 69, 137, 66, 0, 0, 15, 69, 52, 145, 4, 5, 144, 63, 4, 120, 70, 70, 6, 136, 0, 13, 69, 24, 17, 67, 21, 48, 81, 127, 87, 127, 86, 0, 0, 10, 67, 28, 19, 1, 79, 124, 55, 13, 0, 0, 0, 12, 68, 12, 197, 217, 16, 49, 55, 132, 120, 70, 0, 18, 72, 72, 83, 132, 21, 165, 143, 85, 48, 34, 122, 50, 70, 111, 82, 132, 0, 0, 16, 70, 88, 243, 1, 80, 147, 5, 82, 122, 55, 117, 47, 116, 0, 103, 9, 198, 44, 83, 148, 84, 50, 217, 66, 14, 69, 72, 83, 69, 17, 144, 34, 119, 63, 13, 70, 37, 0, 17, 70, 64, 20, 129, 8, 243, 1, 48, 13, 34, 35, 69, 13, 55, 13, 0, 0, 11, 67, 60, 18, 21, 134, 6, 124, 105, 132, 0, 15, 70, 48, 147, 131, 60, 195, 128, 55, 120, 50, 49, 13, 50, 0, 16, 70, 36, 229, 5, 72, 225, 84, 120, 50, 47, 112, 50, 119, 47, 0, 0, 18, 67, 92, 149, 8, 58, 2, 120, 84, 84, 113, 0, 34, 81, 116, 104, 101, 32, 10, 67, 92, 149, 8, 58, 120, 84, 0, 72, 8, 67, 5, 52, 192, 35, 87, 0, 0, 17, 70, 36, 229, 5, 73, 97, 78, 120, 50, 47, 112, 82, 6, 127, 50, 0, 15, 70, 12, 243, 77, 20, 229, 0, 49, 122, 63, 119, 50, 47, 0, 0, 15, 70, 12, 19, 12, 36, 244, 5, 49, 117, 55, 142, 48, 37, 0, 13, 69, 16, 19, 137, 76, 128, 70, 136, 50, 120, 89, 0, 13, 69, 72, 17, 199, 20, 64, 34, 35, 79, 121, 70, 0, 13, 69, 40, 17, 199, 20, 64, 73, 35, 79, 121, 70, 0, 13, 69, 16, 241, 199, 20, 64, 70, 122, 79, 121, 70, 0, 0, 12, 70, 40, 16, 209, 84, 84, 192, 88, 35, 49, 0, 14, 70, 12, 128, 83, 76, 148, 192, 74, 35, 87, 37, 0, 103, 13, 70, 12, 128, 83, 76, 148, 192, 89, 35, 87, 37, 0, 6, 195, 57, 148, 197, 17, 0, 17, 71, 8, 81, 84, 32, 245, 133, 56, 69, 136, 106, 134, 82, 13, 50, 0, 0, 10, 68, 61, 85, 5, 72, 133, 47, 112, 0, 15, 70, 12, 243, 77, 20, 225, 0, 49, 13, 63, 119, 50, 70, 0, 12, 68, 5, 4, 143, 56, 136, 48, 34, 13, 50, 0, 0, 14, 69, 52, 84, 131, 20, 64, 63, 126, 87, 6, 119, 70, 0, 16, 69, 8, 83, 135, 4, 192, 69, 4, 119, 50, 79, 6, 128, 55, 0, 13, 69, 92, 83, 23, 100, 224, 58, 119, 55, 120, 50, 0, 12, 69, 92, 147, 135, 20, 64, 58, 120, 66, 70, 0, 12, 69, 64, 147, 135, 20, 64, 48, 120, 66, 70, 0, 14, 69, 24, 244, 141, 36, 64, 81, 130, 63, 6, 120, 70, 0, 13, 69, 8, 19, 135, 20, 64, 69, 35, 66, 79, 70, 0, 0, 9, 67, 76, 149, 5, 87, 135, 47, 0, 9, 198, 60, 211, 137, 9, 84, 192, 65, 16, 70, 52, 147, 137, 9, 84, 192, 63, 120, 50, 120, 69, 123, 87, 0, 0, 9, 67, 33, 85, 192, 105, 57, 132, 0, 17, 71, 64, 20, 211, 20, 225, 197, 72, 48, 35, 87, 111, 50, 73, 112, 0, 17, 71, 12, 128, 77, 64, 17, 206, 20, 89, 35, 63, 48, 6, 136, 50, 0, 0, 0, 13, 69, 44, 147, 20, 21, 32, 49, 120, 55, 47, 112, 0, 10, 67, 12, 19, 22, 49, 35, 82, 0, 103, 9, 67, 12, 19, 22, 49, 124, 82, 0, 0, 9, 198, 16, 84, 208, 37, 65, 64, 8, 11, 67, 92, 22, 25, 58, 35, 49, 87, 37, 0, 15, 70, 72, 84, 212, 37, 97, 64, 34, 119, 87, 47, 120, 82, 0, 10, 198, 52, 19, 132, 5, 65, 64, 66, 36, 16, 70, 16, 85, 5, 57, 65, 64, 70, 136, 47, 6, 122, 50, 47, 0, 0, 31, 7, 13, 21, 19, 20, 14, 39, 20, 63, 6, 123, 87, 50, 47, 105, 35, 82, 47, 114, 0, 35, 82, 104, 97, 118, 101, 32, 116, 111, 32, 26, 7, 13, 21, 19, 20, 14, 39, 20, 63, 123, 87, 50, 47, 105, 117, 82, 0, 35, 77, 81, 104, 97, 118, 101, 32, 16, 7, 13, 21, 19, 20, 14, 39, 20, 63, 123, 87, 50, 47, 0, 32, 0, 32, 8, 23, 15, 21, 12, 4, 14, 39, 20, 4, 58, 115, 70, 50, 47, 35, 82, 47, 114, 0, 32, 12, 82, 104, 97, 118, 101, 32, 116, 111, 32, 27, 8, 23, 15, 21, 12, 4, 14, 39, 20, 58, 115, 70, 50, 47, 13, 82, 0, 73, 35, 12, 81, 104, 97, 118, 101, 32, 11, 68, 13, 84, 147, 20, 49, 146, 87, 0, 105, 10, 68, 13, 84, 147, 20, 49, 126, 87, 0, 0, 33, 9, 19, 8, 15, 21, 12, 4, 14, 39, 20, 6, 89, 115, 70, 50, 47, 35, 82, 47, 114, 0, 32, 12, 82, 104, 97, 118, 101, 32, 116, 111, 32, 28, 9, 19, 8, 15, 21, 12, 4, 14, 39, 20, 89, 115, 70, 50, 47, 105, 13, 82, 0, 35, 77, 81, 104, 97, 118, 101, 32, 21, 9, 19, 8, 15, 21, 12, 4, 14, 39, 20, 4, 89, 115, 70, 50, 47, 0, 32, 12, 9, 14, 69, 21, 129, 84, 21, 32, 119, 49, 87, 120, 47, 112, 0, 17, 70, 21, 132, 5, 16, 149, 5, 119, 49, 87, 48, 13, 70, 135, 47, 0, 16, 70, 16, 84, 207, 48, 21, 5, 70, 119, 87, 13, 55, 13, 47, 0, 17, 70, 12, 242, 78, 12, 145, 5, 49, 134, 120, 50, 87, 6, 135, 70, 0, 0, 14, 70, 56, 20, 146, 5, 65, 64, 50, 117, 34, 136, 47, 0, 0, 18, 71, 76, 16, 210, 36, 98, 67, 20, 87, 35, 49, 34, 111, 81, 135, 87, 0, 0, 11, 200, 4, 229, 9, 52, 21, 20, 21, 32, 65, 12, 68, 4, 226, 79, 56, 35, 50, 136, 13, 50, 0, 21, 72, 4, 225, 77, 60, 209, 84, 21, 32, 35, 50, 120, 63, 6, 122, 63, 111, 47, 112, 0, 0, 15, 69, 80, 35, 9, 76, 144, 47, 14, 69, 55, 127, 87, 37, 0, 12, 201, 77, 80, 143, 72, 66, 78, 5, 65, 64, 66, 13, 69, 76, 80, 78, 12, 80, 87, 136, 122, 50, 87, 0, 11, 67, 61, 129, 78, 122, 49, 87, 13, 50, 0, 0, 10, 67, 64, 243, 25, 48, 122, 55, 120, 0, 9, 67, 4, 70, 133, 35, 70, 86, 0, 16, 70, 4, 34, 76, 37, 70, 64, 117, 69, 120, 55, 13, 47, 37, 0, 10, 3, 9, 46, 5, 135, 127, 11, 0, 8, 0, 15, 70, 77, 2, 78, 4, 50, 0, 87, 48, 120, 50, 111, 74, 0, 18, 71, 65, 33, 68, 36, 48, 84, 20, 48, 34, 119, 70, 111, 49, 136, 47, 0, 19, 71, 64, 243, 25, 4, 210, 68, 20, 48, 122, 55, 120, 6, 136, 63, 135, 70, 0, 0, 12, 68, 28, 20, 197, 76, 79, 35, 87, 121, 86, 0, 0, 17, 70, 56, 80, 146, 5, 50, 193, 50, 13, 69, 34, 35, 87, 49, 13, 0, 14, 69, 88, 17, 201, 56, 16, 82, 13, 73, 135, 50, 13, 0, 9, 198, 52, 243, 69, 57, 69, 77, 66, 8, 197, 16, 243, 73, 56, 240, 65, 0, 24, 74, 36, 224, 80, 65, 35, 208, 72, 144, 84, 20, 4, 120, 50, 117, 48, 34, 134, 48, 34, 139, 47, 0, 0, 18, 71, 4, 197, 5, 72, 224, 84, 20, 128, 55, 47, 112, 50, 136, 47, 0, 36, 19, 71, 4, 197, 5, 72, 224, 84, 20, 128, 55, 47, 6, 126, 50, 13, 47, 0, 9, 0, 20, 72, 21, 146, 129, 24, 160, 76, 48, 16, 136, 57, 117, 81, 57, 35, 47, 55, 117, 0, 11, 68, 17, 85, 133, 80, 70, 132, 82, 136, 0, 0, 15, 69, 16, 148, 195, 85, 48, 70, 120, 87, 49, 13, 87, 0, 9, 0, 15, 70, 36, 229, 5, 73, 96, 76, 120, 50, 47, 112, 82, 116, 0, 6, 195, 36, 212, 9, 65, 10, 67, 32, 244, 9, 105, 134, 48, 127, 0, 0, 0, 10, 67, 48, 242, 83, 55, 134, 120, 87, 0, 11, 68, 8, 163, 210, 56, 69, 57, 130, 50, 0, 21, 72, 65, 149, 8, 4, 115, 210, 5, 48, 48, 135, 85, 6, 35, 79, 13, 34, 13, 87, 0, 0, 13, 69, 56, 20, 12, 21, 48, 50, 136, 48, 116, 86, 0, 14, 69, 52, 17, 18, 5, 48, 63, 13, 70, 34, 118, 87, 0, 13, 69, 88, 84, 147, 85, 48, 82, 126, 87, 111, 86, 0, 14, 69, 61, 97, 82, 49, 144, 134, 82, 112, 55, 120, 0, 9, 0, 0, 8, 67, 100, 80, 64, 57, 136, 0, 0, 21, 72, 48, 16, 143, 72, 21, 15, 73, 144, 55, 35, 69, 34, 13, 47, 128, 34, 37, 0, 103, 12, 68, 20, 210, 76, 100, 119, 63, 111, 55, 37, 0, 10, 198, 80, 244, 141, 20, 229, 0, 66, 36, 9, 198, 80, 244, 141, 20, 229, 0, 65, 21, 72, 48, 16, 143, 72, 21, 15, 73, 144, 55, 117, 69, 6, 122, 34, 13, 47, 34, 120, 0, 0, 15, 70, 48, 21, 210, 20, 224, 197, 55, 122, 34, 13, 50, 87, 0, 0, 15, 70, 52, 147, 9, 80, 144, 64, 63, 13, 55, 120, 89, 13, 0, 0, 17, 71, 33, 84, 146, 36, 48, 78, 20, 105, 126, 13, 49, 136, 50, 0, 103, 17, 71, 33, 84, 146, 36, 48, 78, 20, 105, 123, 34, 111, 49, 136, 50, 0, 17, 71, 12, 128, 77, 20, 193, 79, 56, 49, 13, 63, 127, 55, 139, 50, 0, 6, 195, 12, 144, 64, 17, 0, 13, 68, 92, 129, 82, 20, 4, 58, 138, 0, 8, 12, 10, 12, 68, 40, 84, 213, 76, 73, 127, 86, 13, 87, 0, 12, 68, 81, 81, 15, 72, 47, 57, 132, 70, 112, 0, 9, 198, 52, 19, 139, 36, 225, 0, 66, 12, 68, 44, 147, 211, 44, 49, 127, 122, 87, 49, 0, 12, 68, 40, 84, 213, 76, 73, 127, 86, 13, 87, 0, 10, 68, 24, 246, 69, 72, 81, 137, 136, 0, 8, 67, 12, 144, 79, 74, 133, 0, 0, 8, 197, 36, 225, 210, 36, 64, 65, 15, 69, 72, 81, 149, 56, 64, 34, 127, 81, 123, 50, 70, 0, 37, 14, 6, 195, 169, 12, 9, 20, 5, 120, 55, 6, 127, 47, 0, 0, 15, 70, 12, 240, 200, 48, 80, 64, 49, 122, 49, 55, 127, 13, 0, 0, 18, 71, 48, 193, 87, 20, 195, 25, 56, 103, 13, 58, 6, 119, 55, 120, 50, 0, 6, 195, 76, 17, 64, 17, 0, 0, 12, 69, 44, 244, 200, 21, 32, 49, 134, 89, 112, 0, 12, 69, 12, 243, 208, 21, 32, 49, 132, 48, 112, 0, 0, 9, 198, 8, 82, 74, 36, 225, 192, 66, 9, 198, 28, 243, 196, 9, 145, 64, 66, 14, 70, 21, 97, 78, 36, 225, 192, 127, 82, 50, 120, 66, 0, 16, 70, 4, 48, 68, 20, 209, 64, 117, 49, 35, 70, 13, 63, 37, 0, 15, 70, 4, 36, 197, 56, 49, 64, 35, 69, 87, 13, 50, 87, 0, 0, 18, 71, 9, 33, 65, 44, 96, 83, 80, 69, 34, 119, 49, 81, 13, 87, 47, 0, 0, 21, 72, 77, 80, 147, 21, 21, 69, 57, 64, 87, 123, 69, 87, 111, 49, 58, 13, 50, 47, 0, 11, 68, 56, 245, 193, 100, 50, 134, 58, 136, 0, 10, 67, 52, 83, 79, 63, 119, 63, 134, 0, 0, 13, 67, 4, 209, 78, 4, 136, 63, 6, 119, 50, 0, 103, 9, 197, 36, 225, 15, 61, 32, 65, 9, 13, 67, 4, 209, 78, 4, 124, 63, 6, 119, 50, 0, 10, 13, 69, 4, 114, 1, 77, 64, 117, 79, 118, 87, 47, 0, 0, 18, 70, 28, 85, 20, 36, 225, 192, 4, 79, 119, 47, 120, 66, 0, 12, 35, 9, 14, 70, 77, 81, 134, 36, 49, 64, 87, 13, 81, 135, 87, 0, 14, 70, 72, 80, 68, 36, 225, 192, 34, 127, 70, 120, 66, 0, 14, 70, 64, 19, 12, 36, 225, 192, 48, 35, 55, 120, 66, 0, 15, 70, 16, 84, 129, 56, 113, 64, 70, 111, 34, 136, 50, 73, 0, 0, 9, 67, 92, 146, 64, 58, 127, 12, 0, 15, 70, 4, 195, 5, 72, 114, 67, 117, 55, 126, 73, 120, 49, 0, 0, 11, 68, 84, 224, 204, 20, 123, 66, 49, 116, 0, 15, 7, 15, 39, 3, 12, 15, 3, 11, 13, 49, 55, 122, 49, 0, 11, 68, 56, 244, 201, 72, 50, 134, 87, 126, 0, 13, 68, 48, 241, 207, 56, 55, 122, 79, 6, 122, 50, 0, 0, 13, 69, 16, 245, 1, 28, 80, 70, 134, 47, 111, 73, 0, 6, 195, 85, 52, 210, 17, 0, 16, 70, 76, 80, 210, 20, 54, 64, 87, 127, 49, 34, 13, 87, 37, 0, 16, 70, 21, 53, 15, 65, 1, 76, 119, 87, 47, 6, 122, 48, 116, 0, 9, 198, 5, 32, 200, 92, 22, 64, 65, 0, 9, 67, 92, 131, 204, 105, 134, 55, 0, 17, 71, 32, 22, 129, 72, 67, 213, 76, 105, 35, 86, 112, 70, 13, 87, 0, 18, 71, 20, 69, 193, 72, 66, 65, 56, 119, 70, 58, 6, 130, 70, 139, 50, 0, 0, 19, 67, 16, 241, 83, 70, 123, 86, 50, 122, 47, 0, 32, 78, 81, 110, 111, 116, 32, 10, 67, 16, 241, 83, 70, 123, 86, 0, 32, 13, 68, 20, 194, 90, 4, 120, 55, 6, 135, 86, 13, 0, 10, 68, 52, 22, 65, 56, 63, 142, 50, 0, 15, 70, 12, 16, 129, 72, 85, 0, 49, 35, 69, 13, 34, 136, 0, 11, 68, 8, 20, 212, 20, 69, 136, 87, 47, 0, 0, 13, 69, 48, 80, 78, 56, 80, 55, 127, 6, 35, 50, 0, 13, 69, 24, 18, 78, 56, 80, 81, 35, 50, 38, 13, 0, 14, 69, 76, 245, 197, 80, 240, 87, 13, 58, 119, 47, 134, 0, 14, 69, 52, 19, 137, 48, 16, 63, 117, 50, 120, 55, 13, 0, 10, 67, 44, 145, 86, 49, 127, 119, 81, 0, 14, 69, 12, 19, 129, 16, 16, 49, 35, 50, 13, 70, 13, 0, 16, 70, 29, 32, 70, 24, 149, 9, 79, 34, 117, 81, 127, 47, 37, 0, 9, 67, 16, 241, 82, 70, 132, 112, 0, 0, 9, 67, 20, 211, 65, 119, 63, 13, 0, 9, 67, 92, 131, 193, 105, 58, 134, 0, 0, 13, 67, 92, 131, 192, 4, 105, 132, 0, 32, 8, 12, 10, 16, 70, 52, 19, 4, 37, 97, 83, 63, 128, 55, 70, 6, 127, 82, 0, 19, 71, 36, 225, 15, 12, 130, 78, 4, 120, 50, 70, 134, 74, 6, 135, 50, 13, 0, 19, 71, 12, 243, 150, 60, 197, 84, 20, 49, 122, 50, 82, 13, 55, 6, 132, 47, 0, 9, 67, 4, 67, 192, 117, 70, 132, 0, 0, 16, 70, 52, 18, 13, 61, 81, 0, 63, 35, 99, 63, 6, 132, 70, 0, 0, 16, 70, 77, 80, 144, 60, 83, 129, 87, 132, 48, 6, 127, 50, 13, 0, 12, 69, 5, 32, 200, 21, 48, 125, 74, 121, 86, 0, 0, 16, 70, 4, 36, 129, 32, 19, 64, 136, 69, 34, 13, 105, 35, 63, 0, 25, 74, 36, 225, 5, 80, 84, 141, 36, 224, 84, 20, 120, 50, 70, 111, 47, 6, 126, 63, 111, 50, 13, 47, 0, 12, 201, 4, 208, 137, 16, 86, 20, 72, 245, 83, 67, 0, 17, 70, 65, 148, 133, 56, 81, 83, 48, 120, 34, 13, 50, 6, 127, 86, 0, 0, 13, 68, 4, 35, 213, 80, 117, 69, 133, 47, 0, 74, 12, 9, 67, 76, 22, 83, 87, 119, 86, 0, 20, 72, 5, 32, 200, 36, 209, 68, 21, 48, 125, 49, 120, 63, 6, 127, 70, 127, 86, 0, 0, 13, 69, 5, 66, 5, 57, 48, 35, 85, 111, 50, 86, 0, 15, 69, 76, 147, 135, 49, 144, 87, 120, 66, 79, 55, 120, 0, 32, 0, 9, 67, 20, 211, 89, 119, 63, 37, 0, 16, 70, 48, 84, 207, 80, 131, 192, 55, 13, 87, 6, 132, 47, 132, 0, 0, 17, 71, 92, 21, 5, 73, 50, 5, 16, 58, 128, 47, 112, 89, 119, 70, 0, 0, 16, 70, 80, 83, 5, 64, 131, 206, 47, 119, 55, 111, 81, 134, 50, 0, 13, 68, 72, 80, 83, 44, 34, 127, 6, 118, 87, 49, 0, 12, 68, 72, 80, 82, 52, 34, 127, 6, 125, 63, 0, 12, 68, 48, 241, 201, 56, 55, 122, 79, 120, 50, 0, 12, 68, 8, 244, 213, 56, 69, 134, 87, 13, 50, 0, 0, 13, 69, 80, 20, 137, 24, 96, 47, 35, 34, 120, 81, 0, 0, 17, 70, 64, 19, 129, 12, 80, 64, 48, 35, 50, 117, 87, 6, 127, 13, 0, 0, 0, 20, 68, 80, 129, 82, 20, 84, 2, 138, 4, 58, 126, 0, 11, 81, 119, 101, 114, 101, 32, 16, 68, 80, 129, 82, 20, 84, 138, 69, 6, 127, 0, 81, 98, 101, 32, 18, 68, 80, 129, 82, 20, 84, 2, 138, 4, 125, 0, 11, 81, 97, 114, 101, 32, 12, 68, 80, 129, 82, 20, 84, 138, 0, 72, 12, 9, 12, 68, 72, 81, 201, 76, 34, 127, 73, 111, 87, 0, 11, 68, 80, 129, 84, 4, 85, 127, 47, 13, 0, 12, 68, 48, 20, 211, 60, 55, 35, 87, 134, 0, 103, 12, 68, 48, 20, 211, 60, 55, 35, 87, 6, 132, 0, 0, 0, 0, 10, 67, 20, 213, 64, 127, 63, 57, 132, 0, 0, 18, 72, 72, 144, 207, 12, 129, 84, 20, 64, 34, 120, 49, 13, 89, 136, 70, 0, 11, 68, 32, 245, 83, 20, 105, 133, 86, 0, 36, 15, 70, 12, 240, 85, 80, 131, 210, 49, 134, 6, 128, 85, 112, 0, 0, 13, 69, 77, 84, 133, 77, 64, 89, 141, 13, 87, 47, 0, 12, 69, 76, 16, 200, 21, 64, 87, 35, 89, 136, 0, 12, 69, 72, 20, 9, 21, 32, 34, 136, 48, 140, 0, 15, 69, 36, 228, 197, 73, 64, 120, 50, 87, 6, 126, 47, 0, 36, 14, 69, 36, 228, 197, 73, 64, 120, 50, 87, 126, 47, 0, 10, 10, 67, 16, 242, 78, 70, 132, 120, 50, 0, 12, 69, 12, 128, 76, 21, 64, 89, 35, 55, 136, 0, 12, 69, 12, 16, 200, 21, 64, 49, 35, 89, 136, 0, 0, 15, 70, 56, 21, 1, 48, 145, 64, 50, 35, 47, 117, 55, 37, 0, 15, 70, 92, 20, 212, 4, 113, 64, 58, 136, 87, 47, 111, 73, 0, 15, 70, 88, 84, 212, 36, 113, 64, 82, 119, 87, 47, 111, 73, 0, 14, 70, 80, 80, 82, 36, 225, 192, 47, 138, 44, 120, 66, 0, 15, 70, 76, 48, 82, 36, 225, 192, 87, 49, 138, 34, 120, 66, 0, 15, 70, 64, 244, 212, 4, 113, 64, 48, 134, 87, 47, 111, 73, 0, 15, 70, 52, 20, 211, 4, 113, 64, 63, 117, 87, 124, 88, 0, 103, 14, 70, 52, 20, 211, 4, 113, 64, 63, 35, 87, 124, 88, 0, 0, 18, 70, 8, 20, 130, 4, 67, 211, 69, 125, 6, 69, 136, 70, 134, 87, 0, 103, 17, 70, 8, 20, 130, 4, 67, 211, 69, 125, 6, 69, 136, 70, 122, 87, 0, 0, 14, 68, 80, 129, 83, 20, 84, 127, 86, 0, 72, 34, 12, 9, 0, 22, 73, 60, 211, 137, 76, 50, 69, 56, 49, 64, 122, 63, 50, 6, 120, 87, 120, 13, 50, 87, 0, 14, 70, 52, 84, 137, 56, 117, 69, 63, 13, 34, 35, 66, 0, 12, 69, 12, 244, 9, 21, 32, 49, 122, 48, 140, 0, 16, 70, 8, 18, 197, 48, 149, 5, 69, 136, 49, 13, 55, 135, 47, 0, 15, 70, 4, 224, 76, 60, 117, 69, 35, 50, 13, 55, 122, 79, 0, 0, 16, 70, 72, 243, 65, 56, 49, 64, 34, 134, 63, 6, 35, 50, 87, 0, 15, 70, 64, 20, 212, 36, 225, 192, 48, 136, 87, 47, 120, 66, 0, 15, 70, 61, 97, 82, 4, 113, 64, 134, 82, 13, 44, 136, 73, 0, 9, 198, 61, 85, 3, 60, 209, 64, 65, 14, 70, 56, 245, 8, 36, 225, 192, 50, 123, 85, 120, 66, 0, 14, 70, 56, 80, 203, 80, 145, 64, 50, 119, 49, 47, 135, 0, 14, 70, 12, 243, 12, 20, 113, 64, 49, 122, 55, 111, 73, 0, 15, 70, 5, 97, 82, 4, 113, 64, 35, 82, 14, 34, 111, 73, 0, 0, 0, 28, 68, 52, 145, 200, 80, 4, 63, 135, 47, 105, 6, 35, 82, 47, 114, 0, 32, 14, 82, 104, 97, 118, 101, 32, 116, 111, 32, 21, 68, 52, 145, 200, 80, 63, 135, 47, 105, 117, 82, 0, 35, 77, 81, 104, 97, 118, 101, 32, 14, 68, 52, 145, 200, 80, 4, 63, 135, 47, 0, 32, 12, 9, 18, 72, 16, 83, 143, 84, 83, 69, 57, 64, 70, 136, 50, 6, 132, 63, 149, 0, 9, 67, 5, 85, 15, 128, 47, 134, 0, 0, 8, 197, 84, 229, 201, 76, 80, 66, 15, 69, 21, 84, 143, 64, 16, 57, 141, 34, 6, 134, 48, 13, 0, 0, 14, 70, 12, 243, 15, 56, 83, 0, 49, 146, 50, 116, 0, 105, 13, 70, 12, 243, 15, 56, 83, 0, 49, 126, 50, 116, 0, 0, 9, 67, 4, 214, 64, 136, 63, 37, 0, 18, 71, 9, 34, 71, 4, 66, 69, 72, 69, 34, 120, 79, 117, 70, 6, 140, 0, 0, 0, 12, 69, 76, 129, 73, 48, 16, 89, 127, 55, 13, 0, 14, 69, 48, 245, 73, 76, 80, 55, 132, 58, 6, 127, 86, 0, 14, 69, 64, 19, 129, 52, 16, 48, 35, 50, 13, 63, 124, 0, 12, 69, 80, 245, 80, 20, 80, 47, 132, 48, 136, 0, 12, 69, 53, 148, 148, 48, 80, 63, 126, 47, 116, 0, 0, 14, 70, 48, 147, 132, 76, 22, 64, 55, 120, 50, 86, 37, 0, 15, 70, 8, 19, 15, 56, 86, 64, 69, 13, 55, 134, 50, 37, 0, 0, 16, 70, 88, 244, 148, 36, 49, 83, 82, 130, 47, 120, 87, 127, 86, 0, 16, 70, 72, 21, 133, 56, 245, 83, 34, 35, 82, 13, 50, 13, 87, 0, 11, 199, 5, 69, 18, 36, 37, 84, 20, 66, 36, 18, 71, 5, 69, 18, 36, 37, 84, 20, 35, 47, 34, 120, 69, 57, 132, 47, 0, 0, 19, 72, 4, 197, 18, 36, 224, 200, 4, 208, 128, 55, 47, 34, 120, 66, 13, 63, 0, 19, 72, 36, 227, 143, 88, 21, 9, 88, 80, 120, 50, 13, 82, 136, 47, 120, 82, 0, 11, 200, 36, 225, 9, 12, 21, 9, 88, 80, 66, 19, 72, 16, 80, 207, 72, 21, 9, 88, 80, 70, 119, 49, 34, 13, 47, 120, 82, 0, 0, 6, 18, 66, 108, 0, 114, 0, 7, 6, 18, 67, 105, 0, 121, 0, 7, 6, 18, 68, 97, 0, 105, 0, 111, 0, 117, 0, 7, 6, 18, 70, 99, 0, 103, 0, 107, 0, 7, 6, 18, 71, 115, 0, 122, 0, 7, 6, 18, 75, 103, 114, 97, 112, 0, 115, 99, 111, 112, 0, 108, 111, 103, 0, 109, 101, 116, 0, 7, 6, 20, 0, 0, 0, 0, 251, 0, 0, 102, 0, 102, 0, 1, 251, 0, 0, 102, 0, 105, 0, 2, 251, 0, 0, 102, 0, 108, 0, 0, 0, 0, 0, 6, 97, 98, 0, 4, 2, 111, 108, 105, 116, 3, 4, 35, 69, 0, 8, 2, 111, 114, 105, 0, 115, 101, 110, 2, 116, 3, 4, 35, 69, 87, 13, 50, 0, 101, 114, 8, 2, 21, 3, 4, 35, 69, 112, 0, 2, 117, 108, 97, 114, 3, 6, 35, 69, 0, 4, 8, 110, 101, 2, 108, 3, 6, 136, 69, 0, 8, 110, 117, 2, 108, 101, 0, 8, 115, 105, 100, 2, 108, 101, 0, 108, 105, 110, 103, 3, 6, 136, 69, 55, 120, 66, 0, 108, 101, 1, 116, 99, 21, 2, 32, 3, 8, 13, 69, 116, 0, 97, 100, 1, 21, 2, 32, 3, 8, 117, 69, 35, 70, 0, 1, 17, 67, 2, 105, 108, 105, 116, 12, 3, 13, 69, 0, 105, 108, 105, 116, 121, 1, 10, 2, 14, 128, 139, 135, 3, 13, 69, 6, 120, 55, 111, 47, 2, 37, 0, 105, 108, 105, 116, 105, 101, 115, 1, 10, 2, 14, 128, 139, 137, 3, 13, 69, 6, 120, 55, 111, 47, 2, 37, 86, 0, 4, 108, 121, 1, 10, 2, 32, 14, 128, 171, 132, 3, 13, 69, 55, 2, 120, 0, 108, 121, 1, 99, 10, 2, 32, 14, 128, 168, 132, 0, 4, 108, 101, 1, 10, 2, 32, 14, 128, 139, 132, 3, 13, 69, 116, 0, 108, 101, 1, 99, 10, 2, 32, 0, 4, 1, 98, 2, 121, 108, 3, 35, 69, 0, 2, 97, 99, 17, 65, 0, 2, 97, 116, 116, 0, 2, 106, 101, 99, 116, 0, 2, 108, 97, 116, 105, 118, 0, 2, 110, 101, 103, 0, 2, 114, 111, 103, 0, 2, 114, 117, 99, 0, 2, 115, 99, 101, 0, 2, 115, 101, 105, 0, 2, 115, 111, 108, 117, 0, 2, 115, 116, 105, 0, 8, 2, 100, 0, 8, 2, 105, 0, 8, 2, 114, 97, 99, 0, 98, 8, 0, 98, 111, 8, 3, 35, 69, 13, 0, 101, 114, 1, 17, 67, 2, 21, 3, 35, 69, 112, 0, 4, 8, 2, 21, 3, 117, 69, 0, 8, 2, 100, 117, 99, 0, 8, 2, 105, 100, 101, 0, 8, 2, 114, 97, 0, 98, 8, 2, 114, 101, 118, 0, 111, 118, 101, 8, 2, 21, 14, 128, 132, 133, 3, 117, 69, 4, 123, 82, 0, 101, 114, 8, 2, 114, 97, 110, 3, 117, 69, 119, 0, 4, 1, 17, 67, 29, 2, 108, 101, 3, 136, 69, 0, 1, 98, 2, 121, 0, 1, 108, 2, 111, 117, 114, 0, 1, 116, 115, 2, 105, 108, 0, 8, 2, 114, 97, 109, 0, 8, 108, 2, 105, 0, 108, 121, 3, 136, 69, 55, 120, 0, 101, 114, 8, 115, 2, 21, 3, 136, 69, 112, 0, 4, 101, 108, 8, 3, 136, 69, 116, 0, 108, 101, 0, 108, 101, 1, 10, 2, 32, 28, 17, 0, 7, 6, 97, 99, 0, 2, 99, 101, 110, 116, 117, 3, 2, 35, 49, 0, 2, 113, 117, 105, 101, 3, 4, 35, 0, 4, 2, 97, 32, 3, 6, 35, 49, 0, 2, 116, 111, 114, 121, 0, 2, 116, 117, 114, 101, 0, 2, 117, 108, 97, 114, 0, 104, 105, 97, 3, 6, 136, 89, 13, 0, 101, 97, 110, 2, 32, 3, 6, 136, 89, 13, 50, 0, 105, 111, 117, 115, 3, 6, 136, 89, 13, 87, 0, 1, 114, 99, 2, 121, 32, 3, 8, 13, 87, 0, 4, 1, 10, 2, 108, 101, 32, 3, 13, 49, 0, 104, 1, 114, 116, 2, 101, 0, 114, 101, 1, 115, 115, 97, 109, 3, 13, 49, 112, 0, 4, 1, 10, 2, 121, 32, 3, 13, 87, 0, 1, 102, 2, 105, 108, 105, 116, 0, 1, 108, 112, 2, 101, 98, 0, 8, 108, 112, 2, 101, 110, 116, 0, 104, 105, 1, 109, 2, 110, 17, 65, 13, 3, 13, 89, 127, 0, 4, 2, 99, 101, 110, 116, 3, 35, 49, 0, 2, 99, 105, 100, 0, 2, 111, 110, 0, 2, 114, 111, 0, 2, 117, 109, 0, 2, 117, 112, 0, 8, 2, 111, 0, 8, 2, 114, 105, 0, 8, 2, 116, 0, 99, 2, 111, 108, 0, 104, 2, 114, 111, 109, 0, 107, 8, 0, 97, 2, 100, 101, 109, 3, 35, 49, 13, 0, 114, 111, 1, 109, 2, 21, 3, 35, 49, 34, 13, 0, 110, 101, 3, 35, 49, 50, 120, 0, 99, 117, 2, 114, 97, 3, 35, 49, 57, 115, 0, 109, 101, 3, 35, 49, 63, 120, 0, 116, 117, 2, 17, 65, 3, 35, 49, 74, 132, 0, 4, 2, 101, 114, 98, 3, 35, 87, 0, 2, 105, 100, 32, 0, 4, 101, 8, 2, 116, 3, 35, 87, 120, 0, 101, 8, 109, 2, 100, 0, 104, 105, 110, 97, 1, 109, 2, 116, 3, 35, 89, 111, 50, 136, 0, 4, 1, 108, 112, 2, 97, 116, 3, 117, 49, 0, 8, 2, 21, 0, 99, 8, 2, 21, 0, 107, 8, 2, 110, 0, 97, 2, 100, 101, 109, 121, 3, 117, 49, 35, 0, 99, 117, 115, 2, 17, 65, 3, 117, 49, 57, 132, 86, 0, 113, 117, 8, 3, 117, 49, 58, 0, 99, 8, 2, 101, 3, 117, 49, 87, 0, 4, 99, 111, 117, 2, 116, 3, 117, 49, 132, 0, 111, 117, 2, 115, 116, 0, 104, 8, 3, 117, 74, 0, 4, 8, 2, 101, 3, 117, 87, 0, 8, 2, 101, 114, 98, 105, 0, 8, 2, 105, 0, 101, 8, 2, 116, 105, 3, 117, 87, 127, 0, 4, 1, 102, 114, 117, 2, 101, 32, 3, 120, 87, 0, 1, 108, 97, 2, 101, 32, 0, 1, 108, 111, 115, 2, 101, 32, 0, 1, 109, 105, 2, 101, 32, 0, 1, 110, 21, 2, 101, 32, 0, 1, 114, 114, 2, 101, 32, 0, 104, 1, 121, 2, 116, 3, 122, 0, 4, 1, 118, 2, 97, 3, 136, 49, 0, 2, 111, 114, 110, 0, 8, 98, 2, 111, 0, 104, 101, 1, 100, 2, 32, 0, 104, 101, 1, 104, 2, 32, 0, 104, 101, 1, 107, 2, 32, 0, 104, 101, 1, 114, 2, 32, 0, 104, 101, 1, 116, 114, 2, 32, 0, 104, 101, 1, 121, 2, 32, 0, 104, 101, 8, 2, 12, 0, 114, 101, 8, 3, 136, 49, 13, 0, 4, 104, 101, 115, 1, 100, 2, 32, 3, 136, 49, 87, 0, 104, 101, 115, 1, 104, 2, 32, 0, 104, 101, 115, 1, 114, 2, 32, 0, 104, 101, 115, 1, 116, 114, 2, 32, 0, 4, 1, 112, 115, 2, 101, 13, 3, 136, 87, 0, 8, 114, 2, 101, 0, 8, 114, 2, 105, 115, 0, 101, 2, 32, 0, 7, 6, 97, 100, 0, 1, 115, 117, 114, 99, 3, 6, 136, 70, 0, 1, 108, 97, 109, 2, 121, 3, 13, 70, 0, 105, 111, 8, 114, 2, 21, 14, 128, 132, 133, 3, 34, 4, 136, 70, 120, 2, 134, 0, 2, 106, 117, 116, 97, 110, 3, 35, 0, 4, 1, 108, 103, 2, 105, 3, 35, 70, 0, 1, 114, 2, 105, 99, 0, 1, 120, 101, 104, 2, 101, 0, 2, 97, 103, 0, 2, 97, 109, 0, 2, 101, 110, 0, 2, 101, 113, 0, 2, 106, 117, 110, 99, 116, 32, 0, 2, 109, 97, 110, 32, 0, 2, 109, 105, 110, 32, 0, 2, 109, 105, 114, 97, 0, 2, 111, 108, 0, 2, 111, 110, 0, 2, 117, 108, 97, 0, 2, 118, 101, 110, 116, 0, 2, 118, 101, 114, 0, 2, 118, 101, 114, 116, 32, 0, 2, 118, 111, 0, 8, 2, 105, 0, 8, 2, 114, 105, 21, 0, 8, 2, 117, 109, 0, 100, 2, 101, 114, 0, 100, 2, 105, 116, 105, 118, 0, 100, 8, 2, 108, 0, 101, 1, 108, 2, 115, 104, 3, 35, 70, 6, 119, 0, 111, 2, 108, 101, 115, 3, 35, 70, 13, 0, 118, 101, 114, 2, 115, 3, 35, 70, 82, 6, 126, 0, 101, 113, 117, 97, 3, 35, 70, 120, 49, 58, 13, 0, 106, 101, 99, 3, 35, 73, 119, 49, 0, 4, 2, 118, 101, 110, 116, 117, 3, 117, 70, 0, 2, 118, 101, 114, 115, 97, 0, 2, 118, 101, 114, 116, 0, 8, 2, 21, 0, 8, 114, 116, 2, 105, 116, 0, 100, 8, 2, 21, 0, 97, 1, 99, 2, 118, 101, 114, 3, 117, 70, 35, 0, 106, 8, 3, 117, 73, 0, 1, 117, 113, 3, 122, 70, 0, 4, 1, 98, 2, 111, 115, 32, 3, 136, 70, 0, 1, 99, 2, 101, 110, 99, 0, 1, 108, 2, 101, 110, 0, 1, 108, 2, 121, 0, 1, 110, 114, 111, 116, 0, 1, 114, 99, 0, 1, 115, 2, 105, 115, 0, 2, 105, 17, 65, 0, 2, 108, 101, 0, 8, 114, 2, 17, 65, 0, 105, 1, 114, 2, 111, 18, 75, 12, 3, 136, 70, 120, 0, 7, 6, 97, 102, 0, 1, 21, 2, 116, 101, 114, 3, 6, 118, 81, 0, 4, 2, 114, 105, 3, 35, 81, 0, 8, 2, 103, 0, 102, 2, 97, 98, 0, 102, 2, 101, 114, 0, 102, 2, 108, 117, 0, 114, 111, 3, 35, 81, 34, 134, 0, 4, 2, 101, 97, 3, 117, 81, 0, 8, 2, 21, 0, 102, 8, 2, 21, 0, 111, 114, 101, 3, 117, 81, 131, 0, 102, 105, 97, 8, 3, 117, 81, 142, 0, 4, 2, 116, 12, 3, 118, 81, 0, 102, 1, 116, 115, 0, 102, 1, 119, 3, 122, 81, 0, 7, 6, 97, 103, 0, 8, 116, 110, 97, 3, 6, 35, 79, 0, 117, 97, 1, 21, 2, 32, 3, 6, 35, 79, 57, 132, 13, 0, 105, 111, 2, 32, 3, 6, 124, 73, 120, 134, 0, 2, 97, 32, 3, 6, 124, 79, 0, 105, 2, 32, 3, 6, 124, 79, 120, 0, 4, 1, 103, 110, 2, 101, 32, 3, 6, 136, 73, 0, 1, 114, 110, 101, 2, 101, 32, 0, 101, 1, 103, 2, 109, 101, 110, 116, 0, 104, 2, 32, 3, 13, 0, 1, 109, 2, 101, 110, 116, 97, 3, 13, 73, 0, 1, 10, 2, 111, 110, 32, 3, 13, 79, 0, 8, 114, 116, 3, 35, 73, 0, 4, 103, 8, 2, 114, 97, 118, 3, 35, 79, 0, 103, 8, 2, 114, 101, 103, 0, 4, 111, 110, 1, 114, 100, 3, 35, 79, 13, 50, 0, 111, 110, 1, 119, 2, 12, 0, 4, 101, 1, 21, 2, 32, 3, 111, 73, 0, 101, 1, 21, 2, 109, 101, 110, 116, 0, 101, 1, 112, 112, 2, 32, 0, 101, 114, 1, 21, 2, 32, 3, 111, 73, 112, 0, 2, 101, 110, 100, 3, 117, 73, 0, 4, 2, 114, 101, 101, 3, 117, 79, 0, 8, 2, 108, 21, 0, 8, 2, 111, 32, 0, 8, 2, 114, 111, 110, 0, 103, 2, 114, 101, 115, 0, 103, 2, 114, 105, 101, 118, 0, 103, 8, 2, 21, 0, 101, 110, 1, 104, 10, 2, 32, 3, 124, 79, 13, 50, 0, 4, 1, 116, 110, 111, 109, 2, 101, 32, 3, 124, 88, 0, 101, 1, 108, 102, 2, 32, 0, 4, 1, 110, 101, 101, 116, 2, 101, 3, 136, 73, 0, 1, 114, 101, 100, 2, 101, 32, 0, 1, 114, 116, 117, 111, 2, 101, 32, 0, 1, 116, 115, 2, 101, 0, 8, 2, 101, 0, 8, 2, 105, 115, 0, 101, 1, 99, 2, 32, 0, 101, 1, 99, 98, 0, 101, 1, 99, 100, 0, 101, 1, 112, 17, 67, 2, 32, 0, 101, 8, 2, 105, 0, 101, 8, 2, 108, 0, 105, 1, 116, 2, 111, 3, 136, 73, 57, 0, 4, 1, 108, 102, 2, 114, 97, 110, 3, 136, 79, 0, 1, 114, 102, 2, 114, 0, 1, 118, 2, 114, 97, 0, 2, 111, 32, 0, 117, 101, 0, 7, 6, 97, 105, 0, 4, 1, 21, 2, 17, 67, 97, 32, 3, 6, 136, 0, 1, 116, 110, 101, 2, 108, 0, 1, 116, 114, 117, 99, 2, 108, 0, 103, 2, 110, 0, 110, 1, 100, 2, 32, 3, 6, 136, 50, 0, 110, 101, 100, 1, 100, 2, 32, 3, 6, 136, 50, 70, 0, 115, 101, 2, 32, 3, 6, 136, 86, 0, 4, 99, 2, 32, 3, 6, 136, 120, 49, 0, 99, 2, 97, 108, 0, 114, 101, 3, 6, 138, 0, 4, 1, 108, 108, 105, 118, 3, 13, 0, 1, 116, 102, 0, 1, 116, 105, 114, 98, 0, 1, 116, 114, 101, 99, 0, 1, 116, 114, 117, 99, 0, 4, 115, 8, 2, 108, 105, 3, 35, 89, 0, 115, 8, 99, 2, 108, 0, 1, 115, 2, 100, 3, 119, 0, 4, 1, 103, 114, 97, 98, 3, 120, 0, 1, 108, 112, 97, 0, 1, 108, 114, 101, 98, 0, 1, 116, 110, 117, 111, 0, 1, 116, 112, 0, 4, 2, 32, 3, 135, 0, 2, 105, 0, 1, 110, 2, 118, 3, 135, 6, 127, 0, 4, 3, 136, 0, 8, 0, 115, 1, 108, 21, 2, 32, 0, 101, 3, 136, 13, 0, 4, 114, 3, 138, 0, 114, 8, 0, 114, 101, 2, 32, 0, 7, 6, 97, 108, 0, 1, 109, 2, 110, 111, 3, 2, 35, 55, 0, 2, 109, 105, 103, 3, 2, 122, 55, 0, 8, 2, 114, 3, 2, 128, 55, 0, 2, 105, 116, 121, 3, 6, 35, 55, 0, 100, 101, 2, 104, 121, 3, 6, 35, 55, 70, 120, 0, 103, 105, 97, 1, 21, 2, 32, 3, 6, 35, 55, 73, 13, 0, 4, 1, 103, 2, 105, 32, 3, 6, 124, 55, 0, 1, 122, 110, 111, 103, 0, 97, 110, 100, 1, 21, 2, 32, 3, 8, 13, 55, 117, 50, 70, 0, 4, 1, 10, 2, 105, 17, 66, 97, 116, 105, 3, 13, 55, 0, 1, 10, 2, 105, 17, 66, 101, 0, 1, 10, 2, 105, 115, 17, 67, 105, 99, 0, 1, 10, 2, 111, 117, 115, 32, 0, 1, 115, 2, 117, 116, 0, 1, 117, 113, 101, 0, 1, 118, 17, 65, 2, 101, 110, 0, 97, 121, 1, 109, 3, 13, 55, 6, 136, 0, 105, 1, 10, 2, 115, 17, 67, 32, 3, 13, 55, 120, 0, 111, 1, 10, 2, 32, 3, 13, 55, 134, 0, 101, 105, 1, 107, 2, 100, 3, 13, 55, 135, 0, 4, 5, 3, 1, 99, 2, 102, 3, 35, 0, 5, 3, 1, 104, 2, 102, 0, 5, 3, 1, 104, 2, 118, 0, 4, 1, 29, 2, 101, 100, 3, 35, 55, 0, 1, 112, 2, 101, 116, 0, 1, 115, 2, 117, 116, 97, 0, 1, 116, 101, 114, 2, 105, 97, 0, 1, 118, 2, 105, 97, 0, 2, 116, 111, 0, 2, 117, 109, 32, 0, 8, 2, 97, 115, 116, 0, 8, 2, 98, 0, 8, 2, 99, 0, 8, 2, 103, 0, 8, 2, 105, 0, 8, 2, 107, 0, 8, 2, 112, 0, 8, 2, 115, 0, 8, 2, 118, 0, 8, 2, 121, 0, 8, 99, 2, 101, 0, 108, 1, 102, 2, 97, 0, 108, 1, 102, 2, 105, 98, 0, 108, 1, 116, 2, 17, 65, 0, 108, 2, 101, 108, 0, 108, 2, 101, 114, 0, 108, 2, 111, 116, 114, 0, 108, 8, 2, 97, 0, 108, 8, 2, 101, 103, 0, 108, 8, 2, 105, 0, 108, 8, 2, 111, 0, 108, 8, 17, 67, 2, 111, 119, 0, 108, 111, 8, 2, 99, 97, 3, 35, 55, 13, 0, 97, 98, 97, 8, 3, 35, 55, 13, 69, 6, 35, 0, 122, 3, 35, 55, 47, 87, 0, 116, 105, 8, 3, 35, 55, 47, 120, 0, 112, 2, 104, 111, 3, 35, 55, 48, 0, 99, 111, 2, 104, 3, 35, 55, 49, 13, 0, 98, 101, 114, 8, 2, 116, 17, 65, 3, 35, 55, 69, 6, 126, 0, 4, 102, 97, 8, 3, 35, 55, 81, 13, 0, 112, 104, 97, 0, 101, 112, 104, 3, 35, 55, 119, 81, 0, 4, 108, 101, 121, 3, 35, 55, 120, 0, 108, 121, 1, 116, 0, 101, 120, 97, 110, 8, 3, 35, 55, 120, 79, 86, 6, 118, 50, 0, 108, 121, 8, 3, 35, 55, 135, 0, 4, 108, 121, 1, 21, 2, 32, 14, 128, 128, 130, 3, 55, 2, 37, 0, 108, 121, 1, 99, 21, 21, 2, 32, 14, 128, 128, 132, 0, 108, 121, 1, 99, 97, 2, 32, 0, 4, 1, 10, 2, 32, 3, 116, 0, 1, 10, 2, 100, 32, 0, 1, 10, 2, 116, 121, 32, 0, 114, 121, 1, 10, 2, 32, 3, 116, 34, 2, 120, 0, 4, 1, 104, 2, 117, 99, 105, 110, 3, 117, 55, 0, 2, 111, 110, 103, 0, 5, 8, 1, 10, 2, 32, 0, 8, 2, 21, 0, 8, 2, 105, 103, 0, 8, 99, 2, 97, 109, 105, 116, 0, 108, 2, 101, 103, 114, 0, 108, 8, 2, 21, 0, 108, 8, 2, 105, 97, 110, 0, 108, 8, 2, 105, 116, 101, 114, 0, 108, 8, 2, 111, 116, 0, 108, 8, 2, 111, 119, 0, 108, 101, 2, 103, 101, 3, 117, 55, 119, 0, 105, 8, 2, 17, 66, 101, 3, 117, 55, 135, 0, 4, 1, 102, 2, 107, 3, 122, 55, 0, 1, 102, 2, 115, 0, 1, 115, 2, 102, 0, 1, 115, 2, 116, 0, 1, 117, 113, 2, 21, 0, 1, 119, 2, 17, 67, 0, 2, 116, 17, 65, 114, 0, 2, 116, 32, 0, 8, 2, 109, 0, 8, 17, 67, 2, 116, 17, 65, 0, 8, 104, 2, 116, 0, 108, 1, 119, 2, 17, 65, 0, 108, 1, 119, 2, 97, 0, 108, 1, 119, 2, 101, 116, 0, 115, 111, 3, 122, 55, 87, 134, 0, 4, 1, 98, 2, 109, 3, 124, 0, 1, 99, 2, 102, 0, 1, 99, 2, 109, 0, 1, 104, 2, 102, 0, 1, 104, 2, 118, 0, 1, 112, 2, 109, 0, 1, 115, 112, 2, 109, 0, 1, 117, 113, 2, 109, 0, 8, 2, 109, 115, 0, 4, 1, 104, 99, 2, 107, 3, 128, 0, 1, 116, 2, 107, 0, 1, 119, 2, 107, 0, 4, 1, 98, 2, 100, 12, 3, 128, 55, 0, 1, 98, 2, 107, 0, 1, 116, 115, 2, 119, 0, 1, 116, 115, 110, 105, 2, 32, 0, 8, 2, 100, 0, 8, 2, 116, 0, 108, 1, 98, 2, 25, 0, 108, 1, 98, 10, 2, 101, 114, 32, 0, 108, 1, 99, 2, 25, 0, 108, 1, 99, 2, 105, 110, 0, 108, 1, 102, 0, 108, 1, 104, 2, 17, 67, 0, 108, 1, 109, 115, 0, 108, 1, 114, 104, 116, 0, 108, 1, 116, 0, 108, 1, 116, 2, 101, 0, 108, 1, 116, 115, 0, 108, 1, 119, 0, 108, 2, 32, 0, 108, 8, 2, 17, 67, 21, 14, 128, 132, 131, 0, 108, 101, 1, 119, 0, 108, 101, 114, 2, 32, 3, 128, 55, 112, 0, 108, 101, 114, 115, 2, 32, 3, 128, 55, 112, 86, 0, 2, 116, 101, 114, 110, 97, 116, 111, 3, 129, 55, 0, 119, 8, 3, 129, 55, 58, 0, 4, 1, 29, 2, 105, 110, 3, 136, 55, 0, 2, 105, 97, 0, 2, 105, 101, 110, 0, 8, 99, 115, 2, 17, 65, 0, 8, 104, 2, 111, 0, 101, 2, 32, 0, 101, 2, 104, 0, 7, 6, 97, 109, 0, 8, 2, 32, 3, 2, 35, 63, 0, 101, 8, 108, 2, 110, 116, 3, 2, 35, 63, 119, 0, 4, 1, 32, 15, 2, 32, 3, 4, 136, 6, 119, 63, 0, 1, 32, 32, 15, 2, 32, 0, 112, 116, 111, 110, 3, 6, 35, 63, 48, 47, 13, 50, 0, 4, 1, 114, 21, 2, 97, 32, 3, 6, 124, 63, 0, 2, 105, 32, 0, 101, 1, 115, 17, 65, 2, 32, 3, 6, 124, 63, 119, 0, 1, 103, 10, 2, 111, 117, 115, 3, 8, 117, 63, 0, 105, 110, 101, 1, 10, 2, 32, 3, 8, 117, 63, 127, 50, 0, 4, 1, 10, 2, 101, 110, 116, 3, 13, 63, 0, 1, 10, 2, 101, 110, 116, 0, 1, 10, 2, 111, 32, 0, 1, 100, 10, 2, 32, 0, 1, 100, 110, 117, 2, 101, 110, 0, 1, 115, 10, 2, 32, 0, 5, 35, 1, 104, 10, 2, 32, 24, 0, 101, 1, 10, 2, 110, 116, 97, 3, 13, 63, 6, 119, 0, 4, 1, 99, 2, 101, 108, 3, 35, 63, 0, 1, 100, 114, 101, 21, 2, 32, 0, 1, 108, 2, 112, 108, 0, 97, 116, 101, 117, 114, 3, 35, 63, 13, 47, 112, 0, 97, 122, 2, 111, 3, 35, 63, 13, 86, 0, 98, 105, 118, 3, 35, 63, 69, 6, 120, 82, 0, 98, 105, 2, 100, 3, 35, 63, 69, 120, 0, 112, 104, 105, 98, 3, 35, 63, 81, 6, 120, 69, 0, 105, 108, 1, 102, 3, 35, 63, 120, 55, 0, 4, 2, 117, 115, 101, 3, 117, 63, 0, 8, 2, 97, 108, 0, 8, 2, 101, 110, 0, 8, 2, 105, 100, 0, 8, 2, 105, 110, 111, 0, 8, 2, 105, 115, 115, 0, 8, 2, 111, 114, 17, 67, 0, 109, 2, 101, 110, 100, 0, 101, 8, 2, 110, 116, 3, 117, 63, 119, 0, 101, 114, 2, 105, 99, 3, 117, 63, 119, 34, 0, 4, 101, 2, 110, 97, 98, 3, 117, 63, 127, 0, 101, 8, 2, 108, 0, 105, 2, 103, 0, 111, 101, 98, 3, 117, 63, 127, 69, 0, 97, 122, 3, 117, 63, 136, 86, 0, 4, 1, 17, 67, 2, 100, 3, 118, 63, 0, 1, 17, 67, 2, 112, 108, 0, 4, 1, 102, 2, 111, 117, 115, 3, 136, 63, 0, 1, 104, 99, 2, 98, 0, 8, 100, 2, 105, 0, 101, 1, 108, 102, 0, 101, 8, 110, 0, 7, 6, 97, 110, 0, 8, 114, 116, 2, 115, 3, 2, 35, 50, 0, 115, 102, 101, 114, 1, 114, 116, 3, 2, 35, 50, 87, 81, 126, 0, 116, 105, 8, 2, 21, 14, 128, 132, 132, 3, 4, 35, 50, 47, 120, 0, 100, 117, 1, 21, 2, 32, 3, 4, 35, 50, 70, 6, 132, 0, 4, 1, 21, 2, 17, 67, 97, 32, 3, 6, 35, 50, 0, 1, 103, 97, 112, 111, 114, 112, 2, 100, 0, 1, 110, 105, 102, 2, 99, 0, 2, 103, 117, 108, 0, 2, 122, 97, 0, 100, 111, 2, 32, 3, 6, 35, 50, 70, 134, 0, 97, 1, 21, 2, 32, 3, 6, 124, 50, 13, 0, 105, 1, 10, 2, 32, 3, 6, 124, 50, 120, 0, 2, 105, 97, 3, 6, 136, 50, 0, 105, 97, 2, 99, 32, 3, 6, 136, 50, 120, 35, 0, 101, 97, 110, 2, 32, 3, 6, 136, 50, 139, 50, 0, 101, 111, 117, 115, 1, 21, 3, 6, 136, 50, 139, 87, 0, 4, 1, 10, 2, 32, 3, 13, 50, 0, 1, 10, 2, 99, 101, 32, 0, 1, 10, 2, 99, 121, 0, 1, 10, 2, 101, 115, 101, 0, 1, 10, 2, 105, 101, 32, 0, 1, 10, 2, 105, 101, 115, 32, 0, 1, 10, 2, 116, 32, 0, 1, 10, 2, 116, 121, 32, 0, 1, 10, 2, 121, 32, 0, 1, 98, 115, 117, 2, 100, 0, 1, 104, 112, 2, 97, 103, 101, 0, 1, 108, 10, 2, 100, 0, 1, 108, 108, 2, 32, 0, 1, 109, 10, 2, 32, 0, 1, 109, 114, 101, 112, 0, 1, 109, 117, 104, 2, 32, 0, 1, 114, 21, 21, 2, 32, 0, 110, 1, 10, 2, 105, 101, 32, 0, 105, 112, 117, 1, 109, 3, 13, 50, 120, 48, 57, 115, 0, 111, 101, 117, 1, 109, 2, 118, 3, 13, 50, 132, 0, 4, 1, 99, 2, 99, 3, 35, 50, 0, 1, 99, 17, 67, 2, 32, 0, 1, 102, 2, 99, 0, 1, 108, 2, 32, 0, 1, 108, 10, 2, 100, 105, 0, 1, 108, 112, 2, 116, 32, 0, 1, 108, 121, 2, 100, 0, 1, 109, 2, 32, 0, 1, 110, 2, 99, 0, 1, 112, 2, 32, 0, 1, 112, 2, 99, 0, 1, 112, 2, 101, 108, 0, 1, 112, 115, 2, 105, 97, 0, 1, 114, 116, 2, 32, 0, 1, 114, 116, 2, 115, 105, 0, 1, 114, 116, 2, 115, 111, 109, 0, 1, 116, 115, 2, 32, 0, 1, 118, 100, 97, 2, 99, 0, 8, 108, 2, 105, 97, 0, 8, 119, 2, 103, 0, 8, 119, 2, 107, 0, 110, 97, 8, 3, 35, 50, 13, 0, 116, 8, 2, 105, 113, 12, 3, 35, 50, 47, 0, 116, 101, 2, 110, 110, 3, 35, 50, 47, 6, 119, 0, 116, 105, 2, 99, 105, 3, 35, 50, 47, 6, 120, 0, 103, 2, 101, 108, 3, 35, 50, 73, 0, 115, 105, 115, 1, 114, 116, 3, 35, 50, 86, 6, 120, 87, 0, 101, 8, 2, 115, 3, 35, 50, 120, 0, 103, 1, 104, 2, 101, 114, 3, 35, 66, 0, 103, 2, 101, 114, 3, 35, 66, 79, 0, 103, 101, 108, 1, 109, 3, 35, 66, 79, 116, 0, 4, 1, 105, 21, 2, 32, 14, 128, 128, 129, 3, 50, 0, 1, 117, 21, 2, 32, 14, 128, 128, 129, 0, 103, 101, 100, 1, 114, 2, 14, 128, 128, 129, 3, 70, 0, 4, 2, 97, 108, 111, 103, 3, 117, 50, 0, 2, 97, 116, 104, 0, 5, 8, 1, 10, 2, 32, 0, 5, 8, 1, 10, 2, 99, 101, 32, 0, 5, 8, 1, 10, 2, 116, 32, 0, 5, 8, 1, 109, 10, 2, 32, 0, 8, 2, 101, 109, 0, 8, 2, 111, 105, 0, 110, 2, 101, 97, 108, 0, 110, 2, 105, 104, 0, 110, 2, 111, 117, 110, 0, 110, 2, 117, 105, 0, 110, 2, 117, 108, 0, 110, 2, 117, 110, 0, 110, 8, 2, 111, 121, 0, 105, 97, 1, 122, 3, 117, 50, 6, 139, 0, 111, 109, 8, 3, 117, 50, 122, 63, 0, 101, 8, 2, 109, 105, 3, 117, 50, 127, 0, 105, 97, 2, 99, 3, 117, 50, 142, 0, 4, 1, 17, 67, 2, 99, 3, 118, 50, 0, 1, 17, 67, 2, 116, 0, 1, 104, 2, 99, 101, 32, 0, 1, 108, 115, 2, 100, 0, 1, 109, 21, 2, 100, 0, 1, 122, 2, 99, 101, 32, 0, 115, 119, 2, 101, 114, 3, 118, 50, 87, 0, 121, 8, 3, 119, 50, 111, 0, 4, 1, 119, 2, 116, 32, 3, 122, 50, 0, 8, 117, 113, 0, 8, 119, 2, 17, 67, 0, 8, 2, 99, 105, 101, 3, 136, 50, 0, 4, 103, 1, 100, 2, 101, 114, 3, 136, 50, 73, 0, 103, 1, 104, 99, 2, 101, 0, 103, 1, 114, 2, 101, 0, 103, 2, 101, 108, 32, 0, 4, 103, 105, 110, 103, 1, 104, 99, 3, 136, 50, 73, 120, 66, 0, 103, 105, 110, 103, 1, 114, 0, 7, 6, 97, 112, 0, 104, 1, 114, 103, 10, 2, 121, 3, 8, 13, 81, 0, 104, 101, 114, 1, 114, 103, 10, 3, 8, 13, 81, 112, 0, 1, 99, 2, 97, 99, 3, 13, 48, 0, 101, 1, 114, 116, 2, 122, 3, 13, 48, 127, 0, 4, 2, 97, 116, 104, 3, 35, 48, 0, 2, 101, 108, 32, 0, 2, 105, 99, 0, 2, 111, 103, 0, 2, 111, 108, 105, 0, 8, 2, 115, 0, 8, 2, 116, 0, 112, 2, 97, 114, 97, 0, 112, 2, 101, 116, 105, 0, 112, 2, 108, 101, 0, 112, 2, 108, 105, 99, 0, 112, 2, 114, 101, 104, 0, 101, 114, 8, 2, 116, 3, 35, 48, 13, 0, 114, 101, 115, 3, 35, 48, 34, 136, 0, 101, 1, 114, 116, 2, 122, 111, 3, 35, 48, 120, 0, 104, 8, 2, 111, 3, 35, 81, 0, 104, 114, 111, 3, 35, 81, 34, 13, 0, 4, 8, 2, 21, 3, 117, 48, 0, 112, 2, 101, 97, 114, 0, 112, 2, 108, 105, 99, 97, 98, 0, 112, 8, 2, 21, 0, 112, 114, 101, 99, 8, 2, 18, 67, 3, 117, 48, 34, 127, 89, 0, 101, 114, 105, 8, 2, 116, 3, 117, 48, 119, 34, 13, 0, 101, 114, 2, 105, 101, 3, 117, 48, 139, 34, 0, 104, 8, 2, 21, 3, 117, 81, 0, 4, 1, 99, 2, 111, 110, 3, 136, 48, 0, 1, 109, 2, 108, 101, 0, 1, 112, 2, 101, 114, 0, 1, 116, 115, 2, 108, 0, 2, 105, 97, 0, 2, 105, 115, 0, 2, 114, 111, 0, 8, 2, 101, 0, 8, 2, 114, 105, 0, 8, 112, 2, 105, 115, 0, 8, 118, 2, 111, 0, 104, 8, 2, 105, 100, 3, 136, 81, 0, 7, 6, 97, 114, 0, 8, 2, 116, 105, 108, 3, 2, 125, 0, 98, 111, 1, 99, 2, 104, 3, 4, 125, 69, 134, 0, 99, 104, 8, 2, 21, 14, 128, 132, 132, 3, 4, 125, 74, 0, 5, 3, 1, 21, 2, 105, 111, 32, 3, 6, 35, 34, 0, 105, 108, 121, 1, 21, 2, 32, 3, 6, 119, 34, 13, 55, 2, 120, 0, 4, 2, 97, 32, 3, 6, 124, 34, 0, 2, 105, 32, 0, 4, 2, 105, 97, 17, 67, 32, 3, 6, 138, 0, 2, 105, 97, 32, 0, 2, 105, 117, 12, 3, 6, 138, 34, 0, 4, 1, 10, 2, 105, 110, 32, 3, 13, 34, 0, 1, 103, 111, 108, 2, 105, 0, 1, 104, 2, 97, 115, 115, 0, 1, 109, 2, 105, 0, 1, 109, 2, 105, 110, 0, 8, 116, 97, 107, 0, 121, 1, 10, 2, 32, 3, 13, 34, 2, 37, 0, 97, 110, 1, 109, 10, 3, 13, 34, 35, 50, 0, 101, 1, 112, 2, 110, 116, 104, 101, 3, 13, 34, 119, 0, 105, 115, 101, 1, 10, 2, 32, 3, 13, 34, 135, 86, 0, 97, 8, 112, 2, 100, 101, 3, 13, 34, 136, 0, 105, 110, 103, 1, 103, 3, 13, 44, 111, 66, 0, 2, 114, 3, 35, 0, 4, 1, 21, 2, 105, 116, 121, 3, 35, 34, 0, 1, 99, 2, 101, 101, 114, 0, 1, 99, 2, 105, 0, 1, 104, 99, 2, 105, 116, 0, 1, 104, 112, 2, 105, 0, 1, 107, 2, 121, 0, 1, 108, 99, 2, 105, 0, 1, 109, 2, 105, 110, 101, 114, 0, 1, 109, 2, 105, 111, 0, 1, 109, 2, 105, 116, 0, 1, 112, 2, 105, 0, 1, 112, 112, 2, 101, 110, 17, 67, 0, 1, 112, 115, 2, 101, 110, 17, 67, 0, 2, 97, 0, 2, 101, 110, 0, 2, 105, 99, 0, 2, 111, 0, 8, 2, 17, 65, 0, 8, 98, 2, 18, 67, 116, 0, 8, 109, 2, 105, 0, 8, 109, 2, 105, 110, 97, 17, 67, 0, 114, 8, 2, 97, 110, 116, 0, 114, 8, 2, 111, 0, 4, 97, 8, 112, 3, 35, 34, 13, 0, 101, 2, 116, 0, 114, 111, 8, 2, 103, 0, 4, 1, 10, 2, 100, 105, 115, 3, 112, 0, 1, 10, 2, 100, 105, 122, 0, 1, 10, 2, 100, 121, 32, 0, 1, 100, 10, 2, 32, 0, 1, 100, 10, 2, 100, 32, 0, 1, 103, 10, 2, 32, 0, 1, 103, 103, 2, 100, 32, 0, 1, 104, 10, 2, 100, 32, 0, 1, 104, 99, 10, 2, 100, 0, 1, 107, 10, 2, 100, 32, 0, 1, 108, 10, 2, 32, 0, 1, 108, 10, 2, 105, 115, 116, 0, 1, 109, 10, 2, 32, 0, 1, 112, 2, 116, 105, 99, 117, 0, 1, 112, 10, 2, 100, 32, 0, 1, 116, 10, 2, 32, 0, 1, 116, 115, 10, 2, 100, 32, 0, 1, 119, 2, 100, 0, 1, 119, 10, 2, 100, 32, 0, 1, 122, 10, 2, 100, 32, 0, 2, 100, 114, 121, 0, 1, 112, 101, 115, 2, 97, 116, 3, 112, 34, 0, 4, 99, 104, 1, 110, 97, 3, 112, 49, 0, 99, 104, 1, 110, 111, 109, 0, 4, 8, 2, 111, 115, 3, 117, 34, 0, 8, 2, 111, 117, 0, 114, 8, 2, 21, 0, 97, 99, 104, 8, 3, 117, 34, 35, 49, 0, 111, 109, 2, 97, 116, 3, 117, 34, 134, 63, 0, 121, 5, 3, 1, 110, 111, 105, 2, 32, 3, 119, 34, 2, 37, 0, 4, 1, 117, 113, 2, 114, 3, 122, 0, 1, 119, 2, 114, 0, 1, 119, 2, 114, 0, 4, 1, 117, 113, 2, 97, 3, 122, 34, 0, 119, 1, 119, 2, 105, 0, 2, 17, 65, 3, 124, 34, 0, 4, 3, 125, 0, 1, 104, 2, 100, 121, 32, 0, 1, 116, 105, 117, 103, 2, 32, 0, 1, 116, 111, 101, 2, 100, 32, 0, 1, 116, 115, 2, 32, 0, 2, 32, 0, 8, 116, 2, 32, 0, 39, 2, 110, 116, 0, 114, 2, 32, 0, 114, 101, 2, 32, 0, 4, 99, 104, 1, 21, 2, 105, 3, 125, 49, 0, 99, 104, 1, 21, 2, 121, 0, 99, 104, 8, 2, 17, 65, 17, 65, 0, 99, 104, 8, 2, 101, 116, 0, 99, 104, 97, 105, 8, 3, 125, 49, 6, 136, 120, 0, 99, 104, 105, 8, 2, 21, 3, 125, 49, 120, 0, 99, 104, 105, 118, 8, 2, 12, 3, 125, 49, 135, 82, 0, 108, 105, 97, 8, 112, 3, 125, 55, 13, 0, 114, 101, 100, 2, 32, 3, 125, 70, 0, 99, 104, 8, 2, 101, 114, 3, 125, 74, 0, 114, 105, 110, 103, 2, 32, 3, 125, 111, 66, 0, 4, 1, 104, 119, 3, 130, 0, 1, 117, 113, 2, 116, 0, 1, 119, 0, 1, 119, 97, 2, 100, 0, 1, 119, 101, 114, 2, 100, 0, 1, 119, 104, 99, 2, 100, 0, 1, 119, 115, 2, 100, 0, 8, 119, 2, 100, 0, 1, 119, 111, 116, 2, 100, 3, 131, 0, 4, 1, 109, 116, 104, 3, 138, 0, 1, 112, 2, 105, 110, 0, 1, 119, 2, 105, 0, 1, 119, 2, 121, 0, 2, 105, 111, 117, 115, 0, 8, 109, 2, 121, 0, 101, 0, 101, 1, 99, 2, 17, 67, 21, 0, 101, 1, 119, 0, 4, 1, 112, 2, 101, 110, 116, 3, 138, 34, 0, 1, 117, 2, 105, 115, 104, 0, 1, 118, 2, 105, 17, 65, 0, 121, 1, 17, 67, 29, 2, 32, 3, 138, 34, 2, 37, 0, 101, 115, 116, 2, 32, 3, 138, 34, 13, 87, 47, 0, 4, 121, 5, 3, 1, 17, 65, 21, 21, 2, 32, 3, 138, 34, 37, 0, 121, 5, 3, 1, 17, 67, 17, 65, 21, 21, 2, 32, 0, 101, 97, 3, 138, 34, 139, 0, 105, 110, 103, 3, 138, 44, 111, 66, 0, 7, 6, 97, 115, 0, 2, 101, 120, 117, 3, 2, 136, 87, 0, 2, 105, 118, 101, 3, 6, 136, 87, 0, 4, 115, 1, 99, 10, 2, 32, 3, 13, 87, 0, 115, 1, 108, 116, 10, 2, 32, 0, 115, 1, 112, 109, 111, 2, 32, 0, 115, 1, 112, 115, 10, 2, 32, 0, 115, 1, 114, 114, 0, 115, 1, 118, 10, 2, 32, 0, 115, 1, 118, 10, 2, 32, 0, 4, 101, 121, 1, 10, 2, 32, 3, 13, 87, 2, 37, 0, 121, 1, 10, 2, 32, 0, 115, 2, 117, 3, 13, 89, 0, 115, 117, 114, 3, 13, 89, 57, 141, 0, 1, 98, 2, 105, 108, 3, 35, 86, 0, 4, 1, 109, 2, 111, 110, 105, 3, 35, 87, 0, 1, 116, 110, 2, 116, 0, 2, 112, 104, 97, 0, 2, 112, 105, 0, 2, 116, 104, 109, 0, 2, 116, 114, 97, 108, 0, 2, 116, 114, 111, 0, 2, 121, 109, 112, 0, 8, 2, 101, 0, 8, 2, 105, 110, 0, 8, 2, 112, 101, 0, 115, 1, 108, 99, 2, 105, 17, 67, 0, 115, 1, 112, 2, 111, 0, 115, 2, 97, 103, 0, 115, 2, 101, 116, 0, 115, 2, 111, 110, 0, 115, 2, 121, 109, 0, 115, 8, 2, 104, 0, 99, 105, 105, 3, 35, 87, 49, 120, 0, 104, 8, 3, 35, 89, 0, 115, 105, 111, 110, 1, 112, 3, 35, 89, 13, 50, 0, 99, 105, 1, 102, 2, 115, 3, 35, 89, 120, 0, 2, 115, 105, 115, 116, 3, 117, 0, 4, 1, 10, 2, 116, 121, 32, 3, 117, 87, 0, 2, 116, 101, 114, 110, 0, 2, 116, 114, 111, 108, 111, 103, 0, 2, 116, 114, 111, 110, 111, 0, 8, 2, 21, 0, 8, 2, 112, 101, 114, 0, 8, 2, 112, 105, 114, 101, 0, 115, 2, 117, 109, 112, 0, 115, 8, 2, 21, 0, 4, 104, 8, 2, 97, 3, 117, 89, 0, 104, 8, 2, 111, 0, 4, 1, 17, 67, 2, 112, 3, 118, 87, 0, 1, 17, 67, 2, 112, 101, 0, 1, 17, 67, 2, 116, 0, 2, 107, 0, 2, 116, 101, 114, 0, 8, 2, 107, 0, 115, 1, 108, 17, 67, 0, 115, 1, 112, 0, 115, 1, 114, 17, 67, 0, 1, 104, 99, 114, 117, 112, 2, 101, 3, 120, 87, 0, 1, 119, 2, 112, 3, 122, 87, 0, 4, 101, 1, 104, 112, 2, 32, 3, 136, 86, 0, 101, 1, 114, 2, 32, 0, 4, 1, 98, 2, 105, 3, 136, 87, 0, 1, 104, 2, 116, 101, 0, 1, 106, 2, 111, 110, 0, 1, 109, 2, 111, 110, 0, 1, 112, 2, 116, 101, 32, 0, 1, 116, 2, 116, 0, 8, 2, 111, 0, 116, 1, 119, 2, 101, 13, 3, 136, 87, 47, 0, 105, 97, 5, 3, 8, 3, 136, 88, 13, 0, 99, 1, 102, 2, 105, 97, 3, 136, 89, 0, 105, 97, 8, 3, 136, 89, 13, 0, 7, 6, 97, 116, 0, 111, 8, 2, 110, 97, 3, 2, 136, 47, 134, 0, 4, 1, 21, 2, 114, 97, 32, 3, 6, 124, 47, 0, 2, 117, 109, 0, 105, 1, 21, 2, 32, 3, 6, 124, 47, 120, 0, 4, 1, 21, 2, 111, 114, 32, 3, 6, 136, 47, 0, 1, 100, 2, 117, 109, 32, 0, 1, 108, 117, 2, 111, 114, 121, 0, 1, 109, 2, 117, 109, 32, 0, 2, 105, 109, 32, 0, 114, 105, 99, 101, 115, 3, 6, 136, 47, 34, 111, 87, 127, 86, 0, 114, 105, 120, 3, 6, 136, 47, 34, 120, 49, 87, 0, 105, 2, 97, 29, 3, 6, 136, 89, 0, 114, 121, 1, 21, 2, 32, 3, 8, 13, 47, 34, 120, 0, 104, 1, 21, 2, 105, 115, 3, 8, 13, 85, 0, 104, 121, 1, 10, 3, 8, 13, 85, 111, 0, 4, 1, 10, 2, 101, 101, 114, 32, 3, 13, 47, 0, 1, 10, 2, 105, 118, 101, 0, 1, 109, 2, 101, 114, 105, 0, 1, 109, 105, 108, 99, 2, 101, 0, 1, 110, 101, 115, 0, 1, 112, 2, 101, 114, 110, 0, 1, 116, 115, 2, 105, 115, 116, 0, 8, 115, 114, 101, 118, 0, 101, 1, 10, 2, 32, 28, 18, 0, 101, 1, 108, 97, 112, 2, 32, 0, 101, 1, 108, 117, 99, 97, 109, 2, 32, 0, 101, 1, 108, 117, 115, 110, 111, 99, 2, 32, 0, 101, 1, 109, 105, 116, 2, 32, 0, 101, 1, 110, 105, 100, 2, 32, 0, 101, 1, 110, 111, 105, 2, 32, 0, 101, 1, 114, 101, 100, 2, 32, 0, 101, 1, 114, 101, 112, 109, 2, 32, 0, 101, 8, 114, 97, 112, 101, 115, 32, 116, 105, 2, 32, 0, 111, 114, 121, 1, 10, 3, 13, 47, 112, 34, 37, 0, 105, 115, 109, 1, 10, 3, 13, 47, 120, 86, 13, 63, 0, 101, 114, 1, 109, 2, 110, 3, 13, 47, 126, 0, 111, 114, 121, 5, 3, 1, 10, 3, 13, 47, 147, 34, 37, 0, 117, 114, 101, 1, 108, 2, 32, 3, 13, 74, 112, 0, 4, 117, 114, 1, 99, 3, 13, 74, 141, 0, 117, 114, 1, 109, 0, 4, 1, 99, 2, 101, 17, 67, 3, 35, 47, 0, 1, 103, 2, 101, 97, 117, 0, 1, 108, 112, 2, 101, 97, 0, 1, 109, 2, 101, 114, 0, 1, 114, 116, 115, 2, 101, 103, 0, 8, 107, 2, 101, 114, 0, 116, 2, 105, 99, 0, 116, 2, 105, 116, 0, 101, 8, 115, 2, 108, 108, 3, 35, 47, 13, 0, 101, 103, 111, 1, 99, 2, 114, 105, 99, 3, 35, 47, 120, 79, 6, 122, 0, 101, 103, 111, 1, 99, 3, 35, 47, 120, 79, 13, 0, 105, 8, 99, 2, 111, 110, 3, 35, 47, 135, 0, 104, 2, 108, 111, 110, 3, 35, 85, 0, 4, 1, 114, 102, 2, 101, 114, 110, 3, 117, 47, 0, 2, 111, 109, 105, 0, 8, 2, 108, 97, 110, 0, 8, 2, 114, 111, 99, 0, 116, 8, 2, 21, 0, 114, 111, 108, 1, 112, 3, 117, 47, 34, 134, 55, 0, 111, 8, 2, 110, 3, 117, 47, 134, 0, 4, 104, 1, 98, 3, 118, 85, 0, 104, 1, 112, 0, 1, 119, 2, 116, 3, 122, 47, 0, 104, 1, 102, 2, 101, 114, 3, 124, 84, 0, 4, 1, 21, 21, 2, 111, 114, 32, 3, 136, 47, 0, 1, 99, 2, 101, 114, 32, 0, 1, 102, 2, 97, 108, 0, 1, 108, 98, 2, 17, 65, 0, 1, 110, 2, 105, 118, 101, 0, 2, 111, 114, 32, 0, 5, 3, 1, 112, 2, 114, 105, 17, 65, 0, 101, 1, 110, 111, 105, 110, 2, 32, 0, 97, 1, 100, 3, 136, 47, 13, 0, 114, 111, 110, 2, 32, 3, 136, 47, 34, 13, 50, 0, 101, 115, 1, 114, 97, 112, 2, 32, 3, 136, 47, 87, 0, 101, 100, 1, 109, 105, 116, 2, 32, 3, 136, 47, 111, 70, 0, 111, 114, 8, 103, 3, 136, 47, 112, 0, 4, 105, 110, 103, 1, 21, 2, 12, 12, 32, 3, 136, 47, 120, 66, 0, 105, 110, 103, 1, 109, 105, 116, 2, 32, 0, 101, 100, 1, 21, 2, 12, 12, 32, 3, 136, 47, 120, 70, 0, 104, 1, 98, 2, 101, 3, 136, 84, 0, 104, 101, 100, 2, 32, 3, 136, 84, 70, 0, 104, 101, 105, 3, 136, 85, 111, 120, 0, 2, 105, 97, 3, 136, 89, 0, 7, 6, 97, 117, 0, 116, 111, 8, 2, 110, 3, 2, 128, 47, 122, 0, 103, 109, 101, 110, 116, 3, 2, 128, 79, 63, 119, 50, 47, 0, 116, 104, 101, 110, 3, 2, 128, 85, 119, 50, 0, 99, 104, 8, 3, 2, 128, 99, 0, 116, 111, 8, 2, 21, 14, 128, 132, 132, 3, 4, 128, 47, 134, 0, 4, 1, 21, 2, 114, 105, 3, 6, 128, 0, 1, 115, 2, 114, 117, 115, 32, 0, 100, 2, 32, 3, 6, 128, 70, 0, 8, 2, 110, 116, 3, 118, 0, 4, 103, 104, 1, 108, 3, 118, 81, 0, 103, 104, 1, 114, 100, 0, 4, 1, 99, 2, 108, 105, 3, 122, 0, 5, 35, 1, 115, 2, 115, 0, 5, 35, 2, 115, 116, 114, 0, 108, 2, 116, 3, 122, 55, 0, 4, 3, 128, 0, 1, 110, 2, 116, 32, 0, 103, 104, 0, 103, 104, 1, 108, 115, 0, 108, 2, 107, 0, 116, 111, 2, 109, 97, 3, 128, 47, 13, 0, 114, 2, 32, 3, 130, 0, 4, 1, 21, 2, 116, 32, 3, 133, 0, 1, 103, 2, 115, 0, 2, 32, 0, 115, 1, 17, 67, 2, 32, 3, 133, 87, 0, 2, 118, 3, 134, 0, 7, 6, 97, 118, 0, 1, 108, 97, 2, 101, 114, 3, 6, 124, 82, 0, 4, 1, 99, 115, 2, 101, 110, 3, 35, 82, 0, 1, 100, 2, 101, 110, 0, 1, 106, 2, 101, 108, 0, 1, 108, 2, 101, 110, 0, 1, 108, 2, 105, 0, 1, 114, 2, 101, 108, 0, 101, 114, 8, 2, 115, 3, 35, 82, 6, 126, 0, 97, 114, 2, 105, 99, 3, 35, 82, 13, 34, 0, 4, 2, 97, 105, 108, 3, 117, 82, 0, 2, 101, 110, 103, 0, 2, 111, 17, 65, 0, 8, 2, 101, 114, 17, 67, 0, 111, 119, 3, 117, 82, 133, 0, 4, 1, 106, 2, 97, 3, 124, 82, 0, 1, 108, 115, 2, 105, 0, 4, 1, 100, 2, 105, 100, 3, 136, 82, 0, 1, 102, 2, 111, 0, 1, 108, 102, 2, 111, 0, 1, 115, 2, 105, 0, 1, 115, 2, 111, 0, 8, 2, 111, 110, 0, 105, 8, 2, 17, 65, 3, 136, 82, 120, 0, 7, 6, 98, 101, 0, 103, 8, 2, 17, 65, 110, 25, 3, 69, 2, 120, 79, 0, 116, 97, 8, 3, 69, 4, 127, 47, 13, 0, 116, 97, 5, 3, 8, 3, 69, 4, 136, 47, 13, 0, 110, 101, 118, 111, 3, 69, 13, 50, 119, 82, 13, 0, 4, 2, 103, 17, 65, 3, 69, 111, 0, 2, 103, 114, 0, 2, 108, 97, 116, 0, 2, 108, 105, 101, 0, 2, 109, 117, 0, 2, 113, 117, 0, 2, 115, 101, 101, 0, 2, 115, 105, 101, 0, 2, 116, 114, 97, 121, 0, 8, 2, 17, 67, 17, 65, 0, 8, 2, 99, 108, 0, 8, 2, 100, 114, 97, 0, 8, 2, 102, 0, 8, 2, 108, 108, 105, 0, 8, 2, 115, 17, 67, 0, 8, 2, 115, 116, 111, 0, 8, 2, 116, 17, 67, 0, 8, 2, 119, 0, 104, 97, 2, 118, 3, 69, 111, 105, 136, 0, 114, 8, 2, 115, 3, 69, 112, 0, 4, 8, 2, 17, 67, 11, 3, 69, 119, 0, 8, 2, 99, 107, 0, 8, 2, 99, 113, 0, 8, 2, 100, 17, 67, 0, 8, 2, 103, 103, 0, 8, 2, 108, 17, 67, 0, 8, 2, 115, 116, 105, 97, 0, 8, 2, 116, 104, 0, 8, 2, 118, 17, 65, 0, 110, 101, 8, 3, 69, 119, 50, 120, 0, 4, 100, 1, 104, 2, 32, 3, 69, 119, 70, 0, 100, 1, 114, 101, 2, 32, 0, 100, 1, 116, 2, 32, 0, 4, 1, 121, 97, 109, 2, 32, 3, 69, 127, 0, 8, 2, 98, 0, 7, 6, 98, 105, 0, 8, 2, 17, 67, 21, 21, 3, 2, 69, 135, 0, 4, 2, 115, 101, 99, 3, 69, 2, 135, 0, 8, 2, 101, 110, 0, 111, 8, 2, 21, 14, 128, 132, 131, 3, 69, 4, 135, 134, 0, 2, 110, 111, 99, 3, 69, 111, 0, 4, 2, 98, 108, 105, 3, 69, 120, 0, 2, 98, 117, 0, 2, 99, 107, 0, 2, 103, 12, 0, 2, 108, 105, 111, 0, 2, 110, 109, 0, 2, 111, 17, 67, 32, 0, 2, 111, 117, 115, 0, 2, 114, 105, 0, 2, 114, 121, 0, 2, 115, 99, 0, 2, 115, 104, 0, 2, 115, 109, 0, 2, 116, 117, 0, 2, 122, 12, 0, 8, 2, 17, 67, 11, 0, 8, 2, 108, 17, 67, 0, 8, 2, 110, 103, 0, 8, 2, 116, 17, 67, 0, 114, 2, 17, 67, 3, 69, 126, 0, 4, 2, 115, 113, 3, 69, 127, 0, 2, 115, 116, 114, 0, 4, 1, 21, 2, 111, 115, 17, 65, 3, 69, 135, 0, 1, 111, 2, 116, 17, 65, 0, 2, 99, 121, 99, 0, 2, 107, 101, 114, 0, 2, 110, 97, 114, 121, 0, 2, 110, 100, 0, 2, 111, 116, 105, 99, 0, 8, 2, 32, 0, 8, 2, 111, 18, 75, 12, 0, 103, 104, 2, 116, 0, 4, 111, 2, 110, 105, 3, 69, 135, 6, 122, 0, 111, 2, 112, 115, 0, 111, 3, 69, 135, 134, 0, 114, 5, 5, 2, 17, 67, 3, 69, 145, 0, 7, 6, 99, 104, 0, 101, 109, 101, 110, 116, 2, 32, 3, 8, 89, 63, 149, 0, 4, 1, 21, 2, 105, 97, 3, 49, 0, 1, 97, 2, 105, 108, 0, 1, 97, 114, 98, 0, 1, 97, 114, 116, 0, 1, 101, 2, 111, 0, 1, 101, 109, 2, 97, 0, 1, 101, 116, 2, 25, 0, 1, 105, 109, 2, 97, 0, 1, 110, 111, 114, 98, 0, 1, 111, 2, 32, 0, 1, 114, 97, 2, 105, 118, 101, 0, 1, 114, 97, 17, 67, 21, 21, 2, 32, 0, 1, 114, 111, 2, 105, 0, 2, 97, 101, 0, 2, 97, 115, 109, 0, 2, 101, 109, 0, 2, 105, 99, 32, 0, 2, 105, 111, 0, 2, 105, 114, 17, 65, 0, 2, 105, 115, 17, 67, 0, 2, 111, 108, 0, 2, 111, 110, 100, 0, 2, 111, 114, 17, 65, 0, 2, 111, 114, 100, 0, 2, 114, 0, 8, 2, 18, 66, 17, 71, 0, 8, 97, 116, 0, 8, 114, 97, 2, 17, 65, 0, 8, 114, 97, 2, 97, 0, 8, 114, 111, 2, 101, 115, 0, 4, 97, 2, 114, 105, 115, 3, 49, 13, 0, 111, 114, 1, 110, 97, 0, 114, 121, 2, 115, 97, 3, 49, 34, 120, 0, 108, 111, 114, 111, 3, 49, 55, 4, 131, 34, 134, 0, 108, 111, 2, 114, 3, 49, 55, 131, 0, 111, 105, 114, 3, 49, 58, 143, 0, 105, 8, 114, 97, 2, 21, 3, 49, 120, 0, 97, 8, 2, 111, 3, 49, 136, 0, 97, 111, 115, 3, 49, 136, 122, 87, 0, 4, 3, 74, 0, 1, 97, 116, 0, 1, 111, 111, 2, 32, 0, 1, 114, 97, 2, 101, 114, 0, 2, 111, 114, 101, 32, 0, 8, 2, 17, 71, 0, 8, 2, 111, 108, 97, 0, 101, 1, 97, 98, 3, 74, 13, 0, 97, 114, 105, 111, 2, 116, 3, 74, 35, 34, 139, 0, 4, 1, 97, 17, 67, 2, 101, 3, 89, 0, 1, 97, 116, 115, 0, 1, 101, 2, 101, 108, 0, 1, 101, 114, 99, 0, 1, 105, 102, 0, 1, 105, 108, 99, 0, 1, 105, 110, 0, 1, 111, 99, 105, 0, 1, 111, 108, 99, 0, 2, 97, 115, 115, 0, 2, 97, 116, 101, 97, 0, 2, 101, 102, 0, 2, 101, 118, 0, 2, 105, 111, 32, 0, 2, 117, 114, 101, 0, 2, 117, 116, 101, 0, 2, 195, 169, 12, 0, 8, 2, 97, 110, 100, 17, 65, 0, 8, 2, 97, 114, 116, 114, 101, 0, 8, 111, 2, 101, 0, 101, 1, 105, 2, 32, 24, 0, 105, 111, 110, 3, 89, 13, 50, 0, 97, 112, 2, 101, 114, 111, 3, 89, 35, 48, 0, 105, 99, 97, 2, 103, 3, 89, 111, 49, 124, 0, 105, 99, 97, 2, 110, 3, 89, 111, 49, 136, 0, 4, 97, 117, 2, 102, 3, 89, 134, 0, 97, 117, 2, 118, 0, 101, 122, 3, 89, 136, 0, 7, 6, 99, 111, 0, 4, 2, 110, 115, 116, 105, 116, 117, 17, 65, 3, 49, 2, 122, 0, 8, 2, 110, 102, 105, 100, 101, 0, 8, 2, 110, 115, 117, 108, 116, 0, 110, 8, 2, 21, 3, 49, 2, 122, 50, 0, 110, 116, 114, 97, 99, 2, 116, 3, 49, 2, 122, 50, 47, 34, 35, 49, 0, 110, 116, 114, 97, 114, 3, 49, 2, 122, 50, 47, 34, 138, 0, 110, 115, 101, 114, 2, 118, 3, 49, 2, 122, 50, 87, 126, 0, 109, 112, 8, 2, 116, 114, 3, 49, 2, 122, 63, 0, 4, 2, 104, 97, 98, 3, 49, 2, 134, 0, 8, 2, 97, 103, 0, 97, 2, 108, 101, 115, 3, 49, 2, 134, 13, 0, 4, 2, 109, 112, 117, 116, 97, 3, 49, 4, 122, 0, 8, 2, 110, 116, 114, 111, 118, 0, 114, 114, 101, 115, 112, 111, 3, 49, 4, 122, 34, 120, 87, 48, 6, 122, 0, 110, 116, 114, 97, 8, 2, 17, 67, 21, 14, 128, 132, 134, 3, 49, 4, 122, 50, 47, 34, 13, 0, 110, 100, 101, 8, 2, 115, 99, 3, 49, 4, 122, 50, 70, 111, 0, 8, 2, 101, 17, 67, 14, 128, 132, 130, 3, 49, 4, 134, 0, 117, 110, 116, 101, 114, 8, 2, 21, 14, 128, 132, 135, 3, 49, 6, 133, 50, 47, 13, 0, 112, 111, 108, 121, 8, 3, 49, 6, 134, 48, 4, 122, 55, 120, 0, 4, 2, 108, 108, 97, 98, 3, 49, 13, 0, 2, 108, 108, 97, 112, 0, 2, 108, 108, 97, 116, 0, 2, 108, 108, 101, 99, 0, 2, 108, 108, 105, 100, 0, 2, 108, 108, 105, 115, 0, 2, 108, 108, 117, 0, 2, 108, 111, 115, 115, 0, 2, 109, 109, 101, 110, 115, 0, 2, 110, 115, 101, 99, 117, 0, 2, 110, 116, 114, 111, 108, 12, 0, 2, 114, 114, 101, 99, 116, 0, 2, 114, 114, 111, 0, 2, 114, 114, 117, 112, 0, 8, 2, 109, 21, 0, 8, 2, 109, 112, 108, 0, 8, 2, 110, 99, 105, 0, 8, 2, 110, 102, 105, 103, 117, 0, 8, 2, 110, 110, 101, 99, 116, 0, 8, 2, 110, 110, 101, 120, 0, 8, 2, 110, 115, 105, 0, 8, 2, 110, 118, 101, 110, 17, 65, 0, 8, 2, 110, 118, 105, 0, 110, 115, 105, 100, 101, 114, 3, 49, 13, 50, 87, 120, 70, 112, 0, 110, 110, 105, 118, 3, 49, 13, 50, 135, 82, 0, 108, 108, 101, 2, 103, 105, 3, 49, 13, 55, 127, 0, 4, 109, 109, 117, 110, 2, 97, 3, 49, 13, 63, 57, 132, 50, 0, 109, 109, 117, 110, 2, 105, 99, 0, 109, 101, 2, 100, 105, 3, 49, 13, 63, 127, 0, 4, 2, 109, 98, 97, 3, 49, 122, 0, 2, 109, 98, 105, 110, 97, 0, 2, 109, 101, 100, 121, 0, 2, 109, 109, 97, 32, 0, 2, 109, 109, 97, 110, 100, 97, 0, 2, 109, 109, 101, 110, 0, 2, 109, 109, 101, 114, 99, 101, 0, 2, 109, 109, 111, 100, 111, 114, 0, 2, 109, 109, 117, 116, 97, 0, 2, 109, 112, 101, 110, 115, 0, 2, 109, 112, 101, 114, 0, 2, 109, 112, 105, 108, 97, 0, 2, 109, 112, 108, 101, 109, 0, 2, 109, 112, 108, 101, 120, 32, 0, 2, 109, 112, 108, 105, 99, 97, 0, 2, 109, 112, 108, 105, 109, 0, 2, 109, 112, 111, 115, 105, 116, 0, 2, 109, 112, 111, 115, 116, 0, 2, 109, 112, 111, 117, 0, 2, 109, 112, 114, 101, 104, 101, 110, 0, 2, 109, 112, 114, 111, 109, 0, 2, 110, 115, 101, 99, 0, 2, 110, 115, 111, 110, 0, 2, 110, 115, 116, 97, 110, 0, 2, 110, 115, 116, 105, 116, 0, 2, 110, 116, 105, 110, 101, 0, 8, 2, 109, 105, 0, 8, 2, 109, 114, 0, 8, 2, 110, 99, 101, 112, 116, 32, 0, 8, 2, 110, 99, 114, 101, 116, 0, 8, 2, 110, 100, 105, 109, 0, 8, 2, 110, 100, 111, 109, 0, 8, 2, 110, 100, 111, 114, 0, 8, 2, 110, 100, 117, 105, 116, 0, 8, 2, 110, 102, 101, 114, 101, 110, 0, 8, 2, 110, 102, 105, 100, 0, 8, 2, 110, 102, 105, 115, 0, 8, 2, 110, 102, 108, 117, 0, 8, 2, 110, 103, 114, 101, 0, 8, 2, 110, 105, 0, 8, 2, 110, 106, 117, 103, 0, 8, 2, 110, 113, 117, 101, 0, 8, 2, 110, 115, 99, 0, 8, 2, 110, 115, 111, 108, 101, 0, 8, 2, 110, 115, 116, 97, 98, 108, 0, 8, 2, 110, 115, 116, 105, 112, 0, 8, 2, 110, 115, 117, 108, 0, 8, 2, 110, 116, 97, 99, 116, 0, 8, 2, 110, 116, 101, 109, 112, 108, 0, 8, 2, 110, 116, 101, 120, 116, 0, 8, 2, 110, 116, 111, 117, 114, 0, 8, 2, 110, 116, 114, 17, 65, 0, 8, 2, 110, 116, 114, 105, 98, 0, 8, 2, 110, 118, 111, 121, 0, 8, 2, 110, 119, 0, 8, 2, 114, 114, 105, 0, 114, 111, 2, 108, 108, 3, 49, 122, 34, 122, 0, 112, 121, 8, 3, 49, 122, 48, 120, 0, 110, 110, 111, 105, 8, 2, 115, 3, 49, 122, 50, 13, 0, 110, 116, 114, 97, 115, 116, 8, 3, 49, 122, 50, 47, 34, 118, 87, 47, 0, 110, 103, 114, 117, 3, 49, 122, 50, 79, 34, 132, 0, 110, 102, 105, 8, 2, 100, 101, 110, 3, 49, 122, 50, 81, 120, 0, 110, 118, 97, 2, 108, 3, 49, 122, 50, 82, 13, 0, 4, 110, 99, 101, 8, 2, 110, 116, 114, 97, 3, 49, 122, 50, 87, 13, 0, 110, 115, 101, 114, 2, 118, 97, 116, 105, 111, 0, 110, 115, 101, 8, 2, 113, 3, 49, 122, 50, 87, 120, 0, 108, 108, 97, 114, 3, 49, 122, 55, 112, 0, 109, 109, 111, 110, 3, 49, 122, 63, 13, 50, 0, 109, 112, 97, 114, 97, 98, 3, 49, 122, 63, 48, 13, 34, 13, 69, 0, 109, 112, 101, 2, 116, 17, 65, 110, 3, 49, 122, 63, 48, 120, 0, 109, 109, 117, 110, 3, 49, 122, 63, 57, 132, 50, 0, 4, 2, 109, 101, 32, 3, 49, 123, 0, 2, 109, 112, 97, 110, 121, 0, 2, 109, 112, 97, 115, 115, 32, 0, 8, 2, 109, 102, 0, 8, 2, 110, 106, 117, 114, 0, 109, 101, 2, 98, 3, 49, 123, 63, 0, 109, 102, 111, 114, 116, 97, 98, 3, 49, 123, 63, 81, 47, 13, 69, 0, 109, 102, 111, 114, 2, 116, 3, 49, 123, 63, 81, 112, 0, 109, 105, 110, 103, 3, 49, 123, 63, 111, 66, 0, 8, 2, 109, 97, 3, 49, 134, 0, 97, 2, 108, 105, 116, 3, 49, 134, 13, 0, 115, 116, 97, 114, 8, 3, 49, 134, 87, 47, 125, 0, 101, 8, 2, 108, 3, 87, 127, 0, 7, 6, 100, 101, 0, 8, 2, 104, 121, 100, 3, 4, 70, 127, 0, 4, 2, 97, 99, 116, 3, 70, 2, 127, 0, 2, 97, 114, 99, 0, 2, 102, 108, 97, 116, 0, 2, 112, 101, 114, 0, 2, 112, 111, 108, 0, 2, 112, 111, 112, 0, 2, 114, 101, 103, 0, 2, 116, 111, 120, 0, 2, 116, 114, 97, 105, 0, 2, 118, 97, 108, 0, 8, 2, 101, 109, 112, 0, 8, 2, 111, 0, 8, 2, 116, 104, 0, 110, 105, 2, 116, 114, 105, 3, 70, 2, 127, 50, 135, 0, 4, 115, 2, 101, 103, 3, 70, 2, 127, 87, 0, 115, 2, 101, 110, 0, 115, 2, 117, 108, 0, 115, 116, 97, 2, 98, 3, 70, 2, 127, 87, 47, 136, 0, 115, 101, 2, 108, 3, 70, 4, 127, 87, 111, 0, 4, 2, 99, 111, 114, 117, 3, 70, 111, 0, 2, 100, 117, 0, 2, 109, 97, 0, 2, 109, 101, 110, 0, 2, 109, 105, 115, 101, 0, 2, 109, 111, 99, 114, 97, 99, 0, 2, 109, 111, 114, 0, 2, 109, 111, 116, 0, 2, 109, 117, 114, 0, 2, 114, 105, 17, 67, 0, 2, 114, 111, 103, 0, 8, 2, 98, 97, 0, 8, 2, 102, 21, 0, 8, 2, 103, 21, 0, 8, 2, 106, 0, 8, 2, 108, 21, 0, 8, 2, 110, 111, 0, 8, 2, 112, 21, 0, 8, 2, 114, 97, 105, 0, 8, 2, 116, 21, 0, 8, 2, 118, 17, 65, 0, 116, 101, 115, 116, 3, 70, 111, 47, 119, 87, 47, 0, 116, 101, 114, 3, 70, 111, 47, 126, 0, 116, 101, 114, 2, 105, 3, 70, 111, 47, 139, 34, 0, 110, 105, 8, 2, 97, 3, 70, 111, 50, 135, 0, 109, 101, 97, 3, 70, 111, 63, 6, 127, 0, 109, 111, 2, 98, 105, 3, 70, 111, 63, 134, 0, 4, 115, 8, 2, 105, 3, 70, 111, 86, 0, 115, 115, 8, 0, 4, 115, 2, 105, 115, 3, 70, 111, 87, 0, 115, 8, 2, 21, 0, 4, 2, 99, 105, 98, 3, 70, 119, 0, 2, 99, 105, 108, 0, 2, 99, 105, 109, 0, 2, 99, 107, 0, 2, 99, 111, 114, 0, 2, 99, 114, 101, 109, 0, 2, 102, 101, 114, 101, 110, 0, 2, 102, 105, 110, 105, 116, 0, 2, 102, 116, 0, 2, 108, 97, 119, 0, 2, 108, 101, 103, 0, 2, 108, 105, 99, 97, 0, 2, 108, 112, 104, 0, 2, 108, 118, 12, 0, 2, 109, 97, 103, 111, 103, 0, 2, 112, 114, 101, 99, 97, 0, 2, 112, 116, 0, 2, 112, 117, 116, 0, 2, 114, 17, 65, 17, 67, 97, 116, 105, 111, 0, 2, 114, 101, 108, 0, 2, 116, 111, 110, 0, 2, 116, 114, 105, 0, 2, 118, 105, 108, 0, 2, 118, 111, 110, 0, 8, 2, 108, 108, 0, 8, 2, 108, 116, 0, 115, 2, 99, 97, 0, 112, 111, 2, 115, 105, 116, 105, 3, 70, 119, 48, 13, 0, 99, 97, 2, 100, 101, 110, 3, 70, 119, 49, 13, 0, 108, 117, 2, 103, 3, 70, 119, 55, 57, 132, 0, 118, 97, 115, 8, 3, 70, 119, 82, 13, 87, 0, 115, 2, 105, 103, 110, 97, 3, 70, 119, 86, 0, 4, 115, 2, 101, 99, 3, 70, 119, 87, 0, 115, 2, 105, 99, 0, 115, 2, 111, 108, 0, 115, 2, 112, 111, 116, 0, 115, 8, 2, 104, 0, 115, 8, 2, 107, 0, 115, 116, 105, 3, 70, 119, 87, 47, 120, 0, 4, 8, 2, 98, 105, 108, 3, 70, 121, 0, 8, 2, 99, 21, 0, 4, 2, 99, 101, 110, 99, 3, 70, 127, 0, 2, 99, 111, 109, 0, 2, 99, 114, 101, 97, 115, 0, 2, 116, 97, 105, 108, 0, 2, 116, 111, 117, 0, 2, 118, 105, 97, 0, 2, 118, 105, 111, 0, 109, 8, 2, 111, 110, 105, 3, 70, 127, 63, 0, 98, 117, 2, 103, 3, 70, 127, 69, 4, 123, 0, 7, 6, 100, 105, 0, 4, 2, 115, 98, 101, 21, 3, 4, 70, 120, 0, 2, 115, 99, 111, 110, 0, 2, 115, 111, 98, 0, 2, 115, 112, 111, 115, 115, 0, 2, 115, 112, 114, 111, 112, 0, 8, 2, 115, 97, 21, 0, 8, 2, 115, 114, 101, 0, 4, 8, 2, 115, 101, 14, 128, 132, 131, 3, 4, 70, 120, 87, 0, 115, 8, 2, 105, 110, 14, 128, 132, 131, 0, 115, 97, 8, 2, 112, 3, 4, 70, 120, 87, 13, 0, 4, 2, 103, 114, 101, 115, 3, 70, 2, 135, 0, 2, 109, 101, 110, 115, 0, 2, 111, 120, 0, 2, 118, 101, 114, 17, 67, 0, 2, 118, 101, 115, 116, 0, 2, 118, 117, 108, 0, 8, 2, 104, 21, 0, 103, 101, 2, 115, 116, 3, 70, 2, 135, 73, 119, 0, 4, 2, 99, 116, 97, 116, 3, 70, 111, 0, 2, 102, 102, 114, 97, 99, 0, 2, 102, 102, 117, 115, 0, 2, 109, 105, 110, 0, 2, 115, 97, 115, 116, 0, 2, 115, 99, 111, 118, 0, 2, 115, 105, 110, 116, 0, 2, 118, 105, 100, 0, 2, 118, 105, 110, 0, 2, 118, 105, 115, 0, 2, 118, 111, 114, 99, 0, 8, 2, 115, 21, 0, 8, 2, 115, 104, 101, 118, 12, 0, 115, 8, 2, 104, 17, 65, 3, 70, 111, 87, 0, 4, 2, 115, 99, 32, 3, 70, 120, 0, 2, 115, 99, 111, 32, 0, 2, 115, 99, 111, 114, 100, 32, 0, 2, 115, 99, 111, 116, 0, 2, 115, 99, 111, 117, 110, 116, 0, 2, 115, 104, 17, 67, 0, 2, 115, 104, 32, 0, 2, 115, 107, 0, 2, 115, 111, 108, 0, 2, 115, 112, 111, 115, 105, 116, 0, 2, 115, 115, 105, 100, 0, 2, 115, 115, 105, 112, 0, 2, 115, 115, 111, 108, 117, 0, 2, 115, 115, 111, 110, 0, 2, 115, 116, 97, 110, 0, 2, 115, 116, 105, 108, 108, 97, 116, 101, 0, 2, 115, 116, 114, 105, 0, 108, 105, 2, 103, 3, 70, 120, 55, 120, 0, 118, 105, 2, 100, 101, 110, 3, 70, 120, 82, 120, 0, 115, 99, 105, 112, 108, 105, 3, 70, 120, 87, 120, 48, 55, 120, 0, 4, 2, 99, 104, 114, 111, 3, 70, 135, 0, 2, 115, 115, 101, 99, 116, 0, 2, 115, 117, 108, 0, 4, 97, 8, 2, 103, 111, 110, 3, 70, 135, 6, 35, 0, 97, 8, 2, 110, 0, 97, 8, 3, 70, 135, 13, 0, 99, 104, 111, 2, 116, 3, 70, 135, 49, 6, 122, 0, 108, 117, 2, 116, 3, 70, 135, 55, 6, 132, 0, 97, 8, 2, 108, 3, 70, 142, 0, 7, 6, 101, 97, 0, 4, 1, 104, 2, 100, 109, 17, 65, 21, 3, 2, 119, 0, 1, 104, 2, 100, 113, 0, 1, 114, 2, 32, 3, 6, 139, 0, 110, 1, 112, 2, 32, 3, 6, 139, 50, 0, 1, 21, 2, 116, 105, 118, 101, 3, 8, 139, 0, 4, 1, 10, 2, 98, 105, 108, 105, 3, 13, 0, 1, 10, 2, 98, 108, 0, 98, 108, 121, 1, 10, 3, 13, 69, 55, 2, 120, 0, 117, 2, 116, 3, 57, 132, 0, 4, 1, 17, 67, 2, 108, 116, 3, 119, 0, 1, 17, 67, 2, 118, 101, 110, 0, 1, 100, 2, 102, 0, 1, 100, 2, 116, 104, 0, 1, 100, 110, 101, 2, 118, 0, 1, 102, 2, 116, 104, 0, 1, 104, 2, 116, 104, 101, 114, 0, 1, 108, 2, 100, 101, 110, 0, 1, 114, 2, 100, 105, 101, 100, 0, 1, 114, 2, 100, 105, 108, 121, 0, 1, 114, 2, 100, 121, 0, 1, 114, 98, 2, 100, 0, 1, 114, 98, 2, 115, 0, 1, 114, 98, 2, 116, 104, 0, 1, 114, 104, 116, 2, 100, 0, 1, 114, 104, 116, 2, 116, 0, 1, 114, 112, 115, 2, 100, 0, 1, 114, 116, 2, 99, 104, 101, 114, 0, 1, 114, 116, 2, 100, 0, 1, 116, 115, 2, 100, 0, 1, 119, 115, 2, 116, 0, 1, 122, 2, 108, 111, 0, 8, 104, 2, 118, 105, 0, 8, 108, 2, 109, 105, 0, 8, 114, 100, 2, 100, 0, 112, 111, 1, 119, 3, 119, 48, 13, 0, 108, 111, 117, 1, 106, 3, 119, 55, 13, 0, 109, 2, 116, 32, 3, 119, 63, 48, 0, 4, 100, 1, 100, 3, 119, 70, 0, 100, 1, 104, 0, 100, 101, 100, 8, 108, 3, 119, 70, 111, 70, 0, 118, 121, 1, 104, 3, 119, 82, 37, 0, 4, 116, 104, 1, 108, 3, 119, 84, 0, 116, 104, 1, 119, 0, 4, 115, 2, 97, 110, 3, 119, 86, 0, 115, 2, 101, 110, 0, 115, 117, 114, 3, 119, 88, 112, 0, 4, 114, 1, 104, 2, 107, 3, 125, 0, 114, 1, 104, 2, 116, 0, 114, 1, 104, 2, 116, 104, 0, 4, 114, 1, 104, 2, 100, 3, 126, 0, 114, 1, 104, 2, 115, 101, 0, 114, 1, 104, 101, 114, 2, 115, 0, 114, 1, 108, 2, 110, 0, 114, 1, 112, 2, 108, 0, 114, 1, 115, 2, 99, 104, 0, 114, 1, 121, 2, 110, 0, 114, 2, 116, 104, 0, 114, 8, 2, 108, 0, 114, 8, 2, 110, 0, 4, 3, 127, 0, 1, 17, 67, 29, 2, 110, 32, 0, 1, 98, 2, 110, 0, 1, 102, 2, 108, 116, 0, 1, 104, 2, 118, 0, 1, 109, 2, 108, 116, 0, 1, 115, 17, 67, 2, 32, 0, 2, 110, 100, 101, 114, 3, 127, 6, 35, 0, 1, 114, 99, 2, 116, 3, 127, 6, 136, 0, 1, 104, 116, 2, 116, 114, 105, 3, 127, 35, 0, 100, 109, 101, 1, 114, 3, 127, 70, 63, 127, 0, 103, 101, 114, 3, 127, 79, 112, 0, 116, 104, 1, 114, 98, 2, 101, 3, 127, 84, 0, 115, 111, 2, 110, 3, 127, 86, 13, 0, 115, 101, 2, 21, 3, 127, 87, 0, 4, 117, 3, 134, 0, 117, 120, 0, 4, 1, 114, 98, 2, 107, 3, 136, 0, 1, 114, 103, 2, 116, 0, 1, 116, 115, 2, 107, 0, 4, 114, 1, 98, 3, 138, 0, 114, 1, 116, 2, 17, 65, 0, 114, 1, 119, 0, 114, 1, 119, 115, 0, 4, 1, 21, 2, 32, 3, 139, 0, 1, 104, 116, 2, 116, 0, 8, 98, 2, 116, 114, 105, 0, 110, 2, 32, 3, 139, 50, 0, 108, 1, 10, 2, 32, 3, 139, 55, 0, 4, 114, 3, 140, 0, 114, 1, 98, 2, 100, 0, 114, 1, 119, 2, 121, 0, 7, 6, 101, 100, 0, 4, 1, 21, 2, 105, 101, 110, 3, 6, 127, 70, 0, 1, 99, 2, 101, 32, 0, 1, 104, 2, 114, 97, 0, 1, 104, 2, 114, 97, 108, 0, 1, 104, 2, 114, 111, 110, 0, 1, 115, 114, 2, 101, 0, 117, 114, 1, 21, 3, 6, 127, 73, 112, 0, 1, 10, 2, 121, 3, 13, 70, 0, 4, 1, 99, 21, 2, 32, 14, 128, 155, 130, 3, 47, 0, 1, 102, 21, 2, 32, 14, 128, 155, 130, 0, 1, 104, 99, 10, 2, 32, 14, 128, 139, 130, 0, 1, 104, 115, 10, 2, 32, 14, 128, 139, 130, 0, 1, 107, 21, 2, 32, 14, 128, 155, 130, 0, 1, 112, 21, 2, 32, 14, 128, 155, 130, 0, 1, 115, 115, 21, 2, 32, 14, 128, 152, 130, 0, 1, 120, 21, 2, 32, 14, 128, 138, 130, 0, 4, 1, 17, 67, 21, 2, 32, 14, 128, 155, 130, 3, 70, 0, 1, 21, 21, 2, 32, 14, 128, 155, 130, 0, 1, 103, 21, 2, 32, 14, 128, 138, 129, 0, 1, 105, 17, 65, 2, 32, 14, 128, 153, 130, 0, 1, 108, 99, 2, 32, 14, 128, 136, 129, 0, 1, 108, 101, 2, 32, 14, 128, 152, 130, 0, 1, 110, 101, 10, 2, 32, 14, 128, 136, 130, 0, 1, 114, 101, 21, 21, 2, 32, 14, 128, 136, 130, 0, 1, 121, 2, 32, 14, 128, 136, 130, 0, 4, 1, 104, 115, 17, 67, 21, 2, 32, 3, 119, 70, 0, 1, 119, 121, 2, 32, 0, 5, 8, 1, 100, 21, 2, 32, 14, 128, 155, 130, 0, 5, 8, 1, 116, 21, 2, 32, 14, 128, 155, 130, 0, 97, 108, 1, 112, 3, 119, 70, 116, 0, 105, 98, 1, 114, 99, 3, 119, 70, 120, 69, 0, 103, 2, 101, 13, 3, 119, 73, 0, 4, 1, 114, 100, 21, 2, 32, 3, 120, 70, 0, 1, 114, 102, 21, 2, 32, 14, 128, 136, 130, 0, 108, 121, 2, 32, 3, 120, 70, 55, 2, 120, 0, 4, 1, 100, 21, 2, 32, 14, 128, 155, 130, 3, 121, 70, 0, 1, 116, 21, 2, 32, 14, 128, 155, 130, 0, 4, 1, 109, 2, 105, 97, 3, 127, 70, 0, 1, 109, 2, 105, 111, 0, 1, 109, 2, 105, 117, 0, 1, 112, 2, 101, 32, 0, 1, 116, 2, 105, 0, 1, 119, 115, 0, 105, 97, 116, 101, 1, 109, 21, 3, 127, 70, 111, 13, 47, 0, 7, 6, 101, 105, 0, 4, 1, 108, 2, 115, 3, 119, 0, 99, 101, 1, 108, 2, 115, 116, 0, 4, 1, 102, 2, 116, 32, 3, 120, 0, 1, 102, 2, 116, 101, 0, 2, 110, 97, 116, 101, 0, 4, 1, 21, 2, 110, 32, 3, 127, 0, 1, 21, 2, 110, 101, 0, 1, 99, 0, 2, 116, 104, 0, 2, 118, 0, 2, 122, 0, 103, 104, 1, 108, 0, 108, 1, 110, 3, 127, 55, 0, 103, 104, 1, 107, 3, 127, 85, 0, 4, 1, 98, 2, 110, 103, 3, 127, 120, 0, 1, 104, 116, 2, 115, 17, 67, 0, 4, 1, 104, 2, 116, 32, 3, 135, 0, 2, 115, 116, 101, 114, 0, 5, 35, 2, 116, 104, 101, 114, 0, 8, 0, 103, 104, 1, 104, 2, 116, 0, 114, 8, 3, 135, 34, 0, 4, 115, 2, 101, 3, 135, 86, 0, 115, 8, 115, 2, 109, 0, 99, 104, 3, 135, 99, 0, 4, 3, 136, 0, 103, 2, 110, 0, 103, 104, 0, 103, 104, 1, 108, 115, 0, 103, 104, 116, 104, 3, 136, 47, 85, 0, 114, 3, 138, 0, 114, 1, 119, 3, 140, 0, 7, 6, 101, 108, 0, 4, 8, 2, 17, 65, 3, 2, 120, 55, 0, 108, 8, 2, 105, 112, 0, 101, 8, 2, 99, 116, 114, 111, 3, 2, 120, 55, 4, 119, 0, 101, 8, 2, 99, 116, 114, 111, 108, 3, 2, 120, 55, 119, 0, 105, 116, 8, 3, 2, 120, 55, 127, 47, 0, 4, 1, 99, 120, 2, 32, 3, 6, 119, 55, 0, 1, 108, 108, 97, 2, 111, 0, 1, 110, 110, 111, 2, 32, 0, 1, 112, 2, 32, 0, 2, 105, 103, 105, 0, 108, 97, 1, 10, 2, 32, 3, 6, 119, 55, 13, 0, 111, 112, 1, 118, 3, 6, 119, 55, 13, 48, 0, 108, 105, 1, 21, 2, 32, 3, 6, 119, 55, 120, 0, 4, 1, 100, 2, 105, 118, 3, 13, 55, 0, 1, 118, 2, 111, 99, 0, 108, 1, 10, 2, 111, 117, 115, 0, 108, 101, 114, 1, 118, 10, 2, 32, 3, 13, 55, 13, 0, 108, 105, 110, 103, 1, 10, 3, 13, 55, 111, 66, 0, 1, 115, 2, 101, 99, 116, 3, 111, 55, 0, 4, 1, 10, 2, 32, 3, 116, 0, 1, 10, 2, 115, 32, 0, 1, 116, 2, 112, 0, 4, 1, 98, 105, 99, 2, 32, 3, 119, 55, 0, 1, 108, 108, 97, 0, 5, 8, 1, 10, 2, 32, 0, 5, 8, 1, 10, 2, 115, 32, 0, 111, 2, 113, 3, 119, 55, 13, 0, 115, 101, 8, 3, 119, 55, 87, 0, 101, 8, 2, 99, 116, 114, 111, 110, 3, 119, 55, 119, 0, 4, 101, 8, 2, 103, 3, 119, 55, 120, 0, 101, 8, 2, 112, 0, 101, 8, 2, 118, 97, 0, 101, 109, 8, 3, 119, 55, 120, 63, 0, 101, 1, 107, 115, 2, 116, 3, 119, 55, 121, 0, 1, 102, 2, 105, 120, 3, 127, 55, 0, 7, 6, 101, 109, 0, 8, 3, 2, 119, 63, 0, 1, 21, 2, 98, 101, 114, 3, 6, 119, 63, 0, 1, 104, 112, 115, 2, 101, 3, 6, 127, 63, 0, 4, 1, 10, 2, 32, 3, 13, 63, 0, 1, 10, 2, 121, 32, 0, 1, 104, 112, 115, 0, 4, 2, 105, 115, 115, 105, 3, 111, 63, 0, 2, 117, 108, 115, 0, 8, 2, 97, 0, 8, 2, 101, 0, 8, 2, 105, 116, 0, 8, 2, 111, 0, 109, 2, 97, 110, 0, 4, 2, 97, 110, 97, 3, 119, 63, 0, 2, 98, 108, 101, 109, 0, 2, 98, 114, 121, 0, 2, 101, 114, 97, 108, 0, 2, 101, 114, 121, 0, 2, 105, 0, 2, 112, 97, 116, 104, 0, 2, 112, 101, 114, 0, 2, 112, 104, 97, 115, 0, 2, 112, 114, 101, 115, 0, 2, 112, 116, 105, 0, 2, 112, 116, 121, 0, 2, 117, 108, 0, 109, 2, 101, 0, 111, 114, 114, 104, 1, 104, 3, 119, 63, 13, 34, 0, 98, 97, 2, 115, 3, 119, 63, 69, 13, 0, 4, 1, 102, 2, 97, 108, 101, 3, 127, 63, 0, 1, 104, 2, 111, 0, 2, 97, 105, 108, 0, 7, 6, 101, 110, 0, 4, 2, 100, 101, 97, 3, 2, 119, 50, 0, 2, 105, 103, 109, 97, 32, 0, 2, 109, 101, 115, 0, 8, 2, 21, 0, 8, 2, 100, 97, 0, 8, 2, 100, 117, 0, 8, 2, 116, 105, 0, 110, 8, 0, 114, 111, 108, 3, 2, 119, 50, 34, 134, 55, 0, 114, 97, 103, 101, 3, 2, 119, 50, 34, 136, 73, 0, 116, 105, 99, 101, 1, 10, 3, 2, 119, 50, 47, 135, 87, 0, 108, 105, 2, 118, 3, 2, 119, 50, 55, 135, 0, 100, 111, 114, 8, 3, 2, 119, 50, 70, 131, 0, 99, 104, 97, 8, 2, 110, 3, 2, 119, 50, 74, 118, 0, 118, 105, 114, 111, 3, 2, 119, 50, 82, 135, 34, 13, 0, 116, 104, 114, 97, 2, 108, 3, 2, 119, 50, 85, 34, 128, 0, 99, 121, 2, 99, 108, 105, 3, 2, 119, 50, 87, 120, 0, 115, 104, 114, 105, 110, 101, 3, 2, 119, 50, 89, 34, 135, 50, 0, 2, 116, 101, 114, 116, 3, 4, 119, 50, 0, 2, 116, 114, 101, 112, 3, 4, 122, 50, 0, 4, 1, 21, 2, 100, 111, 32, 3, 6, 119, 50, 0, 1, 21, 2, 116, 97, 108, 0, 1, 21, 2, 116, 111, 117, 115, 0, 1, 21, 2, 116, 117, 0, 1, 108, 108, 105, 109, 2, 105, 97, 0, 1, 115, 101, 114, 112, 101, 2, 116, 0, 1, 115, 115, 2, 116, 0, 1, 116, 115, 111, 2, 115, 0, 2, 100, 17, 65, 32, 0, 2, 116, 105, 97, 108, 0, 110, 2, 105, 97, 0, 116, 97, 114, 121, 1, 109, 2, 32, 3, 6, 119, 50, 47, 13, 34, 2, 37, 0, 107, 111, 1, 10, 2, 32, 3, 6, 119, 50, 49, 134, 0, 100, 114, 111, 110, 2, 32, 3, 6, 119, 50, 70, 34, 13, 50, 0, 115, 107, 2, 32, 3, 6, 119, 50, 87, 49, 0, 103, 2, 32, 3, 6, 119, 66, 0, 4, 2, 97, 32, 3, 6, 127, 50, 0, 2, 97, 114, 121, 0, 2, 105, 97, 0, 111, 117, 115, 1, 21, 2, 32, 3, 8, 13, 50, 13, 87, 0, 101, 115, 1, 104, 116, 21, 21, 2, 32, 3, 8, 13, 50, 127, 86, 0, 4, 1, 10, 2, 17, 65, 110, 99, 101, 3, 13, 50, 0, 1, 10, 2, 32, 0, 1, 10, 2, 99, 101, 32, 0, 1, 10, 2, 101, 100, 32, 0, 1, 10, 2, 101, 114, 32, 0, 1, 10, 2, 109, 101, 110, 116, 0, 1, 10, 2, 116, 32, 0, 1, 10, 2, 116, 104, 32, 0, 1, 99, 114, 101, 109, 0, 1, 103, 101, 2, 100, 0, 1, 112, 114, 97, 99, 0, 1, 118, 18, 66, 2, 116, 32, 0, 1, 118, 21, 21, 2, 116, 32, 0, 99, 121, 1, 10, 2, 32, 3, 13, 50, 87, 2, 37, 0, 105, 110, 101, 1, 10, 3, 13, 50, 127, 50, 0, 4, 8, 2, 111, 3, 111, 50, 0, 8, 2, 111, 117, 103, 104, 0, 8, 2, 117, 0, 97, 8, 2, 109, 3, 111, 50, 35, 0, 4, 1, 10, 2, 99, 104, 3, 119, 50, 0, 1, 99, 114, 101, 112, 2, 116, 0, 1, 99, 115, 97, 2, 116, 0, 1, 102, 2, 99, 101, 32, 0, 1, 107, 2, 100, 32, 0, 1, 115, 110, 2, 116, 0, 1, 116, 110, 2, 116, 0, 1, 116, 120, 2, 116, 0, 1, 118, 2, 116, 32, 0, 2, 100, 111, 117, 115, 0, 2, 105, 103, 0, 2, 115, 105, 103, 0, 2, 116, 101, 114, 0, 2, 116, 105, 0, 2, 116, 105, 116, 121, 0, 2, 116, 114, 97, 110, 0, 2, 116, 114, 105, 0, 2, 116, 114, 111, 0, 2, 118, 105, 17, 65, 0, 2, 118, 111, 121, 0, 2, 118, 121, 0, 2, 122, 121, 0, 5, 8, 1, 10, 2, 99, 101, 32, 0, 5, 8, 1, 10, 2, 116, 32, 0, 8, 2, 100, 0, 8, 2, 101, 0, 8, 2, 109, 0, 8, 2, 116, 114, 121, 0, 8, 99, 115, 101, 100, 2, 116, 0, 8, 115, 101, 114, 2, 116, 0, 101, 109, 1, 116, 3, 119, 50, 13, 63, 0, 116, 105, 8, 99, 3, 119, 50, 47, 120, 0, 99, 108, 97, 118, 3, 119, 50, 49, 55, 136, 82, 0, 100, 111, 119, 3, 119, 50, 70, 6, 133, 0, 100, 111, 8, 3, 119, 50, 70, 134, 0, 103, 105, 110, 3, 119, 50, 73, 120, 50, 0, 103, 105, 110, 103, 3, 119, 50, 73, 120, 66, 0, 101, 114, 8, 3, 119, 50, 112, 0, 103, 2, 116, 104, 3, 119, 66, 0, 4, 1, 10, 2, 103, 101, 114, 3, 120, 50, 0, 1, 107, 99, 105, 104, 99, 0, 103, 2, 108, 17, 65, 3, 120, 66, 79, 0, 4, 2, 99, 111, 114, 101, 3, 122, 50, 0, 2, 116, 114, 101, 99, 0, 4, 1, 99, 115, 2, 101, 3, 127, 50, 0, 1, 103, 2, 105, 17, 65, 0, 2, 97, 108, 32, 0, 8, 115, 2, 105, 0, 101, 2, 32, 0, 4, 105, 1, 108, 2, 101, 3, 127, 50, 120, 0, 105, 1, 118, 2, 101, 0, 101, 97, 8, 103, 3, 127, 50, 120, 6, 35, 0, 7, 6, 101, 111, 0, 8, 103, 3, 4, 120, 122, 0, 1, 21, 21, 2, 32, 3, 6, 136, 134, 0, 117, 115, 1, 10, 2, 32, 3, 8, 139, 87, 0, 4, 110, 1, 103, 3, 13, 50, 0, 110, 1, 104, 99, 0, 1, 104, 116, 2, 21, 3, 111, 13, 0, 1, 103, 3, 111, 122, 0, 4, 101, 115, 2, 32, 3, 111, 134, 86, 0, 115, 2, 32, 0, 4, 1, 103, 2, 102, 102, 3, 119, 0, 1, 106, 2, 112, 0, 4, 1, 104, 116, 2, 99, 114, 97, 99, 121, 3, 120, 6, 122, 0, 1, 104, 116, 2, 108, 111, 103, 105, 115, 0, 1, 104, 116, 2, 108, 111, 103, 121, 0, 4, 1, 102, 3, 127, 0, 1, 112, 2, 112, 108, 0, 115, 105, 115, 1, 21, 3, 127, 6, 134, 87, 120, 87, 0, 114, 8, 103, 3, 130, 0, 2, 100, 32, 3, 133, 0, 118, 101, 114, 3, 134, 82, 13, 0, 114, 8, 3, 136, 112, 0, 4, 1, 104, 116, 2, 114, 3, 139, 0, 8, 108, 0, 7, 6, 101, 114, 0, 109, 101, 8, 102, 2, 110, 116, 3, 2, 126, 63, 119, 0, 4, 1, 21, 2, 105, 116, 121, 3, 6, 119, 34, 0, 2, 105, 99, 32, 0, 2, 105, 99, 97, 108, 0, 4, 1, 21, 2, 17, 67, 97, 108, 32, 3, 6, 126, 0, 1, 21, 2, 17, 67, 105, 99, 32, 0, 1, 21, 2, 115, 105, 97, 108, 0, 1, 109, 2, 103, 101, 0, 1, 118, 2, 103, 101, 0, 1, 118, 2, 115, 97, 108, 0, 2, 98, 105, 97, 108, 0, 2, 103, 105, 99, 32, 0, 2, 110, 97, 108, 32, 0, 2, 115, 105, 111, 110, 0, 114, 101, 100, 2, 32, 3, 6, 126, 70, 0, 103, 105, 110, 103, 3, 6, 126, 73, 111, 66, 0, 1, 21, 2, 111, 32, 3, 6, 138, 34, 0, 105, 2, 17, 65, 3, 6, 139, 34, 2, 120, 0, 101, 97, 108, 3, 6, 139, 34, 111, 116, 0, 4, 1, 104, 100, 97, 2, 101, 3, 6, 140, 0, 1, 104, 111, 99, 2, 101, 0, 101, 1, 99, 2, 32, 0, 4, 1, 10, 2, 111, 17, 67, 101, 32, 3, 8, 13, 34, 0, 1, 10, 2, 111, 117, 115, 0, 4, 105, 115, 101, 1, 10, 2, 32, 3, 8, 13, 34, 135, 86, 0, 105, 122, 101, 1, 10, 2, 32, 0, 121, 2, 32, 3, 13, 34, 2, 37, 0, 97, 108, 1, 21, 2, 105, 116, 121, 3, 13, 34, 6, 35, 55, 0, 4, 105, 115, 1, 10, 2, 97, 3, 13, 34, 135, 86, 0, 105, 122, 1, 10, 2, 97, 0, 116, 111, 1, 104, 2, 32, 3, 13, 47, 132, 0, 97, 1, 109, 97, 99, 3, 14, 34, 13, 0, 4, 1, 21, 2, 101, 110, 99, 101, 32, 3, 34, 0, 2, 101, 110, 116, 32, 0, 97, 109, 1, 10, 2, 101, 110, 116, 3, 34, 13, 63, 0, 105, 101, 115, 2, 32, 14, 128, 130, 130, 3, 86, 0, 4, 1, 99, 2, 97, 109, 3, 111, 34, 0, 8, 2, 17, 65, 0, 8, 104, 2, 101, 100, 0, 101, 1, 104, 2, 100, 105, 3, 111, 34, 119, 0, 101, 1, 105, 2, 32, 3, 111, 138, 0, 4, 1, 10, 3, 112, 0, 1, 10, 2, 32, 0, 1, 10, 2, 110, 32, 0, 1, 10, 2, 115, 32, 0, 1, 10, 2, 116, 32, 0, 1, 17, 67, 11, 2, 32, 14, 128, 128, 131, 0, 1, 21, 21, 21, 2, 32, 14, 128, 145, 130, 0, 1, 98, 109, 2, 32, 0, 1, 99, 115, 97, 2, 116, 0, 1, 108, 108, 2, 32, 14, 128, 128, 130, 0, 1, 108, 108, 97, 2, 32, 0, 1, 110, 105, 108, 2, 32, 14, 128, 128, 129, 0, 1, 110, 114, 2, 32, 14, 128, 128, 130, 0, 1, 112, 2, 99, 101, 110, 0, 1, 112, 2, 104, 97, 112, 0, 1, 114, 101, 2, 32, 14, 128, 128, 130, 0, 1, 115, 115, 2, 32, 14, 128, 128, 130, 0, 101, 1, 10, 2, 32, 0, 101, 1, 10, 2, 32, 0, 4, 1, 10, 2, 17, 65, 3, 112, 34, 0, 1, 10, 2, 105, 110, 103, 0, 2, 105, 101, 0, 2, 105, 101, 32, 0, 121, 2, 17, 65, 3, 112, 57, 0, 4, 115, 1, 17, 67, 11, 2, 32, 14, 128, 128, 132, 3, 112, 86, 0, 115, 1, 110, 105, 108, 2, 32, 14, 128, 128, 130, 0, 115, 1, 114, 101, 2, 32, 14, 128, 128, 131, 0, 115, 1, 115, 115, 2, 32, 14, 128, 128, 131, 0, 5, 8, 1, 10, 2, 32, 3, 117, 0, 115, 5, 8, 1, 17, 67, 11, 2, 32, 14, 128, 128, 132, 3, 117, 86, 0, 2, 114, 17, 65, 3, 119, 0, 4, 2, 105, 17, 67, 3, 119, 34, 0, 8, 2, 117, 100, 0, 8, 17, 67, 17, 67, 2, 17, 65, 0, 8, 104, 2, 17, 65, 0, 114, 1, 17, 67, 29, 0, 114, 8, 2, 17, 65, 0, 114, 121, 5, 3, 1, 98, 2, 32, 3, 119, 34, 2, 120, 0, 4, 101, 1, 104, 2, 115, 3, 119, 34, 13, 0, 101, 1, 104, 2, 116, 0, 4, 101, 1, 99, 2, 109, 111, 110, 3, 119, 34, 111, 0, 101, 1, 104, 2, 102, 0, 121, 8, 118, 0, 101, 111, 1, 116, 115, 3, 119, 34, 111, 134, 0, 97, 108, 1, 103, 2, 100, 3, 119, 34, 116, 0, 4, 5, 35, 1, 104, 2, 116, 102, 3, 125, 0, 5, 35, 8, 100, 2, 98, 0, 4, 3, 126, 0, 1, 17, 67, 29, 0, 1, 21, 2, 115, 121, 0, 1, 99, 2, 110, 32, 0, 1, 99, 2, 116, 0, 1, 99, 110, 111, 99, 2, 116, 32, 0, 1, 104, 2, 116, 122, 0, 1, 109, 2, 99, 0, 1, 115, 2, 118, 97, 110, 0, 1, 118, 2, 116, 0, 1, 118, 21, 2, 116, 32, 0, 2, 17, 66, 32, 0, 2, 32, 0, 2, 115, 101, 0, 2, 115, 105, 98, 0, 2, 115, 105, 102, 0, 2, 115, 105, 118, 0, 2, 116, 105, 111, 110, 0, 2, 118, 101, 0, 8, 0, 8, 117, 113, 0, 101, 2, 32, 0, 2, 17, 65, 3, 126, 34, 0, 109, 101, 97, 1, 112, 2, 98, 3, 126, 63, 139, 0, 4, 101, 1, 112, 109, 2, 32, 3, 138, 0, 114, 2, 32, 24, 0, 4, 1, 104, 2, 101, 110, 3, 139, 34, 0, 1, 122, 2, 111, 0, 8, 17, 67, 2, 111, 32, 0, 97, 1, 29, 2, 32, 3, 139, 34, 13, 0, 105, 1, 112, 120, 101, 2, 101, 110, 3, 139, 34, 111, 0, 105, 111, 8, 112, 2, 100, 105, 99, 3, 139, 34, 111, 6, 122, 0, 105, 111, 8, 112, 2, 100, 3, 139, 34, 111, 13, 0, 121, 1, 117, 113, 3, 139, 34, 120, 0, 4, 101, 1, 17, 67, 29, 2, 32, 3, 140, 0, 101, 1, 104, 112, 115, 2, 32, 0, 101, 1, 109, 2, 32, 0, 101, 1, 118, 101, 2, 32, 0, 101, 8, 104, 0, 7, 6, 101, 115, 0, 4, 2, 99, 97, 112, 101, 3, 2, 119, 87, 0, 2, 99, 97, 112, 105, 0, 8, 2, 112, 21, 0, 4, 2, 116, 114, 97, 108, 32, 3, 6, 119, 87, 0, 99, 1, 21, 2, 101, 110, 17, 67, 0, 113, 117, 101, 3, 6, 119, 87, 49, 0, 4, 2, 105, 97, 110, 32, 3, 6, 127, 86, 0, 2, 105, 99, 0, 101, 1, 110, 21, 2, 32, 0, 2, 105, 118, 101, 3, 6, 127, 87, 0, 105, 115, 2, 32, 3, 6, 127, 87, 120, 87, 0, 4, 1, 10, 2, 116, 32, 3, 13, 87, 0, 1, 10, 2, 121, 32, 0, 1, 104, 116, 2, 105, 18, 71, 101, 32, 0, 1, 118, 2, 116, 121, 0, 115, 1, 114, 101, 2, 32, 0, 115, 1, 114, 116, 10, 2, 32, 0, 115, 97, 1, 99, 101, 110, 2, 114, 121, 3, 13, 87, 13, 0, 105, 115, 1, 104, 116, 2, 32, 3, 13, 87, 120, 87, 0, 101, 115, 1, 104, 116, 2, 32, 3, 13, 87, 127, 86, 0, 4, 1, 10, 2, 32, 14, 128, 130, 129, 3, 86, 0, 1, 17, 67, 10, 2, 32, 14, 128, 130, 129, 0, 1, 104, 112, 10, 2, 32, 14, 128, 128, 129, 0, 1, 104, 116, 10, 2, 32, 14, 128, 128, 129, 0, 1, 105, 114, 101, 110, 2, 32, 14, 128, 130, 130, 0, 1, 114, 10, 2, 32, 14, 128, 128, 129, 0, 4, 1, 102, 10, 2, 32, 14, 128, 128, 129, 3, 87, 0, 1, 107, 10, 2, 32, 14, 128, 128, 129, 0, 1, 112, 10, 2, 32, 14, 128, 128, 129, 0, 1, 116, 10, 2, 32, 14, 128, 128, 129, 0, 1, 117, 113, 10, 2, 32, 14, 128, 128, 129, 0, 4, 2, 99, 97, 114, 112, 3, 111, 87, 0, 2, 112, 101, 99, 105, 0, 2, 116, 97, 116, 101, 0, 8, 2, 116, 97, 98, 0, 1, 114, 112, 2, 101, 110, 116, 3, 119, 86, 0, 4, 1, 114, 17, 67, 2, 116, 3, 119, 87, 0, 1, 118, 2, 116, 12, 0, 8, 2, 112, 108, 0, 115, 1, 116, 115, 105, 100, 2, 32, 0, 116, 105, 2, 109, 3, 119, 87, 47, 121, 0, 1, 118, 114, 97, 104, 2, 116, 3, 120, 87, 0, 111, 112, 104, 97, 3, 120, 87, 6, 122, 81, 13, 0, 4, 1, 99, 10, 2, 32, 14, 128, 128, 129, 3, 121, 86, 0, 1, 103, 10, 2, 32, 14, 128, 128, 129, 0, 1, 104, 99, 10, 2, 32, 14, 128, 128, 129, 0, 1, 104, 115, 2, 32, 14, 128, 128, 130, 0, 1, 115, 10, 2, 32, 14, 128, 128, 129, 0, 1, 115, 115, 10, 2, 32, 14, 128, 128, 130, 0, 1, 115, 117, 10, 2, 32, 14, 128, 129, 130, 0, 1, 115, 117, 114, 10, 2, 32, 14, 128, 128, 130, 0, 1, 115, 117, 116, 10, 2, 32, 14, 128, 128, 130, 0, 1, 120, 10, 2, 32, 14, 128, 128, 130, 0, 1, 122, 10, 2, 32, 14, 128, 128, 130, 0, 4, 2, 105, 17, 65, 3, 127, 86, 0, 8, 120, 97, 0, 101, 2, 32, 0, 8, 2, 112, 101, 97, 107, 3, 127, 87, 0, 7, 6, 101, 116, 0, 4, 2, 105, 116, 111, 114, 3, 6, 119, 47, 0, 116, 101, 2, 32, 0, 116, 97, 2, 32, 3, 6, 119, 47, 13, 0, 105, 110, 103, 1, 108, 2, 32, 3, 6, 127, 47, 120, 66, 0, 4, 101, 100, 1, 108, 2, 32, 3, 6, 127, 47, 121, 70, 0, 101, 100, 1, 114, 99, 2, 32, 0, 114, 121, 1, 109, 2, 32, 3, 8, 13, 47, 34, 2, 120, 0, 4, 1, 108, 10, 2, 32, 3, 13, 47, 0, 8, 109, 2, 105, 99, 0, 116, 1, 108, 97, 112, 2, 101, 0, 104, 1, 17, 67, 21, 2, 32, 14, 128, 129, 131, 3, 13, 85, 0, 114, 121, 2, 32, 14, 128, 128, 130, 3, 34, 120, 0, 4, 1, 21, 2, 32, 3, 111, 47, 0, 8, 2, 101, 114, 110, 0, 116, 1, 10, 2, 32, 0, 4, 1, 98, 97, 104, 112, 2, 32, 3, 119, 47, 0, 1, 106, 2, 32, 0, 1, 110, 17, 65, 21, 21, 2, 32, 0, 1, 114, 103, 2, 12, 0, 1, 115, 2, 32, 0, 1, 116, 2, 32, 0, 4, 104, 2, 105, 99, 3, 119, 85, 0, 104, 2, 121, 108, 101, 110, 0, 104, 8, 2, 97, 0, 104, 8, 2, 101, 108, 0, 4, 1, 21, 2, 97, 116, 101, 3, 120, 47, 0, 1, 21, 2, 97, 116, 105, 111, 110, 0, 1, 107, 114, 0, 1, 108, 108, 2, 32, 0, 105, 110, 103, 1, 10, 2, 32, 3, 121, 47, 2, 120, 66, 0, 101, 100, 1, 10, 2, 32, 14, 128, 128, 130, 3, 121, 70, 0, 4, 1, 102, 2, 97, 3, 127, 47, 0, 8, 2, 111, 110, 0, 8, 109, 2, 101, 0, 8, 112, 2, 101, 0, 101, 2, 32, 0, 4, 101, 114, 1, 109, 2, 32, 3, 127, 47, 112, 0, 114, 101, 1, 109, 0, 4, 104, 2, 121, 108, 3, 127, 85, 0, 104, 5, 35, 2, 97, 110, 101, 0, 104, 8, 2, 17, 65, 0, 1, 114, 101, 98, 2, 32, 3, 136, 0, 7, 6, 101, 118, 0, 4, 101, 114, 2, 99, 3, 4, 119, 82, 112, 0, 101, 114, 2, 108, 0, 101, 114, 2, 109, 0, 4, 8, 3, 111, 82, 0, 8, 2, 105, 99, 116, 0, 8, 2, 105, 115, 0, 101, 8, 2, 110, 116, 3, 111, 82, 119, 0, 101, 114, 8, 2, 115, 3, 111, 82, 126, 0, 4, 1, 108, 2, 101, 108, 3, 119, 82, 0, 5, 3, 8, 2, 111, 108, 117, 0, 8, 2, 105, 0, 97, 8, 2, 110, 101, 3, 119, 82, 13, 0, 101, 114, 121, 3, 119, 82, 34, 111, 0, 4, 101, 114, 1, 108, 99, 3, 119, 82, 112, 0, 101, 114, 2, 32, 0, 101, 114, 8, 0, 4, 1, 108, 108, 97, 3, 127, 82, 0, 1, 114, 98, 98, 97, 0, 1, 116, 115, 2, 101, 0, 2, 105, 108, 0, 101, 1, 108, 99, 2, 108, 0, 101, 8, 0, 101, 110, 8, 3, 127, 82, 13, 50, 0, 4, 101, 114, 1, 102, 2, 12, 3, 127, 82, 112, 0, 101, 114, 5, 35, 8, 108, 0, 7, 6, 101, 120, 0, 4, 8, 3, 2, 119, 49, 87, 0, 99, 2, 105, 0, 99, 8, 2, 101, 0, 116, 114, 97, 2, 111, 114, 3, 2, 119, 49, 87, 47, 34, 0, 116, 114, 97, 118, 97, 2, 103, 3, 2, 119, 49, 87, 47, 34, 35, 82, 13, 0, 112, 101, 114, 105, 109, 3, 2, 119, 49, 87, 48, 119, 34, 120, 63, 0, 4, 8, 2, 17, 65, 3, 2, 119, 79, 86, 0, 104, 8, 0, 1, 21, 2, 105, 97, 3, 6, 119, 49, 87, 0, 4, 1, 17, 67, 2, 101, 3, 119, 49, 87, 0, 2, 101, 114, 99, 0, 2, 112, 101, 114, 116, 0, 99, 101, 2, 108, 108, 101, 110, 3, 119, 49, 87, 13, 0, 116, 101, 114, 2, 17, 67, 3, 119, 49, 87, 47, 6, 126, 0, 116, 114, 97, 2, 112, 111, 108, 3, 119, 49, 87, 47, 34, 6, 35, 0, 4, 116, 114, 97, 3, 119, 49, 87, 47, 34, 13, 0, 116, 114, 111, 8, 0, 116, 114, 97, 2, 99, 116, 3, 119, 49, 87, 47, 34, 35, 0, 116, 114, 97, 2, 110, 21, 3, 119, 49, 87, 47, 34, 136, 0, 112, 101, 100, 2, 105, 116, 3, 119, 49, 87, 48, 13, 70, 0, 99, 97, 118, 3, 119, 49, 87, 49, 13, 82, 0, 111, 114, 2, 99, 3, 119, 49, 87, 112, 0, 101, 2, 99, 117, 116, 105, 111, 3, 119, 49, 87, 120, 0, 8, 2, 105, 116, 3, 119, 79, 86, 0, 1, 115, 115, 2, 32, 3, 120, 49, 87, 0, 7, 6, 101, 121, 0, 1, 10, 2, 32, 3, 2, 120, 0, 111, 114, 2, 32, 3, 6, 136, 112, 0, 101, 100, 2, 32, 14, 128, 128, 130, 3, 70, 0, 1, 21, 2, 17, 67, 21, 3, 120, 0, 8, 107, 2, 12, 3, 127, 0, 4, 3, 135, 0, 101, 8, 0, 4, 1, 17, 67, 29, 3, 136, 0, 1, 118, 17, 67, 2, 32, 0, 2, 97, 110, 0, 8, 98, 97, 0, 101, 0, 101, 114, 1, 109, 21, 2, 32, 3, 143, 0, 7, 6, 105, 97, 0, 4, 1, 102, 2, 110, 116, 3, 6, 142, 0, 1, 102, 101, 2, 110, 99, 101, 0, 1, 108, 2, 110, 99, 101, 0, 1, 108, 112, 2, 110, 116, 0, 104, 2, 32, 0, 116, 104, 3, 6, 142, 85, 0, 1, 21, 2, 32, 3, 8, 37, 13, 0, 114, 121, 1, 10, 3, 8, 57, 13, 34, 2, 120, 0, 116, 101, 1, 21, 2, 32, 3, 8, 111, 136, 47, 0, 99, 1, 10, 2, 32, 3, 8, 120, 35, 49, 0, 4, 1, 21, 2, 116, 105, 118, 101, 3, 8, 139, 0, 1, 21, 21, 2, 32, 0, 114, 121, 1, 108, 10, 3, 8, 139, 34, 2, 120, 0, 2, 110, 103, 32, 3, 57, 35, 0, 4, 1, 114, 2, 98, 3, 111, 13, 0, 1, 116, 2, 98, 0, 2, 109, 0, 103, 101, 1, 10, 2, 32, 3, 111, 73, 0, 114, 100, 2, 32, 3, 111, 112, 70, 0, 114, 99, 104, 3, 111, 125, 49, 0, 105, 3, 111, 135, 0, 4, 1, 21, 2, 110, 105, 99, 3, 120, 6, 35, 0, 1, 21, 2, 110, 105, 116, 0, 8, 102, 2, 110, 99, 3, 120, 6, 122, 0, 110, 99, 101, 8, 102, 3, 120, 6, 122, 50, 87, 136, 0, 114, 97, 2, 32, 3, 120, 6, 124, 34, 13, 0, 4, 1, 108, 97, 2, 110, 116, 3, 120, 13, 0, 1, 108, 108, 105, 2, 110, 116, 0, 4, 116, 101, 1, 103, 2, 32, 3, 120, 13, 47, 0, 116, 101, 1, 114, 112, 111, 2, 32, 0, 110, 1, 21, 2, 99, 121, 3, 120, 13, 50, 0, 1, 112, 2, 110, 111, 3, 120, 35, 0, 114, 2, 105, 17, 67, 3, 120, 35, 34, 0, 105, 115, 1, 108, 3, 120, 136, 86, 0, 1, 21, 2, 110, 97, 3, 127, 6, 35, 0, 1, 108, 10, 2, 110, 99, 101, 3, 127, 13, 0, 4, 1, 17, 67, 29, 3, 135, 13, 0, 1, 102, 2, 98, 0, 114, 5, 8, 1, 17, 67, 3, 135, 117, 0, 4, 1, 10, 2, 110, 3, 139, 0, 8, 112, 2, 110, 17, 65, 0, 110, 8, 3, 139, 50, 0, 114, 1, 108, 21, 2, 32, 3, 140, 0, 4, 114, 3, 143, 0, 114, 1, 17, 67, 0, 7, 6, 105, 101, 0, 1, 10, 2, 32, 3, 2, 37, 0, 117, 1, 108, 2, 116, 101, 3, 2, 119, 81, 0, 8, 118, 2, 116, 3, 2, 139, 0, 110, 101, 1, 100, 2, 32, 3, 6, 135, 127, 50, 0, 116, 121, 1, 21, 3, 6, 142, 47, 2, 120, 0, 108, 1, 114, 10, 2, 32, 3, 8, 127, 116, 0, 115, 116, 1, 10, 2, 32, 14, 128, 130, 131, 3, 13, 87, 47, 0, 121, 2, 32, 3, 37, 0, 108, 1, 110, 10, 2, 32, 3, 57, 116, 0, 4, 119, 3, 57, 132, 0, 119, 2, 32, 0, 100, 2, 32, 14, 128, 130, 130, 3, 70, 0, 100, 115, 2, 32, 14, 128, 130, 131, 3, 70, 86, 0, 115, 2, 32, 14, 128, 130, 130, 3, 86, 0, 4, 2, 108, 108, 17, 65, 3, 111, 6, 119, 0, 2, 110, 17, 67, 105, 17, 65, 0, 2, 116, 116, 0, 114, 1, 10, 2, 121, 3, 111, 13, 34, 0, 115, 99, 3, 111, 119, 87, 0, 1, 100, 101, 109, 2, 118, 97, 108, 3, 111, 127, 0, 114, 114, 101, 2, 32, 3, 111, 138, 0, 114, 1, 10, 2, 32, 24, 14, 128, 130, 130, 3, 112, 0, 114, 39, 115, 1, 10, 2, 32, 24, 14, 128, 130, 132, 3, 112, 86, 0, 1, 114, 102, 2, 110, 100, 3, 119, 0, 4, 3, 120, 0, 1, 112, 112, 2, 32, 0, 1, 115, 2, 118, 101, 0, 2, 110, 116, 97, 108, 3, 120, 6, 119, 0, 110, 110, 3, 120, 6, 119, 50, 0, 2, 103, 111, 3, 120, 6, 136, 0, 114, 2, 97, 3, 120, 6, 138, 34, 0, 100, 108, 121, 3, 120, 70, 55, 2, 120, 0, 4, 1, 29, 3, 127, 0, 1, 102, 2, 110, 100, 0, 1, 103, 2, 110, 0, 1, 114, 112, 2, 115, 116, 0, 2, 99, 101, 0, 2, 102, 0, 2, 107, 0, 2, 108, 0, 2, 118, 0, 2, 118, 101, 0, 2, 122, 0, 8, 114, 0, 8, 122, 0, 104, 2, 17, 67, 0, 115, 116, 97, 3, 127, 6, 119, 87, 47, 13, 0, 106, 3, 127, 6, 136, 0, 103, 2, 101, 13, 3, 127, 73, 0, 4, 115, 1, 99, 101, 112, 115, 2, 32, 3, 127, 86, 0, 115, 1, 114, 101, 115, 2, 32, 0, 105, 2, 32, 3, 127, 135, 0, 117, 1, 108, 3, 132, 0, 117, 116, 101, 5, 3, 1, 108, 3, 132, 47, 6, 119, 0, 4, 1, 112, 2, 32, 3, 135, 0, 2, 32, 0, 2, 99, 0, 8, 116, 2, 17, 66, 0, 8, 116, 103, 111, 104, 0, 5, 8, 8, 99, 115, 2, 110, 3, 135, 117, 0, 4, 1, 10, 2, 116, 32, 3, 139, 0, 1, 21, 2, 116, 104, 0, 2, 110, 0, 4, 114, 3, 140, 0, 114, 2, 99, 0, 4, 1, 99, 115, 2, 110, 99, 3, 142, 0, 1, 108, 99, 2, 110, 116, 0, 2, 110, 116, 105, 17, 67, 0, 2, 116, 0, 8, 99, 115, 2, 110, 0, 4, 8, 104, 2, 114, 3, 143, 0, 114, 1, 108, 112, 2, 32, 0, 114, 8, 114, 17, 67, 0, 7, 6, 105, 103, 0, 110, 1, 115, 2, 111, 3, 2, 120, 50, 57, 0, 4, 2, 110, 111, 3, 2, 120, 79, 0, 8, 2, 110, 105, 0, 8, 109, 2, 114, 97, 116, 3, 2, 135, 79, 0, 110, 101, 2, 32, 3, 6, 127, 50, 0, 4, 117, 2, 32, 3, 6, 127, 79, 0, 117, 2, 101, 0, 97, 110, 1, 110, 2, 32, 3, 8, 120, 79, 13, 50, 0, 110, 111, 110, 2, 32, 3, 37, 50, 57, 122, 50, 0, 101, 111, 3, 120, 73, 13, 0, 105, 98, 1, 10, 3, 120, 73, 13, 69, 0, 4, 1, 100, 2, 110, 17, 65, 3, 120, 79, 0, 2, 110, 97, 0, 2, 110, 111, 109, 0, 110, 111, 2, 114, 97, 110, 3, 120, 79, 50, 112, 0, 1, 109, 97, 2, 97, 32, 3, 127, 79, 0, 4, 1, 21, 2, 110, 32, 3, 135, 0, 1, 21, 2, 110, 101, 0, 104, 1, 104, 0, 104, 1, 110, 0, 104, 1, 115, 0, 104, 2, 116, 0, 4, 110, 2, 17, 67, 3, 135, 50, 0, 110, 2, 32, 0, 109, 2, 32, 3, 135, 63, 0, 4, 1, 116, 2, 101, 12, 3, 135, 79, 0, 8, 109, 2, 114, 97, 0, 8, 116, 2, 114, 0, 7, 6, 105, 109, 0, 4, 8, 2, 21, 3, 2, 120, 63, 0, 8, 2, 112, 101, 114, 17, 67, 21, 14, 128, 132, 130, 0, 8, 2, 112, 114, 101, 21, 14, 128, 132, 130, 0, 109, 8, 2, 21, 0, 4, 2, 112, 101, 99, 117, 3, 4, 120, 63, 0, 2, 112, 111, 114, 116, 117, 0, 2, 112, 114, 101, 103, 110, 97, 0, 2, 112, 114, 101, 115, 97, 0, 109, 2, 97, 116, 0, 109, 2, 101, 109, 0, 105, 108, 101, 1, 115, 3, 6, 120, 63, 111, 55, 120, 0, 1, 104, 115, 2, 97, 32, 3, 6, 127, 63, 0, 111, 117, 115, 1, 21, 2, 32, 3, 8, 120, 63, 13, 87, 0, 4, 1, 21, 2, 101, 116, 114, 3, 120, 63, 0, 1, 108, 0, 1, 108, 2, 101, 114, 0, 2, 97, 103, 101, 0, 2, 101, 110, 116, 12, 0, 2, 105, 116, 0, 2, 112, 97, 99, 0, 2, 112, 101, 116, 117, 115, 0, 2, 112, 108, 97, 110, 116, 32, 0, 2, 112, 108, 101, 0, 2, 112, 108, 105, 99, 97, 0, 2, 112, 114, 111, 118, 105, 115, 0, 2, 112, 117, 108, 115, 101, 32, 0, 2, 117, 109, 0, 109, 2, 105, 103, 0, 109, 2, 105, 110, 0, 109, 2, 117, 110, 105, 115, 0, 101, 2, 110, 116, 111, 3, 120, 63, 6, 119, 0, 109, 111, 2, 98, 105, 3, 120, 63, 6, 134, 0, 112, 111, 2, 116, 101, 110, 3, 120, 63, 48, 13, 0, 4, 101, 2, 116, 101, 114, 32, 3, 120, 63, 127, 0, 101, 2, 116, 114, 101, 0, 1, 10, 2, 32, 3, 121, 63, 0, 4, 1, 108, 99, 3, 135, 63, 0, 5, 3, 1, 115, 2, 117, 108, 116, 0, 8, 114, 112, 2, 97, 0, 98, 1, 108, 99, 0, 101, 1, 108, 0, 101, 1, 100, 2, 110, 115, 3, 135, 63, 119, 0, 7, 6, 105, 110, 0, 4, 8, 2, 21, 14, 128, 132, 130, 3, 2, 120, 50, 0, 8, 2, 99, 111, 114, 112, 0, 8, 2, 99, 114, 101, 100, 0, 8, 2, 115, 116, 105, 108, 0, 8, 2, 116, 101, 103, 114, 105, 0, 110, 8, 2, 117, 109, 0, 116, 8, 2, 101, 114, 105, 111, 12, 3, 2, 120, 50, 47, 0, 116, 114, 97, 8, 2, 17, 67, 17, 67, 3, 2, 120, 50, 47, 34, 35, 0, 116, 101, 114, 8, 2, 114, 111, 103, 3, 2, 120, 50, 47, 119, 0, 4, 116, 101, 114, 8, 2, 110, 32, 3, 2, 120, 50, 47, 126, 0, 116, 101, 114, 8, 2, 110, 97, 108, 0, 116, 101, 114, 8, 2, 112, 111, 108, 21, 0, 116, 101, 114, 8, 2, 112, 114, 0, 116, 101, 114, 112, 114, 101, 2, 116, 3, 2, 120, 50, 47, 126, 48, 34, 120, 0, 100, 8, 2, 101, 102, 105, 110, 3, 2, 120, 50, 70, 0, 102, 114, 97, 8, 2, 99, 3, 2, 120, 50, 81, 34, 35, 0, 102, 97, 8, 2, 108, 3, 2, 120, 50, 81, 35, 0, 4, 103, 1, 21, 2, 32, 12, 14, 128, 153, 131, 3, 2, 120, 66, 0, 103, 1, 108, 101, 2, 32, 12, 14, 128, 152, 131, 0, 103, 1, 109, 111, 21, 21, 2, 32, 14, 128, 152, 131, 0, 103, 1, 110, 101, 2, 32, 14, 128, 136, 131, 0, 103, 1, 114, 17, 66, 10, 2, 32, 0, 103, 1, 114, 101, 2, 32, 14, 128, 136, 131, 0, 103, 1, 117, 103, 111, 108, 2, 32, 14, 128, 136, 132, 0, 103, 1, 120, 10, 2, 32, 12, 14, 128, 136, 131, 0, 4, 103, 108, 121, 1, 21, 2, 32, 14, 128, 153, 133, 3, 2, 120, 66, 55, 2, 120, 0, 103, 108, 121, 1, 110, 101, 2, 32, 14, 128, 168, 133, 0, 103, 108, 121, 1, 114, 101, 2, 32, 14, 128, 168, 133, 0, 4, 103, 109, 101, 110, 116, 1, 21, 2, 32, 14, 128, 153, 135, 3, 2, 120, 66, 63, 13, 50, 47, 0, 103, 109, 101, 110, 116, 1, 114, 101, 2, 32, 14, 128, 136, 135, 0, 4, 103, 115, 1, 21, 2, 32, 14, 128, 153, 132, 3, 2, 120, 66, 86, 0, 103, 115, 1, 110, 101, 2, 32, 14, 128, 136, 132, 0, 103, 115, 1, 114, 101, 2, 32, 14, 128, 136, 132, 0, 4, 8, 2, 100, 101, 14, 128, 132, 130, 3, 4, 120, 50, 0, 8, 2, 100, 105, 115, 14, 128, 132, 130, 0, 8, 2, 100, 105, 118, 14, 128, 132, 130, 0, 8, 2, 101, 120, 14, 128, 132, 130, 0, 8, 2, 115, 101, 99, 14, 128, 132, 130, 0, 8, 2, 115, 105, 103, 110, 105, 102, 14, 128, 132, 130, 0, 8, 2, 115, 105, 110, 99, 14, 128, 132, 130, 0, 116, 101, 114, 8, 2, 17, 65, 14, 128, 132, 133, 3, 4, 120, 50, 47, 13, 34, 0, 116, 114, 111, 8, 2, 21, 3, 4, 120, 50, 47, 34, 13, 0, 116, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 4, 120, 50, 47, 112, 0, 102, 114, 97, 8, 2, 14, 128, 132, 133, 3, 4, 120, 50, 81, 34, 13, 0, 1, 21, 2, 99, 105, 97, 108, 3, 6, 120, 50, 0, 100, 97, 1, 21, 2, 32, 3, 6, 120, 50, 70, 13, 0, 2, 103, 97, 32, 3, 6, 120, 66, 0, 4, 1, 98, 2, 97, 32, 3, 6, 127, 50, 0, 1, 107, 2, 97, 32, 0, 1, 108, 2, 97, 32, 0, 1, 114, 2, 97, 32, 0, 1, 116, 2, 97, 32, 0, 105, 1, 21, 2, 32, 3, 6, 127, 50, 120, 0, 111, 2, 32, 3, 6, 127, 50, 134, 0, 105, 110, 1, 10, 2, 32, 3, 8, 13, 50, 120, 50, 0, 1, 109, 10, 2, 97, 108, 32, 3, 8, 120, 50, 0, 111, 117, 115, 1, 21, 2, 32, 3, 8, 120, 50, 13, 87, 0, 1, 21, 2, 97, 116, 101, 3, 8, 121, 50, 0, 4, 1, 115, 97, 98, 2, 32, 3, 13, 50, 0, 5, 7, 1, 10, 2, 32, 0, 101, 115, 115, 1, 103, 2, 32, 14, 128, 130, 132, 3, 50, 13, 87, 0, 4, 1, 109, 97, 120, 2, 101, 3, 111, 50, 0, 101, 1, 109, 114, 101, 2, 32, 0, 4, 1, 10, 2, 101, 110, 17, 67, 3, 120, 50, 0, 1, 99, 2, 101, 0, 1, 99, 110, 105, 2, 101, 0, 1, 103, 2, 101, 0, 1, 107, 2, 100, 101, 114, 103, 0, 1, 107, 2, 100, 108, 0, 1, 107, 2, 100, 114, 0, 1, 114, 116, 2, 105, 0, 2, 100, 101, 120, 0, 2, 100, 105, 97, 0, 2, 101, 97, 0, 2, 101, 101, 0, 2, 102, 105, 110, 105, 116, 101, 0, 2, 115, 101, 99, 116, 0, 8, 2, 98, 0, 8, 2, 99, 97, 110, 0, 8, 2, 99, 101, 110, 115, 0, 8, 2, 99, 104, 0, 8, 2, 99, 111, 109, 17, 65, 0, 8, 2, 99, 114, 101, 0, 8, 2, 99, 117, 98, 0, 8, 2, 99, 117, 108, 0, 8, 2, 100, 105, 99, 0, 8, 2, 100, 105, 103, 111, 0, 8, 2, 100, 111, 108, 0, 8, 2, 102, 97, 109, 0, 8, 2, 102, 105, 100, 0, 8, 2, 102, 105, 108, 0, 8, 2, 102, 108, 111, 0, 8, 2, 102, 108, 117, 0, 8, 2, 102, 111, 32, 0, 8, 2, 106, 117, 114, 0, 8, 2, 108, 0, 8, 2, 109, 0, 8, 2, 111, 102, 0, 8, 2, 111, 114, 103, 0, 8, 2, 112, 0, 8, 2, 113, 117, 101, 0, 8, 2, 113, 117, 105, 115, 0, 8, 2, 114, 0, 8, 2, 115, 101, 116, 0, 8, 2, 115, 104, 0, 8, 2, 115, 105, 103, 104, 0, 8, 2, 115, 111, 102, 0, 8, 2, 115, 111, 108, 97, 0, 8, 2, 115, 111, 108, 101, 0, 8, 2, 115, 111, 109, 117, 0, 8, 2, 115, 112, 105, 114, 0, 8, 2, 115, 116, 97, 110, 0, 8, 2, 115, 116, 105, 0, 8, 2, 115, 116, 114, 117, 109, 0, 8, 2, 115, 117, 98, 0, 8, 2, 115, 117, 108, 0, 8, 2, 116, 97, 107, 0, 8, 2, 116, 101, 103, 0, 8, 2, 116, 105, 109, 97, 0, 8, 2, 116, 111, 110, 97, 0, 8, 2, 117, 110, 0, 8, 2, 118, 111, 105, 0, 8, 2, 119, 97, 0, 101, 1, 108, 97, 110, 2, 32, 0, 101, 1, 108, 117, 2, 32, 0, 110, 8, 2, 25, 0, 101, 120, 8, 2, 111, 114, 3, 120, 50, 6, 119, 49, 87, 0, 4, 105, 1, 102, 21, 2, 116, 101, 3, 120, 50, 13, 0, 110, 111, 8, 2, 99, 101, 0, 110, 111, 8, 2, 118, 0, 101, 114, 97, 1, 109, 2, 108, 3, 120, 50, 13, 34, 13, 0, 116, 101, 2, 108, 108, 101, 99, 3, 120, 50, 47, 13, 0, 116, 101, 114, 102, 101, 114, 3, 120, 50, 47, 13, 81, 6, 140, 0, 116, 101, 114, 2, 101, 115, 116, 3, 120, 50, 47, 34, 0, 116, 114, 105, 103, 117, 3, 120, 50, 47, 34, 6, 127, 79, 0, 4, 116, 114, 97, 8, 3, 120, 50, 47, 34, 13, 0, 116, 114, 111, 8, 2, 118, 0, 116, 114, 105, 99, 97, 3, 120, 50, 47, 34, 120, 49, 13, 0, 116, 101, 114, 2, 118, 105, 101, 119, 3, 120, 50, 47, 112, 0, 99, 114, 101, 109, 3, 120, 50, 49, 34, 120, 63, 0, 100, 101, 108, 105, 8, 2, 98, 3, 120, 50, 70, 6, 119, 55, 13, 0, 100, 105, 8, 2, 103, 101, 110, 3, 120, 50, 70, 6, 120, 0, 100, 105, 103, 101, 8, 2, 115, 3, 120, 50, 70, 120, 73, 6, 119, 0, 103, 1, 114, 102, 110, 3, 120, 50, 73, 0, 102, 97, 110, 8, 3, 120, 50, 81, 13, 50, 0, 102, 111, 114, 2, 109, 97, 116, 105, 111, 3, 120, 50, 81, 112, 0, 115, 116, 97, 110, 116, 8, 3, 120, 50, 87, 47, 13, 50, 47, 0, 99, 105, 2, 100, 101, 3, 120, 50, 87, 120, 0, 4, 105, 1, 109, 100, 97, 3, 120, 50, 120, 0, 105, 8, 109, 0, 117, 116, 101, 8, 109, 2, 109, 3, 120, 50, 120, 47, 0, 105, 97, 116, 117, 114, 1, 109, 3, 120, 50, 120, 74, 112, 0, 105, 115, 109, 2, 32, 3, 120, 50, 120, 86, 13, 63, 0, 101, 1, 118, 2, 103, 3, 120, 50, 121, 0, 4, 2, 103, 111, 116, 3, 120, 66, 0, 8, 2, 103, 114, 111, 0, 8, 2, 107, 0, 1, 21, 2, 97, 116, 105, 111, 110, 3, 121, 50, 0, 4, 101, 1, 99, 21, 2, 32, 3, 127, 50, 0, 101, 1, 100, 10, 2, 32, 0, 101, 1, 104, 99, 17, 65, 2, 32, 0, 101, 1, 104, 112, 2, 32, 0, 101, 1, 108, 105, 2, 32, 0, 101, 1, 108, 111, 2, 32, 0, 101, 1, 114, 21, 2, 32, 0, 101, 1, 116, 21, 2, 32, 0, 101, 1, 122, 2, 32, 0, 4, 1, 98, 2, 100, 3, 135, 50, 0, 1, 102, 2, 97, 0, 1, 102, 2, 100, 0, 1, 103, 21, 2, 97, 32, 0, 1, 104, 2, 100, 17, 66, 0, 1, 104, 2, 100, 32, 0, 1, 104, 99, 2, 97, 0, 1, 104, 101, 98, 2, 100, 0, 1, 104, 115, 2, 105, 0, 1, 107, 2, 100, 0, 1, 108, 98, 2, 100, 0, 1, 109, 2, 100, 0, 1, 114, 103, 2, 100, 0, 1, 119, 2, 100, 101, 114, 32, 0, 1, 119, 2, 100, 105, 110, 103, 0, 1, 119, 101, 114, 2, 100, 0, 1, 119, 110, 117, 2, 100, 0, 8, 114, 2, 100, 0, 101, 1, 112, 2, 32, 0, 101, 1, 114, 99, 2, 32, 0, 101, 1, 116, 110, 101, 21, 21, 2, 32, 0, 117, 8, 109, 2, 116, 101, 3, 135, 50, 6, 57, 132, 0, 7, 6, 105, 111, 0, 110, 101, 2, 32, 3, 6, 142, 50, 37, 0, 117, 115, 1, 103, 2, 32, 3, 8, 13, 87, 0, 117, 115, 1, 21, 2, 32, 3, 8, 111, 13, 87, 0, 1, 10, 2, 32, 3, 8, 111, 134, 0, 110, 5, 8, 1, 10, 2, 32, 3, 8, 120, 123, 50, 0, 5, 7, 1, 10, 2, 32, 3, 8, 127, 134, 0, 4, 110, 1, 10, 2, 32, 3, 8, 139, 50, 0, 110, 1, 110, 0, 4, 1, 103, 2, 110, 12, 3, 13, 0, 1, 104, 115, 2, 110, 0, 117, 2, 114, 17, 65, 3, 57, 13, 0, 4, 114, 1, 10, 2, 32, 3, 57, 112, 0, 117, 114, 2, 25, 0, 2, 108, 105, 32, 3, 111, 6, 134, 0, 1, 109, 2, 110, 3, 111, 122, 0, 1, 100, 114, 97, 99, 3, 111, 134, 0, 114, 105, 116, 121, 3, 120, 6, 122, 34, 111, 47, 2, 120, 0, 2, 116, 32, 3, 120, 13, 0, 114, 1, 114, 2, 32, 3, 120, 112, 0, 2, 32, 3, 127, 134, 0, 117, 120, 3, 132, 0, 4, 1, 98, 2, 108, 111, 103, 121, 3, 135, 122, 0, 1, 118, 0, 8, 2, 110, 0, 1, 98, 3, 135, 134, 0, 114, 1, 10, 2, 12, 3, 140, 0, 4, 1, 118, 2, 108, 3, 142, 0, 1, 122, 2, 110, 0, 8, 114, 2, 116, 0, 110, 8, 108, 3, 142, 50, 0, 7, 6, 105, 114, 0, 4, 2, 97, 116, 3, 2, 135, 34, 0, 2, 101, 99, 116, 0, 4, 1, 21, 2, 111, 32, 3, 6, 139, 34, 0, 2, 97, 32, 0, 2, 105, 32, 0, 2, 97, 98, 108, 101, 3, 6, 143, 0, 2, 97, 116, 101, 3, 8, 139, 34, 0, 1, 112, 115, 97, 2, 105, 3, 34, 0, 8, 2, 114, 101, 21, 14, 128, 132, 130, 3, 111, 0, 4, 2, 111, 3, 111, 34, 0, 8, 2, 97, 0, 4, 2, 114, 111, 3, 120, 0, 2, 114, 117, 0, 8, 2, 114, 17, 65, 0, 4, 1, 21, 2, 97, 116, 105, 111, 110, 3, 120, 34, 0, 1, 109, 2, 97, 99, 0, 1, 112, 0, 2, 105, 0, 4, 3, 126, 0, 1, 116, 115, 2, 32, 0, 4, 1, 103, 2, 111, 3, 135, 34, 0, 1, 118, 2, 117, 115, 0, 2, 101, 116, 121, 0, 8, 2, 105, 115, 104, 0, 8, 17, 67, 2, 111, 32, 0, 111, 110, 2, 17, 65, 3, 135, 34, 6, 122, 50, 0, 4, 101, 1, 99, 2, 110, 3, 135, 34, 13, 0, 111, 1, 118, 2, 110, 0, 101, 5, 8, 3, 135, 117, 0, 1, 17, 67, 21, 2, 32, 3, 140, 0, 4, 1, 115, 2, 101, 110, 3, 143, 0, 1, 115, 101, 100, 0, 2, 101, 101, 0, 97, 8, 112, 2, 99, 0, 101, 0, 101, 1, 112, 0, 101, 114, 2, 32, 3, 143, 34, 112, 0, 97, 108, 1, 112, 115, 3, 143, 34, 116, 0, 121, 2, 32, 3, 143, 34, 120, 0, 111, 110, 8, 3, 143, 50, 0, 4, 5, 5, 3, 145, 0, 5, 5, 1, 116, 115, 2, 32, 0, 7, 6, 105, 115, 0, 4, 1, 21, 2, 99, 111, 32, 3, 6, 120, 87, 0, 1, 21, 2, 116, 105, 99, 0, 99, 1, 21, 2, 101, 110, 17, 67, 0, 115, 2, 97, 32, 0, 115, 105, 109, 111, 2, 32, 3, 6, 120, 87, 120, 63, 134, 0, 116, 101, 1, 21, 2, 32, 3, 6, 127, 87, 47, 0, 1, 114, 2, 121, 32, 3, 8, 13, 87, 0, 1, 115, 17, 67, 21, 2, 32, 3, 8, 120, 87, 0, 116, 97, 110, 1, 21, 2, 32, 3, 8, 120, 87, 47, 35, 50, 0, 97, 5, 3, 2, 116, 105, 111, 110, 3, 13, 86, 136, 0, 8, 100, 2, 101, 3, 111, 87, 0, 104, 1, 10, 2, 32, 3, 111, 89, 0, 4, 109, 1, 17, 66, 105, 21, 2, 32, 14, 128, 144, 131, 3, 120, 86, 13, 63, 0, 109, 1, 21, 2, 32, 14, 128, 145, 131, 0, 109, 1, 110, 97, 2, 32, 14, 128, 144, 131, 0, 4, 1, 98, 2, 32, 3, 120, 87, 0, 1, 99, 2, 32, 0, 1, 109, 17, 65, 114, 112, 0, 116, 97, 110, 105, 1, 21, 2, 32, 3, 120, 87, 47, 6, 124, 50, 120, 0, 4, 1, 118, 2, 99, 111, 117, 110, 3, 135, 0, 2, 108, 101, 32, 0, 8, 2, 108, 101, 0, 108, 97, 110, 100, 8, 3, 135, 55, 13, 50, 70, 0, 4, 1, 10, 2, 97, 98, 108, 3, 135, 86, 0, 1, 118, 100, 97, 0, 2, 101, 114, 12, 32, 0, 2, 111, 32, 0, 2, 111, 114, 32, 0, 101, 2, 32, 0, 101, 2, 100, 32, 0, 101, 114, 2, 32, 3, 135, 86, 112, 0, 97, 2, 116, 105, 111, 110, 3, 135, 86, 136, 0, 4, 1, 114, 104, 99, 2, 116, 32, 3, 135, 87, 0, 2, 105, 118, 101, 0, 7, 6, 105, 116, 0, 105, 117, 115, 2, 32, 3, 6, 120, 89, 13, 87, 0, 4, 1, 116, 17, 65, 17, 67, 2, 32, 3, 6, 127, 47, 0, 2, 97, 32, 24, 0, 2, 105, 32, 0, 2, 111, 32, 0, 105, 115, 2, 32, 3, 6, 135, 47, 120, 87, 0, 1, 10, 2, 105, 118, 101, 32, 3, 8, 111, 47, 0, 4, 121, 1, 10, 2, 32, 3, 8, 111, 47, 2, 37, 0, 121, 1, 100, 10, 2, 32, 14, 128, 128, 131, 0, 121, 1, 100, 117, 29, 2, 32, 0, 1, 21, 21, 2, 97, 110, 32, 3, 8, 120, 47, 0, 111, 117, 115, 1, 10, 3, 8, 120, 47, 13, 87, 0, 97, 114, 121, 5, 3, 1, 10, 2, 32, 3, 13, 47, 119, 34, 2, 120, 0, 4, 1, 10, 2, 101, 32, 3, 120, 47, 0, 1, 98, 114, 111, 0, 1, 100, 101, 114, 99, 0, 1, 108, 2, 101, 114, 0, 1, 110, 97, 114, 103, 2, 101, 0, 1, 110, 105, 102, 110, 2, 101, 0, 1, 114, 99, 2, 101, 32, 0, 1, 114, 117, 2, 101, 0, 1, 115, 105, 117, 113, 2, 101, 0, 1, 115, 111, 112, 2, 101, 0, 2, 101, 114, 97, 116, 0, 8, 100, 101, 0, 121, 8, 17, 67, 2, 32, 3, 120, 47, 37, 0, 101, 115, 1, 115, 111, 112, 2, 32, 3, 120, 47, 87, 0, 104, 1, 108, 2, 101, 114, 3, 120, 84, 0, 114, 101, 1, 108, 3, 127, 47, 112, 0, 4, 1, 10, 2, 101, 32, 24, 3, 135, 47, 0, 1, 99, 2, 101, 32, 0, 1, 99, 2, 101, 114, 32, 0, 1, 109, 97, 2, 101, 0, 1, 110, 2, 114, 17, 65, 0, 1, 110, 117, 2, 101, 0, 1, 116, 2, 108, 0, 1, 118, 2, 97, 108, 0, 1, 118, 2, 101, 114, 32, 0, 2, 117, 109, 0, 8, 109, 2, 111, 0, 8, 112, 115, 2, 101, 0, 8, 115, 2, 101, 0, 101, 1, 114, 119, 0, 101, 1, 120, 2, 32, 0, 114, 111, 1, 110, 2, 103, 101, 3, 135, 47, 34, 13, 0, 114, 111, 1, 110, 3, 135, 47, 34, 134, 0, 101, 115, 1, 10, 2, 32, 3, 135, 47, 87, 0, 4, 104, 101, 1, 108, 3, 135, 84, 0, 104, 101, 2, 32, 0, 7, 6, 105, 118, 0, 4, 1, 114, 116, 110, 111, 99, 3, 6, 135, 82, 0, 1, 116, 99, 2, 97, 108, 0, 1, 118, 21, 2, 97, 108, 0, 97, 1, 108, 21, 2, 32, 3, 6, 135, 82, 13, 0, 4, 1, 17, 67, 17, 67, 29, 2, 101, 110, 3, 120, 82, 0, 1, 17, 67, 29, 2, 101, 108, 0, 1, 21, 2, 101, 0, 1, 104, 115, 2, 101, 114, 0, 1, 108, 2, 101, 114, 0, 1, 114, 2, 101, 108, 0, 1, 114, 2, 101, 110, 0, 1, 114, 2, 101, 114, 0, 1, 114, 2, 101, 116, 0, 8, 103, 2, 101, 0, 8, 108, 2, 101, 0, 8, 114, 2, 101, 114, 32, 0, 101, 2, 110, 101, 115, 115, 0, 4, 1, 100, 121, 2, 101, 3, 135, 82, 0, 1, 104, 2, 101, 32, 0, 1, 108, 2, 101, 110, 0, 1, 110, 2, 101, 32, 0, 1, 114, 100, 2, 101, 32, 0, 1, 114, 100, 2, 101, 114, 0, 1, 114, 101, 100, 2, 101, 0, 1, 114, 112, 101, 100, 2, 101, 0, 1, 118, 2, 101, 0, 1, 119, 2, 101, 32, 0, 2, 101, 13, 0, 2, 111, 114, 32, 0, 8, 2, 97, 110, 0, 8, 108, 2, 101, 17, 66, 0, 8, 108, 97, 2, 101, 0, 8, 114, 114, 97, 2, 101, 0, 101, 8, 108, 2, 17, 66, 0, 97, 108, 1, 114, 3, 135, 82, 116, 0, 7, 6, 108, 101, 0, 1, 116, 116, 2, 21, 3, 14, 55, 0, 4, 1, 10, 2, 32, 3, 55, 0, 1, 114, 10, 2, 32, 0, 1, 17, 67, 11, 2, 17, 66, 105, 97, 3, 55, 6, 127, 0, 4, 1, 17, 67, 10, 2, 115, 115, 3, 55, 13, 0, 1, 98, 17, 65, 2, 17, 67, 32, 0, 114, 1, 98, 17, 65, 2, 32, 0, 115, 115, 1, 21, 2, 32, 14, 128, 130, 132, 3, 55, 13, 87, 0, 115, 115, 110, 101, 115, 115, 1, 21, 2, 32, 14, 128, 130, 136, 3, 55, 13, 87, 50, 13, 87, 0, 115, 115, 108, 121, 1, 21, 2, 32, 14, 128, 130, 134, 3, 55, 13, 87, 55, 2, 120, 0, 114, 1, 98, 21, 2, 17, 67, 21, 3, 55, 112, 0, 103, 103, 101, 100, 3, 55, 119, 79, 120, 70, 0, 115, 115, 5, 8, 1, 21, 2, 32, 14, 128, 130, 132, 3, 55, 119, 87, 0, 115, 115, 110, 101, 115, 115, 5, 8, 1, 21, 2, 32, 14, 128, 130, 136, 3, 55, 119, 87, 50, 119, 87, 0, 115, 115, 108, 121, 5, 8, 1, 21, 2, 32, 14, 128, 130, 134, 3, 55, 119, 87, 55, 2, 120, 0, 109, 1, 112, 10, 2, 101, 110, 116, 3, 55, 120, 63, 0, 4, 1, 17, 67, 2, 116, 111, 110, 32, 3, 116, 0, 1, 17, 67, 10, 2, 32, 0, 1, 17, 67, 11, 2, 17, 66, 21, 0, 1, 98, 21, 2, 17, 67, 21, 0, 1, 100, 21, 2, 17, 66, 21, 0, 1, 116, 21, 2, 17, 67, 21, 0, 109, 1, 10, 2, 101, 110, 116, 3, 116, 63, 0, 100, 1, 98, 17, 65, 2, 32, 3, 116, 70, 0, 5, 8, 1, 17, 67, 10, 2, 32, 3, 119, 55, 0, 7, 6, 109, 105, 0, 4, 115, 8, 2, 116, 105, 109, 3, 63, 2, 120, 87, 0, 115, 8, 2, 116, 105, 116, 0, 115, 8, 2, 105, 110, 3, 63, 4, 120, 87, 0, 2, 115, 116, 97, 3, 63, 111, 0, 108, 108, 101, 110, 3, 63, 111, 55, 119, 50, 0, 115, 8, 2, 21, 14, 128, 132, 131, 3, 63, 111, 87, 0, 4, 2, 115, 115, 105, 3, 63, 120, 0, 8, 2, 110, 101, 114, 97, 0, 108, 108, 105, 8, 3, 63, 120, 55, 120, 0, 115, 101, 114, 97, 98, 3, 63, 120, 86, 14, 34, 13, 69, 0, 4, 115, 2, 99, 104, 105, 101, 3, 63, 120, 87, 0, 115, 2, 100, 101, 109, 0, 115, 2, 102, 105, 0, 115, 2, 104, 97, 112, 0, 115, 2, 116, 114, 97, 108, 0, 115, 2, 116, 114, 101, 115, 0, 115, 2, 116, 121, 0, 115, 8, 2, 116, 105, 0, 115, 115, 0, 115, 99, 105, 8, 2, 98, 3, 63, 120, 87, 13, 0, 115, 116, 108, 101, 3, 63, 120, 87, 116, 0, 115, 104, 2, 109, 97, 3, 63, 120, 89, 0, 8, 2, 110, 17, 65, 114, 3, 63, 135, 0, 99, 114, 2, 111, 3, 63, 135, 49, 34, 0, 99, 114, 111, 2, 17, 67, 17, 67, 21, 3, 63, 135, 49, 34, 122, 0, 99, 114, 111, 2, 17, 67, 17, 65, 21, 3, 63, 135, 49, 34, 134, 0, 115, 2, 101, 114, 3, 63, 135, 86, 0, 7, 6, 110, 103, 0, 4, 1, 17, 65, 109, 2, 121, 3, 50, 73, 0, 1, 105, 98, 2, 101, 114, 0, 1, 105, 103, 2, 101, 114, 0, 1, 117, 2, 121, 0, 2, 101, 0, 2, 105, 101, 32, 0, 2, 105, 116, 105, 0, 105, 2, 98, 3, 50, 73, 13, 0, 4, 101, 100, 3, 50, 73, 70, 0, 101, 100, 1, 111, 112, 115, 0, 4, 105, 110, 103, 1, 105, 104, 3, 50, 73, 111, 66, 0, 105, 110, 103, 1, 105, 114, 99, 0, 105, 110, 103, 1, 117, 2, 32, 0, 101, 1, 111, 99, 2, 115, 116, 3, 50, 73, 119, 0, 4, 1, 105, 114, 2, 101, 114, 3, 66, 0, 1, 105, 115, 2, 101, 114, 0, 2, 121, 0, 117, 101, 0, 101, 100, 1, 111, 3, 66, 70, 0, 4, 1, 97, 98, 2, 101, 114, 3, 66, 79, 0, 1, 97, 108, 99, 2, 101, 114, 0, 1, 105, 2, 101, 114, 0, 1, 111, 2, 101, 114, 0, 1, 117, 111, 121, 2, 101, 114, 0, 2, 17, 65, 0, 2, 101, 115, 116, 0, 2, 108, 0, 2, 114, 0, 8, 97, 2, 101, 114, 0, 8, 105, 114, 2, 101, 0, 105, 110, 103, 2, 32, 3, 66, 111, 66, 0, 7, 6, 111, 108, 0, 121, 1, 112, 32, 24, 3, 4, 122, 55, 120, 0, 111, 2, 103, 105, 3, 6, 122, 55, 13, 0, 4, 1, 21, 21, 2, 97, 114, 3, 6, 134, 55, 0, 1, 21, 21, 2, 117, 115, 0, 105, 115, 1, 112, 10, 3, 8, 13, 55, 120, 87, 0, 4, 1, 10, 2, 101, 110, 17, 67, 3, 13, 55, 0, 1, 10, 2, 111, 117, 115, 32, 0, 1, 109, 2, 101, 99, 0, 1, 112, 2, 105, 116, 101, 0, 1, 115, 2, 105, 99, 0, 1, 115, 2, 105, 100, 105, 0, 1, 115, 2, 105, 108, 0, 108, 1, 112, 2, 117, 0, 108, 1, 114, 97, 99, 0, 111, 2, 103, 105, 99, 3, 13, 55, 6, 122, 0, 101, 1, 109, 2, 115, 116, 3, 13, 55, 119, 0, 105, 99, 101, 1, 112, 3, 13, 55, 127, 87, 0, 102, 1, 119, 3, 115, 55, 81, 0, 118, 1, 119, 3, 115, 55, 82, 0, 4, 1, 114, 116, 101, 112, 2, 32, 3, 116, 0, 1, 116, 115, 10, 2, 32, 0, 8, 100, 105, 0, 4, 1, 10, 2, 105, 32, 3, 122, 55, 0, 1, 21, 2, 111, 32, 0, 1, 104, 2, 97, 114, 0, 1, 109, 2, 101, 99, 117, 108, 101, 0, 1, 115, 2, 101, 109, 0, 1, 116, 2, 101, 114, 0, 8, 100, 105, 2, 97, 0, 108, 1, 114, 98, 0, 108, 1, 114, 116, 2, 17, 65, 0, 108, 1, 116, 97, 0, 1, 99, 2, 111, 117, 114, 3, 123, 55, 0, 4, 1, 102, 2, 107, 3, 134, 0, 1, 121, 2, 107, 0, 4, 1, 114, 116, 110, 111, 99, 3, 134, 55, 0, 1, 116, 120, 101, 0, 2, 97, 110, 100, 32, 0, 2, 97, 114, 0, 8, 2, 97, 29, 0, 108, 1, 114, 0, 108, 1, 116, 0, 108, 1, 119, 0, 116, 3, 134, 55, 47, 0, 100, 3, 134, 55, 70, 0, 109, 2, 32, 3, 134, 63, 0, 7, 6, 111, 109, 0, 8, 2, 105, 17, 67, 3, 2, 134, 63, 0, 101, 1, 21, 2, 116, 114, 121, 3, 6, 122, 63, 13, 0, 4, 101, 1, 21, 2, 116, 114, 101, 3, 6, 122, 63, 120, 0, 101, 2, 116, 101, 114, 0, 105, 110, 2, 111, 3, 6, 122, 63, 120, 50, 0, 101, 1, 110, 105, 21, 21, 2, 32, 3, 6, 134, 63, 136, 0, 4, 1, 10, 2, 105, 115, 101, 32, 3, 8, 13, 63, 0, 1, 10, 2, 105, 122, 101, 32, 0, 1, 21, 2, 105, 115, 116, 32, 0, 121, 1, 10, 2, 32, 3, 8, 13, 63, 2, 120, 0, 4, 1, 10, 2, 32, 3, 13, 63, 0, 1, 100, 2, 101, 115, 116, 0, 1, 100, 2, 105, 110, 105, 0, 8, 100, 2, 97, 0, 97, 1, 116, 2, 116, 111, 3, 13, 63, 124, 0, 97, 1, 119, 2, 110, 3, 115, 63, 13, 0, 101, 1, 119, 2, 110, 3, 120, 63, 120, 0, 4, 1, 99, 2, 32, 3, 122, 63, 0, 1, 108, 103, 2, 101, 114, 0, 1, 114, 2, 32, 0, 8, 112, 2, 101, 0, 110, 105, 8, 2, 21, 3, 122, 63, 50, 6, 120, 0, 4, 1, 99, 2, 101, 3, 123, 63, 0, 1, 99, 2, 112, 97, 110, 0, 1, 115, 2, 101, 32, 0, 101, 8, 115, 0, 109, 1, 99, 2, 101, 0, 97, 99, 104, 1, 116, 115, 3, 123, 63, 13, 49, 0, 4, 98, 1, 116, 2, 25, 3, 132, 63, 0, 98, 1, 119, 2, 32, 0, 98, 101, 1, 99, 2, 32, 0, 4, 1, 110, 2, 97, 100, 3, 134, 63, 0, 1, 114, 2, 97, 110, 0, 1, 114, 104, 99, 0, 98, 1, 99, 2, 32, 0, 97, 110, 1, 114, 2, 116, 105, 3, 134, 63, 6, 35, 50, 0, 7, 6, 111, 110, 0, 1, 100, 2, 97, 116, 3, 2, 134, 50, 0, 4, 1, 21, 2, 105, 99, 97, 3, 6, 122, 50, 0, 1, 115, 114, 101, 112, 2, 105, 0, 121, 109, 111, 117, 115, 3, 6, 122, 50, 120, 63, 13, 87, 0, 4, 1, 112, 116, 115, 111, 112, 3, 6, 134, 50, 0, 2, 105, 32, 0, 105, 115, 109, 1, 10, 2, 32, 3, 8, 13, 50, 120, 86, 13, 63, 0, 105, 115, 116, 1, 10, 2, 32, 3, 8, 13, 50, 120, 87, 47, 0, 4, 1, 10, 2, 101, 114, 32, 3, 13, 50, 0, 1, 17, 67, 11, 2, 32, 0, 1, 21, 21, 2, 32, 0, 1, 98, 10, 2, 32, 0, 1, 99, 10, 2, 32, 0, 1, 99, 101, 2, 100, 0, 1, 100, 17, 67, 2, 32, 0, 1, 103, 114, 2, 32, 0, 1, 104, 112, 2, 101, 116, 105, 0, 1, 109, 2, 100, 32, 0, 1, 109, 10, 2, 32, 0, 1, 114, 97, 2, 32, 0, 1, 114, 100, 2, 32, 0, 1, 115, 10, 2, 32, 0, 1, 115, 114, 101, 112, 0, 1, 116, 10, 2, 32, 0, 1, 116, 111, 104, 112, 0, 121, 1, 10, 2, 32, 3, 13, 50, 2, 120, 0, 111, 117, 115, 1, 10, 3, 13, 50, 13, 87, 0, 101, 8, 3, 58, 122, 50, 0, 99, 101, 8, 2, 32, 3, 58, 122, 50, 87, 0, 101, 5, 6, 8, 3, 58, 123, 50, 0, 99, 101, 5, 6, 8, 2, 32, 3, 58, 123, 50, 87, 0, 101, 100, 1, 17, 67, 10, 2, 32, 14, 128, 136, 130, 3, 70, 0, 105, 110, 103, 1, 17, 67, 10, 2, 32, 14, 128, 136, 131, 3, 111, 66, 0, 4, 1, 103, 2, 101, 3, 122, 50, 0, 1, 108, 102, 2, 32, 0, 1, 108, 105, 2, 32, 0, 1, 108, 121, 2, 32, 0, 1, 110, 2, 101, 0, 1, 112, 2, 32, 12, 0, 1, 114, 99, 2, 32, 0, 1, 114, 111, 2, 32, 0, 1, 114, 116, 10, 2, 32, 0, 1, 119, 2, 107, 0, 1, 119, 2, 116, 0, 1, 120, 2, 32, 12, 0, 2, 97, 108, 100, 0, 5, 3, 1, 103, 97, 2, 32, 0, 5, 8, 1, 21, 2, 32, 12, 12, 0, 101, 1, 109, 2, 116, 105, 3, 122, 50, 111, 0, 4, 1, 109, 2, 101, 121, 3, 123, 50, 0, 1, 109, 2, 107, 0, 1, 109, 2, 116, 104, 0, 1, 114, 102, 2, 116, 0, 1, 115, 100, 2, 32, 0, 1, 119, 0, 8, 2, 105, 111, 0, 8, 104, 2, 101, 121, 0, 101, 1, 100, 110, 117, 2, 32, 0, 103, 8, 112, 115, 3, 123, 50, 73, 0, 101, 1, 109, 2, 116, 97, 3, 123, 50, 120, 0, 103, 5, 35, 1, 109, 2, 101, 114, 3, 123, 66, 79, 0, 4, 2, 97, 110, 32, 3, 134, 50, 0, 8, 112, 2, 121, 0, 101, 8, 2, 114, 3, 134, 50, 13, 0, 117, 115, 3, 134, 50, 13, 87, 0, 7, 6, 111, 111, 0, 1, 10, 2, 110, 3, 6, 132, 0, 4, 1, 17, 67, 2, 107, 3, 115, 0, 1, 102, 2, 116, 0, 1, 103, 2, 100, 0, 1, 104, 2, 100, 0, 1, 104, 2, 100, 0, 1, 104, 2, 107, 0, 1, 115, 2, 116, 0, 1, 116, 115, 2, 100, 0, 1, 119, 2, 100, 0, 1, 119, 2, 108, 0, 4, 1, 108, 98, 2, 100, 3, 123, 0, 1, 108, 102, 2, 100, 0, 4, 114, 3, 131, 0, 114, 2, 32, 0, 4, 3, 132, 0, 1, 107, 2, 107, 0, 1, 109, 2, 110, 32, 0, 1, 112, 2, 107, 0, 1, 112, 115, 2, 110, 32, 0, 1, 115, 2, 116, 104, 0, 8, 2, 114, 0, 116, 2, 105, 99, 32, 3, 132, 6, 122, 47, 0, 115, 101, 1, 104, 99, 3, 132, 86, 0, 4, 115, 2, 101, 3, 132, 87, 0, 115, 101, 1, 103, 0, 8, 99, 2, 112, 3, 134, 6, 122, 0, 114, 1, 99, 2, 100, 3, 134, 6, 130, 0, 115, 1, 104, 99, 2, 101, 110, 3, 134, 86, 0, 4, 114, 1, 112, 3, 141, 0, 114, 8, 109, 0, 7, 6, 111, 114, 0, 8, 102, 2, 115, 21, 3, 2, 130, 0, 4, 101, 1, 102, 2, 99, 108, 111, 3, 2, 131, 0, 101, 1, 102, 2, 103, 111, 0, 101, 1, 102, 2, 115, 101, 0, 101, 1, 102, 2, 116, 111, 0, 4, 1, 21, 2, 105, 99, 32, 3, 6, 122, 34, 0, 1, 21, 2, 105, 99, 97, 108, 0, 1, 21, 2, 99, 97, 32, 3, 6, 130, 0, 2, 105, 32, 3, 6, 130, 34, 0, 116, 101, 1, 102, 2, 32, 3, 6, 131, 47, 136, 0, 105, 108, 121, 1, 21, 2, 32, 3, 8, 13, 34, 13, 55, 2, 120, 0, 4, 1, 10, 2, 97, 116, 105, 111, 110, 3, 13, 34, 0, 2, 105, 103, 105, 110, 97, 0, 121, 1, 10, 2, 32, 3, 13, 34, 2, 120, 0, 101, 115, 99, 3, 13, 34, 6, 119, 87, 0, 105, 1, 104, 2, 122, 3, 13, 34, 135, 0, 101, 100, 1, 10, 2, 32, 3, 13, 70, 0, 103, 8, 102, 2, 17, 65, 118, 3, 13, 79, 0, 101, 100, 1, 104, 2, 32, 14, 128, 128, 129, 3, 70, 0, 4, 1, 10, 2, 32, 3, 112, 0, 1, 98, 98, 2, 110, 0, 1, 100, 110, 2, 32, 0, 1, 102, 2, 103, 17, 65, 116, 0, 1, 102, 10, 2, 100, 32, 0, 1, 102, 102, 101, 2, 116, 0, 1, 114, 114, 101, 116, 0, 1, 116, 110, 101, 118, 2, 32, 0, 101, 1, 116, 21, 2, 32, 0, 4, 1, 10, 2, 97, 116, 101, 3, 112, 34, 0, 1, 10, 2, 111, 117, 115, 0, 99, 101, 1, 119, 2, 115, 116, 3, 115, 0, 2, 114, 3, 122, 0, 4, 1, 21, 2, 105, 116, 105, 3, 122, 34, 0, 1, 21, 2, 105, 116, 121, 0, 1, 108, 102, 2, 105, 0, 1, 109, 2, 97, 108, 0, 2, 101, 17, 66, 32, 0, 2, 101, 110, 17, 67, 0, 2, 105, 103, 0, 5, 35, 8, 104, 2, 111, 0, 8, 2, 105, 17, 67, 0, 114, 8, 109, 0, 4, 97, 2, 99, 108, 3, 122, 34, 13, 0, 97, 8, 2, 116, 111, 0, 101, 105, 103, 110, 1, 102, 3, 122, 34, 13, 50, 0, 4, 101, 1, 102, 2, 115, 116, 3, 122, 34, 120, 0, 105, 1, 104, 2, 122, 111, 110, 116, 0, 1, 119, 2, 114, 3, 123, 0, 111, 117, 103, 104, 3, 123, 34, 13, 0, 111, 117, 103, 104, 5, 3, 3, 123, 34, 134, 0, 4, 1, 119, 3, 126, 0, 1, 119, 2, 109, 0, 1, 119, 2, 115, 101, 0, 1, 119, 2, 116, 104, 0, 5, 3, 2, 114, 3, 128, 0, 4, 1, 99, 2, 107, 3, 130, 0, 1, 102, 2, 101, 118, 101, 114, 0, 1, 102, 2, 107, 0, 1, 104, 99, 2, 100, 0, 1, 108, 2, 100, 0, 1, 121, 2, 107, 0, 2, 99, 104, 32, 0, 2, 101, 115, 105, 115, 0, 2, 109, 32, 0, 2, 110, 32, 0, 2, 115, 101, 32, 0, 2, 116, 0, 8, 0, 8, 99, 2, 21, 0, 8, 102, 2, 21, 0, 8, 109, 0, 101, 8, 102, 2, 17, 65, 0, 101, 8, 102, 2, 17, 67, 0, 116, 1, 109, 101, 2, 32, 0, 4, 3, 131, 0, 1, 99, 2, 101, 32, 0, 1, 100, 2, 32, 0, 1, 108, 112, 0, 1, 112, 2, 116, 0, 1, 116, 110, 2, 32, 0, 1, 116, 115, 2, 109, 0, 1, 119, 2, 101, 0, 1, 119, 2, 110, 0, 1, 119, 2, 116, 32, 0, 1, 119, 115, 2, 100, 0, 5, 8, 1, 10, 2, 32, 0, 5, 8, 1, 21, 21, 2, 32, 14, 128, 144, 130, 0, 101, 0, 101, 1, 116, 115, 2, 32, 0, 101, 8, 109, 0, 114, 2, 32, 0, 4, 1, 108, 104, 99, 2, 105, 99, 3, 131, 34, 0, 1, 108, 104, 99, 2, 111, 117, 115, 0, 2, 17, 65, 0, 2, 101, 17, 65, 0, 2, 101, 116, 0, 2, 101, 120, 0, 121, 8, 116, 115, 3, 131, 34, 120, 0, 4, 5, 5, 1, 119, 3, 146, 0, 5, 5, 1, 119, 2, 109, 0, 5, 5, 1, 119, 2, 115, 101, 0, 5, 5, 1, 119, 2, 116, 104, 0, 121, 5, 3, 1, 116, 17, 65, 21, 21, 2, 32, 3, 147, 34, 37, 0, 7, 6, 111, 115, 0, 2, 105, 116, 121, 3, 6, 122, 87, 0, 111, 1, 21, 2, 112, 104, 3, 6, 122, 87, 13, 0, 2, 97, 108, 32, 3, 6, 134, 86, 0, 2, 105, 118, 101, 3, 6, 134, 87, 0, 105, 115, 2, 32, 3, 6, 134, 87, 120, 87, 0, 117, 114, 101, 3, 6, 134, 88, 112, 0, 4, 1, 112, 2, 105, 116, 105, 111, 3, 13, 86, 0, 115, 1, 112, 2, 101, 115, 115, 0, 101, 1, 112, 114, 117, 112, 3, 13, 87, 0, 111, 1, 21, 2, 112, 104, 105, 99, 3, 13, 87, 6, 122, 0, 4, 116, 1, 112, 2, 101, 114, 105, 3, 122, 87, 47, 0, 116, 1, 112, 2, 117, 0, 116, 1, 112, 97, 0, 116, 1, 112, 101, 114, 0, 116, 1, 112, 101, 114, 112, 0, 116, 1, 112, 109, 105, 0, 116, 1, 112, 109, 111, 99, 0, 116, 1, 112, 120, 101, 0, 116, 1, 112, 121, 104, 0, 4, 5, 3, 1, 99, 2, 116, 3, 129, 87, 0, 5, 3, 1, 114, 102, 2, 116, 0, 115, 5, 3, 1, 98, 0, 115, 5, 3, 1, 108, 0, 115, 5, 3, 1, 109, 0, 115, 5, 3, 1, 114, 0, 8, 108, 2, 101, 3, 132, 86, 0, 4, 1, 29, 2, 121, 3, 134, 86, 0, 8, 114, 2, 101, 13, 0, 101, 2, 32, 0, 4, 1, 99, 2, 101, 99, 3, 134, 87, 0, 1, 99, 2, 105, 110, 101, 32, 0, 115, 1, 114, 103, 0, 4, 116, 1, 104, 2, 32, 3, 134, 87, 47, 0, 116, 1, 104, 103, 0, 116, 1, 109, 0, 116, 1, 112, 0, 7, 6, 111, 117, 0, 116, 8, 2, 21, 14, 128, 132, 131, 3, 2, 133, 47, 0, 1, 21, 2, 109, 32, 3, 6, 132, 0, 4, 115, 1, 17, 66, 10, 2, 32, 3, 8, 13, 87, 0, 115, 1, 114, 100, 10, 2, 32, 0, 4, 103, 104, 1, 114, 98, 2, 32, 3, 13, 0, 103, 104, 1, 114, 111, 0, 114, 101, 100, 1, 10, 3, 13, 70, 0, 4, 115, 1, 10, 2, 32, 3, 13, 87, 0, 115, 1, 108, 10, 2, 32, 0, 115, 1, 109, 10, 2, 32, 0, 115, 1, 110, 10, 2, 32, 0, 115, 121, 1, 10, 2, 32, 3, 13, 87, 2, 37, 0, 1, 104, 2, 109, 3, 57, 132, 0, 97, 3, 58, 124, 0, 4, 114, 1, 10, 2, 32, 3, 112, 0, 114, 1, 112, 17, 65, 0, 108, 2, 100, 3, 115, 0, 99, 101, 1, 108, 103, 2, 115, 3, 122, 0, 4, 103, 104, 1, 99, 3, 122, 81, 0, 103, 104, 1, 114, 116, 0, 4, 1, 99, 2, 110, 116, 114, 3, 123, 0, 1, 99, 2, 112, 108, 0, 1, 99, 2, 114, 97, 103, 0, 1, 99, 2, 115, 105, 0, 1, 100, 2, 98, 0, 1, 100, 2, 103, 0, 1, 110, 2, 114, 105, 0, 1, 114, 116, 2, 98, 108, 0, 1, 115, 2, 116, 104, 101, 114, 0, 1, 116, 2, 99, 104, 0, 1, 121, 2, 110, 103, 0, 4, 103, 104, 1, 108, 3, 123, 81, 0, 103, 104, 1, 110, 0, 103, 104, 1, 114, 0, 103, 104, 1, 116, 0, 4, 114, 3, 126, 0, 114, 1, 99, 2, 116, 101, 0, 114, 2, 110, 0, 114, 5, 3, 1, 99, 2, 97, 103, 0, 114, 5, 3, 1, 110, 2, 105, 0, 4, 103, 104, 1, 98, 2, 116, 3, 128, 0, 103, 104, 1, 104, 2, 116, 0, 103, 104, 1, 110, 2, 116, 0, 103, 104, 1, 114, 98, 2, 116, 0, 103, 104, 1, 114, 119, 0, 103, 104, 2, 116, 0, 103, 104, 8, 0, 4, 103, 104, 5, 3, 1, 99, 3, 129, 81, 0, 103, 104, 5, 3, 1, 114, 116, 0, 4, 114, 1, 98, 2, 110, 3, 131, 0, 114, 1, 99, 2, 115, 0, 114, 1, 99, 2, 116, 0, 114, 1, 99, 2, 116, 101, 115, 97, 0, 114, 1, 109, 2, 110, 0, 114, 1, 112, 0, 114, 1, 112, 110, 2, 32, 0, 114, 8, 102, 0, 114, 8, 121, 0, 114, 99, 101, 1, 115, 3, 131, 87, 0, 4, 1, 98, 2, 100, 3, 132, 0, 1, 98, 2, 108, 108, 0, 1, 99, 2, 116, 104, 0, 1, 104, 103, 2, 108, 0, 1, 107, 0, 1, 109, 2, 115, 115, 101, 0, 1, 110, 2, 103, 97, 0, 1, 114, 2, 98, 108, 0, 1, 114, 2, 116, 105, 110, 0, 1, 116, 2, 99, 97, 110, 0, 1, 119, 2, 110, 100, 17, 65, 0, 1, 119, 2, 110, 100, 17, 67, 0, 1, 121, 2, 116, 0, 2, 32, 0, 2, 102, 0, 2, 105, 0, 2, 108, 17, 65, 0, 2, 112, 0, 2, 118, 0, 2, 122, 0, 5, 35, 1, 114, 2, 116, 101, 0, 103, 104, 1, 114, 104, 116, 0, 120, 2, 32, 0, 103, 101, 1, 114, 3, 132, 88, 0, 99, 104, 1, 100, 3, 132, 89, 0, 4, 3, 133, 0, 1, 102, 2, 108, 101, 0, 1, 114, 17, 67, 2, 116, 0, 1, 121, 2, 116, 32, 0, 2, 116, 0, 98, 1, 100, 2, 116, 0, 103, 104, 1, 98, 0, 103, 104, 1, 100, 2, 116, 0, 103, 104, 1, 108, 112, 0, 103, 104, 1, 108, 115, 0, 103, 104, 1, 114, 100, 0, 4, 1, 98, 2, 108, 100, 3, 134, 0, 1, 104, 115, 2, 108, 100, 101, 114, 0, 1, 109, 2, 108, 17, 67, 0, 1, 112, 2, 108, 116, 0, 1, 115, 2, 108, 0, 103, 104, 0, 103, 104, 1, 100, 0, 103, 104, 1, 104, 0, 103, 104, 1, 108, 114, 0, 4, 114, 1, 98, 2, 115, 101, 3, 141, 0, 114, 1, 116, 0, 114, 1, 116, 2, 32, 0, 114, 1, 116, 2, 110, 0, 114, 5, 7, 8, 121, 0, 114, 8, 103, 2, 100, 0, 4, 114, 1, 99, 115, 3, 144, 0, 114, 1, 104, 0, 114, 1, 108, 102, 0, 114, 1, 115, 0, 114, 1, 116, 115, 0, 114, 1, 118, 101, 2, 101, 100, 0, 114, 1, 118, 101, 100, 0, 114, 8, 0, 114, 8, 100, 0, 4, 114, 5, 5, 3, 146, 0, 114, 5, 5, 1, 99, 2, 116, 101, 0, 114, 5, 5, 2, 110, 0, 7, 6, 111, 118, 0, 101, 114, 8, 2, 21, 14, 128, 132, 132, 3, 4, 134, 82, 112, 0, 105, 116, 99, 104, 1, 21, 2, 32, 3, 8, 13, 82, 120, 74, 0, 4, 1, 99, 2, 101, 110, 17, 67, 3, 122, 82, 0, 1, 104, 2, 101, 108, 0, 1, 104, 2, 101, 114, 0, 1, 110, 2, 101, 108, 0, 1, 114, 103, 2, 101, 108, 0, 1, 114, 112, 2, 101, 114, 0, 1, 114, 116, 2, 101, 114, 0, 8, 2, 117, 108, 0, 101, 114, 1, 112, 2, 21, 3, 122, 82, 13, 0, 101, 114, 101, 105, 103, 110, 1, 115, 3, 122, 82, 13, 34, 120, 50, 0, 4, 1, 99, 2, 101, 110, 3, 123, 82, 0, 1, 99, 2, 101, 116, 0, 1, 104, 115, 2, 12, 0, 1, 108, 0, 1, 108, 2, 101, 0, 8, 2, 101, 110, 0, 101, 1, 100, 0, 101, 8, 108, 0, 4, 101, 114, 1, 99, 3, 123, 82, 112, 0, 101, 114, 1, 99, 2, 32, 0, 101, 114, 110, 1, 103, 3, 123, 82, 112, 50, 0, 4, 1, 21, 2, 97, 108, 3, 132, 82, 0, 1, 109, 2, 17, 65, 0, 1, 109, 2, 105, 0, 1, 114, 112, 2, 101, 13, 0, 101, 114, 1, 114, 112, 2, 32, 3, 132, 82, 112, 0, 4, 1, 108, 99, 2, 101, 3, 134, 82, 0, 1, 108, 108, 117, 112, 0, 1, 108, 112, 0, 2, 101, 114, 0, 8, 2, 17, 65, 0, 8, 108, 115, 2, 101, 110, 17, 65, 0, 4, 101, 114, 1, 10, 2, 32, 3, 134, 82, 112, 0, 101, 114, 2, 99, 111, 97, 0, 101, 114, 2, 100, 111, 115, 0, 101, 114, 2, 100, 114, 97, 0, 101, 114, 2, 100, 114, 105, 0, 101, 114, 2, 115, 105, 103, 0, 101, 114, 2, 116, 111, 110, 0, 101, 114, 2, 118, 105, 101, 0, 7, 6, 111, 119, 0, 2, 105, 116, 122, 32, 3, 8, 134, 82, 0, 2, 97, 121, 32, 3, 13, 58, 0, 108, 101, 1, 110, 107, 2, 100, 3, 122, 55, 120, 0, 4, 1, 97, 3, 133, 0, 1, 98, 2, 101, 108, 0, 1, 98, 2, 101, 114, 0, 1, 98, 2, 115, 17, 65, 0, 1, 98, 2, 115, 112, 0, 1, 99, 0, 1, 100, 2, 110, 0, 1, 100, 110, 101, 0, 1, 102, 0, 1, 103, 0, 1, 104, 0, 1, 104, 99, 0, 1, 104, 115, 2, 101, 114, 0, 1, 104, 119, 0, 1, 104, 121, 0, 1, 106, 0, 1, 107, 0, 1, 108, 99, 0, 1, 108, 102, 2, 101, 114, 0, 1, 108, 103, 2, 101, 114, 0, 1, 108, 108, 97, 115, 105, 0, 1, 108, 112, 0, 1, 110, 2, 97, 100, 0, 1, 110, 101, 2, 110, 0, 1, 112, 0, 1, 114, 2, 100, 0, 1, 114, 98, 0, 1, 114, 99, 2, 110, 0, 1, 114, 100, 0, 1, 114, 102, 0, 1, 114, 103, 2, 108, 0, 1, 114, 112, 0, 1, 114, 116, 2, 101, 0, 1, 116, 2, 101, 108, 0, 1, 116, 2, 101, 114, 0, 1, 116, 2, 110, 0, 1, 118, 0, 1, 119, 0, 1, 121, 0, 8, 2, 108, 0, 8, 100, 0, 8, 108, 108, 97, 0, 8, 110, 2, 32, 0, 8, 110, 2, 116, 0, 4, 3, 134, 0, 1, 99, 115, 111, 109, 0, 1, 104, 115, 0, 7, 6, 112, 101, 0, 8, 2, 110, 114, 3, 48, 2, 119, 0, 4, 2, 110, 105, 110, 115, 117, 3, 48, 13, 0, 114, 2, 115, 112, 0, 114, 2, 105, 112, 104, 3, 48, 13, 34, 0, 4, 114, 2, 99, 101, 105, 3, 48, 112, 0, 114, 2, 99, 101, 112, 0, 114, 2, 99, 117, 108, 105, 0, 114, 2, 99, 117, 115, 0, 114, 2, 102, 101, 99, 0, 114, 2, 102, 111, 114, 109, 0, 114, 2, 102, 117, 110, 0, 114, 2, 102, 117, 115, 0, 114, 2, 109, 105, 115, 115, 0, 114, 2, 109, 105, 116, 0, 114, 2, 112, 101, 116, 0, 114, 2, 112, 108, 101, 0, 114, 2, 115, 105, 115, 0, 114, 2, 115, 117, 0, 114, 2, 115, 117, 0, 114, 2, 116, 97, 105, 0, 114, 2, 116, 117, 0, 114, 2, 118, 21, 0, 114, 101, 103, 114, 105, 110, 8, 3, 48, 119, 34, 13, 79, 34, 120, 50, 0, 4, 114, 2, 112, 101, 116, 114, 3, 48, 126, 0, 114, 2, 118, 105, 0, 114, 109, 101, 2, 97, 3, 48, 126, 63, 120, 0, 114, 115, 112, 105, 2, 114, 97, 3, 48, 126, 87, 48, 13, 0, 114, 115, 101, 118, 101, 114, 3, 48, 126, 87, 120, 82, 6, 140, 0, 97, 99, 101, 3, 48, 127, 87, 0, 7, 6, 112, 114, 0, 101, 8, 2, 100, 105, 14, 128, 132, 131, 3, 48, 34, 2, 37, 0, 4, 101, 8, 2, 17, 67, 21, 3, 48, 34, 2, 120, 0, 101, 8, 2, 100, 105, 99, 0, 101, 8, 2, 115, 99, 114, 0, 101, 115, 8, 2, 101, 110, 116, 3, 48, 34, 2, 120, 86, 0, 4, 101, 8, 2, 101, 109, 3, 48, 34, 2, 127, 0, 101, 8, 2, 109, 111, 108, 0, 101, 8, 2, 117, 0, 101, 8, 2, 105, 110, 21, 14, 128, 132, 131, 3, 48, 34, 4, 127, 0, 111, 2, 112, 97, 110, 3, 48, 34, 6, 134, 0, 4, 111, 2, 99, 101, 100, 3, 48, 34, 13, 0, 111, 2, 99, 101, 101, 0, 111, 2, 99, 101, 115, 115, 105, 0, 111, 2, 99, 108, 97, 105, 0, 111, 2, 99, 117, 114, 0, 111, 2, 100, 117, 99, 0, 111, 2, 102, 97, 110, 0, 111, 2, 102, 101, 115, 0, 111, 2, 102, 105, 99, 0, 111, 2, 102, 111, 117, 0, 111, 2, 102, 117, 0, 111, 2, 103, 114, 101, 115, 0, 111, 2, 104, 105, 98, 0, 111, 2, 106, 101, 99, 0, 111, 2, 108, 105, 102, 0, 111, 2, 108, 111, 110, 0, 111, 2, 109, 111, 116, 0, 111, 2, 110, 111, 117, 110, 99, 0, 111, 2, 110, 117, 110, 0, 111, 2, 112, 101, 108, 0, 111, 2, 112, 101, 110, 115, 0, 111, 2, 112, 105, 116, 0, 111, 2, 112, 114, 105, 101, 0, 111, 2, 112, 117, 108, 0, 111, 2, 115, 112, 101, 99, 116, 17, 65, 0, 111, 2, 116, 101, 99, 0, 111, 2, 116, 101, 115, 116, 0, 111, 2, 116, 114, 97, 99, 0, 111, 2, 116, 114, 117, 0, 111, 2, 118, 105, 100, 0, 111, 2, 118, 105, 115, 0, 111, 2, 118, 111, 99, 0, 111, 2, 118, 111, 107, 0, 111, 8, 2, 112, 17, 65, 0, 111, 8, 2, 115, 97, 0, 111, 8, 2, 115, 99, 0, 4, 101, 2, 99, 105, 111, 3, 48, 34, 119, 0, 101, 2, 106, 117, 100, 105, 0, 101, 8, 2, 17, 67, 11, 0, 101, 8, 2, 102, 101, 114, 101, 110, 0, 101, 8, 2, 103, 110, 0, 101, 8, 2, 109, 105, 0, 101, 8, 2, 110, 25, 0, 101, 8, 2, 112, 32, 0, 101, 8, 2, 112, 111, 115, 105, 0, 101, 8, 2, 115, 99, 111, 0, 101, 8, 2, 115, 116, 0, 101, 100, 97, 2, 116, 111, 3, 48, 34, 119, 70, 13, 0, 101, 118, 8, 2, 97, 108, 3, 48, 34, 119, 82, 0, 4, 101, 115, 2, 101, 110, 99, 3, 48, 34, 119, 86, 0, 101, 115, 8, 2, 101, 110, 116, 97, 0, 101, 115, 105, 2, 100, 101, 110, 3, 48, 34, 119, 86, 120, 0, 105, 110, 99, 2, 101, 13, 3, 48, 34, 120, 50, 87, 0, 4, 111, 2, 100, 117, 99, 116, 3, 48, 34, 122, 0, 111, 2, 112, 101, 114, 0, 111, 2, 112, 104, 0, 111, 2, 112, 111, 115, 105, 116, 0, 111, 2, 115, 101, 99, 0, 111, 2, 116, 101, 115, 116, 97, 110, 0, 111, 2, 118, 105, 100, 101, 110, 0, 111, 5, 3, 2, 99, 101, 115, 115, 0, 111, 8, 2, 112, 97, 103, 0, 111, 98, 97, 98, 3, 48, 34, 122, 69, 13, 69, 0, 4, 101, 2, 102, 105, 120, 3, 48, 34, 127, 0, 101, 2, 104, 105, 115, 116, 0, 101, 8, 2, 32, 0, 101, 8, 2, 97, 109, 0, 101, 8, 2, 99, 105, 110, 99, 0, 101, 8, 2, 102, 101, 99, 0, 101, 8, 2, 109, 105, 117, 0, 101, 8, 2, 113, 117, 0, 101, 8, 2, 115, 99, 0, 101, 8, 2, 118, 105, 101, 119, 0, 101, 8, 2, 118, 105, 111, 0, 101, 97, 8, 2, 99, 104, 0, 101, 100, 101, 2, 99, 101, 115, 3, 48, 34, 127, 70, 120, 0, 4, 111, 2, 102, 105, 108, 3, 48, 34, 134, 0, 111, 2, 103, 114, 97, 0, 111, 2, 108, 111, 103, 0, 111, 109, 101, 2, 116, 104, 3, 48, 34, 134, 63, 127, 0, 105, 8, 2, 111, 3, 48, 34, 135, 0, 105, 111, 2, 114, 105, 116, 3, 48, 34, 135, 6, 122, 0, 105, 118, 97, 116, 8, 3, 48, 34, 135, 82, 13, 47, 0, 7, 6, 114, 101, 0, 2, 103, 101, 110, 101, 114, 3, 2, 34, 127, 0, 4, 8, 2, 97, 108, 105, 103, 3, 4, 34, 127, 0, 8, 2, 97, 108, 108, 0, 8, 2, 97, 117, 21, 14, 128, 132, 130, 0, 8, 2, 99, 111, 110, 14, 128, 132, 130, 0, 8, 2, 99, 114, 101, 97, 116, 0, 97, 8, 2, 108, 108, 111, 14, 128, 132, 130, 0, 4, 100, 101, 1, 110, 117, 2, 17, 67, 3, 4, 34, 127, 70, 111, 0, 100, 101, 8, 2, 17, 67, 0, 1, 118, 117, 3, 13, 0, 100, 1, 116, 17, 67, 10, 2, 32, 3, 13, 70, 0, 4, 8, 2, 100, 114, 3, 34, 2, 127, 0, 8, 2, 101, 100, 117, 14, 128, 132, 130, 0, 8, 2, 101, 109, 14, 128, 132, 130, 0, 8, 2, 101, 110, 14, 128, 132, 130, 0, 8, 2, 101, 113, 14, 128, 132, 130, 0, 8, 2, 101, 115, 14, 128, 132, 130, 0, 8, 2, 101, 120, 14, 128, 132, 130, 0, 116, 114, 111, 2, 14, 128, 132, 133, 3, 34, 4, 119, 47, 34, 134, 0, 4, 8, 2, 99, 111, 109, 14, 128, 132, 130, 3, 34, 4, 127, 0, 8, 2, 105, 21, 14, 128, 132, 130, 0, 8, 2, 117, 110, 14, 128, 132, 130, 0, 4, 97, 2, 17, 67, 11, 3, 34, 4, 127, 13, 0, 97, 8, 2, 100, 17, 67, 0, 4, 1, 17, 65, 2, 32, 3, 34, 13, 0, 1, 114, 2, 32, 0, 2, 109, 101, 110, 116, 0, 114, 2, 32, 0, 100, 1, 17, 66, 10, 2, 32, 3, 34, 13, 70, 0, 4, 1, 110, 117, 2, 17, 67, 21, 3, 34, 111, 0, 2, 97, 99, 116, 0, 2, 100, 101, 109, 12, 0, 8, 2, 17, 67, 21, 0, 8, 99, 2, 109, 97, 116, 0, 97, 2, 108, 105, 116, 3, 34, 111, 35, 0, 112, 101, 2, 116, 105, 116, 105, 118, 3, 34, 111, 48, 119, 0, 108, 101, 2, 110, 116, 3, 34, 111, 55, 119, 0, 4, 108, 105, 1, 110, 117, 2, 97, 3, 34, 111, 55, 135, 0, 108, 105, 2, 97, 0, 4, 115, 2, 105, 103, 110, 3, 34, 111, 86, 0, 115, 2, 117, 108, 116, 0, 97, 2, 108, 116, 101, 3, 34, 111, 122, 0, 97, 2, 103, 101, 110, 3, 34, 111, 136, 0, 4, 2, 17, 67, 101, 108, 32, 3, 34, 119, 0, 2, 99, 107, 0, 2, 99, 116, 0, 2, 100, 17, 67, 0, 2, 102, 117, 103, 0, 2, 103, 105, 115, 116, 0, 2, 112, 108, 105, 0, 2, 112, 114, 105, 109, 0, 2, 112, 116, 0, 2, 115, 105, 100, 117, 101, 0, 2, 115, 111, 108, 117, 0, 2, 115, 111, 110, 0, 2, 115, 116, 108, 0, 2, 116, 105, 99, 0, 2, 116, 105, 110, 97, 0, 2, 118, 101, 108, 0, 2, 118, 101, 114, 101, 110, 0, 2, 118, 111, 108, 117, 0, 8, 2, 17, 67, 17, 67, 32, 0, 8, 2, 17, 67, 32, 0, 8, 2, 99, 114, 101, 97, 116, 105, 0, 8, 2, 100, 17, 67, 0, 8, 2, 100, 111, 108, 101, 110, 0, 8, 2, 110, 17, 67, 0, 8, 2, 115, 99, 117, 0, 97, 2, 108, 109, 0, 112, 101, 2, 116, 105, 116, 3, 34, 119, 48, 13, 0, 112, 114, 101, 115, 101, 110, 116, 3, 34, 119, 48, 34, 111, 86, 6, 119, 50, 47, 0, 112, 101, 114, 8, 2, 116, 3, 34, 119, 48, 112, 0, 99, 111, 2, 103, 3, 34, 119, 49, 13, 0, 4, 99, 107, 111, 110, 3, 34, 119, 49, 13, 50, 0, 99, 111, 110, 2, 99, 0, 99, 114, 101, 8, 2, 97, 110, 3, 34, 119, 49, 34, 127, 0, 108, 101, 8, 2, 103, 3, 34, 119, 55, 111, 0, 108, 101, 2, 118, 3, 34, 119, 55, 121, 0, 103, 105, 109, 3, 34, 119, 73, 120, 63, 0, 103, 117, 2, 108, 3, 34, 119, 79, 57, 132, 0, 102, 101, 114, 101, 110, 100, 3, 34, 119, 81, 13, 34, 6, 119, 50, 70, 0, 118, 101, 2, 110, 17, 65, 3, 34, 119, 82, 13, 0, 115, 105, 2, 100, 101, 110, 3, 34, 119, 86, 111, 0, 109, 101, 110, 116, 3, 34, 120, 63, 13, 50, 47, 0, 104, 101, 110, 3, 34, 120, 105, 6, 119, 50, 0, 4, 2, 103, 101, 110, 3, 34, 127, 0, 2, 103, 105, 111, 110, 0, 2, 116, 97, 105, 108, 0, 8, 2, 97, 110, 0, 8, 2, 99, 101, 110, 116, 0, 97, 2, 109, 0, 97, 5, 3, 2, 108, 3, 34, 127, 14, 0, 115, 101, 2, 108, 3, 34, 127, 87, 119, 0, 4, 105, 8, 2, 99, 3, 34, 135, 0, 105, 8, 2, 108, 0, 97, 2, 108, 3, 34, 139, 0, 1, 10, 2, 32, 3, 112, 0, 7, 6, 115, 117, 0, 1, 101, 114, 2, 109, 17, 65, 3, 86, 57, 132, 0, 109, 97, 98, 1, 101, 114, 3, 86, 57, 132, 63, 13, 69, 0, 5, 3, 1, 101, 114, 2, 109, 17, 65, 3, 86, 132, 0, 4, 2, 98, 100, 117, 101, 3, 87, 2, 123, 0, 2, 98, 115, 101, 114, 0, 2, 98, 115, 105, 115, 0, 2, 98, 116, 114, 97, 0, 4, 2, 98, 109, 105, 3, 87, 13, 0, 2, 98, 115, 99, 114, 105, 98, 0, 2, 98, 117, 114, 98, 97, 0, 2, 98, 118, 0, 2, 99, 99, 17, 65, 0, 2, 102, 102, 105, 99, 0, 2, 112, 112, 108, 0, 2, 112, 112, 111, 114, 0, 2, 112, 112, 114, 101, 115, 0, 8, 2, 98, 109, 101, 114, 0, 98, 115, 116, 97, 2, 110, 116, 3, 87, 13, 69, 87, 47, 35, 0, 4, 115, 8, 2, 112, 3, 87, 13, 87, 0, 115, 8, 2, 116, 97, 105, 0, 115, 99, 8, 2, 101, 0, 1, 110, 2, 97, 108, 3, 87, 57, 132, 0, 4, 114, 1, 110, 117, 2, 112, 3, 87, 112, 0, 114, 2, 109, 0, 114, 2, 112, 97, 0, 114, 2, 112, 114, 0, 114, 2, 114, 0, 114, 2, 118, 0, 4, 2, 99, 99, 117, 108, 3, 87, 123, 0, 2, 112, 112, 108, 101, 0, 2, 112, 112, 108, 105, 99, 0, 8, 2, 98, 0, 114, 2, 114, 101, 121, 0, 4, 114, 3, 87, 126, 0, 114, 8, 0, 115, 8, 2, 17, 65, 3, 87, 132, 86, 0, 4, 114, 5, 5, 3, 87, 146, 0, 114, 5, 5, 8, 0, 4, 114, 1, 97, 101, 3, 88, 112, 0, 114, 1, 111, 0, 114, 101, 1, 10, 2, 32, 0, 4, 2, 97, 108, 3, 88, 132, 0, 8, 97, 99, 0, 103, 97, 114, 3, 89, 115, 79, 112, 0, 4, 114, 1, 110, 101, 3, 89, 141, 0, 114, 1, 110, 105, 2, 17, 65, 0, 114, 2, 97, 110, 99, 0, 114, 101, 8, 0, 7, 6, 116, 104, 0, 1, 32, 48, 15, 2, 32, 3, 13, 85, 0, 8, 2, 111, 109, 21, 3, 47, 0, 4, 2, 97, 110, 100, 3, 47, 105, 0, 2, 101, 97, 100, 0, 2, 101, 97, 114, 116, 0, 2, 105, 108, 108, 0, 2, 111, 108, 101, 0, 2, 111, 111, 100, 0, 2, 111, 117, 115, 101, 0, 101, 113, 117, 101, 3, 47, 119, 49, 0, 97, 109, 101, 115, 8, 3, 47, 119, 63, 86, 0, 97, 105, 3, 47, 135, 0, 4, 1, 97, 101, 2, 101, 114, 3, 84, 0, 1, 111, 111, 109, 115, 0, 1, 114, 2, 105, 101, 114, 0, 1, 114, 2, 121, 0, 1, 114, 111, 2, 105, 0, 2, 101, 110, 32, 0, 2, 101, 114, 17, 67, 0, 2, 101, 114, 110, 32, 0, 2, 101, 115, 116, 0, 2, 105, 116, 104, 0, 101, 2, 32, 0, 101, 109, 8, 3, 84, 2, 119, 63, 0, 101, 108, 101, 115, 115, 3, 84, 13, 55, 6, 119, 87, 0, 101, 100, 1, 117, 111, 2, 32, 3, 84, 70, 0, 105, 110, 103, 1, 101, 101, 3, 84, 111, 66, 0, 4, 101, 114, 2, 32, 3, 84, 112, 0, 101, 114, 2, 101, 114, 0, 101, 114, 101, 2, 32, 0, 101, 114, 101, 8, 3, 84, 138, 0, 4, 3, 85, 0, 1, 32, 48, 48, 2, 32, 0, 1, 32, 48, 49, 2, 32, 0, 1, 97, 99, 2, 101, 114, 105, 0, 1, 103, 2, 101, 110, 32, 0, 1, 104, 112, 0, 1, 110, 2, 101, 114, 12, 0, 1, 114, 97, 101, 2, 121, 0, 1, 114, 111, 119, 2, 32, 0, 2, 101, 114, 109, 0, 8, 2, 17, 71, 0, 8, 2, 114, 17, 71, 0, 8, 2, 119, 17, 71, 0, 8, 101, 2, 101, 114, 0, 105, 111, 8, 3, 85, 4, 135, 134, 0, 101, 114, 97, 112, 3, 85, 119, 34, 13, 48, 0, 101, 8, 2, 109, 17, 65, 3, 85, 127, 0, 7, 6, 117, 101, 0, 3, 57, 132, 0, 2, 110, 100, 3, 57, 132, 6, 119, 0, 4, 2, 110, 3, 57, 132, 13, 0, 2, 116, 0, 8, 17, 67, 2, 108, 0, 101, 3, 57, 132, 127, 0, 110, 101, 2, 32, 3, 57, 132, 127, 50, 0, 114, 2, 116, 3, 58, 138, 0, 4, 1, 108, 3, 132, 0, 1, 114, 0, 8, 115, 0, 1, 108, 2, 110, 116, 105, 3, 132, 6, 119, 0, 4, 1, 108, 2, 110, 3, 132, 13, 0, 8, 17, 67, 17, 67, 2, 108, 0, 7, 6, 117, 105, 0, 1, 21, 2, 116, 121, 3, 6, 57, 132, 120, 0, 1, 99, 114, 2, 116, 111, 117, 115, 3, 7, 57, 132, 120, 0, 1, 110, 2, 115, 3, 57, 132, 0, 1, 115, 101, 106, 2, 116, 3, 57, 132, 111, 0, 114, 2, 32, 3, 57, 141, 0, 115, 1, 99, 3, 58, 120, 86, 0, 115, 105, 110, 101, 1, 99, 3, 58, 120, 86, 127, 50, 0, 1, 103, 2, 116, 97, 3, 111, 0, 4, 1, 98, 2, 108, 3, 120, 0, 1, 99, 114, 2, 116, 0, 1, 103, 2, 108, 17, 67, 0, 8, 103, 2, 110, 0, 4, 1, 106, 2, 99, 3, 132, 0, 1, 108, 115, 0, 1, 114, 2, 116, 0, 1, 115, 2, 116, 0, 115, 1, 114, 2, 101, 3, 132, 86, 0, 1, 114, 103, 2, 116, 3, 132, 111, 0, 4, 1, 108, 102, 2, 100, 3, 132, 120, 0, 1, 114, 100, 2, 100, 0, 4, 1, 103, 2, 100, 17, 65, 13, 3, 135, 0, 1, 103, 2, 115, 101, 0, 1, 103, 101, 98, 2, 108, 0, 8, 103, 2, 108, 101, 0, 100, 101, 1, 103, 2, 108, 3, 135, 70, 0, 7, 6, 117, 110, 0, 4, 2, 97, 110, 105, 3, 2, 57, 132, 50, 0, 8, 2, 105, 113, 0, 4, 2, 114, 101, 103, 105, 3, 2, 123, 50, 0, 8, 2, 17, 65, 14, 128, 132, 130, 0, 8, 2, 21, 14, 128, 132, 130, 0, 110, 8, 3, 2, 123, 50, 50, 0, 8, 2, 105, 108, 3, 4, 57, 132, 50, 0, 4, 8, 2, 100, 101, 14, 128, 132, 130, 3, 4, 123, 50, 0, 8, 2, 101, 110, 14, 128, 132, 130, 0, 8, 2, 101, 120, 14, 128, 132, 130, 0, 8, 2, 105, 100, 101, 0, 8, 2, 105, 109, 14, 128, 132, 130, 0, 8, 2, 105, 110, 14, 128, 132, 130, 0, 8, 2, 114, 101, 17, 67, 21, 14, 128, 132, 130, 0, 100, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 4, 123, 50, 70, 112, 0, 97, 8, 2, 98, 3, 4, 123, 50, 117, 0, 1, 21, 2, 97, 108, 3, 6, 57, 132, 50, 0, 4, 1, 17, 67, 2, 101, 114, 3, 57, 132, 50, 0, 1, 116, 2, 101, 0, 2, 105, 0, 8, 2, 105, 111, 0, 8, 2, 105, 120, 0, 101, 2, 32, 0, 105, 116, 2, 101, 3, 57, 132, 50, 6, 135, 47, 0, 105, 8, 3, 57, 132, 50, 120, 0, 4, 1, 112, 2, 105, 115, 104, 3, 123, 50, 0, 2, 17, 65, 0, 8, 2, 100, 117, 108, 97, 0, 8, 2, 103, 117, 0, 4, 1, 106, 2, 17, 65, 3, 132, 50, 0, 1, 114, 2, 105, 0, 5, 3, 1, 116, 2, 101, 0, 101, 1, 108, 2, 32, 0, 101, 1, 114, 2, 32, 0, 101, 5, 3, 1, 100, 2, 32, 0, 101, 5, 3, 1, 116, 2, 32, 0, 7, 6, 117, 112, 0, 4, 8, 2, 98, 3, 2, 123, 48, 0, 8, 2, 99, 0, 8, 2, 100, 0, 8, 2, 101, 0, 8, 2, 103, 0, 8, 2, 104, 0, 8, 2, 115, 101, 0, 8, 2, 115, 116, 0, 1, 115, 2, 114, 101, 3, 2, 132, 48, 0, 1, 99, 99, 111, 3, 57, 115, 48, 0, 121, 1, 99, 99, 111, 3, 57, 115, 48, 135, 0, 111, 110, 3, 123, 48, 122, 50, 0, 4, 1, 17, 67, 2, 108, 101, 3, 132, 48, 0, 1, 17, 67, 2, 108, 105, 0, 2, 108, 32, 0, 101, 114, 105, 1, 115, 2, 111, 3, 132, 48, 6, 139, 34, 120, 0, 101, 114, 1, 115, 3, 132, 48, 112, 0, 7, 6, 117, 114, 0, 1, 106, 2, 121, 3, 13, 34, 0, 101, 100, 1, 103, 2, 32, 3, 13, 70, 0, 1, 116, 2, 17, 65, 3, 57, 13, 34, 0, 101, 1, 115, 10, 2, 32, 3, 57, 13, 112, 0, 4, 101, 1, 110, 101, 2, 32, 3, 57, 112, 0, 101, 5, 3, 1, 103, 2, 32, 0, 4, 1, 17, 67, 2, 17, 65, 3, 57, 115, 34, 0, 1, 21, 2, 97, 116, 105, 111, 110, 0, 1, 21, 2, 121, 0, 97, 1, 21, 2, 116, 3, 57, 115, 34, 136, 0, 1, 98, 2, 101, 3, 57, 132, 13, 34, 0, 4, 2, 101, 100, 32, 3, 57, 141, 0, 8, 2, 17, 65, 0, 8, 102, 2, 17, 65, 0, 8, 102, 2, 121, 0, 101, 1, 116, 97, 99, 105, 2, 32, 0, 101, 2, 32, 0, 4, 1, 103, 10, 2, 32, 3, 112, 0, 1, 104, 10, 2, 32, 0, 1, 109, 10, 2, 32, 0, 1, 116, 97, 115, 2, 100, 0, 101, 1, 103, 2, 32, 0, 101, 1, 106, 110, 2, 32, 0, 101, 1, 122, 105, 0, 4, 1, 98, 2, 105, 3, 119, 34, 0, 1, 98, 2, 121, 0, 114, 5, 35, 1, 98, 2, 111, 3, 123, 34, 0, 4, 1, 112, 115, 2, 32, 3, 126, 0, 2, 17, 66, 0, 2, 32, 0, 114, 1, 102, 2, 121, 0, 114, 2, 32, 0, 114, 5, 3, 0, 103, 1, 98, 2, 101, 114, 3, 126, 79, 0, 4, 101, 1, 108, 105, 2, 32, 3, 140, 0, 101, 1, 114, 2, 32, 0, 4, 1, 106, 2, 105, 3, 141, 0, 1, 108, 2, 17, 65, 12, 0, 1, 112, 10, 2, 32, 0, 8, 106, 2, 121, 0, 1, 114, 2, 17, 65, 12, 3, 141, 34, 0, 4, 5, 5, 1, 112, 115, 2, 32, 3, 146, 0, 5, 5, 2, 17, 66, 0, 5, 5, 2, 32, 0, 114, 5, 5, 1, 102, 2, 121, 0, 114, 5, 5, 2, 32, 0, 103, 5, 5, 1, 98, 2, 101, 114, 3, 146, 79, 0, 7, 6, 39, 0, 114, 101, 2, 32, 14, 128, 128, 131, 3, 13, 0, 118, 101, 2, 32, 14, 128, 128, 131, 3, 13, 82, 0, 100, 2, 32, 14, 128, 128, 130, 3, 70, 0, 4, 115, 1, 32, 54, 49, 2, 32, 3, 86, 0, 115, 2, 32, 14, 128, 128, 130, 0, 4, 115, 1, 102, 2, 32, 14, 128, 128, 130, 3, 87, 0, 115, 1, 104, 99, 111, 2, 32, 14, 128, 128, 130, 0, 115, 1, 107, 2, 32, 14, 128, 128, 130, 0, 115, 1, 112, 2, 32, 14, 128, 128, 130, 0, 115, 1, 116, 2, 32, 14, 128, 128, 130, 0, 4, 115, 1, 32, 54, 2, 32, 3, 111, 86, 0, 115, 1, 101, 99, 2, 32, 14, 128, 128, 130, 0, 115, 1, 101, 115, 2, 32, 14, 128, 128, 130, 0, 115, 1, 104, 99, 2, 32, 14, 128, 128, 130, 0, 115, 1, 104, 115, 2, 32, 14, 128, 128, 130, 0, 115, 1, 115, 2, 32, 14, 128, 128, 130, 0, 115, 1, 120, 2, 32, 14, 128, 128, 130, 0, 115, 1, 122, 2, 32, 14, 128, 128, 130, 0, 108, 108, 2, 32, 14, 128, 128, 131, 3, 116, 0, 7, 6, 69, 0, 3, 0, 4, 1, 21, 2, 109, 98, 101, 114, 3, 6, 119, 0, 2, 110, 116, 105, 0, 2, 110, 116, 111, 117, 115, 0, 2, 110, 116, 117, 0, 116, 116, 101, 2, 32, 3, 6, 119, 47, 0, 116, 116, 97, 2, 32, 3, 6, 119, 47, 13, 0, 99, 116, 111, 109, 121, 2, 32, 14, 128, 128, 134, 3, 6, 119, 49, 47, 13, 63, 120, 0, 110, 2, 100, 17, 65, 32, 3, 6, 119, 50, 0, 110, 115, 107, 2, 32, 3, 6, 119, 50, 87, 49, 0, 108, 108, 97, 2, 32, 3, 6, 119, 55, 13, 0, 115, 113, 117, 101, 3, 6, 119, 87, 49, 0, 4, 2, 17, 67, 105, 97, 3, 6, 127, 0, 2, 115, 105, 97, 0, 109, 2, 105, 99, 32, 3, 6, 127, 63, 0, 97, 2, 110, 32, 3, 6, 139, 0, 114, 105, 2, 17, 65, 3, 6, 139, 34, 111, 0, 101, 114, 2, 32, 3, 6, 140, 0, 111, 117, 115, 2, 32, 3, 8, 57, 13, 87, 0, 97, 2, 32, 3, 8, 139, 0, 110, 101, 114, 2, 32, 3, 10, 50, 13, 0, 110, 105, 110, 103, 2, 32, 3, 10, 50, 111, 66, 0, 4, 2, 17, 66, 17, 67, 32, 3, 13, 0, 2, 17, 66, 17, 67, 101, 32, 0, 2, 17, 66, 32, 0, 2, 110, 116, 32, 0, 114, 2, 105, 101, 32, 3, 13, 34, 0, 114, 121, 2, 32, 3, 13, 34, 2, 120, 0, 4, 110, 2, 32, 3, 13, 50, 0, 110, 2, 97, 116, 17, 65, 0, 110, 101, 100, 2, 32, 3, 13, 50, 70, 0, 109, 2, 32, 3, 13, 63, 0, 115, 1, 114, 17, 67, 2, 32, 14, 128, 129, 130, 3, 13, 86, 0, 116, 114, 121, 2, 32, 14, 128, 128, 130, 3, 34, 120, 0, 4, 100, 1, 99, 10, 2, 32, 14, 128, 139, 130, 3, 47, 0, 100, 1, 104, 99, 10, 2, 32, 14, 128, 139, 130, 0, 100, 1, 107, 10, 2, 32, 14, 128, 139, 130, 0, 100, 1, 112, 10, 2, 32, 14, 128, 139, 130, 0, 100, 1, 120, 10, 2, 32, 14, 128, 136, 130, 0, 4, 100, 1, 21, 21, 2, 32, 14, 128, 139, 130, 3, 70, 0, 100, 1, 109, 111, 21, 21, 10, 2, 32, 14, 128, 136, 130, 0, 100, 1, 114, 117, 2, 32, 14, 128, 138, 129, 0, 100, 1, 121, 2, 32, 0, 115, 1, 10, 2, 32, 14, 128, 129, 130, 3, 86, 0, 100, 1, 17, 67, 10, 2, 32, 14, 128, 139, 130, 3, 107, 0, 4, 115, 1, 102, 2, 32, 14, 128, 129, 130, 3, 108, 0, 115, 1, 107, 2, 32, 14, 128, 129, 130, 0, 115, 1, 112, 2, 32, 14, 128, 129, 130, 0, 115, 1, 116, 2, 32, 14, 128, 129, 130, 0, 2, 111, 32, 3, 111, 0, 117, 115, 2, 32, 3, 111, 13, 87, 0, 4, 114, 1, 100, 97, 2, 32, 14, 128, 128, 129, 3, 112, 0, 114, 2, 17, 67, 0, 114, 2, 32, 0, 114, 115, 1, 100, 97, 2, 32, 14, 128, 128, 130, 3, 112, 86, 0, 4, 108, 2, 32, 3, 116, 0, 108, 101, 2, 32, 0, 108, 108, 2, 12, 0, 4, 1, 108, 2, 112, 115, 3, 119, 0, 1, 108, 2, 112, 116, 0, 2, 110, 100, 111, 117, 115, 0, 2, 110, 105, 110, 103, 0, 2, 115, 115, 0, 2, 116, 105, 99, 32, 0, 2, 116, 114, 105, 99, 0, 2, 120, 32, 0, 114, 2, 105, 99, 32, 3, 119, 34, 0, 110, 5, 8, 2, 32, 3, 119, 50, 0, 110, 105, 110, 103, 5, 8, 2, 32, 3, 119, 50, 111, 66, 0, 108, 5, 8, 2, 32, 3, 119, 55, 0, 115, 115, 2, 32, 3, 119, 87, 0, 1, 107, 97, 110, 2, 100, 3, 120, 0, 100, 108, 121, 2, 32, 14, 128, 129, 132, 3, 120, 70, 55, 2, 120, 0, 4, 100, 1, 100, 10, 2, 32, 14, 128, 139, 130, 3, 121, 70, 0, 100, 1, 116, 10, 2, 32, 14, 128, 139, 130, 0, 4, 39, 115, 1, 99, 2, 32, 14, 128, 129, 131, 3, 121, 86, 0, 39, 115, 1, 115, 2, 32, 14, 128, 129, 130, 0, 115, 1, 99, 2, 32, 14, 128, 129, 130, 0, 115, 1, 103, 2, 32, 14, 128, 129, 130, 0, 115, 1, 104, 99, 2, 32, 14, 128, 129, 130, 0, 115, 1, 104, 112, 2, 32, 14, 128, 129, 130, 0, 115, 1, 104, 115, 2, 32, 14, 128, 129, 130, 0, 115, 1, 115, 2, 32, 14, 128, 129, 130, 0, 115, 1, 120, 2, 32, 14, 128, 128, 130, 0, 4, 2, 100, 105, 97, 32, 3, 127, 0, 2, 100, 105, 99, 32, 0, 2, 116, 101, 32, 0, 69, 2, 32, 0, 101, 2, 32, 0, 101, 2, 100, 0, 105, 2, 110, 32, 0, 110, 101, 2, 32, 3, 127, 50, 0, 109, 101, 2, 32, 3, 127, 63, 0, 115, 101, 2, 32, 3, 127, 86, 0, 119, 2, 32, 3, 132, 0, 105, 2, 32, 3, 135, 0, 121, 1, 98, 111, 2, 32, 3, 136, 0, 7, 6, 97, 0, 8, 2, 113, 117, 3, 2, 35, 0, 101, 114, 8, 99, 3, 2, 138, 0, 8, 2, 32, 15, 3, 4, 136, 0, 4, 1, 21, 2, 107, 105, 32, 3, 6, 35, 0, 1, 104, 2, 122, 97, 114, 0, 2, 122, 122, 32, 0, 4, 1, 21, 2, 122, 105, 32, 3, 6, 124, 0, 2, 17, 66, 111, 32, 0, 2, 17, 66, 117, 32, 0, 2, 17, 67, 97, 32, 0, 107, 117, 2, 32, 3, 6, 124, 49, 132, 0, 119, 105, 1, 21, 2, 32, 3, 6, 124, 58, 120, 0, 122, 101, 1, 107, 21, 2, 32, 3, 6, 124, 86, 120, 0, 4, 97, 114, 3, 6, 125, 0, 101, 114, 1, 114, 0, 101, 2, 118, 97, 108, 3, 6, 127, 0, 4, 1, 21, 2, 17, 66, 105, 97, 3, 6, 136, 0, 1, 21, 2, 17, 66, 105, 117, 0, 1, 21, 2, 116, 105, 111, 117, 115, 0, 2, 17, 67, 97, 98, 108, 101, 0, 2, 17, 67, 97, 98, 108, 121, 0, 2, 17, 67, 105, 98, 108, 101, 0, 2, 116, 105, 111, 110, 0, 2, 122, 105, 100, 101, 0, 8, 2, 45, 0, 101, 97, 3, 6, 139, 0, 1, 98, 10, 2, 32, 3, 8, 13, 0, 111, 2, 32, 3, 8, 133, 0, 4, 1, 10, 2, 32, 3, 13, 0, 1, 103, 2, 122, 101, 17, 67, 11, 0, 1, 109, 2, 104, 111, 103, 0, 1, 119, 111, 2, 100, 0, 2, 119, 97, 121, 32, 0, 104, 1, 10, 2, 32, 0, 113, 117, 97, 2, 116, 3, 13, 49, 58, 35, 0, 4, 3, 35, 0, 1, 17, 67, 2, 120, 12, 0, 1, 109, 2, 106, 101, 115, 0, 1, 110, 2, 116, 105, 111, 110, 97, 108, 0, 1, 110, 2, 116, 117, 114, 97, 0, 1, 114, 98, 2, 122, 105, 108, 0, 1, 114, 114, 105, 2, 116, 105, 111, 0, 1, 119, 115, 2, 103, 0, 1, 119, 115, 2, 109, 32, 0, 1, 119, 115, 2, 110, 107, 0, 2, 17, 66, 101, 17, 67, 111, 32, 0, 2, 17, 66, 101, 114, 17, 65, 0, 2, 17, 66, 101, 114, 17, 67, 0, 2, 17, 66, 101, 116, 0, 2, 17, 67, 101, 101, 12, 0, 2, 119, 17, 65, 0, 8, 2, 118, 101, 0, 8, 2, 120, 12, 0, 8, 114, 2, 116, 105, 111, 110, 0, 4, 97, 1, 97, 97, 3, 35, 12, 0, 97, 2, 97, 0, 107, 1, 21, 2, 105, 97, 3, 35, 49, 0, 113, 117, 2, 97, 3, 35, 49, 58, 0, 113, 117, 105, 3, 35, 49, 58, 120, 0, 101, 100, 1, 21, 2, 32, 14, 128, 128, 130, 3, 70, 0, 4, 1, 45, 2, 45, 3, 117, 0, 8, 2, 32, 0, 8, 2, 45, 104, 97, 108, 102, 0, 8, 2, 107, 21, 0, 8, 2, 119, 104, 21, 0, 113, 117, 2, 97, 114, 105, 17, 65, 3, 117, 49, 58, 0, 4, 119, 8, 2, 97, 12, 3, 117, 58, 0, 119, 8, 2, 111, 107, 0, 1, 108, 2, 116, 104, 3, 118, 0, 2, 17, 66, 105, 110, 103, 3, 119, 0, 101, 109, 111, 114, 114, 104, 1, 104, 3, 119, 63, 112, 34, 0, 1, 110, 103, 105, 115, 2, 116, 117, 114, 101, 3, 120, 0, 4, 1, 117, 113, 115, 2, 115, 104, 3, 122, 0, 1, 119, 2, 98, 0, 1, 119, 2, 100, 0, 1, 119, 2, 115, 0, 1, 119, 2, 116, 99, 0, 1, 119, 115, 2, 17, 66, 0, 4, 1, 17, 67, 29, 2, 32, 3, 124, 0, 1, 17, 67, 100, 110, 97, 114, 103, 2, 32, 0, 1, 119, 115, 2, 122, 0, 97, 0, 104, 2, 17, 67, 0, 104, 2, 32, 0, 4, 101, 3, 127, 0, 101, 1, 104, 2, 109, 0, 101, 8, 2, 111, 110, 0, 111, 105, 115, 2, 32, 3, 127, 89, 0, 111, 105, 115, 101, 2, 32, 3, 127, 89, 13, 0, 4, 1, 119, 2, 116, 101, 114, 3, 128, 0, 119, 0, 119, 8, 2, 102, 0, 119, 8, 2, 107, 0, 119, 101, 2, 17, 66, 0, 119, 101, 2, 32, 0, 119, 101, 8, 0, 119, 97, 108, 3, 128, 55, 0, 4, 111, 1, 109, 3, 133, 0, 111, 1, 109, 2, 114, 105, 0, 111, 1, 116, 0, 4, 101, 1, 109, 2, 115, 116, 3, 135, 0, 121, 8, 0, 4, 1, 17, 67, 29, 2, 17, 66, 121, 32, 3, 136, 0, 1, 32, 15, 2, 32, 0, 1, 104, 2, 122, 17, 65, 0, 1, 108, 2, 122, 17, 71, 0, 1, 108, 98, 2, 122, 111, 110, 0, 1, 108, 103, 2, 99, 105, 0, 1, 109, 2, 106, 111, 114, 32, 0, 1, 109, 2, 106, 111, 114, 101, 0, 1, 110, 2, 17, 67, 97, 108, 0, 1, 110, 2, 116, 117, 114, 0, 1, 112, 2, 116, 105, 101, 110, 0, 1, 114, 2, 99, 105, 17, 65, 0, 1, 114, 2, 122, 105, 0, 1, 114, 101, 2, 115, 117, 114, 0, 1, 116, 115, 2, 116, 117, 115, 0, 1, 119, 2, 17, 66, 101, 13, 0, 1, 119, 115, 2, 116, 104, 0, 2, 17, 66, 101, 13, 0, 2, 17, 67, 97, 98, 105, 108, 105, 116, 121, 0, 2, 115, 105, 111, 110, 0, 2, 116, 104, 101, 32, 12, 0, 2, 122, 121, 0, 8, 2, 32, 45, 0, 8, 2, 118, 105, 97, 116, 0, 8, 2, 118, 111, 110, 0, 101, 2, 108, 0, 121, 0, 121, 1, 119, 0, 111, 114, 3, 136, 6, 131, 0, 111, 1, 103, 2, 108, 3, 136, 13, 0, 113, 117, 101, 2, 111, 3, 136, 49, 58, 120, 0, 39, 115, 8, 2, 32, 3, 136, 86, 0, 122, 111, 114, 1, 114, 3, 136, 86, 112, 0, 121, 108, 101, 8, 3, 136, 116, 0, 111, 3, 136, 122, 0, 4, 101, 114, 3, 138, 0, 101, 114, 8, 2, 111, 0, 121, 114, 8, 0, 4, 101, 114, 111, 2, 112, 108, 97, 110, 3, 138, 34, 13, 0, 101, 114, 111, 2, 115, 111, 108, 0, 101, 114, 111, 8, 3, 138, 34, 134, 0, 119, 114, 2, 32, 3, 144, 0, 7, 6, 98, 0, 4, 1, 109, 2, 32, 3, 0, 2, 98, 3, 0, 4, 116, 1, 101, 100, 3, 47, 0, 116, 1, 117, 115, 2, 108, 0, 4, 3, 69, 0, 8, 2, 18, 66, 17, 71, 0, 104, 8, 0, 97, 8, 2, 109, 98, 21, 3, 69, 2, 35, 0, 4, 97, 108, 108, 105, 8, 2, 21, 3, 69, 4, 35, 55, 111, 0, 97, 108, 108, 121, 8, 2, 21, 0, 97, 116, 116, 108, 101, 8, 2, 21, 14, 128, 132, 134, 3, 69, 6, 35, 47, 116, 0, 111, 111, 107, 8, 2, 21, 21, 14, 128, 132, 132, 3, 69, 6, 115, 49, 0, 117, 114, 121, 1, 21, 2, 32, 14, 128, 130, 132, 3, 69, 34, 2, 120, 0, 114, 122, 8, 2, 101, 3, 69, 34, 86, 0, 117, 103, 8, 2, 108, 101, 3, 69, 57, 132, 79, 0, 111, 8, 2, 115, 111, 109, 3, 69, 115, 0, 97, 108, 108, 105, 2, 115, 116, 3, 69, 117, 55, 6, 120, 0, 117, 114, 121, 5, 3, 1, 21, 2, 32, 14, 128, 130, 132, 3, 69, 119, 34, 2, 120, 0, 121, 116, 101, 8, 3, 69, 135, 47, 0, 97, 121, 111, 117, 8, 3, 69, 135, 132, 0, 7, 6, 99, 0, 4, 1, 115, 2, 101, 3, 0, 2, 113, 3, 0, 122, 8, 2, 97, 114, 3, 47, 87, 0, 4, 3, 49, 0, 1, 97, 109, 2, 105, 110, 0, 2, 101, 108, 116, 0, 8, 2, 18, 66, 17, 71, 0, 99, 0, 99, 1, 111, 99, 2, 105, 32, 0, 99, 1, 111, 115, 2, 101, 114, 0, 99, 104, 0, 107, 0, 104, 97, 114, 97, 2, 99, 116, 3, 49, 35, 34, 111, 0, 117, 97, 1, 101, 3, 49, 58, 35, 0, 4, 99, 2, 101, 3, 49, 87, 0, 99, 2, 105, 0, 119, 109, 8, 3, 49, 115, 63, 0, 97, 99, 111, 2, 112, 104, 3, 49, 117, 49, 6, 122, 0, 105, 97, 8, 2, 114, 97, 3, 49, 139, 0, 122, 8, 2, 101, 3, 74, 0, 2, 101, 108, 108, 18, 68, 32, 3, 74, 6, 0, 122, 101, 99, 104, 3, 74, 119, 49, 0, 4, 2, 69, 3, 87, 0, 2, 97, 101, 115, 0, 2, 101, 0, 2, 105, 0, 2, 121, 0, 2, 195, 169, 0, 101, 8, 2, 108, 101, 115, 116, 3, 87, 13, 0, 101, 109, 101, 110, 116, 8, 3, 87, 111, 63, 119, 50, 47, 0, 105, 115, 109, 2, 32, 3, 87, 120, 86, 13, 63, 0, 105, 112, 104, 2, 101, 114, 3, 87, 135, 81, 0, 105, 97, 2, 114, 121, 3, 89, 8, 13, 0, 4, 101, 111, 117, 115, 3, 89, 8, 13, 87, 0, 105, 111, 117, 115, 0, 4, 105, 97, 110, 2, 32, 3, 89, 13, 50, 0, 105, 101, 110, 0, 105, 111, 110, 0, 105, 97, 108, 3, 89, 13, 55, 0, 105, 97, 108, 2, 32, 3, 89, 116, 0, 105, 97, 108, 5, 8, 2, 32, 3, 89, 117, 55, 0, 105, 101, 110, 5, 8, 3, 89, 119, 50, 0, 105, 97, 2, 108, 105, 116, 121, 3, 89, 120, 35, 0, 105, 97, 2, 98, 3, 89, 139, 0, 105, 97, 110, 3, 89, 139, 50, 0, 7, 6, 100, 0, 2, 100, 3, 0, 117, 109, 1, 21, 2, 32, 3, 8, 70, 13, 63, 0, 116, 2, 32, 3, 47, 0, 110, 101, 1, 101, 119, 2, 115, 100, 3, 50, 0, 4, 3, 70, 0, 1, 101, 21, 21, 2, 32, 14, 128, 128, 129, 0, 8, 2, 18, 66, 17, 71, 0, 8, 2, 104, 21, 21, 0, 8, 2, 110, 105, 101, 0, 8, 2, 119, 17, 71, 0, 39, 8, 2, 17, 65, 14, 128, 132, 130, 0, 100, 104, 0, 104, 2, 25, 0, 98, 2, 32, 3, 70, 4, 127, 69, 127, 0, 109, 105, 8, 2, 116, 114, 3, 70, 13, 63, 127, 0, 4, 117, 114, 2, 17, 65, 3, 70, 57, 141, 0, 117, 114, 2, 32, 0, 121, 101, 8, 3, 70, 135, 0, 105, 114, 8, 2, 32, 3, 70, 143, 0, 4, 103, 2, 17, 67, 3, 73, 0, 103, 2, 32, 0, 103, 2, 101, 0, 103, 2, 105, 0, 103, 2, 121, 0, 106, 0, 106, 8, 2, 17, 71, 0, 103, 101, 100, 2, 32, 3, 73, 70, 0, 117, 114, 101, 1, 101, 99, 3, 73, 112, 0, 4, 117, 2, 97, 108, 32, 3, 73, 132, 0, 117, 2, 99, 97, 116, 0, 117, 2, 112, 108, 0, 117, 5, 3, 1, 10, 2, 17, 67, 17, 65, 0, 7, 6, 101, 0, 4, 1, 10, 2, 32, 3, 0, 4, 1, 21, 21, 2, 109, 101, 110, 116, 32, 3, 0, 4, 2, 102, 117, 108, 3, 0, 2, 119, 111, 114, 107, 3, 0, 4, 1, 17, 66, 99, 97, 2, 32, 3, 2, 120, 0, 2, 102, 102, 101, 99, 0, 2, 102, 102, 105, 99, 0, 2, 113, 117, 105, 112, 0, 8, 2, 99, 108, 0, 8, 2, 102, 102, 117, 0, 8, 2, 106, 17, 65, 0, 8, 2, 112, 104, 101, 109, 0, 8, 2, 113, 117, 97, 116, 0, 113, 117, 105, 118, 3, 2, 120, 49, 58, 120, 82, 0, 2, 17, 67, 105, 99, 97, 108, 3, 6, 119, 0, 117, 114, 2, 32, 3, 6, 126, 0, 117, 115, 101, 1, 21, 2, 32, 3, 6, 126, 86, 0, 4, 1, 21, 2, 17, 67, 105, 97, 32, 3, 6, 127, 0, 1, 21, 2, 103, 105, 99, 0, 1, 104, 2, 115, 105, 111, 110, 0, 2, 17, 66, 111, 32, 0, 2, 17, 66, 111, 101, 32, 0, 101, 1, 116, 2, 110, 32, 0, 101, 2, 109, 0, 117, 115, 101, 5, 3, 1, 21, 2, 32, 3, 6, 132, 86, 0, 117, 1, 115, 2, 109, 32, 3, 6, 139, 0, 101, 114, 3, 6, 140, 0, 117, 114, 5, 3, 2, 32, 3, 6, 141, 0, 117, 114, 5, 5, 2, 32, 3, 6, 146, 0, 117, 115, 1, 10, 2, 32, 3, 8, 111, 13, 87, 0, 122, 1, 21, 2, 32, 3, 8, 119, 86, 0, 4, 1, 10, 2, 110, 3, 13, 0, 1, 108, 2, 103, 105, 116, 0, 1, 108, 101, 99, 2, 98, 114, 97, 0, 98, 108, 101, 1, 21, 21, 2, 32, 3, 13, 69, 116, 0, 103, 1, 10, 2, 121, 3, 13, 73, 0, 39, 115, 1, 114, 17, 67, 10, 2, 32, 3, 13, 86, 0, 99, 121, 1, 10, 2, 32, 3, 13, 87, 2, 37, 0, 4, 117, 3, 57, 132, 0, 119, 0, 119, 2, 32, 0, 117, 114, 111, 8, 3, 57, 141, 34, 134, 0, 117, 114, 111, 8, 2, 112, 101, 3, 57, 141, 44, 13, 0, 119, 97, 121, 2, 32, 14, 128, 128, 131, 3, 58, 136, 0, 4, 39, 115, 1, 17, 67, 10, 2, 32, 14, 128, 130, 130, 3, 86, 0, 39, 115, 1, 104, 116, 10, 2, 32, 14, 128, 130, 130, 0, 39, 115, 1, 114, 10, 2, 32, 14, 128, 130, 130, 0, 4, 39, 115, 1, 102, 10, 2, 32, 14, 128, 130, 130, 3, 87, 0, 39, 115, 1, 107, 10, 2, 32, 14, 128, 130, 130, 0, 39, 115, 1, 112, 10, 2, 32, 14, 128, 130, 130, 0, 39, 115, 1, 116, 10, 2, 32, 14, 128, 130, 130, 0, 4, 1, 110, 2, 103, 111, 116, 3, 111, 0, 2, 111, 0, 4, 112, 2, 111, 120, 3, 111, 48, 0, 112, 8, 2, 105, 115, 17, 67, 0, 102, 121, 1, 21, 21, 2, 32, 3, 111, 81, 135, 0, 102, 105, 101, 114, 2, 32, 3, 111, 81, 143, 0, 4, 3, 119, 0, 1, 104, 17, 65, 2, 110, 0, 1, 112, 115, 2, 99, 105, 97, 0, 1, 114, 10, 2, 110, 0, 1, 114, 99, 2, 112, 101, 12, 0, 1, 114, 99, 115, 105, 100, 2, 116, 105, 111, 110, 0, 2, 17, 67, 105, 99, 32, 0, 112, 105, 8, 3, 119, 48, 120, 0, 112, 105, 100, 101, 114, 8, 3, 119, 48, 120, 70, 6, 126, 0, 99, 104, 1, 116, 2, 32, 3, 119, 49, 0, 103, 105, 1, 108, 2, 98, 3, 119, 73, 13, 0, 4, 1, 108, 108, 2, 110, 103, 101, 3, 120, 0, 1, 109, 2, 99, 104, 97, 110, 105, 99, 0, 1, 116, 110, 105, 2, 103, 101, 0, 1, 116, 110, 105, 2, 103, 114, 97, 0, 1, 116, 114, 101, 118, 2, 98, 0, 8, 108, 101, 2, 109, 101, 110, 0, 101, 1, 102, 102, 111, 99, 0, 99, 111, 110, 111, 2, 109, 3, 120, 49, 6, 122, 50, 13, 0, 4, 39, 115, 1, 99, 10, 2, 32, 14, 128, 130, 130, 3, 120, 86, 0, 39, 115, 1, 103, 10, 2, 32, 14, 128, 130, 130, 0, 39, 115, 1, 104, 99, 10, 2, 32, 14, 128, 130, 130, 0, 39, 115, 1, 104, 112, 10, 2, 32, 14, 128, 130, 130, 0, 39, 115, 1, 104, 115, 10, 2, 32, 14, 128, 130, 130, 0, 39, 115, 1, 115, 10, 2, 32, 14, 128, 130, 130, 0, 39, 115, 1, 120, 10, 2, 32, 14, 128, 130, 130, 0, 117, 114, 1, 108, 3, 126, 0, 4, 1, 17, 67, 29, 2, 17, 66, 101, 32, 3, 127, 0, 1, 17, 67, 29, 2, 32, 24, 0, 1, 21, 2, 116, 105, 111, 0, 1, 29, 2, 103, 97, 110, 32, 0, 1, 100, 2, 102, 97, 117, 108, 116, 0, 1, 108, 2, 103, 97, 108, 0, 1, 110, 2, 103, 114, 111, 0, 1, 112, 115, 2, 99, 105, 101, 115, 0, 1, 114, 2, 103, 97, 108, 0, 1, 114, 102, 2, 113, 0, 2, 17, 67, 105, 117, 17, 66, 0, 2, 98, 114, 105, 97, 0, 2, 109, 101, 32, 0, 2, 109, 101, 111, 117, 0, 2, 113, 117, 97, 108, 0, 8, 2, 113, 117, 97, 0, 8, 17, 67, 2, 109, 117, 114, 0, 8, 115, 2, 113, 117, 101, 0, 101, 0, 117, 2, 109, 32, 0, 99, 111, 110, 111, 2, 109, 105, 99, 3, 127, 49, 13, 50, 6, 122, 0, 99, 111, 8, 2, 115, 3, 127, 49, 134, 0, 103, 105, 111, 110, 1, 108, 3, 127, 73, 13, 50, 0, 103, 121, 2, 112, 116, 3, 127, 73, 120, 0, 4, 101, 115, 101, 1, 104, 99, 3, 127, 86, 0, 101, 122, 101, 2, 21, 0, 4, 119, 1, 106, 2, 12, 3, 132, 0, 119, 1, 108, 2, 12, 0, 119, 1, 114, 2, 12, 0, 119, 5, 3, 1, 100, 0, 119, 5, 3, 1, 110, 0, 119, 5, 3, 1, 116, 0, 119, 8, 115, 0, 119, 101, 1, 106, 2, 108, 3, 132, 13, 0, 119, 8, 115, 2, 32, 3, 134, 0, 4, 104, 2, 25, 3, 136, 0, 106, 1, 118, 2, 32, 0, 4, 117, 1, 100, 2, 116, 115, 3, 137, 0, 117, 1, 114, 2, 100, 0, 39, 101, 114, 3, 138, 0, 117, 114, 5, 5, 3, 146, 0, 7, 6, 102, 0, 2, 102, 3, 0, 4, 3, 81, 0, 8, 2, 18, 66, 17, 71, 0, 116, 2, 101, 110, 0, 111, 114, 2, 115, 101, 101, 3, 81, 2, 130, 0, 111, 114, 2, 119, 97, 114, 100, 3, 81, 6, 131, 0, 4, 97, 2, 109, 105, 108, 105, 97, 114, 3, 81, 13, 0, 111, 114, 2, 98, 97, 100, 0, 111, 114, 2, 98, 105, 100, 0, 105, 8, 2, 116, 122, 21, 3, 81, 111, 0, 101, 100, 1, 114, 101, 2, 32, 3, 81, 119, 70, 0, 106, 8, 2, 111, 114, 100, 3, 81, 120, 6, 0, 97, 2, 99, 105, 17, 65, 3, 81, 136, 0, 7, 6, 103, 0, 8, 2, 110, 17, 71, 3, 0, 2, 121, 110, 111, 117, 115, 32, 3, 8, 73, 0, 111, 2, 110, 97, 108, 32, 3, 8, 79, 122, 0, 104, 116, 3, 47, 0, 110, 2, 32, 3, 50, 0, 109, 2, 32, 3, 63, 0, 4, 1, 101, 118, 2, 101, 116, 3, 73, 0, 1, 111, 2, 101, 116, 0, 1, 114, 101, 2, 101, 116, 0, 2, 69, 0, 2, 101, 0, 2, 101, 116, 116, 101, 32, 0, 2, 105, 0, 2, 121, 0, 103, 1, 97, 120, 101, 2, 101, 114, 0, 101, 2, 110, 105, 99, 32, 3, 73, 6, 119, 0, 101, 110, 101, 115, 105, 115, 3, 73, 6, 119, 50, 111, 87, 120, 87, 0, 101, 111, 117, 115, 3, 73, 8, 13, 87, 0, 4, 105, 97, 1, 10, 2, 17, 67, 32, 3, 73, 13, 0, 105, 97, 1, 10, 2, 32, 0, 105, 117, 1, 10, 2, 109, 0, 4, 105, 110, 103, 1, 108, 3, 73, 111, 66, 0, 105, 110, 103, 1, 114, 0, 97, 111, 108, 8, 3, 73, 136, 55, 0, 4, 3, 79, 0, 1, 17, 65, 11, 2, 101, 114, 0, 1, 110, 117, 104, 0, 1, 111, 2, 121, 32, 0, 1, 111, 98, 2, 69, 121, 0, 1, 111, 103, 2, 105, 99, 32, 0, 2, 101, 97, 114, 0, 2, 101, 101, 107, 0, 2, 101, 116, 0, 2, 105, 102, 116, 0, 2, 105, 103, 103, 0, 2, 105, 108, 17, 67, 0, 2, 105, 108, 116, 0, 2, 105, 114, 25, 0, 2, 105, 118, 101, 0, 8, 2, 18, 66, 17, 71, 0, 8, 2, 101, 99, 0, 8, 2, 101, 107, 0, 8, 2, 101, 114, 116, 0, 8, 2, 105, 100, 0, 8, 2, 105, 108, 25, 0, 8, 2, 105, 109, 0, 8, 2, 105, 116, 0, 8, 2, 105, 122, 0, 8, 2, 119, 17, 71, 0, 8, 2, 121, 110, 0, 103, 0, 104, 1, 17, 67, 2, 17, 65, 0, 104, 2, 17, 67, 0, 104, 2, 32, 0, 104, 2, 97, 110, 0, 104, 8, 2, 17, 71, 0, 117, 101, 2, 32, 0, 105, 2, 32, 3, 79, 2, 120, 0, 101, 2, 100, 100, 3, 79, 6, 119, 0, 110, 117, 8, 3, 79, 13, 50, 132, 0, 117, 97, 121, 1, 21, 2, 32, 3, 79, 58, 135, 0, 4, 101, 1, 114, 111, 102, 2, 116, 3, 79, 119, 0, 117, 101, 8, 0, 105, 103, 97, 8, 3, 79, 120, 79, 13, 0, 117, 101, 114, 8, 2, 110, 3, 79, 126, 0, 105, 1, 97, 2, 32, 3, 79, 135, 0, 7, 6, 104, 0, 4, 2, 32, 3, 0, 4, 2, 104, 3, 0, 4, 8, 2, 111, 110, 111, 114, 3, 0, 4, 8, 2, 111, 110, 111, 117, 3, 0, 8, 17, 66, 3, 0, 101, 39, 8, 3, 2, 105, 127, 0, 108, 1, 25, 3, 103, 0, 3, 105, 0, 111, 109, 111, 8, 2, 115, 3, 105, 4, 134, 63, 134, 0, 4, 121, 112, 111, 2, 100, 101, 3, 105, 4, 135, 48, 13, 0, 121, 112, 111, 2, 116, 104, 101, 116, 0, 121, 112, 111, 8, 2, 21, 14, 128, 132, 132, 3, 105, 4, 135, 48, 134, 0, 97, 109, 109, 101, 100, 1, 21, 3, 105, 6, 35, 63, 120, 70, 0, 97, 110, 1, 101, 2, 32, 3, 105, 13, 50, 0, 97, 110, 1, 17, 65, 2, 32, 3, 105, 35, 50, 0, 111, 111, 100, 1, 10, 2, 32, 14, 128, 128, 132, 3, 105, 115, 70, 0, 111, 111, 100, 115, 1, 10, 2, 32, 14, 128, 128, 133, 3, 105, 115, 70, 86, 0, 101, 116, 101, 114, 111, 8, 3, 105, 119, 47, 34, 134, 0, 101, 97, 100, 1, 21, 2, 32, 14, 128, 128, 132, 3, 105, 119, 70, 0, 121, 112, 111, 8, 2, 99, 114, 3, 105, 120, 48, 122, 0, 111, 114, 114, 105, 8, 3, 105, 122, 34, 120, 0, 111, 114, 115, 101, 8, 3, 105, 130, 87, 0, 111, 117, 115, 101, 115, 2, 32, 14, 128, 128, 134, 3, 105, 133, 86, 111, 86, 0, 4, 111, 117, 115, 101, 2, 32, 14, 128, 128, 133, 3, 105, 133, 87, 0, 111, 117, 115, 101, 8, 2, 21, 0, 111, 108, 100, 1, 10, 2, 32, 14, 128, 128, 132, 3, 105, 134, 55, 70, 0, 111, 108, 109, 101, 3, 105, 134, 63, 0, 111, 109, 101, 8, 2, 111, 3, 105, 134, 63, 127, 0, 111, 109, 111, 101, 111, 8, 3, 105, 134, 63, 127, 134, 0, 4, 121, 112, 111, 2, 116, 101, 110, 117, 3, 105, 135, 48, 6, 122, 0, 121, 112, 111, 2, 116, 104, 101, 115, 0, 97, 2, 115, 116, 3, 105, 136, 0, 101, 114, 111, 3, 105, 139, 34, 134, 0, 111, 110, 101, 2, 115, 116, 3, 122, 50, 120, 0, 101, 105, 114, 3, 138, 0, 111, 117, 114, 3, 144, 0, 7, 6, 105, 0, 108, 8, 2, 108, 21, 3, 2, 120, 55, 0, 4, 8, 100, 2, 108, 97, 116, 3, 2, 135, 0, 39, 8, 0, 4, 1, 21, 2, 98, 117, 116, 105, 118, 101, 3, 6, 120, 0, 1, 21, 2, 98, 117, 116, 111, 114, 0, 1, 21, 2, 99, 105, 112, 0, 2, 17, 67, 17, 67, 105, 32, 0, 2, 99, 105, 97, 108, 0, 2, 103, 101, 110, 111, 117, 115, 0, 2, 116, 105, 111, 110, 0, 4, 108, 97, 1, 21, 2, 32, 3, 6, 120, 55, 13, 0, 108, 108, 97, 1, 21, 2, 32, 0, 102, 2, 105, 99, 17, 65, 110, 17, 67, 3, 6, 120, 81, 0, 99, 105, 97, 110, 3, 6, 120, 89, 13, 50, 0, 4, 1, 21, 2, 100, 111, 32, 3, 6, 127, 0, 2, 98, 97, 32, 0, 2, 113, 117, 101, 32, 0, 2, 119, 111, 0, 4, 1, 99, 2, 100, 97, 108, 3, 6, 135, 0, 2, 122, 111, 110, 32, 0, 99, 104, 97, 101, 108, 1, 109, 3, 6, 135, 49, 116, 0, 97, 108, 1, 10, 2, 32, 3, 8, 111, 13, 55, 0, 117, 115, 1, 10, 3, 8, 111, 13, 87, 0, 99, 111, 1, 10, 2, 32, 3, 8, 111, 49, 134, 0, 102, 121, 1, 10, 2, 32, 3, 8, 111, 81, 135, 0, 4, 1, 10, 2, 99, 32, 3, 8, 120, 0, 1, 10, 2, 99, 97, 32, 0, 1, 10, 2, 99, 97, 108, 0, 1, 10, 2, 99, 105, 17, 67, 101, 32, 0, 1, 10, 2, 99, 105, 115, 109, 32, 0, 1, 10, 2, 99, 105, 115, 116, 32, 0, 1, 100, 2, 32, 0, 1, 104, 21, 21, 2, 32, 0, 1, 107, 115, 10, 2, 32, 0, 2, 99, 117, 115, 32, 0, 1, 21, 2, 17, 67, 97, 116, 101, 32, 3, 8, 121, 0, 1, 104, 2, 32, 3, 8, 135, 0, 117, 1, 10, 2, 109, 3, 8, 139, 0, 4, 108, 2, 105, 115, 101, 3, 13, 55, 0, 108, 2, 105, 122, 101, 0, 108, 101, 1, 10, 2, 103, 101, 3, 13, 55, 120, 0, 98, 108, 121, 1, 21, 2, 32, 14, 128, 169, 132, 3, 13, 69, 55, 2, 120, 0, 98, 108, 101, 1, 21, 2, 32, 14, 128, 137, 132, 3, 13, 69, 116, 0, 122, 97, 5, 3, 2, 116, 105, 111, 110, 3, 13, 86, 136, 0, 4, 1, 98, 98, 2, 32, 3, 37, 0, 1, 104, 115, 2, 32, 0, 2, 32, 0, 100, 104, 2, 32, 0, 108, 121, 1, 10, 2, 32, 14, 128, 130, 130, 3, 55, 2, 120, 0, 4, 1, 21, 2, 99, 101, 32, 3, 111, 0, 1, 21, 2, 99, 101, 100, 32, 0, 1, 102, 2, 100, 101, 108, 0, 2, 111, 0, 2, 122, 101, 110, 0, 4, 99, 101, 1, 102, 102, 111, 3, 111, 87, 0, 99, 101, 1, 118, 114, 101, 115, 0, 4, 108, 1, 98, 21, 2, 32, 3, 116, 0, 108, 1, 99, 17, 67, 21, 2, 32, 0, 108, 1, 112, 21, 2, 32, 0, 108, 1, 114, 21, 2, 32, 0, 108, 1, 115, 21, 2, 32, 0, 108, 1, 116, 110, 2, 32, 0, 108, 1, 118, 21, 2, 32, 0, 4, 3, 120, 0, 1, 10, 2, 17, 67, 101, 110, 99, 0, 1, 10, 2, 17, 67, 101, 110, 116, 0, 1, 17, 67, 2, 120, 12, 12, 0, 1, 21, 2, 17, 67, 101, 114, 0, 1, 21, 2, 99, 101, 110, 99, 101, 0, 1, 21, 2, 108, 101, 115, 115, 0, 1, 21, 2, 110, 101, 115, 115, 0, 1, 99, 99, 97, 2, 100, 0, 1, 104, 99, 2, 108, 100, 114, 0, 1, 108, 2, 98, 101, 114, 0, 1, 108, 108, 101, 116, 110, 0, 1, 112, 117, 2, 100, 101, 0, 1, 114, 98, 2, 100, 103, 0, 1, 114, 105, 2, 100, 0, 1, 115, 115, 111, 103, 2, 112, 0, 1, 119, 2, 108, 100, 101, 114, 17, 67, 0, 2, 17, 66, 101, 101, 0, 2, 17, 66, 101, 108, 32, 0, 2, 17, 66, 101, 116, 32, 0, 2, 97, 110, 105, 32, 0, 2, 98, 105, 108, 105, 116, 0, 2, 100, 101, 111, 0, 2, 108, 101, 17, 65, 0, 8, 2, 100, 105, 0, 8, 108, 2, 17, 67, 121, 32, 0, 8, 112, 2, 116, 121, 32, 0, 112, 101, 100, 101, 3, 120, 48, 127, 70, 0, 99, 104, 8, 3, 120, 49, 0, 4, 108, 8, 2, 108, 110, 3, 120, 55, 0, 108, 8, 2, 108, 117, 115, 116, 0, 108, 101, 1, 114, 99, 97, 115, 3, 120, 55, 120, 0, 98, 101, 1, 116, 2, 116, 3, 120, 69, 6, 119, 0, 102, 101, 1, 110, 97, 109, 2, 115, 3, 120, 81, 119, 0, 102, 105, 101, 114, 2, 32, 3, 120, 81, 143, 0, 105, 2, 32, 3, 120, 135, 0, 4, 1, 17, 67, 29, 2, 17, 67, 97, 32, 3, 127, 0, 1, 17, 67, 29, 2, 17, 67, 111, 32, 0, 1, 102, 2, 106, 0, 2, 98, 111, 32, 0, 2, 113, 117, 32, 0, 5, 7, 2, 111, 0, 8, 108, 2, 98, 114, 101, 0, 122, 122, 8, 112, 3, 127, 47, 87, 0, 108, 108, 97, 114, 100, 2, 32, 3, 127, 124, 0, 4, 1, 10, 2, 122, 97, 98, 108, 3, 135, 0, 1, 17, 67, 2, 108, 101, 114, 0, 1, 17, 67, 29, 2, 17, 67, 101, 114, 32, 0, 1, 17, 67, 29, 2, 17, 67, 121, 32, 0, 1, 17, 67, 29, 2, 32, 0, 1, 21, 2, 17, 67, 105, 110, 103, 0, 1, 98, 2, 32, 0, 1, 98, 2, 98, 108, 101, 32, 0, 1, 99, 2, 32, 0, 1, 102, 2, 98, 114, 101, 0, 1, 104, 2, 106, 0, 1, 104, 99, 2, 108, 100, 0, 1, 108, 2, 98, 101, 108, 0, 1, 114, 2, 102, 108, 0, 1, 114, 98, 2, 100, 108, 0, 1, 114, 99, 115, 2, 98, 101, 114, 0, 1, 114, 102, 2, 100, 97, 121, 0, 1, 114, 112, 2, 99, 101, 0, 1, 115, 2, 108, 101, 110, 0, 1, 115, 2, 122, 17, 65, 0, 1, 116, 110, 101, 2, 99, 101, 0, 1, 116, 115, 2, 102, 108, 0, 1, 118, 2, 98, 114, 0, 1, 118, 100, 97, 2, 99, 101, 0, 1, 118, 101, 100, 2, 99, 101, 0, 2, 17, 66, 101, 13, 0, 2, 98, 101, 114, 32, 0, 2, 100, 101, 114, 12, 32, 0, 2, 100, 101, 114, 32, 12, 0, 8, 2, 17, 66, 111, 0, 8, 2, 17, 67, 121, 32, 0, 8, 2, 97, 0, 8, 2, 98, 0, 8, 2, 99, 0, 8, 2, 100, 0, 8, 2, 100, 108, 101, 0, 8, 2, 104, 0, 8, 2, 111, 0, 8, 17, 67, 2, 108, 97, 103, 101, 0, 8, 17, 67, 2, 108, 111, 0, 8, 108, 2, 98, 114, 0, 8, 109, 2, 108, 100, 0, 8, 115, 2, 100, 101, 114, 0, 8, 115, 2, 100, 108, 0, 8, 115, 2, 112, 104, 0, 8, 119, 2, 108, 100, 0, 104, 105, 1, 110, 3, 135, 13, 0, 108, 1, 108, 2, 97, 104, 32, 3, 135, 55, 0, 98, 97, 98, 1, 21, 3, 135, 69, 13, 69, 0, 100, 101, 97, 8, 3, 135, 70, 6, 139, 0, 4, 122, 2, 101, 114, 32, 3, 135, 86, 0, 122, 101, 2, 32, 0, 122, 101, 2, 100, 32, 0, 122, 97, 2, 116, 105, 111, 110, 3, 135, 86, 136, 0, 7, 6, 106, 0, 2, 106, 3, 0, 4, 1, 110, 2, 97, 32, 3, 57, 0, 2, 195, 188, 0, 4, 111, 107, 117, 108, 108, 2, 32, 14, 128, 128, 134, 3, 57, 126, 49, 132, 47, 105, 0, 195, 182, 107, 117, 108, 108, 2, 32, 14, 128, 128, 134, 0, 3, 73, 0, 97, 8, 2, 109, 97, 105, 3, 73, 117, 0, 101, 114, 101, 8, 2, 17, 67, 3, 73, 119, 34, 13, 0, 101, 115, 8, 2, 117, 105, 3, 73, 119, 86, 0, 111, 97, 8, 2, 110, 21, 3, 73, 134, 6, 35, 0, 117, 97, 110, 3, 105, 58, 124, 50, 0, 7, 6, 107, 0, 2, 107, 3, 0, 4, 3, 49, 0, 8, 2, 18, 66, 17, 71, 0, 8, 2, 104, 17, 71, 0, 8, 2, 119, 17, 71, 0, 105, 110, 101, 115, 105, 115, 3, 49, 13, 50, 6, 127, 87, 121, 87, 0, 106, 8, 2, 101, 21, 3, 49, 57, 0, 117, 97, 110, 3, 49, 58, 35, 50, 0, 105, 8, 2, 108, 17, 67, 21, 3, 49, 111, 0, 105, 8, 2, 108, 108, 21, 3, 49, 120, 0, 105, 108, 111, 8, 2, 21, 3, 49, 120, 55, 13, 0, 104, 97, 3, 49, 124, 0, 104, 97, 114, 3, 49, 125, 0, 117, 2, 99, 104, 3, 49, 132, 0, 117, 119, 97, 105, 116, 3, 49, 132, 58, 6, 136, 47, 0, 4, 110, 2, 105, 102, 3, 50, 0, 110, 2, 105, 116, 0, 110, 2, 105, 118, 0, 110, 2, 111, 98, 0, 110, 2, 111, 119, 0, 110, 8, 2, 17, 71, 0, 7, 6, 108, 0, 4, 1, 108, 3, 0, 1, 108, 17, 65, 2, 32, 3, 0, 111, 1, 21, 2, 103, 111, 117, 115, 3, 8, 55, 13, 0, 105, 110, 103, 1, 116, 10, 2, 32, 3, 10, 55, 120, 66, 0, 105, 110, 103, 1, 103, 110, 2, 32, 3, 14, 55, 120, 66, 0, 121, 1, 108, 21, 2, 32, 14, 128, 128, 130, 3, 37, 0, 4, 3, 55, 0, 1, 17, 65, 2, 108, 121, 32, 0, 1, 114, 2, 32, 0, 1, 119, 2, 32, 0, 2, 17, 67, 0, 2, 32, 0, 2, 69, 0, 8, 2, 104, 17, 71, 0, 108, 1, 17, 65, 0, 108, 1, 17, 65, 2, 17, 65, 0, 108, 1, 39, 17, 65, 0, 108, 1, 121, 0, 108, 2, 17, 67, 0, 108, 8, 2, 17, 71, 0, 108, 101, 2, 32, 0, 4, 121, 1, 21, 2, 32, 14, 128, 130, 130, 3, 55, 2, 37, 0, 121, 1, 102, 101, 105, 2, 32, 14, 128, 128, 130, 0, 121, 1, 102, 102, 2, 32, 14, 128, 128, 130, 0, 121, 1, 102, 111, 2, 32, 14, 128, 128, 130, 0, 121, 1, 112, 10, 2, 32, 14, 128, 128, 130, 0, 69, 115, 115, 1, 21, 2, 32, 14, 128, 130, 132, 3, 55, 13, 87, 0, 69, 115, 115, 108, 121, 1, 21, 2, 32, 14, 128, 130, 134, 3, 55, 13, 87, 55, 2, 37, 0, 106, 117, 8, 3, 55, 57, 132, 0, 121, 8, 2, 100, 3, 55, 120, 0, 105, 110, 117, 120, 3, 55, 120, 50, 123, 49, 87, 0, 105, 109, 1, 10, 2, 101, 110, 116, 3, 55, 120, 63, 0, 105, 110, 103, 1, 17, 66, 10, 2, 32, 3, 55, 120, 66, 0, 105, 110, 103, 115, 1, 17, 66, 10, 2, 32, 3, 55, 120, 66, 86, 0, 105, 115, 116, 101, 110, 3, 55, 120, 87, 13, 50, 0, 111, 5, 3, 8, 2, 103, 25, 3, 55, 129, 0, 117, 2, 110, 97, 3, 55, 132, 0, 4, 121, 1, 102, 2, 32, 3, 55, 135, 0, 121, 1, 112, 2, 32, 0, 121, 1, 112, 105, 116, 108, 117, 109, 0, 4, 108, 101, 100, 1, 21, 21, 2, 32, 14, 128, 136, 131, 3, 70, 0, 108, 101, 100, 1, 111, 21, 21, 2, 32, 14, 128, 136, 131, 0, 108, 97, 110, 8, 3, 103, 2, 35, 50, 0, 1, 17, 66, 2, 32, 3, 116, 0, 105, 110, 103, 1, 108, 10, 2, 32, 14, 128, 152, 132, 3, 120, 66, 0, 7, 6, 109, 0, 4, 1, 17, 66, 2, 32, 3, 13, 63, 0, 1, 104, 2, 32, 0, 110, 8, 2, 101, 3, 50, 0, 4, 3, 63, 0, 1, 108, 2, 32, 0, 98, 1, 111, 2, 101, 0, 98, 2, 32, 0, 98, 8, 111, 98, 2, 25, 0, 98, 8, 117, 100, 0, 109, 0, 110, 2, 32, 0, 101, 116, 97, 8, 2, 108, 108, 117, 3, 63, 2, 119, 47, 35, 0, 101, 1, 17, 66, 10, 2, 32, 3, 63, 2, 120, 0, 4, 97, 108, 8, 2, 102, 14, 128, 132, 131, 3, 63, 4, 35, 55, 0, 97, 108, 8, 2, 110, 14, 128, 132, 131, 0, 97, 108, 8, 2, 112, 14, 128, 132, 131, 0, 97, 108, 8, 2, 116, 114, 14, 128, 132, 131, 0, 101, 116, 97, 8, 2, 21, 3, 63, 4, 119, 47, 13, 0, 117, 108, 116, 105, 8, 2, 21, 21, 14, 128, 132, 133, 3, 63, 4, 123, 55, 47, 120, 0, 101, 1, 114, 111, 116, 2, 110, 116, 12, 3, 63, 6, 119, 0, 69, 110, 116, 97, 114, 121, 2, 32, 3, 63, 6, 119, 50, 47, 13, 34, 2, 120, 0, 101, 110, 116, 101, 100, 1, 17, 67, 3, 63, 6, 119, 50, 47, 120, 70, 0, 4, 99, 8, 2, 18, 70, 3, 63, 13, 0, 99, 8, 2, 32, 18, 70, 0, 111, 2, 110, 111, 116, 111, 0, 4, 97, 99, 8, 2, 97, 100, 14, 128, 132, 131, 3, 63, 13, 49, 0, 97, 99, 8, 2, 98, 14, 128, 132, 131, 0, 97, 99, 8, 2, 100, 14, 128, 132, 131, 0, 97, 99, 8, 2, 108, 14, 128, 132, 131, 0, 97, 99, 8, 2, 109, 14, 128, 132, 131, 0, 99, 8, 2, 17, 67, 0, 99, 8, 2, 32, 17, 67, 0, 111, 110, 2, 111, 112, 111, 108, 3, 63, 13, 50, 0, 111, 110, 111, 2, 103, 97, 3, 63, 13, 50, 6, 122, 0, 4, 69, 110, 116, 2, 32, 3, 63, 13, 50, 47, 0, 101, 110, 116, 1, 10, 2, 32, 14, 128, 128, 132, 0, 101, 110, 116, 1, 117, 2, 32, 0, 4, 101, 110, 116, 115, 1, 10, 2, 32, 14, 128, 128, 133, 3, 63, 13, 50, 47, 87, 0, 101, 110, 116, 115, 1, 117, 2, 32, 0, 4, 97, 108, 8, 2, 101, 118, 3, 63, 13, 55, 0, 97, 108, 8, 2, 105, 0, 111, 98, 105, 108, 101, 3, 63, 13, 69, 127, 55, 0, 111, 117, 116, 104, 1, 10, 2, 32, 3, 63, 13, 85, 0, 97, 8, 2, 109, 3, 63, 35, 0, 4, 99, 8, 2, 17, 65, 3, 63, 35, 49, 0, 99, 8, 2, 32, 17, 65, 0, 98, 108, 121, 3, 63, 69, 55, 2, 120, 0, 101, 116, 97, 98, 111, 3, 63, 119, 47, 6, 35, 69, 122, 0, 101, 116, 97, 108, 8, 2, 17, 67, 3, 63, 119, 47, 116, 0, 101, 110, 1, 21, 2, 32, 3, 63, 119, 50, 0, 101, 110, 116, 5, 8, 1, 10, 2, 32, 14, 128, 128, 132, 3, 63, 119, 50, 47, 0, 101, 110, 116, 115, 5, 8, 1, 10, 2, 32, 14, 128, 128, 133, 3, 63, 119, 50, 47, 87, 0, 101, 103, 97, 8, 3, 63, 119, 79, 13, 0, 111, 110, 2, 111, 120, 3, 63, 122, 50, 0, 111, 110, 111, 8, 3, 63, 122, 50, 134, 0, 117, 108, 116, 105, 8, 3, 63, 123, 55, 47, 120, 0, 111, 98, 105, 108, 101, 8, 3, 63, 134, 69, 135, 55, 0, 111, 115, 116, 1, 21, 2, 32, 14, 128, 128, 132, 3, 63, 134, 87, 47, 0, 97, 121, 111, 114, 5, 35, 3, 63, 138, 0, 7, 6, 110, 0, 4, 1, 110, 3, 0, 4, 1, 110, 2, 32, 3, 0, 4, 100, 1, 32, 50, 2, 32, 3, 0, 101, 1, 110, 10, 2, 32, 3, 0, 2, 17, 67, 111, 32, 3, 8, 50, 0, 4, 1, 17, 66, 2, 32, 3, 13, 50, 0, 1, 69, 2, 32, 0, 8, 2, 103, 17, 71, 12, 3, 14, 66, 0, 4, 3, 50, 0, 1, 21, 2, 99, 104, 0, 1, 97, 105, 10, 2, 32, 14, 128, 128, 129, 0, 1, 103, 2, 32, 0, 1, 103, 2, 105, 110, 103, 12, 0, 1, 108, 2, 32, 0, 2, 107, 110, 0, 101, 1, 17, 66, 10, 2, 32, 3, 50, 2, 120, 0, 97, 110, 111, 8, 2, 14, 128, 132, 132, 3, 50, 4, 35, 50, 134, 0, 111, 110, 8, 2, 21, 14, 128, 132, 131, 3, 50, 4, 122, 50, 0, 101, 119, 115, 8, 2, 14, 128, 132, 132, 3, 50, 6, 57, 132, 86, 0, 101, 119, 115, 5, 3, 8, 2, 14, 128, 132, 132, 3, 50, 6, 132, 86, 0, 101, 115, 115, 1, 10, 2, 32, 14, 128, 130, 132, 3, 50, 13, 87, 0, 101, 99, 101, 115, 115, 105, 116, 3, 50, 13, 87, 119, 87, 120, 47, 0, 39, 116, 3, 50, 47, 0, 107, 5, 7, 3, 50, 49, 0, 115, 1, 97, 105, 10, 2, 32, 14, 128, 128, 130, 3, 50, 86, 0, 101, 115, 115, 5, 8, 1, 10, 2, 32, 14, 128, 130, 132, 3, 50, 119, 87, 0, 111, 110, 99, 104, 97, 108, 97, 5, 3, 2, 110, 3, 50, 122, 50, 89, 13, 55, 6, 124, 0, 111, 110, 99, 104, 97, 108, 97, 2, 110, 3, 50, 122, 50, 89, 13, 55, 13, 0, 117, 114, 115, 101, 8, 2, 17, 66, 3, 50, 126, 87, 0, 101, 111, 8, 3, 50, 127, 134, 0, 97, 117, 115, 101, 3, 50, 128, 87, 120, 0, 105, 110, 116, 104, 3, 50, 135, 50, 85, 0, 97, 109, 101, 1, 10, 2, 32, 14, 128, 128, 132, 3, 50, 136, 63, 0, 4, 1, 21, 2, 99, 17, 67, 3, 66, 0, 2, 99, 32, 0, 2, 120, 0, 103, 0, 107, 3, 66, 49, 0, 7, 6, 111, 0, 4, 2, 98, 106, 101, 3, 2, 122, 0, 2, 98, 108, 105, 103, 97, 116, 111, 0, 8, 2, 98, 108, 0, 8, 2, 98, 115, 0, 8, 2, 98, 116, 0, 112, 112, 111, 114, 2, 116, 117, 3, 2, 122, 48, 112, 0, 98, 115, 8, 2, 101, 114, 3, 2, 122, 69, 86, 0, 4, 1, 99, 2, 105, 110, 99, 105, 3, 2, 134, 0, 1, 100, 2, 100, 101, 99, 0, 1, 108, 2, 99, 97, 116, 0, 8, 2, 98, 101, 115, 0, 39, 8, 2, 14, 128, 132, 130, 0, 1, 108, 2, 99, 111, 109, 3, 4, 134, 0, 101, 2, 118, 101, 3, 4, 134, 6, 119, 0, 4, 2, 17, 67, 105, 99, 32, 3, 6, 122, 0, 2, 17, 67, 105, 99, 97, 108, 0, 2, 103, 101, 110, 111, 117, 115, 0, 2, 103, 101, 110, 121, 0, 116, 114, 111, 2, 112, 121, 3, 6, 122, 47, 34, 13, 0, 112, 111, 108, 1, 21, 2, 18, 67, 3, 6, 122, 48, 13, 55, 0, 99, 114, 97, 116, 101, 115, 2, 32, 3, 6, 122, 49, 34, 117, 47, 127, 86, 0, 120, 2, 105, 100, 101, 3, 6, 122, 49, 87, 0, 109, 101, 116, 101, 114, 1, 21, 3, 6, 122, 63, 120, 47, 13, 0, 103, 114, 97, 112, 104, 101, 114, 1, 21, 3, 6, 122, 79, 34, 13, 81, 112, 0, 112, 104, 97, 1, 99, 114, 2, 103, 3, 6, 122, 81, 13, 0, 4, 1, 116, 115, 117, 99, 2, 100, 105, 3, 6, 134, 0, 2, 17, 66, 97, 32, 0, 2, 17, 66, 101, 111, 110, 0, 2, 17, 66, 105, 17, 65, 0, 2, 17, 67, 105, 32, 0, 2, 17, 67, 111, 32, 0, 2, 17, 67, 111, 105, 115, 116, 0, 2, 98, 105, 99, 32, 0, 2, 99, 114, 101, 32, 0, 97, 2, 32, 3, 6, 134, 13, 0, 4, 105, 2, 110, 97, 32, 3, 6, 137, 0, 121, 2, 17, 65, 32, 0, 101, 97, 2, 32, 3, 6, 139, 0, 4, 1, 10, 2, 112, 104, 101, 114, 3, 8, 13, 0, 2, 99, 121, 116, 101, 32, 0, 103, 1, 108, 21, 2, 121, 3, 8, 13, 73, 0, 103, 105, 115, 109, 1, 108, 3, 8, 13, 73, 120, 86, 13, 63, 0, 112, 104, 101, 1, 10, 2, 32, 3, 8, 13, 81, 2, 120, 0, 1, 17, 67, 21, 21, 2, 32, 3, 8, 134, 0, 4, 1, 10, 2, 103, 101, 110, 32, 3, 13, 0, 1, 10, 2, 112, 32, 0, 1, 102, 102, 2, 99, 17, 65, 0, 1, 104, 115, 105, 98, 2, 112, 0, 1, 104, 116, 101, 109, 2, 100, 32, 0, 1, 105, 114, 101, 112, 2, 100, 32, 0, 1, 109, 2, 120, 0, 1, 109, 109, 2, 100, 111, 114, 0, 1, 112, 2, 116, 101, 110, 116, 105, 0, 1, 115, 2, 112, 104, 105, 115, 116, 105, 99, 0, 1, 116, 2, 98, 97, 99, 99, 0, 1, 116, 115, 117, 99, 2, 100, 0, 1, 118, 105, 112, 2, 116, 0, 2, 99, 99, 97, 115, 105, 0, 2, 99, 99, 108, 117, 0, 2, 102, 102, 105, 99, 105, 0, 2, 112, 105, 110, 105, 0, 102, 2, 102, 101, 110, 0, 4, 116, 1, 103, 10, 2, 32, 3, 13, 47, 0, 116, 1, 114, 114, 2, 32, 0, 112, 112, 2, 114, 101, 115, 3, 13, 48, 0, 112, 111, 108, 105, 116, 97, 110, 3, 13, 48, 6, 122, 55, 120, 47, 13, 50, 0, 112, 101, 100, 1, 10, 2, 32, 3, 13, 48, 70, 0, 99, 107, 1, 17, 67, 11, 10, 2, 32, 3, 13, 49, 0, 4, 99, 99, 117, 114, 3, 13, 49, 126, 0, 99, 99, 117, 114, 114, 0, 4, 99, 99, 117, 114, 5, 5, 3, 13, 49, 146, 0, 99, 99, 117, 114, 114, 5, 5, 0, 105, 120, 2, 32, 3, 58, 35, 0, 105, 115, 1, 21, 2, 32, 3, 58, 124, 0, 4, 105, 114, 3, 58, 125, 0, 105, 114, 101, 0, 101, 1, 10, 2, 115, 32, 14, 128, 128, 130, 3, 86, 0, 101, 115, 111, 112, 104, 97, 3, 111, 87, 122, 81, 13, 0, 4, 3, 122, 0, 1, 98, 2, 116, 104, 101, 114, 0, 1, 104, 2, 112, 32, 0, 1, 108, 102, 2, 112, 32, 0, 1, 109, 2, 100, 101, 108, 0, 1, 109, 2, 100, 101, 114, 0, 1, 109, 2, 100, 101, 115, 116, 0, 1, 112, 2, 112, 32, 0, 1, 114, 2, 103, 101, 114, 0, 1, 114, 2, 112, 32, 0, 1, 114, 112, 2, 112, 101, 0, 1, 116, 2, 112, 32, 0, 2, 17, 66, 101, 17, 67, 111, 32, 0, 2, 17, 67, 101, 109, 105, 99, 0, 2, 17, 67, 101, 116, 32, 0, 2, 98, 108, 105, 103, 97, 0, 2, 98, 108, 111, 0, 2, 98, 115, 116, 105, 110, 0, 2, 102, 102, 105, 99, 0, 2, 120, 12, 12, 0, 8, 2, 17, 67, 121, 12, 0, 8, 2, 112, 101, 114, 0, 8, 98, 2, 100, 121, 0, 8, 114, 2, 98, 101, 114, 0, 8, 114, 2, 116, 104, 101, 114, 0, 104, 1, 106, 2, 110, 0, 116, 121, 108, 101, 1, 99, 3, 122, 47, 120, 55, 6, 127, 0, 120, 121, 3, 122, 49, 87, 120, 0, 98, 115, 111, 2, 108, 3, 122, 69, 87, 13, 0, 4, 103, 101, 1, 108, 21, 2, 32, 3, 122, 79, 0, 103, 117, 101, 1, 21, 21, 0, 4, 1, 100, 2, 122, 101, 110, 3, 123, 0, 1, 116, 2, 110, 103, 117, 0, 2, 116, 104, 101, 114, 12, 0, 4, 101, 1, 102, 2, 116, 17, 65, 3, 127, 0, 101, 8, 2, 100, 0, 101, 8, 2, 115, 0, 97, 1, 114, 98, 2, 100, 3, 128, 0, 4, 5, 3, 1, 10, 2, 102, 102, 3, 129, 0, 5, 3, 1, 99, 2, 102, 102, 0, 5, 3, 1, 103, 2, 110, 103, 0, 5, 3, 1, 108, 99, 2, 116, 104, 0, 5, 3, 1, 109, 2, 116, 104, 0, 5, 3, 1, 114, 2, 110, 103, 0, 5, 3, 1, 115, 2, 110, 103, 0, 5, 3, 2, 102, 116, 0, 5, 3, 8, 2, 102, 102, 0, 4, 39, 101, 114, 3, 131, 0, 97, 114, 0, 97, 114, 2, 32, 0, 4, 1, 100, 2, 105, 110, 103, 3, 132, 0, 101, 1, 104, 115, 2, 12, 0, 4, 1, 17, 67, 29, 2, 17, 66, 97, 108, 3, 134, 0, 1, 17, 67, 29, 2, 17, 66, 117, 115, 32, 0, 1, 21, 2, 105, 115, 116, 0, 1, 29, 2, 17, 66, 121, 32, 0, 1, 29, 2, 112, 104, 101, 114, 0, 1, 98, 2, 116, 104, 0, 1, 99, 2, 116, 97, 110, 0, 1, 100, 2, 99, 105, 108, 0, 1, 102, 2, 99, 17, 65, 0, 1, 103, 105, 2, 32, 0, 1, 107, 2, 100, 17, 65, 0, 1, 109, 2, 116, 105, 118, 0, 1, 110, 2, 98, 105, 108, 0, 1, 110, 2, 98, 108, 0, 1, 110, 2, 116, 97, 0, 1, 110, 2, 116, 111, 114, 0, 1, 114, 2, 116, 97, 0, 1, 114, 2, 116, 111, 0, 1, 114, 99, 2, 97, 116, 0, 1, 114, 99, 2, 99, 117, 0, 1, 114, 112, 112, 97, 2, 112, 0, 1, 116, 2, 116, 97, 0, 2, 17, 66, 101, 13, 0, 2, 17, 66, 101, 110, 17, 67, 0, 2, 17, 66, 105, 110, 103, 0, 2, 17, 67, 97, 103, 104, 32, 0, 2, 32, 0, 2, 98, 97, 0, 2, 98, 101, 100, 0, 2, 98, 121, 32, 0, 2, 100, 97, 32, 0, 2, 103, 97, 110, 32, 0, 2, 104, 17, 65, 0, 2, 105, 110, 103, 0, 2, 105, 115, 109, 0, 2, 107, 121, 32, 0, 2, 115, 104, 17, 65, 32, 0, 2, 116, 97, 116, 0, 2, 116, 105, 111, 110, 0, 8, 2, 17, 66, 97, 108, 0, 8, 2, 122, 111, 0, 8, 17, 67, 2, 116, 105, 0, 8, 104, 2, 99, 117, 0, 8, 108, 2, 99, 17, 65, 0, 8, 109, 2, 98, 105, 108, 0, 8, 114, 2, 98, 111, 0, 8, 118, 2, 99, 17, 65, 0, 97, 0, 101, 0, 104, 0, 101, 114, 3, 134, 13, 0, 116, 111, 114, 1, 109, 3, 134, 47, 13, 0, 116, 105, 99, 1, 110, 2, 17, 65, 3, 134, 47, 111, 87, 0, 116, 111, 1, 114, 112, 2, 110, 3, 134, 47, 122, 0, 116, 111, 1, 114, 112, 3, 134, 47, 134, 0, 4, 112, 101, 1, 110, 117, 2, 110, 3, 134, 48, 13, 0, 112, 101, 8, 2, 110, 0, 112, 101, 100, 1, 99, 2, 32, 3, 134, 48, 70, 0, 99, 104, 1, 114, 116, 3, 134, 49, 0, 100, 111, 2, 114, 17, 65, 3, 134, 70, 13, 0, 4, 100, 111, 114, 3, 134, 70, 112, 0, 100, 111, 117, 114, 0, 103, 101, 110, 105, 2, 99, 3, 134, 73, 6, 119, 50, 120, 0, 4, 103, 8, 2, 114, 101, 3, 134, 79, 0, 103, 117, 101, 1, 114, 0, 103, 117, 101, 1, 118, 0, 4, 116, 104, 1, 108, 2, 105, 3, 134, 84, 0, 116, 104, 1, 108, 2, 105, 97, 110, 0, 116, 104, 1, 114, 116, 101, 98, 0, 116, 104, 101, 1, 108, 99, 0, 116, 104, 101, 1, 114, 116, 0, 105, 2, 99, 3, 134, 111, 0, 101, 1, 112, 2, 116, 105, 3, 134, 119, 0, 4, 101, 1, 112, 2, 109, 3, 134, 120, 0, 101, 1, 112, 2, 116, 0, 4, 105, 3, 137, 0, 105, 2, 99, 101, 0, 105, 2, 99, 101, 13, 0, 105, 2, 99, 107, 0, 121, 0, 105, 97, 3, 137, 13, 0, 7, 6, 112, 0, 4, 1, 115, 97, 114, 2, 98, 3, 0, 2, 112, 3, 0, 104, 111, 110, 121, 1, 10, 2, 32, 3, 8, 81, 13, 50, 120, 0, 4, 116, 1, 105, 101, 3, 47, 0, 116, 8, 2, 17, 71, 0, 4, 3, 48, 0, 2, 104, 97, 122, 97, 0, 2, 104, 111, 108, 101, 0, 8, 2, 18, 66, 17, 71, 0, 104, 2, 97, 109, 32, 0, 104, 2, 101, 114, 100, 0, 111, 114, 2, 116, 114, 97, 121, 3, 48, 2, 131, 0, 111, 108, 121, 2, 21, 21, 3, 48, 4, 122, 55, 120, 0, 121, 114, 111, 8, 2, 21, 21, 14, 128, 132, 132, 3, 48, 4, 135, 34, 134, 0, 97, 108, 101, 111, 8, 2, 21, 14, 128, 132, 133, 3, 48, 4, 136, 55, 127, 134, 0, 97, 1, 109, 121, 115, 3, 48, 13, 0, 111, 116, 97, 2, 116, 3, 48, 13, 47, 136, 0, 121, 111, 110, 3, 48, 57, 122, 50, 0, 117, 114, 8, 2, 115, 117, 3, 48, 112, 0, 117, 116, 2, 32, 3, 48, 115, 47, 0, 111, 108, 121, 2, 21, 3, 48, 122, 55, 120, 0, 117, 116, 1, 115, 2, 32, 3, 48, 123, 47, 0, 105, 99, 111, 8, 3, 48, 127, 49, 134, 0, 105, 101, 99, 101, 2, 32, 14, 128, 128, 133, 3, 48, 127, 87, 0, 121, 114, 111, 109, 2, 101, 3, 48, 135, 34, 6, 122, 63, 0, 110, 8, 2, 101, 117, 3, 50, 0, 110, 101, 117, 3, 50, 57, 132, 0, 4, 102, 8, 2, 17, 71, 3, 81, 0, 104, 0, 104, 8, 2, 17, 71, 0, 104, 8, 2, 18, 66, 17, 71, 0, 104, 101, 110, 121, 108, 3, 81, 4, 127, 50, 135, 55, 0, 104, 111, 116, 111, 8, 2, 21, 21, 14, 128, 132, 133, 3, 81, 4, 134, 47, 134, 0, 104, 121, 99, 111, 8, 3, 81, 4, 135, 49, 134, 0, 104, 116, 104, 8, 2, 17, 65, 3, 81, 85, 0, 104, 101, 110, 111, 109, 101, 2, 110, 3, 81, 111, 50, 122, 63, 120, 0, 104, 105, 108, 97, 3, 81, 120, 55, 35, 0, 4, 104, 111, 116, 2, 111, 103, 114, 97, 112, 104, 12, 3, 81, 134, 47, 0, 104, 111, 116, 8, 2, 111, 18, 75, 12, 12, 0, 104, 111, 116, 111, 99, 111, 112, 3, 81, 134, 47, 13, 49, 122, 48, 0, 104, 111, 116, 111, 110, 3, 81, 134, 47, 122, 50, 0, 104, 111, 116, 111, 3, 81, 134, 47, 134, 0, 115, 8, 2, 17, 71, 3, 87, 0, 115, 121, 99, 104, 111, 2, 108, 111, 3, 87, 2, 135, 49, 122, 0, 115, 101, 117, 100, 111, 3, 87, 132, 70, 134, 0, 115, 121, 99, 104, 3, 87, 135, 49, 0, 115, 121, 99, 104, 111, 3, 87, 135, 49, 134, 0, 7, 6, 113, 0, 2, 113, 3, 0, 4, 3, 49, 0, 117, 1, 99, 97, 106, 0, 117, 2, 32, 0, 117, 2, 101, 114, 32, 0, 117, 101, 1, 21, 2, 32, 0, 117, 101, 116, 116, 3, 49, 6, 119, 47, 0, 117, 105, 1, 115, 101, 109, 2, 116, 3, 49, 6, 127, 0, 117, 101, 117, 3, 49, 57, 132, 0, 117, 3, 49, 58, 0, 117, 2, 17, 67, 3, 49, 58, 13, 0, 117, 101, 8, 2, 32, 3, 49, 58, 119, 0, 117, 101, 115, 116, 3, 49, 58, 119, 87, 47, 0, 117, 121, 3, 49, 58, 120, 0, 117, 97, 1, 115, 2, 17, 66, 3, 49, 58, 122, 0, 117, 97, 115, 2, 17, 65, 3, 49, 58, 136, 86, 0, 117, 97, 115, 105, 3, 49, 58, 136, 86, 135, 0, 117, 101, 116, 1, 97, 114, 3, 49, 111, 47, 0, 117, 111, 114, 1, 105, 108, 3, 49, 112, 0, 117, 97, 121, 3, 49, 127, 0, 117, 101, 116, 2, 32, 3, 49, 136, 0, 7, 6, 114, 0, 4, 1, 114, 2, 32, 3, 0, 100, 1, 32, 51, 2, 32, 3, 0, 109, 8, 3, 4, 125, 119, 63, 0, 1, 21, 2, 17, 66, 3, 13, 0, 4, 3, 34, 0, 104, 1, 17, 67, 0, 104, 8, 2, 17, 71, 0, 114, 0, 119, 8, 2, 97, 3, 34, 2, 115, 0, 121, 1, 116, 110, 97, 10, 2, 32, 14, 128, 128, 130, 3, 34, 2, 120, 0, 4, 114, 104, 101, 97, 3, 34, 6, 139, 0, 114, 104, 111, 101, 97, 0, 1, 17, 67, 2, 32, 24, 3, 34, 13, 0, 69, 114, 2, 32, 3, 34, 112, 0, 104, 121, 116, 104, 3, 34, 120, 84, 0, 4, 117, 110, 8, 2, 97, 3, 34, 123, 50, 0, 117, 110, 8, 2, 111, 0, 4, 104, 101, 117, 3, 34, 132, 0, 117, 8, 2, 98, 18, 66, 0, 4, 104, 111, 8, 2, 100, 3, 34, 134, 0, 104, 111, 8, 2, 116, 0, 104, 111, 100, 111, 8, 2, 21, 3, 34, 134, 70, 13, 0, 4, 104, 105, 2, 110, 3, 34, 135, 0, 104, 105, 2, 122, 0, 1, 101, 2, 32, 3, 112, 0, 7, 6, 115, 0, 4, 2, 99, 105, 111, 117, 115, 3, 0, 4, 2, 115, 3, 0, 116, 1, 32, 49, 2, 32, 3, 0, 104, 101, 39, 8, 3, 2, 89, 127, 0, 101, 108, 102, 2, 32, 3, 6, 87, 119, 55, 81, 0, 101, 108, 118, 101, 115, 2, 32, 3, 6, 87, 119, 55, 82, 86, 0, 105, 97, 2, 32, 3, 8, 86, 139, 0, 99, 111, 112, 121, 1, 21, 2, 32, 3, 8, 87, 49, 13, 48, 2, 120, 0, 99, 105, 115, 2, 32, 3, 8, 87, 49, 120, 87, 0, 99, 105, 2, 32, 3, 8, 87, 49, 135, 0, 105, 97, 1, 17, 67, 2, 32, 3, 8, 87, 139, 0, 105, 97, 5, 3, 2, 32, 3, 8, 88, 13, 0, 115, 105, 111, 110, 2, 32, 3, 8, 89, 13, 50, 0, 115, 105, 111, 110, 5, 8, 2, 32, 3, 8, 89, 123, 50, 0, 105, 97, 110, 1, 21, 2, 32, 14, 128, 128, 129, 3, 50, 0, 4, 1, 21, 2, 32, 14, 128, 128, 129, 3, 86, 0, 1, 32, 15, 2, 32, 0, 1, 32, 54, 49, 2, 32, 0, 1, 39, 32, 15, 2, 32, 0, 1, 97, 2, 101, 108, 32, 0, 1, 97, 2, 109, 0, 1, 97, 101, 2, 105, 101, 0, 1, 97, 101, 2, 105, 108, 0, 1, 97, 101, 2, 121, 0, 1, 97, 101, 108, 112, 2, 101, 0, 1, 97, 101, 112, 2, 101, 0, 1, 97, 101, 116, 2, 101, 0, 1, 97, 104, 112, 2, 101, 0, 1, 97, 108, 2, 101, 0, 1, 97, 109, 2, 101, 0, 1, 97, 112, 2, 101, 0, 1, 97, 114, 2, 101, 0, 1, 103, 110, 2, 32, 14, 128, 128, 129, 0, 1, 105, 17, 65, 2, 121, 0, 1, 105, 97, 2, 101, 0, 1, 105, 114, 112, 2, 111, 0, 1, 109, 2, 105, 0, 1, 109, 2, 121, 0, 1, 110, 2, 32, 14, 128, 128, 129, 0, 1, 111, 2, 109, 0, 1, 111, 17, 67, 2, 69, 110, 0, 1, 111, 17, 67, 2, 69, 114, 0, 1, 114, 2, 100, 0, 2, 32, 0, 8, 97, 101, 2, 101, 0, 8, 97, 104, 2, 32, 0, 8, 101, 114, 2, 111, 0, 8, 105, 111, 17, 67, 2, 101, 0, 101, 1, 105, 117, 2, 32, 0, 101, 1, 111, 2, 32, 0, 101, 1, 111, 100, 2, 32, 0, 101, 1, 111, 111, 104, 99, 0, 101, 1, 111, 116, 2, 32, 0, 101, 1, 117, 97, 2, 32, 0, 101, 1, 117, 102, 2, 32, 0, 101, 1, 119, 0, 4, 105, 110, 1, 105, 97, 2, 32, 3, 86, 13, 50, 0, 105, 110, 1, 117, 2, 32, 0, 105, 98, 1, 17, 65, 3, 86, 13, 69, 0, 4, 3, 87, 0, 1, 21, 2, 104, 101, 97, 100, 32, 0, 1, 21, 2, 104, 105, 108, 108, 32, 0, 1, 21, 2, 104, 111, 117, 115, 0, 1, 97, 2, 101, 0, 1, 99, 2, 32, 0, 1, 99, 10, 2, 32, 14, 128, 128, 129, 0, 1, 101, 112, 10, 2, 32, 14, 128, 128, 129, 0, 1, 101, 116, 2, 32, 14, 128, 128, 129, 0, 1, 102, 2, 32, 0, 1, 102, 10, 2, 32, 14, 128, 128, 129, 0, 1, 104, 116, 2, 32, 0, 1, 104, 116, 10, 2, 32, 14, 128, 128, 129, 0, 1, 105, 114, 2, 32, 14, 128, 128, 129, 0, 1, 107, 2, 32, 0, 1, 107, 10, 2, 32, 14, 128, 128, 129, 0, 1, 112, 2, 32, 0, 1, 112, 10, 2, 32, 14, 128, 128, 129, 0, 1, 116, 2, 32, 14, 128, 128, 129, 0, 1, 116, 10, 2, 32, 14, 128, 128, 129, 0, 2, 115, 104, 0, 5, 3, 1, 101, 114, 2, 111, 117, 114, 0, 8, 2, 99, 17, 71, 0, 8, 2, 99, 18, 66, 17, 71, 0, 8, 2, 107, 17, 71, 0, 8, 2, 107, 18, 66, 17, 71, 0, 8, 2, 108, 17, 71, 0, 8, 2, 109, 17, 71, 0, 8, 2, 110, 17, 71, 0, 8, 2, 112, 17, 71, 0, 8, 2, 112, 18, 66, 17, 71, 0, 8, 2, 112, 104, 17, 71, 0, 8, 2, 113, 117, 0, 8, 2, 114, 105, 0, 8, 2, 116, 17, 71, 0, 8, 2, 116, 114, 17, 71, 0, 8, 2, 117, 0, 8, 2, 118, 97, 0, 8, 2, 118, 101, 0, 8, 2, 119, 17, 71, 0, 8, 2, 122, 17, 71, 0, 8, 17, 65, 17, 66, 2, 32, 0, 8, 105, 109, 2, 104, 0, 99, 1, 117, 109, 2, 108, 0, 99, 2, 18, 67, 0, 101, 1, 111, 111, 2, 32, 0, 115, 1, 111, 114, 99, 2, 104, 0, 115, 2, 32, 0, 115, 101, 2, 32, 0, 101, 109, 105, 8, 2, 21, 21, 14, 128, 132, 132, 3, 87, 4, 119, 63, 111, 0, 99, 105, 2, 98, 3, 87, 13, 0, 105, 110, 1, 97, 2, 32, 3, 87, 13, 50, 0, 116, 8, 2, 32, 3, 87, 13, 50, 47, 0, 111, 109, 97, 8, 2, 108, 105, 3, 87, 13, 63, 124, 0, 105, 98, 1, 10, 3, 87, 13, 69, 0, 111, 99, 105, 101, 8, 2, 116, 3, 87, 13, 87, 142, 0, 116, 101, 105, 110, 3, 87, 47, 135, 50, 0, 116, 97, 116, 101, 8, 2, 21, 3, 87, 47, 136, 47, 0, 4, 99, 2, 101, 112, 116, 3, 87, 49, 0, 99, 104, 2, 111, 0, 99, 104, 5, 3, 2, 101, 100, 0, 99, 104, 8, 2, 105, 115, 109, 0, 99, 97, 114, 8, 2, 97, 3, 87, 49, 35, 34, 0, 99, 104, 105, 122, 8, 3, 87, 49, 120, 47, 87, 0, 99, 104, 101, 2, 109, 3, 87, 49, 127, 0, 99, 97, 114, 8, 2, 17, 65, 3, 87, 49, 138, 0, 99, 97, 114, 99, 3, 87, 49, 138, 87, 0, 101, 8, 2, 99, 108, 117, 3, 87, 111, 0, 101, 99, 117, 114, 3, 87, 111, 49, 57, 141, 0, 101, 109, 105, 110, 8, 3, 87, 119, 63, 120, 50, 0, 121, 2, 110, 101, 114, 103, 3, 87, 120, 0, 111, 109, 101, 1, 21, 2, 32, 14, 128, 128, 132, 3, 87, 123, 63, 0, 111, 109, 101, 1, 111, 21, 21, 2, 32, 14, 128, 128, 132, 3, 87, 134, 63, 0, 105, 122, 101, 8, 2, 17, 67, 21, 3, 87, 135, 86, 0, 4, 105, 111, 110, 1, 17, 65, 3, 88, 13, 50, 0, 105, 111, 110, 5, 3, 1, 114, 101, 0, 105, 111, 110, 5, 8, 1, 17, 65, 3, 88, 123, 50, 0, 4, 99, 104, 2, 17, 67, 3, 89, 0, 99, 104, 2, 32, 0, 99, 104, 8, 0, 99, 104, 8, 2, 105, 108, 0, 99, 104, 8, 101, 0, 104, 0, 104, 8, 2, 17, 71, 0, 104, 8, 2, 18, 66, 17, 71, 0, 115, 2, 117, 101, 0, 115, 117, 114, 101, 1, 97, 3, 89, 6, 141, 0, 4, 104, 105, 114, 101, 1, 10, 2, 32, 14, 128, 128, 133, 3, 89, 13, 0, 115, 105, 97, 2, 32, 0, 4, 105, 111, 110, 1, 17, 67, 3, 89, 13, 50, 0, 115, 105, 111, 110, 0, 115, 117, 114, 3, 89, 112, 0, 104, 105, 112, 1, 10, 2, 32, 14, 128, 128, 132, 3, 89, 120, 48, 0, 104, 105, 112, 115, 1, 10, 2, 32, 14, 128, 128, 133, 3, 89, 120, 48, 87, 0, 105, 111, 110, 5, 8, 1, 17, 67, 3, 89, 123, 50, 0, 195, 173, 111, 8, 3, 89, 127, 0, 115, 117, 101, 1, 105, 116, 3, 89, 132, 0, 104, 105, 114, 101, 5, 3, 1, 10, 2, 32, 14, 128, 128, 133, 3, 89, 139, 0, 115, 117, 114, 1, 97, 3, 89, 141, 0, 1, 32, 54, 2, 32, 3, 111, 86, 0, 8, 2, 32, 3, 119, 87, 0, 4, 1, 101, 99, 21, 2, 32, 14, 128, 128, 129, 3, 121, 86, 0, 1, 101, 115, 10, 2, 32, 14, 128, 128, 129, 0, 1, 101, 115, 115, 10, 2, 32, 14, 128, 128, 130, 0, 7, 6, 116, 0, 4, 1, 115, 2, 108, 3, 0, 1, 116, 3, 0, 105, 118, 101, 1, 17, 67, 17, 65, 2, 32, 3, 8, 47, 120, 82, 0, 117, 1, 21, 2, 108, 97, 116, 101, 3, 8, 74, 115, 0, 4, 3, 47, 0, 1, 105, 112, 2, 105, 97, 0, 1, 115, 105, 2, 105, 97, 110, 12, 0, 8, 2, 114, 17, 71, 0, 8, 2, 115, 17, 71, 0, 8, 2, 119, 17, 71, 0, 115, 107, 8, 3, 47, 6, 13, 87, 49, 0, 4, 111, 2, 109, 111, 114, 114, 3, 47, 13, 0, 116, 117, 2, 114, 0, 4, 114, 105, 8, 2, 98, 117, 3, 47, 34, 120, 0, 114, 105, 8, 2, 103, 0, 114, 105, 8, 2, 110, 105, 0, 114, 105, 8, 2, 118, 105, 0, 114, 105, 8, 2, 120, 17, 65, 0, 4, 114, 105, 8, 2, 17, 65, 3, 47, 34, 135, 0, 114, 105, 8, 2, 17, 67, 17, 65, 0, 114, 105, 8, 2, 17, 67, 121, 0, 114, 105, 101, 8, 0, 114, 105, 98, 101, 3, 47, 34, 135, 69, 0, 105, 97, 110, 8, 3, 47, 57, 35, 50, 0, 105, 97, 108, 1, 115, 10, 3, 47, 57, 116, 0, 4, 122, 3, 47, 87, 0, 122, 8, 2, 97, 114, 0, 4, 115, 101, 2, 32, 3, 47, 87, 37, 0, 122, 101, 2, 32, 0, 115, 117, 8, 3, 47, 87, 132, 0, 101, 114, 97, 8, 3, 47, 119, 34, 13, 0, 101, 108, 101, 8, 3, 47, 119, 55, 111, 0, 111, 8, 2, 110, 110, 3, 47, 123, 0, 119, 111, 8, 3, 47, 132, 0, 111, 119, 110, 1, 21, 2, 32, 14, 128, 128, 132, 3, 47, 133, 50, 0, 4, 99, 104, 3, 74, 0, 115, 99, 104, 0, 117, 114, 1, 21, 2, 97, 108, 32, 3, 74, 8, 13, 34, 0, 105, 97, 1, 115, 10, 2, 32, 3, 74, 13, 0, 4, 117, 114, 1, 21, 2, 17, 65, 3, 74, 13, 34, 0, 117, 114, 1, 21, 2, 121, 0, 105, 111, 110, 1, 115, 10, 3, 74, 13, 50, 0, 4, 117, 114, 1, 21, 2, 32, 3, 74, 112, 0, 117, 114, 101, 2, 32, 0, 105, 111, 110, 5, 8, 1, 115, 10, 3, 74, 123, 50, 0, 117, 1, 21, 2, 97, 108, 3, 74, 132, 0, 103, 97, 1, 114, 2, 103, 3, 79, 120, 0, 1, 21, 2, 105, 97, 3, 89, 0, 105, 111, 110, 1, 10, 3, 89, 8, 13, 50, 0, 105, 111, 117, 115, 1, 10, 3, 89, 8, 13, 87, 0, 105, 111, 110, 2, 97, 108, 3, 89, 8, 14, 50, 0, 105, 111, 110, 5, 8, 1, 10, 3, 89, 8, 123, 50, 0, 4, 105, 97, 1, 10, 2, 32, 3, 89, 13, 0, 105, 97, 1, 105, 2, 108, 105, 18, 71, 0, 4, 105, 97, 110, 1, 10, 2, 32, 3, 89, 13, 50, 0, 105, 101, 110, 1, 10, 0, 105, 101, 110, 99, 101, 1, 10, 3, 89, 13, 50, 87, 0, 105, 97, 108, 1, 10, 3, 89, 116, 0, 105, 1, 10, 2, 97, 108, 105, 3, 89, 120, 0, 101, 2, 114, 114, 101, 115, 116, 3, 106, 13, 0, 7, 6, 117, 0, 108, 1, 102, 2, 102, 105, 108, 3, 2, 115, 55, 0, 108, 116, 114, 97, 8, 2, 21, 3, 4, 115, 55, 47, 34, 35, 0, 4, 1, 21, 2, 100, 97, 32, 3, 6, 57, 132, 0, 1, 102, 2, 103, 97, 108, 0, 2, 17, 67, 105, 17, 65, 0, 2, 115, 105, 111, 110, 0, 2, 116, 105, 111, 110, 0, 4, 1, 108, 2, 115, 105, 111, 110, 3, 6, 132, 0, 1, 114, 2, 17, 67, 105, 17, 65, 0, 1, 114, 2, 115, 105, 111, 110, 0, 1, 115, 2, 17, 67, 17, 65, 32, 0, 2, 103, 97, 32, 0, 2, 107, 105, 32, 0, 2, 109, 97, 32, 0, 2, 109, 111, 32, 0, 2, 122, 122, 105, 32, 0, 121, 2, 17, 65, 32, 3, 6, 132, 57, 0, 4, 1, 10, 2, 108, 111, 117, 115, 32, 3, 8, 57, 115, 0, 1, 21, 2, 108, 97, 32, 0, 1, 21, 2, 108, 97, 114, 0, 1, 21, 2, 108, 97, 116, 101, 0, 1, 21, 2, 108, 117, 109, 0, 108, 105, 1, 21, 2, 32, 3, 8, 57, 115, 55, 135, 0, 2, 97, 32, 3, 8, 57, 132, 0, 111, 117, 115, 1, 21, 3, 8, 57, 132, 13, 87, 0, 1, 104, 2, 32, 3, 8, 132, 0, 111, 117, 115, 1, 18, 66, 21, 3, 8, 132, 13, 87, 0, 108, 108, 121, 1, 102, 10, 2, 32, 3, 13, 55, 2, 120, 0, 109, 1, 114, 2, 101, 110, 116, 3, 13, 63, 0, 103, 103, 101, 1, 115, 2, 115, 116, 3, 13, 73, 119, 0, 115, 1, 10, 2, 32, 3, 13, 87, 0, 97, 1, 103, 2, 114, 17, 65, 3, 35, 0, 2, 108, 17, 65, 3, 57, 115, 0, 4, 1, 25, 2, 116, 114, 105, 3, 57, 132, 0, 1, 100, 2, 108, 121, 0, 1, 104, 2, 109, 97, 110, 0, 1, 108, 97, 118, 0, 1, 108, 108, 2, 108, 0, 1, 108, 111, 118, 2, 109, 0, 1, 110, 97, 109, 0, 1, 110, 101, 109, 2, 32, 0, 1, 115, 2, 108, 101, 32, 0, 2, 17, 67, 17, 65, 0, 2, 17, 67, 101, 17, 67, 111, 32, 0, 2, 32, 0, 2, 97, 0, 2, 97, 108, 32, 0, 2, 101, 115, 113, 0, 2, 105, 0, 2, 108, 101, 32, 0, 2, 109, 101, 0, 2, 111, 0, 2, 116, 121, 0, 8, 2, 116, 105, 108, 0, 8, 108, 111, 115, 2, 17, 67, 0, 103, 1, 112, 109, 2, 110, 0, 103, 104, 1, 104, 0, 117, 1, 99, 97, 118, 0, 117, 2, 109, 3, 57, 132, 13, 0, 97, 114, 121, 2, 32, 3, 57, 132, 13, 34, 2, 120, 0, 99, 108, 101, 1, 110, 3, 57, 132, 49, 55, 120, 0, 99, 108, 101, 97, 114, 1, 110, 3, 57, 132, 49, 55, 140, 0, 115, 8, 2, 17, 65, 3, 57, 132, 86, 0, 115, 117, 114, 112, 3, 57, 132, 86, 6, 126, 48, 0, 115, 117, 114, 112, 5, 5, 3, 57, 132, 86, 6, 146, 48, 0, 115, 117, 2, 97, 108, 3, 57, 132, 88, 132, 0, 1, 103, 2, 105, 3, 58, 0, 97, 1, 103, 21, 2, 103, 101, 3, 58, 120, 0, 97, 8, 103, 3, 58, 124, 0, 4, 97, 1, 115, 2, 100, 101, 3, 58, 136, 0, 97, 1, 115, 2, 115, 0, 97, 103, 1, 115, 3, 58, 136, 73, 0, 4, 1, 98, 2, 100, 100, 104, 3, 115, 0, 1, 98, 2, 115, 104, 0, 1, 98, 2, 116, 99, 104, 0, 1, 99, 2, 115, 104, 0, 1, 112, 2, 115, 104, 0, 1, 112, 2, 115, 115, 0, 8, 102, 2, 108, 17, 67, 0, 4, 108, 1, 98, 2, 114, 3, 115, 55, 0, 108, 1, 98, 2, 119, 0, 108, 108, 1, 98, 0, 108, 108, 1, 102, 0, 108, 108, 1, 112, 0, 108, 108, 121, 1, 98, 3, 115, 55, 120, 0, 4, 108, 1, 99, 105, 10, 2, 116, 32, 3, 116, 0, 108, 1, 102, 10, 2, 32, 0, 1, 116, 116, 101, 108, 2, 99, 101, 3, 120, 0, 4, 115, 1, 98, 2, 105, 17, 65, 3, 120, 86, 0, 115, 1, 98, 2, 121, 0, 115, 105, 110, 101, 115, 115, 1, 98, 3, 120, 86, 50, 13, 87, 0, 4, 3, 123, 0, 1, 102, 2, 108, 99, 114, 0, 1, 108, 2, 99, 107, 0, 2, 103, 117, 17, 67, 0, 2, 108, 117, 108, 0, 2, 115, 104, 0, 2, 120, 17, 65, 12, 0, 99, 117, 108, 3, 123, 49, 57, 115, 55, 0, 108, 5, 8, 1, 102, 10, 2, 32, 3, 123, 55, 0, 108, 108, 121, 5, 8, 1, 102, 10, 2, 32, 3, 123, 55, 2, 120, 0, 103, 1, 108, 112, 2, 17, 65, 3, 123, 79, 0, 120, 117, 114, 1, 108, 3, 123, 79, 88, 132, 112, 0, 115, 8, 2, 32, 3, 123, 86, 0, 97, 114, 1, 103, 2, 100, 3, 125, 0, 4, 1, 18, 66, 2, 32, 3, 132, 0, 1, 104, 99, 2, 17, 67, 17, 65, 0, 1, 104, 114, 2, 17, 67, 17, 65, 0, 1, 106, 2, 17, 67, 17, 65, 0, 1, 106, 2, 108, 105, 0, 1, 106, 10, 2, 17, 67, 17, 65, 0, 1, 108, 2, 17, 67, 17, 65, 0, 1, 108, 2, 97, 0, 1, 108, 2, 98, 114, 105, 0, 1, 114, 2, 17, 67, 17, 65, 0, 1, 114, 2, 97, 17, 67, 12, 0, 1, 114, 2, 105, 0, 1, 114, 2, 116, 104, 0, 1, 115, 2, 17, 67, 17, 65, 0, 1, 115, 2, 105, 0, 1, 119, 2, 17, 67, 17, 65, 0, 1, 119, 2, 99, 104, 17, 65, 0, 2, 17, 67, 117, 32, 0, 2, 32, 24, 0, 2, 108, 121, 0, 5, 3, 1, 100, 2, 17, 67, 17, 65, 0, 5, 3, 1, 100, 2, 116, 121, 0, 5, 3, 1, 110, 2, 17, 67, 17, 65, 0, 5, 3, 1, 116, 2, 17, 67, 17, 65, 12, 0, 5, 3, 1, 116, 2, 105, 0, 8, 2, 108, 17, 65, 0, 8, 108, 2, 97, 0, 8, 108, 2, 99, 0, 104, 2, 17, 67, 0, 97, 114, 121, 1, 114, 2, 32, 3, 132, 34, 2, 120, 0, 99, 108, 101, 5, 3, 1, 110, 3, 132, 49, 55, 120, 0, 99, 108, 101, 97, 114, 5, 3, 1, 110, 3, 132, 49, 55, 140, 0, 103, 2, 101, 114, 32, 3, 132, 79, 0, 121, 3, 135, 0, 111, 121, 3, 137, 0, 111, 114, 1, 108, 102, 3, 141, 0, 7, 6, 118, 0, 2, 118, 3, 0, 4, 3, 82, 0, 8, 2, 108, 97, 0, 105, 98, 114, 97, 8, 2, 116, 3, 82, 2, 135, 69, 34, 136, 0, 105, 118, 105, 2, 21, 3, 82, 120, 82, 120, 0, 105, 118, 2, 32, 3, 82, 135, 82, 0, 97, 1, 21, 2, 108, 101, 110, 3, 82, 136, 0, 101, 104, 101, 109, 8, 3, 82, 139, 63, 0, 7, 6, 119, 0, 4, 1, 109, 2, 105, 99, 104, 32, 3, 0, 4, 1, 115, 17, 65, 2, 105, 99, 107, 3, 0, 2, 119, 3, 0, 101, 1, 17, 67, 2, 32, 3, 8, 58, 120, 0, 4, 114, 3, 34, 0, 114, 8, 2, 17, 71, 0, 4, 3, 58, 0, 104, 0, 104, 8, 2, 17, 71, 0, 4, 105, 116, 104, 2, 17, 65, 3, 58, 2, 120, 84, 0, 105, 116, 104, 2, 17, 67, 0, 101, 115, 116, 1, 17, 67, 3, 58, 6, 119, 87, 47, 0, 105, 116, 104, 1, 101, 2, 32, 3, 58, 6, 120, 84, 0, 101, 114, 101, 8, 2, 14, 128, 132, 132, 3, 58, 6, 138, 23, 0, 1, 17, 67, 2, 32, 3, 58, 13, 0, 111, 111, 100, 1, 10, 2, 32, 14, 128, 128, 132, 3, 58, 115, 70, 0, 105, 107, 105, 3, 58, 120, 49, 37, 0, 4, 105, 110, 103, 1, 17, 66, 2, 32, 3, 58, 120, 66, 0, 105, 110, 103, 1, 17, 66, 2, 115, 32, 0, 104, 105, 99, 104, 3, 58, 120, 74, 0, 105, 116, 104, 2, 101, 3, 58, 120, 84, 0, 104, 97, 116, 3, 58, 122, 47, 0, 4, 111, 114, 1, 115, 115, 2, 100, 3, 58, 126, 0, 111, 114, 2, 116, 104, 32, 0, 101, 2, 119, 3, 58, 127, 0, 105, 115, 101, 1, 21, 2, 32, 14, 128, 128, 132, 3, 58, 135, 86, 0, 97, 121, 1, 69, 2, 32, 14, 128, 128, 131, 3, 58, 136, 0, 104, 101, 114, 101, 3, 58, 138, 0, 4, 111, 114, 5, 5, 1, 115, 115, 2, 100, 3, 58, 146, 0, 111, 114, 5, 5, 2, 116, 104, 32, 0, 104, 2, 111, 108, 3, 105, 0, 4, 104, 111, 2, 32, 3, 105, 132, 0, 104, 111, 2, 100, 0, 104, 111, 2, 109, 0, 104, 111, 2, 115, 0, 104, 111, 39, 0, 1, 17, 67, 2, 29, 3, 115, 0, 111, 114, 1, 115, 2, 100, 3, 131, 0, 7, 6, 120, 0, 1, 120, 2, 17, 65, 3, 0, 105, 115, 2, 32, 3, 8, 49, 87, 120, 87, 0, 105, 111, 117, 115, 3, 8, 49, 89, 13, 87, 0, 117, 2, 97, 3, 8, 49, 89, 132, 0, 3, 49, 87, 0, 117, 114, 101, 2, 32, 3, 49, 89, 2, 141, 0, 105, 111, 2, 110, 3, 49, 89, 13, 0, 8, 2, 17, 71, 3, 86, 0, 121, 8, 3, 86, 135, 0, 7, 6, 121, 0, 1, 10, 2, 32, 24, 3, 2, 37, 0, 111, 117, 39, 3, 2, 57, 132, 0, 4, 1, 10, 2, 32, 3, 2, 120, 0, 1, 17, 67, 0, 1, 102, 17, 65, 11, 2, 32, 0, 1, 102, 17, 67, 2, 32, 0, 1, 104, 2, 112, 111, 99, 114, 0, 4, 2, 17, 67, 105, 99, 32, 3, 6, 120, 0, 2, 17, 67, 105, 99, 97, 108, 0, 2, 17, 67, 105, 102, 121, 0, 2, 110, 97, 32, 3, 6, 127, 0, 4, 1, 21, 2, 114, 97, 32, 3, 6, 135, 0, 2, 112, 97, 108, 0, 115, 105, 115, 1, 10, 2, 32, 3, 8, 13, 87, 120, 87, 0, 1, 107, 115, 10, 2, 32, 3, 8, 37, 0, 1, 17, 67, 10, 2, 108, 101, 110, 101, 32, 3, 8, 120, 0, 4, 1, 45, 2, 45, 3, 13, 0, 114, 2, 32, 0, 1, 17, 66, 11, 2, 32, 24, 14, 128, 144, 129, 3, 37, 0, 4, 3, 57, 0, 2, 97, 114, 0, 2, 101, 97, 114, 0, 2, 105, 17, 67, 32, 0, 97, 110, 103, 3, 57, 6, 35, 66, 0, 39, 8, 2, 17, 67, 14, 128, 132, 130, 3, 57, 13, 0, 101, 115, 8, 3, 57, 119, 87, 0, 101, 97, 104, 3, 57, 119, 105, 0, 117, 2, 21, 3, 57, 132, 0, 101, 111, 2, 17, 67, 3, 57, 134, 0, 8, 2, 32, 3, 58, 135, 0, 1, 17, 67, 2, 97, 98, 108, 3, 111, 0, 114, 105, 110, 103, 1, 115, 3, 111, 34, 120, 50, 73, 0, 4, 1, 17, 66, 11, 2, 32, 14, 128, 144, 129, 3, 120, 0, 1, 17, 66, 111, 29, 2, 21, 12, 0, 1, 17, 67, 2, 105, 0, 1, 17, 67, 17, 67, 2, 110, 32, 0, 1, 17, 67, 21, 2, 103, 101, 110, 0, 1, 17, 67, 21, 2, 109, 17, 65, 110, 32, 0, 1, 99, 2, 108, 105, 110, 0, 1, 99, 2, 110, 105, 0, 1, 99, 2, 114, 0, 1, 99, 105, 98, 2, 99, 108, 0, 1, 102, 102, 2, 32, 0, 1, 108, 2, 114, 105, 0, 1, 108, 103, 2, 99, 101, 114, 0, 1, 108, 103, 2, 112, 104, 0, 1, 112, 2, 114, 97, 0, 1, 112, 2, 114, 105, 0, 1, 116, 2, 112, 105, 99, 0, 1, 116, 2, 114, 97, 110, 110, 0, 1, 119, 2, 110, 0, 2, 17, 67, 0, 2, 17, 67, 17, 67, 0, 2, 17, 67, 32, 0, 2, 115, 116, 0, 5, 35, 1, 100, 2, 110, 97, 115, 0, 8, 2, 17, 67, 21, 0, 8, 115, 0, 101, 105, 103, 104, 116, 1, 116, 2, 32, 3, 120, 6, 136, 47, 0, 116, 119, 111, 1, 116, 2, 32, 3, 120, 47, 6, 132, 0, 112, 111, 99, 114, 105, 1, 104, 2, 116, 3, 120, 48, 13, 49, 34, 120, 0, 120, 1, 17, 67, 2, 32, 3, 120, 49, 87, 0, 110, 99, 104, 1, 115, 3, 120, 50, 49, 0, 111, 110, 101, 1, 116, 2, 32, 3, 120, 58, 6, 122, 50, 0, 111, 110, 101, 5, 6, 1, 116, 2, 32, 3, 120, 58, 6, 123, 50, 0, 102, 111, 117, 114, 1, 116, 2, 32, 3, 120, 81, 6, 131, 0, 102, 105, 118, 101, 1, 116, 2, 32, 3, 120, 81, 6, 135, 82, 0, 115, 1, 104, 112, 2, 105, 3, 120, 86, 0, 115, 101, 118, 101, 110, 1, 116, 2, 32, 3, 120, 87, 6, 119, 82, 13, 50, 0, 115, 101, 1, 100, 2, 110, 3, 120, 87, 13, 0, 4, 8, 2, 110, 21, 3, 123, 0, 8, 2, 115, 21, 0, 4, 1, 17, 67, 21, 2, 17, 66, 101, 13, 3, 135, 0, 1, 17, 67, 29, 0, 1, 98, 101, 114, 101, 2, 32, 0, 1, 98, 114, 97, 101, 2, 32, 0, 1, 99, 2, 99, 108, 0, 1, 99, 2, 99, 108, 105, 99, 32, 0, 1, 102, 2, 32, 0, 1, 102, 115, 2, 32, 0, 1, 104, 2, 17, 67, 114, 0, 1, 104, 116, 2, 108, 32, 0, 1, 107, 2, 108, 32, 0, 1, 108, 101, 98, 2, 32, 0, 1, 108, 102, 0, 1, 110, 2, 108, 32, 0, 1, 110, 101, 100, 2, 32, 0, 1, 112, 2, 116, 104, 0, 1, 116, 2, 108, 32, 0, 1, 116, 2, 112, 32, 0, 1, 116, 2, 112, 105, 115, 116, 0, 1, 116, 115, 2, 114, 101, 0, 2, 17, 66, 101, 13, 0, 2, 32, 0, 2, 101, 114, 32, 0, 2, 108, 117, 109, 0, 8, 17, 67, 0, 8, 17, 67, 2, 17, 67, 101, 0, 8, 17, 67, 2, 112, 104, 0, 8, 17, 67, 115, 0, 8, 98, 2, 12, 0, 101, 2, 32, 0, 116, 101, 2, 32, 3, 135, 47, 0, 112, 101, 1, 116, 3, 135, 48, 0, 110, 97, 109, 1, 100, 3, 135, 50, 35, 63, 0, 4, 101, 115, 1, 17, 67, 2, 32, 3, 135, 86, 0, 115, 101, 2, 32, 12, 0, 4, 115, 101, 100, 2, 32, 3, 135, 86, 70, 0, 122, 101, 100, 2, 32, 0, 115, 105, 110, 103, 2, 32, 3, 135, 86, 111, 66, 0, 114, 101, 2, 32, 3, 143, 0, 7, 6, 122, 0, 2, 122, 3, 0, 117, 2, 32, 3, 8, 86, 132, 0, 4, 3, 86, 0, 8, 2, 108, 111, 116, 0, 8, 2, 119, 17, 71, 0, 115, 8, 2, 17, 71, 0, 97, 108, 101, 115, 1, 21, 2, 32, 3, 86, 6, 124, 55, 13, 87, 0, 117, 101, 3, 86, 58, 6, 136, 0, 101, 115, 2, 32, 3, 86, 111, 86, 0, 111, 2, 111, 108, 111, 3, 86, 132, 0, 4, 104, 3, 88, 0, 104, 8, 2, 17, 71, 0, 117, 114, 101, 3, 88, 112, 0, 7, 6, 206, 0, 4, 172, 3, 6, 35, 55, 81, 13, 10, 0, 177, 0, 4, 173, 3, 6, 119, 48, 87, 120, 55, 122, 50, 10, 0, 181, 0, 4, 174, 3, 6, 127, 47, 13, 10, 0, 183, 0, 191, 3, 6, 134, 63, 120, 49, 34, 122, 50, 10, 0, 186, 3, 49, 6, 35, 48, 13, 10, 0, 190, 3, 49, 87, 6, 135, 10, 0, 189, 3, 50, 6, 57, 132, 10, 0, 187, 3, 55, 6, 35, 63, 70, 13, 10, 0, 188, 3, 63, 6, 57, 132, 10, 0, 178, 3, 69, 6, 127, 47, 13, 10, 0, 178, 5, 3, 3, 69, 6, 136, 47, 13, 10, 0, 180, 3, 70, 6, 119, 55, 47, 13, 10, 0, 179, 3, 79, 6, 35, 63, 13, 10, 0, 184, 3, 85, 6, 127, 47, 13, 10, 0, 182, 3, 86, 6, 127, 47, 13, 10, 0, 4, 175, 3, 135, 6, 134, 47, 13, 10, 0, 185, 0, 7, 6, 207, 0, 4, 133, 3, 6, 115, 48, 87, 120, 55, 122, 50, 10, 0, 141, 0, 140, 3, 6, 134, 63, 120, 49, 34, 122, 50, 10, 0, 4, 137, 3, 6, 134, 63, 120, 79, 13, 10, 0, 142, 0, 129, 3, 34, 6, 134, 10, 0, 132, 3, 47, 6, 133, 10, 0, 128, 3, 48, 6, 135, 10, 0, 136, 3, 48, 87, 6, 135, 10, 0, 135, 3, 74, 6, 135, 10, 0, 134, 3, 81, 6, 135, 10, 0, 4, 130, 3, 87, 6, 120, 79, 63, 13, 10, 0, 131, 0, 7, 6, 0, 4, 33, 2, 33, 3, 0, 4, 39, 3, 0, 4, 46, 1, 46, 3, 0, 58, 1, 32, 15, 2, 32, 15, 15, 32, 3, 0, 195, 169, 8, 3, 2, 120, 0, 46, 2, 46, 3, 9, 0, 33, 3, 9, 119, 49, 87, 49, 55, 13, 63, 136, 89, 13, 50, 9, 0, 45, 8, 2, 32, 15, 3, 10, 0, 195, 177, 3, 21, 101, 115, 0, 195, 160, 3, 35, 0, 58, 3, 49, 134, 55, 13, 50, 0, 33, 61, 3, 50, 122, 47, 127, 49, 58, 116, 86, 0, 60, 61, 3, 55, 119, 87, 130, 127, 49, 58, 116, 0, 45, 8, 32, 2, 32, 15, 3, 63, 135, 50, 13, 87, 0, 45, 1, 32, 15, 2, 32, 15, 3, 70, 35, 89, 0, 46, 3, 70, 122, 47, 0, 36, 3, 70, 122, 55, 112, 0, 196, 141, 3, 74, 0, 62, 61, 3, 79, 34, 136, 47, 13, 130, 127, 49, 58, 116, 0, 195, 176, 3, 84, 0, 195, 190, 3, 85, 0, 4, 195, 159, 3, 87, 0, 195, 167, 0, 197, 190, 3, 88, 0, 4, 197, 159, 3, 89, 0, 197, 161, 0, 4, 195, 164, 3, 119, 0, 195, 171, 0, 195, 170, 3, 119, 12, 0, 195, 182, 3, 126, 0, 4, 195, 169, 101, 3, 127, 0, 195, 175, 0, 195, 188, 3, 132, 0, 195, 169, 3, 136, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts14 = FileInMemory_createWithData (93422, reinterpret_cast (&espeakdata_dicts14_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/en_dict", L"en"); Collection_addItem (me.peek(), espeakdata_dicts14.transfer()); static unsigned char espeakdata_dicts15_data[4669] = { 0, 4, 0, 0, 9, 14, 0, 0, 0, 0, 0, 12, 67, 57, 35, 192, 50, 40, 63, 36, 51, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 8, 1, 3, 105, 35, 74, 6, 36, 49, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 44, 18, 128, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 21, 53, 9, 76, 76, 0, 0, 0, 10, 134, 1, 14, 20, 1, 197, 173, 76, 8, 0, 0, 0, 14, 1, 37, 48, 14, 16, 39, 112, 36, 50, 47, 39, 0, 27, 0, 7, 1, 38, 10, 49, 108, 0, 0, 0, 0, 0, 7, 195, 64, 244, 128, 76, 8, 14, 1, 42, 35, 87, 47, 36, 51, 37, 87, 49, 39, 0, 27, 0, 0, 0, 15, 66, 45, 0, 49, 4, 39, 63, 48, 6, 35, 34, 40, 0, 24, 0, 0, 11, 1, 47, 39, 69, 55, 37, 49, 82, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 11, 46, 1, 49, 108, 35, 55, 6, 37, 108, 0, 0, 0, 15, 3, 11, 46, 3, 49, 108, 112, 36, 47, 6, 36, 51, 36, 0, 0, 0, 0, 0, 10, 1, 61, 36, 79, 35, 55, 35, 0, 27, 0, 0, 7, 196, 21, 53, 21, 76, 76, 0, 8, 1, 64, 10, 74, 36, 10, 0, 0, 0, 7, 195, 44, 147, 192, 76, 8, 0, 0, 0, 0, 0, 0, 0, 16, 3, 11, 46, 19, 49, 108, 4, 87, 37, 6, 63, 37, 55, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 88, 82, 39, 0, 0, 0, 0, 0, 11, 1, 92, 70, 36, 49, 55, 37, 82, 39, 0, 0, 0, 0, 0, 8, 65, 96, 37, 49, 87, 39, 0, 12, 4, 95, 49, 77, 49, 63, 6, 37, 55, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 1, 124, 70, 40, 49, 47, 39, 87, 37, 79, 50, 39, 0, 0, 0, 9, 1, 126, 47, 37, 55, 70, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 12, 39, 55, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 16, 16, 76, 0, 15, 4, 1, 197, 173, 7, 35, 40, 79, 40, 87, 47, 39, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 64, 244, 212, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 66, 9, 96, 69, 39, 50, 4, 82, 39, 55, 40, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 48, 144, 64, 76, 0, 0, 0, 0, 6, 195, 8, 80, 64, 17, 0, 0, 0, 0, 0, 0, 6, 195, 48, 144, 74, 76, 0, 0, 0, 0, 0, 15, 66, 16, 80, 70, 36, 55, 35, 0, 72, 28, 81, 108, 97, 32, 6, 194, 16, 80, 76, 28, 0, 0, 0, 0, 0, 0, 13, 4, 95, 4, 16, 20, 10, 49, 39, 63, 39, 10, 0, 0, 0, 0, 0, 8, 3, 95, 35, 1, 2, 35, 0, 0, 0, 0, 0, 0, 0, 15, 66, 4, 192, 35, 55, 55, 35, 0, 72, 28, 81, 108, 97, 32, 6, 194, 4, 192, 76, 28, 0, 0, 11, 3, 95, 35, 57, 47, 6, 35, 69, 39, 0, 13, 4, 95, 20, 12, 4, 47, 6, 37, 55, 70, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 12, 144, 72, 0, 0, 0, 0, 0, 14, 67, 4, 228, 212, 35, 50, 87, 47, 35, 47, 106, 0, 24, 0, 0, 17, 3, 14, 46, 2, 50, 6, 39, 47, 40, 15, 69, 6, 39, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 80, 144, 77, 28, 0, 0, 0, 0, 17, 67, 24, 80, 128, 81, 4, 36, 69, 14, 16, 40, 6, 35, 51, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 32, 21, 137, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 36, 16, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 32, 21, 137, 76, 76, 0, 0, 0, 8, 133, 197, 157, 9, 1, 10, 76, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 56, 82, 192, 72, 8, 0, 7, 196, 52, 85, 15, 76, 76, 0, 0, 0, 0, 7, 196, 64, 245, 129, 76, 76, 0, 0, 0, 6, 195, 80, 147, 192, 76, 0, 0, 0, 0, 12, 67, 41, 83, 128, 37, 40, 50, 6, 37, 39, 0, 0, 0, 0, 15, 66, 20, 192, 36, 55, 55, 35, 0, 72, 8, 81, 108, 97, 32, 6, 194, 20, 192, 76, 8, 0, 0, 7, 196, 52, 85, 9, 76, 76, 0, 21, 5, 11, 46, 20, 46, 16, 49, 108, 47, 6, 37, 36, 55, 4, 48, 55, 4, 40, 10, 0, 0, 0, 11, 5, 95, 35, 45, 1, 14, 2, 35, 50, 0, 0, 0, 0, 7, 131, 196, 137, 5, 76, 8, 14, 4, 95, 13, 3, 14, 87, 47, 14, 16, 6, 37, 35, 0, 0, 8, 133, 196, 157, 9, 1, 10, 76, 10, 5, 95, 35, 45, 1, 10, 2, 108, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 16, 240, 8, 0, 0, 0, 0, 0, 0, 7, 196, 32, 21, 143, 76, 76, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 16, 46, 11, 48, 4, 39, 87, 47, 49, 14, 16, 6, 37, 87, 47, 39, 0, 24, 0, 0, 15, 66, 20, 224, 36, 50, 55, 35, 0, 72, 28, 81, 108, 97, 32, 6, 194, 20, 224, 76, 28, 0, 14, 3, 95, 51, 88, 47, 14, 16, 6, 37, 70, 36, 49, 0, 0, 10, 3, 95, 48, 67, 112, 36, 50, 47, 0, 0, 0, 0, 7, 195, 81, 32, 64, 72, 8, 0, 7, 196, 32, 21, 129, 76, 76, 20, 3, 16, 46, 19, 48, 4, 39, 87, 47, 35, 87, 49, 14, 16, 6, 37, 69, 39, 0, 0, 0, 0, 0, 11, 3, 95, 49, 67, 112, 6, 36, 50, 47, 0, 0, 0, 0, 0, 0, 0, 6, 194, 40, 80, 72, 28, 8, 66, 48, 16, 2, 55, 35, 0, 0, 7, 195, 65, 34, 64, 76, 8, 0, 0, 0, 6, 131, 196, 137, 9, 72, 0, 0, 0, 0, 6, 194, 41, 80, 72, 28, 7, 131, 196, 137, 21, 72, 28, 0, 12, 67, 41, 83, 0, 37, 40, 55, 6, 37, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 55, 88, 87, 6, 36, 48, 70, 36, 49, 0, 0, 7, 196, 52, 85, 1, 76, 76, 0, 0, 0, 0, 7, 196, 16, 85, 129, 76, 76, 0, 0, 0, 7, 132, 197, 157, 9, 1, 76, 0, 0, 0, 19, 67, 45, 68, 0, 49, 108, 47, 6, 37, 36, 55, 4, 48, 55, 4, 40, 10, 0, 0, 7, 195, 5, 5, 68, 76, 8, 0, 0, 0, 6, 194, 44, 80, 72, 8, 0, 10, 3, 95, 49, 88, 70, 6, 36, 49, 0, 0, 8, 196, 36, 229, 5, 72, 76, 8, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 88, 70, 6, 40, 70, 36, 49, 0, 0, 20, 3, 1, 46, 11, 4, 35, 50, 47, 106, 49, 14, 16, 6, 37, 87, 47, 39, 0, 24, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 144, 64, 76, 0, 0, 0, 0, 0, 13, 3, 95, 63, 63, 55, 37, 47, 4, 36, 51, 39, 0, 0, 0, 0, 14, 3, 95, 52, 88, 49, 82, 6, 35, 51, 70, 36, 49, 0, 0, 0, 6, 195, 52, 144, 74, 76, 0, 0, 0, 0, 0, 17, 66, 44, 112, 49, 6, 37, 55, 39, 79, 14, 16, 6, 35, 63, 110, 0, 0, 17, 67, 76, 84, 20, 87, 36, 48, 4, 47, 36, 63, 69, 14, 16, 39, 0, 14, 3, 95, 53, 88, 49, 82, 6, 37, 50, 70, 36, 49, 0, 0, 0, 0, 0, 0, 7, 196, 16, 85, 143, 76, 76, 0, 0, 0, 13, 3, 95, 54, 88, 87, 6, 36, 87, 70, 36, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 67, 5, 4, 128, 35, 48, 14, 16, 6, 37, 55, 39, 0, 0, 0, 0, 0, 14, 67, 77, 68, 128, 87, 47, 14, 16, 6, 35, 47, 39, 0, 0, 7, 196, 16, 85, 137, 76, 76, 0, 0, 0, 12, 3, 95, 56, 88, 6, 39, 49, 70, 36, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 57, 88, 50, 6, 106, 70, 36, 49, 0, 0, 0, 0, 6, 131, 196, 157, 9, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 52, 85, 21, 76, 76, 0, 0, 0, 15, 4, 95, 15, 7, 15, 87, 40, 69, 105, 6, 39, 49, 35, 0, 0, 7, 196, 16, 85, 149, 76, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 48, 144, 72, 5, 194, 56, 80, 76, 0, 0, 0, 0, 0, 11, 67, 52, 18, 128, 63, 6, 108, 39, 2, 0, 0, 0, 0, 0, 7, 195, 65, 35, 192, 76, 8, 0, 6, 195, 20, 35, 5, 72, 16, 4, 95, 48, 77, 52, 70, 40, 37, 55, 37, 6, 39, 50, 39, 0, 0, 0, 15, 4, 95, 48, 77, 50, 63, 37, 55, 37, 6, 39, 50, 39, 0, 0, 7, 195, 76, 83, 128, 76, 8, 16, 4, 95, 48, 77, 51, 63, 37, 55, 37, 6, 35, 34, 70, 39, 0, 0, 0, 12, 4, 95, 48, 77, 49, 63, 4, 37, 55, 10, 0, 0, 12, 4, 95, 2, 18, 22, 105, 6, 39, 49, 35, 0, 0, 0, 0, 0, 0, 13, 67, 52, 20, 128, 63, 6, 35, 14, 16, 47, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 52, 144, 72, 17, 66, 44, 208, 49, 6, 37, 55, 39, 63, 6, 36, 47, 20, 16, 110, 0, 0, 0, 0, 0, 0, 0, 6, 131, 197, 157, 9, 72, 0, 0, 19, 66, 65, 48, 48, 4, 39, 87, 47, 35, 87, 49, 14, 16, 6, 37, 69, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 77, 80, 128, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 56, 144, 72, 0, 0, 0, 0, 0, 6, 195, 60, 226, 64, 72, 10, 67, 64, 194, 64, 48, 55, 4, 37, 0, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 3, 9, 18, 112, 37, 51, 49, 40, 63, 81, 55, 6, 36, 49, 87, 35, 0, 0, 7, 195, 45, 83, 128, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 77, 84, 128, 76, 8, 0, 0, 0, 0, 14, 4, 95, 19, 20, 11, 87, 47, 14, 16, 36, 49, 35, 0, 0, 0, 21, 4, 95, 1, 3, 21, 70, 36, 49, 87, 47, 14, 16, 35, 49, 6, 39, 51, 50, 35, 0, 0, 21, 3, 95, 194, 171, 70, 40, 6, 39, 69, 55, 35, 49, 14, 16, 6, 35, 63, 48, 39, 0, 0, 0, 0, 0, 0, 0, 15, 3, 20, 46, 5, 47, 37, 39, 4, 36, 87, 47, 35, 87, 0, 0, 10, 67, 64, 193, 74, 48, 55, 4, 109, 0, 0, 0, 13, 4, 95, 18, 14, 7, 51, 6, 37, 50, 79, 35, 0, 0, 0, 19, 3, 20, 46, 14, 47, 6, 37, 36, 55, 4, 50, 39, 63, 6, 35, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 4, 95, 1, 3, 50, 70, 40, 39, 69, 55, 35, 49, 6, 39, 51, 50, 35, 0, 0, 0, 6, 195, 20, 177, 5, 8, 0, 0, 6, 195, 37, 32, 83, 76, 0, 0, 0, 0, 0, 15, 67, 60, 181, 0, 39, 49, 4, 47, 39, 69, 14, 16, 39, 0, 0, 0, 0, 0, 0, 0, 0, 27, 3, 95, 194, 187, 81, 6, 36, 51, 63, 35, 70, 40, 4, 39, 69, 55, 35, 49, 14, 16, 6, 35, 63, 48, 39, 0, 0, 0, 0, 0, 6, 195, 37, 34, 83, 76, 6, 194, 60, 192, 76, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 76, 80, 72, 8, 0, 7, 195, 76, 81, 0, 72, 8, 0, 0, 0, 0, 0, 0, 0, 6, 195, 37, 37, 83, 76, 0, 11, 5, 95, 35, 1, 10, 14, 2, 108, 50, 0, 0, 0, 0, 0, 13, 2, 194, 169, 49, 39, 48, 37, 51, 108, 47, 39, 0, 0, 0, 0, 0, 6, 195, 88, 144, 64, 76, 6, 195, 56, 144, 64, 76, 0, 7, 196, 36, 194, 65, 40, 76, 0, 0, 10, 2, 194, 176, 79, 34, 35, 70, 110, 0, 0, 0, 0, 6, 195, 56, 144, 74, 76, 0, 0, 0, 14, 4, 95, 3, 5, 4, 112, 36, 70, 6, 37, 55, 35, 0, 0, 0, 0, 16, 4, 95, 12, 9, 7, 55, 37, 79, 35, 47, 6, 40, 51, 35, 0, 0, 11, 3, 16, 196, 157, 48, 35, 73, 39, 0, 24, 0, 0, 10, 4, 95, 35, 1, 14, 2, 35, 50, 0, 0, 0, 0, 0, 9, 4, 95, 35, 1, 10, 2, 108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 144, 72, 0, 0, 0, 0, 0, 0, 7, 196, 64, 245, 149, 76, 76, 6, 195, 21, 53, 9, 76, 0, 6, 195, 88, 144, 74, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 132, 12, 1, 197, 173, 76, 28, 0, 0, 0, 0, 0, 7, 196, 80, 19, 69, 56, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 131, 1, 197, 173, 72, 8, 0, 0, 0, 0, 0, 0, 7, 196, 64, 245, 137, 76, 76, 9, 2, 95, 34, 112, 37, 47, 39, 0, 0, 16, 2, 95, 33, 10, 49, 14, 16, 37, 87, 37, 79, 50, 39, 10, 0, 0, 0, 15, 67, 40, 19, 128, 37, 4, 35, 50, 40, 6, 35, 51, 39, 0, 16, 2, 95, 39, 35, 48, 39, 87, 47, 14, 16, 6, 39, 81, 39, 0, 0, 0, 0, 0, 7, 195, 17, 83, 64, 72, 8, 0, 15, 4, 95, 3, 1, 16, 63, 108, 4, 40, 87, 49, 55, 35, 0, 0, 21, 2, 95, 41, 81, 6, 36, 51, 63, 35, 48, 35, 34, 36, 50, 47, 6, 36, 86, 39, 0, 0, 21, 67, 24, 20, 133, 81, 35, 14, 16, 36, 2, 70, 6, 36, 0, 76, 28, 81, 100, 101, 32, 14, 2, 95, 40, 48, 35, 34, 36, 50, 47, 36, 86, 39, 0, 0, 7, 195, 64, 84, 128, 76, 28, 0, 11, 2, 95, 46, 48, 40, 50, 49, 47, 39, 0, 0, 18, 2, 95, 45, 70, 37, 82, 37, 70, 39, 87, 47, 14, 16, 36, 49, 39, 0, 0, 21, 67, 64, 84, 133, 48, 36, 14, 16, 36, 2, 70, 6, 36, 0, 76, 28, 81, 100, 101, 32, 9, 2, 95, 44, 49, 39, 63, 39, 0, 0, 10, 2, 95, 51, 47, 14, 34, 6, 37, 0, 0, 6, 195, 37, 35, 211, 76, 8, 2, 95, 50, 70, 6, 40, 0, 0, 9, 2, 95, 49, 6, 40, 50, 40, 0, 0, 8, 2, 95, 48, 50, 40, 55, 0, 0, 9, 2, 95, 55, 87, 6, 36, 48, 0, 0, 9, 2, 95, 54, 87, 6, 36, 87, 0, 0, 10, 2, 95, 53, 49, 82, 6, 37, 50, 0, 0, 10, 2, 95, 52, 49, 82, 6, 35, 51, 0, 0, 15, 2, 95, 59, 48, 40, 50, 49, 47, 39, 49, 39, 63, 39, 0, 0, 13, 2, 95, 58, 70, 40, 48, 40, 50, 49, 47, 39, 0, 0, 8, 2, 95, 57, 50, 6, 106, 0, 0, 8, 2, 95, 56, 6, 39, 49, 0, 0, 18, 67, 20, 182, 128, 36, 49, 86, 36, 63, 48, 55, 36, 0, 44, 81, 101, 32, 15, 67, 20, 182, 128, 36, 49, 86, 36, 63, 48, 55, 36, 0, 24, 17, 2, 95, 63, 70, 36, 63, 35, 50, 70, 39, 87, 37, 79, 50, 39, 0, 0, 24, 2, 95, 62, 81, 6, 36, 51, 63, 35, 35, 50, 79, 40, 55, 49, 14, 16, 6, 35, 63, 48, 39, 0, 0, 0, 18, 2, 95, 60, 35, 50, 79, 40, 55, 49, 14, 16, 6, 35, 63, 48, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 67, 16, 80, 192, 70, 36, 112, 36, 63, 69, 14, 16, 39, 0, 0, 7, 196, 64, 245, 143, 76, 76, 0, 0, 0, 0, 14, 4, 95, 4, 15, 20, 48, 6, 40, 50, 49, 47, 35, 0, 0, 0, 0, 19, 2, 95, 91, 51, 6, 36, 49, 47, 35, 49, 14, 16, 6, 35, 63, 48, 39, 0, 0, 12, 6, 95, 35, 45, 1, 10, 14, 2, 108, 50, 0, 0, 0, 8, 66, 88, 144, 82, 37, 0, 72, 5, 194, 84, 176, 17, 0, 15, 2, 95, 95, 87, 40, 69, 87, 47, 14, 16, 36, 49, 39, 0, 0, 0, 24, 2, 95, 93, 81, 6, 36, 51, 63, 35, 51, 36, 49, 47, 35, 49, 14, 16, 6, 35, 63, 48, 39, 0, 0, 6, 195, 36, 194, 65, 76, 0, 6, 195, 36, 194, 64, 72, 13, 67, 4, 178, 192, 35, 55, 37, 50, 39, 63, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 24, 4, 95, 7, 18, 22, 63, 35, 55, 70, 36, 49, 87, 47, 14, 16, 35, 49, 6, 39, 51, 50, 35, 0, 0, 0, 0, 0, 0, 7, 195, 16, 84, 192, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 19, 2, 95, 123, 49, 6, 40, 51, 69, 35, 49, 14, 16, 6, 35, 63, 48, 39, 0, 15, 4, 95, 4, 9, 1, 70, 40, 48, 40, 50, 49, 47, 35, 0, 0, 0, 0, 0, 0, 0, 24, 2, 95, 125, 81, 6, 36, 51, 63, 35, 49, 40, 51, 69, 35, 49, 14, 16, 6, 35, 63, 48, 39, 0, 0, 0, 0, 0, 0, 8, 132, 196, 137, 1, 18, 72, 8, 0, 0, 0, 0, 0, 0, 7, 196, 44, 149, 74, 56, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 35, 51, 50, 87, 48, 6, 35, 112, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 196, 157, 9, 1, 76, 9, 4, 95, 35, 45, 1, 2, 35, 0, 0, 0, 9, 197, 65, 33, 84, 21, 32, 76, 28, 0, 10, 3, 9, 46, 1, 6, 37, 6, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 132, 196, 157, 9, 19, 76, 8, 0, 0, 0, 0, 0, 0, 7, 195, 44, 145, 76, 76, 8, 0, 7, 196, 21, 53, 15, 76, 76, 0, 0, 0, 7, 195, 44, 144, 64, 76, 8, 6, 195, 76, 144, 64, 76, 6, 195, 12, 144, 64, 76, 6, 195, 84, 80, 64, 17, 0, 0, 0, 0, 0, 0, 6, 195, 76, 144, 74, 76, 6, 195, 12, 144, 74, 76, 0, 0, 7, 195, 44, 145, 64, 76, 8, 0, 0, 0, 0, 0, 7, 196, 21, 53, 1, 76, 76, 0, 0, 0, 0, 0, 0, 7, 195, 44, 144, 77, 76, 8, 0, 0, 0, 0, 0, 0, 0, 6, 195, 44, 149, 78, 8, 0, 0, 0, 0, 7, 195, 44, 149, 74, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 5, 196, 137, 28, 0, 7, 195, 44, 149, 64, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 99, 0, 120, 0, 9, 1, 0, 0, 103, 0, 120, 0, 29, 1, 0, 0, 104, 0, 120, 0, 37, 1, 0, 0, 106, 0, 120, 0, 53, 1, 0, 0, 115, 0, 120, 0, 93, 1, 0, 0, 117, 0, 120, 0, 109, 1, 0, 0, 0, 0, 0, 0, 6, 97, 0, 4, 3, 35, 0, 8, 2, 32, 0, 197, 173, 3, 106, 0, 106, 3, 108, 0, 7, 6, 98, 0, 3, 69, 0, 8, 2, 32, 3, 69, 39, 0, 7, 6, 99, 0, 4, 104, 1, 25, 3, 74, 0, 104, 2, 25, 0, 104, 8, 2, 32, 3, 74, 39, 0, 3, 112, 0, 8, 2, 32, 3, 112, 39, 0, 7, 6, 100, 0, 3, 70, 0, 8, 2, 45, 114, 105, 110, 111, 3, 70, 4, 39, 49, 47, 39, 0, 8, 2, 32, 3, 70, 39, 0, 8, 2, 45, 114, 111, 3, 70, 39, 49, 47, 6, 39, 0, 7, 6, 101, 0, 4, 3, 36, 0, 8, 2, 32, 0, 197, 173, 3, 107, 0, 106, 3, 109, 0, 7, 6, 102, 0, 3, 81, 0, 8, 2, 32, 3, 81, 39, 0, 8, 2, 45, 105, 110, 111, 3, 81, 51, 2, 106, 55, 0, 8, 2, 45, 108, 111, 3, 81, 51, 106, 0, 7, 6, 103, 0, 104, 2, 25, 3, 73, 0, 3, 79, 0, 8, 2, 32, 3, 79, 39, 0, 7, 6, 104, 0, 104, 3, 99, 0, 3, 105, 0, 8, 2, 32, 3, 105, 39, 0, 7, 6, 105, 0, 4, 3, 37, 0, 8, 2, 32, 0, 7, 6, 106, 0, 3, 57, 0, 8, 2, 32, 3, 57, 39, 0, 104, 2, 17, 67, 3, 88, 0, 7, 6, 107, 0, 3, 49, 0, 8, 2, 45, 100, 105, 110, 111, 3, 49, 6, 35, 63, 35, 51, 35, 0, 8, 2, 45, 105, 110, 111, 3, 49, 6, 35, 63, 35, 51, 35, 70, 0, 8, 2, 45, 100, 111, 3, 49, 35, 63, 35, 51, 6, 35, 0, 8, 2, 32, 3, 49, 39, 0, 7, 6, 108, 0, 4, 3, 55, 0, 108, 2, 32, 0, 8, 2, 32, 3, 55, 39, 0, 7, 6, 109, 0, 3, 63, 0, 8, 2, 32, 3, 63, 39, 0, 7, 6, 110, 0, 4, 3, 50, 0, 2, 32, 14, 128, 128, 129, 0, 8, 2, 32, 3, 50, 39, 0, 8, 2, 45, 114, 111, 3, 50, 40, 63, 6, 36, 0, 7, 6, 111, 0, 4, 1, 29, 45, 2, 32, 3, 2, 39, 0, 1, 45, 2, 32, 0, 4, 110, 1, 29, 45, 2, 32, 3, 2, 39, 50, 0, 110, 1, 45, 2, 32, 0, 4, 106, 1, 29, 45, 2, 32, 3, 2, 110, 0, 106, 1, 45, 2, 32, 0, 4, 3, 39, 0, 8, 2, 32, 0, 106, 3, 110, 0, 7, 6, 112, 0, 3, 48, 0, 8, 2, 32, 3, 48, 39, 0, 4, 104, 1, 25, 3, 81, 0, 104, 2, 25, 0, 7, 6, 113, 0, 3, 49, 0, 8, 2, 32, 3, 49, 58, 39, 0, 117, 3, 49, 82, 0, 7, 6, 114, 0, 1, 25, 2, 17, 65, 3, 14, 16, 0, 4, 3, 51, 0, 1, 17, 65, 2, 17, 65, 0, 8, 2, 32, 3, 51, 39, 0, 114, 3, 51, 51, 0, 7, 6, 115, 0, 3, 87, 0, 8, 2, 45, 105, 110, 111, 3, 87, 4, 37, 50, 57, 39, 51, 0, 8, 2, 45, 116, 97, 32, 3, 87, 6, 35, 50, 49, 0, 4, 8, 2, 45, 97, 110, 105, 110, 111, 3, 87, 6, 35, 63, 4, 37, 70, 36, 0, 8, 2, 45, 97, 110, 111, 0, 8, 2, 45, 114, 111, 3, 87, 37, 50, 57, 6, 39, 0, 8, 2, 32, 3, 87, 39, 0, 4, 104, 1, 25, 3, 89, 0, 104, 2, 25, 0, 104, 8, 2, 32, 3, 89, 39, 0, 7, 6, 116, 0, 3, 47, 0, 97, 1, 45, 2, 32, 3, 47, 2, 35, 0, 8, 2, 32, 3, 47, 39, 0, 4, 104, 1, 25, 3, 85, 0, 104, 2, 25, 0, 7, 6, 117, 0, 4, 3, 40, 0, 8, 2, 32, 0, 106, 3, 111, 0, 7, 6, 118, 0, 3, 82, 0, 8, 2, 32, 3, 82, 39, 0, 7, 6, 119, 0, 4, 3, 58, 0, 104, 1, 25, 0, 8, 2, 32, 3, 70, 40, 6, 39, 69, 55, 35, 82, 4, 39, 0, 7, 6, 120, 0, 8, 2, 32, 3, 37, 49, 87, 39, 0, 3, 49, 87, 0, 8, 3, 86, 0, 7, 6, 121, 0, 1, 25, 2, 25, 3, 37, 0, 8, 2, 32, 3, 37, 48, 87, 37, 55, 39, 50, 39, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 8, 2, 32, 3, 86, 39, 0, 7, 6, 0, 4, 39, 3, 0, 4, 45, 1, 45, 45, 3, 0, 4, 45, 2, 32, 97, 3, 0, 46, 1, 46, 3, 0, 46, 2, 46, 3, 9, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 194, 163, 2, 32, 15, 3, 10, 48, 40, 50, 70, 110, 9, 0, 36, 2, 32, 15, 3, 10, 70, 39, 55, 35, 51, 110, 9, 0, 46, 3, 48, 40, 50, 49, 47, 39, 0, 194, 163, 3, 48, 40, 50, 70, 39, 0, 43, 3, 48, 55, 40, 87, 10, 0, 43, 43, 8, 2, 32, 3, 48, 55, 40, 87, 48, 55, 40, 87, 0, 197, 173, 3, 58, 0, 197, 173, 8, 2, 32, 3, 58, 39, 0, 4, 45, 3, 63, 37, 50, 40, 87, 10, 0, 45, 8, 32, 2, 32, 15, 0, 36, 3, 70, 39, 55, 35, 51, 39, 0, 196, 157, 3, 73, 0, 196, 157, 8, 2, 32, 3, 73, 39, 0, 196, 137, 3, 74, 0, 196, 137, 8, 2, 32, 3, 74, 39, 0, 45, 1, 32, 15, 2, 32, 15, 3, 87, 47, 14, 16, 36, 49, 6, 36, 47, 39, 10, 0, 196, 181, 3, 88, 0, 196, 181, 8, 2, 32, 3, 88, 39, 0, 197, 157, 3, 89, 0, 197, 157, 8, 2, 32, 3, 89, 39, 0, 196, 165, 3, 99, 0, 196, 165, 8, 2, 32, 3, 99, 39, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts15 = FileInMemory_createWithData (4668, reinterpret_cast (&espeakdata_dicts15_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/eo_dict", L"eo"); Collection_addItem (me.peek(), espeakdata_dicts15.transfer()); static unsigned char espeakdata_dicts16_data[6438] = { 0, 4, 0, 0, 148, 20, 0, 0, 0, 0, 0, 0, 0, 6, 65, 4, 35, 0, 14, 5, 193, 4, 72, 28, 0, 0, 0, 0, 6, 65, 8, 69, 36, 0, 0, 0, 0, 0, 6, 65, 12, 85, 36, 0, 0, 0, 7, 195, 69, 81, 64, 72, 8, 13, 4, 95, 8, 1, 3, 49, 35, 34, 6, 108, 50, 0, 0, 0, 6, 65, 16, 70, 36, 0, 0, 0, 10, 199, 21, 53, 1, 72, 83, 79, 76, 72, 9, 134, 19, 5, 18, 195, 173, 1, 72, 0, 0, 0, 5, 194, 100, 240, 76, 0, 16, 4, 95, 48, 67, 15, 85, 107, 50, 47, 6, 107, 87, 37, 63, 0, 0, 9, 134, 19, 5, 18, 195, 161, 14, 72, 0, 8, 65, 24, 23, 107, 81, 36, 0, 0, 0, 0, 0, 6, 65, 28, 99, 36, 0, 0, 0, 16, 4, 95, 51, 88, 15, 47, 34, 37, 99, 6, 107, 87, 37, 63, 0, 0, 0, 7, 65, 32, 35, 74, 36, 0, 0, 10, 135, 20, 5, 14, 195, 169, 9, 19, 72, 9, 198, 89, 81, 83, 81, 35, 192, 76, 9, 198, 57, 81, 83, 81, 35, 192, 76, 0, 0, 15, 1, 35, 35, 55, 63, 108, 35, 84, 6, 37, 96, 35, 0, 27, 0, 9, 134, 19, 5, 18, 195, 161, 19, 72, 0, 10, 135, 8, 1, 2, 195, 169, 9, 19, 72, 15, 1, 37, 48, 108, 34, 85, 57, 6, 107, 50, 47, 39, 0, 27, 0, 14, 1, 38, 35, 63, 48, 107, 34, 87, 6, 35, 50, 47, 0, 0, 0, 8, 65, 40, 99, 108, 47, 35, 0, 0, 0, 7, 195, 64, 244, 128, 72, 8, 15, 1, 42, 35, 87, 47, 107, 34, 6, 37, 87, 49, 39, 0, 27, 0, 9, 1, 43, 63, 6, 35, 87, 0, 27, 0, 6, 65, 44, 49, 35, 0, 0, 0, 10, 1, 46, 48, 40, 50, 47, 39, 0, 27, 0, 9, 1, 47, 69, 35, 51, 52, 35, 0, 0, 8, 65, 48, 23, 107, 55, 36, 0, 0, 0, 0, 12, 137, 8, 1, 2, 195, 173, 1, 13, 15, 19, 72, 0, 8, 65, 52, 23, 107, 63, 36, 0, 9, 198, 89, 81, 83, 81, 35, 211, 76, 9, 198, 57, 81, 83, 81, 35, 211, 76, 0, 10, 135, 195, 169, 18, 1, 13, 15, 19, 72, 0, 0, 0, 8, 65, 56, 23, 107, 50, 36, 0, 9, 5, 95, 48, 1, 14, 4, 37, 0, 0, 0, 0, 0, 6, 65, 60, 39, 0, 14, 5, 193, 60, 72, 8, 0, 11, 1, 61, 37, 98, 58, 6, 35, 55, 0, 27, 0, 0, 0, 6, 65, 64, 48, 36, 0, 11, 1, 64, 35, 51, 52, 6, 39, 80, 35, 0, 0, 10, 135, 3, 21, 195, 161, 12, 5, 19, 8, 0, 0, 0, 6, 65, 68, 49, 40, 0, 0, 10, 135, 8, 1, 3, 195, 169, 9, 19, 76, 0, 6, 195, 84, 224, 64, 72, 0, 0, 8, 65, 72, 23, 107, 34, 36, 0, 0, 0, 12, 137, 5, 19, 20, 1, 18, 195, 173, 1, 14, 72, 0, 0, 8, 65, 76, 23, 107, 87, 36, 0, 0, 11, 70, 77, 0, 78, 37, 50, 0, 21, 0, 10, 0, 0, 0, 6, 65, 80, 47, 36, 0, 0, 0, 0, 0, 9, 198, 56, 244, 207, 81, 35, 211, 76, 0, 0, 16, 4, 95, 49, 67, 15, 85, 107, 50, 47, 6, 107, 87, 37, 63, 0, 0, 0, 8, 65, 88, 23, 40, 80, 36, 0, 0, 5, 194, 5, 48, 76, 0, 0, 18, 4, 95, 49, 77, 52, 6, 40, 50, 69, 37, 57, 12, 6, 108, 50, 0, 102, 16, 4, 95, 49, 77, 52, 6, 40, 50, 69, 37, 96, 6, 108, 50, 0, 0, 15, 65, 92, 4, 40, 80, 36, 15, 70, 6, 108, 80, 55, 36, 0, 0, 9, 198, 32, 16, 197, 52, 244, 192, 76, 0, 16, 1, 94, 85, 37, 34, 49, 40, 63, 81, 55, 6, 36, 99, 39, 0, 0, 0, 9, 65, 96, 23, 107, 49, 37, 87, 0, 0, 18, 4, 95, 49, 77, 50, 6, 40, 50, 63, 37, 57, 12, 6, 108, 50, 0, 102, 16, 4, 95, 49, 77, 50, 6, 40, 50, 63, 37, 96, 6, 108, 50, 0, 0, 0, 7, 196, 32, 16, 133, 72, 72, 0, 14, 65, 100, 4, 37, 79, 34, 6, 37, 107, 98, 35, 0, 14, 7, 65, 100, 2, 37, 0, 8, 0, 0, 6, 195, 48, 244, 192, 72, 0, 12, 137, 5, 19, 20, 1, 18, 195, 173, 1, 19, 72, 0, 8, 65, 104, 85, 107, 47, 35, 0, 0, 9, 198, 5, 21, 69, 48, 192, 64, 76, 0, 0, 0, 0, 0, 0, 18, 67, 77, 37, 1, 115, 101, 195, 177, 111, 114, 105, 116, 97, 0, 41, 24, 29, 0, 0, 0, 0, 0, 0, 19, 67, 17, 5, 15, 100, 101, 112, 97, 114, 116, 97, 109, 101, 110, 116, 111, 0, 29, 0, 0, 0, 0, 6, 195, 84, 224, 83, 72, 0, 0, 0, 10, 135, 19, 5, 18, 195, 173, 1, 14, 72, 0, 9, 198, 33, 80, 137, 52, 244, 192, 72, 0, 0, 0, 0, 10, 135, 19, 5, 18, 195, 173, 1, 19, 72, 0, 0, 0, 0, 0, 16, 67, 77, 32, 64, 115, 101, 195, 177, 111, 114, 97, 0, 41, 24, 29, 19, 4, 95, 49, 57, 15, 84, 36, 85, 37, 63, 39, 50, 39, 80, 6, 36, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 49, 67, 48, 85, 6, 37, 36, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 32, 16, 146, 20, 211, 211, 72, 0, 0, 0, 0, 9, 198, 88, 244, 207, 81, 32, 83, 76, 9, 198, 5, 21, 69, 48, 192, 83, 76, 0, 0, 18, 4, 95, 49, 56, 15, 84, 36, 85, 37, 63, 108, 49, 47, 6, 35, 80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 66, 17, 32, 100, 111, 99, 116, 111, 114, 0, 41, 24, 29, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 139, 5, 19, 20, 1, 18, 195, 173, 1, 13, 15, 19, 72, 0, 0, 0, 0, 17, 67, 77, 32, 83, 115, 101, 195, 177, 111, 114, 97, 115, 0, 41, 24, 29, 0, 0, 0, 0, 0, 0, 0, 0, 17, 67, 77, 33, 83, 115, 101, 195, 177, 111, 114, 101, 115, 0, 41, 24, 29, 0, 0, 0, 0, 0, 10, 199, 33, 80, 137, 77, 65, 73, 76, 72, 15, 4, 95, 49, 49, 15, 40, 50, 70, 6, 107, 85, 37, 63, 0, 0, 0, 0, 0, 0, 7, 196, 48, 147, 149, 96, 65, 0, 9, 198, 25, 82, 83, 80, 82, 83, 72, 0, 0, 0, 0, 0, 14, 66, 16, 80, 70, 4, 36, 55, 35, 0, 81, 108, 97, 32, 5, 194, 16, 80, 72, 6, 195, 84, 227, 211, 72, 0, 0, 7, 196, 21, 32, 73, 76, 72, 0, 8, 197, 4, 193, 213, 56, 16, 72, 6, 195, 16, 83, 0, 72, 0, 0, 20, 4, 95, 49, 51, 15, 84, 36, 85, 37, 63, 39, 47, 107, 34, 85, 6, 107, 34, 0, 0, 11, 4, 95, 4, 16, 20, 49, 39, 63, 35, 0, 0, 8, 197, 21, 53, 1, 8, 16, 72, 8, 197, 21, 53, 1, 8, 16, 72, 0, 5, 194, 21, 48, 72, 0, 0, 0, 0, 0, 13, 4, 95, 49, 48, 15, 84, 6, 107, 85, 37, 63, 0, 0, 0, 8, 197, 25, 82, 77, 61, 48, 72, 0, 7, 66, 12, 128, 74, 36, 0, 6, 194, 4, 192, 72, 28, 0, 0, 13, 4, 95, 20, 12, 4, 47, 6, 37, 55, 70, 36, 0, 0, 0, 0, 18, 4, 95, 49, 53, 15, 84, 36, 85, 37, 63, 39, 49, 6, 37, 50, 47, 0, 0, 7, 196, 80, 83, 135, 60, 72, 0, 0, 0, 0, 9, 198, 33, 80, 137, 21, 35, 206, 72, 0, 0, 0, 16, 4, 95, 49, 50, 15, 84, 58, 39, 84, 6, 107, 85, 37, 63, 0, 0, 21, 68, 21, 128, 205, 4, 101, 120, 99, 101, 108, 101, 110, 116, 115, 105, 109, 97, 0, 24, 29, 0, 0, 27, 66, 20, 80, 107, 87, 47, 6, 35, 84, 39, 87, 15, 40, 50, 6, 37, 84, 39, 87, 0, 82, 46, 32, 117, 117, 32, 0, 6, 195, 32, 22, 64, 72, 0, 0, 9, 198, 5, 21, 69, 48, 195, 211, 76, 0, 0, 20, 4, 95, 49, 55, 15, 84, 36, 85, 37, 63, 39, 87, 6, 107, 48, 47, 37, 63, 0, 0, 7, 196, 20, 195, 15, 76, 76, 0, 0, 0, 0, 0, 0, 0, 19, 4, 95, 49, 52, 15, 84, 36, 85, 37, 63, 39, 49, 58, 6, 35, 34, 47, 0, 0, 0, 0, 0, 0, 0, 18, 68, 37, 164, 68, 4, 105, 122, 113, 117, 105, 101, 114, 100, 97, 0, 24, 29, 7, 196, 80, 83, 133, 72, 72, 0, 0, 0, 0, 7, 196, 20, 195, 1, 76, 76, 0, 0, 0, 6, 195, 25, 81, 64, 72, 0, 0, 19, 4, 95, 49, 54, 15, 84, 36, 85, 37, 63, 39, 87, 6, 107, 49, 87, 47, 0, 0, 0, 0, 0, 0, 5, 194, 32, 16, 72, 0, 6, 195, 25, 82, 64, 72, 0, 0, 0, 0, 0, 0, 0, 16, 5, 95, 48, 77, 49, 15, 63, 37, 55, 6, 107, 87, 37, 63, 0, 0, 6, 195, 32, 19, 128, 72, 0, 0, 19, 4, 95, 55, 88, 15, 87, 107, 48, 47, 58, 35, 99, 6, 107, 87, 37, 63, 0, 0, 0, 0, 0, 11, 136, 8, 1, 2, 18, 195, 169, 9, 19, 72, 0, 7, 195, 64, 20, 129, 72, 8, 0, 0, 0, 0, 12, 137, 5, 19, 20, 1, 18, 195, 169, 9, 19, 72, 0, 0, 21, 68, 21, 128, 205, 60, 101, 120, 99, 101, 108, 101, 110, 116, 115, 105, 109, 111, 0, 24, 29, 11, 200, 21, 53, 21, 88, 145, 82, 60, 224, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 88, 244, 207, 81, 35, 211, 76, 0, 0, 0, 0, 0, 0, 0, 10, 135, 5, 19, 20, 1, 18, 195, 169, 72, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 5, 19, 20, 1, 18, 195, 161, 72, 0, 0, 0, 0, 6, 195, 32, 16, 197, 76, 0, 0, 6, 195, 32, 17, 207, 76, 13, 3, 95, 49, 15, 48, 34, 37, 63, 6, 107, 34, 0, 0, 10, 135, 8, 1, 2, 195, 173, 1, 14, 72, 0, 0, 9, 3, 226, 130, 172, 113, 34, 39, 0, 0, 0, 0, 0, 0, 13, 3, 95, 50, 15, 87, 36, 98, 6, 40, 50, 70, 0, 0, 0, 5, 194, 32, 80, 72, 0, 0, 0, 8, 197, 64, 244, 145, 84, 80, 8, 0, 0, 0, 13, 3, 95, 51, 15, 47, 107, 34, 85, 6, 107, 34, 0, 8, 4, 95, 15, 18, 4, 39, 0, 0, 0, 0, 0, 18, 68, 37, 164, 68, 60, 105, 122, 113, 117, 105, 101, 114, 100, 111, 0, 24, 29, 0, 0, 0, 0, 0, 0, 5, 194, 20, 192, 72, 0, 6, 195, 32, 20, 192, 72, 12, 3, 95, 50, 48, 69, 6, 116, 50, 47, 36, 0, 0, 10, 135, 8, 1, 2, 195, 173, 1, 19, 72, 0, 0, 0, 6, 195, 48, 20, 192, 72, 0, 10, 3, 95, 53, 15, 49, 37, 50, 47, 0, 0, 0, 14, 4, 95, 13, 3, 14, 63, 35, 49, 34, 6, 108, 50, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 54, 15, 87, 6, 107, 49, 87, 47, 0, 0, 0, 0, 7, 132, 1, 19, 195, 173, 8, 0, 0, 0, 0, 0, 12, 3, 95, 55, 15, 87, 6, 107, 47, 37, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 20, 224, 72, 28, 0, 13, 3, 95, 51, 88, 47, 34, 6, 116, 50, 47, 35, 0, 0, 14, 3, 95, 48, 67, 85, 57, 6, 107, 50, 47, 108, 87, 0, 0, 0, 0, 16, 67, 17, 32, 64, 100, 111, 99, 116, 111, 114, 97, 0, 41, 24, 29, 0, 12, 3, 95, 57, 15, 50, 39, 80, 6, 36, 50, 0, 0, 0, 0, 0, 13, 3, 95, 49, 67, 85, 6, 37, 36, 50, 47, 39, 0, 0, 0, 0, 11, 136, 5, 19, 20, 1, 18, 195, 173, 1, 72, 0, 0, 0, 5, 194, 48, 16, 72, 8, 4, 95, 35, 194, 170, 35, 0, 0, 0, 0, 8, 197, 21, 53, 21, 88, 80, 72, 0, 0, 0, 0, 0, 11, 3, 95, 49, 49, 6, 108, 50, 85, 36, 0, 0, 0, 12, 3, 95, 49, 51, 47, 34, 6, 36, 85, 36, 0, 0, 11, 3, 95, 49, 50, 70, 6, 39, 85, 36, 0, 0, 12, 3, 95, 49, 53, 49, 6, 37, 50, 85, 36, 0, 0, 14, 3, 95, 49, 52, 49, 35, 47, 6, 108, 34, 85, 36, 0, 0, 12, 3, 95, 52, 15, 49, 58, 6, 35, 34, 47, 0, 0, 0, 8, 4, 95, 35, 194, 186, 39, 0, 0, 14, 3, 95, 55, 88, 87, 107, 47, 6, 107, 50, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 53, 67, 49, 37, 50, 57, 6, 107, 50, 47, 108, 87, 0, 0, 9, 134, 8, 1, 2, 195, 173, 1, 72, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 88, 70, 57, 6, 107, 85, 0, 0, 0, 0, 12, 137, 19, 5, 18, 195, 173, 1, 13, 15, 19, 72, 0, 0, 0, 0, 0, 11, 3, 95, 50, 88, 69, 6, 116, 50, 47, 0, 0, 7, 196, 5, 21, 69, 48, 76, 19, 3, 95, 55, 67, 87, 4, 36, 47, 36, 85, 57, 6, 107, 50, 47, 108, 87, 0, 0, 0, 0, 0, 12, 3, 95, 56, 15, 108, 49, 47, 6, 35, 80, 0, 0, 0, 0, 0, 0, 8, 197, 25, 81, 82, 60, 224, 72, 0, 0, 0, 14, 3, 95, 63, 63, 87, 6, 37, 63, 69, 108, 55, 39, 0, 0, 0, 0, 15, 3, 95, 52, 88, 49, 58, 35, 34, 6, 107, 50, 47, 35, 0, 0, 19, 3, 95, 57, 67, 50, 4, 108, 80, 36, 85, 57, 6, 107, 50, 47, 108, 87, 0, 0, 0, 0, 0, 0, 0, 16, 66, 44, 112, 107, 105, 108, 111, 103, 114, 97, 109, 111, 0, 24, 29, 0, 16, 3, 95, 53, 88, 85, 37, 50, 49, 58, 6, 107, 50, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 54, 88, 87, 107, 87, 6, 107, 50, 47, 35, 0, 0, 0, 15, 4, 95, 50, 88, 15, 80, 37, 99, 6, 107, 87, 37, 63, 0, 0, 0, 0, 9, 134, 1, 12, 7, 195, 186, 14, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 88, 108, 74, 6, 107, 50, 47, 35, 0, 0, 0, 10, 135, 8, 1, 2, 18, 195, 161, 14, 72, 0, 11, 136, 5, 19, 20, 1, 18, 195, 161, 14, 72, 0, 0, 0, 0, 5, 194, 52, 80, 76, 0, 14, 3, 95, 57, 88, 50, 108, 80, 6, 107, 50, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 5, 19, 20, 1, 18, 195, 161, 19, 72, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 15, 7, 15, 49, 39, 55, 6, 37, 47, 35, 0, 0, 8, 196, 20, 229, 18, 20, 72, 8, 0, 15, 3, 13, 194, 170, 109, 97, 114, 195, 173, 97, 0, 41, 24, 29, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 70, 52, 86, 9, 12, 19, 143, 63, 107, 99, 37, 49, 35, 50, 39, 0, 0, 5, 194, 61, 48, 76, 0, 0, 18, 4, 95, 48, 77, 52, 10, 69, 37, 57, 12, 6, 39, 50, 107, 87, 0, 102, 16, 4, 95, 48, 77, 52, 10, 69, 37, 96, 6, 39, 50, 107, 87, 0, 0, 0, 10, 135, 8, 1, 2, 18, 195, 161, 19, 72, 17, 4, 95, 48, 77, 50, 63, 37, 57, 12, 6, 39, 50, 36, 87, 0, 102, 15, 4, 95, 48, 77, 50, 63, 37, 96, 6, 39, 50, 36, 87, 0, 0, 0, 0, 11, 4, 95, 48, 77, 49, 63, 6, 37, 55, 0, 0, 13, 4, 95, 2, 18, 22, 69, 34, 6, 36, 80, 36, 0, 0, 0, 0, 0, 0, 6, 195, 76, 84, 128, 72, 0, 0, 0, 0, 9, 198, 76, 148, 85, 36, 84, 129, 8, 0, 0, 0, 0, 0, 0, 0, 8, 66, 52, 144, 63, 37, 0, 76, 0, 0, 0, 8, 197, 21, 53, 21, 88, 240, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 8, 1, 2, 195, 173, 1, 9, 19, 72, 0, 0, 13, 138, 5, 19, 20, 1, 18, 195, 173, 1, 9, 19, 72, 0, 10, 66, 48, 192, 107, 57, 12, 36, 0, 102, 8, 66, 48, 192, 107, 96, 36, 0, 0, 0, 7, 196, 80, 145, 78, 20, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 195, 169, 12, 76, 0, 7, 196, 32, 16, 197, 56, 76, 0, 0, 0, 0, 0, 9, 197, 5, 83, 145, 84, 80, 72, 8, 0, 0, 19, 4, 95, 52, 88, 15, 49, 58, 35, 84, 34, 35, 99, 6, 107, 87, 37, 63, 0, 0, 0, 8, 197, 80, 145, 78, 21, 48, 72, 0, 19, 4, 95, 3, 9, 18, 85, 37, 34, 49, 40, 63, 81, 55, 6, 36, 99, 39, 0, 0, 0, 0, 0, 0, 6, 195, 52, 148, 192, 76, 0, 7, 196, 32, 16, 197, 72, 76, 0, 0, 0, 6, 195, 56, 244, 192, 76, 0, 7, 196, 32, 16, 197, 76, 76, 0, 0, 9, 198, 4, 193, 213, 56, 244, 192, 72, 0, 13, 4, 95, 19, 20, 11, 69, 6, 35, 51, 52, 35, 0, 0, 0, 13, 4, 95, 1, 3, 21, 35, 98, 6, 40, 84, 39, 0, 0, 19, 3, 95, 195, 179, 6, 39, 15, 35, 85, 107, 50, 47, 58, 6, 35, 84, 35, 0, 25, 3, 95, 194, 171, 49, 39, 63, 6, 37, 96, 35, 87, 15, 37, 85, 49, 96, 6, 107, 34, 84, 35, 87, 0, 0, 0, 0, 13, 4, 4, 195, 177, 1, 100, 111, 195, 177, 97, 0, 29, 0, 5, 194, 48, 240, 72, 0, 0, 0, 0, 0, 13, 4, 95, 18, 14, 7, 35, 50, 6, 37, 96, 39, 0, 0, 23, 3, 95, 194, 161, 35, 80, 34, 6, 37, 34, 35, 84, 63, 37, 34, 35, 85, 57, 6, 108, 50, 0, 0, 0, 0, 0, 0, 0, 8, 133, 5, 19, 20, 195, 161, 72, 0, 0, 0, 0, 8, 133, 19, 5, 18, 195, 161, 72, 0, 0, 0, 0, 0, 6, 195, 21, 32, 64, 72, 0, 0, 6, 195, 21, 32, 78, 72, 0, 14, 66, 77, 32, 115, 101, 195, 177, 111, 114, 0, 41, 24, 29, 8, 133, 19, 5, 18, 195, 169, 72, 0, 19, 67, 65, 65, 64, 112, 114, 101, 115, 105, 100, 101, 110, 116, 101, 0, 41, 24, 29, 0, 0, 0, 20, 4, 95, 1, 3, 50, 70, 6, 108, 69, 55, 36, 15, 35, 98, 6, 40, 84, 39, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 5, 19, 20, 195, 161, 2, 1, 13, 15, 19, 72, 0, 6, 195, 21, 32, 83, 72, 6, 195, 21, 32, 83, 72, 0, 0, 0, 0, 27, 3, 95, 194, 191, 35, 80, 34, 6, 37, 34, 37, 50, 47, 107, 51, 52, 4, 39, 98, 35, 85, 57, 6, 108, 50, 0, 0, 19, 4, 95, 53, 88, 15, 49, 37, 50, 49, 58, 35, 99, 6, 107, 87, 37, 63, 0, 0, 0, 0, 23, 3, 95, 194, 187, 49, 39, 63, 6, 37, 96, 35, 87, 15, 70, 107, 34, 6, 107, 74, 35, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 67, 37, 164, 64, 105, 122, 113, 117, 105, 101, 114, 100, 97, 0, 24, 29, 6, 195, 77, 84, 192, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 2, 194, 167, 87, 107, 49, 85, 57, 6, 108, 50, 0, 0, 5, 194, 56, 240, 72, 5, 194, 76, 80, 76, 0, 0, 0, 11, 2, 194, 163, 55, 37, 80, 34, 35, 87, 0, 0, 0, 0, 0, 0, 5, 194, 77, 80, 76, 0, 0, 6, 2, 194, 170, 35, 0, 0, 0, 10, 135, 19, 5, 18, 195, 169, 9, 19, 72, 0, 18, 2, 195, 161, 6, 35, 15, 35, 85, 107, 50, 47, 58, 6, 35, 84, 35, 0, 14, 2, 194, 169, 49, 39, 48, 37, 51, 52, 6, 115, 47, 0, 0, 13, 2, 194, 182, 48, 6, 35, 51, 52, 35, 81, 39, 0, 0, 0, 6, 195, 76, 242, 83, 72, 0, 18, 2, 195, 173, 6, 37, 15, 35, 85, 107, 50, 47, 58, 6, 35, 84, 35, 0, 0, 0, 0, 0, 18, 2, 195, 169, 6, 36, 15, 35, 85, 107, 50, 47, 58, 6, 35, 84, 35, 0, 10, 199, 21, 53, 21, 88, 147, 79, 76, 72, 0, 0, 0, 0, 0, 6, 2, 194, 186, 39, 0, 14, 4, 95, 3, 5, 4, 85, 36, 84, 6, 37, 96, 35, 0, 0, 19, 2, 195, 179, 6, 39, 15, 35, 85, 107, 50, 47, 58, 6, 35, 84, 35, 0, 14, 0, 0, 9, 2, 195, 177, 23, 107, 65, 36, 0, 16, 4, 95, 12, 9, 7, 55, 37, 98, 35, 84, 6, 40, 34, 35, 0, 0, 0, 0, 16, 2, 195, 188, 4, 40, 84, 57, 107, 34, 6, 107, 87, 37, 87, 0, 5, 194, 80, 80, 76, 0, 0, 18, 2, 195, 186, 6, 40, 15, 35, 85, 107, 50, 47, 58, 6, 35, 84, 35, 0, 0, 0, 0, 0, 0, 0, 5, 194, 81, 80, 76, 5, 194, 81, 80, 76, 0, 18, 4, 95, 54, 88, 15, 87, 36, 98, 87, 35, 99, 6, 107, 87, 37, 63, 0, 0, 0, 0, 0, 0, 0, 0, 13, 66, 84, 64, 117, 115, 116, 101, 100, 0, 41, 24, 29, 5, 194, 84, 64, 76, 0, 0, 7, 196, 32, 83, 79, 76, 72, 7, 196, 76, 243, 79, 76, 72, 0, 8, 197, 80, 145, 78, 20, 224, 72, 0, 0, 0, 0, 0, 0, 0, 6, 195, 21, 53, 5, 76, 0, 0, 0, 0, 6, 195, 21, 53, 1, 76, 0, 0, 6, 195, 21, 53, 15, 76, 0, 6, 195, 76, 246, 64, 72, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 1, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 15, 39, 0, 0, 0, 0, 0, 9, 198, 21, 53, 1, 8, 18, 83, 72, 6, 195, 21, 48, 64, 76, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 21, 49, 64, 76, 0, 0, 14, 2, 95, 25, 4, 37, 79, 34, 6, 37, 107, 98, 35, 0, 0, 0, 0, 6, 195, 21, 48, 83, 76, 0, 0, 0, 0, 13, 2, 95, 34, 49, 39, 63, 6, 37, 96, 35, 87, 0, 0, 23, 2, 95, 33, 85, 107, 51, 52, 6, 35, 34, 35, 84, 63, 37, 34, 35, 85, 57, 6, 108, 50, 0, 0, 6, 195, 20, 195, 1, 76, 0, 6, 195, 76, 243, 128, 72, 7, 195, 12, 243, 128, 72, 8, 15, 2, 95, 39, 35, 48, 108, 87, 47, 34, 6, 39, 81, 39, 0, 0, 0, 0, 0, 19, 2, 95, 43, 87, 6, 37, 98, 50, 108, 70, 36, 87, 40, 63, 6, 35, 34, 0, 0, 13, 4, 95, 3, 1, 16, 63, 6, 35, 96, 40, 87, 0, 0, 23, 2, 95, 41, 85, 57, 4, 107, 51, 52, 35, 48, 35, 34, 6, 107, 50, 47, 36, 87, 37, 87, 0, 0, 21, 2, 95, 40, 4, 35, 80, 34, 36, 48, 35, 34, 6, 107, 50, 47, 36, 87, 37, 87, 0, 0, 10, 2, 95, 47, 69, 35, 51, 52, 35, 0, 0, 10, 2, 95, 46, 48, 40, 50, 47, 39, 0, 0, 9, 2, 95, 45, 79, 96, 108, 50, 0, 0, 9, 2, 95, 44, 49, 39, 63, 35, 0, 0, 10, 2, 95, 51, 47, 34, 6, 36, 87, 0, 0, 9, 2, 95, 50, 70, 6, 108, 87, 0, 0, 9, 134, 8, 1, 2, 18, 195, 169, 72, 9, 2, 95, 49, 6, 40, 50, 39, 0, 0, 9, 2, 95, 48, 85, 36, 34, 39, 0, 0, 11, 2, 95, 55, 87, 57, 6, 36, 47, 36, 0, 0, 9, 2, 95, 54, 87, 6, 116, 87, 0, 0, 11, 2, 95, 53, 85, 6, 37, 50, 49, 39, 0, 20, 4, 95, 4, 1, 3, 70, 6, 108, 69, 55, 36, 15, 35, 98, 6, 40, 84, 39, 0, 0, 12, 2, 95, 52, 49, 58, 6, 35, 47, 34, 39, 0, 0, 17, 2, 95, 59, 48, 4, 40, 50, 47, 39, 37, 49, 6, 39, 63, 35, 0, 0, 16, 2, 95, 58, 70, 4, 108, 87, 48, 6, 40, 50, 47, 108, 87, 0, 0, 11, 2, 95, 57, 50, 58, 6, 36, 80, 36, 0, 0, 9, 2, 95, 56, 6, 108, 74, 39, 0, 0, 27, 2, 95, 63, 85, 107, 51, 52, 6, 35, 34, 37, 50, 47, 107, 51, 52, 4, 39, 98, 35, 85, 57, 6, 108, 50, 0, 0, 13, 2, 95, 62, 63, 35, 96, 6, 108, 34, 49, 36, 0, 0, 0, 13, 2, 95, 60, 63, 36, 50, 6, 108, 34, 49, 36, 0, 0, 0, 7, 196, 16, 84, 196, 20, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 8, 1, 2, 18, 195, 161, 72, 0, 9, 198, 21, 53, 1, 8, 19, 128, 72, 0, 0, 0, 0, 6, 195, 33, 80, 133, 72, 9, 198, 85, 53, 5, 16, 84, 192, 76, 0, 0, 0, 12, 201, 21, 53, 21, 88, 148, 212, 20, 148, 192, 72, 0, 9, 198, 21, 53, 1, 8, 20, 192, 72, 9, 198, 21, 53, 1, 52, 244, 192, 72, 0, 0, 13, 4, 95, 4, 15, 20, 48, 6, 40, 50, 47, 39, 0, 0, 0, 0, 18, 2, 95, 91, 4, 35, 80, 34, 36, 49, 108, 34, 74, 6, 36, 47, 36, 0, 0, 19, 67, 36, 195, 79, 105, 108, 117, 115, 116, 114, 105, 115, 105, 109, 111, 0, 24, 29, 0, 0, 7, 66, 88, 144, 69, 37, 0, 0, 7, 195, 16, 226, 64, 17, 42, 15, 2, 95, 95, 87, 40, 80, 34, 35, 96, 6, 35, 84, 39, 0, 0, 0, 20, 2, 95, 93, 85, 57, 4, 107, 51, 52, 35, 49, 108, 34, 74, 6, 36, 47, 36, 0, 0, 21, 2, 95, 92, 69, 6, 35, 51, 52, 35, 37, 63, 69, 107, 34, 47, 6, 37, 84, 35, 0, 0, 0, 0, 17, 4, 95, 56, 88, 15, 108, 49, 47, 39, 99, 6, 107, 87, 37, 63, 0, 0, 18, 2, 95, 96, 35, 85, 6, 107, 50, 47, 108, 79, 34, 6, 35, 80, 36, 0, 0, 0, 6, 195, 33, 80, 143, 72, 0, 0, 19, 67, 36, 195, 65, 105, 108, 117, 115, 116, 114, 105, 115, 105, 109, 97, 0, 24, 29, 0, 0, 0, 0, 13, 4, 95, 7, 18, 22, 79, 34, 6, 35, 80, 36, 0, 0, 0, 16, 7, 13, 195, 169, 24, 9, 3, 15, 63, 107, 99, 37, 49, 39, 0, 0, 0, 0, 6, 195, 48, 84, 192, 72, 0, 0, 0, 9, 198, 80, 83, 133, 52, 244, 192, 72, 9, 198, 76, 84, 133, 52, 244, 192, 72, 0, 0, 0, 0, 0, 15, 2, 95, 123, 4, 35, 80, 34, 36, 96, 6, 35, 80, 36, 0, 16, 4, 95, 4, 9, 1, 70, 57, 6, 107, 34, 36, 87, 37, 87, 0, 0, 0, 0, 0, 0, 0, 17, 2, 95, 125, 85, 57, 4, 107, 51, 52, 35, 96, 6, 35, 80, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 85, 53, 5, 16, 76, 0, 0, 5, 194, 84, 224, 72, 0, 0, 0, 0, 9, 198, 89, 81, 83, 81, 32, 64, 76, 9, 198, 57, 81, 83, 81, 32, 64, 76, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 33, 80, 137, 77, 65, 64, 72, 15, 4, 95, 35, 51, 50, 107, 87, 48, 6, 35, 85, 57, 39, 0, 0, 0, 0, 0, 0, 9, 198, 89, 81, 83, 81, 32, 83, 76, 9, 198, 57, 81, 83, 81, 32, 83, 76, 0, 0, 8, 197, 25, 82, 83, 80, 80, 72, 0, 8, 133, 3, 195, 179, 13, 15, 8, 0, 0, 0, 17, 4, 95, 57, 88, 15, 50, 39, 50, 35, 99, 6, 107, 87, 37, 63, 0, 0, 0, 0, 0, 11, 136, 19, 5, 18, 195, 173, 1, 9, 19, 72, 0, 0, 6, 195, 21, 51, 192, 76, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 81, 84, 192, 76, 0, 0, 0, 0, 0, 6, 195, 21, 51, 211, 76, 0, 0, 0, 0, 0, 0, 0, 9, 198, 56, 244, 207, 81, 32, 83, 76, 0, 0, 0, 0, 0, 0, 0, 0, 10, 199, 21, 53, 21, 88, 148, 212, 20, 72, 0, 0, 0, 0, 0, 10, 135, 5, 19, 20, 195, 161, 9, 19, 72, 0, 11, 136, 4, 5, 19, 16, 21, 195, 169, 19, 8, 6, 131, 20, 195, 186, 76, 0, 0, 0, 7, 196, 21, 53, 15, 76, 76, 0, 8, 133, 3, 21, 195, 161, 12, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 21, 53, 1, 76, 76, 0, 0, 0, 0, 7, 196, 21, 53, 1, 72, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 67, 84, 68, 192, 117, 115, 116, 101, 100, 101, 115, 0, 41, 24, 29, 6, 195, 84, 68, 192, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 5, 19, 20, 195, 161, 14, 72, 0, 0, 0, 9, 134, 5, 19, 20, 195, 161, 19, 72, 0, 7, 196, 21, 53, 15, 100, 72, 0, 6, 18, 66, 108, 0, 114, 0, 121, 0, 7, 6, 18, 67, 98, 0, 100, 0, 103, 0, 110, 0, 109, 0, 7, 6, 18, 68, 102, 0, 104, 0, 106, 0, 115, 0, 121, 0, 122, 0, 114, 0, 7, 6, 18, 69, 98, 0, 118, 0, 102, 0, 112, 0, 7, 6, 18, 70, 103, 0, 107, 0, 7, 6, 18, 71, 106, 0, 119, 0, 108, 0, 114, 0, 98, 0, 100, 0, 103, 0, 110, 0, 109, 0, 112, 0, 116, 0, 107, 0, 99, 0, 7, 6, 97, 0, 117, 2, 32, 3, 6, 112, 0, 121, 2, 32, 3, 6, 115, 0, 3, 35, 0, 117, 3, 112, 0, 4, 105, 3, 115, 0, 121, 2, 25, 0, 7, 6, 98, 0, 4, 3, 69, 0, 1, 109, 0, 1, 110, 0, 2, 105, 17, 65, 0, 2, 117, 17, 65, 0, 8, 2, 17, 65, 0, 8, 2, 18, 66, 17, 65, 0, 8, 2, 28, 1, 0, 4, 2, 17, 65, 3, 80, 0, 2, 18, 68, 0, 2, 99, 17, 71, 0, 7, 6, 99, 0, 4, 3, 49, 0, 8, 2, 18, 66, 17, 65, 0, 4, 104, 3, 74, 0, 104, 8, 2, 17, 65, 0, 2, 17, 71, 3, 85, 0, 7, 6, 100, 0, 4, 3, 70, 0, 1, 108, 0, 1, 109, 0, 1, 110, 0, 1, 114, 0, 8, 2, 17, 65, 0, 8, 2, 28, 1, 0, 8, 2, 114, 17, 65, 0, 4, 2, 17, 65, 3, 84, 0, 2, 18, 68, 0, 2, 99, 17, 71, 0, 7, 6, 101, 0, 117, 2, 32, 3, 6, 113, 0, 121, 2, 32, 3, 6, 116, 0, 4, 3, 36, 0, 2, 17, 67, 104, 0, 4, 1, 114, 17, 65, 3, 107, 0, 2, 110, 25, 0, 2, 114, 0, 117, 3, 113, 0, 4, 105, 3, 116, 0, 121, 2, 25, 0, 7, 6, 102, 0, 4, 3, 81, 0, 8, 2, 18, 66, 17, 65, 0, 7, 6, 103, 0, 110, 8, 2, 17, 65, 3, 50, 0, 4, 3, 79, 0, 1, 109, 0, 1, 110, 0, 8, 2, 17, 65, 0, 8, 2, 18, 66, 17, 65, 0, 8, 2, 28, 1, 0, 104, 8, 2, 17, 65, 0, 4, 2, 17, 65, 3, 98, 0, 2, 18, 68, 0, 2, 99, 17, 71, 0, 2, 17, 71, 12, 3, 99, 0, 7, 6, 104, 0, 3, 0, 105, 8, 2, 17, 65, 3, 96, 0, 7, 6, 105, 0, 4, 5, 35, 1, 108, 2, 17, 65, 3, 2, 37, 0, 5, 35, 1, 114, 2, 17, 65, 0, 3, 37, 0, 4, 1, 17, 67, 2, 17, 65, 3, 57, 0, 1, 117, 103, 2, 17, 65, 0, 2, 17, 65, 3, 96, 0, 7, 6, 106, 0, 3, 99, 0, 7, 6, 107, 0, 4, 3, 49, 0, 8, 2, 18, 66, 17, 65, 0, 7, 6, 108, 0, 3, 55, 0, 108, 5, 2, 1, 17, 65, 2, 17, 65, 3, 57, 12, 0, 4, 108, 3, 96, 0, 108, 8, 2, 17, 65, 0, 7, 6, 109, 0, 4, 2, 25, 3, 50, 0, 110, 8, 2, 101, 109, 0, 4, 3, 63, 0, 2, 18, 69, 0, 2, 32, 18, 69, 0, 4, 2, 18, 70, 3, 66, 0, 2, 32, 18, 70, 0, 2, 106, 0, 7, 6, 110, 0, 3, 50, 0, 4, 2, 18, 69, 3, 63, 0, 2, 32, 18, 69, 0, 4, 2, 18, 70, 3, 66, 0, 2, 32, 18, 70, 0, 2, 106, 0, 7, 6, 111, 0, 121, 2, 32, 3, 6, 118, 0, 4, 3, 39, 0, 2, 17, 67, 104, 0, 4, 1, 114, 17, 65, 3, 108, 0, 2, 17, 67, 25, 0, 2, 114, 0, 4, 105, 3, 118, 0, 121, 2, 25, 0, 7, 6, 112, 0, 4, 116, 8, 2, 101, 114, 111, 3, 47, 0, 116, 8, 2, 111, 108, 0, 4, 3, 48, 0, 8, 2, 18, 66, 17, 65, 0, 2, 116, 3, 48, 12, 0, 4, 104, 2, 25, 3, 81, 0, 104, 8, 0, 4, 115, 8, 2, 101, 117, 100, 111, 3, 87, 0, 115, 8, 2, 105, 0, 7, 6, 113, 0, 4, 3, 49, 0, 117, 0, 7, 6, 114, 0, 4, 3, 34, 0, 1, 17, 65, 2, 17, 65, 0, 1, 17, 67, 2, 17, 65, 0, 2, 32, 0, 2, 116, 0, 4, 1, 108, 2, 17, 65, 3, 51, 0, 1, 109, 2, 17, 65, 0, 1, 110, 2, 17, 65, 0, 1, 115, 2, 17, 65, 0, 8, 2, 17, 65, 0, 114, 3, 51, 52, 0, 7, 6, 115, 0, 8, 2, 17, 67, 21, 3, 2, 107, 87, 0, 4, 3, 87, 0, 1, 10, 2, 32, 14, 128, 128, 129, 0, 115, 2, 25, 0, 4, 104, 2, 25, 3, 89, 0, 104, 8, 2, 17, 65, 0, 104, 8, 2, 18, 66, 17, 65, 0, 7, 6, 116, 0, 4, 3, 47, 0, 8, 2, 18, 66, 17, 65, 0, 4, 104, 2, 25, 3, 85, 0, 104, 8, 0, 7, 6, 117, 0, 4, 1, 103, 2, 101, 3, 0, 1, 103, 2, 105, 3, 0, 4, 5, 35, 1, 108, 2, 17, 65, 3, 2, 40, 0, 5, 35, 1, 114, 2, 17, 65, 0, 3, 40, 0, 4, 2, 17, 65, 3, 58, 0, 2, 121, 32, 0, 7, 6, 118, 0, 4, 3, 69, 0, 1, 109, 0, 1, 110, 0, 2, 105, 17, 65, 0, 2, 117, 17, 65, 0, 8, 2, 17, 65, 0, 8, 2, 18, 66, 17, 65, 0, 8, 2, 28, 1, 0, 4, 2, 17, 65, 3, 80, 0, 2, 18, 68, 0, 2, 99, 17, 71, 0, 7, 6, 119, 0, 4, 3, 58, 0, 104, 8, 2, 17, 65, 0, 7, 6, 120, 0, 2, 32, 3, 8, 98, 87, 0, 3, 49, 87, 0, 8, 2, 28, 1, 3, 86, 0, 5, 1, 1, 17, 65, 2, 17, 65, 3, 98, 87, 0, 7, 6, 121, 0, 3, 37, 0, 5, 2, 1, 17, 65, 2, 17, 65, 3, 57, 12, 0, 4, 1, 110, 3, 77, 0, 8, 2, 28, 1, 0, 8, 108, 0, 8, 109, 0, 2, 17, 65, 3, 96, 0, 7, 6, 122, 0, 3, 85, 0, 5, 2, 2, 18, 67, 3, 86, 0, 7, 6, 0, 195, 161, 3, 7, 35, 0, 195, 173, 3, 7, 37, 0, 195, 186, 3, 7, 40, 0, 195, 169, 3, 7, 107, 0, 195, 179, 3, 7, 108, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 195, 188, 3, 40, 0, 44, 2, 15, 3, 49, 108, 63, 35, 0, 45, 8, 2, 32, 15, 3, 63, 6, 107, 50, 108, 87, 0, 195, 177, 3, 65, 0, 36, 3, 70, 6, 108, 55, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts16 = FileInMemory_createWithData (6437, reinterpret_cast (&espeakdata_dicts16_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/es_dict", L"es"); Collection_addItem (me.peek(), espeakdata_dicts16.transfer()); static unsigned char espeakdata_dicts17_data[6770] = { 0, 4, 0, 0, 55, 19, 0, 0, 0, 0, 0, 0, 0, 6, 65, 4, 35, 106, 0, 0, 7, 194, 5, 0, 17, 42, 42, 0, 0, 0, 7, 65, 8, 69, 36, 108, 0, 0, 0, 17, 67, 21, 64, 192, 36, 47, 15, 47, 87, 36, 47, 36, 34, 35, 0, 24, 0, 0, 8, 65, 12, 47, 87, 36, 108, 0, 0, 0, 0, 0, 7, 65, 16, 70, 36, 108, 0, 0, 0, 0, 7, 196, 76, 83, 12, 20, 76, 6, 195, 76, 147, 129, 72, 0, 42, 65, 20, 6, 36, 50, 50, 36, 15, 63, 4, 36, 37, 57, 36, 15, 4, 35, 57, 107, 15, 6, 35, 34, 12, 82, 35, 63, 37, 87, 47, 0, 24, 84, 46, 32, 109, 32, 46, 32, 97, 32, 25, 65, 20, 6, 36, 50, 50, 36, 15, 49, 34, 6, 37, 87, 12, 47, 40, 87, 47, 0, 24, 81, 107, 114, 32, 6, 65, 20, 36, 108, 0, 0, 0, 16, 67, 76, 18, 128, 87, 6, 35, 57, 107, 50, 70, 37, 55, 0, 24, 20, 67, 41, 34, 192, 57, 4, 119, 34, 57, 36, 15, 49, 6, 39, 34, 34, 70, 0, 24, 0, 0, 7, 65, 24, 36, 81, 81, 0, 0, 0, 0, 0, 7, 65, 28, 79, 36, 108, 0, 0, 0, 0, 0, 7, 65, 32, 105, 35, 106, 0, 0, 0, 0, 0, 13, 1, 36, 47, 39, 55, 12, 55, 35, 34, 37, 47, 0, 6, 65, 36, 37, 110, 0, 0, 16, 1, 37, 48, 34, 39, 47, 87, 6, 36, 50, 47, 12, 37, 0, 27, 0, 7, 1, 38, 10, 36, 47, 0, 0, 0, 8, 65, 40, 57, 39, 47, 12, 0, 0, 0, 10, 1, 42, 47, 119, 51, 12, 50, 0, 27, 0, 11, 1, 43, 48, 55, 40, 87, 12, 87, 0, 27, 0, 7, 65, 44, 49, 35, 106, 0, 0, 14, 66, 45, 0, 49, 6, 115, 48, 6, 119, 36, 82, 0, 24, 0, 0, 15, 1, 47, 49, 35, 55, 12, 70, 15, 49, 34, 110, 48, 87, 0, 0, 7, 65, 48, 36, 55, 55, 0, 0, 18, 66, 49, 0, 55, 4, 40, 79, 116, 15, 48, 6, 108, 47, 40, 70, 0, 24, 0, 0, 7, 196, 52, 147, 12, 20, 76, 0, 42, 65, 52, 63, 4, 36, 37, 57, 36, 15, 6, 35, 57, 107, 15, 6, 35, 34, 82, 35, 63, 4, 37, 87, 36, 15, 57, 6, 119, 34, 79, 37, 0, 84, 46, 32, 97, 32, 46, 32, 106, 32, 7, 65, 52, 36, 63, 63, 0, 0, 0, 0, 0, 7, 65, 56, 36, 50, 50, 0, 0, 0, 0, 0, 6, 65, 60, 39, 113, 0, 0, 18, 1, 61, 82, 117, 51, 12, 70, 40, 87, 15, 63, 119, 34, 49, 12, 0, 27, 0, 0, 0, 26, 65, 64, 48, 6, 119, 34, 107, 87, 47, 15, 49, 34, 6, 37, 87, 47, 40, 87, 47, 0, 24, 81, 107, 114, 32, 7, 1, 64, 10, 119, 47, 0, 7, 65, 64, 48, 36, 108, 0, 0, 0, 0, 0, 7, 65, 68, 49, 40, 115, 0, 0, 0, 0, 0, 7, 65, 72, 36, 51, 51, 0, 0, 0, 0, 0, 21, 65, 76, 87, 6, 36, 55, 15, 6, 106, 87, 47, 35, 55, 0, 24, 82, 46, 32, 97, 32, 7, 65, 76, 36, 87, 87, 0, 0, 0, 0, 0, 7, 65, 80, 47, 36, 108, 0, 0, 0, 0, 0, 5, 65, 84, 115, 0, 0, 0, 0, 0, 7, 65, 88, 82, 36, 108, 0, 0, 7, 194, 5, 48, 17, 42, 42, 0, 0, 13, 4, 95, 49, 77, 52, 69, 37, 61, 57, 39, 50, 0, 0, 14, 1, 92, 55, 119, 66, 79, 15, 49, 34, 110, 48, 87, 0, 14, 65, 92, 49, 6, 35, 49, 87, 37, 87, 82, 36, 108, 0, 0, 0, 0, 7, 196, 60, 195, 149, 16, 72, 0, 12, 4, 95, 49, 77, 49, 47, 40, 105, 107, 47, 0, 8, 65, 96, 37, 49, 12, 87, 0, 0, 6, 194, 4, 64, 17, 24, 13, 4, 95, 49, 77, 50, 63, 37, 61, 57, 39, 50, 0, 0, 14, 4, 95, 49, 77, 51, 63, 37, 61, 57, 35, 34, 70, 0, 0, 0, 9, 65, 100, 37, 79, 34, 36, 49, 0, 0, 0, 0, 0, 9, 65, 104, 47, 87, 36, 47, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 66, 12, 16, 47, 87, 6, 37, 34, 49, 35, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 1, 126, 47, 37, 55, 70, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 67, 48, 147, 12, 55, 6, 37, 55, 12, 0, 0, 0, 8, 132, 1, 195, 188, 5, 17, 42, 0, 0, 0, 0, 13, 5, 16, 195, 181, 12, 12, 48, 6, 117, 55, 12, 0, 0, 0, 14, 67, 5, 81, 192, 6, 35, 115, 79, 40, 87, 47, 0, 24, 0, 0, 0, 0, 0, 7, 196, 44, 83, 12, 20, 76, 0, 0, 0, 18, 67, 41, 50, 192, 57, 4, 35, 39, 87, 49, 6, 39, 50, 50, 70, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 66, 16, 32, 47, 4, 36, 112, 130, 87, 37, 15, 69, 6, 36, 55, 55, 37, 0, 24, 0, 0, 0, 0, 20, 67, 72, 213, 11, 34, 6, 106, 63, 35, 47, 40, 15, 49, 6, 39, 79, 40, 0, 24, 0, 0, 0, 0, 14, 66, 17, 32, 47, 6, 39, 49, 12, 47, 39, 34, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 20, 112, 64, 72, 8, 0, 0, 0, 0, 7, 195, 4, 112, 64, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 56, 81, 68, 76, 0, 0, 0, 0, 0, 0, 0, 0, 23, 67, 73, 66, 128, 34, 4, 35, 40, 70, 15, 47, 6, 36, 108, 15, 57, 6, 35, 106, 63, 0, 24, 6, 195, 56, 82, 68, 76, 0, 11, 4, 95, 4, 16, 20, 49, 39, 63, 107, 0, 0, 0, 0, 0, 0, 0, 0, 15, 67, 77, 35, 128, 87, 6, 40, 34, 34, 50, 40, 70, 0, 24, 6, 195, 56, 82, 76, 76, 0, 0, 0, 0, 0, 12, 4, 95, 20, 12, 4, 47, 37, 55, 70, 36, 0, 15, 3, 95, 35, 57, 47, 35, 69, 40, 55, 106, 47, 39, 34, 0, 0, 10, 67, 4, 195, 0, 6, 35, 55, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 56, 83, 132, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 11, 67, 60, 176, 89, 39, 49, 6, 36, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 67, 52, 240, 128, 63, 4, 39, 69, 6, 37, 110, 55, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 66, 32, 16, 105, 6, 36, 49, 12, 47, 35, 34, 37, 47, 0, 24, 14, 66, 20, 112, 50, 6, 125, 47, 12, 36, 49, 87, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 60, 195, 1, 72, 0, 0, 0, 0, 0, 18, 67, 16, 148, 128, 70, 4, 37, 34, 6, 36, 49, 12, 47, 39, 34, 0, 24, 0, 0, 0, 0, 0, 0, 0, 12, 66, 33, 32, 105, 6, 119, 51, 51, 35, 0, 24, 0, 19, 67, 33, 35, 0, 105, 6, 35, 34, 111, 55, 4, 37, 49, 40, 55, 47, 0, 24, 0, 0, 0, 0, 0, 0, 0, 20, 66, 12, 208, 87, 6, 36, 50, 47, 37, 15, 63, 4, 108, 47, 34, 37, 47, 0, 24, 5, 194, 20, 144, 72, 0, 0, 0, 0, 0, 0, 0, 0, 15, 66, 37, 16, 6, 37, 110, 15, 49, 6, 40, 115, 0, 24, 42, 0, 0, 0, 0, 0, 0, 0, 0, 22, 66, 16, 192, 47, 4, 36, 112, 130, 87, 37, 15, 55, 6, 110, 47, 12, 34, 37, 47, 0, 24, 0, 8, 195, 72, 224, 64, 17, 42, 42, 0, 0, 0, 0, 0, 0, 11, 67, 57, 83, 142, 50, 6, 40, 50, 12, 0, 0, 0, 21, 67, 40, 225, 64, 57, 4, 106, 15, 50, 4, 110, 15, 6, 36, 70, 35, 87, 37, 0, 24, 6, 195, 60, 193, 68, 72, 11, 3, 226, 130, 172, 36, 40, 34, 39, 47, 0, 0, 0, 0, 0, 6, 195, 60, 193, 64, 72, 0, 0, 0, 21, 66, 16, 208, 47, 4, 36, 112, 130, 87, 37, 15, 63, 6, 108, 47, 34, 37, 47, 0, 24, 6, 194, 40, 16, 72, 8, 0, 6, 195, 60, 194, 68, 72, 0, 0, 0, 0, 8, 195, 20, 242, 192, 17, 42, 42, 6, 195, 60, 194, 64, 72, 0, 0, 0, 0, 0, 0, 6, 195, 60, 194, 78, 72, 0, 0, 0, 0, 0, 0, 24, 67, 40, 212, 192, 57, 4, 106, 15, 63, 6, 40, 115, 15, 87, 6, 36, 55, 55, 37, 50, 36, 0, 24, 0, 0, 0, 0, 29, 67, 88, 212, 192, 82, 4, 117, 37, 15, 63, 6, 40, 115, 15, 87, 6, 36, 108, 15, 87, 4, 40, 79, 40, 50, 36, 0, 24, 0, 0, 0, 13, 66, 41, 32, 57, 6, 115, 65, 37, 39, 34, 0, 24, 7, 194, 37, 64, 17, 42, 42, 0, 16, 67, 45, 3, 0, 49, 6, 35, 40, 48, 12, 55, 40, 87, 0, 24, 0, 0, 15, 67, 45, 5, 0, 49, 6, 35, 48, 12, 47, 36, 50, 0, 24, 14, 69, 100, 241, 213, 73, 64, 57, 39, 79, 40, 34, 47, 0, 0, 0, 0, 0, 0, 6, 194, 20, 208, 17, 24, 0, 0, 0, 6, 195, 60, 193, 78, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 194, 20, 224, 17, 42, 42, 0, 20, 3, 95, 51, 88, 49, 6, 39, 55, 63, 15, 49, 4, 123, 63, 63, 36, 50, 70, 0, 0, 11, 3, 95, 48, 67, 87, 35, 70, 107, 10, 0, 0, 0, 0, 24, 3, 11, 195, 188, 49, 6, 39, 34, 47, 36, 34, 37, 15, 6, 123, 105, 4, 37, 87, 47, 40, 0, 24, 0, 0, 0, 17, 66, 41, 64, 57, 4, 106, 15, 47, 6, 36, 37, 87, 36, 70, 0, 24, 6, 195, 52, 145, 1, 76, 0, 0, 10, 3, 95, 49, 67, 87, 35, 70, 107, 0, 0, 14, 67, 45, 37, 0, 49, 6, 39, 34, 47, 36, 34, 0, 24, 0, 6, 195, 44, 81, 1, 76, 6, 195, 76, 81, 1, 76, 0, 0, 0, 0, 18, 3, 95, 49, 57, 6, 123, 105, 36, 49, 87, 35, 47, 36, 37, 87, 47, 0, 0, 11, 67, 44, 83, 12, 49, 6, 36, 55, 12, 0, 18, 67, 61, 50, 192, 6, 39, 87, 107, 15, 49, 6, 39, 50, 50, 70, 0, 24, 19, 3, 95, 49, 56, 49, 6, 35, 105, 36, 49, 87, 35, 47, 36, 37, 87, 47, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 49, 49, 123, 49, 87, 47, 36, 37, 87, 47, 0, 0, 12, 3, 95, 49, 48, 49, 6, 123, 63, 63, 36, 0, 0, 16, 3, 95, 49, 51, 49, 6, 39, 55, 63, 47, 36, 37, 87, 47, 0, 0, 16, 3, 95, 49, 50, 49, 6, 35, 49, 87, 47, 36, 37, 87, 47, 0, 0, 15, 3, 95, 49, 53, 82, 6, 110, 87, 47, 36, 37, 87, 47, 0, 0, 16, 3, 95, 49, 52, 50, 6, 36, 55, 37, 47, 36, 37, 87, 47, 0, 0, 18, 3, 95, 49, 55, 87, 6, 36, 37, 47, 87, 36, 47, 36, 37, 87, 47, 0, 0, 15, 3, 95, 49, 54, 49, 6, 115, 87, 47, 36, 37, 87, 47, 0, 0, 11, 66, 44, 64, 49, 6, 126, 70, 36, 0, 24, 0, 22, 3, 95, 55, 88, 87, 6, 36, 37, 47, 87, 36, 15, 49, 4, 123, 63, 63, 36, 50, 70, 0, 0, 0, 0, 0, 0, 0, 0, 12, 66, 41, 96, 57, 6, 119, 34, 34, 82, 0, 24, 6, 194, 45, 64, 17, 24, 0, 0, 0, 0, 0, 0, 0, 0, 7, 194, 52, 16, 17, 42, 42, 5, 194, 52, 16, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 50, 88, 49, 6, 35, 49, 87, 15, 49, 4, 123, 63, 63, 36, 50, 70, 0, 0, 0, 8, 197, 52, 147, 12, 21, 48, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 63, 63, 63, 6, 119, 34, 49, 0, 0, 0, 13, 66, 53, 32, 63, 6, 37, 87, 47, 36, 34, 0, 24, 0, 20, 3, 95, 52, 88, 50, 6, 36, 55, 111, 15, 49, 4, 123, 63, 63, 36, 50, 70, 0, 0, 0, 0, 0, 6, 195, 76, 81, 64, 76, 0, 0, 6, 195, 56, 17, 0, 72, 0, 17, 66, 44, 112, 49, 4, 37, 55, 114, 79, 34, 6, 35, 63, 63, 0, 24, 0, 19, 67, 76, 84, 20, 87, 6, 36, 48, 47, 6, 36, 63, 63, 69, 36, 34, 0, 24, 7, 195, 20, 130, 192, 72, 8, 19, 3, 95, 53, 88, 82, 6, 110, 87, 15, 49, 4, 123, 63, 63, 36, 50, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 3, 95, 54, 88, 49, 6, 115, 87, 15, 49, 4, 123, 63, 63, 36, 50, 70, 0, 0, 0, 0, 0, 0, 0, 0, 21, 66, 40, 160, 57, 4, 106, 15, 57, 6, 119, 34, 34, 79, 63, 37, 87, 36, 70, 0, 24, 0, 16, 67, 5, 4, 128, 4, 35, 48, 48, 34, 6, 37, 61, 61, 0, 24, 0, 0, 0, 0, 0, 14, 4, 14, 195, 164, 4, 50, 6, 119, 70, 107, 55, 0, 24, 0, 0, 14, 66, 57, 32, 50, 6, 40, 63, 63, 69, 36, 34, 0, 24, 0, 23, 3, 95, 56, 88, 49, 6, 35, 105, 36, 49, 87, 35, 15, 49, 4, 123, 63, 63, 36, 50, 70, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 52, 80, 72, 0, 22, 3, 95, 57, 88, 6, 123, 105, 36, 49, 87, 35, 15, 49, 4, 123, 63, 63, 36, 50, 70, 0, 0, 8, 132, 13, 20, 195, 188, 17, 42, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 66, 57, 64, 50, 6, 125, 47, 36, 49, 87, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 20, 66, 52, 112, 63, 4, 37, 61, 61, 37, 15, 79, 34, 6, 35, 63, 63, 37, 0, 24, 15, 66, 40, 208, 57, 4, 106, 15, 63, 6, 40, 115, 70, 0, 24, 0, 18, 67, 65, 34, 192, 48, 6, 36, 34, 109, 15, 49, 6, 39, 50, 70, 0, 24, 0, 0, 0, 0, 24, 67, 40, 213, 0, 57, 4, 106, 15, 63, 6, 40, 115, 70, 15, 47, 6, 36, 37, 87, 36, 70, 0, 24, 29, 67, 76, 82, 128, 87, 6, 113, 57, 40, 87, 15, 36, 55, 6, 36, 49, 47, 34, 37, 15, 57, 6, 35, 106, 63, 0, 42, 42, 0, 7, 196, 60, 194, 84, 20, 72, 0, 0, 0, 19, 67, 93, 67, 192, 82, 4, 108, 15, 47, 4, 108, 15, 6, 39, 113, 0, 42, 42, 0, 6, 195, 52, 147, 129, 72, 13, 4, 95, 48, 77, 52, 69, 37, 61, 57, 39, 50, 0, 0, 18, 67, 65, 35, 198, 48, 34, 4, 39, 81, 6, 36, 87, 128, 39, 34, 0, 24, 0, 13, 4, 95, 48, 77, 50, 63, 37, 61, 57, 39, 50, 0, 0, 14, 4, 95, 48, 77, 51, 63, 37, 61, 57, 35, 34, 70, 0, 0, 0, 12, 4, 95, 48, 77, 49, 47, 40, 105, 107, 47, 0, 0, 18, 66, 52, 128, 63, 6, 40, 115, 15, 105, 6, 40, 55, 79, 35, 87, 0, 24, 12, 66, 40, 224, 57, 6, 113, 65, 37, 87, 0, 24, 10, 4, 95, 2, 18, 22, 49, 106, 34, 0, 0, 0, 0, 0, 0, 0, 0, 14, 67, 65, 35, 0, 48, 34, 6, 36, 37, 55, 37, 0, 24, 0, 12, 66, 65, 32, 48, 34, 6, 39, 40, 35, 0, 24, 0, 0, 0, 0, 0, 18, 67, 56, 245, 128, 50, 4, 39, 82, 6, 36, 63, 63, 69, 36, 34, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 19, 46, 15, 87, 6, 36, 108, 15, 6, 39, 50, 50, 0, 24, 0, 0, 0, 0, 0, 18, 67, 65, 53, 0, 48, 6, 40, 37, 57, 36, 87, 15, 47, 4, 108, 0, 24, 0, 0, 0, 0, 17, 67, 44, 225, 0, 49, 4, 35, 65, 70, 37, 70, 6, 106, 47, 0, 24, 0, 0, 8, 197, 52, 147, 12, 20, 192, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 195, 181, 1, 6, 117, 48, 12, 36, 15, 4, 106, 87, 47, 35, 0, 24, 0, 0, 16, 66, 52, 176, 63, 6, 106, 15, 49, 6, 39, 50, 50, 70, 0, 24, 0, 15, 67, 44, 241, 0, 49, 6, 39, 70, 107, 50, 37, 49, 0, 24, 0, 0, 8, 132, 22, 195, 181, 9, 72, 8, 0, 0, 16, 67, 76, 82, 192, 87, 6, 36, 49, 116, 50, 70, 37, 47, 0, 24, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 3, 9, 18, 49, 35, 47, 40, 87, 0, 0, 21, 67, 28, 211, 192, 79, 6, 36, 108, 15, 4, 36, 63, 63, 15, 6, 39, 113, 0, 24, 42, 0, 0, 13, 67, 72, 35, 0, 34, 6, 40, 69, 55, 35, 0, 24, 0, 20, 66, 52, 192, 63, 4, 37, 61, 61, 37, 15, 55, 6, 110, 47, 34, 37, 47, 0, 24, 0, 17, 67, 52, 193, 0, 63, 6, 37, 61, 57, 35, 34, 70, 37, 47, 0, 24, 6, 195, 52, 148, 192, 76, 0, 0, 0, 0, 6, 195, 44, 84, 192, 76, 0, 21, 68, 76, 80, 76, 32, 87, 6, 36, 35, 55, 15, 105, 4, 40, 55, 79, 35, 87, 0, 24, 0, 26, 67, 77, 3, 0, 87, 6, 40, 48, 111, 15, 55, 4, 40, 87, 37, 49, 35, 15, 47, 6, 125, 47, 12, 0, 24, 0, 0, 0, 0, 12, 4, 95, 1, 3, 21, 35, 49, 6, 115, 47, 0, 0, 0, 0, 0, 0, 5, 194, 76, 16, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 195, 181, 16, 6, 117, 48, 109, 47, 4, 35, 57, 35, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 16, 67, 72, 69, 0, 34, 4, 35, 40, 70, 15, 47, 6, 108, 0, 24, 16, 67, 52, 229, 0, 63, 6, 106, 50, 15, 47, 6, 36, 108, 0, 24, 6, 131, 15, 195, 188, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 66, 60, 176, 39, 49, 6, 36, 110, 0, 5, 194, 80, 16, 72, 0, 0, 0, 0, 0, 11, 67, 88, 147, 12, 82, 6, 37, 55, 12, 0, 16, 67, 60, 181, 0, 4, 39, 49, 47, 6, 113, 69, 36, 34, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 68, 88, 81, 66, 72, 82, 6, 108, 69, 34, 40, 35, 34, 0, 24, 0, 0, 22, 66, 56, 224, 50, 6, 37, 110, 15, 50, 6, 37, 63, 36, 47, 4, 35, 47, 40, 70, 0, 24, 0, 13, 67, 52, 164, 128, 63, 6, 35, 57, 114, 34, 0, 24, 0, 0, 0, 0, 0, 0, 0, 12, 66, 81, 32, 47, 34, 6, 123, 49, 12, 0, 24, 20, 66, 77, 64, 87, 6, 36, 108, 15, 47, 6, 119, 105, 36, 50, 70, 35, 69, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 12, 2, 194, 164, 82, 35, 55, 6, 115, 47, 35, 0, 0, 0, 0, 10, 2, 194, 163, 50, 35, 108, 55, 35, 0, 0, 0, 0, 0, 0, 7, 2, 195, 164, 119, 120, 0, 0, 0, 0, 0, 19, 67, 16, 85, 19, 47, 4, 36, 47, 87, 6, 36, 63, 63, 69, 36, 34, 0, 24, 16, 2, 195, 160, 6, 35, 106, 15, 55, 106, 0, 24, 81, 108, 97, 32, 0, 0, 0, 0, 5, 194, 60, 224, 72, 0, 6, 195, 4, 32, 192, 17, 0, 7, 196, 88, 82, 68, 36, 72, 0, 0, 0, 0, 7, 2, 195, 182, 121, 122, 0, 0, 0, 0, 7, 2, 195, 181, 117, 118, 0, 0, 11, 4, 95, 3, 5, 4, 87, 36, 70, 110, 0, 0, 0, 15, 70, 100, 241, 200, 85, 37, 0, 57, 39, 79, 40, 34, 47, 0, 0, 8, 2, 197, 161, 89, 35, 106, 0, 0, 0, 15, 67, 80, 83, 0, 47, 6, 36, 55, 109, 81, 39, 50, 0, 24, 0, 5, 194, 80, 80, 72, 7, 2, 195, 188, 123, 124, 0, 0, 16, 67, 80, 194, 192, 47, 6, 117, 61, 49, 37, 50, 40, 70, 0, 24, 0, 6, 195, 80, 82, 69, 72, 0, 0, 0, 11, 67, 33, 83, 12, 105, 6, 40, 55, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 60, 194, 77, 20, 72, 6, 195, 80, 83, 65, 72, 8, 2, 197, 190, 88, 36, 108, 0, 0, 0, 19, 66, 76, 128, 87, 6, 36, 35, 55, 15, 105, 4, 40, 55, 79, 35, 87, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 67, 89, 33, 0, 82, 6, 117, 34, 34, 70, 55, 36, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 56, 82, 76, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 67, 44, 243, 142, 49, 6, 39, 50, 12, 0, 0, 0, 8, 195, 85, 48, 64, 17, 42, 42, 0, 0, 0, 12, 66, 89, 64, 82, 6, 35, 106, 47, 35, 0, 24, 7, 194, 85, 96, 17, 42, 42, 0, 6, 195, 37, 49, 64, 72, 0, 0, 0, 0, 0, 0, 0, 16, 66, 92, 48, 82, 6, 36, 108, 15, 47, 87, 6, 36, 108, 0, 24, 0, 17, 67, 65, 66, 192, 48, 4, 36, 35, 15, 47, 6, 123, 49, 12, 0, 24, 14, 3, 1, 195, 188, 6, 35, 106, 15, 6, 123, 124, 0, 24, 0, 0, 0, 0, 12, 2, 95, 35, 47, 34, 36, 61, 61, 37, 70, 0, 0, 15, 2, 95, 34, 57, 40, 47, 116, 63, 4, 119, 34, 49, 12, 0, 0, 16, 2, 95, 33, 105, 127, 12, 57, 40, 63, 4, 119, 34, 49, 12, 0, 0, 0, 13, 2, 95, 39, 123, 55, 107, 15, 49, 39, 63, 35, 0, 0, 7, 195, 56, 147, 135, 72, 8, 16, 2, 95, 38, 57, 6, 35, 106, 15, 63, 4, 119, 34, 49, 12, 0, 0, 15, 2, 95, 37, 48, 34, 39, 47, 87, 36, 50, 47, 12, 0, 66, 15, 2, 95, 37, 48, 34, 39, 47, 87, 6, 36, 50, 47, 12, 0, 0, 12, 2, 95, 36, 47, 39, 55, 12, 55, 35, 34, 0, 0, 0, 10, 4, 95, 3, 1, 16, 87, 115, 34, 0, 0, 18, 2, 95, 41, 55, 117, 48, 36, 47, 35, 82, 15, 87, 40, 55, 12, 79, 0, 0, 18, 2, 95, 40, 35, 55, 116, 87, 47, 35, 82, 15, 87, 40, 55, 12, 79, 0, 0, 0, 11, 2, 95, 46, 48, 40, 50, 49, 12, 47, 0, 0, 10, 2, 95, 45, 49, 34, 110, 48, 87, 0, 0, 9, 2, 95, 44, 49, 39, 63, 107, 0, 0, 14, 67, 53, 36, 192, 63, 6, 37, 129, 129, 37, 87, 0, 24, 11, 2, 95, 51, 49, 6, 39, 55, 12, 63, 0, 0, 11, 2, 95, 50, 49, 6, 35, 49, 12, 87, 0, 0, 10, 2, 95, 49, 6, 123, 49, 12, 87, 0, 0, 11, 2, 95, 48, 50, 6, 40, 55, 12, 55, 0, 0, 12, 2, 95, 55, 87, 6, 36, 37, 47, 87, 36, 0, 0, 10, 2, 95, 54, 49, 6, 40, 115, 87, 0, 0, 10, 2, 95, 53, 82, 6, 37, 110, 87, 0, 0, 10, 2, 95, 52, 50, 6, 36, 55, 111, 0, 0, 0, 10, 2, 95, 58, 49, 113, 55, 39, 50, 0, 0, 12, 2, 95, 57, 6, 123, 105, 36, 49, 87, 35, 0, 0, 12, 66, 80, 176, 47, 6, 123, 49, 12, 37, 0, 24, 13, 2, 95, 56, 49, 6, 35, 105, 36, 49, 87, 35, 0, 0, 15, 2, 95, 63, 49, 123, 129, 111, 63, 4, 119, 34, 49, 12, 0, 0, 10, 2, 95, 62, 87, 115, 34, 36, 63, 0, 0, 0, 12, 2, 95, 60, 82, 125, 49, 12, 87, 36, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 67, 76, 225, 0, 87, 6, 123, 65, 65, 70, 37, 50, 40, 70, 0, 24, 0, 0, 8, 195, 16, 224, 64, 17, 42, 42, 0, 0, 0, 0, 0, 0, 0, 0, 21, 67, 20, 177, 192, 6, 36, 108, 15, 49, 4, 35, 106, 15, 79, 6, 36, 108, 0, 24, 42, 0, 0, 0, 0, 31, 2, 95, 91, 6, 35, 55, 116, 87, 47, 35, 82, 15, 49, 6, 35, 50, 70, 37, 62, 37, 50, 36, 15, 87, 6, 40, 55, 12, 79, 0, 0, 11, 4, 95, 226, 130, 172, 36, 40, 34, 39, 0, 0, 0, 0, 14, 2, 95, 95, 35, 55, 12, 55, 49, 34, 110, 48, 87, 0, 0, 0, 32, 2, 95, 93, 55, 6, 117, 48, 36, 47, 35, 82, 15, 49, 6, 35, 50, 70, 37, 55, 4, 37, 50, 36, 15, 87, 6, 40, 55, 12, 79, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 66, 80, 224, 47, 6, 119, 50, 107, 82, 0, 24, 13, 4, 95, 7, 18, 22, 79, 34, 106, 82, 37, 87, 0, 0, 0, 0, 0, 0, 17, 67, 64, 212, 192, 48, 6, 36, 35, 63, 37, 87, 36, 55, 47, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 4, 9, 1, 47, 119, 48, 37, 70, 0, 30, 2, 95, 123, 35, 55, 116, 87, 47, 35, 82, 15, 55, 6, 113, 79, 36, 55, 4, 37, 50, 36, 15, 87, 6, 40, 55, 12, 79, 0, 0, 0, 0, 0, 0, 0, 30, 2, 95, 125, 55, 117, 48, 36, 47, 35, 82, 15, 55, 6, 113, 79, 36, 55, 4, 37, 50, 36, 15, 87, 6, 40, 55, 12, 79, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 35, 51, 50, 47, 6, 123, 105, 37, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 67, 52, 195, 128, 63, 6, 37, 61, 57, 39, 50, 37, 47, 0, 24, 8, 195, 5, 67, 64, 17, 42, 42, 0, 0, 0, 0, 0, 7, 196, 60, 193, 77, 20, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 5, 13, 195, 164, 19, 19, 63, 6, 119, 87, 12, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 67, 8, 32, 192, 69, 4, 110, 15, 69, 4, 110, 15, 87, 6, 37, 110, 0, 42, 42, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 195, 164, 19, 19, 6, 119, 87, 12, 87, 0, 0, 0, 0, 0, 0, 6, 195, 52, 82, 69, 72, 0, 0, 0, 0, 0, 18, 67, 44, 130, 192, 49, 4, 37, 105, 109, 55, 49, 6, 39, 50, 70, 0, 24, 0, 7, 196, 60, 193, 84, 20, 72, 0, 0, 0, 11, 67, 76, 149, 20, 87, 6, 37, 47, 12, 0, 0, 0, 0, 9, 198, 60, 193, 75, 76, 147, 128, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 195, 5, 69, 128, 17, 42, 42, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 105, 0, 106, 0, 7, 6, 18, 67, 98, 0, 100, 0, 102, 0, 103, 0, 104, 0, 106, 0, 108, 0, 109, 0, 110, 0, 114, 0, 115, 0, 118, 0, 7, 6, 18, 68, 108, 0, 109, 0, 110, 0, 114, 0, 7, 6, 18, 69, 195, 181, 0, 195, 164, 0, 195, 182, 0, 195, 188, 0, 97, 0, 98, 0, 99, 0, 100, 0, 101, 0, 102, 0, 103, 0, 104, 0, 105, 0, 106, 0, 107, 0, 108, 0, 109, 0, 110, 0, 111, 0, 112, 0, 113, 0, 114, 0, 115, 0, 116, 0, 117, 0, 118, 0, 7, 6, 18, 70, 195, 181, 0, 195, 164, 0, 195, 182, 0, 195, 188, 0, 97, 0, 101, 0, 105, 0, 108, 0, 109, 0, 110, 0, 111, 0, 114, 0, 117, 0, 7, 6, 195, 164, 0, 101, 2, 32, 3, 6, 119, 108, 0, 111, 3, 6, 119, 113, 0, 117, 2, 32, 3, 6, 119, 115, 0, 4, 195, 164, 1, 29, 2, 18, 67, 32, 3, 6, 119, 120, 0, 195, 164, 1, 29, 2, 32, 0, 195, 164, 3, 6, 120, 0, 105, 2, 32, 3, 6, 125, 12, 0, 3, 119, 0, 105, 3, 125, 0, 7, 6, 195, 181, 0, 97, 3, 6, 117, 106, 0, 101, 2, 32, 3, 6, 117, 108, 0, 105, 2, 32, 3, 6, 117, 110, 0, 111, 3, 6, 117, 113, 0, 117, 2, 32, 3, 6, 117, 115, 0, 4, 195, 181, 1, 29, 2, 18, 67, 32, 3, 6, 117, 118, 0, 195, 181, 1, 29, 2, 32, 0, 195, 181, 3, 6, 118, 0, 3, 117, 0, 117, 3, 117, 40, 0, 7, 6, 195, 182, 0, 97, 3, 6, 121, 106, 0, 101, 3, 6, 121, 108, 0, 4, 195, 182, 1, 29, 2, 18, 67, 32, 3, 6, 121, 122, 0, 195, 182, 1, 29, 2, 32, 0, 195, 182, 3, 6, 122, 0, 3, 121, 0, 105, 3, 126, 0, 7, 6, 195, 188, 0, 4, 195, 188, 1, 29, 2, 18, 67, 32, 3, 6, 123, 124, 0, 195, 188, 1, 29, 2, 32, 0, 195, 188, 3, 6, 124, 0, 3, 123, 0, 109, 98, 114, 105, 3, 123, 63, 69, 34, 37, 0, 4, 105, 3, 127, 0, 195, 188, 2, 106, 97, 0, 195, 188, 2, 97, 3, 127, 57, 0, 7, 6, 97, 0, 4, 97, 1, 29, 2, 18, 67, 32, 3, 6, 35, 106, 0, 97, 1, 29, 2, 32, 0, 101, 2, 32, 3, 6, 35, 108, 0, 105, 2, 32, 3, 6, 35, 110, 0, 111, 3, 6, 35, 113, 0, 117, 2, 32, 3, 6, 35, 115, 0, 97, 3, 6, 106, 0, 3, 35, 0, 109, 98, 105, 3, 35, 63, 69, 37, 0, 1, 105, 17, 65, 3, 57, 35, 0, 4, 1, 117, 97, 3, 58, 35, 0, 1, 117, 117, 0, 1, 117, 181, 195, 0, 4, 8, 18, 67, 17, 65, 2, 25, 3, 107, 0, 8, 18, 67, 17, 65, 17, 67, 2, 25, 0, 7, 6, 98, 0, 8, 3, 48, 0, 3, 69, 0, 7, 6, 99, 0, 4, 2, 101, 3, 47, 87, 0, 2, 105, 0, 3, 49, 0, 104, 8, 3, 74, 0, 8, 2, 101, 3, 87, 0, 105, 116, 121, 3, 87, 37, 47, 37, 0, 7, 6, 100, 0, 8, 3, 47, 0, 4, 3, 70, 0, 1, 21, 21, 2, 18, 66, 0, 1, 25, 2, 18, 66, 0, 1, 10, 2, 18, 66, 3, 131, 0, 7, 6, 101, 0, 97, 2, 32, 3, 6, 36, 106, 0, 4, 101, 1, 29, 2, 18, 67, 32, 3, 6, 36, 108, 0, 101, 1, 29, 2, 32, 0, 105, 2, 32, 3, 6, 36, 110, 0, 111, 3, 6, 36, 113, 0, 101, 3, 6, 108, 0, 3, 36, 0, 1, 105, 17, 65, 3, 57, 36, 0, 4, 1, 117, 97, 3, 58, 36, 0, 1, 117, 117, 0, 1, 117, 181, 195, 0, 4, 8, 18, 67, 17, 65, 2, 25, 3, 109, 0, 8, 18, 67, 17, 65, 17, 67, 2, 25, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 8, 3, 49, 0, 3, 79, 0, 7, 6, 104, 0, 3, 105, 0, 1, 97, 108, 2, 116, 105, 3, 105, 105, 0, 7, 6, 105, 0, 4, 105, 1, 29, 2, 18, 67, 32, 3, 6, 37, 110, 0, 105, 1, 29, 2, 32, 0, 105, 3, 6, 110, 0, 3, 37, 0, 4, 8, 18, 67, 17, 65, 2, 25, 3, 111, 0, 8, 18, 67, 17, 65, 17, 67, 2, 25, 0, 7, 6, 106, 0, 97, 122, 122, 3, 47, 88, 119, 87, 12, 0, 3, 57, 0, 106, 3, 57, 12, 0, 117, 109, 98, 117, 3, 57, 40, 63, 69, 40, 0, 7, 6, 107, 0, 3, 49, 0, 97, 117, 103, 101, 3, 49, 6, 35, 115, 79, 36, 0, 4, 1, 17, 65, 2, 18, 68, 3, 49, 12, 0, 1, 17, 65, 17, 65, 2, 18, 70, 0, 1, 18, 68, 17, 65, 2, 18, 70, 0, 107, 0, 97, 109, 98, 97, 3, 49, 35, 63, 69, 35, 0, 105, 109, 98, 97, 116, 117, 115, 3, 49, 37, 63, 69, 35, 47, 40, 87, 0, 105, 109, 98, 117, 3, 49, 37, 63, 69, 40, 0, 7, 6, 108, 0, 4, 3, 55, 0, 1, 21, 21, 2, 18, 66, 0, 1, 25, 2, 18, 66, 0, 4, 108, 1, 21, 21, 2, 105, 3, 55, 12, 0, 108, 1, 25, 2, 105, 0, 4, 1, 10, 2, 18, 66, 3, 61, 0, 1, 10, 2, 100, 18, 66, 0, 1, 10, 2, 103, 18, 66, 0, 1, 10, 2, 107, 18, 66, 0, 1, 10, 2, 110, 105, 0, 1, 10, 2, 115, 11, 105, 0, 1, 10, 2, 115, 105, 0, 1, 10, 2, 116, 105, 0, 2, 115, 115, 32, 0, 108, 1, 10, 2, 105, 3, 61, 12, 0, 108, 1, 17, 65, 2, 32, 3, 112, 61, 12, 0, 7, 6, 109, 0, 4, 3, 63, 0, 1, 10, 2, 98, 17, 65, 11, 0, 1, 10, 2, 98, 3, 63, 63, 0, 7, 6, 110, 0, 4, 3, 50, 0, 1, 17, 65, 10, 2, 108, 18, 66, 0, 1, 21, 21, 2, 18, 66, 0, 1, 25, 2, 18, 66, 0, 110, 1, 105, 2, 32, 3, 50, 12, 0, 4, 110, 1, 21, 21, 2, 105, 3, 50, 50, 0, 110, 1, 25, 2, 105, 0, 4, 1, 10, 2, 18, 66, 3, 65, 0, 1, 10, 2, 100, 18, 66, 0, 1, 10, 2, 115, 105, 0, 1, 10, 2, 116, 32, 0, 1, 10, 2, 116, 105, 0, 2, 115, 116, 32, 0, 110, 1, 10, 2, 105, 3, 65, 12, 0, 4, 2, 32, 103, 3, 66, 0, 2, 32, 107, 0, 2, 103, 0, 2, 107, 0, 110, 1, 17, 65, 2, 32, 3, 112, 65, 12, 0, 7, 6, 111, 0, 97, 3, 6, 39, 106, 0, 101, 2, 32, 3, 6, 39, 108, 0, 105, 2, 32, 3, 6, 39, 110, 0, 4, 111, 1, 29, 2, 18, 67, 32, 3, 6, 39, 113, 0, 111, 1, 29, 2, 32, 0, 111, 3, 6, 113, 0, 4, 3, 39, 0, 1, 105, 105, 0, 1, 105, 17, 65, 3, 57, 39, 0, 4, 8, 18, 67, 17, 65, 2, 25, 3, 114, 0, 8, 18, 67, 17, 65, 17, 67, 2, 25, 0, 7, 6, 112, 0, 3, 48, 0, 4, 1, 17, 65, 17, 65, 2, 18, 70, 3, 48, 12, 0, 1, 18, 68, 17, 65, 2, 32, 0, 112, 0, 7, 6, 113, 0, 3, 49, 0, 113, 3, 49, 12, 0, 117, 3, 49, 82, 0, 7, 6, 114, 0, 3, 34, 0, 4, 1, 101, 107, 2, 103, 101, 3, 51, 51, 0, 1, 181, 195, 107, 2, 103, 101, 0, 114, 0, 7, 6, 115, 0, 4, 3, 87, 0, 1, 10, 2, 108, 18, 66, 0, 1, 10, 2, 110, 18, 66, 0, 1, 21, 21, 2, 18, 66, 0, 1, 25, 2, 18, 66, 0, 195, 188, 109, 98, 111, 108, 105, 115, 101, 101, 114, 3, 87, 4, 123, 63, 69, 39, 55, 37, 87, 6, 108, 34, 0, 111, 109, 98, 117, 3, 87, 39, 63, 69, 40, 0, 4, 115, 1, 21, 21, 2, 105, 3, 87, 87, 0, 115, 1, 25, 2, 105, 0, 115, 3, 87, 128, 0, 4, 99, 104, 1, 25, 3, 89, 0, 104, 1, 25, 0, 115, 1, 17, 65, 2, 32, 3, 112, 129, 12, 0, 4, 1, 10, 2, 18, 66, 3, 129, 0, 1, 10, 2, 100, 105, 0, 1, 17, 65, 2, 116, 105, 0, 115, 1, 10, 2, 105, 3, 129, 129, 0, 7, 6, 116, 0, 4, 3, 47, 0, 1, 21, 21, 2, 18, 66, 0, 1, 21, 21, 2, 115, 105, 0, 1, 25, 2, 18, 66, 0, 4, 1, 17, 65, 2, 18, 68, 3, 47, 12, 0, 1, 17, 65, 17, 65, 2, 18, 70, 0, 1, 97, 109, 10, 2, 97, 32, 0, 116, 0, 116, 1, 21, 21, 2, 105, 0, 116, 1, 25, 2, 105, 0, 97, 109, 98, 117, 3, 47, 35, 63, 69, 40, 0, 117, 109, 98, 97, 3, 47, 40, 63, 69, 35, 0, 1, 17, 65, 10, 2, 115, 105, 3, 112, 130, 0, 116, 1, 17, 65, 29, 2, 32, 3, 112, 130, 12, 0, 4, 1, 10, 2, 18, 66, 3, 130, 0, 1, 10, 2, 108, 18, 66, 0, 1, 10, 2, 110, 18, 66, 0, 116, 1, 10, 2, 105, 3, 130, 12, 0, 7, 6, 117, 0, 105, 2, 32, 3, 6, 40, 110, 0, 4, 117, 1, 29, 2, 18, 67, 32, 3, 6, 40, 115, 0, 117, 1, 29, 2, 32, 0, 117, 3, 6, 115, 0, 4, 3, 40, 0, 1, 105, 105, 0, 1, 105, 17, 65, 3, 57, 40, 0, 4, 8, 18, 67, 17, 65, 2, 25, 3, 116, 0, 8, 18, 67, 17, 65, 17, 67, 2, 25, 0, 7, 6, 118, 0, 3, 82, 0, 97, 98, 97, 114, 105, 105, 3, 82, 6, 35, 69, 35, 34, 4, 37, 37, 0, 101, 109, 98, 117, 3, 82, 36, 63, 69, 40, 0, 7, 6, 119, 0, 3, 82, 0, 7, 6, 120, 0, 120, 3, 49, 12, 87, 0, 3, 49, 87, 0, 7, 6, 121, 0, 3, 37, 0, 105, 3, 57, 37, 0, 121, 3, 124, 0, 7, 6, 122, 0, 122, 3, 47, 87, 0, 3, 86, 0, 104, 1, 25, 3, 88, 0, 7, 6, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 45, 8, 32, 2, 32, 15, 3, 63, 110, 50, 40, 87, 0, 197, 190, 3, 88, 0, 197, 161, 3, 89, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts17 = FileInMemory_createWithData (6769, reinterpret_cast (&espeakdata_dicts17_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/et_dict", L"et"); Collection_addItem (me.peek(), espeakdata_dicts17.transfer()); static unsigned char espeakdata_dicts18_data[5131] = { 0, 4, 0, 0, 161, 16, 0, 0, 9, 198, 48, 145, 78, 20, 211, 69, 72, 0, 0, 0, 13, 67, 57, 35, 192, 50, 40, 63, 36, 34, 39, 0, 24, 0, 0, 6, 65, 4, 35, 12, 0, 0, 10, 135, 20, 195, 164, 12, 20, 195, 164, 76, 0, 0, 6, 195, 52, 83, 133, 19, 7, 196, 48, 21, 83, 20, 19, 0, 7, 65, 8, 69, 36, 12, 0, 0, 0, 16, 67, 21, 64, 192, 36, 47, 10, 87, 36, 47, 36, 34, 35, 0, 24, 0, 0, 7, 65, 12, 87, 36, 12, 0, 0, 0, 0, 0, 7, 65, 16, 70, 36, 12, 0, 0, 0, 0, 7, 196, 81, 83, 206, 4, 76, 0, 6, 65, 20, 36, 12, 0, 0, 0, 0, 0, 6, 65, 24, 107, 81, 0, 0, 0, 0, 0, 8, 197, 56, 242, 76, 48, 80, 76, 7, 65, 28, 79, 36, 12, 0, 0, 0, 0, 7, 196, 40, 243, 139, 4, 76, 0, 7, 65, 32, 105, 39, 12, 0, 0, 0, 0, 6, 195, 60, 148, 133, 19, 7, 196, 40, 243, 12, 4, 76, 7, 195, 37, 68, 197, 76, 19, 0, 6, 65, 36, 37, 12, 0, 0, 14, 1, 37, 48, 34, 39, 87, 36, 50, 47, 12, 106, 0, 27, 13, 1, 37, 48, 34, 39, 87, 36, 50, 47, 12, 37, 0, 0, 17, 70, 44, 243, 134, 85, 68, 197, 49, 39, 50, 81, 40, 47, 87, 36, 0, 7, 1, 38, 10, 36, 47, 0, 0, 0, 8, 197, 81, 83, 200, 60, 224, 76, 7, 65, 40, 57, 37, 12, 0, 0, 0, 14, 1, 42, 35, 87, 47, 36, 34, 37, 87, 49, 37, 0, 27, 0, 9, 1, 43, 48, 55, 40, 87, 0, 27, 0, 7, 65, 44, 49, 39, 12, 0, 0, 0, 0, 9, 1, 47, 49, 120, 47, 12, 35, 0, 0, 6, 65, 48, 107, 55, 0, 0, 0, 0, 12, 68, 64, 243, 12, 20, 48, 39, 55, 55, 36, 0, 7, 196, 40, 243, 12, 20, 76, 0, 6, 65, 52, 107, 63, 0, 0, 0, 0, 0, 6, 65, 56, 107, 50, 0, 0, 0, 0, 0, 6, 65, 60, 39, 12, 0, 0, 14, 1, 61, 6, 112, 105, 47, 107, 49, 6, 118, 50, 0, 27, 0, 0, 0, 7, 1, 64, 10, 107, 47, 0, 7, 65, 64, 48, 36, 12, 0, 0, 0, 0, 7, 196, 81, 83, 212, 4, 76, 0, 7, 65, 68, 49, 40, 12, 0, 0, 0, 0, 0, 6, 65, 72, 107, 34, 0, 0, 0, 0, 0, 6, 65, 76, 107, 87, 0, 0, 0, 0, 0, 7, 65, 80, 47, 36, 12, 0, 0, 0, 0, 12, 68, 64, 83, 12, 20, 48, 36, 55, 55, 36, 0, 0, 6, 65, 84, 40, 12, 0, 0, 0, 0, 0, 7, 65, 88, 82, 36, 12, 0, 0, 0, 0, 16, 4, 95, 49, 77, 52, 69, 6, 37, 55, 57, 39, 12, 50, 35, 0, 0, 8, 197, 60, 194, 77, 52, 80, 72, 8, 133, 13, 9, 14, 195, 164, 72, 8, 1, 92, 49, 36, 50, 39, 0, 13, 65, 92, 49, 35, 49, 87, 115, 87, 82, 36, 12, 0, 0, 0, 0, 0, 13, 4, 95, 49, 77, 49, 47, 6, 40, 105, 35, 47, 0, 7, 65, 96, 107, 49, 87, 0, 0, 6, 194, 4, 64, 17, 24, 16, 4, 95, 49, 77, 50, 63, 6, 37, 55, 57, 39, 12, 50, 35, 0, 0, 16, 4, 95, 49, 77, 51, 63, 6, 37, 55, 57, 35, 34, 70, 37, 0, 0, 7, 196, 81, 83, 210, 20, 19, 7, 196, 40, 243, 20, 4, 76, 0, 6, 65, 100, 112, 12, 0, 0, 0, 0, 0, 8, 65, 104, 47, 87, 36, 47, 0, 0, 0, 0, 0, 0, 16, 70, 77, 84, 193, 56, 225, 64, 87, 40, 87, 35, 50, 50, 36, 0, 0, 0, 0, 0, 6, 194, 12, 16, 17, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 1, 126, 47, 37, 55, 70, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 52, 19, 142, 20, 63, 35, 50, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 32, 147, 12, 20, 105, 37, 55, 55, 36, 0, 7, 196, 65, 84, 146, 4, 19, 0, 0, 0, 0, 0, 8, 197, 56, 242, 83, 80, 16, 76, 0, 0, 0, 7, 196, 60, 195, 21, 80, 72, 7, 196, 40, 244, 211, 4, 76, 0, 0, 0, 0, 11, 67, 4, 227, 133, 35, 50, 50, 36, 0, 41, 0, 0, 0, 0, 12, 68, 72, 148, 212, 36, 51, 37, 87, 47, 106, 0, 7, 196, 40, 244, 212, 4, 76, 0, 0, 0, 0, 12, 68, 40, 19, 142, 20, 57, 35, 50, 50, 36, 0, 0, 0, 0, 0, 7, 196, 65, 82, 197, 4, 19, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 56, 19, 12, 20, 50, 35, 55, 55, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 14, 195, 164, 9, 20, 195, 164, 76, 0, 0, 0, 0, 0, 12, 68, 72, 20, 212, 36, 51, 35, 87, 47, 106, 0, 12, 68, 44, 244, 212, 36, 49, 39, 87, 47, 106, 0, 0, 0, 0, 6, 195, 80, 16, 64, 19, 0, 12, 68, 32, 19, 142, 20, 105, 35, 50, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 92, 147, 12, 20, 82, 37, 55, 55, 36, 0, 12, 68, 88, 147, 12, 20, 82, 37, 55, 55, 36, 0, 12, 68, 44, 19, 12, 20, 49, 35, 55, 55, 36, 0, 0, 8, 197, 40, 242, 76, 48, 16, 76, 8, 197, 56, 242, 76, 80, 16, 76, 0, 0, 7, 195, 80, 18, 64, 72, 8, 0, 13, 4, 95, 4, 16, 20, 48, 37, 55, 49, 12, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 20, 12, 4, 47, 37, 55, 70, 36, 0, 12, 3, 95, 35, 57, 87, 35, 34, 49, 113, 50, 0, 0, 8, 197, 56, 242, 72, 36, 224, 76, 0, 0, 0, 0, 0, 5, 194, 21, 64, 72, 0, 0, 0, 8, 197, 60, 194, 86, 5, 64, 72, 0, 0, 0, 0, 0, 0, 0, 7, 196, 49, 83, 196, 20, 19, 0, 8, 197, 60, 193, 84, 80, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 20, 195, 164, 13, 195, 164, 76, 0, 0, 9, 67, 60, 176, 89, 39, 49, 116, 0, 0, 0, 0, 0, 0, 12, 68, 64, 244, 212, 36, 48, 39, 87, 47, 106, 0, 0, 0, 0, 0, 0, 0, 11, 136, 14, 195, 164, 9, 20, 20, 5, 14, 76, 0, 0, 0, 0, 0, 0, 0, 0, 17, 66, 20, 112, 36, 87, 37, 63, 36, 34, 49, 37, 49, 87, 37, 0, 24, 0, 0, 0, 8, 197, 40, 242, 76, 48, 80, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 88, 83, 133, 19, 7, 195, 60, 195, 1, 72, 19, 9, 198, 56, 242, 84, 80, 83, 128, 76, 0, 0, 0, 17, 70, 65, 35, 205, 36, 195, 5, 48, 51, 39, 63, 106, 55, 55, 36, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 40, 242, 15, 56, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 20, 144, 72, 0, 0, 12, 68, 28, 19, 12, 20, 79, 35, 55, 55, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 20, 195, 164, 14, 195, 164, 76, 0, 0, 0, 0, 0, 6, 195, 60, 194, 84, 72, 0, 11, 136, 14, 195, 164, 9, 19, 19, 195, 164, 76, 0, 0, 0, 0, 0, 0, 0, 7, 195, 40, 225, 64, 17, 24, 9, 3, 226, 130, 172, 122, 34, 39, 0, 10, 3, 226, 130, 172, 122, 34, 39, 35, 0, 0, 0, 0, 15, 7, 18, 25, 195, 182, 19, 20, 9, 51, 130, 87, 47, 106, 0, 0, 7, 195, 60, 193, 64, 72, 19, 0, 0, 0, 6, 194, 40, 16, 72, 8, 5, 194, 32, 80, 72, 0, 17, 8, 16, 195, 164, 195, 164, 19, 20, 9, 48, 107, 12, 87, 47, 106, 0, 0, 0, 23, 73, 76, 148, 139, 85, 52, 5, 48, 193, 64, 87, 37, 51, 49, 40, 87, 48, 36, 55, 55, 36, 0, 0, 0, 6, 195, 60, 194, 64, 72, 0, 0, 0, 6, 195, 36, 131, 69, 19, 0, 0, 0, 6, 195, 60, 194, 78, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 56, 242, 68, 20, 224, 76, 0, 0, 0, 0, 16, 69, 100, 241, 213, 73, 64, 57, 39, 79, 40, 34, 47, 12, 37, 0, 0, 0, 0, 0, 9, 198, 60, 194, 83, 37, 69, 5, 72, 0, 6, 194, 20, 208, 17, 24, 0, 0, 0, 6, 195, 60, 193, 78, 72, 0, 0, 0, 0, 8, 197, 81, 83, 211, 80, 16, 76, 0, 0, 6, 195, 60, 193, 84, 72, 0, 0, 0, 0, 0, 0, 0, 5, 194, 20, 224, 72, 0, 6, 195, 61, 64, 64, 19, 20, 3, 95, 51, 88, 49, 6, 39, 55, 63, 36, 49, 112, 63, 63, 36, 50, 47, 107, 0, 0, 13, 3, 95, 48, 67, 87, 6, 35, 47, 35, 12, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 67, 87, 6, 35, 47, 35, 0, 0, 0, 0, 0, 0, 0, 6, 195, 4, 146, 5, 19, 21, 3, 95, 49, 57, 6, 112, 105, 70, 36, 49, 87, 107, 50, 47, 4, 115, 87, 47, 35, 0, 0, 22, 3, 95, 49, 56, 49, 6, 35, 105, 70, 36, 49, 87, 35, 50, 47, 4, 115, 87, 47, 35, 0, 0, 0, 0, 0, 0, 0, 8, 197, 44, 146, 78, 56, 144, 19, 8, 197, 81, 83, 211, 76, 16, 76, 0, 16, 3, 95, 49, 49, 6, 112, 49, 87, 37, 47, 115, 87, 47, 35, 0, 0, 6, 195, 57, 83, 192, 76, 15, 3, 95, 49, 48, 49, 6, 112, 63, 63, 36, 50, 36, 50, 0, 0, 17, 3, 95, 49, 51, 49, 6, 39, 55, 63, 36, 47, 115, 87, 47, 35, 0, 0, 17, 3, 95, 49, 50, 49, 6, 35, 49, 87, 37, 47, 115, 87, 47, 35, 0, 0, 15, 7, 11, 25, 195, 182, 19, 20, 9, 49, 130, 87, 47, 106, 0, 17, 3, 95, 49, 53, 82, 6, 37, 12, 87, 37, 47, 115, 87, 47, 35, 0, 0, 17, 3, 95, 49, 52, 50, 6, 36, 55, 57, 107, 47, 115, 87, 47, 35, 0, 0, 21, 3, 95, 49, 55, 87, 6, 116, 47, 87, 36, 63, 107, 50, 47, 4, 115, 87, 47, 35, 0, 0, 17, 3, 95, 49, 54, 49, 6, 40, 12, 87, 37, 47, 115, 87, 47, 35, 0, 0, 0, 10, 135, 20, 195, 164, 19, 19, 195, 164, 76, 24, 3, 95, 55, 88, 87, 6, 116, 47, 87, 36, 63, 107, 66, 49, 4, 112, 63, 63, 36, 50, 47, 107, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 40, 245, 1, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 50, 88, 49, 6, 35, 49, 87, 37, 49, 112, 63, 63, 36, 50, 47, 107, 0, 0, 0, 0, 0, 0, 11, 136, 14, 195, 164, 9, 12, 12, 195, 164, 76, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 63, 63, 63, 6, 36, 34, 49, 12, 106, 0, 0, 0, 0, 20, 3, 95, 52, 88, 50, 6, 36, 55, 57, 107, 49, 112, 63, 63, 36, 50, 47, 107, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 53, 88, 82, 6, 37, 12, 87, 37, 49, 112, 63, 63, 36, 50, 47, 107, 0, 0, 0, 8, 197, 40, 242, 76, 80, 16, 76, 0, 0, 0, 0, 0, 0, 20, 3, 95, 54, 88, 49, 6, 40, 12, 87, 37, 49, 112, 63, 63, 36, 50, 47, 107, 0, 0, 0, 0, 0, 0, 0, 10, 135, 20, 195, 164, 8, 195, 164, 14, 76, 0, 0, 10, 135, 20, 195, 164, 12, 12, 195, 164, 76, 10, 135, 20, 195, 164, 19, 20, 195, 164, 76, 0, 7, 196, 61, 65, 84, 4, 19, 0, 0, 0, 0, 7, 196, 65, 81, 84, 4, 19, 0, 0, 10, 135, 14, 195, 164, 9, 12, 12, 5, 76, 0, 25, 3, 95, 56, 88, 49, 6, 35, 105, 70, 36, 49, 87, 35, 66, 49, 4, 112, 63, 63, 36, 50, 47, 107, 0, 0, 0, 0, 7, 132, 8, 195, 164, 14, 72, 0, 0, 0, 0, 5, 194, 52, 80, 72, 0, 24, 3, 95, 57, 88, 6, 112, 105, 70, 36, 49, 87, 107, 66, 49, 4, 112, 63, 63, 36, 50, 47, 107, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 45, 144, 17, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 14, 195, 164, 9, 19, 20, 195, 164, 76, 0, 7, 196, 81, 83, 12, 4, 19, 0, 0, 0, 0, 7, 196, 81, 83, 142, 20, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 56, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 61, 48, 17, 24, 0, 0, 6, 195, 40, 243, 129, 76, 17, 4, 95, 48, 77, 52, 69, 6, 37, 55, 57, 39, 12, 50, 35, 12, 0, 0, 0, 17, 4, 95, 48, 77, 50, 63, 6, 37, 55, 57, 39, 12, 50, 35, 12, 0, 0, 17, 4, 95, 48, 77, 51, 63, 6, 37, 55, 57, 35, 34, 70, 37, 35, 0, 0, 0, 15, 4, 95, 48, 77, 49, 47, 6, 40, 105, 35, 47, 12, 35, 0, 0, 13, 4, 95, 2, 18, 22, 69, 34, 6, 36, 82, 36, 0, 0, 0, 7, 196, 40, 242, 84, 4, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 14, 195, 164, 13, 195, 164, 76, 0, 0, 0, 0, 0, 6, 195, 4, 160, 64, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 48, 145, 78, 21, 64, 72, 0, 0, 9, 198, 48, 145, 78, 21, 69, 5, 72, 0, 6, 195, 40, 242, 193, 76, 0, 0, 0, 0, 0, 8, 197, 60, 193, 77, 52, 80, 72, 10, 135, 14, 195, 164, 9, 4, 5, 14, 76, 0, 0, 0, 0, 0, 21, 4, 95, 3, 9, 18, 87, 6, 37, 34, 49, 40, 63, 81, 55, 4, 36, 49, 87, 106, 0, 0, 0, 7, 196, 60, 194, 83, 36, 72, 0, 0, 9, 134, 13, 5, 14, 14, 195, 164, 19, 0, 0, 0, 0, 0, 9, 134, 20, 195, 164, 12, 12, 5, 76, 0, 0, 8, 197, 40, 242, 68, 20, 224, 76, 0, 0, 0, 0, 15, 4, 95, 1, 3, 21, 6, 35, 49, 40, 12, 47, 12, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 48, 145, 78, 20, 80, 72, 0, 5, 194, 61, 144, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 80, 84, 150, 20, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 66, 60, 176, 6, 39, 12, 10, 4, 49, 39, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 70, 64, 83, 1, 77, 66, 64, 48, 36, 55, 35, 87, 47, 106, 0, 0, 0, 7, 196, 40, 245, 11, 4, 76, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 65, 148, 212, 36, 48, 112, 87, 47, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 80, 72, 13, 2, 194, 164, 82, 35, 55, 40, 12, 47, 12, 35, 0, 0, 0, 0, 8, 197, 40, 242, 83, 76, 16, 76, 8, 197, 81, 83, 204, 48, 16, 76, 10, 2, 194, 163, 48, 40, 50, 47, 35, 0, 0, 0, 6, 195, 61, 96, 84, 72, 0, 0, 0, 9, 198, 60, 194, 83, 37, 96, 84, 72, 7, 2, 195, 164, 107, 12, 0, 0, 19, 2, 195, 165, 34, 6, 128, 47, 87, 35, 55, 113, 50, 36, 50, 6, 39, 12, 0, 0, 0, 0, 14, 2, 195, 160, 6, 35, 55, 35, 0, 24, 81, 108, 97, 32, 0, 0, 0, 0, 5, 194, 60, 224, 72, 9, 134, 20, 195, 164, 20, 195, 164, 76, 0, 6, 195, 4, 32, 192, 17, 0, 0, 0, 0, 0, 7, 196, 4, 161, 84, 4, 19, 7, 2, 195, 182, 109, 12, 0, 0, 0, 0, 0, 15, 4, 95, 3, 5, 4, 87, 6, 36, 70, 106, 55, 57, 106, 0, 0, 0, 17, 70, 100, 241, 200, 85, 37, 0, 57, 39, 79, 40, 34, 47, 12, 37, 0, 0, 13, 2, 197, 161, 105, 6, 35, 47, 12, 40, 107, 87, 0, 0, 7, 196, 88, 148, 139, 20, 19, 0, 0, 5, 194, 80, 80, 72, 0, 0, 7, 196, 56, 242, 78, 4, 76, 0, 0, 0, 7, 195, 88, 18, 64, 72, 8, 0, 6, 195, 65, 82, 5, 19, 0, 0, 0, 0, 6, 195, 81, 83, 5, 19, 0, 0, 0, 9, 198, 60, 194, 83, 36, 211, 69, 72, 0, 16, 2, 197, 190, 105, 6, 35, 47, 12, 40, 47, 87, 4, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 48, 145, 78, 20, 224, 72, 0, 0, 17, 70, 64, 144, 78, 37, 53, 9, 48, 37, 35, 50, 37, 87, 47, 106, 0, 0, 0, 10, 135, 22, 195, 164, 8, 195, 164, 14, 76, 0, 0, 0, 6, 195, 5, 53, 5, 19, 0, 0, 0, 0, 7, 196, 40, 242, 78, 4, 76, 0, 8, 197, 60, 194, 84, 80, 80, 72, 8, 197, 81, 83, 204, 48, 80, 76, 0, 0, 0, 7, 196, 88, 148, 136, 20, 19, 0, 10, 135, 14, 195, 164, 9, 8, 9, 14, 76, 0, 9, 134, 5, 9, 22, 195, 164, 20, 72, 0, 0, 0, 12, 137, 12, 9, 5, 14, 5, 22, 195, 164, 20, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 65, 81, 64, 19, 0, 0, 0, 7, 132, 19, 25, 195, 182, 19, 0, 0, 0, 0, 0, 0, 7, 196, 48, 18, 84, 20, 19, 0, 16, 70, 88, 149, 76, 37, 53, 9, 82, 123, 55, 106, 87, 47, 106, 0, 0, 0, 6, 195, 4, 66, 4, 17, 9, 2, 95, 35, 34, 37, 87, 40, 0, 0, 10, 2, 95, 34, 55, 113, 50, 120, 87, 0, 0, 8, 197, 5, 85, 5, 80, 16, 19, 16, 2, 95, 33, 105, 40, 12, 47, 39, 63, 36, 34, 49, 12, 37, 0, 0, 0, 10, 2, 95, 39, 105, 116, 47, 12, 39, 0, 0, 13, 2, 95, 38, 36, 47, 63, 36, 34, 49, 12, 37, 0, 0, 14, 2, 95, 37, 48, 34, 39, 87, 36, 50, 47, 12, 37, 0, 0, 6, 195, 44, 243, 133, 19, 9, 198, 48, 145, 78, 56, 81, 84, 72, 13, 2, 95, 36, 70, 39, 55, 55, 35, 34, 37, 50, 0, 0, 0, 11, 4, 95, 3, 1, 16, 6, 37, 87, 39, 0, 0, 15, 2, 95, 41, 55, 39, 48, 12, 40, 87, 40, 55, 49, 40, 0, 0, 14, 2, 95, 40, 35, 55, 49, 40, 87, 40, 55, 49, 40, 0, 0, 7, 195, 20, 180, 128, 17, 24, 0, 10, 2, 95, 46, 48, 37, 87, 47, 36, 0, 0, 10, 2, 95, 45, 82, 37, 12, 82, 35, 0, 0, 0, 11, 2, 95, 51, 49, 6, 39, 55, 63, 36, 0, 0, 11, 2, 95, 50, 49, 6, 35, 49, 87, 37, 0, 0, 10, 2, 95, 49, 6, 112, 49, 87, 37, 0, 0, 11, 2, 95, 48, 50, 6, 39, 55, 55, 35, 0, 0, 14, 2, 95, 55, 87, 6, 116, 47, 87, 36, 63, 107, 50, 0, 0, 11, 2, 95, 54, 49, 6, 40, 12, 87, 37, 0, 0, 8, 197, 60, 194, 83, 37, 64, 72, 11, 2, 95, 53, 82, 6, 37, 12, 87, 37, 0, 0, 11, 2, 95, 52, 50, 6, 36, 55, 57, 107, 0, 0, 0, 16, 2, 95, 58, 49, 35, 49, 87, 115, 87, 48, 37, 87, 47, 36, 0, 0, 8, 197, 60, 195, 5, 21, 64, 72, 14, 2, 95, 57, 6, 112, 105, 70, 36, 49, 87, 107, 50, 0, 0, 15, 2, 95, 56, 49, 6, 35, 105, 70, 36, 49, 87, 35, 50, 0, 0, 18, 2, 95, 63, 49, 112, 87, 112, 63, 112, 87, 63, 36, 34, 49, 12, 106, 0, 0, 18, 2, 95, 62, 87, 6, 40, 12, 34, 36, 63, 48, 106, 49, 6, 118, 50, 0, 0, 0, 17, 2, 95, 60, 48, 6, 129, 50, 36, 63, 48, 106, 49, 6, 118, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 14, 195, 164, 9, 14, 195, 164, 76, 0, 0, 8, 133, 19, 9, 14, 195, 164, 72, 0, 0, 0, 0, 0, 0, 0, 7, 196, 65, 84, 138, 20, 19, 0, 0, 0, 0, 0, 0, 0, 13, 2, 95, 91, 35, 55, 49, 40, 105, 35, 49, 35, 0, 0, 0, 0, 0, 13, 2, 95, 95, 35, 55, 35, 82, 37, 12, 82, 35, 0, 0, 0, 14, 2, 95, 93, 55, 39, 48, 12, 40, 105, 35, 49, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 70, 52, 20, 137, 4, 227, 133, 63, 35, 51, 106, 35, 50, 50, 36, 0, 0, 14, 4, 95, 7, 18, 22, 79, 34, 6, 35, 82, 106, 87, 0, 0, 0, 0, 0, 6, 195, 65, 84, 133, 19, 0, 0, 0, 0, 6, 195, 21, 69, 5, 72, 0, 0, 0, 0, 0, 13, 4, 95, 4, 9, 1, 6, 40, 63, 55, 120, 47, 0, 14, 2, 95, 123, 35, 55, 49, 40, 35, 12, 55, 47, 39, 0, 0, 0, 0, 0, 0, 0, 15, 2, 95, 125, 55, 39, 48, 12, 40, 35, 12, 55, 47, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 81, 83, 206, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 4, 95, 35, 51, 50, 82, 107, 55, 37, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 40, 242, 83, 80, 16, 76, 0, 16, 70, 88, 20, 129, 77, 66, 64, 82, 35, 51, 35, 87, 47, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 49, 83, 192, 19, 6, 195, 81, 83, 192, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 44, 84, 212, 36, 49, 36, 87, 47, 106, 0, 12, 68, 44, 20, 212, 36, 49, 35, 87, 47, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 56, 242, 83, 76, 16, 76, 8, 197, 81, 83, 204, 80, 16, 76, 0, 16, 70, 65, 84, 137, 77, 66, 64, 48, 40, 51, 106, 87, 47, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 196, 48, 145, 78, 20, 72, 19, 8, 196, 53, 85, 20, 4, 76, 8, 11, 136, 14, 195, 164, 9, 12, 20, 195, 164, 76, 0, 8, 197, 60, 194, 83, 36, 224, 72, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 20, 195, 164, 13, 195, 164, 14, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 56, 242, 76, 48, 16, 76, 0, 0, 0, 0, 9, 133, 5, 14, 20, 195, 164, 72, 8, 0, 6, 195, 20, 211, 69, 72, 0, 0, 0, 0, 0, 10, 135, 19, 25, 195, 182, 4, 195, 164, 19, 0, 0, 9, 134, 14, 195, 164, 25, 20, 5, 19, 0, 0, 0, 0, 8, 197, 40, 242, 72, 36, 224, 76, 0, 6, 195, 5, 85, 1, 19, 0, 0, 0, 0, 0, 18, 71, 45, 83, 135, 25, 85, 19, 20, 49, 40, 66, 81, 40, 47, 87, 36, 0, 0, 0, 0, 16, 66, 100, 208, 112, 50, 50, 107, 10, 63, 40, 12, 47, 35, 0, 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 164, 0, 1, 10, 2, 108, 108, 97, 32, 3, 2, 107, 0, 3, 107, 0, 195, 164, 3, 107, 12, 0, 105, 105, 3, 107, 37, 12, 0, 121, 121, 3, 107, 112, 12, 0, 105, 3, 114, 0, 121, 3, 124, 0, 7, 6, 195, 182, 0, 3, 109, 0, 195, 182, 3, 109, 12, 0, 105, 105, 3, 109, 37, 12, 0, 121, 121, 3, 109, 112, 12, 0, 105, 3, 117, 0, 121, 3, 126, 0, 7, 6, 97, 0, 1, 10, 2, 108, 108, 97, 32, 3, 2, 35, 0, 3, 35, 0, 4, 8, 114, 116, 115, 117, 97, 2, 108, 3, 35, 12, 0, 97, 0, 105, 105, 3, 35, 37, 12, 0, 117, 117, 3, 35, 40, 12, 0, 105, 3, 113, 0, 117, 3, 120, 0, 7, 6, 98, 0, 3, 69, 0, 98, 3, 69, 12, 0, 7, 6, 99, 0, 4, 3, 49, 0, 104, 1, 25, 2, 114, 0, 99, 3, 49, 12, 0, 4, 2, 101, 3, 87, 0, 2, 105, 0, 2, 121, 0, 105, 116, 121, 3, 87, 37, 47, 37, 0, 7, 6, 100, 0, 3, 70, 0, 100, 3, 70, 12, 0, 7, 6, 101, 0, 4, 1, 10, 2, 108, 108, 97, 32, 3, 2, 36, 0, 1, 10, 2, 108, 108, 195, 164, 32, 0, 3, 36, 0, 101, 3, 36, 12, 0, 105, 105, 3, 36, 37, 12, 0, 117, 117, 3, 36, 40, 12, 0, 121, 121, 3, 36, 112, 12, 0, 105, 3, 116, 0, 117, 3, 122, 0, 121, 3, 125, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 3, 79, 0, 103, 3, 79, 12, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 1, 10, 2, 108, 108, 97, 32, 3, 2, 37, 0, 3, 37, 0, 105, 3, 37, 12, 0, 101, 101, 3, 37, 36, 12, 0, 117, 117, 3, 37, 40, 12, 0, 121, 121, 3, 37, 112, 12, 0, 117, 3, 123, 0, 121, 3, 127, 0, 101, 3, 129, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 3, 49, 0, 107, 3, 49, 12, 0, 7, 6, 108, 0, 3, 55, 0, 108, 101, 1, 21, 2, 32, 3, 55, 55, 36, 22, 0, 7, 6, 109, 0, 3, 63, 0, 8, 164, 195, 100, 121, 115, 2, 17, 65, 3, 63, 12, 0, 7, 6, 110, 0, 3, 50, 0, 110, 101, 1, 21, 2, 32, 3, 50, 50, 36, 22, 0, 4, 2, 32, 112, 3, 63, 0, 2, 112, 0, 4, 2, 32, 107, 3, 66, 0, 2, 107, 0, 103, 2, 25, 0, 103, 3, 66, 12, 0, 7, 6, 111, 0, 4, 3, 39, 0, 1, 98, 109, 121, 115, 2, 108, 111, 105, 0, 4, 1, 98, 109, 121, 115, 2, 108, 3, 39, 12, 0, 111, 0, 105, 105, 3, 39, 37, 12, 0, 117, 117, 3, 39, 40, 12, 0, 105, 3, 115, 0, 117, 3, 121, 0, 7, 6, 112, 0, 3, 48, 0, 4, 1, 109, 97, 104, 115, 2, 111, 3, 48, 12, 0, 1, 109, 97, 107, 2, 97, 110, 106, 0, 8, 97, 116, 111, 2, 97, 0, 8, 101, 108, 111, 2, 97, 0, 112, 0, 7, 6, 113, 0, 3, 49, 0, 113, 3, 49, 12, 0, 7, 6, 114, 0, 3, 34, 0, 7, 6, 115, 0, 3, 87, 0, 116, 105, 1, 17, 65, 2, 32, 3, 87, 47, 37, 22, 0, 4, 104, 1, 21, 2, 97, 110, 32, 3, 87, 105, 0, 104, 1, 21, 2, 195, 164, 110, 32, 0, 115, 3, 87, 131, 0, 4, 99, 104, 1, 25, 3, 89, 0, 104, 1, 25, 0, 7, 6, 116, 0, 3, 47, 0, 116, 3, 47, 12, 0, 122, 3, 47, 87, 0, 115, 101, 1, 21, 2, 32, 3, 47, 87, 36, 22, 0, 7, 6, 117, 0, 3, 40, 0, 117, 3, 40, 12, 0, 105, 105, 3, 40, 37, 12, 0, 111, 111, 3, 40, 39, 12, 0, 105, 3, 58, 37, 0, 4, 105, 8, 3, 118, 0, 105, 8, 106, 0, 111, 3, 128, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 82, 0, 7, 6, 120, 0, 120, 3, 49, 12, 87, 0, 3, 49, 87, 0, 7, 6, 121, 0, 3, 112, 0, 121, 3, 112, 12, 0, 105, 105, 3, 112, 37, 12, 0, 195, 182, 195, 182, 3, 112, 109, 12, 0, 105, 3, 119, 0, 195, 182, 3, 130, 0, 7, 6, 122, 0, 4, 3, 47, 87, 0, 122, 0, 104, 1, 25, 3, 88, 0, 7, 6, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 195, 165, 3, 39, 0, 195, 165, 195, 165, 3, 39, 12, 0, 45, 8, 32, 2, 32, 15, 3, 63, 37, 12, 50, 40, 87, 0, 36, 3, 70, 39, 55, 55, 35, 34, 37, 50, 0, 197, 190, 3, 88, 0, 197, 161, 3, 89, 0, 195, 188, 3, 112, 0, 195, 188, 195, 188, 3, 112, 12, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts18 = FileInMemory_createWithData (5130, reinterpret_cast (&espeakdata_dicts18_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/fi_dict", L"fi"); Collection_addItem (me.peek(), espeakdata_dicts18.transfer()); static unsigned char espeakdata_dicts19_data[21421] = { 0, 4, 0, 0, 100, 43, 0, 0, 0, 0, 0, 8, 67, 69, 82, 84, 21, 0, 10, 8, 67, 21, 81, 64, 109, 0, 76, 0, 0, 7, 65, 4, 35, 0, 14, 9, 5, 193, 4, 76, 36, 6, 65, 4, 35, 0, 76, 0, 13, 70, 12, 243, 150, 20, 229, 0, 49, 114, 82, 111, 0, 0, 0, 0, 6, 65, 8, 69, 36, 0, 0, 0, 6, 195, 85, 64, 192, 17, 6, 195, 57, 50, 64, 17, 14, 67, 21, 64, 192, 110, 47, 87, 36, 47, 36, 34, 35, 0, 0, 0, 6, 65, 12, 87, 36, 0, 0, 15, 70, 16, 244, 16, 48, 84, 128, 70, 125, 48, 55, 110, 34, 0, 0, 6, 195, 69, 81, 64, 76, 12, 4, 95, 8, 1, 3, 49, 35, 34, 6, 114, 0, 0, 0, 6, 65, 16, 70, 36, 0, 0, 6, 195, 76, 19, 147, 76, 0, 11, 67, 69, 82, 68, 49, 58, 37, 70, 0, 76, 0, 0, 6, 195, 64, 245, 82, 76, 14, 65, 20, 101, 98, 97, 121, 0, 29, 81, 98, 97, 121, 32, 6, 65, 20, 11, 13, 0, 0, 9, 67, 21, 81, 83, 109, 141, 0, 76, 0, 7, 195, 69, 82, 64, 32, 76, 0, 0, 7, 65, 24, 11, 110, 81, 0, 0, 0, 21, 67, 80, 245, 84, 47, 40, 55, 47, 111, 0, 82, 108, 101, 32, 116, 101, 109, 112, 115, 32, 22, 67, 80, 245, 84, 47, 40, 55, 63, 114, 70, 0, 82, 108, 101, 32, 109, 111, 110, 100, 101, 32, 11, 67, 80, 245, 84, 47, 6, 40, 138, 0, 76, 10, 199, 64, 197, 83, 36, 85, 82, 76, 76, 0, 0, 14, 69, 12, 19, 153, 60, 224, 49, 35, 50, 57, 125, 50, 0, 16, 65, 28, 88, 37, 79, 35, 110, 34, 47, 87, 0, 81, 104, 122, 32, 6, 65, 28, 88, 36, 0, 0, 16, 70, 16, 84, 142, 36, 84, 128, 70, 110, 34, 50, 57, 36, 118, 0, 0, 9, 67, 29, 147, 64, 88, 37, 63, 0, 9, 67, 28, 147, 128, 73, 37, 50, 0, 7, 195, 80, 243, 128, 72, 34, 0, 0, 7, 65, 32, 11, 35, 89, 0, 0, 6, 195, 80, 245, 83, 76, 0, 0, 0, 6, 65, 36, 11, 37, 0, 0, 8, 66, 37, 0, 37, 48, 36, 0, 10, 1, 37, 48, 40, 34, 87, 111, 0, 27, 0, 6, 195, 12, 20, 128, 37, 6, 195, 12, 20, 128, 72, 7, 1, 38, 36, 0, 72, 28, 0, 0, 11, 70, 56, 147, 148, 20, 225, 15, 21, 0, 10, 6, 65, 40, 88, 37, 0, 0, 15, 70, 77, 67, 195, 44, 84, 128, 87, 47, 39, 49, 36, 118, 0, 18, 8, 16, 15, 11, 195, 169, 13, 15, 14, 48, 39, 49, 36, 63, 125, 50, 0, 0, 8, 67, 76, 148, 128, 21, 0, 10, 10, 67, 16, 243, 148, 70, 114, 138, 0, 72, 14, 1, 42, 35, 87, 47, 36, 34, 37, 87, 49, 12, 0, 27, 0, 19, 9, 195, 169, 22, 9, 20, 9, 15, 14, 19, 36, 82, 37, 47, 57, 114, 141, 0, 12, 68, 52, 81, 9, 4, 63, 36, 70, 57, 35, 0, 9, 1, 43, 48, 55, 109, 87, 0, 27, 0, 6, 65, 44, 49, 35, 0, 0, 15, 7, 195, 169, 20, 9, 15, 14, 19, 36, 47, 57, 114, 141, 0, 0, 0, 8, 67, 25, 35, 205, 21, 0, 10, 3, 129, 47, 0, 7, 65, 48, 11, 110, 55, 0, 0, 23, 1, 49, 48, 34, 13, 63, 57, 110, 34, 63, 111, 0, 81, 195, 168, 114, 101, 109, 101, 110, 116, 32, 19, 1, 49, 48, 34, 13, 63, 57, 110, 34, 141, 0, 81, 195, 168, 114, 101, 115, 32, 17, 1, 49, 48, 34, 13, 63, 57, 110, 34, 0, 81, 195, 168, 114, 101, 32, 16, 1, 49, 48, 34, 13, 63, 57, 36, 141, 0, 81, 101, 114, 115, 32, 15, 1, 49, 48, 34, 13, 63, 57, 36, 118, 0, 81, 101, 114, 32, 16, 70, 69, 81, 76, 69, 81, 64, 49, 110, 55, 49, 8, 13, 0, 76, 0, 10, 67, 44, 20, 148, 49, 35, 34, 47, 0, 6, 195, 69, 81, 76, 76, 0, 7, 196, 80, 83, 12, 20, 76, 0, 7, 65, 52, 11, 110, 63, 0, 0, 9, 67, 52, 83, 147, 63, 111, 141, 0, 17, 66, 53, 0, 23, 110, 63, 48, 36, 47, 34, 58, 35, 0, 81, 51, 32, 0, 0, 9, 196, 48, 85, 82, 76, 72, 36, 40, 8, 196, 48, 85, 82, 76, 76, 34, 0, 9, 5, 95, 48, 1, 14, 4, 36, 0, 7, 65, 56, 11, 110, 50, 0, 0, 0, 0, 0, 14, 69, 64, 19, 1, 61, 48, 48, 35, 55, 35, 125, 87, 0, 6, 65, 60, 11, 39, 0, 0, 8, 67, 28, 20, 147, 79, 35, 0, 6, 195, 57, 50, 83, 17, 0, 0, 9, 133, 195, 170, 20, 5, 19, 76, 36, 0, 11, 1, 64, 24, 35, 34, 39, 69, 35, 86, 0, 6, 65, 64, 48, 36, 0, 0, 9, 198, 21, 84, 211, 20, 229, 0, 76, 0, 0, 0, 14, 6, 8, 195, 169, 12, 1, 19, 36, 55, 35, 87, 0, 76, 6, 65, 68, 49, 109, 0, 0, 0, 0, 0, 20, 5, 22, 9, 195, 170, 20, 82, 57, 110, 47, 50, 35, 63, 0, 81, 110, 97, 109, 32, 14, 69, 16, 80, 137, 4, 224, 70, 36, 69, 57, 35, 50, 0, 7, 65, 72, 11, 110, 34, 0, 0, 13, 70, 12, 128, 82, 48, 84, 192, 89, 35, 34, 55, 0, 0, 0, 0, 18, 9, 13, 15, 14, 20, 18, 195, 169, 1, 12, 63, 114, 34, 36, 35, 55, 0, 10, 5, 1, 15, 195, 187, 20, 40, 47, 0, 7, 65, 76, 11, 110, 87, 0, 0, 0, 7, 195, 84, 225, 64, 34, 76, 0, 0, 14, 65, 80, 21, 0, 10, 81, 115, 104, 105, 114, 116, 115, 32, 13, 65, 80, 21, 0, 10, 81, 115, 104, 105, 114, 116, 32, 11, 69, 5, 85, 133, 57, 64, 39, 82, 111, 0, 0, 5, 194, 4, 48, 17, 0, 6, 195, 12, 147, 192, 17, 0, 11, 68, 52, 145, 85, 96, 63, 37, 130, 0, 76, 0, 20, 73, 9, 32, 90, 104, 21, 137, 48, 193, 64, 69, 34, 35, 86, 35, 82, 37, 55, 0, 6, 65, 84, 11, 109, 0, 0, 7, 66, 85, 0, 21, 0, 10, 0, 0, 0, 6, 65, 88, 82, 36, 0, 0, 15, 70, 44, 225, 83, 76, 85, 0, 49, 50, 36, 87, 110, 47, 0, 12, 66, 5, 48, 35, 47, 109, 0, 81, 116, 117, 32, 9, 66, 5, 48, 35, 141, 0, 76, 36, 7, 66, 5, 48, 35, 87, 0, 6, 195, 48, 244, 147, 76, 0, 0, 0, 10, 69, 28, 84, 141, 4, 224, 21, 0, 10, 11, 67, 4, 98, 78, 35, 81, 112, 0, 76, 28, 12, 65, 92, 70, 40, 69, 55, 13, 82, 6, 36, 0, 0, 0, 0, 0, 10, 4, 95, 49, 77, 49, 63, 37, 55, 0, 8, 65, 96, 11, 37, 49, 87, 0, 0, 0, 13, 67, 44, 34, 84, 49, 37, 55, 39, 69, 37, 47, 0, 0, 11, 68, 69, 80, 78, 16, 49, 111, 138, 0, 76, 0, 10, 69, 37, 51, 1, 56, 64, 21, 0, 10, 13, 65, 100, 23, 37, 79, 34, 6, 110, 49, 0, 14, 9, 17, 70, 69, 81, 76, 69, 81, 83, 49, 110, 55, 49, 8, 13, 141, 0, 76, 5, 193, 100, 76, 32, 0, 10, 67, 4, 226, 83, 35, 50, 37, 87, 0, 0, 8, 67, 100, 84, 192, 21, 0, 10, 9, 67, 76, 20, 192, 87, 35, 87, 0, 10, 67, 48, 244, 192, 55, 39, 87, 0, 76, 0, 10, 67, 8, 197, 77, 69, 55, 40, 63, 0, 7, 196, 20, 225, 137, 56, 76, 0, 7, 65, 104, 86, 110, 70, 0, 0, 7, 66, 5, 64, 21, 0, 10, 0, 0, 11, 68, 5, 48, 201, 36, 35, 87, 49, 37, 0, 0, 0, 0, 0, 0, 0, 16, 70, 100, 241, 207, 85, 37, 0, 23, 37, 39, 79, 40, 34, 47, 0, 10, 66, 12, 16, 87, 35, 0, 76, 41, 32, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 5, 80, 72, 34, 0, 11, 67, 52, 84, 192, 63, 121, 141, 0, 72, 34, 0, 0, 0, 0, 9, 1, 126, 47, 37, 55, 70, 36, 0, 0, 7, 195, 5, 86, 0, 72, 34, 0, 0, 15, 66, 8, 64, 98, 111, 117, 108, 101, 118, 97, 114, 100, 0, 29, 0, 0, 0, 0, 0, 0, 6, 195, 69, 83, 201, 76, 0, 13, 69, 52, 147, 15, 84, 64, 63, 37, 55, 40, 70, 0, 0, 0, 0, 12, 67, 5, 98, 0, 35, 82, 4, 36, 35, 89, 0, 0, 13, 69, 12, 19, 131, 21, 32, 49, 111, 87, 110, 34, 0, 0, 0, 0, 10, 4, 95, 49, 67, 48, 87, 111, 138, 0, 0, 0, 7, 66, 8, 80, 21, 0, 10, 7, 195, 5, 97, 67, 76, 28, 0, 18, 71, 21, 52, 5, 72, 19, 148, 60, 110, 87, 48, 36, 34, 111, 47, 39, 0, 6, 195, 57, 66, 64, 17, 0, 0, 0, 0, 0, 11, 68, 20, 225, 133, 72, 111, 81, 110, 34, 0, 10, 2, 13, 46, 63, 13, 87, 37, 130, 0, 0, 0, 0, 0, 0, 0, 14, 70, 64, 128, 76, 49, 84, 192, 81, 35, 55, 109, 87, 0, 0, 9, 67, 9, 85, 0, 69, 109, 47, 0, 9, 67, 9, 85, 0, 69, 109, 0, 36, 0, 0, 0, 17, 70, 52, 20, 135, 5, 33, 84, 63, 35, 34, 79, 35, 34, 110, 47, 0, 0, 15, 71, 76, 128, 77, 64, 242, 78, 28, 89, 111, 48, 58, 112, 0, 0, 11, 68, 69, 80, 78, 80, 49, 111, 138, 0, 72, 0, 0, 0, 0, 7, 196, 5, 96, 78, 80, 76, 0, 0, 13, 66, 17, 32, 70, 39, 49, 47, 130, 34, 0, 24, 41, 0, 9, 67, 21, 84, 192, 109, 141, 0, 76, 0, 0, 0, 0, 9, 198, 64, 245, 82, 69, 83, 201, 76, 0, 8, 67, 48, 149, 5, 21, 0, 10, 10, 67, 8, 85, 1, 69, 36, 47, 35, 0, 0, 13, 69, 52, 22, 143, 85, 64, 63, 35, 86, 40, 47, 0, 13, 138, 14, 195, 169, 1, 14, 13, 15, 9, 14, 19, 76, 0, 14, 70, 52, 22, 79, 81, 65, 64, 63, 35, 57, 125, 47, 0, 12, 66, 4, 144, 110, 88, 0, 76, 81, 106, 101, 32, 6, 194, 4, 144, 76, 36, 6, 194, 12, 80, 76, 34, 0, 0, 0, 11, 69, 16, 83, 135, 84, 80, 70, 112, 79, 0, 0, 0, 7, 195, 4, 149, 0, 76, 36, 9, 134, 7, 21, 195, 168, 18, 5, 76, 7, 195, 12, 85, 0, 72, 34, 0, 9, 67, 4, 150, 0, 110, 49, 87, 0, 0, 0, 0, 0, 12, 68, 77, 67, 213, 80, 87, 47, 35, 40, 47, 0, 0, 21, 69, 12, 83, 12, 21, 48, 87, 110, 55, 15, 55, 35, 0, 32, 76, 81, 108, 195, 160, 32, 20, 69, 12, 83, 12, 21, 48, 87, 110, 55, 15, 87, 37, 0, 32, 76, 81, 99, 105, 32, 8, 197, 12, 83, 12, 21, 48, 76, 0, 18, 70, 76, 51, 210, 9, 85, 0, 115, 99, 111, 114, 98, 117, 116, 116, 0, 29, 0, 9, 67, 13, 85, 0, 49, 115, 47, 0, 0, 12, 68, 49, 82, 71, 36, 55, 58, 37, 73, 37, 0, 0, 0, 8, 67, 101, 97, 83, 37, 82, 0, 0, 0, 0, 0, 0, 8, 67, 57, 83, 12, 21, 0, 10, 0, 0, 20, 73, 12, 243, 148, 20, 229, 9, 60, 228, 192, 49, 114, 47, 111, 47, 57, 114, 141, 0, 0, 0, 19, 71, 29, 80, 84, 20, 208, 76, 4, 79, 58, 35, 47, 36, 63, 35, 55, 35, 0, 0, 0, 8, 67, 76, 48, 78, 21, 0, 10, 0, 0, 0, 0, 13, 5, 4, 39, 5, 19, 20, 70, 6, 110, 87, 47, 0, 0, 6, 194, 16, 80, 72, 34, 0, 0, 0, 0, 0, 18, 71, 32, 19, 66, 85, 33, 197, 72, 23, 111, 69, 13, 34, 79, 115, 34, 0, 9, 67, 8, 149, 0, 69, 37, 47, 0, 6, 195, 52, 242, 64, 76, 6, 195, 12, 50, 64, 17, 0, 12, 68, 80, 245, 84, 20, 47, 6, 40, 47, 0, 76, 13, 4, 95, 4, 16, 20, 82, 37, 34, 79, 109, 55, 0, 0, 0, 15, 70, 81, 32, 77, 92, 22, 64, 47, 34, 35, 63, 58, 135, 0, 8, 66, 21, 48, 110, 141, 0, 76, 9, 66, 17, 80, 70, 128, 0, 72, 34, 0, 0, 0, 0, 11, 70, 65, 35, 199, 72, 19, 64, 21, 0, 10, 0, 11, 70, 76, 19, 69, 80, 147, 69, 21, 0, 10, 9, 67, 21, 53, 0, 110, 138, 0, 76, 0, 0, 0, 15, 70, 8, 80, 85, 12, 245, 80, 69, 39, 49, 40, 137, 0, 76, 0, 0, 15, 3, 95, 35, 57, 47, 35, 69, 109, 55, 35, 87, 37, 114, 0, 12, 4, 95, 20, 12, 4, 47, 6, 37, 55, 70, 0, 0, 0, 0, 12, 67, 52, 228, 192, 63, 37, 50, 109, 47, 141, 0, 10, 67, 4, 197, 0, 24, 35, 55, 47, 0, 0, 12, 68, 32, 147, 132, 36, 23, 37, 50, 70, 37, 0, 0, 0, 7, 66, 21, 64, 36, 0, 76, 0, 0, 0, 0, 24, 74, 48, 145, 67, 33, 65, 78, 77, 65, 73, 56, 55, 37, 89, 47, 115, 50, 89, 47, 35, 57, 50, 0, 0, 0, 11, 4, 5, 195, 187, 20, 109, 138, 0, 76, 36, 0, 8, 197, 5, 85, 1, 57, 64, 76, 0, 0, 12, 67, 4, 209, 0, 35, 4, 110, 63, 70, 36, 0, 0, 17, 72, 52, 243, 148, 76, 84, 146, 5, 64, 63, 114, 87, 36, 34, 35, 0, 0, 0, 9, 198, 21, 84, 211, 36, 86, 128, 76, 15, 70, 4, 225, 18, 60, 145, 0, 111, 70, 34, 39, 37, 70, 0, 0, 0, 10, 68, 48, 245, 73, 76, 55, 58, 37, 0, 0, 13, 69, 8, 83, 9, 104, 80, 69, 36, 55, 37, 86, 0, 10, 69, 64, 83, 208, 48, 80, 21, 0, 10, 0, 7, 66, 21, 80, 109, 0, 76, 0, 0, 0, 0, 0, 10, 67, 21, 85, 0, 109, 138, 0, 76, 36, 0, 9, 67, 21, 86, 0, 130, 141, 0, 76, 0, 15, 70, 12, 245, 83, 12, 245, 83, 49, 40, 87, 49, 40, 87, 0, 0, 8, 67, 4, 225, 0, 21, 0, 10, 0, 0, 0, 0, 0, 0, 10, 67, 25, 81, 76, 81, 57, 40, 55, 0, 0, 0, 0, 16, 70, 65, 33, 77, 36, 84, 128, 48, 34, 13, 63, 57, 36, 118, 0, 0, 16, 67, 80, 19, 148, 47, 111, 48, 37, 0, 76, 81, 112, 105, 115, 32, 19, 67, 80, 19, 148, 47, 111, 63, 57, 130, 0, 76, 81, 109, 105, 101, 117, 120, 32, 10, 67, 80, 19, 148, 47, 111, 138, 0, 76, 0, 0, 0, 0, 6, 195, 5, 97, 192, 17, 0, 0, 0, 9, 198, 69, 83, 201, 69, 81, 64, 72, 0, 16, 7, 11, 15, 23, 5, 195, 175, 20, 49, 39, 58, 110, 57, 47, 0, 11, 67, 4, 243, 0, 35, 4, 39, 110, 55, 0, 0, 20, 68, 12, 83, 12, 20, 87, 110, 55, 15, 55, 35, 0, 32, 76, 81, 108, 195, 160, 32, 19, 68, 12, 83, 12, 20, 87, 110, 55, 15, 87, 37, 0, 32, 76, 81, 99, 105, 32, 7, 196, 12, 83, 12, 20, 76, 0, 17, 70, 4, 195, 5, 49, 82, 65, 35, 55, 36, 55, 40, 37, 6, 35, 0, 0, 0, 0, 0, 0, 0, 8, 67, 32, 19, 128, 23, 111, 0, 0, 0, 11, 67, 25, 85, 0, 81, 109, 138, 0, 76, 36, 0, 0, 7, 195, 52, 243, 128, 72, 34, 0, 0, 0, 6, 194, 20, 128, 76, 28, 7, 66, 16, 160, 21, 0, 10, 0, 6, 195, 64, 20, 128, 76, 12, 67, 60, 52, 128, 39, 87, 4, 36, 110, 34, 0, 0, 0, 15, 69, 44, 192, 88, 60, 224, 49, 55, 35, 49, 87, 125, 50, 0, 0, 0, 0, 8, 196, 20, 195, 5, 76, 76, 32, 0, 18, 3, 226, 132, 162, 63, 35, 34, 49, 70, 13, 81, 35, 69, 34, 37, 49, 0, 0, 0, 18, 71, 24, 83, 4, 77, 0, 84, 32, 81, 110, 55, 70, 87, 48, 35, 47, 0, 0, 0, 12, 69, 8, 22, 69, 85, 128, 69, 35, 57, 130, 0, 0, 0, 0, 12, 68, 44, 83, 153, 4, 49, 36, 50, 57, 35, 0, 9, 68, 64, 245, 76, 76, 48, 40, 0, 10, 67, 16, 19, 147, 70, 111, 141, 0, 76, 22, 68, 64, 20, 131, 20, 48, 35, 34, 87, 49, 114, 132, 0, 76, 81, 113, 117, 39, 111, 110, 32, 26, 68, 64, 20, 131, 20, 48, 35, 34, 87, 49, 110, 55, 141, 0, 76, 81, 113, 117, 39, 101, 108, 108, 101, 115, 32, 24, 68, 64, 20, 131, 20, 48, 35, 34, 87, 49, 110, 55, 0, 76, 81, 113, 117, 39, 101, 108, 108, 101, 32, 24, 68, 64, 20, 131, 20, 48, 35, 34, 87, 49, 37, 55, 141, 0, 76, 81, 113, 117, 39, 105, 108, 115, 32, 22, 68, 64, 20, 131, 20, 48, 35, 34, 87, 49, 37, 55, 0, 76, 81, 113, 117, 39, 105, 108, 32, 19, 68, 64, 20, 131, 20, 48, 35, 34, 87, 49, 13, 0, 76, 81, 113, 117, 101, 32, 0, 0, 9, 198, 64, 245, 82, 80, 19, 148, 76, 17, 66, 12, 208, 99, 101, 110, 116, 105, 109, 195, 168, 116, 114, 101, 0, 29, 0, 12, 67, 16, 149, 152, 70, 37, 82, 37, 49, 87, 0, 0, 0, 8, 67, 28, 85, 0, 21, 0, 10, 0, 0, 9, 67, 32, 20, 148, 35, 34, 47, 0, 0, 0, 0, 0, 0, 0, 13, 69, 92, 19, 12, 37, 48, 58, 35, 55, 37, 87, 0, 14, 69, 32, 84, 141, 21, 48, 23, 110, 34, 63, 110, 87, 0, 0, 0, 0, 0, 0, 0, 0, 21, 70, 44, 212, 12, 5, 145, 82, 49, 35, 4, 110, 63, 48, 55, 110, 57, 6, 115, 34, 0, 0, 0, 0, 0, 12, 68, 92, 20, 137, 60, 58, 35, 34, 57, 39, 0, 0, 0, 16, 70, 4, 192, 137, 56, 244, 192, 35, 55, 69, 37, 50, 39, 87, 0, 6, 195, 57, 97, 1, 17, 0, 11, 3, 226, 130, 172, 13, 34, 6, 39, 0, 76, 0, 0, 0, 0, 15, 70, 80, 83, 148, 36, 243, 147, 47, 111, 47, 57, 114, 141, 0, 6, 195, 44, 65, 64, 17, 0, 0, 10, 69, 72, 81, 8, 5, 64, 21, 0, 10, 12, 69, 21, 84, 133, 57, 64, 109, 34, 138, 0, 76, 0, 7, 66, 32, 80, 21, 0, 10, 0, 0, 12, 68, 5, 37, 66, 4, 35, 34, 40, 69, 35, 0, 6, 195, 88, 84, 147, 37, 10, 67, 88, 84, 147, 82, 110, 34, 0, 76, 0, 14, 69, 25, 85, 21, 56, 16, 81, 40, 47, 40, 50, 35, 0, 8, 197, 12, 128, 81, 84, 80, 76, 16, 69, 20, 32, 196, 36, 48, 13, 69, 36, 87, 36, 70, 37, 49, 0, 0, 0, 0, 0, 13, 69, 4, 113, 78, 16, 16, 35, 88, 112, 70, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 20, 192, 76, 12, 3, 95, 50, 49, 82, 112, 47, 36, 12, 113, 0, 0, 9, 67, 64, 20, 192, 48, 35, 0, 37, 11, 67, 64, 20, 192, 48, 6, 35, 141, 0, 76, 9, 3, 95, 50, 48, 82, 112, 138, 0, 0, 12, 68, 44, 85, 137, 56, 49, 36, 82, 37, 50, 0, 14, 3, 95, 50, 51, 82, 112, 47, 47, 34, 58, 35, 141, 0, 0, 18, 5, 19, 46, 20, 46, 16, 87, 37, 55, 47, 13, 12, 48, 55, 6, 110, 0, 12, 3, 95, 50, 50, 82, 112, 47, 70, 130, 141, 0, 0, 11, 70, 69, 81, 82, 36, 84, 192, 21, 0, 10, 12, 3, 95, 50, 53, 82, 112, 47, 87, 112, 49, 0, 0, 8, 67, 32, 148, 192, 21, 0, 10, 13, 3, 95, 50, 52, 82, 112, 47, 49, 35, 47, 34, 0, 0, 12, 3, 95, 50, 55, 82, 112, 47, 87, 110, 47, 0, 0, 12, 3, 95, 50, 54, 82, 112, 47, 87, 37, 142, 0, 0, 7, 66, 37, 64, 21, 0, 10, 13, 3, 95, 51, 49, 47, 34, 111, 47, 36, 12, 113, 0, 13, 4, 95, 13, 3, 14, 63, 35, 49, 34, 6, 114, 0, 0, 0, 0, 0, 6, 195, 76, 52, 201, 17, 0, 0, 10, 67, 48, 19, 211, 55, 35, 125, 87, 0, 0, 0, 7, 66, 16, 240, 21, 0, 10, 0, 12, 67, 20, 211, 0, 13, 4, 110, 63, 110, 55, 0, 0, 0, 9, 67, 16, 245, 0, 70, 125, 47, 0, 0, 0, 0, 9, 68, 64, 20, 5, 72, 21, 0, 10, 0, 0, 0, 0, 14, 6, 95, 18, 15, 13, 1, 14, 34, 39, 63, 6, 112, 0, 0, 0, 0, 10, 134, 5, 195, 187, 13, 5, 19, 76, 36, 10, 134, 6, 195, 187, 13, 5, 19, 76, 36, 0, 0, 8, 67, 20, 225, 0, 21, 0, 10, 8, 197, 16, 84, 21, 37, 48, 76, 0, 17, 66, 20, 224, 111, 15, 47, 40, 141, 0, 76, 81, 116, 111, 117, 115, 32, 7, 194, 20, 224, 76, 36, 40, 5, 194, 20, 224, 76, 5, 194, 20, 224, 72, 15, 3, 95, 54, 49, 87, 58, 35, 87, 111, 47, 36, 12, 113, 0, 0, 10, 3, 95, 51, 88, 47, 34, 111, 47, 0, 0, 11, 68, 77, 84, 200, 36, 87, 40, 89, 37, 0, 12, 68, 52, 19, 21, 76, 63, 35, 55, 109, 87, 0, 8, 3, 95, 48, 67, 87, 111, 0, 0, 0, 0, 0, 7, 196, 5, 52, 197, 104, 76, 18, 3, 16, 46, 19, 48, 125, 87, 47, 87, 49, 34, 37, 48, 47, 125, 63, 0, 0, 0, 8, 67, 52, 17, 5, 21, 0, 10, 13, 70, 16, 84, 211, 61, 84, 192, 70, 13, 87, 40, 0, 16, 3, 95, 55, 49, 87, 110, 48, 47, 111, 47, 36, 12, 113, 0, 102, 16, 3, 95, 55, 49, 87, 58, 35, 87, 111, 47, 36, 12, 114, 86, 0, 0, 0, 0, 0, 0, 10, 67, 77, 65, 64, 87, 6, 112, 47, 0, 0, 7, 196, 64, 20, 141, 36, 76, 0, 0, 19, 66, 48, 16, 55, 119, 15, 55, 130, 34, 0, 76, 32, 81, 108, 101, 117, 114, 32, 6, 194, 40, 80, 72, 32, 10, 66, 48, 16, 55, 119, 0, 36, 40, 72, 9, 66, 48, 16, 55, 119, 0, 34, 76, 12, 3, 95, 49, 57, 70, 37, 86, 50, 115, 81, 0, 0, 11, 67, 5, 2, 64, 35, 48, 4, 36, 37, 0, 12, 3, 95, 49, 56, 70, 37, 86, 109, 37, 139, 0, 0, 0, 8, 197, 20, 224, 207, 72, 80, 76, 0, 0, 0, 0, 0, 14, 70, 80, 130, 69, 73, 38, 64, 47, 57, 110, 34, 37, 0, 12, 3, 95, 50, 57, 82, 112, 47, 50, 115, 81, 0, 9, 3, 95, 49, 49, 23, 114, 86, 0, 0, 12, 3, 95, 50, 56, 82, 112, 47, 109, 37, 139, 0, 9, 3, 95, 49, 48, 70, 37, 142, 0, 0, 10, 3, 95, 49, 51, 47, 34, 110, 86, 0, 0, 9, 3, 95, 49, 50, 70, 40, 86, 0, 0, 7, 195, 12, 83, 1, 76, 32, 9, 3, 95, 49, 53, 49, 112, 86, 0, 0, 12, 3, 95, 49, 52, 49, 35, 47, 125, 34, 86, 0, 0, 7, 196, 4, 147, 147, 36, 76, 11, 3, 95, 49, 55, 70, 37, 87, 110, 47, 0, 0, 9, 3, 95, 49, 54, 87, 110, 86, 0, 0, 0, 7, 195, 25, 84, 192, 76, 36, 17, 70, 52, 84, 131, 20, 65, 83, 63, 110, 34, 87, 36, 70, 110, 87, 0, 13, 3, 95, 55, 88, 87, 110, 48, 47, 111, 47, 0, 102, 0, 0, 0, 0, 11, 67, 21, 130, 84, 36, 79, 86, 37, 47, 0, 9, 67, 9, 84, 192, 69, 109, 0, 36, 9, 67, 9, 84, 192, 69, 109, 87, 0, 0, 0, 0, 10, 66, 33, 160, 23, 110, 34, 47, 87, 0, 0, 19, 71, 88, 83, 133, 105, 81, 76, 4, 82, 36, 50, 36, 86, 109, 110, 55, 35, 0, 0, 24, 11, 4, 195, 169, 19, 5, 18, 20, 9, 15, 14, 19, 70, 36, 86, 110, 34, 47, 57, 114, 141, 0, 36, 0, 0, 0, 0, 0, 10, 69, 52, 20, 16, 21, 32, 21, 0, 10, 0, 16, 70, 88, 19, 149, 5, 69, 64, 82, 35, 50, 40, 35, 47, 40, 0, 9, 66, 52, 16, 63, 119, 0, 72, 34, 14, 3, 95, 52, 49, 49, 35, 34, 111, 47, 36, 12, 113, 0, 0, 14, 67, 52, 134, 128, 63, 36, 79, 35, 110, 34, 47, 87, 0, 0, 19, 72, 24, 18, 18, 20, 226, 5, 37, 64, 81, 35, 34, 13, 50, 35, 57, 47, 0, 0, 9, 67, 52, 21, 0, 63, 35, 47, 0, 0, 0, 0, 0, 10, 69, 52, 18, 76, 80, 240, 21, 0, 10, 0, 14, 3, 95, 53, 49, 87, 112, 49, 111, 47, 36, 12, 113, 0, 0, 17, 71, 77, 2, 9, 56, 53, 5, 72, 87, 81, 112, 49, 47, 110, 34, 0, 0, 0, 8, 197, 80, 83, 12, 21, 48, 76, 0, 0, 0, 0, 21, 2, 50, 49, 82, 112, 47, 36, 12, 109, 50, 37, 110, 63, 0, 81, 195, 168, 109, 101, 32, 0, 0, 0, 8, 67, 28, 81, 75, 21, 0, 10, 0, 0, 0, 6, 195, 92, 208, 64, 17, 0, 13, 3, 95, 63, 63, 87, 112, 69, 6, 39, 55, 55, 0, 0, 22, 2, 51, 49, 47, 34, 111, 47, 36, 12, 109, 50, 37, 110, 63, 0, 81, 195, 168, 109, 101, 32, 0, 15, 70, 13, 147, 148, 32, 144, 64, 87, 37, 50, 47, 37, 35, 0, 10, 66, 53, 32, 63, 13, 87, 37, 130, 0, 0, 11, 3, 95, 52, 88, 49, 35, 34, 111, 47, 0, 0, 0, 17, 70, 104, 147, 66, 4, 37, 197, 86, 37, 63, 69, 35, 69, 58, 36, 0, 10, 67, 60, 208, 78, 39, 63, 35, 50, 0, 0, 0, 7, 195, 4, 145, 64, 76, 36, 0, 0, 14, 69, 32, 19, 76, 21, 64, 23, 35, 63, 55, 110, 47, 0, 23, 2, 52, 49, 49, 35, 34, 111, 47, 36, 12, 109, 50, 37, 110, 63, 0, 81, 195, 168, 109, 101, 32, 0, 19, 66, 48, 80, 55, 14, 15, 55, 130, 34, 0, 76, 32, 81, 108, 101, 117, 114, 32, 7, 194, 48, 80, 36, 40, 72, 6, 194, 48, 80, 34, 76, 16, 66, 44, 112, 107, 105, 108, 111, 103, 114, 97, 109, 109, 101, 0, 29, 0, 6, 195, 64, 50, 64, 17, 14, 3, 95, 56, 48, 49, 35, 47, 34, 13, 82, 112, 141, 0, 11, 3, 95, 53, 88, 87, 112, 49, 111, 47, 0, 0, 8, 196, 12, 85, 20, 20, 72, 34, 0, 9, 67, 56, 21, 0, 50, 35, 47, 0, 8, 67, 48, 85, 0, 21, 0, 10, 0, 0, 8, 67, 52, 18, 64, 63, 110, 0, 0, 9, 68, 64, 85, 5, 72, 21, 0, 10, 15, 70, 40, 16, 203, 64, 245, 0, 73, 35, 49, 48, 125, 47, 0, 0, 8, 197, 69, 81, 76, 48, 80, 76, 23, 2, 53, 49, 87, 112, 49, 111, 47, 36, 12, 109, 50, 37, 110, 63, 0, 81, 195, 168, 109, 101, 32, 0, 16, 70, 92, 19, 21, 36, 114, 64, 58, 35, 55, 40, 37, 73, 37, 0, 14, 66, 45, 112, 107, 105, 108, 111, 119, 97, 116, 116, 0, 29, 15, 3, 95, 57, 49, 50, 39, 50, 111, 47, 36, 12, 113, 0, 102, 0, 16, 67, 60, 83, 64, 11, 4, 39, 11, 4, 13, 11, 6, 110, 63, 0, 12, 3, 95, 54, 88, 87, 58, 35, 87, 111, 47, 0, 0, 7, 196, 5, 84, 211, 36, 76, 0, 13, 69, 80, 83, 142, 37, 48, 47, 36, 50, 37, 87, 0, 0, 7, 131, 195, 167, 1, 76, 32, 0, 0, 11, 68, 48, 144, 153, 20, 55, 37, 69, 37, 0, 14, 70, 52, 243, 147, 36, 85, 82, 63, 13, 87, 57, 130, 0, 7, 195, 4, 145, 83, 76, 36, 0, 10, 67, 29, 83, 6, 79, 125, 55, 81, 0, 8, 197, 12, 84, 148, 21, 48, 76, 24, 2, 54, 49, 87, 58, 35, 87, 111, 47, 36, 12, 109, 50, 37, 110, 63, 0, 81, 195, 168, 109, 101, 32, 0, 6, 194, 36, 192, 76, 32, 0, 0, 17, 70, 72, 85, 143, 49, 97, 82, 34, 36, 82, 125, 55, 82, 110, 34, 0, 0, 17, 5, 19, 46, 22, 46, 16, 87, 37, 55, 82, 127, 48, 55, 6, 110, 0, 0, 0, 0, 6, 195, 52, 18, 83, 76, 0, 0, 0, 8, 67, 52, 18, 76, 21, 0, 10, 13, 67, 13, 68, 140, 24, 49, 114, 47, 34, 125, 55, 0, 14, 3, 95, 56, 88, 49, 35, 47, 34, 13, 82, 112, 12, 0, 0, 0, 10, 69, 61, 85, 16, 85, 64, 21, 0, 10, 11, 69, 12, 131, 197, 85, 32, 49, 115, 34, 0, 0, 15, 70, 76, 19, 83, 84, 225, 192, 87, 35, 63, 87, 40, 66, 0, 0, 0, 0, 24, 2, 56, 49, 49, 35, 47, 34, 13, 82, 112, 12, 109, 50, 37, 110, 63, 0, 81, 195, 168, 109, 101, 32, 0, 6, 194, 52, 80, 72, 32, 0, 9, 198, 21, 84, 211, 36, 243, 147, 76, 12, 3, 95, 57, 88, 50, 39, 50, 111, 47, 0, 102, 0, 0, 8, 67, 32, 245, 0, 21, 0, 10, 0, 0, 0, 0, 0, 11, 3, 95, 63, 65, 55, 6, 110, 47, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 70, 72, 84, 85, 36, 83, 64, 34, 36, 49, 109, 37, 57, 110, 63, 0, 0, 7, 66, 36, 224, 21, 0, 10, 0, 22, 67, 92, 80, 128, 119, 101, 98, 118, 105, 115, 117, 109, 0, 29, 81, 118, 105, 115, 117, 109, 32, 0, 0, 0, 7, 195, 77, 82, 83, 76, 36, 15, 70, 64, 130, 76, 37, 4, 192, 81, 37, 55, 37, 48, 87, 0, 0, 18, 67, 12, 85, 88, 87, 130, 15, 55, 35, 0, 32, 76, 81, 108, 195, 160, 32, 17, 67, 12, 85, 88, 87, 130, 15, 87, 37, 0, 32, 76, 81, 99, 105, 32, 6, 195, 12, 85, 88, 76, 14, 4, 95, 15, 7, 15, 39, 79, 39, 50, 6, 110, 49, 0, 0, 7, 196, 20, 229, 18, 20, 36, 7, 196, 20, 229, 18, 20, 76, 0, 0, 0, 0, 0, 15, 69, 5, 162, 77, 85, 64, 35, 86, 37, 63, 6, 109, 47, 0, 0, 10, 67, 76, 83, 147, 87, 111, 141, 0, 36, 9, 67, 76, 83, 147, 87, 111, 87, 0, 17, 70, 65, 33, 83, 69, 81, 64, 48, 34, 110, 87, 49, 8, 13, 0, 76, 17, 70, 65, 82, 83, 69, 81, 64, 48, 109, 37, 87, 49, 8, 13, 0, 76, 0, 11, 67, 81, 35, 208, 47, 34, 39, 137, 0, 76, 0, 0, 0, 6, 194, 56, 80, 72, 32, 0, 10, 67, 61, 82, 64, 23, 58, 37, 0, 76, 0, 14, 68, 80, 86, 1, 76, 47, 110, 49, 87, 6, 35, 87, 0, 0, 14, 69, 52, 19, 1, 92, 144, 63, 35, 55, 35, 58, 37, 0, 0, 0, 9, 67, 56, 85, 0, 50, 110, 47, 0, 0, 0, 15, 70, 52, 21, 20, 32, 144, 83, 63, 35, 47, 57, 35, 87, 0, 0, 0, 0, 0, 6, 195, 65, 35, 198, 24, 0, 7, 195, 88, 245, 83, 76, 32, 7, 195, 56, 245, 83, 76, 32, 12, 4, 95, 48, 77, 50, 63, 37, 55, 57, 114, 0, 0, 9, 67, 56, 243, 128, 50, 114, 0, 76, 13, 4, 95, 48, 77, 51, 63, 37, 55, 57, 35, 34, 0, 0, 0, 14, 6, 22, 195, 169, 14, 21, 19, 82, 36, 50, 109, 87, 0, 10, 4, 95, 48, 77, 49, 63, 37, 55, 0, 0, 12, 4, 95, 2, 18, 22, 69, 34, 6, 110, 82, 0, 0, 17, 67, 56, 244, 132, 50, 39, 34, 110, 87, 47, 0, 81, 101, 115, 116, 32, 18, 70, 8, 243, 212, 4, 35, 5, 98, 111, 117, 116, 97, 98, 108, 101, 0, 29, 0, 0, 0, 0, 6, 195, 24, 244, 128, 76, 11, 67, 85, 4, 192, 109, 48, 36, 110, 87, 0, 0, 0, 0, 8, 67, 28, 83, 147, 88, 111, 0, 17, 66, 65, 32, 112, 114, 111, 102, 101, 115, 115, 101, 117, 114, 0, 41, 29, 0, 0, 0, 16, 70, 64, 20, 148, 36, 243, 147, 48, 35, 34, 47, 57, 114, 141, 0, 14, 69, 76, 245, 137, 21, 64, 87, 39, 82, 37, 110, 47, 0, 0, 0, 0, 0, 0, 25, 66, 44, 208, 49, 35, 4, 110, 63, 48, 55, 110, 57, 6, 115, 34, 0, 81, 112, 108, 97, 121, 101, 114, 32, 16, 66, 44, 208, 107, 105, 108, 111, 109, 195, 168, 116, 114, 101, 0, 29, 0, 0, 13, 5, 20, 18, 195, 168, 19, 47, 34, 110, 141, 0, 76, 0, 10, 69, 16, 83, 5, 80, 80, 21, 0, 10, 0, 10, 67, 52, 20, 147, 63, 35, 34, 87, 0, 0, 17, 71, 12, 132, 137, 77, 67, 65, 76, 49, 34, 37, 87, 63, 35, 87, 0, 0, 0, 0, 8, 66, 61, 80, 40, 0, 72, 28, 13, 66, 69, 16, 113, 117, 101, 108, 113, 117, 101, 0, 29, 0, 0, 12, 68, 76, 19, 79, 4, 87, 35, 63, 39, 35, 0, 0, 0, 0, 9, 67, 61, 85, 0, 35, 40, 47, 0, 0, 0, 14, 69, 81, 85, 129, 49, 80, 47, 40, 82, 35, 55, 40, 0, 14, 69, 64, 20, 212, 37, 48, 48, 35, 87, 47, 37, 87, 0, 0, 0, 6, 195, 64, 64, 64, 17, 0, 0, 0, 0, 21, 67, 52, 16, 192, 63, 35, 49, 39, 110, 87, 37, 49, 87, 0, 82, 111, 115, 32, 120, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 12, 80, 201, 76, 32, 0, 0, 14, 70, 64, 245, 82, 12, 83, 148, 48, 40, 34, 87, 111, 0, 5, 194, 56, 144, 72, 0, 0, 9, 68, 20, 208, 67, 76, 21, 0, 10, 0, 0, 9, 3, 195, 168, 19, 110, 87, 0, 72, 0, 11, 4, 4, 195, 168, 19, 70, 110, 141, 0, 72, 0, 9, 68, 69, 81, 82, 100, 21, 0, 10, 0, 0, 0, 13, 67, 36, 35, 64, 37, 69, 4, 36, 6, 110, 63, 0, 0, 0, 0, 22, 4, 95, 3, 9, 18, 35, 49, 87, 111, 87, 37, 34, 49, 114, 81, 55, 6, 110, 49, 87, 0, 0, 8, 67, 77, 83, 128, 21, 0, 10, 0, 8, 67, 20, 32, 89, 21, 0, 10, 0, 14, 69, 8, 148, 211, 5, 80, 69, 37, 87, 35, 6, 39, 0, 8, 197, 5, 85, 18, 21, 48, 76, 0, 0, 13, 67, 52, 34, 84, 63, 36, 79, 35, 69, 37, 47, 0, 0, 12, 3, 95, 194, 181, 63, 37, 49, 34, 6, 39, 0, 0, 0, 16, 70, 28, 83, 133, 76, 148, 192, 88, 36, 50, 36, 86, 37, 87, 0, 16, 70, 76, 243, 1, 72, 148, 192, 87, 39, 55, 35, 34, 37, 87, 0, 0, 9, 67, 52, 20, 192, 63, 35, 87, 0, 6, 195, 77, 84, 128, 76, 7, 195, 88, 244, 192, 72, 34, 7, 195, 56, 244, 192, 72, 34, 11, 67, 76, 84, 192, 87, 121, 141, 0, 72, 34, 11, 67, 12, 84, 192, 87, 36, 141, 0, 72, 34, 0, 9, 68, 100, 244, 200, 36, 21, 0, 10, 12, 68, 81, 83, 137, 76, 47, 109, 50, 37, 87, 0, 0, 0, 27, 70, 9, 84, 139, 36, 224, 64, 69, 40, 34, 49, 37, 50, 35, 15, 81, 35, 87, 39, 0, 81, 102, 97, 115, 111, 32, 14, 70, 12, 130, 69, 56, 194, 84, 89, 57, 111, 55, 37, 0, 0, 11, 4, 95, 19, 20, 11, 69, 6, 35, 34, 0, 6, 131, 95, 195, 180, 43, 0, 9, 68, 80, 131, 211, 20, 21, 0, 10, 0, 16, 4, 95, 1, 3, 21, 35, 49, 87, 111, 47, 110, 79, 6, 109, 0, 0, 17, 3, 95, 194, 171, 40, 82, 34, 36, 15, 79, 37, 57, 63, 6, 110, 0, 0, 6, 195, 28, 229, 64, 17, 0, 0, 10, 69, 76, 50, 69, 57, 64, 87, 37, 0, 0, 9, 66, 76, 16, 87, 119, 0, 72, 34, 17, 66, 52, 208, 109, 105, 108, 108, 105, 109, 195, 168, 116, 114, 101, 0, 29, 13, 3, 95, 194, 167, 87, 110, 49, 87, 57, 6, 114, 0, 0, 10, 67, 45, 84, 148, 49, 40, 34, 47, 0, 0, 0, 0, 6, 195, 76, 20, 0, 17, 0, 15, 4, 95, 18, 14, 7, 34, 114, 138, 111, 89, 6, 110, 81, 0, 0, 0, 0, 16, 70, 9, 84, 149, 56, 66, 64, 69, 40, 34, 40, 50, 70, 37, 0, 0, 23, 67, 33, 69, 16, 35, 89, 47, 4, 36, 47, 4, 36, 48, 6, 36, 10, 0, 81, 58, 47, 47, 32, 0, 0, 15, 69, 72, 148, 195, 61, 48, 34, 37, 87, 49, 39, 110, 87, 0, 0, 0, 6, 131, 95, 195, 160, 43, 0, 11, 70, 72, 80, 207, 72, 65, 82, 21, 0, 10, 0, 14, 69, 84, 37, 78, 81, 80, 40, 69, 40, 50, 47, 40, 0, 0, 10, 66, 52, 224, 63, 37, 50, 109, 47, 0, 0, 0, 6, 131, 15, 195, 185, 76, 0, 0, 0, 0, 11, 68, 48, 83, 206, 20, 55, 36, 125, 50, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 1, 3, 50, 70, 40, 69, 55, 35, 49, 87, 111, 47, 110, 79, 6, 109, 0, 0, 0, 0, 13, 69, 60, 97, 147, 21, 64, 125, 81, 87, 110, 47, 0, 0, 9, 66, 60, 176, 39, 49, 36, 0, 76, 9, 67, 61, 84, 147, 40, 34, 87, 0, 9, 66, 80, 16, 47, 119, 0, 72, 34, 0, 0, 15, 70, 52, 144, 200, 4, 83, 0, 63, 37, 49, 35, 110, 55, 0, 0, 9, 198, 80, 245, 74, 61, 84, 147, 76, 0, 0, 0, 0, 0, 0, 0, 11, 68, 76, 51, 213, 80, 87, 49, 40, 47, 0, 0, 0, 6, 195, 64, 197, 83, 76, 18, 3, 95, 194, 187, 81, 110, 34, 63, 36, 15, 79, 37, 57, 63, 6, 110, 0, 0, 9, 67, 73, 85, 0, 34, 109, 47, 0, 0, 15, 67, 24, 147, 5, 21, 0, 10, 81, 122, 105, 108, 108, 97, 32, 0, 0, 0, 15, 67, 80, 86, 20, 21, 0, 10, 81, 97, 108, 111, 117, 100, 32, 9, 67, 29, 84, 192, 79, 109, 87, 0, 15, 67, 69, 20, 192, 113, 117, 101, 108, 113, 117, 101, 115, 0, 29, 0, 12, 68, 56, 145, 197, 72, 50, 37, 88, 110, 34, 0, 0, 15, 69, 4, 208, 90, 60, 224, 35, 63, 35, 86, 6, 125, 50, 0, 0, 0, 9, 67, 77, 84, 192, 87, 109, 0, 36, 9, 67, 77, 84, 192, 87, 109, 87, 0, 0, 11, 68, 76, 131, 210, 80, 89, 125, 34, 47, 0, 12, 68, 4, 64, 77, 76, 35, 70, 35, 63, 87, 0, 0, 20, 2, 195, 151, 63, 109, 55, 47, 37, 48, 55, 37, 6, 36, 10, 48, 6, 35, 34, 0, 0, 17, 66, 77, 64, 87, 112, 49, 55, 40, 0, 81, 99, 108, 111, 117, 100, 32, 9, 66, 77, 64, 87, 6, 112, 138, 0, 0, 8, 67, 32, 83, 16, 21, 0, 10, 0, 19, 72, 5, 35, 65, 28, 81, 4, 60, 224, 35, 34, 63, 35, 79, 36, 70, 114, 0, 23, 68, 80, 83, 80, 76, 47, 111, 86, 111, 47, 111, 0, 82, 101, 110, 32, 116, 101, 109, 112, 115, 32, 0, 0, 16, 67, 77, 68, 0, 87, 37, 55, 47, 13, 12, 48, 55, 6, 110, 0, 0, 0, 22, 2, 194, 166, 87, 36, 48, 35, 34, 35, 47, 115, 34, 15, 82, 110, 47, 37, 49, 35, 55, 0, 0, 10, 69, 8, 85, 20, 21, 32, 21, 0, 10, 15, 69, 21, 131, 195, 21, 64, 110, 79, 86, 39, 87, 110, 47, 0, 0, 6, 194, 76, 80, 72, 32, 0, 19, 67, 16, 84, 20, 100, 195, 169, 112, 97, 114, 116, 101, 109, 101, 110, 116, 0, 29, 8, 2, 194, 165, 57, 110, 50, 0, 0, 15, 68, 13, 144, 133, 72, 21, 0, 10, 81, 108, 105, 110, 107, 32, 13, 5, 16, 18, 195, 168, 19, 48, 34, 110, 141, 0, 76, 9, 2, 194, 162, 87, 110, 50, 47, 0, 0, 15, 6, 1, 16, 18, 195, 168, 19, 35, 48, 34, 110, 141, 0, 76, 9, 2, 194, 163, 55, 37, 82, 34, 0, 0, 0, 8, 67, 56, 245, 0, 21, 0, 10, 9, 67, 76, 85, 0, 87, 110, 47, 0, 16, 70, 48, 17, 84, 37, 66, 65, 55, 36, 47, 37, 87, 57, 35, 0, 0, 16, 2, 194, 174, 63, 35, 34, 49, 70, 36, 48, 39, 86, 6, 36, 0, 0, 16, 70, 32, 243, 132, 85, 32, 83, 23, 114, 70, 109, 34, 35, 87, 0, 23, 73, 81, 85, 20, 37, 21, 65, 57, 66, 64, 47, 40, 47, 37, 49, 58, 6, 35, 50, 47, 37, 0, 10, 2, 194, 175, 63, 35, 49, 34, 114, 0, 5, 130, 195, 167, 43, 0, 20, 2, 194, 172, 47, 37, 34, 110, 10, 81, 35, 49, 109, 55, 47, 35, 47, 37, 81, 0, 5, 130, 195, 164, 43, 0, 17, 67, 77, 81, 0, 87, 109, 70, 110, 87, 47, 0, 81, 101, 115, 116, 32, 0, 11, 68, 28, 227, 205, 20, 79, 50, 125, 63, 0, 5, 130, 195, 162, 43, 0, 12, 2, 197, 147, 39, 15, 13, 15, 55, 37, 36, 0, 0, 7, 130, 195, 160, 14, 43, 9, 7, 2, 195, 160, 35, 0, 76, 0, 7, 2, 194, 169, 21, 0, 10, 0, 11, 70, 12, 243, 80, 85, 65, 82, 21, 0, 10, 24, 11, 1, 21, 10, 15, 21, 18, 4, 39, 8, 21, 9, 97, 117, 106, 111, 117, 114, 100, 117, 105, 0, 29, 13, 2, 194, 182, 48, 35, 34, 35, 79, 34, 35, 81, 0, 5, 130, 195, 174, 43, 0, 11, 69, 28, 147, 12, 21, 48, 88, 37, 55, 0, 8, 2, 194, 183, 48, 58, 112, 0, 5, 130, 195, 175, 43, 0, 14, 70, 52, 245, 76, 61, 81, 0, 63, 40, 55, 40, 70, 0, 7, 195, 76, 242, 83, 76, 36, 9, 66, 60, 224, 114, 132, 0, 76, 32, 0, 6, 195, 4, 32, 192, 17, 0, 16, 2, 194, 178, 48, 109, 37, 87, 6, 111, 87, 15, 70, 6, 130, 0, 5, 130, 195, 170, 43, 0, 16, 2, 194, 179, 48, 109, 37, 87, 111, 87, 15, 47, 34, 58, 35, 0, 5, 130, 195, 171, 43, 5, 130, 195, 171, 43, 0, 10, 3, 21, 46, 19, 109, 12, 110, 87, 0, 5, 130, 195, 168, 43, 0, 7, 195, 60, 229, 0, 76, 36, 6, 195, 76, 242, 84, 76, 15, 2, 194, 177, 48, 55, 6, 109, 86, 40, 63, 58, 6, 112, 0, 5, 130, 195, 169, 43, 0, 12, 68, 56, 85, 137, 76, 50, 36, 82, 37, 87, 0, 6, 195, 72, 144, 65, 17, 14, 2, 194, 190, 47, 34, 58, 35, 10, 49, 6, 35, 34, 0, 5, 130, 195, 182, 43, 0, 12, 67, 85, 35, 0, 109, 12, 110, 34, 110, 55, 0, 27, 2, 194, 191, 48, 58, 112, 15, 70, 112, 47, 36, 34, 39, 79, 35, 87, 57, 114, 15, 112, 82, 110, 34, 87, 36, 0, 17, 2, 195, 183, 70, 37, 82, 37, 86, 6, 36, 10, 48, 6, 35, 34, 0, 0, 6, 130, 195, 180, 14, 43, 11, 2, 194, 188, 113, 10, 49, 6, 35, 34, 0, 0, 12, 2, 194, 189, 113, 10, 70, 13, 63, 6, 37, 0, 0, 10, 2, 194, 186, 70, 13, 79, 34, 36, 0, 13, 4, 95, 3, 5, 4, 87, 36, 70, 6, 37, 57, 0, 0, 8, 197, 25, 84, 133, 57, 64, 76, 0, 15, 70, 13, 35, 193, 80, 145, 64, 49, 34, 39, 35, 87, 37, 0, 17, 70, 48, 244, 147, 69, 81, 64, 55, 125, 34, 87, 49, 8, 13, 0, 76, 15, 67, 77, 100, 0, 87, 37, 55, 82, 127, 48, 55, 6, 110, 0, 10, 2, 194, 184, 87, 36, 70, 37, 57, 0, 0, 12, 67, 60, 225, 192, 39, 4, 110, 50, 88, 36, 0, 15, 4, 95, 12, 9, 7, 55, 37, 79, 35, 47, 6, 109, 34, 0, 5, 130, 195, 177, 43, 0, 0, 19, 70, 12, 19, 22, 4, 67, 211, 99, 97, 108, 118, 97, 100, 111, 115, 115, 0, 29, 14, 69, 100, 19, 213, 73, 64, 23, 37, 35, 40, 34, 47, 0, 10, 67, 8, 145, 78, 69, 37, 112, 132, 0, 6, 195, 80, 83, 0, 76, 0, 16, 70, 44, 20, 129, 60, 177, 64, 49, 35, 34, 35, 39, 49, 36, 0, 16, 70, 9, 35, 199, 48, 145, 64, 98, 114, 101, 117, 105, 108, 0, 29, 6, 194, 80, 80, 72, 32, 5, 130, 195, 188, 43, 0, 17, 70, 48, 148, 212, 8, 246, 0, 55, 37, 87, 47, 69, 125, 49, 87, 0, 6, 195, 76, 242, 64, 76, 0, 0, 5, 130, 195, 187, 43, 0, 0, 6, 195, 52, 50, 64, 17, 5, 130, 195, 185, 43, 0, 0, 10, 67, 4, 49, 82, 35, 87, 110, 34, 0, 11, 67, 24, 145, 82, 81, 57, 36, 34, 0, 36, 0, 6, 194, 81, 80, 76, 32, 0, 6, 195, 72, 21, 16, 17, 12, 67, 60, 115, 64, 39, 88, 4, 36, 110, 63, 0, 0, 11, 68, 12, 243, 77, 20, 49, 125, 63, 0, 76, 7, 196, 88, 242, 67, 36, 76, 0, 0, 0, 9, 67, 32, 211, 64, 105, 115, 63, 0, 0, 0, 14, 69, 80, 245, 84, 21, 48, 47, 6, 40, 47, 141, 0, 76, 0, 0, 0, 0, 0, 0, 18, 71, 77, 112, 90, 36, 192, 78, 16, 87, 58, 35, 86, 37, 55, 111, 70, 0, 18, 71, 29, 35, 197, 56, 192, 78, 16, 79, 34, 39, 110, 50, 55, 111, 70, 0, 0, 11, 68, 12, 240, 213, 76, 49, 125, 49, 109, 0, 7, 196, 4, 145, 78, 80, 76, 0, 0, 7, 66, 85, 64, 109, 47, 0, 0, 18, 71, 77, 69, 84, 80, 112, 82, 80, 89, 47, 40, 47, 79, 35, 34, 47, 0, 6, 195, 64, 85, 64, 76, 0, 0, 0, 0, 0, 12, 4, 6, 195, 187, 20, 81, 109, 138, 0, 76, 36, 0, 12, 67, 72, 145, 78, 34, 37, 6, 112, 132, 0, 76, 0, 0, 8, 67, 8, 22, 64, 21, 0, 10, 0, 0, 12, 69, 32, 20, 133, 56, 112, 23, 35, 34, 111, 0, 0, 0, 0, 0, 14, 69, 12, 147, 133, 52, 16, 87, 37, 50, 36, 63, 35, 0, 0, 0, 10, 67, 24, 21, 84, 81, 39, 138, 0, 76, 0, 9, 68, 36, 228, 21, 80, 21, 0, 10, 10, 68, 64, 242, 78, 28, 48, 58, 112, 0, 7, 2, 95, 6, 110, 81, 0, 0, 8, 195, 48, 85, 82, 72, 36, 40, 7, 195, 48, 85, 82, 72, 34, 0, 0, 6, 2, 95, 5, 13, 0, 0, 0, 0, 6, 2, 95, 9, 37, 0, 0, 7, 2, 95, 8, 35, 89, 0, 0, 13, 67, 37, 32, 192, 123, 4, 110, 34, 23, 87, 36, 0, 6, 2, 95, 15, 39, 0, 0, 8, 196, 88, 245, 18, 20, 72, 34, 8, 196, 56, 245, 18, 20, 72, 34, 7, 2, 95, 14, 110, 50, 0, 0, 7, 2, 95, 13, 110, 63, 0, 0, 7, 2, 95, 12, 110, 55, 0, 0, 6, 195, 88, 21, 88, 76, 7, 195, 85, 48, 64, 17, 42, 7, 2, 95, 19, 110, 87, 0, 0, 7, 196, 64, 242, 78, 80, 37, 7, 196, 64, 242, 78, 80, 76, 7, 2, 95, 18, 110, 34, 0, 0, 0, 16, 70, 76, 48, 78, 56, 84, 128, 87, 49, 35, 50, 115, 34, 0, 37, 16, 70, 76, 48, 78, 56, 84, 128, 87, 49, 35, 50, 36, 118, 0, 36, 0, 0, 19, 72, 8, 19, 135, 48, 17, 5, 76, 128, 69, 111, 79, 55, 35, 70, 110, 89, 0, 0, 18, 9, 195, 169, 12, 15, 17, 21, 5, 14, 20, 36, 55, 39, 49, 111, 138, 0, 25, 5, 14, 39, 5, 19, 20, 50, 6, 110, 87, 15, 48, 6, 35, 141, 0, 82, 99, 101, 32, 112, 97, 115, 32, 6, 2, 95, 21, 109, 0, 0, 13, 4, 95, 226, 136, 158, 37, 50, 81, 37, 50, 37, 0, 0, 7, 195, 76, 243, 148, 76, 36, 0, 0, 22, 69, 4, 68, 204, 81, 96, 35, 70, 36, 110, 87, 6, 110, 55, 15, 47, 36, 82, 6, 36, 0, 13, 2, 95, 25, 11, 37, 12, 79, 34, 6, 110, 49, 0, 0, 8, 2, 95, 24, 37, 49, 87, 0, 0, 26, 67, 25, 146, 64, 81, 115, 34, 15, 57, 115, 34, 15, 123, 50, 81, 115, 34, 63, 6, 110, 57, 89, 115, 50, 0, 0, 0, 0, 0, 15, 70, 76, 48, 78, 56, 84, 147, 87, 49, 35, 50, 115, 34, 0, 7, 195, 49, 82, 64, 76, 32, 9, 2, 95, 35, 70, 57, 110, 86, 0, 0, 6, 195, 76, 245, 83, 76, 10, 2, 95, 34, 79, 37, 57, 63, 110, 0, 0, 8, 197, 12, 243, 148, 72, 80, 76, 22, 2, 95, 33, 48, 58, 112, 15, 70, 110, 49, 87, 49, 55, 35, 63, 35, 87, 57, 6, 114, 0, 0, 0, 6, 195, 88, 21, 84, 76, 9, 67, 76, 243, 128, 87, 114, 0, 37, 7, 195, 76, 243, 128, 76, 34, 14, 2, 95, 39, 35, 48, 39, 87, 47, 34, 6, 125, 81, 0, 0, 18, 2, 95, 38, 10, 36, 10, 49, 39, 63, 110, 34, 87, 37, 6, 35, 55, 0, 0, 0, 7, 195, 20, 195, 5, 76, 32, 19, 67, 52, 195, 5, 109, 97, 100, 101, 109, 111, 105, 115, 101, 108, 108, 101, 0, 29, 0, 9, 67, 8, 147, 128, 69, 37, 50, 0, 16, 71, 52, 84, 211, 36, 85, 82, 76, 63, 36, 87, 57, 130, 141, 0, 0, 16, 4, 95, 3, 1, 16, 63, 35, 88, 109, 87, 49, 6, 109, 55, 0, 0, 9, 197, 76, 243, 77, 21, 48, 76, 36, 18, 2, 95, 41, 48, 35, 34, 111, 47, 110, 86, 10, 70, 34, 58, 35, 47, 0, 0, 16, 70, 85, 4, 5, 72, 53, 84, 109, 48, 110, 34, 49, 115, 47, 0, 16, 2, 95, 40, 48, 35, 34, 111, 47, 110, 86, 10, 79, 39, 89, 0, 0, 8, 67, 32, 84, 128, 21, 0, 10, 13, 2, 95, 47, 69, 35, 34, 39, 69, 55, 37, 49, 0, 0, 15, 70, 72, 84, 211, 20, 229, 0, 34, 13, 87, 6, 111, 138, 0, 10, 2, 95, 46, 23, 48, 58, 2, 112, 0, 0, 9, 2, 95, 45, 47, 37, 34, 110, 0, 0, 8, 67, 32, 84, 133, 21, 0, 10, 11, 2, 95, 44, 82, 37, 34, 79, 109, 55, 0, 0, 8, 67, 53, 36, 192, 21, 0, 10, 10, 2, 95, 51, 47, 34, 58, 35, 141, 0, 0, 19, 68, 76, 18, 78, 80, 87, 112, 49, 55, 40, 0, 81, 99, 108, 111, 117, 100, 32, 8, 2, 95, 50, 70, 130, 141, 0, 0, 6, 2, 95, 49, 113, 0, 0, 10, 2, 95, 48, 86, 36, 34, 39, 0, 76, 0, 8, 2, 95, 55, 87, 110, 47, 0, 0, 9, 198, 64, 197, 80, 5, 37, 0, 76, 8, 2, 95, 54, 87, 37, 142, 0, 0, 8, 2, 95, 53, 87, 112, 49, 0, 0, 9, 2, 95, 52, 49, 35, 47, 34, 0, 0, 16, 2, 95, 59, 48, 58, 112, 15, 82, 37, 34, 79, 6, 109, 55, 0, 0, 13, 2, 95, 58, 70, 6, 130, 15, 48, 58, 6, 112, 0, 0, 8, 2, 95, 57, 50, 115, 81, 0, 0, 9, 2, 95, 56, 23, 109, 37, 139, 0, 0, 21, 2, 95, 63, 48, 58, 112, 15, 70, 112, 47, 110, 34, 39, 79, 35, 87, 57, 6, 114, 0, 0, 13, 2, 95, 62, 87, 109, 48, 36, 34, 37, 115, 34, 0, 0, 9, 2, 95, 61, 36, 79, 35, 55, 0, 0, 12, 2, 95, 60, 112, 81, 36, 34, 37, 115, 34, 0, 0, 8, 67, 72, 150, 128, 34, 37, 0, 0, 0, 0, 15, 70, 52, 84, 135, 84, 86, 128, 63, 110, 34, 79, 110, 86, 0, 0, 10, 134, 5, 195, 187, 20, 5, 19, 76, 36, 10, 134, 6, 195, 187, 20, 5, 19, 76, 36, 0, 0, 0, 0, 19, 71, 8, 19, 1, 8, 243, 11, 4, 69, 35, 55, 35, 69, 125, 55, 49, 35, 0, 0, 0, 18, 8, 2, 195, 169, 12, 1, 18, 21, 19, 69, 36, 55, 35, 34, 109, 87, 0, 8, 197, 9, 35, 20, 81, 144, 17, 0, 0, 0, 13, 70, 88, 147, 131, 20, 229, 0, 82, 112, 87, 111, 0, 12, 68, 48, 20, 197, 72, 55, 35, 86, 110, 34, 0, 0, 0, 16, 70, 4, 225, 197, 48, 84, 192, 111, 50, 88, 36, 55, 110, 87, 0, 0, 12, 67, 85, 48, 128, 109, 12, 110, 87, 69, 36, 0, 0, 9, 68, 64, 18, 78, 80, 21, 0, 10, 15, 70, 12, 243, 147, 20, 229, 0, 49, 114, 87, 6, 111, 138, 0, 0, 29, 67, 12, 129, 70, 99, 104, 195, 169, 100, 101, 117, 118, 114, 101, 115, 0, 29, 81, 100, 39, 111, 101, 117, 118, 114, 101, 115, 32, 27, 67, 12, 129, 70, 99, 104, 195, 169, 100, 101, 117, 118, 114, 101, 0, 29, 81, 100, 39, 111, 101, 117, 118, 114, 101, 32, 10, 67, 4, 192, 78, 35, 55, 35, 50, 0, 0, 15, 70, 8, 18, 1, 52, 20, 192, 69, 35, 35, 63, 35, 87, 0, 9, 198, 69, 81, 76, 48, 84, 192, 76, 0, 18, 9, 17, 21, 5, 12, 17, 21, 39, 21, 14, 49, 110, 55, 49, 113, 0, 76, 6, 195, 36, 65, 64, 17, 16, 4, 95, 226, 128, 153, 35, 48, 39, 87, 47, 34, 6, 125, 81, 0, 0, 16, 4, 95, 226, 128, 152, 35, 48, 39, 87, 47, 34, 6, 125, 81, 0, 17, 4, 95, 4, 15, 20, 48, 58, 112, 87, 109, 87, 49, 34, 6, 37, 0, 0, 13, 69, 9, 81, 134, 21, 32, 69, 130, 81, 115, 34, 0, 0, 9, 67, 4, 64, 77, 35, 70, 111, 0, 0, 8, 67, 76, 129, 64, 21, 0, 10, 14, 2, 95, 91, 49, 34, 125, 89, 110, 10, 79, 39, 89, 0, 0, 0, 0, 5, 194, 84, 176, 17, 0, 17, 71, 32, 85, 82, 80, 147, 206, 76, 23, 115, 34, 47, 57, 114, 141, 0, 11, 2, 95, 95, 87, 40, 55, 37, 65, 36, 0, 0, 15, 70, 48, 22, 129, 72, 85, 0, 55, 35, 86, 35, 34, 110, 0, 9, 68, 40, 19, 69, 76, 21, 0, 10, 12, 68, 4, 67, 73, 56, 35, 70, 63, 37, 50, 0, 15, 2, 95, 94, 87, 37, 34, 49, 114, 81, 55, 110, 49, 87, 0, 0, 15, 2, 95, 93, 49, 34, 125, 89, 110, 10, 70, 34, 58, 35, 0, 0, 17, 67, 88, 148, 0, 82, 4, 37, 15, 4, 35, 57, 15, 48, 6, 37, 0, 12, 2, 95, 92, 69, 35, 49, 87, 55, 35, 89, 0, 0, 0, 12, 68, 60, 20, 201, 76, 39, 35, 86, 37, 87, 0, 0, 0, 16, 2, 95, 96, 35, 49, 87, 6, 111, 10, 79, 34, 6, 35, 82, 0, 0, 0, 0, 16, 69, 4, 148, 130, 85, 48, 97, 105, 114, 98, 117, 115, 115, 0, 29, 0, 0, 0, 0, 8, 197, 80, 19, 132, 37, 48, 76, 0, 16, 4, 95, 7, 18, 22, 35, 49, 87, 111, 79, 34, 6, 35, 82, 0, 0, 8, 67, 20, 66, 84, 21, 0, 10, 20, 67, 88, 148, 192, 82, 37, 86, 35, 82, 37, 0, 82, 195, 160, 32, 118, 105, 115, 32, 6, 195, 76, 244, 192, 17, 0, 0, 6, 195, 12, 129, 90, 76, 0, 0, 12, 71, 8, 197, 69, 80, 243, 212, 32, 21, 0, 10, 9, 67, 8, 148, 192, 69, 37, 87, 0, 11, 67, 16, 84, 192, 70, 121, 141, 0, 72, 34, 21, 67, 48, 84, 192, 55, 121, 15, 55, 130, 34, 0, 76, 32, 81, 108, 101, 117, 114, 115, 32, 20, 67, 48, 84, 192, 55, 121, 15, 55, 130, 34, 0, 76, 32, 81, 108, 101, 117, 114, 32, 11, 67, 80, 84, 192, 47, 121, 141, 0, 72, 34, 12, 67, 48, 84, 192, 55, 121, 141, 0, 36, 40, 72, 11, 67, 48, 84, 192, 55, 121, 141, 0, 34, 76, 0, 0, 0, 13, 70, 28, 83, 210, 28, 84, 192, 88, 125, 34, 88, 0, 15, 70, 25, 32, 78, 12, 148, 192, 81, 34, 111, 87, 37, 87, 0, 0, 0, 10, 68, 12, 242, 78, 28, 49, 58, 112, 0, 0, 12, 69, 4, 36, 197, 57, 64, 35, 69, 87, 111, 0, 0, 0, 15, 2, 95, 123, 35, 49, 125, 55, 35, 70, 10, 79, 39, 89, 0, 13, 4, 95, 4, 9, 1, 47, 34, 36, 63, 6, 35, 0, 0, 0, 13, 69, 5, 85, 15, 85, 32, 39, 47, 40, 34, 0, 76, 0, 20, 70, 5, 81, 9, 8, 193, 64, 21, 0, 10, 81, 109, 97, 110, 97, 103, 101, 114, 32, 8, 66, 80, 240, 47, 40, 0, 76, 0, 0, 0, 8, 67, 100, 85, 0, 21, 0, 10, 17, 2, 95, 125, 35, 49, 125, 55, 35, 70, 10, 70, 34, 58, 35, 47, 0, 0, 16, 70, 100, 241, 200, 61, 84, 148, 23, 37, 39, 79, 40, 34, 47, 0, 18, 2, 95, 124, 69, 35, 34, 10, 82, 110, 34, 47, 37, 49, 6, 35, 55, 0, 0, 17, 70, 4, 197, 5, 72, 81, 207, 35, 55, 47, 110, 34, 36, 79, 39, 0, 0, 9, 68, 5, 4, 12, 20, 21, 0, 10, 0, 16, 70, 9, 35, 215, 28, 194, 69, 98, 114, 101, 117, 105, 108, 0, 29, 15, 69, 52, 36, 143, 48, 16, 110, 63, 69, 34, 39, 55, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 67, 61, 1, 78, 21, 0, 10, 0, 6, 194, 84, 224, 34, 76, 0, 0, 0, 0, 0, 6, 195, 81, 96, 64, 17, 0, 0, 0, 8, 67, 25, 33, 69, 21, 0, 10, 0, 10, 67, 25, 33, 68, 81, 34, 110, 70, 0, 0, 0, 12, 69, 9, 81, 7, 21, 64, 69, 109, 73, 110, 0, 0, 12, 4, 95, 35, 51, 50, 110, 87, 48, 35, 87, 0, 0, 12, 67, 20, 65, 128, 13, 70, 4, 36, 110, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 70, 4, 52, 143, 8, 21, 0, 97, 99, 114, 111, 98, 97, 116, 101, 0, 29, 0, 0, 11, 70, 61, 85, 12, 60, 242, 192, 21, 0, 10, 5, 194, 97, 144, 17, 0, 11, 67, 25, 33, 84, 81, 34, 6, 110, 47, 0, 12, 67, 4, 67, 128, 35, 70, 4, 36, 110, 50, 0, 0, 16, 70, 28, 19, 135, 77, 65, 82, 79, 111, 79, 87, 47, 110, 34, 0, 0, 9, 67, 105, 85, 0, 86, 109, 47, 0, 0, 16, 70, 21, 66, 5, 72, 225, 84, 36, 47, 110, 34, 50, 110, 47, 0, 0, 18, 71, 4, 100, 137, 44, 16, 78, 76, 35, 81, 34, 37, 49, 35, 50, 87, 0, 0, 0, 8, 197, 40, 19, 65, 37, 48, 76, 0, 38, 70, 36, 229, 5, 72, 225, 84, 112, 47, 110, 34, 50, 6, 110, 47, 15, 110, 49, 87, 48, 55, 125, 34, 6, 115, 34, 0, 81, 101, 120, 112, 108, 111, 114, 101, 114, 32, 17, 70, 36, 229, 5, 72, 225, 84, 112, 47, 110, 34, 50, 6, 110, 47, 0, 0, 0, 9, 198, 12, 243, 77, 20, 229, 0, 76, 0, 0, 12, 70, 40, 16, 209, 84, 84, 192, 88, 35, 49, 0, 0, 0, 0, 0, 0, 6, 195, 13, 5, 64, 17, 0, 12, 68, 4, 195, 210, 76, 35, 55, 125, 34, 0, 76, 0, 0, 0, 0, 0, 14, 69, 64, 243, 4, 21, 32, 48, 125, 55, 70, 110, 34, 0, 0, 0, 14, 67, 28, 134, 128, 88, 37, 79, 35, 110, 34, 47, 87, 0, 0, 0, 9, 67, 88, 245, 0, 82, 125, 47, 0, 0, 0, 14, 67, 44, 134, 128, 49, 37, 55, 39, 110, 34, 47, 87, 0, 0, 9, 68, 8, 197, 69, 76, 21, 0, 10, 0, 10, 69, 28, 243, 199, 48, 80, 21, 0, 10, 0, 19, 9, 16, 1, 20, 1, 17, 21, 195, 168, 19, 48, 35, 47, 35, 49, 110, 87, 0, 0, 0, 0, 0, 9, 134, 22, 15, 9, 12, 195, 160, 76, 0, 11, 67, 9, 37, 84, 69, 34, 6, 109, 47, 0, 0, 0, 13, 69, 8, 148, 211, 85, 48, 69, 37, 87, 109, 87, 0, 0, 0, 0, 7, 196, 5, 85, 18, 20, 76, 0, 14, 69, 88, 148, 135, 36, 224, 82, 37, 34, 88, 37, 50, 0, 0, 14, 67, 96, 96, 197, 37, 49, 87, 110, 81, 87, 36, 13, 0, 0, 6, 195, 12, 144, 64, 17, 0, 0, 16, 70, 77, 84, 208, 20, 228, 197, 87, 109, 87, 48, 110, 50, 87, 0, 0, 16, 70, 72, 21, 9, 60, 228, 192, 34, 35, 47, 57, 114, 141, 0, 36, 15, 70, 16, 21, 9, 60, 228, 192, 70, 35, 47, 57, 114, 141, 0, 11, 70, 12, 243, 12, 36, 228, 192, 21, 0, 10, 0, 13, 67, 52, 209, 64, 109, 97, 100, 97, 109, 101, 0, 29, 0, 0, 21, 73, 12, 243, 147, 80, 21, 9, 60, 228, 192, 49, 114, 87, 47, 35, 47, 57, 114, 141, 0, 10, 69, 12, 83, 148, 21, 32, 21, 0, 10, 8, 197, 17, 84, 129, 57, 64, 76, 0, 23, 6, 17, 21, 39, 5, 19, 20, 49, 110, 87, 49, 13, 0, 72, 82, 99, 101, 32, 113, 117, 101, 32, 0, 6, 195, 85, 65, 128, 17, 0, 0, 0, 0, 9, 67, 92, 146, 64, 58, 37, 12, 0, 6, 195, 80, 242, 64, 76, 0, 9, 68, 48, 241, 207, 56, 21, 0, 10, 0, 0, 0, 10, 199, 80, 245, 84, 20, 99, 201, 76, 76, 0, 0, 0, 0, 12, 71, 52, 84, 211, 20, 225, 197, 72, 21, 0, 10, 0, 0, 6, 195, 48, 242, 78, 76, 0, 8, 67, 76, 19, 69, 21, 0, 10, 0, 0, 9, 68, 4, 35, 213, 80, 21, 0, 10, 0, 12, 69, 76, 245, 82, 37, 48, 87, 40, 34, 37, 0, 0, 15, 70, 48, 84, 207, 80, 131, 192, 55, 36, 86, 125, 47, 39, 0, 0, 0, 9, 68, 48, 241, 201, 56, 21, 0, 10, 0, 0, 16, 70, 88, 245, 9, 60, 228, 192, 82, 125, 39, 47, 57, 114, 141, 0, 0, 7, 195, 36, 196, 192, 76, 32, 0, 12, 68, 76, 208, 82, 80, 87, 63, 35, 34, 47, 0, 9, 68, 80, 129, 82, 20, 21, 0, 10, 0, 0, 0, 0, 0, 23, 73, 21, 132, 12, 60, 149, 9, 60, 228, 192, 110, 49, 87, 48, 55, 58, 35, 47, 57, 114, 141, 0, 0, 0, 14, 67, 4, 68, 204, 35, 70, 4, 36, 110, 87, 110, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 7, 20, 1, 195, 175, 23, 1, 14, 47, 35, 57, 58, 35, 50, 0, 8, 197, 64, 51, 67, 36, 16, 17, 0, 0, 0, 0, 6, 20, 0, 0, 83, 1, 0, 0, 111, 0, 101, 0, 0, 0, 0, 0, 6, 18, 66, 100, 0, 101, 0, 108, 0, 110, 0, 114, 0, 116, 0, 117, 0, 7, 6, 18, 67, 98, 0, 99, 0, 100, 0, 102, 0, 103, 0, 104, 0, 107, 0, 112, 0, 116, 0, 118, 0, 7, 6, 18, 68, 100, 0, 108, 0, 109, 0, 110, 0, 115, 0, 116, 0, 118, 0, 7, 6, 18, 69, 99, 0, 100, 0, 102, 0, 103, 0, 108, 0, 109, 0, 110, 0, 118, 0, 7, 6, 18, 70, 103, 0, 104, 0, 107, 0, 108, 0, 109, 0, 118, 0, 119, 0, 7, 6, 18, 71, 98, 108, 0, 98, 114, 0, 99, 108, 0, 99, 114, 0, 99, 116, 0, 100, 114, 0, 102, 108, 0, 102, 114, 0, 102, 116, 0, 103, 108, 0, 103, 114, 0, 107, 108, 0, 107, 114, 0, 112, 108, 0, 112, 114, 0, 116, 114, 0, 118, 114, 0, 7, 6, 18, 72, 195, 169, 99, 0, 195, 169, 100, 0, 101, 99, 0, 101, 100, 0, 108, 98, 0, 108, 99, 0, 108, 100, 0, 108, 103, 0, 108, 109, 0, 108, 110, 0, 108, 112, 0, 108, 116, 0, 108, 118, 0, 114, 98, 0, 114, 99, 0, 114, 100, 0, 114, 102, 0, 114, 103, 0, 114, 108, 0, 114, 109, 0, 114, 110, 0, 114, 112, 0, 114, 115, 0, 114, 116, 0, 114, 118, 0, 7, 6, 18, 73, 99, 104, 0, 113, 117, 0, 103, 117, 0, 98, 0, 99, 0, 100, 0, 102, 0, 103, 0, 104, 0, 106, 0, 107, 0, 108, 0, 109, 0, 110, 0, 112, 0, 113, 0, 114, 0, 115, 0, 116, 0, 118, 0, 119, 0, 120, 0, 122, 0, 7, 6, 18, 74, 108, 0, 114, 0, 115, 0, 7, 6, 18, 75, 105, 97, 0, 105, 101, 0, 105, 111, 0, 117, 97, 0, 117, 101, 0, 117, 105, 0, 117, 111, 0, 7, 6, 18, 76, 98, 0, 112, 0, 7, 6, 18, 77, 97, 195, 175, 0, 114, 195, 169, 0, 195, 169, 0, 195, 168, 0, 97, 108, 0, 105, 98, 0, 105, 101, 0, 105, 113, 0, 111, 109, 0, 111, 110, 0, 121, 109, 0, 108, 0, 7, 6, 18, 78, 101, 114, 0, 104, 110, 0, 100, 0, 103, 0, 107, 0, 108, 0, 112, 0, 7, 6, 18, 79, 98, 101, 0, 105, 110, 0, 117, 112, 0, 117, 116, 0, 7, 6, 18, 80, 99, 0, 102, 0, 103, 0, 104, 0, 7, 6, 18, 81, 48, 48, 0, 48, 49, 0, 48, 50, 0, 48, 51, 0, 48, 52, 0, 48, 53, 0, 48, 54, 0, 48, 55, 0, 48, 56, 0, 48, 57, 0, 49, 48, 0, 49, 49, 0, 49, 50, 0, 49, 51, 0, 49, 52, 0, 49, 53, 0, 49, 54, 0, 49, 55, 0, 49, 56, 0, 49, 57, 0, 50, 48, 0, 50, 49, 0, 50, 50, 0, 50, 51, 0, 48, 0, 49, 0, 50, 0, 51, 0, 52, 0, 53, 0, 54, 0, 55, 0, 56, 0, 57, 0, 7, 6, 18, 82, 48, 0, 49, 0, 50, 0, 51, 0, 52, 0, 53, 0, 7, 6, 195, 167, 0, 4, 3, 87, 0, 39, 8, 2, 14, 128, 140, 130, 0, 7, 6, 195, 168, 0, 109, 101, 1, 16, 3, 37, 110, 63, 0, 4, 3, 110, 0, 115, 2, 32, 0, 4, 115, 1, 109, 2, 32, 3, 110, 87, 0, 115, 1, 110, 2, 32, 0, 115, 1, 112, 2, 32, 0, 115, 1, 114, 17, 65, 2, 32, 0, 7, 6, 195, 171, 0, 1, 117, 3, 0, 1, 111, 110, 2, 32, 3, 36, 0, 3, 110, 0, 7, 6, 195, 175, 0, 3, 37, 0, 115, 1, 97, 17, 67, 2, 32, 3, 37, 87, 0, 4, 1, 17, 65, 2, 32, 3, 57, 0, 1, 17, 65, 2, 108, 17, 65, 0, 101, 1, 17, 65, 2, 32, 0, 110, 2, 25, 3, 112, 0, 7, 6, 195, 180, 0, 4, 3, 39, 0, 116, 2, 32, 0, 7, 6, 195, 188, 0, 109, 2, 32, 3, 39, 63, 0, 3, 109, 0, 108, 2, 32, 3, 109, 55, 55, 0, 115, 2, 32, 3, 109, 87, 0, 7, 6, 97, 0, 2, 195, 180, 3, 0, 105, 1, 102, 2, 115, 17, 65, 3, 13, 0, 4, 110, 121, 3, 21, 0, 119, 2, 25, 0, 4, 3, 35, 0, 2, 105, 108, 25, 0, 2, 110, 110, 17, 65, 0, 109, 2, 109, 0, 109, 2, 110, 0, 110, 2, 110, 32, 0, 4, 114, 99, 104, 8, 2, 97, 14, 128, 132, 132, 3, 35, 34, 49, 0, 114, 99, 104, 8, 2, 111, 14, 128, 132, 132, 0, 114, 99, 104, 195, 169, 8, 2, 21, 14, 128, 132, 133, 3, 35, 34, 49, 36, 0, 114, 99, 104, 195, 169, 111, 8, 2, 21, 14, 128, 132, 134, 3, 35, 34, 49, 36, 39, 0, 111, 195, 187, 116, 2, 105, 3, 35, 40, 87, 0, 4, 110, 1, 109, 18, 67, 2, 32, 3, 35, 50, 0, 110, 1, 109, 21, 21, 2, 32, 0, 110, 1, 109, 122, 2, 32, 0, 110, 1, 119, 2, 32, 0, 110, 2, 104, 0, 110, 8, 18, 69, 2, 32, 0, 110, 8, 104, 2, 32, 0, 110, 97, 114, 99, 104, 111, 8, 2, 21, 14, 128, 132, 135, 3, 35, 50, 35, 34, 49, 39, 0, 4, 121, 2, 97, 107, 3, 35, 57, 0, 121, 101, 1, 98, 98, 2, 32, 0, 4, 109, 1, 104, 2, 32, 14, 128, 128, 130, 3, 35, 63, 0, 109, 8, 2, 110, 0, 101, 3, 35, 110, 0, 4, 101, 2, 32, 3, 36, 0, 105, 2, 32, 0, 121, 101, 1, 98, 98, 2, 29, 3, 36, 37, 0, 4, 117, 3, 39, 0, 117, 100, 2, 32, 0, 117, 116, 111, 8, 2, 21, 14, 128, 132, 132, 3, 39, 47, 39, 0, 117, 116, 111, 109, 8, 2, 110, 3, 39, 47, 125, 0, 117, 100, 8, 17, 67, 2, 32, 3, 39, 70, 0, 117, 100, 105, 111, 8, 2, 21, 14, 128, 132, 133, 3, 39, 70, 37, 39, 0, 117, 116, 2, 32, 3, 39, 138, 0, 4, 111, 117, 1, 115, 2, 108, 101, 3, 40, 0, 111, 117, 108, 1, 115, 2, 32, 0, 111, 195, 187, 116, 3, 40, 47, 0, 4, 105, 3, 110, 0, 105, 8, 108, 97, 98, 2, 32, 0, 105, 8, 114, 118, 2, 32, 0, 105, 8, 115, 115, 101, 2, 32, 0, 105, 101, 0, 121, 2, 17, 67, 0, 121, 2, 32, 0, 121, 3, 110, 57, 0, 121, 101, 114, 1, 108, 29, 2, 29, 3, 110, 57, 115, 34, 0, 4, 105, 101, 110, 116, 3, 110, 138, 0, 105, 116, 2, 32, 0, 105, 115, 2, 32, 3, 110, 141, 0, 4, 101, 110, 3, 111, 0, 109, 2, 18, 76, 0, 110, 1, 109, 108, 117, 2, 32, 0, 110, 1, 109, 115, 105, 108, 2, 32, 0, 110, 2, 25, 0, 110, 8, 109, 175, 195, 97, 99, 2, 32, 0, 111, 110, 8, 17, 67, 2, 32, 0, 4, 110, 116, 105, 8, 2, 17, 67, 17, 65, 29, 14, 128, 132, 132, 3, 111, 47, 37, 0, 110, 116, 105, 8, 2, 21, 21, 14, 128, 132, 132, 0, 4, 105, 109, 2, 25, 3, 112, 0, 105, 110, 2, 25, 0, 4, 105, 110, 1, 104, 99, 2, 32, 3, 112, 132, 0, 105, 110, 1, 116, 17, 67, 2, 32, 0, 4, 117, 2, 108, 32, 3, 125, 0, 117, 2, 114, 101, 32, 0, 7, 6, 98, 0, 1, 109, 111, 2, 32, 3, 0, 4, 97, 99, 107, 3, 21, 0, 101, 8, 2, 18, 80, 17, 65, 0, 111, 97, 114, 100, 0, 111, 120, 2, 32, 0, 117, 103, 103, 0, 4, 3, 69, 0, 98, 0, 7, 6, 99, 0, 4, 1, 97, 98, 97, 116, 2, 32, 3, 0, 4, 1, 97, 109, 111, 116, 2, 32, 3, 0, 4, 1, 110, 97, 17, 67, 2, 32, 3, 0, 4, 1, 110, 111, 17, 67, 2, 32, 3, 0, 4, 1, 114, 97, 2, 116, 105, 3, 0, 4, 1, 114, 101, 108, 99, 2, 32, 3, 0, 4, 1, 115, 2, 17, 71, 3, 0, 4, 1, 117, 111, 104, 99, 116, 2, 32, 3, 0, 1, 120, 2, 17, 71, 3, 0, 4, 104, 1, 110, 2, 32, 3, 21, 0, 104, 2, 109, 101, 110, 116, 0, 117, 116, 2, 32, 0, 4, 3, 49, 0, 8, 110, 111, 100, 2, 32, 0, 99, 0, 99, 104, 0, 104, 1, 97, 2, 32, 0, 104, 1, 101, 2, 32, 0, 104, 1, 105, 110, 2, 32, 0, 104, 1, 105, 110, 97, 109, 2, 195, 169, 0, 104, 1, 111, 116, 105, 109, 2, 111, 0, 104, 1, 114, 111, 2, 101, 115, 17, 67, 0, 104, 1, 114, 111, 2, 105, 17, 67, 0, 104, 2, 108, 0, 104, 2, 110, 0, 104, 2, 114, 0, 104, 2, 115, 0, 104, 2, 116, 111, 0, 104, 8, 2, 97, 111, 0, 104, 8, 2, 97, 114, 105, 115, 109, 0, 104, 8, 2, 105, 114, 111, 112, 0, 104, 8, 2, 111, 114, 17, 65, 0, 104, 8, 17, 65, 2, 111, 32, 0, 104, 8, 117, 101, 2, 97, 114, 105, 0, 107, 0, 113, 0, 113, 117, 0, 104, 114, 111, 110, 111, 8, 2, 21, 14, 128, 132, 134, 3, 49, 34, 39, 50, 39, 0, 4, 97, 115, 116, 2, 32, 14, 128, 128, 132, 3, 49, 35, 87, 47, 0, 97, 115, 116, 115, 2, 32, 14, 128, 128, 133, 0, 108, 111, 119, 110, 8, 3, 49, 55, 40, 50, 0, 99, 2, 17, 71, 3, 49, 87, 0, 104, 1, 105, 119, 3, 74, 0, 4, 1, 101, 115, 2, 111, 110, 100, 3, 79, 0, 1, 110, 105, 122, 2, 32, 0, 4, 2, 17, 71, 3, 87, 0, 39, 8, 2, 14, 128, 140, 130, 0, 4, 8, 2, 100, 3, 87, 36, 0, 111, 101, 8, 2, 108, 97, 0, 121, 98, 101, 114, 8, 2, 14, 128, 132, 133, 3, 87, 37, 69, 110, 34, 0, 105, 101, 110, 116, 2, 32, 3, 87, 37, 138, 0, 4, 105, 101, 110, 116, 1, 105, 102, 102, 101, 3, 87, 57, 111, 0, 105, 101, 110, 116, 1, 105, 102, 169, 195, 100, 0, 4, 104, 3, 89, 0, 104, 8, 2, 111, 114, 105, 122, 0, 104, 8, 2, 111, 114, 111, 0, 7, 6, 100, 0, 4, 1, 105, 111, 2, 32, 3, 0, 4, 1, 110, 97, 2, 32, 3, 0, 4, 1, 110, 111, 17, 67, 2, 32, 3, 0, 4, 1, 114, 2, 32, 3, 0, 4, 1, 117, 111, 2, 32, 3, 0, 8, 105, 110, 2, 32, 3, 0, 4, 97, 121, 2, 32, 3, 21, 0, 101, 118, 105, 99, 8, 0, 108, 101, 2, 29, 0, 116, 2, 32, 3, 47, 0, 4, 3, 70, 0, 1, 114, 111, 108, 2, 32, 0, 8, 110, 97, 98, 2, 32, 0, 8, 110, 97, 108, 2, 32, 0, 8, 110, 97, 115, 2, 32, 0, 8, 110, 97, 116, 115, 2, 32, 0, 8, 114, 97, 104, 2, 32, 0, 39, 8, 2, 14, 128, 132, 130, 0, 100, 0, 4, 105, 101, 110, 1, 169, 195, 112, 120, 101, 32, 26, 2, 116, 32, 3, 70, 37, 0, 105, 101, 110, 2, 116, 32, 0, 4, 105, 101, 110, 8, 169, 195, 112, 120, 101, 2, 116, 32, 3, 70, 57, 111, 0, 105, 101, 110, 8, 169, 195, 114, 103, 110, 105, 2, 116, 32, 0, 101, 110, 100, 114, 111, 8, 2, 21, 14, 128, 132, 134, 3, 70, 112, 70, 34, 39, 0, 4, 1, 110, 101, 17, 67, 2, 32, 3, 138, 0, 1, 110, 101, 117, 113, 2, 32, 0, 1, 110, 111, 99, 2, 32, 0, 8, 110, 97, 114, 103, 2, 32, 0, 7, 6, 101, 0, 4, 1, 17, 65, 2, 114, 17, 65, 3, 0, 4, 1, 17, 67, 2, 45, 3, 0, 4, 1, 18, 73, 21, 2, 17, 67, 17, 65, 3, 0, 4, 1, 18, 73, 21, 2, 18, 71, 3, 0, 4, 1, 99, 45, 2, 32, 3, 0, 4, 1, 103, 2, 17, 65, 3, 0, 4, 1, 105, 2, 109, 17, 65, 3, 0, 4, 1, 106, 45, 2, 32, 3, 0, 4, 2, 32, 3, 0, 4, 2, 111, 105, 3, 0, 4, 110, 1, 108, 111, 26, 2, 116, 32, 3, 0, 4, 110, 1, 118, 117, 111, 99, 32, 26, 2, 116, 32, 3, 0, 110, 1, 118, 117, 111, 99, 32, 115, 2, 116, 32, 3, 0, 195, 175, 2, 25, 3, 6, 110, 57, 0, 4, 3, 13, 0, 1, 17, 67, 21, 2, 17, 67, 101, 17, 67, 17, 65, 0, 1, 18, 71, 21, 2, 17, 67, 17, 65, 0, 1, 18, 71, 21, 2, 18, 71, 0, 1, 18, 72, 21, 2, 17, 67, 17, 65, 0, 1, 18, 72, 21, 2, 18, 71, 0, 1, 18, 73, 21, 2, 17, 67, 18, 75, 17, 67, 0, 1, 18, 73, 21, 2, 18, 71, 18, 75, 17, 67, 0, 1, 100, 2, 115, 115, 117, 115, 32, 0, 1, 114, 116, 2, 17, 67, 17, 65, 0, 1, 114, 116, 2, 17, 67, 104, 17, 65, 0, 1, 117, 103, 18, 74, 21, 2, 17, 67, 17, 65, 0, 1, 117, 103, 18, 74, 21, 2, 18, 71, 0, 1, 117, 113, 18, 74, 21, 2, 17, 67, 17, 65, 0, 1, 117, 113, 18, 74, 21, 2, 18, 71, 0, 2, 17, 67, 108, 0, 2, 17, 67, 114, 0, 8, 100, 2, 99, 104, 0, 8, 108, 2, 17, 67, 17, 65, 0, 8, 108, 2, 17, 67, 104, 17, 65, 0, 8, 108, 2, 17, 67, 108, 17, 65, 0, 8, 114, 2, 99, 104, 0, 8, 114, 2, 115, 115, 0, 8, 114, 2, 115, 116, 114, 97, 0, 8, 114, 2, 115, 116, 114, 111, 0, 8, 114, 2, 115, 116, 114, 117, 0, 8, 17, 67, 2, 32, 3, 14, 0, 4, 8, 2, 17, 67, 101, 29, 3, 21, 0, 97, 0, 100, 2, 32, 0, 101, 0, 102, 111, 114, 101, 2, 32, 0, 105, 110, 103, 2, 32, 0, 105, 118, 101, 0, 108, 2, 17, 67, 29, 0, 110, 104, 97, 110, 8, 0, 110, 116, 101, 114, 8, 2, 32, 0, 115, 115, 2, 32, 0, 115, 116, 1, 117, 113, 2, 32, 0, 115, 116, 101, 1, 117, 113, 2, 29, 32, 0, 118, 101, 110, 2, 32, 0, 118, 101, 114, 1, 17, 67, 111, 0, 118, 101, 114, 8, 0, 119, 2, 12, 12, 0, 121, 101, 8, 0, 4, 109, 1, 21, 2, 109, 101, 3, 35, 0, 109, 1, 108, 2, 110, 0, 109, 8, 102, 2, 109, 101, 0, 4, 2, 114, 105, 32, 12, 12, 3, 36, 0, 2, 114, 105, 97, 32, 12, 12, 0, 2, 114, 111, 32, 12, 12, 0, 8, 2, 17, 67, 11, 0, 8, 2, 17, 67, 17, 65, 0, 8, 2, 17, 67, 17, 65, 24, 0, 8, 2, 18, 71, 17, 65, 0, 8, 109, 2, 103, 97, 0, 8, 114, 2, 115, 115, 117, 0, 8, 116, 114, 97, 2, 12, 12, 0, 100, 1, 105, 112, 2, 32, 0, 102, 8, 108, 99, 2, 32, 0, 114, 2, 32, 0, 114, 2, 115, 32, 0, 115, 1, 109, 17, 65, 2, 100, 17, 65, 0, 115, 1, 109, 17, 65, 2, 110, 17, 65, 0, 115, 8, 100, 2, 98, 17, 65, 0, 115, 8, 100, 2, 106, 17, 65, 0, 115, 8, 100, 2, 110, 17, 65, 0, 115, 8, 100, 2, 113, 17, 65, 0, 115, 8, 108, 2, 113, 17, 65, 0, 115, 8, 109, 2, 100, 17, 65, 0, 115, 8, 109, 2, 110, 17, 65, 0, 115, 104, 1, 100, 2, 17, 65, 3, 36, 86, 0, 114, 1, 119, 101, 105, 2, 29, 3, 36, 118, 0, 122, 2, 32, 3, 36, 141, 0, 97, 117, 2, 12, 12, 3, 39, 0, 4, 117, 1, 103, 2, 114, 101, 3, 109, 0, 117, 8, 2, 115, 115, 0, 195, 187, 8, 0, 117, 116, 8, 2, 32, 3, 109, 138, 0, 4, 1, 104, 103, 2, 116, 17, 65, 29, 3, 110, 0, 1, 105, 2, 114, 116, 32, 0, 1, 112, 97, 99, 2, 108, 97, 32, 0, 2, 17, 67, 17, 67, 0, 2, 17, 67, 32, 0, 2, 99, 116, 12, 12, 12, 12, 12, 0, 2, 105, 108, 0, 2, 114, 17, 67, 0, 2, 114, 114, 12, 12, 12, 0, 2, 120, 12, 12, 12, 12, 12, 0, 8, 17, 67, 101, 2, 17, 67, 17, 65, 12, 12, 0, 98, 1, 102, 2, 118, 17, 65, 0, 99, 116, 1, 112, 2, 32, 0, 105, 0, 108, 2, 108, 0, 109, 2, 109, 97, 0, 110, 1, 105, 17, 67, 2, 110, 17, 65, 0, 110, 2, 110, 17, 65, 0, 116, 1, 107, 99, 105, 116, 2, 32, 0, 121, 2, 17, 67, 0, 121, 2, 32, 0, 4, 114, 1, 107, 99, 111, 2, 25, 3, 110, 34, 0, 114, 1, 110, 105, 97, 116, 2, 29, 0, 114, 1, 116, 115, 17, 67, 2, 29, 0, 114, 8, 17, 67, 2, 32, 0, 114, 8, 104, 17, 67, 2, 32, 0, 114, 8, 105, 102, 2, 32, 0, 114, 8, 105, 104, 2, 32, 0, 114, 8, 105, 116, 2, 32, 0, 114, 8, 116, 114, 97, 99, 2, 29, 0, 114, 8, 118, 105, 104, 2, 29, 0, 114, 8, 118, 110, 101, 2, 32, 0, 4, 116, 1, 103, 100, 2, 32, 3, 110, 47, 0, 116, 1, 107, 2, 32, 0, 99, 116, 2, 32, 3, 110, 49, 47, 0, 4, 120, 116, 114, 97, 8, 2, 17, 67, 14, 128, 132, 133, 3, 110, 49, 87, 47, 34, 35, 0, 120, 116, 114, 97, 8, 2, 117, 14, 128, 132, 133, 0, 4, 105, 110, 8, 2, 25, 3, 110, 50, 0, 110, 1, 17, 67, 2, 32, 0, 110, 1, 17, 67, 2, 116, 111, 32, 0, 110, 8, 121, 2, 32, 0, 110, 115, 1, 112, 115, 2, 32, 3, 110, 50, 87, 0, 108, 2, 115, 29, 3, 110, 55, 0, 121, 3, 110, 57, 0, 109, 110, 1, 108, 105, 3, 110, 63, 0, 115, 116, 1, 45, 2, 32, 3, 110, 87, 47, 0, 116, 1, 109, 2, 32, 3, 110, 138, 0, 4, 109, 2, 18, 76, 3, 111, 0, 109, 2, 109, 17, 65, 17, 67, 17, 65, 17, 67, 0, 109, 2, 109, 17, 65, 17, 67, 17, 67, 0, 109, 2, 109, 97, 105, 0, 110, 1, 17, 67, 2, 100, 32, 0, 110, 1, 17, 67, 111, 17, 67, 109, 105, 2, 116, 32, 0, 110, 1, 17, 67, 111, 17, 67, 110, 105, 2, 116, 32, 0, 110, 1, 17, 67, 169, 195, 2, 116, 32, 0, 110, 1, 17, 67, 169, 195, 2, 116, 32, 0, 110, 1, 99, 97, 106, 2, 116, 32, 0, 110, 1, 99, 99, 2, 116, 32, 0, 110, 1, 99, 105, 116, 169, 195, 2, 116, 32, 0, 110, 1, 99, 115, 17, 65, 2, 116, 32, 0, 110, 1, 100, 105, 17, 67, 169, 195, 2, 116, 32, 0, 110, 1, 100, 105, 99, 17, 67, 17, 65, 29, 2, 116, 32, 0, 110, 1, 100, 105, 114, 116, 29, 2, 116, 32, 0, 110, 1, 100, 117, 17, 67, 2, 116, 32, 0, 110, 1, 103, 110, 105, 21, 21, 2, 116, 32, 0, 110, 1, 103, 114, 101, 118, 2, 116, 32, 0, 110, 1, 105, 17, 67, 2, 99, 0, 110, 1, 105, 116, 97, 112, 0, 110, 1, 108, 97, 118, 105, 2, 116, 32, 0, 110, 1, 108, 108, 101, 99, 120, 2, 116, 32, 0, 110, 1, 108, 111, 2, 116, 32, 0, 110, 1, 108, 117, 2, 116, 32, 0, 110, 1, 109, 97, 17, 67, 105, 2, 116, 32, 0, 110, 1, 109, 97, 109, 114, 2, 116, 32, 0, 110, 1, 109, 101, 2, 116, 32, 0, 110, 1, 109, 103, 2, 116, 32, 0, 110, 1, 109, 105, 17, 67, 17, 67, 17, 65, 17, 67, 2, 116, 32, 0, 110, 1, 109, 105, 97, 17, 65, 2, 116, 32, 0, 110, 1, 109, 105, 97, 17, 67, 2, 116, 32, 0, 110, 1, 109, 105, 100, 2, 116, 32, 0, 110, 1, 109, 105, 103, 17, 65, 2, 116, 32, 0, 110, 1, 109, 105, 108, 17, 65, 2, 116, 32, 0, 110, 1, 109, 105, 108, 112, 2, 116, 32, 0, 110, 1, 109, 105, 110, 97, 109, 2, 116, 32, 0, 110, 1, 109, 105, 110, 105, 2, 116, 32, 0, 110, 1, 109, 105, 110, 111, 2, 116, 32, 0, 110, 1, 109, 105, 115, 17, 65, 2, 116, 32, 0, 110, 1, 109, 105, 116, 17, 65, 2, 116, 32, 0, 110, 1, 109, 109, 2, 116, 32, 0, 110, 1, 109, 111, 109, 2, 116, 32, 0, 110, 1, 109, 114, 101, 2, 116, 32, 0, 110, 1, 109, 114, 117, 111, 116, 2, 116, 32, 0, 110, 1, 109, 117, 17, 67, 111, 2, 116, 32, 0, 110, 1, 109, 117, 100, 2, 116, 32, 0, 110, 1, 109, 117, 103, 2, 116, 32, 0, 110, 1, 109, 117, 106, 2, 116, 32, 0, 110, 1, 109, 117, 114, 2, 116, 32, 0, 110, 1, 110, 97, 109, 2, 116, 32, 0, 110, 1, 110, 105, 109, 109, 105, 2, 116, 32, 0, 110, 1, 110, 105, 109, 169, 195, 111, 2, 116, 32, 0, 110, 1, 110, 105, 116, 110, 111, 2, 116, 32, 0, 110, 1, 110, 105, 116, 114, 101, 2, 116, 32, 0, 110, 1, 112, 114, 17, 65, 29, 2, 116, 32, 0, 110, 1, 114, 97, 112, 115, 2, 116, 32, 0, 110, 1, 114, 114, 17, 65, 17, 67, 2, 116, 32, 0, 110, 1, 116, 105, 110, 169, 195, 2, 116, 32, 0, 110, 1, 116, 116, 105, 109, 2, 116, 32, 0, 110, 1, 117, 108, 102, 17, 67, 2, 116, 32, 0, 110, 1, 117, 113, 2, 100, 32, 0, 110, 1, 117, 113, 169, 195, 2, 116, 32, 0, 110, 2, 17, 67, 17, 65, 0, 110, 2, 17, 67, 17, 67, 0, 110, 2, 110, 117, 0, 110, 2, 115, 32, 0, 110, 8, 17, 67, 2, 116, 32, 0, 110, 8, 100, 114, 97, 2, 116, 32, 0, 110, 8, 103, 97, 2, 116, 32, 0, 110, 8, 103, 114, 97, 2, 116, 32, 0, 110, 8, 103, 114, 101, 115, 2, 116, 32, 0, 110, 8, 103, 114, 117, 2, 116, 32, 0, 110, 8, 108, 97, 116, 2, 116, 32, 0, 110, 8, 108, 111, 100, 2, 116, 32, 0, 110, 8, 109, 105, 99, 2, 116, 32, 0, 110, 8, 109, 105, 112, 2, 116, 32, 0, 110, 8, 109, 114, 17, 65, 115, 2, 116, 32, 0, 110, 8, 110, 105, 109, 169, 195, 2, 116, 32, 0, 110, 8, 114, 97, 112, 2, 116, 32, 0, 110, 8, 114, 97, 112, 112, 97, 2, 116, 32, 0, 110, 8, 114, 97, 118, 2, 116, 32, 0, 110, 8, 114, 111, 108, 102, 2, 116, 32, 0, 110, 8, 114, 117, 97, 108, 2, 116, 32, 0, 110, 8, 116, 97, 108, 2, 116, 32, 0, 110, 8, 116, 97, 112, 2, 116, 32, 0, 110, 8, 116, 110, 111, 99, 2, 116, 32, 0, 110, 8, 116, 110, 111, 99, 169, 195, 109, 2, 116, 32, 0, 110, 8, 118, 117, 111, 99, 2, 116, 14, 128, 160, 131, 0, 110, 8, 118, 117, 111, 115, 2, 116, 32, 0, 110, 115, 1, 99, 110, 2, 32, 0, 4, 110, 2, 104, 17, 65, 3, 111, 50, 0, 110, 8, 2, 17, 65, 0, 110, 2, 32, 3, 111, 132, 0, 4, 110, 116, 1, 103, 105, 100, 110, 2, 32, 3, 111, 138, 0, 110, 116, 1, 103, 105, 108, 105, 2, 32, 0, 110, 116, 1, 103, 105, 108, 108, 2, 32, 0, 110, 116, 1, 103, 110, 97, 116, 2, 32, 0, 110, 115, 1, 17, 67, 169, 195, 2, 32, 3, 111, 141, 0, 4, 105, 110, 2, 25, 3, 112, 0, 110, 1, 17, 65, 17, 65, 2, 32, 0, 110, 1, 100, 111, 2, 100, 114, 0, 110, 1, 105, 17, 67, 2, 25, 0, 110, 1, 109, 97, 120, 2, 32, 0, 110, 1, 112, 112, 97, 2, 100, 105, 0, 110, 1, 169, 195, 2, 32, 0, 110, 8, 17, 67, 2, 106, 0, 110, 8, 109, 97, 108, 102, 2, 99, 0, 105, 110, 1, 108, 112, 2, 32, 3, 112, 132, 0, 4, 1, 104, 99, 116, 2, 114, 29, 3, 115, 0, 1, 116, 114, 101, 118, 2, 114, 29, 0, 117, 1, 103, 0, 117, 2, 17, 67, 29, 0, 117, 2, 17, 67, 101, 29, 0, 117, 2, 105, 0, 117, 2, 108, 101, 29, 0, 117, 2, 114, 17, 67, 0, 117, 2, 114, 101, 29, 0, 117, 2, 114, 114, 101, 29, 0, 4, 114, 1, 107, 99, 97, 2, 25, 3, 115, 34, 0, 114, 1, 107, 99, 111, 114, 2, 25, 0, 114, 8, 116, 116, 117, 99, 2, 29, 0, 97, 109, 1, 114, 17, 67, 3, 123, 12, 63, 0, 97, 110, 101, 114, 1, 108, 17, 67, 3, 123, 50, 115, 34, 0, 97, 109, 101, 114, 1, 114, 17, 67, 3, 123, 63, 115, 34, 0, 4, 117, 3, 130, 0, 117, 2, 17, 67, 101, 29, 0, 117, 2, 17, 67, 101, 114, 32, 0, 117, 2, 108, 101, 114, 0, 195, 187, 3, 130, 12, 0, 117, 116, 2, 32, 3, 130, 138, 0, 117, 120, 2, 32, 3, 130, 141, 0, 4, 110, 116, 1, 17, 65, 2, 32, 3, 138, 0, 110, 116, 1, 100, 105, 17, 67, 169, 195, 26, 2, 32, 0, 110, 116, 1, 103, 105, 2, 32, 0, 110, 116, 1, 103, 114, 101, 118, 26, 2, 32, 0, 110, 116, 1, 103, 114, 117, 32, 26, 2, 32, 0, 110, 116, 1, 108, 97, 118, 105, 26, 2, 32, 0, 110, 116, 1, 108, 108, 101, 99, 120, 26, 2, 32, 0, 110, 116, 1, 108, 111, 29, 2, 32, 0, 110, 116, 1, 108, 117, 26, 2, 32, 0, 110, 116, 1, 108, 117, 99, 17, 67, 2, 32, 0, 110, 116, 1, 108, 117, 101, 2, 32, 0, 110, 116, 1, 109, 114, 101, 102, 26, 2, 32, 0, 110, 116, 1, 114, 97, 112, 32, 26, 2, 32, 0, 110, 116, 1, 114, 114, 101, 17, 67, 2, 32, 0, 110, 116, 1, 117, 108, 102, 17, 67, 26, 2, 32, 0, 110, 116, 2, 32, 0, 110, 116, 8, 116, 110, 111, 99, 26, 2, 32, 0, 115, 2, 32, 3, 141, 0, 7, 6, 102, 0, 4, 2, 102, 3, 0, 8, 114, 101, 110, 2, 29, 3, 0, 4, 105, 114, 101, 8, 2, 17, 67, 17, 65, 3, 21, 0, 105, 114, 101, 8, 2, 17, 67, 17, 67, 17, 65, 0, 108, 121, 0, 114, 97, 109, 101, 8, 0, 116, 101, 114, 2, 32, 0, 3, 81, 0, 4, 8, 117, 101, 110, 2, 32, 97, 110, 115, 3, 82, 0, 8, 117, 101, 110, 2, 32, 104, 101, 117, 114, 101, 115, 0, 7, 6, 103, 0, 4, 1, 110, 97, 116, 169, 195, 2, 32, 3, 0, 4, 1, 114, 117, 111, 98, 2, 32, 3, 0, 4, 8, 110, 97, 114, 2, 32, 3, 0, 4, 8, 110, 97, 115, 2, 32, 3, 0, 4, 8, 110, 111, 108, 2, 32, 3, 0, 4, 116, 1, 110, 105, 118, 2, 32, 117, 110, 3, 0, 116, 2, 32, 3, 0, 4, 97, 109, 101, 8, 2, 29, 3, 21, 0, 104, 2, 25, 0, 105, 114, 108, 0, 121, 2, 32, 0, 4, 116, 1, 110, 17, 65, 2, 17, 65, 3, 47, 0, 116, 1, 110, 105, 118, 2, 32, 17, 65, 0, 116, 1, 110, 105, 118, 2, 32, 99, 105, 110, 113, 0, 116, 1, 110, 105, 118, 2, 32, 100, 101, 117, 120, 0, 116, 1, 110, 105, 118, 2, 32, 104, 117, 105, 116, 0, 116, 1, 110, 105, 118, 2, 32, 110, 101, 117, 102, 0, 116, 1, 110, 105, 118, 2, 32, 110, 101, 117, 118, 105, 0, 116, 1, 110, 105, 118, 2, 32, 113, 117, 97, 116, 114, 0, 116, 1, 110, 105, 118, 2, 32, 115, 101, 112, 116, 0, 116, 1, 110, 105, 118, 2, 32, 115, 105, 120, 0, 116, 1, 110, 105, 118, 2, 32, 116, 114, 111, 105, 115, 0, 110, 2, 105, 101, 3, 50, 0, 110, 3, 50, 57, 0, 110, 2, 101, 17, 67, 17, 65, 3, 50, 57, 14, 0, 4, 110, 2, 32, 3, 65, 0, 110, 2, 101, 32, 0, 110, 105, 1, 105, 97, 0, 110, 105, 3, 65, 37, 0, 4, 3, 79, 0, 1, 97, 105, 100, 2, 110, 111, 0, 2, 17, 67, 0, 2, 32, 0, 8, 97, 2, 110, 111, 0, 103, 0, 117, 2, 105, 0, 110, 101, 114, 8, 97, 119, 2, 32, 3, 79, 50, 110, 34, 0, 103, 1, 117, 115, 2, 17, 71, 3, 79, 88, 0, 4, 117, 105, 1, 105, 97, 2, 108, 3, 79, 109, 37, 0, 117, 105, 1, 110, 105, 2, 115, 0, 4, 2, 17, 71, 3, 88, 0, 101, 2, 97, 0, 101, 2, 111, 0, 116, 115, 8, 110, 105, 118, 101, 114, 116, 97, 117, 113, 2, 32, 3, 141, 0, 7, 6, 104, 0, 4, 3, 0, 4, 8, 2, 97, 98, 105, 3, 0, 4, 8, 2, 97, 108, 108, 111, 3, 0, 4, 8, 2, 97, 109, 101, 3, 0, 4, 8, 2, 97, 110, 100, 114, 3, 0, 4, 8, 2, 97, 114, 109, 3, 0, 4, 8, 2, 101, 99, 116, 3, 0, 4, 8, 2, 101, 108, 3, 0, 4, 8, 2, 101, 114, 98, 3, 0, 4, 8, 2, 101, 117, 114, 101, 3, 0, 4, 8, 2, 105, 98, 101, 114, 3, 0, 4, 8, 2, 105, 112, 112, 111, 3, 0, 4, 8, 2, 105, 114, 111, 3, 0, 4, 8, 2, 105, 115, 116, 3, 0, 4, 8, 2, 105, 118, 3, 0, 4, 8, 2, 111, 109, 109, 3, 0, 4, 8, 2, 111, 110, 110, 3, 0, 4, 8, 2, 111, 114, 97, 3, 0, 4, 8, 2, 111, 114, 105, 112, 3, 0, 4, 8, 2, 111, 114, 105, 122, 3, 0, 4, 8, 2, 111, 114, 108, 111, 3, 0, 4, 8, 2, 111, 114, 111, 3, 0, 4, 8, 2, 111, 114, 114, 3, 0, 4, 8, 2, 111, 115, 3, 0, 4, 8, 2, 117, 105, 108, 3, 0, 4, 8, 2, 117, 105, 115, 115, 3, 0, 4, 8, 2, 117, 105, 116, 114, 3, 0, 4, 8, 2, 117, 109, 17, 65, 3, 0, 4, 8, 2, 117, 109, 17, 67, 3, 0, 4, 8, 2, 121, 3, 0, 4, 8, 2, 195, 169, 3, 0, 8, 2, 195, 180, 3, 0, 4, 97, 8, 2, 17, 67, 32, 3, 21, 0, 97, 108, 102, 8, 0, 110, 0, 4, 8, 3, 23, 0, 8, 2, 195, 169, 114, 105, 115, 0, 8, 2, 195, 169, 114, 111, 0, 105, 8, 2, 17, 65, 3, 23, 57, 0, 101, 105, 109, 2, 32, 3, 35, 57, 63, 0, 121, 112, 114, 97, 8, 2, 21, 14, 128, 132, 133, 3, 37, 48, 34, 35, 0, 4, 121, 112, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 37, 48, 110, 34, 0, 121, 112, 101, 114, 8, 2, 32, 0, 97, 117, 115, 2, 32, 3, 39, 87, 0, 121, 8, 2, 17, 65, 3, 57, 0, 7, 6, 105, 0, 4, 1, 102, 32, 109, 97, 114, 2, 108, 101, 3, 21, 0, 2, 112, 17, 65, 100, 0, 98, 117, 116, 101, 114, 2, 29, 0, 101, 118, 0, 102, 101, 2, 32, 0, 103, 110, 2, 32, 0, 108, 108, 1, 17, 67, 2, 121, 32, 0, 108, 108, 2, 32, 0, 110, 100, 1, 17, 67, 17, 65, 2, 101, 114, 29, 0, 110, 100, 2, 29, 0, 110, 100, 8, 17, 67, 2, 101, 114, 29, 0, 110, 103, 2, 32, 0, 114, 100, 1, 17, 67, 2, 29, 0, 114, 116, 1, 17, 67, 2, 32, 0, 118, 101, 110, 2, 32, 0, 122, 101, 2, 25, 0, 4, 1, 108, 102, 102, 111, 2, 110, 101, 32, 3, 35, 57, 0, 1, 108, 110, 111, 2, 110, 101, 32, 0, 1, 108, 116, 111, 2, 110, 101, 29, 0, 1, 114, 100, 2, 118, 101, 0, 1, 116, 103, 2, 109, 0, 8, 2, 99, 101, 21, 0, 4, 3, 37, 0, 1, 17, 67, 2, 101, 114, 17, 65, 0, 101, 110, 1, 17, 67, 2, 116, 32, 0, 101, 110, 1, 118, 169, 195, 100, 2, 116, 32, 0, 108, 8, 2, 108, 0, 110, 2, 110, 0, 115, 1, 17, 67, 2, 32, 0, 110, 2, 104, 3, 37, 50, 0, 110, 116, 1, 114, 112, 2, 32, 3, 37, 50, 47, 0, 110, 103, 2, 104, 3, 37, 50, 79, 0, 4, 108, 108, 1, 99, 2, 105, 3, 37, 55, 0, 108, 108, 1, 99, 115, 111, 0, 108, 108, 1, 116, 115, 105, 100, 0, 108, 108, 1, 117, 113, 110, 97, 0, 108, 108, 1, 118, 2, 101, 32, 0, 108, 108, 8, 18, 70, 0, 4, 108, 108, 1, 17, 67, 3, 37, 57, 0, 108, 108, 1, 117, 103, 0, 108, 108, 1, 117, 103, 105, 97, 0, 108, 108, 1, 117, 113, 0, 109, 2, 32, 3, 37, 63, 0, 109, 109, 3, 37, 63, 63, 0, 110, 103, 2, 115, 3, 37, 66, 0, 4, 108, 115, 1, 102, 32, 18, 66, 2, 32, 3, 37, 87, 0, 115, 1, 114, 105, 25, 2, 32, 0, 115, 1, 114, 111, 98, 2, 32, 0, 115, 1, 114, 111, 100, 2, 32, 0, 115, 1, 114, 111, 116, 2, 32, 0, 4, 101, 110, 1, 108, 99, 2, 17, 67, 3, 37, 111, 0, 101, 110, 1, 114, 111, 2, 116, 0, 4, 108, 1, 97, 2, 32, 3, 57, 0, 108, 1, 101, 2, 32, 0, 108, 1, 117, 2, 32, 0, 108, 108, 1, 17, 65, 0, 4, 101, 110, 1, 108, 111, 109, 2, 17, 67, 3, 57, 111, 0, 101, 110, 1, 110, 169, 195, 118, 2, 17, 67, 0, 101, 110, 1, 112, 105, 99, 2, 17, 67, 0, 101, 110, 1, 116, 97, 2, 116, 32, 0, 101, 110, 1, 116, 111, 2, 116, 32, 0, 4, 101, 110, 1, 116, 2, 25, 32, 3, 57, 112, 0, 101, 110, 1, 118, 2, 25, 32, 0, 4, 109, 2, 17, 67, 3, 112, 0, 110, 2, 17, 67, 0, 110, 2, 32, 0, 110, 99, 116, 2, 32, 0, 4, 110, 116, 101, 114, 8, 2, 32, 3, 112, 47, 6, 110, 34, 0, 110, 116, 101, 114, 8, 2, 110, 101, 32, 0, 4, 110, 116, 114, 97, 8, 2, 110, 101, 14, 128, 132, 133, 3, 112, 47, 34, 35, 0, 110, 116, 114, 97, 8, 2, 117, 14, 128, 132, 133, 0, 4, 110, 116, 101, 114, 8, 2, 21, 21, 14, 128, 132, 133, 3, 112, 47, 110, 34, 0, 110, 116, 101, 114, 114, 8, 2, 17, 65, 0, 110, 102, 114, 97, 8, 2, 115, 14, 128, 132, 133, 3, 112, 81, 34, 35, 0, 114, 116, 1, 108, 102, 3, 115, 34, 47, 0, 7, 6, 106, 0, 4, 8, 2, 111, 98, 25, 3, 73, 0, 8, 2, 111, 104, 25, 0, 97, 122, 122, 8, 3, 73, 35, 86, 0, 4, 3, 88, 0, 39, 8, 2, 14, 128, 140, 130, 0, 101, 2, 97, 0, 117, 115, 113, 117, 39, 8, 2, 14, 128, 132, 134, 3, 88, 109, 87, 49, 0, 7, 6, 107, 0, 4, 1, 17, 67, 17, 65, 2, 29, 3, 21, 0, 101, 2, 32, 0, 101, 2, 110, 29, 0, 101, 2, 114, 29, 0, 101, 2, 115, 32, 0, 3, 49, 0, 7, 6, 108, 0, 4, 1, 105, 17, 67, 117, 2, 32, 3, 0, 4, 1, 105, 116, 110, 2, 32, 3, 0, 116, 1, 117, 97, 3, 0, 4, 1, 17, 67, 11, 2, 101, 29, 3, 21, 0, 1, 17, 67, 17, 65, 2, 29, 0, 100, 1, 111, 2, 32, 0, 100, 1, 117, 2, 32, 0, 101, 115, 115, 2, 32, 0, 105, 110, 101, 8, 2, 29, 0, 105, 118, 101, 8, 0, 111, 117, 100, 1, 21, 2, 32, 0, 4, 3, 55, 0, 1, 102, 102, 2, 101, 29, 0, 1, 112, 112, 2, 101, 29, 0, 39, 8, 2, 14, 128, 132, 130, 0, 108, 2, 17, 65, 0, 111, 114, 115, 113, 117, 39, 8, 2, 14, 128, 132, 135, 3, 55, 39, 34, 87, 49, 0, 4, 104, 1, 105, 116, 110, 3, 57, 0, 108, 1, 105, 117, 0, 7, 6, 109, 0, 4, 2, 110, 32, 3, 21, 0, 97, 105, 108, 1, 100, 0, 97, 105, 108, 1, 101, 0, 97, 105, 108, 1, 103, 0, 97, 105, 108, 1, 116, 0, 111, 118, 2, 17, 65, 29, 0, 111, 118, 2, 105, 101, 32, 0, 4, 3, 63, 0, 39, 8, 2, 14, 128, 140, 130, 0, 109, 0, 99, 8, 2, 21, 14, 128, 132, 130, 3, 63, 35, 49, 0, 97, 115, 116, 101, 114, 2, 32, 14, 128, 128, 134, 3, 63, 35, 87, 47, 115, 34, 0, 115, 8, 2, 14, 128, 132, 130, 3, 110, 63, 110, 87, 0, 7, 6, 110, 0, 4, 2, 101, 109, 101, 32, 3, 21, 0, 2, 101, 109, 101, 115, 32, 0, 97, 109, 101, 8, 0, 97, 109, 101, 8, 101, 114, 0, 4, 3, 50, 0, 39, 8, 2, 14, 128, 140, 130, 0, 110, 0, 103, 104, 3, 50, 79, 0, 8, 2, 32, 194, 176, 3, 50, 109, 63, 36, 34, 39, 0, 101, 114, 8, 17, 67, 17, 65, 119, 2, 32, 3, 50, 110, 34, 0, 101, 117, 114, 111, 8, 2, 21, 21, 14, 128, 132, 133, 3, 50, 130, 34, 39, 0, 103, 2, 32, 3, 66, 0, 118, 100, 97, 8, 2, 14, 128, 132, 132, 3, 110, 50, 82, 36, 70, 36, 35, 0, 7, 6, 111, 0, 4, 2, 108, 100, 101, 114, 32, 3, 21, 0, 8, 2, 114, 100, 101, 114, 32, 0, 97, 2, 17, 67, 101, 114, 29, 0, 97, 2, 29, 0, 97, 99, 104, 0, 101, 115, 0, 102, 8, 2, 29, 0, 105, 110, 103, 1, 17, 67, 2, 32, 0, 110, 1, 116, 103, 2, 32, 0, 110, 1, 116, 115, 17, 67, 2, 32, 0, 110, 101, 8, 0, 111, 2, 17, 67, 101, 0, 111, 2, 29, 0, 111, 2, 107, 0, 111, 2, 115, 116, 0, 111, 116, 1, 17, 67, 0, 116, 8, 17, 67, 115, 0, 117, 100, 1, 17, 67, 29, 2, 29, 0, 117, 100, 1, 108, 2, 29, 0, 117, 110, 2, 17, 67, 0, 118, 101, 114, 8, 0, 119, 2, 29, 0, 119, 2, 101, 0, 121, 8, 17, 67, 2, 29, 0, 117, 8, 2, 97, 116, 3, 23, 40, 0, 110, 8, 2, 122, 3, 23, 114, 0, 101, 8, 104, 112, 2, 17, 67, 3, 36, 0, 4, 1, 17, 67, 2, 109, 101, 32, 3, 39, 0, 2, 32, 0, 2, 101, 17, 67, 0, 2, 115, 17, 65, 0, 2, 116, 32, 0, 2, 122, 17, 65, 0, 99, 1, 114, 98, 2, 32, 0, 99, 1, 114, 99, 2, 32, 0, 105, 8, 2, 103, 110, 111, 110, 0, 111, 1, 122, 0, 112, 8, 108, 97, 103, 2, 32, 0, 112, 8, 114, 105, 115, 2, 32, 0, 115, 1, 32, 115, 2, 32, 0, 115, 1, 32, 120, 2, 32, 0, 115, 8, 118, 2, 103, 17, 71, 0, 115, 116, 1, 118, 2, 32, 0, 4, 97, 2, 32, 3, 39, 35, 0, 97, 2, 115, 32, 0, 111, 1, 122, 2, 17, 67, 3, 39, 39, 0, 115, 115, 1, 114, 103, 3, 39, 87, 0, 4, 111, 1, 122, 2, 109, 3, 40, 0, 117, 0, 117, 101, 2, 109, 17, 65, 0, 117, 112, 8, 17, 67, 2, 32, 0, 195, 185, 0, 195, 187, 0, 117, 2, 105, 110, 3, 58, 0, 4, 101, 2, 108, 108, 17, 65, 3, 58, 35, 0, 105, 0, 121, 0, 195, 170, 2, 108, 0, 121, 2, 17, 65, 3, 58, 35, 57, 0, 4, 105, 110, 2, 17, 67, 3, 58, 112, 0, 105, 110, 2, 32, 0, 4, 109, 1, 110, 2, 29, 3, 114, 0, 109, 2, 18, 76, 0, 109, 2, 116, 0, 110, 2, 25, 0, 110, 8, 99, 2, 32, 0, 110, 116, 8, 109, 2, 109, 0, 110, 116, 8, 109, 2, 112, 17, 65, 17, 67, 0, 110, 116, 8, 109, 2, 114, 17, 65, 97, 108, 0, 110, 115, 104, 2, 17, 65, 3, 114, 86, 0, 110, 8, 17, 67, 2, 32, 3, 114, 132, 0, 110, 2, 116, 32, 3, 114, 138, 0, 4, 101, 2, 105, 3, 115, 0, 101, 8, 104, 112, 2, 110, 32, 0, 101, 117, 0, 4, 3, 125, 0, 2, 17, 67, 17, 67, 0, 8, 17, 67, 2, 109, 101, 32, 0, 8, 121, 2, 121, 0, 110, 2, 110, 0, 111, 1, 99, 108, 97, 2, 108, 0, 121, 8, 99, 2, 111, 3, 125, 37, 0, 110, 104, 2, 17, 65, 3, 125, 50, 0, 121, 8, 98, 2, 99, 111, 3, 125, 57, 0, 109, 2, 32, 3, 125, 63, 0, 115, 8, 2, 32, 12, 12, 3, 125, 87, 0, 4, 101, 8, 2, 17, 67, 3, 130, 0, 101, 117, 100, 0, 101, 117, 102, 115, 2, 32, 0, 101, 117, 2, 120, 3, 130, 141, 0, 7, 6, 112, 0, 4, 1, 97, 98, 2, 116, 3, 0, 4, 1, 97, 114, 100, 2, 32, 3, 0, 4, 1, 108, 117, 99, 115, 2, 116, 3, 0, 4, 1, 109, 97, 99, 2, 32, 3, 0, 4, 1, 109, 97, 104, 99, 2, 32, 3, 0, 4, 1, 109, 111, 99, 2, 116, 3, 0, 4, 2, 112, 3, 0, 4, 115, 1, 109, 2, 32, 3, 0, 4, 115, 1, 114, 2, 32, 3, 0, 116, 1, 17, 67, 2, 32, 3, 0, 4, 97, 100, 2, 32, 3, 21, 0, 108, 117, 103, 0, 114, 105, 110, 116, 101, 114, 2, 32, 0, 4, 116, 1, 101, 115, 2, 32, 3, 47, 0, 116, 1, 101, 115, 2, 105, 195, 168, 0, 3, 48, 0, 97, 114, 97, 8, 2, 112, 17, 67, 14, 128, 132, 132, 3, 48, 35, 34, 35, 0, 111, 108, 121, 8, 2, 21, 14, 128, 132, 132, 3, 48, 39, 55, 37, 0, 4, 111, 115, 116, 8, 2, 17, 65, 17, 67, 17, 67, 14, 128, 132, 132, 3, 48, 39, 87, 47, 0, 111, 115, 116, 8, 2, 17, 67, 14, 128, 132, 132, 0, 115, 121, 99, 104, 8, 2, 21, 14, 128, 132, 133, 3, 48, 87, 37, 49, 0, 4, 115, 121, 99, 104, 8, 2, 17, 65, 17, 65, 32, 14, 128, 132, 133, 3, 48, 87, 37, 89, 0, 115, 121, 99, 104, 8, 2, 105, 17, 67, 14, 128, 132, 133, 0, 115, 101, 117, 100, 111, 8, 2, 21, 14, 128, 132, 134, 3, 48, 87, 130, 70, 39, 0, 117, 105, 115, 113, 117, 39, 8, 2, 14, 128, 132, 135, 3, 48, 109, 37, 87, 49, 0, 97, 121, 115, 3, 48, 110, 37, 141, 0, 104, 3, 81, 0, 104, 111, 116, 111, 8, 2, 21, 14, 128, 132, 133, 3, 81, 39, 47, 39, 0, 7, 6, 113, 0, 4, 1, 110, 2, 32, 99, 101, 110, 116, 32, 3, 0, 1, 110, 2, 32, 109, 105, 108, 108, 3, 0, 117, 105, 99, 107, 3, 21, 0, 4, 3, 49, 0, 1, 110, 2, 32, 0, 117, 0, 117, 39, 8, 2, 17, 65, 14, 128, 132, 131, 0, 117, 101, 8, 2, 32, 3, 49, 13, 0, 117, 97, 8, 2, 100, 114, 105, 108, 108, 3, 49, 35, 0, 117, 8, 97, 2, 105, 102, 3, 49, 40, 0, 4, 117, 97, 1, 169, 195, 100, 3, 49, 58, 35, 0, 117, 97, 8, 2, 100, 0, 117, 97, 8, 2, 114, 116, 122, 0, 117, 97, 8, 2, 116, 17, 65, 0, 117, 97, 8, 17, 65, 0, 117, 97, 8, 17, 67, 0, 117, 97, 8, 97, 0, 117, 97, 110, 8, 2, 116, 17, 65, 3, 49, 58, 111, 0, 4, 117, 105, 8, 17, 65, 2, 100, 105, 115, 116, 3, 49, 109, 37, 0, 117, 105, 8, 17, 65, 2, 108, 97, 116, 0, 7, 6, 114, 0, 4, 2, 17, 67, 121, 32, 3, 21, 0, 101, 97, 108, 8, 0, 115, 116, 2, 32, 0, 117, 108, 101, 8, 0, 4, 3, 34, 0, 114, 0, 114, 1, 117, 111, 99, 2, 105, 0, 114, 1, 117, 111, 99, 2, 111, 0, 4, 114, 1, 117, 111, 99, 3, 34, 34, 0, 114, 1, 117, 111, 109, 0, 114, 8, 117, 115, 0, 97, 100, 105, 111, 8, 2, 21, 14, 128, 132, 133, 3, 34, 35, 70, 37, 39, 0, 7, 6, 115, 0, 4, 1, 117, 17, 67, 2, 32, 3, 0, 4, 1, 117, 99, 111, 100, 2, 32, 3, 0, 4, 1, 117, 99, 169, 195, 2, 32, 3, 0, 4, 1, 117, 103, 105, 2, 32, 3, 0, 4, 1, 117, 109, 169, 195, 2, 32, 3, 0, 4, 1, 117, 110, 101, 2, 32, 3, 0, 4, 1, 117, 114, 97, 2, 32, 3, 0, 4, 1, 117, 114, 117, 111, 2, 32, 3, 0, 4, 1, 117, 116, 105, 97, 2, 32, 3, 0, 4, 8, 117, 98, 17, 65, 2, 32, 3, 0, 4, 8, 117, 109, 2, 32, 3, 0, 4, 8, 117, 111, 116, 2, 32, 17, 67, 101, 115, 32, 3, 0, 4, 8, 117, 111, 116, 2, 32, 17, 67, 111, 115, 32, 3, 0, 8, 117, 111, 116, 2, 32, 108, 101, 117, 114, 115, 32, 3, 0, 4, 8, 17, 65, 2, 32, 3, 21, 0, 101, 110, 100, 2, 32, 0, 101, 114, 118, 101, 114, 8, 2, 29, 0, 104, 2, 17, 65, 112, 0, 104, 2, 17, 65, 116, 0, 104, 2, 32, 0, 105, 100, 101, 1, 18, 79, 2, 29, 12, 12, 12, 0, 105, 100, 101, 8, 2, 29, 12, 12, 12, 0, 107, 121, 8, 0, 109, 105, 108, 8, 0, 111, 110, 1, 18, 78, 2, 32, 0, 112, 121, 0, 116, 111, 110, 1, 18, 78, 2, 32, 0, 116, 111, 110, 101, 2, 32, 0, 4, 1, 17, 65, 2, 17, 65, 3, 86, 0, 1, 98, 117, 2, 105, 115, 0, 1, 110, 97, 114, 116, 2, 17, 65, 0, 2, 98, 0, 2, 100, 0, 2, 103, 0, 2, 106, 0, 2, 118, 0, 8, 108, 97, 2, 97, 99, 0, 104, 1, 169, 195, 100, 2, 17, 65, 0, 4, 3, 87, 0, 1, 17, 65, 2, 111, 102, 116, 0, 1, 17, 65, 2, 111, 108, 32, 0, 1, 97, 107, 97, 2, 32, 0, 1, 97, 115, 110, 97, 107, 2, 32, 0, 1, 105, 97, 2, 101, 109, 0, 1, 110, 97, 114, 116, 2, 101, 0, 1, 110, 97, 114, 116, 2, 117, 98, 0, 1, 111, 114, 116, 97, 98, 2, 32, 0, 1, 111, 114, 169, 195, 99, 111, 2, 32, 0, 1, 117, 98, 17, 65, 2, 32, 0, 1, 117, 98, 109, 2, 32, 0, 1, 117, 99, 17, 65, 2, 32, 0, 1, 117, 100, 111, 2, 32, 0, 1, 117, 103, 2, 32, 0, 1, 117, 105, 2, 32, 0, 1, 117, 108, 117, 17, 67, 2, 32, 0, 1, 117, 108, 121, 2, 32, 0, 1, 117, 109, 2, 32, 0, 1, 117, 110, 17, 65, 2, 32, 0, 1, 117, 112, 111, 2, 32, 0, 1, 117, 114, 17, 65, 2, 32, 0, 1, 117, 115, 97, 2, 32, 0, 1, 117, 115, 112, 2, 32, 0, 1, 117, 115, 115, 101, 99, 2, 32, 0, 1, 117, 116, 97, 2, 32, 0, 1, 117, 116, 99, 2, 32, 0, 1, 117, 116, 101, 2, 32, 0, 1, 117, 116, 105, 2, 32, 0, 1, 117, 116, 108, 2, 32, 0, 1, 117, 116, 111, 2, 32, 0, 1, 117, 116, 117, 17, 67, 2, 32, 0, 1, 117, 175, 195, 2, 32, 0, 1, 168, 195, 17, 67, 97, 2, 32, 0, 1, 168, 195, 110, 2, 32, 0, 8, 117, 2, 32, 0, 8, 117, 111, 116, 2, 32, 0, 8, 117, 111, 116, 2, 32, 100, 101, 115, 32, 0, 8, 117, 112, 17, 67, 17, 65, 99, 2, 32, 0, 39, 8, 2, 14, 128, 140, 130, 0, 39, 8, 2, 101, 115, 29, 14, 128, 140, 130, 0, 115, 0, 195, 167, 0, 99, 105, 101, 110, 2, 116, 3, 87, 37, 111, 0, 111, 99, 105, 111, 8, 2, 21, 14, 128, 132, 133, 3, 87, 39, 87, 37, 39, 0, 4, 99, 104, 2, 105, 101, 3, 87, 49, 0, 99, 104, 2, 105, 122, 0, 99, 104, 2, 111, 108, 0, 99, 104, 2, 111, 111, 0, 117, 112, 114, 97, 8, 2, 21, 14, 128, 132, 133, 3, 87, 109, 48, 34, 35, 0, 4, 117, 112, 101, 114, 8, 2, 21, 21, 14, 128, 132, 133, 3, 87, 109, 48, 110, 34, 0, 117, 112, 101, 114, 8, 2, 32, 0, 4, 99, 104, 3, 89, 0, 104, 0, 99, 104, 117, 3, 89, 40, 0, 116, 101, 105, 110, 2, 32, 3, 89, 47, 35, 57, 50, 0, 113, 108, 2, 32, 14, 128, 128, 131, 3, 110, 87, 49, 109, 110, 55, 0, 4, 1, 117, 108, 112, 2, 32, 3, 141, 0, 2, 32, 14, 128, 128, 129, 0, 7, 6, 116, 0, 4, 1, 108, 117, 97, 2, 32, 3, 0, 4, 1, 110, 2, 32, 3, 0, 4, 1, 114, 2, 32, 3, 0, 4, 2, 32, 3, 0, 104, 1, 115, 2, 109, 3, 0, 4, 1, 105, 2, 117, 110, 101, 29, 3, 21, 0, 1, 114, 97, 17, 67, 115, 2, 32, 0, 1, 114, 97, 17, 67, 115, 2, 101, 114, 32, 0, 104, 2, 17, 65, 0, 104, 2, 25, 0, 105, 109, 101, 8, 0, 108, 101, 2, 32, 0, 111, 110, 1, 103, 2, 32, 0, 111, 111, 0, 114, 121, 2, 32, 0, 116, 108, 0, 117, 110, 8, 2, 17, 65, 29, 0, 4, 3, 47, 0, 1, 17, 67, 2, 32, 0, 1, 26, 2, 105, 111, 110, 0, 1, 99, 101, 26, 2, 105, 111, 110, 0, 1, 101, 17, 67, 2, 105, 111, 110, 115, 0, 1, 101, 104, 99, 97, 2, 105, 111, 110, 0, 1, 105, 17, 67, 169, 195, 2, 105, 111, 110, 115, 0, 1, 105, 97, 2, 105, 111, 110, 0, 1, 105, 98, 97, 104, 2, 105, 111, 110, 115, 0, 1, 105, 99, 2, 105, 111, 110, 115, 0, 1, 105, 107, 2, 32, 0, 1, 105, 109, 105, 2, 105, 111, 110, 115, 0, 1, 105, 110, 97, 114, 103, 2, 32, 0, 1, 105, 111, 2, 105, 111, 110, 0, 1, 105, 115, 105, 17, 67, 2, 105, 111, 110, 0, 1, 110, 97, 2, 105, 97, 0, 1, 110, 97, 104, 99, 2, 105, 111, 110, 0, 1, 110, 101, 115, 2, 105, 111, 110, 32, 0, 1, 112, 101, 26, 2, 105, 111, 110, 0, 1, 112, 109, 111, 99, 2, 105, 111, 110, 115, 0, 1, 114, 111, 112, 17, 65, 2, 105, 111, 110, 0, 1, 114, 111, 112, 17, 67, 2, 105, 111, 110, 0, 1, 114, 111, 115, 2, 105, 111, 110, 0, 1, 115, 2, 105, 111, 110, 0, 1, 116, 2, 105, 111, 110, 0, 1, 117, 17, 65, 26, 2, 105, 111, 110, 0, 1, 169, 195, 26, 2, 105, 111, 110, 0, 1, 170, 195, 114, 2, 105, 111, 110, 0, 8, 0, 8, 17, 65, 115, 110, 97, 114, 116, 2, 32, 0, 8, 97, 116, 2, 105, 111, 110, 0, 8, 101, 99, 2, 32, 0, 39, 8, 2, 14, 128, 140, 130, 0, 104, 0, 104, 1, 114, 111, 2, 12, 12, 0, 104, 2, 17, 65, 114, 17, 65, 12, 12, 0, 104, 2, 18, 77, 12, 12, 0, 104, 2, 111, 17, 67, 17, 65, 0, 104, 8, 2, 101, 114, 109, 0, 116, 0, 8, 2, 32, 3, 47, 36, 0, 4, 101, 108, 101, 8, 3, 47, 36, 55, 36, 0, 195, 169, 108, 195, 169, 8, 2, 21, 14, 128, 132, 132, 0, 104, 101, 114, 109, 111, 8, 2, 21, 14, 128, 132, 134, 3, 47, 110, 34, 63, 39, 0, 4, 1, 17, 67, 2, 105, 101, 117, 3, 87, 0, 1, 97, 2, 105, 97, 0, 1, 97, 2, 105, 101, 110, 0, 1, 97, 109, 17, 65, 2, 105, 101, 29, 0, 1, 97, 114, 99, 2, 105, 101, 29, 0, 1, 99, 110, 17, 65, 17, 67, 2, 105, 111, 110, 0, 1, 105, 2, 105, 101, 110, 0, 1, 105, 110, 105, 2, 105, 17, 65, 0, 1, 105, 115, 2, 105, 111, 110, 0, 1, 105, 116, 169, 195, 2, 105, 111, 110, 0, 1, 110, 97, 2, 105, 97, 116, 0, 1, 110, 101, 2, 105, 97, 0, 1, 111, 2, 105, 101, 110, 0, 1, 112, 2, 105, 97, 0, 1, 114, 2, 105, 97, 0, 1, 114, 97, 109, 2, 105, 101, 110, 0, 1, 114, 101, 110, 2, 105, 101, 0, 1, 114, 111, 112, 111, 2, 105, 111, 110, 0, 1, 117, 98, 108, 2, 105, 17, 65, 0, 1, 117, 108, 2, 105, 111, 110, 0, 1, 117, 110, 2, 105, 101, 29, 0, 1, 169, 195, 109, 97, 2, 105, 101, 29, 0, 1, 169, 195, 112, 105, 2, 105, 101, 29, 0, 2, 105, 17, 65, 109, 0, 2, 105, 101, 108, 0, 2, 105, 101, 117, 0, 2, 105, 111, 32, 0, 2, 105, 111, 110, 0, 4, 105, 101, 110, 1, 105, 110, 2, 116, 32, 3, 87, 37, 0, 105, 101, 110, 1, 117, 98, 2, 116, 32, 0, 4, 1, 17, 65, 2, 45, 3, 138, 0, 1, 45, 2, 45, 0, 1, 105, 17, 67, 26, 2, 32, 0, 1, 105, 116, 101, 112, 2, 32, 0, 1, 110, 26, 2, 32, 0, 1, 105, 117, 104, 2, 32, 3, 139, 0, 115, 2, 32, 14, 128, 128, 129, 3, 141, 0, 7, 6, 117, 0, 1, 103, 2, 17, 65, 3, 0, 4, 1, 114, 2, 110, 29, 3, 21, 0, 97, 108, 1, 18, 68, 2, 32, 0, 99, 104, 2, 32, 0, 105, 1, 17, 67, 2, 99, 101, 0, 108, 116, 1, 17, 67, 2, 32, 0, 109, 98, 101, 114, 2, 32, 0, 109, 112, 2, 32, 0, 110, 8, 17, 67, 2, 32, 0, 110, 8, 17, 67, 2, 110, 121, 0, 110, 99, 104, 0, 110, 100, 101, 114, 0, 112, 2, 32, 0, 112, 8, 2, 17, 67, 0, 114, 110, 2, 29, 0, 115, 105, 8, 98, 0, 115, 116, 2, 32, 0, 122, 122, 0, 4, 1, 103, 2, 97, 121, 3, 40, 0, 1, 107, 175, 195, 97, 104, 2, 29, 0, 1, 112, 2, 116, 115, 99, 104, 0, 99, 99, 105, 1, 17, 67, 3, 40, 74, 37, 0, 4, 97, 1, 103, 2, 108, 32, 3, 58, 35, 0, 97, 1, 103, 97, 2, 29, 0, 97, 1, 103, 105, 116, 17, 67, 2, 32, 0, 97, 8, 103, 0, 4, 3, 109, 0, 1, 103, 2, 195, 171, 0, 1, 103, 2, 195, 175, 0, 108, 8, 99, 2, 32, 0, 110, 2, 110, 0, 120, 1, 108, 102, 2, 32, 0, 105, 3, 109, 37, 0, 121, 2, 17, 65, 3, 109, 37, 57, 0, 108, 116, 114, 97, 8, 2, 14, 128, 132, 133, 3, 109, 55, 47, 34, 35, 0, 105, 110, 2, 25, 3, 109, 112, 0, 4, 109, 1, 102, 2, 32, 3, 113, 0, 109, 2, 18, 76, 0, 110, 1, 17, 67, 17, 67, 2, 32, 0, 110, 2, 17, 67, 0, 110, 8, 104, 2, 32, 0, 110, 116, 1, 114, 112, 2, 32, 0, 4, 110, 1, 99, 117, 2, 32, 3, 113, 132, 0, 110, 2, 32, 0, 4, 1, 17, 67, 2, 98, 29, 3, 115, 0, 1, 17, 67, 2, 103, 29, 0, 8, 17, 67, 2, 114, 102, 29, 0, 8, 108, 98, 2, 102, 102, 0, 8, 110, 2, 114, 115, 101, 0, 8, 115, 2, 114, 102, 101, 29, 0, 101, 2, 105, 108, 0, 122, 2, 122, 0, 109, 2, 32, 3, 125, 63, 0, 7, 6, 118, 0, 4, 111, 105, 99, 101, 2, 29, 3, 21, 0, 111, 105, 100, 2, 32, 0, 121, 2, 32, 0, 3, 82, 0, 105, 101, 119, 2, 29, 3, 82, 57, 40, 0, 105, 101, 119, 8, 2, 17, 65, 3, 82, 57, 40, 82, 0, 101, 114, 115, 2, 32, 3, 82, 110, 34, 141, 0, 101, 114, 1, 105, 114, 100, 2, 29, 3, 82, 115, 34, 0, 7, 6, 119, 0, 4, 8, 2, 17, 65, 17, 67, 3, 21, 0, 8, 2, 17, 65, 105, 0, 97, 114, 0, 97, 118, 0, 97, 121, 0, 101, 8, 0, 104, 0, 110, 1, 17, 65, 0, 111, 114, 0, 114, 0, 8, 2, 17, 65, 3, 23, 58, 0, 4, 3, 58, 0, 8, 2, 17, 65, 17, 67, 111, 0, 8, 2, 17, 65, 116, 116, 0, 8, 2, 105, 110, 97, 0, 2, 97, 103, 12, 12, 3, 82, 0, 7, 6, 120, 0, 4, 1, 105, 97, 2, 32, 3, 0, 4, 1, 105, 111, 2, 32, 3, 0, 4, 1, 105, 114, 2, 32, 3, 0, 8, 117, 97, 2, 113, 117, 101, 108, 3, 0, 109, 108, 2, 32, 14, 128, 128, 131, 3, 23, 37, 49, 87, 110, 63, 110, 55, 0, 8, 2, 17, 67, 14, 128, 132, 129, 3, 37, 49, 87, 0, 4, 3, 49, 87, 0, 1, 101, 18, 68, 2, 17, 65, 0, 120, 0, 4, 1, 101, 2, 17, 65, 3, 79, 86, 0, 8, 2, 17, 65, 0, 8, 101, 2, 104, 0, 8, 101, 110, 105, 2, 17, 65, 0, 4, 1, 105, 100, 2, 105, 195, 168, 3, 86, 0, 1, 105, 115, 2, 105, 195, 168, 0, 1, 117, 101, 100, 2, 105, 195, 168, 0, 8, 105, 100, 2, 32, 110, 101, 117, 102, 0, 4, 8, 105, 111, 115, 2, 17, 65, 3, 87, 0, 8, 105, 115, 2, 32, 110, 101, 117, 0, 1, 117, 17, 65, 2, 32, 3, 141, 0, 4, 8, 105, 100, 2, 32, 3, 142, 0, 8, 105, 115, 2, 32, 0, 7, 6, 121, 0, 4, 1, 17, 67, 2, 101, 32, 3, 21, 0, 1, 17, 67, 11, 2, 32, 0, 1, 17, 67, 17, 65, 2, 32, 0, 1, 17, 67, 101, 17, 67, 21, 2, 32, 0, 1, 17, 67, 110, 2, 32, 0, 8, 17, 67, 2, 32, 0, 97, 99, 104, 116, 8, 0, 122, 101, 0, 8, 2, 17, 65, 3, 23, 57, 0, 4, 3, 37, 0, 1, 115, 115, 2, 32, 0, 2, 110, 110, 0, 115, 1, 29, 2, 32, 3, 37, 87, 0, 8, 2, 101, 117, 3, 57, 0, 97, 104, 111, 111, 8, 2, 14, 128, 132, 133, 3, 57, 35, 6, 40, 0, 4, 109, 2, 18, 76, 3, 112, 0, 109, 2, 32, 0, 110, 2, 25, 0, 7, 6, 122, 0, 3, 86, 0, 101, 114, 1, 116, 2, 32, 3, 86, 110, 34, 0, 101, 114, 1, 17, 67, 2, 32, 3, 86, 115, 34, 0, 1, 116, 3, 87, 0, 7, 6, 0, 194, 176, 8, 32, 110, 3, 0, 39, 2, 17, 67, 3, 21, 0, 195, 162, 3, 35, 12, 0, 195, 169, 3, 36, 0, 195, 182, 3, 39, 0, 195, 177, 3, 65, 0, 194, 176, 3, 70, 13, 79, 34, 36, 0, 36, 3, 70, 125, 55, 35, 34, 0, 195, 188, 3, 109, 0, 195, 187, 3, 109, 12, 0, 195, 170, 3, 110, 0, 58, 8, 32, 18, 81, 2, 32, 18, 82, 15, 32, 3, 115, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts19 = FileInMemory_createWithData (21420, reinterpret_cast (&espeakdata_dicts19_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/fr_dict", L"fr"); Collection_addItem (me.peek(), espeakdata_dicts19.transfer()); static unsigned char espeakdata_dicts20_data[3391] = { 0, 4, 0, 0, 220, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 6, 95, 48, 12, 1, 14, 7, 21, 0, 101, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 207, 132, 225, 191, 130, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 207, 132, 225, 191, 178, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 207, 132, 225, 189, 184, 72, 0, 0, 0, 0, 8, 133, 207, 132, 225, 189, 188, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 207, 132, 225, 189, 176, 72, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 207, 132, 225, 189, 176, 207, 130, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 8, 206, 183, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 8, 206, 191, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 207, 132, 206, 177, 225, 189, 182, 207, 130, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 207, 132, 206, 177, 225, 189, 182, 206, 189, 72, 12, 137, 207, 132, 206, 177, 225, 189, 182, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 207, 132, 225, 189, 180, 207, 130, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 207, 132, 225, 189, 180, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 207, 132, 206, 191, 225, 189, 182, 207, 130, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 207, 132, 206, 191, 225, 189, 182, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 207, 132, 206, 191, 225, 189, 186, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 207, 132, 225, 189, 184, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 207, 132, 206, 191, 225, 189, 186, 207, 130, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 206, 191, 8, 206, 185, 72, 0, 0, 0, 0, 8, 133, 206, 177, 8, 206, 185, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 207, 132, 225, 189, 188, 206, 189, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 50, 32, 0, 0, 39, 0, 0, 0, 97, 0, 0, 0, 177, 3, 0, 0, 111, 0, 0, 0, 191, 3, 0, 0, 118, 0, 0, 0, 189, 3, 0, 0, 65, 0, 0, 0, 145, 3, 0, 0, 66, 0, 0, 0, 146, 3, 0, 0, 69, 0, 0, 0, 149, 3, 0, 0, 90, 0, 0, 0, 150, 3, 0, 0, 72, 0, 0, 0, 151, 3, 0, 0, 73, 0, 0, 0, 153, 3, 0, 0, 75, 0, 0, 0, 154, 3, 0, 0, 77, 0, 0, 0, 156, 3, 0, 0, 78, 0, 0, 0, 157, 3, 0, 0, 79, 0, 0, 0, 159, 3, 0, 0, 80, 0, 0, 0, 161, 3, 0, 0, 84, 0, 0, 0, 164, 3, 0, 0, 89, 0, 0, 0, 165, 3, 0, 0, 88, 0, 0, 0, 167, 3, 0, 0, 116, 0, 104, 0, 184, 3, 0, 0, 112, 0, 104, 0, 198, 3, 0, 0, 107, 0, 104, 0, 199, 3, 0, 0, 112, 0, 115, 0, 200, 3, 0, 0, 98, 0, 0, 0, 178, 3, 0, 0, 103, 0, 0, 0, 179, 3, 0, 0, 100, 0, 0, 0, 180, 3, 0, 0, 101, 0, 0, 0, 181, 3, 0, 0, 122, 0, 0, 0, 182, 3, 0, 0, 113, 0, 0, 0, 183, 3, 0, 0, 105, 0, 0, 0, 185, 3, 0, 0, 107, 0, 0, 0, 186, 3, 0, 0, 108, 0, 0, 0, 187, 3, 0, 0, 109, 0, 0, 0, 188, 3, 0, 0, 110, 0, 0, 0, 189, 3, 0, 0, 120, 0, 0, 0, 190, 3, 0, 0, 112, 0, 0, 0, 192, 3, 0, 0, 114, 0, 0, 0, 193, 3, 0, 0, 115, 0, 0, 0, 195, 3, 0, 0, 116, 0, 0, 0, 196, 3, 0, 0, 117, 0, 0, 0, 197, 3, 0, 0, 121, 0, 0, 0, 197, 3, 0, 0, 119, 0, 0, 0, 201, 3, 0, 0, 172, 3, 0, 0, 112, 31, 0, 0, 113, 31, 0, 0, 112, 31, 0, 0, 180, 31, 0, 0, 178, 31, 0, 0, 182, 31, 0, 0, 112, 31, 0, 0, 183, 31, 0, 0, 178, 31, 0, 0, 0, 31, 0, 0, 177, 3, 0, 0, 1, 31, 0, 0, 104, 0, 177, 3, 2, 31, 0, 0, 112, 31, 0, 0, 3, 31, 0, 0, 104, 0, 112, 31, 4, 31, 0, 0, 112, 31, 0, 0, 5, 31, 0, 0, 104, 0, 112, 31, 6, 31, 0, 0, 112, 31, 0, 0, 7, 31, 0, 0, 104, 0, 112, 31, 128, 31, 0, 0, 179, 31, 0, 0, 129, 31, 0, 0, 104, 0, 179, 31, 130, 31, 0, 0, 178, 31, 0, 0, 131, 31, 0, 0, 104, 0, 178, 31, 132, 31, 0, 0, 178, 31, 0, 0, 133, 31, 0, 0, 104, 0, 178, 31, 134, 31, 0, 0, 178, 31, 0, 0, 135, 31, 0, 0, 104, 0, 178, 31, 173, 3, 0, 0, 114, 31, 0, 0, 115, 31, 0, 0, 114, 31, 0, 0, 16, 31, 0, 0, 181, 3, 0, 0, 17, 31, 0, 0, 104, 0, 181, 3, 18, 31, 0, 0, 114, 31, 0, 0, 19, 31, 0, 0, 104, 0, 114, 31, 20, 31, 0, 0, 114, 31, 0, 0, 21, 31, 0, 0, 104, 0, 114, 31, 174, 3, 0, 0, 116, 31, 0, 0, 117, 31, 0, 0, 116, 31, 0, 0, 196, 31, 0, 0, 194, 31, 0, 0, 198, 31, 0, 0, 116, 31, 0, 0, 199, 31, 0, 0, 194, 31, 0, 0, 32, 31, 0, 0, 183, 3, 0, 0, 33, 31, 0, 0, 104, 0, 183, 3, 34, 31, 0, 0, 116, 31, 0, 0, 35, 31, 0, 0, 104, 0, 116, 31, 36, 31, 0, 0, 116, 31, 0, 0, 37, 31, 0, 0, 104, 0, 116, 31, 38, 31, 0, 0, 116, 31, 0, 0, 39, 31, 0, 0, 104, 0, 116, 31, 144, 31, 0, 0, 195, 31, 0, 0, 145, 31, 0, 0, 104, 0, 195, 31, 146, 31, 0, 0, 194, 31, 0, 0, 147, 31, 0, 0, 104, 0, 194, 31, 148, 31, 0, 0, 194, 31, 0, 0, 149, 31, 0, 0, 104, 0, 194, 31, 150, 31, 0, 0, 194, 31, 0, 0, 151, 31, 0, 0, 104, 0, 194, 31, 175, 3, 0, 0, 118, 31, 0, 0, 119, 31, 0, 0, 118, 31, 0, 0, 214, 31, 0, 0, 118, 31, 0, 0, 48, 31, 0, 0, 185, 3, 0, 0, 49, 31, 0, 0, 104, 0, 185, 3, 50, 31, 0, 0, 118, 31, 0, 0, 51, 31, 0, 0, 104, 0, 118, 31, 52, 31, 0, 0, 118, 31, 0, 0, 53, 31, 0, 0, 104, 0, 118, 31, 54, 31, 0, 0, 118, 31, 0, 0, 55, 31, 0, 0, 104, 0, 118, 31, 211, 31, 0, 0, 210, 31, 0, 0, 215, 31, 0, 0, 210, 31, 0, 0, 204, 3, 0, 0, 120, 31, 0, 0, 121, 31, 0, 0, 120, 31, 0, 0, 64, 31, 0, 0, 191, 3, 0, 0, 65, 31, 0, 0, 104, 0, 191, 3, 66, 31, 0, 0, 120, 31, 0, 0, 67, 31, 0, 0, 104, 0, 120, 31, 68, 31, 0, 0, 120, 31, 0, 0, 69, 31, 0, 0, 104, 0, 120, 31, 205, 3, 0, 0, 122, 31, 0, 0, 123, 31, 0, 0, 122, 31, 0, 0, 230, 31, 0, 0, 122, 31, 0, 0, 80, 31, 0, 0, 197, 3, 0, 0, 81, 31, 0, 0, 104, 0, 197, 3, 82, 31, 0, 0, 122, 31, 0, 0, 83, 31, 0, 0, 104, 0, 122, 31, 84, 31, 0, 0, 122, 31, 0, 0, 85, 31, 0, 0, 104, 0, 122, 31, 86, 31, 0, 0, 122, 31, 0, 0, 87, 31, 0, 0, 104, 0, 122, 31, 227, 31, 0, 0, 226, 31, 0, 0, 231, 31, 0, 0, 226, 31, 0, 0, 206, 3, 0, 0, 124, 31, 0, 0, 125, 31, 0, 0, 124, 31, 0, 0, 244, 31, 0, 0, 242, 31, 0, 0, 246, 31, 0, 0, 124, 31, 0, 0, 247, 31, 0, 0, 242, 31, 0, 0, 96, 31, 0, 0, 201, 3, 0, 0, 97, 31, 0, 0, 104, 0, 201, 3, 98, 31, 0, 0, 124, 31, 0, 0, 99, 31, 0, 0, 104, 0, 124, 31, 100, 31, 0, 0, 124, 31, 0, 0, 101, 31, 0, 0, 104, 0, 124, 31, 102, 31, 0, 0, 124, 31, 0, 0, 103, 31, 0, 0, 104, 0, 124, 31, 160, 31, 0, 0, 243, 31, 0, 0, 161, 31, 0, 0, 104, 0, 243, 31, 162, 31, 0, 0, 242, 31, 0, 0, 163, 31, 0, 0, 104, 0, 242, 31, 164, 31, 0, 0, 242, 31, 0, 0, 165, 31, 0, 0, 104, 0, 242, 31, 166, 31, 0, 0, 242, 31, 0, 0, 167, 31, 0, 0, 104, 0, 242, 31, 228, 31, 0, 0, 193, 3, 0, 0, 229, 31, 0, 0, 104, 0, 193, 3, 0, 0, 0, 0, 6, 195, 175, 0, 3, 37, 0, 7, 6, 1, 50, 0, 104, 225, 189, 186, 3, 6, 105, 112, 0, 104, 225, 189, 182, 3, 6, 105, 115, 0, 225, 189, 186, 3, 6, 112, 0, 225, 189, 182, 3, 6, 115, 0, 3, 35, 0, 104, 207, 133, 3, 105, 112, 0, 104, 206, 185, 3, 105, 115, 0, 207, 133, 3, 112, 0, 206, 185, 3, 115, 0, 7, 6, 1, 51, 0, 3, 69, 0, 7, 6, 1, 52, 0, 206, 179, 3, 66, 79, 0, 3, 79, 0, 7, 6, 1, 53, 0, 3, 70, 0, 7, 6, 1, 54, 0, 225, 189, 182, 3, 6, 36, 12, 0, 104, 225, 189, 182, 3, 6, 105, 36, 12, 0, 104, 225, 189, 186, 3, 6, 105, 113, 0, 225, 189, 186, 3, 6, 113, 0, 3, 36, 0, 206, 185, 3, 36, 12, 0, 104, 206, 185, 3, 105, 36, 12, 0, 104, 207, 133, 3, 105, 113, 0, 207, 133, 3, 113, 0, 7, 6, 1, 55, 0, 3, 86, 0, 7, 6, 1, 56, 0, 104, 225, 189, 182, 3, 6, 105, 117, 12, 0, 104, 225, 189, 186, 3, 6, 105, 122, 12, 0, 225, 189, 182, 3, 6, 117, 12, 0, 225, 189, 186, 3, 6, 122, 12, 0, 104, 206, 185, 3, 105, 117, 12, 0, 104, 207, 133, 3, 105, 122, 12, 0, 3, 107, 12, 0, 206, 185, 3, 117, 12, 0, 207, 133, 3, 122, 12, 0, 7, 6, 1, 57, 0, 3, 85, 0, 7, 6, 1, 58, 0, 3, 37, 0, 7, 6, 1, 59, 0, 3, 49, 0, 7, 6, 1, 60, 0, 3, 55, 0, 7, 6, 1, 61, 0, 3, 63, 0, 7, 6, 1, 62, 0, 3, 50, 0, 7, 6, 1, 63, 0, 3, 49, 87, 0, 7, 6, 1, 64, 0, 225, 189, 186, 3, 6, 40, 12, 0, 104, 225, 189, 186, 3, 6, 105, 40, 12, 0, 104, 225, 189, 182, 3, 6, 105, 118, 0, 225, 189, 182, 3, 6, 118, 0, 3, 39, 0, 207, 133, 3, 40, 12, 0, 104, 207, 133, 3, 105, 40, 12, 0, 104, 206, 185, 3, 105, 118, 0, 206, 185, 3, 118, 0, 7, 6, 1, 65, 0, 3, 48, 0, 7, 6, 1, 66, 0, 3, 51, 0, 7, 6, 1, 67, 0, 3, 87, 0, 7, 6, 1, 68, 0, 3, 87, 0, 7, 6, 1, 69, 0, 3, 47, 0, 7, 6, 1, 70, 0, 104, 225, 189, 182, 3, 6, 105, 125, 0, 225, 189, 182, 3, 6, 125, 0, 104, 206, 185, 3, 105, 125, 0, 3, 110, 0, 206, 185, 3, 125, 0, 7, 6, 1, 71, 0, 3, 81, 0, 7, 6, 1, 72, 0, 3, 99, 0, 7, 6, 1, 73, 0, 3, 48, 87, 0, 7, 6, 1, 74, 0, 104, 225, 189, 182, 3, 6, 105, 123, 12, 0, 104, 225, 189, 186, 3, 6, 105, 124, 12, 0, 225, 189, 182, 3, 6, 123, 12, 0, 225, 189, 186, 3, 6, 124, 12, 0, 104, 206, 185, 3, 105, 123, 12, 0, 104, 207, 133, 3, 105, 124, 12, 0, 3, 108, 12, 0, 206, 185, 3, 123, 12, 0, 207, 133, 3, 124, 12, 0, 7, 6, 1, 75, 0, 3, 37, 0, 7, 6, 1, 76, 0, 104, 225, 189, 182, 3, 6, 105, 125, 0, 225, 189, 182, 3, 6, 125, 0, 104, 206, 185, 3, 105, 125, 0, 3, 110, 0, 206, 185, 3, 125, 0, 7, 6, 97, 0, 3, 35, 0, 117, 3, 112, 0, 105, 3, 115, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 100, 0, 3, 70, 0, 7, 6, 101, 0, 3, 36, 0, 105, 3, 36, 12, 0, 117, 3, 113, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 103, 3, 66, 79, 0, 3, 79, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 3, 49, 0, 104, 3, 99, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 7, 6, 111, 0, 3, 39, 0, 117, 3, 40, 12, 0, 105, 3, 118, 0, 7, 6, 112, 0, 3, 48, 0, 104, 3, 81, 0, 7, 6, 113, 0, 3, 107, 12, 0, 105, 3, 117, 12, 0, 117, 3, 122, 12, 0, 7, 6, 114, 0, 3, 51, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 104, 3, 85, 0, 7, 6, 117, 0, 3, 110, 0, 105, 3, 125, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 108, 12, 0, 105, 3, 123, 0, 117, 3, 124, 0, 7, 6, 120, 0, 3, 99, 0, 7, 6, 121, 0, 3, 110, 0, 105, 3, 125, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 225, 189, 176, 3, 6, 35, 0, 225, 189, 178, 3, 6, 36, 0, 4, 225, 189, 182, 3, 6, 37, 0, 225, 191, 146, 0, 225, 189, 184, 3, 6, 39, 0, 225, 189, 180, 3, 6, 107, 12, 0, 225, 189, 188, 3, 6, 108, 12, 0, 4, 225, 189, 186, 3, 6, 110, 0, 225, 191, 162, 0, 225, 190, 178, 3, 6, 115, 12, 0, 225, 191, 130, 3, 6, 117, 12, 0, 225, 191, 178, 3, 6, 123, 12, 0, 39, 3, 8, 0, 225, 190, 179, 3, 115, 12, 0, 225, 191, 131, 3, 117, 12, 0, 225, 191, 179, 3, 123, 12, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts20 = FileInMemory_createWithData (3390, reinterpret_cast (&espeakdata_dicts20_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/grc_dict", L"grc"); Collection_addItem (me.peek(), espeakdata_dicts20.transfer()); static unsigned char espeakdata_dicts21_data[7360] = { 0, 4, 0, 0, 139, 25, 0, 0, 0, 0, 0, 7, 195, 85, 81, 64, 9, 17, 7, 195, 4, 209, 128, 9, 17, 0, 0, 6, 65, 4, 35, 0, 14, 5, 193, 4, 72, 8, 0, 0, 0, 0, 6, 65, 8, 69, 13, 0, 0, 0, 7, 195, 57, 50, 64, 9, 17, 0, 0, 6, 65, 12, 115, 13, 0, 0, 0, 7, 195, 41, 49, 64, 9, 17, 7, 195, 20, 209, 128, 9, 17, 15, 4, 95, 8, 1, 3, 49, 82, 6, 35, 74, 136, 115, 120, 0, 0, 0, 6, 65, 16, 70, 13, 0, 0, 0, 6, 195, 57, 33, 192, 17, 0, 0, 8, 197, 56, 83, 65, 41, 80, 76, 0, 0, 0, 0, 6, 65, 24, 81, 13, 0, 0, 0, 7, 195, 57, 48, 64, 9, 17, 7, 195, 57, 32, 192, 9, 17, 0, 0, 6, 65, 28, 79, 13, 0, 0, 0, 0, 0, 6, 65, 32, 99, 13, 0, 0, 14, 1, 33, 6, 40, 86, 82, 136, 74, 50, 136, 49, 0, 102, 14, 1, 33, 6, 40, 87, 49, 55, 136, 74, 50, 136, 49, 0, 0, 0, 11, 1, 35, 69, 138, 6, 39, 57, 10, 0, 27, 0, 6, 65, 36, 37, 0, 14, 5, 193, 36, 72, 8, 0, 11, 1, 37, 48, 6, 39, 87, 47, 39, 0, 27, 0, 9, 1, 38, 10, 6, 36, 50, 70, 0, 0, 0, 6, 65, 40, 57, 134, 0, 0, 0, 7, 195, 61, 22, 64, 9, 17, 15, 1, 42, 86, 82, 57, 6, 36, 86, 70, 37, 115, 120, 0, 27, 0, 7, 195, 5, 2, 0, 9, 17, 9, 1, 43, 48, 55, 40, 87, 0, 27, 0, 7, 195, 5, 3, 0, 9, 17, 6, 65, 44, 49, 13, 0, 0, 7, 195, 5, 4, 0, 9, 17, 0, 7, 195, 37, 69, 192, 9, 17, 11, 1, 46, 47, 35, 74, 49, 120, 0, 104, 27, 10, 1, 46, 47, 39, 74, 49, 120, 0, 27, 0, 11, 1, 47, 49, 138, 6, 39, 86, 10, 0, 27, 0, 6, 65, 48, 55, 13, 0, 0, 0, 7, 195, 57, 37, 192, 9, 17, 0, 0, 6, 65, 52, 63, 13, 0, 0, 7, 195, 53, 0, 64, 9, 17, 0, 7, 195, 92, 150, 128, 9, 17, 0, 0, 6, 65, 56, 50, 13, 0, 0, 0, 7, 195, 57, 36, 192, 9, 17, 14, 1, 58, 70, 82, 6, 39, 47, 120, 74, 49, 120, 0, 104, 13, 1, 58, 70, 82, 6, 39, 47, 39, 74, 49, 120, 0, 0, 0, 6, 65, 60, 39, 0, 14, 5, 193, 60, 72, 28, 0, 14, 1, 61, 10, 57, 6, 36, 70, 50, 120, 49, 39, 0, 27, 0, 0, 0, 15, 1, 64, 47, 51, 79, 39, 82, 35, 74, 49, 39, 37, 0, 102, 8, 1, 64, 10, 6, 35, 47, 0, 6, 65, 64, 48, 13, 0, 0, 7, 195, 65, 0, 64, 9, 17, 7, 194, 4, 32, 9, 17, 41, 0, 7, 195, 56, 51, 192, 9, 17, 6, 195, 48, 128, 64, 17, 7, 195, 4, 209, 192, 9, 17, 0, 0, 7, 65, 68, 49, 82, 13, 0, 0, 0, 6, 195, 72, 48, 192, 17, 0, 0, 6, 65, 72, 51, 13, 0, 0, 8, 66, 5, 32, 120, 51, 0, 102, 6, 194, 73, 0, 9, 17, 0, 0, 0, 7, 65, 76, 87, 13, 0, 14, 7, 65, 76, 87, 10, 0, 28, 0, 0, 0, 0, 6, 65, 80, 47, 13, 0, 0, 0, 7, 195, 36, 209, 192, 9, 17, 0, 0, 6, 65, 84, 40, 0, 14, 5, 193, 84, 72, 28, 7, 195, 4, 51, 0, 9, 17, 0, 0, 0, 0, 6, 65, 88, 82, 13, 0, 0, 0, 0, 16, 4, 95, 49, 77, 52, 69, 6, 37, 55, 37, 57, 109, 50, 0, 104, 15, 4, 95, 49, 77, 52, 69, 6, 37, 55, 37, 57, 137, 50, 0, 0, 13, 1, 92, 69, 6, 107, 49, 87, 55, 107, 89, 0, 27, 13, 65, 92, 70, 40, 48, 55, 39, 15, 82, 13, 0, 102, 16, 65, 92, 70, 82, 39, 87, 47, 138, 40, 49, 39, 15, 82, 13, 0, 0, 7, 195, 5, 52, 0, 9, 17, 0, 6, 195, 16, 243, 192, 17, 16, 1, 94, 115, 6, 37, 51, 49, 40, 63, 81, 55, 36, 49, 87, 0, 0, 7, 195, 5, 54, 0, 9, 17, 0, 15, 4, 95, 49, 77, 49, 105, 6, 37, 61, 35, 70, 137, 0, 103, 16, 4, 95, 49, 77, 49, 105, 6, 37, 61, 4, 120, 70, 137, 0, 102, 14, 4, 95, 49, 77, 49, 47, 6, 37, 87, 137, 76, 137, 0, 7, 65, 96, 37, 49, 87, 0, 0, 7, 195, 97, 0, 64, 9, 17, 16, 4, 95, 49, 77, 50, 63, 6, 37, 55, 37, 57, 109, 50, 0, 104, 15, 4, 95, 49, 77, 50, 63, 6, 37, 55, 37, 57, 137, 50, 0, 0, 7, 195, 4, 65, 0, 9, 17, 17, 4, 95, 49, 77, 51, 63, 37, 55, 37, 57, 135, 34, 70, 137, 0, 102, 16, 4, 95, 49, 77, 51, 63, 6, 37, 55, 37, 35, 51, 70, 137, 0, 0, 0, 11, 65, 100, 37, 48, 87, 37, 55, 39, 50, 0, 0, 7, 195, 4, 68, 0, 9, 17, 0, 6, 195, 72, 52, 192, 17, 7, 195, 20, 212, 192, 9, 17, 0, 0, 6, 65, 104, 86, 13, 0, 0, 6, 194, 9, 32, 24, 17, 0, 7, 195, 21, 84, 128, 9, 17, 0, 0, 6, 195, 9, 35, 0, 17, 0, 6, 195, 5, 68, 0, 17, 0, 15, 67, 16, 240, 216, 70, 6, 39, 115, 15, 6, 37, 49, 87, 0, 7, 195, 36, 101, 64, 9, 17, 0, 6, 195, 9, 38, 0, 17, 0, 0, 0, 0, 0, 0, 6, 195, 29, 36, 19, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 1, 126, 47, 6, 37, 55, 70, 120, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 97, 128, 64, 9, 17, 6, 195, 73, 64, 64, 17, 0, 0, 0, 6, 194, 13, 32, 9, 17, 6, 194, 5, 96, 9, 17, 0, 0, 0, 0, 0, 7, 195, 97, 129, 64, 9, 17, 7, 195, 36, 97, 128, 9, 17, 7, 195, 13, 37, 0, 9, 17, 0, 0, 0, 0, 15, 67, 76, 148, 216, 87, 6, 37, 87, 15, 6, 37, 49, 87, 0, 7, 195, 97, 2, 64, 9, 17, 7, 195, 93, 34, 64, 9, 17, 6, 195, 73, 69, 12, 17, 7, 195, 60, 34, 128, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 5, 117, 0, 9, 17, 0, 0, 0, 0, 6, 195, 92, 36, 128, 17, 0, 0, 0, 0, 7, 195, 76, 36, 128, 9, 17, 6, 195, 73, 52, 192, 17, 0, 0, 0, 6, 194, 17, 32, 24, 17, 0, 7, 195, 77, 148, 192, 9, 17, 0, 0, 0, 0, 7, 195, 81, 5, 64, 9, 17, 0, 0, 0, 0, 7, 195, 60, 38, 128, 9, 17, 0, 0, 0, 7, 195, 4, 148, 0, 9, 17, 0, 0, 0, 0, 6, 194, 21, 16, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 36, 224, 192, 24, 7, 195, 72, 208, 64, 9, 17, 7, 195, 52, 112, 64, 9, 17, 0, 0, 0, 0, 7, 195, 16, 16, 64, 9, 17, 6, 195, 12, 48, 64, 17, 0, 0, 8, 132, 197, 161, 20, 1, 104, 76, 0, 8, 66, 21, 32, 36, 51, 0, 102, 0, 7, 195, 72, 209, 64, 9, 17, 7, 195, 52, 113, 64, 9, 17, 0, 0, 0, 0, 7, 132, 197, 161, 20, 15, 76, 6, 195, 73, 65, 128, 17, 7, 195, 37, 97, 128, 9, 17, 0, 0, 0, 0, 7, 195, 72, 210, 64, 9, 17, 7, 195, 52, 114, 64, 9, 17, 0, 7, 196, 56, 148, 212, 20, 76, 0, 0, 7, 195, 20, 52, 0, 9, 17, 0, 0, 15, 4, 95, 4, 16, 20, 9, 86, 6, 35, 16, 107, 86, 10, 0, 0, 0, 0, 7, 195, 96, 19, 64, 9, 17, 0, 6, 195, 56, 83, 65, 76, 0, 8, 197, 56, 83, 65, 52, 240, 76, 0, 0, 7, 195, 64, 131, 192, 9, 17, 6, 195, 32, 131, 192, 17, 6, 195, 4, 115, 64, 17, 0, 0, 0, 0, 7, 195, 48, 148, 64, 9, 17, 6, 195, 29, 36, 128, 17, 0, 13, 4, 95, 20, 12, 4, 47, 6, 37, 55, 70, 120, 0, 0, 0, 0, 6, 195, 72, 68, 192, 17, 7, 195, 5, 100, 128, 9, 17, 0, 0, 0, 6, 194, 25, 32, 9, 17, 0, 7, 195, 21, 65, 0, 9, 17, 0, 0, 0, 8, 133, 9, 13, 1, 197, 161, 76, 0, 6, 195, 73, 69, 128, 17, 7, 195, 25, 37, 0, 9, 17, 0, 6, 195, 25, 38, 0, 17, 0, 0, 0, 7, 195, 4, 209, 0, 9, 17, 0, 0, 6, 195, 29, 36, 146, 17, 0, 0, 0, 0, 0, 6, 194, 21, 80, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 77, 48, 64, 9, 17, 0, 0, 0, 6, 194, 29, 32, 9, 17, 0, 7, 195, 72, 209, 128, 9, 17, 0, 0, 0, 6, 195, 29, 36, 0, 17, 0, 6, 195, 5, 97, 192, 17, 0, 7, 195, 29, 38, 0, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 60, 52, 128, 9, 17, 7, 195, 29, 36, 192, 9, 17, 0, 0, 0, 0, 7, 195, 76, 52, 128, 9, 17, 0, 0, 18, 3, 226, 132, 162, 48, 138, 6, 39, 6, 37, 86, 82, 39, 73, 120, 74, 0, 0, 6, 194, 33, 32, 9, 17, 0, 0, 0, 8, 195, 33, 37, 0, 9, 17, 41, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 17, 22, 64, 17, 0, 0, 0, 6, 194, 37, 16, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 96, 32, 64, 9, 17, 7, 195, 24, 96, 64, 9, 17, 0, 0, 18, 3, 226, 128, 166, 47, 138, 6, 37, 15, 47, 6, 35, 74, 49, 36, 0, 104, 17, 3, 226, 128, 166, 47, 138, 6, 37, 15, 47, 6, 39, 74, 49, 36, 0, 0, 23, 3, 226, 128, 161, 70, 82, 6, 39, 87, 47, 51, 137, 49, 37, 15, 49, 51, 6, 87, 47, 0, 102, 22, 3, 226, 128, 161, 70, 82, 6, 39, 87, 47, 138, 137, 49, 37, 15, 49, 138, 6, 37, 88, 0, 0, 7, 195, 12, 64, 64, 9, 17, 7, 195, 5, 112, 128, 9, 17, 12, 3, 226, 128, 160, 49, 44, 6, 87, 47, 0, 102, 11, 3, 226, 128, 160, 49, 138, 6, 37, 88, 0, 0, 0, 21, 3, 226, 128, 162, 49, 138, 6, 40, 48, 50, 35, 15, 47, 6, 35, 74, 49, 120, 0, 104, 20, 3, 226, 128, 162, 49, 138, 6, 40, 48, 50, 35, 15, 47, 6, 39, 74, 49, 120, 0, 0, 6, 195, 57, 97, 1, 17, 0, 12, 3, 226, 130, 172, 6, 36, 82, 138, 39, 0, 104, 11, 3, 226, 130, 172, 6, 36, 40, 51, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 56, 83, 65, 80, 80, 76, 0, 0, 0, 0, 11, 3, 95, 50, 6, 70, 82, 6, 107, 0, 102, 12, 3, 95, 50, 6, 70, 82, 6, 37, 57, 36, 0, 0, 0, 7, 195, 37, 51, 0, 9, 17, 0, 0, 0, 7, 195, 37, 52, 0, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 37, 65, 0, 24, 17, 0, 15, 4, 95, 13, 3, 14, 63, 6, 35, 49, 138, 16, 39, 50, 0, 0, 0, 0, 0, 0, 7, 195, 96, 149, 192, 9, 17, 0, 0, 0, 0, 7, 195, 20, 211, 0, 9, 17, 0, 7, 195, 20, 210, 0, 9, 17, 0, 0, 0, 6, 195, 97, 150, 128, 17, 13, 3, 226, 128, 176, 48, 138, 6, 39, 63, 37, 55, 0, 0, 6, 195, 56, 81, 207, 8, 7, 195, 16, 246, 0, 9, 17, 0, 0, 0, 0, 16, 6, 95, 18, 15, 13, 1, 14, 138, 6, 37, 63, 87, 49, 39, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 93, 64, 64, 17, 15, 3, 95, 51, 88, 47, 138, 6, 37, 70, 107, 87, 107, 47, 0, 0, 12, 3, 95, 48, 67, 87, 47, 6, 109, 10, 0, 102, 11, 3, 95, 48, 67, 87, 47, 6, 39, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 77, 65, 64, 72, 7, 195, 53, 1, 64, 9, 17, 0, 0, 0, 5, 194, 40, 80, 72, 18, 3, 95, 49, 57, 70, 6, 107, 82, 107, 47, 50, 35, 107, 87, 47, 0, 102, 16, 3, 95, 49, 57, 70, 6, 107, 82, 107, 47, 50, 128, 87, 47, 0, 0, 17, 3, 95, 49, 56, 6, 39, 87, 120, 63, 50, 35, 107, 87, 47, 0, 102, 15, 3, 95, 49, 56, 6, 39, 87, 120, 63, 50, 128, 87, 47, 0, 0, 16, 3, 95, 50, 67, 70, 82, 6, 36, 87, 47, 6, 35, 10, 0, 102, 15, 3, 95, 50, 67, 70, 82, 57, 6, 36, 87, 47, 6, 39, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 49, 49, 57, 6, 36, 70, 120, 50, 35, 107, 87, 47, 0, 102, 15, 3, 95, 49, 49, 57, 6, 36, 70, 120, 50, 128, 87, 47, 0, 0, 7, 195, 61, 67, 64, 9, 17, 7, 195, 5, 3, 64, 9, 17, 12, 3, 95, 49, 48, 70, 6, 107, 87, 107, 47, 0, 0, 16, 3, 95, 51, 67, 47, 51, 6, 37, 87, 47, 6, 35, 10, 0, 102, 16, 3, 95, 49, 51, 47, 138, 6, 37, 50, 35, 107, 87, 47, 0, 102, 14, 3, 95, 49, 51, 47, 138, 6, 37, 50, 128, 87, 47, 0, 0, 16, 3, 95, 49, 50, 70, 82, 6, 35, 50, 35, 107, 87, 47, 0, 102, 14, 3, 95, 49, 50, 70, 82, 6, 35, 50, 128, 87, 47, 0, 0, 16, 3, 95, 49, 53, 48, 6, 107, 47, 50, 35, 107, 87, 47, 0, 102, 14, 3, 95, 49, 53, 48, 6, 107, 47, 50, 128, 87, 47, 0, 0, 17, 3, 95, 49, 52, 74, 6, 107, 47, 44, 50, 35, 107, 87, 47, 0, 102, 15, 3, 95, 49, 52, 74, 6, 107, 47, 44, 50, 128, 87, 47, 0, 0, 18, 3, 95, 49, 55, 87, 6, 107, 70, 120, 63, 50, 35, 107, 87, 47, 0, 102, 16, 3, 95, 49, 55, 87, 6, 107, 70, 120, 63, 50, 128, 87, 47, 0, 0, 16, 3, 95, 49, 54, 89, 6, 107, 87, 50, 35, 107, 87, 47, 0, 102, 14, 3, 95, 49, 54, 89, 6, 107, 87, 50, 128, 87, 47, 0, 0, 0, 7, 195, 61, 52, 192, 9, 17, 6, 195, 12, 196, 128, 17, 17, 3, 95, 55, 88, 87, 6, 107, 70, 120, 63, 70, 107, 87, 107, 47, 0, 0, 18, 3, 95, 52, 67, 74, 36, 47, 51, 6, 37, 87, 47, 6, 39, 10, 0, 102, 0, 0, 0, 6, 195, 12, 68, 128, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 12, 68, 151, 17, 13, 3, 95, 54, 67, 89, 6, 107, 87, 47, 6, 39, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 50, 88, 70, 82, 6, 35, 70, 107, 87, 107, 47, 0, 0, 16, 5, 95, 48, 77, 65, 49, 105, 6, 37, 61, 35, 70, 36, 0, 103, 17, 5, 95, 48, 77, 65, 49, 105, 6, 37, 61, 4, 120, 70, 36, 0, 102, 15, 5, 95, 48, 77, 65, 49, 47, 6, 37, 87, 137, 76, 36, 0, 0, 0, 18, 5, 95, 48, 77, 65, 51, 63, 37, 55, 37, 57, 135, 34, 70, 36, 0, 102, 17, 5, 95, 48, 77, 65, 51, 63, 6, 37, 55, 37, 35, 51, 70, 36, 0, 0, 18, 5, 95, 48, 77, 65, 50, 63, 6, 37, 55, 37, 57, 109, 50, 35, 0, 104, 17, 5, 95, 48, 77, 65, 50, 63, 6, 37, 55, 37, 57, 137, 50, 35, 0, 0, 0, 0, 0, 6, 195, 88, 112, 64, 17, 6, 195, 4, 16, 64, 17, 0, 0, 0, 0, 7, 195, 92, 208, 64, 9, 17, 0, 10, 3, 95, 63, 63, 86, 50, 35, 49, 0, 0, 0, 6, 194, 53, 32, 24, 17, 0, 7, 195, 65, 33, 128, 9, 17, 7, 195, 61, 65, 128, 9, 17, 16, 3, 95, 52, 88, 74, 6, 107, 47, 44, 70, 107, 87, 107, 47, 0, 0, 0, 0, 0, 7, 195, 21, 1, 128, 9, 17, 0, 0, 0, 0, 7, 195, 72, 226, 192, 9, 17, 7, 195, 5, 2, 128, 9, 17, 14, 3, 95, 53, 88, 48, 6, 107, 70, 107, 87, 107, 47, 0, 0, 0, 0, 0, 7, 195, 4, 130, 192, 9, 17, 0, 0, 0, 0, 6, 195, 65, 35, 128, 17, 6, 195, 60, 83, 64, 17, 7, 195, 56, 99, 192, 9, 17, 15, 3, 95, 54, 88, 89, 6, 107, 86, 70, 107, 87, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 69, 4, 128, 17, 0, 0, 0, 0, 8, 195, 77, 68, 128, 9, 24, 17, 7, 195, 53, 4, 128, 9, 17, 7, 195, 52, 20, 64, 9, 17, 0, 0, 0, 6, 194, 57, 32, 9, 17, 0, 13, 67, 13, 68, 140, 115, 39, 50, 47, 51, 123, 55, 0, 6, 195, 81, 165, 128, 24, 7, 195, 33, 37, 128, 9, 17, 6, 195, 13, 68, 140, 17, 16, 3, 95, 56, 88, 6, 39, 87, 120, 63, 70, 107, 87, 107, 47, 0, 0, 7, 195, 57, 34, 0, 9, 17, 0, 9, 134, 14, 5, 13, 1, 197, 161, 76, 0, 0, 0, 0, 0, 0, 7, 195, 36, 211, 0, 9, 17, 16, 3, 95, 57, 88, 70, 6, 107, 82, 107, 70, 107, 87, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 63, 65, 87, 55, 39, 82, 39, 0, 0, 0, 0, 0, 7, 195, 53, 84, 0, 17, 41, 0, 0, 0, 0, 0, 0, 7, 195, 60, 33, 0, 9, 17, 7, 195, 21, 128, 192, 9, 17, 0, 0, 0, 0, 6, 195, 72, 112, 128, 17, 7, 195, 60, 37, 0, 9, 17, 14, 4, 95, 15, 7, 15, 6, 39, 79, 39, 50, 107, 49, 0, 0, 13, 68, 77, 64, 82, 80, 87, 47, 6, 35, 51, 47, 0, 0, 0, 6, 195, 33, 166, 143, 17, 0, 7, 195, 84, 145, 128, 9, 17, 7, 195, 65, 33, 192, 9, 17, 0, 0, 0, 0, 7, 195, 4, 145, 128, 9, 17, 0, 0, 0, 5, 194, 48, 144, 72, 0, 7, 195, 97, 50, 64, 9, 17, 7, 195, 33, 34, 192, 9, 17, 7, 195, 29, 82, 64, 9, 17, 0, 7, 195, 60, 54, 0, 9, 17, 0, 0, 0, 0, 0, 0, 7, 194, 61, 48, 9, 17, 41, 0, 0, 17, 4, 95, 48, 77, 52, 69, 6, 37, 55, 37, 57, 109, 50, 35, 0, 104, 16, 4, 95, 48, 77, 52, 69, 6, 37, 55, 37, 57, 137, 50, 35, 0, 0, 6, 195, 65, 35, 198, 24, 0, 17, 4, 95, 48, 77, 50, 63, 6, 37, 55, 37, 57, 109, 50, 35, 0, 104, 16, 4, 95, 48, 77, 50, 63, 6, 37, 55, 37, 57, 137, 50, 35, 0, 0, 17, 4, 95, 48, 77, 51, 63, 37, 55, 37, 57, 135, 34, 70, 136, 0, 102, 16, 4, 95, 48, 77, 51, 63, 6, 37, 55, 37, 35, 51, 70, 136, 0, 0, 0, 15, 4, 95, 48, 77, 49, 105, 6, 37, 61, 35, 70, 120, 0, 103, 16, 4, 95, 48, 77, 49, 105, 6, 37, 61, 4, 120, 70, 120, 0, 102, 14, 4, 95, 48, 77, 49, 47, 6, 37, 87, 137, 76, 120, 0, 0, 13, 4, 95, 2, 18, 22, 69, 138, 16, 6, 107, 82, 0, 7, 66, 48, 160, 61, 13, 0, 0, 0, 0, 0, 0, 7, 195, 20, 20, 128, 9, 17, 0, 0, 0, 6, 194, 65, 32, 9, 17, 0, 0, 0, 0, 0, 7, 195, 65, 37, 0, 9, 17, 0, 0, 0, 0, 7, 195, 37, 22, 64, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 64, 64, 64, 17, 6, 195, 4, 16, 192, 17, 0, 7, 195, 60, 102, 0, 9, 17, 0, 0, 0, 7, 195, 96, 192, 64, 9, 17, 7, 195, 60, 101, 0, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 60, 115, 0, 9, 17, 0, 8, 66, 72, 16, 51, 120, 0, 102, 0, 7, 195, 64, 66, 64, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 76, 211, 192, 72, 6, 195, 80, 179, 192, 76, 6, 195, 36, 35, 64, 17, 0, 0, 0, 19, 4, 95, 3, 9, 18, 115, 6, 37, 51, 49, 137, 63, 81, 55, 107, 49, 87, 0, 0, 7, 195, 64, 179, 192, 9, 17, 0, 0, 0, 5, 194, 72, 32, 17, 7, 66, 56, 160, 65, 13, 0, 0, 0, 0, 6, 131, 95, 195, 186, 43, 0, 0, 7, 195, 17, 52, 128, 9, 17, 0, 0, 0, 0, 13, 4, 95, 19, 20, 11, 49, 138, 16, 6, 39, 86, 0, 0, 26, 3, 95, 194, 173, 48, 138, 6, 37, 82, 138, 36, 63, 36, 50, 120, 15, 115, 6, 44, 47, 6, 37, 115, 120, 0, 0, 12, 4, 95, 1, 3, 21, 6, 35, 49, 137, 47, 0, 0, 25, 3, 95, 194, 171, 6, 39, 47, 82, 39, 51, 36, 50, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 6, 131, 95, 195, 179, 43, 0, 15, 67, 52, 16, 216, 63, 6, 35, 115, 15, 6, 37, 49, 87, 0, 6, 195, 60, 213, 192, 17, 7, 195, 52, 21, 192, 9, 17, 0, 0, 0, 6, 194, 72, 48, 9, 17, 0, 6, 195, 72, 49, 0, 17, 0, 6, 131, 95, 195, 173, 43, 0, 0, 0, 13, 4, 95, 18, 14, 7, 138, 16, 6, 37, 66, 79, 0, 0, 6, 131, 95, 195, 169, 43, 0, 0, 5, 194, 73, 48, 17, 0, 7, 195, 104, 243, 192, 9, 17, 0, 0, 0, 8, 133, 196, 141, 5, 7, 1, 8, 0, 0, 6, 131, 95, 195, 161, 43, 0, 0, 6, 194, 72, 64, 9, 17, 0, 7, 195, 33, 64, 64, 9, 17, 0, 0, 0, 0, 0, 0, 6, 195, 73, 67, 0, 17, 0, 6, 194, 77, 32, 9, 17, 0, 7, 195, 77, 33, 0, 9, 17, 7, 195, 60, 97, 128, 9, 17, 0, 0, 0, 13, 67, 41, 1, 71, 57, 134, 15, 48, 6, 36, 79, 0, 24, 4, 95, 1, 3, 50, 70, 82, 6, 39, 87, 47, 138, 16, 137, 49, 136, 38, 6, 35, 49, 137, 47, 0, 0, 0, 0, 0, 8, 66, 72, 80, 51, 36, 0, 102, 0, 7, 195, 41, 2, 64, 9, 17, 7, 195, 20, 49, 12, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 26, 3, 95, 194, 187, 86, 6, 35, 47, 82, 39, 51, 36, 50, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 7, 195, 73, 115, 192, 9, 17, 0, 6, 195, 8, 147, 1, 72, 0, 7, 2, 196, 135, 76, 134, 0, 0, 6, 195, 8, 147, 15, 72, 0, 6, 195, 68, 36, 128, 17, 0, 0, 0, 0, 0, 6, 195, 8, 147, 9, 72, 0, 10, 2, 195, 151, 48, 6, 40, 47, 120, 0, 0, 0, 7, 2, 196, 141, 74, 13, 0, 0, 20, 2, 197, 130, 55, 13, 15, 87, 120, 15, 115, 6, 44, 47, 6, 37, 115, 39, 63, 0, 0, 0, 0, 0, 0, 13, 2, 194, 167, 6, 39, 70, 55, 39, 63, 120, 49, 0, 0, 12, 2, 194, 164, 82, 6, 35, 55, 40, 47, 120, 0, 0, 0, 7, 196, 36, 208, 84, 20, 76, 0, 0, 0, 7, 2, 196, 145, 75, 134, 0, 0, 18, 2, 194, 174, 51, 6, 36, 79, 37, 87, 47, 138, 35, 115, 136, 57, 120, 0, 0, 0, 5, 194, 77, 80, 72, 5, 194, 73, 112, 17, 0, 0, 0, 0, 14, 2, 194, 168, 48, 138, 6, 36, 79, 55, 120, 87, 0, 102, 15, 2, 194, 168, 48, 138, 6, 37, 57, 36, 79, 55, 120, 87, 0, 0, 19, 2, 194, 169, 6, 125, 47, 39, 51, 87, 49, 120, 15, 48, 138, 35, 82, 120, 0, 0, 12, 2, 194, 182, 74, 55, 6, 35, 50, 120, 49, 0, 0, 10, 2, 194, 183, 48, 6, 40, 47, 120, 0, 0, 6, 194, 72, 128, 9, 17, 0, 7, 195, 104, 16, 64, 9, 17, 6, 195, 4, 32, 192, 17, 11, 2, 194, 181, 63, 6, 37, 49, 138, 39, 0, 0, 0, 6, 195, 37, 49, 14, 17, 0, 13, 2, 194, 176, 87, 47, 6, 36, 48, 36, 50, 0, 104, 12, 2, 194, 176, 87, 47, 6, 40, 48, 120, 65, 0, 0, 7, 195, 64, 208, 64, 9, 17, 0, 0, 7, 195, 85, 35, 0, 9, 17, 16, 2, 195, 183, 48, 6, 39, 70, 36, 61, 4, 36, 50, 39, 0, 102, 17, 2, 195, 183, 48, 6, 39, 70, 37, 57, 36, 61, 4, 36, 50, 39, 0, 0, 5, 194, 73, 128, 17, 0, 0, 14, 4, 95, 3, 5, 4, 115, 6, 107, 70, 136, 55, 120, 0, 0, 0, 12, 2, 194, 184, 87, 36, 70, 6, 37, 55, 120, 0, 0, 17, 4, 95, 12, 9, 7, 55, 6, 37, 79, 120, 47, 4, 137, 51, 120, 0, 7, 2, 197, 161, 89, 13, 0, 0, 0, 0, 0, 7, 195, 5, 34, 128, 9, 17, 7, 195, 4, 34, 192, 9, 17, 0, 0, 0, 0, 6, 195, 12, 114, 64, 17, 0, 0, 0, 0, 7, 195, 85, 49, 0, 9, 17, 7, 195, 36, 51, 64, 9, 17, 7, 195, 4, 51, 64, 9, 17, 0, 0, 0, 0, 0, 7, 2, 197, 190, 88, 13, 0, 0, 7, 195, 84, 67, 0, 9, 17, 0, 0, 6, 195, 4, 36, 192, 17, 0, 0, 0, 0, 7, 195, 57, 4, 128, 24, 17, 6, 195, 84, 69, 0, 17, 6, 195, 24, 20, 64, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 144, 72, 6, 194, 72, 176, 9, 17, 0, 0, 7, 195, 92, 22, 0, 9, 17, 0, 0, 12, 2, 203, 152, 69, 138, 6, 36, 82, 37, 87, 0, 0, 0, 0, 0, 6, 194, 85, 80, 9, 17, 0, 0, 7, 196, 56, 83, 65, 52, 76, 0, 0, 7, 195, 85, 84, 0, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 95, 19, 87, 13, 0, 0, 0, 0, 0, 7, 195, 5, 33, 192, 9, 17, 7, 195, 4, 49, 128, 9, 17, 0, 0, 0, 0, 0, 0, 0, 6, 194, 72, 208, 9, 17, 0, 0, 7, 196, 36, 208, 77, 60, 76, 6, 195, 72, 214, 0, 17, 0, 7, 195, 72, 213, 0, 9, 17, 0, 6, 195, 56, 146, 133, 76, 6, 195, 4, 49, 141, 17, 0, 7, 195, 53, 50, 64, 9, 17, 0, 12, 2, 95, 34, 50, 6, 35, 82, 39, 70, 0, 102, 14, 2, 95, 34, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 0, 0, 7, 195, 5, 51, 64, 9, 17, 14, 2, 95, 39, 6, 35, 48, 39, 87, 47, 138, 39, 81, 0, 0, 19, 2, 95, 38, 47, 6, 44, 79, 6, 39, 82, 120, 74, 49, 39, 15, 6, 37, 0, 0, 0, 11, 2, 95, 36, 70, 6, 39, 55, 120, 51, 0, 0, 0, 6, 195, 84, 130, 0, 17, 15, 2, 95, 42, 86, 82, 6, 36, 86, 70, 37, 115, 120, 0, 102, 15, 2, 95, 42, 86, 82, 57, 6, 36, 86, 70, 37, 115, 120, 0, 15, 4, 95, 3, 1, 16, 49, 6, 35, 48, 136, 47, 120, 55, 0, 0, 24, 2, 95, 41, 86, 6, 35, 47, 82, 39, 51, 36, 50, 120, 15, 86, 6, 35, 79, 138, 35, 70, 120, 0, 0, 5, 194, 80, 160, 24, 5, 194, 76, 192, 24, 6, 194, 72, 224, 9, 17, 23, 2, 95, 40, 6, 39, 47, 82, 39, 51, 36, 50, 120, 15, 86, 6, 35, 79, 138, 35, 70, 120, 0, 0, 0, 7, 196, 36, 208, 74, 84, 76, 12, 2, 95, 46, 47, 6, 35, 74, 49, 120, 0, 104, 11, 2, 95, 46, 47, 6, 39, 74, 49, 120, 0, 0, 13, 2, 95, 45, 115, 6, 44, 47, 6, 37, 115, 120, 0, 11, 2, 95, 45, 63, 6, 37, 50, 40, 87, 0, 0, 13, 2, 95, 44, 86, 6, 35, 48, 36, 47, 35, 0, 102, 11, 2, 95, 44, 86, 6, 35, 51, 36, 86, 0, 0, 7, 195, 53, 36, 192, 24, 17, 9, 2, 95, 51, 47, 138, 6, 37, 0, 0, 9, 2, 95, 50, 70, 82, 6, 35, 0, 0, 7, 195, 85, 129, 0, 9, 17, 11, 2, 95, 49, 57, 6, 36, 70, 120, 50, 0, 0, 10, 2, 95, 48, 50, 6, 40, 55, 120, 0, 0, 11, 2, 95, 55, 87, 6, 107, 70, 120, 63, 0, 0, 10, 2, 95, 54, 89, 6, 107, 87, 47, 0, 0, 9, 2, 95, 53, 48, 6, 107, 47, 0, 0, 12, 2, 95, 52, 74, 6, 107, 47, 136, 51, 136, 0, 0, 18, 2, 95, 59, 47, 6, 35, 74, 49, 120, 86, 4, 35, 16, 107, 86, 0, 103, 19, 2, 95, 59, 47, 6, 35, 74, 49, 120, 86, 4, 35, 48, 36, 47, 35, 0, 102, 17, 2, 95, 59, 47, 6, 39, 74, 49, 120, 86, 4, 35, 16, 107, 86, 0, 0, 0, 11, 2, 95, 57, 70, 6, 107, 82, 107, 47, 0, 0, 10, 2, 95, 56, 6, 39, 87, 120, 63, 0, 0, 7, 195, 73, 22, 64, 9, 17, 13, 2, 95, 63, 6, 40, 48, 37, 47, 50, 136, 49, 0, 0, 14, 2, 95, 62, 82, 6, 36, 74, 37, 15, 6, 39, 70, 0, 0, 13, 2, 95, 61, 57, 6, 36, 70, 50, 120, 49, 39, 0, 13, 2, 95, 61, 57, 6, 36, 70, 50, 120, 49, 39, 0, 0, 7, 195, 84, 148, 0, 9, 17, 14, 2, 95, 60, 63, 6, 35, 65, 37, 15, 6, 39, 70, 0, 0, 0, 0, 0, 8, 2, 95, 64, 36, 47, 0, 102, 19, 2, 95, 64, 47, 6, 44, 79, 6, 39, 82, 120, 74, 49, 39, 15, 6, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 72, 32, 64, 17, 7, 195, 60, 112, 192, 9, 17, 7, 195, 36, 48, 192, 9, 17, 7, 195, 4, 48, 192, 9, 17, 0, 0, 0, 0, 7, 195, 88, 32, 64, 9, 17, 7, 195, 52, 64, 64, 9, 17, 0, 0, 0, 6, 195, 44, 241, 193, 8, 26, 4, 95, 226, 128, 154, 6, 39, 47, 82, 39, 51, 36, 50, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 7, 195, 60, 113, 192, 9, 17, 7, 195, 5, 49, 128, 9, 17, 7, 195, 4, 49, 192, 9, 17, 30, 4, 95, 226, 128, 153, 57, 6, 36, 70, 50, 39, 87, 47, 138, 6, 40, 49, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 26, 4, 95, 226, 128, 152, 6, 39, 47, 82, 39, 51, 36, 50, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 13, 4, 95, 4, 15, 20, 47, 6, 39, 74, 49, 120, 0, 0, 0, 27, 4, 95, 226, 128, 158, 86, 120, 47, 82, 39, 51, 36, 50, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 102, 26, 4, 95, 226, 128, 158, 87, 48, 6, 40, 89, 47, 36, 50, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 7, 195, 88, 33, 64, 9, 17, 7, 195, 52, 65, 64, 9, 17, 24, 2, 95, 91, 6, 39, 47, 82, 39, 51, 36, 50, 120, 15, 6, 40, 79, 55, 120, 87, 47, 120, 0, 102, 22, 2, 95, 91, 6, 39, 47, 82, 39, 51, 36, 50, 120, 15, 6, 40, 79, 55, 120, 47, 120, 0, 27, 4, 95, 226, 128, 157, 86, 6, 35, 47, 82, 39, 51, 36, 50, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 26, 4, 95, 226, 128, 156, 6, 39, 47, 82, 39, 51, 36, 50, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 15, 4, 95, 226, 128, 147, 107, 50, 15, 115, 6, 44, 47, 120, 0, 0, 0, 7, 195, 56, 162, 64, 9, 17, 10, 2, 95, 95, 115, 6, 44, 47, 120, 0, 0, 0, 25, 2, 95, 93, 86, 6, 35, 47, 82, 39, 51, 36, 50, 120, 15, 6, 40, 79, 55, 120, 87, 47, 120, 0, 102, 23, 2, 95, 93, 86, 6, 35, 47, 82, 39, 51, 36, 50, 120, 15, 6, 40, 79, 55, 120, 47, 120, 0, 0, 6, 195, 4, 49, 205, 17, 0, 7, 195, 36, 194, 64, 72, 8, 6, 195, 4, 194, 64, 8, 7, 195, 52, 66, 64, 9, 17, 6, 195, 24, 34, 64, 17, 0, 15, 4, 95, 226, 128, 148, 107, 63, 15, 115, 6, 44, 47, 120, 0, 0, 0, 12, 2, 95, 96, 79, 138, 6, 35, 82, 37, 87, 0, 0, 7, 195, 36, 67, 64, 9, 17, 7, 195, 20, 195, 64, 9, 17, 7, 195, 5, 51, 128, 9, 17, 0, 0, 0, 0, 6, 195, 8, 147, 192, 72, 7, 195, 4, 195, 64, 9, 17, 0, 7, 196, 56, 148, 193, 52, 76, 0, 0, 16, 4, 95, 7, 18, 22, 50, 6, 35, 79, 55, 120, 87, 120, 49, 0, 0, 7, 195, 36, 52, 192, 9, 17, 0, 0, 0, 0, 7, 195, 85, 52, 128, 9, 17, 7, 195, 20, 52, 192, 9, 17, 0, 0, 0, 6, 195, 56, 148, 201, 76, 0, 7, 195, 72, 21, 192, 9, 17, 7, 195, 4, 53, 192, 9, 17, 26, 4, 95, 226, 128, 185, 6, 39, 47, 82, 39, 51, 36, 50, 37, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 0, 0, 0, 25, 2, 95, 123, 6, 39, 47, 82, 39, 51, 36, 50, 120, 15, 82, 6, 37, 47, 37, 74, 120, 87, 47, 120, 0, 14, 4, 95, 4, 9, 1, 6, 40, 63, 55, 120, 137, 47, 0, 0, 0, 0, 0, 0, 0, 26, 2, 95, 125, 86, 6, 35, 47, 82, 39, 51, 36, 50, 120, 15, 82, 6, 37, 47, 37, 74, 120, 87, 47, 120, 0, 0, 15, 2, 95, 124, 6, 40, 87, 48, 51, 120, 82, 50, 120, 0, 102, 13, 2, 95, 124, 6, 39, 49, 39, 63, 37, 115, 120, 0, 0, 0, 0, 0, 6, 194, 101, 80, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 36, 64, 128, 9, 17, 7, 195, 5, 48, 192, 9, 17, 0, 0, 0, 0, 7, 195, 57, 32, 64, 9, 17, 7, 195, 21, 48, 192, 9, 17, 0, 0, 0, 0, 7, 195, 13, 1, 64, 9, 17, 0, 0, 0, 0, 7, 195, 84, 65, 128, 9, 17, 7, 195, 57, 33, 64, 9, 17, 0, 0, 0, 0, 0, 0, 0, 6, 195, 56, 148, 213, 76, 0, 7, 195, 57, 34, 64, 9, 17, 0, 0, 0, 5, 194, 97, 144, 17, 0, 7, 195, 4, 67, 128, 9, 17, 0, 21, 5, 95, 49, 77, 65, 49, 57, 36, 70, 50, 120, 15, 105, 37, 61, 120, 70, 120, 0, 102, 0, 0, 0, 7, 195, 57, 35, 64, 9, 17, 6, 195, 25, 35, 64, 17, 0, 0, 0, 0, 7, 195, 37, 52, 192, 9, 17, 0, 0, 0, 0, 6, 195, 88, 36, 128, 17, 7, 195, 85, 52, 192, 9, 17, 7, 195, 57, 36, 64, 9, 17, 0, 0, 0, 0, 7, 195, 13, 5, 64, 9, 17, 0, 0, 0, 0, 7, 195, 57, 37, 64, 9, 17, 0, 0, 0, 0, 0, 0, 0, 16, 70, 12, 243, 148, 72, 243, 0, 115, 39, 50, 47, 51, 123, 55, 0, 0, 0, 7, 196, 56, 148, 205, 60, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 36, 64, 192, 9, 17, 0, 0, 0, 0, 15, 67, 64, 245, 24, 48, 6, 39, 47, 15, 6, 37, 49, 87, 0, 6, 195, 36, 208, 64, 76, 7, 195, 57, 32, 128, 9, 17, 0, 0, 0, 0, 6, 195, 9, 33, 128, 17, 7, 195, 5, 65, 128, 9, 17, 0, 0, 0, 0, 13, 67, 85, 65, 128, 40, 15, 47, 36, 15, 36, 81, 0, 7, 195, 57, 33, 128, 9, 17, 7, 195, 4, 193, 192, 9, 17, 0, 0, 0, 0, 7, 195, 64, 114, 64, 9, 17, 0, 0, 0, 0, 7, 195, 36, 194, 192, 9, 17, 0, 0, 0, 6, 195, 36, 208, 77, 76, 0, 6, 195, 76, 19, 64, 72, 7, 195, 28, 131, 192, 9, 17, 0, 0, 0, 0, 0, 0, 8, 3, 4, 197, 190, 73, 13, 0, 0, 0, 6, 195, 41, 36, 128, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 4, 68, 204, 17, 0, 0, 0, 0, 7, 195, 37, 70, 128, 9, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 196, 135, 0, 3, 76, 0, 7, 6, 196, 141, 0, 3, 74, 0, 7, 6, 196, 145, 0, 3, 75, 0, 7, 6, 197, 161, 0, 3, 89, 0, 7, 6, 197, 190, 0, 3, 88, 0, 7, 6, 97, 0, 3, 35, 0, 4, 2, 106, 3, 135, 0, 2, 114, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 115, 0, 7, 6, 100, 0, 3, 70, 0, 197, 190, 3, 73, 0, 122, 3, 116, 0, 7, 6, 101, 0, 120, 101, 5, 2, 8, 3, 2, 36, 37, 49, 87, 36, 0, 120, 101, 8, 3, 2, 36, 49, 87, 36, 0, 4, 1, 106, 3, 36, 0, 2, 106, 0, 3, 107, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 3, 79, 0, 7, 6, 104, 0, 8, 3, 99, 0, 3, 105, 0, 7, 6, 105, 0, 110, 105, 1, 32, 46, 3, 2, 37, 50, 37, 0, 3, 37, 0, 7, 6, 106, 0, 3, 57, 0, 1, 17, 65, 29, 2, 32, 3, 57, 10, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 1, 25, 2, 25, 3, 45, 0, 3, 55, 0, 106, 1, 118, 3, 55, 57, 0, 106, 2, 12, 3, 61, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 106, 3, 65, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 7, 6, 111, 0, 3, 39, 0, 117, 3, 127, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 117, 5, 2, 3, 49, 40, 0, 117, 3, 49, 82, 0, 7, 6, 114, 0, 4, 3, 51, 0, 1, 17, 65, 2, 17, 65, 0, 2, 32, 0, 114, 0, 1, 25, 2, 25, 3, 52, 0, 1, 25, 2, 17, 65, 3, 138, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 7, 6, 117, 0, 3, 40, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 82, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 1, 25, 2, 25, 3, 37, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 206, 0, 177, 3, 6, 35, 55, 81, 120, 0, 172, 3, 6, 35, 55, 81, 120, 15, 47, 6, 39, 50, 39, 87, 0, 183, 3, 6, 36, 47, 120, 0, 174, 3, 6, 36, 47, 120, 15, 47, 6, 39, 50, 39, 87, 0, 181, 3, 6, 36, 48, 87, 136, 55, 39, 50, 0, 173, 3, 6, 36, 48, 87, 136, 55, 39, 50, 15, 47, 6, 39, 50, 39, 87, 0, 191, 3, 6, 39, 63, 136, 49, 138, 39, 50, 10, 0, 184, 3, 47, 99, 6, 36, 47, 120, 0, 186, 3, 49, 6, 35, 48, 120, 0, 190, 3, 49, 87, 6, 37, 0, 189, 3, 50, 6, 37, 0, 187, 3, 55, 6, 35, 63, 70, 120, 0, 185, 3, 57, 6, 39, 47, 120, 0, 175, 3, 57, 6, 39, 47, 120, 15, 47, 6, 39, 50, 39, 87, 0, 188, 3, 63, 6, 37, 0, 178, 3, 69, 6, 36, 47, 120, 0, 180, 3, 70, 6, 36, 55, 47, 120, 0, 179, 3, 79, 6, 35, 63, 120, 0, 182, 3, 86, 6, 36, 47, 120, 0, 7, 6, 207, 0, 137, 3, 6, 39, 63, 36, 79, 120, 0, 142, 3, 6, 39, 63, 36, 79, 120, 15, 47, 6, 39, 50, 39, 87, 0, 140, 3, 6, 39, 63, 136, 49, 138, 39, 50, 15, 47, 6, 39, 50, 39, 87, 0, 132, 3, 47, 6, 35, 40, 0, 128, 3, 48, 6, 37, 0, 136, 3, 48, 87, 6, 37, 0, 129, 3, 51, 6, 39, 0, 141, 3, 79, 44, 74, 49, 37, 15, 6, 37, 48, 87, 136, 55, 39, 50, 15, 47, 6, 39, 50, 39, 87, 0, 133, 3, 79, 44, 74, 49, 37, 23, 6, 37, 48, 87, 136, 55, 39, 50, 0, 130, 3, 79, 44, 74, 49, 39, 23, 86, 6, 35, 82, 44, 89, 50, 39, 23, 87, 6, 37, 79, 63, 120, 0, 134, 3, 81, 6, 37, 0, 131, 3, 87, 6, 37, 79, 63, 120, 0, 135, 3, 99, 6, 37, 0, 7, 6, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 4, 195, 159, 3, 21, 100, 101, 0, 195, 164, 0, 195, 182, 0, 195, 188, 0, 45, 8, 32, 2, 32, 15, 3, 63, 37, 50, 40, 87, 0, 36, 3, 70, 6, 39, 55, 120, 51, 0, 195, 173, 3, 119, 0, 195, 169, 3, 121, 0, 195, 161, 3, 122, 0, 195, 179, 3, 123, 0, 195, 186, 3, 124, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts21 = FileInMemory_createWithData (7359, reinterpret_cast (&espeakdata_dicts21_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/hbs_dict", L"hbs"); Collection_addItem (me.peek(), espeakdata_dicts21.transfer()); static unsigned char espeakdata_dicts22_data[5721] = { 0, 4, 0, 0, 152, 15, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 224, 164, 149, 224, 165, 128, 72, 0, 15, 140, 224, 164, 134, 224, 164, 170, 224, 164, 149, 224, 165, 139, 72, 0, 0, 12, 137, 224, 164, 176, 224, 164, 185, 224, 165, 128, 72, 9, 134, 224, 164, 175, 224, 165, 135, 72, 9, 134, 224, 164, 175, 224, 165, 135, 72, 0, 0, 0, 15, 140, 224, 164, 137, 224, 164, 168, 224, 164, 149, 224, 165, 128, 72, 15, 140, 224, 164, 137, 224, 164, 184, 224, 164, 149, 224, 165, 128, 72, 15, 140, 224, 164, 134, 224, 164, 170, 224, 164, 149, 224, 165, 128, 72, 0, 9, 134, 224, 164, 149, 224, 165, 135, 72, 9, 134, 224, 164, 181, 224, 165, 135, 72, 0, 0, 0, 12, 137, 224, 164, 176, 224, 164, 185, 224, 165, 135, 72, 0, 9, 134, 224, 164, 149, 224, 165, 139, 72, 9, 134, 224, 164, 181, 224, 165, 139, 72, 9, 134, 224, 164, 181, 224, 165, 139, 72, 0, 0, 15, 140, 224, 164, 137, 224, 164, 168, 224, 164, 149, 224, 165, 135, 72, 15, 140, 224, 164, 137, 224, 164, 184, 224, 164, 149, 224, 165, 135, 72, 15, 140, 224, 164, 134, 224, 164, 170, 224, 164, 149, 224, 165, 135, 72, 15, 140, 224, 164, 174, 224, 165, 129, 224, 164, 157, 224, 165, 135, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 224, 164, 185, 224, 165, 136, 72, 0, 0, 0, 9, 134, 224, 164, 185, 224, 165, 139, 72, 0, 0, 0, 0, 0, 0, 12, 137, 224, 164, 174, 224, 165, 135, 224, 164, 130, 72, 0, 0, 0, 15, 140, 224, 164, 185, 224, 164, 174, 224, 165, 135, 224, 164, 130, 72, 0, 0, 0, 0, 0, 0, 21, 146, 224, 164, 137, 224, 164, 168, 224, 165, 141, 224, 164, 185, 224, 165, 135, 224, 164, 130, 72, 21, 146, 224, 164, 135, 224, 164, 168, 224, 165, 141, 224, 164, 185, 224, 165, 135, 224, 164, 130, 72, 0, 0, 0, 15, 140, 224, 164, 164, 224, 165, 129, 224, 164, 157, 224, 165, 135, 72, 24, 149, 224, 164, 164, 224, 165, 129, 224, 164, 174, 224, 165, 141, 224, 164, 185, 224, 165, 135, 224, 164, 130, 72, 0, 0, 12, 137, 224, 164, 174, 224, 164, 151, 224, 164, 176, 8, 0, 11, 6, 224, 164, 151, 224, 164, 188, 98, 13, 0, 0, 9, 134, 224, 164, 181, 224, 164, 185, 72, 0, 0, 0, 11, 6, 224, 164, 149, 224, 164, 188, 102, 13, 0, 0, 0, 9, 134, 224, 164, 149, 224, 164, 190, 72, 0, 0, 0, 0, 0, 0, 15, 140, 224, 164, 137, 224, 164, 168, 224, 164, 149, 224, 164, 190, 72, 15, 140, 224, 164, 137, 224, 164, 184, 224, 164, 149, 224, 164, 190, 72, 15, 140, 224, 164, 135, 224, 164, 168, 224, 164, 149, 224, 164, 190, 72, 15, 140, 224, 164, 135, 224, 164, 184, 224, 164, 149, 224, 164, 190, 72, 0, 0, 0, 0, 11, 6, 224, 164, 171, 224, 164, 188, 81, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 140, 224, 164, 149, 224, 165, 141, 224, 164, 175, 224, 164, 190, 72, 8, 0, 12, 137, 224, 164, 176, 224, 164, 185, 224, 164, 190, 72, 0, 17, 4, 95, 4, 16, 20, 10, 70, 13, 87, 13, 63, 55, 6, 117, 10, 0, 0, 0, 15, 140, 224, 164, 134, 224, 164, 170, 224, 164, 149, 224, 164, 190, 72, 0, 0, 0, 0, 0, 0, 31, 21, 224, 164, 149, 224, 165, 141, 224, 164, 176, 224, 164, 191, 224, 164, 149, 224, 165, 135, 224, 164, 159, 49, 34, 111, 49, 6, 114, 47, 0, 0, 0, 0, 9, 134, 224, 164, 175, 224, 164, 185, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 164, 161, 224, 164, 188, 68, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 224, 164, 185, 224, 164, 174, 72, 0, 0, 0, 12, 137, 224, 164, 164, 224, 165, 129, 224, 164, 174, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 51, 57, 120, 50, 47, 116, 55, 6, 111, 87, 0, 12, 3, 95, 50, 49, 111, 49, 12, 6, 111, 87, 0, 0, 12, 3, 95, 51, 56, 35, 34, 47, 6, 111, 87, 0, 10, 3, 95, 50, 48, 69, 6, 110, 87, 0, 0, 11, 3, 95, 50, 51, 47, 6, 112, 111, 87, 0, 0, 11, 3, 95, 50, 50, 69, 6, 116, 111, 87, 0, 0, 13, 3, 95, 50, 53, 48, 13, 78, 12, 6, 111, 87, 0, 0, 12, 3, 95, 50, 52, 78, 6, 118, 69, 111, 87, 0, 0, 14, 3, 95, 50, 55, 87, 13, 47, 12, 6, 116, 111, 87, 0, 0, 14, 3, 95, 50, 54, 142, 13, 69, 69, 6, 110, 34, 87, 0, 0, 14, 3, 95, 51, 49, 111, 49, 13, 47, 12, 6, 111, 87, 0, 0, 10, 3, 95, 51, 48, 47, 6, 110, 87, 0, 0, 12, 3, 95, 51, 51, 47, 125, 47, 6, 111, 87, 0, 0, 13, 3, 95, 51, 50, 69, 35, 47, 12, 6, 111, 87, 0, 0, 9, 134, 224, 164, 165, 224, 165, 128, 72, 12, 3, 95, 51, 53, 48, 125, 47, 6, 111, 87, 0, 0, 12, 3, 95, 51, 52, 78, 128, 47, 6, 111, 87, 0, 0, 12, 3, 95, 51, 55, 87, 125, 47, 6, 111, 87, 0, 0, 13, 3, 95, 51, 54, 142, 35, 85, 6, 47, 111, 87, 0, 0, 0, 9, 134, 224, 164, 165, 224, 165, 135, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 55, 57, 4, 120, 65, 111, 116, 87, 6, 110, 0, 12, 3, 95, 54, 49, 6, 111, 49, 87, 13, 140, 0, 0, 9, 3, 224, 165, 140, 146, 133, 0, 103, 8, 3, 224, 165, 140, 146, 118, 0, 16, 3, 95, 55, 56, 35, 136, 105, 35, 47, 12, 6, 107, 34, 12, 0, 10, 3, 95, 54, 48, 87, 6, 116, 140, 0, 0, 9, 3, 95, 48, 67, 87, 6, 118, 0, 13, 3, 95, 54, 51, 47, 6, 111, 34, 87, 13, 140, 0, 0, 12, 3, 95, 54, 50, 69, 6, 116, 87, 13, 140, 0, 0, 8, 3, 224, 165, 137, 18, 119, 0, 12, 3, 95, 54, 53, 48, 132, 50, 87, 13, 140, 0, 0, 9, 3, 224, 165, 136, 146, 132, 0, 102, 8, 3, 224, 165, 136, 146, 113, 0, 12, 3, 95, 54, 52, 78, 6, 128, 87, 13, 140, 0, 0, 8, 3, 224, 165, 139, 146, 117, 0, 13, 3, 95, 54, 55, 87, 6, 107, 34, 87, 13, 140, 0, 0, 8, 3, 224, 165, 138, 18, 39, 0, 14, 3, 95, 54, 54, 142, 6, 111, 57, 116, 87, 13, 140, 0, 0, 8, 3, 224, 165, 133, 18, 114, 0, 15, 3, 95, 55, 49, 111, 144, 35, 47, 12, 6, 107, 34, 12, 0, 0, 9, 3, 224, 165, 132, 18, 34, 111, 0, 14, 3, 95, 55, 48, 87, 35, 47, 12, 6, 107, 34, 12, 0, 0, 8, 3, 224, 165, 135, 146, 112, 0, 16, 3, 95, 55, 51, 47, 111, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 8, 3, 224, 165, 134, 18, 36, 0, 16, 3, 95, 55, 50, 69, 13, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 8, 3, 224, 165, 129, 18, 120, 0, 17, 3, 95, 55, 53, 48, 35, 142, 4, 35, 47, 12, 6, 107, 34, 12, 0, 0, 8, 3, 224, 165, 128, 146, 110, 0, 16, 3, 95, 55, 52, 78, 118, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 9, 3, 224, 165, 131, 18, 34, 111, 0, 18, 3, 95, 55, 55, 87, 13, 47, 13, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 8, 3, 224, 165, 130, 146, 121, 0, 16, 3, 95, 55, 54, 142, 111, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 12, 3, 95, 49, 57, 120, 50, 50, 6, 111, 87, 0, 0, 13, 3, 95, 49, 56, 107, 140, 12, 6, 116, 34, 109, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 57, 120, 50, 47, 6, 111, 87, 0, 12, 3, 95, 49, 49, 79, 57, 6, 116, 34, 109, 0, 0, 13, 3, 95, 50, 56, 35, 136, 12, 6, 116, 111, 87, 0, 10, 3, 95, 49, 48, 70, 6, 107, 87, 0, 0, 11, 3, 95, 49, 51, 47, 6, 113, 34, 109, 0, 0, 11, 3, 95, 49, 50, 69, 6, 116, 34, 109, 0, 0, 13, 3, 95, 49, 53, 48, 6, 107, 50, 70, 34, 109, 0, 0, 11, 3, 95, 49, 52, 142, 6, 118, 70, 109, 0, 0, 13, 3, 95, 49, 55, 87, 6, 107, 47, 12, 34, 109, 0, 0, 11, 3, 95, 49, 54, 87, 6, 117, 55, 109, 0, 0, 8, 3, 224, 164, 165, 136, 13, 0, 0, 8, 3, 224, 164, 164, 47, 13, 0, 0, 9, 134, 224, 164, 165, 224, 164, 190, 72, 8, 3, 224, 164, 167, 137, 13, 0, 0, 8, 3, 224, 164, 166, 70, 13, 0, 0, 8, 3, 224, 164, 161, 139, 13, 0, 0, 8, 3, 224, 164, 160, 140, 13, 0, 0, 8, 3, 224, 164, 163, 64, 13, 0, 0, 8, 3, 224, 164, 162, 141, 13, 0, 0, 8, 3, 224, 164, 157, 143, 13, 0, 12, 3, 95, 52, 57, 6, 120, 65, 78, 116, 87, 0, 0, 11, 3, 224, 165, 164, 70, 107, 64, 139, 107, 0, 8, 3, 224, 164, 156, 77, 13, 0, 14, 3, 95, 52, 56, 35, 34, 47, 116, 55, 6, 111, 87, 0, 0, 8, 3, 224, 164, 159, 138, 13, 0, 0, 8, 3, 224, 164, 158, 65, 13, 0, 0, 8, 3, 224, 164, 153, 66, 13, 0, 0, 8, 3, 224, 164, 152, 145, 13, 0, 0, 9, 3, 224, 165, 163, 146, 45, 12, 0, 8, 3, 224, 164, 155, 142, 13, 0, 0, 8, 3, 224, 165, 162, 18, 45, 0, 8, 3, 224, 164, 154, 78, 13, 0, 0, 9, 3, 224, 165, 157, 105, 34, 13, 0, 8, 3, 224, 164, 149, 49, 13, 0, 12, 3, 95, 53, 57, 120, 50, 87, 6, 107, 136, 0, 14, 3, 95, 52, 49, 111, 49, 47, 116, 55, 6, 111, 87, 0, 0, 8, 3, 224, 165, 156, 44, 13, 0, 14, 3, 95, 53, 56, 35, 136, 12, 6, 116, 58, 13, 50, 0, 12, 3, 95, 52, 48, 78, 116, 55, 6, 111, 87, 0, 0, 8, 3, 224, 165, 159, 57, 13, 0, 8, 3, 224, 164, 151, 79, 13, 0, 14, 3, 95, 52, 51, 47, 125, 47, 116, 55, 6, 111, 87, 0, 0, 8, 3, 224, 165, 158, 81, 13, 0, 8, 3, 224, 164, 150, 144, 13, 0, 13, 3, 95, 52, 50, 69, 132, 116, 55, 6, 111, 87, 0, 0, 8, 3, 224, 165, 153, 99, 13, 0, 16, 3, 95, 52, 53, 48, 132, 6, 50, 47, 116, 55, 6, 111, 87, 0, 0, 8, 3, 224, 165, 152, 102, 13, 0, 14, 3, 95, 52, 52, 78, 118, 58, 116, 55, 6, 111, 87, 0, 0, 8, 3, 224, 165, 155, 86, 13, 0, 14, 3, 95, 52, 55, 87, 125, 47, 116, 55, 6, 111, 87, 0, 0, 13, 137, 224, 164, 133, 224, 164, 151, 224, 164, 176, 72, 8, 8, 3, 224, 165, 154, 98, 13, 0, 15, 3, 95, 52, 54, 142, 105, 111, 57, 116, 55, 6, 111, 87, 0, 0, 18, 3, 95, 54, 57, 120, 50, 13, 105, 4, 35, 47, 12, 6, 107, 34, 12, 0, 14, 3, 95, 53, 49, 111, 49, 57, 6, 116, 58, 107, 50, 0, 0, 11, 3, 95, 54, 56, 35, 34, 87, 13, 140, 0, 12, 3, 95, 53, 48, 48, 13, 78, 6, 116, 87, 0, 0, 13, 3, 95, 53, 51, 47, 6, 111, 34, 48, 107, 50, 0, 0, 12, 3, 95, 53, 50, 69, 6, 116, 58, 107, 50, 0, 0, 13, 3, 95, 53, 53, 48, 6, 35, 142, 48, 107, 50, 0, 0, 9, 3, 224, 165, 144, 18, 129, 63, 0, 13, 3, 95, 53, 52, 78, 6, 119, 121, 58, 107, 50, 0, 0, 15, 3, 95, 53, 55, 87, 107, 47, 12, 6, 116, 58, 13, 50, 0, 0, 14, 3, 95, 53, 54, 142, 105, 13, 48, 12, 6, 107, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 57, 50, 107, 58, 116, 87, 6, 110, 0, 0, 13, 3, 95, 56, 56, 35, 136, 12, 116, 87, 6, 110, 0, 0, 8, 3, 224, 164, 191, 18, 111, 0, 0, 8, 3, 224, 164, 190, 146, 116, 0, 0, 8, 3, 224, 164, 185, 106, 13, 0, 0, 8, 3, 224, 164, 184, 87, 13, 0, 0, 0, 0, 8, 3, 224, 164, 181, 82, 13, 0, 16, 3, 95, 57, 57, 50, 111, 65, 57, 6, 116, 50, 13, 58, 112, 0, 13, 3, 95, 56, 49, 111, 49, 57, 116, 87, 6, 110, 0, 0, 15, 3, 95, 57, 56, 35, 136, 12, 6, 116, 50, 13, 58, 112, 0, 12, 3, 95, 56, 48, 4, 107, 87, 87, 6, 110, 0, 0, 8, 3, 224, 164, 183, 91, 13, 0, 13, 3, 95, 56, 51, 47, 111, 34, 116, 87, 6, 110, 0, 0, 8, 3, 224, 164, 182, 89, 13, 0, 12, 3, 95, 56, 50, 69, 132, 116, 87, 6, 110, 0, 0, 8, 3, 224, 164, 177, 34, 13, 0, 14, 3, 95, 56, 53, 48, 111, 6, 78, 116, 87, 6, 110, 0, 0, 8, 3, 224, 164, 176, 34, 13, 0, 13, 3, 95, 56, 52, 78, 118, 34, 116, 87, 6, 110, 0, 0, 8, 3, 224, 164, 179, 62, 13, 0, 14, 3, 95, 56, 55, 87, 107, 47, 12, 116, 87, 6, 110, 0, 0, 8, 3, 224, 164, 178, 55, 13, 0, 13, 3, 95, 56, 54, 142, 111, 57, 116, 87, 6, 110, 0, 0, 8, 3, 224, 164, 173, 135, 13, 0, 15, 3, 95, 57, 49, 111, 49, 57, 6, 116, 50, 13, 58, 112, 0, 0, 8, 3, 224, 164, 172, 69, 13, 0, 12, 3, 95, 57, 48, 50, 107, 69, 12, 6, 112, 0, 0, 10, 3, 224, 164, 175, 57, 13, 0, 72, 8, 8, 3, 224, 164, 175, 57, 13, 0, 15, 3, 95, 57, 51, 47, 111, 34, 6, 116, 50, 13, 58, 112, 0, 0, 8, 3, 224, 164, 174, 63, 13, 0, 13, 3, 95, 57, 50, 69, 6, 116, 50, 13, 58, 112, 0, 0, 15, 3, 95, 57, 53, 48, 13, 78, 6, 116, 50, 13, 58, 112, 0, 0, 8, 3, 224, 164, 168, 50, 13, 0, 15, 3, 95, 57, 52, 78, 118, 34, 6, 116, 63, 13, 58, 112, 0, 0, 8, 3, 224, 164, 171, 134, 13, 0, 16, 3, 95, 57, 55, 87, 13, 47, 12, 6, 116, 50, 13, 58, 112, 0, 0, 8, 3, 224, 164, 170, 48, 13, 0, 15, 3, 95, 57, 54, 142, 111, 57, 6, 116, 50, 13, 58, 112, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 48, 77, 52, 6, 107, 34, 13, 69, 0, 0, 13, 4, 95, 48, 77, 53, 144, 6, 107, 34, 13, 69, 0, 0, 11, 4, 95, 48, 77, 50, 55, 6, 116, 144, 0, 0, 13, 4, 95, 48, 77, 51, 78, 34, 6, 39, 34, 36, 0, 0, 0, 13, 4, 95, 48, 77, 49, 105, 13, 86, 6, 116, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 224, 164, 185, 224, 165, 136, 224, 164, 130, 72, 0, 0, 0, 0, 0, 9, 134, 224, 164, 164, 224, 165, 130, 72, 0, 0, 0, 0, 0, 0, 18, 143, 224, 164, 137, 224, 164, 184, 224, 165, 141, 224, 164, 184, 224, 165, 135, 72, 18, 143, 224, 164, 135, 224, 164, 184, 224, 165, 141, 224, 164, 184, 224, 165, 135, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 27, 152, 224, 164, 164, 224, 165, 129, 224, 164, 174, 224, 165, 141, 224, 164, 185, 224, 164, 190, 224, 164, 176, 224, 165, 135, 72, 0, 0, 0, 0, 0, 27, 152, 224, 164, 164, 224, 165, 129, 224, 164, 174, 224, 165, 141, 224, 164, 185, 224, 164, 190, 224, 164, 176, 224, 165, 128, 72, 0, 0, 0, 0, 0, 0, 12, 137, 224, 164, 185, 224, 165, 130, 224, 164, 129, 72, 0, 12, 137, 224, 164, 165, 224, 165, 128, 224, 164, 130, 72, 12, 137, 224, 164, 174, 224, 165, 136, 224, 164, 130, 72, 0, 0, 9, 134, 224, 164, 184, 224, 165, 135, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 224, 164, 164, 224, 164, 149, 72, 0, 0, 0, 18, 143, 224, 164, 133, 224, 164, 151, 224, 164, 176, 224, 164, 154, 224, 165, 135, 8, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 164, 150, 224, 164, 188, 99, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 27, 152, 224, 164, 164, 224, 165, 129, 224, 164, 174, 224, 165, 141, 224, 164, 185, 224, 164, 190, 224, 164, 176, 224, 164, 190, 72, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 224, 164, 170, 224, 164, 176, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 164, 156, 224, 164, 188, 86, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 134, 224, 164, 148, 224, 164, 176, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 16, 140, 224, 164, 172, 224, 164, 191, 224, 164, 168, 224, 164, 190, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 224, 164, 134, 224, 164, 170, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 2, 95, 51, 47, 6, 110, 50, 0, 0, 8, 2, 95, 50, 70, 6, 117, 0, 0, 8, 2, 95, 49, 6, 112, 49, 0, 0, 11, 2, 95, 48, 89, 6, 121, 64, 57, 107, 0, 0, 9, 2, 95, 55, 87, 6, 116, 47, 0, 0, 8, 2, 95, 54, 142, 6, 109, 0, 0, 10, 2, 95, 53, 48, 6, 116, 50, 78, 0, 0, 10, 2, 95, 52, 78, 6, 116, 34, 12, 0, 0, 0, 0, 9, 2, 95, 57, 50, 6, 133, 0, 103, 8, 2, 95, 57, 50, 6, 118, 0, 0, 8, 2, 95, 56, 6, 116, 140, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 164, 174, 224, 165, 135, 224, 164, 176, 224, 165, 135, 72, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 164, 174, 224, 165, 135, 224, 164, 176, 224, 165, 128, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 137, 224, 164, 175, 224, 164, 166, 224, 164, 191, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 143, 224, 164, 185, 224, 164, 174, 224, 164, 190, 224, 164, 176, 224, 165, 135, 72, 0, 0, 0, 0, 0, 0, 0, 18, 143, 224, 164, 185, 224, 164, 174, 224, 164, 190, 224, 164, 176, 224, 165, 128, 72, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 164, 164, 224, 165, 135, 224, 164, 176, 224, 164, 190, 72, 15, 140, 224, 164, 174, 224, 165, 135, 224, 164, 176, 224, 164, 190, 72, 0, 24, 15, 224, 164, 184, 224, 164, 190, 224, 164, 175, 224, 164, 172, 224, 164, 176, 87, 6, 132, 69, 13, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 143, 224, 164, 185, 224, 164, 174, 224, 164, 190, 224, 164, 176, 224, 164, 190, 72, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 102, 9, 0, 0, 48, 0, 0, 0, 103, 9, 0, 0, 49, 0, 0, 0, 104, 9, 0, 0, 50, 0, 0, 0, 105, 9, 0, 0, 51, 0, 0, 0, 106, 9, 0, 0, 52, 0, 0, 0, 107, 9, 0, 0, 53, 0, 0, 0, 108, 9, 0, 0, 54, 0, 0, 0, 109, 9, 0, 0, 55, 0, 0, 0, 110, 9, 0, 0, 56, 0, 0, 0, 111, 9, 0, 0, 57, 0, 0, 0, 0, 0, 0, 0, 6, 1, 2, 0, 3, 50, 0, 7, 6, 1, 3, 0, 3, 50, 0, 4, 2, 224, 164, 170, 3, 63, 0, 2, 224, 164, 171, 0, 2, 224, 164, 172, 0, 2, 224, 164, 173, 0, 2, 224, 164, 174, 0, 4, 2, 224, 164, 159, 3, 64, 0, 2, 224, 164, 160, 0, 2, 224, 164, 161, 0, 2, 224, 164, 162, 0, 2, 224, 164, 163, 0, 4, 2, 224, 164, 154, 3, 65, 0, 2, 224, 164, 155, 0, 2, 224, 164, 156, 0, 2, 224, 164, 157, 0, 2, 224, 164, 158, 0, 2, 224, 164, 175, 0, 4, 2, 224, 164, 149, 3, 66, 0, 2, 224, 164, 150, 0, 2, 224, 164, 151, 0, 2, 224, 164, 152, 0, 2, 224, 164, 153, 0, 2, 224, 164, 185, 0, 7, 6, 1, 4, 0, 3, 106, 0, 7, 6, 1, 6, 0, 3, 107, 0, 4, 1, 185, 164, 224, 133, 164, 224, 3, 114, 0, 2, 224, 164, 185, 0, 7, 6, 1, 7, 0, 3, 116, 0, 7, 6, 1, 8, 0, 3, 111, 0, 7, 6, 1, 9, 0, 2, 32, 3, 37, 0, 3, 110, 0, 7, 6, 1, 10, 0, 3, 120, 0, 7, 6, 1, 11, 0, 3, 121, 0, 4, 224, 164, 129, 3, 131, 0, 224, 164, 130, 0, 7, 6, 1, 12, 0, 3, 34, 111, 0, 7, 6, 1, 13, 0, 3, 45, 0, 7, 6, 1, 14, 0, 3, 114, 0, 7, 6, 1, 15, 0, 3, 36, 0, 7, 6, 1, 16, 0, 3, 112, 0, 7, 6, 1, 17, 0, 3, 113, 0, 4, 224, 164, 129, 3, 125, 0, 224, 164, 130, 0, 5, 2, 3, 132, 0, 7, 6, 1, 18, 0, 3, 119, 0, 7, 6, 1, 19, 0, 3, 39, 0, 7, 6, 1, 20, 0, 3, 117, 0, 4, 224, 164, 129, 3, 129, 0, 224, 164, 130, 0, 7, 6, 1, 21, 0, 3, 118, 0, 4, 224, 164, 129, 3, 128, 0, 224, 164, 130, 0, 5, 3, 3, 133, 0, 7, 6, 1, 22, 0, 2, 17, 66, 3, 49, 0, 2, 224, 165, 141, 224, 164, 175, 3, 49, 12, 0, 3, 49, 107, 0, 224, 164, 188, 2, 17, 66, 3, 102, 0, 224, 164, 188, 3, 102, 107, 0, 7, 6, 1, 23, 0, 224, 164, 188, 2, 17, 66, 3, 99, 0, 224, 164, 188, 3, 99, 107, 0, 2, 17, 66, 3, 144, 0, 3, 144, 107, 0, 7, 6, 1, 24, 0, 2, 17, 66, 3, 79, 0, 3, 79, 107, 0, 224, 164, 188, 2, 17, 66, 3, 98, 0, 224, 164, 188, 3, 98, 107, 0, 7, 6, 1, 25, 0, 2, 17, 66, 3, 145, 0, 3, 145, 107, 0, 7, 6, 1, 26, 0, 2, 17, 66, 3, 66, 0, 1, 141, 165, 224, 2, 32, 3, 66, 13, 0, 3, 66, 107, 0, 7, 6, 1, 27, 0, 2, 17, 66, 3, 78, 0, 2, 224, 165, 141, 224, 164, 175, 3, 78, 12, 0, 3, 78, 107, 0, 7, 6, 1, 28, 0, 2, 17, 66, 3, 142, 0, 3, 142, 107, 0, 7, 6, 1, 29, 0, 2, 17, 66, 3, 77, 0, 3, 77, 107, 0, 224, 164, 188, 2, 17, 66, 3, 86, 0, 224, 164, 188, 3, 86, 107, 0, 7, 6, 1, 30, 0, 2, 17, 66, 3, 143, 0, 3, 143, 107, 0, 7, 6, 1, 31, 0, 4, 1, 141, 165, 224, 2, 32, 3, 65, 0, 2, 17, 66, 0, 3, 65, 107, 0, 7, 6, 1, 32, 0, 2, 17, 66, 3, 138, 0, 2, 224, 165, 141, 224, 164, 175, 3, 138, 12, 0, 3, 138, 107, 0, 7, 6, 1, 33, 0, 2, 17, 66, 3, 140, 0, 3, 140, 107, 0, 7, 6, 1, 34, 0, 224, 164, 188, 2, 17, 66, 3, 68, 0, 224, 164, 188, 3, 68, 107, 0, 2, 17, 66, 3, 139, 0, 3, 139, 107, 0, 7, 6, 1, 35, 0, 224, 164, 188, 2, 17, 66, 3, 68, 105, 0, 224, 164, 188, 3, 68, 105, 107, 0, 2, 17, 66, 3, 141, 0, 3, 141, 107, 0, 7, 6, 1, 36, 0, 2, 17, 66, 3, 64, 0, 1, 141, 165, 224, 2, 32, 3, 64, 13, 0, 3, 64, 107, 0, 7, 6, 1, 37, 0, 2, 17, 66, 3, 47, 0, 2, 224, 165, 141, 224, 164, 175, 3, 47, 12, 0, 3, 47, 107, 0, 7, 6, 1, 38, 0, 2, 17, 66, 3, 136, 0, 3, 136, 107, 0, 7, 6, 1, 39, 0, 2, 17, 66, 3, 70, 0, 3, 70, 107, 0, 7, 6, 1, 40, 0, 2, 17, 66, 3, 137, 0, 3, 137, 107, 0, 7, 6, 1, 41, 0, 4, 1, 141, 165, 224, 176, 164, 224, 2, 32, 3, 50, 0, 2, 17, 66, 0, 1, 141, 165, 224, 2, 32, 3, 50, 13, 0, 3, 50, 107, 0, 7, 6, 1, 42, 0, 3, 50, 12, 0, 7, 6, 1, 43, 0, 2, 17, 66, 3, 48, 0, 2, 224, 165, 141, 224, 164, 175, 3, 48, 12, 0, 3, 48, 107, 0, 7, 6, 1, 44, 0, 224, 164, 188, 2, 17, 66, 3, 81, 0, 224, 164, 188, 3, 81, 107, 0, 2, 17, 66, 3, 134, 0, 3, 134, 107, 0, 7, 6, 1, 45, 0, 2, 17, 66, 3, 69, 0, 3, 69, 107, 0, 7, 6, 1, 46, 0, 2, 17, 66, 3, 135, 0, 3, 135, 107, 0, 7, 6, 1, 47, 0, 4, 1, 141, 165, 224, 168, 164, 224, 2, 32, 3, 63, 0, 1, 141, 165, 224, 176, 164, 224, 2, 32, 0, 2, 17, 66, 0, 1, 141, 165, 224, 2, 32, 3, 63, 13, 0, 3, 63, 107, 0, 7, 6, 1, 48, 0, 2, 17, 66, 3, 57, 0, 1, 141, 165, 224, 2, 32, 3, 57, 13, 0, 3, 57, 107, 0, 7, 6, 1, 49, 0, 2, 17, 66, 3, 34, 0, 1, 141, 165, 224, 2, 32, 3, 34, 13, 0, 3, 34, 107, 0, 7, 6, 1, 50, 0, 2, 17, 66, 3, 34, 0, 1, 141, 165, 224, 2, 32, 3, 34, 13, 0, 3, 34, 107, 0, 7, 6, 1, 51, 0, 2, 17, 66, 3, 55, 0, 1, 141, 165, 224, 2, 32, 3, 55, 13, 0, 3, 55, 107, 0, 7, 6, 1, 52, 0, 2, 17, 66, 3, 62, 0, 1, 141, 165, 224, 2, 32, 3, 62, 13, 0, 3, 62, 107, 0, 7, 6, 1, 53, 0, 2, 17, 66, 3, 62, 0, 1, 141, 165, 224, 2, 32, 3, 62, 13, 0, 3, 62, 107, 0, 7, 6, 1, 54, 0, 8, 2, 17, 66, 3, 58, 0, 8, 3, 58, 107, 0, 4, 2, 17, 66, 3, 82, 0, 8, 2, 224, 165, 141, 0, 3, 82, 107, 0, 7, 6, 1, 55, 0, 2, 17, 66, 3, 89, 0, 3, 89, 107, 0, 7, 6, 1, 56, 0, 2, 17, 66, 3, 91, 0, 3, 91, 107, 0, 7, 6, 1, 57, 0, 2, 17, 66, 3, 87, 0, 3, 87, 107, 0, 7, 6, 1, 58, 0, 2, 17, 66, 3, 106, 0, 3, 106, 107, 0, 7, 6, 1, 62, 0, 3, 12, 0, 7, 6, 1, 63, 0, 3, 116, 0, 224, 164, 181, 3, 133, 0, 7, 6, 1, 64, 0, 3, 111, 0, 7, 6, 1, 65, 0, 2, 32, 3, 37, 0, 3, 110, 0, 7, 6, 1, 66, 0, 3, 120, 0, 7, 6, 1, 67, 0, 3, 121, 0, 4, 224, 164, 129, 3, 131, 0, 224, 164, 130, 0, 7, 6, 1, 68, 0, 3, 34, 111, 0, 7, 6, 1, 69, 0, 3, 34, 111, 0, 7, 6, 1, 70, 0, 3, 114, 0, 7, 6, 1, 71, 0, 3, 36, 0, 7, 6, 1, 72, 0, 3, 112, 0, 7, 6, 1, 73, 0, 3, 113, 0, 4, 224, 164, 129, 3, 125, 0, 224, 164, 130, 0, 5, 2, 3, 132, 0, 7, 6, 1, 74, 0, 3, 119, 0, 7, 6, 1, 75, 0, 3, 39, 0, 7, 6, 1, 76, 0, 3, 117, 0, 4, 224, 164, 129, 3, 129, 0, 224, 164, 130, 0, 7, 6, 1, 77, 0, 3, 118, 0, 4, 224, 164, 129, 3, 128, 0, 224, 164, 130, 0, 5, 3, 3, 133, 0, 7, 6, 1, 78, 0, 3, 0, 7, 6, 1, 81, 0, 3, 129, 63, 0, 7, 6, 1, 89, 0, 2, 17, 66, 3, 102, 0, 3, 102, 107, 0, 7, 6, 1, 90, 0, 2, 17, 66, 3, 99, 0, 3, 99, 107, 0, 7, 6, 1, 91, 0, 2, 17, 66, 3, 98, 0, 3, 98, 107, 0, 7, 6, 1, 92, 0, 2, 17, 66, 3, 86, 0, 3, 86, 107, 0, 7, 6, 1, 93, 0, 2, 17, 66, 3, 68, 0, 3, 68, 107, 0, 7, 6, 1, 94, 0, 2, 17, 66, 3, 68, 105, 0, 3, 68, 105, 107, 0, 7, 6, 1, 95, 0, 2, 17, 66, 3, 81, 0, 3, 81, 107, 0, 7, 6, 1, 96, 0, 2, 17, 66, 3, 57, 0, 3, 57, 107, 0, 7, 6, 1, 97, 0, 3, 107, 20, 34, 34, 0, 7, 6, 1, 98, 0, 3, 45, 12, 0, 7, 6, 1, 99, 0, 3, 45, 0, 7, 6, 1, 100, 0, 3, 45, 12, 0, 7, 6, 111, 0, 102, 1, 32, 32, 15, 2, 32, 32, 15, 194, 160, 194, 160, 194, 160, 3, 63, 36, 0, 7, 6, 0, 37, 3, 48, 107, 87, 114, 50, 47, 0, 36, 3, 70, 119, 55, 107, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts22 = FileInMemory_createWithData (5720, reinterpret_cast (&espeakdata_dicts22_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/hi_dict", L"hi"); Collection_addItem (me.peek(), espeakdata_dicts22.transfer()); static unsigned char espeakdata_dicts23_data[2417] = { 0, 4, 0, 0, 93, 8, 0, 0, 0, 0, 0, 0, 0, 7, 65, 4, 35, 0, 15, 14, 4, 193, 4, 72, 4, 193, 4, 72, 0, 5, 194, 5, 0, 72, 0, 0, 0, 6, 65, 8, 69, 37, 0, 0, 0, 0, 0, 6, 65, 12, 87, 37, 0, 0, 0, 0, 0, 6, 65, 16, 70, 37, 0, 0, 0, 0, 0, 5, 65, 20, 36, 0, 0, 5, 194, 100, 240, 72, 0, 0, 0, 6, 65, 24, 110, 81, 0, 0, 0, 0, 0, 6, 65, 28, 79, 36, 0, 0, 0, 0, 0, 6, 65, 32, 35, 89, 0, 0, 0, 0, 9, 1, 35, 35, 89, 35, 57, 0, 27, 0, 5, 65, 36, 37, 0, 0, 9, 1, 37, 48, 40, 87, 111, 0, 27, 0, 0, 0, 6, 65, 40, 88, 37, 0, 0, 0, 12, 1, 42, 35, 87, 47, 36, 34, 37, 87, 0, 27, 0, 9, 1, 43, 48, 55, 37, 87, 0, 27, 0, 6, 65, 44, 49, 35, 0, 0, 0, 0, 9, 1, 47, 87, 55, 35, 89, 0, 27, 0, 7, 65, 48, 36, 55, 0, 14, 0, 0, 0, 0, 7, 65, 52, 36, 63, 0, 14, 0, 0, 0, 0, 7, 65, 56, 36, 50, 0, 14, 0, 0, 0, 0, 5, 65, 60, 39, 0, 0, 9, 1, 61, 36, 79, 35, 55, 0, 27, 0, 0, 0, 6, 65, 64, 48, 37, 0, 0, 0, 0, 0, 7, 65, 68, 49, 57, 40, 0, 0, 0, 0, 0, 7, 65, 72, 35, 34, 35, 0, 0, 0, 0, 0, 6, 65, 76, 110, 87, 0, 0, 0, 0, 0, 7, 65, 80, 47, 35, 0, 14, 12, 65, 80, 47, 35, 48, 0, 72, 81, 97, 112, 32, 0, 0, 0, 0, 5, 65, 84, 40, 0, 0, 0, 0, 0, 6, 65, 88, 82, 35, 0, 0, 0, 0, 0, 11, 65, 92, 70, 40, 69, 82, 6, 35, 0, 14, 12, 1, 92, 111, 47, 37, 87, 55, 35, 89, 0, 27, 0, 0, 0, 0, 10, 4, 95, 49, 77, 49, 63, 37, 55, 0, 0, 0, 0, 0, 13, 65, 100, 37, 48, 87, 37, 55, 6, 39, 50, 0, 14, 0, 0, 0, 0, 7, 65, 104, 86, 36, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 4, 176, 72, 28, 0, 0, 0, 0, 0, 0, 11, 4, 95, 4, 16, 20, 10, 48, 58, 112, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 4, 224, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 48, 19, 128, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 53, 113, 78, 72, 0, 0, 6, 195, 100, 243, 128, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 51, 57, 47, 34, 111, 47, 50, 110, 81, 0, 12, 3, 95, 50, 49, 82, 112, 47, 36, 38, 112, 0, 0, 13, 3, 95, 51, 56, 47, 34, 111, 47, 109, 37, 47, 0, 8, 3, 95, 50, 48, 82, 112, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 51, 49, 47, 34, 111, 47, 36, 38, 112, 0, 0, 10, 3, 95, 51, 48, 47, 34, 111, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 54, 49, 87, 58, 35, 87, 111, 47, 36, 38, 112, 0, 0, 12, 3, 95, 54, 48, 87, 58, 35, 87, 111, 47, 0, 10, 3, 95, 51, 88, 47, 34, 111, 50, 0, 0, 8, 3, 95, 48, 67, 87, 111, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 55, 49, 87, 58, 35, 87, 111, 47, 36, 38, 114, 86, 0, 0, 15, 3, 95, 55, 48, 87, 58, 35, 87, 111, 47, 70, 37, 87, 0, 0, 0, 0, 0, 6, 195, 65, 32, 76, 72, 0, 0, 0, 5, 194, 48, 16, 72, 12, 3, 95, 49, 57, 70, 37, 86, 50, 110, 81, 0, 0, 12, 3, 95, 49, 56, 70, 37, 86, 109, 37, 47, 0, 0, 0, 0, 0, 7, 195, 21, 2, 64, 72, 8, 0, 0, 0, 12, 3, 95, 50, 57, 82, 112, 47, 50, 110, 81, 0, 8, 3, 95, 49, 49, 114, 86, 0, 0, 12, 3, 95, 50, 56, 82, 112, 47, 109, 37, 47, 0, 9, 3, 95, 49, 48, 70, 37, 87, 0, 0, 10, 3, 95, 49, 51, 47, 34, 110, 86, 0, 0, 9, 3, 95, 49, 50, 70, 40, 86, 0, 0, 9, 3, 95, 49, 53, 49, 112, 86, 0, 0, 11, 3, 95, 49, 52, 49, 35, 47, 125, 86, 0, 0, 11, 3, 95, 49, 55, 70, 37, 87, 110, 47, 0, 0, 9, 3, 95, 49, 54, 87, 110, 86, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 52, 57, 49, 35, 34, 111, 47, 50, 110, 81, 0, 0, 14, 3, 95, 52, 56, 49, 35, 34, 111, 47, 109, 37, 47, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 53, 57, 87, 112, 49, 111, 47, 50, 110, 81, 0, 14, 3, 95, 52, 49, 49, 35, 34, 111, 47, 36, 38, 112, 0, 0, 14, 3, 95, 53, 56, 87, 112, 49, 111, 47, 109, 37, 47, 0, 11, 3, 95, 52, 48, 49, 35, 34, 111, 47, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 53, 49, 87, 112, 49, 111, 47, 36, 38, 112, 0, 0, 11, 3, 95, 53, 48, 87, 112, 49, 111, 47, 0, 9, 3, 95, 50, 88, 82, 112, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 52, 88, 49, 35, 34, 111, 50, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 56, 49, 49, 35, 47, 34, 36, 82, 112, 47, 112, 0, 0, 11, 3, 95, 53, 88, 87, 112, 49, 111, 50, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 57, 49, 49, 35, 47, 34, 36, 82, 112, 47, 114, 86, 0, 0, 12, 3, 95, 54, 88, 87, 58, 35, 87, 111, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 88, 49, 35, 47, 34, 36, 82, 112, 0, 0, 0, 0, 0, 6, 195, 56, 245, 64, 72, 0, 0, 0, 5, 194, 44, 144, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 48, 144, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 48, 77, 52, 69, 37, 55, 57, 39, 50, 0, 0, 0, 13, 4, 95, 48, 77, 50, 63, 37, 55, 57, 39, 50, 0, 0, 12, 4, 95, 48, 77, 51, 63, 37, 55, 57, 35, 0, 0, 0, 10, 4, 95, 48, 77, 49, 63, 37, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 61, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 16, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 80, 16, 72, 0, 0, 0, 0, 6, 195, 80, 20, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 60, 224, 72, 0, 0, 0, 0, 11, 2, 195, 168, 36, 79, 34, 6, 35, 82, 0, 0, 0, 0, 0, 0, 0, 11, 2, 195, 178, 39, 79, 34, 6, 35, 82, 0, 0, 0, 0, 0, 0, 0, 5, 194, 80, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 1, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 95, 14, 36, 50, 0, 0, 7, 2, 95, 13, 36, 63, 0, 0, 7, 2, 95, 12, 36, 55, 0, 0, 0, 0, 0, 0, 11, 2, 95, 23, 70, 40, 69, 82, 6, 35, 0, 0, 0, 0, 7, 2, 95, 20, 47, 35, 0, 0, 0, 0, 13, 2, 95, 25, 37, 48, 87, 37, 55, 6, 39, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 88, 147, 128, 72, 0, 0, 0, 0, 6, 195, 56, 19, 128, 72, 0, 0, 0, 0, 0, 8, 2, 95, 46, 48, 58, 112, 0, 0, 0, 10, 2, 95, 44, 82, 37, 79, 37, 55, 0, 0, 8, 2, 95, 51, 47, 58, 35, 0, 0, 7, 2, 95, 50, 70, 36, 0, 0, 6, 2, 95, 49, 112, 0, 0, 9, 2, 95, 48, 86, 36, 58, 39, 0, 0, 8, 2, 95, 55, 87, 110, 47, 0, 0, 8, 2, 95, 54, 87, 37, 87, 0, 0, 8, 2, 95, 53, 87, 112, 49, 0, 0, 8, 2, 95, 52, 49, 35, 47, 0, 0, 13, 2, 95, 59, 48, 58, 112, 82, 37, 79, 37, 55, 0, 0, 0, 8, 2, 95, 57, 50, 110, 81, 0, 0, 8, 2, 95, 56, 109, 37, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 11, 195, 168, 11, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 64, 245, 64, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 160, 0, 3, 35, 0, 7, 6, 195, 168, 0, 3, 110, 0, 7, 6, 195, 178, 0, 3, 125, 0, 7, 6, 97, 0, 3, 35, 0, 110, 2, 25, 3, 111, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 49, 0, 2, 17, 71, 3, 87, 0, 104, 3, 89, 0, 7, 6, 100, 0, 3, 70, 0, 7, 6, 101, 0, 3, 36, 0, 110, 2, 25, 3, 112, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 3, 79, 0, 7, 6, 104, 0, 3, 0, 7, 6, 105, 0, 3, 37, 0, 7, 6, 106, 0, 3, 88, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 103, 3, 66, 0, 7, 6, 111, 0, 3, 39, 0, 117, 3, 40, 0, 110, 2, 25, 3, 114, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 7, 6, 114, 0, 3, 34, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 99, 104, 3, 74, 0, 7, 6, 117, 0, 3, 40, 0, 105, 3, 109, 37, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 1, 25, 2, 25, 3, 37, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 36, 3, 70, 39, 55, 35, 0, 195, 167, 3, 87, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts23 = FileInMemory_createWithData (2416, reinterpret_cast (&espeakdata_dicts23_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ht_dict", L"ht"); Collection_addItem (me.peek(), espeakdata_dicts23.transfer()); static unsigned char espeakdata_dicts24_data[110542] = { 0, 4, 0, 0, 40, 78, 1, 0, 13, 138, 11, 15, 18, 8, 1, 20, 195, 161, 18, 1, 13, 0, 9, 198, 80, 84, 150, 20, 177, 84, 13, 12, 137, 11, 9, 12, 195, 161, 20, 195, 161, 19, 13, 7, 132, 19, 195, 161, 22, 13, 0, 50, 12, 14, 5, 8, 195, 169, 26, 19, 195, 169, 7, 2, 5, 50, 107, 105, 111, 89, 12, 111, 79, 69, 107, 10, 6, 15, 109, 47, 49, 108, 86, 108, 47, 12, 0, 13, 81, 195, 188, 116, 107, 195, 182, 122, 195, 182, 116, 116, 32, 10, 135, 13, 1, 16, 16, 195, 161, 20, 13, 15, 140, 21, 20, 1, 19, 195, 173, 20, 195, 161, 19, 2, 1, 13, 0, 7, 196, 5, 166, 129, 48, 13, 7, 196, 21, 166, 133, 48, 13, 16, 141, 19, 26, 195, 161, 13, 12, 195, 161, 10, 195, 161, 18, 1, 13, 10, 135, 16, 195, 161, 18, 195, 161, 19, 13, 11, 136, 12, 195, 161, 14, 25, 195, 161, 20, 13, 11, 136, 4, 18, 195, 161, 22, 195, 161, 20, 13, 15, 140, 2, 197, 177, 14, 5, 19, 5, 20, 18, 197, 145, 12, 13, 19, 144, 11, 195, 182, 26, 12, 5, 11, 5, 4, 195, 169, 19, 2, 197, 145, 12, 13, 7, 196, 20, 118, 69, 80, 13, 12, 137, 18, 195, 161, 10, 195, 182, 14, 14, 9, 13, 11, 136, 19, 195, 186, 12, 25, 195, 161, 20, 13, 7, 196, 5, 166, 129, 48, 13, 8, 133, 195, 169, 18, 14, 9, 13, 0, 49, 14, 11, 1, 16, 3, 19, 15, 12, 195, 179, 4, 195, 161, 19, 9, 49, 106, 48, 74, 39, 55, 113, 70, 112, 89, 37, 23, 48, 52, 39, 69, 55, 111, 63, 106, 0, 13, 81, 112, 114, 111, 98, 108, 195, 169, 109, 97, 32, 7, 196, 21, 54, 137, 44, 13, 15, 140, 11, 15, 18, 12, 195, 161, 20, 15, 26, 195, 161, 19, 13, 12, 137, 1, 18, 195, 161, 14, 25, 195, 161, 20, 13, 0, 7, 65, 4, 106, 12, 0, 14, 29, 65, 4, 106, 6, 15, 48, 106, 50, 106, 87, 39, 49, 106, 47, 0, 13, 81, 112, 97, 110, 97, 115, 122, 111, 107, 97, 116, 32, 26, 65, 4, 106, 6, 15, 70, 108, 50, 47, 111, 89, 47, 0, 13, 81, 100, 195, 182, 110, 116, 195, 169, 115, 116, 32, 25, 65, 4, 106, 6, 15, 63, 106, 77, 106, 52, 39, 49, 0, 13, 81, 109, 97, 103, 121, 97, 114, 111, 107, 32, 27, 65, 4, 106, 6, 15, 105, 107, 57, 86, 107, 47, 107, 47, 0, 13, 81, 104, 101, 108, 121, 122, 101, 116, 101, 116, 32, 21, 65, 4, 106, 6, 15, 49, 106, 57, 112, 47, 0, 13, 81, 107, 97, 106, 195, 161, 116, 32, 16, 65, 4, 106, 6, 15, 69, 106, 57, 0, 13, 81, 98, 97, 106, 32, 30, 65, 4, 106, 6, 15, 47, 109, 50, 47, 107, 47, 111, 89, 47, 0, 13, 81, 116, 195, 188, 110, 116, 101, 116, 195, 169, 115, 116, 32, 30, 65, 4, 106, 6, 15, 49, 107, 70, 111, 57, 107, 49, 107, 47, 0, 13, 81, 107, 101, 100, 195, 169, 108, 121, 101, 107, 101, 116, 32, 22, 65, 4, 106, 6, 15, 87, 39, 49, 112, 89, 0, 13, 81, 115, 122, 111, 107, 195, 161, 115, 32, 25, 65, 4, 106, 6, 15, 82, 37, 55, 112, 79, 39, 50, 0, 13, 81, 118, 105, 108, 195, 161, 103, 111, 110, 32, 29, 65, 4, 106, 6, 15, 49, 40, 47, 106, 47, 113, 49, 106, 47, 0, 13, 81, 107, 117, 116, 97, 116, 195, 179, 107, 97, 116, 32, 28, 65, 4, 106, 6, 15, 69, 37, 86, 39, 74, 12, 112, 79, 0, 13, 81, 98, 105, 122, 111, 116, 116, 115, 195, 161, 103, 32, 26, 65, 4, 106, 6, 15, 81, 107, 55, 106, 70, 106, 47, 106, 0, 13, 81, 102, 101, 108, 97, 100, 97, 116, 97, 32, 35, 65, 4, 106, 6, 15, 63, 113, 70, 39, 89, 110, 47, 112, 89, 39, 49, 0, 13, 81, 109, 195, 179, 100, 111, 115, 195, 173, 116, 195, 161, 115, 111, 107, 32, 25, 65, 4, 106, 6, 15, 81, 107, 55, 109, 55, 107, 47, 0, 13, 81, 102, 101, 108, 195, 188, 108, 101, 116, 32, 28, 65, 4, 106, 6, 15, 47, 106, 69, 55, 107, 47, 105, 107, 86, 0, 13, 81, 116, 97, 98, 108, 101, 116, 104, 101, 122, 32, 23, 65, 4, 106, 6, 15, 87, 37, 50, 47, 107, 47, 0, 13, 81, 115, 122, 105, 110, 116, 101, 116, 32, 28, 65, 4, 106, 6, 15, 49, 111, 87, 109, 55, 111, 49, 0, 13, 81, 107, 195, 169, 115, 122, 195, 188, 108, 195, 169, 107, 32, 22, 65, 4, 106, 6, 15, 63, 39, 69, 37, 55, 47, 0, 13, 81, 109, 111, 98, 105, 108, 116, 32, 24, 65, 4, 106, 6, 15, 47, 107, 55, 107, 81, 39, 50, 0, 13, 81, 116, 101, 108, 101, 102, 111, 110, 32, 24, 65, 4, 106, 6, 15, 49, 111, 86, 69, 116, 55, 0, 13, 81, 107, 195, 169, 122, 98, 197, 145, 108, 32, 17, 65, 4, 106, 6, 15, 89, 112, 52, 0, 13, 81, 115, 195, 161, 114, 32, 22, 65, 4, 106, 6, 15, 105, 39, 50, 55, 106, 48, 0, 13, 81, 104, 111, 110, 108, 97, 112, 32, 40, 65, 4, 106, 6, 15, 48, 52, 107, 86, 107, 50, 47, 112, 55, 112, 89, 50, 106, 49, 0, 13, 81, 112, 114, 101, 122, 101, 110, 116, 195, 161, 108, 195, 161, 115, 110, 97, 107, 32, 24, 65, 4, 106, 6, 15, 81, 107, 55, 106, 70, 106, 47, 0, 13, 81, 102, 101, 108, 97, 100, 97, 116, 32, 27, 65, 4, 106, 6, 15, 87, 107, 34, 82, 107, 86, 107, 47, 0, 13, 81, 115, 122, 101, 114, 118, 101, 122, 101, 116, 32, 26, 65, 4, 106, 6, 15, 105, 106, 47, 113, 89, 112, 79, 0, 13, 81, 104, 97, 116, 195, 179, 115, 195, 161, 103, 32, 26, 65, 4, 106, 6, 15, 49, 108, 55, 47, 116, 52, 107, 0, 13, 81, 107, 195, 182, 108, 116, 197, 145, 114, 101, 32, 22, 65, 4, 106, 6, 15, 47, 37, 47, 49, 39, 47, 0, 13, 81, 116, 105, 116, 107, 111, 116, 32, 24, 65, 4, 106, 6, 15, 82, 112, 55, 106, 87, 47, 0, 13, 81, 118, 195, 161, 108, 97, 115, 122, 116, 32, 24, 65, 4, 106, 6, 15, 79, 111, 48, 111, 52, 107, 0, 13, 81, 103, 195, 169, 112, 195, 169, 114, 101, 32, 39, 65, 4, 106, 6, 15, 55, 107, 79, 81, 39, 50, 47, 39, 89, 106, 69, 50, 106, 49, 0, 13, 81, 108, 101, 103, 102, 111, 110, 116, 111, 115, 97, 98, 98, 110, 97, 107, 32, 41, 65, 4, 106, 6, 15, 49, 37, 57, 107, 55, 107, 50, 47, 111, 89, 107, 70, 12, 107, 55, 0, 13, 81, 107, 105, 106, 101, 108, 101, 110, 116, 195, 169, 115, 101, 100, 100, 101, 108, 32, 32, 65, 4, 106, 6, 15, 49, 111, 48, 82, 37, 89, 107, 55, 116, 49, 0, 13, 81, 107, 195, 169, 112, 118, 105, 115, 101, 108, 197, 145, 107, 32, 31, 65, 4, 106, 6, 15, 49, 107, 52, 109, 55, 107, 47, 69, 107, 50, 0, 13, 81, 107, 101, 114, 195, 188, 108, 101, 116, 98, 101, 110, 32, 28, 65, 4, 106, 6, 15, 52, 107, 50, 117, 107, 52, 69, 107, 0, 13, 81, 114, 101, 110, 100, 115, 122, 101, 114, 98, 101, 32, 29, 65, 4, 106, 6, 15, 52, 107, 50, 117, 107, 52, 111, 47, 0, 13, 81, 114, 101, 110, 100, 115, 122, 101, 114, 195, 169, 116, 32, 26, 65, 4, 106, 6, 15, 70, 39, 55, 79, 39, 49, 106, 47, 0, 13, 81, 100, 111, 108, 103, 111, 107, 97, 116, 32, 42, 65, 4, 106, 6, 15, 105, 39, 86, 86, 112, 87, 113, 55, 112, 89, 39, 49, 106, 47, 0, 13, 81, 104, 111, 122, 122, 195, 161, 115, 122, 195, 179, 108, 195, 161, 115, 111, 107, 97, 116, 32, 23, 65, 4, 106, 6, 15, 50, 111, 48, 50, 107, 49, 0, 13, 81, 110, 195, 169, 112, 110, 101, 107, 32, 28, 65, 4, 106, 6, 15, 81, 107, 55, 112, 55, 12, 112, 89, 0, 13, 81, 102, 101, 108, 195, 161, 108, 108, 195, 161, 115, 32, 31, 65, 4, 106, 6, 15, 82, 111, 55, 107, 63, 111, 65, 107, 63, 0, 13, 81, 118, 195, 169, 108, 101, 109, 195, 169, 110, 121, 101, 109, 32, 27, 65, 4, 106, 6, 15, 48, 52, 39, 69, 55, 111, 63, 106, 0, 13, 81, 112, 114, 111, 98, 108, 195, 169, 109, 97, 32, 36, 65, 4, 106, 6, 15, 81, 107, 57, 55, 107, 87, 47, 116, 49, 50, 107, 49, 0, 13, 81, 102, 101, 106, 108, 101, 115, 122, 116, 197, 145, 107, 110, 101, 107, 32, 23, 65, 4, 106, 6, 15, 117, 111, 55, 23, 106, 86, 0, 13, 82, 99, 195, 169, 108, 32, 97, 122, 32, 18, 65, 4, 106, 6, 15, 105, 37, 69, 106, 0, 13, 81, 104, 105, 98, 97, 32, 28, 65, 4, 106, 6, 15, 47, 106, 52, 47, 106, 55, 63, 106, 47, 0, 13, 81, 116, 97, 114, 116, 97, 108, 109, 97, 116, 32, 17, 65, 4, 106, 6, 15, 117, 110, 63, 0, 13, 81, 99, 195, 173, 109, 32, 22, 65, 4, 106, 6, 15, 70, 39, 55, 79, 39, 47, 0, 13, 81, 100, 111, 108, 103, 111, 116, 32, 25, 65, 4, 106, 6, 15, 105, 113, 50, 106, 48, 39, 49, 0, 13, 81, 104, 195, 179, 110, 97, 112, 111, 107, 32, 19, 65, 4, 106, 6, 15, 81, 108, 55, 70, 0, 13, 81, 102, 195, 182, 108, 100, 32, 30, 65, 4, 106, 6, 15, 49, 111, 52, 70, 111, 89, 23, 106, 86, 0, 13, 82, 107, 195, 169, 114, 100, 195, 169, 115, 32, 97, 122, 32, 32, 65, 4, 106, 6, 15, 74, 106, 55, 112, 70, 39, 49, 50, 106, 49, 0, 13, 81, 99, 115, 97, 108, 195, 161, 100, 111, 107, 110, 97, 107, 32, 24, 65, 4, 106, 6, 15, 47, 52, 107, 50, 70, 107, 47, 0, 13, 81, 116, 114, 101, 110, 100, 101, 116, 32, 26, 65, 4, 106, 6, 15, 47, 40, 70, 106, 47, 69, 106, 50, 0, 13, 81, 116, 117, 100, 97, 116, 98, 97, 110, 32, 33, 65, 4, 106, 6, 15, 63, 107, 79, 39, 55, 70, 112, 89, 12, 106, 55, 0, 13, 81, 109, 101, 103, 111, 108, 100, 195, 161, 115, 115, 97, 108, 32, 30, 65, 4, 106, 6, 15, 87, 106, 49, 106, 70, 111, 49, 39, 47, 0, 13, 81, 115, 122, 97, 107, 97, 100, 195, 169, 107, 111, 116, 32, 28, 65, 4, 106, 6, 15, 105, 107, 57, 86, 107, 47, 111, 47, 0, 13, 81, 104, 101, 108, 121, 122, 101, 116, 195, 169, 116, 32, 30, 65, 4, 106, 6, 15, 82, 112, 55, 106, 87, 39, 49, 106, 47, 0, 13, 81, 118, 195, 161, 108, 97, 115, 122, 111, 107, 97, 116, 32, 27, 65, 4, 106, 6, 15, 70, 39, 105, 112, 65, 86, 113, 0, 13, 81, 100, 111, 104, 195, 161, 110, 121, 122, 195, 179, 32, 36, 65, 4, 106, 6, 15, 70, 39, 105, 112, 65, 86, 112, 89, 34, 113, 55, 0, 13, 81, 100, 111, 104, 195, 161, 110, 121, 122, 195, 161, 115, 114, 195, 179, 108, 32, 31, 65, 4, 106, 6, 15, 70, 39, 105, 112, 65, 86, 112, 89, 47, 0, 13, 81, 100, 111, 104, 195, 161, 110, 121, 122, 195, 161, 115, 116, 32, 21, 65, 4, 106, 6, 15, 81, 111, 52, 81, 37, 0, 13, 81, 102, 195, 169, 114, 102, 105, 32, 26, 65, 4, 106, 6, 15, 57, 108, 82, 116, 69, 107, 50, 0, 13, 81, 106, 195, 182, 118, 197, 145, 98, 101, 110, 32, 28, 65, 4, 106, 6, 15, 69, 109, 50, 47, 107, 47, 111, 89, 0, 13, 81, 98, 195, 188, 110, 116, 101, 116, 195, 169, 115, 32, 22, 65, 4, 106, 6, 15, 89, 39, 52, 69, 106, 50, 0, 13, 81, 115, 111, 114, 98, 97, 110, 32, 21, 65, 4, 106, 6, 15, 47, 108, 63, 107, 79, 0, 13, 81, 116, 195, 182, 109, 101, 103, 32, 20, 65, 4, 106, 6, 15, 89, 39, 52, 69, 106, 0, 13, 81, 115, 111, 114, 98, 97, 32, 22, 65, 4, 106, 10, 6, 15, 105, 107, 57, 107, 47, 0, 13, 81, 104, 101, 108, 121, 101, 116, 32, 28, 65, 4, 106, 6, 15, 49, 111, 52, 70, 111, 89, 107, 63, 0, 13, 81, 107, 195, 169, 114, 100, 195, 169, 115, 101, 109, 32, 23, 65, 4, 106, 6, 15, 63, 111, 52, 79, 107, 47, 0, 13, 81, 109, 195, 169, 114, 103, 101, 116, 32, 24, 65, 4, 106, 6, 15, 49, 111, 52, 70, 111, 89, 0, 13, 81, 107, 195, 169, 114, 100, 195, 169, 115, 32, 26, 65, 4, 106, 6, 15, 82, 106, 55, 113, 89, 112, 79, 0, 13, 81, 118, 97, 108, 195, 179, 115, 195, 161, 103, 32, 29, 65, 4, 106, 6, 15, 49, 108, 55, 74, 111, 79, 107, 47, 0, 13, 81, 107, 195, 182, 108, 116, 115, 195, 169, 103, 101, 116, 32, 26, 65, 4, 106, 6, 15, 87, 107, 52, 82, 107, 86, 116, 0, 13, 81, 115, 122, 101, 114, 118, 101, 122, 197, 145, 32, 29, 65, 4, 106, 6, 15, 105, 39, 50, 55, 106, 48, 57, 112, 50, 0, 13, 81, 104, 111, 110, 108, 97, 112, 106, 195, 161, 110, 32, 33, 65, 4, 106, 6, 15, 81, 107, 55, 47, 111, 47, 107, 55, 12, 107, 55, 0, 13, 81, 102, 101, 108, 116, 195, 169, 116, 101, 108, 108, 101, 108, 32, 31, 65, 4, 106, 6, 15, 49, 37, 47, 111, 47, 107, 55, 12, 107, 55, 0, 13, 81, 107, 105, 116, 195, 169, 116, 101, 108, 108, 101, 108, 32, 28, 65, 4, 106, 6, 15, 70, 108, 50, 47, 111, 89, 52, 107, 0, 13, 81, 100, 195, 182, 110, 116, 195, 169, 115, 114, 101, 32, 29, 65, 4, 106, 6, 15, 87, 108, 82, 107, 74, 12, 111, 79, 0, 13, 81, 115, 122, 195, 182, 118, 101, 116, 115, 195, 169, 103, 32, 30, 65, 4, 106, 6, 15, 87, 108, 82, 107, 74, 12, 111, 79, 0, 13, 81, 115, 122, 195, 182, 118, 101, 116, 116, 115, 195, 169, 103, 32, 21, 65, 4, 106, 6, 15, 117, 111, 61, 57, 106, 0, 13, 81, 99, 195, 169, 108, 106, 97, 32, 43, 65, 4, 106, 6, 15, 63, 107, 79, 87, 39, 52, 110, 47, 112, 89, 39, 49, 69, 106, 50, 0, 13, 81, 109, 101, 103, 115, 122, 111, 114, 195, 173, 116, 195, 161, 115, 111, 107, 98, 97, 110, 32, 23, 65, 4, 106, 6, 15, 65, 40, 79, 106, 47, 37, 0, 13, 81, 110, 121, 117, 103, 97, 116, 105, 32, 47, 65, 4, 106, 6, 15, 49, 108, 86, 108, 50, 89, 111, 79, 23, 89, 39, 52, 106, 37, 69, 106, 50, 0, 13, 82, 107, 195, 182, 122, 195, 182, 110, 115, 195, 169, 103, 32, 115, 111, 114, 97, 105, 98, 97, 110, 32, 23, 65, 4, 106, 6, 15, 105, 107, 57, 86, 107, 47, 0, 13, 81, 104, 101, 108, 121, 122, 101, 116, 32, 23, 65, 4, 106, 6, 15, 63, 111, 52, 55, 107, 79, 0, 13, 81, 109, 195, 169, 114, 108, 101, 103, 32, 26, 65, 4, 106, 6, 15, 47, 107, 52, 82, 107, 86, 107, 47, 0, 13, 81, 116, 101, 114, 118, 101, 122, 101, 116, 32, 28, 65, 4, 106, 6, 15, 105, 106, 55, 79, 106, 47, 113, 49, 0, 13, 81, 104, 97, 108, 108, 103, 97, 116, 195, 179, 107, 32, 49, 65, 4, 106, 6, 15, 49, 39, 52, 112, 69, 12, 37, 23, 107, 55, 49, 111, 48, 86, 107, 55, 111, 89, 0, 13, 82, 107, 111, 114, 195, 161, 98, 98, 105, 32, 101, 108, 107, 195, 169, 112, 122, 101, 108, 195, 169, 115, 32, 30, 65, 4, 106, 6, 15, 105, 112, 47, 12, 111, 52, 69, 107, 50, 0, 13, 81, 104, 195, 161, 116, 116, 195, 169, 114, 98, 101, 110, 32, 36, 65, 4, 106, 6, 15, 49, 108, 55, 74, 111, 79, 107, 49, 52, 116, 55, 0, 13, 81, 107, 195, 182, 108, 116, 115, 195, 169, 103, 101, 107, 114, 197, 145, 108, 32, 32, 65, 4, 106, 6, 23, 105, 106, 55, 79, 106, 47, 113, 50, 106, 49, 0, 13, 81, 104, 97, 108, 108, 103, 97, 116, 195, 179, 110, 97, 107, 32, 28, 65, 4, 106, 6, 15, 82, 112, 55, 47, 39, 86, 112, 89, 0, 13, 81, 118, 195, 161, 108, 116, 111, 122, 195, 161, 115, 32, 28, 65, 4, 106, 6, 15, 49, 111, 52, 70, 111, 89, 52, 107, 0, 13, 81, 107, 195, 169, 114, 100, 195, 169, 115, 114, 101, 32, 37, 65, 4, 106, 6, 15, 77, 113, 77, 87, 107, 52, 107, 49, 111, 52, 47, 0, 13, 81, 103, 121, 195, 179, 103, 121, 115, 122, 101, 114, 101, 107, 195, 169, 114, 116, 32, 24, 65, 4, 106, 6, 15, 69, 107, 47, 107, 79, 107, 49, 0, 13, 81, 98, 101, 116, 101, 103, 101, 107, 32, 78, 65, 4, 106, 6, 15, 69, 107, 47, 107, 79, 107, 49, 50, 107, 49, 23, 106, 6, 15, 77, 113, 77, 87, 107, 52, 47, 112, 63, 39, 79, 106, 47, 112, 89, 112, 47, 0, 13, 83, 98, 101, 116, 101, 103, 101, 107, 110, 101, 107, 32, 97, 32, 103, 121, 195, 179, 103, 121, 115, 122, 101, 114, 116, 195, 161, 109, 111, 103, 97, 116, 195, 161, 115, 195, 161, 116, 32, 20, 65, 4, 106, 6, 15, 47, 111, 65, 47, 0, 13, 81, 116, 195, 169, 110, 121, 116, 32, 26, 65, 4, 106, 6, 15, 70, 110, 57, 106, 86, 112, 89, 0, 13, 81, 100, 195, 173, 106, 97, 122, 195, 161, 115, 32, 26, 65, 4, 106, 6, 15, 65, 39, 63, 39, 86, 113, 49, 0, 13, 81, 110, 121, 111, 109, 111, 122, 195, 179, 107, 32, 35, 65, 4, 106, 6, 15, 81, 107, 55, 107, 55, 116, 89, 111, 79, 107, 47, 0, 13, 81, 102, 101, 108, 101, 108, 197, 145, 115, 115, 195, 169, 103, 101, 116, 32, 21, 65, 4, 106, 6, 15, 47, 109, 86, 107, 47, 0, 13, 81, 116, 195, 188, 122, 101, 116, 32, 26, 65, 4, 106, 6, 15, 47, 111, 63, 112, 69, 106, 50, 0, 13, 81, 116, 195, 169, 109, 195, 161, 98, 97, 110, 32, 25, 65, 4, 106, 6, 15, 81, 107, 55, 107, 55, 116, 89, 0, 13, 81, 102, 101, 108, 101, 108, 197, 145, 115, 32, 34, 65, 4, 106, 6, 15, 49, 111, 52, 70, 111, 89, 107, 49, 69, 107, 50, 0, 13, 81, 107, 195, 169, 114, 100, 195, 169, 115, 101, 107, 98, 101, 110, 32, 26, 65, 4, 106, 6, 15, 70, 39, 55, 79, 39, 70, 106, 47, 0, 13, 81, 100, 111, 108, 103, 111, 100, 97, 116, 32, 30, 65, 4, 106, 6, 23, 105, 106, 77, 39, 63, 106, 12, 65, 47, 0, 13, 81, 104, 97, 103, 121, 111, 109, 195, 161, 110, 121, 116, 32, 16, 65, 4, 106, 6, 15, 89, 39, 49, 0, 13, 81, 115, 111, 107, 32, 34, 65, 4, 106, 6, 15, 49, 111, 48, 107, 89, 12, 111, 79, 107, 37, 47, 0, 13, 81, 107, 195, 169, 112, 101, 115, 115, 195, 169, 103, 101, 105, 116, 32, 35, 65, 4, 106, 6, 15, 81, 107, 55, 105, 106, 87, 50, 112, 55, 113, 47, 0, 13, 81, 102, 101, 108, 104, 97, 115, 122, 110, 195, 161, 108, 195, 179, 116, 32, 18, 65, 4, 106, 6, 15, 117, 37, 49, 12, 0, 13, 81, 99, 105, 107, 107, 32, 33, 65, 4, 106, 6, 15, 81, 112, 57, 55, 57, 106, 37, 50, 49, 106, 47, 0, 13, 81, 102, 195, 161, 106, 108, 106, 97, 105, 110, 107, 97, 116, 32, 41, 65, 4, 106, 6, 15, 81, 107, 55, 105, 106, 87, 50, 112, 55, 113, 49, 50, 106, 49, 0, 13, 81, 102, 101, 108, 104, 97, 115, 122, 110, 195, 161, 108, 195, 179, 107, 110, 97, 107, 32, 36, 65, 4, 106, 6, 23, 89, 109, 57, 57, 107, 87, 47, 116, 69, 107, 50, 0, 13, 81, 115, 195, 188, 108, 108, 121, 101, 115, 122, 116, 197, 145, 98, 101, 110, 32, 28, 65, 4, 106, 6, 23, 81, 107, 57, 55, 116, 70, 111, 89, 0, 13, 81, 102, 101, 106, 108, 197, 145, 100, 195, 169, 115, 32, 26, 65, 4, 106, 6, 23, 52, 107, 50, 117, 107, 52, 47, 0, 13, 81, 114, 101, 110, 100, 115, 122, 101, 114, 116, 32, 30, 65, 4, 106, 6, 15, 55, 111, 79, 63, 39, 86, 79, 112, 89, 0, 13, 81, 108, 195, 169, 103, 109, 111, 122, 103, 195, 161, 115, 32, 23, 65, 4, 106, 6, 9, 15, 49, 107, 55, 107, 47, 37, 0, 13, 81, 107, 101, 108, 101, 116, 105, 32, 20, 65, 4, 106, 6, 9, 15, 70, 111, 55, 37, 0, 13, 81, 100, 195, 169, 108, 105, 32, 27, 65, 4, 106, 6, 15, 70, 39, 49, 47, 39, 52, 50, 116, 0, 13, 81, 100, 111, 107, 116, 111, 114, 110, 197, 145, 32, 29, 65, 4, 106, 6, 23, 87, 49, 52, 37, 48, 47, 69, 107, 50, 0, 13, 81, 115, 122, 107, 114, 105, 112, 116, 98, 101, 110, 32, 40, 65, 4, 106, 6, 23, 81, 107, 55, 106, 70, 106, 47, 39, 47, 23, 49, 106, 48, 57, 106, 0, 13, 82, 102, 101, 108, 97, 100, 97, 116, 111, 116, 32, 107, 97, 112, 106, 97, 32, 30, 65, 4, 106, 6, 23, 49, 108, 82, 107, 47, 49, 107, 86, 116, 0, 13, 81, 107, 195, 182, 118, 101, 116, 107, 101, 122, 197, 145, 32, 28, 65, 4, 106, 6, 23, 82, 112, 55, 47, 112, 89, 39, 50, 0, 13, 81, 118, 195, 161, 108, 116, 195, 161, 115, 111, 110, 32, 21, 65, 4, 106, 6, 15, 81, 107, 55, 105, 116, 0, 13, 81, 102, 101, 108, 104, 197, 145, 32, 24, 65, 4, 106, 6, 23, 52, 107, 50, 117, 107, 52, 0, 13, 81, 114, 101, 110, 100, 115, 122, 101, 114, 32, 34, 65, 4, 106, 6, 15, 49, 37, 47, 108, 55, 47, 111, 89, 49, 39, 52, 0, 13, 81, 107, 105, 116, 195, 182, 108, 116, 195, 169, 115, 107, 111, 114, 32, 38, 65, 4, 106, 6, 15, 81, 107, 57, 55, 107, 87, 47, 111, 89, 107, 49, 107, 47, 0, 13, 81, 102, 101, 106, 108, 101, 115, 122, 116, 195, 169, 115, 101, 107, 101, 116, 32, 32, 65, 4, 106, 6, 15, 49, 37, 47, 108, 55, 47, 116, 82, 107, 55, 0, 13, 81, 107, 105, 116, 195, 182, 108, 116, 197, 145, 118, 101, 108, 32, 32, 65, 4, 106, 6, 15, 49, 111, 52, 70, 111, 89, 107, 49, 52, 107, 0, 13, 81, 107, 195, 169, 114, 100, 195, 169, 115, 101, 107, 114, 101, 32, 31, 65, 4, 106, 6, 15, 49, 111, 52, 70, 116, 110, 82, 107, 47, 0, 13, 81, 107, 195, 169, 114, 100, 197, 145, 195, 173, 118, 101, 116, 32, 20, 65, 4, 106, 6, 15, 50, 106, 48, 39, 47, 0, 13, 81, 110, 97, 112, 111, 116, 32, 21, 65, 4, 106, 6, 15, 48, 111, 50, 87, 47, 0, 13, 81, 112, 195, 169, 110, 122, 116, 32, 31, 65, 4, 106, 6, 15, 49, 111, 52, 111, 89, 111, 82, 107, 55, 0, 13, 81, 107, 195, 169, 114, 195, 169, 115, 195, 169, 118, 101, 108, 32, 38, 65, 4, 106, 6, 15, 63, 37, 50, 37, 87, 47, 107, 52, 107, 55, 50, 108, 49, 0, 13, 81, 109, 105, 110, 105, 115, 122, 116, 101, 114, 101, 108, 110, 195, 182, 107, 32, 34, 65, 4, 106, 6, 105, 116, 63, 111, 52, 89, 111, 49, 55, 107, 47, 0, 13, 81, 104, 197, 145, 109, 195, 169, 114, 115, 195, 169, 107, 108, 101, 116, 32, 23, 65, 4, 106, 6, 15, 55, 107, 82, 107, 79, 116, 0, 13, 81, 108, 101, 118, 101, 103, 197, 145, 32, 27, 65, 4, 106, 6, 15, 81, 107, 55, 105, 116, 86, 107, 47, 0, 13, 81, 102, 101, 108, 104, 197, 145, 122, 101, 116, 32, 35, 65, 4, 106, 6, 15, 49, 109, 55, 108, 50, 69, 89, 111, 79, 107, 47, 0, 13, 81, 107, 195, 188, 108, 195, 182, 110, 98, 115, 195, 169, 103, 101, 116, 32, 23, 65, 4, 106, 6, 15, 81, 107, 50, 111, 69, 107, 0, 13, 81, 102, 101, 110, 195, 169, 98, 101, 32, 20, 65, 4, 106, 6, 15, 70, 39, 55, 39, 79, 0, 13, 81, 100, 111, 108, 111, 103, 32, 21, 65, 4, 106, 6, 15, 105, 107, 57, 107, 70, 0, 13, 81, 104, 101, 108, 121, 101, 100, 32, 21, 65, 4, 106, 6, 15, 79, 111, 48, 107, 50, 0, 13, 81, 103, 195, 169, 112, 101, 110, 32, 30, 65, 4, 106, 6, 23, 48, 52, 39, 69, 55, 111, 63, 112, 63, 0, 13, 81, 112, 114, 111, 98, 108, 195, 169, 109, 195, 161, 109, 32, 17, 142, 20, 5, 12, 5, 16, 195, 173, 20, 195, 169, 19, 19, 5, 12, 13, 9, 198, 41, 85, 1, 48, 243, 64, 13, 9, 134, 16, 1, 3, 195, 161, 20, 13, 9, 198, 24, 84, 218, 20, 113, 84, 13, 9, 198, 60, 197, 129, 76, 243, 64, 13, 9, 134, 13, 1, 7, 195, 161, 20, 13, 5, 193, 4, 72, 12, 22, 65, 4, 106, 65, 65, 37, 15, 63, 6, 37, 50, 47, 0, 25, 83, 46, 32, 109, 32, 46, 32, 0, 9, 198, 77, 161, 77, 8, 83, 128, 13, 9, 198, 77, 161, 77, 8, 83, 128, 13, 0, 27, 67, 16, 240, 128, 70, 39, 69, 10, 6, 15, 48, 37, 106, 117, 52, 106, 0, 13, 81, 112, 105, 97, 99, 114, 97, 32, 11, 136, 11, 21, 12, 3, 19, 195, 161, 20, 13, 40, 11, 14, 195, 182, 22, 5, 12, 195, 169, 19, 5, 19, 50, 108, 82, 107, 55, 111, 89, 107, 89, 23, 47, 107, 87, 47, 107, 47, 0, 13, 81, 116, 101, 115, 122, 116, 101, 116, 32, 11, 200, 32, 17, 9, 24, 241, 207, 49, 144, 13, 10, 199, 80, 20, 148, 4, 195, 65, 44, 13, 6, 195, 64, 243, 148, 13, 0, 12, 137, 22, 9, 20, 195, 161, 10, 195, 161, 20, 13, 41, 12, 11, 15, 18, 18, 9, 7, 195, 161, 12, 195, 161, 19, 49, 39, 52, 52, 37, 79, 112, 55, 112, 89, 23, 52, 111, 82, 111, 50, 0, 13, 81, 114, 195, 169, 118, 195, 169, 110, 32, 12, 201, 80, 83, 5, 24, 243, 143, 44, 176, 76, 13, 13, 138, 22, 195, 161, 12, 15, 7, 1, 20, 14, 9, 13, 12, 201, 13, 51, 208, 61, 37, 15, 44, 176, 76, 13, 0, 6, 65, 8, 69, 111, 0, 14, 139, 4, 18, 195, 161, 7, 21, 12, 195, 161, 19, 1, 13, 22, 147, 13, 5, 7, 195, 161, 12, 12, 1, 16, 195, 173, 20, 195, 161, 19, 195, 161, 18, 1, 13, 13, 138, 2, 5, 14, 14, 195, 188, 14, 11, 5, 20, 13, 17, 142, 195, 169, 12, 5, 20, 20, 1, 18, 20, 1, 13, 195, 161, 20, 13, 13, 138, 13, 21, 14, 11, 195, 161, 10, 195, 161, 20, 13, 0, 23, 148, 22, 9, 19, 19, 26, 1, 195, 161, 12, 12, 195, 173, 20, 195, 161, 19, 195, 161, 18, 1, 13, 14, 139, 12, 5, 195, 173, 18, 195, 161, 19, 195, 161, 20, 13, 18, 143, 20, 5, 18, 8, 5, 19, 19, 195, 169, 7, 195, 188, 11, 5, 20, 13, 15, 140, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 1, 13, 9, 198, 33, 83, 12, 61, 69, 0, 13, 10, 135, 16, 195, 169, 14, 20, 5, 11, 20, 0, 15, 140, 11, 195, 169, 16, 22, 9, 19, 5, 12, 197, 145, 20, 13, 14, 139, 11, 9, 14, 195, 169, 26, 5, 20, 20, 5, 12, 13, 9, 134, 16, 195, 169, 12, 4, 1, 13, 9, 134, 11, 195, 182, 26, 20, 5, 13, 9, 134, 16, 195, 169, 12, 4, 1, 13, 15, 140, 10, 195, 161, 18, 1, 4, 195, 169, 11, 195, 161, 20, 13, 0, 11, 136, 13, 21, 14, 11, 195, 161, 19, 20, 13, 61, 13, 12, 5, 8, 5, 20, 197, 145, 19, 195, 169, 7, 5, 20, 55, 107, 105, 107, 47, 116, 89, 111, 79, 107, 47, 10, 6, 15, 63, 107, 79, 82, 106, 55, 113, 89, 110, 47, 106, 50, 37, 0, 13, 81, 109, 101, 103, 118, 97, 108, 195, 179, 115, 195, 173, 116, 97, 110, 105, 32, 19, 144, 14, 195, 169, 16, 19, 26, 195, 161, 13, 12, 195, 161, 12, 195, 161, 19, 13, 14, 139, 16, 18, 195, 179, 2, 195, 161, 12, 20, 1, 13, 13, 10, 135, 20, 195, 169, 20, 5, 12, 5, 13, 16, 141, 12, 5, 8, 5, 20, 197, 145, 19, 195, 169, 7, 5, 20, 13, 0, 6, 65, 12, 117, 111, 0, 9, 198, 24, 244, 132, 84, 195, 203, 13, 13, 138, 11, 195, 182, 22, 5, 20, 20, 195, 169, 11, 13, 10, 135, 13, 195, 169, 18, 20, 5, 14, 13, 11, 136, 19, 26, 195, 161, 14, 20, 1, 13, 13, 17, 142, 6, 5, 12, 5, 12, 197, 145, 19, 19, 195, 169, 7, 5, 20, 13, 8, 197, 44, 86, 132, 88, 80, 13, 0, 48, 73, 16, 242, 213, 52, 83, 148, 84, 212, 129, 70, 39, 49, 40, 63, 107, 50, 47, 40, 63, 52, 106, 23, 105, 37, 82, 106, 47, 49, 39, 86, 82, 106, 0, 13, 81, 104, 105, 118, 97, 116, 107, 111, 122, 118, 97, 32, 0, 9, 134, 195, 188, 26, 5, 13, 5, 13, 11, 4, 95, 8, 1, 3, 48, 37, 48, 106, 0, 0, 14, 139, 13, 1, 7, 25, 1, 18, 195, 161, 26, 20, 1, 13, 11, 136, 5, 12, 197, 145, 20, 20, 5, 4, 13, 11, 200, 77, 161, 82, 88, 86, 133, 80, 80, 13, 12, 137, 11, 5, 18, 5, 19, 20, 195, 169, 11, 13, 0, 6, 65, 16, 70, 111, 0, 15, 140, 1, 4, 15, 13, 195, 161, 14, 25, 15, 26, 20, 1, 13, 8, 197, 88, 148, 197, 49, 64, 13, 20, 145, 19, 26, 195, 161, 13, 195, 173, 20, 195, 179, 7, 195, 169, 16, 16, 5, 12, 13, 6, 195, 44, 147, 142, 13, 0, 27, 3, 58, 47, 47, 40, 107, 101, 116, 116, 197, 145, 115, 112, 111, 110, 116, 112, 101, 114, 112, 101, 114, 41, 0, 8, 29, 10, 135, 22, 195, 161, 18, 21, 14, 11, 13, 8, 133, 20, 195, 169, 13, 1, 13, 17, 142, 19, 26, 5, 18, 22, 5, 26, 5, 20, 11, 195, 169, 14, 20, 13, 9, 134, 20, 197, 145, 12, 5, 4, 13, 0, 13, 138, 2, 197, 145, 22, 195, 173, 20, 5, 14, 9, 13, 15, 140, 8, 15, 26, 26, 195, 161, 11, 5, 26, 4, 5, 11, 13, 9, 198, 40, 21, 129, 76, 195, 205, 13, 9, 198, 80, 20, 148, 4, 195, 205, 13, 0, 14, 139, 19, 26, 195, 161, 13, 195, 173, 20, 1, 14, 9, 13, 11, 200, 52, 81, 214, 21, 36, 197, 49, 64, 13, 10, 135, 14, 25, 195, 186, 12, 14, 9, 13, 10, 135, 195, 169, 18, 4, 5, 13, 5, 13, 11, 136, 19, 26, 195, 161, 14, 20, 1, 4, 13, 11, 136, 18, 5, 14, 4, 197, 145, 18, 20, 13, 0, 4, 193, 20, 72, 4, 193, 20, 14, 4, 193, 20, 72, 0, 8, 133, 195, 173, 18, 14, 9, 13, 9, 198, 56, 147, 131, 76, 83, 128, 13, 0, 10, 199, 48, 144, 197, 56, 49, 73, 80, 13, 10, 199, 32, 19, 12, 61, 69, 21, 44, 13, 15, 140, 12, 5, 6, 5, 4, 5, 20, 20, 19, 195, 169, 7, 13, 14, 4, 95, 48, 67, 15, 87, 112, 86, 106, 70, 37, 49, 0, 0, 0, 7, 65, 24, 107, 81, 81, 0, 8, 197, 20, 209, 76, 56, 144, 13, 11, 136, 22, 195, 161, 12, 1, 19, 26, 1, 13, 13, 138, 195, 161, 12, 12, 195, 173, 20, 21, 14, 11, 13, 0, 18, 143, 19, 26, 5, 13, 2, 5, 19, 195, 188, 12, 14, 9, 195, 188, 11, 13, 9, 198, 60, 179, 218, 61, 69, 0, 13, 0, 14, 139, 18, 195, 161, 2, 195, 182, 11, 195, 182, 20, 20, 13, 10, 135, 13, 1, 14, 21, 195, 161, 12, 13, 0, 45, 8, 195, 161, 12, 12, 1, 16, 15, 20, 112, 55, 12, 106, 48, 39, 47, 23, 57, 106, 82, 110, 47, 112, 89, 112, 52, 106, 0, 13, 81, 106, 97, 118, 195, 173, 116, 195, 161, 115, 195, 161, 114, 97, 32, 9, 134, 20, 195, 169, 12, 5, 14, 13, 11, 136, 195, 161, 12, 12, 1, 16, 15, 20, 13, 0, 6, 65, 28, 79, 111, 0, 16, 141, 20, 195, 182, 18, 22, 195, 169, 14, 25, 18, 197, 145, 12, 13, 46, 11, 9, 7, 195, 169, 14, 25, 5, 9, 8, 5, 26, 37, 79, 111, 65, 107, 37, 105, 107, 86, 23, 37, 79, 106, 86, 110, 47, 106, 50, 37, 0, 13, 81, 105, 103, 97, 122, 195, 173, 116, 97, 110, 105, 32, 20, 136, 5, 19, 26, 13, 195, 169, 10, 5, 13, 81, 104, 101, 118, 195, 173, 116, 105, 32, 10, 135, 14, 25, 15, 13, 195, 161, 14, 13, 0, 9, 198, 24, 147, 13, 20, 177, 84, 13, 11, 136, 6, 195, 161, 10, 12, 8, 15, 26, 13, 13, 138, 10, 21, 20, 20, 1, 20, 195, 161, 19, 20, 13, 0, 10, 199, 32, 21, 133, 72, 160, 73, 52, 13, 43, 6, 11, 195, 182, 26, 20, 9, 49, 108, 87, 47, 37, 23, 49, 109, 55, 108, 50, 69, 89, 111, 79, 107, 49, 0, 13, 81, 107, 195, 188, 108, 195, 182, 110, 98, 115, 195, 169, 103, 101, 107, 32, 28, 9, 7, 195, 169, 16, 5, 11, 8, 5, 26, 79, 111, 48, 107, 49, 105, 107, 86, 23, 37, 89, 0, 13, 81, 105, 115, 32, 53, 6, 11, 195, 182, 26, 20, 9, 49, 108, 87, 47, 37, 23, 50, 111, 86, 107, 47, 107, 55, 47, 111, 52, 111, 89, 107, 49, 107, 47, 0, 13, 81, 110, 195, 169, 122, 101, 116, 101, 108, 116, 195, 169, 114, 195, 169, 115, 101, 107, 101, 116, 32, 11, 136, 1, 11, 1, 18, 10, 195, 161, 11, 13, 10, 199, 16, 243, 7, 61, 166, 143, 56, 13, 10, 135, 14, 1, 16, 10, 195, 161, 20, 13, 17, 4, 95, 54, 48, 15, 105, 106, 47, 82, 106, 50, 106, 70, 37, 49, 0, 0, 38, 72, 44, 85, 133, 76, 80, 130, 20, 224, 49, 107, 82, 107, 89, 107, 69, 12, 107, 50, 10, 6, 15, 106, 50, 12, 112, 55, 0, 13, 81, 97, 110, 110, 195, 161, 108, 32, 17, 142, 11, 15, 14, 7, 18, 5, 19, 19, 26, 21, 19, 195, 161, 14, 13, 15, 140, 12, 195, 161, 20, 15, 7, 1, 20, 195, 161, 19, 20, 13, 0, 6, 65, 32, 105, 112, 0, 14, 67, 52, 196, 218, 107, 63, 107, 55, 107, 87, 0, 42, 42, 0, 47, 10, 195, 182, 19, 19, 26, 5, 7, 195, 169, 20, 108, 87, 12, 107, 79, 111, 47, 23, 81, 107, 55, 47, 109, 50, 47, 107, 89, 12, 107, 0, 13, 81, 102, 101, 108, 116, 195, 188, 110, 116, 101, 115, 115, 101, 32, 9, 134, 195, 169, 7, 5, 20, 20, 13, 8, 133, 20, 195, 169, 12, 9, 20, 0, 13, 138, 4, 195, 182, 14, 20, 195, 169, 19, 5, 9, 13, 10, 199, 44, 20, 8, 5, 67, 129, 44, 13, 15, 140, 20, 195, 161, 13, 15, 7, 1, 20, 10, 195, 161, 11, 13, 51, 71, 24, 145, 217, 20, 195, 69, 80, 81, 37, 77, 107, 55, 63, 107, 47, 23, 49, 107, 55, 12, 23, 81, 39, 52, 70, 110, 47, 106, 50, 37, 0, 13, 82, 107, 101, 108, 108, 32, 102, 111, 114, 100, 195, 173, 116, 97, 110, 105, 32, 10, 199, 24, 145, 217, 20, 195, 69, 80, 13, 15, 140, 2, 15, 19, 19, 26, 1, 14, 20, 195, 179, 1, 11, 13, 10, 199, 48, 18, 207, 76, 242, 193, 80, 13, 13, 138, 19, 26, 1, 11, 195, 173, 20, 1, 14, 9, 13, 10, 199, 24, 83, 22, 21, 66, 5, 80, 13, 10, 135, 14, 25, 15, 13, 195, 161, 20, 13, 0, 17, 1, 35, 49, 107, 47, 12, 116, 89, 49, 107, 52, 107, 87, 47, 0, 27, 16, 141, 9, 18, 195, 161, 14, 25, 195, 173, 20, 10, 195, 161, 11, 13, 15, 140, 14, 25, 195, 186, 10, 20, 195, 161, 19, 195, 161, 20, 13, 7, 132, 11, 195, 186, 20, 13, 7, 132, 3, 195, 169, 12, 13, 0, 45, 9, 22, 195, 161, 12, 12, 1, 12, 1, 20, 82, 112, 55, 12, 106, 55, 106, 47, 23, 49, 108, 86, 55, 107, 63, 111, 65, 107, 0, 13, 81, 107, 195, 182, 122, 108, 101, 109, 195, 169, 110, 121, 101, 32, 16, 141, 6, 15, 18, 13, 195, 161, 12, 195, 161, 19, 195, 161, 20, 13, 15, 140, 20, 5, 12, 10, 5, 19, 195, 173, 20, 5, 14, 9, 13, 15, 140, 20, 5, 12, 10, 5, 19, 195, 173, 20, 5, 14, 9, 13, 20, 145, 11, 195, 169, 19, 26, 195, 188, 12, 195, 169, 11, 195, 188, 14, 11, 5, 20, 13, 16, 141, 12, 5, 16, 1, 11, 15, 12, 195, 161, 19, 195, 161, 20, 13, 8, 197, 20, 210, 65, 81, 64, 13, 0, 24, 1, 37, 115, 122, 195, 161, 122, 97, 108, 195, 169, 107, 107, 97, 108, 0, 44, 29, 81, 107, 97, 108, 32, 12, 1, 37, 87, 112, 86, 106, 55, 111, 49, 0, 27, 13, 138, 11, 15, 18, 8, 1, 20, 195, 161, 18, 20, 13, 8, 197, 37, 0, 82, 8, 16, 13, 0, 7, 1, 38, 111, 89, 0, 27, 14, 139, 20, 5, 14, 4, 5, 14, 3, 9, 195, 161, 20, 13, 13, 138, 19, 195, 169, 18, 5, 12, 13, 5, 26, 9, 13, 9, 198, 40, 83, 5, 57, 68, 197, 13, 10, 199, 77, 163, 205, 8, 21, 9, 28, 22, 10, 199, 5, 81, 213, 77, 165, 21, 76, 20, 0, 12, 137, 6, 5, 12, 6, 15, 7, 195, 161, 19, 13, 19, 144, 18, 1, 20, 9, 6, 9, 11, 195, 161, 12, 195, 161, 19, 195, 161, 20, 13, 31, 68, 72, 18, 148, 4, 52, 106, 57, 47, 106, 23, 79, 111, 48, 107, 55, 50, 37, 0, 13, 81, 103, 195, 169, 112, 101, 108, 110, 105, 32, 57, 10, 11, 195, 169, 18, 4, 197, 145, 195, 173, 22, 49, 111, 52, 70, 116, 110, 82, 23, 82, 111, 55, 107, 63, 111, 65, 107, 86, 111, 89, 111, 52, 107, 0, 13, 81, 118, 195, 169, 108, 101, 109, 195, 169, 110, 121, 101, 122, 195, 169, 115, 195, 169, 114, 101, 32, 12, 137, 20, 1, 12, 195, 161, 12, 21, 14, 11, 13, 7, 196, 72, 18, 148, 4, 13, 0, 6, 65, 40, 57, 111, 0, 0, 11, 136, 6, 5, 2, 18, 21, 195, 161, 18, 20, 0, 11, 1, 42, 74, 37, 55, 55, 106, 79, 0, 27, 16, 141, 195, 161, 12, 12, 1, 13, 16, 15, 12, 7, 195, 161, 18, 13, 9, 198, 48, 84, 218, 60, 179, 137, 13, 13, 138, 3, 19, 9, 14, 195, 161, 12, 20, 1, 13, 13, 10, 199, 36, 225, 193, 80, 192, 78, 80, 13, 18, 143, 11, 195, 188, 12, 195, 182, 14, 2, 19, 195, 169, 7, 7, 5, 12, 13, 6, 195, 32, 246, 128, 13, 0, 9, 1, 43, 48, 55, 40, 87, 0, 27, 10, 135, 22, 195, 161, 18, 20, 1, 13, 13, 10, 135, 10, 195, 161, 18, 20, 1, 13, 13, 12, 137, 8, 9, 2, 195, 161, 26, 20, 1, 11, 13, 11, 136, 11, 195, 182, 26, 16, 15, 14, 20, 13, 0, 6, 65, 44, 49, 112, 0, 10, 135, 5, 19, 5, 20, 195, 169, 14, 13, 32, 8, 195, 169, 18, 5, 26, 20, 5, 13, 111, 52, 107, 87, 47, 107, 63, 23, 63, 106, 79, 106, 63, 0, 13, 81, 109, 97, 103, 97, 109, 32, 11, 136, 12, 5, 195, 173, 18, 20, 1, 13, 13, 15, 140, 13, 5, 12, 12, 195, 169, 11, 5, 12, 20, 5, 13, 13, 11, 136, 195, 169, 18, 5, 26, 20, 5, 13, 13, 8, 197, 48, 85, 20, 20, 176, 13, 10, 135, 5, 19, 5, 20, 195, 169, 14, 13, 8, 197, 44, 20, 14, 4, 176, 13, 0, 12, 137, 19, 195, 169, 18, 20, 5, 14, 195, 169, 13, 14, 139, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 19, 13, 10, 135, 22, 195, 161, 12, 20, 1, 11, 13, 15, 140, 11, 195, 182, 18, 14, 25, 195, 169, 11, 195, 169, 14, 13, 15, 140, 11, 195, 182, 18, 14, 25, 195, 169, 11, 195, 169, 14, 22, 0, 10, 1, 46, 48, 2, 39, 50, 47, 0, 27, 10, 199, 32, 20, 131, 60, 195, 137, 4, 13, 7, 132, 3, 195, 169, 7, 13, 7, 195, 52, 84, 148, 72, 8, 0, 8, 1, 47, 48, 107, 52, 0, 27, 10, 135, 22, 195, 169, 4, 5, 14, 9, 13, 0, 7, 65, 48, 107, 55, 55, 0, 9, 198, 52, 17, 218, 5, 67, 203, 13, 8, 197, 32, 149, 5, 49, 64, 13, 8, 197, 44, 144, 211, 37, 64, 13, 13, 138, 19, 26, 5, 18, 5, 20, 14, 195, 169, 11, 13, 17, 1, 48, 50, 40, 55, 12, 112, 89, 47, 0, 44, 81, 32, 115, 116, 32, 20, 1, 48, 50, 40, 55, 12, 112, 52, 113, 55, 0, 44, 81, 32, 114, 195, 179, 108, 32, 15, 1, 48, 50, 40, 55, 12, 112, 50, 0, 44, 81, 32, 110, 32, 20, 1, 48, 50, 40, 55, 12, 112, 47, 113, 55, 0, 44, 81, 32, 116, 195, 179, 108, 32, 21, 1, 48, 50, 40, 55, 12, 112, 89, 39, 50, 0, 44, 81, 32, 195, 161, 115, 111, 110, 32, 19, 1, 48, 50, 40, 55, 12, 112, 69, 106, 0, 44, 81, 32, 195, 161, 98, 97, 32, 21, 1, 48, 50, 40, 55, 12, 112, 69, 106, 50, 0, 44, 81, 32, 195, 161, 98, 97, 110, 32, 16, 1, 48, 50, 40, 55, 12, 112, 50, 0, 44, 81, 32, 97, 110, 32, 16, 1, 48, 50, 40, 55, 12, 112, 47, 0, 44, 81, 32, 97, 116, 32, 22, 1, 48, 50, 40, 55, 12, 112, 47, 113, 55, 0, 44, 81, 32, 195, 161, 116, 195, 179, 108, 32, 17, 1, 48, 50, 40, 55, 12, 112, 47, 0, 44, 81, 32, 195, 161, 116, 32, 17, 1, 48, 50, 40, 55, 12, 112, 69, 106, 0, 44, 81, 32, 98, 97, 32, 19, 1, 48, 50, 40, 55, 12, 112, 69, 106, 50, 0, 44, 81, 32, 98, 97, 110, 32, 17, 1, 48, 50, 40, 55, 12, 112, 37, 79, 0, 44, 81, 32, 105, 103, 32, 17, 1, 48, 50, 40, 55, 12, 112, 50, 0, 44, 81, 32, 195, 161, 110, 32, 19, 1, 48, 50, 40, 55, 12, 112, 52, 106, 0, 44, 81, 32, 195, 161, 114, 97, 32, 15, 1, 48, 50, 40, 55, 12, 112, 89, 0, 44, 81, 32, 115, 32, 19, 1, 48, 50, 40, 55, 12, 112, 105, 39, 86, 0, 44, 81, 32, 104, 111, 122, 32, 20, 1, 48, 50, 40, 55, 12, 112, 50, 112, 55, 0, 44, 81, 32, 110, 195, 161, 108, 32, 17, 1, 48, 50, 40, 55, 12, 112, 52, 106, 0, 44, 81, 32, 114, 97, 32, 19, 1, 48, 50, 40, 55, 12, 112, 82, 106, 55, 0, 44, 81, 32, 118, 97, 108, 32, 15, 1, 48, 50, 40, 55, 12, 112, 47, 0, 44, 81, 32, 116, 32, 17, 1, 48, 50, 40, 55, 12, 112, 89, 0, 44, 81, 32, 195, 161, 115, 32, 0, 14, 139, 22, 195, 169, 7, 26, 197, 145, 4, 20, 5, 11, 13, 8, 133, 13, 195, 169, 12, 25, 13, 17, 1, 49, 107, 77, 12, 107, 55, 0, 44, 81, 32, 103, 121, 101, 108, 32, 17, 1, 49, 107, 77, 12, 107, 89, 0, 44, 81, 32, 103, 121, 101, 115, 32, 17, 1, 49, 107, 77, 12, 107, 47, 0, 44, 81, 32, 103, 121, 101, 116, 32, 22, 1, 49, 101, 108, 115, 101, 106, 195, 169, 116, 0, 44, 21, 29, 81, 32, 106, 195, 169, 116, 32, 25, 1, 49, 101, 108, 115, 101, 106, 195, 169, 104, 101, 122, 0, 44, 21, 29, 81, 32, 195, 169, 104, 101, 122, 32, 21, 1, 49, 101, 108, 115, 101, 106, 101, 105, 0, 44, 21, 29, 81, 32, 105, 107, 101, 105, 32, 19, 1, 49, 101, 108, 115, 101, 106, 101, 0, 44, 21, 29, 81, 32, 105, 107, 101, 32, 20, 1, 49, 101, 108, 115, 101, 106, 101, 105, 0, 44, 21, 29, 81, 32, 105, 107, 105, 32, 27, 1, 49, 101, 108, 115, 101, 106, 195, 169, 110, 195, 169, 108, 0, 44, 21, 29, 81, 32, 195, 169, 110, 195, 169, 108, 32, 28, 1, 49, 101, 108, 115, 101, 106, 195, 169, 110, 195, 169, 108, 0, 44, 21, 29, 81, 32, 106, 195, 169, 110, 195, 169, 108, 32, 23, 1, 49, 101, 108, 115, 101, 106, 195, 169, 118, 101, 108, 0, 44, 21, 29, 81, 32, 118, 101, 108, 32, 25, 1, 49, 101, 108, 115, 101, 106, 195, 169, 110, 101, 107, 0, 44, 21, 29, 81, 32, 195, 169, 110, 101, 107, 32, 24, 1, 49, 101, 108, 115, 101, 106, 195, 169, 105, 103, 0, 44, 21, 29, 81, 32, 106, 195, 169, 105, 103, 32, 28, 1, 49, 101, 108, 115, 101, 106, 195, 169, 116, 197, 145, 108, 0, 44, 21, 29, 81, 32, 106, 195, 169, 116, 197, 145, 108, 32, 24, 1, 49, 101, 108, 115, 101, 106, 195, 169, 114, 101, 0, 44, 21, 29, 81, 32, 106, 195, 169, 114, 101, 32, 26, 1, 49, 101, 108, 115, 101, 106, 195, 169, 118, 101, 108, 0, 44, 21, 29, 81, 32, 106, 195, 169, 118, 101, 108, 32, 20, 1, 49, 101, 108, 115, 101, 106, 101, 105, 0, 44, 21, 29, 81, 32, 106, 101, 105, 32, 18, 1, 49, 101, 108, 115, 101, 106, 101, 0, 44, 21, 29, 81, 32, 106, 101, 32, 21, 1, 49, 101, 108, 115, 101, 106, 195, 169, 116, 0, 44, 21, 29, 81, 32, 195, 169, 116, 32, 27, 1, 49, 101, 108, 115, 101, 106, 195, 169, 116, 197, 145, 108, 0, 44, 21, 29, 81, 32, 195, 169, 116, 197, 145, 108, 32, 22, 1, 49, 101, 108, 115, 101, 106, 195, 169, 105, 103, 0, 44, 29, 81, 32, 195, 169, 105, 103, 32, 24, 1, 49, 101, 108, 115, 101, 106, 195, 169, 118, 101, 108, 0, 44, 29, 81, 32, 195, 169, 118, 101, 108, 32, 25, 1, 49, 101, 108, 115, 101, 106, 195, 169, 114, 197, 145, 108, 0, 44, 21, 29, 81, 32, 114, 197, 145, 108, 32, 27, 1, 49, 101, 108, 115, 101, 106, 195, 169, 114, 197, 145, 108, 0, 44, 21, 29, 81, 32, 195, 169, 114, 197, 145, 108, 32, 21, 1, 49, 101, 108, 115, 101, 106, 195, 169, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 25, 1, 49, 101, 108, 115, 101, 106, 195, 169, 116, 197, 145, 108, 0, 44, 21, 29, 81, 32, 116, 197, 145, 108, 32, 21, 1, 49, 101, 108, 115, 101, 106, 195, 169, 114, 101, 0, 44, 21, 29, 81, 32, 114, 101, 32, 23, 1, 49, 101, 108, 115, 101, 106, 195, 169, 114, 101, 0, 44, 21, 29, 81, 32, 195, 169, 114, 101, 32, 19, 1, 49, 101, 108, 115, 101, 106, 101, 105, 0, 44, 21, 29, 81, 32, 101, 105, 32, 18, 1, 49, 101, 108, 115, 101, 106, 101, 105, 0, 44, 21, 29, 81, 32, 105, 32, 22, 1, 49, 101, 108, 115, 101, 106, 195, 169, 110, 0, 44, 21, 29, 81, 32, 106, 195, 169, 110, 32, 21, 1, 49, 101, 108, 115, 101, 106, 195, 169, 110, 0, 44, 21, 29, 81, 32, 195, 169, 110, 32, 17, 1, 49, 101, 108, 115, 101, 106, 101, 0, 44, 21, 29, 81, 32, 101, 32, 0, 11, 136, 195, 179, 18, 195, 161, 11, 9, 7, 13, 13, 138, 10, 5, 12, 5, 14, 20, 5, 14, 195, 169, 13, 18, 1, 50, 49, 107, 47, 12, 116, 82, 107, 55, 0, 44, 81, 32, 101, 108, 32, 15, 1, 50, 49, 107, 47, 12, 116, 63, 0, 44, 81, 32, 109, 32, 15, 1, 50, 49, 107, 47, 12, 116, 50, 0, 44, 81, 32, 110, 32, 17, 1, 50, 49, 107, 47, 12, 116, 50, 0, 44, 81, 32, 197, 145, 110, 32, 17, 1, 50, 49, 107, 47, 12, 116, 47, 0, 44, 81, 32, 197, 145, 116, 32, 18, 1, 50, 49, 111, 117, 12, 107, 52, 0, 44, 81, 32, 115, 122, 101, 114, 32, 28, 1, 50, 109, 195, 161, 115, 111, 100, 105, 107, 195, 161, 116, 195, 179, 108, 0, 44, 21, 29, 81, 32, 116, 197, 145, 108, 32, 30, 1, 50, 109, 195, 161, 115, 111, 100, 105, 107, 195, 161, 116, 195, 179, 108, 0, 44, 21, 29, 81, 32, 195, 169, 116, 197, 145, 108, 32, 24, 1, 50, 109, 195, 161, 115, 111, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 21, 1, 50, 109, 195, 161, 115, 111, 100, 105, 107, 97, 105, 0, 44, 21, 29, 81, 32, 105, 32, 0, 12, 137, 13, 15, 2, 9, 12, 3, 195, 169, 7, 13, 6, 131, 6, 197, 145, 13, 17, 1, 51, 105, 112, 52, 63, 106, 89, 0, 44, 81, 32, 109, 97, 115, 32, 15, 1, 51, 105, 112, 52, 63, 106, 47, 0, 44, 81, 32, 116, 32, 26, 1, 51, 105, 106, 52, 63, 106, 70, 37, 49, 12, 106, 55, 0, 44, 81, 32, 97, 100, 105, 107, 107, 97, 108, 32, 24, 1, 51, 105, 106, 52, 63, 106, 70, 37, 49, 39, 50, 0, 44, 81, 32, 97, 100, 105, 107, 111, 110, 32, 24, 1, 51, 105, 106, 52, 63, 106, 70, 37, 49, 106, 47, 0, 44, 81, 32, 97, 100, 105, 107, 97, 116, 32, 20, 1, 51, 105, 106, 52, 63, 106, 70, 37, 49, 0, 44, 81, 32, 97, 100, 105, 107, 32, 16, 1, 51, 105, 112, 52, 63, 39, 50, 0, 44, 81, 32, 111, 110, 32, 18, 1, 51, 105, 112, 52, 39, 63, 12, 106, 55, 0, 44, 81, 32, 97, 108, 32, 24, 1, 51, 104, 97, 114, 109, 97, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 21, 1, 51, 105, 106, 52, 10, 63, 106, 70, 37, 49, 106, 37, 0, 44, 21, 81, 32, 105, 32, 0, 7, 65, 52, 107, 63, 63, 0, 45, 69, 60, 179, 218, 80, 16, 39, 49, 39, 87, 47, 106, 23, 48, 52, 39, 69, 55, 111, 63, 112, 49, 69, 113, 55, 0, 13, 81, 112, 114, 111, 98, 108, 195, 169, 109, 195, 161, 107, 98, 195, 179, 108, 32, 8, 197, 60, 179, 218, 80, 16, 13, 25, 1, 52, 50, 107, 77, 107, 70, 37, 49, 12, 107, 55, 0, 44, 81, 32, 101, 100, 105, 107, 107, 101, 108, 32, 23, 1, 52, 50, 107, 77, 107, 70, 37, 49, 107, 50, 0, 44, 81, 32, 101, 100, 105, 107, 101, 110, 32, 23, 1, 52, 50, 107, 77, 107, 70, 37, 49, 107, 47, 0, 44, 81, 32, 101, 100, 105, 107, 101, 116, 32, 19, 1, 52, 50, 107, 77, 107, 70, 37, 49, 0, 44, 81, 32, 101, 100, 105, 107, 32, 14, 1, 52, 50, 111, 77, 107, 47, 0, 44, 81, 32, 116, 32, 18, 1, 52, 50, 111, 77, 12, 107, 55, 0, 44, 81, 32, 103, 121, 101, 108, 32, 16, 1, 52, 50, 111, 77, 12, 107, 55, 0, 44, 81, 32, 101, 108, 32, 0, 40, 5, 11, 195, 169, 14, 5, 49, 111, 50, 107, 10, 6, 15, 82, 112, 55, 106, 87, 47, 106, 50, 39, 63, 0, 13, 81, 118, 195, 161, 108, 97, 115, 122, 116, 97, 110, 111, 109, 32, 31, 70, 20, 195, 65, 72, 17, 0, 107, 55, 63, 106, 52, 106, 70, 23, 106, 47, 12, 113, 55, 0, 13, 81, 97, 116, 116, 195, 179, 108, 32, 10, 135, 22, 195, 161, 12, 21, 14, 11, 13, 8, 133, 11, 195, 169, 14, 5, 13, 15, 1, 53, 108, 47, 12, 107, 55, 0, 44, 81, 32, 101, 108, 32, 18, 1, 53, 108, 117, 12, 108, 52, 0, 44, 81, 32, 115, 122, 195, 182, 114, 32, 13, 1, 53, 108, 47, 108, 47, 0, 44, 81, 32, 116, 32, 23, 1, 53, 108, 47, 108, 70, 37, 49, 111, 47, 116, 55, 0, 44, 21, 81, 32, 116, 197, 145, 108, 32, 15, 1, 53, 108, 47, 12, 107, 55, 0, 44, 81, 32, 101, 108, 32, 16, 1, 53, 108, 47, 12, 107, 55, 0, 44, 81, 32, 116, 101, 108, 32, 13, 7, 95, 35, 45, 195, 169, 9, 7, 111, 37, 79, 0, 0, 35, 7, 8, 195, 169, 20, 20, 5, 12, 105, 111, 47, 12, 107, 55, 23, 107, 86, 107, 55, 116, 47, 12, 0, 13, 81, 101, 122, 101, 108, 197, 145, 116, 116, 32, 10, 199, 20, 195, 69, 57, 65, 78, 36, 13, 10, 135, 195, 169, 18, 22, 5, 12, 20, 13, 10, 199, 32, 19, 12, 28, 21, 14, 36, 13, 6, 195, 52, 83, 148, 13, 18, 1, 54, 105, 106, 117, 12, 39, 52, 0, 44, 81, 32, 115, 122, 111, 114, 32, 24, 1, 54, 105, 106, 47, 39, 70, 37, 49, 112, 47, 113, 55, 0, 44, 21, 81, 32, 116, 195, 179, 108, 32, 18, 1, 54, 105, 106, 47, 12, 113, 55, 0, 44, 81, 32, 116, 195, 179, 108, 32, 17, 1, 54, 105, 106, 47, 12, 106, 55, 0, 44, 81, 32, 116, 97, 108, 32, 16, 1, 54, 105, 106, 47, 12, 106, 55, 0, 44, 81, 32, 97, 108, 32, 23, 1, 54, 104, 97, 116, 111, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 19, 1, 54, 105, 106, 47, 39, 70, 37, 49, 106, 37, 0, 44, 21, 81, 32, 105, 32, 0, 31, 68, 80, 83, 142, 36, 47, 107, 50, 12, 37, 10, 6, 15, 106, 49, 106, 52, 112, 89, 0, 13, 81, 97, 107, 97, 114, 195, 161, 115, 32, 22, 68, 80, 83, 142, 36, 47, 107, 50, 12, 37, 23, 106, 87, 47, 0, 13, 81, 97, 122, 116, 32, 9, 134, 5, 19, 20, 195, 169, 14, 13, 7, 196, 80, 83, 142, 36, 13, 18, 1, 55, 105, 111, 117, 12, 107, 52, 0, 44, 81, 32, 115, 122, 101, 114, 32, 19, 1, 55, 105, 107, 47, 107, 89, 12, 107, 55, 0, 44, 81, 32, 115, 101, 108, 32, 22, 1, 55, 105, 107, 47, 107, 89, 107, 49, 52, 107, 0, 44, 81, 32, 115, 101, 107, 114, 101, 32, 16, 1, 55, 105, 111, 47, 12, 107, 55, 0, 44, 81, 32, 101, 108, 32, 17, 1, 55, 105, 111, 47, 12, 107, 55, 0, 44, 81, 32, 116, 101, 108, 32, 24, 1, 55, 105, 107, 47, 107, 70, 37, 49, 111, 47, 116, 55, 0, 44, 21, 81, 32, 116, 197, 145, 108, 32, 18, 1, 55, 105, 111, 47, 12, 116, 55, 0, 44, 81, 32, 116, 197, 145, 108, 32, 0, 7, 65, 56, 107, 50, 50, 0, 8, 197, 57, 147, 205, 60, 176, 13, 8, 197, 24, 17, 217, 56, 144, 13, 9, 134, 1, 11, 3, 9, 195, 179, 13, 8, 197, 88, 84, 218, 36, 176, 13, 10, 135, 22, 195, 169, 7, 195, 169, 14, 13, 7, 132, 195, 188, 7, 25, 13, 10, 135, 22, 195, 169, 7, 195, 169, 14, 20, 17, 1, 56, 65, 39, 55, 117, 12, 106, 55, 0, 44, 81, 32, 97, 108, 32, 18, 1, 56, 65, 39, 55, 117, 12, 106, 55, 0, 44, 81, 32, 99, 97, 108, 32, 25, 1, 56, 110, 121, 111, 108, 99, 97, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 20, 1, 56, 65, 39, 55, 117, 106, 70, 37, 49, 106, 37, 0, 44, 21, 81, 32, 105, 32, 0, 51, 10, 22, 195, 161, 12, 1, 19, 26, 15, 12, 20, 82, 112, 55, 106, 87, 39, 55, 47, 23, 106, 6, 15, 81, 107, 55, 82, 107, 47, 111, 89, 52, 107, 0, 13, 82, 97, 32, 102, 101, 108, 118, 101, 116, 195, 169, 115, 114, 101, 32, 12, 137, 20, 1, 12, 195, 161, 12, 20, 1, 13, 13, 57, 15, 11, 195, 182, 20, 5, 12, 5, 26, 5, 20, 20, 19, 195, 169, 7, 49, 108, 47, 107, 55, 107, 86, 107, 74, 12, 111, 79, 23, 69, 37, 87, 47, 39, 89, 110, 47, 106, 50, 37, 0, 13, 81, 98, 105, 122, 116, 111, 115, 195, 173, 116, 97, 110, 105, 32, 10, 135, 20, 197, 177, 14, 20, 5, 11, 13, 19, 1, 57, 49, 37, 55, 107, 50, 117, 107, 47, 0, 44, 81, 32, 99, 101, 116, 32, 20, 1, 57, 49, 37, 55, 107, 50, 117, 12, 107, 55, 0, 44, 81, 32, 99, 101, 108, 32, 19, 1, 57, 49, 37, 55, 107, 50, 117, 12, 107, 55, 0, 44, 81, 32, 101, 108, 32, 0, 29, 10, 19, 26, 195, 161, 13, 15, 12, 20, 1, 13, 87, 112, 63, 39, 55, 47, 106, 63, 23, 49, 37, 0, 13, 81, 107, 105, 32, 10, 135, 26, 195, 161, 18, 21, 12, 20, 13, 10, 135, 2, 5, 19, 26, 195, 169, 12, 13, 9, 134, 2, 195, 173, 26, 22, 1, 13, 14, 139, 6, 5, 10, 12, 197, 145, 4, 195, 182, 20, 20, 13, 14, 139, 11, 5, 26, 4, 197, 145, 4, 195, 182, 20, 20, 13, 0, 12, 137, 5, 12, 20, 197, 177, 14, 20, 5, 11, 13, 7, 196, 77, 160, 71, 4, 13, 12, 137, 5, 10, 20, 5, 20, 20, 195, 169, 11, 13, 0, 36, 69, 80, 84, 212, 72, 80, 47, 107, 89, 47, 52, 107, 10, 6, 15, 87, 106, 69, 105, 106, 47, 113, 0, 13, 81, 115, 122, 97, 98, 104, 97, 116, 195, 179, 32, 38, 8, 5, 7, 25, 195, 188, 22, 195, 169, 107, 77, 12, 109, 82, 111, 23, 47, 106, 34, 47, 39, 86, 112, 89, 0, 13, 81, 116, 97, 114, 116, 111, 122, 195, 161, 115, 32, 9, 198, 13, 48, 80, 5, 67, 203, 13, 44, 12, 22, 1, 12, 195, 179, 19, 26, 195, 173, 14, 197, 177, 82, 106, 55, 113, 87, 110, 50, 115, 15, 10, 105, 37, 70, 107, 79, 107, 69, 12, 0, 13, 81, 104, 105, 100, 101, 103, 101, 98, 98, 32, 8, 197, 4, 64, 84, 60, 176, 13, 16, 141, 5, 12, 11, 5, 26, 4, 197, 145, 4, 195, 182, 20, 20, 13, 12, 137, 11, 9, 20, 195, 169, 20, 5, 12, 20, 13, 15, 140, 22, 1, 12, 195, 179, 19, 26, 195, 173, 14, 197, 177, 13, 16, 141, 10, 5, 12, 195, 182, 12, 195, 169, 19, 14, 195, 169, 12, 13, 0, 11, 1, 61, 107, 77, 107, 50, 55, 116, 0, 27, 18, 143, 6, 5, 12, 5, 12, 197, 145, 19, 19, 195, 169, 7, 195, 188, 11, 13, 17, 142, 13, 5, 7, 11, 5, 26, 4, 197, 145, 4, 195, 182, 20, 20, 13, 17, 142, 195, 169, 18, 4, 5, 11, 12, 197, 145, 4, 195, 182, 20, 20, 13, 0, 40, 9, 11, 195, 169, 16, 20, 5, 12, 5, 14, 49, 111, 48, 47, 107, 55, 107, 50, 23, 69, 107, 47, 107, 79, 50, 107, 49, 0, 13, 81, 98, 101, 116, 101, 103, 110, 101, 107, 32, 56, 13, 195, 169, 16, 195, 188, 12, 5, 20, 5, 11, 8, 5, 26, 111, 48, 109, 55, 107, 47, 107, 49, 105, 107, 86, 23, 105, 106, 87, 39, 50, 55, 110, 47, 39, 47, 12, 106, 0, 13, 81, 104, 97, 115, 111, 110, 108, 195, 173, 116, 111, 116, 116, 97, 32, 0, 45, 9, 20, 1, 12, 195, 161, 12, 20, 1, 11, 47, 106, 55, 112, 55, 47, 106, 49, 23, 106, 6, 15, 65, 39, 63, 39, 86, 113, 49, 0, 13, 82, 97, 32, 110, 121, 111, 109, 111, 122, 195, 179, 107, 32, 12, 137, 20, 1, 12, 195, 161, 12, 20, 1, 11, 13, 30, 9, 13, 5, 18, 195, 188, 12, 20, 5, 11, 63, 107, 52, 109, 55, 47, 107, 49, 23, 81, 107, 55, 0, 13, 81, 102, 101, 108, 32, 12, 137, 16, 195, 179, 26, 15, 12, 20, 1, 11, 13, 19, 144, 2, 9, 12, 12, 5, 14, 20, 25, 197, 177, 26, 5, 20, 20, 5, 12, 13, 14, 139, 9, 7, 1, 26, 7, 1, 20, 195, 179, 10, 1, 13, 11, 200, 72, 83, 132, 77, 161, 82, 8, 80, 13, 0, 10, 1, 64, 49, 40, 49, 106, 117, 0, 27, 6, 65, 64, 48, 111, 0, 13, 138, 19, 26, 195, 161, 13, 15, 12, 20, 1, 11, 13, 0, 13, 138, 11, 195, 169, 18, 195, 169, 19, 195, 169, 20, 13, 23, 5, 20, 195, 169, 14, 25, 47, 111, 65, 10, 6, 15, 89, 107, 63, 0, 13, 81, 115, 101, 109, 32, 42, 70, 77, 162, 78, 80, 83, 128, 87, 37, 50, 47, 107, 50, 23, 47, 107, 89, 47, 52, 107, 87, 106, 69, 50, 37, 0, 13, 81, 116, 101, 115, 116, 114, 101, 115, 122, 97, 98, 110, 105, 32, 9, 198, 77, 162, 78, 80, 83, 128, 13, 8, 133, 20, 195, 169, 14, 25, 13, 0, 14, 139, 20, 5, 13, 5, 20, 197, 145, 10, 195, 169, 20, 13, 17, 142, 13, 5, 7, 1, 12, 1, 16, 195, 173, 20, 195, 179, 10, 1, 13, 15, 140, 195, 169, 18, 20, 5, 19, 195, 188, 12, 20, 5, 11, 13, 0, 10, 135, 195, 169, 18, 9, 14, 20, 9, 13, 0, 6, 65, 68, 49, 40, 0, 31, 8, 195, 169, 10, 19, 26, 1, 11, 1, 111, 57, 87, 106, 49, 106, 10, 6, 15, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 12, 137, 20, 197, 177, 26, 6, 1, 12, 1, 20, 13, 11, 136, 20, 1, 18, 20, 1, 14, 195, 161, 13, 0, 19, 144, 13, 197, 177, 11, 195, 182, 4, 20, 5, 20, 195, 169, 19, 8, 5, 26, 13, 0, 11, 136, 6, 195, 161, 10, 12, 21, 14, 11, 13, 10, 199, 12, 83, 148, 72, 146, 213, 76, 13, 0, 18, 68, 77, 161, 19, 104, 101, 115, 122, 100, 195, 169, 101, 115, 122, 0, 29, 42, 38, 68, 4, 32, 129, 56, 106, 69, 12, 106, 50, 23, 81, 39, 79, 55, 106, 55, 47, 106, 49, 106, 47, 0, 13, 81, 102, 111, 103, 108, 97, 108, 116, 97, 107, 97, 116, 32, 18, 143, 11, 195, 182, 26, 9, 14, 20, 195, 169, 26, 13, 195, 169, 14, 25, 13, 11, 136, 13, 195, 161, 19, 18, 195, 179, 12, 13, 16, 141, 3, 195, 169, 12, 11, 9, 20, 197, 177, 26, 195, 169, 19, 13, 7, 196, 20, 32, 133, 56, 13, 7, 196, 4, 32, 129, 56, 13, 0, 7, 65, 72, 107, 51, 51, 0, 21, 146, 22, 195, 169, 7, 12, 5, 7, 5, 19, 195, 173, 20, 5, 20, 20, 195, 169, 11, 13, 8, 197, 32, 148, 218, 20, 64, 13, 0, 10, 135, 18, 195, 169, 13, 12, 9, 11, 13, 8, 133, 13, 195, 169, 7, 25, 13, 0, 12, 137, 9, 18, 195, 161, 14, 25, 8, 15, 26, 13, 10, 199, 80, 20, 148, 4, 195, 65, 104, 13, 0, 7, 196, 81, 81, 19, 104, 76, 18, 67, 32, 241, 217, 105, 39, 77, 4, 106, 49, 37, 0, 81, 97, 107, 105, 32, 17, 67, 32, 241, 217, 105, 4, 39, 77, 4, 106, 86, 0, 81, 97, 122, 32, 15, 67, 32, 241, 217, 105, 4, 39, 77, 4, 106, 0, 81, 97, 32, 9, 198, 80, 84, 133, 52, 33, 78, 13, 34, 7, 5, 21, 18, 195, 179, 16, 1, 107, 40, 52, 113, 48, 106, 15, 10, 65, 40, 79, 106, 47, 37, 0, 13, 81, 110, 121, 117, 103, 97, 116, 105, 32, 6, 195, 52, 81, 217, 13, 7, 132, 19, 195, 179, 20, 13, 6, 195, 52, 81, 217, 13, 0, 7, 65, 76, 107, 89, 0, 14, 6, 65, 76, 89, 10, 0, 8, 197, 60, 179, 218, 56, 144, 13, 43, 10, 22, 15, 14, 1, 20, 11, 15, 26, 195, 179, 82, 39, 50, 106, 47, 49, 39, 86, 113, 10, 6, 15, 48, 39, 50, 78, 106, 37, 47, 0, 13, 81, 112, 111, 110, 116, 106, 97, 105, 116, 32, 8, 197, 88, 86, 133, 80, 144, 13, 8, 197, 44, 20, 21, 56, 176, 13, 13, 138, 22, 15, 14, 1, 20, 11, 15, 26, 195, 179, 13, 11, 136, 13, 9, 12, 12, 9, 195, 179, 13, 13, 8, 197, 16, 243, 7, 61, 64, 13, 19, 3, 22, 195, 182, 82, 6, 107, 88, 70, 15, 10, 6, 108, 87, 120, 107, 0, 25, 0, 9, 198, 60, 179, 218, 56, 18, 192, 13, 9, 198, 13, 48, 80, 5, 67, 212, 13, 0, 9, 198, 32, 19, 12, 61, 69, 1, 13, 18, 143, 22, 195, 161, 12, 20, 15, 26, 1, 20, 195, 161, 2, 195, 179, 12, 13, 0, 11, 200, 52, 20, 129, 16, 160, 78, 4, 176, 13, 0, 12, 201, 52, 20, 129, 16, 128, 84, 56, 18, 192, 13, 12, 201, 28, 243, 132, 61, 50, 207, 16, 146, 192, 13, 8, 197, 24, 83, 22, 21, 64, 13, 0, 21, 146, 14, 25, 9, 12, 22, 195, 161, 14, 195, 173, 20, 195, 161, 19, 20, 195, 179, 12, 13, 12, 137, 19, 195, 169, 20, 195, 161, 12, 14, 9, 13, 12, 137, 14, 25, 195, 186, 10, 20, 1, 14, 9, 13, 5, 194, 8, 16, 13, 0, 35, 67, 52, 81, 192, 63, 107, 79, 23, 49, 107, 55, 12, 23, 39, 55, 70, 106, 50, 37, 0, 13, 82, 107, 101, 108, 108, 32, 111, 108, 100, 97, 110, 105, 32, 41, 67, 52, 81, 192, 63, 107, 79, 23, 49, 107, 55, 12, 23, 82, 37, 88, 79, 112, 55, 50, 37, 0, 13, 82, 107, 101, 108, 108, 32, 118, 105, 122, 115, 103, 195, 161, 108, 110, 105, 32, 38, 67, 52, 81, 192, 63, 107, 79, 10, 6, 15, 49, 107, 55, 12, 10, 6, 15, 65, 39, 63, 50, 37, 0, 13, 82, 107, 101, 108, 108, 32, 110, 121, 111, 109, 110, 105, 32, 25, 67, 52, 81, 192, 63, 107, 79, 23, 106, 86, 39, 49, 106, 47, 0, 13, 81, 97, 122, 111, 107, 97, 116, 32, 28, 67, 52, 81, 192, 63, 107, 79, 23, 106, 6, 15, 89, 39, 52, 69, 106, 0, 13, 82, 97, 32, 115, 111, 114, 98, 97, 32, 45, 67, 52, 81, 192, 63, 107, 79, 23, 106, 6, 15, 57, 107, 55, 107, 50, 47, 49, 107, 86, 116, 82, 107, 55, 0, 13, 82, 97, 32, 106, 101, 108, 101, 110, 116, 107, 101, 122, 197, 145, 118, 101, 108, 32, 29, 67, 52, 81, 192, 63, 107, 79, 23, 37, 89, 23, 47, 40, 70, 39, 63, 0, 13, 82, 105, 115, 32, 116, 117, 100, 111, 109, 32, 24, 67, 52, 81, 192, 63, 107, 79, 23, 106, 23, 105, 110, 52, 0, 13, 82, 97, 32, 104, 195, 173, 114, 32, 15, 67, 52, 81, 192, 63, 107, 79, 23, 106, 0, 13, 81, 97, 32, 6, 195, 52, 81, 192, 13, 0, 11, 136, 13, 9, 12, 12, 9, 195, 179, 20, 13, 24, 68, 20, 208, 133, 72, 107, 63, 69, 107, 52, 23, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 13, 196, 20, 208, 133, 72, 13, 81, 118, 111, 108, 116, 32, 8, 133, 1, 12, 22, 195, 179, 13, 7, 196, 20, 208, 133, 72, 13, 0, 8, 133, 11, 195, 182, 12, 20, 13, 28, 67, 8, 19, 0, 69, 106, 55, 23, 39, 55, 70, 106, 55, 112, 50, 0, 13, 81, 111, 108, 100, 97, 108, 195, 161, 110, 32, 12, 201, 20, 194, 5, 49, 145, 90, 21, 69, 0, 13, 8, 133, 10, 195, 182, 20, 20, 13, 11, 193, 84, 17, 83, 46, 32, 105, 32, 46, 32, 0, 6, 195, 12, 146, 203, 13, 9, 66, 85, 0, 40, 48, 0, 42, 42, 0, 11, 136, 10, 195, 161, 18, 20, 21, 14, 11, 13, 41, 73, 44, 20, 3, 76, 243, 1, 80, 32, 78, 49, 106, 48, 74, 39, 55, 106, 47, 69, 106, 50, 23, 106, 86, 23, 82, 39, 55, 47, 0, 13, 82, 97, 122, 32, 118, 111, 108, 116, 32, 10, 199, 20, 193, 143, 28, 17, 14, 36, 13, 10, 199, 8, 83, 85, 80, 21, 14, 36, 13, 10, 199, 20, 197, 137, 76, 83, 14, 36, 13, 9, 134, 3, 195, 169, 12, 10, 1, 13, 10, 135, 5, 12, 10, 195, 182, 20, 20, 13, 20, 145, 20, 5, 12, 10, 5, 19, 195, 173, 20, 195, 169, 19, 195, 169, 8, 5, 26, 13, 11, 136, 20, 197, 145, 12, 195, 188, 14, 11, 13, 0, 10, 135, 12, 195, 161, 20, 20, 1, 13, 13, 0, 4, 193, 88, 42, 6, 65, 88, 82, 111, 0, 12, 201, 40, 81, 217, 104, 85, 5, 44, 85, 0, 13, 9, 134, 22, 195, 173, 22, 15, 11, 13, 8, 197, 72, 243, 148, 40, 16, 13, 8, 197, 57, 147, 205, 60, 208, 13, 8, 197, 48, 83, 20, 20, 208, 13, 0, 9, 198, 29, 145, 82, 52, 82, 192, 13, 34, 11, 19, 26, 1, 2, 195, 161, 12, 25, 26, 195, 179, 87, 106, 69, 112, 57, 86, 113, 23, 40, 47, 112, 50, 0, 13, 81, 117, 116, 195, 161, 110, 32, 9, 198, 72, 17, 207, 104, 226, 64, 13, 13, 138, 22, 1, 4, 195, 161, 19, 26, 15, 20, 20, 13, 9, 198, 40, 83, 5, 104, 226, 64, 13, 9, 198, 57, 145, 82, 80, 82, 192, 13, 16, 141, 2, 9, 26, 15, 14, 25, 195, 173, 20, 1, 14, 9, 1, 13, 5, 194, 5, 48, 72, 0, 9, 134, 2, 195, 173, 26, 26, 1, 13, 13, 138, 11, 195, 182, 20, 5, 12, 5, 26, 197, 145, 13, 12, 137, 18, 195, 182, 22, 9, 4, 5, 2, 2, 13, 10, 135, 10, 15, 7, 18, 195, 179, 12, 13, 13, 138, 19, 26, 15, 12, 7, 195, 161, 12, 14, 1, 13, 8, 133, 195, 186, 20, 15, 14, 13, 8, 133, 11, 195, 182, 19, 26, 13, 8, 133, 195, 186, 20, 15, 14, 20, 0, 15, 140, 195, 182, 19, 19, 26, 5, 18, 1, 11, 15, 20, 20, 13, 16, 141, 13, 5, 7, 20, 5, 12, 195, 173, 20, 195, 188, 14, 11, 13, 15, 4, 95, 49, 77, 52, 107, 77, 69, 37, 55, 55, 37, 113, 0, 0, 12, 1, 92, 69, 107, 49, 120, 55, 107, 89, 0, 27, 11, 65, 92, 70, 40, 48, 55, 106, 82, 111, 0, 11, 136, 7, 25, 1, 14, 195, 186, 10, 1, 13, 8, 197, 88, 85, 20, 20, 176, 13, 11, 136, 6, 195, 188, 12, 5, 11, 18, 5, 13, 12, 201, 88, 243, 129, 80, 179, 218, 56, 18, 192, 13, 9, 134, 12, 1, 11, 195, 179, 11, 13, 12, 201, 24, 241, 204, 4, 194, 207, 104, 226, 64, 13, 0, 10, 135, 10, 195, 182, 20, 20, 5, 11, 13, 0, 14, 1, 94, 81, 108, 55, 81, 107, 55, 111, 65, 110, 55, 0, 9, 134, 20, 195, 169, 18, 14, 9, 13, 13, 138, 22, 9, 26, 19, 7, 195, 161, 12, 10, 1, 13, 9, 134, 11, 195, 182, 20, 14, 9, 13, 0, 14, 139, 11, 18, 9, 20, 9, 11, 195, 161, 11, 18, 1, 13, 38, 4, 7, 195, 169, 16, 79, 111, 48, 23, 81, 39, 77, 106, 87, 47, 112, 89, 112, 47, 0, 13, 81, 102, 111, 103, 121, 97, 115, 122, 116, 195, 161, 115, 195, 161, 116, 32, 11, 200, 57, 146, 84, 61, 69, 21, 56, 176, 13, 10, 135, 19, 5, 7, 195, 169, 12, 25, 13, 7, 132, 13, 195, 179, 4, 13, 7, 132, 7, 195, 169, 16, 13, 0, 4, 193, 96, 42, 7, 65, 96, 37, 49, 87, 0, 11, 136, 18, 195, 161, 22, 5, 14, 14, 9, 13, 16, 65, 96, 47, 110, 86, 86, 107, 55, 0, 44, 42, 81, 101, 108, 32, 0, 10, 135, 10, 195, 161, 18, 20, 1, 19, 13, 5, 194, 4, 64, 13, 15, 4, 95, 49, 77, 50, 107, 77, 63, 37, 55, 55, 37, 113, 0, 0, 14, 139, 11, 195, 169, 18, 4, 195, 169, 19, 195, 169, 20, 13, 18, 143, 13, 5, 7, 1, 12, 195, 161, 26, 195, 161, 19, 18, 195, 179, 12, 13, 10, 199, 80, 20, 148, 4, 195, 65, 80, 13, 15, 140, 195, 169, 12, 3, 5, 12, 197, 145, 4, 20, 5, 11, 13, 13, 138, 16, 9, 19, 26, 11, 195, 161, 12, 14, 9, 13, 13, 138, 19, 5, 2, 5, 19, 19, 195, 169, 7, 5, 13, 17, 4, 95, 49, 77, 51, 107, 77, 63, 37, 55, 55, 37, 112, 52, 70, 0, 0, 14, 139, 195, 186, 10, 4, 15, 14, 19, 195, 161, 7, 1, 13, 40, 7, 14, 25, 5, 12, 22, 197, 177, 65, 107, 55, 82, 115, 23, 37, 89, 63, 107, 52, 47, 107, 47, 116, 49, 0, 13, 81, 105, 115, 109, 101, 114, 116, 101, 116, 197, 145, 107, 32, 8, 133, 195, 169, 12, 5, 19, 13, 0, 11, 65, 100, 37, 48, 87, 37, 55, 39, 50, 0, 24, 149, 20, 195, 182, 18, 22, 195, 169, 14, 25, 10, 1, 22, 1, 19, 12, 1, 20, 18, 195, 179, 12, 13, 20, 145, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 195, 161, 2, 195, 179, 12, 13, 33, 6, 11, 5, 22, 195, 169, 19, 49, 107, 82, 111, 89, 23, 106, 23, 81, 107, 55, 105, 116, 0, 13, 82, 97, 32, 102, 101, 108, 104, 197, 145, 32, 11, 136, 22, 195, 169, 7, 5, 26, 14, 9, 13, 13, 138, 20, 5, 11, 9, 14, 20, 195, 188, 14, 11, 13, 8, 197, 4, 176, 82, 77, 160, 13, 9, 134, 11, 5, 22, 195, 169, 19, 13, 12, 67, 16, 245, 206, 70, 39, 58, 50, 0, 42, 42, 0, 16, 141, 195, 182, 14, 11, 195, 182, 12, 20, 19, 195, 169, 7, 5, 13, 33, 70, 57, 149, 71, 60, 69, 0, 65, 40, 79, 39, 47, 12, 15, 63, 106, 52, 106, 70, 50, 37, 0, 13, 81, 109, 97, 114, 97, 100, 110, 105, 32, 9, 198, 24, 244, 132, 84, 197, 0, 13, 0, 46, 10, 8, 15, 18, 4, 5, 18, 5, 10, 197, 177, 105, 39, 52, 70, 107, 52, 107, 57, 115, 23, 49, 111, 52, 70, 111, 89, 69, 107, 50, 0, 13, 81, 107, 195, 169, 114, 100, 195, 169, 115, 98, 101, 110, 32, 10, 199, 32, 83, 25, 104, 85, 2, 20, 13, 6, 195, 76, 20, 192, 13, 0, 19, 144, 13, 5, 7, 19, 26, 195, 188, 12, 5, 20, 195, 169, 19, 195, 169, 20, 13, 45, 68, 20, 118, 73, 44, 107, 77, 12, 37, 49, 10, 6, 15, 47, 107, 55, 107, 48, 105, 107, 57, 111, 52, 116, 55, 0, 13, 81, 116, 101, 108, 101, 112, 104, 101, 108, 121, 195, 169, 114, 197, 145, 108, 32, 33, 68, 20, 118, 73, 44, 107, 77, 12, 37, 49, 23, 82, 107, 86, 107, 47, 116, 57, 107, 0, 13, 81, 118, 101, 122, 101, 116, 197, 145, 106, 101, 32, 40, 68, 20, 118, 73, 44, 107, 77, 12, 37, 49, 23, 49, 111, 48, 82, 37, 89, 107, 55, 116, 57, 107, 0, 13, 81, 107, 195, 169, 112, 118, 105, 115, 101, 108, 197, 145, 106, 101, 32, 19, 144, 6, 5, 12, 20, 195, 188, 14, 20, 5, 20, 195, 169, 19, 195, 169, 20, 13, 12, 137, 12, 5, 8, 5, 20, 195, 188, 14, 11, 13, 7, 196, 20, 118, 73, 44, 13, 0, 6, 65, 104, 86, 111, 0, 25, 69, 24, 244, 132, 84, 192, 81, 39, 34, 70, 40, 55, 23, 107, 55, 116, 0, 13, 81, 101, 108, 197, 145, 32, 39, 69, 32, 243, 140, 5, 0, 105, 39, 50, 55, 106, 48, 10, 6, 15, 47, 108, 52, 55, 111, 89, 111, 47, 0, 13, 81, 116, 195, 182, 114, 108, 195, 169, 115, 195, 169, 116, 32, 8, 197, 57, 147, 205, 60, 224, 13, 13, 138, 18, 5, 14, 4, 197, 145, 18, 195, 182, 11, 13, 13, 138, 20, 5, 18, 5, 13, 20, 195, 188, 14, 11, 13, 8, 197, 64, 144, 67, 60, 224, 13, 8, 197, 24, 244, 132, 84, 192, 13, 0, 16, 141, 5, 18, 5, 4, 13, 195, 169, 14, 25, 5, 26, 197, 145, 13, 13, 138, 13, 21, 14, 11, 195, 161, 18, 195, 179, 12, 13, 9, 198, 88, 149, 1, 80, 160, 64, 13, 9, 198, 53, 85, 1, 80, 160, 64, 13, 12, 137, 6, 5, 12, 14, 195, 182, 22, 197, 145, 13, 8, 133, 12, 195, 169, 7, 25, 13, 0, 10, 135, 11, 195, 169, 13, 13, 5, 12, 13, 10, 199, 52, 243, 137, 80, 244, 143, 44, 13, 14, 139, 22, 195, 161, 12, 12, 195, 161, 18, 195, 179, 12, 13, 10, 199, 24, 244, 132, 84, 197, 1, 44, 13, 0, 25, 68, 97, 98, 73, 36, 47, 37, 86, 107, 50, 65, 39, 55, 117, 12, 106, 55, 0, 44, 42, 81, 97, 108, 32, 0, 34, 69, 40, 83, 5, 57, 64, 57, 107, 55, 107, 50, 47, 23, 87, 112, 63, 40, 49, 52, 106, 0, 13, 81, 115, 122, 195, 161, 109, 117, 107, 114, 97, 32, 12, 137, 195, 179, 18, 195, 161, 20, 195, 179, 12, 13, 13, 138, 19, 26, 195, 161, 18, 13, 1, 26, 195, 179, 13, 8, 197, 40, 83, 5, 57, 64, 13, 16, 9, 95, 35, 45, 195, 161, 18, 195, 179, 12, 112, 52, 113, 55, 0, 0, 0, 13, 138, 6, 197, 145, 8, 1, 4, 14, 1, 7, 25, 13, 0, 45, 68, 85, 64, 193, 36, 40, 117, 12, 106, 37, 23, 111, 48, 109, 55, 107, 47, 107, 23, 107, 55, 116, 47, 12, 0, 13, 82, 195, 169, 112, 195, 188, 108, 101, 116, 101, 32, 101, 108, 197, 145, 116, 116, 32, 0, 8, 197, 4, 192, 75, 61, 64, 13, 8, 197, 80, 84, 150, 21, 64, 13, 0, 14, 139, 11, 195, 182, 22, 5, 20, 11, 5, 26, 9, 11, 13, 9, 198, 8, 85, 137, 80, 83, 20, 13, 9, 134, 20, 195, 161, 13, 1, 4, 13, 0, 9, 198, 32, 83, 25, 21, 69, 5, 13, 14, 139, 6, 5, 12, 15, 12, 22, 1, 19, 195, 179, 20, 13, 10, 135, 7, 18, 195, 179, 6, 15, 20, 13, 0, 13, 138, 8, 5, 12, 25, 195, 188, 11, 195, 182, 14, 13, 19, 144, 8, 1, 19, 26, 14, 195, 161, 12, 1, 20, 195, 161, 18, 195, 179, 12, 13, 7, 132, 11, 195, 182, 4, 13, 7, 196, 80, 83, 9, 44, 13, 7, 132, 195, 188, 12, 20, 13, 0, 25, 5, 195, 161, 12, 12, 20, 112, 55, 47, 23, 108, 87, 12, 107, 0, 13, 81, 195, 182, 115, 115, 122, 101, 32, 35, 5, 195, 161, 12, 12, 20, 112, 55, 47, 23, 48, 111, 55, 70, 106, 49, 111, 50, 47, 0, 13, 81, 112, 195, 169, 108, 100, 97, 107, 195, 169, 110, 116, 32, 19, 4, 195, 173, 7, 25, 110, 77, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 8, 197, 77, 160, 75, 52, 16, 13, 21, 4, 195, 173, 7, 25, 110, 77, 15, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 10, 135, 5, 19, 26, 11, 195, 182, 26, 13, 8, 133, 195, 161, 12, 12, 20, 13, 7, 132, 195, 173, 7, 25, 13, 0, 9, 198, 72, 243, 148, 4, 226, 64, 13, 9, 198, 80, 84, 141, 20, 149, 0, 13, 9, 198, 48, 85, 5, 56, 226, 64, 13, 21, 146, 13, 195, 179, 4, 15, 19, 195, 173, 20, 195, 161, 19, 195, 161, 18, 195, 179, 12, 13, 9, 198, 80, 20, 148, 4, 226, 64, 13, 9, 198, 52, 243, 132, 4, 226, 64, 13, 0, 9, 198, 80, 20, 148, 4, 226, 65, 13, 15, 204, 4, 194, 193, 48, 208, 90, 61, 69, 1, 44, 224, 75, 13, 0, 7, 196, 80, 242, 138, 4, 13, 10, 135, 21, 20, 3, 195, 161, 2, 1, 13, 11, 200, 32, 149, 129, 80, 179, 218, 88, 16, 13, 0, 8, 197, 88, 17, 217, 60, 176, 72, 11, 136, 20, 5, 19, 20, 195, 169, 2, 5, 13, 8, 197, 88, 20, 212, 4, 112, 13, 40, 9, 19, 9, 11, 5, 18, 195, 188, 12, 20, 89, 37, 49, 107, 52, 109, 55, 47, 23, 49, 37, 81, 39, 79, 50, 39, 63, 0, 13, 81, 107, 105, 102, 111, 103, 110, 111, 109, 32, 8, 197, 24, 17, 217, 60, 176, 13, 12, 201, 24, 83, 4, 60, 193, 207, 104, 226, 64, 13, 9, 134, 3, 195, 173, 13, 5, 11, 13, 13, 138, 11, 9, 20, 195, 169, 18, 195, 188, 14, 11, 13, 9, 134, 3, 195, 169, 12, 15, 11, 13, 16, 9, 95, 35, 45, 195, 161, 20, 195, 179, 12, 112, 47, 113, 55, 0, 0, 9, 198, 48, 84, 218, 80, 82, 192, 72, 9, 198, 24, 84, 212, 20, 226, 64, 13, 9, 198, 44, 84, 133, 76, 226, 64, 13, 9, 198, 88, 84, 218, 80, 82, 192, 13, 0, 22, 67, 44, 148, 192, 49, 37, 89, 23, 47, 107, 55, 113, 0, 13, 81, 116, 101, 108, 195, 179, 32, 30, 67, 44, 148, 192, 49, 37, 89, 15, 47, 109, 52, 107, 55, 63, 107, 47, 0, 13, 81, 116, 195, 188, 114, 101, 108, 109, 101, 116, 32, 19, 144, 5, 12, 11, 195, 169, 16, 26, 5, 12, 195, 169, 19, 195, 188, 14, 11, 13, 24, 67, 44, 148, 192, 49, 37, 89, 15, 107, 52, 107, 57, 115, 0, 13, 81, 101, 114, 101, 106, 197, 177, 32, 13, 138, 19, 26, 15, 12, 7, 195, 161, 12, 10, 1, 13, 10, 199, 77, 163, 205, 8, 21, 15, 56, 22, 0, 15, 140, 20, 18, 195, 179, 14, 10, 195, 161, 18, 195, 179, 12, 13, 15, 140, 20, 9, 12, 1, 12, 13, 195, 161, 18, 195, 179, 12, 13, 11, 200, 29, 144, 78, 4, 180, 218, 36, 176, 13, 15, 140, 4, 195, 182, 18, 195, 182, 13, 2, 195, 182, 12, 20, 13, 9, 134, 3, 195, 173, 13, 5, 14, 13, 12, 137, 22, 195, 161, 12, 20, 15, 26, 195, 179, 13, 0, 12, 201, 52, 83, 133, 81, 33, 78, 16, 85, 0, 13, 16, 141, 22, 195, 161, 12, 20, 15, 26, 20, 1, 20, 15, 20, 20, 13, 39, 69, 72, 18, 206, 4, 176, 52, 106, 49, 50, 106, 49, 10, 6, 15, 69, 107, 50, 12, 109, 50, 49, 107, 47, 0, 13, 81, 98, 101, 110, 110, 195, 188, 110, 107, 101, 116, 32, 24, 69, 88, 82, 5, 80, 144, 82, 107, 105, 107, 47, 37, 23, 106, 87, 47, 0, 13, 81, 97, 122, 116, 32, 12, 201, 44, 146, 133, 48, 83, 148, 20, 226, 64, 13, 0, 28, 70, 76, 146, 197, 72, 84, 192, 89, 37, 49, 107, 52, 107, 89, 23, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 12, 137, 19, 26, 195, 161, 13, 21, 11, 18, 1, 13, 9, 198, 12, 146, 203, 56, 82, 192, 13, 0, 9, 1, 126, 47, 37, 55, 70, 107, 0, 10, 135, 20, 195, 182, 2, 2, 9, 20, 13, 0, 15, 140, 16, 15, 19, 26, 20, 10, 195, 161, 18, 195, 179, 12, 13, 15, 140, 15, 11, 20, 1, 20, 195, 161, 19, 2, 195, 179, 12, 13, 10, 135, 5, 12, 195, 169, 18, 14, 9, 13, 9, 198, 16, 80, 197, 52, 33, 82, 20, 9, 198, 56, 245, 133, 52, 33, 82, 20, 0, 12, 201, 36, 225, 15, 44, 243, 20, 56, 18, 192, 13, 9, 198, 80, 20, 148, 4, 224, 75, 13, 0, 33, 70, 77, 161, 82, 36, 229, 0, 87, 107, 52, 37, 50, 47, 23, 106, 86, 39, 49, 50, 106, 49, 0, 13, 81, 97, 122, 111, 107, 110, 97, 107, 32, 27, 70, 77, 161, 82, 36, 229, 0, 87, 107, 52, 37, 50, 47, 23, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 44, 70, 77, 161, 82, 36, 229, 0, 87, 107, 52, 37, 50, 47, 23, 63, 113, 70, 39, 89, 110, 47, 105, 106, 47, 113, 0, 13, 81, 109, 195, 179, 100, 111, 115, 195, 173, 116, 104, 97, 116, 195, 179, 32, 12, 137, 13, 5, 7, 11, 195, 169, 18, 14, 9, 13, 16, 141, 10, 5, 12, 5, 14, 19, 195, 169, 7, 5, 11, 18, 5, 13, 12, 137, 13, 5, 7, 14, 195, 169, 26, 14, 9, 13, 9, 198, 77, 161, 82, 36, 229, 0, 13, 0, 18, 143, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 2, 195, 179, 12, 13, 0, 15, 204, 44, 243, 80, 72, 243, 73, 77, 54, 149, 52, 242, 192, 13, 55, 8, 19, 26, 195, 161, 13, 195, 173, 20, 87, 112, 63, 110, 47, 10, 6, 15, 106, 6, 15, 63, 37, 50, 37, 87, 47, 107, 52, 107, 55, 50, 108, 49, 0, 13, 82, 97, 32, 109, 105, 110, 105, 115, 122, 116, 101, 114, 101, 108, 110, 195, 182, 107, 32, 12, 201, 80, 20, 148, 4, 195, 65, 104, 224, 75, 13, 12, 201, 80, 20, 148, 4, 195, 65, 104, 224, 75, 13, 11, 136, 19, 26, 195, 161, 13, 195, 173, 20, 13, 0, 11, 136, 195, 169, 18, 11, 5, 26, 197, 145, 13, 12, 137, 195, 188, 26, 5, 13, 13, 195, 179, 4, 13, 13, 138, 9, 7, 195, 169, 14, 25, 195, 188, 14, 11, 13, 20, 145, 11, 15, 14, 3, 5, 16, 3, 9, 195, 179, 10, 195, 161, 18, 195, 179, 12, 13, 0, 20, 145, 20, 5, 22, 195, 169, 11, 5, 14, 25, 19, 195, 169, 7, 5, 11, 18, 5, 13, 9, 198, 32, 22, 149, 17, 64, 64, 13, 0, 31, 10, 22, 9, 26, 19, 7, 195, 161, 12, 14, 9, 82, 37, 88, 79, 112, 55, 50, 37, 23, 106, 87, 47, 0, 13, 81, 97, 122, 116, 32, 0, 14, 139, 14, 195, 169, 16, 5, 19, 19, 195, 169, 7, 5, 13, 33, 68, 48, 83, 142, 20, 55, 107, 50, 12, 107, 23, 87, 107, 52, 37, 50, 47, 107, 63, 0, 13, 81, 115, 122, 101, 114, 105, 110, 116, 101, 109, 32, 24, 67, 77, 161, 77, 87, 107, 63, 23, 107, 55, 116, 47, 12, 0, 13, 81, 101, 108, 197, 145, 116, 116, 32, 22, 68, 48, 83, 142, 20, 55, 107, 50, 12, 107, 23, 87, 113, 0, 13, 81, 115, 122, 195, 179, 32, 35, 68, 48, 83, 142, 20, 55, 107, 50, 12, 107, 23, 87, 109, 49, 89, 111, 79, 107, 63, 0, 13, 81, 115, 122, 195, 188, 107, 115, 195, 169, 103, 101, 109, 32, 31, 68, 48, 83, 142, 20, 55, 107, 50, 12, 107, 15, 87, 109, 49, 89, 111, 79, 0, 13, 81, 115, 122, 195, 188, 107, 115, 195, 169, 103, 32, 14, 139, 11, 195, 169, 16, 5, 19, 19, 195, 169, 7, 5, 13, 14, 139, 11, 195, 169, 16, 22, 9, 19, 5, 12, 197, 145, 13, 12, 137, 19, 9, 5, 20, 20, 195, 188, 14, 11, 13, 7, 132, 11, 195, 182, 16, 13, 7, 196, 48, 83, 142, 20, 13, 0, 0, 31, 6, 1, 20, 20, 195, 179, 12, 106, 47, 12, 113, 55, 10, 6, 15, 81, 111, 55, 50, 37, 0, 13, 81, 102, 195, 169, 108, 110, 105, 32, 10, 135, 11, 15, 18, 195, 186, 1, 11, 13, 11, 136, 7, 25, 5, 14, 7, 195, 169, 14, 13, 8, 133, 14, 195, 169, 7, 25, 13, 9, 134, 1, 20, 20, 195, 179, 12, 13, 0, 9, 198, 52, 81, 212, 20, 227, 137, 13, 11, 136, 22, 195, 161, 7, 25, 14, 1, 11, 13, 10, 199, 20, 192, 86, 84, 197, 1, 44, 13, 6, 195, 32, 145, 4, 13, 0, 12, 137, 22, 195, 161, 12, 1, 19, 26, 15, 11, 13, 0, 12, 201, 77, 160, 66, 4, 67, 129, 65, 32, 64, 13, 11, 136, 20, 1, 12, 195, 161, 12, 20, 1, 13, 13, 138, 2, 15, 18, 195, 173, 20, 1, 14, 1, 11, 13, 12, 137, 3, 19, 195, 182, 11, 11, 5, 14, 20, 13, 8, 197, 28, 243, 66, 61, 64, 13, 8, 197, 21, 161, 75, 21, 64, 13, 0, 0, 15, 140, 8, 1, 20, 195, 179, 19, 195, 161, 7, 14, 1, 11, 13, 21, 146, 195, 161, 12, 12, 1, 13, 20, 9, 20, 11, 195, 161, 18, 19, 195, 161, 7, 1, 13, 15, 140, 5, 12, 12, 195, 161, 20, 195, 179, 11, 14, 1, 11, 13, 13, 138, 11, 9, 20, 1, 12, 195, 161, 12, 20, 1, 13, 6, 195, 5, 81, 192, 20, 0, 18, 68, 53, 54, 141, 64, 101, 109, 101, 115, 122, 101, 109, 112, 195, 169, 0, 29, 19, 68, 53, 54, 141, 64, 101, 109, 101, 115, 122, 101, 109, 112, 195, 169, 0, 29, 42, 22, 4, 195, 161, 12, 12, 112, 55, 12, 23, 106, 52, 52, 106, 0, 13, 81, 97, 114, 114, 97, 32, 16, 141, 13, 5, 7, 6, 5, 12, 5, 12, 197, 145, 14, 5, 11, 13, 16, 141, 19, 26, 1, 11, 195, 169, 18, 20, 197, 145, 14, 5, 11, 13, 16, 141, 2, 9, 26, 15, 20, 20, 19, 195, 161, 7, 14, 1, 11, 13, 7, 132, 195, 161, 12, 12, 13, 0, 17, 142, 2, 9, 3, 9, 11, 12, 9, 26, 197, 145, 11, 14, 5, 11, 13, 15, 140, 11, 195, 182, 18, 195, 188, 12, 195, 182, 20, 20, 5, 13, 0, 12, 137, 3, 19, 5, 18, 195, 169, 12, 14, 9, 13, 25, 66, 8, 80, 69, 107, 10, 6, 15, 106, 87, 47, 23, 37, 89, 0, 13, 82, 97, 122, 116, 32, 105, 115, 32, 5, 194, 8, 80, 13, 5, 194, 8, 80, 13, 0, 9, 198, 72, 82, 212, 61, 32, 73, 13, 15, 140, 7, 1, 26, 4, 1, 19, 195, 161, 7, 14, 1, 11, 13, 15, 140, 5, 12, 5, 7, 5, 14, 4, 197, 145, 14, 5, 11, 13, 14, 203, 52, 81, 198, 60, 112, 76, 52, 22, 143, 81, 64, 13, 6, 195, 76, 20, 212, 13, 0, 22, 68, 88, 243, 14, 4, 82, 39, 55, 50, 106, 23, 81, 107, 55, 0, 13, 81, 102, 101, 108, 32, 22, 68, 88, 243, 14, 4, 82, 39, 55, 50, 106, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 33, 68, 88, 243, 14, 4, 82, 39, 55, 50, 106, 23, 63, 107, 79, 23, 116, 49, 107, 47, 0, 13, 82, 109, 101, 103, 32, 197, 145, 107, 101, 116, 32, 32, 68, 88, 243, 14, 4, 82, 39, 55, 50, 106, 23, 47, 107, 52, 82, 107, 86, 50, 37, 0, 13, 81, 116, 101, 114, 118, 101, 122, 110, 105, 32, 45, 68, 88, 243, 14, 4, 82, 39, 55, 50, 106, 23, 106, 23, 49, 111, 52, 70, 116, 110, 82, 107, 49, 107, 47, 0, 13, 82, 97, 32, 107, 195, 169, 114, 100, 197, 145, 195, 173, 118, 101, 107, 101, 116, 32, 12, 137, 19, 26, 15, 11, 195, 161, 19, 15, 19, 13, 12, 137, 19, 5, 2, 5, 19, 19, 195, 169, 7, 13, 12, 137, 19, 26, 195, 188, 11, 19, 195, 169, 7, 13, 12, 137, 19, 26, 195, 188, 11, 19, 195, 169, 7, 13, 11, 200, 32, 19, 1, 77, 165, 15, 81, 64, 13, 7, 196, 32, 148, 218, 36, 13, 7, 196, 88, 243, 14, 4, 13, 0, 36, 69, 32, 243, 14, 5, 0, 105, 39, 55, 50, 106, 48, 23, 70, 111, 55, 107, 55, 116, 47, 12, 0, 13, 81, 100, 195, 169, 108, 101, 108, 197, 145, 116, 116, 32, 34, 69, 32, 243, 14, 5, 0, 105, 39, 55, 50, 106, 48, 23, 70, 111, 55, 40, 47, 112, 50, 0, 13, 81, 100, 195, 169, 108, 117, 116, 195, 161, 110, 32, 8, 197, 32, 243, 14, 5, 0, 13, 34, 69, 32, 243, 14, 5, 0, 105, 39, 55, 50, 106, 48, 15, 70, 111, 55, 40, 47, 112, 50, 0, 13, 81, 100, 195, 169, 108, 117, 116, 195, 161, 110, 32, 36, 69, 32, 243, 14, 5, 0, 105, 39, 55, 50, 106, 48, 15, 70, 111, 55, 107, 55, 116, 47, 12, 0, 13, 81, 100, 195, 169, 108, 101, 108, 197, 145, 116, 116, 32, 9, 198, 61, 37, 143, 76, 224, 75, 13, 8, 197, 52, 243, 132, 80, 16, 13, 0, 6, 195, 32, 19, 11, 13, 12, 67, 57, 54, 139, 107, 50, 107, 87, 49, 112, 0, 0, 10, 199, 57, 149, 71, 60, 69, 1, 56, 13, 11, 136, 13, 195, 169, 18, 14, 195, 182, 11, 13, 13, 67, 36, 98, 128, 37, 81, 57, 106, 69, 12, 0, 25, 17, 4, 95, 50, 67, 15, 49, 111, 47, 87, 112, 86, 106, 70, 37, 49, 0, 0, 6, 195, 84, 227, 137, 13, 7, 196, 52, 83, 142, 36, 13, 0, 9, 198, 80, 19, 149, 49, 69, 75, 13, 0, 7, 66, 13, 48, 74, 111, 0, 0, 10, 199, 77, 161, 82, 20, 197, 5, 44, 13, 0, 11, 200, 88, 148, 197, 48, 177, 68, 56, 144, 13, 11, 200, 16, 243, 7, 61, 163, 137, 84, 176, 13, 40, 68, 60, 193, 1, 48, 39, 55, 70, 106, 55, 23, 107, 55, 49, 111, 87, 110, 47, 111, 89, 107, 0, 13, 81, 101, 108, 107, 195, 169, 115, 122, 195, 173, 116, 195, 169, 115, 101, 32, 11, 200, 8, 85, 129, 48, 195, 212, 80, 16, 13, 6, 195, 8, 83, 5, 13, 11, 200, 52, 81, 205, 60, 225, 1, 56, 144, 13, 7, 196, 60, 193, 1, 48, 13, 16, 4, 95, 50, 77, 52, 49, 111, 47, 69, 37, 55, 55, 37, 113, 0, 0, 35, 70, 44, 86, 132, 20, 225, 75, 49, 107, 86, 70, 107, 50, 107, 49, 6, 23, 37, 52, 112, 50, 47, 106, 0, 13, 81, 105, 114, 195, 161, 110, 116, 97, 32, 12, 137, 22, 9, 26, 19, 7, 195, 161, 12, 20, 13, 0, 31, 6, 11, 5, 18, 195, 188, 12, 49, 107, 52, 109, 55, 10, 6, 15, 37, 47, 105, 39, 50, 0, 13, 81, 105, 116, 116, 104, 111, 110, 32, 24, 6, 11, 5, 18, 195, 188, 12, 49, 107, 52, 109, 55, 23, 89, 39, 52, 0, 13, 81, 115, 111, 114, 32, 9, 134, 11, 5, 18, 195, 188, 12, 13, 0, 29, 67, 61, 37, 20, 111, 101, 114, 114, 116, 195, 169, 116, 195, 169, 116, 197, 145, 108, 0, 44, 29, 42, 81, 116, 197, 145, 108, 32, 12, 137, 19, 1, 18, 11, 195, 161, 8, 15, 26, 13, 15, 140, 19, 26, 195, 161, 13, 195, 173, 20, 1, 14, 1, 11, 13, 61, 10, 20, 5, 18, 195, 188, 12, 5, 20, 18, 5, 47, 107, 52, 109, 55, 107, 47, 52, 107, 10, 6, 15, 37, 89, 10, 6, 15, 49, 39, 50, 117, 107, 50, 47, 52, 112, 55, 50, 37, 0, 13, 82, 105, 115, 32, 107, 111, 110, 99, 101, 110, 116, 114, 195, 161, 108, 110, 105, 32, 10, 135, 20, 195, 182, 2, 2, 5, 20, 13, 26, 7, 20, 195, 182, 2, 2, 5, 20, 47, 108, 69, 12, 107, 47, 23, 81, 39, 79, 0, 13, 81, 102, 111, 103, 32, 32, 7, 20, 195, 182, 2, 2, 5, 20, 47, 108, 69, 12, 107, 47, 15, 47, 40, 70, 50, 106, 49, 0, 13, 81, 116, 117, 100, 110, 97, 107, 32, 8, 195, 61, 37, 20, 17, 42, 42, 0, 11, 136, 19, 5, 18, 5, 7, 195, 169, 20, 13, 47, 12, 195, 182, 19, 19, 26, 5, 15, 13, 12, 15, 20, 20, 108, 87, 12, 107, 39, 63, 55, 39, 47, 12, 23, 106, 23, 52, 107, 50, 117, 107, 52, 0, 13, 82, 97, 32, 114, 101, 110, 100, 115, 122, 101, 114, 32, 6, 195, 24, 83, 5, 13, 6, 195, 88, 83, 5, 13, 0, 17, 142, 7, 25, 1, 14, 195, 186, 19, 195, 173, 20, 1, 14, 1, 11, 13, 9, 198, 36, 225, 21, 49, 64, 75, 13, 15, 140, 11, 195, 169, 16, 5, 18, 14, 25, 197, 145, 18, 5, 13, 17, 10, 95, 35, 45, 9, 11, 195, 161, 14, 1, 11, 112, 50, 106, 49, 0, 14, 4, 95, 50, 77, 49, 49, 111, 47, 107, 86, 107, 52, 0, 0, 18, 66, 16, 32, 100, 97, 114, 97, 98, 111, 116, 0, 44, 29, 81, 111, 116, 32, 18, 66, 16, 32, 100, 97, 114, 97, 98, 111, 115, 0, 44, 29, 81, 111, 115, 32, 17, 66, 12, 64, 99, 195, 169, 100, 195, 169, 109, 0, 44, 29, 81, 109, 32, 18, 66, 12, 64, 99, 195, 169, 100, 195, 169, 109, 0, 44, 29, 42, 81, 109, 32, 18, 66, 12, 64, 99, 195, 169, 100, 195, 169, 100, 0, 44, 29, 42, 81, 100, 32, 17, 66, 12, 64, 99, 195, 169, 100, 195, 169, 100, 0, 44, 29, 81, 100, 32, 17, 66, 12, 64, 99, 195, 169, 100, 195, 169, 110, 0, 44, 29, 81, 110, 32, 18, 66, 12, 64, 99, 195, 169, 100, 195, 169, 110, 0, 44, 29, 42, 81, 110, 32, 17, 66, 12, 64, 99, 195, 169, 100, 195, 169, 107, 0, 44, 29, 81, 107, 32, 18, 66, 12, 64, 99, 195, 169, 100, 195, 169, 107, 0, 44, 29, 42, 81, 107, 32, 12, 137, 195, 169, 16, 195, 173, 20, 5, 14, 9, 13, 37, 66, 12, 64, 117, 111, 70, 111, 107, 55, 12, 107, 50, 116, 52, 86, 111, 89, 47, 0, 44, 42, 81, 101, 108, 108, 101, 110, 197, 145, 114, 122, 195, 169, 115, 116, 32, 16, 4, 95, 50, 77, 50, 49, 111, 47, 63, 37, 55, 55, 37, 113, 0, 0, 28, 71, 57, 149, 71, 60, 69, 1, 52, 65, 40, 79, 39, 47, 12, 106, 63, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 19, 144, 11, 195, 169, 19, 26, 195, 188, 12, 195, 169, 11, 5, 9, 14, 5, 11, 13, 10, 135, 10, 195, 182, 22, 197, 145, 20, 13, 10, 135, 195, 188, 26, 5, 14, 5, 20, 13, 18, 4, 95, 50, 77, 51, 49, 111, 47, 63, 37, 55, 55, 37, 112, 52, 70, 0, 0, 43, 70, 72, 83, 132, 77, 161, 82, 52, 107, 50, 117, 107, 52, 23, 81, 40, 47, 12, 106, 47, 112, 89, 112, 52, 106, 0, 13, 81, 102, 117, 116, 116, 97, 116, 195, 161, 115, 195, 161, 114, 97, 32, 41, 70, 72, 83, 132, 77, 161, 82, 52, 107, 50, 117, 107, 52, 23, 81, 52, 37, 89, 12, 110, 47, 111, 89, 47, 0, 13, 81, 102, 114, 105, 115, 115, 195, 173, 116, 195, 169, 115, 116, 32, 15, 140, 19, 5, 2, 5, 19, 19, 195, 169, 7, 195, 169, 20, 13, 15, 140, 11, 195, 182, 12, 20, 19, 195, 169, 7, 195, 169, 20, 13, 9, 198, 72, 83, 132, 77, 161, 82, 13, 11, 136, 19, 26, 195, 161, 13, 195, 161, 20, 13, 7, 196, 16, 243, 15, 28, 13, 0, 11, 136, 19, 26, 5, 18, 5, 20, 197, 145, 13, 16, 141, 13, 21, 14, 11, 1, 20, 195, 161, 18, 19, 195, 161, 20, 13, 18, 143, 195, 161, 12, 12, 195, 173, 20, 195, 161, 19, 195, 161, 8, 15, 26, 13, 15, 140, 2, 5, 195, 161, 12, 12, 195, 173, 20, 1, 14, 9, 13, 15, 140, 5, 7, 25, 5, 14, 12, 195, 173, 20, 5, 14, 9, 13, 8, 197, 52, 243, 132, 60, 64, 13, 11, 136, 11, 5, 18, 195, 188, 12, 197, 145, 13, 8, 133, 6, 195, 161, 10, 20, 13, 0, 57, 70, 24, 241, 193, 17, 64, 64, 81, 39, 79, 106, 47, 12, 106, 23, 106, 86, 6, 23, 107, 55, 49, 111, 48, 86, 107, 55, 111, 89, 107, 49, 107, 47, 0, 13, 82, 97, 122, 32, 101, 108, 107, 195, 169, 112, 122, 101, 108, 195, 169, 115, 101, 107, 101, 116, 32, 9, 198, 48, 81, 202, 60, 32, 128, 13, 9, 198, 48, 20, 211, 4, 32, 128, 13, 9, 198, 24, 241, 193, 17, 64, 64, 13, 0, 20, 145, 2, 9, 26, 20, 15, 19, 195, 173, 20, 195, 161, 19, 195, 161, 8, 15, 26, 13, 10, 199, 40, 83, 5, 57, 65, 78, 20, 13, 0, 7, 196, 24, 82, 130, 20, 13, 9, 134, 195, 161, 18, 2, 1, 14, 13, 7, 196, 80, 148, 218, 80, 13, 0, 12, 201, 32, 19, 135, 61, 165, 1, 81, 64, 64, 13, 0, 12, 66, 17, 32, 70, 39, 49, 47, 39, 52, 0, 25, 0, 9, 134, 13, 195, 182, 7, 195, 169, 13, 0, 12, 137, 11, 195, 188, 26, 4, 5, 14, 5, 11, 13, 9, 134, 11, 195, 179, 4, 195, 186, 13, 0, 32, 69, 64, 84, 131, 21, 64, 48, 107, 52, 117, 107, 47, 23, 81, 37, 86, 107, 47, 107, 49, 0, 13, 81, 102, 105, 122, 101, 116, 101, 107, 32, 8, 197, 9, 82, 203, 4, 224, 13, 12, 201, 52, 81, 212, 36, 197, 15, 81, 64, 64, 13, 8, 133, 6, 195, 161, 10, 12, 13, 8, 197, 52, 147, 139, 21, 64, 13, 8, 197, 52, 147, 139, 21, 64, 13, 12, 137, 5, 7, 25, 1, 18, 195, 161, 14, 20, 13, 0, 9, 198, 77, 161, 82, 21, 1, 64, 13, 12, 137, 11, 195, 182, 26, 195, 182, 12, 20, 5, 13, 9, 133, 197, 145, 19, 26, 9, 20, 13, 0, 14, 139, 6, 197, 145, 15, 19, 26, 20, 195, 161, 10, 20, 13, 6, 195, 32, 19, 20, 13, 0, 49, 13, 15, 19, 26, 20, 195, 161, 12, 25, 195, 161, 14, 1, 11, 39, 87, 47, 112, 57, 112, 50, 106, 49, 23, 82, 107, 86, 107, 47, 111, 89, 111, 47, 0, 13, 81, 118, 101, 122, 101, 116, 195, 169, 115, 195, 169, 116, 32, 16, 141, 20, 195, 161, 18, 7, 25, 1, 12, 10, 1, 14, 1, 11, 13, 16, 141, 20, 195, 161, 18, 7, 25, 1, 12, 10, 1, 14, 1, 11, 13, 0, 10, 135, 195, 179, 18, 1, 11, 15, 18, 13, 38, 14, 9, 14, 4, 195, 173, 20, 22, 195, 161, 14, 25, 14, 1, 11, 37, 50, 70, 110, 47, 82, 112, 65, 50, 106, 49, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 34, 11, 195, 161, 12, 12, 1, 16, 15, 20, 2, 1, 14, 112, 55, 12, 106, 48, 39, 47, 69, 106, 50, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 17, 142, 5, 12, 22, 195, 161, 18, 195, 161, 19, 15, 11, 14, 1, 11, 13, 8, 197, 24, 241, 193, 37, 64, 13, 9, 198, 80, 20, 148, 61, 162, 75, 13, 0, 10, 135, 195, 182, 19, 19, 26, 5, 7, 13, 14, 139, 22, 5, 26, 5, 20, 197, 145, 11, 14, 5, 11, 13, 9, 198, 52, 243, 132, 61, 69, 0, 13, 0, 19, 144, 11, 195, 169, 16, 22, 9, 19, 5, 12, 20, 10, 5, 9, 14, 5, 11, 13, 11, 136, 26, 195, 161, 19, 26, 12, 195, 179, 13, 0, 16, 141, 11, 21, 20, 1, 20, 195, 161, 19, 15, 11, 14, 1, 11, 13, 10, 135, 22, 195, 169, 11, 15, 14, 25, 13, 0, 8, 197, 16, 243, 7, 60, 176, 13, 45, 69, 16, 243, 7, 60, 176, 70, 39, 55, 79, 39, 49, 10, 6, 15, 37, 70, 107, 79, 107, 89, 110, 47, 107, 50, 107, 49, 0, 13, 81, 105, 100, 101, 103, 101, 115, 195, 173, 116, 101, 110, 101, 107, 32, 13, 138, 2, 5, 12, 197, 145, 14, 9, 195, 188, 11, 13, 17, 142, 9, 14, 20, 195, 169, 26, 13, 195, 169, 14, 25, 14, 5, 11, 13, 6, 195, 77, 160, 82, 13, 9, 198, 4, 192, 80, 77, 162, 75, 13, 15, 140, 195, 169, 12, 5, 20, 20, 1, 18, 20, 1, 13, 1, 13, 12, 201, 24, 241, 193, 48, 208, 90, 61, 69, 0, 13, 6, 195, 77, 160, 82, 13, 0, 40, 11, 11, 195, 182, 26, 195, 182, 14, 19, 195, 169, 7, 49, 108, 86, 108, 50, 89, 111, 79, 23, 89, 39, 52, 106, 37, 69, 106, 0, 13, 81, 115, 111, 114, 97, 105, 98, 97, 32, 12, 201, 80, 20, 1, 77, 165, 1, 49, 64, 77, 13, 9, 198, 77, 165, 15, 72, 149, 0, 13, 13, 138, 22, 1, 12, 12, 15, 13, 195, 161, 19, 20, 13, 0, 11, 136, 20, 21, 4, 8, 1, 20, 195, 179, 13, 10, 199, 4, 64, 75, 61, 163, 212, 80, 13, 16, 134, 11, 195, 169, 26, 2, 5, 13, 81, 118, 101, 110, 110, 105, 32, 0, 7, 196, 85, 64, 76, 80, 13, 7, 196, 4, 65, 9, 28, 13, 58, 13, 20, 5, 22, 195, 169, 11, 5, 14, 25, 19, 195, 169, 7, 47, 107, 82, 111, 49, 107, 65, 89, 111, 79, 23, 49, 108, 86, 111, 48, 12, 39, 50, 78, 112, 69, 106, 0, 13, 81, 107, 195, 182, 122, 195, 169, 112, 112, 111, 110, 116, 106, 195, 161, 98, 97, 32, 38, 9, 19, 26, 1, 2, 8, 1, 20, 195, 179, 87, 106, 69, 105, 106, 47, 113, 23, 63, 107, 50, 109, 82, 107, 55, 0, 13, 81, 109, 101, 110, 195, 188, 118, 101, 108, 32, 12, 137, 15, 19, 26, 20, 8, 1, 20, 195, 179, 13, 11, 136, 3, 19, 9, 14, 195, 161, 12, 20, 13, 16, 141, 20, 5, 22, 195, 169, 11, 5, 14, 25, 19, 195, 169, 7, 13, 12, 137, 22, 195, 161, 7, 8, 1, 20, 195, 179, 13, 12, 137, 12, 195, 161, 20, 8, 1, 20, 195, 179, 13, 7, 196, 32, 147, 142, 36, 13, 7, 196, 48, 83, 142, 36, 13, 0, 9, 198, 88, 148, 197, 49, 65, 75, 13, 17, 142, 20, 1, 12, 195, 161, 12, 13, 195, 161, 14, 25, 21, 14, 11, 13, 13, 138, 6, 15, 7, 1, 4, 8, 1, 20, 195, 179, 13, 0, 9, 198, 57, 145, 76, 88, 85, 0, 13, 42, 11, 5, 12, 22, 195, 161, 18, 8, 1, 20, 195, 179, 107, 55, 82, 112, 52, 105, 106, 47, 113, 23, 87, 107, 52, 37, 50, 47, 107, 0, 13, 81, 115, 122, 101, 114, 105, 110, 116, 101, 32, 12, 137, 19, 26, 195, 161, 13, 15, 4, 18, 1, 13, 14, 139, 6, 21, 20, 20, 1, 20, 8, 1, 20, 195, 179, 13, 12, 137, 5, 12, 11, 195, 182, 12, 20, 22, 5, 13, 14, 139, 20, 1, 12, 195, 161, 12, 8, 1, 20, 195, 179, 13, 0, 15, 140, 11, 1, 16, 3, 19, 15, 12, 8, 1, 20, 195, 179, 13, 9, 198, 88, 148, 197, 49, 65, 77, 13, 11, 136, 8, 1, 20, 195, 161, 19, 21, 11, 13, 15, 140, 6, 15, 18, 4, 195, 173, 20, 8, 1, 20, 195, 179, 13, 6, 195, 32, 149, 20, 13, 15, 8, 95, 35, 45, 195, 169, 14, 5, 11, 111, 50, 107, 49, 0, 0, 7, 196, 24, 82, 133, 16, 13, 16, 141, 11, 9, 20, 1, 12, 195, 161, 12, 8, 1, 20, 195, 179, 13, 12, 137, 22, 9, 12, 195, 161, 7, 14, 1, 11, 13, 0, 14, 139, 8, 195, 169, 20, 22, 195, 169, 7, 195, 169, 14, 13, 40, 14, 12, 5, 8, 5, 20, 197, 145, 19, 195, 169, 7, 195, 188, 11, 55, 107, 105, 107, 47, 116, 89, 111, 79, 109, 49, 23, 106, 52, 52, 106, 0, 13, 81, 97, 114, 114, 97, 32, 6, 195, 77, 161, 82, 72, 0, 9, 198, 80, 148, 9, 45, 84, 192, 13, 9, 134, 8, 195, 179, 14, 1, 16, 13, 0, 17, 142, 5, 12, 5, 11, 20, 18, 15, 14, 9, 11, 195, 161, 10, 1, 13, 0, 11, 136, 3, 195, 169, 12, 10, 1, 9, 20, 13, 50, 72, 36, 229, 5, 72, 225, 84, 21, 48, 37, 50, 47, 107, 52, 50, 107, 47, 107, 89, 15, 49, 37, 47, 108, 55, 47, 111, 89, 111, 52, 107, 0, 13, 81, 107, 105, 116, 195, 182, 108, 116, 195, 169, 115, 195, 169, 114, 101, 32, 20, 145, 13, 5, 7, 195, 161, 12, 12, 1, 16, 195, 173, 20, 8, 1, 20, 195, 179, 13, 0, 45, 10, 2, 197, 177, 14, 195, 182, 19, 14, 5, 11, 69, 115, 50, 108, 89, 50, 107, 49, 10, 6, 15, 47, 106, 55, 112, 61, 57, 112, 49, 0, 13, 81, 116, 97, 108, 195, 161, 108, 106, 195, 161, 107, 32, 12, 137, 7, 25, 5, 18, 5, 11, 195, 169, 20, 13, 14, 139, 195, 169, 16, 195, 188, 12, 5, 20, 2, 5, 14, 13, 14, 139, 11, 5, 18, 195, 188, 12, 5, 20, 2, 5, 14, 13, 0, 12, 137, 11, 5, 26, 4, 197, 145, 4, 197, 145, 13, 14, 139, 6, 21, 14, 11, 3, 9, 195, 179, 14, 1, 11, 13, 0, 0, 11, 136, 5, 7, 195, 169, 19, 26, 5, 20, 13, 0, 8, 197, 77, 160, 66, 4, 64, 76, 11, 136, 13, 195, 169, 18, 5, 20, 197, 177, 13, 64, 14, 6, 5, 12, 22, 195, 169, 20, 5, 12, 195, 169, 14, 5, 11, 81, 107, 55, 82, 111, 47, 107, 55, 111, 50, 107, 49, 23, 87, 109, 49, 89, 111, 79, 107, 89, 12, 111, 79, 111, 47, 0, 13, 81, 115, 122, 195, 188, 107, 115, 195, 169, 103, 101, 115, 115, 195, 169, 103, 195, 169, 116, 32, 11, 136, 195, 169, 16, 195, 188, 12, 197, 145, 13, 6, 195, 36, 113, 78, 13, 8, 133, 11, 195, 169, 18, 20, 13, 10, 4, 95, 49, 48, 5, 47, 37, 86, 0, 0, 0, 14, 139, 195, 169, 12, 13, 195, 169, 14, 25, 195, 169, 20, 13, 10, 199, 24, 148, 148, 5, 52, 213, 44, 13, 19, 144, 14, 195, 182, 22, 5, 11, 5, 4, 195, 169, 19, 195, 169, 14, 5, 11, 13, 14, 139, 20, 195, 161, 18, 8, 5, 12, 25, 195, 169, 20, 13, 32, 7, 18, 5, 1, 7, 195, 161, 12, 52, 107, 106, 79, 112, 55, 23, 47, 108, 69, 12, 111, 0, 13, 81, 116, 195, 182, 98, 98, 195, 169, 32, 6, 195, 60, 176, 64, 13, 10, 199, 20, 197, 133, 32, 85, 9, 44, 13, 10, 135, 195, 173, 7, 195, 169, 18, 20, 13, 0, 7, 196, 77, 162, 78, 80, 13, 0, 10, 135, 16, 9, 1, 3, 195, 161, 14, 13, 8, 133, 6, 9, 195, 186, 20, 13, 8, 133, 2, 197, 145, 18, 20, 13, 0, 39, 66, 5, 160, 106, 86, 23, 111, 52, 47, 111, 49, 107, 89, 110, 47, 111, 89, 47, 0, 13, 81, 195, 169, 114, 116, 195, 169, 107, 101, 115, 195, 173, 116, 195, 169, 115, 116, 32, 22, 66, 5, 160, 106, 86, 23, 37, 70, 116, 52, 107, 0, 13, 81, 105, 100, 197, 145, 114, 101, 32, 18, 66, 5, 160, 106, 86, 23, 87, 106, 52, 0, 13, 81, 115, 122, 97, 114, 32, 34, 66, 5, 160, 106, 86, 23, 106, 55, 106, 48, 111, 55, 63, 111, 65, 107, 0, 13, 81, 97, 108, 97, 112, 195, 169, 108, 109, 195, 169, 110, 121, 101, 32, 25, 66, 5, 160, 106, 86, 23, 109, 77, 107, 49, 107, 47, 0, 13, 81, 195, 188, 103, 121, 101, 107, 101, 116, 32, 27, 66, 5, 160, 106, 86, 23, 109, 77, 107, 49, 69, 107, 50, 0, 13, 81, 195, 188, 103, 121, 101, 107, 98, 101, 110, 32, 29, 66, 5, 160, 106, 86, 10, 6, 15, 106, 70, 106, 47, 39, 49, 106, 47, 0, 13, 81, 97, 100, 97, 116, 111, 107, 97, 116, 32, 32, 66, 5, 160, 106, 86, 10, 6, 15, 37, 50, 70, 39, 49, 55, 112, 89, 47, 0, 13, 81, 105, 110, 100, 111, 107, 108, 195, 161, 115, 116, 32, 22, 66, 5, 160, 106, 86, 10, 6, 15, 107, 55, 89, 116, 0, 13, 81, 101, 108, 115, 197, 145, 32, 28, 66, 5, 160, 106, 86, 10, 6, 15, 37, 55, 12, 107, 47, 116, 47, 0, 13, 81, 105, 108, 108, 101, 116, 197, 145, 116, 32, 27, 66, 5, 160, 106, 86, 10, 6, 15, 107, 89, 107, 47, 69, 107, 50, 0, 13, 81, 101, 115, 101, 116, 98, 101, 110, 32, 27, 66, 5, 160, 106, 86, 10, 6, 15, 49, 107, 55, 12, 107, 50, 107, 0, 13, 81, 107, 101, 108, 108, 101, 110, 101, 32, 23, 66, 5, 160, 106, 86, 10, 6, 15, 112, 52, 112, 47, 0, 13, 81, 195, 161, 114, 195, 161, 116, 32, 34, 66, 5, 160, 106, 86, 10, 6, 15, 107, 87, 49, 108, 86, 108, 49, 107, 47, 0, 13, 81, 101, 115, 122, 107, 195, 182, 122, 195, 182, 107, 101, 116, 32, 22, 66, 5, 160, 106, 86, 10, 6, 15, 111, 82, 107, 47, 0, 13, 81, 195, 169, 118, 101, 116, 32, 22, 66, 5, 160, 106, 86, 10, 6, 15, 37, 70, 116, 47, 0, 13, 81, 105, 100, 197, 145, 116, 32, 24, 66, 5, 160, 106, 86, 10, 6, 15, 106, 6, 15, 69, 106, 57, 0, 13, 82, 97, 32, 98, 97, 106, 32, 21, 66, 5, 160, 106, 86, 10, 6, 15, 106, 70, 106, 47, 0, 13, 81, 97, 100, 97, 116, 32, 31, 66, 5, 160, 106, 86, 10, 6, 15, 39, 34, 87, 112, 79, 69, 106, 50, 0, 13, 81, 111, 114, 115, 122, 195, 161, 103, 98, 97, 110, 32, 23, 66, 5, 160, 106, 86, 10, 6, 15, 107, 55, 82, 107, 47, 0, 13, 81, 101, 108, 118, 101, 116, 32, 24, 66, 5, 160, 106, 86, 10, 6, 15, 111, 61, 57, 107, 55, 0, 13, 81, 195, 169, 106, 106, 101, 108, 32, 23, 66, 5, 160, 106, 86, 10, 6, 15, 106, 50, 79, 39, 55, 0, 13, 81, 97, 110, 103, 111, 108, 32, 34, 66, 5, 160, 106, 86, 10, 6, 15, 37, 50, 70, 110, 47, 82, 112, 65, 106, 0, 13, 81, 105, 110, 100, 195, 173, 116, 118, 195, 161, 110, 121, 97, 32, 25, 66, 5, 160, 106, 86, 10, 6, 15, 39, 55, 70, 106, 55, 47, 0, 13, 81, 111, 108, 100, 97, 108, 116, 32, 26, 66, 5, 160, 106, 86, 10, 6, 15, 109, 77, 52, 116, 55, 0, 13, 81, 195, 188, 103, 121, 114, 197, 145, 108, 32, 35, 66, 5, 160, 106, 86, 10, 6, 15, 107, 55, 50, 108, 49, 89, 111, 79, 107, 47, 0, 13, 81, 101, 108, 110, 195, 182, 107, 115, 195, 169, 103, 101, 116, 32, 36, 66, 5, 160, 106, 86, 10, 6, 15, 107, 77, 12, 107, 89, 109, 55, 107, 47, 107, 49, 0, 13, 81, 101, 103, 121, 101, 115, 195, 188, 108, 101, 116, 101, 107, 32, 39, 66, 5, 160, 106, 86, 10, 6, 15, 107, 55, 116, 52, 107, 57, 107, 55, 86, 111, 89, 107, 0, 13, 81, 101, 108, 197, 145, 114, 101, 106, 101, 108, 122, 195, 169, 115, 101, 32, 36, 66, 5, 160, 106, 86, 10, 6, 15, 37, 50, 47, 111, 86, 63, 111, 65, 107, 49, 0, 13, 81, 105, 110, 116, 195, 169, 122, 109, 195, 169, 110, 121, 101, 107, 32, 36, 66, 5, 160, 106, 86, 10, 6, 15, 37, 50, 70, 39, 49, 55, 112, 89, 12, 106, 55, 0, 13, 81, 105, 110, 100, 111, 107, 108, 195, 161, 115, 115, 97, 108, 32, 36, 66, 5, 160, 106, 86, 10, 6, 15, 112, 55, 12, 106, 48, 39, 47, 40, 49, 39, 50, 0, 13, 81, 195, 161, 108, 108, 97, 112, 111, 116, 117, 107, 111, 110, 32, 38, 66, 5, 160, 106, 86, 23, 89, 107, 63, 23, 87, 39, 49, 82, 112, 65, 39, 89, 0, 13, 82, 115, 101, 109, 32, 115, 122, 111, 107, 118, 195, 161, 110, 121, 111, 115, 32, 25, 66, 5, 160, 106, 86, 10, 6, 15, 109, 77, 69, 107, 50, 0, 13, 81, 195, 188, 103, 121, 98, 101, 110, 32, 41, 66, 5, 160, 106, 86, 10, 6, 15, 106, 55, 106, 48, 37, 55, 12, 107, 47, 63, 111, 65, 107, 0, 13, 81, 97, 108, 97, 112, 105, 108, 108, 101, 116, 109, 195, 169, 110, 121, 101, 32, 29, 66, 5, 160, 106, 86, 10, 6, 15, 37, 86, 79, 106, 55, 63, 106, 89, 0, 13, 81, 105, 122, 103, 97, 108, 109, 97, 115, 32, 30, 66, 5, 160, 106, 86, 23, 106, 6, 15, 49, 111, 52, 70, 111, 89, 0, 13, 82, 97, 32, 107, 195, 169, 114, 100, 195, 169, 115, 32, 34, 66, 5, 160, 106, 86, 23, 37, 50, 47, 111, 86, 107, 47, 107, 49, 107, 47, 0, 13, 81, 105, 110, 116, 195, 169, 122, 101, 116, 101, 107, 101, 116, 32, 21, 66, 5, 160, 106, 86, 23, 107, 55, 82, 107, 47, 0, 13, 81, 101, 108, 118, 101, 116, 32, 24, 66, 5, 160, 106, 86, 23, 111, 55, 107, 47, 107, 70, 0, 13, 81, 195, 169, 108, 101, 116, 101, 100, 32, 31, 66, 5, 160, 106, 86, 6, 23, 114, 57, 110, 47, 112, 89, 39, 49, 0, 13, 81, 195, 186, 106, 195, 173, 116, 195, 161, 115, 111, 107, 32, 31, 66, 5, 160, 106, 86, 6, 23, 112, 55, 12, 106, 48, 39, 47, 39, 63, 0, 13, 81, 195, 161, 108, 108, 97, 112, 111, 116, 111, 109, 32, 36, 66, 5, 160, 106, 86, 23, 37, 50, 47, 107, 52, 50, 107, 47, 107, 86, 111, 89, 0, 13, 81, 105, 110, 116, 101, 114, 110, 101, 116, 101, 122, 195, 169, 115, 32, 47, 66, 5, 160, 106, 86, 23, 106, 49, 106, 70, 112, 57, 63, 107, 50, 47, 107, 89, 110, 47, 111, 89, 0, 13, 81, 97, 107, 97, 100, 195, 161, 108, 121, 109, 101, 110, 116, 101, 115, 195, 173, 116, 195, 169, 115, 32, 35, 66, 5, 160, 106, 86, 10, 6, 15, 106, 6, 15, 48, 52, 39, 69, 55, 111, 63, 106, 0, 13, 82, 97, 32, 112, 114, 111, 98, 108, 195, 169, 109, 97, 32, 25, 66, 5, 160, 106, 86, 6, 15, 10, 111, 87, 106, 49, 37, 0, 13, 81, 195, 169, 115, 122, 97, 107, 105, 32, 18, 66, 5, 160, 106, 86, 23, 107, 89, 116, 0, 13, 81, 101, 115, 197, 145, 32, 17, 66, 5, 160, 106, 86, 23, 111, 4, 79, 0, 13, 81, 195, 169, 103, 32, 17, 66, 5, 160, 106, 86, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 22, 66, 5, 160, 106, 86, 23, 37, 50, 81, 113, 47, 0, 13, 81, 105, 110, 102, 195, 179, 116, 32, 15, 66, 5, 160, 106, 86, 15, 37, 89, 0, 13, 81, 105, 115, 32, 20, 66, 5, 160, 10, 106, 86, 15, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 9, 134, 20, 195, 161, 18, 15, 12, 13, 6, 194, 5, 160, 72, 12, 0, 15, 140, 19, 26, 195, 169, 12, 12, 195, 182, 11, 195, 169, 19, 13, 8, 133, 11, 195, 169, 19, 26, 13, 0, 11, 136, 3, 195, 169, 7, 195, 169, 18, 20, 13, 9, 134, 16, 195, 161, 18, 15, 14, 13, 14, 139, 22, 9, 26, 19, 7, 195, 161, 12, 1, 20, 1, 13, 0, 12, 137, 16, 195, 169, 12, 4, 195, 161, 21, 12, 13, 8, 133, 11, 195, 169, 19, 20, 13, 15, 69, 29, 145, 83, 21, 96, 77, 107, 89, 107, 82, 0, 42, 42, 0, 39, 70, 44, 83, 12, 21, 69, 0, 49, 107, 55, 12, 107, 47, 12, 23, 49, 106, 48, 74, 39, 55, 50, 39, 63, 0, 13, 81, 107, 97, 112, 99, 115, 111, 108, 110, 111, 109, 32, 29, 70, 44, 83, 12, 21, 69, 0, 49, 107, 55, 12, 107, 47, 12, 23, 106, 105, 39, 86, 0, 13, 81, 97, 104, 104, 111, 122, 32, 40, 70, 44, 83, 12, 21, 69, 0, 49, 107, 55, 12, 107, 47, 12, 23, 107, 55, 39, 55, 82, 106, 89, 50, 39, 63, 0, 13, 81, 101, 108, 111, 108, 118, 97, 115, 110, 111, 109, 32, 13, 138, 20, 195, 182, 13, 5, 7, 18, 197, 145, 12, 13, 9, 198, 44, 83, 12, 21, 69, 0, 13, 6, 131, 8, 195, 179, 13, 0, 10, 135, 20, 15, 10, 195, 161, 19, 20, 13, 29, 67, 5, 165, 0, 106, 87, 47, 10, 6, 15, 82, 112, 52, 57, 112, 49, 0, 13, 81, 118, 195, 161, 114, 106, 195, 161, 107, 32, 31, 67, 5, 165, 0, 106, 87, 47, 10, 6, 15, 87, 107, 52, 107, 47, 50, 111, 0, 13, 81, 115, 122, 101, 114, 101, 116, 110, 195, 169, 32, 27, 67, 5, 165, 0, 106, 87, 47, 10, 6, 15, 57, 107, 55, 86, 37, 49, 0, 13, 81, 106, 101, 108, 122, 105, 107, 32, 38, 67, 5, 165, 0, 106, 87, 47, 10, 6, 15, 77, 106, 50, 110, 47, 39, 47, 12, 112, 49, 0, 13, 81, 103, 121, 97, 110, 195, 173, 116, 111, 116, 116, 195, 161, 107, 32, 33, 67, 5, 165, 0, 106, 87, 47, 10, 6, 49, 111, 48, 82, 37, 89, 107, 55, 37, 0, 13, 81, 107, 195, 169, 112, 118, 105, 115, 101, 108, 105, 32, 37, 67, 5, 165, 0, 106, 87, 47, 6, 23, 106, 23, 105, 106, 77, 39, 63, 112, 65, 47, 0, 13, 82, 97, 32, 104, 97, 103, 121, 111, 109, 195, 161, 110, 121, 116, 32, 36, 67, 5, 165, 0, 106, 87, 47, 23, 47, 106, 48, 106, 87, 47, 106, 55, 47, 106, 63, 0, 13, 81, 116, 97, 112, 97, 115, 122, 116, 97, 108, 116, 97, 109, 32, 37, 67, 5, 165, 0, 106, 87, 47, 23, 47, 106, 50, 112, 74, 39, 57, 57, 57, 112, 49, 0, 13, 81, 116, 97, 110, 195, 161, 99, 115, 111, 108, 106, 195, 161, 107, 32, 56, 67, 5, 165, 0, 106, 87, 47, 23, 49, 111, 52, 47, 107, 23, 106, 86, 23, 112, 55, 12, 106, 63, 47, 37, 47, 49, 112, 52, 0, 13, 83, 107, 195, 169, 114, 116, 101, 32, 97, 122, 32, 195, 161, 108, 108, 97, 109, 116, 105, 116, 107, 195, 161, 114, 32, 14, 195, 5, 165, 0, 13, 81, 108, 195, 161, 116, 110, 105, 32, 10, 195, 5, 165, 0, 13, 81, 105, 115, 32, 6, 195, 5, 165, 0, 13, 12, 137, 6, 15, 12, 25, 1, 13, 195, 161, 14, 20, 0, 11, 200, 72, 83, 132, 20, 193, 84, 21, 64, 13, 25, 67, 96, 146, 73, 47, 37, 86, 107, 50, 105, 112, 52, 39, 63, 12, 106, 55, 0, 44, 42, 81, 97, 108, 32, 0, 12, 201, 56, 85, 133, 48, 177, 68, 21, 69, 0, 13, 16, 141, 8, 1, 10, 12, 195, 169, 11, 20, 1, 12, 1, 14, 20, 13, 0, 15, 66, 16, 80, 70, 107, 23, 106, 86, 0, 13, 81, 97, 122, 32, 6, 194, 16, 80, 76, 8, 0, 10, 135, 195, 173, 18, 195, 161, 19, 20, 13, 0, 14, 139, 22, 195, 161, 12, 1, 19, 26, 20, 1, 14, 9, 13, 7, 196, 5, 32, 78, 100, 13, 0, 8, 197, 24, 241, 213, 56, 176, 76, 11, 136, 20, 1, 12, 195, 161, 12, 14, 9, 13, 8, 197, 28, 243, 132, 40, 16, 13, 0, 10, 135, 22, 5, 18, 26, 9, 195, 179, 13, 21, 146, 11, 195, 182, 26, 2, 9, 26, 20, 15, 14, 19, 195, 161, 7, 195, 169, 18, 20, 13, 9, 198, 80, 149, 5, 44, 85, 0, 13, 0, 10, 199, 44, 20, 3, 76, 243, 14, 36, 13, 30, 7, 11, 5, 18, 195, 188, 12, 20, 49, 107, 52, 109, 55, 47, 23, 87, 113, 69, 106, 0, 13, 81, 115, 122, 195, 179, 98, 97, 32, 29, 7, 11, 5, 18, 195, 188, 12, 20, 49, 107, 52, 109, 55, 47, 23, 106, 105, 39, 86, 0, 13, 81, 97, 104, 104, 111, 122, 32, 10, 135, 11, 5, 18, 195, 188, 12, 20, 13, 14, 139, 22, 195, 161, 12, 20, 15, 26, 195, 161, 19, 20, 13, 10, 199, 48, 83, 69, 57, 65, 78, 36, 13, 10, 135, 11, 5, 18, 195, 188, 12, 20, 13, 25, 67, 96, 146, 64, 47, 37, 86, 107, 50, 49, 107, 47, 12, 116, 82, 107, 55, 0, 44, 42, 81, 101, 108, 32, 0, 22, 68, 20, 65, 9, 28, 107, 70, 12, 37, 79, 23, 89, 107, 63, 0, 13, 81, 115, 101, 109, 32, 11, 136, 9, 4, 195, 169, 26, 5, 20, 20, 13, 15, 204, 24, 145, 217, 20, 195, 69, 105, 65, 84, 21, 69, 0, 13, 7, 196, 88, 83, 142, 36, 13, 7, 196, 88, 147, 142, 36, 13, 12, 4, 95, 4, 16, 20, 15, 107, 79, 111, 87, 0, 0, 8, 197, 104, 18, 140, 36, 176, 13, 15, 140, 13, 5, 7, 11, 195, 188, 26, 4, 5, 14, 9, 5, 13, 47, 14, 14, 25, 9, 12, 22, 195, 161, 14, 15, 19, 19, 195, 161, 7, 65, 37, 55, 82, 112, 50, 39, 89, 12, 112, 79, 23, 87, 112, 63, 112, 52, 106, 0, 13, 81, 115, 122, 195, 161, 109, 195, 161, 114, 97, 32, 12, 201, 8, 148, 218, 80, 244, 207, 44, 21, 0, 13, 8, 197, 52, 83, 142, 20, 176, 13, 11, 136, 20, 195, 169, 13, 195, 161, 18, 1, 13, 12, 201, 52, 81, 207, 48, 64, 78, 84, 226, 192, 13, 8, 197, 32, 148, 218, 20, 208, 13, 15, 4, 95, 49, 48, 17, 47, 37, 86, 107, 70, 37, 49, 107, 0, 0, 32, 11, 13, 5, 7, 15, 12, 4, 8, 1, 20, 195, 179, 63, 107, 79, 39, 55, 70, 105, 106, 47, 113, 23, 106, 86, 0, 13, 81, 97, 122, 32, 13, 138, 195, 169, 18, 20, 5, 19, 195, 188, 12, 20, 13, 9, 198, 52, 17, 213, 44, 21, 0, 13, 5, 194, 21, 48, 72, 0, 39, 67, 56, 83, 64, 50, 107, 63, 23, 57, 107, 55, 107, 50, 47, 23, 89, 107, 63, 12, 37, 47, 0, 13, 82, 106, 101, 108, 101, 110, 116, 32, 115, 101, 109, 109, 105, 116, 32, 31, 71, 56, 147, 131, 76, 83, 133, 44, 50, 37, 50, 74, 107, 50, 107, 49, 23, 52, 113, 55, 106, 0, 13, 81, 114, 195, 179, 108, 97, 32, 12, 137, 195, 188, 12, 195, 169, 19, 195, 169, 14, 13, 47, 67, 56, 83, 64, 50, 107, 63, 23, 82, 39, 55, 47, 23, 47, 37, 87, 47, 107, 89, 12, 111, 79, 107, 89, 0, 13, 82, 118, 111, 108, 116, 32, 116, 105, 115, 122, 116, 101, 115, 115, 195, 169, 103, 101, 115, 32, 24, 67, 56, 83, 64, 50, 107, 63, 23, 55, 112, 47, 12, 106, 0, 13, 81, 108, 195, 161, 116, 116, 97, 32, 21, 67, 56, 83, 64, 50, 107, 63, 23, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 44, 67, 56, 83, 64, 50, 107, 63, 23, 63, 39, 86, 79, 106, 47, 12, 106, 23, 47, 39, 82, 112, 69, 12, 0, 13, 82, 109, 111, 122, 103, 97, 116, 116, 97, 32, 116, 111, 118, 195, 161, 98, 98, 32, 14, 203, 77, 161, 82, 88, 86, 133, 80, 82, 206, 20, 176, 13, 20, 67, 56, 83, 64, 50, 107, 63, 23, 55, 107, 87, 0, 13, 81, 108, 101, 115, 122, 32, 40, 67, 56, 83, 64, 50, 107, 63, 15, 63, 107, 52, 47, 107, 63, 15, 55, 107, 110, 52, 50, 37, 0, 13, 82, 109, 101, 114, 116, 101, 109, 32, 108, 101, 195, 173, 114, 110, 105, 32, 14, 139, 18, 195, 169, 19, 26, 5, 19, 195, 188, 12, 20, 13, 10, 135, 195, 169, 16, 195, 188, 12, 20, 13, 7, 195, 56, 83, 64, 102, 12, 8, 195, 56, 83, 64, 12, 23, 22, 15, 8, 95, 35, 45, 195, 161, 14, 1, 11, 112, 50, 106, 49, 0, 0, 14, 139, 20, 1, 18, 20, 1, 12, 13, 195, 161, 18, 1, 13, 14, 139, 11, 195, 169, 18, 5, 12, 13, 195, 169, 18, 5, 13, 0, 15, 140, 9, 11, 15, 14, 20, 195, 169, 13, 195, 161, 18, 1, 13, 12, 201, 77, 161, 82, 88, 86, 133, 81, 65, 76, 13, 0, 9, 134, 195, 188, 12, 197, 145, 20, 13, 12, 137, 20, 195, 161, 12, 3, 195, 161, 18, 1, 13, 9, 198, 80, 85, 19, 104, 85, 20, 13, 0, 47, 67, 88, 85, 20, 82, 107, 47, 12, 23, 106, 23, 47, 112, 34, 77, 106, 55, 112, 89, 39, 49, 69, 106, 50, 0, 13, 82, 97, 32, 116, 195, 161, 114, 103, 121, 97, 108, 195, 161, 115, 111, 107, 98, 97, 110, 32, 8, 133, 14, 25, 195, 161, 18, 13, 6, 195, 88, 85, 20, 13, 8, 133, 14, 25, 195, 161, 18, 20, 14, 4, 95, 49, 48, 15, 47, 37, 86, 107, 70, 37, 49, 0, 0, 17, 142, 6, 5, 10, 12, 5, 19, 26, 20, 195, 169, 19, 195, 169, 14, 13, 17, 142, 22, 9, 19, 5, 12, 11, 5, 4, 195, 169, 19, 195, 169, 14, 13, 18, 143, 9, 14, 20, 195, 169, 26, 13, 195, 169, 14, 25, 5, 11, 2, 5, 13, 0, 17, 142, 22, 15, 14, 21, 12, 8, 1, 20, 14, 195, 161, 14, 1, 11, 13, 12, 137, 22, 9, 12, 195, 161, 7, 195, 161, 20, 13, 12, 201, 44, 145, 133, 41, 65, 84, 80, 83, 64, 13, 13, 138, 12, 195, 161, 20, 19, 26, 1, 14, 1, 11, 13, 17, 10, 95, 35, 45, 9, 11, 195, 169, 14, 5, 11, 111, 50, 107, 49, 0, 0, 29, 10, 15, 12, 3, 19, 195, 179, 2, 2, 1, 20, 39, 55, 74, 113, 69, 12, 106, 47, 23, 37, 89, 0, 13, 81, 105, 115, 32, 20, 145, 13, 5, 7, 195, 161, 12, 12, 195, 173, 20, 195, 161, 19, 195, 161, 18, 1, 13, 13, 138, 20, 1, 7, 19, 195, 161, 7, 195, 161, 20, 13, 9, 198, 52, 243, 132, 80, 19, 64, 13, 0, 14, 139, 11, 18, 9, 20, 9, 11, 195, 161, 11, 1, 20, 13, 9, 198, 24, 18, 193, 17, 64, 77, 13, 10, 135, 11, 195, 169, 16, 5, 9, 20, 13, 0, 14, 139, 195, 188, 26, 5, 13, 5, 12, 20, 5, 20, 9, 13, 23, 67, 61, 36, 129, 39, 52, 52, 106, 10, 6, 15, 106, 55, 112, 0, 13, 81, 97, 108, 195, 161, 32, 16, 141, 1, 12, 11, 15, 20, 13, 195, 161, 14, 25, 14, 1, 11, 13, 9, 3, 95, 35, 57, 47, 106, 69, 0, 12, 4, 95, 20, 12, 4, 47, 37, 55, 70, 107, 0, 0, 15, 140, 195, 186, 10, 18, 1, 195, 173, 18, 195, 161, 19, 1, 13, 0, 0, 17, 142, 22, 195, 169, 12, 5, 13, 195, 169, 14, 25, 5, 26, 14, 9, 13, 8, 133, 15, 11, 195, 161, 14, 13, 13, 138, 8, 1, 20, 195, 161, 18, 15, 26, 14, 9, 13, 11, 67, 4, 197, 0, 106, 55, 47, 0, 42, 42, 0, 23, 68, 76, 147, 131, 76, 89, 37, 50, 74, 15, 79, 39, 50, 70, 0, 13, 81, 103, 111, 110, 100, 32, 37, 68, 76, 147, 131, 76, 89, 37, 50, 74, 23, 107, 77, 12, 107, 47, 111, 52, 47, 111, 89, 0, 13, 81, 101, 103, 121, 101, 116, 195, 169, 114, 116, 195, 169, 115, 32, 11, 136, 19, 26, 15, 12, 7, 195, 161, 12, 13, 14, 139, 8, 5, 12, 25, 5, 26, 8, 5, 20, 197, 145, 13, 7, 196, 76, 147, 131, 76, 13, 7, 132, 197, 145, 18, 20, 13, 7, 132, 195, 161, 18, 20, 13, 7, 196, 72, 244, 211, 104, 13, 0, 19, 144, 11, 195, 182, 18, 2, 5, 10, 195, 161, 20, 19, 26, 195, 161, 19, 1, 13, 15, 140, 11, 9, 20, 195, 182, 12, 20, 8, 5, 20, 197, 145, 13, 0, 11, 136, 3, 195, 173, 13, 5, 11, 5, 14, 13, 9, 134, 7, 25, 195, 186, 10, 20, 13, 5, 194, 21, 64, 13, 0, 21, 67, 17, 97, 0, 100, 195, 169, 118, 195, 169, 100, 195, 169, 109, 0, 44, 29, 81, 109, 32, 22, 67, 17, 97, 0, 100, 195, 169, 118, 195, 169, 100, 195, 169, 116, 0, 44, 29, 42, 81, 109, 32, 22, 67, 17, 97, 0, 100, 195, 169, 118, 195, 169, 100, 195, 169, 100, 0, 44, 29, 42, 81, 100, 32, 21, 67, 17, 97, 0, 100, 195, 169, 118, 195, 169, 100, 195, 169, 100, 0, 44, 29, 81, 100, 32, 21, 67, 17, 97, 0, 100, 195, 169, 118, 195, 169, 100, 195, 169, 110, 0, 44, 29, 81, 110, 32, 22, 67, 17, 97, 0, 100, 195, 169, 118, 195, 169, 100, 195, 169, 110, 0, 44, 29, 42, 81, 110, 32, 21, 67, 17, 97, 0, 100, 195, 169, 118, 195, 169, 100, 195, 169, 107, 0, 44, 29, 81, 107, 32, 22, 67, 17, 97, 0, 100, 195, 169, 118, 195, 169, 100, 195, 169, 107, 0, 44, 29, 42, 81, 107, 32, 43, 8, 8, 195, 188, 22, 5, 12, 25, 11, 105, 109, 82, 107, 57, 49, 10, 6, 15, 112, 47, 63, 111, 52, 116, 57, 115, 0, 13, 81, 195, 161, 116, 109, 195, 169, 114, 197, 145, 106, 197, 177, 32, 16, 141, 195, 161, 12, 12, 1, 13, 20, 9, 20, 11, 195, 161, 18, 13, 0, 16, 141, 20, 5, 18, 22, 5, 26, 8, 5, 20, 195, 188, 14, 11, 13, 18, 143, 8, 15, 26, 26, 195, 161, 6, 195, 169, 18, 8, 5, 20, 197, 145, 13, 11, 136, 9, 18, 195, 161, 14, 25, 21, 12, 13, 0, 0, 9, 198, 40, 241, 207, 77, 83, 20, 13, 13, 202, 4, 194, 193, 48, 208, 90, 104, 19, 129, 44, 13, 13, 138, 10, 195, 182, 22, 197, 145, 18, 197, 145, 12, 13, 14, 5, 95, 50, 77, 49, 5, 49, 111, 47, 107, 86, 52, 0, 0, 9, 134, 6, 197, 177, 26, 14, 9, 13, 0, 0, 6, 195, 36, 112, 90, 13, 0, 12, 137, 11, 195, 182, 26, 195, 182, 12, 14, 9, 13, 16, 141, 20, 1, 14, 20, 5, 19, 20, 195, 188, 12, 5, 20, 5, 13, 12, 137, 195, 161, 20, 14, 195, 169, 26, 14, 9, 13, 11, 5, 95, 48, 77, 49, 5, 107, 86, 52, 0, 0, 24, 67, 20, 118, 64, 107, 77, 23, 49, 37, 89, 12, 107, 69, 0, 13, 81, 107, 105, 115, 101, 98, 98, 32, 28, 67, 20, 118, 64, 107, 77, 10, 6, 15, 48, 52, 113, 69, 112, 47, 0, 13, 81, 112, 114, 195, 179, 98, 195, 161, 116, 32, 35, 67, 20, 118, 64, 107, 77, 10, 6, 15, 81, 39, 79, 106, 70, 112, 89, 40, 50, 49, 0, 13, 81, 102, 111, 103, 97, 100, 195, 161, 115, 117, 110, 107, 32, 37, 67, 20, 118, 64, 107, 77, 23, 105, 106, 57, 55, 111, 49, 47, 106, 55, 106, 50, 47, 0, 13, 81, 104, 97, 106, 108, 195, 169, 107, 116, 97, 108, 97, 110, 116, 32, 27, 67, 20, 118, 64, 107, 77, 23, 81, 113, 52, 40, 63, 39, 50, 0, 13, 81, 102, 195, 179, 114, 117, 109, 111, 110, 32, 9, 198, 52, 147, 132, 20, 226, 201, 13, 23, 67, 20, 118, 64, 107, 77, 10, 6, 15, 70, 37, 112, 49, 0, 13, 81, 100, 105, 195, 161, 107, 32, 25, 67, 20, 118, 64, 107, 77, 10, 6, 15, 81, 111, 52, 81, 37, 0, 13, 81, 102, 195, 169, 114, 102, 105, 32, 32, 67, 20, 118, 64, 107, 77, 23, 81, 107, 55, 63, 111, 52, 111, 89, 47, 0, 13, 81, 102, 101, 108, 109, 195, 169, 114, 195, 169, 115, 116, 32, 29, 67, 20, 118, 64, 107, 77, 23, 87, 39, 81, 47, 82, 107, 52, 47, 0, 13, 81, 115, 122, 111, 102, 116, 118, 101, 114, 116, 32, 38, 67, 20, 118, 64, 107, 77, 23, 110, 52, 112, 89, 47, 40, 70, 106, 47, 55, 106, 50, 0, 13, 81, 195, 173, 114, 195, 161, 115, 116, 117, 100, 97, 116, 108, 97, 110, 32, 22, 67, 20, 118, 64, 107, 77, 23, 37, 70, 107, 37, 79, 0, 13, 81, 105, 100, 101, 105, 103, 32, 23, 67, 20, 118, 64, 107, 77, 23, 79, 111, 48, 107, 47, 0, 13, 81, 103, 195, 169, 112, 101, 116, 32, 33, 67, 20, 118, 64, 107, 77, 23, 87, 106, 69, 106, 70, 50, 106, 48, 52, 106, 0, 13, 81, 115, 122, 97, 98, 97, 100, 110, 97, 112, 114, 97, 32, 10, 135, 11, 195, 169, 16, 5, 19, 20, 13, 6, 195, 20, 118, 64, 13, 0, 49, 12, 19, 26, 5, 18, 26, 197, 145, 4, 195, 169, 19, 20, 87, 107, 52, 86, 116, 70, 111, 89, 47, 23, 49, 107, 55, 12, 23, 49, 108, 47, 50, 37, 0, 13, 82, 107, 101, 108, 108, 32, 107, 195, 182, 116, 110, 105, 32, 11, 200, 65, 35, 198, 21, 52, 218, 61, 32, 13, 19, 144, 9, 14, 6, 15, 18, 13, 195, 161, 3, 9, 195, 179, 195, 169, 18, 20, 13, 15, 140, 19, 26, 5, 18, 26, 197, 145, 4, 195, 169, 19, 20, 13, 7, 196, 4, 227, 129, 44, 13, 0, 8, 197, 81, 81, 21, 56, 176, 76, 30, 6, 6, 15, 12, 25, 195, 179, 81, 39, 57, 113, 15, 82, 107, 52, 89, 107, 65, 0, 13, 81, 118, 101, 114, 115, 101, 110, 121, 32, 13, 138, 20, 195, 161, 18, 19, 1, 19, 195, 161, 7, 13, 8, 197, 48, 18, 212, 4, 176, 13, 0, 9, 198, 52, 147, 132, 20, 118, 64, 13, 42, 10, 13, 5, 7, 15, 12, 4, 195, 161, 19, 20, 63, 107, 79, 39, 55, 70, 112, 89, 47, 23, 111, 48, 110, 47, 23, 69, 107, 0, 13, 82, 195, 169, 112, 195, 173, 116, 32, 98, 101, 32, 23, 70, 32, 83, 25, 104, 85, 0, 105, 107, 57, 86, 107, 47, 23, 106, 86, 0, 13, 81, 97, 122, 32, 9, 198, 44, 244, 146, 20, 181, 0, 13, 9, 198, 32, 83, 25, 104, 85, 0, 13, 13, 138, 13, 5, 7, 15, 12, 4, 195, 161, 19, 20, 13, 16, 67, 61, 33, 139, 39, 107, 51, 107, 81, 49, 112, 0, 17, 42, 42, 0, 10, 135, 18, 5, 16, 195, 188, 12, 20, 13, 8, 133, 7, 25, 197, 145, 26, 13, 10, 135, 14, 195, 169, 26, 5, 20, 20, 13, 0, 11, 136, 195, 161, 20, 195, 161, 12, 12, 20, 13, 11, 136, 22, 195, 169, 7, 26, 5, 20, 20, 13, 11, 136, 22, 195, 169, 7, 26, 5, 20, 20, 13, 15, 140, 5, 12, 4, 15, 2, 195, 161, 12, 195, 161, 19, 20, 13, 7, 196, 80, 82, 5, 72, 13, 10, 135, 13, 21, 14, 11, 195, 161, 13, 13, 7, 196, 16, 240, 142, 36, 13, 18, 5, 95, 50, 77, 49, 15, 49, 111, 47, 107, 86, 52, 107, 70, 37, 49, 0, 0, 27, 8, 20, 195, 182, 12, 20, 19, 5, 13, 47, 108, 55, 74, 107, 63, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 8, 197, 80, 84, 150, 20, 176, 13, 12, 137, 16, 18, 15, 4, 21, 11, 195, 161, 12, 13, 8, 197, 52, 83, 142, 36, 80, 13, 12, 201, 77, 160, 75, 20, 208, 133, 72, 82, 64, 13, 8, 133, 13, 195, 186, 12, 20, 13, 0, 14, 66, 21, 80, 101, 117, 110, 0, 44, 29, 42, 81, 110, 32, 12, 137, 3, 19, 9, 18, 11, 195, 169, 18, 5, 13, 22, 147, 19, 26, 15, 6, 20, 22, 5, 18, 6, 5, 10, 12, 5, 19, 26, 20, 197, 145, 11, 13, 9, 198, 80, 20, 148, 84, 226, 192, 13, 0, 18, 143, 2, 5, 18, 5, 14, 4, 5, 26, 11, 5, 4, 195, 169, 19, 20, 13, 9, 134, 2, 195, 173, 26, 14, 1, 13, 52, 10, 13, 5, 7, 15, 12, 4, 195, 161, 19, 9, 63, 107, 79, 39, 55, 70, 112, 89, 37, 23, 55, 107, 105, 107, 47, 116, 89, 111, 79, 12, 107, 55, 0, 13, 81, 108, 101, 104, 101, 116, 197, 145, 115, 195, 169, 103, 103, 101, 108, 32, 9, 134, 10, 195, 179, 11, 1, 9, 13, 10, 135, 12, 195, 169, 16, 5, 20, 20, 13, 0, 33, 11, 22, 1, 12, 195, 179, 19, 195, 173, 20, 10, 1, 82, 106, 55, 113, 89, 110, 78, 12, 106, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 19, 144, 8, 15, 26, 26, 195, 161, 10, 195, 161, 18, 21, 12, 195, 161, 19, 20, 13, 40, 8, 13, 9, 5, 12, 197, 145, 20, 20, 63, 37, 107, 55, 116, 47, 12, 23, 81, 39, 57, 47, 106, 47, 50, 112, 0, 13, 81, 102, 111, 108, 121, 116, 97, 116, 110, 195, 161, 32, 11, 200, 44, 146, 133, 48, 83, 148, 36, 176, 13, 14, 139, 20, 1, 18, 20, 195, 161, 19, 195, 161, 18, 1, 13, 0, 28, 8, 20, 1, 12, 195, 161, 12, 10, 1, 47, 106, 55, 112, 55, 57, 106, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 15, 140, 9, 14, 4, 21, 12, 195, 161, 19, 195, 161, 18, 1, 13, 30, 9, 11, 195, 182, 22, 5, 20, 5, 20, 20, 49, 108, 82, 107, 47, 107, 47, 12, 10, 6, 15, 107, 55, 0, 13, 81, 101, 108, 32, 12, 137, 11, 195, 182, 22, 5, 20, 5, 20, 20, 13, 12, 137, 195, 169, 18, 9, 14, 20, 5, 20, 20, 13, 0, 20, 5, 195, 161, 6, 195, 161, 195, 161, 102, 195, 161, 116, 0, 44, 29, 42, 81, 116, 32, 13, 138, 4, 195, 169, 12, 5, 12, 197, 145, 20, 20, 22, 0, 39, 7, 13, 21, 14, 11, 195, 161, 20, 63, 40, 50, 49, 112, 47, 10, 6, 15, 82, 111, 79, 107, 87, 47, 107, 49, 0, 13, 81, 118, 195, 169, 103, 101, 122, 116, 101, 107, 32, 26, 7, 13, 21, 14, 11, 195, 161, 20, 63, 40, 50, 49, 112, 47, 23, 37, 47, 12, 0, 13, 81, 105, 116, 116, 32, 14, 139, 11, 195, 173, 22, 195, 188, 12, 18, 197, 145, 12, 13, 10, 135, 20, 9, 20, 11, 195, 161, 20, 13, 10, 135, 13, 21, 14, 11, 195, 161, 20, 13, 12, 137, 16, 195, 169, 14, 20, 5, 11, 5, 14, 22, 0, 35, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 23, 87, 112, 63, 110, 47, 106, 50, 37, 0, 13, 81, 115, 122, 195, 161, 109, 195, 173, 116, 97, 110, 105, 32, 38, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 23, 106, 49, 106, 70, 112, 57, 39, 86, 50, 37, 0, 13, 81, 97, 107, 97, 100, 195, 161, 108, 121, 111, 122, 110, 105, 32, 18, 143, 6, 5, 14, 14, 20, 1, 18, 20, 195, 161, 19, 195, 161, 18, 1, 13, 25, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 23, 111, 52, 50, 37, 0, 13, 81, 195, 169, 114, 110, 105, 32, 41, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 10, 6, 15, 47, 40, 70, 50, 37, 10, 6, 15, 51, 113, 55, 106, 0, 13, 82, 116, 117, 100, 110, 105, 32, 114, 195, 179, 108, 97, 32, 33, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 10, 6, 15, 37, 89, 63, 107, 52, 116, 89, 0, 13, 81, 105, 115, 109, 101, 114, 197, 145, 115, 32, 28, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 10, 6, 15, 82, 107, 50, 12, 37, 0, 13, 81, 118, 101, 110, 110, 105, 32, 34, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 10, 6, 15, 63, 106, 34, 49, 39, 55, 50, 37, 0, 13, 81, 109, 97, 114, 107, 111, 108, 110, 105, 32, 36, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 10, 6, 15, 57, 107, 55, 107, 50, 47, 107, 50, 37, 0, 13, 81, 106, 101, 108, 101, 110, 116, 101, 110, 105, 32, 26, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 23, 107, 86, 86, 107, 55, 0, 13, 81, 101, 122, 122, 101, 108, 32, 34, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 23, 105, 106, 87, 50, 112, 55, 50, 37, 0, 13, 81, 104, 97, 115, 122, 110, 195, 161, 108, 110, 105, 32, 36, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 23, 106, 86, 10, 6, 15, 109, 77, 69, 107, 50, 0, 13, 82, 97, 122, 32, 195, 188, 103, 121, 98, 101, 110, 32, 27, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 23, 50, 111, 86, 50, 37, 0, 13, 81, 110, 195, 169, 122, 110, 105, 32, 32, 68, 48, 82, 5, 80, 55, 107, 105, 107, 47, 23, 74, 106, 48, 106, 70, 111, 49, 0, 13, 81, 99, 115, 97, 112, 97, 100, 195, 169, 107, 32, 7, 196, 80, 82, 5, 80, 13, 11, 136, 4, 195, 173, 10, 1, 11, 1, 20, 13, 7, 196, 88, 83, 5, 16, 13, 7, 196, 48, 82, 5, 80, 13, 14, 139, 195, 169, 10, 19, 26, 1, 11, 195, 161, 18, 1, 22, 0, 11, 136, 20, 1, 18, 20, 195, 161, 19, 1, 13, 0, 39, 9, 15, 12, 22, 1, 19, 195, 161, 19, 1, 39, 55, 82, 106, 89, 112, 89, 106, 10, 6, 15, 49, 108, 86, 69, 107, 50, 0, 13, 81, 107, 195, 182, 122, 98, 101, 110, 32, 14, 139, 6, 15, 18, 4, 195, 173, 20, 19, 195, 161, 11, 13, 13, 138, 20, 1, 14, 195, 161, 3, 19, 195, 161, 20, 13, 0, 14, 139, 20, 5, 18, 13, 195, 169, 11, 5, 11, 5, 20, 13, 5, 194, 4, 224, 72, 15, 66, 28, 32, 79, 37, 79, 106, 69, 112, 57, 47, 0, 42, 42, 0, 15, 140, 13, 195, 161, 19, 15, 4, 16, 5, 18, 3, 5, 20, 13, 12, 137, 5, 19, 5, 4, 195, 169, 11, 5, 19, 13, 6, 195, 72, 82, 148, 13, 6, 195, 24, 80, 128, 20, 0, 12, 137, 12, 195, 169, 22, 197, 145, 11, 5, 20, 13, 11, 136, 195, 169, 18, 26, 195, 169, 19, 5, 13, 7, 196, 20, 130, 5, 104, 13, 16, 141, 19, 26, 195, 161, 26, 1, 12, 195, 169, 11, 195, 161, 20, 13, 7, 196, 12, 83, 12, 4, 13, 15, 140, 2, 5, 14, 25, 195, 186, 10, 20, 195, 161, 19, 1, 13, 0, 12, 137, 6, 5, 12, 5, 12, 197, 145, 19, 5, 13, 24, 5, 11, 195, 182, 26, 20, 49, 108, 87, 47, 15, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 9, 198, 61, 54, 148, 61, 163, 137, 13, 17, 142, 11, 195, 169, 16, 22, 9, 19, 5, 12, 197, 145, 11, 5, 20, 13, 11, 136, 20, 18, 195, 161, 7, 195, 161, 18, 13, 9, 134, 22, 195, 169, 12, 5, 13, 13, 9, 133, 11, 195, 182, 26, 20, 13, 22, 8, 133, 7, 195, 161, 26, 20, 13, 0, 14, 139, 195, 182, 19, 19, 26, 5, 7, 5, 11, 5, 20, 13, 18, 143, 11, 195, 169, 19, 26, 195, 188, 12, 195, 169, 11, 5, 11, 5, 20, 13, 14, 139, 22, 195, 161, 12, 1, 19, 26, 15, 11, 1, 20, 13, 14, 139, 195, 169, 18, 20, 195, 169, 11, 5, 11, 5, 20, 13, 6, 195, 32, 144, 129, 13, 11, 136, 195, 161, 16, 18, 9, 12, 9, 19, 20, 0, 15, 140, 8, 1, 12, 12, 7, 1, 20, 195, 179, 11, 1, 20, 13, 55, 12, 19, 26, 1, 14, 11, 3, 9, 195, 179, 11, 1, 20, 87, 106, 50, 49, 117, 37, 113, 49, 106, 47, 15, 106, 55, 49, 106, 55, 63, 106, 86, 86, 106, 50, 106, 49, 0, 13, 81, 97, 108, 107, 97, 108, 109, 97, 122, 122, 97, 110, 97, 107, 32, 14, 139, 7, 25, 197, 145, 26, 11, 195, 182, 4, 14, 9, 13, 10, 199, 72, 83, 132, 77, 161, 82, 20, 13, 15, 140, 8, 5, 12, 25, 19, 195, 169, 7, 5, 11, 5, 20, 13, 11, 67, 80, 16, 128, 47, 106, 69, 0, 42, 42, 0, 20, 145, 16, 1, 18, 1, 14, 3, 19, 14, 15, 11, 19, 195, 161, 7, 195, 161, 20, 13, 7, 196, 4, 66, 143, 56, 13, 36, 68, 24, 18, 148, 4, 81, 106, 57, 47, 106, 23, 57, 106, 82, 110, 47, 112, 89, 39, 49, 0, 13, 81, 106, 97, 118, 195, 173, 116, 195, 161, 115, 111, 107, 32, 11, 200, 8, 150, 129, 48, 243, 77, 4, 192, 13, 12, 137, 195, 169, 18, 20, 5, 20, 20, 5, 13, 13, 7, 196, 13, 49, 82, 20, 13, 6, 195, 80, 19, 139, 13, 7, 196, 72, 243, 131, 76, 13, 0, 11, 136, 14, 195, 169, 26, 14, 195, 169, 11, 13, 13, 138, 19, 26, 195, 188, 12, 5, 20, 20, 5, 13, 13, 9, 134, 195, 169, 18, 20, 5, 13, 13, 17, 142, 14, 5, 8, 195, 169, 26, 19, 195, 169, 7, 5, 11, 5, 20, 13, 0, 22, 66, 25, 64, 81, 39, 52, 37, 50, 47, 12, 113, 55, 0, 44, 13, 81, 116, 195, 179, 108, 32, 21, 66, 25, 64, 81, 39, 52, 37, 50, 47, 50, 106, 49, 0, 44, 13, 81, 110, 97, 107, 32, 19, 66, 25, 64, 81, 39, 52, 37, 50, 47, 69, 106, 0, 44, 13, 81, 98, 97, 32, 19, 66, 25, 64, 81, 39, 52, 37, 50, 47, 39, 47, 0, 44, 13, 81, 111, 116, 32, 21, 66, 25, 64, 81, 39, 52, 37, 50, 47, 12, 106, 55, 0, 44, 13, 81, 116, 97, 108, 32, 12, 66, 25, 64, 81, 39, 52, 37, 50, 47, 0, 13, 31, 6, 5, 19, 195, 169, 10, 20, 107, 89, 111, 57, 47, 10, 6, 15, 55, 112, 47, 39, 49, 0, 13, 81, 108, 195, 161, 116, 111, 107, 32, 0, 11, 136, 3, 195, 173, 13, 5, 26, 20, 5, 13, 10, 199, 88, 19, 1, 44, 147, 133, 44, 13, 9, 134, 195, 169, 18, 4, 5, 11, 13, 0, 8, 133, 4, 195, 169, 12, 9, 13, 11, 200, 77, 162, 210, 37, 5, 2, 20, 224, 13, 16, 141, 20, 5, 12, 5, 16, 195, 173, 20, 5, 20, 20, 5, 13, 13, 7, 196, 4, 67, 137, 4, 13, 0, 8, 197, 36, 225, 21, 49, 64, 13, 6, 195, 77, 163, 210, 72, 0, 22, 147, 11, 195, 182, 20, 5, 12, 5, 26, 5, 20, 20, 19, 195, 169, 7, 5, 11, 5, 20, 13, 12, 137, 20, 195, 161, 13, 1, 4, 20, 1, 11, 13, 37, 5, 5, 12, 195, 169, 7, 107, 55, 111, 79, 15, 81, 37, 77, 107, 55, 63, 107, 89, 107, 50, 0, 13, 81, 102, 105, 103, 121, 101, 108, 109, 101, 115, 101, 110, 32, 8, 133, 5, 12, 195, 169, 7, 13, 9, 134, 22, 195, 169, 12, 5, 4, 13, 0, 13, 138, 19, 26, 195, 188, 12, 5, 20, 20, 5, 11, 13, 12, 201, 65, 32, 75, 80, 146, 213, 76, 16, 130, 13, 0, 17, 67, 13, 48, 75, 74, 106, 49, 23, 49, 37, 0, 13, 81, 107, 105, 32, 31, 67, 13, 48, 75, 74, 106, 49, 10, 6, 15, 63, 107, 79, 47, 107, 50, 12, 37, 0, 13, 81, 109, 101, 103, 116, 101, 110, 110, 105, 32, 18, 143, 13, 15, 18, 6, 15, 14, 4, 195, 173, 18, 15, 26, 20, 1, 11, 13, 27, 67, 13, 48, 75, 74, 106, 49, 23, 49, 111, 89, 116, 69, 12, 0, 13, 81, 107, 195, 169, 115, 197, 145, 98, 98, 32, 23, 67, 13, 48, 75, 74, 106, 49, 23, 106, 49, 12, 39, 52, 0, 13, 81, 97, 107, 107, 111, 114, 32, 23, 67, 13, 48, 75, 74, 106, 49, 23, 55, 107, 105, 107, 47, 0, 13, 81, 108, 101, 104, 101, 116, 32, 7, 196, 64, 84, 131, 20, 13, 12, 137, 19, 5, 7, 195, 173, 20, 5, 14, 9, 13, 10, 135, 195, 186, 10, 19, 195, 161, 7, 13, 16, 141, 8, 1, 14, 7, 19, 195, 186, 12, 25, 15, 26, 20, 1, 13, 10, 135, 6, 1, 11, 1, 4, 195, 179, 13, 14, 139, 9, 14, 4, 195, 173, 20, 15, 20, 20, 1, 11, 13, 6, 195, 13, 48, 75, 13, 0, 9, 134, 2, 195, 173, 26, 14, 9, 13, 8, 197, 52, 240, 137, 49, 64, 13, 6, 195, 13, 48, 74, 13, 0, 14, 139, 20, 1, 11, 1, 18, 195, 173, 20, 1, 14, 9, 13, 16, 141, 11, 195, 169, 19, 26, 195, 173, 20, 5, 20, 20, 5, 11, 13, 16, 141, 19, 26, 195, 161, 13, 195, 173, 20, 15, 20, 20, 1, 11, 13, 19, 66, 32, 16, 105, 106, 23, 49, 107, 55, 12, 0, 13, 81, 107, 101, 108, 108, 32, 14, 139, 11, 195, 169, 19, 26, 195, 173, 20, 5, 14, 9, 13, 9, 134, 195, 169, 18, 20, 5, 4, 13, 6, 194, 32, 16, 72, 8, 0, 20, 67, 24, 83, 0, 81, 107, 55, 10, 6, 15, 52, 112, 0, 13, 81, 114, 195, 161, 32, 30, 67, 24, 83, 0, 81, 107, 55, 23, 106, 6, 15, 89, 39, 52, 69, 106, 50, 0, 13, 82, 97, 32, 115, 111, 114, 98, 97, 110, 32, 15, 140, 5, 12, 8, 195, 161, 18, 195, 173, 20, 1, 14, 9, 13, 30, 67, 24, 83, 0, 81, 107, 55, 23, 106, 23, 55, 107, 82, 107, 79, 116, 0, 13, 82, 97, 32, 108, 101, 118, 101, 103, 197, 145, 32, 15, 140, 2, 9, 26, 20, 15, 19, 195, 173, 20, 1, 14, 9, 13, 6, 195, 32, 19, 0, 13, 6, 195, 24, 83, 0, 13, 0, 23, 68, 80, 84, 218, 36, 47, 107, 87, 37, 23, 63, 106, 57, 70, 0, 13, 81, 109, 97, 106, 100, 32, 46, 12, 19, 26, 195, 161, 26, 1, 12, 195, 169, 11, 15, 20, 87, 112, 86, 106, 55, 111, 49, 39, 47, 23, 82, 107, 87, 110, 47, 107, 50, 107, 0, 13, 81, 118, 101, 115, 122, 195, 173, 116, 101, 110, 101, 32, 9, 198, 77, 163, 205, 8, 21, 0, 20, 0, 8, 197, 52, 243, 132, 60, 176, 13, 8, 197, 28, 243, 132, 60, 176, 13, 6, 195, 32, 21, 0, 13, 6, 195, 24, 80, 146, 20, 0, 33, 74, 80, 20, 1, 77, 165, 1, 48, 21, 15, 16, 47, 106, 48, 106, 87, 47, 106, 55, 106, 47, 39, 70, 23, 37, 89, 0, 13, 81, 105, 115, 32, 18, 143, 11, 195, 169, 14, 25, 19, 26, 5, 18, 195, 173, 20, 5, 14, 9, 13, 12, 137, 16, 195, 169, 14, 20, 5, 11, 9, 7, 22, 11, 4, 195, 161, 19, 26, 112, 87, 0, 42, 42, 7, 132, 197, 145, 19, 26, 20, 7, 132, 195, 161, 16, 18, 20, 0, 10, 135, 6, 5, 11, 195, 188, 4, 20, 13, 10, 199, 88, 84, 218, 80, 85, 20, 20, 13, 11, 136, 22, 195, 161, 12, 20, 1, 14, 1, 13, 36, 71, 88, 84, 218, 80, 85, 20, 20, 82, 107, 87, 47, 107, 47, 12, 107, 23, 111, 55, 107, 47, 111, 47, 0, 13, 81, 195, 169, 108, 101, 116, 195, 169, 116, 32, 10, 135, 4, 5, 18, 195, 188, 12, 20, 13, 10, 135, 13, 5, 18, 195, 188, 12, 20, 13, 6, 195, 13, 48, 80, 13, 9, 134, 20, 197, 177, 14, 9, 11, 13, 11, 67, 80, 18, 128, 47, 106, 57, 0, 42, 42, 0, 20, 145, 195, 182, 19, 19, 26, 16, 15, 14, 20, 15, 19, 195, 173, 20, 1, 14, 9, 13, 19, 68, 56, 147, 131, 76, 50, 37, 50, 74, 23, 37, 89, 0, 13, 81, 105, 115, 32, 14, 139, 195, 161, 12, 20, 1, 12, 195, 161, 14, 15, 19, 13, 9, 134, 21, 20, 3, 195, 161, 14, 13, 7, 196, 76, 244, 130, 4, 13, 7, 196, 56, 147, 131, 76, 13, 0, 22, 69, 20, 209, 76, 80, 80, 107, 63, 107, 55, 47, 107, 23, 49, 37, 0, 13, 81, 107, 105, 32, 51, 73, 77, 161, 82, 88, 86, 133, 80, 82, 192, 87, 107, 52, 82, 107, 86, 107, 47, 107, 49, 23, 48, 112, 57, 112, 86, 105, 106, 47, 50, 106, 49, 0, 13, 81, 112, 195, 161, 108, 121, 195, 161, 122, 104, 97, 116, 110, 97, 107, 32, 15, 140, 19, 26, 195, 161, 26, 1, 12, 195, 169, 11, 15, 19, 13, 12, 137, 11, 9, 4, 5, 18, 195, 188, 12, 20, 13, 8, 197, 60, 193, 1, 56, 144, 13, 9, 134, 14, 195, 169, 26, 22, 5, 13, 8, 197, 60, 193, 1, 56, 144, 13, 6, 195, 24, 83, 142, 13, 8, 133, 3, 195, 169, 12, 20, 13, 0, 7, 132, 6, 9, 195, 186, 13, 15, 5, 95, 48, 77, 49, 15, 107, 86, 52, 107, 70, 37, 49, 0, 0, 6, 195, 72, 83, 132, 13, 10, 135, 13, 5, 19, 195, 169, 12, 20, 13, 15, 140, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 18, 1, 13, 10, 135, 13, 5, 19, 195, 169, 12, 20, 13, 6, 195, 52, 243, 132, 13, 14, 67, 29, 51, 64, 79, 111, 107, 89, 107, 63, 0, 42, 42, 0, 11, 136, 11, 195, 188, 20, 25, 195, 188, 20, 13, 14, 139, 11, 195, 182, 12, 20, 195, 182, 26, 20, 5, 11, 13, 7, 196, 88, 83, 5, 52, 13, 7, 196, 29, 32, 77, 52, 13, 0, 25, 67, 25, 85, 0, 81, 40, 47, 10, 6, 15, 52, 106, 57, 47, 106, 0, 13, 81, 114, 97, 106, 116, 97, 32, 6, 195, 25, 85, 0, 13, 0, 40, 70, 29, 144, 75, 72, 19, 128, 77, 106, 49, 52, 106, 50, 23, 55, 107, 87, 23, 111, 55, 111, 50, 49, 0, 13, 82, 108, 101, 115, 122, 32, 195, 169, 108, 195, 169, 110, 107, 32, 12, 137, 3, 19, 1, 16, 1, 4, 195, 169, 11, 13, 13, 138, 22, 1, 12, 1, 13, 9, 18, 197, 145, 12, 13, 9, 134, 195, 169, 16, 195, 188, 12, 13, 0, 17, 142, 2, 9, 26, 15, 14, 25, 195, 173, 20, 195, 169, 11, 15, 11, 13, 6, 195, 8, 83, 128, 72, 0, 36, 11, 6, 5, 10, 12, 5, 19, 26, 20, 197, 145, 11, 81, 107, 57, 55, 107, 87, 47, 116, 49, 23, 81, 107, 55, 111, 0, 13, 81, 102, 101, 108, 195, 169, 32, 16, 141, 8, 1, 14, 7, 19, 195, 186, 12, 25, 15, 26, 22, 1, 13, 24, 67, 32, 19, 135, 105, 106, 50, 79, 15, 63, 37, 106, 47, 12, 0, 13, 81, 109, 105, 97, 116, 116, 32, 7, 196, 40, 83, 5, 80, 13, 7, 196, 24, 83, 5, 48, 13, 6, 195, 32, 19, 135, 13, 0, 9, 134, 11, 195, 169, 18, 197, 145, 13, 42, 6, 12, 195, 169, 22, 197, 145, 55, 111, 82, 116, 105, 106, 89, 39, 50, 55, 113, 89, 112, 79, 39, 47, 0, 13, 81, 104, 97, 115, 111, 110, 108, 195, 179, 115, 195, 161, 103, 111, 116, 32, 15, 140, 6, 5, 12, 11, 5, 18, 195, 188, 12, 20, 5, 11, 13, 9, 134, 12, 195, 169, 22, 197, 145, 13, 8, 197, 24, 243, 148, 61, 48, 13, 10, 135, 10, 1, 14, 21, 195, 161, 18, 20, 0, 15, 140, 8, 1, 10, 12, 195, 169, 11, 20, 1, 12, 1, 14, 13, 17, 142, 11, 195, 169, 19, 26, 195, 188, 12, 195, 169, 11, 11, 5, 12, 13, 0, 6, 195, 88, 84, 128, 13, 39, 12, 2, 15, 14, 25, 15, 12, 195, 173, 20, 1, 14, 9, 69, 39, 65, 39, 55, 110, 47, 106, 50, 37, 23, 52, 106, 57, 47, 106, 0, 13, 81, 114, 97, 106, 116, 97, 32, 0, 11, 136, 8, 9, 2, 195, 161, 11, 1, 20, 13, 14, 139, 19, 26, 5, 18, 5, 20, 14, 195, 169, 14, 11, 13, 6, 195, 32, 20, 131, 13, 0, 9, 134, 14, 195, 161, 12, 1, 13, 13, 45, 73, 24, 242, 207, 104, 21, 15, 76, 19, 128, 81, 39, 49, 39, 86, 106, 47, 39, 89, 106, 50, 23, 63, 107, 79, 87, 115, 50, 37, 49, 0, 13, 81, 109, 101, 103, 115, 122, 197, 177, 110, 105, 107, 32, 16, 141, 13, 5, 7, 19, 26, 195, 179, 12, 1, 12, 20, 1, 20, 13, 11, 136, 195, 161, 12, 12, 20, 21, 14, 11, 13, 6, 195, 8, 83, 142, 13, 8, 133, 19, 195, 173, 14, 20, 13, 0, 17, 142, 13, 5, 7, 1, 12, 11, 15, 20, 195, 161, 19, 195, 161, 20, 13, 17, 142, 13, 5, 3, 8, 1, 14, 9, 26, 13, 21, 19, 195, 161, 20, 13, 71, 6, 195, 161, 12, 20, 1, 12, 112, 55, 47, 106, 55, 10, 6, 15, 49, 110, 50, 112, 55, 47, 10, 6, 15, 87, 39, 55, 79, 112, 55, 47, 106, 47, 112, 89, 39, 49, 106, 47, 0, 13, 82, 107, 195, 173, 110, 195, 161, 108, 116, 32, 115, 122, 111, 108, 103, 195, 161, 108, 116, 97, 116, 195, 161, 115, 111, 107, 97, 116, 32, 9, 134, 13, 5, 19, 195, 169, 12, 13, 9, 134, 195, 161, 12, 20, 1, 12, 13, 13, 138, 22, 1, 18, 195, 161, 26, 19, 12, 1, 20, 13, 12, 137, 5, 7, 25, 195, 188, 20, 20, 5, 19, 13, 9, 195, 28, 68, 0, 102, 17, 42, 42, 14, 67, 28, 68, 0, 73, 110, 70, 110, 48, 110, 0, 42, 42, 0, 9, 134, 195, 173, 18, 20, 1, 11, 13, 6, 195, 32, 18, 148, 13, 0, 34, 68, 8, 83, 142, 20, 69, 107, 50, 12, 107, 23, 114, 57, 70, 39, 50, 89, 112, 79, 0, 13, 81, 195, 186, 106, 100, 111, 110, 115, 195, 161, 103, 32, 18, 143, 6, 195, 161, 10, 4, 1, 12, 15, 13, 13, 5, 14, 20, 5, 19, 13, 28, 68, 8, 83, 142, 20, 69, 107, 50, 12, 107, 15, 69, 37, 87, 47, 39, 89, 0, 13, 81, 98, 105, 122, 116, 111, 115, 32, 11, 200, 32, 21, 1, 48, 243, 77, 4, 192, 13, 7, 196, 60, 227, 129, 56, 13, 16, 141, 11, 195, 188, 12, 195, 182, 14, 2, 195, 182, 26, 197, 145, 13, 15, 140, 6, 5, 12, 20, 195, 169, 20, 5, 12, 5, 9, 20, 13, 7, 196, 8, 83, 142, 20, 13, 10, 135, 20, 195, 182, 18, 20, 5, 11, 13, 9, 198, 28, 243, 132, 60, 197, 0, 13, 7, 196, 36, 227, 133, 56, 13, 0, 12, 3, 226, 132, 162, 82, 111, 70, 57, 107, 77, 0, 12, 201, 81, 83, 1, 40, 67, 206, 61, 48, 64, 13, 22, 6, 195, 173, 18, 20, 1, 13, 110, 52, 47, 106, 63, 23, 55, 107, 0, 13, 81, 108, 101, 32, 12, 201, 81, 83, 1, 40, 67, 206, 61, 48, 64, 13, 12, 137, 20, 195, 182, 18, 20, 195, 169, 14, 20, 13, 9, 134, 195, 173, 18, 20, 1, 13, 13, 11, 136, 22, 195, 161, 7, 25, 195, 179, 11, 13, 12, 137, 20, 195, 182, 18, 20, 195, 169, 14, 20, 13, 0, 7, 66, 17, 160, 118, 111, 0, 36, 70, 64, 84, 131, 44, 244, 128, 48, 107, 52, 117, 49, 39, 52, 15, 10, 49, 111, 87, 109, 55, 47, 0, 13, 81, 107, 195, 169, 115, 122, 195, 188, 108, 116, 32, 0, 6, 195, 8, 83, 148, 13, 0, 33, 7, 22, 195, 161, 7, 10, 21, 11, 82, 112, 79, 57, 40, 49, 10, 6, 15, 88, 107, 69, 52, 107, 0, 13, 81, 122, 115, 101, 98, 114, 101, 32, 7, 196, 4, 227, 153, 36, 13, 14, 139, 22, 195, 169, 4, 5, 11, 5, 26, 20, 5, 11, 13, 6, 195, 64, 20, 139, 13, 0, 8, 197, 4, 210, 65, 81, 64, 13, 36, 69, 24, 83, 5, 49, 64, 81, 107, 55, 107, 55, 47, 23, 82, 39, 55, 50, 106, 23, 63, 107, 79, 0, 13, 82, 118, 111, 108, 110, 97, 32, 109, 101, 103, 32, 17, 142, 11, 5, 26, 4, 5, 13, 195, 169, 14, 25, 5, 26, 20, 5, 13, 20, 145, 9, 14, 6, 18, 1, 19, 20, 18, 21, 11, 20, 195, 186, 18, 195, 161, 20, 13, 16, 141, 8, 1, 19, 26, 14, 195, 161, 12, 1, 20, 20, 1, 12, 13, 20, 145, 19, 26, 195, 161, 12, 12, 195, 161, 19, 8, 5, 12, 25, 5, 11, 5, 20, 13, 8, 197, 24, 83, 5, 49, 64, 13, 0, 24, 6, 14, 195, 161, 12, 1, 4, 50, 112, 55, 106, 70, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 6, 195, 56, 85, 133, 13, 0, 30, 67, 24, 83, 148, 81, 107, 50, 47, 23, 106, 6, 15, 105, 107, 57, 107, 47, 0, 13, 82, 97, 32, 104, 101, 108, 121, 101, 116, 32, 6, 195, 24, 83, 148, 13, 12, 201, 32, 19, 12, 5, 68, 218, 61, 69, 0, 13, 10, 199, 24, 243, 148, 61, 48, 66, 8, 13, 23, 67, 96, 149, 128, 47, 37, 86, 107, 50, 50, 111, 77, 12, 107, 55, 0, 44, 42, 81, 101, 108, 32, 0, 12, 137, 16, 18, 15, 2, 12, 195, 169, 13, 1, 13, 14, 139, 11, 195, 169, 18, 4, 5, 26, 20, 195, 169, 11, 13, 0, 11, 136, 20, 5, 14, 14, 9, 195, 188, 11, 13, 31, 5, 14, 25, 195, 186, 12, 65, 114, 55, 15, 87, 107, 52, 107, 48, 111, 47, 0, 13, 81, 115, 122, 101, 114, 101, 112, 195, 169, 116, 32, 13, 138, 11, 9, 20, 195, 182, 12, 20, 5, 14, 9, 13, 8, 197, 49, 149, 75, 5, 64, 13, 8, 133, 14, 25, 195, 186, 12, 13, 8, 133, 8, 195, 186, 19, 20, 13, 0, 5, 194, 20, 144, 72, 21, 66, 12, 208, 117, 107, 50, 47, 37, 63, 111, 47, 107, 52, 47, 0, 44, 13, 81, 116, 32, 23, 66, 12, 208, 117, 107, 50, 47, 37, 63, 111, 47, 107, 52, 107, 89, 0, 44, 13, 81, 101, 115, 32, 24, 66, 12, 208, 117, 107, 50, 47, 37, 63, 111, 47, 107, 52, 65, 37, 0, 44, 13, 81, 110, 121, 105, 32, 28, 66, 12, 208, 117, 107, 50, 47, 37, 63, 111, 47, 107, 52, 65, 37, 52, 107, 0, 44, 13, 81, 110, 121, 105, 114, 101, 32, 23, 66, 12, 208, 117, 107, 50, 47, 37, 63, 111, 47, 107, 52, 52, 107, 0, 44, 13, 81, 114, 101, 32, 16, 66, 12, 208, 117, 107, 50, 47, 37, 63, 111, 47, 107, 52, 0, 13, 0, 0, 17, 68, 77, 165, 147, 104, 101, 115, 122, 118, 195, 169, 101, 115, 122, 0, 29, 39, 68, 20, 195, 5, 56, 107, 55, 12, 107, 50, 23, 55, 111, 47, 52, 107, 105, 39, 86, 39, 47, 12, 0, 13, 81, 108, 195, 169, 116, 114, 101, 104, 111, 122, 111, 116, 116, 32, 47, 68, 20, 195, 5, 56, 107, 55, 12, 107, 50, 10, 6, 15, 105, 37, 52, 70, 107, 47, 12, 111, 49, 10, 6, 15, 63, 107, 79, 0, 13, 82, 104, 105, 114, 100, 101, 116, 116, 195, 169, 107, 32, 109, 101, 103, 32, 47, 11, 19, 26, 195, 161, 13, 15, 12, 14, 21, 14, 11, 87, 112, 63, 39, 55, 50, 40, 50, 49, 23, 49, 107, 55, 12, 23, 106, 86, 86, 106, 55, 0, 13, 82, 107, 101, 108, 108, 32, 97, 122, 122, 97, 108, 32, 7, 196, 88, 85, 9, 44, 13, 26, 70, 24, 150, 133, 80, 81, 0, 81, 37, 86, 107, 47, 107, 70, 15, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 7, 196, 20, 195, 5, 56, 13, 7, 196, 32, 21, 14, 4, 13, 7, 196, 4, 130, 15, 104, 13, 7, 196, 21, 49, 84, 80, 13, 7, 196, 20, 195, 5, 56, 13, 0, 8, 197, 28, 243, 132, 60, 208, 13, 8, 197, 52, 243, 132, 60, 208, 13, 8, 197, 80, 84, 218, 36, 176, 13, 0, 9, 198, 65, 33, 77, 36, 84, 148, 13, 6, 195, 48, 22, 129, 13, 9, 134, 14, 25, 195, 173, 12, 20, 13, 0, 17, 142, 2, 5, 6, 5, 10, 5, 26, 195, 169, 19, 195, 169, 9, 7, 13, 9, 134, 18, 195, 161, 10, 21, 11, 13, 10, 135, 14, 195, 182, 22, 5, 12, 20, 13, 10, 199, 24, 243, 25, 80, 21, 10, 4, 13, 0, 11, 200, 8, 85, 133, 104, 85, 20, 20, 176, 13, 9, 134, 20, 5, 12, 195, 169, 14, 20, 0, 8, 197, 80, 148, 218, 80, 16, 13, 8, 197, 32, 148, 218, 36, 176, 13, 10, 6, 95, 35, 45, 9, 11, 9, 37, 0, 0, 14, 139, 4, 195, 182, 14, 20, 195, 182, 20, 20, 5, 13, 13, 0, 37, 71, 20, 118, 69, 80, 83, 69, 56, 107, 77, 107, 47, 107, 63, 107, 50, 23, 82, 111, 79, 86, 107, 47, 12, 0, 13, 81, 118, 195, 169, 103, 122, 101, 116, 116, 32, 14, 203, 44, 243, 80, 5, 66, 66, 36, 194, 83, 20, 176, 13, 10, 199, 24, 83, 5, 41, 65, 84, 80, 13, 11, 136, 22, 195, 169, 4, 5, 12, 5, 13, 13, 0, 14, 139, 2, 5, 14, 25, 15, 13, 195, 161, 19, 15, 11, 13, 7, 196, 32, 83, 25, 20, 13, 10, 135, 20, 195, 161, 18, 10, 21, 11, 13, 0, 45, 13, 5, 7, 25, 5, 19, 195, 188, 12, 5, 20, 20, 5, 12, 107, 77, 12, 107, 89, 109, 55, 107, 47, 12, 107, 55, 23, 87, 107, 63, 69, 107, 50, 0, 13, 81, 115, 122, 101, 109, 98, 101, 110, 32, 14, 139, 6, 5, 12, 195, 188, 12, 5, 20, 195, 169, 14, 13, 10, 135, 19, 26, 195, 169, 12, 5, 14, 13, 10, 6, 95, 35, 45, 9, 11, 5, 107, 0, 0, 18, 143, 9, 14, 6, 18, 1, 19, 20, 18, 21, 11, 20, 195, 186, 18, 1, 13, 12, 137, 19, 26, 195, 161, 14, 4, 195, 169, 11, 13, 0, 9, 198, 24, 243, 148, 61, 48, 75, 13, 13, 138, 11, 195, 182, 26, 195, 182, 12, 20, 5, 11, 13, 12, 137, 5, 19, 20, 195, 169, 10, 195, 169, 14, 22, 9, 134, 13, 195, 161, 10, 21, 19, 20, 0, 14, 139, 4, 195, 182, 14, 20, 195, 182, 20, 20, 5, 11, 13, 0, 12, 137, 5, 12, 14, 195, 182, 11, 195, 169, 20, 13, 38, 6, 195, 182, 18, 195, 182, 13, 108, 52, 108, 63, 23, 106, 6, 23, 87, 112, 63, 39, 63, 52, 106, 0, 13, 82, 97, 32, 115, 122, 195, 161, 109, 111, 109, 114, 97, 32, 17, 142, 6, 9, 14, 1, 14, 19, 26, 195, 173, 18, 15, 26, 22, 1, 13, 12, 201, 8, 150, 143, 57, 149, 1, 48, 19, 128, 13, 9, 134, 20, 21, 4, 14, 195, 161, 13, 11, 136, 22, 9, 19, 19, 26, 195, 188, 11, 13, 10, 6, 95, 35, 45, 9, 11, 1, 106, 0, 0, 16, 141, 13, 197, 177, 11, 195, 182, 4, 20, 5, 20, 20, 5, 11, 13, 15, 140, 7, 195, 169, 16, 5, 12, 195, 169, 19, 8, 5, 26, 13, 9, 198, 44, 86, 132, 40, 83, 128, 13, 15, 3, 95, 50, 17, 49, 107, 47, 12, 107, 70, 37, 49, 107, 0, 0, 15, 140, 22, 195, 161, 12, 1, 19, 26, 20, 195, 169, 11, 1, 13, 14, 139, 11, 195, 188, 12, 4, 195, 182, 20, 20, 5, 20, 13, 6, 195, 60, 64, 64, 13, 14, 139, 18, 5, 14, 4, 5, 12, 5, 20, 195, 169, 20, 13, 10, 199, 44, 20, 3, 76, 243, 1, 80, 13, 6, 195, 60, 64, 64, 13, 0, 0, 22, 3, 226, 128, 166, 10, 48, 2, 39, 50, 47, 48, 2, 39, 50, 47, 48, 2, 39, 50, 47, 0, 9, 134, 22, 5, 14, 14, 195, 169, 13, 16, 141, 1, 12, 1, 16, 195, 182, 20, 12, 5, 20, 195, 169, 20, 13, 6, 195, 20, 165, 0, 13, 8, 133, 2, 195, 186, 10, 20, 13, 0, 9, 198, 84, 69, 129, 72, 244, 192, 13, 0, 14, 139, 5, 13, 12, 195, 169, 11, 5, 26, 20, 5, 20, 13, 10, 199, 28, 243, 132, 60, 194, 149, 44, 13, 0, 31, 11, 6, 18, 9, 19, 19, 195, 173, 20, 195, 169, 19, 81, 52, 37, 89, 12, 110, 47, 111, 89, 23, 37, 89, 0, 13, 81, 105, 115, 32, 11, 5, 95, 35, 45, 5, 9, 107, 37, 0, 21, 13, 3, 95, 49, 15, 107, 77, 12, 107, 70, 37, 49, 0, 0, 0, 27, 67, 57, 97, 1, 101, 110, 118, 195, 169, 100, 195, 169, 195, 161, 118, 97, 108, 0, 44, 29, 42, 81, 118, 97, 108, 32, 29, 67, 57, 97, 1, 101, 110, 118, 195, 169, 100, 195, 169, 195, 161, 116, 195, 179, 108, 0, 44, 29, 42, 81, 116, 195, 179, 108, 32, 23, 67, 57, 97, 1, 101, 110, 118, 195, 169, 100, 195, 169, 195, 161, 116, 0, 44, 29, 42, 81, 116, 32, 23, 67, 57, 97, 1, 101, 110, 118, 195, 169, 100, 195, 169, 195, 161, 115, 0, 44, 29, 42, 81, 115, 32, 27, 67, 57, 97, 1, 101, 110, 118, 195, 169, 100, 195, 169, 195, 161, 110, 97, 107, 0, 44, 29, 42, 81, 110, 97, 107, 32, 27, 67, 57, 97, 1, 101, 110, 118, 195, 169, 100, 195, 169, 195, 161, 104, 111, 122, 0, 44, 29, 42, 81, 104, 111, 122, 32, 29, 67, 57, 97, 1, 101, 110, 118, 195, 169, 100, 195, 169, 195, 161, 98, 195, 179, 108, 0, 44, 29, 42, 81, 98, 195, 179, 108, 32, 27, 67, 57, 97, 1, 101, 110, 118, 195, 169, 100, 195, 169, 195, 161, 98, 97, 110, 0, 44, 29, 42, 81, 98, 97, 110, 32, 25, 67, 57, 97, 1, 101, 110, 118, 195, 169, 100, 195, 169, 195, 161, 98, 97, 0, 44, 29, 42, 81, 98, 97, 32, 27, 66, 21, 160, 107, 86, 10, 6, 15, 82, 106, 55, 106, 63, 37, 47, 0, 13, 81, 118, 97, 108, 97, 109, 105, 116, 32, 10, 135, 197, 145, 18, 14, 1, 7, 25, 13, 15, 66, 21, 160, 107, 86, 23, 106, 86, 0, 13, 81, 97, 122, 32, 35, 66, 21, 160, 107, 86, 10, 6, 15, 106, 6, 15, 48, 52, 39, 69, 55, 111, 63, 106, 0, 13, 82, 97, 32, 112, 114, 111, 98, 108, 195, 169, 109, 97, 32, 5, 194, 21, 160, 13, 15, 67, 57, 97, 1, 107, 50, 82, 111, 70, 111, 106, 0, 42, 42, 15, 8, 95, 35, 45, 195, 169, 8, 5, 26, 111, 105, 107, 86, 0, 16, 3, 95, 51, 17, 105, 106, 52, 10, 63, 106, 70, 37, 49, 106, 0, 0, 10, 3, 226, 130, 172, 107, 40, 52, 39, 0, 36, 71, 72, 83, 132, 77, 161, 82, 80, 52, 107, 50, 117, 107, 52, 47, 10, 6, 15, 49, 111, 87, 110, 47, 0, 13, 81, 107, 195, 169, 115, 122, 195, 173, 116, 32, 41, 12, 22, 5, 26, 5, 20, 197, 145, 19, 195, 169, 7, 9, 82, 107, 86, 107, 47, 116, 89, 111, 79, 37, 23, 47, 106, 79, 57, 106, 37, 0, 13, 81, 116, 97, 103, 106, 97, 105, 32, 17, 142, 19, 26, 195, 161, 13, 195, 173, 20, 8, 1, 20, 21, 14, 11, 13, 9, 198, 24, 150, 133, 80, 225, 75, 13, 6, 195, 60, 179, 212, 13, 10, 199, 72, 83, 132, 77, 161, 82, 80, 13, 0, 10, 135, 12, 195, 161, 14, 3, 15, 11, 13, 7, 196, 20, 227, 153, 36, 13, 6, 131, 10, 195, 179, 13, 0, 19, 67, 21, 165, 0, 107, 87, 47, 10, 6, 15, 106, 86, 0, 13, 81, 97, 122, 32, 21, 67, 21, 165, 0, 107, 87, 47, 23, 49, 107, 55, 12, 0, 13, 81, 107, 101, 108, 108, 32, 8, 197, 24, 244, 137, 57, 64, 13, 12, 137, 2, 1, 10, 15, 11, 18, 195, 179, 12, 13, 8, 197, 37, 51, 69, 73, 64, 13, 6, 195, 21, 165, 0, 13, 0, 13, 138, 22, 9, 12, 195, 161, 7, 18, 195, 179, 12, 13, 9, 198, 77, 161, 77, 24, 241, 192, 13, 6, 195, 64, 144, 201, 13, 12, 137, 13, 197, 177, 11, 195, 182, 4, 9, 11, 13, 9, 3, 95, 49, 5, 107, 77, 12, 0, 0, 14, 139, 22, 195, 169, 4, 5, 12, 5, 13, 13, 5, 12, 13, 12, 201, 61, 4, 133, 56, 68, 218, 21, 37, 0, 13, 12, 137, 13, 21, 14, 11, 195, 161, 8, 15, 26, 13, 13, 138, 5, 13, 12, 195, 169, 11, 19, 26, 9, 11, 13, 11, 136, 19, 26, 5, 13, 195, 169, 12, 25, 13, 6, 195, 80, 17, 192, 13, 0, 10, 135, 195, 188, 12, 195, 188, 14, 11, 13, 14, 3, 95, 50, 15, 49, 107, 47, 12, 107, 70, 37, 49, 0, 0, 8, 197, 56, 83, 90, 21, 64, 13, 9, 134, 18, 195, 161, 26, 14, 9, 13, 13, 138, 22, 195, 169, 12, 5, 13, 195, 169, 14, 25, 13, 13, 138, 8, 1, 19, 26, 14, 195, 161, 12, 14, 9, 13, 0, 13, 138, 8, 15, 26, 1, 4, 195, 169, 11, 15, 20, 13, 9, 3, 95, 50, 1, 49, 111, 47, 0, 0, 20, 67, 80, 20, 148, 47, 106, 52, 47, 23, 39, 47, 12, 0, 13, 81, 111, 116, 116, 32, 15, 140, 12, 5, 7, 5, 14, 5, 18, 195, 161, 12, 14, 9, 13, 9, 134, 10, 195, 161, 18, 195, 179, 13, 14, 139, 10, 195, 161, 18, 1, 4, 195, 169, 11, 15, 20, 13, 6, 195, 80, 20, 148, 13, 6, 195, 56, 82, 192, 13, 0, 22, 68, 40, 83, 26, 36, 57, 107, 55, 86, 37, 10, 6, 15, 106, 86, 0, 13, 81, 97, 122, 32, 7, 196, 88, 85, 14, 36, 13, 7, 196, 40, 83, 26, 36, 13, 10, 135, 22, 5, 12, 195, 188, 14, 11, 13, 6, 195, 88, 84, 147, 13, 0, 8, 197, 81, 81, 20, 60, 176, 76, 8, 197, 88, 19, 142, 4, 176, 13, 0, 9, 198, 85, 64, 90, 56, 18, 192, 13, 9, 198, 8, 19, 139, 56, 18, 192, 13, 12, 201, 88, 148, 218, 60, 230, 85, 48, 224, 75, 13, 31, 70, 72, 144, 68, 56, 18, 192, 51, 37, 106, 70, 50, 106, 49, 23, 82, 37, 87, 12, 106, 0, 13, 81, 118, 105, 115, 115, 122, 97, 32, 9, 198, 5, 163, 203, 56, 18, 192, 13, 9, 198, 32, 19, 135, 104, 146, 192, 13, 9, 198, 52, 243, 132, 41, 82, 192, 13, 9, 198, 32, 19, 135, 104, 146, 192, 13, 9, 134, 6, 195, 161, 10, 12, 20, 13, 10, 3, 95, 50, 5, 49, 107, 47, 12, 0, 0, 15, 140, 11, 195, 182, 18, 195, 188, 12, 13, 195, 169, 14, 25, 13, 20, 145, 13, 5, 7, 6, 9, 7, 25, 5, 12, 195, 169, 19, 195, 169, 8, 5, 26, 13, 15, 140, 11, 9, 8, 1, 19, 26, 14, 195, 161, 12, 14, 9, 13, 14, 139, 2, 15, 18, 195, 173, 20, 195, 169, 11, 15, 20, 13, 11, 136, 19, 26, 195, 179, 12, 20, 1, 13, 13, 8, 133, 8, 195, 186, 19, 26, 13, 6, 195, 88, 84, 148, 13, 0, 42, 8, 2, 5, 3, 19, 195, 188, 12, 20, 69, 107, 74, 109, 55, 47, 23, 111, 52, 47, 111, 49, 111, 50, 107, 49, 0, 13, 81, 195, 169, 114, 116, 195, 169, 107, 195, 169, 110, 101, 107, 32, 12, 137, 10, 5, 12, 19, 26, 195, 179, 18, 1, 13, 11, 200, 24, 83, 9, 76, 209, 82, 56, 144, 13, 15, 3, 95, 51, 15, 105, 106, 52, 10, 63, 106, 70, 37, 49, 0, 11, 4, 95, 15, 18, 4, 107, 70, 37, 49, 0, 0, 8, 197, 81, 81, 14, 4, 176, 76, 13, 138, 11, 195, 182, 26, 16, 15, 14, 20, 10, 1, 13, 8, 197, 81, 81, 14, 4, 176, 13, 11, 136, 18, 5, 13, 195, 169, 12, 9, 11, 13, 0, 13, 66, 33, 80, 104, 117, 110, 0, 44, 29, 81, 110, 32, 28, 66, 37, 48, 37, 89, 23, 82, 37, 47, 106, 78, 12, 112, 49, 0, 13, 81, 118, 105, 116, 97, 116, 106, 195, 161, 107, 32, 27, 66, 37, 48, 37, 89, 23, 106, 55, 112, 110, 52, 47, 106, 0, 13, 81, 97, 108, 195, 161, 195, 173, 114, 116, 97, 32, 30, 66, 37, 48, 37, 89, 23, 63, 107, 79, 107, 63, 55, 110, 47, 37, 0, 13, 81, 109, 101, 103, 101, 109, 108, 195, 173, 116, 105, 32, 22, 66, 37, 48, 37, 89, 23, 63, 111, 52, 37, 49, 0, 13, 81, 109, 195, 169, 114, 105, 107, 32, 27, 66, 37, 48, 37, 89, 23, 47, 108, 34, 47, 111, 50, 47, 0, 13, 81, 116, 195, 182, 114, 116, 195, 169, 110, 116, 32, 25, 66, 37, 48, 37, 89, 23, 69, 107, 87, 111, 55, 47, 0, 13, 81, 98, 101, 115, 122, 195, 169, 108, 116, 32, 54, 66, 37, 48, 37, 89, 10, 6, 15, 55, 107, 105, 107, 47, 10, 6, 15, 74, 106, 47, 55, 106, 49, 39, 87, 47, 106, 47, 50, 37, 0, 13, 82, 108, 101, 104, 101, 116, 32, 99, 115, 97, 116, 108, 97, 107, 111, 122, 116, 97, 116, 110, 105, 32, 45, 66, 37, 48, 37, 89, 10, 6, 15, 55, 107, 105, 107, 47, 10, 6, 15, 69, 116, 82, 110, 47, 107, 50, 37, 0, 13, 82, 108, 101, 104, 101, 116, 32, 98, 197, 145, 118, 195, 173, 116, 101, 110, 105, 32, 45, 66, 37, 48, 37, 89, 10, 6, 15, 55, 107, 105, 107, 47, 10, 6, 15, 105, 106, 87, 50, 112, 55, 50, 37, 0, 13, 82, 108, 101, 104, 101, 116, 32, 104, 97, 115, 122, 110, 195, 161, 108, 110, 105, 32, 33, 66, 37, 48, 37, 89, 10, 6, 15, 47, 106, 55, 112, 55, 105, 106, 47, 113, 0, 13, 81, 116, 97, 108, 195, 161, 108, 104, 97, 116, 195, 179, 32, 31, 66, 37, 48, 37, 89, 10, 6, 15, 57, 107, 77, 107, 87, 47, 109, 49, 0, 13, 81, 106, 101, 103, 121, 101, 122, 116, 195, 188, 107, 32, 25, 66, 37, 48, 37, 89, 10, 6, 15, 82, 106, 50, 12, 106, 49, 0, 13, 81, 118, 97, 110, 110, 97, 107, 32, 36, 66, 37, 48, 37, 89, 10, 6, 15, 63, 107, 79, 63, 40, 47, 106, 78, 12, 112, 49, 0, 13, 81, 109, 101, 103, 109, 117, 116, 97, 116, 106, 195, 161, 107, 32, 40, 66, 37, 48, 37, 89, 10, 6, 15, 49, 37, 107, 79, 111, 87, 110, 47, 107, 47, 12, 107, 0, 13, 81, 107, 105, 101, 103, 195, 169, 115, 122, 195, 173, 116, 101, 116, 116, 101, 32, 37, 66, 37, 48, 37, 89, 10, 6, 15, 52, 107, 50, 70, 107, 55, 49, 107, 87, 47, 107, 49, 0, 13, 81, 114, 101, 110, 100, 101, 108, 107, 101, 122, 116, 101, 107, 32, 34, 66, 37, 48, 37, 89, 6, 15, 49, 108, 87, 108, 50, 105, 107, 47, 116, 0, 13, 81, 107, 195, 182, 115, 122, 195, 182, 110, 104, 101, 116, 197, 145, 32, 33, 66, 37, 48, 37, 89, 10, 6, 15, 110, 47, 111, 55, 105, 107, 47, 37, 49, 0, 13, 81, 195, 173, 116, 195, 169, 108, 104, 101, 116, 105, 107, 32, 38, 66, 37, 48, 37, 89, 10, 6, 15, 49, 39, 50, 117, 107, 50, 47, 52, 112, 55, 50, 37, 0, 13, 81, 107, 111, 110, 99, 101, 110, 116, 114, 195, 161, 108, 110, 105, 32, 22, 66, 37, 48, 37, 89, 10, 6, 15, 112, 52, 40, 55, 0, 13, 81, 195, 161, 114, 117, 108, 32, 23, 66, 37, 48, 37, 89, 10, 6, 15, 47, 37, 55, 39, 89, 0, 13, 81, 116, 105, 108, 111, 115, 32, 29, 66, 37, 48, 37, 89, 10, 6, 15, 109, 77, 107, 55, 47, 107, 49, 0, 13, 81, 195, 188, 103, 121, 101, 108, 116, 101, 107, 32, 22, 66, 37, 48, 37, 89, 10, 6, 55, 107, 50, 12, 107, 0, 13, 81, 108, 101, 110, 110, 101, 32, 35, 66, 37, 48, 37, 89, 10, 6, 15, 82, 112, 55, 106, 87, 47, 39, 47, 12, 106, 0, 13, 81, 118, 195, 161, 108, 97, 115, 122, 116, 111, 116, 116, 97, 32, 24, 66, 37, 48, 37, 89, 10, 6, 15, 55, 112, 86, 106, 70, 0, 13, 81, 108, 195, 161, 122, 97, 100, 32, 18, 66, 37, 48, 37, 89, 10, 6, 15, 111, 52, 0, 13, 81, 195, 169, 114, 32, 25, 66, 37, 48, 37, 89, 10, 6, 15, 105, 106, 47, 39, 47, 12, 0, 13, 81, 104, 97, 116, 111, 116, 116, 32, 32, 66, 37, 48, 37, 89, 10, 6, 15, 87, 109, 49, 89, 111, 79, 107, 89, 0, 13, 81, 115, 122, 195, 188, 107, 115, 195, 169, 103, 101, 115, 32, 29, 66, 37, 48, 37, 89, 23, 87, 107, 52, 107, 47, 50, 111, 49, 0, 13, 81, 115, 122, 101, 114, 101, 116, 110, 195, 169, 107, 32, 39, 66, 37, 48, 37, 89, 23, 107, 77, 12, 109, 47, 63, 115, 49, 108, 70, 37, 49, 0, 13, 81, 101, 103, 121, 195, 188, 116, 116, 109, 197, 177, 107, 195, 182, 100, 105, 107, 32, 28, 66, 37, 48, 37, 89, 23, 57, 107, 55, 107, 86, 47, 111, 49, 0, 13, 81, 106, 101, 108, 101, 122, 116, 195, 169, 107, 32, 34, 66, 37, 48, 37, 89, 23, 87, 109, 49, 108, 89, 107, 69, 12, 107, 49, 0, 13, 81, 115, 122, 197, 177, 107, 195, 182, 115, 101, 98, 98, 101, 107, 32, 35, 66, 37, 48, 37, 89, 23, 49, 37, 57, 107, 55, 108, 55, 105, 107, 47, 116, 0, 13, 81, 107, 105, 106, 101, 108, 195, 182, 108, 104, 101, 116, 197, 145, 32, 34, 66, 37, 48, 37, 89, 23, 105, 106, 87, 50, 112, 55, 105, 106, 47, 113, 0, 13, 81, 104, 97, 115, 122, 110, 195, 161, 108, 104, 97, 116, 195, 179, 32, 36, 66, 37, 48, 37, 89, 23, 105, 106, 87, 50, 112, 55, 105, 106, 47, 113, 49, 0, 13, 81, 104, 97, 115, 122, 110, 195, 161, 108, 104, 97, 116, 195, 179, 107, 32, 35, 66, 37, 48, 37, 89, 23, 63, 107, 79, 87, 107, 52, 107, 87, 47, 111, 49, 0, 13, 81, 109, 101, 103, 115, 122, 101, 114, 101, 122, 116, 195, 169, 107, 32, 26, 66, 37, 48, 37, 89, 23, 55, 107, 55, 108, 82, 37, 49, 0, 13, 81, 108, 101, 108, 195, 182, 118, 105, 107, 32, 30, 66, 37, 48, 37, 89, 23, 47, 112, 63, 39, 79, 106, 78, 12, 106, 0, 13, 81, 116, 195, 161, 109, 111, 103, 97, 116, 106, 97, 32, 39, 66, 37, 48, 37, 89, 23, 107, 52, 107, 70, 63, 111, 65, 107, 86, 105, 107, 47, 37, 0, 13, 81, 101, 114, 101, 100, 109, 195, 169, 110, 121, 101, 122, 104, 101, 116, 105, 32, 23, 66, 37, 48, 37, 89, 23, 82, 39, 55, 47, 106, 49, 0, 13, 81, 118, 111, 108, 116, 97, 107, 32, 26, 66, 37, 48, 37, 89, 23, 49, 37, 70, 107, 52, 109, 55, 0, 13, 81, 107, 105, 100, 101, 114, 195, 188, 108, 32, 31, 66, 37, 48, 37, 89, 10, 6, 15, 81, 107, 55, 82, 107, 47, 105, 107, 47, 0, 13, 81, 102, 101, 108, 118, 101, 116, 104, 101, 116, 32, 42, 66, 37, 48, 37, 89, 23, 52, 107, 63, 111, 65, 49, 107, 70, 105, 107, 47, 109, 50, 49, 0, 13, 81, 114, 101, 109, 195, 169, 110, 121, 107, 101, 100, 104, 101, 116, 195, 188, 110, 107, 32, 18, 66, 37, 48, 37, 89, 23, 55, 107, 87, 0, 13, 81, 108, 101, 115, 122, 32, 30, 66, 37, 48, 37, 89, 23, 81, 107, 55, 63, 107, 52, 109, 55, 47, 0, 13, 81, 102, 101, 108, 109, 101, 114, 195, 188, 108, 116, 32, 38, 66, 37, 48, 37, 89, 23, 52, 112, 82, 37, 55, 112, 79, 110, 47, 39, 47, 12, 0, 13, 81, 114, 195, 161, 118, 105, 108, 195, 161, 103, 195, 173, 116, 111, 116, 116, 32, 67, 66, 37, 48, 37, 89, 23, 81, 37, 86, 107, 47, 105, 107, 47, 50, 107, 49, 23, 106, 6, 15, 77, 113, 77, 87, 107, 52, 107, 49, 111, 52, 47, 0, 13, 83, 102, 105, 122, 101, 116, 104, 101, 116, 110, 101, 107, 32, 97, 32, 103, 121, 195, 179, 103, 121, 115, 122, 101, 114, 101, 107, 195, 169, 114, 116, 32, 29, 66, 37, 48, 37, 89, 23, 47, 106, 52, 47, 106, 55, 63, 106, 86, 0, 13, 81, 116, 97, 114, 116, 97, 108, 109, 97, 122, 32, 24, 66, 37, 48, 37, 89, 23, 81, 39, 57, 50, 106, 49, 0, 13, 81, 102, 111, 108, 121, 110, 97, 107, 32, 21, 66, 37, 48, 37, 89, 23, 108, 52, 108, 63, 0, 13, 81, 195, 182, 114, 195, 182, 109, 32, 23, 66, 37, 48, 37, 89, 23, 69, 40, 49, 12, 106, 50, 0, 13, 81, 98, 117, 107, 107, 97, 110, 32, 29, 66, 37, 48, 37, 89, 23, 105, 37, 112, 65, 39, 55, 39, 63, 0, 13, 81, 104, 105, 195, 161, 110, 121, 111, 108, 111, 109, 32, 19, 66, 37, 48, 37, 89, 23, 55, 107, 47, 12, 0, 13, 81, 108, 101, 116, 116, 32, 19, 66, 37, 48, 37, 89, 23, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 36, 66, 37, 48, 37, 89, 23, 63, 111, 52, 89, 111, 49, 55, 116, 70, 37, 49, 0, 13, 81, 109, 195, 169, 114, 115, 195, 169, 107, 108, 197, 145, 100, 105, 107, 32, 33, 66, 37, 48, 37, 89, 23, 49, 110, 89, 111, 52, 105, 107, 47, 37, 49, 0, 13, 81, 107, 195, 173, 115, 195, 169, 114, 104, 101, 116, 105, 107, 32, 26, 66, 37, 48, 37, 89, 23, 49, 37, 82, 112, 52, 50, 37, 0, 13, 81, 107, 105, 118, 195, 161, 114, 110, 105, 32, 28, 66, 37, 48, 37, 89, 23, 81, 107, 57, 55, 116, 70, 37, 49, 0, 13, 81, 102, 101, 106, 108, 197, 145, 100, 105, 107, 32, 22, 66, 37, 48, 37, 89, 23, 82, 112, 55, 37, 49, 0, 13, 81, 118, 195, 161, 108, 105, 107, 32, 20, 66, 37, 48, 37, 89, 23, 81, 109, 79, 12, 0, 13, 81, 102, 195, 188, 103, 103, 32, 27, 66, 37, 48, 37, 89, 23, 82, 112, 52, 105, 106, 47, 113, 0, 13, 81, 118, 195, 161, 114, 104, 97, 116, 195, 179, 32, 25, 66, 37, 48, 37, 89, 23, 69, 107, 37, 49, 47, 106, 47, 0, 13, 81, 98, 101, 105, 107, 116, 97, 116, 32, 26, 66, 37, 48, 37, 89, 23, 63, 107, 50, 107, 49, 109, 55, 0, 13, 81, 109, 101, 110, 101, 107, 195, 188, 108, 32, 20, 66, 37, 48, 37, 89, 23, 52, 113, 55, 106, 0, 13, 81, 114, 195, 179, 108, 97, 32, 38, 66, 37, 48, 37, 89, 23, 49, 37, 107, 79, 111, 87, 110, 47, 107, 47, 12, 107, 0, 13, 81, 107, 105, 101, 103, 195, 169, 115, 122, 195, 173, 116, 101, 116, 116, 101, 32, 16, 66, 37, 48, 37, 89, 23, 106, 86, 6, 0, 13, 81, 97, 122, 32, 33, 66, 37, 48, 37, 89, 23, 63, 107, 79, 63, 106, 52, 106, 77, 12, 39, 50, 0, 13, 81, 109, 101, 103, 109, 97, 114, 97, 100, 106, 111, 110, 32, 36, 66, 37, 48, 37, 89, 23, 81, 107, 57, 55, 107, 87, 47, 107, 47, 12, 107, 49, 0, 13, 81, 102, 101, 106, 108, 101, 115, 122, 116, 101, 116, 116, 101, 107, 32, 31, 66, 37, 48, 37, 89, 15, 105, 6, 106, 57, 55, 106, 50, 70, 113, 49, 0, 13, 81, 104, 97, 106, 108, 97, 110, 100, 195, 179, 107, 32, 10, 135, 195, 186, 19, 26, 20, 1, 13, 13, 24, 66, 37, 48, 37, 89, 23, 40, 77, 106, 50, 106, 86, 0, 13, 81, 117, 103, 121, 97, 110, 97, 122, 32, 40, 66, 37, 48, 37, 89, 23, 49, 106, 47, 106, 87, 47, 52, 113, 81, 112, 105, 39, 86, 0, 13, 81, 107, 97, 116, 97, 115, 122, 116, 114, 195, 179, 102, 195, 161, 104, 111, 122, 32, 16, 141, 6, 5, 12, 8, 197, 145, 20, 1, 11, 1, 18, 195, 179, 13, 33, 66, 37, 48, 37, 89, 23, 81, 39, 79, 55, 106, 55, 49, 39, 86, 39, 63, 0, 13, 81, 102, 111, 103, 108, 97, 108, 107, 111, 122, 111, 109, 32, 36, 66, 37, 48, 37, 89, 23, 107, 55, 116, 81, 39, 52, 70, 40, 55, 105, 106, 47, 0, 13, 81, 101, 108, 197, 145, 102, 111, 114, 100, 117, 108, 104, 97, 116, 32, 37, 66, 37, 48, 37, 89, 23, 49, 111, 48, 86, 116, 70, 105, 107, 47, 50, 107, 49, 0, 13, 81, 107, 195, 169, 112, 122, 197, 145, 100, 104, 101, 116, 110, 101, 107, 32, 21, 66, 37, 48, 37, 89, 23, 55, 107, 105, 107, 47, 0, 13, 81, 108, 101, 104, 101, 116, 32, 25, 66, 37, 48, 37, 89, 23, 49, 107, 86, 107, 55, 47, 107, 0, 13, 81, 107, 101, 122, 101, 108, 116, 101, 32, 29, 66, 37, 48, 37, 89, 23, 87, 109, 55, 107, 47, 107, 47, 12, 0, 13, 81, 115, 122, 195, 188, 108, 101, 116, 101, 116, 116, 32, 80, 66, 37, 48, 37, 89, 23, 49, 37, 47, 108, 55, 47, 105, 107, 47, 12, 111, 49, 23, 82, 39, 55, 50, 106, 23, 106, 23, 49, 111, 52, 70, 116, 110, 82, 107, 49, 107, 47, 0, 13, 84, 107, 105, 116, 195, 182, 108, 116, 104, 101, 116, 116, 195, 169, 107, 32, 118, 111, 108, 110, 97, 32, 97, 32, 107, 195, 169, 114, 100, 197, 145, 195, 173, 118, 101, 107, 101, 116, 32, 36, 66, 37, 48, 37, 89, 23, 106, 23, 49, 111, 52, 70, 116, 110, 82, 107, 47, 0, 13, 82, 97, 32, 107, 195, 169, 114, 100, 197, 145, 195, 173, 118, 101, 116, 32, 26, 66, 37, 48, 37, 89, 23, 81, 107, 50, 12, 112, 55, 12, 0, 13, 81, 102, 101, 110, 110, 195, 161, 108, 108, 32, 36, 66, 37, 48, 37, 89, 23, 107, 55, 116, 81, 39, 52, 70, 40, 55, 50, 106, 49, 0, 13, 81, 101, 108, 197, 145, 102, 111, 114, 100, 117, 108, 110, 97, 107, 32, 29, 66, 37, 48, 37, 89, 23, 81, 107, 55, 52, 106, 49, 47, 106, 63, 0, 13, 81, 102, 101, 108, 114, 97, 107, 116, 97, 109, 32, 35, 66, 37, 48, 37, 89, 15, 81, 107, 55, 107, 57, 47, 49, 107, 87, 47, 107, 63, 0, 13, 81, 102, 101, 108, 101, 106, 116, 107, 101, 122, 116, 101, 109, 32, 22, 66, 37, 48, 37, 89, 15, 52, 107, 74, 107, 79, 0, 13, 81, 114, 101, 99, 115, 101, 103, 32, 14, 139, 1, 11, 20, 9, 22, 195, 161, 12, 20, 1, 13, 13, 10, 135, 11, 5, 26, 195, 169, 2, 5, 13, 28, 66, 37, 48, 37, 89, 15, 82, 112, 55, 47, 39, 86, 37, 49, 0, 13, 81, 118, 195, 161, 108, 116, 111, 122, 105, 107, 32, 40, 66, 37, 48, 37, 89, 15, 49, 107, 55, 12, 15, 81, 37, 86, 107, 47, 50, 37, 109, 49, 0, 13, 82, 107, 101, 108, 108, 32, 102, 105, 122, 101, 116, 110, 105, 195, 188, 107, 32, 29, 66, 37, 48, 37, 89, 15, 107, 55, 37, 89, 63, 107, 52, 47, 107, 0, 13, 81, 101, 108, 105, 115, 109, 101, 114, 116, 101, 32, 23, 66, 37, 48, 37, 89, 10, 6, 15, 106, 49, 106, 47, 12, 0, 13, 81, 97, 107, 97, 100, 116, 32, 9, 198, 52, 20, 129, 16, 226, 64, 13, 9, 198, 44, 146, 149, 80, 226, 64, 13, 9, 198, 24, 150, 133, 80, 226, 64, 13, 9, 198, 52, 20, 129, 16, 226, 64, 13, 9, 198, 52, 243, 132, 80, 18, 192, 13, 9, 198, 36, 225, 21, 48, 226, 64, 13, 9, 134, 1, 2, 2, 195, 179, 12, 13, 5, 194, 37, 48, 13, 6, 195, 56, 82, 201, 13, 5, 194, 37, 48, 72, 0, 10, 199, 57, 147, 205, 61, 37, 76, 80, 13, 13, 138, 11, 195, 169, 16, 5, 26, 14, 195, 169, 11, 13, 49, 8, 3, 195, 169, 12, 15, 11, 18, 1, 117, 111, 55, 39, 49, 52, 106, 23, 105, 106, 87, 50, 112, 55, 105, 106, 47, 50, 112, 49, 0, 13, 81, 104, 97, 115, 122, 110, 195, 161, 108, 104, 97, 116, 110, 195, 161, 107, 32, 13, 138, 8, 1, 19, 26, 14, 195, 161, 12, 15, 11, 13, 0, 16, 141, 11, 9, 16, 18, 195, 179, 2, 195, 161, 12, 20, 1, 13, 13, 7, 196, 52, 20, 129, 16, 13, 9, 134, 20, 5, 18, 195, 169, 14, 13, 0, 11, 136, 19, 26, 195, 179, 12, 20, 1, 11, 13, 13, 138, 8, 1, 19, 26, 14, 195, 161, 12, 15, 13, 13, 11, 135, 5, 12, 5, 10, 195, 169, 14, 20, 13, 0, 17, 142, 8, 1, 12, 12, 7, 1, 20, 195, 179, 11, 20, 195, 179, 12, 13, 9, 198, 21, 49, 84, 8, 83, 128, 13, 9, 198, 80, 83, 5, 24, 243, 128, 13, 14, 139, 6, 9, 7, 25, 5, 12, 13, 195, 169, 2, 5, 13, 10, 3, 95, 51, 5, 105, 112, 52, 63, 0, 0, 13, 138, 8, 197, 145, 2, 195, 182, 18, 195, 182, 7, 13, 28, 153, 1, 11, 1, 4, 195, 161, 12, 25, 13, 5, 14, 20, 5, 19, 195, 173, 20, 195, 169, 19, 195, 169, 8, 5, 26, 13, 11, 136, 5, 7, 25, 19, 195, 169, 7, 5, 13, 10, 199, 52, 20, 129, 17, 69, 78, 44, 13, 10, 199, 24, 244, 137, 57, 69, 78, 44, 13, 11, 136, 20, 195, 161, 18, 15, 12, 14, 9, 13, 0, 16, 141, 11, 9, 11, 195, 169, 18, 4, 5, 26, 14, 195, 169, 13, 13, 11, 136, 7, 25, 5, 14, 7, 195, 188, 12, 13, 8, 133, 20, 5, 22, 197, 145, 13, 0, 15, 140, 18, 5, 11, 12, 195, 161, 13, 3, 19, 195, 173, 11, 13, 8, 197, 80, 21, 129, 49, 144, 13, 0, 39, 6, 9, 19, 13, 195, 169, 20, 37, 89, 63, 111, 47, 10, 6, 15, 81, 107, 55, 63, 107, 52, 109, 55, 47, 0, 13, 81, 102, 101, 108, 109, 101, 114, 195, 188, 108, 116, 32, 22, 66, 20, 192, 107, 55, 23, 48, 111, 50, 87, 47, 0, 13, 81, 112, 195, 169, 110, 122, 116, 32, 27, 66, 20, 192, 107, 55, 23, 106, 6, 15, 81, 111, 52, 81, 37, 0, 13, 82, 97, 32, 102, 195, 169, 114, 102, 105, 32, 27, 66, 20, 192, 107, 55, 23, 63, 37, 50, 70, 107, 50, 49, 37, 0, 13, 81, 109, 105, 110, 100, 101, 110, 107, 105, 32, 25, 66, 20, 192, 107, 55, 10, 6, 15, 50, 107, 49, 47, 107, 49, 0, 13, 81, 110, 101, 107, 116, 101, 107, 32, 35, 66, 20, 192, 107, 55, 6, 23, 106, 6, 15, 52, 107, 50, 70, 116, 52, 108, 49, 0, 13, 82, 97, 32, 114, 101, 110, 100, 197, 145, 114, 195, 182, 107, 32, 30, 67, 25, 84, 129, 81, 40, 52, 106, 23, 70, 39, 55, 79, 39, 49, 106, 47, 0, 13, 81, 100, 111, 108, 103, 111, 107, 97, 116, 32, 30, 6, 9, 19, 13, 195, 169, 20, 37, 89, 63, 111, 47, 23, 107, 55, 107, 52, 107, 70, 0, 13, 81, 101, 108, 101, 114, 101, 100, 32, 6, 195, 25, 84, 129, 13, 14, 139, 22, 195, 161, 19, 195, 161, 18, 15, 12, 14, 9, 13, 5, 194, 20, 192, 13, 14, 66, 36, 64, 37, 70, 116, 89, 107, 69, 12, 0, 25, 9, 14, 3, 95, 54, 17, 105, 106, 47, 39, 70, 37, 49, 106, 0, 0, 15, 140, 5, 12, 12, 5, 14, 197, 145, 18, 9, 26, 14, 9, 13, 8, 133, 7, 18, 195, 179, 6, 13, 9, 3, 95, 50, 48, 105, 114, 87, 0, 0, 14, 139, 5, 12, 18, 5, 14, 4, 5, 26, 195, 169, 19, 13, 12, 137, 4, 15, 11, 20, 15, 18, 14, 197, 145, 13, 14, 139, 19, 5, 12, 5, 10, 20, 5, 26, 195, 169, 19, 13, 0, 20, 145, 9, 14, 4, 195, 173, 20, 22, 195, 161, 14, 25, 15, 11, 18, 195, 179, 12, 13, 30, 69, 4, 192, 80, 84, 192, 106, 55, 106, 48, 40, 55, 23, 82, 107, 50, 12, 37, 107, 0, 13, 81, 118, 101, 110, 110, 105, 101, 32, 8, 197, 8, 83, 142, 20, 64, 13, 8, 197, 4, 192, 80, 84, 192, 13, 11, 136, 4, 195, 182, 14, 20, 195, 169, 19, 13, 0, 14, 139, 11, 195, 182, 19, 26, 195, 182, 14, 195, 182, 13, 13, 0, 9, 134, 195, 169, 18, 20, 9, 11, 13, 10, 199, 80, 84, 133, 53, 68, 197, 56, 13, 9, 134, 14, 195, 169, 26, 9, 11, 13, 0, 44, 11, 22, 9, 19, 19, 26, 1, 5, 19, 195, 169, 19, 82, 37, 87, 12, 106, 107, 89, 111, 89, 23, 105, 106, 47, 112, 89, 106, 37, 47, 0, 13, 81, 104, 97, 116, 195, 161, 115, 97, 105, 116, 32, 27, 7, 14, 25, 195, 173, 12, 9, 11, 65, 110, 55, 37, 49, 15, 106, 52, 52, 106, 0, 13, 81, 97, 114, 114, 97, 32, 11, 200, 36, 229, 5, 72, 225, 84, 20, 224, 13, 14, 68, 29, 148, 197, 88, 77, 107, 89, 107, 82, 0, 42, 42, 11, 5, 95, 35, 45, 1, 9, 106, 37, 0, 21, 12, 3, 95, 53, 15, 108, 47, 108, 70, 37, 49, 0, 0, 0, 9, 198, 80, 18, 193, 72, 160, 64, 13, 9, 198, 4, 212, 21, 48, 192, 64, 13, 9, 134, 14, 25, 195, 186, 10, 20, 13, 13, 4, 95, 13, 3, 14, 63, 106, 49, 52, 39, 50, 0, 14, 3, 95, 55, 17, 105, 107, 47, 107, 70, 37, 49, 107, 0, 0, 13, 138, 20, 195, 182, 18, 20, 195, 169, 14, 9, 11, 13, 0, 11, 200, 77, 161, 75, 80, 244, 146, 4, 192, 13, 10, 135, 18, 195, 169, 7, 9, 5, 11, 13, 0, 9, 134, 6, 197, 145, 26, 14, 9, 13, 23, 67, 37, 69, 0, 37, 47, 12, 23, 89, 107, 50, 49, 37, 0, 13, 81, 115, 101, 110, 107, 105, 32, 17, 67, 37, 69, 0, 37, 47, 12, 23, 37, 89, 0, 13, 81, 105, 115, 32, 29, 67, 37, 69, 0, 37, 47, 12, 23, 39, 55, 82, 106, 89, 47, 106, 63, 0, 13, 81, 111, 108, 118, 97, 115, 116, 97, 109, 32, 23, 67, 37, 69, 0, 37, 47, 12, 55, 112, 47, 12, 106, 0, 13, 81, 108, 195, 161, 116, 116, 97, 32, 9, 134, 14, 195, 169, 26, 14, 9, 13, 6, 195, 37, 69, 0, 13, 8, 133, 5, 12, 195, 182, 12, 13, 0, 0, 9, 134, 15, 12, 3, 19, 195, 179, 13, 14, 203, 60, 179, 211, 80, 83, 5, 24, 243, 142, 4, 192, 13, 12, 201, 52, 81, 212, 21, 68, 218, 21, 69, 0, 13, 0, 10, 135, 14, 25, 21, 7, 22, 195, 179, 13, 12, 201, 8, 83, 211, 105, 67, 212, 80, 160, 73, 13, 12, 137, 2, 15, 20, 18, 195, 161, 14, 25, 1, 13, 13, 3, 95, 54, 15, 105, 106, 47, 39, 70, 37, 49, 0, 0, 13, 138, 20, 195, 182, 18, 20, 195, 169, 14, 14, 9, 13, 40, 13, 11, 9, 1, 4, 195, 161, 19, 15, 11, 2, 195, 179, 12, 49, 37, 106, 70, 112, 89, 39, 49, 69, 113, 55, 23, 106, 105, 39, 86, 0, 13, 81, 97, 104, 104, 111, 122, 32, 13, 138, 20, 195, 182, 18, 20, 195, 169, 14, 14, 9, 13, 0, 17, 142, 16, 9, 12, 12, 1, 14, 1, 20, 15, 11, 2, 195, 179, 12, 13, 0, 9, 198, 32, 20, 141, 4, 66, 75, 13, 0, 6, 195, 24, 84, 211, 13, 0, 8, 197, 24, 241, 206, 4, 176, 76, 8, 197, 88, 149, 20, 20, 208, 13, 8, 197, 44, 83, 5, 80, 144, 13, 13, 138, 8, 195, 161, 20, 18, 195, 161, 14, 25, 1, 13, 8, 197, 60, 179, 218, 104, 16, 13, 8, 133, 4, 195, 186, 12, 20, 13, 0, 9, 198, 8, 195, 203, 44, 242, 192, 13, 6, 195, 44, 20, 0, 13, 0, 16, 141, 5, 19, 26, 11, 195, 182, 26, 195, 182, 11, 195, 182, 14, 13, 11, 136, 13, 5, 7, 25, 195, 169, 2, 5, 13, 10, 199, 32, 85, 9, 48, 20, 15, 44, 13, 6, 195, 24, 84, 212, 13, 0, 9, 198, 80, 84, 218, 80, 85, 0, 13, 7, 196, 44, 84, 133, 76, 13, 7, 196, 44, 84, 133, 76, 13, 13, 3, 95, 55, 15, 105, 107, 47, 107, 70, 37, 49, 0, 0, 12, 201, 72, 17, 193, 77, 162, 207, 16, 226, 64, 13, 13, 138, 8, 1, 19, 26, 14, 195, 161, 12, 10, 1, 13, 11, 136, 20, 195, 161, 18, 7, 25, 1, 11, 13, 8, 197, 84, 115, 210, 56, 144, 13, 6, 195, 60, 179, 218, 13, 0, 7, 66, 29, 144, 77, 111, 0, 14, 139, 16, 18, 5, 6, 5, 18, 195, 161, 12, 10, 1, 13, 9, 198, 32, 21, 129, 104, 146, 192, 13, 9, 198, 4, 176, 82, 56, 18, 192, 13, 9, 198, 44, 86, 133, 48, 226, 64, 13, 9, 198, 56, 85, 133, 104, 146, 192, 13, 9, 198, 24, 241, 193, 16, 226, 64, 13, 12, 137, 4, 15, 12, 7, 15, 26, 195, 179, 11, 13, 9, 134, 14, 25, 195, 186, 12, 20, 13, 14, 3, 95, 49, 17, 107, 77, 12, 107, 70, 37, 49, 107, 0, 0, 13, 138, 14, 195, 182, 22, 5, 11, 19, 26, 9, 11, 13, 11, 136, 3, 19, 5, 18, 195, 169, 2, 5, 13, 12, 201, 32, 20, 132, 88, 84, 133, 44, 85, 0, 13, 14, 203, 80, 20, 1, 77, 165, 1, 48, 21, 21, 56, 176, 13, 9, 198, 52, 241, 5, 48, 193, 75, 13, 17, 142, 195, 169, 18, 20, 5, 12, 13, 5, 26, 14, 195, 188, 14, 11, 13, 10, 199, 77, 161, 82, 21, 1, 76, 80, 13, 13, 138, 20, 195, 182, 18, 5, 11, 19, 26, 9, 11, 13, 10, 135, 12, 195, 179, 7, 15, 20, 20, 13, 10, 135, 19, 26, 195, 161, 12, 12, 20, 13, 0, 10, 135, 11, 12, 195, 179, 14, 15, 11, 13, 32, 6, 195, 186, 10, 1, 2, 2, 114, 57, 106, 69, 12, 23, 81, 107, 55, 106, 70, 106, 47, 0, 13, 81, 102, 101, 108, 97, 100, 97, 116, 32, 7, 196, 80, 84, 133, 80, 13, 12, 137, 3, 5, 12, 12, 195, 161, 11, 18, 1, 13, 16, 141, 195, 161, 12, 12, 195, 161, 19, 16, 15, 14, 20, 10, 1, 13, 8, 133, 22, 195, 169, 7, 5, 13, 0, 32, 10, 8, 1, 20, 195, 161, 18, 15, 26, 26, 1, 105, 106, 47, 112, 52, 39, 86, 86, 106, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 17, 142, 22, 9, 26, 19, 7, 195, 161, 12, 1, 20, 15, 11, 18, 1, 13, 13, 138, 11, 195, 173, 22, 195, 161, 14, 3, 19, 9, 13, 0, 14, 139, 12, 195, 182, 11, 195, 169, 19, 5, 11, 18, 5, 13, 52, 13, 13, 5, 7, 14, 195, 182, 22, 5, 11, 19, 26, 9, 11, 63, 107, 79, 50, 108, 82, 107, 49, 87, 37, 49, 23, 106, 23, 81, 107, 55, 105, 116, 86, 107, 47, 0, 13, 82, 97, 32, 102, 101, 108, 104, 197, 145, 122, 101, 116, 32, 9, 134, 195, 188, 7, 25, 5, 20, 13, 12, 137, 5, 12, 22, 195, 169, 7, 26, 9, 11, 13, 18, 143, 8, 15, 26, 26, 195, 161, 20, 1, 18, 20, 15, 26, 195, 179, 9, 13, 9, 134, 6, 195, 169, 14, 25, 20, 13, 9, 3, 95, 55, 5, 105, 107, 47, 0, 0, 13, 138, 5, 18, 197, 145, 19, 195, 182, 4, 9, 11, 13, 10, 199, 24, 83, 18, 4, 181, 1, 52, 13, 15, 140, 195, 169, 16, 195, 188, 12, 5, 20, 195, 169, 2, 5, 13, 15, 140, 11, 195, 169, 18, 4, 195, 169, 19, 5, 11, 18, 5, 13, 13, 138, 22, 195, 161, 18, 8, 1, 20, 195, 179, 11, 13, 0, 11, 200, 77, 1, 67, 36, 98, 75, 85, 48, 13, 60, 13, 8, 195, 161, 12, 195, 179, 26, 1, 20, 15, 11, 18, 1, 105, 112, 55, 113, 86, 106, 47, 39, 49, 52, 106, 23, 74, 106, 47, 55, 106, 49, 39, 86, 105, 106, 47, 40, 50, 49, 0, 13, 81, 99, 115, 97, 116, 108, 97, 107, 111, 122, 104, 97, 116, 117, 110, 107, 32, 7, 196, 32, 83, 25, 80, 13, 7, 196, 24, 243, 25, 80, 13, 15, 3, 95, 48, 15, 50, 6, 40, 55, 55, 106, 70, 37, 49, 0, 0, 22, 67, 20, 225, 0, 114, 57, 89, 4, 39, 52, 0, 44, 82, 111, 102, 32, 108, 105, 110, 101, 32, 17, 142, 5, 12, 22, 195, 169, 7, 26, 195, 169, 19, 195, 169, 2, 5, 13, 8, 195, 37, 5, 22, 17, 42, 42, 0, 18, 143, 195, 169, 12, 5, 12, 13, 9, 19, 26, 5, 18, 5, 11, 18, 5, 13, 14, 139, 22, 1, 18, 9, 195, 161, 14, 19, 19, 195, 161, 13, 5, 194, 44, 32, 13, 10, 135, 19, 26, 197, 177, 18, 197, 145, 13, 10, 135, 19, 26, 195, 179, 12, 14, 9, 13, 5, 194, 20, 224, 13, 5, 194, 20, 224, 72, 16, 66, 44, 32, 49, 108, 52, 109, 55, 69, 107, 55, 109, 55, 0, 25, 0, 10, 199, 4, 192, 80, 61, 165, 1, 52, 13, 10, 199, 28, 243, 132, 60, 197, 1, 52, 13, 14, 139, 19, 26, 1, 2, 2, 22, 195, 161, 14, 25, 20, 13, 15, 140, 6, 5, 12, 5, 12, 197, 145, 19, 195, 169, 7, 5, 13, 15, 4, 95, 48, 90, 53, 87, 112, 86, 107, 86, 52, 107, 70, 0, 13, 3, 95, 51, 88, 105, 106, 52, 63, 37, 50, 117, 0, 0, 16, 141, 12, 5, 22, 5, 26, 195, 169, 14, 25, 5, 12, 14, 9, 13, 7, 196, 20, 197, 133, 44, 13, 12, 137, 12, 5, 7, 25, 197, 145, 26, 14, 9, 13, 12, 137, 2, 1, 2, 18, 195, 161, 12, 14, 9, 13, 7, 196, 104, 21, 129, 72, 13, 7, 132, 20, 195, 169, 12, 20, 15, 4, 95, 48, 90, 52, 47, 110, 86, 107, 86, 52, 107, 70, 0, 9, 3, 95, 48, 67, 87, 112, 86, 0, 0, 10, 135, 195, 188, 12, 10, 195, 182, 14, 13, 9, 134, 22, 195, 169, 12, 20, 5, 13, 18, 4, 95, 48, 90, 55, 47, 110, 86, 63, 37, 55, 37, 39, 63, 39, 70, 0, 0, 14, 139, 22, 5, 19, 26, 20, 5, 19, 195, 169, 7, 5, 13, 9, 198, 52, 20, 129, 17, 96, 64, 13, 9, 198, 16, 20, 129, 9, 32, 64, 13, 15, 4, 95, 48, 90, 54, 63, 37, 55, 37, 39, 63, 39, 70, 0, 0, 15, 140, 11, 9, 16, 18, 195, 179, 2, 195, 161, 12, 14, 9, 13, 57, 15, 195, 161, 12, 12, 195, 161, 19, 16, 15, 14, 20, 15, 13, 1, 20, 112, 55, 12, 112, 89, 48, 39, 50, 47, 39, 63, 106, 47, 23, 105, 106, 50, 79, 39, 87, 47, 106, 47, 39, 63, 0, 13, 81, 104, 97, 110, 103, 111, 122, 116, 97, 116, 111, 109, 32, 15, 140, 12, 5, 8, 5, 20, 197, 145, 19, 195, 169, 7, 5, 13, 8, 133, 9, 4, 195, 169, 14, 22, 12, 4, 95, 48, 90, 49, 47, 37, 86, 107, 70, 0, 0, 10, 135, 13, 15, 19, 14, 195, 169, 11, 13, 9, 198, 52, 147, 132, 20, 229, 0, 13, 24, 5, 14, 195, 169, 8, 1, 50, 111, 105, 106, 15, 82, 107, 55, 107, 0, 13, 81, 118, 101, 108, 101, 32, 10, 135, 18, 195, 169, 19, 26, 5, 11, 13, 12, 137, 11, 9, 1, 2, 195, 161, 12, 20, 1, 13, 9, 198, 52, 147, 132, 20, 229, 0, 11, 16, 3, 95, 57, 15, 49, 37, 55, 107, 50, 117, 107, 70, 37, 49, 0, 0, 10, 135, 11, 195, 182, 26, 2, 5, 14, 13, 28, 7, 11, 195, 182, 26, 2, 5, 14, 49, 108, 86, 69, 107, 50, 10, 6, 15, 89, 107, 63, 0, 13, 81, 115, 101, 109, 32, 45, 70, 72, 81, 199, 20, 196, 133, 52, 107, 79, 12, 107, 55, 52, 36, 23, 111, 69, 52, 107, 70, 105, 107, 47, 109, 50, 49, 0, 13, 81, 195, 169, 98, 114, 101, 100, 104, 101, 116, 195, 188, 110, 107, 32, 35, 70, 72, 81, 199, 20, 196, 133, 52, 107, 79, 12, 107, 55, 52, 107, 23, 63, 107, 79, 105, 106, 55, 47, 0, 13, 81, 109, 101, 103, 104, 97, 108, 116, 32, 13, 138, 8, 9, 195, 161, 14, 25, 15, 12, 20, 1, 13, 12, 4, 95, 48, 90, 51, 107, 86, 52, 107, 70, 0, 0, 47, 9, 8, 5, 12, 25, 195, 169, 14, 5, 11, 105, 107, 57, 111, 50, 107, 49, 23, 63, 107, 79, 47, 106, 55, 112, 55, 112, 89, 106, 0, 13, 81, 109, 101, 103, 116, 97, 108, 195, 161, 108, 195, 161, 115, 97, 32, 14, 139, 22, 195, 161, 12, 1, 19, 26, 15, 12, 20, 1, 13, 17, 66, 37, 96, 50, 111, 77, 12, 107, 55, 0, 44, 42, 81, 101, 108, 32, 12, 4, 95, 48, 90, 50, 87, 112, 86, 106, 70, 0, 0, 7, 195, 88, 243, 20, 13, 22, 28, 67, 88, 243, 20, 82, 39, 55, 47, 10, 6, 15, 105, 106, 55, 39, 47, 12, 0, 13, 81, 104, 97, 108, 111, 116, 116, 32, 25, 67, 88, 243, 20, 82, 39, 55, 47, 10, 6, 15, 39, 57, 106, 50, 0, 13, 81, 111, 108, 121, 97, 110, 32, 36, 67, 88, 243, 20, 82, 39, 55, 47, 10, 6, 15, 107, 55, 81, 39, 79, 55, 106, 55, 82, 106, 0, 13, 81, 101, 108, 102, 111, 103, 108, 97, 108, 118, 97, 32, 9, 134, 14, 197, 145, 14, 5, 11, 13, 39, 71, 24, 241, 204, 4, 197, 1, 44, 81, 39, 79, 55, 106, 55, 47, 106, 49, 10, 6, 15, 112, 55, 12, 112, 89, 47, 0, 13, 81, 195, 161, 108, 108, 195, 161, 115, 116, 32, 22, 67, 88, 243, 20, 82, 39, 55, 47, 15, 107, 52, 52, 107, 0, 13, 81, 101, 114, 114, 101, 32, 15, 140, 11, 9, 6, 15, 7, 195, 161, 19, 15, 12, 20, 1, 13, 6, 195, 44, 81, 4, 20, 0, 14, 139, 9, 7, 195, 169, 14, 25, 5, 9, 14, 5, 11, 13, 11, 136, 8, 195, 161, 26, 2, 195, 179, 12, 13, 12, 137, 5, 12, 195, 161, 18, 21, 12, 20, 1, 13, 10, 135, 8, 9, 20, 20, 195, 169, 11, 13, 0, 14, 3, 226, 136, 158, 82, 107, 79, 47, 107, 55, 107, 50, 0, 38, 10, 12, 5, 8, 5, 20, 197, 145, 22, 195, 169, 55, 107, 105, 107, 47, 116, 82, 111, 23, 47, 111, 47, 107, 55, 107, 0, 13, 81, 116, 195, 169, 116, 101, 108, 101, 32, 14, 139, 4, 18, 195, 161, 7, 195, 161, 2, 2, 1, 14, 13, 8, 197, 72, 18, 207, 81, 64, 13, 36, 10, 12, 5, 8, 5, 20, 197, 145, 22, 195, 169, 55, 107, 105, 107, 47, 116, 82, 111, 23, 47, 107, 50, 12, 111, 0, 13, 81, 116, 101, 110, 110, 195, 169, 32, 23, 67, 88, 84, 218, 82, 107, 87, 23, 52, 111, 87, 47, 0, 13, 81, 114, 195, 169, 115, 122, 116, 32, 15, 140, 8, 1, 12, 12, 7, 1, 20, 195, 179, 14, 1, 11, 13, 28, 69, 4, 227, 153, 37, 64, 106, 65, 65, 37, 47, 47, 40, 70, 40, 50, 49, 0, 76, 81, 116, 117, 100, 117, 110, 107, 32, 13, 138, 15, 18, 4, 9, 2, 195, 161, 12, 20, 1, 13, 10, 135, 9, 4, 5, 10, 195, 169, 14, 13, 6, 195, 88, 84, 218, 13, 10, 135, 197, 145, 19, 26, 195, 169, 14, 20, 0, 14, 139, 195, 169, 18, 20, 195, 169, 11, 5, 12, 20, 5, 13, 0, 15, 3, 226, 137, 160, 50, 107, 63, 107, 77, 107, 50, 55, 116, 0, 19, 67, 9, 81, 192, 69, 40, 79, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 13, 138, 14, 25, 15, 13, 20, 1, 20, 195, 179, 11, 13, 10, 135, 13, 195, 182, 7, 195, 188, 12, 13, 0, 53, 11, 3, 19, 197, 145, 4, 10, 195, 169, 14, 5, 11, 74, 116, 77, 12, 111, 50, 107, 49, 23, 107, 55, 49, 107, 52, 109, 55, 111, 89, 111, 52, 107, 0, 13, 81, 101, 108, 107, 101, 114, 195, 188, 108, 195, 169, 115, 195, 169, 114, 101, 32, 13, 138, 195, 182, 22, 5, 26, 5, 20, 2, 5, 14, 13, 14, 139, 13, 5, 8, 5, 20, 14, 195, 169, 14, 5, 11, 13, 14, 139, 11, 195, 182, 26, 195, 182, 12, 20, 195, 169, 11, 13, 10, 135, 10, 195, 161, 18, 21, 14, 11, 13, 13, 138, 1, 4, 195, 179, 26, 195, 161, 19, 195, 186, 13, 11, 136, 14, 195, 169, 12, 11, 195, 188, 12, 13, 0, 12, 3, 226, 136, 154, 77, 108, 49, 57, 107, 55, 0, 8, 197, 8, 243, 20, 61, 64, 13, 18, 143, 15, 18, 19, 26, 195, 161, 7, 18, 195, 169, 19, 26, 2, 5, 14, 13, 9, 198, 44, 148, 129, 44, 21, 1, 13, 15, 140, 20, 1, 12, 195, 161, 12, 8, 1, 20, 195, 179, 11, 13, 6, 195, 32, 148, 218, 13, 0, 14, 139, 18, 195, 182, 7, 26, 195, 173, 20, 5, 14, 9, 13, 5, 194, 36, 112, 13, 14, 3, 95, 52, 17, 50, 107, 77, 107, 70, 37, 49, 107, 0, 0, 6, 195, 44, 83, 12, 13, 24, 67, 44, 83, 12, 49, 107, 55, 12, 23, 82, 107, 50, 12, 37, 0, 13, 81, 118, 101, 110, 110, 105, 32, 28, 67, 44, 83, 12, 49, 107, 55, 12, 23, 81, 39, 79, 106, 70, 50, 37, 0, 13, 81, 102, 111, 103, 97, 100, 110, 105, 32, 25, 67, 44, 83, 12, 49, 107, 55, 12, 23, 49, 108, 47, 50, 37, 0, 13, 81, 107, 195, 182, 116, 110, 105, 32, 32, 67, 44, 83, 12, 49, 107, 55, 12, 23, 39, 49, 47, 106, 47, 50, 37, 40, 49, 0, 13, 81, 111, 107, 116, 97, 116, 110, 105, 117, 107, 32, 32, 67, 44, 83, 12, 49, 107, 55, 12, 23, 105, 106, 52, 117, 39, 55, 50, 37, 106, 0, 13, 81, 104, 97, 114, 99, 111, 108, 110, 105, 97, 32, 17, 142, 5, 12, 4, 195, 182, 14, 20, 195, 182, 20, 20, 195, 169, 11, 13, 12, 201, 72, 16, 143, 76, 179, 196, 61, 69, 0, 13, 6, 195, 40, 83, 0, 13, 6, 195, 52, 244, 212, 13, 0, 12, 137, 2, 5, 19, 26, 195, 169, 12, 14, 9, 13, 7, 196, 48, 244, 14, 36, 13, 0, 8, 197, 8, 19, 139, 40, 16, 13, 17, 142, 20, 21, 12, 1, 10, 4, 15, 14, 195, 173, 20, 1, 14, 9, 13, 8, 197, 37, 51, 69, 72, 144, 13, 13, 138, 195, 161, 20, 16, 1, 11, 15, 12, 14, 9, 13, 9, 198, 28, 243, 132, 60, 195, 137, 13, 9, 198, 28, 243, 132, 60, 194, 129, 13, 8, 197, 77, 161, 82, 80, 80, 13, 7, 132, 6, 195, 161, 11, 13, 0, 31, 67, 48, 20, 0, 55, 106, 48, 9, 15, 47, 107, 47, 107, 57, 111, 52, 107, 0, 13, 81, 116, 101, 116, 101, 106, 195, 169, 114, 101, 32, 6, 195, 48, 20, 0, 13, 7, 132, 6, 195, 161, 10, 13, 7, 195, 56, 242, 1, 72, 8, 0, 15, 140, 19, 26, 1, 2, 195, 161, 12, 25, 15, 26, 14, 9, 13, 21, 146, 13, 5, 7, 22, 195, 161, 19, 195, 161, 18, 15, 12, 8, 1, 20, 195, 179, 11, 13, 15, 140, 18, 195, 161, 2, 5, 19, 26, 195, 169, 12, 14, 9, 13, 12, 201, 24, 83, 1, 16, 21, 15, 44, 21, 0, 13, 10, 199, 40, 21, 129, 76, 243, 10, 4, 13, 11, 136, 195, 161, 6, 1, 1, 58, 6, 1, 42, 0, 11, 200, 60, 197, 129, 76, 112, 84, 88, 16, 13, 22, 147, 13, 15, 2, 9, 12, 19, 26, 15, 12, 7, 195, 161, 12, 20, 1, 20, 195, 179, 11, 13, 9, 134, 11, 195, 161, 15, 19, 26, 13, 0, 11, 3, 226, 136, 146, 63, 37, 50, 40, 87, 0, 9, 198, 64, 244, 148, 60, 195, 137, 13, 8, 197, 20, 165, 5, 56, 144, 13, 0, 10, 135, 22, 195, 169, 7, 26, 5, 13, 13, 15, 140, 9, 14, 4, 195, 173, 20, 195, 161, 19, 11, 15, 18, 13, 13, 3, 95, 53, 17, 108, 47, 108, 70, 37, 49, 107, 0, 0, 9, 134, 6, 197, 145, 14, 5, 11, 13, 13, 138, 14, 25, 195, 186, 10, 20, 1, 14, 1, 11, 13, 10, 199, 52, 81, 205, 60, 225, 10, 4, 13, 8, 133, 9, 4, 195, 169, 26, 13, 10, 135, 3, 19, 9, 14, 195, 161, 12, 13, 9, 3, 95, 49, 48, 47, 110, 86, 0, 0, 11, 200, 76, 84, 139, 20, 229, 5, 56, 144, 13, 7, 196, 16, 149, 129, 80, 13, 7, 132, 8, 195, 169, 20, 13, 0, 15, 140, 11, 5, 18, 195, 188, 12, 14, 195, 169, 14, 5, 11, 13, 7, 132, 6, 197, 145, 19, 13, 11, 136, 10, 195, 161, 20, 19, 26, 9, 11, 13, 6, 195, 41, 85, 0, 13, 0, 11, 136, 13, 5, 13, 2, 18, 195, 161, 14, 13, 9, 134, 195, 169, 16, 195, 173, 20, 13, 12, 4, 8, 195, 169, 22, 105, 111, 82, 0, 42, 42, 0, 19, 71, 44, 147, 15, 29, 32, 77, 52, 107, 105, 108, 111, 103, 114, 97, 109, 0, 29, 27, 4, 5, 19, 197, 145, 107, 89, 116, 23, 52, 111, 87, 111, 47, 0, 13, 81, 114, 195, 169, 115, 122, 195, 169, 116, 32, 29, 4, 5, 19, 197, 145, 107, 89, 116, 23, 48, 39, 50, 78, 106, 37, 50, 0, 13, 81, 112, 111, 110, 116, 106, 97, 105, 110, 32, 11, 136, 20, 195, 161, 18, 8, 5, 12, 25, 13, 7, 132, 5, 19, 197, 145, 13, 0, 14, 139, 11, 15, 18, 13, 195, 161, 14, 25, 14, 1, 11, 13, 27, 4, 6, 197, 145, 20, 81, 116, 47, 23, 82, 112, 52, 40, 50, 49, 0, 13, 81, 118, 195, 161, 114, 117, 110, 107, 32, 15, 140, 18, 5, 14, 4, 19, 26, 5, 18, 18, 197, 145, 12, 13, 15, 140, 19, 26, 5, 13, 20, 1, 14, 195, 186, 22, 1, 12, 13, 7, 132, 12, 195, 169, 16, 13, 7, 132, 6, 197, 145, 20, 13, 7, 132, 6, 195, 161, 20, 13, 13, 3, 95, 52, 15, 50, 107, 77, 107, 70, 37, 49, 0, 18, 4, 95, 48, 90, 56, 87, 112, 86, 63, 37, 55, 37, 39, 63, 39, 70, 0, 0, 12, 137, 8, 1, 19, 15, 14, 12, 195, 173, 20, 13, 15, 140, 20, 1, 18, 20, 1, 12, 13, 195, 161, 14, 1, 11, 13, 9, 134, 12, 5, 12, 11, 197, 177, 13, 13, 138, 8, 1, 20, 195, 161, 18, 9, 4, 197, 145, 13, 0, 9, 198, 20, 195, 65, 72, 17, 20, 13, 13, 138, 18, 195, 169, 19, 26, 5, 19, 195, 188, 12, 13, 16, 141, 16, 18, 15, 7, 18, 1, 13, 10, 195, 161, 14, 1, 11, 13, 12, 201, 64, 19, 129, 77, 162, 207, 16, 224, 75, 13, 10, 135, 6, 195, 188, 7, 7, 197, 145, 13, 12, 137, 1, 11, 20, 21, 195, 161, 12, 9, 19, 13, 13, 138, 14, 25, 21, 7, 4, 195, 173, 10, 1, 20, 13, 0, 15, 140, 9, 18, 195, 161, 14, 25, 195, 173, 20, 1, 14, 9, 13, 9, 198, 16, 243, 7, 61, 162, 75, 13, 12, 3, 95, 55, 88, 105, 107, 47, 82, 107, 50, 0, 0, 10, 135, 18, 5, 195, 161, 12, 9, 19, 13, 7, 196, 64, 81, 9, 28, 13, 49, 70, 88, 148, 218, 60, 229, 0, 82, 37, 87, 39, 50, 47, 23, 107, 55, 107, 50, 79, 107, 70, 105, 107, 47, 107, 47, 55, 107, 50, 0, 13, 81, 101, 108, 101, 110, 103, 101, 100, 104, 101, 116, 101, 116, 108, 101, 110, 32, 23, 70, 88, 148, 218, 60, 229, 0, 82, 37, 87, 39, 50, 47, 23, 106, 86, 0, 13, 81, 97, 122, 32, 25, 150, 18, 5, 14, 4, 19, 26, 5, 18, 20, 5, 12, 5, 16, 195, 173, 20, 195, 169, 19, 11, 15, 18, 13, 50, 70, 88, 148, 218, 60, 229, 0, 82, 37, 87, 39, 50, 47, 23, 106, 87, 47, 23, 47, 106, 48, 106, 87, 47, 106, 55, 47, 106, 63, 0, 13, 82, 97, 122, 116, 32, 116, 97, 112, 97, 115, 122, 116, 97, 108, 116, 97, 109, 32, 9, 198, 88, 148, 218, 60, 229, 0, 13, 7, 196, 52, 20, 16, 4, 13, 7, 196, 44, 20, 20, 4, 13, 0, 17, 142, 6, 5, 12, 20, 5, 12, 5, 16, 195, 173, 20, 5, 14, 9, 13, 8, 197, 44, 20, 10, 60, 224, 13, 9, 198, 4, 192, 75, 84, 195, 137, 13, 0, 18, 143, 13, 5, 7, 22, 1, 12, 195, 179, 19, 195, 173, 20, 1, 14, 9, 13, 44, 7, 195, 161, 12, 12, 1, 13, 9, 112, 55, 12, 106, 63, 37, 10, 6, 15, 47, 112, 63, 39, 79, 106, 47, 112, 89, 106, 0, 13, 81, 116, 195, 161, 109, 111, 103, 97, 116, 195, 161, 115, 97, 32, 18, 4, 14, 195, 169, 26, 50, 111, 86, 23, 49, 37, 0, 13, 81, 107, 105, 32, 11, 136, 13, 195, 179, 4, 19, 26, 5, 18, 13, 10, 135, 7, 25, 195, 182, 18, 7, 25, 13, 9, 198, 88, 149, 1, 81, 64, 64, 13, 9, 198, 81, 81, 1, 81, 64, 64, 13, 7, 132, 14, 195, 169, 26, 13, 7, 132, 22, 195, 173, 26, 13, 0, 10, 199, 65, 35, 202, 20, 181, 10, 20, 13, 0, 22, 68, 81, 33, 78, 16, 47, 52, 107, 50, 70, 10, 6, 15, 106, 86, 0, 13, 81, 97, 122, 32, 0, 13, 138, 11, 195, 182, 22, 5, 20, 5, 12, 20, 5, 13, 9, 134, 6, 195, 182, 12, 195, 169, 13, 0, 20, 66, 37, 128, 49, 37, 55, 107, 50, 117, 12, 107, 55, 0, 44, 42, 81, 101, 108, 32, 9, 5, 95, 35, 45, 9, 11, 15, 0, 0, 6, 195, 44, 83, 20, 13, 6, 195, 24, 243, 20, 13, 0, 9, 198, 104, 18, 140, 61, 69, 0, 13, 0, 12, 137, 6, 5, 12, 195, 161, 18, 18, 1, 12, 13, 11, 136, 5, 18, 197, 145, 19, 26, 1, 11, 13, 11, 136, 13, 1, 7, 195, 161, 14, 1, 11, 13, 14, 139, 20, 5, 18, 195, 188, 12, 5, 20, 195, 169, 14, 13, 7, 132, 8, 195, 173, 7, 13, 8, 197, 44, 20, 15, 81, 64, 13, 0, 12, 137, 12, 1, 11, 14, 195, 161, 14, 1, 11, 13, 20, 145, 8, 1, 10, 12, 195, 169, 11, 20, 1, 12, 1, 14, 10, 1, 9, 14, 11, 13, 9, 198, 88, 85, 5, 81, 65, 64, 13, 12, 5, 95, 35, 45, 9, 7, 111, 37, 79, 0, 21, 0, 13, 138, 9, 4, 197, 145, 19, 26, 1, 11, 15, 11, 13, 0, 9, 198, 77, 162, 210, 37, 5, 0, 13, 9, 198, 77, 162, 210, 37, 5, 0, 13, 16, 141, 2, 5, 6, 15, 12, 25, 195, 161, 19, 15, 12, 20, 1, 13, 0, 15, 140, 4, 15, 12, 7, 15, 26, 14, 195, 161, 14, 1, 11, 13, 15, 140, 13, 5, 7, 15, 12, 4, 195, 161, 19, 14, 1, 11, 13, 11, 136, 12, 195, 161, 19, 26, 12, 195, 179, 13, 9, 198, 76, 244, 143, 104, 21, 1, 13, 13, 138, 13, 5, 7, 22, 195, 169, 4, 5, 14, 9, 13, 0, 20, 145, 6, 5, 12, 8, 1, 19, 26, 14, 195, 161, 12, 195, 179, 11, 14, 1, 11, 13, 29, 66, 52, 16, 63, 106, 15, 70, 111, 55, 107, 55, 116, 47, 12, 0, 13, 81, 100, 195, 169, 108, 101, 108, 197, 145, 116, 116, 32, 19, 144, 195, 161, 12, 12, 1, 13, 20, 9, 20, 11, 195, 161, 18, 2, 1, 14, 13, 27, 66, 52, 16, 63, 106, 15, 70, 111, 55, 40, 47, 112, 50, 0, 13, 81, 100, 195, 169, 108, 117, 116, 195, 161, 110, 32, 5, 194, 52, 16, 13, 19, 66, 36, 144, 49, 107, 47, 12, 116, 82, 107, 55, 0, 44, 42, 81, 101, 108, 32, 21, 2, 48, 48, 50, 40, 55, 12, 106, 50, 40, 55, 12, 112, 50, 0, 44, 81, 32, 110, 32, 26, 2, 48, 48, 50, 40, 55, 12, 106, 50, 40, 55, 12, 112, 47, 113, 55, 0, 44, 81, 32, 116, 195, 179, 108, 32, 21, 2, 48, 48, 50, 40, 55, 12, 106, 50, 40, 55, 12, 112, 89, 0, 44, 81, 32, 115, 32, 23, 2, 48, 48, 50, 40, 55, 12, 106, 50, 40, 55, 12, 112, 37, 79, 0, 44, 81, 32, 105, 103, 32, 15, 3, 95, 56, 17, 65, 39, 55, 117, 106, 70, 37, 49, 106, 0, 0, 22, 67, 52, 134, 128, 109, 101, 103, 97, 104, 101, 114, 99, 101, 110, 0, 44, 29, 81, 101, 110, 32, 23, 67, 52, 134, 128, 109, 101, 103, 97, 104, 101, 114, 99, 101, 110, 0, 44, 29, 42, 81, 101, 110, 32, 13, 138, 6, 9, 26, 5, 20, 14, 9, 195, 188, 11, 13, 11, 3, 95, 49, 88, 47, 37, 86, 107, 50, 0, 0, 8, 133, 195, 169, 12, 22, 5, 13, 10, 135, 1, 4, 8, 1, 20, 195, 179, 13, 0, 8, 197, 24, 241, 212, 60, 176, 76, 11, 136, 22, 195, 169, 7, 195, 169, 9, 7, 13, 8, 197, 45, 83, 3, 76, 16, 13, 68, 69, 29, 145, 78, 28, 80, 77, 107, 50, 79, 107, 15, 55, 111, 79, 63, 39, 86, 79, 112, 89, 52, 106, 23, 87, 112, 63, 110, 47, 105, 106, 47, 40, 50, 49, 0, 13, 82, 108, 195, 169, 103, 109, 111, 122, 103, 195, 161, 115, 114, 97, 32, 115, 122, 195, 161, 109, 195, 173, 116, 104, 97, 116, 117, 110, 107, 32, 19, 144, 5, 13, 2, 5, 18, 20, 195, 161, 18, 19, 1, 9, 11, 14, 1, 11, 13, 11, 136, 12, 195, 161, 20, 20, 21, 14, 11, 13, 0, 50, 9, 22, 195, 161, 18, 8, 1, 20, 195, 179, 82, 112, 52, 105, 106, 47, 113, 23, 106, 55, 106, 49, 40, 55, 112, 89, 112, 52, 113, 55, 0, 13, 81, 97, 108, 97, 107, 117, 108, 195, 161, 115, 195, 161, 114, 195, 179, 108, 32, 12, 137, 8, 1, 12, 12, 8, 1, 20, 195, 179, 13, 30, 9, 22, 195, 161, 18, 8, 1, 20, 195, 179, 82, 112, 52, 105, 106, 47, 113, 23, 107, 89, 116, 0, 13, 81, 101, 115, 197, 145, 32, 12, 137, 22, 195, 161, 18, 8, 1, 20, 195, 179, 13, 9, 198, 20, 208, 133, 73, 33, 76, 13, 9, 198, 32, 246, 142, 37, 82, 192, 13, 12, 137, 22, 195, 161, 18, 8, 1, 20, 195, 179, 13, 0, 23, 4, 195, 186, 7, 25, 114, 77, 10, 6, 15, 81, 107, 89, 47, 0, 13, 81, 102, 101, 115, 116, 32, 38, 4, 195, 186, 7, 25, 114, 77, 10, 6, 15, 111, 52, 47, 107, 55, 63, 107, 87, 47, 107, 63, 0, 13, 81, 195, 169, 114, 116, 101, 108, 109, 101, 122, 116, 101, 109, 32, 36, 4, 195, 186, 7, 25, 114, 77, 10, 6, 15, 111, 52, 47, 107, 55, 63, 107, 86, 107, 63, 0, 13, 81, 195, 169, 114, 116, 101, 108, 109, 101, 122, 101, 109, 32, 10, 199, 16, 243, 7, 61, 163, 212, 80, 13, 10, 199, 24, 83, 1, 16, 21, 15, 44, 13, 22, 4, 195, 186, 7, 25, 114, 77, 23, 105, 37, 87, 37, 0, 13, 81, 104, 105, 115, 122, 105, 32, 10, 199, 20, 211, 5, 28, 85, 14, 36, 13, 7, 132, 195, 186, 7, 25, 13, 0, 12, 137, 2, 5, 19, 26, 195, 169, 12, 22, 5, 13, 11, 200, 36, 225, 193, 80, 192, 78, 84, 176, 13, 9, 134, 195, 169, 12, 195, 169, 14, 13, 7, 132, 14, 195, 169, 12, 13, 0, 8, 197, 81, 33, 78, 16, 144, 13, 15, 140, 195, 161, 12, 12, 195, 173, 20, 8, 1, 20, 195, 179, 13, 8, 197, 81, 81, 14, 36, 16, 13, 8, 197, 44, 20, 20, 4, 176, 13, 0, 16, 141, 22, 9, 26, 19, 7, 195, 161, 12, 8, 1, 20, 195, 179, 13, 50, 9, 195, 161, 12, 12, 10, 1, 14, 1, 11, 112, 57, 57, 106, 50, 106, 49, 23, 52, 107, 50, 70, 107, 55, 49, 107, 86, 111, 89, 52, 107, 0, 13, 81, 114, 101, 110, 100, 101, 108, 107, 101, 122, 195, 169, 115, 114, 101, 32, 6, 131, 12, 197, 145, 13, 17, 2, 49, 48, 47, 110, 86, 86, 107, 55, 0, 44, 81, 32, 101, 108, 32, 15, 2, 49, 48, 47, 37, 86, 107, 47, 0, 44, 81, 32, 116, 32, 23, 2, 49, 48, 47, 110, 87, 12, 107, 52, 107, 89, 0, 44, 81, 32, 115, 122, 101, 114, 101, 115, 32, 19, 2, 49, 48, 47, 110, 87, 12, 107, 52, 0, 44, 81, 32, 115, 122, 101, 114, 32, 17, 3, 95, 57, 17, 49, 37, 55, 107, 50, 117, 107, 70, 37, 49, 107, 0, 0, 10, 199, 20, 194, 83, 52, 84, 148, 20, 13, 9, 134, 10, 195, 179, 14, 1, 11, 13, 8, 133, 195, 169, 12, 19, 26, 13, 30, 2, 49, 51, 116, 105, 122, 101, 110, 104, 97, 114, 109, 97, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 11, 3, 95, 50, 88, 105, 40, 87, 39, 50, 0, 0, 11, 136, 2, 5, 19, 26, 195, 169, 12, 20, 13, 11, 136, 2, 5, 19, 26, 195, 169, 12, 20, 13, 10, 135, 12, 195, 161, 20, 20, 21, 11, 13, 11, 136, 2, 5, 19, 26, 195, 169, 12, 20, 13, 7, 132, 14, 195, 169, 16, 13, 7, 196, 29, 147, 210, 76, 13, 7, 132, 20, 195, 169, 20, 13, 0, 20, 67, 49, 53, 0, 101, 108, 101, 115, 116, 195, 169, 110, 0, 44, 29, 42, 81, 110, 32, 20, 67, 49, 53, 0, 101, 108, 101, 115, 116, 195, 169, 107, 0, 44, 29, 42, 81, 107, 32, 15, 140, 19, 26, 195, 188, 12, 5, 19, 19, 5, 14, 5, 11, 13, 7, 132, 18, 195, 169, 19, 13, 14, 67, 49, 53, 0, 107, 55, 107, 89, 47, 111, 0, 42, 42, 0, 13, 202, 88, 243, 129, 80, 179, 218, 104, 19, 129, 44, 13, 16, 141, 18, 5, 14, 4, 197, 145, 18, 195, 182, 11, 14, 5, 11, 13, 12, 137, 9, 20, 195, 169, 12, 20, 195, 169, 11, 13, 7, 132, 22, 195, 169, 18, 13, 0, 10, 199, 88, 19, 1, 52, 149, 133, 48, 13, 11, 136, 20, 5, 18, 10, 5, 4, 197, 145, 13, 12, 137, 19, 20, 195, 173, 12, 21, 19, 195, 186, 13, 11, 136, 2, 195, 161, 14, 20, 1, 14, 9, 13, 0, 11, 136, 8, 9, 20, 5, 12, 195, 169, 20, 13, 11, 136, 195, 169, 12, 5, 20, 195, 169, 20, 13, 10, 135, 19, 26, 195, 173, 14, 5, 19, 13, 8, 133, 22, 195, 169, 12, 9, 13, 8, 133, 22, 195, 169, 12, 9, 13, 29, 2, 49, 54, 116, 105, 122, 101, 110, 104, 97, 116, 111, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 14, 3, 95, 56, 15, 65, 39, 55, 117, 106, 70, 37, 49, 0, 0, 14, 139, 9, 14, 20, 195, 169, 26, 5, 20, 2, 5, 14, 13, 46, 6, 6, 5, 12, 8, 197, 145, 81, 107, 55, 105, 116, 23, 55, 107, 87, 23, 81, 107, 55, 107, 47, 12, 109, 50, 49, 0, 13, 82, 108, 101, 115, 122, 32, 102, 101, 108, 101, 116, 116, 195, 188, 110, 107, 32, 38, 6, 6, 5, 12, 8, 197, 145, 81, 107, 55, 105, 116, 23, 82, 106, 55, 113, 87, 110, 50, 115, 0, 13, 81, 118, 97, 108, 195, 179, 115, 122, 195, 173, 110, 197, 177, 32, 16, 141, 195, 169, 19, 26, 18, 5, 22, 195, 169, 20, 5, 12, 20, 13, 13, 138, 19, 26, 195, 161, 14, 4, 195, 169, 11, 1, 13, 11, 136, 12, 5, 14, 14, 195, 169, 14, 11, 13, 6, 195, 9, 84, 218, 13, 0, 24, 66, 52, 32, 109, 101, 103, 97, 98, 195, 161, 106, 116, 116, 97, 108, 0, 44, 29, 42, 81, 97, 108, 32, 31, 7, 22, 5, 26, 5, 20, 197, 145, 82, 107, 86, 107, 47, 116, 23, 50, 116, 50, 107, 49, 0, 13, 81, 110, 197, 145, 110, 101, 107, 32, 15, 140, 5, 12, 12, 5, 14, 20, 195, 169, 20, 2, 5, 14, 13, 10, 135, 19, 26, 195, 188, 12, 197, 145, 13, 10, 135, 22, 5, 26, 5, 20, 197, 145, 13, 14, 139, 11, 5, 4, 22, 5, 26, 13, 195, 169, 14, 25, 13, 7, 132, 20, 195, 169, 18, 13, 7, 132, 14, 195, 169, 22, 13, 7, 132, 8, 195, 173, 18, 13, 15, 66, 52, 32, 63, 107, 79, 106, 69, 112, 57, 47, 0, 42, 42, 17, 2, 50, 48, 105, 114, 87, 12, 106, 55, 0, 44, 81, 32, 97, 108, 32, 25, 2, 50, 48, 104, 117, 115, 122, 97, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 22, 2, 50, 48, 104, 117, 115, 122, 97, 100, 105, 107, 97, 105, 0, 44, 21, 29, 81, 32, 105, 32, 31, 2, 49, 56, 116, 105, 122, 101, 110, 110, 121, 111, 108, 99, 97, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 0, 9, 198, 41, 85, 15, 81, 64, 75, 13, 22, 5, 16, 195, 169, 14, 26, 48, 111, 50, 86, 15, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 17, 142, 5, 24, 16, 5, 4, 195, 173, 3, 9, 195, 179, 14, 1, 11, 13, 10, 135, 9, 4, 5, 10, 195, 169, 20, 13, 16, 141, 11, 195, 182, 18, 14, 25, 5, 26, 5, 20, 2, 5, 14, 13, 8, 133, 16, 195, 169, 14, 26, 13, 31, 2, 50, 51, 104, 117, 115, 122, 111, 110, 104, 97, 114, 109, 97, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 0, 14, 139, 3, 19, 9, 14, 195, 161, 12, 10, 21, 14, 11, 13, 7, 196, 25, 35, 206, 80, 13, 7, 132, 20, 197, 145, 12, 13, 0, 12, 137, 22, 5, 26, 195, 169, 18, 195, 169, 20, 13, 13, 138, 14, 5, 22, 5, 26, 8, 5, 20, 197, 145, 13, 12, 137, 20, 1, 14, 4, 195, 173, 10, 1, 20, 13, 7, 195, 44, 101, 0, 13, 42, 8, 133, 19, 195, 169, 18, 20, 13, 0, 34, 6, 6, 5, 12, 197, 145, 12, 81, 107, 55, 116, 55, 10, 6, 15, 50, 111, 86, 86, 109, 49, 0, 13, 81, 110, 195, 169, 122, 122, 195, 188, 107, 32, 16, 141, 9, 14, 20, 5, 18, 14, 5, 20, 5, 26, 195, 169, 19, 13, 7, 132, 20, 195, 161, 14, 13, 9, 134, 6, 5, 12, 197, 145, 12, 13, 12, 7, 95, 35, 45, 9, 11, 5, 9, 107, 37, 0, 0, 10, 135, 22, 15, 12, 20, 195, 161, 12, 72, 10, 199, 77, 163, 198, 81, 97, 82, 20, 13, 33, 71, 32, 149, 129, 80, 19, 15, 76, 105, 37, 82, 106, 47, 106, 55, 39, 89, 23, 55, 107, 50, 12, 107, 0, 13, 81, 108, 101, 110, 110, 101, 32, 10, 199, 60, 179, 218, 32, 21, 20, 4, 13, 7, 132, 18, 195, 161, 13, 13, 7, 132, 18, 195, 161, 13, 13, 14, 67, 77, 64, 128, 89, 106, 47, 108, 69, 12, 37, 0, 25, 0, 33, 6, 5, 7, 195, 169, 19, 26, 107, 79, 111, 87, 23, 49, 107, 55, 12, 107, 63, 107, 89, 0, 13, 81, 107, 101, 108, 108, 101, 109, 101, 115, 32, 7, 132, 18, 197, 145, 12, 13, 18, 3, 95, 63, 63, 49, 106, 52, 106, 49, 47, 107, 34, 15, 49, 113, 70, 0, 30, 2, 50, 54, 104, 117, 115, 122, 111, 110, 104, 97, 116, 111, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 11, 6, 95, 35, 45, 195, 161, 14, 112, 50, 0, 0, 17, 142, 12, 195, 169, 20, 5, 19, 195, 173, 20, 13, 195, 169, 14, 25, 13, 11, 136, 12, 195, 169, 20, 5, 26, 9, 11, 13, 11, 136, 12, 195, 169, 20, 5, 26, 9, 11, 13, 0, 9, 198, 45, 34, 84, 36, 176, 64, 13, 13, 138, 195, 182, 20, 12, 5, 20, 20, 197, 145, 12, 13, 13, 138, 22, 1, 12, 12, 195, 179, 11, 11, 1, 12, 13, 13, 138, 16, 195, 161, 18, 20, 15, 11, 11, 1, 12, 13, 12, 137, 195, 169, 18, 20, 195, 169, 11, 5, 11, 13, 12, 66, 53, 32, 63, 37, 87, 47, 107, 52, 0, 25, 21, 2, 51, 48, 105, 106, 52, 63, 37, 50, 117, 12, 106, 55, 0, 44, 81, 32, 97, 108, 32, 22, 2, 51, 48, 105, 106, 52, 63, 37, 50, 117, 12, 106, 55, 0, 44, 81, 32, 99, 97, 108, 32, 25, 2, 51, 48, 104, 97, 114, 109, 105, 110, 99, 97, 100, 105, 107, 97, 105, 0, 44, 21, 29, 81, 32, 105, 32, 28, 2, 51, 48, 104, 97, 114, 109, 105, 110, 99, 97, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 32, 2, 50, 56, 104, 117, 115, 122, 111, 110, 110, 121, 111, 108, 99, 97, 100, 105, 107, 195, 161, 105, 103, 0, 44, 21, 29, 81, 32, 105, 103, 32, 0, 20, 145, 3, 19, 1, 16, 1, 4, 195, 169, 11, 18, 5, 14, 4, 19, 26, 5, 18, 13, 12, 3, 95, 52, 88, 50, 107, 77, 82, 107, 50, 0, 0, 40, 11, 8, 21, 12, 12, 1, 4, 195, 169, 11, 15, 11, 105, 40, 55, 12, 106, 70, 111, 49, 39, 49, 23, 74, 40, 48, 112, 50, 0, 13, 81, 99, 115, 117, 112, 195, 161, 110, 32, 24, 70, 52, 83, 12, 21, 69, 0, 63, 107, 55, 12, 107, 47, 12, 23, 106, 86, 0, 13, 81, 97, 122, 32, 38, 6, 1, 12, 1, 16, 195, 186, 106, 55, 106, 48, 114, 10, 6, 15, 52, 107, 50, 117, 107, 52, 107, 50, 0, 13, 81, 114, 101, 110, 100, 115, 122, 101, 114, 101, 110, 32, 34, 9, 195, 169, 16, 195, 188, 12, 5, 20, 5, 111, 48, 109, 55, 107, 47, 107, 23, 107, 55, 116, 47, 12, 0, 13, 81, 101, 108, 197, 145, 116, 116, 32, 18, 143, 4, 9, 195, 161, 11, 20, 195, 188, 14, 20, 5, 20, 195, 169, 19, 13, 9, 134, 1, 12, 1, 16, 195, 186, 13, 12, 137, 195, 161, 12, 4, 15, 26, 1, 20, 1, 13, 6, 131, 12, 195, 179, 13, 9, 198, 52, 83, 12, 21, 69, 0, 13, 0, 50, 8, 9, 19, 11, 15, 12, 195, 161, 11, 37, 89, 49, 39, 55, 112, 49, 23, 63, 109, 49, 108, 47, 12, 107, 47, 111, 89, 111, 47, 0, 13, 81, 109, 197, 177, 107, 195, 182, 100, 116, 101, 116, 195, 169, 115, 195, 169, 116, 32, 8, 197, 8, 195, 199, 61, 64, 13, 7, 132, 1, 4, 195, 179, 13, 7, 132, 8, 195, 161, 7, 13, 0, 11, 136, 13, 1, 7, 195, 161, 8, 15, 26, 13, 14, 139, 6, 15, 12, 25, 195, 179, 9, 18, 1, 20, 1, 13, 11, 136, 16, 15, 14, 20, 10, 195, 161, 14, 13, 13, 138, 11, 15, 18, 195, 186, 1, 11, 11, 1, 12, 13, 10, 135, 13, 195, 161, 19, 26, 14, 9, 13, 0, 70, 10, 19, 26, 5, 14, 22, 5, 4, 197, 145, 11, 87, 107, 50, 82, 107, 70, 116, 49, 23, 49, 108, 52, 111, 69, 107, 50, 23, 48, 52, 113, 69, 112, 55, 50, 112, 49, 23, 49, 37, 0, 13, 83, 107, 195, 182, 114, 195, 169, 98, 101, 110, 32, 112, 114, 195, 179, 98, 195, 161, 108, 110, 195, 161, 107, 32, 107, 105, 32, 11, 136, 11, 195, 188, 12, 4, 5, 14, 9, 13, 0, 14, 139, 11, 5, 18, 5, 19, 11, 5, 4, 197, 145, 11, 13, 7, 132, 18, 195, 161, 4, 13, 0, 53, 73, 80, 20, 148, 4, 195, 65, 44, 176, 76, 47, 106, 52, 47, 106, 55, 63, 106, 49, 12, 106, 55, 10, 6, 15, 49, 106, 48, 74, 39, 55, 106, 47, 69, 106, 50, 0, 13, 81, 107, 97, 112, 99, 115, 111, 108, 97, 116, 98, 97, 110, 32, 13, 138, 13, 5, 7, 195, 169, 18, 20, 5, 14, 9, 13, 11, 136, 13, 5, 14, 20, 195, 188, 14, 11, 13, 8, 197, 80, 21, 129, 77, 160, 20, 0, 27, 6, 18, 195, 182, 22, 9, 4, 52, 108, 82, 37, 70, 23, 106, 105, 39, 86, 0, 13, 81, 97, 104, 104, 111, 122, 32, 9, 134, 18, 195, 182, 22, 9, 4, 13, 26, 66, 48, 80, 55, 107, 10, 6, 15, 82, 39, 49, 89, 112, 47, 0, 13, 81, 118, 111, 107, 115, 195, 161, 116, 32, 19, 144, 7, 25, 195, 179, 7, 25, 21, 12, 195, 161, 19, 195, 161, 8, 15, 26, 13, 29, 66, 48, 80, 55, 107, 23, 81, 39, 79, 23, 81, 40, 47, 50, 37, 0, 13, 82, 102, 111, 103, 32, 102, 117, 116, 110, 105, 32, 6, 195, 5, 2, 129, 13, 22, 194, 48, 80, 13, 82, 107, 101, 108, 108, 32, 115, 122, 195, 182, 103, 101, 122, 110, 101, 109, 32, 17, 142, 16, 15, 12, 7, 195, 161, 18, 13, 5, 19, 20, 5, 18, 20, 13, 7, 132, 12, 195, 161, 2, 13, 5, 194, 56, 16, 72, 5, 194, 48, 80, 13, 5, 194, 36, 176, 13, 20, 2, 52, 48, 50, 107, 77, 82, 107, 50, 12, 107, 55, 0, 44, 81, 32, 101, 108, 32, 0, 22, 147, 16, 195, 169, 14, 26, 9, 14, 20, 195, 169, 26, 5, 20, 5, 11, 20, 197, 145, 12, 13, 11, 3, 95, 53, 88, 108, 47, 82, 107, 50, 0, 0, 10, 135, 15, 18, 19, 26, 195, 161, 7, 13, 30, 7, 15, 18, 19, 26, 195, 161, 7, 10, 39, 52, 87, 112, 79, 23, 81, 108, 55, 111, 0, 13, 81, 102, 195, 182, 108, 195, 169, 32, 8, 133, 20, 195, 169, 22, 5, 13, 7, 196, 32, 149, 20, 20, 13, 0, 11, 136, 8, 1, 19, 15, 14, 12, 195, 179, 13, 8, 197, 24, 241, 206, 36, 16, 13, 17, 142, 15, 16, 20, 9, 13, 1, 12, 9, 26, 195, 161, 12, 14, 9, 13, 0, 19, 67, 56, 20, 0, 50, 106, 48, 10, 6, 15, 37, 89, 0, 13, 81, 105, 115, 32, 12, 137, 2, 9, 26, 1, 11, 15, 4, 195, 179, 13, 12, 137, 20, 195, 161, 18, 15, 12, 21, 14, 11, 13, 6, 195, 56, 20, 0, 13, 0, 12, 201, 37, 51, 69, 72, 85, 5, 44, 85, 0, 13, 22, 6, 20, 195, 161, 10, 1, 11, 47, 112, 57, 106, 49, 23, 37, 89, 0, 13, 81, 105, 115, 32, 9, 198, 28, 243, 132, 60, 195, 203, 13, 10, 199, 40, 21, 129, 76, 243, 14, 36, 13, 10, 199, 77, 160, 86, 5, 163, 212, 80, 13, 13, 138, 19, 195, 186, 10, 20, 8, 1, 20, 195, 179, 13, 13, 138, 7, 25, 1, 18, 1, 16, 15, 4, 195, 179, 13, 20, 67, 36, 146, 64, 105, 112, 52, 39, 63, 12, 106, 55, 0, 44, 42, 81, 97, 108, 32, 0, 25, 150, 20, 195, 182, 18, 22, 195, 169, 14, 25, 10, 1, 22, 1, 19, 12, 1, 20, 195, 161, 8, 15, 26, 13, 9, 198, 88, 243, 129, 48, 21, 0, 13, 11, 200, 44, 145, 137, 104, 85, 14, 36, 80, 13, 39, 11, 10, 195, 161, 18, 21, 12, 195, 169, 11, 15, 19, 57, 112, 52, 40, 55, 111, 49, 39, 89, 23, 107, 55, 107, 63, 107, 49, 0, 13, 81, 101, 108, 101, 109, 101, 107, 32, 54, 11, 13, 9, 12, 12, 9, 195, 161, 18, 4, 15, 19, 63, 37, 55, 37, 112, 52, 70, 39, 89, 23, 50, 111, 48, 87, 112, 63, 55, 112, 55, 112, 89, 0, 13, 81, 110, 195, 169, 112, 115, 122, 195, 161, 109, 108, 195, 161, 108, 195, 161, 115, 32, 23, 148, 195, 182, 14, 11, 15, 18, 13, 195, 161, 14, 25, 26, 1, 20, 15, 11, 14, 195, 161, 12, 13, 18, 6, 195, 161, 14, 20, 19, 26, 112, 107, 50, 47, 111, 107, 87, 0, 42, 42, 0, 12, 137, 195, 169, 18, 11, 5, 26, 5, 20, 20, 13, 9, 198, 28, 243, 132, 60, 195, 205, 13, 9, 134, 22, 195, 161, 12, 14, 1, 13, 9, 134, 13, 5, 12, 12, 195, 169, 13, 0, 7, 132, 12, 195, 161, 26, 13, 48, 70, 32, 149, 129, 80, 19, 0, 105, 37, 82, 106, 47, 106, 55, 23, 37, 55, 12, 107, 47, 111, 49, 107, 89, 111, 82, 107, 55, 0, 13, 81, 105, 108, 108, 101, 116, 195, 169, 107, 101, 115, 195, 169, 118, 101, 108, 32, 49, 15, 2, 197, 177, 14, 3, 19, 5, 12, 5, 11, 13, 195, 169, 14, 25, 69, 109, 50, 74, 107, 55, 107, 49, 63, 111, 65, 10, 6, 15, 77, 106, 50, 114, 57, 106, 0, 13, 81, 103, 121, 97, 110, 195, 186, 106, 97, 32, 16, 141, 8, 1, 19, 26, 14, 195, 161, 12, 8, 1, 20, 195, 179, 13, 13, 138, 5, 12, 197, 145, 6, 15, 18, 4, 21, 12, 13, 12, 137, 20, 5, 18, 13, 195, 169, 11, 5, 11, 13, 16, 141, 8, 1, 19, 26, 14, 195, 161, 12, 8, 1, 20, 195, 179, 13, 9, 198, 32, 149, 129, 80, 19, 0, 13, 19, 2, 53, 48, 108, 47, 82, 107, 50, 12, 107, 55, 0, 44, 81, 32, 101, 108, 32, 0, 34, 4, 9, 4, 197, 145, 37, 70, 116, 23, 82, 106, 55, 113, 87, 110, 50, 115, 0, 13, 81, 118, 97, 108, 195, 179, 115, 122, 195, 173, 110, 197, 177, 32, 30, 4, 9, 4, 197, 145, 37, 70, 116, 23, 82, 112, 52, 105, 106, 47, 113, 0, 13, 81, 118, 195, 161, 114, 104, 97, 116, 195, 179, 32, 13, 138, 16, 15, 14, 20, 10, 195, 161, 14, 1, 11, 13, 21, 4, 9, 4, 197, 145, 37, 70, 116, 23, 55, 107, 87, 0, 13, 81, 108, 101, 115, 122, 32, 15, 140, 11, 5, 18, 195, 188, 12, 5, 20, 5, 11, 2, 5, 13, 15, 140, 5, 12, 195, 169, 18, 195, 169, 19, 195, 169, 18, 5, 13, 15, 140, 7, 25, 197, 177, 10, 20, 197, 145, 14, 5, 22, 5, 13, 7, 132, 9, 4, 197, 145, 13, 12, 3, 95, 54, 88, 105, 106, 47, 82, 106, 50, 0, 0, 22, 4, 12, 195, 161, 20, 55, 112, 47, 23, 63, 106, 57, 70, 0, 13, 81, 109, 97, 106, 100, 32, 14, 139, 195, 182, 12, 20, 195, 182, 26, 14, 195, 169, 11, 13, 17, 142, 8, 1, 19, 26, 14, 195, 161, 12, 1, 20, 1, 11, 15, 18, 13, 7, 132, 12, 195, 161, 20, 13, 7, 132, 8, 195, 161, 20, 13, 0, 8, 197, 44, 21, 137, 13, 48, 13, 13, 138, 195, 188, 26, 12, 5, 20, 5, 11, 2, 5, 13, 16, 141, 18, 195, 161, 11, 195, 169, 18, 4, 5, 26, 5, 20, 20, 13, 0, 11, 136, 8, 1, 20, 195, 161, 19, 195, 186, 13, 13, 138, 10, 15, 7, 11, 195, 182, 18, 18, 5, 12, 13, 12, 137, 4, 195, 182, 14, 20, 5, 14, 5, 11, 13, 12, 137, 195, 182, 14, 195, 182, 11, 14, 5, 11, 13, 18, 143, 13, 5, 7, 9, 19, 13, 5, 18, 195, 169, 19, 195, 169, 18, 5, 13, 10, 135, 19, 26, 195, 161, 14, 14, 9, 13, 7, 132, 10, 195, 161, 18, 13, 0, 12, 137, 3, 19, 9, 14, 195, 161, 12, 19, 26, 13, 19, 67, 76, 83, 64, 89, 107, 63, 23, 81, 39, 79, 0, 13, 81, 102, 111, 103, 32, 31, 67, 76, 83, 64, 89, 107, 63, 10, 6, 15, 69, 37, 87, 47, 39, 89, 106, 49, 0, 13, 81, 98, 105, 122, 116, 111, 115, 97, 107, 32, 19, 67, 76, 83, 64, 89, 107, 63, 10, 6, 15, 106, 86, 0, 13, 81, 97, 122, 32, 32, 67, 76, 83, 64, 89, 107, 63, 10, 6, 15, 63, 40, 47, 106, 78, 12, 112, 49, 0, 13, 81, 109, 117, 116, 97, 116, 106, 195, 161, 107, 32, 25, 67, 76, 83, 64, 89, 107, 63, 10, 6, 15, 63, 107, 52, 107, 49, 0, 13, 81, 109, 101, 114, 101, 107, 32, 42, 67, 76, 83, 64, 89, 107, 63, 10, 6, 15, 51, 37, 106, 70, 50, 106, 49, 23, 82, 37, 87, 12, 106, 0, 13, 82, 114, 105, 97, 100, 110, 97, 107, 32, 118, 105, 115, 115, 122, 97, 32, 40, 67, 76, 83, 64, 89, 107, 63, 23, 107, 63, 55, 110, 47, 107, 47, 12, 23, 106, 52, 52, 106, 0, 13, 82, 101, 109, 108, 195, 173, 116, 101, 116, 116, 32, 97, 114, 114, 97, 32, 54, 67, 76, 83, 64, 89, 107, 63, 23, 57, 107, 55, 107, 50, 47, 111, 49, 47, 107, 55, 107, 50, 23, 108, 87, 12, 107, 79, 0, 13, 82, 106, 101, 108, 101, 110, 116, 195, 169, 107, 116, 101, 108, 101, 110, 32, 195, 182, 115, 115, 122, 101, 103, 32, 23, 67, 76, 83, 64, 89, 107, 63, 23, 47, 40, 47, 12, 106, 0, 13, 81, 116, 117, 100, 116, 97, 32, 21, 67, 76, 83, 64, 89, 107, 63, 23, 49, 107, 55, 12, 0, 13, 81, 107, 101, 108, 108, 32, 26, 67, 76, 83, 64, 89, 107, 63, 23, 49, 37, 86, 112, 52, 47, 0, 13, 81, 107, 105, 122, 195, 161, 114, 116, 32, 26, 6, 8, 9, 2, 195, 161, 19, 105, 37, 69, 112, 89, 23, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 41, 67, 76, 83, 64, 89, 107, 63, 23, 47, 40, 47, 12, 106, 49, 23, 63, 39, 50, 70, 106, 50, 37, 0, 13, 82, 116, 117, 100, 116, 97, 107, 32, 109, 111, 110, 100, 97, 110, 105, 32, 65, 67, 76, 83, 64, 89, 107, 63, 23, 81, 37, 77, 107, 55, 63, 107, 87, 47, 107, 47, 107, 47, 12, 23, 105, 106, 50, 79, 57, 107, 55, 86, 111, 89, 0, 13, 82, 102, 105, 103, 121, 101, 108, 109, 101, 122, 116, 101, 116, 101, 116, 116, 32, 104, 97, 110, 103, 106, 101, 108, 122, 195, 169, 115, 32, 66, 67, 76, 83, 64, 89, 107, 63, 23, 112, 55, 12, 23, 63, 113, 77, 12, 40, 49, 69, 106, 50, 23, 107, 55, 12, 107, 50, 116, 52, 37, 86, 50, 37, 0, 13, 83, 195, 161, 108, 108, 32, 109, 195, 179, 100, 106, 117, 107, 98, 97, 110, 32, 101, 108, 108, 101, 110, 197, 145, 114, 105, 122, 110, 105, 32, 19, 67, 76, 83, 64, 89, 107, 63, 63, 107, 77, 0, 13, 81, 109, 101, 103, 121, 32, 35, 67, 76, 83, 64, 89, 107, 63, 15, 106, 55, 49, 106, 55, 63, 106, 86, 50, 106, 49, 0, 13, 81, 97, 108, 107, 97, 108, 109, 97, 122, 110, 97, 107, 32, 24, 67, 76, 83, 64, 89, 107, 63, 15, 47, 108, 63, 37, 49, 0, 13, 81, 116, 195, 182, 109, 105, 107, 32, 15, 140, 195, 169, 16, 195, 188, 12, 5, 20, 5, 11, 2, 5, 13, 6, 195, 76, 83, 64, 13, 0, 7, 196, 32, 85, 5, 80, 13, 11, 136, 9, 14, 20, 195, 169, 26, 5, 20, 13, 32, 68, 32, 85, 5, 80, 105, 107, 47, 107, 47, 23, 105, 106, 87, 50, 112, 55, 47, 0, 13, 81, 104, 97, 115, 122, 110, 195, 161, 108, 116, 32, 11, 136, 11, 22, 195, 179, 20, 195, 161, 20, 13, 14, 139, 11, 5, 12, 12, 5, 14, 195, 169, 14, 5, 11, 13, 7, 196, 20, 197, 133, 80, 13, 7, 196, 20, 197, 133, 80, 13, 22, 147, 4, 9, 1, 7, 14, 15, 19, 26, 20, 9, 26, 195, 161, 12, 8, 1, 20, 195, 179, 13, 10, 134, 8, 1, 2, 195, 161, 18, 72, 8, 0, 17, 142, 16, 15, 12, 7, 195, 161, 18, 13, 5, 19, 20, 5, 18, 5, 13, 0, 22, 147, 22, 195, 169, 12, 5, 13, 195, 169, 14, 25, 5, 26, 195, 169, 19, 195, 169, 18, 5, 13, 53, 14, 11, 195, 182, 12, 20, 19, 195, 169, 7, 5, 11, 11, 5, 12, 49, 108, 55, 74, 111, 79, 107, 49, 12, 107, 55, 23, 81, 109, 79, 12, 23, 108, 87, 12, 107, 0, 13, 82, 102, 195, 188, 103, 103, 32, 195, 182, 115, 115, 122, 101, 32, 9, 198, 28, 243, 132, 60, 195, 196, 13, 20, 2, 54, 48, 105, 106, 47, 82, 106, 50, 12, 106, 55, 0, 44, 81, 32, 97, 108, 32, 0, 13, 138, 9, 12, 12, 5, 20, 195, 169, 11, 5, 19, 13, 15, 140, 3, 19, 195, 182, 11, 11, 5, 14, 195, 169, 19, 5, 13, 31, 67, 4, 131, 204, 106, 105, 39, 55, 23, 82, 106, 50, 23, 48, 111, 50, 86, 0, 13, 82, 118, 97, 110, 32, 112, 195, 169, 110, 122, 32, 11, 136, 13, 5, 7, 12, 5, 16, 197, 145, 13, 10, 135, 195, 173, 22, 5, 11, 5, 20, 13, 14, 67, 36, 195, 0, 37, 55, 55, 107, 47, 82, 107, 0, 25, 0, 11, 136, 16, 15, 14, 20, 10, 195, 161, 20, 13, 35, 7, 11, 9, 1, 4, 195, 161, 19, 49, 37, 106, 70, 112, 89, 23, 117, 111, 61, 57, 106, 37, 47, 0, 13, 81, 99, 195, 169, 108, 106, 97, 105, 116, 32, 12, 137, 11, 195, 182, 20, 8, 5, 20, 197, 145, 13, 26, 7, 11, 9, 1, 4, 195, 161, 19, 49, 37, 106, 70, 112, 89, 23, 55, 107, 87, 0, 81, 108, 101, 115, 122, 32, 12, 137, 3, 19, 9, 14, 195, 161, 12, 14, 9, 13, 12, 137, 195, 169, 18, 20, 8, 5, 20, 197, 145, 13, 16, 141, 6, 5, 12, 8, 1, 19, 26, 14, 195, 161, 12, 14, 9, 13, 10, 135, 11, 9, 1, 4, 195, 161, 19, 13, 12, 137, 11, 195, 182, 20, 8, 5, 20, 197, 145, 13, 12, 137, 11, 195, 169, 18, 8, 5, 20, 197, 145, 13, 7, 132, 4, 197, 145, 12, 13, 0, 44, 9, 20, 5, 18, 13, 195, 169, 11, 5, 20, 47, 107, 52, 63, 111, 49, 107, 47, 23, 82, 112, 89, 112, 52, 39, 55, 39, 49, 0, 13, 81, 118, 195, 161, 115, 195, 161, 114, 111, 108, 111, 107, 32, 37, 9, 22, 195, 161, 12, 20, 15, 26, 1, 20, 82, 112, 55, 47, 39, 86, 106, 47, 23, 107, 89, 107, 47, 111, 50, 0, 13, 81, 101, 115, 101, 116, 195, 169, 110, 32, 12, 201, 24, 241, 204, 4, 194, 207, 104, 243, 64, 13, 12, 137, 22, 195, 161, 12, 20, 15, 26, 1, 20, 13, 13, 138, 5, 12, 20, 195, 161, 18, 15, 12, 14, 9, 13, 13, 138, 5, 12, 195, 169, 18, 8, 5, 20, 197, 145, 13, 8, 133, 22, 195, 169, 18, 20, 13, 0, 14, 139, 5, 12, 197, 145, 195, 169, 12, 5, 20, 197, 177, 13, 12, 137, 14, 15, 18, 13, 195, 161, 12, 9, 19, 13, 17, 142, 5, 12, 197, 145, 195, 173, 18, 195, 161, 19, 15, 11, 1, 20, 13, 17, 142, 11, 195, 169, 18, 4, 197, 145, 195, 173, 22, 5, 11, 5, 20, 13, 12, 7, 95, 35, 45, 9, 11, 1, 9, 106, 37, 0, 0, 38, 10, 6, 5, 12, 195, 161, 12, 12, 195, 161, 19, 81, 107, 55, 112, 55, 12, 112, 89, 23, 87, 107, 52, 37, 50, 47, 0, 13, 81, 115, 122, 101, 114, 105, 110, 116, 32, 15, 140, 11, 9, 19, 26, 197, 177, 18, 8, 5, 20, 197, 145, 13, 10, 199, 80, 84, 141, 20, 195, 133, 44, 13, 10, 135, 13, 5, 12, 12, 197, 145, 12, 13, 0, 16, 141, 195, 182, 19, 26, 20, 195, 182, 14, 26, 195, 169, 19, 5, 13, 15, 140, 11, 195, 182, 26, 16, 15, 14, 20, 10, 195, 161, 20, 13, 28, 4, 195, 173, 18, 20, 110, 52, 47, 23, 49, 108, 65, 82, 107, 47, 0, 13, 81, 107, 195, 182, 110, 121, 118, 101, 116, 32, 40, 72, 60, 197, 129, 76, 21, 12, 4, 224, 39, 55, 82, 106, 89, 106, 47, 55, 106, 50, 23, 55, 107, 82, 111, 55, 52, 107, 0, 13, 81, 108, 101, 118, 195, 169, 108, 114, 101, 32, 16, 141, 5, 13, 12, 195, 169, 11, 5, 26, 20, 5, 20, 197, 145, 13, 11, 136, 2, 195, 169, 18, 195, 169, 18, 20, 13, 16, 141, 11, 195, 182, 19, 26, 195, 182, 14, 8, 5, 20, 197, 145, 13, 7, 132, 195, 173, 18, 20, 13, 7, 132, 2, 197, 145, 12, 72, 0, 47, 8, 20, 1, 18, 20, 10, 195, 161, 11, 47, 106, 52, 78, 112, 49, 23, 48, 52, 39, 69, 55, 111, 63, 112, 89, 50, 106, 49, 0, 13, 81, 112, 114, 111, 98, 108, 195, 169, 109, 195, 161, 115, 110, 97, 107, 32, 10, 135, 1, 26, 21, 20, 195, 161, 14, 13, 12, 137, 19, 26, 5, 18, 22, 20, 197, 145, 12, 13, 16, 141, 11, 195, 169, 18, 4, 197, 145, 195, 173, 22, 195, 169, 20, 13, 16, 141, 19, 26, 1, 2, 1, 4, 19, 195, 161, 7, 195, 161, 20, 13, 12, 137, 11, 1, 12, 11, 21, 12, 195, 161, 12, 13, 15, 140, 20, 195, 182, 18, 12, 5, 19, 26, 20, 195, 169, 19, 13, 9, 198, 16, 243, 7, 61, 163, 137, 13, 8, 133, 6, 195, 182, 12, 4, 13, 11, 136, 20, 1, 18, 20, 10, 195, 161, 11, 13, 0, 13, 138, 11, 5, 4, 22, 195, 169, 195, 169, 18, 20, 13, 13, 138, 22, 1, 12, 1, 13, 9, 195, 169, 18, 20, 13, 30, 6, 13, 9, 195, 169, 18, 20, 63, 37, 111, 52, 47, 15, 82, 106, 50, 15, 106, 86, 0, 13, 82, 118, 97, 110, 32, 97, 122, 32, 17, 142, 9, 14, 20, 5, 18, 6, 195, 169, 19, 26, 5, 11, 5, 20, 13, 24, 6, 13, 9, 195, 169, 18, 20, 63, 37, 111, 52, 47, 15, 50, 107, 63, 0, 13, 81, 110, 101, 109, 32, 13, 202, 57, 146, 76, 5, 66, 207, 104, 21, 15, 44, 13, 7, 132, 8, 195, 161, 26, 13, 9, 134, 5, 18, 18, 197, 145, 12, 13, 20, 2, 55, 48, 105, 107, 47, 82, 107, 50, 12, 107, 55, 0, 44, 81, 32, 101, 108, 32, 0, 30, 6, 22, 195, 161, 12, 9, 11, 82, 112, 55, 37, 49, 23, 106, 6, 15, 117, 111, 79, 0, 13, 82, 97, 32, 99, 195, 169, 103, 32, 13, 138, 11, 1, 16, 8, 1, 20, 10, 195, 161, 11, 13, 9, 134, 22, 195, 161, 12, 9, 11, 13, 8, 133, 22, 195, 169, 19, 26, 13, 9, 134, 22, 195, 169, 12, 9, 11, 13, 8, 133, 18, 195, 169, 19, 26, 13, 13, 3, 95, 56, 88, 65, 39, 55, 117, 82, 106, 50, 0, 0, 19, 144, 195, 161, 12, 12, 195, 161, 19, 16, 15, 14, 20, 10, 21, 11, 1, 20, 13, 12, 137, 13, 15, 14, 4, 1, 14, 195, 161, 13, 13, 11, 136, 20, 5, 18, 22, 18, 197, 145, 12, 13, 12, 137, 19, 26, 5, 18, 19, 26, 195, 161, 13, 13, 9, 198, 44, 86, 132, 21, 69, 0, 13, 15, 140, 12, 195, 169, 16, 195, 169, 19, 5, 11, 11, 5, 12, 13, 0, 19, 144, 3, 19, 1, 16, 1, 4, 195, 169, 11, 8, 21, 12, 12, 195, 161, 19, 13, 9, 134, 12, 195, 161, 14, 25, 1, 13, 11, 136, 195, 169, 18, 11, 5, 26, 9, 11, 13, 16, 141, 11, 195, 169, 16, 26, 195, 169, 19, 5, 11, 11, 5, 12, 13, 8, 133, 18, 195, 169, 19, 20, 13, 0, 17, 142, 195, 169, 12, 13, 195, 169, 14, 25, 195, 169, 20, 197, 145, 12, 13, 13, 138, 13, 15, 4, 5, 12, 12, 2, 197, 145, 12, 13, 10, 135, 19, 5, 7, 195, 173, 20, 9, 13, 10, 135, 11, 195, 161, 18, 20, 25, 1, 13, 13, 138, 8, 5, 12, 25, 195, 169, 18, 197, 145, 12, 13, 12, 136, 8, 195, 169, 20, 6, 197, 145, 14, 20, 22, 0, 16, 141, 20, 195, 182, 18, 22, 195, 169, 14, 25, 5, 11, 5, 14, 13, 16, 141, 12, 5, 10, 195, 161, 20, 19, 26, 195, 179, 8, 15, 26, 13, 16, 141, 19, 26, 15, 18, 195, 173, 20, 195, 161, 19, 195, 161, 14, 13, 14, 139, 16, 5, 20, 197, 145, 6, 9, 18, 197, 145, 12, 13, 14, 139, 8, 5, 12, 25, 26, 5, 20, 195, 169, 18, 20, 13, 14, 139, 18, 5, 14, 4, 10, 195, 169, 18, 197, 145, 12, 13, 0, 15, 140, 6, 5, 12, 195, 188, 12, 5, 20, 2, 197, 145, 12, 13, 14, 139, 11, 5, 26, 5, 12, 8, 5, 20, 197, 145, 11, 13, 18, 143, 8, 1, 19, 26, 14, 195, 161, 12, 8, 1, 20, 10, 195, 161, 11, 13, 13, 138, 1, 12, 11, 1, 20, 18, 195, 169, 19, 26, 13, 7, 196, 85, 64, 83, 80, 13, 0, 13, 138, 5, 18, 5, 4, 13, 195, 169, 14, 25, 5, 13, 8, 197, 44, 86, 132, 21, 64, 13, 15, 140, 19, 11, 195, 161, 12, 195, 161, 26, 20, 195, 161, 11, 13, 0, 30, 66, 44, 144, 49, 37, 23, 82, 39, 55, 47, 23, 110, 52, 82, 106, 0, 13, 82, 118, 111, 108, 116, 32, 195, 173, 114, 118, 97, 32, 39, 66, 44, 144, 49, 37, 23, 49, 107, 55, 12, 23, 47, 107, 52, 57, 107, 70, 50, 37, 107, 0, 13, 82, 107, 101, 108, 108, 32, 116, 101, 114, 106, 101, 100, 110, 105, 101, 32, 35, 66, 44, 144, 49, 37, 23, 49, 107, 55, 12, 23, 63, 39, 50, 70, 106, 50, 37, 0, 13, 82, 107, 101, 108, 108, 32, 109, 111, 110, 100, 97, 110, 105, 32, 32, 66, 44, 144, 49, 37, 10, 6, 15, 106, 86, 10, 6, 15, 108, 47, 55, 107, 47, 0, 13, 82, 97, 122, 32, 195, 182, 116, 108, 101, 116, 32, 29, 66, 44, 144, 10, 49, 37, 15, 81, 39, 79, 15, 110, 52, 50, 37, 0, 13, 82, 102, 111, 103, 32, 195, 173, 114, 110, 105, 32, 21, 66, 44, 144, 49, 37, 15, 47, 40, 77, 12, 106, 0, 13, 81, 116, 117, 100, 106, 97, 32, 25, 66, 44, 144, 49, 37, 55, 107, 105, 107, 47, 106, 86, 0, 13, 82, 108, 101, 104, 101, 116, 32, 97, 122, 32, 17, 142, 19, 26, 5, 13, 5, 20, 5, 19, 5, 11, 2, 197, 145, 12, 13, 17, 142, 18, 195, 169, 19, 26, 12, 5, 20, 5, 9, 18, 197, 145, 12, 13, 13, 138, 195, 169, 16, 195, 173, 20, 195, 169, 19, 20, 13, 5, 194, 44, 144, 13, 21, 2, 56, 48, 65, 39, 55, 117, 82, 106, 50, 12, 106, 55, 0, 44, 81, 32, 97, 108, 32, 0, 45, 16, 11, 195, 182, 12, 20, 19, 195, 169, 7, 22, 5, 20, 195, 169, 19, 9, 49, 108, 55, 74, 111, 79, 82, 107, 47, 111, 89, 37, 23, 89, 39, 52, 39, 50, 0, 13, 81, 115, 111, 114, 111, 110, 32, 37, 8, 195, 169, 18, 20, 5, 12, 13, 5, 111, 52, 47, 107, 55, 63, 107, 23, 81, 107, 55, 52, 113, 50, 37, 0, 13, 81, 102, 101, 108, 114, 195, 179, 110, 105, 32, 18, 143, 5, 12, 20, 197, 177, 14, 195, 169, 19, 195, 169, 18, 197, 145, 12, 13, 11, 136, 195, 169, 18, 20, 5, 12, 13, 5, 13, 15, 3, 95, 57, 88, 49, 37, 55, 107, 50, 117, 82, 107, 50, 0, 0, 7, 196, 56, 20, 10, 4, 13, 8, 133, 8, 195, 173, 18, 5, 13, 8, 133, 22, 195, 169, 22, 5, 13, 12, 5, 95, 35, 45, 18, 5, 111, 52, 107, 0, 21, 0, 11, 136, 12, 5, 19, 26, 195, 188, 14, 11, 72, 12, 137, 11, 5, 26, 5, 12, 195, 169, 19, 20, 13, 8, 197, 72, 18, 148, 4, 208, 13, 13, 138, 20, 195, 161, 18, 7, 25, 1, 12, 14, 9, 13, 16, 141, 195, 186, 10, 18, 1, 11, 5, 26, 4, 195, 169, 19, 20, 13, 8, 197, 8, 83, 142, 20, 208, 13, 0, 21, 146, 16, 15, 12, 7, 195, 161, 18, 13, 5, 19, 20, 5, 18, 5, 11, 11, 5, 12, 13, 0, 10, 199, 80, 84, 150, 21, 161, 84, 20, 13, 15, 7, 95, 35, 45, 20, 197, 145, 12, 111, 47, 116, 55, 0, 21, 0, 73, 21, 1, 11, 1, 4, 195, 161, 12, 25, 13, 5, 14, 20, 5, 19, 195, 173, 20, 195, 169, 19, 9, 106, 49, 106, 70, 112, 57, 63, 107, 50, 47, 107, 89, 110, 47, 111, 89, 37, 10, 6, 15, 107, 55, 82, 112, 52, 112, 89, 39, 49, 50, 106, 49, 0, 13, 81, 101, 108, 118, 195, 161, 114, 195, 161, 115, 111, 107, 110, 97, 107, 32, 7, 196, 44, 20, 19, 104, 13, 7, 132, 14, 195, 161, 12, 13, 12, 5, 95, 35, 45, 18, 1, 112, 52, 106, 0, 21, 0, 13, 138, 5, 12, 22, 195, 169, 7, 5, 26, 26, 5, 13, 23, 69, 80, 20, 148, 40, 16, 47, 106, 34, 78, 106, 10, 6, 15, 107, 55, 0, 13, 81, 101, 108, 32, 39, 69, 8, 243, 20, 60, 176, 69, 39, 55, 47, 39, 49, 10, 6, 15, 106, 57, 112, 50, 55, 106, 47, 106, 37, 0, 13, 81, 97, 106, 195, 161, 110, 108, 97, 116, 97, 105, 32, 40, 9, 22, 5, 22, 197, 145, 11, 11, 5, 12, 82, 107, 82, 116, 49, 12, 107, 55, 23, 49, 108, 47, 107, 50, 70, 116, 0, 13, 81, 107, 195, 182, 116, 101, 110, 100, 197, 145, 32, 31, 10, 20, 195, 161, 13, 1, 19, 26, 20, 10, 1, 47, 112, 63, 106, 87, 78, 106, 23, 106, 55, 112, 0, 13, 81, 97, 108, 195, 161, 32, 35, 10, 20, 195, 182, 2, 2, 14, 25, 9, 18, 5, 47, 108, 69, 65, 37, 52, 107, 23, 77, 107, 50, 79, 107, 0, 13, 81, 103, 121, 101, 110, 103, 101, 32, 15, 140, 20, 195, 182, 18, 5, 11, 19, 26, 195, 188, 14, 11, 13, 8, 197, 80, 20, 148, 40, 16, 13, 9, 198, 77, 161, 82, 21, 163, 137, 13, 8, 197, 48, 83, 142, 36, 80, 13, 0, 9, 198, 57, 147, 205, 84, 226, 192, 13, 13, 138, 22, 1, 12, 1, 11, 9, 20, 197, 145, 12, 13, 13, 138, 11, 195, 169, 18, 4, 5, 26, 5, 20, 20, 13, 12, 137, 19, 195, 186, 10, 20, 10, 195, 161, 11, 13, 23, 2, 57, 48, 49, 37, 55, 107, 50, 117, 82, 107, 50, 12, 107, 55, 0, 44, 81, 32, 101, 108, 32, 15, 8, 95, 35, 45, 195, 161, 8, 15, 26, 112, 105, 39, 86, 0, 13, 7, 95, 35, 45, 195, 169, 18, 5, 111, 52, 107, 0, 0, 15, 140, 8, 195, 169, 20, 22, 195, 169, 7, 195, 169, 18, 5, 13, 15, 140, 13, 195, 169, 18, 20, 195, 169, 11, 195, 169, 18, 5, 13, 9, 198, 24, 241, 193, 48, 213, 75, 13, 10, 135, 12, 5, 195, 161, 12, 12, 20, 13, 9, 198, 73, 81, 193, 48, 208, 83, 13, 14, 139, 22, 195, 169, 4, 5, 11, 5, 26, 5, 20, 20, 13, 13, 138, 19, 26, 195, 161, 18, 13, 1, 26, 9, 11, 13, 0, 11, 136, 16, 5, 18, 3, 18, 197, 145, 12, 22, 11, 136, 195, 169, 18, 4, 5, 11, 5, 12, 13, 35, 6, 19, 15, 18, 195, 161, 14, 89, 39, 52, 112, 50, 23, 49, 37, 70, 107, 52, 109, 55, 47, 0, 13, 81, 107, 105, 100, 101, 114, 195, 188, 108, 116, 32, 66, 7, 20, 21, 4, 20, 195, 161, 11, 47, 40, 47, 12, 112, 49, 23, 81, 39, 52, 70, 110, 47, 106, 50, 37, 23, 106, 23, 49, 111, 52, 70, 116, 110, 82, 107, 47, 0, 13, 83, 102, 111, 114, 100, 195, 173, 116, 97, 110, 105, 32, 97, 32, 107, 195, 169, 114, 100, 197, 145, 195, 173, 118, 101, 116, 32, 60, 6, 15, 18, 2, 195, 161, 14, 39, 52, 69, 112, 50, 23, 82, 37, 49, 47, 39, 52, 23, 63, 37, 50, 37, 87, 47, 107, 52, 107, 55, 50, 108, 49, 0, 13, 82, 118, 105, 107, 116, 111, 114, 32, 109, 105, 110, 105, 115, 122, 116, 101, 114, 101, 108, 110, 195, 182, 107, 32, 10, 135, 20, 21, 4, 20, 195, 161, 11, 13, 7, 196, 12, 149, 137, 48, 13, 9, 134, 19, 15, 18, 195, 161, 14, 13, 0, 13, 138, 195, 182, 18, 195, 182, 13, 195, 169, 18, 5, 13, 12, 137, 19, 5, 7, 195, 173, 20, 5, 20, 20, 13, 7, 132, 14, 197, 145, 19, 13, 9, 198, 44, 81, 22, 21, 163, 133, 13, 5, 130, 57, 53, 13, 15, 140, 8, 1, 19, 26, 14, 195, 161, 12, 10, 195, 161, 11, 13, 15, 140, 19, 26, 15, 12, 7, 195, 161, 12, 10, 195, 161, 11, 13, 12, 137, 4, 5, 18, 195, 173, 20, 5, 20, 20, 13, 8, 133, 197, 145, 11, 5, 20, 13, 8, 197, 32, 83, 25, 21, 48, 76, 0, 12, 137, 18, 5, 14, 4, 5, 12, 197, 145, 11, 13, 9, 134, 6, 15, 7, 195, 161, 20, 13, 10, 135, 8, 5, 22, 195, 173, 20, 9, 13, 13, 138, 19, 26, 195, 188, 12, 5, 20, 5, 20, 20, 13, 12, 137, 19, 26, 195, 161, 13, 12, 195, 161, 11, 13, 9, 134, 20, 5, 8, 195, 161, 20, 13, 7, 132, 26, 195, 161, 18, 13, 7, 132, 22, 195, 161, 18, 13, 12, 6, 95, 35, 45, 195, 161, 20, 112, 47, 0, 21, 0, 31, 8, 12, 195, 169, 16, 195, 169, 19, 5, 55, 111, 48, 111, 89, 107, 23, 107, 55, 12, 107, 50, 0, 13, 81, 101, 108, 108, 101, 110, 32, 46, 71, 77, 161, 82, 88, 86, 133, 80, 87, 107, 52, 82, 107, 86, 107, 47, 10, 6, 15, 63, 115, 49, 108, 47, 12, 107, 47, 12, 107, 0, 13, 81, 109, 197, 177, 107, 195, 182, 100, 116, 101, 116, 116, 101, 32, 37, 8, 2, 195, 169, 18, 12, 5, 20, 9, 69, 111, 52, 55, 107, 47, 37, 23, 70, 110, 57, 106, 49, 52, 106, 0, 13, 81, 100, 195, 173, 106, 97, 107, 114, 97, 32, 30, 71, 24, 244, 132, 84, 194, 1, 80, 81, 39, 52, 70, 40, 55, 105, 106, 47, 23, 107, 55, 116, 0, 13, 81, 101, 108, 197, 145, 32, 14, 139, 6, 18, 9, 19, 19, 195, 173, 20, 5, 20, 20, 13, 10, 199, 77, 161, 82, 88, 86, 133, 80, 13, 8, 133, 19, 26, 197, 145, 18, 13, 12, 137, 20, 1, 22, 1, 19, 26, 195, 161, 14, 20, 0, 12, 137, 11, 195, 169, 18, 4, 195, 169, 19, 5, 13, 11, 136, 195, 169, 12, 197, 145, 11, 5, 20, 13, 14, 139, 2, 195, 173, 18, 195, 161, 12, 20, 195, 161, 11, 13, 16, 141, 8, 195, 161, 12, 195, 179, 26, 1, 20, 15, 11, 2, 1, 13, 7, 132, 14, 197, 145, 20, 13, 0, 15, 140, 6, 9, 14, 15, 13, 195, 173, 20, 19, 195, 161, 11, 13, 16, 141, 13, 197, 177, 11, 195, 182, 4, 20, 5, 20, 5, 20, 20, 13, 0, 22, 67, 40, 240, 130, 57, 39, 69, 12, 23, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 38, 67, 40, 240, 130, 57, 39, 69, 12, 10, 6, 15, 47, 112, 63, 39, 79, 106, 47, 112, 89, 106, 0, 13, 81, 116, 195, 161, 109, 111, 103, 97, 116, 195, 161, 115, 97, 32, 47, 70, 48, 82, 5, 80, 85, 20, 55, 107, 105, 107, 47, 107, 47, 12, 23, 82, 37, 88, 79, 112, 55, 50, 37, 23, 106, 87, 47, 0, 13, 82, 118, 105, 122, 115, 103, 195, 161, 108, 110, 105, 32, 97, 122, 116, 32, 36, 70, 48, 82, 5, 80, 85, 20, 55, 107, 105, 107, 47, 107, 47, 12, 23, 87, 112, 63, 112, 52, 106, 0, 13, 81, 115, 122, 195, 161, 109, 195, 161, 114, 97, 32, 17, 142, 20, 195, 182, 18, 20, 195, 169, 14, 8, 5, 20, 5, 20, 20, 13, 18, 143, 13, 5, 7, 5, 12, 197, 145, 26, 195, 169, 19, 195, 169, 18, 5, 13, 12, 137, 11, 195, 169, 18, 14, 195, 188, 14, 11, 13, 9, 198, 48, 82, 5, 80, 85, 20, 13, 6, 195, 40, 240, 130, 13, 0, 42, 11, 6, 21, 14, 11, 3, 9, 195, 179, 11, 1, 20, 81, 40, 50, 49, 117, 37, 113, 49, 106, 47, 23, 107, 55, 12, 112, 47, 113, 0, 13, 81, 101, 108, 108, 195, 161, 116, 195, 179, 32, 14, 139, 195, 161, 12, 12, 1, 16, 15, 20, 195, 161, 20, 13, 9, 134, 5, 13, 12, 197, 145, 19, 13, 14, 139, 6, 21, 14, 11, 3, 9, 195, 179, 11, 1, 20, 13, 14, 139, 10, 5, 12, 26, 195, 169, 19, 5, 11, 5, 20, 13, 10, 135, 195, 186, 20, 10, 195, 161, 20, 13, 10, 135, 195, 186, 20, 10, 195, 161, 20, 13, 14, 139, 195, 188, 26, 5, 14, 5, 20, 5, 11, 5, 20, 13, 17, 142, 11, 9, 6, 15, 7, 195, 161, 19, 15, 12, 20, 195, 161, 11, 13, 8, 133, 6, 195, 182, 14, 14, 13, 0, 16, 141, 20, 195, 182, 14, 11, 18, 5, 20, 5, 8, 5, 20, 9, 13, 14, 139, 1, 12, 11, 1, 12, 13, 1, 26, 195, 161, 19, 13, 12, 137, 11, 195, 169, 16, 26, 195, 169, 19, 5, 13, 12, 137, 6, 9, 26, 5, 20, 195, 169, 19, 5, 13, 11, 136, 11, 195, 179, 4, 15, 11, 1, 20, 13, 40, 7, 6, 5, 12, 8, 197, 145, 19, 81, 107, 55, 105, 116, 89, 23, 37, 70, 116, 87, 106, 49, 69, 106, 50, 0, 13, 81, 105, 100, 197, 145, 115, 122, 97, 107, 98, 97, 110, 32, 45, 7, 6, 5, 12, 8, 197, 145, 19, 81, 107, 55, 105, 116, 89, 23, 47, 107, 52, 109, 55, 107, 47, 107, 49, 23, 37, 89, 0, 13, 82, 116, 101, 114, 195, 188, 108, 101, 116, 101, 107, 32, 105, 115, 32, 12, 137, 22, 5, 26, 5, 20, 195, 169, 19, 5, 13, 15, 140, 20, 5, 18, 195, 188, 12, 5, 20, 5, 11, 5, 20, 13, 15, 140, 13, 197, 177, 22, 5, 12, 5, 20, 5, 11, 5, 20, 13, 10, 135, 6, 5, 12, 8, 197, 145, 19, 13, 12, 137, 11, 195, 169, 16, 26, 195, 169, 19, 5, 13, 0, 53, 15, 20, 5, 12, 5, 16, 195, 188, 12, 195, 169, 19, 5, 11, 5, 14, 47, 107, 55, 107, 48, 109, 55, 111, 89, 107, 49, 107, 50, 10, 6, 15, 70, 39, 55, 79, 39, 86, 37, 49, 0, 13, 81, 100, 111, 108, 103, 111, 122, 105, 107, 32, 48, 13, 195, 186, 10, 195, 173, 20, 195, 161, 19, 15, 11, 1, 20, 114, 57, 110, 47, 112, 89, 39, 49, 106, 47, 15, 69, 107, 82, 107, 86, 107, 47, 50, 37, 0, 13, 81, 98, 101, 118, 101, 122, 101, 116, 110, 105, 32, 12, 137, 4, 9, 195, 161, 11, 15, 11, 1, 20, 13, 16, 141, 8, 1, 19, 26, 14, 195, 161, 12, 195, 179, 11, 1, 20, 13, 11, 136, 9, 19, 11, 15, 12, 195, 161, 19, 13, 7, 196, 48, 20, 15, 44, 13, 15, 140, 19, 5, 7, 195, 173, 20, 5, 14, 195, 188, 14, 11, 13, 12, 137, 6, 195, 161, 10, 12, 10, 195, 161, 20, 13, 12, 137, 16, 15, 19, 26, 20, 10, 195, 161, 20, 13, 8, 133, 19, 26, 195, 169, 11, 13, 7, 196, 57, 145, 82, 80, 13, 11, 6, 95, 35, 45, 195, 169, 14, 111, 50, 0, 0, 22, 147, 11, 5, 26, 4, 5, 13, 195, 169, 14, 25, 5, 26, 195, 169, 19, 195, 169, 18, 5, 13, 22, 5, 20, 197, 177, 14, 20, 47, 115, 50, 47, 10, 6, 15, 49, 37, 0, 13, 81, 107, 105, 32, 20, 5, 20, 197, 177, 14, 20, 47, 115, 50, 47, 23, 107, 55, 0, 13, 81, 101, 108, 32, 14, 139, 13, 197, 177, 11, 195, 182, 4, 195, 169, 19, 5, 13, 8, 197, 32, 83, 25, 20, 64, 13, 8, 133, 20, 197, 177, 14, 20, 13, 12, 137, 10, 21, 20, 20, 1, 20, 195, 161, 19, 13, 12, 137, 195, 186, 10, 195, 173, 20, 195, 161, 19, 13, 8, 133, 20, 195, 169, 18, 20, 13, 8, 133, 8, 195, 173, 18, 20, 13, 8, 133, 20, 197, 177, 14, 20, 13, 0, 7, 132, 4, 195, 173, 10, 13, 14, 139, 3, 19, 15, 16, 15, 18, 20, 10, 195, 161, 20, 13, 15, 140, 6, 18, 9, 19, 19, 195, 173, 20, 195, 169, 19, 5, 13, 49, 11, 11, 9, 1, 4, 195, 161, 19, 15, 11, 1, 20, 49, 37, 106, 70, 112, 89, 39, 49, 106, 47, 23, 48, 52, 107, 81, 107, 52, 112, 61, 57, 106, 0, 13, 81, 112, 114, 101, 102, 101, 114, 195, 161, 108, 106, 97, 32, 18, 143, 6, 5, 10, 12, 5, 19, 26, 20, 195, 169, 19, 5, 11, 5, 20, 13, 14, 139, 12, 195, 169, 16, 195, 169, 19, 5, 11, 5, 20, 13, 18, 143, 6, 5, 12, 16, 21, 8, 195, 173, 20, 195, 161, 19, 195, 161, 20, 13, 19, 144, 11, 195, 182, 12, 20, 19, 195, 169, 7, 22, 5, 20, 195, 169, 19, 5, 13, 13, 138, 21, 20, 1, 19, 195, 173, 20, 195, 161, 19, 13, 9, 134, 16, 195, 169, 14, 26, 20, 13, 8, 133, 20, 197, 145, 12, 5, 13, 0, 15, 140, 2, 5, 6, 15, 12, 25, 195, 161, 19, 195, 161, 20, 13, 52, 6, 11, 195, 169, 18, 20, 5, 49, 111, 52, 47, 107, 10, 6, 15, 81, 107, 55, 23, 63, 114, 55, 47, 10, 6, 15, 105, 111, 47, 107, 50, 0, 13, 83, 102, 101, 108, 32, 109, 195, 186, 108, 116, 32, 104, 195, 169, 116, 101, 110, 32, 19, 144, 13, 195, 179, 4, 15, 19, 195, 173, 20, 195, 161, 19, 15, 11, 1, 20, 13, 9, 134, 11, 195, 169, 18, 20, 5, 13, 13, 4, 95, 15, 7, 15, 105, 39, 52, 79, 39, 49, 0, 0, 16, 141, 11, 195, 169, 19, 26, 195, 188, 12, 195, 169, 11, 5, 20, 13, 10, 135, 2, 5, 12, 197, 145, 12, 5, 13, 11, 200, 5, 52, 218, 60, 227, 153, 4, 192, 13, 20, 145, 5, 12, 197, 145, 195, 161, 12, 12, 195, 173, 20, 195, 161, 19, 195, 161, 20, 13, 7, 196, 36, 65, 74, 20, 13, 16, 141, 19, 26, 195, 161, 14, 4, 195, 169, 11, 21, 11, 1, 20, 13, 15, 140, 2, 5, 195, 161, 12, 12, 195, 173, 20, 195, 161, 19, 13, 16, 141, 11, 195, 169, 19, 26, 195, 188, 12, 195, 169, 11, 5, 20, 13, 20, 145, 19, 26, 15, 12, 7, 195, 161, 12, 20, 1, 20, 195, 161, 19, 195, 161, 20, 13, 0, 17, 142, 9, 4, 197, 145, 10, 195, 161, 18, 195, 161, 19, 195, 161, 20, 13, 21, 146, 19, 26, 15, 12, 7, 195, 161, 12, 20, 1, 20, 195, 161, 19, 15, 11, 1, 20, 13, 44, 18, 19, 26, 15, 12, 7, 195, 161, 12, 20, 1, 20, 195, 161, 19, 15, 11, 1, 20, 87, 39, 55, 79, 112, 55, 47, 106, 47, 112, 89, 39, 49, 106, 47, 23, 37, 89, 0, 13, 81, 105, 115, 32, 11, 136, 195, 173, 7, 195, 169, 18, 20, 5, 13, 21, 146, 3, 19, 1, 20, 12, 1, 11, 15, 26, 20, 1, 20, 195, 161, 19, 195, 161, 20, 13, 11, 136, 195, 173, 7, 195, 169, 18, 20, 5, 13, 8, 133, 19, 26, 195, 169, 12, 13, 0, 18, 143, 22, 195, 161, 12, 1, 19, 26, 20, 195, 161, 19, 15, 11, 1, 20, 13, 22, 147, 13, 5, 7, 22, 195, 161, 12, 20, 15, 26, 20, 1, 20, 195, 161, 19, 195, 161, 20, 13, 18, 143, 11, 195, 182, 26, 22, 195, 169, 12, 5, 13, 195, 169, 14, 25, 20, 13, 9, 198, 52, 243, 137, 80, 244, 128, 13, 22, 147, 22, 9, 19, 19, 26, 1, 195, 161, 12, 12, 195, 173, 20, 195, 161, 19, 195, 161, 20, 13, 0, 10, 199, 77, 163, 198, 81, 97, 82, 80, 13, 10, 199, 28, 243, 132, 60, 197, 21, 44, 13, 10, 199, 32, 19, 135, 77, 161, 82, 80, 13, 11, 136, 22, 195, 169, 12, 9, 20, 5, 11, 13, 6, 195, 88, 243, 148, 13, 6, 195, 88, 243, 148, 13, 0, 19, 68, 57, 145, 76, 88, 65, 107, 55, 82, 23, 37, 89, 0, 13, 81, 105, 115, 32, 11, 200, 65, 35, 199, 72, 19, 77, 4, 192, 13, 12, 137, 8, 9, 20, 20, 195, 169, 20, 5, 11, 13, 7, 132, 20, 195, 186, 12, 13, 0, 8, 197, 32, 83, 25, 21, 64, 13, 8, 197, 77, 161, 77, 21, 64, 13, 9, 198, 4, 192, 84, 80, 144, 75, 13, 8, 197, 40, 21, 149, 49, 64, 13, 0, 19, 144, 22, 1, 12, 195, 179, 19, 26, 195, 173, 14, 197, 177, 20, 12, 5, 14, 13, 31, 7, 13, 9, 12, 12, 9, 195, 179, 63, 37, 55, 37, 113, 23, 81, 39, 52, 37, 50, 47, 0, 13, 81, 102, 111, 114, 105, 110, 116, 32, 12, 201, 36, 225, 193, 80, 192, 78, 84, 176, 129, 13, 0, 27, 152, 7, 25, 195, 179, 7, 25, 19, 26, 5, 18, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 195, 161, 20, 13, 9, 198, 20, 195, 79, 56, 69, 1, 13, 7, 195, 52, 147, 148, 102, 13, 7, 195, 52, 147, 148, 13, 23, 0, 10, 135, 13, 5, 7, 195, 169, 18, 9, 13, 0, 11, 136, 12, 195, 169, 20, 5, 26, 14, 9, 13, 13, 138, 19, 26, 5, 13, 20, 1, 14, 195, 186, 11, 13, 6, 131, 195, 161, 14, 72, 18, 69, 88, 68, 218, 77, 160, 82, 111, 70, 111, 107, 87, 107, 87, 0, 42, 42, 0, 24, 66, 56, 80, 50, 107, 10, 6, 15, 47, 107, 50, 12, 111, 0, 13, 81, 116, 101, 110, 110, 195, 169, 32, 14, 139, 11, 5, 18, 5, 19, 197, 145, 10, 195, 188, 11, 13, 9, 198, 85, 64, 90, 61, 69, 0, 13, 9, 198, 32, 83, 25, 21, 69, 0, 13, 5, 194, 56, 80, 13, 0, 22, 67, 52, 18, 132, 63, 106, 57, 70, 10, 6, 15, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 32, 67, 52, 18, 132, 63, 106, 57, 70, 10, 6, 15, 63, 115, 49, 108, 70, 50, 37, 0, 13, 81, 109, 197, 177, 107, 195, 182, 100, 110, 105, 32, 34, 67, 52, 18, 132, 63, 106, 57, 70, 10, 6, 15, 55, 107, 105, 107, 47, 116, 82, 111, 0, 13, 81, 108, 101, 104, 101, 116, 197, 145, 118, 195, 169, 32, 40, 67, 52, 18, 132, 63, 106, 57, 70, 10, 6, 15, 63, 107, 79, 47, 107, 49, 37, 50, 47, 107, 50, 37, 0, 13, 81, 109, 101, 103, 116, 101, 107, 105, 110, 116, 101, 110, 105, 32, 33, 67, 52, 18, 132, 63, 106, 57, 70, 10, 6, 15, 105, 106, 55, 79, 106, 47, 50, 37, 0, 13, 81, 104, 97, 108, 108, 103, 97, 116, 110, 105, 32, 26, 67, 52, 18, 132, 63, 106, 57, 70, 10, 6, 15, 52, 106, 57, 47, 106, 0, 13, 81, 114, 97, 106, 116, 97, 32, 15, 140, 195, 169, 18, 4, 5, 11, 5, 19, 19, 195, 169, 7, 13, 6, 195, 52, 18, 132, 13, 0, 10, 135, 195, 161, 18, 21, 12, 14, 9, 13, 9, 134, 8, 195, 169, 20, 5, 14, 13, 7, 196, 44, 20, 14, 36, 13, 7, 196, 57, 145, 76, 80, 13, 6, 131, 195, 161, 13, 13, 15, 4, 95, 50, 17, 24, 63, 112, 89, 39, 70, 37, 49, 106, 0, 0, 40, 69, 20, 195, 5, 56, 144, 107, 55, 12, 107, 50, 37, 23, 81, 107, 55, 12, 111, 48, 111, 89, 52, 107, 0, 13, 81, 102, 101, 108, 108, 195, 169, 112, 195, 169, 115, 114, 101, 32, 8, 197, 88, 19, 1, 44, 144, 13, 10, 135, 6, 195, 169, 18, 6, 9, 14, 13, 8, 197, 28, 243, 66, 72, 16, 13, 0, 35, 5, 195, 169, 22, 18, 5, 111, 82, 52, 107, 10, 6, 15, 49, 111, 87, 109, 55, 50, 107, 0, 13, 81, 107, 195, 169, 115, 122, 195, 188, 108, 110, 101, 32, 8, 133, 195, 169, 22, 18, 5, 13, 11, 136, 3, 19, 195, 182, 11, 11, 5, 14, 13, 10, 135, 20, 21, 4, 10, 195, 161, 11, 13, 10, 135, 20, 21, 4, 10, 195, 161, 11, 13, 6, 131, 197, 145, 11, 13, 7, 131, 197, 145, 11, 13, 8, 0, 14, 139, 20, 195, 188, 14, 20, 5, 20, 195, 169, 19, 20, 13, 12, 201, 72, 83, 132, 20, 194, 197, 104, 83, 0, 13, 14, 139, 6, 5, 12, 12, 195, 169, 16, 195, 169, 19, 20, 13, 0, 10, 135, 195, 169, 12, 5, 20, 2, 5, 13, 9, 134, 10, 15, 7, 195, 161, 14, 13, 12, 137, 19, 26, 195, 161, 14, 10, 195, 161, 11, 13, 8, 133, 20, 195, 161, 14, 3, 13, 7, 132, 18, 195, 186, 4, 13, 7, 196, 77, 161, 80, 80, 20, 0, 13, 138, 7, 25, 195, 161, 18, 20, 10, 195, 161, 11, 13, 12, 201, 29, 145, 82, 52, 82, 197, 44, 85, 0, 13, 24, 149, 2, 197, 177, 14, 3, 19, 5, 12, 5, 11, 13, 195, 169, 14, 25, 5, 11, 195, 169, 18, 20, 13, 0, 15, 66, 49, 144, 107, 55, 55, 37, 48, 87, 37, 55, 39, 50, 0, 21, 146, 5, 7, 25, 195, 188, 20, 20, 13, 197, 177, 11, 195, 182, 4, 195, 169, 19, 20, 13, 11, 136, 12, 5, 12, 11, 195, 169, 19, 26, 13, 9, 198, 4, 64, 84, 60, 176, 84, 13, 9, 198, 88, 19, 1, 44, 149, 0, 13, 7, 132, 2, 197, 145, 18, 13, 5, 194, 61, 48, 72, 8, 132, 2, 195, 161, 18, 72, 8, 0, 34, 8, 12, 195, 161, 20, 19, 26, 9, 11, 55, 112, 117, 12, 37, 49, 10, 6, 15, 47, 107, 105, 112, 47, 0, 13, 81, 116, 101, 104, 195, 161, 116, 32, 31, 3, 195, 161, 20, 112, 47, 23, 106, 6, 23, 70, 52, 112, 82, 112, 47, 0, 13, 82, 97, 32, 100, 114, 195, 161, 118, 195, 161, 116, 32, 10, 135, 11, 195, 182, 26, 197, 177, 12, 13, 11, 136, 12, 195, 161, 20, 19, 26, 9, 11, 13, 6, 131, 197, 145, 20, 13, 6, 131, 195, 161, 20, 13, 15, 7, 95, 35, 45, 18, 197, 145, 12, 111, 52, 116, 55, 0, 21, 0, 12, 137, 19, 26, 195, 161, 14, 20, 195, 161, 11, 13, 24, 68, 36, 225, 21, 48, 37, 50, 70, 40, 55, 23, 63, 106, 57, 70, 0, 13, 81, 109, 97, 106, 100, 32, 11, 200, 32, 83, 25, 21, 69, 5, 76, 80, 13, 38, 68, 36, 225, 21, 48, 37, 50, 70, 40, 55, 23, 106, 6, 15, 81, 107, 55, 105, 116, 86, 107, 47, 0, 13, 82, 97, 32, 102, 101, 108, 104, 197, 145, 122, 101, 116, 32, 16, 141, 2, 9, 26, 20, 15, 19, 195, 173, 20, 10, 195, 161, 11, 13, 7, 196, 24, 150, 133, 80, 13, 12, 137, 10, 195, 161, 18, 1, 4, 195, 169, 11, 13, 11, 136, 8, 5, 12, 25, 18, 197, 145, 12, 13, 13, 4, 95, 48, 77, 52, 69, 37, 55, 55, 37, 113, 0, 0, 14, 139, 2, 5, 22, 195, 169, 20, 5, 12, 8, 5, 26, 13, 12, 137, 195, 169, 22, 5, 11, 2, 197, 145, 12, 13, 15, 140, 13, 21, 14, 11, 1, 20, 195, 161, 18, 19, 1, 9, 13, 12, 201, 40, 21, 129, 76, 192, 84, 60, 176, 84, 13, 12, 137, 195, 169, 22, 5, 11, 2, 197, 145, 12, 13, 6, 131, 197, 145, 18, 13, 12, 137, 4, 195, 182, 14, 20, 195, 182, 20, 20, 13, 0, 14, 139, 2, 195, 188, 14, 20, 5, 19, 19, 195, 169, 11, 13, 13, 138, 12, 5, 11, 195, 182, 20, 195, 182, 20, 20, 13, 10, 135, 6, 15, 18, 18, 195, 161, 19, 13, 13, 4, 95, 48, 77, 50, 63, 37, 55, 55, 37, 113, 0, 0, 14, 139, 22, 195, 169, 12, 5, 11, 5, 4, 5, 20, 20, 13, 10, 135, 6, 195, 169, 18, 6, 9, 20, 13, 10, 135, 8, 9, 195, 161, 14, 25, 20, 13, 6, 195, 88, 243, 128, 13, 6, 195, 52, 147, 132, 13, 15, 4, 95, 48, 77, 51, 63, 37, 55, 55, 37, 112, 52, 70, 0, 0, 9, 134, 13, 195, 169, 20, 5, 18, 13, 11, 136, 15, 12, 4, 1, 12, 195, 161, 20, 13, 12, 137, 20, 5, 8, 5, 20, 10, 195, 188, 11, 13, 11, 136, 11, 5, 18, 195, 188, 12, 5, 20, 13, 11, 136, 7, 195, 169, 16, 5, 11, 5, 20, 13, 9, 198, 24, 241, 193, 48, 208, 90, 13, 0, 45, 13, 5, 12, 12, 5, 14, 197, 145, 18, 26, 195, 182, 20, 20, 107, 55, 12, 107, 50, 108, 52, 86, 108, 47, 12, 23, 107, 77, 89, 111, 79, 107, 0, 13, 81, 101, 103, 121, 115, 195, 169, 103, 101, 32, 12, 137, 9, 4, 5, 7, 5, 19, 195, 173, 20, 13, 9, 134, 11, 195, 169, 16, 5, 19, 13, 11, 4, 95, 48, 77, 49, 107, 86, 107, 52, 0, 0, 9, 134, 10, 195, 182, 8, 5, 20, 13, 61, 16, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 10, 195, 161, 8, 15, 26, 48, 52, 39, 69, 55, 111, 63, 112, 57, 112, 105, 39, 86, 23, 105, 106, 89, 39, 50, 55, 110, 47, 39, 47, 12, 106, 0, 13, 81, 104, 97, 115, 111, 110, 108, 195, 173, 116, 111, 116, 116, 97, 32, 9, 134, 195, 161, 18, 195, 161, 20, 13, 10, 135, 20, 1, 18, 20, 195, 161, 19, 13, 13, 138, 195, 173, 7, 195, 169, 18, 5, 20, 5, 20, 13, 9, 134, 12, 195, 161, 14, 25, 20, 13, 13, 4, 95, 2, 18, 22, 81, 111, 55, 49, 108, 52, 0, 0, 8, 67, 17, 164, 192, 73, 111, 0, 14, 139, 10, 15, 7, 19, 195, 169, 18, 20, 197, 145, 20, 13, 18, 143, 20, 5, 12, 5, 16, 8, 5, 12, 25, 195, 169, 18, 197, 145, 12, 13, 22, 147, 19, 5, 7, 195, 169, 4, 5, 19, 26, 11, 195, 182, 26, 195, 182, 11, 11, 5, 12, 13, 18, 143, 10, 5, 12, 5, 14, 12, 195, 169, 20, 195, 169, 18, 197, 145, 12, 13, 6, 195, 8, 244, 128, 13, 0, 16, 141, 195, 169, 18, 20, 5, 12, 13, 5, 26, 26, 195, 188, 11, 13, 43, 11, 5, 7, 25, 5, 19, 195, 188, 12, 5, 20, 9, 107, 77, 12, 107, 89, 109, 55, 107, 47, 37, 23, 82, 107, 86, 107, 47, 116, 49, 0, 13, 81, 118, 101, 122, 101, 116, 197, 145, 107, 32, 9, 198, 48, 82, 5, 77, 49, 78, 13, 9, 198, 72, 244, 211, 104, 16, 130, 13, 15, 140, 22, 195, 161, 12, 20, 1, 11, 15, 26, 8, 1, 20, 13, 0, 12, 201, 29, 145, 82, 52, 82, 197, 36, 177, 84, 13, 16, 141, 9, 19, 13, 5, 18, 197, 145, 19, 5, 9, 11, 5, 20, 13, 10, 135, 19, 26, 195, 169, 16, 5, 14, 13, 0, 24, 70, 4, 192, 75, 84, 197, 0, 106, 55, 106, 49, 40, 55, 47, 23, 49, 37, 0, 13, 81, 107, 105, 32, 14, 139, 22, 195, 161, 12, 1, 19, 26, 20, 195, 161, 19, 13, 11, 136, 8, 195, 161, 2, 15, 18, 195, 186, 13, 13, 138, 9, 19, 11, 15, 12, 195, 161, 11, 1, 20, 13, 9, 134, 19, 26, 195, 161, 14, 20, 13, 11, 136, 19, 26, 195, 169, 12, 195, 169, 14, 13, 14, 139, 5, 7, 25, 5, 14, 18, 21, 8, 195, 161, 19, 22, 0, 22, 147, 20, 5, 22, 195, 169, 11, 5, 14, 25, 19, 195, 169, 7, 195, 169, 18, 197, 145, 12, 13, 14, 139, 195, 161, 12, 12, 15, 13, 195, 161, 14, 25, 20, 13, 18, 143, 2, 9, 12, 12, 5, 14, 20, 25, 197, 177, 26, 5, 20, 5, 20, 13, 14, 139, 11, 5, 4, 195, 169, 12, 25, 5, 11, 5, 20, 13, 10, 135, 22, 195, 161, 12, 12, 1, 12, 13, 7, 132, 8, 195, 186, 19, 13, 8, 133, 19, 26, 195, 173, 14, 13, 0, 7, 196, 24, 241, 207, 44, 76, 6, 195, 52, 148, 133, 13, 12, 137, 13, 15, 14, 4, 1, 14, 195, 169, 11, 13, 7, 196, 77, 161, 82, 80, 13, 0, 47, 13, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 11, 1, 20, 48, 52, 39, 69, 55, 111, 63, 112, 49, 106, 47, 23, 49, 106, 48, 106, 52, 79, 106, 47, 0, 13, 81, 107, 97, 112, 97, 114, 103, 97, 116, 32, 26, 69, 4, 192, 75, 84, 192, 106, 55, 106, 49, 40, 55, 23, 63, 106, 57, 70, 0, 13, 81, 109, 97, 106, 100, 32, 16, 141, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 11, 1, 20, 13, 16, 141, 8, 1, 14, 7, 13, 9, 14, 20, 195, 161, 11, 1, 20, 13, 16, 141, 195, 161, 12, 12, 195, 173, 20, 195, 161, 19, 195, 161, 20, 13, 8, 197, 4, 192, 75, 84, 192, 13, 16, 141, 6, 15, 18, 4, 195, 173, 20, 195, 161, 19, 195, 161, 20, 13, 12, 137, 6, 5, 12, 20, 195, 169, 20, 5, 12, 13, 0, 16, 141, 12, 195, 182, 22, 195, 182, 12, 4, 195, 182, 26, 197, 145, 13, 6, 131, 195, 169, 7, 13, 12, 201, 72, 83, 132, 77, 161, 82, 20, 180, 133, 13, 6, 131, 195, 169, 7, 13, 0, 19, 144, 13, 5, 7, 14, 25, 9, 12, 22, 195, 161, 14, 21, 12, 195, 161, 19, 13, 9, 198, 13, 51, 205, 4, 116, 129, 13, 0, 17, 142, 22, 9, 12, 195, 161, 7, 8, 195, 161, 2, 15, 18, 195, 186, 13, 11, 200, 29, 145, 82, 20, 177, 75, 20, 224, 13, 7, 196, 76, 83, 77, 36, 13, 0, 8, 197, 5, 163, 203, 5, 64, 13, 42, 69, 24, 83, 5, 81, 64, 81, 107, 55, 107, 47, 12, 23, 37, 89, 23, 63, 107, 79, 87, 115, 50, 37, 49, 0, 13, 82, 105, 115, 32, 109, 101, 103, 115, 122, 197, 177, 110, 105, 107, 32, 8, 197, 24, 83, 5, 81, 64, 13, 17, 9, 95, 35, 45, 195, 169, 14, 195, 169, 12, 111, 50, 111, 55, 0, 21, 0, 21, 146, 195, 182, 14, 11, 15, 18, 13, 195, 161, 14, 25, 26, 1, 20, 15, 11, 1, 20, 13, 12, 137, 11, 195, 169, 18, 4, 5, 26, 20, 5, 13, 9, 134, 19, 26, 195, 161, 12, 12, 13, 13, 67, 61, 68, 0, 113, 47, 111, 48, 111, 0, 42, 42, 7, 132, 10, 195, 186, 14, 20, 13, 7, 95, 35, 45, 195, 161, 9, 7, 112, 37, 79, 0, 0, 19, 67, 61, 69, 0, 39, 47, 12, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 13, 138, 7, 25, 195, 182, 20, 195, 182, 18, 20, 5, 13, 6, 195, 61, 69, 0, 13, 6, 195, 56, 245, 128, 20, 0, 7, 196, 24, 241, 207, 52, 13, 7, 196, 48, 20, 15, 80, 13, 7, 132, 10, 195, 186, 12, 20, 0, 0, 18, 66, 64, 48, 112, 195, 169, 99, 195, 169, 115, 0, 44, 29, 42, 81, 115, 32, 17, 66, 64, 48, 112, 195, 169, 99, 195, 169, 110, 0, 44, 29, 81, 110, 32, 18, 66, 64, 48, 112, 195, 169, 99, 195, 169, 110, 0, 44, 29, 42, 81, 110, 32, 18, 66, 64, 48, 112, 195, 169, 99, 195, 169, 107, 0, 44, 29, 42, 81, 107, 32, 32, 7, 22, 5, 20, 20, 195, 188, 11, 82, 107, 47, 12, 109, 49, 10, 6, 15, 111, 87, 52, 107, 0, 13, 81, 195, 169, 115, 122, 114, 101, 32, 7, 132, 2, 195, 173, 26, 13, 9, 198, 88, 82, 5, 77, 49, 64, 13, 5, 194, 52, 144, 13, 20, 66, 44, 208, 49, 37, 55, 113, 63, 111, 47, 107, 52, 47, 0, 44, 13, 81, 116, 32, 22, 66, 44, 208, 49, 37, 55, 113, 63, 111, 47, 107, 52, 107, 89, 0, 44, 13, 81, 101, 115, 32, 23, 66, 44, 208, 49, 37, 55, 113, 63, 111, 47, 107, 52, 65, 37, 0, 44, 13, 81, 110, 121, 105, 32, 27, 66, 44, 208, 49, 37, 55, 113, 63, 111, 47, 107, 52, 65, 37, 52, 107, 0, 44, 13, 81, 110, 121, 105, 114, 101, 32, 22, 66, 44, 208, 49, 37, 55, 113, 63, 111, 47, 107, 52, 52, 107, 0, 44, 13, 81, 114, 101, 32, 15, 66, 44, 208, 49, 37, 55, 113, 63, 111, 47, 107, 52, 0, 13, 0, 31, 6, 19, 26, 195, 161, 13, 1, 87, 112, 63, 106, 23, 74, 108, 49, 12, 107, 50, 0, 13, 81, 99, 115, 195, 182, 107, 107, 101, 110, 32, 36, 67, 44, 86, 132, 49, 107, 86, 70, 23, 106, 6, 23, 81, 107, 55, 105, 116, 86, 107, 47, 0, 13, 82, 97, 32, 102, 101, 108, 104, 197, 145, 122, 101, 116, 32, 9, 134, 19, 26, 195, 161, 13, 1, 13, 6, 195, 44, 86, 132, 13, 0, 11, 200, 44, 85, 133, 72, 81, 5, 81, 64, 13, 11, 200, 76, 146, 197, 72, 81, 5, 81, 64, 13, 0, 8, 197, 32, 21, 14, 4, 176, 13, 12, 201, 4, 194, 193, 48, 208, 90, 61, 69, 0, 13, 0, 43, 11, 12, 5, 8, 5, 20, 197, 145, 19, 195, 169, 7, 55, 107, 105, 107, 47, 116, 89, 111, 79, 15, 82, 106, 50, 15, 106, 52, 52, 106, 0, 13, 82, 118, 97, 110, 32, 97, 114, 114, 97, 32, 10, 135, 11, 195, 169, 18, 12, 5, 11, 13, 9, 198, 8, 150, 148, 61, 48, 84, 13, 14, 139, 12, 5, 8, 5, 20, 197, 145, 19, 195, 169, 7, 13, 10, 135, 12, 5, 14, 14, 195, 169, 11, 13, 0, 22, 67, 52, 149, 0, 63, 37, 47, 23, 107, 87, 107, 55, 0, 13, 81, 101, 115, 122, 101, 108, 32, 38, 67, 52, 149, 0, 63, 37, 47, 10, 6, 15, 82, 112, 55, 47, 39, 87, 47, 106, 47, 50, 37, 0, 13, 81, 118, 195, 161, 108, 116, 111, 122, 116, 97, 116, 110, 105, 32, 6, 195, 8, 244, 148, 13, 6, 195, 52, 149, 0, 13, 0, 7, 196, 24, 241, 206, 36, 13, 11, 200, 80, 20, 148, 32, 21, 14, 4, 176, 13, 31, 68, 24, 241, 202, 4, 81, 39, 79, 57, 106, 10, 6, 15, 111, 52, 47, 107, 50, 37, 0, 13, 81, 195, 169, 114, 116, 101, 110, 105, 32, 40, 68, 24, 241, 202, 4, 81, 39, 79, 57, 106, 23, 107, 52, 107, 70, 63, 111, 65, 107, 86, 50, 37, 0, 13, 81, 101, 114, 101, 100, 109, 195, 169, 110, 121, 101, 122, 110, 105, 32, 10, 135, 6, 195, 161, 10, 12, 2, 1, 13, 11, 200, 72, 83, 132, 77, 161, 82, 72, 80, 13, 7, 196, 24, 241, 202, 4, 13, 0, 8, 197, 44, 85, 25, 20, 112, 13, 8, 197, 8, 18, 129, 36, 208, 13, 8, 197, 77, 160, 86, 4, 176, 13, 0, 12, 137, 20, 1, 7, 195, 161, 12, 12, 1, 13, 13, 12, 137, 11, 5, 26, 5, 12, 197, 145, 10, 5, 13, 13, 138, 22, 195, 161, 19, 195, 161, 18, 15, 12, 20, 13, 7, 132, 2, 195, 173, 18, 13, 0, 14, 203, 20, 195, 85, 48, 20, 218, 80, 245, 20, 84, 176, 13, 14, 203, 24, 83, 15, 49, 96, 83, 32, 21, 14, 4, 176, 13, 10, 199, 80, 84, 150, 21, 161, 84, 80, 13, 10, 135, 12, 5, 14, 14, 195, 169, 12, 13, 11, 136, 22, 195, 169, 12, 20, 195, 169, 11, 13, 10, 135, 195, 169, 10, 6, 195, 169, 12, 22, 0, 11, 136, 11, 195, 182, 20, 195, 182, 20, 20, 13, 15, 140, 11, 15, 14, 3, 5, 14, 20, 18, 195, 161, 12, 20, 13, 6, 131, 14, 197, 145, 13, 0, 6, 131, 195, 173, 18, 13, 12, 137, 11, 195, 188, 12, 4, 195, 182, 20, 20, 13, 8, 133, 19, 26, 195, 169, 16, 13, 0, 12, 6, 95, 35, 45, 195, 169, 20, 111, 47, 0, 21, 0, 10, 135, 11, 195, 169, 16, 12, 5, 20, 13, 0, 15, 140, 14, 5, 22, 5, 12, 197, 145, 11, 14, 195, 169, 12, 13, 60, 8, 6, 5, 12, 195, 188, 12, 5, 20, 81, 107, 55, 109, 55, 107, 47, 23, 106, 49, 106, 70, 112, 57, 63, 107, 50, 47, 107, 89, 12, 111, 79, 111, 47, 0, 13, 81, 97, 107, 97, 100, 195, 161, 108, 121, 109, 101, 110, 116, 101, 115, 115, 195, 169, 103, 195, 169, 116, 32, 11, 136, 6, 5, 12, 195, 188, 12, 5, 20, 13, 28, 8, 6, 5, 12, 195, 188, 12, 5, 20, 81, 107, 55, 109, 55, 107, 47, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 9, 134, 6, 5, 8, 195, 169, 18, 13, 10, 135, 19, 26, 195, 179, 22, 195, 161, 13, 7, 132, 6, 195, 182, 12, 13, 0, 12, 137, 20, 5, 19, 20, 195, 188, 12, 5, 20, 13, 8, 133, 19, 26, 195, 169, 20, 13, 0, 13, 138, 6, 5, 12, 195, 188, 12, 5, 20, 5, 20, 13, 9, 134, 19, 5, 7, 195, 173, 20, 13, 8, 133, 12, 195, 161, 14, 25, 13, 0, 24, 3, 195, 182, 20, 108, 47, 23, 49, 108, 52, 109, 55, 0, 13, 81, 107, 195, 182, 114, 195, 188, 108, 32, 14, 139, 20, 5, 18, 22, 5, 26, 5, 20, 195, 169, 20, 13, 14, 139, 11, 195, 169, 20, 19, 195, 169, 7, 5, 9, 20, 13, 0, 18, 143, 11, 195, 169, 20, 19, 195, 169, 7, 2, 5, 5, 19, 20, 5, 13, 13, 12, 137, 9, 19, 13, 5, 18, 20, 195, 188, 11, 13, 14, 139, 11, 18, 9, 20, 9, 11, 21, 19, 19, 195, 161, 13, 11, 136, 1, 10, 195, 161, 14, 12, 1, 20, 13, 11, 4, 95, 49, 15, 24, 107, 55, 89, 116, 0, 0, 35, 8, 11, 15, 18, 13, 195, 161, 14, 25, 49, 39, 52, 63, 112, 65, 23, 49, 108, 86, 108, 47, 12, 0, 13, 81, 107, 195, 182, 122, 195, 182, 116, 116, 32, 15, 140, 5, 7, 25, 195, 169, 18, 20, 5, 12, 13, 197, 177, 13, 0, 6, 131, 195, 182, 19, 72, 0, 12, 137, 14, 1, 7, 25, 11, 15, 18, 195, 186, 13, 14, 139, 195, 169, 12, 5, 20, 195, 169, 22, 195, 169, 20, 13, 13, 138, 2, 1, 10, 11, 5, 22, 5, 18, 197, 145, 13, 8, 133, 195, 161, 18, 195, 186, 13, 0, 15, 140, 11, 195, 169, 14, 25, 19, 26, 5, 18, 195, 173, 20, 13, 0, 16, 141, 13, 1, 18, 1, 4, 22, 195, 161, 14, 25, 1, 9, 20, 13, 19, 144, 20, 5, 12, 10, 5, 19, 195, 173, 20, 13, 195, 169, 14, 25, 197, 177, 13, 8, 133, 4, 195, 182, 14, 20, 13, 0, 0, 11, 136, 10, 195, 161, 18, 1, 20, 15, 11, 13, 6, 195, 40, 241, 192, 13, 8, 133, 19, 26, 195, 179, 18, 72, 0, 22, 147, 8, 1, 19, 26, 14, 195, 161, 12, 8, 1, 20, 1, 20, 12, 1, 14, 14, 195, 161, 13, 6, 195, 40, 241, 193, 13, 0, 0, 0, 6, 195, 24, 241, 192, 13, 36, 67, 24, 241, 192, 81, 39, 79, 23, 106, 6, 15, 69, 37, 86, 39, 74, 12, 112, 79, 0, 13, 82, 97, 32, 98, 105, 122, 111, 116, 116, 115, 195, 161, 103, 32, 29, 67, 24, 241, 192, 81, 39, 79, 23, 105, 106, 34, 117, 39, 55, 50, 37, 0, 13, 81, 104, 97, 114, 99, 111, 108, 110, 105, 32, 0, 6, 195, 24, 241, 193, 13, 15, 140, 5, 21, 18, 195, 179, 16, 195, 161, 2, 195, 179, 12, 13, 8, 133, 18, 195, 161, 14, 11, 13, 6, 195, 52, 17, 193, 13, 0, 42, 3, 195, 169, 14, 111, 50, 15, 37, 89, 15, 63, 107, 79, 74, 37, 50, 112, 55, 47, 106, 63, 0, 13, 82, 105, 115, 32, 109, 101, 103, 99, 115, 105, 110, 195, 161, 108, 116, 97, 109, 32, 16, 3, 195, 169, 14, 111, 50, 15, 37, 89, 0, 13, 81, 105, 115, 32, 12, 137, 6, 21, 14, 11, 3, 9, 195, 179, 20, 13, 9, 134, 11, 9, 12, 195, 179, 19, 13, 6, 131, 195, 169, 14, 13, 8, 133, 19, 26, 195, 179, 20, 13, 6, 131, 195, 169, 14, 13, 0, 15, 140, 11, 195, 188, 12, 6, 195, 182, 12, 4, 195, 182, 14, 13, 9, 198, 40, 83, 26, 21, 69, 0, 13, 5, 194, 72, 16, 13, 0, 7, 132, 10, 195, 179, 11, 13, 6, 131, 195, 169, 12, 13, 0, 7, 132, 20, 195, 179, 12, 13, 0, 8, 197, 36, 195, 5, 80, 144, 13, 22, 5, 1, 12, 195, 179, 12, 106, 55, 113, 55, 10, 6, 15, 106, 86, 0, 13, 81, 97, 122, 32, 35, 69, 88, 19, 1, 52, 144, 82, 106, 55, 106, 63, 37, 15, 48, 52, 39, 69, 55, 111, 63, 106, 0, 13, 81, 112, 114, 111, 98, 108, 195, 169, 109, 97, 32, 8, 197, 88, 19, 1, 52, 144, 13, 8, 197, 25, 85, 14, 4, 176, 13, 8, 197, 64, 243, 148, 40, 16, 13, 8, 133, 1, 12, 195, 179, 12, 13, 0, 9, 198, 24, 150, 133, 80, 82, 192, 13, 9, 198, 88, 84, 147, 20, 230, 64, 13, 9, 198, 60, 179, 218, 80, 18, 192, 13, 9, 198, 80, 17, 202, 4, 149, 0, 13, 9, 198, 88, 83, 5, 80, 82, 192, 13, 14, 67, 48, 212, 0, 107, 55, 107, 63, 48, 111, 0, 42, 42, 0, 23, 67, 24, 242, 192, 81, 39, 49, 23, 49, 108, 86, 111, 0, 13, 81, 107, 195, 182, 122, 195, 169, 32, 43, 67, 24, 242, 192, 81, 39, 49, 23, 49, 108, 86, 111, 23, 107, 63, 107, 55, 49, 107, 70, 37, 49, 0, 13, 82, 107, 195, 182, 122, 195, 169, 32, 101, 109, 101, 108, 107, 101, 100, 105, 107, 32, 46, 67, 24, 242, 192, 81, 39, 49, 23, 49, 108, 86, 108, 47, 12, 23, 87, 113, 52, 113, 70, 37, 49, 0, 13, 82, 107, 195, 182, 122, 195, 182, 116, 116, 32, 115, 122, 195, 179, 114, 195, 179, 100, 105, 107, 32, 70, 67, 24, 242, 192, 81, 39, 49, 23, 49, 108, 86, 111, 23, 74, 108, 49, 12, 107, 50, 23, 106, 23, 105, 116, 63, 111, 52, 89, 111, 49, 55, 107, 47, 0, 13, 84, 107, 195, 182, 122, 195, 169, 32, 99, 115, 195, 182, 107, 107, 101, 110, 32, 97, 32, 104, 197, 145, 109, 195, 169, 114, 115, 195, 169, 107, 108, 101, 116, 32, 41, 67, 24, 242, 192, 81, 39, 49, 23, 49, 108, 86, 108, 47, 12, 23, 106, 55, 106, 49, 40, 55, 0, 13, 82, 107, 195, 182, 122, 195, 182, 116, 116, 32, 97, 108, 97, 107, 117, 108, 32, 74, 67, 24, 242, 192, 81, 39, 49, 23, 81, 108, 55, 111, 23, 107, 63, 107, 55, 49, 107, 70, 37, 49, 23, 106, 23, 105, 116, 63, 111, 52, 89, 111, 49, 55, 107, 47, 0, 13, 84, 102, 195, 182, 108, 195, 169, 32, 101, 109, 101, 108, 107, 101, 100, 105, 107, 32, 97, 32, 104, 197, 145, 109, 195, 169, 114, 115, 195, 169, 107, 108, 101, 116, 32, 45, 67, 24, 242, 192, 81, 39, 49, 23, 49, 108, 86, 108, 47, 12, 23, 82, 112, 51, 105, 106, 47, 113, 0, 13, 82, 107, 195, 182, 122, 195, 182, 116, 116, 32, 118, 195, 161, 114, 104, 97, 116, 195, 179, 32, 6, 195, 24, 242, 192, 13, 15, 140, 3, 19, 195, 188, 20, 195, 182, 18, 20, 195, 182, 11, 20, 0, 6, 195, 24, 241, 217, 13, 10, 135, 20, 195, 182, 14, 11, 18, 5, 13, 12, 137, 1, 10, 195, 161, 14, 12, 10, 21, 11, 13, 7, 132, 10, 195, 179, 12, 13, 7, 132, 6, 195, 169, 12, 13, 6, 131, 195, 169, 9, 72, 7, 132, 18, 195, 179, 12, 13, 0, 24, 3, 195, 169, 22, 111, 82, 23, 107, 55, 47, 107, 55, 47, 0, 13, 81, 101, 108, 116, 101, 108, 116, 32, 22, 3, 195, 169, 22, 111, 82, 23, 106, 55, 106, 47, 12, 0, 13, 81, 97, 108, 97, 116, 116, 32, 31, 69, 77, 160, 86, 4, 208, 87, 106, 82, 106, 63, 15, 57, 112, 52, 112, 89, 106, 0, 13, 81, 106, 195, 161, 114, 195, 161, 115, 97, 32, 12, 201, 77, 161, 82, 21, 1, 76, 56, 82, 192, 13, 8, 197, 80, 17, 202, 4, 144, 13, 6, 131, 195, 169, 22, 13, 8, 133, 19, 26, 195, 179, 12, 13, 12, 137, 12, 195, 161, 20, 19, 26, 15, 20, 20, 13, 6, 131, 195, 182, 14, 13, 0, 7, 66, 57, 144, 107, 65, 0, 9, 198, 52, 20, 129, 16, 242, 192, 13, 10, 135, 22, 195, 161, 7, 195, 179, 11, 13, 41, 5, 195, 169, 7, 18, 5, 111, 79, 52, 107, 23, 87, 112, 63, 110, 47, 105, 106, 47, 40, 50, 49, 0, 13, 81, 115, 122, 195, 161, 109, 195, 173, 116, 104, 97, 116, 117, 110, 107, 32, 9, 198, 88, 19, 1, 52, 149, 0, 13, 9, 198, 24, 243, 25, 56, 18, 192, 13, 9, 134, 5, 14, 14, 195, 169, 12, 13, 0, 26, 71, 32, 83, 25, 21, 161, 84, 80, 105, 107, 57, 107, 86, 107, 47, 12, 23, 49, 37, 0, 13, 81, 107, 105, 32, 10, 199, 80, 145, 210, 37, 51, 133, 44, 13, 14, 139, 8, 1, 20, 195, 161, 18, 15, 26, 15, 20, 20, 13, 7, 132, 12, 195, 179, 7, 13, 9, 134, 11, 195, 182, 26, 195, 169, 13, 0, 15, 140, 7, 15, 14, 4, 15, 12, 1, 20, 20, 195, 179, 12, 13, 15, 140, 16, 195, 169, 12, 4, 195, 161, 11, 20, 195, 179, 12, 13, 13, 138, 12, 5, 7, 9, 14, 11, 195, 161, 2, 2, 13, 15, 140, 11, 15, 18, 12, 195, 161, 20, 15, 26, 15, 20, 20, 13, 15, 204, 40, 83, 5, 57, 66, 197, 104, 129, 84, 56, 82, 192, 13, 12, 136, 11, 195, 182, 26, 195, 182, 20, 20, 72, 22, 0, 23, 3, 195, 169, 18, 111, 52, 23, 82, 111, 79, 107, 47, 0, 13, 81, 118, 195, 169, 103, 101, 116, 32, 18, 3, 195, 169, 18, 111, 52, 10, 6, 15, 107, 55, 0, 13, 81, 101, 108, 32, 11, 136, 10, 195, 161, 18, 1, 20, 1, 9, 13, 12, 137, 11, 15, 18, 195, 161, 2, 195, 179, 12, 13, 12, 201, 72, 83, 132, 77, 161, 82, 56, 82, 192, 13, 11, 136, 195, 173, 18, 195, 161, 19, 18, 1, 13, 12, 137, 8, 9, 2, 195, 161, 26, 15, 20, 20, 13, 6, 131, 195, 169, 18, 13, 0, 42, 10, 4, 15, 12, 7, 15, 11, 18, 195, 179, 12, 70, 39, 55, 79, 39, 49, 52, 113, 55, 23, 69, 107, 87, 111, 55, 107, 49, 0, 13, 81, 98, 101, 115, 122, 195, 169, 108, 101, 107, 32, 17, 3, 195, 169, 19, 111, 89, 23, 57, 113, 0, 13, 81, 106, 195, 179, 32, 26, 3, 195, 169, 19, 111, 89, 23, 81, 106, 48, 106, 70, 39, 89, 0, 13, 81, 102, 97, 112, 97, 100, 111, 115, 32, 34, 3, 195, 169, 19, 111, 89, 23, 69, 39, 87, 12, 106, 50, 47, 113, 106, 49, 0, 13, 81, 98, 111, 115, 115, 122, 97, 110, 116, 195, 179, 97, 107, 32, 13, 138, 9, 14, 4, 9, 195, 161, 2, 195, 179, 12, 13, 19, 144, 22, 195, 161, 12, 20, 15, 26, 195, 169, 11, 15, 14, 25, 1, 2, 2, 13, 25, 3, 195, 169, 19, 111, 89, 63, 113, 77, 12, 112, 47, 0, 13, 81, 109, 195, 179, 100, 106, 195, 161, 116, 32, 9, 134, 9, 14, 4, 195, 173, 20, 13, 8, 131, 195, 169, 19, 72, 12, 22, 18, 4, 95, 3, 9, 18, 117, 37, 52, 49, 40, 63, 81, 55, 107, 49, 87, 0, 0, 19, 5, 19, 26, 195, 173, 22, 87, 110, 82, 23, 107, 55, 0, 13, 81, 101, 108, 32, 13, 138, 22, 195, 161, 18, 15, 19, 195, 161, 2, 1, 13, 9, 134, 8, 15, 26, 26, 195, 161, 13, 0, 54, 11, 3, 19, 1, 16, 1, 4, 195, 169, 11, 18, 1, 74, 106, 48, 106, 70, 111, 49, 52, 106, 23, 89, 37, 50, 74, 23, 49, 37, 55, 112, 47, 112, 89, 0, 13, 82, 115, 105, 110, 99, 115, 32, 107, 105, 108, 195, 161, 116, 195, 161, 115, 32, 15, 140, 195, 161, 12, 12, 1, 16, 15, 20, 18, 195, 179, 12, 13, 7, 196, 52, 81, 217, 20, 13, 7, 196, 53, 83, 139, 4, 13, 19, 144, 11, 1, 12, 195, 179, 26, 11, 15, 4, 195, 161, 19, 20, 195, 179, 12, 13, 0, 15, 140, 20, 1, 14, 195, 161, 3, 19, 1, 4, 195, 179, 9, 13, 12, 137, 22, 195, 169, 20, 5, 12, 195, 169, 20, 13, 16, 141, 6, 15, 7, 12, 1, 12, 20, 1, 11, 18, 195, 179, 12, 13, 6, 131, 195, 179, 14, 72, 0, 17, 3, 95, 194, 183, 49, 108, 86, 111, 48, 89, 116, 48, 39, 50, 47, 0, 9, 134, 11, 5, 26, 195, 169, 20, 13, 10, 135, 8, 9, 20, 20, 195, 188, 11, 13, 17, 142, 11, 1, 16, 1, 3, 9, 20, 195, 161, 19, 18, 195, 179, 12, 13, 8, 133, 14, 5, 22, 197, 177, 13, 10, 135, 8, 9, 20, 20, 195, 188, 11, 13, 0, 32, 7, 5, 19, 195, 169, 12, 25, 20, 107, 89, 111, 57, 47, 10, 6, 15, 55, 112, 47, 39, 49, 0, 13, 81, 108, 195, 161, 116, 111, 107, 32, 10, 135, 5, 18, 5, 10, 195, 169, 20, 13, 18, 143, 20, 195, 161, 18, 19, 1, 19, 8, 195, 161, 26, 2, 195, 179, 12, 13, 18, 143, 19, 26, 5, 13, 16, 15, 14, 20, 10, 195, 161, 2, 195, 179, 12, 13, 10, 199, 52, 243, 132, 4, 229, 78, 44, 13, 9, 134, 11, 195, 169, 18, 14, 9, 13, 8, 133, 19, 26, 195, 182, 18, 72, 0, 11, 136, 19, 26, 5, 18, 22, 195, 169, 20, 13, 0, 19, 3, 95, 194, 178, 63, 112, 89, 39, 70, 37, 49, 105, 106, 47, 82, 112, 65, 0, 19, 144, 11, 195, 182, 26, 195, 169, 16, 16, 15, 14, 20, 10, 195, 161, 2, 1, 13, 12, 137, 19, 26, 5, 13, 195, 169, 12, 25, 20, 13, 11, 136, 5, 12, 12, 195, 161, 20, 14, 9, 13, 9, 134, 2, 195, 161, 14, 9, 11, 13, 11, 136, 11, 5, 18, 195, 188, 12, 14, 9, 13, 0, 20, 3, 95, 194, 179, 105, 106, 34, 63, 106, 70, 37, 49, 105, 106, 47, 82, 112, 65, 0, 42, 8, 19, 26, 15, 13, 15, 18, 195, 186, 87, 39, 63, 39, 52, 114, 23, 82, 39, 55, 47, 23, 55, 112, 47, 50, 37, 0, 13, 82, 118, 111, 108, 116, 32, 108, 195, 161, 116, 110, 105, 32, 21, 146, 5, 12, 2, 15, 3, 19, 195, 161, 20, 195, 161, 19, 15, 11, 18, 195, 179, 12, 13, 12, 137, 5, 7, 25, 19, 26, 5, 18, 197, 177, 13, 14, 4, 195, 182, 26, 22, 108, 86, 82, 107, 77, 0, 25, 9, 0, 14, 139, 19, 26, 195, 161, 13, 195, 173, 20, 8, 1, 20, 13, 12, 137, 5, 12, 197, 145, 19, 26, 195, 182, 18, 13, 14, 139, 18, 5, 14, 4, 19, 26, 5, 18, 195, 169, 20, 13, 14, 139, 22, 195, 169, 12, 5, 13, 195, 169, 14, 25, 20, 13, 10, 199, 40, 21, 129, 76, 243, 20, 4, 13, 6, 195, 56, 244, 192, 72, 11, 67, 65, 54, 148, 48, 87, 12, 47, 0, 41, 0, 44, 12, 11, 195, 182, 26, 12, 5, 13, 195, 169, 14, 25, 20, 49, 108, 86, 55, 107, 63, 111, 65, 47, 23, 106, 70, 39, 47, 12, 23, 49, 37, 0, 13, 82, 97, 100, 111, 116, 116, 32, 107, 105, 32, 14, 139, 10, 15, 7, 19, 26, 1, 2, 195, 161, 12, 25, 13, 12, 137, 22, 195, 161, 12, 20, 15, 26, 9, 11, 13, 0, 9, 198, 48, 81, 217, 20, 225, 75, 13, 0, 16, 141, 19, 195, 169, 18, 195, 188, 12, 195, 169, 11, 5, 14, 25, 13, 9, 198, 52, 81, 212, 20, 197, 0, 13, 8, 133, 12, 195, 161, 7, 25, 13, 0, 10, 199, 77, 163, 210, 84, 194, 143, 56, 13, 9, 198, 48, 81, 143, 29, 147, 137, 13, 11, 136, 11, 5, 4, 22, 197, 177, 5, 11, 13, 10, 199, 24, 19, 129, 80, 146, 213, 76, 13, 14, 4, 95, 19, 20, 11, 112, 47, 105, 114, 86, 112, 89, 0, 15, 7, 95, 35, 45, 18, 195, 179, 12, 112, 52, 113, 55, 0, 21, 0, 16, 3, 95, 194, 173, 55, 112, 77, 49, 108, 47, 116, 57, 107, 55, 0, 63, 14, 5, 7, 25, 195, 169, 18, 20, 5, 12, 13, 197, 177, 5, 14, 107, 77, 12, 111, 52, 47, 107, 55, 63, 115, 107, 50, 23, 63, 107, 79, 112, 55, 12, 106, 48, 110, 47, 39, 47, 12, 106, 0, 13, 81, 109, 101, 103, 195, 161, 108, 108, 97, 112, 195, 173, 116, 111, 116, 116, 97, 32, 33, 72, 48, 82, 5, 80, 85, 12, 20, 224, 55, 107, 105, 107, 47, 107, 47, 55, 107, 50, 23, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 12, 137, 7, 25, 195, 161, 18, 20, 195, 179, 11, 13, 7, 132, 20, 195, 182, 12, 13, 0, 8, 133, 1, 4, 195, 179, 20, 13, 11, 4, 95, 1, 3, 21, 111, 55, 107, 89, 0, 0, 22, 3, 95, 194, 171, 69, 107, 55, 89, 116, 69, 106, 55, 37, 70, 111, 86, 116, 57, 107, 55, 0, 44, 70, 52, 81, 5, 72, 33, 64, 63, 107, 70, 107, 52, 69, 107, 23, 47, 107, 52, 107, 55, 111, 89, 111, 69, 107, 50, 0, 13, 81, 116, 101, 114, 101, 108, 195, 169, 115, 195, 169, 98, 101, 110, 32, 9, 134, 11, 195, 179, 4, 15, 20, 13, 13, 138, 3, 5, 12, 12, 195, 161, 18, 195, 179, 12, 13, 6, 131, 195, 179, 19, 72, 0, 22, 4, 20, 195, 182, 11, 47, 108, 49, 23, 37, 79, 106, 86, 0, 13, 81, 105, 103, 97, 122, 32, 15, 140, 20, 1, 18, 20, 195, 179, 26, 11, 15, 4, 9, 11, 13, 11, 136, 8, 195, 179, 14, 1, 16, 9, 7, 13, 0, 40, 70, 40, 241, 207, 44, 32, 78, 57, 39, 79, 39, 49, 69, 106, 50, 23, 37, 55, 12, 107, 47, 111, 49, 107, 89, 0, 13, 81, 105, 108, 108, 101, 116, 195, 169, 107, 101, 115, 32, 15, 140, 8, 1, 12, 195, 161, 12, 195, 161, 18, 195, 179, 12, 13, 11, 136, 8, 195, 179, 14, 1, 16, 15, 20, 13, 7, 132, 10, 195, 179, 20, 13, 7, 132, 18, 195, 182, 12, 13, 0, 12, 137, 7, 25, 195, 161, 18, 20, 195, 179, 20, 13, 16, 141, 20, 1, 18, 20, 195, 161, 19, 195, 161, 18, 195, 179, 12, 13, 11, 136, 10, 5, 12, 195, 182, 12, 14, 9, 13, 0, 20, 66, 52, 208, 63, 37, 55, 37, 63, 111, 47, 107, 52, 47, 0, 44, 13, 81, 116, 32, 22, 66, 52, 208, 63, 37, 55, 37, 63, 111, 47, 107, 52, 107, 89, 0, 44, 13, 81, 101, 115, 32, 27, 66, 52, 208, 63, 37, 55, 37, 63, 111, 47, 107, 52, 65, 37, 52, 107, 0, 44, 13, 81, 110, 121, 105, 114, 101, 32, 23, 66, 52, 208, 63, 37, 55, 37, 63, 111, 47, 107, 52, 65, 37, 0, 44, 13, 81, 110, 121, 105, 32, 15, 66, 52, 208, 63, 37, 55, 37, 63, 111, 47, 107, 52, 0, 13, 0, 16, 3, 95, 194, 164, 48, 111, 50, 86, 50, 107, 63, 57, 107, 55, 0, 0, 19, 144, 5, 12, 6, 15, 7, 1, 4, 195, 161, 19, 195, 161, 18, 195, 179, 12, 13, 10, 135, 22, 195, 161, 12, 14, 9, 1, 13, 30, 67, 40, 241, 201, 57, 39, 79, 37, 23, 87, 108, 82, 107, 79, 107, 47, 0, 13, 81, 115, 122, 195, 182, 118, 101, 103, 101, 116, 32, 34, 67, 40, 241, 201, 57, 39, 79, 37, 15, 55, 111, 48, 111, 89, 107, 49, 107, 47, 0, 13, 81, 108, 195, 169, 112, 195, 169, 115, 101, 107, 101, 116, 32, 14, 139, 14, 25, 195, 186, 10, 20, 195, 179, 26, 14, 9, 13, 0, 8, 197, 76, 82, 148, 20, 208, 13, 8, 197, 32, 83, 25, 20, 176, 13, 16, 141, 6, 15, 18, 18, 195, 161, 19, 11, 195, 179, 4, 15, 20, 13, 8, 197, 56, 82, 212, 20, 176, 13, 0, 9, 198, 48, 84, 218, 56, 82, 192, 72, 9, 198, 44, 84, 133, 76, 146, 192, 13, 9, 198, 4, 230, 65, 28, 242, 192, 13, 9, 198, 24, 82, 211, 104, 146, 192, 13, 10, 135, 22, 195, 169, 7, 26, 9, 11, 13, 9, 198, 72, 244, 211, 104, 18, 192, 13, 0, 11, 3, 95, 194, 160, 87, 113, 49, 108, 86, 0, 10, 199, 21, 49, 84, 20, 176, 133, 56, 13, 10, 135, 12, 195, 161, 20, 15, 20, 20, 13, 10, 4, 95, 18, 14, 7, 49, 108, 52, 0, 0, 16, 3, 95, 194, 161, 106, 55, 89, 113, 37, 50, 70, 107, 49, 87, 0, 7, 3, 95, 195, 169, 111, 0, 14, 139, 195, 182, 19, 19, 26, 5, 22, 5, 20, 14, 9, 13, 8, 133, 19, 26, 195, 182, 7, 13, 7, 132, 2, 195, 179, 12, 72, 0, 8, 197, 52, 83, 148, 20, 208, 13, 12, 137, 7, 25, 195, 161, 18, 20, 15, 20, 20, 13, 8, 133, 11, 195, 188, 26, 4, 13, 0, 13, 138, 9, 18, 195, 161, 14, 25, 20, 195, 179, 12, 13, 36, 6, 1, 18, 18, 195, 179, 12, 106, 52, 52, 113, 55, 10, 6, 15, 82, 106, 50, 10, 6, 15, 87, 113, 0, 13, 82, 118, 97, 110, 32, 115, 122, 195, 179, 32, 11, 136, 9, 4, 197, 145, 19, 5, 2, 2, 13, 12, 137, 11, 195, 169, 18, 195, 169, 19, 18, 5, 13, 46, 10, 20, 1, 18, 11, 195, 173, 20, 15, 20, 20, 47, 106, 52, 49, 110, 47, 39, 47, 12, 15, 10, 37, 70, 116, 57, 112, 52, 112, 89, 0, 13, 81, 105, 100, 197, 145, 106, 195, 161, 114, 195, 161, 115, 32, 9, 198, 53, 85, 1, 80, 226, 64, 13, 10, 135, 1, 4, 195, 179, 4, 9, 11, 13, 9, 198, 52, 240, 137, 48, 242, 192, 13, 9, 134, 1, 18, 18, 195, 179, 12, 13, 9, 134, 1, 18, 18, 195, 179, 12, 13, 0, 12, 137, 4, 18, 195, 161, 7, 195, 161, 2, 2, 13, 50, 11, 20, 195, 161, 13, 15, 7, 1, 20, 15, 20, 20, 47, 112, 63, 39, 79, 106, 47, 39, 47, 12, 23, 49, 37, 106, 70, 112, 89, 23, 55, 107, 87, 0, 13, 82, 107, 105, 97, 100, 195, 161, 115, 32, 108, 101, 115, 122, 32, 14, 139, 20, 195, 161, 13, 15, 7, 1, 20, 15, 20, 20, 13, 10, 199, 77, 161, 82, 88, 86, 142, 36, 13, 0, 11, 200, 24, 241, 207, 73, 99, 211, 60, 208, 13, 16, 141, 9, 14, 20, 195, 169, 26, 13, 195, 169, 14, 25, 5, 11, 13, 12, 137, 20, 195, 161, 18, 15, 12, 195, 179, 11, 13, 7, 196, 72, 17, 193, 16, 13, 7, 196, 20, 225, 197, 52, 13, 0, 11, 136, 8, 195, 179, 14, 1, 16, 10, 1, 13, 12, 137, 11, 15, 18, 195, 161, 18, 195, 179, 12, 13, 11, 136, 5, 12, 195, 169, 7, 7, 195, 169, 13, 13, 138, 5, 18, 197, 145, 12, 20, 5, 20, 9, 11, 13, 12, 201, 60, 64, 70, 36, 118, 69, 48, 226, 64, 13, 9, 134, 5, 12, 14, 195, 182, 11, 13, 0, 15, 140, 12, 5, 7, 4, 18, 195, 161, 7, 195, 161, 2, 2, 13, 9, 134, 14, 195, 169, 14, 9, 20, 13, 13, 138, 20, 195, 169, 13, 195, 161, 18, 195, 179, 12, 13, 12, 137, 195, 161, 12, 12, 195, 173, 20, 10, 1, 13, 0, 9, 198, 77, 161, 82, 20, 195, 69, 13, 33, 11, 11, 1, 20, 15, 14, 195, 161, 18, 195, 179, 12, 49, 106, 47, 39, 50, 112, 52, 113, 55, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 14, 139, 11, 1, 20, 15, 14, 195, 161, 18, 195, 179, 12, 13, 17, 142, 4, 21, 16, 12, 9, 11, 195, 161, 3, 9, 195, 179, 18, 1, 13, 14, 139, 6, 15, 18, 18, 195, 161, 19, 2, 195, 179, 12, 13, 13, 138, 22, 9, 12, 195, 161, 7, 195, 161, 2, 1, 13, 0, 17, 142, 12, 5, 7, 6, 5, 12, 20, 197, 177, 14, 197, 145, 2, 2, 13, 26, 68, 44, 144, 211, 36, 49, 37, 74, 37, 10, 6, 15, 106, 105, 39, 86, 0, 13, 81, 97, 104, 104, 111, 122, 32, 19, 144, 8, 195, 161, 26, 19, 26, 1, 2, 195, 161, 12, 25, 20, 195, 179, 12, 13, 14, 139, 8, 1, 19, 26, 14, 195, 161, 12, 14, 15, 13, 13, 0, 20, 69, 84, 37, 78, 81, 80, 117, 98, 117, 110, 116, 117, 110, 0, 44, 29, 81, 110, 32, 56, 14, 6, 5, 12, 8, 1, 19, 26, 14, 195, 161, 12, 195, 179, 11, 81, 107, 55, 105, 106, 87, 50, 112, 55, 113, 49, 23, 55, 107, 47, 108, 55, 47, 111, 89, 107, 37, 47, 0, 13, 81, 108, 101, 116, 195, 182, 108, 116, 195, 169, 115, 101, 105, 116, 32, 12, 137, 195, 169, 12, 13, 195, 169, 14, 25, 20, 13, 45, 14, 6, 5, 12, 8, 1, 19, 26, 14, 195, 161, 12, 195, 179, 11, 81, 107, 55, 105, 106, 87, 50, 112, 55, 113, 49, 23, 57, 108, 50, 12, 107, 49, 0, 13, 81, 106, 195, 182, 110, 110, 101, 107, 32, 16, 141, 8, 15, 14, 12, 1, 16, 10, 195, 161, 18, 195, 179, 12, 13, 16, 141, 22, 195, 161, 12, 12, 1, 12, 1, 20, 2, 195, 179, 12, 13, 16, 141, 5, 12, 12, 195, 161, 20, 15, 7, 1, 20, 15, 20, 20, 13, 0, 17, 142, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 18, 195, 179, 12, 13, 0, 10, 199, 32, 19, 12, 61, 69, 1, 52, 13, 13, 138, 11, 195, 182, 20, 5, 12, 5, 26, 14, 9, 13, 6, 195, 88, 19, 12, 13, 0, 14, 139, 11, 195, 182, 26, 12, 5, 11, 5, 4, 197, 145, 13, 43, 11, 14, 5, 13, 26, 5, 20, 11, 195, 182, 26, 9, 50, 107, 63, 86, 107, 47, 49, 108, 86, 37, 23, 87, 106, 69, 82, 112, 65, 0, 13, 81, 115, 122, 97, 98, 118, 195, 161, 110, 121, 32, 44, 11, 14, 5, 13, 26, 5, 20, 11, 195, 182, 26, 9, 50, 107, 63, 86, 107, 47, 49, 108, 86, 37, 23, 87, 106, 69, 82, 112, 65, 0, 13, 81, 115, 122, 97, 98, 98, 118, 195, 161, 110, 121, 32, 6, 195, 4, 32, 129, 13, 11, 136, 11, 195, 169, 19, 26, 195, 173, 20, 13, 9, 134, 195, 169, 18, 10, 5, 14, 13, 14, 4, 95, 50, 15, 24, 63, 112, 89, 39, 70, 37, 49, 0, 0, 19, 144, 14, 25, 21, 7, 195, 161, 12, 12, 15, 13, 195, 161, 14, 25, 2, 1, 13, 0, 37, 67, 13, 80, 195, 117, 40, 117, 12, 23, 49, 109, 55, 81, 108, 55, 70, 52, 116, 55, 0, 13, 81, 107, 195, 188, 108, 102, 195, 182, 108, 100, 114, 197, 145, 108, 32, 6, 195, 13, 80, 195, 13, 9, 198, 32, 21, 143, 57, 64, 64, 13, 11, 136, 22, 5, 18, 26, 9, 195, 179, 14, 13, 25, 7, 195, 182, 12, 10, 195, 169, 11, 108, 57, 57, 111, 49, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 10, 135, 13, 195, 169, 18, 14, 5, 11, 13, 9, 134, 195, 169, 10, 10, 5, 12, 13, 10, 135, 195, 161, 12, 12, 14, 1, 11, 13, 14, 6, 95, 35, 45, 22, 5, 12, 111, 82, 107, 55, 0, 21, 0, 12, 137, 11, 195, 169, 16, 5, 11, 2, 5, 14, 22, 15, 7, 95, 35, 45, 20, 195, 179, 12, 112, 47, 113, 55, 0, 21, 0, 19, 144, 2, 197, 177, 14, 3, 19, 5, 12, 5, 11, 13, 195, 169, 14, 25, 20, 13, 7, 196, 80, 244, 148, 4, 13, 7, 196, 80, 84, 150, 20, 13, 0, 10, 135, 195, 188, 7, 25, 2, 5, 14, 13, 13, 138, 19, 26, 195, 161, 13, 15, 12, 14, 1, 11, 13, 10, 135, 19, 26, 195, 161, 13, 15, 14, 13, 8, 197, 72, 144, 211, 4, 160, 13, 0, 9, 198, 32, 144, 130, 4, 229, 0, 13, 34, 7, 12, 195, 161, 20, 195, 179, 11, 55, 112, 47, 113, 49, 23, 87, 112, 63, 112, 52, 106, 0, 13, 81, 115, 122, 195, 161, 109, 195, 161, 114, 97, 32, 9, 198, 4, 35, 1, 45, 32, 64, 13, 11, 136, 20, 21, 4, 195, 161, 19, 195, 186, 13, 10, 135, 20, 5, 20, 20, 195, 169, 11, 13, 14, 139, 8, 1, 19, 26, 14, 195, 161, 12, 14, 1, 11, 13, 0, 15, 140, 22, 195, 161, 19, 195, 161, 18, 15, 12, 14, 1, 11, 13, 10, 199, 53, 83, 139, 4, 129, 76, 100, 13, 10, 135, 19, 26, 195, 161, 13, 15, 12, 13, 12, 137, 22, 195, 182, 12, 7, 25, 2, 5, 14, 13, 19, 134, 12, 195, 161, 20, 20, 1, 13, 81, 112, 101, 116, 197, 145, 102, 105, 116, 32, 6, 195, 21, 33, 68, 13, 14, 139, 18, 1, 14, 7, 10, 1, 9, 20, 195, 179, 12, 13, 9, 134, 195, 169, 18, 26, 5, 13, 13, 9, 134, 12, 195, 161, 20, 20, 1, 13, 6, 131, 195, 188, 12, 13, 6, 195, 80, 83, 20, 13, 0, 11, 200, 9, 81, 1, 64, 84, 212, 20, 224, 13, 0, 12, 137, 13, 195, 186, 12, 20, 18, 195, 179, 12, 13, 16, 141, 11, 15, 12, 12, 195, 169, 7, 195, 161, 9, 22, 1, 12, 13, 13, 138, 18, 5, 14, 4, 197, 145, 18, 14, 5, 11, 13, 8, 197, 24, 241, 207, 81, 64, 13, 13, 138, 195, 173, 20, 195, 169, 12, 20, 195, 169, 11, 13, 0, 15, 140, 6, 5, 12, 2, 15, 14, 20, 195, 161, 19, 195, 186, 13, 17, 142, 195, 169, 18, 20, 5, 19, 195, 173, 20, 197, 145, 22, 5, 12, 13, 7, 132, 10, 195, 182, 14, 13, 7, 132, 8, 195, 182, 26, 13, 13, 4, 95, 1, 3, 50, 49, 107, 47, 12, 116, 89, 0, 0, 18, 143, 9, 12, 12, 5, 20, 195, 169, 11, 5, 19, 195, 169, 22, 5, 12, 13, 10, 135, 12, 195, 161, 20, 195, 179, 20, 13, 18, 143, 19, 5, 7, 195, 173, 20, 19, 195, 169, 7, 195, 169, 22, 5, 12, 13, 13, 138, 5, 12, 13, 5, 19, 195, 169, 12, 20, 5, 13, 6, 195, 88, 145, 4, 13, 0, 19, 144, 11, 195, 182, 26, 195, 182, 19, 19, 195, 169, 7, 195, 169, 22, 5, 12, 13, 14, 139, 11, 18, 9, 20, 9, 26, 195, 161, 12, 20, 1, 13, 0, 11, 136, 19, 26, 195, 161, 12, 12, 14, 9, 13, 9, 198, 4, 64, 75, 61, 162, 75, 13, 17, 142, 11, 15, 14, 3, 5, 14, 20, 18, 195, 161, 12, 14, 1, 11, 13, 17, 142, 8, 1, 10, 12, 195, 169, 11, 20, 1, 12, 1, 14, 15, 11, 13, 0, 9, 198, 77, 160, 66, 61, 69, 0, 13, 23, 148, 8, 15, 26, 26, 195, 161, 10, 195, 161, 18, 21, 12, 195, 161, 19, 15, 11, 2, 1, 14, 13, 9, 134, 195, 169, 18, 26, 5, 4, 13, 5, 194, 72, 80, 13, 9, 66, 60, 176, 39, 49, 0, 42, 42, 11, 67, 52, 148, 211, 63, 37, 87, 12, 0, 25, 0, 10, 135, 19, 26, 195, 161, 13, 15, 20, 13, 0, 16, 141, 195, 169, 18, 20, 195, 169, 11, 5, 12, 10, 195, 188, 11, 13, 6, 195, 76, 242, 1, 13, 15, 140, 22, 9, 26, 19, 7, 195, 161, 12, 1, 20, 15, 20, 13, 0, 8, 197, 81, 81, 20, 84, 176, 13, 20, 145, 11, 195, 169, 19, 26, 195, 188, 12, 195, 169, 11, 5, 11, 14, 195, 169, 12, 13, 10, 135, 13, 21, 19, 26, 195, 161, 10, 13, 15, 140, 2, 9, 26, 15, 14, 25, 195, 173, 20, 1, 14, 9, 13, 8, 197, 52, 20, 139, 60, 208, 13, 0, 9, 198, 80, 82, 5, 80, 82, 192, 13, 0, 6, 195, 60, 181, 0, 20, 0, 15, 140, 19, 26, 1, 2, 195, 161, 12, 25, 26, 195, 179, 20, 13, 0, 40, 69, 56, 85, 133, 104, 144, 50, 107, 82, 107, 86, 37, 23, 47, 40, 55, 106, 57, 70, 39, 50, 39, 89, 106, 0, 13, 81, 116, 117, 108, 97, 106, 100, 111, 110, 111, 115, 97, 32, 30, 67, 21, 161, 82, 107, 86, 107, 52, 23, 81, 39, 52, 37, 50, 47, 39, 47, 0, 13, 81, 102, 111, 114, 105, 110, 116, 111, 116, 32, 26, 67, 21, 161, 82, 107, 86, 107, 52, 23, 81, 39, 52, 37, 50, 47, 0, 13, 81, 102, 111, 114, 105, 110, 116, 32, 8, 197, 40, 81, 217, 20, 144, 13, 16, 141, 6, 195, 188, 7, 7, 5, 20, 12, 5, 14, 195, 188, 12, 13, 9, 198, 80, 82, 5, 80, 225, 75, 13, 9, 198, 48, 82, 5, 80, 225, 75, 13, 0, 15, 3, 95, 203, 135, 55, 107, 81, 107, 55, 111, 65, 110, 55, 0, 9, 198, 29, 144, 75, 61, 34, 64, 13, 0, 14, 139, 195, 169, 18, 4, 5, 11, 5, 9, 22, 5, 12, 13, 14, 139, 5, 12, 197, 145, 6, 15, 18, 4, 21, 12, 20, 13, 15, 140, 11, 195, 182, 22, 5, 20, 11, 5, 26, 14, 5, 11, 13, 18, 4, 95, 56, 48, 15, 65, 39, 55, 117, 82, 106, 50, 106, 70, 37, 49, 0, 0, 11, 200, 40, 83, 12, 20, 209, 90, 80, 80, 13, 33, 68, 52, 17, 193, 16, 63, 106, 79, 106, 70, 23, 107, 77, 107, 50, 107, 89, 107, 50, 0, 13, 81, 101, 103, 121, 101, 110, 101, 115, 101, 110, 32, 14, 139, 11, 9, 2, 195, 169, 11, 195, 188, 12, 22, 5, 13, 15, 140, 11, 9, 1, 4, 195, 161, 19, 195, 161, 22, 1, 12, 13, 11, 200, 77, 163, 198, 81, 97, 82, 20, 144, 13, 7, 196, 52, 17, 193, 16, 13, 0, 12, 3, 95, 194, 186, 89, 39, 34, 87, 112, 63, 0, 9, 134, 20, 15, 10, 195, 161, 19, 13, 0, 23, 3, 95, 194, 187, 69, 107, 55, 89, 116, 57, 39, 69, 69, 37, 70, 111, 86, 116, 57, 107, 55, 0, 17, 142, 20, 1, 18, 20, 15, 26, 195, 169, 11, 195, 161, 22, 1, 12, 13, 37, 9, 6, 15, 18, 4, 195, 173, 20, 22, 1, 81, 39, 52, 70, 110, 47, 82, 106, 23, 106, 6, 23, 87, 113, 47, 0, 13, 82, 97, 32, 115, 122, 195, 179, 116, 32, 13, 138, 22, 195, 161, 12, 20, 15, 26, 15, 20, 20, 13, 12, 137, 10, 195, 161, 20, 19, 26, 1, 14, 1, 13, 15, 140, 6, 15, 18, 13, 195, 161, 10, 195, 161, 2, 1, 14, 13, 0, 0, 16, 3, 95, 194, 185, 107, 55, 87, 116, 105, 106, 47, 82, 112, 65, 0, 17, 142, 20, 195, 161, 18, 19, 1, 4, 1, 12, 15, 13, 2, 1, 14, 13, 19, 144, 13, 5, 3, 8, 1, 14, 9, 26, 13, 21, 19, 195, 161, 22, 1, 12, 13, 0, 53, 10, 19, 26, 5, 13, 195, 169, 12, 25, 5, 19, 87, 107, 63, 111, 57, 107, 89, 23, 69, 107, 112, 55, 12, 37, 47, 112, 89, 39, 49, 106, 47, 0, 13, 81, 98, 101, 195, 161, 108, 108, 195, 173, 116, 195, 161, 115, 111, 107, 97, 116, 32, 15, 140, 22, 195, 169, 12, 5, 13, 195, 169, 14, 25, 5, 13, 13, 11, 136, 10, 5, 12, 12, 5, 7, 197, 177, 13, 9, 198, 53, 85, 1, 80, 224, 75, 13, 0, 10, 67, 56, 21, 15, 50, 112, 47, 113, 0, 21, 146, 22, 195, 169, 7, 18, 5, 8, 1, 10, 20, 195, 161, 19, 195, 161, 22, 1, 12, 13, 14, 139, 13, 5, 7, 14, 195, 169, 26, 26, 195, 188, 11, 13, 10, 135, 18, 195, 179, 12, 21, 14, 11, 13, 0, 7, 131, 195, 186, 20, 20, 13, 0, 6, 195, 32, 83, 25, 13, 23, 148, 8, 15, 26, 26, 195, 161, 10, 195, 161, 18, 21, 12, 195, 161, 19, 195, 161, 22, 1, 12, 13, 6, 195, 32, 83, 25, 13, 6, 195, 32, 83, 25, 13, 0, 45, 8, 195, 169, 18, 9, 14, 20, 197, 145, 111, 52, 37, 50, 47, 116, 23, 49, 111, 52, 70, 111, 89, 107, 49, 69, 107, 50, 0, 13, 81, 107, 195, 169, 114, 100, 195, 169, 115, 101, 107, 98, 101, 110, 32, 35, 69, 32, 83, 25, 20, 224, 105, 107, 57, 107, 50, 23, 49, 37, 105, 106, 77, 12, 112, 49, 0, 13, 81, 107, 105, 104, 97, 103, 121, 106, 195, 161, 107, 32, 45, 8, 195, 169, 18, 9, 14, 20, 197, 145, 111, 52, 37, 50, 47, 116, 23, 81, 52, 37, 89, 12, 110, 47, 111, 89, 107, 49, 0, 13, 81, 102, 114, 105, 115, 115, 195, 173, 116, 195, 169, 115, 101, 107, 32, 15, 140, 8, 9, 22, 1, 20, 1, 12, 15, 19, 19, 195, 161, 13, 11, 136, 195, 169, 18, 9, 14, 20, 197, 145, 13, 8, 197, 32, 83, 25, 20, 224, 13, 10, 135, 13, 5, 14, 20, 195, 169, 14, 13, 6, 131, 195, 186, 18, 13, 0, 12, 137, 11, 5, 22, 5, 18, 195, 169, 11, 5, 13, 14, 139, 14, 195, 182, 22, 5, 11, 5, 4, 195, 169, 19, 13, 14, 139, 14, 5, 21, 18, 15, 12, 195, 179, 7, 21, 19, 13, 10, 135, 22, 195, 161, 18, 14, 1, 11, 13, 10, 135, 10, 195, 161, 18, 14, 1, 11, 13, 10, 135, 14, 195, 169, 26, 14, 5, 11, 13, 8, 133, 18, 195, 179, 12, 1, 13, 14, 6, 95, 35, 45, 22, 1, 12, 112, 82, 106, 55, 0, 21, 0, 9, 198, 24, 83, 12, 20, 195, 137, 13, 17, 142, 10, 5, 12, 5, 14, 20, 197, 145, 19, 195, 169, 7, 197, 177, 13, 0, 13, 138, 197, 145, 19, 26, 9, 14, 20, 195, 169, 14, 13, 30, 10, 8, 1, 19, 26, 14, 195, 161, 12, 19, 26, 105, 106, 87, 50, 112, 55, 87, 15, 81, 107, 55, 0, 13, 81, 102, 101, 108, 32, 13, 138, 8, 1, 19, 26, 14, 195, 161, 12, 19, 26, 13, 14, 139, 195, 169, 16, 195, 173, 20, 195, 169, 19, 197, 177, 13, 7, 132, 195, 169, 10, 20, 13, 15, 8, 95, 35, 45, 195, 161, 22, 1, 12, 112, 82, 106, 55, 0, 15, 8, 95, 35, 45, 195, 169, 22, 5, 12, 111, 82, 107, 55, 0, 0, 11, 2, 195, 151, 47, 106, 55, 48, 106, 89, 0, 9, 198, 48, 85, 20, 21, 65, 75, 13, 10, 135, 20, 1, 14, 4, 195, 173, 10, 13, 8, 197, 24, 145, 217, 20, 192, 13, 12, 201, 57, 146, 76, 5, 66, 207, 105, 64, 64, 13, 14, 139, 195, 161, 12, 12, 1, 13, 15, 11, 2, 1, 14, 13, 0, 16, 141, 6, 5, 10, 12, 5, 19, 26, 20, 195, 169, 19, 197, 177, 13, 13, 138, 8, 15, 18, 4, 195, 161, 9, 22, 1, 12, 13, 47, 10, 9, 4, 197, 145, 14, 11, 195, 169, 14, 20, 37, 70, 116, 50, 49, 111, 50, 47, 23, 106, 6, 15, 81, 107, 55, 105, 116, 86, 107, 47, 0, 13, 82, 97, 32, 102, 101, 108, 104, 197, 145, 122, 101, 116, 32, 11, 136, 14, 5, 22, 195, 169, 2, 5, 14, 13, 14, 139, 20, 195, 182, 18, 5, 11, 5, 4, 14, 5, 11, 13, 10, 135, 22, 195, 161, 12, 14, 1, 11, 13, 0, 16, 141, 5, 12, 13, 195, 169, 12, 5, 20, 5, 11, 2, 5, 14, 13, 12, 137, 12, 1, 16, 10, 195, 161, 2, 1, 14, 13, 12, 137, 19, 26, 15, 2, 195, 161, 2, 1, 14, 13, 12, 137, 20, 195, 169, 13, 195, 161, 2, 1, 14, 13, 14, 139, 9, 18, 195, 161, 14, 25, 195, 161, 22, 1, 12, 13, 0, 6, 195, 88, 149, 1, 13, 15, 140, 19, 26, 195, 182, 22, 5, 7, 195, 169, 22, 5, 12, 13, 13, 138, 21, 4, 22, 1, 18, 195, 161, 2, 1, 14, 13, 12, 201, 40, 83, 5, 57, 66, 197, 105, 65, 75, 13, 7, 132, 4, 195, 186, 12, 13, 0, 14, 139, 5, 7, 195, 169, 19, 26, 195, 169, 2, 5, 14, 13, 16, 141, 11, 9, 22, 195, 169, 20, 5, 12, 195, 169, 22, 5, 12, 13, 0, 26, 70, 56, 85, 133, 105, 65, 64, 50, 107, 82, 107, 87, 47, 107, 23, 106, 87, 47, 0, 13, 81, 97, 122, 116, 32, 17, 142, 11, 195, 173, 14, 195, 161, 12, 1, 20, 195, 161, 22, 1, 12, 13, 26, 70, 56, 85, 133, 105, 65, 64, 50, 107, 82, 107, 87, 47, 107, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 19, 144, 20, 195, 161, 18, 7, 25, 1, 12, 195, 161, 19, 15, 11, 2, 1, 14, 13, 10, 135, 20, 1, 14, 21, 12, 195, 179, 13, 9, 198, 56, 85, 133, 105, 65, 64, 13, 9, 198, 8, 194, 75, 45, 33, 64, 13, 10, 135, 13, 195, 169, 12, 20, 195, 179, 13, 9, 198, 80, 20, 148, 61, 69, 0, 13, 8, 133, 6, 195, 169, 14, 25, 13, 0, 18, 143, 8, 1, 19, 26, 14, 195, 161, 12, 1, 20, 195, 161, 22, 1, 12, 13, 15, 140, 2, 9, 26, 15, 14, 25, 195, 173, 20, 195, 169, 11, 13, 18, 143, 2, 5, 13, 21, 20, 1, 20, 195, 161, 19, 195, 161, 22, 1, 12, 13, 11, 136, 195, 169, 18, 20, 10, 195, 188, 11, 13, 6, 195, 12, 243, 20, 13, 0, 12, 201, 57, 146, 76, 5, 66, 207, 105, 64, 75, 13, 19, 144, 5, 12, 15, 19, 26, 12, 1, 20, 195, 161, 19, 195, 161, 22, 1, 12, 13, 19, 144, 1, 12, 11, 1, 12, 13, 1, 26, 195, 161, 19, 195, 161, 22, 1, 12, 13, 32, 67, 32, 85, 5, 105, 107, 47, 107, 23, 105, 106, 87, 50, 112, 55, 39, 63, 0, 13, 81, 104, 97, 115, 122, 110, 195, 161, 108, 111, 109, 32, 11, 136, 6, 18, 9, 19, 19, 195, 188, 12, 13, 17, 142, 5, 12, 12, 195, 161, 20, 195, 161, 19, 195, 161, 2, 1, 14, 13, 15, 140, 12, 195, 169, 16, 195, 169, 19, 11, 195, 169, 14, 20, 13, 0, 11, 2, 194, 167, 87, 6, 106, 49, 106, 87, 0, 9, 2, 195, 159, 21, 100, 101, 0, 10, 32, 69, 81, 81, 15, 81, 64, 47, 40, 70, 39, 47, 12, 23, 48, 37, 105, 107, 50, 12, 37, 0, 13, 81, 112, 105, 104, 101, 110, 110, 105, 32, 18, 143, 20, 5, 19, 26, 20, 5, 12, 195, 169, 19, 195, 169, 2, 5, 14, 13, 20, 145, 11, 15, 18, 12, 195, 161, 20, 15, 26, 195, 161, 19, 195, 161, 22, 1, 12, 13, 9, 198, 20, 195, 69, 57, 66, 75, 13, 9, 198, 80, 82, 201, 57, 66, 75, 13, 8, 197, 81, 81, 15, 81, 64, 13, 0, 22, 66, 76, 80, 89, 107, 23, 69, 110, 52, 39, 63, 0, 13, 81, 98, 195, 173, 114, 111, 109, 32, 21, 66, 76, 80, 89, 107, 23, 49, 106, 48, 50, 37, 0, 13, 81, 107, 97, 112, 110, 105, 32, 29, 66, 76, 80, 89, 107, 23, 111, 52, 47, 107, 47, 12, 111, 49, 0, 13, 81, 195, 169, 114, 116, 101, 116, 116, 195, 169, 107, 32, 24, 66, 76, 80, 89, 107, 10, 6, 15, 47, 52, 111, 81, 106, 0, 13, 81, 116, 114, 195, 169, 102, 97, 32, 27, 66, 76, 80, 89, 107, 23, 74, 37, 50, 112, 55, 39, 49, 0, 13, 81, 99, 115, 105, 110, 195, 161, 108, 111, 107, 32, 23, 66, 76, 80, 89, 107, 23, 82, 107, 47, 12, 107, 63, 0, 13, 81, 118, 101, 116, 116, 101, 109, 32, 12, 137, 11, 195, 182, 26, 195, 182, 20, 20, 9, 13, 5, 194, 56, 240, 72, 5, 194, 76, 80, 13, 0, 0, 9, 198, 20, 209, 76, 21, 65, 78, 13, 11, 200, 40, 21, 129, 76, 192, 84, 61, 64, 13, 11, 200, 32, 20, 207, 56, 192, 84, 61, 64, 13, 0, 8, 197, 88, 243, 20, 4, 176, 13, 0, 12, 137, 10, 195, 161, 20, 19, 26, 1, 14, 9, 13, 13, 138, 8, 9, 18, 4, 5, 20, 14, 195, 169, 4, 13, 10, 135, 11, 195, 169, 18, 14, 5, 11, 13, 0, 10, 135, 9, 4, 197, 145, 22, 5, 12, 13, 10, 199, 72, 81, 201, 77, 165, 5, 72, 13, 9, 134, 12, 195, 169, 20, 18, 5, 13, 0, 14, 2, 194, 174, 69, 107, 57, 107, 77, 86, 107, 47, 12, 0, 5, 130, 195, 166, 43, 35, 68, 32, 246, 142, 4, 105, 39, 86, 50, 106, 23, 63, 107, 79, 39, 55, 70, 112, 89, 47, 0, 13, 81, 109, 101, 103, 111, 108, 100, 195, 161, 115, 116, 32, 12, 137, 195, 169, 12, 22, 5, 26, 14, 5, 11, 13, 28, 4, 195, 169, 12, 20, 111, 55, 47, 6, 23, 89, 39, 49, 112, 37, 79, 0, 13, 81, 115, 111, 107, 195, 161, 105, 103, 32, 12, 137, 11, 5, 18, 195, 188, 12, 14, 5, 11, 13, 9, 134, 6, 195, 169, 12, 19, 26, 13, 7, 132, 195, 169, 12, 20, 13, 0, 5, 130, 195, 167, 43, 29, 7, 19, 26, 195, 179, 12, 19, 26, 87, 113, 55, 87, 23, 105, 39, 86, 86, 112, 0, 13, 81, 104, 111, 122, 122, 195, 161, 32, 8, 197, 32, 17, 217, 88, 16, 13, 9, 198, 32, 148, 218, 37, 65, 75, 13, 10, 135, 19, 26, 195, 179, 12, 19, 26, 13, 17, 3, 21, 46, 14, 114, 77, 50, 107, 82, 107, 86, 107, 47, 12, 0, 25, 17, 3, 195, 186, 14, 114, 77, 50, 107, 82, 107, 86, 107, 47, 12, 0, 25, 0, 15, 2, 194, 172, 55, 39, 79, 37, 49, 106, 37, 50, 107, 63, 0, 5, 130, 195, 164, 43, 9, 134, 195, 169, 20, 5, 12, 20, 13, 43, 8, 195, 186, 10, 15, 14, 14, 1, 14, 114, 57, 39, 50, 12, 106, 50, 23, 47, 107, 55, 107, 48, 110, 47, 107, 47, 12, 0, 13, 81, 116, 101, 108, 101, 112, 195, 173, 116, 101, 116, 116, 32, 9, 198, 80, 84, 150, 21, 162, 64, 13, 9, 198, 32, 19, 12, 41, 82, 192, 13, 10, 135, 2, 195, 186, 10, 14, 1, 11, 13, 10, 135, 22, 5, 20, 20, 195, 169, 11, 13, 15, 140, 8, 1, 20, 195, 179, 1, 14, 25, 1, 7, 195, 186, 13, 10, 135, 22, 9, 20, 20, 195, 169, 11, 13, 9, 198, 80, 21, 129, 77, 162, 64, 20, 0, 9, 135, 5, 7, 25, 195, 188, 20, 20, 24, 67, 48, 85, 20, 55, 107, 47, 12, 23, 82, 39, 55, 50, 106, 0, 13, 81, 118, 111, 108, 110, 97, 32, 22, 67, 48, 85, 20, 55, 107, 47, 12, 23, 79, 39, 50, 70, 0, 13, 81, 103, 111, 110, 100, 32, 6, 195, 48, 85, 20, 13, 0, 7, 196, 72, 149, 11, 4, 13, 14, 139, 195, 173, 20, 195, 169, 12, 20, 5, 20, 22, 5, 13, 24, 68, 56, 82, 197, 16, 50, 107, 49, 107, 70, 15, 49, 107, 55, 12, 0, 13, 81, 107, 101, 108, 108, 32, 36, 72, 77, 163, 198, 81, 97, 82, 20, 176, 87, 39, 81, 47, 82, 107, 52, 107, 49, 15, 106, 52, 112, 65, 106, 0, 13, 81, 97, 114, 195, 161, 110, 121, 97, 32, 10, 135, 19, 26, 195, 179, 12, 22, 1, 13, 7, 196, 56, 82, 197, 16, 13, 0, 28, 3, 195, 186, 10, 114, 57, 10, 6, 15, 106, 69, 55, 106, 49, 39, 47, 0, 13, 81, 97, 98, 108, 97, 107, 111, 116, 32, 31, 3, 195, 186, 10, 114, 57, 23, 63, 107, 79, 39, 55, 70, 112, 89, 47, 0, 13, 81, 109, 101, 103, 111, 108, 100, 195, 161, 115, 116, 32, 31, 69, 8, 150, 148, 61, 48, 69, 37, 87, 47, 39, 89, 23, 87, 107, 52, 37, 50, 47, 0, 13, 81, 115, 122, 101, 114, 105, 110, 116, 32, 21, 3, 195, 186, 10, 114, 57, 15, 106, 57, 47, 113, 0, 13, 81, 97, 106, 116, 195, 179, 32, 8, 197, 8, 150, 148, 61, 48, 13, 8, 133, 195, 173, 22, 5, 20, 13, 6, 131, 195, 186, 10, 13, 0, 15, 140, 16, 15, 12, 9, 20, 9, 11, 195, 161, 2, 1, 14, 13, 14, 139, 8, 9, 195, 161, 14, 25, 15, 26, 14, 1, 11, 13, 13, 138, 22, 5, 18, 26, 9, 195, 179, 22, 1, 12, 13, 12, 138, 22, 5, 18, 26, 9, 195, 179, 22, 1, 12, 16, 141, 9, 14, 20, 15, 14, 195, 161, 3, 9, 195, 179, 10, 1, 13, 9, 198, 80, 84, 150, 21, 161, 84, 13, 11, 136, 9, 14, 1, 11, 20, 195, 173, 22, 13, 15, 140, 12, 9, 19, 20, 195, 161, 10, 195, 161, 2, 1, 14, 13, 15, 140, 8, 5, 12, 25, 19, 26, 195, 173, 14, 195, 169, 14, 13, 16, 141, 19, 26, 5, 13, 12, 195, 169, 12, 20, 5, 20, 22, 5, 13, 11, 136, 20, 5, 19, 20, 22, 195, 169, 18, 13, 0, 18, 2, 194, 169, 117, 39, 48, 37, 52, 37, 79, 105, 47, 20, 57, 107, 55, 0, 10, 199, 13, 51, 205, 4, 113, 193, 48, 13, 0, 13, 2, 194, 182, 69, 107, 49, 107, 86, 70, 111, 89, 0, 11, 136, 16, 21, 19, 26, 20, 195, 173, 20, 13, 7, 196, 52, 17, 193, 52, 13, 7, 132, 4, 195, 188, 8, 13, 0, 13, 138, 18, 5, 13, 195, 169, 12, 10, 195, 188, 11, 13, 44, 8, 11, 15, 18, 195, 161, 2, 2, 9, 49, 39, 52, 112, 69, 12, 37, 23, 107, 55, 49, 111, 48, 86, 107, 55, 111, 89, 0, 13, 81, 101, 108, 107, 195, 169, 112, 122, 101, 108, 195, 169, 115, 32, 12, 137, 13, 195, 169, 18, 5, 20, 195, 169, 20, 13, 0, 17, 142, 195, 169, 20, 5, 12, 8, 15, 18, 4, 195, 179, 22, 1, 12, 13, 14, 139, 8, 1, 14, 7, 10, 5, 12, 26, 195, 169, 19, 13, 10, 135, 12, 195, 169, 16, 195, 169, 19, 13, 12, 137, 13, 195, 169, 18, 20, 195, 169, 11, 5, 13, 9, 198, 56, 85, 133, 104, 85, 20, 13, 10, 135, 11, 5, 12, 20, 195, 169, 19, 13, 5, 194, 60, 224, 13, 13, 66, 64, 192, 48, 111, 55, 70, 112, 40, 55, 0, 25, 0, 7, 2, 194, 181, 63, 115, 0, 6, 195, 4, 176, 68, 13, 9, 134, 6, 195, 169, 18, 6, 9, 13, 11, 136, 11, 195, 169, 18, 4, 195, 169, 19, 13, 0, 16, 141, 5, 12, 197, 145, 18, 5, 10, 5, 12, 26, 195, 169, 19, 13, 7, 196, 8, 195, 203, 44, 13, 14, 139, 13, 9, 14, 197, 145, 19, 195, 169, 7, 197, 177, 13, 9, 134, 6, 1, 12, 195, 161, 14, 13, 8, 133, 19, 26, 197, 177, 11, 13, 9, 196, 33, 49, 16, 4, 17, 42, 42, 0, 15, 140, 13, 5, 14, 14, 25, 9, 19, 195, 169, 7, 197, 177, 13, 30, 5, 11, 195, 161, 18, 20, 49, 112, 52, 47, 10, 6, 15, 39, 49, 39, 86, 50, 106, 0, 13, 81, 111, 107, 111, 122, 110, 97, 32, 16, 141, 20, 195, 182, 18, 20, 195, 169, 14, 5, 20, 195, 169, 20, 13, 8, 133, 5, 12, 197, 145, 12, 13, 10, 135, 12, 9, 19, 20, 195, 161, 14, 13, 9, 134, 1, 4, 10, 195, 161, 11, 13, 8, 133, 5, 12, 197, 145, 12, 13, 8, 133, 11, 195, 161, 18, 20, 13, 8, 133, 6, 195, 186, 10, 20, 13, 8, 133, 5, 12, 197, 145, 12, 13, 0, 8, 2, 194, 176, 81, 39, 49, 0, 11, 2, 194, 176, 81, 39, 49, 57, 107, 55, 0, 0, 14, 2, 194, 177, 48, 55, 40, 87, 63, 37, 50, 40, 87, 0, 5, 130, 195, 169, 14, 38, 70, 24, 244, 137, 57, 64, 129, 81, 39, 52, 37, 50, 47, 69, 106, 23, 49, 107, 52, 109, 55, 50, 107, 49, 0, 13, 81, 107, 101, 114, 195, 188, 108, 110, 101, 107, 32, 12, 137, 16, 1, 12, 5, 20, 20, 195, 161, 14, 13, 9, 134, 12, 195, 161, 20, 15, 13, 13, 11, 136, 13, 15, 14, 4, 10, 195, 161, 11, 13, 5, 130, 195, 169, 72, 0, 15, 2, 194, 190, 105, 112, 52, 39, 63, 50, 107, 77, 107, 70, 0, 12, 137, 22, 9, 20, 1, 20, 10, 195, 161, 11, 13, 9, 134, 3, 195, 169, 12, 195, 186, 13, 7, 132, 195, 182, 14, 20, 13, 0, 10, 2, 195, 183, 39, 87, 47, 112, 89, 0, 13, 138, 11, 9, 8, 1, 7, 25, 10, 195, 161, 11, 13, 12, 137, 19, 26, 195, 179, 12, 20, 195, 161, 12, 13, 13, 138, 20, 195, 161, 13, 1, 4, 10, 195, 161, 11, 13, 12, 137, 16, 21, 12, 195, 179, 22, 5, 18, 20, 13, 8, 133, 2, 195, 169, 18, 20, 13, 8, 197, 32, 149, 20, 20, 64, 13, 13, 138, 12, 195, 161, 20, 19, 26, 15, 20, 15, 11, 13, 0, 10, 2, 194, 188, 50, 107, 77, 107, 70, 0, 8, 133, 19, 26, 195, 161, 13, 13, 9, 134, 5, 2, 2, 197, 145, 12, 13, 0, 8, 2, 194, 189, 81, 111, 55, 0, 54, 71, 81, 83, 1, 40, 67, 206, 80, 47, 40, 55, 106, 57, 70, 39, 50, 47, 23, 82, 111, 70, 116, 23, 47, 108, 52, 82, 111, 65, 107, 49, 0, 13, 82, 118, 195, 169, 100, 197, 145, 32, 116, 195, 182, 114, 118, 195, 169, 110, 121, 101, 107, 32, 15, 140, 22, 9, 26, 19, 7, 195, 161, 12, 10, 195, 161, 11, 13, 15, 140, 1, 12, 11, 1, 12, 13, 1, 26, 26, 195, 161, 11, 13, 11, 136, 18, 195, 186, 7, 20, 195, 161, 11, 13, 11, 136, 13, 15, 14, 4, 20, 195, 161, 11, 13, 0, 46, 5, 195, 169, 22, 9, 7, 111, 82, 37, 79, 23, 55, 107, 87, 23, 47, 112, 63, 39, 79, 106, 47, 39, 47, 12, 0, 13, 82, 108, 101, 115, 122, 32, 116, 195, 161, 109, 111, 103, 97, 116, 111, 116, 116, 32, 13, 138, 12, 195, 169, 16, 8, 5, 19, 19, 5, 14, 13, 11, 136, 20, 5, 18, 22, 2, 197, 145, 12, 13, 8, 133, 19, 18, 195, 161, 3, 13, 14, 4, 95, 3, 5, 4, 117, 111, 70, 37, 55, 55, 107, 0, 19, 67, 88, 146, 73, 65, 39, 55, 117, 12, 106, 55, 0, 44, 42, 81, 97, 108, 32, 0, 13, 138, 7, 15, 14, 4, 15, 12, 20, 195, 161, 11, 13, 47, 69, 20, 208, 133, 73, 64, 107, 63, 69, 107, 52, 47, 23, 49, 37, 63, 107, 50, 107, 49, 110, 47, 107, 47, 12, 107, 49, 0, 13, 81, 107, 105, 109, 101, 110, 101, 107, 195, 173, 116, 101, 116, 116, 101, 107, 32, 37, 6, 22, 9, 12, 195, 161, 7, 82, 37, 55, 112, 79, 15, 70, 37, 74, 116, 89, 111, 79, 107, 0, 13, 81, 100, 105, 99, 115, 197, 145, 115, 195, 169, 103, 101, 32, 13, 138, 20, 195, 161, 13, 1, 4, 20, 195, 161, 11, 13, 8, 197, 80, 149, 11, 61, 64, 13, 13, 138, 20, 1, 18, 20, 15, 20, 20, 195, 161, 11, 13, 0, 9, 198, 32, 149, 129, 80, 19, 20, 13, 0, 5, 130, 195, 177, 43, 13, 138, 7, 15, 13, 2, 15, 12, 14, 195, 161, 13, 13, 14, 139, 18, 195, 169, 19, 26, 195, 169, 2, 197, 145, 12, 13, 42, 8, 1, 12, 1, 16, 21, 12, 195, 179, 106, 55, 106, 48, 40, 55, 113, 23, 47, 108, 52, 47, 111, 50, 107, 47, 107, 0, 13, 81, 116, 195, 182, 114, 116, 195, 169, 110, 101, 116, 101, 32, 13, 138, 20, 9, 19, 26, 20, 5, 12, 197, 145, 9, 13, 14, 203, 80, 20, 1, 77, 165, 1, 48, 21, 20, 4, 192, 13, 9, 198, 80, 84, 150, 21, 165, 133, 13, 8, 133, 19, 20, 195, 161, 2, 13, 15, 4, 95, 12, 9, 7, 55, 37, 79, 106, 47, 114, 52, 106, 0, 0, 34, 8, 10, 5, 12, 26, 195, 169, 19, 20, 57, 107, 55, 86, 111, 89, 47, 10, 6, 15, 106, 70, 50, 106, 49, 0, 13, 81, 97, 100, 110, 97, 107, 32, 9, 134, 26, 195, 161, 16, 15, 18, 13, 10, 135, 195, 161, 12, 12, 14, 9, 1, 13, 0, 11, 136, 4, 195, 182, 14, 20, 5, 14, 9, 13, 9, 134, 19, 1, 10, 20, 195, 179, 13, 8, 133, 19, 26, 195, 161, 4, 13, 6, 195, 88, 19, 0, 13, 0, 40, 15, 195, 161, 12, 12, 1, 16, 195, 173, 20, 15, 20, 20, 195, 161, 11, 112, 55, 12, 106, 48, 110, 47, 39, 47, 12, 112, 49, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 9, 198, 64, 20, 129, 77, 165, 0, 13, 9, 198, 44, 83, 20, 21, 69, 0, 13, 9, 134, 20, 195, 169, 7, 5, 4, 13, 5, 194, 80, 80, 13, 0, 21, 5, 195, 169, 22, 5, 14, 111, 82, 107, 50, 23, 112, 47, 0, 13, 81, 195, 161, 116, 32, 13, 138, 5, 12, 4, 195, 182, 14, 20, 5, 14, 9, 13, 15, 140, 11, 9, 22, 5, 20, 14, 9, 22, 1, 12, 195, 179, 13, 18, 67, 88, 146, 64, 105, 111, 47, 12, 107, 55, 0, 44, 42, 81, 101, 108, 32, 0, 10, 135, 11, 195, 182, 20, 14, 9, 5, 13, 11, 200, 52, 147, 137, 77, 165, 5, 73, 64, 13, 0, 8, 197, 88, 243, 20, 4, 208, 72, 8, 197, 64, 84, 131, 72, 80, 22, 28, 67, 4, 176, 82, 106, 49, 106, 52, 23, 82, 106, 55, 106, 63, 37, 47, 0, 13, 81, 118, 97, 108, 97, 109, 105, 116, 32, 20, 145, 2, 5, 18, 5, 14, 4, 5, 26, 11, 5, 4, 195, 169, 19, 19, 5, 12, 13, 28, 69, 32, 18, 148, 40, 16, 105, 106, 57, 78, 106, 23, 82, 111, 79, 52, 107, 0, 13, 81, 118, 195, 169, 103, 114, 101, 32, 36, 13, 18, 5, 14, 4, 5, 12, 11, 5, 26, 195, 169, 19, 20, 51, 107, 50, 70, 107, 55, 49, 107, 86, 111, 89, 47, 23, 37, 89, 0, 13, 81, 105, 115, 32, 34, 67, 4, 176, 82, 106, 49, 106, 52, 10, 6, 15, 106, 6, 15, 77, 112, 52, 47, 113, 0, 13, 82, 97, 32, 103, 121, 195, 161, 114, 116, 195, 179, 32, 43, 69, 88, 243, 148, 4, 176, 82, 39, 50, 47, 106, 49, 23, 81, 107, 55, 107, 55, 116, 89, 111, 79, 51, 107, 0, 13, 81, 102, 101, 108, 101, 108, 197, 145, 115, 115, 195, 169, 103, 114, 101, 32, 29, 67, 4, 176, 82, 106, 6, 49, 106, 52, 23, 63, 106, 52, 106, 70, 50, 37, 0, 13, 81, 109, 97, 114, 97, 100, 110, 105, 32, 8, 197, 88, 243, 20, 4, 208, 13, 8, 197, 32, 20, 131, 60, 176, 13, 12, 201, 88, 148, 197, 48, 177, 68, 21, 69, 0, 13, 10, 135, 3, 5, 12, 12, 195, 161, 14, 13, 7, 132, 195, 169, 22, 1, 13, 8, 197, 40, 83, 26, 20, 208, 13, 6, 195, 4, 176, 82, 13, 8, 133, 12, 197, 145, 20, 20, 13, 0, 5, 130, 195, 184, 43, 16, 141, 11, 195, 182, 26, 12, 5, 11, 5, 4, 20, 5, 20, 9, 13, 21, 146, 2, 5, 195, 161, 12, 12, 195, 173, 20, 195, 161, 19, 15, 11, 14, 195, 161, 12, 13, 11, 136, 15, 12, 3, 19, 195, 179, 2, 2, 13, 9, 198, 52, 17, 213, 56, 176, 84, 13, 0, 30, 71, 52, 147, 137, 77, 165, 5, 72, 63, 37, 50, 37, 87, 47, 107, 52, 15, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 9, 134, 19, 26, 195, 179, 2, 1, 13, 14, 139, 20, 1, 18, 20, 8, 1, 20, 14, 195, 161, 4, 13, 10, 199, 65, 35, 199, 72, 19, 66, 4, 13, 10, 199, 52, 147, 137, 77, 165, 5, 72, 13, 0, 41, 68, 52, 17, 193, 76, 63, 106, 79, 106, 89, 23, 105, 116, 63, 111, 52, 89, 111, 49, 55, 107, 47, 0, 13, 81, 104, 197, 145, 109, 195, 169, 114, 115, 195, 169, 107, 108, 101, 116, 32, 12, 137, 20, 5, 8, 5, 20, 14, 195, 169, 11, 13, 7, 196, 52, 17, 193, 76, 13, 7, 196, 24, 241, 214, 4, 13, 7, 196, 32, 246, 142, 36, 13, 7, 196, 32, 246, 142, 36, 13, 0, 13, 138, 11, 9, 19, 6, 9, 195, 186, 14, 1, 11, 13, 32, 69, 81, 81, 20, 4, 176, 47, 40, 47, 12, 106, 49, 23, 63, 39, 50, 70, 106, 50, 37, 0, 13, 81, 109, 111, 110, 100, 97, 110, 105, 32, 7, 132, 195, 169, 22, 5, 13, 8, 133, 19, 195, 188, 12, 20, 13, 9, 134, 18, 195, 179, 12, 21, 11, 13, 8, 133, 6, 195, 169, 12, 20, 13, 0, 12, 137, 16, 5, 18, 5, 13, 195, 169, 18, 5, 13, 15, 140, 13, 195, 169, 12, 25, 19, 195, 169, 7, 2, 5, 14, 13, 14, 139, 22, 195, 161, 12, 12, 1, 12, 14, 9, 21, 11, 13, 8, 133, 2, 195, 169, 18, 5, 13, 11, 136, 19, 26, 195, 179, 12, 10, 15, 14, 13, 14, 139, 6, 18, 9, 19, 19, 195, 188, 12, 14, 5, 11, 13, 11, 136, 11, 15, 18, 195, 161, 2, 1, 14, 13, 9, 134, 19, 26, 195, 179, 12, 20, 13, 18, 4, 195, 186, 46, 14, 114, 77, 50, 107, 82, 107, 86, 107, 47, 12, 0, 25, 0, 6, 195, 81, 81, 0, 13, 13, 138, 16, 195, 169, 12, 4, 195, 161, 26, 26, 1, 13, 14, 139, 22, 195, 169, 20, 5, 12, 195, 169, 22, 5, 12, 13, 50, 9, 11, 195, 182, 18, 195, 169, 2, 5, 14, 49, 108, 52, 111, 69, 107, 50, 23, 48, 52, 113, 69, 112, 55, 50, 112, 49, 23, 49, 37, 0, 13, 82, 112, 114, 195, 179, 98, 195, 161, 108, 110, 195, 161, 107, 32, 107, 105, 32, 34, 67, 80, 85, 20, 47, 107, 47, 12, 23, 106, 86, 10, 6, 15, 109, 77, 69, 107, 50, 0, 13, 82, 97, 122, 32, 195, 188, 103, 121, 98, 101, 110, 32, 45, 9, 11, 195, 182, 18, 195, 169, 2, 5, 14, 49, 108, 52, 111, 69, 107, 50, 23, 37, 89, 23, 82, 37, 47, 106, 47, 39, 47, 12, 0, 13, 82, 105, 115, 32, 118, 105, 116, 97, 116, 111, 116, 116, 32, 12, 137, 11, 195, 182, 18, 195, 186, 20, 15, 14, 13, 34, 71, 48, 81, 129, 29, 147, 212, 80, 55, 107, 81, 106, 77, 39, 47, 12, 23, 63, 37, 50, 70, 107, 50, 0, 13, 81, 109, 105, 110, 100, 101, 110, 32, 9, 198, 4, 64, 75, 61, 163, 137, 13, 14, 139, 195, 182, 14, 13, 1, 7, 195, 161, 22, 1, 12, 13, 9, 134, 2, 195, 173, 18, 10, 1, 13, 6, 195, 81, 81, 0, 13, 6, 195, 80, 85, 20, 13, 11, 67, 72, 19, 64, 52, 106, 63, 0, 42, 42, 0, 12, 137, 22, 195, 161, 4, 15, 12, 14, 1, 11, 13, 44, 9, 7, 25, 197, 145, 26, 20, 195, 169, 11, 77, 116, 86, 47, 111, 49, 23, 81, 107, 55, 70, 39, 55, 79, 39, 86, 50, 37, 0, 13, 81, 102, 101, 108, 100, 111, 108, 103, 111, 122, 110, 105, 32, 10, 135, 22, 5, 26, 195, 169, 18, 5, 13, 7, 196, 24, 241, 193, 80, 13, 11, 200, 80, 243, 1, 44, 241, 20, 4, 176, 13, 7, 196, 24, 18, 193, 16, 13, 0, 11, 136, 19, 26, 5, 13, 195, 169, 18, 5, 13, 0, 54, 9, 5, 12, 12, 5, 14, 195, 169, 18, 5, 107, 55, 12, 107, 50, 111, 52, 107, 23, 37, 89, 23, 69, 37, 87, 47, 39, 89, 110, 47, 106, 50, 112, 0, 13, 82, 105, 115, 32, 98, 105, 122, 116, 111, 115, 195, 173, 116, 97, 110, 195, 161, 32, 12, 137, 9, 11, 15, 14, 10, 195, 161, 18, 1, 13, 12, 137, 13, 195, 179, 4, 10, 195, 161, 18, 1, 13, 0, 10, 199, 13, 48, 80, 60, 194, 1, 80, 13, 15, 140, 195, 188, 26, 5, 13, 5, 12, 20, 5, 20, 9, 11, 13, 10, 199, 20, 195, 153, 21, 35, 137, 20, 13, 10, 199, 80, 84, 218, 80, 82, 197, 80, 13, 6, 195, 88, 149, 20, 13, 11, 136, 13, 195, 161, 18, 3, 9, 21, 19, 20, 0, 31, 5, 195, 169, 22, 5, 19, 111, 82, 107, 89, 23, 49, 37, 89, 81, 37, 114, 47, 0, 13, 81, 107, 105, 115, 102, 105, 195, 186, 116, 32, 29, 5, 195, 169, 22, 5, 19, 111, 82, 107, 89, 23, 49, 37, 89, 81, 37, 114, 0, 13, 81, 107, 105, 115, 102, 105, 195, 186, 32, 17, 142, 11, 195, 182, 26, 16, 15, 14, 20, 10, 195, 161, 2, 1, 14, 13, 36, 5, 195, 169, 22, 5, 19, 111, 82, 107, 89, 23, 47, 112, 63, 39, 79, 106, 47, 112, 89, 0, 13, 81, 116, 195, 161, 109, 111, 103, 97, 116, 195, 161, 115, 32, 19, 144, 20, 5, 12, 5, 16, 195, 173, 20, 195, 169, 19, 195, 169, 22, 5, 12, 13, 32, 5, 195, 169, 22, 5, 19, 111, 82, 107, 89, 15, 49, 39, 52, 112, 69, 113, 55, 0, 13, 81, 107, 111, 114, 195, 161, 98, 195, 179, 108, 32, 31, 5, 195, 169, 22, 5, 19, 111, 82, 107, 89, 15, 77, 107, 52, 107, 49, 107, 47, 0, 13, 81, 103, 121, 101, 114, 101, 107, 101, 116, 32, 9, 198, 64, 243, 148, 40, 18, 78, 13, 8, 133, 9, 4, 197, 145, 19, 13, 8, 133, 195, 169, 22, 5, 19, 13, 7, 196, 56, 82, 197, 52, 13, 0, 12, 137, 8, 1, 4, 10, 195, 161, 18, 1, 20, 13, 37, 10, 6, 5, 12, 5, 20, 20, 195, 188, 14, 11, 81, 107, 55, 107, 47, 12, 109, 50, 49, 23, 106, 86, 23, 111, 79, 0, 13, 82, 97, 122, 32, 195, 169, 103, 32, 15, 140, 12, 5, 22, 5, 7, 197, 145, 10, 195, 169, 18, 5, 13, 0, 56, 11, 19, 26, 195, 188, 11, 19, 195, 169, 7, 5, 19, 87, 109, 49, 89, 111, 79, 107, 89, 23, 37, 50, 47, 111, 87, 49, 107, 70, 111, 89, 107, 49, 107, 47, 0, 13, 81, 105, 110, 116, 195, 169, 122, 107, 101, 100, 195, 169, 115, 101, 107, 101, 116, 32, 46, 9, 20, 195, 182, 18, 22, 195, 169, 14, 25, 47, 108, 52, 82, 111, 65, 10, 10, 47, 107, 52, 82, 107, 86, 107, 47, 111, 69, 107, 0, 13, 81, 116, 101, 114, 118, 101, 122, 101, 116, 195, 169, 98, 101, 32, 53, 9, 20, 195, 182, 18, 22, 195, 169, 14, 25, 47, 108, 52, 82, 111, 65, 23, 49, 39, 50, 117, 107, 48, 117, 37, 113, 57, 112, 52, 113, 55, 0, 13, 81, 107, 111, 110, 99, 101, 112, 99, 105, 195, 179, 106, 195, 161, 114, 195, 179, 108, 32, 12, 137, 11, 195, 169, 16, 26, 5, 12, 14, 9, 13, 14, 139, 12, 5, 8, 5, 20, 19, 195, 169, 7, 5, 19, 13, 12, 137, 20, 195, 182, 18, 22, 195, 169, 14, 25, 13, 9, 198, 77, 161, 82, 104, 85, 20, 13, 9, 134, 19, 195, 186, 12, 25, 20, 13, 0, 17, 142, 6, 9, 14, 1, 14, 19, 26, 195, 173, 18, 15, 26, 26, 1, 13, 10, 199, 52, 81, 198, 36, 118, 69, 48, 13, 27, 5, 21, 20, 195, 161, 14, 40, 47, 112, 50, 23, 50, 111, 86, 50, 37, 0, 13, 81, 110, 195, 169, 122, 110, 105, 32, 9, 134, 12, 195, 161, 20, 14, 9, 13, 9, 133, 21, 20, 195, 161, 14, 13, 22, 9, 134, 14, 25, 195, 161, 18, 9, 20, 0, 35, 67, 5, 36, 129, 106, 52, 52, 106, 10, 6, 15, 47, 108, 52, 107, 49, 107, 70, 50, 37, 0, 13, 81, 116, 195, 182, 114, 101, 107, 101, 100, 110, 105, 32, 30, 67, 5, 36, 129, 106, 52, 52, 106, 10, 6, 15, 49, 111, 52, 57, 109, 49, 0, 13, 81, 107, 195, 169, 114, 106, 195, 188, 107, 32, 36, 7, 19, 26, 9, 14, 20, 197, 177, 87, 37, 50, 47, 115, 23, 81, 107, 55, 105, 116, 86, 107, 47, 0, 13, 81, 102, 101, 108, 104, 197, 145, 122, 101, 116, 32, 30, 67, 5, 36, 129, 106, 52, 52, 106, 23, 57, 40, 47, 39, 47, 12, 106, 63, 0, 13, 81, 106, 117, 116, 111, 116, 116, 97, 109, 32, 37, 67, 5, 36, 129, 106, 52, 52, 106, 23, 82, 39, 50, 106, 47, 49, 39, 86, 113, 106, 50, 0, 13, 81, 118, 111, 110, 97, 116, 107, 111, 122, 195, 179, 97, 110, 32, 18, 67, 5, 36, 129, 106, 52, 52, 106, 23, 37, 89, 0, 13, 81, 105, 115, 32, 45, 67, 5, 36, 129, 106, 52, 52, 106, 23, 49, 107, 55, 12, 23, 39, 70, 106, 81, 37, 77, 107, 55, 50, 37, 0, 13, 82, 107, 101, 108, 108, 32, 111, 100, 97, 102, 105, 103, 121, 101, 108, 110, 105, 32, 7, 196, 80, 18, 193, 72, 13, 16, 141, 4, 195, 182, 14, 20, 195, 182, 20, 20, 195, 188, 14, 11, 13, 14, 139, 2, 5, 19, 26, 5, 18, 26, 195, 169, 19, 5, 13, 11, 136, 19, 5, 7, 195, 169, 12, 25, 20, 13, 6, 195, 21, 36, 133, 13, 6, 195, 5, 36, 129, 13, 0, 8, 197, 32, 20, 131, 60, 192, 13, 11, 136, 5, 12, 10, 195, 161, 18, 14, 9, 13, 9, 134, 195, 169, 18, 26, 9, 11, 13, 9, 134, 3, 195, 169, 7, 5, 11, 13, 8, 133, 10, 195, 161, 18, 20, 13, 0, 13, 138, 7, 25, 1, 14, 195, 186, 10, 195, 161, 20, 13, 46, 4, 195, 169, 18, 22, 111, 52, 82, 23, 106, 6, 15, 55, 37, 50, 40, 49, 87, 23, 63, 107, 55, 12, 107, 47, 12, 0, 13, 83, 97, 32, 108, 105, 110, 117, 120, 32, 109, 101, 108, 108, 101, 116, 116, 32, 26, 6, 1, 26, 195, 169, 18, 20, 106, 86, 111, 52, 47, 15, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 14, 139, 20, 5, 19, 26, 20, 5, 12, 195, 188, 14, 11, 13, 7, 132, 195, 169, 18, 22, 13, 14, 139, 6, 5, 10, 12, 5, 19, 26, 20, 195, 169, 19, 13, 20, 145, 13, 5, 7, 2, 195, 188, 14, 20, 5, 20, 195, 169, 19, 195, 169, 18, 5, 13, 9, 134, 1, 26, 195, 169, 18, 20, 13, 0, 56, 11, 11, 195, 182, 12, 20, 19, 195, 169, 7, 5, 20, 49, 108, 55, 74, 111, 79, 107, 47, 23, 57, 107, 55, 107, 50, 47, 23, 87, 112, 63, 40, 49, 52, 106, 0, 13, 82, 106, 101, 108, 101, 110, 116, 32, 115, 122, 195, 161, 109, 117, 107, 114, 97, 32, 14, 139, 18, 195, 169, 19, 26, 12, 5, 20, 5, 9, 20, 13, 10, 199, 65, 35, 199, 72, 19, 79, 44, 13, 21, 146, 13, 5, 7, 19, 26, 195, 188, 14, 20, 5, 20, 195, 169, 19, 195, 169, 18, 5, 13, 0, 7, 196, 4, 176, 82, 80, 13, 15, 140, 22, 195, 161, 12, 20, 15, 26, 1, 20, 1, 9, 20, 13, 7, 196, 52, 245, 15, 72, 13, 7, 196, 32, 246, 148, 4, 13, 7, 132, 195, 169, 18, 20, 13, 7, 196, 56, 82, 201, 44, 13, 0, 10, 135, 9, 7, 1, 26, 195, 161, 14, 13, 13, 138, 7, 15, 14, 4, 15, 12, 10, 195, 161, 11, 13, 13, 138, 20, 1, 7, 12, 1, 12, 10, 195, 161, 11, 13, 10, 135, 14, 25, 1, 18, 195, 161, 14, 20, 0, 13, 138, 3, 195, 173, 13, 195, 169, 20, 197, 145, 12, 13, 13, 138, 6, 15, 18, 9, 14, 20, 195, 169, 18, 20, 13, 43, 10, 6, 15, 18, 9, 14, 20, 195, 169, 18, 20, 81, 39, 52, 37, 50, 47, 111, 52, 47, 23, 107, 55, 82, 37, 105, 107, 47, 116, 0, 13, 81, 101, 108, 118, 105, 104, 101, 116, 197, 145, 32, 10, 135, 19, 26, 197, 177, 18, 9, 11, 13, 30, 6, 5, 26, 195, 169, 18, 20, 107, 86, 111, 52, 47, 15, 82, 106, 50, 15, 106, 86, 0, 13, 82, 118, 97, 110, 32, 97, 122, 32, 17, 142, 195, 188, 7, 25, 14, 195, 182, 11, 19, 195, 169, 7, 5, 20, 13, 0, 45, 15, 20, 5, 22, 195, 169, 11, 5, 14, 25, 19, 195, 169, 7, 5, 20, 47, 107, 82, 111, 49, 107, 65, 89, 111, 79, 107, 47, 23, 82, 111, 79, 107, 86, 0, 13, 81, 118, 195, 169, 103, 101, 122, 32, 9, 134, 2, 195, 161, 18, 11, 9, 13, 0, 39, 5, 22, 1, 12, 195, 179, 82, 106, 55, 113, 23, 47, 52, 109, 49, 12, 108, 86, 111, 89, 47, 0, 13, 81, 116, 114, 195, 188, 107, 107, 195, 182, 122, 195, 169, 115, 116, 32, 11, 136, 8, 1, 19, 26, 14, 195, 161, 12, 13, 8, 133, 22, 1, 12, 195, 179, 13, 6, 195, 21, 53, 5, 22, 0, 13, 138, 1, 12, 1, 16, 15, 26, 20, 195, 161, 11, 13, 17, 142, 19, 26, 195, 182, 22, 5, 20, 20, 19, 195, 169, 7, 5, 11, 13, 13, 138, 11, 195, 182, 20, 8, 5, 20, 197, 145, 11, 13, 8, 133, 13, 195, 161, 19, 20, 13, 17, 9, 95, 35, 45, 195, 161, 14, 195, 161, 12, 112, 50, 112, 55, 0, 21, 0, 13, 138, 5, 7, 25, 13, 195, 161, 19, 19, 1, 12, 13, 0, 14, 139, 18, 195, 169, 19, 26, 195, 169, 18, 197, 145, 12, 13, 0, 10, 135, 12, 195, 169, 16, 14, 9, 5, 13, 10, 135, 1, 18, 195, 161, 14, 25, 1, 13, 16, 67, 44, 98, 201, 49, 112, 107, 81, 49, 112, 37, 0, 17, 42, 42, 0, 42, 6, 15, 16, 3, 9, 195, 179, 39, 48, 117, 37, 113, 23, 69, 107, 49, 106, 48, 74, 39, 55, 112, 89, 106, 0, 13, 81, 98, 101, 107, 97, 112, 99, 115, 111, 108, 195, 161, 115, 97, 32, 24, 6, 15, 16, 3, 9, 195, 179, 39, 48, 117, 37, 113, 15, 50, 107, 63, 0, 13, 81, 110, 101, 109, 32, 0, 36, 10, 5, 12, 14, 195, 169, 26, 195, 169, 19, 20, 107, 55, 50, 111, 86, 111, 89, 47, 23, 49, 111, 52, 107, 49, 0, 13, 81, 107, 195, 169, 114, 101, 107, 32, 10, 135, 14, 5, 11, 195, 188, 14, 11, 13, 11, 5, 95, 49, 77, 49, 5, 107, 86, 52, 0, 0, 14, 139, 8, 195, 161, 12, 195, 179, 26, 1, 20, 15, 20, 13, 0, 29, 68, 4, 192, 84, 80, 106, 55, 106, 47, 12, 23, 49, 111, 87, 109, 55, 0, 13, 81, 107, 195, 169, 115, 122, 195, 188, 108, 32, 34, 68, 4, 192, 84, 80, 106, 55, 106, 47, 12, 15, 70, 39, 55, 79, 39, 87, 47, 106, 49, 0, 13, 81, 100, 111, 108, 103, 111, 122, 116, 97, 107, 32, 10, 135, 11, 195, 169, 18, 14, 9, 5, 13, 19, 144, 8, 1, 19, 26, 14, 195, 161, 12, 1, 20, 195, 161, 195, 169, 18, 20, 13, 7, 196, 88, 85, 20, 20, 13, 7, 196, 80, 85, 20, 20, 13, 7, 196, 4, 192, 84, 80, 13, 0, 11, 136, 15, 4, 1, 195, 173, 18, 14, 9, 13, 10, 135, 8, 195, 161, 20, 195, 161, 14, 13, 13, 138, 16, 1, 18, 20, 195, 173, 3, 9, 195, 179, 13, 0, 21, 146, 13, 5, 7, 9, 14, 4, 195, 173, 20, 195, 161, 19, 195, 161, 195, 169, 18, 20, 13, 12, 137, 11, 195, 182, 22, 5, 20, 14, 9, 5, 13, 13, 138, 20, 1, 12, 195, 161, 12, 14, 195, 161, 4, 13, 9, 198, 24, 81, 5, 104, 85, 0, 13, 13, 138, 5, 12, 20, 195, 169, 18, 195, 169, 19, 20, 13, 11, 136, 12, 195, 161, 20, 20, 195, 161, 14, 13, 7, 132, 20, 197, 177, 26, 13, 10, 135, 11, 1, 16, 10, 195, 161, 11, 13, 0, 43, 6, 9, 4, 197, 145, 18, 5, 37, 70, 116, 52, 107, 23, 87, 112, 63, 110, 47, 105, 106, 47, 40, 50, 49, 0, 13, 81, 115, 122, 195, 161, 109, 195, 173, 116, 104, 97, 116, 117, 110, 107, 32, 42, 6, 9, 4, 197, 145, 18, 5, 37, 70, 116, 52, 107, 23, 82, 106, 50, 23, 49, 37, 55, 112, 47, 112, 89, 0, 13, 82, 118, 97, 110, 32, 107, 105, 108, 195, 161, 116, 195, 161, 115, 32, 9, 198, 25, 85, 20, 5, 67, 137, 13, 9, 198, 25, 85, 20, 5, 66, 129, 13, 0, 10, 135, 11, 9, 22, 195, 169, 22, 5, 13, 44, 6, 195, 179, 18, 195, 161, 14, 113, 52, 112, 50, 10, 6, 15, 69, 107, 55, 109, 55, 10, 6, 15, 63, 106, 52, 106, 70, 0, 13, 82, 98, 101, 108, 195, 188, 108, 32, 109, 97, 114, 97, 100, 32, 11, 200, 40, 83, 5, 57, 65, 84, 80, 80, 13, 7, 132, 195, 182, 12, 20, 13, 8, 133, 13, 195, 161, 18, 3, 20, 15, 5, 95, 49, 77, 49, 15, 107, 86, 52, 107, 70, 37, 49, 0, 0, 8, 197, 21, 54, 142, 20, 176, 13, 32, 6, 195, 169, 12, 197, 145, 11, 111, 55, 116, 49, 23, 105, 107, 57, 86, 107, 47, 107, 0, 13, 81, 104, 101, 108, 121, 122, 101, 116, 101, 32, 10, 135, 12, 195, 161, 2, 195, 161, 14, 13, 24, 69, 81, 81, 20, 4, 208, 47, 40, 47, 12, 106, 63, 23, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 8, 197, 72, 80, 211, 20, 112, 13, 8, 197, 32, 17, 217, 80, 16, 13, 11, 136, 22, 9, 12, 195, 161, 7, 2, 1, 13, 17, 9, 95, 35, 45, 195, 169, 20, 197, 145, 12, 111, 47, 116, 55, 0, 21, 0, 9, 198, 88, 17, 217, 84, 226, 192, 13, 9, 198, 64, 144, 67, 60, 176, 84, 13, 9, 198, 88, 17, 217, 84, 226, 192, 13, 12, 137, 19, 26, 195, 161, 13, 15, 13, 18, 1, 13, 17, 142, 195, 188, 12, 4, 195, 182, 7, 195, 169, 12, 195, 169, 19, 20, 13, 14, 139, 195, 161, 12, 12, 195, 173, 20, 10, 195, 161, 11, 13, 0, 7, 2, 95, 1, 106, 12, 0, 9, 134, 22, 9, 20, 195, 161, 9, 13, 10, 199, 52, 81, 207, 48, 64, 78, 36, 13, 19, 144, 8, 195, 161, 20, 20, 195, 169, 18, 20, 195, 161, 18, 15, 12, 195, 179, 13, 9, 134, 2, 195, 173, 18, 14, 1, 13, 11, 136, 12, 195, 161, 20, 20, 195, 161, 11, 13, 11, 136, 18, 195, 179, 12, 1, 20, 15, 11, 13, 9, 134, 12, 195, 161, 20, 10, 1, 13, 0, 9, 134, 19, 15, 6, 197, 145, 18, 13, 7, 196, 76, 242, 193, 80, 13, 16, 141, 13, 1, 7, 25, 1, 18, 195, 161, 26, 26, 195, 161, 11, 13, 11, 200, 20, 208, 133, 72, 82, 206, 20, 176, 13, 8, 133, 5, 18, 197, 145, 19, 13, 0, 32, 9, 5, 13, 12, 195, 173, 20, 5, 20, 20, 107, 63, 55, 110, 47, 107, 47, 12, 23, 106, 52, 52, 106, 0, 13, 81, 97, 114, 114, 97, 32, 13, 138, 5, 12, 13, 15, 14, 4, 20, 195, 161, 11, 13, 37, 9, 5, 13, 12, 195, 173, 20, 5, 20, 20, 107, 63, 55, 110, 47, 107, 47, 12, 23, 117, 37, 49, 69, 107, 50, 0, 13, 81, 99, 105, 107, 107, 98, 101, 110, 32, 41, 9, 5, 13, 12, 195, 173, 20, 5, 20, 20, 107, 63, 55, 110, 47, 107, 47, 12, 23, 87, 107, 52, 82, 107, 86, 107, 47, 0, 13, 81, 115, 122, 101, 114, 118, 101, 122, 101, 116, 32, 11, 136, 12, 1, 11, 195, 161, 19, 2, 1, 13, 9, 134, 195, 179, 18, 195, 161, 19, 13, 0, 9, 198, 77, 163, 203, 80, 19, 64, 13, 17, 142, 6, 5, 12, 5, 19, 195, 169, 7, 195, 169, 20, 197, 145, 12, 13, 9, 134, 22, 9, 20, 195, 161, 20, 13, 14, 139, 10, 1, 22, 1, 19, 15, 12, 20, 195, 161, 11, 13, 0, 6, 2, 95, 5, 107, 0, 17, 142, 13, 5, 7, 13, 5, 14, 20, 195, 169, 19, 195, 169, 18, 5, 13, 28, 71, 8, 150, 143, 56, 230, 65, 48, 69, 37, 86, 39, 65, 65, 106, 55, 10, 6, 15, 106, 86, 0, 13, 81, 97, 122, 32, 10, 199, 16, 243, 7, 60, 178, 193, 48, 13, 10, 199, 20, 208, 133, 72, 82, 197, 80, 13, 0, 33, 9, 5, 12, 10, 195, 161, 18, 195, 161, 19, 107, 55, 57, 112, 52, 112, 89, 23, 37, 50, 70, 40, 55, 0, 13, 81, 105, 110, 100, 117, 108, 32, 16, 141, 19, 26, 195, 188, 11, 19, 195, 169, 7, 5, 19, 5, 11, 13, 12, 137, 5, 12, 10, 195, 161, 18, 195, 161, 19, 13, 18, 143, 6, 5, 10, 12, 5, 19, 26, 20, 195, 169, 19, 195, 169, 18, 5, 13, 0, 16, 141, 11, 195, 188, 12, 6, 195, 182, 12, 4, 18, 197, 145, 12, 13, 11, 136, 5, 13, 5, 12, 195, 169, 19, 5, 13, 17, 142, 18, 5, 14, 4, 5, 12, 11, 5, 26, 195, 169, 19, 5, 11, 13, 0, 47, 14, 19, 26, 15, 6, 20, 22, 5, 18, 5, 11, 18, 197, 145, 12, 87, 39, 81, 47, 82, 107, 52, 107, 49, 52, 116, 55, 23, 82, 106, 50, 23, 87, 113, 0, 13, 82, 118, 97, 110, 32, 115, 122, 195, 179, 32, 9, 134, 3, 195, 169, 7, 5, 20, 13, 28, 10, 20, 195, 182, 18, 22, 195, 169, 14, 25, 20, 47, 108, 52, 82, 111, 65, 47, 23, 37, 89, 0, 13, 81, 105, 115, 32, 13, 138, 20, 195, 182, 18, 22, 195, 169, 14, 25, 20, 13, 9, 198, 52, 243, 132, 40, 19, 64, 13, 14, 139, 195, 169, 19, 26, 10, 195, 161, 18, 195, 161, 19, 13, 46, 15, 19, 26, 195, 179, 11, 1, 16, 3, 19, 15, 12, 1, 20, 15, 11, 87, 113, 49, 106, 48, 74, 39, 55, 106, 47, 39, 49, 23, 82, 106, 50, 12, 106, 49, 0, 13, 81, 118, 97, 110, 110, 97, 107, 32, 56, 11, 9, 4, 197, 145, 10, 195, 161, 18, 195, 161, 19, 37, 70, 116, 57, 112, 52, 112, 89, 23, 55, 107, 87, 23, 106, 23, 57, 107, 55, 12, 107, 63, 86, 116, 0, 13, 83, 108, 101, 115, 122, 32, 97, 32, 106, 101, 108, 108, 101, 109, 122, 197, 145, 32, 10, 135, 18, 1, 2, 12, 195, 161, 19, 13, 13, 202, 64, 148, 218, 80, 243, 25, 60, 178, 193, 48, 13, 9, 134, 195, 179, 18, 195, 161, 20, 13, 16, 141, 6, 15, 18, 4, 21, 12, 1, 20, 19, 26, 195, 161, 13, 13, 0, 14, 139, 6, 15, 12, 25, 1, 13, 1, 20, 195, 161, 20, 13, 13, 138, 10, 5, 12, 5, 14, 20, 195, 169, 19, 5, 13, 25, 7, 19, 26, 1, 22, 195, 161, 20, 87, 106, 82, 112, 47, 23, 89, 107, 63, 0, 13, 81, 115, 101, 109, 32, 13, 138, 13, 5, 7, 7, 25, 197, 145, 26, 14, 9, 13, 13, 138, 14, 195, 182, 22, 5, 12, 195, 169, 19, 5, 13, 9, 134, 1, 4, 195, 161, 19, 1, 13, 0, 9, 198, 88, 243, 20, 5, 67, 203, 72, 12, 137, 5, 12, 12, 195, 161, 20, 195, 161, 19, 13, 11, 136, 18, 195, 169, 20, 5, 7, 5, 20, 13, 15, 140, 4, 195, 182, 14, 20, 195, 169, 19, 5, 11, 5, 20, 13, 11, 136, 16, 12, 195, 161, 26, 195, 161, 20, 13, 11, 136, 11, 1, 16, 21, 10, 195, 161, 20, 13, 0, 16, 205, 80, 20, 137, 24, 16, 211, 60, 208, 71, 60, 178, 193, 48, 13, 7, 196, 76, 244, 143, 56, 13, 12, 201, 32, 19, 135, 61, 165, 1, 80, 243, 64, 13, 11, 136, 11, 195, 182, 20, 195, 169, 19, 5, 13, 10, 135, 22, 195, 161, 18, 10, 21, 11, 13, 12, 201, 24, 83, 142, 4, 176, 68, 80, 19, 64, 13, 19, 144, 13, 5, 7, 19, 5, 7, 195, 173, 20, 195, 169, 19, 195, 169, 18, 5, 13, 32, 8, 11, 9, 1, 4, 195, 161, 19, 1, 49, 37, 106, 70, 112, 89, 106, 23, 55, 107, 105, 107, 47, 0, 13, 81, 108, 101, 104, 101, 116, 32, 12, 137, 22, 1, 7, 25, 15, 14, 195, 161, 20, 13, 0, 47, 70, 80, 17, 202, 4, 148, 129, 47, 106, 79, 57, 106, 37, 52, 106, 23, 82, 39, 50, 106, 47, 49, 39, 86, 12, 106, 50, 106, 49, 0, 13, 81, 118, 111, 110, 97, 116, 107, 111, 122, 122, 97, 110, 97, 107, 32, 14, 139, 7, 25, 15, 18, 19, 195, 173, 20, 195, 161, 19, 13, 10, 135, 22, 195, 161, 12, 1, 19, 26, 13, 14, 139, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 13, 0, 9, 134, 26, 195, 161, 18, 21, 12, 13, 0, 19, 67, 85, 48, 64, 117, 115, 195, 161, 98, 97, 0, 44, 29, 42, 81, 98, 97, 32, 21, 67, 85, 48, 64, 117, 115, 195, 161, 98, 97, 110, 0, 44, 29, 42, 81, 98, 97, 110, 32, 25, 67, 85, 48, 64, 117, 115, 195, 161, 195, 169, 118, 97, 108, 0, 44, 29, 42, 81, 195, 169, 118, 97, 108, 32, 21, 67, 85, 48, 64, 117, 115, 195, 161, 110, 97, 107, 0, 44, 29, 42, 81, 110, 97, 107, 32, 23, 67, 85, 48, 64, 117, 115, 195, 161, 98, 195, 179, 108, 0, 44, 29, 42, 81, 98, 195, 179, 108, 32, 7, 2, 95, 19, 107, 89, 0, 14, 139, 5, 12, 4, 195, 182, 14, 20, 195, 169, 19, 5, 13, 10, 199, 24, 83, 153, 20, 113, 84, 36, 13, 16, 141, 20, 195, 186, 12, 12, 195, 169, 16, 20, 195, 188, 14, 11, 13, 10, 199, 16, 243, 7, 61, 163, 129, 44, 13, 6, 195, 57, 146, 84, 13, 6, 195, 104, 18, 148, 13, 10, 4, 95, 50, 48, 5, 105, 40, 87, 0, 0, 17, 142, 13, 5, 7, 195, 161, 12, 12, 1, 16, 15, 4, 195, 161, 19, 13, 49, 14, 13, 5, 7, 195, 161, 12, 12, 1, 16, 15, 4, 195, 161, 19, 63, 107, 79, 112, 55, 12, 106, 48, 39, 70, 112, 89, 23, 49, 108, 47, 105, 107, 47, 116, 0, 13, 81, 107, 195, 182, 116, 104, 101, 116, 197, 145, 32, 57, 14, 13, 5, 7, 195, 161, 12, 12, 1, 16, 15, 4, 195, 161, 19, 63, 107, 79, 112, 55, 12, 106, 48, 39, 70, 112, 89, 23, 37, 89, 23, 87, 109, 55, 107, 47, 107, 47, 12, 0, 13, 82, 105, 115, 32, 115, 122, 195, 188, 108, 101, 116, 101, 116, 116, 32, 16, 141, 11, 21, 12, 20, 195, 186, 18, 195, 161, 10, 195, 161, 20, 13, 12, 68, 65, 52, 218, 80, 48, 87, 12, 47, 0, 41, 0, 27, 152, 19, 1, 10, 20, 195, 179, 20, 195, 161, 10, 195, 169, 11, 15, 26, 20, 1, 20, 195, 179, 10, 195, 161, 14, 13, 9, 134, 26, 195, 161, 18, 20, 1, 13, 9, 134, 22, 195, 161, 18, 20, 1, 13, 0, 7, 66, 77, 160, 107, 87, 0, 0, 17, 142, 19, 1, 10, 195, 161, 20, 15, 19, 19, 195, 161, 7, 15, 11, 13, 0, 20, 145, 11, 195, 182, 20, 5, 12, 5, 26, 5, 20, 20, 19, 195, 169, 7, 5, 20, 13, 0, 21, 146, 11, 15, 14, 6, 9, 7, 21, 18, 195, 161, 3, 9, 195, 179, 10, 195, 161, 20, 13, 8, 197, 24, 18, 149, 49, 64, 13, 9, 198, 64, 192, 84, 24, 244, 141, 13, 8, 197, 52, 20, 129, 17, 64, 13, 0, 12, 137, 8, 195, 169, 20, 6, 197, 145, 9, 7, 22, 0, 6, 195, 88, 83, 0, 13, 0, 17, 142, 1, 4, 15, 20, 20, 19, 195, 161, 7, 1, 9, 8, 15, 26, 13, 12, 137, 22, 9, 7, 25, 195, 161, 26, 14, 9, 13, 10, 135, 20, 5, 7, 25, 195, 188, 11, 13, 0, 15, 140, 20, 5, 14, 14, 9, 22, 1, 12, 195, 179, 14, 11, 13, 11, 136, 195, 173, 18, 14, 195, 161, 14, 11, 13, 6, 195, 48, 83, 142, 13, 0, 35, 70, 80, 83, 69, 77, 49, 64, 47, 107, 63, 107, 89, 12, 107, 23, 107, 55, 23, 114, 57, 52, 106, 0, 13, 82, 101, 108, 32, 195, 186, 106, 114, 97, 32, 9, 134, 22, 195, 169, 4, 5, 4, 13, 13, 138, 10, 5, 12, 5, 14, 20, 195, 169, 19, 20, 13, 9, 198, 77, 161, 77, 52, 83, 0, 13, 7, 132, 195, 169, 19, 26, 13, 5, 194, 80, 144, 13, 11, 66, 92, 48, 82, 111, 117, 111, 0, 42, 42, 0, 21, 67, 8, 18, 128, 69, 106, 57, 10, 6, 15, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 19, 67, 8, 18, 128, 69, 106, 57, 10, 6, 15, 106, 86, 0, 13, 81, 97, 122, 32, 47, 71, 65, 35, 199, 72, 19, 79, 80, 48, 52, 39, 79, 52, 106, 63, 39, 47, 23, 37, 50, 70, 110, 47, 106, 50, 112, 50, 106, 49, 0, 13, 81, 105, 110, 100, 195, 173, 116, 97, 110, 195, 161, 110, 97, 107, 32, 20, 67, 8, 18, 128, 69, 106, 57, 15, 82, 39, 55, 47, 0, 81, 118, 111, 108, 116, 32, 10, 135, 11, 195, 182, 26, 195, 188, 12, 13, 43, 71, 65, 35, 199, 72, 19, 79, 80, 48, 52, 39, 79, 52, 106, 63, 39, 47, 15, 47, 107, 87, 47, 107, 55, 109, 50, 49, 0, 13, 81, 116, 101, 115, 122, 116, 101, 108, 195, 188, 110, 107, 32, 6, 195, 8, 18, 128, 13, 10, 135, 11, 195, 182, 26, 195, 188, 12, 13, 15, 4, 95, 50, 48, 17, 105, 40, 87, 106, 70, 37, 49, 106, 0, 0, 11, 200, 24, 243, 25, 4, 208, 84, 61, 64, 13, 20, 68, 4, 178, 207, 72, 106, 49, 12, 39, 52, 23, 37, 89, 0, 13, 81, 105, 115, 32, 7, 196, 4, 178, 207, 72, 13, 0, 20, 5, 4, 197, 145, 12, 20, 70, 116, 55, 47, 23, 69, 107, 0, 13, 81, 98, 101, 32, 10, 135, 22, 195, 161, 7, 25, 19, 26, 13, 11, 136, 12, 195, 161, 20, 10, 195, 161, 11, 13, 12, 137, 4, 195, 182, 14, 20, 195, 169, 19, 20, 13, 11, 136, 12, 195, 161, 20, 10, 195, 161, 11, 13, 8, 133, 4, 197, 145, 12, 20, 13, 0, 13, 138, 10, 195, 179, 19, 26, 195, 161, 7, 15, 20, 13, 26, 70, 88, 86, 133, 80, 146, 192, 82, 107, 86, 107, 47, 37, 49, 10, 6, 15, 107, 55, 0, 13, 81, 101, 108, 32, 9, 198, 84, 118, 65, 56, 22, 128, 13, 12, 137, 6, 5, 10, 12, 197, 145, 4, 9, 11, 13, 12, 137, 11, 5, 26, 4, 197, 145, 4, 9, 11, 13, 0, 9, 198, 4, 194, 193, 48, 208, 83, 13, 17, 142, 3, 19, 195, 188, 20, 195, 182, 18, 20, 195, 182, 11, 9, 7, 22, 0, 13, 2, 95, 34, 37, 70, 111, 86, 116, 57, 107, 55, 0, 15, 140, 2, 195, 173, 18, 195, 179, 19, 195, 161, 7, 15, 20, 13, 14, 139, 10, 1, 22, 1, 19, 15, 12, 10, 195, 161, 11, 13, 10, 135, 6, 1, 10, 20, 195, 161, 11, 13, 10, 135, 8, 15, 26, 20, 195, 161, 11, 13, 15, 140, 2, 9, 26, 15, 20, 20, 19, 195, 161, 7, 15, 20, 13, 13, 138, 20, 21, 12, 1, 10, 4, 15, 14, 195, 186, 13, 7, 196, 52, 17, 213, 44, 13, 0, 17, 2, 95, 33, 81, 107, 55, 49, 37, 112, 55, 47, 113, 57, 107, 55, 0, 28, 69, 4, 176, 82, 60, 176, 106, 49, 106, 52, 39, 49, 23, 55, 107, 50, 12, 37, 0, 13, 81, 108, 101, 110, 110, 105, 32, 16, 141, 5, 12, 12, 5, 14, 197, 145, 18, 26, 195, 169, 19, 20, 13, 32, 69, 4, 176, 82, 40, 16, 106, 49, 106, 52, 57, 106, 23, 105, 106, 57, 47, 106, 50, 37, 0, 13, 81, 104, 97, 106, 116, 97, 110, 105, 32, 9, 134, 21, 20, 195, 161, 14, 1, 13, 8, 197, 4, 176, 82, 40, 16, 13, 11, 136, 22, 195, 161, 18, 20, 195, 161, 11, 13, 0, 7, 66, 81, 144, 78, 111, 0, 10, 135, 2, 5, 195, 173, 18, 22, 1, 13, 11, 136, 21, 4, 22, 1, 18, 195, 161, 14, 13, 17, 142, 8, 1, 19, 15, 14, 12, 195, 179, 19, 195, 161, 7, 15, 20, 13, 12, 137, 6, 195, 169, 14, 25, 5, 19, 5, 11, 13, 9, 134, 1, 14, 14, 195, 161, 12, 13, 10, 135, 12, 5, 195, 173, 18, 22, 1, 13, 0, 13, 2, 95, 39, 106, 48, 39, 87, 47, 52, 113, 81, 0, 28, 8, 20, 195, 169, 13, 195, 161, 10, 1, 47, 111, 63, 112, 57, 106, 23, 55, 107, 87, 0, 13, 81, 108, 101, 115, 122, 32, 16, 141, 20, 195, 161, 18, 7, 25, 1, 12, 195, 161, 19, 15, 14, 13, 11, 136, 20, 195, 169, 13, 195, 161, 10, 1, 13, 6, 195, 28, 243, 132, 13, 6, 195, 21, 49, 84, 13, 6, 195, 28, 243, 132, 13, 6, 195, 8, 19, 128, 72, 6, 195, 40, 19, 128, 20, 0, 28, 8, 6, 195, 182, 12, 195, 182, 20, 20, 81, 108, 55, 108, 47, 12, 23, 112, 55, 12, 0, 13, 81, 195, 161, 108, 108, 32, 7, 196, 12, 145, 201, 80, 13, 15, 140, 11, 22, 1, 12, 9, 6, 9, 11, 195, 161, 12, 20, 13, 20, 145, 13, 5, 7, 19, 26, 195, 161, 13, 12, 195, 161, 12, 20, 1, 20, 14, 9, 13, 25, 8, 6, 195, 182, 12, 195, 182, 20, 20, 81, 108, 55, 108, 47, 12, 23, 37, 89, 0, 13, 81, 105, 115, 32, 13, 138, 6, 5, 10, 22, 1, 4, 195, 161, 19, 26, 13, 6, 195, 21, 50, 75, 13, 11, 136, 6, 195, 182, 12, 195, 182, 20, 20, 13, 11, 136, 13, 195, 182, 7, 195, 182, 20, 20, 13, 10, 135, 10, 195, 186, 12, 9, 21, 19, 20, 0, 8, 197, 44, 243, 79, 49, 144, 13, 11, 136, 12, 5, 195, 173, 18, 195, 161, 19, 13, 20, 145, 20, 195, 161, 13, 15, 7, 1, 20, 15, 20, 20, 19, 195, 161, 7, 15, 20, 13, 16, 9, 95, 35, 45, 195, 169, 18, 197, 145, 12, 111, 52, 116, 55, 0, 14, 4, 95, 50, 48, 15, 105, 40, 87, 106, 70, 37, 49, 0, 0, 41, 74, 4, 192, 80, 4, 230, 65, 28, 242, 210, 4, 106, 55, 106, 48, 106, 65, 106, 79, 39, 49, 52, 106, 23, 49, 111, 65, 107, 89, 0, 13, 81, 107, 195, 169, 110, 121, 101, 115, 32, 16, 141, 20, 195, 161, 18, 7, 25, 1, 12, 195, 161, 19, 15, 11, 13, 50, 73, 20, 193, 75, 81, 35, 206, 36, 181, 83, 107, 55, 107, 49, 47, 52, 39, 50, 37, 49, 40, 89, 23, 82, 112, 55, 47, 39, 86, 106, 47, 112, 47, 0, 13, 81, 118, 195, 161, 108, 116, 111, 122, 97, 116, 195, 161, 116, 32, 14, 139, 195, 188, 26, 5, 13, 13, 195, 179, 4, 2, 1, 13, 16, 141, 2, 5, 18, 5, 14, 4, 5, 26, 195, 169, 19, 5, 11, 13, 9, 198, 5, 163, 206, 8, 19, 128, 13, 0, 7, 195, 88, 19, 128, 13, 22, 21, 67, 88, 19, 128, 82, 106, 50, 10, 6, 15, 37, 47, 12, 0, 13, 81, 105, 116, 116, 32, 32, 67, 88, 19, 128, 82, 106, 50, 23, 87, 109, 49, 89, 111, 79, 107, 63, 0, 13, 81, 115, 122, 195, 188, 107, 115, 195, 169, 103, 101, 109, 32, 18, 67, 88, 19, 128, 82, 106, 50, 23, 52, 112, 0, 13, 81, 114, 195, 161, 32, 23, 67, 88, 19, 128, 82, 106, 50, 23, 37, 70, 107, 57, 107, 0, 13, 81, 105, 100, 101, 106, 101, 32, 14, 139, 18, 195, 169, 19, 26, 5, 13, 18, 197, 145, 12, 13, 10, 135, 20, 15, 18, 20, 195, 161, 20, 13, 0, 18, 143, 8, 1, 14, 7, 19, 195, 186, 12, 25, 15, 26, 20, 195, 161, 11, 13, 27, 67, 8, 19, 139, 69, 106, 50, 49, 23, 89, 107, 79, 110, 47, 37, 0, 13, 81, 115, 101, 103, 195, 173, 116, 105, 32, 11, 136, 16, 195, 169, 12, 4, 195, 161, 20, 13, 9, 134, 16, 15, 8, 195, 161, 18, 13, 11, 136, 197, 145, 18, 195, 182, 11, 5, 20, 13, 15, 140, 20, 195, 169, 20, 5, 12, 195, 169, 18, 197, 145, 12, 13, 9, 134, 19, 26, 20, 195, 161, 18, 13, 6, 195, 64, 84, 131, 13, 12, 4, 95, 3, 1, 16, 50, 6, 106, 77, 23, 0, 10, 135, 10, 195, 186, 14, 9, 21, 19, 20, 0, 17, 2, 95, 41, 57, 6, 39, 69, 86, 112, 52, 113, 57, 107, 55, 0, 27, 38, 67, 5, 163, 206, 106, 86, 39, 50, 10, 6, 15, 79, 39, 50, 70, 39, 55, 49, 39, 70, 50, 37, 0, 13, 81, 103, 111, 110, 100, 111, 108, 107, 111, 100, 110, 105, 32, 12, 137, 8, 1, 12, 195, 161, 12, 195, 161, 20, 13, 6, 195, 5, 163, 206, 13, 9, 134, 3, 195, 173, 13, 197, 177, 13, 0, 17, 2, 95, 40, 69, 6, 106, 55, 86, 112, 52, 113, 57, 107, 55, 0, 27, 37, 70, 20, 208, 133, 72, 83, 128, 107, 63, 69, 107, 52, 107, 50, 23, 89, 107, 79, 110, 47, 105, 107, 47, 0, 13, 81, 115, 101, 103, 195, 173, 116, 104, 101, 116, 32, 6, 195, 44, 244, 129, 13, 34, 9, 13, 5, 7, 15, 12, 4, 195, 161, 19, 63, 107, 79, 39, 55, 70, 112, 89, 15, 48, 107, 70, 37, 79, 0, 13, 81, 112, 101, 100, 105, 103, 32, 12, 137, 13, 5, 7, 15, 12, 4, 195, 161, 19, 13, 9, 198, 20, 208, 133, 72, 83, 128, 13, 9, 198, 88, 86, 133, 80, 129, 84, 13, 0, 6, 195, 76, 244, 128, 13, 11, 67, 8, 20, 128, 69, 106, 52, 0, 42, 42, 0, 9, 2, 95, 46, 48, 39, 50, 47, 0, 11, 200, 24, 243, 25, 4, 208, 84, 61, 48, 13, 11, 136, 11, 1, 13, 5, 18, 195, 161, 20, 13, 15, 140, 20, 195, 182, 18, 20, 195, 169, 14, 5, 20, 5, 20, 13, 11, 136, 195, 182, 14, 195, 182, 11, 5, 20, 13, 15, 140, 5, 19, 26, 11, 195, 182, 26, 195, 182, 11, 5, 20, 13, 13, 138, 16, 1, 18, 1, 13, 195, 169, 20, 5, 18, 13, 8, 133, 195, 169, 18, 20, 5, 13, 15, 140, 9, 14, 4, 195, 173, 20, 22, 195, 161, 14, 25, 20, 13, 13, 138, 11, 195, 182, 14, 25, 22, 20, 195, 161, 18, 13, 6, 195, 5, 163, 203, 13, 11, 136, 20, 5, 18, 195, 188, 12, 5, 20, 13, 0, 12, 2, 95, 45, 63, 6, 37, 50, 40, 87, 0, 27, 20, 145, 12, 5, 8, 5, 20, 197, 145, 19, 195, 169, 7, 5, 9, 18, 197, 145, 12, 13, 19, 144, 19, 26, 5, 13, 195, 169, 12, 25, 12, 5, 195, 173, 18, 195, 161, 19, 13, 12, 201, 61, 69, 8, 60, 229, 1, 48, 19, 128, 13, 16, 140, 20, 5, 18, 13, 195, 169, 19, 26, 5, 20, 5, 19, 72, 65, 0, 10, 2, 95, 44, 82, 107, 87, 120, 116, 0, 15, 140, 8, 195, 161, 20, 20, 195, 169, 18, 20, 195, 161, 18, 13, 13, 138, 6, 15, 18, 13, 195, 161, 10, 195, 161, 20, 13, 0, 6, 195, 81, 68, 192, 13, 22, 147, 11, 1, 18, 12, 5, 14, 4, 195, 173, 20, 195, 169, 19, 5, 11, 2, 197, 145, 12, 13, 8, 133, 195, 173, 18, 19, 26, 13, 6, 195, 8, 18, 148, 13, 12, 67, 53, 36, 192, 63, 37, 87, 37, 87, 0, 25, 6, 195, 49, 68, 192, 20, 10, 2, 95, 51, 105, 112, 52, 39, 63, 0, 0, 15, 140, 18, 195, 161, 7, 25, 195, 186, 10, 20, 8, 1, 20, 13, 9, 198, 52, 17, 193, 76, 16, 130, 13, 14, 139, 8, 1, 19, 26, 14, 195, 161, 12, 10, 21, 11, 13, 9, 198, 29, 147, 210, 76, 16, 130, 13, 8, 133, 195, 173, 18, 20, 1, 13, 10, 2, 95, 50, 49, 107, 47, 12, 116, 0, 0, 12, 137, 8, 1, 19, 26, 14, 195, 161, 12, 4, 13, 11, 136, 195, 182, 20, 12, 5, 20, 5, 11, 13, 8, 197, 61, 69, 8, 60, 224, 13, 8, 133, 20, 195, 182, 18, 20, 13, 11, 136, 20, 197, 145, 12, 5, 20, 5, 11, 13, 7, 2, 95, 49, 107, 77, 0, 0, 17, 142, 11, 195, 188, 12, 195, 182, 14, 2, 19, 195, 169, 7, 5, 20, 13, 12, 137, 12, 5, 14, 14, 195, 169, 20, 5, 11, 13, 6, 195, 4, 69, 1, 13, 10, 2, 95, 48, 50, 40, 55, 55, 106, 0, 0, 9, 134, 15, 11, 15, 26, 195, 179, 13, 16, 141, 11, 195, 182, 18, 14, 25, 5, 26, 5, 20, 8, 5, 26, 13, 8, 2, 95, 55, 105, 111, 119, 0, 0, 8, 2, 95, 54, 105, 106, 119, 0, 0, 8, 197, 80, 84, 133, 53, 64, 13, 9, 198, 88, 19, 1, 32, 245, 129, 13, 8, 197, 76, 83, 139, 37, 64, 13, 7, 2, 95, 53, 108, 119, 0, 0, 21, 146, 11, 195, 182, 20, 5, 12, 5, 26, 5, 20, 20, 19, 195, 169, 7, 195, 169, 20, 13, 9, 198, 88, 86, 133, 77, 49, 64, 13, 19, 144, 8, 1, 19, 26, 14, 195, 161, 12, 8, 1, 20, 1, 20, 12, 1, 14, 13, 8, 2, 95, 52, 50, 111, 77, 0, 0, 16, 2, 95, 59, 48, 39, 50, 47, 39, 89, 82, 107, 87, 120, 116, 0, 9, 134, 195, 161, 20, 12, 1, 7, 13, 15, 140, 8, 9, 7, 1, 14, 25, 19, 26, 195, 161, 12, 1, 13, 0, 15, 2, 95, 58, 49, 107, 47, 12, 116, 89, 48, 39, 50, 47, 0, 0, 19, 144, 19, 26, 195, 161, 13, 195, 173, 20, 195, 179, 7, 195, 169, 16, 5, 11, 13, 11, 2, 95, 57, 49, 37, 55, 107, 50, 117, 0, 0, 23, 9, 5, 7, 25, 5, 26, 19, 195, 169, 7, 101, 103, 103, 121, 101, 115, 115, 195, 169, 103, 0, 29, 32, 70, 24, 244, 137, 57, 67, 212, 81, 39, 52, 37, 50, 47, 39, 47, 23, 111, 52, 50, 107, 49, 0, 13, 81, 195, 169, 114, 110, 101, 107, 32, 9, 198, 24, 244, 137, 57, 67, 212, 13, 9, 2, 95, 56, 65, 39, 55, 117, 0, 0, 13, 2, 95, 63, 49, 111, 52, 70, 116, 57, 107, 55, 0, 13, 138, 22, 5, 19, 26, 20, 5, 19, 195, 169, 7, 13, 10, 199, 57, 145, 82, 80, 84, 197, 36, 13, 6, 195, 32, 86, 128, 13, 0, 10, 2, 95, 62, 50, 106, 77, 39, 69, 0, 12, 137, 10, 195, 161, 18, 22, 195, 161, 14, 25, 13, 7, 196, 45, 83, 3, 76, 13, 7, 196, 41, 85, 14, 36, 13, 11, 200, 77, 161, 80, 80, 83, 66, 21, 32, 20, 0, 8, 197, 40, 83, 26, 36, 176, 13, 8, 197, 24, 83, 18, 4, 176, 13, 25, 6, 18, 195, 169, 19, 26, 5, 52, 111, 87, 107, 15, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 9, 134, 18, 195, 169, 19, 26, 5, 13, 0, 11, 2, 95, 60, 49, 37, 89, 89, 107, 69, 0, 6, 195, 88, 150, 133, 13, 11, 136, 195, 188, 14, 14, 5, 16, 5, 14, 13, 53, 9, 20, 1, 14, 195, 161, 3, 19, 15, 11, 47, 106, 50, 112, 74, 39, 49, 23, 49, 111, 52, 70, 111, 89, 111, 52, 116, 55, 23, 37, 89, 0, 13, 82, 107, 195, 169, 114, 100, 195, 169, 115, 195, 169, 114, 197, 145, 108, 32, 105, 115, 32, 14, 139, 5, 12, 197, 145, 11, 5, 18, 5, 19, 14, 9, 13, 0, 17, 142, 4, 9, 19, 26, 20, 18, 9, 2, 195, 186, 3, 9, 195, 179, 13, 12, 201, 65, 35, 199, 72, 19, 79, 44, 21, 0, 13, 9, 198, 48, 20, 20, 61, 3, 203, 13, 6, 195, 57, 145, 76, 13, 0, 13, 138, 15, 19, 26, 20, 195, 161, 12, 25, 15, 14, 13, 8, 133, 8, 195, 161, 26, 1, 13, 11, 200, 44, 145, 15, 48, 115, 218, 80, 16, 13, 12, 137, 22, 5, 26, 5, 20, 197, 145, 10, 5, 13, 10, 135, 12, 195, 161, 20, 10, 21, 11, 13, 8, 133, 195, 173, 18, 22, 1, 13, 0, 8, 197, 80, 20, 148, 60, 176, 13, 44, 69, 56, 17, 217, 72, 16, 50, 106, 77, 52, 106, 10, 6, 15, 82, 106, 50, 10, 6, 15, 112, 55, 110, 47, 82, 106, 0, 13, 82, 118, 97, 110, 32, 195, 161, 108, 108, 195, 173, 116, 118, 97, 32, 12, 137, 9, 18, 195, 161, 14, 25, 21, 12, 20, 13, 9, 134, 20, 195, 161, 22, 18, 1, 13, 8, 197, 77, 161, 82, 16, 16, 20, 0, 26, 5, 6, 195, 188, 7, 7, 81, 109, 79, 12, 23, 108, 87, 12, 107, 0, 13, 81, 195, 182, 115, 115, 122, 101, 32, 22, 3, 18, 195, 161, 52, 112, 23, 37, 79, 111, 65, 0, 13, 81, 105, 103, 195, 169, 110, 121, 32, 31, 3, 18, 195, 161, 52, 112, 23, 87, 109, 49, 89, 111, 79, 107, 63, 0, 13, 81, 115, 122, 195, 188, 107, 115, 195, 169, 103, 101, 109, 32, 8, 133, 6, 195, 188, 7, 7, 13, 6, 131, 18, 195, 161, 13, 0, 30, 10, 20, 5, 18, 195, 188, 12, 5, 20, 5, 11, 47, 107, 52, 109, 55, 107, 47, 107, 49, 23, 37, 89, 0, 13, 81, 105, 115, 32, 24, 5, 5, 7, 195, 169, 18, 107, 79, 111, 52, 23, 82, 39, 55, 47, 0, 13, 81, 118, 111, 108, 116, 32, 15, 140, 19, 26, 1, 11, 195, 169, 18, 20, 197, 145, 10, 5, 13, 11, 136, 6, 15, 18, 13, 195, 161, 10, 1, 13, 15, 140, 13, 5, 7, 1, 12, 11, 15, 20, 195, 179, 10, 1, 13, 10, 199, 80, 85, 20, 20, 147, 133, 44, 13, 0, 12, 137, 18, 1, 11, 20, 195, 161, 18, 18, 1, 13, 0, 13, 138, 19, 5, 7, 195, 173, 20, 5, 14, 195, 169, 13, 12, 201, 13, 51, 205, 4, 115, 203, 32, 246, 128, 13, 0, 0, 10, 135, 12, 195, 169, 16, 8, 5, 20, 13, 15, 140, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 10, 1, 13, 10, 135, 22, 195, 161, 12, 8, 1, 20, 13, 14, 139, 13, 197, 177, 11, 195, 182, 4, 195, 182, 20, 20, 13, 0, 20, 145, 6, 18, 1, 11, 3, 9, 195, 179, 22, 5, 26, 5, 20, 197, 145, 10, 5, 13, 40, 7, 22, 5, 7, 25, 195, 188, 11, 82, 107, 77, 109, 49, 10, 6, 15, 81, 37, 77, 107, 55, 107, 63, 69, 107, 0, 13, 81, 102, 105, 103, 121, 101, 108, 101, 109, 98, 101, 32, 6, 195, 88, 144, 195, 13, 0, 33, 4, 95, 226, 128, 163, 105, 112, 52, 39, 63, 87, 108, 79, 106, 55, 106, 49, 114, 81, 107, 55, 89, 39, 52, 39, 55, 112, 89, 57, 107, 55, 0, 12, 201, 37, 35, 196, 4, 195, 205, 8, 19, 128, 13, 9, 134, 20, 197, 177, 14, 197, 145, 13, 0, 15, 4, 95, 226, 128, 162, 55, 37, 89, 47, 106, 57, 107, 55, 0, 13, 138, 195, 169, 18, 20, 5, 12, 13, 195, 169, 20, 13, 13, 138, 11, 5, 18, 5, 19, 26, 20, 195, 188, 12, 13, 9, 134, 195, 182, 20, 12, 5, 20, 13, 9, 134, 195, 161, 12, 12, 1, 20, 13, 11, 136, 20, 195, 161, 14, 25, 195, 169, 18, 13, 10, 135, 8, 195, 169, 20, 6, 197, 145, 20, 0, 17, 142, 195, 182, 19, 19, 26, 5, 6, 195, 188, 7, 7, 195, 169, 19, 13, 25, 4, 195, 179, 20, 1, 113, 47, 106, 23, 47, 106, 52, 47, 113, 0, 13, 81, 116, 97, 114, 116, 195, 179, 32, 13, 138, 11, 9, 20, 195, 182, 12, 20, 195, 169, 19, 13, 16, 141, 16, 15, 12, 7, 195, 161, 18, 13, 5, 19, 20, 5, 18, 13, 10, 135, 195, 161, 12, 12, 8, 1, 20, 13, 10, 135, 11, 195, 169, 18, 8, 5, 20, 13, 9, 132, 195, 179, 20, 1, 13, 20, 22, 0, 7, 196, 24, 241, 211, 104, 76, 0, 13, 138, 11, 195, 188, 12, 6, 195, 182, 12, 4, 9, 13, 8, 197, 77, 64, 66, 36, 192, 13, 12, 137, 10, 195, 161, 20, 19, 26, 8, 1, 20, 13, 12, 137, 11, 5, 18, 195, 188, 12, 8, 5, 20, 13, 16, 141, 5, 12, 197, 145, 6, 15, 18, 4, 21, 12, 8, 1, 20, 13, 8, 197, 37, 69, 8, 60, 224, 13, 0, 19, 4, 95, 226, 128, 166, 48, 39, 50, 47, 48, 39, 50, 47, 48, 39, 50, 47, 0, 13, 138, 5, 19, 26, 11, 195, 182, 26, 195, 169, 20, 13, 27, 6, 18, 195, 169, 19, 26, 20, 52, 111, 87, 47, 23, 82, 107, 50, 12, 37, 0, 13, 81, 118, 101, 110, 110, 105, 32, 24, 6, 18, 195, 169, 19, 26, 20, 52, 111, 87, 47, 23, 82, 107, 87, 0, 13, 81, 118, 101, 115, 122, 32, 13, 138, 22, 195, 161, 12, 20, 15, 26, 8, 1, 20, 13, 29, 6, 18, 195, 169, 19, 26, 20, 52, 111, 87, 47, 23, 82, 107, 47, 12, 107, 49, 0, 13, 81, 118, 101, 116, 116, 101, 107, 32, 14, 139, 18, 5, 14, 4, 5, 12, 11, 5, 26, 197, 145, 13, 9, 134, 9, 18, 195, 161, 14, 20, 13, 9, 134, 18, 195, 169, 19, 26, 20, 13, 0, 19, 67, 85, 48, 128, 195, 186, 101, 115, 98, 195, 169, 116, 0, 44, 29, 81, 116, 32, 19, 67, 85, 48, 128, 195, 186, 101, 115, 98, 195, 169, 110, 0, 44, 29, 81, 110, 32, 20, 67, 85, 48, 128, 195, 186, 101, 115, 98, 195, 169, 110, 0, 44, 29, 42, 81, 110, 32, 9, 134, 22, 1, 12, 195, 179, 11, 13, 6, 195, 16, 80, 192, 20, 0, 14, 139, 15, 16, 5, 18, 195, 161, 20, 15, 18, 15, 11, 13, 6, 131, 18, 195, 179, 13, 6, 195, 76, 242, 203, 13, 0, 15, 4, 95, 226, 128, 155, 37, 70, 111, 86, 116, 57, 107, 55, 0, 16, 141, 13, 5, 14, 14, 25, 9, 19, 195, 169, 7, 195, 169, 20, 13, 9, 134, 12, 195, 182, 11, 20, 5, 13, 7, 132, 19, 26, 195, 179, 13, 0, 15, 4, 95, 226, 128, 154, 37, 70, 111, 86, 116, 57, 107, 55, 0, 9, 198, 84, 118, 65, 56, 148, 192, 13, 34, 10, 20, 21, 4, 15, 13, 195, 161, 19, 21, 12, 47, 40, 70, 39, 63, 112, 89, 40, 55, 23, 49, 107, 55, 12, 0, 13, 81, 107, 101, 108, 108, 32, 30, 5, 1, 16, 18, 195, 179, 106, 48, 52, 113, 10, 6, 15, 70, 39, 55, 79, 39, 49, 0, 13, 81, 100, 111, 108, 103, 111, 107, 32, 56, 14, 19, 26, 5, 18, 5, 12, 22, 195, 169, 14, 25, 5, 9, 20, 87, 107, 52, 107, 55, 82, 111, 65, 107, 37, 47, 23, 63, 107, 79, 107, 52, 116, 89, 110, 47, 82, 107, 0, 13, 81, 109, 101, 103, 101, 114, 197, 145, 115, 195, 173, 116, 118, 101, 32, 11, 136, 2, 15, 12, 25, 7, 195, 179, 14, 13, 0, 25, 4, 95, 226, 128, 153, 57, 39, 69, 12, 39, 55, 70, 106, 55, 37, 37, 70, 111, 86, 116, 57, 107, 55, 0, 6, 195, 36, 65, 64, 13, 15, 140, 13, 1, 18, 1, 4, 22, 195, 161, 14, 25, 1, 9, 13, 13, 138, 20, 21, 4, 15, 13, 195, 161, 19, 21, 11, 13, 13, 138, 13, 195, 169, 18, 5, 20, 197, 177, 5, 11, 13, 6, 195, 36, 65, 64, 13, 0, 24, 4, 95, 226, 128, 152, 69, 106, 55, 39, 55, 70, 106, 55, 37, 37, 70, 111, 86, 116, 57, 107, 55, 0, 0, 15, 4, 95, 226, 128, 159, 37, 70, 111, 86, 116, 57, 107, 55, 0, 12, 137, 13, 195, 169, 18, 6, 195, 182, 12, 4, 13, 9, 198, 24, 148, 148, 5, 69, 1, 13, 0, 15, 4, 95, 226, 128, 158, 37, 70, 111, 86, 116, 57, 107, 55, 0, 0, 15, 4, 95, 226, 128, 157, 37, 70, 111, 86, 116, 57, 107, 55, 0, 19, 2, 95, 91, 65, 6, 37, 47, 113, 87, 108, 79, 55, 107, 47, 107, 89, 0, 27, 9, 134, 22, 195, 161, 18, 15, 19, 13, 0, 15, 4, 95, 226, 128, 156, 37, 70, 111, 86, 116, 57, 107, 55, 0, 20, 67, 4, 194, 71, 106, 55, 37, 79, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 10, 135, 8, 1, 26, 195, 161, 14, 11, 13, 18, 143, 6, 5, 12, 19, 26, 195, 179, 12, 1, 12, 195, 161, 19, 15, 11, 13, 6, 195, 76, 244, 147, 13, 0, 18, 4, 95, 226, 128, 147, 79, 39, 50, 70, 39, 55, 106, 47, 57, 107, 55, 0, 16, 141, 22, 195, 161, 12, 1, 19, 26, 1, 9, 2, 195, 179, 12, 13, 15, 140, 22, 195, 161, 12, 12, 1, 12, 11, 15, 26, 195, 179, 13, 9, 134, 22, 195, 161, 18, 14, 9, 13, 6, 195, 80, 84, 150, 13, 0, 35, 70, 21, 49, 84, 48, 81, 192, 107, 89, 107, 47, 55, 107, 79, 23, 107, 55, 111, 52, 105, 107, 47, 0, 13, 81, 101, 108, 195, 169, 114, 104, 101, 116, 32, 9, 198, 77, 161, 77, 64, 243, 148, 13, 9, 134, 12, 5, 7, 195, 179, 20, 13, 6, 195, 32, 81, 217, 13, 17, 66, 88, 144, 105, 106, 47, 12, 106, 55, 0, 44, 42, 81, 97, 108, 32, 0, 14, 2, 95, 95, 106, 55, 112, 105, 114, 86, 112, 89, 0, 27, 30, 67, 76, 242, 192, 89, 39, 49, 23, 47, 109, 52, 107, 55, 63, 107, 47, 0, 13, 81, 116, 195, 188, 114, 101, 108, 109, 101, 116, 32, 13, 138, 13, 15, 14, 4, 1, 14, 195, 161, 14, 11, 13, 6, 195, 76, 242, 192, 13, 20, 4, 95, 51, 48, 17, 105, 106, 52, 10, 63, 37, 50, 117, 106, 70, 37, 49, 106, 0, 0, 11, 200, 84, 118, 65, 56, 18, 203, 61, 32, 13, 41, 6, 7, 195, 169, 16, 5, 14, 79, 111, 48, 107, 50, 23, 87, 109, 49, 89, 111, 79, 107, 89, 107, 49, 0, 13, 81, 115, 122, 195, 188, 107, 115, 195, 169, 103, 101, 115, 101, 107, 32, 24, 6, 7, 195, 169, 16, 5, 14, 79, 111, 48, 107, 50, 15, 81, 40, 47, 0, 13, 81, 102, 117, 116, 32, 9, 134, 7, 195, 169, 16, 5, 14, 13, 7, 196, 25, 85, 14, 36, 13, 10, 135, 15, 12, 3, 19, 195, 179, 11, 13, 9, 134, 20, 195, 161, 22, 15, 14, 13, 0, 19, 2, 95, 93, 86, 6, 112, 52, 113, 87, 108, 79, 55, 107, 47, 107, 89, 0, 27, 9, 134, 22, 195, 161, 18, 15, 13, 13, 10, 135, 22, 195, 161, 12, 10, 15, 14, 13, 0, 38, 67, 56, 17, 217, 50, 106, 77, 10, 6, 15, 63, 107, 79, 55, 107, 48, 107, 47, 111, 89, 47, 0, 13, 81, 109, 101, 103, 108, 101, 112, 101, 116, 195, 169, 115, 116, 32, 9, 198, 8, 85, 5, 28, 82, 192, 13, 9, 198, 64, 147, 12, 4, 224, 84, 13, 9, 198, 20, 195, 69, 56, 226, 64, 13, 14, 139, 20, 1, 12, 195, 161, 12, 13, 195, 161, 14, 25, 13, 6, 195, 56, 17, 217, 13, 0, 6, 195, 4, 64, 84, 13, 6, 195, 64, 84, 148, 13, 9, 134, 13, 195, 186, 12, 9, 11, 13, 6, 195, 76, 244, 148, 13, 6, 195, 56, 18, 192, 13, 0, 17, 4, 95, 226, 128, 148, 49, 82, 37, 52, 47, 63, 110, 50, 40, 87, 0, 11, 200, 24, 83, 153, 20, 113, 84, 88, 80, 13, 12, 137, 8, 1, 20, 195, 161, 12, 25, 2, 1, 13, 10, 135, 195, 161, 12, 12, 195, 179, 11, 13, 9, 134, 10, 195, 161, 18, 19, 26, 13, 13, 138, 11, 195, 182, 22, 5, 20, 197, 145, 5, 14, 13, 0, 41, 6, 13, 195, 179, 4, 10, 1, 63, 113, 77, 12, 106, 23, 63, 107, 79, 82, 112, 55, 47, 39, 86, 37, 49, 0, 13, 81, 109, 101, 103, 118, 195, 161, 108, 116, 111, 122, 105, 107, 32, 13, 138, 5, 12, 195, 169, 18, 195, 169, 19, 18, 5, 13, 38, 69, 44, 86, 133, 48, 144, 49, 107, 86, 107, 55, 37, 23, 106, 6, 23, 86, 107, 50, 111, 49, 107, 47, 0, 13, 82, 97, 32, 122, 101, 110, 195, 169, 107, 101, 116, 32, 13, 138, 5, 12, 11, 5, 18, 195, 188, 12, 10, 5, 13, 12, 137, 8, 1, 19, 26, 14, 195, 161, 12, 20, 13, 8, 197, 4, 176, 82, 80, 16, 13, 12, 201, 72, 83, 132, 20, 194, 197, 104, 146, 192, 13, 12, 201, 24, 145, 217, 20, 195, 69, 76, 82, 192, 13, 9, 134, 10, 195, 161, 18, 14, 1, 13, 8, 197, 80, 20, 148, 60, 208, 13, 8, 197, 32, 149, 20, 20, 208, 13, 9, 134, 22, 195, 182, 12, 7, 25, 13, 0, 10, 2, 95, 96, 47, 39, 63, 48, 106, 0, 6, 195, 8, 18, 201, 13, 35, 70, 20, 208, 133, 72, 82, 192, 107, 63, 69, 107, 52, 107, 49, 23, 87, 112, 63, 112, 52, 106, 0, 13, 81, 115, 122, 195, 161, 109, 195, 161, 114, 97, 32, 9, 198, 48, 85, 143, 56, 226, 64, 13, 11, 136, 18, 195, 169, 19, 26, 195, 169, 14, 13, 0, 13, 138, 18, 195, 169, 19, 26, 12, 5, 20, 5, 11, 13, 10, 199, 60, 181, 1, 80, 226, 85, 44, 13, 10, 199, 80, 83, 5, 24, 243, 143, 44, 13, 0, 11, 200, 44, 83, 5, 80, 177, 90, 36, 176, 13, 12, 137, 2, 195, 186, 10, 20, 1, 20, 10, 1, 13, 0, 9, 134, 4, 195, 182, 6, 197, 145, 13, 13, 138, 195, 188, 7, 25, 22, 195, 169, 4, 10, 5, 13, 11, 136, 22, 195, 169, 7, 26, 195, 169, 19, 13, 19, 4, 95, 51, 48, 15, 105, 106, 52, 10, 63, 37, 50, 117, 106, 70, 37, 49, 0, 0, 17, 142, 20, 21, 12, 1, 10, 4, 15, 14, 15, 19, 20, 195, 179, 12, 13, 9, 198, 61, 37, 143, 77, 48, 76, 13, 13, 138, 3, 19, 15, 13, 1, 7, 18, 195, 179, 12, 13, 0, 10, 199, 40, 83, 12, 20, 113, 197, 48, 13, 18, 143, 6, 5, 12, 195, 188, 12, 22, 9, 26, 19, 7, 195, 161, 12, 20, 13, 0, 45, 13, 11, 1, 20, 5, 7, 195, 179, 18, 9, 195, 161, 2, 1, 49, 106, 47, 107, 79, 113, 52, 37, 112, 69, 106, 23, 89, 39, 52, 39, 55, 39, 63, 0, 13, 81, 115, 111, 114, 111, 108, 111, 109, 32, 10, 135, 11, 195, 182, 20, 195, 169, 19, 13, 8, 133, 197, 145, 18, 26, 9, 13, 7, 196, 80, 81, 217, 20, 13, 43, 76, 36, 225, 143, 72, 208, 84, 36, 181, 83, 56, 18, 192, 37, 50, 81, 39, 52, 10, 63, 106, 47, 37, 49, 40, 89, 50, 106, 49, 15, 49, 107, 55, 12, 0, 13, 81, 107, 101, 108, 108, 32, 15, 140, 20, 1, 12, 195, 161, 12, 11, 15, 26, 15, 20, 20, 13, 8, 133, 195, 169, 18, 26, 9, 13, 0, 9, 134, 1, 18, 195, 161, 14, 25, 13, 36, 8, 14, 5, 22, 5, 12, 195, 169, 19, 50, 107, 82, 107, 55, 111, 89, 23, 47, 111, 63, 112, 57, 106, 0, 13, 81, 116, 195, 169, 109, 195, 161, 106, 97, 32, 9, 134, 10, 195, 161, 18, 14, 9, 13, 0, 10, 135, 2, 5, 195, 173, 18, 14, 9, 13, 18, 143, 195, 161, 12, 12, 1, 20, 20, 1, 18, 20, 195, 161, 19, 18, 1, 13, 13, 138, 18, 195, 169, 19, 26, 12, 5, 20, 5, 20, 13, 9, 134, 195, 182, 19, 195, 169, 20, 13, 12, 4, 95, 7, 18, 22, 47, 39, 63, 48, 106, 0, 0, 9, 198, 44, 83, 12, 20, 225, 75, 13, 18, 143, 19, 26, 195, 169, 11, 8, 195, 161, 26, 195, 161, 2, 195, 179, 12, 13, 10, 135, 11, 195, 182, 18, 195, 169, 20, 13, 11, 136, 12, 195, 169, 14, 25, 5, 7, 5, 13, 10, 135, 10, 195, 161, 18, 8, 1, 20, 13, 10, 135, 11, 195, 182, 18, 195, 169, 20, 13, 0, 11, 136, 18, 195, 169, 19, 26, 195, 169, 20, 13, 12, 137, 19, 15, 11, 1, 19, 195, 161, 7, 1, 13, 12, 137, 10, 5, 12, 12, 5, 13, 26, 197, 145, 13, 9, 134, 13, 195, 179, 4, 15, 14, 13, 0, 10, 135, 8, 15, 19, 19, 26, 195, 186, 13, 20, 145, 9, 14, 20, 195, 169, 26, 13, 195, 169, 14, 25, 5, 11, 14, 195, 169, 12, 13, 15, 140, 5, 12, 11, 195, 169, 16, 26, 5, 12, 195, 169, 19, 13, 8, 197, 44, 81, 4, 20, 224, 22, 0, 6, 195, 88, 17, 217, 72, 17, 142, 7, 25, 197, 177, 18, 197, 145, 4, 195, 169, 19, 5, 9, 20, 13, 12, 201, 52, 147, 137, 77, 165, 5, 72, 225, 75, 13, 6, 195, 24, 17, 217, 13, 7, 195, 88, 17, 217, 76, 8, 0, 10, 135, 8, 195, 179, 2, 15, 18, 20, 13, 14, 139, 22, 5, 26, 5, 20, 195, 169, 19, 195, 169, 20, 13, 0, 13, 138, 19, 26, 195, 179, 12, 1, 12, 10, 15, 14, 13, 10, 135, 15, 16, 3, 9, 195, 179, 11, 13, 10, 135, 22, 9, 4, 5, 195, 179, 11, 13, 11, 200, 37, 51, 69, 72, 85, 12, 20, 224, 13, 7, 196, 21, 164, 133, 56, 13, 10, 135, 11, 195, 182, 4, 195, 182, 19, 13, 0, 16, 141, 13, 197, 177, 11, 195, 182, 4, 195, 169, 19, 195, 169, 20, 13, 0, 9, 198, 24, 20, 1, 16, 244, 192, 13, 13, 138, 5, 12, 1, 4, 195, 179, 20, 195, 179, 12, 13, 21, 66, 97, 96, 47, 37, 86, 107, 50, 108, 47, 12, 107, 55, 0, 44, 42, 81, 101, 108, 32, 0, 9, 198, 81, 81, 10, 4, 224, 75, 13, 48, 15, 10, 5, 12, 5, 14, 20, 11, 5, 26, 195, 169, 19, 195, 169, 20, 57, 107, 55, 107, 50, 47, 49, 107, 86, 111, 89, 111, 47, 23, 82, 112, 52, 57, 40, 49, 0, 13, 81, 118, 195, 161, 114, 106, 117, 107, 32, 18, 143, 20, 5, 12, 10, 5, 19, 195, 173, 20, 195, 169, 19, 195, 169, 20, 13, 10, 199, 36, 225, 15, 44, 243, 20, 4, 13, 12, 137, 19, 26, 195, 161, 12, 12, 10, 15, 14, 13, 0, 11, 200, 65, 35, 199, 72, 19, 66, 4, 224, 13, 10, 135, 12, 195, 169, 14, 25, 5, 7, 13, 0, 43, 73, 44, 20, 3, 76, 243, 1, 80, 244, 192, 49, 106, 48, 74, 39, 55, 106, 47, 39, 89, 23, 77, 106, 50, 114, 52, 113, 55, 0, 13, 81, 103, 121, 97, 110, 195, 186, 114, 195, 179, 108, 32, 45, 73, 44, 20, 3, 76, 243, 1, 80, 244, 192, 49, 106, 48, 74, 39, 55, 106, 47, 39, 89, 23, 47, 107, 52, 82, 107, 49, 52, 116, 55, 0, 13, 81, 116, 101, 114, 118, 101, 107, 114, 197, 145, 108, 32, 41, 73, 44, 20, 3, 76, 243, 1, 80, 244, 192, 49, 106, 48, 74, 39, 55, 106, 47, 39, 89, 23, 105, 110, 52, 107, 49, 107, 47, 0, 13, 81, 104, 195, 173, 114, 101, 107, 101, 116, 32, 58, 73, 44, 20, 3, 76, 243, 1, 80, 244, 192, 49, 106, 48, 74, 39, 55, 106, 47, 39, 89, 23, 69, 37, 86, 39, 65, 47, 106, 55, 106, 50, 89, 112, 79, 39, 49, 0, 13, 81, 98, 105, 122, 111, 110, 121, 116, 97, 108, 97, 110, 115, 195, 161, 103, 111, 107, 32, 12, 201, 44, 20, 3, 76, 243, 1, 80, 244, 192, 13, 8, 197, 76, 241, 15, 73, 64, 13, 0, 36, 6, 13, 195, 179, 4, 15, 20, 63, 113, 70, 39, 47, 23, 82, 112, 55, 106, 87, 47, 39, 63, 0, 13, 81, 118, 195, 161, 108, 97, 115, 122, 116, 111, 109, 32, 43, 70, 44, 83, 12, 20, 225, 64, 49, 107, 55, 12, 107, 50, 36, 23, 69, 37, 87, 47, 39, 87, 110, 47, 106, 50, 37, 0, 13, 81, 98, 105, 122, 116, 111, 115, 195, 173, 116, 97, 110, 105, 32, 34, 70, 44, 83, 12, 20, 225, 64, 49, 107, 55, 12, 107, 50, 107, 23, 81, 37, 86, 107, 47, 50, 37, 0, 13, 81, 102, 105, 122, 101, 116, 110, 105, 32, 39, 70, 44, 83, 12, 20, 225, 64, 49, 107, 55, 12, 107, 50, 107, 23, 106, 6, 15, 48, 52, 39, 79, 52, 106, 63, 0, 13, 82, 97, 32, 112, 114, 111, 103, 114, 97, 109, 32, 37, 70, 44, 83, 12, 20, 225, 64, 49, 107, 55, 12, 107, 50, 107, 15, 49, 108, 82, 107, 47, 50, 37, 107, 0, 13, 81, 107, 195, 182, 118, 101, 116, 110, 105, 101, 32, 13, 202, 4, 194, 193, 48, 208, 90, 61, 69, 1, 44, 13, 17, 142, 2, 9, 26, 15, 20, 20, 19, 195, 161, 7, 20, 195, 179, 12, 13, 9, 198, 44, 83, 12, 20, 225, 64, 13, 0, 18, 2, 95, 123, 49, 6, 107, 86, 70, 116, 49, 106, 48, 74, 39, 89, 0, 27, 12, 4, 95, 4, 9, 1, 47, 52, 111, 63, 106, 0, 0, 15, 140, 20, 195, 182, 18, 22, 195, 169, 14, 14, 25, 5, 12, 13, 0, 20, 4, 95, 226, 128, 179, 70, 40, 48, 55, 106, 106, 48, 39, 87, 47, 52, 113, 81, 0, 8, 197, 105, 82, 1, 57, 64, 13, 0, 15, 4, 95, 226, 128, 178, 106, 48, 39, 87, 47, 52, 113, 81, 0, 10, 135, 11, 9, 195, 173, 18, 14, 9, 13, 0, 10, 199, 28, 243, 132, 60, 197, 78, 44, 13, 7, 132, 195, 179, 18, 1, 13, 0, 14, 4, 95, 226, 128, 176, 107, 86, 52, 107, 55, 111, 49, 0, 22, 68, 36, 112, 90, 4, 37, 79, 106, 86, 106, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 15, 140, 11, 195, 188, 12, 195, 182, 14, 1, 4, 195, 179, 20, 13, 0, 16, 2, 95, 125, 82, 6, 111, 79, 49, 106, 48, 74, 39, 89, 0, 27, 35, 12, 7, 5, 14, 5, 18, 195, 161, 3, 9, 195, 179, 19, 79, 107, 50, 107, 52, 112, 117, 37, 113, 89, 10, 6, 15, 39, 49, 0, 13, 81, 111, 107, 32, 12, 137, 195, 182, 18, 195, 182, 11, 195, 182, 12, 13, 9, 134, 2, 195, 161, 3, 19, 9, 13, 15, 140, 7, 5, 14, 5, 18, 195, 161, 3, 9, 195, 179, 19, 13, 9, 134, 195, 161, 12, 12, 10, 1, 13, 8, 197, 48, 18, 206, 4, 176, 13, 8, 197, 44, 81, 4, 36, 112, 22, 0, 20, 2, 95, 124, 81, 109, 79, 12, 116, 55, 107, 79, 107, 89, 82, 39, 50, 106, 55, 0, 9, 198, 32, 145, 199, 100, 82, 192, 13, 9, 198, 44, 86, 133, 48, 146, 192, 13, 9, 198, 40, 21, 129, 76, 192, 84, 13, 9, 198, 77, 68, 133, 77, 54, 128, 13, 0, 13, 138, 22, 195, 169, 7, 26, 197, 145, 4, 9, 11, 13, 15, 140, 195, 182, 19, 19, 26, 5, 10, 195, 182, 14, 14, 9, 13, 0, 11, 200, 8, 84, 218, 21, 33, 90, 56, 144, 13, 33, 72, 53, 85, 1, 80, 179, 218, 36, 176, 63, 40, 47, 106, 47, 49, 39, 86, 37, 49, 10, 6, 15, 63, 107, 79, 0, 13, 81, 109, 101, 103, 32, 11, 200, 88, 243, 129, 80, 179, 218, 56, 16, 13, 11, 200, 4, 192, 75, 84, 195, 137, 84, 176, 13, 11, 136, 9, 7, 195, 169, 14, 25, 5, 12, 13, 11, 200, 88, 243, 129, 80, 179, 218, 36, 176, 13, 11, 200, 53, 85, 1, 80, 179, 218, 36, 176, 13, 0, 22, 6, 13, 195, 161, 19, 18, 1, 63, 112, 89, 52, 106, 23, 37, 89, 0, 13, 81, 105, 115, 32, 11, 136, 9, 7, 195, 169, 14, 25, 5, 11, 13, 9, 134, 22, 195, 161, 18, 10, 1, 13, 10, 135, 9, 14, 11, 195, 161, 2, 2, 13, 12, 137, 1, 7, 7, 195, 179, 4, 15, 20, 20, 13, 12, 137, 195, 173, 18, 195, 179, 4, 15, 20, 20, 13, 0, 7, 66, 105, 48, 88, 111, 0, 9, 198, 88, 17, 217, 80, 242, 192, 13, 14, 139, 1, 12, 10, 1, 19, 19, 195, 161, 7, 18, 1, 13, 10, 135, 22, 9, 20, 195, 161, 2, 1, 13, 9, 198, 60, 197, 129, 76, 226, 64, 13, 18, 70, 53, 97, 217, 61, 54, 128, 107, 63, 82, 111, 77, 111, 39, 107, 87, 0, 0, 10, 135, 10, 5, 12, 195, 182, 12, 20, 13, 11, 136, 5, 19, 26, 11, 195, 182, 26, 5, 13, 22, 147, 20, 195, 182, 18, 22, 195, 169, 14, 25, 10, 1, 22, 1, 19, 12, 1, 20, 15, 20, 13, 11, 136, 9, 18, 15, 4, 195, 161, 2, 1, 13, 15, 140, 2, 195, 173, 18, 195, 179, 19, 195, 161, 7, 18, 1, 13, 10, 135, 8, 195, 173, 22, 15, 20, 20, 13, 0, 27, 5, 5, 12, 19, 197, 145, 107, 55, 89, 116, 10, 6, 15, 111, 82, 107, 50, 0, 13, 81, 195, 169, 118, 101, 110, 32, 38, 5, 5, 12, 19, 197, 145, 107, 55, 89, 116, 23, 89, 39, 52, 69, 106, 50, 112, 55, 12, 113, 0, 13, 81, 115, 111, 114, 98, 97, 110, 195, 161, 108, 108, 195, 179, 32, 57, 72, 24, 83, 13, 85, 64, 84, 56, 144, 81, 107, 55, 63, 40, 47, 106, 47, 50, 37, 23, 106, 6, 15, 47, 112, 52, 77, 106, 55, 112, 89, 39, 49, 39, 50, 0, 13, 82, 97, 32, 116, 195, 161, 114, 103, 121, 97, 108, 195, 161, 115, 111, 107, 111, 110, 32, 8, 133, 5, 12, 19, 197, 145, 13, 11, 200, 81, 83, 1, 40, 242, 206, 4, 176, 13, 7, 196, 88, 148, 197, 48, 13, 0, 31, 10, 19, 26, 195, 161, 13, 21, 14, 11, 18, 1, 87, 112, 63, 40, 50, 49, 52, 106, 10, 6, 15, 106, 86, 0, 13, 81, 97, 122, 32, 12, 201, 24, 144, 84, 4, 195, 203, 56, 18, 192, 13, 12, 137, 9, 14, 4, 195, 173, 20, 15, 20, 20, 13, 13, 138, 19, 26, 195, 161, 13, 21, 14, 11, 18, 1, 13, 12, 201, 16, 243, 7, 61, 166, 129, 56, 18, 192, 13, 13, 138, 9, 18, 195, 161, 14, 25, 195, 161, 2, 1, 13, 0, 13, 138, 3, 19, 1, 12, 195, 179, 4, 15, 20, 20, 13, 59, 12, 10, 5, 12, 5, 14, 20, 197, 145, 19, 5, 2, 2, 57, 107, 55, 107, 50, 47, 116, 89, 107, 69, 12, 23, 74, 106, 48, 106, 70, 111, 49, 105, 40, 55, 12, 112, 89, 0, 13, 81, 99, 115, 97, 112, 97, 100, 195, 169, 107, 104, 117, 108, 108, 195, 161, 115, 32, 17, 198, 72, 244, 211, 105, 83, 0, 13, 81, 102, 117, 116, 111, 116, 116, 32, 15, 140, 6, 9, 14, 1, 14, 19, 26, 195, 173, 18, 15, 26, 13, 16, 141, 19, 26, 5, 18, 11, 5, 26, 5, 20, 197, 177, 5, 11, 13, 0, 19, 144, 14, 25, 9, 12, 22, 195, 161, 14, 15, 19, 19, 195, 161, 7, 18, 1, 13, 13, 138, 5, 19, 26, 11, 195, 182, 26, 195, 182, 11, 13, 14, 139, 11, 15, 18, 195, 161, 2, 2, 18, 195, 179, 12, 13, 14, 139, 19, 26, 195, 161, 13, 195, 173, 20, 15, 20, 20, 13, 0, 47, 13, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 18, 1, 47, 112, 63, 39, 79, 106, 47, 112, 89, 52, 106, 23, 57, 39, 79, 39, 89, 40, 55, 47, 0, 13, 81, 106, 111, 103, 111, 115, 117, 108, 116, 32, 21, 6, 11, 195, 182, 14, 25, 22, 49, 108, 65, 82, 23, 37, 89, 0, 13, 81, 105, 115, 32, 20, 145, 13, 5, 7, 11, 195, 182, 26, 5, 12, 195, 173, 20, 195, 169, 19, 18, 5, 13, 0, 9, 198, 80, 20, 148, 4, 195, 65, 13, 11, 136, 20, 5, 18, 22, 195, 188, 14, 11, 13, 7, 132, 11, 195, 169, 11, 13, 0, 41, 16, 12, 5, 7, 11, 195, 169, 14, 25, 5, 12, 13, 5, 19, 5, 2, 2, 55, 107, 79, 49, 111, 65, 107, 55, 63, 107, 89, 107, 69, 12, 23, 106, 86, 0, 13, 81, 97, 122, 32, 18, 143, 20, 1, 18, 20, 195, 179, 26, 11, 15, 4, 195, 161, 19, 18, 1, 13, 0, 9, 134, 20, 195, 182, 13, 9, 11, 13, 19, 144, 14, 25, 9, 12, 22, 195, 161, 14, 195, 173, 20, 195, 161, 19, 18, 1, 13, 0, 8, 133, 195, 188, 26, 5, 13, 13, 10, 135, 6, 195, 169, 12, 14, 5, 11, 13, 9, 134, 14, 195, 169, 22, 5, 14, 13, 9, 134, 20, 195, 169, 18, 5, 14, 13, 0, 24, 6, 8, 195, 173, 18, 5, 13, 105, 110, 52, 107, 63, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 10, 135, 12, 195, 169, 16, 10, 5, 14, 13, 0, 34, 9, 10, 195, 182, 8, 5, 20, 14, 5, 11, 57, 108, 105, 107, 47, 50, 107, 49, 23, 87, 113, 69, 106, 0, 13, 81, 115, 122, 195, 179, 98, 97, 32, 11, 136, 195, 169, 22, 5, 11, 2, 5, 14, 13, 12, 137, 13, 197, 177, 19, 15, 18, 14, 1, 11, 13, 9, 134, 13, 197, 177, 22, 5, 12, 13, 6, 195, 57, 147, 205, 13, 0, 16, 67, 53, 54, 144, 101, 109, 101, 115, 122, 112, 195, 169, 0, 29, 42, 9, 198, 44, 84, 133, 77, 65, 75, 13, 9, 134, 8, 195, 173, 18, 5, 11, 13, 13, 138, 13, 197, 177, 11, 195, 182, 4, 14, 5, 11, 13, 11, 136, 11, 195, 182, 22, 5, 20, 20, 5, 13, 9, 134, 197, 145, 18, 14, 5, 11, 13, 7, 132, 11, 195, 169, 13, 13, 6, 195, 53, 64, 64, 17, 0, 26, 5, 22, 195, 161, 7, 25, 82, 112, 77, 23, 111, 79, 107, 47, 12, 0, 13, 81, 195, 169, 103, 101, 116, 116, 32, 41, 10, 13, 5, 7, 25, 195, 169, 11, 2, 5, 14, 63, 107, 77, 111, 49, 69, 107, 50, 23, 82, 112, 52, 105, 106, 47, 113, 0, 13, 81, 118, 195, 161, 114, 104, 97, 116, 195, 179, 32, 10, 135, 20, 5, 18, 13, 195, 169, 11, 13, 15, 140, 20, 195, 161, 18, 19, 1, 4, 1, 12, 13, 1, 20, 13, 13, 138, 15, 18, 19, 26, 195, 161, 7, 2, 1, 14, 13, 8, 133, 22, 195, 161, 7, 25, 13, 7, 196, 48, 18, 201, 44, 13, 0, 9, 198, 32, 20, 131, 60, 195, 137, 13, 12, 137, 195, 186, 7, 25, 20, 197, 177, 14, 20, 13, 13, 138, 7, 25, 195, 161, 18, 20, 15, 20, 20, 1, 13, 6, 195, 88, 148, 218, 13, 9, 134, 20, 195, 161, 18, 7, 25, 13, 7, 132, 13, 195, 169, 7, 13, 18, 143, 3, 19, 195, 188, 20, 195, 182, 18, 20, 195, 182, 11, 195, 182, 14, 22, 0, 14, 139, 20, 1, 19, 26, 195, 173, 20, 15, 20, 20, 1, 13, 12, 137, 20, 21, 4, 10, 195, 161, 20, 15, 11, 13, 17, 66, 97, 128, 105, 114, 87, 12, 106, 55, 0, 44, 42, 81, 97, 108, 32, 23, 67, 97, 98, 73, 47, 37, 86, 107, 50, 105, 111, 47, 12, 107, 55, 0, 44, 42, 81, 101, 108, 32, 0, 13, 138, 19, 26, 195, 188, 12, 5, 20, 14, 5, 11, 13, 14, 203, 65, 35, 199, 72, 19, 74, 4, 146, 203, 4, 192, 13, 69, 13, 195, 186, 20, 13, 21, 20, 1, 20, 195, 179, 2, 1, 14, 114, 47, 63, 40, 47, 106, 47, 113, 69, 106, 50, 23, 37, 89, 23, 106, 87, 47, 23, 47, 106, 50, 112, 74, 39, 57, 57, 57, 112, 49, 0, 13, 83, 105, 115, 32, 97, 122, 116, 32, 116, 97, 110, 195, 161, 99, 115, 111, 108, 106, 195, 161, 107, 32, 16, 141, 12, 195, 161, 20, 15, 7, 1, 20, 195, 179, 2, 1, 14, 13, 10, 199, 16, 243, 7, 61, 165, 1, 44, 13, 6, 195, 85, 64, 76, 13, 0, 14, 139, 11, 195, 182, 22, 5, 20, 5, 12, 14, 5, 11, 13, 40, 14, 19, 26, 5, 18, 26, 197, 145, 4, 195, 169, 19, 2, 5, 14, 87, 107, 52, 86, 116, 70, 111, 89, 69, 107, 50, 23, 49, 107, 55, 12, 0, 13, 81, 107, 101, 108, 108, 32, 13, 138, 195, 169, 12, 5, 20, 195, 169, 2, 5, 14, 13, 13, 138, 20, 5, 13, 5, 20, 197, 145, 2, 5, 14, 13, 11, 136, 5, 19, 26, 11, 195, 182, 26, 20, 13, 22, 67, 97, 134, 0, 105, 106, 52, 63, 37, 50, 117, 12, 35, 55, 0, 44, 42, 81, 97, 108, 32, 0, 7, 195, 48, 84, 218, 72, 22, 30, 67, 48, 84, 218, 55, 107, 87, 23, 106, 57, 112, 50, 55, 39, 47, 12, 0, 13, 81, 97, 106, 195, 161, 110, 108, 111, 116, 116, 32, 25, 8, 8, 9, 19, 19, 26, 195, 188, 11, 105, 37, 87, 12, 109, 49, 23, 107, 55, 0, 13, 81, 101, 108, 32, 9, 134, 22, 195, 161, 7, 14, 9, 13, 13, 138, 20, 195, 161, 13, 15, 7, 1, 20, 20, 1, 13, 11, 136, 22, 195, 169, 12, 10, 195, 188, 11, 13, 8, 133, 6, 195, 188, 19, 20, 13, 0, 63, 14, 20, 5, 18, 22, 5, 26, 195, 169, 19, 195, 169, 22, 5, 12, 47, 107, 34, 82, 107, 86, 111, 89, 111, 82, 107, 55, 23, 81, 39, 79, 55, 106, 55, 49, 39, 86, 113, 23, 117, 111, 79, 0, 13, 82, 102, 111, 103, 108, 97, 108, 107, 111, 122, 195, 179, 32, 99, 195, 169, 103, 32, 9, 198, 37, 51, 69, 73, 97, 64, 13, 9, 198, 80, 83, 5, 57, 65, 64, 13, 12, 4, 95, 35, 51, 50, 87, 113, 49, 108, 86, 0, 0, 12, 201, 32, 149, 129, 80, 179, 218, 61, 69, 0, 13, 17, 142, 11, 195, 169, 16, 26, 197, 145, 4, 8, 5, 20, 14, 5, 11, 13, 16, 141, 20, 5, 18, 5, 12, 195, 169, 19, 195, 169, 2, 5, 14, 13, 16, 141, 13, 195, 169, 18, 20, 195, 169, 11, 195, 169, 2, 5, 14, 13, 0, 10, 135, 20, 197, 145, 12, 195, 188, 11, 13, 0, 18, 143, 20, 195, 182, 18, 20, 195, 169, 14, 5, 20, 195, 169, 2, 5, 14, 13, 18, 143, 13, 5, 7, 11, 195, 182, 20, 195, 169, 19, 195, 169, 2, 5, 14, 13, 18, 143, 19, 195, 188, 12, 12, 25, 5, 19, 26, 20, 197, 145, 2, 5, 14, 13, 11, 136, 9, 7, 1, 26, 19, 195, 161, 7, 13, 0, 21, 146, 22, 9, 19, 19, 26, 1, 20, 195, 169, 18, 195, 169, 19, 195, 169, 22, 5, 12, 13, 12, 137, 2, 5, 12, 197, 145, 12, 195, 188, 11, 13, 9, 198, 40, 83, 5, 105, 65, 64, 13, 9, 198, 44, 20, 3, 76, 243, 20, 13, 0, 9, 198, 8, 83, 69, 57, 65, 75, 13, 9, 134, 195, 169, 12, 14, 5, 11, 13, 13, 138, 8, 5, 12, 25, 26, 5, 20, 195, 188, 11, 13, 10, 135, 11, 195, 173, 22, 195, 188, 12, 13, 11, 136, 14, 195, 169, 8, 195, 161, 14, 25, 13, 23, 67, 97, 98, 64, 47, 37, 86, 107, 50, 105, 106, 47, 12, 106, 55, 0, 44, 42, 81, 97, 108, 32, 26, 67, 97, 98, 64, 47, 37, 86, 107, 50, 105, 106, 47, 39, 70, 37, 49, 37, 79, 0, 44, 42, 81, 105, 103, 32, 0, 7, 196, 21, 164, 133, 76, 13, 11, 200, 77, 160, 86, 5, 160, 84, 61, 64, 13, 18, 143, 13, 9, 14, 9, 19, 26, 20, 5, 18, 5, 12, 14, 195, 182, 11, 13, 12, 137, 2, 195, 188, 14, 20, 5, 20, 14, 9, 13, 26, 67, 96, 150, 0, 47, 37, 86, 107, 50, 49, 37, 55, 107, 50, 117, 12, 107, 55, 0, 44, 42, 81, 101, 108, 32, 0, 9, 134, 12, 195, 169, 16, 22, 5, 13, 12, 137, 15, 18, 19, 26, 195, 161, 7, 15, 20, 13, 8, 197, 64, 243, 148, 60, 176, 13, 0, 9, 198, 32, 83, 25, 21, 162, 64, 13, 9, 198, 40, 83, 5, 57, 66, 64, 13, 0, 11, 136, 6, 5, 8, 195, 169, 18, 2, 5, 13, 13, 138, 13, 21, 14, 11, 195, 161, 19, 14, 1, 11, 13, 15, 140, 22, 195, 161, 12, 20, 15, 26, 20, 1, 20, 14, 9, 13, 14, 139, 7, 1, 26, 4, 1, 19, 195, 161, 7, 15, 20, 13, 13, 138, 22, 195, 161, 12, 12, 1, 12, 14, 1, 11, 13, 10, 135, 20, 1, 12, 195, 161, 12, 20, 13, 8, 133, 6, 15, 11, 195, 186, 13, 10, 199, 20, 197, 5, 72, 161, 68, 80, 13, 6, 195, 64, 84, 212, 13, 8, 195, 53, 66, 64, 17, 42, 42, 0, 12, 137, 19, 26, 5, 18, 26, 197, 145, 10, 5, 13, 11, 136, 10, 15, 7, 195, 161, 22, 1, 12, 13, 18, 143, 18, 5, 14, 4, 5, 12, 12, 5, 14, 5, 19, 19, 195, 169, 7, 13, 0, 10, 135, 16, 15, 12, 3, 195, 161, 14, 13, 31, 9, 11, 195, 169, 19, 26, 195, 188, 12, 20, 49, 111, 87, 109, 55, 47, 23, 52, 113, 55, 106, 0, 13, 81, 114, 195, 179, 108, 97, 32, 12, 137, 20, 195, 169, 13, 195, 161, 22, 1, 12, 13, 8, 197, 28, 22, 132, 4, 112, 13, 9, 198, 52, 81, 212, 84, 66, 129, 13, 9, 198, 24, 241, 204, 4, 194, 129, 13, 16, 141, 13, 195, 169, 12, 20, 195, 179, 19, 195, 161, 7, 15, 20, 13, 11, 136, 20, 195, 173, 16, 21, 19, 15, 11, 13, 12, 137, 11, 9, 20, 1, 12, 195, 161, 12, 20, 13, 12, 137, 11, 195, 169, 19, 26, 195, 188, 12, 20, 13, 7, 132, 11, 195, 169, 19, 13, 9, 134, 195, 182, 19, 19, 26, 5, 13, 0, 64, 17, 195, 161, 12, 12, 1, 13, 20, 9, 20, 11, 195, 161, 18, 19, 195, 161, 7, 35, 55, 12, 106, 63, 47, 37, 47, 49, 112, 52, 89, 112, 79, 23, 47, 107, 34, 82, 107, 86, 107, 47, 111, 52, 116, 55, 0, 13, 81, 116, 101, 114, 118, 101, 122, 101, 116, 195, 169, 114, 197, 145, 108, 32, 6, 195, 4, 67, 129, 13, 9, 198, 32, 148, 132, 21, 66, 64, 13, 9, 198, 52, 243, 132, 81, 82, 192, 13, 7, 132, 11, 195, 169, 18, 13, 0, 12, 137, 20, 5, 18, 13, 195, 169, 2, 5, 14, 13, 9, 198, 40, 83, 5, 57, 66, 75, 13, 13, 138, 9, 19, 11, 15, 12, 195, 161, 19, 15, 11, 13, 13, 67, 5, 67, 64, 112, 47, 111, 107, 63, 0, 42, 42, 0, 9, 134, 195, 173, 7, 195, 169, 18, 13, 13, 138, 19, 5, 18, 5, 7, 195, 169, 2, 5, 14, 13, 10, 135, 2, 5, 14, 14, 195, 188, 11, 13, 17, 142, 11, 9, 195, 161, 12, 12, 195, 173, 20, 195, 161, 19, 15, 14, 13, 11, 136, 22, 1, 12, 195, 179, 19, 21, 12, 13, 15, 140, 20, 1, 18, 20, 1, 12, 13, 195, 161, 22, 1, 12, 13, 11, 136, 4, 18, 195, 161, 7, 21, 12, 20, 13, 7, 132, 11, 195, 169, 16, 13, 0, 17, 67, 80, 84, 218, 47, 107, 87, 15, 49, 37, 0, 13, 81, 107, 105, 32, 17, 142, 11, 195, 182, 18, 195, 188, 12, 13, 195, 169, 14, 25, 5, 9, 13, 6, 195, 80, 84, 218, 13, 0, 20, 145, 2, 9, 26, 15, 14, 25, 20, 1, 12, 1, 14, 19, 195, 161, 7, 15, 11, 13, 13, 138, 195, 182, 18, 195, 182, 11, 195, 182, 12, 20, 13, 13, 138, 11, 195, 182, 26, 20, 21, 4, 15, 20, 20, 13, 9, 198, 20, 118, 69, 80, 83, 64, 13, 0, 10, 199, 77, 162, 210, 37, 5, 5, 80, 13, 0, 18, 143, 13, 5, 7, 19, 26, 15, 18, 195, 173, 20, 195, 161, 19, 15, 11, 13, 19, 144, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 195, 161, 22, 1, 12, 13, 12, 137, 13, 197, 177, 11, 195, 182, 4, 197, 145, 13, 7, 132, 11, 195, 169, 20, 13, 0, 20, 145, 20, 1, 12, 195, 161, 12, 11, 15, 26, 195, 179, 10, 195, 161, 22, 1, 12, 13, 18, 143, 13, 1, 7, 25, 1, 18, 15, 18, 19, 26, 195, 161, 7, 15, 14, 13, 12, 137, 22, 1, 19, 195, 161, 18, 14, 1, 16, 20, 0, 21, 146, 195, 161, 12, 12, 1, 13, 20, 9, 20, 11, 195, 161, 18, 195, 161, 22, 1, 12, 13, 19, 144, 11, 195, 182, 26, 12, 5, 13, 195, 169, 14, 25, 195, 169, 2, 5, 14, 13, 7, 132, 7, 195, 161, 26, 13, 6, 195, 4, 67, 137, 13, 0, 11, 136, 9, 10, 5, 19, 26, 20, 197, 145, 13, 40, 8, 11, 195, 182, 18, 195, 188, 12, 9, 49, 108, 52, 109, 55, 37, 23, 108, 87, 12, 107, 79, 69, 116, 55, 0, 13, 81, 195, 182, 115, 115, 122, 101, 103, 98, 197, 145, 108, 32, 24, 4, 5, 12, 195, 169, 107, 55, 111, 23, 82, 107, 47, 37, 49, 0, 13, 81, 118, 101, 116, 105, 107, 32, 7, 132, 5, 12, 195, 169, 13, 0, 7, 196, 81, 81, 15, 44, 76, 44, 6, 18, 1, 14, 7, 195, 186, 52, 106, 50, 79, 114, 23, 47, 37, 87, 47, 82, 37, 89, 107, 55, 116, 57, 107, 0, 13, 81, 116, 105, 115, 122, 116, 118, 105, 115, 101, 108, 197, 145, 106, 101, 32, 11, 136, 22, 195, 161, 7, 25, 1, 9, 20, 13, 0, 12, 201, 24, 145, 217, 20, 195, 69, 105, 65, 84, 13, 16, 141, 22, 195, 169, 12, 5, 13, 195, 169, 14, 25, 195, 169, 20, 13, 0, 0, 10, 135, 2, 1, 14, 195, 161, 14, 20, 13, 9, 134, 195, 173, 18, 14, 1, 11, 13, 11, 136, 20, 195, 161, 13, 1, 4, 20, 1, 13, 6, 195, 9, 34, 84, 13, 10, 135, 6, 18, 195, 161, 19, 26, 20, 13, 0, 13, 138, 195, 161, 12, 12, 195, 161, 19, 2, 1, 14, 13, 8, 133, 14, 195, 161, 12, 1, 13, 0, 41, 8, 11, 195, 182, 14, 25, 22, 5, 11, 49, 108, 65, 82, 107, 49, 23, 55, 112, 47, 105, 106, 47, 39, 106, 49, 0, 13, 81, 108, 195, 161, 116, 104, 97, 116, 195, 179, 97, 107, 32, 26, 69, 44, 148, 197, 8, 32, 49, 37, 89, 12, 107, 69, 12, 23, 107, 89, 116, 0, 13, 81, 101, 115, 197, 145, 32, 13, 138, 5, 13, 12, 195, 173, 20, 5, 20, 20, 5, 13, 11, 136, 195, 161, 18, 21, 12, 14, 1, 11, 13, 11, 136, 11, 195, 182, 14, 25, 22, 5, 11, 13, 0, 11, 136, 22, 9, 20, 195, 161, 2, 1, 14, 13, 33, 70, 60, 193, 1, 49, 32, 64, 39, 55, 70, 106, 55, 52, 106, 6, 15, 69, 40, 49, 12, 106, 50, 0, 13, 81, 98, 117, 107, 107, 97, 110, 32, 14, 139, 8, 15, 26, 26, 195, 161, 20, 5, 20, 20, 5, 13, 13, 138, 20, 1, 18, 9, 6, 195, 161, 22, 1, 12, 13, 12, 137, 12, 195, 169, 20, 5, 26, 14, 5, 11, 13, 14, 139, 195, 161, 12, 12, 195, 173, 20, 15, 20, 20, 1, 13, 9, 198, 60, 193, 1, 49, 32, 64, 13, 0, 14, 139, 4, 15, 2, 195, 161, 19, 195, 161, 22, 1, 12, 13, 12, 137, 6, 15, 18, 13, 195, 161, 2, 1, 14, 13, 16, 141, 11, 195, 169, 18, 4, 195, 169, 19, 5, 11, 2, 5, 14, 13, 51, 9, 6, 15, 18, 13, 195, 161, 2, 1, 14, 81, 39, 52, 63, 112, 69, 106, 50, 23, 106, 6, 15, 47, 107, 52, 82, 107, 86, 107, 47, 69, 107, 50, 0, 13, 82, 97, 32, 116, 101, 114, 118, 101, 122, 101, 116, 98, 101, 110, 32, 6, 195, 20, 197, 128, 13, 9, 198, 29, 144, 76, 60, 115, 211, 13, 16, 141, 11, 21, 20, 1, 20, 195, 161, 19, 15, 11, 2, 1, 14, 13, 8, 4, 95, 35, 45, 5, 107, 0, 0, 14, 139, 20, 195, 161, 18, 7, 25, 1, 12, 14, 1, 11, 13, 38, 7, 19, 26, 195, 179, 12, 195, 179, 87, 113, 55, 113, 23, 57, 106, 82, 106, 89, 55, 106, 47, 39, 47, 0, 13, 81, 106, 97, 118, 97, 115, 108, 97, 116, 111, 116, 32, 13, 138, 11, 5, 18, 5, 20, 195, 169, 2, 5, 14, 13, 7, 196, 81, 81, 15, 52, 13, 10, 135, 19, 26, 195, 179, 12, 195, 179, 13, 0, 14, 139, 8, 1, 20, 195, 161, 19, 195, 161, 2, 1, 14, 13, 15, 140, 195, 182, 19, 19, 26, 5, 195, 188, 12, 14, 5, 11, 13, 8, 197, 20, 193, 71, 21, 64, 13, 8, 197, 40, 241, 193, 37, 64, 13, 16, 141, 18, 195, 169, 19, 26, 12, 5, 7, 195, 169, 22, 5, 12, 13, 8, 197, 57, 147, 205, 77, 160, 13, 9, 134, 20, 195, 182, 13, 14, 9, 13, 8, 197, 41, 85, 15, 81, 64, 13, 0, 15, 140, 195, 169, 18, 20, 5, 12, 13, 195, 169, 2, 5, 14, 13, 18, 143, 11, 9, 5, 7, 195, 169, 19, 26, 195, 173, 20, 5, 20, 20, 5, 13, 15, 140, 21, 20, 1, 12, 22, 195, 161, 14, 25, 2, 1, 14, 13, 12, 137, 19, 26, 5, 18, 4, 195, 161, 9, 7, 22, 0, 72, 73, 24, 83, 142, 80, 20, 148, 61, 69, 0, 81, 107, 50, 12, 47, 106, 52, 47, 39, 47, 12, 23, 37, 89, 49, 39, 55, 112, 49, 23, 63, 109, 49, 108, 47, 12, 107, 47, 111, 89, 111, 47, 0, 13, 82, 105, 115, 107, 111, 108, 195, 161, 107, 32, 109, 197, 177, 107, 195, 182, 100, 116, 101, 116, 195, 169, 115, 195, 169, 116, 32, 16, 141, 20, 5, 11, 9, 14, 20, 5, 20, 195, 169, 2, 5, 14, 13, 13, 138, 9, 7, 1, 26, 19, 195, 161, 7, 15, 19, 13, 16, 141, 2, 197, 177, 14, 20, 5, 20, 20, 195, 169, 2, 5, 14, 13, 9, 134, 22, 5, 12, 195, 188, 11, 13, 6, 195, 29, 5, 64, 17, 9, 4, 95, 35, 45, 1, 106, 0, 21, 0, 0, 8, 197, 4, 64, 84, 61, 64, 13, 11, 136, 14, 25, 195, 186, 10, 20, 195, 179, 13, 16, 141, 22, 195, 161, 12, 20, 15, 26, 1, 20, 2, 195, 179, 12, 13, 20, 145, 19, 20, 18, 1, 20, 195, 169, 7, 9, 195, 161, 10, 195, 161, 22, 1, 12, 13, 11, 136, 19, 26, 20, 18, 195, 161, 10, 11, 13, 0, 19, 144, 11, 195, 169, 16, 22, 9, 19, 5, 12, 5, 20, 195, 169, 2, 5, 14, 13, 19, 144, 1, 12, 11, 1, 12, 13, 1, 26, 195, 161, 19, 195, 161, 2, 1, 14, 13, 12, 137, 10, 5, 12, 5, 14, 19, 195, 169, 7, 13, 12, 137, 8, 5, 12, 25, 9, 19, 195, 169, 7, 13, 0, 28, 5, 20, 195, 182, 2, 2, 47, 108, 69, 12, 23, 39, 52, 87, 112, 79, 0, 13, 81, 111, 114, 115, 122, 195, 161, 103, 32, 79, 5, 20, 195, 182, 2, 2, 47, 108, 69, 12, 23, 105, 107, 57, 107, 50, 23, 87, 106, 49, 106, 70, 39, 86, 37, 49, 23, 81, 107, 55, 23, 106, 23, 81, 107, 55, 105, 116, 86, 107, 47, 0, 13, 85, 104, 101, 108, 121, 101, 110, 32, 115, 122, 97, 107, 97, 100, 111, 122, 105, 107, 32, 102, 101, 108, 32, 97, 32, 102, 101, 108, 104, 197, 145, 122, 101, 116, 32, 49, 5, 20, 195, 182, 2, 2, 47, 108, 69, 12, 23, 81, 107, 55, 105, 116, 23, 82, 106, 55, 113, 87, 110, 50, 115, 0, 13, 82, 102, 101, 108, 104, 197, 145, 32, 118, 97, 108, 195, 179, 115, 122, 195, 173, 110, 197, 177, 32, 26, 67, 85, 64, 84, 40, 47, 106, 47, 15, 49, 106, 48, 39, 47, 12, 0, 13, 81, 107, 97, 112, 111, 116, 116, 32, 8, 133, 20, 195, 182, 2, 2, 13, 0, 9, 198, 80, 17, 207, 104, 21, 0, 13, 6, 195, 85, 64, 83, 13, 7, 196, 4, 197, 68, 80, 13, 7, 196, 81, 81, 10, 4, 13, 9, 134, 14, 25, 1, 11, 195, 186, 13, 7, 196, 81, 81, 14, 36, 13, 0, 8, 197, 48, 84, 218, 20, 176, 72, 26, 5, 22, 195, 161, 12, 20, 82, 112, 55, 47, 23, 82, 39, 55, 50, 106, 0, 13, 81, 118, 111, 108, 110, 97, 32, 8, 197, 80, 81, 217, 20, 176, 13, 22, 133, 22, 195, 161, 12, 20, 13, 81, 104, 105, 118, 97, 116, 97, 108, 111, 115, 115, 195, 161, 32, 9, 134, 11, 195, 182, 26, 2, 5, 13, 8, 133, 22, 195, 161, 12, 20, 13, 0, 9, 198, 4, 176, 82, 41, 82, 192, 13, 0, 12, 137, 195, 179, 18, 195, 161, 11, 2, 1, 14, 13, 12, 137, 22, 9, 12, 195, 161, 7, 2, 1, 14, 13, 9, 134, 195, 182, 14, 14, 5, 11, 13, 6, 195, 32, 244, 16, 13, 10, 4, 95, 35, 45, 9, 107, 37, 0, 21, 0, 43, 68, 80, 17, 202, 4, 47, 106, 79, 57, 106, 23, 37, 89, 23, 74, 106, 47, 55, 106, 49, 39, 86, 37, 49, 0, 13, 82, 105, 115, 32, 99, 115, 97, 116, 108, 97, 107, 111, 122, 105, 107, 32, 7, 196, 80, 17, 202, 4, 13, 11, 200, 52, 243, 132, 32, 21, 10, 84, 176, 13, 0, 10, 135, 11, 195, 169, 18, 10, 5, 14, 13, 12, 137, 195, 169, 18, 4, 5, 11, 5, 12, 20, 13, 14, 139, 5, 12, 5, 13, 26, 197, 145, 11, 2, 5, 14, 13, 9, 134, 19, 195, 161, 22, 2, 1, 13, 12, 201, 28, 243, 132, 60, 192, 84, 80, 19, 0, 13, 15, 140, 20, 5, 19, 20, 195, 188, 12, 5, 20, 14, 5, 11, 13, 9, 134, 13, 195, 186, 12, 22, 1, 13, 8, 197, 88, 148, 211, 104, 16, 13, 0, 10, 135, 22, 9, 20, 195, 161, 10, 1, 13, 15, 140, 19, 26, 195, 182, 22, 5, 7, 5, 11, 2, 5, 14, 13, 42, 8, 6, 5, 12, 195, 169, 2, 5, 14, 81, 107, 55, 111, 69, 107, 50, 23, 112, 55, 105, 106, 47, 6, 15, 69, 6, 107, 0, 13, 82, 195, 161, 108, 108, 104, 97, 116, 32, 98, 101, 32, 0, 23, 7, 19, 26, 195, 179, 22, 1, 12, 87, 113, 82, 106, 55, 23, 106, 86, 0, 13, 81, 97, 122, 32, 16, 141, 11, 15, 14, 3, 5, 16, 3, 9, 195, 179, 2, 1, 14, 13, 10, 135, 19, 26, 195, 179, 22, 1, 12, 13, 16, 141, 8, 5, 12, 25, 19, 195, 169, 7, 5, 11, 2, 5, 14, 13, 10, 135, 19, 26, 195, 179, 22, 1, 12, 13, 7, 132, 1, 12, 195, 161, 13, 0, 31, 70, 77, 163, 198, 81, 97, 82, 87, 39, 81, 47, 82, 107, 52, 23, 50, 107, 82, 111, 47, 0, 13, 81, 110, 101, 118, 195, 169, 116, 32, 12, 137, 14, 1, 16, 20, 195, 161, 18, 2, 1, 13, 11, 200, 53, 85, 15, 28, 21, 10, 84, 176, 13, 11, 200, 24, 83, 11, 21, 33, 83, 56, 144, 13, 11, 200, 20, 193, 143, 28, 17, 20, 4, 176, 13, 0, 9, 134, 11, 5, 26, 4, 197, 145, 13, 0, 17, 142, 22, 195, 173, 22, 13, 195, 161, 14, 25, 1, 9, 22, 1, 12, 13, 19, 144, 10, 15, 7, 19, 26, 1, 2, 195, 161, 12, 25, 15, 11, 2, 1, 14, 13, 0, 14, 203, 57, 145, 82, 76, 19, 153, 4, 115, 203, 72, 16, 13, 10, 199, 24, 147, 13, 20, 178, 197, 48, 13, 10, 199, 77, 161, 82, 36, 229, 5, 52, 13, 9, 134, 20, 195, 173, 16, 21, 19, 13, 0, 12, 137, 11, 195, 182, 20, 5, 14, 4, 197, 145, 13, 11, 136, 6, 5, 8, 195, 169, 18, 5, 20, 13, 0, 13, 138, 6, 5, 12, 195, 188, 7, 25, 5, 12, 9, 13, 12, 201, 57, 146, 76, 5, 66, 207, 104, 245, 20, 13, 0, 13, 138, 22, 195, 169, 4, 5, 12, 13, 195, 169, 20, 13, 13, 138, 19, 26, 195, 161, 13, 12, 195, 161, 9, 20, 13, 9, 198, 4, 194, 207, 80, 245, 20, 13, 0, 0, 27, 68, 81, 81, 20, 4, 47, 40, 47, 12, 106, 6, 15, 82, 39, 55, 50, 106, 0, 13, 81, 118, 111, 108, 110, 97, 32, 47, 12, 11, 195, 169, 18, 4, 197, 145, 195, 173, 22, 5, 20, 49, 111, 52, 70, 116, 110, 82, 107, 47, 23, 49, 111, 87, 110, 47, 107, 50, 37, 0, 13, 81, 107, 195, 169, 115, 122, 195, 173, 116, 101, 110, 105, 32, 49, 12, 11, 195, 169, 18, 4, 197, 145, 195, 173, 22, 5, 20, 49, 111, 52, 70, 116, 110, 82, 107, 47, 23, 49, 111, 87, 110, 47, 107, 50, 107, 49, 0, 13, 81, 107, 195, 169, 115, 122, 195, 173, 116, 101, 110, 101, 107, 32, 9, 198, 12, 146, 204, 60, 229, 0, 13, 15, 140, 11, 195, 169, 18, 4, 197, 145, 195, 173, 22, 5, 20, 13, 7, 196, 81, 81, 20, 4, 13, 8, 133, 6, 5, 12, 195, 169, 13, 0, 8, 197, 48, 84, 218, 20, 192, 72, 9, 198, 24, 244, 132, 84, 195, 137, 13, 11, 136, 20, 1, 18, 20, 19, 195, 161, 11, 13, 24, 149, 195, 188, 7, 25, 6, 5, 12, 5, 11, 36, 21, 14, 19, 20, 18, 5, 19, 19, 5, 14, 4, 13, 9, 198, 24, 83, 20, 20, 227, 137, 13, 9, 198, 32, 83, 25, 21, 163, 137, 13, 9, 198, 24, 244, 132, 84, 195, 137, 13, 9, 198, 32, 83, 25, 21, 163, 137, 13, 13, 138, 19, 26, 1, 11, 195, 169, 18, 20, 197, 145, 13, 0, 27, 9, 2, 195, 161, 14, 20, 19, 195, 161, 11, 69, 112, 50, 74, 112, 49, 23, 116, 47, 0, 13, 81, 197, 145, 116, 32, 7, 132, 13, 195, 161, 10, 20, 0, 0, 13, 138, 195, 161, 12, 12, 1, 16, 15, 20, 195, 186, 13, 7, 196, 84, 118, 65, 56, 13, 23, 7, 195, 161, 19, 20, 195, 161, 11, 112, 89, 47, 112, 49, 23, 107, 55, 0, 13, 81, 101, 108, 32, 7, 196, 40, 241, 207, 44, 13, 0, 16, 141, 5, 7, 195, 169, 19, 26, 19, 195, 169, 7, 195, 169, 20, 13, 11, 136, 8, 195, 173, 22, 10, 195, 161, 11, 13, 38, 69, 12, 146, 204, 60, 224, 117, 37, 49, 55, 39, 50, 23, 47, 106, 55, 112, 55, 105, 106, 47, 113, 0, 13, 81, 116, 97, 108, 195, 161, 108, 104, 97, 116, 195, 179, 32, 13, 138, 11, 195, 169, 18, 4, 195, 169, 19, 5, 13, 13, 8, 197, 48, 81, 217, 20, 224, 13, 0, 12, 137, 11, 195, 173, 19, 195, 169, 18, 9, 11, 13, 17, 142, 5, 12, 8, 5, 12, 25, 5, 26, 195, 169, 19, 195, 169, 20, 13, 0, 16, 141, 5, 7, 25, 5, 26, 20, 5, 20, 195, 169, 19, 5, 14, 13, 16, 141, 5, 7, 25, 5, 26, 20, 5, 20, 195, 169, 19, 5, 14, 13, 36, 13, 5, 7, 25, 5, 26, 20, 5, 20, 195, 169, 19, 5, 14, 107, 77, 12, 107, 87, 47, 107, 47, 111, 89, 107, 50, 23, 37, 89, 0, 13, 81, 105, 115, 32, 13, 138, 10, 1, 22, 195, 173, 20, 10, 195, 161, 11, 13, 13, 138, 10, 1, 22, 195, 173, 20, 10, 195, 161, 11, 13, 0, 14, 139, 13, 15, 14, 4, 8, 1, 20, 14, 195, 161, 11, 13, 0, 9, 198, 24, 148, 148, 5, 69, 129, 13, 8, 197, 64, 144, 67, 61, 64, 13, 13, 138, 11, 195, 169, 18, 4, 195, 169, 19, 5, 9, 13, 0, 17, 142, 7, 25, 195, 179, 7, 25, 19, 26, 5, 18, 2, 197, 145, 12, 13, 16, 141, 20, 5, 12, 5, 16, 195, 188, 12, 195, 169, 19, 5, 11, 13, 0, 10, 135, 1, 12, 22, 195, 161, 19, 20, 13, 14, 139, 11, 195, 169, 18, 4, 195, 169, 19, 19, 5, 12, 13, 0, 7, 196, 40, 241, 207, 52, 13, 8, 133, 14, 197, 145, 14, 9, 13, 11, 136, 18, 195, 186, 7, 195, 161, 19, 20, 13, 0, 30, 10, 11, 1, 20, 5, 7, 195, 179, 18, 9, 1, 49, 106, 47, 107, 79, 113, 52, 37, 106, 23, 37, 89, 0, 13, 81, 105, 115, 32, 13, 138, 11, 1, 20, 5, 7, 195, 179, 18, 9, 1, 13, 19, 144, 20, 195, 161, 10, 195, 169, 11, 15, 26, 20, 1, 20, 20, 195, 161, 11, 13, 11, 136, 22, 15, 12, 14, 195, 161, 14, 11, 13, 0, 14, 139, 13, 5, 7, 7, 25, 197, 145, 26, 14, 9, 5, 13, 9, 198, 20, 194, 78, 17, 83, 20, 13, 13, 138, 5, 12, 10, 195, 161, 18, 195, 161, 19, 20, 13, 0, 13, 138, 8, 1, 19, 26, 14, 195, 161, 12, 195, 179, 13, 0, 9, 198, 40, 83, 5, 44, 85, 0, 13, 25, 68, 36, 198, 69, 56, 37, 57, 107, 50, 10, 6, 15, 69, 39, 55, 47, 0, 13, 81, 98, 111, 108, 116, 32, 31, 68, 60, 198, 65, 56, 39, 57, 106, 50, 10, 6, 15, 49, 111, 52, 70, 111, 89, 0, 13, 81, 107, 195, 169, 114, 100, 195, 169, 115, 32, 11, 136, 19, 20, 18, 195, 161, 6, 15, 20, 13, 23, 68, 36, 198, 69, 56, 37, 57, 107, 50, 15, 87, 111, 48, 0, 13, 81, 115, 122, 195, 169, 112, 32, 9, 134, 22, 195, 169, 7, 5, 26, 13, 7, 196, 60, 198, 65, 56, 13, 13, 4, 95, 49, 17, 24, 107, 55, 89, 107, 57, 107, 0, 0, 27, 69, 57, 146, 84, 56, 144, 65, 37, 47, 50, 37, 23, 106, 49, 12, 39, 52, 0, 13, 81, 97, 107, 107, 111, 114, 32, 8, 197, 57, 146, 84, 40, 16, 13, 8, 197, 88, 84, 218, 20, 208, 13, 43, 12, 11, 9, 19, 26, 15, 12, 7, 195, 161, 12, 195, 179, 49, 37, 87, 39, 55, 79, 112, 55, 113, 23, 57, 112, 52, 106, 47, 106, 37, 0, 13, 81, 106, 195, 161, 114, 97, 116, 97, 105, 32, 15, 140, 11, 9, 19, 26, 15, 12, 7, 195, 161, 12, 195, 179, 13, 0, 11, 136, 195, 188, 12, 195, 169, 19, 5, 14, 13, 8, 133, 4, 9, 195, 161, 11, 13, 9, 198, 16, 243, 7, 84, 176, 84, 13, 0, 12, 137, 12, 1, 11, 195, 161, 19, 2, 1, 14, 13, 29, 6, 13, 195, 161, 19, 9, 11, 63, 112, 89, 37, 49, 10, 6, 15, 47, 111, 63, 106, 0, 13, 81, 116, 195, 169, 109, 97, 32, 10, 199, 77, 160, 75, 61, 37, 143, 76, 13, 0, 40, 6, 18, 195, 169, 7, 5, 14, 52, 111, 79, 107, 50, 23, 49, 37, 47, 106, 55, 112, 55, 47, 112, 49, 0, 13, 81, 107, 105, 116, 97, 108, 195, 161, 108, 116, 195, 161, 107, 32, 13, 138, 195, 182, 19, 19, 26, 5, 7, 2, 5, 14, 13, 41, 68, 40, 241, 210, 4, 57, 39, 79, 52, 106, 23, 82, 112, 55, 47, 39, 87, 47, 106, 47, 39, 47, 12, 0, 13, 81, 118, 195, 161, 108, 116, 111, 122, 116, 97, 116, 111, 116, 116, 32, 11, 136, 5, 26, 5, 12, 197, 145, 20, 20, 13, 11, 200, 88, 148, 197, 48, 177, 68, 36, 176, 13, 11, 200, 88, 148, 197, 48, 177, 68, 36, 176, 13, 8, 133, 195, 173, 18, 10, 1, 13, 7, 196, 4, 67, 212, 80, 13, 0, 11, 136, 22, 195, 161, 18, 10, 195, 161, 11, 13, 13, 138, 13, 195, 169, 18, 14, 195, 182, 11, 5, 9, 13, 8, 197, 72, 82, 140, 36, 176, 13, 12, 137, 13, 9, 12, 12, 9, 195, 161, 18, 4, 13, 35, 9, 13, 9, 12, 12, 9, 195, 161, 18, 4, 63, 37, 55, 37, 112, 52, 70, 23, 81, 39, 52, 37, 50, 47, 0, 13, 81, 102, 111, 114, 105, 110, 116, 32, 8, 197, 52, 144, 84, 80, 16, 13, 8, 197, 81, 81, 10, 84, 176, 13, 8, 197, 44, 86, 132, 80, 80, 13, 8, 197, 52, 243, 132, 40, 16, 13, 0, 14, 139, 7, 25, 195, 179, 7, 25, 20, 15, 18, 14, 1, 13, 52, 8, 195, 161, 7, 195, 161, 2, 1, 14, 112, 79, 112, 69, 106, 50, 15, 89, 37, 50, 74, 15, 55, 107, 74, 107, 52, 111, 55, 50, 37, 0, 13, 82, 115, 105, 110, 99, 115, 32, 108, 101, 99, 115, 101, 114, 195, 169, 108, 110, 105, 32, 7, 132, 11, 195, 161, 18, 13, 12, 4, 13, 195, 161, 22, 63, 112, 82, 0, 42, 42, 0, 12, 137, 13, 21, 14, 11, 195, 161, 2, 1, 14, 13, 14, 139, 20, 5, 12, 5, 6, 15, 14, 195, 161, 12, 20, 13, 12, 137, 12, 9, 19, 20, 195, 161, 2, 1, 14, 13, 17, 142, 6, 15, 18, 18, 195, 161, 19, 11, 195, 179, 4, 14, 1, 11, 13, 7, 132, 5, 12, 197, 145, 13, 7, 132, 5, 12, 197, 145, 13, 0, 13, 138, 9, 19, 11, 15, 12, 195, 161, 2, 1, 14, 13, 7, 132, 19, 195, 173, 16, 13, 0, 11, 136, 20, 5, 19, 19, 26, 195, 188, 11, 13, 31, 11, 195, 182, 14, 13, 1, 7, 195, 161, 2, 1, 14, 108, 50, 63, 106, 79, 112, 69, 106, 50, 23, 106, 86, 0, 13, 81, 97, 122, 32, 49, 4, 13, 195, 161, 19, 63, 112, 89, 23, 87, 107, 63, 55, 111, 55, 107, 47, 107, 47, 23, 49, 108, 82, 107, 47, 0, 13, 82, 115, 122, 101, 109, 108, 195, 169, 108, 101, 116, 101, 116, 32, 107, 195, 182, 118, 101, 116, 32, 20, 4, 13, 195, 161, 19, 63, 112, 89, 23, 89, 107, 63, 0, 13, 81, 115, 101, 109, 32, 27, 4, 13, 195, 161, 19, 63, 112, 89, 23, 79, 111, 48, 12, 107, 55, 0, 13, 81, 103, 195, 169, 112, 112, 101, 108, 32, 14, 139, 195, 169, 18, 4, 5, 11, 195, 169, 2, 5, 14, 13, 14, 139, 195, 169, 18, 4, 5, 11, 195, 169, 2, 5, 14, 13, 7, 132, 13, 195, 161, 19, 13, 0, 25, 4, 13, 195, 161, 18, 63, 112, 52, 10, 6, 15, 106, 48, 52, 113, 0, 13, 81, 97, 112, 114, 195, 179, 32, 32, 4, 13, 195, 161, 18, 63, 112, 52, 10, 6, 15, 107, 55, 111, 52, 47, 111, 49, 0, 13, 81, 101, 108, 195, 169, 114, 116, 195, 169, 107, 32, 50, 4, 13, 195, 161, 18, 63, 112, 52, 10, 6, 15, 49, 107, 82, 111, 89, 69, 111, 10, 6, 15, 105, 106, 55, 12, 106, 50, 37, 0, 13, 82, 107, 101, 118, 195, 169, 115, 98, 195, 169, 32, 104, 97, 108, 108, 97, 110, 105, 32, 35, 4, 13, 195, 161, 18, 63, 112, 52, 23, 55, 107, 105, 107, 74, 12, 111, 79, 107, 89, 0, 13, 81, 108, 101, 104, 101, 116, 115, 195, 169, 103, 101, 115, 32, 33, 4, 13, 195, 161, 18, 63, 112, 52, 23, 63, 107, 79, 87, 39, 49, 39, 47, 12, 0, 13, 81, 109, 101, 103, 115, 122, 111, 107, 111, 116, 116, 32, 28, 6, 2, 5, 12, 195, 188, 12, 69, 107, 55, 109, 55, 23, 63, 106, 52, 106, 70, 0, 13, 81, 109, 97, 114, 97, 100, 32, 33, 4, 13, 195, 161, 18, 63, 112, 52, 23, 49, 39, 52, 112, 69, 52, 113, 55, 0, 13, 81, 107, 111, 114, 195, 161, 98, 98, 114, 195, 179, 108, 32, 24, 4, 13, 195, 161, 18, 63, 112, 52, 15, 89, 39, 49, 106, 47, 0, 13, 81, 115, 111, 107, 97, 116, 32, 9, 134, 6, 5, 12, 195, 188, 12, 13, 13, 138, 2, 5, 12, 5, 19, 26, 195, 179, 12, 20, 13, 9, 134, 2, 5, 12, 195, 188, 12, 13, 17, 142, 13, 197, 177, 11, 195, 182, 4, 195, 169, 19, 18, 197, 145, 12, 13, 7, 132, 13, 195, 161, 18, 13, 0, 18, 143, 2, 195, 182, 14, 7, 195, 169, 19, 26, 197, 145, 2, 197, 145, 12, 13, 10, 199, 13, 51, 206, 80, 242, 193, 80, 13, 0, 12, 137, 22, 5, 19, 26, 197, 145, 4, 14, 9, 13, 19, 144, 11, 195, 169, 19, 26, 195, 173, 20, 195, 169, 19, 195, 169, 22, 5, 12, 13, 11, 136, 11, 195, 182, 14, 25, 22, 5, 20, 13, 11, 136, 20, 195, 161, 13, 15, 7, 1, 20, 13, 16, 141, 6, 18, 1, 11, 3, 9, 195, 179, 10, 195, 161, 18, 1, 13, 7, 196, 53, 85, 1, 80, 13, 0, 9, 134, 12, 195, 169, 16, 14, 9, 13, 8, 133, 19, 26, 195, 188, 12, 13, 0, 25, 70, 32, 19, 135, 104, 245, 20, 105, 106, 50, 79, 86, 39, 47, 12, 23, 107, 55, 0, 13, 81, 101, 108, 32, 27, 70, 32, 19, 135, 104, 245, 20, 105, 106, 50, 79, 86, 39, 47, 12, 10, 6, 15, 107, 55, 0, 13, 81, 101, 108, 32, 9, 198, 77, 161, 76, 48, 83, 64, 13, 41, 7, 12, 1, 11, 195, 161, 19, 1, 55, 106, 49, 112, 89, 106, 23, 77, 40, 55, 12, 106, 47, 12, 23, 49, 37, 0, 13, 82, 103, 121, 117, 108, 108, 97, 100, 116, 32, 107, 105, 32, 10, 135, 5, 12, 14, 195, 182, 11, 5, 13, 23, 6, 22, 195, 169, 7, 5, 20, 82, 111, 79, 107, 47, 23, 111, 52, 0, 13, 81, 195, 169, 114, 32, 13, 138, 2, 1, 18, 195, 161, 20, 10, 195, 161, 20, 13, 9, 134, 22, 195, 169, 7, 5, 20, 13, 11, 136, 15, 11, 20, 195, 179, 2, 5, 18, 20, 0, 32, 67, 4, 210, 84, 106, 63, 37, 47, 23, 105, 106, 87, 50, 112, 55, 39, 49, 0, 13, 81, 104, 97, 115, 122, 110, 195, 161, 108, 111, 107, 32, 18, 143, 8, 1, 10, 12, 195, 169, 11, 20, 1, 12, 1, 14, 14, 1, 12, 13, 11, 136, 19, 26, 1, 2, 195, 161, 12, 25, 13, 14, 67, 16, 228, 192, 70, 111, 107, 50, 107, 89, 0, 42, 42, 0, 11, 136, 14, 195, 169, 26, 5, 7, 5, 20, 13, 11, 136, 13, 195, 179, 4, 10, 195, 161, 20, 13, 0, 13, 138, 20, 195, 161, 13, 15, 7, 1, 20, 14, 9, 13, 11, 136, 20, 195, 182, 13, 5, 7, 5, 11, 13, 9, 198, 44, 81, 22, 20, 224, 197, 13, 12, 137, 16, 195, 161, 18, 20, 10, 195, 161, 20, 13, 11, 136, 19, 26, 197, 177, 18, 197, 145, 11, 13, 8, 133, 22, 195, 161, 18, 20, 13, 0, 10, 135, 13, 195, 169, 4, 9, 21, 13, 13, 12, 137, 13, 21, 20, 1, 20, 10, 195, 161, 11, 13, 9, 198, 4, 192, 80, 40, 18, 84, 13, 0, 14, 139, 4, 195, 182, 14, 20, 195, 169, 19, 195, 169, 20, 13, 10, 199, 65, 35, 196, 84, 49, 82, 20, 13, 18, 143, 8, 1, 19, 15, 14, 12, 195, 173, 20, 7, 1, 20, 14, 15, 4, 13, 0, 16, 141, 11, 15, 18, 12, 195, 161, 20, 15, 26, 195, 161, 19, 1, 13, 14, 139, 22, 195, 161, 18, 8, 1, 20, 195, 179, 1, 11, 13, 14, 139, 12, 195, 161, 20, 8, 1, 20, 195, 179, 1, 11, 13, 10, 135, 195, 173, 18, 14, 195, 161, 11, 13, 11, 200, 32, 83, 25, 104, 85, 2, 20, 224, 13, 0, 15, 140, 20, 195, 161, 13, 15, 7, 1, 20, 14, 195, 161, 11, 13, 15, 140, 15, 12, 22, 1, 19, 8, 1, 20, 10, 195, 161, 11, 13, 16, 141, 6, 5, 12, 5, 12, 197, 145, 19, 195, 169, 7, 5, 20, 13, 14, 139, 22, 1, 19, 195, 161, 18, 14, 1, 16, 15, 14, 22, 0, 60, 14, 10, 5, 12, 5, 14, 20, 197, 145, 19, 195, 169, 7, 5, 20, 57, 107, 55, 107, 50, 47, 116, 89, 111, 79, 107, 47, 23, 47, 40, 55, 106, 57, 70, 39, 50, 110, 47, 106, 50, 37, 0, 13, 81, 116, 117, 108, 97, 106, 100, 111, 110, 195, 173, 116, 97, 110, 105, 32, 33, 11, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 13, 48, 52, 39, 69, 55, 111, 63, 112, 63, 23, 82, 106, 50, 0, 13, 81, 118, 97, 110, 32, 16, 141, 19, 26, 195, 182, 22, 5, 20, 19, 195, 169, 7, 5, 11, 13, 42, 8, 1, 12, 1, 16, 10, 195, 161, 14, 106, 55, 106, 48, 57, 112, 50, 23, 110, 47, 111, 55, 49, 107, 86, 107, 55, 0, 13, 81, 195, 173, 116, 195, 169, 108, 107, 101, 122, 101, 108, 32, 37, 11, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 13, 48, 52, 39, 69, 55, 111, 63, 112, 63, 15, 106, 49, 106, 47, 12, 0, 13, 81, 97, 107, 97, 100, 116, 32, 16, 141, 20, 1, 12, 195, 161, 12, 8, 1, 20, 195, 179, 1, 11, 13, 11, 136, 1, 12, 1, 16, 10, 195, 161, 14, 13, 0, 12, 137, 6, 9, 26, 9, 11, 21, 13, 195, 186, 13, 13, 138, 2, 15, 18, 195, 173, 20, 10, 195, 161, 11, 13, 18, 143, 5, 12, 12, 5, 14, 197, 145, 18, 26, 195, 169, 19, 195, 169, 20, 13, 0, 14, 139, 16, 18, 15, 2, 12, 195, 169, 13, 195, 161, 11, 13, 19, 144, 11, 9, 20, 5, 18, 10, 5, 19, 26, 20, 195, 169, 19, 195, 169, 20, 13, 7, 196, 40, 241, 207, 80, 13, 7, 196, 40, 241, 207, 80, 13, 0, 8, 197, 88, 242, 211, 61, 64, 13, 15, 140, 6, 5, 12, 12, 195, 169, 16, 195, 169, 19, 5, 11, 13, 0, 0, 12, 201, 52, 81, 212, 20, 129, 84, 21, 69, 0, 13, 11, 136, 11, 9, 10, 195, 182, 14, 14, 9, 13, 15, 67, 4, 68, 204, 112, 70, 111, 107, 89, 107, 55, 0, 42, 42, 0, 41, 70, 24, 82, 140, 21, 69, 0, 81, 107, 57, 55, 107, 47, 12, 10, 6, 15, 48, 52, 39, 117, 107, 87, 12, 39, 52, 0, 13, 81, 112, 114, 111, 99, 101, 115, 115, 122, 111, 114, 32, 49, 11, 20, 1, 14, 195, 173, 20, 1, 14, 4, 195, 179, 47, 106, 50, 110, 47, 106, 50, 70, 113, 23, 37, 89, 63, 107, 52, 107, 47, 107, 49, 107, 47, 0, 13, 81, 105, 115, 109, 101, 114, 101, 116, 101, 107, 101, 116, 32, 17, 142, 13, 5, 7, 2, 195, 173, 26, 8, 1, 20, 195, 179, 1, 14, 13, 11, 200, 32, 243, 20, 80, 84, 212, 21, 64, 13, 14, 139, 9, 14, 20, 15, 14, 195, 161, 3, 9, 195, 179, 13, 14, 139, 22, 1, 19, 195, 161, 18, 14, 1, 16, 9, 7, 22, 0, 8, 197, 56, 17, 217, 61, 64, 13, 13, 138, 20, 195, 182, 18, 197, 145, 4, 14, 9, 5, 13, 16, 141, 16, 18, 9, 15, 18, 9, 20, 195, 161, 19, 19, 1, 12, 13, 0, 13, 138, 20, 21, 4, 8, 1, 20, 14, 195, 161, 4, 13, 17, 142, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 19, 1, 12, 13, 17, 142, 1, 12, 11, 1, 12, 13, 1, 26, 195, 161, 19, 19, 1, 12, 13, 12, 137, 7, 1, 26, 4, 1, 19, 195, 161, 7, 13, 13, 138, 5, 12, 12, 195, 161, 20, 195, 161, 19, 20, 13, 0, 23, 7, 11, 195, 182, 18, 195, 188, 12, 49, 108, 52, 109, 55, 23, 37, 89, 0, 13, 81, 105, 115, 32, 13, 138, 6, 195, 161, 18, 1, 19, 26, 20, 195, 179, 13, 17, 142, 18, 5, 7, 9, 19, 26, 20, 18, 195, 161, 3, 9, 195, 179, 13, 13, 138, 1, 14, 9, 13, 195, 161, 3, 9, 195, 179, 13, 14, 139, 195, 161, 20, 195, 161, 12, 12, 195, 161, 19, 20, 13, 12, 135, 11, 195, 182, 18, 195, 188, 12, 13, 20, 22, 0, 52, 12, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 20, 47, 112, 63, 39, 79, 106, 47, 112, 89, 47, 23, 69, 37, 87, 47, 39, 89, 110, 47, 106, 50, 37, 0, 13, 81, 98, 105, 122, 116, 111, 115, 195, 173, 116, 97, 110, 105, 32, 15, 140, 1, 12, 11, 1, 12, 13, 1, 26, 195, 161, 19, 20, 13, 15, 140, 20, 195, 161, 13, 15, 7, 1, 20, 195, 161, 19, 20, 13, 11, 136, 11, 195, 169, 19, 26, 195, 188, 12, 13, 15, 140, 7, 25, 15, 18, 19, 195, 173, 20, 195, 161, 19, 20, 13, 11, 136, 11, 195, 169, 19, 26, 195, 188, 12, 13, 0, 8, 197, 88, 19, 12, 88, 16, 13, 10, 135, 9, 18, 15, 4, 195, 161, 14, 13, 16, 141, 19, 26, 9, 7, 15, 18, 195, 173, 20, 195, 161, 19, 20, 13, 8, 197, 24, 241, 202, 84, 176, 13, 16, 141, 13, 5, 7, 2, 195, 173, 26, 1, 20, 195, 161, 19, 20, 13, 8, 197, 20, 192, 68, 56, 144, 13, 15, 140, 9, 14, 6, 15, 18, 13, 195, 161, 3, 9, 195, 179, 13, 8, 133, 14, 197, 145, 20, 20, 13, 0, 9, 198, 88, 243, 20, 84, 226, 192, 72, 30, 6, 5, 12, 197, 145, 20, 20, 107, 55, 116, 47, 12, 23, 49, 108, 86, 108, 55, 0, 13, 81, 107, 195, 182, 122, 195, 182, 108, 32, 39, 6, 5, 12, 197, 145, 20, 20, 107, 55, 116, 47, 12, 23, 48, 40, 69, 55, 37, 49, 112, 55, 47, 106, 0, 13, 81, 112, 117, 98, 108, 105, 107, 195, 161, 108, 116, 97, 32, 8, 133, 195, 173, 18, 15, 11, 13, 17, 142, 19, 26, 1, 2, 195, 161, 12, 25, 15, 26, 195, 161, 19, 20, 13, 17, 142, 20, 1, 18, 20, 195, 179, 26, 11, 15, 4, 195, 161, 19, 20, 13, 17, 142, 10, 1, 22, 1, 4, 1, 12, 13, 1, 26, 195, 161, 19, 20, 13, 12, 137, 15, 12, 22, 1, 19, 19, 195, 161, 11, 13, 11, 136, 19, 26, 5, 18, 4, 195, 161, 14, 22, 11, 134, 5, 12, 197, 145, 20, 20, 20, 22, 13, 0, 18, 143, 13, 5, 7, 195, 161, 12, 12, 1, 16, 15, 4, 195, 161, 19, 20, 13, 17, 142, 11, 15, 14, 6, 9, 7, 21, 18, 195, 161, 3, 9, 195, 179, 13, 18, 143, 14, 25, 9, 12, 22, 195, 161, 14, 195, 173, 20, 195, 161, 19, 20, 13, 0, 30, 68, 52, 144, 84, 80, 63, 37, 106, 47, 12, 23, 82, 106, 50, 23, 110, 77, 0, 13, 82, 118, 97, 110, 32, 195, 173, 103, 121, 32, 11, 200, 53, 83, 139, 4, 145, 5, 40, 80, 13, 43, 7, 6, 15, 7, 10, 195, 161, 11, 81, 39, 79, 57, 112, 49, 23, 107, 55, 12, 107, 50, 116, 52, 37, 86, 50, 37, 0, 13, 81, 101, 108, 108, 101, 110, 197, 145, 114, 105, 122, 110, 105, 32, 34, 68, 52, 144, 84, 80, 63, 6, 37, 106, 47, 12, 15, 65, 39, 63, 39, 86, 50, 106, 49, 0, 13, 81, 110, 121, 111, 109, 111, 122, 110, 97, 107, 32, 38, 68, 52, 144, 84, 80, 63, 37, 106, 47, 12, 23, 47, 37, 55, 47, 106, 49, 39, 86, 50, 106, 49, 0, 13, 81, 116, 105, 108, 116, 97, 107, 111, 122, 110, 97, 107, 32, 11, 200, 32, 17, 19, 21, 33, 71, 8, 80, 13, 12, 137, 11, 195, 182, 12, 20, 197, 145, 18, 5, 13, 10, 135, 6, 15, 7, 10, 195, 161, 11, 13, 10, 135, 195, 173, 18, 10, 195, 161, 11, 13, 7, 196, 52, 144, 84, 80, 13, 0, 15, 140, 11, 195, 169, 16, 5, 19, 19, 195, 169, 7, 5, 11, 13, 30, 8, 13, 195, 161, 19, 15, 4, 9, 11, 63, 112, 89, 39, 70, 37, 49, 23, 107, 55, 107, 63, 0, 13, 81, 101, 108, 101, 109, 32, 8, 197, 52, 240, 211, 60, 176, 13, 11, 136, 11, 195, 169, 16, 5, 19, 5, 11, 13, 15, 140, 11, 195, 169, 16, 22, 9, 19, 5, 12, 197, 145, 11, 13, 10, 135, 195, 161, 12, 12, 10, 15, 14, 13, 0, 16, 141, 2, 9, 26, 15, 14, 25, 195, 173, 20, 10, 195, 161, 11, 13, 35, 70, 81, 81, 10, 84, 226, 192, 47, 40, 77, 12, 40, 50, 49, 23, 47, 108, 55, 47, 107, 50, 37, 0, 13, 81, 116, 195, 182, 108, 116, 101, 110, 105, 32, 11, 136, 11, 1, 16, 3, 19, 195, 161, 14, 13, 13, 7, 95, 35, 45, 195, 161, 18, 1, 112, 52, 106, 0, 0, 10, 135, 19, 16, 195, 179, 18, 15, 12, 13, 13, 138, 19, 26, 195, 179, 18, 195, 179, 4, 9, 11, 13, 11, 136, 9, 18, 15, 4, 195, 161, 18, 1, 13, 11, 136, 13, 1, 16, 16, 195, 161, 18, 1, 13, 16, 141, 6, 5, 10, 12, 5, 19, 26, 20, 195, 169, 19, 5, 14, 13, 13, 138, 20, 21, 4, 8, 1, 20, 10, 195, 161, 11, 13, 0, 11, 200, 52, 81, 214, 21, 54, 142, 20, 176, 13, 7, 196, 36, 198, 69, 80, 13, 14, 139, 10, 5, 12, 5, 14, 20, 195, 169, 19, 5, 11, 13, 15, 140, 6, 5, 12, 195, 188, 12, 5, 20, 18, 197, 145, 12, 13, 0, 6, 20, 0, 0, 244, 0, 0, 0, 81, 1, 0, 0, 251, 0, 0, 0, 113, 1, 0, 0, 0, 0, 0, 0, 6, 18, 66, 98, 0, 99, 0, 100, 0, 102, 0, 103, 0, 104, 0, 106, 0, 107, 0, 108, 0, 109, 0, 110, 0, 112, 0, 115, 0, 116, 0, 114, 0, 118, 0, 119, 0, 122, 0, 7, 6, 99, 104, 0, 4, 1, 169, 195, 122, 115, 3, 74, 0, 8, 105, 122, 2, 121, 0, 4, 101, 8, 169, 195, 122, 115, 2, 110, 121, 3, 74, 111, 0, 195, 169, 8, 169, 195, 122, 115, 2, 110, 121, 0, 1, 110, 188, 195, 109, 2, 101, 110, 3, 97, 0, 4, 1, 97, 99, 114, 97, 2, 111, 110, 3, 105, 0, 1, 97, 100, 108, 97, 98, 2, 105, 110, 0, 1, 97, 106, 2, 116, 0, 1, 97, 109, 2, 105, 97, 118, 101, 108, 108, 0, 1, 97, 109, 2, 105, 110, 195, 161, 0, 1, 97, 110, 97, 109, 108, 97, 0, 1, 101, 109, 2, 97, 0, 1, 101, 116, 0, 1, 105, 116, 122, 115, 105, 100, 2, 111, 110, 0, 1, 105, 116, 122, 115, 111, 110, 111, 114, 107, 2, 111, 110, 0, 1, 105, 122, 115, 112, 0, 1, 111, 115, 97, 109, 2, 105, 115, 116, 17, 65, 0, 1, 111, 122, 97, 109, 2, 105, 115, 0, 1, 111, 122, 97, 109, 2, 105, 122, 109, 0, 1, 114, 97, 2, 97, 105, 107, 117, 115, 0, 1, 114, 97, 2, 105, 116, 101, 107, 116, 195, 186, 0, 1, 114, 97, 2, 105, 118, 195, 161, 108, 0, 1, 114, 97, 2, 195, 173, 118, 0, 1, 114, 97, 103, 105, 108, 111, 0, 1, 114, 97, 110, 97, 2, 105, 0, 1, 114, 97, 110, 111, 109, 2, 105, 0, 1, 114, 97, 114, 101, 105, 104, 2, 105, 0, 1, 114, 111, 2, 195, 173, 100, 101, 97, 0, 1, 121, 122, 115, 112, 0, 8, 114, 97, 2, 105, 109, 195, 169, 0, 8, 114, 111, 2, 105, 100, 101, 0, 4, 1, 101, 99, 2, 101, 116, 3, 105, 12, 0, 1, 101, 112, 103, 101, 108, 2, 101, 115, 0, 1, 105, 114, 116, 115, 2, 101, 108, 0, 8, 101, 112, 0, 7, 6, 100, 122, 0, 4, 1, 97, 122, 161, 195, 122, 115, 2, 101, 110, 101, 3, 70, 86, 0, 1, 101, 114, 122, 101, 2, 101, 110, 101, 0, 1, 103, 97, 114, 97, 109, 115, 2, 195, 182, 108, 100, 0, 1, 169, 195, 118, 110, 111, 104, 2, 195, 161, 115, 122, 108, 195, 179, 0, 1, 169, 195, 122, 115, 101, 98, 2, 97, 118, 97, 114, 0, 4, 115, 3, 73, 0, 115, 1, 17, 67, 0, 115, 1, 97, 2, 17, 65, 0, 115, 2, 17, 67, 0, 4, 115, 1, 97, 114, 97, 104, 97, 109, 2, 17, 65, 3, 73, 12, 0, 115, 1, 101, 110, 101, 109, 2, 17, 65, 0, 115, 1, 105, 114, 98, 2, 17, 65, 0, 115, 5, 1, 1, 111, 98, 109, 97, 107, 2, 17, 65, 0, 115, 8, 111, 100, 2, 17, 65, 0, 4, 1, 145, 197, 108, 101, 100, 101, 122, 115, 3, 86, 0, 1, 145, 197, 108, 101, 116, 101, 118, 182, 195, 107, 0, 1, 145, 197, 114, 169, 195, 107, 0, 1, 145, 197, 116, 101, 103, 101, 116, 110, 101, 109, 0, 1, 145, 197, 116, 101, 103, 101, 121, 110, 101, 102, 0, 1, 177, 197, 114, 177, 197, 121, 103, 2, 105, 107, 0, 1, 179, 195, 103, 111, 102, 2, 195, 179, 0, 1, 179, 195, 108, 108, 105, 118, 0, 1, 179, 195, 108, 111, 107, 114, 117, 98, 0, 1, 179, 195, 108, 111, 107, 116, 105, 116, 0, 1, 179, 195, 108, 161, 195, 98, 109, 105, 104, 0, 1, 179, 195, 108, 161, 195, 98, 111, 100, 0, 1, 179, 195, 108, 161, 195, 112, 97, 107, 0, 1, 179, 195, 112, 97, 114, 97, 104, 0, 1, 179, 195, 112, 111, 108, 0, 1, 179, 195, 114, 97, 107, 97, 0, 1, 179, 195, 115, 114, 111, 98, 0, 1, 179, 195, 116, 97, 103, 108, 108, 97, 104, 0, 1, 179, 195, 116, 97, 103, 110, 105, 114, 0, 1, 179, 195, 116, 97, 103, 110, 161, 195, 114, 0, 1, 179, 195, 116, 97, 103, 111, 112, 97, 116, 0, 1, 145, 197, 108, 101, 100, 101, 122, 115, 2, 107, 195, 182, 3, 87, 0, 4, 1, 101, 114, 169, 195, 107, 3, 117, 0, 1, 101, 114, 169, 195, 109, 2, 107, 0, 1, 179, 195, 2, 107, 111, 100, 0, 1, 179, 195, 103, 111, 102, 2, 107, 111, 100, 0, 1, 179, 195, 122, 186, 195, 104, 0, 8, 179, 195, 2, 107, 111, 0, 4, 3, 118, 12, 0, 0, 1, 17, 65, 2, 17, 65, 0, 1, 101, 2, 195, 169, 115, 0, 1, 101, 2, 197, 145, 0, 7, 6, 103, 121, 0, 115, 3, 74, 0, 115, 1, 17, 65, 2, 17, 65, 3, 74, 12, 0, 4, 3, 77, 0, 1, 97, 2, 115, 101, 98, 195, 169, 115, 122, 0, 1, 97, 2, 115, 101, 106, 0, 1, 97, 2, 115, 195, 169, 114, 195, 188, 108, 0, 1, 97, 102, 2, 115, 195, 169, 114, 195, 188, 108, 0, 1, 97, 110, 2, 115, 97, 108, 108, 195, 179, 0, 1, 97, 110, 2, 115, 97, 114, 108, 195, 179, 0, 1, 97, 110, 2, 115, 101, 98, 101, 115, 0, 1, 97, 110, 2, 115, 105, 101, 116, 0, 1, 97, 110, 2, 115, 105, 107, 101, 114, 0, 1, 97, 110, 2, 115, 111, 107, 195, 161, 114, 97, 0, 1, 97, 110, 2, 115, 116, 114, 97, 116, 195, 169, 103, 105, 97, 0, 1, 97, 110, 2, 115, 116, 195, 173, 108, 0, 1, 97, 110, 2, 115, 195, 161, 103, 0, 1, 97, 110, 2, 115, 195, 161, 112, 0, 1, 101, 2, 101, 115, 45, 101, 103, 121, 101, 100, 195, 188, 108, 0, 1, 101, 2, 106, 101, 103, 121, 197, 177, 0, 1, 101, 2, 106, 101, 108, 101, 110, 116, 195, 169, 115, 197, 177, 0, 1, 101, 2, 115, 97, 114, 107, 195, 186, 0, 1, 101, 2, 115, 101, 106, 116, 197, 177, 0, 1, 101, 2, 115, 111, 114, 0, 1, 101, 2, 115, 195, 173, 110, 197, 177, 0, 1, 101, 104, 2, 115, 195, 169, 103, 0, 1, 101, 106, 2, 101, 110, 107, 195, 169, 110, 116, 0, 1, 101, 106, 2, 101, 122, 116, 101, 0, 1, 101, 106, 2, 195, 169, 114, 116, 0, 1, 110, 182, 195, 121, 103, 2, 115, 111, 114, 0, 1, 111, 104, 2, 115, 101, 0, 1, 111, 104, 101, 115, 2, 115, 101, 0, 1, 114, 161, 195, 116, 2, 106, 117, 116, 97, 108, 0, 1, 114, 161, 195, 116, 2, 115, 111, 114, 0, 1, 114, 161, 195, 116, 2, 115, 111, 114, 111, 122, 97, 116, 0, 1, 161, 195, 2, 115, 111, 114, 0, 1, 161, 195, 108, 2, 115, 195, 161, 0, 1, 161, 195, 118, 116, 169, 195, 2, 106, 97, 118, 195, 173, 116, 0, 1, 169, 195, 110, 2, 106, 101, 103, 121, 0, 1, 169, 195, 110, 2, 115, 97, 114, 111, 107, 0, 1, 169, 195, 110, 2, 115, 111, 114, 0, 1, 169, 195, 110, 2, 115, 195, 161, 118, 0, 1, 186, 195, 2, 115, 101, 109, 0, 1, 186, 195, 2, 115, 105, 110, 99, 115, 0, 8, 101, 2, 115, 101, 0, 8, 101, 100, 110, 105, 109, 2, 105, 107, 0, 8, 173, 195, 2, 106, 195, 161, 114, 0, 106, 1, 17, 67, 0, 4, 1, 101, 2, 45, 101, 103, 121, 3, 77, 12, 0, 1, 101, 2, 97, 114, 195, 161, 110, 116, 0, 1, 101, 2, 97, 122, 111, 110, 0, 1, 101, 2, 101, 108, 197, 145, 114, 101, 0, 1, 101, 2, 101, 109, 98, 101, 114, 0, 1, 101, 2, 101, 110, 107, 195, 169, 110, 116, 0, 1, 101, 2, 101, 110, 114, 97, 110, 103, 0, 1, 101, 2, 101, 110, 115, 195, 186, 108, 121, 0, 1, 101, 2, 101, 115, 195, 188, 108, 101, 116, 0, 1, 101, 2, 101, 116, 195, 169, 114, 116, 0, 1, 101, 2, 101, 122, 107, 101, 100, 0, 1, 101, 2, 101, 122, 116, 101, 116, 0, 1, 101, 2, 105, 100, 101, 106, 197, 177, 0, 1, 101, 2, 105, 114, 195, 161, 110, 121, 195, 186, 0, 1, 101, 2, 195, 161, 108, 116, 97, 108, 195, 161, 110, 0, 1, 101, 2, 195, 169, 106, 115, 122, 97, 107, 0, 1, 101, 2, 195, 169, 114, 116, 0, 1, 101, 2, 195, 169, 114, 116, 101, 108, 109, 197, 177, 0, 1, 101, 2, 195, 186, 116, 116, 97, 108, 0, 1, 101, 45, 109, 101, 110, 2, 101, 122, 0, 1, 101, 45, 109, 101, 110, 2, 105, 107, 0, 1, 101, 45, 109, 101, 110, 2, 195, 188, 116, 116, 0, 1, 101, 97, 114, 106, 186, 195, 2, 101, 115, 195, 173, 116, 0, 1, 101, 99, 110, 105, 109, 114, 97, 104, 2, 101, 100, 105, 107, 0, 1, 101, 101, 108, 101, 98, 2, 101, 122, 0, 1, 101, 101, 122, 115, 115, 182, 195, 2, 101, 115, 195, 173, 116, 0, 1, 101, 103, 101, 109, 108, 169, 195, 102, 2, 101, 122, 0, 1, 101, 105, 107, 2, 101, 122, 0, 1, 101, 110, 101, 122, 105, 116, 2, 101, 100, 105, 107, 0, 1, 101, 110, 101, 122, 105, 116, 2, 101, 100, 115, 122, 101, 114, 0, 1, 101, 110, 101, 122, 105, 116, 2, 101, 110, 0, 1, 101, 110, 101, 122, 105, 116, 2, 101, 115, 0, 1, 101, 110, 101, 122, 105, 116, 2, 101, 116, 0, 1, 101, 110, 111, 122, 115, 117, 104, 2, 101, 100, 0, 1, 101, 110, 111, 122, 115, 117, 104, 2, 101, 100, 105, 107, 0, 1, 101, 110, 111, 122, 115, 117, 104, 2, 101, 115, 0, 1, 101, 110, 111, 122, 115, 117, 104, 2, 101, 122, 0, 1, 101, 116, 101, 108, 188, 195, 112, 169, 195, 2, 195, 188, 116, 116, 0, 1, 101, 122, 161, 195, 122, 115, 2, 101, 100, 105, 107, 0, 1, 101, 122, 161, 195, 122, 115, 2, 101, 115, 0, 8, 101, 2, 97, 98, 108, 97, 107, 0, 8, 101, 2, 101, 108, 0, 8, 101, 2, 101, 115, 0, 8, 101, 2, 101, 116, 32, 0, 8, 101, 2, 101, 116, 108, 101, 110, 0, 8, 101, 2, 101, 122, 0, 8, 101, 2, 101, 122, 109, 195, 169, 110, 121, 0, 8, 101, 2, 105, 100, 197, 145, 0, 8, 101, 2, 105, 107, 0, 8, 101, 2, 111, 108, 100, 97, 108, 0, 8, 101, 2, 195, 161, 103, 121, 0, 8, 101, 2, 195, 169, 32, 0, 8, 101, 2, 195, 169, 118, 0, 8, 101, 2, 195, 179, 114, 195, 161, 0, 8, 101, 2, 195, 182, 110, 116, 101, 116, 0, 8, 101, 2, 195, 182, 115, 115, 122, 101, 103, 0, 8, 101, 2, 195, 188, 116, 0, 8, 101, 45, 116, 110, 105, 109, 2, 195, 169, 32, 0, 8, 101, 103, 101, 109, 2, 101, 122, 0, 8, 101, 107, 101, 122, 115, 105, 104, 2, 101, 0, 8, 101, 110, 111, 122, 115, 117, 104, 2, 101, 0, 8, 101, 114, 101, 122, 115, 121, 103, 101, 2, 101, 0, 106, 1, 17, 65, 2, 17, 65, 0, 106, 1, 97, 104, 0, 106, 1, 101, 2, 101, 108, 101, 110, 116, 195, 169, 115, 197, 177, 3, 77, 57, 0, 4, 115, 122, 3, 77, 87, 0, 115, 122, 1, 17, 65, 2, 17, 65, 0, 115, 122, 1, 97, 110, 2, 97, 0, 4, 115, 1, 101, 2, 195, 161, 118, 3, 77, 89, 0, 115, 1, 101, 2, 195, 169, 103, 0, 115, 1, 101, 2, 195, 173, 107, 0, 115, 1, 186, 195, 2, 101, 0, 115, 8, 173, 195, 2, 101, 0, 7, 6, 115, 115, 0, 4, 122, 1, 97, 2, 105, 115, 122, 116, 101, 110, 115, 3, 87, 0, 122, 1, 97, 2, 105, 115, 122, 116, 195, 161, 108, 0, 122, 1, 97, 107, 2, 195, 173, 114, 111, 122, 0, 122, 1, 97, 109, 2, 195, 173, 114, 111, 122, 0, 122, 1, 97, 112, 2, 195, 173, 114, 111, 122, 0, 122, 1, 111, 114, 105, 112, 2, 107, 97, 0, 122, 2, 18, 66, 0, 122, 2, 45, 18, 66, 0, 122, 8, 97, 2, 105, 115, 122, 116, 0, 122, 8, 101, 2, 101, 110, 99, 105, 0, 122, 8, 101, 122, 115, 101, 110, 2, 101, 114, 0, 4, 1, 117, 105, 98, 117, 110, 97, 100, 3, 87, 12, 0, 1, 117, 116, 110, 101, 118, 117, 106, 0, 8, 101, 107, 2, 101, 108, 114, 105, 110, 103, 0, 122, 1, 97, 118, 97, 116, 2, 97, 0, 122, 1, 97, 118, 107, 2, 105, 97, 107, 195, 169, 114, 0, 122, 1, 97, 118, 108, 111, 0, 122, 1, 97, 118, 109, 97, 104, 0, 122, 1, 97, 118, 114, 111, 115, 2, 195, 161, 107, 0, 122, 1, 97, 118, 117, 121, 110, 0, 122, 1, 97, 118, 121, 116, 111, 107, 0, 122, 1, 97, 118, 186, 195, 121, 110, 0, 122, 1, 101, 108, 169, 195, 108, 182, 195, 102, 2, 101, 109, 0, 122, 1, 117, 105, 98, 117, 110, 97, 100, 0, 122, 1, 117, 116, 110, 101, 118, 117, 106, 0, 122, 8, 97, 108, 101, 109, 2, 195, 173, 110, 0, 122, 8, 97, 118, 97, 114, 0, 122, 8, 97, 118, 114, 111, 115, 0, 122, 8, 97, 118, 117, 115, 2, 97, 0, 122, 8, 169, 195, 110, 101, 112, 2, 195, 173, 110, 0, 122, 114, 3, 87, 52, 0, 122, 98, 3, 87, 69, 0, 4, 1, 117, 109, 2, 111, 108, 105, 110, 3, 87, 120, 0, 122, 0, 4, 1, 117, 116, 108, 101, 2, 111, 108, 3, 89, 0, 1, 145, 197, 108, 101, 108, 101, 102, 2, 195, 169, 103, 0, 1, 188, 195, 108, 112, 2, 122, 115, 0, 2, 18, 66, 0, 2, 45, 18, 66, 0, 4, 1, 105, 114, 102, 2, 122, 195, 182, 108, 3, 89, 12, 0, 1, 161, 195, 110, 97, 98, 98, 111, 114, 0, 114, 3, 89, 52, 0, 98, 3, 89, 69, 0, 4, 122, 1, 97, 103, 97, 109, 2, 195, 161, 114, 195, 186, 3, 89, 87, 0, 122, 1, 97, 103, 111, 102, 2, 101, 103, 0, 122, 1, 97, 103, 117, 108, 2, 101, 114, 197, 177, 0, 122, 1, 97, 107, 2, 195, 169, 107, 0, 122, 1, 97, 107, 97, 107, 2, 195, 169, 107, 0, 122, 1, 97, 107, 114, 97, 102, 2, 101, 109, 0, 122, 1, 97, 107, 114, 97, 102, 2, 101, 114, 197, 177, 0, 122, 1, 97, 107, 114, 97, 102, 2, 117, 107, 0, 122, 1, 97, 107, 114, 97, 102, 2, 195, 188, 114, 107, 0, 122, 1, 97, 107, 114, 97, 102, 2, 197, 145, 108, 197, 145, 0, 122, 1, 97, 109, 114, 161, 195, 104, 2, 97, 98, 0, 122, 1, 97, 109, 114, 161, 195, 104, 2, 195, 161, 109, 0, 122, 1, 97, 109, 114, 161, 195, 104, 2, 195, 182, 0, 122, 1, 97, 115, 2, 101, 109, 0, 122, 1, 97, 115, 97, 118, 2, 97, 107, 0, 122, 1, 97, 116, 116, 111, 108, 97, 104, 0, 122, 1, 97, 116, 117, 2, 101, 114, 0, 122, 1, 97, 116, 117, 2, 105, 110, 116, 0, 122, 1, 97, 116, 117, 2, 111, 108, 103, 0, 122, 1, 97, 116, 117, 2, 195, 161, 108, 0, 122, 1, 97, 116, 117, 2, 195, 161, 109, 0, 122, 1, 97, 118, 109, 97, 104, 2, 197, 145, 107, 101, 0, 122, 1, 97, 122, 114, 111, 98, 2, 197, 145, 114, 0, 122, 1, 101, 98, 98, 182, 195, 116, 2, 195, 161, 109, 0, 122, 1, 101, 100, 101, 122, 105, 116, 2, 195, 161, 108, 108, 195, 161, 115, 0, 122, 1, 101, 100, 108, 182, 195, 122, 2, 195, 188, 114, 107, 0, 122, 1, 101, 100, 108, 182, 195, 122, 2, 195, 188, 114, 107, 101, 0, 122, 1, 101, 100, 169, 195, 2, 195, 161, 106, 0, 122, 1, 101, 100, 169, 195, 2, 195, 188, 108, 0, 122, 1, 101, 104, 169, 195, 2, 195, 161, 106, 0, 122, 1, 101, 104, 169, 195, 109, 0, 122, 1, 101, 107, 169, 195, 2, 195, 179, 0, 122, 1, 101, 107, 169, 195, 2, 195, 179, 108, 0, 122, 1, 101, 107, 169, 195, 107, 2, 195, 188, 114, 107, 0, 122, 1, 101, 108, 101, 100, 101, 102, 2, 195, 161, 114, 110, 121, 0, 122, 1, 101, 108, 101, 102, 106, 101, 116, 2, 195, 161, 106, 0, 122, 1, 101, 108, 169, 195, 2, 101, 109, 0, 122, 1, 101, 108, 182, 195, 107, 2, 101, 109, 0, 122, 1, 101, 109, 101, 110, 2, 195, 173, 118, 0, 122, 1, 101, 109, 101, 110, 2, 197, 145, 114, 109, 0, 122, 1, 101, 109, 121, 108, 101, 115, 2, 197, 145, 107, 101, 0, 122, 1, 101, 110, 101, 121, 103, 101, 0, 122, 1, 101, 110, 101, 121, 103, 101, 2, 195, 161, 108, 0, 122, 1, 101, 112, 101, 122, 115, 2, 111, 109, 98, 97, 116, 0, 122, 1, 101, 114, 100, 101, 109, 2, 195, 169, 107, 0, 122, 1, 101, 114, 101, 118, 2, 197, 145, 107, 101, 0, 122, 1, 101, 114, 101, 122, 115, 145, 197, 108, 0, 122, 1, 101, 114, 169, 195, 104, 101, 102, 2, 195, 188, 114, 107, 0, 122, 1, 101, 114, 169, 195, 104, 101, 102, 2, 197, 145, 107, 101, 0, 122, 1, 101, 114, 169, 195, 118, 2, 195, 161, 106, 0, 122, 1, 101, 115, 99, 169, 195, 109, 0, 122, 1, 101, 115, 182, 195, 114, 182, 195, 118, 2, 197, 145, 107, 101, 0, 122, 1, 101, 116, 101, 108, 101, 121, 103, 188, 195, 2, 111, 98, 0, 122, 1, 101, 116, 101, 122, 114, 101, 122, 115, 2, 101, 114, 0, 122, 1, 101, 116, 114, 169, 195, 118, 2, 195, 161, 122, 97, 100, 0, 122, 1, 101, 116, 114, 169, 195, 118, 2, 197, 145, 108, 197, 145, 0, 122, 1, 101, 118, 100, 101, 110, 2, 195, 188, 114, 107, 0, 122, 1, 101, 118, 101, 108, 2, 101, 100, 0, 122, 1, 101, 118, 121, 110, 182, 195, 107, 0, 122, 1, 101, 118, 121, 110, 182, 195, 107, 2, 101, 107, 0, 122, 1, 101, 121, 103, 101, 104, 2, 195, 182, 103, 0, 122, 1, 101, 121, 108, 101, 107, 107, 105, 112, 2, 195, 161, 114, 110, 121, 0, 122, 1, 101, 121, 110, 101, 104, 114, 182, 195, 118, 2, 197, 145, 107, 101, 0, 122, 1, 101, 122, 115, 145, 197, 0, 122, 1, 101, 122, 188, 195, 116, 2, 101, 109, 0, 122, 1, 105, 107, 2, 101, 98, 0, 122, 1, 105, 107, 2, 101, 100, 0, 122, 1, 105, 107, 2, 101, 107, 114, 195, 169, 110, 121, 0, 122, 1, 105, 107, 2, 101, 114, 197, 177, 0, 122, 1, 105, 107, 2, 111, 98, 0, 122, 1, 105, 107, 2, 195, 161, 109, 0, 122, 1, 105, 107, 2, 195, 169, 107, 0, 122, 1, 105, 107, 2, 195, 179, 116, 195, 161, 114, 0, 122, 1, 105, 109, 97, 114, 105, 112, 2, 101, 114, 197, 177, 0, 122, 1, 105, 115, 99, 111, 107, 2, 101, 114, 101, 112, 0, 122, 1, 105, 116, 169, 195, 102, 2, 101, 114, 197, 177, 0, 122, 1, 105, 118, 182, 195, 116, 0, 122, 1, 105, 118, 182, 195, 116, 2, 195, 186, 114, 0, 122, 1, 105, 122, 161, 195, 111, 2, 101, 114, 197, 177, 0, 122, 1, 105, 122, 161, 195, 114, 102, 2, 101, 114, 197, 177, 0, 122, 1, 110, 101, 105, 108, 107, 2, 111, 102, 116, 0, 122, 1, 111, 99, 114, 97, 104, 0, 122, 1, 111, 100, 108, 111, 115, 122, 0, 122, 1, 111, 103, 111, 108, 97, 121, 103, 0, 122, 1, 111, 103, 161, 195, 108, 105, 118, 0, 122, 1, 111, 103, 161, 195, 108, 105, 118, 2, 195, 188, 114, 107, 101, 0, 122, 1, 111, 103, 161, 195, 108, 105, 118, 2, 197, 145, 107, 101, 0, 122, 1, 111, 107, 2, 97, 114, 118, 0, 122, 1, 111, 107, 97, 108, 2, 195, 161, 109, 0, 122, 1, 111, 107, 116, 105, 116, 2, 111, 108, 103, 195, 161, 108, 0, 122, 1, 111, 107, 161, 195, 98, 117, 116, 2, 101, 108, 0, 122, 1, 111, 107, 179, 195, 105, 102, 2, 101, 107, 114, 0, 122, 1, 111, 108, 169, 195, 99, 110, 161, 195, 112, 0, 122, 1, 111, 109, 97, 108, 108, 105, 118, 0, 122, 1, 111, 109, 97, 108, 108, 105, 118, 2, 195, 169, 107, 0, 122, 1, 111, 109, 111, 108, 112, 109, 101, 116, 2, 97, 107, 0, 122, 1, 111, 109, 114, 111, 107, 0, 122, 1, 111, 112, 97, 108, 2, 195, 161, 114, 0, 122, 1, 111, 112, 186, 195, 112, 2, 195, 186, 110, 121, 111, 103, 0, 122, 1, 111, 114, 97, 107, 2, 195, 169, 107, 0, 122, 1, 111, 114, 97, 107, 2, 195, 169, 114, 105, 97, 0, 122, 1, 111, 114, 97, 107, 2, 195, 169, 114, 105, 195, 161, 0, 122, 1, 111, 114, 97, 107, 2, 195, 169, 114, 105, 195, 161, 106, 195, 186, 0, 122, 1, 111, 114, 97, 109, 0, 122, 1, 111, 114, 97, 118, 97, 122, 2, 195, 188, 114, 0, 122, 1, 111, 114, 97, 118, 117, 102, 2, 101, 107, 195, 169, 114, 0, 122, 1, 111, 114, 105, 112, 2, 101, 109, 0, 122, 1, 111, 114, 105, 112, 97, 112, 0, 122, 1, 111, 114, 111, 112, 145, 197, 108, 0, 122, 1, 111, 114, 111, 116, 111, 109, 2, 101, 109, 195, 188, 118, 101, 103, 0, 122, 1, 111, 114, 111, 116, 111, 109, 2, 195, 161, 110, 0, 122, 1, 111, 114, 111, 122, 115, 2, 101, 114, 197, 177, 0, 122, 1, 111, 114, 161, 195, 118, 2, 101, 114, 0, 122, 1, 111, 114, 161, 195, 118, 2, 105, 108, 117, 101, 116, 116, 0, 122, 1, 111, 114, 161, 195, 118, 2, 195, 169, 112, 101, 0, 122, 1, 111, 114, 173, 195, 115, 122, 2, 195, 161, 106, 0, 122, 1, 111, 114, 173, 195, 115, 122, 2, 195, 169, 110, 0, 122, 1, 111, 116, 108, 161, 195, 116, 2, 195, 161, 114, 110, 121, 0, 122, 1, 111, 118, 114, 111, 2, 97, 107, 195, 169, 114, 116, 197, 145, 0, 122, 1, 111, 118, 114, 111, 2, 101, 109, 195, 169, 108, 121, 0, 122, 1, 111, 118, 114, 111, 2, 101, 114, 0, 122, 1, 111, 118, 114, 111, 2, 101, 114, 0, 122, 1, 111, 118, 114, 111, 2, 195, 161, 122, 0, 122, 1, 111, 118, 114, 111, 2, 195, 182, 118, 101, 116, 115, 195, 169, 103, 0, 122, 1, 111, 121, 103, 97, 102, 2, 101, 110, 116, 0, 122, 1, 111, 121, 110, 97, 114, 97, 2, 197, 145, 107, 101, 0, 122, 1, 114, 101, 118, 2, 97, 107, 0, 122, 1, 114, 101, 118, 2, 101, 114, 122, 0, 122, 1, 114, 111, 98, 2, 101, 109, 0, 122, 1, 114, 111, 98, 2, 195, 179, 114, 0, 122, 1, 114, 111, 115, 2, 101, 114, 197, 177, 0, 122, 1, 114, 111, 121, 103, 2, 197, 177, 114, 0, 122, 1, 114, 145, 197, 145, 197, 108, 101, 2, 101, 114, 197, 177, 0, 122, 1, 114, 161, 195, 116, 2, 101, 107, 195, 169, 114, 0, 122, 1, 114, 161, 195, 116, 2, 101, 114, 0, 122, 1, 114, 161, 195, 116, 2, 111, 109, 115, 122, 195, 169, 100, 0, 122, 1, 114, 161, 195, 116, 2, 195, 182, 118, 101, 0, 122, 1, 117, 103, 179, 195, 103, 97, 100, 101, 112, 2, 111, 98, 0, 122, 1, 117, 103, 179, 195, 108, 97, 116, 97, 107, 2, 195, 161, 109, 0, 122, 1, 117, 107, 105, 115, 122, 117, 109, 0, 122, 1, 117, 109, 116, 105, 114, 2, 97, 98, 0, 122, 1, 117, 109, 122, 105, 107, 101, 116, 97, 107, 2, 101, 114, 197, 177, 0, 122, 1, 117, 110, 161, 195, 108, 117, 2, 195, 161, 122, 97, 100, 0, 122, 1, 117, 112, 97, 107, 0, 122, 1, 117, 112, 105, 116, 2, 195, 161, 109, 0, 122, 1, 117, 116, 105, 98, 97, 104, 2, 101, 114, 197, 177, 0, 122, 1, 117, 116, 110, 105, 114, 105, 98, 97, 108, 2, 101, 114, 0, 122, 1, 117, 116, 161, 195, 107, 105, 100, 110, 105, 122, 115, 0, 122, 1, 117, 120, 117, 108, 0, 122, 1, 117, 122, 108, 117, 112, 2, 195, 161, 109, 0, 122, 1, 145, 197, 2, 97, 114, 118, 0, 122, 1, 145, 197, 2, 195, 161, 114, 109, 0, 122, 1, 145, 197, 2, 195, 182, 114, 110, 121, 0, 122, 1, 145, 197, 2, 195, 188, 108, 101, 0, 122, 1, 145, 197, 2, 195, 188, 108, 197, 145, 0, 122, 1, 145, 197, 104, 2, 101, 114, 101, 108, 0, 122, 1, 145, 197, 104, 2, 101, 114, 101, 112, 0, 122, 1, 145, 197, 108, 188, 195, 112, 101, 114, 2, 116, 114, 195, 161, 106, 107, 0, 122, 1, 145, 197, 108, 188, 195, 112, 101, 114, 2, 195, 161, 114, 110, 121, 0, 122, 1, 161, 195, 100, 97, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 100, 97, 2, 195, 188, 110, 101, 116, 0, 122, 1, 161, 195, 100, 97, 122, 161, 195, 108, 0, 122, 1, 161, 195, 100, 111, 112, 97, 108, 108, 161, 195, 103, 101, 109, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 100, 111, 118, 2, 105, 110, 116, 0, 122, 1, 161, 195, 100, 114, 161, 195, 115, 99, 2, 195, 179, 108, 0, 122, 1, 161, 195, 100, 117, 116, 2, 105, 110, 116, 0, 122, 1, 161, 195, 100, 117, 116, 2, 111, 109, 106, 0, 122, 1, 161, 195, 100, 179, 195, 122, 115, 2, 105, 0, 122, 1, 161, 195, 101, 116, 2, 101, 114, 118, 0, 122, 1, 161, 195, 103, 108, 97, 115, 114, 161, 195, 116, 2, 195, 161, 109, 98, 97, 0, 122, 1, 161, 195, 103, 110, 111, 122, 114, 111, 98, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 103, 110, 161, 195, 114, 2, 101, 114, 0, 122, 1, 161, 195, 103, 111, 104, 117, 115, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 103, 111, 116, 116, 97, 107, 0, 122, 1, 161, 195, 103, 111, 118, 161, 195, 121, 110, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 103, 114, 161, 195, 115, 0, 122, 1, 161, 195, 103, 122, 111, 109, 0, 122, 1, 161, 195, 103, 186, 195, 114, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 104, 108, 161, 195, 109, 0, 122, 1, 161, 195, 104, 117, 114, 2, 101, 107, 101, 114, 101, 0, 122, 1, 161, 195, 104, 117, 114, 2, 101, 107, 114, 195, 169, 110, 121, 0, 122, 1, 161, 195, 104, 117, 114, 2, 111, 98, 0, 122, 1, 161, 195, 106, 161, 195, 102, 2, 101, 114, 0, 122, 1, 161, 195, 107, 97, 108, 2, 101, 110, 0, 122, 1, 161, 195, 107, 105, 114, 112, 97, 112, 0, 122, 1, 161, 195, 107, 110, 111, 115, 0, 122, 1, 161, 195, 107, 111, 122, 115, 2, 101, 114, 0, 122, 1, 161, 195, 107, 111, 122, 115, 2, 195, 161, 109, 0, 122, 1, 161, 195, 108, 97, 116, 117, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 108, 106, 97, 104, 2, 195, 182, 103, 0, 122, 1, 161, 195, 108, 107, 117, 115, 99, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 108, 108, 97, 118, 2, 97, 98, 0, 122, 1, 161, 195, 108, 108, 161, 195, 0, 122, 1, 161, 195, 108, 108, 161, 195, 2, 195, 182, 103, 0, 122, 1, 161, 195, 108, 108, 161, 195, 110, 101, 108, 108, 101, 2, 101, 107, 114, 195, 169, 110, 121, 0, 122, 1, 161, 195, 108, 109, 97, 122, 115, 117, 115, 99, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 108, 109, 111, 2, 97, 103, 0, 122, 1, 161, 195, 108, 109, 161, 195, 116, 2, 195, 169, 107, 0, 122, 1, 161, 195, 108, 114, 111, 116, 105, 118, 0, 122, 1, 161, 195, 108, 116, 179, 195, 112, 0, 122, 1, 161, 195, 108, 117, 100, 110, 161, 195, 114, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 108, 117, 103, 161, 195, 116, 2, 97, 98, 195, 161, 108, 121, 0, 122, 1, 161, 195, 108, 117, 106, 161, 195, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 108, 179, 195, 122, 115, 2, 97, 98, 97, 100, 0, 122, 1, 161, 195, 109, 2, 101, 114, 0, 122, 1, 161, 195, 109, 2, 111, 114, 0, 122, 1, 161, 195, 109, 2, 197, 145, 114, 0, 122, 1, 161, 195, 109, 108, 97, 2, 195, 188, 114, 107, 0, 122, 1, 161, 195, 109, 108, 97, 2, 195, 188, 114, 107, 101, 0, 122, 1, 161, 195, 109, 111, 116, 161, 195, 108, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 109, 111, 121, 110, 2, 97, 98, 0, 122, 1, 161, 195, 109, 111, 121, 110, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 110, 97, 98, 98, 111, 114, 2, 101, 114, 0, 122, 1, 161, 195, 110, 97, 98, 98, 111, 115, 99, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 110, 97, 104, 117, 122, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 110, 97, 107, 107, 105, 121, 110, 2, 101, 114, 0, 122, 1, 161, 195, 110, 97, 108, 108, 105, 118, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 110, 97, 116, 116, 97, 115, 99, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 110, 103, 161, 195, 109, 0, 122, 1, 161, 195, 110, 114, 97, 98, 2, 197, 145, 107, 0, 122, 1, 161, 195, 110, 114, 161, 195, 112, 2, 195, 169, 107, 0, 122, 1, 161, 195, 110, 169, 195, 122, 115, 2, 101, 107, 0, 122, 1, 161, 195, 112, 97, 115, 99, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 112, 97, 115, 99, 2, 195, 161, 109, 0, 122, 1, 161, 195, 114, 97, 112, 97, 107, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 114, 97, 118, 97, 107, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 114, 97, 118, 97, 115, 99, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 114, 103, 117, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 114, 161, 195, 106, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 114, 161, 195, 106, 2, 111, 108, 103, 195, 161, 108, 97, 116, 0, 122, 1, 161, 195, 114, 173, 195, 2, 97, 107, 195, 169, 114, 0, 122, 1, 161, 195, 114, 173, 195, 145, 197, 108, 101, 2, 101, 114, 0, 122, 1, 161, 195, 114, 186, 195, 122, 115, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 116, 97, 103, 117, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 116, 97, 104, 2, 195, 188, 110, 101, 0, 122, 1, 161, 195, 116, 97, 108, 108, 97, 118, 2, 101, 114, 0, 122, 1, 161, 195, 116, 97, 116, 122, 111, 107, 116, 97, 108, 105, 121, 110, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 116, 97, 118, 105, 104, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 116, 106, 97, 104, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 116, 106, 186, 195, 121, 103, 2, 97, 98, 195, 161, 108, 121, 0, 122, 1, 161, 195, 116, 108, 111, 107, 105, 115, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 116, 110, 161, 195, 114, 0, 122, 1, 161, 195, 116, 110, 161, 195, 114, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 116, 114, 105, 2, 195, 169, 108, 0, 122, 1, 161, 195, 116, 161, 195, 108, 2, 195, 182, 103, 0, 122, 1, 161, 195, 116, 161, 195, 108, 108, 101, 2, 101, 114, 0, 122, 1, 161, 195, 116, 173, 195, 115, 97, 116, 117, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 118, 108, 97, 2, 101, 103, 0, 122, 1, 161, 195, 118, 173, 195, 104, 105, 107, 0, 122, 1, 161, 195, 121, 110, 161, 195, 104, 2, 97, 103, 0, 122, 1, 161, 195, 121, 116, 114, 161, 195, 104, 2, 195, 161, 114, 110, 121, 0, 122, 1, 161, 195, 122, 97, 116, 117, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 122, 111, 107, 97, 114, 179, 195, 122, 115, 2, 195, 161, 109, 0, 122, 1, 161, 195, 122, 111, 107, 108, 97, 108, 103, 111, 102, 2, 101, 114, 197, 177, 0, 122, 1, 161, 195, 122, 114, 161, 195, 103, 117, 115, 0, 122, 1, 169, 195, 100, 145, 197, 122, 114, 101, 122, 115, 2, 101, 0, 122, 1, 169, 195, 103, 110, 101, 108, 2, 97, 98, 195, 161, 108, 121, 0, 122, 1, 169, 195, 103, 110, 101, 114, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 103, 110, 101, 122, 103, 169, 195, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 103, 114, 101, 112, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 103, 114, 182, 195, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 103, 114, 182, 195, 100, 0, 122, 1, 169, 195, 103, 114, 182, 195, 100, 121, 110, 110, 101, 109, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 103, 122, 101, 114, 2, 195, 161, 109, 0, 122, 1, 169, 195, 103, 145, 197, 98, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 103, 169, 195, 2, 97, 98, 195, 161, 108, 121, 0, 122, 1, 169, 195, 103, 169, 195, 2, 97, 103, 0, 122, 1, 169, 195, 103, 182, 195, 104, 182, 195, 107, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 107, 2, 195, 186, 114, 195, 161, 115, 0, 122, 1, 169, 195, 107, 182, 195, 108, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 107, 182, 195, 108, 2, 195, 161, 109, 0, 122, 1, 169, 195, 108, 101, 107, 169, 195, 122, 114, 169, 195, 2, 105, 110, 116, 0, 122, 1, 169, 195, 108, 101, 109, 101, 2, 101, 114, 0, 122, 1, 169, 195, 108, 101, 114, 101, 122, 115, 2, 101, 116, 116, 0, 122, 1, 169, 195, 108, 101, 115, 105, 118, 100, 110, 111, 103, 2, 101, 114, 0, 122, 1, 169, 195, 108, 107, 182, 195, 121, 110, 182, 195, 107, 2, 195, 169, 108, 0, 122, 1, 169, 195, 108, 108, 101, 103, 182, 195, 122, 115, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 108, 121, 110, 169, 195, 118, 114, 182, 195, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 108, 145, 197, 100, 2, 195, 182, 103, 0, 122, 1, 169, 195, 108, 169, 195, 98, 2, 97, 108, 97, 103, 0, 122, 1, 169, 195, 108, 169, 195, 98, 2, 195, 182, 118, 0, 122, 1, 169, 195, 108, 188, 195, 2, 97, 107, 0, 122, 1, 169, 195, 108, 188, 195, 107, 101, 110, 101, 109, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 108, 188, 195, 112, 101, 108, 101, 116, 2, 101, 114, 0, 122, 1, 169, 195, 108, 188, 195, 112, 101, 114, 2, 101, 114, 0, 122, 1, 169, 195, 110, 101, 107, 107, 182, 195, 122, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 110, 101, 108, 101, 106, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 114, 112, 2, 101, 114, 0, 122, 1, 169, 195, 114, 169, 195, 107, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 114, 182, 195, 116, 2, 195, 182, 103, 0, 122, 1, 169, 195, 114, 182, 195, 116, 105, 107, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 115, 101, 2, 195, 182, 103, 0, 122, 1, 169, 195, 116, 101, 100, 114, 105, 104, 2, 101, 114, 118, 101, 0, 122, 1, 169, 195, 116, 101, 100, 114, 105, 104, 2, 195, 182, 118, 101, 103, 0, 122, 1, 169, 195, 116, 101, 103, 169, 195, 98, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 116, 101, 107, 101, 102, 2, 195, 188, 114, 107, 0, 122, 1, 169, 195, 116, 101, 108, 188, 195, 122, 115, 2, 97, 98, 0, 122, 1, 169, 195, 116, 101, 112, 101, 108, 103, 101, 109, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 116, 101, 116, 2, 101, 0, 122, 1, 169, 195, 116, 101, 116, 108, 101, 100, 110, 101, 114, 2, 101, 114, 0, 122, 1, 169, 195, 116, 106, 101, 108, 2, 195, 182, 103, 0, 122, 1, 169, 195, 116, 108, 182, 195, 116, 2, 97, 98, 0, 122, 1, 169, 195, 116, 108, 182, 195, 116, 2, 97, 98, 195, 161, 108, 121, 111, 122, 0, 122, 1, 169, 195, 116, 108, 182, 195, 116, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 116, 108, 182, 195, 116, 2, 195, 161, 109, 0, 122, 1, 169, 195, 116, 110, 101, 108, 101, 106, 2, 105, 110, 116, 0, 122, 1, 169, 195, 116, 110, 105, 104, 182, 195, 107, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 116, 114, 101, 115, 0, 122, 1, 169, 195, 116, 114, 169, 195, 115, 2, 195, 161, 109, 0, 122, 1, 169, 195, 116, 122, 115, 101, 118, 169, 195, 116, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 116, 173, 195, 114, 101, 107, 0, 122, 1, 169, 195, 116, 173, 195, 114, 101, 121, 110, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 116, 177, 197, 102, 2, 97, 103, 0, 122, 1, 169, 195, 116, 182, 195, 107, 0, 122, 1, 169, 195, 116, 188, 195, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 116, 188, 195, 2, 195, 161, 109, 0, 122, 1, 169, 195, 116, 188, 195, 97, 116, 106, 97, 114, 2, 101, 114, 0, 122, 1, 169, 195, 118, 182, 195, 108, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 118, 182, 195, 108, 121, 108, 111, 116, 122, 115, 105, 112, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 122, 101, 107, 108, 101, 100, 110, 101, 114, 2, 101, 114, 0, 122, 1, 169, 195, 122, 108, 101, 106, 2, 101, 114, 197, 177, 0, 122, 1, 169, 195, 122, 145, 197, 116, 114, 101, 102, 2, 101, 114, 197, 177, 0, 122, 1, 179, 195, 100, 97, 2, 195, 161, 109, 108, 97, 0, 122, 1, 179, 195, 105, 99, 161, 195, 107, 105, 110, 117, 109, 109, 111, 107, 2, 111, 98, 0, 122, 1, 179, 195, 105, 100, 161, 195, 114, 2, 101, 114, 101, 112, 0, 122, 1, 179, 195, 105, 100, 161, 195, 114, 2, 111, 98, 0, 122, 1, 179, 195, 107, 105, 115, 99, 0, 122, 1, 179, 195, 107, 105, 115, 99, 2, 195, 161, 109, 0, 122, 1, 179, 195, 110, 111, 118, 2, 101, 114, 101, 110, 195, 161, 100, 0, 122, 1, 179, 195, 112, 109, 97, 107, 0, 122, 1, 179, 195, 114, 186, 195, 122, 115, 2, 101, 109, 0, 122, 1, 179, 195, 116, 117, 97, 2, 101, 109, 195, 188, 118, 101, 103, 0, 122, 1, 179, 195, 118, 186, 195, 102, 2, 101, 114, 115, 122, 0, 122, 1, 179, 195, 118, 186, 195, 102, 2, 105, 109, 0, 122, 1, 182, 195, 108, 182, 195, 102, 106, 101, 116, 2, 195, 161, 106, 0, 122, 1, 182, 195, 114, 107, 182, 195, 2, 101, 107, 195, 169, 114, 0, 122, 1, 182, 195, 114, 145, 197, 122, 115, 2, 195, 173, 118, 0, 122, 1, 182, 195, 114, 182, 195, 118, 2, 101, 109, 0, 122, 1, 182, 195, 116, 110, 182, 195, 107, 0, 122, 1, 182, 195, 116, 110, 182, 195, 107, 2, 101, 114, 197, 177, 0, 122, 1, 182, 195, 118, 177, 197, 104, 2, 101, 109, 197, 177, 0, 122, 1, 186, 195, 100, 2, 97, 107, 195, 161, 108, 108, 0, 122, 1, 186, 195, 104, 2, 97, 102, 116, 0, 122, 1, 186, 195, 104, 2, 101, 107, 114, 195, 169, 110, 121, 0, 122, 1, 186, 195, 104, 2, 101, 108, 101, 116, 0, 122, 1, 186, 195, 104, 2, 195, 161, 108, 108, 195, 173, 116, 0, 122, 1, 186, 195, 121, 103, 161, 195, 0, 122, 1, 188, 195, 108, 112, 2, 101, 114, 197, 177, 0, 122, 2, 195, 173, 110, 197, 177, 0, 122, 8, 97, 100, 114, 111, 0, 122, 8, 97, 107, 97, 107, 2, 195, 179, 0, 122, 8, 97, 107, 114, 97, 102, 2, 105, 103, 0, 122, 8, 97, 107, 114, 97, 102, 2, 195, 161, 106, 0, 122, 8, 97, 110, 105, 0, 122, 8, 97, 115, 2, 101, 103, 0, 122, 8, 97, 115, 2, 195, 161, 114, 110, 121, 0, 122, 8, 97, 116, 117, 115, 97, 118, 0, 122, 8, 97, 118, 109, 97, 104, 2, 195, 188, 114, 107, 101, 0, 122, 8, 101, 100, 169, 195, 2, 101, 115, 122, 116, 101, 115, 116, 0, 122, 8, 101, 103, 169, 195, 115, 99, 110, 101, 122, 115, 2, 197, 177, 122, 0, 122, 8, 101, 107, 101, 114, 101, 107, 2, 195, 169, 107, 0, 122, 8, 101, 110, 169, 195, 109, 0, 122, 8, 101, 114, 101, 118, 0, 122, 8, 101, 116, 110, 101, 104, 2, 97, 107, 0, 122, 8, 101, 122, 115, 101, 109, 2, 195, 188, 114, 0, 122, 8, 105, 102, 107, 97, 98, 0, 122, 8, 105, 107, 2, 195, 161, 108, 108, 195, 161, 0, 122, 8, 105, 112, 115, 161, 195, 106, 2, 111, 98, 0, 122, 8, 105, 114, 103, 105, 116, 0, 122, 8, 105, 114, 145, 197, 107, 0, 122, 8, 105, 115, 97, 104, 2, 97, 103, 0, 122, 8, 111, 103, 161, 195, 108, 105, 118, 2, 101, 109, 0, 122, 8, 111, 107, 2, 101, 109, 0, 122, 8, 111, 107, 122, 115, 105, 112, 0, 122, 8, 111, 112, 97, 110, 2, 111, 98, 0, 122, 8, 111, 114, 161, 195, 118, 0, 122, 8, 111, 114, 161, 195, 118, 2, 195, 169, 108, 0, 122, 8, 111, 121, 103, 110, 111, 114, 0, 122, 8, 114, 101, 118, 2, 101, 114, 0, 122, 8, 114, 111, 115, 2, 101, 115, 122, 195, 169, 108, 121, 0, 122, 8, 114, 111, 121, 103, 0, 122, 8, 114, 161, 195, 104, 0, 122, 8, 114, 161, 195, 116, 2, 111, 98, 0, 122, 8, 114, 161, 195, 121, 110, 2, 101, 114, 197, 177, 0, 122, 8, 117, 100, 108, 111, 107, 2, 101, 0, 122, 8, 117, 103, 179, 195, 103, 97, 100, 101, 112, 2, 101, 114, 0, 122, 8, 117, 107, 101, 104, 2, 97, 103, 0, 122, 8, 117, 107, 179, 195, 109, 0, 122, 8, 117, 112, 173, 195, 116, 2, 195, 161, 109, 0, 122, 8, 117, 112, 173, 195, 116, 2, 195, 182, 118, 101, 103, 0, 122, 8, 117, 114, 173, 195, 118, 2, 101, 114, 0, 122, 8, 145, 197, 2, 101, 108, 108, 0, 122, 8, 145, 197, 2, 101, 114, 197, 177, 0, 122, 8, 145, 197, 2, 105, 0, 122, 8, 145, 197, 2, 111, 107, 195, 161, 0, 122, 8, 145, 197, 2, 195, 169, 107, 0, 122, 8, 145, 197, 104, 0, 122, 8, 161, 195, 102, 2, 195, 173, 110, 0, 122, 8, 161, 195, 103, 97, 99, 97, 107, 2, 101, 114, 0, 122, 8, 161, 195, 103, 114, 111, 102, 0, 122, 8, 161, 195, 107, 97, 108, 0, 122, 8, 161, 195, 107, 97, 114, 0, 122, 8, 161, 195, 108, 97, 2, 111, 108, 103, 0, 122, 8, 161, 195, 108, 179, 195, 122, 115, 0, 122, 8, 161, 195, 109, 2, 195, 179, 0, 122, 8, 161, 195, 109, 111, 108, 108, 97, 118, 0, 122, 8, 161, 195, 114, 114, 111, 102, 0, 122, 8, 161, 195, 115, 0, 122, 8, 161, 195, 115, 122, 179, 195, 114, 2, 197, 145, 107, 0, 122, 8, 161, 195, 116, 97, 104, 2, 101, 114, 0, 122, 8, 161, 195, 116, 110, 97, 107, 114, 111, 104, 2, 101, 114, 0, 122, 8, 161, 195, 116, 114, 111, 112, 0, 122, 8, 161, 195, 116, 161, 195, 108, 2, 195, 182, 103, 0, 122, 8, 169, 195, 99, 101, 114, 2, 195, 161, 114, 195, 186, 0, 122, 8, 169, 195, 100, 101, 107, 108, 101, 122, 173, 195, 104, 0, 122, 8, 169, 195, 103, 169, 195, 0, 122, 8, 169, 195, 107, 112, 105, 115, 99, 0, 122, 8, 169, 195, 114, 2, 101, 114, 197, 177, 0, 122, 8, 169, 195, 116, 101, 100, 108, 188, 195, 107, 0, 122, 8, 169, 195, 116, 101, 116, 110, 188, 195, 116, 105, 107, 0, 122, 8, 169, 195, 116, 101, 118, 0, 122, 8, 169, 195, 116, 106, 101, 108, 0, 122, 8, 169, 195, 116, 173, 195, 114, 101, 107, 2, 97, 103, 0, 122, 8, 169, 195, 118, 101, 107, 0, 122, 8, 169, 195, 118, 101, 107, 2, 101, 114, 0, 122, 8, 169, 195, 122, 101, 100, 110, 101, 114, 101, 98, 2, 101, 0, 122, 8, 179, 195, 106, 0, 122, 8, 179, 195, 106, 97, 104, 0, 122, 8, 179, 195, 116, 173, 195, 114, 105, 112, 2, 101, 0, 122, 8, 182, 195, 114, 107, 182, 195, 2, 101, 103, 0, 122, 8, 182, 195, 114, 107, 182, 195, 2, 101, 107, 101, 114, 101, 0, 122, 8, 182, 195, 114, 107, 188, 195, 116, 0, 122, 8, 182, 195, 114, 182, 195, 107, 2, 105, 103, 0, 122, 8, 182, 195, 114, 182, 195, 118, 0, 122, 8, 186, 195, 104, 2, 97, 108, 111, 110, 110, 97, 0, 122, 8, 186, 195, 104, 2, 105, 103, 101, 116, 0, 122, 8, 186, 195, 104, 2, 195, 173, 110, 0, 7, 6, 115, 122, 0, 4, 3, 87, 0, 1, 97, 118, 97, 114, 2, 195, 161, 114, 0, 1, 97, 118, 97, 116, 2, 195, 161, 114, 97, 0, 1, 100, 110, 101, 114, 2, 101, 114, 101, 116, 197, 145, 0, 1, 100, 110, 101, 114, 2, 101, 114, 3, 87, 12, 0, 4, 116, 1, 97, 114, 97, 112, 2, 115, 101, 103, 103, 3, 87, 47, 0, 116, 1, 101, 98, 122, 97, 2, 115, 105, 115, 97, 107, 0, 116, 1, 101, 114, 101, 107, 2, 115, 111, 114, 0, 116, 1, 101, 114, 101, 107, 2, 115, 122, 101, 114, 0, 116, 1, 117, 121, 110, 2, 115, 195, 188, 118, 101, 103, 0, 4, 116, 115, 122, 3, 87, 47, 87, 0, 116, 115, 122, 1, 97, 114, 97, 112, 2, 97, 103, 0, 116, 115, 122, 1, 97, 114, 97, 112, 2, 97, 110, 100, 195, 161, 108, 0, 116, 115, 122, 1, 97, 114, 97, 112, 2, 101, 107, 0, 116, 115, 122, 1, 101, 114, 101, 107, 2, 101, 0, 116, 115, 122, 1, 105, 108, 2, 101, 114, 197, 177, 0, 116, 115, 122, 1, 105, 116, 97, 98, 2, 101, 114, 197, 177, 0, 116, 115, 122, 8, 97, 109, 97, 100, 0, 4, 116, 115, 122, 101, 1, 105, 116, 97, 98, 2, 103, 195, 169, 3, 87, 47, 87, 107, 0, 116, 115, 122, 101, 1, 105, 116, 101, 109, 97, 0, 116, 115, 122, 101, 1, 111, 114, 100, 2, 114, 122, 197, 145, 0, 116, 115, 122, 101, 8, 97, 107, 0, 4, 116, 115, 1, 97, 108, 97, 109, 2, 117, 103, 97, 108, 3, 87, 47, 89, 0, 116, 115, 1, 97, 114, 97, 112, 2, 105, 104, 101, 100, 0, 116, 115, 1, 97, 114, 97, 112, 2, 111, 110, 107, 0, 116, 115, 1, 97, 114, 97, 112, 2, 111, 114, 115, 0, 116, 115, 1, 97, 114, 97, 112, 2, 117, 104, 97, 110, 0, 116, 115, 1, 97, 114, 97, 112, 2, 195, 188, 116, 101, 0, 116, 115, 1, 101, 116, 2, 111, 114, 111, 122, 0, 116, 115, 8, 97, 109, 97, 100, 0, 116, 115, 3, 87, 74, 12, 0, 116, 115, 122, 97, 3, 87, 117, 106, 0, 116, 115, 122, 101, 3, 87, 117, 107, 0, 115, 1, 169, 195, 103, 101, 2, 195, 169, 103, 3, 89, 0, 4, 115, 1, 97, 103, 105, 2, 195, 161, 103, 111, 115, 3, 89, 12, 0, 115, 1, 169, 195, 107, 103, 101, 108, 2, 195, 169, 103, 101, 115, 0, 1, 97, 118, 2, 97, 98, 108, 3, 89, 15, 86, 0, 4, 1, 97, 118, 2, 195, 161, 112, 111, 114, 3, 89, 86, 0, 1, 97, 118, 2, 195, 161, 114, 0, 1, 111, 114, 97, 109, 2, 117, 103, 0, 1, 161, 195, 108, 108, 97, 104, 2, 97, 118, 97, 114, 0, 1, 161, 195, 121, 108, 107, 161, 195, 102, 2, 101, 110, 101, 0, 1, 169, 195, 118, 101, 2, 97, 118, 97, 114, 0, 1, 179, 195, 110, 111, 118, 2, 101, 110, 101, 0, 1, 182, 195, 114, 182, 195, 107, 2, 117, 103, 0, 2, 97, 99, 115, 107, 0, 2, 195, 182, 108, 100, 0, 4, 115, 1, 97, 118, 2, 97, 110, 195, 169, 114, 3, 89, 88, 0, 115, 1, 97, 118, 2, 195, 173, 114, 0, 115, 1, 101, 122, 105, 118, 2, 101, 109, 0, 115, 1, 161, 195, 107, 110, 111, 115, 2, 101, 109, 108, 0, 115, 1, 161, 195, 116, 2, 105, 110, 0, 115, 1, 169, 195, 116, 114, 101, 115, 2, 195, 173, 114, 0, 115, 2, 195, 161, 107, 0, 7, 6, 116, 106, 0, 4, 1, 97, 104, 2, 101, 103, 121, 197, 177, 3, 47, 57, 0, 1, 97, 108, 108, 161, 195, 2, 195, 179, 108, 195, 169, 116, 0, 1, 97, 108, 111, 100, 110, 111, 103, 2, 101, 108, 0, 1, 97, 108, 117, 103, 110, 97, 104, 2, 97, 118, 195, 173, 116, 0, 1, 97, 108, 117, 103, 110, 97, 104, 2, 101, 108, 0, 1, 97, 109, 97, 121, 108, 111, 102, 2, 101, 108, 0, 1, 97, 110, 111, 118, 2, 101, 103, 121, 0, 1, 97, 112, 97, 115, 99, 2, 101, 108, 0, 1, 97, 112, 97, 115, 99, 2, 195, 161, 116, 195, 169, 107, 0, 1, 97, 122, 111, 103, 108, 111, 100, 2, 97, 118, 195, 173, 116, 0, 1, 101, 108, 98, 98, 182, 195, 116, 2, 195, 182, 118, 101, 100, 101, 108, 0, 1, 101, 108, 101, 116, 122, 115, 105, 116, 2, 101, 103, 121, 0, 1, 101, 108, 114, 169, 195, 98, 2, 101, 103, 121, 0, 1, 101, 108, 169, 195, 2, 101, 108, 0, 1, 101, 108, 169, 195, 2, 195, 161, 114, 97, 100, 195, 169, 107, 0, 1, 101, 108, 188, 195, 114, 101, 116, 2, 101, 108, 195, 182, 108, 0, 1, 101, 109, 169, 195, 110, 2, 117, 104, 195, 161, 0, 1, 101, 110, 101, 109, 2, 101, 103, 103, 121, 0, 1, 101, 110, 101, 109, 2, 101, 103, 121, 0, 1, 101, 110, 101, 122, 188, 195, 2, 101, 108, 0, 1, 101, 110, 114, 101, 116, 110, 105, 2, 101, 103, 121, 0, 1, 101, 110, 188, 195, 122, 115, 2, 101, 108, 0, 1, 101, 115, 101, 2, 111, 103, 0, 1, 101, 122, 101, 106, 101, 102, 2, 101, 108, 0, 1, 101, 122, 115, 169, 195, 109, 114, 101, 116, 2, 111, 103, 0, 1, 101, 122, 115, 169, 195, 109, 114, 101, 116, 2, 195, 161, 114, 0, 1, 101, 122, 115, 169, 195, 109, 114, 101, 116, 2, 195, 161, 116, 195, 169, 107, 0, 1, 101, 122, 121, 108, 101, 104, 2, 101, 108, 0, 1, 101, 122, 177, 197, 121, 116, 110, 101, 108, 108, 105, 98, 2, 101, 108, 0, 1, 108, 111, 104, 2, 195, 161, 116, 195, 169, 107, 0, 1, 110, 97, 107, 107, 111, 114, 2, 195, 161, 114, 97, 100, 195, 169, 107, 0, 1, 110, 101, 122, 115, 2, 195, 161, 110, 111, 115, 0, 1, 110, 111, 114, 102, 2, 195, 161, 114, 0, 1, 110, 111, 115, 99, 2, 195, 161, 116, 195, 169, 107, 0, 1, 111, 112, 97, 108, 108, 161, 195, 2, 97, 118, 117, 108, 0, 1, 111, 112, 97, 108, 108, 161, 195, 2, 101, 108, 0, 1, 114, 111, 112, 115, 2, 195, 161, 116, 195, 169, 107, 0, 1, 114, 188, 195, 107, 2, 101, 108, 0, 1, 115, 101, 116, 2, 195, 161, 116, 195, 169, 107, 0, 1, 115, 188, 195, 122, 101, 2, 101, 108, 118, 0, 1, 122, 115, 182, 195, 114, 182, 195, 107, 2, 195, 161, 114, 0, 1, 161, 195, 2, 117, 115, 115, 0, 1, 161, 195, 2, 117, 116, 0, 1, 161, 195, 2, 195, 161, 114, 0, 1, 161, 195, 2, 195, 182, 0, 1, 161, 195, 2, 195, 182, 104, 101, 0, 1, 161, 195, 2, 195, 182, 110, 0, 1, 161, 195, 2, 195, 182, 115, 115, 122, 0, 1, 161, 195, 2, 195, 182, 116, 0, 1, 169, 195, 104, 2, 101, 103, 121, 197, 177, 0, 1, 169, 195, 107, 2, 101, 103, 121, 197, 177, 0, 1, 169, 195, 107, 105, 112, 2, 195, 161, 116, 115, 122, 0, 1, 169, 195, 108, 2, 111, 103, 111, 115, 117, 108, 116, 115, 195, 161, 103, 0, 1, 169, 195, 110, 101, 122, 2, 195, 161, 116, 115, 122, 0, 1, 179, 195, 107, 115, 2, 117, 104, 195, 161, 115, 122, 0, 1, 179, 195, 112, 2, 101, 0, 1, 182, 195, 2, 101, 103, 121, 197, 177, 0, 1, 186, 195, 2, 97, 118, 195, 173, 0, 1, 186, 195, 2, 101, 108, 122, 195, 169, 115, 0, 1, 186, 195, 2, 101, 108, 122, 197, 145, 0, 1, 186, 195, 2, 111, 103, 0, 2, 101, 108, 0, 8, 97, 122, 161, 195, 108, 98, 161, 195, 116, 2, 101, 103, 121, 0, 8, 101, 108, 101, 116, 122, 115, 105, 116, 2, 101, 108, 0, 8, 101, 108, 122, 115, 169, 195, 107, 2, 101, 108, 101, 110, 0, 8, 110, 97, 122, 115, 101, 100, 2, 195, 161, 114, 109, 0, 8, 122, 115, 101, 114, 101, 107, 2, 195, 161, 0, 8, 122, 115, 169, 195, 118, 2, 195, 179, 115, 108, 0, 8, 161, 195, 2, 101, 108, 101, 110, 116, 107, 101, 122, 0, 8, 161, 195, 2, 117, 0, 8, 161, 195, 2, 195, 182, 106, 0, 4, 195, 161, 116, 115, 115, 122, 1, 161, 195, 3, 47, 57, 112, 117, 12, 0, 195, 161, 116, 115, 122, 1, 161, 195, 0, 4, 1, 17, 67, 3, 78, 0, 1, 110, 111, 115, 99, 0, 1, 114, 188, 195, 107, 0, 1, 115, 188, 195, 122, 101, 0, 4, 1, 17, 65, 2, 17, 65, 3, 78, 12, 0, 1, 101, 108, 122, 188, 195, 0, 1, 161, 195, 103, 2, 195, 161, 114, 0, 1, 161, 195, 104, 2, 195, 161, 114, 0, 1, 161, 195, 108, 114, 111, 107, 2, 195, 161, 114, 97, 0, 1, 161, 195, 114, 97, 98, 2, 195, 161, 114, 0, 7, 6, 116, 115, 0, 4, 122, 1, 97, 100, 97, 3, 47, 87, 0, 122, 1, 97, 100, 97, 2, 111, 108, 103, 195, 161, 108, 116, 97, 116, 0, 122, 1, 97, 104, 2, 195, 161, 122, 0, 122, 1, 97, 108, 117, 100, 110, 105, 2, 195, 179, 0, 122, 1, 101, 108, 98, 98, 182, 195, 116, 2, 111, 108, 0, 122, 1, 101, 108, 188, 195, 115, 99, 101, 98, 2, 195, 179, 0, 122, 1, 101, 110, 2, 111, 0, 122, 1, 101, 110, 101, 109, 2, 195, 169, 108, 0, 122, 1, 101, 116, 101, 114, 101, 122, 115, 2, 111, 108, 103, 195, 161, 108, 97, 116, 0, 122, 1, 101, 122, 109, 101, 110, 2, 111, 0, 122, 1, 105, 104, 2, 101, 0, 122, 1, 105, 104, 2, 195, 179, 0, 122, 1, 106, 101, 115, 2, 195, 182, 0, 122, 1, 110, 97, 108, 2, 195, 179, 0, 122, 1, 110, 101, 98, 2, 111, 114, 117, 108, 0, 122, 1, 110, 101, 122, 115, 2, 111, 98, 114, 111, 107, 0, 122, 1, 110, 101, 122, 115, 2, 195, 169, 107, 0, 122, 1, 110, 111, 114, 102, 2, 111, 108, 103, 195, 161, 108, 0, 122, 1, 110, 111, 115, 99, 2, 195, 169, 110, 0, 122, 1, 110, 161, 195, 112, 2, 195, 169, 108, 0, 122, 1, 111, 112, 97, 121, 103, 0, 122, 1, 114, 101, 107, 2, 111, 109, 115, 122, 195, 169, 100, 0, 122, 1, 114, 111, 112, 115, 2, 111, 108, 103, 195, 161, 108, 0, 122, 1, 114, 188, 195, 107, 2, 195, 179, 0, 122, 1, 161, 195, 2, 97, 0, 122, 1, 161, 195, 2, 101, 0, 122, 1, 161, 195, 2, 111, 107, 0, 122, 1, 161, 195, 2, 195, 182, 0, 122, 1, 161, 195, 2, 195, 186, 0, 122, 1, 161, 195, 2, 197, 145, 0, 122, 1, 161, 195, 2, 197, 177, 0, 122, 1, 161, 195, 98, 97, 107, 2, 195, 169, 0, 122, 1, 161, 195, 104, 2, 195, 169, 108, 0, 122, 1, 161, 195, 108, 2, 101, 0, 122, 1, 161, 195, 108, 2, 101, 114, 195, 169, 115, 122, 0, 122, 1, 161, 195, 122, 115, 115, 97, 112, 2, 195, 169, 108, 0, 122, 1, 169, 195, 104, 2, 195, 161, 122, 0, 122, 1, 169, 195, 107, 2, 101, 114, 101, 112, 0, 122, 1, 169, 195, 107, 2, 195, 161, 122, 0, 122, 1, 169, 195, 107, 2, 195, 173, 110, 0, 122, 1, 169, 195, 108, 2, 195, 161, 109, 0, 122, 1, 169, 195, 116, 182, 195, 115, 2, 197, 145, 107, 101, 0, 122, 1, 179, 195, 107, 115, 2, 111, 107, 110, 121, 0, 122, 1, 179, 195, 114, 100, 2, 197, 145, 114, 0, 122, 1, 182, 195, 2, 195, 161, 122, 0, 122, 1, 186, 195, 2, 111, 114, 111, 115, 0, 122, 1, 186, 195, 2, 195, 169, 108, 0, 122, 2, 97, 0, 122, 2, 101, 0, 122, 2, 195, 161, 0, 122, 8, 97, 104, 2, 111, 98, 0, 122, 8, 161, 195, 2, 111, 108, 103, 195, 161, 108, 0, 122, 8, 161, 195, 2, 111, 114, 111, 110, 103, 0, 122, 8, 161, 195, 2, 111, 114, 117, 108, 116, 0, 122, 8, 161, 195, 2, 111, 114, 195, 173, 116, 0, 122, 8, 169, 195, 104, 2, 111, 98, 0, 122, 8, 169, 195, 107, 2, 111, 98, 0, 122, 8, 179, 195, 112, 2, 195, 169, 107, 0, 122, 8, 182, 195, 2, 111, 98, 0, 122, 195, 169, 1, 169, 195, 122, 115, 3, 47, 87, 111, 0, 4, 1, 97, 100, 97, 3, 47, 89, 0, 1, 97, 100, 97, 108, 101, 102, 2, 111, 114, 0, 1, 97, 104, 2, 195, 161, 118, 0, 1, 97, 108, 108, 161, 195, 2, 101, 114, 101, 103, 0, 1, 97, 108, 111, 100, 110, 111, 103, 2, 111, 114, 0, 1, 97, 108, 114, 111, 107, 97, 121, 103, 2, 111, 114, 111, 122, 0, 1, 97, 108, 117, 100, 122, 111, 109, 2, 111, 0, 1, 97, 108, 161, 195, 103, 115, 122, 105, 118, 2, 111, 114, 0, 1, 97, 108, 161, 195, 103, 115, 122, 105, 118, 2, 111, 114, 111, 122, 97, 0, 1, 97, 109, 97, 121, 108, 111, 102, 2, 195, 161, 118, 0, 1, 97, 110, 97, 103, 97, 100, 2, 101, 106, 0, 1, 97, 114, 105, 108, 101, 102, 2, 195, 161, 118, 0, 1, 97, 122, 161, 195, 108, 98, 161, 195, 116, 2, 111, 114, 0, 1, 101, 103, 105, 122, 115, 2, 111, 114, 0, 1, 101, 108, 101, 118, 177, 197, 109, 2, 111, 0, 1, 101, 108, 101, 118, 177, 197, 109, 2, 195, 161, 118, 0, 1, 101, 108, 101, 121, 103, 101, 107, 2, 195, 169, 114, 0, 1, 101, 108, 114, 169, 195, 115, 173, 195, 107, 2, 111, 114, 111, 122, 97, 116, 0, 1, 101, 108, 122, 188, 195, 2, 111, 114, 0, 1, 101, 108, 188, 195, 112, 169, 195, 2, 97, 114, 111, 107, 0, 1, 101, 108, 188, 195, 112, 169, 195, 2, 97, 114, 111, 107, 0, 1, 101, 108, 188, 195, 114, 101, 116, 2, 195, 161, 118, 0, 1, 101, 108, 188, 195, 115, 99, 101, 98, 2, 195, 169, 0, 1, 101, 110, 2, 101, 0, 1, 101, 110, 2, 195, 161, 116, 111, 114, 0, 1, 101, 110, 101, 109, 2, 111, 114, 0, 1, 101, 118, 182, 195, 122, 115, 2, 97, 112, 107, 0, 1, 101, 122, 109, 101, 110, 2, 116, 114, 97, 116, 195, 169, 0, 1, 101, 122, 188, 195, 102, 97, 107, 110, 117, 109, 2, 97, 98, 108, 0, 1, 105, 98, 2, 101, 98, 101, 115, 115, 195, 169, 103, 0, 1, 105, 109, 2, 101, 0, 1, 108, 97, 98, 111, 107, 2, 117, 103, 195, 161, 114, 0, 1, 108, 111, 104, 2, 195, 161, 112, 97, 100, 116, 0, 1, 110, 105, 109, 2, 101, 109, 0, 1, 110, 111, 115, 99, 2, 195, 169, 114, 0, 1, 110, 161, 195, 114, 111, 107, 2, 101, 0, 1, 111, 111, 98, 2, 111, 114, 114, 101, 110, 100, 0, 1, 111, 112, 97, 108, 108, 161, 195, 2, 111, 114, 0, 1, 114, 97, 112, 2, 195, 161, 118, 0, 1, 114, 161, 195, 112, 2, 97, 106, 116, 195, 179, 0, 1, 114, 161, 195, 122, 2, 111, 114, 195, 186, 0, 1, 115, 101, 116, 2, 195, 169, 114, 0, 1, 117, 99, 110, 117, 104, 2, 195, 161, 103, 0, 1, 122, 115, 101, 116, 2, 111, 114, 0, 1, 161, 195, 2, 101, 103, 195, 173, 116, 0, 1, 161, 195, 2, 101, 106, 108, 101, 0, 1, 161, 195, 2, 111, 114, 0, 1, 161, 195, 2, 117, 103, 0, 1, 161, 195, 2, 117, 104, 0, 1, 161, 195, 2, 117, 114, 0, 1, 161, 195, 2, 195, 169, 0, 1, 161, 195, 2, 195, 182, 112, 114, 197, 145, 0, 1, 161, 195, 2, 195, 182, 112, 195, 182, 114, 0, 1, 161, 195, 2, 195, 188, 108, 116, 0, 1, 161, 195, 2, 195, 188, 116, 0, 1, 161, 195, 2, 195, 188, 118, 195, 173, 116, 0, 1, 161, 195, 103, 2, 195, 188, 108, 108, 121, 101, 100, 0, 1, 169, 195, 107, 2, 97, 114, 107, 195, 186, 0, 1, 169, 195, 107, 2, 97, 114, 111, 107, 0, 1, 169, 195, 107, 2, 101, 98, 101, 115, 115, 195, 169, 103, 101, 115, 0, 1, 169, 195, 107, 2, 111, 114, 0, 1, 169, 195, 107, 2, 195, 161, 118, 0, 1, 169, 195, 114, 182, 195, 115, 2, 101, 98, 0, 1, 179, 195, 107, 115, 2, 97, 112, 107, 97, 0, 1, 179, 195, 114, 100, 2, 195, 182, 118, 195, 169, 110, 110, 121, 0, 1, 179, 195, 114, 100, 2, 195, 182, 118, 195, 169, 110, 121, 0, 1, 179, 195, 122, 111, 98, 2, 111, 0, 1, 186, 195, 107, 2, 117, 103, 0, 8, 161, 195, 2, 111, 100, 111, 114, 0, 8, 186, 195, 2, 195, 161, 118, 0, 4, 1, 106, 3, 74, 0, 1, 110, 101, 109, 2, 118, 195, 161, 114, 0, 1, 110, 182, 195, 100, 2, 195, 182, 110, 0, 2, 32, 14, 128, 128, 130, 0, 2, 97, 0, 2, 101, 0, 2, 111, 0, 2, 117, 0, 2, 195, 161, 0, 2, 195, 169, 0, 4, 1, 97, 108, 108, 161, 195, 2, 195, 161, 103, 3, 74, 12, 0, 1, 97, 108, 117, 109, 0, 1, 101, 104, 101, 108, 2, 195, 169, 103, 0, 1, 101, 104, 101, 116, 2, 195, 169, 103, 0, 1, 101, 105, 115, 0, 1, 101, 107, 188, 195, 115, 2, 195, 169, 103, 0, 1, 101, 108, 106, 101, 102, 2, 195, 169, 103, 0, 1, 101, 109, 169, 195, 110, 2, 195, 169, 103, 0, 1, 101, 114, 101, 109, 115, 105, 2, 195, 169, 103, 0, 1, 101, 114, 169, 195, 2, 195, 169, 103, 0, 1, 101, 118, 101, 110, 2, 195, 169, 103, 0, 1, 101, 118, 182, 195, 107, 2, 195, 169, 103, 0, 1, 101, 118, 182, 195, 122, 115, 2, 195, 169, 103, 0, 1, 101, 122, 101, 108, 101, 116, 182, 195, 107, 2, 195, 169, 103, 0, 1, 101, 122, 105, 102, 2, 195, 169, 103, 0, 1, 101, 122, 109, 101, 110, 0, 1, 105, 103, 101, 115, 2, 195, 169, 0, 1, 111, 116, 97, 103, 111, 109, 161, 195, 116, 2, 195, 161, 103, 0, 1, 111, 122, 105, 98, 2, 195, 161, 103, 0, 1, 117, 99, 110, 117, 104, 2, 195, 161, 103, 0, 1, 161, 195, 2, 195, 179, 0, 1, 161, 195, 106, 97, 115, 2, 195, 161, 103, 0, 1, 161, 195, 112, 97, 2, 195, 161, 103, 0, 1, 161, 195, 114, 97, 98, 0, 1, 169, 195, 107, 2, 195, 169, 103, 0, 1, 169, 195, 109, 101, 122, 115, 2, 195, 169, 103, 0, 1, 169, 195, 114, 2, 195, 169, 103, 0, 1, 169, 195, 116, 182, 195, 115, 2, 195, 169, 103, 0, 1, 169, 195, 118, 2, 195, 169, 103, 0, 1, 173, 195, 103, 101, 115, 0, 1, 173, 195, 108, 108, 161, 195, 0, 1, 173, 195, 114, 111, 122, 115, 2, 97, 0, 1, 173, 195, 114, 188, 195, 2, 101, 0, 1, 177, 197, 102, 0, 1, 177, 197, 104, 0, 1, 182, 195, 116, 182, 195, 107, 2, 195, 169, 103, 0, 8, 161, 195, 104, 2, 195, 161, 103, 0, 100, 3, 74, 70, 0, 195, 182, 3, 74, 108, 0, 195, 188, 3, 74, 109, 0, 4, 122, 1, 101, 109, 2, 118, 101, 3, 117, 0, 122, 1, 101, 109, 101, 108, 2, 118, 195, 169, 110, 0, 122, 1, 161, 195, 106, 2, 104, 97, 115, 115, 0, 122, 1, 161, 195, 106, 2, 104, 97, 116, 0, 122, 1, 161, 195, 106, 2, 109, 0, 122, 1, 161, 195, 106, 2, 118, 0, 4, 115, 122, 1, 97, 108, 108, 97, 104, 2, 111, 110, 3, 117, 12, 0, 115, 122, 1, 101, 109, 2, 101, 0, 115, 122, 1, 101, 109, 2, 195, 188, 107, 0, 115, 122, 1, 161, 195, 106, 0, 115, 122, 1, 161, 195, 108, 2, 97, 110, 97, 107, 0, 115, 122, 1, 161, 195, 108, 2, 111, 110, 0, 115, 122, 8, 161, 195, 108, 2, 195, 169, 107, 0, 122, 1, 97, 108, 108, 97, 104, 2, 97, 0, 122, 1, 97, 108, 108, 97, 104, 2, 105, 107, 0, 122, 1, 101, 105, 115, 0, 122, 1, 101, 109, 2, 101, 0, 122, 1, 101, 109, 2, 101, 116, 0, 122, 1, 101, 109, 2, 105, 107, 0, 122, 1, 101, 116, 0, 122, 1, 161, 195, 106, 2, 17, 65, 0, 122, 1, 161, 195, 106, 2, 111, 107, 0, 122, 1, 161, 195, 108, 2, 17, 65, 0, 122, 1, 169, 195, 104, 2, 101, 114, 0, 122, 1, 169, 195, 107, 2, 101, 114, 0, 122, 1, 182, 195, 2, 195, 182, 114, 0, 122, 1, 182, 195, 112, 2, 101, 110, 0, 122, 2, 32, 14, 128, 128, 131, 0, 122, 2, 111, 0, 122, 2, 195, 169, 0, 122, 2, 197, 145, 0, 122, 195, 179, 2, 32, 14, 128, 128, 132, 3, 117, 12, 113, 0, 7, 6, 116, 116, 0, 4, 1, 97, 108, 97, 2, 106, 195, 161, 114, 3, 47, 0, 1, 101, 107, 105, 114, 107, 2, 106, 195, 161, 116, 0, 1, 101, 107, 105, 114, 107, 2, 106, 195, 161, 116, 0, 1, 111, 108, 97, 104, 2, 115, 195, 161, 112, 97, 100, 0, 1, 182, 195, 108, 188, 195, 122, 115, 110, 110, 101, 98, 2, 106, 101, 108, 109, 101, 122, 0, 4, 3, 47, 12, 0, 1, 101, 122, 101, 121, 108, 101, 104, 2, 114, 197, 145, 108, 0, 1, 122, 115, 101, 114, 101, 107, 2, 197, 177, 122, 0, 1, 169, 195, 122, 115, 2, 114, 97, 110, 99, 115, 195, 173, 114, 0, 103, 121, 3, 47, 12, 77, 0, 114, 3, 47, 52, 0, 4, 115, 2, 195, 161, 3, 74, 12, 0, 115, 2, 195, 169, 0, 4, 106, 3, 78, 12, 0, 121, 0, 121, 106, 0, 115, 122, 1, 101, 109, 2, 101, 116, 3, 117, 12, 0, 7, 6, 116, 121, 0, 1, 110, 101, 122, 115, 100, 110, 105, 109, 3, 47, 37, 0, 2, 97, 114, 100, 3, 47, 57, 0, 7, 6, 195, 161, 0, 3, 112, 0, 105, 103, 1, 21, 2, 32, 14, 128, 192, 131, 3, 112, 37, 79, 0, 116, 195, 179, 108, 1, 21, 2, 32, 14, 128, 192, 132, 3, 112, 47, 113, 55, 0, 110, 97, 107, 1, 21, 2, 32, 14, 128, 192, 132, 3, 112, 50, 106, 49, 0, 114, 97, 1, 21, 2, 32, 14, 128, 192, 131, 3, 112, 52, 106, 0, 98, 97, 110, 1, 21, 2, 32, 14, 128, 192, 132, 3, 112, 69, 106, 50, 0, 7, 6, 195, 169, 0, 3, 111, 0, 105, 2, 195, 169, 3, 111, 12, 110, 0, 105, 103, 1, 21, 2, 32, 14, 128, 192, 131, 3, 111, 37, 79, 0, 116, 197, 145, 108, 1, 21, 2, 32, 14, 128, 192, 132, 3, 111, 47, 116, 55, 0, 110, 101, 107, 1, 21, 2, 32, 14, 128, 192, 132, 3, 111, 50, 107, 49, 0, 114, 101, 1, 21, 2, 32, 14, 128, 192, 131, 3, 111, 52, 107, 0, 98, 101, 110, 1, 21, 2, 32, 14, 128, 192, 132, 3, 111, 69, 107, 50, 0, 104, 115, 195, 169, 103, 3, 111, 89, 111, 79, 0, 104, 115, 195, 169, 103, 103, 3, 111, 89, 111, 79, 12, 0, 7, 6, 195, 171, 0, 3, 108, 0, 7, 6, 195, 173, 0, 4, 1, 116, 2, 122, 101, 110, 3, 37, 0, 1, 116, 2, 122, 101, 115, 0, 1, 116, 2, 122, 101, 116, 0, 1, 118, 2, 122, 101, 110, 0, 1, 118, 2, 122, 195, 169, 114, 101, 0, 1, 122, 115, 2, 118, 97, 116, 110, 0, 1, 122, 115, 2, 118, 97, 116, 195, 161, 115, 0, 1, 122, 115, 2, 118, 101, 0, 8, 116, 2, 122, 195, 188, 107, 0, 8, 118, 2, 122, 105, 0, 8, 122, 115, 2, 110, 195, 169, 115, 115, 122, 0, 8, 122, 115, 2, 110, 195, 169, 115, 122, 0, 8, 122, 115, 2, 118, 97, 116, 116, 97, 107, 0, 8, 122, 115, 2, 118, 97, 116, 116, 195, 161, 107, 107, 0, 8, 122, 115, 2, 118, 97, 116, 195, 179, 0, 8, 122, 115, 103, 101, 109, 2, 118, 97, 116, 116, 97, 0, 116, 115, 122, 1, 100, 97, 98, 97, 122, 115, 3, 37, 117, 12, 0, 4, 3, 110, 0, 1, 116, 2, 122, 101, 115, 122, 0, 1, 122, 115, 2, 118, 101, 108, 0, 1, 122, 115, 2, 118, 101, 109, 195, 169, 115, 122, 116, 0, 1, 122, 115, 115, 101, 114, 103, 97, 2, 118, 0, 8, 118, 2, 122, 105, 195, 179, 0, 116, 115, 3, 110, 74, 12, 0, 116, 115, 100, 3, 110, 74, 70, 0, 116, 115, 122, 1, 122, 115, 101, 118, 3, 110, 117, 12, 0, 7, 6, 195, 179, 0, 3, 113, 0, 7, 6, 195, 182, 0, 3, 108, 0, 7, 6, 195, 186, 0, 4, 1, 104, 2, 103, 111, 109, 3, 40, 0, 1, 104, 2, 115, 122, 97, 110, 0, 1, 104, 2, 115, 122, 97, 115, 0, 1, 104, 2, 115, 122, 97, 116, 0, 8, 104, 2, 103, 103, 121, 0, 8, 104, 2, 103, 111, 99, 115, 0, 8, 104, 2, 103, 121, 0, 4, 3, 114, 0, 1, 104, 2, 115, 122, 97, 110, 110, 121, 0, 7, 6, 195, 188, 0, 3, 109, 0, 116, 116, 2, 18, 66, 3, 109, 47, 0, 116, 116, 3, 109, 47, 12, 0, 116, 116, 114, 3, 109, 47, 52, 0, 116, 116, 98, 3, 109, 47, 69, 0, 116, 116, 121, 2, 18, 66, 3, 109, 78, 0, 116, 116, 121, 3, 109, 78, 12, 0, 116, 116, 121, 114, 3, 109, 78, 52, 0, 116, 116, 121, 98, 3, 109, 78, 69, 0, 7, 6, 197, 145, 0, 3, 116, 0, 7, 6, 197, 177, 0, 4, 1, 116, 2, 122, 105, 106, 195, 161, 116, 195, 169, 107, 3, 109, 0, 8, 116, 2, 110, 106, 195, 182, 110, 0, 8, 116, 2, 110, 195, 169, 115, 0, 3, 115, 0, 7, 6, 97, 0, 8, 2, 32, 3, 2, 106, 0, 108, 1, 45, 32, 48, 48, 15, 2, 32, 3, 86, 106, 55, 0, 3, 106, 0, 108, 1, 45, 32, 48, 48, 48, 2, 32, 3, 106, 55, 0, 104, 104, 111, 122, 3, 106, 105, 39, 86, 0, 7, 6, 98, 0, 4, 1, 45, 98, 3, 0, 1, 45, 98, 98, 3, 0, 4, 3, 69, 0, 98, 2, 18, 66, 0, 98, 2, 45, 18, 66, 0, 4, 2, 45, 98, 3, 69, 12, 0, 98, 0, 98, 2, 45, 98, 0, 105, 122, 2, 17, 65, 3, 69, 37, 86, 4, 0, 98, 114, 3, 69, 52, 0, 98, 106, 3, 69, 57, 0, 97, 110, 1, 21, 2, 32, 14, 128, 192, 131, 3, 69, 106, 50, 0, 97, 116, 116, 104, 105, 195, 161, 110, 121, 8, 3, 69, 106, 78, 12, 112, 65, 37, 0, 101, 110, 1, 21, 2, 32, 14, 128, 128, 131, 3, 69, 107, 50, 0, 105, 101, 100, 101, 114, 109, 101, 105, 101, 114, 5, 1, 3, 69, 110, 70, 107, 52, 63, 112, 57, 107, 52, 0, 7, 6, 99, 0, 4, 1, 45, 99, 3, 0, 4, 1, 45, 99, 99, 3, 0, 4, 99, 115, 1, 45, 115, 99, 3, 0, 4, 99, 115, 1, 45, 115, 99, 99, 3, 0, 4, 115, 1, 45, 99, 3, 0, 4, 115, 1, 45, 115, 99, 3, 0, 115, 1, 45, 115, 99, 99, 3, 0, 107, 5, 1, 8, 111, 116, 115, 2, 104, 111, 108, 109, 3, 49, 0, 4, 99, 115, 1, 45, 99, 99, 3, 74, 0, 99, 115, 2, 18, 66, 0, 99, 115, 2, 45, 18, 66, 0, 115, 0, 115, 1, 45, 99, 99, 0, 115, 1, 105, 118, 97, 107, 2, 122, 0, 115, 1, 105, 118, 97, 107, 2, 122, 195, 161, 116, 111, 110, 121, 0, 115, 1, 108, 117, 107, 2, 122, 195, 182, 114, 103, 0, 115, 1, 108, 182, 195, 109, 188, 195, 121, 103, 2, 122, 115, 0, 115, 1, 110, 105, 108, 105, 98, 2, 122, 195, 182, 114, 0, 115, 1, 110, 105, 108, 105, 107, 2, 122, 195, 182, 114, 0, 115, 1, 110, 161, 195, 116, 2, 105, 99, 115, 0, 115, 1, 110, 161, 195, 116, 161, 195, 115, 2, 97, 112, 0, 115, 1, 114, 169, 195, 2, 195, 173, 112, 116, 101, 0, 115, 1, 117, 112, 97, 112, 0, 115, 1, 161, 195, 116, 114, 97, 107, 2, 122, 195, 161, 112, 111, 0, 4, 99, 115, 3, 74, 12, 0, 99, 115, 2, 45, 99, 99, 115, 0, 99, 115, 2, 45, 99, 115, 0, 115, 1, 161, 195, 114, 97, 98, 2, 195, 161, 103, 116, 97, 0, 115, 2, 45, 99, 99, 115, 0, 115, 2, 45, 99, 115, 0, 99, 115, 114, 3, 74, 52, 0, 115, 122, 1, 161, 195, 112, 97, 108, 97, 107, 2, 101, 110, 3, 74, 86, 0, 4, 99, 115, 2, 45, 115, 122, 3, 74, 87, 0, 115, 2, 45, 115, 122, 0, 115, 122, 115, 3, 74, 88, 0, 4, 3, 117, 0, 1, 97, 108, 97, 109, 2, 115, 195, 161, 0, 1, 97, 108, 97, 109, 2, 115, 195, 188, 108, 0, 1, 97, 122, 97, 108, 0, 1, 101, 114, 101, 112, 2, 99, 115, 0, 1, 101, 114, 101, 112, 2, 115, 195, 188, 116, 0, 1, 108, 105, 102, 2, 99, 115, 105, 122, 0, 1, 108, 111, 112, 2, 115, 111, 0, 1, 108, 111, 121, 110, 2, 115, 101, 98, 0, 1, 110, 97, 104, 117, 115, 0, 1, 110, 101, 99, 105, 108, 2, 115, 195, 169, 114, 116, 195, 169, 115, 0, 1, 110, 101, 108, 105, 107, 2, 99, 115, 97, 116, 111, 114, 110, 0, 1, 110, 101, 108, 105, 107, 2, 115, 99, 104, 105, 108, 108, 0, 1, 110, 101, 108, 105, 107, 2, 115, 195, 161, 118, 0, 1, 110, 101, 121, 103, 101, 102, 0, 1, 110, 101, 121, 110, 173, 195, 2, 115, 195, 169, 103, 0, 1, 110, 105, 114, 101, 103, 0, 1, 110, 111, 98, 97, 114, 97, 103, 2, 115, 101, 114, 0, 1, 110, 111, 103, 114, 97, 121, 110, 2, 99, 115, 0, 1, 110, 111, 114, 97, 118, 100, 117, 2, 115, 101, 114, 0, 1, 110, 161, 195, 108, 2, 99, 115, 0, 1, 110, 161, 195, 116, 2, 99, 115, 0, 1, 110, 161, 195, 116, 2, 115, 0, 1, 110, 182, 195, 108, 188, 195, 107, 2, 115, 195, 169, 0, 1, 111, 98, 114, 161, 195, 2, 99, 115, 195, 186, 99, 115, 0, 1, 111, 98, 114, 161, 195, 2, 115, 117, 100, 0, 1, 111, 122, 115, 2, 115, 101, 103, 195, 169, 108, 121, 0, 1, 114, 97, 2, 99, 115, 111, 110, 0, 1, 114, 97, 100, 117, 107, 2, 115, 111, 114, 111, 122, 97, 116, 0, 1, 114, 97, 104, 2, 99, 115, 101, 108, 101, 107, 0, 1, 114, 97, 104, 2, 99, 115, 111, 112, 111, 114, 116, 0, 1, 114, 101, 110, 2, 115, 116, 195, 179, 108, 97, 0, 1, 114, 111, 112, 2, 115, 122, 0, 1, 114, 111, 112, 2, 115, 195, 169, 0, 1, 114, 169, 195, 2, 115, 111, 100, 114, 0, 1, 114, 169, 195, 98, 2, 99, 115, 117, 116, 0, 1, 114, 169, 195, 98, 2, 115, 195, 188, 118, 101, 103, 0, 1, 161, 195, 112, 2, 115, 195, 179, 0, 1, 169, 195, 116, 105, 110, 97, 122, 115, 2, 99, 115, 0, 1, 179, 195, 98, 114, 161, 195, 2, 99, 115, 195, 186, 99, 115, 0, 1, 179, 195, 104, 111, 98, 2, 115, 97, 112, 107, 0, 1, 179, 195, 104, 111, 98, 2, 115, 105, 112, 107, 0, 1, 179, 195, 108, 97, 116, 114, 97, 109, 0, 1, 179, 195, 114, 107, 111, 112, 2, 99, 115, 0, 8, 97, 105, 112, 2, 99, 115, 97, 114, 110, 111, 107, 0, 8, 97, 108, 97, 109, 2, 115, 105, 118, 195, 173, 116, 0, 8, 101, 103, 101, 106, 0, 8, 108, 105, 102, 2, 99, 115, 195, 173, 107, 0, 8, 108, 111, 112, 2, 99, 115, 97, 116, 0, 8, 110, 97, 98, 97, 108, 0, 8, 110, 101, 106, 169, 195, 107, 0, 8, 110, 101, 108, 105, 107, 2, 99, 115, 111, 109, 195, 179, 0, 8, 110, 101, 108, 105, 107, 2, 99, 115, 195, 182, 118, 0, 8, 110, 105, 114, 112, 2, 115, 195, 169, 103, 0, 8, 110, 111, 103, 114, 105, 118, 2, 115, 195, 161, 103, 0, 8, 110, 111, 106, 186, 195, 0, 8, 110, 169, 195, 109, 108, 101, 2, 115, 195, 169, 103, 0, 8, 114, 97, 2, 115, 101, 98, 0, 8, 114, 97, 2, 115, 195, 169, 114, 195, 188, 108, 0, 8, 114, 101, 110, 2, 115, 116, 195, 179, 108, 195, 161, 0, 8, 114, 169, 195, 2, 99, 115, 0, 8, 114, 169, 195, 2, 115, 97, 108, 97, 107, 0, 8, 114, 169, 195, 2, 115, 97, 115, 0, 8, 114, 169, 195, 2, 115, 101, 108, 121, 0, 8, 114, 169, 195, 2, 115, 105, 115, 97, 107, 0, 8, 114, 169, 195, 2, 115, 195, 173, 112, 0, 8, 117, 114, 117, 107, 0, 8, 161, 195, 107, 97, 2, 115, 195, 182, 118, 0, 8, 161, 195, 107, 161, 195, 2, 115, 195, 182, 118, 0, 8, 161, 195, 114, 2, 115, 195, 161, 103, 0, 8, 169, 195, 108, 106, 101, 102, 0, 8, 179, 195, 104, 111, 98, 2, 115, 122, 0, 8, 179, 195, 107, 2, 99, 115, 111, 109, 195, 179, 0, 8, 179, 195, 108, 97, 112, 2, 115, 195, 161, 103, 0, 99, 2, 18, 66, 0, 99, 2, 45, 18, 66, 0, 99, 2, 45, 99, 99, 115, 0, 99, 2, 45, 99, 115, 0, 99, 8, 105, 118, 2, 115, 111, 114, 0, 122, 1, 19, 0, 122, 8, 110, 105, 2, 195, 169, 100, 0, 4, 2, 45, 99, 3, 117, 12, 0, 99, 0, 99, 2, 45, 99, 0, 99, 114, 3, 117, 52, 0, 2, 45, 99, 115, 3, 117, 74, 0, 115, 122, 3, 117, 87, 0, 115, 8, 179, 195, 104, 111, 98, 3, 117, 89, 0, 115, 111, 114, 8, 114, 97, 104, 3, 117, 89, 39, 52, 0, 7, 6, 100, 0, 4, 1, 45, 100, 3, 0, 4, 1, 45, 100, 100, 3, 0, 1, 114, 111, 107, 101, 114, 2, 115, 101, 98, 101, 115, 115, 195, 169, 103, 3, 0, 116, 1, 122, 101, 107, 3, 47, 0, 4, 116, 3, 47, 12, 0, 116, 2, 115, 122, 0, 116, 116, 0, 116, 116, 1, 101, 108, 108, 188, 195, 102, 2, 195, 169, 0, 116, 115, 122, 195, 169, 3, 47, 12, 87, 111, 0, 110, 121, 1, 110, 105, 109, 3, 65, 0, 4, 3, 70, 0, 1, 97, 98, 97, 122, 115, 2, 106, 101, 103, 0, 1, 97, 98, 97, 122, 115, 2, 115, 116, 114, 97, 110, 100, 0, 1, 97, 98, 97, 122, 115, 2, 115, 122, 101, 108, 108, 101, 0, 1, 97, 98, 97, 122, 115, 2, 115, 122, 101, 114, 101, 108, 0, 1, 97, 98, 97, 122, 115, 2, 115, 122, 111, 102, 116, 0, 1, 97, 98, 97, 122, 115, 2, 115, 122, 111, 109, 98, 97, 116, 0, 1, 97, 98, 97, 122, 115, 2, 115, 122, 195, 161, 106, 195, 186, 0, 1, 97, 98, 97, 122, 115, 2, 115, 122, 195, 161, 108, 108, 195, 161, 115, 0, 1, 97, 98, 97, 122, 115, 2, 115, 122, 195, 179, 108, 0, 1, 97, 104, 2, 106, 195, 161, 114, 97, 116, 0, 1, 97, 104, 2, 115, 101, 103, 195, 169, 100, 0, 1, 97, 104, 2, 115, 111, 114, 0, 1, 97, 104, 2, 115, 122, 101, 114, 116, 195, 161, 0, 1, 97, 104, 2, 115, 122, 105, 110, 0, 1, 97, 104, 145, 197, 102, 2, 115, 101, 103, 195, 169, 100, 0, 1, 97, 109, 114, 97, 104, 2, 115, 111, 114, 0, 1, 97, 109, 114, 97, 104, 2, 115, 122, 105, 110, 116, 0, 1, 97, 109, 114, 97, 104, 2, 115, 122, 195, 161, 122, 0, 1, 97, 112, 2, 115, 111, 114, 0, 1, 97, 112, 2, 115, 122, 101, 114, 197, 177, 0, 1, 97, 112, 2, 115, 122, 197, 145, 110, 121, 0, 1, 97, 118, 2, 115, 122, 101, 100, 101, 114, 0, 1, 97, 118, 2, 115, 122, 101, 103, 102, 0, 1, 97, 118, 2, 115, 122, 101, 114, 197, 177, 0, 1, 97, 118, 2, 115, 122, 105, 108, 118, 0, 1, 97, 118, 2, 115, 122, 116, 114, 195, 161, 106, 107, 0, 1, 97, 118, 2, 115, 122, 195, 179, 106, 0, 1, 97, 118, 2, 115, 122, 197, 145, 0, 1, 97, 118, 2, 115, 195, 161, 102, 114, 0, 1, 97, 122, 161, 195, 122, 115, 2, 115, 122, 101, 109, 108, 101, 0, 1, 97, 122, 161, 195, 122, 115, 2, 115, 122, 105, 110, 116, 0, 1, 97, 122, 161, 195, 122, 115, 2, 115, 122, 195, 161, 109, 0, 1, 101, 101, 119, 116, 2, 115, 97, 112, 107, 0, 1, 101, 101, 119, 116, 2, 115, 122, 195, 182, 118, 101, 116, 0, 1, 101, 114, 122, 101, 2, 115, 101, 103, 195, 169, 0, 1, 101, 114, 122, 101, 2, 115, 122, 101, 109, 0, 1, 101, 114, 122, 101, 2, 115, 122, 101, 114, 116, 101, 0, 1, 101, 114, 122, 101, 2, 115, 122, 105, 110, 0, 1, 101, 114, 122, 101, 2, 115, 122, 195, 161, 0, 1, 101, 114, 122, 101, 2, 122, 195, 161, 115, 122, 108, 0, 1, 101, 121, 103, 101, 110, 2, 115, 122, 195, 161, 122, 0, 1, 101, 121, 103, 101, 110, 2, 115, 122, 195, 169, 108, 0, 1, 101, 122, 105, 116, 2, 115, 122, 195, 161, 109, 0, 1, 101, 122, 105, 116, 2, 115, 122, 195, 161, 122, 0, 1, 103, 97, 114, 97, 109, 115, 2, 115, 122, 195, 173, 110, 0, 1, 105, 118, 182, 195, 114, 2, 115, 111, 114, 111, 122, 0, 1, 105, 118, 182, 195, 114, 2, 122, 195, 161, 114, 0, 1, 105, 118, 182, 195, 114, 2, 122, 195, 161, 114, 108, 97, 116, 0, 1, 106, 97, 102, 2, 116, 121, 195, 186, 107, 0, 1, 108, 111, 98, 111, 107, 2, 115, 122, 195, 182, 103, 0, 1, 108, 111, 104, 2, 115, 195, 188, 0, 1, 108, 182, 195, 102, 2, 115, 122, 101, 103, 195, 169, 108, 121, 0, 1, 108, 182, 195, 102, 2, 115, 122, 101, 114, 107, 101, 0, 1, 108, 182, 195, 102, 2, 115, 122, 101, 114, 122, 195, 169, 0, 1, 108, 182, 195, 102, 2, 115, 122, 101, 114, 197, 177, 0, 1, 108, 182, 195, 102, 2, 115, 122, 111, 114, 111, 115, 0, 1, 108, 182, 195, 102, 2, 115, 122, 195, 173, 110, 101, 107, 0, 1, 108, 182, 195, 102, 2, 115, 122, 195, 173, 110, 195, 169, 0, 1, 108, 182, 195, 102, 2, 115, 122, 195, 173, 110, 197, 177, 0, 1, 108, 182, 195, 102, 2, 115, 122, 195, 182, 107, 197, 145, 0, 1, 108, 182, 195, 102, 2, 115, 122, 195, 188, 114, 107, 0, 1, 108, 182, 195, 102, 2, 115, 195, 161, 110, 99, 0, 1, 108, 182, 195, 102, 2, 115, 195, 161, 118, 0, 1, 108, 182, 195, 122, 2, 115, 97, 112, 107, 0, 1, 108, 182, 195, 122, 2, 115, 122, 101, 109, 0, 1, 108, 182, 195, 122, 2, 115, 122, 195, 173, 110, 0, 1, 108, 182, 195, 122, 2, 115, 195, 161, 118, 0, 1, 110, 97, 108, 97, 107, 2, 106, 195, 161, 116, 195, 169, 107, 0, 1, 110, 97, 108, 97, 107, 2, 115, 122, 101, 114, 0, 1, 110, 97, 108, 97, 107, 2, 115, 122, 101, 114, 101, 112, 0, 1, 110, 97, 114, 116, 115, 2, 115, 122, 101, 122, 111, 110, 0, 1, 110, 101, 114, 2, 115, 122, 97, 0, 1, 110, 101, 114, 2, 115, 122, 101, 114, 101, 116, 197, 145, 0, 1, 110, 101, 114, 2, 122, 97, 118, 97, 114, 0, 1, 110, 101, 115, 99, 2, 115, 195, 169, 114, 116, 195, 169, 115, 0, 1, 110, 105, 109, 2, 106, 111, 98, 98, 97, 110, 0, 1, 111, 115, 161, 195, 109, 2, 115, 111, 114, 0, 1, 111, 115, 161, 195, 109, 2, 115, 122, 97, 107, 195, 161, 0, 1, 111, 115, 161, 195, 109, 2, 115, 122, 101, 114, 101, 112, 0, 1, 111, 115, 161, 195, 109, 2, 115, 122, 105, 110, 0, 1, 111, 115, 161, 195, 109, 2, 115, 122, 195, 188, 108, 195, 182, 116, 116, 0, 1, 114, 97, 100, 110, 97, 116, 115, 2, 106, 101, 103, 121, 0, 1, 114, 97, 107, 2, 115, 117, 0, 1, 114, 97, 107, 2, 115, 122, 101, 114, 197, 177, 0, 1, 114, 97, 107, 2, 115, 122, 195, 173, 106, 0, 1, 114, 111, 104, 2, 115, 122, 195, 169, 107, 0, 1, 114, 111, 104, 2, 115, 122, 195, 173, 0, 1, 114, 111, 106, 102, 2, 115, 122, 101, 114, 197, 177, 0, 1, 114, 111, 107, 101, 114, 2, 115, 101, 98, 101, 115, 115, 195, 169, 103, 0, 1, 114, 111, 107, 101, 114, 2, 115, 117, 103, 195, 161, 114, 0, 1, 114, 111, 107, 101, 114, 2, 115, 122, 101, 114, 107, 101, 122, 0, 1, 114, 111, 107, 101, 114, 2, 115, 122, 105, 110, 116, 0, 1, 114, 161, 195, 105, 108, 105, 109, 2, 115, 122, 111, 114, 0, 1, 114, 161, 195, 122, 97, 104, 2, 106, 195, 161, 116, 195, 169, 107, 0, 1, 114, 161, 195, 122, 110, 97, 109, 2, 115, 122, 111, 98, 0, 1, 114, 169, 195, 116, 2, 115, 122, 111, 107, 110, 121, 0, 1, 114, 169, 195, 116, 2, 115, 122, 195, 173, 106, 0, 1, 114, 169, 195, 116, 2, 115, 195, 169, 114, 195, 188, 108, 0, 1, 145, 197, 114, 101, 2, 115, 122, 101, 114, 197, 177, 0, 1, 161, 195, 108, 97, 115, 99, 2, 106, 111, 103, 0, 1, 161, 195, 108, 97, 115, 99, 2, 115, 101, 103, 195, 173, 116, 0, 1, 161, 195, 108, 97, 115, 99, 2, 115, 122, 101, 114, 101, 116, 197, 145, 0, 1, 161, 195, 108, 97, 115, 99, 2, 115, 122, 111, 99, 105, 111, 108, 0, 1, 161, 195, 110, 0, 1, 161, 195, 110, 2, 115, 117, 104, 111, 103, 0, 1, 161, 195, 110, 2, 115, 122, 101, 114, 100, 0, 1, 161, 195, 110, 2, 115, 122, 105, 108, 195, 161, 110, 0, 1, 161, 195, 110, 2, 115, 122, 195, 169, 107, 0, 1, 161, 195, 110, 2, 115, 122, 195, 182, 118, 101, 0, 1, 161, 195, 110, 2, 115, 122, 197, 145, 110, 121, 101, 0, 1, 161, 195, 110, 2, 115, 195, 173, 112, 0, 1, 161, 195, 112, 114, 161, 195, 2, 115, 195, 161, 118, 0, 1, 161, 195, 112, 114, 161, 195, 2, 115, 195, 161, 118, 0, 1, 161, 195, 112, 114, 161, 195, 2, 122, 195, 161, 115, 122, 108, 195, 179, 0, 1, 161, 195, 118, 2, 115, 122, 195, 179, 122, 97, 0, 1, 161, 195, 122, 115, 105, 108, 97, 112, 2, 115, 111, 114, 0, 1, 169, 195, 98, 101, 2, 106, 101, 103, 0, 1, 169, 195, 108, 101, 115, 99, 2, 115, 111, 0, 1, 169, 195, 118, 2, 106, 101, 103, 121, 0, 1, 169, 195, 118, 110, 111, 104, 2, 115, 101, 114, 101, 103, 0, 1, 169, 195, 118, 121, 103, 188, 195, 2, 106, 101, 108, 0, 1, 169, 195, 122, 115, 101, 98, 2, 106, 97, 118, 195, 173, 116, 0, 1, 169, 195, 122, 115, 101, 98, 2, 106, 101, 108, 0, 1, 169, 195, 122, 115, 101, 98, 2, 115, 101, 98, 101, 115, 115, 195, 169, 103, 0, 1, 169, 195, 122, 115, 101, 98, 2, 115, 116, 195, 173, 108, 117, 115, 0, 1, 169, 195, 122, 115, 101, 98, 2, 115, 122, 105, 110, 0, 1, 169, 195, 122, 115, 101, 98, 2, 122, 97, 103, 121, 0, 1, 169, 195, 122, 115, 109, 111, 122, 115, 2, 115, 111, 114, 0, 1, 173, 195, 104, 2, 115, 122, 101, 114, 0, 1, 173, 195, 104, 2, 115, 122, 101, 114, 107, 101, 122, 101, 116, 0, 1, 179, 195, 104, 2, 115, 122, 197, 145, 114, 0, 1, 179, 195, 106, 2, 115, 122, 105, 118, 195, 161, 114, 0, 1, 179, 195, 107, 2, 106, 101, 108, 0, 1, 179, 195, 107, 2, 115, 111, 114, 0, 1, 179, 195, 107, 2, 115, 122, 101, 114, 107, 101, 0, 1, 179, 195, 107, 2, 115, 122, 195, 179, 0, 1, 179, 195, 109, 2, 106, 97, 118, 97, 115, 108, 97, 116, 0, 1, 179, 195, 109, 2, 115, 111, 114, 0, 1, 179, 195, 114, 112, 97, 2, 115, 122, 0, 1, 179, 195, 116, 97, 107, 2, 115, 117, 103, 195, 161, 114, 0, 1, 179, 195, 116, 117, 2, 106, 101, 108, 195, 182, 108, 0, 1, 179, 195, 116, 117, 2, 115, 122, 101, 114, 118, 0, 1, 179, 195, 122, 105, 112, 101, 2, 115, 122, 101, 114, 0, 1, 179, 195, 122, 105, 112, 101, 2, 115, 122, 101, 114, 101, 112, 0, 1, 182, 195, 107, 2, 115, 122, 105, 114, 195, 169, 110, 0, 1, 182, 195, 107, 2, 115, 122, 105, 116, 195, 161, 108, 195, 161, 115, 0, 1, 182, 195, 116, 182, 195, 2, 115, 122, 195, 188, 108, 195, 182, 0, 1, 186, 195, 108, 2, 122, 115, 195, 173, 114, 0, 8, 97, 104, 2, 106, 195, 161, 116, 195, 169, 107, 0, 8, 97, 104, 2, 115, 122, 101, 114, 0, 8, 97, 104, 2, 115, 122, 195, 161, 108, 108, 0, 8, 97, 109, 114, 97, 104, 2, 115, 122, 195, 188, 108, 0, 8, 97, 118, 2, 115, 122, 97, 103, 0, 8, 97, 118, 2, 115, 122, 97, 109, 0, 8, 97, 118, 2, 115, 122, 195, 161, 114, 110, 121, 0, 8, 103, 97, 114, 97, 109, 115, 2, 115, 122, 0, 8, 108, 111, 104, 2, 115, 97, 114, 108, 195, 179, 0, 8, 108, 182, 195, 102, 2, 115, 122, 101, 108, 108, 101, 0, 8, 108, 182, 195, 102, 2, 115, 122, 101, 114, 122, 0, 8, 108, 182, 195, 102, 2, 115, 122, 105, 103, 101, 116, 0, 8, 108, 182, 195, 102, 2, 115, 122, 117, 114, 111, 107, 0, 8, 108, 182, 195, 102, 2, 115, 122, 195, 173, 110, 0, 8, 108, 182, 195, 102, 2, 115, 122, 195, 188, 108, 116, 0, 8, 110, 101, 114, 2, 106, 101, 108, 0, 8, 110, 111, 103, 2, 115, 122, 101, 114, 0, 8, 114, 97, 107, 2, 115, 122, 195, 186, 114, 0, 8, 114, 111, 104, 2, 115, 122, 101, 107, 0, 8, 114, 161, 195, 105, 108, 105, 98, 2, 115, 122, 111, 0, 8, 114, 169, 195, 116, 2, 122, 115, 101, 98, 0, 8, 122, 188, 195, 107, 2, 115, 122, 101, 108, 108, 0, 8, 161, 195, 110, 2, 115, 195, 182, 118, 0, 8, 161, 195, 114, 2, 115, 195, 179, 122, 0, 8, 179, 195, 107, 2, 115, 122, 111, 98, 0, 8, 182, 195, 107, 2, 115, 122, 101, 114, 197, 177, 0, 8, 182, 195, 107, 2, 115, 122, 195, 188, 114, 107, 0, 8, 186, 195, 108, 2, 115, 122, 111, 107, 195, 161, 115, 0, 100, 1, 97, 104, 2, 32, 14, 128, 128, 130, 0, 100, 2, 18, 66, 0, 100, 2, 45, 18, 66, 0, 4, 2, 45, 100, 3, 70, 12, 0, 100, 0, 100, 1, 161, 195, 110, 0, 100, 2, 45, 100, 0, 111, 98, 101, 114, 109, 97, 110, 110, 3, 70, 39, 69, 12, 107, 52, 63, 106, 50, 0, 100, 114, 3, 70, 52, 0, 100, 98, 3, 70, 69, 0, 122, 1, 101, 101, 119, 116, 2, 97, 107, 3, 70, 86, 0, 4, 115, 122, 1, 97, 2, 195, 173, 3, 70, 87, 0, 115, 122, 1, 101, 101, 119, 116, 2, 111, 107, 0, 115, 122, 1, 110, 101, 114, 2, 101, 114, 105, 110, 116, 0, 115, 122, 1, 110, 101, 114, 116, 101, 110, 101, 109, 2, 101, 114, 197, 177, 0, 115, 122, 1, 169, 195, 0, 115, 122, 2, 97, 0, 115, 122, 2, 195, 161, 0, 115, 122, 8, 110, 101, 114, 2, 101, 114, 101, 116, 101, 116, 0, 195, 188, 104, 116, 197, 145, 108, 3, 70, 109, 47, 116, 55, 0, 195, 188, 104, 98, 101, 3, 70, 109, 69, 107, 0, 195, 188, 104, 118, 101, 108, 3, 70, 109, 82, 107, 55, 0, 105, 101, 115, 101, 108, 5, 1, 3, 70, 110, 86, 107, 55, 0, 4, 100, 122, 115, 2, 18, 66, 3, 73, 0, 100, 122, 115, 2, 45, 18, 66, 0, 4, 100, 122, 115, 1, 105, 114, 98, 2, 101, 108, 3, 73, 12, 0, 122, 115, 1, 111, 98, 109, 97, 107, 0, 4, 115, 1, 17, 67, 3, 74, 0, 115, 2, 17, 67, 0, 4, 115, 1, 17, 65, 2, 17, 65, 3, 74, 12, 0, 115, 1, 169, 195, 108, 101, 115, 99, 2, 195, 169, 103, 0, 116, 115, 0, 106, 1, 17, 67, 3, 77, 0, 4, 106, 3, 77, 12, 0, 106, 1, 17, 65, 2, 17, 65, 0, 4, 115, 122, 3, 117, 0, 115, 122, 1, 110, 101, 114, 2, 101, 114, 105, 110, 116, 101, 103, 114, 195, 161, 99, 105, 195, 179, 0, 115, 122, 2, 17, 67, 0, 115, 122, 8, 110, 111, 109, 2, 97, 0, 4, 115, 122, 1, 97, 2, 17, 65, 3, 117, 12, 0, 115, 122, 1, 101, 2, 17, 65, 0, 115, 122, 1, 111, 2, 17, 65, 0, 115, 122, 1, 179, 195, 0, 115, 122, 1, 182, 195, 116, 182, 195, 2, 195, 182, 114, 0, 115, 122, 2, 32, 14, 128, 128, 131, 0, 100, 122, 2, 18, 66, 3, 118, 0, 7, 6, 101, 0, 108, 1, 45, 32, 48, 48, 48, 2, 32, 3, 51, 107, 55, 0, 3, 107, 0, 108, 1, 45, 32, 48, 48, 48, 48, 48, 48, 2, 32, 3, 107, 55, 0, 103, 121, 101, 122, 115, 195, 169, 103, 8, 3, 107, 77, 12, 107, 89, 89, 111, 79, 0, 103, 121, 101, 122, 115, 195, 169, 103, 103, 8, 3, 107, 77, 12, 107, 89, 89, 111, 79, 12, 0, 104, 104, 101, 122, 8, 3, 107, 105, 107, 86, 0, 7, 6, 102, 0, 4, 3, 81, 0, 102, 1, 97, 2, 195, 169, 108, 0, 102, 1, 101, 2, 97, 106, 116, 0, 102, 1, 101, 2, 195, 169, 108, 0, 102, 2, 18, 66, 0, 102, 2, 45, 18, 66, 0, 102, 114, 3, 81, 52, 0, 102, 98, 3, 81, 69, 0, 195, 188, 104, 114, 101, 114, 5, 1, 3, 81, 115, 52, 107, 52, 0, 7, 6, 103, 0, 4, 1, 45, 103, 3, 0, 4, 121, 1, 45, 103, 3, 0, 4, 121, 1, 45, 103, 103, 3, 0, 121, 1, 45, 121, 103, 3, 0, 107, 3, 49, 12, 0, 104, 1, 169, 195, 2, 97, 106, 108, 97, 3, 49, 105, 0, 4, 103, 121, 1, 101, 109, 2, 18, 66, 3, 77, 0, 103, 121, 1, 101, 109, 2, 45, 18, 66, 0, 103, 121, 1, 101, 109, 2, 109, 97, 103, 0, 103, 121, 2, 18, 66, 0, 103, 121, 2, 45, 18, 66, 0, 4, 103, 121, 3, 77, 12, 0, 103, 121, 1, 101, 108, 101, 2, 195, 169, 0, 103, 121, 1, 101, 109, 2, 32, 14, 128, 128, 131, 0, 103, 121, 1, 101, 109, 2, 45, 103, 121, 0, 103, 121, 1, 101, 109, 2, 101, 108, 0, 103, 121, 1, 101, 109, 2, 101, 109, 0, 103, 121, 1, 101, 109, 2, 101, 115, 0, 103, 121, 1, 101, 109, 2, 101, 116, 0, 103, 121, 1, 101, 109, 2, 195, 173, 122, 0, 103, 121, 8, 101, 109, 2, 101, 110, 32, 0, 103, 121, 106, 1, 111, 114, 2, 195, 169, 107, 0, 121, 2, 45, 103, 121, 0, 4, 103, 121, 114, 3, 77, 52, 0, 103, 121, 114, 1, 101, 109, 0, 4, 103, 121, 98, 3, 77, 69, 0, 103, 121, 98, 1, 101, 109, 0, 4, 3, 79, 0, 1, 97, 116, 2, 103, 121, 197, 177, 108, 0, 1, 97, 121, 108, 179, 195, 104, 2, 103, 121, 117, 108, 0, 1, 97, 121, 110, 97, 2, 103, 121, 195, 161, 114, 0, 1, 97, 121, 110, 97, 2, 103, 121, 197, 145, 122, 0, 1, 97, 121, 110, 97, 2, 103, 121, 197, 177, 106, 116, 0, 1, 97, 121, 110, 97, 105, 100, 97, 104, 2, 103, 121, 195, 161, 114, 0, 1, 101, 100, 105, 2, 103, 121, 0, 1, 101, 108, 2, 103, 121, 0, 1, 101, 109, 2, 103, 121, 0, 1, 101, 114, 101, 115, 2, 103, 121, 197, 177, 106, 0, 1, 101, 114, 101, 121, 110, 2, 103, 121, 0, 1, 101, 114, 169, 195, 109, 2, 103, 121, 0, 1, 101, 114, 188, 195, 99, 114, 97, 2, 103, 121, 117, 108, 108, 97, 100, 195, 161, 115, 0, 1, 101, 116, 101, 98, 2, 103, 121, 195, 179, 103, 121, 195, 161, 115, 122, 0, 1, 101, 118, 182, 195, 122, 115, 2, 103, 121, 197, 177, 106, 116, 0, 1, 101, 118, 188, 195, 2, 103, 121, 0, 1, 101, 121, 108, 169, 195, 98, 2, 103, 121, 197, 177, 106, 116, 0, 1, 105, 103, 169, 195, 118, 2, 103, 121, 97, 0, 1, 105, 103, 169, 195, 118, 2, 103, 121, 195, 182, 0, 1, 110, 97, 104, 2, 103, 121, 97, 107, 111, 114, 0, 1, 110, 117, 108, 112, 117, 107, 2, 103, 121, 195, 161, 114, 0, 1, 111, 100, 161, 195, 98, 2, 103, 121, 0, 1, 111, 102, 2, 103, 121, 97, 108, 117, 0, 1, 111, 102, 2, 103, 121, 195, 182, 0, 1, 111, 102, 2, 103, 121, 197, 177, 114, 197, 177, 0, 1, 111, 106, 2, 103, 121, 97, 107, 111, 114, 0, 1, 111, 108, 161, 195, 122, 2, 103, 121, 0, 1, 111, 114, 100, 2, 103, 121, 97, 110, 195, 186, 0, 1, 111, 114, 112, 2, 103, 121, 97, 107, 0, 1, 161, 195, 108, 105, 118, 2, 103, 121, 0, 1, 161, 195, 108, 105, 118, 2, 103, 121, 197, 177, 108, 195, 182, 108, 0, 1, 161, 195, 114, 2, 103, 121, 197, 177, 106, 116, 0, 1, 161, 195, 114, 105, 118, 2, 103, 121, 0, 1, 161, 195, 115, 97, 107, 116, 105, 114, 2, 103, 121, 197, 177, 106, 116, 0, 1, 161, 195, 115, 100, 161, 195, 109, 105, 2, 103, 121, 197, 177, 106, 116, 0, 1, 161, 195, 115, 115, 111, 103, 161, 195, 108, 105, 118, 2, 103, 121, 0, 1, 161, 195, 122, 115, 114, 111, 2, 103, 121, 97, 114, 97, 112, 111, 100, 0, 1, 161, 195, 122, 115, 114, 111, 2, 103, 121, 197, 177, 108, 195, 169, 115, 0, 1, 169, 195, 100, 110, 101, 118, 2, 103, 121, 0, 1, 169, 195, 106, 177, 197, 109, 2, 103, 121, 195, 161, 114, 0, 1, 169, 195, 108, 2, 103, 121, 195, 182, 107, 0, 1, 169, 195, 115, 101, 108, 101, 2, 103, 121, 0, 1, 169, 195, 115, 105, 103, 169, 195, 114, 2, 103, 121, 197, 177, 106, 116, 0, 1, 169, 195, 115, 108, 101, 102, 2, 103, 121, 0, 1, 169, 195, 115, 115, 101, 108, 101, 116, 182, 195, 107, 2, 103, 121, 97, 107, 0, 1, 169, 195, 115, 116, 110, 101, 122, 115, 2, 103, 121, 0, 1, 182, 195, 100, 2, 103, 121, 97, 112, 106, 195, 186, 0, 1, 182, 195, 122, 115, 2, 103, 121, 195, 161, 114, 0, 8, 97, 121, 103, 97, 2, 103, 121, 0, 8, 110, 161, 195, 108, 2, 103, 121, 0, 8, 111, 108, 2, 103, 121, 197, 177, 106, 116, 0, 8, 169, 195, 106, 2, 103, 121, 195, 161, 114, 0, 8, 169, 195, 115, 101, 108, 101, 102, 2, 103, 121, 105, 108, 107, 111, 115, 0, 103, 1, 117, 103, 2, 111, 108, 0, 103, 2, 18, 66, 0, 103, 2, 45, 18, 66, 0, 4, 2, 45, 103, 3, 79, 12, 0, 103, 0, 103, 1, 101, 108, 2, 114, 111, 116, 101, 115, 122, 107, 0, 103, 114, 3, 79, 52, 0, 103, 98, 3, 79, 69, 0, 4, 2, 45, 103, 121, 3, 79, 77, 0, 103, 2, 45, 103, 121, 0, 111, 101, 116, 104, 5, 1, 8, 3, 79, 116, 47, 107, 0, 7, 6, 104, 0, 4, 8, 101, 115, 99, 2, 111, 114, 115, 122, 195, 161, 103, 3, 0, 4, 8, 101, 115, 99, 2, 115, 122, 108, 111, 118, 195, 161, 107, 3, 0, 4, 8, 117, 106, 2, 107, 111, 108, 98, 3, 0, 4, 8, 117, 106, 2, 115, 97, 106, 116, 3, 0, 4, 8, 117, 106, 2, 115, 122, 195, 161, 114, 110, 121, 195, 169, 107, 3, 0, 8, 117, 106, 2, 116, 101, 110, 121, 195, 169, 115, 122, 3, 0, 4, 3, 105, 0, 104, 1, 101, 100, 110, 105, 109, 2, 101, 122, 0, 104, 2, 45, 18, 66, 0, 101, 114, 116, 122, 3, 105, 107, 52, 117, 0, 7, 6, 105, 0, 4, 3, 37, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 103, 1, 21, 2, 32, 14, 128, 128, 130, 3, 37, 79, 0, 104, 111, 122, 1, 21, 2, 32, 14, 128, 192, 132, 3, 37, 105, 39, 86, 0, 7, 6, 106, 0, 4, 3, 57, 0, 106, 2, 18, 66, 0, 106, 2, 45, 18, 66, 0, 106, 114, 3, 57, 52, 0, 106, 98, 3, 57, 69, 0, 97, 118, 195, 173, 116, 115, 8, 3, 57, 106, 82, 110, 74, 12, 0, 97, 118, 195, 173, 116, 115, 100, 8, 3, 57, 106, 82, 110, 74, 70, 0, 195, 169, 105, 103, 1, 21, 2, 32, 14, 128, 128, 132, 3, 57, 111, 37, 79, 0, 195, 169, 116, 197, 145, 108, 1, 21, 2, 32, 14, 128, 128, 133, 3, 57, 111, 47, 116, 55, 0, 195, 169, 110, 101, 107, 1, 21, 2, 32, 14, 128, 128, 133, 3, 57, 111, 50, 107, 49, 0, 195, 169, 114, 101, 1, 21, 2, 32, 14, 128, 128, 132, 3, 57, 111, 52, 107, 0, 195, 169, 118, 101, 108, 1, 21, 2, 32, 14, 128, 128, 133, 3, 57, 111, 82, 107, 55, 0, 195, 161, 105, 103, 1, 21, 2, 32, 14, 128, 192, 132, 3, 57, 112, 37, 79, 0, 195, 161, 116, 195, 179, 108, 1, 21, 2, 32, 14, 128, 192, 133, 3, 57, 112, 47, 113, 55, 0, 195, 161, 110, 97, 107, 1, 21, 2, 32, 14, 128, 192, 133, 3, 57, 112, 50, 106, 49, 0, 195, 161, 114, 97, 1, 21, 2, 32, 14, 128, 192, 132, 3, 57, 112, 52, 106, 0, 195, 161, 98, 97, 110, 1, 21, 2, 32, 14, 128, 192, 133, 3, 57, 112, 69, 106, 50, 0, 195, 161, 118, 97, 108, 1, 21, 2, 32, 14, 128, 192, 133, 3, 57, 112, 82, 106, 55, 0, 7, 6, 107, 0, 4, 1, 45, 107, 3, 0, 1, 45, 107, 107, 3, 0, 4, 3, 49, 0, 107, 2, 18, 66, 0, 107, 2, 45, 18, 66, 0, 195, 182, 122, 116, 195, 161, 114, 115, 97, 115, 195, 161, 103, 8, 3, 49, 6, 108, 87, 47, 112, 52, 89, 106, 89, 112, 79, 0, 195, 182, 122, 116, 195, 161, 114, 115, 97, 115, 195, 161, 103, 103, 8, 3, 49, 6, 108, 87, 47, 112, 52, 89, 106, 89, 112, 79, 12, 0, 4, 2, 45, 107, 3, 49, 12, 0, 107, 0, 107, 2, 17, 67, 0, 107, 2, 45, 107, 0, 107, 8, 169, 195, 116, 161, 195, 106, 2, 108, 105, 101, 110, 115, 0, 111, 115, 115, 117, 116, 104, 3, 49, 39, 89, 114, 47, 0, 111, 115, 115, 117, 116, 104, 116, 3, 49, 39, 89, 114, 47, 12, 0, 111, 115, 115, 117, 116, 104, 106, 3, 49, 39, 89, 114, 78, 12, 0, 107, 114, 3, 49, 52, 0, 107, 106, 3, 49, 57, 0, 107, 98, 3, 49, 69, 0, 195, 182, 122, 8, 3, 49, 108, 86, 0, 195, 182, 122, 116, 8, 3, 49, 108, 87, 47, 0, 195, 182, 122, 112, 111, 110, 116, 3, 49, 108, 87, 48, 39, 50, 47, 0, 195, 182, 122, 112, 111, 110, 116, 116, 3, 49, 108, 87, 48, 39, 50, 47, 12, 0, 195, 182, 122, 112, 111, 110, 116, 106, 3, 49, 108, 87, 48, 39, 50, 78, 0, 195, 182, 122, 115, 195, 169, 103, 3, 49, 108, 89, 89, 111, 79, 0, 195, 169, 115, 122, 115, 195, 169, 103, 3, 49, 111, 89, 89, 111, 79, 0, 195, 169, 115, 122, 115, 195, 169, 103, 103, 3, 49, 111, 89, 89, 111, 79, 12, 0, 7, 6, 108, 0, 4, 3, 55, 0, 1, 101, 2, 106, 117, 115, 0, 1, 101, 2, 106, 117, 116, 0, 1, 101, 2, 106, 195, 161, 116, 115, 122, 0, 1, 101, 102, 2, 106, 97, 118, 195, 173, 116, 0, 1, 101, 102, 2, 106, 101, 103, 121, 0, 1, 101, 102, 2, 106, 101, 108, 101, 110, 0, 1, 101, 102, 2, 106, 111, 103, 111, 115, 195, 173, 116, 0, 1, 101, 102, 2, 106, 117, 0, 1, 101, 102, 2, 106, 195, 161, 114, 0, 1, 101, 102, 2, 106, 195, 182, 0, 1, 106, 161, 195, 102, 0, 1, 169, 195, 122, 115, 2, 106, 101, 103, 121, 0, 1, 169, 195, 122, 115, 2, 106, 195, 161, 114, 0, 1, 188, 195, 116, 122, 115, 101, 114, 101, 107, 2, 106, 0, 8, 169, 195, 102, 2, 106, 111, 98, 98, 0, 108, 1, 101, 2, 105, 112, 115, 122, 0, 108, 1, 101, 116, 97, 103, 97, 98, 2, 105, 122, 0, 108, 1, 101, 116, 110, 105, 2, 105, 103, 101, 0, 108, 1, 105, 109, 2, 105, 0, 108, 2, 18, 66, 0, 108, 2, 45, 18, 66, 0, 4, 1, 182, 195, 107, 182, 195, 2, 106, 111, 103, 3, 55, 12, 0, 1, 186, 195, 116, 2, 106, 0, 4, 121, 1, 17, 67, 2, 32, 3, 55, 37, 0, 121, 8, 104, 116, 169, 195, 107, 0, 108, 114, 3, 55, 52, 0, 4, 108, 121, 1, 101, 117, 109, 97, 122, 115, 3, 55, 55, 37, 0, 121, 1, 101, 117, 109, 97, 122, 115, 0, 4, 106, 1, 101, 2, 195, 161, 114, 3, 55, 57, 0, 106, 8, 97, 116, 2, 195, 161, 110, 0, 106, 8, 101, 2, 195, 182, 0, 108, 98, 3, 55, 69, 0, 4, 108, 1, 161, 195, 2, 106, 3, 57, 0, 108, 121, 2, 45, 18, 66, 0, 121, 0, 4, 1, 97, 108, 106, 161, 195, 102, 2, 106, 3, 57, 57, 0, 1, 169, 195, 99, 2, 106, 195, 161, 0, 106, 1, 101, 107, 0, 106, 1, 101, 114, 169, 195, 98, 0, 106, 1, 169, 195, 122, 115, 101, 98, 0, 108, 121, 0, 4, 106, 1, 111, 100, 110, 111, 103, 3, 57, 57, 57, 0, 106, 1, 161, 195, 110, 106, 97, 115, 0, 108, 106, 0, 4, 106, 3, 61, 57, 0, 106, 1, 17, 65, 2, 17, 65, 0, 7, 6, 109, 0, 4, 3, 63, 0, 109, 1, 111, 107, 2, 117, 110, 105, 0, 109, 2, 18, 66, 0, 109, 2, 45, 18, 66, 0, 7, 6, 110, 0, 4, 3, 50, 0, 1, 97, 108, 116, 97, 103, 110, 105, 2, 106, 111, 103, 0, 1, 101, 98, 121, 108, 101, 104, 2, 106, 195, 161, 114, 0, 1, 101, 98, 122, 182, 195, 107, 2, 106, 195, 161, 114, 0, 1, 101, 98, 145, 197, 102, 2, 106, 195, 161, 114, 0, 1, 101, 108, 108, 101, 2, 106, 97, 118, 97, 108, 108, 116, 0, 1, 101, 108, 108, 101, 2, 106, 97, 118, 97, 115, 108, 97, 116, 0, 1, 101, 108, 108, 101, 2, 106, 101, 103, 121, 0, 1, 101, 108, 108, 101, 2, 106, 195, 161, 116, 195, 169, 107, 0, 1, 101, 108, 108, 111, 112, 2, 106, 101, 108, 101, 110, 0, 1, 101, 108, 169, 195, 2, 106, 195, 161, 114, 0, 1, 101, 118, 116, 182, 195, 2, 121, 97, 114, 100, 0, 1, 101, 118, 121, 103, 101, 110, 2, 121, 97, 114, 100, 0, 1, 101, 121, 103, 101, 2, 106, 111, 103, 195, 186, 0, 1, 101, 121, 103, 110, 105, 0, 1, 105, 98, 97, 107, 2, 110, 121, 195, 173, 108, 0, 1, 111, 100, 106, 97, 108, 117, 116, 2, 106, 111, 103, 0, 1, 111, 102, 111, 114, 107, 105, 109, 2, 110, 121, 195, 173, 108, 195, 161, 115, 0, 1, 111, 114, 101, 112, 2, 106, 101, 103, 121, 0, 1, 111, 116, 101, 98, 2, 106, 195, 161, 114, 100, 97, 0, 1, 111, 121, 103, 97, 118, 2, 110, 121, 105, 108, 97, 116, 107, 111, 122, 97, 116, 0, 1, 145, 197, 115, 169, 195, 107, 2, 106, 195, 182, 118, 197, 145, 0, 1, 161, 195, 101, 99, 179, 195, 2, 106, 195, 161, 114, 0, 1, 161, 195, 103, 97, 109, 2, 106, 101, 108, 108, 101, 103, 0, 1, 161, 195, 103, 97, 109, 2, 106, 111, 103, 0, 1, 161, 195, 103, 97, 109, 2, 110, 121, 101, 108, 0, 1, 161, 195, 108, 122, 115, 111, 114, 111, 2, 110, 121, 111, 109, 0, 1, 161, 195, 114, 103, 105, 108, 105, 102, 2, 110, 121, 101, 108, 0, 1, 161, 195, 116, 117, 2, 110, 121, 111, 109, 0, 1, 173, 195, 122, 115, 2, 106, 101, 108, 122, 195, 169, 115, 0, 1, 173, 195, 122, 115, 2, 106, 195, 161, 116, 0, 1, 173, 195, 122, 115, 2, 106, 195, 179, 122, 97, 110, 0, 1, 173, 195, 122, 115, 2, 110, 121, 111, 109, 0, 1, 177, 197, 98, 2, 106, 101, 108, 0, 1, 182, 195, 2, 106, 101, 108, 195, 182, 108, 0, 1, 182, 195, 2, 106, 195, 161, 114, 195, 179, 0, 1, 182, 195, 115, 99, 108, 182, 195, 107, 2, 106, 101, 103, 121, 122, 0, 2, 103, 0, 2, 107, 0, 8, 101, 108, 108, 101, 2, 106, 97, 118, 0, 8, 101, 108, 116, 101, 116, 101, 104, 100, 100, 101, 102, 2, 106, 101, 108, 108, 101, 0, 8, 105, 122, 115, 2, 106, 195, 161, 116, 115, 122, 0, 8, 177, 197, 98, 2, 110, 121, 111, 109, 0, 8, 182, 195, 2, 110, 121, 111, 109, 0, 110, 1, 111, 107, 2, 101, 107, 116, 111, 114, 0, 110, 2, 18, 66, 0, 110, 2, 45, 18, 66, 0, 110, 114, 3, 50, 52, 0, 106, 1, 105, 122, 110, 101, 98, 3, 50, 57, 0, 110, 121, 1, 161, 195, 103, 97, 109, 2, 117, 103, 100, 195, 173, 106, 3, 50, 65, 0, 110, 98, 3, 50, 69, 0, 121, 108, 111, 110, 5, 1, 8, 3, 50, 107, 57, 55, 39, 50, 0, 101, 109, 8, 2, 45, 3, 50, 107, 63, 0, 108, 1, 161, 195, 106, 97, 3, 55, 12, 0, 108, 106, 1, 161, 195, 106, 97, 3, 57, 12, 0, 2, 112, 3, 63, 0, 4, 106, 1, 101, 104, 105, 112, 2, 32, 14, 128, 128, 130, 3, 65, 0, 106, 1, 105, 2, 101, 107, 99, 105, 195, 179, 0, 110, 121, 1, 101, 109, 2, 111, 114, 115, 122, 195, 161, 103, 0, 110, 121, 1, 105, 2, 101, 107, 99, 105, 195, 179, 0, 110, 121, 2, 18, 66, 0, 110, 121, 2, 45, 18, 66, 0, 110, 121, 2, 99, 115, 0, 110, 121, 8, 101, 109, 2, 97, 115, 115, 122, 0, 121, 0, 121, 1, 101, 115, 114, 101, 118, 2, 106, 111, 103, 0, 121, 1, 101, 115, 114, 101, 118, 2, 106, 195, 161, 116, 195, 169, 107, 0, 121, 1, 145, 197, 122, 101, 109, 2, 106, 0, 121, 1, 161, 195, 105, 104, 2, 106, 0, 121, 1, 161, 195, 109, 111, 108, 108, 161, 195, 2, 106, 101, 108, 0, 121, 1, 161, 195, 109, 114, 111, 107, 2, 106, 97, 118, 97, 115, 108, 97, 116, 0, 121, 1, 161, 195, 109, 114, 111, 107, 2, 106, 101, 108, 101, 110, 116, 195, 169, 115, 0, 121, 1, 161, 195, 109, 116, 111, 107, 108, 97, 2, 106, 0, 121, 1, 161, 195, 114, 105, 2, 106, 101, 108, 0, 121, 1, 161, 195, 114, 116, 111, 98, 2, 106, 195, 161, 116, 195, 169, 107, 0, 121, 1, 161, 195, 118, 114, 161, 195, 118, 105, 122, 115, 2, 106, 195, 161, 116, 115, 122, 0, 121, 1, 169, 195, 100, 105, 2, 106, 101, 108, 0, 121, 1, 169, 195, 102, 2, 106, 101, 108, 0, 121, 1, 169, 195, 109, 100, 101, 114, 101, 2, 106, 0, 121, 1, 169, 195, 109, 101, 114, 101, 121, 110, 2, 106, 195, 161, 116, 195, 169, 107, 0, 121, 1, 169, 195, 109, 101, 115, 101, 2, 106, 101, 108, 0, 121, 1, 169, 195, 109, 116, 173, 195, 115, 101, 106, 108, 101, 116, 2, 106, 97, 118, 117, 0, 121, 1, 169, 195, 118, 114, 182, 195, 116, 2, 106, 97, 118, 97, 0, 121, 8, 101, 109, 2, 97, 115, 115, 122, 0, 110, 121, 114, 3, 65, 52, 0, 4, 106, 3, 65, 65, 0, 110, 121, 0, 121, 106, 0, 110, 121, 98, 3, 65, 69, 0, 118, 100, 97, 8, 2, 45, 3, 107, 50, 82, 111, 70, 111, 112, 0, 7, 6, 111, 0, 3, 39, 0, 7, 6, 112, 0, 4, 1, 45, 112, 3, 0, 1, 45, 112, 112, 3, 0, 4, 3, 48, 0, 112, 2, 18, 66, 0, 112, 2, 45, 18, 66, 0, 2, 118, 3, 48, 10, 0, 4, 2, 45, 112, 3, 48, 12, 0, 112, 0, 112, 2, 17, 67, 0, 111, 116, 115, 100, 97, 109, 5, 1, 8, 3, 48, 39, 117, 70, 112, 63, 0, 112, 114, 3, 48, 52, 0, 112, 98, 3, 48, 69, 0, 7, 6, 113, 0, 4, 3, 49, 82, 0, 117, 0, 7, 6, 114, 0, 4, 2, 99, 99, 3, 51, 0, 2, 114, 0, 101, 1, 21, 2, 32, 14, 128, 128, 130, 3, 51, 107, 0, 4, 3, 52, 0, 1, 114, 0, 114, 1, 97, 2, 111, 103, 195, 161, 110, 115, 0, 114, 1, 101, 116, 2, 105, 101, 114, 0, 114, 1, 101, 116, 2, 111, 114, 105, 0, 114, 1, 105, 2, 105, 116, 195, 161, 0, 114, 1, 111, 107, 2, 101, 112, 101, 116, 195, 161, 0, 114, 1, 117, 107, 110, 111, 107, 2, 101, 110, 0, 114, 2, 18, 66, 0, 114, 2, 45, 18, 66, 0, 114, 8, 97, 2, 111, 103, 97, 110, 99, 105, 0, 109, 3, 52, 10, 63, 0, 4, 105, 99, 104, 97, 5, 1, 8, 2, 114, 100, 3, 52, 37, 97, 112, 0, 105, 99, 104, 195, 161, 8, 2, 114, 100, 0, 114, 114, 3, 52, 52, 0, 114, 98, 3, 52, 69, 0, 97, 1, 21, 2, 32, 14, 128, 128, 130, 3, 52, 106, 0, 7, 6, 115, 0, 122, 1, 45, 115, 3, 0, 5, 1, 1, 108, 101, 104, 2, 105, 110, 107, 105, 3, 86, 0, 4, 1, 108, 101, 103, 110, 101, 3, 87, 0, 5, 1, 1, 117, 105, 98, 117, 110, 97, 100, 0, 5, 1, 1, 117, 116, 110, 101, 118, 117, 106, 0, 2, 45, 115, 122, 3, 87, 12, 0, 4, 108, 111, 5, 1, 8, 111, 3, 87, 55, 113, 0, 108, 195, 179, 5, 1, 8, 111, 0, 4, 101, 109, 109, 101, 108, 119, 101, 105, 115, 8, 3, 87, 107, 63, 63, 107, 55, 82, 107, 57, 87, 0, 101, 109, 109, 101, 108, 119, 101, 105, 115, 115, 8, 0, 101, 109, 109, 101, 108, 119, 101, 105, 195, 159, 8, 0, 97, 97, 114, 5, 1, 8, 3, 87, 112, 52, 0, 4, 3, 89, 0, 1, 97, 107, 114, 97, 102, 2, 115, 122, 197, 145, 114, 0, 1, 97, 118, 2, 115, 0, 1, 100, 108, 182, 195, 102, 2, 195, 161, 110, 99, 0, 1, 101, 110, 103, 161, 195, 109, 0, 1, 101, 121, 110, 110, 101, 122, 115, 2, 122, 115, 195, 161, 0, 1, 101, 122, 110, 169, 195, 112, 0, 1, 105, 107, 2, 122, 115, 105, 100, 195, 179, 0, 1, 105, 120, 97, 108, 97, 103, 0, 1, 111, 103, 111, 108, 97, 121, 103, 2, 122, 195, 161, 115, 122, 108, 195, 179, 0, 1, 111, 107, 111, 116, 2, 122, 195, 161, 115, 122, 108, 0, 1, 111, 108, 169, 195, 99, 110, 161, 195, 112, 0, 1, 111, 114, 161, 195, 118, 2, 122, 97, 106, 0, 1, 111, 114, 161, 195, 118, 2, 122, 115, 0, 1, 111, 116, 161, 195, 110, 161, 195, 114, 103, 0, 1, 111, 121, 110, 111, 103, 97, 114, 100, 0, 1, 117, 100, 108, 111, 107, 0, 1, 117, 103, 179, 195, 103, 97, 100, 101, 112, 2, 115, 122, 116, 114, 195, 161, 106, 107, 0, 1, 117, 109, 116, 105, 114, 2, 122, 97, 106, 0, 1, 117, 109, 116, 105, 114, 2, 122, 97, 118, 97, 114, 0, 1, 117, 112, 173, 195, 116, 2, 122, 117, 98, 0, 1, 145, 197, 121, 110, 114, 101, 145, 197, 116, 106, 101, 0, 1, 161, 195, 100, 97, 104, 2, 115, 122, 97, 103, 0, 1, 161, 195, 102, 2, 115, 122, 195, 161, 114, 195, 186, 0, 1, 161, 195, 103, 122, 111, 109, 2, 122, 97, 118, 97, 0, 1, 161, 195, 105, 114, 179, 195, 0, 1, 161, 195, 106, 111, 116, 0, 1, 161, 195, 107, 115, 117, 112, 0, 1, 161, 195, 108, 100, 97, 112, 0, 1, 161, 195, 108, 108, 97, 104, 2, 122, 97, 118, 97, 114, 0, 1, 161, 195, 110, 97, 98, 98, 111, 114, 0, 1, 161, 195, 110, 97, 98, 98, 111, 114, 2, 122, 97, 106, 0, 1, 161, 195, 114, 114, 111, 102, 145, 197, 114, 101, 2, 122, 97, 98, 195, 161, 108, 0, 1, 161, 195, 116, 105, 116, 110, 101, 100, 105, 2, 122, 97, 118, 97, 114, 0, 1, 161, 195, 116, 114, 97, 116, 97, 103, 97, 109, 2, 122, 97, 118, 97, 114, 0, 1, 161, 195, 116, 161, 195, 108, 2, 122, 97, 118, 97, 114, 0, 1, 161, 195, 118, 108, 97, 2, 122, 97, 118, 97, 0, 1, 161, 195, 121, 108, 107, 161, 195, 102, 2, 122, 101, 110, 0, 1, 161, 195, 122, 97, 109, 108, 97, 107, 108, 97, 2, 115, 122, 101, 114, 118, 101, 114, 0, 1, 169, 195, 100, 101, 107, 108, 101, 115, 105, 118, 2, 122, 97, 118, 97, 0, 1, 169, 195, 100, 182, 195, 107, 177, 197, 109, 2, 122, 97, 118, 97, 0, 1, 169, 195, 103, 101, 107, 101, 114, 98, 0, 1, 169, 195, 108, 101, 109, 114, 101, 116, 0, 1, 169, 195, 112, 169, 195, 108, 0, 1, 169, 195, 116, 188, 195, 2, 122, 195, 161, 112, 0, 1, 169, 195, 122, 101, 100, 101, 102, 0, 1, 186, 195, 104, 2, 115, 122, 97, 103, 0, 8, 101, 118, 177, 197, 109, 145, 197, 107, 2, 115, 122, 0, 8, 105, 107, 2, 122, 111, 109, 98, 111, 114, 0, 8, 105, 108, 105, 112, 0, 8, 111, 108, 97, 116, 122, 115, 97, 0, 8, 111, 114, 105, 112, 0, 8, 117, 103, 114, 161, 195, 0, 8, 161, 195, 100, 108, 161, 195, 0, 8, 161, 195, 107, 110, 117, 109, 0, 8, 161, 195, 108, 173, 195, 121, 110, 0, 8, 169, 195, 108, 182, 195, 107, 114, 182, 195, 112, 2, 115, 122, 0, 8, 169, 195, 114, 145, 197, 108, 2, 115, 122, 0, 8, 169, 195, 122, 112, 169, 195, 107, 0, 8, 169, 195, 122, 115, 116, 101, 116, 0, 8, 179, 195, 118, 186, 195, 102, 2, 122, 101, 110, 101, 0, 8, 182, 195, 114, 182, 195, 107, 2, 115, 122, 97, 107, 195, 161, 108, 0, 8, 182, 195, 114, 182, 195, 118, 0, 104, 5, 1, 8, 97, 119, 2, 105, 110, 103, 0, 4, 115, 122, 8, 161, 195, 110, 114, 97, 98, 2, 195, 188, 114, 107, 101, 3, 89, 87, 0, 115, 122, 8, 161, 195, 118, 108, 97, 2, 195, 188, 107, 115, 195, 169, 0, 1, 105, 107, 2, 101, 98, 98, 3, 89, 89, 0, 7, 6, 116, 0, 4, 1, 45, 116, 3, 0, 4, 1, 45, 116, 116, 3, 0, 4, 121, 1, 45, 116, 3, 0, 4, 121, 1, 45, 116, 116, 3, 0, 121, 1, 45, 121, 116, 3, 0, 4, 3, 47, 0, 1, 45, 2, 32, 0, 1, 97, 99, 117, 116, 2, 115, 122, 195, 169, 112, 0, 1, 97, 104, 2, 99, 101, 108, 108, 0, 1, 97, 108, 100, 97, 112, 2, 115, 122, 197, 145, 110, 121, 0, 1, 97, 108, 108, 161, 195, 2, 115, 101, 98, 195, 169, 115, 122, 0, 1, 97, 108, 108, 161, 195, 2, 115, 122, 197, 145, 114, 0, 1, 97, 108, 111, 121, 116, 97, 112, 2, 115, 101, 108, 121, 0, 1, 97, 112, 97, 115, 99, 2, 115, 122, 111, 108, 103, 0, 1, 97, 114, 161, 195, 106, 2, 115, 122, 111, 108, 103, 195, 161, 108, 0, 1, 97, 118, 105, 100, 2, 99, 105, 107, 107, 0, 1, 97, 118, 105, 100, 2, 115, 122, 195, 169, 112, 0, 1, 97, 122, 161, 195, 108, 98, 161, 195, 116, 2, 99, 101, 108, 108, 0, 1, 97, 122, 179, 195, 108, 161, 195, 104, 2, 115, 101, 109, 108, 101, 103, 101, 115, 0, 1, 101, 108, 101, 115, 99, 108, 182, 195, 98, 2, 115, 97, 118, 97, 0, 1, 101, 108, 103, 182, 195, 122, 115, 2, 115, 122, 111, 98, 0, 1, 101, 108, 121, 103, 188, 195, 2, 115, 122, 111, 98, 0, 1, 101, 108, 122, 188, 195, 2, 115, 122, 111, 98, 0, 1, 101, 108, 169, 195, 2, 115, 111, 114, 118, 97, 115, 122, 0, 1, 101, 108, 169, 195, 2, 115, 122, 111, 109, 106, 0, 1, 101, 108, 188, 195, 114, 101, 116, 2, 99, 195, 169, 108, 0, 1, 101, 109, 114, 101, 112, 2, 115, 122, 101, 114, 197, 177, 0, 1, 101, 110, 2, 99, 0, 1, 101, 116, 114, 169, 195, 115, 173, 195, 107, 2, 115, 122, 195, 161, 122, 97, 100, 0, 1, 101, 116, 182, 195, 107, 2, 115, 122, 195, 161, 109, 0, 1, 101, 118, 182, 195, 122, 115, 2, 115, 195, 161, 118, 0, 1, 101, 122, 101, 106, 101, 102, 2, 99, 195, 173, 109, 0, 1, 101, 122, 101, 106, 101, 102, 2, 115, 111, 114, 0, 1, 101, 122, 109, 101, 110, 2, 115, 122, 195, 173, 110, 0, 1, 101, 122, 121, 103, 169, 195, 110, 2, 99, 101, 110, 116, 105, 0, 1, 105, 102, 97, 114, 103, 2, 99, 101, 114, 117, 122, 0, 1, 105, 108, 101, 2, 115, 122, 111, 108, 103, 0, 1, 105, 112, 114, 161, 195, 107, 2, 115, 122, 197, 145, 110, 121, 0, 1, 105, 122, 105, 118, 2, 115, 122, 111, 98, 0, 1, 108, 97, 122, 115, 97, 2, 106, 101, 103, 0, 1, 108, 161, 195, 110, 122, 115, 97, 104, 2, 99, 105, 107, 107, 0, 1, 110, 97, 107, 107, 111, 114, 2, 115, 101, 103, 195, 173, 116, 0, 1, 110, 111, 106, 97, 118, 2, 115, 122, 111, 114, 111, 115, 0, 1, 110, 111, 114, 102, 2, 115, 101, 98, 195, 169, 115, 122, 0, 1, 110, 111, 115, 99, 2, 115, 111, 118, 195, 161, 110, 121, 0, 1, 110, 111, 115, 99, 2, 115, 195, 161, 114, 103, 97, 0, 1, 110, 161, 195, 102, 101, 108, 101, 2, 115, 122, 197, 145, 114, 0, 1, 110, 161, 195, 109, 169, 195, 121, 103, 2, 115, 122, 111, 108, 105, 0, 1, 111, 98, 111, 114, 2, 115, 122, 111, 110, 100, 0, 1, 114, 111, 112, 115, 2, 99, 101, 110, 116, 0, 1, 114, 161, 195, 112, 2, 115, 122, 195, 169, 107, 104, 195, 161, 122, 0, 1, 114, 161, 195, 122, 2, 115, 122, 195, 169, 107, 0, 1, 115, 188, 195, 122, 101, 2, 115, 97, 114, 107, 0, 1, 115, 188, 195, 122, 101, 2, 115, 122, 111, 98, 0, 1, 115, 188, 195, 122, 101, 2, 115, 122, 195, 169, 108, 0, 1, 115, 188, 195, 122, 101, 2, 115, 122, 197, 145, 107, 101, 0, 1, 115, 188, 195, 122, 101, 2, 115, 122, 197, 145, 114, 0, 1, 117, 109, 97, 109, 2, 115, 122, 197, 145, 114, 0, 1, 117, 109, 97, 112, 2, 99, 195, 169, 114, 0, 1, 117, 109, 97, 112, 2, 115, 122, 111, 107, 0, 1, 122, 115, 101, 116, 2, 99, 105, 107, 107, 0, 1, 122, 115, 101, 116, 2, 99, 195, 169, 108, 0, 1, 122, 115, 105, 108, 2, 99, 105, 112, 101, 108, 0, 1, 161, 195, 2, 99, 97, 112, 108, 97, 116, 0, 1, 161, 195, 2, 99, 105, 107, 195, 161, 122, 0, 1, 161, 195, 2, 99, 195, 173, 109, 0, 1, 161, 195, 106, 97, 115, 2, 115, 122, 101, 109, 195, 169, 0, 1, 161, 195, 106, 97, 115, 2, 115, 122, 101, 114, 197, 177, 0, 1, 161, 195, 107, 97, 108, 112, 2, 99, 195, 169, 103, 0, 1, 161, 195, 107, 111, 114, 98, 2, 115, 101, 108, 121, 0, 1, 161, 195, 107, 111, 114, 98, 2, 115, 122, 0, 1, 161, 195, 108, 114, 97, 107, 115, 2, 115, 122, 195, 173, 110, 0, 1, 161, 195, 118, 105, 118, 2, 115, 122, 195, 179, 0, 1, 169, 195, 107, 110, 101, 122, 105, 116, 2, 115, 122, 195, 169, 108, 0, 1, 169, 195, 116, 182, 195, 115, 2, 115, 122, 111, 98, 0, 1, 169, 195, 122, 115, 2, 115, 117, 103, 195, 161, 114, 0, 1, 169, 195, 122, 115, 2, 115, 122, 111, 114, 116, 195, 173, 114, 0, 1, 169, 195, 122, 115, 2, 115, 122, 111, 114, 195, 173, 116, 0, 1, 169, 195, 122, 115, 2, 115, 195, 182, 112, 195, 182, 114, 0, 1, 179, 195, 112, 2, 115, 101, 108, 101, 106, 116, 0, 1, 182, 195, 2, 121, 97, 114, 100, 0, 2, 99, 115, 0, 8, 97, 108, 108, 161, 195, 2, 115, 122, 111, 98, 0, 8, 101, 108, 103, 101, 122, 115, 2, 115, 122, 0, 8, 102, 97, 116, 2, 115, 101, 108, 121, 0, 8, 105, 115, 122, 161, 195, 112, 2, 115, 122, 0, 8, 106, 97, 115, 2, 115, 122, 195, 173, 110, 0, 8, 110, 111, 122, 115, 105, 118, 2, 115, 122, 111, 108, 103, 195, 161, 108, 0, 8, 114, 97, 112, 2, 115, 122, 195, 169, 108, 0, 8, 114, 111, 112, 115, 2, 99, 195, 169, 108, 0, 8, 115, 101, 2, 115, 122, 195, 169, 108, 0, 8, 115, 101, 116, 2, 115, 122, 197, 145, 114, 0, 8, 145, 197, 114, 2, 115, 122, 197, 145, 107, 0, 8, 161, 195, 2, 115, 122, 111, 108, 103, 195, 161, 108, 116, 97, 116, 0, 8, 169, 195, 104, 2, 99, 111, 108, 0, 8, 169, 195, 107, 2, 115, 122, 195, 169, 108, 0, 8, 169, 195, 116, 182, 195, 115, 2, 115, 122, 197, 145, 107, 0, 8, 179, 195, 112, 2, 115, 122, 111, 108, 103, 195, 161, 108, 0, 104, 1, 97, 2, 195, 169, 110, 0, 116, 1, 182, 195, 100, 108, 188, 195, 107, 2, 103, 121, 197, 177, 108, 0, 116, 2, 18, 66, 0, 116, 2, 45, 18, 66, 0, 116, 8, 111, 114, 102, 2, 195, 173, 114, 0, 4, 2, 45, 116, 3, 47, 12, 0, 116, 2, 45, 116, 0, 4, 121, 1, 114, 97, 109, 115, 182, 195, 114, 182, 195, 118, 3, 47, 37, 0, 121, 1, 122, 115, 111, 110, 0, 121, 8, 97, 107, 2, 110, 0, 116, 106, 8, 111, 2, 195, 161, 114, 3, 47, 57, 0, 115, 122, 8, 186, 195, 2, 195, 169, 107, 3, 47, 87, 0, 101, 114, 109, 195, 169, 115, 122, 101, 116, 101, 115, 3, 47, 107, 52, 63, 111, 87, 107, 47, 107, 89, 0, 104, 195, 182, 107, 195, 182, 108, 121, 3, 47, 108, 49, 108, 55, 37, 0, 8, 2, 32, 3, 47, 111, 0, 195, 179, 108, 1, 21, 2, 32, 14, 128, 192, 131, 3, 47, 113, 55, 0, 197, 145, 108, 1, 21, 2, 32, 14, 128, 192, 131, 3, 47, 116, 55, 0, 4, 115, 1, 105, 115, 97, 122, 161, 195, 104, 2, 97, 3, 74, 12, 0, 115, 1, 169, 195, 107, 169, 195, 98, 101, 122, 115, 115, 182, 195, 2, 101, 0, 115, 8, 105, 107, 97, 122, 115, 2, 111, 110, 0, 4, 116, 121, 2, 18, 66, 3, 78, 0, 121, 0, 121, 106, 1, 17, 67, 0, 4, 2, 45, 116, 121, 3, 78, 12, 0, 116, 2, 45, 116, 121, 0, 121, 2, 45, 116, 121, 0, 121, 106, 1, 17, 65, 2, 17, 65, 0, 4, 115, 122, 1, 101, 109, 2, 118, 195, 169, 110, 121, 3, 117, 0, 115, 122, 1, 101, 116, 2, 104, 0, 115, 122, 1, 161, 195, 106, 2, 100, 0, 115, 122, 1, 161, 195, 108, 2, 118, 97, 0, 115, 122, 2, 104, 0, 4, 99, 3, 117, 12, 0, 115, 115, 122, 1, 161, 195, 108, 105, 107, 2, 195, 169, 107, 0, 115, 122, 1, 97, 108, 108, 97, 104, 2, 195, 161, 110, 97, 107, 0, 115, 122, 1, 97, 108, 108, 97, 104, 2, 195, 179, 100, 0, 115, 122, 1, 101, 109, 2, 105, 116, 101, 107, 0, 115, 122, 8, 182, 195, 107, 2, 101, 114, 0, 7, 6, 117, 0, 3, 40, 0, 1, 116, 101, 106, 118, 111, 122, 115, 2, 110, 105, 195, 179, 3, 114, 0, 7, 6, 118, 0, 3, 82, 0, 101, 114, 115, 97, 105, 108, 108, 101, 115, 5, 1, 8, 3, 82, 107, 52, 87, 112, 57, 0, 8, 2, 32, 3, 82, 111, 0, 7, 6, 119, 0, 3, 82, 0, 7, 6, 120, 0, 8, 2, 32, 3, 37, 49, 87, 0, 3, 49, 87, 0, 7, 6, 121, 0, 4, 3, 37, 0, 1, 25, 2, 25, 0, 8, 3, 57, 0, 97, 114, 100, 3, 57, 106, 52, 70, 0, 97, 114, 100, 100, 3, 57, 106, 52, 70, 12, 0, 7, 6, 122, 0, 4, 3, 86, 0, 1, 97, 114, 161, 195, 122, 115, 2, 115, 195, 188, 108, 116, 0, 1, 101, 109, 101, 108, 2, 115, 116, 195, 186, 0, 1, 101, 109, 101, 108, 2, 115, 122, 101, 114, 122, 0, 1, 101, 109, 101, 110, 0, 1, 110, 169, 195, 112, 0, 1, 114, 111, 116, 2, 115, 195, 161, 103, 0, 1, 117, 97, 108, 97, 107, 2, 115, 195, 161, 103, 0, 1, 145, 197, 2, 115, 195, 182, 114, 195, 169, 116, 0, 1, 145, 197, 103, 2, 115, 117, 103, 195, 161, 114, 0, 1, 145, 197, 103, 2, 115, 195, 173, 112, 0, 1, 161, 195, 103, 2, 99, 115, 197, 145, 0, 1, 161, 195, 103, 2, 115, 112, 114, 97, 0, 1, 161, 195, 103, 2, 115, 117, 103, 0, 1, 161, 195, 104, 2, 115, 97, 114, 107, 111, 116, 0, 1, 161, 195, 104, 2, 115, 97, 114, 111, 107, 0, 1, 161, 195, 104, 2, 115, 111, 0, 1, 161, 195, 104, 114, 179, 195, 107, 2, 115, 195, 161, 0, 1, 161, 195, 112, 111, 116, 0, 1, 161, 195, 118, 116, 110, 111, 115, 99, 0, 1, 169, 195, 104, 101, 110, 2, 115, 195, 186, 108, 121, 0, 1, 169, 195, 104, 101, 110, 2, 115, 195, 186, 108, 121, 195, 186, 0, 1, 169, 195, 107, 2, 115, 101, 98, 0, 1, 169, 195, 107, 2, 115, 122, 0, 1, 169, 195, 107, 2, 115, 195, 169, 114, 195, 188, 108, 0, 1, 169, 195, 107, 2, 122, 115, 105, 98, 98, 97, 100, 195, 161, 115, 0, 1, 169, 195, 109, 2, 115, 195, 182, 114, 0, 1, 169, 195, 114, 2, 115, 97, 114, 107, 0, 1, 169, 195, 114, 2, 115, 97, 118, 0, 1, 169, 195, 114, 2, 115, 101, 114, 108, 101, 103, 0, 1, 169, 195, 114, 2, 115, 101, 114, 112, 101, 110, 121, 197, 145, 0, 1, 169, 195, 114, 2, 115, 105, 112, 107, 0, 1, 169, 195, 114, 2, 115, 105, 115, 97, 107, 0, 1, 169, 195, 114, 2, 115, 111, 100, 0, 1, 169, 195, 114, 2, 115, 111, 100, 114, 111, 110, 121, 0, 1, 169, 195, 114, 2, 115, 195, 161, 114, 107, 195, 161, 0, 1, 169, 195, 114, 2, 115, 195, 173, 112, 0, 1, 173, 195, 99, 101, 114, 112, 2, 115, 195, 169, 103, 0, 1, 173, 195, 116, 2, 115, 195, 161, 118, 0, 1, 173, 195, 118, 114, 161, 195, 2, 115, 195, 186, 106, 0, 1, 177, 197, 116, 0, 1, 177, 197, 116, 2, 122, 115, 195, 161, 107, 0, 1, 177, 197, 122, 115, 2, 115, 195, 188, 108, 116, 0, 1, 179, 195, 108, 97, 107, 0, 1, 179, 195, 114, 116, 97, 109, 2, 115, 97, 112, 107, 0, 1, 179, 195, 114, 116, 97, 109, 2, 115, 105, 112, 107, 0, 1, 179, 195, 114, 116, 97, 109, 2, 122, 115, 195, 161, 107, 0, 1, 182, 195, 107, 122, 101, 2, 115, 111, 114, 0, 1, 182, 195, 107, 122, 101, 2, 115, 195, 161, 118, 0, 1, 182, 195, 107, 122, 115, 101, 2, 115, 111, 114, 0, 1, 182, 195, 107, 122, 115, 101, 2, 115, 195, 161, 118, 0, 8, 110, 111, 114, 98, 0, 8, 114, 111, 98, 2, 122, 115, 195, 173, 114, 0, 8, 145, 197, 2, 115, 101, 98, 0, 8, 145, 197, 2, 115, 117, 116, 0, 8, 145, 197, 103, 0, 8, 145, 197, 103, 2, 115, 195, 188, 118, 195, 182, 108, 116, 0, 8, 161, 195, 108, 2, 115, 101, 98, 0, 8, 161, 195, 108, 2, 115, 195, 179, 104, 0, 8, 161, 195, 122, 115, 2, 115, 111, 114, 0, 8, 169, 195, 109, 2, 115, 101, 114, 0, 8, 169, 195, 109, 2, 115, 195, 161, 114, 103, 0, 8, 169, 195, 116, 105, 118, 0, 8, 173, 195, 116, 2, 115, 104, 105, 108, 108, 0, 8, 173, 195, 116, 2, 115, 111, 114, 0, 8, 173, 195, 116, 2, 115, 111, 117, 0, 8, 173, 195, 116, 2, 122, 115, 195, 161, 107, 0, 8, 173, 195, 118, 2, 115, 0, 8, 177, 197, 116, 2, 122, 115, 111, 110, 103, 108, 197, 145, 114, 0, 99, 1, 161, 195, 109, 2, 115, 122, 0, 99, 1, 169, 195, 109, 2, 115, 122, 0, 122, 1, 161, 195, 121, 103, 105, 118, 2, 195, 161, 108, 108, 0, 122, 2, 98, 0, 122, 2, 116, 0, 122, 2, 118, 0, 4, 115, 122, 3, 86, 87, 0, 115, 122, 8, 161, 195, 103, 2, 195, 161, 109, 108, 97, 0, 115, 122, 8, 161, 195, 103, 2, 195, 161, 109, 108, 195, 161, 0, 4, 115, 1, 97, 103, 2, 195, 161, 103, 3, 86, 89, 0, 115, 1, 145, 197, 2, 117, 116, 97, 0, 115, 8, 161, 195, 118, 2, 111, 114, 0, 115, 8, 169, 195, 104, 101, 110, 2, 101, 108, 121, 0, 115, 8, 169, 195, 114, 2, 195, 179, 0, 4, 1, 97, 2, 116, 3, 87, 0, 1, 97, 2, 116, 195, 161, 110, 0, 1, 97, 109, 108, 97, 107, 108, 97, 2, 107, 111, 0, 1, 101, 2, 116, 0, 1, 101, 100, 110, 101, 114, 2, 107, 101, 100, 0, 1, 101, 106, 101, 102, 101, 98, 2, 116, 101, 0, 1, 101, 106, 101, 102, 101, 108, 2, 116, 101, 0, 1, 101, 106, 101, 102, 101, 108, 2, 116, 195, 169, 107, 0, 1, 101, 107, 2, 100, 116, 0, 1, 101, 118, 114, 101, 122, 115, 2, 107, 101, 100, 0, 1, 101, 121, 103, 101, 2, 107, 101, 0, 1, 101, 121, 103, 101, 2, 116, 101, 0, 1, 101, 121, 108, 101, 104, 2, 107, 101, 0, 1, 101, 121, 108, 101, 104, 2, 107, 101, 100, 0, 1, 105, 98, 2, 116, 97, 116, 0, 1, 105, 98, 2, 116, 111, 110, 115, 0, 1, 105, 98, 2, 116, 111, 115, 0, 1, 110, 169, 195, 112, 2, 116, 0, 1, 110, 169, 195, 112, 2, 116, 195, 161, 114, 0, 1, 111, 98, 111, 100, 2, 116, 0, 1, 111, 98, 111, 107, 2, 116, 0, 1, 111, 102, 111, 112, 2, 107, 111, 100, 0, 1, 111, 103, 108, 111, 100, 2, 116, 0, 1, 111, 103, 110, 97, 104, 2, 116, 0, 1, 111, 103, 111, 98, 2, 116, 195, 161, 107, 0, 1, 111, 104, 2, 116, 97, 0, 1, 111, 104, 2, 116, 195, 161, 0, 1, 111, 107, 97, 108, 116, 97, 115, 99, 2, 116, 97, 0, 1, 111, 107, 97, 108, 116, 97, 115, 99, 2, 116, 111, 107, 0, 1, 111, 107, 108, 97, 108, 103, 111, 102, 2, 116, 0, 1, 111, 107, 108, 161, 195, 108, 97, 116, 2, 116, 0, 1, 111, 107, 111, 2, 116, 0, 1, 111, 107, 116, 97, 110, 111, 118, 2, 116, 97, 0, 1, 111, 107, 116, 97, 116, 105, 118, 2, 116, 0, 1, 111, 107, 169, 195, 100, 110, 161, 195, 106, 97, 2, 116, 0, 1, 111, 107, 169, 195, 106, 161, 195, 116, 2, 116, 97, 115, 115, 0, 1, 111, 107, 169, 195, 106, 161, 195, 116, 2, 116, 97, 116, 0, 1, 111, 114, 161, 195, 116, 97, 104, 2, 116, 0, 1, 111, 116, 108, 161, 195, 118, 2, 116, 97, 115, 115, 0, 1, 111, 116, 108, 161, 195, 118, 2, 116, 97, 116, 0, 1, 111, 116, 114, 97, 116, 2, 107, 0, 1, 111, 116, 114, 97, 116, 2, 116, 0, 1, 111, 116, 122, 115, 111, 2, 107, 111, 100, 0, 1, 111, 121, 110, 161, 195, 105, 104, 2, 116, 0, 1, 111, 121, 110, 161, 195, 109, 108, 117, 110, 97, 116, 2, 116, 0, 1, 145, 197, 108, 101, 100, 101, 122, 115, 2, 107, 195, 182, 0, 1, 145, 197, 108, 108, 101, 122, 115, 2, 116, 101, 116, 0, 1, 145, 197, 116, 106, 101, 114, 2, 107, 195, 182, 0, 1, 145, 197, 116, 106, 101, 114, 2, 116, 0, 1, 145, 197, 121, 103, 2, 107, 195, 182, 100, 0, 1, 145, 197, 121, 103, 2, 116, 0, 1, 161, 195, 98, 105, 104, 2, 116, 97, 116, 0, 1, 161, 195, 104, 2, 116, 97, 114, 116, 195, 161, 115, 0, 1, 161, 195, 107, 99, 111, 107, 2, 116, 97, 0, 1, 161, 195, 114, 2, 107, 195, 179, 100, 0, 1, 161, 195, 114, 97, 121, 103, 97, 109, 2, 107, 111, 100, 0, 1, 161, 195, 114, 97, 121, 103, 97, 109, 2, 116, 0, 1, 161, 195, 116, 122, 115, 105, 116, 2, 116, 0, 1, 169, 195, 116, 110, 105, 2, 107, 101, 100, 0, 1, 169, 195, 116, 110, 105, 2, 116, 0, 1, 173, 195, 118, 2, 115, 122, 105, 110, 116, 0, 1, 179, 195, 116, 106, 186, 195, 121, 110, 2, 107, 111, 0, 1, 179, 195, 116, 114, 97, 116, 2, 107, 0, 1, 179, 195, 116, 114, 97, 116, 2, 116, 0, 1, 182, 195, 98, 110, 182, 195, 108, 188, 195, 107, 2, 116, 101, 116, 0, 1, 182, 195, 100, 108, 188, 195, 2, 116, 0, 1, 182, 195, 107, 103, 101, 100, 105, 2, 112, 111, 110, 0, 1, 182, 195, 107, 109, 101, 122, 115, 2, 116, 0, 1, 182, 195, 107, 115, 99, 161, 195, 110, 97, 116, 2, 116, 195, 161, 114, 115, 97, 115, 195, 161, 103, 0, 1, 182, 195, 107, 122, 115, 101, 2, 116, 0, 1, 182, 195, 116, 108, 182, 195, 2, 107, 195, 182, 0, 1, 182, 195, 116, 108, 182, 195, 2, 116, 101, 0, 1, 182, 195, 116, 108, 182, 195, 107, 2, 107, 195, 182, 100, 0, 1, 182, 195, 116, 182, 195, 107, 2, 107, 195, 182, 0, 1, 182, 195, 116, 182, 195, 107, 2, 116, 0, 1, 186, 195, 115, 99, 186, 195, 98, 2, 107, 111, 0, 1, 186, 195, 115, 99, 186, 195, 98, 2, 107, 111, 100, 0, 1, 186, 195, 115, 99, 186, 195, 98, 2, 116, 0, 1, 186, 195, 115, 99, 186, 195, 98, 2, 116, 97, 116, 0, 4, 115, 122, 1, 161, 195, 122, 115, 2, 111, 114, 3, 87, 12, 0, 115, 122, 1, 173, 195, 116, 2, 101, 114, 0, 115, 122, 1, 173, 195, 118, 2, 105, 110, 116, 101, 115, 0, 115, 122, 1, 177, 197, 116, 2, 101, 114, 195, 169, 115, 115, 122, 0, 115, 122, 1, 177, 197, 116, 2, 101, 114, 195, 169, 115, 122, 0, 4, 115, 3, 88, 0, 115, 8, 110, 169, 195, 112, 2, 101, 100, 0, 115, 8, 111, 114, 2, 122, 97, 98, 195, 161, 108, 0, 4, 115, 122, 115, 1, 111, 114, 2, 101, 109, 3, 88, 12, 0, 122, 115, 0, 115, 122, 1, 114, 182, 195, 116, 2, 195, 161, 115, 122, 108, 195, 179, 3, 88, 86, 0, 4, 1, 169, 195, 104, 101, 110, 2, 115, 195, 169, 3, 89, 0, 115, 1, 105, 114, 2, 116, 0, 115, 1, 161, 195, 114, 97, 100, 2, 102, 195, 169, 115, 122, 101, 107, 0, 115, 1, 161, 195, 114, 97, 103, 2, 116, 195, 161, 114, 111, 108, 195, 179, 0, 4, 115, 1, 97, 103, 2, 195, 161, 103, 3, 89, 89, 0, 115, 1, 97, 103, 105, 2, 195, 161, 103, 0, 115, 8, 97, 114, 161, 195, 122, 115, 2, 195, 161, 103, 0, 4, 1, 108, 97, 119, 2, 101, 114, 3, 117, 0, 1, 179, 195, 103, 111, 102, 2, 107, 111, 100, 0, 4, 105, 112, 112, 122, 195, 161, 114, 3, 117, 37, 48, 86, 112, 52, 0, 105, 112, 122, 195, 161, 114, 0, 195, 188, 114, 105, 99, 104, 8, 3, 117, 109, 52, 37, 0, 7, 6, 0, 195, 177, 3, 65, 0, 36, 3, 70, 39, 55, 55, 112, 52, 0, 195, 167, 3, 74, 0, 195, 159, 3, 87, 0, 4, 195, 164, 3, 107, 0, 195, 166, 0, 195, 184, 3, 108, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts24 = FileInMemory_createWithData (110541, reinterpret_cast (&espeakdata_dicts24_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/hu_dict", L"hu"); Collection_addItem (me.peek(), espeakdata_dicts24.transfer()); static unsigned char espeakdata_dicts25_data[2436] = { 0, 4, 0, 0, 114, 6, 0, 0, 0, 0, 0, 0, 0, 5, 65, 4, 35, 0, 0, 0, 0, 0, 6, 65, 8, 69, 37, 0, 0, 0, 0, 0, 6, 65, 12, 87, 37, 0, 0, 0, 0, 0, 6, 65, 16, 70, 37, 0, 0, 0, 0, 0, 5, 65, 20, 36, 0, 0, 0, 0, 0, 6, 65, 24, 36, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 4, 95, 4, 16, 20, 10, 87, 47, 39, 67, 35, 49, 6, 36, 55, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 51, 88, 57, 36, 34, 36, 87, 6, 40, 50, 0, 0, 13, 3, 95, 48, 67, 105, 35, 34, 57, 6, 40, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 48, 47, 6, 35, 87, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 55, 88, 57, 36, 39, 25, 35, 50, 35, 87, 6, 40, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 49, 88, 47, 35, 87, 50, 6, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 50, 88, 113, 87, 6, 35, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 63, 63, 79, 4, 37, 51, 0, 0, 0, 0, 14, 3, 95, 52, 88, 113, 35, 67, 35, 87, 6, 40, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 53, 88, 105, 37, 87, 40, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 54, 88, 82, 35, 25, 87, 40, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 56, 88, 40, 25, 87, 6, 40, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 57, 88, 37, 50, 50, 35, 87, 6, 40, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 48, 77, 50, 63, 37, 55, 6, 39, 50, 0, 0, 0, 0, 13, 4, 95, 48, 77, 49, 105, 35, 86, 6, 35, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 3, 95, 214, 133, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 95, 213, 168, 6, 13, 25, 0, 0, 7, 3, 95, 213, 167, 36, 0, 0, 0, 0, 0, 0, 0, 8, 3, 95, 213, 161, 108, 69, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 3, 1, 16, 63, 4, 36, 115, 23, 0, 0, 0, 0, 0, 0, 0, 0, 11, 2, 95, 51, 57, 36, 34, 6, 36, 113, 0, 0, 11, 2, 95, 50, 57, 36, 34, 49, 6, 40, 0, 0, 9, 2, 95, 49, 63, 6, 36, 49, 0, 0, 10, 2, 95, 48, 86, 13, 67, 6, 39, 0, 0, 9, 2, 95, 55, 57, 6, 39, 25, 0, 0, 9, 2, 95, 54, 82, 6, 36, 112, 0, 0, 10, 2, 95, 53, 105, 6, 37, 50, 79, 0, 0, 10, 2, 95, 52, 74, 6, 39, 34, 87, 0, 0, 0, 7, 2, 214, 134, 81, 36, 0, 0, 9, 2, 95, 57, 6, 37, 50, 13, 0, 0, 8, 2, 95, 56, 6, 40, 25, 0, 7, 2, 214, 132, 113, 36, 0, 0, 8, 2, 214, 131, 111, 106, 34, 0, 0, 8, 2, 214, 130, 105, 106, 50, 0, 0, 7, 2, 214, 129, 115, 39, 0, 0, 7, 2, 214, 128, 34, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 213, 166, 86, 35, 0, 0, 8, 2, 213, 165, 57, 36, 74, 0, 0, 7, 2, 213, 164, 70, 35, 0, 0, 8, 2, 213, 163, 79, 37, 63, 0, 0, 8, 2, 213, 162, 69, 36, 50, 0, 0, 0, 0, 8, 2, 213, 175, 49, 36, 50, 0, 0, 7, 2, 213, 174, 115, 35, 0, 0, 7, 2, 213, 173, 104, 36, 0, 0, 8, 2, 213, 172, 55, 106, 50, 0, 0, 8, 2, 213, 171, 37, 50, 37, 0, 0, 7, 2, 213, 170, 88, 36, 0, 0, 7, 2, 213, 169, 25, 39, 0, 0, 0, 7, 2, 213, 183, 89, 35, 0, 0, 7, 2, 213, 182, 50, 40, 0, 0, 7, 2, 213, 181, 105, 37, 0, 0, 8, 2, 213, 180, 63, 36, 50, 0, 0, 7, 2, 213, 179, 78, 36, 0, 0, 8, 2, 213, 178, 54, 35, 70, 0, 0, 7, 2, 213, 177, 114, 35, 0, 0, 7, 2, 213, 176, 105, 39, 0, 0, 8, 2, 213, 191, 47, 106, 50, 0, 0, 8, 2, 213, 190, 82, 36, 82, 0, 0, 7, 2, 213, 189, 87, 36, 0, 0, 7, 2, 213, 188, 67, 35, 0, 0, 7, 2, 213, 187, 73, 36, 0, 0, 7, 2, 213, 186, 48, 36, 0, 0, 7, 2, 213, 185, 74, 35, 0, 0, 7, 2, 213, 184, 82, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 213, 162, 0, 213, 163, 0, 213, 169, 0, 213, 175, 0, 213, 186, 0, 213, 191, 0, 214, 132, 0, 7, 6, 18, 67, 213, 184, 214, 130, 0, 213, 161, 213, 181, 0, 213, 171, 214, 130, 0, 213, 171, 213, 181, 0, 213, 184, 213, 181, 0, 7, 6, 20, 0, 0, 135, 5, 0, 0, 101, 5, 130, 5, 0, 0, 0, 0, 6, 1, 50, 0, 4, 3, 35, 0, 213, 181, 2, 32, 0, 213, 181, 3, 108, 0, 7, 6, 1, 51, 0, 3, 69, 0, 8, 2, 17, 67, 3, 69, 13, 0, 7, 6, 1, 52, 0, 3, 79, 0, 8, 2, 17, 67, 3, 79, 13, 0, 7, 6, 1, 53, 0, 3, 70, 0, 8, 2, 17, 67, 3, 70, 13, 0, 7, 6, 1, 54, 0, 3, 36, 0, 213, 161, 3, 57, 35, 0, 8, 3, 57, 36, 0, 214, 133, 3, 57, 39, 0, 7, 6, 1, 55, 0, 8, 2, 18, 66, 3, 13, 86, 0, 3, 86, 0, 8, 2, 17, 67, 3, 86, 13, 0, 7, 6, 1, 56, 0, 3, 36, 0, 214, 133, 3, 107, 0, 213, 181, 3, 109, 0, 7, 6, 1, 57, 0, 3, 13, 0, 7, 6, 1, 58, 0, 3, 25, 0, 8, 2, 17, 67, 3, 25, 13, 0, 7, 6, 1, 59, 0, 3, 88, 0, 7, 6, 1, 60, 0, 3, 37, 0, 214, 130, 2, 32, 3, 37, 82, 0, 214, 130, 3, 106, 0, 213, 181, 3, 110, 0, 7, 6, 1, 61, 0, 3, 55, 0, 8, 2, 17, 67, 3, 55, 13, 0, 7, 6, 1, 62, 0, 3, 104, 0, 7, 6, 1, 63, 0, 3, 115, 0, 8, 2, 17, 67, 3, 115, 13, 0, 7, 6, 1, 64, 0, 3, 49, 0, 8, 2, 17, 67, 3, 49, 13, 0, 7, 6, 1, 65, 0, 3, 105, 0, 8, 2, 17, 67, 3, 105, 13, 0, 7, 6, 1, 66, 0, 3, 114, 0, 8, 2, 17, 67, 3, 114, 13, 0, 7, 6, 1, 67, 0, 3, 54, 0, 8, 2, 17, 67, 3, 54, 13, 0, 7, 6, 1, 68, 0, 3, 78, 0, 8, 2, 17, 67, 3, 78, 13, 0, 7, 6, 1, 69, 0, 1, 17, 67, 2, 32, 3, 13, 63, 0, 4, 3, 63, 0, 1, 18, 67, 2, 32, 0, 8, 2, 17, 67, 3, 63, 13, 0, 7, 6, 1, 70, 0, 3, 105, 0, 8, 2, 17, 67, 3, 105, 13, 0, 7, 6, 1, 71, 0, 1, 17, 67, 2, 32, 3, 13, 50, 0, 4, 3, 50, 0, 1, 18, 67, 2, 32, 0, 8, 2, 17, 67, 3, 50, 13, 0, 7, 6, 1, 72, 0, 8, 2, 213, 191, 3, 13, 89, 0, 3, 89, 0, 8, 2, 17, 67, 3, 89, 13, 0, 7, 6, 1, 73, 0, 4, 3, 39, 0, 213, 181, 2, 32, 0, 213, 181, 1, 17, 65, 3, 39, 57, 0, 214, 130, 3, 40, 0, 213, 181, 3, 40, 57, 0, 214, 130, 2, 17, 65, 3, 82, 0, 8, 3, 82, 39, 0, 7, 6, 1, 74, 0, 3, 74, 0, 8, 2, 17, 67, 3, 74, 13, 0, 7, 6, 1, 75, 0, 3, 48, 0, 8, 2, 17, 67, 3, 48, 13, 0, 7, 6, 1, 76, 0, 3, 73, 0, 8, 2, 17, 67, 3, 73, 13, 0, 7, 6, 1, 77, 0, 3, 67, 0, 8, 2, 17, 67, 3, 67, 13, 0, 7, 6, 1, 78, 0, 8, 2, 18, 66, 3, 13, 87, 0, 3, 87, 0, 8, 2, 17, 67, 3, 87, 13, 0, 7, 6, 1, 79, 0, 3, 82, 0, 8, 2, 17, 67, 3, 82, 13, 0, 7, 6, 1, 80, 0, 3, 47, 0, 8, 2, 17, 67, 3, 47, 13, 0, 7, 6, 1, 81, 0, 1, 17, 67, 2, 32, 3, 13, 34, 0, 4, 3, 34, 0, 1, 18, 67, 2, 32, 0, 8, 2, 17, 67, 3, 34, 13, 0, 7, 6, 1, 82, 0, 3, 112, 0, 8, 2, 17, 67, 3, 112, 13, 0, 7, 6, 1, 83, 0, 3, 82, 0, 8, 2, 17, 67, 3, 82, 13, 0, 7, 6, 1, 84, 0, 8, 2, 17, 67, 3, 48, 6, 13, 0, 3, 111, 0, 7, 6, 1, 85, 0, 3, 113, 0, 8, 2, 17, 67, 3, 113, 13, 0, 7, 6, 1, 86, 0, 3, 39, 0, 7, 6, 1, 87, 0, 3, 81, 0, 8, 2, 17, 67, 3, 81, 13, 0, 7, 6, 0, 36, 3, 70, 39, 55, 13, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts25 = FileInMemory_createWithData (2435, reinterpret_cast (&espeakdata_dicts25_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/hy_dict", L"hy"); Collection_addItem (me.peek(), espeakdata_dicts25.transfer()); static unsigned char espeakdata_dicts26_data[3083] = { 0, 4, 0, 0, 29, 10, 0, 0, 0, 0, 0, 0, 0, 5, 65, 4, 35, 0, 0, 0, 0, 0, 6, 65, 8, 69, 36, 0, 0, 0, 0, 0, 6, 65, 12, 74, 36, 0, 0, 0, 13, 4, 95, 8, 1, 3, 105, 6, 35, 74, 107, 49, 0, 0, 0, 6, 65, 16, 70, 36, 0, 0, 0, 0, 0, 5, 65, 20, 36, 0, 0, 0, 0, 0, 6, 65, 24, 107, 81, 0, 0, 0, 0, 0, 6, 65, 28, 79, 36, 0, 0, 6, 195, 76, 19, 135, 72, 0, 0, 0, 6, 65, 32, 105, 35, 0, 0, 0, 0, 11, 1, 35, 48, 6, 35, 79, 35, 51, 0, 27, 0, 5, 65, 36, 37, 0, 0, 12, 1, 37, 48, 13, 52, 87, 6, 107, 50, 0, 27, 0, 14, 1, 38, 47, 4, 35, 50, 70, 35, 70, 6, 35, 50, 0, 0, 12, 68, 8, 80, 133, 44, 69, 107, 69, 122, 19, 0, 0, 6, 65, 40, 73, 36, 0, 0, 0, 12, 1, 42, 69, 6, 37, 50, 47, 35, 66, 0, 27, 0, 12, 1, 43, 47, 6, 35, 63, 69, 35, 105, 0, 27, 0, 6, 65, 44, 49, 35, 0, 0, 0, 0, 18, 1, 47, 79, 4, 35, 52, 37, 87, 15, 63, 6, 37, 52, 37, 66, 0, 27, 0, 6, 65, 48, 107, 55, 0, 0, 0, 0, 0, 6, 65, 52, 107, 63, 0, 0, 0, 0, 0, 6, 65, 56, 107, 50, 0, 0, 0, 0, 0, 5, 65, 60, 39, 0, 0, 17, 1, 61, 87, 4, 35, 63, 35, 15, 70, 6, 107, 66, 35, 50, 0, 27, 0, 0, 0, 12, 1, 64, 35, 15, 49, 6, 107, 108, 50, 79, 0, 6, 65, 64, 48, 36, 0, 0, 0, 0, 0, 6, 65, 68, 49, 37, 0, 0, 0, 0, 0, 6, 65, 72, 107, 51, 0, 0, 0, 0, 0, 6, 65, 76, 107, 87, 0, 0, 0, 0, 0, 6, 65, 80, 47, 36, 0, 0, 0, 0, 0, 5, 65, 84, 40, 0, 0, 0, 0, 0, 6, 65, 88, 81, 36, 0, 0, 0, 0, 0, 12, 1, 92, 6, 69, 107, 49, 87, 55, 107, 89, 0, 6, 65, 92, 58, 36, 0, 0, 0, 15, 1, 94, 47, 4, 35, 50, 70, 35, 47, 6, 39, 48, 37, 0, 0, 0, 15, 4, 95, 49, 77, 49, 87, 13, 34, 6, 37, 69, 40, 10, 0, 7, 65, 96, 107, 49, 87, 0, 0, 15, 4, 95, 49, 77, 50, 87, 13, 73, 6, 40, 47, 35, 10, 0, 0, 16, 4, 95, 49, 77, 51, 87, 13, 63, 6, 37, 55, 57, 35, 51, 0, 0, 0, 6, 65, 100, 57, 36, 0, 0, 0, 0, 0, 7, 65, 104, 86, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 1, 126, 47, 6, 37, 55, 70, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 64, 17, 1, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 4, 16, 20, 10, 49, 4, 39, 63, 35, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 20, 12, 4, 47, 6, 37, 55, 70, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 36, 19, 1, 32, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 16, 144, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 16, 19, 128, 72, 0, 6, 195, 32, 19, 135, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 16, 20, 137, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 8, 18, 23, 4, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 13, 3, 14, 63, 6, 35, 49, 52, 108, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 51, 88, 47, 6, 37, 79, 35, 48, 40, 55, 40, 105, 0, 0, 13, 3, 95, 48, 67, 51, 6, 35, 47, 40, 87, 23, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 49, 67, 87, 13, 52, 6, 35, 47, 40, 87, 23, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 49, 57, 87, 13, 63, 69, 6, 37, 55, 35, 50, 69, 13, 55, 35, 87, 0, 0, 19, 3, 95, 49, 56, 70, 13, 55, 6, 35, 48, 35, 50, 69, 13, 55, 35, 87, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 49, 49, 87, 6, 13, 69, 13, 55, 35, 87, 0, 0, 14, 3, 95, 49, 48, 87, 13, 48, 6, 40, 55, 40, 105, 0, 0, 16, 3, 95, 49, 51, 47, 6, 37, 79, 35, 69, 13, 55, 35, 87, 0, 0, 15, 3, 95, 49, 50, 70, 6, 40, 35, 69, 13, 55, 35, 87, 0, 0, 16, 3, 95, 49, 53, 55, 6, 37, 63, 35, 69, 13, 55, 35, 87, 0, 0, 17, 3, 95, 49, 52, 6, 13, 63, 48, 35, 47, 69, 13, 55, 35, 87, 0, 0, 17, 3, 95, 49, 55, 47, 6, 40, 73, 40, 105, 69, 13, 55, 35, 87, 0, 0, 16, 3, 95, 49, 54, 6, 13, 50, 35, 63, 69, 13, 55, 35, 87, 0, 0, 0, 17, 3, 95, 55, 88, 47, 6, 40, 73, 40, 105, 48, 40, 55, 40, 105, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 66, 44, 80, 49, 13, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 50, 88, 70, 6, 40, 35, 48, 40, 55, 40, 105, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 63, 63, 49, 4, 39, 70, 36, 105, 6, 40, 52, 40, 81, 0, 0, 0, 0, 17, 3, 95, 52, 88, 6, 107, 63, 48, 35, 47, 48, 40, 55, 40, 105, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 53, 88, 55, 6, 37, 63, 35, 48, 40, 55, 40, 105, 0, 0, 0, 0, 9, 198, 76, 80, 129, 28, 18, 64, 72, 0, 0, 0, 0, 0, 16, 3, 95, 54, 88, 6, 107, 50, 35, 63, 48, 40, 55, 40, 105, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 3, 95, 56, 88, 70, 13, 55, 6, 35, 48, 35, 50, 48, 40, 55, 40, 105, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 57, 88, 87, 13, 63, 69, 6, 37, 55, 35, 50, 48, 40, 55, 40, 105, 0, 0, 0, 0, 0, 0, 7, 196, 77, 80, 84, 84, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 15, 7, 15, 6, 108, 79, 39, 50, 107, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 100, 19, 135, 72, 13, 4, 95, 48, 77, 50, 73, 6, 40, 47, 35, 10, 0, 0, 14, 4, 95, 48, 77, 51, 63, 6, 37, 55, 57, 35, 51, 0, 0, 0, 13, 4, 95, 48, 77, 49, 51, 6, 37, 69, 40, 10, 0, 0, 13, 4, 95, 2, 18, 22, 69, 52, 6, 37, 12, 82, 0, 0, 0, 0, 0, 0, 0, 12, 68, 8, 80, 197, 44, 69, 107, 74, 122, 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 3, 9, 18, 47, 6, 39, 48, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 19, 20, 11, 87, 47, 51, 6, 39, 49, 0, 0, 0, 13, 4, 95, 1, 3, 21, 35, 49, 57, 6, 40, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 18, 14, 7, 52, 6, 37, 66, 79, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 4, 95, 1, 3, 50, 70, 40, 69, 13, 55, 35, 49, 57, 6, 40, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 16, 20, 137, 64, 17, 1, 72, 0, 0, 0, 0, 0, 0, 16, 2, 194, 163, 48, 39, 50, 87, 47, 6, 107, 52, 55, 37, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 3, 5, 4, 87, 13, 70, 6, 37, 55, 35, 0, 0, 0, 0, 14, 4, 95, 12, 9, 7, 70, 6, 115, 79, 51, 35, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 8, 82, 193, 76, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 144, 72, 0, 0, 0, 8, 197, 64, 84, 129, 56, 112, 66, 0, 0, 0, 7, 196, 84, 229, 21, 44, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 2, 95, 34, 47, 4, 35, 50, 70, 35, 49, 6, 40, 47, 37, 48, 0, 0, 17, 2, 95, 33, 47, 4, 35, 50, 70, 35, 15, 87, 6, 107, 52, 40, 0, 0, 0, 19, 2, 95, 39, 49, 4, 40, 47, 37, 48, 15, 47, 6, 40, 66, 79, 35, 55, 0, 0, 0, 0, 0, 0, 13, 4, 95, 3, 1, 16, 69, 6, 107, 87, 35, 51, 0, 0, 18, 2, 95, 41, 49, 4, 40, 52, 40, 66, 15, 47, 6, 40, 47, 40, 48, 0, 0, 17, 2, 95, 40, 49, 4, 40, 52, 40, 66, 15, 69, 6, 40, 49, 35, 0, 0, 10, 67, 64, 84, 128, 48, 13, 34, 0, 72, 0, 11, 2, 95, 46, 47, 6, 37, 47, 37, 19, 0, 0, 17, 2, 95, 45, 47, 4, 35, 50, 70, 35, 105, 6, 40, 69, 40, 66, 0, 0, 10, 2, 95, 44, 49, 6, 39, 63, 35, 0, 0, 10, 2, 95, 51, 47, 6, 37, 79, 35, 0, 0, 9, 2, 95, 50, 70, 6, 40, 35, 0, 0, 10, 2, 95, 49, 87, 6, 35, 47, 40, 0, 0, 9, 2, 95, 48, 50, 6, 39, 55, 0, 0, 11, 2, 95, 55, 47, 6, 40, 73, 40, 105, 0, 0, 10, 2, 95, 54, 6, 13, 50, 35, 63, 0, 0, 10, 2, 95, 53, 55, 6, 37, 63, 35, 0, 0, 11, 2, 95, 52, 6, 13, 63, 48, 35, 47, 0, 0, 17, 2, 95, 59, 47, 4, 37, 47, 37, 19, 15, 49, 6, 39, 63, 35, 0, 0, 16, 2, 95, 58, 47, 4, 37, 47, 37, 19, 15, 70, 6, 40, 35, 0, 0, 14, 2, 95, 57, 87, 13, 63, 69, 6, 37, 55, 35, 50, 0, 0, 13, 2, 95, 56, 70, 13, 55, 6, 35, 48, 35, 50, 0, 0, 17, 2, 95, 63, 47, 4, 35, 50, 70, 35, 15, 47, 6, 35, 65, 35, 0, 0, 17, 2, 95, 62, 55, 4, 107, 69, 37, 105, 15, 70, 6, 35, 52, 37, 0, 0, 0, 17, 2, 95, 60, 49, 4, 40, 52, 35, 66, 15, 70, 6, 35, 52, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 4, 95, 4, 15, 20, 70, 6, 108, 47, 0, 0, 0, 0, 17, 2, 95, 91, 49, 4, 40, 52, 40, 66, 15, 87, 6, 37, 49, 40, 0, 0, 0, 0, 0, 18, 2, 95, 95, 79, 4, 35, 52, 37, 87, 15, 69, 6, 35, 58, 35, 105, 0, 0, 0, 24, 2, 95, 93, 49, 4, 40, 52, 40, 66, 15, 87, 4, 37, 49, 40, 15, 47, 6, 40, 47, 40, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 7, 18, 22, 79, 52, 6, 35, 82, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 2, 95, 123, 49, 4, 40, 52, 40, 66, 15, 49, 40, 52, 6, 35, 58, 35, 55, 0, 13, 4, 95, 4, 9, 1, 6, 40, 63, 55, 112, 47, 0, 0, 0, 0, 0, 0, 0, 27, 2, 95, 125, 49, 4, 40, 52, 40, 66, 15, 49, 40, 52, 4, 35, 58, 35, 55, 15, 47, 6, 40, 47, 40, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 5, 64, 85, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 4, 64, 76, 4, 128, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 97, 0, 4, 1, 32, 17, 65, 3, 23, 35, 0, 1, 97, 0, 1, 117, 97, 0, 3, 35, 0, 117, 3, 112, 0, 105, 3, 115, 0, 7, 6, 98, 0, 3, 69, 0, 4, 101, 2, 110, 3, 69, 13, 0, 101, 8, 2, 21, 21, 0, 7, 6, 99, 0, 3, 74, 0, 104, 3, 104, 0, 7, 6, 100, 0, 3, 70, 0, 106, 3, 73, 0, 7, 6, 101, 0, 4, 1, 32, 17, 65, 3, 23, 107, 0, 1, 101, 0, 4, 3, 107, 0, 2, 32, 0, 7, 6, 102, 0, 4, 3, 81, 0, 102, 0, 7, 6, 103, 0, 3, 79, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 4, 1, 32, 17, 65, 3, 23, 37, 0, 1, 105, 0, 4, 3, 37, 0, 101, 0, 7, 6, 106, 0, 3, 73, 0, 7, 6, 107, 0, 4, 3, 49, 0, 2, 32, 0, 4, 101, 2, 110, 3, 49, 13, 0, 101, 8, 2, 21, 21, 0, 104, 3, 99, 0, 7, 6, 108, 0, 4, 3, 55, 0, 108, 0, 7, 6, 109, 0, 3, 63, 0, 101, 8, 2, 21, 21, 3, 63, 13, 0, 101, 109, 112, 101, 8, 2, 21, 3, 63, 13, 63, 48, 13, 0, 7, 6, 110, 0, 3, 50, 0, 121, 3, 65, 0, 103, 3, 66, 0, 7, 6, 111, 0, 4, 1, 32, 17, 65, 3, 23, 39, 0, 1, 111, 0, 3, 39, 0, 101, 3, 40, 0, 2, 114, 3, 108, 0, 7, 6, 112, 0, 4, 3, 48, 0, 112, 0, 101, 8, 2, 21, 21, 3, 48, 13, 0, 104, 3, 81, 0, 7, 6, 113, 0, 3, 49, 0, 117, 3, 49, 58, 0, 7, 6, 114, 0, 4, 1, 101, 2, 25, 3, 51, 0, 2, 25, 0, 3, 52, 0, 7, 6, 115, 0, 4, 3, 87, 0, 115, 0, 101, 8, 2, 21, 21, 3, 87, 13, 0, 4, 106, 3, 97, 0, 121, 0, 7, 6, 116, 0, 3, 47, 0, 101, 114, 8, 2, 21, 21, 3, 47, 13, 51, 0, 101, 108, 8, 3, 47, 13, 55, 0, 106, 3, 74, 0, 7, 6, 117, 0, 4, 1, 32, 17, 65, 3, 23, 40, 0, 1, 117, 0, 3, 40, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 49, 87, 0, 8, 3, 86, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 4, 42, 1, 42, 2, 42, 3, 0, 42, 42, 3, 0, 42, 1, 42, 42, 2, 32, 3, 24, 0, 45, 8, 32, 2, 32, 15, 3, 47, 4, 35, 50, 70, 35, 49, 6, 40, 52, 35, 66, 0, 42, 3, 69, 6, 37, 50, 47, 35, 66, 0, 36, 3, 70, 108, 55, 35, 51, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts26 = FileInMemory_createWithData (3082, reinterpret_cast (&espeakdata_dicts26_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/id_dict", L"id"); Collection_addItem (me.peek(), espeakdata_dicts26.transfer()); static unsigned char espeakdata_dicts27_data[5469] = { 0, 4, 0, 0, 1, 16, 0, 0, 0, 0, 0, 0, 0, 8, 132, 5, 195, 176, 1, 76, 8, 0, 0, 0, 8, 196, 25, 148, 137, 72, 76, 8, 0, 7, 65, 8, 69, 57, 110, 0, 0, 0, 9, 134, 13, 195, 173, 14, 21, 13, 76, 0, 0, 7, 65, 12, 87, 57, 110, 0, 0, 0, 0, 6, 195, 20, 225, 1, 8, 0, 7, 65, 16, 70, 57, 110, 0, 6, 195, 76, 147, 142, 76, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 24, 109, 81, 0, 8, 197, 28, 81, 206, 84, 208, 28, 0, 0, 0, 0, 7, 65, 28, 79, 57, 110, 0, 0, 0, 0, 0, 6, 65, 32, 105, 124, 0, 0, 0, 0, 9, 1, 35, 63, 107, 55, 55, 35, 0, 0, 0, 0, 9, 134, 8, 195, 182, 6, 21, 13, 72, 0, 0, 8, 65, 40, 57, 6, 113, 84, 0, 0, 0, 0, 9, 1, 43, 69, 55, 6, 114, 87, 0, 0, 7, 65, 44, 49, 6, 124, 0, 0, 0, 0, 12, 1, 47, 87, 49, 123, 87, 70, 136, 107, 79, 0, 0, 6, 65, 48, 109, 135, 0, 8, 133, 195, 190, 1, 195, 176, 76, 8, 133, 195, 190, 1, 195, 176, 72, 0, 9, 134, 5, 9, 7, 9, 195, 176, 76, 0, 10, 135, 21, 18, 195, 176, 21, 195, 176, 72, 0, 0, 6, 65, 52, 109, 63, 0, 12, 137, 8, 195, 182, 6, 195, 176, 21, 195, 176, 72, 8, 133, 5, 18, 21, 195, 176, 72, 0, 0, 0, 7, 196, 52, 147, 142, 4, 76, 10, 135, 195, 190, 5, 9, 18, 18, 1, 76, 0, 6, 65, 56, 109, 50, 0, 6, 131, 6, 195, 166, 76, 6, 131, 6, 195, 166, 76, 10, 5, 95, 48, 1, 14, 4, 113, 98, 0, 0, 0, 0, 0, 0, 19, 1, 61, 87, 6, 111, 63, 35, 87, 109, 63, 63, 4, 109, 34, 136, 49, 107, 0, 0, 0, 10, 135, 195, 190, 5, 9, 18, 18, 9, 76, 0, 7, 65, 64, 48, 57, 110, 0, 0, 0, 6, 195, 53, 83, 128, 76, 0, 7, 196, 52, 147, 12, 36, 8, 0, 6, 65, 68, 49, 114, 0, 0, 0, 0, 0, 7, 65, 72, 109, 34, 136, 0, 6, 195, 100, 98, 82, 28, 0, 0, 0, 6, 195, 53, 83, 137, 76, 0, 6, 65, 76, 109, 87, 0, 8, 197, 53, 147, 132, 37, 32, 76, 0, 0, 0, 8, 132, 13, 195, 179, 20, 76, 28, 0, 7, 65, 80, 47, 57, 110, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 52, 147, 142, 36, 76, 0, 7, 65, 88, 82, 35, 81, 0, 0, 0, 0, 0, 16, 65, 92, 47, 82, 6, 118, 82, 35, 55, 70, 82, 4, 35, 81, 0, 0, 0, 0, 0, 7, 65, 96, 110, 99, 87, 0, 0, 18, 4, 95, 49, 77, 50, 122, 50, 15, 63, 6, 107, 70, 55, 57, 125, 50, 0, 0, 0, 0, 16, 65, 100, 6, 115, 81, 87, 37, 55, 112, 50, 15, 4, 108, 0, 14, 0, 0, 9, 134, 195, 190, 5, 19, 19, 9, 76, 9, 134, 195, 190, 5, 19, 19, 9, 76, 0, 0, 8, 65, 104, 87, 110, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 195, 190, 5, 19, 19, 21, 76, 0, 8, 196, 84, 225, 9, 72, 72, 28, 0, 0, 0, 6, 195, 53, 83, 148, 76, 0, 6, 195, 53, 83, 149, 76, 0, 0, 0, 0, 0, 0, 0, 6, 195, 28, 20, 212, 76, 9, 134, 195, 190, 5, 19, 19, 1, 76, 0, 9, 134, 13, 195, 173, 14, 9, 18, 76, 0, 0, 6, 194, 4, 96, 76, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 7, 195, 161, 20, 21, 13, 76, 0, 0, 0, 0, 10, 135, 22, 1, 18, 195, 176, 19, 20, 72, 0, 0, 0, 0, 10, 135, 6, 195, 169, 11, 11, 19, 20, 76, 0, 0, 0, 0, 6, 195, 5, 82, 192, 28, 0, 7, 196, 32, 147, 142, 4, 76, 0, 8, 197, 53, 83, 132, 84, 208, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 22, 4, 95, 50, 77, 50, 47, 82, 6, 120, 34, 136, 15, 63, 6, 107, 70, 55, 57, 125, 50, 0, 0, 0, 12, 68, 8, 243, 12, 4, 69, 112, 55, 55, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 195, 190, 9, 14, 14, 76, 0, 7, 196, 77, 83, 85, 72, 76, 0, 0, 0, 0, 7, 196, 32, 147, 142, 36, 76, 0, 0, 0, 6, 195, 32, 149, 20, 76, 0, 0, 0, 0, 0, 9, 134, 13, 195, 173, 14, 1, 18, 76, 0, 0, 0, 0, 9, 134, 195, 161, 195, 176, 21, 18, 8, 0, 0, 0, 0, 0, 0, 5, 194, 21, 32, 72, 0, 0, 0, 0, 0, 6, 195, 21, 37, 0, 72, 0, 0, 8, 197, 32, 147, 142, 5, 32, 76, 0, 0, 6, 195, 56, 82, 64, 76, 0, 0, 0, 0, 0, 10, 135, 22, 5, 18, 195, 176, 21, 13, 72, 15, 4, 95, 4, 16, 20, 10, 49, 4, 112, 63, 63, 35, 10, 0, 0, 8, 133, 195, 190, 9, 20, 20, 76, 0, 0, 0, 6, 195, 56, 83, 65, 8, 0, 8, 197, 4, 227, 129, 73, 48, 8, 7, 132, 195, 190, 1, 21, 76, 7, 132, 195, 190, 1, 21, 72, 0, 0, 0, 0, 0, 9, 198, 56, 242, 203, 85, 35, 128, 76, 23, 4, 95, 51, 77, 50, 85, 136, 57, 6, 124, 34, 136, 15, 63, 6, 107, 70, 55, 57, 125, 50, 0, 0, 0, 7, 196, 32, 147, 137, 72, 76, 0, 10, 135, 22, 5, 18, 195, 176, 21, 18, 72, 0, 8, 133, 6, 195, 161, 21, 13, 76, 0, 0, 7, 196, 32, 19, 132, 4, 28, 0, 0, 0, 0, 7, 132, 8, 9, 195, 176, 76, 0, 0, 0, 7, 132, 195, 190, 9, 7, 76, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 28, 21, 0, 76, 0, 7, 132, 195, 161, 20, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 20, 96, 76, 8, 0, 0, 8, 133, 13, 195, 173, 14, 21, 76, 0, 0, 0, 0, 0, 9, 134, 19, 195, 173, 14, 21, 13, 76, 0, 6, 195, 32, 17, 129, 72, 10, 135, 195, 190, 195, 173, 14, 21, 13, 76, 8, 133, 13, 195, 173, 14, 19, 76, 0, 0, 0, 0, 0, 10, 135, 6, 5, 14, 7, 21, 195, 176, 76, 0, 8, 132, 22, 9, 195, 176, 76, 28, 7, 132, 22, 9, 195, 176, 72, 0, 0, 0, 0, 8, 133, 7, 195, 161, 20, 21, 76, 0, 6, 195, 32, 147, 142, 76, 0, 0, 0, 8, 133, 13, 195, 173, 14, 1, 76, 0, 6, 195, 32, 19, 142, 72, 0, 6, 195, 32, 19, 129, 76, 0, 0, 0, 0, 6, 195, 32, 147, 129, 76, 0, 6, 195, 32, 147, 128, 76, 0, 0, 0, 6, 195, 88, 84, 129, 72, 0, 0, 7, 196, 32, 81, 149, 72, 72, 7, 196, 32, 147, 129, 72, 76, 0, 0, 0, 0, 0, 0, 6, 195, 32, 147, 149, 76, 0, 0, 0, 0, 0, 0, 11, 136, 22, 5, 18, 195, 176, 9, 195, 176, 72, 6, 195, 32, 147, 147, 76, 0, 0, 9, 134, 8, 1, 6, 9, 195, 176, 72, 0, 0, 0, 8, 197, 56, 242, 203, 72, 16, 76, 6, 195, 28, 85, 0, 76, 0, 0, 0, 8, 133, 19, 195, 173, 14, 1, 76, 0, 9, 134, 195, 190, 195, 173, 14, 1, 76, 0, 0, 8, 132, 8, 10, 195, 161, 76, 28, 0, 0, 0, 0, 0, 8, 133, 12, 195, 173, 11, 1, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 24, 83, 135, 84, 76, 0, 10, 3, 95, 49, 6, 6, 121, 105, 70, 0, 0, 9, 134, 7, 5, 20, 9, 195, 176, 76, 0, 0, 8, 196, 20, 101, 9, 72, 76, 8, 0, 0, 0, 0, 0, 10, 3, 95, 50, 6, 47, 82, 6, 118, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 51, 6, 85, 136, 57, 6, 114, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 52, 6, 81, 57, 6, 118, 98, 115, 34, 136, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 32, 147, 149, 52, 76, 0, 0, 6, 194, 20, 224, 76, 8, 0, 16, 3, 95, 51, 88, 85, 136, 57, 6, 124, 47, 37, 38, 4, 115, 0, 0, 15, 3, 95, 48, 67, 105, 6, 115, 50, 70, 14, 16, 115, 84, 0, 0, 9, 134, 195, 161, 20, 20, 21, 13, 76, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 49, 67, 6, 121, 105, 70, 15, 105, 6, 115, 50, 70, 14, 51, 35, 84, 0, 0, 8, 197, 56, 242, 203, 85, 32, 76, 0, 0, 0, 9, 198, 56, 242, 203, 85, 37, 0, 76, 0, 0, 13, 3, 95, 49, 57, 50, 6, 106, 70, 57, 123, 50, 0, 0, 12, 3, 95, 49, 56, 6, 124, 70, 57, 123, 50, 0, 0, 7, 196, 88, 244, 129, 72, 76, 20, 3, 95, 50, 67, 47, 82, 6, 118, 15, 105, 6, 115, 50, 70, 14, 51, 115, 84, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 49, 49, 6, 109, 70, 55, 109, 82, 4, 115, 0, 0, 11, 3, 95, 49, 48, 47, 6, 106, 38, 115, 0, 0, 21, 3, 95, 51, 67, 85, 136, 57, 6, 114, 15, 105, 6, 115, 50, 70, 14, 51, 115, 84, 0, 14, 3, 95, 49, 51, 85, 136, 6, 109, 105, 70, 123, 50, 0, 0, 11, 3, 95, 49, 50, 47, 6, 125, 103, 81, 0, 0, 13, 3, 95, 49, 53, 81, 6, 107, 63, 47, 123, 50, 0, 0, 15, 3, 95, 49, 52, 81, 57, 6, 125, 34, 136, 47, 123, 50, 0, 0, 13, 3, 95, 49, 55, 87, 6, 128, 70, 57, 123, 50, 0, 0, 14, 3, 95, 49, 54, 87, 6, 109, 99, 87, 70, 123, 50, 0, 0, 11, 136, 195, 190, 5, 9, 18, 18, 1, 18, 76, 0, 15, 3, 95, 55, 88, 87, 57, 6, 118, 47, 37, 38, 4, 115, 0, 0, 9, 134, 195, 161, 20, 20, 9, 18, 76, 24, 3, 95, 52, 67, 81, 57, 6, 118, 98, 115, 34, 136, 15, 105, 6, 115, 50, 70, 14, 51, 115, 84, 0, 0, 0, 0, 0, 0, 0, 6, 195, 28, 85, 1, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 195, 190, 5, 9, 13, 76, 8, 133, 195, 190, 5, 9, 13, 76, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 50, 88, 47, 6, 115, 105, 70, 115, 98, 4, 115, 0, 0, 0, 0, 0, 0, 9, 134, 19, 195, 173, 14, 1, 18, 76, 0, 10, 135, 195, 190, 195, 173, 14, 1, 18, 76, 0, 0, 8, 133, 195, 190, 5, 9, 18, 76, 8, 133, 195, 190, 5, 9, 18, 72, 0, 7, 196, 33, 99, 210, 80, 8, 0, 0, 7, 132, 6, 195, 166, 18, 76, 0, 0, 12, 3, 95, 63, 63, 47, 6, 123, 79, 105, 132, 0, 0, 0, 0, 18, 3, 95, 52, 88, 81, 57, 6, 118, 16, 51, 115, 47, 4, 37, 38, 115, 0, 0, 0, 8, 197, 52, 147, 142, 5, 32, 76, 0, 0, 14, 6, 8, 1, 12, 12, 195, 179, 105, 35, 55, 55, 125, 0, 0, 0, 0, 0, 15, 3, 95, 53, 88, 81, 6, 107, 63, 47, 37, 38, 4, 115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 54, 88, 87, 6, 109, 99, 87, 70, 37, 38, 4, 115, 0, 0, 0, 0, 0, 7, 195, 76, 83, 64, 76, 28, 6, 195, 52, 149, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 56, 88, 6, 123, 105, 70, 35, 47, 4, 37, 38, 115, 0, 0, 0, 0, 0, 10, 135, 14, 15, 11, 11, 21, 195, 176, 76, 0, 0, 0, 0, 16, 3, 95, 57, 88, 50, 6, 106, 38, 115, 47, 4, 37, 38, 115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 147, 142, 76, 0, 0, 0, 9, 134, 13, 5, 195, 176, 1, 14, 8, 0, 0, 0, 0, 0, 0, 9, 134, 13, 21, 14, 9, 195, 176, 76, 9, 134, 22, 5, 18, 9, 195, 176, 72, 0, 0, 8, 133, 195, 190, 5, 19, 19, 76, 0, 7, 131, 195, 161, 14, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 8, 195, 186, 14, 72, 0, 0, 7, 196, 28, 85, 21, 52, 76, 0, 0, 15, 4, 95, 48, 77, 50, 63, 6, 107, 70, 55, 57, 125, 50, 0, 0, 0, 0, 14, 4, 95, 48, 77, 49, 85, 6, 114, 87, 115, 50, 70, 0, 0, 0, 0, 12, 68, 53, 147, 12, 4, 63, 107, 55, 55, 35, 0, 0, 0, 9, 198, 56, 242, 203, 72, 20, 128, 76, 0, 6, 195, 88, 244, 128, 76, 0, 7, 196, 28, 85, 21, 72, 76, 6, 195, 88, 244, 129, 76, 0, 0, 9, 198, 56, 242, 203, 72, 148, 128, 76, 6, 131, 195, 169, 7, 72, 0, 0, 8, 132, 13, 5, 195, 176, 76, 28, 0, 0, 0, 0, 0, 8, 133, 195, 190, 9, 195, 176, 72, 0, 0, 0, 6, 131, 14, 195, 169, 8, 0, 0, 0, 0, 7, 196, 88, 81, 206, 4, 8, 7, 196, 88, 81, 206, 4, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 100, 178, 213, 72, 76, 7, 196, 60, 178, 213, 72, 76, 0, 6, 195, 28, 81, 206, 28, 0, 0, 0, 7, 196, 53, 83, 132, 36, 76, 0, 0, 0, 6, 195, 52, 145, 192, 76, 0, 6, 195, 20, 145, 193, 76, 0, 8, 197, 53, 83, 132, 37, 32, 76, 0, 0, 9, 134, 8, 1, 6, 195, 176, 9, 72, 0, 0, 8, 133, 22, 5, 18, 195, 176, 72, 0, 6, 194, 60, 112, 76, 8, 0, 6, 195, 88, 244, 148, 76, 0, 6, 195, 88, 244, 149, 72, 0, 0, 0, 0, 0, 6, 195, 88, 244, 142, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 195, 189, 6, 115, 81, 87, 37, 55, 112, 50, 15, 4, 106, 0, 0, 11, 136, 6, 18, 1, 13, 8, 10, 195, 161, 28, 0, 0, 9, 134, 22, 5, 18, 195, 176, 1, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 22, 1, 18, 195, 176, 72, 0, 0, 0, 7, 3, 95, 195, 173, 106, 0, 0, 0, 0, 0, 7, 196, 53, 83, 132, 84, 76, 0, 0, 8, 133, 21, 18, 195, 176, 21, 72, 0, 0, 6, 195, 21, 37, 21, 72, 0, 10, 135, 8, 1, 6, 195, 176, 9, 18, 72, 0, 0, 0, 7, 3, 95, 195, 161, 124, 0, 0, 0, 0, 0, 8, 133, 6, 195, 169, 11, 11, 76, 0, 0, 0, 0, 0, 0, 0, 9, 134, 195, 190, 5, 20, 20, 1, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 53, 83, 137, 72, 76, 0, 0, 0, 0, 0, 0, 0, 8, 133, 195, 190, 1, 14, 14, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 131, 195, 186, 18, 76, 28, 0, 0, 8, 133, 195, 190, 195, 173, 14, 76, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 21, 37, 64, 72, 0, 0, 0, 0, 0, 6, 195, 21, 37, 77, 72, 0, 10, 135, 195, 190, 5, 14, 14, 1, 14, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 195, 161, 124, 0, 14, 5, 130, 195, 161, 76, 6, 130, 195, 161, 76, 28, 0, 0, 0, 0, 7, 2, 195, 173, 106, 0, 14, 6, 130, 195, 173, 76, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 195, 176, 110, 84, 0, 0, 0, 11, 2, 195, 190, 85, 6, 112, 34, 70, 132, 0, 0, 0, 0, 17, 2, 195, 189, 6, 115, 81, 87, 37, 55, 112, 50, 15, 4, 106, 0, 14, 0, 0, 11, 136, 195, 190, 5, 19, 19, 1, 18, 9, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 88, 244, 149, 52, 72, 0, 0, 0, 8, 133, 195, 190, 195, 166, 18, 76, 12, 137, 195, 190, 5, 19, 19, 1, 18, 1, 18, 76, 8, 133, 195, 190, 195, 166, 18, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 88, 20, 147, 80, 72, 0, 0, 10, 135, 195, 190, 1, 14, 14, 9, 7, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 195, 190, 5, 7, 1, 18, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 53, 147, 132, 36, 76, 0, 10, 135, 19, 195, 173, 195, 176, 1, 14, 8, 0, 0, 6, 195, 32, 81, 128, 72, 0, 0, 0, 0, 10, 135, 13, 25, 14, 4, 21, 195, 176, 76, 10, 135, 13, 21, 14, 4, 21, 195, 176, 76, 10, 135, 7, 195, 161, 20, 21, 195, 176, 76, 10, 135, 195, 161, 20, 20, 21, 195, 176, 76, 7, 195, 80, 147, 0, 76, 28, 7, 131, 1, 195, 176, 76, 28, 0, 0, 16, 2, 95, 25, 6, 115, 81, 87, 37, 55, 112, 50, 15, 4, 108, 0, 0, 0, 0, 0, 0, 0, 0, 13, 2, 95, 34, 77, 120, 87, 35, 55, 117, 105, 69, 0, 0, 23, 2, 95, 33, 6, 115, 105, 69, 136, 125, 48, 115, 50, 35, 51, 63, 4, 109, 34, 136, 49, 107, 0, 0, 0, 0, 13, 2, 95, 38, 113, 98, 63, 109, 34, 136, 49, 107, 0, 0, 10, 135, 195, 190, 5, 19, 19, 9, 18, 76, 0, 13, 2, 95, 36, 70, 6, 112, 70, 55, 35, 34, 136, 0, 24, 4, 95, 52, 77, 50, 81, 57, 6, 126, 16, 35, 34, 136, 15, 63, 6, 107, 70, 55, 57, 125, 50, 0, 0, 6, 195, 77, 99, 192, 8, 0, 14, 4, 95, 3, 1, 16, 87, 70, 6, 125, 34, 136, 70, 0, 0, 18, 2, 95, 41, 87, 82, 6, 108, 57, 107, 55, 6, 113, 49, 35, 87, 70, 0, 0, 10, 2, 95, 40, 87, 82, 108, 57, 107, 0, 0, 0, 15, 2, 95, 46, 48, 6, 40, 134, 105, 79, 70, 115, 34, 136, 0, 0, 15, 2, 95, 45, 69, 35, 50, 70, 87, 70, 34, 136, 107, 79, 0, 0, 11, 2, 95, 44, 49, 6, 112, 63, 63, 35, 0, 0, 6, 195, 88, 20, 128, 72, 11, 2, 95, 51, 85, 136, 6, 106, 34, 136, 0, 0, 11, 2, 95, 50, 70, 82, 6, 122, 34, 136, 0, 0, 9, 2, 95, 49, 6, 121, 70, 50, 0, 0, 9, 2, 95, 48, 50, 6, 40, 135, 0, 0, 9, 2, 95, 55, 87, 57, 6, 118, 0, 0, 10, 2, 95, 54, 87, 6, 110, 99, 87, 0, 0, 9, 2, 95, 53, 81, 6, 107, 63, 0, 0, 9, 134, 6, 195, 161, 9, 195, 176, 76, 14, 2, 95, 52, 81, 57, 6, 126, 16, 51, 107, 34, 136, 0, 0, 16, 2, 95, 59, 87, 6, 110, 63, 37, 49, 4, 112, 63, 63, 35, 0, 0, 18, 2, 95, 58, 70, 82, 6, 106, 48, 40, 134, 105, 79, 70, 115, 34, 136, 0, 0, 10, 2, 95, 57, 50, 6, 106, 38, 115, 0, 0, 9, 134, 13, 21, 14, 21, 195, 176, 76, 10, 2, 95, 56, 6, 123, 105, 70, 35, 0, 0, 23, 2, 95, 63, 87, 69, 6, 115, 34, 70, 132, 37, 66, 79, 4, 35, 63, 109, 34, 136, 49, 107, 0, 0, 20, 2, 95, 62, 6, 112, 70, 79, 55, 112, 82, 107, 55, 4, 113, 49, 35, 87, 70, 0, 0, 8, 197, 24, 83, 135, 84, 208, 76, 0, 12, 2, 95, 60, 112, 70, 79, 55, 112, 82, 107, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 132, 6, 18, 195, 161, 76, 28, 0, 7, 196, 20, 145, 213, 52, 76, 0, 0, 7, 132, 195, 190, 195, 186, 72, 0, 0, 0, 0, 0, 0, 0, 7, 132, 195, 190, 195, 179, 8, 0, 0, 0, 0, 0, 0, 15, 2, 95, 91, 105, 112, 34, 70, 132, 79, 55, 112, 82, 107, 0, 0, 0, 0, 9, 134, 6, 195, 166, 18, 195, 176, 76, 0, 16, 2, 95, 95, 115, 50, 70, 107, 51, 87, 70, 34, 136, 107, 79, 0, 0, 0, 23, 2, 95, 93, 105, 6, 112, 34, 70, 132, 79, 55, 112, 82, 107, 55, 6, 113, 49, 35, 87, 70, 0, 0, 20, 2, 95, 92, 6, 118, 82, 115, 99, 70, 87, 49, 4, 123, 87, 70, 136, 107, 79, 0, 0, 0, 7, 196, 53, 147, 132, 84, 76, 0, 0, 0, 7, 132, 195, 190, 195, 161, 76, 7, 132, 195, 190, 195, 161, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 133, 195, 190, 22, 195, 173, 76, 8, 8, 133, 195, 190, 22, 195, 173, 76, 0, 0, 0, 0, 0, 0, 6, 195, 20, 178, 201, 76, 0, 0, 0, 0, 0, 15, 2, 95, 123, 87, 55, 128, 82, 115, 87, 82, 107, 57, 107, 0, 0, 0, 0, 6, 194, 84, 208, 76, 28, 0, 0, 0, 24, 2, 95, 125, 87, 55, 6, 128, 82, 115, 87, 82, 4, 107, 57, 107, 55, 6, 113, 49, 35, 87, 70, 0, 0, 0, 0, 0, 0, 10, 135, 8, 195, 182, 6, 195, 176, 21, 72, 6, 131, 19, 195, 161, 76, 10, 135, 195, 190, 5, 19, 19, 21, 13, 76, 0, 0, 0, 0, 0, 0, 0, 6, 131, 19, 195, 186, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 25, 32, 77, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 53, 147, 132, 84, 208, 76, 0, 0, 0, 0, 7, 195, 33, 97, 82, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 13, 195, 173, 14, 76, 0, 0, 0, 0, 7, 132, 19, 195, 173, 14, 76, 0, 0, 0, 0, 0, 11, 136, 8, 195, 182, 6, 195, 176, 21, 13, 72, 0, 0, 0, 0, 0, 8, 133, 195, 161, 20, 20, 9, 76, 0, 0, 0, 0, 8, 133, 195, 161, 20, 20, 21, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 21, 18, 195, 176, 21, 13, 72, 0, 0, 6, 195, 76, 149, 20, 76, 0, 0, 10, 135, 195, 190, 5, 19, 19, 1, 18, 76, 0, 0, 0, 7, 196, 53, 83, 149, 52, 76, 7, 196, 53, 83, 149, 52, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 22, 15, 18, 21, 195, 176, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 195, 173, 0, 195, 189, 0, 195, 166, 0, 101, 0, 105, 0, 121, 0, 106, 0, 7, 6, 18, 67, 195, 190, 0, 99, 0, 102, 0, 104, 0, 107, 0, 112, 0, 116, 0, 120, 0, 115, 0, 7, 6, 18, 68, 112, 0, 116, 0, 107, 0, 7, 6, 20, 0, 0, 0, 120, 0, 0, 0, 120, 0, 122, 0, 0, 0, 0, 0, 6, 195, 161, 0, 2, 17, 67, 17, 67, 3, 123, 0, 4, 3, 124, 0, 2, 17, 69, 17, 68, 0, 7, 6, 195, 166, 0, 2, 17, 67, 17, 67, 3, 119, 0, 4, 3, 120, 0, 2, 17, 69, 17, 68, 0, 7, 6, 195, 169, 0, 2, 17, 67, 17, 67, 3, 57, 109, 0, 4, 3, 57, 110, 0, 2, 17, 69, 17, 68, 0, 7, 6, 195, 173, 0, 2, 17, 67, 17, 67, 3, 37, 0, 4, 3, 106, 0, 2, 17, 69, 17, 68, 0, 7, 6, 195, 176, 0, 3, 84, 0, 4, 2, 17, 66, 3, 85, 0, 2, 32, 32, 0, 7, 6, 195, 179, 0, 2, 17, 67, 17, 67, 3, 125, 0, 4, 3, 126, 0, 2, 17, 69, 17, 68, 0, 7, 6, 195, 182, 0, 8, 2, 21, 14, 128, 132, 129, 3, 4, 118, 0, 2, 17, 67, 17, 67, 3, 117, 0, 4, 3, 118, 0, 2, 17, 69, 17, 68, 0, 4, 2, 110, 103, 3, 127, 0, 2, 110, 103, 0, 7, 6, 195, 186, 0, 2, 17, 67, 17, 67, 3, 40, 0, 4, 3, 114, 0, 2, 17, 69, 17, 68, 0, 7, 6, 195, 189, 0, 2, 17, 67, 17, 67, 3, 37, 0, 4, 3, 106, 0, 2, 17, 69, 17, 68, 0, 7, 6, 195, 190, 0, 3, 85, 0, 7, 6, 97, 0, 108, 8, 2, 21, 14, 128, 132, 130, 3, 4, 111, 55, 0, 4, 2, 17, 67, 17, 67, 3, 35, 0, 8, 2, 108, 108, 12, 0, 4, 3, 111, 0, 2, 17, 69, 17, 68, 0, 4, 2, 110, 103, 3, 123, 0, 2, 110, 107, 0, 117, 2, 17, 67, 17, 67, 3, 127, 0, 4, 117, 3, 128, 0, 117, 2, 17, 69, 17, 68, 0, 7, 6, 98, 0, 4, 3, 69, 0, 98, 0, 7, 6, 99, 0, 3, 49, 0, 4, 2, 101, 3, 87, 0, 2, 105, 0, 7, 6, 100, 0, 4, 3, 70, 0, 100, 0, 7, 6, 101, 0, 2, 17, 67, 17, 67, 3, 109, 0, 4, 3, 110, 0, 2, 17, 69, 17, 68, 0, 4, 2, 110, 103, 3, 121, 0, 2, 110, 107, 0, 105, 2, 17, 67, 17, 67, 0, 121, 2, 17, 67, 17, 67, 0, 4, 105, 3, 122, 0, 105, 2, 17, 69, 17, 68, 0, 121, 0, 121, 2, 17, 69, 17, 68, 0, 103, 105, 3, 122, 57, 107, 0, 7, 6, 102, 0, 110, 100, 3, 63, 47, 0, 4, 1, 21, 2, 108, 3, 69, 0, 1, 21, 2, 110, 0, 4, 3, 81, 0, 102, 0, 4, 1, 17, 65, 2, 17, 65, 3, 82, 0, 1, 108, 2, 17, 65, 0, 110, 116, 3, 131, 69, 47, 0, 7, 6, 103, 0, 4, 1, 161, 195, 2, 97, 3, 0, 4, 1, 161, 195, 2, 117, 3, 0, 4, 1, 179, 195, 2, 97, 3, 0, 4, 1, 179, 195, 2, 117, 3, 0, 4, 1, 186, 195, 2, 97, 3, 0, 1, 186, 195, 2, 117, 3, 0, 4, 1, 17, 65, 2, 105, 3, 57, 0, 1, 17, 65, 2, 106, 0, 4, 2, 105, 3, 77, 0, 8, 2, 101, 0, 8, 2, 105, 0, 8, 2, 195, 166, 0, 8, 2, 195, 173, 0, 106, 0, 106, 8, 0, 4, 3, 79, 0, 1, 17, 65, 2, 108, 0, 1, 17, 65, 2, 110, 0, 8, 0, 103, 0, 110, 2, 32, 3, 79, 132, 0, 4, 1, 17, 65, 2, 97, 3, 98, 0, 1, 17, 65, 2, 114, 0, 1, 17, 65, 2, 117, 0, 1, 17, 65, 2, 195, 176, 0, 4, 2, 32, 3, 99, 0, 2, 115, 0, 116, 3, 99, 70, 0, 7, 6, 104, 0, 118, 3, 49, 82, 0, 106, 3, 97, 0, 108, 3, 103, 0, 3, 105, 0, 110, 3, 105, 132, 0, 114, 3, 105, 136, 0, 7, 6, 105, 0, 4, 1, 25, 2, 110, 103, 3, 37, 0, 1, 25, 2, 110, 107, 0, 2, 17, 67, 17, 67, 3, 107, 0, 4, 3, 108, 0, 2, 17, 69, 17, 68, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 2, 116, 3, 47, 0, 8, 3, 49, 0, 2, 18, 66, 3, 77, 0, 4, 8, 2, 18, 66, 3, 78, 0, 106, 0, 4, 3, 79, 0, 2, 25, 0, 2, 115, 3, 99, 0, 2, 107, 3, 105, 0, 7, 6, 108, 0, 3, 55, 0, 108, 3, 70, 55, 0, 4, 2, 17, 66, 29, 3, 103, 0, 2, 32, 0, 4, 108, 2, 17, 66, 29, 3, 135, 0, 108, 2, 32, 0, 7, 6, 109, 0, 4, 3, 63, 0, 109, 2, 25, 0, 1, 17, 66, 3, 105, 131, 0, 2, 18, 68, 3, 131, 0, 7, 6, 110, 0, 4, 3, 50, 0, 110, 2, 25, 0, 110, 3, 50, 12, 0, 2, 103, 105, 3, 65, 0, 2, 103, 3, 66, 0, 103, 2, 32, 3, 66, 79, 0, 4, 110, 1, 105, 101, 3, 70, 50, 0, 110, 1, 117, 97, 0, 110, 1, 121, 101, 0, 110, 1, 161, 195, 0, 110, 1, 166, 195, 0, 110, 1, 169, 195, 0, 110, 1, 173, 195, 0, 110, 1, 179, 195, 0, 110, 1, 186, 195, 0, 110, 1, 189, 195, 0, 1, 17, 66, 3, 105, 132, 0, 2, 18, 68, 3, 132, 0, 107, 2, 105, 3, 133, 77, 0, 2, 107, 3, 134, 0, 103, 116, 2, 25, 3, 134, 70, 0, 1, 17, 65, 2, 107, 3, 134, 105, 0, 7, 6, 111, 0, 2, 17, 67, 17, 67, 3, 112, 0, 4, 3, 113, 0, 2, 17, 69, 17, 68, 0, 4, 2, 110, 103, 3, 125, 0, 2, 110, 107, 0, 4, 2, 103, 105, 3, 129, 0, 2, 103, 106, 0, 7, 6, 112, 0, 8, 3, 48, 0, 3, 69, 0, 4, 2, 107, 3, 81, 0, 2, 115, 0, 2, 116, 0, 112, 3, 105, 69, 0, 7, 6, 113, 0, 3, 49, 82, 0, 7, 6, 114, 0, 1, 17, 67, 3, 14, 51, 0, 1, 17, 65, 2, 17, 65, 3, 16, 51, 0, 2, 32, 3, 23, 51, 0, 4, 3, 23, 52, 0, 8, 0, 2, 18, 67, 3, 34, 136, 0, 114, 3, 51, 16, 51, 0, 110, 3, 51, 70, 132, 0, 108, 2, 17, 66, 3, 51, 135, 0, 1, 108, 3, 67, 51, 0, 108, 3, 70, 55, 0, 7, 6, 115, 0, 3, 87, 0, 115, 3, 87, 137, 0, 4, 104, 2, 32, 3, 89, 0, 104, 8, 0, 7, 6, 116, 0, 8, 3, 47, 0, 3, 70, 0, 4, 104, 2, 32, 3, 85, 0, 104, 8, 0, 4, 2, 108, 3, 105, 70, 0, 2, 110, 0, 116, 0, 7, 6, 117, 0, 4, 1, 25, 2, 110, 103, 3, 40, 0, 1, 25, 2, 110, 107, 0, 1, 21, 2, 110, 117, 109, 32, 3, 112, 0, 2, 17, 67, 17, 67, 3, 115, 0, 4, 3, 116, 0, 2, 17, 69, 17, 68, 0, 4, 2, 103, 105, 3, 130, 0, 2, 103, 106, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 82, 0, 7, 6, 120, 0, 4, 3, 49, 87, 0, 122, 0, 7, 6, 121, 0, 4, 1, 25, 2, 110, 103, 3, 37, 0, 1, 25, 2, 110, 107, 0, 2, 17, 67, 17, 67, 3, 107, 0, 4, 3, 108, 0, 2, 17, 69, 17, 68, 0, 7, 6, 122, 0, 122, 3, 47, 87, 0, 3, 86, 0, 7, 6, 0, 36, 3, 70, 112, 55, 55, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts27 = FileInMemory_createWithData (5468, reinterpret_cast (&espeakdata_dicts27_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/is_dict", L"is"); Collection_addItem (me.peek(), espeakdata_dicts27.transfer()); static unsigned char espeakdata_dicts28_data[43393] = { 0, 4, 0, 0, 251, 159, 0, 0, 0, 9, 198, 5, 97, 86, 4, 227, 192, 72, 17, 70, 88, 16, 213, 60, 195, 192, 82, 35, 49, 6, 40, 108, 55, 39, 0, 0, 10, 199, 56, 80, 210, 60, 195, 199, 36, 20, 0, 6, 195, 52, 83, 128, 21, 0, 6, 195, 60, 35, 9, 66, 0, 7, 65, 4, 35, 12, 0, 14, 4, 193, 4, 72, 9, 197, 64, 244, 144, 61, 32, 65, 21, 9, 198, 8, 192, 83, 24, 83, 64, 20, 0, 9, 198, 80, 144, 149, 72, 243, 128, 67, 10, 198, 80, 83, 5, 28, 243, 128, 66, 20, 9, 198, 76, 147, 131, 72, 243, 128, 65, 9, 198, 5, 48, 193, 48, 17, 128, 66, 9, 198, 4, 229, 9, 24, 243, 128, 66, 0, 10, 199, 88, 243, 20, 4, 209, 84, 72, 66, 10, 199, 80, 84, 1, 56, 80, 200, 36, 20, 10, 199, 64, 192, 78, 36, 209, 84, 72, 66, 10, 199, 64, 83, 148, 4, 209, 84, 72, 66, 9, 198, 60, 211, 212, 80, 84, 137, 20, 10, 199, 52, 147, 12, 36, 209, 84, 72, 66, 6, 195, 48, 240, 128, 20, 9, 198, 37, 51, 212, 80, 84, 137, 20, 9, 198, 29, 32, 84, 80, 84, 137, 66, 10, 199, 12, 83, 148, 36, 209, 84, 72, 66, 0, 9, 198, 76, 245, 20, 61, 163, 206, 20, 7, 196, 72, 144, 133, 12, 20, 12, 200, 64, 84, 143, 56, 244, 208, 61, 32, 67, 20, 0, 6, 65, 8, 69, 37, 0, 13, 202, 16, 144, 201, 4, 227, 143, 88, 84, 201, 52, 20, 9, 197, 12, 243, 147, 60, 224, 65, 20, 8, 197, 12, 148, 205, 60, 224, 66, 9, 197, 12, 83, 148, 36, 224, 65, 20, 8, 197, 12, 20, 140, 36, 224, 66, 0, 9, 198, 72, 144, 207, 88, 84, 128, 66, 0, 9, 198, 65, 35, 211, 12, 83, 137, 20, 11, 199, 64, 84, 147, 20, 99, 206, 20, 66, 20, 0, 9, 198, 76, 241, 199, 36, 244, 142, 21, 9, 198, 4, 197, 15, 24, 244, 142, 21, 0, 6, 65, 12, 74, 37, 0, 8, 197, 88, 86, 154, 20, 224, 65, 8, 197, 72, 83, 132, 36, 224, 65, 8, 197, 12, 244, 142, 20, 240, 65, 8, 197, 12, 243, 15, 72, 224, 21, 8, 197, 12, 149, 137, 48, 80, 66, 8, 197, 8, 244, 142, 20, 240, 65, 0, 9, 198, 88, 144, 68, 61, 69, 0, 21, 9, 198, 52, 17, 199, 36, 244, 128, 21, 9, 198, 48, 21, 20, 61, 50, 64, 20, 9, 198, 12, 20, 9, 56, 84, 128, 21, 0, 13, 4, 95, 8, 1, 3, 105, 6, 35, 74, 36, 49, 0, 6, 195, 80, 241, 128, 20, 10, 199, 24, 147, 1, 80, 83, 9, 4, 68, 10, 199, 16, 148, 204, 21, 52, 201, 4, 67, 0, 11, 200, 64, 20, 133, 77, 65, 83, 36, 80, 68, 7, 196, 48, 145, 86, 20, 20, 7, 196, 40, 84, 207, 48, 20, 11, 200, 20, 211, 196, 36, 19, 9, 76, 144, 67, 11, 200, 13, 84, 150, 36, 194, 78, 20, 240, 67, 0, 6, 65, 16, 70, 37, 0, 12, 201, 76, 19, 148, 4, 32, 82, 8, 20, 128, 67, 8, 197, 69, 80, 76, 61, 32, 21, 9, 197, 64, 84, 137, 21, 32, 65, 21, 6, 195, 52, 83, 142, 21, 8, 197, 21, 2, 82, 61, 64, 20, 8, 197, 16, 148, 133, 81, 64, 20, 0, 6, 195, 77, 3, 211, 20, 9, 198, 76, 244, 130, 37, 67, 204, 67, 0, 12, 201, 81, 84, 130, 61, 97, 78, 80, 243, 0, 20, 10, 198, 61, 69, 5, 56, 84, 133, 67, 21, 10, 199, 56, 244, 141, 4, 225, 9, 4, 67, 9, 198, 52, 148, 197, 72, 84, 133, 67, 0, 11, 200, 52, 243, 148, 20, 51, 211, 5, 32, 67, 0, 7, 65, 20, 36, 12, 0, 14, 5, 193, 20, 72, 8, 6, 195, 80, 243, 142, 21, 8, 197, 36, 194, 5, 85, 48, 21, 16, 69, 29, 80, 73, 56, 16, 79, 58, 35, 6, 37, 12, 50, 35, 0, 8, 197, 16, 145, 83, 37, 48, 20, 12, 201, 12, 19, 80, 60, 64, 82, 76, 81, 192, 67, 0, 6, 195, 21, 0, 64, 20, 9, 198, 64, 19, 12, 5, 99, 204, 67, 10, 198, 36, 225, 5, 8, 149, 0, 66, 21, 9, 198, 24, 147, 15, 76, 241, 128, 66, 9, 198, 21, 0, 82, 12, 130, 65, 67, 9, 198, 21, 0, 71, 56, 85, 76, 65, 9, 198, 20, 227, 129, 28, 243, 128, 66, 0, 6, 195, 100, 241, 0, 20, 10, 199, 81, 32, 84, 4, 194, 65, 76, 67, 10, 199, 52, 83, 132, 20, 193, 86, 36, 20, 10, 199, 52, 19, 77, 36, 97, 82, 36, 66, 10, 199, 48, 144, 193, 57, 68, 143, 64, 66, 6, 195, 25, 35, 196, 20, 0, 11, 67, 69, 82, 65, 49, 58, 6, 37, 35, 0, 11, 200, 12, 243, 143, 76, 49, 82, 48, 16, 66, 6, 195, 80, 243, 137, 20, 7, 196, 72, 145, 83, 36, 20, 0, 8, 65, 24, 36, 81, 81, 36, 0, 8, 197, 88, 243, 19, 12, 144, 20, 8, 197, 77, 1, 67, 36, 80, 20, 8, 197, 76, 83, 137, 48, 80, 66, 8, 197, 52, 84, 211, 36, 16, 66, 8, 197, 52, 84, 143, 64, 80, 65, 8, 197, 48, 241, 199, 36, 16, 20, 8, 197, 48, 147, 79, 56, 80, 20, 9, 197, 44, 20, 129, 80, 80, 67, 20, 8, 197, 24, 241, 199, 36, 16, 20, 8, 197, 21, 67, 201, 48, 80, 65, 8, 197, 5, 64, 76, 36, 16, 67, 8, 197, 4, 229, 15, 56, 144, 20, 0, 9, 198, 77, 84, 16, 61, 53, 0, 21, 9, 198, 52, 17, 206, 21, 50, 64, 20, 9, 198, 12, 20, 147, 60, 194, 64, 66, 9, 198, 4, 224, 76, 37, 50, 64, 66, 0, 10, 198, 88, 19, 19, 21, 50, 65, 66, 20, 10, 198, 52, 17, 206, 21, 50, 65, 66, 20, 10, 199, 36, 212, 5, 72, 97, 84, 80, 20, 9, 198, 16, 148, 212, 60, 226, 65, 67, 9, 198, 12, 83, 143, 52, 19, 137, 66, 6, 195, 9, 35, 196, 20, 9, 198, 4, 208, 90, 104, 243, 137, 66, 0, 7, 196, 64, 193, 83, 36, 20, 9, 198, 21, 81, 197, 56, 243, 0, 68, 11, 200, 12, 20, 15, 48, 149, 133, 72, 144, 67, 0, 6, 65, 28, 73, 37, 0, 8, 197, 52, 243, 129, 16, 80, 65, 8, 197, 24, 244, 16, 60, 192, 20, 8, 197, 24, 19, 5, 12, 144, 20, 8, 197, 20, 195, 1, 16, 80, 65, 9, 198, 4, 229, 9, 17, 35, 199, 20, 0, 13, 202, 77, 3, 1, 56, 51, 143, 64, 193, 85, 72, 67, 6, 195, 48, 243, 135, 20, 10, 198, 37, 51, 208, 80, 84, 128, 66, 20, 9, 198, 4, 224, 66, 5, 50, 64, 66, 0, 14, 203, 88, 147, 12, 5, 96, 76, 48, 83, 15, 56, 112, 20, 10, 199, 81, 33, 78, 80, 84, 201, 52, 20, 6, 195, 80, 243, 128, 20, 10, 199, 80, 83, 5, 12, 19, 69, 72, 67, 6, 195, 16, 243, 128, 21, 10, 199, 12, 21, 5, 12, 129, 83, 36, 20, 9, 198, 4, 208, 90, 104, 243, 133, 66, 0, 11, 200, 77, 84, 5, 73, 53, 9, 80, 80, 66, 11, 200, 52, 147, 12, 20, 99, 199, 48, 144, 20, 6, 195, 16, 243, 129, 66, 11, 200, 12, 243, 148, 72, 17, 82, 20, 240, 67, 0, 8, 65, 32, 35, 49, 12, 35, 0, 12, 201, 12, 20, 212, 72, 243, 9, 8, 84, 128, 67, 0, 9, 198, 64, 243, 9, 28, 243, 128, 66, 9, 198, 52, 16, 195, 32, 147, 128, 65, 9, 198, 5, 4, 137, 12, 83, 128, 21, 0, 6, 195, 80, 244, 132, 21, 6, 195, 48, 244, 132, 21, 0, 8, 196, 56, 83, 12, 4, 72, 28, 15, 1, 35, 49, 35, 50, 74, 36, 55, 55, 36, 47, 12, 39, 0, 7, 196, 64, 243, 12, 36, 20, 7, 196, 56, 81, 213, 76, 20, 6, 195, 52, 84, 137, 66, 7, 196, 48, 147, 12, 4, 66, 6, 195, 5, 67, 205, 65, 0, 6, 195, 5, 67, 206, 65, 7, 65, 36, 37, 12, 0, 14, 5, 193, 36, 72, 9, 8, 197, 88, 147, 131, 37, 64, 65, 8, 197, 76, 147, 12, 4, 32, 65, 6, 195, 64, 246, 154, 21, 6, 195, 5, 67, 206, 66, 0, 15, 1, 37, 48, 36, 14, 16, 74, 6, 36, 50, 47, 39, 0, 27, 9, 198, 81, 34, 71, 48, 145, 128, 65, 9, 198, 8, 20, 207, 16, 147, 128, 66, 9, 198, 5, 32, 207, 76, 83, 128, 21, 0, 6, 1, 38, 10, 36, 0, 10, 199, 80, 16, 200, 36, 209, 84, 72, 66, 9, 198, 76, 98, 78, 80, 84, 133, 66, 10, 199, 65, 35, 211, 36, 81, 213, 60, 20, 0, 6, 195, 80, 244, 129, 66, 7, 196, 64, 83, 142, 20, 21, 0, 8, 65, 40, 73, 36, 12, 57, 0, 6, 195, 80, 244, 130, 21, 9, 198, 64, 83, 1, 88, 84, 135, 21, 8, 197, 12, 148, 15, 48, 192, 21, 8, 197, 4, 212, 15, 48, 192, 21, 0, 9, 198, 76, 115, 205, 8, 84, 128, 65, 10, 198, 72, 240, 149, 72, 83, 148, 67, 20, 9, 198, 72, 147, 66, 61, 36, 192, 21, 9, 198, 64, 20, 1, 88, 84, 128, 66, 7, 195, 12, 148, 143, 66, 20, 0, 14, 1, 42, 35, 87, 47, 36, 51, 37, 87, 49, 39, 0, 27, 10, 199, 77, 68, 129, 64, 147, 205, 8, 21, 9, 198, 60, 224, 207, 28, 83, 133, 67, 9, 198, 16, 148, 208, 20, 225, 9, 20, 0, 8, 1, 43, 48, 57, 40, 0, 27, 7, 196, 80, 19, 9, 4, 66, 7, 196, 64, 243, 9, 4, 66, 7, 196, 52, 81, 9, 4, 20, 0, 8, 197, 36, 225, 15, 48, 240, 66, 9, 65, 44, 49, 35, 48, 12, 35, 0, 8, 197, 80, 84, 133, 9, 32, 65, 9, 197, 76, 193, 83, 36, 16, 65, 20, 8, 197, 48, 148, 212, 60, 224, 66, 8, 197, 21, 51, 206, 21, 32, 66, 8, 197, 8, 246, 154, 60, 192, 20, 0, 6, 195, 48, 244, 143, 72, 7, 195, 48, 244, 143, 76, 9, 9, 198, 16, 83, 9, 8, 84, 128, 66, 0, 10, 1, 46, 48, 40, 50, 47, 39, 0, 27, 10, 199, 69, 80, 78, 80, 243, 69, 56, 21, 9, 198, 60, 224, 207, 28, 83, 137, 67, 0, 9, 1, 47, 87, 55, 35, 89, 0, 27, 7, 196, 80, 83, 137, 4, 20, 7, 196, 76, 145, 80, 20, 20, 8, 196, 76, 83, 142, 60, 66, 20, 7, 196, 76, 16, 133, 36, 66, 11, 200, 64, 21, 15, 28, 83, 133, 76, 144, 67, 11, 200, 53, 85, 1, 28, 83, 133, 76, 144, 67, 7, 196, 52, 17, 137, 4, 65, 11, 200, 25, 32, 84, 21, 35, 137, 80, 16, 68, 11, 200, 21, 52, 15, 76, 147, 69, 81, 32, 67, 11, 200, 12, 20, 18, 36, 99, 199, 48, 144, 20, 0, 8, 65, 48, 107, 55, 55, 36, 0, 8, 197, 36, 228, 197, 81, 64, 20, 0, 9, 198, 64, 20, 129, 8, 244, 132, 21, 0, 6, 195, 69, 81, 76, 72, 10, 199, 88, 83, 131, 21, 51, 1, 60, 67, 10, 199, 12, 243, 80, 4, 115, 137, 4, 67, 0, 8, 196, 56, 83, 12, 20, 72, 28, 11, 200, 16, 244, 16, 36, 244, 5, 81, 64, 20, 7, 196, 5, 32, 66, 36, 65, 0, 8, 65, 52, 107, 63, 63, 36, 0, 8, 197, 12, 195, 196, 36, 16, 20, 0, 9, 198, 53, 85, 1, 28, 83, 128, 66, 12, 201, 24, 244, 129, 52, 147, 137, 24, 84, 137, 68, 9, 198, 16, 148, 25, 48, 243, 128, 65, 0, 10, 199, 72, 150, 154, 36, 51, 206, 36, 66, 6, 195, 52, 83, 148, 21, 6, 195, 52, 83, 148, 21, 0, 10, 67, 69, 81, 73, 49, 120, 36, 57, 0, 7, 196, 72, 243, 154, 36, 66, 7, 196, 72, 240, 130, 36, 20, 7, 196, 72, 16, 130, 36, 66, 7, 196, 64, 193, 85, 72, 65, 7, 196, 52, 84, 197, 72, 65, 7, 196, 36, 225, 84, 80, 20, 10, 198, 16, 80, 197, 8, 19, 0, 66, 20, 7, 196, 8, 240, 130, 36, 20, 0, 8, 197, 24, 16, 197, 88, 144, 76, 8, 65, 56, 107, 50, 50, 36, 0, 8, 197, 64, 83, 15, 64, 80, 65, 0, 9, 198, 28, 197, 67, 61, 50, 64, 20, 9, 198, 13, 33, 77, 37, 50, 64, 65, 0, 14, 1, 58, 70, 4, 40, 36, 48, 6, 40, 50, 47, 37, 0, 10, 199, 77, 81, 4, 36, 16, 207, 56, 66, 10, 199, 65, 33, 68, 36, 193, 84, 80, 20, 9, 198, 5, 49, 137, 77, 50, 65, 67, 0, 11, 200, 28, 147, 143, 28, 83, 133, 76, 144, 67, 9, 198, 20, 193, 77, 61, 50, 78, 67, 0, 7, 65, 60, 108, 12, 0, 14, 9, 198, 64, 84, 148, 4, 229, 15, 8, 5, 193, 60, 72, 8, 9, 198, 81, 32, 83, 12, 244, 147, 21, 8, 197, 76, 99, 199, 28, 144, 20, 8, 197, 76, 83, 5, 56, 144, 20, 8, 197, 64, 147, 1, 16, 80, 65, 8, 197, 52, 145, 15, 48, 192, 21, 8, 197, 52, 19, 132, 20, 144, 66, 8, 197, 36, 229, 18, 36, 112, 66, 8, 197, 25, 80, 201, 48, 80, 66, 8, 197, 16, 83, 5, 8, 144, 20, 8, 197, 12, 147, 133, 76, 144, 20, 0, 11, 1, 61, 40, 79, 58, 35, 55, 36, 0, 27, 6, 195, 61, 0, 67, 66, 9, 198, 52, 243, 143, 24, 244, 128, 66, 9, 198, 48, 243, 137, 12, 84, 128, 66, 9, 198, 16, 144, 83, 64, 244, 128, 66, 0, 9, 198, 81, 34, 67, 21, 50, 77, 20, 10, 199, 12, 83, 148, 72, 243, 69, 72, 66, 0, 9, 198, 72, 85, 9, 56, 243, 0, 67, 11, 200, 24, 149, 15, 12, 83, 143, 76, 144, 21, 9, 198, 12, 192, 85, 76, 243, 0, 65, 9, 198, 5, 3, 211, 81, 35, 198, 66, 7, 196, 4, 192, 133, 16, 20, 0, 13, 1, 64, 49, 37, 6, 39, 74, 12, 39, 55, 35, 0, 13, 1, 64, 49, 37, 6, 39, 74, 12, 39, 55, 35, 0, 6, 65, 64, 48, 37, 0, 0, 9, 198, 64, 81, 1, 88, 83, 128, 21, 10, 198, 61, 33, 193, 56, 243, 128, 65, 21, 9, 198, 52, 21, 1, 64, 19, 128, 67, 9, 198, 37, 51, 211, 64, 147, 128, 67, 0, 9, 198, 4, 210, 76, 12, 20, 133, 66, 0, 0, 6, 65, 68, 49, 40, 0, 9, 198, 72, 80, 201, 65, 35, 195, 66, 6, 195, 52, 86, 154, 20, 8, 197, 9, 32, 68, 37, 0, 65, 0, 0, 7, 195, 84, 224, 64, 72, 9, 6, 195, 60, 34, 84, 65, 0, 8, 196, 76, 83, 15, 56, 66, 20, 7, 196, 61, 48, 193, 72, 20, 7, 196, 12, 240, 129, 76, 20, 7, 196, 4, 192, 133, 72, 65, 0, 8, 65, 72, 107, 51, 16, 36, 0, 8, 197, 64, 84, 132, 60, 224, 21, 8, 197, 52, 19, 16, 20, 192, 21, 0, 9, 198, 88, 19, 19, 20, 48, 192, 21, 6, 195, 80, 240, 195, 21, 9, 198, 64, 244, 201, 48, 194, 80, 66, 9, 198, 4, 229, 5, 72, 244, 192, 65, 0, 9, 198, 77, 1, 67, 84, 197, 77, 65, 10, 199, 76, 84, 150, 60, 100, 133, 56, 21, 10, 199, 72, 240, 195, 5, 49, 67, 12, 21, 10, 199, 52, 243, 143, 4, 192, 133, 72, 67, 10, 199, 24, 197, 77, 20, 225, 15, 76, 20, 0, 7, 196, 4, 32, 137, 4, 76, 12, 200, 80, 83, 5, 56, 49, 70, 4, 192, 67, 20, 7, 196, 76, 19, 13, 36, 66, 12, 200, 52, 84, 197, 56, 49, 70, 4, 192, 67, 20, 6, 195, 16, 241, 197, 20, 0, 8, 65, 76, 36, 87, 87, 36, 0, 9, 198, 77, 64, 77, 8, 80, 195, 21, 12, 201, 65, 35, 208, 20, 65, 85, 80, 144, 192, 67, 8, 197, 52, 20, 141, 61, 32, 65, 8, 197, 28, 85, 20, 37, 64, 65, 6, 195, 20, 97, 66, 20, 8, 197, 12, 83, 66, 4, 192, 65, 8, 197, 12, 19, 129, 4, 224, 65, 8, 197, 12, 19, 9, 9, 32, 65, 8, 197, 8, 21, 20, 37, 64, 65, 8, 197, 8, 20, 130, 21, 32, 65, 0, 8, 197, 77, 0, 84, 60, 192, 65, 8, 197, 77, 0, 76, 5, 64, 65, 9, 198, 77, 0, 71, 56, 243, 0, 66, 12, 201, 77, 0, 67, 12, 19, 129, 64, 243, 9, 67, 11, 200, 77, 0, 67, 12, 17, 143, 72, 224, 21, 9, 198, 65, 33, 70, 21, 69, 0, 20, 9, 198, 64, 147, 194, 8, 144, 192, 21, 7, 195, 20, 225, 71, 65, 20, 10, 198, 16, 145, 1, 12, 129, 64, 67, 20, 9, 198, 12, 83, 12, 60, 193, 64, 21, 9, 198, 4, 147, 15, 12, 129, 64, 20, 0, 6, 195, 80, 241, 192, 20, 6, 195, 48, 241, 192, 20, 6, 195, 36, 211, 204, 65, 10, 199, 12, 19, 80, 4, 115, 143, 48, 67, 0, 11, 200, 64, 84, 141, 4, 100, 143, 77, 64, 65, 7, 196, 61, 32, 201, 4, 21, 7, 196, 21, 100, 143, 76, 20, 7, 196, 12, 241, 15, 48, 21, 0, 6, 65, 80, 47, 37, 0, 10, 198, 80, 84, 143, 48, 65, 71, 66, 20, 8, 197, 80, 20, 148, 5, 32, 65, 8, 197, 77, 81, 5, 77, 64, 66, 6, 195, 76, 147, 206, 66, 8, 197, 72, 148, 15, 77, 64, 21, 8, 197, 65, 35, 212, 37, 32, 65, 8, 197, 64, 84, 146, 21, 32, 66, 9, 198, 52, 86, 154, 4, 225, 71, 66, 8, 197, 36, 229, 5, 29, 32, 65, 8, 197, 21, 100, 133, 85, 128, 65, 8, 197, 16, 84, 15, 77, 64, 21, 8, 197, 12, 244, 146, 21, 32, 66, 8, 197, 8, 148, 15, 77, 64, 21, 0, 9, 198, 81, 34, 80, 60, 65, 64, 65, 10, 198, 28, 147, 214, 4, 225, 64, 65, 21, 9, 198, 12, 243, 134, 36, 225, 64, 66, 9, 198, 12, 131, 210, 104, 245, 192, 66, 13, 202, 12, 130, 85, 76, 21, 133, 12, 50, 9, 4, 20, 13, 202, 8, 19, 14, 20, 245, 5, 72, 20, 9, 4, 70, 0, 6, 195, 76, 147, 192, 66, 10, 199, 76, 147, 131, 72, 243, 137, 4, 67, 9, 198, 64, 84, 195, 32, 144, 201, 20, 10, 199, 64, 19, 1, 28, 243, 137, 4, 68, 9, 198, 52, 240, 207, 56, 84, 201, 66, 6, 195, 21, 83, 128, 65, 9, 198, 20, 211, 211, 80, 20, 201, 66, 10, 199, 12, 147, 195, 36, 20, 137, 4, 67, 10, 199, 4, 225, 137, 28, 243, 137, 4, 68, 6, 195, 4, 224, 80, 65, 0, 7, 195, 76, 18, 197, 66, 20, 7, 196, 64, 83, 12, 20, 21, 0, 9, 197, 80, 83, 133, 72, 80, 66, 21, 12, 201, 28, 83, 133, 72, 22, 137, 60, 225, 64, 20, 8, 197, 12, 20, 1, 12, 80, 66, 12, 201, 5, 48, 204, 21, 2, 79, 16, 245, 0, 68, 0, 9, 198, 77, 1, 67, 12, 130, 64, 20, 9, 198, 65, 35, 211, 80, 21, 0, 65, 9, 198, 21, 32, 129, 12, 83, 192, 66, 9, 198, 5, 3, 211, 80, 21, 0, 66, 0, 9, 198, 77, 1, 67, 12, 130, 65, 20, 6, 195, 20, 226, 64, 66, 9, 198, 12, 19, 66, 60, 66, 65, 20, 0, 11, 200, 80, 85, 18, 5, 32, 200, 36, 16, 67, 7, 196, 76, 19, 148, 20, 66, 7, 196, 72, 80, 130, 36, 21, 11, 200, 65, 35, 195, 60, 228, 207, 48, 80, 20, 7, 196, 56, 83, 142, 36, 20, 9, 198, 20, 211, 212, 36, 51, 206, 66, 7, 195, 12, 147, 197, 66, 20, 0, 6, 65, 88, 82, 40, 0, 8, 197, 72, 149, 15, 12, 48, 21, 8, 197, 72, 85, 133, 72, 80, 21, 8, 197, 36, 225, 68, 36, 16, 20, 8, 197, 28, 16, 129, 48, 144, 65, 8, 197, 13, 84, 131, 84, 208, 65, 8, 197, 5, 4, 137, 48, 80, 66, 0, 6, 195, 80, 244, 147, 21, 12, 201, 76, 50, 9, 104, 241, 146, 20, 226, 65, 68, 9, 198, 52, 243, 15, 12, 130, 64, 20, 9, 198, 29, 32, 68, 60, 194, 64, 65, 9, 198, 12, 19, 142, 60, 34, 64, 20, 0, 9, 198, 81, 32, 71, 20, 66, 65, 20, 0, 8, 196, 56, 83, 12, 60, 72, 28, 17, 4, 95, 49, 77, 52, 40, 50, 69, 37, 55, 37, 6, 39, 50, 36, 0, 11, 200, 28, 192, 85, 12, 241, 129, 56, 80, 67, 11, 200, 12, 244, 142, 84, 51, 208, 36, 16, 20, 11, 200, 12, 244, 18, 60, 192, 76, 36, 16, 68, 7, 196, 12, 16, 129, 48, 65, 7, 196, 4, 208, 137, 80, 65, 0, 12, 1, 92, 69, 35, 49, 87, 55, 35, 89, 0, 27, 14, 65, 92, 70, 6, 39, 48, 12, 57, 35, 82, 6, 40, 0, 6, 195, 80, 244, 142, 21, 8, 197, 80, 130, 69, 76, 144, 20, 8, 197, 76, 148, 212, 20, 208, 20, 8, 197, 56, 243, 65, 16, 80, 65, 8, 197, 48, 243, 135, 32, 144, 20, 8, 197, 12, 20, 211, 60, 192, 66, 8, 197, 5, 69, 15, 72, 224, 21, 0, 9, 198, 76, 243, 15, 64, 16, 192, 67, 9, 198, 57, 83, 129, 80, 18, 192, 67, 9, 198, 56, 83, 199, 72, 80, 192, 20, 6, 195, 28, 147, 199, 21, 7, 195, 20, 97, 83, 65, 20, 0, 0, 7, 196, 64, 243, 148, 60, 20, 11, 200, 65, 35, 194, 61, 48, 201, 16, 80, 20, 0, 13, 4, 95, 49, 77, 49, 63, 6, 37, 55, 55, 36, 0, 8, 65, 96, 6, 37, 49, 87, 0, 8, 197, 28, 243, 142, 21, 48, 20, 8, 197, 20, 226, 201, 17, 80, 20, 6, 195, 16, 246, 154, 21, 9, 198, 4, 113, 83, 36, 192, 79, 68, 0, 6, 194, 4, 64, 72, 28, 17, 4, 95, 49, 77, 50, 40, 50, 63, 37, 55, 37, 6, 39, 50, 36, 0, 9, 198, 21, 81, 193, 56, 83, 192, 67, 0, 18, 4, 95, 49, 77, 51, 40, 50, 63, 37, 55, 37, 6, 35, 51, 70, 39, 0, 10, 199, 36, 224, 207, 53, 3, 5, 80, 20, 6, 195, 36, 98, 84, 65, 9, 198, 12, 130, 67, 32, 144, 137, 67, 9, 198, 12, 128, 77, 8, 84, 153, 21, 9, 198, 12, 21, 1, 48, 148, 201, 66, 0, 7, 196, 104, 81, 137, 72, 65, 7, 196, 80, 243, 22, 20, 20, 7, 196, 73, 83, 212, 36, 20, 7, 196, 64, 243, 9, 76, 21, 7, 195, 60, 20, 201, 65, 20, 7, 196, 48, 144, 133, 72, 65, 7, 196, 48, 144, 133, 72, 65, 7, 196, 48, 16, 129, 72, 65, 6, 195, 16, 244, 197, 20, 9, 198, 9, 32, 71, 4, 66, 78, 67, 9, 198, 8, 20, 130, 4, 225, 82, 21, 0, 12, 65, 100, 6, 37, 48, 87, 37, 55, 39, 50, 0, 7, 195, 4, 211, 210, 66, 21, 0, 9, 198, 52, 20, 129, 52, 19, 192, 67, 0, 10, 199, 64, 147, 142, 37, 1, 68, 36, 66, 9, 198, 64, 20, 129, 85, 37, 9, 67, 9, 198, 36, 225, 133, 48, 144, 197, 67, 9, 198, 24, 245, 15, 48, 148, 201, 66, 11, 199, 5, 48, 197, 57, 50, 79, 56, 68, 21, 6, 195, 4, 226, 84, 65, 0, 7, 196, 80, 19, 15, 72, 21, 7, 196, 65, 35, 214, 20, 20, 8, 196, 12, 17, 134, 20, 66, 20, 0, 10, 65, 104, 70, 86, 36, 12, 47, 35, 0, 8, 197, 24, 244, 131, 60, 192, 21, 8, 197, 12, 244, 146, 20, 64, 20, 12, 201, 12, 243, 134, 72, 21, 5, 72, 226, 84, 67, 8, 197, 12, 241, 207, 72, 224, 21, 8, 197, 12, 84, 131, 60, 192, 21, 8, 197, 5, 32, 71, 60, 224, 67, 8, 197, 4, 48, 197, 56, 224, 21, 0, 9, 198, 4, 211, 210, 28, 244, 192, 67, 0, 6, 195, 64, 244, 192, 20, 10, 199, 57, 84, 129, 52, 147, 137, 76, 66, 10, 199, 52, 19, 143, 16, 244, 5, 72, 67, 0, 7, 196, 21, 32, 78, 60, 72, 12, 201, 52, 81, 9, 80, 84, 146, 4, 225, 79, 68, 7, 196, 13, 80, 195, 84, 66, 15, 204, 5, 32, 201, 12, 243, 134, 72, 21, 5, 72, 226, 84, 69, 0, 8, 197, 92, 21, 20, 61, 32, 21, 8, 197, 88, 83, 132, 37, 64, 65, 8, 197, 80, 19, 77, 5, 32, 65, 9, 198, 76, 20, 131, 60, 96, 71, 66, 6, 195, 28, 147, 214, 21, 8, 197, 24, 84, 142, 21, 64, 66, 12, 201, 20, 194, 79, 12, 83, 148, 72, 144, 192, 20, 0, 9, 198, 48, 84, 85, 36, 193, 64, 20, 9, 198, 13, 84, 212, 60, 65, 64, 20, 9, 198, 12, 244, 146, 21, 69, 0, 20, 9, 198, 4, 225, 77, 60, 225, 64, 20, 9, 198, 4, 65, 76, 36, 225, 64, 21, 0, 10, 199, 81, 84, 130, 60, 113, 84, 80, 20, 9, 198, 81, 33, 83, 21, 69, 5, 20, 10, 199, 80, 240, 207, 24, 84, 143, 48, 68, 10, 199, 52, 84, 131, 4, 230, 137, 4, 67, 10, 199, 36, 229, 5, 72, 209, 90, 104, 20, 10, 199, 28, 84, 129, 72, 50, 9, 4, 67, 10, 199, 24, 83, 143, 12, 244, 9, 4, 20, 10, 199, 21, 51, 212, 72, 244, 9, 4, 68, 10, 199, 21, 2, 76, 21, 52, 201, 4, 68, 12, 201, 20, 225, 5, 12, 20, 201, 48, 192, 66, 68, 10, 199, 12, 20, 15, 12, 50, 9, 4, 20, 9, 198, 5, 69, 9, 88, 149, 1, 68, 10, 199, 5, 64, 82, 5, 52, 201, 4, 68, 0, 7, 196, 64, 243, 9, 64, 65, 7, 196, 64, 147, 15, 80, 20, 7, 196, 64, 83, 15, 80, 20, 0, 9, 198, 52, 145, 206, 4, 225, 71, 66, 12, 201, 52, 20, 131, 36, 20, 9, 20, 65, 64, 20, 8, 197, 36, 225, 68, 37, 64, 66, 8, 197, 12, 19, 80, 61, 32, 65, 0, 9, 198, 80, 84, 211, 36, 193, 64, 20, 9, 198, 80, 83, 198, 4, 225, 64, 66, 9, 198, 76, 84, 211, 36, 193, 64, 20, 9, 198, 28, 147, 214, 36, 225, 64, 21, 0, 10, 198, 65, 35, 199, 56, 244, 201, 65, 20, 10, 199, 8, 244, 135, 61, 35, 211, 20, 20, 9, 198, 4, 224, 67, 48, 20, 201, 66, 6, 195, 4, 81, 0, 20, 0, 7, 196, 77, 65, 67, 12, 21, 7, 196, 61, 33, 193, 56, 65, 7, 196, 21, 33, 68, 20, 20, 10, 198, 5, 53, 78, 12, 147, 206, 67, 21, 0, 9, 197, 88, 243, 5, 72, 80, 66, 21, 8, 197, 88, 84, 129, 12, 80, 66, 8, 197, 48, 21, 82, 20, 16, 65, 8, 197, 12, 244, 205, 36, 48, 20, 8, 197, 12, 244, 143, 56, 80, 20, 0, 9, 198, 81, 34, 80, 60, 194, 64, 65, 12, 201, 65, 50, 67, 61, 50, 78, 80, 84, 201, 67, 12, 201, 65, 50, 67, 60, 19, 129, 48, 148, 201, 68, 9, 198, 65, 33, 71, 4, 66, 64, 67, 9, 198, 64, 192, 84, 4, 226, 64, 65, 9, 198, 64, 81, 1, 28, 241, 192, 20, 0, 10, 199, 80, 83, 5, 88, 145, 5, 60, 67, 9, 198, 64, 192, 84, 4, 226, 65, 67, 9, 198, 52, 16, 195, 4, 33, 73, 67, 10, 199, 29, 80, 82, 16, 20, 143, 8, 20, 9, 198, 13, 84, 212, 60, 66, 65, 20, 9, 198, 12, 243, 77, 20, 66, 65, 20, 10, 199, 8, 144, 140, 36, 245, 5, 12, 20, 9, 198, 4, 227, 205, 4, 194, 65, 68, 6, 195, 4, 85, 0, 20, 0, 7, 196, 72, 147, 150, 36, 66, 11, 200, 64, 19, 147, 64, 84, 141, 36, 16, 67, 7, 196, 25, 33, 68, 16, 21, 11, 200, 21, 35, 212, 60, 208, 78, 36, 16, 69, 8, 196, 5, 32, 200, 20, 66, 20, 0, 9, 197, 76, 81, 5, 72, 80, 66, 21, 8, 197, 76, 80, 143, 72, 112, 21, 12, 201, 65, 32, 84, 61, 97, 67, 12, 130, 64, 20, 9, 197, 64, 245, 5, 72, 80, 66, 21, 9, 197, 64, 241, 5, 72, 80, 66, 21, 8, 197, 60, 32, 140, 36, 112, 20, 8, 197, 57, 80, 204, 20, 240, 65, 23, 73, 28, 84, 143, 28, 194, 70, 36, 51, 192, 73, 107, 51, 39, 61, 6, 37, 81, 37, 49, 39, 0, 8, 197, 21, 84, 143, 64, 144, 20, 8, 197, 20, 225, 193, 28, 80, 67, 12, 201, 12, 243, 12, 21, 97, 67, 12, 130, 64, 20, 0, 9, 198, 81, 34, 69, 56, 226, 64, 20, 9, 198, 76, 48, 80, 60, 194, 64, 65, 9, 198, 29, 80, 82, 4, 226, 64, 67, 9, 198, 20, 227, 133, 4, 66, 64, 66, 12, 201, 4, 229, 18, 61, 3, 211, 60, 98, 65, 69, 0, 9, 198, 80, 84, 148, 20, 226, 65, 67, 9, 198, 80, 83, 211, 60, 98, 65, 68, 6, 195, 52, 84, 192, 20, 9, 198, 36, 228, 207, 56, 226, 65, 20, 9, 198, 28, 20, 132, 20, 226, 65, 20, 0, 7, 196, 76, 16, 129, 80, 65, 7, 196, 65, 33, 67, 36, 20, 7, 196, 52, 243, 137, 80, 65, 7, 196, 52, 241, 5, 52, 20, 7, 196, 28, 80, 133, 48, 20, 0, 8, 197, 56, 80, 212, 60, 224, 20, 0, 6, 195, 60, 33, 83, 20, 13, 202, 12, 20, 212, 20, 197, 5, 72, 210, 78, 36, 67, 9, 198, 8, 148, 212, 20, 48, 192, 21, 0, 9, 1, 126, 47, 37, 55, 70, 36, 0, 6, 195, 80, 129, 84, 20, 0, 7, 196, 80, 83, 149, 20, 20, 11, 200, 64, 83, 15, 64, 243, 142, 21, 48, 20, 7, 196, 5, 144, 77, 20, 67, 0, 15, 204, 8, 21, 18, 4, 51, 205, 36, 243, 65, 12, 130, 65, 71, 0, 9, 198, 76, 145, 5, 72, 83, 192, 66, 9, 198, 56, 144, 207, 48, 19, 192, 67, 9, 198, 4, 192, 137, 72, 83, 192, 66, 0, 10, 199, 76, 16, 195, 5, 35, 211, 36, 20, 10, 199, 28, 19, 1, 81, 67, 211, 36, 20, 9, 198, 4, 224, 77, 56, 84, 201, 66, 0, 7, 196, 61, 69, 9, 12, 20, 9, 198, 8, 244, 195, 60, 225, 82, 21, 0, 8, 197, 81, 34, 79, 56, 96, 21, 0, 9, 198, 49, 80, 201, 25, 81, 192, 66, 29, 74, 12, 244, 148, 60, 50, 82, 13, 82, 84, 60, 49, 108, 14, 16, 47, 39, 74, 37, 14, 16, 49, 6, 40, 37, 47, 39, 0, 9, 198, 8, 16, 195, 5, 32, 64, 67, 0, 10, 199, 16, 80, 193, 52, 84, 143, 56, 66, 0, 7, 196, 88, 83, 148, 36, 21, 7, 196, 80, 241, 1, 72, 65, 7, 196, 77, 67, 210, 52, 21, 7, 196, 24, 241, 5, 72, 65, 7, 196, 4, 225, 143, 72, 65, 0, 8, 197, 84, 226, 83, 60, 224, 66, 6, 195, 61, 32, 70, 65, 8, 197, 52, 20, 131, 60, 224, 66, 0, 9, 198, 24, 147, 15, 9, 84, 192, 65, 9, 198, 16, 144, 129, 81, 66, 84, 66, 0, 10, 199, 77, 84, 5, 72, 99, 21, 60, 66, 6, 195, 69, 83, 212, 20, 10, 199, 65, 83, 148, 5, 49, 67, 12, 21, 9, 198, 56, 245, 133, 52, 36, 133, 20, 6, 195, 21, 97, 64, 20, 6, 195, 13, 33, 68, 20, 10, 199, 5, 33, 207, 77, 67, 204, 36, 67, 10, 199, 4, 48, 201, 64, 149, 5, 72, 66, 0, 7, 196, 88, 243, 20, 60, 21, 7, 196, 77, 67, 210, 56, 21, 11, 200, 8, 21, 20, 36, 32, 76, 20, 224, 21, 7, 196, 8, 17, 9, 4, 66, 0, 8, 197, 81, 85, 20, 61, 32, 21, 6, 195, 52, 243, 22, 20, 8, 197, 16, 19, 13, 5, 64, 65, 8, 197, 12, 243, 15, 56, 224, 21, 8, 197, 12, 19, 134, 61, 32, 65, 0, 10, 198, 65, 35, 212, 21, 84, 192, 65, 20, 12, 201, 48, 84, 15, 77, 3, 206, 16, 147, 9, 20, 9, 198, 33, 80, 72, 36, 225, 64, 67, 6, 195, 29, 33, 67, 20, 12, 201, 12, 147, 145, 84, 19, 148, 20, 227, 137, 20, 9, 198, 12, 20, 131, 5, 33, 64, 65, 0, 10, 199, 64, 20, 135, 32, 83, 9, 4, 67, 10, 199, 52, 144, 210, 60, 51, 211, 52, 20, 9, 198, 24, 83, 9, 12, 149, 1, 68, 10, 199, 8, 20, 137, 12, 83, 148, 72, 20, 0, 7, 196, 96, 83, 137, 4, 67, 11, 200, 81, 33, 68, 36, 49, 83, 36, 208, 20, 7, 196, 76, 243, 137, 4, 66, 7, 196, 61, 53, 9, 4, 65, 7, 196, 4, 33, 9, 4, 66, 0, 17, 70, 24, 18, 67, 12, 130, 79, 81, 35, 6, 37, 49, 12, 37, 39, 0, 9, 198, 20, 209, 82, 61, 65, 67, 20, 8, 197, 4, 197, 1, 37, 32, 66, 0, 9, 198, 4, 32, 137, 5, 65, 64, 76, 7, 194, 16, 16, 72, 9, 28, 9, 198, 81, 32, 77, 37, 65, 64, 65, 9, 198, 76, 244, 135, 21, 33, 64, 21, 9, 198, 52, 84, 211, 21, 33, 64, 66, 9, 198, 48, 81, 199, 21, 33, 64, 20, 9, 198, 8, 84, 135, 21, 33, 64, 66, 0, 9, 198, 88, 83, 15, 12, 149, 1, 68, 10, 199, 77, 68, 133, 81, 67, 201, 4, 21, 10, 199, 24, 245, 15, 28, 83, 137, 4, 68, 10, 199, 20, 194, 79, 24, 19, 137, 4, 69, 14, 203, 16, 144, 201, 5, 52, 197, 81, 65, 83, 36, 208, 20, 0, 10, 67, 20, 115, 9, 36, 61, 37, 0, 76, 11, 200, 88, 84, 143, 48, 19, 149, 61, 96, 20, 7, 196, 61, 37, 9, 12, 66, 7, 196, 44, 81, 137, 72, 20, 8, 196, 16, 80, 143, 72, 65, 20, 7, 196, 12, 241, 129, 56, 65, 11, 200, 12, 21, 5, 56, 19, 149, 61, 96, 20, 7, 196, 5, 33, 193, 56, 65, 0, 6, 195, 16, 19, 0, 72, 9, 197, 48, 84, 15, 72, 80, 65, 20, 9, 197, 24, 83, 79, 72, 80, 65, 20, 8, 197, 16, 241, 9, 12, 144, 21, 8, 197, 12, 83, 143, 8, 144, 20, 8, 197, 8, 244, 206, 36, 16, 20, 8, 197, 8, 19, 129, 72, 144, 65, 6, 195, 5, 97, 78, 21, 0, 11, 198, 12, 243, 12, 60, 66, 64, 66, 20, 9, 9, 198, 76, 148, 148, 61, 34, 64, 65, 12, 201, 69, 80, 84, 81, 35, 210, 84, 245, 5, 20, 9, 198, 24, 244, 195, 5, 34, 64, 65, 9, 198, 16, 84, 15, 76, 149, 0, 66, 9, 198, 12, 243, 12, 60, 66, 64, 20, 9, 198, 12, 19, 69, 17, 34, 64, 20, 10, 198, 4, 225, 68, 16, 245, 0, 66, 20, 0, 9, 198, 80, 83, 199, 60, 226, 65, 68, 10, 199, 72, 147, 80, 72, 245, 133, 72, 66, 10, 199, 52, 144, 210, 60, 98, 76, 52, 67, 10, 199, 28, 149, 76, 36, 19, 143, 88, 20, 11, 199, 28, 85, 19, 20, 208, 78, 36, 66, 20, 9, 198, 28, 83, 65, 81, 34, 65, 67, 10, 199, 12, 147, 143, 64, 149, 5, 12, 20, 6, 195, 8, 85, 0, 20, 9, 198, 8, 80, 195, 5, 34, 65, 67, 10, 199, 5, 64, 82, 28, 21, 9, 76, 66, 0, 7, 196, 88, 81, 15, 88, 65, 8, 196, 76, 81, 1, 56, 65, 20, 11, 200, 64, 244, 148, 4, 99, 199, 48, 144, 20, 6, 195, 61, 162, 65, 66, 7, 196, 56, 17, 9, 72, 66, 7, 196, 37, 81, 197, 72, 65, 0, 8, 197, 24, 16, 197, 88, 240, 76, 8, 197, 20, 32, 133, 72, 240, 72, 8, 197, 4, 192, 193, 48, 144, 65, 0, 10, 198, 76, 83, 142, 61, 34, 64, 65, 20, 9, 198, 64, 20, 129, 8, 149, 0, 66, 9, 198, 13, 33, 83, 12, 149, 0, 65, 9, 198, 12, 20, 131, 21, 34, 64, 65, 0, 9, 198, 81, 84, 135, 61, 98, 65, 20, 9, 198, 52, 244, 195, 61, 98, 65, 20, 9, 198, 52, 17, 83, 81, 34, 65, 67, 9, 198, 21, 131, 198, 61, 34, 65, 68, 9, 198, 20, 66, 84, 61, 34, 65, 68, 6, 195, 13, 33, 84, 20, 0, 7, 196, 65, 33, 71, 36, 20, 6, 195, 52, 243, 5, 20, 11, 200, 36, 51, 206, 61, 53, 1, 76, 144, 67, 9, 198, 8, 243, 142, 4, 224, 82, 66, 9, 198, 4, 210, 71, 16, 19, 0, 66, 0, 12, 201, 81, 34, 78, 37, 64, 80, 60, 194, 64, 67, 8, 197, 72, 147, 69, 16, 144, 20, 6, 195, 24, 81, 18, 20, 8, 197, 24, 19, 69, 16, 144, 20, 12, 201, 12, 20, 212, 20, 196, 197, 65, 34, 64, 20, 0, 13, 201, 81, 33, 66, 5, 49, 76, 20, 114, 5, 67, 21, 9, 198, 81, 32, 78, 76, 85, 20, 20, 6, 195, 29, 33, 83, 20, 0, 6, 195, 64, 244, 212, 21, 11, 199, 16, 145, 78, 12, 81, 129, 48, 66, 20, 6, 195, 13, 33, 80, 20, 0, 12, 201, 76, 245, 20, 60, 53, 84, 4, 225, 79, 68, 7, 196, 76, 50, 5, 16, 20, 7, 196, 5, 48, 197, 80, 20, 0, 0, 26, 73, 72, 240, 195, 5, 32, 73, 56, 243, 1, 14, 16, 39, 49, 12, 35, 51, 35, 6, 37, 50, 108, 55, 35, 0, 9, 198, 65, 35, 211, 64, 85, 20, 20, 9, 198, 65, 33, 80, 61, 53, 0, 21, 6, 195, 13, 33, 83, 20, 0, 9, 198, 104, 19, 132, 60, 32, 137, 20, 0, 7, 196, 88, 145, 5, 60, 65, 7, 196, 81, 34, 65, 12, 65, 7, 196, 77, 67, 208, 64, 21, 7, 196, 52, 148, 212, 4, 66, 9, 198, 52, 147, 137, 28, 243, 6, 67, 7, 196, 5, 33, 78, 20, 21, 0, 12, 201, 76, 19, 22, 4, 51, 206, 16, 245, 20, 21, 24, 73, 5, 85, 15, 88, 82, 67, 60, 195, 192, 35, 40, 47, 39, 82, 107, 6, 37, 49, 39, 55, 39, 0, 0, 9, 198, 64, 243, 9, 20, 68, 128, 20, 9, 198, 16, 144, 77, 21, 68, 128, 66, 0, 10, 199, 76, 83, 69, 77, 65, 78, 20, 66, 9, 198, 36, 224, 207, 57, 48, 201, 20, 0, 7, 195, 4, 115, 9, 72, 9, 7, 196, 12, 243, 15, 8, 65, 0, 8, 197, 88, 145, 206, 60, 192, 66, 8, 197, 24, 83, 19, 36, 224, 65, 9, 197, 9, 33, 71, 4, 224, 65, 20, 0, 0, 10, 199, 65, 33, 83, 8, 149, 5, 72, 66, 9, 198, 16, 144, 197, 52, 36, 133, 20, 10, 199, 12, 20, 193, 80, 244, 146, 20, 21, 0, 6, 195, 72, 85, 5, 21, 6, 195, 56, 84, 9, 20, 7, 196, 52, 19, 9, 4, 66, 7, 196, 28, 243, 9, 4, 66, 0, 8, 197, 80, 83, 196, 61, 64, 66, 9, 197, 76, 244, 150, 60, 192, 66, 21, 8, 197, 76, 195, 199, 4, 224, 20, 8, 197, 72, 149, 18, 61, 96, 20, 8, 197, 21, 35, 196, 61, 64, 66, 6, 195, 8, 83, 22, 21, 8, 197, 8, 17, 206, 60, 192, 66, 0, 9, 198, 24, 84, 212, 37, 96, 76, 65, 13, 202, 20, 193, 84, 81, 35, 212, 20, 51, 137, 12, 20, 9, 198, 12, 20, 212, 61, 33, 64, 65, 0, 10, 199, 48, 243, 66, 5, 33, 9, 4, 67, 0, 6, 195, 80, 21, 1, 66, 7, 196, 64, 243, 131, 20, 20, 6, 195, 64, 148, 9, 66, 11, 200, 52, 22, 154, 4, 48, 200, 21, 32, 66, 7, 196, 52, 19, 137, 4, 66, 7, 196, 44, 83, 137, 4, 20, 0, 9, 197, 80, 83, 80, 21, 32, 65, 20, 9, 197, 52, 85, 5, 61, 32, 66, 21, 0, 5, 194, 4, 144, 72, 9, 198, 48, 19, 131, 21, 69, 0, 21, 9, 198, 13, 35, 195, 21, 69, 0, 21, 9, 198, 8, 240, 195, 21, 69, 0, 21, 0, 10, 199, 24, 84, 146, 4, 115, 211, 80, 21, 9, 198, 4, 229, 9, 24, 21, 5, 66, 0, 7, 196, 76, 16, 137, 72, 66, 8, 196, 72, 243, 12, 20, 66, 20, 7, 196, 65, 34, 69, 28, 20, 0, 12, 201, 64, 243, 9, 52, 84, 212, 61, 33, 64, 67, 8, 197, 48, 16, 207, 56, 144, 65, 8, 197, 36, 225, 207, 72, 112, 21, 8, 197, 21, 2, 76, 60, 112, 66, 8, 197, 16, 147, 195, 48, 80, 65, 0, 9, 198, 104, 147, 135, 5, 34, 64, 65, 9, 198, 104, 145, 199, 85, 32, 84, 65, 9, 198, 16, 80, 213, 8, 149, 0, 66, 9, 198, 12, 243, 147, 84, 85, 0, 20, 0, 9, 198, 76, 81, 206, 5, 98, 65, 67, 9, 198, 76, 20, 148, 61, 34, 65, 67, 10, 199, 64, 243, 9, 13, 32, 84, 20, 66, 9, 198, 28, 84, 135, 61, 98, 65, 20, 6, 195, 12, 85, 0, 20, 9, 198, 12, 19, 148, 61, 34, 65, 67, 11, 199, 12, 17, 15, 56, 81, 200, 20, 66, 20, 0, 11, 200, 93, 80, 200, 21, 33, 82, 36, 16, 67, 11, 200, 80, 83, 73, 77, 67, 195, 48, 80, 66, 11, 200, 64, 243, 9, 80, 80, 206, 36, 48, 20, 11, 200, 37, 3, 195, 60, 225, 18, 36, 16, 68, 11, 200, 37, 1, 82, 81, 35, 198, 36, 16, 68, 7, 196, 36, 225, 133, 72, 65, 7, 196, 25, 35, 196, 20, 20, 11, 200, 16, 145, 76, 21, 69, 18, 36, 48, 20, 7, 196, 16, 17, 142, 36, 66, 11, 200, 12, 84, 131, 61, 2, 84, 20, 48, 20, 11, 200, 9, 84, 143, 13, 32, 90, 36, 16, 68, 10, 198, 9, 80, 197, 24, 19, 0, 66, 20, 0, 8, 197, 76, 147, 21, 72, 144, 65, 8, 197, 72, 245, 1, 72, 144, 65, 8, 197, 61, 99, 214, 36, 16, 67, 9, 198, 52, 18, 69, 85, 66, 67, 66, 8, 197, 28, 84, 146, 20, 144, 66, 8, 197, 12, 21, 1, 72, 144, 65, 0, 12, 201, 60, 67, 206, 80, 242, 65, 81, 34, 65, 70, 9, 198, 5, 48, 204, 21, 2, 64, 20, 0, 9, 198, 81, 85, 20, 5, 98, 65, 8, 9, 198, 81, 85, 20, 5, 98, 65, 67, 9, 198, 80, 147, 148, 61, 34, 65, 67, 9, 198, 76, 21, 18, 5, 2, 65, 67, 10, 199, 21, 21, 73, 48, 21, 5, 72, 67, 9, 198, 12, 244, 211, 21, 34, 65, 66, 9, 198, 5, 3, 195, 72, 149, 9, 66, 0, 7, 196, 76, 50, 5, 52, 20, 7, 196, 72, 244, 211, 36, 21, 7, 196, 65, 34, 65, 52, 65, 11, 200, 64, 193, 67, 61, 69, 5, 72, 144, 20, 7, 196, 61, 69, 9, 52, 20, 7, 196, 21, 49, 68, 72, 20, 9, 198, 16, 245, 129, 16, 243, 0, 66, 11, 200, 16, 148, 12, 60, 208, 90, 36, 16, 68, 8, 196, 12, 81, 129, 48, 65, 20, 11, 200, 4, 226, 83, 61, 69, 5, 72, 144, 20, 0, 8, 197, 80, 145, 80, 60, 192, 20, 8, 197, 64, 147, 154, 60, 192, 66, 0, 12, 201, 72, 17, 9, 61, 65, 82, 5, 2, 65, 70, 12, 201, 65, 50, 67, 61, 65, 82, 5, 2, 65, 69, 12, 201, 65, 32, 78, 61, 65, 82, 5, 2, 65, 69, 12, 201, 64, 84, 195, 5, 52, 197, 72, 243, 9, 67, 12, 201, 24, 148, 201, 61, 65, 82, 5, 2, 65, 70, 12, 201, 13, 35, 205, 61, 65, 82, 5, 2, 65, 69, 12, 201, 5, 35, 205, 5, 65, 82, 5, 2, 65, 70, 9, 198, 4, 208, 68, 21, 84, 192, 21, 0, 0, 10, 198, 80, 83, 5, 52, 85, 18, 66, 20, 9, 198, 16, 244, 201, 52, 85, 18, 66, 0, 15, 204, 13, 34, 83, 80, 19, 12, 61, 65, 82, 5, 2, 65, 70, 0, 0, 14, 203, 69, 80, 84, 80, 244, 132, 36, 49, 83, 36, 208, 20, 9, 198, 52, 20, 133, 81, 66, 77, 21, 9, 198, 12, 84, 142, 60, 32, 137, 20, 0, 7, 196, 80, 84, 208, 36, 20, 7, 196, 76, 147, 143, 72, 21, 7, 196, 72, 243, 12, 36, 66, 6, 195, 56, 83, 73, 20, 7, 196, 12, 243, 12, 36, 20, 0, 8, 197, 80, 19, 12, 20, 64, 66, 6, 195, 64, 131, 206, 20, 6, 195, 20, 35, 0, 20, 0, 9, 198, 81, 34, 77, 21, 68, 128, 65, 9, 198, 76, 240, 201, 21, 64, 64, 67, 9, 198, 64, 149, 5, 12, 144, 64, 20, 9, 198, 64, 20, 129, 88, 144, 64, 67, 9, 198, 36, 68, 143, 24, 240, 128, 66, 0, 12, 201, 64, 243, 148, 20, 192, 78, 16, 243, 6, 20, 6, 195, 52, 240, 64, 20, 0, 7, 196, 24, 83, 137, 76, 21, 0, 9, 198, 5, 97, 83, 76, 147, 79, 72, 12, 201, 56, 20, 131, 60, 193, 83, 76, 144, 64, 68, 6, 195, 52, 240, 66, 66, 12, 201, 48, 144, 193, 57, 68, 143, 64, 144, 64, 68, 8, 197, 21, 48, 200, 36, 192, 20, 9, 197, 16, 20, 137, 20, 224, 67, 21, 8, 197, 12, 194, 77, 20, 224, 65, 12, 201, 12, 21, 1, 64, 193, 83, 76, 144, 64, 68, 8, 197, 9, 37, 71, 60, 192, 65, 0, 9, 198, 88, 83, 129, 72, 144, 64, 67, 9, 198, 88, 19, 9, 28, 144, 64, 66, 9, 198, 84, 52, 143, 56, 144, 64, 67, 10, 198, 76, 147, 5, 76, 144, 64, 66, 20, 18, 70, 76, 81, 5, 12, 144, 64, 87, 36, 70, 36, 74, 6, 37, 12, 35, 0, 10, 198, 64, 243, 5, 76, 144, 64, 66, 20, 10, 198, 52, 19, 5, 76, 144, 64, 66, 20, 9, 198, 12, 243, 69, 16, 144, 64, 20, 0, 9, 198, 88, 83, 148, 20, 227, 137, 20, 10, 199, 64, 83, 148, 5, 3, 204, 36, 66, 10, 199, 52, 83, 16, 60, 209, 78, 20, 66, 10, 199, 52, 19, 5, 77, 49, 82, 20, 20, 6, 195, 21, 33, 0, 21, 10, 199, 8, 83, 133, 77, 49, 82, 20, 20, 0, 6, 195, 105, 83, 21, 66, 7, 196, 80, 244, 211, 20, 21, 8, 196, 76, 244, 201, 4, 65, 20, 7, 196, 4, 50, 5, 36, 66, 0, 8, 197, 61, 4, 15, 77, 64, 21, 8, 197, 52, 243, 135, 61, 160, 20, 12, 201, 28, 195, 211, 76, 243, 1, 48, 144, 64, 68, 8, 197, 24, 147, 195, 36, 224, 66, 8, 197, 21, 2, 84, 21, 64, 66, 12, 201, 12, 148, 195, 5, 80, 193, 76, 144, 64, 68, 8, 197, 8, 20, 130, 5, 32, 65, 8, 197, 4, 194, 77, 20, 224, 21, 0, 6, 195, 64, 145, 71, 20, 9, 198, 21, 2, 84, 60, 209, 64, 66, 0, 6, 195, 64, 145, 64, 20, 9, 198, 52, 17, 206, 20, 230, 137, 20, 0, 14, 68, 37, 48, 73, 4, 37, 86, 35, 6, 37, 12, 35, 0, 9, 198, 13, 35, 205, 60, 99, 210, 66, 8, 196, 12, 81, 15, 48, 65, 20, 7, 196, 5, 33, 79, 48, 66, 0, 8, 197, 72, 148, 207, 73, 64, 21, 8, 197, 64, 243, 9, 105, 160, 65, 0, 5, 194, 24, 16, 76, 6, 194, 16, 80, 72, 9, 9, 198, 80, 245, 82, 56, 81, 64, 21, 9, 198, 60, 193, 65, 12, 81, 64, 67, 13, 202, 53, 84, 201, 12, 245, 5, 72, 20, 9, 4, 70, 5, 194, 20, 48, 20, 13, 202, 12, 129, 77, 36, 245, 5, 72, 20, 9, 4, 70, 9, 198, 5, 65, 78, 60, 193, 128, 20, 0, 9, 67, 32, 18, 64, 35, 57, 0, 72, 7, 195, 56, 82, 64, 72, 28, 10, 199, 76, 81, 199, 36, 245, 137, 4, 67, 9, 198, 64, 19, 1, 52, 81, 5, 20, 10, 199, 24, 147, 15, 76, 241, 137, 4, 68, 9, 198, 12, 243, 80, 61, 53, 5, 21, 10, 199, 12, 16, 137, 56, 245, 137, 4, 68, 10, 199, 4, 229, 9, 52, 17, 137, 4, 67, 6, 195, 4, 112, 84, 65, 0, 7, 196, 64, 84, 212, 20, 20, 7, 196, 5, 97, 86, 4, 72, 7, 196, 5, 97, 84, 20, 72, 8, 196, 77, 66, 76, 20, 66, 20, 6, 195, 36, 229, 137, 66, 9, 198, 24, 244, 196, 36, 227, 214, 20, 7, 196, 8, 145, 143, 72, 65, 7, 196, 5, 96, 82, 36, 65, 7, 196, 5, 65, 76, 20, 65, 0, 7, 195, 16, 83, 0, 72, 9, 8, 197, 77, 3, 199, 48, 144, 20, 9, 198, 72, 82, 77, 64, 145, 71, 20, 8, 197, 65, 35, 195, 56, 80, 20, 12, 201, 29, 80, 82, 16, 19, 9, 56, 81, 64, 67, 9, 197, 12, 240, 204, 20, 16, 65, 20, 8, 197, 9, 35, 199, 48, 144, 20, 9, 197, 8, 243, 7, 36, 16, 65, 20, 8, 197, 4, 224, 78, 36, 16, 67, 9, 197, 4, 193, 82, 36, 16, 66, 21, 0, 9, 198, 9, 84, 195, 20, 210, 64, 20, 0, 6, 195, 16, 18, 64, 72, 10, 199, 88, 84, 195, 61, 98, 76, 20, 67, 0, 7, 196, 25, 83, 77, 60, 72, 16, 4, 95, 4, 16, 20, 10, 82, 6, 37, 51, 79, 39, 55, 35, 0, 7, 196, 76, 19, 132, 20, 66, 11, 200, 64, 81, 15, 28, 83, 133, 76, 144, 67, 11, 200, 61, 32, 200, 36, 64, 67, 20, 80, 67, 11, 200, 52, 85, 1, 24, 243, 133, 76, 144, 20, 0, 8, 197, 69, 81, 71, 48, 144, 72, 8, 197, 80, 83, 210, 36, 16, 67, 12, 201, 77, 66, 76, 61, 3, 201, 16, 82, 64, 69, 8, 197, 73, 85, 5, 56, 144, 20, 8, 197, 72, 80, 76, 80, 16, 67, 8, 197, 64, 20, 143, 16, 144, 66, 8, 197, 64, 20, 143, 16, 144, 20, 8, 197, 48, 245, 133, 72, 80, 21, 8, 197, 48, 85, 137, 80, 16, 67, 8, 197, 37, 3, 212, 20, 48, 20, 10, 198, 36, 115, 5, 76, 144, 83, 66, 20, 8, 197, 24, 83, 9, 12, 80, 66, 8, 197, 21, 48, 200, 36, 208, 20, 9, 197, 16, 245, 133, 72, 80, 66, 21, 9, 198, 12, 244, 144, 61, 33, 79, 66, 8, 197, 12, 83, 148, 72, 144, 20, 8, 197, 8, 245, 67, 48, 80, 67, 8, 197, 5, 85, 1, 72, 144, 65, 0, 9, 198, 65, 35, 208, 4, 227, 204, 67, 9, 198, 12, 243, 131, 72, 85, 0, 20, 9, 198, 12, 20, 133, 28, 114, 64, 21, 9, 198, 8, 19, 19, 4, 210, 64, 65, 9, 198, 4, 195, 15, 28, 114, 64, 20, 0, 9, 198, 76, 19, 79, 28, 114, 65, 20, 6, 195, 72, 85, 20, 20, 11, 199, 64, 20, 148, 20, 50, 80, 20, 66, 21, 9, 198, 48, 244, 133, 28, 114, 65, 20, 20, 70, 24, 20, 141, 4, 50, 65, 81, 35, 14, 16, 63, 35, 74, 6, 37, 12, 35, 0, 9, 198, 16, 240, 146, 84, 114, 65, 66, 0, 7, 196, 80, 20, 211, 36, 66, 7, 196, 69, 82, 69, 80, 20, 6, 195, 48, 19, 69, 66, 9, 198, 21, 84, 143, 64, 243, 0, 68, 8, 196, 16, 80, 137, 80, 65, 21, 11, 200, 12, 244, 205, 60, 115, 206, 36, 16, 68, 7, 196, 8, 144, 137, 80, 65, 11, 200, 5, 34, 83, 80, 241, 129, 56, 80, 67, 6, 195, 4, 227, 193, 20, 0, 9, 198, 24, 16, 195, 36, 19, 79, 76, 6, 195, 88, 85, 18, 21, 8, 197, 52, 243, 154, 60, 224, 66, 12, 201, 12, 20, 212, 20, 192, 201, 88, 149, 0, 67, 0, 9, 198, 76, 83, 73, 72, 85, 20, 20, 9, 198, 64, 20, 129, 64, 85, 20, 20, 9, 198, 20, 227, 133, 76, 147, 64, 20, 0, 6, 195, 21, 53, 0, 9, 6, 195, 84, 243, 64, 20, 10, 199, 64, 20, 129, 25, 32, 83, 36, 66, 10, 199, 52, 85, 1, 12, 83, 148, 72, 20, 6, 195, 21, 53, 0, 21, 6, 195, 16, 145, 84, 20, 0, 7, 196, 88, 84, 208, 72, 20, 7, 196, 77, 2, 69, 16, 20, 6, 195, 64, 21, 21, 66, 7, 195, 60, 35, 197, 65, 20, 7, 196, 52, 244, 212, 72, 21, 7, 196, 13, 80, 213, 48, 66, 10, 198, 13, 35, 199, 36, 243, 0, 65, 20, 7, 196, 12, 147, 133, 52, 65, 0, 8, 197, 72, 148, 207, 73, 48, 21, 8, 197, 72, 144, 207, 73, 48, 21, 6, 195, 8, 83, 66, 20, 0, 6, 194, 4, 192, 72, 9, 6, 194, 20, 64, 72, 8, 9, 198, 52, 243, 143, 64, 85, 20, 20, 10, 198, 4, 229, 9, 76, 243, 64, 67, 20, 0, 13, 201, 8, 20, 130, 4, 34, 69, 80, 243, 0, 67, 20, 0, 12, 68, 64, 244, 212, 4, 48, 108, 87, 47, 35, 0, 13, 4, 95, 20, 12, 4, 47, 6, 37, 55, 70, 36, 0, 7, 196, 88, 147, 143, 88, 20, 7, 196, 64, 83, 1, 28, 65, 7, 196, 16, 83, 5, 28, 65, 7, 196, 9, 33, 86, 20, 20, 0, 8, 197, 64, 21, 20, 36, 224, 65, 8, 197, 36, 229, 15, 72, 224, 21, 8, 197, 12, 243, 132, 36, 192, 20, 0, 9, 198, 104, 83, 143, 8, 144, 64, 20, 12, 201, 81, 33, 78, 80, 17, 21, 21, 50, 77, 20, 9, 198, 24, 21, 71, 48, 144, 64, 66, 9, 198, 12, 20, 143, 56, 144, 64, 67, 9, 198, 5, 64, 83, 76, 144, 64, 67, 9, 198, 5, 34, 84, 52, 144, 64, 67, 9, 198, 5, 32, 197, 88, 144, 64, 20, 9, 198, 4, 209, 71, 48, 144, 64, 20, 9, 198, 4, 84, 143, 88, 144, 64, 67, 0, 10, 199, 80, 83, 196, 61, 50, 65, 56, 69, 10, 199, 76, 83, 73, 9, 33, 86, 20, 20, 10, 198, 48, 147, 143, 48, 85, 77, 66, 20, 10, 199, 20, 195, 5, 77, 3, 206, 80, 20, 10, 199, 12, 20, 15, 48, 21, 143, 72, 21, 0, 7, 196, 80, 83, 5, 24, 65, 7, 196, 49, 83, 65, 12, 66, 7, 196, 12, 243, 15, 72, 21, 7, 196, 8, 243, 143, 76, 20, 7, 196, 4, 225, 18, 20, 66, 0, 12, 201, 80, 80, 206, 60, 52, 129, 104, 144, 64, 68, 9, 197, 76, 241, 199, 60, 192, 66, 21, 8, 197, 64, 84, 137, 60, 64, 66, 12, 201, 12, 20, 148, 60, 208, 78, 104, 144, 64, 68, 0, 9, 198, 61, 37, 9, 28, 144, 64, 66, 5, 194, 21, 64, 20, 10, 198, 12, 244, 141, 60, 228, 192, 66, 20, 9, 198, 8, 20, 143, 56, 144, 64, 67, 9, 198, 5, 33, 207, 88, 144, 64, 20, 0, 10, 199, 81, 35, 214, 5, 35, 194, 20, 20, 10, 199, 80, 84, 129, 64, 85, 84, 36, 67, 10, 199, 64, 20, 129, 64, 83, 132, 36, 68, 10, 199, 52, 19, 3, 21, 50, 78, 20, 21, 0, 11, 200, 76, 20, 132, 4, 224, 80, 4, 192, 67, 14, 68, 49, 80, 201, 4, 55, 40, 74, 6, 37, 12, 35, 0, 7, 196, 36, 115, 143, 80, 20, 7, 196, 24, 83, 143, 48, 66, 7, 196, 24, 83, 3, 20, 21, 0, 8, 197, 76, 49, 84, 81, 32, 20, 12, 201, 52, 148, 193, 57, 68, 143, 64, 144, 64, 68, 8, 197, 52, 83, 69, 57, 64, 20, 9, 198, 12, 147, 79, 48, 18, 83, 67, 12, 201, 12, 130, 82, 60, 208, 78, 104, 144, 64, 68, 12, 201, 4, 226, 83, 61, 68, 143, 64, 144, 64, 69, 0, 9, 198, 69, 80, 68, 73, 84, 12, 65, 9, 198, 65, 35, 212, 21, 69, 0, 20, 9, 198, 16, 148, 208, 21, 69, 0, 20, 0, 16, 67, 5, 101, 128, 97, 118, 118, 111, 99, 97, 116, 111, 0, 25, 29, 10, 199, 56, 21, 77, 4, 50, 9, 4, 68, 9, 198, 29, 32, 84, 84, 149, 1, 67, 6, 195, 24, 85, 68, 65, 0, 7, 196, 104, 83, 15, 80, 20, 7, 196, 88, 147, 133, 4, 65, 7, 196, 81, 34, 79, 16, 65, 11, 200, 81, 32, 80, 21, 163, 197, 17, 32, 20, 7, 196, 80, 147, 133, 4, 65, 9, 198, 80, 84, 146, 4, 227, 214, 20, 7, 196, 48, 147, 133, 4, 65, 7, 196, 24, 240, 137, 4, 66, 7, 196, 24, 147, 15, 80, 20, 11, 200, 12, 192, 77, 36, 67, 198, 61, 32, 67, 0, 8, 197, 72, 80, 204, 85, 64, 65, 8, 197, 28, 147, 206, 5, 64, 65, 8, 197, 13, 33, 77, 21, 32, 65, 0, 6, 194, 12, 144, 76, 9, 9, 198, 5, 52, 201, 20, 209, 64, 20, 0, 0, 7, 196, 5, 97, 86, 36, 72, 7, 196, 52, 19, 1, 28, 65, 9, 198, 28, 243, 5, 4, 67, 210, 68, 7, 196, 24, 243, 1, 28, 65, 7, 196, 24, 147, 143, 72, 21, 7, 196, 12, 81, 21, 60, 20, 0, 12, 201, 76, 245, 20, 60, 213, 76, 80, 148, 12, 67, 8, 197, 76, 83, 77, 4, 144, 66, 8, 197, 76, 51, 199, 48, 144, 20, 8, 197, 52, 85, 15, 16, 144, 20, 8, 197, 48, 21, 82, 36, 16, 67, 8, 197, 24, 84, 137, 80, 16, 67, 8, 197, 12, 245, 20, 36, 208, 20, 8, 197, 5, 81, 213, 72, 80, 65, 0, 9, 198, 56, 16, 129, 80, 82, 64, 67, 9, 198, 4, 48, 207, 48, 149, 0, 66, 0, 0, 7, 196, 85, 50, 78, 36, 65, 9, 198, 64, 147, 133, 72, 243, 0, 67, 9, 198, 64, 20, 129, 8, 243, 0, 66, 7, 196, 12, 243, 15, 56, 66, 11, 200, 12, 243, 12, 20, 224, 200, 36, 208, 20, 6, 195, 5, 101, 137, 66, 0, 9, 197, 64, 84, 15, 48, 144, 65, 20, 9, 198, 61, 69, 15, 80, 148, 0, 66, 8, 197, 12, 84, 193, 72, 80, 65, 8, 197, 12, 20, 207, 48, 144, 65, 8, 197, 12, 20, 148, 4, 208, 65, 0, 9, 198, 56, 149, 5, 72, 242, 64, 21, 9, 198, 52, 19, 133, 28, 114, 64, 67, 0, 6, 195, 64, 145, 84, 20, 9, 198, 52, 19, 137, 12, 243, 73, 20, 9, 198, 12, 243, 15, 76, 147, 73, 66, 0, 7, 196, 104, 83, 137, 80, 20, 7, 196, 96, 147, 5, 52, 20, 9, 198, 88, 144, 146, 4, 99, 206, 66, 8, 196, 80, 83, 133, 16, 65, 20, 7, 196, 28, 243, 7, 36, 20, 9, 198, 13, 34, 83, 76, 243, 0, 66, 8, 196, 12, 83, 133, 16, 65, 20, 7, 196, 12, 19, 129, 16, 65, 11, 200, 4, 192, 137, 28, 224, 83, 20, 112, 67, 0, 9, 198, 64, 84, 134, 84, 112, 83, 65, 19, 70, 29, 32, 84, 84, 149, 15, 79, 14, 16, 35, 47, 6, 40, 37, 47, 39, 0, 12, 201, 16, 147, 137, 81, 35, 198, 20, 227, 204, 69, 0, 10, 198, 4, 227, 205, 4, 195, 192, 66, 20, 9, 198, 5, 100, 129, 56, 227, 192, 72, 9, 198, 77, 3, 212, 61, 35, 128, 21, 9, 198, 36, 229, 5, 72, 147, 64, 65, 13, 201, 29, 80, 82, 16, 144, 82, 20, 114, 65, 67, 20, 13, 202, 12, 19, 15, 49, 162, 79, 12, 244, 148, 20, 21, 0, 6, 195, 48, 145, 84, 20, 10, 199, 36, 224, 207, 57, 53, 69, 80, 20, 9, 198, 21, 21, 65, 56, 147, 69, 66, 0, 12, 68, 32, 19, 142, 60, 35, 50, 50, 39, 0, 72, 6, 195, 89, 81, 21, 66, 7, 196, 76, 243, 9, 80, 65, 7, 196, 65, 35, 195, 36, 20, 7, 196, 64, 19, 129, 52, 65, 7, 196, 16, 147, 129, 52, 65, 7, 196, 16, 19, 129, 20, 65, 0, 0, 9, 198, 52, 243, 148, 72, 80, 76, 21, 9, 198, 12, 243, 148, 61, 35, 128, 21, 0, 6, 195, 61, 32, 193, 21, 10, 199, 77, 1, 82, 52, 144, 201, 16, 67, 6, 195, 61, 51, 73, 20, 6, 195, 36, 243, 137, 20, 10, 199, 4, 195, 15, 9, 35, 199, 36, 66, 0, 9, 198, 81, 34, 71, 20, 210, 78, 66, 9, 198, 76, 48, 76, 36, 113, 82, 66, 9, 198, 65, 33, 67, 4, 209, 82, 66, 6, 195, 56, 80, 128, 20, 6, 195, 24, 80, 128, 20, 0, 7, 196, 16, 83, 12, 4, 72, 7, 196, 16, 19, 12, 4, 72, 7, 196, 81, 34, 66, 84, 66, 8, 196, 80, 83, 133, 72, 65, 20, 7, 196, 76, 243, 129, 72, 20, 7, 196, 64, 147, 5, 60, 65, 7, 196, 36, 243, 1, 60, 67, 12, 201, 36, 225, 137, 56, 149, 5, 76, 147, 64, 20, 7, 196, 29, 33, 86, 20, 20, 7, 196, 16, 147, 129, 72, 65, 8, 196, 5, 97, 82, 20, 66, 21, 0, 13, 202, 64, 20, 148, 20, 227, 199, 20, 225, 83, 36, 68, 8, 197, 52, 16, 200, 36, 224, 65, 0, 9, 198, 81, 32, 83, 8, 244, 132, 21, 9, 198, 76, 99, 199, 48, 144, 64, 20, 6, 195, 72, 83, 137, 21, 9, 198, 64, 243, 9, 52, 84, 128, 66, 9, 198, 52, 85, 1, 52, 84, 128, 66, 9, 198, 4, 65, 83, 52, 144, 64, 67, 0, 6, 195, 73, 80, 64, 66, 10, 199, 12, 20, 144, 36, 225, 84, 36, 21, 0, 7, 196, 88, 148, 201, 72, 66, 12, 201, 65, 35, 212, 60, 208, 82, 80, 148, 133, 67, 7, 196, 64, 83, 132, 36, 66, 11, 200, 25, 32, 78, 12, 240, 143, 48, 192, 21, 11, 200, 12, 243, 5, 77, 65, 82, 60, 192, 68, 11, 200, 4, 192, 66, 5, 53, 18, 60, 224, 66, 0, 9, 198, 64, 243, 9, 56, 243, 73, 20, 8, 197, 64, 192, 84, 4, 224, 65, 8, 197, 64, 84, 137, 64, 192, 65, 9, 197, 8, 245, 133, 28, 224, 65, 20, 0, 9, 198, 80, 81, 15, 24, 244, 128, 66, 9, 198, 76, 51, 210, 64, 244, 128, 65, 9, 198, 52, 85, 1, 24, 244, 128, 66, 5, 194, 21, 96, 20, 9, 198, 4, 113, 78, 104, 144, 64, 67, 0, 6, 195, 61, 35, 208, 20, 10, 199, 36, 229, 18, 36, 228, 197, 12, 66, 10, 199, 21, 85, 9, 25, 35, 206, 20, 67, 10, 199, 16, 83, 9, 4, 229, 79, 88, 20, 10, 199, 5, 32, 207, 8, 19, 5, 56, 21, 0, 7, 196, 5, 97, 86, 60, 72, 7, 196, 76, 83, 3, 20, 21, 7, 196, 20, 208, 143, 48, 20, 7, 196, 12, 243, 5, 36, 66, 7, 196, 12, 19, 9, 4, 66, 7, 196, 8, 19, 9, 4, 66, 0, 0, 6, 195, 80, 16, 137, 66, 9, 198, 76, 240, 130, 61, 33, 192, 21, 9, 198, 60, 115, 137, 80, 83, 80, 20, 9, 198, 52, 19, 132, 61, 35, 0, 65, 13, 202, 12, 243, 148, 20, 212, 15, 72, 19, 133, 60, 68, 9, 198, 12, 20, 193, 56, 245, 128, 20, 0, 10, 199, 80, 85, 18, 4, 209, 84, 72, 66, 11, 199, 64, 243, 9, 56, 84, 201, 4, 67, 20, 11, 67, 9, 81, 64, 69, 6, 40, 12, 36, 0, 0, 11, 200, 64, 243, 1, 72, 147, 69, 81, 32, 67, 7, 196, 64, 147, 131, 20, 66, 7, 196, 52, 85, 15, 16, 20, 8, 196, 48, 19, 132, 60, 66, 20, 7, 196, 17, 33, 83, 16, 20, 11, 200, 13, 80, 143, 81, 64, 69, 17, 32, 20, 7, 196, 13, 35, 195, 20, 66, 9, 198, 12, 20, 131, 60, 99, 210, 66, 0, 8, 197, 81, 34, 69, 17, 32, 20, 12, 201, 12, 243, 148, 72, 244, 9, 20, 65, 64, 20, 8, 197, 4, 48, 197, 81, 64, 21, 0, 7, 66, 32, 16, 35, 0, 72, 7, 194, 16, 144, 72, 9, 28, 13, 202, 81, 32, 71, 36, 51, 205, 52, 81, 9, 4, 20, 5, 194, 20, 112, 20, 9, 198, 5, 3, 195, 72, 145, 128, 66, 0, 6, 195, 25, 82, 64, 72, 10, 199, 96, 83, 143, 24, 240, 137, 4, 68, 10, 199, 4, 229, 9, 4, 84, 133, 4, 67, 0, 7, 196, 16, 19, 12, 20, 72, 7, 196, 61, 98, 76, 20, 66, 9, 198, 12, 243, 80, 48, 85, 0, 20, 7, 196, 12, 19, 1, 60, 66, 0, 9, 197, 81, 35, 193, 16, 80, 65, 20, 8, 197, 77, 65, 82, 20, 240, 65, 8, 197, 64, 83, 70, 36, 112, 20, 8, 197, 56, 243, 131, 32, 80, 66, 6, 195, 24, 85, 0, 20, 9, 197, 21, 3, 195, 32, 80, 67, 20, 8, 197, 12, 19, 66, 72, 144, 66, 8, 197, 12, 19, 4, 20, 144, 66, 6, 195, 4, 245, 0, 20, 18, 70, 4, 195, 5, 49, 82, 65, 35, 55, 55, 107, 55, 6, 40, 37, 35, 0, 9, 197, 4, 193, 83, 36, 16, 66, 20, 0, 6, 195, 56, 85, 77, 65, 6, 195, 29, 35, 205, 21, 11, 67, 9, 82, 65, 69, 6, 40, 37, 35, 0, 0, 10, 199, 61, 37, 15, 81, 65, 82, 36, 20, 10, 199, 8, 148, 197, 77, 66, 76, 20, 67, 10, 199, 5, 85, 15, 24, 240, 213, 76, 20, 0, 7, 196, 81, 34, 79, 72, 21, 7, 196, 77, 67, 194, 36, 20, 11, 200, 76, 147, 85, 49, 64, 78, 20, 240, 67, 11, 200, 16, 144, 201, 4, 227, 143, 88, 80, 20, 7, 196, 12, 243, 132, 20, 66, 11, 200, 12, 19, 80, 36, 67, 199, 48, 144, 20, 12, 200, 8, 244, 135, 61, 49, 83, 36, 16, 67, 20, 7, 196, 4, 229, 9, 12, 66, 0, 8, 197, 104, 244, 16, 36, 16, 66, 8, 197, 76, 144, 129, 72, 144, 65, 8, 197, 76, 51, 210, 12, 144, 21, 10, 198, 64, 19, 132, 61, 50, 65, 66, 20, 8, 197, 52, 244, 137, 56, 144, 65, 8, 197, 24, 243, 12, 36, 16, 66, 8, 197, 12, 244, 16, 36, 16, 20, 8, 197, 8, 20, 137, 48, 80, 66, 10, 198, 4, 208, 146, 61, 50, 65, 66, 20, 0, 6, 195, 72, 83, 133, 20, 5, 194, 25, 80, 72, 9, 198, 104, 17, 193, 72, 243, 0, 67, 7, 195, 80, 19, 133, 66, 20, 9, 198, 61, 52, 197, 69, 82, 64, 20, 9, 198, 60, 211, 137, 80, 83, 0, 67, 9, 198, 21, 49, 71, 21, 50, 64, 20, 9, 198, 12, 147, 206, 16, 243, 0, 21, 9, 198, 4, 210, 76, 61, 50, 64, 20, 9, 198, 4, 208, 146, 61, 50, 64, 20, 0, 10, 199, 88, 84, 154, 20, 115, 137, 76, 20, 6, 195, 88, 83, 128, 21, 10, 199, 77, 3, 206, 80, 19, 133, 60, 66, 6, 195, 13, 35, 196, 20, 0, 6, 195, 104, 83, 135, 20, 7, 196, 80, 19, 1, 52, 65, 7, 196, 76, 83, 3, 36, 21, 7, 196, 76, 19, 1, 52, 66, 9, 198, 65, 35, 208, 61, 53, 0, 21, 23, 72, 52, 20, 195, 4, 197, 67, 36, 16, 63, 35, 87, 49, 35, 55, 40, 74, 6, 37, 12, 35, 0, 7, 196, 28, 243, 5, 52, 20, 11, 200, 25, 83, 210, 36, 193, 71, 28, 80, 21, 11, 200, 21, 32, 84, 61, 53, 5, 56, 80, 67, 12, 201, 16, 17, 200, 21, 36, 143, 80, 148, 0, 67, 9, 198, 12, 243, 80, 61, 53, 0, 21, 9, 198, 12, 243, 80, 61, 53, 0, 21, 11, 200, 12, 21, 1, 77, 68, 143, 24, 80, 66, 7, 196, 12, 19, 129, 48, 66, 11, 67, 9, 82, 79, 69, 6, 40, 37, 39, 0, 0, 9, 198, 64, 243, 5, 76, 147, 133, 21, 6, 195, 64, 21, 82, 66, 12, 201, 52, 85, 1, 52, 244, 134, 61, 50, 64, 67, 9, 198, 37, 4, 15, 52, 83, 133, 66, 0, 9, 198, 80, 84, 129, 64, 85, 84, 67, 6, 195, 36, 243, 133, 20, 18, 70, 25, 37, 83, 12, 147, 192, 81, 14, 16, 40, 89, 6, 37, 12, 39, 0, 0, 10, 199, 80, 20, 211, 4, 209, 84, 72, 66, 6, 195, 72, 83, 128, 21, 10, 199, 64, 20, 133, 56, 50, 9, 52, 20, 14, 203, 61, 98, 68, 21, 3, 211, 37, 162, 79, 56, 80, 20, 6, 195, 52, 243, 128, 20, 10, 199, 4, 229, 9, 13, 33, 83, 36, 20, 0, 7, 196, 28, 244, 135, 4, 21, 7, 196, 24, 243, 133, 52, 20, 7, 196, 16, 81, 9, 80, 65, 7, 196, 12, 19, 143, 4, 20, 0, 13, 201, 52, 144, 210, 61, 52, 15, 73, 83, 64, 66, 20, 9, 198, 4, 229, 9, 28, 243, 133, 66, 9, 198, 4, 229, 9, 21, 35, 197, 20, 0, 9, 198, 37, 51, 195, 72, 243, 128, 66, 9, 198, 28, 20, 143, 24, 19, 128, 66, 5, 194, 20, 128, 21, 7, 195, 16, 20, 133, 66, 20, 6, 195, 8, 84, 133, 21, 9, 198, 5, 53, 18, 4, 112, 76, 66, 0, 6, 195, 88, 84, 128, 21, 6, 195, 88, 84, 128, 21, 6, 195, 61, 36, 192, 21, 6, 195, 61, 36, 192, 21, 6, 195, 56, 84, 128, 21, 0, 7, 196, 80, 19, 129, 72, 65, 8, 196, 76, 243, 5, 60, 65, 20, 7, 196, 57, 83, 69, 72, 65, 9, 198, 48, 147, 73, 81, 35, 198, 66, 7, 196, 20, 195, 5, 72, 21, 7, 196, 12, 243, 133, 72, 65, 7, 196, 4, 229, 9, 24, 65, 0, 8, 197, 80, 244, 142, 60, 192, 21, 12, 201, 76, 19, 22, 4, 67, 210, 20, 115, 128, 20, 8, 197, 64, 17, 18, 60, 224, 66, 8, 197, 56, 17, 148, 60, 192, 66, 8, 197, 52, 22, 154, 60, 192, 66, 0, 6, 195, 104, 85, 137, 20, 6, 195, 64, 20, 133, 66, 9, 198, 28, 194, 67, 21, 35, 204, 67, 9, 198, 20, 97, 137, 52, 84, 128, 66, 9, 198, 16, 244, 137, 24, 244, 128, 66, 0, 10, 199, 76, 245, 133, 73, 161, 78, 20, 66, 11, 199, 64, 193, 88, 36, 115, 1, 76, 65, 20, 0, 6, 195, 88, 84, 135, 21, 7, 196, 88, 83, 5, 56, 21, 7, 196, 64, 19, 5, 56, 21, 7, 196, 8, 19, 5, 56, 21, 11, 200, 4, 52, 85, 4, 100, 133, 16, 64, 21, 0, 9, 198, 61, 69, 15, 8, 243, 137, 20, 9, 197, 20, 227, 149, 64, 192, 65, 20, 0, 9, 198, 36, 225, 197, 57, 80, 64, 20, 9, 198, 16, 82, 79, 80, 20, 128, 66, 9, 198, 5, 4, 9, 60, 208, 128, 21, 0, 10, 199, 16, 241, 5, 12, 19, 133, 76, 20, 10, 199, 4, 65, 77, 64, 145, 82, 20, 66, 0, 7, 196, 72, 148, 5, 36, 66, 9, 198, 28, 20, 196, 61, 69, 0, 21, 7, 196, 20, 36, 133, 36, 66, 11, 200, 12, 83, 133, 72, 83, 148, 60, 192, 20, 7, 196, 12, 19, 129, 64, 65, 7, 196, 12, 19, 129, 64, 65, 7, 196, 5, 52, 193, 36, 66, 11, 200, 5, 34, 83, 80, 244, 211, 20, 224, 67, 0, 8, 197, 48, 145, 86, 37, 64, 66, 8, 197, 16, 149, 137, 21, 64, 20, 6, 195, 13, 35, 214, 20, 8, 197, 4, 112, 68, 21, 160, 67, 0, 9, 198, 88, 145, 207, 56, 245, 128, 20, 6, 195, 80, 20, 137, 66, 6, 195, 64, 21, 133, 66, 6, 195, 52, 244, 137, 21, 18, 70, 4, 208, 133, 17, 81, 64, 35, 63, 69, 36, 70, 6, 40, 12, 36, 0, 0, 6, 195, 84, 245, 128, 20, 9, 198, 52, 20, 211, 5, 35, 211, 20, 0, 7, 196, 76, 20, 133, 36, 72, 6, 195, 13, 35, 211, 20, 7, 196, 12, 244, 133, 4, 65, 11, 200, 12, 19, 15, 72, 147, 69, 81, 32, 67, 7, 196, 8, 244, 133, 4, 65, 0, 9, 198, 76, 147, 129, 48, 81, 133, 20, 8, 197, 61, 37, 137, 21, 64, 20, 6, 195, 52, 246, 154, 21, 9, 197, 16, 243, 12, 5, 32, 65, 20, 8, 197, 5, 52, 197, 81, 64, 20, 8, 197, 5, 52, 5, 81, 64, 20, 8, 197, 4, 97, 133, 81, 64, 20, 0, 6, 66, 20, 144, 116, 0, 6, 195, 80, 16, 149, 66, 5, 194, 28, 80, 20, 18, 70, 12, 147, 65, 9, 81, 64, 74, 37, 63, 35, 69, 6, 40, 12, 36, 0, 9, 198, 8, 19, 131, 60, 227, 212, 20, 9, 198, 5, 161, 79, 81, 35, 208, 67, 0, 9, 198, 76, 147, 134, 61, 35, 211, 20, 10, 199, 20, 210, 67, 72, 19, 137, 4, 68, 12, 201, 20, 193, 84, 81, 35, 196, 61, 69, 0, 21, 6, 195, 8, 243, 0, 20, 0, 7, 196, 16, 83, 12, 20, 72, 8, 196, 20, 51, 15, 28, 65, 20, 7, 196, 9, 35, 204, 48, 21, 0, 8, 197, 88, 148, 137, 48, 80, 66, 8, 197, 85, 67, 208, 36, 16, 67, 8, 197, 84, 33, 82, 80, 16, 67, 8, 197, 64, 243, 12, 36, 48, 20, 8, 197, 52, 243, 12, 36, 48, 66, 6, 195, 28, 85, 0, 20, 8, 197, 21, 66, 79, 64, 80, 66, 8, 197, 17, 34, 79, 64, 80, 65, 8, 197, 5, 34, 69, 80, 80, 20, 0, 9, 198, 52, 20, 141, 37, 35, 204, 67, 9, 198, 36, 229, 5, 73, 3, 204, 67, 9, 198, 12, 20, 148, 61, 50, 64, 20, 9, 198, 4, 195, 15, 16, 243, 0, 66, 0, 10, 199, 4, 193, 5, 8, 20, 129, 56, 68, 0, 7, 196, 88, 84, 132, 20, 21, 11, 200, 88, 83, 15, 12, 148, 5, 16, 80, 67, 7, 196, 65, 34, 79, 72, 21, 9, 198, 5, 50, 78, 13, 35, 206, 66, 0, 6, 195, 104, 80, 146, 20, 12, 201, 88, 83, 148, 72, 147, 15, 69, 82, 64, 20, 8, 197, 72, 144, 143, 76, 144, 20, 8, 197, 64, 243, 80, 20, 144, 66, 8, 197, 60, 209, 76, 36, 16, 67, 8, 197, 24, 81, 5, 48, 80, 21, 8, 197, 12, 147, 137, 76, 144, 65, 8, 197, 5, 84, 207, 56, 144, 20, 9, 198, 4, 229, 9, 12, 148, 0, 66, 8, 197, 4, 209, 76, 36, 16, 67, 0, 9, 198, 76, 147, 80, 61, 50, 64, 20, 9, 198, 52, 19, 142, 61, 50, 64, 20, 9, 198, 12, 243, 131, 21, 50, 64, 20, 0, 10, 199, 48, 149, 15, 72, 19, 133, 60, 67, 15, 203, 12, 243, 80, 85, 64, 90, 36, 243, 129, 48, 80, 69, 21, 0, 7, 196, 16, 19, 12, 60, 72, 8, 196, 88, 83, 133, 80, 65, 20, 11, 200, 65, 32, 83, 76, 149, 5, 48, 80, 66, 11, 200, 64, 244, 212, 21, 34, 79, 72, 144, 21, 7, 196, 56, 85, 84, 72, 65, 11, 200, 52, 147, 12, 20, 98, 79, 72, 144, 21, 11, 200, 8, 192, 84, 80, 242, 68, 20, 144, 68, 11, 200, 5, 53, 5, 72, 242, 68, 20, 144, 69, 12, 201, 4, 225, 204, 61, 48, 83, 76, 243, 137, 67, 0, 9, 198, 80, 148, 201, 24, 243, 133, 66, 9, 198, 64, 244, 193, 52, 147, 133, 67, 8, 197, 28, 243, 129, 73, 48, 66, 0, 9, 198, 4, 48, 197, 81, 67, 192, 20, 9, 198, 20, 48, 197, 81, 67, 192, 8, 9, 198, 81, 34, 83, 76, 147, 128, 65, 9, 198, 64, 148, 143, 88, 19, 128, 66, 9, 198, 64, 84, 147, 36, 19, 128, 67, 9, 198, 52, 81, 193, 24, 243, 128, 66, 13, 202, 12, 243, 148, 72, 244, 207, 28, 113, 84, 80, 20, 9, 198, 4, 197, 1, 48, 83, 128, 21, 0, 10, 199, 4, 224, 76, 24, 16, 133, 80, 20, 0, 7, 196, 24, 244, 131, 4, 21, 7, 196, 88, 148, 201, 80, 65, 7, 196, 76, 244, 131, 36, 21, 8, 196, 72, 243, 132, 60, 66, 20, 9, 198, 21, 2, 67, 20, 229, 18, 20, 12, 201, 4, 225, 204, 61, 48, 83, 76, 243, 133, 67, 7, 196, 4, 211, 5, 80, 20, 0, 8, 197, 32, 83, 12, 5, 48, 66, 0, 9, 198, 24, 244, 211, 21, 35, 192, 72, 0, 6, 195, 76, 51, 204, 21, 0, 7, 196, 76, 84, 133, 56, 21, 0, 9, 198, 20, 97, 137, 12, 16, 197, 67, 0, 6, 195, 60, 195, 73, 20, 10, 198, 24, 193, 71, 36, 20, 192, 65, 20, 9, 198, 21, 21, 73, 88, 240, 192, 66, 0, 6, 195, 64, 19, 204, 65, 6, 195, 60, 192, 64, 66, 10, 199, 12, 19, 12, 36, 116, 129, 24, 66, 0, 13, 68, 4, 84, 133, 60, 35, 6, 107, 51, 36, 39, 0, 6, 195, 104, 80, 195, 21, 7, 196, 80, 84, 133, 76, 20, 7, 196, 76, 20, 129, 28, 65, 6, 195, 72, 80, 195, 21, 11, 200, 65, 33, 71, 4, 230, 137, 60, 192, 68, 7, 196, 52, 244, 133, 76, 20, 9, 198, 16, 84, 196, 20, 211, 206, 20, 7, 196, 16, 84, 143, 28, 65, 6, 195, 8, 80, 195, 21, 0, 8, 197, 80, 147, 137, 4, 224, 66, 12, 201, 24, 20, 141, 4, 49, 85, 80, 144, 192, 67, 8, 197, 8, 83, 148, 60, 224, 20, 0, 9, 198, 65, 35, 211, 20, 194, 84, 66, 9, 198, 65, 35, 211, 20, 48, 192, 21, 9, 198, 65, 35, 208, 61, 50, 84, 66, 9, 198, 12, 243, 80, 61, 50, 84, 66, 9, 198, 5, 69, 9, 52, 148, 192, 65, 0, 6, 195, 76, 51, 212, 20, 10, 199, 64, 244, 148, 4, 192, 133, 72, 66, 6, 195, 60, 65, 64, 20, 10, 199, 28, 245, 20, 5, 49, 67, 12, 21, 10, 199, 4, 229, 9, 4, 84, 133, 60, 67, 0, 7, 196, 61, 52, 201, 4, 66, 9, 198, 12, 16, 193, 76, 83, 142, 21, 0, 6, 195, 88, 84, 154, 21, 8, 197, 12, 84, 130, 21, 32, 65, 0, 0, 6, 195, 60, 193, 64, 66, 10, 199, 52, 243, 129, 72, 50, 9, 4, 67, 6, 195, 8, 81, 192, 20, 0, 7, 196, 76, 20, 129, 36, 72, 11, 200, 65, 33, 83, 85, 4, 15, 77, 64, 21, 7, 196, 64, 20, 137, 4, 66, 8, 196, 56, 20, 132, 60, 66, 20, 8, 196, 24, 245, 133, 4, 65, 20, 7, 196, 13, 33, 83, 80, 21, 7, 196, 12, 21, 133, 4, 65, 9, 198, 12, 20, 142, 37, 99, 210, 66, 7, 196, 5, 34, 83, 80, 65, 0, 9, 198, 73, 80, 197, 48, 192, 73, 67, 6, 195, 28, 193, 66, 20, 8, 197, 12, 20, 144, 5, 32, 65, 0, 9, 198, 76, 20, 133, 8, 33, 64, 72, 10, 198, 64, 192, 67, 12, 129, 64, 66, 20, 9, 198, 52, 148, 137, 4, 65, 64, 66, 6, 195, 9, 80, 149, 66, 0, 7, 195, 12, 243, 0, 72, 9, 10, 3, 226, 130, 164, 55, 37, 34, 35, 0, 10, 199, 77, 65, 82, 20, 245, 9, 64, 67, 9, 198, 72, 83, 9, 28, 147, 211, 21, 6, 195, 60, 66, 64, 20, 6, 195, 12, 194, 64, 65, 0, 7, 196, 28, 83, 133, 72, 65, 7, 196, 88, 20, 133, 56, 21, 7, 196, 61, 52, 197, 60, 65, 9, 198, 28, 144, 82, 4, 37, 66, 67, 0, 8, 197, 88, 241, 204, 36, 16, 20, 8, 197, 88, 83, 133, 72, 80, 20, 12, 201, 52, 243, 148, 21, 49, 71, 4, 193, 64, 67, 8, 197, 36, 212, 9, 20, 112, 20, 8, 197, 24, 241, 204, 36, 16, 20, 8, 197, 16, 144, 76, 60, 112, 66, 6, 195, 12, 245, 0, 20, 6, 195, 12, 245, 0, 20, 0, 9, 198, 60, 113, 197, 8, 34, 64, 20, 11, 67, 28, 194, 65, 61, 6, 37, 12, 35, 0, 10, 198, 20, 224, 197, 24, 19, 0, 66, 20, 9, 198, 12, 240, 195, 36, 66, 64, 20, 0, 10, 67, 28, 194, 64, 61, 37, 0, 9, 72, 10, 199, 76, 50, 9, 5, 98, 84, 84, 67, 6, 195, 52, 242, 192, 20, 0, 7, 196, 28, 83, 133, 76, 65, 7, 196, 64, 84, 133, 28, 65, 9, 198, 64, 83, 148, 4, 115, 206, 66, 11, 200, 48, 18, 71, 84, 81, 204, 36, 16, 20, 0, 8, 197, 61, 52, 9, 80, 80, 20, 12, 201, 61, 33, 129, 56, 245, 18, 60, 98, 64, 20, 8, 197, 52, 241, 204, 36, 16, 20, 8, 197, 52, 18, 79, 72, 144, 21, 8, 197, 13, 33, 77, 36, 16, 65, 9, 197, 8, 84, 212, 36, 16, 65, 21, 8, 197, 5, 33, 193, 48, 144, 67, 8, 197, 5, 32, 77, 20, 144, 67, 0, 9, 198, 85, 48, 133, 12, 130, 64, 20, 9, 198, 52, 20, 195, 4, 194, 64, 65, 0, 10, 199, 76, 147, 66, 36, 243, 148, 20, 21, 0, 7, 196, 16, 83, 12, 60, 72, 11, 200, 52, 244, 19, 84, 84, 212, 36, 16, 66, 7, 196, 52, 84, 137, 80, 65, 11, 200, 52, 19, 1, 88, 241, 204, 36, 16, 20, 7, 196, 12, 244, 133, 16, 65, 6, 195, 12, 193, 83, 20, 7, 196, 12, 19, 143, 64, 20, 0, 9, 198, 4, 229, 9, 88, 20, 137, 66, 0, 9, 198, 4, 32, 137, 4, 211, 192, 76, 9, 198, 4, 32, 137, 4, 211, 192, 72, 10, 198, 80, 83, 5, 24, 243, 128, 66, 20, 9, 198, 72, 19, 65, 16, 19, 128, 67, 9, 198, 25, 32, 83, 76, 147, 128, 65, 0, 10, 199, 72, 85, 18, 60, 116, 129, 16, 66, 10, 199, 29, 32, 86, 36, 209, 84, 72, 66, 6, 195, 12, 193, 84, 20, 0, 7, 196, 24, 19, 142, 60, 76, 7, 196, 64, 148, 129, 52, 65, 0, 12, 201, 76, 245, 20, 21, 36, 129, 56, 83, 192, 67, 9, 198, 4, 50, 5, 52, 83, 133, 66, 0, 15, 3, 95, 50, 49, 82, 6, 36, 50, 47, 6, 40, 50, 39, 0, 10, 198, 60, 197, 18, 20, 211, 196, 67, 20, 7, 195, 52, 244, 197, 66, 20, 9, 198, 20, 212, 9, 72, 83, 192, 66, 5, 194, 20, 192, 21, 0, 6, 195, 24, 84, 192, 20, 0, 7, 196, 76, 52, 143, 24, 20, 0, 8, 197, 65, 35, 198, 36, 192, 66, 8, 197, 64, 144, 68, 20, 224, 66, 8, 197, 16, 243, 6, 36, 224, 66, 0, 9, 198, 104, 20, 133, 88, 144, 192, 20, 9, 198, 72, 85, 18, 60, 98, 84, 65, 9, 198, 20, 229, 5, 72, 144, 192, 21, 9, 198, 20, 193, 71, 36, 16, 192, 67, 0, 6, 195, 72, 84, 192, 21, 0, 8, 196, 76, 86, 154, 20, 66, 20, 7, 196, 12, 244, 134, 84, 66, 8, 196, 12, 20, 142, 20, 66, 20, 7, 196, 8, 243, 148, 4, 66, 0, 8, 197, 76, 84, 150, 4, 192, 66, 9, 197, 24, 195, 210, 36, 224, 65, 21, 0, 15, 4, 95, 13, 3, 14, 63, 6, 35, 49, 14, 16, 39, 50, 0, 0, 6, 195, 100, 241, 192, 20, 10, 199, 12, 20, 9, 80, 19, 133, 60, 67, 6, 195, 8, 83, 212, 20, 0, 7, 196, 12, 21, 1, 36, 66, 7, 195, 9, 84, 143, 66, 20, 7, 196, 4, 148, 143, 48, 66, 0, 8, 197, 100, 241, 213, 73, 64, 20, 8, 197, 76, 145, 206, 61, 32, 21, 12, 201, 76, 80, 207, 56, 67, 199, 20, 226, 84, 68, 9, 198, 12, 20, 148, 60, 48, 201, 20, 0, 9, 198, 80, 244, 130, 60, 193, 64, 21, 9, 198, 76, 147, 129, 28, 241, 192, 20, 9, 198, 56, 21, 70, 72, 17, 192, 65, 9, 198, 16, 147, 205, 20, 65, 64, 20, 0, 10, 199, 72, 19, 143, 12, 50, 9, 4, 20, 10, 199, 69, 80, 82, 80, 148, 143, 48, 67, 10, 199, 52, 86, 154, 4, 68, 137, 4, 67, 10, 199, 4, 209, 84, 72, 244, 9, 4, 68, 0, 9, 198, 77, 65, 83, 36, 51, 210, 66, 9, 198, 64, 84, 134, 21, 69, 0, 20, 7, 196, 52, 244, 137, 4, 66, 9, 198, 36, 229, 5, 72, 147, 210, 21, 7, 196, 8, 245, 15, 48, 65, 7, 196, 8, 148, 15, 48, 66, 0, 15, 69, 80, 84, 211, 21, 32, 47, 36, 87, 87, 6, 107, 51, 0, 8, 197, 80, 84, 211, 21, 32, 65, 8, 197, 76, 84, 211, 21, 32, 20, 8, 197, 28, 147, 204, 37, 64, 65, 9, 198, 24, 19, 148, 60, 48, 201, 20, 6, 195, 16, 241, 0, 20, 8, 197, 16, 80, 210, 21, 64, 20, 0, 9, 198, 92, 147, 1, 56, 245, 192, 67, 9, 198, 80, 84, 146, 20, 211, 212, 20, 9, 198, 77, 68, 143, 48, 17, 192, 65, 10, 198, 76, 83, 133, 28, 129, 64, 65, 20, 9, 198, 64, 244, 131, 36, 193, 64, 66, 9, 198, 64, 83, 147, 36, 193, 64, 20, 9, 198, 61, 37, 15, 56, 245, 128, 20, 9, 198, 52, 83, 147, 36, 193, 64, 66, 10, 198, 52, 83, 78, 60, 225, 64, 65, 20, 5, 194, 20, 208, 20, 13, 202, 12, 149, 137, 80, 21, 133, 12, 50, 9, 4, 20, 0, 10, 199, 69, 80, 68, 72, 148, 15, 48, 67, 10, 199, 64, 244, 148, 61, 35, 211, 20, 20, 10, 199, 64, 20, 211, 5, 65, 77, 64, 20, 6, 195, 16, 243, 0, 20, 8, 197, 13, 34, 83, 61, 0, 20, 0, 11, 200, 81, 85, 20, 61, 52, 15, 73, 64, 67, 7, 196, 64, 245, 133, 72, 65, 7, 196, 21, 35, 201, 56, 67, 7, 196, 12, 19, 143, 88, 65, 0, 6, 195, 72, 81, 206, 21, 8, 197, 64, 243, 73, 12, 80, 21, 8, 197, 60, 225, 83, 80, 16, 67, 8, 197, 48, 145, 213, 72, 80, 65, 9, 197, 16, 161, 77, 8, 80, 66, 20, 9, 198, 12, 243, 148, 20, 212, 0, 20, 8, 197, 12, 83, 9, 8, 80, 65, 9, 198, 12, 20, 21, 48, 85, 9, 21, 8, 197, 4, 224, 76, 60, 112, 66, 0, 9, 198, 77, 81, 15, 88, 84, 212, 20, 9, 198, 8, 83, 133, 88, 243, 0, 20, 9, 198, 5, 165, 5, 12, 130, 64, 20, 0, 10, 199, 80, 21, 82, 36, 19, 143, 88, 20, 12, 201, 64, 192, 78, 80, 17, 197, 56, 85, 0, 20, 10, 199, 61, 38, 137, 57, 83, 214, 36, 20, 10, 199, 13, 34, 83, 80, 241, 143, 72, 66, 0, 7, 196, 85, 52, 193, 56, 65, 7, 196, 72, 245, 15, 72, 20, 9, 198, 72, 16, 129, 72, 32, 82, 66, 11, 200, 64, 145, 86, 21, 1, 76, 4, 112, 67, 7, 196, 64, 20, 5, 72, 65, 11, 200, 52, 149, 15, 12, 243, 132, 72, 144, 20, 6, 195, 16, 246, 0, 20, 9, 198, 16, 147, 199, 56, 85, 0, 20, 0, 8, 197, 88, 243, 20, 72, 144, 21, 12, 201, 64, 144, 195, 60, 195, 205, 36, 226, 64, 67, 8, 197, 20, 227, 210, 52, 80, 21, 8, 197, 20, 36, 137, 16, 144, 20, 8, 197, 16, 241, 193, 48, 144, 65, 8, 197, 12, 19, 210, 48, 80, 65, 8, 197, 5, 3, 212, 20, 208, 20, 8, 197, 4, 229, 5, 52, 144, 20, 0, 9, 198, 72, 150, 154, 60, 194, 64, 66, 0, 10, 199, 60, 226, 67, 60, 99, 210, 36, 67, 19, 70, 24, 244, 148, 84, 149, 15, 81, 108, 14, 16, 47, 6, 40, 37, 47, 39, 0, 0, 12, 200, 77, 68, 129, 64, 245, 5, 72, 80, 67, 21, 0, 9, 198, 36, 68, 143, 48, 148, 201, 66, 6, 195, 21, 133, 18, 20, 0, 6, 195, 40, 84, 201, 20, 9, 198, 13, 85, 1, 56, 83, 192, 66, 9, 198, 9, 35, 206, 104, 83, 192, 65, 0, 0, 9, 198, 72, 149, 133, 72, 33, 82, 66, 7, 196, 61, 52, 197, 80, 20, 7, 196, 52, 245, 5, 48, 66, 7, 196, 36, 212, 5, 80, 65, 7, 196, 29, 35, 211, 36, 20, 11, 200, 12, 144, 204, 60, 52, 143, 77, 48, 67, 7, 196, 12, 84, 129, 52, 65, 8, 196, 8, 244, 132, 60, 66, 20, 7, 196, 8, 85, 5, 48, 20, 7, 196, 5, 35, 211, 36, 20, 9, 198, 4, 197, 9, 52, 85, 18, 66, 0, 0, 6, 195, 72, 241, 9, 20, 9, 198, 5, 32, 143, 72, 83, 192, 66, 0, 14, 3, 95, 51, 88, 47, 14, 16, 6, 36, 50, 47, 35, 0, 6, 195, 61, 48, 192, 20, 0, 12, 3, 95, 48, 67, 74, 6, 36, 50, 47, 39, 0, 7, 196, 72, 148, 15, 76, 20, 7, 196, 64, 84, 133, 104, 21, 7, 196, 56, 245, 5, 76, 20, 7, 196, 8, 21, 129, 72, 65, 12, 201, 5, 3, 195, 5, 64, 83, 80, 20, 201, 68, 13, 201, 4, 211, 137, 60, 49, 78, 80, 84, 201, 68, 20, 0, 8, 197, 64, 192, 67, 20, 32, 20, 8, 197, 52, 243, 15, 12, 128, 20, 8, 197, 52, 22, 154, 36, 224, 66, 8, 197, 8, 243, 132, 20, 224, 21, 0, 17, 70, 12, 83, 19, 37, 84, 192, 121, 107, 55, 87, 57, 6, 40, 87, 0, 9, 198, 76, 244, 18, 4, 34, 84, 66, 9, 198, 24, 84, 143, 12, 144, 64, 20, 9, 198, 12, 147, 133, 80, 80, 192, 20, 9, 198, 5, 85, 15, 9, 84, 192, 65, 0, 0, 6, 195, 88, 241, 11, 20, 9, 198, 81, 34, 85, 53, 98, 82, 66, 7, 196, 64, 244, 143, 76, 21, 11, 200, 52, 86, 154, 60, 114, 79, 72, 224, 21, 7, 196, 52, 18, 15, 56, 66, 0, 17, 4, 95, 48, 90, 51, 63, 37, 55, 55, 6, 36, 86, 37, 63, 37, 0, 12, 201, 72, 16, 132, 60, 208, 78, 104, 144, 64, 68, 8, 197, 21, 64, 78, 60, 192, 67, 0, 17, 4, 95, 48, 90, 50, 74, 36, 50, 47, 6, 36, 86, 37, 63, 37, 0, 6, 195, 76, 81, 5, 20, 9, 198, 72, 19, 80, 60, 195, 0, 21, 0, 6, 195, 73, 83, 212, 20, 0, 9, 198, 88, 145, 9, 29, 32, 70, 66, 15, 204, 72, 243, 66, 36, 53, 66, 61, 69, 1, 20, 68, 128, 20, 7, 196, 52, 244, 143, 48, 66, 14, 68, 12, 243, 21, 36, 49, 39, 55, 6, 40, 12, 37, 0, 7, 196, 12, 83, 148, 72, 20, 7, 196, 8, 20, 143, 48, 66, 0, 6, 195, 88, 243, 22, 20, 6, 195, 76, 83, 22, 21, 8, 197, 48, 19, 135, 85, 32, 66, 9, 197, 24, 244, 198, 61, 32, 65, 20, 9, 197, 24, 244, 134, 61, 32, 65, 21, 8, 197, 12, 243, 132, 61, 32, 20, 0, 9, 198, 64, 19, 12, 5, 33, 64, 65, 9, 198, 52, 243, 132, 60, 193, 128, 20, 9, 198, 48, 19, 132, 60, 193, 128, 20, 9, 198, 24, 243, 7, 61, 33, 64, 65, 9, 198, 5, 85, 15, 29, 37, 64, 68, 9, 198, 4, 229, 9, 61, 1, 64, 66, 9, 198, 4, 195, 5, 28, 129, 64, 65, 0, 6, 195, 89, 83, 212, 20, 6, 195, 65, 33, 68, 20, 10, 199, 64, 81, 15, 24, 147, 9, 4, 68, 6, 195, 57, 83, 212, 20, 10, 199, 44, 19, 80, 84, 50, 5, 4, 21, 0, 7, 196, 65, 33, 90, 104, 20, 6, 195, 65, 33, 71, 20, 7, 196, 61, 33, 201, 4, 65, 0, 10, 198, 65, 33, 83, 8, 149, 5, 65, 20, 12, 201, 64, 244, 148, 61, 97, 78, 21, 33, 64, 20, 6, 195, 57, 83, 214, 20, 9, 198, 36, 225, 137, 56, 149, 1, 68, 8, 197, 28, 130, 79, 81, 64, 21, 8, 197, 12, 244, 211, 61, 96, 65, 0, 6, 194, 48, 16, 72, 9, 16, 3, 95, 49, 57, 70, 37, 74, 35, 50, 50, 6, 39, 82, 36, 0, 9, 198, 84, 224, 78, 36, 209, 64, 66, 13, 202, 77, 3, 5, 56, 243, 69, 28, 19, 9, 4, 69, 6, 195, 52, 18, 5, 66, 9, 198, 5, 3, 195, 61, 1, 64, 66, 0, 14, 3, 95, 49, 56, 70, 37, 74, 6, 108, 47, 12, 39, 0, 6, 195, 88, 243, 12, 21, 6, 195, 88, 84, 208, 20, 10, 199, 72, 240, 149, 77, 65, 90, 104, 20, 6, 195, 52, 244, 212, 21, 10, 199, 52, 148, 207, 28, 147, 137, 4, 68, 0, 7, 196, 28, 146, 143, 56, 66, 7, 196, 12, 147, 137, 72, 65, 7, 196, 4, 197, 133, 60, 65, 0, 8, 197, 76, 243, 65, 48, 144, 65, 8, 197, 76, 100, 133, 28, 144, 20, 8, 197, 57, 83, 69, 72, 144, 65, 12, 201, 20, 193, 84, 81, 35, 206, 88, 243, 20, 68, 8, 197, 12, 19, 129, 64, 80, 65, 0, 9, 198, 52, 19, 5, 88, 243, 0, 20, 9, 198, 8, 148, 197, 57, 162, 64, 20, 0, 10, 199, 88, 19, 16, 4, 229, 5, 56, 21, 10, 199, 76, 145, 206, 61, 34, 76, 20, 67, 10, 199, 72, 147, 143, 64, 149, 5, 12, 20, 10, 199, 64, 145, 84, 72, 20, 143, 40, 20, 6, 195, 8, 243, 12, 21, 0, 7, 196, 88, 148, 5, 72, 65, 7, 196, 80, 245, 1, 56, 65, 7, 196, 76, 21, 1, 56, 65, 7, 196, 64, 84, 140, 20, 66, 7, 196, 48, 21, 5, 72, 65, 7, 196, 12, 19, 148, 84, 66, 0, 8, 197, 4, 229, 5, 72, 16, 66, 8, 197, 69, 81, 76, 48, 16, 72, 8, 197, 88, 149, 133, 72, 144, 65, 9, 197, 88, 145, 193, 56, 240, 67, 20, 8, 197, 76, 81, 9, 12, 144, 21, 9, 197, 65, 35, 212, 20, 240, 65, 20, 8, 197, 52, 81, 9, 84, 208, 20, 8, 197, 17, 81, 207, 56, 112, 20, 8, 197, 12, 246, 79, 80, 80, 20, 9, 197, 12, 84, 193, 72, 240, 67, 20, 8, 197, 5, 32, 143, 72, 80, 67, 8, 197, 4, 225, 197, 48, 144, 65, 0, 13, 3, 95, 49, 49, 6, 40, 50, 70, 37, 74, 37, 0, 9, 198, 76, 20, 141, 5, 66, 64, 65, 9, 198, 64, 149, 20, 60, 226, 64, 65, 6, 195, 52, 19, 5, 20, 6, 195, 52, 19, 5, 66, 9, 198, 28, 84, 212, 85, 34, 64, 65, 9, 198, 8, 21, 20, 21, 34, 64, 66, 9, 198, 8, 17, 206, 60, 194, 64, 66, 0, 16, 3, 95, 50, 56, 82, 6, 36, 50, 47, 6, 108, 47, 12, 39, 0, 12, 3, 95, 49, 48, 70, 37, 6, 36, 74, 37, 0, 10, 199, 77, 80, 129, 13, 21, 69, 60, 66, 14, 203, 64, 144, 83, 81, 34, 78, 61, 1, 78, 36, 16, 70, 9, 198, 61, 37, 15, 81, 66, 67, 20, 9, 198, 20, 193, 84, 81, 34, 67, 20, 0, 15, 3, 95, 49, 51, 47, 14, 16, 6, 36, 70, 37, 74, 37, 0, 6, 195, 88, 243, 7, 20, 11, 200, 72, 17, 9, 12, 241, 129, 56, 144, 67, 7, 196, 64, 148, 143, 64, 20, 7, 196, 52, 19, 149, 48, 66, 11, 200, 12, 130, 82, 60, 112, 76, 20, 240, 67, 0, 13, 3, 95, 49, 50, 70, 6, 39, 70, 37, 74, 37, 0, 9, 198, 16, 147, 211, 13, 84, 137, 66, 9, 198, 4, 229, 9, 80, 84, 201, 66, 8, 197, 4, 35, 205, 5, 48, 66, 0, 15, 3, 95, 49, 53, 49, 120, 6, 37, 63, 70, 37, 74, 37, 0, 9, 198, 77, 68, 133, 57, 83, 192, 20, 6, 195, 40, 243, 5, 20, 12, 201, 36, 68, 143, 20, 193, 84, 81, 34, 67, 20, 0, 18, 3, 95, 49, 52, 49, 120, 35, 47, 12, 6, 108, 51, 70, 37, 74, 37, 0, 10, 199, 52, 84, 197, 56, 50, 9, 52, 20, 0, 7, 196, 12, 244, 147, 4, 21, 17, 3, 95, 49, 55, 70, 37, 74, 35, 87, 12, 6, 107, 47, 12, 36, 0, 9, 198, 72, 243, 66, 60, 81, 18, 20, 15, 204, 64, 244, 148, 4, 83, 9, 12, 245, 20, 21, 34, 64, 20, 8, 196, 64, 85, 1, 48, 65, 20, 7, 196, 64, 84, 137, 52, 66, 9, 198, 64, 84, 137, 52, 85, 18, 66, 7, 196, 28, 148, 5, 80, 20, 7, 196, 12, 244, 5, 80, 20, 16, 204, 12, 243, 148, 4, 50, 9, 48, 243, 69, 81, 34, 64, 68, 20, 9, 198, 12, 20, 146, 60, 64, 78, 66, 0, 13, 3, 95, 49, 54, 87, 6, 36, 70, 37, 74, 37, 0, 9, 198, 76, 244, 137, 76, 243, 5, 66, 9, 198, 25, 37, 77, 20, 230, 137, 20, 9, 198, 12, 20, 146, 60, 48, 201, 20, 9, 198, 12, 19, 12, 36, 51, 5, 65, 0, 6, 195, 61, 52, 193, 21, 9, 198, 12, 21, 1, 48, 85, 20, 20, 0, 15, 3, 95, 55, 88, 87, 36, 47, 12, 6, 35, 50, 47, 35, 0, 0, 7, 196, 77, 81, 204, 36, 72, 7, 196, 72, 21, 5, 60, 65, 7, 196, 52, 241, 15, 12, 20, 7, 196, 48, 84, 18, 20, 20, 7, 196, 8, 21, 133, 72, 65, 0, 9, 198, 64, 83, 133, 48, 244, 5, 66, 9, 198, 4, 229, 9, 48, 244, 5, 66, 8, 197, 4, 225, 84, 60, 192, 67, 0, 6, 195, 88, 245, 9, 20, 9, 198, 88, 20, 137, 21, 64, 64, 68, 9, 198, 76, 147, 149, 21, 52, 192, 20, 9, 198, 65, 35, 212, 61, 66, 80, 66, 9, 198, 65, 33, 84, 21, 34, 84, 66, 9, 198, 61, 69, 1, 20, 68, 128, 20, 0, 9, 198, 65, 84, 144, 85, 33, 79, 66, 0, 8, 196, 80, 85, 1, 56, 65, 20, 7, 196, 76, 149, 1, 72, 66, 7, 196, 32, 84, 150, 20, 66, 0, 8, 197, 64, 83, 148, 60, 64, 20, 8, 197, 52, 84, 212, 60, 192, 21, 9, 198, 28, 19, 132, 60, 193, 137, 20, 8, 197, 12, 83, 148, 60, 192, 20, 0, 10, 198, 80, 83, 5, 80, 86, 20, 67, 20, 13, 67, 65, 37, 65, 48, 14, 16, 6, 40, 12, 35, 0, 9, 198, 64, 19, 16, 20, 36, 128, 65, 13, 202, 28, 194, 80, 80, 241, 15, 57, 66, 68, 36, 20, 9, 198, 16, 83, 79, 13, 34, 84, 66, 0, 8, 197, 37, 51, 212, 61, 0, 66, 8, 197, 21, 83, 79, 49, 0, 20, 0, 10, 198, 80, 83, 5, 29, 32, 70, 66, 20, 7, 196, 76, 81, 9, 4, 20, 7, 196, 76, 52, 143, 80, 20, 11, 200, 65, 35, 212, 61, 53, 5, 48, 192, 21, 7, 196, 61, 36, 207, 48, 21, 7, 196, 56, 84, 143, 48, 65, 7, 196, 12, 20, 143, 80, 20, 0, 9, 198, 24, 16, 197, 88, 21, 5, 76, 9, 198, 80, 83, 199, 56, 145, 5, 20, 9, 198, 37, 51, 195, 72, 21, 5, 66, 0, 10, 198, 56, 85, 20, 5, 33, 64, 65, 20, 9, 198, 52, 19, 12, 5, 33, 64, 65, 9, 198, 36, 228, 213, 9, 33, 64, 65, 9, 198, 25, 83, 133, 9, 33, 64, 65, 0, 10, 199, 76, 245, 20, 61, 3, 211, 80, 21, 10, 199, 56, 144, 207, 52, 81, 9, 4, 20, 0, 7, 196, 8, 244, 146, 60, 21, 11, 200, 64, 246, 154, 4, 225, 200, 21, 32, 66, 7, 196, 24, 244, 147, 20, 21, 7, 196, 24, 83, 20, 72, 21, 9, 198, 24, 20, 195, 21, 69, 0, 21, 9, 198, 24, 16, 195, 21, 69, 0, 21, 9, 198, 12, 243, 132, 61, 69, 0, 21, 0, 9, 198, 52, 150, 20, 20, 50, 9, 20, 9, 198, 36, 65, 78, 80, 149, 1, 68, 12, 201, 16, 144, 201, 5, 52, 197, 81, 65, 64, 20, 8, 197, 4, 226, 67, 21, 64, 20, 0, 5, 194, 52, 16, 8, 9, 198, 89, 83, 20, 85, 33, 64, 65, 9, 198, 85, 33, 84, 21, 33, 64, 67, 9, 198, 77, 64, 84, 21, 33, 64, 66, 9, 198, 76, 147, 131, 61, 1, 64, 65, 9, 198, 52, 85, 20, 21, 33, 64, 20, 9, 198, 52, 85, 5, 61, 33, 64, 66, 9, 198, 13, 32, 84, 21, 33, 64, 66, 0, 10, 199, 76, 52, 137, 88, 19, 137, 4, 67, 10, 199, 65, 34, 71, 36, 243, 137, 4, 67, 10, 199, 64, 192, 78, 5, 33, 201, 4, 66, 10, 199, 52, 144, 83, 80, 83, 137, 4, 68, 6, 195, 24, 243, 0, 20, 10, 199, 13, 34, 79, 28, 83, 137, 4, 68, 10, 199, 12, 20, 15, 48, 147, 133, 4, 67, 0, 10, 198, 76, 50, 5, 81, 66, 78, 65, 21, 7, 196, 56, 245, 133, 72, 65, 9, 198, 52, 19, 147, 84, 85, 0, 20, 10, 198, 16, 81, 137, 12, 149, 0, 65, 20, 7, 196, 4, 229, 5, 72, 65, 0, 9, 198, 81, 34, 70, 60, 115, 9, 20, 9, 198, 80, 83, 5, 24, 147, 13, 67, 8, 197, 76, 49, 80, 76, 144, 20, 8, 197, 72, 240, 130, 36, 16, 20, 8, 197, 52, 147, 69, 76, 144, 20, 8, 197, 52, 81, 15, 48, 80, 65, 6, 195, 24, 245, 0, 20, 12, 201, 24, 243, 148, 4, 224, 70, 72, 81, 4, 21, 8, 197, 12, 194, 80, 20, 240, 65, 0, 10, 198, 81, 33, 86, 21, 34, 64, 65, 20, 9, 198, 36, 228, 213, 9, 34, 64, 65, 9, 198, 36, 228, 197, 81, 66, 64, 20, 9, 198, 12, 244, 129, 105, 160, 84, 66, 0, 10, 199, 77, 64, 84, 60, 193, 5, 72, 20, 10, 199, 52, 147, 132, 5, 81, 193, 76, 65, 10, 199, 24, 147, 15, 13, 32, 84, 20, 66, 10, 199, 21, 38, 133, 28, 245, 137, 56, 67, 6, 195, 12, 84, 16, 21, 10, 199, 8, 19, 131, 5, 35, 212, 80, 21, 0, 7, 196, 76, 83, 154, 4, 8, 7, 196, 80, 21, 1, 72, 65, 7, 196, 80, 20, 9, 72, 65, 7, 196, 77, 65, 76, 48, 21, 8, 196, 76, 85, 133, 76, 65, 20, 11, 200, 76, 20, 146, 4, 49, 78, 36, 16, 20, 7, 196, 65, 35, 218, 36, 66, 7, 196, 64, 21, 5, 72, 65, 7, 196, 52, 83, 148, 20, 21, 7, 196, 36, 229, 133, 72, 21, 11, 200, 24, 245, 15, 72, 149, 15, 12, 48, 21, 7, 196, 12, 21, 5, 56, 21, 7, 196, 5, 52, 207, 72, 65, 9, 198, 4, 229, 9, 16, 245, 0, 66, 0, 8, 197, 60, 211, 137, 84, 208, 20, 9, 198, 60, 208, 89, 100, 17, 9, 66, 9, 198, 52, 147, 149, 80, 243, 9, 66, 9, 198, 28, 20, 129, 57, 162, 65, 67, 8, 197, 24, 83, 20, 72, 80, 21, 8, 197, 12, 20, 212, 36, 112, 66, 8, 197, 8, 21, 78, 20, 144, 67, 0, 9, 198, 81, 33, 86, 37, 34, 64, 65, 9, 198, 64, 244, 212, 21, 34, 64, 65, 9, 198, 64, 84, 133, 80, 243, 0, 66, 9, 198, 52, 86, 133, 57, 162, 64, 20, 0, 12, 3, 95, 50, 88, 82, 6, 36, 50, 47, 57, 0, 10, 199, 81, 33, 78, 80, 83, 142, 36, 20, 10, 199, 12, 130, 82, 61, 3, 212, 20, 20, 0, 7, 196, 80, 245, 5, 52, 20, 11, 200, 77, 84, 18, 20, 208, 90, 36, 16, 68, 7, 196, 64, 20, 143, 64, 20, 11, 200, 56, 85, 82, 61, 69, 5, 72, 144, 20, 11, 200, 12, 21, 129, 48, 48, 86, 36, 16, 68, 0, 12, 201, 80, 148, 193, 56, 245, 20, 21, 34, 64, 20, 12, 201, 64, 20, 129, 12, 85, 1, 52, 243, 0, 69, 12, 201, 48, 84, 9, 16, 245, 20, 21, 34, 64, 20, 9, 198, 4, 227, 137, 8, 19, 5, 66, 0, 9, 198, 76, 51, 210, 72, 85, 20, 20, 0, 6, 195, 65, 33, 84, 20, 10, 199, 64, 84, 137, 77, 64, 83, 36, 66, 10, 199, 52, 85, 1, 77, 64, 83, 36, 66, 10, 199, 37, 4, 15, 64, 245, 1, 52, 67, 11, 199, 36, 68, 143, 12, 81, 129, 48, 67, 20, 6, 195, 28, 85, 20, 20, 9, 198, 8, 83, 12, 61, 97, 83, 20, 0, 6, 195, 81, 33, 83, 20, 6, 195, 81, 33, 83, 20, 9, 198, 76, 50, 5, 48, 85, 18, 65, 7, 196, 64, 245, 1, 48, 65, 7, 196, 60, 97, 137, 16, 20, 12, 200, 29, 32, 78, 60, 195, 5, 73, 48, 67, 21, 0, 12, 201, 88, 83, 148, 72, 147, 15, 69, 83, 192, 66, 9, 198, 80, 243, 20, 20, 50, 9, 20, 9, 198, 52, 19, 15, 12, 50, 9, 20, 9, 198, 36, 225, 133, 16, 83, 5, 21, 6, 195, 12, 85, 18, 21, 0, 6, 195, 52, 147, 73, 66, 9, 198, 36, 225, 197, 57, 83, 192, 20, 0, 6, 195, 52, 144, 64, 72, 12, 201, 12, 149, 15, 76, 50, 5, 48, 85, 18, 67, 12, 201, 12, 130, 85, 16, 147, 5, 81, 65, 82, 20, 6, 195, 8, 240, 64, 20, 0, 7, 196, 28, 245, 20, 4, 21, 7, 196, 12, 244, 20, 36, 20, 7, 196, 8, 22, 129, 72, 66, 0, 8, 197, 25, 32, 71, 60, 192, 65, 0, 9, 198, 88, 19, 5, 72, 144, 64, 66, 9, 198, 76, 84, 85, 4, 196, 192, 66, 6, 195, 56, 243, 73, 20, 9, 198, 52, 20, 207, 88, 144, 64, 20, 10, 198, 28, 83, 205, 21, 68, 128, 66, 20, 9, 198, 21, 48, 77, 21, 68, 128, 66, 9, 198, 8, 243, 129, 72, 48, 68, 66, 6, 195, 8, 241, 77, 20, 0, 10, 199, 88, 84, 208, 5, 50, 65, 56, 68, 10, 199, 76, 96, 82, 24, 19, 12, 36, 67, 6, 195, 44, 80, 64, 21, 10, 199, 12, 20, 212, 20, 195, 15, 56, 67, 0, 14, 3, 95, 63, 63, 87, 6, 37, 63, 69, 39, 55, 39, 0, 7, 196, 12, 20, 146, 20, 66, 11, 200, 4, 224, 84, 72, 240, 195, 60, 192, 20, 0, 12, 201, 21, 53, 5, 57, 50, 77, 21, 68, 128, 67, 0, 9, 198, 88, 144, 193, 72, 144, 64, 67, 9, 198, 88, 149, 15, 72, 144, 64, 21, 10, 198, 80, 148, 133, 76, 144, 64, 66, 20, 13, 202, 52, 20, 147, 36, 51, 214, 21, 65, 82, 20, 20, 9, 198, 28, 19, 5, 72, 144, 64, 66, 9, 198, 21, 81, 197, 56, 144, 64, 20, 9, 198, 21, 81, 143, 72, 144, 64, 68, 0, 6, 195, 52, 145, 64, 72, 15, 3, 95, 52, 88, 49, 120, 35, 51, 6, 35, 50, 47, 35, 0, 10, 199, 77, 2, 78, 21, 67, 204, 36, 66, 14, 203, 64, 20, 129, 48, 193, 76, 21, 2, 80, 20, 64, 69, 10, 199, 52, 81, 193, 12, 243, 15, 56, 20, 0, 9, 198, 76, 244, 208, 21, 69, 0, 20, 6, 195, 60, 209, 71, 20, 7, 196, 16, 85, 143, 80, 20, 7, 196, 12, 244, 9, 4, 20, 0, 8, 197, 77, 2, 82, 37, 64, 65, 8, 197, 64, 193, 84, 81, 32, 20, 9, 198, 64, 145, 15, 12, 50, 9, 20, 9, 198, 25, 83, 7, 20, 230, 137, 20, 12, 201, 12, 20, 16, 20, 195, 1, 56, 144, 64, 68, 12, 201, 5, 163, 207, 77, 1, 82, 52, 144, 64, 69, 12, 201, 5, 84, 212, 72, 19, 1, 76, 144, 64, 68, 0, 9, 198, 64, 243, 12, 36, 49, 64, 20, 0, 10, 199, 61, 2, 83, 80, 241, 15, 52, 67, 6, 195, 60, 193, 192, 20, 6, 195, 56, 241, 64, 20, 6, 195, 56, 241, 64, 66, 0, 15, 204, 81, 35, 205, 8, 240, 201, 80, 244, 5, 56, 144, 64, 70, 7, 196, 48, 241, 15, 48, 65, 9, 198, 36, 209, 78, 60, 99, 210, 67, 7, 196, 24, 84, 137, 4, 65, 9, 198, 12, 19, 12, 36, 49, 66, 20, 0, 12, 201, 76, 245, 20, 61, 52, 5, 12, 145, 64, 20, 12, 201, 64, 243, 148, 5, 52, 201, 21, 97, 64, 20, 8, 197, 53, 83, 148, 5, 160, 66, 9, 197, 48, 85, 129, 57, 64, 65, 20, 9, 197, 12, 243, 80, 85, 64, 65, 20, 8, 197, 4, 213, 76, 21, 64, 20, 0, 6, 194, 48, 80, 72, 9, 9, 198, 52, 17, 15, 56, 145, 64, 67, 9, 198, 36, 228, 201, 20, 209, 64, 20, 9, 198, 16, 149, 20, 60, 225, 192, 20, 13, 202, 16, 17, 200, 21, 36, 143, 80, 148, 9, 4, 69, 0, 16, 3, 95, 53, 88, 74, 37, 50, 49, 120, 6, 35, 50, 47, 35, 0, 10, 199, 88, 145, 5, 60, 51, 9, 64, 68, 10, 199, 52, 145, 204, 36, 244, 137, 4, 67, 6, 195, 52, 16, 84, 66, 6, 195, 28, 243, 0, 20, 10, 199, 9, 34, 83, 28, 245, 137, 4, 20, 0, 7, 196, 77, 33, 84, 20, 72, 9, 198, 81, 32, 78, 76, 149, 0, 65, 7, 196, 77, 70, 76, 20, 66, 11, 200, 65, 34, 77, 60, 113, 78, 37, 64, 67, 9, 198, 64, 19, 13, 4, 227, 214, 20, 9, 198, 60, 36, 207, 48, 85, 0, 20, 7, 196, 48, 84, 18, 36, 20, 7, 196, 24, 21, 9, 12, 66, 0, 6, 195, 72, 245, 26, 20, 8, 197, 72, 20, 1, 12, 80, 66, 9, 198, 56, 244, 207, 12, 243, 73, 20, 6, 195, 48, 85, 0, 20, 6, 195, 28, 245, 0, 20, 12, 201, 24, 21, 20, 37, 52, 5, 12, 145, 64, 20, 8, 197, 20, 193, 85, 76, 144, 66, 10, 198, 12, 147, 9, 20, 114, 65, 67, 20, 8, 197, 12, 19, 69, 72, 144, 65, 8, 197, 4, 115, 206, 36, 16, 67, 10, 198, 4, 48, 78, 80, 241, 9, 67, 20, 0, 9, 198, 81, 33, 68, 36, 50, 64, 21, 9, 198, 12, 147, 9, 20, 114, 64, 20, 9, 198, 8, 240, 66, 16, 147, 0, 67, 9, 198, 4, 211, 210, 72, 82, 64, 67, 0, 9, 198, 24, 16, 197, 88, 19, 79, 76, 6, 195, 76, 82, 64, 72, 7, 195, 88, 242, 64, 76, 9, 7, 195, 56, 242, 64, 76, 9, 10, 199, 16, 244, 15, 48, 21, 143, 72, 21, 10, 199, 5, 36, 15, 13, 32, 84, 20, 66, 0, 12, 200, 5, 69, 18, 5, 97, 82, 76, 240, 28, 67, 8, 196, 76, 245, 5, 72, 66, 21, 11, 200, 60, 229, 15, 28, 83, 133, 76, 144, 67, 11, 200, 52, 19, 135, 36, 21, 15, 36, 16, 21, 11, 200, 52, 19, 9, 56, 51, 206, 36, 16, 68, 9, 198, 48, 19, 80, 72, 81, 0, 20, 11, 200, 29, 32, 77, 36, 224, 67, 20, 80, 67, 11, 200, 13, 33, 86, 4, 192, 207, 72, 80, 20, 7, 196, 12, 244, 148, 20, 21, 7, 196, 8, 245, 133, 76, 20, 8, 196, 8, 85, 15, 56, 66, 20, 0, 8, 197, 69, 81, 76, 48, 80, 72, 8, 197, 72, 17, 9, 12, 80, 66, 9, 198, 64, 20, 129, 80, 242, 65, 21, 8, 197, 25, 80, 211, 36, 16, 65, 8, 197, 25, 34, 71, 36, 16, 65, 9, 198, 24, 19, 1, 76, 50, 65, 67, 9, 198, 21, 84, 137, 80, 210, 65, 68, 8, 197, 5, 32, 207, 72, 80, 65, 9, 198, 5, 3, 208, 81, 145, 205, 66, 8, 197, 4, 193, 78, 36, 16, 20, 0, 9, 198, 16, 244, 143, 80, 82, 64, 67, 7, 195, 4, 147, 69, 66, 20, 0, 15, 3, 95, 54, 88, 87, 36, 87, 87, 6, 35, 50, 47, 35, 0, 10, 199, 88, 19, 4, 37, 51, 212, 80, 21, 10, 199, 80, 85, 18, 5, 3, 196, 20, 66, 6, 195, 76, 85, 20, 20, 6, 195, 76, 85, 20, 20, 6, 195, 8, 243, 64, 20, 0, 11, 200, 77, 2, 65, 56, 21, 15, 36, 16, 21, 11, 200, 64, 192, 83, 52, 241, 5, 76, 208, 20, 7, 196, 56, 80, 149, 48, 21, 11, 200, 52, 83, 1, 56, 51, 206, 36, 16, 68, 0, 0, 9, 198, 4, 32, 137, 4, 227, 192, 76, 6, 195, 12, 195, 197, 20, 18, 70, 4, 32, 129, 36, 227, 192, 35, 69, 12, 35, 6, 37, 12, 50, 39, 0, 0, 6, 195, 85, 5, 80, 65, 6, 195, 72, 245, 20, 21, 10, 199, 64, 84, 137, 25, 32, 83, 36, 66, 10, 199, 61, 37, 15, 12, 83, 148, 72, 20, 14, 203, 36, 229, 5, 48, 194, 71, 32, 83, 154, 36, 16, 20, 9, 198, 8, 20, 201, 48, 85, 83, 21, 6, 195, 4, 131, 192, 66, 0, 9, 198, 64, 20, 129, 52, 85, 18, 66, 11, 200, 64, 16, 137, 48, 195, 206, 37, 48, 20, 7, 196, 21, 34, 90, 104, 65, 7, 196, 20, 54, 133, 52, 20, 7, 196, 12, 21, 5, 80, 20, 7, 196, 8, 85, 9, 48, 21, 0, 6, 195, 28, 195, 194, 20, 0, 6, 194, 36, 192, 72, 9, 9, 198, 56, 144, 207, 16, 83, 64, 20, 9, 198, 20, 225, 137, 80, 85, 84, 67, 0, 12, 201, 65, 35, 198, 60, 225, 9, 52, 85, 18, 67, 0, 9, 198, 72, 85, 143, 49, 97, 82, 20, 9, 198, 64, 243, 3, 21, 97, 82, 66, 11, 200, 16, 243, 85, 76, 227, 214, 5, 48, 20, 9, 198, 12, 243, 132, 60, 210, 78, 66, 0, 9, 197, 64, 243, 12, 36, 224, 65, 20, 8, 197, 9, 32, 68, 4, 224, 65, 0, 6, 195, 61, 68, 133, 21, 9, 198, 52, 148, 197, 72, 144, 64, 66, 9, 198, 25, 83, 137, 88, 144, 64, 67, 9, 198, 21, 81, 15, 12, 144, 64, 20, 9, 198, 16, 21, 1, 72, 144, 64, 67, 9, 198, 13, 84, 129, 104, 144, 64, 67, 9, 198, 12, 19, 15, 72, 144, 64, 67, 9, 198, 5, 37, 5, 72, 144, 64, 66, 9, 198, 5, 35, 79, 56, 144, 64, 67, 9, 198, 4, 192, 129, 56, 144, 64, 67, 9, 198, 4, 32, 129, 104, 144, 64, 67, 0, 10, 199, 64, 83, 148, 5, 65, 85, 12, 67, 9, 198, 5, 33, 78, 4, 49, 79, 67, 0, 12, 201, 56, 144, 193, 72, 17, 213, 20, 228, 197, 21, 12, 201, 16, 85, 84, 21, 35, 211, 80, 243, 73, 20, 0, 8, 197, 81, 32, 80, 4, 224, 65, 8, 197, 80, 244, 144, 20, 64, 20, 8, 197, 76, 84, 137, 60, 192, 66, 8, 197, 28, 144, 86, 20, 224, 21, 8, 197, 12, 244, 146, 36, 64, 66, 9, 198, 12, 19, 16, 21, 53, 9, 67, 8, 197, 4, 229, 5, 56, 224, 21, 0, 9, 198, 76, 51, 210, 16, 144, 64, 66, 9, 198, 64, 243, 9, 104, 144, 64, 67, 9, 198, 56, 145, 197, 72, 144, 64, 66, 9, 198, 52, 21, 5, 72, 144, 64, 66, 9, 198, 48, 149, 1, 56, 144, 64, 67, 9, 198, 48, 81, 193, 104, 144, 64, 67, 9, 198, 36, 212, 12, 36, 50, 84, 66, 0, 14, 3, 95, 56, 88, 39, 47, 12, 6, 35, 50, 47, 35, 0, 6, 195, 104, 241, 64, 20, 0, 11, 200, 88, 19, 2, 72, 85, 133, 56, 224, 21, 11, 200, 64, 244, 148, 36, 48, 201, 60, 192, 67, 11, 200, 64, 21, 76, 36, 192, 84, 36, 224, 68, 9, 198, 12, 244, 208, 21, 69, 0, 20, 0, 12, 201, 96, 83, 143, 28, 195, 211, 76, 144, 64, 68, 12, 201, 80, 84, 141, 60, 51, 208, 64, 144, 64, 20, 12, 201, 76, 84, 211, 84, 241, 143, 8, 144, 64, 68, 8, 197, 61, 68, 129, 57, 64, 65, 8, 197, 21, 48, 69, 17, 32, 20, 12, 201, 4, 229, 9, 52, 21, 5, 72, 144, 64, 68, 0, 9, 198, 65, 33, 67, 60, 49, 64, 20, 10, 198, 5, 85, 15, 56, 241, 64, 67, 20, 0, 10, 199, 37, 51, 212, 72, 244, 9, 4, 68, 0, 7, 196, 80, 240, 137, 4, 66, 7, 196, 77, 1, 79, 80, 20, 7, 196, 52, 84, 131, 20, 66, 0, 8, 197, 80, 83, 80, 61, 32, 65, 8, 197, 80, 83, 80, 61, 32, 20, 8, 197, 5, 52, 207, 73, 64, 21, 0, 5, 194, 32, 240, 72, 6, 195, 52, 145, 73, 72, 9, 198, 76, 81, 213, 4, 49, 64, 66, 9, 198, 61, 33, 70, 36, 49, 64, 21, 6, 195, 56, 241, 77, 20, 0, 14, 3, 95, 57, 88, 50, 39, 82, 6, 35, 50, 47, 35, 0, 10, 199, 81, 32, 84, 80, 244, 137, 4, 67, 9, 198, 60, 198, 78, 80, 131, 211, 65, 10, 199, 48, 81, 193, 80, 244, 137, 4, 68, 0, 7, 196, 65, 33, 84, 20, 20, 11, 200, 12, 20, 212, 20, 195, 149, 61, 96, 20, 9, 198, 4, 194, 81, 84, 245, 0, 66, 0, 8, 197, 88, 84, 143, 48, 144, 65, 8, 197, 80, 244, 129, 12, 80, 66, 8, 197, 52, 244, 134, 20, 208, 20, 8, 197, 28, 244, 135, 36, 16, 65, 8, 197, 28, 144, 67, 60, 208, 65, 8, 197, 24, 244, 135, 36, 16, 65, 8, 197, 13, 80, 133, 8, 80, 20, 8, 197, 5, 35, 79, 16, 144, 20, 0, 9, 198, 80, 245, 15, 28, 243, 0, 67, 0, 10, 199, 81, 33, 83, 76, 85, 20, 20, 20, 11, 199, 12, 84, 150, 21, 65, 82, 36, 66, 20, 0, 11, 200, 84, 226, 86, 21, 36, 201, 80, 16, 69, 9, 198, 37, 4, 15, 48, 149, 0, 66, 9, 198, 12, 244, 9, 48, 245, 0, 20, 9, 198, 5, 50, 78, 80, 245, 0, 66, 0, 9, 197, 88, 81, 5, 72, 80, 66, 21, 8, 197, 56, 245, 77, 20, 16, 21, 10, 198, 56, 244, 150, 20, 114, 65, 66, 20, 8, 197, 48, 148, 19, 36, 16, 65, 12, 201, 16, 85, 84, 21, 35, 206, 60, 210, 64, 20, 0, 15, 3, 95, 63, 65, 55, 36, 47, 12, 6, 36, 12, 51, 35, 0, 9, 198, 85, 50, 71, 56, 243, 0, 67, 10, 198, 12, 241, 199, 36, 243, 0, 65, 20, 9, 198, 12, 85, 14, 36, 50, 64, 20, 9, 198, 12, 20, 137, 56, 243, 0, 66, 9, 198, 5, 4, 15, 28, 114, 64, 20, 0, 10, 199, 12, 83, 148, 72, 145, 149, 28, 66, 0, 9, 198, 37, 51, 204, 4, 35, 206, 20, 7, 196, 9, 37, 83, 36, 66, 0, 12, 201, 52, 243, 148, 20, 114, 79, 72, 114, 64, 21, 8, 197, 45, 32, 75, 61, 112, 66, 0, 0, 0, 8, 196, 72, 81, 15, 96, 66, 20, 0, 6, 195, 60, 209, 82, 65, 0, 9, 198, 12, 20, 5, 48, 195, 192, 21, 13, 202, 57, 80, 204, 20, 244, 201, 57, 65, 83, 36, 68, 0, 7, 194, 36, 224, 72, 28, 9, 18, 66, 36, 224, 37, 50, 15, 49, 120, 4, 37, 0, 8, 81, 99, 117, 105, 32, 5, 194, 60, 32, 20, 12, 201, 20, 225, 15, 76, 50, 5, 48, 85, 18, 67, 0, 9, 67, 92, 80, 128, 58, 107, 69, 0, 15, 204, 88, 83, 148, 37, 21, 65, 81, 68, 133, 76, 147, 64, 20, 12, 201, 76, 245, 20, 60, 147, 147, 36, 83, 69, 20, 6, 195, 72, 240, 128, 20, 6, 195, 8, 240, 128, 20, 0, 7, 196, 77, 83, 12, 4, 72, 6, 195, 77, 67, 205, 20, 12, 201, 76, 84, 211, 4, 229, 5, 76, 147, 64, 20, 0, 8, 197, 21, 48, 71, 60, 224, 66, 8, 197, 8, 83, 9, 4, 192, 67, 8, 197, 4, 113, 82, 60, 192, 66, 0, 9, 198, 76, 50, 76, 36, 20, 128, 67, 9, 198, 21, 32, 137, 88, 244, 128, 66, 10, 198, 20, 48, 197, 80, 84, 128, 66, 20, 9, 198, 12, 243, 15, 56, 144, 64, 67, 0, 6, 195, 77, 80, 64, 72, 15, 4, 95, 15, 7, 15, 39, 79, 6, 39, 12, 50, 36, 49, 0, 6, 195, 76, 80, 128, 20, 6, 195, 12, 80, 128, 20, 10, 199, 12, 20, 212, 20, 195, 1, 72, 67, 10, 199, 5, 32, 201, 64, 83, 1, 28, 67, 0, 7, 196, 85, 48, 133, 12, 20, 7, 196, 84, 226, 84, 4, 67, 6, 195, 76, 83, 137, 20, 11, 200, 64, 243, 9, 77, 66, 82, 60, 192, 68, 7, 196, 60, 131, 73, 12, 20, 0, 6, 195, 81, 35, 214, 20, 8, 197, 81, 33, 77, 36, 192, 66, 8, 197, 80, 84, 146, 20, 224, 21, 8, 197, 80, 20, 144, 4, 224, 66, 8, 197, 72, 17, 204, 4, 224, 66, 8, 197, 64, 192, 84, 36, 224, 65, 6, 195, 61, 35, 0, 21, 8, 197, 12, 20, 212, 36, 224, 65, 0, 6, 195, 65, 35, 211, 20, 9, 198, 56, 144, 207, 80, 84, 128, 66, 9, 198, 41, 80, 90, 20, 148, 128, 65, 0, 6, 195, 81, 35, 212, 20, 0, 11, 200, 80, 244, 131, 32, 144, 82, 60, 192, 67, 7, 196, 53, 84, 197, 36, 66, 11, 200, 36, 228, 197, 81, 66, 67, 36, 64, 68, 8, 196, 24, 84, 143, 16, 66, 20, 0, 14, 73, 4, 48, 197, 48, 84, 129, 80, 244, 128, 21, 0, 10, 6, 195, 65, 35, 214, 20, 6, 195, 65, 35, 214, 20, 8, 197, 52, 20, 195, 5, 32, 65, 8, 197, 20, 194, 83, 37, 32, 67, 8, 197, 16, 147, 69, 81, 32, 65, 8, 197, 5, 162, 77, 85, 64, 65, 0, 9, 198, 13, 35, 206, 61, 67, 208, 66, 12, 201, 12, 20, 212, 20, 197, 133, 80, 84, 133, 20, 0, 6, 195, 77, 81, 64, 72, 6, 195, 77, 67, 208, 20, 6, 195, 65, 35, 212, 20, 10, 199, 52, 19, 5, 8, 243, 7, 20, 20, 10, 199, 5, 144, 84, 60, 195, 1, 32, 68, 11, 199, 4, 48, 193, 16, 83, 73, 4, 67, 20, 0, 11, 200, 77, 1, 83, 76, 147, 69, 81, 32, 66, 7, 196, 61, 97, 83, 80, 20, 9, 198, 16, 243, 9, 4, 227, 214, 20, 8, 196, 12, 241, 201, 4, 65, 20, 9, 198, 5, 85, 15, 52, 86, 154, 20, 0, 8, 195, 56, 83, 0, 72, 28, 9, 9, 197, 80, 244, 148, 61, 32, 65, 21, 8, 197, 72, 145, 197, 81, 64, 20, 6, 195, 56, 83, 0, 21, 8, 197, 16, 145, 133, 81, 64, 20, 8, 197, 12, 20, 211, 5, 32, 65, 8, 197, 5, 32, 137, 81, 32, 65, 0, 7, 194, 56, 80, 72, 28, 9, 9, 66, 48, 144, 55, 37, 0, 76, 9, 6, 194, 36, 240, 76, 9, 0, 6, 195, 76, 85, 76, 66, 10, 199, 52, 243, 143, 80, 243, 137, 4, 68, 14, 203, 36, 51, 211, 36, 67, 196, 20, 48, 69, 17, 32, 20, 0, 7, 196, 77, 83, 12, 20, 72, 15, 68, 104, 18, 82, 4, 70, 86, 35, 6, 37, 12, 51, 35, 0, 9, 198, 88, 147, 129, 88, 147, 0, 67, 7, 196, 65, 33, 86, 36, 20, 7, 196, 65, 33, 83, 76, 20, 7, 196, 56, 83, 73, 12, 66, 8, 196, 44, 20, 15, 44, 66, 20, 6, 195, 28, 83, 137, 20, 11, 200, 20, 224, 78, 80, 147, 205, 21, 32, 68, 11, 200, 12, 130, 69, 76, 19, 149, 61, 96, 20, 0, 9, 198, 24, 16, 197, 88, 19, 143, 76, 8, 197, 25, 84, 143, 56, 240, 72, 8, 197, 81, 32, 66, 20, 16, 65, 8, 197, 72, 240, 195, 36, 16, 20, 8, 197, 64, 84, 131, 32, 80, 66, 8, 197, 24, 80, 195, 36, 16, 20, 8, 197, 12, 244, 195, 36, 16, 20, 8, 197, 12, 240, 195, 36, 16, 20, 8, 197, 8, 240, 195, 36, 16, 20, 8, 197, 5, 32, 193, 16, 80, 65, 8, 197, 4, 194, 83, 20, 144, 67, 0, 17, 206, 72, 243, 66, 36, 51, 211, 36, 67, 196, 20, 48, 69, 17, 32, 20, 9, 198, 36, 228, 207, 48, 149, 0, 66, 10, 198, 12, 19, 21, 52, 85, 0, 67, 21, 0, 6, 195, 77, 82, 64, 72, 10, 199, 104, 145, 207, 81, 65, 82, 36, 20, 10, 199, 80, 144, 133, 72, 144, 68, 20, 67, 10, 199, 76, 21, 143, 72, 115, 129, 56, 67, 10, 199, 36, 225, 129, 57, 66, 76, 20, 67, 10, 199, 5, 32, 201, 65, 33, 84, 20, 20, 0, 9, 198, 64, 84, 140, 60, 209, 78, 21, 7, 196, 48, 84, 143, 76, 21, 11, 200, 21, 35, 69, 56, 85, 84, 36, 48, 67, 9, 198, 8, 84, 148, 36, 243, 0, 66, 9, 198, 4, 84, 143, 76, 243, 0, 67, 0, 8, 197, 104, 19, 143, 8, 144, 20, 8, 197, 88, 83, 148, 72, 80, 20, 8, 197, 76, 147, 143, 64, 80, 20, 8, 197, 72, 84, 213, 52, 80, 67, 6, 195, 65, 35, 194, 20, 8, 197, 64, 84, 147, 36, 16, 65, 8, 197, 61, 53, 9, 48, 80, 66, 9, 197, 48, 83, 85, 72, 80, 65, 20, 9, 197, 36, 67, 206, 20, 240, 66, 20, 6, 195, 29, 81, 82, 21, 9, 197, 20, 225, 129, 76, 144, 65, 20, 9, 198, 13, 33, 84, 4, 49, 79, 66, 9, 197, 12, 20, 201, 56, 240, 67, 20, 8, 197, 12, 20, 137, 80, 80, 67, 8, 197, 8, 145, 78, 56, 144, 20, 0, 9, 198, 65, 33, 83, 80, 149, 0, 65, 14, 202, 32, 84, 129, 12, 193, 79, 64, 243, 9, 76, 67, 21, 6, 195, 17, 35, 199, 20, 9, 198, 4, 211, 210, 61, 50, 64, 21, 0, 9, 198, 64, 243, 9, 13, 35, 205, 66, 14, 203, 20, 193, 84, 81, 35, 205, 4, 115, 133, 80, 80, 20, 6, 195, 8, 243, 128, 20, 10, 199, 5, 3, 204, 48, 147, 133, 60, 67, 0, 15, 4, 95, 48, 77, 52, 69, 37, 55, 37, 6, 39, 50, 37, 0, 11, 200, 61, 37, 15, 16, 244, 211, 36, 16, 68, 6, 195, 56, 243, 133, 20, 11, 200, 25, 32, 78, 12, 130, 71, 36, 16, 66, 7, 196, 12, 149, 137, 80, 65, 6, 195, 12, 83, 133, 21, 11, 200, 9, 83, 206, 5, 36, 143, 80, 144, 20, 0, 0, 15, 4, 95, 48, 77, 50, 63, 37, 55, 37, 6, 39, 50, 37, 0, 6, 195, 56, 245, 83, 66, 9, 198, 48, 20, 9, 16, 83, 192, 66, 7, 195, 21, 3, 195, 65, 20, 9, 198, 20, 193, 84, 81, 35, 196, 20, 0, 16, 4, 95, 48, 77, 51, 63, 37, 55, 37, 6, 35, 51, 70, 37, 0, 6, 195, 76, 83, 128, 21, 11, 199, 64, 20, 133, 57, 65, 83, 36, 66, 20, 9, 198, 64, 19, 5, 52, 243, 133, 20, 6, 195, 56, 243, 128, 20, 6, 195, 24, 243, 128, 20, 9, 198, 24, 147, 5, 52, 243, 133, 20, 9, 198, 12, 194, 83, 80, 83, 133, 65, 6, 195, 12, 83, 128, 21, 6, 195, 8, 243, 132, 20, 0, 7, 196, 8, 240, 195, 4, 21, 7, 196, 12, 20, 21, 80, 66, 0, 12, 4, 95, 48, 77, 49, 63, 6, 37, 55, 35, 0, 7, 195, 21, 3, 206, 65, 20, 6, 195, 12, 83, 142, 21, 0, 15, 4, 95, 2, 18, 22, 69, 14, 16, 6, 36, 12, 82, 36, 0, 9, 198, 61, 69, 1, 28, 243, 128, 66, 5, 194, 60, 64, 20, 9, 198, 52, 19, 1, 64, 83, 128, 21, 0, 9, 198, 76, 147, 132, 72, 243, 69, 65, 11, 199, 16, 148, 195, 72, 81, 9, 80, 66, 21, 9, 198, 12, 19, 12, 37, 35, 197, 66, 0, 7, 196, 12, 244, 137, 104, 65, 0, 8, 197, 64, 83, 132, 60, 192, 20, 8, 197, 52, 81, 15, 48, 192, 21, 8, 197, 32, 145, 82, 60, 224, 66, 0, 9, 198, 105, 80, 195, 32, 84, 128, 65, 9, 198, 72, 84, 208, 60, 228, 192, 20, 9, 198, 36, 68, 143, 88, 244, 128, 66, 6, 195, 12, 84, 131, 21, 6, 195, 12, 84, 131, 21, 6, 195, 8, 244, 135, 21, 0, 6, 195, 24, 244, 128, 21, 9, 198, 13, 34, 83, 4, 244, 133, 66, 6, 195, 12, 84, 128, 21, 6, 195, 12, 84, 128, 21, 0, 6, 195, 76, 84, 129, 21, 7, 196, 77, 65, 80, 64, 21, 6, 195, 72, 244, 133, 20, 7, 196, 64, 16, 197, 12, 20, 6, 195, 52, 20, 129, 66, 7, 196, 24, 241, 204, 36, 20, 9, 198, 24, 147, 15, 77, 49, 78, 66, 7, 196, 16, 241, 204, 36, 20, 6, 195, 8, 244, 133, 20, 0, 8, 197, 88, 83, 148, 60, 192, 20, 12, 201, 69, 80, 68, 72, 147, 1, 80, 84, 128, 67, 8, 197, 16, 243, 13, 4, 224, 20, 8, 197, 12, 22, 154, 60, 192, 66, 0, 5, 194, 61, 64, 20, 9, 198, 52, 243, 143, 52, 84, 128, 66, 9, 198, 48, 83, 208, 60, 193, 0, 20, 0, 6, 195, 8, 245, 128, 20, 6, 195, 8, 245, 128, 20, 0, 7, 196, 76, 147, 73, 4, 65, 8, 196, 72, 240, 143, 80, 66, 20, 6, 195, 56, 245, 133, 20, 0, 8, 197, 76, 245, 137, 21, 64, 66, 12, 201, 53, 83, 20, 37, 3, 5, 96, 84, 128, 20, 12, 201, 20, 210, 67, 72, 148, 20, 60, 98, 84, 68, 0, 13, 202, 88, 19, 4, 60, 32, 137, 4, 65, 78, 20, 67, 9, 198, 76, 19, 134, 72, 243, 148, 66, 6, 195, 21, 3, 211, 20, 0, 10, 199, 88, 19, 12, 20, 195, 206, 28, 20, 6, 195, 56, 245, 128, 20, 9, 198, 52, 147, 12, 21, 50, 77, 20, 10, 199, 37, 3, 212, 21, 35, 73, 4, 68, 10, 199, 28, 83, 212, 21, 35, 73, 4, 68, 9, 198, 21, 2, 71, 72, 17, 133, 66, 0, 7, 196, 16, 148, 15, 48, 66, 6, 195, 8, 245, 133, 20, 0, 9, 197, 80, 83, 133, 9, 32, 65, 20, 9, 197, 48, 85, 129, 57, 160, 65, 20, 8, 197, 36, 225, 133, 81, 64, 20, 8, 197, 20, 97, 133, 81, 64, 20, 8, 197, 16, 84, 213, 21, 64, 20, 8, 197, 8, 84, 207, 105, 160, 21, 0, 6, 194, 52, 144, 76, 9, 9, 198, 65, 35, 201, 21, 69, 0, 20, 9, 198, 65, 35, 196, 61, 69, 0, 21, 6, 195, 21, 21, 79, 20, 9, 198, 12, 81, 129, 48, 241, 128, 66, 6, 195, 8, 244, 147, 21, 0, 10, 199, 77, 2, 78, 5, 166, 143, 48, 67, 10, 199, 64, 148, 143, 52, 19, 137, 4, 68, 10, 199, 28, 244, 135, 60, 230, 143, 48, 67, 6, 195, 28, 86, 128, 21, 9, 198, 12, 130, 65, 88, 20, 137, 65, 10, 199, 12, 20, 148, 5, 1, 83, 80, 21, 9, 198, 4, 224, 71, 72, 17, 133, 66, 0, 7, 131, 14, 195, 169, 8, 9, 7, 196, 36, 209, 78, 36, 20, 9, 198, 28, 192, 68, 36, 243, 0, 66, 0, 8, 197, 88, 84, 195, 36, 48, 66, 8, 197, 77, 3, 5, 56, 144, 20, 8, 197, 64, 84, 195, 32, 80, 20, 6, 195, 24, 244, 146, 21, 8, 197, 21, 35, 69, 80, 80, 20, 8, 197, 8, 148, 5, 16, 80, 65, 0, 9, 198, 81, 32, 86, 21, 50, 64, 20, 9, 198, 21, 129, 82, 21, 50, 64, 66, 0, 20, 71, 60, 194, 77, 64, 144, 68, 20, 39, 55, 37, 63, 48, 6, 37, 35, 70, 36, 0, 14, 203, 64, 149, 67, 12, 129, 80, 21, 33, 133, 81, 64, 20, 9, 198, 52, 144, 210, 61, 67, 205, 66, 10, 199, 5, 32, 207, 12, 244, 197, 56, 21, 0, 7, 196, 84, 35, 204, 16, 20, 9, 198, 72, 81, 199, 37, 49, 78, 21, 7, 196, 65, 33, 84, 80, 20, 11, 200, 52, 243, 148, 20, 193, 80, 72, 80, 20, 8, 196, 52, 17, 207, 28, 66, 20, 6, 195, 21, 21, 73, 20, 9, 198, 9, 85, 1, 56, 243, 0, 67, 0, 8, 197, 81, 34, 65, 16, 80, 65, 8, 197, 80, 21, 1, 72, 144, 65, 8, 197, 76, 147, 132, 36, 16, 66, 8, 197, 36, 228, 207, 52, 208, 21, 8, 197, 36, 225, 133, 72, 144, 65, 6, 195, 24, 244, 142, 21, 8, 197, 17, 34, 65, 16, 80, 65, 8, 197, 4, 210, 68, 20, 144, 67, 0, 9, 198, 80, 83, 195, 72, 149, 0, 66, 6, 195, 52, 20, 143, 20, 6, 195, 52, 20, 143, 66, 9, 198, 16, 147, 195, 21, 50, 64, 66, 9, 198, 12, 19, 69, 72, 245, 0, 20, 0, 6, 195, 104, 243, 128, 20, 10, 199, 80, 19, 12, 60, 98, 84, 20, 66, 10, 199, 12, 243, 80, 61, 50, 84, 20, 66, 0, 7, 196, 76, 19, 79, 4, 20, 7, 196, 73, 80, 133, 48, 66, 11, 200, 64, 245, 1, 52, 241, 193, 48, 80, 67, 9, 198, 37, 3, 195, 20, 229, 18, 20, 11, 200, 36, 209, 78, 61, 69, 5, 72, 144, 20, 11, 200, 21, 65, 82, 61, 69, 5, 72, 144, 20, 9, 198, 16, 148, 208, 72, 86, 154, 20, 11, 200, 8, 147, 211, 36, 229, 5, 76, 144, 67, 11, 200, 5, 34, 83, 80, 245, 5, 48, 80, 67, 0, 12, 201, 72, 244, 208, 36, 115, 9, 61, 50, 64, 21, 6, 195, 8, 244, 142, 21, 12, 201, 5, 32, 201, 16, 147, 195, 21, 50, 64, 68, 0, 12, 201, 12, 243, 148, 72, 245, 133, 73, 50, 65, 67, 0, 10, 199, 52, 20, 129, 80, 243, 133, 80, 20, 9, 198, 48, 83, 211, 80, 83, 133, 66, 9, 198, 16, 147, 143, 52, 83, 133, 66, 9, 198, 8, 243, 7, 32, 84, 137, 65, 0, 6, 195, 104, 243, 133, 21, 7, 195, 24, 244, 137, 20, 9, 7, 196, 76, 240, 195, 36, 20, 6, 195, 24, 244, 137, 66, 0, 12, 201, 16, 83, 65, 72, 85, 5, 36, 243, 128, 21, 0, 10, 198, 88, 145, 197, 88, 19, 128, 66, 20, 9, 198, 24, 83, 143, 52, 83, 128, 66, 9, 198, 21, 69, 1, 28, 243, 128, 66, 10, 198, 21, 4, 201, 48, 243, 128, 65, 20, 9, 198, 8, 20, 137, 80, 243, 128, 66, 0, 6, 195, 28, 80, 192, 20, 0, 7, 196, 81, 80, 133, 72, 65, 7, 196, 52, 242, 82, 20, 67, 13, 68, 12, 144, 78, 20, 74, 6, 37, 35, 50, 36, 0, 0, 8, 197, 81, 32, 70, 36, 192, 66, 8, 197, 13, 33, 83, 60, 192, 66, 8, 197, 12, 243, 132, 60, 224, 21, 0, 6, 195, 76, 80, 195, 21, 9, 198, 64, 193, 85, 72, 144, 192, 65, 6, 195, 12, 80, 195, 21, 0, 10, 199, 80, 83, 5, 48, 21, 143, 72, 21, 10, 199, 36, 229, 5, 73, 50, 78, 16, 67, 0, 6, 195, 12, 80, 193, 20, 7, 196, 88, 81, 204, 36, 20, 7, 196, 76, 241, 204, 36, 20, 11, 200, 60, 197, 18, 20, 240, 197, 4, 224, 68, 7, 196, 53, 81, 148, 36, 66, 7, 196, 48, 147, 73, 56, 65, 0, 12, 201, 76, 83, 142, 4, 50, 5, 72, 144, 128, 68, 7, 195, 20, 32, 78, 65, 20, 12, 201, 12, 243, 80, 72, 21, 133, 56, 66, 84, 67, 0, 6, 195, 60, 225, 71, 20, 9, 198, 36, 65, 78, 80, 144, 192, 20, 9, 198, 21, 64, 77, 64, 84, 192, 65, 9, 198, 4, 229, 9, 48, 240, 192, 66, 9, 198, 4, 225, 18, 20, 148, 192, 66, 0, 9, 198, 76, 19, 80, 21, 148, 133, 66, 6, 195, 72, 241, 192, 20, 0, 7, 196, 77, 83, 12, 60, 72, 0, 8, 197, 104, 83, 154, 21, 32, 65, 9, 198, 88, 147, 12, 5, 35, 211, 20, 8, 197, 9, 84, 130, 21, 32, 65, 8, 197, 8, 84, 130, 21, 32, 65, 0, 10, 198, 24, 145, 83, 60, 193, 64, 65, 20, 9, 198, 24, 145, 78, 36, 193, 64, 66, 0, 14, 5, 19, 1, 18, 195, 178, 87, 106, 34, 6, 108, 0, 72, 10, 199, 21, 5, 1, 72, 50, 9, 4, 67, 0, 7, 196, 76, 83, 79, 48, 65, 6, 195, 72, 129, 65, 21, 7, 196, 48, 81, 199, 20, 21, 0, 8, 197, 76, 48, 80, 37, 64, 65, 6, 195, 64, 83, 0, 21, 6, 195, 64, 83, 0, 21, 9, 197, 52, 245, 13, 61, 64, 66, 20, 12, 201, 21, 2, 71, 48, 245, 20, 36, 65, 64, 20, 8, 197, 12, 19, 1, 9, 32, 65, 8, 197, 4, 112, 80, 37, 64, 66, 0, 9, 198, 5, 100, 133, 8, 33, 64, 72, 9, 198, 88, 84, 135, 36, 225, 64, 21, 9, 198, 76, 245, 20, 36, 193, 64, 66, 9, 198, 24, 149, 15, 24, 17, 192, 66, 9, 198, 16, 19, 79, 12, 193, 64, 65, 9, 198, 12, 84, 131, 36, 225, 64, 21, 9, 198, 12, 20, 205, 20, 225, 64, 65, 9, 198, 4, 227, 198, 20, 193, 64, 66, 0, 6, 195, 64, 81, 0, 20, 9, 198, 16, 144, 71, 56, 244, 201, 66, 0, 11, 200, 88, 84, 212, 20, 224, 78, 61, 96, 20, 7, 196, 76, 145, 193, 72, 65, 7, 196, 64, 145, 68, 20, 20, 11, 200, 12, 148, 131, 60, 49, 78, 81, 32, 20, 6, 195, 4, 34, 65, 66, 0, 8, 197, 5, 97, 83, 76, 80, 72, 9, 197, 88, 83, 133, 80, 144, 65, 20, 8, 197, 76, 241, 204, 36, 16, 20, 8, 197, 76, 19, 5, 52, 144, 20, 8, 197, 72, 144, 197, 72, 48, 21, 8, 197, 64, 244, 212, 84, 208, 65, 8, 197, 36, 208, 143, 12, 48, 21, 8, 197, 36, 68, 143, 64, 80, 65, 8, 197, 28, 83, 133, 88, 80, 20, 8, 197, 28, 19, 69, 80, 80, 20, 8, 197, 25, 81, 193, 12, 80, 66, 8, 197, 21, 34, 84, 20, 208, 20, 8, 197, 4, 193, 83, 76, 144, 20, 8, 197, 4, 115, 129, 80, 144, 65, 0, 9, 198, 88, 83, 133, 72, 66, 64, 67, 9, 198, 85, 52, 197, 28, 194, 64, 20, 9, 198, 80, 85, 84, 60, 226, 64, 65, 9, 198, 77, 3, 5, 56, 66, 68, 20, 9, 198, 28, 149, 71, 28, 147, 204, 65, 9, 198, 21, 2, 83, 60, 66, 64, 20, 9, 198, 5, 4, 15, 76, 149, 0, 66, 0, 9, 198, 104, 243, 198, 36, 194, 65, 68, 10, 199, 72, 144, 195, 60, 35, 206, 36, 20, 10, 199, 12, 83, 148, 85, 34, 80, 20, 66, 0, 8, 196, 64, 83, 206, 36, 65, 9, 11, 200, 80, 20, 132, 36, 116, 129, 16, 144, 66, 8, 196, 76, 83, 73, 56, 65, 21, 7, 196, 64, 19, 73, 72, 66, 6, 195, 56, 245, 137, 20, 7, 196, 56, 243, 73, 56, 65, 7, 196, 52, 16, 193, 12, 66, 11, 200, 8, 20, 137, 80, 243, 133, 76, 144, 20, 0, 8, 197, 76, 83, 80, 72, 80, 20, 6, 195, 72, 246, 154, 21, 8, 197, 65, 33, 77, 36, 16, 65, 9, 197, 48, 83, 85, 72, 144, 65, 20, 8, 197, 32, 243, 143, 72, 80, 67, 8, 197, 25, 84, 148, 20, 144, 66, 8, 197, 24, 83, 142, 20, 48, 20, 8, 197, 8, 20, 212, 36, 16, 65, 8, 197, 4, 194, 78, 20, 16, 66, 0, 9, 198, 64, 149, 5, 28, 194, 64, 20, 12, 201, 52, 144, 210, 60, 49, 70, 4, 194, 65, 69, 0, 6, 195, 52, 147, 192, 72, 9, 198, 76, 147, 148, 60, 226, 65, 67, 9, 198, 76, 19, 13, 60, 66, 65, 67, 10, 199, 20, 195, 5, 56, 144, 200, 20, 20, 0, 9, 198, 81, 33, 86, 37, 48, 78, 67, 12, 200, 16, 147, 143, 12, 81, 129, 48, 144, 67, 20, 0, 0, 22, 4, 95, 3, 9, 18, 74, 37, 38, 14, 16, 49, 39, 50, 81, 55, 6, 36, 87, 87, 39, 0, 0, 9, 198, 105, 80, 195, 32, 84, 137, 65, 10, 199, 77, 80, 131, 60, 228, 195, 36, 20, 9, 198, 8, 147, 1, 80, 84, 137, 66, 0, 7, 196, 64, 241, 199, 36, 20, 9, 198, 8, 240, 195, 4, 225, 82, 21, 0, 8, 133, 19, 1, 18, 195, 160, 72, 9, 198, 76, 20, 146, 4, 37, 83, 65, 0, 9, 198, 5, 100, 133, 52, 211, 192, 72, 9, 198, 76, 20, 133, 52, 211, 192, 72, 10, 198, 60, 210, 67, 72, 243, 128, 65, 20, 5, 194, 60, 128, 20, 6, 195, 8, 244, 195, 20, 0, 10, 67, 36, 20, 192, 37, 35, 86, 0, 65, 6, 195, 72, 244, 192, 20, 10, 199, 52, 85, 1, 8, 243, 9, 80, 67, 6, 195, 8, 244, 192, 20, 0, 7, 196, 52, 86, 9, 12, 21, 0, 8, 197, 24, 19, 3, 60, 224, 66, 0, 9, 198, 81, 34, 67, 32, 80, 192, 20, 9, 198, 13, 80, 213, 72, 34, 84, 66, 9, 198, 4, 229, 9, 28, 20, 192, 67, 0, 10, 199, 80, 148, 129, 64, 145, 68, 36, 20, 10, 199, 16, 241, 5, 12, 17, 207, 56, 67, 6, 195, 12, 84, 192, 20, 10, 199, 12, 20, 193, 48, 35, 210, 20, 66, 9, 198, 5, 37, 5, 24, 144, 197, 21, 6, 195, 4, 34, 84, 65, 0, 7, 196, 76, 51, 208, 4, 21, 6, 131, 95, 195, 185, 43, 7, 196, 84, 192, 197, 72, 65, 7, 196, 76, 16, 200, 4, 66, 6, 195, 72, 244, 197, 66, 7, 196, 72, 83, 79, 72, 65, 7, 196, 64, 193, 66, 20, 20, 7, 196, 60, 48, 200, 36, 20, 7, 196, 52, 16, 193, 60, 66, 7, 196, 12, 16, 193, 60, 66, 0, 8, 197, 64, 20, 212, 20, 224, 65, 9, 198, 60, 211, 199, 20, 225, 79, 67, 8, 197, 24, 16, 137, 60, 192, 66, 0, 9, 198, 76, 83, 65, 24, 244, 128, 66, 9, 198, 36, 115, 137, 80, 244, 128, 65, 0, 13, 4, 95, 19, 20, 11, 69, 6, 35, 51, 16, 35, 0, 12, 201, 9, 35, 195, 12, 244, 212, 20, 195, 0, 21, 0, 7, 196, 76, 80, 207, 48, 20, 7, 196, 64, 240, 207, 48, 66, 0, 14, 4, 95, 1, 3, 21, 35, 49, 6, 40, 12, 47, 39, 0, 6, 131, 95, 195, 178, 43, 8, 197, 64, 84, 132, 37, 64, 65, 6, 195, 28, 83, 214, 65, 0, 6, 131, 95, 195, 179, 43, 9, 198, 100, 19, 213, 56, 65, 64, 68, 9, 198, 21, 65, 79, 12, 193, 64, 66, 9, 198, 8, 21, 9, 12, 193, 64, 65, 0, 10, 199, 64, 81, 9, 5, 68, 137, 4, 67, 0, 9, 198, 81, 84, 130, 60, 96, 78, 67, 7, 196, 72, 83, 79, 80, 20, 6, 195, 12, 84, 201, 20, 7, 196, 5, 33, 5, 4, 65, 7, 196, 4, 225, 207, 48, 66, 0, 8, 197, 77, 64, 83, 21, 32, 21, 12, 201, 76, 83, 80, 72, 85, 133, 72, 65, 64, 21, 6, 195, 48, 243, 0, 20, 0, 6, 194, 48, 240, 72, 9, 9, 198, 77, 81, 134, 21, 69, 0, 20, 9, 198, 76, 147, 132, 60, 225, 64, 65, 9, 198, 12, 194, 77, 20, 225, 64, 65, 0, 6, 131, 95, 195, 172, 43, 10, 199, 80, 83, 195, 72, 22, 137, 4, 68, 6, 195, 48, 241, 0, 20, 9, 198, 25, 37, 84, 80, 244, 201, 20, 10, 198, 12, 147, 133, 8, 246, 0, 67, 20, 6, 195, 12, 84, 212, 21, 10, 199, 5, 84, 212, 72, 20, 201, 4, 67, 10, 199, 5, 37, 5, 52, 148, 201, 4, 67, 0, 12, 201, 88, 147, 12, 5, 52, 5, 12, 147, 211, 21, 7, 196, 52, 16, 197, 72, 65, 7, 196, 8, 16, 197, 56, 21, 0, 8, 197, 69, 81, 83, 80, 16, 72, 8, 197, 88, 149, 129, 12, 80, 66, 8, 197, 65, 35, 197, 52, 144, 20, 8, 197, 56, 80, 195, 32, 144, 20, 8, 197, 52, 83, 133, 12, 208, 20, 8, 197, 24, 148, 195, 32, 144, 66, 8, 197, 21, 52, 197, 72, 80, 20, 8, 197, 16, 144, 68, 20, 208, 20, 8, 197, 12, 240, 195, 32, 144, 20, 9, 197, 8, 241, 77, 36, 16, 66, 20, 8, 197, 5, 81, 1, 12, 80, 67, 8, 197, 5, 49, 80, 76, 144, 20, 8, 197, 4, 212, 5, 72, 80, 66, 8, 197, 4, 195, 21, 12, 80, 65, 0, 10, 198, 76, 84, 85, 4, 226, 64, 65, 20, 9, 198, 72, 83, 211, 80, 21, 0, 66, 9, 198, 64, 84, 20, 36, 66, 64, 20, 9, 198, 36, 225, 207, 8, 34, 64, 20, 0, 14, 4, 95, 18, 14, 7, 35, 50, 6, 36, 55, 55, 39, 0, 6, 131, 95, 195, 168, 43, 10, 199, 81, 33, 80, 64, 145, 68, 20, 20, 10, 199, 76, 16, 197, 72, 67, 212, 20, 20, 9, 198, 52, 84, 211, 20, 226, 65, 20, 6, 195, 48, 245, 0, 20, 9, 198, 36, 98, 71, 20, 226, 65, 68, 9, 198, 16, 144, 82, 12, 130, 65, 67, 10, 199, 12, 244, 148, 20, 229, 79, 88, 20, 10, 199, 8, 244, 195, 36, 208, 78, 36, 66, 10, 199, 5, 32, 200, 36, 209, 68, 20, 20, 0, 6, 131, 95, 195, 169, 43, 7, 196, 48, 147, 79, 56, 66, 6, 195, 28, 84, 213, 66, 12, 201, 12, 20, 148, 36, 192, 71, 36, 225, 79, 68, 9, 198, 5, 84, 212, 72, 19, 0, 67, 0, 8, 197, 4, 115, 211, 80, 16, 65, 8, 197, 88, 244, 212, 72, 16, 72, 8, 197, 56, 244, 212, 72, 16, 72, 9, 198, 80, 19, 135, 4, 226, 67, 67, 8, 197, 61, 33, 9, 56, 80, 21, 8, 197, 52, 242, 5, 48, 144, 21, 8, 197, 20, 195, 209, 84, 144, 20, 8, 197, 4, 227, 205, 20, 144, 67, 0, 9, 198, 72, 145, 15, 48, 98, 64, 20, 9, 198, 72, 85, 15, 72, 34, 68, 21, 9, 198, 5, 37, 5, 72, 147, 204, 67, 0, 29, 67, 33, 69, 16, 6, 35, 49, 12, 35, 47, 4, 37, 12, 47, 4, 37, 12, 48, 6, 37, 12, 10, 0, 81, 58, 47, 47, 32, 9, 198, 72, 20, 19, 60, 66, 65, 67, 9, 198, 24, 149, 15, 24, 17, 201, 66, 10, 199, 12, 20, 142, 37, 99, 210, 36, 66, 0, 7, 196, 72, 241, 201, 80, 65, 7, 196, 24, 16, 197, 80, 20, 7, 196, 16, 145, 67, 36, 20, 11, 200, 12, 83, 148, 61, 2, 69, 16, 144, 20, 6, 195, 8, 244, 201, 20, 7, 196, 4, 192, 193, 52, 65, 12, 200, 4, 112, 77, 20, 227, 143, 56, 80, 67, 20, 0, 0, 0, 6, 131, 95, 195, 160, 43, 9, 198, 76, 19, 21, 16, 80, 201, 20, 9, 198, 52, 85, 1, 80, 84, 201, 66, 0, 12, 68, 48, 81, 199, 36, 55, 36, 73, 6, 37, 0, 10, 198, 104, 84, 16, 20, 194, 78, 65, 20, 7, 196, 76, 81, 199, 36, 20, 7, 196, 72, 16, 197, 52, 20, 7, 196, 52, 241, 199, 36, 20, 0, 9, 197, 52, 82, 206, 21, 48, 66, 20, 6, 195, 5, 32, 66, 65, 0, 9, 198, 64, 148, 137, 80, 243, 192, 66, 9, 198, 56, 20, 195, 61, 53, 0, 21, 0, 10, 199, 64, 148, 201, 77, 68, 129, 80, 66, 10, 199, 24, 147, 15, 77, 68, 129, 80, 66, 9, 198, 9, 34, 78, 16, 148, 201, 65, 0, 6, 195, 20, 32, 133, 72, 7, 196, 104, 17, 193, 72, 65, 7, 196, 80, 83, 80, 36, 20, 6, 195, 76, 241, 9, 20, 9, 198, 64, 20, 129, 29, 32, 70, 66, 6, 195, 60, 115, 9, 20, 7, 196, 24, 145, 193, 72, 65, 6, 195, 4, 32, 129, 66, 0, 8, 197, 77, 2, 78, 60, 192, 65, 0, 9, 198, 8, 20, 130, 21, 32, 64, 66, 9, 198, 77, 3, 210, 60, 98, 84, 66, 12, 201, 64, 84, 132, 5, 49, 5, 24, 241, 213, 20, 9, 198, 48, 144, 133, 73, 64, 64, 67, 9, 198, 12, 148, 18, 21, 52, 192, 20, 0, 7, 195, 21, 32, 64, 72, 9, 9, 198, 88, 84, 148, 20, 36, 133, 65, 6, 195, 64, 83, 12, 21, 0, 6, 195, 77, 83, 201, 72, 9, 198, 64, 243, 9, 77, 65, 78, 66, 7, 196, 61, 33, 129, 56, 65, 7, 196, 60, 49, 65, 56, 66, 7, 196, 52, 240, 200, 36, 20, 7, 196, 28, 129, 68, 36, 20, 11, 200, 21, 33, 207, 77, 65, 82, 60, 192, 68, 8, 196, 8, 145, 206, 20, 66, 20, 7, 196, 4, 225, 207, 72, 65, 7, 196, 4, 192, 207, 88, 20, 0, 8, 197, 76, 48, 84, 60, 192, 65, 12, 201, 65, 35, 212, 60, 49, 82, 20, 36, 128, 67, 0, 9, 198, 88, 84, 148, 20, 36, 128, 65, 0, 10, 199, 52, 245, 15, 13, 35, 211, 76, 67, 0, 7, 196, 64, 145, 67, 20, 20, 7, 196, 61, 33, 133, 36, 66, 6, 195, 5, 33, 65, 65, 0, 12, 201, 52, 19, 5, 88, 243, 5, 57, 160, 64, 8, 8, 197, 88, 84, 195, 61, 96, 65, 6, 195, 21, 33, 66, 65, 9, 197, 8, 244, 198, 61, 32, 65, 20, 0, 23, 4, 95, 1, 3, 50, 70, 6, 39, 48, 12, 37, 38, 39, 23, 35, 49, 6, 40, 12, 47, 39, 0, 9, 198, 76, 83, 137, 61, 33, 64, 20, 9, 198, 52, 20, 141, 61, 33, 64, 65, 9, 198, 16, 243, 3, 21, 69, 0, 21, 9, 198, 16, 144, 66, 21, 65, 64, 20, 0, 10, 199, 61, 37, 15, 64, 81, 9, 4, 68, 0, 6, 195, 20, 32, 137, 72, 7, 196, 64, 145, 68, 72, 20, 11, 200, 5, 32, 201, 88, 84, 195, 61, 96, 67, 0, 6, 195, 52, 243, 0, 20, 6, 195, 52, 243, 0, 20, 8, 197, 52, 20, 141, 5, 32, 65, 8, 197, 13, 34, 67, 21, 64, 20, 0, 9, 198, 5, 100, 133, 77, 65, 64, 72, 9, 198, 17, 84, 129, 57, 65, 64, 8, 9, 198, 81, 32, 68, 61, 69, 0, 21, 6, 195, 72, 244, 211, 21, 6, 195, 72, 244, 211, 21, 0, 9, 198, 77, 66, 71, 52, 21, 5, 65, 6, 195, 72, 244, 208, 20, 6, 195, 52, 241, 0, 20, 6, 195, 52, 241, 0, 20, 10, 199, 37, 51, 208, 76, 81, 137, 4, 68, 9, 198, 20, 228, 195, 32, 81, 5, 67, 9, 198, 12, 243, 85, 56, 149, 1, 68, 0, 7, 196, 76, 144, 77, 60, 72, 8, 196, 76, 244, 18, 4, 76, 28, 7, 196, 80, 83, 80, 20, 20, 9, 198, 76, 243, 1, 72, 243, 0, 67, 9, 198, 64, 243, 9, 28, 19, 0, 66, 7, 196, 52, 241, 193, 56, 65, 6, 195, 21, 33, 77, 65, 0, 8, 197, 4, 195, 15, 72, 16, 21, 8, 197, 5, 97, 83, 76, 144, 72, 8, 197, 81, 32, 66, 36, 16, 66, 8, 197, 76, 83, 73, 16, 144, 67, 9, 197, 76, 19, 15, 52, 80, 67, 20, 8, 197, 65, 35, 206, 4, 240, 20, 6, 195, 20, 32, 146, 20, 8, 197, 12, 20, 129, 12, 240, 67, 6, 195, 5, 33, 78, 21, 9, 198, 4, 193, 197, 9, 34, 67, 20, 0, 9, 198, 76, 147, 5, 57, 162, 64, 20, 6, 195, 76, 84, 211, 20, 9, 198, 52, 243, 143, 64, 244, 212, 21, 9, 198, 36, 228, 85, 36, 85, 0, 20, 9, 198, 8, 84, 130, 21, 34, 64, 65, 0, 7, 195, 21, 34, 64, 72, 9, 10, 199, 56, 242, 67, 5, 69, 1, 72, 67, 6, 195, 52, 245, 0, 20, 6, 195, 52, 245, 0, 20, 6, 195, 12, 243, 12, 21, 6, 195, 12, 243, 12, 21, 10, 199, 12, 20, 193, 80, 83, 143, 88, 20, 9, 198, 12, 20, 135, 20, 114, 5, 20, 10, 199, 12, 20, 1, 56, 227, 210, 36, 66, 9, 198, 4, 225, 137, 64, 243, 9, 66, 0, 7, 196, 76, 147, 85, 56, 66, 7, 196, 72, 85, 143, 12, 65, 9, 198, 52, 85, 1, 56, 243, 0, 67, 7, 196, 8, 86, 154, 36, 20, 7, 196, 4, 192, 207, 72, 66, 0, 8, 197, 64, 84, 211, 36, 208, 20, 9, 198, 52, 20, 141, 61, 33, 79, 66, 8, 197, 12, 130, 69, 76, 80, 20, 8, 197, 5, 160, 82, 36, 16, 67, 8, 197, 5, 96, 82, 36, 16, 67, 8, 197, 5, 37, 5, 52, 144, 20, 8, 197, 4, 224, 84, 20, 208, 20, 0, 9, 198, 5, 100, 133, 77, 66, 64, 72, 9, 198, 77, 1, 84, 81, 34, 64, 20, 14, 202, 56, 16, 149, 12, 241, 15, 56, 244, 207, 72, 68, 20, 9, 198, 52, 243, 132, 61, 98, 64, 67, 0, 12, 201, 76, 19, 80, 36, 84, 132, 5, 33, 78, 21, 9, 198, 65, 35, 199, 20, 226, 69, 20, 9, 198, 13, 35, 195, 21, 98, 65, 67, 9, 198, 12, 244, 132, 60, 115, 9, 20, 0, 7, 196, 76, 144, 78, 60, 72, 11, 200, 52, 19, 9, 56, 53, 79, 72, 80, 20, 11, 200, 48, 84, 212, 72, 145, 207, 56, 144, 66, 12, 201, 24, 245, 15, 20, 193, 84, 81, 34, 67, 20, 7, 196, 24, 81, 193, 80, 65, 7, 196, 21, 81, 5, 52, 20, 6, 195, 12, 243, 1, 66, 13, 68, 12, 144, 78, 60, 74, 6, 37, 35, 50, 39, 0, 7, 196, 9, 81, 129, 48, 65, 0, 0, 0, 6, 195, 77, 83, 192, 72, 9, 198, 81, 34, 83, 12, 83, 5, 65, 6, 195, 76, 243, 4, 20, 9, 198, 52, 20, 211, 20, 230, 137, 20, 10, 198, 37, 51, 211, 12, 83, 5, 66, 20, 9, 198, 24, 80, 130, 72, 147, 5, 66, 10, 199, 20, 51, 211, 37, 53, 5, 52, 20, 9, 198, 5, 4, 18, 60, 48, 201, 20, 0, 7, 196, 76, 17, 193, 52, 65, 7, 196, 64, 81, 199, 36, 20, 7, 196, 61, 32, 137, 80, 65, 7, 196, 4, 225, 197, 48, 65, 7, 196, 4, 225, 197, 48, 65, 0, 0, 0, 10, 199, 65, 34, 86, 36, 193, 71, 36, 20, 9, 198, 64, 147, 143, 12, 50, 9, 20, 10, 199, 8, 17, 206, 61, 33, 71, 36, 20, 0, 7, 196, 88, 84, 18, 20, 20, 8, 196, 60, 96, 78, 80, 65, 20, 7, 196, 24, 147, 206, 16, 21, 7, 196, 20, 227, 206, 20, 20, 6, 195, 12, 245, 9, 20, 6, 195, 8, 19, 9, 66, 7, 196, 4, 112, 86, 20, 65, 0, 8, 197, 56, 83, 77, 20, 224, 21, 8, 197, 52, 21, 18, 60, 224, 20, 8, 197, 20, 117, 77, 20, 224, 66, 10, 198, 5, 33, 197, 57, 65, 79, 66, 20, 0, 9, 198, 64, 241, 5, 77, 64, 64, 67, 0, 10, 199, 76, 83, 5, 84, 50, 68, 36, 66, 9, 198, 52, 81, 193, 64, 241, 9, 20, 10, 199, 20, 194, 67, 61, 69, 5, 72, 20, 9, 198, 12, 243, 150, 60, 115, 9, 20, 0, 7, 196, 16, 81, 204, 36, 72, 7, 196, 16, 17, 204, 36, 72, 7, 196, 76, 21, 143, 12, 65, 7, 195, 72, 20, 5, 66, 20, 6, 195, 56, 21, 9, 66, 6, 195, 28, 245, 9, 20, 6, 195, 13, 83, 201, 20, 0, 8, 197, 88, 22, 154, 60, 192, 66, 8, 197, 61, 34, 71, 4, 224, 66, 8, 197, 24, 20, 147, 4, 192, 65, 8, 197, 12, 20, 211, 4, 192, 65, 0, 9, 198, 81, 34, 78, 37, 64, 64, 67, 9, 198, 24, 19, 13, 20, 229, 0, 20, 9, 198, 12, 243, 135, 20, 226, 84, 66, 9, 198, 12, 21, 20, 20, 68, 128, 65, 0, 9, 198, 24, 147, 9, 77, 65, 73, 67, 0, 6, 195, 24, 21, 5, 76, 6, 195, 88, 21, 5, 66, 7, 196, 76, 209, 71, 52, 20, 6, 195, 64, 84, 9, 20, 7, 196, 48, 19, 73, 4, 65, 0, 9, 198, 88, 145, 5, 61, 65, 67, 20, 8, 197, 52, 16, 193, 9, 32, 65, 9, 198, 28, 148, 19, 61, 65, 67, 20, 8, 197, 20, 193, 84, 81, 32, 20, 8, 197, 20, 193, 84, 81, 32, 20, 0, 9, 198, 52, 20, 148, 37, 33, 64, 65, 9, 198, 49, 81, 213, 9, 33, 64, 65, 9, 198, 12, 83, 5, 9, 33, 64, 65, 0, 10, 199, 76, 81, 206, 5, 3, 211, 80, 21, 9, 198, 65, 32, 83, 76, 81, 5, 20, 9, 198, 48, 144, 207, 52, 81, 5, 20, 10, 199, 20, 229, 21, 76, 144, 83, 52, 68, 10, 199, 16, 148, 212, 72, 241, 137, 4, 67, 9, 198, 12, 19, 148, 4, 36, 137, 65, 9, 198, 12, 19, 1, 52, 149, 1, 68, 0, 7, 196, 80, 83, 80, 72, 20, 12, 201, 72, 240, 195, 4, 115, 15, 72, 147, 211, 21, 6, 195, 72, 21, 5, 66, 9, 198, 20, 225, 15, 13, 34, 78, 66, 7, 196, 16, 145, 68, 72, 20, 6, 195, 12, 245, 5, 20, 7, 196, 12, 243, 79, 16, 65, 7, 196, 8, 145, 201, 4, 65, 7, 196, 4, 194, 67, 20, 66, 0, 8, 197, 77, 81, 200, 21, 32, 65, 8, 197, 72, 148, 18, 61, 96, 20, 8, 197, 72, 145, 15, 81, 64, 21, 12, 201, 64, 144, 90, 104, 21, 15, 73, 33, 64, 21, 6, 195, 56, 243, 0, 20, 8, 197, 37, 51, 194, 5, 32, 66, 8, 197, 12, 243, 12, 21, 32, 20, 0, 7, 66, 56, 240, 50, 108, 0, 9, 198, 5, 97, 86, 5, 65, 64, 72, 9, 198, 21, 32, 86, 5, 65, 64, 72, 5, 194, 76, 80, 8, 9, 198, 61, 69, 15, 9, 33, 64, 21, 5, 194, 60, 208, 20, 0, 9, 198, 65, 34, 78, 12, 148, 9, 65, 9, 198, 72, 19, 143, 12, 50, 9, 20, 9, 198, 65, 34, 78, 12, 148, 9, 66, 10, 199, 64, 243, 148, 20, 98, 67, 20, 21, 6, 195, 56, 241, 0, 20, 9, 198, 28, 195, 212, 80, 145, 5, 20, 10, 199, 16, 241, 5, 12, 17, 68, 72, 20, 10, 199, 12, 243, 147, 20, 194, 67, 20, 21, 9, 198, 12, 19, 69, 24, 149, 5, 66, 10, 199, 5, 4, 5, 56, 66, 67, 20, 67, 0, 7, 196, 72, 144, 201, 56, 65, 8, 196, 64, 80, 207, 72, 65, 20, 7, 196, 52, 242, 197, 56, 20, 8, 196, 20, 48, 84, 20, 65, 20, 7, 196, 12, 144, 197, 72, 65, 7, 196, 5, 33, 1, 72, 65, 7, 196, 4, 48, 82, 36, 65, 0, 9, 197, 88, 144, 193, 72, 144, 65, 9, 8, 197, 5, 97, 83, 80, 80, 72, 8, 197, 5, 97, 83, 80, 80, 72, 8, 197, 69, 81, 83, 80, 80, 72, 14, 2, 194, 163, 87, 47, 36, 34, 55, 6, 37, 50, 35, 0, 8, 197, 104, 145, 207, 80, 80, 20, 8, 197, 88, 240, 130, 36, 16, 20, 8, 197, 84, 226, 86, 60, 48, 66, 8, 197, 80, 19, 73, 28, 144, 66, 12, 201, 65, 33, 77, 36, 192, 213, 61, 33, 64, 20, 8, 197, 64, 84, 135, 4, 208, 65, 9, 197, 64, 80, 193, 72, 144, 65, 20, 8, 197, 37, 69, 9, 72, 144, 65, 8, 197, 5, 48, 193, 72, 144, 65, 0, 9, 198, 80, 147, 132, 5, 34, 64, 65, 9, 198, 80, 20, 148, 5, 34, 64, 65, 9, 198, 65, 33, 83, 21, 2, 64, 20, 9, 198, 36, 195, 5, 12, 149, 0, 66, 13, 202, 36, 51, 211, 37, 65, 84, 72, 17, 68, 72, 20, 10, 198, 17, 33, 78, 28, 245, 0, 66, 20, 9, 198, 16, 148, 208, 5, 34, 64, 65, 9, 198, 5, 52, 197, 57, 162, 64, 20, 0, 10, 198, 88, 84, 218, 65, 33, 77, 66, 21, 10, 199, 76, 83, 5, 84, 50, 68, 20, 66, 6, 195, 56, 245, 0, 20, 6, 195, 56, 245, 0, 20, 9, 198, 52, 243, 146, 61, 98, 65, 20, 9, 198, 37, 51, 212, 61, 2, 65, 68, 9, 198, 24, 84, 146, 61, 98, 65, 67, 6, 195, 12, 244, 20, 20, 9, 198, 12, 244, 5, 64, 241, 9, 20, 0, 16, 7, 3, 12, 9, 3, 8, 195, 169, 49, 55, 37, 12, 89, 36, 0, 7, 196, 80, 83, 80, 48, 20, 9, 198, 76, 50, 65, 8, 243, 0, 65, 11, 200, 72, 244, 1, 48, 240, 197, 72, 144, 67, 11, 200, 53, 83, 20, 36, 85, 14, 36, 48, 20, 11, 200, 37, 1, 82, 76, 243, 142, 36, 16, 68, 7, 196, 28, 83, 73, 56, 65, 0, 8, 197, 5, 97, 77, 52, 240, 72, 6, 195, 77, 83, 0, 72, 8, 197, 88, 244, 212, 72, 80, 72, 8, 197, 56, 244, 212, 72, 80, 72, 9, 198, 76, 243, 12, 21, 66, 67, 21, 8, 197, 37, 35, 206, 36, 16, 67, 8, 197, 4, 65, 15, 52, 80, 20, 0, 6, 194, 77, 80, 72, 9, 9, 198, 77, 68, 143, 57, 162, 64, 20, 12, 201, 64, 145, 84, 72, 20, 5, 73, 162, 65, 68, 12, 201, 52, 84, 137, 80, 240, 210, 5, 162, 65, 69, 12, 201, 37, 1, 82, 52, 85, 18, 61, 2, 65, 69, 9, 198, 25, 84, 142, 5, 34, 64, 65, 9, 198, 8, 148, 212, 85, 34, 64, 65, 12, 201, 5, 34, 83, 80, 240, 210, 5, 162, 65, 69, 0, 9, 198, 65, 35, 198, 21, 162, 65, 67, 9, 198, 64, 244, 134, 37, 34, 65, 67, 9, 198, 52, 241, 5, 77, 66, 65, 66, 6, 195, 48, 85, 20, 20, 9, 198, 20, 229, 1, 49, 2, 65, 67, 9, 198, 12, 20, 208, 21, 34, 65, 66, 9, 198, 4, 195, 5, 29, 34, 65, 67, 0, 7, 196, 80, 16, 201, 80, 65, 7, 196, 72, 80, 201, 80, 65, 9, 198, 36, 51, 211, 4, 81, 18, 20, 7, 196, 28, 227, 205, 20, 20, 0, 15, 204, 76, 240, 201, 4, 193, 5, 52, 240, 210, 5, 162, 65, 70, 9, 198, 12, 20, 15, 49, 83, 199, 20, 0, 9, 198, 36, 225, 9, 72, 85, 20, 20, 9, 198, 16, 148, 208, 61, 53, 0, 21, 9, 198, 9, 32, 67, 12, 85, 20, 21, 0, 13, 2, 194, 169, 49, 6, 39, 48, 37, 34, 115, 47, 0, 9, 198, 85, 65, 78, 76, 147, 5, 67, 9, 198, 52, 19, 143, 12, 50, 9, 20, 0, 0, 6, 195, 72, 16, 66, 66, 0, 12, 201, 72, 243, 80, 37, 48, 193, 80, 243, 5, 67, 9, 198, 60, 193, 79, 16, 245, 20, 21, 9, 198, 12, 19, 1, 76, 85, 20, 20, 0, 0, 7, 196, 64, 244, 16, 36, 21, 6, 195, 21, 32, 133, 66, 0, 8, 197, 100, 18, 23, 20, 128, 66, 8, 197, 12, 20, 131, 4, 224, 65, 0, 7, 2, 195, 168, 107, 0, 72, 9, 198, 76, 50, 79, 88, 144, 64, 66, 9, 198, 12, 84, 131, 32, 144, 64, 21, 9, 198, 4, 195, 5, 48, 144, 64, 67, 9, 198, 4, 193, 83, 76, 144, 64, 67, 0, 9, 198, 16, 80, 193, 64, 243, 9, 66, 0, 8, 196, 8, 17, 204, 36, 66, 9, 8, 196, 88, 84, 147, 60, 76, 28, 6, 195, 80, 83, 73, 20, 7, 196, 76, 21, 9, 72, 65, 7, 196, 64, 21, 9, 56, 65, 7, 196, 56, 147, 194, 20, 65, 8, 196, 24, 83, 73, 56, 65, 21, 7, 196, 12, 130, 78, 20, 66, 7, 196, 12, 130, 69, 76, 20, 12, 68, 8, 17, 204, 36, 69, 35, 61, 6, 37, 0, 0, 8, 197, 77, 2, 71, 60, 192, 65, 8, 197, 72, 20, 19, 60, 64, 66, 8, 197, 72, 20, 19, 60, 64, 20, 12, 201, 65, 50, 67, 32, 144, 84, 72, 144, 64, 67, 8, 197, 56, 245, 77, 20, 224, 66, 8, 197, 8, 19, 194, 4, 32, 67, 0, 9, 198, 80, 84, 129, 64, 144, 64, 67, 9, 198, 77, 3, 199, 48, 144, 64, 20, 9, 198, 76, 147, 79, 56, 144, 64, 67, 9, 198, 76, 19, 147, 13, 34, 84, 65, 9, 198, 76, 19, 65, 72, 144, 64, 67, 9, 198, 52, 243, 143, 16, 144, 64, 67, 9, 198, 21, 52, 12, 36, 50, 84, 66, 9, 198, 20, 208, 143, 48, 144, 64, 67, 9, 198, 5, 68, 143, 24, 144, 64, 67, 0, 8, 67, 4, 49, 64, 21, 0, 10, 10, 199, 76, 85, 20, 20, 208, 146, 20, 20, 9, 198, 36, 208, 146, 60, 115, 9, 20, 0, 14, 4, 95, 3, 5, 4, 74, 36, 70, 6, 37, 61, 35, 0, 9, 198, 88, 147, 12, 5, 51, 210, 67, 6, 195, 80, 83, 85, 66, 8, 196, 12, 130, 79, 16, 66, 20, 15, 204, 4, 229, 9, 65, 50, 67, 32, 144, 84, 72, 144, 64, 69, 0, 13, 201, 88, 19, 12, 20, 52, 143, 76, 144, 64, 67, 20, 8, 197, 80, 20, 129, 57, 64, 65, 8, 197, 77, 1, 84, 81, 32, 20, 12, 201, 56, 80, 210, 60, 208, 78, 104, 144, 64, 68, 12, 201, 36, 68, 143, 80, 84, 129, 64, 144, 64, 69, 12, 201, 24, 149, 15, 80, 84, 129, 64, 144, 64, 69, 12, 201, 16, 148, 208, 5, 33, 85, 56, 144, 64, 69, 12, 201, 12, 193, 80, 80, 243, 65, 56, 144, 64, 68, 8, 197, 12, 19, 148, 21, 32, 65, 8, 197, 12, 17, 134, 5, 32, 65, 12, 201, 5, 37, 5, 80, 84, 129, 64, 144, 64, 69, 0, 9, 198, 72, 148, 208, 21, 69, 0, 20, 9, 198, 16, 83, 148, 36, 49, 64, 20, 9, 198, 12, 243, 12, 21, 69, 0, 20, 0, 18, 4, 95, 12, 9, 7, 55, 4, 36, 79, 35, 47, 6, 40, 12, 51, 35, 0, 6, 195, 80, 83, 80, 20, 9, 198, 48, 21, 82, 20, 230, 137, 20, 10, 199, 36, 67, 204, 5, 68, 137, 4, 68, 9, 198, 28, 147, 143, 12, 50, 9, 20, 10, 199, 4, 227, 210, 21, 52, 201, 4, 68, 10, 199, 4, 208, 140, 36, 244, 9, 4, 68, 0, 7, 196, 76, 51, 210, 76, 21, 9, 198, 12, 84, 131, 60, 49, 66, 20, 8, 196, 12, 17, 206, 60, 66, 20, 0, 6, 195, 80, 83, 0, 21, 8, 197, 56, 81, 210, 5, 32, 66, 6, 195, 48, 83, 78, 20, 6, 195, 36, 48, 82, 65, 8, 197, 5, 65, 76, 21, 64, 20, 6, 195, 4, 48, 82, 65, 0, 5, 194, 80, 80, 20, 0, 7, 195, 12, 242, 64, 72, 9, 10, 199, 56, 245, 20, 21, 65, 77, 64, 20, 9, 198, 24, 147, 143, 12, 50, 9, 20, 10, 199, 20, 229, 21, 76, 144, 83, 80, 68, 10, 199, 12, 20, 142, 20, 98, 67, 20, 21, 0, 7, 196, 4, 224, 200, 20, 8, 11, 200, 80, 84, 154, 60, 113, 78, 37, 64, 67, 7, 196, 76, 85, 20, 20, 20, 7, 196, 76, 84, 18, 36, 20, 7, 196, 52, 81, 193, 72, 65, 6, 195, 28, 243, 77, 21, 6, 195, 28, 227, 205, 20, 14, 68, 24, 18, 78, 4, 81, 35, 6, 37, 12, 50, 35, 0, 0, 8, 197, 5, 100, 133, 52, 240, 72, 8, 197, 76, 20, 133, 52, 240, 72, 8, 197, 76, 21, 18, 5, 0, 65, 8, 197, 29, 32, 70, 20, 208, 20, 15, 69, 24, 197, 73, 16, 240, 81, 55, 6, 40, 37, 70, 39, 0, 8, 197, 20, 227, 212, 20, 48, 20, 8, 197, 12, 19, 143, 56, 80, 65, 8, 197, 12, 16, 195, 4, 208, 65, 0, 9, 198, 85, 38, 149, 48, 82, 64, 67, 13, 202, 81, 32, 78, 76, 48, 85, 12, 20, 201, 4, 68, 9, 198, 60, 195, 15, 48, 18, 64, 67, 9, 198, 56, 148, 195, 20, 210, 64, 20, 10, 198, 21, 52, 197, 72, 50, 64, 65, 20, 9, 198, 5, 51, 79, 56, 82, 64, 67, 0, 6, 195, 24, 18, 64, 76, 6, 195, 16, 82, 64, 72, 7, 195, 48, 82, 64, 76, 9, 10, 199, 64, 243, 9, 20, 68, 137, 12, 20, 10, 199, 24, 147, 15, 81, 65, 84, 20, 20, 10, 198, 12, 19, 66, 60, 114, 65, 66, 20, 0, 7, 196, 84, 197, 18, 4, 66, 6, 195, 76, 243, 77, 21, 7, 196, 60, 225, 193, 72, 65, 7, 196, 48, 19, 79, 56, 66, 7, 196, 16, 243, 73, 56, 65, 7, 196, 4, 194, 66, 36, 65, 0, 6, 195, 76, 227, 194, 20, 8, 197, 72, 245, 133, 72, 80, 21, 8, 197, 72, 81, 21, 12, 80, 65, 12, 201, 69, 80, 84, 80, 244, 132, 36, 50, 64, 21, 9, 198, 64, 19, 131, 72, 80, 83, 65, 8, 197, 21, 49, 77, 64, 144, 20, 9, 197, 16, 240, 204, 20, 16, 65, 20, 6, 195, 4, 49, 82, 65, 0, 8, 67, 4, 49, 83, 21, 0, 10, 6, 194, 81, 80, 76, 9, 9, 198, 64, 148, 133, 56, 82, 64, 67, 9, 198, 61, 35, 204, 60, 114, 64, 20, 9, 198, 52, 243, 143, 48, 149, 0, 66, 9, 198, 12, 19, 129, 104, 82, 64, 67, 9, 198, 12, 19, 79, 76, 50, 64, 20, 9, 198, 8, 148, 143, 12, 50, 64, 20, 9, 198, 4, 208, 146, 60, 114, 64, 20, 0, 10, 199, 77, 66, 76, 60, 32, 84, 20, 66, 6, 195, 76, 243, 64, 20, 9, 198, 24, 84, 137, 80, 242, 65, 21, 6, 195, 8, 145, 84, 20, 0, 11, 200, 80, 20, 129, 57, 64, 83, 36, 16, 67, 7, 196, 76, 84, 19, 36, 20, 11, 200, 76, 19, 9, 76, 49, 78, 16, 144, 21, 7, 196, 13, 80, 137, 80, 65, 9, 198, 4, 229, 9, 64, 21, 18, 66, 11, 200, 4, 229, 9, 56, 49, 78, 16, 144, 20, 9, 198, 4, 225, 18, 60, 114, 78, 66, 0, 7, 195, 20, 50, 74, 65, 21, 6, 195, 4, 50, 78, 65, 0, 10, 198, 48, 147, 134, 60, 227, 196, 67, 20, 0, 6, 195, 76, 227, 196, 20, 6, 195, 64, 85, 20, 20, 10, 199, 36, 65, 78, 80, 146, 201, 80, 68, 6, 195, 36, 49, 84, 65, 11, 199, 12, 244, 132, 20, 227, 206, 76, 67, 20, 10, 199, 12, 19, 142, 4, 195, 206, 28, 20, 10, 199, 4, 229, 9, 76, 84, 19, 36, 20, 0, 5, 195, 12, 243, 69, 9, 198, 88, 243, 20, 52, 85, 18, 65, 7, 196, 28, 83, 73, 80, 65, 0, 8, 197, 12, 244, 148, 21, 48, 66, 0, 9, 198, 20, 225, 137, 76, 83, 64, 20, 0, 9, 198, 88, 83, 12, 21, 68, 137, 21, 10, 199, 80, 84, 141, 61, 53, 1, 80, 66, 0, 7, 196, 80, 85, 20, 36, 20, 10, 198, 64, 148, 143, 76, 48, 70, 66, 20, 7, 196, 8, 243, 66, 20, 66, 0, 8, 197, 80, 244, 130, 36, 64, 21, 8, 197, 80, 147, 80, 4, 224, 65, 8, 197, 80, 19, 148, 4, 192, 65, 12, 201, 69, 82, 78, 16, 144, 197, 76, 147, 64, 20, 8, 197, 13, 35, 212, 4, 192, 65, 8, 197, 5, 84, 133, 60, 192, 67, 0, 9, 198, 76, 147, 143, 64, 144, 64, 20, 9, 198, 72, 149, 137, 56, 50, 84, 66, 9, 198, 65, 83, 9, 104, 144, 64, 67, 9, 198, 36, 225, 129, 52, 144, 64, 66, 9, 198, 21, 128, 197, 57, 68, 128, 20, 9, 198, 21, 84, 129, 76, 144, 64, 67, 9, 198, 21, 52, 5, 72, 144, 64, 66, 9, 198, 5, 53, 5, 72, 144, 64, 66, 10, 198, 5, 33, 5, 76, 144, 64, 66, 20, 0, 0, 7, 196, 72, 85, 9, 56, 65, 8, 196, 52, 22, 154, 20, 66, 20, 7, 196, 48, 19, 73, 56, 65, 0, 8, 197, 88, 19, 132, 4, 192, 65, 8, 197, 76, 19, 132, 4, 192, 65, 12, 201, 52, 84, 207, 64, 245, 1, 52, 144, 64, 68, 12, 201, 5, 85, 15, 12, 81, 129, 48, 144, 64, 70, 0, 9, 198, 73, 85, 5, 56, 144, 64, 20, 9, 198, 72, 147, 129, 76, 50, 84, 66, 9, 198, 65, 32, 83, 76, 80, 64, 65, 9, 198, 64, 20, 143, 16, 144, 64, 67, 9, 198, 24, 192, 77, 20, 224, 192, 21, 7, 195, 21, 36, 143, 66, 20, 10, 198, 16, 243, 15, 52, 144, 64, 66, 20, 9, 198, 5, 53, 5, 56, 144, 64, 67, 9, 198, 4, 193, 207, 88, 144, 64, 20, 0, 10, 199, 76, 53, 79, 48, 16, 149, 76, 67, 0, 9, 198, 24, 244, 211, 4, 227, 214, 20, 9, 198, 12, 20, 144, 60, 99, 210, 66, 7, 196, 4, 226, 68, 72, 65, 0, 8, 197, 81, 32, 70, 61, 32, 21, 12, 201, 80, 16, 200, 36, 48, 82, 16, 144, 64, 68, 12, 201, 52, 148, 195, 20, 195, 1, 56, 80, 64, 67, 7, 195, 20, 53, 66, 65, 20, 12, 201, 9, 32, 68, 36, 48, 82, 16, 144, 64, 68, 0, 6, 195, 48, 85, 67, 65, 0, 10, 199, 16, 145, 204, 61, 52, 201, 4, 67, 0, 6, 195, 64, 242, 0, 20, 7, 196, 8, 80, 82, 56, 21, 0, 8, 197, 81, 34, 77, 21, 32, 65, 8, 197, 81, 34, 70, 61, 32, 65, 6, 195, 64, 243, 0, 20, 8, 197, 37, 51, 205, 21, 32, 66, 8, 197, 16, 148, 208, 85, 64, 65, 8, 197, 9, 83, 7, 5, 32, 65, 0, 6, 194, 76, 144, 76, 9, 9, 198, 76, 241, 134, 36, 49, 64, 20, 9, 198, 64, 84, 142, 36, 49, 64, 66, 9, 198, 56, 20, 148, 20, 49, 64, 20, 9, 198, 52, 20, 211, 36, 209, 64, 65, 9, 198, 37, 53, 18, 36, 49, 64, 65, 9, 198, 24, 244, 142, 4, 49, 64, 66, 0, 10, 199, 76, 96, 67, 80, 84, 137, 4, 66, 10, 199, 29, 82, 68, 37, 166, 143, 48, 67, 10, 199, 29, 81, 82, 72, 18, 79, 48, 21, 0, 13, 68, 24, 145, 82, 36, 81, 6, 37, 36, 51, 37, 0, 7, 196, 64, 84, 149, 56, 66, 7, 196, 12, 243, 73, 76, 65, 7, 196, 12, 147, 69, 28, 65, 9, 198, 4, 100, 129, 28, 243, 0, 21, 0, 8, 197, 5, 97, 83, 80, 144, 72, 8, 197, 69, 81, 83, 80, 144, 72, 8, 197, 52, 243, 143, 52, 144, 20, 8, 197, 48, 84, 194, 36, 48, 20, 8, 197, 12, 83, 9, 56, 80, 21, 8, 197, 8, 244, 135, 36, 16, 65, 0, 9, 198, 76, 19, 85, 72, 18, 64, 67, 6, 195, 64, 244, 0, 20, 9, 198, 5, 69, 5, 56, 67, 204, 20, 0, 9, 198, 52, 147, 137, 52, 22, 0, 67, 10, 199, 25, 33, 67, 12, 85, 20, 20, 21, 9, 198, 5, 36, 143, 76, 50, 65, 20, 9, 198, 4, 225, 207, 76, 50, 65, 20, 0, 11, 200, 88, 83, 148, 37, 49, 84, 80, 80, 20, 7, 196, 80, 244, 142, 36, 21, 9, 198, 52, 20, 129, 80, 131, 206, 67, 7, 196, 24, 147, 79, 56, 66, 7, 196, 20, 66, 76, 20, 66, 0, 8, 197, 88, 244, 212, 72, 144, 72, 8, 197, 56, 244, 212, 72, 144, 72, 8, 197, 73, 80, 146, 36, 48, 66, 8, 197, 56, 84, 212, 48, 80, 66, 8, 197, 52, 20, 147, 36, 16, 65, 9, 197, 21, 69, 15, 72, 80, 65, 20, 8, 197, 21, 51, 198, 4, 112, 66, 8, 197, 12, 243, 12, 20, 112, 20, 8, 197, 12, 80, 201, 80, 16, 67, 9, 198, 12, 20, 148, 4, 49, 79, 66, 0, 9, 198, 72, 245, 133, 76, 50, 64, 20, 14, 202, 52, 243, 148, 20, 51, 205, 64, 21, 18, 36, 67, 20, 9, 198, 52, 19, 132, 36, 35, 204, 66, 9, 198, 21, 32, 67, 48, 149, 0, 66, 0, 7, 2, 95, 1, 35, 12, 0, 14, 203, 88, 147, 12, 4, 208, 83, 76, 20, 135, 36, 16, 68, 9, 198, 85, 53, 1, 76, 50, 65, 65, 9, 198, 72, 245, 133, 76, 50, 65, 20, 20, 71, 12, 20, 129, 36, 34, 67, 60, 49, 35, 51, 35, 6, 37, 69, 37, 49, 39, 0, 10, 199, 12, 19, 142, 36, 32, 76, 20, 66, 10, 199, 12, 19, 80, 4, 226, 76, 20, 67, 19, 70, 4, 195, 208, 20, 50, 65, 35, 55, 39, 48, 36, 74, 6, 37, 12, 35, 0, 0, 11, 200, 80, 83, 80, 61, 32, 78, 20, 240, 67, 7, 196, 24, 195, 197, 52, 20, 0, 12, 201, 52, 20, 148, 37, 35, 204, 60, 114, 64, 20, 0, 17, 70, 88, 82, 67, 60, 195, 192, 82, 107, 6, 37, 49, 39, 55, 39, 0, 9, 198, 65, 35, 194, 48, 83, 64, 20, 9, 198, 21, 48, 78, 80, 83, 64, 20, 0, 7, 2, 95, 5, 36, 12, 0, 10, 199, 20, 225, 137, 80, 85, 83, 36, 67, 0, 7, 196, 88, 243, 73, 80, 65, 7, 196, 76, 83, 69, 48, 20, 0, 8, 197, 16, 147, 206, 37, 48, 66, 0, 7, 2, 95, 9, 37, 12, 0, 9, 198, 64, 84, 137, 20, 113, 84, 20, 0, 10, 199, 61, 35, 199, 20, 225, 83, 36, 67, 6, 195, 36, 65, 9, 66, 6, 195, 8, 16, 129, 66, 0, 7, 2, 95, 15, 108, 12, 0, 6, 195, 44, 240, 128, 20, 6, 195, 12, 240, 128, 20, 0, 7, 196, 76, 35, 195, 12, 21, 7, 196, 56, 147, 69, 28, 20, 6, 195, 21, 48, 67, 20, 12, 201, 16, 144, 201, 61, 69, 5, 76, 147, 64, 20, 8, 196, 12, 131, 195, 60, 66, 20, 7, 196, 8, 147, 206, 16, 21, 0, 8, 197, 88, 242, 86, 60, 64, 20, 8, 197, 76, 244, 135, 60, 224, 65, 6, 195, 64, 83, 142, 21, 0, 9, 198, 72, 243, 65, 56, 144, 64, 67, 9, 198, 12, 243, 131, 61, 36, 192, 21, 0, 6, 195, 81, 80, 64, 72, 10, 199, 12, 192, 90, 60, 209, 78, 20, 66, 10, 198, 8, 243, 148, 20, 35, 203, 65, 20, 0, 7, 196, 88, 243, 69, 72, 65, 7, 196, 88, 84, 142, 20, 66, 8, 196, 80, 83, 69, 56, 65, 20, 7, 196, 76, 19, 65, 72, 65, 12, 200, 52, 243, 148, 20, 66, 83, 60, 224, 66, 20, 7, 196, 52, 81, 204, 36, 20, 7, 196, 13, 83, 133, 60, 65, 7, 196, 12, 19, 65, 72, 65, 0, 8, 197, 104, 244, 16, 60, 192, 20, 12, 201, 80, 80, 200, 56, 144, 207, 48, 244, 128, 20, 8, 197, 72, 149, 15, 72, 224, 21, 8, 197, 60, 210, 67, 36, 64, 67, 8, 197, 56, 84, 208, 60, 192, 20, 8, 197, 45, 84, 149, 52, 32, 65, 8, 197, 40, 244, 16, 60, 192, 20, 9, 198, 12, 243, 12, 61, 21, 73, 20, 8, 197, 12, 20, 144, 36, 224, 65, 0, 9, 198, 53, 83, 20, 37, 3, 0, 65, 9, 198, 52, 16, 207, 52, 84, 128, 67, 9, 198, 12, 243, 137, 24, 84, 128, 66, 10, 198, 12, 243, 135, 73, 80, 64, 65, 20, 9, 198, 4, 208, 82, 12, 244, 132, 67, 0, 10, 199, 104, 20, 15, 80, 80, 200, 36, 20, 10, 199, 9, 33, 78, 80, 243, 137, 12, 21, 10, 199, 4, 229, 9, 12, 19, 69, 72, 67, 0, 11, 200, 64, 144, 78, 80, 84, 146, 20, 224, 21, 0, 7, 2, 95, 21, 40, 12, 0, 9, 198, 88, 83, 148, 21, 50, 77, 20, 9, 197, 44, 84, 139, 101, 32, 65, 21, 9, 198, 12, 83, 148, 21, 50, 77, 20, 0, 9, 198, 12, 243, 137, 84, 113, 64, 65, 0, 6, 195, 81, 81, 64, 72, 6, 195, 88, 83, 0, 21, 6, 195, 88, 83, 0, 21, 10, 199, 12, 16, 200, 21, 52, 201, 4, 67, 0, 7, 196, 64, 84, 195, 20, 21, 8, 196, 52, 84, 201, 4, 65, 20, 0, 8, 197, 104, 147, 135, 5, 32, 65, 8, 197, 60, 113, 197, 81, 64, 20, 8, 197, 52, 20, 148, 61, 32, 65, 8, 197, 52, 19, 77, 85, 64, 66, 6, 195, 28, 243, 142, 21, 0, 6, 194, 80, 144, 76, 9, 9, 198, 72, 19, 69, 77, 49, 64, 20, 9, 198, 64, 83, 137, 76, 243, 0, 66, 6, 195, 61, 101, 137, 20, 9, 198, 24, 144, 193, 72, 243, 0, 67, 6, 195, 4, 65, 9, 66, 0, 10, 199, 5, 100, 133, 8, 33, 82, 60, 72, 10, 199, 28, 243, 9, 5, 33, 9, 4, 68, 10, 198, 8, 80, 84, 72, 150, 0, 65, 21, 11, 199, 5, 21, 73, 48, 81, 201, 4, 67, 20, 0, 6, 195, 76, 243, 143, 72, 6, 195, 76, 243, 143, 72, 7, 196, 4, 195, 69, 56, 21, 0, 6, 195, 88, 85, 0, 20, 8, 197, 80, 17, 4, 20, 144, 66, 6, 195, 76, 243, 142, 21, 9, 197, 76, 83, 143, 56, 144, 65, 20, 9, 198, 28, 19, 66, 85, 50, 65, 66, 8, 197, 16, 83, 79, 56, 80, 20, 6, 195, 12, 243, 142, 21, 8, 197, 12, 19, 137, 48, 80, 66, 9, 198, 5, 4, 129, 77, 50, 65, 67, 0, 6, 195, 28, 243, 137, 20, 9, 198, 16, 144, 76, 37, 50, 64, 66, 0, 7, 195, 49, 82, 64, 76, 9, 10, 199, 77, 64, 78, 37, 51, 1, 60, 67, 10, 199, 64, 20, 142, 5, 52, 207, 76, 67, 10, 199, 52, 20, 143, 8, 241, 21, 60, 20, 9, 198, 48, 148, 85, 36, 112, 83, 67, 9, 198, 21, 53, 18, 4, 225, 79, 66, 10, 199, 12, 243, 2, 72, 144, 207, 56, 67, 0, 15, 2, 95, 34, 82, 37, 51, 79, 39, 55, 36, 47, 12, 36, 0, 11, 200, 37, 53, 1, 57, 64, 78, 20, 16, 67, 7, 196, 28, 83, 196, 20, 20, 7, 196, 8, 193, 86, 36, 20, 0, 23, 2, 95, 33, 48, 4, 40, 50, 47, 39, 36, 87, 49, 55, 35, 63, 35, 47, 6, 37, 82, 39, 0, 8, 197, 88, 149, 18, 20, 240, 65, 8, 197, 88, 147, 137, 48, 80, 66, 12, 201, 80, 84, 141, 60, 113, 78, 21, 50, 64, 67, 8, 197, 69, 82, 69, 80, 80, 20, 12, 201, 61, 53, 5, 60, 113, 78, 21, 50, 64, 68, 9, 197, 52, 83, 79, 72, 80, 65, 20, 12, 201, 20, 193, 84, 81, 35, 204, 37, 50, 64, 67, 8, 197, 8, 242, 5, 52, 80, 20, 8, 197, 8, 144, 137, 80, 80, 65, 8, 197, 8, 19, 1, 4, 208, 65, 0, 6, 195, 64, 83, 129, 21, 6, 195, 4, 195, 5, 72, 11, 67, 20, 195, 1, 36, 55, 55, 35, 0, 76, 6, 195, 81, 85, 21, 66, 9, 198, 76, 147, 148, 21, 50, 64, 65, 9, 198, 37, 3, 198, 37, 50, 64, 66, 6, 195, 24, 19, 133, 66, 6, 195, 21, 35, 197, 20, 7, 195, 16, 83, 133, 66, 20, 9, 198, 5, 3, 198, 37, 50, 64, 66, 0, 8, 195, 12, 243, 128, 72, 8, 9, 15, 2, 95, 39, 35, 48, 6, 108, 87, 47, 51, 39, 81, 39, 0, 6, 195, 80, 85, 84, 65, 10, 199, 76, 21, 5, 48, 194, 84, 20, 66, 6, 195, 12, 240, 136, 21, 0, 12, 68, 40, 80, 78, 76, 73, 37, 12, 50, 86, 0, 7, 196, 72, 84, 197, 16, 20, 11, 200, 64, 243, 148, 72, 83, 79, 48, 144, 66, 11, 200, 64, 20, 146, 60, 48, 200, 36, 16, 20, 12, 200, 48, 84, 9, 48, 83, 85, 72, 80, 67, 20, 7, 196, 37, 51, 1, 52, 66, 11, 200, 21, 65, 82, 60, 113, 78, 20, 240, 68, 7, 196, 20, 195, 199, 36, 20, 6, 195, 12, 243, 135, 20, 0, 10, 198, 52, 16, 197, 16, 243, 133, 66, 20, 8, 197, 44, 18, 82, 61, 48, 66, 9, 198, 28, 19, 1, 80, 243, 133, 66, 12, 201, 24, 245, 15, 76, 147, 148, 21, 50, 64, 67, 9, 198, 16, 21, 80, 32, 147, 133, 68, 9, 198, 13, 81, 204, 36, 84, 137, 65, 9, 198, 12, 193, 79, 52, 83, 133, 66, 8, 197, 12, 21, 67, 5, 48, 65, 9, 198, 5, 52, 197, 52, 35, 5, 67, 6, 195, 5, 50, 78, 65, 0, 6, 195, 48, 83, 129, 21, 6, 195, 4, 195, 1, 72, 7, 195, 104, 19, 133, 66, 20, 6, 195, 20, 195, 5, 21, 0, 7, 195, 21, 35, 192, 72, 9, 6, 195, 64, 83, 132, 21, 6, 195, 5, 50, 76, 66, 0, 6, 195, 4, 195, 15, 72, 17, 4, 95, 3, 1, 16, 63, 35, 57, 6, 40, 87, 49, 39, 55, 35, 0, 7, 196, 76, 243, 65, 48, 65, 7, 196, 56, 83, 66, 72, 20, 8, 196, 28, 243, 73, 80, 65, 21, 7, 196, 20, 227, 195, 32, 20, 7, 196, 8, 241, 213, 20, 66, 9, 198, 4, 65, 78, 60, 209, 82, 67, 0, 21, 2, 95, 41, 49, 57, 4, 40, 86, 35, 48, 35, 51, 6, 36, 50, 47, 36, 86, 37, 0, 8, 197, 80, 131, 204, 61, 48, 21, 9, 198, 12, 21, 133, 16, 147, 133, 21, 0, 6, 195, 24, 20, 133, 76, 10, 198, 4, 48, 193, 57, 67, 192, 76, 28, 22, 2, 95, 40, 35, 48, 4, 36, 51, 47, 35, 48, 35, 51, 6, 36, 50, 47, 36, 86, 37, 0, 9, 198, 48, 244, 133, 16, 19, 128, 67, 9, 198, 44, 128, 77, 76, 147, 128, 66, 9, 198, 37, 4, 201, 48, 243, 128, 65, 13, 202, 20, 193, 84, 81, 35, 198, 61, 33, 83, 36, 20, 9, 198, 8, 20, 153, 80, 243, 128, 65, 0, 8, 195, 64, 84, 128, 72, 8, 9, 10, 199, 76, 81, 9, 12, 84, 201, 52, 20, 6, 195, 21, 50, 84, 65, 10, 199, 12, 243, 73, 57, 65, 82, 56, 67, 0, 7, 196, 77, 4, 133, 12, 20, 6, 195, 76, 244, 135, 21, 7, 196, 52, 16, 201, 56, 65, 7, 196, 21, 67, 137, 12, 20, 8, 196, 20, 35, 204, 36, 65, 20, 0, 14, 2, 95, 45, 47, 14, 16, 35, 47, 12, 37, 50, 39, 0, 12, 201, 84, 197, 18, 5, 65, 82, 72, 83, 128, 21, 8, 197, 81, 34, 84, 60, 224, 65, 8, 197, 64, 246, 154, 60, 192, 66, 0, 13, 2, 95, 44, 82, 6, 37, 51, 79, 39, 55, 35, 0, 9, 198, 76, 240, 195, 61, 36, 192, 21, 9, 198, 76, 50, 79, 64, 84, 128, 65, 9, 198, 76, 19, 79, 88, 20, 128, 67, 9, 198, 72, 147, 131, 61, 36, 192, 21, 13, 202, 65, 50, 67, 61, 65, 82, 5, 1, 85, 80, 69, 9, 198, 64, 84, 131, 61, 36, 192, 21, 9, 198, 61, 35, 5, 4, 228, 192, 21, 6, 195, 44, 244, 133, 66, 9, 198, 16, 148, 195, 61, 36, 192, 21, 6, 195, 12, 244, 133, 20, 9, 198, 12, 19, 15, 28, 84, 128, 66, 9, 198, 4, 193, 197, 56, 144, 128, 20, 0, 9, 2, 95, 51, 47, 51, 6, 36, 0, 6, 195, 76, 244, 132, 21, 10, 199, 12, 243, 12, 4, 113, 78, 20, 66, 0, 9, 2, 95, 50, 70, 6, 40, 36, 0, 7, 196, 76, 21, 21, 72, 65, 7, 196, 48, 147, 69, 56, 65, 6, 195, 12, 243, 147, 20, 7, 196, 12, 19, 69, 72, 65, 9, 198, 8, 84, 148, 60, 193, 0, 20, 0, 9, 2, 95, 49, 6, 40, 50, 39, 0, 8, 197, 77, 82, 67, 36, 64, 66, 6, 195, 64, 86, 154, 20, 8, 197, 52, 145, 206, 60, 192, 65, 8, 197, 24, 83, 77, 36, 224, 65, 8, 197, 16, 243, 142, 60, 192, 20, 12, 201, 8, 244, 135, 61, 48, 84, 60, 195, 0, 21, 9, 197, 5, 4, 18, 60, 64, 66, 20, 0, 11, 2, 95, 48, 70, 86, 6, 36, 51, 39, 0, 9, 198, 77, 64, 70, 24, 244, 128, 65, 6, 195, 48, 85, 133, 20, 10, 198, 12, 240, 207, 52, 84, 128, 66, 21, 0, 11, 2, 95, 55, 87, 6, 107, 47, 12, 36, 0, 10, 199, 24, 244, 141, 4, 194, 84, 4, 68, 6, 195, 5, 163, 212, 20, 0, 7, 196, 5, 100, 133, 36, 72, 9, 2, 95, 54, 87, 6, 107, 57, 0, 7, 196, 80, 148, 143, 48, 66, 7, 195, 64, 84, 143, 66, 20, 7, 196, 21, 67, 137, 4, 66, 7, 196, 17, 83, 9, 4, 66, 9, 198, 12, 244, 146, 61, 69, 0, 21, 0, 12, 2, 95, 53, 74, 6, 37, 50, 49, 120, 36, 0, 8, 197, 64, 192, 67, 37, 64, 65, 8, 197, 56, 20, 195, 37, 64, 65, 8, 197, 48, 20, 195, 37, 64, 65, 0, 13, 2, 95, 52, 49, 120, 6, 35, 47, 12, 51, 39, 0, 9, 198, 76, 48, 82, 64, 19, 148, 65, 13, 202, 8, 147, 212, 85, 32, 129, 104, 147, 206, 20, 20, 0, 9, 198, 5, 97, 83, 76, 84, 143, 72, 20, 2, 95, 59, 48, 4, 40, 50, 47, 39, 36, 82, 6, 37, 51, 79, 39, 55, 35, 0, 0, 7, 196, 52, 83, 66, 72, 20, 12, 201, 12, 147, 145, 84, 19, 148, 21, 50, 77, 20, 0, 10, 2, 95, 57, 50, 6, 108, 82, 36, 0, 8, 197, 64, 84, 141, 85, 64, 65, 8, 197, 28, 19, 66, 21, 32, 65, 8, 197, 12, 21, 20, 5, 32, 65, 0, 10, 2, 95, 56, 6, 108, 47, 12, 39, 0, 10, 198, 76, 241, 204, 36, 243, 0, 65, 20, 9, 198, 52, 85, 1, 64, 243, 148, 20, 10, 198, 5, 85, 15, 77, 67, 208, 68, 20, 0, 24, 2, 95, 63, 48, 4, 40, 50, 47, 39, 37, 50, 47, 36, 51, 39, 79, 35, 47, 6, 37, 82, 39, 0, 10, 199, 64, 20, 129, 16, 148, 197, 4, 67, 0, 18, 2, 95, 62, 49, 57, 4, 40, 86, 35, 6, 35, 50, 79, 39, 55, 39, 0, 11, 200, 81, 84, 130, 60, 19, 2, 21, 32, 67, 9, 198, 64, 148, 143, 77, 49, 78, 66, 11, 200, 12, 243, 148, 72, 19, 2, 21, 32, 66, 10, 198, 5, 85, 15, 13, 67, 206, 67, 20, 0, 9, 198, 77, 66, 80, 20, 225, 9, 20, 6, 195, 72, 245, 0, 20, 8, 197, 72, 16, 193, 48, 80, 65, 9, 197, 64, 144, 195, 32, 80, 66, 20, 10, 198, 61, 37, 5, 57, 50, 65, 66, 20, 8, 197, 52, 147, 9, 80, 80, 65, 8, 197, 48, 148, 1, 72, 144, 65, 9, 197, 48, 16, 195, 32, 80, 66, 20, 8, 197, 28, 83, 133, 76, 144, 20, 9, 197, 16, 80, 193, 16, 80, 65, 20, 8, 197, 12, 243, 147, 12, 144, 20, 9, 198, 12, 243, 80, 20, 225, 9, 20, 8, 197, 9, 83, 20, 20, 144, 66, 0, 19, 2, 95, 60, 35, 48, 4, 36, 51, 47, 35, 6, 35, 50, 79, 39, 55, 39, 0, 9, 198, 104, 19, 66, 21, 50, 64, 20, 9, 198, 61, 37, 5, 57, 50, 64, 20, 9, 198, 16, 145, 82, 21, 50, 64, 65, 0, 6, 195, 12, 244, 148, 21, 0, 7, 196, 80, 19, 65, 72, 65, 11, 200, 72, 85, 20, 36, 194, 78, 20, 240, 67, 9, 198, 56, 144, 197, 72, 21, 0, 66, 7, 196, 16, 147, 69, 72, 65, 11, 200, 16, 145, 1, 76, 48, 76, 36, 16, 68, 7, 196, 16, 19, 65, 72, 65, 11, 200, 9, 32, 67, 32, 144, 197, 72, 144, 66, 7, 196, 4, 211, 210, 36, 21, 0, 8, 197, 76, 81, 9, 48, 80, 66, 8, 197, 76, 19, 132, 36, 16, 66, 12, 201, 65, 50, 67, 60, 50, 78, 21, 50, 64, 20, 8, 197, 64, 20, 146, 60, 48, 65, 12, 201, 64, 19, 9, 56, 113, 78, 21, 50, 64, 67, 8, 197, 48, 244, 147, 36, 48, 21, 8, 197, 48, 145, 206, 20, 240, 65, 8, 197, 48, 84, 211, 36, 48, 20, 9, 198, 48, 21, 82, 5, 50, 65, 67, 8, 197, 36, 194, 65, 16, 80, 66, 8, 197, 21, 53, 1, 76, 144, 65, 8, 197, 12, 244, 142, 20, 16, 65, 8, 197, 12, 129, 79, 64, 80, 65, 8, 197, 8, 17, 9, 48, 80, 66, 12, 201, 4, 225, 201, 60, 113, 78, 21, 50, 64, 67, 0, 9, 198, 76, 147, 134, 37, 50, 64, 65, 9, 198, 65, 35, 212, 21, 50, 64, 65, 9, 198, 37, 3, 212, 21, 50, 64, 66, 9, 198, 16, 144, 84, 21, 50, 64, 66, 9, 198, 9, 34, 65, 57, 163, 204, 67, 0, 10, 199, 12, 244, 15, 48, 147, 69, 72, 67, 0, 9, 196, 76, 245, 20, 60, 76, 28, 21, 11, 200, 80, 244, 142, 4, 37, 79, 56, 144, 20, 15, 204, 61, 52, 201, 16, 244, 133, 17, 85, 20, 5, 50, 64, 65, 11, 200, 60, 194, 71, 5, 32, 200, 36, 16, 68, 11, 200, 12, 243, 5, 61, 69, 5, 72, 144, 20, 9, 198, 8, 243, 135, 36, 244, 142, 21, 11, 200, 5, 85, 5, 57, 66, 67, 32, 80, 20, 0, 9, 198, 64, 244, 137, 24, 84, 137, 66, 9, 198, 36, 224, 207, 49, 83, 69, 66, 0, 9, 198, 8, 20, 212, 36, 19, 128, 66, 0, 14, 203, 5, 48, 201, 84, 112, 67, 5, 1, 76, 48, 144, 21, 0, 7, 196, 88, 244, 199, 36, 20, 7, 196, 76, 147, 69, 80, 20, 12, 201, 72, 240, 195, 4, 114, 79, 88, 147, 133, 21, 12, 201, 52, 243, 148, 21, 97, 82, 28, 147, 133, 21, 6, 195, 36, 193, 79, 65, 7, 195, 28, 241, 207, 66, 20, 7, 196, 28, 19, 65, 48, 65, 12, 201, 5, 34, 83, 80, 241, 201, 80, 243, 133, 68, 0, 8, 133, 1, 22, 18, 195, 160, 72, 8, 197, 81, 33, 86, 21, 48, 20, 9, 198, 69, 80, 82, 21, 50, 77, 21, 8, 197, 60, 34, 68, 61, 48, 21, 9, 198, 52, 83, 15, 52, 19, 133, 66, 8, 197, 8, 147, 199, 5, 48, 67, 0, 10, 198, 8, 145, 78, 80, 147, 128, 65, 20, 9, 198, 8, 22, 65, 52, 243, 128, 67, 0, 10, 199, 76, 20, 133, 8, 33, 82, 60, 72, 10, 199, 84, 225, 9, 12, 84, 201, 52, 20, 6, 195, 80, 83, 204, 66, 10, 199, 52, 19, 12, 60, 96, 71, 36, 66, 0, 7, 196, 80, 84, 197, 72, 65, 7, 196, 77, 68, 133, 76, 20, 6, 195, 48, 80, 195, 21, 12, 201, 36, 229, 15, 56, 20, 149, 52, 244, 137, 21, 0, 8, 197, 48, 19, 80, 4, 64, 65, 8, 197, 16, 84, 205, 4, 224, 20, 6, 195, 12, 241, 206, 20, 9, 198, 5, 52, 197, 52, 147, 137, 66, 0, 9, 198, 60, 208, 133, 48, 144, 192, 67, 9, 198, 16, 243, 69, 56, 144, 192, 21, 0, 10, 199, 81, 34, 65, 80, 131, 15, 56, 65, 6, 195, 80, 80, 192, 20, 9, 198, 28, 243, 1, 76, 80, 195, 21, 6, 195, 16, 80, 192, 20, 10, 199, 12, 130, 76, 36, 17, 207, 56, 67, 0, 6, 195, 80, 80, 207, 21, 12, 200, 28, 195, 194, 36, 49, 70, 4, 192, 67, 20, 12, 200, 21, 65, 82, 60, 49, 70, 4, 192, 68, 20, 7, 196, 4, 224, 207, 72, 21, 0, 9, 198, 80, 19, 69, 72, 144, 197, 67, 8, 197, 52, 20, 146, 60, 224, 66, 8, 197, 28, 20, 154, 60, 224, 66, 8, 197, 16, 20, 147, 20, 224, 65, 8, 197, 12, 243, 77, 60, 64, 20, 9, 198, 8, 84, 135, 20, 113, 201, 21, 0, 13, 202, 80, 84, 141, 60, 83, 5, 81, 68, 137, 12, 20, 9, 198, 80, 83, 5, 52, 16, 192, 20, 9, 198, 21, 84, 137, 48, 240, 192, 67, 9, 198, 4, 225, 137, 48, 240, 192, 66, 0, 10, 199, 88, 19, 19, 5, 52, 201, 56, 66, 6, 195, 80, 80, 204, 20, 10, 199, 16, 148, 207, 72, 66, 78, 20, 21, 0, 7, 196, 5, 100, 129, 36, 72, 30, 4, 95, 4, 15, 20, 48, 6, 40, 50, 47, 39, 15, 87, 4, 39, 82, 14, 16, 35, 87, 49, 14, 16, 6, 37, 47, 12, 39, 0, 6, 195, 80, 80, 203, 20, 9, 198, 52, 19, 148, 36, 51, 210, 66, 9, 198, 12, 147, 133, 12, 197, 66, 67, 0, 8, 197, 77, 81, 4, 37, 64, 65, 8, 197, 76, 83, 137, 61, 32, 20, 8, 197, 76, 83, 137, 61, 32, 65, 8, 197, 72, 147, 142, 61, 96, 20, 8, 197, 72, 81, 4, 37, 64, 65, 8, 197, 65, 83, 16, 37, 64, 65, 8, 197, 64, 147, 214, 21, 32, 66, 8, 197, 52, 83, 136, 37, 32, 66, 9, 197, 13, 33, 68, 37, 64, 65, 21, 8, 197, 12, 243, 80, 37, 64, 65, 0, 10, 198, 76, 241, 143, 12, 193, 64, 65, 20, 6, 195, 20, 65, 65, 21, 6, 195, 16, 80, 201, 20, 6, 195, 8, 17, 197, 66, 6, 195, 4, 193, 65, 65, 0, 14, 5, 1, 22, 18, 195, 178, 106, 82, 34, 6, 108, 0, 72, 7, 195, 12, 129, 64, 72, 8, 20, 2, 95, 91, 35, 48, 6, 36, 51, 47, 35, 49, 120, 6, 35, 70, 14, 16, 35, 0, 10, 199, 64, 19, 12, 4, 229, 79, 80, 20, 9, 198, 52, 243, 143, 64, 16, 203, 67, 6, 195, 16, 81, 192, 20, 10, 199, 13, 34, 83, 61, 53, 15, 52, 66, 6, 195, 4, 193, 64, 66, 0, 9, 198, 77, 84, 5, 72, 147, 210, 21, 6, 195, 76, 244, 147, 21, 7, 196, 52, 148, 201, 4, 65, 7, 196, 12, 83, 66, 72, 20, 7, 196, 5, 36, 9, 4, 66, 12, 201, 4, 65, 78, 60, 148, 15, 24, 148, 201, 69, 0, 6, 195, 76, 241, 0, 20, 8, 197, 76, 50, 5, 73, 160, 21, 9, 198, 64, 148, 143, 48, 148, 201, 66, 8, 197, 64, 19, 132, 5, 32, 65, 6, 195, 48, 83, 206, 21, 8, 197, 20, 194, 88, 37, 32, 67, 6, 195, 20, 65, 78, 20, 9, 197, 16, 21, 150, 21, 32, 66, 21, 9, 197, 12, 243, 131, 5, 96, 65, 20, 6, 195, 4, 193, 78, 21, 0, 8, 198, 69, 80, 76, 12, 129, 64, 9, 66, 88, 144, 82, 37, 0, 76, 9, 9, 198, 76, 48, 78, 16, 19, 0, 65, 9, 198, 69, 80, 68, 72, 145, 192, 66, 9, 198, 64, 243, 12, 36, 225, 64, 20, 9, 198, 64, 84, 137, 12, 193, 64, 65, 9, 198, 56, 145, 86, 60, 193, 64, 20, 9, 198, 20, 113, 77, 60, 225, 64, 20, 9, 198, 12, 243, 147, 60, 193, 64, 20, 9, 198, 12, 243, 135, 72, 81, 192, 20, 6, 195, 8, 18, 193, 66, 9, 198, 5, 52, 1, 72, 17, 192, 66, 0, 8, 67, 12, 128, 84, 21, 0, 10, 16, 2, 95, 95, 6, 40, 50, 70, 36, 51, 87, 49, 39, 51, 36, 0, 10, 199, 65, 83, 3, 32, 84, 137, 4, 66, 9, 198, 64, 85, 20, 36, 225, 79, 66, 6, 195, 60, 130, 64, 20, 0, 13, 2, 95, 94, 49, 35, 48, 12, 40, 74, 12, 39, 0, 7, 196, 20, 193, 84, 80, 20, 10, 198, 8, 18, 129, 104, 85, 0, 67, 21, 7, 196, 5, 4, 5, 56, 21, 0, 8, 197, 5, 100, 133, 80, 80, 72, 8, 197, 69, 81, 83, 80, 240, 72, 19, 2, 95, 93, 49, 57, 4, 40, 86, 35, 49, 120, 6, 35, 70, 14, 16, 35, 0, 9, 198, 80, 148, 129, 56, 226, 65, 67, 9, 197, 64, 20, 133, 72, 80, 66, 21, 8, 197, 52, 147, 208, 36, 16, 67, 8, 197, 48, 147, 73, 80, 80, 65, 6, 195, 36, 51, 206, 20, 9, 198, 16, 144, 67, 60, 226, 65, 68, 8, 197, 16, 83, 79, 56, 144, 67, 8, 197, 12, 84, 131, 32, 144, 21, 8, 197, 8, 244, 135, 32, 144, 21, 0, 9, 198, 77, 65, 70, 4, 226, 64, 65, 6, 195, 64, 84, 149, 66, 9, 198, 36, 224, 197, 56, 66, 64, 20, 9, 198, 16, 80, 197, 56, 226, 64, 20, 9, 198, 12, 144, 204, 4, 66, 64, 65, 9, 198, 4, 48, 197, 28, 194, 64, 20, 0, 9, 198, 12, 243, 80, 72, 84, 211, 20, 6, 195, 4, 194, 64, 66, 0, 11, 200, 76, 83, 73, 12, 84, 131, 32, 144, 21, 12, 201, 76, 50, 9, 88, 83, 143, 28, 194, 65, 20, 12, 201, 69, 80, 76, 76, 149, 143, 28, 194, 65, 20, 11, 200, 64, 19, 142, 60, 48, 200, 36, 16, 20, 11, 200, 36, 229, 5, 73, 4, 133, 80, 80, 66, 8, 196, 20, 194, 84, 20, 65, 21, 7, 195, 12, 130, 79, 66, 20, 0, 8, 197, 88, 244, 212, 72, 240, 72, 8, 197, 56, 244, 212, 72, 240, 72, 6, 195, 76, 245, 146, 21, 9, 197, 56, 244, 212, 60, 144, 65, 21, 8, 197, 56, 18, 65, 16, 80, 65, 9, 198, 52, 19, 20, 20, 212, 0, 20, 8, 197, 24, 243, 79, 72, 144, 65, 8, 197, 21, 53, 15, 56, 144, 65, 8, 197, 21, 21, 73, 16, 144, 20, 9, 198, 20, 113, 77, 60, 226, 65, 68, 9, 198, 4, 226, 82, 36, 66, 65, 68, 0, 13, 2, 95, 96, 69, 35, 49, 48, 14, 16, 115, 63, 0, 12, 201, 60, 67, 206, 80, 245, 5, 12, 226, 67, 20, 9, 198, 52, 243, 135, 60, 194, 64, 20, 9, 198, 5, 96, 77, 64, 244, 212, 21, 0, 0, 11, 200, 80, 84, 129, 64, 85, 84, 36, 48, 67, 8, 196, 48, 80, 201, 80, 65, 21, 11, 200, 36, 229, 5, 72, 194, 78, 20, 16, 67, 7, 196, 21, 84, 137, 80, 65, 12, 201, 20, 224, 201, 12, 195, 208, 20, 66, 65, 69, 12, 201, 12, 147, 145, 84, 81, 143, 28, 194, 69, 20, 7, 196, 5, 67, 5, 80, 20, 6, 195, 4, 193, 83, 20, 7, 196, 4, 67, 69, 80, 20, 0, 8, 197, 65, 35, 212, 5, 48, 65, 6, 195, 28, 246, 154, 21, 8, 197, 24, 17, 68, 37, 48, 20, 6, 195, 20, 65, 82, 65, 0, 10, 198, 81, 34, 86, 20, 225, 84, 66, 20, 9, 198, 72, 245, 21, 48, 83, 192, 66, 9, 198, 52, 81, 9, 12, 83, 192, 66, 9, 198, 24, 244, 129, 56, 83, 192, 66, 0, 10, 199, 64, 83, 148, 5, 67, 5, 80, 20, 6, 195, 48, 83, 192, 21, 0, 12, 201, 65, 35, 211, 80, 17, 133, 72, 84, 201, 67, 6, 195, 64, 84, 195, 20, 6, 195, 64, 84, 195, 20, 6, 195, 12, 244, 195, 20, 7, 196, 5, 36, 133, 16, 20, 0, 9, 198, 72, 241, 9, 80, 244, 137, 21, 9, 198, 57, 85, 143, 48, 243, 133, 20, 0, 15, 4, 95, 7, 18, 22, 79, 14, 16, 6, 35, 12, 82, 36, 0, 6, 195, 12, 244, 193, 66, 10, 198, 12, 83, 1, 16, 243, 128, 65, 21, 0, 10, 199, 28, 194, 67, 60, 194, 83, 36, 66, 6, 195, 20, 66, 84, 65, 9, 198, 12, 241, 84, 4, 225, 79, 67, 9, 198, 12, 21, 20, 4, 225, 79, 66, 6, 195, 4, 194, 84, 65, 0, 11, 200, 12, 243, 69, 28, 194, 65, 57, 48, 67, 0, 8, 197, 104, 240, 195, 60, 192, 20, 8, 197, 88, 20, 133, 56, 224, 21, 8, 197, 72, 240, 195, 60, 192, 20, 8, 197, 64, 83, 132, 84, 192, 20, 8, 197, 52, 243, 20, 20, 224, 21, 6, 195, 48, 84, 194, 20, 8, 197, 16, 144, 67, 60, 224, 66, 8, 197, 12, 19, 73, 60, 224, 65, 8, 197, 9, 81, 134, 4, 192, 65, 0, 9, 198, 69, 80, 76, 12, 244, 192, 20, 7, 195, 65, 84, 133, 66, 20, 9, 198, 60, 198, 77, 64, 244, 192, 65, 9, 198, 52, 20, 137, 64, 244, 192, 20, 0, 6, 195, 20, 66, 80, 65, 10, 199, 17, 32, 71, 4, 210, 78, 20, 67, 0, 7, 196, 77, 68, 143, 24, 20, 8, 196, 72, 244, 197, 60, 65, 20, 9, 198, 72, 145, 146, 20, 65, 0, 21, 11, 200, 5, 32, 201, 16, 144, 67, 60, 224, 67, 0, 9, 198, 104, 84, 134, 4, 194, 85, 67, 8, 197, 52, 83, 147, 60, 192, 20, 9, 198, 12, 243, 80, 48, 144, 197, 20, 8, 197, 12, 243, 15, 28, 224, 20, 8, 197, 12, 19, 132, 20, 192, 21, 0, 6, 195, 65, 84, 137, 66, 6, 195, 64, 84, 201, 20, 9, 198, 64, 83, 148, 5, 67, 0, 20, 9, 198, 64, 83, 148, 5, 67, 0, 65, 9, 198, 12, 83, 148, 72, 144, 192, 20, 0, 0, 7, 196, 52, 84, 207, 48, 65, 13, 201, 16, 144, 207, 80, 147, 5, 16, 243, 137, 68, 20, 9, 198, 12, 243, 134, 21, 69, 0, 20, 0, 8, 197, 76, 148, 15, 57, 64, 20, 9, 198, 76, 128, 78, 28, 128, 73, 66, 9, 198, 64, 20, 129, 48, 148, 201, 66, 9, 197, 48, 84, 1, 57, 64, 65, 20, 0, 6, 195, 80, 84, 201, 20, 9, 198, 76, 84, 150, 36, 193, 64, 66, 10, 198, 52, 81, 193, 12, 193, 64, 65, 20, 9, 198, 21, 34, 71, 60, 225, 64, 66, 6, 195, 16, 84, 201, 20, 0, 20, 2, 95, 123, 35, 48, 4, 36, 51, 47, 35, 79, 14, 16, 6, 35, 81, 12, 35, 0, 16, 4, 95, 4, 9, 1, 70, 57, 36, 51, 6, 36, 12, 86, 124, 0, 10, 199, 76, 147, 135, 32, 147, 218, 104, 21, 10, 199, 5, 85, 15, 64, 147, 15, 80, 20, 9, 198, 5, 32, 200, 20, 192, 79, 67, 0, 8, 196, 76, 84, 201, 4, 65, 20, 7, 196, 72, 84, 201, 4, 65, 7, 196, 52, 84, 211, 20, 20, 0, 6, 195, 80, 241, 0, 20, 8, 197, 77, 83, 195, 21, 32, 65, 8, 197, 72, 83, 132, 37, 64, 65, 8, 197, 65, 35, 198, 21, 64, 20, 8, 197, 64, 20, 212, 61, 32, 21, 12, 201, 12, 20, 212, 20, 197, 133, 72, 65, 64, 21, 0, 9, 198, 77, 84, 146, 20, 225, 64, 21, 9, 198, 72, 85, 20, 36, 98, 76, 67, 9, 198, 64, 144, 90, 104, 243, 0, 67, 9, 198, 61, 53, 18, 60, 115, 212, 20, 9, 198, 28, 83, 148, 36, 193, 64, 66, 9, 198, 21, 48, 200, 36, 225, 64, 20, 9, 198, 16, 80, 201, 8, 83, 0, 67, 9, 198, 16, 80, 193, 48, 241, 192, 66, 9, 198, 12, 244, 148, 36, 193, 64, 66, 10, 198, 12, 86, 129, 56, 225, 64, 65, 21, 9, 198, 12, 21, 1, 48, 241, 192, 66, 9, 198, 4, 229, 5, 56, 225, 64, 21, 0, 0, 7, 196, 81, 84, 129, 56, 66, 7, 196, 72, 148, 193, 56, 65, 9, 198, 72, 80, 193, 72, 81, 0, 20, 7, 196, 52, 20, 197, 72, 66, 7, 196, 12, 244, 197, 56, 21, 7, 196, 5, 83, 15, 76, 67, 0, 19, 2, 95, 125, 49, 57, 4, 40, 86, 35, 79, 14, 16, 6, 35, 81, 12, 35, 0, 8, 197, 84, 36, 137, 4, 48, 67, 6, 195, 80, 245, 0, 20, 8, 197, 80, 84, 195, 32, 144, 20, 9, 197, 76, 20, 5, 72, 80, 66, 21, 9, 198, 52, 243, 133, 28, 194, 65, 20, 12, 201, 52, 81, 137, 77, 67, 198, 20, 193, 64, 67, 8, 197, 28, 19, 1, 80, 144, 65, 9, 198, 21, 2, 70, 4, 226, 65, 68, 8, 197, 5, 52, 197, 16, 144, 20, 9, 198, 4, 224, 82, 12, 130, 65, 67, 0, 6, 195, 80, 244, 0, 20, 9, 198, 52, 243, 5, 12, 243, 0, 20, 9, 198, 52, 148, 212, 72, 19, 0, 66, 6, 195, 20, 69, 73, 20, 0, 10, 199, 76, 245, 20, 60, 35, 211, 12, 20, 9, 198, 76, 244, 16, 72, 84, 211, 20, 10, 199, 64, 147, 129, 12, 245, 5, 12, 20, 11, 199, 64, 20, 148, 20, 227, 208, 20, 66, 20, 10, 199, 52, 243, 132, 4, 67, 210, 36, 21, 10, 199, 52, 20, 148, 36, 226, 84, 80, 67, 0, 8, 196, 21, 52, 5, 72, 65, 20, 11, 200, 61, 38, 137, 88, 80, 195, 32, 144, 20, 9, 198, 21, 2, 84, 72, 149, 0, 66, 9, 198, 12, 243, 80, 36, 85, 0, 20, 7, 196, 5, 165, 5, 12, 20, 7, 196, 4, 229, 65, 44, 66, 9, 198, 4, 193, 129, 8, 85, 0, 20, 7, 196, 4, 115, 210, 4, 67, 0, 8, 197, 80, 83, 129, 12, 80, 66, 9, 198, 76, 195, 214, 20, 226, 65, 20, 8, 197, 76, 50, 5, 72, 208, 21, 9, 198, 72, 243, 65, 56, 66, 65, 67, 9, 198, 65, 35, 211, 60, 66, 65, 67, 34, 77, 60, 194, 71, 60, 65, 78, 17, 35, 199, 48, 147, 205, 4, 108, 55, 37, 79, 39, 70, 36, 50, 70, 14, 16, 39, 61, 6, 37, 108, 63, 35, 0, 8, 197, 56, 21, 83, 20, 16, 65, 9, 198, 52, 243, 148, 60, 113, 201, 20, 8, 197, 52, 148, 212, 72, 16, 66, 8, 197, 48, 85, 20, 36, 112, 66, 8, 197, 20, 208, 140, 20, 208, 20, 0, 9, 198, 88, 19, 132, 4, 194, 64, 65, 6, 195, 80, 81, 213, 66, 6, 195, 76, 240, 201, 20, 6, 195, 48, 84, 205, 20, 9, 198, 29, 84, 208, 36, 226, 64, 65, 9, 198, 17, 84, 15, 56, 66, 64, 20, 6, 195, 12, 244, 201, 66, 9, 198, 12, 129, 82, 4, 66, 64, 65, 0, 10, 199, 24, 83, 77, 36, 226, 76, 20, 67, 10, 199, 13, 35, 211, 80, 16, 197, 60, 66, 0, 11, 200, 81, 84, 144, 36, 195, 209, 84, 144, 20, 9, 198, 72, 148, 208, 61, 53, 0, 21, 11, 200, 52, 243, 148, 21, 97, 82, 16, 80, 21, 11, 200, 37, 1, 82, 80, 84, 141, 36, 16, 68, 7, 196, 21, 84, 143, 64, 20, 0, 12, 201, 69, 80, 68, 72, 145, 143, 28, 194, 64, 20, 9, 198, 37, 3, 212, 4, 192, 77, 67, 0, 9, 198, 5, 97, 86, 4, 211, 192, 72, 9, 198, 21, 32, 86, 4, 211, 192, 72, 6, 195, 61, 4, 9, 20, 13, 202, 52, 20, 129, 12, 19, 1, 28, 243, 137, 76, 20, 6, 195, 12, 244, 205, 20, 6, 195, 12, 244, 205, 20, 0, 10, 199, 61, 34, 84, 80, 84, 143, 64, 67, 0, 9, 198, 81, 34, 80, 61, 53, 0, 21, 8, 196, 76, 84, 193, 52, 65, 20, 0, 8, 197, 76, 85, 146, 21, 48, 20, 9, 198, 16, 148, 208, 72, 244, 201, 20, 0, 9, 198, 24, 244, 211, 36, 211, 192, 72, 6, 194, 84, 224, 72, 9, 16, 70, 76, 49, 73, 12, 51, 192, 89, 107, 6, 37, 49, 12, 39, 0, 9, 198, 4, 229, 5, 48, 19, 192, 67, 0, 6, 195, 64, 243, 12, 21, 6, 195, 64, 243, 12, 21, 9, 198, 64, 84, 144, 21, 69, 79, 20, 19, 70, 12, 148, 131, 84, 149, 15, 74, 37, 14, 16, 49, 6, 40, 37, 47, 39, 0, 0, 7, 195, 76, 19, 15, 66, 20, 7, 196, 49, 85, 5, 60, 65, 9, 198, 4, 224, 67, 60, 225, 0, 20, 7, 196, 4, 115, 210, 16, 65, 0, 8, 197, 81, 84, 143, 48, 64, 20, 8, 197, 76, 19, 148, 20, 224, 65, 9, 197, 56, 147, 82, 60, 64, 66, 20, 9, 198, 52, 147, 12, 20, 227, 137, 20, 9, 197, 12, 244, 132, 60, 32, 65, 21, 0, 6, 195, 81, 83, 201, 72, 9, 198, 69, 80, 76, 37, 64, 64, 67, 6, 195, 52, 81, 9, 20, 6, 195, 5, 48, 197, 66, 0, 10, 199, 36, 229, 5, 72, 209, 68, 36, 20, 12, 201, 8, 245, 76, 21, 85, 5, 72, 147, 206, 21, 0, 0, 8, 197, 76, 50, 5, 72, 224, 21, 8, 197, 76, 48, 80, 60, 192, 65, 12, 201, 64, 244, 211, 36, 34, 76, 37, 64, 64, 69, 9, 198, 64, 80, 195, 36, 243, 9, 20, 10, 198, 56, 83, 65, 80, 241, 9, 67, 20, 8, 197, 12, 244, 16, 60, 192, 20, 0, 10, 198, 36, 224, 207, 28, 226, 84, 66, 20, 9, 198, 24, 20, 142, 21, 51, 204, 67, 9, 198, 5, 32, 200, 21, 66, 80, 66, 10, 198, 4, 48, 210, 20, 66, 84, 66, 21, 0, 10, 199, 80, 84, 212, 36, 211, 206, 20, 20, 10, 199, 61, 53, 18, 60, 115, 212, 36, 20, 10, 199, 52, 17, 206, 21, 68, 143, 56, 65, 10, 199, 16, 148, 207, 56, 84, 212, 4, 68, 9, 198, 16, 148, 195, 61, 65, 67, 20, 0, 7, 196, 104, 85, 71, 52, 65, 7, 196, 29, 85, 5, 36, 66, 0, 12, 201, 88, 147, 12, 5, 50, 77, 37, 84, 192, 68, 8, 197, 72, 148, 207, 49, 64, 20, 8, 197, 52, 244, 195, 61, 96, 20, 9, 197, 52, 243, 15, 81, 32, 65, 20, 8, 197, 17, 32, 71, 85, 64, 66, 8, 197, 13, 84, 195, 85, 64, 65, 0, 13, 202, 80, 83, 78, 61, 52, 15, 56, 66, 76, 36, 20, 9, 198, 76, 20, 211, 60, 225, 64, 65, 10, 198, 64, 144, 67, 21, 33, 64, 67, 21, 9, 198, 52, 17, 206, 21, 65, 64, 20, 7, 195, 48, 241, 5, 66, 20, 0, 10, 199, 9, 35, 206, 12, 130, 79, 48, 66, 6, 195, 9, 33, 68, 20, 8, 197, 8, 147, 212, 61, 0, 66, 9, 198, 4, 225, 137, 5, 32, 79, 67, 0, 7, 196, 61, 52, 143, 20, 65, 7, 196, 20, 194, 77, 36, 65, 7, 196, 13, 84, 15, 48, 65, 0, 9, 198, 64, 84, 144, 21, 69, 65, 20, 9, 198, 48, 245, 26, 61, 32, 73, 67, 6, 195, 25, 33, 78, 21, 0, 9, 198, 76, 20, 133, 77, 65, 64, 72, 9, 198, 88, 19, 12, 21, 97, 64, 20, 9, 198, 52, 144, 200, 36, 83, 0, 66, 14, 202, 12, 195, 210, 4, 209, 133, 56, 144, 207, 48, 69, 20, 9, 198, 12, 144, 204, 61, 1, 64, 20, 0, 10, 199, 69, 80, 68, 73, 84, 15, 48, 67, 10, 199, 64, 144, 195, 5, 33, 9, 4, 67, 10, 199, 52, 16, 210, 60, 51, 211, 52, 20, 0, 7, 196, 76, 148, 193, 72, 65, 7, 196, 72, 84, 201, 56, 65, 7, 196, 52, 148, 197, 72, 65, 7, 196, 12, 84, 193, 72, 65, 7, 195, 12, 17, 15, 66, 20, 6, 195, 5, 65, 79, 65, 7, 196, 4, 195, 208, 20, 65, 0, 6, 195, 104, 85, 0, 20, 15, 69, 80, 82, 83, 80, 16, 47, 107, 6, 37, 87, 47, 35, 0, 9, 198, 76, 145, 206, 61, 34, 65, 67, 8, 197, 64, 83, 15, 76, 144, 21, 9, 198, 56, 85, 83, 81, 34, 65, 65, 8, 197, 52, 147, 143, 72, 144, 21, 8, 197, 48, 144, 133, 72, 144, 65, 8, 197, 24, 80, 130, 72, 80, 20, 8, 197, 21, 81, 133, 52, 144, 20, 9, 198, 20, 229, 18, 61, 2, 65, 67, 9, 198, 20, 211, 198, 36, 194, 65, 68, 8, 197, 16, 80, 143, 48, 80, 65, 6, 195, 9, 33, 78, 21, 8, 197, 8, 19, 19, 4, 208, 65, 8, 197, 5, 48, 197, 76, 144, 20, 8, 197, 4, 148, 143, 48, 80, 20, 8, 197, 4, 32, 129, 100, 80, 67, 0, 6, 195, 84, 244, 0, 20, 9, 198, 76, 20, 211, 60, 226, 64, 65, 9, 198, 72, 147, 131, 61, 66, 64, 20, 9, 198, 20, 224, 207, 49, 2, 64, 20, 9, 198, 8, 243, 129, 77, 51, 204, 67, 0, 6, 195, 64, 84, 212, 21, 6, 195, 37, 51, 204, 65, 10, 199, 20, 48, 197, 57, 68, 137, 12, 20, 0, 11, 200, 80, 244, 142, 5, 33, 67, 12, 144, 20, 11, 200, 72, 81, 133, 72, 83, 132, 84, 208, 20, 11, 200, 61, 4, 18, 36, 209, 78, 80, 80, 20, 6, 195, 49, 83, 199, 20, 7, 196, 21, 84, 133, 44, 65, 10, 198, 4, 65, 5, 8, 149, 0, 66, 21, 9, 198, 4, 52, 143, 8, 21, 0, 66, 0, 8, 197, 77, 97, 86, 36, 16, 20, 8, 197, 72, 85, 15, 72, 80, 65, 10, 198, 61, 35, 211, 12, 244, 0, 66, 20, 8, 197, 24, 244, 141, 36, 48, 66, 9, 198, 24, 21, 20, 61, 34, 65, 67, 8, 197, 21, 21, 73, 64, 80, 65, 8, 197, 16, 243, 143, 72, 144, 67, 12, 201, 12, 192, 86, 36, 49, 77, 8, 19, 0, 67, 8, 197, 4, 53, 76, 20, 240, 66, 0, 9, 198, 76, 20, 133, 77, 66, 64, 72, 9, 198, 105, 80, 195, 5, 34, 64, 65, 13, 202, 80, 145, 204, 5, 68, 9, 48, 84, 197, 72, 20, 6, 195, 76, 244, 201, 20, 9, 198, 64, 147, 69, 57, 65, 76, 67, 9, 198, 28, 148, 143, 77, 64, 84, 66, 9, 198, 9, 80, 195, 5, 34, 64, 65, 0, 10, 198, 64, 19, 13, 5, 33, 83, 67, 20, 10, 199, 60, 211, 218, 36, 115, 212, 20, 20, 10, 199, 52, 148, 129, 24, 147, 210, 36, 21, 10, 199, 36, 229, 18, 60, 67, 212, 80, 21, 6, 195, 21, 51, 196, 20, 0, 6, 195, 64, 243, 3, 20, 7, 196, 64, 193, 90, 104, 20, 7, 196, 48, 85, 67, 36, 65, 12, 201, 37, 3, 195, 48, 244, 137, 17, 34, 65, 69, 11, 200, 16, 83, 79, 13, 32, 90, 36, 16, 68, 11, 200, 12, 21, 20, 37, 97, 82, 36, 16, 67, 11, 200, 8, 21, 20, 36, 53, 79, 72, 80, 20, 11, 200, 4, 116, 143, 76, 148, 212, 20, 208, 20, 0, 6, 195, 80, 243, 6, 20, 9, 198, 65, 33, 78, 76, 147, 5, 20, 6, 195, 61, 1, 82, 21, 9, 198, 28, 21, 68, 20, 230, 137, 20, 9, 198, 12, 84, 129, 56, 84, 201, 66, 0, 6, 195, 76, 19, 5, 66, 9, 198, 36, 227, 143, 13, 83, 192, 20, 6, 195, 28, 147, 5, 66, 10, 198, 20, 211, 69, 57, 64, 76, 65, 20, 0, 6, 195, 81, 83, 192, 72, 6, 195, 80, 243, 4, 20, 10, 199, 60, 113, 201, 28, 147, 210, 56, 21, 6, 195, 37, 64, 76, 65, 10, 199, 24, 147, 129, 48, 35, 210, 28, 21, 10, 199, 8, 243, 129, 12, 243, 19, 36, 20, 0, 7, 196, 36, 228, 201, 80, 65, 7, 196, 4, 67, 210, 56, 21, 0, 9, 198, 56, 240, 195, 36, 243, 1, 66, 9, 198, 52, 20, 195, 32, 147, 5, 66, 6, 195, 48, 241, 26, 21, 0, 11, 70, 36, 229, 5, 72, 225, 84, 21, 0, 10, 11, 67, 21, 52, 197, 36, 87, 87, 36, 0, 76, 6, 195, 64, 244, 5, 20, 6, 195, 17, 83, 205, 20, 10, 198, 12, 243, 135, 73, 83, 192, 65, 20, 0, 10, 199, 76, 16, 210, 36, 193, 71, 36, 20, 10, 199, 16, 241, 9, 12, 84, 201, 52, 20, 0, 6, 195, 80, 245, 15, 66, 6, 195, 80, 245, 15, 20, 7, 196, 44, 22, 65, 44, 66, 8, 196, 21, 69, 1, 72, 65, 20, 0, 9, 198, 64, 192, 83, 52, 241, 9, 20, 8, 197, 12, 147, 212, 60, 192, 65, 9, 198, 12, 19, 12, 36, 244, 5, 66, 8, 197, 9, 80, 195, 36, 224, 65, 0, 11, 67, 21, 52, 193, 36, 87, 87, 35, 0, 76, 9, 198, 88, 83, 149, 77, 64, 64, 67, 9, 198, 72, 17, 206, 5, 65, 76, 21, 10, 198, 48, 147, 65, 77, 51, 204, 67, 21, 13, 202, 21, 48, 67, 37, 51, 212, 80, 17, 68, 72, 20, 9, 198, 16, 148, 195, 5, 2, 84, 66, 0, 10, 199, 65, 35, 211, 21, 36, 9, 56, 66, 10, 199, 28, 19, 66, 4, 51, 210, 80, 21, 6, 195, 21, 52, 192, 21, 10, 199, 12, 243, 73, 56, 99, 210, 52, 67, 6, 195, 5, 51, 204, 65, 0, 7, 196, 24, 244, 212, 36, 72, 7, 196, 80, 85, 67, 72, 65, 7, 196, 48, 241, 204, 36, 20, 7, 196, 12, 244, 212, 4, 66, 0, 9, 198, 88, 19, 7, 60, 115, 9, 20, 8, 197, 52, 84, 195, 4, 192, 66, 8, 197, 16, 243, 13, 20, 224, 20, 8, 197, 12, 243, 135, 20, 64, 20, 0, 10, 198, 60, 211, 137, 9, 84, 192, 65, 20, 9, 198, 56, 81, 210, 37, 64, 64, 67, 9, 198, 12, 244, 148, 37, 51, 204, 67, 0, 15, 67, 93, 117, 192, 6, 82, 40, 6, 82, 40, 6, 82, 40, 0, 10, 199, 52, 243, 148, 61, 33, 129, 56, 66, 10, 199, 8, 192, 83, 80, 244, 15, 72, 66, 10, 199, 4, 116, 137, 24, 241, 204, 36, 20, 0, 7, 196, 80, 81, 207, 48, 65, 9, 198, 65, 35, 199, 21, 69, 0, 20, 9, 198, 64, 19, 131, 21, 69, 0, 21, 7, 196, 56, 241, 77, 36, 20, 7, 196, 28, 147, 210, 56, 21, 0, 8, 197, 53, 84, 212, 21, 32, 66, 9, 198, 48, 240, 193, 48, 149, 1, 68, 9, 198, 24, 147, 1, 72, 85, 5, 20, 9, 198, 12, 19, 3, 5, 33, 69, 66, 0, 11, 67, 21, 52, 201, 36, 87, 87, 37, 0, 76, 9, 198, 80, 84, 211, 21, 33, 64, 20, 9, 198, 56, 84, 212, 61, 33, 64, 65, 6, 195, 16, 245, 5, 20, 10, 198, 12, 80, 210, 61, 1, 64, 65, 20, 0, 12, 201, 36, 226, 78, 80, 84, 146, 61, 69, 0, 21, 6, 195, 21, 51, 208, 20, 10, 199, 12, 243, 12, 20, 195, 206, 28, 20, 0, 7, 196, 24, 244, 211, 20, 72, 11, 200, 52, 243, 148, 20, 97, 76, 81, 32, 21, 0, 8, 197, 76, 81, 213, 37, 64, 65, 8, 197, 64, 243, 4, 21, 32, 20, 9, 198, 61, 69, 15, 80, 148, 9, 66, 8, 197, 56, 148, 16, 85, 32, 66, 8, 197, 48, 85, 20, 21, 32, 20, 8, 197, 28, 19, 66, 5, 32, 65, 9, 197, 16, 84, 208, 61, 64, 65, 20, 0, 5, 194, 88, 240, 20, 6, 195, 60, 145, 9, 66, 9, 198, 48, 16, 200, 21, 65, 64, 20, 0, 11, 199, 29, 35, 211, 76, 243, 79, 16, 67, 20, 12, 201, 25, 32, 78, 12, 144, 67, 61, 37, 0, 21, 0, 7, 196, 76, 144, 84, 20, 72, 7, 196, 64, 17, 201, 56, 65, 11, 200, 24, 83, 137, 12, 245, 20, 21, 32, 20, 11, 200, 8, 19, 5, 56, 245, 20, 21, 32, 20, 7, 196, 5, 52, 18, 36, 66, 0, 8, 197, 24, 16, 197, 88, 16, 76, 6, 195, 88, 245, 0, 20, 8, 197, 76, 147, 148, 60, 208, 65, 8, 197, 72, 22, 154, 36, 16, 66, 8, 197, 64, 22, 154, 36, 16, 66, 9, 198, 52, 84, 137, 77, 65, 77, 20, 8, 197, 52, 20, 133, 52, 208, 21, 8, 197, 36, 212, 1, 72, 144, 65, 8, 197, 5, 3, 210, 36, 16, 67, 0, 6, 195, 64, 241, 9, 20, 9, 198, 64, 18, 12, 5, 98, 64, 65, 9, 198, 9, 33, 83, 4, 243, 0, 66, 0, 9, 198, 76, 20, 146, 60, 50, 0, 66, 9, 198, 5, 85, 5, 57, 66, 67, 20, 9, 198, 5, 85, 5, 57, 66, 67, 20, 0, 7, 196, 24, 244, 212, 20, 72, 9, 198, 76, 19, 79, 76, 21, 0, 66, 11, 200, 56, 147, 134, 60, 208, 78, 36, 16, 68, 7, 196, 36, 224, 213, 8, 65, 7, 196, 21, 53, 5, 72, 65, 9, 198, 4, 192, 193, 57, 64, 82, 66, 0, 9, 197, 12, 243, 148, 72, 240, 76, 28, 9, 197, 76, 51, 210, 104, 80, 66, 20, 8, 197, 72, 81, 9, 56, 144, 65, 9, 198, 60, 211, 212, 61, 2, 65, 68, 9, 197, 53, 81, 199, 36, 240, 66, 20, 8, 197, 28, 197, 84, 20, 240, 65, 8, 197, 28, 149, 82, 36, 16, 66, 9, 198, 24, 243, 7, 5, 34, 65, 67, 8, 197, 20, 113, 82, 36, 16, 66, 9, 198, 9, 83, 7, 5, 34, 65, 67, 8, 197, 4, 97, 143, 72, 144, 65, 8, 197, 4, 50, 5, 56, 144, 20, 0, 9, 198, 76, 147, 133, 17, 34, 64, 20, 9, 198, 9, 83, 7, 5, 34, 64, 65, 9, 198, 4, 84, 143, 77, 64, 84, 66, 0, 15, 203, 52, 243, 143, 12, 245, 9, 48, 81, 15, 56, 144, 69, 20, 10, 199, 4, 52, 85, 20, 67, 212, 80, 21, 0, 11, 200, 77, 68, 129, 56, 117, 82, 36, 16, 67, 11, 200, 52, 243, 148, 21, 97, 82, 16, 144, 21, 11, 200, 52, 243, 66, 5, 35, 195, 12, 144, 20, 7, 195, 44, 20, 15, 66, 20, 11, 200, 13, 80, 149, 49, 65, 82, 36, 16, 67, 11, 200, 4, 115, 210, 4, 99, 194, 36, 16, 69, 11, 200, 4, 34, 79, 81, 35, 198, 36, 16, 69, 0, 6, 195, 85, 65, 82, 65, 6, 195, 52, 85, 18, 21, 10, 198, 36, 83, 80, 76, 19, 5, 65, 20, 8, 197, 4, 64, 77, 5, 48, 67, 0, 0, 15, 204, 56, 85, 82, 61, 4, 201, 12, 130, 65, 81, 34, 65, 70, 14, 203, 36, 195, 21, 52, 147, 143, 80, 80, 206, 36, 48, 20, 0, 7, 196, 21, 53, 5, 80, 20, 7, 196, 5, 53, 1, 80, 65, 9, 198, 5, 32, 71, 61, 53, 0, 21, 0, 8, 197, 52, 17, 18, 5, 48, 66, 9, 198, 4, 65, 82, 8, 19, 5, 66, 0, 9, 198, 72, 144, 83, 76, 85, 20, 20, 0, 10, 199, 88, 19, 12, 20, 51, 210, 76, 21, 10, 199, 24, 147, 1, 57, 68, 143, 64, 66, 0, 7, 196, 76, 145, 86, 20, 20, 0, 8, 197, 77, 1, 67, 60, 192, 20, 12, 201, 76, 245, 20, 61, 4, 143, 16, 245, 20, 21, 8, 197, 24, 20, 195, 36, 224, 65, 8, 197, 12, 20, 195, 36, 224, 65, 8, 197, 8, 20, 142, 4, 32, 65, 8, 197, 4, 192, 207, 60, 192, 65, 0, 9, 198, 88, 80, 195, 32, 144, 64, 20, 9, 198, 81, 84, 131, 32, 144, 64, 66, 9, 198, 80, 85, 20, 60, 144, 64, 21, 9, 198, 72, 244, 193, 48, 144, 64, 67, 9, 198, 52, 19, 16, 20, 228, 192, 21, 9, 198, 24, 244, 195, 32, 144, 64, 66, 9, 198, 12, 240, 195, 32, 144, 64, 20, 9, 198, 12, 20, 137, 61, 66, 80, 67, 9, 198, 4, 48, 193, 16, 144, 64, 67, 9, 198, 4, 32, 129, 16, 144, 64, 67, 0, 6, 195, 76, 144, 64, 72, 10, 135, 2, 5, 14, 3, 8, 195, 168, 8, 10, 199, 65, 35, 208, 72, 145, 84, 4, 68, 12, 201, 65, 35, 195, 20, 66, 77, 20, 229, 0, 20, 0, 8, 196, 56, 81, 204, 36, 72, 28, 11, 200, 52, 243, 148, 21, 161, 77, 60, 192, 20, 9, 198, 16, 144, 80, 5, 51, 206, 66, 7, 196, 12, 244, 212, 36, 66, 9, 198, 4, 32, 129, 56, 67, 206, 21, 0, 8, 197, 76, 20, 147, 36, 224, 65, 8, 197, 52, 19, 135, 4, 224, 65, 12, 201, 4, 229, 15, 56, 243, 65, 76, 144, 64, 68, 0, 9, 198, 72, 244, 207, 48, 144, 64, 67, 9, 198, 64, 193, 83, 80, 144, 64, 65, 13, 202, 64, 145, 90, 60, 83, 5, 81, 68, 137, 12, 20, 0, 10, 198, 76, 179, 208, 20, 195, 211, 65, 21, 6, 195, 20, 209, 64, 20, 11, 199, 8, 83, 22, 20, 65, 82, 20, 67, 21, 0, 7, 196, 72, 81, 207, 48, 65, 7, 196, 64, 17, 207, 16, 20, 12, 200, 52, 243, 148, 20, 209, 83, 60, 192, 67, 20, 7, 196, 52, 241, 207, 48, 66, 9, 198, 16, 144, 76, 21, 69, 0, 20, 6, 195, 12, 145, 67, 20, 7, 196, 4, 228, 201, 4, 65, 7, 196, 4, 115, 211, 80, 21, 0, 9, 197, 104, 81, 134, 37, 32, 65, 20, 12, 201, 21, 51, 211, 12, 129, 76, 21, 68, 128, 67, 6, 195, 4, 209, 66, 20, 0, 9, 198, 21, 49, 81, 84, 145, 64, 20, 9, 198, 12, 240, 195, 36, 113, 64, 20, 0, 6, 195, 64, 241, 64, 20, 0, 7, 196, 76, 17, 207, 52, 65, 0, 8, 197, 88, 84, 148, 61, 96, 65, 8, 197, 80, 81, 84, 21, 64, 20, 8, 197, 80, 19, 129, 29, 32, 65, 8, 197, 48, 22, 154, 5, 32, 65, 12, 201, 24, 243, 148, 4, 225, 76, 36, 49, 64, 21, 8, 197, 20, 209, 82, 37, 64, 66, 9, 198, 12, 243, 3, 32, 145, 5, 20, 0, 9, 198, 88, 84, 142, 36, 49, 64, 66, 6, 195, 80, 243, 73, 20, 9, 198, 12, 244, 142, 36, 49, 64, 66, 9, 198, 4, 229, 9, 56, 241, 64, 66, 0, 10, 199, 81, 32, 77, 60, 113, 201, 4, 20, 12, 201, 24, 243, 148, 4, 226, 71, 61, 33, 0, 21, 9, 198, 12, 19, 3, 5, 33, 79, 66, 0, 7, 196, 73, 81, 137, 56, 65, 9, 198, 64, 19, 148, 4, 195, 206, 67, 7, 196, 52, 241, 207, 72, 65, 7, 196, 8, 21, 76, 20, 67, 0, 8, 197, 36, 229, 133, 12, 80, 8, 8, 197, 81, 83, 137, 76, 144, 65, 8, 197, 73, 81, 134, 36, 16, 66, 8, 197, 65, 35, 210, 60, 112, 65, 8, 197, 61, 32, 77, 4, 144, 67, 8, 197, 56, 147, 137, 88, 80, 65, 9, 198, 37, 51, 212, 72, 244, 0, 66, 8, 197, 12, 130, 83, 76, 16, 66, 8, 197, 5, 32, 197, 56, 80, 65, 10, 198, 4, 48, 68, 20, 210, 65, 67, 20, 0, 10, 135, 16, 5, 18, 3, 8, 195, 169, 8, 9, 198, 81, 33, 77, 21, 166, 128, 20, 9, 198, 80, 243, 13, 21, 166, 128, 20, 0, 6, 195, 64, 244, 16, 21, 11, 200, 28, 84, 211, 61, 0, 76, 20, 224, 21, 10, 199, 12, 243, 5, 61, 69, 5, 72, 20, 0, 7, 196, 76, 49, 76, 80, 21, 8, 196, 61, 101, 133, 72, 66, 21, 9, 198, 52, 20, 133, 52, 245, 0, 20, 10, 198, 36, 229, 143, 49, 80, 210, 66, 20, 7, 195, 20, 209, 83, 65, 20, 0, 8, 197, 84, 243, 73, 56, 144, 65, 9, 198, 76, 83, 5, 84, 50, 65, 66, 8, 197, 4, 52, 85, 20, 240, 65, 8, 197, 4, 32, 90, 36, 16, 67, 0, 6, 195, 16, 243, 65, 20, 6, 195, 4, 195, 197, 20, 0, 0, 12, 200, 52, 144, 210, 60, 225, 83, 36, 16, 67, 20, 11, 200, 36, 224, 213, 73, 50, 79, 56, 80, 20, 11, 200, 28, 83, 195, 20, 229, 18, 36, 48, 20, 11, 200, 12, 243, 131, 20, 229, 18, 36, 48, 20, 0, 0, 6, 195, 80, 243, 69, 66, 9, 198, 28, 84, 143, 48, 19, 64, 66, 13, 202, 12, 20, 212, 72, 245, 137, 48, 192, 82, 36, 67, 9, 198, 4, 208, 76, 28, 19, 64, 66, 0, 6, 195, 21, 67, 128, 20, 9, 198, 5, 32, 200, 36, 195, 195, 66, 7, 195, 4, 195, 192, 66, 20, 0, 7, 196, 24, 244, 211, 36, 72, 9, 198, 80, 85, 18, 4, 81, 18, 20, 0, 0, 9, 198, 76, 20, 129, 56, 227, 192, 72, 9, 198, 64, 243, 9, 24, 83, 64, 20, 9, 198, 52, 16, 193, 16, 19, 64, 67, 0, 6, 195, 20, 196, 192, 21, 6, 195, 20, 67, 204, 20, 9, 198, 4, 229, 8, 20, 210, 83, 65, 0, 7, 196, 64, 145, 86, 20, 20, 0, 9, 198, 8, 20, 149, 52, 147, 137, 66, 0, 9, 198, 81, 32, 78, 88, 144, 64, 66, 9, 198, 72, 81, 193, 48, 144, 64, 67, 9, 198, 36, 224, 197, 57, 68, 128, 20, 9, 198, 21, 161, 67, 32, 144, 64, 67, 0, 9, 198, 88, 147, 204, 4, 49, 79, 67, 10, 199, 76, 49, 71, 48, 145, 82, 20, 65, 10, 199, 5, 34, 83, 80, 17, 207, 72, 67, 0, 8, 196, 80, 145, 210, 20, 66, 20, 0, 12, 201, 76, 51, 210, 12, 144, 84, 60, 144, 64, 21, 9, 198, 4, 48, 213, 52, 243, 9, 66, 0, 9, 198, 52, 83, 15, 16, 144, 64, 67, 9, 198, 4, 227, 211, 52, 144, 64, 67, 9, 198, 4, 192, 149, 56, 80, 64, 66, 0, 10, 199, 72, 148, 18, 37, 53, 9, 56, 66, 10, 199, 64, 80, 197, 56, 81, 200, 36, 20, 10, 199, 36, 225, 197, 28, 225, 82, 20, 67, 6, 195, 20, 213, 64, 66, 10, 199, 12, 83, 148, 60, 48, 200, 36, 20, 0, 9, 198, 12, 149, 20, 4, 227, 214, 20, 0, 8, 197, 24, 84, 133, 81, 32, 65, 12, 201, 12, 148, 212, 36, 97, 76, 48, 80, 64, 67, 8, 197, 8, 20, 129, 81, 32, 65, 0, 0, 0, 0, 9, 198, 88, 147, 204, 4, 49, 69, 67, 0, 9, 198, 76, 85, 20, 36, 209, 64, 65, 9, 198, 76, 52, 143, 24, 243, 0, 65, 6, 195, 64, 241, 77, 20, 9, 198, 56, 240, 195, 36, 243, 0, 20, 9, 198, 25, 32, 84, 80, 83, 80, 20, 10, 198, 12, 21, 5, 12, 243, 0, 67, 20, 9, 198, 4, 84, 143, 28, 83, 0, 67, 0, 10, 199, 64, 84, 146, 20, 112, 85, 96, 66, 9, 198, 36, 68, 143, 12, 244, 147, 21, 10, 199, 4, 224, 83, 80, 20, 201, 4, 67, 0, 7, 196, 76, 145, 84, 20, 72, 9, 198, 36, 225, 15, 52, 149, 0, 66, 9, 198, 21, 49, 82, 12, 149, 0, 66, 7, 196, 12, 245, 80, 20, 67, 9, 198, 8, 144, 84, 32, 195, 206, 65, 0, 8, 197, 24, 16, 195, 36, 240, 76, 9, 198, 88, 148, 201, 28, 245, 9, 20, 8, 197, 80, 80, 206, 36, 48, 20, 8, 197, 72, 148, 15, 48, 144, 65, 8, 197, 64, 144, 206, 36, 48, 66, 8, 197, 61, 35, 211, 20, 144, 67, 9, 197, 8, 84, 143, 36, 16, 65, 21, 8, 197, 8, 16, 200, 20, 48, 20, 8, 197, 5, 161, 71, 48, 144, 20, 0, 9, 198, 81, 32, 77, 21, 166, 128, 20, 9, 198, 64, 20, 146, 36, 50, 68, 67, 9, 198, 48, 19, 149, 76, 82, 64, 67, 9, 198, 5, 32, 193, 56, 113, 76, 66, 0, 10, 199, 12, 129, 76, 36, 49, 82, 36, 66, 0, 11, 200, 76, 245, 20, 61, 33, 9, 56, 80, 21, 12, 201, 76, 51, 5, 72, 241, 5, 72, 210, 65, 68, 9, 198, 72, 80, 193, 64, 149, 0, 66, 11, 200, 52, 243, 69, 57, 64, 78, 20, 240, 67, 11, 200, 37, 53, 1, 57, 64, 78, 20, 240, 67, 0, 8, 197, 48, 83, 206, 104, 144, 20, 9, 198, 4, 192, 200, 36, 210, 65, 66, 0, 9, 198, 72, 243, 65, 28, 227, 204, 67, 9, 198, 12, 243, 12, 20, 114, 64, 20, 0, 6, 195, 64, 241, 84, 20, 11, 199, 20, 212, 5, 16, 240, 204, 20, 66, 20, 10, 199, 12, 20, 193, 80, 145, 76, 48, 21, 0, 9, 198, 77, 64, 82, 61, 53, 0, 65, 11, 200, 72, 83, 1, 80, 149, 137, 80, 16, 69, 11, 200, 64, 148, 143, 80, 80, 206, 36, 48, 20, 11, 200, 52, 81, 193, 21, 51, 198, 4, 112, 68, 12, 200, 24, 244, 211, 4, 49, 83, 36, 16, 67, 20, 11, 200, 20, 115, 195, 20, 229, 18, 36, 48, 20, 0, 6, 18, 66, 195, 160, 0, 195, 178, 0, 195, 179, 0, 195, 185, 0, 97, 0, 111, 0, 117, 0, 7, 6, 18, 67, 195, 169, 0, 195, 168, 0, 101, 0, 7, 6, 195, 160, 0, 3, 7, 35, 0, 117, 3, 7, 35, 2, 40, 0, 111, 2, 32, 24, 3, 7, 112, 0, 105, 2, 25, 3, 7, 115, 0, 7, 6, 97, 0, 4, 1, 21, 2, 98, 105, 108, 101, 32, 3, 6, 35, 0, 1, 21, 2, 103, 103, 105, 110, 101, 32, 0, 2, 116, 116, 101, 114, 17, 65, 32, 0, 118, 97, 110, 111, 1, 21, 2, 32, 14, 128, 128, 133, 3, 6, 35, 82, 35, 50, 39, 0, 4, 1, 21, 2, 99, 17, 65, 32, 3, 8, 35, 0, 1, 21, 2, 99, 104, 101, 32, 0, 4, 3, 35, 0, 1, 17, 67, 21, 2, 32, 14, 128, 192, 129, 0, 1, 105, 21, 2, 32, 14, 128, 192, 129, 0, 2, 105, 115, 109, 111, 32, 0, 2, 105, 115, 116, 17, 65, 32, 0, 117, 3, 35, 2, 40, 0, 111, 2, 32, 24, 3, 112, 0, 4, 101, 8, 2, 114, 3, 115, 0, 105, 2, 25, 0, 7, 6, 98, 0, 3, 69, 0, 98, 3, 69, 12, 0, 7, 6, 99, 0, 111, 1, 21, 2, 108, 17, 65, 32, 3, 8, 49, 39, 0, 4, 3, 49, 0, 104, 0, 4, 99, 3, 49, 12, 0, 99, 104, 0, 4, 2, 17, 71, 3, 74, 0, 2, 39, 0, 105, 2, 17, 65, 0, 4, 99, 2, 17, 71, 3, 74, 12, 0, 99, 105, 2, 17, 65, 0, 7, 6, 100, 0, 101, 114, 101, 1, 110, 3, 8, 70, 36, 51, 36, 0, 3, 70, 0, 100, 3, 70, 12, 0, 7, 6, 101, 0, 4, 1, 21, 2, 115, 105, 109, 111, 32, 3, 6, 36, 0, 1, 21, 2, 118, 111, 108, 17, 65, 32, 0, 2, 109, 111, 110, 17, 65, 32, 0, 4, 1, 17, 65, 2, 114, 32, 3, 6, 107, 0, 1, 21, 2, 114, 114, 105, 109, 111, 32, 0, 1, 21, 2, 99, 105, 32, 3, 8, 36, 0, 4, 1, 17, 67, 2, 114, 101, 32, 3, 8, 107, 0, 1, 17, 67, 11, 2, 114, 17, 65, 32, 0, 4, 3, 36, 0, 1, 17, 67, 21, 2, 32, 14, 128, 192, 129, 0, 1, 102, 2, 114, 109, 0, 1, 104, 2, 115, 115, 0, 1, 109, 2, 115, 115, 0, 1, 109, 21, 2, 110, 116, 17, 65, 32, 0, 1, 114, 17, 65, 21, 2, 32, 0, 2, 110, 103, 17, 65, 32, 0, 2, 114, 115, 105, 32, 24, 0, 2, 115, 115, 97, 32, 0, 2, 116, 116, 17, 65, 32, 0, 2, 122, 122, 17, 65, 32, 0, 8, 17, 67, 115, 2, 115, 115, 0, 4, 1, 99, 2, 116, 116, 17, 65, 32, 3, 107, 0, 1, 103, 2, 110, 101, 0, 1, 103, 103, 2, 114, 111, 32, 0, 1, 114, 2, 109, 0, 2, 17, 65, 0, 2, 17, 67, 11, 17, 65, 32, 0, 2, 17, 67, 32, 0, 2, 17, 67, 105, 17, 67, 17, 65, 32, 0, 2, 17, 67, 117, 108, 17, 65, 32, 0, 2, 108, 0, 2, 108, 108, 117, 0, 2, 110, 17, 65, 32, 0, 2, 110, 17, 67, 17, 65, 32, 0, 2, 114, 0, 2, 115, 116, 0, 2, 116, 105, 0, 2, 116, 114, 0, 2, 116, 116, 105, 21, 0, 2, 118, 105, 32, 0, 2, 118, 111, 32, 0, 2, 122, 17, 65, 0, 8, 114, 0, 105, 2, 25, 3, 107, 57, 0, 7, 6, 102, 0, 4, 1, 17, 65, 2, 101, 114, 111, 32, 3, 8, 81, 0, 1, 17, 65, 21, 2, 105, 108, 111, 32, 0, 3, 81, 0, 7, 6, 103, 0, 103, 101, 114, 1, 21, 2, 108, 111, 32, 3, 8, 73, 12, 36, 51, 0, 4, 108, 2, 105, 3, 61, 0, 108, 2, 195, 172, 0, 108, 105, 2, 17, 65, 0, 110, 3, 65, 0, 4, 2, 17, 71, 3, 73, 0, 105, 1, 110, 2, 97, 32, 0, 105, 2, 17, 65, 0, 4, 105, 2, 97, 32, 3, 73, 6, 123, 0, 195, 172, 2, 97, 32, 0, 4, 103, 2, 17, 71, 3, 73, 12, 0, 103, 105, 2, 17, 65, 0, 4, 3, 79, 0, 104, 0, 103, 3, 79, 12, 0, 108, 8, 3, 79, 55, 0, 117, 2, 17, 65, 3, 79, 58, 0, 7, 6, 104, 0, 3, 0, 4, 97, 8, 3, 105, 6, 35, 0, 195, 160, 8, 0, 7, 6, 105, 0, 4, 1, 108, 2, 17, 65, 3, 2, 37, 0, 1, 114, 2, 17, 65, 0, 4, 1, 21, 2, 98, 105, 108, 101, 32, 3, 6, 37, 0, 1, 21, 2, 100, 101, 114, 101, 32, 0, 2, 97, 99, 17, 65, 32, 0, 2, 97, 115, 105, 32, 0, 2, 103, 101, 110, 17, 65, 32, 0, 4, 97, 1, 29, 2, 32, 3, 6, 37, 35, 0, 97, 1, 102, 97, 2, 32, 0, 97, 1, 110, 111, 102, 2, 32, 0, 97, 1, 112, 111, 99, 115, 2, 32, 0, 97, 1, 114, 101, 2, 32, 0, 97, 1, 114, 111, 103, 2, 32, 0, 97, 1, 114, 116, 101, 109, 2, 32, 0, 97, 1, 116, 2, 32, 0, 110, 97, 115, 2, 32, 3, 6, 37, 50, 35, 87, 0, 115, 115, 101, 114, 111, 1, 21, 2, 32, 14, 128, 128, 134, 3, 6, 37, 87, 87, 36, 34, 39, 0, 115, 115, 105, 109, 97, 1, 21, 2, 32, 14, 128, 128, 134, 3, 6, 37, 87, 87, 37, 63, 35, 0, 115, 115, 105, 109, 101, 1, 21, 2, 32, 14, 128, 128, 134, 3, 6, 37, 87, 87, 37, 63, 36, 0, 115, 115, 105, 109, 105, 1, 21, 2, 32, 14, 128, 128, 134, 3, 6, 37, 87, 87, 37, 63, 37, 0, 115, 115, 105, 109, 111, 1, 21, 2, 32, 14, 128, 128, 134, 3, 6, 37, 87, 87, 37, 63, 39, 0, 4, 1, 21, 2, 99, 17, 65, 32, 3, 8, 37, 0, 1, 21, 2, 99, 104, 17, 65, 32, 0, 1, 21, 2, 100, 17, 65, 32, 0, 1, 21, 2, 103, 17, 65, 32, 0, 1, 21, 2, 109, 97, 32, 0, 1, 21, 2, 109, 111, 32, 0, 1, 98, 2, 108, 101, 32, 0, 1, 99, 2, 108, 17, 65, 32, 0, 1, 103, 2, 108, 17, 65, 32, 0, 1, 109, 2, 108, 101, 32, 0, 1, 112, 2, 116, 101, 32, 0, 1, 114, 17, 67, 97, 108, 2, 109, 97, 32, 0, 1, 115, 115, 2, 108, 17, 65, 32, 0, 2, 108, 17, 65, 32, 0, 2, 110, 101, 32, 0, 97, 1, 21, 2, 32, 3, 8, 37, 2, 35, 0, 111, 1, 21, 2, 32, 14, 128, 192, 129, 3, 8, 37, 2, 39, 0, 4, 3, 37, 0, 1, 17, 67, 21, 2, 32, 14, 128, 192, 129, 0, 1, 21, 2, 17, 65, 110, 116, 101, 32, 0, 1, 114, 2, 109, 97, 32, 0, 1, 114, 116, 2, 99, 101, 32, 0, 1, 116, 115, 2, 109, 97, 32, 0, 1, 122, 110, 101, 2, 109, 97, 32, 0, 2, 111, 0, 2, 195, 178, 0, 2, 195, 179, 0, 8, 17, 67, 2, 97, 0, 8, 17, 67, 2, 195, 160, 0, 195, 160, 1, 21, 2, 32, 3, 37, 6, 35, 0, 4, 101, 1, 21, 2, 114, 17, 65, 32, 3, 37, 6, 107, 0, 195, 168, 1, 21, 2, 114, 17, 65, 32, 0, 195, 169, 1, 21, 2, 114, 17, 65, 32, 0, 4, 1, 18, 67, 2, 12, 3, 57, 0, 1, 97, 2, 12, 0, 1, 111, 2, 12, 0, 1, 160, 195, 2, 12, 0, 2, 17, 65, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 3, 49, 0, 107, 3, 49, 12, 0, 7, 6, 108, 0, 4, 3, 55, 0, 108, 2, 32, 0, 108, 2, 17, 67, 3, 55, 10, 0, 7, 6, 109, 0, 3, 63, 0, 105, 1, 17, 65, 2, 97, 32, 3, 63, 6, 37, 0, 7, 6, 110, 0, 4, 3, 50, 0, 2, 103, 17, 71, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 7, 6, 111, 0, 4, 1, 21, 2, 103, 110, 111, 108, 111, 32, 3, 6, 39, 0, 1, 21, 2, 110, 122, 111, 108, 111, 32, 0, 4, 1, 21, 2, 102, 111, 110, 111, 32, 3, 6, 108, 0, 1, 21, 2, 103, 114, 97, 102, 111, 32, 0, 1, 21, 2, 108, 111, 103, 111, 32, 0, 1, 21, 2, 109, 101, 116, 114, 111, 32, 0, 1, 21, 2, 110, 111, 109, 111, 32, 0, 1, 108, 2, 103, 105, 99, 111, 32, 0, 2, 103, 101, 110, 17, 65, 32, 0, 2, 112, 111, 108, 17, 65, 32, 0, 2, 115, 116, 114, 97, 99, 17, 65, 32, 0, 4, 1, 21, 2, 100, 105, 32, 3, 8, 39, 0, 1, 21, 2, 100, 111, 32, 0, 1, 114, 100, 2, 109, 111, 32, 0, 1, 118, 2, 108, 17, 65, 32, 0, 4, 1, 17, 67, 17, 67, 2, 108, 17, 65, 32, 3, 8, 108, 0, 1, 21, 2, 108, 111, 32, 0, 1, 100, 110, 2, 108, 17, 65, 32, 0, 1, 105, 99, 2, 108, 17, 65, 32, 0, 1, 115, 110, 2, 108, 17, 65, 32, 0, 4, 3, 39, 0, 1, 17, 67, 21, 2, 32, 14, 128, 192, 129, 0, 1, 99, 115, 2, 108, 116, 17, 65, 32, 0, 1, 102, 2, 114, 109, 17, 65, 32, 0, 1, 105, 2, 110, 101, 0, 1, 105, 2, 115, 111, 32, 0, 1, 105, 21, 2, 32, 14, 128, 192, 129, 0, 1, 114, 17, 65, 2, 115, 115, 17, 65, 32, 0, 2, 110, 105, 32, 0, 2, 114, 101, 32, 0, 105, 2, 111, 32, 3, 39, 2, 124, 0, 105, 2, 115, 17, 67, 17, 65, 32, 3, 39, 6, 37, 0, 4, 1, 21, 2, 108, 97, 32, 3, 108, 0, 1, 21, 2, 108, 105, 17, 65, 32, 0, 1, 21, 2, 109, 97, 32, 0, 1, 21, 2, 109, 111, 32, 0, 1, 99, 2, 108, 116, 17, 65, 32, 0, 1, 99, 115, 2, 112, 0, 1, 105, 0, 1, 105, 2, 108, 17, 65, 32, 0, 1, 109, 2, 98, 105, 108, 101, 0, 1, 110, 103, 2, 108, 97, 32, 0, 1, 117, 2, 108, 17, 65, 32, 0, 1, 118, 2, 108, 116, 0, 2, 17, 67, 11, 17, 65, 32, 0, 2, 17, 67, 17, 65, 17, 67, 17, 65, 32, 0, 2, 17, 67, 17, 67, 32, 0, 2, 17, 67, 114, 0, 2, 99, 97, 32, 0, 2, 99, 111, 32, 0, 2, 108, 29, 0, 2, 108, 105, 0, 2, 110, 105, 0, 2, 110, 111, 32, 0, 2, 111, 0, 2, 114, 0, 2, 115, 105, 32, 0, 2, 115, 115, 0, 2, 115, 116, 0, 2, 116, 116, 111, 108, 0, 2, 122, 17, 65, 0, 105, 3, 108, 2, 124, 0, 7, 6, 112, 0, 1, 109, 21, 2, 101, 114, 101, 32, 3, 8, 48, 0, 3, 48, 0, 112, 3, 48, 12, 0, 110, 8, 2, 21, 21, 3, 50, 0, 115, 8, 2, 17, 65, 21, 3, 87, 0, 7, 6, 113, 0, 4, 3, 49, 120, 0, 117, 0, 7, 6, 114, 0, 4, 3, 14, 16, 0, 1, 17, 67, 0, 8, 0, 1, 17, 65, 2, 17, 65, 3, 51, 0, 114, 3, 51, 16, 0, 7, 6, 115, 0, 1, 17, 65, 2, 17, 65, 3, 86, 0, 105, 97, 1, 21, 3, 86, 6, 37, 35, 0, 105, 195, 160, 1, 21, 3, 86, 37, 6, 35, 0, 4, 3, 87, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 1, 107, 0, 1, 108, 0, 1, 112, 0, 2, 99, 0, 2, 102, 0, 2, 107, 0, 2, 112, 0, 2, 113, 0, 2, 116, 0, 2, 120, 0, 8, 0, 105, 97, 1, 17, 67, 21, 3, 87, 6, 37, 35, 0, 99, 104, 2, 17, 71, 3, 87, 49, 0, 115, 3, 87, 87, 0, 4, 99, 2, 17, 71, 3, 89, 0, 99, 105, 2, 17, 65, 0, 104, 1, 25, 0, 104, 2, 25, 0, 4, 99, 105, 2, 105, 3, 89, 2, 37, 0, 99, 105, 2, 195, 172, 0, 7, 6, 116, 0, 3, 47, 0, 116, 3, 47, 12, 0, 7, 6, 117, 0, 4, 1, 21, 2, 99, 111, 108, 111, 32, 3, 6, 40, 0, 1, 21, 2, 100, 105, 110, 101, 32, 0, 2, 105, 116, 111, 32, 0, 1, 21, 2, 108, 17, 65, 32, 3, 8, 40, 0, 4, 3, 40, 0, 1, 108, 25, 2, 17, 65, 0, 1, 114, 25, 2, 17, 65, 0, 2, 17, 65, 3, 120, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 120, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 2, 25, 3, 37, 0, 3, 57, 0, 7, 6, 122, 0, 4, 2, 18, 66, 17, 65, 3, 70, 86, 0, 8, 2, 105, 0, 8, 2, 195, 172, 0, 3, 121, 0, 122, 1, 17, 65, 3, 121, 12, 0, 7, 6, 0, 33, 1, 19, 3, 0, 195, 169, 3, 7, 36, 0, 195, 172, 3, 7, 37, 0, 195, 179, 3, 7, 39, 0, 195, 179, 105, 3, 7, 39, 124, 0, 195, 185, 3, 7, 40, 0, 195, 168, 3, 7, 107, 0, 195, 168, 105, 2, 25, 3, 7, 107, 57, 0, 195, 178, 3, 7, 108, 0, 195, 178, 105, 3, 7, 108, 124, 0, 195, 169, 105, 2, 25, 3, 7, 116, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 33, 3, 10, 48, 6, 40, 50, 47, 39, 36, 87, 49, 55, 35, 63, 35, 47, 6, 37, 82, 39, 10, 0, 45, 8, 32, 2, 32, 15, 3, 63, 36, 50, 39, 0, 36, 3, 70, 39, 55, 55, 35, 34, 39, 0, 44, 2, 15, 3, 82, 6, 37, 34, 79, 39, 55, 35, 0, 194, 167, 3, 87, 36, 121, 37, 6, 39, 50, 36, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts28 = FileInMemory_createWithData (43392, reinterpret_cast (&espeakdata_dicts28_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/it_dict", L"it"); Collection_addItem (me.peek(), espeakdata_dicts28.transfer()); static unsigned char espeakdata_dicts29_data[2058] = { 0, 4, 0, 0, 84, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 8, 69, 13, 0, 0, 0, 0, 0, 6, 65, 12, 89, 13, 0, 0, 0, 0, 0, 6, 65, 16, 70, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 24, 81, 13, 0, 0, 0, 0, 0, 6, 65, 28, 79, 13, 0, 0, 0, 0, 0, 10, 65, 32, 13, 105, 6, 13, 69, 40, 0, 0, 0, 0, 0, 7, 65, 36, 37, 9, 0, 72, 0, 0, 0, 0, 6, 65, 40, 88, 13, 0, 0, 0, 0, 0, 6, 65, 44, 49, 13, 0, 0, 0, 0, 0, 6, 65, 48, 55, 13, 0, 0, 0, 0, 0, 6, 65, 52, 63, 13, 0, 0, 0, 0, 0, 6, 65, 56, 50, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 64, 48, 13, 0, 0, 0, 0, 0, 9, 65, 68, 49, 6, 13, 69, 40, 0, 0, 0, 0, 0, 6, 65, 72, 51, 13, 0, 0, 0, 0, 0, 6, 65, 76, 87, 13, 0, 0, 0, 0, 0, 6, 65, 80, 47, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 88, 82, 13, 0, 0, 0, 0, 0, 9, 65, 92, 82, 6, 13, 69, 40, 0, 0, 0, 0, 0, 6, 65, 96, 99, 13, 0, 0, 0, 0, 0, 8, 65, 100, 6, 13, 69, 40, 0, 0, 0, 0, 0, 6, 65, 104, 86, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 3, 21, 39, 9, 89, 6, 40, 105, 37, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 4, 95, 4, 16, 20, 48, 37, 10, 0, 0, 0, 0, 0, 0, 7, 132, 16, 15, 39, 5, 76, 0, 0, 0, 0, 7, 132, 26, 15, 39, 5, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 16, 15, 39, 21, 27, 48, 39, 105, 40, 0, 72, 0, 0, 0, 0, 13, 4, 14, 15, 39, 21, 27, 50, 39, 105, 40, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 69, 36, 163, 206, 4, 144, 27, 37, 88, 39, 50, 6, 108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 69, 36, 161, 78, 4, 144, 27, 37, 88, 36, 50, 108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 10, 1, 39, 1, 88, 6, 35, 105, 35, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 66, 45, 80, 49, 40, 24, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 66, 56, 16, 50, 6, 35, 11, 0, 0, 10, 67, 8, 242, 64, 69, 110, 24, 0, 72, 0, 0, 0, 0, 10, 67, 44, 82, 64, 49, 109, 24, 0, 72, 10, 67, 56, 242, 64, 27, 50, 110, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 36, 160, 64, 27, 37, 88, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 36, 161, 64, 27, 37, 88, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 68, 36, 224, 74, 4, 27, 37, 50, 35, 88, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 18, 21, 39, 5, 51, 6, 40, 105, 36, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 5, 9, 10, 5, 39, 9, 27, 37, 88, 36, 105, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 5, 39, 15, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 64, 82, 64, 48, 6, 109, 11, 0, 0, 0, 0, 0, 10, 67, 28, 242, 64, 27, 79, 110, 0, 72, 10, 67, 56, 18, 64, 50, 6, 108, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 36, 163, 192, 27, 37, 88, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 88, 21, 64, 82, 106, 24, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 2, 95, 1, 35, 69, 40, 0, 0, 0, 0, 0, 8, 2, 95, 5, 36, 69, 40, 0, 0, 0, 0, 8, 2, 95, 9, 37, 69, 40, 0, 0, 0, 8, 2, 95, 15, 39, 69, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 2, 95, 21, 40, 69, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 95, 51, 89, 37, 0, 0, 7, 2, 95, 50, 51, 36, 0, 0, 7, 2, 95, 49, 48, 35, 0, 0, 7, 2, 95, 48, 50, 39, 0, 0, 7, 2, 95, 55, 86, 36, 0, 0, 7, 2, 95, 54, 99, 35, 0, 0, 7, 2, 95, 53, 63, 40, 0, 0, 7, 2, 95, 52, 82, 39, 0, 0, 0, 0, 7, 2, 95, 57, 87, 39, 0, 0, 7, 2, 95, 56, 69, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 69, 36, 160, 78, 4, 144, 27, 37, 88, 35, 50, 6, 108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 66, 80, 240, 24, 47, 39, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 80, 242, 64, 47, 110, 24, 0, 72, 10, 67, 76, 18, 64, 87, 6, 108, 11, 0, 10, 67, 12, 18, 64, 89, 6, 108, 11, 0, 0, 0, 0, 0, 10, 67, 64, 242, 64, 27, 48, 110, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 97, 0, 1, 29, 2, 32, 3, 4, 35, 0, 117, 1, 29, 2, 32, 3, 4, 106, 0, 105, 1, 29, 2, 32, 3, 4, 108, 0, 3, 35, 0, 117, 3, 106, 0, 105, 3, 108, 0, 7, 6, 98, 0, 3, 69, 0, 2, 17, 67, 3, 69, 10, 0, 7, 6, 99, 0, 3, 89, 0, 1, 25, 2, 17, 67, 3, 89, 11, 0, 7, 6, 100, 0, 3, 70, 0, 106, 3, 73, 0, 7, 6, 101, 0, 1, 29, 2, 32, 3, 4, 36, 0, 105, 1, 29, 2, 32, 3, 4, 109, 0, 3, 36, 0, 105, 3, 109, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 105, 8, 2, 39, 17, 65, 32, 3, 27, 79, 37, 0, 3, 79, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 1, 29, 2, 32, 3, 4, 37, 0, 1, 29, 2, 17, 65, 32, 3, 4, 57, 0, 3, 37, 0, 2, 17, 65, 3, 57, 0, 7, 6, 106, 0, 3, 88, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 3, 45, 0, 4, 1, 17, 65, 3, 55, 0, 2, 17, 65, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 42, 0, 4, 1, 17, 65, 3, 50, 0, 2, 17, 65, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 7, 6, 111, 0, 1, 29, 2, 32, 3, 4, 39, 0, 105, 1, 29, 2, 32, 3, 4, 110, 0, 3, 39, 0, 105, 3, 110, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 58, 0, 7, 6, 114, 0, 3, 44, 0, 4, 1, 17, 65, 3, 51, 0, 2, 17, 65, 0, 2, 17, 67, 3, 51, 10, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 99, 3, 74, 0, 7, 6, 117, 0, 1, 29, 2, 32, 3, 4, 40, 0, 1, 29, 2, 17, 65, 32, 3, 4, 58, 0, 3, 40, 0, 2, 17, 65, 3, 58, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 99, 0, 7, 6, 121, 0, 3, 13, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 203, 136, 3, 6, 0, 39, 8, 2, 32, 3, 6, 13, 105, 13, 0, 4, 46, 3, 11, 0, 46, 2, 32, 14, 128, 128, 129, 0, 46, 8, 2, 21, 14, 128, 132, 129, 0, 39, 3, 105, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts29 = FileInMemory_createWithData (2057, reinterpret_cast (&espeakdata_dicts29_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/jbo_dict", L"jbo"); Collection_addItem (me.peek(), espeakdata_dicts29.transfer()); static unsigned char espeakdata_dicts30_data[3220] = { 0, 4, 0, 0, 215, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 54, 48, 1, 87, 6, 35, 63, 39, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 1, 33, 109, 6, 35, 99, 37, 55, 37, 87, 15, 50, 4, 37, 89, 35, 50, 37, 0, 0, 0, 12, 1, 35, 50, 6, 39, 63, 36, 34, 37, 0, 27, 0, 0, 13, 1, 37, 48, 34, 39, 107, 36, 50, 47, 37, 0, 27, 0, 6, 1, 38, 70, 35, 0, 0, 0, 0, 0, 16, 1, 42, 82, 35, 34, 82, 87, 49, 82, 55, 35, 82, 37, 0, 27, 0, 11, 1, 43, 48, 55, 37, 40, 87, 37, 0, 27, 0, 0, 0, 11, 1, 46, 110, 36, 34, 47, 37, 55, 37, 0, 0, 29, 1, 47, 63, 6, 35, 34, 107, 99, 50, 37, 82, 15, 70, 6, 35, 99, 34, 37, 55, 37, 15, 99, 6, 35, 86, 37, 0, 27, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 5, 95, 48, 1, 14, 4, 70, 2, 35, 0, 0, 0, 0, 0, 0, 11, 1, 61, 47, 39, 55, 39, 69, 35, 0, 27, 0, 0, 0, 11, 1, 64, 109, 35, 98, 55, 40, 49, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 4, 95, 48, 67, 48, 35, 87, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 29, 1, 92, 63, 6, 35, 34, 73, 82, 50, 37, 82, 15, 70, 6, 35, 99, 34, 37, 55, 37, 15, 99, 6, 35, 86, 37, 0, 27, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 49, 56, 1, 25, 82, 34, 6, 35, 63, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 49, 57, 1, 107, 99, 34, 6, 35, 63, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 4, 95, 49, 48, 1, 6, 35, 25, 0, 0, 0, 0, 0, 0, 10, 134, 225, 131, 147, 225, 131, 144, 72, 28, 0, 0, 0, 15, 4, 95, 49, 49, 1, 25, 6, 36, 34, 25, 63, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 4, 16, 20, 63, 25, 36, 55, 37, 10, 0, 0, 14, 4, 95, 49, 50, 1, 25, 6, 39, 34, 63, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 49, 51, 1, 107, 6, 35, 63, 36, 47, 0, 0, 0, 9, 3, 225, 131, 156, 50, 6, 13, 0, 0, 7, 3, 225, 131, 157, 39, 0, 0, 9, 3, 225, 131, 158, 48, 6, 13, 0, 0, 9, 3, 225, 131, 159, 88, 6, 13, 0, 0, 7, 3, 225, 131, 152, 37, 0, 0, 9, 3, 225, 131, 153, 49, 6, 13, 0, 0, 9, 3, 225, 131, 154, 55, 6, 13, 0, 15, 4, 95, 49, 52, 1, 25, 6, 39, 25, 99, 63, 36, 47, 0, 0, 9, 3, 225, 131, 155, 63, 6, 13, 0, 0, 0, 9, 3, 225, 131, 149, 82, 6, 13, 0, 0, 9, 3, 225, 131, 150, 86, 6, 13, 0, 16, 5, 95, 48, 77, 50, 24, 63, 6, 37, 55, 37, 39, 50, 37, 0, 0, 9, 3, 225, 131, 151, 25, 6, 13, 0, 0, 7, 3, 225, 131, 144, 35, 0, 0, 9, 3, 225, 131, 145, 69, 6, 13, 0, 0, 9, 3, 225, 131, 146, 79, 6, 13, 0, 15, 4, 95, 49, 53, 1, 25, 99, 6, 40, 25, 63, 36, 47, 0, 0, 9, 3, 225, 131, 147, 70, 6, 13, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 49, 54, 1, 25, 6, 36, 108, 82, 87, 63, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 49, 55, 1, 74, 82, 6, 37, 70, 63, 36, 47, 0, 0, 0, 0, 0, 0, 14, 5, 95, 48, 77, 49, 24, 6, 35, 25, 35, 87, 37, 0, 0, 0, 11, 3, 225, 131, 184, 36, 55, 37, 81, 37, 0, 0, 0, 0, 9, 3, 225, 131, 181, 105, 39, 36, 0, 0, 9, 3, 225, 131, 180, 105, 35, 34, 0, 0, 10, 3, 225, 131, 183, 87, 105, 82, 35, 0, 0, 8, 3, 225, 131, 182, 81, 37, 0, 0, 8, 3, 225, 131, 177, 105, 36, 0, 0, 9, 3, 225, 131, 176, 105, 6, 13, 0, 0, 9, 3, 225, 131, 179, 82, 37, 36, 0, 0, 9, 3, 225, 131, 178, 105, 37, 36, 0, 0, 9, 3, 225, 131, 173, 78, 6, 13, 0, 0, 9, 3, 225, 131, 172, 110, 6, 13, 0, 0, 9, 3, 225, 131, 175, 73, 6, 13, 0, 0, 9, 3, 225, 131, 174, 99, 6, 13, 0, 0, 9, 3, 225, 131, 169, 74, 6, 13, 0, 0, 9, 3, 225, 131, 168, 89, 6, 13, 0, 0, 9, 3, 225, 131, 171, 109, 6, 13, 0, 0, 9, 3, 225, 131, 170, 107, 6, 13, 0, 0, 9, 3, 225, 131, 165, 108, 6, 13, 0, 0, 9, 3, 225, 131, 164, 106, 6, 13, 0, 0, 9, 3, 225, 131, 167, 102, 6, 13, 0, 0, 9, 3, 225, 131, 166, 98, 6, 13, 0, 0, 9, 3, 225, 131, 161, 87, 6, 13, 0, 0, 9, 3, 225, 131, 160, 34, 6, 13, 0, 0, 13, 3, 225, 131, 163, 40, 50, 69, 34, 37, 79, 40, 0, 7, 3, 225, 131, 163, 40, 0, 0, 9, 3, 225, 131, 162, 47, 6, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 48, 1, 50, 6, 40, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 49, 1, 6, 36, 34, 25, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 95, 50, 1, 6, 39, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 51, 1, 87, 6, 35, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 52, 1, 6, 39, 25, 99, 0, 0, 10, 3, 95, 50, 48, 6, 39, 107, 37, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 53, 1, 99, 6, 40, 25, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 54, 1, 6, 36, 108, 82, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 55, 1, 89, 82, 6, 37, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 48, 90, 53, 63, 36, 6, 35, 87, 37, 35, 25, 35, 87, 36, 70, 37, 0, 13, 3, 95, 54, 48, 87, 6, 35, 63, 39, 110, 37, 0, 0, 20, 4, 95, 48, 90, 52, 63, 36, 6, 35, 25, 37, 35, 25, 35, 87, 36, 70, 37, 0, 8, 3, 95, 48, 67, 35, 87, 0, 0, 0, 19, 4, 95, 48, 90, 54, 63, 36, 63, 6, 37, 55, 37, 39, 50, 36, 70, 37, 0, 0, 15, 4, 95, 48, 90, 49, 63, 36, 6, 35, 25, 36, 70, 37, 0, 13, 4, 95, 52, 48, 1, 6, 39, 34, 63, 39, 110, 0, 0, 0, 17, 4, 95, 48, 90, 51, 63, 36, 6, 35, 25, 35, 87, 36, 70, 37, 0, 0, 15, 4, 95, 48, 90, 50, 63, 36, 6, 35, 87, 36, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 49, 57, 107, 99, 34, 6, 35, 63, 36, 47, 37, 0, 0, 15, 3, 95, 49, 56, 25, 82, 34, 6, 35, 63, 36, 47, 37, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 49, 49, 25, 6, 36, 34, 25, 63, 36, 47, 37, 0, 0, 10, 3, 95, 49, 48, 6, 35, 25, 37, 0, 0, 13, 3, 95, 49, 51, 107, 6, 35, 63, 36, 47, 37, 0, 0, 14, 3, 95, 49, 50, 25, 6, 39, 34, 63, 36, 47, 37, 0, 0, 15, 3, 95, 49, 53, 25, 99, 6, 40, 25, 63, 36, 47, 37, 0, 0, 15, 3, 95, 49, 52, 25, 6, 39, 25, 99, 63, 36, 47, 37, 0, 0, 15, 3, 95, 49, 55, 74, 82, 6, 37, 70, 63, 36, 47, 37, 0, 0, 16, 3, 95, 49, 54, 25, 6, 36, 108, 82, 87, 63, 36, 47, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 52, 48, 6, 39, 34, 63, 39, 110, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 95, 50, 88, 6, 39, 107, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 52, 88, 6, 39, 34, 63, 39, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 48, 6, 39, 25, 99, 39, 110, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 54, 88, 87, 6, 35, 63, 39, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 56, 88, 6, 39, 25, 99, 39, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 48, 77, 50, 63, 6, 37, 55, 37, 39, 50, 0, 0, 0, 0, 12, 4, 95, 48, 77, 49, 6, 35, 25, 35, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 67, 33, 69, 16, 6, 36, 57, 74, 47, 37, 47, 37, 48, 105, 37, 10, 0, 81, 58, 47, 47, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 56, 48, 1, 6, 39, 25, 99, 39, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 4, 95, 225, 131, 148, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 4, 95, 50, 48, 1, 6, 39, 107, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 2, 95, 34, 69, 34, 14, 78, 102, 35, 55, 37, 0, 0, 0, 0, 14, 2, 95, 39, 35, 48, 39, 87, 47, 34, 39, 81, 37, 0, 0, 0, 0, 0, 0, 0, 34, 2, 95, 41, 63, 6, 35, 34, 73, 82, 36, 50, 35, 15, 63, 34, 14, 79, 82, 6, 35, 55, 37, 15, 106, 34, 14, 74, 99, 6, 37, 55, 37, 0, 35, 2, 95, 41, 63, 6, 35, 34, 73, 82, 36, 50, 35, 15, 106, 6, 37, 79, 40, 34, 4, 40, 55, 37, 15, 106, 34, 14, 74, 99, 6, 37, 55, 37, 0, 0, 34, 2, 95, 40, 63, 6, 35, 34, 107, 99, 36, 50, 35, 15, 63, 34, 14, 79, 82, 6, 35, 55, 37, 15, 106, 34, 14, 74, 99, 6, 37, 55, 37, 0, 35, 2, 95, 40, 63, 6, 35, 34, 107, 99, 36, 50, 35, 15, 106, 6, 37, 79, 40, 34, 4, 40, 55, 37, 15, 106, 34, 14, 74, 99, 6, 37, 55, 37, 0, 0, 0, 0, 9, 2, 95, 45, 47, 37, 34, 36, 0, 0, 10, 2, 95, 44, 63, 109, 37, 63, 36, 0, 0, 10, 2, 95, 51, 87, 6, 35, 63, 37, 0, 0, 9, 2, 95, 50, 6, 39, 34, 37, 0, 0, 10, 2, 95, 49, 6, 36, 34, 25, 37, 0, 0, 10, 2, 95, 48, 50, 6, 40, 55, 37, 0, 0, 11, 2, 95, 55, 89, 82, 6, 37, 70, 37, 0, 0, 11, 2, 95, 54, 6, 36, 108, 82, 87, 37, 0, 0, 10, 2, 95, 53, 99, 6, 40, 25, 37, 0, 0, 10, 2, 95, 52, 6, 39, 25, 99, 37, 0, 0, 16, 2, 95, 59, 110, 36, 34, 47, 37, 55, 63, 109, 37, 63, 36, 0, 0, 14, 2, 95, 58, 39, 34, 110, 36, 34, 47, 37, 55, 37, 0, 0, 10, 2, 95, 57, 107, 99, 34, 6, 35, 0, 0, 9, 2, 95, 56, 34, 82, 6, 35, 0, 0, 21, 2, 95, 63, 49, 6, 37, 25, 99, 82, 37, 87, 15, 50, 4, 37, 89, 35, 50, 37, 0, 0, 11, 2, 95, 62, 63, 36, 47, 39, 69, 35, 0, 0, 0, 14, 2, 95, 60, 50, 35, 49, 55, 36, 69, 39, 69, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 37, 2, 95, 91, 63, 6, 35, 34, 107, 99, 36, 50, 35, 15, 49, 82, 6, 35, 70, 34, 35, 47, 4, 40, 55, 37, 15, 106, 34, 14, 74, 99, 6, 37, 55, 37, 0, 0, 0, 0, 0, 0, 0, 35, 2, 95, 93, 63, 6, 35, 34, 73, 82, 36, 50, 35, 15, 106, 6, 37, 79, 40, 34, 4, 40, 55, 37, 15, 106, 34, 14, 74, 99, 6, 37, 55, 37, 0, 0, 0, 0, 0, 0, 21, 2, 95, 96, 40, 49, 40, 98, 63, 35, 15, 35, 48, 39, 87, 47, 34, 39, 81, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 1, 81, 0, 1, 45, 2, 32, 3, 2, 35, 0, 3, 35, 0, 7, 6, 1, 82, 0, 3, 69, 0, 7, 6, 1, 83, 0, 3, 79, 0, 7, 6, 1, 84, 0, 3, 70, 0, 7, 6, 1, 85, 0, 1, 45, 2, 32, 3, 2, 36, 0, 3, 36, 0, 7, 6, 1, 86, 0, 3, 82, 0, 7, 6, 1, 87, 0, 3, 86, 0, 7, 6, 1, 88, 0, 3, 25, 0, 7, 6, 1, 89, 0, 1, 45, 2, 32, 3, 2, 37, 0, 3, 37, 0, 7, 6, 1, 90, 0, 3, 49, 0, 7, 6, 1, 91, 0, 3, 55, 0, 7, 6, 1, 92, 0, 3, 63, 0, 7, 6, 1, 93, 0, 3, 50, 0, 7, 6, 1, 94, 0, 1, 45, 2, 32, 3, 2, 39, 0, 3, 39, 0, 7, 6, 1, 95, 0, 3, 48, 0, 7, 6, 1, 96, 0, 3, 88, 0, 7, 6, 1, 97, 0, 3, 34, 0, 1, 25, 2, 17, 67, 17, 67, 3, 34, 14, 0, 7, 6, 1, 98, 0, 3, 87, 0, 7, 6, 1, 99, 0, 3, 47, 0, 7, 6, 1, 100, 0, 1, 45, 2, 32, 3, 2, 40, 0, 3, 40, 0, 7, 6, 1, 101, 0, 3, 106, 0, 7, 6, 1, 102, 0, 3, 108, 0, 7, 6, 1, 103, 0, 3, 98, 0, 7, 6, 1, 104, 0, 3, 102, 0, 7, 6, 1, 105, 0, 3, 89, 0, 7, 6, 1, 106, 0, 3, 74, 0, 7, 6, 1, 107, 0, 3, 107, 0, 7, 6, 1, 108, 0, 3, 109, 0, 7, 6, 1, 109, 0, 3, 110, 0, 7, 6, 1, 110, 0, 3, 78, 0, 7, 6, 1, 111, 0, 3, 99, 0, 7, 6, 1, 112, 0, 3, 73, 0, 7, 6, 1, 113, 0, 3, 105, 0, 7, 6, 1, 114, 0, 3, 36, 57, 0, 7, 6, 1, 115, 0, 3, 57, 0, 7, 6, 1, 116, 0, 3, 58, 0, 7, 6, 1, 117, 0, 3, 99, 0, 7, 6, 1, 118, 0, 3, 39, 12, 0, 7, 6, 1, 119, 0, 3, 81, 0, 7, 6, 1, 120, 0, 3, 13, 0, 7, 6, 1, 121, 0, 3, 19, 0, 7, 6, 1, 122, 0, 3, 0, 7, 6, 1, 123, 0, 3, 0, 7, 6, 208, 0, 3, 21, 114, 117, 0, 7, 6, 209, 0, 3, 21, 114, 117, 0, 7, 6, 210, 0, 3, 21, 114, 117, 0, 7, 6, 211, 0, 3, 21, 114, 117, 0, 7, 6, 0, 36, 3, 70, 39, 55, 35, 34, 37, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts30 = FileInMemory_createWithData (3219, reinterpret_cast (&espeakdata_dicts30_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ka_dict", L"ka"); Collection_addItem (me.peek(), espeakdata_dicts30.transfer()); static unsigned char espeakdata_dicts31_data[2024] = { 0, 4, 0, 0, 132, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 4, 16, 20, 10, 69, 4, 108, 47, 106, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 4, 95, 48, 90, 53, 88, 6, 108, 86, 15, 63, 4, 107, 66, 50, 110, 50, 0, 11, 3, 95, 51, 88, 6, 39, 47, 107, 86, 0, 0, 18, 4, 95, 48, 90, 52, 6, 39, 50, 15, 63, 4, 107, 66, 50, 110, 50, 0, 10, 3, 95, 48, 67, 88, 6, 108, 86, 0, 0, 22, 4, 95, 48, 90, 55, 6, 39, 50, 15, 63, 37, 55, 55, 37, 4, 39, 50, 50, 110, 50, 0, 0, 18, 4, 95, 48, 90, 54, 63, 37, 55, 55, 37, 6, 39, 50, 50, 110, 50, 0, 0, 13, 4, 95, 48, 90, 49, 6, 39, 50, 50, 110, 50, 0, 0, 0, 14, 4, 95, 48, 90, 51, 63, 6, 107, 66, 50, 110, 50, 0, 0, 14, 4, 95, 48, 90, 50, 88, 6, 108, 86, 70, 36, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 4, 95, 48, 90, 57, 63, 37, 55, 55, 37, 6, 110, 34, 70, 47, 110, 50, 0, 0, 23, 4, 95, 48, 90, 56, 88, 6, 108, 86, 15, 63, 37, 55, 55, 37, 6, 39, 50, 50, 110, 50, 0, 0, 0, 0, 13, 3, 95, 55, 88, 88, 6, 36, 47, 48, 106, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 95, 49, 88, 6, 39, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 50, 88, 88, 37, 6, 107, 34, 63, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 52, 88, 102, 6, 107, 34, 107, 102, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 53, 88, 6, 36, 55, 38, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 54, 88, 6, 110, 55, 48, 107, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 88, 87, 6, 36, 49, 87, 36, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 57, 88, 47, 6, 39, 102, 87, 110, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 48, 77, 50, 63, 37, 55, 55, 37, 6, 39, 50, 0, 0, 16, 4, 95, 48, 77, 51, 63, 37, 55, 55, 37, 6, 110, 34, 70, 0, 0, 0, 11, 4, 95, 48, 77, 49, 63, 6, 107, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 209, 135, 74, 36, 0, 0, 8, 2, 209, 134, 47, 87, 36, 0, 0, 7, 2, 209, 133, 104, 110, 0, 0, 7, 2, 209, 132, 112, 81, 0, 0, 0, 7, 2, 209, 130, 47, 36, 0, 0, 7, 2, 209, 129, 112, 87, 0, 0, 7, 2, 209, 128, 112, 34, 0, 0, 0, 0, 0, 15, 2, 209, 140, 88, 106, 66, 106, 89, 49, 36, 55, 106, 49, 0, 0, 0, 10, 2, 209, 138, 110, 57, 107, 34, 40, 0, 0, 8, 2, 209, 137, 89, 74, 35, 0, 0, 7, 2, 209, 136, 89, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 210, 147, 114, 36, 0, 0, 0, 0, 0, 7, 2, 95, 51, 108, 89, 0, 0, 9, 2, 95, 50, 36, 49, 6, 106, 0, 0, 9, 2, 95, 49, 69, 6, 106, 34, 0, 0, 9, 2, 95, 48, 50, 6, 113, 55, 0, 0, 11, 2, 95, 55, 88, 6, 36, 47, 6, 106, 0, 7, 2, 210, 155, 102, 110, 0, 0, 10, 2, 95, 54, 110, 55, 47, 6, 107, 0, 0, 9, 2, 95, 53, 69, 6, 36, 87, 0, 0, 10, 2, 95, 52, 47, 6, 113, 34, 47, 0, 0, 7, 2, 208, 183, 86, 36, 0, 0, 7, 2, 208, 182, 88, 36, 0, 0, 11, 2, 95, 57, 47, 39, 114, 6, 107, 86, 0, 0, 11, 2, 95, 56, 87, 36, 79, 6, 106, 86, 0, 7, 2, 208, 180, 70, 36, 0, 0, 7, 2, 210, 163, 112, 66, 0, 7, 2, 208, 179, 79, 36, 0, 0, 7, 2, 208, 178, 82, 36, 0, 0, 7, 2, 208, 177, 69, 36, 0, 0, 0, 7, 2, 208, 191, 48, 36, 0, 0, 0, 7, 2, 208, 189, 112, 50, 0, 0, 7, 2, 208, 188, 112, 63, 0, 0, 7, 2, 208, 187, 112, 55, 0, 0, 7, 2, 208, 186, 49, 110, 0, 0, 12, 2, 208, 185, 102, 107, 87, 102, 110, 6, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 210, 187, 105, 110, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 1, 17, 0, 2, 208, 185, 3, 35, 0, 3, 110, 0, 7, 6, 1, 18, 0, 3, 69, 0, 7, 6, 1, 19, 0, 3, 82, 0, 7, 6, 1, 20, 0, 3, 79, 0, 7, 6, 1, 21, 0, 3, 70, 0, 7, 6, 1, 22, 0, 3, 36, 0, 7, 6, 1, 23, 0, 3, 88, 0, 7, 6, 1, 24, 0, 3, 86, 0, 7, 6, 1, 25, 0, 3, 37, 0, 7, 6, 1, 26, 0, 3, 57, 0, 7, 6, 1, 27, 0, 3, 49, 0, 7, 6, 1, 28, 0, 3, 55, 0, 7, 6, 1, 29, 0, 3, 63, 0, 7, 6, 1, 30, 0, 3, 50, 0, 7, 6, 1, 31, 0, 3, 39, 0, 7, 6, 1, 32, 0, 3, 48, 0, 7, 6, 1, 33, 0, 3, 34, 0, 7, 6, 1, 34, 0, 3, 87, 0, 7, 6, 1, 35, 0, 3, 47, 0, 7, 6, 1, 36, 0, 3, 40, 0, 4, 1, 17, 65, 3, 58, 0, 2, 17, 65, 0, 7, 6, 1, 37, 0, 3, 81, 0, 7, 6, 1, 38, 0, 3, 104, 0, 7, 6, 1, 39, 0, 3, 47, 87, 0, 7, 6, 1, 40, 0, 3, 74, 0, 7, 6, 1, 41, 0, 3, 89, 0, 7, 6, 1, 42, 0, 3, 89, 74, 0, 7, 6, 1, 44, 0, 3, 107, 0, 7, 6, 1, 46, 0, 3, 112, 0, 7, 6, 1, 47, 0, 3, 38, 40, 0, 7, 6, 1, 48, 0, 3, 38, 35, 0, 7, 6, 1, 50, 0, 3, 38, 39, 0, 7, 6, 1, 55, 0, 3, 106, 0, 7, 6, 1, 116, 0, 3, 114, 0, 7, 6, 1, 124, 0, 3, 102, 0, 7, 6, 210, 163, 0, 3, 66, 0, 7, 6, 210, 175, 0, 3, 108, 0, 7, 6, 210, 177, 0, 3, 109, 0, 7, 6, 210, 187, 0, 3, 105, 0, 7, 6, 211, 153, 0, 3, 111, 0, 7, 6, 211, 169, 0, 3, 113, 0, 7, 6, 0, 4, 209, 138, 3, 0, 209, 140, 3, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts31 = FileInMemory_createWithData (2023, reinterpret_cast (&espeakdata_dicts31_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/kk_dict", L"kk"); Collection_addItem (me.peek(), espeakdata_dicts31.transfer()); static unsigned char espeakdata_dicts32_data[5368] = { 0, 4, 0, 0, 127, 17, 0, 0, 0, 0, 0, 0, 0, 6, 65, 4, 112, 57, 0, 0, 0, 0, 0, 6, 65, 8, 69, 110, 0, 0, 0, 0, 0, 6, 65, 12, 87, 110, 0, 0, 0, 0, 0, 6, 65, 16, 70, 110, 0, 0, 0, 11, 6, 224, 178, 149, 224, 179, 141, 37, 49, 0, 0, 0, 5, 65, 20, 110, 0, 0, 0, 0, 0, 6, 65, 24, 114, 81, 0, 0, 0, 0, 0, 6, 65, 28, 73, 110, 0, 0, 0, 0, 0, 6, 65, 32, 112, 74, 0, 0, 16, 1, 33, 116, 87, 142, 35, 34, 57, 35, 142, 37, 50, 105, 36, 0, 0, 0, 0, 6, 65, 36, 116, 57, 0, 0, 13, 1, 37, 48, 34, 35, 47, 37, 91, 35, 47, 35, 0, 0, 9, 1, 38, 63, 35, 47, 47, 40, 0, 0, 0, 7, 65, 40, 73, 112, 57, 0, 0, 0, 0, 0, 14, 1, 44, 35, 55, 48, 35, 82, 37, 34, 116, 63, 35, 0, 7, 65, 44, 49, 112, 57, 0, 0, 0, 15, 1, 46, 48, 121, 34, 64, 35, 82, 37, 34, 116, 63, 35, 0, 0, 0, 6, 65, 48, 114, 55, 0, 0, 13, 1, 49, 49, 116, 55, 40, 0, 82, 47, 32, 52, 32, 13, 1, 49, 35, 34, 137, 35, 0, 82, 47, 32, 50, 32, 0, 0, 16, 1, 51, 63, 40, 49, 49, 116, 55, 40, 0, 82, 47, 32, 52, 32, 0, 6, 65, 52, 114, 63, 0, 0, 0, 0, 0, 6, 65, 56, 114, 50, 0, 0, 0, 0, 0, 5, 65, 60, 117, 0, 0, 0, 0, 0, 6, 65, 64, 48, 110, 0, 0, 15, 140, 224, 178, 164, 224, 178, 174, 224, 179, 141, 224, 178, 174, 72, 0, 0, 0, 7, 65, 68, 49, 57, 121, 0, 0, 0, 0, 0, 15, 140, 224, 178, 135, 224, 178, 181, 224, 178, 168, 224, 179, 129, 72, 6, 65, 72, 116, 34, 0, 0, 0, 0, 0, 6, 65, 76, 114, 87, 0, 0, 0, 0, 12, 4, 95, 48, 67, 48, 50, 6, 121, 34, 40, 0, 0, 6, 65, 80, 136, 110, 0, 0, 0, 25, 149, 224, 178, 134, 224, 178, 166, 224, 178, 190, 224, 178, 151, 224, 179, 141, 224, 178, 175, 224, 179, 130, 72, 8, 0, 0, 6, 65, 84, 57, 121, 0, 0, 0, 0, 0, 6, 65, 88, 82, 110, 0, 0, 0, 0, 0, 11, 65, 92, 70, 35, 69, 35, 55, 57, 121, 0, 0, 0, 0, 0, 7, 65, 96, 114, 49, 87, 0, 0, 0, 0, 0, 7, 65, 100, 58, 116, 57, 0, 0, 0, 0, 0, 15, 140, 224, 178, 135, 224, 178, 181, 224, 178, 179, 224, 179, 129, 72, 7, 65, 104, 86, 114, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 178, 168, 224, 178, 168, 224, 179, 141, 224, 178, 168, 72, 0, 0, 0, 18, 143, 224, 178, 168, 224, 178, 191, 224, 178, 168, 224, 179, 141, 224, 178, 168, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 4, 95, 49, 67, 48, 50, 121, 34, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 50, 67, 48, 6, 37, 50, 50, 121, 34, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 4, 16, 20, 10, 70, 6, 35, 91, 116, 63, 91, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 5, 95, 48, 77, 50, 24, 55, 6, 35, 49, 89, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 5, 95, 48, 77, 49, 24, 87, 6, 116, 82, 37, 34, 35, 0, 11, 6, 224, 178, 175, 224, 179, 141, 37, 57, 0, 0, 0, 0, 0, 11, 6, 224, 178, 173, 224, 179, 141, 37, 135, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 51, 67, 48, 63, 6, 40, 50, 50, 121, 34, 40, 0, 0, 0, 0, 0, 0, 11, 6, 224, 178, 179, 224, 179, 141, 37, 62, 0, 11, 6, 224, 178, 171, 224, 179, 141, 37, 134, 0, 0, 0, 0, 0, 11, 6, 224, 178, 177, 224, 179, 141, 37, 34, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 224, 178, 133, 224, 178, 181, 224, 179, 129, 72, 0, 0, 0, 15, 140, 224, 178, 185, 224, 178, 178, 224, 178, 181, 224, 179, 129, 72, 15, 140, 224, 178, 164, 224, 178, 190, 224, 178, 181, 224, 179, 129, 72, 15, 140, 224, 178, 168, 224, 178, 190, 224, 178, 181, 224, 179, 129, 72, 0, 0, 11, 6, 224, 178, 159, 224, 179, 141, 37, 138, 0, 0, 18, 143, 224, 178, 149, 224, 179, 134, 224, 178, 178, 224, 178, 181, 224, 179, 129, 72, 0, 0, 0, 11, 6, 224, 178, 157, 224, 179, 141, 37, 143, 0, 0, 0, 15, 140, 224, 178, 133, 224, 178, 168, 224, 179, 135, 224, 178, 149, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 178, 163, 224, 179, 141, 37, 64, 0, 11, 6, 224, 178, 155, 224, 179, 141, 37, 142, 0, 0, 0, 0, 0, 11, 6, 224, 178, 185, 224, 179, 141, 37, 105, 0, 11, 6, 224, 178, 161, 224, 179, 141, 37, 139, 0, 11, 6, 224, 178, 153, 224, 179, 141, 37, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 178, 167, 224, 179, 141, 37, 139, 0, 0, 0, 0, 0, 12, 137, 224, 178, 133, 224, 178, 181, 224, 178, 176, 72, 11, 6, 224, 178, 165, 224, 179, 141, 37, 136, 0, 0, 12, 137, 224, 178, 133, 224, 178, 181, 224, 178, 179, 72, 0, 0, 0, 0, 0, 0, 0, 12, 137, 224, 178, 133, 224, 178, 181, 224, 178, 168, 72, 0, 0, 0, 18, 143, 224, 178, 135, 224, 178, 181, 224, 179, 129, 224, 178, 151, 224, 178, 179, 72, 18, 143, 224, 178, 133, 224, 178, 181, 224, 179, 129, 224, 178, 151, 224, 178, 179, 72, 0, 0, 0, 0, 0, 0, 15, 140, 224, 178, 168, 224, 178, 174, 224, 179, 141, 224, 178, 174, 72, 0, 0, 0, 18, 143, 224, 178, 168, 224, 178, 191, 224, 178, 174, 224, 179, 141, 224, 178, 174, 72, 0, 0, 0, 0, 0, 19, 3, 95, 51, 57, 63, 6, 39, 82, 35, 136, 39, 63, 69, 35, 136, 12, 40, 0, 18, 3, 95, 50, 49, 6, 111, 48, 12, 35, 6, 136, 12, 39, 50, 70, 40, 0, 0, 15, 140, 224, 178, 168, 224, 179, 128, 224, 178, 181, 224, 179, 129, 72, 16, 3, 95, 51, 56, 63, 6, 39, 82, 35, 136, 36, 50, 138, 40, 0, 0, 18, 3, 95, 50, 51, 111, 48, 12, 35, 6, 136, 12, 63, 6, 121, 34, 40, 0, 0, 18, 3, 95, 50, 50, 111, 48, 12, 35, 6, 136, 12, 36, 34, 35, 139, 40, 0, 11, 6, 224, 178, 183, 224, 179, 141, 37, 91, 0, 0, 17, 3, 95, 50, 53, 111, 48, 12, 35, 6, 136, 12, 6, 132, 70, 40, 0, 0, 15, 140, 224, 178, 133, 224, 178, 181, 224, 178, 179, 224, 179, 129, 72, 19, 3, 95, 50, 52, 111, 48, 12, 35, 6, 136, 12, 50, 6, 116, 55, 49, 40, 0, 0, 16, 3, 95, 50, 55, 111, 48, 12, 35, 6, 136, 12, 112, 62, 40, 0, 0, 16, 3, 95, 50, 54, 111, 48, 12, 35, 6, 136, 12, 116, 34, 40, 0, 11, 6, 224, 178, 181, 224, 179, 141, 37, 82, 0, 0, 17, 3, 95, 51, 49, 63, 6, 39, 82, 35, 136, 12, 39, 50, 70, 40, 0, 0, 0, 17, 3, 95, 51, 51, 63, 6, 39, 82, 35, 136, 63, 6, 121, 34, 40, 0, 0, 17, 3, 95, 51, 50, 63, 6, 39, 82, 35, 136, 36, 34, 35, 139, 40, 0, 0, 16, 3, 95, 51, 53, 63, 6, 39, 82, 35, 136, 6, 132, 70, 40, 0, 0, 18, 3, 95, 51, 52, 63, 6, 39, 82, 35, 136, 50, 6, 116, 55, 49, 40, 0, 0, 15, 3, 95, 51, 55, 63, 6, 39, 82, 35, 136, 112, 62, 40, 0, 0, 15, 3, 95, 51, 54, 63, 6, 39, 82, 35, 136, 116, 34, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 55, 57, 114, 48, 12, 35, 136, 39, 63, 69, 35, 136, 12, 40, 0, 17, 3, 95, 54, 49, 35, 34, 35, 82, 35, 136, 12, 39, 50, 70, 40, 0, 0, 15, 3, 95, 55, 56, 114, 48, 12, 35, 136, 36, 50, 138, 40, 0, 14, 3, 95, 51, 88, 63, 6, 39, 82, 35, 136, 12, 40, 0, 0, 11, 3, 95, 48, 67, 50, 6, 121, 34, 116, 0, 17, 3, 95, 54, 51, 35, 34, 35, 82, 35, 136, 63, 6, 121, 34, 40, 0, 0, 17, 3, 95, 54, 50, 35, 34, 35, 82, 35, 136, 36, 34, 35, 139, 40, 0, 0, 15, 3, 95, 54, 53, 35, 34, 35, 82, 35, 136, 132, 70, 40, 0, 0, 18, 3, 95, 54, 52, 35, 34, 35, 82, 35, 136, 50, 6, 116, 55, 49, 40, 0, 0, 15, 3, 95, 54, 55, 35, 34, 35, 82, 35, 136, 112, 62, 40, 0, 0, 15, 3, 95, 54, 54, 35, 34, 35, 82, 35, 136, 116, 34, 40, 0, 0, 16, 3, 95, 55, 49, 114, 48, 12, 35, 136, 12, 39, 50, 70, 40, 0, 0, 0, 10, 3, 95, 49, 67, 50, 121, 34, 116, 0, 16, 3, 95, 55, 51, 114, 48, 12, 35, 136, 63, 6, 121, 34, 40, 0, 0, 16, 3, 95, 55, 50, 114, 48, 12, 35, 136, 36, 34, 35, 139, 40, 0, 0, 14, 3, 95, 55, 53, 114, 48, 12, 35, 136, 132, 70, 40, 0, 0, 17, 3, 95, 55, 52, 114, 48, 12, 35, 136, 50, 6, 116, 55, 49, 40, 0, 0, 13, 4, 95, 53, 67, 48, 6, 132, 50, 121, 34, 40, 0, 14, 3, 95, 55, 55, 114, 48, 12, 35, 136, 112, 62, 40, 0, 0, 14, 3, 95, 55, 54, 114, 48, 12, 35, 136, 116, 34, 40, 0, 0, 19, 3, 95, 49, 57, 105, 35, 6, 136, 12, 6, 39, 63, 69, 35, 136, 12, 40, 0, 0, 16, 3, 95, 49, 56, 105, 35, 70, 37, 50, 6, 36, 50, 138, 40, 0, 0, 13, 3, 95, 50, 67, 6, 37, 50, 50, 121, 34, 116, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 50, 57, 111, 48, 12, 35, 6, 136, 12, 39, 63, 69, 35, 136, 12, 40, 0, 15, 3, 95, 49, 49, 105, 35, 50, 50, 6, 39, 50, 70, 40, 0, 0, 17, 3, 95, 50, 56, 111, 48, 12, 35, 6, 136, 12, 36, 50, 138, 40, 0, 0, 14, 3, 95, 51, 67, 63, 6, 40, 50, 50, 121, 34, 116, 0, 15, 3, 95, 49, 51, 105, 35, 70, 37, 63, 6, 121, 34, 40, 0, 0, 15, 3, 95, 49, 50, 105, 35, 50, 12, 36, 34, 35, 139, 40, 0, 0, 14, 3, 95, 49, 53, 105, 35, 70, 37, 50, 132, 70, 40, 0, 0, 16, 3, 95, 49, 52, 105, 35, 70, 37, 50, 6, 116, 55, 49, 40, 0, 0, 15, 3, 95, 49, 55, 105, 35, 70, 37, 50, 6, 112, 62, 40, 0, 0, 14, 3, 95, 49, 54, 105, 35, 70, 37, 50, 116, 34, 40, 0, 0, 0, 14, 3, 95, 55, 88, 6, 114, 48, 12, 35, 136, 12, 40, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 52, 57, 50, 6, 35, 55, 35, 82, 35, 136, 39, 63, 69, 35, 136, 12, 40, 0, 0, 18, 3, 95, 52, 56, 50, 6, 35, 55, 35, 82, 35, 136, 36, 50, 138, 40, 0, 0, 12, 3, 95, 53, 67, 6, 132, 50, 121, 34, 116, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 53, 57, 132, 82, 35, 136, 39, 63, 69, 35, 136, 12, 40, 0, 19, 3, 95, 52, 49, 50, 6, 35, 55, 35, 82, 35, 136, 12, 39, 50, 70, 40, 0, 0, 14, 3, 95, 53, 56, 132, 82, 35, 136, 36, 50, 138, 40, 0, 12, 3, 95, 49, 88, 105, 6, 35, 136, 12, 40, 0, 0, 19, 3, 95, 52, 51, 50, 6, 35, 55, 35, 82, 35, 136, 63, 6, 121, 34, 40, 0, 0, 19, 3, 95, 52, 50, 50, 6, 35, 55, 35, 82, 35, 136, 36, 34, 35, 139, 40, 0, 0, 17, 3, 95, 52, 53, 50, 6, 35, 55, 35, 82, 35, 136, 132, 70, 40, 0, 0, 20, 3, 95, 52, 52, 50, 6, 35, 55, 35, 82, 35, 136, 50, 6, 116, 55, 49, 40, 0, 0, 17, 3, 95, 52, 55, 50, 6, 35, 55, 35, 82, 35, 136, 112, 62, 40, 0, 0, 17, 3, 95, 52, 54, 50, 6, 35, 55, 35, 82, 35, 136, 116, 34, 40, 0, 0, 19, 3, 95, 54, 57, 35, 34, 35, 82, 35, 136, 39, 63, 69, 35, 136, 12, 40, 0, 15, 3, 95, 53, 49, 132, 82, 35, 136, 12, 39, 50, 70, 40, 0, 0, 16, 3, 95, 54, 56, 35, 34, 35, 82, 35, 136, 36, 50, 138, 40, 0, 13, 3, 95, 50, 88, 111, 48, 12, 35, 136, 12, 40, 0, 0, 15, 3, 95, 53, 51, 132, 82, 35, 136, 63, 6, 121, 34, 40, 0, 0, 15, 3, 95, 53, 50, 132, 82, 35, 136, 36, 34, 35, 139, 40, 0, 0, 14, 3, 95, 53, 53, 132, 82, 35, 136, 6, 132, 70, 40, 0, 0, 16, 3, 95, 53, 52, 132, 82, 35, 136, 50, 6, 116, 55, 49, 40, 0, 0, 13, 3, 95, 53, 55, 132, 82, 35, 136, 112, 62, 40, 0, 0, 13, 3, 95, 53, 54, 132, 82, 35, 136, 116, 34, 40, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 63, 63, 35, 49, 91, 35, 34, 35, 0, 0, 0, 18, 3, 95, 56, 57, 114, 63, 69, 35, 136, 39, 63, 69, 35, 136, 12, 40, 0, 0, 15, 3, 95, 56, 56, 114, 63, 69, 35, 136, 36, 50, 138, 40, 0, 16, 3, 95, 52, 88, 50, 6, 35, 55, 35, 82, 35, 136, 12, 40, 0, 0, 15, 3, 95, 57, 67, 39, 63, 69, 35, 37, 50, 121, 34, 116, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 57, 57, 136, 6, 39, 63, 69, 35, 136, 39, 63, 69, 35, 136, 12, 40, 0, 16, 3, 95, 56, 49, 114, 63, 69, 35, 136, 12, 39, 50, 70, 40, 0, 0, 17, 3, 95, 57, 56, 136, 6, 39, 63, 69, 35, 136, 36, 50, 138, 40, 0, 13, 3, 95, 53, 88, 6, 132, 82, 35, 136, 12, 40, 0, 0, 16, 3, 95, 56, 51, 114, 63, 69, 35, 136, 63, 6, 121, 34, 40, 0, 0, 16, 3, 95, 56, 50, 114, 63, 69, 35, 136, 36, 34, 35, 139, 40, 0, 0, 14, 3, 95, 56, 53, 114, 63, 69, 35, 136, 132, 70, 40, 0, 0, 17, 3, 95, 56, 52, 114, 63, 69, 35, 136, 50, 6, 116, 55, 49, 40, 0, 0, 14, 3, 95, 56, 55, 114, 63, 69, 35, 136, 112, 62, 40, 0, 0, 14, 3, 95, 56, 54, 114, 63, 69, 35, 136, 116, 34, 40, 0, 0, 18, 3, 95, 57, 49, 136, 6, 39, 63, 69, 35, 136, 12, 39, 50, 70, 40, 0, 0, 15, 3, 95, 54, 88, 6, 35, 34, 35, 82, 35, 136, 12, 40, 0, 0, 18, 3, 95, 57, 51, 136, 6, 39, 63, 69, 35, 136, 63, 6, 121, 34, 40, 0, 0, 19, 3, 95, 57, 50, 136, 6, 39, 63, 69, 35, 136, 12, 36, 34, 35, 139, 40, 0, 0, 16, 3, 95, 57, 53, 136, 6, 39, 63, 69, 35, 136, 132, 70, 40, 0, 0, 19, 3, 95, 57, 52, 136, 6, 39, 63, 69, 35, 136, 50, 6, 116, 55, 49, 40, 0, 0, 12, 137, 224, 178, 135, 224, 178, 181, 224, 179, 129, 72, 16, 3, 95, 57, 55, 136, 6, 39, 63, 69, 35, 136, 112, 62, 40, 0, 0, 16, 3, 95, 57, 54, 136, 6, 39, 63, 69, 35, 136, 116, 34, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 179, 158, 224, 179, 141, 37, 81, 0, 11, 6, 224, 178, 150, 224, 179, 141, 37, 144, 0, 0, 0, 14, 3, 95, 56, 88, 6, 114, 63, 69, 35, 136, 12, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 57, 88, 136, 6, 39, 63, 69, 35, 136, 12, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 224, 178, 135, 224, 178, 181, 224, 178, 168, 72, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 224, 178, 135, 224, 178, 181, 224, 178, 179, 72, 0, 12, 137, 224, 178, 135, 224, 178, 181, 224, 178, 176, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 48, 77, 52, 69, 6, 37, 55, 37, 39, 50, 0, 0, 0, 15, 4, 95, 48, 77, 50, 55, 6, 35, 49, 89, 35, 70, 35, 0, 0, 12, 4, 95, 48, 77, 51, 49, 6, 39, 138, 37, 0, 0, 0, 16, 4, 95, 48, 77, 49, 87, 6, 116, 82, 37, 34, 35, 70, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 224, 178, 136, 76, 0, 0, 6, 131, 224, 178, 134, 76, 0, 0, 8, 3, 224, 179, 140, 146, 133, 0, 0, 11, 3, 224, 179, 141, 82, 35, 47, 47, 40, 0, 0, 8, 3, 224, 179, 138, 18, 39, 0, 8, 3, 224, 178, 130, 35, 63, 0, 0, 9, 3, 224, 179, 139, 146, 117, 12, 0, 8, 3, 224, 178, 131, 35, 105, 0, 0, 8, 3, 224, 179, 136, 146, 132, 0, 0, 0, 8, 3, 224, 179, 134, 18, 36, 0, 0, 9, 3, 224, 179, 135, 146, 112, 12, 0, 0, 9, 3, 224, 179, 132, 146, 44, 12, 0, 0, 0, 9, 3, 224, 179, 130, 146, 121, 12, 0, 0, 9, 3, 224, 179, 131, 18, 34, 40, 0, 0, 9, 3, 224, 179, 128, 146, 110, 12, 0, 0, 8, 3, 224, 179, 129, 18, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 178, 135, 224, 178, 181, 224, 178, 176, 224, 179, 129, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 67, 65, 101, 0, 48, 34, 132, 82, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 224, 178, 190, 146, 116, 12, 0, 0, 8, 3, 224, 178, 191, 18, 37, 0, 0, 21, 67, 33, 69, 16, 112, 74, 47, 110, 47, 110, 6, 48, 110, 10, 0, 81, 58, 47, 47, 32, 11, 3, 224, 178, 188, 50, 40, 49, 47, 35, 0, 0, 14, 3, 224, 178, 189, 35, 82, 35, 79, 34, 35, 105, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 57, 67, 48, 39, 63, 69, 35, 37, 50, 121, 34, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 2, 194, 190, 63, 40, 49, 49, 116, 55, 40, 0, 0, 13, 2, 195, 183, 135, 116, 79, 116, 49, 116, 34, 35, 0, 0, 9, 2, 194, 188, 49, 116, 55, 40, 0, 0, 9, 2, 194, 189, 35, 34, 137, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 224, 178, 136, 224, 178, 151, 72, 0, 0, 11, 6, 224, 178, 168, 224, 179, 141, 37, 50, 0, 0, 0, 0, 0, 11, 6, 224, 178, 174, 224, 179, 141, 37, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 178, 172, 224, 179, 141, 37, 69, 0, 11, 6, 224, 178, 164, 224, 179, 141, 37, 47, 0, 0, 0, 0, 0, 11, 6, 224, 178, 178, 224, 179, 141, 37, 55, 0, 11, 6, 224, 178, 170, 224, 179, 141, 37, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 178, 184, 224, 179, 141, 37, 87, 0, 11, 6, 224, 178, 176, 224, 179, 141, 37, 34, 0, 11, 6, 224, 178, 152, 224, 179, 141, 37, 145, 0, 0, 0, 15, 140, 224, 178, 133, 224, 178, 181, 224, 178, 168, 224, 179, 129, 72, 10, 2, 95, 51, 63, 6, 121, 34, 40, 0, 0, 11, 2, 95, 50, 6, 36, 34, 35, 139, 40, 0, 0, 21, 146, 224, 178, 175, 224, 178, 190, 224, 178, 181, 224, 179, 129, 224, 178, 166, 224, 179, 129, 72, 10, 2, 95, 49, 6, 39, 50, 70, 40, 0, 11, 6, 224, 178, 158, 224, 179, 141, 37, 65, 0, 0, 11, 2, 95, 48, 87, 6, 39, 50, 50, 36, 0, 0, 21, 146, 224, 178, 175, 224, 178, 190, 224, 178, 181, 224, 179, 129, 224, 178, 166, 224, 179, 135, 72, 9, 2, 95, 55, 6, 112, 62, 40, 0, 0, 9, 2, 95, 54, 6, 116, 34, 40, 0, 0, 12, 137, 224, 178, 135, 224, 178, 164, 224, 178, 176, 72, 9, 2, 95, 53, 6, 132, 70, 40, 0, 0, 11, 2, 95, 52, 50, 6, 116, 55, 49, 40, 0, 0, 0, 0, 13, 2, 95, 57, 6, 39, 63, 69, 35, 136, 12, 40, 0, 0, 10, 2, 95, 56, 6, 36, 50, 138, 40, 0, 0, 11, 2, 95, 63, 35, 49, 91, 35, 34, 35, 0, 0, 0, 11, 6, 224, 178, 156, 224, 179, 141, 37, 77, 0, 0, 0, 0, 14, 9, 224, 178, 156, 224, 178, 188, 224, 179, 141, 37, 86, 0, 14, 9, 224, 178, 171, 224, 178, 188, 224, 179, 141, 37, 81, 0, 0, 11, 6, 224, 178, 162, 224, 179, 141, 37, 141, 0, 11, 6, 224, 178, 154, 224, 179, 141, 37, 78, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 224, 178, 135, 224, 178, 166, 224, 179, 129, 72, 12, 137, 224, 178, 133, 224, 178, 166, 224, 179, 129, 72, 0, 0, 16, 140, 224, 178, 134, 224, 178, 166, 224, 178, 176, 224, 179, 134, 72, 8, 0, 0, 0, 11, 6, 224, 178, 160, 224, 179, 141, 37, 140, 0, 0, 0, 15, 140, 224, 178, 133, 224, 178, 181, 224, 178, 176, 224, 179, 129, 72, 15, 140, 224, 178, 168, 224, 179, 128, 224, 178, 168, 224, 179, 129, 72, 15, 140, 224, 178, 168, 224, 178, 190, 224, 178, 168, 224, 179, 129, 72, 0, 0, 11, 6, 224, 178, 166, 224, 179, 141, 37, 70, 0, 0, 19, 143, 224, 178, 174, 224, 178, 164, 224, 179, 141, 224, 178, 164, 224, 179, 129, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 224, 178, 135, 224, 178, 130, 224, 178, 166, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 224, 178, 135, 224, 178, 166, 224, 178, 176, 72, 12, 137, 224, 178, 133, 224, 178, 166, 224, 178, 176, 72, 11, 6, 224, 178, 182, 224, 179, 141, 37, 95, 0, 0, 28, 152, 224, 178, 134, 224, 178, 166, 224, 179, 141, 224, 178, 166, 224, 178, 176, 224, 178, 191, 224, 178, 130, 224, 178, 166, 72, 8, 16, 70, 44, 19, 142, 4, 64, 64, 49, 35, 50, 50, 35, 139, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 178, 151, 224, 179, 141, 37, 79, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 0, 230, 12, 0, 0, 48, 0, 0, 0, 231, 12, 0, 0, 49, 0, 0, 0, 232, 12, 0, 0, 50, 0, 0, 0, 233, 12, 0, 0, 51, 0, 0, 0, 234, 12, 0, 0, 52, 0, 0, 0, 235, 12, 0, 0, 53, 0, 0, 0, 236, 12, 0, 0, 54, 0, 0, 0, 237, 12, 0, 0, 55, 0, 0, 0, 238, 12, 0, 0, 56, 0, 0, 0, 239, 12, 0, 0, 57, 0, 0, 0, 0, 0, 0, 0, 6, 1, 6, 0, 3, 35, 0, 7, 6, 1, 7, 0, 3, 116, 0, 7, 6, 1, 8, 0, 3, 37, 0, 7, 6, 1, 9, 0, 3, 110, 0, 7, 6, 1, 10, 0, 3, 40, 0, 7, 6, 1, 11, 0, 3, 121, 0, 7, 6, 1, 12, 0, 3, 34, 40, 0, 7, 6, 1, 15, 0, 3, 36, 0, 7, 6, 1, 16, 0, 3, 112, 0, 7, 6, 1, 17, 0, 3, 132, 0, 7, 6, 1, 19, 0, 3, 39, 0, 7, 6, 1, 20, 0, 3, 117, 0, 7, 6, 1, 21, 0, 3, 133, 0, 7, 6, 1, 22, 0, 2, 17, 66, 3, 49, 0, 3, 49, 35, 0, 7, 6, 1, 23, 0, 2, 17, 66, 3, 144, 0, 3, 144, 35, 0, 7, 6, 1, 24, 0, 2, 17, 66, 3, 79, 0, 3, 79, 35, 0, 7, 6, 1, 25, 0, 2, 17, 66, 3, 145, 0, 3, 145, 35, 0, 7, 6, 1, 26, 0, 2, 17, 66, 3, 66, 0, 3, 66, 35, 0, 7, 6, 1, 27, 0, 2, 17, 66, 3, 78, 0, 3, 78, 35, 0, 7, 6, 1, 28, 0, 2, 17, 66, 3, 142, 0, 3, 142, 35, 0, 7, 6, 1, 29, 0, 2, 17, 66, 3, 77, 0, 3, 77, 35, 0, 224, 178, 188, 2, 17, 66, 3, 86, 0, 224, 178, 188, 3, 86, 35, 0, 7, 6, 1, 30, 0, 2, 17, 66, 3, 143, 0, 3, 143, 35, 0, 7, 6, 1, 31, 0, 2, 17, 66, 3, 65, 0, 3, 65, 35, 0, 7, 6, 1, 32, 0, 2, 17, 66, 3, 138, 0, 3, 138, 35, 0, 7, 6, 1, 33, 0, 2, 17, 66, 3, 140, 0, 3, 140, 35, 0, 7, 6, 1, 34, 0, 2, 17, 66, 3, 139, 0, 3, 139, 35, 0, 7, 6, 1, 35, 0, 2, 17, 66, 3, 141, 0, 3, 141, 35, 0, 7, 6, 1, 36, 0, 2, 17, 66, 3, 64, 0, 3, 64, 35, 0, 7, 6, 1, 37, 0, 2, 17, 66, 3, 47, 0, 3, 47, 35, 0, 7, 6, 1, 38, 0, 2, 17, 66, 3, 136, 0, 3, 136, 35, 0, 7, 6, 1, 39, 0, 2, 17, 66, 3, 70, 0, 3, 70, 35, 0, 7, 6, 1, 40, 0, 2, 17, 66, 3, 137, 0, 3, 137, 35, 0, 7, 6, 1, 41, 0, 2, 17, 66, 3, 50, 0, 3, 50, 35, 0, 7, 6, 1, 43, 0, 2, 17, 66, 3, 48, 0, 3, 48, 35, 0, 7, 6, 1, 44, 0, 224, 178, 188, 2, 17, 66, 3, 81, 0, 224, 178, 188, 3, 81, 35, 0, 2, 17, 66, 3, 134, 0, 3, 134, 35, 0, 7, 6, 1, 45, 0, 2, 17, 66, 3, 69, 0, 3, 69, 35, 0, 7, 6, 1, 46, 0, 2, 17, 66, 3, 135, 0, 3, 135, 35, 0, 7, 6, 1, 47, 0, 2, 17, 66, 3, 63, 0, 3, 63, 35, 0, 7, 6, 1, 48, 0, 2, 17, 66, 3, 57, 0, 3, 57, 35, 0, 7, 6, 1, 49, 0, 2, 17, 66, 3, 34, 0, 3, 34, 35, 0, 7, 6, 1, 50, 0, 2, 17, 66, 3, 34, 0, 3, 34, 35, 0, 7, 6, 1, 51, 0, 2, 17, 66, 3, 55, 0, 3, 55, 35, 0, 7, 6, 1, 52, 0, 2, 17, 66, 3, 62, 0, 3, 62, 35, 0, 7, 6, 1, 54, 0, 2, 17, 66, 3, 82, 0, 3, 82, 35, 0, 7, 6, 1, 55, 0, 2, 17, 66, 3, 95, 0, 3, 95, 35, 0, 7, 6, 1, 56, 0, 2, 17, 66, 3, 91, 0, 3, 91, 35, 0, 7, 6, 1, 57, 0, 2, 17, 66, 3, 87, 0, 3, 87, 35, 0, 7, 6, 1, 58, 0, 2, 17, 66, 3, 105, 0, 3, 105, 35, 0, 7, 6, 1, 95, 0, 2, 17, 66, 3, 81, 0, 3, 81, 35, 0, 7, 6, 1, 97, 0, 3, 44, 0, 7, 6, 224, 164, 0, 3, 21, 104, 105, 0, 7, 6, 224, 165, 0, 3, 21, 104, 105, 0, 7, 6, 224, 178, 0, 191, 3, 37, 0, 130, 3, 63, 0, 131, 3, 105, 0, 190, 3, 116, 0, 7, 6, 224, 179, 0, 141, 3, 0, 4, 149, 3, 12, 0, 150, 0, 131, 3, 34, 40, 0, 134, 3, 36, 0, 138, 3, 39, 0, 129, 3, 40, 0, 132, 3, 44, 12, 0, 128, 3, 110, 0, 135, 3, 112, 0, 139, 3, 117, 0, 130, 3, 121, 0, 136, 3, 132, 0, 140, 3, 133, 0, 7, 6, 0, 36, 3, 70, 117, 62, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts32 = FileInMemory_createWithData (5367, reinterpret_cast (&espeakdata_dicts32_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/kn_dict", L"kn"); Collection_addItem (me.peek(), espeakdata_dicts32.transfer()); static unsigned char espeakdata_dicts33_data[2277] = { 0, 4, 0, 0, 124, 7, 0, 0, 0, 0, 0, 0, 0, 4, 193, 4, 76, 0, 0, 0, 0, 6, 65, 8, 69, 36, 0, 0, 0, 0, 0, 6, 65, 12, 73, 36, 0, 0, 0, 0, 0, 6, 65, 16, 70, 36, 0, 0, 0, 6, 195, 92, 19, 128, 76, 0, 0, 0, 0, 0, 0, 6, 65, 24, 81, 36, 0, 0, 0, 0, 0, 6, 65, 28, 79, 36, 0, 0, 0, 0, 0, 6, 65, 32, 105, 36, 0, 0, 0, 0, 0, 0, 8, 1, 37, 87, 107, 70, 36, 0, 0, 0, 0, 6, 65, 40, 88, 36, 0, 0, 0, 9, 1, 42, 87, 47, 36, 51, 49, 0, 0, 0, 6, 65, 44, 49, 36, 0, 0, 0, 0, 0, 6, 65, 48, 55, 36, 0, 0, 0, 0, 0, 6, 65, 52, 63, 36, 0, 0, 0, 0, 0, 6, 65, 56, 50, 36, 0, 10, 5, 95, 48, 1, 14, 4, 10, 40, 0, 0, 0, 6, 195, 44, 148, 128, 72, 0, 0, 0, 0, 0, 0, 6, 65, 64, 48, 36, 0, 0, 0, 0, 0, 6, 65, 68, 102, 36, 0, 0, 0, 0, 0, 6, 65, 72, 51, 36, 0, 0, 0, 0, 0, 6, 65, 76, 87, 36, 0, 0, 0, 0, 0, 6, 65, 80, 47, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 88, 82, 36, 0, 0, 0, 0, 0, 6, 65, 92, 58, 36, 0, 0, 0, 0, 0, 6, 65, 96, 99, 36, 0, 13, 4, 95, 49, 77, 49, 105, 107, 86, 6, 35, 34, 0, 0, 14, 4, 95, 49, 77, 50, 63, 122, 55, 6, 57, 39, 50, 0, 0, 0, 0, 6, 65, 100, 57, 36, 0, 0, 0, 0, 0, 6, 65, 104, 86, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 23, 195, 174, 76, 0, 0, 0, 0, 6, 131, 23, 195, 170, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 4, 226, 137, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 16, 80, 72, 5, 194, 8, 144, 72, 0, 0, 0, 0, 0, 0, 11, 4, 95, 4, 16, 20, 10, 99, 35, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 25, 195, 170, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 4, 224, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 16, 144, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 21, 160, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 8, 84, 192, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 14, 5, 2, 195, 187, 65, 0, 0, 0, 18, 67, 33, 113, 0, 105, 107, 34, 15, 58, 107, 49, 37, 15, 70, 122, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 95, 51, 88, 87, 6, 37, 0, 0, 10, 3, 95, 48, 67, 87, 6, 107, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 49, 67, 87, 6, 107, 70, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 49, 57, 50, 39, 86, 70, 6, 107, 105, 0, 0, 13, 3, 95, 49, 56, 105, 122, 88, 70, 6, 107, 105, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 49, 49, 57, 35, 86, 70, 6, 123, 0, 0, 10, 3, 95, 49, 48, 70, 6, 107, 105, 0, 0, 12, 3, 95, 49, 51, 87, 36, 86, 70, 6, 123, 0, 0, 13, 3, 95, 49, 50, 70, 35, 50, 86, 70, 6, 123, 0, 0, 13, 3, 95, 49, 53, 48, 35, 50, 86, 70, 6, 123, 0, 0, 12, 3, 95, 49, 52, 74, 35, 51, 70, 6, 123, 0, 0, 13, 3, 95, 49, 55, 105, 122, 82, 70, 6, 107, 105, 0, 0, 13, 3, 95, 49, 54, 89, 35, 50, 86, 70, 6, 123, 0, 0, 0, 12, 3, 95, 55, 88, 105, 107, 81, 47, 6, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 12, 195, 170, 76, 0, 0, 0, 0, 0, 0, 11, 3, 95, 50, 88, 69, 6, 122, 87, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 63, 63, 47, 37, 48, 35, 0, 0, 0, 0, 10, 3, 95, 52, 88, 74, 6, 122, 55, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 40, 144, 72, 0, 12, 3, 95, 53, 88, 48, 36, 50, 73, 6, 37, 0, 0, 0, 6, 195, 28, 245, 0, 72, 0, 0, 0, 0, 0, 0, 11, 3, 95, 54, 88, 89, 6, 36, 87, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 56, 88, 105, 36, 89, 47, 6, 36, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 52, 80, 76, 0, 10, 3, 95, 57, 88, 50, 6, 39, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 100, 19, 128, 72, 0, 0, 0, 14, 4, 95, 48, 77, 50, 63, 122, 55, 6, 57, 39, 50, 0, 0, 0, 0, 13, 4, 95, 48, 77, 49, 105, 107, 86, 6, 35, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 195, 170, 14, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 3, 95, 195, 187, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 3, 95, 195, 174, 37, 0, 0, 0, 0, 0, 7, 3, 95, 195, 170, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 72, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 195, 167, 74, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 197, 159, 89, 36, 0, 0, 0, 0, 5, 130, 195, 170, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 80, 80, 76, 0, 0, 0, 6, 130, 195, 187, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 1, 35, 0, 0, 0, 0, 0, 6, 2, 95, 5, 107, 0, 0, 0, 0, 6, 2, 95, 9, 122, 0, 0, 0, 6, 2, 95, 15, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 21, 109, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 2, 95, 33, 69, 35, 50, 107, 89, 6, 35, 50, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 3, 1, 16, 63, 36, 86, 37, 50, 0, 0, 0, 0, 0, 8, 2, 95, 46, 99, 35, 55, 0, 0, 11, 2, 95, 45, 69, 107, 50, 70, 122, 49, 0, 0, 11, 2, 95, 44, 69, 36, 105, 50, 39, 49, 0, 0, 8, 2, 95, 51, 87, 6, 36, 0, 0, 8, 2, 95, 50, 70, 6, 109, 0, 0, 9, 2, 95, 49, 57, 6, 107, 49, 0, 0, 10, 2, 95, 48, 87, 6, 122, 81, 34, 0, 0, 10, 2, 95, 55, 105, 6, 107, 81, 47, 0, 0, 9, 2, 95, 54, 89, 6, 107, 89, 0, 0, 10, 2, 95, 53, 48, 6, 36, 50, 73, 0, 0, 9, 2, 95, 52, 73, 6, 35, 34, 0, 0, 14, 2, 95, 59, 99, 35, 55, 69, 36, 105, 50, 39, 49, 0, 0, 11, 2, 95, 58, 73, 39, 47, 99, 35, 55, 0, 0, 9, 2, 95, 57, 50, 6, 107, 105, 0, 0, 5, 194, 100, 16, 72, 5, 194, 92, 80, 76, 11, 2, 95, 56, 105, 6, 107, 57, 89, 47, 0, 0, 15, 2, 95, 63, 48, 122, 51, 87, 50, 37, 89, 6, 35, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 25, 195, 170, 14, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 195, 174, 0, 105, 121, 0, 195, 170, 0, 101, 119, 0, 101, 121, 0, 7, 6, 195, 167, 0, 3, 74, 0, 7, 6, 195, 170, 0, 1, 21, 2, 32, 14, 128, 128, 129, 3, 2, 36, 0, 110, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 36, 50, 0, 3, 36, 0, 7, 6, 195, 174, 0, 3, 37, 0, 7, 6, 195, 187, 0, 3, 40, 0, 7, 6, 197, 159, 0, 3, 89, 0, 7, 6, 97, 0, 1, 21, 2, 32, 14, 128, 128, 129, 3, 2, 35, 0, 110, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 35, 50, 0, 3, 35, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 73, 0, 7, 6, 100, 0, 3, 70, 0, 7, 6, 101, 0, 3, 107, 0, 119, 3, 113, 0, 121, 3, 116, 0, 2, 32, 3, 123, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 2, 18, 66, 3, 77, 0, 3, 79, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 3, 122, 0, 7, 6, 106, 0, 3, 88, 0, 7, 6, 107, 0, 3, 49, 0, 2, 18, 66, 3, 78, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 7, 6, 111, 0, 3, 39, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 102, 0, 7, 6, 114, 0, 1, 17, 65, 2, 17, 65, 3, 16, 0, 4, 3, 51, 0, 114, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 7, 6, 117, 0, 3, 109, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 99, 0, 119, 101, 3, 99, 58, 124, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 36, 3, 70, 109, 55, 35, 34, 0, 195, 188, 3, 110, 0, 195, 182, 3, 122, 12, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts33 = FileInMemory_createWithData (2276, reinterpret_cast (&espeakdata_dicts33_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ku_dict", L"ku"); Collection_addItem (me.peek(), espeakdata_dicts33.transfer()); static unsigned char espeakdata_dicts34_data[3818] = { 0, 4, 0, 0, 55, 11, 0, 0, 11, 136, 6, 21, 196, 171, 19, 20, 9, 19, 72, 0, 0, 0, 0, 6, 195, 76, 144, 137, 72, 6, 195, 69, 80, 69, 72, 6, 195, 69, 80, 69, 72, 0, 4, 193, 4, 72, 5, 65, 4, 110, 0, 0, 6, 131, 5, 196, 171, 72, 0, 7, 132, 6, 21, 196, 171, 72, 0, 7, 196, 37, 86, 20, 4, 72, 0, 6, 65, 8, 69, 111, 0, 0, 0, 0, 6, 195, 69, 80, 77, 72, 0, 6, 65, 12, 49, 111, 0, 0, 0, 0, 0, 6, 65, 16, 70, 111, 0, 0, 0, 10, 199, 65, 35, 208, 80, 84, 133, 4, 8, 6, 195, 21, 83, 64, 72, 0, 0, 4, 193, 20, 72, 5, 65, 20, 111, 0, 0, 0, 0, 6, 195, 76, 147, 133, 72, 6, 195, 64, 243, 133, 72, 0, 6, 65, 24, 106, 81, 0, 0, 0, 0, 0, 6, 65, 28, 79, 111, 0, 0, 0, 0, 7, 196, 21, 53, 9, 76, 72, 0, 6, 65, 32, 105, 110, 0, 0, 0, 0, 6, 195, 21, 68, 201, 8, 0, 10, 65, 36, 6, 114, 50, 109, 87, 0, 41, 5, 65, 36, 112, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 6, 21, 196, 147, 18, 21, 14, 20, 72, 0, 6, 65, 44, 49, 110, 0, 0, 0, 7, 132, 5, 196, 171, 19, 72, 0, 6, 195, 4, 229, 5, 72, 0, 6, 65, 48, 106, 55, 0, 0, 0, 10, 199, 65, 32, 69, 80, 84, 133, 4, 72, 0, 0, 6, 65, 52, 106, 63, 0, 0, 0, 0, 21, 2, 1, 46, 6, 35, 50, 47, 106, 15, 70, 6, 107, 38, 106, 63, 0, 81, 100, 46, 32, 29, 2, 1, 46, 35, 69, 15, 58, 51, 69, 4, 106, 15, 49, 108, 50, 70, 6, 112, 47, 35, 0, 82, 117, 46, 32, 99, 46, 32, 0, 6, 65, 56, 106, 50, 0, 0, 0, 0, 0, 5, 65, 60, 113, 0, 0, 0, 0, 0, 6, 65, 64, 48, 111, 0, 0, 10, 135, 6, 21, 5, 18, 196, 129, 19, 72, 5, 194, 4, 32, 72, 0, 0, 0, 7, 65, 68, 49, 58, 114, 0, 0, 0, 0, 0, 6, 65, 72, 106, 34, 0, 0, 0, 0, 0, 6, 65, 76, 106, 87, 0, 0, 0, 0, 22, 2, 4, 46, 70, 4, 112, 87, 15, 63, 6, 110, 50, 107, 69, 109, 87, 0, 81, 77, 46, 32, 0, 6, 65, 80, 47, 111, 0, 0, 5, 194, 4, 48, 72, 0, 0, 0, 5, 65, 84, 114, 0, 0, 0, 0, 0, 5, 65, 88, 114, 0, 0, 0, 0, 0, 8, 197, 69, 82, 66, 85, 48, 72, 0, 0, 0, 0, 7, 65, 96, 106, 49, 87, 0, 0, 9, 198, 36, 64, 201, 72, 51, 192, 8, 5, 194, 4, 64, 72, 0, 0, 0, 5, 65, 100, 112, 0, 0, 0, 0, 0, 9, 65, 104, 6, 86, 111, 47, 35, 0, 0, 5, 194, 5, 64, 8, 0, 0, 6, 195, 20, 226, 77, 8, 0, 0, 9, 198, 25, 81, 82, 21, 83, 148, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 65, 35, 208, 20, 72, 16, 2, 9, 46, 4, 107, 70, 15, 106, 87, 47, 0, 81, 101, 46, 32, 0, 0, 0, 0, 0, 0, 0, 6, 195, 5, 85, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 21, 32, 78, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 69, 83, 196, 8, 6, 195, 69, 83, 196, 72, 0, 0, 0, 0, 6, 195, 64, 244, 212, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 65, 35, 208, 37, 84, 192, 72, 0, 0, 7, 196, 81, 32, 78, 76, 72, 0, 0, 0, 0, 0, 0, 5, 194, 20, 16, 72, 0, 0, 0, 0, 0, 0, 7, 196, 77, 83, 85, 76, 72, 7, 196, 77, 84, 18, 4, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 16, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 21, 48, 72, 0, 0, 7, 196, 65, 35, 213, 80, 8, 0, 0, 0, 6, 195, 21, 53, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 21, 64, 72, 28, 0, 0, 0, 0, 0, 7, 132, 9, 196, 171, 19, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 21, 66, 65, 52, 8, 0, 0, 0, 0, 7, 196, 69, 83, 193, 16, 8, 0, 0, 0, 0, 0, 0, 9, 134, 6, 21, 5, 18, 197, 141, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 25, 82, 84, 72, 0, 8, 133, 5, 18, 196, 129, 13, 72, 7, 196, 64, 83, 133, 76, 72, 0, 0, 5, 194, 21, 128, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 80, 144, 137, 72, 0, 0, 0, 8, 197, 21, 34, 84, 37, 48, 72, 0, 8, 133, 5, 18, 196, 129, 19, 72, 0, 0, 0, 8, 133, 5, 18, 196, 129, 20, 72, 15, 67, 36, 33, 0, 6, 107, 69, 112, 15, 70, 4, 106, 63, 0, 0, 14, 66, 36, 32, 6, 107, 69, 112, 15, 70, 4, 106, 63, 0, 0, 6, 195, 56, 80, 192, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 5, 18, 197, 141, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 12, 148, 131, 4, 72, 0, 0, 5, 194, 36, 64, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 51, 88, 47, 14, 16, 112, 79, 6, 107, 50, 47, 110, 0, 0, 13, 3, 95, 48, 67, 49, 6, 106, 50, 47, 109, 63, 0, 0, 0, 6, 195, 65, 32, 69, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 49, 57, 114, 50, 70, 106, 58, 107, 79, 6, 107, 50, 47, 107, 0, 0, 19, 3, 95, 49, 56, 70, 109, 108, 70, 106, 58, 107, 79, 6, 107, 50, 47, 107, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 49, 49, 6, 114, 50, 70, 106, 49, 107, 63, 0, 6, 195, 52, 146, 9, 72, 0, 12, 3, 95, 49, 48, 70, 6, 106, 49, 106, 63, 0, 0, 17, 3, 95, 49, 51, 47, 14, 16, 4, 111, 70, 6, 106, 49, 107, 63, 0, 0, 15, 3, 95, 49, 50, 70, 109, 6, 108, 70, 106, 49, 107, 63, 0, 0, 17, 3, 95, 49, 53, 49, 58, 4, 112, 50, 70, 6, 106, 49, 107, 63, 0, 0, 20, 3, 95, 49, 52, 49, 58, 35, 47, 12, 58, 6, 108, 51, 70, 106, 49, 107, 63, 0, 0, 18, 3, 95, 49, 55, 87, 106, 48, 47, 6, 106, 50, 70, 106, 49, 107, 63, 0, 0, 14, 3, 95, 49, 54, 87, 6, 106, 70, 106, 49, 107, 63, 0, 0, 0, 18, 3, 95, 55, 88, 87, 106, 48, 47, 109, 110, 79, 6, 107, 50, 47, 110, 0, 0, 6, 131, 19, 21, 63, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 5, 5, 68, 72, 0, 0, 11, 136, 6, 21, 196, 171, 19, 20, 196, 171, 72, 0, 10, 66, 36, 144, 70, 6, 109, 108, 0, 42, 7, 66, 36, 144, 107, 107, 0, 0, 0, 7, 196, 36, 229, 5, 72, 72, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 50, 88, 58, 112, 79, 6, 107, 50, 47, 112, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 21, 37, 78, 80, 72, 0, 0, 0, 19, 3, 95, 52, 88, 49, 58, 35, 70, 14, 16, 110, 79, 6, 107, 50, 47, 110, 0, 0, 7, 196, 5, 68, 85, 36, 8, 0, 0, 0, 0, 0, 8, 197, 77, 80, 148, 21, 32, 72, 0, 0, 19, 3, 95, 53, 88, 49, 58, 112, 66, 49, 58, 110, 79, 6, 107, 50, 47, 110, 0, 0, 7, 196, 36, 225, 146, 4, 72, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 54, 88, 87, 106, 49, 87, 110, 79, 6, 107, 50, 47, 110, 0, 0, 7, 196, 5, 68, 85, 20, 8, 0, 0, 9, 198, 88, 84, 212, 73, 83, 64, 72, 0, 6, 195, 20, 19, 64, 72, 0, 7, 196, 69, 80, 83, 36, 8, 0, 0, 0, 0, 6, 131, 20, 21, 63, 72, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 56, 88, 108, 49, 47, 113, 79, 6, 107, 50, 47, 110, 0, 0, 0, 7, 132, 13, 5, 196, 171, 72, 0, 0, 0, 0, 0, 0, 16, 3, 95, 57, 88, 50, 113, 50, 110, 79, 6, 107, 50, 47, 110, 0, 0, 6, 131, 13, 196, 147, 72, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 20, 149, 83, 72, 0, 8, 197, 21, 34, 77, 85, 48, 72, 0, 0, 0, 10, 135, 5, 18, 196, 129, 13, 21, 19, 72, 0, 7, 132, 17, 21, 196, 171, 72, 0, 12, 137, 6, 21, 5, 18, 196, 129, 13, 21, 19, 72, 0, 5, 194, 60, 32, 72, 5, 194, 36, 224, 72, 5, 194, 36, 224, 72, 0, 0, 0, 12, 137, 6, 21, 5, 18, 196, 171, 13, 21, 19, 72, 0, 9, 198, 65, 32, 69, 80, 84, 128, 72, 0, 0, 0, 0, 9, 198, 25, 81, 82, 84, 229, 0, 72, 0, 0, 0, 0, 10, 135, 6, 21, 5, 18, 196, 171, 19, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 65, 35, 192, 72, 0, 0, 0, 0, 6, 195, 77, 83, 64, 72, 6, 195, 13, 83, 64, 72, 5, 195, 56, 243, 128, 0, 8, 133, 17, 21, 197, 141, 19, 72, 0, 13, 4, 95, 48, 77, 49, 63, 6, 107, 55, 55, 106, 0, 8, 197, 25, 82, 77, 85, 48, 72, 0, 0, 0, 0, 12, 201, 69, 81, 77, 4, 67, 79, 17, 83, 64, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 69, 80, 77, 69, 80, 77, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 12, 148, 131, 84, 208, 72, 0, 0, 0, 0, 0, 0, 0, 8, 133, 17, 21, 196, 129, 19, 72, 0, 0, 9, 198, 56, 244, 212, 73, 83, 64, 72, 0, 0, 0, 0, 0, 6, 195, 77, 80, 128, 72, 0, 0, 0, 0, 6, 195, 77, 83, 148, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 21, 65, 78, 36, 208, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 14, 197, 141, 2, 196, 171, 19, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 76, 80, 213, 56, 69, 77, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 77, 83, 148, 60, 72, 0, 0, 0, 6, 195, 21, 34, 84, 72, 0, 0, 0, 6, 195, 21, 34, 83, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 80, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 84, 197, 18, 4, 72, 7, 196, 36, 229, 18, 4, 72, 0, 8, 197, 21, 53, 15, 80, 80, 72, 8, 197, 12, 243, 148, 72, 16, 72, 0, 0, 0, 0, 0, 0, 6, 195, 56, 19, 64, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 21, 53, 5, 72, 0, 0, 9, 198, 69, 80, 77, 16, 149, 64, 8, 10, 135, 22, 197, 141, 2, 196, 171, 19, 72, 0, 0, 0, 8, 197, 25, 81, 82, 5, 64, 72, 0, 6, 195, 21, 53, 15, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 5, 197, 141, 18, 21, 13, 72, 0, 0, 0, 0, 0, 9, 198, 65, 35, 208, 80, 84, 128, 72, 0, 0, 0, 0, 6, 195, 21, 33, 193, 72, 0, 0, 6, 195, 21, 33, 207, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 17, 83, 64, 8, 0, 0, 0, 0, 6, 195, 64, 84, 128, 72, 0, 0, 0, 10, 135, 17, 21, 196, 129, 18, 21, 13, 72, 0, 11, 2, 95, 51, 47, 14, 16, 4, 111, 87, 0, 0, 9, 2, 95, 50, 70, 6, 109, 108, 0, 0, 10, 2, 95, 49, 6, 114, 50, 109, 87, 0, 0, 11, 2, 95, 48, 50, 6, 109, 55, 55, 35, 0, 0, 12, 2, 95, 55, 87, 6, 106, 48, 47, 106, 63, 0, 0, 10, 2, 95, 54, 87, 4, 106, 49, 87, 0, 0, 13, 2, 95, 53, 49, 58, 6, 112, 66, 49, 58, 106, 0, 0, 14, 2, 95, 52, 49, 58, 6, 35, 47, 12, 109, 108, 51, 0, 0, 0, 0, 11, 2, 95, 57, 50, 6, 108, 58, 106, 63, 0, 0, 10, 2, 95, 56, 6, 108, 49, 47, 113, 0, 0, 0, 0, 0, 10, 135, 17, 21, 197, 141, 18, 21, 13, 72, 0, 0, 0, 8, 197, 56, 19, 81, 84, 80, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 36, 65, 79, 8, 0, 0, 0, 0, 7, 196, 77, 84, 5, 72, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 67, 36, 66, 66, 6, 112, 70, 107, 69, 109, 87, 0, 0, 11, 66, 88, 144, 87, 4, 106, 49, 87, 0, 42, 7, 66, 88, 144, 58, 107, 0, 0, 0, 0, 9, 134, 5, 196, 129, 18, 21, 13, 72, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 5, 196, 129, 19, 72, 0, 12, 137, 6, 21, 5, 18, 196, 171, 20, 9, 19, 72, 0, 0, 0, 0, 12, 137, 6, 21, 5, 18, 196, 129, 20, 9, 19, 72, 0, 14, 67, 36, 68, 64, 112, 70, 6, 106, 63, 49, 58, 106, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 56, 148, 201, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 25, 81, 82, 4, 208, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 20, 196, 147, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 5, 85, 5, 52, 8, 0, 7, 132, 5, 197, 141, 19, 72, 0, 0, 0, 0, 8, 197, 88, 84, 147, 85, 48, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 21, 133, 18, 4, 72, 0, 0, 0, 0, 0, 0, 0, 9, 198, 65, 35, 216, 36, 213, 83, 72, 0, 10, 135, 5, 18, 196, 129, 20, 9, 19, 72, 0, 0, 0, 0, 0, 0, 6, 131, 5, 196, 129, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 25, 81, 82, 37, 64, 72, 0, 6, 131, 5, 197, 141, 72, 0, 0, 0, 8, 197, 69, 80, 78, 16, 240, 8, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 0, 226, 0, 0, 0, 1, 1, 0, 0, 234, 0, 0, 0, 19, 1, 0, 0, 238, 0, 0, 0, 43, 1, 0, 0, 244, 0, 0, 0, 77, 1, 0, 0, 251, 0, 0, 0, 107, 1, 0, 0, 119, 1, 0, 0, 121, 0, 121, 0, 0, 0, 0, 0, 6, 18, 66, 97, 101, 0, 97, 117, 0, 101, 117, 0, 111, 101, 0, 121, 121, 0, 196, 129, 0, 196, 147, 0, 196, 171, 0, 197, 141, 0, 197, 171, 0, 195, 171, 0, 195, 188, 0, 195, 169, 0, 195, 166, 0, 97, 0, 101, 0, 105, 0, 111, 0, 117, 0, 121, 0, 7, 6, 18, 67, 99, 104, 114, 0, 110, 103, 0, 113, 117, 0, 112, 114, 0, 116, 114, 0, 99, 114, 0, 98, 114, 0, 100, 114, 0, 103, 114, 0, 112, 108, 0, 99, 108, 0, 98, 108, 0, 103, 108, 0, 112, 104, 0, 116, 104, 0, 99, 104, 0, 7, 6, 113, 117, 0, 3, 49, 58, 0, 7, 6, 195, 166, 0, 3, 118, 0, 7, 6, 196, 129, 0, 3, 110, 0, 7, 6, 196, 147, 0, 3, 111, 0, 7, 6, 196, 171, 0, 3, 112, 0, 7, 6, 197, 141, 0, 3, 113, 0, 7, 6, 197, 171, 0, 3, 114, 0, 7, 6, 97, 0, 4, 2, 17, 67, 18, 66, 29, 3, 8, 35, 0, 2, 18, 66, 29, 0, 2, 18, 67, 18, 66, 29, 0, 2, 103, 117, 18, 66, 29, 0, 4, 3, 35, 0, 2, 120, 12, 0, 117, 2, 12, 12, 12, 3, 117, 0, 101, 2, 12, 12, 12, 3, 118, 0, 7, 6, 98, 0, 3, 69, 0, 98, 3, 69, 12, 0, 7, 6, 99, 0, 3, 49, 0, 99, 3, 49, 12, 0, 99, 104, 3, 49, 12, 122, 0, 104, 3, 49, 122, 0, 7, 6, 100, 0, 3, 70, 0, 100, 3, 70, 12, 0, 7, 6, 101, 0, 4, 2, 17, 67, 18, 66, 29, 3, 8, 106, 0, 2, 18, 66, 29, 0, 2, 18, 67, 18, 66, 29, 0, 2, 103, 117, 18, 66, 29, 0, 4, 3, 106, 0, 2, 120, 12, 0, 117, 2, 12, 12, 12, 3, 120, 0, 7, 6, 102, 0, 3, 81, 0, 102, 3, 81, 12, 0, 7, 6, 103, 0, 2, 110, 3, 66, 0, 3, 79, 0, 103, 3, 79, 12, 0, 103, 117, 2, 17, 65, 3, 79, 12, 58, 0, 117, 2, 17, 65, 3, 79, 58, 0, 7, 6, 104, 0, 3, 105, 0, 58, 3, 105, 12, 0, 7, 6, 105, 0, 4, 1, 117, 17, 65, 2, 18, 66, 29, 12, 12, 3, 8, 107, 0, 1, 117, 103, 2, 18, 66, 29, 12, 12, 0, 1, 117, 113, 2, 18, 66, 29, 12, 12, 0, 2, 17, 67, 18, 66, 29, 0, 2, 18, 66, 29, 0, 2, 18, 67, 18, 66, 29, 0, 2, 103, 117, 18, 66, 29, 0, 8, 117, 2, 18, 66, 29, 12, 12, 0, 2, 105, 29, 3, 8, 107, 19, 0, 8, 2, 17, 65, 3, 57, 0, 4, 1, 17, 65, 2, 17, 65, 12, 3, 57, 12, 0, 1, 117, 97, 2, 17, 65, 12, 12, 12, 0, 1, 117, 101, 2, 17, 65, 12, 12, 12, 0, 4, 3, 107, 0, 1, 117, 17, 65, 2, 17, 65, 12, 12, 0, 1, 117, 103, 2, 17, 65, 12, 12, 0, 1, 117, 113, 2, 17, 65, 12, 12, 0, 2, 120, 12, 0, 8, 117, 2, 17, 65, 12, 12, 0, 2, 105, 3, 107, 19, 0, 7, 6, 107, 0, 3, 49, 0, 107, 3, 49, 12, 0, 7, 6, 108, 0, 3, 55, 0, 108, 3, 55, 12, 0, 7, 6, 109, 0, 3, 63, 0, 109, 3, 63, 12, 0, 7, 6, 110, 0, 3, 50, 0, 110, 3, 50, 12, 0, 4, 2, 99, 3, 66, 0, 2, 103, 0, 2, 107, 0, 2, 113, 0, 2, 120, 0, 7, 6, 111, 0, 4, 2, 17, 67, 18, 66, 29, 3, 8, 108, 0, 2, 18, 66, 29, 0, 2, 18, 67, 18, 66, 29, 0, 2, 103, 117, 18, 66, 29, 0, 4, 3, 108, 0, 2, 120, 12, 0, 101, 2, 12, 12, 12, 3, 121, 0, 7, 6, 112, 0, 3, 48, 0, 112, 3, 48, 12, 0, 112, 104, 3, 48, 12, 122, 0, 104, 3, 48, 122, 0, 7, 6, 114, 0, 1, 17, 67, 3, 14, 16, 0, 4, 3, 51, 0, 1, 17, 65, 2, 17, 65, 0, 8, 0, 114, 3, 51, 16, 0, 7, 6, 115, 0, 3, 87, 0, 115, 3, 87, 12, 0, 7, 6, 116, 0, 3, 47, 0, 116, 3, 47, 12, 0, 116, 104, 3, 47, 12, 122, 0, 104, 3, 47, 122, 0, 7, 6, 117, 0, 4, 2, 17, 67, 18, 66, 29, 3, 8, 109, 0, 2, 18, 66, 29, 0, 2, 18, 67, 18, 66, 29, 0, 2, 103, 117, 18, 66, 29, 0, 4, 1, 17, 65, 2, 17, 65, 12, 12, 3, 58, 0, 8, 2, 17, 65, 12, 0, 4, 3, 109, 0, 2, 120, 12, 0, 7, 6, 118, 0, 4, 3, 58, 0, 8, 0, 118, 2, 12, 12, 12, 3, 58, 12, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 3, 115, 0, 121, 3, 116, 0, 7, 6, 122, 0, 3, 86, 0, 4, 1, 17, 65, 2, 17, 65, 3, 86, 12, 0, 122, 0, 7, 6, 0, 106, 3, 57, 0, 119, 3, 58, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts34 = FileInMemory_createWithData (3817, reinterpret_cast (&espeakdata_dicts34_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/la_dict", L"la"); Collection_addItem (me.peek(), espeakdata_dicts34.transfer()); static unsigned char espeakdata_dicts35_data[12328] = { 0, 4, 0, 0, 72, 18, 0, 0, 0, 0, 11, 195, 44, 21, 84, 66, 81, 107, 196, 129, 32, 11, 195, 44, 21, 84, 66, 81, 99, 105, 107, 32, 0, 0, 0, 5, 65, 4, 35, 0, 0, 5, 194, 5, 0, 72, 0, 20, 67, 76, 16, 128, 87, 35, 69, 120, 70, 52, 106, 69, 35, 0, 44, 81, 98, 97, 32, 0, 0, 6, 65, 8, 69, 36, 0, 0, 0, 0, 0, 6, 65, 12, 122, 36, 0, 0, 0, 13, 4, 95, 8, 1, 3, 105, 6, 35, 74, 36, 49, 0, 0, 0, 6, 65, 16, 70, 36, 0, 0, 0, 0, 0, 5, 65, 20, 36, 0, 0, 0, 14, 4, 95, 48, 67, 15, 87, 6, 37, 63, 47, 114, 87, 0, 0, 0, 6, 65, 24, 36, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 32, 105, 35, 0, 0, 0, 0, 0, 10, 1, 36, 70, 39, 55, 111, 52, 37, 0, 5, 65, 36, 37, 0, 0, 13, 1, 37, 48, 52, 39, 122, 36, 50, 47, 37, 0, 27, 0, 6, 1, 38, 40, 50, 0, 8, 1, 38, 11, 2, 40, 50, 0, 0, 0, 6, 65, 40, 57, 36, 0, 0, 0, 9, 198, 64, 19, 1, 36, 176, 77, 66, 6, 195, 28, 20, 128, 72, 14, 1, 42, 86, 82, 114, 79, 86, 50, 106, 47, 36, 0, 27, 0, 10, 1, 43, 48, 55, 40, 87, 87, 0, 27, 0, 8, 197, 40, 80, 139, 4, 64, 66, 6, 65, 44, 49, 35, 0, 0, 0, 19, 67, 76, 21, 128, 87, 35, 82, 120, 50, 106, 69, 35, 0, 44, 81, 98, 97, 32, 0, 15, 1, 47, 87, 55, 106, 48, 87, 82, 106, 47, 51, 35, 0, 27, 0, 6, 65, 48, 36, 55, 0, 0, 9, 66, 49, 0, 55, 35, 48, 35, 0, 0, 0, 0, 6, 65, 52, 36, 63, 0, 0, 0, 0, 0, 6, 65, 56, 36, 50, 0, 0, 0, 0, 7, 196, 48, 16, 129, 16, 72, 0, 5, 65, 60, 117, 0, 0, 13, 1, 61, 10, 82, 120, 50, 111, 70, 87, 10, 0, 27, 0, 0, 0, 9, 134, 6, 15, 1, 10, 196, 147, 67, 7, 1, 64, 35, 47, 9, 0, 6, 65, 64, 48, 36, 0, 0, 0, 0, 0, 6, 65, 68, 49, 113, 0, 0, 0, 0, 0, 7, 65, 72, 36, 51, 52, 0, 0, 5, 194, 5, 32, 72, 0, 0, 0, 6, 65, 76, 36, 87, 0, 0, 0, 0, 0, 6, 65, 80, 47, 107, 0, 0, 0, 11, 136, 16, 9, 1, 14, 196, 171, 14, 15, 20, 0, 0, 5, 65, 84, 40, 0, 0, 0, 0, 0, 6, 65, 88, 82, 36, 0, 0, 0, 0, 0, 25, 1, 92, 6, 35, 48, 79, 52, 120, 86, 47, 111, 15, 87, 55, 6, 106, 48, 87, 82, 106, 47, 51, 35, 0, 13, 65, 92, 70, 40, 69, 40, 55, 47, 6, 82, 36, 0, 0, 0, 0, 0, 18, 4, 95, 49, 77, 49, 47, 6, 113, 49, 87, 47, 117, 12, 47, 37, 87, 0, 7, 65, 96, 37, 49, 87, 0, 0, 15, 4, 95, 49, 77, 50, 63, 6, 37, 55, 57, 112, 50, 87, 0, 0, 0, 0, 9, 65, 100, 37, 79, 52, 36, 49, 0, 0, 9, 198, 20, 208, 129, 72, 115, 192, 20, 0, 0, 0, 6, 65, 104, 86, 36, 0, 0, 9, 198, 37, 67, 133, 45, 84, 128, 67, 0, 0, 0, 8, 197, 80, 146, 208, 5, 64, 66, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 4, 197, 190, 21, 4, 15, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 64, 19, 142, 60, 20, 0, 0, 13, 67, 36, 84, 203, 120, 87, 49, 114, 47, 117, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 199, 21, 52, 5, 72, 19, 148, 60, 20, 9, 134, 1, 16, 1, 11, 197, 161, 72, 0, 10, 135, 16, 18, 9, 5, 11, 197, 161, 72, 0, 0, 0, 7, 195, 8, 85, 0, 72, 8, 0, 0, 0, 6, 195, 4, 227, 143, 20, 0, 0, 0, 8, 133, 4, 196, 147, 196, 188, 72, 0, 0, 0, 12, 137, 11, 15, 13, 21, 14, 9, 11, 196, 147, 68, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 88, 85, 15, 20, 12, 66, 17, 32, 70, 39, 49, 47, 112, 52, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 67, 48, 21, 22, 55, 35, 47, 82, 120, 89, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 11, 15, 16, 197, 161, 72, 0, 6, 195, 64, 145, 64, 72, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 245, 15, 20, 6, 195, 52, 245, 15, 20, 0, 0, 14, 4, 95, 4, 16, 20, 49, 6, 39, 63, 35, 122, 10, 0, 0, 0, 5, 194, 21, 48, 72, 0, 0, 7, 196, 32, 19, 12, 60, 20, 0, 0, 0, 6, 195, 84, 227, 192, 20, 6, 195, 104, 83, 64, 72, 0, 0, 0, 0, 0, 16, 3, 95, 35, 57, 47, 35, 69, 40, 55, 35, 47, 112, 52, 87, 0, 13, 4, 95, 20, 12, 4, 47, 6, 37, 55, 70, 36, 0, 0, 0, 0, 0, 7, 196, 8, 147, 135, 60, 20, 12, 137, 20, 21, 18, 16, 18, 5, 20, 196, 171, 66, 0, 0, 0, 0, 0, 9, 134, 18, 1, 14, 196, 141, 15, 20, 0, 0, 0, 0, 0, 0, 0, 7, 196, 81, 34, 77, 60, 20, 13, 67, 64, 145, 77, 48, 120, 63, 107, 52, 35, 63, 0, 0, 0, 0, 12, 67, 76, 176, 84, 87, 49, 35, 47, 106, 47, 0, 0, 0, 0, 10, 135, 7, 1, 12, 9, 6, 196, 147, 67, 0, 0, 7, 196, 9, 32, 86, 60, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 76, 243, 133, 72, 16, 20, 15, 67, 24, 80, 146, 81, 36, 69, 52, 40, 111, 52, 37, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 80, 146, 214, 36, 83, 128, 66, 9, 198, 4, 150, 150, 36, 83, 128, 66, 0, 0, 0, 0, 9, 198, 52, 17, 83, 81, 35, 192, 20, 9, 198, 52, 17, 83, 81, 35, 192, 66, 0, 6, 195, 64, 20, 128, 72, 0, 7, 196, 81, 34, 75, 60, 20, 0, 0, 0, 0, 7, 196, 16, 147, 135, 60, 20, 0, 0, 11, 66, 17, 160, 70, 86, 37, 63, 37, 87, 0, 8, 66, 17, 160, 70, 86, 107, 0, 0, 0, 0, 9, 134, 22, 9, 197, 134, 197, 161, 72, 0, 0, 0, 0, 0, 0, 11, 195, 56, 86, 128, 66, 81, 107, 97, 100, 32, 0, 0, 0, 0, 6, 195, 8, 86, 128, 72, 0, 0, 8, 197, 72, 242, 207, 44, 240, 20, 0, 0, 0, 10, 135, 1, 20, 5, 12, 10, 196, 147, 67, 0, 0, 0, 0, 0, 0, 7, 132, 16, 196, 129, 18, 72, 0, 0, 0, 0, 0, 0, 13, 3, 95, 49, 15, 48, 6, 37, 52, 63, 114, 87, 0, 0, 0, 0, 12, 67, 64, 17, 192, 48, 35, 79, 35, 87, 122, 0, 9, 3, 226, 130, 172, 115, 52, 112, 0, 9, 3, 226, 130, 172, 115, 51, 39, 0, 0, 0, 0, 0, 13, 3, 226, 130, 168, 52, 113, 48, 106, 57, 35, 87, 0, 0, 12, 3, 95, 50, 15, 6, 39, 47, 52, 114, 87, 0, 0, 8, 197, 81, 84, 144, 5, 64, 66, 0, 0, 12, 67, 64, 18, 192, 48, 35, 49, 111, 48, 36, 0, 0, 0, 0, 0, 0, 13, 3, 95, 51, 15, 47, 51, 6, 36, 89, 114, 87, 0, 9, 4, 95, 15, 18, 4, 114, 87, 0, 0, 0, 0, 0, 0, 0, 8, 133, 197, 190, 1, 2, 15, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 53, 15, 48, 6, 120, 49, 47, 114, 87, 0, 0, 0, 14, 4, 95, 13, 3, 14, 63, 6, 35, 49, 52, 39, 50, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 54, 15, 87, 6, 36, 87, 47, 114, 87, 0, 0, 0, 0, 9, 134, 196, 141, 5, 12, 12, 15, 20, 0, 0, 0, 0, 0, 15, 3, 95, 55, 15, 87, 6, 36, 48, 47, 106, 47, 114, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 51, 88, 47, 51, 6, 106, 87, 70, 36, 87, 63, 37, 47, 0, 0, 9, 198, 64, 21, 12, 4, 32, 78, 66, 13, 3, 95, 48, 67, 87, 6, 37, 63, 47, 37, 10, 0, 0, 0, 0, 0, 7, 196, 64, 148, 141, 76, 72, 14, 3, 95, 57, 15, 70, 6, 36, 82, 106, 47, 114, 87, 0, 0, 0, 0, 0, 11, 3, 95, 49, 67, 87, 6, 37, 63, 122, 0, 0, 0, 0, 0, 0, 0, 19, 3, 95, 49, 57, 70, 6, 36, 82, 37, 65, 48, 35, 70, 87, 63, 37, 47, 0, 0, 19, 3, 95, 49, 56, 6, 35, 87, 47, 117, 65, 48, 35, 70, 87, 63, 37, 47, 0, 0, 0, 12, 67, 48, 21, 0, 55, 35, 47, 106, 65, 40, 0, 0, 0, 0, 0, 12, 3, 226, 136, 146, 63, 106, 50, 40, 87, 87, 0, 0, 17, 3, 95, 49, 49, 82, 6, 120, 50, 48, 35, 70, 87, 63, 37, 47, 0, 0, 13, 3, 95, 49, 48, 70, 6, 36, 87, 63, 37, 47, 0, 0, 18, 3, 95, 49, 51, 47, 51, 6, 106, 87, 48, 35, 70, 87, 63, 37, 47, 0, 0, 17, 3, 95, 49, 50, 70, 6, 37, 82, 48, 35, 70, 87, 63, 37, 47, 0, 0, 9, 198, 49, 83, 66, 4, 115, 192, 20, 17, 3, 95, 49, 53, 48, 6, 120, 122, 48, 35, 70, 87, 63, 37, 47, 0, 0, 18, 3, 95, 49, 52, 74, 6, 36, 47, 52, 48, 35, 70, 87, 63, 37, 47, 0, 0, 7, 196, 80, 84, 1, 80, 66, 15, 3, 95, 52, 15, 74, 6, 36, 47, 40, 51, 47, 114, 87, 0, 20, 3, 95, 49, 55, 87, 6, 36, 48, 47, 37, 65, 48, 35, 70, 87, 63, 37, 47, 0, 0, 7, 132, 16, 196, 147, 3, 72, 17, 3, 95, 49, 54, 87, 6, 36, 89, 48, 35, 70, 87, 63, 37, 47, 0, 0, 0, 19, 3, 95, 55, 88, 87, 6, 36, 48, 47, 37, 65, 70, 36, 87, 63, 37, 47, 0, 0, 6, 195, 24, 245, 15, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 66, 49, 48, 55, 35, 47, 37, 0, 41, 0, 16, 3, 95, 50, 88, 70, 6, 37, 82, 70, 36, 87, 63, 37, 47, 0, 0, 10, 135, 11, 1, 14, 1, 16, 196, 147, 67, 0, 0, 0, 6, 195, 65, 33, 84, 72, 0, 14, 3, 95, 56, 15, 6, 35, 87, 47, 39, 47, 114, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 63, 63, 52, 35, 49, 87, 47, 86, 106, 63, 36, 0, 0, 0, 5, 194, 37, 160, 72, 0, 17, 3, 95, 52, 88, 74, 6, 36, 47, 52, 70, 36, 87, 63, 37, 47, 0, 0, 12, 3, 1, 47, 19, 35, 49, 78, 37, 57, 40, 0, 0, 0, 0, 0, 0, 0, 0, 16, 67, 76, 84, 20, 87, 36, 48, 47, 36, 63, 69, 52, 37, 87, 0, 17, 3, 95, 53, 88, 48, 6, 120, 122, 70, 4, 36, 87, 63, 37, 47, 0, 0, 0, 8, 197, 4, 146, 201, 16, 240, 20, 0, 0, 0, 0, 0, 5, 194, 49, 80, 17, 0, 6, 195, 60, 67, 192, 20, 16, 3, 95, 54, 88, 87, 6, 36, 89, 70, 36, 87, 63, 37, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 67, 5, 4, 128, 35, 48, 52, 106, 55, 37, 87, 0, 0, 0, 0, 0, 0, 0, 0, 10, 66, 57, 32, 50, 40, 63, 40, 52, 0, 0, 18, 3, 95, 56, 88, 6, 35, 87, 47, 117, 65, 70, 36, 87, 63, 37, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 57, 88, 70, 6, 36, 82, 37, 65, 70, 36, 87, 63, 37, 47, 0, 0, 12, 196, 56, 86, 137, 56, 67, 81, 107, 117, 114, 32, 0, 0, 0, 0, 7, 196, 77, 64, 82, 64, 72, 0, 0, 10, 3, 95, 63, 65, 69, 40, 52, 122, 0, 0, 0, 7, 196, 9, 37, 78, 60, 20, 0, 0, 0, 0, 0, 0, 0, 11, 3, 226, 153, 175, 70, 120, 12, 86, 87, 0, 0, 0, 12, 3, 226, 153, 173, 69, 36, 63, 112, 55, 87, 0, 0, 0, 0, 14, 4, 95, 15, 7, 15, 6, 39, 79, 39, 50, 36, 49, 0, 0, 0, 0, 0, 10, 199, 52, 144, 210, 61, 51, 198, 80, 20, 0, 0, 0, 0, 0, 0, 0, 5, 194, 64, 16, 72, 0, 12, 67, 64, 17, 0, 48, 35, 70, 117, 63, 36, 0, 0, 0, 8, 197, 8, 243, 5, 72, 240, 20, 0, 13, 4, 10, 197, 171, 14, 57, 113, 50, 37, 57, 87, 0, 0, 12, 4, 197, 161, 196, 183, 89, 78, 37, 52, 35, 0, 0, 13, 4, 10, 197, 171, 12, 57, 113, 55, 37, 57, 87, 0, 0, 8, 197, 44, 22, 137, 56, 240, 20, 8, 197, 36, 225, 9, 28, 240, 20, 8, 197, 24, 144, 83, 44, 240, 20, 0, 5, 194, 57, 80, 72, 0, 6, 195, 61, 67, 192, 20, 21, 67, 52, 147, 128, 63, 37, 50, 37, 87, 47, 52, 37, 57, 35, 0, 44, 81, 106, 97, 32, 14, 67, 52, 147, 128, 63, 37, 50, 37, 63, 40, 63, 87, 0, 0, 0, 0, 15, 4, 95, 48, 77, 50, 63, 6, 37, 55, 57, 112, 50, 37, 0, 0, 0, 0, 17, 4, 95, 48, 77, 49, 47, 6, 113, 49, 87, 47, 117, 12, 89, 37, 0, 0, 13, 4, 95, 2, 18, 22, 6, 106, 87, 40, 63, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 10, 197, 171, 19, 72, 0, 7, 196, 9, 37, 84, 60, 20, 0, 0, 0, 15, 67, 56, 245, 128, 50, 39, 82, 36, 63, 69, 52, 37, 87, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 16, 15, 18, 20, 10, 196, 147, 66, 0, 6, 195, 4, 150, 128, 72, 0, 0, 0, 0, 0, 7, 196, 52, 85, 18, 60, 20, 0, 0, 10, 135, 2, 5, 14, 4, 197, 190, 15, 20, 10, 135, 2, 1, 14, 4, 197, 190, 15, 20, 0, 0, 0, 0, 6, 195, 72, 242, 211, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 19, 15, 12, 6, 5, 4, 197, 190, 15, 20, 12, 137, 19, 15, 12, 6, 5, 4, 197, 190, 15, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 22, 9, 197, 134, 1, 72, 0, 0, 0, 0, 19, 4, 95, 3, 9, 18, 70, 6, 37, 35, 49, 52, 37, 47, 37, 87, 49, 111, 0, 0, 0, 0, 0, 8, 133, 22, 9, 197, 134, 9, 72, 0, 12, 3, 95, 194, 180, 35, 49, 122, 36, 50, 122, 0, 0, 7, 196, 56, 82, 213, 72, 66, 0, 0, 16, 67, 52, 18, 211, 63, 35, 49, 87, 37, 63, 111, 55, 114, 87, 0, 0, 14, 67, 56, 244, 192, 50, 117, 87, 116, 49, 40, 63, 87, 0, 0, 0, 0, 0, 13, 4, 95, 19, 20, 11, 87, 47, 34, 6, 112, 49, 0, 0, 0, 13, 4, 95, 1, 3, 21, 6, 35, 49, 57, 113, 47, 0, 0, 14, 3, 95, 194, 171, 48, 6, 107, 70, 37, 65, 35, 87, 0, 0, 9, 198, 64, 20, 9, 48, 224, 77, 66, 0, 0, 27, 3, 95, 194, 166, 87, 6, 35, 70, 35, 55, 106, 47, 35, 15, 87, 47, 6, 111, 82, 87, 82, 106, 47, 52, 35, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 18, 14, 7, 52, 6, 37, 50, 79, 0, 0, 0, 0, 0, 11, 136, 6, 18, 9, 11, 1, 19, 196, 147, 67, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 5, 85, 15, 52, 245, 15, 20, 0, 0, 0, 7, 196, 64, 144, 78, 60, 66, 0, 8, 197, 40, 80, 139, 85, 32, 66, 0, 19, 4, 95, 1, 3, 50, 70, 6, 40, 69, 40, 55, 122, 35, 49, 57, 113, 47, 0, 0, 16, 5, 4, 26, 196, 171, 22, 70, 86, 106, 82, 117, 57, 37, 87, 0, 0, 0, 0, 6, 195, 65, 52, 147, 17, 0, 6, 195, 73, 2, 64, 17, 0, 0, 0, 0, 14, 67, 60, 181, 0, 39, 49, 47, 112, 69, 52, 37, 87, 0, 11, 136, 4, 5, 11, 15, 12, 20, 196, 147, 67, 0, 0, 0, 28, 3, 95, 194, 191, 6, 35, 48, 79, 52, 120, 86, 47, 111, 15, 57, 6, 116, 47, 111, 57, 40, 63, 86, 106, 63, 36, 0, 0, 0, 7, 196, 56, 82, 193, 16, 66, 0, 0, 19, 3, 95, 194, 187, 48, 6, 107, 70, 37, 65, 35, 87, 15, 122, 6, 120, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 196, 129, 111, 0, 0, 7, 2, 197, 134, 36, 65, 0, 0, 8, 197, 5, 37, 137, 20, 224, 66, 8, 2, 195, 151, 52, 115, 86, 0, 0, 6, 195, 16, 84, 15, 20, 9, 66, 77, 64, 87, 35, 50, 47, 0, 0, 7, 2, 196, 141, 74, 36, 0, 0, 0, 0, 0, 0, 0, 12, 2, 194, 167, 87, 36, 49, 122, 37, 57, 35, 0, 0, 5, 194, 56, 240, 72, 0, 12, 67, 56, 241, 0, 50, 117, 70, 35, 61, 35, 0, 10, 2, 194, 165, 57, 107, 50, 35, 87, 0, 0, 10, 2, 194, 162, 122, 36, 50, 47, 37, 0, 0, 13, 2, 194, 163, 63, 111, 52, 122, 37, 65, 35, 87, 0, 6, 2, 196, 147, 107, 0, 0, 0, 0, 14, 2, 194, 174, 52, 36, 77, 37, 87, 47, 52, 107, 122, 0, 0, 7, 2, 197, 151, 36, 34, 0, 0, 0, 0, 0, 0, 0, 16, 2, 194, 169, 116, 47, 112, 52, 47, 120, 87, 106, 69, 35, 87, 0, 0, 14, 2, 194, 182, 48, 35, 52, 35, 79, 52, 111, 81, 87, 0, 0, 0, 0, 10, 2, 194, 181, 63, 37, 49, 51, 112, 0, 0, 0, 7, 2, 196, 163, 77, 36, 0, 0, 10, 2, 194, 176, 79, 52, 111, 70, 37, 0, 0, 15, 2, 194, 177, 48, 55, 40, 87, 63, 106, 50, 40, 87, 87, 0, 0, 23, 2, 194, 190, 47, 52, 6, 106, 87, 15, 122, 4, 36, 47, 40, 52, 47, 70, 35, 61, 35, 87, 0, 0, 10, 2, 195, 183, 70, 35, 55, 106, 122, 0, 0, 11, 66, 77, 96, 87, 82, 107, 47, 114, 87, 0, 17, 2, 194, 188, 122, 6, 36, 47, 40, 52, 47, 70, 4, 35, 61, 35, 0, 0, 9, 2, 194, 189, 48, 40, 87, 36, 0, 0, 14, 4, 95, 3, 5, 4, 87, 6, 36, 70, 106, 55, 35, 0, 0, 6, 2, 196, 171, 106, 0, 0, 10, 135, 1, 4, 1, 4, 197, 190, 15, 20, 10, 135, 1, 4, 1, 4, 197, 190, 15, 66, 0, 16, 4, 95, 12, 9, 7, 55, 6, 37, 79, 35, 47, 113, 52, 35, 0, 7, 2, 197, 161, 36, 89, 0, 0, 7, 196, 24, 16, 212, 60, 20, 17, 5, 16, 18, 45, 11, 19, 48, 52, 120, 49, 89, 50, 120, 49, 87, 0, 0, 7, 2, 196, 183, 78, 36, 0, 0, 0, 0, 0, 6, 2, 197, 171, 113, 0, 0, 0, 7, 195, 88, 18, 64, 72, 8, 0, 0, 0, 5, 194, 81, 80, 72, 7, 2, 196, 188, 36, 61, 0, 0, 0, 0, 9, 134, 22, 9, 197, 134, 1, 19, 72, 0, 0, 0, 7, 2, 197, 190, 88, 36, 0, 0, 0, 9, 198, 64, 20, 133, 80, 19, 64, 66, 0, 0, 0, 0, 0, 0, 7, 196, 44, 18, 193, 60, 20, 7, 196, 44, 18, 193, 60, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 64, 21, 137, 76, 19, 64, 66, 0, 8, 133, 12, 196, 171, 4, 26, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 67, 72, 18, 128, 52, 35, 57, 117, 50, 87, 0, 0, 0, 0, 0, 13, 67, 8, 146, 128, 69, 37, 57, 40, 89, 114, 87, 0, 12, 2, 95, 35, 34, 36, 87, 47, 106, 47, 36, 0, 0, 12, 2, 95, 34, 48, 107, 70, 37, 65, 35, 87, 0, 0, 13, 138, 16, 1, 20, 9, 5, 197, 161, 196, 129, 13, 66, 16, 2, 95, 33, 37, 86, 87, 116, 49, 40, 63, 86, 106, 63, 36, 0, 0, 0, 14, 2, 95, 39, 35, 48, 39, 87, 47, 34, 112, 81, 87, 0, 0, 7, 196, 76, 19, 66, 60, 20, 0, 0, 9, 134, 20, 196, 129, 16, 1, 20, 66, 0, 0, 12, 4, 95, 3, 1, 16, 55, 120, 55, 114, 87, 0, 0, 16, 2, 95, 41, 6, 120, 49, 35, 82, 35, 15, 122, 6, 120, 47, 0, 0, 11, 2, 95, 40, 6, 120, 49, 35, 82, 35, 0, 0, 0, 10, 2, 95, 46, 48, 40, 50, 49, 122, 0, 0, 11, 2, 95, 45, 63, 106, 50, 40, 87, 87, 0, 0, 10, 2, 95, 44, 49, 39, 63, 35, 122, 0, 0, 9, 2, 95, 51, 47, 51, 106, 87, 0, 0, 10, 2, 95, 50, 70, 6, 37, 82, 37, 0, 0, 10, 2, 95, 49, 82, 6, 120, 50, 87, 0, 0, 11, 2, 95, 48, 50, 6, 40, 55, 55, 36, 0, 0, 13, 2, 95, 55, 87, 6, 36, 48, 47, 37, 65, 37, 0, 0, 7, 196, 72, 85, 18, 60, 20, 10, 2, 95, 54, 87, 6, 36, 89, 37, 0, 0, 14, 67, 40, 19, 150, 57, 35, 50, 82, 111, 52, 37, 87, 0, 10, 2, 95, 53, 48, 6, 120, 122, 37, 0, 0, 11, 2, 95, 52, 74, 6, 36, 47, 52, 37, 0, 0, 13, 2, 95, 59, 87, 36, 63, 37, 49, 112, 55, 87, 0, 0, 9, 2, 95, 58, 49, 112, 55, 87, 0, 0, 12, 2, 95, 57, 70, 6, 36, 82, 37, 65, 37, 0, 0, 12, 2, 95, 56, 6, 35, 87, 47, 117, 65, 37, 0, 0, 16, 2, 95, 63, 57, 116, 47, 111, 57, 40, 63, 86, 106, 63, 36, 0, 0, 17, 2, 95, 62, 55, 6, 120, 55, 111, 49, 87, 15, 48, 6, 35, 52, 0, 0, 0, 17, 2, 95, 60, 63, 6, 35, 86, 111, 49, 87, 15, 48, 6, 35, 52, 0, 0, 0, 0, 0, 12, 137, 16, 18, 15, 20, 5, 197, 190, 196, 147, 67, 7, 2, 95, 64, 35, 47, 0, 0, 0, 0, 0, 0, 0, 6, 195, 48, 81, 207, 20, 0, 0, 0, 0, 0, 0, 0, 15, 67, 16, 80, 192, 70, 36, 78, 36, 63, 69, 52, 37, 87, 0, 0, 0, 0, 5, 194, 85, 160, 72, 0, 0, 13, 4, 95, 4, 15, 20, 48, 6, 40, 50, 49, 122, 0, 0, 0, 0, 18, 2, 95, 91, 49, 82, 6, 35, 70, 52, 111, 47, 120, 49, 35, 82, 35, 0, 0, 6, 195, 88, 148, 147, 72, 0, 0, 15, 4, 95, 226, 128, 146, 70, 117, 63, 40, 86, 106, 63, 36, 0, 0, 20, 2, 95, 95, 48, 35, 87, 82, 106, 47, 52, 117, 57, 40, 63, 86, 106, 63, 36, 0, 0, 10, 2, 95, 94, 87, 35, 49, 50, 36, 0, 0, 23, 2, 95, 93, 49, 82, 6, 35, 70, 52, 111, 47, 120, 49, 35, 82, 35, 15, 122, 6, 120, 47, 0, 0, 27, 4, 95, 226, 128, 150, 70, 6, 40, 69, 40, 55, 122, 47, 111, 87, 47, 4, 111, 82, 87, 82, 106, 47, 52, 35, 0, 0, 15, 67, 24, 18, 192, 81, 35, 49, 40, 55, 47, 111, 47, 36, 0, 14, 4, 2, 45, 2, 1, 69, 120, 70, 52, 106, 69, 35, 0, 0, 0, 8, 197, 44, 20, 212, 72, 240, 20, 0, 26, 2, 95, 96, 6, 35, 48, 79, 52, 120, 86, 47, 114, 87, 15, 6, 35, 48, 39, 87, 47, 52, 39, 81, 87, 0, 0, 0, 0, 0, 9, 198, 56, 84, 1, 72, 179, 192, 67, 0, 0, 0, 0, 12, 4, 95, 7, 18, 22, 79, 52, 6, 111, 82, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 9, 5, 11, 197, 161, 72, 0, 0, 0, 16, 2, 95, 123, 81, 6, 37, 79, 113, 52, 120, 49, 35, 82, 35, 0, 13, 4, 95, 4, 9, 1, 6, 40, 63, 55, 116, 122, 0, 0, 0, 0, 0, 10, 199, 36, 226, 207, 28, 226, 84, 60, 20, 0, 10, 2, 95, 126, 47, 37, 55, 70, 36, 0, 0, 21, 2, 95, 125, 81, 6, 37, 79, 113, 52, 120, 49, 35, 82, 35, 15, 122, 6, 120, 47, 0, 0, 15, 2, 95, 124, 87, 47, 111, 82, 87, 82, 106, 47, 52, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 84, 224, 72, 8, 0, 0, 6, 195, 33, 81, 207, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 35, 51, 50, 47, 40, 49, 89, 40, 63, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 199, 36, 229, 5, 72, 209, 67, 60, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 13, 196, 147, 19, 72, 0, 0, 6, 195, 49, 101, 64, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 16, 243, 73, 56, 240, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 3, 4, 197, 190, 73, 107, 0, 0, 9, 198, 64, 17, 193, 48, 19, 64, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 12, 21, 82, 72, 0, 0, 0, 0, 6, 18, 66, 102, 0, 104, 0, 119, 0, 120, 0, 7, 6, 18, 67, 196, 141, 0, 196, 183, 0, 196, 188, 0, 197, 134, 0, 197, 190, 0, 7, 6, 18, 68, 105, 101, 109, 0, 97, 109, 0, 111, 115, 0, 196, 129, 0, 115, 0, 97, 0, 117, 0, 105, 0, 7, 6, 18, 69, 196, 129, 109, 0, 196, 129, 115, 0, 97, 115, 0, 97, 105, 0, 196, 129, 0, 117, 0, 97, 0, 7, 6, 18, 70, 105, 101, 109, 0, 105, 115, 0, 105, 109, 0, 111, 115, 0, 196, 171, 0, 105, 0, 7, 6, 18, 71, 196, 129, 0, 97, 0, 7, 6, 18, 72, 196, 147, 109, 0, 196, 147, 115, 0, 101, 115, 0, 101, 105, 0, 196, 147, 0, 101, 0, 105, 0, 117, 0, 7, 6, 18, 73, 97, 109, 105, 101, 115, 0, 97, 109, 196, 129, 115, 0, 97, 109, 97, 115, 0, 97, 109, 97, 0, 97, 109, 105, 0, 97, 109, 115, 0, 7, 6, 18, 74, 197, 161, 0, 115, 0, 7, 6, 18, 75, 116, 0, 100, 0, 106, 0, 7, 6, 18, 76, 105, 101, 109, 0, 111, 115, 0, 105, 0, 117, 0, 7, 6, 18, 77, 105, 101, 109, 0, 97, 109, 0, 111, 115, 0, 196, 129, 0, 115, 0, 7, 6, 18, 78, 196, 147, 0, 101, 0, 7, 6, 196, 129, 0, 3, 111, 0, 7, 6, 196, 141, 0, 3, 74, 0, 7, 6, 196, 147, 0, 3, 107, 0, 7, 6, 196, 163, 0, 3, 77, 0, 7, 6, 196, 171, 0, 3, 106, 0, 7, 6, 196, 183, 0, 3, 78, 0, 7, 6, 196, 188, 0, 4, 1, 107, 2, 117, 3, 55, 57, 0, 1, 107, 2, 117, 0, 3, 61, 0, 7, 6, 197, 134, 0, 3, 65, 0, 7, 6, 197, 141, 0, 3, 112, 0, 7, 6, 197, 151, 0, 3, 34, 0, 7, 6, 197, 161, 0, 3, 89, 0, 7, 6, 197, 171, 0, 3, 113, 0, 7, 6, 197, 190, 0, 3, 88, 0, 7, 6, 97, 0, 3, 35, 0, 112, 3, 35, 48, 0, 105, 3, 114, 0, 117, 3, 116, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 104, 3, 74, 0, 3, 122, 0, 4, 104, 1, 105, 114, 100, 105, 114, 102, 2, 115, 3, 122, 105, 0, 104, 1, 114, 101, 2, 101, 114, 99, 111, 103, 115, 0, 7, 6, 100, 0, 3, 70, 0, 7, 6, 101, 0, 3, 36, 0, 105, 3, 115, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 3, 79, 0, 8, 2, 32, 3, 79, 35, 0, 1, 32, 32, 15, 15, 2, 32, 3, 79, 35, 70, 35, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 101, 3, 120, 0, 117, 3, 121, 0, 7, 6, 106, 0, 3, 57, 0, 196, 129, 8, 3, 57, 111, 0, 196, 129, 110, 111, 8, 3, 57, 111, 50, 117, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 3, 55, 0, 108, 3, 55, 55, 12, 0, 7, 6, 109, 0, 3, 63, 0, 97, 122, 8, 3, 63, 35, 86, 0, 109, 3, 63, 63, 12, 0, 7, 6, 110, 0, 3, 50, 0, 110, 3, 50, 50, 12, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 7, 6, 111, 0, 4, 1, 97, 2, 114, 3, 39, 0, 1, 97, 104, 0, 1, 98, 2, 98, 0, 1, 98, 2, 106, 18, 69, 32, 0, 1, 98, 2, 107, 115, 0, 1, 98, 2, 109, 98, 0, 1, 98, 2, 110, 196, 147, 0, 1, 98, 2, 114, 97, 107, 0, 1, 98, 2, 114, 97, 116, 0, 1, 98, 2, 114, 116, 0, 1, 98, 2, 116, 196, 129, 110, 0, 1, 98, 2, 196, 188, 197, 161, 0, 1, 98, 97, 2, 110, 0, 1, 98, 97, 2, 114, 0, 1, 98, 97, 107, 2, 116, 0, 1, 98, 97, 108, 2, 114, 97, 0, 1, 98, 97, 115, 2, 116, 0, 1, 98, 105, 114, 2, 110, 117, 107, 0, 1, 98, 109, 111, 0, 1, 98, 114, 97, 107, 0, 1, 98, 114, 117, 116, 0, 1, 99, 2, 108, 108, 0, 1, 99, 101, 109, 0, 1, 100, 2, 99, 0, 1, 100, 2, 100, 101, 107, 0, 1, 100, 2, 103, 109, 0, 1, 100, 2, 107, 117, 0, 1, 100, 2, 109, 105, 110, 0, 1, 100, 2, 109, 110, 18, 69, 32, 0, 1, 100, 2, 110, 107, 0, 1, 100, 2, 110, 110, 0, 1, 100, 2, 112, 0, 1, 100, 2, 114, 105, 0, 1, 100, 2, 116, 196, 129, 99, 0, 1, 100, 2, 116, 196, 147, 0, 1, 100, 2, 122, 0, 1, 100, 97, 2, 107, 0, 1, 100, 97, 2, 112, 0, 1, 100, 105, 101, 115, 112, 0, 1, 100, 105, 112, 115, 0, 1, 100, 110, 97, 109, 2, 108, 0, 1, 100, 111, 116, 114, 111, 2, 107, 0, 1, 101, 0, 1, 101, 163, 196, 0, 1, 102, 0, 1, 102, 2, 110, 111, 0, 1, 102, 2, 116, 111, 0, 1, 103, 2, 98, 101, 0, 1, 103, 2, 107, 0, 1, 103, 2, 110, 0, 1, 103, 2, 114, 105, 108, 0, 1, 103, 2, 116, 102, 0, 1, 103, 97, 2, 110, 196, 129, 0, 1, 103, 97, 102, 0, 1, 103, 105, 122, 2, 116, 18, 68, 32, 0, 1, 103, 110, 105, 114, 0, 1, 104, 0, 1, 105, 0, 1, 105, 2, 103, 0, 1, 105, 98, 0, 1, 105, 99, 2, 110, 0, 1, 105, 114, 116, 0, 1, 105, 115, 0, 1, 106, 2, 100, 101, 0, 1, 106, 2, 103, 0, 1, 106, 2, 110, 105, 0, 1, 106, 97, 109, 0, 1, 106, 102, 0, 1, 107, 2, 97, 108, 0, 1, 107, 2, 100, 101, 107, 0, 1, 107, 2, 100, 105, 102, 0, 1, 107, 2, 100, 196, 147, 0, 1, 107, 2, 101, 0, 1, 107, 2, 103, 110, 0, 1, 107, 2, 107, 111, 0, 1, 107, 2, 108, 97, 98, 0, 1, 107, 2, 108, 101, 0, 1, 107, 2, 108, 104, 0, 1, 107, 2, 108, 105, 0, 1, 107, 2, 108, 111, 0, 1, 107, 2, 108, 112, 0, 1, 107, 2, 108, 196, 129, 0, 1, 107, 2, 108, 196, 147, 0, 1, 107, 2, 108, 196, 171, 0, 1, 107, 2, 112, 101, 110, 0, 1, 107, 2, 112, 105, 106, 0, 1, 107, 2, 112, 117, 108, 196, 129, 0, 1, 107, 2, 112, 117, 108, 196, 147, 0, 1, 107, 2, 112, 196, 147, 17, 67, 0, 1, 107, 2, 112, 196, 147, 32, 0, 1, 107, 2, 114, 17, 65, 102, 0, 1, 107, 2, 114, 97, 0, 1, 107, 2, 114, 101, 106, 0, 1, 107, 2, 114, 101, 107, 0, 1, 107, 2, 114, 101, 108, 0, 1, 107, 2, 114, 101, 115, 0, 1, 107, 2, 114, 112, 0, 1, 107, 2, 114, 116, 0, 1, 107, 2, 114, 117, 109, 0, 1, 107, 2, 114, 117, 110, 0, 1, 107, 2, 114, 117, 112, 0, 1, 107, 2, 114, 118, 0, 1, 107, 2, 115, 105, 110, 0, 1, 107, 2, 115, 109, 0, 1, 107, 2, 115, 116, 196, 171, 109, 0, 1, 107, 2, 116, 97, 110, 0, 1, 107, 2, 116, 101, 0, 1, 107, 2, 116, 108, 0, 1, 107, 2, 116, 196, 147, 0, 1, 107, 2, 118, 0, 1, 107, 2, 196, 183, 0, 1, 107, 97, 2, 114, 0, 1, 107, 101, 100, 0, 1, 107, 105, 101, 108, 0, 1, 107, 105, 110, 0, 1, 107, 108, 97, 0, 1, 107, 111, 107, 2, 115, 0, 1, 107, 111, 115, 0, 1, 107, 111, 161, 197, 0, 1, 107, 114, 97, 110, 0, 1, 107, 114, 97, 115, 0, 1, 108, 2, 103, 97, 114, 0, 1, 108, 2, 106, 18, 71, 108, 0, 1, 108, 2, 107, 97, 108, 0, 1, 108, 2, 114, 110, 0, 1, 108, 2, 115, 106, 0, 1, 108, 2, 116, 18, 72, 32, 0, 1, 108, 2, 196, 163, 105, 122, 12, 0, 1, 108, 98, 2, 107, 0, 1, 108, 98, 2, 110, 0, 1, 108, 98, 2, 196, 183, 0, 1, 108, 101, 109, 2, 100, 114, 0, 1, 108, 101, 109, 2, 109, 0, 1, 108, 101, 118, 0, 1, 108, 102, 0, 1, 108, 103, 2, 98, 0, 1, 108, 103, 2, 109, 0, 1, 108, 103, 2, 114, 105, 0, 1, 108, 104, 2, 114, 111, 0, 1, 108, 105, 102, 0, 1, 108, 105, 112, 2, 116, 0, 1, 108, 107, 2, 122, 101, 116, 0, 1, 108, 111, 104, 0, 1, 108, 111, 107, 0, 1, 108, 112, 2, 109, 0, 1, 108, 112, 2, 118, 18, 68, 32, 0, 1, 108, 112, 115, 107, 101, 0, 1, 108, 115, 2, 118, 0, 1, 108, 115, 105, 100, 0, 1, 109, 2, 98, 0, 1, 109, 2, 100, 97, 108, 0, 1, 109, 2, 100, 101, 0, 1, 109, 2, 100, 105, 102, 0, 1, 109, 2, 100, 117, 0, 1, 109, 2, 100, 196, 129, 108, 0, 1, 109, 2, 108, 100, 0, 1, 109, 2, 108, 101, 0, 1, 109, 2, 108, 105, 0, 1, 109, 2, 108, 117, 0, 1, 109, 2, 109, 101, 110, 116, 0, 1, 109, 2, 110, 97, 114, 104, 0, 1, 109, 2, 110, 105, 116, 0, 1, 109, 2, 110, 111, 0, 1, 109, 2, 110, 115, 116, 0, 1, 109, 2, 110, 116, 0, 1, 109, 2, 112, 0, 1, 109, 2, 114, 97, 0, 1, 109, 2, 114, 102, 0, 1, 109, 2, 114, 115, 0, 1, 109, 2, 114, 196, 129, 0, 1, 109, 2, 116, 105, 0, 1, 109, 2, 116, 196, 171, 0, 1, 109, 2, 197, 161, 101, 0, 1, 109, 97, 2, 110, 0, 1, 109, 97, 2, 114, 0, 1, 109, 101, 100, 0, 1, 109, 105, 2, 110, 0, 1, 109, 114, 97, 104, 2, 110, 105, 122, 196, 147, 0, 1, 109, 114, 97, 104, 2, 110, 196, 147, 0, 1, 109, 115, 2, 196, 188, 0, 1, 109, 115, 105, 101, 115, 0, 1, 109, 115, 111, 2, 103, 0, 1, 109, 116, 97, 2, 115, 0, 1, 109, 117, 104, 0, 1, 110, 2, 107, 18, 75, 0, 1, 110, 2, 109, 101, 110, 0, 1, 110, 2, 109, 105, 110, 18, 71, 0, 1, 110, 2, 109, 105, 110, 18, 78, 0, 1, 110, 2, 114, 98, 0, 1, 110, 2, 114, 100, 0, 1, 110, 2, 114, 109, 0, 1, 110, 2, 114, 118, 0, 1, 110, 2, 116, 97, 114, 0, 1, 110, 2, 116, 196, 129, 114, 0, 1, 110, 2, 118, 18, 69, 32, 0, 1, 110, 2, 118, 97, 116, 0, 1, 110, 2, 118, 101, 108, 18, 72, 32, 0, 1, 110, 2, 118, 111, 0, 1, 110, 2, 118, 196, 129, 99, 105, 0, 1, 110, 97, 2, 108, 0, 1, 110, 97, 2, 109, 0, 1, 110, 97, 2, 110, 0, 1, 110, 97, 2, 116, 0, 1, 110, 97, 101, 107, 111, 0, 1, 110, 97, 114, 97, 112, 0, 1, 110, 101, 99, 115, 0, 1, 110, 101, 100, 0, 1, 110, 101, 102, 0, 1, 110, 101, 103, 0, 1, 110, 101, 116, 115, 2, 103, 0, 1, 110, 103, 0, 1, 110, 103, 97, 0, 1, 110, 105, 97, 107, 0, 1, 110, 105, 108, 2, 116, 105, 112, 0, 1, 110, 105, 109, 97, 0, 1, 110, 105, 118, 107, 101, 0, 1, 110, 111, 0, 1, 110, 111, 103, 0, 1, 110, 111, 109, 0, 1, 110, 111, 115, 0, 1, 110, 112, 105, 104, 0, 1, 110, 114, 97, 0, 1, 110, 116, 101, 0, 1, 112, 2, 100, 101, 0, 1, 112, 2, 101, 0, 1, 112, 2, 108, 97, 0, 1, 112, 2, 108, 101, 109, 0, 1, 112, 2, 108, 105, 0, 1, 112, 2, 108, 111, 0, 1, 112, 2, 108, 115, 116, 0, 1, 112, 2, 108, 196, 129, 0, 1, 112, 2, 108, 196, 171, 0, 1, 112, 2, 109, 101, 114, 0, 1, 112, 2, 109, 112, 0, 1, 112, 2, 110, 99, 0, 1, 112, 2, 112, 0, 1, 112, 2, 114, 99, 0, 1, 112, 2, 114, 111, 0, 1, 112, 2, 114, 116, 0, 1, 112, 2, 115, 116, 97, 109, 0, 1, 112, 2, 115, 116, 101, 109, 0, 1, 112, 2, 115, 116, 101, 110, 0, 1, 112, 2, 115, 116, 101, 114, 0, 1, 112, 2, 115, 116, 109, 0, 1, 112, 2, 115, 116, 115, 111, 0, 1, 112, 2, 115, 116, 117, 108, 0, 1, 112, 2, 116, 101, 110, 0, 1, 112, 2, 122, 0, 1, 112, 2, 196, 147, 0, 1, 112, 97, 2, 107, 0, 1, 112, 97, 2, 108, 0, 1, 112, 97, 2, 115, 116, 114, 111, 102, 0, 1, 112, 101, 2, 108, 0, 1, 112, 101, 2, 115, 18, 68, 32, 0, 1, 112, 101, 100, 0, 1, 112, 105, 104, 0, 1, 112, 105, 116, 0, 1, 112, 105, 116, 110, 97, 0, 1, 112, 111, 0, 1, 112, 111, 114, 112, 0, 1, 112, 114, 101, 116, 110, 105, 0, 1, 112, 115, 2, 110, 0, 1, 112, 115, 2, 114, 116, 0, 1, 112, 115, 101, 100, 0, 1, 112, 115, 105, 100, 0, 1, 114, 2, 108, 0, 1, 114, 2, 109, 97, 0, 1, 114, 2, 109, 98, 0, 1, 114, 2, 109, 196, 129, 0, 1, 114, 2, 114, 0, 1, 114, 2, 115, 105, 106, 0, 1, 114, 2, 115, 116, 98, 0, 1, 114, 2, 116, 101, 114, 0, 1, 114, 2, 116, 196, 147, 0, 1, 114, 97, 108, 111, 112, 0, 1, 114, 97, 109, 0, 1, 114, 97, 112, 2, 100, 0, 1, 114, 98, 2, 109, 0, 1, 114, 98, 2, 110, 0, 1, 114, 98, 2, 197, 161, 0, 1, 114, 100, 105, 104, 0, 1, 114, 101, 2, 103, 0, 1, 114, 101, 97, 2, 100, 0, 1, 114, 101, 97, 2, 102, 111, 0, 1, 114, 101, 97, 2, 115, 111, 0, 1, 114, 101, 116, 115, 0, 1, 114, 102, 2, 110, 0, 1, 114, 102, 97, 0, 1, 114, 103, 97, 0, 1, 114, 104, 2, 109, 0, 1, 114, 104, 2, 110, 111, 0, 1, 114, 104, 110, 105, 115, 0, 1, 114, 105, 98, 0, 1, 114, 105, 101, 110, 0, 1, 114, 105, 112, 0, 1, 114, 105, 190, 197, 0, 1, 114, 107, 2, 110, 197, 161, 0, 1, 114, 107, 2, 115, 0, 1, 114, 107, 97, 0, 1, 114, 111, 108, 104, 0, 1, 114, 111, 112, 0, 1, 114, 112, 2, 98, 0, 1, 114, 112, 2, 99, 0, 1, 114, 112, 2, 100, 0, 1, 114, 112, 2, 103, 110, 0, 1, 114, 112, 2, 103, 114, 0, 1, 114, 112, 2, 106, 0, 1, 114, 112, 2, 107, 0, 1, 114, 112, 2, 108, 101, 0, 1, 114, 112, 2, 109, 0, 1, 114, 112, 2, 112, 0, 1, 114, 112, 2, 115, 112, 0, 1, 114, 112, 2, 115, 116, 0, 1, 114, 112, 2, 116, 101, 0, 1, 114, 112, 2, 116, 111, 0, 1, 114, 112, 2, 118, 105, 110, 0, 1, 114, 112, 2, 118, 105, 122, 0, 1, 114, 112, 2, 118, 196, 171, 122, 0, 1, 114, 112, 2, 197, 190, 0, 1, 114, 112, 101, 0, 1, 114, 112, 109, 105, 0, 1, 114, 116, 2, 109, 0, 1, 114, 116, 2, 116, 0, 1, 114, 116, 101, 109, 0, 1, 114, 116, 101, 114, 0, 1, 114, 116, 105, 0, 1, 114, 116, 110, 105, 0, 1, 114, 116, 115, 97, 2, 110, 0, 1, 114, 116, 115, 107, 111, 0, 1, 115, 2, 99, 105, 0, 1, 115, 2, 107, 111, 0, 1, 115, 2, 107, 114, 0, 1, 115, 2, 108, 97, 114, 0, 1, 115, 2, 108, 102, 0, 1, 115, 2, 108, 105, 100, 0, 1, 115, 2, 108, 111, 196, 163, 0, 1, 115, 2, 108, 115, 116, 0, 1, 115, 2, 108, 116, 0, 1, 115, 2, 108, 118, 0, 1, 115, 2, 108, 196, 129, 114, 0, 1, 115, 2, 108, 196, 171, 100, 18, 68, 32, 0, 1, 115, 2, 108, 196, 171, 100, 196, 129, 0, 1, 115, 2, 110, 111, 0, 1, 115, 2, 110, 196, 129, 0, 1, 115, 2, 112, 114, 0, 1, 115, 2, 114, 0, 1, 115, 2, 118, 0, 1, 115, 97, 107, 110, 105, 0, 1, 115, 97, 114, 2, 108, 0, 1, 115, 98, 97, 2, 108, 0, 1, 115, 105, 2, 110, 0, 1, 115, 107, 101, 0, 1, 115, 110, 111, 107, 0, 1, 116, 2, 107, 115, 0, 1, 116, 2, 108, 101, 114, 0, 1, 116, 2, 109, 97, 115, 0, 1, 116, 2, 110, 0, 1, 116, 2, 110, 105, 122, 0, 1, 116, 2, 110, 110, 0, 1, 116, 2, 114, 0, 1, 116, 2, 114, 97, 0, 1, 116, 2, 114, 111, 0, 1, 116, 2, 114, 196, 129, 0, 1, 116, 2, 116, 196, 147, 109, 0, 1, 116, 97, 100, 0, 1, 116, 97, 109, 101, 110, 105, 107, 0, 1, 116, 101, 98, 0, 1, 116, 101, 103, 0, 1, 116, 101, 109, 2, 100, 0, 1, 116, 101, 110, 0, 1, 116, 101, 116, 2, 118, 0, 1, 116, 105, 99, 0, 1, 116, 105, 108, 0, 1, 116, 110, 97, 2, 108, 0, 1, 116, 110, 97, 2, 110, 0, 1, 116, 110, 97, 112, 0, 1, 116, 110, 101, 0, 1, 116, 110, 111, 0, 1, 116, 111, 102, 2, 103, 114, 0, 1, 116, 111, 109, 2, 100, 114, 111, 0, 1, 116, 111, 114, 112, 0, 1, 116, 112, 101, 2, 21, 0, 1, 116, 112, 105, 114, 107, 0, 1, 116, 114, 97, 107, 0, 1, 116, 114, 111, 0, 1, 116, 115, 2, 107, 104, 0, 1, 116, 115, 2, 109, 97, 116, 0, 1, 116, 115, 101, 114, 104, 0, 1, 116, 115, 105, 104, 0, 1, 116, 115, 105, 114, 97, 0, 1, 116, 115, 111, 2, 112, 18, 68, 32, 0, 1, 116, 117, 97, 2, 109, 0, 1, 116, 117, 97, 2, 114, 105, 0, 1, 116, 117, 108, 112, 2, 107, 0, 1, 118, 2, 98, 0, 1, 118, 2, 107, 97, 0, 1, 118, 2, 108, 100, 0, 1, 118, 2, 108, 101, 106, 0, 1, 118, 2, 108, 102, 0, 1, 118, 2, 108, 116, 0, 1, 118, 2, 108, 117, 0, 1, 118, 2, 108, 118, 0, 1, 118, 97, 102, 0, 1, 118, 97, 108, 115, 0, 1, 118, 97, 114, 98, 0, 1, 118, 101, 2, 108, 0, 1, 118, 105, 0, 1, 118, 105, 97, 114, 2, 32, 0, 1, 118, 107, 0, 1, 118, 110, 111, 107, 0, 1, 118, 114, 101, 110, 0, 1, 119, 0, 1, 120, 0, 1, 122, 2, 106, 18, 68, 32, 12, 0, 1, 122, 2, 110, 17, 65, 116, 111, 0, 1, 122, 2, 110, 100, 0, 1, 122, 97, 114, 0, 1, 122, 101, 109, 0, 1, 122, 105, 2, 108, 0, 1, 122, 110, 101, 0, 1, 161, 197, 2, 107, 0, 1, 161, 197, 2, 115, 101, 106, 0, 1, 190, 197, 2, 107, 101, 106, 0, 1, 190, 197, 2, 110, 103, 0, 1, 190, 197, 97, 109, 0, 1, 190, 197, 100, 2, 117, 108, 0, 2, 18, 66, 0, 2, 18, 71, 0, 2, 28, 17, 12, 12, 12, 12, 0, 2, 98, 97, 109, 0, 2, 98, 106, 101, 0, 2, 100, 105, 97, 0, 2, 105, 0, 2, 107, 101, 0, 2, 107, 115, 105, 0, 2, 107, 115, 111, 108, 0, 2, 107, 116, 0, 2, 107, 116, 111, 0, 2, 107, 117, 108, 0, 2, 107, 117, 112, 0, 2, 107, 196, 129, 108, 0, 2, 108, 101, 111, 0, 2, 108, 105, 103, 0, 2, 108, 105, 109, 112, 0, 2, 108, 111, 103, 0, 2, 108, 111, 196, 163, 0, 2, 108, 196, 171, 118, 0, 2, 109, 110, 105, 98, 0, 2, 109, 196, 129, 114, 0, 2, 110, 103, 0, 2, 110, 107, 111, 0, 2, 110, 111, 0, 2, 110, 116, 111, 0, 2, 112, 99, 0, 2, 112, 101, 114, 97, 116, 0, 2, 112, 111, 0, 2, 112, 116, 105, 107, 0, 2, 112, 116, 105, 109, 0, 2, 112, 116, 105, 115, 0, 2, 112, 116, 105, 196, 183, 0, 2, 114, 97, 110, 12, 0, 2, 114, 97, 116, 0, 2, 114, 100, 0, 2, 114, 103, 0, 2, 114, 104, 105, 100, 0, 2, 114, 105, 101, 110, 0, 2, 114, 105, 103, 0, 2, 114, 105, 196, 163, 0, 2, 114, 107, 0, 2, 114, 110, 105, 116, 0, 2, 114, 116, 111, 0, 2, 114, 196, 129, 107, 0, 2, 114, 196, 129, 116, 0, 2, 114, 196, 183, 0, 2, 115, 99, 105, 108, 0, 2, 115, 109, 111, 0, 2, 117, 0, 2, 122, 111, 110, 0, 8, 2, 98, 108, 105, 103, 0, 8, 2, 98, 115, 0, 8, 2, 100, 101, 107, 0, 8, 2, 107, 115, 97, 110, 18, 69, 32, 0, 8, 2, 107, 115, 102, 0, 8, 2, 108, 97, 102, 18, 68, 32, 0, 8, 2, 108, 103, 18, 69, 32, 0, 8, 2, 110, 100, 97, 116, 114, 0, 8, 2, 112, 101, 114, 0, 8, 2, 115, 107, 97, 114, 18, 68, 32, 0, 8, 2, 118, 196, 129, 99, 0, 8, 2, 196, 188, 101, 103, 18, 68, 32, 0, 8, 98, 2, 108, 196, 171, 100, 18, 68, 32, 0, 8, 98, 2, 116, 18, 72, 32, 0, 8, 100, 2, 103, 18, 68, 32, 0, 8, 100, 2, 107, 18, 68, 32, 0, 8, 100, 110, 105, 0, 8, 100, 129, 196, 2, 108, 102, 18, 68, 0, 8, 106, 2, 116, 18, 69, 32, 0, 8, 107, 2, 106, 18, 69, 0, 8, 107, 2, 114, 196, 129, 0, 8, 107, 105, 112, 0, 8, 107, 115, 97, 2, 108, 100, 18, 68, 32, 0, 8, 108, 2, 108, 105, 116, 18, 69, 32, 0, 8, 108, 2, 110, 0, 8, 108, 2, 116, 105, 197, 134, 18, 69, 0, 8, 108, 97, 2, 116, 0, 8, 108, 97, 103, 2, 112, 18, 68, 0, 8, 108, 105, 107, 0, 8, 109, 2, 110, 0, 8, 110, 2, 97, 115, 18, 68, 32, 0, 8, 110, 2, 116, 18, 69, 32, 0, 8, 110, 2, 118, 101, 109, 98, 0, 8, 110, 97, 110, 0, 8, 110, 101, 116, 115, 0, 8, 112, 2, 108, 105, 101, 100, 0, 8, 112, 2, 110, 105, 106, 18, 68, 32, 0, 8, 112, 2, 116, 97, 197, 161, 18, 69, 0, 8, 114, 2, 98, 101, 114, 116, 0, 8, 114, 2, 100, 101, 114, 105, 107, 18, 68, 32, 0, 8, 114, 2, 107, 196, 129, 100, 18, 72, 32, 0, 8, 114, 2, 122, 101, 116, 18, 72, 32, 0, 8, 114, 2, 122, 196, 171, 110, 18, 72, 32, 0, 8, 114, 97, 98, 2, 107, 0, 8, 114, 97, 98, 2, 109, 0, 8, 114, 97, 98, 2, 110, 17, 65, 0, 8, 114, 98, 2, 107, 196, 129, 116, 18, 68, 32, 0, 8, 114, 98, 108, 117, 2, 107, 18, 69, 32, 0, 8, 114, 99, 105, 109, 0, 8, 114, 103, 2, 122, 110, 105, 106, 0, 8, 114, 107, 105, 109, 2, 12, 0, 8, 114, 116, 2, 106, 0, 8, 116, 2, 110, 105, 106, 18, 69, 32, 0, 8, 116, 2, 112, 98, 0, 8, 116, 2, 112, 105, 110, 97, 109, 0, 8, 116, 2, 112, 109, 0, 8, 116, 2, 112, 196, 129, 122, 18, 68, 32, 0, 8, 116, 2, 114, 101, 0, 8, 116, 2, 114, 112, 17, 65, 100, 0, 8, 116, 2, 114, 116, 18, 72, 32, 0, 8, 116, 105, 118, 2, 108, 100, 18, 68, 32, 0, 8, 116, 107, 101, 104, 0, 8, 116, 110, 97, 2, 197, 134, 105, 110, 18, 69, 32, 0, 8, 116, 117, 97, 0, 8, 122, 101, 2, 116, 0, 8, 122, 105, 0, 8, 161, 197, 2, 114, 116, 18, 76, 0, 114, 112, 111, 1, 107, 3, 39, 34, 48, 39, 0, 4, 116, 111, 1, 108, 2, 32, 3, 39, 47, 39, 0, 116, 111, 8, 0, 116, 111, 1, 109, 3, 39, 47, 112, 0, 4, 112, 111, 1, 114, 116, 110, 97, 3, 39, 48, 39, 0, 112, 111, 8, 116, 2, 103, 0, 112, 111, 8, 116, 2, 108, 0, 112, 111, 8, 116, 2, 110, 0, 112, 116, 111, 8, 3, 39, 48, 47, 39, 0, 107, 97, 107, 111, 1, 107, 2, 108, 3, 39, 49, 35, 49, 112, 0, 107, 111, 107, 2, 18, 68, 32, 3, 39, 49, 39, 49, 0, 107, 111, 109, 111, 1, 108, 3, 39, 49, 39, 63, 39, 0, 107, 111, 100, 1, 114, 107, 3, 39, 49, 39, 70, 0, 4, 107, 111, 1, 114, 2, 112, 101, 3, 39, 49, 112, 0, 107, 111, 1, 116, 111, 114, 112, 0, 4, 110, 1, 107, 3, 39, 50, 0, 110, 8, 108, 107, 0, 4, 110, 111, 1, 107, 3, 39, 50, 39, 0, 110, 111, 8, 109, 0, 4, 110, 111, 1, 100, 3, 39, 50, 112, 0, 110, 111, 1, 107, 101, 0, 110, 111, 1, 114, 116, 115, 97, 0, 114, 111, 1, 107, 3, 39, 52, 39, 0, 114, 110, 111, 1, 112, 3, 39, 52, 50, 39, 0, 109, 1, 107, 3, 39, 63, 0, 4, 109, 111, 1, 104, 3, 39, 63, 39, 0, 109, 111, 1, 107, 0, 109, 111, 1, 116, 0, 109, 111, 116, 2, 111, 3, 39, 63, 39, 47, 0, 109, 111, 110, 111, 115, 111, 1, 108, 3, 39, 63, 39, 50, 6, 39, 87, 39, 0, 109, 112, 111, 1, 107, 3, 39, 63, 48, 39, 0, 110, 103, 111, 108, 111, 1, 109, 3, 39, 66, 79, 39, 55, 39, 0, 110, 103, 111, 1, 109, 3, 39, 66, 79, 112, 0, 98, 1, 107, 3, 39, 69, 0, 98, 111, 1, 114, 2, 116, 3, 39, 69, 39, 0, 100, 105, 111, 8, 3, 39, 70, 37, 112, 0, 4, 100, 111, 1, 106, 3, 39, 70, 39, 0, 100, 111, 1, 114, 2, 100, 101, 110, 0, 100, 111, 8, 0, 103, 111, 1, 108, 3, 39, 79, 39, 0, 118, 111, 1, 114, 112, 3, 39, 82, 39, 0, 118, 103, 111, 114, 111, 100, 1, 110, 3, 39, 82, 79, 39, 34, 39, 70, 0, 122, 111, 1, 108, 105, 102, 3, 39, 86, 112, 0, 115, 116, 111, 106, 1, 100, 3, 39, 87, 47, 39, 57, 0, 115, 102, 111, 1, 102, 3, 39, 87, 81, 112, 0, 4, 115, 111, 1, 98, 105, 114, 3, 39, 87, 112, 0, 115, 111, 1, 108, 105, 102, 0, 111, 3, 39, 112, 0, 4, 1, 98, 2, 108, 3, 112, 0, 1, 98, 2, 114, 115, 0, 1, 99, 114, 101, 104, 2, 103, 0, 1, 100, 101, 104, 2, 110, 0, 1, 100, 107, 101, 110, 97, 0, 1, 100, 110, 2, 109, 18, 68, 32, 0, 1, 100, 110, 111, 103, 2, 108, 0, 1, 100, 114, 2, 109, 18, 68, 32, 0, 1, 101, 100, 105, 118, 0, 1, 102, 2, 110, 105, 0, 1, 103, 2, 103, 0, 1, 103, 2, 110, 105, 106, 0, 1, 103, 2, 114, 105, 106, 0, 1, 103, 2, 116, 105, 107, 0, 1, 103, 2, 116, 105, 115, 0, 1, 103, 2, 196, 163, 0, 1, 103, 97, 2, 110, 0, 1, 103, 101, 2, 110, 0, 1, 103, 101, 98, 2, 110, 105, 0, 1, 103, 101, 108, 97, 2, 114, 0, 1, 103, 101, 116, 97, 107, 2, 114, 0, 1, 103, 114, 101, 110, 101, 0, 1, 103, 114, 117, 102, 2, 110, 0, 1, 105, 2, 100, 18, 72, 32, 0, 1, 105, 2, 110, 18, 72, 32, 0, 1, 105, 100, 97, 114, 0, 1, 105, 100, 105, 0, 1, 105, 100, 117, 97, 0, 1, 105, 114, 116, 97, 112, 0, 1, 105, 118, 97, 0, 1, 106, 108, 0, 1, 107, 2, 100, 18, 77, 32, 0, 1, 107, 2, 109, 18, 69, 32, 12, 0, 1, 107, 97, 108, 2, 110, 0, 1, 107, 110, 105, 115, 0, 1, 107, 115, 2, 112, 18, 68, 32, 0, 1, 107, 115, 2, 112, 105, 106, 18, 69, 32, 0, 1, 107, 115, 2, 112, 105, 115, 0, 1, 108, 2, 103, 12, 0, 1, 108, 2, 110, 0, 1, 108, 2, 196, 163, 0, 1, 108, 2, 196, 163, 12, 0, 1, 108, 97, 2, 103, 0, 1, 108, 97, 107, 2, 114, 0, 1, 108, 104, 2, 114, 0, 1, 108, 105, 2, 103, 0, 1, 108, 107, 105, 99, 0, 1, 108, 107, 108, 111, 102, 0, 1, 108, 111, 2, 110, 105, 106, 0, 1, 108, 111, 2, 110, 105, 115, 116, 0, 1, 108, 111, 115, 0, 1, 109, 2, 99, 97, 114, 0, 1, 109, 2, 100, 18, 69, 32, 0, 1, 109, 97, 110, 105, 100, 0, 1, 109, 101, 2, 99, 105, 0, 1, 109, 105, 101, 110, 112, 0, 1, 109, 114, 97, 104, 2, 110, 0, 1, 109, 115, 111, 0, 1, 110, 2, 100, 18, 72, 32, 0, 1, 110, 2, 109, 18, 68, 32, 0, 1, 110, 2, 109, 18, 72, 32, 0, 1, 110, 2, 109, 105, 106, 18, 69, 32, 0, 1, 110, 97, 2, 100, 0, 1, 110, 105, 107, 0, 1, 110, 112, 105, 104, 2, 122, 18, 72, 32, 0, 1, 112, 2, 108, 18, 68, 32, 0, 1, 112, 2, 108, 18, 72, 32, 0, 1, 112, 109, 111, 112, 0, 1, 114, 100, 2, 109, 18, 68, 0, 1, 114, 101, 97, 0, 1, 114, 101, 108, 107, 115, 0, 1, 114, 104, 2, 110, 0, 1, 114, 105, 101, 0, 1, 114, 107, 97, 109, 0, 1, 114, 107, 105, 2, 110, 0, 1, 114, 116, 2, 102, 18, 69, 32, 0, 1, 114, 116, 2, 112, 0, 1, 114, 116, 105, 2, 110, 0, 1, 114, 116, 107, 101, 108, 101, 0, 1, 114, 116, 110, 111, 107, 0, 1, 114, 117, 107, 2, 114, 18, 72, 32, 0, 1, 115, 2, 108, 111, 0, 1, 115, 2, 114, 18, 68, 32, 12, 0, 1, 115, 2, 114, 18, 72, 32, 12, 12, 0, 1, 115, 111, 114, 101, 97, 2, 108, 0, 1, 115, 112, 97, 114, 0, 1, 115, 114, 101, 112, 2, 110, 0, 1, 116, 2, 100, 18, 72, 32, 12, 0, 1, 116, 2, 108, 18, 69, 32, 12, 0, 1, 116, 2, 110, 105, 107, 18, 69, 32, 0, 1, 116, 2, 110, 105, 115, 107, 0, 1, 116, 2, 114, 18, 72, 32, 12, 12, 0, 1, 116, 21, 2, 114, 0, 1, 116, 97, 2, 109, 0, 1, 116, 97, 114, 97, 109, 0, 1, 116, 97, 114, 111, 0, 1, 116, 107, 111, 0, 1, 116, 108, 97, 100, 2, 110, 0, 1, 116, 110, 97, 2, 110, 18, 68, 32, 0, 1, 116, 110, 111, 112, 2, 110, 0, 1, 116, 111, 2, 112, 18, 68, 32, 0, 1, 116, 111, 102, 0, 1, 116, 111, 110, 111, 109, 2, 110, 0, 1, 116, 112, 2, 109, 18, 68, 32, 0, 1, 116, 117, 2, 112, 105, 0, 1, 117, 108, 102, 2, 114, 0, 1, 122, 2, 110, 0, 1, 122, 2, 114, 18, 68, 32, 12, 0, 1, 122, 2, 114, 18, 72, 32, 12, 12, 0, 1, 122, 105, 112, 101, 2, 100, 0, 2, 32, 0, 2, 108, 18, 68, 32, 12, 0, 2, 110, 18, 68, 32, 12, 0, 2, 112, 18, 68, 32, 12, 0, 2, 114, 18, 68, 32, 12, 0, 2, 122, 18, 68, 32, 0, 2, 122, 18, 72, 32, 12, 0, 8, 2, 109, 105, 0, 8, 2, 109, 115, 0, 8, 2, 112, 101, 114, 18, 69, 32, 0, 8, 100, 2, 122, 18, 69, 32, 12, 12, 0, 8, 101, 114, 101, 116, 115, 0, 8, 102, 2, 108, 105, 106, 18, 69, 32, 0, 8, 103, 105, 2, 114, 18, 68, 32, 0, 8, 106, 2, 103, 18, 68, 32, 0, 8, 107, 101, 0, 8, 108, 2, 197, 190, 18, 69, 32, 0, 8, 108, 103, 2, 114, 105, 106, 18, 69, 32, 0, 8, 109, 2, 110, 105, 107, 18, 69, 32, 0, 8, 109, 2, 122, 117, 0, 8, 109, 97, 114, 2, 110, 18, 69, 32, 0, 8, 109, 115, 2, 103, 18, 68, 32, 0, 8, 114, 97, 98, 2, 110, 18, 68, 32, 0, 8, 115, 107, 111, 2, 108, 18, 68, 32, 0, 8, 116, 2, 110, 117, 115, 18, 68, 32, 0, 8, 116, 2, 114, 105, 106, 18, 68, 32, 0, 8, 116, 110, 97, 102, 2, 109, 18, 68, 32, 0, 8, 116, 114, 97, 107, 2, 110, 18, 68, 32, 0, 108, 111, 1, 112, 2, 32, 3, 112, 55, 112, 0, 115, 116, 111, 112, 1, 116, 117, 97, 3, 112, 87, 47, 39, 48, 0, 4, 3, 117, 0, 1, 98, 2, 32, 0, 1, 98, 2, 108, 111, 197, 161, 0, 1, 98, 2, 108, 196, 171, 100, 18, 73, 32, 0, 1, 98, 2, 108, 196, 171, 106, 0, 1, 98, 2, 108, 196, 171, 115, 0, 1, 98, 2, 108, 196, 171, 116, 0, 1, 98, 2, 108, 196, 171, 197, 161, 0, 1, 98, 97, 118, 2, 108, 18, 72, 32, 0, 1, 98, 129, 196, 2, 108, 0, 1, 99, 2, 32, 0, 1, 100, 2, 32, 0, 1, 100, 2, 122, 18, 72, 32, 12, 12, 0, 1, 102, 114, 147, 196, 115, 0, 1, 103, 2, 32, 0, 1, 103, 2, 114, 111, 0, 1, 103, 97, 109, 2, 110, 0, 1, 103, 97, 118, 2, 110, 0, 1, 103, 105, 97, 100, 2, 110, 0, 1, 103, 105, 97, 109, 2, 110, 0, 1, 103, 105, 97, 122, 0, 1, 103, 108, 105, 2, 110, 18, 70, 32, 0, 1, 103, 111, 108, 115, 0, 1, 103, 114, 97, 109, 2, 110, 0, 1, 103, 117, 97, 2, 110, 0, 1, 103, 171, 196, 108, 0, 1, 106, 2, 32, 0, 1, 106, 2, 110, 18, 70, 32, 0, 1, 107, 2, 32, 0, 1, 107, 2, 107, 111, 103, 0, 1, 107, 2, 107, 116, 196, 147, 108, 0, 1, 107, 2, 110, 18, 70, 32, 0, 1, 107, 2, 112, 106, 0, 1, 107, 2, 112, 196, 147, 106, 18, 68, 32, 0, 1, 107, 2, 112, 196, 147, 106, 18, 69, 32, 0, 1, 107, 2, 114, 18, 70, 32, 12, 0, 1, 107, 2, 197, 134, 18, 70, 32, 0, 1, 107, 97, 114, 116, 0, 1, 107, 101, 105, 110, 0, 1, 107, 107, 105, 116, 2, 32, 0, 1, 107, 108, 97, 109, 2, 18, 75, 0, 1, 107, 108, 97, 161, 197, 0, 1, 107, 114, 147, 196, 112, 2, 110, 0, 1, 107, 114, 147, 196, 112, 2, 197, 134, 0, 1, 107, 115, 2, 108, 0, 1, 107, 115, 2, 108, 18, 69, 32, 0, 1, 107, 115, 97, 118, 0, 1, 107, 171, 197, 107, 0, 1, 108, 2, 32, 0, 1, 108, 2, 122, 18, 72, 32, 0, 1, 108, 103, 97, 2, 110, 18, 69, 32, 0, 1, 108, 103, 97, 110, 0, 1, 108, 103, 101, 2, 110, 0, 1, 108, 105, 97, 100, 2, 110, 0, 1, 108, 105, 100, 2, 110, 0, 1, 108, 105, 100, 2, 197, 134, 0, 1, 108, 105, 122, 2, 110, 0, 1, 108, 105, 122, 2, 197, 134, 0, 1, 108, 111, 107, 115, 2, 18, 74, 0, 1, 108, 111, 107, 115, 2, 18, 75, 0, 1, 108, 111, 115, 2, 115, 32, 0, 1, 108, 111, 115, 2, 116, 0, 1, 108, 111, 115, 2, 116, 32, 0, 1, 108, 111, 115, 2, 197, 161, 0, 1, 108, 115, 2, 103, 18, 68, 32, 0, 1, 108, 115, 2, 103, 111, 0, 1, 108, 147, 196, 2, 32, 0, 1, 108, 147, 196, 99, 0, 1, 108, 161, 197, 2, 103, 18, 68, 32, 0, 1, 109, 2, 32, 0, 1, 109, 105, 97, 122, 0, 1, 109, 115, 2, 107, 0, 1, 109, 115, 114, 101, 118, 0, 1, 109, 122, 105, 118, 0, 1, 110, 2, 32, 0, 1, 110, 2, 108, 105, 107, 0, 1, 110, 2, 109, 18, 69, 32, 0, 1, 110, 97, 161, 197, 0, 1, 110, 101, 116, 115, 2, 18, 74, 0, 1, 110, 101, 116, 115, 2, 18, 75, 0, 1, 110, 110, 97, 118, 0, 1, 112, 2, 32, 0, 1, 112, 2, 114, 97, 0, 1, 112, 2, 115, 116, 111, 0, 1, 112, 2, 115, 116, 196, 171, 0, 1, 114, 2, 32, 0, 1, 114, 2, 98, 101, 197, 190, 0, 1, 114, 2, 107, 116, 117, 0, 1, 114, 2, 122, 18, 72, 32, 0, 1, 114, 97, 98, 2, 107, 108, 0, 1, 114, 97, 98, 2, 107, 196, 188, 0, 1, 114, 98, 2, 32, 0, 1, 114, 100, 2, 32, 0, 1, 114, 103, 2, 122, 12, 0, 1, 114, 107, 2, 103, 0, 1, 114, 107, 2, 107, 111, 0, 1, 114, 107, 2, 112, 196, 188, 111, 0, 1, 114, 112, 97, 2, 99, 18, 72, 32, 0, 1, 114, 112, 97, 2, 107, 0, 1, 114, 116, 171, 196, 118, 115, 0, 1, 115, 2, 32, 0, 1, 115, 2, 108, 18, 68, 32, 0, 1, 115, 2, 108, 18, 70, 32, 0, 1, 115, 2, 108, 111, 116, 0, 1, 115, 2, 108, 111, 197, 161, 0, 1, 115, 2, 108, 196, 171, 18, 75, 0, 1, 116, 2, 32, 0, 1, 116, 2, 110, 18, 70, 32, 0, 1, 116, 2, 114, 110, 12, 0, 1, 116, 2, 114, 197, 134, 12, 0, 1, 116, 101, 105, 99, 2, 107, 0, 1, 116, 110, 97, 107, 0, 1, 116, 114, 111, 107, 2, 115, 32, 0, 1, 116, 114, 111, 112, 115, 0, 1, 116, 115, 2, 112, 111, 0, 1, 116, 117, 97, 188, 196, 0, 1, 116, 129, 196, 2, 32, 0, 1, 116, 147, 196, 2, 32, 0, 1, 116, 171, 196, 118, 2, 108, 18, 68, 32, 0, 1, 118, 2, 32, 0, 1, 118, 97, 0, 1, 118, 101, 105, 114, 0, 1, 118, 108, 97, 0, 1, 118, 129, 196, 108, 98, 0, 1, 118, 171, 196, 114, 98, 0, 1, 122, 2, 32, 0, 1, 122, 105, 98, 2, 18, 75, 12, 0, 1, 134, 197, 0, 1, 141, 196, 0, 1, 161, 197, 2, 32, 0, 1, 161, 197, 111, 2, 32, 0, 1, 161, 197, 117, 2, 32, 0, 1, 163, 196, 2, 32, 0, 1, 183, 196, 0, 1, 188, 196, 0, 1, 190, 197, 0, 2, 18, 67, 0, 2, 100, 101, 114, 101, 0, 2, 100, 101, 114, 196, 147, 0, 2, 110, 97, 107, 116, 32, 0, 2, 115, 32, 0, 2, 115, 116, 32, 0, 2, 116, 32, 12, 12, 0, 2, 116, 105, 101, 115, 32, 12, 0, 2, 197, 161, 115, 32, 0, 2, 197, 161, 197, 134, 0, 8, 2, 108, 18, 69, 32, 12, 0, 8, 2, 114, 18, 70, 32, 0, 8, 98, 2, 108, 97, 32, 0, 8, 98, 2, 108, 117, 0, 8, 98, 2, 108, 196, 129, 109, 32, 0, 8, 98, 2, 122, 18, 72, 32, 12, 0, 8, 98, 2, 122, 97, 32, 0, 8, 100, 2, 110, 18, 69, 32, 12, 12, 0, 8, 100, 171, 196, 112, 115, 2, 108, 18, 69, 32, 0, 8, 103, 2, 114, 97, 32, 0, 8, 103, 2, 114, 111, 115, 32, 12, 0, 8, 106, 2, 32, 0, 8, 106, 2, 122, 97, 32, 0, 8, 107, 2, 100, 18, 72, 32, 0, 8, 107, 2, 112, 18, 69, 32, 0, 8, 107, 2, 112, 196, 129, 32, 0, 8, 107, 2, 114, 18, 72, 32, 0, 8, 107, 2, 114, 97, 32, 0, 8, 107, 2, 114, 100, 105, 114, 0, 8, 107, 2, 114, 100, 122, 0, 8, 107, 2, 118, 196, 129, 114, 110, 18, 70, 32, 0, 8, 107, 101, 110, 2, 32, 0, 8, 107, 115, 2, 112, 18, 68, 32, 0, 8, 107, 115, 97, 112, 2, 112, 18, 68, 32, 0, 8, 108, 2, 103, 18, 68, 32, 0, 8, 108, 2, 110, 18, 72, 32, 0, 8, 108, 105, 112, 2, 116, 32, 0, 8, 108, 147, 196, 116, 2, 116, 117, 32, 0, 8, 109, 2, 100, 18, 72, 32, 0, 8, 109, 105, 97, 108, 2, 110, 18, 70, 32, 0, 8, 109, 117, 107, 2, 100, 18, 72, 32, 0, 8, 110, 2, 12, 0, 8, 112, 2, 108, 18, 70, 32, 0, 8, 112, 2, 108, 105, 101, 0, 8, 112, 2, 108, 105, 106, 18, 69, 32, 0, 8, 112, 2, 112, 18, 72, 32, 0, 8, 112, 2, 196, 188, 0, 8, 112, 129, 196, 114, 2, 32, 0, 8, 114, 2, 109, 18, 69, 32, 0, 8, 114, 101, 116, 115, 2, 115, 32, 0, 8, 114, 112, 2, 106, 196, 129, 109, 32, 0, 8, 114, 112, 2, 109, 32, 0, 8, 114, 112, 2, 109, 98, 0, 8, 114, 112, 2, 109, 101, 115, 0, 8, 114, 116, 115, 2, 112, 18, 68, 32, 0, 8, 114, 116, 115, 97, 107, 2, 108, 18, 70, 32, 0, 8, 116, 2, 12, 0, 8, 116, 2, 114, 101, 105, 122, 32, 0, 8, 116, 2, 114, 117, 100, 0, 8, 116, 2, 122, 105, 101, 109, 32, 0, 8, 116, 97, 100, 2, 115, 32, 0, 8, 116, 110, 111, 107, 2, 115, 32, 0, 8, 116, 110, 111, 108, 98, 2, 115, 32, 0, 8, 116, 115, 2, 114, 18, 72, 32, 0, 8, 116, 115, 97, 115, 2, 112, 97, 109, 32, 0, 8, 134, 197, 161, 197, 2, 114, 18, 70, 32, 0, 8, 161, 197, 2, 122, 105, 101, 109, 32, 0, 8, 183, 196, 161, 197, 2, 114, 18, 70, 32, 0, 116, 111, 2, 32, 3, 117, 47, 117, 0, 112, 8, 114, 116, 2, 18, 68, 32, 3, 117, 48, 0, 4, 112, 111, 1, 107, 3, 117, 48, 117, 0, 112, 111, 1, 116, 2, 116, 0, 112, 111, 1, 116, 2, 197, 161, 0, 108, 1, 112, 171, 196, 115, 2, 18, 68, 32, 3, 117, 55, 0, 4, 108, 111, 1, 107, 115, 3, 117, 55, 117, 0, 108, 111, 1, 108, 2, 18, 75, 0, 108, 111, 8, 108, 2, 18, 74, 0, 98, 111, 8, 114, 2, 116, 32, 3, 117, 69, 117, 0, 4, 100, 111, 1, 107, 2, 108, 3, 117, 70, 117, 0, 100, 111, 8, 2, 115, 32, 0, 103, 1, 114, 112, 115, 3, 117, 79, 0, 122, 111, 2, 108, 18, 68, 32, 3, 117, 86, 117, 0, 115, 116, 1, 114, 112, 115, 3, 117, 87, 47, 0, 115, 116, 111, 2, 18, 75, 3, 117, 87, 47, 117, 0, 7, 6, 112, 0, 3, 48, 0, 117, 115, 8, 3, 48, 40, 87, 0, 7, 6, 113, 0, 3, 49, 82, 0, 7, 6, 114, 0, 3, 52, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 1, 115, 2, 115, 3, 47, 12, 0, 111, 8, 2, 32, 3, 47, 117, 0, 7, 6, 117, 0, 3, 40, 0, 105, 3, 119, 0, 7, 6, 118, 0, 3, 82, 0, 105, 115, 8, 3, 82, 37, 87, 0, 7, 6, 119, 0, 3, 82, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 4, 33, 2, 33, 3, 0, 4, 35, 1, 35, 3, 0, 4, 39, 3, 0, 4, 46, 1, 46, 3, 0, 58, 1, 32, 15, 2, 32, 15, 15, 32, 3, 0, 46, 2, 46, 3, 9, 0, 33, 3, 9, 37, 86, 87, 116, 49, 40, 63, 86, 106, 63, 36, 9, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 35, 1, 35, 35, 2, 32, 3, 24, 0, 58, 3, 49, 39, 55, 87, 0, 33, 61, 3, 50, 35, 82, 15, 82, 120, 50, 111, 70, 87, 0, 4, 35, 1, 32, 17, 65, 3, 52, 36, 87, 47, 106, 47, 36, 0, 35, 1, 32, 17, 67, 0, 62, 61, 3, 55, 6, 120, 55, 111, 49, 87, 15, 4, 82, 114, 15, 82, 6, 120, 50, 111, 70, 87, 0, 60, 61, 3, 63, 35, 86, 111, 49, 87, 15, 4, 82, 114, 15, 82, 6, 120, 50, 111, 70, 87, 0, 45, 8, 32, 2, 32, 15, 3, 63, 106, 50, 40, 87, 0, 36, 3, 70, 39, 55, 111, 34, 37, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts35 = FileInMemory_createWithData (12327, reinterpret_cast (&espeakdata_dicts35_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/lv_dict", L"lv"); Collection_addItem (me.peek(), espeakdata_dicts35.transfer()); static unsigned char espeakdata_dicts36_data[4946] = { 0, 4, 0, 0, 152, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 208, 184, 208, 188, 208, 176, 208, 176, 209, 130, 76, 0, 0, 15, 140, 208, 189, 208, 181, 208, 188, 208, 176, 208, 176, 209, 130, 76, 0, 0, 0, 0, 0, 0, 0, 0, 13, 1, 33, 6, 37, 86, 82, 136, 74, 50, 136, 49, 0, 0, 0, 11, 1, 35, 69, 14, 16, 6, 39, 57, 10, 0, 0, 0, 10, 1, 37, 48, 6, 39, 87, 47, 39, 0, 0, 7, 1, 38, 10, 6, 37, 0, 0, 0, 0, 0, 0, 8, 1, 43, 48, 55, 40, 87, 0, 0, 0, 0, 0, 11, 1, 47, 49, 14, 16, 6, 39, 86, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 5, 95, 48, 1, 14, 4, 37, 0, 0, 0, 13, 1, 58, 70, 82, 36, 10, 47, 39, 74, 49, 37, 0, 0, 0, 0, 0, 0, 0, 8, 1, 64, 10, 6, 36, 47, 0, 0, 0, 0, 0, 7, 65, 68, 49, 82, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 49, 77, 52, 69, 37, 55, 37, 6, 39, 50, 0, 0, 17, 65, 92, 70, 82, 39, 87, 47, 14, 16, 40, 49, 39, 15, 82, 13, 0, 0, 0, 16, 1, 94, 115, 6, 37, 34, 49, 40, 63, 81, 55, 36, 49, 87, 0, 0, 0, 7, 65, 96, 37, 49, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 104, 86, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 1, 126, 47, 6, 37, 55, 70, 120, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 208, 189, 208, 181, 208, 181, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 4, 16, 20, 9, 86, 6, 35, 48, 37, 16, 49, 120, 10, 0, 0, 0, 0, 9, 134, 209, 129, 209, 130, 208, 181, 72, 0, 0, 0, 0, 13, 138, 208, 189, 208, 181, 209, 129, 209, 130, 208, 181, 76, 0, 0, 15, 140, 208, 189, 208, 181, 208, 188, 208, 176, 209, 130, 208, 181, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 208, 184, 208, 188, 208, 176, 209, 136, 76, 0, 0, 0, 0, 0, 0, 9, 134, 209, 129, 209, 131, 208, 188, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 208, 189, 208, 181, 209, 129, 209, 131, 208, 188, 76, 0, 0, 0, 20, 3, 226, 132, 162, 48, 14, 16, 39, 37, 86, 82, 6, 39, 70, 37, 47, 36, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 208, 189, 208, 181, 208, 179, 208, 190, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 208, 186, 208, 190, 208, 179, 208, 190, 8, 0, 0, 0, 18, 3, 226, 128, 166, 47, 14, 16, 6, 37, 15, 47, 6, 39, 74, 49, 37, 0, 0, 19, 3, 226, 128, 161, 70, 82, 6, 39, 36, 50, 15, 49, 14, 16, 6, 87, 47, 0, 0, 11, 3, 226, 128, 160, 49, 14, 16, 87, 47, 0, 0, 0, 20, 3, 226, 128, 162, 79, 6, 39, 55, 36, 63, 35, 15, 47, 6, 39, 74, 49, 120, 0, 0, 0, 11, 3, 226, 130, 172, 6, 36, 82, 51, 39, 0, 0, 0, 0, 0, 0, 11, 136, 208, 184, 208, 188, 208, 176, 208, 188, 76, 0, 11, 3, 95, 49, 6, 6, 36, 70, 50, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 50, 6, 70, 82, 6, 36, 0, 0, 0, 0, 0, 13, 138, 208, 184, 208, 188, 208, 176, 208, 188, 208, 181, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 226, 128, 176, 48, 14, 16, 6, 39, 63, 37, 55, 0, 0, 11, 136, 208, 189, 208, 181, 208, 188, 208, 176, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 51, 88, 47, 14, 16, 6, 37, 107, 87, 107, 47, 0, 0, 11, 3, 95, 48, 67, 87, 47, 6, 39, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 49, 57, 70, 107, 82, 107, 47, 50, 6, 35, 36, 87, 36, 47, 0, 0, 17, 3, 95, 49, 56, 39, 87, 40, 63, 50, 6, 35, 36, 87, 36, 47, 0, 0, 14, 3, 95, 50, 67, 70, 82, 6, 36, 87, 47, 6, 35, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 49, 49, 36, 70, 136, 50, 6, 35, 36, 87, 36, 47, 0, 0, 12, 3, 95, 49, 48, 70, 6, 107, 87, 107, 47, 0, 0, 17, 3, 95, 49, 51, 47, 14, 16, 37, 50, 6, 35, 36, 87, 36, 47, 0, 0, 16, 3, 95, 49, 50, 70, 82, 35, 50, 6, 35, 36, 87, 36, 47, 0, 0, 16, 3, 95, 49, 53, 48, 107, 47, 50, 6, 35, 36, 87, 36, 47, 0, 0, 19, 3, 95, 49, 52, 74, 107, 47, 37, 34, 37, 50, 6, 35, 36, 87, 36, 47, 0, 0, 18, 3, 95, 49, 55, 87, 107, 70, 40, 63, 50, 6, 35, 36, 87, 36, 47, 0, 0, 16, 3, 95, 49, 54, 89, 107, 87, 50, 6, 35, 36, 87, 36, 47, 0, 0, 0, 17, 3, 95, 55, 88, 87, 107, 70, 6, 40, 63, 70, 107, 87, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 54, 67, 89, 6, 107, 87, 47, 6, 39, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 50, 88, 70, 82, 6, 35, 107, 87, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 63, 63, 86, 50, 35, 49, 0, 0, 0, 0, 17, 3, 95, 52, 88, 74, 107, 47, 37, 44, 6, 37, 107, 87, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 53, 88, 48, 6, 107, 107, 87, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 208, 186, 208, 190, 209, 152, 76, 0, 13, 3, 95, 54, 88, 89, 6, 107, 107, 87, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 56, 88, 39, 87, 6, 40, 63, 70, 107, 87, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 57, 88, 70, 107, 82, 6, 107, 107, 87, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 63, 65, 69, 40, 49, 82, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 134, 208, 184, 208, 187, 208, 184, 72, 8, 9, 134, 208, 184, 208, 187, 208, 184, 8, 0, 0, 0, 0, 0, 0, 11, 136, 208, 177, 208, 184, 208, 187, 208, 176, 72, 0, 0, 0, 0, 15, 4, 95, 48, 77, 52, 69, 37, 55, 37, 6, 39, 50, 37, 0, 0, 0, 15, 4, 95, 48, 77, 50, 63, 37, 55, 37, 6, 39, 50, 37, 0, 0, 16, 4, 95, 48, 77, 51, 63, 6, 37, 55, 37, 35, 34, 70, 136, 0, 0, 7, 132, 208, 187, 208, 184, 72, 0, 14, 4, 95, 48, 77, 49, 6, 37, 55, 57, 35, 70, 37, 0, 0, 11, 136, 208, 177, 208, 184, 208, 187, 208, 190, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 208, 184, 208, 188, 208, 176, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 29, 3, 95, 194, 173, 48, 14, 16, 6, 37, 82, 14, 16, 36, 63, 36, 50, 120, 15, 115, 6, 44, 47, 6, 37, 74, 49, 120, 0, 0, 0, 24, 3, 95, 194, 171, 6, 39, 47, 82, 39, 51, 36, 50, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 0, 0, 9, 134, 208, 177, 208, 184, 208, 187, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 208, 189, 208, 181, 209, 129, 208, 181, 76, 0, 25, 3, 95, 194, 187, 86, 6, 35, 47, 82, 39, 51, 36, 50, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 0, 11, 136, 208, 189, 208, 181, 209, 129, 208, 184, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 2, 195, 151, 48, 6, 39, 0, 0, 0, 0, 20, 2, 197, 130, 55, 13, 15, 87, 120, 15, 115, 6, 44, 47, 6, 37, 115, 39, 63, 0, 0, 0, 0, 0, 0, 8, 2, 194, 167, 70, 36, 55, 0, 0, 12, 2, 194, 164, 82, 6, 35, 55, 40, 47, 120, 0, 0, 0, 0, 0, 0, 0, 19, 2, 194, 174, 51, 6, 36, 79, 37, 87, 47, 14, 16, 35, 115, 136, 57, 120, 0, 0, 0, 0, 0, 0, 0, 16, 2, 194, 168, 48, 14, 16, 6, 37, 57, 36, 79, 55, 120, 87, 0, 0, 13, 138, 208, 184, 208, 188, 208, 176, 209, 130, 208, 181, 76, 21, 2, 194, 169, 6, 35, 82, 47, 39, 51, 87, 49, 120, 15, 48, 14, 16, 35, 82, 120, 0, 0, 9, 2, 194, 182, 74, 55, 36, 50, 0, 0, 7, 2, 194, 183, 48, 39, 0, 0, 0, 12, 2, 194, 181, 63, 6, 37, 49, 14, 16, 39, 0, 0, 0, 0, 12, 2, 194, 176, 87, 47, 6, 36, 48, 36, 50, 0, 0, 0, 0, 15, 2, 195, 183, 48, 39, 70, 6, 36, 61, 4, 36, 50, 39, 0, 0, 0, 0, 0, 0, 12, 2, 194, 184, 87, 36, 70, 6, 37, 55, 120, 0, 0, 0, 9, 134, 209, 136, 209, 130, 208, 190, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 2, 203, 152, 69, 14, 16, 6, 36, 82, 37, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 209, 135, 74, 13, 0, 0, 7, 2, 209, 134, 115, 13, 0, 0, 7, 2, 209, 133, 99, 13, 0, 0, 7, 2, 209, 132, 81, 13, 0, 0, 0, 7, 2, 209, 130, 47, 13, 0, 0, 7, 2, 209, 129, 87, 13, 0, 0, 7, 2, 209, 128, 51, 13, 0, 0, 0, 0, 0, 0, 0, 8, 132, 208, 183, 208, 176, 72, 28, 0, 0, 7, 2, 209, 136, 89, 13, 0, 0, 0, 14, 2, 95, 34, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 7, 2, 209, 149, 116, 13, 0, 0, 0, 15, 2, 95, 39, 6, 35, 48, 39, 87, 47, 14, 16, 39, 81, 0, 7, 2, 209, 147, 75, 13, 0, 0, 18, 2, 95, 38, 47, 6, 44, 79, 6, 39, 82, 87, 49, 39, 15, 6, 37, 0, 0, 0, 11, 2, 95, 36, 70, 6, 39, 55, 120, 51, 0, 0, 7, 2, 209, 159, 73, 13, 0, 0, 15, 2, 95, 42, 116, 82, 6, 36, 86, 70, 37, 74, 49, 120, 0, 15, 2, 95, 42, 116, 82, 6, 36, 86, 70, 37, 74, 49, 13, 0, 0, 25, 2, 95, 41, 86, 6, 35, 47, 82, 39, 51, 36, 50, 120, 15, 86, 6, 35, 79, 14, 16, 35, 70, 120, 0, 0, 24, 2, 95, 40, 6, 39, 47, 82, 39, 51, 36, 50, 120, 15, 86, 6, 35, 79, 14, 16, 35, 70, 120, 0, 7, 2, 209, 156, 139, 13, 0, 0, 0, 11, 2, 95, 46, 47, 6, 39, 74, 49, 120, 0, 7, 2, 209, 154, 65, 13, 0, 0, 14, 2, 95, 45, 115, 6, 44, 47, 6, 37, 74, 49, 120, 0, 11, 2, 95, 45, 63, 6, 37, 50, 40, 87, 0, 7, 2, 209, 153, 61, 13, 0, 0, 13, 2, 95, 44, 86, 6, 35, 48, 37, 51, 49, 120, 0, 7, 2, 209, 152, 57, 134, 0, 0, 9, 2, 95, 51, 47, 51, 6, 37, 0, 0, 10, 2, 95, 50, 70, 6, 82, 6, 35, 0, 0, 10, 2, 95, 49, 6, 36, 70, 36, 50, 0, 0, 10, 2, 95, 48, 50, 6, 40, 55, 120, 0, 0, 11, 2, 95, 55, 87, 6, 107, 70, 40, 63, 0, 0, 10, 2, 95, 54, 89, 6, 107, 87, 47, 0, 0, 9, 2, 95, 53, 48, 6, 107, 47, 0, 0, 12, 2, 95, 52, 74, 6, 107, 47, 136, 16, 136, 0, 0, 19, 2, 95, 59, 47, 6, 39, 74, 49, 120, 86, 4, 35, 48, 37, 51, 49, 35, 0, 7, 2, 208, 183, 86, 13, 0, 0, 7, 2, 208, 182, 88, 13, 0, 0, 7, 2, 208, 181, 107, 0, 14, 6, 130, 208, 181, 72, 28, 11, 2, 95, 57, 70, 6, 107, 82, 107, 47, 0, 0, 10, 2, 95, 56, 6, 39, 87, 40, 63, 0, 7, 2, 208, 180, 70, 13, 0, 0, 15, 2, 95, 63, 48, 34, 6, 35, 89, 35, 55, 50, 37, 49, 0, 7, 2, 208, 179, 79, 13, 0, 0, 18, 2, 95, 62, 48, 39, 79, 6, 39, 55, 36, 63, 39, 15, 6, 39, 70, 0, 7, 2, 208, 178, 82, 13, 0, 0, 13, 2, 95, 61, 6, 36, 70, 50, 120, 49, 82, 39, 0, 13, 2, 95, 61, 6, 36, 70, 50, 120, 49, 82, 39, 0, 7, 2, 208, 177, 69, 13, 0, 0, 7, 2, 208, 176, 35, 0, 14, 8, 2, 208, 176, 35, 0, 72, 8, 16, 2, 95, 60, 48, 6, 39, 63, 35, 55, 39, 15, 6, 39, 70, 0, 0, 7, 2, 208, 191, 48, 13, 0, 0, 0, 7, 2, 208, 189, 50, 13, 0, 0, 13, 138, 208, 189, 208, 181, 208, 188, 208, 176, 209, 136, 76, 18, 2, 95, 64, 47, 6, 44, 79, 6, 39, 82, 87, 49, 39, 15, 6, 35, 0, 7, 2, 208, 188, 63, 13, 0, 0, 7, 2, 208, 187, 55, 13, 0, 0, 7, 2, 208, 186, 49, 13, 0, 0, 0, 8, 2, 208, 184, 37, 10, 0, 14, 9, 2, 208, 184, 37, 9, 0, 72, 8, 13, 2, 92, 92, 69, 6, 107, 49, 87, 55, 107, 89, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 25, 4, 95, 226, 128, 154, 6, 39, 47, 82, 39, 51, 36, 50, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 26, 4, 95, 226, 128, 153, 6, 36, 70, 37, 50, 36, 74, 36, 50, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 25, 4, 95, 226, 128, 152, 6, 39, 47, 82, 39, 51, 36, 50, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 0, 25, 4, 95, 226, 128, 158, 86, 35, 47, 82, 39, 51, 36, 50, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 32, 2, 95, 91, 6, 39, 47, 82, 39, 51, 36, 50, 120, 15, 87, 51, 6, 36, 70, 50, 120, 15, 86, 6, 35, 79, 14, 16, 35, 70, 120, 0, 26, 4, 95, 226, 128, 157, 86, 6, 35, 47, 82, 39, 51, 36, 50, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 25, 4, 95, 226, 128, 156, 6, 39, 47, 82, 39, 51, 36, 50, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 15, 4, 95, 226, 128, 147, 107, 50, 15, 115, 6, 44, 47, 120, 0, 0, 0, 10, 2, 95, 95, 115, 6, 44, 47, 120, 0, 0, 0, 33, 2, 95, 93, 86, 6, 35, 47, 82, 39, 51, 36, 50, 120, 15, 87, 51, 6, 36, 70, 50, 120, 15, 86, 6, 35, 79, 14, 16, 35, 70, 120, 0, 0, 0, 0, 15, 4, 95, 226, 128, 148, 107, 63, 15, 115, 6, 44, 47, 120, 0, 0, 13, 138, 208, 189, 208, 181, 209, 129, 208, 188, 208, 181, 76, 9, 134, 209, 129, 208, 188, 208, 181, 72, 0, 13, 2, 95, 96, 79, 14, 16, 6, 35, 82, 37, 87, 0, 0, 15, 140, 208, 189, 208, 181, 208, 188, 208, 176, 208, 188, 208, 181, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 208, 189, 208, 181, 208, 188, 208, 176, 208, 188, 76, 0, 0, 0, 0, 0, 25, 4, 95, 226, 128, 185, 6, 39, 47, 82, 39, 51, 36, 50, 15, 50, 6, 35, 82, 39, 70, 50, 136, 49, 0, 0, 0, 0, 0, 32, 2, 95, 123, 6, 39, 47, 82, 39, 51, 36, 50, 120, 15, 79, 6, 39, 55, 36, 63, 120, 15, 86, 6, 35, 79, 14, 16, 35, 70, 120, 0, 0, 0, 0, 0, 0, 0, 34, 2, 95, 125, 86, 6, 35, 47, 82, 39, 51, 36, 50, 120, 15, 79, 6, 39, 55, 36, 63, 35, 120, 15, 86, 6, 35, 79, 14, 16, 35, 70, 120, 0, 0, 21, 2, 95, 124, 82, 36, 51, 47, 37, 49, 35, 55, 50, 120, 15, 115, 6, 44, 47, 120, 0, 0, 7, 132, 209, 129, 208, 181, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 209, 129, 208, 184, 72, 0, 0, 10, 4, 209, 129, 208, 190, 87, 10, 0, 28, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 208, 177, 208, 181, 208, 176, 72, 0, 0, 0, 0, 17, 5, 95, 49, 77, 65, 51, 63, 6, 37, 55, 37, 35, 34, 70, 35, 0, 0, 15, 5, 95, 49, 77, 65, 50, 63, 37, 55, 37, 6, 39, 50, 0, 0, 15, 5, 95, 49, 77, 65, 49, 6, 37, 55, 57, 35, 70, 120, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 132, 208, 178, 208, 190, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 97, 0, 0, 0, 48, 4, 0, 0, 98, 0, 0, 0, 49, 4, 0, 0, 99, 0, 0, 0, 70, 4, 0, 0, 7, 1, 0, 0, 91, 4, 0, 0, 13, 1, 0, 0, 71, 4, 0, 0, 100, 0, 126, 1, 95, 4, 0, 0, 100, 0, 122, 0, 85, 4, 0, 0, 100, 0, 0, 0, 52, 4, 0, 0, 17, 1, 0, 0, 82, 4, 0, 0, 101, 0, 0, 0, 53, 4, 0, 0, 102, 0, 0, 0, 68, 4, 0, 0, 103, 0, 0, 0, 51, 4, 0, 0, 104, 0, 0, 0, 69, 4, 0, 0, 105, 0, 0, 0, 56, 4, 0, 0, 106, 0, 0, 0, 88, 4, 0, 0, 107, 0, 0, 0, 58, 4, 0, 0, 108, 0, 106, 0, 89, 4, 0, 0, 108, 0, 0, 0, 59, 4, 0, 0, 109, 0, 0, 0, 60, 4, 0, 0, 110, 0, 106, 0, 90, 4, 0, 0, 110, 0, 0, 0, 61, 4, 0, 0, 111, 0, 0, 0, 62, 4, 0, 0, 112, 0, 0, 0, 63, 4, 0, 0, 114, 0, 0, 0, 64, 4, 0, 0, 115, 0, 0, 0, 65, 4, 0, 0, 97, 1, 0, 0, 72, 4, 0, 0, 116, 0, 0, 0, 66, 4, 0, 0, 117, 0, 0, 0, 67, 4, 0, 0, 118, 0, 0, 0, 50, 4, 0, 0, 122, 0, 0, 0, 55, 4, 0, 0, 126, 1, 0, 0, 54, 4, 0, 0, 17, 1, 0, 0, 83, 4, 0, 0, 7, 1, 0, 0, 92, 4, 0, 0, 0, 0, 0, 0, 6, 196, 135, 0, 3, 76, 0, 7, 6, 196, 141, 0, 3, 74, 0, 7, 6, 196, 145, 0, 3, 75, 0, 7, 6, 197, 161, 0, 3, 89, 0, 7, 6, 197, 190, 0, 3, 88, 0, 7, 6, 208, 176, 0, 3, 35, 0, 7, 6, 208, 177, 0, 3, 69, 0, 7, 6, 208, 178, 0, 2, 32, 3, 81, 0, 3, 82, 0, 7, 6, 208, 179, 0, 3, 79, 0, 7, 6, 208, 180, 0, 3, 70, 0, 7, 6, 208, 181, 0, 3, 36, 0, 7, 6, 208, 182, 0, 3, 88, 0, 7, 6, 208, 183, 0, 3, 86, 0, 7, 6, 208, 184, 0, 3, 37, 0, 8, 3, 37, 10, 0, 7, 6, 208, 186, 0, 3, 49, 0, 7, 6, 208, 187, 0, 3, 55, 0, 7, 6, 208, 188, 0, 3, 63, 0, 7, 6, 208, 189, 0, 3, 50, 0, 7, 6, 208, 190, 0, 3, 39, 0, 7, 6, 208, 191, 0, 3, 48, 0, 7, 6, 209, 128, 0, 1, 17, 67, 2, 17, 67, 3, 6, 34, 0, 1, 25, 2, 25, 3, 6, 44, 0, 1, 25, 2, 17, 65, 3, 14, 16, 0, 4, 3, 51, 0, 1, 17, 65, 2, 17, 65, 0, 2, 32, 0, 209, 128, 0, 7, 6, 209, 129, 0, 3, 87, 0, 7, 6, 209, 130, 0, 3, 47, 0, 7, 6, 209, 131, 0, 3, 40, 0, 7, 6, 209, 132, 0, 3, 81, 0, 7, 6, 209, 133, 0, 3, 105, 0, 7, 6, 209, 134, 0, 3, 115, 0, 7, 6, 209, 135, 0, 3, 76, 0, 7, 6, 209, 136, 0, 3, 89, 0, 7, 6, 209, 147, 0, 3, 75, 0, 7, 6, 209, 149, 0, 3, 116, 0, 7, 6, 209, 152, 0, 3, 57, 0, 7, 6, 209, 153, 0, 3, 61, 0, 7, 6, 209, 154, 0, 3, 65, 0, 7, 6, 209, 156, 0, 3, 139, 0, 7, 6, 209, 159, 0, 3, 73, 0, 7, 6, 97, 0, 3, 35, 0, 4, 2, 106, 3, 135, 0, 2, 114, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 115, 0, 7, 6, 100, 0, 3, 70, 0, 197, 190, 3, 73, 0, 122, 3, 116, 0, 7, 6, 101, 0, 120, 101, 1, 32, 46, 3, 2, 36, 49, 87, 36, 0, 4, 1, 106, 3, 36, 0, 2, 106, 0, 3, 107, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 3, 79, 0, 7, 6, 104, 0, 8, 3, 99, 0, 3, 105, 0, 7, 6, 105, 0, 110, 105, 1, 32, 46, 3, 2, 37, 50, 37, 0, 3, 37, 0, 7, 6, 106, 0, 3, 57, 0, 1, 17, 65, 29, 2, 32, 3, 57, 10, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 1, 25, 2, 25, 3, 45, 0, 3, 55, 0, 106, 2, 12, 3, 61, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 106, 3, 65, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 7, 6, 111, 0, 3, 39, 0, 117, 3, 127, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 117, 3, 49, 82, 0, 7, 6, 114, 0, 1, 25, 2, 25, 3, 6, 44, 0, 1, 25, 2, 17, 65, 3, 14, 16, 0, 4, 3, 51, 0, 1, 17, 65, 2, 17, 65, 0, 2, 32, 0, 114, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 7, 6, 117, 0, 3, 40, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 82, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 1, 25, 2, 25, 3, 37, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 206, 0, 177, 3, 6, 35, 55, 81, 120, 0, 172, 3, 6, 35, 55, 81, 120, 15, 47, 6, 39, 50, 39, 87, 0, 183, 3, 6, 36, 47, 120, 0, 174, 3, 6, 36, 47, 120, 15, 47, 6, 39, 50, 39, 87, 0, 181, 3, 6, 36, 48, 87, 136, 55, 39, 50, 0, 173, 3, 6, 36, 48, 87, 136, 55, 39, 50, 15, 47, 6, 39, 50, 39, 87, 0, 191, 3, 6, 39, 63, 136, 49, 14, 16, 39, 50, 10, 0, 184, 3, 47, 99, 6, 36, 47, 120, 0, 186, 3, 49, 6, 35, 48, 120, 0, 190, 3, 49, 87, 6, 37, 0, 189, 3, 50, 6, 37, 0, 187, 3, 55, 6, 35, 63, 70, 120, 0, 185, 3, 57, 6, 39, 47, 120, 0, 175, 3, 57, 6, 39, 47, 120, 15, 47, 6, 39, 50, 39, 87, 0, 188, 3, 63, 6, 37, 0, 178, 3, 69, 6, 36, 47, 120, 0, 180, 3, 70, 6, 36, 55, 47, 120, 0, 179, 3, 79, 6, 35, 63, 120, 0, 182, 3, 86, 6, 36, 47, 120, 0, 7, 6, 207, 0, 137, 3, 6, 39, 63, 36, 79, 120, 0, 142, 3, 6, 39, 63, 36, 79, 120, 15, 47, 6, 39, 50, 39, 87, 0, 140, 3, 6, 39, 63, 136, 49, 14, 16, 39, 50, 15, 47, 6, 39, 50, 39, 87, 0, 132, 3, 47, 6, 35, 40, 0, 128, 3, 48, 6, 37, 0, 136, 3, 48, 87, 6, 37, 0, 129, 3, 51, 6, 39, 0, 141, 3, 79, 44, 74, 49, 37, 15, 6, 37, 48, 87, 136, 55, 39, 50, 15, 47, 6, 39, 50, 39, 87, 0, 133, 3, 79, 44, 74, 49, 37, 23, 6, 37, 48, 87, 136, 55, 39, 50, 0, 130, 3, 79, 44, 74, 49, 39, 23, 86, 6, 35, 82, 44, 89, 50, 39, 23, 87, 6, 37, 79, 63, 120, 0, 134, 3, 81, 6, 37, 0, 131, 3, 87, 6, 37, 79, 63, 120, 0, 135, 3, 99, 6, 37, 0, 7, 6, 0, 4, 42, 1, 42, 2, 42, 3, 0, 4, 42, 42, 3, 0, 4, 45, 1, 45, 45, 3, 0, 4, 46, 1, 46, 3, 0, 4, 61, 1, 61, 2, 61, 3, 0, 61, 2, 61, 61, 3, 0, 61, 3, 6, 36, 70, 50, 120, 49, 82, 39, 0, 46, 2, 46, 3, 9, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 4, 195, 159, 3, 21, 100, 101, 0, 195, 164, 0, 195, 182, 0, 195, 188, 0, 4, 42, 1, 42, 42, 2, 32, 3, 24, 0, 61, 1, 61, 61, 2, 32, 0, 46, 3, 47, 39, 74, 49, 120, 0, 45, 8, 32, 2, 32, 15, 3, 63, 37, 50, 40, 87, 0, 36, 3, 70, 6, 39, 55, 120, 51, 0, 42, 3, 116, 82, 6, 36, 86, 70, 37, 74, 49, 120, 0, 195, 173, 3, 119, 0, 195, 169, 3, 121, 0, 195, 161, 3, 122, 0, 195, 179, 3, 123, 0, 195, 186, 3, 124, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts36 = FileInMemory_createWithData (4945, reinterpret_cast (&espeakdata_dicts36_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/mk_dict", L"mk"); Collection_addItem (me.peek(), espeakdata_dicts36.transfer()); static unsigned char espeakdata_dicts37_data[3020] = { 0, 4, 0, 0, 8, 8, 0, 0, 0, 0, 0, 0, 0, 6, 65, 4, 112, 57, 0, 0, 0, 0, 0, 6, 65, 8, 69, 110, 0, 0, 0, 0, 0, 6, 65, 12, 87, 110, 0, 0, 0, 0, 0, 6, 65, 16, 70, 110, 0, 0, 0, 0, 0, 5, 65, 20, 110, 0, 0, 0, 0, 0, 6, 65, 24, 114, 81, 0, 0, 0, 0, 0, 6, 65, 28, 73, 110, 0, 0, 0, 0, 0, 6, 65, 32, 112, 74, 0, 0, 0, 0, 0, 6, 65, 36, 116, 57, 0, 0, 14, 1, 37, 95, 35, 47, 13, 63, 116, 50, 13, 63, 0, 27, 0, 14, 1, 38, 87, 35, 63, 40, 78, 78, 35, 57, 13, 63, 0, 0, 0, 7, 65, 40, 73, 112, 57, 0, 0, 0, 13, 1, 42, 35, 87, 47, 13, 34, 37, 87, 49, 0, 27, 0, 12, 1, 43, 49, 121, 138, 138, 13, 64, 13, 63, 0, 0, 7, 65, 44, 49, 112, 57, 0, 0, 0, 0, 0, 6, 65, 48, 114, 55, 0, 0, 0, 0, 0, 6, 65, 52, 114, 63, 0, 0, 0, 0, 0, 6, 65, 56, 114, 50, 0, 0, 0, 0, 0, 5, 65, 60, 117, 0, 0, 9, 1, 61, 87, 35, 63, 13, 63, 0, 0, 0, 0, 6, 65, 64, 48, 110, 0, 0, 0, 0, 0, 7, 65, 68, 49, 57, 121, 0, 0, 0, 0, 0, 6, 65, 72, 116, 51, 0, 0, 0, 0, 0, 6, 65, 76, 114, 87, 0, 0, 0, 0, 0, 6, 65, 80, 47, 110, 0, 0, 0, 0, 0, 6, 65, 84, 57, 121, 0, 0, 0, 0, 0, 6, 65, 88, 82, 110, 0, 0, 0, 0, 0, 11, 65, 92, 70, 107, 69, 107, 55, 57, 121, 0, 0, 0, 0, 0, 7, 65, 96, 114, 49, 87, 0, 0, 0, 0, 0, 7, 65, 100, 58, 116, 57, 0, 0, 0, 0, 0, 7, 65, 104, 86, 114, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 4, 95, 4, 16, 20, 10, 70, 6, 35, 95, 116, 63, 95, 13, 63, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 6, 224, 180, 179, 224, 181, 142, 10, 6, 147, 62, 0, 0, 0, 0, 0, 13, 6, 224, 180, 177, 224, 181, 142, 10, 6, 147, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 6, 224, 180, 149, 224, 181, 142, 10, 37, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 6, 224, 180, 163, 224, 181, 142, 10, 6, 147, 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 51, 88, 63, 6, 40, 48, 48, 35, 47, 0, 0, 10, 3, 95, 48, 67, 50, 6, 121, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 49, 57, 48, 6, 35, 47, 47, 39, 63, 48, 35, 47, 40, 0, 0, 16, 3, 95, 49, 56, 48, 6, 35, 47, 37, 50, 112, 138, 138, 147, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 49, 49, 48, 6, 35, 47, 37, 50, 39, 50, 50, 147, 0, 0, 12, 3, 95, 49, 48, 48, 6, 35, 47, 47, 147, 0, 0, 0, 16, 3, 95, 49, 50, 48, 6, 35, 50, 47, 34, 35, 64, 138, 147, 0, 0, 16, 3, 95, 49, 53, 48, 6, 35, 47, 37, 50, 35, 65, 78, 147, 0, 0, 0, 15, 3, 95, 49, 55, 48, 6, 35, 47, 37, 50, 112, 52, 147, 0, 0, 15, 3, 95, 49, 54, 48, 6, 35, 47, 37, 50, 35, 52, 147, 0, 0, 0, 13, 3, 95, 55, 88, 6, 36, 68, 40, 48, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 88, 48, 6, 35, 47, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 50, 88, 6, 37, 34, 40, 48, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 52, 88, 50, 6, 116, 55, 48, 48, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 53, 88, 6, 35, 50, 48, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 54, 88, 6, 35, 52, 40, 48, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 56, 88, 6, 36, 64, 48, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 57, 88, 47, 6, 39, 64, 64, 121, 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 224, 181, 142, 142, 37, 62, 35, 142, 35, 34, 35, 63, 0, 0, 0, 8, 3, 224, 181, 140, 146, 133, 0, 0, 17, 3, 224, 181, 141, 142, 35, 50, 70, 34, 35, 49, 116, 34, 13, 63, 0, 0, 8, 3, 224, 181, 138, 18, 39, 0, 9, 3, 224, 180, 130, 6, 148, 63, 0, 0, 9, 3, 224, 181, 139, 146, 117, 12, 0, 14, 3, 224, 180, 131, 82, 37, 87, 35, 34, 79, 13, 63, 0, 0, 8, 3, 224, 181, 136, 146, 132, 0, 0, 0, 8, 3, 224, 181, 134, 18, 36, 0, 0, 9, 3, 224, 181, 135, 146, 112, 12, 0, 0, 10, 3, 224, 181, 132, 146, 34, 110, 12, 0, 0, 0, 9, 3, 224, 181, 130, 146, 121, 12, 0, 0, 9, 3, 224, 181, 131, 18, 34, 37, 0, 0, 9, 3, 224, 181, 128, 146, 110, 12, 0, 0, 8, 3, 224, 181, 129, 18, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 48, 77, 50, 55, 6, 35, 49, 91, 35, 63, 0, 0, 12, 4, 95, 48, 77, 51, 49, 6, 117, 138, 37, 0, 0, 0, 14, 4, 95, 48, 77, 49, 6, 116, 57, 37, 51, 35, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 3, 224, 181, 151, 146, 133, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 224, 180, 190, 146, 116, 12, 0, 0, 8, 3, 224, 180, 191, 18, 37, 0, 0, 0, 14, 3, 224, 180, 189, 35, 82, 35, 79, 34, 35, 105, 35, 0, 0, 0, 0, 0, 0, 10, 3, 224, 181, 190, 10, 6, 147, 62, 0, 0, 9, 3, 224, 181, 191, 10, 37, 49, 0, 0, 10, 3, 224, 181, 188, 10, 6, 147, 51, 0, 0, 9, 3, 224, 181, 189, 10, 37, 55, 0, 0, 10, 3, 224, 181, 186, 10, 6, 147, 64, 0, 0, 9, 3, 224, 181, 187, 10, 37, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 6, 224, 180, 178, 224, 181, 142, 10, 37, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 2, 95, 33, 116, 95, 78, 13, 34, 57, 35, 78, 37, 105, 50, 13, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 2, 95, 46, 69, 37, 50, 70, 40, 0, 0, 0, 12, 2, 95, 44, 35, 66, 49, 40, 95, 13, 63, 0, 0, 11, 2, 95, 51, 63, 6, 40, 50, 50, 147, 0, 0, 11, 2, 95, 50, 34, 6, 35, 64, 138, 147, 0, 0, 10, 2, 95, 49, 6, 39, 50, 50, 147, 0, 0, 12, 2, 95, 48, 48, 6, 121, 77, 57, 13, 63, 0, 0, 9, 2, 95, 55, 6, 112, 68, 147, 0, 0, 9, 2, 95, 54, 6, 35, 52, 147, 0, 0, 10, 2, 95, 53, 6, 35, 65, 78, 147, 0, 0, 10, 2, 95, 52, 50, 6, 116, 55, 147, 0, 0, 11, 2, 95, 59, 34, 117, 137, 37, 50, 37, 0, 0, 0, 12, 2, 95, 57, 6, 39, 50, 48, 35, 47, 147, 0, 0, 10, 2, 95, 56, 6, 36, 138, 138, 147, 0, 0, 16, 2, 95, 63, 78, 117, 70, 57, 13, 78, 37, 105, 50, 13, 63, 0, 0, 12, 6, 224, 180, 168, 224, 181, 142, 10, 37, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 102, 13, 0, 0, 48, 0, 0, 0, 103, 13, 0, 0, 49, 0, 0, 0, 104, 13, 0, 0, 50, 0, 0, 0, 105, 13, 0, 0, 51, 0, 0, 0, 106, 13, 0, 0, 52, 0, 0, 0, 107, 13, 0, 0, 53, 0, 0, 0, 108, 13, 0, 0, 54, 0, 0, 0, 109, 13, 0, 0, 55, 0, 0, 0, 110, 13, 0, 0, 56, 0, 0, 0, 111, 13, 0, 0, 57, 0, 0, 0, 71, 13, 62, 13, 75, 13, 0, 0, 70, 13, 62, 13, 74, 13, 0, 0, 70, 13, 87, 13, 76, 13, 0, 0, 0, 0, 0, 0, 6, 1, 22, 0, 2, 17, 66, 3, 49, 0, 3, 49, 35, 0, 7, 6, 1, 23, 0, 2, 17, 66, 3, 144, 0, 3, 144, 35, 0, 7, 6, 1, 24, 0, 2, 17, 66, 3, 79, 0, 3, 79, 35, 0, 7, 6, 1, 25, 0, 2, 17, 66, 3, 145, 0, 3, 145, 35, 0, 7, 6, 1, 26, 0, 2, 17, 66, 3, 66, 0, 3, 66, 35, 0, 7, 6, 1, 27, 0, 2, 17, 66, 3, 78, 0, 3, 78, 35, 0, 7, 6, 1, 28, 0, 2, 17, 66, 3, 142, 0, 3, 142, 35, 0, 7, 6, 1, 29, 0, 2, 17, 66, 3, 77, 0, 3, 77, 35, 0, 7, 6, 1, 30, 0, 2, 17, 66, 3, 143, 0, 3, 143, 35, 0, 7, 6, 1, 31, 0, 2, 17, 66, 3, 65, 0, 3, 65, 35, 0, 7, 6, 1, 32, 0, 2, 17, 66, 3, 138, 0, 3, 138, 35, 0, 7, 6, 1, 33, 0, 2, 17, 66, 3, 140, 0, 3, 140, 35, 0, 7, 6, 1, 34, 0, 2, 17, 66, 3, 139, 0, 3, 139, 35, 0, 7, 6, 1, 35, 0, 2, 17, 66, 3, 141, 0, 3, 141, 35, 0, 7, 6, 1, 36, 0, 2, 17, 66, 3, 64, 0, 3, 64, 35, 0, 7, 6, 1, 37, 0, 2, 17, 66, 3, 47, 0, 3, 47, 35, 0, 7, 6, 1, 38, 0, 2, 17, 66, 3, 136, 0, 3, 136, 35, 0, 7, 6, 1, 39, 0, 2, 17, 66, 3, 70, 0, 3, 70, 35, 0, 7, 6, 1, 40, 0, 2, 17, 66, 3, 137, 0, 3, 137, 35, 0, 7, 6, 1, 41, 0, 2, 17, 66, 3, 50, 0, 3, 50, 35, 0, 7, 6, 1, 43, 0, 2, 17, 66, 3, 48, 0, 3, 48, 35, 0, 7, 6, 1, 44, 0, 2, 17, 66, 3, 48, 0, 8, 138, 181, 224, 176, 180, 224, 141, 181, 224, 170, 180, 224, 2, 224, 180, 184, 224, 180, 176, 224, 181, 141, 3, 81, 35, 0, 3, 134, 35, 0, 7, 6, 1, 45, 0, 2, 17, 66, 3, 69, 0, 3, 69, 35, 0, 7, 6, 1, 46, 0, 2, 17, 66, 3, 135, 0, 3, 135, 35, 0, 7, 6, 1, 47, 0, 2, 17, 66, 3, 63, 0, 3, 63, 35, 0, 7, 6, 1, 48, 0, 2, 17, 66, 3, 57, 0, 3, 57, 35, 0, 7, 6, 1, 49, 0, 2, 17, 66, 3, 34, 0, 3, 34, 35, 0, 7, 6, 1, 50, 0, 2, 17, 66, 3, 52, 0, 3, 52, 35, 0, 224, 181, 141, 224, 180, 177, 3, 138, 138, 0, 1, 141, 181, 224, 168, 180, 224, 3, 149, 0, 7, 6, 1, 51, 0, 2, 17, 66, 3, 55, 0, 3, 55, 35, 0, 7, 6, 1, 52, 0, 2, 17, 66, 3, 62, 0, 3, 62, 35, 0, 7, 6, 1, 53, 0, 2, 17, 66, 3, 68, 0, 3, 68, 35, 0, 7, 6, 1, 54, 0, 2, 17, 66, 3, 82, 0, 3, 82, 35, 0, 7, 6, 1, 55, 0, 2, 17, 66, 3, 95, 0, 3, 95, 35, 0, 7, 6, 1, 56, 0, 2, 17, 66, 3, 91, 0, 3, 91, 35, 0, 7, 6, 1, 57, 0, 2, 17, 66, 3, 87, 0, 3, 87, 35, 0, 7, 6, 1, 58, 0, 2, 17, 66, 3, 105, 0, 3, 105, 35, 0, 7, 6, 1, 123, 0, 3, 64, 0, 7, 6, 1, 124, 0, 3, 50, 0, 7, 6, 1, 125, 0, 3, 34, 0, 7, 6, 1, 126, 0, 3, 55, 0, 7, 6, 1, 127, 0, 3, 62, 0, 7, 6, 1, 128, 0, 3, 49, 0, 7, 6, 224, 164, 0, 3, 21, 104, 105, 0, 7, 6, 224, 165, 0, 3, 21, 104, 105, 0, 7, 6, 224, 180, 0, 189, 3, 0, 133, 3, 35, 0, 142, 3, 36, 0, 4, 135, 3, 37, 0, 191, 0, 142, 8, 3, 38, 36, 0, 143, 8, 3, 38, 112, 0, 146, 3, 39, 0, 137, 3, 40, 0, 139, 3, 51, 147, 0, 130, 3, 63, 0, 131, 3, 105, 0, 136, 3, 110, 0, 191, 2, 224, 180, 178, 224, 181, 141, 25, 3, 111, 0, 143, 3, 112, 0, 4, 134, 3, 116, 0, 190, 0, 147, 3, 117, 0, 138, 3, 121, 0, 144, 3, 132, 0, 148, 3, 133, 0, 7, 6, 224, 181, 0, 4, 141, 3, 0, 4, 141, 224, 181, 141, 3, 0, 142, 3, 0, 134, 3, 36, 0, 138, 3, 39, 0, 129, 3, 40, 0, 131, 3, 44, 0, 132, 3, 44, 12, 0, 160, 3, 51, 147, 12, 0, 161, 3, 55, 147, 12, 0, 128, 3, 110, 0, 135, 3, 112, 0, 139, 3, 117, 0, 130, 3, 121, 0, 136, 3, 132, 0, 4, 140, 3, 133, 0, 151, 0, 141, 2, 32, 3, 147, 0, 7, 6, 0, 36, 3, 70, 117, 62, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts37 = FileInMemory_createWithData (3019, reinterpret_cast (&espeakdata_dicts37_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ml_dict", L"ml"); Collection_addItem (me.peek(), espeakdata_dicts37.transfer()); static unsigned char espeakdata_dicts38_data[4388] = { 0, 4, 0, 0, 189, 14, 0, 0, 0, 16, 70, 69, 81, 4, 36, 83, 64, 6, 13, 40, 70, 37, 12, 63, 0, 0, 0, 0, 0, 5, 65, 4, 35, 0, 0, 0, 0, 0, 10, 5, 7, 196, 167, 1, 24, 35, 89, 0, 6, 65, 8, 69, 13, 0, 0, 0, 0, 0, 6, 65, 12, 49, 35, 0, 0, 12, 5, 4, 9, 196, 161, 1, 70, 37, 73, 35, 0, 0, 0, 0, 7, 65, 16, 70, 36, 36, 0, 0, 0, 10, 67, 44, 145, 128, 97, 37, 12, 81, 0, 0, 0, 5, 65, 20, 36, 0, 0, 0, 0, 0, 8, 65, 24, 36, 81, 81, 36, 0, 0, 0, 0, 0, 6, 65, 28, 79, 124, 0, 0, 0, 10, 67, 92, 20, 84, 40, 35, 12, 47, 0, 0, 0, 8, 65, 32, 35, 49, 49, 35, 0, 0, 0, 0, 0, 19, 9, 20, 1, 7, 196, 167, 13, 9, 12, 24, 47, 35, 12, 63, 37, 55, 89, 0, 5, 65, 36, 37, 0, 0, 0, 0, 14, 7, 16, 15, 196, 161, 196, 161, 9, 39, 73, 37, 12, 0, 0, 17, 8, 20, 16, 15, 196, 161, 196, 161, 9, 47, 48, 39, 73, 37, 12, 0, 5, 65, 40, 124, 0, 0, 0, 11, 1, 42, 87, 47, 37, 55, 12, 35, 0, 27, 0, 10, 67, 92, 20, 129, 40, 35, 34, 35, 0, 10, 67, 92, 20, 129, 40, 35, 34, 35, 0, 16, 7, 20, 9, 5, 7, 196, 167, 9, 47, 37, 12, 110, 12, 0, 72, 9, 1, 43, 48, 55, 40, 87, 0, 27, 0, 7, 65, 44, 49, 6, 13, 0, 0, 0, 0, 16, 7, 20, 9, 5, 7, 196, 167, 21, 47, 37, 12, 40, 12, 0, 72, 9, 1, 47, 49, 116, 47, 12, 35, 0, 0, 8, 65, 48, 36, 55, 55, 36, 0, 0, 0, 0, 0, 8, 65, 52, 36, 63, 63, 36, 0, 0, 0, 0, 0, 8, 65, 56, 36, 50, 50, 36, 0, 0, 0, 0, 0, 5, 65, 60, 39, 0, 0, 12, 1, 61, 37, 12, 49, 58, 13, 55, 86, 0, 27, 0, 0, 0, 7, 1, 64, 10, 35, 47, 0, 6, 65, 64, 48, 36, 0, 0, 0, 0, 0, 6, 65, 68, 6, 13, 0, 0, 0, 0, 0, 8, 65, 72, 36, 34, 34, 36, 0, 0, 0, 0, 0, 14, 69, 44, 145, 78, 21, 64, 49, 37, 12, 50, 36, 47, 0, 8, 65, 76, 36, 87, 87, 36, 0, 0, 0, 0, 0, 6, 65, 80, 47, 36, 0, 0, 0, 0, 12, 67, 36, 229, 9, 37, 50, 47, 37, 12, 0, 72, 0, 5, 65, 84, 40, 0, 5, 65, 84, 40, 0, 0, 0, 0, 17, 6, 22, 9, 196, 139, 9, 14, 82, 37, 12, 89, 13, 37, 12, 50, 0, 0, 6, 65, 88, 82, 36, 0, 0, 0, 0, 0, 8, 1, 92, 49, 36, 50, 39, 0, 7, 65, 92, 40, 6, 13, 0, 0, 17, 70, 52, 147, 134, 48, 242, 192, 63, 37, 50, 81, 55, 39, 74, 36, 0, 0, 0, 0, 6, 132, 95, 49, 77, 49, 8, 65, 96, 36, 89, 89, 36, 0, 0, 0, 0, 0, 5, 65, 100, 109, 0, 0, 0, 0, 0, 8, 65, 104, 47, 87, 36, 36, 0, 0, 0, 15, 7, 1, 7, 196, 167, 13, 5, 12, 35, 12, 63, 36, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 53, 84, 128, 63, 40, 12, 34, 0, 0, 11, 68, 68, 16, 133, 48, 35, 69, 36, 55, 0, 12, 68, 68, 16, 133, 48, 35, 12, 69, 36, 55, 0, 0, 0, 0, 9, 1, 126, 47, 37, 55, 70, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 70, 52, 147, 139, 20, 162, 129, 63, 37, 50, 74, 112, 12, 35, 0, 15, 70, 52, 147, 139, 20, 162, 129, 63, 37, 50, 97, 112, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 50, 77, 49, 36, 55, 81, 112, 40, 50, 0, 0, 0, 13, 4, 95, 50, 77, 51, 86, 6, 13, 118, 79, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 5, 5, 196, 139, 196, 139, 101, 116, 83, 101, 116, 114, 97, 0, 29, 0, 0, 0, 0, 0, 0, 15, 5, 1, 196, 167, 14, 1, 35, 105, 6, 13, 50, 35, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 70, 64, 84, 141, 21, 166, 128, 48, 36, 34, 63, 36, 47, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 51, 77, 51, 47, 55, 36, 47, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 32, 146, 129, 37, 12, 35, 0, 72, 0, 0, 0, 0, 0, 0, 16, 8, 7, 196, 167, 1, 13, 9, 12, 20, 35, 63, 37, 55, 47, 0, 0, 10, 67, 8, 82, 142, 69, 112, 12, 50, 0, 10, 67, 8, 82, 142, 69, 112, 12, 50, 0, 0, 0, 9, 67, 16, 19, 128, 70, 35, 50, 0, 0, 0, 0, 0, 10, 67, 25, 84, 64, 81, 40, 6, 13, 0, 0, 0, 0, 0, 0, 15, 5, 9, 197, 188, 4, 1, 37, 12, 86, 6, 13, 70, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 66, 12, 208, 116, 83, 101, 110, 116, 105, 109, 39, 101, 116, 114, 105, 0, 29, 0, 0, 0, 0, 0, 0, 13, 68, 16, 20, 130, 4, 70, 35, 34, 12, 69, 35, 0, 0, 0, 0, 19, 8, 6, 9, 12, 45, 13, 9, 10, 1, 81, 37, 12, 45, 63, 37, 12, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 7, 7, 196, 167, 1, 13, 5, 12, 35, 12, 63, 36, 55, 0, 15, 7, 7, 196, 167, 1, 13, 5, 12, 35, 12, 63, 36, 55, 0, 14, 7, 7, 196, 167, 1, 13, 5, 12, 35, 63, 36, 55, 0, 0, 0, 0, 0, 10, 3, 226, 130, 172, 36, 58, 34, 39, 0, 0, 0, 0, 0, 0, 0, 0, 8, 66, 24, 144, 81, 37, 12, 0, 0, 10, 67, 52, 244, 148, 63, 39, 34, 47, 0, 0, 0, 0, 0, 9, 67, 16, 18, 192, 70, 35, 49, 0, 0, 13, 68, 52, 147, 132, 84, 63, 37, 50, 70, 40, 12, 0, 0, 0, 0, 0, 13, 68, 76, 20, 133, 80, 87, 35, 12, 34, 36, 47, 0, 0, 0, 0, 0, 0, 14, 4, 95, 53, 77, 51, 105, 6, 13, 35, 63, 36, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 8, 10, 1, 7, 196, 167, 13, 5, 12, 37, 35, 12, 63, 36, 55, 0, 0, 0, 0, 9, 67, 40, 85, 192, 124, 40, 12, 0, 0, 9, 67, 40, 82, 203, 124, 74, 36, 0, 0, 0, 0, 0, 0, 10, 67, 16, 21, 206, 70, 116, 12, 50, 0, 0, 0, 17, 8, 20, 1, 7, 196, 167, 8, 15, 13, 47, 35, 105, 39, 63, 0, 72, 0, 10, 67, 16, 21, 203, 70, 116, 12, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 52, 133, 88, 63, 40, 12, 89, 0, 9, 67, 52, 133, 88, 63, 40, 89, 0, 14, 3, 95, 51, 88, 47, 55, 6, 13, 47, 37, 12, 50, 0, 0, 10, 3, 95, 48, 67, 63, 37, 12, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 49, 67, 63, 37, 12, 116, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 49, 57, 47, 87, 36, 47, 35, 89, 36, 0, 0, 14, 3, 95, 49, 56, 47, 63, 37, 50, 47, 35, 89, 36, 0, 0, 0, 0, 16, 7, 20, 1, 7, 196, 167, 14, 1, 47, 35, 50, 35, 12, 0, 72, 0, 0, 0, 0, 13, 3, 95, 49, 49, 105, 6, 13, 70, 35, 89, 36, 0, 0, 11, 3, 95, 49, 48, 35, 6, 13, 34, 35, 0, 0, 13, 3, 95, 49, 51, 47, 55, 36, 47, 35, 89, 36, 0, 0, 11, 3, 95, 49, 50, 47, 50, 35, 89, 36, 0, 0, 16, 3, 95, 49, 53, 105, 6, 13, 63, 37, 87, 47, 35, 89, 36, 0, 0, 14, 3, 95, 49, 52, 36, 34, 69, 35, 47, 35, 89, 36, 0, 0, 13, 3, 95, 49, 55, 87, 69, 35, 47, 35, 89, 36, 0, 0, 12, 3, 95, 49, 54, 87, 37, 47, 35, 89, 36, 0, 0, 0, 13, 3, 95, 55, 88, 87, 6, 13, 69, 112, 12, 50, 0, 0, 0, 0, 17, 7, 20, 1, 7, 196, 167, 8, 1, 47, 35, 105, 6, 13, 35, 0, 72, 0, 0, 0, 15, 8, 2, 226, 128, 153, 8, 5, 11, 11, 69, 36, 74, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 66, 52, 16, 57, 37, 87, 47, 35, 99, 0, 11, 66, 52, 16, 57, 34, 37, 70, 40, 99, 0, 10, 66, 52, 16, 49, 124, 50, 40, 99, 0, 9, 66, 52, 16, 49, 124, 50, 99, 0, 5, 194, 52, 16, 72, 0, 10, 67, 52, 19, 0, 63, 35, 55, 12, 0, 0, 0, 0, 14, 7, 7, 196, 167, 1, 14, 4, 21, 35, 50, 70, 40, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 88, 39, 89, 36, 34, 37, 50, 0, 0, 0, 0, 20, 10, 13, 39, 7, 196, 167, 1, 14, 4, 21, 24, 63, 6, 35, 50, 70, 40, 89, 0, 0, 0, 0, 0, 14, 7, 7, 196, 167, 1, 14, 4, 9, 35, 50, 70, 37, 0, 0, 0, 15, 6, 196, 167, 4, 5, 10, 14, 105, 6, 13, 70, 112, 50, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 52, 88, 36, 34, 69, 110, 12, 50, 0, 0, 0, 0, 0, 0, 0, 0, 17, 66, 44, 112, 107, 105, 108, 111, 103, 114, 39, 97, 109, 58, 105, 0, 29, 0, 10, 67, 45, 83, 12, 78, 40, 55, 12, 0, 9, 67, 45, 83, 12, 63, 37, 50, 0, 11, 67, 45, 83, 12, 70, 35, 34, 69, 35, 0, 15, 3, 95, 53, 88, 105, 6, 13, 35, 63, 87, 37, 12, 50, 0, 0, 13, 8, 17, 9, 5, 7, 196, 167, 5, 4, 124, 70, 0, 0, 0, 0, 0, 0, 18, 8, 20, 9, 5, 7, 196, 167, 5, 11, 47, 37, 12, 35, 49, 36, 0, 72, 0, 0, 13, 3, 95, 54, 88, 87, 37, 47, 12, 37, 12, 50, 0, 0, 0, 0, 0, 9, 67, 68, 21, 20, 35, 47, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 67, 80, 181, 78, 99, 37, 0, 0, 0, 15, 8, 7, 196, 167, 1, 14, 4, 8, 1, 35, 50, 12, 35, 0, 13, 3, 95, 56, 88, 47, 63, 36, 50, 37, 12, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 57, 88, 70, 4, 109, 70, 37, 50, 6, 37, 87, 112, 12, 50, 0, 0, 0, 0, 0, 0, 16, 4, 52, 48, 48, 48, 36, 34, 69, 35, 47, 36, 55, 36, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 52, 147, 142, 63, 37, 50, 12, 0, 10, 67, 52, 147, 142, 105, 36, 63, 63, 0, 10, 67, 52, 147, 142, 81, 36, 57, 50, 0, 10, 67, 52, 147, 142, 63, 37, 12, 50, 0, 0, 0, 0, 12, 68, 37, 52, 201, 72, 37, 87, 12, 37, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 48, 147, 0, 105, 37, 50, 50, 0, 11, 67, 48, 147, 0, 55, 37, 12, 55, 12, 0, 0, 17, 66, 52, 112, 109, 105, 108, 105, 103, 114, 39, 97, 109, 58, 105, 0, 29, 0, 0, 12, 68, 40, 145, 78, 4, 119, 36, 50, 35, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 48, 77, 50, 63, 6, 37, 55, 119, 50, 0, 0, 15, 4, 95, 48, 77, 51, 69, 37, 6, 55, 37, 6, 40, 50, 0, 0, 0, 10, 4, 95, 48, 77, 49, 36, 55, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 9, 13, 9, 14, 7, 196, 167, 1, 10, 18, 63, 37, 12, 50, 110, 34, 0, 19, 9, 13, 9, 14, 7, 196, 167, 1, 10, 18, 63, 37, 12, 50, 110, 12, 34, 0, 0, 0, 0, 0, 0, 0, 0, 16, 66, 44, 208, 107, 105, 108, 111, 109, 39, 101, 116, 114, 105, 0, 29, 0, 0, 0, 0, 0, 0, 0, 17, 8, 20, 1, 7, 196, 167, 11, 15, 13, 47, 35, 49, 39, 63, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 68, 44, 145, 78, 84, 97, 124, 50, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 196, 161, 15, 73, 36, 39, 0, 0, 0, 0, 0, 0, 0, 30, 76, 37, 36, 133, 77, 1, 84, 80, 149, 129, 52, 83, 148, 37, 34, 12, 36, 87, 48, 36, 47, 37, 82, 35, 63, 36, 50, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 66, 52, 192, 109, 105, 108, 105, 108, 39, 105, 116, 114, 105, 0, 29, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 66, 52, 208, 109, 105, 108, 105, 109, 39, 101, 116, 114, 105, 0, 29, 0, 10, 67, 24, 244, 212, 81, 39, 87, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 22, 10, 9, 12, 45, 17, 21, 4, 4, 9, 5, 13, 37, 45, 70, 37, 12, 63, 12, 6, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 69, 34, 66, 34, 37, 12, 48, 0, 0, 8, 66, 80, 16, 47, 35, 12, 0, 0, 15, 70, 52, 133, 77, 36, 86, 0, 40, 63, 40, 63, 37, 89, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 2, 196, 139, 74, 13, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 2, 194, 163, 87, 47, 36, 34, 55, 37, 50, 35, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 37, 49, 133, 48, 37, 87, 81, 36, 55, 0, 0, 0, 0, 0, 0, 8, 2, 196, 167, 105, 6, 13, 0, 0, 0, 0, 0, 0, 0, 7, 2, 196, 161, 73, 36, 0, 0, 0, 0, 0, 18, 70, 52, 147, 130, 5, 36, 129, 63, 37, 50, 69, 35, 12, 34, 35, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 32, 83, 77, 36, 63, 12, 0, 0, 14, 69, 44, 243, 148, 72, 16, 78, 39, 50, 47, 34, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 67, 36, 181, 78, 37, 78, 40, 12, 50, 12, 0, 0, 15, 70, 16, 19, 23, 5, 21, 0, 70, 35, 55, 40, 35, 47, 0, 8, 2, 197, 188, 86, 6, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 68, 36, 229, 15, 52, 37, 12, 50, 47, 39, 63, 0, 72, 0, 15, 69, 52, 17, 23, 5, 32, 63, 35, 70, 40, 12, 35, 34, 0, 15, 69, 52, 17, 23, 5, 32, 63, 35, 70, 40, 35, 12, 34, 0, 0, 0, 0, 0, 0, 0, 0, 17, 70, 24, 194, 77, 44, 145, 78, 81, 55, 37, 50, 49, 37, 12, 63, 0, 17, 70, 24, 194, 77, 44, 145, 78, 81, 55, 37, 63, 49, 37, 50, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 68, 36, 180, 197, 8, 37, 12, 49, 87, 36, 69, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 5, 20, 1, 196, 167, 20, 47, 35, 105, 47, 0, 12, 5, 20, 1, 196, 167, 20, 47, 35, 105, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 2, 95, 35, 105, 35, 87, 105, 0, 0, 11, 2, 95, 34, 49, 58, 39, 108, 47, 87, 0, 0, 10, 67, 80, 213, 82, 47, 63, 40, 34, 0, 9, 2, 95, 33, 48, 40, 50, 47, 0, 0, 9, 67, 33, 83, 65, 40, 63, 35, 0, 11, 67, 33, 83, 65, 40, 12, 63, 35, 0, 72, 0, 11, 2, 95, 39, 35, 78, 78, 36, 50, 47, 0, 0, 6, 2, 95, 38, 40, 0, 0, 11, 4, 95, 52, 77, 51, 36, 34, 69, 35, 0, 17, 2, 95, 37, 48, 34, 39, 78, 36, 50, 47, 40, 35, 55, 37, 12, 0, 0, 13, 2, 95, 36, 70, 39, 55, 55, 35, 34, 40, 12, 0, 0, 0, 0, 14, 2, 95, 41, 48, 35, 34, 36, 50, 47, 36, 86, 37, 0, 0, 14, 2, 95, 40, 48, 35, 34, 36, 50, 47, 36, 86, 37, 0, 0, 0, 9, 2, 95, 46, 48, 40, 50, 47, 0, 0, 11, 2, 95, 45, 105, 35, 106, 81, 13, 50, 0, 0, 9, 2, 95, 44, 49, 39, 63, 35, 0, 0, 12, 2, 95, 51, 47, 55, 37, 12, 36, 47, 35, 0, 0, 9, 2, 95, 50, 50, 112, 12, 50, 0, 0, 10, 67, 48, 82, 142, 55, 112, 50, 12, 0, 11, 2, 95, 49, 114, 12, 105, 6, 13, 70, 0, 0, 10, 2, 95, 48, 86, 6, 36, 16, 39, 0, 0, 10, 2, 95, 55, 87, 36, 69, 35, 12, 0, 0, 11, 2, 95, 54, 87, 37, 12, 47, 12, 35, 0, 0, 12, 2, 95, 53, 105, 6, 13, 35, 63, 87, 35, 0, 0, 9, 2, 95, 52, 36, 34, 69, 35, 0, 0, 16, 2, 95, 59, 87, 36, 63, 106, 49, 6, 39, 108, 55, 13, 50, 0, 0, 11, 2, 95, 58, 49, 39, 108, 55, 13, 50, 0, 0, 14, 2, 95, 57, 70, 109, 70, 37, 50, 6, 35, 87, 35, 0, 0, 13, 2, 95, 56, 47, 63, 37, 12, 50, 37, 12, 35, 0, 0, 15, 2, 95, 63, 63, 37, 87, 47, 39, 102, 87, 37, 57, 35, 0, 0, 10, 2, 95, 62, 35, 49, 69, 35, 34, 0, 0, 0, 9, 2, 95, 60, 37, 86, 6, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 2, 95, 91, 48, 35, 34, 36, 50, 47, 36, 86, 37, 0, 0, 0, 13, 69, 76, 82, 138, 21, 32, 87, 112, 12, 36, 34, 0, 0, 0, 13, 2, 95, 95, 35, 55, 35, 82, 37, 12, 82, 35, 0, 0, 0, 14, 2, 95, 93, 48, 35, 34, 36, 50, 47, 36, 86, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 96, 244, 148, 4, 89, 39, 34, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 14, 2, 95, 123, 35, 55, 49, 40, 35, 12, 55, 47, 39, 0, 0, 0, 0, 0, 0, 10, 67, 8, 148, 211, 69, 37, 87, 12, 0, 0, 15, 2, 95, 125, 55, 39, 48, 12, 40, 35, 12, 55, 47, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 69, 28, 128, 78, 17, 80, 57, 49, 39, 55, 55, 105, 39, 63, 0, 0, 0, 0, 0, 0, 0, 0, 11, 68, 40, 148, 212, 4, 37, 87, 47, 35, 0, 18, 9, 7, 196, 167, 1, 12, 11, 5, 13, 13, 35, 55, 74, 36, 63, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 66, 96, 144, 89, 37, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 37, 52, 193, 37, 87, 12, 35, 0, 0, 0, 0, 0, 0, 0, 12, 68, 8, 244, 212, 4, 69, 39, 87, 47, 35, 0, 0, 0, 9, 67, 33, 85, 193, 40, 12, 35, 0, 9, 67, 33, 85, 193, 40, 35, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 44, 145, 78, 97, 37, 12, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 9, 7, 196, 167, 1, 14, 4, 8, 15, 13, 35, 50, 70, 39, 63, 0, 0, 0, 0, 16, 7, 50, 48, 48, 48, 48, 48, 48, 86, 6, 13, 118, 79, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 51, 48, 48, 48, 47, 55, 36, 47, 12, 0, 0, 0, 0, 0, 0, 11, 5, 7, 196, 167, 1, 12, 35, 55, 12, 0, 0, 0, 0, 0, 6, 196, 139, 0, 3, 74, 13, 0, 97, 3, 74, 13, 35, 0, 101, 3, 74, 13, 36, 0, 105, 3, 74, 13, 37, 0, 119, 3, 74, 13, 40, 6, 13, 0, 7, 6, 196, 161, 0, 3, 73, 0, 111, 3, 73, 39, 0, 7, 6, 196, 167, 0, 3, 105, 0, 117, 3, 105, 12, 40, 12, 0, 116, 3, 105, 47, 0, 7, 6, 197, 188, 0, 3, 86, 6, 13, 0, 4, 97, 3, 86, 35, 0, 103, 196, 167, 0, 101, 3, 86, 36, 0, 105, 101, 3, 86, 37, 12, 36, 0, 7, 6, 97, 0, 3, 35, 0, 97, 3, 35, 12, 0, 120, 3, 35, 89, 0, 117, 3, 116, 0, 7, 6, 98, 0, 3, 69, 0, 101, 3, 69, 6, 13, 0, 98, 3, 69, 12, 0, 114, 3, 69, 34, 6, 13, 0, 105, 101, 3, 69, 37, 6, 13, 0, 105, 3, 69, 37, 12, 0, 7, 6, 99, 0, 3, 78, 0, 7, 6, 100, 0, 100, 3, 70, 12, 0, 3, 70, 36, 0, 7, 6, 101, 0, 3, 36, 0, 119, 3, 118, 0, 117, 3, 118, 12, 0, 7, 6, 102, 0, 3, 81, 0, 102, 3, 81, 12, 0, 111, 3, 81, 39, 0, 7, 6, 103, 0, 196, 167, 3, 12, 0, 3, 79, 0, 103, 3, 79, 12, 0, 105, 3, 79, 37, 12, 0, 101, 3, 79, 124, 0, 7, 6, 104, 0, 3, 12, 0, 7, 6, 105, 0, 101, 3, 37, 12, 0, 3, 106, 0, 117, 3, 106, 40, 0, 7, 6, 106, 0, 106, 3, 37, 12, 0, 97, 3, 37, 35, 0, 111, 3, 37, 39, 0, 3, 119, 0, 101, 3, 124, 0, 7, 6, 107, 0, 97, 3, 49, 35, 0, 4, 3, 49, 36, 0, 101, 0, 105, 3, 49, 37, 12, 0, 105, 101, 3, 49, 37, 12, 36, 0, 117, 3, 49, 40, 12, 0, 111, 3, 78, 39, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 4, 2, 110, 3, 37, 63, 0, 2, 112, 0, 2, 114, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 117, 3, 50, 40, 12, 0, 7, 6, 111, 0, 3, 39, 0, 7, 6, 112, 0, 3, 48, 0, 4, 1, 109, 97, 104, 115, 2, 111, 3, 48, 12, 0, 1, 109, 97, 107, 2, 97, 110, 106, 0, 1, 109, 97, 115, 2, 111, 111, 0, 8, 97, 116, 111, 2, 97, 0, 8, 101, 108, 111, 2, 97, 0, 112, 0, 7, 6, 113, 0, 117, 3, 0, 3, 6, 13, 0, 97, 3, 35, 0, 101, 3, 36, 0, 111, 3, 39, 0, 7, 6, 114, 0, 3, 34, 0, 97, 3, 34, 35, 12, 0, 105, 101, 3, 34, 37, 12, 36, 0, 111, 3, 34, 39, 12, 0, 7, 6, 115, 0, 3, 87, 0, 4, 97, 113, 3, 87, 35, 0, 97, 113, 113, 0, 105, 101, 3, 87, 37, 12, 36, 0, 7, 6, 116, 0, 3, 47, 0, 116, 3, 47, 12, 0, 7, 6, 117, 0, 3, 40, 0, 120, 3, 40, 89, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 40, 0, 7, 6, 120, 0, 3, 89, 36, 0, 105, 101, 3, 89, 112, 12, 0, 7, 6, 121, 0, 3, 109, 0, 121, 3, 109, 12, 0, 105, 3, 115, 0, 195, 182, 3, 125, 0, 7, 6, 122, 0, 3, 47, 87, 36, 0, 104, 1, 25, 3, 88, 0, 7, 6, 0, 196, 139, 3, 74, 13, 0, 197, 188, 3, 86, 6, 13, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts38 = FileInMemory_createWithData (4387, reinterpret_cast (&espeakdata_dicts38_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/mt_dict", L"mt"); Collection_addItem (me.peek(), espeakdata_dicts38.transfer()); static unsigned char espeakdata_dicts39_data[1535] = { 0, 4, 0, 0, 251, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 50, 48, 87, 36, 63, 48, 108, 12, 58, 35, 55, 55, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 29, 3, 95, 51, 48, 87, 36, 63, 48, 108, 12, 58, 35, 55, 55, 37, 39, 63, 63, 35, 19, 47, 55, 35, 49, 47, 55, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 31, 3, 95, 51, 88, 87, 36, 63, 48, 108, 12, 58, 35, 55, 55, 37, 39, 63, 63, 35, 19, 47, 55, 35, 49, 47, 55, 37, 39, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 49, 48, 63, 35, 19, 47, 55, 35, 49, 47, 55, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 49, 88, 63, 35, 19, 47, 55, 35, 49, 47, 55, 37, 39, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 3, 95, 50, 88, 87, 36, 63, 48, 108, 12, 58, 35, 55, 55, 37, 39, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 2, 95, 51, 36, 12, 57, 37, 0, 0, 9, 2, 95, 50, 108, 12, 63, 36, 0, 0, 8, 2, 95, 49, 87, 36, 12, 0, 0, 10, 2, 95, 48, 35, 19, 47, 55, 36, 0, 0, 12, 2, 95, 55, 74, 37, 78, 108, 12, 63, 36, 0, 0, 13, 2, 95, 54, 74, 37, 49, 58, 35, 87, 36, 12, 0, 0, 15, 2, 95, 53, 63, 35, 12, 49, 58, 37, 12, 55, 55, 37, 0, 0, 10, 2, 95, 52, 50, 35, 12, 58, 37, 0, 0, 0, 0, 14, 2, 95, 57, 74, 37, 58, 49, 50, 35, 12, 58, 37, 0, 0, 13, 2, 95, 56, 74, 37, 58, 49, 36, 12, 57, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 196, 147, 0, 196, 171, 0, 101, 0, 105, 0, 7, 6, 196, 129, 0, 3, 35, 12, 0, 7, 6, 196, 147, 0, 2, 32, 3, 6, 36, 12, 0, 3, 36, 12, 0, 7, 6, 196, 171, 0, 3, 37, 12, 0, 7, 6, 197, 141, 0, 3, 39, 12, 0, 7, 6, 97, 0, 3, 35, 0, 7, 6, 99, 0, 3, 49, 0, 117, 3, 49, 58, 0, 104, 3, 74, 0, 2, 18, 66, 3, 87, 0, 7, 6, 101, 0, 3, 36, 0, 7, 6, 104, 0, 3, 19, 0, 117, 3, 58, 0, 7, 6, 105, 0, 3, 37, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 7, 6, 111, 0, 3, 39, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 117, 3, 49, 0, 7, 6, 116, 0, 3, 47, 0, 7, 6, 117, 0, 3, 39, 0, 113, 3, 49, 0, 4, 2, 17, 65, 3, 58, 0, 104, 0, 99, 3, 58, 49, 0, 7, 6, 120, 0, 3, 89, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 87, 0, 7, 6, 0, 35, 3, 9, 0, 107, 3, 49, 0, 114, 3, 51, 0, 119, 3, 58, 0, 98, 3, 69, 0, 100, 3, 70, 0, 103, 3, 79, 0, 102, 3, 81, 0, 118, 3, 82, 0, 4, 115, 3, 87, 0, 195, 167, 0, 106, 3, 99, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts39 = FileInMemory_createWithData (1534, reinterpret_cast (&espeakdata_dicts39_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/nci_dict", L"nci"); Collection_addItem (me.peek(), espeakdata_dicts39.transfer()); static unsigned char espeakdata_dicts40_data[5658] = { 0, 4, 0, 0, 32, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 164, 151, 224, 164, 188, 98, 13, 0, 0, 0, 0, 0, 11, 6, 224, 164, 149, 224, 164, 188, 102, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 164, 171, 224, 164, 188, 81, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 4, 16, 20, 10, 70, 13, 87, 13, 63, 55, 6, 117, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 164, 161, 224, 164, 188, 68, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 51, 57, 40, 50, 47, 35, 55, 6, 37, 87, 0, 12, 3, 95, 50, 49, 36, 49, 12, 6, 132, 87, 0, 0, 12, 3, 95, 51, 56, 35, 34, 47, 6, 37, 87, 0, 10, 3, 95, 50, 48, 69, 6, 37, 87, 0, 0, 10, 3, 95, 50, 51, 47, 6, 148, 87, 0, 0, 10, 3, 95, 50, 50, 69, 6, 132, 87, 0, 0, 13, 3, 95, 50, 53, 48, 13, 78, 12, 6, 37, 87, 0, 0, 12, 3, 95, 50, 52, 78, 6, 39, 69, 37, 87, 0, 0, 13, 3, 95, 50, 55, 87, 13, 47, 12, 6, 132, 87, 0, 0, 14, 3, 95, 50, 54, 142, 13, 69, 69, 6, 37, 34, 87, 0, 0, 13, 3, 95, 51, 49, 36, 49, 47, 12, 6, 37, 87, 0, 0, 10, 3, 95, 51, 48, 47, 6, 37, 87, 0, 0, 13, 3, 95, 51, 51, 47, 36, 47, 12, 6, 37, 87, 0, 0, 13, 3, 95, 51, 50, 69, 35, 47, 12, 6, 37, 87, 0, 0, 15, 3, 95, 51, 53, 48, 13, 111, 50, 47, 12, 6, 37, 87, 0, 0, 12, 3, 95, 51, 52, 78, 129, 47, 6, 37, 87, 0, 0, 14, 3, 95, 51, 55, 87, 13, 111, 50, 47, 6, 37, 87, 0, 0, 14, 3, 95, 51, 54, 142, 35, 85, 12, 6, 47, 37, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 55, 57, 4, 40, 65, 37, 35, 87, 6, 37, 0, 14, 3, 95, 54, 49, 6, 37, 49, 87, 13, 138, 105, 37, 0, 0, 16, 3, 95, 55, 56, 35, 136, 105, 35, 47, 12, 6, 107, 34, 12, 0, 12, 3, 95, 54, 48, 87, 6, 35, 138, 105, 37, 0, 0, 10, 3, 95, 48, 67, 87, 6, 107, 36, 0, 15, 3, 95, 54, 51, 47, 6, 37, 34, 87, 13, 138, 105, 37, 0, 0, 15, 3, 95, 54, 50, 69, 6, 13, 37, 87, 13, 138, 105, 37, 0, 0, 15, 3, 95, 54, 53, 48, 13, 111, 50, 87, 13, 138, 105, 37, 0, 0, 14, 3, 95, 54, 52, 78, 6, 128, 87, 13, 138, 105, 37, 0, 0, 15, 3, 95, 54, 55, 87, 6, 107, 34, 87, 13, 138, 105, 37, 0, 0, 16, 3, 95, 54, 54, 142, 6, 37, 57, 35, 87, 13, 138, 105, 37, 0, 0, 15, 3, 95, 55, 49, 37, 144, 35, 47, 12, 6, 107, 34, 12, 0, 0, 14, 3, 95, 55, 48, 87, 35, 47, 12, 6, 107, 34, 12, 0, 0, 16, 3, 95, 55, 51, 47, 37, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 16, 3, 95, 55, 50, 69, 13, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 17, 3, 95, 55, 53, 48, 35, 142, 4, 35, 47, 12, 6, 107, 34, 12, 0, 0, 16, 3, 95, 55, 52, 78, 39, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 18, 3, 95, 55, 55, 87, 13, 47, 13, 105, 35, 47, 12, 6, 107, 34, 12, 0, 0, 16, 3, 95, 55, 54, 142, 108, 57, 108, 47, 12, 6, 107, 34, 12, 0, 0, 12, 3, 95, 49, 57, 40, 50, 50, 6, 132, 87, 0, 0, 14, 3, 95, 49, 56, 107, 138, 105, 12, 6, 35, 34, 109, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 57, 40, 50, 47, 6, 37, 87, 0, 12, 3, 95, 49, 49, 36, 145, 6, 35, 34, 13, 0, 0, 12, 3, 95, 50, 56, 35, 136, 12, 6, 132, 87, 0, 9, 3, 95, 49, 48, 70, 107, 87, 0, 0, 11, 3, 95, 49, 51, 47, 6, 36, 34, 13, 0, 0, 11, 3, 95, 49, 50, 69, 6, 35, 34, 13, 0, 0, 13, 3, 95, 49, 53, 48, 6, 107, 50, 70, 34, 13, 0, 0, 11, 3, 95, 49, 52, 142, 6, 39, 70, 13, 0, 0, 13, 3, 95, 49, 55, 87, 6, 107, 47, 12, 34, 109, 0, 0, 11, 3, 95, 49, 54, 87, 6, 39, 34, 13, 0, 0, 8, 3, 224, 164, 165, 136, 13, 0, 0, 8, 3, 224, 164, 164, 47, 13, 0, 0, 8, 3, 224, 164, 167, 137, 13, 0, 0, 8, 3, 224, 164, 166, 70, 13, 0, 0, 8, 3, 224, 164, 161, 139, 13, 0, 0, 9, 3, 224, 164, 160, 138, 105, 13, 0, 0, 8, 3, 224, 164, 163, 64, 13, 0, 0, 9, 3, 224, 164, 162, 139, 105, 13, 0, 0, 8, 3, 224, 164, 157, 143, 13, 0, 12, 3, 95, 52, 57, 6, 40, 65, 78, 35, 87, 0, 0, 8, 3, 224, 164, 156, 77, 13, 0, 14, 3, 95, 52, 56, 35, 34, 47, 35, 55, 6, 37, 87, 0, 0, 8, 3, 224, 164, 159, 138, 13, 0, 0, 8, 3, 224, 164, 158, 65, 13, 0, 0, 8, 3, 224, 164, 153, 66, 13, 0, 0, 8, 3, 224, 164, 152, 145, 13, 0, 0, 8, 3, 224, 164, 155, 142, 13, 0, 0, 8, 3, 224, 164, 154, 78, 13, 0, 0, 9, 3, 224, 165, 157, 105, 34, 13, 0, 8, 3, 224, 164, 149, 49, 13, 0, 17, 3, 95, 53, 57, 40, 50, 13, 50, 6, 87, 35, 47, 12, 105, 37, 0, 14, 3, 95, 52, 49, 37, 49, 78, 35, 55, 6, 37, 87, 0, 0, 8, 3, 224, 165, 156, 44, 13, 0, 15, 3, 95, 53, 56, 13, 50, 136, 12, 6, 133, 50, 50, 13, 0, 12, 3, 95, 52, 48, 78, 35, 55, 6, 37, 87, 0, 0, 8, 3, 224, 165, 159, 57, 13, 0, 8, 3, 224, 164, 151, 79, 13, 0, 14, 3, 95, 52, 51, 47, 125, 47, 35, 55, 6, 37, 87, 0, 0, 8, 3, 224, 165, 158, 81, 13, 0, 8, 3, 224, 164, 150, 144, 13, 0, 13, 3, 95, 52, 50, 69, 132, 35, 55, 6, 37, 87, 0, 0, 8, 3, 224, 165, 153, 99, 13, 0, 15, 3, 95, 52, 53, 48, 132, 6, 50, 47, 35, 55, 37, 87, 0, 0, 8, 3, 224, 165, 152, 102, 13, 0, 14, 3, 95, 52, 52, 78, 39, 58, 35, 55, 6, 37, 87, 0, 0, 8, 3, 224, 165, 155, 86, 13, 0, 14, 3, 95, 52, 55, 87, 125, 47, 35, 55, 6, 37, 87, 0, 0, 8, 3, 224, 165, 154, 98, 13, 0, 15, 3, 95, 52, 54, 142, 105, 37, 57, 35, 55, 6, 37, 87, 0, 0, 18, 3, 95, 54, 57, 40, 50, 13, 35, 50, 87, 13, 47, 47, 13, 34, 37, 0, 13, 3, 95, 53, 49, 36, 49, 6, 133, 50, 50, 13, 0, 0, 13, 3, 95, 54, 56, 35, 34, 87, 13, 138, 105, 37, 0, 12, 3, 95, 53, 48, 48, 13, 78, 6, 35, 87, 0, 0, 14, 3, 95, 53, 51, 47, 34, 6, 37, 48, 50, 50, 13, 0, 0, 14, 3, 95, 53, 50, 69, 35, 106, 6, 40, 50, 50, 13, 0, 0, 15, 3, 95, 53, 53, 48, 6, 35, 142, 48, 13, 50, 50, 13, 0, 0, 15, 3, 95, 53, 52, 78, 6, 119, 40, 58, 13, 50, 50, 13, 0, 0, 15, 3, 95, 53, 55, 87, 13, 50, 47, 6, 133, 50, 50, 13, 0, 0, 17, 3, 95, 53, 54, 142, 105, 13, 48, 12, 6, 48, 13, 50, 50, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 56, 57, 6, 40, 50, 35, 50, 12, 6, 50, 13, 69, 12, 36, 0, 0, 13, 3, 95, 56, 56, 35, 136, 12, 35, 87, 6, 37, 0, 0, 0, 0, 8, 3, 224, 164, 185, 106, 13, 0, 0, 8, 3, 224, 164, 184, 87, 13, 0, 0, 0, 0, 8, 3, 224, 164, 181, 82, 13, 0, 16, 3, 95, 57, 57, 50, 37, 65, 57, 6, 35, 50, 13, 58, 36, 0, 13, 3, 95, 56, 49, 37, 49, 57, 35, 87, 6, 37, 0, 0, 15, 3, 95, 57, 56, 35, 136, 12, 6, 35, 50, 13, 58, 36, 0, 12, 3, 95, 56, 48, 4, 107, 87, 87, 6, 37, 0, 0, 8, 3, 224, 164, 183, 91, 13, 0, 13, 3, 95, 56, 51, 47, 37, 34, 35, 87, 6, 37, 0, 0, 8, 3, 224, 164, 182, 89, 13, 0, 12, 3, 95, 56, 50, 69, 132, 35, 87, 6, 37, 0, 0, 8, 3, 224, 164, 177, 34, 13, 0, 13, 3, 95, 56, 53, 48, 13, 6, 78, 35, 87, 37, 0, 0, 8, 3, 224, 164, 176, 34, 13, 0, 13, 3, 95, 56, 52, 78, 39, 34, 35, 87, 6, 37, 0, 0, 8, 3, 224, 164, 179, 62, 13, 0, 14, 3, 95, 56, 55, 87, 107, 47, 12, 35, 87, 6, 37, 0, 0, 8, 3, 224, 164, 178, 55, 13, 0, 13, 3, 95, 56, 54, 142, 37, 57, 35, 87, 6, 37, 0, 0, 8, 3, 224, 164, 173, 135, 13, 0, 15, 3, 95, 57, 49, 37, 49, 57, 6, 35, 50, 13, 58, 36, 0, 0, 8, 3, 224, 164, 172, 69, 13, 0, 12, 3, 95, 57, 48, 50, 107, 69, 12, 6, 36, 0, 0, 8, 3, 224, 164, 175, 57, 13, 0, 15, 3, 95, 57, 51, 47, 37, 34, 6, 35, 50, 13, 58, 36, 0, 0, 8, 3, 224, 164, 174, 63, 13, 0, 13, 3, 95, 57, 50, 69, 6, 35, 50, 13, 58, 36, 0, 0, 15, 3, 95, 57, 53, 48, 13, 78, 6, 35, 50, 13, 58, 36, 0, 0, 8, 3, 224, 164, 168, 50, 13, 0, 15, 3, 95, 57, 52, 78, 39, 34, 6, 35, 63, 13, 58, 36, 0, 0, 8, 3, 224, 164, 171, 134, 13, 0, 16, 3, 95, 57, 55, 87, 13, 47, 12, 6, 35, 50, 13, 58, 36, 0, 0, 8, 3, 224, 164, 170, 48, 13, 0, 15, 3, 95, 57, 54, 142, 37, 57, 6, 35, 50, 13, 58, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 48, 77, 52, 69, 6, 37, 55, 37, 39, 50, 0, 0, 0, 11, 4, 95, 48, 77, 50, 55, 6, 35, 144, 0, 0, 13, 4, 95, 48, 77, 51, 78, 34, 6, 39, 34, 36, 0, 0, 0, 13, 4, 95, 48, 77, 49, 105, 13, 86, 6, 35, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 164, 150, 224, 164, 188, 99, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 164, 156, 224, 164, 188, 86, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 2, 95, 51, 47, 6, 37, 50, 0, 0, 8, 2, 95, 50, 70, 6, 154, 0, 0, 8, 2, 95, 49, 6, 36, 49, 0, 0, 11, 2, 95, 48, 89, 6, 40, 64, 57, 108, 0, 0, 9, 2, 95, 55, 87, 6, 35, 47, 0, 0, 8, 2, 95, 54, 142, 6, 109, 0, 0, 10, 2, 95, 53, 48, 6, 35, 50, 78, 0, 0, 10, 2, 95, 52, 78, 6, 35, 34, 12, 0, 0, 0, 0, 8, 2, 95, 57, 50, 6, 151, 0, 0, 9, 2, 95, 56, 6, 35, 138, 105, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 102, 9, 0, 0, 48, 0, 0, 0, 103, 9, 0, 0, 49, 0, 0, 0, 104, 9, 0, 0, 50, 0, 0, 0, 105, 9, 0, 0, 51, 0, 0, 0, 106, 9, 0, 0, 52, 0, 0, 0, 107, 9, 0, 0, 53, 0, 0, 0, 108, 9, 0, 0, 54, 0, 0, 0, 109, 9, 0, 0, 55, 0, 0, 0, 110, 9, 0, 0, 56, 0, 0, 0, 111, 9, 0, 0, 57, 0, 0, 0, 0, 0, 0, 0, 6, 1, 2, 0, 3, 50, 0, 7, 6, 1, 3, 0, 4, 3, 63, 0, 2, 224, 164, 170, 0, 2, 224, 164, 171, 0, 2, 224, 164, 172, 0, 2, 224, 164, 173, 0, 2, 224, 164, 174, 0, 4, 2, 224, 164, 159, 3, 64, 0, 2, 224, 164, 160, 0, 2, 224, 164, 161, 0, 2, 224, 164, 162, 0, 2, 224, 164, 163, 0, 4, 2, 224, 164, 154, 3, 65, 0, 2, 224, 164, 155, 0, 2, 224, 164, 156, 0, 2, 224, 164, 157, 0, 2, 224, 164, 158, 0, 2, 224, 164, 175, 0, 4, 2, 224, 164, 149, 3, 66, 0, 2, 224, 164, 150, 0, 2, 224, 164, 151, 0, 2, 224, 164, 152, 0, 2, 224, 164, 153, 0, 2, 224, 164, 185, 0, 7, 6, 1, 4, 0, 3, 106, 0, 7, 6, 1, 6, 0, 3, 107, 0, 224, 164, 129, 3, 127, 0, 7, 6, 1, 7, 0, 3, 35, 0, 224, 164, 129, 3, 126, 0, 224, 164, 135, 3, 132, 0, 4, 224, 164, 137, 3, 133, 0, 224, 164, 138, 0, 7, 6, 1, 8, 0, 3, 37, 0, 224, 164, 129, 3, 122, 0, 7, 6, 1, 9, 0, 3, 37, 0, 224, 164, 129, 3, 122, 0, 7, 6, 1, 10, 0, 3, 40, 0, 224, 164, 129, 3, 131, 0, 224, 164, 136, 3, 154, 0, 7, 6, 1, 11, 0, 3, 40, 0, 224, 164, 129, 3, 131, 0, 7, 6, 1, 12, 0, 3, 34, 111, 0, 7, 6, 1, 13, 0, 3, 45, 0, 7, 6, 1, 14, 0, 3, 114, 0, 7, 6, 1, 15, 0, 3, 36, 0, 224, 164, 129, 3, 124, 0, 7, 6, 1, 16, 0, 3, 36, 0, 224, 164, 129, 3, 124, 0, 224, 164, 137, 3, 149, 0, 7, 6, 1, 17, 0, 3, 150, 0, 7, 6, 1, 18, 0, 3, 119, 0, 7, 6, 1, 19, 0, 3, 39, 0, 7, 6, 1, 20, 0, 3, 39, 0, 224, 164, 135, 3, 152, 0, 4, 224, 164, 137, 3, 153, 0, 224, 164, 138, 0, 7, 6, 1, 21, 0, 3, 151, 0, 7, 6, 1, 22, 0, 4, 2, 17, 66, 3, 49, 0, 5, 1, 2, 32, 0, 2, 224, 165, 141, 224, 164, 175, 3, 49, 12, 0, 3, 49, 107, 0, 224, 164, 129, 3, 49, 127, 0, 1, 141, 165, 224, 2, 32, 3, 49, 147, 0, 4, 224, 164, 188, 2, 17, 66, 3, 102, 0, 224, 164, 188, 5, 1, 2, 32, 0, 224, 164, 188, 3, 102, 107, 0, 224, 164, 188, 224, 164, 129, 3, 102, 127, 0, 224, 164, 188, 1, 141, 165, 224, 2, 32, 3, 102, 147, 0, 7, 6, 1, 23, 0, 4, 224, 164, 188, 2, 17, 66, 3, 99, 0, 224, 164, 188, 5, 1, 2, 32, 0, 224, 164, 188, 3, 99, 107, 0, 224, 164, 188, 224, 164, 129, 3, 99, 127, 0, 224, 164, 188, 1, 141, 165, 224, 2, 32, 3, 99, 147, 0, 4, 2, 17, 66, 3, 144, 0, 5, 1, 2, 32, 0, 3, 144, 107, 0, 224, 164, 129, 3, 144, 127, 0, 1, 141, 165, 224, 2, 32, 3, 144, 147, 0, 7, 6, 1, 24, 0, 4, 2, 17, 66, 3, 79, 0, 5, 1, 2, 32, 0, 3, 79, 107, 0, 224, 164, 129, 3, 79, 127, 0, 1, 141, 165, 224, 2, 32, 3, 79, 147, 0, 4, 224, 164, 188, 2, 17, 66, 3, 98, 0, 224, 164, 188, 5, 1, 2, 32, 0, 224, 164, 188, 3, 98, 107, 0, 224, 164, 188, 224, 164, 129, 3, 98, 127, 0, 224, 164, 188, 1, 141, 165, 224, 2, 32, 3, 98, 147, 0, 7, 6, 1, 25, 0, 4, 2, 17, 66, 3, 145, 0, 5, 1, 2, 32, 0, 3, 145, 107, 0, 224, 164, 129, 3, 145, 127, 0, 1, 141, 165, 224, 2, 32, 3, 145, 147, 0, 7, 6, 1, 26, 0, 4, 2, 17, 66, 3, 66, 0, 5, 1, 2, 32, 0, 3, 66, 107, 0, 224, 164, 129, 3, 66, 127, 0, 1, 141, 165, 224, 2, 32, 3, 66, 147, 0, 7, 6, 1, 27, 0, 4, 2, 17, 66, 3, 78, 0, 5, 1, 2, 32, 0, 2, 224, 165, 141, 224, 164, 175, 3, 78, 12, 0, 3, 78, 108, 0, 224, 164, 129, 3, 78, 127, 0, 1, 141, 165, 224, 2, 32, 3, 78, 147, 0, 7, 6, 1, 28, 0, 2, 17, 66, 3, 142, 0, 3, 142, 108, 0, 224, 164, 129, 3, 142, 127, 0, 1, 141, 165, 224, 2, 32, 3, 142, 147, 0, 7, 6, 1, 29, 0, 4, 2, 17, 66, 3, 77, 0, 5, 1, 2, 32, 0, 3, 77, 108, 0, 224, 164, 129, 3, 77, 127, 0, 1, 141, 165, 224, 2, 32, 3, 77, 147, 0, 4, 224, 164, 188, 2, 17, 66, 3, 86, 0, 224, 164, 188, 5, 1, 2, 32, 0, 224, 164, 188, 3, 86, 107, 0, 224, 164, 188, 224, 164, 129, 3, 86, 127, 0, 224, 164, 188, 1, 141, 165, 224, 2, 32, 3, 86, 147, 0, 7, 6, 1, 30, 0, 4, 2, 17, 66, 3, 143, 0, 5, 1, 2, 32, 0, 3, 143, 108, 0, 224, 164, 129, 3, 143, 127, 0, 1, 141, 165, 224, 2, 32, 3, 143, 147, 0, 7, 6, 1, 31, 0, 4, 1, 141, 165, 224, 2, 32, 3, 65, 0, 2, 17, 66, 0, 5, 1, 2, 32, 0, 3, 65, 108, 0, 3, 65, 127, 0, 7, 6, 1, 32, 0, 4, 2, 17, 66, 3, 138, 0, 5, 1, 2, 32, 0, 2, 224, 165, 141, 224, 164, 175, 3, 138, 12, 0, 3, 138, 107, 0, 224, 164, 129, 3, 138, 127, 0, 1, 141, 165, 224, 2, 32, 3, 138, 147, 0, 7, 6, 1, 33, 0, 4, 2, 17, 66, 3, 138, 105, 0, 5, 1, 2, 32, 0, 3, 138, 105, 107, 0, 224, 164, 129, 3, 138, 105, 127, 0, 1, 141, 165, 224, 2, 32, 3, 138, 105, 147, 0, 7, 6, 1, 34, 0, 4, 224, 164, 188, 2, 17, 66, 3, 68, 0, 224, 164, 188, 5, 1, 2, 32, 0, 224, 164, 188, 3, 68, 107, 0, 224, 164, 188, 224, 164, 129, 3, 68, 127, 0, 224, 164, 188, 1, 141, 165, 224, 2, 32, 3, 68, 147, 0, 4, 2, 17, 66, 3, 139, 0, 5, 1, 2, 32, 0, 3, 139, 107, 0, 224, 164, 129, 3, 139, 127, 0, 1, 141, 165, 224, 2, 32, 3, 139, 147, 0, 7, 6, 1, 35, 0, 4, 224, 164, 188, 2, 17, 66, 3, 68, 105, 0, 224, 164, 188, 5, 1, 2, 32, 0, 224, 164, 188, 3, 68, 105, 107, 0, 224, 164, 188, 224, 164, 129, 3, 68, 105, 127, 0, 224, 164, 188, 1, 141, 165, 224, 2, 32, 3, 68, 105, 147, 0, 4, 2, 17, 66, 3, 139, 105, 0, 5, 1, 2, 32, 0, 3, 139, 105, 107, 0, 224, 164, 129, 3, 139, 105, 127, 0, 1, 141, 165, 224, 2, 32, 3, 139, 105, 147, 0, 7, 6, 1, 36, 0, 4, 2, 17, 66, 3, 64, 0, 5, 1, 2, 32, 0, 3, 64, 107, 0, 224, 164, 129, 3, 64, 127, 0, 1, 141, 165, 224, 2, 32, 3, 64, 147, 0, 7, 6, 1, 37, 0, 4, 2, 17, 66, 3, 47, 0, 5, 1, 2, 32, 0, 2, 224, 165, 141, 224, 164, 175, 3, 47, 12, 0, 3, 47, 107, 0, 224, 164, 129, 3, 47, 127, 0, 1, 141, 165, 224, 2, 32, 3, 47, 147, 0, 7, 6, 1, 38, 0, 4, 2, 17, 66, 3, 136, 0, 5, 1, 2, 32, 0, 3, 136, 107, 0, 224, 164, 129, 3, 136, 127, 0, 1, 141, 165, 224, 2, 32, 3, 136, 147, 0, 7, 6, 1, 39, 0, 4, 2, 17, 66, 3, 70, 0, 5, 1, 2, 32, 0, 3, 70, 107, 0, 224, 164, 129, 3, 70, 127, 0, 1, 141, 165, 224, 2, 32, 3, 70, 147, 0, 7, 6, 1, 40, 0, 4, 2, 17, 66, 3, 137, 0, 5, 1, 2, 32, 0, 3, 137, 107, 0, 224, 164, 129, 3, 137, 127, 0, 1, 141, 165, 224, 2, 32, 3, 137, 147, 0, 7, 6, 1, 41, 0, 4, 1, 141, 165, 224, 176, 164, 224, 2, 32, 3, 50, 0, 2, 17, 66, 0, 5, 1, 2, 32, 0, 3, 50, 107, 0, 224, 164, 129, 3, 50, 127, 0, 1, 141, 165, 224, 2, 32, 3, 50, 147, 0, 7, 6, 1, 42, 0, 3, 50, 12, 0, 7, 6, 1, 43, 0, 4, 2, 17, 66, 3, 48, 0, 5, 1, 2, 32, 0, 2, 224, 165, 141, 224, 164, 175, 3, 48, 12, 0, 3, 48, 107, 0, 224, 164, 129, 3, 48, 127, 0, 1, 141, 165, 224, 2, 32, 3, 48, 147, 0, 7, 6, 1, 44, 0, 4, 224, 164, 188, 2, 17, 66, 3, 81, 0, 224, 164, 188, 5, 1, 2, 32, 0, 224, 164, 188, 3, 81, 107, 0, 224, 164, 188, 224, 164, 129, 3, 81, 127, 0, 224, 164, 188, 1, 141, 165, 224, 2, 32, 3, 81, 147, 0, 4, 1, 141, 165, 224, 2, 32, 3, 134, 0, 2, 17, 66, 0, 5, 1, 2, 32, 0, 3, 134, 107, 0, 224, 164, 129, 3, 134, 127, 0, 7, 6, 1, 45, 0, 4, 2, 17, 66, 3, 69, 0, 5, 1, 2, 32, 0, 3, 69, 107, 0, 224, 164, 129, 3, 69, 127, 0, 1, 141, 165, 224, 2, 32, 3, 69, 147, 0, 7, 6, 1, 46, 0, 4, 2, 17, 66, 3, 135, 0, 5, 1, 2, 32, 0, 3, 135, 107, 0, 224, 164, 129, 3, 135, 127, 0, 1, 141, 165, 224, 2, 32, 3, 135, 147, 0, 7, 6, 1, 47, 0, 4, 1, 141, 165, 224, 168, 164, 224, 2, 32, 3, 63, 0, 1, 141, 165, 224, 176, 164, 224, 2, 32, 0, 2, 17, 66, 0, 5, 1, 2, 32, 0, 3, 63, 107, 0, 224, 164, 129, 3, 63, 127, 0, 1, 141, 165, 224, 2, 32, 3, 63, 147, 0, 7, 6, 1, 48, 0, 4, 2, 17, 66, 3, 57, 0, 5, 1, 2, 32, 0, 3, 57, 108, 0, 224, 164, 129, 3, 57, 127, 0, 1, 141, 165, 224, 2, 32, 3, 57, 147, 0, 7, 6, 1, 49, 0, 4, 2, 17, 66, 3, 34, 0, 5, 1, 2, 32, 0, 4, 3, 34, 109, 0, 224, 164, 129, 0, 1, 141, 165, 224, 2, 32, 3, 34, 147, 0, 7, 6, 1, 50, 0, 4, 2, 17, 66, 3, 34, 0, 5, 1, 2, 32, 0, 3, 34, 107, 0, 1, 141, 165, 224, 2, 32, 3, 34, 147, 0, 7, 6, 1, 51, 0, 4, 2, 17, 66, 3, 55, 0, 5, 1, 2, 32, 0, 3, 55, 107, 0, 224, 164, 129, 3, 55, 127, 0, 1, 141, 165, 224, 2, 32, 3, 55, 147, 0, 7, 6, 1, 52, 0, 4, 2, 17, 66, 3, 62, 0, 5, 1, 2, 32, 0, 3, 62, 107, 0, 224, 164, 129, 3, 62, 127, 0, 1, 141, 165, 224, 2, 32, 3, 62, 147, 0, 7, 6, 1, 53, 0, 4, 2, 17, 66, 3, 62, 0, 5, 1, 2, 32, 0, 3, 62, 107, 0, 224, 164, 129, 3, 62, 127, 0, 1, 141, 165, 224, 2, 32, 3, 62, 147, 0, 7, 6, 1, 54, 0, 8, 2, 17, 66, 3, 58, 0, 8, 3, 58, 107, 0, 224, 164, 129, 8, 3, 58, 127, 0, 4, 2, 17, 66, 3, 82, 0, 5, 1, 2, 32, 0, 8, 2, 224, 165, 141, 0, 3, 82, 107, 0, 224, 164, 129, 3, 82, 127, 0, 1, 141, 165, 224, 2, 32, 3, 82, 147, 0, 7, 6, 1, 55, 0, 4, 2, 17, 66, 3, 89, 0, 5, 1, 2, 32, 0, 3, 89, 107, 0, 224, 164, 129, 3, 89, 127, 0, 1, 141, 165, 224, 2, 32, 3, 89, 147, 0, 7, 6, 1, 56, 0, 4, 2, 17, 66, 3, 91, 0, 5, 1, 2, 32, 0, 3, 91, 107, 0, 224, 164, 129, 3, 91, 127, 0, 1, 141, 165, 224, 2, 32, 3, 91, 147, 0, 7, 6, 1, 57, 0, 4, 2, 17, 66, 3, 87, 0, 5, 1, 2, 32, 0, 3, 87, 107, 0, 224, 164, 129, 3, 87, 127, 0, 1, 141, 165, 224, 2, 32, 3, 87, 147, 0, 7, 6, 1, 58, 0, 4, 2, 17, 66, 3, 106, 0, 5, 1, 2, 32, 0, 3, 106, 107, 0, 224, 164, 129, 3, 106, 127, 0, 1, 141, 165, 224, 2, 32, 3, 106, 147, 0, 7, 6, 1, 62, 0, 3, 12, 0, 7, 6, 1, 63, 0, 3, 35, 0, 224, 164, 129, 3, 126, 0, 224, 164, 135, 3, 132, 0, 4, 224, 164, 137, 3, 133, 0, 224, 164, 138, 0, 7, 6, 1, 64, 0, 3, 37, 0, 224, 164, 129, 3, 122, 0, 7, 6, 1, 65, 0, 3, 37, 0, 224, 164, 129, 3, 122, 0, 7, 6, 1, 66, 0, 3, 40, 0, 224, 164, 129, 3, 131, 0, 224, 164, 136, 3, 154, 0, 7, 6, 1, 67, 0, 3, 40, 0, 224, 164, 129, 3, 131, 0, 7, 6, 1, 68, 0, 3, 34, 111, 0, 7, 6, 1, 69, 0, 3, 34, 111, 0, 7, 6, 1, 70, 0, 3, 114, 0, 7, 6, 1, 71, 0, 3, 36, 0, 224, 164, 129, 3, 124, 0, 7, 6, 1, 72, 0, 3, 36, 0, 224, 164, 129, 3, 124, 0, 224, 164, 137, 3, 149, 0, 7, 6, 1, 73, 0, 3, 150, 0, 7, 6, 1, 74, 0, 3, 119, 0, 7, 6, 1, 75, 0, 3, 39, 0, 7, 6, 1, 76, 0, 3, 39, 0, 224, 164, 135, 3, 152, 0, 4, 224, 164, 137, 3, 153, 0, 224, 164, 138, 0, 7, 6, 1, 77, 0, 3, 151, 0, 7, 6, 1, 78, 0, 3, 0, 7, 6, 1, 81, 0, 3, 129, 63, 0, 7, 6, 1, 89, 0, 4, 2, 17, 66, 3, 102, 0, 5, 1, 2, 32, 0, 3, 102, 107, 0, 1, 141, 165, 224, 2, 32, 3, 102, 147, 0, 7, 6, 1, 90, 0, 4, 2, 17, 66, 3, 99, 0, 5, 1, 2, 32, 0, 3, 99, 107, 0, 1, 141, 165, 224, 2, 32, 3, 99, 147, 0, 7, 6, 1, 91, 0, 4, 2, 17, 66, 3, 98, 0, 5, 1, 2, 32, 0, 3, 98, 107, 0, 1, 141, 165, 224, 2, 32, 3, 98, 147, 0, 7, 6, 1, 92, 0, 4, 2, 17, 66, 3, 86, 0, 5, 1, 2, 32, 0, 3, 86, 107, 0, 1, 141, 165, 224, 2, 32, 3, 86, 147, 0, 7, 6, 1, 93, 0, 4, 2, 17, 66, 3, 90, 0, 5, 1, 2, 32, 0, 3, 90, 107, 0, 1, 141, 165, 224, 2, 32, 3, 90, 147, 0, 7, 6, 1, 94, 0, 4, 2, 17, 66, 3, 68, 105, 0, 5, 1, 2, 32, 0, 3, 68, 105, 107, 0, 1, 141, 165, 224, 2, 32, 3, 68, 105, 147, 0, 7, 6, 1, 95, 0, 4, 2, 17, 66, 3, 81, 0, 5, 1, 2, 32, 0, 3, 81, 107, 0, 1, 141, 165, 224, 2, 32, 3, 81, 147, 0, 7, 6, 1, 96, 0, 4, 2, 17, 66, 3, 57, 0, 5, 1, 2, 32, 0, 3, 57, 107, 0, 1, 141, 165, 224, 2, 32, 3, 57, 147, 0, 7, 6, 1, 97, 0, 3, 107, 20, 34, 34, 0, 7, 6, 1, 98, 0, 3, 45, 12, 0, 7, 6, 1, 99, 0, 3, 45, 0, 7, 6, 1, 100, 0, 3, 45, 12, 0, 7, 6, 0, 37, 3, 48, 107, 87, 114, 50, 47, 0, 36, 3, 70, 119, 55, 107, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts40 = FileInMemory_createWithData (5657, reinterpret_cast (&espeakdata_dicts40_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ne_dict", L"ne"); Collection_addItem (me.peek(), espeakdata_dicts40.transfer()); static unsigned char espeakdata_dicts41_data[21599] = { 0, 4, 0, 0, 41, 59, 0, 0, 0, 0, 0, 0, 0, 8, 197, 104, 242, 69, 81, 48, 66, 0, 10, 199, 44, 20, 130, 60, 226, 197, 48, 20, 10, 199, 52, 21, 83, 60, 193, 85, 52, 20, 0, 11, 70, 32, 20, 132, 92, 20, 133, 21, 0, 10, 7, 195, 92, 19, 148, 72, 8, 0, 0, 8, 197, 92, 145, 71, 20, 192, 20, 8, 197, 61, 32, 75, 20, 192, 20, 8, 197, 8, 85, 71, 20, 192, 20, 8, 197, 45, 33, 71, 20, 192, 20, 6, 65, 8, 69, 117, 0, 0, 9, 198, 76, 193, 78, 80, 84, 128, 20, 9, 198, 64, 197, 78, 16, 84, 128, 20, 9, 198, 44, 224, 80, 64, 84, 128, 20, 9, 198, 44, 192, 80, 64, 84, 128, 20, 9, 198, 12, 128, 82, 80, 84, 128, 20, 9, 198, 92, 19, 142, 20, 84, 128, 8, 0, 0, 11, 67, 12, 17, 133, 49, 113, 81, 6, 117, 0, 7, 196, 89, 32, 71, 20, 20, 0, 13, 69, 16, 145, 83, 20, 192, 70, 37, 86, 13, 55, 0, 24, 73, 8, 245, 82, 28, 243, 132, 36, 84, 128, 69, 40, 34, 99, 6, 120, 50, 70, 37, 12, 13, 34, 0, 8, 197, 77, 82, 203, 20, 192, 20, 8, 197, 72, 149, 19, 20, 192, 20, 9, 197, 104, 243, 1, 56, 112, 66, 8, 6, 65, 12, 87, 117, 0, 0, 9, 198, 57, 80, 200, 80, 84, 128, 20, 0, 13, 4, 95, 8, 1, 3, 105, 6, 113, 74, 109, 49, 0, 0, 11, 200, 89, 35, 213, 92, 83, 135, 20, 176, 22, 0, 8, 197, 49, 82, 77, 21, 32, 20, 6, 65, 16, 70, 117, 0, 0, 13, 202, 60, 225, 197, 52, 18, 203, 20, 194, 74, 44, 67, 0, 9, 67, 20, 83, 128, 13, 50, 0, 9, 0, 0, 8, 197, 52, 20, 141, 21, 32, 20, 16, 65, 20, 37, 12, 63, 117, 55, 0, 44, 81, 109, 97, 105, 108, 32, 5, 65, 20, 117, 0, 0, 16, 70, 21, 0, 85, 48, 85, 0, 117, 48, 120, 55, 6, 109, 47, 0, 0, 9, 67, 92, 146, 128, 83, 2, 121, 0, 9, 67, 28, 146, 128, 98, 2, 121, 0, 18, 4, 95, 48, 67, 15, 105, 6, 111, 50, 70, 109, 34, 47, 87, 47, 13, 0, 0, 0, 6, 65, 24, 109, 81, 0, 0, 0, 0, 9, 198, 76, 227, 197, 104, 83, 0, 20, 9, 198, 45, 114, 83, 64, 83, 0, 20, 9, 198, 45, 34, 78, 44, 83, 0, 20, 0, 8, 197, 52, 85, 19, 20, 192, 20, 6, 65, 28, 98, 117, 0, 0, 17, 70, 16, 85, 197, 88, 84, 128, 70, 13, 6, 83, 117, 82, 13, 34, 0, 16, 70, 8, 245, 68, 60, 148, 128, 69, 40, 70, 58, 6, 113, 34, 0, 9, 198, 76, 194, 68, 16, 84, 128, 20, 9, 198, 44, 193, 68, 16, 84, 128, 20, 0, 6, 195, 44, 19, 128, 72, 0, 0, 12, 201, 36, 225, 197, 92, 146, 203, 20, 193, 0, 67, 6, 65, 32, 105, 113, 0, 0, 9, 198, 64, 20, 148, 36, 177, 76, 20, 9, 198, 81, 35, 203, 44, 83, 128, 20, 0, 0, 11, 1, 35, 105, 6, 109, 49, 57, 13, 0, 27, 0, 6, 65, 36, 37, 12, 0, 0, 9, 198, 52, 240, 200, 80, 83, 128, 72, 13, 1, 37, 48, 14, 16, 120, 87, 6, 109, 50, 47, 0, 0, 0, 0, 8, 197, 92, 19, 139, 20, 192, 20, 8, 197, 88, 193, 71, 20, 192, 20, 8, 197, 44, 147, 139, 20, 192, 20, 8, 197, 32, 18, 203, 20, 192, 20, 8, 197, 92, 242, 203, 20, 192, 20, 8, 197, 80, 80, 203, 20, 192, 20, 6, 65, 40, 57, 117, 0, 0, 9, 198, 88, 194, 78, 16, 84, 128, 20, 9, 198, 76, 226, 80, 64, 84, 128, 20, 9, 198, 64, 19, 1, 88, 84, 128, 20, 9, 198, 44, 226, 80, 64, 84, 128, 20, 9, 198, 44, 193, 80, 64, 84, 128, 20, 9, 198, 32, 84, 143, 88, 84, 128, 20, 9, 198, 28, 197, 78, 16, 84, 128, 20, 9, 198, 24, 194, 80, 64, 84, 128, 20, 9, 198, 8, 197, 78, 16, 84, 128, 20, 0, 15, 1, 42, 87, 47, 6, 109, 16, 34, 109, 47, 38, 13, 0, 27, 0, 7, 196, 49, 32, 71, 20, 20, 7, 196, 17, 32, 71, 20, 20, 10, 1, 43, 48, 55, 6, 108, 87, 0, 27, 0, 8, 197, 64, 147, 135, 20, 192, 20, 8, 197, 40, 83, 135, 20, 192, 20, 8, 197, 32, 83, 135, 20, 192, 20, 8, 197, 24, 18, 203, 20, 192, 20, 8, 197, 17, 82, 75, 20, 192, 20, 8, 197, 9, 83, 135, 20, 192, 20, 8, 197, 8, 146, 203, 20, 192, 20, 8, 197, 8, 83, 135, 20, 192, 20, 8, 197, 80, 82, 203, 20, 192, 20, 8, 197, 16, 243, 135, 20, 192, 20, 6, 65, 44, 49, 113, 0, 0, 9, 198, 44, 225, 84, 80, 84, 128, 20, 9, 198, 28, 194, 84, 80, 84, 128, 20, 9, 198, 24, 192, 68, 16, 84, 128, 20, 0, 9, 1, 46, 48, 108, 50, 47, 0, 27, 0, 9, 1, 47, 87, 55, 6, 109, 89, 0, 0, 6, 65, 48, 109, 55, 0, 0, 0, 0, 0, 6, 65, 52, 109, 63, 0, 0, 9, 198, 16, 243, 210, 16, 21, 0, 66, 6, 194, 104, 240, 9, 76, 0, 0, 0, 10, 5, 95, 48, 1, 14, 4, 109, 50, 0, 6, 65, 56, 109, 50, 0, 0, 9, 198, 8, 146, 154, 36, 83, 132, 66, 0, 0, 9, 198, 76, 227, 210, 44, 83, 0, 20, 14, 70, 76, 133, 70, 24, 83, 0, 89, 108, 81, 13, 55, 0, 7, 196, 76, 16, 133, 48, 20, 13, 68, 48, 16, 133, 48, 55, 117, 69, 13, 55, 0, 20, 7, 196, 44, 16, 133, 48, 20, 9, 198, 81, 37, 70, 24, 83, 0, 20, 7, 196, 80, 16, 133, 48, 66, 7, 196, 104, 243, 69, 72, 20, 0, 8, 197, 25, 85, 19, 20, 192, 20, 0, 9, 198, 52, 148, 211, 80, 19, 132, 65, 9, 198, 64, 193, 84, 80, 84, 128, 20, 9, 198, 44, 193, 84, 80, 84, 128, 20, 9, 198, 44, 192, 68, 16, 84, 128, 20, 9, 198, 8, 192, 68, 16, 84, 128, 20, 15, 70, 81, 113, 65, 44, 84, 128, 47, 83, 37, 49, 13, 34, 0, 7, 194, 61, 0, 9, 76, 28, 0, 20, 71, 36, 225, 197, 56, 145, 85, 72, 106, 50, 86, 57, 13, 50, 57, 6, 119, 34, 0, 10, 199, 44, 241, 75, 20, 195, 197, 72, 20, 0, 0, 19, 1, 64, 9, 6, 113, 48, 13, 50, 87, 47, 4, 113, 34, 47, 38, 13, 9, 0, 6, 65, 64, 48, 117, 0, 0, 14, 70, 12, 128, 78, 76, 243, 128, 89, 115, 87, 6, 116, 0, 9, 198, 28, 83, 79, 28, 83, 128, 72, 0, 12, 201, 76, 50, 1, 72, 210, 78, 44, 83, 0, 20, 0, 13, 68, 104, 244, 1, 76, 86, 120, 48, 6, 114, 87, 0, 0, 6, 65, 68, 49, 107, 0, 0, 0, 17, 8, 3, 18, 195, 168, 3, 8, 5, 19, 49, 34, 109, 89, 13, 87, 0, 0, 0, 8, 197, 104, 241, 68, 20, 192, 20, 8, 197, 92, 147, 80, 20, 192, 20, 8, 197, 72, 241, 4, 20, 192, 20, 8, 197, 64, 241, 68, 20, 192, 20, 8, 197, 64, 147, 80, 20, 192, 20, 14, 69, 64, 17, 4, 20, 192, 48, 109, 70, 13, 55, 0, 20, 8, 197, 16, 243, 80, 20, 192, 20, 8, 197, 72, 241, 68, 20, 192, 20, 8, 197, 52, 145, 4, 20, 192, 20, 8, 197, 8, 241, 68, 20, 192, 20, 6, 65, 72, 109, 34, 0, 0, 16, 70, 12, 245, 82, 21, 84, 128, 49, 40, 12, 34, 6, 119, 34, 0, 0, 18, 71, 4, 53, 9, 21, 5, 78, 80, 114, 49, 87, 37, 48, 108, 50, 47, 0, 8, 67, 80, 129, 64, 84, 13, 0, 0, 6, 195, 76, 17, 197, 20, 7, 196, 29, 32, 71, 20, 20, 0, 8, 197, 44, 145, 84, 20, 192, 20, 8, 197, 12, 146, 134, 21, 32, 20, 6, 65, 76, 109, 87, 0, 0, 9, 198, 77, 0, 82, 80, 83, 0, 20, 8, 197, 77, 0, 84, 20, 192, 20, 0, 9, 198, 56, 19, 1, 80, 145, 197, 66, 0, 0, 8, 197, 24, 195, 210, 21, 64, 66, 6, 65, 80, 47, 117, 0, 0, 9, 198, 56, 19, 1, 80, 145, 192, 66, 0, 16, 70, 52, 20, 85, 21, 69, 5, 63, 113, 49, 6, 109, 47, 13, 0, 16, 70, 12, 244, 85, 21, 69, 5, 49, 120, 49, 6, 109, 47, 13, 0, 0, 0, 6, 65, 84, 2, 107, 0, 0, 9, 198, 45, 114, 78, 80, 85, 0, 66, 7, 66, 85, 0, 21, 0, 10, 0, 0, 9, 198, 105, 113, 78, 16, 83, 0, 20, 9, 198, 64, 20, 129, 8, 83, 0, 20, 0, 6, 65, 88, 81, 117, 0, 0, 9, 198, 8, 18, 143, 56, 85, 0, 67, 0, 0, 7, 196, 92, 17, 133, 48, 20, 9, 198, 28, 145, 67, 32, 83, 0, 20, 7, 196, 24, 16, 133, 48, 20, 7, 196, 56, 240, 133, 48, 20, 7, 196, 48, 144, 133, 48, 66, 0, 8, 197, 32, 84, 141, 4, 224, 65, 8, 197, 4, 212, 212, 20, 192, 20, 8, 197, 92, 144, 200, 20, 192, 20, 8, 197, 72, 240, 200, 20, 192, 20, 8, 197, 44, 149, 20, 20, 192, 20, 8, 197, 8, 245, 20, 20, 192, 20, 12, 1, 92, 69, 6, 109, 49, 87, 55, 109, 89, 0, 6, 65, 92, 82, 117, 0, 0, 0, 0, 0, 7, 65, 96, 106, 49, 87, 0, 0, 15, 70, 40, 16, 209, 84, 85, 0, 88, 35, 49, 6, 109, 47, 0, 0, 10, 199, 76, 50, 18, 60, 212, 5, 48, 20, 18, 71, 12, 20, 146, 61, 84, 197, 48, 49, 113, 34, 40, 87, 6, 109, 55, 0, 0, 7, 196, 76, 240, 133, 72, 20, 9, 198, 76, 50, 15, 84, 65, 82, 20, 9, 68, 77, 1, 65, 44, 21, 0, 10, 9, 68, 37, 65, 77, 76, 21, 0, 10, 0, 12, 69, 5, 35, 65, 56, 64, 21, 102, 114, 0, 10, 5, 65, 100, 121, 0, 0, 0, 0, 11, 200, 28, 81, 146, 37, 69, 85, 72, 64, 67, 0, 8, 197, 80, 147, 148, 20, 192, 20, 8, 197, 52, 19, 148, 20, 192, 20, 8, 197, 32, 244, 212, 20, 192, 20, 8, 197, 104, 245, 68, 20, 224, 72, 8, 197, 32, 17, 4, 20, 224, 72, 7, 65, 104, 86, 109, 47, 0, 0, 0, 7, 195, 92, 20, 192, 72, 9, 0, 0, 8, 197, 88, 243, 132, 20, 192, 20, 8, 197, 88, 83, 132, 20, 192, 20, 8, 197, 81, 85, 20, 20, 192, 20, 8, 197, 80, 85, 84, 20, 192, 20, 8, 197, 56, 85, 84, 20, 192, 20, 8, 197, 44, 16, 200, 20, 192, 20, 8, 197, 32, 19, 132, 20, 192, 20, 8, 197, 8, 240, 200, 20, 192, 20, 8, 197, 28, 243, 132, 20, 192, 20, 8, 197, 52, 20, 141, 61, 64, 66, 8, 197, 76, 244, 130, 21, 64, 66, 0, 14, 70, 28, 245, 65, 12, 129, 64, 98, 40, 6, 114, 89, 0, 0, 9, 198, 56, 17, 5, 48, 145, 197, 66, 0, 0, 13, 69, 52, 148, 211, 21, 32, 63, 106, 87, 13, 34, 0, 8, 197, 76, 84, 150, 21, 64, 66, 8, 195, 16, 243, 210, 9, 76, 28, 0, 9, 198, 56, 17, 5, 48, 145, 192, 66, 9, 198, 52, 148, 211, 48, 17, 192, 65, 0, 0, 0, 0, 0, 20, 71, 72, 84, 197, 73, 99, 201, 72, 34, 117, 86, 109, 34, 82, 58, 6, 113, 34, 0, 0, 9, 198, 44, 229, 80, 64, 83, 0, 20, 9, 198, 29, 33, 80, 64, 83, 0, 20, 0, 0, 0, 0, 9, 198, 105, 114, 74, 52, 83, 0, 20, 7, 196, 80, 17, 133, 48, 20, 0, 8, 197, 64, 145, 80, 20, 192, 20, 8, 197, 44, 241, 80, 20, 192, 20, 8, 197, 76, 241, 80, 20, 192, 20, 8, 197, 49, 85, 20, 20, 192, 20, 6, 195, 60, 33, 82, 20, 0, 0, 0, 9, 198, 56, 245, 133, 52, 33, 82, 66, 9, 198, 16, 80, 197, 52, 33, 82, 66, 7, 196, 8, 81, 5, 48, 20, 0, 23, 73, 4, 48, 197, 77, 51, 201, 72, 84, 192, 35, 49, 87, 109, 87, 58, 6, 35, 34, 13, 87, 0, 11, 70, 4, 148, 140, 36, 225, 83, 21, 0, 10, 0, 9, 198, 52, 20, 137, 60, 225, 84, 68, 0, 0, 7, 196, 21, 33, 197, 72, 20, 0, 9, 3, 13, 39, 14, 63, 13, 50, 0, 0, 0, 0, 7, 196, 28, 17, 5, 72, 20, 0, 0, 9, 198, 105, 112, 67, 33, 65, 76, 20, 0, 0, 11, 68, 52, 148, 211, 20, 63, 106, 87, 13, 0, 0, 8, 197, 76, 18, 203, 21, 32, 20, 0, 9, 198, 44, 242, 197, 81, 65, 64, 66, 0, 0, 0, 8, 197, 33, 83, 139, 21, 32, 20, 0, 5, 194, 8, 80, 17, 0, 39, 79, 60, 225, 5, 72, 128, 78, 16, 83, 9, 56, 116, 206, 61, 64, 64, 4, 39, 50, 70, 13, 34, 6, 105, 114, 50, 70, 13, 55, 106, 66, 87, 4, 50, 120, 47, 113, 0, 0, 7, 196, 20, 225, 5, 72, 20, 0, 0, 0, 7, 195, 16, 21, 0, 72, 8, 6, 195, 16, 21, 0, 72, 0, 12, 67, 8, 82, 1, 69, 117, 10, 105, 6, 113, 0, 0, 8, 197, 49, 144, 197, 84, 208, 20, 0, 9, 198, 40, 19, 149, 5, 34, 64, 67, 9, 198, 76, 50, 15, 24, 97, 76, 20, 0, 12, 201, 65, 35, 202, 20, 53, 9, 20, 193, 78, 67, 0, 9, 198, 5, 3, 211, 80, 83, 0, 20, 7, 196, 36, 161, 5, 48, 20, 0, 0, 9, 198, 44, 192, 82, 36, 225, 84, 67, 0, 0, 7, 196, 72, 241, 5, 48, 20, 7, 196, 40, 241, 5, 48, 20, 9, 198, 36, 224, 149, 72, 113, 82, 20, 7, 196, 28, 82, 1, 16, 72, 0, 0, 9, 198, 64, 21, 18, 36, 245, 0, 67, 17, 70, 64, 148, 212, 60, 193, 84, 48, 37, 87, 47, 120, 55, 6, 109, 0, 0, 0, 9, 198, 92, 81, 9, 41, 97, 82, 20, 9, 198, 28, 83, 79, 20, 65, 82, 20, 7, 196, 60, 81, 133, 56, 20, 0, 0, 0, 0, 7, 196, 44, 17, 5, 72, 20, 7, 196, 20, 97, 133, 56, 20, 0, 14, 69, 52, 85, 5, 20, 224, 63, 109, 47, 6, 117, 50, 0, 8, 197, 53, 83, 77, 20, 192, 20, 0, 9, 198, 76, 210, 69, 77, 1, 76, 20, 0, 0, 0, 8, 197, 81, 82, 77, 20, 192, 20, 8, 197, 72, 146, 141, 20, 192, 20, 8, 197, 17, 82, 77, 20, 192, 20, 8, 197, 8, 19, 139, 21, 64, 66, 8, 197, 64, 147, 131, 21, 64, 66, 8, 197, 92, 147, 4, 21, 32, 20, 8, 197, 44, 243, 4, 21, 32, 20, 8, 197, 44, 145, 80, 21, 32, 20, 8, 197, 32, 83, 4, 21, 32, 20, 8, 197, 16, 245, 20, 21, 32, 20, 0, 13, 70, 48, 148, 197, 81, 65, 64, 21, 102, 114, 0, 10, 0, 0, 0, 22, 73, 77, 81, 134, 72, 17, 197, 81, 65, 64, 87, 107, 81, 34, 113, 88, 6, 109, 47, 13, 0, 8, 197, 12, 244, 147, 21, 64, 66, 8, 197, 80, 83, 80, 21, 32, 20, 8, 197, 48, 241, 4, 21, 32, 20, 8, 197, 24, 147, 20, 21, 32, 20, 8, 197, 8, 17, 4, 21, 32, 20, 0, 0, 0, 7, 196, 60, 225, 5, 72, 20, 7, 196, 4, 225, 5, 72, 20, 0, 0, 0, 14, 67, 20, 230, 128, 109, 50, 86, 120, 82, 120, 34, 47, 0, 0, 9, 198, 105, 113, 78, 28, 83, 0, 20, 9, 198, 45, 112, 78, 76, 83, 0, 20, 9, 198, 9, 32, 66, 8, 83, 0, 20, 9, 198, 45, 33, 85, 64, 83, 0, 20, 7, 196, 80, 81, 5, 72, 20, 7, 196, 56, 81, 5, 72, 20, 7, 196, 56, 17, 5, 72, 20, 7, 196, 48, 81, 5, 72, 20, 0, 0, 0, 0, 7, 196, 72, 17, 133, 48, 20, 9, 198, 28, 226, 70, 24, 83, 0, 20, 9, 198, 21, 2, 83, 80, 83, 0, 20, 7, 196, 40, 241, 133, 48, 20, 0, 16, 205, 4, 50, 20, 21, 34, 204, 20, 147, 139, 36, 225, 5, 72, 20, 0, 0, 0, 7, 196, 104, 17, 5, 48, 20, 9, 198, 76, 193, 67, 33, 65, 82, 20, 7, 196, 60, 209, 1, 80, 8, 0, 0, 21, 7, 19, 13, 19, 39, 10, 5, 19, 109, 87, 109, 63, 6, 109, 87, 10, 57, 13, 87, 0, 0, 0, 7, 196, 81, 82, 69, 72, 20, 7, 196, 49, 82, 69, 72, 20, 0, 8, 197, 65, 33, 86, 20, 192, 20, 8, 197, 93, 33, 86, 20, 192, 20, 8, 197, 76, 163, 198, 20, 192, 20, 0, 9, 198, 76, 50, 9, 52, 209, 76, 20, 0, 0, 12, 68, 56, 17, 148, 4, 50, 114, 81, 47, 113, 0, 0, 8, 197, 72, 241, 70, 20, 192, 20, 8, 197, 32, 82, 66, 20, 192, 20, 8, 197, 16, 241, 90, 20, 192, 20, 0, 9, 198, 76, 50, 15, 52, 209, 76, 20, 7, 66, 21, 32, 13, 34, 0, 0, 6, 195, 105, 83, 20, 72, 7, 195, 16, 145, 64, 72, 28, 0, 0, 8, 197, 76, 86, 20, 21, 64, 66, 8, 197, 104, 243, 132, 21, 32, 20, 8, 197, 73, 82, 84, 21, 32, 20, 8, 197, 64, 85, 84, 21, 32, 20, 8, 197, 52, 147, 132, 21, 32, 20, 8, 197, 16, 242, 212, 21, 32, 20, 10, 197, 104, 243, 132, 21, 32, 9, 76, 8, 0, 0, 0, 9, 67, 36, 225, 197, 106, 66, 13, 0, 11, 200, 76, 241, 5, 52, 145, 84, 21, 32, 20, 0, 8, 197, 76, 84, 20, 21, 64, 66, 15, 69, 80, 242, 76, 21, 64, 47, 83, 114, 55, 6, 109, 47, 0, 8, 197, 60, 209, 76, 21, 64, 67, 8, 197, 92, 146, 132, 21, 32, 20, 8, 197, 48, 20, 212, 21, 32, 20, 8, 197, 28, 148, 212, 21, 32, 20, 0, 7, 66, 16, 80, 70, 13, 0, 0, 0, 11, 68, 32, 83, 137, 56, 21, 102, 114, 0, 10, 7, 196, 104, 245, 133, 72, 8, 0, 6, 195, 32, 16, 82, 72, 0, 0, 19, 71, 64, 148, 143, 84, 85, 20, 20, 48, 37, 16, 40, 83, 6, 109, 47, 13, 0, 10, 199, 21, 53, 1, 24, 85, 20, 20, 67, 0, 7, 196, 72, 17, 5, 72, 20, 7, 196, 60, 97, 133, 72, 20, 13, 4, 95, 4, 16, 20, 10, 49, 6, 111, 63, 113, 0, 0, 0, 26, 74, 84, 197, 18, 5, 98, 79, 48, 85, 20, 20, 108, 55, 47, 34, 113, 82, 37, 120, 55, 6, 109, 47, 13, 0, 0, 0, 12, 68, 8, 83, 7, 4, 69, 109, 55, 98, 113, 0, 7, 196, 76, 18, 133, 80, 66, 0, 0, 0, 0, 7, 196, 45, 82, 197, 48, 20, 7, 196, 44, 17, 5, 80, 66, 7, 196, 12, 17, 5, 80, 66, 8, 67, 80, 147, 69, 21, 0, 10, 9, 68, 13, 32, 83, 32, 21, 0, 10, 8, 196, 56, 17, 1, 80, 74, 8, 6, 195, 88, 211, 65, 17, 0, 0, 22, 66, 4, 192, 114, 55, 9, 49, 6, 114, 57, 70, 114, 0, 44, 81, 113, 97, 101, 100, 97, 32, 9, 198, 53, 50, 210, 4, 19, 64, 65, 0, 0, 12, 68, 92, 19, 133, 56, 83, 113, 50, 13, 50, 0, 13, 4, 95, 20, 12, 4, 47, 6, 106, 55, 70, 13, 0, 0, 13, 69, 52, 241, 83, 20, 192, 63, 40, 86, 13, 55, 0, 8, 197, 104, 16, 130, 20, 192, 20, 8, 197, 81, 83, 142, 20, 192, 20, 8, 197, 64, 85, 90, 20, 192, 20, 8, 197, 28, 146, 154, 20, 192, 20, 8, 197, 17, 82, 86, 20, 192, 20, 8, 197, 8, 240, 130, 20, 192, 20, 8, 197, 8, 16, 130, 20, 192, 20, 8, 197, 52, 244, 154, 20, 192, 20, 8, 197, 37, 48, 66, 20, 192, 67, 0, 9, 198, 44, 192, 85, 80, 84, 128, 20, 0, 10, 198, 48, 147, 143, 48, 85, 77, 20, 66, 0, 0, 8, 197, 105, 112, 86, 20, 192, 20, 8, 197, 44, 244, 146, 20, 192, 20, 8, 197, 8, 244, 146, 20, 192, 20, 8, 197, 8, 20, 146, 20, 192, 20, 8, 197, 49, 82, 70, 20, 192, 20, 8, 197, 44, 84, 150, 20, 192, 20, 8, 197, 44, 83, 142, 20, 192, 20, 0, 9, 198, 81, 34, 65, 56, 113, 76, 20, 0, 0, 11, 200, 92, 19, 140, 84, 145, 5, 56, 64, 66, 0, 14, 69, 64, 240, 200, 21, 64, 48, 111, 89, 6, 109, 47, 0, 10, 69, 64, 192, 89, 21, 32, 21, 0, 10, 0, 0, 0, 7, 196, 76, 147, 132, 76, 8, 0, 15, 69, 72, 81, 204, 21, 64, 34, 117, 98, 55, 6, 109, 47, 0, 8, 197, 92, 16, 73, 21, 32, 20, 8, 197, 48, 19, 77, 21, 32, 20, 0, 0, 0, 7, 196, 45, 82, 69, 72, 20, 0, 0, 11, 70, 4, 225, 18, 60, 145, 0, 21, 0, 10, 0, 18, 71, 21, 66, 81, 84, 85, 20, 20, 117, 47, 37, 49, 6, 109, 47, 13, 0, 0, 22, 72, 52, 147, 137, 77, 65, 82, 36, 80, 63, 37, 50, 106, 87, 47, 6, 106, 12, 34, 37, 0, 9, 198, 9, 37, 83, 76, 83, 0, 20, 9, 198, 45, 112, 75, 44, 83, 0, 20, 9, 198, 29, 34, 69, 104, 83, 0, 20, 0, 8, 197, 52, 22, 9, 52, 16, 65, 0, 10, 66, 21, 80, 117, 10, 107, 12, 0, 17, 0, 0, 9, 198, 77, 66, 69, 24, 83, 0, 20, 9, 198, 45, 34, 69, 8, 83, 0, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 56, 16, 137, 40, 50, 35, 69, 6, 121, 0, 0, 8, 197, 44, 227, 203, 20, 192, 20, 8, 197, 29, 37, 87, 20, 192, 20, 8, 197, 32, 80, 130, 20, 224, 72, 0, 9, 198, 88, 195, 212, 80, 84, 128, 20, 9, 198, 76, 227, 212, 80, 84, 128, 20, 9, 198, 76, 177, 76, 80, 84, 128, 20, 9, 198, 76, 50, 5, 52, 84, 128, 20, 9, 198, 24, 195, 212, 80, 84, 128, 20, 9, 198, 24, 195, 196, 16, 84, 128, 20, 9, 198, 9, 35, 197, 16, 84, 128, 20, 0, 0, 11, 68, 4, 195, 5, 76, 114, 55, 13, 87, 0, 13, 68, 4, 193, 21, 76, 114, 55, 70, 6, 108, 87, 0, 0, 8, 197, 44, 20, 19, 20, 192, 20, 8, 197, 33, 84, 211, 20, 192, 20, 8, 197, 45, 83, 142, 20, 224, 72, 0, 9, 198, 60, 181, 15, 8, 84, 128, 66, 9, 198, 77, 66, 74, 25, 49, 76, 20, 9, 198, 88, 194, 69, 28, 84, 128, 20, 9, 198, 77, 2, 74, 44, 84, 128, 20, 9, 198, 76, 195, 197, 8, 84, 128, 20, 9, 198, 52, 243, 147, 80, 84, 128, 20, 9, 198, 52, 81, 82, 16, 84, 128, 20, 9, 198, 52, 80, 78, 16, 84, 128, 20, 9, 198, 44, 226, 75, 44, 84, 128, 20, 9, 198, 24, 194, 75, 44, 84, 128, 20, 9, 198, 8, 194, 75, 44, 84, 128, 20, 9, 198, 8, 81, 78, 16, 84, 128, 20, 0, 0, 0, 8, 197, 76, 197, 73, 21, 32, 20, 8, 197, 52, 146, 141, 21, 32, 20, 8, 197, 44, 241, 84, 21, 32, 20, 0, 0, 0, 0, 0, 11, 70, 72, 84, 197, 5, 32, 200, 21, 0, 10, 0, 0, 7, 196, 92, 147, 4, 20, 72, 0, 8, 197, 61, 3, 1, 28, 80, 20, 6, 195, 16, 149, 0, 72, 0, 9, 198, 17, 112, 82, 72, 83, 0, 20, 11, 70, 52, 81, 9, 12, 19, 0, 21, 0, 10, 0, 18, 71, 76, 245, 66, 72, 85, 20, 20, 87, 40, 69, 34, 6, 109, 47, 13, 0, 10, 199, 52, 18, 143, 72, 85, 20, 20, 67, 16, 71, 12, 245, 67, 32, 85, 20, 20, 49, 40, 89, 6, 109, 47, 0, 9, 67, 32, 146, 128, 105, 2, 121, 0, 0, 9, 198, 76, 50, 1, 88, 245, 0, 66, 16, 70, 12, 245, 80, 48, 85, 0, 49, 40, 48, 55, 6, 109, 47, 0, 16, 70, 52, 19, 131, 32, 85, 0, 63, 114, 50, 89, 6, 109, 47, 0, 15, 70, 13, 35, 195, 32, 85, 0, 49, 34, 111, 89, 6, 109, 0, 0, 0, 9, 198, 77, 68, 149, 36, 177, 76, 20, 0, 0, 0, 0, 0, 11, 199, 64, 85, 18, 60, 193, 85, 52, 20, 66, 7, 195, 8, 83, 128, 72, 9, 0, 0, 0, 0, 0, 9, 198, 8, 83, 5, 52, 209, 82, 20, 0, 8, 197, 56, 21, 143, 20, 192, 66, 8, 197, 80, 147, 135, 20, 192, 20, 8, 197, 52, 84, 135, 20, 192, 20, 8, 197, 44, 243, 139, 20, 192, 20, 8, 197, 28, 244, 135, 20, 192, 20, 8, 197, 52, 242, 203, 20, 192, 20, 11, 70, 76, 241, 148, 92, 20, 133, 21, 0, 10, 0, 9, 198, 105, 112, 66, 8, 84, 128, 20, 9, 198, 77, 5, 84, 80, 84, 128, 20, 9, 198, 77, 1, 84, 80, 84, 128, 20, 9, 198, 44, 82, 76, 16, 84, 128, 20, 0, 12, 201, 92, 19, 148, 72, 245, 87, 20, 225, 0, 66, 0, 0, 13, 69, 52, 148, 211, 20, 224, 63, 106, 87, 13, 50, 0, 8, 197, 92, 146, 203, 20, 192, 20, 8, 197, 80, 242, 203, 20, 192, 20, 13, 69, 80, 16, 203, 20, 192, 47, 109, 49, 13, 55, 0, 8, 197, 16, 145, 199, 20, 192, 20, 8, 197, 44, 225, 75, 20, 192, 20, 0, 9, 198, 105, 112, 75, 44, 84, 128, 20, 9, 198, 49, 82, 83, 80, 84, 128, 20, 9, 198, 32, 241, 78, 16, 84, 128, 20, 9, 198, 24, 192, 75, 44, 84, 128, 20, 9, 198, 17, 82, 83, 80, 84, 128, 20, 9, 198, 12, 245, 78, 80, 84, 128, 20, 0, 7, 195, 8, 83, 148, 72, 9, 0, 0, 0, 0, 10, 199, 92, 146, 201, 64, 81, 9, 4, 67, 0, 0, 9, 198, 104, 241, 15, 20, 225, 5, 66, 0, 7, 66, 28, 80, 79, 13, 0, 0, 0, 0, 16, 69, 16, 19, 137, 12, 16, 70, 35, 50, 6, 37, 47, 87, 35, 0, 0, 9, 198, 76, 224, 66, 8, 83, 0, 20, 9, 198, 76, 163, 197, 52, 83, 0, 20, 9, 198, 44, 224, 66, 8, 83, 0, 20, 9, 198, 29, 32, 66, 8, 83, 0, 20, 9, 198, 28, 243, 195, 32, 83, 0, 20, 9, 198, 17, 33, 85, 80, 83, 0, 20, 0, 0, 12, 68, 8, 83, 137, 28, 69, 117, 50, 13, 98, 0, 0, 0, 9, 198, 77, 65, 67, 32, 83, 0, 20, 9, 198, 44, 226, 66, 8, 83, 0, 20, 9, 198, 25, 35, 205, 52, 83, 0, 20, 9, 198, 76, 50, 5, 16, 83, 0, 20, 0, 0, 7, 196, 56, 243, 133, 80, 66, 10, 198, 28, 85, 197, 21, 53, 0, 72, 9, 0, 0, 16, 70, 76, 147, 8, 61, 81, 84, 87, 37, 55, 40, 6, 109, 47, 0, 0, 0, 7, 196, 64, 19, 5, 80, 66, 0, 15, 69, 16, 149, 133, 73, 48, 70, 37, 82, 6, 109, 34, 87, 0, 0, 9, 198, 44, 84, 147, 80, 83, 128, 20, 0, 10, 199, 76, 50, 14, 4, 32, 133, 48, 20, 0, 0, 14, 69, 8, 83, 129, 72, 64, 69, 13, 50, 114, 34, 47, 0, 8, 197, 32, 241, 80, 20, 192, 20, 8, 197, 8, 82, 84, 20, 192, 20, 14, 69, 9, 33, 84, 20, 192, 69, 34, 13, 47, 109, 55, 0, 0, 9, 198, 76, 50, 21, 36, 97, 76, 20, 0, 0, 15, 70, 48, 21, 82, 20, 229, 0, 55, 120, 34, 6, 114, 65, 0, 7, 196, 44, 84, 5, 72, 20, 13, 3, 95, 49, 15, 6, 106, 12, 34, 87, 47, 13, 0, 0, 8, 197, 80, 148, 16, 20, 192, 20, 8, 197, 80, 83, 80, 20, 192, 20, 8, 197, 72, 147, 80, 20, 192, 20, 8, 197, 48, 148, 208, 20, 192, 20, 8, 197, 32, 243, 80, 20, 192, 20, 8, 197, 24, 145, 68, 20, 192, 20, 8, 197, 76, 147, 80, 20, 192, 20, 0, 17, 70, 76, 52, 129, 8, 33, 76, 87, 49, 34, 109, 69, 13, 55, 0, 20, 6, 195, 48, 17, 197, 20, 6, 195, 57, 97, 1, 17, 0, 14, 139, 9, 14, 7, 18, 5, 4, 9, 195, 171, 14, 20, 68, 16, 3, 226, 130, 172, 6, 119, 16, 120, 47, 4, 117, 49, 13, 50, 0, 0, 0, 9, 198, 16, 148, 203, 21, 69, 5, 66, 9, 198, 12, 20, 211, 21, 69, 5, 66, 8, 197, 8, 147, 10, 21, 64, 66, 8, 197, 105, 82, 86, 21, 32, 20, 8, 197, 49, 80, 130, 21, 32, 20, 8, 197, 48, 80, 130, 21, 32, 20, 8, 197, 33, 82, 86, 21, 32, 20, 8, 197, 8, 144, 130, 21, 32, 20, 11, 70, 32, 243, 69, 64, 17, 197, 21, 0, 10, 0, 12, 67, 64, 17, 197, 21, 0, 10, 81, 117, 112, 32, 14, 67, 64, 17, 197, 21, 0, 10, 81, 100, 111, 119, 110, 32, 0, 19, 71, 13, 84, 133, 81, 64, 71, 20, 49, 107, 34, 13, 47, 6, 113, 88, 13, 0, 0, 12, 3, 95, 50, 15, 47, 83, 6, 117, 70, 13, 0, 0, 0, 0, 0, 13, 68, 8, 83, 137, 56, 69, 117, 50, 6, 37, 50, 0, 9, 198, 12, 16, 137, 56, 85, 0, 67, 0, 10, 67, 32, 85, 0, 105, 13, 47, 0, 9, 0, 9, 198, 45, 35, 197, 104, 83, 0, 20, 9, 198, 44, 194, 78, 28, 83, 0, 20, 0, 16, 70, 24, 16, 197, 8, 243, 203, 81, 109, 37, 87, 69, 40, 49, 0, 10, 199, 76, 84, 20, 20, 208, 133, 72, 66, 0, 9, 198, 44, 16, 137, 56, 85, 0, 67, 7, 196, 92, 20, 5, 56, 20, 12, 3, 95, 51, 15, 70, 6, 109, 34, 70, 13, 0, 9, 4, 95, 15, 18, 4, 70, 13, 0, 0, 8, 197, 4, 113, 78, 16, 16, 66, 8, 197, 36, 230, 129, 28, 80, 20, 0, 9, 198, 17, 35, 208, 64, 83, 0, 20, 9, 198, 77, 67, 208, 64, 83, 0, 20, 6, 194, 37, 48, 72, 9, 0, 0, 7, 196, 64, 20, 133, 48, 20, 0, 0, 0, 0, 7, 196, 56, 20, 5, 48, 20, 7, 196, 64, 244, 5, 48, 20, 7, 196, 48, 84, 5, 48, 20, 7, 196, 64, 148, 5, 80, 66, 12, 68, 28, 147, 5, 80, 88, 37, 55, 6, 109, 0, 12, 68, 24, 147, 5, 80, 81, 37, 55, 6, 117, 0, 9, 198, 76, 50, 9, 48, 65, 82, 20, 0, 0, 0, 0, 0, 8, 197, 64, 83, 132, 20, 192, 20, 8, 197, 56, 16, 200, 20, 192, 20, 8, 197, 9, 82, 84, 20, 192, 20, 8, 197, 32, 83, 132, 20, 192, 20, 8, 197, 92, 147, 4, 20, 224, 72, 0, 9, 198, 77, 68, 149, 8, 33, 76, 20, 9, 198, 76, 195, 196, 16, 84, 128, 20, 9, 198, 44, 195, 196, 16, 84, 128, 20, 0, 0, 7, 196, 44, 20, 5, 72, 20, 12, 3, 95, 53, 15, 82, 6, 121, 82, 70, 13, 0, 0, 8, 197, 92, 83, 148, 20, 192, 20, 8, 197, 80, 244, 148, 20, 192, 20, 8, 197, 44, 20, 148, 20, 192, 20, 8, 197, 32, 20, 208, 20, 192, 20, 8, 197, 16, 20, 148, 20, 192, 20, 8, 197, 52, 244, 148, 20, 192, 20, 8, 197, 9, 82, 68, 20, 192, 20, 8, 197, 105, 83, 12, 20, 224, 72, 0, 15, 4, 95, 13, 3, 14, 63, 6, 114, 49, 14, 16, 111, 50, 0, 0, 8, 67, 56, 85, 192, 50, 125, 0, 0, 0, 17, 70, 4, 226, 83, 21, 69, 5, 113, 50, 37, 86, 6, 109, 47, 13, 0, 14, 69, 88, 145, 206, 21, 64, 82, 106, 65, 6, 109, 47, 0, 8, 197, 92, 241, 75, 21, 32, 20, 0, 0, 0, 12, 3, 95, 54, 15, 86, 6, 109, 87, 70, 13, 0, 0, 13, 69, 36, 225, 205, 5, 32, 106, 66, 63, 114, 34, 0, 8, 197, 12, 244, 150, 21, 64, 66, 8, 197, 76, 243, 142, 21, 64, 66, 8, 197, 64, 82, 71, 21, 32, 20, 8, 197, 40, 241, 75, 21, 32, 20, 0, 0, 0, 7, 196, 92, 244, 132, 80, 72, 0, 0, 16, 70, 73, 80, 146, 36, 82, 192, 34, 107, 69, 34, 6, 37, 49, 0, 9, 198, 44, 227, 203, 44, 83, 0, 20, 0, 19, 71, 92, 83, 9, 77, 112, 65, 72, 83, 109, 55, 106, 87, 58, 6, 113, 34, 0, 0, 13, 68, 8, 84, 137, 28, 69, 106, 12, 34, 13, 98, 0, 7, 196, 32, 20, 5, 72, 20, 7, 196, 44, 85, 5, 56, 20, 14, 3, 95, 55, 15, 86, 6, 117, 82, 13, 50, 70, 13, 0, 0, 8, 197, 41, 83, 12, 36, 80, 72, 8, 197, 41, 83, 12, 36, 80, 72, 0, 0, 0, 7, 196, 44, 21, 133, 48, 20, 0, 0, 0, 11, 199, 72, 81, 5, 44, 21, 133, 48, 20, 65, 0, 7, 196, 104, 85, 5, 48, 20, 7, 196, 44, 85, 5, 48, 20, 9, 68, 64, 21, 3, 32, 21, 0, 10, 0, 0, 9, 198, 12, 244, 147, 20, 193, 84, 67, 6, 194, 20, 224, 72, 8, 0, 13, 3, 95, 51, 88, 70, 6, 109, 34, 47, 13, 99, 0, 0, 7, 196, 104, 85, 133, 72, 20, 7, 196, 48, 85, 133, 72, 20, 7, 196, 16, 21, 133, 72, 20, 9, 68, 76, 149, 5, 76, 21, 0, 10, 14, 3, 95, 48, 67, 105, 6, 111, 50, 70, 109, 34, 47, 0, 0, 8, 197, 52, 243, 77, 20, 192, 20, 8, 197, 44, 243, 132, 20, 224, 72, 0, 0, 0, 21, 72, 60, 225, 193, 77, 69, 146, 36, 160, 111, 50, 98, 114, 87, 47, 82, 34, 6, 121, 0, 7, 196, 92, 21, 5, 72, 20, 7, 196, 104, 85, 5, 56, 20, 0, 8, 197, 64, 145, 77, 20, 192, 20, 0, 0, 17, 71, 72, 240, 200, 20, 99, 210, 80, 34, 39, 89, 6, 81, 39, 34, 0, 10, 199, 44, 19, 5, 24, 21, 5, 72, 20, 0, 0, 8, 197, 53, 84, 203, 21, 64, 66, 8, 197, 8, 241, 75, 21, 64, 66, 8, 197, 44, 144, 203, 21, 32, 20, 0, 9, 198, 53, 84, 197, 81, 65, 64, 66, 0, 0, 0, 21, 73, 52, 18, 83, 60, 227, 133, 81, 65, 64, 63, 109, 86, 111, 50, 6, 109, 47, 13, 0, 8, 197, 92, 18, 203, 21, 32, 20, 8, 197, 52, 82, 203, 21, 32, 20, 0, 7, 66, 40, 80, 57, 13, 0, 15, 3, 95, 49, 57, 50, 6, 117, 98, 13, 50, 47, 37, 50, 0, 0, 12, 3, 95, 49, 56, 6, 114, 99, 47, 37, 50, 0, 0, 14, 68, 8, 84, 137, 56, 69, 106, 12, 34, 6, 106, 50, 0, 7, 196, 80, 245, 133, 72, 20, 7, 196, 44, 21, 133, 72, 20, 7, 196, 20, 229, 5, 72, 20, 0, 0, 9, 198, 81, 33, 85, 104, 83, 0, 20, 9, 198, 45, 112, 66, 8, 83, 0, 20, 9, 198, 45, 33, 78, 28, 83, 0, 20, 9, 198, 44, 229, 84, 76, 83, 0, 20, 9, 198, 17, 37, 80, 64, 83, 0, 20, 0, 0, 9, 198, 64, 19, 70, 48, 85, 0, 66, 7, 196, 80, 21, 5, 72, 20, 7, 196, 64, 84, 5, 72, 20, 7, 196, 44, 244, 5, 72, 20, 7, 196, 8, 85, 5, 72, 20, 0, 0, 9, 198, 81, 114, 74, 24, 83, 0, 20, 9, 198, 76, 211, 203, 44, 83, 0, 20, 10, 3, 95, 49, 49, 6, 109, 55, 81, 0, 0, 10, 3, 95, 49, 48, 47, 6, 37, 50, 0, 0, 7, 196, 56, 85, 133, 48, 20, 7, 196, 44, 85, 133, 48, 20, 7, 196, 56, 21, 133, 48, 20, 7, 196, 8, 20, 133, 80, 66, 13, 3, 95, 49, 51, 70, 6, 109, 34, 47, 37, 50, 0, 0, 12, 3, 95, 49, 50, 47, 83, 6, 113, 55, 81, 0, 0, 13, 3, 95, 49, 53, 82, 6, 121, 81, 47, 37, 50, 0, 0, 14, 3, 95, 49, 52, 81, 6, 106, 12, 34, 47, 37, 50, 0, 0, 12, 68, 76, 84, 137, 20, 87, 106, 12, 34, 37, 0, 7, 196, 80, 149, 5, 48, 20, 7, 196, 56, 85, 5, 48, 20, 7, 196, 52, 85, 5, 48, 20, 7, 196, 52, 245, 5, 80, 66, 7, 196, 104, 241, 1, 80, 66, 12, 3, 95, 52, 15, 82, 6, 37, 34, 70, 13, 0, 15, 3, 95, 49, 55, 86, 6, 117, 82, 13, 50, 47, 37, 50, 0, 0, 13, 3, 95, 49, 54, 86, 6, 109, 87, 47, 37, 50, 0, 0, 0, 10, 199, 64, 19, 148, 60, 97, 133, 48, 20, 15, 3, 95, 55, 88, 86, 6, 117, 82, 13, 50, 47, 13, 99, 0, 0, 13, 68, 12, 245, 133, 72, 49, 108, 82, 13, 34, 0, 20, 8, 196, 92, 20, 133, 56, 72, 9, 0, 0, 0, 0, 7, 196, 8, 245, 5, 72, 20, 0, 8, 197, 104, 245, 133, 20, 192, 66, 8, 197, 104, 241, 207, 20, 64, 66, 0, 0, 0, 0, 0, 16, 70, 88, 81, 5, 81, 65, 64, 82, 13, 70, 6, 109, 47, 13, 0, 11, 70, 92, 80, 147, 37, 65, 64, 21, 0, 10, 0, 0, 0, 8, 197, 92, 148, 16, 21, 32, 20, 8, 197, 65, 84, 144, 21, 32, 20, 8, 197, 52, 244, 16, 21, 32, 20, 0, 0, 0, 13, 68, 60, 213, 133, 72, 120, 63, 82, 6, 109, 34, 0, 9, 198, 44, 243, 80, 48, 245, 0, 66, 0, 9, 198, 76, 83, 4, 21, 34, 69, 65, 15, 70, 72, 85, 129, 56, 50, 5, 34, 13, 82, 115, 50, 89, 0, 18, 70, 53, 148, 212, 21, 34, 69, 63, 106, 87, 47, 6, 106, 12, 34, 37, 0, 9, 198, 52, 148, 203, 60, 244, 0, 65, 18, 70, 33, 148, 212, 21, 34, 69, 105, 106, 87, 47, 106, 12, 34, 6, 37, 0, 0, 9, 198, 76, 50, 15, 80, 83, 0, 20, 0, 10, 199, 77, 84, 16, 61, 37, 5, 72, 20, 0, 9, 198, 64, 244, 148, 72, 85, 0, 66, 7, 196, 36, 165, 133, 72, 20, 0, 16, 70, 64, 148, 212, 4, 50, 5, 48, 37, 87, 47, 6, 114, 89, 0, 0, 9, 198, 45, 83, 147, 80, 83, 0, 20, 9, 198, 44, 20, 9, 81, 65, 76, 20, 0, 10, 69, 48, 20, 20, 61, 0, 21, 0, 10, 14, 3, 95, 50, 88, 47, 83, 6, 106, 50, 47, 13, 99, 0, 0, 7, 196, 32, 85, 133, 48, 20, 12, 68, 28, 85, 133, 48, 98, 117, 82, 13, 55, 0, 0, 9, 198, 12, 243, 148, 72, 243, 5, 66, 0, 0, 0, 7, 196, 72, 21, 5, 48, 20, 7, 196, 60, 53, 5, 80, 66, 9, 198, 76, 50, 21, 81, 65, 82, 20, 9, 198, 76, 50, 9, 81, 65, 82, 20, 13, 3, 95, 56, 15, 6, 114, 99, 47, 87, 47, 13, 0, 0, 0, 0, 0, 7, 196, 48, 22, 133, 72, 20, 9, 198, 28, 194, 78, 77, 65, 82, 20, 0, 0, 0, 16, 67, 9, 96, 128, 69, 121, 82, 6, 120, 34, 69, 117, 55, 47, 0, 0, 13, 3, 95, 63, 63, 87, 6, 37, 63, 69, 120, 55, 0, 0, 8, 197, 44, 145, 90, 20, 192, 20, 0, 0, 8, 67, 40, 241, 64, 73, 120, 0, 6, 195, 104, 245, 64, 72, 14, 3, 95, 52, 88, 81, 6, 106, 12, 34, 47, 13, 99, 0, 0, 0, 15, 69, 76, 177, 76, 21, 64, 87, 49, 13, 55, 6, 109, 47, 0, 8, 197, 88, 244, 132, 21, 32, 20, 8, 197, 44, 147, 132, 21, 32, 20, 8, 197, 8, 192, 68, 21, 32, 20, 0, 0, 0, 0, 8, 197, 4, 213, 76, 21, 64, 67, 8, 197, 44, 192, 84, 21, 32, 20, 0, 7, 194, 56, 16, 9, 76, 8, 8, 66, 36, 176, 2, 106, 49, 0, 0, 7, 195, 44, 210, 64, 17, 42, 13, 3, 95, 53, 88, 82, 6, 121, 81, 47, 13, 99, 0, 0, 7, 196, 104, 241, 18, 4, 66, 0, 0, 9, 198, 44, 225, 85, 44, 83, 0, 20, 9, 198, 52, 148, 129, 8, 83, 0, 67, 0, 17, 71, 12, 245, 82, 28, 85, 20, 20, 49, 40, 34, 88, 6, 109, 47, 0, 0, 9, 198, 52, 147, 129, 72, 85, 0, 67, 17, 70, 44, 194, 78, 44, 85, 0, 49, 55, 106, 66, 49, 6, 109, 47, 0, 11, 70, 21, 132, 12, 60, 149, 0, 21, 0, 10, 0, 7, 195, 52, 16, 82, 72, 8, 0, 9, 198, 105, 114, 69, 8, 83, 0, 20, 9, 198, 65, 34, 69, 28, 83, 0, 20, 0, 13, 3, 95, 54, 88, 86, 6, 109, 87, 47, 13, 99, 0, 0, 7, 196, 88, 86, 133, 48, 20, 7, 196, 24, 86, 133, 48, 20, 7, 196, 52, 22, 133, 48, 20, 7, 196, 56, 246, 133, 48, 20, 0, 6, 195, 20, 145, 82, 20, 0, 0, 11, 70, 92, 80, 147, 37, 65, 83, 21, 0, 10, 0, 7, 196, 36, 166, 133, 48, 20, 9, 198, 76, 50, 5, 81, 65, 82, 20, 0, 0, 10, 67, 40, 241, 89, 73, 120, 58, 37, 0, 0, 0, 0, 8, 197, 72, 144, 130, 20, 192, 20, 8, 197, 56, 85, 90, 20, 192, 20, 8, 197, 17, 80, 130, 20, 192, 20, 8, 197, 105, 82, 86, 20, 192, 20, 0, 9, 198, 80, 84, 212, 36, 177, 76, 20, 9, 198, 81, 33, 73, 80, 84, 128, 20, 0, 0, 0, 8, 197, 92, 84, 150, 20, 192, 20, 8, 197, 45, 113, 90, 20, 192, 20, 8, 197, 76, 224, 86, 20, 192, 20, 8, 197, 32, 244, 154, 20, 192, 20, 9, 198, 41, 80, 137, 48, 85, 77, 20, 0, 10, 66, 57, 32, 50, 108, 63, 13, 34, 0, 0, 10, 199, 92, 81, 215, 36, 166, 133, 72, 20, 13, 3, 95, 56, 88, 47, 6, 114, 99, 47, 13, 99, 0, 0, 0, 0, 0, 7, 195, 104, 240, 76, 66, 9, 0, 0, 8, 197, 44, 20, 144, 21, 64, 66, 8, 197, 80, 147, 77, 21, 32, 20, 8, 197, 48, 83, 77, 21, 32, 20, 0, 16, 70, 52, 21, 5, 72, 145, 64, 63, 113, 47, 6, 117, 34, 37, 0, 10, 198, 28, 84, 212, 4, 113, 64, 20, 66, 7, 66, 52, 80, 63, 13, 0, 0, 15, 3, 95, 57, 88, 50, 6, 117, 79, 13, 50, 47, 13, 99, 0, 0, 16, 70, 12, 148, 131, 84, 149, 0, 87, 106, 34, 49, 40, 6, 37, 0, 0, 14, 69, 8, 83, 137, 28, 80, 69, 117, 50, 13, 98, 13, 0, 8, 195, 52, 85, 0, 9, 76, 28, 0, 14, 70, 76, 133, 84, 80, 83, 0, 89, 108, 47, 13, 55, 0, 16, 70, 12, 83, 129, 44, 83, 0, 87, 13, 50, 113, 49, 13, 55, 0, 0, 10, 199, 12, 128, 82, 48, 245, 20, 20, 66, 10, 199, 9, 83, 12, 16, 246, 133, 72, 20, 0, 7, 196, 36, 166, 133, 72, 20, 0, 0, 9, 198, 77, 68, 133, 56, 113, 76, 20, 12, 3, 95, 63, 65, 55, 6, 109, 47, 13, 34, 0, 0, 0, 7, 196, 8, 22, 133, 48, 20, 13, 72, 20, 229, 5, 73, 4, 137, 76, 80, 21, 0, 10, 0, 6, 195, 84, 145, 82, 20, 0, 0, 0, 0, 0, 0, 7, 194, 36, 224, 9, 76, 28, 0, 0, 0, 16, 70, 36, 225, 197, 8, 244, 135, 106, 66, 117, 69, 111, 34, 99, 0, 0, 9, 198, 64, 19, 148, 76, 84, 128, 20, 9, 198, 44, 194, 69, 16, 84, 128, 20, 9, 198, 24, 195, 206, 44, 84, 128, 20, 0, 14, 4, 95, 15, 7, 15, 6, 120, 99, 120, 50, 109, 49, 0, 0, 0, 8, 197, 36, 164, 211, 20, 192, 20, 8, 197, 64, 241, 75, 20, 192, 20, 8, 197, 40, 241, 75, 20, 192, 20, 0, 9, 198, 105, 112, 78, 28, 84, 128, 20, 9, 198, 72, 243, 211, 80, 84, 128, 20, 9, 198, 28, 194, 66, 8, 84, 128, 20, 9, 198, 8, 243, 19, 80, 84, 128, 20, 0, 0, 0, 9, 198, 52, 148, 194, 73, 82, 75, 65, 8, 197, 57, 83, 77, 21, 32, 20, 0, 0, 10, 199, 36, 225, 197, 88, 243, 7, 20, 67, 0, 0, 0, 0, 29, 75, 20, 193, 147, 80, 81, 5, 57, 67, 195, 33, 64, 4, 109, 55, 81, 6, 87, 47, 117, 70, 13, 50, 47, 39, 98, 47, 0, 0, 12, 201, 60, 225, 197, 48, 243, 198, 48, 146, 139, 67, 9, 198, 81, 35, 197, 80, 83, 0, 20, 9, 198, 77, 112, 70, 24, 83, 0, 20, 9, 198, 65, 37, 84, 80, 83, 0, 20, 20, 72, 80, 245, 82, 56, 148, 85, 21, 64, 47, 40, 34, 50, 37, 49, 6, 109, 47, 0, 0, 0, 0, 10, 199, 52, 241, 9, 56, 85, 20, 20, 67, 0, 9, 198, 33, 82, 67, 32, 83, 0, 20, 9, 198, 29, 82, 67, 32, 83, 0, 20, 9, 198, 17, 33, 77, 52, 83, 0, 20, 9, 198, 77, 65, 78, 28, 83, 0, 20, 20, 72, 12, 128, 77, 9, 33, 84, 80, 80, 89, 35, 63, 69, 34, 6, 109, 47, 13, 0, 0, 8, 197, 52, 148, 211, 36, 80, 65, 0, 14, 139, 1, 12, 5, 24, 1, 14, 4, 18, 9, 195, 171, 67, 0, 23, 67, 88, 243, 132, 82, 111, 50, 10, 47, 114, 10, 47, 13, 0, 82, 100, 97, 116, 32, 100, 101, 32, 8, 195, 4, 19, 128, 9, 76, 28, 0, 7, 196, 72, 246, 133, 80, 66, 14, 4, 95, 48, 77, 52, 69, 6, 37, 55, 57, 40, 50, 0, 0, 6, 195, 52, 146, 142, 72, 0, 9, 198, 48, 243, 195, 32, 83, 128, 20, 6, 195, 104, 246, 143, 66, 6, 195, 40, 245, 87, 72, 14, 4, 95, 48, 77, 50, 63, 6, 37, 55, 57, 40, 50, 0, 0, 10, 199, 81, 32, 86, 21, 53, 9, 20, 67, 15, 4, 95, 48, 77, 51, 63, 6, 37, 55, 57, 114, 34, 47, 0, 0, 0, 14, 4, 95, 48, 77, 49, 70, 6, 122, 86, 109, 50, 47, 0, 0, 14, 4, 95, 2, 18, 22, 69, 14, 16, 6, 117, 82, 13, 0, 0, 19, 71, 12, 16, 146, 36, 243, 5, 80, 49, 113, 69, 34, 37, 39, 55, 6, 109, 0, 0, 12, 68, 8, 85, 20, 100, 69, 109, 12, 47, 37, 0, 24, 73, 36, 212, 18, 20, 115, 133, 72, 147, 135, 106, 63, 48, 34, 4, 109, 98, 50, 6, 117, 106, 66, 0, 0, 8, 197, 56, 20, 193, 4, 192, 66, 8, 197, 76, 145, 80, 20, 192, 20, 8, 197, 72, 147, 139, 20, 192, 20, 8, 197, 32, 18, 211, 20, 192, 20, 8, 197, 12, 148, 139, 20, 192, 20, 0, 9, 198, 76, 160, 67, 32, 84, 128, 20, 9, 198, 44, 226, 83, 64, 84, 128, 20, 9, 198, 44, 225, 85, 80, 84, 128, 20, 9, 198, 44, 193, 85, 80, 84, 128, 20, 9, 198, 8, 197, 66, 8, 84, 128, 20, 11, 70, 92, 81, 75, 20, 225, 0, 21, 0, 10, 0, 6, 195, 92, 84, 132, 72, 0, 20, 72, 12, 128, 77, 64, 145, 206, 60, 224, 89, 114, 63, 48, 37, 57, 6, 111, 50, 0, 0, 8, 197, 92, 18, 203, 20, 192, 20, 8, 197, 80, 147, 139, 20, 192, 20, 8, 197, 76, 146, 203, 20, 192, 20, 8, 197, 24, 243, 139, 20, 192, 20, 8, 197, 16, 148, 211, 20, 192, 20, 8, 197, 88, 83, 139, 20, 192, 20, 0, 9, 198, 44, 226, 83, 80, 84, 128, 20, 9, 198, 12, 197, 83, 80, 84, 128, 20, 0, 0, 0, 8, 197, 104, 147, 22, 21, 32, 20, 8, 197, 8, 82, 82, 21, 32, 20, 0, 0, 0, 7, 196, 44, 20, 15, 80, 66, 0, 15, 69, 52, 83, 149, 21, 64, 63, 117, 50, 107, 6, 109, 47, 0, 8, 197, 76, 243, 66, 21, 32, 20, 0, 0, 19, 71, 25, 32, 78, 12, 130, 83, 20, 81, 34, 114, 6, 89, 37, 12, 86, 13, 0, 0, 9, 198, 77, 64, 70, 24, 83, 0, 20, 9, 198, 76, 193, 85, 80, 83, 0, 20, 9, 198, 45, 32, 66, 8, 83, 0, 20, 9, 198, 25, 37, 84, 76, 83, 0, 20, 0, 16, 205, 64, 20, 148, 36, 165, 143, 61, 38, 137, 81, 65, 82, 76, 66, 10, 69, 16, 83, 5, 80, 80, 21, 0, 10, 0, 9, 198, 44, 245, 5, 48, 85, 0, 67, 0, 0, 9, 198, 45, 34, 66, 8, 83, 0, 20, 9, 198, 9, 33, 73, 16, 83, 0, 20, 0, 0, 0, 0, 12, 68, 52, 85, 18, 60, 63, 117, 47, 34, 120, 0, 7, 196, 28, 22, 133, 80, 66, 7, 196, 41, 80, 133, 48, 20, 0, 0, 0, 18, 70, 24, 80, 146, 84, 20, 137, 81, 117, 69, 34, 107, 6, 113, 34, 37, 0, 19, 71, 12, 20, 212, 4, 115, 133, 80, 49, 114, 87, 47, 114, 65, 6, 109, 47, 0, 0, 0, 0, 9, 198, 76, 50, 5, 64, 83, 128, 20, 6, 194, 60, 96, 72, 8, 6, 194, 60, 96, 72, 8, 0, 0, 7, 195, 44, 227, 73, 17, 42, 0, 8, 197, 81, 34, 80, 20, 192, 20, 0, 9, 198, 48, 21, 133, 56, 65, 76, 20, 9, 198, 44, 22, 149, 36, 97, 76, 20, 0, 0, 0, 14, 69, 52, 148, 208, 20, 192, 63, 106, 87, 48, 13, 55, 0, 8, 197, 77, 64, 80, 20, 192, 20, 8, 197, 76, 20, 16, 20, 192, 20, 8, 197, 56, 84, 212, 20, 192, 20, 8, 197, 52, 148, 208, 20, 192, 20, 8, 197, 44, 244, 16, 20, 192, 20, 8, 197, 33, 84, 16, 20, 192, 20, 8, 197, 64, 84, 16, 20, 192, 20, 8, 197, 44, 84, 16, 20, 192, 20, 9, 3, 4, 39, 18, 70, 13, 34, 0, 0, 16, 70, 12, 243, 148, 61, 84, 128, 49, 120, 50, 47, 6, 40, 34, 0, 9, 198, 77, 68, 137, 8, 33, 76, 20, 0, 0, 0, 8, 197, 73, 80, 130, 21, 32, 20, 8, 197, 48, 240, 130, 21, 32, 20, 8, 197, 48, 16, 130, 21, 32, 20, 8, 197, 28, 144, 130, 21, 32, 20, 8, 197, 16, 240, 130, 21, 32, 20, 8, 197, 16, 16, 130, 21, 32, 20, 8, 195, 88, 243, 210, 9, 76, 8, 0, 0, 6, 195, 52, 17, 192, 72, 0, 0, 8, 197, 44, 192, 86, 21, 32, 20, 9, 3, 195, 169, 14, 109, 50, 0, 8, 0, 0, 17, 70, 61, 1, 82, 21, 69, 5, 120, 48, 13, 34, 6, 109, 47, 13, 0, 9, 198, 9, 37, 78, 21, 69, 5, 66, 18, 70, 4, 212, 5, 72, 17, 197, 114, 63, 48, 13, 34, 6, 113, 88, 13, 0, 0, 0, 0, 12, 201, 32, 81, 5, 57, 65, 78, 16, 17, 197, 20, 0, 9, 198, 56, 17, 18, 84, 178, 197, 66, 0, 9, 198, 36, 225, 197, 88, 19, 0, 67, 9, 198, 29, 35, 206, 16, 83, 0, 20, 0, 0, 0, 6, 195, 44, 211, 192, 17, 0, 0, 0, 20, 4, 95, 3, 9, 18, 87, 6, 106, 34, 49, 111, 50, 81, 55, 117, 49, 87, 13, 0, 0, 0, 0, 0, 0, 0, 7, 196, 65, 80, 133, 72, 20, 0, 8, 197, 76, 147, 148, 20, 192, 20, 8, 197, 28, 244, 132, 20, 192, 20, 0, 9, 198, 76, 50, 1, 80, 84, 128, 20, 0, 10, 199, 56, 21, 149, 48, 32, 65, 72, 66, 0, 15, 67, 52, 148, 197, 63, 37, 86, 115, 0, 44, 81, 101, 110, 32, 0, 8, 197, 92, 244, 148, 20, 192, 20, 8, 197, 92, 19, 132, 20, 192, 20, 8, 197, 52, 20, 148, 20, 192, 20, 8, 197, 28, 148, 208, 20, 192, 20, 8, 197, 105, 112, 84, 20, 192, 20, 8, 197, 16, 244, 144, 20, 192, 20, 8, 197, 16, 148, 212, 20, 192, 20, 0, 0, 6, 195, 45, 83, 148, 72, 14, 4, 95, 19, 20, 11, 87, 47, 14, 16, 6, 117, 48, 0, 0, 0, 13, 4, 95, 1, 3, 21, 6, 113, 37, 99, 4, 107, 0, 0, 9, 198, 104, 241, 1, 56, 145, 192, 66, 0, 16, 70, 72, 245, 76, 21, 69, 5, 34, 40, 55, 6, 109, 47, 13, 0, 17, 70, 17, 32, 73, 56, 17, 197, 70, 34, 109, 50, 6, 113, 88, 13, 0, 0, 0, 8, 197, 88, 243, 11, 21, 32, 20, 8, 197, 64, 145, 75, 21, 32, 20, 0, 0, 0, 9, 198, 76, 225, 85, 88, 83, 0, 20, 9, 198, 44, 194, 80, 64, 83, 0, 20, 9, 198, 29, 33, 78, 16, 83, 0, 20, 7, 196, 104, 81, 197, 56, 20, 7, 196, 72, 81, 197, 56, 20, 7, 196, 40, 81, 197, 56, 20, 7, 196, 52, 241, 197, 56, 72, 0, 9, 198, 88, 243, 12, 20, 66, 71, 66, 9, 198, 52, 148, 211, 80, 20, 0, 65, 0, 15, 70, 56, 85, 2, 60, 242, 192, 50, 109, 47, 69, 40, 49, 0, 0, 14, 4, 95, 18, 14, 7, 49, 6, 120, 16, 120, 50, 113, 0, 0, 7, 196, 61, 32, 133, 72, 20, 0, 0, 9, 198, 52, 148, 207, 60, 116, 212, 65, 0, 0, 11, 200, 36, 225, 143, 72, 208, 84, 36, 80, 67, 7, 196, 104, 81, 197, 48, 20, 7, 196, 72, 81, 197, 48, 20, 7, 196, 24, 16, 197, 80, 66, 9, 198, 88, 192, 65, 56, 65, 82, 20, 0, 0, 0, 0, 7, 196, 20, 225, 197, 48, 20, 0, 18, 69, 84, 37, 78, 81, 80, 40, 12, 6, 69, 40, 12, 50, 47, 40, 12, 0, 0, 0, 0, 7, 196, 48, 81, 197, 72, 20, 7, 196, 48, 17, 197, 72, 20, 0, 8, 197, 8, 241, 77, 20, 192, 20, 8, 197, 28, 19, 77, 20, 192, 20, 8, 197, 92, 244, 132, 20, 224, 72, 0, 9, 198, 28, 84, 5, 85, 1, 76, 20, 0, 0, 9, 198, 80, 84, 151, 36, 163, 0, 8, 0, 8, 197, 72, 243, 77, 20, 192, 20, 8, 197, 32, 243, 77, 20, 192, 20, 0, 0, 0, 11, 200, 92, 19, 147, 12, 128, 80, 20, 224, 66, 0, 8, 197, 40, 18, 203, 21, 32, 20, 8, 197, 32, 243, 135, 21, 32, 20, 8, 197, 9, 83, 139, 21, 32, 20, 14, 69, 104, 245, 193, 5, 32, 86, 120, 83, 6, 113, 34, 0, 0, 18, 4, 95, 1, 3, 50, 70, 6, 108, 69, 109, 55, 6, 113, 37, 99, 107, 0, 0, 0, 0, 8, 197, 9, 34, 75, 21, 64, 66, 8, 197, 44, 19, 139, 21, 32, 20, 8, 197, 16, 243, 139, 21, 32, 20, 0, 16, 70, 104, 83, 26, 5, 65, 64, 86, 36, 55, 86, 35, 47, 13, 0, 0, 0, 9, 198, 88, 16, 78, 16, 83, 0, 20, 9, 198, 4, 208, 78, 16, 83, 0, 20, 0, 0, 0, 0, 15, 70, 60, 194, 69, 76, 83, 0, 120, 55, 37, 87, 13, 55, 0, 10, 68, 12, 129, 67, 44, 74, 109, 49, 0, 11, 68, 12, 128, 79, 76, 99, 113, 111, 87, 0, 9, 198, 8, 244, 147, 80, 83, 0, 20, 9, 198, 77, 67, 198, 24, 83, 0, 20, 0, 0, 9, 198, 52, 148, 196, 73, 82, 192, 65, 9, 198, 81, 35, 205, 64, 85, 0, 66, 0, 15, 70, 28, 19, 65, 76, 50, 5, 98, 113, 63, 6, 114, 89, 0, 0, 7, 196, 88, 241, 197, 48, 20, 7, 196, 80, 81, 197, 48, 20, 7, 196, 56, 17, 197, 48, 20, 7, 196, 44, 81, 197, 48, 20, 7, 196, 32, 17, 197, 48, 20, 0, 0, 0, 0, 7, 196, 4, 225, 197, 48, 20, 9, 198, 64, 193, 73, 77, 65, 82, 20, 7, 196, 57, 81, 1, 80, 8, 0, 8, 197, 65, 35, 195, 21, 48, 66, 0, 0, 0, 0, 8, 197, 53, 84, 141, 20, 192, 20, 0, 9, 198, 76, 50, 1, 73, 33, 76, 20, 0, 0, 7, 196, 61, 81, 5, 72, 20, 7, 196, 32, 81, 70, 80, 72, 0, 8, 197, 49, 83, 77, 20, 192, 20, 8, 197, 45, 83, 77, 20, 192, 20, 0, 12, 6, 95, 15, 18, 4, 50, 48, 87, 47, 13, 0, 0, 0, 11, 68, 8, 82, 71, 20, 69, 109, 88, 13, 0, 0, 8, 197, 88, 241, 68, 21, 32, 20, 8, 197, 77, 81, 4, 21, 32, 20, 8, 197, 72, 81, 4, 21, 32, 20, 8, 197, 52, 241, 68, 21, 32, 20, 8, 197, 52, 241, 4, 21, 32, 20, 8, 197, 24, 243, 20, 21, 32, 20, 8, 197, 4, 50, 20, 21, 32, 20, 0, 9, 198, 8, 82, 1, 49, 97, 64, 8, 0, 0, 7, 196, 56, 19, 205, 36, 66, 0, 8, 197, 92, 147, 139, 21, 64, 66, 8, 197, 45, 35, 203, 21, 64, 66, 8, 197, 92, 84, 212, 21, 32, 20, 8, 197, 92, 20, 16, 21, 32, 20, 8, 197, 72, 20, 212, 21, 32, 20, 8, 197, 64, 145, 84, 21, 32, 20, 8, 197, 48, 84, 16, 21, 32, 20, 8, 197, 44, 85, 84, 21, 32, 20, 8, 197, 44, 85, 20, 21, 32, 20, 8, 197, 24, 243, 4, 21, 32, 20, 8, 197, 24, 241, 84, 21, 32, 20, 8, 197, 9, 83, 4, 21, 32, 20, 0, 7, 194, 60, 208, 9, 76, 28, 0, 0, 11, 200, 81, 35, 205, 64, 85, 20, 21, 32, 20, 7, 196, 52, 17, 197, 72, 20, 7, 196, 36, 210, 197, 72, 20, 7, 196, 72, 82, 197, 56, 20, 7, 196, 52, 240, 200, 80, 72, 6, 195, 60, 230, 133, 72, 0, 8, 197, 53, 84, 197, 84, 208, 20, 0, 0, 18, 70, 8, 16, 212, 21, 34, 69, 69, 114, 49, 47, 6, 106, 12, 34, 37, 0, 0, 9, 198, 77, 65, 77, 64, 83, 0, 20, 9, 198, 77, 2, 74, 8, 83, 0, 20, 9, 198, 45, 35, 206, 44, 83, 0, 20, 9, 198, 29, 34, 70, 24, 83, 0, 20, 9, 198, 17, 34, 66, 8, 83, 0, 20, 9, 198, 17, 33, 77, 64, 83, 0, 20, 0, 6, 195, 61, 97, 82, 20, 8, 195, 61, 97, 82, 9, 76, 8, 0, 9, 198, 77, 68, 143, 53, 1, 76, 20, 0, 10, 199, 20, 84, 135, 37, 53, 5, 72, 20, 0, 9, 198, 44, 17, 1, 77, 65, 82, 66, 7, 196, 80, 18, 197, 48, 20, 7, 196, 64, 81, 197, 48, 20, 7, 196, 44, 241, 197, 48, 20, 7, 196, 44, 18, 197, 48, 20, 7, 196, 104, 245, 197, 48, 66, 7, 196, 104, 245, 193, 80, 66, 0, 0, 0, 0, 7, 196, 16, 145, 69, 80, 66, 7, 196, 20, 226, 197, 48, 20, 9, 198, 77, 3, 9, 57, 65, 82, 20, 20, 70, 12, 243, 80, 85, 65, 82, 49, 111, 63, 48, 57, 6, 40, 47, 13, 34, 0, 20, 0, 17, 70, 5, 81, 213, 77, 69, 83, 123, 98, 6, 108, 87, 47, 108, 87, 0, 0, 9, 198, 104, 242, 149, 37, 53, 0, 66, 0, 0, 12, 68, 8, 82, 197, 72, 69, 117, 49, 13, 34, 0, 7, 196, 104, 82, 197, 72, 20, 7, 196, 52, 242, 197, 72, 20, 0, 8, 197, 92, 145, 66, 20, 192, 20, 8, 197, 28, 145, 66, 20, 192, 20, 0, 18, 70, 8, 83, 8, 4, 209, 76, 69, 6, 109, 55, 105, 113, 63, 13, 55, 0, 0, 0, 7, 196, 52, 82, 69, 72, 20, 0, 8, 197, 92, 82, 70, 20, 192, 20, 8, 197, 24, 241, 90, 20, 192, 20, 14, 69, 29, 32, 86, 20, 192, 98, 34, 109, 82, 13, 55, 0, 0, 0, 0, 7, 196, 24, 17, 207, 80, 66, 14, 4, 95, 3, 5, 4, 87, 6, 117, 70, 106, 55, 13, 0, 0, 8, 197, 8, 19, 12, 21, 64, 66, 8, 197, 92, 147, 148, 21, 32, 20, 0, 0, 15, 4, 95, 12, 9, 7, 55, 6, 37, 99, 113, 47, 107, 34, 0, 0, 0, 8, 197, 76, 224, 84, 21, 32, 20, 8, 197, 73, 83, 132, 21, 32, 20, 8, 197, 64, 21, 80, 21, 32, 20, 8, 197, 48, 245, 84, 21, 32, 20, 8, 197, 32, 147, 132, 21, 32, 20, 8, 197, 16, 243, 132, 21, 32, 20, 8, 197, 8, 20, 212, 21, 32, 20, 0, 9, 198, 64, 243, 9, 28, 195, 212, 67, 7, 194, 80, 80, 9, 76, 28, 0, 0, 7, 196, 80, 82, 197, 56, 20, 0, 21, 73, 72, 83, 129, 37, 52, 193, 56, 49, 64, 34, 109, 50, 117, 87, 6, 115, 87, 13, 0, 7, 195, 56, 16, 82, 9, 76, 0, 0, 0, 9, 198, 77, 2, 69, 28, 83, 0, 20, 9, 198, 76, 50, 1, 44, 83, 0, 20, 9, 198, 9, 35, 196, 16, 83, 0, 20, 9, 198, 16, 81, 77, 77, 64, 82, 20, 0, 0, 0, 0, 7, 196, 64, 146, 197, 80, 66, 7, 196, 48, 242, 197, 80, 66, 9, 198, 44, 197, 73, 77, 65, 82, 20, 0, 0, 0, 0, 9, 198, 76, 50, 1, 53, 1, 82, 20, 0, 14, 69, 8, 83, 132, 21, 48, 69, 109, 50, 70, 13, 87, 0, 0, 0, 0, 7, 196, 44, 242, 197, 72, 20, 7, 196, 8, 18, 197, 72, 20, 0, 8, 197, 92, 17, 134, 20, 192, 20, 8, 197, 76, 16, 130, 20, 192, 20, 8, 197, 72, 145, 134, 20, 192, 20, 8, 197, 72, 85, 90, 20, 192, 20, 8, 197, 72, 80, 130, 20, 192, 20, 8, 197, 65, 86, 154, 20, 192, 20, 8, 197, 44, 16, 130, 20, 192, 20, 8, 197, 28, 17, 134, 20, 192, 20, 8, 197, 16, 240, 130, 20, 192, 20, 8, 197, 9, 80, 130, 20, 192, 20, 8, 197, 8, 85, 90, 20, 192, 20, 8, 197, 72, 85, 90, 20, 192, 20, 8, 197, 17, 81, 134, 20, 192, 20, 0, 9, 198, 60, 36, 212, 4, 177, 76, 20, 0, 6, 195, 60, 228, 192, 72, 0, 0, 8, 197, 88, 146, 154, 20, 192, 20, 8, 197, 52, 244, 146, 20, 192, 20, 8, 197, 4, 20, 154, 20, 192, 20, 0, 9, 198, 77, 4, 143, 44, 177, 76, 20, 0, 0, 0, 8, 197, 80, 16, 140, 21, 64, 66, 8, 197, 48, 243, 77, 21, 32, 20, 8, 197, 44, 243, 77, 21, 32, 20, 0, 0, 6, 195, 92, 245, 64, 72, 0, 18, 72, 20, 208, 143, 84, 50, 21, 85, 32, 115, 69, 40, 89, 6, 107, 34, 0, 0, 8, 197, 88, 147, 204, 21, 64, 67, 8, 197, 64, 241, 73, 21, 32, 20, 8, 197, 40, 19, 77, 21, 32, 20, 0, 10, 198, 76, 243, 77, 36, 113, 64, 9, 76, 0, 0, 9, 198, 52, 148, 129, 44, 83, 0, 20, 7, 196, 8, 18, 197, 56, 20, 0, 8, 197, 52, 147, 137, 52, 16, 65, 0, 9, 198, 80, 83, 148, 4, 177, 76, 20, 0, 18, 71, 4, 211, 213, 72, 85, 20, 20, 113, 63, 40, 16, 6, 109, 47, 13, 0, 6, 195, 92, 21, 0, 72, 0, 7, 196, 72, 243, 65, 56, 66, 11, 200, 52, 148, 211, 37, 52, 201, 64, 144, 67, 11, 68, 24, 144, 200, 20, 81, 37, 89, 13, 0, 7, 196, 4, 226, 197, 72, 20, 0, 0, 9, 198, 76, 145, 193, 72, 85, 0, 67, 0, 0, 7, 196, 72, 18, 197, 48, 20, 7, 196, 64, 82, 197, 48, 20, 7, 196, 32, 82, 197, 48, 20, 7, 196, 20, 146, 197, 48, 20, 12, 68, 77, 82, 133, 80, 87, 107, 88, 6, 109, 0, 0, 0, 0, 10, 199, 8, 19, 133, 56, 114, 68, 76, 22, 10, 199, 76, 50, 18, 36, 178, 197, 48, 20, 22, 67, 56, 145, 84, 10, 50, 6, 37, 47, 15, 63, 4, 117, 34, 0, 81, 109, 101, 101, 114, 32, 11, 67, 56, 145, 84, 50, 4, 37, 47, 0, 11, 0, 7, 196, 104, 83, 69, 48, 20, 0, 0, 0, 0, 6, 195, 32, 80, 128, 72, 0, 0, 8, 197, 80, 85, 71, 20, 192, 20, 8, 197, 45, 33, 75, 20, 192, 20, 8, 197, 32, 82, 75, 20, 192, 20, 8, 197, 28, 85, 201, 48, 64, 72, 0, 9, 198, 76, 194, 78, 28, 84, 128, 20, 9, 198, 76, 177, 69, 48, 84, 128, 20, 9, 198, 36, 226, 193, 16, 84, 128, 20, 9, 198, 28, 194, 77, 52, 84, 128, 20, 0, 7, 2, 95, 19, 109, 87, 0, 0, 0, 8, 197, 92, 148, 211, 20, 192, 20, 8, 197, 33, 85, 19, 20, 192, 20, 8, 197, 9, 84, 211, 20, 192, 20, 8, 197, 77, 65, 75, 20, 192, 20, 8, 197, 65, 82, 203, 20, 192, 20, 6, 195, 104, 146, 142, 72, 8, 197, 32, 241, 87, 20, 192, 8, 6, 195, 104, 146, 142, 72, 0, 9, 198, 81, 114, 84, 80, 84, 128, 20, 9, 198, 77, 69, 77, 64, 84, 128, 20, 9, 198, 77, 67, 212, 80, 84, 128, 20, 9, 198, 77, 65, 75, 44, 84, 128, 20, 9, 198, 77, 65, 73, 28, 84, 128, 20, 9, 198, 76, 195, 194, 8, 84, 128, 20, 9, 198, 32, 19, 83, 80, 84, 128, 20, 0, 0, 0, 0, 7, 2, 95, 20, 47, 117, 0, 0, 0, 0, 8, 197, 104, 246, 133, 21, 32, 66, 0, 9, 198, 45, 37, 73, 52, 83, 0, 20, 0, 0, 0, 0, 9, 198, 93, 34, 69, 52, 83, 0, 20, 9, 198, 44, 197, 78, 28, 83, 0, 20, 9, 198, 25, 37, 77, 52, 83, 0, 20, 9, 198, 25, 34, 69, 52, 83, 0, 20, 9, 198, 5, 37, 9, 44, 83, 0, 20, 9, 198, 76, 50, 1, 52, 83, 0, 20, 0, 6, 195, 32, 80, 148, 72, 8, 195, 8, 146, 128, 9, 76, 8, 9, 67, 104, 146, 128, 86, 2, 121, 0, 9, 67, 40, 146, 128, 57, 2, 121, 0, 0, 11, 200, 92, 20, 211, 21, 33, 84, 80, 80, 67, 20, 2, 95, 34, 6, 113, 50, 105, 113, 55, 106, 50, 99, 87, 47, 117, 49, 13, 50, 0, 0, 18, 2, 95, 33, 6, 122, 47, 14, 16, 40, 48, 47, 4, 117, 49, 13, 50, 0, 0, 5, 194, 85, 112, 72, 0, 11, 67, 17, 81, 84, 70, 107, 6, 109, 47, 0, 6, 195, 44, 243, 128, 72, 10, 67, 32, 83, 128, 105, 2, 109, 50, 0, 0, 7, 196, 4, 210, 78, 60, 65, 7, 196, 72, 18, 197, 80, 66, 7, 196, 44, 242, 197, 80, 66, 0, 0, 0, 7, 195, 88, 19, 128, 9, 76, 0, 7, 196, 92, 83, 69, 48, 20, 17, 4, 95, 3, 1, 16, 105, 6, 120, 81, 70, 55, 109, 47, 13, 34, 0, 0, 12, 201, 12, 20, 130, 60, 194, 78, 21, 83, 64, 20, 18, 2, 95, 41, 105, 6, 113, 49, 57, 13, 87, 55, 6, 122, 47, 13, 50, 0, 0, 19, 2, 95, 40, 105, 6, 113, 49, 57, 13, 23, 6, 120, 48, 117, 50, 13, 50, 0, 0, 21, 71, 64, 84, 137, 24, 84, 137, 20, 48, 106, 12, 34, 37, 81, 106, 12, 34, 6, 37, 0, 10, 199, 52, 20, 141, 60, 193, 85, 52, 20, 0, 0, 8, 197, 92, 17, 199, 20, 192, 20, 8, 197, 72, 243, 147, 20, 192, 20, 8, 197, 72, 19, 147, 20, 192, 20, 8, 197, 64, 147, 139, 20, 192, 20, 8, 197, 52, 243, 139, 20, 192, 20, 8, 197, 52, 83, 135, 20, 192, 20, 8, 197, 33, 82, 75, 20, 192, 20, 8, 197, 8, 145, 199, 20, 192, 20, 8, 197, 76, 242, 203, 20, 192, 20, 17, 2, 95, 45, 49, 6, 111, 48, 109, 55, 47, 4, 117, 49, 13, 50, 0, 0, 9, 198, 76, 197, 73, 52, 84, 128, 20, 9, 198, 64, 195, 197, 80, 84, 128, 20, 9, 198, 44, 241, 83, 80, 84, 128, 20, 10, 2, 95, 44, 49, 6, 111, 63, 113, 0, 0, 6, 195, 48, 84, 128, 20, 9, 2, 95, 51, 70, 34, 6, 37, 0, 0, 11, 68, 76, 18, 78, 80, 21, 102, 114, 0, 10, 7, 196, 20, 211, 69, 72, 20, 9, 2, 95, 50, 47, 83, 6, 117, 0, 0, 8, 197, 92, 147, 139, 20, 192, 20, 8, 197, 92, 21, 87, 20, 192, 20, 8, 197, 76, 147, 135, 20, 192, 20, 8, 197, 72, 147, 135, 20, 192, 20, 8, 197, 56, 146, 203, 20, 192, 20, 8, 197, 52, 19, 135, 20, 192, 20, 8, 197, 32, 147, 139, 20, 192, 20, 8, 197, 80, 83, 135, 20, 192, 20, 8, 197, 44, 242, 203, 20, 192, 20, 12, 201, 12, 243, 147, 84, 210, 78, 16, 84, 128, 20, 8, 2, 95, 49, 6, 117, 50, 0, 0, 9, 198, 80, 82, 83, 80, 84, 128, 20, 9, 198, 52, 81, 83, 80, 84, 128, 20, 9, 198, 45, 113, 84, 80, 84, 128, 20, 9, 198, 44, 194, 78, 44, 84, 128, 20, 9, 198, 28, 81, 83, 80, 84, 128, 20, 9, 2, 95, 48, 50, 6, 108, 55, 0, 0, 11, 2, 95, 55, 86, 6, 117, 82, 13, 50, 0, 0, 9, 2, 95, 54, 86, 6, 109, 87, 0, 0, 8, 197, 65, 83, 22, 21, 32, 20, 8, 197, 44, 19, 22, 21, 32, 20, 9, 2, 95, 53, 82, 6, 121, 81, 0, 0, 9, 2, 95, 52, 82, 6, 37, 34, 0, 0, 15, 2, 95, 59, 48, 6, 108, 50, 47, 49, 111, 63, 4, 113, 0, 0, 17, 2, 95, 58, 70, 6, 108, 69, 13, 55, 13, 48, 4, 108, 50, 47, 0, 0, 8, 197, 52, 19, 135, 5, 64, 22, 8, 197, 44, 19, 70, 21, 32, 20, 11, 2, 95, 57, 50, 6, 117, 98, 13, 50, 0, 0, 9, 198, 88, 84, 132, 21, 35, 208, 67, 9, 198, 81, 35, 205, 52, 83, 0, 20, 9, 198, 77, 67, 205, 52, 83, 0, 20, 9, 198, 17, 35, 205, 52, 83, 0, 20, 6, 195, 16, 86, 133, 72, 7, 66, 92, 80, 83, 13, 0, 9, 2, 95, 56, 6, 114, 99, 47, 0, 0, 18, 71, 61, 85, 9, 48, 192, 71, 20, 40, 47, 37, 57, 6, 113, 88, 13, 0, 16, 2, 95, 63, 82, 14, 16, 6, 113, 99, 47, 117, 49, 13, 50, 0, 0, 7, 196, 64, 242, 197, 72, 20, 0, 8, 197, 76, 19, 15, 52, 240, 65, 8, 195, 84, 149, 0, 9, 76, 28, 0, 9, 198, 81, 114, 78, 44, 83, 0, 20, 9, 198, 93, 35, 206, 28, 83, 0, 20, 0, 0, 7, 196, 32, 19, 69, 72, 20, 9, 198, 88, 243, 210, 16, 21, 0, 8, 0, 0, 0, 0, 0, 0, 0, 14, 203, 92, 16, 82, 76, 50, 9, 40, 227, 9, 40, 176, 66, 10, 199, 52, 148, 194, 4, 180, 197, 48, 65, 0, 7, 196, 104, 19, 69, 48, 20, 7, 196, 32, 83, 69, 48, 20, 0, 0, 12, 201, 60, 225, 197, 72, 145, 70, 48, 146, 139, 67, 24, 73, 16, 145, 148, 60, 225, 197, 72, 147, 135, 70, 106, 81, 47, 4, 111, 66, 6, 117, 34, 106, 66, 0, 15, 70, 12, 130, 70, 24, 243, 128, 89, 37, 81, 6, 111, 50, 0, 0, 10, 199, 12, 243, 15, 77, 49, 85, 52, 20, 0, 7, 196, 48, 20, 197, 72, 20, 0, 8, 197, 72, 243, 80, 20, 192, 20, 8, 197, 28, 82, 213, 56, 64, 72, 0, 8, 67, 72, 16, 197, 21, 0, 10, 0, 0, 7, 196, 4, 196, 207, 24, 8, 0, 17, 70, 44, 147, 147, 32, 20, 193, 49, 106, 50, 89, 6, 113, 87, 113, 0, 13, 69, 92, 19, 135, 20, 224, 83, 114, 66, 13, 50, 0, 8, 197, 52, 84, 16, 20, 192, 20, 8, 197, 76, 85, 20, 20, 192, 20, 8, 197, 44, 85, 84, 20, 192, 20, 8, 197, 80, 83, 154, 36, 160, 8, 0, 0, 0, 12, 4, 95, 4, 15, 20, 48, 6, 108, 50, 47, 0, 0, 22, 73, 20, 83, 147, 28, 83, 9, 40, 180, 192, 117, 50, 87, 98, 13, 55, 6, 121, 49, 87, 0, 9, 198, 88, 147, 204, 21, 69, 5, 67, 9, 198, 72, 16, 204, 21, 69, 5, 66, 8, 197, 44, 241, 134, 21, 32, 20, 8, 197, 44, 17, 134, 21, 32, 20, 8, 197, 28, 16, 130, 21, 32, 20, 8, 197, 9, 81, 134, 21, 32, 20, 8, 197, 80, 245, 4, 5, 64, 8, 0, 15, 74, 20, 229, 5, 73, 64, 73, 56, 209, 78, 80, 21, 0, 10, 0, 6, 195, 104, 19, 0, 72, 0, 0, 15, 69, 9, 33, 86, 21, 64, 69, 34, 13, 82, 6, 109, 47, 0, 8, 197, 77, 2, 78, 21, 64, 66, 17, 70, 12, 245, 82, 80, 17, 197, 49, 40, 34, 47, 6, 113, 88, 13, 0, 8, 3, 201, 153, 14, 14, 50, 0, 0, 9, 198, 77, 65, 71, 28, 83, 0, 20, 9, 198, 76, 210, 83, 64, 83, 0, 20, 9, 198, 76, 197, 78, 28, 83, 0, 20, 0, 9, 67, 12, 128, 84, 74, 109, 47, 0, 6, 195, 20, 65, 76, 20, 8, 67, 24, 16, 212, 21, 0, 10, 21, 2, 95, 95, 55, 6, 106, 79, 109, 50, 47, 87, 47, 14, 16, 6, 117, 48, 57, 13, 0, 0, 9, 198, 45, 112, 82, 80, 85, 0, 66, 9, 198, 48, 22, 129, 72, 85, 0, 67, 0, 10, 69, 60, 227, 9, 56, 80, 21, 0, 10, 0, 17, 70, 56, 18, 82, 60, 34, 64, 50, 114, 57, 34, 6, 120, 69, 37, 0, 15, 70, 44, 83, 142, 20, 70, 64, 49, 109, 50, 13, 70, 109, 0, 9, 198, 45, 112, 82, 80, 83, 0, 20, 9, 198, 45, 32, 85, 92, 83, 0, 20, 9, 198, 44, 227, 194, 8, 83, 0, 20, 0, 6, 195, 4, 65, 76, 20, 7, 195, 60, 242, 192, 9, 76, 0, 0, 8, 197, 72, 81, 201, 52, 80, 66, 6, 195, 4, 65, 82, 20, 0, 0, 6, 195, 33, 83, 128, 72, 7, 3, 201, 153, 20, 47, 0, 0, 21, 72, 8, 194, 84, 104, 180, 137, 20, 112, 69, 55, 106, 47, 87, 49, 34, 37, 12, 79, 0, 7, 196, 5, 4, 5, 48, 20, 9, 198, 32, 84, 137, 56, 225, 82, 20, 0, 0, 0, 0, 0, 0, 14, 4, 95, 7, 18, 22, 98, 14, 16, 6, 113, 82, 13, 0, 0, 0, 0, 8, 197, 76, 146, 144, 20, 192, 20, 8, 197, 44, 19, 148, 20, 192, 20, 0, 9, 198, 77, 69, 73, 80, 84, 128, 20, 8, 67, 8, 20, 197, 21, 0, 10, 0, 0, 11, 200, 36, 225, 210, 36, 164, 5, 56, 64, 66, 0, 13, 69, 8, 82, 76, 20, 224, 69, 121, 55, 13, 50, 0, 14, 69, 52, 148, 212, 20, 224, 63, 106, 87, 47, 13, 50, 0, 8, 197, 80, 144, 200, 20, 192, 20, 8, 197, 72, 85, 84, 20, 192, 20, 8, 197, 44, 193, 80, 20, 192, 20, 8, 197, 32, 16, 200, 20, 192, 20, 8, 197, 9, 83, 132, 20, 192, 20, 8, 197, 24, 148, 212, 20, 192, 20, 8, 197, 92, 147, 12, 20, 224, 72, 0, 0, 0, 0, 12, 201, 80, 81, 197, 56, 224, 84, 85, 84, 128, 68, 15, 70, 64, 240, 200, 21, 69, 5, 48, 111, 89, 6, 109, 47, 0, 14, 69, 9, 81, 134, 21, 64, 69, 107, 81, 6, 109, 47, 0, 8, 197, 44, 244, 142, 21, 64, 66, 8, 197, 12, 20, 142, 21, 64, 66, 18, 70, 41, 83, 69, 48, 17, 197, 88, 107, 63, 13, 55, 6, 113, 88, 13, 0, 0, 0, 6, 195, 92, 147, 0, 72, 18, 2, 95, 123, 82, 6, 37, 34, 49, 114, 50, 47, 13, 105, 4, 113, 49, 0, 13, 4, 95, 4, 9, 1, 6, 108, 63, 55, 123, 47, 0, 0, 0, 9, 198, 4, 211, 210, 21, 69, 5, 67, 17, 70, 21, 21, 73, 64, 17, 197, 117, 49, 37, 48, 6, 113, 88, 13, 0, 8, 197, 48, 21, 87, 21, 32, 20, 0, 16, 70, 41, 84, 212, 36, 225, 64, 88, 107, 87, 47, 6, 37, 50, 0, 9, 198, 12, 128, 82, 4, 65, 64, 66, 9, 198, 81, 34, 80, 64, 83, 0, 20, 9, 198, 77, 66, 80, 64, 83, 0, 20, 9, 198, 9, 35, 203, 44, 83, 0, 20, 9, 198, 64, 84, 137, 44, 83, 0, 20, 16, 70, 16, 80, 201, 8, 83, 0, 70, 117, 87, 37, 69, 109, 55, 0, 11, 70, 60, 97, 140, 36, 225, 64, 21, 0, 10, 0, 0, 0, 8, 195, 80, 245, 0, 9, 76, 8, 25, 2, 95, 125, 82, 6, 37, 34, 49, 114, 50, 47, 13, 105, 4, 113, 49, 87, 55, 6, 122, 47, 13, 50, 0, 0, 17, 70, 52, 148, 212, 72, 19, 0, 63, 37, 87, 47, 34, 6, 114, 55, 0, 9, 198, 81, 32, 80, 64, 83, 0, 20, 9, 198, 17, 33, 78, 80, 83, 0, 20, 0, 0, 8, 67, 40, 21, 211, 21, 0, 10, 0, 0, 0, 0, 13, 68, 28, 84, 197, 48, 98, 117, 87, 13, 55, 0, 20, 0, 0, 10, 67, 56, 20, 201, 50, 114, 87, 37, 0, 0, 10, 67, 104, 144, 200, 86, 2, 106, 99, 0, 0, 13, 68, 5, 4, 137, 48, 113, 48, 34, 6, 106, 55, 0, 0, 6, 195, 61, 1, 78, 20, 0, 17, 70, 64, 192, 78, 12, 129, 84, 48, 55, 114, 50, 89, 6, 109, 47, 0, 0, 0, 7, 196, 21, 69, 5, 72, 20, 0, 8, 197, 92, 145, 77, 20, 192, 20, 8, 197, 77, 64, 77, 20, 192, 20, 8, 197, 72, 19, 77, 20, 192, 20, 0, 18, 70, 16, 148, 195, 37, 1, 76, 70, 106, 87, 6, 37, 48, 13, 55, 0, 20, 0, 10, 199, 56, 17, 5, 72, 128, 78, 16, 67, 0, 0, 8, 197, 16, 243, 77, 20, 192, 20, 0, 0, 0, 0, 14, 69, 9, 81, 7, 21, 64, 69, 108, 73, 6, 109, 47, 0, 8, 197, 24, 19, 19, 21, 64, 66, 15, 69, 12, 195, 211, 21, 64, 49, 55, 120, 86, 6, 109, 47, 0, 8, 197, 48, 82, 203, 21, 32, 20, 8, 197, 8, 17, 199, 21, 32, 20, 0, 0, 6, 195, 92, 147, 20, 72, 0, 0, 8, 197, 21, 66, 75, 21, 64, 67, 8, 197, 88, 147, 135, 21, 32, 20, 8, 197, 77, 82, 75, 21, 32, 20, 8, 197, 44, 84, 139, 21, 32, 20, 8, 197, 40, 243, 135, 21, 32, 20, 8, 197, 8, 192, 75, 21, 32, 20, 0, 9, 198, 45, 113, 66, 8, 83, 0, 20, 9, 198, 45, 34, 78, 28, 83, 0, 20, 11, 70, 52, 19, 23, 5, 33, 64, 21, 0, 10, 7, 66, 104, 80, 86, 13, 0, 0, 0, 0, 0, 9, 198, 88, 193, 85, 28, 83, 0, 20, 9, 198, 77, 69, 78, 80, 83, 0, 20, 0, 0, 11, 200, 52, 148, 214, 5, 69, 9, 56, 112, 65, 12, 68, 8, 84, 212, 20, 69, 109, 87, 47, 13, 0, 16, 70, 16, 245, 66, 48, 85, 0, 70, 40, 69, 55, 6, 109, 47, 0, 0, 9, 198, 17, 147, 129, 77, 66, 69, 67, 0, 0, 0, 7, 196, 17, 85, 133, 48, 20, 9, 198, 76, 50, 9, 65, 1, 82, 20, 0, 0, 0, 0, 0, 0, 0, 16, 67, 57, 148, 192, 50, 121, 87, 70, 6, 122, 86, 109, 50, 47, 0, 0, 7, 196, 20, 227, 210, 52, 66, 0, 9, 197, 56, 17, 9, 20, 224, 66, 9, 8, 197, 65, 83, 77, 20, 192, 20, 8, 197, 52, 244, 141, 20, 192, 20, 0, 14, 70, 12, 128, 83, 76, 148, 192, 89, 114, 87, 6, 37, 0, 0, 7, 195, 17, 84, 192, 72, 8, 0, 13, 72, 53, 83, 20, 37, 67, 213, 12, 128, 21, 0, 10, 0, 8, 197, 33, 83, 77, 20, 192, 20, 0, 8, 67, 76, 149, 5, 21, 0, 10, 0, 18, 71, 12, 128, 77, 64, 17, 206, 20, 89, 114, 63, 48, 6, 114, 65, 13, 0, 0, 0, 8, 197, 64, 20, 139, 21, 64, 66, 8, 197, 76, 145, 4, 21, 32, 20, 8, 197, 72, 145, 4, 21, 32, 20, 8, 197, 64, 241, 68, 21, 32, 20, 8, 197, 48, 145, 68, 21, 32, 20, 8, 197, 32, 19, 20, 21, 32, 20, 8, 197, 28, 241, 68, 21, 32, 20, 11, 70, 84, 197, 9, 52, 21, 5, 21, 0, 10, 0, 0, 0, 0, 8, 197, 64, 18, 203, 21, 64, 66, 8, 197, 104, 243, 4, 21, 32, 20, 8, 197, 80, 85, 20, 21, 32, 20, 8, 197, 64, 243, 4, 21, 32, 20, 8, 197, 52, 145, 84, 21, 32, 20, 8, 197, 48, 85, 84, 21, 32, 20, 8, 197, 48, 85, 20, 21, 32, 20, 8, 197, 8, 243, 4, 21, 32, 20, 8, 197, 8, 149, 20, 21, 32, 20, 0, 9, 198, 76, 229, 70, 24, 83, 0, 20, 9, 198, 44, 229, 70, 24, 83, 0, 20, 16, 70, 60, 228, 218, 20, 193, 128, 111, 50, 87, 6, 109, 55, 81, 0, 0, 0, 11, 200, 52, 147, 12, 36, 209, 84, 21, 32, 20, 0, 9, 198, 36, 225, 21, 13, 66, 69, 66, 9, 198, 4, 211, 133, 77, 66, 69, 67, 10, 69, 21, 48, 193, 64, 80, 21, 0, 10, 0, 9, 198, 92, 244, 147, 80, 83, 0, 20, 9, 198, 92, 20, 133, 53, 1, 76, 20, 0, 0, 0, 14, 69, 28, 243, 199, 48, 80, 79, 40, 12, 79, 13, 55, 0, 0, 17, 70, 40, 20, 146, 21, 65, 76, 88, 35, 34, 13, 47, 6, 109, 55, 0, 0, 0, 8, 196, 104, 240, 76, 76, 66, 8, 0, 0, 0, 10, 199, 77, 1, 75, 80, 18, 197, 48, 66, 10, 199, 77, 1, 75, 80, 18, 197, 48, 20, 0, 9, 198, 76, 229, 73, 77, 65, 82, 20, 9, 198, 64, 147, 139, 77, 65, 82, 20, 9, 198, 24, 197, 73, 77, 65, 82, 20, 0, 9, 3, 26, 39, 14, 86, 13, 50, 0, 0, 0, 0, 0, 14, 69, 8, 85, 133, 56, 64, 69, 117, 82, 13, 50, 70, 0, 8, 197, 24, 241, 70, 20, 192, 20, 8, 197, 72, 241, 66, 20, 192, 20, 8, 197, 52, 85, 66, 20, 192, 20, 9, 198, 5, 66, 5, 56, 85, 77, 20, 6, 195, 80, 241, 78, 8, 0, 0, 0, 0, 14, 69, 36, 225, 210, 36, 64, 106, 66, 14, 16, 106, 47, 0, 8, 197, 44, 85, 86, 20, 192, 20, 8, 197, 17, 33, 86, 20, 192, 20, 8, 197, 32, 85, 86, 20, 192, 20, 0, 9, 198, 77, 4, 129, 56, 177, 76, 20, 0, 0, 0, 8, 197, 48, 19, 80, 21, 64, 66, 8, 197, 44, 83, 148, 21, 32, 20, 8, 197, 9, 83, 80, 21, 32, 20, 0, 0, 0, 0, 8, 197, 52, 148, 218, 37, 64, 65, 23, 73, 16, 19, 65, 76, 49, 82, 36, 225, 192, 70, 35, 63, 114, 38, 87, 6, 117, 34, 106, 66, 0, 8, 197, 104, 147, 132, 21, 32, 20, 8, 197, 92, 243, 132, 21, 32, 20, 8, 197, 81, 85, 20, 21, 32, 20, 8, 197, 80, 85, 84, 21, 32, 20, 8, 197, 17, 112, 84, 21, 32, 20, 8, 197, 16, 83, 132, 21, 32, 20, 0, 9, 198, 88, 82, 9, 44, 83, 0, 20, 0, 0, 0, 12, 201, 21, 80, 200, 5, 34, 83, 80, 145, 64, 68, 0, 9, 198, 77, 2, 75, 44, 83, 0, 20, 9, 198, 65, 34, 75, 44, 83, 0, 20, 9, 198, 45, 33, 85, 44, 83, 0, 20, 9, 198, 81, 35, 197, 8, 83, 0, 20, 0, 0, 16, 70, 12, 16, 129, 72, 85, 0, 49, 113, 69, 113, 34, 6, 109, 0, 0, 14, 69, 12, 19, 129, 16, 16, 49, 114, 50, 113, 70, 113, 0, 0, 8, 67, 28, 19, 69, 21, 0, 10, 8, 67, 32, 243, 69, 21, 0, 10, 0, 34, 79, 104, 145, 75, 20, 226, 21, 37, 48, 133, 88, 19, 12, 36, 225, 192, 86, 37, 12, 49, 13, 50, 105, 122, 87, 69, 13, 82, 114, 55, 106, 66, 0, 0, 9, 198, 12, 128, 80, 37, 65, 82, 66, 0, 0, 0, 10, 199, 76, 16, 210, 37, 53, 9, 20, 67, 0, 0, 0, 0, 0, 0, 8, 197, 77, 82, 90, 20, 192, 20, 8, 197, 72, 241, 134, 20, 192, 20, 8, 197, 72, 17, 134, 20, 192, 20, 8, 197, 52, 241, 134, 20, 192, 20, 8, 197, 17, 82, 90, 20, 192, 20, 8, 197, 9, 81, 134, 20, 192, 20, 0, 0, 7, 195, 4, 196, 192, 72, 8, 0, 0, 8, 197, 92, 20, 146, 20, 192, 20, 8, 197, 52, 22, 154, 20, 192, 20, 8, 197, 44, 225, 86, 20, 192, 20, 8, 197, 44, 144, 130, 20, 192, 20, 8, 197, 32, 240, 130, 20, 192, 20, 8, 197, 77, 65, 86, 20, 224, 20, 0, 0, 0, 0, 12, 69, 12, 128, 76, 21, 64, 89, 113, 55, 109, 0, 13, 69, 12, 16, 200, 21, 64, 49, 114, 89, 6, 109, 0, 0, 0, 0, 0, 14, 69, 80, 245, 80, 21, 64, 47, 40, 48, 6, 109, 47, 0, 14, 69, 64, 245, 76, 21, 64, 48, 40, 55, 6, 109, 47, 0, 0, 9, 198, 76, 211, 197, 104, 83, 0, 20, 9, 198, 76, 210, 75, 44, 83, 0, 20, 9, 198, 29, 37, 73, 104, 83, 0, 20, 17, 70, 89, 34, 74, 4, 113, 64, 82, 34, 117, 57, 6, 113, 88, 13, 0, 17, 70, 52, 85, 18, 4, 113, 64, 63, 117, 47, 34, 6, 113, 88, 13, 0, 0, 12, 71, 52, 147, 11, 76, 128, 75, 20, 21, 0, 10, 0, 0, 15, 69, 8, 84, 137, 28, 80, 69, 106, 12, 34, 13, 98, 13, 0, 6, 195, 92, 16, 82, 8, 0, 9, 198, 81, 35, 199, 28, 83, 0, 20, 0, 0, 0, 0, 9, 198, 77, 4, 133, 56, 177, 76, 20, 0, 0, 21, 72, 4, 48, 197, 77, 51, 201, 72, 80, 35, 49, 87, 109, 87, 58, 6, 35, 34, 13, 0, 21, 72, 12, 19, 79, 84, 99, 1, 28, 80, 49, 113, 63, 40, 81, 55, 6, 113, 88, 13, 0, 0, 6, 18, 66, 103, 0, 107, 0, 7, 6, 98, 101, 0, 8, 2, 21, 14, 128, 132, 130, 3, 69, 13, 0, 8, 2, 114, 101, 110, 3, 69, 106, 12, 0, 4, 2, 108, 103, 3, 69, 109, 0, 8, 2, 17, 67, 11, 0, 8, 2, 17, 67, 17, 67, 101, 32, 0, 8, 2, 17, 67, 17, 67, 101, 110, 32, 0, 8, 2, 17, 67, 106, 101, 25, 0, 8, 2, 99, 17, 67, 0, 8, 2, 110, 103, 101, 108, 0, 8, 2, 114, 109, 0, 8, 2, 115, 116, 105, 97, 0, 105, 101, 8, 2, 114, 3, 69, 109, 37, 13, 0, 4, 8, 2, 17, 67, 101, 114, 32, 3, 69, 117, 0, 8, 2, 100, 101, 108, 0, 8, 2, 116, 101, 114, 0, 8, 2, 118, 101, 110, 32, 0, 8, 2, 122, 101, 109, 0, 8, 2, 122, 105, 103, 0, 101, 8, 2, 12, 0, 118, 101, 114, 8, 3, 69, 117, 82, 13, 34, 0, 117, 8, 3, 69, 119, 0, 4, 105, 8, 2, 100, 101, 3, 69, 121, 0, 105, 8, 2, 116, 101, 108, 0, 7, 6, 99, 104, 0, 101, 1, 10, 2, 32, 3, 8, 89, 0, 4, 8, 2, 97, 100, 111, 114, 3, 74, 0, 8, 2, 97, 114, 116, 101, 114, 0, 8, 2, 105, 112, 0, 101, 114, 114, 121, 8, 3, 74, 109, 34, 37, 0, 4, 1, 97, 116, 101, 100, 3, 89, 0, 1, 110, 97, 108, 98, 0, 1, 110, 97, 118, 101, 114, 2, 101, 0, 1, 110, 117, 114, 98, 0, 1, 111, 114, 98, 2, 101, 0, 1, 111, 114, 98, 2, 117, 0, 1, 114, 97, 109, 0, 2, 195, 169, 0, 8, 0, 8, 111, 112, 2, 101, 0, 105, 8, 2, 99, 97, 110, 101, 3, 89, 2, 37, 0, 97, 117, 8, 2, 102, 102, 101, 3, 89, 2, 120, 0, 97, 112, 101, 114, 111, 110, 8, 3, 89, 4, 114, 48, 13, 34, 116, 50, 0, 97, 117, 8, 2, 118, 105, 110, 3, 89, 4, 120, 0, 101, 113, 117, 101, 8, 3, 89, 109, 49, 0, 111, 8, 2, 113, 117, 101, 3, 89, 111, 0, 97, 114, 103, 8, 2, 21, 3, 89, 114, 34, 88, 0, 97, 110, 103, 8, 2, 101, 3, 89, 115, 88, 0, 4, 3, 99, 0, 8, 2, 97, 111, 0, 8, 2, 97, 114, 105, 0, 8, 2, 101, 109, 105, 0, 8, 2, 108, 111, 0, 8, 2, 111, 108, 101, 0, 8, 2, 111, 114, 0, 8, 2, 114, 0, 7, 6, 101, 114, 0, 4, 1, 21, 2, 105, 110, 103, 32, 3, 6, 106, 12, 34, 0, 1, 21, 2, 105, 110, 103, 101, 110, 32, 0, 101, 110, 2, 32, 3, 6, 106, 12, 34, 13, 50, 0, 4, 1, 10, 2, 32, 28, 33, 3, 8, 13, 34, 0, 1, 10, 2, 100, 32, 28, 33, 0, 1, 10, 2, 100, 101, 32, 28, 33, 0, 1, 10, 2, 100, 101, 110, 32, 28, 33, 0, 1, 10, 2, 101, 32, 28, 33, 0, 1, 10, 2, 101, 110, 32, 28, 33, 0, 1, 10, 2, 101, 110, 100, 32, 28, 33, 0, 1, 10, 2, 101, 110, 100, 101, 32, 28, 33, 0, 1, 10, 2, 105, 110, 103, 32, 28, 33, 0, 1, 10, 2, 105, 110, 103, 101, 110, 32, 28, 33, 0, 1, 10, 2, 116, 32, 28, 33, 0, 4, 1, 10, 2, 32, 3, 13, 34, 0, 1, 10, 2, 101, 110, 32, 28, 33, 0, 1, 21, 2, 97, 97, 114, 32, 0, 1, 108, 111, 116, 2, 97, 98, 101, 108, 0, 1, 115, 105, 109, 2, 97, 98, 101, 108, 0, 2, 105, 106, 32, 0, 105, 101, 2, 32, 3, 13, 34, 6, 37, 0, 101, 1, 10, 2, 32, 3, 13, 34, 13, 0, 97, 1, 10, 2, 32, 3, 13, 34, 113, 0, 8, 2, 21, 14, 128, 132, 130, 3, 109, 34, 0, 103, 101, 114, 8, 3, 109, 34, 98, 13, 34, 0, 1, 10, 2, 17, 67, 21, 3, 110, 34, 0, 7, 6, 111, 110, 0, 4, 103, 8, 2, 97, 97, 114, 110, 3, 4, 111, 50, 98, 6, 0, 103, 8, 2, 97, 110, 115, 0, 103, 8, 2, 114, 105, 106, 112, 98, 97, 97, 114, 0, 103, 8, 2, 114, 111, 110, 100, 0, 103, 8, 2, 117, 110, 115, 116, 105, 103, 0, 103, 8, 2, 117, 117, 114, 0, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 4, 111, 50, 98, 13, 0, 100, 101, 114, 8, 2, 21, 14, 128, 132, 133, 3, 6, 111, 50, 70, 13, 34, 0, 8, 2, 116, 101, 21, 14, 128, 132, 130, 3, 111, 50, 0, 97, 97, 110, 8, 2, 21, 14, 128, 132, 133, 3, 111, 50, 6, 113, 50, 0, 116, 8, 2, 21, 14, 128, 132, 131, 3, 111, 50, 47, 0, 100, 101, 114, 8, 3, 111, 50, 70, 13, 34, 0, 4, 103, 101, 8, 2, 100, 105, 101, 114, 116, 3, 111, 50, 98, 13, 0, 103, 101, 8, 2, 108, 111, 111, 102, 0, 103, 101, 8, 2, 108, 117, 107, 0, 103, 101, 8, 2, 109, 97, 107, 0, 103, 101, 8, 2, 110, 97, 100, 101, 0, 103, 101, 8, 2, 114, 105, 101, 102, 0, 103, 101, 8, 2, 118, 97, 108, 0, 7, 6, 114, 101, 0, 4, 8, 2, 99, 101, 110, 116, 3, 34, 13, 0, 8, 2, 99, 101, 112, 116, 0, 8, 2, 99, 108, 97, 109, 0, 8, 2, 103, 101, 101, 114, 0, 8, 2, 103, 101, 114, 101, 110, 0, 8, 2, 115, 101, 114, 118, 101, 32, 0, 8, 2, 99, 111, 114, 100, 3, 34, 36, 6, 0, 8, 2, 99, 101, 112, 116, 105, 101, 102, 3, 34, 117, 0, 112, 114, 101, 2, 115, 97, 105, 108, 108, 3, 34, 117, 48, 34, 117, 0, 7, 6, 116, 101, 0, 103, 101, 110, 8, 2, 14, 128, 132, 133, 3, 47, 6, 117, 98, 13, 50, 0, 4, 8, 2, 103, 101, 108, 105, 106, 107, 14, 128, 132, 130, 3, 47, 13, 0, 8, 2, 103, 101, 109, 111, 101, 116, 14, 128, 132, 130, 0, 8, 2, 103, 111, 101, 100, 0, 8, 2, 104, 117, 105, 0, 8, 2, 107, 101, 101, 114, 0, 8, 2, 107, 111, 114, 116, 0, 8, 2, 108, 101, 117, 114, 0, 8, 2, 108, 111, 111, 114, 0, 8, 2, 109, 101, 101, 114, 0, 8, 2, 109, 105, 100, 100, 0, 8, 2, 110, 97, 0, 8, 2, 110, 101, 101, 114, 0, 8, 2, 114, 101, 99, 104, 116, 0, 8, 2, 115, 97, 109, 0, 8, 2, 118, 101, 101, 108, 0, 8, 2, 118, 101, 114, 103, 101, 101, 102, 14, 128, 132, 130, 0, 8, 2, 118, 111, 111, 114, 115, 99, 104, 105, 106, 110, 0, 8, 2, 118, 111, 114, 0, 8, 2, 118, 114, 101, 100, 0, 8, 2, 119, 101, 114, 107, 0, 114, 117, 103, 8, 2, 14, 128, 132, 133, 3, 47, 13, 34, 6, 108, 99, 0, 119, 101, 101, 103, 8, 2, 14, 128, 132, 134, 3, 47, 13, 83, 6, 117, 99, 0, 7, 6, 97, 0, 99, 104, 1, 109, 2, 105, 110, 3, 2, 113, 89, 0, 102, 102, 105, 99, 104, 8, 3, 2, 114, 81, 37, 89, 0, 105, 114, 101, 2, 32, 3, 6, 109, 12, 34, 13, 0, 105, 114, 2, 32, 3, 6, 109, 34, 0, 4, 1, 21, 2, 100, 101, 32, 3, 6, 113, 0, 1, 21, 2, 116, 97, 32, 0, 2, 116, 111, 114, 32, 0, 97, 2, 17, 67, 32, 0, 97, 2, 114, 100, 32, 0, 114, 105, 115, 2, 32, 3, 6, 113, 34, 106, 87, 0, 114, 105, 115, 115, 101, 110, 2, 32, 3, 6, 113, 34, 106, 87, 13, 50, 0, 97, 110, 8, 2, 21, 14, 128, 132, 131, 3, 6, 113, 50, 0, 98, 101, 108, 1, 21, 2, 32, 3, 6, 113, 69, 13, 55, 0, 98, 101, 108, 101, 1, 21, 2, 32, 3, 6, 113, 69, 13, 55, 13, 0, 103, 101, 2, 32, 24, 3, 6, 113, 88, 13, 0, 4, 110, 116, 1, 21, 2, 32, 3, 6, 114, 50, 47, 0, 110, 116, 1, 21, 2, 101, 32, 0, 110, 116, 1, 21, 2, 101, 110, 32, 0, 110, 116, 1, 21, 2, 101, 114, 32, 0, 105, 108, 108, 101, 2, 32, 3, 6, 114, 57, 13, 0, 105, 108, 108, 101, 115, 2, 32, 3, 6, 114, 57, 13, 87, 0, 103, 110, 101, 1, 21, 2, 32, 3, 6, 114, 65, 13, 0, 102, 8, 2, 17, 67, 21, 14, 128, 132, 130, 3, 6, 114, 81, 0, 1, 17, 67, 21, 21, 2, 32, 3, 8, 113, 0, 103, 101, 115, 2, 32, 14, 128, 128, 129, 3, 87, 0, 105, 8, 2, 109, 97, 98, 101, 108, 3, 109, 0, 4, 3, 113, 0, 1, 116, 2, 98, 108, 101, 97, 117, 0, 97, 0, 97, 1, 122, 2, 109, 32, 0, 101, 0, 97, 114, 1, 21, 2, 32, 14, 128, 128, 131, 3, 113, 34, 0, 97, 114, 100, 1, 21, 2, 32, 14, 128, 128, 132, 3, 113, 34, 47, 0, 4, 97, 105, 3, 113, 57, 0, 121, 0, 103, 101, 2, 32, 28, 17, 3, 113, 98, 13, 0, 4, 2, 17, 67, 25, 3, 114, 0, 2, 120, 0, 4, 1, 98, 2, 98, 121, 3, 117, 0, 105, 1, 100, 2, 115, 121, 0, 105, 108, 1, 109, 3, 117, 106, 55, 0, 4, 117, 3, 123, 0, 117, 119, 0, 7, 6, 98, 0, 1, 98, 3, 0, 97, 97, 114, 1, 10, 2, 32, 14, 128, 128, 132, 3, 8, 69, 113, 34, 0, 97, 114, 101, 1, 10, 2, 32, 14, 128, 128, 132, 3, 8, 69, 113, 34, 13, 0, 8, 111, 2, 115, 116, 97, 107, 3, 48, 0, 115, 2, 32, 24, 3, 48, 87, 0, 3, 69, 0, 105, 106, 2, 122, 111, 110, 100, 3, 69, 2, 37, 0, 105, 110, 110, 101, 110, 8, 2, 14, 128, 132, 134, 3, 69, 6, 106, 50, 13, 50, 0, 117, 117, 114, 116, 8, 2, 21, 21, 14, 128, 132, 133, 3, 69, 6, 107, 34, 47, 0, 111, 118, 101, 110, 8, 2, 14, 128, 132, 133, 3, 69, 6, 120, 82, 13, 50, 0, 105, 106, 8, 2, 17, 67, 21, 14, 128, 132, 131, 3, 69, 6, 121, 0, 117, 105, 116, 101, 110, 8, 2, 14, 128, 132, 134, 3, 69, 6, 122, 47, 13, 50, 0, 114, 97, 110, 100, 8, 3, 69, 34, 6, 114, 50, 70, 0, 97, 97, 110, 3, 69, 113, 50, 0, 7, 6, 99, 0, 4, 3, 49, 0, 107, 0, 111, 2, 110, 99, 101, 114, 116, 3, 49, 2, 111, 0, 111, 110, 103, 114, 101, 115, 8, 3, 49, 111, 50, 98, 34, 6, 109, 87, 0, 111, 97, 99, 104, 3, 49, 120, 74, 0, 4, 2, 101, 3, 87, 0, 2, 105, 0, 2, 121, 0, 4, 105, 1, 21, 2, 101, 101, 108, 3, 89, 0, 105, 1, 21, 2, 101, 117, 115, 0, 105, 1, 21, 2, 101, 117, 122, 0, 105, 1, 21, 2, 195, 171, 0, 105, 2, 97, 0, 105, 2, 111, 0, 7, 6, 100, 0, 1, 100, 3, 0, 4, 2, 115, 116, 3, 47, 0, 116, 0, 106, 3, 47, 57, 0, 115, 2, 32, 24, 3, 47, 87, 0, 3, 70, 0, 4, 101, 8, 2, 103, 101, 101, 110, 3, 70, 13, 0, 101, 8, 2, 122, 101, 108, 102, 0, 106, 8, 3, 73, 0, 7, 6, 101, 0, 117, 109, 1, 115, 117, 109, 21, 2, 32, 3, 4, 117, 108, 63, 0, 4, 1, 21, 2, 114, 101, 110, 100, 101, 32, 3, 6, 106, 0, 1, 21, 2, 114, 101, 110, 100, 101, 110, 32, 0, 101, 1, 21, 2, 114, 32, 0, 101, 1, 21, 2, 114, 100, 32, 0, 101, 1, 21, 2, 114, 100, 101, 32, 0, 101, 1, 21, 2, 114, 100, 101, 110, 32, 0, 101, 1, 21, 2, 114, 116, 32, 0, 4, 110, 116, 1, 21, 2, 32, 3, 6, 109, 50, 47, 0, 110, 116, 1, 21, 2, 101, 32, 0, 110, 116, 1, 21, 2, 101, 110, 32, 0, 110, 116, 1, 21, 2, 101, 114, 32, 0, 110, 116, 1, 21, 2, 101, 114, 101, 32, 0, 110, 116, 1, 21, 2, 115, 116, 32, 0, 110, 116, 1, 21, 2, 115, 116, 101, 32, 0, 110, 116, 1, 103, 97, 0, 108, 1, 21, 2, 32, 3, 6, 109, 55, 0, 115, 1, 21, 2, 32, 14, 128, 208, 130, 3, 6, 109, 87, 0, 115, 115, 101, 110, 1, 21, 2, 32, 14, 128, 208, 133, 3, 6, 109, 87, 13, 50, 0, 4, 101, 1, 21, 2, 29, 32, 3, 6, 117, 0, 101, 1, 21, 2, 32, 0, 108, 101, 1, 10, 2, 32, 3, 6, 117, 55, 13, 0, 108, 101, 110, 1, 21, 2, 32, 3, 6, 117, 55, 13, 50, 0, 117, 109, 2, 32, 28, 17, 3, 6, 117, 108, 63, 0, 97, 2, 32, 3, 6, 117, 113, 0, 117, 114, 1, 21, 2, 32, 3, 6, 119, 34, 0, 117, 122, 101, 1, 105, 2, 32, 3, 6, 119, 86, 13, 0, 117, 122, 101, 114, 1, 105, 2, 32, 3, 6, 119, 86, 13, 34, 0, 117, 122, 101, 114, 101, 1, 105, 2, 32, 3, 6, 119, 86, 13, 34, 13, 0, 117, 115, 1, 105, 2, 32, 3, 6, 119, 87, 0, 117, 115, 116, 1, 105, 2, 32, 3, 6, 119, 87, 47, 0, 117, 115, 116, 101, 1, 105, 2, 32, 3, 6, 119, 87, 47, 13, 0, 97, 117, 2, 32, 3, 6, 120, 0, 105, 116, 1, 116, 105, 2, 32, 3, 6, 121, 47, 0, 110, 1, 10, 2, 101, 32, 28, 33, 14, 128, 129, 131, 3, 8, 13, 50, 13, 0, 110, 1, 10, 2, 101, 110, 32, 28, 33, 14, 128, 129, 132, 3, 8, 13, 50, 13, 50, 0, 110, 1, 10, 2, 116, 32, 28, 33, 14, 128, 129, 131, 3, 8, 13, 50, 47, 0, 4, 108, 1, 10, 2, 32, 28, 33, 3, 8, 13, 55, 0, 108, 1, 10, 2, 100, 101, 32, 28, 33, 0, 108, 1, 10, 2, 100, 101, 110, 32, 28, 33, 0, 108, 1, 10, 2, 101, 32, 28, 33, 0, 108, 1, 10, 2, 101, 110, 32, 28, 33, 0, 108, 1, 10, 2, 101, 110, 100, 32, 28, 33, 0, 108, 1, 10, 2, 105, 110, 103, 32, 28, 33, 0, 108, 1, 10, 2, 105, 110, 103, 101, 110, 32, 28, 33, 0, 108, 1, 10, 2, 116, 32, 28, 33, 0, 4, 1, 10, 2, 109, 101, 110, 116, 3, 13, 0, 1, 10, 2, 110, 105, 115, 115, 101, 110, 32, 0, 1, 17, 67, 10, 2, 32, 14, 128, 208, 129, 0, 1, 17, 67, 17, 65, 25, 2, 32, 14, 128, 129, 129, 0, 1, 103, 105, 2, 32, 12, 14, 128, 208, 129, 0, 1, 106, 17, 65, 25, 2, 32, 14, 128, 128, 129, 0, 1, 108, 101, 2, 32, 12, 14, 128, 208, 129, 0, 1, 114, 101, 2, 32, 12, 14, 128, 208, 129, 0, 1, 115, 2, 99, 111, 110, 100, 0, 1, 115, 2, 99, 117, 117, 114, 0, 2, 32, 0, 110, 100, 101, 1, 10, 2, 32, 14, 128, 128, 129, 0, 117, 105, 108, 108, 101, 3, 13, 6, 107, 0, 195, 175, 2, 12, 3, 13, 10, 106, 0, 114, 101, 115, 1, 21, 2, 32, 14, 128, 208, 132, 3, 13, 34, 6, 109, 87, 0, 114, 101, 115, 115, 101, 110, 1, 21, 2, 32, 14, 128, 192, 135, 3, 13, 34, 6, 109, 87, 13, 50, 0, 4, 110, 1, 10, 2, 32, 14, 128, 208, 130, 3, 13, 50, 0, 110, 1, 17, 67, 17, 65, 25, 2, 32, 14, 128, 129, 130, 0, 110, 1, 100, 110, 97, 2, 32, 14, 128, 128, 130, 0, 110, 1, 106, 17, 65, 25, 2, 32, 14, 128, 128, 130, 0, 110, 1, 108, 101, 2, 32, 12, 14, 128, 208, 130, 0, 110, 1, 108, 108, 2, 32, 14, 128, 128, 131, 0, 110, 1, 114, 101, 2, 32, 12, 14, 128, 208, 130, 0, 110, 100, 101, 110, 1, 10, 2, 32, 14, 128, 128, 130, 0, 116, 116, 101, 110, 1, 21, 2, 32, 14, 128, 128, 131, 0, 110, 100, 1, 10, 2, 32, 3, 13, 50, 70, 0, 110, 115, 1, 10, 2, 32, 14, 128, 192, 131, 3, 13, 50, 87, 0, 108, 105, 106, 107, 115, 1, 10, 3, 13, 55, 13, 49, 87, 0, 108, 100, 1, 10, 2, 32, 3, 13, 55, 70, 0, 109, 1, 10, 2, 32, 3, 13, 63, 0, 4, 115, 1, 17, 67, 17, 65, 25, 2, 32, 14, 128, 129, 130, 3, 13, 87, 0, 115, 1, 21, 2, 32, 28, 33, 0, 115, 1, 106, 21, 2, 32, 0, 4, 2, 114, 3, 106, 12, 0, 101, 2, 114, 0, 4, 1, 99, 2, 110, 116, 114, 117, 109, 3, 109, 0, 1, 100, 105, 2, 110, 116, 0, 1, 115, 101, 114, 112, 2, 110, 116, 0, 2, 17, 67, 25, 0, 2, 114, 116, 115, 15, 0, 2, 120, 0, 120, 112, 111, 115, 105, 116, 105, 101, 8, 3, 109, 49, 87, 48, 120, 86, 6, 37, 47, 87, 37, 0, 1, 10, 2, 110, 17, 66, 21, 3, 110, 0, 4, 1, 29, 3, 117, 0, 1, 99, 111, 114, 112, 2, 100, 117, 0, 8, 112, 2, 110, 105, 98, 101, 108, 0, 101, 0, 100, 101, 110, 3, 117, 70, 13, 50, 0, 3, 118, 0, 117, 3, 119, 0, 97, 117, 3, 120, 0, 105, 2, 12, 3, 121, 0, 101, 117, 119, 3, 124, 0, 7, 6, 102, 0, 1, 102, 3, 0, 3, 81, 0, 7, 6, 103, 0, 4, 105, 1, 21, 2, 101, 117, 115, 3, 88, 0, 105, 1, 21, 2, 101, 117, 122, 0, 4, 3, 98, 0, 103, 0, 101, 110, 101, 114, 2, 97, 97, 108, 3, 98, 4, 117, 50, 13, 34, 0, 4, 101, 2, 98, 105, 101, 100, 3, 98, 13, 0, 101, 2, 115, 112, 114, 101, 107, 0, 101, 2, 118, 97, 108, 0, 101, 8, 2, 21, 14, 128, 132, 130, 0, 101, 108, 105, 106, 107, 8, 3, 98, 13, 55, 121, 49, 0, 105, 1, 105, 108, 101, 114, 2, 101, 117, 3, 98, 37, 57, 0, 101, 8, 2, 114, 17, 67, 3, 98, 109, 0, 4, 101, 8, 2, 118, 101, 110, 3, 98, 117, 0, 101, 8, 2, 118, 101, 114, 0, 101, 8, 2, 118, 105, 110, 103, 0, 101, 101, 8, 0, 101, 117, 8, 3, 98, 119, 0, 1, 115, 3, 99, 0, 7, 6, 104, 0, 1, 17, 67, 2, 25, 3, 0, 3, 105, 0, 101, 114, 105, 110, 110, 8, 3, 105, 2, 109, 34, 106, 50, 0, 101, 114, 115, 101, 110, 8, 3, 105, 6, 109, 34, 87, 13, 50, 0, 101, 114, 8, 2, 101, 110, 3, 105, 106, 12, 34, 0, 101, 114, 8, 2, 21, 14, 128, 132, 131, 3, 105, 109, 34, 0, 101, 105, 100, 1, 10, 2, 32, 14, 128, 128, 132, 3, 105, 121, 47, 0, 7, 6, 105, 0, 4, 101, 1, 100, 2, 32, 3, 6, 37, 0, 101, 1, 103, 2, 32, 0, 101, 1, 109, 2, 32, 0, 101, 1, 112, 2, 32, 0, 101, 2, 17, 67, 101, 32, 0, 101, 2, 17, 67, 101, 110, 32, 0, 101, 2, 17, 67, 101, 114, 32, 0, 101, 2, 17, 67, 101, 114, 101, 32, 0, 101, 2, 17, 67, 106, 101, 29, 32, 0, 101, 2, 17, 67, 115, 116, 101, 32, 0, 101, 2, 17, 67, 116, 106, 101, 29, 32, 0, 101, 2, 29, 0, 101, 2, 114, 100, 32, 0, 101, 2, 114, 101, 110, 32, 0, 98, 101, 108, 1, 21, 2, 32, 3, 6, 37, 69, 13, 55, 0, 98, 101, 108, 101, 1, 21, 2, 32, 3, 6, 37, 69, 13, 55, 13, 0, 110, 110, 8, 2, 21, 14, 128, 132, 130, 3, 6, 106, 0, 110, 8, 2, 17, 67, 21, 14, 128, 132, 130, 3, 6, 106, 50, 0, 115, 116, 1, 21, 2, 32, 3, 6, 106, 87, 47, 0, 115, 116, 101, 110, 1, 21, 2, 32, 3, 6, 106, 87, 47, 13, 50, 0, 115, 109, 101, 1, 21, 2, 32, 3, 6, 106, 87, 63, 13, 0, 4, 106, 1, 21, 2, 110, 32, 3, 6, 121, 0, 106, 2, 32, 0, 106, 2, 101, 32, 0, 106, 2, 101, 110, 0, 106, 2, 116, 106, 101, 29, 0, 103, 101, 1, 21, 2, 32, 14, 128, 208, 131, 3, 8, 13, 98, 13, 0, 103, 101, 114, 1, 21, 2, 32, 3, 8, 13, 98, 13, 34, 0, 103, 101, 114, 101, 1, 21, 2, 32, 3, 8, 13, 98, 13, 34, 13, 0, 103, 101, 110, 1, 21, 2, 32, 3, 8, 13, 98, 13, 50, 0, 103, 115, 116, 1, 21, 2, 32, 3, 8, 13, 98, 87, 47, 0, 103, 115, 116, 101, 1, 21, 2, 32, 3, 8, 13, 98, 87, 47, 13, 0, 103, 1, 21, 2, 32, 14, 128, 208, 130, 3, 8, 13, 99, 0, 99, 117, 115, 1, 10, 2, 32, 3, 8, 37, 49, 108, 87, 0, 4, 99, 97, 1, 10, 2, 32, 3, 8, 37, 49, 113, 0, 107, 97, 1, 10, 2, 32, 0, 4, 99, 111, 1, 10, 2, 32, 3, 8, 37, 49, 120, 0, 107, 111, 1, 10, 2, 32, 0, 115, 99, 104, 1, 21, 2, 32, 3, 8, 37, 87, 0, 115, 99, 104, 101, 1, 21, 2, 32, 3, 8, 37, 87, 13, 0, 99, 105, 1, 10, 2, 32, 3, 8, 37, 87, 37, 0, 4, 3, 37, 0, 2, 99, 104, 101, 32, 0, 101, 0, 101, 117, 122, 101, 2, 32, 3, 37, 57, 6, 119, 86, 13, 0, 101, 117, 122, 101, 114, 2, 32, 3, 37, 57, 6, 119, 86, 13, 34, 0, 101, 117, 122, 101, 114, 101, 2, 32, 3, 37, 57, 6, 119, 86, 13, 34, 13, 0, 101, 117, 115, 2, 32, 3, 37, 57, 6, 119, 87, 0, 101, 117, 115, 116, 2, 32, 3, 37, 57, 6, 119, 87, 47, 0, 101, 117, 115, 116, 101, 2, 32, 3, 37, 57, 6, 119, 87, 47, 13, 0, 101, 117, 119, 3, 37, 58, 0, 111, 2, 110, 97, 103, 101, 3, 37, 111, 0, 101, 101, 3, 37, 117, 0, 4, 2, 17, 67, 25, 3, 106, 0, 2, 120, 0, 106, 2, 12, 3, 121, 0, 7, 6, 106, 0, 3, 57, 0, 111, 117, 2, 114, 110, 97, 3, 88, 40, 0, 7, 6, 107, 0, 1, 107, 3, 0, 3, 49, 0, 111, 110, 105, 110, 103, 8, 3, 49, 6, 120, 50, 106, 66, 0, 111, 107, 107, 101, 114, 101, 108, 3, 49, 111, 49, 13, 34, 6, 109, 55, 0, 97, 108, 101, 8, 2, 110, 100, 101, 3, 49, 113, 55, 6, 109, 0, 111, 110, 105, 110, 103, 105, 110, 8, 3, 49, 120, 50, 106, 98, 6, 106, 50, 0, 7, 6, 108, 0, 1, 108, 3, 0, 3, 55, 0, 105, 106, 107, 1, 10, 2, 32, 14, 128, 128, 132, 3, 55, 13, 49, 0, 105, 106, 107, 101, 1, 10, 2, 32, 14, 128, 128, 133, 3, 55, 13, 49, 13, 0, 105, 106, 107, 101, 114, 1, 10, 2, 32, 14, 128, 128, 134, 3, 55, 13, 49, 13, 34, 0, 105, 106, 107, 101, 114, 101, 1, 10, 2, 32, 14, 128, 128, 135, 3, 55, 13, 49, 13, 34, 13, 0, 105, 106, 107, 101, 110, 1, 10, 2, 32, 14, 128, 128, 134, 3, 55, 13, 49, 13, 50, 0, 105, 106, 107, 115, 116, 1, 10, 2, 32, 14, 128, 128, 134, 3, 55, 13, 49, 87, 47, 0, 105, 106, 107, 115, 116, 101, 1, 10, 2, 32, 14, 128, 128, 135, 3, 55, 13, 49, 87, 47, 13, 0, 105, 106, 107, 104, 101, 105, 100, 1, 10, 2, 32, 14, 128, 128, 136, 3, 55, 13, 49, 105, 121, 47, 0, 97, 110, 103, 101, 8, 2, 21, 14, 128, 132, 133, 3, 55, 35, 66, 13, 0, 97, 97, 110, 1, 10, 2, 32, 14, 128, 128, 132, 3, 55, 113, 50, 0, 111, 122, 101, 1, 21, 2, 32, 14, 128, 128, 132, 3, 55, 120, 86, 13, 0, 111, 122, 101, 110, 1, 21, 2, 32, 14, 128, 128, 133, 3, 55, 120, 86, 13, 50, 0, 111, 111, 115, 1, 21, 2, 32, 14, 128, 128, 132, 3, 55, 120, 87, 0, 111, 111, 103, 1, 21, 2, 32, 3, 55, 120, 99, 0, 7, 6, 109, 0, 1, 109, 3, 0, 3, 63, 0, 105, 8, 2, 115, 21, 3, 63, 2, 106, 0, 105, 115, 8, 2, 103, 117, 110, 3, 63, 2, 106, 87, 0, 4, 105, 115, 8, 2, 99, 111, 109, 109, 14, 128, 132, 131, 3, 63, 6, 106, 87, 0, 105, 115, 8, 2, 100, 97, 14, 128, 132, 131, 0, 105, 115, 8, 2, 103, 21, 14, 128, 132, 131, 0, 105, 115, 8, 2, 103, 101, 21, 14, 128, 132, 131, 0, 105, 115, 8, 2, 105, 110, 21, 14, 128, 132, 131, 0, 105, 115, 8, 2, 107, 108, 101, 117, 14, 128, 132, 131, 0, 105, 115, 8, 2, 108, 105, 101, 112, 14, 128, 132, 131, 0, 105, 115, 8, 2, 108, 111, 14, 128, 132, 131, 0, 105, 115, 8, 2, 116, 17, 65, 0, 105, 115, 118, 101, 114, 8, 2, 21, 3, 63, 6, 106, 87, 81, 13, 34, 0, 101, 101, 8, 2, 21, 14, 128, 132, 131, 3, 63, 6, 117, 0, 101, 110, 117, 2, 32, 3, 63, 13, 50, 107, 0, 4, 105, 115, 8, 2, 97, 110, 17, 67, 3, 63, 37, 86, 0, 105, 115, 8, 2, 195, 168, 0, 97, 110, 97, 103, 101, 109, 101, 110, 116, 3, 63, 113, 50, 106, 73, 63, 13, 50, 47, 0, 7, 6, 110, 0, 1, 110, 3, 0, 4, 3, 50, 0, 2, 103, 28, 19, 0, 2, 107, 28, 19, 0, 4, 97, 2, 116, 117, 114, 3, 50, 2, 113, 0, 97, 2, 118, 105, 103, 0, 97, 8, 2, 112, 111, 108, 17, 65, 0, 97, 8, 2, 118, 111, 108, 103, 21, 0, 97, 112, 111, 108, 101, 111, 110, 3, 50, 2, 113, 48, 120, 55, 13, 57, 111, 50, 0, 97, 8, 2, 114, 99, 3, 50, 2, 114, 0, 97, 114, 99, 105, 8, 2, 115, 3, 50, 2, 114, 34, 87, 106, 0, 105, 101, 117, 119, 115, 8, 2, 21, 14, 128, 132, 134, 3, 50, 6, 37, 58, 87, 0, 4, 97, 8, 2, 17, 67, 21, 21, 14, 128, 132, 130, 3, 50, 6, 113, 0, 97, 8, 2, 17, 67, 21, 24, 0, 97, 110, 111, 8, 2, 21, 14, 128, 132, 132, 3, 50, 6, 113, 50, 120, 0, 105, 115, 1, 21, 21, 2, 32, 14, 128, 128, 131, 3, 50, 106, 87, 0, 105, 115, 101, 110, 1, 21, 21, 2, 32, 14, 128, 128, 133, 3, 50, 106, 87, 13, 50, 0, 4, 97, 8, 2, 100, 101, 114, 3, 50, 113, 0, 97, 8, 2, 116, 105, 111, 110, 0, 97, 8, 2, 118, 114, 0, 97, 116, 117, 117, 114, 8, 3, 50, 113, 47, 6, 107, 34, 0, 4, 97, 8, 2, 17, 67, 11, 3, 50, 114, 0, 97, 8, 2, 99, 104, 116, 0, 111, 111, 114, 100, 8, 2, 21, 14, 128, 132, 133, 3, 50, 120, 34, 70, 0, 106, 3, 65, 0, 4, 2, 107, 3, 66, 0, 103, 0, 7, 6, 111, 0, 110, 8, 2, 21, 14, 128, 132, 130, 3, 2, 111, 50, 0, 118, 101, 114, 8, 2, 21, 14, 128, 132, 132, 3, 4, 120, 82, 13, 34, 0, 101, 2, 29, 32, 3, 6, 40, 0, 105, 114, 2, 32, 3, 6, 83, 113, 34, 0, 112, 8, 2, 21, 21, 14, 128, 132, 130, 3, 6, 111, 48, 0, 4, 111, 2, 17, 67, 32, 3, 6, 120, 0, 111, 2, 29, 0, 112, 8, 2, 101, 114, 97, 3, 6, 120, 48, 0, 112, 101, 110, 8, 2, 21, 14, 128, 132, 132, 3, 6, 120, 48, 13, 50, 0, 112, 101, 110, 105, 110, 103, 115, 8, 2, 14, 128, 132, 136, 3, 6, 120, 48, 13, 50, 106, 66, 87, 0, 111, 110, 3, 6, 120, 50, 0, 1, 17, 67, 21, 21, 2, 32, 3, 8, 120, 0, 98, 115, 99, 2, 117, 3, 39, 48, 87, 49, 0, 4, 101, 3, 40, 0, 117, 1, 99, 2, 112, 117, 0, 117, 1, 100, 2, 98, 108, 117, 0, 117, 1, 114, 116, 2, 118, 97, 105, 108, 0, 117, 2, 99, 104, 101, 32, 0, 117, 2, 114, 97, 103, 101, 0, 117, 1, 116, 2, 114, 3, 40, 12, 0, 101, 105, 3, 40, 57, 0, 117, 118, 101, 2, 114, 116, 117, 3, 40, 82, 109, 0, 117, 99, 104, 2, 101, 110, 32, 3, 40, 89, 0, 4, 105, 1, 99, 2, 102, 102, 117, 3, 83, 114, 0, 105, 1, 108, 112, 2, 116, 0, 4, 2, 17, 67, 25, 3, 111, 0, 2, 120, 0, 112, 8, 2, 116, 105, 111, 110, 3, 111, 48, 0, 111, 2, 114, 3, 112, 0, 4, 3, 120, 0, 1, 114, 112, 2, 103, 114, 97, 109, 0, 2, 114, 0, 111, 0, 111, 105, 3, 120, 57, 0, 111, 115, 116, 8, 2, 21, 14, 128, 132, 132, 3, 120, 87, 47, 0, 4, 117, 3, 123, 0, 117, 119, 0, 7, 6, 112, 0, 1, 112, 3, 0, 3, 48, 0, 97, 114, 97, 99, 104, 2, 117, 116, 3, 48, 4, 113, 34, 113, 89, 0, 111, 108, 105, 116, 105, 101, 8, 2, 21, 3, 48, 120, 55, 6, 37, 47, 87, 37, 0, 111, 108, 105, 116, 105, 101, 107, 8, 3, 48, 120, 55, 37, 47, 6, 37, 49, 0, 4, 104, 2, 25, 3, 81, 0, 104, 8, 0, 114, 111, 103, 114, 97, 109, 109, 97, 1, 21, 2, 32, 14, 128, 128, 135, 3, 120, 98, 34, 114, 63, 63, 35, 0, 7, 6, 113, 0, 4, 3, 49, 0, 117, 1, 21, 2, 101, 101, 114, 0, 117, 1, 21, 2, 101, 114, 101, 110, 32, 0, 117, 101, 1, 21, 2, 32, 0, 117, 3, 49, 82, 0, 7, 6, 114, 0, 114, 3, 16, 34, 0, 4, 3, 34, 0, 1, 17, 65, 2, 17, 65, 0, 1, 17, 67, 2, 17, 65, 0, 101, 118, 97, 110, 99, 104, 3, 34, 13, 82, 115, 50, 89, 0, 101, 99, 104, 101, 114, 99, 104, 3, 34, 13, 89, 109, 34, 89, 0, 111, 117, 116, 101, 3, 34, 40, 47, 13, 0, 7, 6, 115, 0, 2, 115, 3, 0, 101, 108, 1, 10, 2, 32, 3, 8, 87, 13, 55, 0, 101, 108, 101, 110, 1, 10, 2, 32, 3, 8, 87, 13, 55, 13, 50, 0, 4, 1, 17, 65, 2, 17, 65, 3, 86, 0, 2, 98, 0, 2, 100, 0, 4, 3, 87, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 8, 101, 114, 118, 2, 101, 0, 99, 0, 99, 104, 2, 32, 0, 99, 104, 2, 101, 32, 0, 116, 97, 110, 100, 97, 97, 114, 100, 8, 2, 21, 14, 128, 132, 137, 3, 87, 47, 6, 114, 50, 70, 113, 34, 47, 0, 116, 114, 97, 97, 116, 1, 21, 2, 32, 14, 128, 128, 134, 3, 87, 47, 34, 113, 47, 0, 4, 99, 2, 111, 111, 112, 3, 87, 49, 0, 99, 2, 111, 112, 105, 0, 106, 101, 1, 21, 2, 32, 3, 87, 57, 13, 0, 99, 104, 3, 87, 99, 0, 105, 1, 17, 65, 2, 111, 3, 88, 0, 4, 99, 104, 8, 2, 110, 3, 89, 0, 104, 2, 25, 0, 104, 8, 0, 105, 1, 21, 2, 111, 0, 106, 0, 115, 105, 1, 21, 2, 111, 0, 7, 6, 116, 0, 1, 116, 3, 0, 105, 101, 1, 115, 2, 32, 3, 8, 47, 37, 0, 105, 101, 2, 32, 3, 8, 47, 87, 37, 0, 4, 105, 101, 1, 99, 2, 32, 3, 8, 87, 37, 0, 105, 101, 1, 107, 2, 32, 0, 105, 101, 1, 112, 2, 32, 0, 4, 3, 47, 0, 1, 115, 2, 105, 12, 12, 0, 2, 104, 97, 97, 114, 0, 2, 104, 97, 118, 0, 100, 0, 104, 0, 104, 8, 0, 101, 97, 109, 8, 3, 47, 6, 37, 12, 63, 0, 111, 101, 8, 2, 21, 14, 128, 132, 131, 3, 47, 6, 40, 0, 114, 97, 110, 115, 8, 2, 21, 14, 128, 132, 133, 3, 47, 34, 4, 114, 50, 87, 0, 114, 97, 105, 110, 8, 3, 47, 34, 117, 50, 0, 101, 97, 109, 2, 32, 3, 47, 37, 12, 63, 0, 106, 3, 47, 38, 0, 111, 117, 99, 104, 2, 101, 3, 47, 40, 89, 0, 105, 101, 1, 97, 114, 99, 2, 32, 3, 47, 87, 6, 37, 0, 115, 106, 3, 74, 0, 4, 105, 1, 21, 2, 97, 3, 89, 0, 105, 1, 21, 2, 101, 117, 115, 0, 105, 1, 21, 2, 101, 117, 122, 0, 105, 1, 21, 2, 111, 110, 0, 105, 1, 21, 2, 195, 171, 0, 4, 105, 101, 101, 2, 108, 32, 3, 89, 6, 117, 0, 105, 195, 171, 2, 108, 101, 32, 0, 7, 6, 117, 0, 4, 2, 115, 105, 101, 32, 3, 6, 107, 0, 117, 2, 114, 32, 0, 116, 101, 1, 21, 2, 32, 3, 6, 107, 47, 0, 105, 116, 8, 2, 21, 14, 128, 132, 131, 3, 6, 122, 47, 0, 4, 3, 107, 0, 117, 0, 4, 2, 17, 67, 25, 3, 108, 0, 2, 120, 0, 105, 3, 122, 0, 4, 119, 3, 125, 0, 119, 2, 32, 0, 7, 6, 118, 0, 1, 115, 3, 81, 0, 3, 82, 0, 97, 110, 8, 2, 21, 14, 128, 132, 131, 3, 82, 2, 114, 50, 0, 111, 111, 114, 116, 8, 2, 21, 14, 128, 132, 133, 3, 82, 6, 112, 34, 47, 0, 101, 114, 8, 2, 21, 14, 128, 132, 131, 3, 82, 13, 34, 0, 101, 114, 103, 101, 8, 2, 108, 101, 3, 82, 13, 34, 98, 6, 117, 0, 101, 114, 8, 2, 115, 105, 101, 32, 3, 82, 109, 34, 0, 101, 114, 100, 101, 114, 8, 3, 82, 109, 34, 70, 13, 34, 0, 97, 110, 122, 101, 108, 102, 8, 2, 21, 14, 128, 132, 135, 3, 82, 114, 50, 86, 4, 109, 55, 81, 0, 97, 110, 103, 8, 3, 82, 114, 66, 0, 7, 6, 119, 0, 4, 2, 17, 67, 25, 3, 58, 0, 2, 29, 0, 114, 8, 3, 82, 34, 0, 3, 83, 0, 101, 103, 8, 2, 21, 14, 128, 132, 131, 3, 83, 6, 109, 98, 0, 97, 110, 8, 2, 21, 14, 128, 132, 131, 3, 83, 6, 114, 50, 0, 97, 110, 8, 2, 18, 66, 21, 14, 128, 132, 131, 3, 83, 6, 114, 66, 0, 101, 115, 116, 8, 2, 21, 14, 128, 132, 132, 3, 83, 109, 87, 47, 0, 4, 97, 110, 8, 2, 100, 101, 108, 3, 83, 114, 50, 0, 97, 110, 110, 8, 2, 101, 101, 114, 0, 97, 110, 111, 114, 100, 101, 108, 105, 106, 107, 8, 3, 83, 114, 50, 23, 6, 111, 34, 70, 13, 55, 13, 49, 0, 97, 110, 116, 114, 111, 117, 119, 105, 103, 8, 3, 83, 114, 50, 47, 34, 6, 123, 13, 98, 0, 97, 110, 118, 111, 101, 103, 108, 105, 106, 107, 8, 3, 83, 114, 50, 82, 6, 40, 99, 55, 13, 49, 0, 97, 110, 115, 116, 97, 108, 116, 105, 103, 8, 3, 83, 114, 50, 87, 47, 6, 114, 55, 47, 13, 98, 0, 97, 110, 115, 109, 97, 107, 101, 108, 105, 106, 107, 8, 3, 83, 114, 50, 87, 63, 6, 113, 49, 13, 55, 13, 49, 0, 97, 110, 104, 111, 112, 105, 103, 8, 3, 83, 114, 50, 105, 6, 120, 48, 13, 98, 0, 97, 110, 8, 2, 107, 101, 108, 3, 83, 114, 66, 0, 4, 101, 103, 8, 2, 101, 32, 3, 83, 117, 98, 0, 101, 103, 8, 2, 101, 110, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 3, 37, 0, 8, 2, 17, 65, 3, 57, 0, 4, 2, 17, 67, 25, 3, 106, 0, 2, 120, 0, 7, 6, 122, 0, 4, 1, 115, 3, 0, 2, 122, 3, 0, 3, 86, 0, 111, 103, 101, 8, 2, 21, 14, 128, 132, 132, 3, 86, 4, 39, 79, 13, 0, 101, 108, 101, 2, 32, 14, 128, 128, 132, 3, 86, 117, 55, 13, 0, 117, 105, 100, 8, 2, 21, 14, 128, 132, 132, 3, 86, 122, 47, 0, 101, 108, 102, 1, 21, 2, 32, 14, 128, 128, 132, 3, 87, 6, 109, 55, 81, 0, 7, 6, 0, 195, 168, 114, 101, 2, 32, 3, 6, 109, 34, 13, 0, 195, 169, 2, 32, 3, 6, 117, 0, 195, 171, 110, 1, 101, 105, 114, 101, 2, 32, 14, 128, 128, 130, 3, 13, 50, 0, 44, 2, 15, 3, 49, 6, 111, 63, 113, 0, 45, 8, 32, 2, 32, 15, 3, 63, 6, 106, 50, 0, 36, 3, 70, 6, 111, 55, 114, 34, 0, 39, 115, 1, 21, 2, 32, 14, 128, 128, 130, 3, 87, 0, 4, 195, 169, 3, 117, 0, 195, 169, 195, 169, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts41 = FileInMemory_createWithData (21598, reinterpret_cast (&espeakdata_dicts41_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/nl_dict", L"nl"); Collection_addItem (me.peek(), espeakdata_dicts41.transfer()); static unsigned char espeakdata_dicts42_data[4198] = { 0, 4, 0, 0, 246, 12, 0, 0, 0, 0, 0, 7, 195, 52, 83, 128, 72, 8, 0, 0, 5, 65, 4, 118, 0, 0, 0, 0, 0, 6, 65, 8, 69, 115, 0, 0, 0, 0, 0, 6, 65, 12, 87, 115, 0, 0, 0, 0, 0, 6, 65, 16, 70, 115, 0, 0, 0, 6, 195, 76, 147, 128, 76, 0, 0, 0, 0, 16, 4, 95, 48, 67, 15, 105, 6, 123, 50, 70, 51, 13, 70, 106, 0, 0, 6, 195, 76, 147, 133, 76, 0, 6, 65, 24, 113, 81, 0, 0, 0, 0, 0, 6, 65, 28, 79, 115, 0, 0, 0, 6, 195, 44, 19, 128, 76, 0, 0, 6, 65, 32, 105, 120, 0, 0, 0, 0, 15, 1, 35, 50, 123, 63, 63, 13, 51, 47, 113, 66, 50, 0, 27, 0, 6, 65, 36, 108, 0, 14, 5, 193, 36, 72, 28, 0, 14, 1, 37, 48, 51, 6, 122, 87, 6, 113, 50, 47, 0, 27, 0, 7, 1, 38, 119, 12, 79, 0, 0, 0, 6, 65, 40, 57, 115, 0, 0, 0, 11, 1, 42, 87, 93, 35, 51, 50, 106, 0, 27, 0, 9, 1, 43, 48, 55, 123, 87, 0, 27, 0, 6, 65, 44, 49, 120, 0, 0, 0, 0, 14, 1, 47, 87, 49, 51, 119, 87, 47, 51, 13, 49, 0, 27, 0, 6, 65, 48, 113, 55, 0, 0, 0, 0, 0, 6, 65, 52, 113, 63, 0, 0, 6, 195, 52, 83, 147, 8, 7, 195, 52, 83, 147, 72, 8, 0, 0, 0, 10, 5, 95, 48, 1, 14, 4, 122, 79, 0, 6, 65, 56, 113, 50, 0, 0, 0, 0, 0, 0, 10, 1, 61, 35, 51, 55, 108, 49, 0, 27, 0, 0, 0, 13, 1, 64, 49, 51, 111, 55, 55, 117, 55, 81, 117, 0, 6, 65, 64, 48, 115, 0, 0, 0, 0, 0, 6, 65, 68, 49, 124, 0, 0, 0, 0, 0, 6, 65, 72, 114, 51, 0, 0, 0, 6, 195, 8, 193, 64, 76, 0, 0, 6, 65, 76, 113, 87, 0, 0, 0, 0, 0, 6, 65, 80, 47, 115, 0, 0, 0, 11, 70, 12, 243, 148, 36, 229, 69, 21, 0, 10, 6, 195, 52, 81, 192, 76, 0, 0, 0, 0, 0, 0, 6, 65, 88, 82, 115, 0, 0, 0, 0, 0, 22, 1, 92, 119, 63, 82, 113, 50, 70, 47, 15, 87, 49, 51, 119, 87, 47, 51, 13, 49, 0, 27, 14, 65, 92, 70, 6, 119, 69, 12, 113, 55, 4, 82, 115, 0, 0, 0, 15, 1, 94, 87, 107, 51, 49, 123, 63, 81, 55, 113, 49, 87, 0, 0, 0, 17, 4, 95, 49, 77, 49, 6, 113, 47, 15, 47, 6, 124, 87, 13, 50, 0, 7, 65, 96, 113, 49, 87, 0, 0, 21, 4, 95, 49, 77, 50, 6, 115, 50, 15, 63, 6, 107, 55, 55, 108, 38, 4, 122, 50, 0, 0, 0, 0, 6, 195, 8, 194, 82, 76, 0, 0, 0, 0, 7, 65, 104, 87, 113, 47, 0, 0, 6, 194, 5, 64, 72, 8, 0, 0, 0, 0, 0, 0, 0, 8, 197, 45, 83, 142, 21, 64, 76, 0, 0, 0, 7, 196, 32, 17, 4, 20, 72, 0, 0, 0, 0, 0, 0, 0, 7, 195, 32, 244, 192, 72, 8, 0, 0, 15, 69, 77, 148, 212, 20, 208, 87, 109, 87, 47, 6, 115, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 49, 57, 15, 50, 6, 107, 47, 12, 13, 50, 70, 106, 0, 0, 0, 0, 6, 194, 5, 96, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 84, 225, 5, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 20, 227, 128, 72, 8, 15, 4, 95, 49, 56, 15, 6, 117, 47, 12, 13, 50, 70, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 32, 83, 142, 20, 76, 0, 0, 0, 0, 0, 10, 69, 72, 80, 68, 21, 32, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 32, 21, 20, 72, 6, 195, 16, 149, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 49, 49, 15, 6, 113, 55, 55, 113, 82, 47, 106, 0, 0, 0, 0, 8, 66, 21, 32, 4, 114, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 66, 16, 80, 70, 108, 0, 76, 0, 0, 0, 0, 0, 9, 67, 16, 85, 0, 70, 115, 0, 76, 17, 4, 95, 49, 51, 15, 47, 51, 6, 113, 47, 12, 13, 50, 70, 106, 0, 0, 12, 4, 95, 4, 16, 20, 49, 119, 63, 63, 117, 0, 0, 0, 5, 194, 17, 80, 76, 0, 6, 195, 32, 19, 64, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 20, 12, 4, 47, 6, 107, 55, 70, 106, 0, 0, 0, 0, 16, 4, 95, 49, 53, 15, 81, 6, 113, 63, 47, 13, 50, 70, 106, 0, 0, 0, 0, 8, 66, 21, 64, 113, 47, 0, 72, 0, 0, 0, 0, 0, 14, 4, 95, 49, 50, 15, 47, 6, 119, 55, 82, 47, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 49, 55, 15, 87, 6, 109, 47, 12, 13, 50, 70, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 76, 176, 76, 76, 17, 4, 95, 49, 52, 15, 81, 57, 6, 121, 51, 47, 13, 63, 70, 106, 0, 0, 0, 0, 10, 67, 4, 225, 0, 106, 50, 70, 0, 9, 0, 0, 0, 0, 0, 0, 0, 7, 196, 16, 83, 142, 20, 76, 0, 0, 0, 0, 0, 17, 4, 95, 49, 54, 15, 87, 6, 113, 49, 87, 47, 13, 50, 70, 106, 0, 0, 0, 0, 0, 0, 5, 194, 32, 16, 76, 5, 194, 16, 144, 76, 0, 0, 0, 0, 0, 0, 8, 196, 48, 19, 135, 76, 72, 8, 0, 0, 16, 5, 95, 48, 77, 49, 15, 47, 6, 124, 87, 13, 50, 70, 106, 0, 0, 6, 195, 16, 147, 128, 76, 6, 195, 32, 19, 128, 76, 0, 0, 0, 6, 195, 16, 147, 133, 76, 0, 0, 0, 0, 0, 6, 195, 32, 20, 128, 72, 0, 8, 196, 20, 195, 5, 72, 72, 8, 0, 10, 69, 12, 19, 131, 20, 192, 21, 0, 10, 0, 0, 0, 7, 196, 24, 244, 132, 36, 8, 7, 196, 36, 227, 133, 56, 8, 0, 0, 0, 0, 6, 195, 32, 19, 147, 76, 0, 0, 0, 0, 0, 0, 5, 194, 20, 144, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 16, 84, 133, 76, 76, 13, 3, 95, 49, 15, 81, 6, 111, 51, 87, 47, 106, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 40, 81, 192, 57, 114, 107, 0, 76, 0, 12, 3, 95, 50, 15, 6, 117, 50, 70, 51, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 51, 15, 47, 51, 6, 113, 70, 57, 106, 0, 11, 4, 95, 15, 18, 4, 13, 50, 70, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 32, 83, 142, 21, 48, 76, 0, 0, 0, 7, 196, 24, 244, 129, 56, 8, 0, 0, 0, 0, 12, 3, 95, 53, 15, 81, 6, 113, 63, 47, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 54, 15, 89, 6, 113, 47, 12, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 20, 224, 72, 0, 13, 3, 95, 51, 88, 47, 51, 6, 113, 47, 12, 108, 0, 0, 13, 3, 95, 48, 67, 105, 6, 123, 50, 70, 51, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 49, 67, 6, 113, 47, 15, 105, 6, 123, 50, 70, 51, 106, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 49, 57, 50, 6, 107, 47, 12, 13, 50, 0, 0, 12, 3, 95, 49, 56, 6, 117, 47, 12, 13, 50, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 49, 6, 113, 55, 82, 106, 0, 0, 9, 3, 95, 49, 48, 47, 6, 108, 0, 0, 14, 3, 95, 49, 51, 47, 51, 6, 113, 47, 12, 13, 50, 0, 0, 11, 3, 95, 49, 50, 47, 6, 119, 55, 82, 0, 0, 13, 3, 95, 49, 53, 81, 6, 113, 63, 47, 13, 50, 0, 0, 14, 3, 95, 49, 52, 81, 57, 6, 121, 51, 47, 13, 50, 0, 0, 12, 3, 95, 52, 15, 81, 57, 6, 116, 51, 106, 0, 13, 3, 95, 49, 55, 87, 6, 109, 47, 12, 13, 50, 0, 0, 14, 3, 95, 49, 54, 87, 6, 113, 49, 87, 47, 13, 50, 0, 0, 0, 6, 195, 61, 52, 192, 76, 12, 3, 95, 55, 88, 87, 6, 109, 47, 12, 108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 50, 88, 93, 6, 124, 106, 0, 0, 0, 0, 0, 0, 14, 3, 95, 56, 15, 6, 119, 47, 12, 13, 50, 70, 106, 0, 0, 0, 0, 0, 0, 10, 69, 76, 52, 133, 20, 224, 21, 0, 10, 0, 0, 0, 0, 0, 0, 12, 3, 95, 52, 88, 81, 6, 112, 51, 47, 108, 0, 0, 0, 0, 0, 10, 67, 56, 241, 64, 50, 121, 12, 106, 0, 0, 0, 0, 0, 12, 3, 95, 53, 88, 81, 6, 113, 63, 47, 108, 0, 0, 0, 0, 0, 0, 0, 13, 69, 60, 97, 137, 12, 80, 119, 81, 81, 108, 87, 0, 0, 0, 13, 3, 95, 54, 88, 87, 6, 113, 49, 87, 47, 108, 0, 0, 0, 14, 4, 95, 50, 88, 15, 93, 6, 124, 13, 50, 70, 106, 0, 0, 7, 132, 22, 195, 165, 18, 76, 0, 6, 195, 52, 149, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 56, 88, 6, 119, 47, 12, 108, 0, 0, 0, 0, 0, 0, 0, 7, 195, 52, 81, 0, 72, 8, 0, 0, 12, 3, 95, 57, 88, 50, 6, 107, 47, 12, 108, 0, 0, 7, 196, 16, 85, 20, 20, 76, 0, 11, 67, 56, 241, 78, 50, 121, 12, 13, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 36, 224, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 56, 81, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 147, 128, 76, 0, 0, 0, 19, 4, 95, 48, 77, 50, 63, 6, 107, 55, 55, 108, 38, 4, 122, 50, 13, 51, 0, 0, 0, 6, 195, 52, 147, 133, 76, 7, 196, 60, 246, 13, 48, 17, 0, 13, 4, 95, 48, 77, 49, 47, 6, 124, 87, 13, 50, 0, 0, 0, 0, 0, 0, 0, 12, 67, 24, 244, 128, 81, 119, 34, 12, 0, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 52, 144, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 60, 112, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 4, 95, 3, 9, 18, 87, 6, 107, 51, 49, 123, 63, 81, 55, 113, 49, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 1, 3, 21, 118, 6, 49, 123, 47, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 3, 95, 195, 165, 120, 0, 0, 0, 0, 0, 0, 0, 8, 133, 15, 7, 19, 195, 165, 28, 0, 0, 0, 0, 0, 0, 7, 196, 45, 83, 142, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 52, 245, 0, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 60, 208, 72, 28, 0, 0, 0, 0, 0, 0, 0, 6, 195, 61, 97, 82, 28, 0, 0, 7, 2, 195, 165, 120, 0, 14, 6, 130, 195, 165, 72, 28, 0, 0, 0, 0, 0, 7, 131, 16, 195, 165, 72, 28, 0, 0, 0, 0, 0, 0, 0, 5, 130, 195, 169, 43, 0, 0, 0, 0, 0, 15, 4, 95, 3, 5, 4, 87, 6, 115, 70, 107, 55, 55, 106, 0, 0, 0, 0, 0, 0, 0, 7, 132, 2, 195, 184, 18, 76, 7, 132, 6, 195, 184, 18, 8, 5, 130, 195, 188, 43, 0, 0, 0, 0, 8, 133, 22, 195, 165, 18, 5, 76, 0, 0, 0, 0, 0, 9, 67, 44, 243, 64, 49, 119, 63, 0, 7, 195, 76, 243, 64, 72, 8, 0, 0, 0, 0, 6, 195, 16, 83, 64, 76, 0, 0, 0, 0, 0, 0, 8, 133, 22, 195, 165, 18, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 144, 76, 0, 0, 0, 0, 0, 12, 71, 52, 17, 206, 36, 98, 69, 72, 21, 0, 10, 0, 0, 8, 197, 16, 84, 147, 60, 208, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 9, 108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 80, 147, 0, 72, 28, 0, 0, 0, 0, 0, 8, 133, 22, 195, 166, 18, 5, 76, 0, 8, 197, 76, 181, 76, 48, 80, 76, 0, 0, 0, 9, 198, 76, 181, 76, 48, 85, 0, 76, 13, 2, 95, 34, 117, 50, 81, 112, 51, 89, 13, 55, 0, 0, 8, 197, 52, 83, 12, 60, 208, 8, 15, 2, 95, 33, 124, 47, 51, 122, 48, 87, 47, 113, 66, 50, 0, 0, 0, 14, 2, 95, 39, 117, 48, 121, 87, 47, 51, 6, 122, 81, 0, 0, 0, 0, 11, 2, 95, 36, 70, 119, 55, 55, 118, 51, 0, 0, 6, 195, 16, 83, 128, 76, 0, 11, 2, 95, 42, 87, 93, 35, 51, 50, 106, 0, 0, 21, 2, 95, 41, 48, 35, 51, 35, 66, 47, 6, 115, 87, 15, 89, 55, 6, 123, 47, 12, 0, 0, 6, 195, 16, 84, 133, 76, 6, 195, 16, 84, 133, 76, 24, 2, 95, 40, 48, 35, 51, 35, 66, 47, 6, 115, 87, 15, 69, 13, 57, 6, 109, 50, 50, 13, 51, 0, 0, 9, 67, 32, 84, 128, 105, 114, 51, 0, 0, 12, 2, 95, 46, 48, 123, 66, 49, 47, 124, 63, 0, 0, 8, 133, 22, 195, 166, 18, 20, 72, 10, 2, 95, 45, 87, 47, 51, 115, 49, 0, 0, 6, 195, 8, 20, 133, 72, 10, 2, 95, 44, 49, 119, 63, 63, 117, 0, 0, 9, 67, 16, 84, 128, 70, 114, 51, 0, 6, 195, 88, 20, 128, 72, 9, 2, 95, 51, 47, 51, 6, 115, 0, 0, 8, 2, 95, 50, 47, 6, 122, 0, 0, 8, 2, 95, 49, 6, 115, 50, 0, 0, 9, 2, 95, 48, 50, 6, 123, 55, 0, 0, 8, 2, 95, 55, 89, 6, 124, 0, 0, 10, 2, 95, 54, 87, 6, 113, 49, 87, 0, 0, 9, 2, 95, 53, 81, 6, 113, 63, 0, 0, 10, 2, 95, 52, 81, 6, 108, 51, 113, 0, 0, 14, 2, 95, 59, 87, 115, 63, 108, 49, 122, 55, 119, 50, 0, 0, 10, 2, 95, 58, 49, 122, 55, 119, 50, 0, 0, 8, 2, 95, 57, 50, 6, 108, 0, 0, 10, 2, 95, 56, 6, 119, 47, 12, 106, 0, 0, 18, 2, 95, 63, 87, 48, 111, 51, 89, 63, 119, 55, 87, 47, 113, 66, 50, 0, 0, 13, 2, 95, 62, 87, 47, 111, 51, 13, 15, 113, 50, 0, 0, 10, 2, 95, 61, 35, 51, 55, 108, 49, 0, 0, 14, 2, 95, 60, 63, 107, 50, 70, 51, 106, 15, 113, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 88, 147, 0, 76, 6, 195, 16, 81, 192, 76, 28, 2, 95, 91, 82, 6, 113, 50, 87, 47, 51, 106, 15, 105, 6, 118, 49, 115, 48, 35, 51, 35, 66, 47, 6, 115, 87, 0, 0, 0, 0, 6, 195, 36, 178, 197, 72, 5, 194, 88, 144, 76, 0, 6, 195, 8, 18, 192, 8, 15, 2, 95, 95, 123, 50, 70, 35, 51, 89, 47, 51, 13, 49, 0, 0, 0, 25, 2, 95, 93, 105, 6, 129, 51, 106, 15, 105, 6, 118, 49, 115, 48, 35, 51, 35, 66, 47, 6, 115, 87, 0, 0, 22, 2, 95, 92, 119, 63, 82, 113, 50, 70, 47, 15, 87, 49, 51, 119, 87, 47, 51, 13, 49, 0, 0, 0, 0, 0, 23, 2, 95, 96, 6, 119, 63, 82, 113, 50, 70, 47, 15, 117, 48, 121, 87, 47, 51, 6, 122, 81, 0, 0, 6, 195, 33, 83, 128, 76, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 7, 18, 22, 79, 51, 6, 118, 82, 108, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 4, 9, 1, 47, 51, 6, 115, 63, 117, 0, 0, 0, 0, 0, 0, 7, 196, 8, 194, 84, 80, 76, 0, 0, 0, 11, 70, 24, 148, 133, 24, 246, 0, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 7, 131, 19, 195, 165, 72, 8, 0, 10, 4, 95, 35, 48, 57, 47, 118, 69, 0, 0, 0, 0, 0, 0, 8, 196, 21, 69, 5, 72, 72, 8, 0, 0, 0, 7, 195, 25, 32, 64, 72, 8, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 35, 51, 50, 63, 113, 55, 55, 119, 63, 51, 122, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 33, 98, 83, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 16, 148, 211, 20, 76, 0, 6, 195, 85, 65, 78, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 48, 241, 64, 55, 122, 0, 41, 0, 0, 0, 0, 7, 195, 76, 19, 84, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 76, 149, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 164, 0, 2, 17, 67, 17, 67, 3, 113, 0, 3, 114, 0, 7, 6, 195, 165, 0, 2, 17, 67, 17, 67, 3, 119, 0, 3, 120, 0, 101, 3, 120, 106, 0, 7, 6, 195, 166, 0, 2, 17, 67, 17, 67, 3, 35, 0, 3, 114, 0, 2, 114, 3, 116, 0, 7, 6, 195, 182, 0, 2, 17, 67, 17, 67, 3, 111, 0, 3, 112, 0, 7, 6, 195, 184, 0, 2, 17, 67, 17, 67, 3, 111, 0, 3, 112, 0, 121, 3, 129, 0, 7, 6, 97, 0, 4, 2, 17, 67, 3, 35, 0, 101, 2, 17, 67, 17, 67, 0, 101, 3, 116, 0, 4, 2, 17, 67, 17, 67, 3, 117, 0, 2, 32, 0, 3, 118, 0, 97, 2, 17, 67, 17, 67, 3, 119, 0, 97, 3, 120, 0, 105, 3, 125, 0, 117, 3, 130, 0, 7, 6, 98, 0, 3, 69, 0, 98, 3, 69, 12, 0, 101, 8, 2, 21, 3, 69, 13, 0, 7, 6, 99, 0, 3, 49, 0, 99, 3, 49, 12, 0, 4, 2, 101, 105, 3, 87, 0, 2, 105, 0, 2, 121, 0, 2, 195, 184, 121, 0, 8, 2, 101, 0, 104, 3, 89, 0, 7, 6, 100, 0, 1, 114, 2, 32, 3, 0, 3, 70, 0, 100, 3, 70, 12, 0, 101, 116, 1, 10, 2, 32, 3, 70, 106, 0, 7, 6, 101, 0, 1, 10, 2, 17, 67, 32, 3, 13, 0, 116, 1, 10, 2, 32, 3, 13, 47, 0, 110, 1, 10, 2, 32, 3, 13, 50, 0, 110, 115, 1, 10, 2, 32, 3, 13, 50, 87, 0, 115, 1, 10, 2, 32, 3, 13, 87, 0, 2, 114, 17, 67, 3, 35, 0, 1, 10, 2, 32, 3, 106, 0, 4, 1, 29, 2, 109, 32, 3, 113, 0, 2, 17, 67, 17, 67, 0, 110, 101, 1, 10, 2, 32, 3, 113, 50, 106, 0, 3, 115, 0, 105, 3, 126, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 4, 2, 101, 105, 3, 57, 0, 2, 105, 0, 2, 121, 0, 2, 195, 184, 121, 0, 106, 0, 2, 110, 3, 66, 0, 3, 79, 0, 103, 3, 79, 12, 0, 7, 6, 104, 0, 106, 3, 57, 0, 118, 3, 82, 0, 3, 105, 0, 7, 6, 105, 0, 4, 2, 17, 67, 17, 67, 3, 107, 0, 103, 1, 10, 2, 32, 0, 3, 108, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 3, 49, 0, 107, 3, 49, 12, 0, 4, 2, 101, 105, 3, 99, 0, 2, 105, 0, 2, 121, 0, 2, 195, 184, 121, 0, 106, 0, 7, 6, 108, 0, 4, 3, 55, 0, 108, 2, 25, 0, 100, 3, 55, 55, 0, 106, 3, 57, 0, 7, 6, 109, 0, 4, 3, 63, 0, 109, 2, 25, 0, 7, 6, 110, 0, 4, 3, 50, 0, 110, 2, 25, 0, 100, 3, 50, 50, 0, 4, 2, 107, 3, 66, 0, 103, 0, 7, 6, 111, 0, 2, 17, 67, 17, 67, 3, 119, 0, 101, 3, 119, 106, 0, 4, 2, 110, 100, 3, 121, 0, 2, 114, 116, 0, 2, 115, 116, 0, 4, 3, 122, 0, 1, 98, 2, 114, 100, 0, 101, 1, 98, 21, 2, 32, 0, 105, 3, 127, 0, 7, 6, 112, 0, 3, 48, 0, 112, 3, 48, 12, 0, 7, 6, 113, 0, 3, 49, 0, 113, 3, 49, 12, 0, 117, 3, 49, 58, 0, 7, 6, 114, 0, 3, 51, 0, 115, 2, 32, 3, 89, 0, 7, 6, 115, 0, 4, 3, 87, 0, 1, 17, 65, 2, 108, 17, 65, 0, 115, 2, 32, 0, 115, 3, 87, 87, 0, 4, 1, 114, 3, 89, 0, 2, 108, 0, 99, 104, 0, 106, 0, 107, 2, 101, 105, 0, 107, 2, 105, 0, 107, 2, 121, 0, 107, 2, 195, 184, 121, 0, 107, 106, 0, 7, 6, 116, 0, 3, 47, 0, 116, 3, 47, 12, 0, 105, 2, 111, 110, 3, 89, 0, 106, 3, 93, 0, 7, 6, 117, 0, 2, 17, 67, 17, 67, 3, 123, 0, 3, 124, 0, 105, 3, 128, 0, 7, 6, 118, 0, 4, 3, 82, 0, 118, 2, 32, 0, 7, 6, 119, 0, 3, 82, 0, 7, 6, 120, 0, 2, 120, 3, 0, 3, 49, 87, 0, 8, 3, 87, 0, 7, 6, 121, 0, 2, 17, 67, 17, 67, 3, 109, 0, 3, 110, 0, 7, 6, 122, 0, 4, 122, 3, 86, 0, 122, 2, 32, 0, 3, 87, 0, 7, 6, 0, 4, 33, 1, 19, 3, 0, 46, 1, 46, 3, 0, 195, 169, 3, 6, 115, 0, 46, 2, 46, 3, 9, 0, 33, 3, 9, 6, 124, 47, 51, 122, 48, 87, 47, 113, 66, 50, 9, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 46, 3, 48, 123, 66, 49, 47, 124, 63, 0, 45, 8, 32, 2, 32, 15, 3, 63, 108, 50, 124, 87, 0, 36, 3, 70, 119, 55, 55, 118, 51, 0, 195, 188, 3, 110, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts42 = FileInMemory_createWithData (4197, reinterpret_cast (&espeakdata_dicts42_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/no_dict", L"no"); Collection_addItem (me.peek(), espeakdata_dicts42.transfer()); static unsigned char espeakdata_dicts43_data[3416] = { 0, 4, 0, 0, 113, 11, 0, 0, 0, 0, 0, 0, 0, 22, 4, 95, 56, 77, 49, 70, 37, 49, 6, 36, 47, 36, 87, 37, 87, 58, 6, 35, 12, 37, 0, 5, 65, 4, 35, 0, 0, 33, 4, 95, 56, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 87, 37, 87, 58, 6, 35, 12, 37, 0, 0, 0, 0, 9, 65, 8, 69, 37, 12, 37, 12, 0, 0, 0, 0, 0, 9, 65, 12, 87, 37, 12, 37, 12, 0, 0, 0, 0, 7, 196, 100, 16, 78, 36, 8, 0, 9, 65, 16, 70, 37, 12, 37, 12, 0, 0, 0, 0, 0, 8, 65, 20, 37, 12, 37, 12, 0, 0, 0, 0, 0, 8, 65, 24, 36, 12, 81, 40, 0, 0, 0, 0, 0, 9, 197, 12, 129, 78, 100, 80, 72, 28, 6, 65, 28, 109, 13, 0, 0, 0, 0, 6, 195, 100, 83, 129, 76, 0, 8, 65, 32, 36, 37, 74, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 65, 40, 73, 6, 36, 37, 0, 0, 0, 0, 0, 7, 65, 44, 49, 36, 37, 0, 0, 0, 0, 0, 8, 65, 48, 36, 12, 55, 37, 0, 0, 0, 0, 0, 8, 65, 52, 6, 36, 63, 40, 0, 0, 0, 0, 0, 8, 65, 56, 6, 36, 50, 37, 0, 0, 0, 0, 0, 8, 65, 60, 39, 12, 39, 12, 0, 0, 0, 0, 8, 196, 104, 83, 153, 20, 72, 28, 8, 196, 100, 83, 153, 20, 72, 28, 8, 196, 92, 83, 153, 20, 72, 28, 0, 10, 65, 64, 48, 6, 37, 12, 37, 12, 0, 0, 0, 0, 0, 7, 65, 68, 49, 57, 40, 0, 0, 0, 0, 0, 7, 65, 72, 35, 53, 36, 0, 0, 0, 0, 0, 9, 65, 76, 6, 36, 12, 87, 37, 0, 0, 0, 0, 0, 10, 65, 80, 47, 6, 37, 12, 37, 12, 0, 0, 0, 6, 195, 92, 19, 192, 76, 0, 0, 8, 65, 84, 40, 12, 40, 12, 0, 0, 0, 0, 7, 195, 80, 242, 193, 72, 28, 0, 10, 65, 88, 82, 6, 37, 12, 37, 12, 0, 0, 0, 0, 0, 16, 69, 76, 82, 207, 48, 240, 87, 36, 49, 6, 106, 12, 55, 106, 0, 11, 65, 92, 70, 35, 69, 35, 55, 57, 40, 0, 0, 0, 0, 6, 195, 92, 18, 197, 76, 0, 17, 4, 95, 49, 77, 49, 23, 6, 87, 20, 6, 37, 49, 36, 47, 36, 0, 10, 65, 96, 36, 49, 6, 36, 87, 36, 0, 0, 25, 4, 95, 49, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 55, 36, 49, 104, 6, 39, 12, 55, 39, 0, 0, 0, 6, 195, 76, 148, 201, 76, 0, 8, 65, 100, 58, 6, 35, 37, 0, 0, 0, 0, 0, 10, 65, 104, 86, 6, 36, 12, 47, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 5, 80, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 32, 17, 9, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 32, 147, 15, 76, 0, 0, 0, 0, 0, 0, 0, 8, 197, 45, 112, 86, 100, 240, 8, 0, 0, 0, 0, 19, 4, 95, 50, 77, 49, 70, 37, 49, 6, 36, 47, 36, 48, 6, 36, 70, 37, 0, 0, 30, 4, 95, 50, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 48, 6, 36, 70, 37, 0, 0, 0, 7, 196, 4, 145, 8, 4, 8, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 32, 21, 1, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 8, 144, 72, 28, 0, 0, 0, 0, 0, 6, 195, 32, 146, 64, 72, 0, 19, 4, 95, 4, 16, 20, 81, 36, 12, 104, 36, 55, 40, 6, 35, 12, 50, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 51, 77, 49, 70, 37, 49, 6, 36, 47, 36, 47, 6, 35, 12, 53, 39, 0, 0, 31, 4, 95, 51, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 47, 6, 35, 12, 53, 39, 0, 0, 0, 0, 0, 0, 0, 8, 196, 64, 147, 132, 36, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 37, 112, 80, 60, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 197, 89, 145, 78, 100, 80, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 53, 112, 64, 72, 28, 0, 0, 0, 13, 67, 80, 16, 129, 47, 10, 6, 35, 12, 69, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 45, 112, 76, 60, 8, 0, 0, 6, 194, 4, 240, 72, 8, 0, 0, 0, 9, 197, 53, 113, 78, 100, 80, 72, 28, 9, 197, 44, 21, 9, 44, 16, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 72, 83, 129, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 92, 19, 1, 44, 147, 137, 8, 0, 0, 0, 0, 0, 0, 17, 67, 41, 85, 64, 77, 4, 40, 12, 57, 35, 0, 8, 81, 121, 97, 32, 0, 8, 196, 80, 20, 129, 4, 76, 8, 10, 68, 80, 19, 135, 84, 89, 40, 0, 28, 0, 0, 0, 0, 0, 8, 197, 64, 19, 129, 64, 240, 8, 0, 0, 0, 0, 8, 197, 48, 18, 201, 56, 144, 8, 8, 197, 36, 225, 193, 92, 16, 8, 0, 6, 195, 100, 243, 129, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 56, 224, 64, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 133, 49, 5, 14, 25, 5, 72, 28, 0, 0, 6, 194, 24, 144, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 53, 77, 49, 70, 37, 49, 6, 36, 47, 36, 103, 6, 35, 12, 50, 39, 0, 0, 0, 0, 30, 4, 95, 53, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 103, 6, 35, 50, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 51, 88, 63, 35, 87, 6, 39, 12, 63, 36, 47, 6, 35, 12, 53, 39, 0, 0, 14, 3, 95, 48, 67, 55, 36, 49, 104, 6, 39, 55, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 48, 16, 72, 28, 0, 0, 19, 3, 95, 50, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 48, 36, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 51, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 47, 6, 35, 12, 53, 39, 0, 0, 0, 0, 21, 4, 95, 54, 77, 49, 70, 37, 49, 6, 36, 47, 36, 47, 87, 6, 36, 12, 55, 35, 0, 0, 7, 196, 45, 112, 89, 20, 8, 0, 0, 32, 4, 95, 54, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 47, 87, 6, 36, 12, 55, 35, 0, 0, 20, 3, 95, 55, 88, 63, 35, 87, 6, 39, 12, 63, 36, 89, 6, 40, 12, 48, 35, 0, 0, 19, 3, 95, 52, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 6, 42, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 53, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 103, 6, 35, 12, 50, 39, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 49, 88, 55, 36, 87, 6, 39, 12, 63, 36, 0, 0, 22, 3, 95, 54, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 47, 87, 6, 36, 12, 55, 35, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 50, 88, 63, 35, 87, 6, 39, 12, 63, 36, 48, 36, 70, 37, 0, 0, 20, 3, 95, 55, 67, 63, 35, 49, 104, 6, 39, 55, 39, 89, 6, 40, 12, 48, 35, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 147, 73, 76, 0, 0, 22, 3, 95, 56, 67, 63, 35, 49, 104, 6, 39, 55, 39, 87, 37, 87, 58, 6, 35, 12, 37, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 52, 88, 63, 35, 87, 6, 39, 12, 63, 36, 6, 42, 50, 36, 0, 0, 21, 3, 95, 57, 67, 63, 35, 49, 104, 6, 39, 55, 39, 87, 36, 65, 6, 35, 50, 36, 0, 0, 0, 0, 0, 0, 0, 6, 194, 56, 16, 72, 8, 0, 20, 3, 95, 53, 88, 63, 35, 87, 6, 39, 12, 63, 36, 103, 6, 35, 12, 50, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 54, 88, 63, 35, 87, 6, 39, 12, 63, 36, 47, 87, 6, 36, 12, 55, 35, 0, 0, 0, 0, 0, 19, 4, 95, 55, 77, 49, 70, 37, 49, 6, 36, 47, 36, 89, 40, 12, 48, 35, 0, 0, 0, 0, 30, 4, 95, 55, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 89, 40, 12, 48, 35, 0, 0, 10, 199, 36, 160, 80, 60, 181, 87, 4, 8, 0, 0, 0, 0, 0, 0, 0, 0, 22, 3, 95, 56, 88, 63, 35, 87, 6, 39, 12, 63, 36, 87, 37, 87, 58, 6, 35, 12, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 57, 88, 63, 35, 87, 6, 39, 12, 63, 36, 87, 36, 65, 6, 35, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 64, 16, 72, 28, 6, 194, 64, 16, 72, 28, 0, 0, 0, 17, 69, 72, 19, 15, 44, 16, 53, 2, 35, 55, 6, 106, 12, 49, 35, 0, 0, 0, 0, 13, 68, 80, 128, 66, 4, 47, 6, 35, 12, 69, 35, 0, 0, 9, 197, 45, 112, 77, 8, 16, 72, 8, 0, 0, 7, 195, 52, 147, 128, 72, 28, 0, 6, 195, 92, 83, 129, 76, 6, 195, 8, 243, 129, 72, 16, 4, 95, 48, 77, 52, 23, 69, 37, 55, 37, 6, 39, 50, 37, 0, 0, 0, 0, 16, 4, 95, 48, 77, 51, 23, 63, 37, 55, 37, 6, 39, 50, 37, 0, 0, 0, 16, 4, 95, 48, 77, 49, 6, 87, 20, 6, 37, 49, 36, 47, 36, 0, 0, 0, 0, 8, 196, 8, 16, 68, 4, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 100, 18, 197, 76, 0, 0, 0, 0, 0, 0, 12, 4, 95, 3, 9, 18, 49, 6, 36, 81, 35, 0, 32, 4, 95, 57, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 87, 36, 65, 6, 35, 50, 36, 0, 0, 0, 0, 21, 4, 95, 57, 77, 49, 70, 37, 49, 6, 36, 47, 36, 87, 36, 65, 6, 35, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 92, 85, 197, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 45, 84, 213, 16, 144, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 4, 225, 193, 60, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 8, 147, 1, 72, 8, 0, 0, 0, 0, 7, 195, 8, 19, 9, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 45, 85, 193, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 40, 20, 15, 8, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 45, 80, 78, 104, 144, 64, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 92, 16, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 36, 160, 80, 60, 8, 0, 0, 0, 0, 7, 195, 89, 144, 64, 72, 28, 0, 0, 0, 0, 22, 67, 45, 112, 64, 49, 58, 35, 15, 49, 4, 40, 58, 35, 0, 8, 81, 107, 117, 119, 97, 32, 7, 195, 45, 112, 64, 72, 28, 7, 195, 45, 112, 64, 72, 28, 0, 7, 196, 44, 148, 200, 4, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 45, 112, 79, 8, 0, 0, 0, 0, 0, 0, 6, 195, 48, 83, 129, 76, 28, 4, 95, 52, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 42, 50, 36, 0, 0, 17, 4, 95, 52, 77, 49, 70, 37, 49, 6, 36, 47, 36, 42, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 2, 95, 51, 47, 6, 35, 12, 53, 39, 0, 0, 10, 2, 95, 50, 48, 6, 36, 70, 37, 0, 0, 8, 2, 95, 49, 47, 36, 36, 0, 0, 13, 2, 95, 48, 55, 36, 81, 6, 36, 12, 55, 35, 0, 0, 11, 2, 95, 55, 89, 6, 40, 12, 48, 35, 0, 0, 12, 2, 95, 54, 47, 87, 6, 36, 12, 55, 35, 0, 0, 11, 2, 95, 53, 103, 6, 35, 12, 50, 39, 0, 0, 9, 2, 95, 52, 6, 42, 50, 36, 0, 0, 0, 0, 12, 2, 95, 57, 87, 36, 65, 6, 35, 50, 36, 0, 0, 6, 194, 100, 16, 72, 28, 13, 2, 95, 56, 87, 37, 87, 58, 6, 35, 12, 37, 0, 0, 0, 0, 8, 197, 57, 146, 78, 100, 144, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 67, 8, 160, 64, 82, 82, 77, 6, 35, 0, 6, 195, 36, 192, 64, 8, 7, 195, 12, 128, 64, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 104, 16, 72, 28, 0, 0, 0, 8, 197, 64, 19, 79, 40, 16, 8, 0, 6, 195, 104, 18, 197, 76, 0, 7, 195, 36, 194, 64, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 8, 20, 201, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 92, 19, 1, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 33, 82, 207, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 45, 112, 67, 32, 240, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 4, 208, 64, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 199, 36, 194, 75, 92, 19, 66, 4, 8, 0, 0, 9, 198, 8, 17, 1, 48, 22, 65, 8, 0, 7, 195, 44, 19, 65, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 100, 86, 69, 76, 0, 0, 0, 0, 0, 0, 0, 6, 97, 0, 4, 3, 35, 0, 2, 32, 0, 8, 2, 17, 67, 0, 8, 17, 67, 0, 2, 115, 3, 35, 12, 0, 7, 6, 98, 0, 3, 80, 0, 7, 6, 99, 0, 3, 49, 0, 104, 3, 74, 0, 7, 6, 100, 0, 3, 70, 0, 104, 3, 84, 0, 7, 6, 101, 0, 3, 36, 0, 1, 115, 3, 37, 0, 101, 3, 37, 38, 36, 12, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 104, 3, 98, 0, 3, 104, 0, 8, 107, 3, 109, 0, 7, 6, 104, 0, 108, 3, 103, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 105, 3, 37, 12, 0, 7, 6, 106, 0, 3, 77, 0, 7, 6, 107, 0, 3, 49, 0, 104, 3, 99, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 4, 1, 25, 2, 21, 21, 3, 23, 63, 0, 1, 25, 2, 98, 21, 21, 0, 1, 25, 2, 118, 21, 21, 0, 1, 25, 2, 119, 21, 21, 0, 4, 1, 25, 2, 17, 67, 3, 41, 0, 8, 0, 4, 3, 63, 0, 2, 17, 65, 0, 7, 6, 110, 0, 8, 3, 42, 0, 4, 8, 2, 103, 3, 43, 0, 8, 2, 103, 21, 21, 0, 8, 2, 107, 0, 8, 2, 107, 21, 21, 0, 4, 3, 50, 0, 2, 17, 65, 0, 2, 21, 21, 0, 4, 2, 99, 104, 3, 65, 0, 2, 106, 0, 121, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 103, 0, 103, 39, 0, 7, 6, 111, 0, 111, 3, 39, 12, 0, 3, 106, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 7, 6, 114, 0, 3, 53, 0, 7, 6, 115, 0, 3, 87, 0, 2, 101, 3, 87, 20, 0, 101, 8, 116, 3, 87, 37, 12, 0, 7, 6, 116, 0, 3, 47, 0, 115, 101, 110, 3, 47, 87, 6, 36, 12, 50, 0, 104, 3, 47, 105, 0, 108, 3, 103, 0, 108, 104, 3, 108, 0, 7, 6, 117, 0, 3, 40, 0, 4, 8, 100, 3, 40, 12, 0, 117, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 4, 42, 1, 42, 2, 42, 3, 0, 42, 42, 3, 0, 42, 1, 42, 42, 2, 32, 3, 24, 0, 37, 3, 35, 87, 37, 55, 37, 63, 37, 35, 0, 195, 180, 3, 39, 0, 42, 3, 65, 39, 47, 35, 0, 36, 3, 70, 39, 55, 35, 0, 197, 161, 8, 116, 3, 74, 0, 4, 197, 161, 3, 89, 0, 197, 161, 8, 112, 2, 104, 0, 195, 170, 3, 107, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts43 = FileInMemory_createWithData (3415, reinterpret_cast (&espeakdata_dicts43_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/nso_dict", L"nso"); Collection_addItem (me.peek(), espeakdata_dicts43.transfer()); static unsigned char espeakdata_dicts44_data[4993] = { 0, 4, 0, 0, 183, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 4, 95, 4, 16, 20, 10, 70, 119, 136, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 51, 57, 120, 50, 13, 47, 6, 35, 55, 37, 0, 10, 3, 95, 50, 49, 111, 49, 12, 37, 0, 0, 13, 3, 95, 51, 56, 107, 140, 6, 107, 47, 12, 37, 0, 10, 3, 95, 50, 48, 82, 6, 37, 106, 0, 0, 10, 3, 95, 50, 51, 47, 6, 36, 37, 0, 0, 19, 4, 95, 224, 168, 135, 6, 111, 51, 111, 15, 87, 111, 105, 6, 35, 51, 37, 0, 10, 3, 95, 50, 50, 69, 6, 35, 37, 0, 0, 18, 4, 95, 224, 168, 134, 6, 114, 51, 107, 15, 49, 107, 50, 50, 6, 35, 0, 12, 3, 95, 50, 53, 48, 6, 107, 50, 143, 37, 0, 0, 11, 3, 95, 50, 52, 78, 6, 119, 82, 37, 0, 0, 12, 3, 95, 50, 55, 87, 13, 47, 6, 35, 37, 0, 0, 12, 3, 95, 50, 54, 142, 6, 107, 69, 12, 37, 0, 0, 13, 3, 95, 51, 49, 111, 49, 6, 107, 47, 12, 37, 0, 0, 10, 3, 95, 51, 48, 47, 6, 37, 106, 0, 0, 11, 3, 95, 51, 51, 47, 6, 36, 47, 37, 0, 0, 12, 3, 95, 51, 50, 69, 6, 107, 47, 12, 37, 0, 0, 11, 3, 95, 51, 53, 48, 6, 125, 47, 37, 0, 0, 11, 3, 95, 51, 52, 78, 6, 128, 47, 37, 0, 0, 11, 3, 95, 51, 55, 87, 6, 125, 47, 37, 0, 0, 12, 3, 95, 51, 54, 142, 6, 107, 47, 12, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 55, 57, 120, 64, 6, 35, 87, 37, 0, 11, 3, 95, 54, 49, 111, 49, 6, 35, 140, 0, 0, 14, 3, 95, 55, 56, 107, 140, 6, 107, 47, 12, 13, 51, 0, 11, 3, 95, 54, 48, 87, 6, 107, 140, 12, 0, 0, 9, 3, 95, 48, 67, 87, 6, 119, 0, 13, 3, 95, 54, 51, 47, 13, 51, 6, 36, 140, 106, 0, 0, 11, 3, 95, 54, 50, 69, 6, 35, 140, 106, 0, 0, 10, 3, 95, 54, 53, 48, 6, 125, 140, 0, 0, 11, 3, 95, 54, 52, 78, 6, 119, 140, 106, 0, 0, 14, 3, 95, 54, 55, 87, 13, 47, 6, 35, 106, 13, 140, 0, 0, 11, 3, 95, 54, 54, 142, 111, 6, 35, 140, 0, 0, 15, 3, 95, 55, 49, 111, 49, 106, 6, 107, 47, 12, 13, 51, 0, 0, 13, 3, 95, 55, 48, 87, 6, 107, 47, 12, 13, 51, 0, 0, 15, 3, 95, 55, 51, 47, 13, 106, 6, 107, 47, 12, 13, 51, 0, 0, 15, 3, 95, 55, 50, 69, 13, 106, 6, 107, 47, 12, 13, 51, 0, 0, 16, 3, 95, 55, 53, 48, 13, 50, 77, 6, 107, 47, 12, 13, 51, 0, 0, 15, 3, 95, 55, 52, 78, 119, 106, 6, 107, 47, 12, 13, 51, 0, 0, 15, 3, 95, 55, 55, 87, 13, 47, 6, 107, 47, 12, 13, 51, 0, 0, 15, 3, 95, 55, 54, 142, 111, 106, 6, 107, 47, 12, 13, 51, 0, 0, 10, 3, 95, 49, 57, 6, 120, 50, 37, 0, 0, 12, 3, 95, 49, 56, 107, 140, 6, 35, 51, 126, 0, 0, 19, 4, 95, 224, 168, 148, 6, 114, 51, 107, 15, 49, 107, 50, 119, 51, 6, 35, 0, 0, 0, 0, 0, 20, 4, 95, 224, 168, 144, 6, 114, 51, 107, 15, 70, 120, 55, 6, 35, 82, 35, 63, 0, 0, 17, 4, 95, 224, 168, 147, 6, 120, 51, 107, 15, 105, 39, 51, 6, 35, 0, 0, 13, 3, 95, 50, 57, 120, 50, 6, 107, 47, 12, 37, 0, 12, 3, 95, 49, 49, 79, 111, 6, 35, 51, 126, 0, 0, 11, 3, 95, 50, 56, 107, 140, 6, 35, 37, 0, 10, 3, 95, 49, 48, 70, 6, 107, 87, 0, 0, 11, 3, 95, 49, 51, 47, 6, 36, 51, 126, 0, 0, 18, 4, 95, 224, 168, 143, 6, 111, 51, 111, 15, 55, 6, 35, 82, 35, 63, 0, 11, 3, 95, 49, 50, 69, 6, 35, 51, 126, 0, 0, 14, 3, 95, 49, 53, 48, 6, 107, 50, 70, 13, 51, 126, 0, 0, 18, 4, 95, 224, 168, 137, 6, 120, 51, 107, 15, 6, 119, 50, 49, 35, 51, 0, 11, 3, 95, 49, 52, 78, 6, 119, 70, 126, 0, 0, 19, 4, 95, 224, 168, 136, 6, 111, 51, 111, 15, 69, 111, 105, 6, 35, 51, 37, 0, 13, 3, 95, 49, 55, 87, 13, 47, 6, 35, 51, 126, 0, 0, 11, 3, 95, 49, 54, 87, 6, 39, 62, 126, 0, 0, 21, 4, 95, 224, 168, 138, 6, 120, 51, 107, 15, 70, 120, 55, 6, 114, 50, 49, 35, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 52, 57, 6, 120, 64, 123, 77, 35, 0, 0, 12, 3, 224, 165, 164, 70, 107, 50, 70, 6, 37, 0, 15, 3, 95, 52, 56, 107, 140, 12, 13, 47, 6, 35, 55, 37, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 53, 57, 120, 64, 6, 35, 140, 0, 14, 3, 95, 52, 49, 111, 49, 13, 47, 6, 35, 55, 37, 0, 0, 15, 3, 95, 53, 56, 6, 107, 140, 12, 13, 82, 123, 77, 35, 0, 11, 3, 95, 52, 48, 78, 6, 35, 55, 37, 0, 0, 15, 3, 95, 52, 51, 47, 13, 51, 13, 47, 6, 35, 55, 37, 0, 0, 13, 3, 95, 52, 50, 69, 13, 47, 6, 35, 55, 37, 0, 0, 16, 3, 95, 52, 53, 48, 13, 50, 77, 13, 47, 6, 35, 55, 37, 0, 0, 13, 3, 95, 52, 52, 78, 119, 47, 6, 35, 55, 37, 0, 0, 14, 3, 95, 52, 55, 87, 13, 50, 47, 6, 35, 55, 37, 0, 0, 12, 3, 95, 52, 54, 142, 111, 6, 35, 55, 37, 0, 0, 14, 3, 95, 54, 57, 120, 64, 6, 107, 47, 12, 13, 51, 0, 14, 3, 95, 53, 49, 6, 111, 49, 13, 82, 123, 77, 35, 0, 0, 12, 3, 95, 54, 56, 107, 140, 12, 6, 35, 140, 0, 13, 3, 95, 53, 48, 48, 13, 50, 77, 6, 35, 106, 0, 0, 15, 3, 95, 53, 51, 47, 6, 107, 51, 13, 82, 123, 77, 35, 0, 0, 13, 3, 95, 53, 50, 69, 6, 107, 82, 123, 77, 35, 0, 0, 15, 3, 95, 53, 53, 48, 6, 107, 78, 13, 82, 123, 77, 35, 0, 0, 13, 3, 95, 53, 52, 78, 6, 107, 51, 123, 77, 35, 0, 0, 15, 3, 95, 53, 55, 87, 6, 107, 47, 13, 82, 123, 77, 35, 0, 0, 13, 3, 95, 53, 54, 142, 6, 107, 48, 123, 77, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 56, 57, 120, 64, 126, 50, 13, 82, 6, 36, 66, 0, 0, 12, 3, 95, 56, 56, 107, 140, 6, 35, 87, 37, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 57, 57, 50, 111, 51, 6, 107, 50, 50, 13, 82, 124, 0, 12, 3, 95, 56, 49, 111, 49, 6, 35, 87, 37, 0, 0, 14, 3, 95, 57, 56, 107, 140, 6, 35, 50, 13, 82, 124, 0, 11, 3, 95, 56, 48, 6, 107, 87, 87, 37, 0, 0, 14, 3, 95, 56, 51, 47, 13, 51, 13, 6, 35, 87, 37, 0, 0, 12, 3, 95, 56, 50, 69, 111, 6, 35, 87, 37, 0, 0, 14, 3, 95, 56, 53, 48, 13, 50, 77, 6, 35, 87, 37, 0, 0, 13, 3, 95, 56, 52, 78, 13, 51, 6, 35, 87, 37, 0, 0, 13, 3, 95, 56, 55, 87, 13, 47, 6, 35, 87, 37, 0, 0, 12, 3, 95, 56, 54, 142, 111, 6, 35, 87, 37, 0, 0, 16, 3, 95, 57, 49, 111, 49, 13, 6, 35, 50, 13, 82, 4, 124, 0, 0, 12, 3, 95, 57, 48, 50, 6, 107, 69, 12, 36, 0, 0, 16, 3, 95, 57, 51, 47, 13, 51, 13, 6, 35, 50, 13, 82, 124, 0, 0, 16, 3, 95, 57, 50, 69, 111, 38, 6, 35, 50, 13, 82, 4, 124, 0, 0, 15, 3, 95, 57, 53, 48, 13, 78, 6, 35, 50, 13, 82, 124, 0, 0, 15, 3, 95, 57, 52, 78, 13, 51, 6, 35, 50, 13, 82, 124, 0, 0, 15, 3, 95, 57, 55, 87, 13, 47, 6, 35, 50, 13, 82, 124, 0, 0, 14, 3, 95, 57, 54, 142, 111, 6, 35, 50, 13, 82, 124, 0, 0, 10, 3, 224, 168, 133, 6, 114, 51, 107, 0, 12, 3, 224, 169, 141, 105, 107, 55, 107, 50, 47, 0, 0, 13, 3, 224, 169, 140, 49, 107, 50, 6, 119, 51, 35, 0, 0, 0, 0, 0, 13, 3, 224, 169, 136, 70, 120, 55, 35, 82, 35, 63, 0, 0, 11, 3, 224, 169, 139, 105, 39, 51, 6, 35, 0, 12, 3, 224, 168, 131, 82, 37, 87, 35, 51, 79, 0, 0, 12, 3, 224, 168, 130, 69, 111, 50, 70, 6, 37, 0, 0, 0, 0, 11, 3, 224, 169, 135, 55, 35, 82, 35, 63, 0, 0, 0, 11, 3, 224, 169, 129, 119, 50, 49, 35, 51, 0, 0, 13, 3, 224, 169, 128, 69, 111, 105, 6, 35, 51, 37, 0, 0, 0, 15, 3, 224, 169, 130, 70, 120, 55, 6, 114, 50, 49, 35, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 48, 77, 52, 6, 107, 51, 13, 69, 0, 0, 13, 4, 95, 48, 77, 53, 144, 6, 107, 51, 13, 69, 0, 0, 12, 4, 95, 48, 77, 50, 55, 6, 107, 144, 12, 0, 0, 13, 4, 95, 48, 77, 51, 49, 6, 107, 51, 39, 51, 0, 0, 0, 13, 4, 95, 48, 77, 49, 106, 13, 77, 6, 35, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 224, 168, 190, 49, 107, 50, 50, 6, 35, 0, 0, 13, 3, 224, 168, 191, 87, 111, 105, 6, 35, 51, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 224, 169, 178, 6, 111, 51, 111, 0, 0, 10, 3, 224, 169, 179, 6, 120, 51, 107, 0, 0, 12, 3, 224, 169, 176, 47, 111, 48, 48, 6, 37, 0, 0, 11, 3, 224, 169, 177, 107, 70, 70, 107, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 2, 95, 51, 47, 6, 123, 50, 0, 0, 8, 2, 95, 50, 70, 6, 39, 0, 0, 9, 2, 95, 49, 6, 111, 49, 12, 0, 0, 10, 2, 95, 48, 86, 6, 37, 51, 39, 0, 0, 10, 2, 95, 55, 87, 6, 107, 47, 12, 0, 0, 8, 2, 95, 54, 142, 6, 36, 0, 0, 10, 2, 95, 53, 48, 6, 107, 50, 77, 0, 0, 9, 2, 95, 52, 78, 6, 35, 51, 0, 0, 0, 0, 8, 2, 95, 57, 50, 6, 128, 0, 0, 9, 2, 95, 56, 6, 107, 140, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 0, 230, 10, 0, 0, 48, 0, 0, 0, 231, 10, 0, 0, 49, 0, 0, 0, 232, 10, 0, 0, 50, 0, 0, 0, 233, 10, 0, 0, 51, 0, 0, 0, 234, 10, 0, 0, 52, 0, 0, 0, 235, 10, 0, 0, 53, 0, 0, 0, 236, 10, 0, 0, 54, 0, 0, 0, 237, 10, 0, 0, 55, 0, 0, 0, 238, 10, 0, 0, 56, 0, 0, 0, 239, 10, 0, 0, 57, 0, 0, 0, 56, 10, 60, 10, 54, 10, 0, 0, 50, 10, 60, 10, 51, 10, 0, 0, 22, 10, 60, 10, 89, 10, 0, 0, 23, 10, 60, 10, 90, 10, 0, 0, 28, 10, 60, 10, 91, 10, 0, 0, 43, 10, 60, 10, 94, 10, 0, 0, 5, 10, 72, 10, 16, 10, 0, 0, 5, 10, 62, 10, 6, 10, 0, 0, 5, 10, 76, 10, 20, 10, 0, 0, 114, 10, 64, 10, 8, 10, 0, 0, 114, 10, 63, 10, 7, 10, 0, 0, 114, 10, 71, 10, 15, 10, 0, 0, 115, 10, 65, 10, 9, 10, 0, 0, 115, 10, 66, 10, 10, 10, 0, 0, 0, 0, 0, 0, 6, 1, 3, 0, 3, 66, 0, 7, 6, 1, 4, 0, 3, 105, 0, 7, 6, 1, 6, 0, 3, 4, 107, 0, 4, 224, 168, 130, 3, 127, 0, 224, 169, 176, 0, 7, 6, 1, 7, 0, 3, 35, 0, 4, 224, 168, 130, 3, 126, 0, 224, 169, 176, 0, 7, 6, 1, 8, 0, 3, 111, 0, 4, 224, 168, 130, 3, 123, 0, 224, 169, 176, 0, 7, 6, 1, 9, 0, 3, 37, 0, 4, 224, 168, 130, 3, 122, 0, 224, 169, 176, 0, 7, 6, 1, 10, 0, 3, 120, 0, 4, 224, 168, 130, 3, 130, 0, 224, 169, 176, 0, 7, 6, 1, 11, 0, 3, 40, 0, 4, 224, 168, 130, 3, 131, 0, 224, 169, 176, 0, 7, 6, 1, 16, 0, 3, 36, 0, 4, 224, 168, 130, 3, 124, 0, 224, 169, 176, 0, 7, 6, 1, 17, 0, 3, 114, 0, 4, 224, 168, 130, 3, 125, 0, 224, 169, 176, 0, 7, 6, 1, 20, 0, 3, 39, 0, 4, 224, 168, 130, 3, 129, 0, 224, 169, 176, 0, 7, 6, 1, 21, 0, 3, 119, 0, 4, 224, 168, 130, 3, 128, 0, 224, 169, 176, 0, 7, 6, 1, 22, 0, 4, 1, 21, 2, 32, 3, 49, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 49, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 49, 12, 107, 0, 3, 49, 107, 0, 7, 6, 1, 23, 0, 4, 1, 21, 2, 32, 3, 144, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 144, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 144, 12, 107, 0, 3, 144, 107, 0, 7, 6, 1, 24, 0, 4, 1, 21, 2, 32, 3, 79, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 79, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 79, 12, 107, 0, 3, 79, 107, 0, 7, 6, 1, 25, 0, 8, 2, 17, 66, 3, 49, 147, 0, 8, 3, 49, 147, 107, 0, 4, 1, 21, 2, 32, 3, 145, 0, 2, 17, 66, 0, 3, 145, 107, 0, 7, 6, 1, 26, 0, 4, 1, 21, 2, 32, 3, 66, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 66, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 66, 12, 107, 0, 3, 66, 107, 0, 7, 6, 1, 27, 0, 4, 1, 21, 2, 32, 3, 78, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 78, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 78, 12, 107, 0, 3, 78, 107, 0, 7, 6, 1, 28, 0, 4, 1, 21, 2, 32, 3, 142, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 142, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 142, 12, 107, 0, 3, 142, 107, 0, 7, 6, 1, 29, 0, 4, 1, 21, 2, 32, 3, 77, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 77, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 77, 12, 107, 0, 3, 77, 107, 0, 7, 6, 1, 30, 0, 8, 2, 17, 66, 3, 78, 147, 0, 8, 3, 78, 147, 107, 0, 4, 1, 21, 2, 32, 3, 143, 0, 2, 17, 66, 0, 3, 143, 107, 0, 7, 6, 1, 31, 0, 4, 1, 21, 2, 32, 3, 65, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 65, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 65, 12, 107, 0, 3, 65, 107, 0, 7, 6, 1, 32, 0, 4, 1, 21, 2, 32, 3, 138, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 138, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 138, 12, 107, 0, 3, 138, 107, 0, 7, 6, 1, 33, 0, 4, 1, 21, 2, 32, 3, 140, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 140, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 140, 12, 107, 0, 3, 140, 107, 0, 7, 6, 1, 34, 0, 4, 1, 21, 2, 32, 3, 139, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 139, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 139, 12, 107, 0, 3, 139, 107, 0, 7, 6, 1, 35, 0, 8, 2, 17, 66, 3, 138, 0, 8, 3, 138, 147, 107, 0, 4, 1, 21, 2, 32, 3, 141, 0, 2, 17, 66, 0, 3, 141, 107, 0, 7, 6, 1, 36, 0, 4, 1, 21, 2, 32, 3, 64, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 64, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 64, 12, 107, 0, 3, 64, 107, 0, 7, 6, 1, 37, 0, 4, 1, 21, 2, 32, 3, 47, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 47, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 47, 12, 107, 0, 3, 47, 107, 0, 7, 6, 1, 38, 0, 4, 1, 21, 2, 32, 3, 136, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 136, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 136, 12, 107, 0, 3, 136, 107, 0, 7, 6, 1, 39, 0, 4, 1, 21, 2, 32, 3, 70, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 70, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 70, 12, 107, 0, 3, 70, 107, 0, 7, 6, 1, 40, 0, 8, 2, 17, 66, 3, 47, 147, 0, 8, 3, 47, 147, 107, 0, 4, 1, 21, 2, 32, 3, 137, 0, 2, 17, 66, 0, 3, 137, 107, 0, 7, 6, 1, 41, 0, 4, 1, 21, 2, 32, 3, 50, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 50, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 50, 12, 107, 0, 3, 50, 107, 0, 7, 6, 1, 43, 0, 4, 1, 21, 2, 32, 3, 48, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 48, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 48, 12, 107, 0, 3, 48, 107, 0, 7, 6, 1, 44, 0, 4, 1, 21, 2, 32, 3, 134, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 134, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 134, 12, 107, 0, 3, 134, 107, 0, 7, 6, 1, 45, 0, 4, 1, 21, 2, 32, 3, 69, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 69, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 69, 12, 107, 0, 3, 69, 107, 0, 7, 6, 1, 46, 0, 8, 2, 17, 66, 3, 48, 147, 0, 8, 3, 48, 147, 107, 0, 4, 1, 21, 2, 32, 3, 135, 0, 2, 17, 66, 0, 3, 135, 107, 0, 7, 6, 1, 47, 0, 4, 1, 21, 2, 32, 3, 63, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 63, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 63, 12, 107, 0, 3, 63, 107, 0, 7, 6, 1, 48, 0, 4, 1, 21, 2, 32, 3, 57, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 57, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 57, 12, 107, 0, 3, 57, 107, 0, 7, 6, 1, 49, 0, 4, 1, 21, 2, 32, 3, 51, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 51, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 51, 12, 107, 0, 3, 51, 107, 0, 7, 6, 1, 51, 0, 4, 1, 21, 2, 32, 3, 55, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 55, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 55, 12, 107, 0, 3, 55, 107, 0, 7, 6, 1, 52, 0, 4, 1, 21, 2, 32, 3, 62, 0, 2, 17, 66, 0, 3, 62, 107, 0, 7, 6, 1, 54, 0, 4, 1, 21, 2, 32, 3, 82, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 82, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 82, 12, 107, 0, 3, 82, 107, 0, 7, 6, 1, 55, 0, 4, 1, 21, 2, 32, 3, 89, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 89, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 89, 12, 107, 0, 3, 89, 107, 0, 7, 6, 1, 57, 0, 4, 1, 21, 2, 32, 3, 87, 0, 2, 17, 66, 0, 4, 1, 177, 169, 224, 2, 17, 66, 3, 87, 12, 0, 1, 177, 169, 224, 2, 32, 0, 1, 177, 169, 224, 3, 87, 12, 107, 0, 3, 87, 107, 0, 7, 6, 1, 58, 0, 4, 1, 21, 2, 32, 3, 106, 0, 2, 17, 66, 0, 3, 106, 107, 0, 7, 6, 1, 61, 0, 3, 0, 7, 6, 1, 63, 0, 3, 35, 0, 4, 224, 168, 130, 3, 126, 0, 224, 169, 176, 0, 7, 6, 1, 64, 0, 3, 111, 0, 4, 224, 168, 130, 3, 123, 0, 224, 169, 176, 0, 7, 6, 1, 65, 0, 3, 37, 0, 4, 224, 168, 130, 3, 122, 0, 224, 169, 176, 0, 7, 6, 1, 66, 0, 3, 120, 0, 4, 224, 168, 130, 3, 130, 0, 224, 169, 176, 0, 7, 6, 1, 67, 0, 3, 40, 0, 4, 224, 168, 130, 3, 131, 0, 224, 169, 176, 0, 7, 6, 1, 72, 0, 3, 36, 0, 4, 224, 168, 130, 3, 124, 0, 224, 169, 176, 0, 7, 6, 1, 73, 0, 3, 114, 0, 4, 224, 168, 130, 3, 125, 0, 224, 169, 176, 0, 7, 6, 1, 76, 0, 3, 39, 0, 4, 224, 168, 130, 3, 129, 0, 224, 169, 176, 0, 7, 6, 1, 77, 0, 3, 119, 0, 4, 224, 168, 130, 3, 128, 0, 224, 169, 176, 0, 7, 6, 1, 78, 0, 3, 0, 7, 6, 1, 90, 0, 4, 1, 21, 2, 32, 3, 99, 0, 2, 17, 66, 0, 3, 99, 107, 0, 7, 6, 1, 91, 0, 4, 1, 21, 2, 32, 3, 98, 0, 2, 17, 66, 0, 3, 98, 107, 0, 7, 6, 1, 92, 0, 4, 1, 21, 2, 32, 3, 86, 0, 2, 17, 66, 0, 3, 86, 107, 0, 7, 6, 1, 93, 0, 4, 1, 21, 2, 32, 3, 52, 0, 2, 17, 66, 0, 3, 52, 107, 0, 7, 6, 1, 95, 0, 4, 1, 21, 2, 32, 3, 81, 0, 2, 17, 66, 0, 3, 81, 107, 0, 7, 6, 1, 113, 0, 3, 50, 0, 7, 6, 1, 114, 0, 3, 0, 7, 6, 1, 115, 0, 3, 37, 0, 7, 6, 1, 116, 0, 3, 40, 0, 7, 6, 224, 171, 0, 160, 3, 44, 0, 7, 6, 0, 37, 3, 48, 107, 87, 114, 50, 47, 0, 36, 3, 70, 119, 55, 107, 51, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts44 = FileInMemory_createWithData (4992, reinterpret_cast (&espeakdata_dicts44_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/pa_dict", L"pa"); Collection_addItem (me.peek(), espeakdata_dicts44.transfer()); static unsigned char espeakdata_dicts45_data[2134] = { 0, 4, 0, 0, 163, 6, 0, 0, 0, 0, 0, 0, 0, 4, 193, 4, 76, 0, 0, 0, 0, 6, 65, 8, 69, 36, 0, 0, 0, 0, 0, 6, 65, 12, 87, 36, 0, 0, 0, 0, 0, 6, 65, 16, 70, 36, 0, 0, 0, 0, 0, 4, 193, 20, 76, 0, 0, 0, 0, 6, 65, 24, 107, 81, 0, 0, 0, 0, 0, 6, 65, 28, 79, 36, 0, 0, 0, 0, 0, 6, 65, 32, 105, 35, 0, 0, 0, 0, 0, 5, 193, 36, 76, 8, 0, 0, 0, 0, 6, 65, 40, 57, 36, 0, 0, 0, 6, 195, 64, 244, 128, 76, 0, 0, 6, 65, 44, 49, 35, 0, 0, 0, 0, 0, 6, 65, 48, 107, 55, 0, 0, 0, 0, 0, 6, 65, 52, 107, 63, 0, 0, 0, 0, 0, 6, 65, 56, 107, 50, 0, 0, 0, 0, 0, 5, 193, 60, 76, 8, 0, 0, 0, 0, 6, 65, 64, 48, 36, 0, 0, 0, 0, 0, 6, 65, 68, 49, 110, 0, 0, 0, 0, 0, 6, 65, 72, 107, 51, 0, 0, 0, 0, 0, 6, 65, 76, 107, 87, 0, 0, 0, 0, 0, 6, 65, 80, 47, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 88, 82, 36, 0, 0, 0, 0, 0, 6, 65, 92, 58, 36, 0, 0, 0, 0, 0, 7, 65, 96, 107, 49, 87, 0, 0, 0, 0, 0, 11, 65, 100, 37, 79, 51, 6, 107, 49, 0, 14, 5, 193, 100, 72, 8, 0, 0, 0, 0, 7, 65, 104, 86, 107, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 4, 16, 20, 10, 49, 108, 63, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 16, 144, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 8, 240, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 20, 192, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 51, 88, 47, 51, 6, 37, 50, 47, 35, 0, 0, 11, 3, 95, 48, 67, 87, 57, 6, 36, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 49, 49, 70, 57, 36, 87, 6, 40, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 55, 88, 87, 36, 47, 6, 36, 50, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 52, 16, 8, 0, 11, 3, 95, 49, 88, 70, 57, 6, 36, 87, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 45, 80, 76, 28, 0, 12, 3, 95, 50, 88, 69, 6, 37, 50, 47, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 52, 88, 49, 58, 35, 51, 6, 36, 50, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 56, 16, 76, 0, 16, 3, 95, 53, 88, 87, 37, 50, 49, 58, 6, 36, 50, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 54, 88, 87, 36, 87, 6, 36, 50, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 88, 39, 74, 6, 36, 50, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 57, 88, 50, 39, 69, 6, 36, 50, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 48, 77, 50, 63, 37, 6, 39, 50, 0, 0, 11, 195, 44, 83, 128, 72, 28, 81, 115, 117, 32, 0, 0, 11, 4, 95, 48, 77, 49, 63, 6, 37, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 52, 144, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 56, 244, 192, 76, 0, 0, 0, 0, 0, 0, 13, 4, 95, 1, 3, 21, 87, 49, 107, 51, 48, 37, 0, 0, 0, 0, 0, 7, 131, 195, 178, 6, 76, 8, 0, 5, 194, 48, 240, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 8, 244, 207, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 80, 16, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 77, 80, 76, 0, 0, 0, 0, 0, 5, 130, 195, 161, 43, 0, 0, 0, 0, 5, 130, 195, 173, 43, 0, 0, 0, 0, 5, 130, 195, 169, 43, 0, 0, 0, 0, 0, 0, 5, 130, 195, 179, 43, 0, 0, 8, 2, 195, 177, 36, 65, 36, 0, 0, 0, 0, 0, 0, 5, 130, 195, 186, 43, 0, 0, 0, 0, 0, 0, 0, 6, 195, 4, 35, 192, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 1, 35, 0, 0, 0, 0, 0, 6, 2, 95, 5, 36, 0, 0, 0, 0, 6, 2, 95, 9, 37, 0, 0, 0, 6, 2, 95, 15, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 2, 95, 25, 37, 79, 51, 6, 107, 49, 0, 14, 0, 0, 0, 0, 0, 0, 0, 7, 196, 4, 193, 213, 56, 76, 0, 0, 0, 0, 0, 0, 0, 6, 195, 16, 83, 128, 76, 6, 195, 56, 19, 128, 76, 0, 0, 0, 0, 0, 0, 0, 0, 10, 2, 95, 51, 47, 51, 6, 36, 87, 0, 0, 9, 2, 95, 50, 70, 6, 39, 87, 0, 0, 9, 2, 95, 49, 6, 40, 50, 40, 0, 0, 10, 2, 95, 48, 86, 6, 36, 51, 39, 0, 0, 10, 2, 95, 55, 89, 6, 36, 47, 36, 0, 0, 10, 2, 95, 54, 87, 6, 107, 57, 87, 0, 0, 11, 2, 95, 53, 87, 6, 37, 50, 49, 40, 0, 0, 12, 2, 95, 52, 49, 58, 35, 47, 6, 36, 51, 0, 0, 0, 0, 11, 2, 95, 57, 50, 58, 6, 36, 69, 36, 0, 0, 9, 2, 95, 56, 6, 39, 74, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 7, 18, 22, 79, 51, 35, 82, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 194, 80, 240, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 84, 224, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 80, 16, 129, 80, 16, 76, 0, 0, 6, 195, 4, 210, 64, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 168, 0, 3, 6, 107, 0, 7, 6, 195, 177, 0, 3, 65, 0, 7, 6, 195, 178, 0, 3, 6, 108, 0, 7, 6, 195, 185, 0, 3, 111, 0, 105, 3, 111, 57, 0, 7, 6, 195, 188, 0, 3, 110, 0, 105, 3, 110, 57, 0, 7, 6, 97, 0, 3, 35, 0, 97, 3, 35, 12, 0, 105, 3, 115, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 49, 0, 104, 3, 74, 0, 2, 17, 71, 3, 87, 0, 7, 6, 100, 0, 3, 70, 0, 106, 3, 73, 0, 7, 6, 101, 0, 3, 36, 0, 101, 3, 36, 12, 0, 117, 3, 36, 58, 0, 105, 3, 116, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 4, 3, 79, 0, 117, 2, 17, 71, 0, 2, 17, 71, 3, 99, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 4, 1, 17, 65, 2, 25, 3, 57, 0, 2, 17, 65, 0, 106, 3, 116, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 97, 110, 1, 10, 2, 32, 3, 50, 2, 35, 50, 0, 2, 32, 3, 66, 0, 7, 6, 111, 0, 3, 39, 0, 111, 3, 39, 12, 0, 117, 3, 39, 58, 0, 101, 3, 40, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 117, 2, 17, 65, 3, 49, 58, 0, 117, 105, 3, 49, 58, 37, 0, 7, 6, 114, 0, 3, 51, 0, 7, 6, 115, 0, 3, 87, 0, 104, 3, 89, 0, 7, 6, 116, 0, 3, 47, 0, 7, 6, 117, 0, 3, 40, 0, 105, 3, 40, 57, 0, 2, 17, 65, 3, 58, 0, 117, 3, 110, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 49, 87, 0, 8, 2, 17, 65, 3, 86, 0, 7, 6, 121, 0, 1, 25, 2, 25, 3, 37, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 106, 3, 88, 0, 7, 6, 0, 195, 161, 3, 7, 35, 0, 195, 169, 3, 7, 36, 0, 195, 173, 3, 7, 37, 0, 195, 179, 3, 7, 39, 0, 195, 186, 3, 7, 40, 0, 39, 3, 19, 0, 36, 3, 70, 108, 55, 108, 0, 195, 167, 3, 87, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts45 = FileInMemory_createWithData (2133, reinterpret_cast (&espeakdata_dicts45_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/pap_dict", L"pap"); Collection_addItem (me.peek(), espeakdata_dicts45.transfer()); static unsigned char espeakdata_dicts46_data[39433] = { 0, 4, 0, 0, 41, 121, 0, 0, 0, 0, 0, 0, 0, 7, 132, 196, 135, 13, 9, 20, 12, 65, 4, 35, 55, 6, 35, 0, 81, 108, 97, 32, 5, 193, 4, 72, 28, 13, 138, 16, 9, 196, 153, 3, 9, 21, 19, 5, 20, 65, 0, 8, 133, 196, 135, 16, 15, 13, 20, 0, 0, 7, 196, 104, 194, 67, 104, 20, 10, 135, 4, 197, 186, 7, 14, 196, 133, 20, 0, 17, 142, 4, 26, 9, 5, 23, 9, 196, 153, 3, 9, 21, 19, 5, 20, 66, 6, 65, 8, 69, 107, 0, 0, 12, 137, 23, 3, 8, 18, 26, 3, 26, 196, 133, 20, 0, 7, 132, 4, 21, 197, 155, 20, 17, 71, 12, 128, 82, 52, 85, 83, 20, 89, 35, 51, 63, 107, 86, 0, 66, 15, 67, 21, 64, 192, 107, 115, 6, 107, 47, 107, 51, 35, 0, 24, 0, 7, 196, 92, 145, 83, 104, 20, 11, 67, 12, 17, 133, 49, 35, 81, 107, 0, 66, 16, 141, 4, 26, 9, 5, 23, 9, 196, 153, 196, 135, 19, 5, 20, 65, 0, 10, 135, 12, 197, 155, 14, 9, 19, 26, 20, 6, 65, 12, 115, 107, 0, 0, 9, 198, 76, 180, 154, 100, 54, 128, 20, 7, 132, 12, 5, 197, 186, 20, 0, 16, 71, 12, 130, 72, 84, 18, 21, 4, 74, 37, 58, 35, 58, 35, 0, 13, 4, 95, 8, 1, 3, 105, 6, 35, 74, 107, 49, 0, 0, 8, 133, 19, 16, 1, 197, 155, 20, 8, 133, 13, 18, 196, 133, 3, 20, 7, 132, 12, 5, 197, 188, 20, 0, 15, 69, 64, 242, 82, 61, 64, 48, 40, 58, 35, 51, 6, 109, 0, 6, 65, 16, 70, 107, 0, 0, 9, 134, 26, 4, 196, 133, 197, 188, 20, 10, 135, 20, 18, 26, 196, 133, 197, 155, 20, 10, 135, 19, 11, 18, 26, 196, 133, 3, 20, 10, 135, 18, 197, 188, 14, 196, 133, 3, 20, 9, 134, 4, 18, 196, 133, 197, 188, 20, 0, 9, 134, 19, 26, 3, 26, 196, 133, 20, 11, 136, 16, 19, 20, 18, 26, 196, 133, 3, 20, 0, 7, 196, 92, 145, 82, 104, 20, 7, 196, 76, 176, 77, 48, 20, 11, 68, 13, 84, 146, 100, 49, 35, 51, 110, 0, 0, 13, 138, 23, 3, 8, 18, 26, 3, 26, 196, 133, 3, 20, 8, 197, 53, 38, 133, 77, 160, 20, 8, 197, 29, 38, 133, 77, 160, 20, 11, 136, 3, 8, 18, 26, 3, 26, 196, 133, 20, 21, 65, 20, 37, 63, 107, 57, 55, 109, 82, 107, 0, 81, 109, 97, 105, 108, 111, 119, 101, 32, 25, 65, 20, 37, 63, 107, 57, 55, 109, 82, 107, 79, 109, 0, 81, 109, 97, 105, 108, 111, 119, 101, 103, 111, 32, 21, 65, 20, 37, 63, 107, 57, 55, 109, 82, 110, 0, 81, 109, 97, 105, 108, 111, 119, 121, 32, 19, 65, 20, 37, 63, 107, 57, 55, 109, 63, 0, 81, 109, 97, 105, 108, 111, 109, 32, 17, 65, 20, 37, 63, 107, 57, 55, 37, 0, 81, 109, 97, 105, 108, 105, 32, 17, 65, 20, 37, 63, 107, 57, 55, 107, 0, 81, 109, 97, 105, 108, 101, 32, 19, 65, 20, 37, 63, 107, 57, 55, 107, 63, 0, 81, 109, 97, 105, 108, 101, 109, 32, 17, 65, 20, 37, 63, 107, 57, 55, 35, 0, 81, 109, 97, 105, 108, 97, 32, 15, 65, 20, 37, 63, 107, 57, 55, 0, 81, 109, 97, 105, 108, 32, 5, 65, 20, 107, 0, 0, 0, 6, 195, 92, 146, 128, 20, 8, 133, 196, 135, 13, 9, 10, 20, 25, 67, 69, 82, 64, 49, 82, 37, 48, 51, 109, 49, 82, 109, 0, 67, 82, 112, 114, 111, 32, 113, 117, 111, 32, 0, 12, 137, 2, 197, 188, 4, 197, 188, 196, 133, 3, 20, 9, 198, 4, 33, 82, 16, 81, 78, 65, 12, 68, 72, 145, 200, 80, 51, 35, 57, 47, 0, 17, 0, 6, 65, 24, 107, 81, 0, 0, 11, 136, 26, 23, 9, 195, 179, 26, 197, 130, 20, 0, 8, 133, 26, 18, 1, 197, 186, 20, 8, 133, 23, 196, 153, 19, 26, 20, 0, 7, 196, 93, 160, 137, 40, 20, 7, 196, 44, 195, 137, 20, 20, 20, 68, 65, 38, 133, 104, 48, 89, 6, 107, 86, 65, 38, 107, 0, 81, 110, 105, 101, 32, 21, 68, 65, 38, 133, 104, 48, 89, 6, 107, 86, 65, 37, 105, 0, 81, 110, 105, 99, 104, 32, 20, 68, 65, 38, 133, 104, 48, 89, 6, 107, 86, 82, 35, 87, 0, 81, 119, 97, 115, 32, 21, 68, 65, 38, 133, 104, 48, 89, 6, 107, 87, 47, 110, 105, 0, 81, 116, 121, 99, 104, 32, 18, 68, 65, 38, 133, 104, 48, 89, 6, 107, 87, 47, 109, 0, 81, 116, 111, 32, 18, 68, 65, 38, 133, 104, 48, 89, 6, 107, 87, 47, 107, 0, 81, 116, 101, 32, 19, 68, 65, 38, 133, 104, 48, 89, 6, 107, 87, 47, 112, 0, 81, 116, 196, 133, 32, 21, 68, 65, 38, 133, 104, 48, 89, 6, 107, 86, 65, 38, 112, 0, 81, 110, 105, 196, 133, 32, 20, 68, 65, 38, 133, 104, 48, 89, 6, 107, 86, 50, 35, 87, 0, 81, 110, 97, 115, 32, 0, 7, 132, 197, 188, 7, 1, 20, 10, 135, 197, 155, 13, 9, 5, 19, 26, 20, 7, 65, 28, 79, 57, 107, 0, 0, 10, 135, 11, 18, 26, 20, 21, 197, 155, 20, 10, 135, 2, 25, 197, 130, 1, 197, 155, 76, 0, 11, 136, 13, 9, 1, 197, 130, 1, 197, 155, 76, 0, 7, 196, 104, 64, 82, 104, 20, 9, 134, 18, 197, 188, 14, 9, 10, 20, 0, 6, 65, 32, 99, 35, 0, 0, 8, 133, 13, 11, 14, 196, 133, 20, 0, 9, 134, 4, 18, 23, 9, 196, 153, 20, 9, 134, 3, 26, 3, 26, 196, 133, 20, 0, 10, 135, 13, 19, 26, 3, 26, 196, 133, 20, 7, 196, 52, 179, 137, 40, 20, 8, 1, 35, 105, 35, 89, 0, 27, 0, 8, 197, 104, 36, 143, 13, 160, 20, 8, 197, 76, 53, 75, 73, 160, 20, 5, 193, 36, 72, 28, 0, 8, 133, 197, 188, 18, 196, 133, 20, 21, 6, 4, 195, 169, 10, 195, 160, 70, 107, 88, 35, 82, 6, 37, 0, 81, 118, 117, 101, 32, 20, 6, 4, 195, 169, 10, 195, 160, 70, 107, 88, 35, 82, 6, 37, 0, 81, 118, 117, 32, 12, 1, 37, 48, 51, 6, 109, 115, 107, 50, 47, 0, 0, 9, 134, 197, 188, 7, 14, 196, 133, 20, 6, 195, 105, 54, 80, 20, 7, 1, 38, 35, 50, 70, 0, 0, 9, 134, 26, 12, 1, 26, 197, 130, 20, 7, 196, 104, 64, 83, 104, 20, 7, 196, 44, 195, 137, 40, 20, 0, 9, 134, 26, 9, 197, 155, 196, 135, 20, 7, 65, 40, 57, 109, 47, 0, 0, 10, 135, 26, 12, 5, 197, 186, 196, 135, 20, 10, 135, 23, 12, 5, 197, 186, 196, 135, 20, 0, 9, 67, 76, 148, 128, 87, 107, 51, 0, 14, 1, 42, 79, 82, 38, 6, 35, 87, 47, 49, 35, 0, 27, 0, 12, 137, 23, 19, 9, 196, 133, 197, 155, 196, 135, 20, 9, 1, 43, 48, 55, 40, 87, 0, 27, 0, 8, 197, 80, 50, 14, 36, 160, 20, 8, 197, 76, 50, 14, 36, 160, 20, 6, 195, 28, 20, 130, 20, 12, 201, 12, 132, 137, 77, 67, 208, 32, 84, 128, 65, 6, 65, 44, 49, 35, 0, 0, 9, 134, 26, 23, 196, 133, 20, 16, 20, 0, 8, 133, 23, 18, 196, 133, 2, 20, 8, 133, 20, 18, 196, 133, 2, 20, 12, 137, 19, 20, 23, 9, 5, 18, 4, 197, 186, 20, 10, 199, 28, 83, 148, 48, 83, 65, 56, 65, 12, 1, 46, 49, 51, 6, 109, 48, 49, 35, 0, 27, 0, 8, 133, 20, 18, 196, 133, 3, 20, 8, 133, 20, 14, 196, 133, 3, 20, 8, 133, 16, 18, 196, 133, 3, 20, 8, 133, 16, 14, 196, 133, 3, 20, 9, 67, 76, 148, 133, 87, 37, 51, 0, 9, 1, 47, 87, 55, 107, 89, 0, 27, 0, 8, 197, 93, 50, 207, 13, 160, 20, 8, 133, 13, 18, 21, 197, 188, 20, 7, 132, 7, 14, 196, 133, 20, 6, 65, 48, 107, 55, 0, 0, 10, 135, 23, 16, 18, 26, 196, 133, 3, 20, 9, 134, 19, 197, 130, 21, 197, 188, 20, 8, 133, 12, 7, 14, 196, 133, 20, 9, 134, 11, 18, 196, 133, 197, 188, 20, 0, 10, 135, 16, 18, 26, 196, 133, 197, 188, 20, 0, 11, 136, 23, 16, 18, 26, 196, 133, 197, 188, 20, 8, 133, 23, 13, 195, 179, 23, 20, 8, 133, 20, 12, 196, 133, 3, 20, 10, 135, 4, 197, 186, 7, 14, 196, 153, 20, 0, 8, 197, 104, 65, 80, 13, 160, 20, 9, 134, 13, 4, 12, 196, 133, 3, 20, 9, 134, 12, 197, 188, 196, 133, 3, 20, 9, 134, 7, 197, 188, 196, 133, 3, 20, 6, 65, 52, 107, 63, 0, 0, 12, 137, 23, 3, 8, 18, 26, 3, 26, 196, 153, 20, 8, 133, 13, 11, 14, 196, 153, 20, 0, 9, 134, 19, 26, 3, 26, 196, 153, 20, 9, 134, 3, 26, 3, 26, 196, 153, 20, 0, 7, 196, 104, 211, 195, 104, 20, 10, 135, 13, 19, 26, 3, 26, 196, 153, 20, 7, 196, 9, 38, 141, 36, 20, 0, 11, 136, 3, 8, 18, 26, 3, 26, 196, 153, 20, 6, 65, 56, 107, 50, 0, 0, 9, 198, 92, 145, 83, 104, 54, 128, 20, 16, 66, 57, 0, 50, 35, 48, 89, 6, 110, 49, 58, 35, 70, 0, 24, 0, 8, 133, 23, 18, 1, 197, 186, 20, 0, 6, 195, 44, 20, 141, 20, 19, 67, 64, 246, 129, 48, 109, 86, 6, 35, 65, 37, 63, 0, 81, 110, 105, 109, 32, 20, 67, 64, 246, 129, 48, 109, 86, 6, 35, 65, 38, 112, 0, 81, 110, 105, 196, 133, 32, 20, 67, 64, 246, 129, 48, 109, 86, 6, 35, 63, 50, 112, 0, 81, 109, 110, 196, 133, 32, 30, 7, 13, 1, 9, 20, 18, 195, 169, 63, 107, 47, 51, 107, 70, 109, 47, 6, 107, 55, 0, 81, 100, 39, 104, 111, 116, 101, 108, 32, 0, 14, 65, 60, 6, 109, 82, 35, 87, 0, 81, 119, 97, 115, 32, 15, 65, 60, 6, 109, 47, 110, 63, 10, 0, 81, 116, 121, 109, 32, 15, 65, 60, 6, 109, 47, 110, 105, 0, 81, 116, 121, 99, 104, 32, 12, 65, 60, 6, 109, 47, 109, 0, 81, 116, 111, 32, 12, 65, 60, 6, 109, 47, 107, 0, 81, 116, 101, 32, 13, 65, 60, 6, 109, 47, 112, 0, 81, 116, 196, 133, 32, 15, 65, 60, 6, 109, 65, 38, 112, 0, 81, 110, 105, 196, 133, 32, 14, 65, 60, 6, 109, 65, 38, 107, 0, 81, 110, 105, 101, 32, 14, 65, 60, 6, 109, 65, 37, 63, 0, 81, 110, 105, 109, 32, 16, 65, 60, 6, 109, 65, 38, 107, 57, 0, 81, 110, 105, 101, 106, 32, 14, 65, 60, 6, 109, 50, 35, 87, 0, 81, 110, 97, 115, 32, 16, 65, 60, 6, 109, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 4, 193, 60, 76, 0, 14, 1, 61, 51, 6, 40, 82, 50, 35, 15, 95, 107, 0, 27, 0, 0, 7, 196, 52, 179, 137, 20, 20, 0, 8, 133, 19, 20, 196, 133, 16, 20, 10, 1, 64, 63, 6, 35, 58, 48, 35, 0, 6, 65, 64, 48, 107, 0, 0, 9, 134, 23, 19, 20, 196, 133, 16, 20, 15, 70, 12, 128, 78, 76, 243, 128, 89, 35, 50, 87, 112, 0, 66, 0, 0, 0, 8, 197, 105, 114, 69, 77, 160, 20, 8, 197, 73, 114, 69, 77, 160, 20, 8, 197, 28, 226, 69, 77, 160, 20, 6, 65, 68, 49, 40, 0, 0, 0, 14, 67, 16, 240, 192, 70, 6, 109, 115, 107, 50, 47, 0, 24, 0, 9, 134, 23, 9, 12, 7, 197, 130, 20, 9, 134, 4, 14, 9, 15, 197, 130, 20, 0, 10, 135, 197, 155, 13, 9, 15, 197, 130, 20, 10, 135, 19, 20, 197, 130, 21, 3, 26, 20, 9, 134, 19, 16, 19, 15, 196, 135, 20, 10, 135, 19, 16, 197, 130, 21, 3, 26, 20, 9, 134, 197, 130, 7, 15, 196, 135, 20, 6, 65, 72, 107, 51, 0, 0, 10, 135, 23, 4, 26, 9, 15, 196, 135, 20, 9, 134, 197, 155, 3, 9, 5, 12, 20, 10, 135, 4, 197, 186, 7, 15, 196, 135, 20, 17, 70, 16, 85, 137, 12, 84, 192, 70, 37, 82, 35, 57, 87, 37, 87, 0, 0, 0, 0, 10, 135, 23, 196, 135, 23, 9, 3, 26, 20, 6, 195, 92, 34, 74, 20, 6, 65, 76, 107, 87, 0, 0, 7, 196, 77, 0, 82, 104, 20, 6, 195, 77, 0, 76, 20, 9, 198, 76, 180, 154, 101, 54, 128, 20, 0, 0, 21, 72, 13, 84, 146, 36, 53, 76, 84, 208, 49, 40, 51, 6, 37, 49, 40, 55, 40, 63, 0, 0, 8, 197, 80, 181, 201, 77, 160, 20, 9, 134, 197, 155, 3, 9, 5, 3, 20, 8, 197, 77, 161, 77, 73, 160, 20, 6, 65, 80, 47, 107, 0, 0, 0, 9, 134, 197, 188, 7, 14, 196, 153, 20, 7, 132, 13, 195, 179, 23, 20, 8, 133, 13, 9, 15, 197, 130, 20, 7, 195, 4, 226, 64, 76, 8, 0, 10, 135, 19, 26, 197, 130, 1, 2, 25, 20, 9, 198, 104, 208, 82, 77, 160, 218, 20, 6, 195, 77, 163, 9, 20, 7, 132, 19, 195, 179, 12, 20, 7, 196, 52, 145, 82, 104, 20, 9, 134, 197, 130, 7, 15, 197, 130, 20, 6, 195, 52, 226, 69, 72, 0, 7, 132, 26, 23, 196, 153, 20, 10, 135, 23, 12, 195, 179, 11, 197, 130, 20, 10, 135, 23, 4, 26, 9, 15, 197, 130, 20, 7, 132, 7, 14, 196, 153, 20, 10, 135, 4, 197, 186, 7, 15, 197, 130, 20, 10, 135, 3, 8, 3, 9, 15, 197, 130, 20, 0, 10, 135, 197, 155, 13, 9, 15, 196, 135, 20, 8, 133, 19, 26, 197, 130, 1, 20, 8, 133, 12, 7, 14, 196, 153, 20, 0, 6, 195, 93, 146, 128, 20, 12, 137, 23, 197, 155, 3, 9, 5, 11, 197, 130, 20, 0, 7, 196, 104, 161, 83, 104, 20, 9, 134, 16, 12, 23, 15, 197, 130, 20, 9, 198, 13, 162, 206, 36, 84, 218, 20, 0, 7, 65, 88, 81, 35, 58, 0, 0, 11, 136, 26, 23, 12, 195, 179, 11, 197, 130, 20, 7, 132, 11, 195, 179, 10, 20, 0, 14, 67, 52, 80, 192, 63, 107, 115, 107, 50, 35, 87, 0, 24, 0, 9, 134, 26, 4, 23, 195, 179, 10, 20, 15, 4, 95, 49, 77, 52, 69, 38, 6, 37, 55, 57, 109, 50, 0, 0, 12, 69, 40, 16, 203, 36, 80, 73, 107, 49, 37, 0, 13, 1, 92, 69, 6, 107, 49, 87, 55, 107, 89, 0, 27, 8, 65, 92, 82, 110, 0, 72, 14, 0, 8, 197, 93, 0, 84, 73, 160, 20, 0, 10, 1, 94, 70, 6, 35, 89, 107, 49, 0, 0, 7, 196, 104, 65, 82, 104, 20, 7, 196, 48, 115, 137, 20, 20, 0, 7, 132, 18, 23, 196, 133, 20, 6, 195, 52, 226, 74, 20, 16, 7, 4, 39, 1, 13, 15, 21, 18, 70, 35, 63, 40, 51, 0, 66, 11, 1, 96, 6, 35, 49, 115, 107, 50, 47, 0, 7, 65, 96, 37, 49, 87, 0, 14, 4, 95, 49, 77, 49, 47, 6, 110, 95, 109, 50, 115, 0, 0, 8, 133, 197, 188, 18, 196, 153, 20, 22, 66, 4, 64, 35, 70, 6, 109, 49, 40, 55, 109, 87, 0, 81, 111, 99, 117, 108, 111, 115, 32, 16, 66, 4, 64, 35, 70, 105, 6, 109, 49, 0, 81, 104, 111, 99, 32, 15, 4, 95, 49, 77, 50, 63, 38, 6, 37, 55, 57, 109, 50, 0, 0, 16, 4, 95, 49, 77, 51, 63, 38, 6, 37, 55, 57, 35, 51, 70, 0, 0, 22, 5, 16, 16, 197, 130, 11, 48, 109, 47, 48, 40, 58, 49, 6, 109, 82, 50, 37, 49, 0, 24, 0, 9, 134, 16, 12, 23, 15, 196, 135, 20, 9, 134, 13, 15, 197, 155, 196, 135, 20, 8, 197, 17, 33, 80, 13, 160, 20, 7, 132, 196, 135, 16, 1, 20, 10, 65, 100, 6, 37, 79, 51, 107, 49, 0, 0, 0, 0, 7, 132, 7, 15, 197, 132, 20, 22, 72, 13, 83, 66, 21, 35, 1, 56, 64, 49, 6, 35, 63, 69, 107, 51, 55, 107, 50, 70, 0, 0, 9, 134, 197, 188, 7, 15, 196, 135, 20, 10, 135, 26, 12, 196, 133, 11, 197, 130, 20, 9, 134, 23, 19, 9, 15, 196, 135, 20, 9, 134, 10, 5, 197, 155, 196, 135, 20, 8, 65, 104, 86, 110, 0, 72, 14, 0, 9, 134, 26, 13, 25, 197, 155, 12, 20, 10, 135, 26, 1, 10, 197, 155, 196, 135, 20, 10, 135, 23, 25, 10, 197, 155, 196, 135, 20, 11, 136, 23, 19, 9, 196, 133, 11, 197, 130, 20, 10, 135, 16, 12, 5, 197, 155, 196, 135, 20, 11, 136, 2, 18, 26, 13, 9, 15, 197, 130, 20, 0, 19, 67, 12, 148, 192, 115, 37, 87, 63, 6, 109, 55, 0, 81, 109, 111, 108, 108, 32, 18, 67, 12, 148, 192, 115, 37, 87, 70, 6, 40, 51, 0, 81, 100, 117, 114, 32, 0, 9, 134, 197, 155, 13, 9, 5, 10, 20, 14, 68, 5, 48, 201, 36, 6, 35, 87, 49, 107, 57, 0, 17, 0, 0, 0, 0, 0, 6, 195, 80, 240, 218, 20, 9, 134, 19, 3, 8, 197, 130, 15, 20, 0, 9, 198, 104, 210, 69, 73, 165, 192, 20, 10, 135, 19, 26, 3, 26, 196, 133, 3, 20, 0, 0, 9, 134, 197, 188, 7, 15, 197, 130, 20, 8, 133, 26, 13, 195, 179, 23, 20, 9, 134, 23, 19, 9, 15, 197, 130, 20, 7, 196, 48, 115, 137, 40, 20, 12, 137, 3, 8, 18, 26, 3, 26, 196, 133, 3, 20, 9, 134, 2, 12, 1, 11, 197, 130, 20, 16, 4, 9, 14, 197, 188, 37, 50, 88, 6, 110, 65, 107, 51, 0, 24, 0, 8, 197, 104, 210, 69, 73, 160, 20, 6, 195, 104, 193, 74, 20, 10, 135, 26, 2, 12, 1, 11, 197, 130, 20, 7, 132, 18, 23, 196, 153, 20, 0, 8, 133, 26, 197, 130, 15, 13, 20, 10, 135, 23, 5, 10, 197, 155, 196, 135, 20, 0, 10, 199, 92, 50, 18, 104, 50, 83, 104, 20, 11, 136, 20, 197, 130, 21, 197, 155, 196, 135, 20, 0, 9, 134, 26, 23, 9, 15, 197, 130, 20, 9, 134, 20, 197, 130, 21, 3, 26, 20, 7, 196, 77, 2, 83, 104, 20, 9, 134, 12, 196, 133, 11, 197, 130, 20, 9, 198, 17, 33, 206, 36, 84, 218, 20, 0, 6, 195, 104, 70, 66, 20, 13, 138, 19, 20, 18, 26, 196, 133, 197, 155, 196, 135, 20, 13, 138, 19, 16, 18, 26, 196, 133, 197, 155, 196, 135, 20, 13, 138, 3, 8, 18, 26, 196, 153, 197, 155, 196, 135, 20, 13, 69, 40, 19, 137, 12, 80, 73, 107, 65, 37, 87, 0, 0, 9, 198, 104, 116, 154, 21, 54, 128, 20, 9, 198, 76, 180, 154, 21, 54, 128, 20, 0, 9, 134, 19, 3, 8, 197, 130, 1, 20, 0, 6, 195, 104, 64, 77, 20, 9, 134, 196, 135, 23, 9, 3, 26, 20, 7, 196, 13, 161, 77, 84, 76, 0, 20, 1, 124, 49, 51, 4, 107, 87, 49, 35, 15, 48, 38, 109, 50, 6, 109, 82, 35, 0, 0, 8, 133, 19, 26, 197, 130, 25, 20, 9, 198, 44, 195, 137, 21, 54, 128, 20, 0, 10, 1, 126, 47, 6, 110, 55, 70, 35, 0, 0, 8, 133, 26, 13, 195, 179, 3, 20, 7, 132, 19, 196, 153, 16, 20, 0, 7, 132, 26, 23, 196, 133, 20, 6, 195, 104, 64, 74, 20, 0, 0, 0, 0, 9, 134, 26, 23, 9, 15, 196, 135, 20, 8, 197, 76, 50, 18, 85, 0, 20, 9, 134, 16, 1, 197, 155, 196, 135, 20, 0, 10, 135, 26, 5, 10, 197, 155, 196, 135, 20, 10, 135, 7, 18, 26, 13, 15, 196, 135, 20, 10, 135, 4, 15, 10, 197, 155, 196, 135, 20, 0, 11, 136, 23, 26, 5, 10, 197, 155, 196, 135, 20, 11, 136, 19, 9, 196, 133, 197, 155, 196, 135, 20, 0, 7, 196, 77, 162, 204, 36, 20, 12, 137, 16, 18, 26, 5, 10, 197, 155, 196, 135, 20, 7, 196, 17, 162, 65, 8, 20, 0, 8, 197, 104, 70, 137, 20, 192, 20, 8, 197, 77, 4, 201, 20, 160, 20, 0, 8, 133, 19, 20, 12, 196, 133, 20, 0, 0, 0, 0, 7, 132, 23, 15, 197, 186, 20, 0, 0, 9, 134, 26, 10, 1, 4, 197, 130, 20, 9, 134, 19, 26, 5, 4, 197, 130, 20, 7, 196, 29, 38, 141, 36, 20, 0, 11, 136, 23, 9, 12, 7, 197, 130, 2, 25, 20, 11, 136, 4, 14, 9, 15, 197, 130, 2, 25, 20, 10, 135, 23, 19, 26, 5, 4, 197, 130, 20, 8, 197, 76, 96, 74, 13, 160, 20, 10, 135, 16, 12, 195, 179, 20, 197, 130, 20, 0, 12, 137, 197, 155, 13, 9, 15, 197, 130, 2, 25, 20, 11, 136, 26, 2, 18, 26, 25, 4, 197, 130, 20, 11, 136, 23, 16, 12, 195, 179, 20, 197, 130, 20, 11, 136, 19, 16, 12, 195, 179, 20, 197, 130, 20, 11, 136, 7, 14, 9, 195, 179, 20, 197, 130, 20, 0, 0, 9, 134, 20, 23, 195, 179, 18, 26, 20, 0, 11, 136, 16, 12, 23, 15, 197, 130, 2, 25, 20, 10, 135, 11, 18, 26, 5, 16, 197, 130, 20, 0, 11, 136, 26, 23, 9, 195, 179, 4, 197, 130, 20, 0, 13, 138, 26, 23, 12, 195, 179, 11, 197, 130, 2, 25, 20, 0, 7, 196, 93, 2, 83, 104, 20, 0, 6, 195, 40, 81, 26, 20, 0, 0, 0, 33, 7, 3, 8, 1, 18, 7, 195, 169, 89, 35, 51, 88, 107, 70, 35, 81, 107, 51, 0, 68, 81, 100, 39, 97, 102, 102, 97, 105, 114, 101, 115, 32, 0, 8, 197, 76, 50, 12, 60, 208, 20, 6, 195, 29, 32, 74, 20, 6, 195, 13, 160, 74, 20, 0, 8, 133, 19, 20, 12, 196, 153, 20, 0, 0, 6, 195, 29, 32, 77, 20, 18, 72, 8, 80, 85, 40, 243, 1, 37, 48, 69, 109, 88, 109, 55, 6, 107, 0, 0, 0, 0, 9, 134, 19, 3, 8, 197, 130, 25, 20, 20, 71, 13, 80, 137, 13, 83, 21, 52, 49, 40, 69, 6, 37, 49, 40, 55, 40, 63, 0, 0, 7, 196, 77, 2, 69, 12, 20, 7, 196, 13, 162, 193, 40, 20, 0, 6, 195, 13, 165, 74, 20, 8, 197, 8, 16, 129, 12, 128, 66, 0, 0, 0, 7, 196, 64, 50, 1, 40, 20, 7, 196, 45, 32, 67, 104, 20, 0, 6, 195, 93, 165, 74, 20, 0, 13, 66, 17, 32, 70, 6, 109, 49, 47, 109, 51, 0, 24, 0, 0, 8, 133, 23, 4, 15, 196, 135, 20, 7, 196, 77, 162, 207, 48, 20, 8, 133, 11, 15, 16, 196, 135, 20, 0, 6, 195, 93, 38, 74, 20, 6, 195, 77, 166, 74, 20, 9, 134, 19, 11, 15, 16, 196, 135, 20, 8, 197, 9, 161, 21, 73, 160, 20, 0, 10, 135, 23, 26, 14, 9, 5, 196, 135, 20, 11, 136, 23, 26, 7, 1, 18, 4, 197, 186, 20, 11, 136, 197, 155, 23, 9, 19, 26, 3, 26, 20, 0, 8, 133, 23, 4, 15, 197, 130, 20, 8, 133, 16, 1, 4, 197, 130, 20, 7, 132, 11, 15, 197, 155, 20, 0, 9, 134, 19, 20, 25, 7, 197, 130, 20, 7, 196, 64, 197, 207, 52, 20, 7, 196, 17, 33, 207, 52, 20, 9, 134, 2, 12, 1, 4, 197, 130, 20, 0, 15, 140, 19, 3, 8, 197, 130, 25, 2, 25, 197, 155, 13, 25, 20, 10, 135, 26, 2, 12, 1, 4, 197, 130, 20, 10, 135, 23, 9, 196, 133, 4, 197, 130, 20, 8, 197, 12, 131, 85, 73, 160, 20, 21, 73, 88, 147, 129, 36, 116, 133, 81, 65, 64, 58, 37, 50, 107, 79, 34, 107, 47, 0, 67, 0, 11, 136, 26, 23, 9, 196, 133, 4, 197, 130, 20, 11, 136, 26, 13, 9, 195, 179, 20, 197, 130, 20, 11, 136, 23, 13, 9, 195, 179, 20, 197, 130, 20, 8, 133, 12, 197, 155, 14, 9, 20, 0, 6, 195, 13, 166, 64, 72, 0, 7, 196, 77, 4, 149, 40, 20, 9, 134, 11, 23, 9, 20, 197, 130, 20, 7, 196, 17, 38, 153, 40, 20, 7, 196, 17, 33, 193, 40, 20, 0, 10, 135, 197, 155, 12, 5, 16, 197, 130, 20, 0, 0, 13, 138, 26, 23, 9, 195, 179, 26, 197, 130, 2, 25, 20, 8, 133, 18, 1, 4, 197, 186, 20, 9, 134, 4, 197, 186, 7, 15, 13, 20, 0, 9, 134, 26, 10, 5, 4, 197, 186, 20, 0, 0, 12, 137, 2, 25, 197, 130, 25, 197, 155, 13, 25, 76, 0, 13, 138, 19, 26, 12, 9, 2, 25, 197, 155, 13, 25, 20, 13, 138, 13, 9, 1, 197, 130, 25, 197, 155, 13, 25, 76, 0, 13, 138, 19, 3, 8, 197, 130, 15, 19, 26, 3, 26, 20, 7, 196, 64, 50, 1, 52, 20, 0, 10, 135, 26, 23, 195, 179, 4, 197, 186, 20, 10, 135, 19, 26, 11, 15, 4, 197, 186, 20, 7, 195, 61, 32, 90, 72, 28, 0, 11, 136, 26, 197, 130, 21, 19, 26, 3, 26, 20, 0, 0, 7, 196, 80, 179, 137, 20, 20, 7, 196, 17, 33, 193, 52, 20, 7, 196, 13, 162, 193, 52, 20, 0, 11, 136, 26, 12, 1, 26, 197, 130, 2, 25, 20, 0, 12, 137, 26, 12, 196, 133, 11, 197, 130, 2, 25, 20, 0, 13, 138, 23, 19, 9, 196, 133, 11, 197, 130, 2, 25, 20, 13, 138, 2, 18, 26, 13, 9, 15, 197, 130, 2, 25, 20, 0, 7, 196, 93, 50, 69, 40, 20, 7, 196, 76, 50, 12, 4, 20, 0, 11, 136, 26, 23, 9, 15, 197, 130, 2, 25, 20, 11, 136, 12, 196, 133, 11, 197, 130, 2, 25, 20, 8, 197, 76, 50, 12, 5, 0, 20, 0, 8, 133, 7, 26, 9, 196, 133, 20, 6, 195, 60, 35, 203, 76, 0, 8, 133, 197, 155, 14, 9, 10, 20, 9, 134, 4, 197, 186, 7, 1, 13, 20, 0, 9, 134, 23, 196, 153, 4, 197, 186, 20, 9, 134, 19, 26, 25, 4, 197, 186, 20, 8, 133, 7, 26, 9, 196, 135, 20, 9, 134, 196, 135, 16, 1, 19, 26, 20, 10, 135, 11, 20, 195, 179, 18, 25, 13, 76, 0, 9, 134, 26, 19, 26, 25, 196, 135, 20, 10, 135, 26, 4, 18, 1, 4, 197, 186, 20, 9, 134, 26, 2, 9, 5, 197, 155, 20, 8, 197, 77, 162, 204, 36, 160, 20, 9, 134, 19, 11, 18, 25, 196, 135, 20, 9, 134, 16, 12, 23, 1, 196, 135, 20, 9, 134, 13, 197, 188, 25, 196, 135, 20, 9, 134, 13, 4, 12, 9, 196, 135, 20, 9, 134, 197, 130, 7, 1, 196, 135, 20, 0, 8, 133, 197, 188, 7, 15, 13, 20, 10, 135, 23, 26, 14, 9, 5, 197, 155, 20, 9, 134, 11, 18, 5, 197, 155, 12, 20, 10, 135, 4, 197, 186, 7, 1, 196, 135, 20, 11, 66, 13, 96, 87, 37, 82, 6, 37, 0, 17, 0, 9, 134, 197, 155, 16, 9, 196, 133, 20, 6, 195, 76, 48, 76, 20, 7, 132, 18, 25, 196, 135, 20, 7, 132, 16, 9, 196, 135, 20, 13, 138, 14, 9, 5, 11, 20, 195, 179, 18, 25, 13, 76, 0, 8, 133, 26, 13, 21, 197, 155, 20, 8, 133, 16, 19, 21, 196, 135, 20, 8, 133, 11, 18, 25, 196, 135, 20, 9, 134, 4, 197, 186, 7, 1, 10, 20, 0, 9, 134, 26, 197, 188, 25, 196, 135, 20, 10, 135, 26, 7, 195, 179, 4, 197, 186, 20, 9, 134, 23, 19, 26, 25, 196, 135, 20, 8, 197, 13, 160, 201, 77, 160, 20, 10, 135, 3, 8, 195, 179, 4, 197, 186, 20, 7, 195, 13, 166, 74, 72, 12, 0, 10, 135, 23, 4, 26, 9, 1, 196, 135, 20, 11, 136, 23, 3, 8, 195, 179, 4, 197, 186, 20, 10, 135, 197, 155, 13, 9, 1, 196, 135, 20, 11, 136, 19, 26, 11, 195, 179, 4, 197, 186, 20, 10, 135, 19, 16, 19, 9, 5, 196, 135, 20, 9, 134, 19, 197, 130, 25, 197, 132, 20, 11, 136, 19, 3, 8, 195, 179, 4, 197, 186, 20, 7, 132, 18, 25, 197, 130, 20, 7, 132, 16, 9, 197, 130, 20, 11, 136, 2, 197, 186, 4, 26, 9, 19, 26, 20, 0, 8, 133, 16, 19, 21, 197, 130, 20, 8, 133, 13, 9, 1, 197, 130, 20, 8, 133, 11, 18, 25, 197, 130, 20, 8, 133, 13, 9, 1, 197, 130, 76, 12, 137, 2, 196, 153, 4, 26, 9, 5, 19, 26, 76, 0, 9, 134, 26, 197, 188, 25, 197, 130, 20, 9, 134, 23, 19, 26, 25, 197, 130, 20, 9, 134, 197, 155, 3, 9, 21, 2, 20, 9, 134, 4, 14, 9, 1, 197, 130, 20, 6, 195, 13, 166, 77, 77, 0, 8, 133, 23, 19, 21, 197, 132, 20, 10, 135, 23, 4, 26, 9, 1, 197, 130, 20, 10, 135, 197, 155, 13, 9, 1, 197, 130, 20, 6, 195, 45, 38, 74, 20, 8, 133, 3, 26, 25, 197, 132, 20, 10, 135, 3, 8, 3, 9, 1, 197, 130, 20, 0, 9, 134, 26, 13, 9, 5, 197, 132, 20, 9, 134, 23, 20, 18, 25, 197, 132, 20, 7, 132, 20, 25, 197, 130, 20, 23, 66, 16, 80, 70, 107, 82, 109, 55, 6, 35, 57, 0, 81, 118, 111, 108, 97, 105, 108, 108, 101, 32, 25, 66, 16, 80, 70, 107, 55, 35, 63, 107, 86, 6, 112, 0, 82, 108, 97, 32, 109, 97, 105, 115, 111, 110, 32, 17, 66, 16, 80, 70, 107, 57, 40, 51, 107, 0, 81, 105, 117, 114, 101, 32, 19, 66, 16, 80, 70, 107, 81, 35, 49, 47, 109, 0, 81, 102, 97, 99, 116, 111, 32, 14, 70, 52, 21, 82, 36, 49, 64, 63, 109, 51, 37, 87, 0, 0, 0, 7, 196, 105, 114, 69, 40, 20, 9, 134, 26, 19, 26, 25, 197, 130, 20, 6, 195, 104, 67, 205, 20, 7, 196, 80, 179, 137, 40, 20, 7, 196, 77, 68, 149, 40, 20, 9, 134, 19, 11, 18, 25, 197, 130, 20, 9, 134, 16, 12, 23, 1, 197, 130, 20, 9, 134, 13, 197, 188, 25, 197, 130, 20, 9, 134, 13, 4, 12, 9, 197, 130, 20, 9, 134, 197, 130, 7, 1, 197, 130, 20, 0, 8, 197, 64, 50, 14, 36, 80, 20, 10, 135, 4, 197, 186, 7, 1, 197, 130, 20, 0, 0, 8, 133, 197, 188, 7, 1, 10, 20, 8, 133, 23, 9, 4, 197, 186, 20, 8, 133, 23, 1, 4, 197, 186, 20, 8, 133, 19, 1, 4, 197, 186, 20, 0, 9, 134, 26, 2, 21, 4, 197, 186, 20, 9, 134, 20, 18, 21, 4, 197, 186, 20, 9, 134, 19, 3, 5, 4, 197, 186, 20, 18, 4, 95, 4, 16, 20, 10, 48, 89, 107, 117, 6, 37, 50, 107, 49, 10, 0, 0, 10, 135, 19, 16, 196, 153, 4, 197, 186, 20, 10, 135, 19, 9, 196, 133, 4, 197, 186, 20, 0, 8, 133, 197, 188, 7, 1, 13, 20, 11, 136, 26, 2, 18, 26, 25, 4, 197, 186, 20, 9, 198, 104, 20, 19, 81, 38, 128, 20, 11, 136, 23, 19, 9, 196, 133, 4, 197, 186, 20, 9, 198, 77, 2, 69, 65, 38, 128, 20, 9, 198, 64, 244, 19, 81, 38, 128, 20, 0, 8, 133, 26, 197, 188, 21, 10, 20, 0, 7, 196, 40, 80, 149, 80, 66, 0, 7, 132, 13, 197, 188, 25, 20, 0, 11, 136, 19, 16, 18, 1, 23, 4, 197, 186, 20, 22, 67, 16, 145, 83, 114, 6, 37, 57, 107, 87, 6, 37, 51, 107, 0, 81, 105, 114, 97, 101, 32, 0, 6, 195, 104, 214, 76, 20, 9, 134, 197, 155, 16, 9, 196, 153, 20, 12, 137, 19, 11, 18, 26, 25, 23, 4, 197, 186, 20, 6, 195, 52, 243, 64, 20, 6, 195, 40, 83, 64, 20, 6, 195, 16, 19, 64, 20, 0, 7, 196, 105, 114, 69, 52, 20, 7, 196, 17, 162, 69, 48, 20, 0, 0, 0, 0, 7, 196, 76, 50, 12, 36, 20, 7, 196, 52, 67, 5, 40, 20, 7, 196, 40, 242, 131, 104, 20, 7, 196, 13, 160, 201, 40, 20, 7, 196, 12, 131, 5, 40, 20, 14, 4, 95, 20, 12, 4, 86, 47, 6, 110, 55, 70, 112, 0, 9, 3, 95, 35, 57, 47, 35, 69, 0, 0, 6, 195, 76, 181, 74, 20, 0, 0, 9, 134, 197, 155, 14, 9, 196, 133, 20, 6, 195, 76, 181, 76, 20, 8, 133, 14, 21, 4, 197, 186, 20, 7, 132, 2, 9, 196, 135, 20, 0, 7, 196, 93, 54, 153, 40, 20, 9, 134, 197, 155, 3, 9, 19, 26, 20, 8, 133, 19, 13, 21, 196, 135, 20, 8, 133, 7, 14, 9, 196, 135, 20, 8, 133, 3, 14, 9, 196, 135, 20, 12, 68, 5, 32, 213, 76, 35, 34, 49, 40, 87, 0, 0, 9, 134, 197, 188, 7, 1, 196, 135, 20, 10, 135, 26, 197, 130, 21, 4, 197, 186, 20, 6, 195, 92, 181, 74, 20, 9, 134, 197, 155, 14, 9, 196, 135, 20, 8, 197, 77, 68, 154, 21, 0, 20, 10, 135, 19, 20, 18, 21, 4, 197, 186, 20, 9, 134, 19, 20, 12, 9, 196, 135, 20, 9, 134, 11, 18, 196, 153, 196, 135, 20, 0, 10, 135, 23, 11, 18, 196, 153, 196, 135, 20, 10, 135, 19, 11, 18, 196, 153, 196, 135, 20, 8, 133, 11, 16, 9, 196, 133, 20, 0, 7, 132, 2, 25, 196, 135, 20, 14, 6, 3, 15, 21, 16, 195, 169, 49, 40, 48, 6, 107, 0, 7, 132, 2, 25, 196, 135, 76, 14, 67, 17, 97, 0, 70, 37, 82, 37, 70, 6, 37, 0, 17, 0, 8, 133, 23, 11, 21, 196, 135, 20, 8, 133, 19, 11, 21, 196, 135, 20, 8, 133, 14, 196, 153, 196, 135, 20, 8, 133, 11, 16, 9, 196, 135, 20, 7, 196, 29, 112, 82, 104, 20, 8, 133, 3, 12, 9, 196, 135, 20, 6, 195, 40, 83, 85, 72, 0, 9, 134, 26, 23, 9, 1, 196, 135, 20, 9, 134, 23, 19, 9, 1, 196, 135, 20, 8, 197, 77, 65, 82, 13, 160, 20, 6, 195, 76, 181, 66, 20, 8, 197, 64, 148, 218, 13, 160, 20, 0, 7, 132, 2, 25, 197, 130, 20, 7, 132, 2, 25, 197, 130, 76, 0, 8, 133, 23, 11, 21, 197, 130, 20, 8, 133, 19, 11, 21, 197, 130, 20, 8, 133, 11, 16, 9, 197, 130, 20, 11, 136, 7, 18, 26, 13, 9, 5, 196, 135, 20, 8, 133, 3, 12, 9, 197, 130, 20, 0, 12, 137, 16, 9, 15, 197, 130, 2, 25, 197, 155, 20, 9, 134, 26, 23, 9, 1, 197, 130, 20, 9, 134, 23, 19, 9, 1, 197, 130, 20, 12, 137, 11, 19, 26, 20, 1, 197, 130, 196, 135, 20, 0, 8, 133, 26, 19, 21, 197, 132, 20, 9, 134, 13, 11, 14, 196, 133, 3, 20, 0, 10, 135, 3, 26, 3, 26, 196, 133, 3, 20, 11, 136, 2, 18, 26, 13, 9, 1, 197, 130, 20, 7, 132, 2, 9, 197, 130, 20, 21, 66, 12, 144, 87, 37, 70, 107, 82, 6, 35, 66, 0, 81, 100, 101, 118, 97, 110, 116, 32, 6, 194, 12, 144, 72, 12, 0, 6, 195, 64, 145, 76, 20, 11, 136, 13, 19, 26, 3, 26, 196, 133, 3, 20, 8, 133, 7, 14, 9, 197, 130, 20, 8, 133, 3, 14, 9, 197, 130, 20, 0, 9, 134, 197, 188, 7, 1, 197, 130, 20, 7, 196, 104, 115, 137, 40, 20, 9, 134, 197, 155, 14, 9, 197, 130, 20, 9, 134, 19, 20, 12, 9, 197, 130, 20, 0, 0, 6, 195, 28, 20, 0, 20, 0, 0, 6, 195, 93, 38, 133, 20, 7, 196, 92, 179, 5, 40, 20, 9, 134, 16, 196, 153, 4, 197, 186, 20, 9, 134, 196, 135, 13, 9, 19, 26, 20, 0, 10, 135, 23, 16, 196, 153, 4, 197, 186, 20, 6, 195, 64, 145, 74, 20, 8, 197, 13, 162, 206, 36, 80, 20, 8, 197, 52, 22, 9, 52, 16, 65, 0, 8, 133, 13, 197, 155, 3, 9, 20, 0, 8, 133, 23, 197, 188, 25, 10, 20, 19, 71, 12, 244, 25, 72, 145, 200, 80, 49, 6, 109, 48, 110, 51, 35, 57, 47, 0, 0, 0, 10, 135, 197, 155, 16, 9, 5, 19, 26, 20, 0, 0, 0, 9, 198, 92, 50, 18, 104, 50, 74, 20, 0, 0, 0, 10, 67, 61, 32, 193, 109, 51, 49, 35, 0, 0, 7, 132, 13, 18, 196, 133, 20, 16, 70, 12, 128, 82, 52, 85, 82, 89, 35, 51, 63, 107, 51, 0, 66, 20, 67, 32, 16, 128, 105, 35, 69, 37, 55, 37, 47, 109, 82, 6, 35, 50, 110, 0, 24, 10, 135, 11, 20, 195, 179, 18, 26, 25, 76, 0, 7, 132, 23, 1, 197, 188, 20, 7, 196, 12, 131, 1, 40, 20, 0, 9, 134, 19, 11, 18, 26, 196, 133, 20, 0, 8, 133, 19, 11, 21, 197, 155, 20, 10, 135, 16, 19, 20, 18, 26, 196, 133, 20, 7, 132, 12, 9, 197, 186, 20, 8, 133, 11, 1, 18, 196, 135, 20, 13, 138, 14, 9, 5, 11, 20, 195, 179, 18, 26, 25, 76, 0, 7, 132, 23, 18, 196, 133, 20, 9, 134, 23, 9, 5, 18, 196, 135, 20, 7, 132, 197, 155, 12, 5, 20, 8, 133, 7, 18, 25, 197, 186, 20, 0, 9, 134, 23, 7, 18, 25, 197, 186, 20, 7, 132, 13, 1, 197, 188, 20, 7, 132, 12, 9, 197, 188, 20, 7, 196, 29, 32, 83, 104, 20, 0, 8, 197, 29, 38, 141, 36, 160, 20, 7, 132, 7, 1, 197, 155, 20, 0, 8, 133, 23, 13, 21, 197, 155, 20, 0, 0, 10, 135, 20, 18, 26, 196, 153, 197, 155, 20, 8, 133, 11, 16, 9, 196, 153, 20, 0, 13, 69, 77, 68, 133, 21, 64, 87, 47, 51, 37, 47, 0, 19, 67, 65, 3, 210, 48, 109, 70, 48, 109, 51, 6, 40, 74, 65, 37, 49, 0, 24, 0, 0, 9, 134, 197, 188, 18, 196, 133, 3, 20, 9, 134, 2, 18, 14, 196, 133, 3, 20, 0, 10, 135, 197, 188, 7, 14, 196, 133, 3, 20, 7, 196, 92, 179, 5, 64, 20, 10, 135, 20, 3, 8, 14, 196, 133, 3, 20, 16, 70, 24, 244, 151, 5, 33, 0, 81, 109, 51, 58, 107, 51, 70, 0, 0, 9, 134, 197, 155, 14, 9, 196, 153, 20, 10, 135, 19, 197, 130, 1, 2, 197, 130, 20, 0, 8, 133, 3, 12, 196, 133, 3, 20, 7, 195, 81, 147, 73, 72, 12, 0, 9, 134, 197, 155, 12, 196, 133, 3, 20, 0, 9, 198, 104, 211, 137, 20, 164, 218, 20, 10, 135, 197, 130, 197, 188, 196, 133, 3, 20, 7, 196, 45, 114, 67, 104, 20, 10, 135, 4, 18, 197, 188, 196, 133, 3, 20, 0, 8, 133, 23, 196, 133, 20, 16, 20, 24, 69, 65, 38, 133, 104, 80, 48, 89, 107, 86, 6, 107, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 20, 73, 72, 21, 1, 80, 245, 73, 48, 193, 64, 34, 35, 47, 35, 47, 40, 57, 0, 67, 0, 6, 195, 29, 35, 205, 20, 0, 8, 133, 23, 9, 5, 197, 186, 20, 6, 195, 64, 146, 128, 20, 6, 195, 16, 18, 128, 20, 6, 195, 40, 82, 128, 72, 0, 7, 196, 105, 54, 153, 40, 20, 7, 196, 76, 179, 5, 40, 20, 0, 14, 69, 52, 17, 1, 52, 80, 63, 35, 70, 6, 35, 63, 0, 12, 137, 16, 15, 14, 9, 5, 23, 1, 197, 188, 8, 0, 9, 198, 93, 54, 133, 64, 54, 128, 20, 6, 195, 13, 160, 201, 20, 0, 7, 132, 197, 155, 14, 9, 20, 9, 134, 19, 11, 23, 1, 197, 155, 20, 7, 195, 81, 147, 64, 72, 12, 18, 67, 57, 83, 64, 50, 40, 63, 55, 109, 49, 0, 81, 108, 111, 99, 107, 32, 0, 9, 134, 12, 197, 188, 25, 19, 26, 20, 0, 0, 0, 6, 195, 92, 181, 80, 20, 7, 132, 13, 18, 196, 153, 20, 18, 67, 52, 243, 128, 63, 112, 89, 107, 51, 0, 66, 81, 99, 104, 101, 114, 32, 18, 67, 52, 243, 128, 63, 109, 50, 35, 63, 37, 0, 67, 81, 97, 109, 105, 32, 0, 8, 133, 3, 14, 9, 196, 153, 20, 0, 6, 195, 77, 50, 74, 20, 0, 0, 17, 8, 3, 15, 12, 12, 195, 168, 7, 5, 49, 109, 55, 107, 88, 0, 66, 16, 67, 52, 116, 128, 63, 35, 79, 6, 37, 87, 47, 107, 51, 0, 24, 0, 7, 196, 93, 67, 195, 104, 20, 7, 196, 92, 116, 129, 40, 20, 22, 73, 52, 17, 5, 52, 242, 83, 20, 195, 5, 63, 35, 70, 63, 40, 35, 86, 6, 107, 55, 0, 12, 68, 17, 34, 86, 20, 70, 34, 35, 57, 82, 0, 0, 8, 197, 64, 50, 14, 36, 160, 20, 0, 9, 134, 23, 19, 11, 1, 197, 188, 20, 9, 134, 18, 26, 196, 153, 197, 188, 20, 0, 0, 9, 134, 23, 23, 9, 5, 197, 186, 20, 10, 135, 23, 23, 9, 5, 18, 196, 135, 20, 10, 135, 23, 7, 9, 196, 153, 196, 135, 20, 0, 9, 134, 19, 3, 8, 14, 196, 133, 20, 10, 135, 7, 12, 196, 153, 4, 197, 186, 20, 16, 3, 226, 132, 162, 47, 51, 6, 107, 57, 70, 63, 35, 51, 49, 0, 0, 8, 133, 26, 12, 15, 196, 135, 20, 9, 134, 16, 18, 196, 153, 197, 188, 20, 8, 133, 11, 15, 18, 196, 135, 20, 0, 11, 136, 23, 19, 26, 3, 26, 14, 196, 133, 20, 7, 132, 23, 18, 196, 153, 20, 9, 134, 19, 13, 196, 153, 196, 135, 20, 9, 134, 19, 11, 15, 18, 196, 135, 20, 8, 133, 18, 15, 4, 197, 186, 20, 9, 134, 12, 5, 197, 186, 196, 135, 20, 0, 9, 134, 18, 26, 196, 153, 197, 186, 20, 7, 196, 64, 50, 15, 52, 20, 7, 196, 12, 131, 1, 64, 20, 0, 0, 7, 132, 18, 196, 133, 2, 20, 12, 137, 7, 18, 26, 196, 133, 197, 186, 196, 135, 20, 0, 8, 133, 26, 12, 15, 197, 130, 20, 9, 134, 11, 12, 14, 196, 133, 3, 20, 13, 138, 4, 197, 186, 7, 14, 9, 196, 153, 196, 135, 20, 0, 7, 196, 104, 37, 82, 104, 20, 9, 198, 77, 3, 204, 77, 160, 218, 20, 9, 198, 76, 181, 201, 21, 32, 218, 20, 10, 135, 19, 3, 8, 14, 196, 133, 3, 20, 0, 9, 134, 19, 11, 18, 26, 196, 153, 20, 14, 6, 13, 195, 188, 19, 12, 9, 63, 40, 87, 55, 37, 0, 0, 10, 135, 16, 19, 20, 18, 26, 196, 153, 20, 5, 194, 8, 240, 8, 0, 8, 133, 26, 14, 15, 197, 130, 20, 9, 134, 18, 197, 188, 196, 133, 3, 20, 9, 134, 13, 197, 188, 196, 133, 3, 20, 0, 9, 134, 26, 23, 1, 18, 197, 130, 20, 9, 134, 26, 20, 1, 18, 197, 130, 20, 9, 134, 23, 20, 1, 18, 197, 130, 20, 9, 134, 23, 16, 1, 18, 197, 130, 20, 7, 132, 11, 1, 197, 188, 20, 0, 12, 69, 12, 130, 76, 48, 144, 74, 37, 55, 37, 0, 0, 0, 0, 7, 196, 52, 147, 3, 104, 20, 22, 72, 77, 1, 67, 36, 19, 9, 80, 80, 87, 48, 107, 87, 57, 35, 55, 37, 47, 6, 107, 0, 0, 0, 0, 0, 9, 134, 11, 15, 197, 132, 3, 26, 20, 12, 137, 13, 9, 5, 12, 9, 197, 155, 13, 25, 76, 0, 0, 9, 198, 4, 195, 9, 76, 243, 128, 65, 0, 0, 7, 196, 76, 181, 82, 92, 20, 0, 8, 197, 77, 163, 9, 9, 144, 20, 0, 9, 134, 26, 19, 20, 196, 133, 16, 20, 0, 6, 195, 92, 64, 64, 20, 6, 195, 17, 144, 128, 20, 0, 7, 196, 92, 54, 149, 40, 20, 7, 196, 81, 35, 195, 104, 20, 7, 196, 77, 67, 195, 104, 20, 0, 0, 6, 195, 77, 67, 9, 20, 8, 133, 16, 18, 15, 196, 135, 20, 0, 9, 134, 26, 7, 18, 15, 196, 135, 20, 7, 132, 19, 19, 196, 133, 20, 8, 133, 19, 196, 133, 3, 26, 20, 6, 195, 76, 64, 64, 17, 0, 9, 134, 26, 197, 130, 195, 179, 10, 20, 9, 134, 23, 11, 18, 195, 179, 10, 20, 9, 134, 19, 11, 18, 195, 179, 10, 20, 7, 196, 13, 161, 83, 104, 20, 0, 6, 195, 92, 193, 74, 20, 8, 197, 13, 162, 206, 36, 160, 20, 0, 8, 133, 26, 14, 15, 197, 155, 20, 8, 133, 26, 4, 15, 196, 135, 20, 8, 133, 19, 20, 15, 196, 135, 20, 6, 195, 16, 32, 77, 20, 16, 67, 57, 97, 1, 107, 50, 81, 35, 58, 70, 107, 6, 35, 0, 17, 0, 9, 134, 7, 15, 197, 155, 196, 135, 20, 0, 7, 196, 61, 53, 18, 104, 20, 10, 135, 11, 197, 130, 195, 179, 196, 135, 20, 0, 8, 197, 17, 37, 201, 77, 160, 20, 0, 12, 137, 16, 18, 26, 25, 10, 197, 155, 196, 135, 20, 21, 67, 64, 17, 197, 48, 107, 57, 73, 70, 6, 35, 58, 50, 0, 81, 100, 111, 119, 110, 32, 17, 67, 64, 17, 197, 48, 107, 57, 73, 6, 35, 48, 0, 81, 117, 112, 32, 0, 8, 133, 26, 4, 15, 197, 130, 20, 11, 136, 23, 19, 26, 3, 26, 14, 196, 153, 20, 6, 195, 92, 179, 208, 20, 8, 133, 20, 12, 15, 197, 130, 20, 8, 133, 19, 20, 15, 197, 130, 20, 0, 6, 195, 92, 193, 67, 20, 7, 196, 92, 68, 129, 64, 20, 0, 10, 135, 26, 18, 195, 179, 19, 197, 130, 20, 8, 197, 104, 116, 129, 77, 160, 20, 10, 135, 23, 18, 195, 179, 19, 197, 130, 20, 10, 135, 14, 9, 195, 179, 19, 197, 130, 20, 6, 195, 16, 32, 74, 20, 0, 11, 136, 23, 26, 18, 195, 179, 19, 197, 130, 20, 11, 136, 19, 20, 18, 26, 5, 7, 197, 130, 20, 5, 194, 40, 16, 76, 0, 9, 134, 26, 197, 130, 195, 179, 23, 20, 12, 137, 23, 26, 14, 9, 195, 179, 19, 197, 130, 20, 6, 195, 81, 146, 128, 20, 8, 133, 16, 18, 15, 197, 130, 20, 8, 133, 7, 1, 19, 197, 130, 20, 6, 195, 12, 194, 64, 20, 0, 13, 138, 26, 197, 188, 195, 179, 197, 130, 11, 197, 130, 20, 9, 134, 26, 7, 18, 15, 197, 130, 20, 7, 196, 104, 116, 129, 8, 20, 11, 136, 23, 3, 8, 197, 130, 15, 197, 132, 20, 7, 196, 53, 35, 195, 104, 20, 6, 195, 36, 50, 0, 72, 0, 0, 9, 198, 76, 50, 12, 36, 38, 64, 20, 9, 198, 80, 179, 137, 21, 54, 128, 20, 0, 0, 7, 196, 92, 19, 3, 104, 20, 7, 196, 77, 160, 218, 4, 20, 0, 0, 8, 133, 16, 18, 15, 197, 155, 20, 9, 198, 29, 38, 141, 37, 54, 128, 20, 0, 0, 12, 68, 40, 19, 133, 80, 73, 35, 50, 107, 47, 0, 0, 9, 134, 19, 3, 8, 14, 196, 153, 20, 6, 195, 64, 20, 154, 20, 13, 69, 16, 147, 135, 33, 144, 114, 37, 66, 79, 37, 0, 0, 6, 195, 80, 18, 201, 76, 0, 11, 136, 11, 20, 195, 179, 18, 5, 13, 21, 76, 10, 199, 12, 19, 129, 88, 84, 129, 48, 66, 0, 9, 198, 93, 38, 133, 77, 160, 218, 20, 7, 196, 92, 181, 82, 92, 20, 7, 196, 92, 116, 129, 52, 20, 12, 68, 12, 148, 131, 4, 115, 37, 51, 49, 35, 0, 0, 6, 195, 8, 80, 218, 20, 18, 4, 16, 197, 130, 11, 48, 40, 58, 49, 6, 109, 82, 50, 37, 49, 0, 24, 0, 14, 139, 14, 9, 5, 11, 20, 195, 179, 18, 5, 13, 21, 76, 9, 198, 61, 50, 69, 53, 49, 84, 65, 0, 0, 7, 196, 9, 35, 195, 104, 20, 0, 8, 133, 7, 4, 25, 197, 188, 8, 0, 0, 9, 134, 19, 11, 1, 18, 196, 135, 20, 9, 134, 16, 197, 130, 15, 196, 135, 20, 0, 10, 135, 23, 16, 197, 130, 15, 196, 135, 20, 10, 135, 19, 26, 3, 26, 15, 196, 135, 20, 10, 135, 19, 16, 197, 130, 15, 196, 135, 20, 0, 10, 135, 26, 197, 130, 196, 133, 3, 26, 20, 8, 197, 12, 128, 201, 20, 160, 20, 18, 70, 4, 225, 197, 48, 144, 193, 35, 50, 79, 107, 55, 37, 49, 35, 0, 66, 18, 67, 37, 65, 0, 37, 15, 47, 35, 49, 15, 70, 35, 55, 107, 57, 0, 24, 0, 8, 133, 23, 12, 15, 196, 135, 20, 15, 70, 29, 32, 69, 12, 20, 192, 79, 51, 107, 49, 35, 87, 0, 19, 4, 95, 13, 3, 14, 50, 35, 70, 49, 51, 107, 95, 55, 6, 109, 50, 107, 0, 0, 9, 134, 23, 18, 195, 179, 196, 135, 20, 7, 132, 197, 155, 16, 9, 20, 9, 67, 56, 85, 192, 65, 38, 40, 0, 19, 71, 21, 99, 204, 85, 66, 79, 56, 107, 82, 109, 55, 6, 40, 89, 110, 50, 0, 0, 10, 135, 26, 23, 18, 195, 179, 196, 135, 20, 10, 135, 23, 16, 1, 197, 155, 196, 135, 20, 7, 196, 92, 181, 82, 104, 20, 10, 135, 19, 16, 1, 197, 155, 196, 135, 20, 10, 135, 19, 11, 18, 195, 179, 196, 135, 20, 10, 135, 13, 197, 130, 195, 179, 196, 135, 20, 7, 196, 12, 131, 9, 64, 20, 0, 6, 195, 104, 224, 74, 20, 11, 136, 26, 13, 197, 130, 195, 179, 196, 135, 20, 11, 136, 23, 16, 12, 5, 197, 155, 196, 135, 20, 11, 136, 19, 16, 12, 5, 197, 155, 196, 135, 20, 11, 136, 19, 11, 197, 130, 195, 179, 196, 135, 20, 11, 136, 16, 195, 179, 10, 197, 155, 196, 135, 20, 6, 195, 12, 194, 74, 20, 15, 67, 45, 5, 0, 49, 35, 48, 6, 37, 47, 35, 50, 0, 24, 0, 6, 195, 104, 224, 77, 20, 12, 137, 20, 18, 26, 196, 133, 197, 155, 196, 135, 20, 12, 137, 16, 18, 26, 196, 133, 197, 155, 196, 135, 20, 8, 133, 7, 14, 196, 133, 3, 20, 21, 67, 37, 68, 0, 37, 15, 47, 107, 63, 40, 15, 48, 109, 70, 109, 69, 50, 107, 0, 24, 13, 67, 76, 52, 201, 87, 49, 6, 35, 86, 37, 0, 17, 0, 10, 135, 23, 26, 2, 18, 15, 197, 132, 20, 13, 138, 23, 16, 18, 26, 196, 133, 197, 155, 196, 135, 20, 8, 133, 23, 12, 15, 197, 130, 20, 8, 133, 19, 16, 15, 197, 130, 20, 10, 135, 19, 16, 197, 130, 15, 197, 132, 20, 9, 134, 12, 7, 14, 196, 133, 3, 20, 0, 9, 134, 26, 7, 1, 4, 197, 130, 20, 7, 196, 104, 68, 129, 64, 20, 9, 134, 18, 195, 179, 19, 197, 130, 20, 9, 134, 12, 196, 133, 7, 197, 130, 20, 7, 196, 12, 132, 129, 64, 20, 12, 68, 12, 148, 131, 20, 49, 37, 51, 49, 107, 0, 0, 10, 135, 26, 2, 9, 5, 7, 197, 130, 20, 10, 135, 23, 2, 9, 5, 7, 197, 130, 20, 0, 5, 194, 16, 240, 76, 0, 6, 195, 44, 192, 80, 20, 8, 133, 11, 9, 19, 197, 130, 20, 6, 195, 40, 84, 212, 76, 0, 9, 134, 26, 23, 9, 19, 197, 130, 20, 9, 134, 26, 14, 9, 11, 197, 130, 20, 9, 134, 26, 13, 25, 19, 197, 130, 20, 7, 196, 104, 116, 129, 40, 20, 9, 134, 19, 16, 1, 19, 197, 130, 20, 9, 134, 19, 11, 9, 19, 197, 130, 20, 9, 134, 13, 1, 18, 26, 197, 130, 20, 13, 5, 10, 15, 19, 195, 169, 105, 109, 86, 6, 107, 0, 0, 10, 135, 19, 26, 3, 26, 15, 197, 130, 20, 6, 195, 44, 193, 74, 20, 0, 11, 136, 20, 18, 26, 196, 133, 19, 197, 130, 20, 9, 198, 52, 179, 137, 21, 54, 128, 20, 9, 198, 48, 115, 137, 21, 54, 128, 20, 9, 198, 9, 35, 137, 21, 54, 128, 20, 0, 12, 137, 197, 188, 195, 179, 197, 130, 11, 197, 130, 20, 10, 135, 23, 197, 155, 3, 9, 5, 12, 20, 12, 137, 19, 20, 18, 26, 196, 133, 19, 197, 130, 20, 0, 9, 134, 197, 130, 196, 133, 3, 26, 20, 7, 196, 45, 2, 83, 104, 20, 7, 196, 17, 162, 79, 8, 20, 0, 10, 135, 23, 197, 130, 196, 133, 3, 26, 20, 11, 136, 11, 20, 195, 179, 18, 5, 7, 15, 76, 15, 69, 16, 85, 137, 12, 80, 70, 37, 82, 6, 35, 57, 87, 0, 0, 8, 133, 26, 18, 15, 197, 155, 20, 0, 8, 133, 26, 197, 188, 25, 10, 20, 9, 134, 23, 26, 14, 15, 197, 155, 20, 7, 132, 19, 19, 196, 153, 20, 0, 9, 134, 16, 197, 130, 1, 3, 26, 20, 9, 134, 12, 197, 155, 14, 9, 10, 20, 14, 139, 14, 9, 5, 11, 20, 195, 179, 18, 5, 7, 15, 76, 0, 6, 195, 92, 64, 74, 20, 10, 135, 19, 16, 197, 130, 1, 3, 26, 20, 6, 195, 48, 144, 218, 20, 0, 6, 195, 92, 64, 77, 20, 0, 9, 134, 23, 26, 13, 195, 179, 3, 20, 6, 195, 92, 193, 80, 20, 0, 7, 196, 104, 116, 129, 52, 20, 0, 6, 195, 52, 240, 218, 20, 6, 195, 16, 20, 218, 20, 0, 0, 11, 136, 19, 3, 8, 197, 130, 1, 2, 25, 20, 16, 3, 95, 51, 88, 47, 89, 110, 118, 6, 107, 95, 78, 38, 37, 0, 0, 0, 6, 195, 81, 32, 70, 20, 0, 7, 132, 197, 188, 21, 10, 20, 0, 7, 132, 20, 12, 196, 133, 20, 0, 8, 133, 13, 4, 12, 196, 133, 20, 7, 196, 16, 84, 3, 104, 20, 11, 200, 52, 21, 20, 21, 34, 15, 72, 224, 65, 0, 0, 8, 133, 23, 14, 15, 197, 155, 20, 0, 10, 135, 23, 197, 130, 195, 179, 197, 188, 20, 0, 7, 196, 12, 131, 21, 64, 20, 10, 3, 95, 49, 67, 87, 47, 6, 109, 0, 0, 0, 0, 8, 133, 10, 1, 4, 197, 130, 20, 0, 9, 134, 19, 9, 1, 4, 197, 130, 20, 9, 134, 18, 26, 5, 4, 197, 130, 20, 9, 134, 11, 18, 1, 4, 197, 130, 20, 9, 134, 3, 8, 21, 4, 197, 130, 20, 0, 10, 135, 26, 18, 26, 5, 4, 197, 130, 20, 10, 135, 23, 11, 18, 1, 4, 197, 130, 20, 10, 135, 19, 11, 18, 1, 4, 197, 130, 20, 10, 135, 19, 3, 8, 21, 4, 197, 130, 20, 10, 135, 11, 197, 130, 1, 4, 197, 130, 20, 6, 195, 40, 84, 218, 20, 10, 135, 2, 18, 26, 25, 4, 197, 130, 20, 0, 11, 136, 26, 7, 196, 153, 19, 20, 197, 130, 20, 6, 195, 64, 50, 1, 20, 5, 194, 40, 80, 20, 18, 3, 95, 49, 57, 118, 107, 82, 38, 107, 47, 50, 6, 35, 95, 117, 107, 0, 0, 12, 137, 26, 7, 14, 9, 195, 179, 20, 197, 130, 20, 12, 137, 23, 7, 14, 9, 195, 179, 20, 197, 130, 20, 16, 3, 95, 49, 56, 109, 95, 107, 63, 50, 6, 35, 95, 117, 107, 0, 0, 9, 134, 19, 9, 15, 4, 197, 130, 20, 9, 134, 2, 195, 179, 4, 197, 130, 20, 15, 3, 95, 50, 67, 70, 82, 38, 6, 107, 95, 78, 38, 107, 0, 0, 10, 135, 23, 19, 9, 15, 4, 197, 130, 20, 10, 135, 3, 8, 18, 25, 16, 197, 130, 20, 0, 11, 136, 19, 11, 18, 26, 5, 16, 197, 130, 20, 11, 136, 19, 3, 8, 18, 25, 16, 197, 130, 20, 0, 6, 195, 17, 32, 80, 20, 0, 9, 134, 18, 26, 5, 197, 186, 2, 20, 26, 68, 12, 20, 148, 20, 49, 35, 51, 47, 69, 55, 6, 35, 50, 89, 0, 81, 98, 108, 97, 110, 99, 104, 101, 32, 0, 8, 197, 40, 84, 212, 20, 208, 76, 0, 16, 3, 95, 49, 49, 57, 107, 70, 107, 50, 6, 35, 95, 117, 107, 0, 0, 13, 3, 95, 49, 48, 118, 6, 107, 95, 107, 65, 117, 0, 0, 8, 133, 13, 4, 12, 196, 153, 20, 8, 133, 4, 197, 186, 7, 1, 20, 13, 3, 95, 51, 67, 47, 89, 6, 110, 87, 47, 35, 0, 15, 3, 95, 49, 51, 47, 89, 110, 50, 6, 35, 95, 117, 107, 0, 0, 15, 3, 95, 49, 50, 70, 82, 35, 50, 6, 35, 95, 117, 107, 0, 0, 11, 136, 26, 23, 9, 196, 153, 11, 19, 26, 20, 16, 3, 95, 49, 53, 48, 57, 107, 47, 50, 6, 35, 95, 117, 107, 0, 0, 16, 3, 95, 49, 52, 74, 47, 107, 51, 50, 6, 35, 95, 117, 107, 0, 0, 17, 3, 95, 49, 55, 95, 107, 70, 107, 63, 50, 6, 35, 95, 117, 107, 0, 0, 15, 3, 95, 49, 54, 89, 107, 87, 50, 6, 35, 95, 117, 107, 0, 0, 0, 13, 67, 81, 148, 192, 47, 110, 95, 111, 115, 110, 0, 24, 18, 3, 95, 55, 88, 95, 107, 70, 107, 63, 118, 6, 107, 95, 109, 50, 47, 0, 0, 15, 3, 95, 52, 67, 74, 47, 6, 107, 51, 110, 87, 47, 35, 0, 0, 0, 9, 134, 19, 11, 1, 18, 197, 188, 20, 0, 6, 195, 93, 69, 76, 20, 10, 199, 13, 165, 5, 73, 148, 212, 4, 65, 0, 10, 135, 19, 11, 18, 26, 25, 196, 135, 20, 0, 0, 0, 10, 135, 26, 197, 130, 195, 179, 197, 188, 20, 0, 10, 135, 26, 7, 14, 9, 5, 196, 135, 20, 15, 3, 95, 53, 67, 48, 38, 6, 107, 65, 117, 87, 107, 47, 0, 0, 13, 138, 19, 3, 8, 197, 130, 25, 197, 155, 13, 25, 20, 8, 197, 64, 145, 80, 73, 160, 20, 0, 11, 136, 7, 197, 130, 1, 19, 26, 3, 26, 20, 0, 12, 137, 19, 16, 197, 130, 1, 19, 26, 3, 26, 20, 0, 9, 134, 19, 16, 1, 4, 197, 130, 20, 7, 196, 13, 162, 207, 52, 20, 0, 10, 135, 26, 19, 9, 1, 4, 197, 130, 20, 10, 135, 23, 19, 9, 1, 4, 197, 130, 20, 8, 197, 77, 2, 69, 13, 160, 20, 10, 135, 13, 9, 195, 179, 20, 197, 130, 20, 0, 11, 136, 19, 20, 18, 26, 25, 7, 197, 130, 20, 11, 136, 16, 18, 26, 196, 133, 4, 197, 130, 20, 5, 194, 52, 16, 20, 5, 194, 52, 16, 76, 0, 12, 137, 23, 16, 18, 26, 196, 133, 4, 197, 130, 20, 12, 137, 19, 16, 18, 26, 196, 133, 4, 197, 130, 20, 0, 7, 196, 81, 37, 193, 40, 20, 13, 3, 95, 54, 67, 89, 6, 107, 95, 87, 107, 47, 0, 0, 10, 135, 26, 19, 9, 15, 4, 197, 130, 20, 10, 135, 19, 11, 18, 26, 25, 197, 130, 20, 0, 11, 136, 23, 23, 9, 195, 179, 4, 197, 130, 20, 0, 7, 132, 197, 188, 18, 5, 20, 8, 197, 77, 160, 218, 101, 0, 20, 12, 137, 3, 8, 197, 130, 195, 179, 4, 197, 130, 20, 0, 9, 134, 23, 10, 5, 4, 197, 186, 20, 7, 196, 77, 160, 218, 100, 20, 9, 134, 19, 20, 21, 4, 197, 186, 20, 7, 196, 45, 37, 193, 92, 20, 0, 10, 135, 26, 23, 196, 153, 4, 197, 186, 20, 8, 197, 77, 160, 218, 60, 208, 20, 10, 135, 11, 197, 130, 1, 4, 197, 186, 20, 10, 135, 7, 197, 130, 1, 4, 197, 186, 20, 0, 14, 139, 19, 26, 197, 130, 25, 2, 25, 197, 155, 13, 25, 20, 14, 139, 19, 3, 8, 12, 9, 2, 25, 197, 155, 13, 25, 20, 11, 136, 26, 7, 197, 130, 1, 4, 197, 186, 20, 9, 134, 23, 18, 195, 179, 197, 188, 20, 0, 11, 136, 19, 26, 12, 9, 197, 155, 13, 25, 20, 7, 132, 20, 12, 196, 153, 20, 12, 137, 19, 26, 3, 26, 196, 153, 4, 197, 186, 20, 12, 137, 3, 8, 197, 130, 15, 19, 26, 3, 26, 20, 7, 195, 81, 144, 200, 72, 12, 15, 3, 95, 50, 88, 70, 82, 35, 118, 6, 107, 95, 117, 35, 0, 0, 16, 5, 95, 48, 77, 65, 49, 47, 110, 95, 6, 109, 50, 115, 107, 0, 15, 3, 95, 55, 67, 95, 6, 107, 70, 107, 63, 87, 107, 47, 0, 0, 0, 11, 136, 2, 197, 130, 25, 19, 26, 3, 26, 20, 18, 5, 95, 48, 77, 65, 51, 63, 38, 37, 55, 57, 6, 35, 51, 70, 110, 0, 0, 17, 70, 88, 20, 137, 21, 65, 83, 82, 35, 34, 57, 107, 47, 107, 0, 67, 17, 5, 95, 48, 77, 65, 50, 63, 38, 37, 55, 57, 6, 109, 50, 110, 0, 0, 7, 196, 81, 37, 193, 52, 20, 0, 17, 5, 95, 48, 77, 65, 52, 69, 38, 37, 55, 57, 6, 109, 50, 110, 0, 0, 0, 6, 195, 80, 176, 64, 20, 0, 14, 3, 95, 56, 67, 6, 109, 95, 107, 63, 87, 107, 47, 0, 0, 27, 69, 76, 52, 133, 20, 224, 87, 49, 51, 37, 50, 51, 6, 37, 70, 107, 34, 0, 81, 114, 101, 97, 100, 101, 114, 32, 0, 8, 133, 26, 2, 9, 196, 135, 20, 8, 133, 23, 2, 9, 196, 135, 20, 0, 9, 134, 23, 197, 188, 25, 196, 135, 20, 9, 134, 23, 26, 2, 9, 196, 135, 20, 8, 133, 11, 196, 133, 19, 26, 20, 8, 133, 10, 5, 4, 197, 186, 20, 9, 134, 4, 18, 7, 1, 196, 135, 20, 9, 134, 3, 26, 11, 1, 196, 135, 20, 0, 7, 196, 53, 37, 67, 104, 20, 9, 134, 197, 130, 1, 4, 197, 186, 20, 9, 134, 2, 18, 5, 4, 197, 186, 20, 12, 137, 10, 5, 19, 20, 5, 197, 155, 13, 25, 76, 12, 3, 95, 63, 63, 87, 110, 63, 69, 109, 55, 0, 0, 10, 135, 26, 23, 9, 5, 4, 197, 186, 20, 8, 197, 77, 160, 218, 84, 160, 20, 7, 132, 11, 21, 196, 135, 20, 0, 8, 133, 26, 9, 1, 196, 135, 20, 8, 133, 26, 2, 25, 196, 135, 20, 8, 133, 23, 18, 25, 196, 135, 20, 8, 133, 20, 12, 9, 196, 135, 20, 8, 133, 19, 26, 25, 196, 135, 20, 12, 137, 18, 197, 188, 14, 9, 196, 153, 196, 135, 20, 8, 133, 13, 9, 5, 196, 135, 20, 10, 135, 12, 197, 155, 14, 9, 196, 133, 20, 8, 133, 13, 9, 5, 196, 135, 76, 0, 12, 137, 19, 16, 18, 26, 196, 153, 4, 197, 186, 20, 9, 134, 12, 197, 188, 25, 196, 135, 20, 9, 134, 7, 14, 9, 5, 196, 135, 20, 9, 134, 4, 26, 9, 1, 196, 135, 20, 9, 134, 4, 14, 9, 5, 196, 135, 20, 17, 3, 95, 52, 88, 74, 47, 107, 51, 118, 6, 107, 95, 78, 38, 37, 0, 0, 10, 135, 23, 7, 14, 9, 5, 196, 135, 20, 10, 135, 197, 155, 13, 9, 5, 196, 135, 20, 10, 135, 19, 26, 11, 12, 9, 196, 135, 20, 10, 135, 19, 16, 197, 130, 25, 196, 135, 20, 7, 196, 76, 54, 133, 64, 20, 10, 135, 12, 197, 155, 14, 9, 196, 135, 20, 10, 135, 3, 8, 23, 9, 1, 196, 135, 20, 9, 134, 3, 8, 15, 4, 197, 186, 20, 10, 135, 3, 8, 3, 9, 5, 196, 135, 20, 9, 134, 2, 195, 179, 4, 197, 186, 20, 17, 3, 95, 57, 67, 118, 6, 107, 82, 38, 107, 65, 117, 87, 107, 47, 0, 0, 9, 134, 197, 188, 7, 14, 9, 5, 20, 10, 135, 26, 18, 195, 179, 4, 197, 186, 20, 8, 133, 26, 7, 1, 197, 132, 20, 10, 135, 19, 13, 18, 15, 4, 197, 186, 20, 10, 135, 19, 197, 130, 15, 4, 197, 186, 20, 11, 136, 16, 19, 20, 18, 26, 25, 196, 135, 20, 11, 136, 2, 197, 186, 4, 26, 9, 196, 135, 20, 10, 135, 2, 18, 195, 179, 4, 197, 186, 20, 0, 11, 136, 19, 13, 18, 195, 179, 4, 197, 186, 20, 7, 132, 11, 21, 197, 130, 20, 11, 136, 7, 197, 130, 195, 179, 4, 197, 186, 20, 0, 8, 133, 26, 9, 1, 197, 130, 20, 8, 133, 26, 2, 25, 197, 130, 20, 8, 133, 23, 18, 25, 197, 130, 20, 8, 133, 20, 12, 9, 197, 130, 20, 8, 133, 19, 26, 25, 197, 130, 20, 0, 7, 132, 19, 21, 197, 132, 20, 9, 134, 12, 197, 188, 25, 197, 130, 20, 9, 134, 4, 26, 9, 1, 197, 130, 20, 7, 196, 12, 132, 149, 64, 20, 0, 10, 135, 19, 26, 11, 12, 9, 197, 130, 20, 10, 135, 19, 16, 19, 9, 1, 197, 130, 20, 10, 135, 12, 197, 155, 14, 9, 197, 130, 20, 10, 135, 3, 8, 23, 9, 1, 197, 130, 20, 18, 67, 56, 17, 0, 50, 6, 35, 70, 82, 35, 87, 0, 81, 119, 97, 115, 32, 18, 67, 56, 17, 0, 50, 6, 35, 47, 47, 110, 63, 0, 81, 116, 121, 109, 32, 16, 67, 56, 17, 0, 50, 6, 35, 47, 47, 109, 0, 81, 116, 111, 32, 16, 67, 56, 17, 0, 50, 6, 35, 47, 47, 107, 0, 81, 116, 101, 32, 17, 67, 56, 17, 0, 50, 6, 35, 47, 47, 112, 0, 81, 116, 196, 133, 32, 18, 67, 56, 17, 0, 50, 6, 35, 70, 65, 38, 107, 0, 81, 110, 105, 101, 32, 19, 67, 56, 17, 0, 50, 6, 35, 70, 65, 37, 105, 0, 81, 110, 105, 99, 104, 32, 18, 67, 56, 17, 0, 50, 6, 35, 70, 65, 37, 63, 0, 81, 110, 105, 109, 32, 19, 67, 56, 17, 0, 50, 6, 35, 70, 65, 38, 112, 0, 81, 110, 105, 196, 133, 32, 18, 67, 56, 17, 0, 50, 6, 35, 70, 50, 35, 87, 0, 81, 110, 97, 115, 32, 6, 195, 56, 17, 0, 76, 0, 11, 136, 16, 19, 20, 18, 26, 25, 197, 130, 20, 11, 136, 2, 197, 186, 4, 26, 9, 197, 130, 20, 16, 66, 56, 16, 50, 6, 35, 82, 35, 87, 0, 81, 119, 97, 115, 32, 17, 66, 56, 16, 50, 6, 35, 47, 110, 63, 10, 0, 81, 116, 121, 109, 32, 17, 66, 56, 16, 50, 6, 35, 47, 110, 105, 0, 81, 116, 121, 99, 104, 32, 14, 66, 56, 16, 50, 6, 35, 47, 109, 0, 81, 116, 111, 32, 14, 66, 56, 16, 50, 6, 35, 47, 107, 0, 81, 116, 101, 32, 15, 66, 56, 16, 50, 6, 35, 47, 112, 0, 81, 116, 196, 133, 32, 17, 66, 56, 16, 50, 6, 35, 65, 38, 112, 0, 81, 110, 105, 196, 133, 32, 16, 66, 56, 16, 50, 6, 35, 65, 38, 107, 0, 81, 110, 105, 101, 32, 17, 66, 56, 16, 50, 6, 35, 65, 37, 105, 0, 81, 110, 105, 99, 104, 32, 16, 66, 56, 16, 50, 6, 35, 65, 37, 63, 0, 81, 110, 105, 109, 32, 18, 66, 56, 16, 50, 6, 35, 65, 38, 107, 57, 0, 81, 110, 105, 101, 106, 32, 16, 66, 56, 16, 50, 6, 35, 50, 35, 87, 0, 81, 110, 97, 115, 32, 18, 66, 56, 16, 50, 6, 35, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 5, 194, 56, 16, 76, 0, 8, 133, 26, 2, 9, 197, 130, 20, 10, 135, 23, 16, 197, 130, 25, 197, 132, 20, 8, 133, 23, 2, 9, 197, 130, 20, 6, 195, 77, 69, 76, 20, 10, 135, 19, 16, 197, 130, 25, 197, 132, 20, 6, 195, 28, 243, 0, 20, 16, 71, 12, 128, 76, 48, 83, 135, 20, 74, 107, 55, 107, 50, 73, 0, 17, 3, 95, 53, 88, 48, 38, 107, 65, 118, 6, 107, 95, 109, 50, 47, 0, 0, 9, 134, 23, 197, 188, 25, 197, 130, 20, 9, 134, 23, 26, 2, 9, 197, 130, 20, 9, 134, 4, 18, 7, 1, 197, 130, 20, 9, 134, 3, 26, 11, 1, 197, 130, 20, 0, 6, 195, 65, 37, 74, 20, 0, 6, 195, 92, 67, 205, 20, 8, 133, 13, 9, 5, 197, 155, 20, 0, 0, 9, 134, 26, 14, 21, 4, 197, 186, 20, 7, 196, 77, 160, 82, 64, 20, 9, 134, 197, 130, 21, 4, 197, 186, 20, 9, 134, 2, 196, 133, 4, 197, 186, 20, 0, 10, 135, 26, 2, 18, 21, 4, 197, 186, 20, 10, 135, 23, 19, 20, 25, 4, 197, 186, 20, 6, 195, 81, 37, 74, 20, 10, 135, 19, 23, 196, 153, 4, 197, 186, 20, 10, 135, 197, 130, 1, 19, 26, 3, 26, 20, 10, 135, 2, 18, 26, 25, 4, 197, 186, 20, 12, 69, 60, 97, 137, 12, 80, 109, 81, 37, 87, 0, 0, 11, 136, 26, 18, 26, 196, 153, 4, 197, 186, 20, 11, 136, 16, 18, 26, 196, 153, 4, 197, 186, 20, 0, 12, 137, 23, 16, 18, 26, 196, 153, 4, 197, 186, 20, 12, 137, 19, 16, 18, 26, 196, 133, 4, 197, 186, 20, 15, 67, 81, 163, 128, 47, 109, 15, 86, 50, 35, 74, 110, 0, 24, 16, 3, 95, 54, 88, 89, 107, 94, 118, 6, 107, 95, 109, 50, 47, 0, 0, 9, 134, 197, 188, 7, 14, 9, 10, 20, 9, 134, 26, 18, 15, 4, 197, 186, 20, 9, 134, 23, 18, 15, 4, 197, 186, 20, 0, 10, 135, 23, 3, 8, 15, 4, 197, 186, 20, 0, 0, 6, 195, 52, 19, 64, 20, 6, 195, 52, 19, 64, 76, 0, 15, 70, 52, 243, 147, 36, 85, 82, 63, 107, 87, 57, 6, 107, 0, 0, 0, 6, 195, 16, 35, 205, 20, 0, 0, 0, 8, 133, 26, 14, 9, 197, 188, 20, 7, 132, 11, 21, 197, 155, 20, 0, 7, 132, 197, 188, 25, 10, 20, 8, 133, 26, 23, 1, 196, 135, 20, 8, 133, 20, 11, 1, 196, 135, 20, 8, 133, 19, 19, 1, 196, 135, 20, 8, 133, 18, 23, 1, 196, 135, 20, 6, 195, 52, 19, 89, 76, 0, 8, 133, 26, 12, 9, 197, 186, 20, 9, 134, 26, 7, 14, 9, 196, 135, 20, 9, 134, 20, 18, 23, 1, 196, 135, 20, 10, 135, 19, 20, 18, 26, 25, 197, 188, 20, 8, 133, 10, 21, 4, 197, 186, 20, 0, 9, 134, 26, 23, 9, 4, 197, 186, 20, 9, 134, 19, 196, 133, 4, 197, 186, 20, 10, 135, 13, 11, 14, 196, 133, 196, 135, 20, 9, 134, 2, 18, 21, 4, 197, 186, 20, 0, 8, 133, 26, 13, 1, 197, 188, 20, 10, 135, 26, 2, 196, 133, 4, 197, 186, 20, 11, 136, 197, 155, 23, 9, 196, 153, 196, 135, 20, 10, 135, 18, 26, 196, 133, 4, 197, 186, 20, 7, 132, 3, 21, 196, 135, 20, 0, 8, 133, 26, 18, 25, 196, 135, 20, 8, 133, 26, 7, 1, 197, 155, 20, 8, 133, 23, 16, 9, 196, 135, 20, 8, 133, 23, 9, 1, 196, 135, 20, 8, 133, 19, 16, 9, 196, 135, 20, 8, 133, 19, 9, 1, 196, 135, 20, 11, 136, 16, 18, 26, 196, 133, 4, 197, 186, 20, 8, 133, 16, 9, 1, 196, 135, 20, 12, 137, 4, 197, 188, 4, 197, 188, 25, 196, 135, 20, 11, 136, 2, 197, 130, 196, 133, 4, 197, 186, 20, 18, 67, 65, 38, 153, 48, 89, 6, 110, 82, 35, 87, 0, 81, 119, 97, 115, 32, 18, 67, 65, 38, 153, 48, 89, 6, 110, 47, 110, 63, 0, 81, 116, 121, 109, 32, 19, 67, 65, 38, 153, 48, 89, 6, 110, 47, 110, 105, 0, 81, 116, 121, 99, 104, 32, 18, 67, 65, 38, 153, 48, 89, 6, 110, 47, 107, 57, 0, 81, 116, 101, 106, 32, 18, 67, 65, 38, 153, 48, 89, 6, 110, 65, 37, 63, 0, 81, 110, 105, 109, 32, 20, 67, 65, 38, 153, 48, 89, 6, 110, 65, 38, 107, 57, 0, 81, 110, 105, 101, 106, 32, 19, 67, 65, 38, 153, 48, 89, 6, 110, 65, 37, 105, 0, 81, 110, 105, 99, 104, 32, 18, 67, 65, 38, 153, 48, 89, 6, 110, 50, 35, 87, 0, 81, 110, 97, 115, 32, 20, 67, 65, 38, 153, 48, 89, 6, 110, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 6, 195, 65, 38, 153, 76, 0, 12, 137, 26, 2, 197, 130, 196, 133, 4, 197, 186, 20, 12, 137, 23, 16, 18, 26, 196, 133, 4, 197, 186, 20, 15, 67, 13, 68, 140, 49, 6, 109, 50, 47, 51, 109, 55, 0, 17, 17, 3, 95, 56, 88, 109, 95, 107, 63, 118, 6, 107, 95, 109, 50, 47, 0, 0, 9, 134, 26, 13, 18, 15, 197, 186, 20, 10, 135, 197, 155, 23, 9, 5, 196, 135, 20, 10, 135, 19, 26, 3, 26, 25, 196, 135, 20, 10, 135, 12, 7, 14, 9, 5, 196, 135, 20, 10, 135, 12, 7, 14, 196, 133, 196, 135, 20, 0, 11, 136, 26, 7, 23, 1, 197, 130, 196, 135, 20, 11, 136, 20, 3, 8, 14, 9, 5, 196, 135, 20, 10, 135, 13, 197, 155, 3, 9, 19, 26, 20, 0, 12, 137, 23, 19, 26, 3, 26, 196, 133, 196, 135, 20, 9, 134, 3, 8, 3, 5, 197, 132, 20, 9, 67, 12, 195, 213, 49, 55, 40, 0, 0, 8, 133, 26, 18, 25, 197, 130, 20, 8, 133, 23, 16, 9, 197, 130, 20, 8, 133, 23, 9, 1, 197, 130, 20, 8, 133, 19, 16, 9, 197, 130, 20, 8, 133, 19, 9, 1, 197, 130, 20, 8, 133, 16, 9, 1, 197, 130, 20, 26, 12, 19, 16, 195, 169, 3, 9, 1, 12, 9, 20, 195, 169, 87, 48, 107, 87, 57, 35, 55, 37, 47, 6, 107, 0, 0, 0, 10, 135, 12, 7, 14, 196, 133, 197, 130, 20, 0, 11, 136, 7, 18, 26, 13, 9, 1, 197, 130, 20, 5, 194, 36, 208, 72, 0, 8, 133, 197, 188, 25, 197, 130, 20, 8, 133, 26, 23, 1, 197, 130, 20, 12, 137, 23, 19, 26, 3, 26, 196, 133, 197, 130, 20, 8, 133, 20, 11, 1, 197, 130, 20, 8, 133, 19, 19, 1, 197, 130, 20, 8, 133, 18, 23, 1, 197, 130, 20, 19, 3, 95, 57, 88, 118, 107, 82, 38, 107, 65, 118, 6, 107, 95, 109, 50, 47, 0, 0, 9, 134, 26, 7, 14, 9, 197, 130, 20, 9, 134, 20, 18, 23, 1, 197, 130, 20, 7, 196, 17, 37, 201, 40, 20, 0, 10, 135, 13, 11, 14, 196, 133, 197, 130, 20, 6, 195, 52, 145, 74, 20, 13, 69, 24, 243, 132, 84, 80, 81, 112, 70, 6, 37, 0, 12, 69, 88, 243, 196, 60, 240, 82, 40, 70, 40, 0, 0, 9, 198, 65, 38, 153, 45, 38, 128, 20, 8, 133, 14, 9, 5, 197, 155, 20, 7, 132, 9, 4, 197, 186, 20, 0, 11, 136, 16, 9, 15, 197, 130, 2, 25, 13, 20, 6, 195, 52, 145, 76, 20, 12, 137, 4, 197, 188, 4, 197, 188, 25, 197, 130, 20, 0, 9, 134, 197, 155, 12, 5, 19, 26, 20, 0, 8, 197, 17, 33, 206, 36, 80, 20, 0, 5, 194, 53, 80, 72, 12, 3, 95, 63, 65, 55, 37, 47, 107, 51, 35, 0, 0, 0, 9, 134, 18, 195, 179, 4, 197, 186, 20, 0, 10, 135, 23, 18, 195, 179, 4, 197, 186, 20, 6, 195, 80, 176, 74, 20, 10, 135, 19, 3, 8, 15, 4, 197, 186, 20, 10, 135, 7, 18, 195, 179, 4, 197, 186, 20, 0, 6, 195, 80, 176, 77, 20, 11, 136, 19, 197, 130, 195, 179, 4, 197, 186, 20, 11, 136, 16, 197, 130, 195, 179, 4, 197, 186, 20, 10, 135, 12, 197, 155, 14, 9, 196, 153, 20, 0, 12, 137, 19, 16, 197, 130, 195, 179, 4, 197, 186, 20, 12, 137, 19, 3, 8, 197, 130, 15, 4, 197, 186, 20, 12, 137, 3, 8, 197, 130, 195, 179, 4, 197, 186, 20, 0, 13, 138, 19, 3, 8, 197, 130, 195, 179, 4, 197, 186, 20, 7, 196, 52, 20, 148, 92, 20, 0, 0, 0, 0, 0, 9, 134, 26, 7, 18, 25, 197, 186, 20, 0, 9, 134, 26, 23, 9, 5, 197, 155, 20, 6, 195, 105, 112, 66, 20, 10, 135, 19, 11, 15, 197, 132, 3, 26, 20, 0, 7, 132, 23, 5, 197, 186, 20, 0, 11, 136, 19, 20, 18, 26, 196, 153, 197, 155, 20, 9, 134, 18, 197, 188, 14, 196, 133, 20, 17, 4, 95, 15, 7, 15, 86, 109, 79, 6, 109, 50, 78, 38, 107, 63, 0, 0, 9, 134, 197, 188, 18, 5, 19, 26, 20, 6, 195, 104, 227, 205, 20, 0, 7, 132, 16, 14, 196, 133, 20, 0, 10, 135, 7, 23, 1, 197, 130, 196, 135, 20, 0, 6, 195, 93, 67, 208, 20, 10, 199, 52, 144, 210, 61, 51, 198, 80, 65, 0, 10, 135, 11, 20, 195, 179, 18, 196, 133, 76, 0, 6, 195, 105, 114, 74, 20, 8, 197, 92, 144, 200, 73, 160, 20, 13, 137, 16, 18, 26, 5, 3, 9, 5, 197, 188, 76, 8, 0, 11, 136, 23, 16, 5, 197, 130, 26, 197, 130, 20, 11, 136, 19, 16, 5, 197, 130, 26, 197, 130, 20, 0, 13, 138, 14, 9, 5, 11, 20, 195, 179, 18, 196, 133, 76, 0, 9, 134, 26, 13, 1, 18, 197, 130, 20, 6, 195, 17, 33, 193, 20, 0, 10, 135, 16, 5, 197, 130, 26, 197, 130, 20, 6, 195, 64, 19, 0, 20, 8, 197, 12, 128, 82, 13, 160, 20, 0, 0, 11, 136, 7, 18, 26, 13, 9, 196, 133, 3, 20, 0, 6, 195, 105, 114, 69, 20, 6, 195, 73, 114, 69, 20, 0, 8, 133, 19, 11, 1, 197, 188, 20, 0, 9, 198, 104, 226, 69, 52, 54, 128, 20, 11, 136, 26, 13, 9, 196, 153, 11, 3, 26, 20, 9, 198, 81, 35, 211, 104, 54, 128, 20, 0, 8, 133, 19, 11, 1, 197, 186, 20, 10, 199, 13, 165, 5, 73, 148, 212, 84, 65, 0, 7, 196, 9, 166, 67, 104, 20, 12, 68, 40, 84, 146, 100, 73, 107, 51, 110, 0, 9, 10, 68, 40, 84, 146, 100, 73, 107, 51, 0, 0, 0, 9, 134, 26, 2, 12, 9, 197, 188, 20, 15, 67, 65, 35, 195, 48, 34, 6, 109, 115, 107, 50, 47, 0, 24, 0, 0, 7, 196, 105, 112, 82, 104, 20, 7, 196, 76, 147, 210, 8, 20, 17, 4, 95, 48, 77, 52, 69, 38, 37, 55, 57, 6, 109, 50, 40, 81, 0, 0, 6, 195, 73, 114, 74, 20, 16, 67, 65, 35, 198, 48, 51, 109, 81, 6, 107, 87, 109, 51, 0, 24, 0, 9, 198, 52, 147, 137, 53, 83, 64, 65, 15, 70, 52, 21, 82, 20, 83, 128, 63, 109, 51, 6, 37, 50, 0, 17, 4, 95, 48, 77, 50, 63, 38, 37, 55, 57, 6, 109, 50, 40, 81, 0, 0, 9, 67, 88, 243, 128, 81, 109, 50, 0, 18, 4, 95, 48, 77, 51, 63, 38, 37, 55, 57, 6, 35, 51, 70, 40, 81, 0, 0, 0, 15, 4, 95, 48, 77, 49, 47, 110, 95, 6, 107, 50, 115, 110, 0, 0, 5, 194, 60, 64, 72, 14, 4, 95, 2, 18, 22, 69, 51, 6, 107, 82, 37, 87, 0, 0, 8, 133, 23, 12, 9, 197, 186, 20, 8, 133, 3, 5, 4, 197, 186, 20, 0, 9, 134, 26, 23, 9, 5, 197, 186, 20, 9, 134, 26, 19, 1, 4, 197, 186, 20, 9, 134, 23, 19, 1, 4, 197, 186, 20, 0, 8, 133, 26, 23, 1, 197, 188, 20, 9, 134, 197, 130, 11, 1, 196, 135, 20, 0, 8, 133, 2, 18, 14, 196, 133, 20, 0, 9, 134, 20, 3, 8, 14, 196, 133, 20, 9, 134, 19, 11, 12, 14, 196, 133, 20, 18, 71, 13, 35, 201, 77, 48, 78, 80, 49, 51, 40, 35, 87, 6, 35, 66, 0, 0, 6, 195, 104, 116, 129, 20, 9, 134, 7, 18, 15, 4, 197, 186, 20, 9, 134, 2, 18, 15, 4, 197, 186, 20, 0, 8, 133, 19, 13, 1, 197, 188, 20, 17, 8, 4, 5, 12, 39, 1, 18, 20, 5, 70, 107, 55, 6, 35, 51, 0, 0, 8, 133, 197, 130, 197, 188, 5, 20, 8, 133, 11, 12, 14, 196, 133, 20, 14, 3, 197, 155, 23, 95, 82, 38, 107, 50, 47, 110, 0, 24, 0, 9, 134, 16, 3, 8, 14, 196, 133, 20, 17, 70, 24, 16, 201, 20, 225, 9, 81, 35, 87, 57, 107, 50, 70, 37, 0, 0, 8, 133, 19, 19, 196, 133, 3, 20, 0, 7, 132, 16, 14, 196, 153, 20, 0, 11, 136, 26, 26, 9, 196, 133, 2, 197, 130, 20, 9, 134, 197, 130, 11, 1, 197, 132, 20, 0, 24, 3, 197, 155, 16, 95, 82, 38, 107, 50, 47, 107, 57, 15, 48, 35, 63, 38, 107, 65, 117, 37, 0, 24, 0, 9, 134, 26, 4, 1, 18, 197, 130, 20, 9, 134, 23, 4, 1, 18, 197, 130, 20, 6, 195, 81, 37, 193, 20, 9, 134, 197, 130, 11, 1, 197, 130, 20, 0, 10, 135, 26, 13, 1, 18, 26, 197, 130, 20, 0, 10, 135, 197, 155, 16, 9, 196, 133, 3, 20, 5, 194, 52, 144, 72, 0, 9, 134, 18, 197, 188, 14, 196, 153, 20, 11, 136, 12, 197, 155, 14, 9, 196, 133, 3, 20, 0, 0, 10, 135, 14, 9, 15, 197, 132, 3, 26, 20, 15, 69, 16, 83, 5, 80, 80, 70, 37, 55, 6, 107, 57, 47, 0, 0, 0, 0, 7, 196, 77, 1, 83, 104, 20, 0, 14, 69, 12, 194, 67, 32, 80, 49, 55, 37, 89, 6, 107, 0, 11, 136, 2, 25, 12, 9, 197, 155, 13, 25, 76, 0, 12, 137, 19, 3, 8, 12, 9, 197, 155, 13, 25, 20, 12, 137, 19, 26, 197, 130, 25, 197, 155, 13, 25, 20, 5, 194, 53, 144, 76, 0, 6, 195, 105, 112, 76, 20, 10, 135, 19, 16, 18, 196, 153, 197, 188, 20, 0, 0, 8, 133, 19, 11, 196, 133, 16, 20, 0, 9, 198, 52, 22, 9, 53, 83, 64, 65, 0, 9, 67, 61, 85, 0, 35, 58, 47, 0, 0, 0, 8, 197, 76, 180, 154, 101, 112, 20, 8, 133, 19, 9, 196, 133, 16, 20, 0, 0, 6, 195, 16, 192, 64, 72, 6, 195, 32, 64, 64, 17, 0, 7, 196, 77, 67, 9, 40, 20, 9, 134, 4, 18, 197, 188, 25, 10, 20, 13, 68, 88, 242, 76, 4, 82, 40, 35, 55, 35, 0, 67, 0, 9, 134, 26, 14, 9, 5, 197, 155, 20, 9, 134, 23, 14, 9, 5, 197, 155, 20, 9, 134, 23, 7, 18, 15, 196, 135, 20, 9, 134, 196, 135, 16, 15, 196, 135, 20, 9, 134, 3, 8, 12, 15, 196, 135, 20, 8, 197, 9, 38, 141, 36, 160, 20, 0, 10, 135, 19, 3, 8, 12, 15, 196, 135, 20, 7, 132, 16, 195, 179, 10, 20, 0, 7, 132, 12, 15, 196, 135, 20, 6, 195, 28, 224, 64, 20, 10, 135, 4, 26, 9, 5, 18, 197, 188, 20, 6, 195, 60, 224, 64, 76, 0, 9, 134, 26, 8, 1, 197, 132, 2, 20, 11, 136, 26, 4, 26, 9, 5, 18, 197, 188, 20, 0, 10, 135, 26, 13, 9, 5, 18, 197, 186, 20, 9, 134, 26, 197, 130, 15, 196, 135, 20, 8, 197, 77, 160, 218, 100, 160, 20, 9, 134, 19, 20, 18, 15, 196, 135, 20, 9, 134, 19, 16, 18, 15, 196, 135, 20, 8, 197, 76, 180, 154, 100, 160, 20, 8, 197, 17, 33, 206, 36, 160, 20, 9, 134, 2, 197, 130, 15, 196, 135, 20, 0, 7, 132, 12, 15, 197, 130, 20, 0, 0, 9, 134, 19, 16, 18, 15, 197, 130, 20, 7, 132, 18, 15, 197, 132, 20, 0, 6, 195, 52, 20, 154, 20, 0, 11, 136, 26, 14, 9, 195, 179, 19, 197, 130, 20, 11, 136, 23, 14, 9, 195, 179, 19, 197, 130, 20, 0, 6, 195, 60, 225, 64, 76, 0, 9, 134, 23, 7, 18, 15, 197, 130, 20, 7, 132, 20, 15, 197, 132, 20, 7, 196, 77, 3, 15, 52, 20, 9, 134, 18, 197, 188, 15, 197, 130, 20, 9, 134, 13, 9, 12, 11, 197, 130, 20, 9, 134, 13, 4, 12, 15, 197, 130, 20, 8, 133, 197, 130, 195, 179, 23, 20, 9, 134, 196, 135, 16, 15, 197, 130, 20, 9, 134, 3, 8, 12, 15, 197, 130, 20, 9, 198, 40, 243, 129, 80, 128, 78, 65, 0, 10, 135, 26, 13, 195, 179, 7, 197, 130, 20, 10, 135, 26, 13, 9, 12, 11, 197, 130, 20, 10, 135, 19, 3, 8, 12, 15, 197, 130, 20, 6, 195, 65, 53, 74, 20, 8, 197, 45, 2, 79, 73, 160, 20, 10, 135, 11, 12, 196, 153, 19, 197, 130, 20, 0, 11, 136, 23, 26, 13, 195, 179, 7, 197, 130, 20, 9, 134, 19, 20, 18, 15, 197, 132, 20, 11, 136, 19, 11, 12, 196, 153, 19, 197, 130, 20, 9, 134, 11, 197, 130, 15, 197, 132, 20, 9, 134, 3, 8, 18, 15, 197, 132, 20, 8, 133, 2, 18, 14, 196, 153, 20, 6, 194, 56, 144, 72, 23, 0, 6, 195, 104, 115, 204, 20, 6, 195, 80, 194, 64, 20, 10, 135, 19, 11, 197, 130, 15, 197, 132, 20, 9, 134, 19, 11, 12, 14, 196, 153, 20, 10, 135, 19, 3, 8, 18, 15, 197, 132, 20, 6, 195, 53, 146, 128, 20, 15, 70, 40, 80, 78, 21, 69, 5, 88, 35, 50, 6, 107, 47, 0, 0, 9, 134, 20, 1, 197, 132, 3, 26, 20, 6, 195, 28, 226, 69, 20, 0, 0, 9, 198, 76, 50, 12, 5, 54, 128, 20, 13, 5, 3, 1, 6, 195, 169, 49, 35, 81, 107, 0, 66, 0, 8, 133, 19, 20, 195, 179, 10, 20, 6, 195, 45, 82, 128, 20, 6, 195, 60, 226, 64, 76, 10, 199, 16, 148, 195, 61, 97, 82, 100, 66, 0, 6, 195, 80, 179, 205, 20, 0, 24, 69, 65, 38, 133, 16, 80, 48, 89, 107, 70, 6, 107, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 23, 69, 65, 38, 133, 16, 80, 48, 89, 107, 70, 6, 107, 63, 50, 112, 0, 81, 109, 110, 196, 133, 32, 0, 7, 132, 18, 195, 179, 2, 20, 11, 136, 3, 8, 197, 130, 5, 16, 3, 26, 20, 0, 8, 133, 23, 18, 195, 179, 2, 20, 0, 6, 195, 28, 224, 77, 20, 0, 8, 197, 65, 53, 18, 105, 144, 20, 6, 195, 28, 224, 74, 20, 0, 8, 133, 11, 12, 14, 196, 153, 20, 16, 4, 95, 3, 9, 18, 86, 70, 6, 35, 89, 78, 38, 107, 63, 0, 0, 8, 133, 26, 4, 195, 179, 2, 20, 9, 134, 16, 3, 8, 14, 196, 153, 20, 10, 199, 76, 145, 68, 20, 212, 197, 80, 65, 0, 7, 196, 92, 145, 76, 8, 20, 9, 198, 81, 38, 133, 77, 160, 218, 20, 0, 6, 195, 76, 229, 74, 20, 0, 0, 9, 134, 20, 3, 8, 14, 196, 153, 20, 7, 132, 2, 15, 196, 135, 20, 15, 67, 52, 193, 0, 63, 37, 55, 57, 35, 51, 70, 40, 81, 0, 0, 9, 134, 23, 18, 196, 153, 3, 26, 20, 6, 195, 80, 181, 201, 20, 7, 196, 76, 180, 153, 40, 20, 8, 133, 11, 14, 15, 196, 135, 20, 8, 133, 7, 18, 15, 196, 135, 20, 8, 133, 7, 14, 15, 196, 135, 20, 8, 133, 4, 2, 15, 196, 135, 20, 8, 133, 2, 18, 15, 196, 135, 20, 11, 68, 76, 48, 78, 20, 87, 49, 35, 50, 0, 0, 9, 134, 11, 197, 130, 15, 197, 155, 20, 9, 134, 7, 18, 26, 15, 196, 135, 20, 0, 0, 8, 133, 23, 16, 195, 179, 10, 20, 8, 133, 19, 16, 195, 179, 10, 20, 7, 132, 14, 15, 197, 155, 20, 7, 132, 4, 15, 196, 135, 20, 18, 71, 12, 128, 78, 80, 147, 12, 100, 89, 35, 50, 47, 37, 57, 37, 0, 67, 0, 7, 196, 45, 37, 83, 104, 20, 19, 67, 13, 84, 129, 49, 37, 51, 35, 87, 35, 109, 0, 81, 195, 167, 97, 111, 32, 11, 67, 40, 244, 197, 105, 109, 86, 6, 107, 0, 0, 9, 134, 23, 19, 20, 15, 196, 135, 20, 9, 134, 23, 16, 18, 15, 197, 155, 20, 9, 134, 19, 197, 130, 15, 196, 135, 20, 9, 134, 19, 11, 14, 15, 196, 135, 20, 9, 134, 16, 3, 8, 15, 196, 135, 20, 6, 195, 12, 226, 74, 20, 6, 195, 8, 240, 218, 20, 0, 10, 135, 26, 7, 197, 130, 15, 197, 155, 20, 7, 132, 4, 15, 197, 130, 20, 15, 70, 12, 128, 66, 48, 148, 192, 89, 35, 69, 55, 37, 0, 66, 0, 8, 133, 12, 5, 7, 197, 130, 20, 9, 134, 2, 196, 153, 4, 196, 133, 76, 17, 4, 95, 19, 20, 11, 87, 49, 51, 107, 95, 55, 6, 109, 50, 107, 0, 0, 9, 134, 23, 19, 20, 15, 197, 130, 20, 9, 134, 19, 197, 130, 15, 197, 130, 20, 9, 134, 16, 3, 8, 15, 197, 130, 20, 0, 10, 135, 23, 9, 196, 153, 4, 197, 130, 20, 6, 195, 28, 226, 74, 20, 8, 133, 2, 18, 15, 197, 132, 20, 14, 4, 95, 1, 3, 21, 10, 6, 109, 87, 47, 51, 107, 0, 0, 11, 136, 16, 18, 26, 196, 133, 7, 197, 130, 20, 20, 3, 95, 195, 179, 4, 40, 10, 49, 51, 107, 87, 49, 109, 82, 6, 35, 50, 107, 0, 0, 12, 137, 23, 16, 18, 26, 196, 133, 7, 197, 130, 20, 12, 137, 19, 16, 18, 26, 196, 133, 7, 197, 130, 20, 8, 133, 16, 1, 19, 197, 130, 20, 8, 133, 7, 18, 15, 197, 130, 20, 8, 133, 7, 14, 15, 197, 130, 20, 8, 133, 4, 2, 15, 197, 130, 20, 0, 9, 134, 26, 7, 1, 19, 197, 130, 20, 9, 134, 13, 195, 179, 7, 197, 130, 20, 9, 134, 7, 18, 26, 15, 197, 130, 20, 10, 135, 4, 197, 186, 7, 14, 9, 5, 20, 0, 10, 135, 23, 13, 1, 18, 26, 197, 130, 20, 10, 135, 4, 18, 197, 188, 15, 197, 130, 20, 0, 7, 132, 2, 195, 179, 10, 20, 0, 10, 135, 19, 16, 5, 197, 130, 197, 132, 20, 8, 133, 18, 196, 153, 3, 26, 20, 8, 133, 13, 196, 153, 3, 26, 20, 8, 133, 10, 196, 153, 3, 26, 20, 9, 134, 2, 197, 186, 4, 26, 9, 20, 9, 134, 13, 9, 1, 197, 130, 25, 76, 0, 9, 134, 26, 7, 14, 195, 179, 10, 20, 0, 9, 134, 19, 16, 18, 15, 197, 155, 20, 14, 69, 88, 149, 129, 12, 80, 82, 37, 82, 35, 74, 107, 0, 0, 11, 136, 23, 4, 26, 9, 196, 153, 3, 26, 20, 7, 132, 4, 195, 179, 10, 20, 0, 12, 137, 4, 197, 186, 23, 9, 196, 153, 3, 26, 20, 16, 4, 95, 18, 14, 7, 86, 49, 6, 40, 58, 78, 38, 107, 63, 0, 0, 9, 134, 4, 18, 196, 153, 3, 26, 20, 0, 9, 134, 7, 197, 130, 15, 197, 155, 20, 10, 135, 4, 197, 186, 7, 14, 9, 10, 20, 10, 135, 2, 18, 26, 196, 153, 3, 26, 20, 17, 70, 12, 243, 5, 76, 192, 87, 49, 109, 55, 107, 87, 55, 109, 58, 0, 0, 9, 67, 72, 240, 203, 34, 109, 49, 0, 17, 70, 4, 229, 8, 60, 230, 64, 107, 50, 47, 109, 50, 110, 0, 65, 9, 14, 70, 4, 229, 8, 60, 230, 64, 107, 50, 47, 109, 50, 0, 0, 8, 133, 26, 18, 195, 179, 2, 20, 0, 7, 196, 13, 166, 73, 52, 76, 0, 0, 0, 9, 134, 2, 196, 153, 4, 196, 153, 76, 0, 7, 132, 20, 196, 153, 16, 20, 10, 67, 64, 192, 89, 48, 55, 107, 57, 0, 0, 8, 197, 76, 180, 151, 5, 112, 20, 0, 0, 0, 10, 135, 19, 26, 197, 130, 25, 2, 25, 20, 7, 196, 93, 51, 149, 40, 20, 9, 198, 5, 32, 200, 37, 33, 74, 67, 0, 9, 134, 16, 9, 3, 8, 196, 135, 20, 0, 0, 0, 7, 196, 76, 176, 67, 104, 20, 0, 11, 136, 2, 197, 188, 4, 197, 188, 196, 133, 20, 0, 9, 134, 13, 14, 195, 179, 197, 188, 20, 8, 133, 11, 197, 130, 1, 13, 20, 0, 10, 135, 20, 18, 23, 195, 179, 197, 188, 20, 8, 133, 7, 14, 196, 153, 2, 20, 9, 134, 2, 25, 197, 130, 5, 13, 76, 0, 21, 67, 56, 17, 5, 50, 35, 70, 6, 107, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 20, 67, 56, 17, 5, 50, 35, 70, 6, 107, 63, 50, 112, 0, 81, 109, 110, 196, 133, 32, 11, 136, 11, 20, 195, 179, 18, 25, 3, 8, 76, 14, 68, 52, 144, 77, 36, 63, 35, 57, 6, 35, 63, 37, 0, 13, 68, 20, 161, 67, 80, 37, 88, 6, 107, 49, 47, 0, 0, 10, 135, 26, 4, 5, 3, 8, 197, 130, 20, 6, 195, 52, 20, 218, 76, 0, 11, 136, 197, 155, 3, 9, 3, 8, 197, 130, 20, 21, 4, 95, 1, 3, 50, 99, 4, 40, 66, 79, 35, 51, 6, 40, 63, 55, 35, 58, 47, 0, 0, 9, 134, 12, 15, 197, 130, 2, 25, 20, 14, 139, 14, 9, 5, 11, 20, 195, 179, 18, 25, 3, 8, 76, 0, 10, 135, 26, 9, 15, 197, 130, 2, 25, 20, 10, 135, 26, 4, 15, 197, 130, 2, 25, 20, 10, 135, 20, 12, 15, 197, 130, 2, 25, 20, 10, 135, 19, 20, 15, 197, 130, 2, 25, 20, 10, 135, 14, 9, 11, 197, 130, 2, 25, 20, 0, 11, 136, 19, 16, 18, 15, 197, 130, 2, 25, 20, 11, 136, 4, 18, 7, 15, 197, 130, 2, 25, 20, 11, 136, 3, 26, 11, 15, 197, 130, 2, 25, 20, 8, 197, 104, 115, 210, 77, 160, 20, 6, 195, 44, 229, 74, 20, 10, 135, 3, 9, 5, 18, 16, 197, 130, 20, 0, 15, 66, 64, 144, 48, 107, 37, 38, 6, 107, 87, 0, 81, 115, 32, 12, 137, 26, 18, 195, 179, 19, 197, 130, 2, 25, 20, 12, 137, 23, 18, 195, 179, 19, 197, 130, 2, 25, 20, 12, 137, 19, 16, 19, 9, 15, 197, 130, 2, 25, 20, 12, 137, 19, 16, 9, 5, 11, 197, 130, 2, 25, 20, 12, 137, 14, 9, 195, 179, 19, 197, 130, 2, 25, 20, 12, 137, 3, 8, 23, 9, 15, 197, 130, 2, 25, 20, 11, 66, 60, 176, 109, 49, 6, 107, 57, 0, 42, 11, 66, 60, 176, 109, 49, 109, 58, 109, 0, 24, 6, 194, 80, 16, 72, 12, 0, 13, 138, 26, 14, 9, 195, 179, 19, 197, 130, 2, 25, 20, 13, 138, 23, 26, 18, 195, 179, 19, 197, 130, 2, 25, 20, 13, 138, 23, 14, 9, 195, 179, 19, 197, 130, 2, 25, 20, 13, 138, 19, 20, 18, 26, 5, 7, 197, 130, 2, 25, 20, 12, 137, 197, 155, 3, 9, 5, 18, 16, 197, 130, 20, 12, 137, 16, 9, 5, 18, 26, 3, 8, 197, 130, 20, 0, 14, 139, 23, 26, 14, 9, 195, 179, 19, 197, 130, 2, 25, 20, 9, 198, 93, 53, 18, 104, 83, 0, 20, 0, 15, 140, 26, 197, 188, 195, 179, 197, 130, 11, 197, 130, 2, 25, 20, 6, 195, 64, 197, 74, 20, 0, 0, 8, 133, 13, 18, 15, 197, 186, 20, 8, 133, 12, 197, 188, 25, 10, 20, 13, 138, 2, 196, 153, 4, 26, 9, 5, 3, 9, 5, 76, 0, 18, 72, 40, 16, 209, 84, 83, 9, 56, 80, 88, 35, 49, 55, 6, 37, 50, 0, 0, 6, 195, 65, 147, 0, 20, 12, 69, 12, 128, 82, 52, 80, 89, 35, 51, 63, 0, 19, 71, 8, 16, 203, 77, 0, 67, 20, 69, 6, 107, 49, 87, 48, 107, 57, 87, 0, 0, 9, 134, 26, 13, 195, 179, 197, 188, 20, 0, 10, 135, 23, 4, 18, 195, 179, 197, 188, 20, 0, 10, 67, 12, 243, 1, 49, 109, 55, 35, 0, 0, 10, 135, 19, 20, 23, 195, 179, 18, 26, 20, 0, 11, 136, 19, 20, 3, 8, 195, 179, 18, 26, 20, 9, 134, 3, 26, 197, 130, 1, 16, 20, 0, 0, 7, 196, 104, 36, 153, 48, 20, 0, 7, 2, 196, 135, 117, 37, 0, 0, 0, 13, 67, 52, 164, 128, 63, 6, 35, 57, 109, 51, 0, 24, 6, 2, 196, 133, 112, 0, 0, 0, 0, 8, 133, 197, 155, 12, 196, 133, 20, 0, 0, 7, 196, 104, 34, 69, 12, 20, 0, 8, 197, 76, 50, 12, 4, 160, 20, 9, 134, 197, 130, 11, 15, 196, 135, 20, 10, 2, 195, 151, 51, 6, 35, 86, 110, 0, 0, 10, 135, 14, 9, 5, 197, 155, 196, 135, 20, 11, 136, 11, 18, 26, 25, 23, 4, 197, 186, 20, 7, 2, 197, 132, 65, 37, 0, 0, 10, 135, 23, 26, 13, 195, 179, 197, 188, 20, 11, 136, 19, 3, 26, 25, 197, 155, 196, 135, 20, 11, 136, 7, 14, 9, 5, 197, 155, 196, 135, 20, 9, 134, 2, 25, 197, 130, 1, 13, 76, 10, 199, 5, 32, 200, 36, 66, 65, 44, 67, 5, 130, 196, 141, 43, 5, 130, 196, 141, 43, 0, 12, 137, 23, 7, 14, 9, 5, 197, 155, 196, 135, 20, 9, 134, 197, 130, 11, 15, 197, 130, 20, 9, 134, 3, 9, 3, 8, 197, 130, 20, 7, 2, 197, 130, 58, 110, 0, 0, 8, 197, 12, 128, 197, 77, 160, 20, 0, 11, 136, 7, 197, 130, 21, 3, 8, 197, 130, 20, 0, 9, 134, 23, 25, 197, 130, 2, 25, 20, 9, 134, 18, 25, 197, 130, 2, 25, 20, 9, 134, 16, 9, 197, 130, 2, 25, 20, 9, 134, 11, 21, 197, 130, 2, 25, 20, 0, 10, 135, 26, 9, 1, 197, 130, 2, 25, 20, 10, 135, 26, 2, 25, 197, 130, 2, 25, 20, 10, 135, 23, 18, 25, 197, 130, 2, 25, 20, 10, 135, 20, 12, 9, 197, 130, 2, 25, 20, 10, 135, 19, 26, 25, 197, 130, 2, 25, 20, 10, 135, 16, 19, 21, 197, 130, 2, 25, 20, 10, 135, 16, 18, 1, 197, 130, 2, 25, 20, 10, 135, 16, 12, 21, 197, 130, 2, 25, 20, 10, 135, 13, 9, 1, 197, 130, 2, 25, 20, 10, 135, 11, 18, 25, 197, 130, 2, 25, 20, 9, 134, 23, 197, 155, 3, 9, 2, 20, 7, 196, 81, 37, 207, 52, 20, 11, 68, 4, 194, 67, 20, 107, 55, 37, 87, 0, 0, 11, 136, 26, 197, 188, 25, 197, 130, 2, 25, 20, 11, 136, 26, 197, 188, 21, 197, 130, 2, 25, 20, 11, 136, 26, 7, 18, 1, 197, 130, 2, 25, 20, 11, 136, 23, 19, 26, 25, 197, 130, 2, 25, 20, 11, 136, 23, 7, 18, 1, 197, 130, 2, 25, 20, 11, 136, 19, 16, 18, 1, 197, 130, 2, 25, 20, 11, 136, 12, 197, 188, 25, 197, 130, 2, 25, 20, 11, 136, 4, 26, 9, 1, 197, 130, 2, 25, 20, 11, 136, 4, 14, 9, 1, 197, 130, 2, 25, 20, 11, 136, 3, 26, 3, 9, 197, 130, 2, 25, 20, 8, 197, 105, 115, 5, 13, 160, 20, 8, 197, 81, 38, 133, 77, 160, 20, 10, 135, 20, 196, 153, 3, 8, 197, 130, 20, 8, 197, 64, 50, 1, 77, 160, 20, 14, 2, 194, 167, 48, 35, 51, 6, 35, 79, 51, 35, 81, 0, 16, 2, 195, 159, 89, 4, 35, 34, 81, 107, 87, 10, 6, 107, 87, 0, 0, 12, 137, 23, 4, 26, 9, 1, 197, 130, 2, 25, 20, 12, 137, 197, 155, 13, 9, 1, 197, 130, 2, 25, 20, 12, 137, 19, 26, 11, 12, 9, 197, 130, 2, 25, 20, 12, 137, 19, 16, 19, 9, 1, 197, 130, 2, 25, 20, 12, 137, 19, 197, 130, 1, 2, 197, 130, 2, 25, 20, 12, 137, 12, 197, 155, 14, 9, 197, 130, 2, 25, 20, 12, 137, 3, 8, 23, 9, 1, 197, 130, 2, 25, 20, 12, 137, 3, 8, 3, 9, 1, 197, 130, 2, 25, 20, 12, 2, 194, 164, 82, 35, 55, 6, 40, 47, 35, 0, 0, 13, 138, 23, 16, 5, 197, 130, 26, 197, 130, 2, 25, 20, 13, 138, 19, 16, 5, 197, 130, 26, 197, 130, 2, 25, 20, 13, 138, 16, 19, 20, 18, 26, 25, 197, 130, 2, 25, 20, 13, 138, 3, 8, 18, 26, 3, 9, 197, 130, 2, 25, 20, 13, 138, 2, 197, 186, 4, 26, 9, 197, 130, 2, 25, 20, 8, 133, 21, 10, 4, 197, 186, 20, 8, 2, 194, 165, 57, 107, 50, 0, 0, 9, 134, 14, 1, 10, 4, 197, 186, 20, 33, 68, 12, 144, 197, 72, 115, 4, 37, 115, 107, 51, 49, 40, 63, 49, 6, 35, 58, 55, 107, 0, 82, 99, 117, 109, 32, 99, 97, 117, 108, 101, 32, 9, 2, 194, 162, 115, 107, 50, 47, 0, 0, 11, 136, 2, 197, 188, 4, 197, 188, 196, 153, 20, 9, 2, 194, 163, 81, 40, 50, 47, 0, 0, 15, 70, 12, 245, 78, 81, 38, 64, 49, 35, 50, 47, 51, 110, 0, 0, 25, 2, 194, 161, 109, 70, 82, 51, 4, 109, 47, 50, 110, 15, 82, 110, 49, 89, 6, 110, 49, 65, 37, 49, 0, 0, 7, 196, 92, 34, 69, 12, 20, 7, 196, 76, 180, 154, 100, 20, 11, 136, 13, 9, 1, 197, 188, 4, 197, 188, 20, 16, 7, 3, 12, 9, 3, 8, 195, 169, 49, 55, 37, 89, 6, 107, 0, 15, 2, 194, 174, 86, 35, 87, 74, 107, 88, 6, 109, 50, 110, 0, 5, 130, 195, 166, 43, 5, 130, 195, 166, 43, 0, 12, 137, 26, 13, 9, 15, 197, 188, 4, 197, 188, 20, 8, 197, 76, 180, 154, 101, 0, 20, 17, 2, 194, 175, 50, 35, 70, 49, 51, 107, 95, 55, 6, 107, 65, 107, 0, 0, 15, 70, 12, 130, 65, 57, 66, 64, 49, 57, 35, 50, 47, 37, 0, 13, 2, 194, 172, 50, 107, 79, 6, 35, 115, 57, 35, 0, 5, 130, 195, 164, 43, 5, 130, 195, 164, 43, 0, 5, 130, 195, 165, 43, 5, 130, 195, 165, 43, 0, 10, 135, 13, 9, 1, 197, 130, 5, 13, 76, 0, 8, 133, 11, 197, 130, 1, 16, 20, 25, 2, 194, 171, 81, 51, 35, 50, 115, 4, 40, 87, 78, 37, 15, 115, 40, 116, 6, 110, 87, 58, 40, 81, 0, 0, 12, 2, 194, 168, 6, 40, 63, 55, 35, 58, 47, 0, 0, 9, 134, 4, 15, 197, 130, 2, 25, 20, 13, 2, 195, 161, 35, 55, 6, 35, 0, 81, 108, 97, 32, 6, 2, 196, 153, 111, 0, 0, 10, 135, 26, 12, 15, 197, 130, 2, 25, 20, 10, 135, 23, 12, 15, 197, 130, 2, 25, 20, 10, 135, 23, 9, 15, 197, 130, 2, 25, 20, 10, 135, 19, 16, 15, 197, 130, 2, 25, 20, 10, 135, 19, 9, 15, 197, 130, 2, 25, 20, 10, 135, 16, 9, 15, 197, 130, 2, 25, 20, 10, 135, 12, 5, 7, 197, 130, 2, 25, 20, 12, 2, 194, 182, 35, 49, 6, 35, 48, 37, 47, 0, 0, 11, 136, 26, 7, 1, 4, 197, 130, 2, 25, 20, 11, 136, 23, 19, 20, 15, 197, 130, 2, 25, 20, 11, 136, 23, 12, 5, 11, 197, 130, 2, 25, 20, 11, 136, 20, 18, 23, 15, 197, 130, 2, 25, 20, 11, 136, 19, 197, 130, 15, 197, 130, 2, 25, 20, 11, 136, 18, 195, 179, 19, 197, 130, 2, 25, 20, 11, 136, 16, 9, 5, 11, 197, 130, 2, 25, 20, 11, 136, 16, 3, 8, 15, 197, 130, 2, 25, 20, 11, 136, 12, 196, 133, 7, 197, 130, 2, 25, 20, 9, 134, 26, 4, 197, 130, 1, 23, 20, 9, 134, 23, 19, 197, 130, 1, 23, 20, 15, 69, 64, 17, 197, 85, 0, 48, 107, 57, 73, 6, 35, 48, 0, 0, 12, 137, 26, 23, 12, 5, 11, 197, 130, 2, 25, 20, 12, 137, 26, 2, 9, 5, 7, 197, 130, 2, 25, 20, 12, 137, 23, 9, 196, 153, 4, 197, 130, 2, 25, 20, 12, 137, 23, 2, 9, 5, 7, 197, 130, 2, 25, 20, 5, 194, 60, 224, 76, 19, 2, 194, 180, 4, 109, 87, 47, 51, 110, 10, 6, 35, 49, 115, 107, 50, 47, 0, 0, 13, 138, 26, 26, 9, 196, 133, 2, 197, 130, 2, 25, 20, 13, 138, 23, 23, 9, 195, 179, 26, 197, 130, 2, 25, 20, 13, 138, 19, 20, 197, 130, 21, 11, 197, 130, 2, 25, 20, 13, 138, 16, 18, 26, 196, 133, 7, 197, 130, 2, 25, 20, 13, 138, 7, 18, 26, 13, 9, 15, 197, 130, 2, 25, 20, 7, 132, 23, 9, 196, 135, 20, 7, 132, 13, 25, 196, 135, 20, 9, 67, 88, 144, 64, 82, 37, 35, 0, 5, 130, 195, 173, 43, 5, 130, 195, 173, 43, 0, 14, 139, 23, 16, 18, 26, 196, 133, 7, 197, 130, 2, 25, 20, 14, 139, 197, 155, 13, 9, 5, 18, 4, 197, 130, 2, 25, 20, 14, 139, 19, 16, 18, 26, 196, 133, 7, 197, 130, 2, 25, 20, 7, 196, 105, 115, 5, 12, 20, 8, 133, 26, 12, 5, 196, 135, 20, 9, 134, 26, 5, 10, 4, 197, 186, 20, 9, 134, 26, 1, 10, 4, 197, 186, 20, 8, 133, 23, 26, 21, 196, 135, 20, 9, 134, 23, 25, 10, 4, 197, 186, 20, 9, 134, 23, 5, 10, 4, 197, 186, 20, 8, 133, 20, 18, 21, 196, 135, 20, 9, 134, 197, 155, 16, 9, 19, 26, 20, 8, 133, 16, 18, 21, 196, 135, 20, 7, 196, 16, 226, 69, 40, 20, 8, 133, 4, 196, 133, 196, 135, 20, 13, 2, 194, 178, 49, 82, 6, 35, 70, 51, 35, 47, 0, 0, 10, 135, 26, 14, 1, 10, 4, 197, 186, 20, 9, 134, 26, 13, 196, 133, 196, 135, 20, 6, 195, 104, 145, 74, 20, 9, 134, 23, 26, 12, 5, 196, 135, 20, 10, 135, 23, 26, 5, 10, 4, 197, 186, 20, 10, 135, 23, 20, 197, 130, 15, 3, 26, 20, 10, 135, 23, 197, 130, 195, 179, 3, 26, 20, 9, 134, 23, 3, 26, 21, 196, 135, 20, 10, 135, 19, 20, 197, 130, 15, 3, 26, 20, 9, 134, 11, 12, 196, 133, 196, 135, 20, 10, 135, 7, 18, 1, 14, 4, 197, 186, 20, 9, 134, 7, 9, 196, 133, 196, 135, 20, 9, 134, 3, 9, 196, 133, 196, 135, 20, 9, 134, 3, 8, 23, 25, 196, 135, 20, 21, 10, 22, 1, 18, 9, 195, 169, 20, 195, 169, 19, 82, 35, 34, 57, 107, 47, 107, 0, 67, 12, 2, 194, 179, 89, 6, 107, 95, 76, 35, 50, 0, 7, 2, 197, 155, 95, 37, 0, 0, 11, 136, 26, 23, 197, 130, 195, 179, 3, 26, 20, 11, 136, 26, 7, 18, 1, 14, 4, 197, 186, 20, 10, 135, 26, 7, 9, 196, 133, 196, 135, 20, 10, 135, 23, 26, 9, 196, 133, 196, 135, 20, 10, 135, 23, 7, 9, 196, 133, 196, 135, 20, 10, 135, 23, 3, 9, 196, 133, 196, 135, 20, 10, 135, 19, 11, 12, 196, 133, 196, 135, 20, 10, 135, 19, 3, 8, 23, 25, 196, 135, 20, 13, 2, 194, 176, 87, 47, 6, 109, 48, 38, 107, 65, 0, 0, 8, 133, 197, 188, 18, 25, 10, 20, 7, 132, 23, 25, 196, 135, 20, 11, 136, 197, 155, 3, 9, 196, 133, 196, 135, 20, 7, 132, 19, 25, 196, 135, 20, 15, 2, 194, 177, 48, 55, 40, 87, 63, 6, 37, 50, 40, 87, 0, 5, 130, 197, 153, 43, 5, 130, 197, 153, 43, 0, 8, 133, 16, 12, 21, 196, 135, 20, 10, 135, 7, 18, 26, 13, 9, 196, 133, 20, 16, 2, 194, 190, 47, 15, 89, 110, 74, 81, 6, 35, 51, 47, 107, 0, 5, 130, 195, 182, 43, 5, 130, 195, 182, 43, 0, 9, 134, 23, 7, 18, 1, 196, 135, 20, 9, 134, 20, 18, 26, 5, 196, 135, 20, 9, 134, 19, 20, 18, 1, 196, 135, 20, 9, 134, 19, 16, 18, 1, 196, 135, 20, 9, 134, 16, 18, 26, 5, 196, 135, 20, 13, 67, 85, 35, 0, 40, 107, 51, 6, 107, 55, 0, 17, 23, 2, 194, 191, 109, 70, 82, 51, 4, 109, 47, 50, 110, 15, 48, 110, 47, 35, 57, 65, 37, 49, 0, 13, 2, 195, 183, 118, 107, 55, 6, 107, 65, 38, 107, 0, 0, 7, 132, 23, 25, 197, 130, 20, 17, 2, 194, 188, 57, 107, 70, 50, 35, 74, 81, 6, 35, 51, 47, 35, 0, 0, 8, 133, 16, 12, 21, 197, 130, 20, 7, 195, 56, 145, 64, 72, 23, 6, 195, 56, 145, 64, 76, 16, 2, 194, 189, 57, 107, 70, 50, 35, 70, 51, 6, 40, 79, 35, 0, 0, 7, 132, 23, 9, 197, 132, 20, 9, 134, 23, 7, 18, 1, 197, 130, 20, 9, 134, 19, 16, 18, 1, 197, 130, 20, 7, 195, 80, 83, 85, 72, 12, 15, 4, 95, 3, 5, 4, 86, 115, 107, 114, 6, 37, 55, 112, 0, 0, 8, 197, 92, 116, 129, 77, 160, 20, 7, 132, 18, 197, 188, 25, 20, 32, 2, 194, 187, 48, 51, 6, 35, 82, 110, 15, 81, 51, 35, 50, 115, 4, 40, 87, 78, 37, 15, 115, 40, 116, 6, 110, 87, 58, 40, 81, 0, 0, 9, 134, 23, 197, 188, 5, 197, 132, 20, 7, 132, 23, 9, 197, 130, 20, 7, 132, 13, 25, 197, 130, 20, 13, 2, 194, 184, 115, 107, 114, 6, 37, 55, 55, 35, 0, 0, 8, 133, 23, 26, 21, 197, 130, 20, 8, 133, 20, 18, 21, 197, 130, 20, 8, 133, 16, 18, 21, 197, 130, 20, 8, 133, 4, 196, 133, 197, 130, 20, 16, 2, 194, 185, 57, 107, 70, 107, 50, 79, 6, 40, 51, 50, 107, 0, 5, 130, 195, 177, 43, 5, 130, 197, 161, 43, 5, 130, 195, 177, 43, 5, 130, 197, 161, 43, 16, 4, 95, 12, 9, 7, 55, 37, 79, 35, 47, 6, 40, 51, 35, 0, 0, 10, 135, 10, 1, 4, 197, 130, 2, 25, 20, 9, 134, 23, 3, 26, 21, 197, 130, 20, 9, 134, 18, 197, 188, 1, 197, 130, 20, 7, 132, 18, 1, 197, 132, 20, 7, 132, 13, 9, 197, 132, 20, 9, 134, 11, 12, 196, 133, 197, 130, 20, 9, 134, 7, 9, 196, 133, 197, 130, 20, 0, 11, 136, 26, 10, 1, 4, 197, 130, 2, 25, 20, 11, 136, 19, 26, 5, 4, 197, 130, 2, 25, 20, 11, 136, 19, 9, 1, 4, 197, 130, 2, 25, 20, 11, 136, 18, 26, 5, 4, 197, 130, 2, 25, 20, 11, 136, 11, 18, 1, 4, 197, 130, 2, 25, 20, 11, 136, 3, 8, 21, 4, 197, 130, 2, 25, 20, 10, 135, 26, 7, 9, 196, 133, 197, 130, 20, 8, 197, 93, 164, 149, 77, 160, 20, 10, 135, 23, 26, 9, 196, 133, 197, 130, 20, 10, 135, 23, 7, 9, 196, 133, 197, 130, 20, 10, 135, 23, 3, 9, 196, 133, 197, 130, 20, 8, 197, 77, 50, 69, 77, 160, 20, 10, 135, 19, 11, 12, 196, 133, 197, 130, 20, 8, 197, 76, 54, 133, 77, 160, 20, 8, 197, 64, 226, 69, 77, 160, 20, 8, 133, 16, 12, 21, 197, 132, 20, 7, 132, 12, 197, 188, 25, 20, 8, 197, 45, 2, 65, 73, 160, 20, 8, 197, 13, 162, 193, 77, 160, 20, 12, 201, 80, 133, 78, 16, 84, 130, 37, 33, 0, 65, 0, 12, 137, 26, 18, 26, 5, 4, 197, 130, 2, 25, 20, 12, 137, 26, 4, 5, 3, 8, 197, 130, 2, 25, 20, 12, 137, 23, 19, 26, 5, 4, 197, 130, 2, 25, 20, 12, 137, 23, 11, 18, 1, 4, 197, 130, 2, 25, 20, 12, 137, 19, 11, 18, 1, 4, 197, 130, 2, 25, 20, 12, 137, 19, 3, 8, 21, 4, 197, 130, 2, 25, 20, 12, 137, 16, 12, 195, 179, 20, 197, 130, 2, 25, 20, 12, 137, 11, 197, 130, 1, 4, 197, 130, 2, 25, 20, 12, 137, 2, 18, 26, 25, 4, 197, 130, 2, 25, 20, 8, 133, 197, 155, 12, 196, 153, 20, 11, 136, 197, 155, 3, 9, 196, 133, 197, 130, 20, 20, 66, 88, 16, 82, 35, 69, 6, 35, 66, 49, 0, 81, 98, 97, 110, 113, 117, 101, 32, 6, 194, 80, 80, 72, 12, 5, 130, 195, 188, 43, 5, 130, 195, 188, 43, 0, 13, 138, 26, 7, 196, 153, 19, 20, 197, 130, 2, 25, 20, 13, 138, 26, 2, 18, 26, 25, 4, 197, 130, 2, 25, 20, 13, 138, 23, 16, 12, 195, 179, 20, 197, 130, 2, 25, 20, 13, 138, 197, 155, 3, 9, 3, 8, 197, 130, 2, 25, 20, 13, 138, 19, 20, 196, 153, 3, 8, 197, 130, 2, 25, 20, 13, 138, 19, 16, 12, 195, 179, 20, 197, 130, 2, 25, 20, 13, 138, 7, 14, 9, 195, 179, 20, 197, 130, 2, 25, 20, 0, 14, 139, 26, 7, 14, 9, 195, 179, 20, 197, 130, 2, 25, 20, 14, 139, 23, 7, 14, 9, 195, 179, 20, 197, 130, 2, 25, 20, 14, 139, 197, 155, 13, 9, 15, 18, 4, 197, 130, 2, 25, 20, 7, 196, 92, 193, 67, 104, 20, 6, 195, 28, 227, 205, 20, 9, 134, 4, 15, 10, 4, 197, 186, 20, 7, 196, 81, 147, 11, 60, 76, 0, 15, 140, 19, 16, 9, 5, 18, 26, 3, 8, 197, 130, 2, 25, 20, 8, 197, 77, 68, 154, 100, 48, 20, 13, 69, 53, 81, 83, 48, 144, 63, 40, 87, 55, 37, 0, 12, 69, 28, 83, 210, 28, 80, 73, 109, 34, 73, 0, 0, 11, 136, 19, 16, 9, 5, 18, 4, 197, 186, 20, 11, 136, 16, 18, 26, 5, 10, 4, 197, 186, 20, 5, 130, 195, 184, 43, 5, 130, 195, 184, 43, 0, 0, 7, 196, 76, 145, 67, 104, 20, 0, 8, 197, 76, 179, 14, 36, 80, 20, 8, 197, 76, 50, 12, 4, 208, 20, 11, 2, 203, 135, 49, 6, 35, 51, 109, 50, 0, 0, 0, 0, 7, 196, 104, 161, 68, 104, 20, 0, 6, 195, 77, 84, 218, 20, 0, 0, 9, 134, 4, 21, 197, 130, 2, 25, 20, 9, 134, 2, 25, 197, 130, 2, 25, 20, 6, 195, 60, 227, 192, 76, 0, 10, 135, 197, 188, 21, 197, 130, 2, 25, 20, 10, 135, 26, 18, 25, 197, 130, 2, 25, 20, 10, 135, 26, 14, 1, 197, 130, 2, 25, 20, 10, 135, 23, 16, 9, 197, 130, 2, 25, 20, 10, 135, 23, 11, 21, 197, 130, 2, 25, 20, 10, 135, 23, 9, 1, 197, 130, 2, 25, 20, 10, 135, 23, 4, 15, 197, 130, 2, 25, 20, 10, 135, 19, 16, 9, 197, 130, 2, 25, 20, 10, 135, 19, 11, 21, 197, 130, 2, 25, 20, 10, 135, 19, 9, 1, 197, 130, 2, 25, 20, 10, 135, 16, 9, 1, 197, 130, 2, 25, 20, 10, 135, 16, 1, 4, 197, 130, 2, 25, 20, 10, 135, 11, 16, 9, 197, 130, 2, 25, 20, 10, 135, 7, 18, 1, 197, 130, 2, 25, 20, 10, 135, 7, 14, 1, 197, 130, 2, 25, 20, 10, 135, 4, 2, 1, 197, 130, 2, 25, 20, 10, 135, 3, 12, 9, 197, 130, 2, 25, 20, 7, 196, 92, 50, 69, 48, 20, 5, 130, 197, 190, 43, 5, 130, 197, 190, 43, 0, 11, 136, 26, 23, 9, 1, 197, 130, 2, 25, 20, 11, 136, 23, 19, 9, 1, 197, 130, 2, 25, 20, 11, 136, 20, 11, 23, 9, 197, 130, 2, 25, 20, 11, 136, 19, 20, 25, 7, 197, 130, 2, 25, 20, 11, 136, 19, 16, 1, 4, 197, 130, 2, 25, 20, 11, 136, 19, 197, 130, 1, 197, 130, 2, 25, 20, 11, 136, 197, 130, 11, 15, 197, 130, 2, 25, 20, 11, 136, 7, 18, 26, 1, 197, 130, 2, 25, 20, 11, 136, 4, 18, 23, 9, 197, 130, 2, 25, 20, 11, 136, 3, 9, 3, 8, 197, 130, 2, 25, 20, 11, 136, 2, 12, 1, 4, 197, 130, 2, 25, 20, 0, 12, 137, 26, 19, 9, 1, 4, 197, 130, 2, 25, 20, 12, 137, 26, 2, 12, 1, 4, 197, 130, 2, 25, 20, 12, 137, 23, 19, 9, 1, 4, 197, 130, 2, 25, 20, 12, 137, 23, 9, 196, 133, 4, 197, 130, 2, 25, 20, 12, 137, 19, 26, 3, 26, 1, 197, 130, 2, 25, 20, 12, 137, 13, 197, 155, 3, 9, 197, 130, 2, 25, 20, 12, 137, 13, 9, 195, 179, 20, 197, 130, 2, 25, 20, 12, 137, 12, 7, 14, 196, 133, 197, 130, 2, 25, 20, 9, 198, 92, 147, 133, 29, 33, 84, 67, 11, 66, 76, 128, 107, 87, 6, 99, 35, 0, 17, 16, 2, 197, 188, 88, 107, 47, 86, 49, 51, 6, 109, 48, 49, 112, 0, 0, 13, 138, 26, 23, 9, 196, 133, 4, 197, 130, 2, 25, 20, 13, 138, 26, 13, 9, 195, 179, 20, 197, 130, 2, 25, 20, 13, 138, 23, 13, 9, 195, 179, 20, 197, 130, 2, 25, 20, 13, 138, 19, 20, 18, 26, 25, 7, 197, 130, 2, 25, 20, 13, 138, 16, 18, 26, 196, 133, 4, 197, 130, 2, 25, 20, 13, 138, 7, 18, 26, 13, 9, 1, 197, 130, 2, 25, 20, 13, 138, 7, 197, 130, 21, 3, 8, 197, 130, 2, 25, 20, 13, 138, 2, 18, 26, 13, 9, 1, 197, 130, 2, 25, 20, 7, 132, 12, 1, 196, 135, 20, 7, 132, 4, 1, 196, 135, 20, 0, 14, 139, 23, 19, 26, 3, 26, 196, 133, 197, 130, 2, 25, 20, 14, 139, 23, 16, 18, 26, 196, 133, 4, 197, 130, 2, 25, 20, 14, 139, 197, 155, 13, 9, 1, 18, 4, 197, 130, 2, 25, 20, 14, 139, 19, 16, 18, 26, 196, 133, 4, 197, 130, 2, 25, 20, 8, 133, 26, 26, 21, 196, 135, 20, 8, 133, 26, 4, 21, 197, 155, 20, 8, 133, 23, 12, 5, 196, 135, 20, 8, 133, 19, 14, 21, 196, 135, 20, 8, 133, 18, 26, 21, 196, 135, 20, 8, 133, 16, 12, 5, 196, 135, 20, 7, 2, 197, 186, 94, 37, 0, 0, 9, 134, 23, 19, 20, 1, 196, 135, 20, 9, 134, 19, 26, 16, 5, 196, 135, 20, 9, 134, 16, 3, 8, 1, 196, 135, 20, 10, 135, 197, 130, 197, 188, 5, 19, 26, 20, 9, 134, 196, 135, 16, 1, 196, 135, 20, 9, 134, 196, 135, 13, 9, 196, 135, 20, 9, 134, 3, 8, 12, 1, 196, 135, 20, 0, 10, 135, 23, 20, 18, 196, 133, 196, 135, 20, 10, 135, 20, 11, 14, 196, 133, 196, 135, 20, 10, 135, 19, 26, 3, 26, 21, 196, 135, 20, 10, 135, 19, 20, 18, 196, 133, 196, 135, 20, 10, 135, 19, 3, 8, 12, 1, 196, 135, 20, 10, 135, 2, 18, 14, 196, 133, 196, 135, 20, 0, 11, 136, 197, 188, 7, 14, 196, 133, 196, 135, 20, 7, 132, 23, 9, 197, 155, 20, 11, 136, 20, 3, 8, 14, 196, 133, 196, 135, 20, 11, 136, 19, 3, 8, 197, 130, 5, 197, 155, 20, 10, 199, 76, 50, 12, 5, 54, 131, 104, 20, 11, 136, 18, 197, 188, 14, 196, 133, 196, 135, 20, 7, 132, 16, 1, 197, 155, 20, 9, 134, 196, 135, 13, 9, 196, 133, 20, 7, 132, 2, 1, 196, 135, 20, 9, 198, 52, 18, 211, 36, 213, 77, 65, 0, 8, 133, 197, 188, 21, 196, 135, 20, 8, 133, 7, 18, 1, 196, 135, 20, 8, 133, 7, 14, 1, 196, 135, 20, 12, 137, 4, 197, 186, 7, 14, 196, 133, 196, 135, 20, 8, 133, 4, 2, 1, 196, 135, 20, 10, 135, 2, 18, 26, 13, 9, 196, 133, 20, 8, 133, 2, 18, 1, 196, 135, 20, 32, 68, 12, 130, 76, 36, 74, 4, 37, 55, 37, 49, 109, 50, 49, 6, 35, 34, 50, 107, 0, 82, 99, 111, 110, 32, 99, 97, 114, 110, 101, 32, 11, 68, 12, 130, 76, 36, 74, 37, 55, 37, 0, 6, 195, 9, 147, 9, 76, 0, 9, 134, 20, 11, 23, 9, 196, 135, 20, 9, 134, 19, 197, 130, 1, 196, 135, 20, 9, 134, 13, 18, 26, 5, 196, 135, 20, 9, 134, 7, 18, 26, 1, 196, 135, 20, 9, 134, 4, 18, 26, 5, 196, 135, 20, 6, 195, 16, 210, 74, 20, 0, 10, 135, 19, 26, 3, 26, 5, 196, 135, 20, 0, 8, 133, 197, 188, 21, 197, 130, 20, 9, 134, 20, 11, 23, 9, 196, 133, 20, 9, 134, 19, 26, 11, 12, 196, 133, 20, 8, 133, 7, 18, 1, 197, 130, 20, 8, 133, 7, 14, 1, 197, 130, 20, 8, 133, 4, 2, 1, 197, 130, 20, 0, 9, 134, 20, 11, 23, 9, 197, 130, 20, 9, 134, 19, 197, 130, 1, 197, 130, 20, 8, 133, 18, 23, 196, 133, 3, 20, 9, 134, 7, 18, 26, 1, 197, 130, 20, 7, 132, 7, 9, 197, 132, 20, 0, 8, 133, 16, 12, 5, 197, 132, 20, 0, 9, 134, 23, 19, 20, 1, 197, 132, 20, 9, 134, 197, 155, 23, 9, 197, 132, 20, 7, 132, 12, 1, 197, 130, 20, 7, 132, 4, 1, 197, 130, 20, 0, 8, 133, 26, 26, 21, 197, 130, 20, 8, 133, 19, 14, 21, 197, 130, 20, 0, 7, 196, 104, 116, 143, 52, 20, 9, 134, 23, 19, 20, 1, 197, 130, 20, 6, 195, 64, 197, 193, 20, 9, 134, 16, 3, 8, 1, 197, 130, 20, 9, 134, 13, 4, 12, 1, 197, 130, 20, 9, 134, 196, 135, 16, 1, 197, 130, 20, 9, 134, 196, 135, 13, 9, 197, 130, 20, 9, 134, 3, 8, 12, 1, 197, 130, 20, 0, 6, 195, 92, 19, 0, 20, 10, 135, 20, 11, 14, 196, 133, 197, 130, 20, 8, 197, 77, 161, 80, 13, 160, 20, 10, 135, 19, 26, 3, 26, 21, 197, 130, 20, 6, 195, 76, 147, 0, 20, 10, 135, 19, 3, 8, 12, 1, 197, 130, 20, 8, 197, 56, 148, 218, 13, 160, 20, 8, 133, 13, 195, 179, 4, 12, 20, 10, 135, 4, 18, 197, 188, 1, 197, 130, 20, 10, 135, 2, 18, 14, 196, 133, 197, 130, 20, 7, 132, 19, 9, 196, 153, 72, 0, 11, 136, 197, 188, 7, 14, 196, 133, 197, 130, 20, 11, 136, 20, 3, 8, 14, 196, 133, 197, 130, 20, 11, 136, 18, 197, 188, 14, 196, 133, 197, 130, 20, 7, 132, 18, 1, 197, 186, 20, 16, 66, 64, 240, 48, 6, 109, 82, 35, 87, 0, 81, 119, 97, 115, 32, 16, 66, 64, 240, 48, 6, 109, 47, 110, 63, 0, 81, 116, 121, 109, 32, 14, 66, 64, 240, 48, 6, 109, 47, 109, 0, 81, 116, 111, 32, 14, 66, 64, 240, 48, 6, 109, 47, 107, 0, 81, 116, 101, 32, 15, 66, 64, 240, 48, 6, 109, 47, 112, 0, 81, 116, 196, 133, 32, 16, 66, 64, 240, 48, 6, 109, 65, 38, 107, 0, 81, 110, 105, 101, 32, 17, 66, 64, 240, 48, 6, 109, 65, 37, 105, 0, 81, 110, 105, 99, 104, 32, 16, 66, 64, 240, 48, 6, 109, 65, 37, 63, 0, 81, 110, 105, 109, 32, 18, 66, 64, 240, 48, 6, 109, 65, 38, 107, 57, 0, 81, 110, 105, 101, 106, 32, 16, 66, 64, 240, 48, 6, 109, 50, 35, 87, 0, 81, 110, 97, 115, 32, 18, 66, 64, 240, 48, 6, 109, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 5, 194, 64, 240, 76, 0, 12, 137, 4, 197, 186, 7, 14, 196, 133, 197, 130, 20, 18, 67, 64, 241, 0, 48, 6, 109, 70, 82, 35, 87, 0, 81, 119, 97, 115, 32, 18, 67, 64, 241, 0, 48, 6, 109, 47, 47, 110, 63, 0, 81, 116, 121, 109, 32, 16, 67, 64, 241, 0, 48, 6, 109, 47, 47, 109, 0, 81, 116, 111, 32, 16, 67, 64, 241, 0, 48, 6, 109, 47, 47, 107, 0, 81, 116, 101, 32, 17, 67, 64, 241, 0, 48, 6, 109, 47, 47, 112, 0, 81, 116, 196, 133, 32, 18, 67, 64, 241, 0, 48, 6, 109, 70, 65, 38, 107, 0, 81, 110, 105, 101, 32, 19, 67, 64, 241, 0, 48, 6, 109, 70, 65, 37, 105, 0, 81, 110, 105, 99, 104, 32, 18, 67, 64, 241, 0, 48, 6, 109, 70, 65, 37, 63, 0, 81, 110, 105, 109, 32, 19, 67, 64, 241, 0, 48, 6, 109, 70, 65, 38, 112, 0, 81, 110, 105, 196, 133, 32, 18, 67, 64, 241, 0, 48, 6, 109, 70, 50, 35, 87, 0, 81, 110, 97, 115, 32, 6, 195, 64, 241, 0, 76, 19, 2, 203, 157, 99, 4, 40, 66, 79, 35, 51, 6, 40, 63, 55, 35, 58, 47, 0, 0, 9, 134, 20, 197, 130, 15, 3, 26, 20, 7, 196, 76, 180, 143, 8, 20, 6, 195, 53, 38, 133, 20, 9, 134, 197, 130, 197, 188, 25, 10, 20, 10, 135, 7, 18, 26, 13, 9, 196, 153, 20, 0, 8, 133, 4, 196, 133, 197, 188, 20, 12, 2, 203, 155, 109, 79, 6, 109, 50, 107, 49, 0, 0, 12, 2, 203, 152, 69, 51, 6, 107, 82, 37, 87, 0, 0, 19, 2, 203, 153, 79, 6, 40, 51, 50, 35, 10, 49, 51, 6, 109, 48, 49, 35, 0, 0, 9, 134, 197, 188, 7, 1, 19, 26, 20, 9, 134, 197, 155, 14, 9, 19, 26, 20, 10, 68, 8, 241, 85, 24, 69, 107, 81, 0, 0, 0, 0, 6, 2, 95, 1, 35, 0, 0, 0, 0, 9, 67, 88, 145, 87, 82, 38, 40, 0, 0, 9, 134, 19, 26, 11, 12, 196, 153, 20, 0, 7, 196, 92, 145, 68, 104, 20, 0, 11, 136, 19, 3, 8, 197, 130, 15, 2, 25, 20, 12, 137, 15, 197, 155, 13, 9, 21, 19, 5, 20, 65, 13, 69, 40, 84, 147, 21, 144, 73, 107, 51, 86, 37, 0, 0, 6, 2, 95, 9, 37, 0, 0, 9, 134, 196, 135, 13, 9, 196, 153, 20, 14, 139, 19, 26, 5, 197, 155, 3, 9, 21, 19, 5, 20, 65, 0, 6, 2, 95, 15, 109, 0, 0, 9, 134, 26, 197, 130, 1, 197, 186, 20, 9, 134, 23, 197, 130, 1, 197, 186, 20, 7, 196, 28, 224, 83, 104, 20, 0, 8, 197, 4, 194, 83, 60, 224, 65, 0, 9, 134, 23, 9, 196, 133, 197, 188, 20, 0, 7, 132, 20, 18, 196, 133, 20, 7, 132, 16, 18, 196, 133, 20, 0, 18, 9, 4, 5, 12, 12, 39, 1, 18, 20, 5, 70, 107, 55, 6, 35, 51, 0, 10, 135, 10, 5, 19, 20, 5, 197, 155, 76, 0, 11, 136, 19, 20, 18, 26, 196, 133, 197, 155, 20, 9, 134, 4, 18, 7, 14, 196, 133, 20, 9, 134, 3, 26, 11, 14, 196, 133, 20, 0, 16, 70, 8, 16, 203, 92, 20, 132, 69, 107, 49, 58, 107, 51, 70, 0, 0, 9, 134, 19, 20, 197, 130, 21, 3, 20, 8, 133, 4, 197, 130, 21, 2, 20, 9, 134, 3, 8, 3, 196, 133, 3, 20, 7, 2, 95, 23, 82, 40, 0, 0, 0, 9, 134, 20, 11, 23, 9, 196, 153, 20, 6, 2, 95, 21, 40, 0, 0, 0, 0, 7, 196, 92, 116, 143, 52, 20, 10, 135, 197, 155, 14, 9, 196, 133, 3, 20, 10, 135, 196, 135, 13, 9, 196, 133, 3, 20, 8, 2, 95, 26, 86, 107, 47, 0, 0, 8, 197, 105, 112, 76, 13, 160, 20, 10, 135, 26, 7, 18, 25, 26, 197, 130, 20, 11, 136, 2, 18, 26, 13, 9, 196, 133, 3, 20, 13, 138, 10, 5, 19, 20, 5, 197, 155, 3, 9, 5, 76, 0, 8, 133, 11, 18, 1, 197, 155, 20, 10, 135, 2, 18, 26, 13, 9, 196, 153, 20, 0, 8, 133, 196, 135, 16, 1, 10, 20, 0, 7, 196, 92, 194, 67, 104, 20, 7, 196, 16, 32, 83, 104, 20, 10, 135, 2, 25, 197, 130, 5, 197, 155, 76, 11, 200, 52, 19, 132, 20, 192, 146, 61, 64, 65, 0, 10, 135, 26, 7, 197, 130, 21, 19, 26, 20, 0, 11, 136, 197, 188, 7, 14, 9, 5, 19, 26, 20, 9, 134, 26, 13, 18, 21, 197, 188, 20, 6, 195, 52, 67, 9, 20, 18, 67, 16, 82, 129, 70, 107, 88, 35, 82, 6, 37, 0, 81, 118, 117, 101, 32, 17, 67, 16, 82, 129, 70, 107, 88, 35, 82, 6, 37, 0, 81, 118, 117, 32, 9, 134, 11, 15, 12, 1, 197, 188, 66, 0, 10, 135, 26, 23, 9, 196, 133, 197, 188, 20, 8, 133, 26, 12, 5, 197, 186, 20, 8, 133, 23, 12, 5, 197, 186, 20, 6, 195, 48, 82, 128, 20, 6, 195, 8, 146, 128, 20, 7, 195, 80, 82, 128, 72, 12, 0, 7, 196, 104, 36, 143, 40, 20, 9, 134, 13, 197, 188, 25, 19, 26, 20, 8, 133, 196, 135, 16, 1, 13, 20, 14, 2, 95, 34, 115, 40, 116, 6, 110, 87, 58, 40, 81, 0, 0, 9, 198, 93, 54, 131, 104, 226, 69, 20, 10, 135, 4, 197, 186, 7, 1, 19, 26, 20, 11, 69, 69, 82, 67, 32, 80, 49, 37, 89, 0, 15, 2, 95, 33, 82, 110, 49, 89, 6, 110, 49, 65, 37, 49, 0, 0, 9, 198, 93, 64, 83, 104, 54, 128, 20, 9, 198, 44, 192, 83, 104, 54, 128, 20, 5, 194, 81, 144, 76, 0, 10, 135, 19, 20, 18, 26, 5, 197, 188, 20, 9, 67, 12, 243, 128, 49, 109, 50, 0, 14, 2, 95, 39, 35, 48, 6, 109, 87, 47, 51, 109, 81, 0, 0, 9, 198, 93, 54, 131, 104, 226, 74, 20, 7, 196, 92, 180, 143, 64, 20, 0, 0, 16, 67, 52, 195, 5, 63, 35, 70, 63, 40, 35, 86, 6, 107, 55, 0, 10, 67, 40, 19, 133, 73, 107, 57, 50, 0, 11, 2, 95, 36, 70, 6, 109, 55, 35, 51, 0, 0, 7, 195, 80, 83, 128, 72, 12, 0, 7, 196, 77, 3, 1, 52, 20, 12, 68, 4, 66, 69, 84, 35, 70, 57, 6, 107, 0, 7, 196, 52, 16, 201, 20, 76, 13, 4, 95, 3, 1, 16, 70, 6, 40, 88, 107, 10, 0, 0, 23, 73, 12, 147, 145, 84, 80, 197, 57, 67, 192, 74, 37, 50, 49, 58, 107, 74, 107, 50, 47, 109, 0, 15, 2, 95, 41, 48, 109, 50, 35, 82, 38, 6, 35, 95, 107, 0, 0, 6, 195, 92, 116, 129, 20, 11, 2, 95, 40, 50, 35, 82, 38, 35, 87, 0, 0, 8, 133, 11, 197, 130, 21, 10, 20, 0, 8, 133, 20, 11, 14, 196, 133, 20, 10, 135, 7, 18, 25, 197, 186, 196, 135, 20, 0, 11, 136, 26, 23, 9, 5, 197, 186, 196, 135, 20, 8, 133, 26, 14, 21, 197, 188, 20, 11, 136, 26, 7, 18, 25, 197, 186, 196, 135, 20, 11, 136, 23, 23, 9, 5, 197, 186, 196, 135, 20, 10, 135, 23, 9, 5, 197, 132, 3, 26, 20, 11, 136, 23, 7, 18, 25, 197, 186, 196, 135, 20, 8, 133, 13, 25, 197, 155, 12, 20, 13, 2, 95, 45, 63, 6, 110, 95, 55, 50, 37, 49, 0, 0, 11, 136, 26, 23, 9, 5, 197, 132, 3, 26, 20, 8, 133, 9, 197, 155, 196, 135, 20, 14, 2, 95, 44, 48, 89, 107, 117, 6, 37, 50, 107, 49, 0, 0, 7, 132, 4, 18, 196, 133, 20, 19, 71, 12, 19, 69, 52, 33, 82, 80, 49, 35, 63, 107, 63, 69, 6, 107, 51, 0, 9, 2, 95, 51, 47, 89, 6, 110, 0, 0, 10, 135, 26, 10, 5, 197, 155, 196, 135, 20, 10, 135, 23, 9, 5, 197, 186, 196, 135, 20, 11, 136, 19, 16, 18, 26, 196, 133, 197, 188, 20, 7, 196, 9, 35, 137, 40, 20, 8, 133, 13, 1, 10, 196, 133, 76, 27, 68, 76, 245, 78, 16, 87, 35, 58, 50, 70, 15, 73, 6, 40, 87, 107, 51, 0, 81, 106, 117, 105, 99, 101, 114, 32, 9, 2, 95, 50, 70, 82, 6, 35, 0, 0, 8, 197, 76, 179, 14, 36, 160, 20, 8, 197, 76, 50, 12, 20, 160, 20, 11, 2, 95, 49, 57, 6, 107, 70, 107, 50, 0, 0, 11, 136, 197, 155, 23, 9, 15, 4, 3, 26, 20, 11, 2, 95, 48, 86, 6, 107, 51, 109, 12, 0, 0, 7, 132, 16, 18, 196, 153, 20, 6, 195, 45, 114, 76, 20, 11, 2, 95, 55, 95, 6, 107, 70, 107, 63, 0, 0, 10, 2, 95, 54, 89, 6, 107, 95, 117, 0, 0, 9, 134, 3, 26, 11, 14, 196, 153, 20, 11, 2, 95, 53, 48, 38, 6, 107, 65, 117, 0, 0, 11, 136, 23, 23, 9, 195, 179, 26, 197, 130, 20, 8, 133, 4, 13, 196, 133, 3, 20, 11, 2, 95, 52, 74, 47, 6, 107, 51, 110, 0, 0, 8, 133, 12, 1, 26, 197, 130, 20, 9, 134, 11, 16, 9, 196, 133, 3, 20, 13, 2, 95, 59, 95, 51, 6, 107, 70, 65, 37, 49, 0, 0, 9, 134, 23, 12, 1, 26, 197, 130, 20, 10, 135, 20, 11, 23, 9, 196, 133, 3, 20, 10, 135, 197, 155, 13, 9, 196, 133, 3, 20, 10, 135, 19, 26, 11, 12, 196, 133, 3, 20, 9, 134, 7, 18, 25, 26, 197, 130, 20, 10, 135, 4, 18, 23, 9, 196, 133, 3, 20, 9, 198, 12, 131, 1, 77, 160, 218, 20, 15, 2, 95, 58, 70, 82, 40, 49, 51, 6, 109, 48, 107, 49, 0, 0, 10, 135, 23, 9, 195, 179, 26, 197, 130, 20, 10, 135, 23, 7, 18, 25, 26, 197, 130, 20, 8, 197, 64, 197, 193, 77, 160, 20, 13, 2, 95, 57, 118, 6, 107, 82, 38, 107, 65, 117, 0, 0, 14, 139, 19, 3, 8, 197, 130, 25, 197, 155, 3, 9, 5, 20, 18, 66, 92, 80, 82, 6, 107, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 16, 70, 12, 128, 82, 52, 19, 148, 89, 35, 51, 63, 35, 50, 0, 66, 5, 194, 92, 80, 72, 10, 2, 95, 56, 6, 109, 95, 107, 63, 0, 0, 19, 71, 12, 243, 131, 36, 84, 135, 20, 49, 109, 50, 87, 57, 6, 107, 51, 88, 0, 20, 2, 95, 63, 86, 50, 4, 35, 49, 15, 86, 35, 48, 110, 47, 6, 35, 65, 35, 0, 0, 9, 134, 26, 23, 196, 153, 197, 186, 20, 7, 196, 76, 179, 195, 104, 20, 13, 2, 95, 62, 58, 38, 6, 107, 66, 49, 89, 107, 0, 0, 12, 137, 26, 2, 197, 130, 1, 197, 186, 197, 132, 20, 0, 11, 136, 197, 155, 23, 9, 1, 4, 3, 26, 20, 9, 198, 64, 197, 83, 104, 54, 128, 20, 9, 198, 52, 20, 147, 104, 54, 128, 20, 12, 2, 95, 60, 63, 65, 6, 107, 57, 89, 107, 0, 0, 0, 7, 196, 105, 37, 83, 104, 20, 7, 196, 104, 35, 195, 104, 20, 7, 196, 12, 145, 82, 64, 20, 0, 0, 9, 198, 104, 226, 83, 104, 54, 128, 20, 9, 198, 12, 132, 154, 12, 146, 128, 20, 0, 7, 132, 20, 18, 196, 153, 20, 0, 7, 196, 76, 180, 143, 64, 20, 7, 132, 11, 196, 133, 16, 20, 7, 196, 9, 35, 137, 20, 20, 0, 9, 134, 4, 18, 7, 14, 196, 153, 20, 0, 9, 198, 61, 5, 9, 53, 83, 64, 65, 0, 6, 195, 93, 112, 76, 20, 0, 7, 196, 64, 21, 18, 104, 20, 0, 0, 6, 195, 104, 161, 77, 20, 8, 133, 23, 4, 21, 197, 155, 20, 8, 133, 16, 19, 15, 196, 135, 20, 10, 135, 4, 197, 188, 4, 197, 188, 25, 20, 10, 67, 12, 240, 193, 49, 109, 49, 35, 0, 0, 9, 134, 13, 1, 197, 155, 196, 135, 20, 9, 134, 4, 26, 9, 15, 196, 135, 20, 0, 10, 135, 3, 26, 25, 197, 155, 196, 135, 20, 0, 11, 136, 26, 13, 9, 5, 197, 155, 196, 135, 20, 11, 136, 26, 7, 196, 153, 197, 155, 196, 135, 20, 11, 136, 23, 13, 9, 5, 197, 155, 196, 135, 20, 11, 136, 23, 11, 18, 1, 197, 155, 196, 135, 20, 11, 136, 19, 20, 18, 5, 197, 155, 196, 135, 20, 11, 136, 19, 11, 18, 1, 197, 155, 196, 135, 20, 0, 8, 133, 26, 9, 15, 196, 135, 20, 12, 137, 26, 7, 14, 9, 5, 197, 155, 196, 135, 20, 12, 137, 23, 26, 14, 9, 5, 197, 155, 196, 135, 20, 10, 67, 88, 144, 197, 82, 37, 115, 107, 0, 9, 198, 4, 225, 197, 48, 84, 192, 65, 0, 9, 134, 16, 21, 197, 155, 196, 135, 20, 8, 133, 8, 1, 197, 132, 2, 20, 9, 134, 4, 18, 7, 15, 196, 135, 20, 9, 134, 3, 26, 11, 15, 196, 135, 20, 13, 67, 85, 48, 128, 40, 107, 87, 69, 6, 107, 0, 17, 0, 10, 135, 18, 195, 179, 197, 155, 196, 135, 20, 10, 135, 13, 9, 5, 197, 155, 196, 135, 20, 10, 135, 3, 8, 23, 9, 15, 196, 135, 20, 10, 135, 2, 195, 179, 197, 155, 196, 135, 20, 0, 11, 136, 26, 18, 195, 179, 197, 155, 196, 135, 20, 6, 195, 104, 34, 74, 20, 11, 136, 23, 18, 195, 179, 197, 155, 196, 135, 20, 0, 0, 8, 133, 26, 9, 15, 197, 130, 20, 8, 133, 14, 9, 11, 197, 130, 20, 14, 67, 20, 177, 192, 107, 49, 35, 79, 38, 6, 107, 0, 17, 19, 71, 25, 32, 78, 12, 148, 195, 60, 81, 51, 35, 50, 87, 37, 87, 49, 109, 0, 0, 9, 198, 77, 4, 154, 100, 180, 154, 20, 8, 133, 4, 18, 197, 188, 25, 20, 9, 134, 4, 18, 7, 15, 197, 130, 20, 9, 134, 3, 26, 11, 15, 197, 130, 20, 14, 4, 95, 4, 15, 20, 86, 49, 51, 109, 48, 49, 112, 0, 0, 10, 135, 19, 16, 19, 9, 15, 197, 130, 20, 10, 135, 19, 16, 9, 5, 11, 197, 130, 20, 10, 135, 3, 8, 23, 9, 15, 197, 130, 20, 0, 0, 6, 195, 104, 161, 64, 20, 7, 195, 4, 193, 64, 76, 28, 24, 2, 95, 91, 50, 4, 35, 82, 38, 35, 87, 15, 49, 82, 35, 70, 51, 35, 47, 6, 109, 82, 110, 0, 0, 9, 134, 26, 23, 25, 11, 197, 130, 20, 8, 133, 20, 11, 14, 196, 153, 20, 9, 134, 18, 26, 5, 11, 197, 130, 20, 9, 134, 4, 26, 9, 15, 197, 130, 20, 9, 134, 2, 18, 1, 11, 197, 130, 20, 0, 10, 135, 26, 18, 26, 5, 11, 197, 130, 20, 10, 135, 26, 2, 18, 1, 11, 197, 130, 20, 8, 197, 93, 160, 149, 73, 160, 20, 8, 197, 92, 180, 143, 13, 160, 20, 8, 197, 81, 37, 193, 77, 160, 20, 8, 197, 17, 33, 193, 77, 160, 20, 0, 6, 195, 64, 226, 69, 20, 16, 66, 104, 16, 86, 6, 35, 65, 38, 107, 0, 81, 110, 105, 101, 32, 17, 66, 104, 16, 86, 6, 35, 65, 37, 105, 0, 81, 110, 105, 99, 104, 32, 16, 66, 104, 16, 86, 6, 35, 82, 35, 87, 0, 81, 119, 97, 115, 32, 16, 66, 104, 16, 86, 6, 35, 47, 110, 63, 0, 81, 116, 121, 109, 32, 14, 66, 104, 16, 86, 6, 35, 47, 109, 0, 81, 116, 111, 32, 14, 66, 104, 16, 86, 6, 35, 47, 107, 0, 81, 116, 101, 32, 15, 66, 104, 16, 86, 6, 35, 47, 112, 0, 81, 116, 196, 133, 32, 16, 66, 104, 16, 86, 6, 35, 65, 37, 63, 0, 81, 110, 105, 109, 32, 17, 66, 104, 16, 86, 6, 35, 65, 38, 112, 0, 81, 110, 105, 196, 133, 32, 16, 66, 104, 16, 86, 6, 35, 50, 35, 87, 0, 81, 110, 97, 115, 32, 18, 66, 104, 16, 86, 6, 35, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 5, 194, 104, 16, 76, 0, 8, 133, 11, 18, 195, 179, 10, 20, 17, 2, 95, 95, 48, 109, 70, 49, 51, 107, 95, 55, 6, 107, 65, 107, 0, 0, 9, 134, 23, 11, 197, 130, 21, 10, 20, 7, 196, 80, 181, 201, 40, 20, 9, 134, 19, 11, 197, 130, 21, 10, 20, 18, 70, 64, 17, 197, 16, 245, 206, 48, 107, 57, 73, 70, 6, 35, 58, 50, 0, 0, 10, 135, 14, 9, 1, 197, 132, 3, 26, 20, 28, 69, 52, 18, 84, 72, 80, 63, 107, 47, 51, 107, 70, 109, 47, 6, 107, 55, 0, 81, 100, 39, 104, 111, 116, 101, 108, 32, 30, 2, 95, 93, 48, 51, 35, 82, 110, 15, 50, 4, 35, 82, 38, 35, 87, 15, 49, 82, 35, 70, 51, 35, 47, 6, 109, 82, 110, 0, 0, 9, 198, 77, 162, 204, 37, 54, 128, 20, 9, 198, 65, 53, 18, 105, 146, 128, 20, 10, 67, 40, 18, 197, 73, 107, 57, 49, 0, 0, 6, 195, 73, 146, 128, 20, 6, 195, 17, 82, 128, 20, 9, 67, 12, 243, 204, 49, 40, 55, 0, 0, 7, 196, 12, 145, 83, 104, 20, 12, 137, 2, 196, 153, 4, 26, 9, 5, 13, 25, 76, 8, 133, 2, 25, 197, 130, 1, 76, 0, 6, 195, 8, 16, 218, 20, 31, 69, 12, 128, 82, 28, 80, 89, 35, 51, 88, 107, 70, 35, 81, 107, 51, 0, 68, 81, 100, 39, 97, 102, 102, 97, 105, 114, 101, 115, 32, 0, 9, 198, 77, 160, 218, 101, 54, 128, 20, 8, 133, 2, 25, 197, 130, 15, 76, 0, 7, 132, 4, 18, 196, 153, 20, 0, 0, 6, 195, 64, 226, 74, 20, 0, 0, 0, 0, 0, 8, 133, 26, 23, 15, 196, 135, 20, 8, 133, 20, 11, 15, 196, 135, 20, 8, 133, 19, 19, 15, 196, 135, 20, 8, 133, 18, 23, 15, 196, 135, 20, 16, 70, 13, 84, 129, 12, 19, 192, 49, 37, 51, 35, 87, 35, 109, 0, 26, 67, 12, 244, 193, 49, 4, 109, 86, 35, 50, 6, 109, 87, 47, 51, 35, 0, 81, 110, 111, 115, 116, 114, 97, 32, 14, 4, 95, 7, 18, 22, 117, 6, 111, 89, 78, 38, 107, 0, 0, 9, 134, 21, 10, 197, 155, 196, 135, 20, 20, 67, 88, 148, 192, 82, 37, 86, 35, 82, 37, 0, 67, 82, 97, 32, 118, 105, 115, 32, 21, 67, 88, 148, 192, 82, 37, 86, 35, 82, 37, 0, 67, 82, 195, 160, 32, 118, 105, 115, 32, 0, 9, 134, 26, 13, 196, 153, 3, 26, 20, 7, 196, 12, 226, 83, 104, 20, 8, 133, 3, 8, 3, 196, 133, 20, 12, 68, 13, 83, 16, 4, 49, 40, 55, 48, 35, 0, 0, 11, 136, 26, 23, 9, 5, 197, 155, 196, 135, 20, 11, 136, 26, 14, 9, 5, 197, 155, 196, 135, 20, 11, 136, 23, 14, 9, 5, 197, 155, 196, 135, 20, 8, 197, 92, 70, 137, 20, 160, 20, 0, 12, 137, 23, 26, 18, 195, 179, 197, 155, 196, 135, 20, 8, 133, 23, 9, 15, 196, 135, 20, 8, 133, 19, 9, 15, 196, 135, 20, 8, 133, 16, 9, 15, 196, 135, 20, 6, 131, 19, 196, 133, 76, 0, 8, 133, 197, 188, 25, 3, 26, 20, 9, 134, 20, 18, 23, 15, 196, 135, 20, 9, 134, 16, 15, 197, 155, 196, 135, 20, 0, 10, 135, 23, 16, 21, 197, 155, 196, 135, 20, 10, 135, 19, 16, 21, 197, 155, 196, 135, 20, 10, 135, 16, 9, 5, 197, 155, 196, 135, 20, 10, 135, 14, 1, 10, 197, 155, 196, 135, 20, 10, 135, 11, 18, 1, 197, 155, 196, 135, 20, 0, 11, 136, 11, 197, 130, 1, 197, 155, 196, 135, 20, 8, 197, 12, 133, 201, 20, 160, 20, 0, 10, 135, 19, 3, 8, 197, 130, 15, 13, 20, 0, 8, 133, 23, 9, 15, 197, 130, 20, 8, 133, 19, 9, 15, 197, 130, 20, 8, 133, 16, 9, 15, 197, 130, 20, 6, 195, 8, 21, 192, 20, 0, 9, 134, 26, 13, 195, 179, 18, 26, 20, 9, 134, 23, 12, 5, 11, 197, 130, 20, 9, 134, 20, 18, 23, 15, 197, 130, 20, 9, 134, 16, 9, 5, 11, 197, 130, 20, 0, 10, 135, 26, 23, 12, 5, 11, 197, 130, 20, 6, 195, 48, 80, 218, 20, 0, 11, 136, 19, 20, 197, 130, 21, 11, 197, 130, 20, 11, 136, 7, 18, 26, 13, 9, 15, 197, 130, 20, 0, 8, 133, 26, 23, 15, 197, 130, 20, 8, 133, 20, 11, 15, 197, 130, 20, 12, 137, 197, 155, 13, 9, 5, 18, 4, 197, 130, 20, 8, 133, 19, 19, 15, 197, 130, 20, 8, 133, 18, 23, 15, 197, 130, 20, 21, 2, 95, 123, 50, 4, 35, 82, 38, 35, 87, 15, 49, 55, 35, 63, 51, 109, 82, 110, 0, 15, 4, 95, 4, 9, 1, 10, 6, 40, 63, 55, 35, 58, 47, 0, 0, 9, 198, 80, 50, 14, 36, 84, 218, 20, 9, 134, 19, 9, 5, 11, 197, 130, 20, 9, 198, 76, 50, 14, 36, 84, 218, 20, 9, 134, 13, 195, 179, 11, 197, 130, 20, 9, 134, 3, 9, 5, 11, 197, 130, 20, 9, 198, 12, 132, 154, 12, 148, 218, 20, 8, 133, 2, 25, 197, 130, 25, 76, 7, 195, 80, 81, 207, 72, 12, 0, 10, 135, 26, 13, 195, 179, 11, 197, 130, 20, 10, 135, 23, 3, 9, 5, 11, 197, 130, 20, 10, 135, 20, 197, 130, 21, 11, 197, 130, 20, 0, 9, 134, 20, 18, 23, 15, 197, 132, 20, 11, 136, 197, 155, 3, 9, 5, 11, 197, 130, 20, 9, 134, 4, 26, 23, 15, 197, 132, 20, 10, 135, 2, 196, 153, 4, 26, 9, 5, 76, 5, 194, 80, 240, 72, 0, 10, 135, 19, 20, 18, 23, 15, 197, 132, 20, 0, 7, 196, 104, 224, 67, 104, 20, 6, 195, 104, 32, 87, 20, 7, 196, 77, 4, 129, 92, 20, 7, 196, 25, 84, 131, 104, 20, 7, 196, 12, 194, 83, 104, 20, 0, 8, 197, 77, 160, 218, 4, 208, 20, 23, 73, 12, 130, 80, 64, 83, 132, 4, 193, 64, 74, 37, 48, 107, 50, 70, 107, 57, 55, 0, 65, 9, 21, 73, 12, 130, 80, 64, 83, 132, 4, 193, 64, 74, 37, 48, 107, 50, 70, 107, 57, 55, 0, 9, 134, 11, 20, 195, 179, 18, 1, 76, 28, 2, 95, 125, 48, 51, 35, 82, 110, 15, 50, 4, 35, 82, 38, 35, 87, 15, 49, 55, 35, 63, 51, 6, 109, 82, 110, 0, 0, 8, 133, 19, 11, 15, 197, 155, 20, 0, 0, 8, 133, 11, 197, 130, 15, 13, 20, 12, 137, 14, 9, 5, 11, 20, 195, 179, 18, 1, 76, 12, 67, 40, 21, 211, 73, 6, 107, 58, 87, 0, 17, 0, 10, 135, 19, 20, 18, 196, 153, 3, 26, 20, 10, 135, 19, 16, 197, 130, 15, 19, 26, 20, 6, 195, 72, 16, 218, 20, 9, 134, 11, 20, 195, 179, 18, 5, 76, 0, 9, 198, 77, 160, 218, 5, 54, 128, 20, 9, 198, 9, 38, 141, 37, 54, 128, 20, 5, 194, 93, 144, 76, 0, 6, 195, 12, 134, 76, 20, 0, 12, 137, 14, 9, 5, 11, 20, 195, 179, 18, 5, 76, 0, 0, 0, 0, 9, 198, 76, 179, 14, 36, 84, 218, 20, 9, 198, 64, 50, 14, 36, 84, 218, 20, 8, 133, 3, 8, 3, 196, 153, 20, 0, 0, 17, 70, 12, 16, 133, 72, 225, 84, 49, 35, 69, 107, 51, 50, 6, 107, 0, 0, 8, 133, 26, 197, 130, 1, 10, 20, 0, 9, 134, 23, 20, 18, 195, 179, 10, 20, 9, 134, 19, 20, 18, 195, 179, 10, 20, 0, 15, 70, 12, 243, 84, 21, 52, 197, 49, 112, 47, 6, 107, 87, 0, 0, 0, 8, 133, 23, 23, 15, 197, 186, 20, 0, 8, 133, 26, 197, 130, 1, 13, 20, 8, 133, 23, 197, 130, 1, 13, 20, 11, 136, 19, 20, 18, 23, 195, 179, 197, 188, 20, 8, 133, 12, 197, 188, 196, 133, 20, 7, 196, 17, 84, 3, 104, 20, 6, 195, 9, 32, 75, 20, 0, 0, 21, 67, 64, 241, 5, 48, 109, 70, 6, 107, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 20, 67, 64, 241, 5, 48, 109, 70, 6, 107, 63, 50, 112, 0, 81, 109, 110, 196, 133, 32, 0, 8, 133, 11, 195, 179, 18, 26, 20, 0, 0, 0, 10, 135, 16, 18, 15, 197, 130, 2, 25, 20, 10, 135, 13, 9, 15, 197, 130, 2, 25, 20, 10, 135, 7, 1, 19, 197, 130, 2, 25, 20, 11, 136, 19, 20, 196, 153, 3, 8, 197, 130, 20, 13, 4, 95, 35, 51, 50, 87, 48, 35, 115, 57, 35, 0, 0, 11, 136, 26, 23, 25, 11, 197, 130, 2, 25, 20, 11, 136, 26, 7, 18, 15, 197, 130, 2, 25, 20, 11, 136, 23, 7, 18, 15, 197, 130, 2, 25, 20, 11, 136, 18, 197, 188, 15, 197, 130, 2, 25, 20, 11, 136, 18, 26, 5, 11, 197, 130, 2, 25, 20, 11, 136, 13, 9, 12, 11, 197, 130, 2, 25, 20, 11, 136, 13, 4, 12, 15, 197, 130, 2, 25, 20, 11, 136, 197, 130, 7, 15, 197, 130, 2, 25, 20, 11, 136, 4, 26, 9, 15, 197, 130, 2, 25, 20, 11, 136, 196, 135, 16, 15, 197, 130, 2, 25, 20, 11, 136, 3, 8, 12, 15, 197, 130, 2, 25, 20, 11, 136, 2, 18, 1, 11, 197, 130, 2, 25, 20, 9, 134, 23, 26, 14, 195, 179, 23, 20, 12, 137, 197, 155, 13, 9, 15, 18, 4, 197, 130, 20, 15, 67, 85, 49, 192, 40, 10, 107, 87, 79, 38, 6, 107, 0, 17, 0, 12, 137, 26, 18, 26, 5, 11, 197, 130, 2, 25, 20, 12, 137, 26, 13, 195, 179, 7, 197, 130, 2, 25, 20, 12, 137, 26, 13, 9, 12, 11, 197, 130, 2, 25, 20, 12, 137, 26, 2, 18, 1, 11, 197, 130, 2, 25, 20, 12, 137, 23, 12, 195, 179, 11, 197, 130, 2, 25, 20, 12, 137, 23, 4, 26, 9, 15, 197, 130, 2, 25, 20, 12, 137, 19, 3, 8, 12, 15, 197, 130, 2, 25, 20, 12, 137, 11, 12, 196, 153, 19, 197, 130, 2, 25, 20, 12, 137, 4, 197, 186, 7, 15, 197, 130, 2, 25, 20, 12, 137, 3, 8, 3, 9, 15, 197, 130, 2, 25, 20, 13, 138, 19, 16, 9, 5, 18, 26, 3, 8, 197, 130, 20, 9, 134, 19, 5, 3, 8, 197, 130, 20, 9, 134, 16, 21, 3, 8, 197, 130, 20, 12, 137, 2, 25, 12, 9, 197, 155, 3, 9, 5, 76, 0, 13, 138, 19, 3, 8, 12, 9, 197, 155, 3, 9, 5, 20, 13, 138, 19, 26, 197, 130, 25, 197, 155, 3, 9, 5, 20, 13, 138, 23, 26, 13, 195, 179, 7, 197, 130, 2, 25, 20, 13, 138, 19, 11, 12, 196, 153, 19, 197, 130, 2, 25, 20, 8, 197, 92, 65, 80, 13, 160, 20, 13, 138, 2, 25, 197, 130, 25, 197, 155, 3, 9, 5, 76, 0, 14, 139, 19, 26, 12, 9, 2, 25, 197, 155, 3, 9, 5, 20, 14, 139, 23, 197, 155, 3, 9, 5, 11, 197, 130, 2, 25, 20, 17, 66, 104, 80, 86, 6, 107, 63, 50, 112, 0, 81, 109, 110, 196, 133, 32, 18, 66, 104, 80, 86, 6, 107, 63, 65, 38, 107, 0, 81, 109, 110, 105, 101, 32, 14, 139, 13, 9, 1, 197, 130, 25, 197, 155, 3, 9, 5, 76, 0, 15, 140, 19, 26, 197, 130, 25, 2, 25, 197, 155, 3, 9, 5, 20, 15, 140, 19, 8, 197, 130, 25, 2, 25, 197, 155, 3, 9, 5, 20, 15, 140, 19, 3, 8, 12, 9, 2, 25, 197, 155, 3, 9, 5, 20, 11, 136, 19, 3, 8, 197, 130, 25, 2, 25, 20, 6, 195, 45, 2, 64, 20, 0, 13, 138, 26, 13, 9, 5, 18, 26, 3, 8, 197, 130, 20, 7, 196, 93, 4, 129, 92, 20, 10, 68, 12, 243, 84, 20, 49, 112, 47, 0, 11, 200, 76, 145, 68, 52, 149, 83, 21, 64, 65, 0, 10, 135, 197, 155, 12, 196, 153, 3, 26, 20, 0, 0, 0, 0, 6, 195, 77, 2, 74, 20, 0, 10, 135, 19, 3, 8, 197, 130, 5, 13, 20, 0, 14, 67, 52, 195, 128, 63, 37, 55, 57, 109, 50, 40, 81, 0, 0, 0, 8, 133, 26, 197, 130, 1, 16, 20, 6, 195, 93, 2, 74, 20, 6, 195, 9, 144, 218, 20, 9, 134, 11, 20, 195, 179, 18, 25, 76, 0, 0, 0, 12, 137, 14, 9, 5, 11, 20, 195, 179, 18, 25, 76, 0, 14, 69, 4, 225, 18, 21, 112, 107, 50, 70, 34, 57, 40, 0, 0, 0, 7, 132, 3, 12, 196, 133, 20, 0, 7, 196, 105, 38, 133, 12, 20, 7, 196, 93, 53, 1, 92, 20, 0, 6, 195, 105, 165, 74, 20, 9, 134, 197, 130, 197, 188, 196, 133, 20, 9, 134, 4, 18, 197, 188, 196, 133, 20, 10, 135, 11, 20, 195, 179, 18, 5, 10, 76, 0, 7, 131, 20, 196, 133, 72, 12, 0, 8, 133, 26, 23, 15, 197, 186, 20, 0, 8, 133, 18, 197, 188, 196, 133, 20, 8, 133, 13, 197, 188, 196, 133, 20, 10, 135, 13, 197, 155, 3, 9, 196, 135, 20, 13, 138, 14, 9, 5, 11, 20, 195, 179, 18, 5, 10, 76, 0, 6, 195, 105, 38, 74, 20, 6, 195, 45, 2, 74, 20, 6, 195, 33, 80, 218, 20, 0, 0, 8, 133, 26, 14, 1, 197, 130, 20, 0, 8, 133, 12, 197, 188, 196, 153, 20, 0, 9, 134, 23, 9, 197, 130, 2, 25, 20, 9, 134, 20, 25, 197, 130, 2, 25, 20, 9, 134, 13, 25, 197, 130, 2, 25, 20, 10, 135, 26, 13, 196, 133, 4, 18, 26, 20, 8, 197, 92, 145, 84, 73, 160, 20, 8, 197, 77, 68, 129, 77, 160, 20, 10, 135, 13, 197, 155, 3, 9, 197, 130, 20, 0, 10, 135, 26, 12, 1, 197, 130, 2, 25, 20, 10, 135, 26, 4, 1, 197, 130, 2, 25, 20, 10, 135, 26, 2, 9, 197, 130, 2, 25, 20, 10, 135, 23, 26, 21, 197, 130, 2, 25, 20, 10, 135, 23, 4, 1, 197, 130, 2, 25, 20, 10, 135, 23, 2, 9, 197, 130, 2, 25, 20, 10, 135, 20, 18, 21, 197, 130, 2, 25, 20, 10, 135, 16, 18, 21, 197, 130, 2, 25, 20, 10, 135, 4, 196, 133, 197, 130, 2, 25, 20, 10, 135, 3, 26, 21, 197, 130, 2, 25, 20, 0, 11, 136, 26, 19, 26, 25, 197, 130, 2, 25, 20, 11, 136, 26, 13, 1, 18, 197, 130, 2, 25, 20, 11, 136, 23, 197, 188, 25, 197, 130, 2, 25, 20, 11, 136, 23, 26, 2, 9, 197, 130, 2, 25, 20, 11, 136, 23, 3, 26, 21, 197, 130, 2, 25, 20, 11, 136, 19, 20, 18, 21, 197, 130, 2, 25, 20, 11, 136, 19, 16, 18, 21, 197, 130, 2, 25, 20, 11, 136, 19, 11, 18, 25, 197, 130, 2, 25, 20, 11, 136, 18, 197, 188, 1, 197, 130, 2, 25, 20, 11, 136, 16, 12, 23, 1, 197, 130, 2, 25, 20, 11, 136, 13, 197, 188, 25, 197, 130, 2, 25, 20, 11, 136, 13, 9, 196, 133, 197, 130, 2, 25, 20, 11, 136, 13, 4, 12, 9, 197, 130, 2, 25, 20, 11, 136, 197, 130, 7, 1, 197, 130, 2, 25, 20, 11, 136, 11, 12, 196, 133, 197, 130, 2, 25, 20, 11, 136, 7, 9, 196, 133, 197, 130, 2, 25, 20, 11, 136, 4, 18, 7, 1, 197, 130, 2, 25, 20, 11, 136, 3, 26, 11, 1, 197, 130, 2, 25, 20, 0, 12, 137, 19, 26, 12, 9, 197, 155, 3, 9, 5, 20, 12, 137, 26, 197, 188, 196, 133, 197, 130, 2, 25, 20, 12, 137, 26, 13, 9, 196, 133, 197, 130, 2, 25, 20, 12, 137, 26, 7, 18, 25, 26, 197, 130, 2, 25, 20, 12, 137, 26, 7, 9, 196, 133, 197, 130, 2, 25, 20, 12, 137, 23, 197, 188, 196, 133, 197, 130, 2, 25, 20, 12, 137, 23, 26, 9, 196, 133, 197, 130, 2, 25, 20, 12, 137, 23, 26, 4, 196, 133, 197, 130, 2, 25, 20, 12, 137, 23, 16, 9, 196, 133, 197, 130, 2, 25, 20, 12, 137, 23, 7, 9, 196, 133, 197, 130, 2, 25, 20, 12, 137, 23, 3, 9, 196, 133, 197, 130, 2, 25, 20, 12, 137, 19, 16, 9, 196, 133, 197, 130, 2, 25, 20, 12, 137, 19, 11, 12, 196, 133, 197, 130, 2, 25, 20, 12, 137, 16, 5, 197, 130, 26, 197, 130, 2, 25, 20, 12, 137, 4, 197, 186, 7, 1, 197, 130, 2, 25, 20, 10, 67, 12, 149, 15, 115, 37, 47, 109, 0, 19, 67, 12, 20, 19, 49, 35, 48, 87, 55, 109, 49, 0, 81, 108, 111, 99, 107, 32, 0, 13, 138, 23, 19, 16, 9, 196, 133, 197, 130, 2, 25, 20, 13, 138, 197, 155, 3, 9, 196, 133, 197, 130, 2, 25, 20, 8, 197, 104, 34, 69, 73, 160, 20, 8, 197, 77, 2, 69, 77, 160, 20, 13, 138, 13, 9, 5, 12, 9, 197, 155, 3, 9, 5, 76, 0, 14, 139, 23, 3, 8, 18, 26, 3, 9, 197, 130, 2, 25, 20, 0, 0, 8, 133, 197, 130, 11, 15, 13, 20, 0, 15, 69, 21, 48, 193, 64, 80, 107, 87, 49, 6, 107, 57, 48, 0, 0, 11, 136, 26, 10, 5, 197, 186, 4, 197, 186, 20, 0, 12, 137, 7, 14, 9, 5, 197, 186, 4, 197, 186, 20, 0, 7, 196, 64, 197, 193, 40, 20, 9, 134, 13, 197, 155, 3, 9, 10, 20, 0, 0, 10, 135, 19, 3, 8, 197, 130, 1, 13, 20, 0, 0, 7, 196, 64, 197, 193, 52, 20, 9, 134, 13, 196, 133, 4, 18, 26, 20, 7, 132, 197, 130, 1, 16, 20, 9, 198, 4, 195, 9, 77, 65, 82, 65, 0, 6, 195, 73, 144, 218, 20, 0, 10, 135, 26, 23, 15, 197, 130, 2, 25, 20, 10, 135, 26, 14, 15, 197, 130, 2, 25, 20, 10, 135, 20, 11, 15, 197, 130, 2, 25, 20, 10, 135, 19, 19, 15, 197, 130, 2, 25, 20, 10, 135, 18, 23, 15, 197, 130, 2, 25, 20, 10, 135, 16, 1, 19, 197, 130, 2, 25, 20, 10, 135, 12, 1, 26, 197, 130, 2, 25, 20, 10, 135, 11, 9, 19, 197, 130, 2, 25, 20, 10, 135, 7, 18, 15, 197, 130, 2, 25, 20, 10, 135, 7, 14, 15, 197, 130, 2, 25, 20, 10, 135, 4, 2, 15, 197, 130, 2, 25, 20, 8, 133, 197, 130, 26, 1, 23, 20, 15, 6, 22, 15, 9, 12, 195, 160, 82, 40, 35, 55, 35, 0, 67, 0, 11, 136, 197, 188, 7, 15, 197, 130, 2, 25, 20, 11, 136, 26, 23, 9, 19, 197, 130, 2, 25, 20, 11, 136, 26, 23, 1, 18, 197, 130, 2, 25, 20, 11, 136, 26, 20, 1, 18, 197, 130, 2, 25, 20, 11, 136, 26, 14, 9, 11, 197, 130, 2, 25, 20, 11, 136, 26, 13, 25, 19, 197, 130, 2, 25, 20, 11, 136, 26, 7, 1, 19, 197, 130, 2, 25, 20, 11, 136, 26, 4, 1, 18, 197, 130, 2, 25, 20, 11, 136, 23, 20, 1, 18, 197, 130, 2, 25, 20, 11, 136, 23, 19, 9, 15, 197, 130, 2, 25, 20, 11, 136, 23, 16, 1, 18, 197, 130, 2, 25, 20, 11, 136, 23, 12, 1, 26, 197, 130, 2, 25, 20, 11, 136, 23, 4, 1, 18, 197, 130, 2, 25, 20, 11, 136, 19, 16, 1, 19, 197, 130, 2, 25, 20, 11, 136, 19, 11, 9, 19, 197, 130, 2, 25, 20, 11, 136, 19, 9, 5, 11, 197, 130, 2, 25, 20, 11, 136, 13, 195, 179, 11, 197, 130, 2, 25, 20, 11, 136, 13, 195, 179, 7, 197, 130, 2, 25, 20, 11, 136, 13, 1, 18, 26, 197, 130, 2, 25, 20, 11, 136, 197, 130, 11, 1, 197, 130, 2, 25, 20, 11, 136, 7, 18, 26, 15, 197, 130, 2, 25, 20, 11, 136, 7, 18, 25, 26, 197, 130, 2, 25, 20, 11, 136, 3, 9, 5, 11, 197, 130, 2, 25, 20, 11, 136, 2, 12, 1, 11, 197, 130, 2, 25, 20, 0, 12, 137, 26, 13, 195, 179, 11, 197, 130, 2, 25, 20, 12, 137, 26, 13, 1, 18, 26, 197, 130, 2, 25, 20, 12, 137, 26, 2, 12, 1, 11, 197, 130, 2, 25, 20, 12, 137, 23, 13, 1, 18, 26, 197, 130, 2, 25, 20, 12, 137, 23, 9, 195, 179, 26, 197, 130, 2, 25, 20, 12, 137, 23, 7, 18, 25, 26, 197, 130, 2, 25, 20, 12, 137, 23, 3, 9, 5, 11, 197, 130, 2, 25, 20, 12, 137, 20, 197, 130, 21, 11, 197, 130, 2, 25, 20, 12, 137, 19, 26, 3, 26, 15, 197, 130, 2, 25, 20, 12, 137, 4, 18, 197, 188, 15, 197, 130, 2, 25, 20, 9, 134, 10, 196, 133, 20, 18, 26, 20, 7, 196, 12, 133, 193, 48, 20, 20, 68, 65, 38, 133, 16, 48, 89, 6, 107, 70, 65, 38, 107, 0, 81, 110, 105, 101, 32, 21, 68, 65, 38, 133, 16, 48, 89, 6, 107, 70, 65, 37, 105, 0, 81, 110, 105, 99, 104, 32, 20, 68, 65, 38, 133, 16, 48, 89, 6, 107, 70, 82, 35, 87, 0, 81, 119, 97, 115, 32, 20, 68, 65, 38, 133, 16, 48, 89, 6, 107, 47, 47, 110, 63, 0, 81, 116, 121, 109, 32, 21, 68, 65, 38, 133, 16, 48, 89, 6, 107, 47, 47, 110, 105, 0, 81, 116, 121, 99, 104, 32, 18, 68, 65, 38, 133, 16, 48, 89, 6, 107, 47, 47, 109, 0, 81, 116, 111, 32, 18, 68, 65, 38, 133, 16, 48, 89, 6, 107, 47, 47, 107, 0, 81, 116, 101, 32, 19, 68, 65, 38, 133, 16, 48, 89, 6, 107, 47, 47, 112, 0, 81, 116, 196, 133, 32, 20, 68, 65, 38, 133, 16, 48, 89, 6, 107, 70, 65, 37, 63, 0, 81, 110, 105, 109, 32, 21, 68, 65, 38, 133, 16, 48, 89, 6, 107, 70, 65, 38, 112, 0, 81, 110, 105, 196, 133, 32, 20, 68, 65, 38, 133, 16, 48, 89, 6, 107, 70, 50, 35, 87, 0, 81, 110, 97, 115, 32, 7, 196, 65, 38, 133, 16, 76, 0, 13, 138, 20, 18, 26, 196, 133, 19, 197, 130, 2, 25, 20, 13, 138, 197, 155, 3, 9, 5, 11, 197, 130, 2, 25, 20, 8, 197, 104, 208, 82, 81, 112, 20, 6, 195, 92, 145, 74, 20, 7, 132, 14, 21, 196, 135, 20, 0, 14, 139, 197, 188, 195, 179, 197, 130, 11, 197, 130, 2, 25, 20, 14, 139, 19, 20, 18, 26, 196, 133, 19, 197, 130, 2, 25, 20, 8, 133, 26, 12, 1, 196, 135, 20, 8, 133, 26, 4, 1, 196, 135, 20, 8, 133, 23, 4, 1, 196, 135, 20, 11, 136, 19, 16, 9, 196, 153, 20, 18, 26, 20, 8, 133, 13, 12, 5, 196, 135, 20, 8, 133, 13, 196, 133, 196, 135, 20, 6, 195, 12, 128, 197, 20, 0, 9, 134, 19, 20, 18, 21, 196, 135, 20, 9, 134, 19, 16, 18, 21, 196, 135, 20, 9, 134, 18, 197, 188, 5, 196, 135, 20, 9, 134, 16, 9, 196, 133, 196, 135, 20, 10, 199, 4, 212, 212, 21, 33, 1, 52, 65, 0, 10, 135, 26, 197, 188, 196, 133, 196, 135, 20, 10, 135, 26, 13, 9, 196, 133, 196, 135, 20, 10, 135, 23, 26, 4, 196, 133, 196, 135, 20, 10, 135, 23, 16, 9, 196, 133, 196, 135, 20, 10, 135, 19, 16, 9, 196, 133, 196, 135, 20, 8, 133, 197, 130, 11, 1, 13, 20, 7, 196, 52, 145, 76, 36, 76, 9, 198, 4, 194, 83, 80, 18, 82, 65, 0, 11, 136, 23, 19, 16, 9, 196, 133, 196, 135, 20, 10, 135, 10, 5, 197, 186, 4, 197, 186, 20, 0, 6, 195, 92, 145, 77, 20, 12, 137, 23, 3, 8, 18, 26, 3, 9, 196, 135, 20, 8, 133, 16, 18, 1, 196, 135, 20, 10, 67, 12, 149, 25, 115, 37, 47, 110, 0, 0, 9, 134, 197, 188, 18, 5, 196, 135, 20, 9, 134, 26, 197, 188, 21, 196, 135, 20, 9, 134, 26, 7, 18, 1, 196, 135, 20, 12, 137, 26, 2, 18, 21, 197, 186, 4, 197, 186, 20, 9, 134, 23, 18, 26, 5, 196, 135, 20, 8, 133, 197, 130, 11, 1, 10, 20, 12, 137, 4, 197, 186, 7, 14, 9, 5, 19, 26, 20, 9, 134, 3, 26, 3, 9, 196, 135, 20, 10, 67, 48, 240, 68, 55, 109, 58, 70, 0, 0, 9, 134, 19, 197, 130, 25, 19, 26, 20, 11, 136, 13, 9, 15, 197, 188, 4, 197, 188, 20, 13, 68, 24, 246, 69, 72, 81, 40, 35, 57, 6, 107, 0, 10, 67, 12, 144, 79, 74, 57, 35, 58, 0, 0, 11, 136, 3, 8, 18, 26, 3, 9, 196, 135, 20, 0, 0, 6, 195, 92, 145, 64, 20, 8, 133, 16, 18, 1, 197, 130, 20, 0, 9, 134, 26, 197, 188, 21, 197, 130, 20, 9, 134, 26, 7, 18, 1, 197, 130, 20, 8, 133, 18, 197, 188, 196, 153, 20, 9, 134, 3, 26, 3, 9, 197, 130, 20, 6, 195, 12, 145, 67, 20, 0, 8, 133, 26, 7, 9, 197, 132, 20, 8, 197, 77, 67, 9, 77, 160, 20, 0, 11, 136, 3, 8, 18, 26, 3, 9, 197, 130, 20, 0, 11, 136, 19, 9, 15, 4, 197, 130, 2, 25, 20, 11, 136, 19, 5, 3, 8, 197, 130, 2, 25, 20, 11, 136, 16, 21, 3, 8, 197, 130, 2, 25, 20, 11, 136, 2, 195, 179, 4, 197, 130, 2, 25, 20, 8, 133, 26, 12, 1, 197, 130, 20, 8, 133, 26, 4, 1, 197, 130, 20, 8, 133, 23, 4, 1, 197, 130, 20, 8, 133, 3, 26, 21, 197, 130, 20, 7, 132, 3, 12, 196, 153, 20, 0, 12, 137, 23, 19, 9, 15, 4, 197, 130, 2, 25, 20, 12, 137, 11, 18, 26, 5, 16, 197, 130, 2, 25, 20, 12, 137, 3, 9, 5, 18, 16, 197, 130, 2, 25, 20, 12, 137, 3, 8, 18, 25, 16, 197, 130, 2, 25, 20, 7, 196, 104, 112, 82, 8, 20, 7, 196, 81, 38, 133, 64, 20, 9, 134, 19, 20, 18, 21, 197, 130, 20, 9, 134, 19, 16, 18, 21, 197, 130, 20, 9, 134, 13, 9, 196, 133, 197, 130, 20, 7, 196, 45, 38, 133, 64, 20, 0, 13, 138, 26, 23, 9, 195, 179, 4, 197, 130, 2, 25, 20, 13, 138, 19, 11, 18, 26, 5, 16, 197, 130, 2, 25, 20, 13, 138, 19, 3, 8, 18, 25, 16, 197, 130, 2, 25, 20, 10, 135, 26, 197, 188, 196, 133, 197, 130, 20, 10, 135, 26, 13, 9, 196, 133, 197, 130, 20, 10, 135, 23, 197, 188, 196, 133, 197, 130, 20, 10, 135, 23, 26, 4, 196, 133, 197, 130, 20, 10, 135, 23, 16, 9, 196, 133, 197, 130, 20, 8, 197, 77, 2, 69, 73, 160, 20, 10, 135, 19, 16, 9, 196, 133, 197, 130, 20, 8, 197, 76, 180, 149, 77, 160, 20, 8, 197, 52, 67, 9, 77, 160, 20, 8, 197, 45, 38, 153, 13, 160, 20, 9, 134, 4, 18, 197, 188, 196, 153, 20, 0, 14, 139, 197, 155, 3, 9, 5, 18, 16, 197, 130, 2, 25, 20, 14, 139, 16, 9, 5, 18, 26, 3, 8, 197, 130, 2, 25, 20, 11, 136, 23, 19, 16, 9, 196, 133, 197, 130, 20, 0, 15, 140, 26, 13, 9, 5, 18, 26, 3, 8, 197, 130, 2, 25, 20, 12, 137, 23, 3, 8, 18, 26, 3, 9, 197, 130, 20, 10, 135, 3, 8, 18, 26, 1, 197, 132, 20, 0, 11, 200, 93, 54, 131, 104, 226, 69, 77, 160, 20, 11, 136, 19, 3, 8, 18, 26, 1, 197, 132, 20, 0, 10, 135, 19, 9, 5, 18, 4, 197, 186, 20, 18, 8, 3, 21, 18, 1, 195, 167, 1, 15, 49, 37, 51, 35, 87, 35, 109, 0, 0, 11, 136, 20, 23, 9, 5, 18, 4, 197, 186, 20, 0, 0, 0, 12, 137, 26, 13, 9, 1, 197, 188, 4, 197, 188, 20, 8, 197, 80, 50, 14, 36, 80, 20, 8, 197, 76, 50, 14, 36, 80, 20, 8, 197, 12, 132, 154, 12, 144, 20, 0, 9, 198, 105, 114, 67, 33, 38, 128, 20, 9, 198, 93, 160, 137, 21, 38, 128, 20, 10, 67, 32, 243, 69, 99, 109, 58, 63, 0, 0, 6, 195, 16, 243, 64, 20, 0, 9, 198, 65, 53, 18, 105, 148, 218, 20, 0, 9, 134, 12, 1, 197, 130, 2, 25, 20, 9, 134, 4, 1, 197, 130, 2, 25, 20, 9, 134, 2, 9, 197, 130, 2, 25, 20, 0, 10, 135, 197, 188, 25, 197, 130, 2, 25, 20, 10, 135, 26, 26, 21, 197, 130, 2, 25, 20, 10, 135, 26, 23, 1, 197, 130, 2, 25, 20, 10, 135, 26, 13, 25, 197, 130, 2, 25, 20, 10, 135, 23, 12, 1, 197, 130, 2, 25, 20, 10, 135, 20, 12, 1, 197, 130, 2, 25, 20, 10, 135, 20, 11, 1, 197, 130, 2, 25, 20, 10, 135, 19, 20, 1, 197, 130, 2, 25, 20, 10, 135, 19, 19, 1, 197, 130, 2, 25, 20, 10, 135, 19, 16, 1, 197, 130, 2, 25, 20, 10, 135, 19, 14, 21, 197, 130, 2, 25, 20, 10, 135, 18, 23, 1, 197, 130, 2, 25, 20, 10, 135, 11, 14, 21, 197, 130, 2, 25, 20, 10, 135, 10, 196, 133, 197, 130, 2, 25, 20, 10, 135, 7, 14, 9, 197, 130, 2, 25, 20, 10, 135, 3, 14, 9, 197, 130, 2, 25, 20, 0, 11, 136, 197, 188, 7, 1, 197, 130, 2, 25, 20, 11, 136, 26, 7, 14, 9, 197, 130, 2, 25, 20, 11, 136, 23, 19, 20, 1, 197, 130, 2, 25, 20, 11, 136, 23, 19, 14, 21, 197, 130, 2, 25, 20, 11, 136, 20, 18, 23, 1, 197, 130, 2, 25, 20, 11, 136, 197, 155, 14, 9, 197, 130, 2, 25, 20, 11, 136, 19, 20, 12, 9, 197, 130, 2, 25, 20, 11, 136, 16, 3, 8, 1, 197, 130, 2, 25, 20, 11, 136, 13, 4, 12, 1, 197, 130, 2, 25, 20, 11, 136, 11, 23, 9, 20, 197, 130, 2, 25, 20, 11, 136, 11, 197, 130, 21, 197, 130, 2, 25, 20, 11, 136, 196, 135, 16, 1, 197, 130, 2, 25, 20, 11, 136, 196, 135, 13, 9, 197, 130, 2, 25, 20, 11, 136, 3, 8, 12, 1, 197, 130, 2, 25, 20, 6, 195, 92, 19, 64, 72, 0, 12, 137, 26, 19, 9, 15, 4, 197, 130, 2, 25, 20, 12, 137, 26, 4, 10, 196, 133, 197, 130, 2, 25, 20, 12, 137, 23, 11, 197, 130, 21, 197, 130, 2, 25, 20, 12, 137, 20, 11, 14, 196, 133, 197, 130, 2, 25, 20, 12, 137, 20, 196, 153, 3, 8, 197, 130, 2, 25, 20, 12, 137, 197, 155, 12, 5, 16, 197, 130, 2, 25, 20, 12, 137, 19, 26, 3, 26, 21, 197, 130, 2, 25, 20, 12, 137, 19, 11, 18, 26, 25, 197, 130, 2, 25, 20, 12, 137, 19, 11, 197, 130, 21, 197, 130, 2, 25, 20, 12, 137, 19, 3, 8, 12, 1, 197, 130, 2, 25, 20, 12, 137, 13, 11, 14, 196, 133, 197, 130, 2, 25, 20, 12, 137, 4, 18, 197, 188, 1, 197, 130, 2, 25, 20, 12, 137, 2, 18, 14, 196, 133, 197, 130, 2, 25, 20, 0, 13, 138, 197, 188, 7, 14, 196, 133, 197, 130, 2, 25, 20, 13, 138, 23, 23, 9, 195, 179, 4, 197, 130, 2, 25, 20, 13, 138, 20, 3, 8, 14, 196, 133, 197, 130, 2, 25, 20, 13, 138, 18, 197, 188, 14, 196, 133, 197, 130, 2, 25, 20, 13, 138, 16, 3, 8, 14, 196, 133, 197, 130, 2, 25, 20, 13, 138, 4, 18, 7, 14, 196, 133, 197, 130, 2, 25, 20, 13, 138, 3, 26, 11, 14, 196, 133, 197, 130, 2, 25, 20, 9, 134, 197, 130, 197, 188, 196, 153, 20, 7, 132, 12, 5, 196, 135, 20, 0, 14, 139, 4, 197, 188, 4, 197, 188, 25, 197, 130, 2, 25, 20, 14, 139, 4, 197, 186, 7, 14, 196, 133, 197, 130, 2, 25, 20, 14, 139, 3, 8, 197, 130, 195, 179, 4, 197, 130, 2, 25, 20, 8, 133, 26, 23, 9, 196, 135, 20, 8, 133, 26, 13, 25, 196, 135, 20, 8, 133, 23, 12, 1, 196, 135, 20, 8, 133, 19, 20, 1, 196, 135, 20, 8, 133, 11, 14, 21, 196, 135, 20, 8, 133, 11, 12, 5, 196, 135, 20, 8, 133, 10, 196, 133, 196, 135, 20, 0, 9, 134, 26, 18, 26, 21, 196, 135, 20, 9, 134, 23, 19, 14, 21, 196, 135, 20, 9, 134, 23, 18, 26, 21, 196, 135, 20, 9, 134, 23, 16, 12, 5, 196, 135, 20, 9, 134, 19, 16, 12, 5, 196, 135, 20, 9, 134, 19, 11, 12, 5, 196, 135, 20, 9, 134, 16, 14, 196, 133, 196, 135, 20, 9, 134, 13, 4, 12, 5, 196, 135, 20, 9, 134, 11, 197, 130, 21, 196, 135, 20, 13, 67, 45, 4, 128, 49, 35, 48, 51, 35, 55, 0, 24, 0, 10, 135, 26, 4, 10, 196, 133, 196, 135, 20, 10, 135, 23, 11, 197, 130, 21, 196, 135, 20, 8, 133, 19, 19, 9, 196, 133, 20, 10, 135, 19, 11, 197, 130, 21, 196, 135, 20, 10, 135, 4, 18, 197, 188, 5, 196, 135, 20, 9, 198, 4, 192, 83, 80, 18, 82, 65, 0, 11, 136, 19, 20, 197, 130, 1, 13, 197, 155, 20, 11, 136, 19, 3, 8, 14, 196, 133, 196, 135, 20, 11, 136, 19, 3, 8, 197, 130, 1, 197, 155, 20, 10, 135, 16, 195, 179, 10, 4, 197, 186, 20, 11, 136, 16, 3, 8, 14, 196, 133, 196, 135, 20, 7, 132, 4, 21, 196, 135, 20, 11, 136, 4, 18, 7, 14, 196, 133, 196, 135, 20, 11, 136, 3, 26, 11, 14, 196, 133, 196, 135, 20, 0, 11, 136, 18, 197, 188, 14, 9, 5, 19, 26, 20, 11, 136, 16, 18, 26, 25, 10, 4, 197, 186, 20, 0, 10, 135, 197, 155, 3, 9, 5, 18, 16, 20, 9, 134, 16, 197, 130, 1, 196, 135, 20, 9, 134, 4, 18, 23, 9, 196, 135, 20, 0, 10, 135, 23, 16, 197, 130, 1, 196, 135, 20, 10, 135, 19, 26, 3, 26, 1, 196, 135, 20, 10, 135, 19, 16, 197, 130, 1, 196, 135, 20, 9, 134, 197, 130, 11, 1, 19, 26, 20, 11, 136, 7, 23, 9, 197, 188, 4, 197, 188, 20, 19, 67, 12, 131, 215, 74, 35, 58, 74, 35, 40, 0, 66, 81, 99, 104, 111, 119, 32, 0, 8, 197, 77, 68, 154, 20, 192, 20, 9, 134, 4, 18, 23, 9, 196, 133, 20, 0, 8, 133, 26, 23, 196, 133, 3, 20, 7, 132, 4, 21, 197, 130, 20, 0, 0, 9, 134, 4, 18, 23, 9, 197, 130, 20, 0, 8, 133, 26, 23, 9, 197, 132, 20, 10, 135, 19, 26, 3, 26, 1, 197, 130, 20, 8, 133, 19, 20, 1, 197, 132, 20, 9, 134, 18, 197, 188, 14, 9, 5, 20, 0, 9, 134, 197, 188, 197, 130, 15, 16, 20, 9, 134, 19, 6, 18, 21, 197, 132, 20, 14, 70, 12, 245, 20, 4, 113, 64, 49, 109, 47, 110, 73, 0, 15, 70, 12, 243, 12, 4, 113, 64, 49, 109, 55, 6, 35, 88, 0, 10, 135, 13, 9, 196, 153, 4, 26, 25, 76, 0, 8, 133, 26, 13, 25, 197, 130, 20, 8, 133, 23, 12, 1, 197, 130, 20, 8, 133, 20, 12, 1, 197, 130, 20, 12, 137, 197, 155, 13, 9, 1, 18, 4, 197, 130, 20, 8, 133, 19, 20, 1, 197, 130, 20, 8, 133, 19, 16, 1, 197, 130, 20, 8, 133, 11, 14, 21, 197, 130, 20, 8, 133, 10, 196, 133, 197, 130, 20, 18, 67, 12, 131, 208, 74, 109, 48, 87, 40, 37, 0, 81, 115, 117, 101, 121, 32, 0, 9, 134, 23, 19, 14, 21, 197, 130, 20, 7, 196, 93, 38, 133, 64, 20, 9, 134, 11, 197, 130, 21, 197, 130, 20, 0, 8, 133, 26, 18, 1, 197, 132, 20, 8, 197, 104, 210, 76, 13, 160, 20, 10, 135, 26, 4, 10, 196, 133, 197, 130, 20, 10, 135, 23, 11, 197, 130, 21, 197, 130, 20, 10, 135, 19, 11, 197, 130, 21, 197, 130, 20, 8, 197, 52, 150, 132, 73, 160, 20, 8, 197, 29, 86, 132, 73, 160, 20, 0, 9, 134, 19, 16, 12, 21, 197, 132, 20, 11, 136, 16, 3, 8, 14, 196, 133, 197, 130, 20, 11, 136, 4, 18, 7, 14, 196, 133, 197, 130, 20, 11, 136, 3, 26, 11, 14, 196, 133, 197, 130, 20, 14, 70, 12, 243, 12, 20, 113, 64, 49, 109, 55, 107, 73, 0, 0, 8, 197, 105, 54, 129, 73, 0, 20, 0, 7, 196, 104, 224, 83, 104, 20, 7, 196, 92, 64, 83, 104, 20, 12, 68, 12, 245, 80, 20, 49, 40, 48, 6, 107, 0, 7, 132, 20, 5, 197, 188, 8, 0, 9, 198, 93, 54, 131, 104, 84, 0, 20, 11, 136, 23, 19, 11, 18, 26, 5, 197, 155, 20, 6, 195, 76, 145, 74, 20, 10, 135, 4, 18, 197, 188, 25, 19, 26, 20, 0, 11, 136, 2, 18, 21, 197, 186, 4, 197, 186, 20, 0, 0, 8, 133, 23, 197, 130, 15, 13, 20, 7, 196, 80, 176, 83, 104, 20, 0, 8, 133, 16, 18, 1, 197, 188, 20, 0, 0, 7, 132, 197, 130, 11, 1, 20, 0, 0, 6, 18, 66, 107, 97, 99, 104, 0, 107, 196, 153, 0, 107, 196, 133, 0, 107, 111, 109, 0, 107, 97, 0, 107, 105, 0, 99, 101, 0, 107, 111, 0, 7, 6, 100, 103, 0, 4, 1, 101, 122, 114, 112, 3, 70, 79, 0, 8, 97, 110, 0, 8, 97, 110, 101, 105, 110, 0, 8, 97, 110, 111, 112, 0, 8, 97, 110, 111, 112, 101, 105, 110, 0, 8, 111, 0, 8, 111, 101, 105, 110, 0, 8, 111, 111, 112, 0, 8, 111, 111, 112, 101, 105, 110, 0, 8, 111, 112, 0, 8, 111, 112, 101, 105, 110, 0, 8, 111, 112, 111, 112, 0, 8, 111, 112, 111, 112, 101, 105, 110, 0, 4, 3, 73, 0, 101, 2, 32, 0, 7, 6, 111, 101, 0, 4, 1, 106, 2, 114, 3, 107, 0, 1, 106, 108, 0, 1, 115, 2, 114, 0, 1, 106, 99, 3, 109, 107, 0, 7, 6, 112, 104, 0, 3, 81, 0, 7, 6, 115, 104, 0, 4, 8, 105, 102, 2, 97, 114, 109, 111, 110, 3, 87, 99, 0, 8, 107, 101, 0, 8, 121, 100, 0, 3, 89, 0, 105, 114, 101, 3, 89, 35, 57, 107, 51, 0, 7, 6, 116, 104, 0, 4, 8, 3, 47, 0, 8, 101, 2, 97, 110, 97, 107, 0, 101, 8, 2, 32, 3, 70, 107, 0, 101, 119, 3, 81, 57, 40, 0, 117, 110, 100, 101, 114, 98, 105, 8, 2, 114, 100, 3, 81, 107, 50, 70, 107, 51, 69, 107, 0, 97, 110, 107, 8, 3, 81, 107, 66, 49, 0, 3, 87, 0, 2, 105, 101, 32, 3, 93, 0, 7, 6, 116, 122, 0, 2, 197, 130, 3, 47, 86, 0, 3, 115, 0, 7, 6, 195, 164, 0, 3, 107, 0, 7, 6, 195, 165, 0, 3, 109, 0, 7, 6, 195, 166, 0, 3, 107, 0, 7, 6, 195, 173, 0, 3, 37, 0, 2, 17, 65, 3, 37, 57, 0, 7, 6, 195, 177, 0, 3, 65, 0, 2, 17, 65, 3, 65, 38, 0, 7, 6, 195, 179, 0, 4, 1, 21, 2, 17, 67, 197, 130, 98, 121, 32, 3, 8, 40, 0, 1, 21, 2, 17, 67, 197, 130, 98, 121, 109, 32, 0, 1, 21, 2, 17, 67, 197, 130, 98, 121, 197, 155, 32, 0, 3, 40, 0, 7, 6, 195, 182, 0, 3, 107, 0, 7, 6, 195, 184, 0, 3, 107, 0, 7, 6, 195, 188, 0, 3, 37, 0, 7, 6, 196, 133, 0, 4, 2, 108, 3, 109, 0, 2, 197, 130, 0, 4, 2, 99, 3, 109, 50, 0, 2, 100, 0, 2, 116, 0, 4, 2, 98, 3, 109, 63, 0, 2, 112, 0, 4, 2, 99, 105, 3, 109, 65, 0, 2, 100, 122, 105, 0, 2, 100, 197, 186, 0, 2, 196, 135, 0, 4, 2, 103, 3, 109, 66, 0, 2, 107, 0, 3, 112, 0, 4, 2, 32, 3, 112, 10, 0, 2, 32, 17, 65, 0, 7, 6, 196, 135, 0, 3, 117, 0, 4, 2, 98, 3, 118, 0, 2, 103, 0, 7, 6, 196, 141, 0, 3, 74, 0, 7, 6, 196, 153, 0, 4, 1, 105, 2, 116, 110, 97, 3, 107, 0, 2, 32, 0, 2, 108, 0, 2, 197, 130, 0, 2, 32, 17, 65, 3, 107, 10, 0, 4, 2, 99, 3, 107, 50, 0, 2, 100, 0, 2, 116, 0, 4, 2, 98, 3, 107, 63, 0, 2, 112, 0, 4, 2, 99, 105, 3, 107, 65, 0, 2, 100, 122, 105, 0, 2, 100, 197, 186, 0, 2, 115, 105, 0, 2, 196, 135, 0, 2, 197, 155, 0, 196, 135, 2, 100, 122, 105, 101, 0, 4, 2, 103, 3, 107, 66, 0, 2, 107, 0, 3, 111, 0, 7, 6, 197, 130, 0, 2, 32, 3, 0, 3, 58, 0, 4, 1, 17, 65, 2, 32, 3, 58, 10, 0, 1, 115, 121, 109, 2, 32, 0, 98, 121, 109, 1, 21, 2, 32, 14, 128, 128, 129, 3, 63, 0, 98, 121, 197, 155, 1, 21, 2, 32, 14, 128, 128, 129, 3, 95, 0, 7, 6, 197, 132, 0, 3, 65, 0, 7, 6, 197, 153, 0, 3, 88, 0, 7, 6, 197, 155, 0, 196, 135, 2, 100, 122, 105, 101, 3, 94, 0, 3, 95, 0, 7, 6, 197, 161, 0, 3, 89, 0, 7, 6, 197, 186, 0, 3, 94, 0, 2, 32, 3, 95, 0, 7, 6, 197, 188, 0, 3, 88, 0, 2, 32, 3, 89, 0, 7, 6, 197, 190, 0, 3, 88, 0, 7, 6, 97, 0, 108, 108, 111, 119, 101, 101, 1, 104, 2, 110, 32, 3, 6, 35, 55, 109, 58, 110, 0, 4, 1, 21, 2, 197, 130, 98, 121, 32, 3, 8, 35, 0, 1, 21, 2, 197, 130, 98, 121, 109, 32, 0, 1, 21, 2, 197, 130, 98, 121, 197, 155, 32, 0, 1, 130, 197, 21, 2, 98, 121, 32, 0, 1, 130, 197, 21, 2, 98, 121, 109, 32, 0, 1, 130, 197, 21, 2, 98, 121, 197, 155, 32, 0, 3, 35, 0, 2, 32, 3, 35, 10, 0, 4, 105, 8, 107, 2, 114, 3, 35, 37, 0, 105, 8, 116, 108, 97, 2, 114, 0, 114, 99, 121, 8, 2, 21, 14, 129, 132, 132, 3, 35, 51, 115, 110, 0, 108, 108, 111, 119, 101, 101, 1, 104, 2, 110, 3, 35, 55, 109, 58, 110, 0, 101, 8, 2, 114, 17, 65, 3, 35, 107, 0, 4, 101, 2, 32, 3, 107, 0, 101, 8, 0, 105, 1, 17, 67, 2, 114, 0, 99, 107, 117, 2, 112, 3, 107, 49, 35, 0, 114, 99, 104, 105, 101, 8, 3, 107, 51, 74, 37, 0, 114, 99, 104, 105, 101, 8, 2, 17, 67, 3, 107, 51, 74, 38, 107, 0, 108, 8, 104, 2, 108, 3, 109, 0, 7, 6, 98, 0, 4, 2, 32, 3, 48, 0, 197, 130, 1, 97, 106, 2, 107, 17, 65, 0, 3, 69, 0, 2, 105, 3, 69, 38, 0, 105, 2, 17, 65, 3, 69, 38, 57, 0, 4, 101, 114, 103, 1, 21, 21, 2, 32, 14, 129, 128, 132, 3, 69, 107, 34, 79, 0, 195, 182, 114, 103, 1, 21, 21, 2, 32, 14, 129, 128, 132, 0, 195, 184, 114, 103, 1, 21, 21, 2, 32, 14, 129, 128, 132, 0, 111, 114, 103, 1, 21, 21, 2, 32, 14, 129, 128, 132, 3, 69, 109, 34, 79, 0, 7, 6, 99, 0, 104, 97, 2, 109, 112, 105, 3, 47, 88, 107, 0, 4, 1, 17, 65, 118, 3, 49, 0, 1, 101, 115, 111, 99, 2, 97, 110, 115, 0, 1, 105, 100, 2, 116, 17, 65, 0, 2, 97, 99, 105, 101, 32, 0, 2, 97, 108, 118, 0, 2, 97, 116, 32, 0, 2, 97, 116, 97, 32, 0, 2, 97, 116, 97, 109, 105, 32, 0, 2, 97, 116, 101, 109, 32, 0, 2, 97, 116, 111, 32, 0, 2, 97, 116, 111, 109, 32, 0, 2, 108, 105, 112, 0, 2, 111, 115, 101, 99, 97, 110, 115, 0, 2, 111, 115, 105, 110, 0, 2, 111, 116, 97, 110, 103, 0, 2, 115, 0, 8, 2, 97, 98, 101, 114, 110, 101, 116, 0, 8, 2, 97, 108, 101, 110, 100, 0, 8, 2, 97, 110, 0, 8, 2, 97, 112, 112, 0, 8, 2, 97, 112, 115, 32, 0, 8, 2, 97, 112, 115, 108, 111, 0, 8, 2, 97, 114, 97, 118, 0, 8, 2, 97, 114, 108, 0, 8, 2, 97, 114, 112, 0, 8, 2, 97, 114, 116, 0, 8, 2, 97, 114, 118, 0, 8, 2, 108, 17, 65, 0, 8, 2, 111, 109, 0, 8, 2, 111, 110, 17, 67, 0, 8, 2, 111, 114, 17, 67, 0, 8, 2, 111, 119, 98, 111, 0, 8, 2, 114, 0, 8, 2, 117, 109, 117, 108, 0, 8, 101, 100, 2, 111, 114, 0, 8, 110, 105, 108, 2, 111, 108, 110, 0, 8, 114, 97, 2, 97, 100, 105, 97, 32, 0, 8, 114, 97, 2, 97, 100, 105, 105, 32, 0, 8, 114, 97, 2, 97, 100, 105, 111, 32, 0, 8, 114, 97, 2, 97, 100, 105, 196, 133, 32, 0, 8, 114, 97, 2, 97, 100, 105, 196, 153, 32, 0, 8, 115, 105, 100, 2, 111, 0, 99, 2, 97, 99, 105, 101, 32, 0, 99, 2, 97, 116, 17, 65, 0, 99, 2, 97, 116, 32, 0, 99, 2, 97, 116, 97, 32, 0, 99, 2, 97, 116, 97, 109, 105, 32, 0, 99, 2, 97, 116, 101, 109, 32, 0, 99, 2, 97, 116, 111, 32, 0, 99, 2, 97, 116, 111, 109, 32, 0, 99, 8, 111, 109, 2, 17, 65, 0, 104, 8, 2, 114, 105, 115, 116, 111, 0, 107, 1, 17, 65, 118, 0, 107, 1, 111, 108, 2, 32, 0, 107, 1, 111, 108, 2, 97, 32, 0, 107, 1, 111, 108, 2, 105, 101, 109, 32, 0, 107, 1, 111, 108, 2, 117, 32, 0, 107, 8, 101, 100, 0, 107, 8, 111, 114, 2, 17, 65, 0, 4, 8, 2, 97, 109, 101, 109, 98, 101, 114, 116, 3, 49, 35, 0, 97, 108, 2, 108, 17, 65, 0, 97, 108, 121, 2, 112, 115, 3, 49, 35, 55, 37, 0, 97, 115, 99, 3, 49, 35, 87, 49, 0, 117, 114, 105, 101, 8, 3, 49, 37, 51, 37, 0, 114, 111, 105, 115, 115, 8, 3, 49, 51, 34, 40, 35, 87, 0, 114, 97, 99, 107, 3, 49, 51, 35, 49, 0, 114, 101, 101, 110, 114, 101, 97, 8, 115, 2, 100, 3, 49, 51, 37, 50, 51, 37, 0, 114, 101, 115, 99, 2, 101, 110, 100, 3, 49, 51, 107, 89, 74, 0, 108, 111, 119, 8, 2, 110, 3, 49, 55, 35, 58, 0, 108, 101, 97, 8, 2, 17, 67, 3, 49, 55, 37, 0, 108, 111, 105, 115, 8, 2, 111, 3, 49, 55, 40, 35, 86, 0, 108, 111, 99, 104, 8, 2, 97, 114, 100, 3, 49, 55, 109, 89, 0, 4, 97, 8, 2, 109, 3, 49, 107, 0, 117, 8, 2, 114, 108, 105, 0, 97, 108, 2, 108, 3, 49, 109, 0, 111, 112, 121, 119, 114, 105, 8, 2, 116, 3, 49, 109, 48, 110, 51, 35, 57, 0, 111, 99, 107, 8, 3, 49, 109, 49, 0, 111, 110, 99, 8, 2, 101, 114, 116, 3, 49, 109, 50, 74, 0, 111, 97, 99, 104, 8, 3, 49, 109, 58, 74, 0, 4, 99, 2, 105, 32, 3, 74, 0, 99, 2, 105, 97, 32, 0, 99, 2, 105, 99, 104, 32, 0, 99, 2, 105, 101, 103, 111, 32, 0, 99, 2, 105, 101, 109, 32, 0, 99, 2, 105, 101, 109, 117, 32, 0, 99, 2, 105, 105, 101, 32, 0, 99, 2, 105, 109, 32, 0, 99, 2, 105, 109, 105, 32, 0, 99, 2, 105, 110, 97, 32, 0, 99, 2, 105, 110, 101, 109, 32, 0, 99, 2, 105, 110, 105, 101, 32, 0, 99, 2, 105, 110, 111, 32, 0, 99, 2, 105, 111, 32, 0, 104, 1, 17, 65, 118, 0, 104, 8, 2, 105, 112, 0, 122, 0, 104, 97, 110, 2, 110, 101, 108, 3, 74, 35, 0, 104, 97, 114, 108, 101, 8, 2, 115, 3, 74, 35, 51, 55, 87, 0, 104, 111, 119, 8, 2, 100, 101, 114, 3, 74, 35, 58, 0, 104, 105, 101, 8, 2, 102, 3, 74, 37, 0, 104, 105, 112, 112, 101, 110, 100, 97, 108, 8, 2, 17, 65, 3, 74, 37, 48, 107, 50, 70, 107, 57, 55, 0, 105, 99, 8, 2, 101, 114, 111, 110, 3, 74, 37, 74, 0, 104, 97, 108, 108, 101, 110, 103, 8, 2, 101, 114, 3, 74, 107, 55, 107, 50, 73, 0, 8, 2, 105, 110, 101, 114, 3, 87, 0, 4, 105, 1, 114, 97, 2, 97, 32, 3, 87, 37, 57, 0, 105, 1, 114, 97, 2, 105, 32, 0, 105, 1, 114, 97, 2, 111, 32, 0, 105, 1, 114, 97, 2, 196, 133, 32, 0, 105, 1, 114, 97, 2, 196, 153, 32, 0, 4, 105, 1, 17, 65, 2, 97, 110, 97, 32, 3, 87, 57, 0, 105, 1, 17, 65, 2, 97, 110, 101, 109, 32, 0, 105, 1, 17, 65, 2, 97, 110, 105, 101, 32, 0, 105, 1, 17, 65, 2, 97, 110, 111, 32, 0, 105, 1, 17, 65, 2, 97, 110, 111, 119, 105, 32, 0, 105, 1, 105, 108, 2, 97, 32, 0, 105, 1, 105, 108, 2, 105, 32, 0, 105, 1, 105, 108, 2, 111, 32, 0, 105, 1, 105, 108, 2, 196, 133, 32, 0, 105, 1, 105, 108, 2, 196, 153, 32, 0, 4, 104, 2, 101, 114, 114, 3, 89, 0, 104, 2, 101, 118, 0, 104, 105, 99, 8, 2, 97, 103, 17, 65, 3, 89, 37, 49, 0, 104, 111, 112, 105, 8, 2, 110, 3, 89, 109, 48, 107, 0, 104, 2, 105, 3, 97, 0, 104, 3, 105, 0, 104, 105, 1, 121, 115, 112, 2, 97, 3, 105, 37, 0, 104, 105, 2, 17, 65, 3, 105, 57, 0, 4, 3, 115, 0, 1, 105, 118, 2, 101, 0, 8, 2, 105, 114, 0, 8, 2, 111, 109, 98, 101, 114, 0, 8, 2, 111, 109, 98, 114, 17, 65, 0, 8, 2, 111, 109, 105, 101, 115, 0, 8, 2, 111, 109, 105, 110, 117, 0, 4, 2, 105, 3, 117, 0, 105, 2, 17, 65, 0, 7, 6, 100, 0, 2, 32, 3, 47, 0, 3, 70, 0, 105, 2, 17, 65, 3, 70, 57, 0, 4, 197, 188, 8, 97, 110, 3, 70, 88, 0, 197, 188, 8, 97, 110, 111, 112, 0, 197, 188, 8, 111, 0, 197, 188, 8, 111, 112, 0, 4, 122, 105, 8, 97, 110, 2, 101, 109, 3, 70, 94, 0, 122, 105, 8, 111, 112, 2, 101, 109, 0, 197, 188, 3, 73, 0, 197, 188, 2, 32, 3, 74, 0, 2, 105, 3, 114, 0, 4, 105, 101, 115, 2, 101, 108, 3, 114, 37, 86, 0, 105, 101, 115, 2, 108, 17, 65, 0, 122, 2, 32, 3, 115, 0, 122, 3, 116, 0, 197, 186, 2, 32, 3, 117, 0, 4, 122, 2, 105, 3, 118, 0, 122, 105, 2, 17, 65, 0, 197, 186, 0, 7, 6, 101, 0, 4, 1, 21, 2, 17, 67, 197, 130, 98, 121, 32, 3, 8, 107, 0, 1, 21, 2, 17, 67, 197, 130, 98, 121, 109, 32, 0, 1, 21, 2, 17, 67, 197, 130, 98, 121, 197, 155, 32, 0, 4, 105, 8, 2, 17, 67, 3, 35, 57, 0, 105, 8, 108, 107, 2, 110, 0, 4, 97, 1, 100, 2, 108, 101, 114, 3, 37, 0, 97, 1, 112, 115, 2, 107, 0, 97, 1, 116, 0, 97, 8, 17, 67, 2, 32, 0, 97, 8, 104, 2, 108, 101, 0, 97, 8, 108, 2, 100, 0, 101, 2, 110, 0, 101, 8, 17, 67, 2, 32, 0, 97, 108, 105, 116, 121, 1, 114, 2, 32, 3, 37, 6, 107, 55, 37, 47, 110, 0, 109, 97, 105, 108, 8, 3, 37, 63, 107, 57, 55, 0, 97, 115, 1, 108, 2, 105, 110, 3, 37, 86, 0, 4, 3, 107, 0, 97, 1, 114, 2, 103, 97, 110, 0, 97, 8, 104, 2, 100, 0, 2, 32, 17, 65, 3, 107, 10, 0, 97, 1, 116, 2, 116, 114, 3, 107, 35, 0, 97, 118, 121, 1, 104, 2, 25, 3, 107, 82, 37, 0, 1, 105, 2, 32, 3, 108, 0, 117, 2, 116, 115, 99, 104, 3, 109, 57, 0, 7, 6, 102, 0, 3, 81, 0, 105, 2, 17, 65, 3, 81, 38, 57, 0, 7, 6, 103, 0, 2, 32, 3, 49, 0, 101, 110, 116, 108, 101, 109, 97, 110, 8, 3, 73, 107, 50, 47, 107, 55, 63, 107, 50, 0, 4, 101, 111, 114, 103, 105, 8, 2, 97, 32, 3, 73, 109, 51, 73, 57, 0, 101, 111, 114, 103, 105, 8, 2, 105, 32, 0, 101, 111, 114, 103, 105, 8, 2, 111, 32, 0, 101, 111, 114, 103, 105, 8, 2, 196, 133, 32, 0, 101, 111, 114, 103, 105, 8, 2, 196, 153, 32, 0, 4, 3, 79, 0, 104, 0, 2, 105, 3, 79, 38, 0, 105, 1, 105, 104, 2, 101, 3, 79, 57, 0, 197, 130, 2, 32, 3, 79, 58, 0, 97, 116, 101, 2, 115, 3, 79, 107, 57, 47, 0, 7, 6, 104, 0, 2, 105, 3, 97, 0, 3, 99, 0, 105, 2, 17, 65, 3, 99, 57, 0, 7, 6, 105, 0, 114, 101, 8, 102, 2, 102, 111, 120, 32, 3, 6, 35, 57, 107, 51, 0, 4, 1, 21, 2, 98, 121, 197, 155, 99, 105, 101, 32, 3, 8, 37, 0, 1, 21, 2, 98, 121, 197, 155, 109, 121, 32, 0, 1, 97, 100, 117, 21, 2, 18, 66, 32, 0, 1, 97, 104, 99, 21, 2, 18, 66, 32, 0, 1, 97, 122, 111, 21, 2, 18, 66, 32, 0, 1, 98, 97, 108, 21, 2, 18, 66, 32, 0, 1, 102, 97, 114, 21, 2, 18, 66, 32, 0, 1, 102, 105, 108, 21, 2, 18, 66, 32, 0, 1, 102, 111, 114, 21, 2, 18, 66, 32, 0, 1, 102, 121, 99, 21, 2, 18, 66, 32, 0, 1, 103, 97, 114, 21, 2, 18, 66, 32, 0, 1, 103, 111, 103, 21, 2, 18, 66, 32, 0, 1, 103, 111, 108, 2, 18, 66, 32, 0, 1, 103, 114, 117, 21, 2, 18, 66, 32, 0, 1, 104, 99, 121, 21, 2, 18, 66, 32, 0, 1, 108, 21, 2, 98, 121, 32, 0, 1, 108, 21, 2, 197, 155, 99, 105, 101, 32, 0, 1, 108, 21, 2, 197, 155, 109, 121, 32, 0, 1, 108, 97, 116, 21, 2, 18, 66, 32, 0, 1, 108, 98, 117, 21, 2, 18, 66, 32, 0, 1, 108, 107, 121, 21, 2, 18, 66, 32, 0, 1, 108, 111, 98, 21, 2, 18, 66, 32, 0, 1, 108, 111, 104, 21, 2, 18, 66, 32, 0, 1, 108, 112, 101, 21, 2, 18, 66, 32, 0, 1, 108, 117, 97, 21, 2, 18, 66, 32, 0, 1, 109, 97, 110, 21, 2, 18, 66, 32, 0, 1, 109, 97, 114, 21, 2, 18, 66, 32, 0, 1, 109, 101, 108, 21, 2, 18, 66, 32, 0, 1, 109, 101, 110, 21, 2, 18, 66, 32, 0, 1, 109, 101, 115, 21, 2, 18, 66, 32, 0, 1, 109, 105, 109, 2, 18, 66, 32, 0, 1, 109, 105, 110, 21, 2, 18, 66, 32, 0, 1, 109, 108, 97, 21, 2, 18, 66, 32, 0, 1, 109, 111, 107, 21, 2, 18, 66, 32, 0, 1, 109, 111, 110, 21, 2, 18, 66, 32, 0, 1, 109, 111, 114, 21, 2, 18, 66, 32, 0, 1, 109, 114, 101, 21, 2, 18, 66, 32, 0, 1, 109, 114, 111, 21, 2, 18, 66, 32, 0, 1, 109, 115, 106, 21, 2, 18, 66, 32, 0, 1, 109, 116, 121, 21, 2, 18, 66, 32, 0, 1, 110, 21, 2, 98, 121, 32, 0, 1, 110, 21, 2, 197, 155, 99, 105, 101, 32, 0, 1, 110, 97, 103, 21, 2, 18, 66, 32, 0, 1, 110, 97, 104, 21, 2, 18, 66, 32, 0, 1, 110, 97, 116, 21, 2, 18, 66, 32, 0, 1, 110, 97, 117, 21, 2, 18, 66, 32, 0, 1, 110, 101, 103, 21, 2, 18, 66, 32, 0, 1, 110, 104, 99, 21, 2, 18, 66, 32, 0, 1, 110, 105, 108, 21, 2, 18, 66, 32, 0, 1, 110, 111, 101, 21, 2, 18, 66, 32, 0, 1, 110, 111, 102, 21, 2, 18, 66, 32, 0, 1, 110, 111, 105, 21, 2, 18, 66, 32, 0, 1, 110, 111, 109, 21, 2, 18, 66, 32, 0, 1, 110, 111, 110, 21, 2, 18, 66, 32, 0, 1, 110, 111, 112, 21, 2, 18, 66, 32, 0, 1, 110, 111, 114, 21, 2, 18, 66, 32, 0, 1, 110, 111, 116, 2, 99, 101, 32, 0, 1, 110, 111, 116, 2, 107, 111, 32, 0, 1, 110, 111, 116, 2, 107, 196, 133, 32, 0, 1, 110, 111, 116, 2, 107, 196, 153, 32, 0, 1, 110, 111, 116, 97, 116, 2, 107, 97, 32, 0, 1, 110, 111, 116, 97, 116, 2, 107, 97, 99, 104, 32, 0, 1, 110, 111, 116, 97, 116, 2, 107, 105, 32, 0, 1, 110, 111, 116, 107, 101, 116, 2, 107, 97, 32, 0, 1, 110, 111, 116, 107, 101, 116, 2, 107, 97, 99, 104, 32, 0, 1, 110, 111, 116, 107, 101, 116, 2, 107, 105, 32, 0, 1, 110, 117, 109, 21, 2, 18, 66, 32, 0, 1, 111, 114, 101, 21, 2, 18, 66, 32, 0, 1, 112, 111, 114, 21, 2, 18, 66, 32, 0, 1, 112, 112, 105, 21, 2, 18, 66, 32, 0, 1, 119, 97, 108, 21, 2, 18, 66, 32, 0, 2, 197, 130, 98, 121, 32, 0, 2, 197, 130, 98, 121, 109, 32, 0, 2, 197, 130, 98, 121, 197, 155, 32, 0, 8, 109, 114, 101, 116, 2, 18, 66, 32, 0, 8, 109, 116, 121, 114, 2, 18, 66, 32, 0, 8, 110, 111, 116, 2, 107, 97, 32, 0, 8, 110, 111, 116, 2, 107, 97, 99, 104, 32, 0, 8, 110, 111, 116, 2, 107, 105, 32, 0, 8, 112, 101, 2, 18, 66, 0, 4, 97, 1, 17, 67, 21, 2, 197, 130, 121, 98, 121, 32, 3, 8, 38, 35, 0, 97, 1, 17, 67, 21, 2, 197, 130, 121, 98, 121, 197, 155, 99, 105, 101, 32, 0, 97, 1, 17, 67, 21, 2, 197, 130, 121, 98, 121, 197, 155, 109, 121, 32, 0, 4, 101, 1, 17, 67, 21, 2, 108, 105, 98, 121, 32, 3, 8, 38, 107, 0, 101, 1, 17, 67, 21, 2, 108, 105, 98, 121, 197, 155, 99, 105, 101, 32, 0, 101, 1, 17, 67, 21, 2, 108, 105, 98, 121, 197, 155, 109, 121, 32, 0, 8, 114, 100, 2, 118, 3, 35, 57, 0, 99, 8, 109, 2, 114, 111, 3, 35, 57, 49, 0, 109, 101, 8, 116, 3, 35, 57, 63, 0, 109, 101, 8, 116, 2, 114, 3, 35, 57, 63, 107, 0, 114, 101, 8, 102, 2, 102, 111, 3, 35, 57, 107, 51, 0, 4, 3, 37, 0, 8, 110, 105, 109, 111, 100, 2, 99, 101, 32, 12, 12, 0, 8, 110, 105, 109, 111, 100, 2, 107, 97, 32, 12, 12, 0, 8, 110, 105, 109, 111, 100, 2, 107, 97, 99, 104, 32, 12, 12, 0, 8, 110, 105, 109, 111, 100, 2, 107, 105, 32, 12, 12, 0, 8, 110, 105, 109, 111, 100, 2, 107, 111, 32, 12, 12, 0, 8, 110, 105, 109, 111, 100, 2, 107, 111, 109, 32, 12, 12, 0, 8, 110, 105, 109, 111, 100, 2, 107, 196, 133, 32, 12, 12, 0, 8, 110, 105, 109, 111, 100, 2, 107, 196, 153, 32, 12, 12, 0, 8, 110, 111, 114, 101, 119, 2, 99, 101, 32, 12, 12, 0, 8, 110, 111, 114, 101, 119, 2, 107, 97, 32, 12, 12, 0, 8, 110, 111, 114, 101, 119, 2, 107, 97, 99, 104, 32, 12, 12, 0, 8, 110, 111, 114, 101, 119, 2, 107, 105, 32, 12, 12, 0, 8, 110, 111, 114, 101, 119, 2, 107, 111, 32, 12, 12, 0, 8, 110, 111, 114, 101, 119, 2, 107, 111, 109, 32, 12, 12, 0, 8, 110, 111, 114, 101, 119, 2, 107, 196, 133, 32, 12, 12, 0, 8, 110, 111, 114, 101, 119, 2, 107, 196, 153, 32, 12, 12, 0, 4, 105, 1, 107, 97, 114, 2, 32, 3, 37, 57, 37, 0, 105, 1, 109, 188, 197, 2, 32, 0, 1, 17, 67, 2, 17, 65, 3, 38, 0, 8, 108, 107, 2, 101, 3, 38, 37, 57, 0, 101, 1, 17, 67, 2, 32, 3, 38, 108, 0, 4, 1, 17, 65, 2, 17, 65, 3, 57, 0, 2, 17, 65, 32, 12, 0, 7, 6, 106, 0, 3, 57, 0, 8, 2, 105, 109, 3, 73, 0, 101, 97, 2, 110, 115, 3, 73, 37, 0, 4, 97, 99, 107, 8, 2, 32, 3, 73, 107, 49, 0, 97, 99, 107, 8, 2, 115, 0, 97, 99, 107, 8, 2, 121, 0, 97, 99, 107, 121, 8, 2, 32, 3, 73, 107, 49, 37, 0, 97, 109, 101, 115, 8, 3, 73, 107, 57, 63, 87, 0, 97, 109, 101, 115, 105, 8, 2, 101, 32, 3, 73, 107, 57, 63, 95, 0, 101, 102, 102, 8, 3, 73, 107, 81, 0, 97, 122, 122, 3, 73, 107, 86, 0, 97, 122, 122, 2, 32, 3, 73, 107, 87, 0, 111, 104, 110, 8, 3, 73, 109, 50, 0, 111, 110, 97, 116, 104, 8, 3, 73, 109, 50, 35, 47, 0, 111, 104, 110, 105, 8, 2, 101, 3, 73, 109, 65, 38, 0, 97, 99, 113, 117, 101, 115, 8, 3, 88, 35, 49, 0, 8, 2, 105, 109, 101, 110, 3, 105, 0, 7, 6, 107, 0, 3, 49, 0, 108, 111, 119, 8, 2, 110, 3, 49, 55, 35, 58, 0, 197, 130, 2, 32, 3, 49, 58, 0, 7, 6, 108, 0, 3, 55, 0, 2, 32, 3, 55, 10, 0, 105, 8, 111, 112, 2, 17, 65, 3, 55, 37, 0, 105, 2, 17, 65, 3, 55, 57, 0, 7, 6, 109, 0, 3, 63, 0, 2, 32, 3, 63, 10, 0, 106, 8, 2, 114, 17, 65, 3, 63, 35, 57, 109, 0, 105, 8, 101, 105, 122, 2, 17, 65, 3, 63, 38, 0, 105, 1, 17, 65, 2, 17, 65, 3, 63, 57, 0, 99, 8, 2, 14, 129, 132, 130, 3, 63, 107, 49, 0, 7, 6, 110, 0, 3, 50, 0, 2, 32, 3, 50, 10, 0, 116, 111, 110, 1, 17, 65, 21, 2, 32, 14, 129, 128, 132, 3, 50, 47, 109, 50, 0, 103, 1, 97, 2, 101, 108, 3, 50, 73, 0, 4, 111, 102, 102, 2, 32, 14, 129, 128, 132, 3, 50, 109, 82, 0, 111, 102, 102, 2, 97, 32, 0, 111, 102, 102, 2, 97, 99, 104, 32, 0, 111, 102, 102, 2, 97, 109, 105, 32, 0, 111, 102, 102, 2, 101, 109, 32, 0, 111, 102, 102, 2, 105, 101, 32, 0, 111, 102, 102, 2, 111, 109, 32, 0, 111, 102, 102, 2, 111, 119, 105, 32, 0, 111, 102, 102, 2, 117, 32, 0, 4, 2, 99, 105, 3, 65, 0, 2, 100, 122, 105, 0, 2, 100, 197, 186, 0, 2, 105, 0, 2, 196, 135, 0, 4, 105, 2, 17, 65, 3, 65, 38, 0, 121, 2, 39, 101, 103, 111, 32, 0, 121, 2, 39, 101, 109, 117, 32, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 103, 116, 111, 110, 1, 17, 65, 21, 2, 32, 14, 129, 128, 133, 3, 66, 79, 47, 109, 50, 0, 7, 6, 111, 0, 117, 116, 8, 103, 97, 114, 2, 32, 3, 6, 40, 0, 119, 8, 100, 2, 110, 3, 35, 58, 0, 117, 116, 115, 105, 100, 8, 3, 35, 58, 115, 35, 57, 70, 0, 105, 8, 112, 2, 114, 111, 116, 17, 65, 3, 40, 58, 35, 0, 101, 116, 104, 3, 107, 47, 0, 3, 109, 0, 2, 32, 17, 65, 3, 109, 12, 10, 0, 116, 101, 98, 111, 111, 8, 110, 2, 17, 67, 3, 109, 58, 47, 69, 40, 0, 7, 6, 112, 0, 3, 48, 0, 4, 197, 130, 8, 2, 99, 3, 48, 40, 58, 49, 109, 82, 50, 37, 0, 197, 130, 8, 2, 107, 0, 4, 105, 8, 111, 107, 2, 17, 65, 3, 48, 57, 0, 105, 8, 111, 107, 111, 116, 111, 102, 2, 17, 65, 0, 4, 112, 197, 130, 8, 2, 99, 3, 48, 109, 47, 48, 40, 58, 49, 109, 82, 50, 37, 0, 112, 197, 130, 8, 2, 107, 0, 7, 6, 113, 0, 3, 49, 0, 117, 2, 17, 65, 3, 49, 82, 0, 7, 6, 114, 0, 4, 3, 51, 0, 1, 17, 65, 2, 122, 197, 130, 0, 1, 25, 2, 17, 65, 0, 1, 32, 17, 65, 2, 17, 65, 0, 1, 97, 109, 2, 122, 108, 105, 110, 0, 1, 97, 109, 2, 122, 110, 0, 1, 97, 109, 100, 111, 2, 122, 97, 0, 2, 122, 105, 0, 8, 97, 109, 97, 122, 2, 122, 97, 0, 8, 97, 109, 122, 2, 122, 97, 0, 8, 111, 98, 2, 122, 111, 106, 0, 114, 1, 17, 65, 2, 17, 65, 0, 121, 39, 2, 101, 0, 105, 2, 17, 65, 3, 51, 57, 0, 4, 122, 8, 105, 109, 2, 97, 32, 12, 12, 12, 3, 51, 86, 0, 122, 8, 105, 109, 2, 97, 99, 104, 32, 12, 12, 12, 0, 122, 8, 105, 109, 2, 97, 109, 105, 32, 12, 12, 12, 0, 122, 8, 105, 109, 2, 111, 32, 12, 12, 12, 0, 122, 8, 105, 109, 2, 111, 119, 105, 101, 32, 12, 12, 12, 0, 122, 8, 105, 109, 2, 121, 32, 12, 12, 12, 0, 122, 8, 105, 109, 2, 195, 179, 119, 32, 12, 12, 12, 0, 122, 8, 105, 109, 2, 196, 133, 32, 12, 12, 12, 0, 122, 8, 105, 109, 2, 196, 153, 32, 12, 12, 12, 0, 122, 8, 117, 109, 2, 97, 32, 12, 12, 12, 0, 122, 8, 117, 109, 2, 97, 99, 104, 32, 12, 12, 12, 0, 122, 8, 117, 109, 2, 97, 109, 105, 32, 12, 12, 12, 0, 122, 8, 117, 109, 2, 97, 115, 105, 99, 104, 108, 0, 122, 8, 117, 109, 2, 111, 32, 12, 12, 12, 0, 122, 8, 117, 109, 2, 111, 119, 105, 101, 32, 12, 12, 12, 0, 122, 8, 117, 109, 2, 121, 32, 12, 12, 12, 0, 122, 8, 117, 109, 2, 195, 179, 119, 32, 12, 12, 12, 0, 122, 8, 117, 109, 2, 196, 133, 32, 12, 12, 12, 0, 122, 8, 117, 109, 2, 196, 153, 32, 12, 12, 12, 0, 4, 122, 2, 97, 110, 100, 3, 51, 115, 0, 122, 2, 105, 110, 105, 32, 0, 122, 2, 105, 110, 105, 99, 104, 32, 0, 122, 2, 105, 110, 105, 101, 103, 111, 32, 0, 122, 2, 105, 110, 105, 101, 109, 117, 32, 0, 122, 2, 105, 110, 105, 109, 32, 0, 122, 2, 105, 110, 105, 109, 105, 32, 0, 122, 2, 111, 110, 105, 32, 0, 122, 2, 111, 110, 105, 99, 104, 32, 0, 122, 2, 111, 110, 105, 101, 103, 111, 32, 0, 122, 2, 111, 110, 105, 101, 109, 117, 32, 0, 122, 2, 111, 110, 105, 109, 32, 0, 122, 2, 111, 110, 105, 109, 105, 32, 0, 122, 3, 88, 0, 4, 122, 1, 99, 2, 17, 65, 3, 89, 0, 122, 1, 102, 2, 17, 65, 0, 122, 1, 104, 0, 122, 1, 107, 0, 122, 1, 112, 0, 122, 1, 115, 2, 17, 65, 0, 122, 1, 116, 0, 122, 1, 122, 99, 2, 17, 65, 0, 122, 1, 122, 115, 2, 17, 65, 0, 122, 1, 135, 196, 2, 17, 65, 0, 122, 1, 155, 197, 2, 17, 65, 0, 122, 2, 32, 0, 7, 6, 115, 0, 4, 105, 1, 115, 2, 109, 97, 32, 3, 8, 37, 0, 105, 1, 115, 2, 109, 101, 109, 32, 0, 105, 1, 115, 2, 109, 105, 101, 32, 0, 105, 1, 115, 2, 109, 111, 32, 0, 4, 111, 110, 8, 101, 99, 108, 97, 115, 2, 32, 12, 12, 3, 8, 87, 109, 50, 0, 111, 110, 8, 105, 116, 97, 112, 2, 32, 12, 12, 0, 8, 97, 117, 113, 2, 105, 3, 86, 0, 3, 87, 0, 4, 105, 1, 107, 101, 108, 112, 2, 32, 3, 87, 37, 0, 105, 2, 98, 0, 105, 2, 99, 0, 105, 2, 100, 0, 105, 2, 102, 0, 105, 2, 103, 0, 105, 2, 104, 0, 105, 2, 108, 105, 107, 111, 0, 105, 2, 108, 108, 0, 105, 2, 108, 111, 115, 0, 105, 2, 108, 118, 0, 105, 2, 109, 0, 105, 2, 110, 103, 0, 105, 2, 110, 117, 115, 0, 105, 2, 113, 0, 105, 2, 114, 0, 105, 2, 116, 0, 105, 2, 118, 0, 105, 2, 120, 0, 105, 8, 107, 97, 109, 2, 32, 0, 116, 101, 105, 110, 1, 121, 3, 87, 47, 107, 37, 50, 0, 99, 104, 101, 114, 122, 3, 87, 49, 107, 51, 115, 0, 4, 105, 8, 97, 116, 115, 97, 110, 97, 2, 97, 32, 3, 87, 57, 0, 105, 8, 97, 116, 115, 97, 110, 97, 2, 105, 32, 0, 105, 8, 97, 116, 115, 97, 110, 97, 2, 111, 32, 0, 105, 8, 97, 116, 115, 97, 110, 97, 2, 196, 133, 32, 0, 105, 8, 97, 116, 115, 97, 110, 97, 2, 196, 153, 32, 0, 4, 99, 104, 1, 97, 112, 2, 97, 3, 87, 99, 0, 99, 104, 1, 101, 2, 97, 116, 111, 0, 99, 104, 2, 97, 98, 17, 65, 32, 0, 99, 104, 2, 97, 98, 32, 0, 99, 104, 2, 97, 98, 97, 109, 105, 32, 0, 99, 104, 2, 97, 98, 101, 109, 32, 0, 99, 104, 2, 97, 98, 105, 101, 32, 0, 99, 104, 2, 97, 98, 111, 109, 0, 99, 104, 2, 97, 98, 111, 115, 122, 0, 99, 104, 2, 97, 98, 111, 119, 17, 65, 0, 99, 104, 2, 97, 98, 195, 179, 0, 99, 104, 2, 97, 100, 122, 17, 65, 0, 99, 104, 2, 97, 100, 122, 107, 0, 99, 104, 2, 97, 109, 32, 0, 99, 104, 2, 97, 109, 105, 0, 99, 104, 2, 97, 109, 105, 17, 65, 0, 99, 104, 2, 97, 114, 97, 107, 116, 0, 99, 104, 2, 101, 100, 17, 65, 0, 99, 104, 2, 101, 100, 32, 0, 99, 104, 2, 101, 109, 97, 116, 0, 99, 104, 2, 105, 122, 109, 17, 65, 0, 99, 104, 2, 105, 122, 109, 32, 0, 99, 104, 2, 105, 122, 111, 0, 99, 104, 2, 108, 97, 108, 105, 0, 99, 104, 2, 108, 97, 110, 17, 65, 0, 99, 104, 2, 108, 97, 196, 135, 0, 99, 104, 2, 108, 97, 197, 130, 0, 99, 104, 2, 108, 101, 108, 105, 0, 99, 104, 2, 108, 117, 100, 110, 17, 65, 0, 99, 104, 2, 110, 105, 101, 32, 0, 99, 104, 2, 110, 105, 196, 153, 0, 99, 104, 2, 110, 196, 133, 0, 99, 104, 2, 110, 196, 153, 0, 99, 104, 2, 111, 100, 97, 99, 104, 32, 0, 99, 104, 2, 111, 100, 97, 109, 105, 32, 0, 99, 104, 2, 111, 100, 101, 107, 32, 0, 99, 104, 2, 111, 100, 107, 97, 0, 99, 104, 2, 111, 100, 107, 105, 0, 99, 104, 2, 111, 100, 107, 105, 101, 109, 32, 0, 99, 104, 2, 111, 100, 107, 111, 119, 0, 99, 104, 2, 111, 100, 107, 111, 119, 105, 32, 0, 99, 104, 2, 111, 100, 107, 117, 32, 0, 99, 104, 2, 111, 100, 107, 195, 179, 0, 99, 104, 2, 111, 100, 111, 119, 0, 99, 104, 2, 111, 100, 121, 32, 0, 99, 104, 2, 111, 100, 122, 105, 0, 99, 104, 2, 111, 100, 122, 196, 133, 0, 99, 104, 2, 111, 100, 122, 196, 153, 0, 99, 104, 2, 111, 100, 195, 179, 0, 99, 104, 2, 111, 114, 111, 119, 97, 0, 99, 104, 2, 111, 114, 122, 101, 0, 99, 104, 2, 111, 119, 17, 65, 0, 99, 104, 2, 111, 119, 97, 0, 99, 104, 2, 114, 111, 110, 17, 65, 0, 99, 104, 2, 114, 111, 110, 32, 0, 99, 104, 2, 114, 117, 112, 32, 0, 99, 104, 2, 114, 117, 112, 97, 108, 105, 0, 99, 104, 2, 114, 117, 112, 97, 110, 17, 65, 0, 99, 104, 2, 114, 117, 112, 97, 196, 135, 32, 0, 99, 104, 2, 114, 117, 112, 97, 197, 130, 0, 99, 104, 2, 114, 117, 112, 105, 17, 65, 0, 99, 104, 2, 114, 121, 112, 17, 65, 0, 99, 104, 2, 114, 121, 112, 108, 0, 99, 104, 2, 114, 121, 112, 197, 130, 0, 99, 104, 2, 114, 122, 17, 65, 0, 99, 104, 2, 117, 100, 110, 0, 99, 104, 2, 119, 121, 99, 105, 0, 99, 104, 2, 119, 121, 116, 17, 65, 0, 99, 104, 2, 121, 108, 17, 65, 0, 99, 104, 2, 121, 197, 130, 0, 99, 104, 2, 195, 179, 0, 99, 104, 2, 196, 133, 0, 99, 104, 2, 196, 153, 0, 99, 104, 2, 197, 130, 0, 99, 104, 8, 2, 101, 116, 121, 0, 99, 104, 8, 2, 101, 116, 121, 110, 0, 99, 104, 8, 2, 108, 101, 98, 32, 0, 99, 104, 8, 2, 108, 101, 98, 105, 0, 99, 104, 8, 2, 121, 108, 32, 0, 99, 104, 8, 119, 2, 111, 100, 0, 101, 110, 1, 21, 2, 32, 14, 129, 128, 131, 3, 87, 107, 50, 0, 111, 110, 1, 21, 2, 32, 14, 129, 128, 131, 3, 87, 109, 50, 0, 4, 99, 104, 3, 89, 0, 107, 106, 2, 17, 65, 0, 122, 0, 4, 116, 101, 105, 110, 3, 89, 47, 35, 57, 50, 0, 116, 101, 105, 110, 2, 32, 14, 129, 128, 133, 0, 99, 104, 119, 97, 114, 122, 3, 89, 82, 35, 51, 115, 0, 99, 104, 111, 101, 3, 89, 107, 0, 4, 101, 97, 8, 2, 110, 32, 3, 89, 109, 0, 101, 97, 8, 2, 110, 97, 32, 0, 101, 97, 8, 2, 110, 101, 109, 32, 0, 101, 97, 8, 2, 110, 105, 101, 32, 0, 101, 97, 8, 2, 110, 111, 119, 105, 32, 0, 101, 97, 8, 2, 110, 117, 32, 0, 4, 2, 105, 3, 95, 0, 105, 2, 17, 65, 0, 4, 105, 1, 117, 100, 2, 103, 114, 3, 95, 37, 0, 105, 2, 98, 114, 122, 0, 105, 2, 99, 17, 65, 0, 105, 2, 99, 104, 0, 105, 2, 99, 122, 0, 105, 2, 100, 108, 17, 65, 0, 105, 2, 100, 108, 32, 0, 105, 2, 100, 197, 130, 0, 105, 8, 2, 116, 17, 65, 0, 105, 8, 2, 116, 32, 0, 105, 8, 2, 116, 107, 0, 7, 6, 116, 0, 4, 3, 47, 0, 2, 114, 122, 0, 2, 115, 0, 111, 119, 110, 2, 32, 14, 129, 128, 132, 3, 47, 35, 58, 50, 0, 105, 2, 17, 65, 3, 47, 57, 0, 116, 104, 101, 119, 3, 87, 57, 40, 0, 2, 105, 3, 113, 0, 7, 6, 117, 0, 4, 1, 21, 2, 197, 130, 98, 121, 32, 3, 8, 40, 0, 1, 21, 2, 197, 130, 98, 121, 109, 32, 0, 1, 21, 2, 197, 130, 98, 121, 197, 155, 32, 0, 110, 99, 104, 8, 108, 3, 35, 50, 74, 0, 4, 3, 40, 0, 1, 97, 110, 2, 99, 122, 0, 1, 97, 110, 2, 107, 0, 1, 97, 114, 97, 112, 0, 1, 97, 116, 101, 109, 0, 1, 101, 17, 67, 2, 109, 32, 0, 1, 101, 17, 67, 2, 115, 0, 8, 97, 122, 0, 8, 101, 105, 110, 0, 8, 101, 122, 114, 112, 0, 2, 32, 17, 65, 3, 40, 10, 0, 101, 116, 111, 111, 116, 104, 8, 108, 98, 3, 40, 47, 40, 81, 0, 115, 105, 99, 8, 109, 2, 97, 108, 32, 3, 57, 6, 40, 86, 37, 49, 0, 115, 105, 99, 8, 109, 2, 97, 108, 3, 57, 40, 86, 37, 49, 0, 4, 1, 97, 3, 58, 0, 1, 101, 0, 8, 97, 122, 2, 116, 111, 0, 105, 99, 107, 8, 98, 3, 58, 37, 49, 0, 7, 6, 118, 0, 105, 99, 101, 8, 2, 21, 14, 129, 132, 132, 3, 58, 37, 115, 107, 0, 4, 1, 102, 2, 17, 65, 3, 81, 0, 1, 104, 2, 17, 65, 0, 1, 107, 2, 17, 65, 0, 1, 112, 2, 17, 65, 0, 1, 115, 2, 17, 65, 0, 1, 116, 2, 17, 65, 0, 2, 111, 108, 107, 115, 0, 3, 82, 0, 105, 108, 108, 101, 2, 32, 14, 129, 128, 133, 3, 82, 37, 55, 0, 7, 6, 119, 0, 2, 115, 107, 3, 10, 82, 0, 4, 114, 105, 103, 104, 3, 51, 35, 57, 0, 114, 105, 103, 104, 1, 17, 67, 0, 8, 2, 32, 3, 58, 0, 101, 101, 2, 107, 3, 58, 37, 0, 4, 8, 2, 32, 102, 3, 58, 107, 0, 8, 2, 32, 109, 110, 0, 97, 115, 104, 105, 8, 3, 58, 109, 89, 37, 0, 105, 110, 100, 111, 119, 8, 3, 58, 110, 50, 70, 109, 58, 0, 4, 1, 99, 2, 17, 65, 3, 81, 0, 1, 102, 2, 17, 65, 0, 1, 104, 2, 17, 65, 0, 1, 107, 2, 17, 65, 0, 1, 112, 2, 17, 65, 0, 1, 115, 2, 17, 65, 0, 1, 116, 2, 17, 65, 0, 1, 122, 99, 2, 17, 65, 0, 1, 122, 115, 2, 17, 65, 0, 1, 135, 196, 2, 17, 65, 0, 1, 155, 197, 2, 17, 65, 0, 2, 32, 0, 8, 2, 32, 99, 0, 8, 2, 32, 104, 0, 8, 2, 32, 107, 0, 8, 2, 32, 112, 0, 8, 2, 32, 115, 0, 8, 2, 32, 116, 0, 3, 82, 0, 105, 99, 101, 8, 2, 21, 14, 129, 132, 132, 3, 82, 37, 115, 107, 0, 115, 122, 1, 114, 101, 105, 2, 17, 65, 3, 89, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 4, 39, 1, 114, 2, 101, 103, 111, 32, 3, 0, 39, 1, 114, 2, 101, 109, 117, 32, 3, 0, 4, 1, 21, 2, 197, 130, 98, 121, 32, 3, 8, 110, 0, 1, 21, 2, 197, 130, 98, 121, 109, 32, 0, 1, 21, 2, 197, 130, 98, 121, 197, 155, 32, 0, 1, 98, 101, 2, 197, 155, 99, 105, 101, 32, 0, 1, 98, 101, 2, 197, 155, 109, 121, 32, 0, 1, 100, 108, 97, 21, 2, 18, 66, 32, 0, 1, 100, 111, 108, 21, 2, 18, 66, 32, 0, 1, 100, 111, 116, 21, 2, 18, 66, 32, 0, 1, 100, 114, 111, 21, 2, 18, 66, 32, 0, 1, 114, 101, 109, 21, 2, 18, 66, 32, 0, 1, 114, 101, 116, 21, 2, 18, 66, 32, 0, 1, 114, 111, 102, 21, 2, 18, 66, 32, 0, 1, 114, 111, 103, 21, 2, 18, 66, 32, 0, 1, 114, 111, 116, 21, 2, 18, 66, 32, 0, 1, 114, 116, 101, 21, 2, 18, 66, 32, 0, 1, 114, 116, 107, 21, 2, 18, 66, 32, 0, 1, 114, 116, 112, 21, 2, 18, 66, 32, 0, 1, 115, 97, 108, 21, 2, 18, 66, 32, 0, 1, 115, 107, 101, 21, 2, 18, 66, 32, 0, 1, 116, 97, 98, 21, 2, 18, 66, 32, 0, 1, 116, 97, 105, 21, 2, 18, 66, 32, 0, 1, 116, 97, 109, 21, 2, 18, 66, 32, 0, 1, 116, 97, 114, 21, 2, 18, 66, 32, 0, 1, 116, 97, 116, 21, 2, 18, 66, 32, 0, 1, 116, 101, 97, 21, 2, 18, 66, 32, 0, 1, 116, 101, 99, 21, 2, 18, 66, 32, 0, 1, 116, 101, 100, 21, 2, 18, 66, 32, 0, 1, 116, 101, 103, 21, 2, 18, 66, 32, 0, 1, 116, 101, 104, 21, 2, 18, 66, 32, 0, 1, 116, 101, 108, 21, 2, 18, 66, 32, 0, 1, 116, 101, 109, 21, 2, 18, 66, 32, 0, 1, 116, 101, 110, 21, 2, 18, 66, 32, 0, 1, 116, 101, 111, 21, 2, 18, 66, 32, 0, 1, 116, 101, 114, 21, 2, 18, 66, 32, 0, 1, 116, 101, 116, 21, 2, 18, 66, 32, 0, 1, 116, 105, 108, 21, 2, 18, 66, 32, 0, 1, 116, 107, 97, 21, 2, 18, 66, 32, 0, 1, 116, 107, 101, 21, 2, 18, 66, 32, 0, 1, 116, 107, 114, 21, 2, 18, 66, 32, 0, 1, 116, 108, 97, 21, 2, 18, 66, 32, 0, 1, 116, 110, 97, 21, 2, 18, 66, 32, 0, 1, 116, 110, 101, 21, 2, 18, 66, 32, 0, 1, 116, 111, 98, 21, 2, 18, 66, 32, 0, 1, 116, 111, 105, 21, 2, 18, 66, 32, 0, 1, 116, 111, 110, 21, 2, 18, 66, 32, 0, 1, 116, 111, 114, 21, 2, 18, 66, 32, 0, 1, 116, 111, 122, 21, 2, 18, 66, 32, 0, 1, 116, 112, 101, 21, 2, 18, 66, 32, 0, 1, 116, 112, 105, 21, 2, 18, 66, 32, 0, 1, 116, 112, 111, 2, 18, 66, 32, 0, 1, 116, 115, 97, 21, 2, 18, 66, 32, 0, 1, 116, 115, 101, 21, 2, 18, 66, 32, 0, 1, 116, 115, 105, 21, 2, 18, 66, 32, 0, 1, 116, 115, 111, 21, 2, 18, 66, 32, 0, 1, 116, 115, 117, 21, 2, 18, 66, 32, 0, 1, 116, 115, 121, 21, 2, 18, 66, 32, 0, 1, 116, 117, 97, 21, 2, 18, 66, 32, 0, 1, 116, 117, 101, 21, 2, 18, 66, 32, 0, 1, 116, 121, 114, 21, 2, 18, 66, 32, 0, 1, 122, 101, 110, 21, 2, 18, 66, 32, 0, 1, 122, 105, 102, 2, 18, 66, 32, 0, 1, 130, 197, 21, 2, 98, 121, 32, 0, 1, 130, 197, 21, 2, 98, 121, 197, 155, 99, 105, 101, 32, 0, 1, 130, 197, 21, 2, 98, 121, 197, 155, 109, 121, 32, 0, 8, 98, 97, 2, 197, 155, 99, 105, 101, 32, 0, 8, 98, 97, 2, 197, 155, 109, 121, 32, 0, 8, 115, 97, 108, 107, 2, 18, 66, 32, 0, 8, 116, 97, 116, 115, 2, 18, 66, 32, 0, 8, 116, 101, 2, 18, 66, 32, 0, 8, 116, 107, 97, 114, 112, 2, 18, 66, 32, 0, 8, 116, 115, 105, 109, 2, 18, 66, 0, 8, 116, 121, 114, 107, 2, 18, 66, 32, 0, 4, 39, 1, 17, 67, 2, 101, 103, 111, 32, 3, 38, 0, 39, 1, 17, 67, 2, 101, 109, 117, 32, 0, 4, 1, 17, 65, 2, 17, 65, 3, 57, 0, 1, 17, 65, 2, 32, 0, 8, 2, 17, 65, 0, 4, 3, 110, 0, 8, 114, 111, 116, 115, 105, 104, 2, 107, 97, 12, 12, 0, 8, 114, 111, 116, 115, 105, 104, 2, 107, 111, 109, 12, 12, 0, 8, 114, 116, 101, 116, 2, 107, 97, 12, 12, 0, 8, 114, 116, 101, 116, 2, 107, 111, 109, 12, 12, 0, 8, 116, 97, 112, 2, 12, 12, 0, 2, 32, 17, 65, 3, 110, 10, 0, 7, 6, 122, 0, 4, 3, 86, 0, 8, 2, 32, 0, 8, 111, 114, 2, 105, 17, 67, 0, 4, 105, 8, 2, 17, 67, 3, 86, 10, 37, 0, 105, 8, 101, 105, 110, 2, 17, 67, 0, 122, 8, 2, 97, 32, 3, 86, 10, 86, 0, 4, 105, 1, 111, 109, 2, 108, 108, 3, 86, 37, 0, 105, 2, 17, 67, 0, 8, 2, 32, 109, 110, 3, 86, 107, 0, 4, 2, 32, 3, 87, 0, 8, 2, 32, 99, 0, 8, 2, 32, 102, 0, 8, 2, 32, 104, 0, 8, 2, 32, 107, 0, 8, 2, 32, 112, 0, 8, 2, 32, 115, 0, 8, 2, 32, 116, 0, 4, 2, 105, 3, 94, 0, 105, 2, 17, 65, 0, 4, 105, 2, 109, 12, 3, 94, 37, 0, 105, 8, 2, 112, 0, 4, 2, 105, 110, 105, 32, 3, 115, 0, 2, 105, 110, 105, 99, 104, 32, 0, 2, 105, 110, 105, 101, 103, 111, 32, 0, 2, 105, 110, 105, 101, 109, 117, 32, 0, 2, 105, 110, 105, 109, 32, 0, 2, 105, 110, 105, 109, 105, 32, 0, 122, 2, 97, 32, 0, 122, 2, 97, 99, 104, 32, 0, 122, 2, 97, 109, 105, 32, 0, 122, 2, 97, 110, 105, 32, 0, 122, 2, 97, 110, 105, 99, 104, 32, 0, 122, 2, 97, 110, 105, 101, 103, 111, 32, 0, 122, 2, 97, 110, 105, 101, 109, 117, 32, 0, 122, 2, 97, 110, 105, 109, 32, 0, 122, 2, 97, 110, 105, 109, 105, 32, 0, 122, 2, 105, 110, 105, 32, 0, 122, 2, 105, 110, 105, 99, 104, 32, 0, 122, 2, 105, 110, 105, 101, 103, 111, 32, 0, 122, 2, 105, 110, 105, 101, 109, 117, 32, 0, 122, 2, 105, 110, 105, 109, 32, 0, 122, 2, 105, 110, 105, 109, 105, 32, 0, 122, 2, 111, 32, 0, 122, 2, 111, 110, 105, 32, 0, 122, 2, 111, 110, 105, 99, 104, 32, 0, 122, 2, 111, 110, 105, 101, 103, 111, 32, 0, 122, 2, 111, 110, 105, 101, 109, 117, 32, 0, 122, 2, 111, 110, 105, 109, 32, 0, 122, 2, 111, 110, 105, 109, 105, 32, 0, 122, 2, 121, 32, 0, 122, 2, 195, 179, 119, 32, 0, 122, 2, 196, 153, 32, 0, 122, 8, 17, 65, 109, 2, 17, 65, 0, 122, 8, 105, 112, 0, 117, 114, 105, 8, 2, 99, 104, 3, 115, 40, 51, 110, 0, 7, 6, 126, 0, 3, 0, 7, 6, 0, 39, 97, 2, 32, 14, 128, 128, 130, 3, 35, 0, 39, 117, 2, 32, 14, 128, 128, 130, 3, 40, 0, 36, 3, 70, 109, 55, 35, 51, 0, 39, 101, 109, 2, 32, 14, 128, 128, 131, 3, 107, 63, 0, 39, 101, 109, 117, 2, 32, 14, 128, 128, 132, 3, 107, 63, 40, 0, 39, 101, 103, 111, 2, 32, 14, 128, 128, 132, 3, 107, 79, 109, 0, 39, 111, 119, 105, 2, 32, 14, 128, 128, 132, 3, 109, 82, 37, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts46 = FileInMemory_createWithData (39432, reinterpret_cast (&espeakdata_dicts46_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/pl_dict", L"pl"); Collection_addItem (me.peek(), espeakdata_dicts46.transfer()); static unsigned char espeakdata_dicts47_data[2570] = { 0, 4, 0, 0, 12, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 5, 95, 48, 1, 14, 4, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 95, 51, 88, 87, 6, 37, 0, 0, 10, 3, 95, 48, 67, 87, 6, 107, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 55, 88, 105, 6, 107, 81, 47, 107, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 49, 88, 70, 6, 107, 105, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 50, 88, 69, 6, 37, 87, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 52, 88, 74, 6, 106, 105, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 53, 88, 48, 6, 37, 50, 73, 107, 105, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 54, 88, 89, 6, 107, 87, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 88, 105, 6, 107, 89, 47, 107, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 57, 88, 50, 107, 82, 6, 107, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 2, 95, 51, 87, 6, 106, 12, 105, 0, 0, 9, 2, 95, 50, 70, 6, 40, 12, 0, 0, 9, 2, 95, 49, 57, 6, 107, 49, 0, 0, 11, 2, 95, 48, 87, 106, 6, 81, 106, 34, 0, 0, 10, 2, 95, 55, 105, 6, 107, 81, 47, 0, 0, 9, 2, 95, 54, 89, 106, 6, 89, 0, 0, 10, 2, 95, 53, 48, 107, 6, 50, 73, 0, 0, 10, 2, 95, 52, 74, 6, 107, 105, 34, 0, 0, 0, 0, 8, 2, 95, 57, 50, 6, 39, 0, 0, 10, 2, 95, 56, 105, 6, 107, 89, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 2, 217, 135, 105, 6, 106, 12, 70, 39, 74, 107, 89, 63, 0, 0, 9, 2, 217, 134, 50, 6, 40, 50, 0, 0, 9, 2, 217, 133, 63, 6, 37, 63, 0, 0, 9, 2, 217, 132, 55, 6, 107, 63, 0, 0, 0, 9, 2, 217, 130, 51, 6, 107, 81, 0, 0, 9, 2, 217, 129, 81, 6, 106, 12, 0, 0, 0, 0, 9, 2, 218, 134, 74, 6, 106, 12, 0, 0, 0, 0, 0, 0, 0, 10, 2, 217, 136, 58, 6, 39, 12, 58, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 2, 216, 167, 107, 55, 6, 106, 81, 0, 0, 0, 0, 9, 2, 219, 140, 57, 6, 107, 12, 0, 0, 0, 0, 12, 2, 216, 161, 105, 107, 63, 86, 6, 106, 12, 0, 0, 0, 9, 2, 216, 175, 70, 6, 107, 55, 0, 0, 9, 2, 216, 174, 104, 6, 106, 12, 0, 0, 9, 2, 216, 173, 105, 6, 106, 12, 0, 0, 9, 2, 216, 172, 73, 6, 37, 63, 0, 0, 9, 2, 216, 171, 87, 6, 106, 12, 0, 0, 9, 2, 216, 170, 47, 6, 106, 12, 0, 0, 0, 9, 2, 216, 168, 69, 6, 106, 12, 0, 0, 9, 2, 216, 183, 47, 6, 107, 12, 0, 0, 9, 2, 216, 182, 86, 6, 107, 70, 0, 0, 9, 2, 216, 181, 87, 6, 107, 70, 0, 0, 9, 2, 216, 180, 89, 6, 37, 50, 0, 0, 9, 2, 216, 179, 87, 6, 37, 50, 0, 0, 9, 2, 216, 178, 86, 6, 106, 12, 0, 0, 9, 2, 216, 177, 34, 6, 106, 12, 0, 0, 9, 2, 216, 176, 86, 6, 107, 55, 0, 0, 9, 2, 218, 175, 79, 6, 107, 81, 0, 0, 0, 0, 0, 0, 9, 2, 216, 186, 51, 6, 108, 50, 0, 0, 9, 2, 218, 169, 49, 6, 107, 81, 0, 8, 2, 216, 185, 6, 108, 50, 0, 0, 9, 2, 216, 184, 86, 6, 107, 12, 0, 0, 0, 9, 2, 217, 190, 48, 6, 106, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 96, 6, 0, 0, 48, 0, 0, 0, 97, 6, 0, 0, 49, 0, 0, 0, 98, 6, 0, 0, 50, 0, 0, 0, 99, 6, 0, 0, 51, 0, 0, 0, 100, 6, 0, 0, 52, 0, 0, 0, 101, 6, 0, 0, 53, 0, 0, 0, 102, 6, 0, 0, 54, 0, 0, 0, 103, 6, 0, 0, 55, 0, 0, 0, 104, 6, 0, 0, 56, 0, 0, 0, 105, 6, 0, 0, 57, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 217, 142, 0, 217, 144, 0, 217, 143, 0, 217, 139, 0, 217, 141, 0, 217, 136, 0, 216, 167, 0, 217, 135, 0, 219, 140, 0, 216, 169, 0, 217, 138, 0, 7, 6, 18, 67, 217, 142, 0, 217, 144, 0, 217, 143, 0, 7, 6, 18, 68, 216, 167, 0, 216, 168, 0, 217, 190, 0, 216, 170, 0, 216, 171, 0, 216, 172, 0, 218, 134, 0, 216, 173, 0, 216, 174, 0, 216, 175, 0, 216, 176, 0, 216, 177, 0, 216, 178, 0, 218, 152, 0, 216, 179, 0, 216, 180, 0, 216, 181, 0, 216, 182, 0, 216, 183, 0, 216, 184, 0, 216, 185, 0, 216, 186, 0, 217, 129, 0, 217, 130, 0, 218, 169, 0, 218, 175, 0, 217, 132, 0, 217, 133, 0, 217, 134, 0, 217, 136, 0, 217, 135, 0, 219, 140, 0, 7, 6, 1, 34, 0, 2, 18, 66, 3, 0, 3, 13, 0, 7, 6, 1, 35, 0, 3, 107, 0, 7, 6, 1, 40, 0, 8, 2, 18, 66, 3, 0, 217, 141, 3, 106, 50, 0, 4, 3, 107, 0, 2, 32, 0, 217, 139, 3, 107, 50, 0, 7, 6, 1, 41, 0, 4, 1, 18, 68, 2, 18, 68, 3, 69, 0, 2, 18, 66, 0, 2, 32, 0, 3, 69, 107, 0, 7, 6, 1, 42, 0, 2, 32, 3, 13, 0, 2, 18, 66, 3, 105, 0, 3, 105, 107, 0, 7, 6, 1, 43, 0, 4, 2, 18, 66, 3, 47, 0, 2, 32, 0, 3, 47, 107, 0, 7, 6, 1, 44, 0, 4, 2, 18, 66, 3, 87, 0, 2, 32, 0, 3, 87, 107, 0, 7, 6, 1, 45, 0, 4, 2, 18, 66, 3, 73, 0, 2, 32, 0, 3, 73, 107, 0, 7, 6, 1, 46, 0, 4, 2, 18, 66, 3, 105, 0, 2, 32, 0, 3, 105, 107, 0, 7, 6, 1, 47, 0, 4, 2, 18, 66, 3, 104, 0, 2, 32, 0, 3, 104, 107, 0, 7, 6, 1, 48, 0, 4, 2, 18, 66, 3, 70, 0, 2, 32, 0, 3, 70, 107, 0, 7, 6, 1, 49, 0, 4, 2, 18, 66, 3, 86, 0, 2, 32, 0, 3, 86, 107, 0, 7, 6, 1, 50, 0, 4, 2, 18, 66, 3, 51, 0, 2, 32, 0, 3, 51, 107, 0, 7, 6, 1, 51, 0, 4, 2, 18, 66, 3, 86, 0, 2, 32, 0, 3, 86, 107, 0, 7, 6, 1, 52, 0, 4, 1, 18, 67, 2, 18, 68, 3, 87, 0, 1, 18, 68, 2, 18, 68, 0, 2, 18, 66, 0, 2, 32, 0, 3, 87, 107, 0, 7, 6, 1, 53, 0, 4, 2, 18, 66, 3, 89, 0, 2, 32, 0, 3, 89, 107, 0, 7, 6, 1, 54, 0, 4, 2, 18, 66, 3, 87, 0, 2, 32, 0, 3, 87, 107, 0, 7, 6, 1, 55, 0, 4, 2, 18, 66, 3, 86, 0, 2, 32, 0, 3, 86, 107, 0, 7, 6, 1, 56, 0, 4, 2, 18, 66, 3, 47, 0, 2, 32, 0, 3, 47, 107, 0, 7, 6, 1, 57, 0, 4, 2, 18, 66, 3, 86, 0, 2, 32, 0, 3, 86, 107, 0, 7, 6, 1, 58, 0, 2, 18, 66, 3, 0, 2, 32, 3, 13, 9, 0, 3, 107, 0, 7, 6, 1, 59, 0, 4, 2, 18, 66, 3, 51, 0, 2, 32, 0, 3, 51, 107, 0, 7, 6, 1, 65, 0, 3, 0, 7, 6, 1, 66, 0, 4, 2, 18, 66, 3, 81, 0, 2, 32, 0, 3, 81, 107, 0, 7, 6, 1, 67, 0, 4, 2, 18, 66, 3, 51, 0, 2, 32, 0, 3, 51, 107, 0, 7, 6, 1, 69, 0, 4, 2, 18, 66, 3, 55, 0, 2, 32, 0, 3, 55, 107, 0, 7, 6, 1, 70, 0, 4, 2, 18, 66, 3, 63, 0, 2, 32, 0, 3, 63, 107, 0, 7, 6, 1, 71, 0, 4, 1, 18, 67, 2, 18, 68, 3, 50, 0, 1, 18, 68, 2, 18, 68, 0, 2, 18, 66, 0, 2, 32, 0, 3, 50, 107, 0, 7, 6, 1, 72, 0, 2, 32, 3, 13, 0, 2, 18, 66, 3, 105, 0, 3, 105, 107, 0, 7, 6, 1, 73, 0, 4, 1, 18, 68, 2, 18, 68, 3, 40, 0, 2, 32, 0, 2, 18, 66, 3, 82, 0, 3, 82, 107, 0, 7, 6, 1, 75, 0, 3, 37, 0, 8, 3, 57, 107, 0, 7, 6, 1, 79, 0, 3, 107, 0, 7, 6, 1, 80, 0, 3, 39, 0, 7, 6, 1, 81, 0, 3, 106, 0, 7, 6, 1, 82, 0, 3, 12, 0, 7, 6, 1, 127, 0, 4, 1, 18, 68, 2, 18, 68, 3, 48, 0, 2, 18, 66, 0, 2, 32, 0, 3, 48, 107, 0, 7, 6, 218, 134, 0, 4, 2, 18, 66, 3, 74, 0, 2, 32, 0, 3, 74, 107, 0, 7, 6, 218, 152, 0, 4, 2, 18, 66, 3, 88, 0, 2, 32, 0, 3, 88, 107, 0, 7, 6, 218, 169, 0, 4, 1, 18, 67, 2, 18, 68, 3, 49, 0, 1, 18, 68, 2, 18, 68, 0, 2, 18, 66, 0, 2, 32, 0, 3, 49, 107, 0, 7, 6, 218, 175, 0, 4, 2, 18, 66, 3, 79, 0, 2, 32, 0, 3, 79, 107, 0, 7, 6, 219, 140, 0, 3, 37, 0, 8, 3, 57, 107, 0, 7, 6, 0, 36, 3, 70, 39, 55, 13, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts47 = FileInMemory_createWithData (2569, reinterpret_cast (&espeakdata_dicts47_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/prs_dict", L"prs"); Collection_addItem (me.peek(), espeakdata_dicts47.transfer()); static unsigned char espeakdata_dicts48_data[14776] = { 0, 4, 0, 0, 2, 37, 0, 0, 22, 69, 16, 84, 15, 37, 48, 70, 36, 48, 6, 134, 87, 49, 133, 0, 102, 81, 113, 117, 101, 32, 0, 0, 0, 0, 0, 18, 70, 28, 245, 133, 72, 227, 192, 79, 39, 82, 6, 36, 34, 50, 109, 0, 37, 6, 65, 4, 35, 0, 14, 9, 198, 12, 243, 148, 84, 67, 192, 102, 8, 65, 4, 130, 0, 101, 76, 34, 5, 193, 4, 76, 34, 0, 0, 18, 70, 32, 20, 132, 92, 20, 133, 105, 6, 35, 34, 70, 58, 36, 14, 0, 102, 19, 70, 32, 20, 132, 92, 20, 133, 6, 35, 34, 70, 4, 58, 6, 107, 44, 0, 101, 0, 12, 68, 37, 48, 65, 12, 37, 86, 6, 130, 49, 0, 7, 196, 52, 147, 136, 4, 76, 0, 0, 17, 70, 8, 16, 203, 85, 4, 192, 69, 107, 49, 6, 130, 48, 87, 0, 102, 0, 9, 67, 53, 82, 64, 63, 58, 37, 0, 6, 195, 21, 80, 64, 17, 16, 67, 21, 64, 192, 4, 36, 121, 6, 107, 47, 36, 16, 130, 0, 102, 16, 67, 21, 64, 192, 4, 36, 121, 6, 107, 47, 12, 16, 130, 0, 101, 0, 0, 0, 0, 6, 195, 69, 81, 64, 72, 13, 4, 95, 8, 1, 3, 49, 35, 16, 6, 39, 66, 0, 0, 11, 68, 28, 21, 83, 76, 79, 6, 112, 87, 0, 6, 195, 32, 242, 133, 21, 0, 0, 0, 10, 199, 21, 53, 1, 72, 83, 79, 76, 72, 0, 0, 6, 65, 20, 107, 0, 14, 7, 65, 20, 37, 0, 102, 72, 7, 65, 20, 37, 0, 101, 72, 0, 9, 198, 16, 80, 129, 37, 131, 192, 102, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 1, 37, 48, 39, 34, 87, 6, 116, 66, 47, 109, 0, 27, 0, 8, 1, 38, 10, 6, 36, 10, 0, 0, 0, 14, 73, 64, 192, 89, 77, 64, 84, 36, 243, 128, 21, 0, 10, 0, 0, 7, 195, 64, 244, 128, 102, 72, 6, 195, 64, 244, 128, 72, 15, 1, 42, 130, 87, 47, 36, 16, 6, 37, 87, 49, 109, 0, 27, 0, 15, 68, 52, 81, 9, 4, 63, 6, 107, 70, 4, 37, 130, 0, 101, 8, 1, 43, 63, 115, 136, 0, 27, 0, 17, 69, 92, 17, 206, 21, 32, 82, 6, 35, 79, 122, 50, 36, 34, 0, 103, 15, 69, 92, 17, 206, 21, 32, 82, 6, 35, 79, 50, 36, 34, 0, 0, 0, 11, 1, 46, 48, 6, 39, 66, 47, 109, 0, 27, 0, 0, 0, 0, 0, 0, 13, 138, 5, 19, 20, 195, 161, 22, 1, 13, 15, 19, 72, 0, 10, 135, 195, 169, 18, 1, 13, 15, 19, 72, 0, 0, 11, 67, 52, 83, 149, 63, 36, 50, 40, 0, 101, 0, 11, 69, 24, 81, 15, 72, 16, 21, 0, 101, 10, 8, 197, 21, 48, 207, 88, 16, 21, 8, 197, 76, 84, 137, 4, 208, 72, 9, 5, 95, 48, 1, 14, 4, 37, 0, 0, 0, 0, 0, 6, 65, 60, 108, 0, 14, 5, 193, 60, 76, 34, 0, 14, 1, 61, 10, 10, 37, 79, 58, 6, 130, 55, 10, 0, 27, 0, 0, 0, 6, 195, 69, 81, 82, 102, 10, 1, 64, 130, 99, 6, 39, 69, 130, 0, 0, 17, 70, 32, 19, 9, 76, 243, 128, 130, 55, 6, 37, 87, 130, 66, 0, 101, 0, 0, 6, 195, 16, 240, 197, 21, 0, 0, 0, 11, 67, 16, 240, 192, 70, 6, 108, 49, 0, 101, 0, 7, 196, 69, 81, 68, 4, 20, 0, 15, 69, 16, 80, 137, 4, 224, 70, 6, 107, 69, 57, 127, 66, 0, 0, 0, 0, 0, 14, 69, 65, 149, 8, 60, 224, 48, 6, 115, 85, 127, 66, 0, 0, 14, 68, 77, 0, 67, 20, 87, 48, 6, 116, 87, 110, 0, 101, 0, 0, 0, 0, 11, 67, 48, 240, 203, 55, 6, 108, 49, 0, 101, 0, 0, 24, 72, 21, 52, 5, 4, 177, 68, 37, 64, 37, 87, 48, 6, 37, 12, 49, 107, 70, 4, 37, 47, 0, 101, 0, 16, 69, 92, 147, 132, 61, 112, 58, 6, 37, 66, 70, 39, 58, 0, 102, 17, 69, 92, 147, 132, 61, 112, 58, 6, 37, 66, 70, 6, 39, 40, 0, 101, 0, 8, 66, 85, 0, 130, 48, 0, 101, 0, 0, 21, 72, 61, 1, 78, 60, 97, 137, 12, 80, 6, 39, 48, 116, 66, 6, 108, 81, 37, 87, 0, 0, 6, 65, 88, 82, 36, 0, 0, 6, 194, 5, 48, 76, 34, 0, 0, 17, 4, 95, 49, 77, 52, 6, 126, 50, 47, 34, 37, 55, 57, 6, 128, 0, 0, 15, 69, 72, 243, 131, 32, 144, 34, 6, 108, 50, 97, 37, 12, 0, 8, 197, 52, 147, 136, 5, 48, 76, 0, 0, 0, 0, 12, 4, 95, 49, 77, 49, 63, 6, 114, 10, 0, 102, 13, 4, 95, 49, 77, 49, 63, 6, 37, 55, 10, 0, 101, 7, 65, 96, 89, 37, 136, 0, 0, 6, 195, 84, 229, 19, 17, 15, 4, 95, 49, 77, 50, 6, 126, 63, 37, 55, 57, 6, 128, 0, 0, 16, 4, 95, 49, 77, 51, 6, 126, 63, 69, 37, 55, 57, 6, 128, 0, 0, 12, 68, 77, 1, 65, 44, 87, 48, 37, 12, 49, 0, 7, 196, 64, 83, 15, 76, 72, 0, 13, 67, 16, 245, 206, 70, 6, 35, 4, 58, 50, 0, 101, 0, 0, 11, 67, 100, 84, 192, 57, 6, 107, 87, 0, 101, 6, 195, 16, 244, 192, 72, 6, 195, 48, 244, 192, 72, 0, 12, 137, 20, 9, 22, 195, 169, 18, 5, 9, 19, 72, 0, 0, 0, 10, 199, 64, 241, 5, 72, 83, 79, 76, 76, 0, 0, 0, 9, 198, 4, 193, 213, 52, 20, 192, 72, 6, 195, 12, 20, 207, 102, 0, 0, 7, 196, 80, 83, 136, 60, 72, 0, 0, 18, 70, 16, 20, 85, 20, 193, 64, 70, 130, 49, 6, 36, 55, 110, 0, 76, 34, 5, 194, 4, 80, 17, 0, 0, 0, 0, 12, 67, 48, 241, 207, 55, 6, 108, 79, 109, 0, 102, 19, 67, 48, 241, 207, 55, 6, 108, 79, 40, 49, 133, 0, 102, 81, 113, 117, 101, 32, 0, 0, 0, 0, 0, 0, 15, 68, 21, 128, 197, 48, 4, 107, 49, 87, 6, 107, 55, 0, 101, 14, 68, 25, 32, 77, 20, 81, 51, 6, 116, 63, 37, 0, 102, 14, 68, 25, 32, 77, 20, 81, 34, 6, 116, 63, 110, 0, 101, 0, 9, 198, 64, 244, 148, 4, 229, 15, 102, 0, 0, 14, 67, 84, 226, 88, 57, 6, 40, 50, 37, 49, 87, 0, 102, 15, 67, 84, 226, 88, 4, 40, 12, 50, 6, 37, 49, 87, 0, 101, 0, 0, 16, 69, 64, 147, 210, 21, 48, 48, 37, 6, 108, 16, 37, 87, 0, 102, 0, 0, 0, 0, 0, 0, 7, 195, 77, 32, 64, 102, 24, 18, 67, 77, 32, 64, 4, 107, 93, 6, 107, 34, 34, 57, 6, 35, 0, 101, 24, 0, 7, 196, 64, 241, 5, 72, 76, 7, 196, 80, 147, 136, 4, 72, 0, 13, 201, 12, 19, 3, 84, 192, 68, 61, 32, 64, 101, 21, 0, 19, 70, 21, 132, 18, 21, 52, 192, 4, 107, 49, 87, 48, 34, 6, 107, 87, 0, 101, 0, 0, 6, 195, 72, 81, 5, 21, 0, 0, 0, 0, 11, 4, 95, 49, 67, 48, 87, 6, 116, 66, 0, 0, 0, 6, 194, 16, 16, 72, 34, 0, 0, 0, 8, 197, 21, 53, 9, 88, 80, 72, 0, 0, 11, 67, 16, 21, 0, 70, 6, 35, 47, 0, 101, 0, 0, 0, 0, 0, 7, 196, 64, 241, 5, 52, 76, 0, 0, 19, 70, 36, 229, 18, 4, 225, 84, 37, 66, 47, 51, 35, 50, 6, 107, 47, 0, 102, 0, 0, 11, 67, 56, 83, 5, 50, 36, 55, 110, 0, 77, 0, 8, 197, 21, 53, 1, 37, 48, 72, 0, 0, 0, 13, 68, 100, 18, 15, 60, 37, 35, 105, 6, 40, 0, 102, 15, 68, 100, 18, 15, 60, 6, 37, 4, 35, 105, 6, 40, 0, 101, 0, 0, 10, 198, 76, 83, 136, 61, 32, 64, 101, 21, 0, 13, 67, 56, 86, 20, 50, 6, 107, 49, 87, 47, 0, 101, 0, 0, 0, 5, 194, 17, 32, 24, 0, 0, 13, 68, 56, 84, 211, 20, 50, 6, 36, 87, 110, 0, 76, 0, 15, 69, 32, 149, 12, 21, 32, 105, 6, 37, 47, 55, 36, 34, 0, 16, 69, 72, 80, 68, 21, 32, 34, 6, 37, 70, 4, 130, 44, 0, 101, 0, 0, 0, 0, 0, 0, 0, 16, 68, 56, 84, 212, 20, 50, 6, 36, 87, 74, 37, 0, 102, 76, 34, 0, 0, 6, 195, 52, 241, 15, 20, 0, 0, 0, 16, 69, 36, 229, 133, 40, 16, 37, 66, 82, 6, 107, 88, 130, 0, 102, 0, 0, 0, 6, 131, 8, 195, 161, 76, 20, 68, 76, 19, 22, 60, 87, 6, 35, 55, 82, 40, 87, 133, 0, 102, 81, 115, 101, 32, 14, 68, 56, 244, 211, 4, 50, 6, 108, 87, 130, 0, 102, 76, 0, 0, 0, 0, 0, 0, 0, 0, 14, 68, 52, 83, 143, 72, 63, 36, 50, 6, 108, 34, 0, 102, 14, 68, 52, 83, 143, 72, 63, 110, 50, 6, 108, 44, 0, 101, 0, 0, 0, 0, 0, 0, 19, 70, 16, 245, 206, 48, 240, 68, 70, 35, 126, 66, 55, 6, 39, 58, 70, 0, 103, 18, 70, 16, 245, 206, 48, 240, 68, 70, 112, 66, 55, 6, 39, 58, 70, 0, 102, 21, 70, 16, 245, 206, 48, 240, 68, 70, 6, 35, 4, 58, 50, 55, 6, 39, 40, 70, 0, 101, 0, 0, 15, 68, 48, 147, 149, 96, 55, 6, 37, 50, 109, 49, 87, 0, 102, 16, 68, 48, 147, 149, 96, 55, 4, 37, 50, 6, 40, 49, 87, 0, 101, 0, 0, 15, 70, 8, 16, 130, 4, 113, 64, 69, 6, 35, 69, 37, 73, 0, 0, 0, 7, 196, 5, 1, 68, 88, 17, 0, 0, 5, 194, 16, 80, 72, 0, 0, 0, 0, 0, 0, 17, 70, 32, 245, 13, 4, 147, 0, 105, 39, 47, 63, 6, 116, 55, 0, 102, 18, 70, 32, 245, 13, 4, 147, 0, 105, 6, 108, 47, 63, 6, 116, 55, 0, 101, 16, 4, 95, 4, 16, 20, 10, 82, 6, 37, 34, 79, 40, 55, 130, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 67, 80, 147, 69, 47, 6, 115, 63, 110, 0, 101, 0, 0, 0, 0, 9, 3, 95, 35, 57, 47, 35, 69, 0, 11, 4, 95, 20, 12, 4, 47, 37, 55, 0, 101, 10, 4, 95, 20, 12, 4, 74, 6, 114, 0, 0, 0, 6, 195, 20, 68, 0, 17, 0, 19, 71, 48, 21, 143, 37, 50, 69, 72, 55, 35, 82, 58, 35, 86, 57, 6, 36, 0, 11, 67, 4, 197, 0, 6, 35, 55, 47, 0, 101, 7, 195, 84, 228, 192, 72, 34, 0, 0, 0, 25, 12, 19, 3, 8, 18, 195, 182, 4, 9, 14, 7, 5, 18, 89, 34, 6, 36, 70, 37, 50, 79, 36, 34, 0, 0, 0, 0, 15, 69, 64, 192, 89, 21, 32, 48, 55, 6, 116, 130, 44, 0, 101, 0, 0, 0, 14, 68, 64, 21, 83, 20, 48, 6, 35, 40, 12, 86, 0, 101, 0, 0, 0, 0, 8, 196, 56, 244, 211, 60, 102, 76, 0, 0, 9, 198, 21, 53, 1, 72, 82, 64, 72, 0, 0, 11, 68, 48, 245, 73, 76, 21, 102, 114, 0, 10, 0, 8, 197, 80, 147, 136, 4, 208, 72, 0, 17, 7, 1, 12, 13, 15, 195, 167, 15, 112, 63, 6, 108, 87, 109, 0, 36, 6, 194, 21, 80, 76, 32, 0, 0, 0, 9, 134, 16, 18, 5, 195, 167, 15, 21, 8, 197, 4, 193, 213, 57, 48, 72, 0, 9, 198, 80, 149, 133, 72, 19, 64, 72, 9, 198, 80, 149, 133, 72, 19, 64, 72, 0, 0, 12, 68, 25, 33, 85, 16, 81, 34, 6, 134, 70, 0, 18, 70, 20, 147, 147, 80, 82, 78, 11, 6, 115, 50, 89, 47, 4, 115, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 67, 80, 16, 128, 47, 6, 35, 69, 0, 101, 6, 195, 5, 96, 192, 17, 0, 7, 196, 57, 83, 65, 76, 72, 0, 16, 69, 76, 52, 143, 48, 192, 87, 49, 12, 34, 6, 39, 55, 0, 101, 0, 0, 9, 67, 61, 33, 192, 108, 34, 79, 0, 0, 0, 0, 0, 0, 13, 68, 52, 245, 83, 20, 63, 6, 112, 86, 37, 0, 102, 0, 0, 5, 194, 4, 240, 72, 0, 6, 195, 25, 82, 64, 72, 6, 195, 61, 50, 64, 17, 0, 7, 196, 64, 244, 211, 60, 76, 0, 15, 69, 21, 52, 5, 4, 176, 37, 87, 48, 6, 37, 12, 49, 0, 8, 197, 20, 208, 143, 72, 16, 102, 0, 17, 70, 48, 82, 66, 56, 150, 128, 55, 6, 115, 69, 50, 37, 12, 121, 0, 0, 0, 0, 8, 197, 80, 149, 133, 72, 16, 72, 0, 19, 70, 72, 146, 142, 16, 17, 76, 99, 6, 35, 37, 50, 38, 70, 6, 35, 55, 0, 6, 195, 57, 83, 65, 72, 0, 6, 195, 57, 83, 64, 72, 0, 12, 67, 60, 194, 15, 6, 39, 61, 109, 0, 104, 37, 13, 67, 60, 194, 15, 6, 39, 55, 57, 109, 0, 102, 37, 0, 0, 12, 67, 48, 147, 133, 55, 6, 35, 37, 50, 0, 101, 18, 70, 72, 85, 15, 72, 227, 192, 99, 36, 47, 6, 108, 34, 50, 109, 0, 36, 0, 0, 6, 195, 17, 3, 195, 17, 0, 0, 17, 70, 77, 65, 80, 32, 83, 128, 87, 47, 6, 37, 12, 82, 13, 50, 0, 13, 66, 16, 160, 70, 4, 37, 12, 73, 6, 116, 0, 101, 19, 67, 64, 20, 129, 48, 4, 35, 16, 130, 49, 133, 0, 102, 81, 113, 117, 101, 32, 6, 195, 64, 20, 129, 72, 0, 0, 0, 16, 70, 88, 243, 20, 4, 148, 133, 82, 108, 55, 47, 6, 107, 34, 0, 16, 69, 85, 3, 15, 4, 64, 130, 48, 55, 6, 39, 40, 70, 0, 101, 18, 70, 76, 241, 148, 92, 20, 133, 87, 6, 108, 81, 47, 58, 36, 14, 0, 102, 20, 70, 76, 241, 148, 92, 20, 133, 87, 6, 108, 81, 47, 4, 58, 6, 107, 44, 0, 101, 17, 69, 12, 19, 131, 20, 192, 49, 6, 130, 50, 87, 6, 107, 55, 0, 101, 0, 17, 70, 8, 84, 142, 32, 20, 132, 69, 36, 34, 50, 6, 35, 34, 70, 0, 0, 0, 7, 196, 17, 83, 65, 76, 72, 0, 0, 18, 70, 21, 53, 9, 88, 84, 128, 36, 87, 74, 37, 82, 6, 107, 34, 0, 72, 0, 0, 0, 0, 12, 67, 48, 149, 133, 55, 6, 35, 37, 82, 0, 101, 6, 195, 80, 149, 133, 72, 0, 6, 195, 32, 149, 128, 17, 0, 12, 67, 56, 84, 143, 50, 6, 107, 34, 40, 0, 101, 7, 196, 80, 84, 133, 36, 72, 7, 196, 76, 84, 133, 36, 72, 0, 11, 136, 6, 195, 180, 13, 1, 13, 15, 19, 72, 0, 0, 0, 15, 68, 64, 83, 1, 76, 48, 6, 36, 55, 130, 87, 0, 102, 72, 7, 196, 16, 83, 5, 76, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 70, 77, 3, 210, 80, 147, 135, 87, 48, 6, 108, 34, 47, 4, 37, 50, 79, 0, 101, 0, 0, 11, 136, 20, 195, 173, 14, 8, 5, 9, 19, 72, 0, 10, 135, 5, 19, 20, 1, 18, 195, 161, 72, 0, 0, 14, 68, 20, 197, 15, 56, 6, 107, 55, 47, 130, 66, 0, 101, 10, 135, 6, 195, 180, 18, 5, 9, 19, 72, 0, 0, 17, 70, 52, 18, 79, 72, 84, 192, 63, 115, 6, 108, 16, 37, 87, 0, 102, 0, 0, 27, 11, 20, 5, 12, 5, 13, 195, 179, 22, 5, 9, 19, 47, 4, 107, 55, 4, 107, 63, 6, 108, 82, 116, 136, 0, 101, 0, 0, 6, 195, 57, 97, 1, 17, 0, 10, 3, 226, 130, 172, 6, 113, 16, 109, 0, 0, 6, 195, 57, 83, 147, 72, 0, 0, 10, 67, 64, 17, 197, 48, 6, 116, 73, 0, 0, 0, 0, 12, 67, 64, 147, 210, 48, 37, 6, 108, 34, 0, 102, 0, 12, 137, 20, 195, 173, 14, 8, 1, 13, 15, 19, 72, 0, 0, 7, 196, 16, 83, 1, 76, 76, 20, 6, 16, 18, 15, 6, 194, 170, 48, 51, 4, 39, 81, 36, 87, 6, 39, 16, 130, 0, 0, 8, 197, 64, 244, 145, 84, 80, 102, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 199, 21, 53, 9, 88, 84, 129, 52, 72, 6, 195, 4, 244, 192, 72, 0, 7, 196, 48, 244, 5, 76, 20, 0, 0, 0, 6, 195, 16, 20, 192, 72, 6, 195, 48, 20, 192, 72, 0, 0, 16, 69, 56, 83, 19, 60, 224, 50, 6, 107, 55, 87, 130, 66, 0, 101, 0, 14, 4, 95, 13, 3, 14, 63, 35, 49, 51, 6, 39, 66, 0, 0, 0, 0, 0, 0, 0, 7, 196, 76, 84, 137, 4, 72, 0, 0, 17, 70, 9, 32, 73, 48, 193, 64, 69, 51, 6, 35, 37, 55, 37, 0, 102, 18, 70, 9, 32, 73, 48, 193, 64, 69, 12, 34, 6, 35, 37, 55, 110, 0, 101, 5, 194, 20, 208, 72, 6, 194, 16, 240, 72, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 68, 24, 244, 129, 52, 81, 39, 16, 128, 0, 73, 0, 11, 67, 20, 225, 0, 6, 36, 50, 70, 0, 101, 0, 0, 6, 195, 65, 32, 64, 72, 13, 3, 95, 51, 88, 47, 51, 6, 37, 66, 47, 130, 0, 0, 19, 6, 16, 18, 15, 6, 194, 186, 48, 51, 4, 39, 81, 36, 87, 6, 39, 34, 0, 14, 3, 95, 48, 67, 87, 6, 116, 66, 47, 109, 136, 0, 102, 14, 3, 95, 48, 67, 87, 6, 116, 66, 47, 40, 136, 0, 101, 0, 0, 0, 21, 71, 12, 193, 86, 21, 36, 207, 56, 49, 55, 6, 107, 82, 36, 34, 87, 39, 66, 0, 102, 21, 71, 12, 193, 86, 21, 36, 207, 56, 49, 55, 6, 107, 82, 110, 34, 87, 130, 66, 0, 101, 6, 195, 17, 32, 64, 24, 0, 8, 196, 76, 240, 146, 20, 101, 21, 14, 68, 76, 240, 146, 20, 87, 6, 39, 69, 51, 110, 0, 102, 0, 17, 69, 16, 84, 201, 28, 224, 70, 4, 37, 86, 6, 35, 37, 50, 0, 101, 0, 0, 18, 71, 76, 192, 67, 45, 112, 82, 20, 87, 55, 6, 35, 49, 58, 36, 14, 0, 7, 132, 20, 195, 170, 13, 72, 0, 13, 67, 53, 1, 71, 4, 107, 63, 48, 6, 107, 79, 0, 12, 3, 95, 49, 67, 87, 6, 116, 66, 47, 40, 0, 0, 0, 0, 0, 0, 0, 5, 194, 48, 16, 72, 16, 3, 95, 49, 57, 70, 36, 86, 36, 50, 6, 108, 82, 110, 0, 102, 16, 3, 95, 49, 57, 70, 110, 86, 130, 50, 6, 108, 82, 110, 0, 101, 0, 14, 3, 95, 49, 56, 70, 36, 86, 6, 118, 47, 40, 0, 102, 15, 3, 95, 49, 56, 70, 110, 86, 6, 108, 37, 47, 40, 0, 101, 0, 16, 3, 95, 50, 67, 70, 40, 86, 6, 116, 66, 47, 109, 86, 0, 102, 16, 3, 95, 50, 67, 70, 40, 86, 6, 116, 66, 47, 40, 136, 0, 101, 0, 0, 0, 0, 0, 8, 197, 29, 35, 211, 76, 240, 21, 16, 69, 21, 53, 5, 88, 80, 36, 87, 47, 36, 82, 110, 0, 102, 74, 0, 11, 3, 95, 49, 49, 6, 39, 66, 86, 110, 0, 0, 10, 3, 95, 49, 48, 70, 6, 107, 136, 0, 0, 7, 196, 5, 52, 201, 52, 102, 17, 3, 95, 51, 67, 47, 51, 36, 86, 6, 36, 66, 47, 109, 86, 0, 102, 17, 3, 95, 51, 67, 47, 34, 110, 86, 6, 36, 66, 47, 40, 136, 0, 101, 13, 3, 95, 49, 51, 47, 51, 6, 36, 86, 37, 0, 102, 13, 3, 95, 49, 51, 47, 34, 6, 36, 86, 110, 0, 101, 0, 8, 197, 80, 84, 133, 37, 48, 72, 8, 197, 76, 84, 133, 37, 48, 72, 11, 3, 95, 49, 50, 70, 6, 39, 86, 110, 0, 0, 12, 3, 95, 49, 53, 49, 6, 37, 66, 86, 110, 0, 0, 15, 3, 95, 49, 52, 49, 35, 47, 6, 39, 34, 86, 110, 0, 102, 15, 3, 95, 49, 52, 49, 130, 47, 6, 39, 34, 86, 110, 0, 101, 0, 6, 195, 4, 145, 19, 17, 17, 3, 95, 49, 55, 70, 4, 36, 86, 36, 87, 6, 107, 74, 110, 0, 102, 16, 3, 95, 49, 55, 70, 110, 86, 130, 87, 6, 107, 47, 110, 0, 101, 0, 16, 3, 95, 49, 54, 70, 4, 36, 86, 36, 87, 6, 116, 136, 0, 102, 16, 3, 95, 49, 54, 70, 110, 86, 130, 87, 6, 36, 37, 136, 0, 101, 0, 0, 15, 3, 95, 55, 88, 87, 36, 47, 6, 116, 66, 47, 130, 0, 102, 15, 3, 95, 55, 88, 87, 110, 47, 6, 116, 66, 47, 130, 0, 101, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 64, 241, 9, 4, 76, 16, 3, 95, 53, 67, 49, 37, 65, 6, 116, 66, 47, 109, 86, 0, 102, 16, 3, 95, 53, 67, 49, 37, 65, 6, 116, 66, 47, 40, 136, 0, 101, 0, 0, 0, 0, 0, 14, 69, 48, 22, 79, 85, 64, 55, 6, 116, 4, 112, 47, 0, 16, 69, 12, 243, 8, 21, 32, 49, 39, 61, 6, 107, 34, 0, 104, 37, 17, 69, 12, 243, 8, 21, 32, 49, 39, 55, 57, 6, 107, 34, 0, 102, 37, 0, 12, 137, 16, 15, 4, 195, 173, 1, 13, 15, 19, 76, 0, 13, 138, 20, 9, 22, 195, 169, 18, 1, 13, 15, 19, 72, 6, 195, 52, 19, 0, 102, 6, 195, 4, 20, 16, 17, 0, 6, 195, 65, 32, 83, 72, 11, 3, 1, 46, 3, 6, 35, 87, 6, 36, 0, 0, 0, 12, 137, 19, 5, 18, 195, 173, 1, 13, 15, 19, 72, 0, 21, 71, 44, 193, 86, 21, 36, 207, 56, 49, 55, 6, 107, 82, 36, 34, 87, 130, 66, 0, 101, 8, 132, 1, 20, 195, 169, 102, 72, 0, 21, 68, 4, 229, 5, 76, 6, 127, 66, 74, 37, 87, 49, 133, 0, 102, 81, 113, 117, 101, 32, 0, 21, 69, 21, 128, 197, 80, 240, 36, 87, 6, 107, 47, 40, 87, 133, 0, 102, 81, 115, 101, 32, 0, 0, 13, 3, 95, 50, 88, 82, 6, 37, 66, 74, 110, 0, 102, 13, 3, 95, 50, 88, 82, 6, 37, 66, 47, 110, 0, 101, 0, 0, 0, 16, 70, 72, 145, 77, 4, 227, 128, 34, 6, 37, 12, 63, 35, 50, 0, 0, 0, 0, 8, 197, 5, 1, 78, 5, 48, 102, 17, 69, 56, 84, 212, 21, 48, 50, 6, 36, 87, 74, 37, 87, 0, 102, 76, 0, 0, 19, 71, 25, 34, 69, 17, 34, 67, 32, 81, 34, 6, 37, 12, 70, 34, 37, 89, 0, 0, 14, 68, 25, 35, 206, 80, 81, 34, 6, 39, 50, 47, 0, 101, 7, 196, 24, 22, 133, 72, 76, 0, 0, 0, 0, 15, 3, 95, 63, 63, 87, 6, 37, 63, 69, 39, 55, 109, 10, 0, 0, 11, 4, 14, 195, 163, 15, 50, 4, 128, 0, 11, 0, 5, 194, 53, 32, 24, 0, 14, 5, 22, 15, 3, 195, 170, 82, 39, 87, 6, 36, 0, 76, 16, 3, 95, 52, 88, 49, 58, 35, 16, 6, 116, 66, 47, 130, 0, 102, 16, 3, 95, 52, 88, 49, 58, 130, 16, 6, 36, 66, 47, 130, 0, 101, 0, 0, 0, 0, 0, 0, 0, 5, 194, 56, 16, 72, 0, 16, 3, 95, 53, 88, 87, 37, 66, 49, 58, 6, 116, 66, 47, 130, 0, 0, 0, 0, 0, 6, 195, 24, 242, 64, 72, 0, 12, 200, 65, 35, 198, 21, 52, 207, 72, 16, 101, 21, 0, 15, 69, 60, 97, 137, 12, 80, 6, 108, 81, 4, 37, 87, 0, 101, 8, 197, 5, 21, 69, 48, 16, 76, 0, 0, 15, 3, 95, 54, 88, 87, 36, 87, 6, 116, 66, 47, 130, 0, 102, 15, 3, 95, 54, 88, 87, 110, 87, 6, 116, 66, 47, 130, 0, 101, 0, 0, 0, 0, 6, 195, 76, 83, 64, 102, 0, 7, 196, 24, 22, 133, 52, 76, 0, 17, 7, 11, 18, 195, 188, 7, 5, 18, 49, 51, 6, 37, 88, 36, 34, 0, 0, 0, 0, 13, 68, 77, 65, 86, 20, 87, 47, 6, 37, 12, 82, 0, 7, 196, 52, 241, 15, 76, 20, 0, 0, 9, 198, 80, 241, 1, 88, 144, 64, 102, 0, 0, 14, 68, 53, 82, 84, 4, 63, 58, 6, 37, 66, 47, 130, 0, 0, 0, 18, 70, 36, 228, 212, 4, 195, 0, 4, 37, 50, 87, 47, 6, 35, 55, 0, 101, 0, 10, 67, 52, 18, 76, 63, 6, 116, 55, 0, 17, 67, 13, 68, 140, 49, 6, 39, 66, 47, 12, 34, 4, 108, 55, 0, 101, 9, 134, 20, 5, 18, 195, 163, 15, 72, 13, 3, 95, 56, 88, 118, 47, 6, 116, 66, 47, 130, 0, 0, 0, 11, 136, 16, 15, 4, 5, 18, 195, 163, 15, 76, 0, 0, 6, 195, 88, 245, 64, 76, 7, 195, 76, 85, 64, 76, 34, 0, 0, 12, 5, 11, 195, 188, 8, 12, 49, 6, 37, 55, 0, 0, 5, 194, 52, 80, 72, 0, 15, 3, 95, 57, 88, 50, 39, 82, 6, 116, 66, 47, 130, 0, 102, 15, 3, 95, 57, 88, 50, 40, 82, 6, 116, 66, 47, 130, 0, 101, 0, 0, 17, 69, 72, 80, 68, 52, 80, 34, 6, 37, 12, 70, 63, 37, 12, 0, 101, 0, 0, 0, 0, 0, 13, 3, 95, 63, 65, 55, 6, 36, 47, 51, 130, 10, 0, 0, 0, 0, 11, 136, 5, 19, 20, 1, 18, 195, 163, 15, 72, 0, 0, 0, 0, 8, 197, 24, 244, 212, 21, 48, 72, 16, 69, 56, 244, 211, 5, 48, 50, 6, 108, 87, 130, 87, 0, 102, 76, 0, 0, 0, 11, 67, 92, 80, 128, 58, 6, 107, 69, 0, 102, 0, 0, 13, 69, 28, 82, 83, 20, 192, 79, 6, 115, 86, 135, 0, 0, 0, 7, 132, 22, 195, 163, 15, 76, 6, 195, 77, 80, 64, 76, 14, 4, 95, 15, 7, 15, 39, 79, 39, 50, 6, 36, 49, 0, 0, 14, 68, 77, 64, 82, 80, 87, 47, 6, 35, 34, 47, 0, 101, 7, 196, 20, 229, 18, 20, 102, 0, 9, 198, 20, 228, 85, 4, 229, 15, 102, 0, 6, 195, 65, 35, 211, 72, 0, 23, 71, 52, 144, 210, 61, 51, 198, 80, 63, 6, 115, 49, 51, 39, 58, 87, 6, 108, 81, 47, 0, 102, 24, 71, 52, 144, 210, 61, 51, 198, 80, 63, 4, 37, 49, 12, 34, 6, 39, 87, 4, 108, 81, 47, 0, 101, 0, 7, 195, 60, 225, 5, 102, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 195, 160, 19, 4, 35, 12, 87, 0, 0, 0, 0, 15, 69, 81, 84, 137, 56, 112, 47, 6, 40, 16, 37, 66, 79, 0, 8, 197, 64, 241, 9, 4, 208, 76, 16, 69, 5, 21, 69, 48, 80, 130, 49, 6, 36, 55, 110, 0, 76, 34, 0, 11, 67, 21, 145, 83, 6, 35, 37, 86, 0, 101, 6, 194, 61, 48, 76, 34, 0, 7, 195, 65, 35, 192, 72, 34, 0, 17, 4, 95, 48, 77, 52, 47, 34, 37, 55, 57, 6, 125, 57, 86, 0, 102, 17, 4, 95, 48, 77, 52, 47, 34, 37, 55, 57, 6, 125, 57, 136, 0, 101, 0, 9, 134, 20, 5, 18, 195, 161, 19, 72, 12, 67, 65, 35, 198, 48, 34, 6, 108, 81, 0, 24, 0, 6, 195, 76, 85, 83, 76, 16, 4, 95, 48, 77, 50, 63, 37, 55, 57, 6, 125, 57, 86, 0, 102, 16, 4, 95, 48, 77, 50, 63, 37, 55, 57, 6, 125, 57, 136, 0, 101, 0, 10, 67, 88, 243, 128, 81, 2, 108, 50, 0, 16, 4, 95, 48, 77, 51, 69, 37, 55, 57, 6, 125, 57, 86, 0, 102, 16, 4, 95, 48, 77, 51, 69, 37, 55, 57, 6, 125, 57, 136, 0, 101, 0, 14, 68, 53, 82, 84, 60, 63, 58, 6, 37, 66, 47, 109, 0, 0, 12, 4, 95, 48, 77, 49, 63, 6, 114, 10, 0, 102, 13, 4, 95, 48, 77, 49, 63, 6, 37, 55, 10, 0, 101, 0, 13, 4, 95, 2, 18, 22, 69, 51, 6, 107, 82, 37, 0, 0, 0, 0, 16, 69, 56, 85, 212, 60, 224, 50, 6, 37, 38, 40, 47, 39, 66, 0, 0, 0, 6, 195, 76, 84, 128, 72, 0, 6, 195, 24, 244, 129, 72, 0, 0, 0, 0, 7, 196, 65, 33, 84, 60, 21, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 69, 16, 83, 5, 80, 80, 70, 6, 37, 55, 6, 37, 47, 0, 101, 0, 6, 195, 77, 80, 83, 76, 0, 0, 0, 0, 6, 194, 61, 80, 102, 72, 0, 0, 0, 0, 17, 70, 24, 86, 78, 52, 19, 128, 81, 6, 35, 37, 50, 63, 13, 50, 0, 0, 0, 0, 0, 8, 133, 20, 5, 18, 195, 161, 72, 0, 0, 6, 195, 8, 240, 193, 21, 7, 196, 88, 19, 79, 76, 76, 10, 135, 16, 15, 4, 5, 18, 195, 161, 79, 7, 196, 80, 83, 79, 76, 72, 0, 0, 0, 0, 7, 196, 24, 241, 207, 76, 20, 0, 9, 134, 22, 15, 3, 195, 170, 19, 76, 0, 9, 198, 64, 241, 5, 52, 244, 192, 76, 0, 7, 132, 14, 195, 179, 19, 76, 6, 195, 12, 225, 64, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 24, 244, 211, 20, 208, 21, 8, 197, 21, 53, 1, 88, 16, 72, 23, 69, 76, 83, 80, 72, 80, 87, 6, 36, 66, 48, 34, 37, 49, 133, 0, 102, 81, 113, 117, 101, 32, 0, 0, 0, 0, 0, 9, 3, 195, 169, 19, 107, 87, 0, 72, 20, 4, 95, 3, 9, 18, 87, 37, 34, 49, 126, 66, 81, 55, 6, 107, 49, 87, 109, 0, 0, 0, 0, 0, 0, 6, 131, 95, 195, 188, 43, 0, 0, 6, 131, 95, 195, 186, 43, 0, 0, 7, 195, 52, 20, 192, 102, 72, 11, 67, 56, 244, 192, 50, 40, 136, 0, 102, 72, 6, 195, 56, 244, 192, 72, 6, 195, 60, 212, 192, 17, 0, 0, 0, 0, 6, 131, 95, 195, 180, 43, 12, 4, 95, 19, 20, 11, 69, 6, 35, 99, 130, 0, 0, 6, 131, 95, 195, 181, 43, 0, 12, 3, 95, 194, 170, 35, 86, 6, 37, 65, 109, 0, 13, 4, 95, 1, 3, 21, 130, 79, 6, 40, 70, 109, 0, 0, 6, 131, 95, 195, 179, 43, 0, 6, 195, 60, 229, 64, 65, 0, 0, 0, 5, 194, 48, 240, 72, 12, 66, 76, 16, 4, 107, 87, 57, 6, 35, 0, 101, 12, 3, 4, 46, 3, 70, 4, 36, 87, 6, 36, 0, 0, 0, 6, 131, 95, 195, 173, 43, 0, 6, 131, 95, 195, 170, 43, 0, 12, 67, 40, 241, 207, 88, 6, 108, 79, 109, 0, 36, 0, 13, 4, 95, 18, 14, 7, 127, 50, 6, 107, 55, 0, 101, 11, 4, 95, 18, 14, 7, 127, 50, 6, 135, 0, 0, 28, 3, 95, 194, 161, 4, 36, 87, 49, 55, 130, 63, 35, 87, 4, 128, 4, 37, 66, 82, 36, 34, 74, 6, 37, 70, 130, 0, 6, 131, 95, 195, 169, 43, 0, 0, 0, 23, 67, 33, 69, 16, 35, 79, 4, 35, 47, 36, 47, 36, 6, 48, 36, 10, 0, 81, 58, 47, 47, 32, 0, 0, 6, 131, 95, 195, 162, 43, 0, 14, 5, 5, 19, 20, 195, 161, 36, 87, 47, 6, 35, 0, 72, 6, 131, 95, 195, 163, 43, 0, 6, 131, 95, 195, 160, 43, 6, 131, 95, 195, 160, 43, 0, 6, 131, 95, 195, 161, 43, 0, 15, 69, 84, 37, 78, 81, 80, 40, 69, 6, 40, 50, 47, 40, 0, 8, 197, 80, 244, 146, 21, 48, 21, 0, 14, 5, 19, 5, 18, 195, 161, 87, 36, 16, 35, 0, 102, 74, 0, 0, 0, 0, 6, 195, 64, 83, 15, 72, 0, 10, 67, 21, 32, 64, 107, 16, 130, 0, 73, 0, 0, 0, 5, 194, 77, 32, 24, 0, 7, 132, 22, 195, 179, 19, 76, 0, 10, 67, 21, 32, 77, 107, 16, 128, 0, 73, 0, 10, 67, 77, 83, 210, 87, 58, 108, 34, 0, 0, 15, 67, 41, 1, 71, 88, 4, 108, 47, 130, 48, 6, 107, 79, 0, 19, 4, 95, 1, 3, 50, 130, 79, 6, 40, 70, 109, 70, 6, 40, 48, 55, 109, 0, 0, 0, 0, 15, 69, 8, 16, 203, 85, 0, 69, 107, 49, 6, 130, 48, 0, 102, 0, 9, 66, 60, 176, 108, 49, 6, 116, 0, 9, 198, 17, 84, 129, 57, 65, 64, 102, 0, 0, 0, 0, 0, 0, 0, 0, 30, 3, 95, 194, 191, 4, 37, 66, 47, 36, 99, 4, 39, 79, 35, 87, 4, 128, 4, 37, 66, 82, 36, 34, 74, 6, 37, 70, 130, 0, 0, 0, 14, 68, 88, 241, 197, 48, 81, 6, 39, 12, 79, 13, 55, 0, 14, 68, 76, 51, 213, 80, 87, 49, 6, 35, 40, 47, 0, 101, 13, 67, 64, 83, 1, 48, 6, 36, 55, 130, 0, 102, 72, 11, 67, 16, 83, 5, 70, 36, 55, 110, 0, 77, 7, 196, 4, 32, 68, 88, 17, 0, 12, 3, 95, 194, 186, 108, 86, 6, 37, 65, 109, 0, 0, 0, 11, 136, 19, 5, 18, 195, 173, 5, 9, 19, 72, 0, 6, 195, 16, 83, 1, 76, 0, 8, 197, 12, 244, 144, 61, 48, 20, 0, 0, 0, 12, 67, 77, 84, 197, 86, 6, 40, 12, 121, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 80, 85, 1, 21, 0, 15, 69, 53, 83, 8, 21, 32, 63, 40, 61, 6, 107, 34, 0, 104, 16, 69, 53, 83, 8, 21, 32, 63, 40, 55, 57, 6, 107, 34, 0, 102, 15, 2, 194, 167, 48, 130, 16, 6, 35, 79, 51, 35, 81, 109, 0, 9, 2, 195, 159, 21, 100, 101, 0, 10, 0, 5, 194, 76, 80, 72, 9, 66, 56, 240, 50, 40, 0, 72, 34, 9, 2, 194, 164, 6, 113, 16, 109, 0, 0, 0, 0, 0, 0, 6, 195, 60, 213, 0, 17, 0, 12, 67, 24, 150, 5, 81, 6, 37, 89, 110, 0, 101, 10, 67, 72, 150, 1, 99, 37, 89, 130, 0, 0, 10, 4, 1, 24, 195, 169, 35, 89, 107, 0, 5, 130, 195, 167, 43, 0, 0, 9, 134, 16, 15, 18, 195, 169, 13, 102, 0, 0, 0, 15, 70, 56, 85, 77, 4, 227, 128, 50, 6, 134, 63, 35, 50, 0, 6, 195, 12, 244, 15, 20, 8, 2, 195, 160, 4, 35, 12, 0, 0, 0, 13, 68, 52, 245, 137, 20, 63, 6, 40, 82, 37, 0, 101, 0, 8, 197, 52, 244, 148, 61, 48, 20, 0, 6, 195, 76, 242, 83, 72, 0, 19, 71, 28, 245, 20, 25, 34, 69, 16, 79, 6, 108, 47, 81, 34, 37, 12, 47, 0, 11, 136, 12, 195, 173, 4, 5, 18, 5, 19, 21, 6, 195, 4, 32, 192, 17, 0, 14, 68, 4, 67, 194, 20, 130, 70, 6, 108, 69, 110, 0, 101, 13, 68, 76, 130, 70, 80, 89, 6, 37, 81, 47, 0, 101, 0, 0, 9, 2, 194, 176, 79, 51, 6, 112, 0, 0, 7, 2, 195, 169, 107, 0, 72, 0, 7, 196, 56, 245, 143, 76, 20, 0, 15, 69, 16, 20, 151, 36, 224, 70, 6, 132, 34, 58, 37, 50, 0, 0, 0, 0, 15, 4, 95, 3, 5, 4, 87, 110, 70, 6, 37, 61, 130, 0, 101, 15, 4, 95, 3, 5, 4, 87, 36, 73, 6, 37, 55, 57, 130, 0, 0, 0, 9, 198, 12, 21, 15, 73, 161, 64, 21, 0, 16, 4, 95, 12, 9, 7, 55, 37, 79, 35, 70, 6, 40, 16, 130, 0, 0, 6, 195, 65, 81, 5, 76, 0, 0, 17, 70, 32, 21, 203, 36, 225, 192, 105, 6, 39, 12, 49, 37, 50, 79, 0, 5, 194, 80, 80, 72, 0, 0, 7, 196, 24, 243, 79, 76, 72, 0, 23, 73, 52, 243, 148, 21, 52, 85, 36, 85, 64, 63, 4, 39, 66, 47, 36, 87, 49, 57, 6, 36, 0, 0, 7, 195, 12, 243, 79, 102, 72, 0, 6, 195, 88, 18, 64, 76, 0, 0, 0, 19, 70, 65, 35, 196, 84, 53, 0, 48, 12, 34, 6, 130, 70, 130, 49, 47, 0, 101, 5, 194, 81, 80, 76, 0, 10, 67, 12, 243, 64, 49, 39, 63, 0, 101, 6, 195, 12, 243, 64, 72, 0, 0, 0, 0, 6, 195, 80, 83, 64, 72, 0, 0, 9, 134, 195, 169, 18, 5, 9, 19, 72, 0, 0, 0, 7, 196, 76, 243, 79, 76, 72, 0, 0, 0, 0, 0, 16, 69, 44, 84, 142, 20, 192, 49, 6, 107, 34, 50, 13, 55, 0, 102, 17, 69, 44, 84, 142, 20, 192, 49, 6, 107, 34, 50, 4, 107, 55, 0, 101, 0, 0, 6, 195, 76, 245, 64, 72, 0, 14, 67, 21, 53, 5, 6, 36, 87, 74, 37, 0, 102, 76, 34, 0, 0, 0, 7, 195, 80, 85, 64, 76, 34, 0, 14, 67, 21, 53, 1, 6, 107, 87, 47, 130, 0, 102, 76, 34, 0, 8, 197, 5, 1, 83, 5, 32, 102, 0, 5, 194, 84, 80, 17, 0, 0, 14, 68, 52, 18, 197, 72, 63, 6, 116, 49, 130, 44, 0, 101, 8, 133, 16, 18, 195, 160, 19, 72, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 1, 35, 0, 0, 0, 0, 9, 198, 5, 53, 1, 88, 19, 64, 72, 0, 6, 2, 95, 5, 107, 0, 0, 0, 0, 9, 198, 65, 81, 5, 72, 19, 64, 76, 0, 0, 6, 2, 95, 15, 108, 0, 6, 195, 76, 240, 128, 102, 0, 12, 68, 64, 17, 88, 4, 48, 35, 36, 89, 35, 0, 0, 16, 69, 4, 194, 83, 60, 224, 130, 55, 6, 37, 87, 130, 66, 0, 101, 0, 9, 198, 88, 19, 133, 77, 48, 64, 21, 0, 6, 195, 81, 80, 64, 76, 0, 14, 68, 64, 242, 78, 80, 48, 6, 39, 37, 50, 47, 0, 101, 8, 133, 16, 195, 180, 4, 5, 76, 0, 0, 17, 70, 76, 48, 78, 56, 84, 128, 87, 49, 6, 107, 50, 130, 34, 0, 101, 0, 0, 6, 195, 80, 83, 147, 72, 0, 0, 0, 0, 15, 68, 76, 85, 21, 64, 87, 6, 107, 47, 6, 130, 48, 0, 101, 0, 0, 13, 4, 95, 226, 136, 146, 63, 6, 36, 50, 109, 87, 0, 0, 0, 13, 68, 76, 182, 80, 20, 87, 49, 6, 115, 48, 0, 102, 14, 68, 76, 182, 80, 20, 87, 49, 6, 35, 37, 48, 0, 101, 0, 16, 69, 4, 51, 210, 16, 240, 130, 49, 6, 108, 34, 70, 109, 0, 36, 0, 0, 15, 2, 95, 35, 49, 4, 35, 34, 73, 37, 50, 6, 112, 0, 102, 16, 2, 95, 35, 49, 4, 35, 34, 70, 37, 50, 6, 35, 55, 0, 101, 0, 24, 2, 95, 34, 6, 35, 69, 51, 37, 38, 6, 35, 87, 48, 130, 15, 70, 6, 40, 48, 55, 130, 136, 0, 11, 2, 95, 34, 6, 35, 87, 48, 130, 136, 0, 0, 16, 2, 95, 33, 4, 36, 87, 49, 55, 130, 63, 35, 87, 6, 128, 0, 0, 0, 11, 67, 61, 99, 192, 6, 39, 82, 40, 0, 101, 16, 2, 95, 39, 130, 48, 6, 108, 87, 47, 51, 39, 81, 109, 0, 102, 17, 2, 95, 39, 35, 48, 6, 108, 87, 47, 34, 4, 39, 81, 110, 0, 101, 0, 6, 195, 80, 85, 83, 76, 7, 2, 95, 38, 6, 36, 0, 0, 0, 6, 195, 17, 83, 65, 72, 12, 2, 95, 36, 87, 4, 37, 81, 51, 6, 128, 0, 0, 6, 195, 17, 83, 64, 72, 0, 14, 68, 28, 208, 73, 48, 88, 36, 63, 6, 116, 55, 0, 102, 15, 68, 28, 208, 73, 48, 79, 4, 36, 63, 6, 116, 55, 0, 101, 15, 2, 95, 42, 130, 87, 47, 36, 16, 6, 37, 87, 49, 109, 0, 16, 4, 95, 3, 1, 16, 63, 115, 6, 40, 87, 49, 40, 55, 109, 0, 0, 8, 197, 17, 35, 199, 5, 48, 20, 20, 2, 95, 41, 81, 4, 107, 89, 130, 48, 35, 16, 6, 116, 66, 47, 36, 86, 110, 0, 0, 20, 2, 95, 40, 4, 35, 69, 51, 37, 48, 35, 16, 6, 116, 66, 47, 36, 86, 110, 0, 0, 10, 2, 95, 47, 69, 6, 35, 98, 130, 0, 0, 0, 10, 2, 95, 45, 6, 37, 81, 116, 66, 0, 0, 16, 70, 45, 37, 69, 28, 84, 128, 49, 51, 6, 37, 88, 36, 34, 0, 13, 2, 95, 44, 82, 6, 37, 34, 79, 40, 55, 130, 0, 0, 6, 195, 80, 84, 128, 72, 6, 195, 53, 36, 192, 24, 10, 2, 95, 51, 47, 51, 6, 36, 136, 0, 0, 9, 2, 95, 50, 70, 6, 118, 136, 0, 0, 24, 73, 61, 4, 5, 56, 129, 73, 52, 84, 128, 11, 6, 108, 48, 13, 50, 105, 4, 115, 63, 35, 34, 0, 9, 2, 95, 49, 6, 126, 66, 0, 102, 9, 2, 95, 49, 6, 40, 63, 0, 101, 0, 15, 70, 53, 81, 76, 48, 84, 128, 63, 6, 37, 55, 36, 34, 0, 11, 67, 80, 85, 133, 47, 36, 82, 110, 0, 73, 11, 2, 95, 48, 86, 6, 107, 16, 109, 0, 102, 11, 2, 95, 48, 86, 6, 107, 16, 40, 0, 101, 0, 11, 2, 95, 55, 87, 6, 107, 74, 110, 0, 102, 11, 2, 95, 55, 87, 6, 107, 47, 110, 0, 101, 0, 9, 2, 95, 54, 87, 6, 116, 136, 0, 0, 11, 2, 95, 53, 87, 6, 37, 66, 49, 40, 0, 0, 13, 2, 95, 52, 49, 58, 6, 35, 47, 51, 40, 0, 102, 13, 2, 95, 52, 49, 58, 6, 35, 47, 34, 40, 0, 101, 0, 21, 2, 95, 59, 48, 4, 39, 66, 47, 40, 10, 37, 82, 6, 37, 34, 79, 40, 55, 130, 0, 0, 16, 2, 95, 58, 70, 4, 118, 87, 48, 6, 39, 66, 47, 40, 87, 0, 0, 10, 2, 95, 57, 50, 6, 108, 82, 110, 0, 0, 9, 2, 95, 56, 6, 118, 47, 40, 0, 0, 18, 2, 95, 63, 4, 37, 66, 47, 36, 99, 4, 39, 79, 35, 87, 6, 128, 0, 0, 6, 195, 81, 80, 83, 76, 10, 2, 95, 62, 63, 115, 6, 108, 34, 0, 0, 8, 197, 80, 20, 5, 80, 80, 21, 11, 2, 95, 61, 37, 79, 58, 6, 112, 0, 102, 12, 2, 95, 61, 37, 79, 58, 6, 35, 55, 0, 101, 0, 11, 2, 95, 60, 63, 36, 50, 6, 108, 34, 0, 0, 6, 195, 24, 22, 128, 76, 0, 17, 70, 88, 243, 11, 52, 19, 142, 81, 6, 108, 55, 49, 63, 35, 50, 0, 21, 68, 16, 84, 196, 20, 70, 6, 36, 87, 73, 37, 49, 133, 0, 102, 81, 113, 117, 101, 32, 8, 196, 16, 84, 196, 20, 102, 72, 0, 0, 0, 0, 15, 6, 13, 195, 188, 12, 5, 18, 63, 6, 37, 55, 36, 34, 0, 0, 0, 0, 0, 0, 0, 8, 133, 16, 18, 195, 178, 19, 72, 0, 6, 195, 20, 192, 64, 76, 6, 195, 36, 48, 192, 17, 0, 0, 0, 18, 70, 52, 83, 143, 72, 84, 192, 63, 36, 50, 6, 108, 16, 37, 87, 0, 102, 0, 6, 195, 85, 48, 128, 17, 6, 195, 56, 32, 64, 17, 0, 14, 68, 64, 18, 78, 80, 48, 6, 35, 37, 50, 47, 0, 101, 11, 67, 8, 16, 203, 69, 6, 107, 49, 0, 101, 0, 11, 67, 4, 192, 78, 6, 35, 55, 13, 50, 0, 0, 9, 198, 65, 81, 5, 52, 244, 192, 76, 9, 198, 24, 22, 133, 52, 244, 192, 76, 9, 198, 80, 149, 133, 52, 244, 192, 72, 9, 198, 21, 53, 1, 52, 244, 192, 72, 0, 11, 67, 20, 193, 64, 6, 36, 55, 110, 0, 76, 0, 16, 70, 72, 144, 200, 5, 33, 0, 99, 6, 37, 89, 130, 34, 70, 0, 13, 4, 95, 4, 15, 20, 48, 6, 39, 66, 47, 109, 0, 0, 0, 0, 6, 195, 20, 49, 192, 17, 18, 2, 95, 91, 4, 35, 69, 51, 37, 49, 39, 58, 89, 6, 36, 74, 37, 0, 0, 6, 195, 20, 192, 83, 76, 0, 14, 69, 20, 194, 88, 37, 32, 36, 55, 37, 89, 37, 34, 0, 0, 7, 66, 88, 144, 82, 37, 0, 0, 16, 2, 95, 95, 87, 4, 40, 69, 55, 37, 65, 6, 35, 70, 40, 0, 0, 19, 2, 95, 94, 87, 4, 37, 34, 49, 126, 66, 81, 55, 6, 107, 49, 87, 40, 0, 0, 14, 69, 60, 227, 9, 56, 80, 39, 66, 55, 115, 66, 0, 102, 18, 2, 95, 93, 81, 4, 107, 89, 130, 49, 39, 58, 89, 6, 36, 74, 37, 0, 0, 21, 2, 95, 92, 69, 4, 35, 99, 130, 4, 37, 66, 82, 36, 34, 74, 6, 37, 70, 130, 0, 0, 6, 195, 24, 34, 64, 17, 0, 6, 195, 20, 193, 83, 76, 0, 16, 69, 4, 115, 211, 80, 240, 130, 79, 6, 39, 87, 47, 109, 0, 102, 0, 11, 2, 95, 96, 79, 51, 6, 35, 82, 37, 0, 0, 0, 7, 132, 16, 18, 195, 160, 72, 0, 16, 7, 13, 195, 188, 12, 12, 5, 18, 63, 6, 37, 55, 36, 34, 0, 0, 0, 0, 0, 0, 13, 4, 95, 7, 18, 22, 79, 51, 6, 35, 82, 37, 0, 0, 16, 67, 76, 244, 192, 4, 107, 87, 57, 4, 108, 6, 107, 87, 0, 101, 0, 0, 0, 18, 70, 92, 147, 132, 61, 116, 192, 58, 6, 37, 66, 70, 39, 58, 87, 0, 102, 20, 70, 92, 147, 132, 61, 116, 192, 58, 6, 37, 66, 70, 6, 39, 40, 12, 86, 0, 101, 0, 10, 199, 21, 53, 9, 88, 83, 79, 76, 72, 6, 195, 56, 20, 192, 72, 0, 0, 0, 9, 198, 80, 84, 133, 52, 244, 192, 72, 9, 198, 76, 84, 133, 52, 244, 192, 72, 7, 132, 16, 18, 195, 178, 72, 0, 0, 6, 195, 17, 83, 147, 72, 12, 67, 8, 147, 211, 69, 6, 37, 4, 108, 89, 0, 0, 0, 0, 15, 2, 95, 123, 4, 35, 69, 51, 37, 89, 6, 35, 82, 37, 0, 13, 4, 95, 4, 9, 1, 47, 51, 6, 36, 63, 130, 0, 0, 0, 15, 69, 52, 83, 8, 61, 32, 63, 36, 61, 6, 108, 34, 0, 104, 16, 69, 52, 83, 8, 61, 32, 63, 36, 55, 57, 6, 108, 34, 0, 102, 0, 16, 70, 60, 97, 140, 36, 225, 64, 108, 81, 55, 6, 115, 66, 0, 102, 6, 194, 84, 208, 72, 34, 0, 0, 13, 68, 64, 245, 197, 72, 48, 6, 112, 130, 44, 0, 101, 9, 2, 95, 126, 74, 6, 114, 0, 102, 10, 2, 95, 126, 47, 6, 37, 55, 0, 101, 0, 8, 197, 64, 84, 132, 20, 208, 20, 15, 2, 95, 125, 81, 4, 107, 89, 130, 89, 6, 35, 82, 37, 0, 0, 20, 2, 95, 124, 69, 4, 35, 99, 130, 82, 4, 36, 34, 74, 37, 49, 6, 112, 0, 102, 21, 2, 95, 124, 69, 4, 35, 99, 130, 82, 4, 36, 34, 74, 37, 49, 6, 35, 55, 0, 101, 0, 19, 70, 24, 148, 133, 24, 246, 0, 81, 6, 35, 37, 13, 81, 108, 49, 87, 0, 102, 20, 70, 24, 148, 133, 24, 246, 0, 81, 6, 35, 37, 130, 34, 81, 108, 49, 87, 0, 101, 0, 13, 67, 40, 21, 211, 73, 6, 35, 40, 12, 86, 0, 101, 0, 0, 0, 0, 0, 16, 69, 4, 48, 197, 77, 48, 6, 35, 49, 87, 4, 107, 87, 0, 101, 0, 0, 0, 0, 0, 0, 0, 15, 68, 8, 194, 78, 16, 69, 55, 6, 35, 37, 50, 70, 0, 101, 0, 0, 0, 12, 67, 21, 48, 192, 6, 107, 87, 49, 122, 0, 103, 11, 67, 21, 48, 192, 6, 107, 87, 49, 0, 102, 0, 0, 0, 6, 195, 64, 241, 5, 76, 0, 0, 0, 0, 18, 70, 88, 84, 130, 21, 65, 64, 82, 36, 34, 69, 6, 36, 74, 37, 0, 102, 14, 4, 95, 35, 51, 50, 89, 48, 6, 35, 87, 109, 0, 101, 14, 4, 95, 35, 51, 50, 36, 87, 48, 6, 35, 87, 109, 0, 0, 0, 0, 20, 8, 19, 195, 173, 13, 2, 15, 12, 15, 87, 6, 37, 66, 69, 39, 55, 109, 0, 104, 19, 8, 19, 195, 173, 13, 2, 15, 12, 15, 87, 6, 37, 63, 69, 39, 55, 109, 0, 0, 0, 0, 11, 5, 5, 46, 21, 46, 1, 107, 40, 35, 0, 0, 0, 16, 70, 4, 32, 67, 5, 130, 64, 35, 69, 35, 49, 35, 89, 110, 0, 0, 0, 21, 72, 32, 82, 83, 20, 224, 133, 72, 112, 105, 6, 115, 86, 107, 50, 69, 36, 34, 79, 0, 13, 68, 52, 18, 79, 72, 63, 115, 6, 108, 34, 0, 102, 15, 68, 52, 18, 79, 72, 63, 4, 130, 57, 6, 108, 44, 0, 101, 0, 0, 17, 70, 61, 85, 12, 60, 242, 192, 4, 112, 47, 55, 6, 40, 49, 0, 102, 18, 70, 61, 85, 12, 60, 242, 192, 6, 35, 40, 47, 55, 6, 40, 49, 0, 101, 0, 19, 70, 88, 84, 130, 21, 65, 83, 82, 36, 34, 69, 6, 36, 74, 37, 87, 0, 102, 0, 12, 68, 52, 18, 76, 76, 63, 6, 116, 55, 87, 0, 20, 70, 21, 132, 12, 61, 33, 82, 36, 49, 87, 48, 55, 6, 108, 16, 36, 34, 0, 102, 22, 70, 21, 132, 12, 61, 33, 82, 4, 36, 49, 87, 48, 55, 6, 108, 12, 16, 130, 44, 0, 101, 0, 0, 0, 0, 0, 0, 19, 70, 36, 229, 5, 72, 225, 84, 37, 66, 47, 36, 34, 50, 6, 107, 47, 0, 102, 13, 67, 21, 52, 197, 6, 36, 87, 37, 0, 102, 76, 34, 0, 6, 195, 37, 52, 192, 17, 0, 0, 0, 11, 67, 21, 52, 193, 6, 107, 87, 130, 0, 76, 0, 0, 6, 195, 13, 5, 67, 17, 0, 0, 12, 67, 76, 149, 5, 87, 6, 115, 74, 37, 0, 102, 11, 67, 76, 149, 5, 87, 6, 115, 47, 0, 101, 13, 67, 76, 20, 9, 87, 4, 35, 48, 6, 37, 0, 101, 9, 198, 88, 147, 204, 21, 64, 64, 21, 0, 6, 195, 13, 5, 64, 17, 0, 0, 0, 26, 10, 20, 5, 12, 5, 13, 195, 179, 22, 5, 12, 47, 4, 107, 55, 4, 107, 63, 6, 108, 82, 107, 55, 0, 101, 9, 198, 80, 149, 133, 77, 65, 64, 72, 0, 0, 12, 67, 12, 20, 19, 49, 6, 35, 48, 87, 0, 101, 7, 196, 24, 244, 211, 20, 21, 13, 68, 16, 84, 211, 20, 70, 6, 36, 87, 110, 0, 76, 0, 0, 0, 0, 12, 68, 44, 193, 73, 56, 49, 55, 6, 115, 50, 0, 16, 68, 21, 53, 5, 76, 6, 36, 87, 74, 37, 87, 0, 102, 76, 34, 0, 15, 69, 21, 48, 193, 64, 80, 89, 49, 6, 116, 48, 110, 0, 101, 0, 11, 67, 52, 86, 1, 63, 6, 36, 89, 130, 0, 0, 0, 7, 196, 24, 244, 212, 20, 72, 0, 15, 69, 28, 243, 199, 48, 80, 79, 6, 40, 79, 39, 55, 0, 102, 16, 69, 28, 243, 199, 48, 80, 79, 6, 40, 12, 79, 130, 55, 0, 101, 0, 0, 9, 198, 80, 149, 133, 77, 65, 83, 72, 0, 0, 0, 0, 0, 0, 16, 69, 56, 244, 211, 61, 48, 50, 6, 108, 87, 109, 87, 0, 102, 76, 0, 0, 7, 195, 84, 208, 64, 72, 34, 0, 6, 195, 64, 242, 83, 102, 0, 0, 0, 9, 134, 5, 19, 20, 195, 163, 15, 72, 0, 11, 67, 52, 86, 15, 63, 6, 36, 89, 109, 0, 0, 19, 70, 16, 146, 139, 77, 68, 129, 70, 6, 37, 57, 49, 87, 47, 34, 132, 12, 0, 0, 0, 0, 7, 196, 21, 53, 15, 84, 72, 0, 0, 11, 67, 52, 86, 9, 63, 36, 89, 6, 37, 0, 6, 195, 36, 81, 69, 17, 0, 0, 14, 68, 28, 244, 212, 60, 79, 6, 108, 87, 47, 109, 0, 36, 0, 14, 69, 53, 81, 76, 21, 32, 63, 6, 37, 55, 36, 34, 0, 0, 0, 0, 0, 7, 132, 19, 195, 163, 15, 72, 0, 0, 0, 7, 196, 21, 53, 1, 72, 72, 0, 14, 70, 72, 245, 83, 76, 80, 85, 51, 40, 87, 6, 39, 0, 0, 13, 67, 32, 243, 69, 105, 6, 39, 58, 63, 37, 0, 102, 11, 67, 32, 243, 69, 6, 39, 63, 110, 0, 101, 0, 20, 71, 52, 84, 211, 20, 225, 197, 72, 63, 6, 107, 87, 130, 50, 73, 130, 44, 0, 101, 18, 70, 52, 83, 8, 61, 33, 83, 63, 36, 61, 6, 108, 16, 37, 87, 0, 104, 19, 70, 52, 83, 8, 61, 33, 83, 63, 36, 55, 57, 6, 108, 16, 37, 87, 0, 102, 0, 0, 0, 0, 0, 0, 8, 197, 80, 83, 132, 21, 48, 72, 0, 8, 133, 6, 1, 195, 167, 15, 76, 0, 0, 0, 0, 0, 9, 134, 19, 5, 18, 195, 163, 15, 72, 0, 14, 68, 76, 208, 82, 80, 87, 63, 6, 35, 34, 47, 0, 101, 7, 196, 40, 241, 207, 76, 20, 0, 0, 0, 21, 71, 65, 80, 140, 37, 50, 5, 72, 48, 6, 130, 69, 55, 4, 37, 89, 130, 44, 0, 101, 10, 199, 8, 244, 130, 60, 193, 84, 4, 21, 0, 0, 0, 0, 7, 195, 52, 85, 64, 76, 34, 6, 195, 4, 68, 204, 17, 0, 7, 195, 84, 208, 83, 72, 34, 0, 0, 0, 0, 18, 7, 3, 15, 13, 5, 195, 167, 15, 49, 39, 63, 6, 107, 87, 109, 0, 36, 0, 17, 70, 76, 83, 22, 4, 113, 77, 87, 113, 82, 6, 35, 88, 116, 66, 0, 8, 197, 69, 80, 78, 16, 240, 102, 0, 9, 198, 64, 241, 5, 72, 82, 64, 79, 0, 0, 0, 0, 0, 0, 6, 195, 52, 85, 83, 76, 0, 6, 195, 160, 0, 3, 35, 0, 8, 2, 115, 32, 3, 115, 0, 4, 2, 109, 3, 127, 0, 2, 110, 0, 109, 2, 25, 3, 127, 63, 0, 110, 104, 2, 17, 65, 3, 127, 65, 0, 110, 2, 25, 3, 127, 66, 0, 7, 6, 195, 161, 0, 4, 3, 7, 35, 0, 2, 105, 17, 67, 25, 0, 2, 117, 17, 67, 25, 0, 4, 117, 3, 7, 112, 0, 117, 2, 115, 0, 4, 105, 3, 7, 115, 0, 105, 2, 115, 0, 121, 0, 108, 5, 1, 3, 7, 132, 55, 0, 7, 6, 195, 162, 0, 4, 2, 109, 3, 7, 127, 0, 2, 110, 0, 109, 2, 25, 3, 7, 127, 63, 0, 110, 104, 3, 7, 127, 65, 0, 110, 2, 25, 3, 7, 127, 66, 0, 3, 7, 130, 0, 7, 6, 195, 163, 0, 3, 127, 0, 111, 3, 128, 0, 7, 6, 195, 169, 0, 4, 3, 7, 107, 0, 2, 105, 17, 67, 25, 0, 2, 117, 17, 67, 25, 0, 121, 3, 7, 116, 0, 4, 109, 2, 32, 3, 7, 116, 66, 0, 109, 2, 115, 32, 0, 110, 2, 32, 0, 110, 2, 115, 32, 0, 4, 105, 3, 7, 117, 0, 105, 2, 115, 0, 4, 117, 3, 7, 135, 0, 117, 2, 115, 0, 7, 6, 195, 170, 0, 3, 7, 36, 0, 110, 104, 3, 7, 36, 65, 0, 109, 2, 17, 67, 3, 7, 116, 63, 0, 4, 109, 2, 32, 3, 7, 116, 66, 0, 109, 2, 32, 0, 110, 2, 25, 0, 7, 6, 195, 173, 0, 4, 3, 7, 37, 0, 2, 109, 0, 2, 110, 0, 109, 2, 17, 67, 3, 7, 37, 63, 0, 110, 104, 3, 7, 37, 65, 0, 4, 109, 2, 32, 3, 7, 37, 66, 0, 110, 2, 25, 0, 7, 6, 195, 179, 0, 4, 3, 7, 108, 0, 2, 105, 17, 67, 25, 0, 117, 3, 7, 108, 58, 0, 4, 105, 3, 7, 134, 0, 105, 2, 115, 0, 121, 0, 7, 6, 195, 180, 0, 3, 7, 39, 0, 109, 2, 17, 67, 3, 7, 39, 63, 0, 110, 104, 3, 7, 39, 65, 0, 4, 109, 2, 32, 3, 7, 39, 66, 0, 110, 2, 25, 0, 7, 6, 195, 181, 0, 3, 125, 0, 101, 3, 125, 57, 0, 7, 6, 195, 186, 0, 3, 7, 40, 0, 109, 2, 17, 67, 3, 7, 126, 63, 0, 110, 104, 3, 7, 126, 65, 0, 4, 109, 2, 32, 3, 7, 126, 66, 0, 109, 5, 4, 2, 17, 67, 0, 110, 2, 25, 0, 7, 6, 97, 0, 5, 1, 2, 108, 25, 3, 4, 132, 0, 4, 2, 114, 32, 3, 6, 35, 0, 5, 1, 2, 122, 32, 0, 8, 2, 32, 31, 0, 99, 195, 167, 5, 1, 1, 17, 67, 3, 6, 35, 6, 87, 0, 5, 1, 2, 108, 32, 3, 6, 132, 0, 5, 1, 1, 112, 2, 100, 32, 3, 8, 107, 0, 109, 2, 32, 3, 8, 127, 66, 0, 109, 2, 32, 3, 8, 128, 0, 4, 1, 10, 2, 32, 3, 8, 130, 0, 1, 10, 2, 115, 32, 0, 5, 1, 2, 32, 0, 5, 1, 2, 115, 32, 0, 4, 1, 10, 2, 32, 97, 3, 8, 131, 0, 1, 10, 2, 32, 195, 160, 0, 5, 1, 2, 32, 97, 0, 5, 1, 2, 32, 195, 160, 0, 4, 3, 35, 0, 2, 105, 17, 67, 25, 0, 2, 105, 117, 32, 0, 2, 108, 104, 12, 0, 2, 117, 17, 67, 25, 0, 8, 2, 32, 0, 4, 108, 5, 2, 2, 25, 3, 112, 0, 111, 2, 32, 0, 117, 0, 117, 2, 115, 0, 4, 105, 3, 115, 0, 105, 2, 115, 0, 121, 0, 4, 2, 109, 3, 127, 0, 2, 110, 0, 109, 2, 17, 67, 3, 127, 63, 0, 110, 104, 2, 17, 65, 3, 127, 65, 0, 4, 109, 5, 4, 2, 17, 67, 3, 127, 66, 0, 110, 2, 25, 12, 0, 4, 2, 17, 67, 17, 67, 32, 3, 130, 0, 2, 17, 67, 32, 0, 2, 109, 17, 65, 21, 0, 2, 109, 17, 65, 114, 32, 0, 2, 110, 17, 65, 21, 0, 2, 110, 17, 65, 114, 32, 0, 7, 6, 98, 0, 2, 98, 3, 0, 4, 3, 69, 0, 5, 3, 2, 115, 0, 5, 3, 2, 32, 17, 67, 3, 69, 10, 0, 8, 2, 32, 3, 69, 36, 0, 5, 3, 2, 17, 66, 3, 69, 122, 0, 7, 6, 99, 0, 5, 1, 2, 99, 3, 0, 116, 5, 1, 1, 17, 65, 3, 47, 0, 4, 3, 49, 0, 5, 3, 2, 115, 0, 5, 3, 2, 116, 0, 107, 0, 5, 3, 2, 32, 17, 67, 3, 49, 10, 0, 116, 5, 1, 1, 97, 116, 110, 111, 99, 2, 17, 65, 3, 49, 47, 0, 5, 3, 2, 17, 66, 3, 49, 122, 0, 4, 2, 17, 71, 3, 87, 0, 195, 167, 5, 1, 1, 17, 65, 0, 8, 2, 32, 3, 87, 36, 0, 104, 3, 89, 0, 7, 6, 100, 0, 2, 100, 3, 0, 3, 70, 0, 5, 3, 2, 32, 17, 67, 3, 70, 10, 0, 8, 2, 32, 3, 70, 36, 0, 4, 5, 2, 2, 101, 32, 3, 73, 0, 5, 2, 2, 105, 0, 5, 2, 2, 195, 173, 0, 5, 3, 2, 17, 66, 3, 73, 122, 0, 7, 6, 101, 0, 4, 5, 1, 1, 100, 2, 110, 17, 67, 17, 65, 17, 65, 3, 4, 36, 0, 5, 1, 1, 100, 2, 110, 17, 67, 17, 65, 17, 67, 17, 65, 0, 5, 1, 1, 100, 2, 110, 17, 67, 17, 65, 17, 67, 17, 67, 17, 65, 0, 4, 5, 1, 1, 17, 67, 2, 99, 17, 67, 3, 4, 107, 0, 5, 1, 1, 112, 105, 104, 2, 114, 0, 5, 1, 1, 112, 117, 115, 2, 114, 0, 5, 1, 1, 114, 2, 108, 118, 97, 0, 5, 1, 1, 118, 2, 108, 32, 0, 5, 1, 8, 109, 2, 103, 97, 0, 5, 1, 8, 116, 110, 105, 2, 114, 110, 0, 5, 1, 1, 17, 67, 2, 111, 3, 6, 37, 0, 4, 5, 1, 1, 108, 2, 116, 97, 3, 6, 107, 0, 5, 1, 1, 110, 2, 116, 0, 5, 1, 2, 108, 32, 0, 5, 1, 2, 108, 97, 32, 0, 99, 195, 167, 5, 1, 1, 17, 67, 3, 6, 107, 6, 87, 0, 4, 5, 2, 1, 108, 10, 2, 32, 17, 65, 24, 3, 8, 37, 0, 5, 2, 1, 114, 10, 2, 32, 17, 65, 24, 0, 4, 2, 32, 3, 8, 110, 0, 2, 115, 32, 0, 4, 109, 2, 32, 3, 8, 116, 66, 0, 109, 2, 115, 32, 0, 110, 2, 32, 0, 110, 2, 115, 32, 0, 4, 5, 1, 2, 32, 105, 24, 3, 8, 133, 0, 5, 2, 2, 32, 17, 65, 24, 0, 4, 3, 36, 0, 1, 100, 101, 2, 114, 17, 65, 109, 32, 0, 1, 100, 111, 112, 2, 114, 17, 65, 32, 0, 1, 104, 2, 103, 17, 65, 32, 0, 1, 104, 2, 103, 17, 65, 109, 32, 0, 1, 110, 17, 65, 2, 116, 17, 65, 32, 0, 1, 114, 2, 99, 104, 111, 32, 0, 1, 116, 2, 118, 101, 32, 0, 1, 122, 97, 103, 2, 116, 97, 32, 0, 2, 105, 17, 67, 25, 0, 2, 108, 104, 12, 0, 2, 108, 111, 32, 0, 2, 117, 17, 67, 25, 0, 2, 118, 105, 32, 0, 2, 118, 195, 170, 32, 0, 101, 5, 2, 1, 114, 112, 2, 110, 3, 36, 36, 0, 101, 120, 8, 114, 2, 17, 65, 3, 36, 36, 86, 0, 110, 104, 3, 36, 65, 0, 4, 5, 1, 1, 17, 67, 2, 97, 3, 37, 0, 5, 1, 1, 17, 67, 2, 195, 163, 0, 5, 1, 1, 17, 67, 2, 195, 186, 0, 5, 1, 2, 101, 0, 5, 1, 8, 2, 102, 0, 5, 1, 8, 110, 2, 110, 104, 117, 0, 101, 5, 2, 0, 5, 1, 1, 163, 195, 17, 67, 3, 57, 0, 115, 5, 1, 8, 2, 17, 67, 21, 21, 3, 89, 0, 4, 1, 98, 105, 2, 114, 17, 65, 32, 3, 107, 0, 1, 98, 105, 2, 114, 17, 65, 109, 32, 0, 1, 100, 2, 114, 17, 65, 32, 0, 1, 100, 2, 114, 17, 65, 109, 32, 0, 1, 105, 2, 114, 32, 0, 1, 106, 2, 116, 17, 65, 32, 0, 1, 106, 2, 116, 17, 65, 109, 32, 0, 1, 109, 2, 114, 17, 65, 32, 0, 1, 112, 115, 2, 114, 17, 65, 32, 0, 1, 112, 115, 2, 114, 17, 65, 109, 32, 0, 1, 115, 21, 2, 114, 17, 65, 32, 0, 1, 115, 21, 2, 114, 17, 65, 109, 32, 0, 1, 115, 21, 2, 114, 32, 0, 1, 117, 2, 114, 32, 0, 1, 118, 2, 108, 104, 17, 65, 32, 0, 1, 118, 105, 2, 114, 17, 65, 109, 32, 0, 2, 98, 101, 32, 0, 2, 98, 101, 109, 32, 0, 2, 99, 97, 32, 0, 2, 99, 101, 32, 0, 2, 99, 101, 109, 32, 0, 2, 99, 104, 17, 65, 32, 0, 2, 99, 104, 17, 65, 109, 32, 0, 2, 99, 108, 17, 65, 32, 0, 2, 99, 108, 17, 65, 109, 32, 0, 2, 99, 111, 32, 0, 2, 99, 116, 17, 65, 32, 0, 2, 99, 116, 17, 65, 109, 32, 0, 2, 100, 101, 32, 0, 2, 100, 101, 109, 32, 0, 2, 102, 97, 32, 0, 2, 103, 17, 65, 32, 0, 2, 103, 17, 65, 109, 32, 0, 2, 103, 114, 17, 65, 32, 0, 2, 103, 114, 17, 65, 109, 32, 0, 2, 103, 117, 101, 32, 0, 2, 103, 117, 101, 109, 32, 0, 2, 108, 17, 65, 32, 0, 2, 108, 17, 65, 109, 32, 0, 2, 114, 103, 17, 65, 32, 0, 2, 114, 103, 17, 65, 109, 32, 0, 2, 114, 110, 17, 65, 32, 0, 2, 114, 110, 17, 65, 109, 32, 0, 2, 114, 114, 17, 65, 32, 0, 2, 114, 114, 17, 65, 109, 32, 0, 2, 114, 114, 17, 65, 115, 32, 0, 2, 114, 115, 17, 65, 32, 0, 2, 114, 115, 17, 65, 109, 32, 0, 2, 114, 116, 17, 65, 32, 0, 2, 114, 116, 17, 65, 109, 32, 0, 2, 114, 118, 17, 65, 32, 0, 2, 114, 118, 17, 65, 109, 32, 0, 2, 115, 101, 32, 0, 2, 115, 101, 109, 32, 0, 2, 115, 115, 17, 65, 32, 0, 2, 115, 115, 17, 65, 109, 32, 0, 2, 115, 116, 17, 65, 32, 0, 2, 115, 116, 17, 65, 109, 32, 0, 2, 115, 116, 114, 17, 65, 32, 0, 2, 116, 17, 65, 32, 0, 2, 116, 17, 65, 109, 32, 0, 2, 118, 17, 65, 32, 0, 2, 118, 17, 65, 109, 32, 0, 2, 120, 17, 65, 32, 0, 2, 120, 17, 65, 109, 32, 0, 2, 120, 32, 0, 2, 195, 167, 17, 65, 32, 0, 2, 195, 167, 17, 65, 109, 32, 0, 5, 2, 8, 110, 2, 116, 0, 8, 2, 32, 0, 4, 5, 1, 1, 99, 2, 114, 101, 97, 3, 110, 0, 5, 1, 1, 100, 2, 17, 67, 17, 65, 17, 65, 0, 5, 1, 1, 100, 2, 17, 67, 17, 65, 17, 67, 17, 65, 17, 65, 0, 5, 1, 1, 100, 2, 17, 67, 17, 65, 17, 67, 17, 65, 17, 67, 0, 5, 1, 1, 100, 2, 17, 67, 17, 65, 17, 67, 17, 67, 0, 5, 1, 1, 100, 2, 17, 67, 17, 67, 17, 65, 17, 65, 0, 5, 1, 1, 100, 2, 17, 67, 17, 67, 17, 65, 17, 67, 17, 65, 0, 5, 1, 1, 100, 2, 17, 67, 17, 67, 17, 65, 17, 67, 17, 67, 17, 65, 0, 5, 1, 1, 100, 2, 102, 105, 99, 105, 0, 5, 1, 1, 112, 2, 115, 115, 111, 97, 0, 5, 1, 1, 114, 2, 99, 111, 114, 0, 5, 1, 1, 114, 2, 108, 117, 122, 0, 5, 1, 1, 114, 2, 115, 109, 117, 110, 103, 0, 5, 1, 1, 114, 2, 115, 115, 0, 5, 1, 1, 114, 2, 118, 101, 108, 0, 5, 1, 1, 114, 2, 118, 111, 108, 118, 0, 5, 1, 1, 114, 112, 2, 99, 105, 115, 0, 5, 1, 1, 114, 112, 2, 102, 0, 5, 1, 8, 100, 2, 102, 105, 110, 105, 0, 5, 1, 8, 100, 2, 115, 108, 105, 103, 0, 5, 1, 8, 100, 2, 115, 108, 111, 99, 0, 5, 1, 8, 102, 2, 99, 104, 0, 5, 1, 8, 102, 2, 114, 114, 97, 109, 101, 110, 116, 97, 0, 5, 1, 8, 112, 2, 114, 99, 101, 110, 116, 97, 103, 0, 5, 1, 8, 112, 2, 115, 113, 117, 0, 5, 1, 8, 114, 2, 99, 105, 99, 108, 0, 5, 1, 8, 116, 2, 114, 109, 105, 110, 0, 5, 1, 8, 118, 2, 108, 111, 99, 105, 0, 4, 117, 3, 113, 0, 117, 2, 115, 0, 4, 105, 3, 116, 0, 105, 2, 115, 0, 121, 0, 109, 2, 17, 67, 3, 116, 63, 0, 110, 2, 25, 3, 116, 66, 0, 108, 5, 2, 2, 25, 3, 135, 0, 7, 6, 102, 0, 2, 102, 3, 0, 8, 2, 32, 3, 6, 107, 81, 36, 0, 3, 81, 0, 5, 3, 2, 32, 17, 67, 3, 81, 10, 0, 5, 3, 2, 17, 66, 3, 81, 122, 0, 5, 1, 8, 2, 32, 3, 107, 81, 0, 5, 1, 8, 2, 32, 31, 3, 107, 81, 38, 0, 7, 6, 103, 0, 2, 103, 3, 0, 4, 3, 79, 0, 117, 2, 17, 71, 0, 117, 5, 1, 1, 110, 97, 109, 2, 101, 105, 0, 117, 5, 1, 2, 195, 169, 109, 32, 0, 5, 3, 2, 32, 17, 67, 3, 79, 10, 0, 5, 1, 8, 2, 32, 3, 79, 36, 0, 117, 5, 1, 1, 110, 2, 17, 65, 3, 79, 58, 0, 117, 101, 110, 5, 1, 2, 17, 67, 3, 79, 58, 6, 116, 66, 0, 5, 3, 2, 17, 66, 3, 79, 122, 0, 2, 17, 71, 3, 88, 0, 4, 5, 1, 8, 2, 32, 31, 3, 88, 36, 0, 8, 2, 32, 0, 7, 6, 104, 0, 3, 0, 8, 2, 32, 3, 35, 79, 6, 35, 0, 7, 6, 105, 0, 4, 2, 17, 65, 32, 3, 6, 37, 0, 2, 32, 0, 2, 97, 109, 32, 0, 5, 1, 8, 2, 110, 116, 101, 114, 110, 0, 4, 110, 103, 5, 1, 1, 21, 2, 32, 3, 21, 0, 110, 103, 115, 5, 1, 1, 21, 2, 32, 0, 4, 3, 37, 0, 1, 108, 17, 67, 0, 1, 114, 17, 67, 0, 2, 108, 104, 12, 0, 2, 111, 0, 2, 111, 17, 67, 25, 0, 2, 117, 17, 67, 25, 0, 8, 2, 32, 0, 109, 2, 17, 67, 3, 37, 63, 0, 110, 104, 3, 37, 65, 0, 4, 109, 2, 32, 3, 37, 66, 0, 109, 5, 4, 2, 17, 67, 0, 110, 2, 17, 67, 0, 110, 2, 103, 0, 110, 2, 107, 0, 4, 1, 17, 67, 17, 67, 161, 195, 2, 17, 65, 32, 3, 57, 0, 1, 17, 67, 17, 67, 162, 195, 2, 17, 65, 32, 0, 1, 17, 67, 17, 67, 169, 195, 2, 17, 65, 32, 0, 1, 17, 67, 17, 67, 170, 195, 2, 17, 65, 32, 0, 1, 17, 67, 17, 67, 173, 195, 2, 17, 65, 32, 0, 1, 17, 67, 17, 67, 179, 195, 2, 17, 65, 32, 0, 1, 17, 67, 17, 67, 180, 195, 2, 17, 65, 32, 0, 1, 17, 67, 17, 67, 186, 195, 2, 17, 65, 32, 0, 1, 17, 67, 161, 195, 2, 17, 65, 32, 0, 1, 17, 67, 162, 195, 2, 17, 65, 32, 0, 1, 17, 67, 169, 195, 2, 17, 65, 32, 0, 1, 17, 67, 170, 195, 2, 17, 65, 32, 0, 1, 17, 67, 173, 195, 2, 17, 65, 32, 0, 1, 17, 67, 179, 195, 2, 17, 65, 32, 0, 1, 17, 67, 180, 195, 2, 17, 65, 32, 0, 1, 17, 67, 186, 195, 2, 17, 65, 32, 0, 2, 17, 65, 0, 4, 108, 5, 2, 2, 25, 3, 114, 0, 111, 2, 32, 0, 111, 2, 115, 32, 0, 117, 2, 32, 0, 117, 2, 115, 32, 0, 7, 6, 106, 0, 3, 88, 0, 8, 2, 32, 3, 88, 6, 108, 47, 130, 0, 5, 3, 2, 32, 17, 67, 3, 88, 10, 0, 5, 3, 2, 17, 66, 3, 88, 122, 0, 7, 6, 107, 0, 2, 107, 3, 0, 4, 3, 49, 0, 5, 3, 2, 115, 0, 5, 3, 2, 116, 0, 5, 1, 8, 2, 32, 3, 49, 6, 35, 48, 130, 0, 5, 3, 2, 32, 17, 67, 3, 49, 10, 0, 5, 2, 8, 2, 32, 3, 49, 35, 0, 5, 3, 2, 17, 66, 3, 49, 122, 0, 7, 6, 108, 0, 1, 108, 3, 0, 8, 2, 32, 3, 6, 107, 55, 36, 0, 3, 55, 0, 104, 1, 17, 65, 3, 55, 57, 0, 4, 104, 3, 61, 0, 104, 5, 1, 1, 17, 65, 0, 104, 5, 4, 1, 17, 65, 0, 5, 1, 8, 2, 32, 3, 107, 55, 0, 5, 1, 8, 2, 32, 31, 3, 107, 55, 38, 0, 7, 6, 109, 0, 2, 109, 3, 0, 8, 2, 32, 3, 6, 36, 63, 36, 0, 3, 63, 0, 5, 3, 2, 32, 17, 67, 3, 63, 10, 0, 5, 3, 2, 17, 66, 3, 63, 122, 0, 5, 1, 8, 2, 32, 3, 107, 63, 0, 5, 1, 8, 2, 32, 31, 3, 107, 63, 38, 0, 7, 6, 110, 0, 2, 110, 3, 0, 8, 2, 32, 3, 6, 36, 50, 36, 0, 4, 3, 50, 0, 110, 5, 1, 1, 17, 65, 0, 5, 3, 2, 32, 17, 67, 3, 50, 10, 0, 5, 3, 2, 17, 66, 3, 50, 122, 0, 104, 3, 65, 0, 5, 1, 8, 2, 32, 3, 107, 50, 0, 5, 1, 8, 2, 32, 31, 3, 107, 50, 38, 0, 7, 6, 111, 0, 110, 1, 115, 21, 2, 32, 3, 2, 39, 66, 0, 5, 1, 2, 108, 32, 3, 6, 108, 0, 4, 1, 21, 2, 32, 3, 8, 109, 0, 2, 115, 32, 0, 4, 3, 39, 0, 1, 21, 21, 2, 114, 17, 65, 32, 0, 1, 98, 2, 114, 101, 32, 0, 1, 99, 2, 114, 101, 32, 0, 1, 100, 2, 114, 101, 32, 0, 1, 108, 2, 114, 101, 32, 0, 1, 109, 2, 118, 97, 32, 0, 1, 109, 2, 118, 97, 109, 32, 0, 1, 116, 2, 100, 17, 65, 32, 0, 1, 116, 2, 114, 101, 32, 0, 1, 118, 2, 114, 101, 32, 0, 2, 105, 17, 67, 25, 0, 2, 108, 104, 12, 0, 2, 109, 97, 32, 0, 2, 110, 97, 32, 0, 2, 114, 17, 67, 111, 32, 0, 2, 115, 111, 32, 0, 2, 115, 116, 111, 32, 0, 111, 1, 99, 3, 39, 39, 0, 4, 111, 5, 1, 1, 17, 67, 2, 32, 3, 39, 58, 0, 117, 0, 109, 2, 17, 67, 3, 39, 63, 0, 110, 104, 3, 39, 65, 0, 4, 109, 2, 32, 3, 39, 66, 0, 109, 5, 4, 2, 17, 67, 0, 110, 2, 25, 0, 4, 5, 1, 1, 102, 2, 114, 109, 97, 116, 3, 40, 0, 5, 1, 1, 102, 2, 114, 109, 117, 108, 195, 161, 0, 5, 1, 1, 114, 112, 2, 102, 0, 5, 1, 1, 114, 114, 101, 116, 110, 105, 2, 103, 0, 5, 1, 8, 17, 67, 2, 17, 67, 17, 65, 17, 67, 17, 65, 17, 67, 0, 5, 1, 8, 112, 2, 114, 116, 117, 17, 67, 0, 5, 1, 8, 115, 2, 108, 117, 0, 111, 0, 4, 1, 98, 2, 114, 17, 65, 32, 3, 108, 0, 1, 112, 2, 100, 17, 65, 32, 0, 1, 112, 2, 100, 17, 65, 109, 32, 0, 2, 98, 114, 17, 65, 32, 0, 2, 98, 114, 17, 65, 109, 32, 0, 2, 99, 17, 65, 32, 0, 2, 99, 17, 65, 109, 32, 0, 2, 100, 17, 65, 32, 0, 2, 100, 17, 65, 109, 32, 0, 2, 103, 32, 0, 2, 103, 101, 32, 0, 2, 103, 101, 109, 32, 0, 2, 103, 115, 32, 0, 2, 106, 17, 65, 32, 0, 2, 106, 17, 65, 109, 32, 0, 2, 108, 17, 65, 32, 0, 2, 108, 17, 65, 109, 32, 0, 2, 108, 100, 17, 65, 32, 0, 2, 108, 100, 17, 65, 109, 32, 0, 2, 108, 116, 17, 65, 32, 0, 2, 108, 116, 17, 65, 109, 32, 0, 2, 112, 32, 0, 2, 113, 117, 101, 32, 0, 2, 113, 117, 101, 109, 32, 0, 2, 114, 17, 65, 32, 0, 2, 114, 17, 65, 109, 32, 0, 2, 114, 17, 67, 17, 65, 32, 0, 2, 114, 17, 67, 17, 65, 109, 32, 0, 2, 115, 17, 65, 32, 0, 2, 115, 17, 65, 109, 32, 0, 2, 115, 115, 17, 65, 32, 0, 2, 115, 115, 17, 65, 109, 32, 0, 2, 115, 116, 17, 65, 32, 0, 2, 115, 116, 17, 65, 109, 32, 0, 2, 115, 116, 114, 17, 65, 32, 0, 2, 116, 17, 65, 32, 0, 2, 116, 17, 65, 109, 32, 0, 2, 118, 17, 65, 109, 32, 0, 2, 118, 97, 32, 0, 2, 118, 101, 17, 67, 115, 32, 0, 2, 118, 101, 32, 0, 2, 122, 101, 115, 32, 0, 5, 1, 1, 118, 2, 108, 116, 0, 5, 1, 8, 2, 17, 67, 0, 5, 2, 2, 120, 32, 0, 5, 2, 8, 2, 108, 104, 17, 65, 32, 0, 5, 2, 8, 2, 108, 104, 17, 65, 109, 32, 0, 115, 2, 116, 114, 17, 65, 109, 32, 0, 108, 5, 2, 2, 32, 3, 108, 58, 0, 122, 5, 2, 2, 32, 3, 108, 86, 0, 122, 5, 1, 2, 32, 3, 108, 136, 0, 4, 105, 3, 118, 0, 105, 2, 115, 0, 111, 110, 3, 126, 66, 0, 121, 3, 134, 0, 7, 6, 112, 0, 2, 112, 3, 0, 108, 101, 5, 1, 2, 32, 3, 21, 0, 4, 3, 48, 0, 5, 3, 2, 115, 0, 5, 3, 2, 116, 0, 5, 3, 2, 32, 17, 67, 3, 48, 10, 0, 8, 2, 32, 3, 48, 36, 0, 5, 3, 2, 17, 66, 3, 48, 122, 0, 104, 5, 1, 3, 81, 0, 7, 6, 113, 0, 4, 3, 49, 0, 117, 2, 17, 71, 0, 117, 101, 105, 5, 1, 8, 2, 17, 67, 3, 49, 6, 116, 0, 4, 8, 2, 32, 3, 49, 36, 0, 117, 101, 5, 1, 1, 17, 65, 2, 110, 17, 65, 32, 0, 117, 101, 5, 1, 2, 108, 0, 117, 101, 5, 1, 8, 0, 117, 101, 5, 2, 8, 2, 32, 25, 0, 117, 195, 170, 5, 1, 1, 17, 67, 2, 32, 0, 4, 117, 101, 99, 5, 1, 3, 49, 36, 87, 0, 117, 101, 195, 167, 5, 1, 0, 117, 105, 5, 1, 3, 49, 37, 0, 117, 2, 25, 3, 49, 40, 0, 117, 105, 5, 1, 1, 110, 97, 114, 116, 3, 49, 40, 37, 0, 117, 105, 110, 100, 5, 1, 8, 3, 49, 40, 37, 50, 70, 0, 117, 111, 5, 1, 8, 3, 49, 40, 39, 0, 4, 117, 3, 49, 58, 0, 195, 188, 0, 4, 117, 101, 110, 5, 1, 1, 17, 65, 2, 17, 67, 3, 49, 58, 6, 116, 66, 0, 117, 101, 110, 5, 1, 1, 17, 67, 2, 17, 67, 0, 117, 97, 5, 1, 8, 3, 49, 58, 35, 0, 117, 101, 5, 1, 2, 114, 32, 3, 49, 107, 0, 117, 101, 8, 2, 32, 3, 49, 110, 0, 5, 3, 2, 17, 66, 3, 49, 122, 0, 7, 6, 114, 0, 5, 1, 8, 2, 32, 3, 6, 107, 34, 34, 0, 5, 1, 8, 2, 32, 31, 3, 6, 107, 34, 34, 38, 0, 8, 2, 32, 3, 6, 107, 99, 36, 0, 4, 3, 16, 0, 1, 17, 65, 2, 17, 65, 0, 1, 17, 65, 2, 32, 17, 65, 0, 1, 17, 67, 2, 17, 65, 0, 2, 17, 67, 3, 16, 14, 0, 2, 32, 3, 34, 0, 5, 1, 1, 17, 65, 2, 32, 3, 44, 0, 1, 17, 67, 29, 2, 17, 65, 3, 51, 0, 4, 1, 108, 3, 99, 0, 1, 110, 2, 12, 0, 1, 115, 0, 8, 0, 114, 0, 8, 2, 32, 36, 3, 99, 36, 6, 112, 0, 7, 6, 115, 0, 5, 2, 8, 2, 32, 3, 6, 107, 87, 36, 0, 4, 1, 17, 65, 2, 17, 65, 3, 86, 0, 1, 17, 65, 2, 32, 17, 65, 14, 128, 128, 129, 0, 1, 21, 2, 32, 17, 65, 0, 5, 36, 1, 17, 65, 2, 32, 17, 70, 14, 128, 128, 129, 0, 5, 36, 1, 21, 2, 32, 17, 70, 0, 4, 3, 87, 0, 1, 17, 65, 2, 32, 14, 128, 128, 129, 0, 1, 101, 115, 101, 2, 32, 0, 99, 2, 17, 71, 0, 115, 0, 115, 5, 1, 1, 17, 65, 0, 195, 167, 0, 111, 98, 114, 101, 8, 2, 21, 14, 128, 132, 133, 3, 87, 39, 69, 16, 36, 0, 4, 5, 1, 1, 17, 65, 2, 17, 70, 12, 3, 88, 0, 5, 1, 1, 17, 65, 2, 32, 17, 70, 12, 14, 128, 128, 129, 0, 104, 3, 89, 0, 5, 1, 8, 2, 32, 3, 107, 87, 0, 5, 1, 8, 2, 32, 31, 3, 107, 87, 38, 0, 5, 4, 8, 2, 17, 67, 3, 122, 87, 0, 4, 5, 1, 1, 17, 65, 2, 17, 67, 3, 136, 0, 5, 1, 1, 17, 65, 2, 32, 25, 14, 128, 128, 129, 0, 5, 1, 1, 21, 2, 32, 0, 5, 2, 2, 32, 0, 7, 6, 116, 0, 2, 116, 3, 0, 4, 104, 5, 1, 3, 21, 0, 105, 111, 110, 5, 1, 2, 32, 0, 3, 47, 0, 5, 3, 2, 32, 17, 67, 3, 47, 10, 0, 8, 2, 32, 3, 47, 36, 0, 4, 5, 2, 2, 101, 32, 3, 74, 0, 5, 2, 2, 105, 0, 5, 2, 2, 195, 173, 0, 5, 3, 2, 17, 66, 3, 74, 122, 0, 7, 6, 117, 0, 1, 103, 2, 17, 71, 3, 0, 2, 17, 65, 32, 3, 6, 40, 0, 4, 3, 40, 0, 1, 114, 2, 17, 65, 0, 1, 114, 2, 32, 17, 65, 0, 2, 105, 17, 67, 25, 0, 8, 2, 32, 0, 4, 2, 17, 65, 3, 58, 0, 2, 32, 17, 65, 0, 2, 105, 117, 0, 4, 105, 3, 119, 0, 121, 0, 109, 2, 17, 67, 3, 126, 63, 0, 110, 104, 3, 126, 65, 0, 4, 109, 2, 32, 3, 126, 66, 0, 109, 5, 4, 2, 17, 67, 0, 110, 2, 25, 0, 7, 6, 118, 0, 2, 118, 3, 0, 3, 82, 0, 5, 3, 2, 32, 17, 67, 3, 82, 10, 0, 5, 3, 2, 17, 66, 3, 82, 122, 0, 7, 6, 119, 0, 5, 1, 2, 32, 3, 21, 0, 5, 4, 8, 3, 40, 0, 3, 58, 0, 5, 2, 8, 2, 32, 3, 70, 6, 35, 69, 55, 57, 40, 0, 5, 1, 8, 2, 32, 3, 70, 6, 130, 69, 55, 4, 37, 40, 0, 7, 6, 120, 0, 2, 115, 3, 0, 4, 1, 17, 65, 2, 17, 65, 3, 49, 87, 0, 1, 101, 2, 17, 65, 0, 2, 32, 0, 8, 111, 2, 105, 0, 8, 114, 97, 109, 0, 4, 2, 195, 179, 32, 3, 86, 0, 8, 101, 2, 17, 65, 0, 8, 101, 104, 2, 17, 65, 0, 8, 101, 110, 105, 2, 17, 65, 0, 8, 101, 111, 99, 2, 17, 65, 0, 8, 170, 195, 2, 17, 65, 0, 4, 1, 17, 65, 114, 112, 2, 105, 3, 87, 0, 1, 161, 195, 109, 2, 105, 109, 0, 2, 17, 67, 0, 8, 117, 97, 0, 99, 2, 17, 71, 0, 4, 1, 17, 65, 114, 98, 2, 17, 65, 3, 89, 0, 1, 17, 65, 120, 2, 17, 65, 0, 1, 17, 71, 98, 2, 17, 65, 0, 1, 97, 2, 97, 0, 1, 97, 2, 97, 114, 0, 1, 97, 2, 101, 105, 0, 1, 97, 2, 195, 161, 0, 1, 97, 108, 101, 114, 2, 17, 65, 0, 1, 97, 114, 103, 2, 17, 65, 0, 1, 101, 108, 97, 2, 97, 0, 1, 101, 109, 2, 17, 65, 0, 1, 105, 97, 2, 17, 65, 0, 1, 105, 101, 2, 17, 65, 0, 1, 105, 112, 2, 17, 65, 0, 1, 105, 114, 2, 17, 65, 0, 1, 105, 117, 113, 2, 17, 65, 0, 1, 111, 109, 2, 97, 0, 1, 117, 2, 105, 0, 1, 117, 97, 98, 2, 17, 65, 0, 1, 117, 111, 2, 12, 0, 1, 117, 112, 2, 17, 65, 0, 2, 17, 65, 0, 2, 17, 65, 120, 17, 65, 0, 2, 105, 113, 117, 0, 5, 1, 1, 101, 2, 17, 67, 17, 65, 0, 5, 1, 1, 105, 2, 97, 32, 0, 5, 1, 1, 105, 2, 97, 115, 32, 0, 8, 97, 99, 2, 17, 65, 0, 8, 97, 102, 2, 105, 0, 8, 97, 114, 112, 2, 17, 65, 0, 8, 101, 108, 102, 2, 97, 0, 8, 101, 118, 2, 17, 65, 0, 8, 105, 108, 2, 17, 65, 0, 8, 105, 120, 2, 17, 65, 0, 8, 111, 2, 17, 65, 0, 8, 111, 99, 2, 17, 65, 0, 8, 111, 114, 2, 17, 65, 0, 8, 111, 114, 112, 2, 17, 65, 0, 8, 117, 108, 2, 17, 65, 0, 8, 169, 195, 109, 2, 105, 0, 7, 6, 121, 0, 2, 32, 3, 2, 37, 0, 5, 1, 8, 2, 32, 3, 6, 37, 48, 87, 4, 37, 55, 108, 66, 0, 5, 2, 8, 2, 32, 3, 6, 37, 48, 87, 37, 55, 39, 66, 0, 3, 37, 0, 2, 17, 65, 3, 57, 0, 7, 6, 122, 0, 2, 122, 3, 0, 4, 3, 86, 0, 1, 21, 2, 32, 17, 65, 0, 1, 21, 2, 32, 17, 70, 0, 5, 3, 2, 32, 17, 67, 3, 86, 10, 0, 8, 2, 32, 3, 86, 36, 0, 5, 3, 2, 17, 66, 3, 86, 122, 0, 5, 2, 1, 21, 2, 32, 3, 87, 0, 4, 5, 1, 1, 17, 65, 2, 17, 70, 12, 3, 88, 0, 5, 1, 1, 17, 65, 2, 32, 17, 70, 12, 0, 4, 5, 1, 1, 17, 65, 2, 17, 67, 3, 89, 0, 5, 1, 1, 17, 65, 2, 32, 17, 67, 0, 5, 1, 1, 21, 2, 32, 0, 7, 6, 0, 36, 8, 32, 114, 3, 0, 194, 170, 1, 32, 15, 3, 2, 35, 0, 194, 186, 1, 32, 15, 3, 2, 39, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 195, 188, 3, 40, 0, 45, 8, 32, 2, 32, 15, 3, 63, 6, 36, 50, 109, 87, 0, 44, 2, 15, 3, 82, 6, 37, 34, 79, 40, 55, 130, 0, 4, 195, 159, 3, 87, 0, 195, 167, 0, 36, 3, 87, 37, 81, 51, 6, 128, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts48 = FileInMemory_createWithData (14775, reinterpret_cast (&espeakdata_dicts48_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/pt_dict", L"pt"); Collection_addItem (me.peek(), espeakdata_dicts48.transfer()); static unsigned char espeakdata_dicts49_data[26886] = { 0, 4, 0, 0, 207, 91, 0, 0, 13, 138, 195, 174, 14, 3, 8, 5, 9, 5, 20, 21, 68, 13, 138, 195, 174, 14, 3, 1, 18, 3, 5, 18, 1, 68, 0, 17, 7, 20, 195, 162, 18, 26, 9, 21, 47, 110, 34, 86, 6, 37, 40, 0, 9, 134, 18, 196, 131, 7, 5, 20, 65, 6, 195, 61, 4, 137, 66, 9, 4, 95, 48, 15, 6, 70, 36, 0, 0, 0, 9, 198, 16, 85, 5, 72, 210, 78, 66, 0, 0, 13, 65, 4, 35, 121, 122, 0, 72, 81, 197, 163, 105, 32, 13, 65, 4, 35, 95, 122, 0, 72, 81, 197, 159, 105, 32, 6, 193, 4, 72, 28, 32, 0, 20, 71, 56, 144, 201, 16, 80, 213, 52, 50, 37, 74, 122, 70, 36, 49, 6, 40, 63, 0, 0, 0, 0, 21, 65, 8, 98, 117, 108, 101, 118, 97, 114, 100, 117, 108, 0, 44, 29, 81, 100, 117, 108, 32, 6, 65, 8, 69, 36, 0, 0, 12, 137, 195, 174, 14, 20, 9, 14, 4, 5, 13, 66, 0, 15, 67, 21, 64, 192, 101, 116, 99, 101, 116, 101, 114, 97, 0, 29, 0, 11, 67, 53, 82, 65, 63, 6, 40, 57, 35, 0, 7, 196, 77, 80, 197, 4, 66, 7, 196, 49, 80, 197, 4, 66, 7, 196, 17, 80, 197, 4, 66, 6, 195, 84, 225, 5, 28, 0, 8, 197, 88, 150, 129, 88, 144, 67, 8, 197, 36, 81, 148, 36, 224, 65, 8, 197, 16, 144, 86, 60, 192, 65, 8, 197, 12, 149, 137, 48, 80, 66, 12, 65, 12, 49, 35, 34, 0, 72, 81, 97, 114, 32, 10, 65, 12, 49, 39, 0, 72, 81, 111, 32, 6, 65, 12, 74, 36, 0, 0, 12, 201, 65, 33, 84, 85, 66, 78, 16, 83, 137, 67, 9, 198, 4, 115, 206, 37, 50, 64, 68, 0, 11, 136, 16, 196, 131, 19, 20, 18, 196, 131, 66, 11, 136, 9, 13, 1, 7, 9, 14, 196, 131, 67, 9, 198, 16, 84, 198, 84, 225, 1, 67, 9, 198, 16, 81, 197, 56, 84, 129, 68, 9, 198, 12, 243, 134, 84, 225, 1, 67, 11, 136, 22, 15, 1, 19, 20, 18, 196, 131, 76, 11, 136, 14, 15, 1, 19, 20, 18, 196, 131, 77, 11, 136, 22, 15, 1, 19, 20, 18, 196, 131, 77, 13, 4, 95, 8, 1, 3, 105, 6, 35, 74, 36, 49, 0, 0, 11, 200, 65, 35, 212, 60, 51, 193, 48, 80, 67, 11, 67, 53, 82, 69, 63, 6, 40, 57, 36, 0, 0, 18, 8, 195, 174, 14, 3, 8, 5, 9, 1, 110, 50, 49, 36, 6, 57, 35, 0, 6, 65, 16, 70, 36, 0, 0, 21, 9, 22, 5, 197, 159, 14, 9, 3, 9, 5, 82, 36, 89, 50, 37, 74, 6, 37, 36, 0, 10, 135, 16, 195, 162, 14, 20, 5, 3, 65, 20, 9, 195, 174, 14, 1, 9, 14, 20, 5, 1, 110, 50, 35, 6, 37, 50, 47, 133, 0, 21, 9, 8, 196, 131, 18, 14, 9, 3, 9, 5, 105, 13, 34, 50, 37, 74, 6, 37, 36, 0, 0, 23, 10, 6, 9, 5, 11, 196, 131, 18, 21, 9, 1, 81, 57, 36, 78, 6, 13, 34, 119, 35, 0, 76, 0, 9, 134, 26, 1, 8, 196, 131, 18, 65, 12, 137, 3, 12, 196, 131, 20, 9, 14, 196, 131, 67, 14, 139, 195, 174, 14, 7, 8, 9, 15, 14, 20, 5, 1, 67, 10, 135, 7, 195, 162, 14, 4, 5, 1, 66, 0, 8, 197, 12, 147, 133, 88, 16, 67, 6, 65, 20, 36, 0, 14, 7, 65, 20, 57, 36, 0, 72, 17, 142, 4, 21, 13, 14, 5, 1, 22, 15, 1, 19, 20, 18, 196, 131, 79, 0, 14, 5, 20, 18, 196, 131, 9, 47, 14, 16, 13, 6, 37, 0, 29, 13, 16, 18, 5, 197, 159, 5, 4, 9, 14, 197, 163, 9, 5, 48, 14, 16, 36, 89, 36, 70, 37, 50, 121, 6, 37, 36, 0, 0, 9, 198, 76, 84, 150, 36, 50, 73, 66, 10, 199, 5, 34, 9, 80, 80, 212, 84, 68, 9, 198, 4, 197, 3, 84, 149, 129, 67, 9, 198, 4, 115, 206, 37, 49, 65, 68, 9, 134, 1, 197, 159, 5, 26, 1, 67, 0, 14, 139, 1, 12, 1, 12, 20, 196, 131, 9, 5, 18, 9, 66, 10, 135, 19, 5, 13, 196, 131, 14, 1, 67, 0, 8, 197, 72, 85, 133, 56, 144, 67, 6, 65, 24, 81, 36, 0, 0, 0, 9, 134, 3, 5, 18, 197, 159, 9, 66, 0, 11, 200, 65, 35, 198, 21, 51, 210, 36, 144, 66, 7, 196, 5, 64, 67, 4, 67, 0, 8, 197, 89, 82, 69, 80, 80, 65, 8, 197, 76, 83, 69, 56, 80, 65, 8, 197, 16, 81, 137, 56, 144, 67, 16, 69, 61, 34, 67, 84, 208, 39, 16, 122, 49, 4, 40, 63, 0, 76, 8, 132, 1, 197, 159, 1, 66, 28, 6, 65, 28, 73, 36, 0, 0, 12, 137, 5, 24, 16, 12, 15, 18, 196, 131, 13, 67, 0, 13, 138, 3, 15, 12, 1, 2, 15, 18, 196, 131, 13, 68, 9, 198, 72, 81, 197, 56, 84, 129, 68, 0, 7, 196, 64, 19, 9, 16, 65, 11, 67, 4, 99, 1, 35, 81, 55, 6, 35, 0, 0, 7, 65, 32, 105, 35, 89, 0, 0, 12, 137, 195, 174, 14, 22, 195, 162, 18, 20, 9, 67, 0, 19, 70, 76, 84, 150, 36, 50, 85, 87, 36, 34, 82, 6, 37, 74, 6, 57, 40, 0, 0, 15, 67, 12, 20, 133, 49, 35, 34, 36, 55, 0, 72, 81, 108, 32, 7, 195, 12, 20, 133, 73, 28, 10, 1, 35, 70, 57, 6, 36, 86, 0, 27, 0, 11, 65, 36, 57, 115, 0, 72, 81, 97, 105, 32, 12, 65, 36, 57, 35, 63, 0, 72, 81, 97, 109, 32, 13, 65, 36, 37, 35, 89, 0, 72, 81, 97, 197, 159, 32, 12, 65, 36, 57, 35, 34, 0, 72, 81, 97, 114, 32, 0, 0, 10, 67, 4, 84, 128, 6, 115, 36, 34, 0, 6, 195, 48, 244, 128, 76, 13, 1, 38, 35, 63, 48, 36, 34, 87, 35, 50, 70, 0, 0, 10, 135, 15, 2, 197, 163, 9, 14, 21, 67, 10, 135, 7, 196, 131, 12, 2, 21, 9, 66, 10, 67, 4, 99, 9, 35, 81, 55, 37, 0, 0, 6, 65, 40, 88, 36, 0, 0, 17, 70, 52, 19, 129, 28, 84, 128, 63, 6, 36, 50, 36, 73, 13, 34, 0, 6, 131, 22, 196, 131, 72, 9, 198, 4, 49, 83, 80, 244, 128, 78, 0, 9, 198, 88, 240, 201, 24, 84, 129, 68, 15, 6, 4, 196, 131, 18, 21, 9, 70, 13, 16, 58, 6, 37, 0, 9, 198, 4, 49, 83, 80, 244, 129, 78, 13, 1, 42, 35, 87, 47, 36, 16, 37, 87, 49, 0, 27, 0, 14, 139, 4, 5, 19, 3, 8, 9, 4, 5, 197, 163, 9, 66, 9, 1, 43, 48, 55, 40, 87, 0, 27, 0, 15, 140, 3, 21, 14, 15, 1, 197, 159, 20, 5, 197, 163, 9, 66, 6, 65, 44, 49, 35, 0, 0, 10, 135, 4, 15, 13, 9, 14, 196, 131, 65, 12, 137, 3, 15, 14, 3, 21, 18, 196, 131, 13, 67, 16, 70, 8, 195, 199, 28, 84, 128, 69, 55, 6, 39, 79, 13, 34, 0, 0, 11, 136, 5, 12, 9, 13, 9, 14, 196, 131, 66, 15, 6, 16, 196, 131, 12, 5, 1, 48, 35, 55, 36, 6, 35, 0, 9, 198, 48, 81, 201, 24, 84, 129, 68, 9, 198, 16, 83, 9, 8, 84, 129, 68, 10, 1, 46, 48, 40, 50, 49, 47, 0, 27, 0, 9, 134, 19, 21, 6, 196, 131, 18, 65, 8, 1, 47, 87, 55, 36, 89, 0, 0, 10, 135, 20, 195, 162, 14, 196, 131, 18, 65, 13, 65, 48, 55, 35, 89, 0, 72, 81, 97, 197, 159, 32, 12, 65, 48, 55, 35, 34, 0, 72, 81, 97, 114, 32, 12, 65, 48, 55, 39, 34, 0, 72, 81, 111, 114, 32, 11, 65, 48, 55, 115, 0, 72, 81, 97, 105, 32, 15, 65, 48, 55, 35, 139, 122, 0, 72, 81, 97, 197, 163, 105, 32, 12, 65, 48, 55, 35, 63, 0, 72, 81, 97, 109, 32, 11, 65, 48, 55, 112, 0, 72, 81, 97, 117, 32, 10, 65, 48, 55, 35, 0, 72, 81, 97, 32, 18, 8, 14, 15, 21, 196, 131, 12, 5, 1, 50, 6, 39, 40, 13, 55, 133, 0, 0, 10, 135, 4, 196, 131, 21, 14, 196, 131, 67, 10, 135, 3, 195, 162, 14, 20, 5, 3, 65, 12, 137, 18, 196, 131, 19, 3, 15, 12, 5, 1, 67, 0, 11, 136, 13, 9, 197, 159, 21, 14, 196, 131, 65, 10, 199, 24, 147, 15, 104, 241, 137, 36, 68, 13, 138, 195, 174, 14, 22, 195, 162, 18, 20, 5, 1, 67, 0, 9, 198, 16, 148, 133, 13, 67, 210, 66, 0, 8, 197, 48, 245, 137, 81, 80, 67, 12, 65, 52, 63, 35, 89, 0, 72, 81, 97, 83, 32, 12, 65, 52, 63, 35, 34, 0, 72, 81, 97, 114, 32, 12, 65, 52, 63, 39, 34, 0, 72, 81, 111, 114, 32, 8, 197, 72, 81, 201, 104, 16, 67, 0, 12, 137, 197, 159, 1, 16, 20, 5, 12, 5, 1, 65, 0, 13, 138, 195, 174, 14, 6, 12, 15, 18, 9, 20, 21, 68, 12, 137, 4, 5, 19, 3, 15, 16, 196, 131, 18, 66, 0, 10, 135, 6, 18, 195, 162, 14, 20, 21, 66, 0, 8, 197, 72, 84, 5, 104, 144, 65, 8, 197, 64, 19, 9, 104, 144, 65, 8, 197, 56, 85, 5, 16, 80, 65, 8, 197, 52, 241, 5, 48, 80, 66, 12, 65, 56, 50, 39, 34, 0, 72, 81, 111, 114, 32, 12, 65, 56, 50, 39, 34, 0, 72, 81, 111, 114, 32, 10, 65, 56, 50, 35, 0, 72, 81, 97, 32, 13, 65, 56, 50, 35, 89, 0, 72, 81, 97, 197, 159, 32, 10, 65, 56, 50, 39, 0, 72, 81, 111, 32, 8, 197, 16, 81, 197, 72, 16, 67, 8, 197, 13, 80, 197, 72, 144, 67, 11, 136, 195, 174, 14, 19, 21, 197, 159, 9, 77, 11, 5, 95, 48, 1, 14, 4, 10, 89, 37, 0, 0, 8, 133, 21, 18, 196, 131, 13, 66, 11, 136, 197, 163, 5, 1, 16, 196, 131, 14, 65, 0, 9, 198, 48, 240, 193, 48, 150, 129, 68, 0, 0, 8, 197, 53, 81, 197, 80, 80, 65, 11, 136, 2, 21, 3, 21, 18, 196, 131, 13, 67, 11, 136, 1, 4, 13, 9, 18, 196, 131, 13, 67, 18, 8, 14, 9, 13, 196, 131, 14, 21, 9, 50, 37, 63, 13, 50, 6, 119, 0, 4, 193, 60, 72, 4, 193, 60, 72, 0, 11, 136, 26, 4, 18, 1, 22, 196, 131, 14, 65, 12, 137, 195, 174, 14, 3, 21, 18, 1, 10, 1, 68, 10, 1, 61, 36, 79, 6, 35, 55, 0, 27, 0, 13, 138, 1, 12, 196, 131, 20, 21, 18, 196, 131, 13, 68, 0, 6, 195, 16, 244, 137, 66, 0, 11, 136, 14, 196, 131, 22, 196, 131, 12, 9, 67, 9, 134, 8, 15, 12, 2, 196, 131, 66, 10, 1, 64, 35, 16, 6, 39, 50, 70, 0, 6, 65, 64, 48, 36, 0, 0, 0, 9, 198, 5, 98, 67, 84, 197, 21, 68, 0, 7, 196, 21, 64, 76, 4, 67, 0, 7, 65, 68, 49, 57, 40, 0, 0, 8, 133, 19, 196, 131, 16, 1, 66, 9, 198, 12, 19, 3, 84, 192, 64, 67, 0, 9, 134, 3, 195, 162, 18, 13, 9, 66, 18, 70, 16, 83, 193, 72, 80, 197, 70, 36, 136, 34, 36, 74, 6, 36, 0, 8, 6, 195, 84, 224, 64, 77, 0, 7, 196, 61, 48, 193, 72, 65, 7, 196, 36, 193, 143, 88, 65, 6, 195, 84, 225, 73, 73, 0, 8, 197, 80, 84, 141, 36, 224, 65, 8, 197, 24, 245, 2, 4, 192, 65, 8, 197, 8, 20, 141, 4, 224, 65, 11, 136, 6, 18, 5, 13, 196, 131, 20, 1, 67, 6, 65, 72, 34, 36, 0, 0, 12, 137, 195, 174, 14, 7, 8, 9, 197, 163, 9, 67, 6, 194, 5, 32, 76, 32, 0, 0, 7, 196, 64, 241, 5, 4, 66, 7, 196, 77, 81, 197, 4, 66, 0, 8, 197, 72, 81, 213, 48, 144, 65, 11, 136, 4, 9, 19, 20, 18, 196, 131, 13, 66, 8, 197, 12, 195, 195, 61, 64, 65, 10, 65, 76, 87, 39, 0, 72, 81, 111, 32, 12, 65, 76, 87, 39, 34, 0, 72, 81, 111, 114, 32, 12, 65, 76, 87, 35, 34, 0, 72, 81, 97, 114, 32, 0, 18, 70, 77, 0, 78, 36, 243, 5, 87, 48, 35, 50, 37, 6, 39, 55, 36, 0, 12, 137, 16, 196, 131, 19, 20, 18, 196, 131, 13, 66, 9, 134, 3, 1, 16, 196, 131, 20, 65, 17, 70, 5, 4, 143, 64, 244, 192, 35, 48, 14, 16, 39, 48, 6, 39, 0, 0, 10, 199, 77, 80, 133, 77, 66, 77, 4, 68, 10, 199, 65, 33, 76, 84, 225, 197, 4, 67, 18, 70, 12, 243, 148, 36, 229, 65, 49, 39, 50, 47, 37, 50, 58, 6, 35, 0, 0, 7, 196, 12, 17, 133, 4, 66, 7, 196, 89, 35, 201, 4, 66, 0, 11, 136, 26, 1, 18, 26, 196, 131, 18, 9, 65, 8, 197, 76, 84, 150, 21, 32, 65, 11, 136, 16, 196, 131, 19, 196, 131, 18, 9, 65, 6, 65, 80, 47, 36, 0, 0, 9, 198, 25, 32, 71, 20, 65, 64, 65, 0, 0, 7, 196, 65, 34, 86, 36, 67, 0, 0, 12, 67, 85, 0, 192, 40, 48, 36, 74, 6, 36, 0, 0, 12, 137, 16, 196, 131, 19, 20, 18, 196, 131, 22, 65, 16, 141, 195, 174, 14, 3, 196, 131, 16, 5, 18, 9, 12, 15, 18, 67, 9, 134, 196, 131, 12, 15, 18, 1, 77, 0, 10, 135, 20, 1, 2, 196, 131, 18, 1, 65, 6, 195, 48, 245, 137, 66, 0, 19, 8, 19, 16, 21, 14, 5, 197, 163, 9, 87, 48, 6, 40, 50, 36, 121, 122, 0, 16, 69, 21, 131, 212, 36, 48, 36, 79, 86, 6, 39, 47, 37, 49, 0, 13, 65, 88, 82, 35, 89, 0, 72, 81, 97, 197, 159, 32, 12, 65, 88, 82, 35, 34, 0, 72, 81, 97, 114, 32, 7, 193, 88, 72, 81, 111, 32, 12, 65, 88, 82, 35, 63, 0, 72, 81, 97, 109, 32, 11, 65, 88, 82, 112, 0, 72, 81, 97, 117, 32, 15, 65, 88, 82, 35, 139, 122, 0, 72, 81, 97, 197, 163, 105, 32, 8, 197, 81, 33, 67, 20, 16, 66, 8, 197, 12, 243, 147, 80, 16, 66, 11, 136, 16, 196, 131, 18, 196, 131, 19, 9, 67, 11, 136, 195, 174, 14, 19, 21, 197, 163, 9, 77, 6, 65, 88, 82, 36, 0, 0, 8, 133, 16, 196, 131, 20, 21, 65, 9, 198, 16, 83, 211, 20, 34, 64, 67, 6, 194, 5, 48, 76, 32, 0, 9, 134, 20, 196, 131, 18, 9, 9, 65, 13, 138, 18, 5, 197, 163, 9, 14, 5, 197, 163, 9, 66, 10, 199, 17, 84, 133, 72, 147, 15, 72, 66, 0, 14, 139, 18, 196, 131, 13, 195, 162, 14, 5, 197, 163, 9, 66, 7, 196, 52, 243, 9, 52, 65, 10, 135, 12, 1, 7, 196, 131, 18, 5, 65, 14, 68, 29, 33, 79, 36, 79, 14, 16, 36, 6, 39, 57, 0, 7, 196, 17, 80, 197, 52, 65, 10, 135, 3, 196, 131, 18, 15, 18, 1, 73, 10, 135, 3, 196, 131, 18, 15, 18, 1, 73, 17, 4, 95, 49, 77, 52, 6, 40, 50, 69, 37, 55, 6, 57, 39, 50, 0, 0, 9, 198, 76, 147, 66, 60, 194, 67, 66, 8, 197, 13, 33, 83, 13, 80, 66, 18, 4, 95, 49, 77, 53, 6, 40, 50, 69, 37, 55, 6, 57, 35, 34, 70, 0, 12, 65, 92, 70, 40, 69, 55, 40, 6, 82, 36, 0, 0, 12, 137, 1, 12, 5, 18, 7, 196, 131, 20, 21, 68, 0, 0, 7, 196, 52, 147, 137, 52, 65, 14, 139, 195, 174, 14, 6, 21, 14, 4, 196, 131, 20, 21, 68, 14, 139, 195, 174, 14, 3, 21, 18, 3, 196, 131, 20, 21, 68, 0, 13, 4, 95, 49, 77, 49, 4, 39, 63, 6, 37, 36, 0, 7, 65, 96, 37, 49, 87, 0, 0, 11, 136, 197, 159, 13, 5, 3, 8, 5, 18, 65, 17, 4, 95, 49, 77, 50, 6, 40, 50, 63, 37, 55, 6, 57, 39, 50, 0, 0, 9, 198, 52, 146, 140, 60, 16, 197, 65, 6, 195, 84, 229, 76, 77, 18, 4, 95, 49, 77, 51, 6, 40, 50, 63, 37, 55, 6, 57, 35, 34, 70, 0, 0, 7, 196, 48, 144, 133, 72, 65, 7, 196, 65, 33, 68, 4, 66, 11, 67, 53, 84, 137, 63, 40, 34, 6, 37, 0, 0, 11, 136, 16, 195, 162, 14, 20, 5, 3, 5, 65, 10, 65, 100, 6, 37, 79, 34, 36, 49, 0, 0, 0, 6, 195, 5, 84, 128, 65, 9, 134, 8, 196, 131, 3, 21, 9, 67, 0, 7, 196, 80, 83, 137, 76, 65, 12, 68, 80, 19, 148, 36, 47, 35, 50, 47, 37, 0, 6, 195, 84, 229, 73, 73, 0, 11, 136, 1, 12, 5, 7, 5, 197, 163, 9, 66, 7, 65, 104, 86, 36, 47, 0, 0, 12, 137, 19, 195, 162, 13, 2, 196, 131, 20, 1, 65, 9, 198, 64, 243, 9, 80, 144, 192, 66, 8, 133, 2, 15, 197, 163, 9, 66, 8, 133, 196, 131, 19, 20, 1, 77, 0, 9, 198, 77, 68, 133, 13, 84, 129, 67, 0, 7, 196, 76, 17, 5, 4, 66, 7, 196, 88, 81, 5, 4, 66, 7, 196, 25, 81, 197, 4, 66, 0, 11, 136, 197, 159, 15, 1, 18, 5, 3, 9, 65, 8, 197, 25, 83, 7, 21, 32, 65, 0, 16, 141, 195, 174, 14, 197, 163, 5, 12, 5, 7, 5, 197, 163, 9, 67, 12, 137, 195, 174, 13, 2, 195, 162, 3, 19, 9, 67, 0, 0, 0, 8, 197, 53, 83, 20, 61, 32, 73, 0, 9, 198, 64, 20, 148, 20, 225, 64, 67, 14, 5, 5, 197, 159, 20, 9, 57, 36, 89, 47, 122, 0, 76, 5, 194, 12, 16, 72, 0, 15, 140, 195, 174, 14, 20, 195, 162, 13, 16, 9, 14, 196, 131, 66, 0, 7, 196, 76, 19, 22, 4, 66, 10, 135, 1, 3, 5, 197, 159, 20, 9, 72, 0, 8, 197, 48, 147, 135, 20, 16, 66, 8, 132, 1, 197, 163, 9, 76, 32, 0, 9, 198, 65, 35, 214, 20, 226, 64, 67, 12, 137, 1, 4, 196, 131, 16, 15, 19, 20, 9, 68, 0, 10, 199, 77, 84, 5, 73, 98, 90, 4, 68, 0, 7, 196, 53, 81, 213, 72, 65, 10, 135, 6, 1, 3, 5, 197, 163, 9, 65, 10, 135, 4, 21, 3, 5, 197, 163, 9, 65, 0, 11, 136, 20, 18, 1, 7, 5, 197, 163, 9, 65, 11, 136, 15, 1, 19, 16, 5, 197, 163, 9, 65, 11, 136, 8, 1, 9, 4, 5, 197, 163, 9, 65, 11, 136, 3, 18, 5, 4, 5, 197, 163, 9, 65, 11, 136, 1, 4, 21, 3, 5, 197, 163, 9, 66, 11, 136, 195, 174, 14, 3, 1, 18, 14, 1, 67, 11, 136, 195, 174, 14, 20, 5, 197, 163, 9, 67, 11, 136, 19, 21, 14, 20, 5, 197, 163, 9, 77, 0, 12, 137, 197, 163, 1, 14, 4, 196, 131, 18, 1, 65, 12, 137, 4, 5, 4, 21, 3, 5, 197, 163, 9, 66, 5, 194, 5, 80, 76, 0, 13, 138, 16, 18, 15, 1, 19, 16, 5, 197, 163, 9, 65, 13, 138, 16, 18, 5, 6, 1, 3, 5, 197, 163, 9, 66, 13, 138, 3, 18, 5, 197, 159, 20, 5, 197, 163, 9, 65, 0, 13, 68, 88, 243, 21, 52, 82, 39, 55, 6, 40, 63, 0, 0, 11, 136, 12, 21, 3, 18, 196, 131, 20, 21, 67, 0, 8, 133, 16, 196, 131, 19, 1, 66, 0, 13, 138, 22, 9, 14, 15, 22, 196, 131, 197, 163, 9, 20, 13, 138, 14, 21, 13, 196, 131, 18, 196, 131, 20, 21, 68, 0, 14, 139, 22, 196, 131, 20, 196, 131, 13, 196, 131, 20, 21, 68, 11, 200, 64, 244, 148, 60, 48, 76, 37, 80, 68, 9, 134, 16, 196, 131, 3, 21, 18, 65, 15, 139, 3, 21, 13, 16, 196, 131, 18, 196, 131, 20, 21, 67, 18, 0, 15, 140, 26, 4, 18, 21, 14, 3, 9, 14, 196, 131, 20, 21, 68, 11, 136, 197, 159, 15, 1, 18, 5, 3, 5, 65, 15, 140, 16, 9, 5, 16, 20, 196, 131, 14, 196, 131, 20, 21, 68, 11, 136, 195, 174, 14, 3, 8, 5, 7, 1, 67, 0, 0, 9, 134, 18, 195, 162, 14, 10, 9, 66, 0, 11, 67, 48, 147, 9, 55, 6, 37, 55, 37, 0, 7, 196, 80, 84, 212, 4, 66, 10, 135, 1, 7, 196, 131, 197, 163, 1, 67, 0, 8, 197, 25, 32, 71, 20, 64, 65, 0, 20, 145, 195, 174, 14, 20, 18, 5, 4, 5, 19, 3, 8, 9, 26, 196, 131, 20, 21, 70, 9, 198, 24, 197, 73, 21, 32, 64, 67, 9, 198, 20, 229, 77, 21, 32, 64, 68, 0, 0, 0, 0, 8, 133, 16, 196, 131, 18, 21, 66, 9, 198, 52, 244, 195, 61, 96, 64, 65, 9, 198, 65, 35, 205, 61, 96, 64, 67, 9, 198, 12, 243, 131, 85, 32, 64, 67, 0, 11, 136, 3, 18, 9, 22, 196, 131, 197, 163, 65, 0, 14, 139, 19, 21, 19, 197, 163, 9, 14, 5, 197, 163, 9, 66, 14, 139, 13, 5, 14, 197, 163, 9, 14, 5, 197, 163, 9, 66, 8, 133, 4, 21, 16, 196, 131, 28, 0, 8, 197, 76, 147, 135, 85, 32, 65, 8, 197, 12, 19, 131, 21, 32, 65, 0, 14, 139, 9, 14, 20, 5, 18, 19, 5, 3, 20, 196, 131, 67, 9, 198, 36, 81, 148, 36, 225, 64, 65, 9, 198, 24, 197, 73, 21, 33, 64, 65, 12, 137, 195, 174, 14, 19, 196, 131, 197, 159, 9, 77, 0, 13, 138, 20, 15, 22, 1, 18, 196, 131, 197, 159, 9, 66, 11, 136, 3, 195, 162, 14, 5, 16, 196, 131, 65, 9, 134, 3, 196, 131, 26, 14, 9, 66, 0, 12, 67, 13, 33, 65, 49, 14, 16, 36, 6, 35, 0, 6, 195, 5, 97, 65, 78, 10, 135, 196, 131, 19, 20, 5, 9, 1, 77, 0, 0, 9, 198, 76, 147, 135, 85, 33, 64, 65, 0, 13, 138, 197, 163, 196, 131, 14, 4, 196, 131, 18, 9, 65, 13, 138, 3, 196, 131, 19, 196, 131, 20, 15, 18, 9, 68, 7, 195, 61, 34, 64, 72, 8, 0, 7, 196, 92, 80, 133, 72, 65, 11, 200, 56, 244, 212, 36, 210, 76, 61, 32, 65, 6, 195, 5, 97, 77, 76, 0, 8, 197, 52, 84, 135, 20, 16, 66, 0, 9, 198, 16, 144, 86, 60, 194, 64, 65, 0, 6, 195, 37, 98, 64, 66, 17, 6, 3, 196, 131, 20, 18, 5, 49, 6, 13, 47, 14, 16, 36, 0, 28, 0, 12, 137, 20, 15, 22, 1, 18, 196, 131, 197, 159, 66, 11, 200, 64, 20, 148, 20, 225, 82, 20, 144, 67, 0, 8, 197, 76, 19, 20, 20, 16, 66, 16, 69, 61, 32, 78, 28, 80, 6, 39, 14, 16, 37, 50, 73, 122, 0, 8, 197, 53, 86, 137, 12, 16, 65, 8, 197, 77, 83, 148, 20, 208, 77, 0, 0, 10, 199, 16, 83, 79, 57, 53, 18, 4, 67, 0, 12, 137, 197, 163, 1, 14, 197, 163, 15, 197, 159, 65, 10, 135, 16, 9, 3, 196, 131, 20, 21, 67, 13, 68, 52, 81, 9, 84, 63, 6, 36, 70, 57, 40, 0, 10, 135, 12, 5, 7, 196, 131, 20, 21, 67, 6, 195, 80, 19, 5, 77, 0, 8, 197, 24, 145, 82, 81, 80, 66, 11, 136, 1, 16, 21, 3, 196, 131, 20, 21, 68, 8, 197, 37, 160, 149, 80, 144, 67, 12, 137, 3, 5, 12, 196, 131, 12, 1, 12, 20, 79, 0, 12, 137, 21, 18, 26, 9, 3, 196, 131, 20, 21, 68, 12, 137, 1, 18, 21, 14, 3, 196, 131, 20, 21, 68, 0, 13, 138, 8, 21, 18, 4, 21, 3, 196, 131, 20, 21, 68, 13, 138, 1, 12, 21, 14, 5, 3, 196, 131, 20, 21, 68, 9, 134, 16, 18, 196, 131, 10, 9, 66, 0, 10, 135, 14, 5, 3, 196, 131, 10, 9, 67, 14, 139, 195, 174, 14, 18, 5, 7, 9, 19, 20, 18, 1, 68, 0, 15, 140, 195, 174, 14, 3, 18, 5, 14, 7, 196, 131, 20, 21, 68, 15, 140, 195, 174, 14, 3, 196, 131, 18, 3, 196, 131, 20, 21, 68, 11, 136, 195, 174, 13, 16, 12, 9, 14, 9, 67, 0, 0, 0, 12, 68, 100, 18, 15, 60, 57, 35, 105, 6, 40, 0, 9, 134, 197, 159, 21, 9, 5, 18, 65, 9, 198, 64, 20, 148, 20, 225, 82, 67, 7, 196, 65, 84, 148, 4, 66, 7, 196, 5, 1, 76, 4, 67, 17, 7, 22, 15, 197, 159, 20, 18, 9, 82, 39, 89, 47, 16, 37, 0, 77, 17, 7, 14, 15, 197, 159, 20, 18, 9, 50, 39, 89, 47, 16, 37, 0, 77, 0, 19, 70, 36, 229, 5, 73, 5, 83, 37, 50, 47, 36, 14, 16, 48, 6, 40, 87, 0, 0, 9, 198, 60, 36, 197, 73, 96, 64, 67, 9, 198, 53, 84, 141, 85, 32, 64, 67, 0, 9, 198, 81, 34, 77, 37, 65, 77, 66, 9, 134, 7, 18, 5, 197, 159, 9, 66, 0, 0, 0, 9, 198, 21, 129, 67, 85, 64, 64, 68, 9, 198, 5, 50, 71, 85, 32, 64, 68, 0, 0, 12, 137, 6, 15, 14, 5, 20, 9, 3, 196, 131, 66, 16, 7, 1, 18, 196, 131, 197, 163, 9, 35, 34, 6, 13, 121, 122, 0, 6, 195, 48, 148, 9, 66, 14, 68, 61, 34, 67, 20, 39, 16, 122, 74, 4, 36, 0, 75, 0, 8, 197, 21, 128, 77, 20, 224, 66, 11, 136, 195, 174, 14, 6, 21, 14, 4, 1, 67, 0, 9, 198, 52, 20, 148, 61, 33, 64, 65, 9, 198, 16, 240, 212, 61, 33, 64, 65, 0, 6, 195, 5, 101, 64, 66, 0, 12, 137, 16, 18, 5, 15, 3, 21, 16, 196, 131, 68, 0, 8, 197, 13, 32, 84, 21, 32, 65, 0, 8, 133, 20, 196, 131, 9, 5, 66, 6, 194, 4, 144, 76, 32, 5, 194, 12, 80, 76, 6, 194, 4, 144, 72, 28, 8, 66, 20, 16, 57, 35, 0, 76, 0, 9, 198, 88, 144, 212, 61, 34, 73, 66, 10, 135, 197, 159, 21, 2, 18, 5, 4, 65, 13, 138, 3, 5, 20, 196, 131, 197, 163, 21, 9, 5, 67, 0, 7, 196, 53, 86, 137, 44, 65, 16, 7, 3, 5, 1, 21, 197, 159, 21, 74, 133, 6, 40, 89, 40, 0, 0, 8, 197, 84, 212, 12, 20, 16, 66, 11, 136, 4, 5, 197, 163, 9, 14, 5, 1, 67, 15, 140, 195, 174, 14, 22, 196, 131, 18, 20, 5, 10, 5, 1, 68, 6, 195, 12, 83, 0, 76, 0, 9, 198, 52, 20, 148, 61, 34, 64, 65, 0, 13, 138, 3, 196, 131, 12, 196, 131, 21, 26, 5, 1, 68, 10, 199, 56, 144, 201, 84, 225, 76, 20, 77, 0, 7, 196, 88, 81, 5, 72, 66, 7, 196, 72, 17, 1, 72, 65, 7, 196, 48, 145, 5, 72, 65, 11, 135, 20, 15, 20, 21, 197, 159, 9, 65, 28, 0, 8, 197, 36, 224, 77, 36, 48, 67, 8, 197, 32, 242, 15, 80, 80, 65, 11, 136, 3, 195, 162, 20, 21, 197, 159, 9, 65, 8, 197, 52, 241, 5, 72, 16, 67, 8, 197, 13, 85, 133, 56, 144, 67, 13, 69, 16, 242, 76, 20, 16, 70, 6, 118, 55, 133, 0, 0, 9, 198, 64, 144, 212, 61, 34, 64, 65, 9, 198, 24, 16, 212, 61, 34, 64, 65, 5, 194, 13, 80, 72, 0, 0, 0, 11, 136, 2, 15, 13, 2, 196, 131, 14, 5, 65, 0, 17, 70, 77, 84, 144, 49, 84, 192, 87, 40, 16, 48, 55, 6, 40, 87, 0, 12, 137, 13, 5, 14, 197, 163, 9, 14, 5, 13, 66, 0, 10, 199, 16, 84, 195, 32, 145, 5, 52, 66, 0, 12, 67, 80, 22, 9, 47, 6, 35, 49, 87, 37, 0, 13, 68, 64, 149, 73, 20, 48, 6, 37, 40, 37, 36, 0, 7, 196, 13, 81, 197, 80, 65, 14, 139, 3, 12, 196, 131, 14, 197, 163, 196, 131, 14, 5, 65, 0, 11, 136, 195, 174, 14, 7, 18, 9, 10, 9, 67, 0, 0, 9, 198, 64, 144, 212, 61, 34, 73, 65, 0, 7, 196, 72, 244, 212, 36, 66, 0, 0, 9, 198, 56, 147, 69, 72, 80, 64, 67, 9, 198, 16, 245, 133, 16, 80, 64, 67, 0, 0, 7, 196, 9, 80, 213, 72, 65, 7, 196, 60, 53, 80, 4, 67, 0, 8, 197, 80, 84, 141, 20, 224, 65, 0, 12, 137, 19, 20, 18, 195, 162, 14, 7, 5, 13, 65, 9, 198, 12, 19, 129, 64, 80, 64, 67, 0, 11, 67, 72, 80, 76, 34, 36, 6, 35, 55, 0, 10, 199, 36, 228, 208, 20, 53, 15, 72, 66, 13, 138, 195, 174, 14, 20, 195, 162, 13, 16, 12, 1, 67, 0, 7, 196, 81, 33, 67, 84, 66, 7, 196, 48, 147, 149, 96, 65, 0, 0, 9, 198, 60, 34, 67, 20, 149, 64, 67, 0, 0, 11, 200, 36, 224, 77, 36, 50, 76, 61, 32, 67, 10, 135, 18, 5, 21, 197, 159, 5, 1, 67, 7, 196, 28, 243, 133, 4, 66, 10, 135, 3, 5, 18, 197, 159, 5, 1, 66, 13, 68, 5, 32, 213, 36, 35, 34, 49, 40, 6, 37, 0, 0, 8, 197, 72, 240, 133, 73, 64, 65, 6, 195, 84, 227, 210, 73, 0, 11, 66, 16, 80, 70, 133, 0, 72, 81, 97, 32, 25, 66, 16, 80, 70, 2, 36, 15, 35, 47, 6, 40, 50, 74, 122, 0, 8, 81, 97, 116, 117, 110, 99, 105, 32, 14, 66, 16, 80, 70, 36, 55, 35, 0, 72, 81, 108, 97, 32, 5, 194, 16, 80, 72, 0, 7, 195, 88, 82, 64, 76, 32, 0, 7, 196, 72, 84, 212, 84, 65, 7, 196, 104, 37, 82, 4, 66, 0, 8, 197, 4, 210, 78, 80, 144, 67, 0, 9, 198, 20, 225, 82, 28, 146, 64, 20, 8, 133, 18, 196, 131, 3, 9, 66, 0, 10, 199, 65, 35, 193, 77, 1, 84, 20, 65, 19, 70, 24, 20, 141, 4, 50, 69, 81, 35, 14, 16, 63, 35, 74, 6, 37, 36, 0, 9, 134, 1, 13, 196, 131, 7, 9, 67, 0, 11, 67, 80, 21, 9, 47, 6, 35, 47, 37, 0, 16, 4, 95, 4, 16, 20, 10, 82, 6, 37, 34, 79, 40, 55, 13, 0, 0, 15, 69, 64, 20, 143, 16, 144, 48, 35, 16, 39, 70, 6, 37, 0, 0, 8, 133, 16, 196, 131, 4, 21, 66, 0, 0, 8, 196, 36, 228, 213, 48, 65, 18, 6, 195, 32, 147, 69, 66, 0, 15, 69, 77, 84, 208, 85, 48, 87, 40, 87, 48, 6, 40, 87, 0, 14, 69, 32, 147, 132, 85, 48, 37, 50, 70, 6, 40, 87, 0, 0, 0, 0, 22, 72, 76, 83, 73, 65, 35, 196, 85, 48, 87, 36, 63, 37, 48, 16, 39, 70, 6, 40, 87, 0, 6, 195, 73, 83, 1, 66, 7, 196, 21, 99, 195, 4, 67, 13, 68, 61, 53, 15, 36, 39, 87, 47, 39, 6, 37, 0, 0, 0, 9, 198, 64, 145, 82, 16, 83, 64, 65, 6, 194, 4, 192, 72, 28, 0, 0, 7, 196, 76, 148, 212, 4, 66, 10, 3, 95, 35, 57, 47, 6, 35, 69, 0, 13, 4, 95, 20, 12, 4, 47, 6, 37, 55, 70, 13, 0, 0, 0, 9, 198, 80, 82, 135, 32, 80, 64, 66, 9, 198, 65, 85, 5, 72, 80, 64, 66, 12, 201, 36, 225, 146, 5, 53, 18, 84, 53, 21, 68, 18, 70, 16, 148, 212, 73, 84, 192, 70, 37, 87, 47, 14, 16, 6, 40, 87, 0, 0, 14, 67, 72, 68, 192, 6, 36, 34, 70, 36, 6, 36, 87, 0, 10, 199, 12, 20, 129, 13, 65, 82, 20, 67, 0, 13, 5, 14, 15, 21, 196, 131, 50, 6, 39, 40, 13, 0, 13, 68, 12, 243, 15, 72, 49, 39, 55, 6, 39, 16, 0, 7, 196, 76, 53, 84, 36, 66, 0, 11, 136, 18, 195, 162, 14, 10, 5, 20, 5, 65, 12, 201, 77, 84, 18, 4, 84, 212, 36, 208, 64, 69, 0, 9, 198, 65, 35, 214, 60, 48, 64, 67, 18, 70, 5, 4, 143, 64, 144, 64, 35, 48, 14, 16, 39, 48, 37, 6, 35, 0, 0, 10, 199, 52, 85, 1, 24, 244, 137, 12, 67, 15, 6, 3, 196, 131, 21, 20, 1, 49, 13, 40, 47, 6, 35, 0, 0, 7, 196, 24, 83, 137, 96, 65, 0, 13, 6, 3, 1, 21, 20, 196, 131, 49, 112, 47, 13, 0, 0, 9, 198, 88, 144, 212, 36, 209, 64, 65, 9, 198, 77, 64, 84, 84, 145, 64, 66, 0, 11, 136, 6, 12, 1, 13, 21, 18, 196, 131, 65, 9, 134, 7, 18, 196, 131, 2, 9, 68, 0, 7, 196, 57, 83, 65, 36, 65, 7, 196, 24, 83, 9, 96, 65, 7, 196, 88, 83, 133, 4, 66, 7, 196, 57, 83, 69, 4, 66, 0, 0, 9, 198, 88, 149, 18, 20, 113, 64, 65, 9, 198, 12, 243, 150, 36, 225, 192, 66, 6, 194, 4, 208, 76, 32, 0, 0, 7, 196, 85, 66, 76, 20, 66, 9, 198, 4, 210, 67, 36, 195, 210, 66, 7, 196, 32, 243, 2, 4, 66, 0, 8, 197, 29, 85, 21, 36, 80, 66, 8, 197, 12, 240, 201, 56, 80, 65, 11, 136, 16, 12, 195, 162, 14, 7, 5, 1, 66, 8, 197, 60, 66, 72, 56, 144, 67, 7, 132, 195, 174, 13, 9, 72, 0, 9, 198, 4, 100, 137, 12, 146, 64, 65, 0, 0, 13, 68, 77, 84, 21, 76, 87, 40, 48, 6, 40, 87, 0, 7, 196, 25, 83, 69, 28, 65, 0, 8, 197, 64, 20, 134, 84, 208, 66, 16, 69, 13, 34, 83, 80, 144, 49, 14, 16, 6, 37, 87, 47, 37, 0, 11, 136, 19, 195, 162, 14, 7, 5, 18, 1, 67, 11, 136, 18, 196, 131, 20, 196, 131, 3, 9, 67, 11, 136, 18, 196, 131, 20, 196, 131, 3, 9, 67, 8, 197, 32, 242, 15, 80, 144, 67, 19, 8, 3, 195, 162, 197, 163, 9, 22, 1, 49, 110, 121, 122, 82, 6, 35, 0, 78, 0, 9, 198, 88, 149, 18, 20, 114, 64, 65, 9, 198, 48, 16, 210, 36, 210, 64, 65, 8, 66, 21, 80, 57, 113, 0, 76, 0, 0, 7, 196, 89, 82, 69, 80, 65, 10, 135, 197, 159, 21, 9, 5, 18, 1, 67, 0, 19, 8, 3, 195, 174, 197, 163, 9, 22, 1, 49, 110, 121, 122, 82, 6, 35, 0, 78, 0, 12, 137, 195, 174, 14, 4, 21, 18, 5, 18, 1, 68, 0, 0, 7, 196, 53, 81, 197, 80, 65, 16, 70, 20, 147, 147, 80, 82, 78, 6, 115, 50, 89, 47, 115, 50, 0, 7, 196, 77, 67, 195, 4, 66, 0, 8, 197, 25, 34, 80, 81, 80, 66, 0, 9, 134, 18, 195, 162, 19, 5, 20, 65, 0, 24, 73, 25, 32, 78, 44, 83, 147, 80, 82, 78, 81, 34, 6, 35, 50, 49, 36, 50, 89, 47, 115, 50, 0, 6, 195, 57, 83, 73, 66, 0, 0, 7, 196, 29, 32, 86, 84, 66, 0, 8, 197, 72, 243, 129, 48, 64, 65, 11, 4, 15, 18, 196, 131, 6, 39, 34, 13, 0, 9, 198, 52, 85, 1, 24, 244, 133, 66, 9, 198, 24, 147, 15, 104, 241, 137, 20, 9, 134, 19, 16, 196, 131, 12, 1, 66, 9, 198, 65, 35, 211, 64, 84, 129, 67, 0, 13, 138, 195, 174, 14, 4, 18, 196, 131, 26, 14, 9, 67, 0, 10, 199, 64, 20, 148, 20, 225, 82, 20, 67, 19, 8, 195, 174, 14, 1, 9, 14, 20, 5, 110, 50, 35, 6, 37, 50, 47, 36, 0, 15, 6, 6, 196, 131, 18, 196, 131, 81, 4, 13, 34, 13, 0, 8, 0, 7, 196, 80, 19, 135, 60, 66, 8, 133, 3, 196, 131, 26, 21, 66, 12, 201, 16, 84, 195, 60, 228, 201, 16, 84, 129, 69, 0, 9, 198, 76, 80, 213, 72, 144, 197, 67, 9, 198, 52, 84, 193, 28, 84, 129, 67, 9, 198, 36, 224, 201, 56, 84, 129, 68, 9, 198, 16, 84, 195, 85, 32, 193, 67, 0, 9, 198, 52, 85, 1, 24, 244, 128, 66, 10, 135, 12, 21, 3, 18, 196, 131, 13, 66, 0, 11, 136, 195, 174, 14, 1, 9, 14, 20, 1, 67, 9, 134, 16, 195, 162, 14, 196, 131, 8, 7, 132, 20, 196, 131, 21, 76, 0, 10, 135, 12, 1, 20, 21, 18, 196, 131, 65, 7, 196, 65, 34, 77, 36, 66, 0, 11, 136, 22, 196, 131, 4, 21, 22, 196, 131, 65, 11, 136, 20, 18, 5, 13, 21, 18, 196, 131, 65, 11, 136, 16, 196, 131, 20, 21, 18, 196, 131, 65, 11, 136, 13, 196, 131, 20, 21, 18, 196, 131, 65, 11, 136, 5, 12, 9, 2, 5, 18, 196, 131, 68, 13, 138, 3, 21, 13, 16, 196, 131, 18, 196, 131, 13, 67, 0, 10, 135, 3, 196, 131, 18, 21, 9, 1, 73, 0, 13, 138, 3, 21, 20, 18, 5, 13, 21, 18, 196, 131, 66, 0, 8, 133, 20, 196, 131, 3, 21, 66, 7, 196, 16, 244, 133, 4, 66, 7, 196, 12, 84, 133, 4, 66, 14, 68, 4, 116, 133, 4, 35, 79, 14, 16, 36, 6, 35, 0, 7, 196, 12, 84, 133, 4, 66, 12, 137, 197, 159, 196, 131, 19, 5, 12, 5, 1, 65, 0, 13, 138, 14, 5, 22, 196, 131, 19, 20, 21, 9, 5, 67, 9, 134, 18, 195, 162, 4, 5, 1, 66, 23, 10, 15, 18, 9, 3, 196, 131, 18, 21, 9, 1, 39, 16, 122, 49, 13, 34, 40, 37, 35, 0, 79, 0, 6, 195, 88, 83, 137, 66, 10, 135, 1, 197, 163, 9, 14, 20, 9, 67, 10, 135, 3, 196, 131, 18, 5, 9, 1, 73, 0, 10, 135, 4, 196, 131, 18, 196, 131, 20, 66, 26, 4, 197, 159, 46, 1, 89, 37, 11, 35, 89, 4, 35, 15, 63, 115, 15, 70, 36, 48, 6, 35, 34, 47, 36, 0, 0, 0, 8, 197, 48, 16, 207, 52, 144, 65, 8, 197, 36, 226, 77, 36, 144, 65, 13, 138, 3, 196, 131, 18, 196, 131, 18, 21, 9, 5, 68, 8, 197, 88, 83, 133, 72, 16, 67, 8, 197, 4, 193, 82, 28, 16, 67, 23, 10, 15, 18, 9, 3, 196, 131, 18, 5, 9, 1, 39, 16, 122, 49, 13, 34, 36, 37, 35, 0, 79, 0, 13, 138, 195, 174, 14, 4, 196, 131, 18, 196, 131, 20, 67, 14, 139, 6, 12, 196, 131, 3, 196, 131, 18, 21, 9, 5, 67, 0, 10, 199, 64, 20, 148, 20, 225, 82, 36, 67, 10, 199, 12, 19, 132, 36, 64, 84, 84, 68, 7, 132, 20, 196, 131, 9, 76, 0, 12, 137, 26, 7, 195, 162, 18, 9, 5, 20, 21, 68, 11, 200, 64, 20, 148, 20, 225, 82, 36, 144, 67, 7, 196, 13, 82, 86, 4, 66, 11, 200, 65, 33, 83, 85, 5, 78, 20, 16, 68, 0, 8, 197, 84, 225, 5, 88, 16, 67, 8, 197, 81, 33, 67, 20, 208, 65, 9, 134, 4, 5, 197, 163, 9, 9, 66, 9, 198, 5, 68, 137, 9, 82, 65, 68, 13, 138, 19, 196, 131, 22, 195, 162, 18, 197, 159, 9, 67, 8, 197, 16, 85, 133, 56, 144, 67, 0, 10, 135, 2, 196, 131, 20, 196, 131, 9, 66, 0, 7, 195, 16, 147, 128, 72, 28, 0, 7, 196, 5, 66, 78, 28, 66, 0, 9, 198, 12, 243, 210, 16, 243, 129, 68, 0, 14, 139, 195, 174, 14, 7, 8, 9, 197, 163, 9, 20, 21, 68, 0, 20, 71, 76, 84, 150, 36, 50, 85, 48, 87, 36, 34, 82, 6, 37, 74, 57, 40, 55, 0, 11, 136, 22, 5, 197, 159, 20, 5, 10, 9, 67, 0, 7, 196, 21, 3, 195, 36, 65, 0, 9, 134, 3, 196, 131, 12, 3, 1, 66, 14, 3, 3, 6, 46, 99, 111, 110, 102, 111, 114, 109, 0, 29, 0, 16, 7, 19, 16, 1, 197, 163, 9, 21, 87, 48, 35, 121, 57, 40, 0, 17, 70, 56, 144, 201, 13, 83, 64, 50, 37, 74, 122, 49, 6, 40, 63, 0, 0, 0, 7, 196, 5, 34, 80, 36, 65, 7, 196, 37, 34, 84, 4, 67, 7, 196, 21, 98, 84, 4, 67, 0, 13, 138, 195, 174, 14, 7, 8, 9, 15, 14, 20, 9, 67, 0, 9, 198, 72, 81, 201, 104, 244, 128, 66, 11, 136, 16, 12, 195, 162, 14, 7, 5, 18, 65, 11, 67, 13, 35, 201, 49, 34, 39, 6, 37, 0, 0, 9, 134, 20, 21, 18, 14, 196, 131, 66, 7, 195, 16, 20, 128, 72, 8, 0, 0, 11, 136, 18, 5, 16, 12, 9, 3, 196, 131, 65, 11, 136, 9, 13, 16, 12, 9, 3, 196, 131, 66, 9, 198, 4, 115, 15, 52, 84, 129, 68, 0, 10, 135, 26, 2, 21, 18, 196, 131, 13, 66, 12, 137, 20, 196, 131, 22, 9, 197, 163, 196, 131, 66, 0, 11, 136, 18, 5, 16, 1, 18, 196, 131, 13, 67, 7, 132, 196, 131, 9, 1, 77, 0, 12, 137, 3, 15, 13, 16, 1, 18, 196, 131, 13, 67, 10, 135, 1, 18, 20, 5, 18, 196, 131, 66, 0, 13, 138, 22, 195, 162, 14, 196, 131, 20, 196, 131, 9, 67, 13, 138, 19, 20, 18, 5, 3, 21, 18, 196, 131, 13, 67, 13, 138, 18, 5, 3, 21, 16, 5, 18, 196, 131, 13, 68, 11, 136, 16, 1, 14, 20, 5, 18, 196, 131, 66, 0, 14, 139, 22, 195, 162, 12, 22, 196, 131, 20, 196, 131, 9, 67, 10, 135, 1, 19, 20, 196, 131, 26, 9, 65, 10, 135, 22, 195, 162, 19, 12, 5, 1, 66, 0, 11, 4, 2, 196, 131, 21, 69, 13, 6, 40, 0, 0, 9, 134, 12, 1, 26, 196, 131, 18, 65, 16, 141, 195, 174, 14, 6, 196, 131, 197, 159, 21, 18, 196, 131, 13, 68, 7, 196, 24, 84, 133, 4, 66, 0, 13, 138, 195, 174, 14, 22, 196, 131, 18, 20, 5, 1, 67, 0, 8, 66, 20, 144, 57, 116, 0, 76, 16, 66, 12, 208, 99, 101, 110, 116, 105, 109, 101, 116, 114, 105, 0, 29, 0, 0, 13, 68, 16, 81, 21, 76, 70, 36, 70, 6, 40, 87, 0, 0, 8, 197, 72, 84, 5, 16, 80, 65, 8, 197, 64, 19, 9, 16, 80, 65, 8, 197, 52, 243, 137, 12, 16, 66, 8, 197, 12, 243, 132, 20, 144, 66, 9, 134, 3, 196, 131, 12, 4, 21, 66, 10, 135, 1, 3, 15, 16, 196, 131, 18, 66, 8, 197, 88, 244, 130, 20, 16, 66, 8, 197, 80, 243, 5, 72, 16, 67, 8, 197, 72, 83, 5, 88, 16, 67, 8, 197, 72, 81, 149, 104, 16, 67, 8, 197, 60, 35, 9, 28, 16, 67, 8, 197, 16, 84, 208, 72, 80, 28, 0, 14, 139, 1, 12, 2, 196, 131, 19, 20, 18, 21, 9, 5, 67, 0, 10, 135, 20, 195, 162, 18, 3, 15, 12, 66, 0, 0, 8, 197, 77, 5, 78, 20, 16, 66, 8, 197, 12, 243, 147, 84, 208, 66, 8, 197, 12, 20, 5, 80, 80, 65, 13, 138, 18, 5, 1, 3, 197, 163, 9, 15, 14, 1, 67, 8, 197, 16, 145, 197, 72, 16, 67, 8, 197, 52, 21, 1, 48, 80, 78, 0, 10, 135, 19, 16, 5, 18, 196, 131, 13, 66, 10, 135, 15, 16, 5, 18, 196, 131, 13, 67, 6, 195, 24, 84, 137, 66, 0, 11, 136, 19, 20, 18, 15, 16, 197, 159, 9, 66, 0, 0, 17, 70, 88, 241, 1, 24, 243, 133, 82, 6, 39, 70, 35, 81, 39, 50, 0, 9, 198, 64, 20, 193, 28, 84, 137, 67, 0, 14, 139, 18, 5, 3, 5, 16, 197, 163, 9, 15, 14, 5, 68, 14, 139, 5, 3, 8, 9, 12, 9, 2, 18, 196, 131, 13, 68, 0, 11, 136, 18, 196, 131, 19, 3, 15, 12, 9, 67, 0, 0, 0, 0, 0, 0, 0, 9, 134, 20, 1, 20, 196, 131, 12, 65, 9, 198, 16, 84, 201, 29, 84, 128, 66, 10, 67, 4, 128, 65, 35, 105, 6, 35, 0, 9, 198, 81, 34, 85, 52, 96, 64, 67, 9, 198, 21, 128, 77, 36, 224, 64, 68, 9, 198, 5, 48, 213, 49, 64, 64, 67, 10, 135, 18, 5, 7, 196, 131, 19, 9, 67, 12, 67, 16, 16, 193, 70, 35, 49, 13, 0, 72, 8, 0, 6, 195, 60, 51, 204, 66, 10, 67, 4, 128, 64, 35, 105, 6, 35, 0, 11, 136, 3, 196, 131, 16, 196, 131, 20, 1, 67, 10, 199, 72, 244, 212, 60, 115, 204, 36, 68, 0, 10, 135, 18, 9, 4, 9, 3, 196, 131, 66, 7, 196, 52, 19, 148, 4, 66, 0, 11, 136, 13, 195, 162, 14, 5, 3, 196, 131, 65, 11, 136, 9, 14, 20, 18, 9, 7, 196, 131, 65, 11, 136, 5, 24, 16, 12, 9, 3, 196, 131, 66, 9, 134, 14, 9, 197, 159, 20, 5, 73, 0, 10, 135, 9, 14, 20, 18, 196, 131, 13, 66, 0, 13, 138, 195, 174, 14, 22, 196, 131, 197, 163, 196, 131, 67, 10, 3, 226, 130, 172, 6, 113, 16, 39, 0, 0, 14, 139, 16, 196, 131, 18, 20, 9, 3, 9, 3, 196, 131, 67, 12, 137, 3, 15, 14, 6, 9, 197, 159, 20, 5, 66, 0, 14, 69, 8, 19, 142, 21, 32, 69, 6, 36, 50, 13, 34, 0, 9, 134, 16, 12, 196, 131, 20, 9, 66, 0, 6, 195, 72, 80, 201, 65, 0, 13, 138, 195, 174, 13, 2, 18, 196, 131, 3, 196, 131, 67, 0, 12, 137, 6, 12, 196, 131, 3, 196, 131, 18, 9, 65, 0, 13, 5, 1, 18, 196, 131, 20, 35, 34, 6, 13, 47, 0, 0, 9, 198, 80, 16, 129, 12, 129, 64, 67, 9, 198, 65, 35, 195, 20, 69, 64, 67, 0, 0, 7, 196, 81, 33, 90, 36, 66, 0, 8, 197, 60, 19, 69, 56, 144, 65, 8, 197, 52, 84, 135, 20, 208, 65, 8, 197, 28, 83, 69, 56, 144, 65, 8, 197, 16, 19, 66, 48, 16, 66, 8, 197, 12, 244, 212, 84, 208, 66, 8, 197, 16, 148, 197, 12, 16, 67, 0, 6, 195, 72, 85, 137, 66, 0, 0, 12, 137, 6, 12, 196, 131, 3, 196, 131, 18, 1, 65, 7, 196, 13, 83, 86, 4, 66, 7, 196, 88, 244, 130, 36, 66, 7, 196, 64, 244, 142, 36, 66, 0, 9, 134, 19, 20, 196, 131, 20, 21, 66, 8, 197, 37, 53, 15, 88, 144, 67, 11, 3, 95, 50, 6, 70, 6, 39, 40, 13, 0, 0, 10, 135, 16, 1, 19, 196, 131, 18, 5, 65, 9, 198, 36, 208, 71, 36, 226, 64, 66, 0, 11, 136, 21, 13, 6, 12, 196, 131, 20, 21, 67, 10, 199, 77, 64, 78, 16, 20, 132, 20, 65, 25, 11, 195, 174, 14, 196, 131, 21, 14, 20, 18, 21, 12, 110, 50, 13, 6, 40, 50, 47, 14, 16, 40, 55, 0, 11, 136, 2, 196, 131, 20, 196, 131, 20, 21, 67, 0, 7, 196, 52, 84, 137, 80, 65, 12, 137, 3, 18, 196, 131, 16, 196, 131, 20, 21, 67, 12, 137, 1, 12, 9, 14, 20, 196, 131, 20, 21, 68, 11, 200, 36, 229, 5, 73, 162, 67, 20, 16, 68, 11, 200, 36, 229, 5, 73, 49, 67, 80, 16, 68, 7, 196, 5, 5, 67, 4, 67, 0, 0, 9, 198, 44, 83, 5, 52, 83, 128, 65, 14, 139, 195, 174, 14, 22, 196, 131, 20, 196, 131, 20, 21, 68, 31, 14, 4, 9, 14, 195, 174, 14, 196, 131, 21, 14, 20, 18, 21, 12, 70, 37, 50, 110, 50, 13, 6, 40, 50, 47, 14, 16, 40, 55, 0, 0, 15, 140, 195, 174, 14, 3, 18, 21, 14, 20, 196, 131, 20, 21, 68, 11, 136, 16, 196, 131, 3, 196, 131, 12, 9, 67, 0, 7, 196, 84, 197, 9, 52, 65, 7, 196, 17, 82, 85, 52, 66, 12, 137, 19, 6, 195, 162, 18, 20, 5, 3, 1, 67, 0, 9, 198, 28, 80, 77, 4, 225, 21, 67, 0, 9, 66, 20, 192, 57, 36, 55, 0, 76, 0, 11, 136, 3, 195, 162, 14, 20, 5, 3, 5, 65, 15, 3, 95, 50, 48, 70, 39, 40, 13, 86, 6, 36, 74, 122, 0, 0, 11, 200, 52, 17, 201, 77, 68, 129, 81, 80, 68, 0, 9, 198, 17, 83, 73, 56, 144, 193, 66, 0, 9, 198, 25, 33, 68, 60, 224, 64, 67, 9, 133, 4, 1, 3, 196, 131, 72, 8, 0, 11, 136, 197, 159, 21, 2, 18, 5, 4, 5, 65, 9, 134, 16, 12, 5, 3, 196, 131, 66, 10, 134, 1, 4, 9, 3, 196, 131, 66, 28, 0, 10, 135, 16, 9, 19, 9, 3, 196, 131, 66, 10, 135, 1, 16, 12, 5, 3, 196, 131, 67, 7, 196, 12, 243, 148, 4, 66, 10, 135, 5, 24, 9, 19, 20, 196, 131, 72, 0, 11, 136, 6, 15, 18, 6, 15, 20, 196, 131, 65, 11, 136, 1, 3, 5, 1, 19, 20, 196, 131, 76, 0, 9, 198, 65, 35, 212, 60, 51, 204, 67, 9, 198, 80, 19, 80, 60, 224, 64, 67, 15, 4, 95, 13, 3, 14, 63, 35, 49, 14, 16, 6, 39, 50, 0, 0, 9, 134, 19, 20, 15, 3, 196, 131, 66, 15, 3, 95, 51, 48, 47, 14, 16, 116, 86, 6, 36, 74, 122, 0, 0, 12, 137, 19, 20, 18, 9, 7, 196, 131, 20, 5, 65, 7, 196, 52, 21, 5, 36, 66, 22, 11, 7, 196, 131, 7, 196, 131, 21, 197, 163, 196, 131, 79, 13, 79, 13, 6, 40, 121, 13, 0, 0, 11, 136, 3, 5, 18, 3, 5, 20, 196, 131, 67, 0, 9, 198, 5, 99, 195, 5, 69, 64, 68, 0, 11, 136, 16, 18, 5, 7, 196, 131, 20, 9, 67, 0, 8, 133, 13, 196, 131, 19, 21, 66, 0, 9, 198, 12, 147, 131, 36, 193, 65, 65, 0, 18, 70, 61, 34, 67, 36, 225, 64, 39, 16, 122, 74, 4, 37, 50, 36, 0, 79, 0, 0, 12, 137, 13, 21, 12, 197, 163, 21, 13, 5, 1, 67, 8, 133, 195, 174, 197, 163, 9, 72, 0, 8, 197, 88, 147, 132, 20, 208, 65, 8, 197, 84, 212, 12, 20, 208, 65, 0, 0, 10, 199, 65, 35, 198, 21, 51, 210, 36, 66, 10, 199, 12, 83, 5, 48, 19, 20, 20, 79, 0, 0, 14, 69, 37, 2, 15, 56, 80, 35, 37, 81, 6, 128, 50, 0, 0, 10, 135, 2, 15, 18, 196, 131, 20, 21, 67, 0, 11, 136, 3, 196, 131, 26, 196, 131, 20, 21, 67, 11, 136, 195, 174, 14, 20, 18, 5, 2, 1, 67, 0, 8, 133, 12, 196, 131, 19, 1, 66, 0, 13, 138, 195, 174, 14, 10, 21, 18, 196, 131, 20, 21, 68, 0, 0, 11, 136, 3, 196, 131, 19, 196, 131, 16, 9, 67, 0, 7, 196, 56, 85, 5, 16, 65, 9, 198, 12, 243, 147, 36, 65, 82, 66, 7, 196, 48, 19, 147, 4, 66, 7, 196, 16, 19, 147, 4, 66, 0, 17, 142, 195, 174, 14, 6, 196, 131, 197, 159, 21, 18, 196, 131, 20, 21, 69, 9, 134, 195, 174, 14, 5, 3, 1, 67, 0, 0, 9, 134, 13, 9, 197, 159, 20, 15, 66, 18, 70, 36, 229, 18, 60, 69, 83, 37, 50, 47, 34, 39, 70, 6, 40, 87, 0, 15, 3, 95, 51, 88, 47, 14, 16, 6, 116, 86, 36, 74, 122, 0, 13, 3, 95, 54, 48, 89, 115, 86, 6, 36, 74, 122, 0, 0, 7, 196, 76, 17, 9, 12, 65, 20, 9, 15, 1, 18, 5, 197, 159, 9, 3, 5, 39, 35, 16, 36, 89, 74, 36, 0, 68, 7, 196, 13, 33, 90, 84, 66, 11, 3, 95, 48, 67, 87, 6, 40, 47, 36, 0, 0, 0, 6, 195, 41, 80, 193, 66, 9, 198, 25, 84, 142, 37, 160, 64, 67, 0, 0, 0, 12, 4, 95, 48, 90, 51, 63, 6, 130, 63, 37, 0, 0, 9, 198, 72, 80, 76, 37, 160, 64, 68, 9, 198, 16, 148, 195, 85, 64, 64, 67, 9, 198, 12, 84, 131, 21, 64, 64, 67, 14, 4, 95, 48, 90, 50, 87, 6, 40, 47, 37, 63, 37, 0, 0, 11, 136, 18, 5, 197, 163, 9, 14, 5, 13, 66, 16, 3, 95, 55, 48, 89, 35, 48, 47, 36, 86, 6, 36, 74, 122, 0, 0, 10, 135, 22, 9, 26, 9, 20, 196, 131, 65, 10, 135, 3, 196, 131, 21, 20, 196, 131, 67, 13, 3, 95, 49, 67, 4, 39, 87, 6, 40, 47, 13, 0, 0, 9, 198, 16, 84, 15, 104, 149, 5, 66, 0, 9, 198, 36, 224, 213, 49, 69, 64, 67, 6, 195, 12, 81, 1, 66, 0, 11, 136, 26, 21, 7, 18, 196, 131, 22, 9, 67, 0, 7, 196, 32, 242, 15, 80, 65, 0, 8, 197, 76, 147, 131, 21, 32, 65, 9, 198, 72, 84, 208, 20, 53, 1, 67, 0, 9, 198, 9, 80, 149, 37, 69, 64, 68, 9, 198, 4, 101, 77, 5, 69, 64, 68, 6, 194, 48, 16, 72, 28, 9, 198, 88, 240, 83, 81, 33, 64, 76, 9, 198, 56, 240, 83, 81, 33, 64, 77, 9, 198, 4, 229, 77, 37, 65, 64, 75, 20, 3, 95, 49, 57, 50, 6, 129, 13, 87, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 0, 6, 195, 72, 84, 212, 65, 11, 136, 1, 13, 196, 131, 18, 21, 9, 5, 67, 19, 3, 95, 49, 56, 6, 39, 48, 121, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 0, 13, 68, 20, 229, 5, 72, 36, 50, 47, 13, 34, 0, 65, 16, 3, 95, 50, 67, 70, 6, 39, 40, 13, 87, 6, 40, 47, 36, 0, 0, 13, 138, 16, 196, 131, 19, 196, 131, 18, 21, 9, 5, 67, 8, 197, 29, 83, 5, 72, 80, 65, 13, 138, 6, 18, 9, 7, 196, 131, 18, 21, 9, 5, 67, 13, 138, 3, 196, 131, 13, 196, 131, 18, 21, 9, 5, 67, 8, 197, 12, 240, 143, 72, 16, 67, 8, 197, 37, 161, 207, 56, 144, 67, 0, 0, 11, 136, 19, 6, 195, 162, 18, 197, 159, 9, 66, 0, 7, 196, 36, 225, 9, 12, 66, 7, 196, 16, 19, 148, 84, 66, 7, 196, 88, 144, 146, 4, 66, 0, 8, 197, 64, 20, 143, 48, 80, 66, 8, 197, 52, 19, 143, 48, 80, 66, 0, 10, 135, 21, 19, 3, 196, 131, 20, 21, 67, 6, 195, 12, 83, 5, 77, 19, 3, 95, 49, 49, 6, 40, 50, 87, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 0, 11, 136, 195, 174, 14, 19, 5, 13, 14, 1, 67, 11, 3, 95, 49, 48, 86, 6, 36, 74, 36, 0, 0, 12, 137, 22, 196, 131, 18, 19, 196, 131, 20, 21, 67, 12, 67, 81, 34, 79, 47, 14, 16, 6, 37, 39, 0, 12, 137, 20, 18, 196, 131, 19, 196, 131, 20, 21, 67, 12, 137, 16, 9, 197, 159, 3, 196, 131, 20, 21, 67, 12, 137, 3, 196, 131, 12, 3, 196, 131, 20, 21, 67, 21, 3, 95, 49, 51, 47, 14, 16, 6, 116, 87, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 0, 9, 198, 48, 149, 5, 72, 21, 21, 68, 13, 138, 195, 174, 13, 2, 21, 3, 196, 131, 20, 21, 68, 9, 134, 22, 18, 196, 131, 10, 9, 66, 9, 198, 76, 51, 9, 24, 244, 201, 67, 19, 3, 95, 49, 50, 70, 6, 118, 87, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 0, 14, 139, 195, 174, 14, 20, 15, 18, 19, 196, 131, 20, 21, 68, 14, 139, 1, 13, 5, 19, 20, 5, 3, 196, 131, 20, 21, 69, 20, 3, 95, 49, 53, 74, 6, 37, 50, 87, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 0, 15, 140, 195, 174, 13, 16, 21, 197, 159, 3, 196, 131, 20, 21, 68, 19, 3, 95, 49, 52, 48, 6, 115, 87, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 0, 22, 3, 95, 49, 55, 89, 6, 35, 48, 47, 36, 87, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 0, 9, 198, 16, 81, 197, 72, 21, 21, 68, 7, 195, 65, 34, 78, 72, 28, 19, 3, 95, 49, 54, 89, 6, 115, 87, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 0, 0, 19, 70, 77, 84, 18, 5, 5, 83, 87, 40, 48, 14, 16, 35, 48, 6, 40, 87, 0, 16, 3, 95, 55, 88, 89, 6, 35, 48, 47, 36, 86, 36, 74, 122, 0, 0, 7, 196, 25, 34, 90, 84, 66, 0, 0, 9, 198, 72, 84, 208, 37, 32, 64, 67, 9, 198, 65, 33, 80, 5, 32, 64, 67, 9, 198, 65, 33, 70, 21, 32, 64, 67, 0, 11, 136, 21, 3, 9, 4, 5, 197, 163, 9, 66, 0, 10, 135, 1, 18, 196, 131, 20, 196, 131, 67, 0, 18, 70, 28, 147, 78, 5, 162, 85, 73, 37, 63, 50, 6, 35, 86, 57, 40, 0, 0, 12, 137, 13, 15, 4, 9, 6, 9, 3, 196, 131, 66, 14, 139, 195, 174, 14, 3, 8, 9, 4, 5, 197, 163, 9, 66, 9, 198, 85, 66, 76, 37, 160, 64, 68, 6, 195, 84, 149, 1, 66, 9, 198, 80, 83, 80, 21, 32, 64, 67, 0, 0, 7, 196, 8, 149, 143, 48, 65, 0, 9, 198, 17, 83, 78, 20, 21, 1, 79, 0, 6, 195, 88, 245, 1, 66, 0, 10, 199, 36, 229, 5, 73, 162, 67, 20, 67, 10, 199, 12, 144, 193, 81, 34, 67, 20, 67, 10, 199, 8, 16, 212, 21, 34, 69, 36, 66, 10, 199, 4, 69, 133, 57, 66, 67, 20, 67, 0, 7, 196, 48, 21, 5, 96, 65, 12, 137, 19, 21, 19, 197, 163, 9, 14, 5, 1, 67, 13, 68, 16, 85, 137, 4, 70, 36, 82, 37, 6, 35, 0, 0, 8, 197, 89, 83, 20, 85, 32, 65, 9, 134, 197, 163, 9, 14, 5, 1, 66, 9, 198, 64, 84, 141, 37, 65, 65, 67, 9, 134, 16, 196, 131, 26, 5, 1, 66, 0, 11, 67, 17, 37, 77, 70, 34, 6, 40, 63, 0, 9, 198, 13, 32, 84, 21, 33, 64, 65, 0, 17, 3, 95, 52, 48, 48, 35, 47, 14, 16, 40, 86, 6, 36, 74, 122, 0, 0, 9, 198, 16, 84, 15, 104, 149, 0, 66, 12, 137, 3, 15, 14, 197, 163, 9, 14, 5, 1, 67, 0, 9, 198, 65, 35, 205, 37, 65, 77, 66, 9, 198, 64, 84, 141, 37, 65, 77, 66, 8, 197, 56, 147, 73, 12, 16, 66, 9, 197, 80, 245, 21, 76, 144, 65, 28, 0, 9, 198, 12, 20, 129, 12, 19, 0, 66, 0, 0, 7, 196, 12, 83, 148, 84, 66, 11, 200, 77, 84, 144, 72, 147, 132, 20, 16, 67, 11, 200, 77, 1, 67, 36, 19, 9, 104, 16, 68, 0, 15, 69, 44, 245, 133, 76, 144, 49, 6, 39, 82, 36, 89, 37, 0, 8, 197, 28, 150, 143, 72, 144, 65, 8, 197, 77, 81, 197, 72, 16, 67, 8, 197, 52, 148, 143, 76, 144, 67, 0, 9, 198, 89, 83, 20, 85, 34, 64, 65, 10, 135, 3, 195, 162, 14, 4, 22, 1, 66, 0, 10, 199, 20, 50, 9, 48, 144, 146, 4, 68, 15, 3, 95, 50, 88, 70, 6, 39, 40, 13, 86, 36, 74, 122, 0, 14, 3, 95, 53, 48, 74, 37, 50, 86, 6, 36, 74, 122, 0, 0, 12, 137, 19, 21, 19, 197, 163, 9, 14, 5, 13, 66, 11, 200, 24, 84, 133, 77, 68, 149, 36, 80, 67, 7, 196, 16, 21, 137, 16, 65, 7, 196, 8, 21, 5, 52, 65, 11, 67, 5, 5, 83, 35, 48, 6, 40, 87, 0, 17, 68, 16, 147, 148, 72, 70, 37, 50, 47, 14, 34, 39, 0, 81, 111, 32, 0, 8, 197, 12, 244, 205, 61, 48, 65, 0, 0, 10, 135, 18, 196, 131, 3, 14, 5, 20, 65, 0, 0, 9, 198, 12, 243, 148, 72, 243, 1, 67, 0, 13, 138, 19, 3, 18, 195, 162, 197, 159, 14, 5, 20, 65, 11, 67, 52, 147, 73, 63, 6, 37, 63, 37, 0, 10, 135, 195, 174, 14, 22, 5, 12, 9, 67, 0, 10, 67, 52, 144, 64, 63, 6, 37, 35, 0, 0, 0, 9, 198, 65, 33, 70, 4, 49, 77, 66, 13, 138, 16, 196, 131, 9, 1, 14, 10, 5, 14, 9, 66, 0, 13, 5, 4, 15, 21, 196, 131, 70, 6, 39, 40, 13, 0, 9, 198, 72, 84, 12, 36, 48, 64, 67, 9, 198, 21, 132, 12, 36, 48, 64, 67, 9, 198, 104, 80, 197, 48, 80, 64, 65, 9, 198, 61, 5, 21, 48, 80, 64, 65, 0, 11, 136, 18, 196, 131, 3, 14, 5, 20, 5, 65, 6, 195, 12, 80, 64, 76, 0, 15, 3, 95, 63, 63, 49, 35, 16, 35, 49, 47, 6, 36, 34, 0, 0, 0, 14, 139, 19, 3, 18, 195, 162, 197, 159, 14, 5, 20, 5, 65, 18, 70, 5, 4, 133, 12, 144, 64, 35, 48, 14, 16, 36, 74, 57, 6, 35, 0, 0, 10, 67, 52, 145, 64, 63, 6, 37, 36, 0, 17, 3, 95, 52, 88, 48, 6, 35, 47, 14, 16, 40, 86, 36, 74, 122, 0, 0, 8, 133, 16, 196, 131, 26, 9, 66, 0, 8, 197, 77, 2, 82, 37, 64, 65, 0, 9, 198, 21, 132, 12, 36, 49, 64, 66, 10, 67, 12, 80, 73, 74, 6, 133, 57, 0, 6, 195, 77, 81, 1, 66, 10, 135, 19, 20, 195, 162, 18, 14, 9, 67, 7, 195, 12, 81, 65, 72, 28, 0, 0, 0, 9, 198, 89, 83, 20, 85, 34, 73, 65, 9, 198, 65, 33, 90, 36, 49, 65, 67, 0, 10, 135, 16, 196, 131, 18, 5, 18, 9, 66, 17, 7, 8, 195, 162, 18, 20, 9, 5, 105, 110, 34, 47, 6, 37, 36, 0, 11, 66, 48, 80, 55, 133, 0, 72, 81, 97, 32, 13, 66, 48, 80, 55, 133, 34, 0, 72, 81, 97, 114, 32, 16, 66, 48, 80, 55, 133, 121, 122, 0, 72, 81, 97, 197, 163, 105, 32, 13, 66, 48, 80, 55, 133, 57, 0, 72, 81, 97, 105, 32, 13, 66, 48, 80, 55, 133, 63, 0, 72, 81, 97, 109, 32, 11, 66, 48, 80, 55, 133, 0, 72, 81, 97, 32, 5, 194, 48, 80, 72, 15, 66, 44, 112, 107, 105, 108, 111, 103, 114, 97, 109, 101, 0, 29, 0, 14, 3, 95, 53, 88, 74, 6, 37, 50, 86, 36, 74, 122, 0, 14, 3, 95, 56, 48, 39, 48, 47, 86, 6, 36, 74, 122, 0, 0, 9, 198, 81, 35, 211, 56, 85, 0, 65, 7, 196, 72, 145, 9, 12, 66, 7, 196, 77, 1, 82, 4, 66, 12, 137, 195, 174, 14, 22, 9, 14, 7, 5, 1, 67, 0, 9, 134, 197, 163, 9, 14, 5, 13, 65, 8, 197, 52, 83, 129, 40, 80, 67, 8, 197, 48, 21, 9, 12, 80, 66, 8, 197, 56, 147, 69, 56, 144, 77, 0, 10, 135, 22, 196, 131, 4, 21, 22, 5, 65, 10, 135, 16, 196, 131, 18, 5, 18, 5, 66, 11, 67, 52, 19, 73, 63, 6, 35, 63, 37, 0, 6, 195, 88, 242, 65, 66, 0, 7, 195, 88, 242, 64, 76, 32, 6, 195, 52, 18, 64, 72, 6, 195, 88, 242, 64, 76, 6, 195, 56, 242, 64, 76, 6, 195, 12, 82, 64, 76, 0, 12, 137, 195, 174, 14, 3, 9, 14, 7, 5, 13, 66, 8, 133, 4, 196, 131, 4, 21, 66, 12, 137, 1, 4, 195, 162, 14, 3, 9, 20, 21, 68, 11, 200, 12, 243, 131, 72, 85, 9, 104, 16, 68, 0, 8, 197, 56, 244, 212, 36, 208, 65, 8, 197, 13, 32, 84, 36, 208, 65, 8, 197, 8, 149, 143, 48, 144, 65, 13, 138, 195, 174, 14, 22, 15, 12, 2, 21, 18, 1, 68, 8, 197, 5, 69, 78, 12, 144, 8, 0, 10, 135, 197, 159, 5, 4, 5, 18, 5, 66, 9, 198, 17, 84, 133, 72, 146, 64, 66, 17, 70, 16, 148, 208, 48, 22, 64, 70, 37, 87, 48, 55, 6, 36, 57, 0, 0, 10, 199, 12, 243, 131, 20, 229, 18, 4, 67, 11, 136, 1, 12, 196, 131, 20, 21, 18, 1, 68, 13, 3, 95, 54, 88, 89, 6, 115, 86, 36, 74, 122, 0, 14, 3, 95, 57, 48, 50, 129, 13, 86, 6, 36, 74, 122, 0, 0, 0, 13, 138, 195, 174, 14, 3, 196, 131, 16, 5, 18, 5, 67, 9, 198, 12, 20, 137, 12, 21, 21, 68, 0, 9, 198, 76, 51, 193, 80, 83, 64, 65, 0, 7, 195, 88, 243, 64, 76, 32, 0, 0, 15, 69, 65, 35, 208, 85, 48, 48, 34, 39, 48, 6, 40, 87, 0, 8, 197, 36, 229, 133, 73, 48, 65, 15, 69, 36, 224, 204, 85, 48, 37, 50, 49, 55, 6, 40, 87, 0, 15, 69, 12, 243, 80, 85, 48, 49, 39, 63, 48, 6, 40, 87, 0, 9, 198, 8, 193, 83, 80, 83, 65, 67, 0, 0, 12, 136, 1, 12, 196, 131, 20, 21, 18, 9, 66, 28, 0, 6, 131, 13, 196, 131, 72, 0, 8, 197, 88, 148, 195, 60, 192, 65, 0, 9, 198, 16, 80, 201, 16, 80, 64, 67, 16, 70, 81, 33, 73, 48, 80, 64, 47, 14, 16, 6, 116, 55, 133, 0, 0, 0, 13, 68, 84, 208, 140, 36, 6, 40, 63, 69, 55, 37, 0, 7, 196, 12, 83, 154, 84, 66, 0, 0, 11, 136, 3, 18, 195, 162, 14, 3, 5, 14, 65, 0, 18, 7, 15, 18, 9, 3, 195, 162, 20, 39, 16, 122, 49, 4, 110, 47, 0, 76, 14, 3, 95, 56, 88, 6, 39, 48, 47, 86, 36, 74, 122, 0, 0, 0, 12, 201, 64, 20, 193, 28, 84, 137, 48, 244, 128, 67, 11, 136, 13, 21, 18, 13, 21, 18, 196, 131, 65, 0, 9, 198, 76, 19, 83, 84, 225, 192, 65, 6, 195, 28, 83, 85, 66, 0, 11, 136, 195, 174, 13, 16, 12, 5, 20, 9, 67, 0, 0, 8, 197, 77, 81, 140, 21, 64, 65, 13, 138, 18, 196, 131, 19, 16, 21, 20, 5, 18, 9, 67, 9, 198, 17, 32, 71, 61, 53, 5, 65, 8, 197, 13, 33, 73, 21, 32, 65, 9, 134, 9, 5, 197, 159, 5, 1, 66, 0, 10, 135, 197, 159, 15, 6, 5, 18, 9, 66, 10, 66, 48, 112, 36, 55, 73, 6, 37, 0, 9, 198, 36, 224, 77, 36, 49, 64, 67, 18, 70, 16, 21, 15, 72, 145, 64, 70, 35, 47, 39, 14, 16, 6, 37, 36, 0, 10, 135, 12, 196, 131, 18, 7, 5, 1, 66, 0, 10, 199, 64, 20, 193, 28, 84, 137, 36, 67, 11, 136, 4, 5, 19, 6, 196, 131, 3, 21, 67, 14, 3, 95, 57, 88, 50, 6, 129, 13, 86, 36, 74, 122, 0, 0, 13, 138, 197, 159, 15, 6, 5, 18, 9, 12, 15, 18, 66, 13, 138, 3, 196, 131, 4, 5, 18, 9, 12, 15, 18, 66, 0, 14, 139, 19, 3, 196, 131, 4, 5, 18, 9, 12, 15, 18, 66, 8, 197, 5, 53, 80, 72, 16, 28, 0, 10, 135, 8, 195, 162, 18, 20, 9, 9, 66, 10, 135, 3, 195, 162, 20, 5, 22, 1, 67, 10, 135, 1, 20, 195, 162, 18, 14, 1, 67, 0, 11, 136, 197, 159, 20, 5, 18, 7, 5, 13, 65, 10, 199, 64, 84, 147, 21, 97, 82, 4, 68, 10, 199, 16, 84, 195, 61, 1, 82, 36, 68, 0, 0, 8, 197, 88, 81, 5, 72, 80, 66, 8, 197, 77, 5, 78, 20, 208, 65, 13, 138, 195, 174, 14, 20, 15, 1, 18, 3, 5, 13, 66, 8, 197, 72, 86, 133, 52, 16, 67, 8, 197, 72, 148, 201, 64, 144, 67, 0, 10, 135, 3, 196, 131, 4, 5, 18, 5, 66, 9, 198, 76, 51, 212, 60, 50, 64, 67, 0, 11, 136, 19, 3, 196, 131, 4, 5, 18, 5, 66, 11, 136, 22, 195, 162, 14, 20, 21, 18, 1, 67, 0, 8, 133, 2, 196, 131, 7, 1, 66, 0, 9, 134, 13, 9, 197, 159, 3, 1, 66, 0, 0, 15, 140, 3, 8, 5, 12, 196, 131, 12, 196, 131, 9, 20, 21, 69, 0, 0, 0, 0, 6, 194, 36, 224, 72, 28, 0, 11, 67, 77, 82, 84, 87, 40, 6, 37, 47, 0, 12, 137, 195, 174, 13, 16, 21, 197, 159, 3, 1, 67, 0, 13, 68, 76, 81, 21, 76, 87, 36, 70, 6, 40, 87, 0, 0, 0, 9, 198, 64, 130, 76, 37, 4, 192, 65, 9, 198, 36, 229, 18, 36, 112, 64, 65, 0, 9, 198, 21, 128, 83, 64, 84, 129, 68, 9, 198, 4, 48, 197, 48, 84, 129, 68, 14, 4, 95, 15, 7, 15, 39, 79, 39, 50, 6, 36, 49, 0, 0, 12, 137, 195, 174, 14, 20, 18, 5, 2, 196, 131, 67, 13, 3, 197, 159, 9, 89, 122, 35, 0, 72, 81, 97, 32, 6, 131, 197, 159, 9, 72, 0, 9, 134, 15, 6, 5, 18, 196, 131, 66, 0, 18, 70, 21, 35, 201, 48, 244, 128, 36, 34, 34, 6, 39, 37, 55, 39, 34, 0, 9, 198, 12, 129, 76, 56, 84, 128, 65, 0, 11, 136, 19, 3, 21, 20, 21, 18, 196, 131, 65, 21, 71, 52, 144, 210, 61, 51, 198, 80, 63, 6, 115, 78, 14, 16, 39, 87, 39, 81, 47, 0, 9, 198, 72, 80, 213, 64, 84, 129, 68, 0, 12, 137, 22, 195, 162, 14, 20, 21, 18, 196, 131, 67, 0, 15, 140, 195, 174, 14, 3, 196, 131, 16, 5, 18, 9, 12, 5, 67, 8, 197, 24, 197, 73, 21, 32, 65, 0, 12, 137, 3, 196, 131, 4, 5, 18, 9, 12, 5, 66, 0, 8, 133, 21, 13, 196, 131, 18, 65, 13, 138, 19, 3, 196, 131, 4, 5, 18, 9, 12, 5, 66, 9, 198, 4, 197, 3, 84, 213, 129, 67, 0, 7, 196, 104, 144, 197, 4, 66, 7, 196, 37, 80, 133, 4, 66, 9, 198, 4, 229, 77, 37, 67, 210, 75, 0, 8, 197, 16, 240, 212, 61, 32, 65, 0, 14, 66, 56, 80, 50, 133, 87, 0, 72, 81, 97, 197, 159, 32, 13, 66, 56, 80, 50, 133, 34, 0, 72, 81, 97, 114, 32, 13, 66, 56, 80, 50, 133, 63, 0, 72, 81, 97, 109, 32, 12, 137, 14, 196, 131, 16, 21, 19, 20, 5, 1, 67, 5, 194, 56, 80, 72, 15, 66, 52, 112, 109, 105, 108, 105, 103, 114, 97, 109, 101, 0, 29, 0, 10, 199, 37, 3, 195, 72, 150, 137, 36, 68, 0, 11, 136, 20, 18, 5, 1, 3, 196, 131, 20, 65, 7, 196, 12, 20, 20, 84, 66, 7, 196, 76, 83, 78, 4, 66, 14, 139, 4, 9, 19, 16, 18, 5, 197, 163, 21, 9, 1, 68, 0, 8, 197, 81, 32, 71, 20, 208, 65, 8, 197, 52, 146, 140, 60, 48, 65, 10, 67, 13, 82, 66, 49, 6, 119, 69, 0, 8, 197, 81, 33, 90, 20, 16, 66, 8, 197, 65, 34, 86, 20, 16, 66, 0, 9, 198, 36, 229, 18, 36, 114, 64, 65, 0, 0, 26, 11, 19, 21, 16, 18, 5, 13, 1, 197, 163, 9, 5, 87, 40, 48, 14, 16, 36, 63, 35, 121, 6, 37, 36, 0, 7, 196, 84, 225, 76, 20, 73, 0, 8, 197, 60, 34, 67, 20, 144, 67, 8, 197, 56, 149, 133, 48, 80, 66, 8, 197, 36, 225, 9, 28, 240, 67, 11, 136, 3, 195, 162, 20, 15, 18, 22, 1, 67, 11, 136, 3, 196, 131, 197, 159, 21, 14, 1, 67, 8, 197, 16, 147, 148, 72, 80, 28, 7, 131, 195, 174, 14, 72, 28, 0, 12, 66, 57, 80, 50, 40, 37, 0, 72, 81, 105, 32, 9, 198, 4, 101, 82, 37, 50, 64, 68, 5, 194, 57, 80, 76, 0, 6, 131, 195, 174, 12, 72, 0, 6, 195, 52, 146, 137, 66, 15, 4, 95, 48, 77, 52, 69, 37, 55, 6, 57, 136, 50, 36, 0, 0, 11, 136, 195, 174, 14, 4, 15, 9, 20, 21, 68, 16, 140, 4, 5, 19, 16, 196, 131, 18, 197, 163, 9, 20, 21, 68, 18, 16, 4, 95, 48, 77, 53, 69, 37, 55, 6, 57, 35, 34, 70, 36, 0, 0, 6, 195, 21, 3, 195, 65, 15, 4, 95, 48, 77, 50, 63, 37, 55, 6, 57, 136, 50, 36, 0, 0, 6, 195, 13, 83, 64, 8, 16, 4, 95, 48, 77, 51, 63, 37, 55, 6, 57, 35, 34, 70, 36, 0, 0, 6, 131, 195, 174, 9, 72, 0, 8, 197, 4, 52, 137, 81, 80, 67, 10, 4, 95, 48, 77, 49, 63, 6, 130, 0, 0, 12, 137, 16, 18, 15, 14, 21, 14, 197, 163, 1, 67, 14, 4, 95, 2, 18, 22, 49, 13, 74, 6, 40, 55, 13, 0, 0, 6, 195, 36, 20, 128, 8, 0, 6, 195, 5, 3, 201, 66, 6, 195, 52, 148, 129, 66, 0, 0, 0, 9, 198, 16, 80, 197, 48, 84, 129, 68, 7, 195, 88, 244, 128, 76, 32, 0, 7, 196, 37, 4, 207, 76, 65, 0, 0, 9, 198, 77, 64, 78, 16, 20, 132, 65, 17, 70, 20, 97, 67, 81, 80, 64, 36, 81, 36, 49, 47, 58, 6, 35, 0, 0, 11, 136, 12, 9, 14, 7, 21, 18, 196, 131, 65, 0, 6, 195, 60, 101, 1, 66, 0, 13, 5, 15, 13, 196, 131, 20, 39, 63, 6, 13, 47, 0, 0, 0, 13, 138, 3, 21, 14, 15, 1, 197, 159, 20, 5, 13, 66, 0, 6, 195, 12, 85, 129, 66, 10, 135, 19, 20, 196, 131, 20, 5, 1, 66, 10, 135, 195, 174, 14, 4, 15, 9, 1, 67, 7, 196, 84, 225, 73, 4, 77, 0, 0, 9, 194, 52, 144, 72, 81, 97, 114, 32, 9, 194, 52, 144, 72, 81, 97, 105, 32, 9, 194, 52, 144, 72, 81, 97, 109, 32, 13, 66, 52, 144, 63, 37, 4, 36, 0, 72, 81, 101, 32, 5, 194, 52, 144, 72, 29, 66, 44, 208, 49, 37, 55, 39, 63, 6, 36, 47, 14, 16, 37, 11, 48, 36, 15, 6, 39, 34, 13, 0, 82, 47, 32, 104, 32, 15, 66, 44, 208, 107, 105, 108, 111, 109, 101, 116, 114, 105, 0, 29, 0, 9, 134, 4, 196, 131, 4, 5, 1, 66, 0, 7, 196, 56, 147, 73, 12, 66, 6, 195, 12, 84, 149, 66, 0, 8, 197, 85, 35, 5, 80, 80, 65, 8, 197, 81, 83, 133, 80, 80, 65, 8, 197, 77, 83, 133, 80, 80, 65, 8, 197, 88, 19, 15, 72, 16, 67, 15, 69, 77, 64, 71, 56, 16, 87, 47, 35, 79, 50, 6, 35, 0, 8, 197, 64, 244, 142, 20, 16, 66, 0, 9, 198, 72, 81, 197, 49, 82, 64, 65, 0, 17, 5, 195, 174, 14, 20, 18, 110, 50, 47, 14, 16, 39, 0, 81, 111, 32, 9, 134, 4, 196, 131, 21, 14, 1, 67, 0, 10, 135, 13, 9, 197, 159, 21, 14, 1, 67, 0, 8, 197, 88, 81, 5, 72, 144, 66, 8, 197, 88, 20, 201, 48, 80, 66, 8, 197, 65, 35, 208, 84, 144, 66, 24, 73, 65, 34, 69, 80, 83, 149, 49, 82, 64, 48, 14, 16, 57, 6, 36, 47, 36, 50, 40, 55, 119, 0, 8, 197, 64, 149, 9, 12, 144, 66, 11, 136, 13, 195, 162, 14, 5, 3, 9, 9, 66, 8, 197, 48, 145, 5, 72, 144, 65, 8, 197, 32, 18, 1, 48, 80, 67, 8, 197, 16, 81, 197, 80, 80, 65, 8, 197, 17, 82, 14, 20, 16, 66, 8, 197, 9, 80, 213, 72, 16, 67, 8, 197, 76, 100, 137, 40, 144, 66, 0, 6, 195, 52, 20, 143, 66, 8, 133, 20, 195, 162, 18, 1, 66, 21, 9, 6, 9, 5, 3, 196, 131, 18, 21, 9, 81, 57, 36, 49, 6, 13, 34, 119, 0, 72, 0, 0, 0, 15, 69, 76, 84, 135, 37, 80, 87, 6, 36, 34, 73, 57, 40, 0, 11, 136, 3, 12, 196, 131, 20, 9, 14, 1, 67, 0, 11, 5, 95, 15, 6, 77, 49, 63, 6, 130, 0, 0, 0, 7, 196, 20, 97, 77, 20, 67, 0, 8, 197, 29, 32, 84, 37, 48, 65, 8, 197, 13, 33, 65, 81, 80, 67, 0, 0, 0, 13, 68, 88, 242, 76, 4, 82, 40, 35, 55, 6, 35, 0, 0, 0, 9, 198, 28, 84, 141, 36, 224, 64, 67, 0, 9, 134, 19, 3, 196, 131, 16, 1, 66, 6, 195, 77, 80, 128, 28, 0, 7, 196, 61, 32, 129, 56, 65, 7, 196, 24, 150, 137, 12, 65, 7, 196, 60, 51, 204, 36, 67, 0, 0, 9, 198, 64, 243, 15, 56, 144, 192, 67, 9, 198, 8, 148, 197, 72, 144, 192, 66, 9, 198, 16, 84, 197, 52, 224, 64, 67, 0, 13, 138, 6, 12, 196, 131, 3, 196, 131, 18, 9, 9, 65, 13, 138, 195, 174, 13, 16, 196, 131, 18, 197, 163, 9, 67, 6, 195, 77, 83, 148, 76, 6, 195, 77, 83, 148, 76, 0, 7, 196, 64, 195, 213, 4, 66, 0, 0, 13, 5, 197, 159, 20, 9, 1, 89, 47, 6, 57, 35, 0, 0, 0, 11, 67, 4, 144, 201, 35, 6, 37, 74, 122, 0, 10, 135, 26, 7, 195, 162, 18, 9, 1, 67, 0, 0, 13, 5, 197, 159, 20, 9, 5, 89, 47, 6, 37, 36, 0, 9, 198, 48, 147, 80, 20, 65, 64, 65, 5, 194, 56, 144, 72, 12, 137, 195, 174, 14, 20, 195, 162, 12, 14, 9, 67, 6, 194, 64, 80, 72, 28, 0, 9, 198, 64, 21, 18, 84, 193, 65, 65, 0, 11, 67, 4, 34, 65, 35, 69, 57, 6, 35, 0, 0, 12, 201, 64, 20, 148, 20, 225, 82, 20, 193, 64, 67, 8, 197, 28, 83, 69, 80, 80, 65, 9, 198, 16, 84, 203, 80, 244, 0, 65, 0, 9, 198, 77, 3, 5, 56, 66, 68, 65, 12, 137, 13, 195, 162, 14, 7, 195, 162, 9, 1, 67, 9, 198, 72, 245, 21, 56, 162, 64, 67, 0, 10, 199, 28, 147, 78, 5, 53, 9, 12, 66, 0, 0, 8, 197, 36, 229, 9, 52, 80, 65, 8, 197, 60, 97, 82, 20, 16, 67, 8, 197, 4, 37, 82, 20, 16, 66, 8, 197, 77, 68, 137, 88, 144, 66, 0, 9, 198, 76, 20, 131, 36, 226, 64, 65, 9, 198, 52, 20, 135, 36, 226, 64, 65, 0, 10, 199, 88, 150, 149, 4, 194, 90, 4, 68, 13, 138, 4, 5, 19, 16, 196, 131, 18, 197, 163, 9, 67, 9, 134, 1, 22, 5, 197, 163, 9, 76, 0, 10, 135, 21, 9, 20, 196, 131, 20, 21, 67, 0, 0, 18, 70, 65, 34, 69, 80, 83, 128, 48, 14, 16, 57, 6, 36, 47, 36, 50, 0, 12, 137, 18, 196, 131, 19, 20, 21, 18, 14, 1, 67, 19, 4, 95, 3, 9, 18, 74, 37, 34, 49, 40, 63, 81, 55, 6, 36, 49, 87, 0, 0, 13, 138, 22, 196, 131, 9, 5, 20, 196, 131, 20, 21, 68, 6, 195, 4, 34, 76, 66, 0, 7, 196, 48, 147, 73, 80, 65, 14, 139, 195, 174, 14, 197, 163, 5, 16, 196, 131, 20, 21, 68, 7, 196, 24, 16, 197, 52, 65, 6, 195, 85, 35, 1, 66, 6, 195, 77, 83, 129, 66, 10, 135, 1, 14, 21, 14, 197, 163, 1, 67, 0, 15, 69, 61, 98, 68, 37, 80, 39, 82, 6, 37, 70, 57, 40, 0, 19, 8, 5, 24, 39, 15, 20, 9, 3, 5, 36, 79, 86, 39, 47, 37, 74, 36, 0, 0, 15, 66, 52, 192, 109, 105, 108, 105, 108, 105, 116, 114, 105, 0, 29, 0, 9, 198, 52, 20, 135, 36, 226, 73, 65, 9, 134, 18, 195, 162, 6, 14, 9, 66, 0, 0, 9, 134, 12, 196, 131, 19, 196, 131, 66, 11, 136, 14, 196, 131, 16, 21, 19, 20, 9, 67, 0, 9, 198, 80, 84, 141, 36, 224, 64, 67, 9, 198, 65, 35, 212, 20, 160, 64, 67, 12, 137, 195, 174, 14, 196, 131, 12, 197, 163, 1, 67, 9, 198, 20, 194, 77, 36, 224, 64, 68, 9, 198, 12, 192, 88, 60, 224, 64, 67, 8, 3, 95, 196, 131, 6, 13, 0, 0, 9, 198, 5, 37, 5, 24, 144, 197, 67, 9, 134, 1, 18, 196, 131, 20, 1, 67, 0, 12, 137, 4, 15, 13, 14, 9, 197, 163, 196, 131, 66, 15, 3, 197, 163, 9, 121, 57, 39, 57, 0, 72, 81, 111, 105, 32, 15, 3, 197, 163, 9, 121, 57, 35, 34, 0, 72, 81, 97, 114, 32, 15, 3, 197, 163, 9, 121, 57, 35, 63, 0, 72, 81, 97, 109, 32, 14, 3, 197, 163, 9, 121, 6, 57, 36, 0, 72, 81, 101, 32, 14, 3, 197, 163, 9, 121, 57, 115, 0, 72, 81, 97, 105, 32, 14, 3, 197, 163, 9, 121, 57, 112, 0, 72, 81, 97, 117, 32, 15, 3, 197, 163, 9, 121, 57, 35, 34, 0, 72, 81, 97, 114, 32, 15, 3, 197, 163, 9, 121, 57, 35, 63, 0, 72, 81, 97, 109, 32, 6, 131, 197, 163, 9, 72, 0, 9, 134, 2, 196, 131, 7, 196, 131, 66, 13, 138, 1, 13, 5, 14, 9, 14, 197, 163, 196, 131, 66, 0, 9, 198, 56, 144, 201, 84, 224, 64, 77, 0, 9, 198, 52, 241, 9, 24, 144, 193, 68, 12, 4, 95, 19, 20, 11, 87, 55, 6, 36, 89, 0, 0, 7, 196, 76, 80, 207, 48, 65, 0, 11, 136, 16, 196, 131, 18, 5, 18, 9, 9, 66, 8, 197, 8, 19, 9, 57, 64, 65, 8, 197, 4, 192, 133, 73, 64, 65, 15, 4, 95, 1, 3, 21, 35, 87, 49, 40, 121, 6, 37, 47, 0, 0, 9, 198, 80, 84, 141, 36, 225, 64, 65, 0, 10, 199, 12, 129, 82, 21, 53, 5, 4, 67, 9, 134, 13, 195, 162, 14, 10, 9, 66, 0, 7, 196, 5, 33, 5, 4, 66, 0, 8, 197, 104, 115, 205, 61, 64, 65, 13, 3, 95, 195, 174, 4, 110, 70, 37, 50, 6, 37, 0, 0, 5, 194, 76, 16, 76, 15, 66, 52, 208, 109, 105, 108, 105, 109, 101, 116, 114, 105, 0, 29, 0, 9, 198, 5, 49, 77, 20, 225, 65, 66, 9, 198, 4, 194, 77, 20, 229, 1, 68, 6, 195, 24, 244, 212, 76, 0, 6, 195, 76, 80, 213, 66, 9, 198, 72, 245, 15, 12, 243, 0, 67, 7, 196, 84, 227, 210, 4, 77, 0, 8, 197, 17, 84, 133, 72, 80, 66, 12, 201, 12, 20, 129, 13, 65, 82, 20, 193, 64, 67, 8, 197, 72, 83, 1, 96, 16, 67, 15, 140, 195, 174, 13, 16, 18, 196, 131, 197, 159, 20, 9, 1, 67, 0, 9, 198, 56, 144, 201, 84, 229, 76, 77, 9, 198, 56, 144, 201, 84, 229, 76, 77, 0, 9, 134, 1, 16, 196, 131, 18, 1, 67, 0, 10, 135, 19, 21, 16, 196, 131, 18, 1, 67, 0, 8, 197, 88, 244, 19, 20, 16, 66, 8, 197, 84, 50, 68, 20, 208, 66, 8, 197, 64, 21, 9, 52, 144, 65, 8, 197, 61, 33, 9, 56, 80, 65, 8, 197, 32, 18, 68, 20, 208, 65, 8, 197, 24, 84, 137, 12, 80, 65, 9, 198, 21, 2, 83, 12, 244, 0, 66, 11, 136, 3, 21, 13, 16, 196, 131, 18, 1, 67, 0, 9, 198, 80, 84, 141, 20, 226, 64, 65, 0, 9, 134, 21, 18, 196, 131, 20, 21, 67, 0, 16, 70, 84, 225, 200, 37, 83, 0, 6, 40, 50, 79, 57, 40, 55, 0, 14, 139, 195, 174, 14, 22, 18, 5, 4, 14, 9, 3, 9, 68, 0, 11, 136, 1, 4, 21, 14, 196, 131, 20, 21, 68, 13, 3, 95, 195, 162, 4, 110, 70, 37, 50, 6, 35, 0, 0, 12, 137, 21, 19, 20, 21, 18, 196, 131, 20, 21, 68, 0, 13, 138, 13, 196, 131, 20, 21, 18, 196, 131, 20, 21, 68, 9, 134, 1, 16, 196, 131, 19, 1, 67, 0, 14, 139, 4, 196, 131, 18, 195, 162, 13, 196, 131, 20, 21, 68, 7, 196, 64, 193, 67, 4, 66, 0, 11, 136, 18, 5, 14, 21, 14, 197, 163, 1, 67, 0, 12, 137, 1, 13, 5, 14, 9, 14, 197, 163, 1, 68, 0, 9, 198, 56, 144, 201, 84, 226, 73, 77, 0, 0, 0, 12, 137, 3, 195, 162, 197, 159, 20, 9, 7, 1, 67, 0, 11, 67, 21, 32, 64, 57, 36, 16, 35, 0, 78, 0, 0, 11, 136, 4, 5, 16, 196, 131, 197, 159, 9, 67, 0, 17, 70, 56, 84, 213, 65, 84, 192, 50, 36, 87, 40, 48, 6, 40, 87, 0, 9, 198, 64, 19, 148, 21, 32, 64, 66, 9, 198, 4, 197, 3, 21, 96, 64, 67, 9, 198, 76, 53, 84, 85, 32, 64, 67, 9, 198, 12, 243, 5, 13, 64, 64, 67, 0, 6, 195, 5, 33, 64, 76, 0, 12, 137, 3, 21, 22, 195, 162, 14, 20, 196, 131, 67, 12, 137, 3, 15, 14, 20, 18, 15, 12, 196, 131, 67, 12, 67, 21, 32, 77, 57, 36, 16, 35, 63, 0, 78, 9, 134, 3, 196, 131, 18, 15, 18, 73, 0, 9, 134, 13, 195, 162, 14, 5, 3, 65, 16, 69, 9, 35, 203, 21, 32, 69, 14, 16, 6, 39, 49, 13, 34, 0, 0, 9, 198, 80, 20, 212, 5, 69, 64, 67, 9, 198, 13, 33, 68, 37, 65, 64, 65, 9, 198, 12, 195, 195, 61, 65, 64, 65, 16, 70, 8, 19, 142, 21, 33, 64, 69, 6, 36, 50, 13, 16, 36, 0, 21, 4, 95, 1, 3, 50, 70, 6, 40, 69, 55, 40, 35, 87, 49, 40, 6, 121, 37, 47, 0, 0, 9, 198, 81, 35, 211, 56, 85, 5, 65, 9, 198, 12, 243, 147, 80, 21, 1, 67, 0, 7, 196, 20, 194, 67, 20, 66, 7, 196, 12, 129, 77, 4, 66, 6, 195, 77, 80, 201, 66, 11, 67, 21, 32, 73, 57, 36, 16, 115, 0, 78, 0, 8, 197, 76, 83, 154, 61, 32, 65, 8, 197, 64, 144, 212, 61, 32, 65, 8, 197, 24, 16, 212, 61, 32, 65, 14, 69, 8, 16, 203, 85, 0, 69, 6, 36, 49, 35, 48, 0, 0, 9, 198, 77, 2, 82, 37, 65, 64, 65, 9, 66, 60, 176, 39, 49, 6, 116, 0, 12, 137, 18, 196, 131, 13, 195, 162, 14, 5, 1, 67, 12, 137, 195, 174, 13, 2, 21, 12, 26, 5, 1, 67, 5, 194, 80, 16, 76, 0, 10, 199, 72, 80, 213, 56, 244, 195, 84, 67, 9, 198, 77, 84, 208, 20, 53, 1, 67, 13, 138, 19, 20, 196, 131, 16, 195, 162, 14, 5, 1, 67, 9, 134, 16, 195, 162, 14, 4, 9, 66, 0, 7, 196, 88, 146, 84, 84, 66, 7, 196, 84, 209, 68, 20, 65, 6, 195, 24, 147, 9, 66, 11, 67, 21, 32, 85, 57, 36, 16, 112, 0, 78, 0, 11, 136, 16, 196, 131, 18, 5, 18, 5, 1, 66, 8, 197, 28, 83, 133, 72, 16, 67, 8, 197, 13, 33, 68, 20, 16, 67, 0, 0, 19, 71, 80, 245, 4, 20, 21, 78, 4, 47, 39, 47, 70, 133, 6, 40, 50, 35, 0, 13, 138, 195, 174, 14, 3, 196, 131, 12, 26, 5, 1, 67, 13, 138, 18, 196, 131, 19, 16, 195, 162, 14, 4, 9, 67, 9, 134, 16, 196, 131, 197, 159, 9, 66, 0, 7, 196, 56, 144, 201, 60, 77, 0, 8, 197, 88, 149, 18, 20, 112, 65, 8, 197, 36, 225, 201, 56, 80, 67, 8, 197, 72, 244, 212, 20, 16, 66, 8, 197, 72, 145, 9, 12, 16, 67, 8, 197, 16, 81, 9, 12, 16, 67, 16, 69, 81, 33, 66, 84, 144, 47, 14, 16, 36, 69, 58, 6, 37, 0, 8, 197, 4, 197, 15, 72, 16, 77, 0, 17, 70, 72, 20, 133, 61, 34, 64, 34, 35, 16, 36, 6, 39, 143, 122, 0, 0, 18, 70, 24, 20, 134, 85, 34, 69, 81, 35, 34, 81, 40, 16, 6, 37, 36, 0, 9, 134, 1, 12, 5, 197, 159, 9, 66, 0, 7, 196, 52, 22, 9, 52, 65, 0, 0, 12, 201, 64, 20, 148, 20, 225, 82, 84, 197, 73, 67, 0, 13, 138, 1, 4, 195, 162, 14, 3, 196, 131, 20, 21, 68, 0, 0, 0, 12, 137, 195, 174, 14, 3, 196, 131, 18, 3, 1, 67, 12, 137, 3, 196, 131, 12, 196, 131, 21, 26, 9, 68, 0, 6, 195, 5, 34, 80, 65, 11, 136, 195, 174, 14, 3, 15, 20, 18, 15, 67, 0, 8, 133, 18, 21, 12, 196, 131, 66, 7, 196, 28, 150, 143, 72, 65, 0, 8, 197, 36, 208, 71, 36, 224, 66, 8, 2, 196, 131, 6, 13, 0, 14, 0, 9, 198, 20, 194, 66, 21, 32, 64, 68, 0, 0, 8, 133, 15, 6, 20, 196, 131, 66, 12, 137, 195, 174, 14, 3, 5, 18, 3, 196, 131, 67, 0, 8, 197, 65, 34, 67, 36, 224, 65, 0, 8, 133, 22, 196, 131, 26, 21, 66, 8, 133, 197, 163, 9, 14, 21, 66, 9, 198, 72, 240, 133, 73, 64, 64, 66, 9, 198, 16, 148, 208, 21, 32, 64, 67, 9, 198, 16, 84, 9, 77, 64, 64, 67, 9, 198, 16, 83, 5, 13, 64, 64, 67, 21, 9, 15, 18, 9, 3, 196, 131, 18, 5, 9, 39, 16, 122, 49, 13, 34, 36, 37, 0, 79, 9, 198, 4, 49, 65, 77, 64, 64, 76, 0, 11, 136, 22, 9, 18, 7, 21, 12, 196, 131, 65, 9, 198, 65, 34, 67, 21, 1, 77, 66, 9, 134, 18, 196, 131, 2, 4, 1, 66, 0, 12, 137, 16, 18, 5, 26, 5, 14, 20, 196, 131, 67, 7, 196, 4, 210, 67, 20, 66, 0, 12, 201, 20, 98, 67, 36, 83, 148, 37, 160, 64, 69, 12, 201, 72, 81, 67, 32, 147, 9, 9, 32, 64, 69, 0, 0, 23, 10, 195, 174, 14, 196, 131, 21, 14, 20, 18, 21, 110, 50, 13, 6, 40, 50, 47, 14, 16, 40, 0, 24, 10, 4, 9, 14, 196, 131, 21, 14, 20, 18, 21, 70, 37, 50, 13, 6, 40, 50, 47, 14, 16, 40, 0, 9, 134, 19, 196, 131, 18, 5, 1, 66, 9, 134, 197, 159, 15, 16, 20, 9, 66, 0, 6, 195, 5, 35, 85, 66, 0, 15, 69, 24, 243, 4, 21, 32, 81, 6, 39, 55, 70, 13, 34, 0, 0, 5, 194, 76, 80, 72, 0, 9, 198, 4, 48, 197, 57, 69, 65, 67, 0, 7, 196, 64, 149, 9, 12, 66, 6, 195, 13, 84, 213, 66, 0, 8, 197, 72, 18, 15, 88, 16, 65, 8, 197, 64, 84, 132, 20, 16, 66, 8, 197, 17, 84, 133, 72, 144, 66, 11, 136, 19, 20, 195, 162, 18, 14, 5, 1, 66, 8, 197, 72, 84, 5, 72, 16, 67, 0, 0, 9, 198, 8, 16, 212, 21, 34, 69, 66, 0, 14, 139, 195, 174, 14, 3, 196, 131, 16, 5, 18, 5, 1, 67, 11, 200, 36, 65, 78, 80, 145, 137, 12, 16, 69, 7, 196, 76, 84, 150, 36, 66, 0, 8, 197, 5, 37, 5, 72, 16, 66, 8, 197, 12, 194, 78, 80, 144, 66, 0, 9, 198, 4, 36, 207, 49, 98, 64, 68, 0, 12, 137, 16, 196, 131, 9, 1, 14, 10, 5, 14, 66, 0, 7, 196, 64, 21, 9, 52, 65, 7, 196, 48, 148, 19, 36, 66, 7, 196, 16, 81, 197, 80, 65, 11, 200, 16, 84, 208, 72, 147, 132, 20, 16, 67, 13, 2, 195, 162, 4, 110, 70, 37, 50, 6, 35, 0, 14, 0, 16, 69, 81, 32, 68, 85, 48, 47, 14, 16, 35, 70, 6, 40, 87, 0, 15, 6, 18, 196, 131, 16, 21, 19, 34, 13, 48, 6, 40, 87, 0, 16, 69, 17, 32, 68, 85, 48, 47, 14, 16, 35, 70, 6, 40, 87, 0, 11, 136, 1, 3, 5, 9, 1, 197, 159, 9, 66, 0, 12, 137, 18, 196, 131, 13, 195, 162, 14, 5, 13, 66, 0, 9, 198, 12, 192, 86, 36, 21, 21, 67, 9, 134, 13, 195, 162, 14, 3, 1, 66, 13, 2, 194, 169, 49, 6, 35, 48, 37, 34, 115, 47, 0, 0, 7, 196, 36, 229, 9, 52, 65, 19, 70, 12, 243, 80, 85, 65, 82, 49, 39, 63, 48, 6, 57, 40, 47, 13, 34, 0, 7, 196, 5, 33, 5, 52, 65, 13, 2, 195, 174, 4, 110, 70, 37, 50, 6, 37, 0, 14, 0, 8, 197, 88, 244, 212, 73, 80, 76, 8, 197, 56, 244, 212, 73, 80, 77, 7, 2, 197, 159, 89, 36, 0, 0, 0, 9, 198, 64, 148, 212, 60, 19, 5, 66, 9, 198, 8, 16, 212, 21, 34, 73, 66, 0, 0, 0, 9, 198, 40, 20, 15, 56, 144, 64, 66, 11, 2, 194, 176, 79, 14, 16, 35, 70, 36, 0, 0, 0, 11, 200, 64, 20, 148, 20, 225, 82, 84, 192, 67, 6, 195, 85, 35, 137, 66, 5, 130, 195, 182, 43, 0, 8, 197, 56, 144, 201, 84, 224, 77, 0, 9, 198, 4, 209, 82, 36, 48, 64, 66, 9, 198, 72, 85, 133, 56, 80, 64, 67, 0, 10, 67, 88, 145, 64, 82, 6, 37, 36, 0, 10, 199, 16, 86, 143, 72, 66, 78, 20, 66, 10, 199, 12, 243, 132, 84, 53, 15, 72, 66, 9, 198, 65, 33, 79, 13, 84, 1, 67, 11, 67, 24, 145, 64, 81, 6, 37, 36, 0, 72, 0, 10, 135, 197, 163, 9, 16, 5, 20, 5, 65, 7, 196, 80, 83, 69, 4, 66, 6, 195, 4, 49, 65, 78, 14, 4, 95, 3, 5, 4, 87, 36, 70, 6, 37, 55, 13, 0, 0, 7, 2, 197, 163, 121, 36, 0, 0, 9, 198, 65, 35, 208, 36, 49, 64, 66, 0, 16, 4, 95, 12, 9, 7, 55, 37, 79, 35, 47, 6, 40, 34, 13, 0, 0, 14, 139, 195, 174, 14, 3, 196, 131, 16, 5, 18, 9, 9, 67, 0, 11, 136, 195, 174, 14, 6, 9, 7, 5, 1, 67, 0, 9, 198, 52, 21, 18, 36, 49, 64, 66, 9, 198, 12, 84, 130, 36, 49, 64, 66, 14, 66, 80, 80, 47, 133, 89, 0, 72, 81, 97, 197, 159, 32, 13, 66, 80, 80, 47, 133, 34, 0, 72, 81, 97, 114, 32, 13, 66, 80, 80, 47, 133, 57, 0, 72, 81, 97, 105, 32, 13, 66, 80, 80, 47, 133, 63, 0, 72, 81, 97, 109, 32, 6, 194, 88, 16, 76, 32, 5, 194, 80, 80, 72, 0, 10, 67, 4, 50, 64, 35, 74, 6, 37, 0, 13, 138, 19, 20, 18, 196, 131, 12, 21, 3, 5, 1, 67, 9, 198, 65, 35, 212, 21, 53, 1, 67, 9, 198, 65, 35, 196, 84, 49, 65, 67, 13, 138, 195, 174, 14, 3, 18, 5, 197, 163, 5, 1, 67, 9, 198, 12, 243, 132, 84, 49, 65, 67, 8, 67, 88, 146, 64, 82, 130, 0, 0, 7, 196, 4, 49, 76, 20, 78, 6, 195, 4, 49, 73, 76, 0, 8, 197, 76, 51, 212, 20, 16, 66, 8, 197, 52, 84, 137, 80, 16, 67, 0, 9, 198, 60, 227, 198, 72, 82, 64, 67, 9, 198, 60, 19, 69, 56, 146, 64, 65, 9, 198, 56, 21, 21, 72, 146, 64, 67, 0, 18, 70, 88, 19, 5, 56, 50, 65, 82, 35, 55, 6, 36, 50, 87, 57, 35, 0, 10, 199, 4, 116, 137, 13, 83, 20, 84, 68, 10, 199, 13, 85, 18, 20, 145, 82, 4, 68, 13, 138, 195, 174, 13, 16, 196, 131, 20, 21, 18, 9, 69, 6, 195, 4, 49, 76, 76, 0, 10, 135, 197, 163, 196, 131, 18, 9, 9, 65, 9, 198, 12, 20, 9, 80, 243, 0, 66, 7, 196, 4, 130, 76, 20, 66, 7, 196, 4, 65, 82, 4, 67, 14, 139, 18, 5, 195, 174, 14, 20, 195, 162, 12, 14, 9, 68, 0, 8, 197, 72, 145, 9, 12, 80, 66, 11, 136, 16, 18, 196, 131, 10, 9, 20, 21, 67, 8, 197, 16, 83, 154, 36, 48, 66, 8, 197, 52, 83, 79, 72, 16, 67, 8, 197, 16, 243, 73, 56, 16, 67, 8, 197, 16, 84, 149, 48, 16, 67, 8, 197, 60, 52, 143, 80, 144, 67, 11, 136, 13, 21, 12, 197, 163, 21, 13, 9, 67, 0, 9, 198, 80, 84, 129, 64, 146, 64, 67, 5, 194, 81, 80, 76, 0, 10, 199, 4, 197, 21, 56, 65, 86, 4, 68, 9, 198, 4, 49, 83, 80, 82, 65, 78, 0, 9, 198, 88, 82, 9, 13, 83, 0, 66, 7, 196, 4, 210, 67, 36, 66, 7, 196, 8, 195, 195, 4, 67, 11, 200, 8, 192, 71, 61, 51, 15, 88, 144, 68, 0, 15, 69, 65, 35, 196, 85, 48, 48, 16, 39, 70, 6, 40, 87, 0, 15, 69, 21, 128, 204, 85, 48, 36, 99, 49, 55, 6, 40, 87, 0, 15, 69, 12, 243, 132, 85, 48, 49, 39, 50, 70, 6, 40, 87, 0, 0, 0, 9, 198, 88, 82, 9, 13, 83, 5, 66, 9, 134, 3, 196, 131, 19, 3, 1, 66, 0, 12, 68, 56, 85, 143, 36, 50, 36, 82, 6, 118, 0, 13, 68, 48, 149, 137, 84, 55, 6, 37, 82, 57, 40, 0, 6, 195, 37, 160, 137, 66, 0, 15, 140, 19, 20, 18, 196, 131, 6, 21, 12, 7, 5, 18, 1, 68, 0, 0, 10, 135, 26, 195, 162, 13, 2, 5, 20, 65, 9, 198, 4, 209, 82, 36, 50, 73, 66, 0, 0, 9, 197, 4, 197, 6, 20, 192, 65, 28, 0, 9, 198, 77, 84, 21, 56, 80, 64, 67, 9, 198, 77, 5, 77, 20, 112, 64, 68, 9, 198, 72, 81, 133, 72, 80, 64, 67, 17, 70, 56, 81, 207, 12, 144, 64, 50, 36, 79, 39, 74, 37, 6, 35, 0, 12, 137, 195, 174, 13, 2, 18, 196, 131, 3, 1, 67, 12, 137, 195, 174, 14, 3, 196, 131, 12, 26, 9, 67, 0, 21, 71, 65, 33, 68, 37, 52, 21, 76, 48, 14, 16, 36, 70, 37, 87, 48, 6, 40, 87, 0, 11, 136, 7, 195, 162, 4, 9, 12, 196, 131, 65, 0, 7, 196, 36, 229, 18, 20, 28, 11, 67, 17, 84, 1, 70, 40, 48, 13, 0, 28, 0, 11, 136, 26, 195, 162, 13, 2, 5, 20, 5, 65, 13, 138, 195, 174, 14, 4, 18, 5, 16, 20, 196, 131, 67, 0, 9, 198, 24, 243, 15, 76, 80, 64, 67, 9, 198, 16, 85, 133, 56, 80, 64, 67, 9, 198, 4, 165, 78, 28, 80, 64, 67, 0, 0, 12, 67, 21, 53, 5, 57, 36, 87, 47, 36, 0, 76, 6, 195, 5, 53, 1, 76, 0, 0, 9, 198, 37, 53, 5, 72, 145, 64, 67, 0, 9, 134, 197, 159, 15, 19, 5, 1, 66, 12, 201, 64, 20, 148, 20, 225, 82, 36, 195, 210, 67, 9, 134, 7, 196, 131, 19, 5, 1, 66, 0, 11, 67, 104, 149, 65, 86, 6, 37, 120, 35, 0, 11, 200, 56, 244, 212, 36, 209, 76, 61, 32, 65, 14, 139, 195, 174, 14, 197, 163, 5, 12, 5, 7, 5, 13, 67, 7, 196, 36, 226, 77, 4, 65, 7, 196, 12, 130, 77, 36, 20, 10, 135, 19, 9, 13, 197, 163, 5, 1, 66, 0, 11, 136, 18, 196, 131, 19, 21, 3, 5, 1, 67, 0, 17, 70, 88, 84, 154, 84, 145, 64, 82, 36, 34, 86, 6, 40, 57, 36, 0, 18, 70, 65, 35, 211, 80, 145, 64, 48, 14, 16, 39, 87, 47, 6, 37, 36, 0, 9, 198, 56, 244, 212, 36, 209, 64, 65, 8, 133, 6, 196, 131, 3, 21, 66, 9, 198, 16, 83, 154, 36, 49, 64, 66, 9, 198, 13, 32, 84, 36, 209, 64, 65, 0, 12, 201, 64, 20, 148, 20, 225, 82, 20, 195, 210, 67, 9, 134, 26, 196, 131, 3, 5, 1, 66, 9, 134, 18, 196, 131, 3, 5, 1, 66, 9, 134, 6, 196, 131, 3, 5, 1, 66, 0, 10, 135, 195, 174, 14, 20, 195, 162, 9, 66, 7, 196, 33, 83, 143, 72, 65, 7, 196, 20, 112, 76, 20, 66, 14, 139, 195, 174, 14, 197, 163, 5, 12, 5, 7, 5, 1, 68, 14, 139, 195, 174, 13, 16, 196, 131, 18, 197, 163, 5, 1, 67, 7, 196, 17, 82, 14, 36, 66, 0, 14, 69, 52, 242, 83, 20, 144, 63, 39, 37, 87, 6, 116, 0, 8, 197, 5, 4, 137, 28, 80, 65, 8, 197, 72, 84, 5, 80, 16, 67, 0, 9, 198, 65, 85, 5, 72, 146, 64, 66, 12, 137, 16, 18, 5, 6, 196, 131, 3, 5, 1, 67, 0, 9, 198, 40, 20, 15, 56, 145, 73, 66, 20, 71, 16, 84, 195, 60, 212, 21, 76, 70, 36, 87, 49, 39, 63, 48, 6, 40, 87, 0, 9, 198, 12, 243, 132, 84, 49, 77, 66, 10, 199, 4, 209, 82, 36, 50, 76, 20, 66, 7, 195, 64, 245, 0, 76, 32, 0, 11, 200, 28, 20, 212, 72, 243, 143, 52, 144, 20, 7, 196, 24, 16, 212, 84, 66, 0, 8, 197, 12, 147, 133, 52, 16, 65, 8, 197, 5, 4, 143, 64, 240, 67, 11, 136, 195, 174, 14, 6, 9, 5, 18, 1, 67, 8, 197, 16, 244, 141, 20, 16, 66, 0, 9, 198, 64, 20, 143, 16, 146, 64, 67, 0, 6, 2, 95, 1, 35, 0, 0, 14, 139, 195, 174, 14, 6, 196, 131, 197, 159, 21, 18, 1, 68, 7, 196, 12, 195, 195, 36, 66, 0, 0, 10, 67, 88, 145, 87, 82, 6, 57, 40, 0, 0, 21, 10, 6, 196, 131, 7, 196, 131, 4, 21, 21, 9, 81, 13, 79, 13, 70, 40, 6, 37, 0, 6, 2, 95, 5, 36, 0, 0, 14, 139, 195, 174, 14, 7, 18, 196, 131, 4, 9, 20, 21, 68, 6, 195, 85, 38, 137, 66, 0, 15, 69, 16, 148, 208, 85, 48, 70, 37, 87, 48, 6, 40, 87, 0, 0, 9, 198, 16, 81, 21, 12, 83, 64, 66, 9, 198, 4, 165, 78, 28, 83, 64, 66, 6, 2, 95, 9, 37, 0, 0, 0, 6, 2, 95, 15, 39, 0, 0, 13, 68, 84, 212, 12, 36, 6, 40, 63, 48, 55, 37, 0, 7, 196, 4, 114, 84, 4, 67, 7, 2, 95, 14, 50, 36, 0, 0, 8, 197, 28, 84, 129, 48, 64, 65, 11, 136, 6, 21, 18, 14, 9, 26, 196, 131, 67, 9, 198, 77, 5, 76, 8, 84, 129, 67, 9, 134, 3, 195, 162, 14, 20, 1, 66, 7, 2, 95, 13, 63, 36, 0, 0, 15, 70, 88, 245, 67, 32, 84, 128, 82, 6, 112, 74, 13, 34, 0, 10, 135, 197, 159, 5, 14, 9, 12, 5, 66, 6, 195, 85, 32, 193, 66, 9, 198, 8, 19, 1, 57, 48, 64, 67, 7, 2, 95, 12, 55, 36, 0, 0, 11, 136, 195, 174, 14, 3, 5, 16, 5, 13, 66, 10, 199, 64, 20, 148, 36, 50, 80, 4, 68, 7, 2, 95, 19, 87, 36, 0, 0, 0, 11, 136, 197, 163, 5, 12, 9, 14, 196, 131, 65, 8, 197, 12, 192, 84, 36, 224, 65, 0, 16, 70, 76, 48, 78, 56, 84, 128, 87, 49, 6, 36, 50, 13, 34, 0, 9, 198, 32, 19, 83, 80, 84, 128, 65, 0, 11, 136, 3, 18, 5, 197, 159, 20, 5, 13, 65, 11, 136, 3, 21, 22, 195, 162, 14, 20, 1, 67, 11, 136, 195, 174, 14, 197, 159, 5, 12, 1, 67, 0, 9, 134, 12, 1, 7, 196, 131, 18, 65, 7, 196, 24, 83, 69, 36, 66, 0, 6, 2, 95, 21, 40, 0, 0, 0, 11, 136, 14, 196, 131, 197, 159, 20, 5, 1, 66, 11, 136, 3, 18, 5, 197, 159, 20, 5, 1, 66, 18, 8, 1, 20, 195, 162, 197, 163, 9, 1, 35, 47, 6, 110, 121, 57, 35, 0, 7, 132, 19, 196, 131, 21, 76, 0, 9, 134, 14, 21, 13, 196, 131, 18, 65, 7, 196, 48, 16, 207, 52, 65, 7, 196, 36, 226, 77, 36, 65, 7, 196, 17, 84, 133, 4, 66, 12, 137, 3, 21, 14, 15, 197, 159, 20, 5, 1, 67, 7, 196, 4, 49, 83, 80, 76, 0, 8, 197, 52, 20, 148, 61, 32, 65, 0, 0, 14, 203, 12, 20, 129, 13, 65, 82, 20, 193, 76, 61, 32, 67, 7, 132, 19, 196, 131, 9, 76, 0, 7, 196, 12, 240, 201, 56, 65, 0, 8, 197, 52, 243, 9, 52, 80, 65, 8, 197, 12, 20, 133, 88, 16, 67, 13, 138, 195, 174, 14, 4, 5, 16, 12, 9, 14, 9, 68, 0, 6, 195, 16, 82, 129, 66, 6, 195, 28, 243, 137, 66, 0, 11, 136, 3, 195, 162, 18, 16, 9, 20, 21, 67, 6, 195, 49, 82, 64, 76, 0, 12, 137, 3, 18, 195, 162, 14, 3, 5, 14, 5, 65, 15, 2, 95, 34, 79, 105, 37, 55, 37, 63, 6, 36, 55, 36, 0, 0, 8, 197, 88, 144, 212, 36, 208, 65, 8, 197, 65, 85, 5, 72, 80, 66, 9, 198, 64, 85, 18, 20, 49, 77, 66, 8, 197, 56, 245, 137, 12, 80, 66, 13, 138, 195, 174, 14, 20, 196, 131, 18, 9, 20, 21, 68, 8, 197, 24, 243, 15, 76, 144, 67, 8, 197, 16, 243, 73, 56, 80, 65, 8, 197, 36, 229, 137, 80, 16, 67, 8, 197, 16, 243, 79, 48, 144, 67, 8, 197, 80, 240, 205, 4, 144, 73, 9, 198, 4, 49, 83, 81, 82, 65, 78, 16, 2, 95, 33, 36, 49, 87, 49, 55, 35, 63, 6, 35, 16, 36, 0, 0, 0, 24, 7, 19, 46, 1, 46, 13, 46, 4, 89, 36, 35, 89, 35, 63, 115, 70, 36, 48, 35, 34, 47, 36, 0, 15, 2, 95, 39, 35, 48, 39, 87, 47, 14, 16, 6, 39, 81, 0, 0, 7, 196, 80, 83, 69, 52, 65, 12, 137, 195, 174, 14, 7, 18, 5, 21, 14, 1, 68, 0, 0, 6, 195, 65, 85, 21, 66, 0, 0, 17, 4, 95, 3, 1, 16, 63, 35, 88, 40, 87, 49, 6, 40, 55, 13, 0, 0, 9, 197, 64, 83, 148, 73, 80, 72, 28, 22, 2, 95, 41, 48, 35, 16, 35, 50, 47, 4, 36, 86, 13, 110, 50, 49, 6, 37, 87, 13, 0, 0, 9, 198, 77, 4, 137, 40, 147, 128, 65, 6, 195, 88, 148, 129, 66, 23, 2, 95, 40, 48, 35, 16, 35, 50, 47, 4, 36, 86, 13, 70, 36, 87, 49, 6, 37, 87, 13, 0, 0, 9, 134, 9, 14, 9, 13, 196, 131, 65, 0, 0, 10, 135, 7, 5, 1, 13, 196, 131, 14, 65, 14, 2, 95, 45, 49, 14, 16, 6, 35, 47, 37, 63, 13, 0, 0, 9, 198, 12, 129, 83, 80, 244, 128, 65, 12, 67, 24, 20, 129, 81, 4, 13, 34, 13, 0, 8, 13, 2, 95, 44, 82, 6, 37, 34, 79, 40, 55, 13, 0, 0, 11, 136, 6, 5, 14, 9, 3, 197, 159, 9, 65, 10, 2, 95, 51, 47, 14, 16, 6, 116, 0, 0, 7, 196, 29, 83, 5, 72, 65, 10, 135, 1, 197, 159, 5, 26, 196, 131, 67, 7, 196, 12, 194, 80, 36, 66, 21, 9, 15, 18, 9, 3, 196, 131, 18, 21, 9, 39, 16, 122, 49, 13, 34, 40, 37, 0, 79, 8, 2, 95, 50, 70, 6, 118, 0, 0, 11, 136, 16, 18, 15, 20, 5, 10, 196, 131, 67, 9, 134, 18, 5, 21, 197, 159, 9, 67, 9, 2, 95, 49, 6, 40, 50, 40, 0, 0, 10, 2, 95, 48, 86, 6, 36, 16, 39, 0, 0, 15, 140, 2, 9, 14, 5, 3, 21, 22, 195, 162, 14, 20, 1, 69, 11, 136, 4, 5, 19, 12, 21, 197, 159, 9, 67, 11, 2, 95, 55, 89, 6, 35, 48, 47, 36, 0, 0, 12, 137, 195, 174, 14, 3, 8, 9, 4, 5, 13, 66, 10, 2, 95, 54, 89, 6, 35, 87, 36, 0, 0, 12, 137, 1, 4, 5, 22, 196, 131, 18, 21, 12, 67, 11, 2, 95, 53, 74, 6, 37, 50, 74, 122, 0, 0, 6, 195, 85, 36, 201, 66, 12, 2, 95, 52, 48, 6, 35, 47, 14, 16, 40, 0, 0, 10, 135, 7, 5, 1, 13, 196, 131, 20, 65, 12, 4, 197, 163, 9, 5, 121, 6, 57, 36, 0, 72, 12, 4, 197, 163, 9, 5, 121, 6, 37, 36, 0, 76, 22, 2, 95, 59, 48, 6, 40, 50, 49, 47, 15, 89, 37, 82, 6, 37, 34, 79, 40, 55, 13, 0, 0, 7, 196, 76, 244, 197, 4, 66, 12, 137, 16, 18, 5, 7, 196, 131, 20, 5, 1, 67, 7, 196, 84, 229, 73, 4, 77, 17, 2, 95, 58, 70, 39, 6, 40, 13, 48, 6, 40, 50, 49, 47, 36, 0, 0, 9, 198, 65, 33, 90, 20, 229, 1, 67, 9, 134, 3, 196, 131, 4, 5, 1, 66, 9, 2, 95, 57, 50, 6, 129, 13, 0, 0, 9, 2, 95, 56, 6, 39, 48, 47, 0, 0, 16, 2, 95, 63, 110, 50, 47, 14, 16, 36, 69, 6, 35, 16, 36, 0, 0, 11, 136, 19, 20, 18, 9, 7, 196, 131, 20, 65, 12, 137, 3, 18, 195, 162, 14, 3, 5, 14, 9, 65, 7, 196, 4, 35, 206, 4, 67, 13, 2, 95, 62, 63, 115, 15, 63, 6, 35, 16, 36, 0, 0, 8, 197, 84, 197, 9, 52, 80, 65, 8, 197, 81, 84, 133, 48, 80, 66, 12, 137, 16, 18, 15, 1, 19, 16, 196, 131, 20, 65, 8, 197, 8, 244, 132, 20, 144, 66, 8, 197, 5, 4, 137, 28, 144, 65, 8, 197, 77, 68, 137, 12, 16, 66, 9, 198, 64, 20, 129, 48, 150, 129, 68, 0, 6, 195, 5, 36, 213, 66, 12, 2, 95, 60, 63, 115, 15, 63, 6, 37, 49, 0, 0, 10, 199, 28, 130, 76, 36, 209, 76, 20, 67, 0, 7, 196, 12, 240, 207, 76, 65, 7, 196, 76, 197, 74, 36, 66, 30, 8, 197, 159, 46, 1, 46, 13, 46, 4, 89, 37, 11, 35, 89, 4, 35, 15, 63, 115, 15, 70, 36, 48, 6, 35, 34, 47, 36, 0, 0, 8, 197, 56, 85, 5, 104, 144, 65, 14, 139, 13, 5, 19, 1, 7, 5, 18, 196, 131, 36, 50, 66, 8, 197, 104, 34, 69, 72, 16, 66, 0, 0, 11, 136, 1, 3, 5, 5, 1, 197, 159, 9, 66, 0, 7, 196, 85, 35, 5, 80, 65, 7, 196, 81, 83, 133, 80, 65, 7, 196, 77, 83, 133, 80, 65, 12, 137, 3, 196, 131, 16, 20, 21, 197, 159, 9, 67, 0, 8, 197, 52, 20, 137, 85, 48, 65, 0, 0, 26, 12, 195, 174, 14, 20, 15, 20, 4, 5, 1, 21, 14, 1, 110, 50, 47, 39, 47, 70, 133, 6, 40, 50, 35, 0, 0, 7, 196, 65, 83, 133, 52, 65, 7, 196, 72, 148, 195, 4, 66, 0, 8, 197, 4, 192, 137, 81, 80, 67, 0, 6, 195, 84, 193, 73, 66, 6, 195, 24, 16, 197, 76, 0, 21, 71, 65, 34, 69, 80, 83, 137, 20, 48, 14, 16, 57, 36, 47, 36, 50, 6, 37, 36, 0, 0, 7, 196, 48, 20, 197, 72, 65, 9, 133, 16, 15, 197, 163, 9, 76, 32, 0, 9, 134, 13, 196, 131, 18, 9, 9, 65, 0, 9, 198, 4, 53, 77, 84, 192, 64, 68, 17, 7, 22, 9, 5, 197, 163, 21, 9, 82, 57, 36, 121, 40, 6, 37, 0, 0, 9, 134, 195, 174, 14, 19, 196, 131, 8, 0, 7, 196, 77, 84, 5, 72, 65, 0, 9, 198, 36, 229, 5, 72, 84, 193, 68, 16, 6, 5, 18, 1, 197, 163, 9, 57, 36, 16, 35, 139, 122, 0, 78, 11, 136, 6, 9, 9, 14, 4, 3, 196, 131, 8, 0, 10, 135, 16, 21, 14, 5, 197, 163, 9, 65, 9, 198, 4, 209, 83, 80, 80, 192, 66, 9, 198, 76, 50, 9, 52, 32, 64, 66, 6, 195, 56, 144, 201, 8, 0, 11, 136, 3, 196, 131, 4, 5, 18, 9, 9, 66, 11, 136, 12, 9, 14, 7, 21, 197, 159, 9, 67, 11, 67, 20, 193, 64, 57, 36, 55, 36, 0, 76, 0, 12, 137, 19, 3, 196, 131, 4, 5, 18, 9, 9, 66, 12, 137, 195, 174, 14, 3, 18, 5, 197, 163, 9, 67, 12, 4, 95, 4, 15, 20, 48, 40, 50, 49, 47, 0, 0, 8, 197, 13, 33, 68, 37, 64, 65, 15, 67, 84, 67, 82, 117, 100, 101, 109, 101, 114, 39, 101, 0, 29, 0, 6, 195, 16, 80, 201, 8, 0, 7, 195, 4, 193, 64, 72, 28, 24, 2, 95, 91, 48, 35, 16, 35, 50, 47, 4, 36, 86, 13, 48, 13, 47, 14, 16, 6, 35, 47, 13, 0, 0, 0, 0, 11, 67, 36, 194, 69, 37, 55, 6, 37, 36, 0, 7, 66, 88, 144, 82, 37, 0, 0, 15, 2, 95, 95, 87, 40, 69, 55, 37, 50, 57, 6, 35, 47, 0, 0, 7, 196, 5, 4, 137, 28, 65, 8, 133, 7, 196, 131, 19, 9, 66, 0, 8, 197, 77, 69, 68, 36, 80, 66, 8, 197, 64, 244, 9, 12, 80, 66, 8, 197, 64, 148, 201, 12, 16, 66, 8, 197, 48, 147, 73, 80, 80, 65, 8, 197, 13, 33, 68, 20, 208, 65, 8, 197, 4, 193, 71, 20, 208, 66, 8, 197, 4, 69, 67, 20, 208, 66, 8, 197, 4, 98, 82, 52, 16, 67, 8, 197, 16, 245, 133, 16, 144, 67, 31, 2, 95, 93, 48, 35, 16, 35, 50, 47, 4, 36, 86, 13, 48, 13, 47, 14, 16, 6, 35, 47, 13, 110, 50, 49, 6, 37, 87, 13, 0, 0, 9, 198, 37, 53, 1, 52, 37, 76, 67, 10, 135, 18, 196, 131, 19, 21, 3, 9, 67, 14, 2, 95, 92, 69, 4, 36, 49, 87, 55, 6, 36, 89, 0, 0, 0, 7, 196, 16, 83, 79, 56, 65, 9, 133, 22, 5, 197, 163, 9, 76, 32, 0, 8, 197, 65, 85, 5, 72, 144, 66, 13, 138, 1, 16, 196, 131, 18, 196, 131, 18, 9, 9, 67, 8, 197, 5, 3, 5, 12, 16, 67, 9, 134, 1, 13, 5, 197, 163, 9, 67, 0, 9, 134, 22, 196, 131, 18, 21, 12, 65, 10, 135, 20, 5, 13, 5, 197, 163, 9, 65, 9, 198, 65, 33, 86, 20, 226, 64, 67, 10, 135, 196, 131, 19, 20, 15, 18, 1, 77, 0, 11, 136, 197, 163, 9, 14, 5, 197, 163, 9, 65, 0, 7, 196, 88, 84, 197, 48, 65, 20, 72, 8, 194, 84, 104, 180, 137, 20, 112, 69, 55, 6, 37, 121, 49, 34, 37, 79, 0, 11, 200, 72, 84, 18, 21, 161, 78, 80, 16, 68, 0, 8, 197, 37, 160, 137, 81, 80, 67, 9, 134, 26, 195, 162, 13, 2, 9, 66, 0, 6, 195, 24, 145, 213, 66, 0, 11, 136, 20, 196, 131, 22, 9, 197, 163, 5, 66, 0, 15, 3, 19, 196, 131, 87, 13, 124, 122, 0, 72, 81, 109, 105, 32, 16, 3, 19, 196, 131, 87, 13, 95, 122, 0, 72, 81, 197, 159, 105, 32, 12, 3, 19, 196, 131, 87, 127, 0, 72, 81, 105, 32, 13, 3, 19, 196, 131, 87, 13, 55, 0, 72, 81, 108, 32, 6, 131, 19, 196, 131, 72, 0, 0, 6, 195, 88, 148, 193, 66, 13, 4, 95, 7, 18, 22, 79, 14, 16, 6, 35, 82, 0, 0, 6, 195, 20, 66, 84, 65, 0, 24, 73, 16, 147, 148, 61, 65, 5, 5, 83, 129, 70, 37, 50, 47, 39, 47, 70, 133, 6, 40, 50, 35, 0, 10, 135, 12, 195, 162, 14, 7, 196, 131, 28, 6, 131, 3, 196, 131, 76, 0, 0, 16, 70, 92, 147, 132, 61, 116, 192, 6, 58, 37, 50, 70, 128, 87, 0, 9, 198, 49, 81, 15, 88, 144, 192, 65, 16, 70, 12, 80, 73, 56, 144, 192, 74, 6, 133, 57, 50, 37, 49, 0, 6, 195, 17, 84, 129, 66, 0, 6, 195, 4, 193, 88, 65, 0, 7, 196, 64, 148, 201, 12, 65, 14, 68, 24, 146, 78, 16, 81, 37, 6, 37, 50, 70, 0, 8, 0, 9, 198, 12, 243, 80, 48, 144, 197, 66, 9, 198, 12, 243, 85, 56, 144, 193, 68, 0, 10, 135, 3, 1, 16, 5, 197, 163, 9, 65, 10, 135, 2, 1, 20, 5, 197, 163, 9, 65, 10, 135, 1, 18, 4, 5, 197, 163, 9, 65, 9, 198, 36, 228, 212, 4, 192, 64, 67, 11, 135, 16, 21, 20, 5, 197, 163, 9, 76, 32, 0, 11, 136, 22, 9, 14, 4, 5, 197, 163, 9, 65, 11, 136, 21, 13, 16, 12, 5, 197, 163, 9, 65, 11, 136, 20, 196, 131, 3, 5, 18, 9, 9, 66, 10, 67, 4, 69, 64, 35, 70, 6, 40, 0, 0, 12, 137, 16, 9, 5, 18, 4, 5, 197, 163, 9, 65, 7, 196, 65, 85, 5, 4, 78, 0, 13, 138, 20, 18, 9, 13, 9, 20, 5, 197, 163, 9, 66, 13, 138, 16, 18, 15, 13, 9, 20, 5, 197, 163, 9, 66, 13, 138, 16, 18, 9, 3, 5, 16, 5, 197, 163, 9, 66, 13, 138, 195, 174, 14, 3, 5, 16, 5, 197, 163, 9, 66, 0, 14, 139, 195, 174, 14, 20, 9, 14, 4, 5, 197, 163, 9, 66, 9, 198, 24, 80, 146, 36, 193, 64, 66, 9, 198, 12, 20, 148, 20, 193, 64, 66, 0, 10, 199, 17, 32, 71, 61, 53, 5, 4, 65, 11, 136, 1, 3, 5, 197, 159, 20, 9, 1, 72, 23, 2, 95, 123, 48, 35, 16, 35, 50, 47, 4, 36, 86, 13, 35, 49, 39, 55, 6, 35, 70, 13, 0, 14, 4, 95, 4, 9, 1, 47, 14, 16, 6, 36, 63, 13, 0, 0, 12, 137, 3, 196, 131, 12, 3, 195, 162, 9, 5, 66, 0, 8, 197, 56, 148, 212, 61, 32, 65, 9, 198, 28, 19, 2, 20, 226, 73, 65, 9, 198, 5, 48, 213, 56, 65, 65, 67, 0, 9, 198, 28, 19, 2, 20, 225, 64, 65, 0, 0, 11, 68, 16, 242, 78, 4, 70, 118, 50, 35, 0, 12, 137, 19, 6, 196, 131, 18, 195, 162, 13, 1, 67, 11, 2, 95, 126, 47, 6, 37, 55, 70, 13, 0, 0, 8, 197, 64, 84, 5, 56, 80, 65, 8, 197, 21, 130, 83, 80, 16, 67, 8, 197, 16, 80, 207, 48, 16, 67, 9, 134, 16, 196, 131, 197, 163, 9, 66, 9, 133, 3, 195, 162, 14, 4, 72, 8, 8, 197, 4, 197, 5, 36, 16, 77, 30, 2, 95, 125, 48, 35, 16, 35, 50, 47, 4, 36, 86, 13, 35, 49, 39, 55, 6, 35, 70, 13, 110, 50, 49, 6, 37, 87, 13, 0, 0, 20, 2, 95, 124, 69, 6, 35, 34, 13, 82, 36, 34, 47, 37, 49, 6, 35, 55, 13, 0, 0, 0, 11, 67, 4, 69, 83, 35, 70, 6, 40, 87, 0, 20, 8, 15, 18, 9, 3, 195, 162, 14, 4, 39, 16, 122, 49, 4, 110, 50, 70, 0, 76, 0, 8, 197, 64, 17, 213, 8, 80, 65, 8, 197, 4, 210, 67, 36, 144, 66, 9, 134, 1, 13, 21, 197, 163, 9, 67, 0, 9, 198, 28, 19, 2, 20, 226, 64, 65, 10, 135, 3, 21, 7, 5, 197, 163, 9, 65, 0, 27, 12, 19, 21, 16, 18, 1, 22, 9, 5, 197, 163, 21, 9, 87, 40, 48, 34, 35, 82, 57, 36, 121, 40, 6, 37, 0, 0, 12, 137, 19, 3, 15, 1, 20, 5, 197, 163, 9, 65, 11, 200, 12, 243, 148, 72, 22, 137, 12, 80, 67, 11, 200, 4, 67, 73, 56, 148, 212, 72, 16, 68, 0, 13, 138, 16, 5, 18, 13, 9, 20, 5, 197, 163, 9, 66, 9, 198, 24, 19, 129, 80, 144, 201, 66, 17, 142, 195, 174, 13, 2, 21, 14, 196, 131, 20, 196, 131, 197, 163, 9, 69, 0, 14, 139, 4, 9, 19, 20, 9, 14, 7, 5, 197, 163, 9, 66, 14, 139, 4, 5, 19, 3, 8, 9, 26, 196, 131, 20, 21, 68, 0, 11, 136, 195, 174, 14, 6, 12, 15, 18, 9, 67, 0, 12, 137, 16, 196, 131, 4, 21, 18, 9, 3, 5, 67, 7, 196, 61, 5, 9, 52, 65, 0, 8, 197, 5, 97, 78, 81, 80, 67, 0, 19, 9, 22, 9, 19, 45, 1, 45, 22, 9, 19, 82, 37, 86, 35, 82, 6, 37, 0, 5, 194, 84, 224, 72, 0, 11, 136, 7, 196, 131, 21, 18, 9, 3, 5, 66, 0, 10, 135, 4, 5, 3, 15, 12, 196, 131, 67, 0, 9, 134, 15, 2, 197, 163, 9, 9, 66, 13, 138, 7, 195, 162, 7, 195, 162, 12, 9, 3, 5, 67, 0, 9, 198, 72, 86, 137, 77, 64, 64, 67, 9, 198, 25, 83, 7, 21, 32, 64, 67, 9, 198, 21, 132, 12, 61, 32, 64, 67, 9, 198, 21, 128, 71, 21, 32, 64, 68, 9, 198, 12, 243, 69, 57, 64, 64, 67, 0, 12, 136, 9, 1, 18, 196, 131, 197, 159, 9, 65, 8, 0, 0, 0, 10, 135, 7, 195, 162, 4, 9, 12, 1, 67, 10, 135, 13, 15, 12, 5, 197, 159, 9, 67, 0, 11, 136, 20, 18, 5, 3, 5, 197, 163, 9, 65, 11, 136, 13, 5, 18, 7, 5, 197, 163, 9, 65, 10, 199, 16, 80, 207, 56, 80, 212, 4, 68, 0, 12, 137, 1, 10, 21, 14, 7, 5, 197, 163, 9, 66, 12, 137, 195, 174, 14, 4, 18, 5, 16, 20, 1, 67, 0, 13, 138, 197, 159, 20, 5, 18, 7, 5, 197, 163, 9, 65, 13, 138, 16, 5, 20, 18, 5, 3, 5, 197, 163, 9, 66, 15, 140, 195, 174, 14, 4, 5, 16, 196, 131, 18, 20, 196, 131, 68, 13, 138, 4, 5, 19, 6, 1, 3, 5, 197, 163, 9, 66, 13, 138, 3, 15, 14, 4, 21, 3, 5, 197, 163, 9, 66, 9, 198, 24, 16, 201, 48, 149, 1, 68, 0, 14, 139, 19, 20, 18, 195, 162, 14, 7, 5, 197, 163, 9, 65, 14, 139, 195, 174, 14, 3, 9, 14, 7, 5, 197, 163, 9, 66, 9, 198, 25, 83, 7, 21, 33, 64, 65, 13, 4, 95, 35, 51, 50, 87, 48, 6, 35, 121, 114, 0, 0, 15, 140, 195, 174, 14, 20, 15, 1, 18, 3, 5, 197, 163, 9, 66, 0, 7, 196, 5, 86, 133, 4, 66, 12, 137, 1, 197, 159, 20, 5, 18, 14, 5, 1, 67, 0, 8, 197, 88, 144, 212, 61, 32, 65, 15, 69, 52, 20, 139, 21, 32, 63, 6, 35, 34, 49, 13, 34, 0, 9, 134, 2, 18, 15, 197, 159, 21, 66, 8, 197, 5, 50, 71, 85, 32, 66, 9, 198, 64, 245, 18, 37, 97, 65, 67, 9, 134, 7, 195, 162, 14, 4, 9, 66, 0, 9, 198, 77, 68, 149, 13, 69, 64, 66, 9, 198, 60, 20, 208, 21, 65, 64, 65, 9, 198, 9, 81, 142, 37, 69, 64, 67, 0, 11, 136, 20, 196, 131, 3, 5, 18, 5, 1, 66, 11, 136, 195, 174, 14, 7, 18, 15, 26, 9, 67, 0, 11, 200, 36, 228, 212, 73, 80, 212, 61, 32, 66, 10, 135, 4, 18, 1, 7, 15, 197, 159, 65, 7, 196, 13, 83, 20, 84, 66, 0, 8, 197, 4, 100, 137, 12, 16, 65, 8, 197, 65, 33, 68, 20, 16, 66, 0, 9, 198, 76, 195, 194, 61, 162, 64, 67, 9, 198, 16, 84, 197, 73, 98, 64, 67, 0, 11, 136, 195, 174, 14, 18, 15, 197, 159, 9, 67, 11, 136, 195, 174, 14, 18, 15, 197, 159, 9, 67, 0, 7, 196, 36, 66, 76, 20, 66, 8, 133, 2, 21, 197, 159, 9, 66, 9, 133, 4, 5, 197, 159, 9, 66, 8, 0, 8, 197, 48, 16, 210, 36, 208, 65, 15, 69, 77, 1, 82, 36, 16, 87, 48, 36, 16, 6, 57, 35, 0, 0, 6, 195, 28, 19, 5, 66, 6, 195, 76, 244, 201, 66, 9, 198, 64, 245, 18, 37, 98, 64, 67, 10, 198, 64, 245, 133, 77, 66, 64, 67, 9, 6, 195, 52, 83, 5, 77, 0, 19, 8, 195, 174, 14, 12, 15, 3, 21, 9, 110, 50, 55, 39, 49, 40, 6, 37, 0, 0, 12, 67, 9, 34, 79, 69, 14, 16, 6, 37, 39, 0, 12, 137, 16, 18, 196, 131, 2, 21, 197, 159, 9, 67, 0, 0, 14, 139, 195, 174, 14, 16, 21, 14, 19, 196, 131, 20, 21, 68, 6, 195, 12, 19, 5, 65, 6, 195, 76, 19, 5, 77, 0, 10, 199, 16, 148, 212, 36, 225, 197, 52, 66, 0, 0, 8, 197, 4, 113, 78, 81, 80, 67, 0, 10, 135, 6, 21, 18, 9, 197, 159, 1, 67, 0, 10, 135, 18, 195, 162, 14, 10, 5, 20, 65, 11, 136, 195, 174, 14, 3, 21, 18, 3, 1, 67, 10, 199, 12, 192, 83, 36, 98, 67, 4, 68, 0, 10, 135, 1, 12, 5, 18, 7, 196, 131, 66, 0, 0, 12, 137, 14, 5, 18, 5, 7, 21, 12, 196, 131, 66, 9, 198, 12, 243, 133, 13, 64, 64, 67, 9, 198, 53, 83, 20, 61, 32, 64, 77, 10, 135, 195, 174, 14, 19, 21, 13, 9, 77, 0, 0, 13, 68, 12, 244, 212, 4, 49, 39, 87, 47, 6, 35, 0, 0, 0, 6, 195, 64, 245, 5, 66, 9, 198, 60, 34, 69, 13, 64, 64, 67, 9, 198, 4, 49, 76, 61, 32, 64, 78, 0, 11, 136, 1, 197, 159, 20, 5, 16, 20, 1, 67, 0, 9, 198, 65, 35, 198, 21, 51, 210, 66, 13, 68, 13, 85, 9, 4, 49, 40, 47, 6, 37, 35, 0, 0, 9, 134, 16, 196, 131, 18, 5, 1, 66, 12, 201, 21, 132, 5, 72, 147, 69, 57, 64, 64, 69, 0, 9, 198, 104, 115, 205, 61, 65, 64, 65, 9, 198, 12, 244, 133, 13, 69, 64, 67, 10, 135, 1, 16, 196, 131, 18, 5, 1, 67, 0, 0, 12, 137, 26, 21, 7, 18, 196, 131, 22, 5, 1, 67, 12, 137, 4, 9, 19, 16, 196, 131, 18, 5, 1, 67, 0, 0, 9, 198, 77, 81, 140, 21, 65, 64, 65, 9, 198, 64, 240, 206, 37, 69, 64, 67, 9, 198, 64, 16, 207, 77, 65, 64, 65, 10, 135, 195, 174, 14, 3, 21, 9, 5, 66, 9, 198, 28, 20, 142, 37, 69, 64, 67, 18, 70, 61, 34, 67, 5, 33, 64, 39, 16, 122, 49, 4, 35, 16, 36, 0, 76, 0, 11, 136, 4, 5, 21, 14, 196, 131, 26, 9, 68, 11, 136, 3, 196, 131, 4, 5, 18, 5, 1, 66, 0, 7, 196, 84, 209, 90, 36, 65, 12, 137, 19, 3, 196, 131, 4, 5, 18, 5, 1, 66, 7, 196, 64, 17, 201, 56, 65, 8, 196, 64, 240, 84, 20, 76, 32, 0, 8, 197, 76, 80, 207, 48, 80, 65, 8, 197, 64, 84, 5, 56, 144, 65, 8, 197, 24, 20, 207, 48, 80, 66, 8, 197, 72, 84, 1, 72, 16, 67, 8, 197, 4, 67, 210, 52, 144, 67, 0, 10, 135, 16, 196, 131, 19, 20, 18, 1, 66, 6, 195, 12, 149, 9, 66, 0, 0, 7, 196, 48, 241, 201, 12, 65, 7, 196, 4, 69, 78, 4, 67, 0, 14, 69, 28, 243, 199, 48, 80, 79, 6, 40, 79, 13, 55, 0, 8, 197, 12, 130, 77, 36, 48, 65, 8, 197, 4, 225, 18, 20, 144, 66, 8, 197, 64, 194, 77, 8, 16, 66, 8, 197, 61, 33, 15, 56, 16, 67, 15, 69, 21, 99, 204, 84, 16, 36, 82, 39, 55, 58, 6, 35, 0, 0, 14, 139, 22, 9, 14, 15, 22, 196, 131, 197, 163, 9, 9, 68, 0, 11, 136, 18, 196, 131, 7, 21, 197, 159, 9, 67, 0, 11, 67, 61, 5, 83, 39, 48, 6, 40, 87, 0, 13, 68, 13, 85, 9, 20, 49, 40, 47, 6, 37, 36, 0, 8, 196, 65, 85, 5, 52, 76, 32, 12, 137, 1, 3, 5, 12, 5, 1, 197, 159, 9, 66, 0, 9, 198, 52, 16, 213, 48, 21, 21, 68, 8, 197, 25, 32, 67, 81, 80, 66, 0, 14, 139, 195, 174, 14, 20, 195, 162, 13, 16, 9, 14, 1, 68, 0, 0, 12, 68, 5, 84, 137, 84, 35, 40, 16, 6, 114, 0, 7, 196, 80, 144, 211, 36, 66, 0, 0, 0, 10, 199, 4, 212, 212, 21, 33, 1, 52, 65, 11, 136, 195, 174, 14, 3, 5, 18, 3, 1, 67, 0, 10, 135, 18, 5, 26, 5, 13, 196, 131, 67, 7, 196, 61, 33, 9, 56, 65, 0, 8, 197, 76, 20, 131, 36, 224, 65, 8, 197, 28, 84, 129, 72, 64, 65, 9, 197, 5, 53, 6, 20, 192, 65, 8, 0, 10, 135, 18, 196, 131, 7, 5, 20, 5, 65, 9, 198, 21, 132, 5, 16, 144, 64, 67, 9, 198, 17, 84, 133, 72, 80, 64, 66, 0, 6, 195, 52, 80, 64, 76, 0, 7, 196, 81, 81, 15, 72, 65, 7, 196, 60, 97, 82, 20, 66, 7, 196, 28, 192, 90, 84, 66, 7, 196, 4, 165, 84, 4, 67, 0, 0, 12, 137, 3, 15, 14, 20, 9, 14, 21, 196, 131, 66, 9, 198, 56, 147, 73, 12, 80, 64, 67, 0, 23, 11, 20, 18, 9, 39, 21, 14, 7, 8, 9, 21, 12, 47, 16, 37, 40, 50, 79, 57, 40, 55, 0, 0, 7, 196, 13, 85, 9, 36, 66, 0, 9, 198, 77, 64, 82, 61, 53, 5, 65, 0, 17, 70, 12, 192, 85, 16, 149, 64, 49, 55, 35, 6, 40, 70, 57, 40, 0, 9, 198, 8, 17, 10, 60, 53, 64, 67, 10, 135, 1, 13, 21, 197, 163, 5, 1, 67, 0, 6, 195, 84, 209, 68, 65, 11, 136, 18, 15, 13, 195, 174, 14, 9, 1, 67, 0, 0, 8, 197, 48, 81, 148, 21, 32, 65, 13, 138, 195, 174, 13, 2, 195, 162, 3, 19, 5, 1, 67, 0, 10, 135, 18, 196, 131, 13, 195, 162, 9, 66, 9, 198, 52, 84, 212, 20, 49, 64, 65, 0, 9, 67, 36, 82, 64, 6, 57, 116, 0, 0, 21, 9, 13, 21, 18, 4, 196, 131, 18, 9, 5, 63, 40, 34, 70, 13, 16, 6, 37, 36, 0, 13, 68, 48, 21, 90, 36, 55, 6, 35, 40, 86, 122, 0, 6, 195, 4, 210, 67, 66, 10, 135, 1, 3, 5, 12, 1, 197, 159, 66, 0, 8, 197, 80, 84, 129, 64, 144, 20, 8, 197, 64, 148, 201, 12, 144, 66, 9, 198, 16, 84, 198, 4, 49, 77, 66, 8, 197, 36, 228, 197, 72, 16, 67, 8, 197, 4, 225, 193, 40, 16, 67, 0, 14, 139, 13, 196, 131, 18, 20, 21, 18, 9, 19, 5, 1, 68, 0, 6, 195, 52, 82, 64, 76, 0, 0, 9, 198, 56, 84, 133, 29, 83, 9, 66, 8, 197, 8, 83, 7, 36, 16, 65, 8, 197, 4, 38, 137, 12, 80, 66, 8, 197, 16, 80, 149, 80, 16, 67, 14, 69, 61, 34, 67, 84, 144, 39, 16, 122, 49, 119, 0, 79, 0, 6, 195, 80, 244, 9, 66, 10, 135, 195, 174, 14, 19, 5, 18, 1, 67, 0, 10, 199, 4, 197, 3, 36, 225, 86, 4, 68, 10, 199, 72, 85, 133, 72, 33, 82, 4, 68, 6, 195, 12, 19, 64, 72, 0, 0, 0, 9, 198, 52, 20, 137, 80, 147, 64, 66, 0, 0, 0, 9, 198, 104, 68, 133, 48, 149, 21, 67, 0, 9, 198, 16, 147, 131, 60, 195, 192, 65, 0, 10, 199, 65, 85, 5, 72, 226, 67, 36, 66, 10, 67, 32, 242, 84, 105, 6, 118, 47, 0, 10, 199, 12, 21, 1, 16, 144, 211, 36, 68, 0, 7, 196, 64, 17, 213, 8, 65, 0, 24, 10, 5, 24, 5, 18, 3, 9, 197, 163, 9, 21, 36, 79, 86, 36, 34, 74, 6, 37, 121, 57, 40, 0, 0, 10, 135, 18, 195, 162, 19, 5, 20, 5, 65, 17, 70, 12, 192, 85, 16, 144, 64, 49, 55, 35, 6, 40, 70, 57, 35, 0, 6, 195, 77, 4, 133, 28, 0, 0, 14, 68, 21, 132, 21, 76, 36, 49, 87, 48, 6, 40, 87, 0, 0, 8, 197, 28, 19, 2, 20, 224, 65, 0, 9, 198, 77, 81, 133, 72, 80, 64, 67, 17, 7, 18, 196, 131, 19, 6, 15, 9, 34, 13, 87, 81, 39, 6, 37, 0, 0, 10, 199, 77, 80, 143, 72, 66, 78, 20, 66, 7, 195, 76, 21, 64, 72, 8, 0, 0, 15, 6, 197, 159, 5, 6, 9, 1, 89, 36, 81, 6, 37, 35, 0, 0, 9, 198, 24, 16, 212, 36, 49, 64, 66, 0, 6, 195, 52, 85, 64, 76, 0, 7, 196, 53, 84, 133, 4, 66, 12, 137, 195, 174, 14, 20, 5, 197, 163, 5, 1, 67, 12, 137, 4, 5, 16, 196, 131, 197, 159, 5, 1, 67, 0, 22, 10, 3, 5, 1, 21, 197, 159, 5, 19, 3, 21, 74, 133, 40, 89, 6, 36, 87, 49, 40, 0, 8, 197, 4, 49, 76, 61, 32, 74, 0, 10, 135, 20, 196, 131, 3, 5, 18, 9, 66, 9, 198, 65, 33, 76, 36, 225, 192, 66, 10, 135, 20, 18, 196, 131, 7, 5, 1, 66, 10, 135, 16, 12, 196, 131, 3, 5, 1, 66, 0, 11, 136, 16, 12, 196, 131, 3, 5, 18, 9, 66, 11, 136, 195, 174, 14, 4, 5, 19, 5, 1, 67, 0, 12, 68, 104, 243, 66, 36, 86, 39, 63, 69, 37, 0, 7, 196, 76, 145, 213, 72, 65, 0, 8, 197, 52, 241, 5, 48, 16, 67, 0, 10, 135, 20, 196, 131, 3, 5, 18, 5, 66, 10, 135, 195, 174, 14, 3, 5, 16, 21, 67, 0, 11, 136, 16, 12, 196, 131, 3, 5, 18, 5, 66, 10, 199, 4, 53, 80, 84, 224, 212, 84, 68, 10, 199, 16, 85, 5, 72, 210, 78, 4, 68, 10, 199, 13, 85, 18, 20, 213, 82, 4, 68, 0, 7, 196, 36, 148, 213, 76, 66, 8, 133, 22, 195, 162, 14, 1, 66, 7, 196, 60, 97, 82, 36, 67, 0, 9, 134, 2, 196, 131, 21, 20, 21, 67, 13, 138, 195, 174, 14, 3, 196, 131, 9, 5, 18, 1, 68, 8, 197, 21, 53, 9, 52, 16, 67, 8, 197, 16, 148, 212, 72, 16, 66, 13, 138, 26, 196, 131, 4, 196, 131, 18, 14, 9, 9, 68, 0, 0, 10, 199, 81, 32, 78, 76, 97, 82, 4, 68, 10, 199, 36, 229, 5, 72, 97, 82, 4, 68, 0, 11, 136, 197, 159, 14, 9, 197, 163, 5, 12, 65, 7, 196, 72, 81, 213, 48, 65, 7, 196, 52, 144, 213, 48, 65, 0, 6, 20, 0, 0, 0, 25, 2, 0, 0, 95, 1, 0, 0, 27, 2, 0, 0, 99, 1, 0, 0, 24, 2, 0, 0, 95, 1, 0, 0, 26, 2, 0, 0, 99, 1, 0, 0, 0, 0, 0, 0, 6, 195, 162, 0, 105, 101, 1, 21, 2, 32, 3, 8, 131, 36, 0, 3, 110, 0, 105, 3, 131, 0, 117, 3, 132, 0, 7, 6, 195, 174, 0, 1, 21, 2, 32, 3, 6, 110, 0, 3, 110, 0, 7, 6, 196, 131, 0, 117, 2, 32, 3, 6, 128, 0, 1, 21, 2, 17, 67, 196, 131, 32, 3, 8, 13, 0, 105, 101, 1, 21, 2, 32, 3, 8, 127, 36, 0, 4, 3, 13, 0, 1, 10, 2, 32, 14, 128, 192, 129, 0, 1, 17, 67, 131, 196, 21, 2, 32, 0, 1, 99, 101, 10, 2, 32, 0, 1, 114, 101, 21, 2, 32, 0, 1, 163, 197, 105, 21, 2, 32, 0, 4, 114, 105, 2, 17, 65, 17, 65, 32, 3, 13, 16, 6, 37, 0, 114, 105, 2, 17, 65, 32, 0, 114, 105, 105, 2, 32, 3, 13, 16, 6, 130, 0, 4, 117, 1, 99, 2, 116, 3, 13, 40, 0, 117, 8, 98, 2, 116, 0, 117, 8, 100, 2, 110, 0, 117, 8, 108, 2, 100, 0, 116, 196, 131, 1, 21, 2, 32, 14, 129, 128, 131, 3, 13, 47, 13, 0, 116, 101, 1, 21, 2, 32, 14, 129, 128, 131, 3, 13, 47, 36, 0, 116, 101, 108, 101, 1, 21, 2, 32, 14, 129, 128, 133, 3, 13, 47, 36, 55, 36, 0, 116, 101, 108, 111, 114, 1, 21, 2, 32, 14, 129, 128, 134, 3, 13, 47, 36, 55, 39, 34, 0, 116, 117, 108, 1, 21, 2, 32, 14, 129, 128, 132, 3, 13, 47, 40, 55, 0, 116, 117, 108, 117, 105, 1, 21, 2, 32, 14, 129, 128, 134, 3, 13, 47, 40, 55, 119, 0, 105, 2, 32, 3, 127, 0, 117, 3, 128, 0, 7, 6, 197, 159, 0, 3, 89, 0, 110, 105, 1, 21, 2, 32, 3, 89, 50, 6, 37, 0, 105, 1, 45, 2, 32, 3, 89, 122, 0, 1, 21, 2, 105, 32, 3, 95, 0, 7, 6, 197, 163, 0, 3, 121, 0, 1, 21, 2, 105, 32, 3, 139, 0, 105, 1, 45, 2, 32, 3, 139, 126, 0, 7, 6, 97, 0, 4, 1, 21, 26, 2, 24, 32, 3, 6, 35, 0, 1, 105, 131, 196, 2, 32, 0, 1, 110, 111, 105, 21, 2, 32, 0, 117, 8, 108, 2, 100, 3, 6, 35, 40, 0, 108, 101, 1, 21, 2, 32, 3, 6, 35, 55, 36, 0, 98, 105, 108, 1, 21, 2, 32, 3, 6, 35, 69, 37, 55, 0, 117, 2, 32, 3, 6, 112, 0, 105, 2, 32, 3, 6, 115, 0, 4, 3, 35, 0, 1, 10, 2, 32, 14, 128, 192, 129, 0, 1, 105, 103, 2, 32, 14, 128, 192, 129, 0, 2, 17, 65, 17, 65, 17, 65, 0, 105, 1, 110, 2, 118, 3, 35, 37, 0, 4, 117, 1, 99, 2, 116, 3, 35, 40, 0, 117, 2, 100, 0, 117, 2, 114, 0, 117, 2, 115, 116, 0, 117, 2, 122, 0, 110, 116, 105, 8, 2, 21, 14, 128, 132, 132, 3, 35, 50, 47, 37, 0, 105, 2, 97, 3, 35, 57, 0, 117, 3, 112, 0, 105, 3, 115, 0, 7, 6, 98, 0, 4, 1, 21, 2, 105, 108, 32, 3, 8, 69, 0, 1, 21, 2, 105, 108, 97, 32, 0, 1, 21, 2, 105, 108, 105, 32, 0, 1, 21, 2, 105, 108, 105, 105, 32, 0, 1, 21, 2, 105, 108, 105, 108, 101, 32, 0, 1, 21, 2, 105, 108, 105, 108, 111, 114, 32, 0, 1, 21, 2, 105, 108, 117, 108, 117, 105, 32, 0, 4, 3, 69, 0, 98, 0, 105, 108, 1, 111, 109, 2, 32, 3, 69, 6, 37, 55, 0, 1, 21, 2, 105, 32, 3, 141, 0, 7, 6, 99, 0, 111, 108, 1, 21, 21, 2, 32, 3, 8, 49, 39, 55, 0, 111, 108, 105, 1, 21, 21, 2, 32, 14, 129, 128, 129, 3, 8, 122, 0, 111, 108, 101, 1, 21, 21, 2, 32, 14, 129, 128, 129, 3, 36, 0, 4, 3, 49, 0, 104, 0, 110, 105, 1, 21, 2, 32, 3, 49, 50, 6, 37, 0, 110, 101, 97, 1, 21, 2, 32, 3, 49, 50, 36, 6, 35, 0, 4, 2, 101, 3, 74, 0, 2, 105, 0, 105, 2, 111, 0, 105, 105, 3, 74, 130, 0, 7, 6, 100, 0, 4, 3, 70, 0, 100, 0, 1, 21, 2, 105, 32, 3, 142, 0, 7, 6, 101, 0, 1, 17, 67, 10, 2, 114, 101, 32, 3, 2, 36, 0, 117, 1, 21, 2, 108, 32, 3, 6, 36, 40, 0, 117, 1, 21, 2, 32, 24, 3, 6, 113, 0, 105, 1, 114, 2, 101, 114, 32, 3, 6, 116, 0, 4, 1, 21, 2, 114, 97, 32, 3, 8, 36, 0, 1, 21, 2, 114, 101, 32, 0, 1, 21, 2, 114, 101, 97, 32, 0, 1, 21, 2, 114, 101, 105, 32, 0, 1, 21, 2, 114, 105, 32, 0, 1, 21, 2, 114, 105, 105, 32, 0, 1, 21, 2, 114, 196, 131, 32, 0, 197, 159, 1, 21, 2, 32, 3, 8, 36, 89, 0, 197, 159, 105, 108, 111, 114, 1, 21, 2, 32, 3, 8, 36, 89, 37, 55, 39, 34, 0, 197, 159, 117, 108, 1, 21, 2, 32, 3, 8, 36, 89, 40, 55, 0, 197, 159, 117, 108, 117, 105, 1, 21, 2, 32, 3, 8, 36, 89, 40, 55, 119, 0, 197, 159, 105, 1, 21, 2, 32, 3, 8, 36, 89, 122, 0, 4, 3, 36, 0, 1, 102, 21, 2, 114, 97, 32, 0, 1, 102, 21, 2, 114, 97, 32, 0, 1, 105, 2, 114, 97, 32, 0, 1, 105, 2, 114, 101, 32, 0, 1, 105, 2, 114, 101, 97, 32, 0, 1, 105, 2, 114, 105, 32, 0, 1, 105, 2, 114, 105, 105, 32, 0, 1, 105, 2, 114, 196, 131, 32, 0, 2, 17, 65, 17, 65, 17, 65, 0, 111, 1, 100, 2, 115, 101, 98, 3, 36, 39, 0, 117, 1, 21, 2, 32, 3, 36, 40, 0, 99, 1, 116, 17, 65, 21, 2, 105, 105, 32, 3, 36, 74, 0, 4, 101, 8, 99, 97, 2, 97, 3, 116, 0, 105, 2, 32, 0, 105, 8, 0, 4, 97, 3, 133, 0, 97, 1, 10, 2, 32, 14, 128, 192, 130, 0, 83, 105, 1, 10, 3, 133, 57, 0, 97, 117, 3, 133, 58, 0, 111, 3, 134, 0, 111, 97, 3, 134, 6, 35, 0, 7, 6, 102, 0, 4, 3, 81, 0, 102, 0, 1, 21, 2, 105, 32, 3, 140, 0, 7, 6, 103, 0, 4, 2, 101, 3, 73, 0, 2, 105, 0, 105, 105, 1, 10, 2, 32, 3, 73, 6, 130, 0, 105, 1, 10, 2, 17, 65, 32, 3, 73, 37, 0, 105, 105, 3, 73, 130, 0, 4, 3, 79, 0, 104, 0, 7, 6, 104, 0, 1, 21, 2, 105, 32, 3, 97, 0, 3, 105, 0, 7, 6, 105, 0, 1, 99, 2, 117, 17, 67, 3, 0, 110, 103, 1, 10, 2, 32, 3, 2, 37, 66, 79, 0, 4, 101, 105, 1, 108, 105, 102, 2, 32, 3, 6, 36, 37, 0, 101, 105, 1, 109, 111, 110, 2, 32, 0, 4, 1, 10, 26, 2, 24, 32, 3, 6, 37, 0, 1, 114, 99, 115, 2, 101, 0, 2, 116, 32, 0, 4, 97, 1, 17, 67, 131, 196, 2, 32, 3, 6, 37, 35, 0, 97, 1, 17, 67, 162, 195, 2, 32, 0, 97, 1, 102, 97, 114, 103, 2, 32, 0, 97, 1, 108, 105, 102, 2, 32, 0, 97, 1, 109, 111, 110, 2, 32, 0, 97, 1, 110, 111, 2, 32, 0, 97, 1, 112, 111, 99, 115, 2, 32, 0, 97, 1, 114, 101, 2, 32, 0, 97, 1, 159, 197, 117, 2, 32, 0, 4, 101, 1, 17, 67, 131, 196, 2, 32, 3, 6, 37, 36, 0, 101, 1, 17, 67, 162, 195, 2, 32, 0, 101, 1, 102, 97, 114, 103, 2, 32, 0, 101, 1, 108, 105, 102, 2, 32, 0, 101, 1, 109, 111, 110, 2, 32, 0, 101, 1, 110, 111, 2, 32, 0, 101, 1, 112, 111, 99, 115, 2, 32, 0, 101, 1, 159, 197, 117, 2, 32, 0, 4, 101, 105, 1, 102, 97, 114, 103, 2, 32, 3, 6, 37, 116, 0, 101, 105, 1, 110, 111, 2, 32, 0, 101, 105, 1, 114, 101, 2, 32, 0, 101, 105, 1, 159, 197, 117, 2, 32, 0, 101, 105, 2, 32, 0, 4, 105, 1, 102, 97, 114, 103, 2, 32, 3, 6, 130, 0, 105, 1, 112, 111, 99, 115, 2, 32, 0, 4, 1, 21, 2, 197, 163, 101, 32, 3, 8, 37, 0, 1, 21, 2, 197, 163, 101, 105, 32, 0, 1, 21, 2, 197, 163, 101, 108, 101, 32, 0, 1, 21, 2, 197, 163, 101, 108, 111, 114, 32, 0, 1, 21, 2, 197, 163, 196, 131, 32, 12, 12, 12, 12, 12, 12, 12, 12, 0, 1, 103, 2, 110, 101, 32, 0, 1, 103, 2, 110, 101, 97, 32, 0, 101, 1, 163, 197, 99, 2, 32, 3, 8, 37, 36, 0, 99, 1, 10, 2, 32, 3, 8, 37, 49, 0, 99, 97, 1, 10, 2, 32, 3, 8, 37, 49, 35, 0, 99, 101, 1, 10, 2, 32, 3, 8, 37, 74, 36, 0, 99, 105, 108, 101, 1, 10, 2, 32, 3, 8, 37, 74, 37, 55, 36, 0, 99, 105, 108, 111, 114, 1, 10, 2, 32, 3, 8, 37, 74, 37, 55, 39, 34, 0, 99, 101, 105, 1, 21, 2, 32, 3, 8, 37, 74, 116, 0, 99, 105, 105, 1, 21, 2, 32, 3, 8, 37, 74, 130, 0, 197, 159, 116, 101, 1, 21, 2, 32, 3, 8, 37, 89, 47, 36, 0, 197, 159, 116, 101, 97, 1, 21, 2, 32, 3, 8, 37, 89, 47, 133, 0, 101, 105, 1, 163, 197, 99, 2, 32, 3, 8, 37, 116, 0, 97, 1, 163, 197, 99, 2, 32, 3, 8, 57, 35, 0, 1, 45, 105, 163, 197, 2, 32, 3, 10, 0, 4, 3, 37, 0, 1, 10, 2, 32, 24, 14, 128, 192, 129, 0, 1, 10, 2, 45, 24, 14, 128, 192, 129, 0, 1, 39, 10, 2, 32, 0, 1, 114, 17, 67, 2, 32, 12, 12, 12, 0, 1, 163, 197, 2, 45, 17, 67, 105, 0, 1, 163, 197, 2, 45, 17, 67, 196, 131, 0, 1, 163, 197, 2, 45, 108, 0, 1, 163, 197, 2, 45, 110, 101, 0, 105, 105, 3, 37, 57, 37, 0, 101, 105, 1, 112, 111, 99, 115, 2, 32, 3, 37, 116, 0, 4, 1, 21, 2, 101, 32, 3, 57, 0, 1, 45, 2, 32, 0, 2, 17, 65, 0, 117, 3, 57, 40, 0, 111, 97, 3, 57, 108, 6, 35, 0, 117, 2, 32, 3, 114, 0, 1, 17, 67, 10, 2, 32, 24, 14, 128, 192, 129, 3, 126, 0, 4, 105, 3, 130, 0, 105, 1, 10, 2, 32, 14, 128, 192, 130, 0, 7, 6, 106, 0, 3, 88, 0, 1, 21, 2, 105, 32, 3, 94, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 4, 3, 55, 0, 1, 45, 2, 32, 0, 1, 117, 105, 2, 32, 14, 129, 128, 129, 0, 108, 0, 4, 8, 2, 32, 3, 55, 36, 0, 101, 1, 10, 2, 32, 14, 129, 128, 130, 0, 111, 114, 1, 10, 2, 32, 14, 129, 128, 131, 3, 55, 39, 34, 0, 117, 105, 1, 10, 2, 32, 14, 129, 128, 131, 3, 55, 119, 0, 1, 21, 2, 105, 32, 3, 123, 0, 7, 6, 109, 0, 4, 3, 63, 0, 8, 2, 45, 97, 0, 109, 0, 8, 2, 32, 3, 63, 36, 0, 105, 1, 45, 2, 32, 3, 63, 126, 0, 1, 21, 2, 105, 32, 3, 124, 0, 7, 6, 110, 0, 4, 1, 21, 2, 105, 99, 32, 3, 8, 50, 0, 1, 21, 2, 116, 105, 99, 32, 0, 4, 3, 50, 0, 1, 45, 2, 32, 0, 8, 2, 45, 97, 0, 4, 8, 2, 32, 3, 50, 36, 0, 101, 1, 105, 100, 117, 116, 105, 21, 2, 32, 14, 129, 128, 130, 0, 105, 1, 105, 100, 117, 116, 105, 21, 2, 32, 14, 129, 128, 130, 3, 50, 37, 0, 105, 108, 101, 1, 105, 100, 117, 116, 105, 21, 2, 32, 14, 129, 128, 132, 3, 50, 37, 55, 36, 0, 105, 108, 111, 114, 1, 105, 100, 117, 116, 105, 21, 2, 32, 14, 129, 128, 133, 3, 50, 37, 55, 39, 34, 0, 105, 105, 1, 105, 100, 117, 116, 105, 21, 2, 32, 14, 129, 128, 131, 3, 50, 130, 0, 101, 97, 1, 105, 100, 117, 116, 105, 21, 2, 32, 14, 129, 128, 131, 3, 50, 133, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 1, 21, 2, 105, 32, 3, 125, 0, 7, 6, 111, 0, 1, 17, 67, 21, 2, 114, 105, 105, 105, 32, 3, 6, 39, 0, 105, 2, 32, 3, 6, 39, 57, 0, 117, 2, 32, 24, 3, 6, 129, 0, 4, 3, 39, 0, 2, 17, 65, 17, 65, 17, 65, 0, 117, 2, 32, 3, 39, 40, 0, 105, 8, 3, 39, 57, 0, 117, 3, 129, 0, 97, 3, 136, 0, 97, 105, 3, 136, 57, 0, 7, 6, 112, 0, 4, 3, 48, 0, 112, 0, 104, 3, 81, 0, 1, 21, 2, 105, 32, 3, 137, 0, 7, 6, 113, 0, 3, 49, 0, 117, 3, 49, 58, 0, 7, 6, 114, 0, 1, 17, 67, 2, 17, 65, 3, 14, 16, 0, 105, 1, 17, 67, 2, 32, 3, 14, 16, 37, 0, 4, 1, 17, 65, 2, 17, 65, 3, 16, 0, 2, 196, 131, 32, 0, 196, 131, 197, 163, 105, 1, 21, 2, 32, 14, 129, 128, 132, 3, 16, 13, 121, 122, 0, 114, 3, 16, 34, 0, 101, 1, 117, 21, 2, 32, 14, 129, 128, 130, 3, 16, 36, 0, 4, 3, 34, 0, 114, 0, 4, 101, 8, 2, 21, 14, 128, 132, 130, 3, 34, 36, 0, 101, 8, 2, 103, 117, 108, 0, 105, 108, 101, 1, 117, 21, 2, 32, 14, 129, 128, 132, 3, 34, 37, 55, 36, 0, 105, 108, 111, 114, 1, 117, 21, 2, 32, 14, 129, 128, 133, 3, 34, 37, 55, 39, 34, 0, 105, 1, 117, 21, 2, 32, 24, 14, 129, 128, 130, 3, 34, 122, 0, 105, 105, 1, 117, 21, 2, 32, 14, 129, 128, 131, 3, 34, 130, 0, 196, 131, 109, 1, 21, 2, 32, 14, 129, 128, 129, 3, 63, 0, 1, 17, 65, 2, 105, 32, 3, 143, 0, 7, 6, 115, 0, 101, 114, 196, 131, 1, 21, 2, 32, 14, 129, 128, 130, 3, 16, 13, 0, 101, 114, 196, 131, 109, 1, 21, 2, 32, 14, 129, 128, 131, 3, 16, 13, 63, 0, 101, 114, 196, 131, 197, 163, 105, 1, 21, 2, 32, 14, 129, 128, 132, 3, 16, 13, 121, 122, 0, 101, 109, 1, 21, 2, 32, 14, 129, 128, 129, 3, 63, 0, 4, 3, 87, 0, 1, 45, 2, 32, 0, 8, 2, 45, 97, 0, 115, 0, 8, 2, 32, 3, 87, 36, 0, 112, 114, 101, 122, 101, 99, 101, 1, 10, 2, 32, 14, 129, 128, 136, 3, 87, 48, 14, 16, 36, 86, 4, 36, 74, 36, 0, 110, 105, 1, 21, 2, 32, 3, 87, 50, 6, 37, 0, 104, 3, 89, 0, 101, 197, 159, 105, 1, 21, 2, 32, 14, 129, 128, 130, 3, 89, 122, 0, 7, 6, 116, 0, 4, 3, 47, 0, 116, 0, 116, 2, 32, 0, 4, 115, 3, 121, 0, 122, 0, 1, 21, 2, 105, 32, 3, 138, 0, 7, 6, 117, 0, 1, 17, 67, 131, 196, 21, 2, 24, 32, 3, 6, 40, 0, 105, 2, 32, 3, 6, 119, 0, 105, 101, 1, 21, 2, 32, 3, 8, 58, 37, 36, 0, 3, 40, 0, 105, 1, 10, 26, 2, 32, 24, 3, 40, 6, 37, 0, 114, 105, 108, 101, 1, 99, 105, 21, 2, 32, 14, 128, 128, 133, 3, 40, 34, 37, 55, 36, 0, 114, 105, 1, 99, 105, 21, 2, 32, 14, 128, 128, 131, 3, 40, 34, 122, 0, 105, 1, 114, 2, 110, 3, 40, 37, 0, 4, 108, 1, 10, 2, 32, 14, 129, 128, 130, 3, 40, 55, 0, 108, 1, 99, 105, 21, 2, 32, 14, 129, 128, 130, 0, 108, 1, 116, 115, 101, 100, 0, 108, 101, 1, 99, 105, 21, 2, 32, 14, 129, 128, 131, 3, 40, 55, 36, 0, 4, 108, 117, 105, 1, 10, 2, 32, 14, 129, 128, 132, 3, 40, 55, 119, 0, 108, 117, 105, 1, 99, 105, 21, 2, 32, 14, 129, 128, 132, 0, 105, 97, 2, 32, 3, 40, 57, 6, 35, 0, 4, 109, 1, 21, 2, 32, 14, 128, 192, 130, 3, 40, 63, 0, 109, 1, 99, 2, 32, 0, 109, 117, 114, 105, 1, 21, 2, 32, 14, 129, 128, 133, 3, 40, 63, 40, 34, 37, 0, 109, 117, 114, 105, 108, 101, 1, 21, 2, 32, 14, 129, 128, 135, 3, 40, 63, 40, 34, 37, 55, 36, 0, 109, 117, 114, 105, 108, 111, 114, 1, 21, 2, 32, 14, 129, 128, 136, 3, 40, 63, 40, 34, 37, 55, 39, 34, 0, 109, 117, 108, 1, 21, 2, 32, 14, 129, 128, 132, 3, 40, 63, 40, 55, 0, 109, 117, 108, 117, 105, 1, 21, 2, 32, 14, 129, 128, 134, 3, 40, 63, 40, 55, 119, 0, 115, 1, 21, 2, 32, 14, 129, 128, 130, 3, 40, 87, 0, 115, 117, 114, 105, 1, 21, 2, 32, 14, 129, 128, 133, 3, 40, 87, 40, 34, 37, 0, 115, 117, 114, 105, 108, 101, 1, 21, 2, 32, 14, 129, 128, 135, 3, 40, 87, 40, 34, 37, 55, 36, 0, 115, 117, 114, 105, 108, 111, 114, 1, 21, 2, 32, 14, 129, 128, 136, 3, 40, 87, 40, 34, 37, 55, 39, 34, 0, 115, 117, 108, 1, 21, 2, 32, 14, 129, 128, 132, 3, 40, 87, 40, 55, 0, 115, 117, 108, 117, 105, 1, 21, 2, 32, 14, 129, 128, 134, 3, 40, 87, 40, 55, 119, 0, 2, 17, 65, 3, 58, 0, 105, 2, 101, 3, 58, 37, 0, 105, 8, 3, 119, 0, 7, 6, 118, 0, 3, 82, 0, 1, 21, 2, 105, 32, 3, 144, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 4, 3, 49, 87, 0, 1, 101, 2, 17, 65, 103, 0, 1, 101, 2, 105, 17, 65, 32, 0, 1, 101, 2, 105, 117, 0, 1, 101, 108, 2, 12, 0, 1, 101, 109, 2, 105, 99, 0, 2, 101, 32, 0, 8, 101, 108, 97, 0, 4, 1, 101, 2, 97, 3, 79, 86, 0, 1, 101, 2, 101, 0, 1, 101, 2, 105, 0, 7, 6, 121, 0, 3, 37, 0, 2, 17, 65, 3, 57, 0, 7, 6, 122, 0, 4, 3, 86, 0, 122, 0, 1, 21, 2, 105, 32, 3, 92, 0, 7, 6, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 37, 3, 48, 14, 16, 39, 74, 36, 50, 47, 0, 37, 1, 32, 15, 3, 55, 35, 10, 87, 40, 47, 13, 0, 45, 8, 32, 2, 32, 15, 3, 63, 6, 37, 50, 40, 87, 0, 36, 3, 70, 39, 55, 35, 34, 0, 44, 2, 15, 3, 82, 6, 37, 34, 79, 40, 55, 13, 0, 195, 182, 3, 111, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts49 = FileInMemory_createWithData (26885, reinterpret_cast (&espeakdata_dicts49_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ro_dict", L"ro"); Collection_addItem (me.peek(), espeakdata_dicts49.transfer()); static unsigned char espeakdata_dicts50_data[6158] = { 0, 4, 0, 0, 140, 10, 0, 0, 0, 0, 0, 0, 0, 4, 193, 4, 14, 5, 193, 4, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 7, 65, 12, 82, 119, 0, 14, 6, 65, 12, 82, 0, 72, 0, 0, 0, 0, 0, 0, 0, 11, 4, 95, 100, 112, 116, 9, 6, 37, 9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 1, 35, 34, 36, 89, 6, 119, 47, 49, 35, 0, 27, 0, 8, 197, 64, 240, 156, 77, 208, 74, 7, 65, 36, 37, 0, 72, 8, 11, 1, 36, 70, 6, 39, 55, 55, 35, 34, 0, 0, 13, 1, 37, 48, 34, 124, 108, 6, 119, 50, 47, 0, 27, 0, 14, 1, 38, 35, 63, 48, 36, 34, 87, 6, 35, 50, 70, 0, 0, 0, 0, 0, 12, 1, 42, 86, 82, 36, 86, 70, 6, 35, 0, 27, 0, 10, 1, 43, 48, 55, 6, 129, 87, 0, 27, 0, 0, 0, 0, 10, 1, 47, 87, 55, 6, 119, 89, 0, 27, 0, 6, 195, 25, 36, 198, 73, 0, 0, 0, 0, 0, 0, 0, 6, 195, 25, 36, 221, 73, 0, 0, 0, 0, 0, 0, 9, 198, 64, 240, 148, 21, 68, 192, 74, 11, 1, 61, 34, 35, 82, 50, 6, 39, 0, 27, 0, 0, 0, 11, 1, 64, 87, 39, 69, 6, 35, 49, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 65, 72, 119, 87, 0, 14, 6, 65, 72, 87, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 80, 40, 0, 72, 0, 0, 0, 6, 195, 9, 195, 9, 73, 0, 0, 0, 0, 0, 0, 6, 195, 9, 195, 15, 73, 0, 0, 0, 8, 197, 72, 211, 199, 25, 48, 73, 13, 1, 92, 69, 119, 49, 87, 55, 6, 119, 89, 0, 27, 0, 0, 11, 1, 94, 49, 34, 6, 113, 89, 49, 35, 0, 0, 13, 1, 95, 48, 39, 70, 76, 6, 126, 34, 49, 0, 27, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 1, 126, 47, 6, 37, 55, 70, 35, 0, 0, 0, 4, 193, 128, 72, 0, 0, 0, 7, 196, 9, 65, 70, 52, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 193, 144, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 9, 65, 84, 73, 0, 7, 196, 9, 65, 70, 76, 73, 0, 0, 0, 0, 0, 4, 193, 160, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 246, 29, 72, 0, 0, 0, 0, 0, 0, 6, 195, 52, 241, 35, 74, 0, 0, 0, 0, 0, 17, 5, 95, 100, 112, 116, 50, 10, 110, 115, 93, 6, 35, 47, 133, 99, 0, 0, 0, 0, 0, 6, 195, 52, 241, 20, 74, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 72, 211, 199, 24, 208, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 9, 195, 0, 73, 0, 7, 196, 9, 65, 84, 76, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 64, 240, 148, 20, 99, 64, 74, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 97, 51, 194, 112, 8, 0, 8, 197, 9, 65, 70, 76, 96, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 72, 211, 196, 48, 144, 74, 12, 3, 226, 132, 150, 50, 6, 39, 63, 36, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 9, 196, 221, 73, 0, 0, 0, 9, 198, 64, 240, 148, 20, 102, 93, 74, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 73, 68, 221, 73, 0, 0, 0, 0, 0, 6, 195, 72, 211, 196, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 20, 200, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 51, 88, 47, 34, 38, 6, 37, 47, 108, 124, 109, 0, 0, 10, 3, 95, 48, 67, 87, 47, 6, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 3, 95, 49, 57, 110, 121, 82, 38, 115, 47, 50, 6, 132, 47, 108, 124, 109, 0, 0, 18, 3, 95, 49, 56, 82, 125, 93, 115, 63, 50, 6, 132, 47, 108, 124, 109, 0, 0, 14, 3, 95, 50, 67, 70, 82, 38, 6, 36, 93, 109, 115, 0, 0, 8, 197, 72, 211, 196, 48, 240, 74, 0, 0, 0, 0, 0, 17, 3, 95, 49, 49, 125, 110, 6, 37, 50, 50, 124, 47, 108, 124, 109, 0, 0, 12, 3, 95, 49, 48, 110, 6, 36, 93, 115, 109, 0, 0, 14, 3, 95, 51, 67, 47, 34, 38, 6, 37, 87, 47, 35, 0, 17, 3, 95, 49, 51, 47, 51, 38, 115, 50, 6, 132, 47, 108, 124, 109, 0, 0, 17, 3, 95, 49, 50, 70, 82, 38, 115, 50, 6, 132, 47, 108, 124, 109, 0, 0, 17, 3, 95, 49, 53, 48, 38, 115, 47, 50, 6, 132, 47, 108, 124, 109, 0, 0, 20, 3, 95, 49, 52, 108, 38, 115, 47, 6, 113, 14, 16, 50, 124, 47, 108, 124, 109, 0, 0, 16, 3, 95, 49, 55, 93, 115, 63, 50, 6, 132, 47, 108, 124, 109, 0, 0, 17, 3, 95, 49, 54, 89, 120, 87, 47, 50, 6, 132, 47, 108, 124, 109, 0, 0, 0, 15, 3, 95, 55, 88, 93, 6, 36, 63, 110, 121, 93, 124, 47, 0, 0, 7, 196, 52, 241, 12, 36, 74, 18, 3, 95, 52, 67, 108, 38, 115, 47, 6, 113, 34, 38, 121, 87, 47, 35, 0, 0, 0, 9, 198, 64, 240, 148, 20, 100, 192, 74, 0, 0, 0, 0, 0, 0, 9, 198, 64, 240, 148, 20, 100, 198, 74, 15, 3, 95, 53, 67, 48, 38, 4, 115, 109, 87, 6, 39, 47, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 102, 39, 70, 50, 6, 35, 0, 0, 0, 0, 15, 3, 95, 54, 67, 89, 4, 120, 93, 109, 87, 6, 39, 47, 0, 0, 0, 0, 0, 0, 11, 3, 95, 50, 102, 70, 82, 38, 6, 36, 0, 0, 0, 14, 3, 95, 50, 88, 70, 82, 6, 132, 47, 108, 124, 109, 0, 0, 7, 196, 52, 241, 12, 60, 74, 16, 5, 95, 48, 77, 65, 49, 47, 6, 113, 93, 115, 108, 38, 37, 0, 14, 3, 95, 55, 67, 93, 4, 115, 63, 87, 6, 39, 47, 0, 0, 0, 19, 5, 95, 48, 77, 65, 51, 111, 4, 115, 55, 115, 38, 6, 35, 34, 70, 35, 0, 0, 18, 5, 95, 48, 77, 65, 50, 111, 4, 115, 55, 115, 38, 6, 39, 50, 35, 0, 0, 0, 0, 0, 0, 15, 3, 95, 56, 67, 82, 125, 93, 115, 63, 87, 6, 39, 47, 0, 0, 0, 0, 0, 0, 8, 197, 52, 241, 198, 76, 96, 73, 0, 0, 13, 3, 95, 52, 88, 87, 6, 39, 14, 16, 125, 49, 0, 0, 15, 3, 95, 57, 67, 70, 36, 82, 38, 124, 108, 6, 39, 47, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 53, 88, 48, 38, 124, 110, 110, 115, 93, 6, 118, 47, 0, 0, 7, 196, 64, 240, 156, 48, 73, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 54, 88, 89, 121, 92, 110, 110, 115, 93, 6, 118, 47, 0, 0, 0, 8, 197, 72, 211, 196, 81, 48, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 56, 88, 82, 6, 39, 93, 121, 63, 110, 121, 93, 124, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 57, 88, 110, 121, 82, 38, 115, 50, 6, 39, 87, 47, 125, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 52, 241, 20, 76, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 61, 48, 72, 0, 0, 0, 0, 18, 4, 95, 48, 77, 50, 111, 4, 115, 55, 115, 38, 6, 39, 50, 39, 81, 0, 0, 19, 4, 95, 48, 77, 51, 111, 4, 115, 55, 115, 38, 6, 35, 34, 70, 39, 81, 0, 0, 0, 14, 4, 95, 48, 77, 49, 47, 6, 113, 93, 124, 108, 38, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 64, 240, 156, 140, 75, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 72, 211, 199, 25, 151, 64, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 9, 65, 70, 101, 208, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 194, 171, 6, 39, 47, 49, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 72, 211, 216, 116, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 88, 244, 224, 66, 8, 0, 7, 196, 52, 241, 198, 52, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 241, 0, 73, 0, 0, 0, 0, 0, 0, 0, 0, 11, 67, 97, 51, 192, 89, 47, 39, 0, 72, 8, 0, 0, 0, 11, 3, 95, 194, 187, 86, 6, 35, 49, 34, 0, 0, 0, 0, 8, 197, 52, 241, 198, 101, 208, 73, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 52, 241, 198, 76, 73, 0, 0, 6, 194, 56, 240, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 36, 35, 192, 72, 8, 7, 195, 36, 35, 192, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 95, 3, 82, 119, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 95, 18, 119, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 2, 95, 34, 49, 124, 82, 6, 113, 76, 49, 35, 0, 0, 8, 197, 64, 240, 156, 48, 144, 74, 12, 2, 95, 33, 82, 6, 39, 87, 49, 55, 38, 0, 0, 0, 14, 2, 95, 39, 35, 48, 6, 39, 87, 47, 34, 124, 81, 0, 0, 0, 0, 0, 0, 0, 14, 2, 95, 41, 86, 6, 35, 49, 34, 49, 34, 40, 79, 0, 0, 14, 2, 95, 40, 6, 39, 47, 49, 34, 49, 34, 40, 79, 0, 0, 0, 11, 2, 95, 46, 47, 6, 39, 76, 49, 35, 0, 0, 11, 2, 95, 45, 70, 36, 81, 6, 37, 87, 0, 0, 13, 2, 95, 44, 86, 124, 48, 37, 47, 6, 35, 118, 0, 0, 10, 2, 95, 51, 47, 51, 38, 6, 37, 0, 0, 9, 2, 95, 50, 70, 82, 6, 132, 0, 0, 11, 2, 95, 49, 39, 57, 110, 6, 37, 50, 0, 0, 10, 2, 95, 48, 50, 6, 39, 57, 61, 0, 0, 10, 2, 95, 55, 93, 6, 36, 57, 63, 0, 0, 10, 2, 95, 54, 89, 6, 119, 93, 109, 0, 0, 10, 2, 95, 53, 48, 38, 6, 118, 109, 0, 0, 13, 2, 95, 52, 76, 115, 47, 6, 113, 51, 38, 115, 0, 0, 13, 2, 95, 59, 47, 6, 39, 76, 49, 86, 35, 48, 0, 0, 15, 2, 95, 58, 70, 82, 124, 36, 47, 6, 39, 76, 37, 36, 0, 0, 11, 2, 95, 57, 110, 6, 36, 82, 117, 109, 0, 0, 11, 2, 95, 56, 82, 6, 39, 93, 121, 63, 0, 0, 12, 2, 95, 63, 82, 39, 48, 34, 6, 39, 87, 0, 0, 7, 196, 72, 211, 196, 80, 73, 12, 2, 95, 62, 69, 6, 39, 55, 38, 89, 119, 0, 0, 0, 12, 2, 95, 60, 63, 6, 36, 50, 38, 89, 119, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 72, 211, 199, 25, 49, 128, 73, 0, 17, 2, 95, 91, 6, 39, 47, 49, 34, 49, 82, 35, 70, 34, 35, 47, 0, 0, 0, 0, 0, 0, 0, 17, 2, 95, 93, 86, 6, 35, 49, 34, 49, 82, 35, 70, 34, 35, 47, 0, 0, 0, 0, 0, 0, 12, 2, 95, 96, 35, 49, 108, 6, 119, 50, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 2, 95, 123, 6, 39, 47, 49, 34, 81, 37, 79, 40, 34, 0, 0, 0, 0, 0, 0, 0, 15, 2, 95, 125, 86, 6, 35, 49, 34, 81, 37, 79, 40, 34, 0, 0, 10, 2, 95, 124, 82, 6, 36, 34, 47, 0, 0, 0, 0, 8, 197, 64, 240, 156, 48, 240, 74, 0, 0, 0, 0, 0, 0, 0, 7, 196, 72, 211, 196, 140, 74, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 25, 34, 64, 74, 0, 0, 0, 18, 5, 95, 49, 77, 65, 51, 111, 4, 115, 55, 115, 38, 6, 35, 34, 47, 0, 0, 17, 5, 95, 49, 77, 65, 50, 111, 4, 115, 55, 115, 38, 6, 39, 50, 0, 0, 16, 5, 95, 49, 77, 65, 49, 47, 6, 113, 93, 115, 108, 38, 124, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 25, 35, 93, 73, 0, 6, 195, 25, 35, 92, 73, 0, 13, 68, 68, 17, 73, 60, 34, 6, 35, 110, 115, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 64, 240, 148, 21, 64, 74, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 1, 17, 0, 4, 2, 32, 3, 35, 0, 8, 0, 8, 2, 32, 0, 4, 3, 124, 0, 1, 17, 66, 2, 32, 0, 7, 6, 1, 18, 0, 4, 2, 32, 3, 48, 0, 2, 208, 186, 17, 71, 0, 2, 208, 186, 209, 140, 0, 2, 209, 129, 17, 71, 0, 2, 209, 129, 209, 140, 0, 2, 209, 130, 17, 71, 0, 2, 209, 130, 209, 140, 0, 2, 209, 133, 17, 71, 0, 2, 209, 133, 208, 186, 17, 71, 0, 2, 209, 133, 208, 186, 209, 140, 0, 2, 209, 133, 209, 140, 0, 2, 209, 135, 0, 2, 209, 137, 0, 4, 2, 208, 191, 17, 71, 3, 48, 38, 0, 2, 208, 191, 209, 140, 0, 2, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 209, 140, 0, 2, 209, 132, 209, 140, 0, 2, 209, 140, 32, 0, 3, 69, 0, 4, 2, 17, 71, 3, 69, 38, 0, 2, 208, 177, 17, 71, 0, 2, 208, 177, 208, 178, 17, 71, 0, 2, 208, 177, 208, 178, 209, 140, 0, 2, 208, 177, 208, 188, 17, 71, 0, 2, 208, 177, 208, 188, 209, 140, 0, 2, 208, 177, 209, 140, 0, 2, 208, 178, 17, 71, 0, 2, 208, 178, 209, 140, 0, 2, 208, 188, 17, 71, 0, 2, 208, 188, 209, 140, 0, 2, 209, 140, 0, 8, 2, 32, 3, 69, 119, 0, 7, 6, 1, 19, 0, 4, 2, 32, 3, 81, 0, 2, 208, 186, 17, 71, 0, 2, 208, 186, 209, 140, 0, 2, 209, 129, 17, 71, 0, 2, 209, 129, 209, 140, 0, 2, 209, 130, 17, 71, 0, 2, 209, 130, 209, 140, 0, 2, 209, 133, 17, 71, 0, 2, 209, 133, 208, 186, 17, 71, 0, 2, 209, 133, 208, 186, 209, 140, 0, 2, 209, 133, 209, 140, 0, 2, 209, 135, 0, 2, 209, 137, 0, 4, 2, 208, 191, 39, 3, 81, 38, 0, 2, 209, 132, 39, 0, 2, 209, 140, 32, 0, 3, 82, 0, 4, 2, 17, 71, 3, 82, 38, 0, 2, 208, 177, 17, 71, 0, 2, 208, 177, 209, 140, 0, 2, 208, 178, 17, 71, 0, 2, 208, 178, 208, 177, 17, 71, 0, 2, 208, 178, 208, 177, 209, 140, 0, 2, 208, 178, 208, 188, 17, 71, 0, 2, 208, 178, 208, 188, 209, 140, 0, 2, 208, 178, 209, 140, 0, 2, 208, 188, 17, 71, 0, 2, 208, 188, 209, 140, 0, 2, 209, 140, 0, 8, 2, 32, 3, 82, 119, 0, 7, 6, 1, 20, 0, 4, 2, 32, 3, 49, 0, 2, 208, 191, 17, 71, 0, 2, 208, 191, 209, 140, 0, 2, 209, 129, 17, 71, 0, 2, 209, 129, 209, 140, 0, 2, 209, 130, 17, 71, 0, 2, 209, 130, 209, 140, 0, 2, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 209, 140, 0, 2, 209, 132, 209, 140, 0, 2, 209, 133, 17, 71, 0, 2, 209, 133, 208, 186, 17, 71, 0, 2, 209, 133, 208, 186, 209, 140, 0, 2, 209, 133, 209, 140, 0, 4, 3, 79, 0, 8, 190, 208, 189, 208, 188, 208, 2, 208, 190, 32, 0, 4, 2, 17, 71, 3, 79, 38, 0, 2, 209, 140, 0, 8, 2, 32, 3, 79, 119, 0, 4, 1, 181, 208, 2, 208, 190, 209, 129, 209, 143, 32, 3, 82, 0, 1, 181, 208, 17, 67, 2, 208, 190, 32, 0, 1, 190, 208, 17, 67, 2, 208, 190, 32, 0, 8, 181, 208, 2, 208, 190, 32, 0, 8, 181, 208, 129, 209, 2, 208, 190, 0, 8, 181, 208, 129, 209, 178, 208, 2, 208, 190, 32, 0, 8, 181, 208, 189, 208, 2, 208, 190, 32, 0, 8, 181, 208, 190, 208, 178, 208, 130, 209, 2, 208, 190, 32, 0, 8, 181, 208, 190, 208, 188, 208, 2, 208, 190, 32, 0, 2, 208, 186, 3, 99, 0, 7, 6, 1, 21, 0, 4, 2, 32, 3, 47, 0, 2, 208, 186, 17, 71, 0, 2, 208, 186, 209, 140, 0, 2, 208, 191, 17, 71, 0, 2, 208, 191, 209, 140, 0, 2, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 209, 140, 0, 2, 209, 132, 209, 140, 0, 2, 209, 133, 17, 71, 0, 2, 209, 133, 208, 186, 17, 71, 0, 2, 209, 133, 208, 186, 209, 140, 0, 2, 209, 133, 209, 140, 0, 3, 70, 0, 8, 2, 32, 3, 70, 119, 0, 4, 2, 209, 129, 17, 71, 3, 109, 0, 2, 209, 129, 209, 140, 0, 2, 209, 130, 17, 71, 0, 2, 209, 130, 209, 140, 0, 2, 209, 140, 32, 0, 4, 2, 17, 66, 3, 110, 0, 2, 17, 71, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 2, 208, 189, 209, 140, 0, 2, 209, 140, 0, 7, 6, 1, 22, 0, 3, 36, 0, 4, 1, 17, 65, 3, 57, 36, 0, 1, 138, 209, 0, 1, 140, 209, 0, 8, 2, 32, 0, 4, 1, 17, 65, 2, 32, 3, 57, 117, 0, 1, 138, 209, 2, 32, 0, 1, 140, 209, 2, 32, 0, 8, 0, 4, 1, 130, 209, 2, 209, 129, 209, 130, 3, 123, 0, 1, 130, 209, 128, 209, 176, 208, 177, 208, 2, 209, 128, 0, 1, 130, 209, 142, 209, 140, 209, 191, 208, 188, 208, 190, 208, 186, 208, 2, 209, 128, 0, 1, 130, 209, 186, 208, 176, 208, 177, 208, 2, 209, 128, 0, 1, 130, 209, 189, 208, 184, 208, 2, 209, 128, 0, 7, 6, 1, 23, 0, 3, 88, 0, 8, 2, 32, 3, 88, 119, 0, 4, 2, 32, 3, 89, 0, 2, 208, 186, 17, 71, 0, 2, 208, 186, 209, 140, 0, 2, 208, 191, 17, 71, 0, 2, 208, 191, 209, 140, 0, 2, 209, 129, 17, 71, 0, 2, 209, 129, 209, 140, 0, 2, 209, 130, 17, 71, 0, 2, 209, 130, 209, 140, 0, 2, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 209, 140, 0, 2, 209, 132, 209, 140, 0, 2, 209, 133, 17, 71, 0, 2, 209, 133, 208, 186, 17, 71, 0, 2, 209, 133, 208, 186, 209, 140, 0, 2, 209, 133, 209, 140, 0, 209, 135, 3, 95, 0, 7, 6, 1, 24, 0, 3, 86, 0, 8, 2, 32, 3, 86, 119, 0, 4, 2, 32, 3, 87, 0, 2, 208, 186, 17, 71, 0, 2, 208, 186, 209, 140, 0, 2, 208, 191, 17, 71, 0, 2, 208, 191, 209, 140, 0, 2, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 209, 140, 0, 2, 209, 132, 209, 140, 0, 2, 209, 133, 17, 71, 0, 2, 209, 133, 208, 186, 17, 71, 0, 2, 209, 133, 208, 186, 209, 140, 0, 2, 209, 133, 209, 140, 0, 2, 209, 137, 0, 2, 208, 182, 3, 88, 0, 2, 209, 136, 3, 89, 0, 4, 2, 17, 71, 3, 92, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 208, 180, 17, 71, 0, 2, 208, 183, 208, 180, 209, 140, 0, 2, 208, 183, 208, 189, 17, 66, 0, 2, 208, 183, 208, 189, 17, 71, 0, 2, 208, 183, 208, 189, 209, 140, 0, 2, 208, 183, 209, 140, 0, 2, 208, 189, 17, 66, 0, 2, 208, 189, 17, 71, 0, 2, 208, 189, 209, 140, 0, 2, 209, 140, 0, 4, 2, 208, 183, 17, 71, 32, 3, 93, 0, 2, 208, 183, 208, 180, 17, 71, 32, 0, 2, 208, 183, 208, 180, 209, 140, 32, 0, 2, 208, 183, 208, 189, 17, 66, 32, 0, 2, 208, 183, 208, 189, 17, 71, 32, 0, 2, 208, 183, 208, 189, 209, 140, 32, 0, 2, 208, 183, 209, 140, 32, 0, 2, 209, 129, 17, 71, 0, 2, 209, 129, 209, 140, 0, 2, 209, 130, 17, 71, 0, 2, 209, 130, 209, 140, 0, 4, 209, 135, 3, 95, 0, 209, 137, 0, 7, 6, 1, 25, 0, 4, 3, 37, 0, 8, 2, 32, 0, 4, 1, 17, 68, 3, 113, 0, 1, 136, 209, 0, 1, 182, 208, 0, 4, 2, 32, 3, 115, 0, 8, 0, 7, 6, 1, 26, 0, 8, 2, 32, 3, 4, 37, 6, 49, 14, 16, 6, 132, 47, 49, 125, 57, 115, 0, 3, 57, 0, 7, 6, 1, 27, 0, 3, 49, 0, 4, 2, 17, 71, 3, 49, 38, 0, 2, 209, 140, 0, 8, 2, 32, 3, 49, 132, 0, 4, 2, 208, 177, 3, 79, 0, 2, 208, 177, 17, 71, 0, 2, 208, 177, 209, 140, 0, 2, 208, 179, 0, 2, 208, 179, 17, 71, 0, 2, 208, 179, 209, 140, 0, 2, 208, 180, 0, 2, 208, 180, 17, 66, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 182, 0, 2, 208, 183, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 7, 6, 1, 28, 0, 3, 55, 0, 2, 17, 71, 3, 61, 0, 8, 2, 32, 3, 119, 61, 0, 7, 6, 1, 29, 0, 3, 63, 0, 4, 2, 17, 71, 3, 111, 0, 2, 208, 177, 17, 71, 0, 2, 208, 177, 209, 140, 0, 2, 208, 178, 17, 71, 0, 2, 208, 178, 209, 140, 0, 2, 208, 191, 17, 71, 0, 2, 208, 191, 209, 140, 0, 2, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 209, 140, 0, 2, 209, 132, 209, 140, 0, 2, 209, 140, 0, 8, 2, 32, 3, 119, 63, 0, 7, 6, 1, 30, 0, 3, 50, 0, 208, 181, 1, 183, 208, 184, 208, 177, 208, 2, 209, 129, 3, 50, 123, 0, 2, 32, 3, 106, 0, 8, 2, 32, 3, 119, 106, 0, 7, 6, 1, 31, 0, 3, 39, 0, 7, 6, 1, 32, 0, 3, 48, 0, 4, 2, 17, 71, 3, 48, 38, 0, 2, 208, 188, 17, 71, 0, 2, 208, 188, 209, 140, 0, 2, 208, 191, 17, 71, 0, 2, 208, 191, 208, 188, 17, 71, 0, 2, 208, 191, 208, 188, 209, 140, 0, 2, 208, 191, 209, 132, 17, 71, 0, 2, 208, 191, 209, 132, 209, 140, 0, 2, 208, 191, 209, 140, 0, 2, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 17, 71, 0, 2, 209, 132, 209, 132, 209, 140, 0, 2, 209, 132, 209, 140, 0, 2, 209, 140, 0, 8, 2, 32, 3, 48, 119, 0, 4, 2, 208, 177, 3, 69, 0, 2, 208, 179, 0, 2, 208, 179, 17, 71, 0, 2, 208, 179, 209, 140, 0, 2, 208, 180, 0, 2, 208, 180, 17, 66, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 182, 0, 2, 208, 183, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 2, 208, 177, 39, 3, 69, 38, 0, 7, 6, 1, 33, 0, 3, 34, 0, 4, 2, 17, 66, 3, 34, 38, 0, 2, 17, 71, 0, 2, 209, 140, 3, 34, 112, 0, 8, 2, 32, 3, 119, 34, 0, 7, 6, 1, 34, 0, 4, 2, 208, 177, 3, 86, 0, 2, 208, 179, 0, 2, 208, 180, 0, 2, 208, 182, 0, 2, 208, 183, 0, 4, 3, 87, 0, 2, 209, 130, 209, 140, 0, 2, 208, 182, 3, 88, 0, 2, 209, 136, 3, 89, 0, 4, 2, 208, 180, 17, 66, 3, 92, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 4, 2, 17, 71, 3, 93, 0, 2, 208, 189, 17, 66, 0, 2, 208, 189, 17, 71, 0, 2, 208, 189, 209, 140, 0, 2, 209, 129, 17, 71, 0, 2, 209, 129, 209, 140, 0, 2, 209, 130, 17, 71, 0, 2, 209, 140, 0, 2, 209, 137, 3, 93, 93, 0, 209, 135, 3, 95, 0, 8, 2, 32, 3, 119, 87, 0, 7, 6, 1, 35, 0, 3, 47, 0, 8, 2, 32, 3, 47, 119, 0, 4, 2, 208, 177, 3, 70, 0, 2, 208, 179, 0, 2, 208, 180, 0, 2, 208, 182, 0, 2, 208, 182, 0, 2, 208, 183, 0, 209, 129, 1, 17, 71, 3, 108, 0, 4, 2, 17, 71, 3, 109, 0, 2, 208, 189, 17, 66, 0, 2, 208, 189, 17, 71, 0, 2, 208, 189, 209, 140, 0, 2, 209, 129, 17, 71, 0, 2, 209, 129, 209, 140, 0, 2, 209, 130, 17, 71, 0, 2, 209, 130, 209, 140, 0, 2, 209, 140, 0, 4, 2, 208, 180, 17, 66, 3, 110, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 7, 6, 1, 36, 0, 4, 3, 40, 0, 8, 2, 32, 0, 1, 17, 66, 3, 127, 0, 7, 6, 1, 37, 0, 3, 81, 0, 4, 2, 17, 71, 3, 81, 38, 0, 2, 208, 188, 17, 71, 0, 2, 208, 188, 209, 140, 0, 2, 208, 191, 17, 71, 0, 2, 208, 191, 208, 188, 17, 71, 0, 2, 208, 191, 208, 188, 209, 140, 0, 2, 208, 191, 209, 132, 17, 71, 0, 2, 208, 191, 209, 132, 209, 140, 0, 2, 208, 191, 209, 140, 0, 2, 209, 132, 17, 71, 0, 2, 209, 132, 209, 140, 0, 2, 209, 140, 0, 4, 2, 208, 177, 3, 82, 0, 2, 208, 179, 0, 2, 208, 179, 17, 71, 0, 2, 208, 179, 209, 140, 0, 2, 208, 180, 0, 2, 208, 180, 17, 66, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 182, 0, 2, 208, 183, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 2, 208, 177, 39, 3, 82, 38, 0, 8, 2, 32, 3, 119, 81, 0, 7, 6, 1, 38, 0, 4, 3, 99, 0, 2, 17, 71, 0, 2, 32, 208, 177, 209, 139, 0, 2, 208, 177, 0, 2, 208, 177, 17, 71, 0, 2, 208, 177, 208, 178, 17, 71, 0, 2, 208, 177, 208, 178, 209, 140, 0, 2, 208, 177, 208, 188, 17, 71, 0, 2, 208, 177, 208, 188, 209, 140, 0, 2, 208, 177, 209, 140, 0, 2, 208, 179, 0, 2, 208, 179, 17, 71, 0, 2, 208, 179, 209, 140, 0, 2, 208, 180, 0, 2, 208, 180, 17, 66, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 182, 0, 2, 208, 183, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 2, 208, 186, 17, 71, 0, 2, 208, 186, 209, 140, 0, 2, 209, 140, 0, 8, 2, 32, 3, 99, 132, 0, 7, 6, 1, 39, 0, 4, 2, 208, 177, 3, 70, 86, 0, 2, 208, 177, 17, 71, 0, 2, 208, 177, 208, 178, 17, 71, 0, 2, 208, 177, 208, 178, 209, 140, 0, 2, 208, 177, 208, 188, 17, 71, 0, 2, 208, 177, 208, 188, 209, 140, 0, 2, 208, 177, 209, 140, 0, 2, 208, 179, 0, 2, 208, 179, 17, 71, 0, 2, 208, 179, 209, 140, 0, 2, 208, 180, 0, 2, 208, 180, 17, 66, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 182, 0, 2, 208, 183, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 3, 108, 0, 8, 2, 32, 3, 108, 119, 0, 7, 6, 1, 40, 0, 1, 131, 209, 187, 208, 2, 209, 136, 208, 181, 3, 47, 0, 4, 2, 208, 177, 3, 75, 0, 2, 208, 177, 17, 71, 0, 2, 208, 177, 208, 178, 17, 71, 0, 2, 208, 177, 208, 178, 209, 140, 0, 2, 208, 177, 208, 188, 17, 71, 0, 2, 208, 177, 208, 188, 209, 140, 0, 2, 208, 177, 209, 140, 0, 2, 208, 179, 0, 2, 208, 179, 17, 71, 0, 2, 208, 179, 209, 140, 0, 2, 208, 180, 0, 2, 208, 180, 17, 66, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 182, 0, 2, 208, 183, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 3, 76, 0, 8, 2, 32, 3, 76, 36, 0, 4, 1, 131, 209, 186, 208, 129, 209, 2, 208, 189, 3, 89, 0, 1, 143, 209, 130, 209, 129, 209, 131, 209, 191, 208, 2, 208, 189, 0, 1, 181, 208, 128, 209, 190, 208, 178, 208, 186, 208, 129, 209, 2, 208, 189, 0, 1, 181, 208, 189, 208, 190, 208, 186, 208, 2, 208, 189, 208, 190, 0, 1, 184, 208, 143, 209, 2, 208, 189, 208, 184, 0, 1, 184, 208, 178, 208, 181, 208, 180, 208, 2, 208, 189, 0, 2, 208, 189, 208, 176, 32, 0, 2, 208, 189, 208, 181, 32, 0, 2, 208, 189, 208, 190, 208, 185, 32, 0, 2, 208, 189, 209, 131, 32, 0, 2, 208, 189, 209, 139, 32, 0, 8, 2, 209, 130, 208, 190, 0, 7, 6, 1, 41, 0, 4, 2, 208, 177, 3, 88, 0, 2, 208, 177, 17, 71, 0, 2, 208, 177, 208, 178, 17, 71, 0, 2, 208, 177, 208, 178, 209, 140, 0, 2, 208, 177, 208, 188, 17, 71, 0, 2, 208, 177, 208, 188, 209, 140, 0, 2, 208, 177, 209, 140, 0, 2, 208, 179, 0, 2, 208, 179, 17, 71, 0, 2, 208, 179, 209, 140, 0, 2, 208, 180, 0, 2, 208, 180, 17, 66, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 182, 0, 2, 208, 183, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 3, 89, 0, 8, 2, 32, 3, 89, 132, 0, 7, 6, 1, 42, 0, 4, 2, 208, 177, 3, 94, 0, 2, 208, 177, 17, 71, 0, 2, 208, 177, 208, 178, 17, 71, 0, 2, 208, 177, 208, 178, 209, 140, 0, 2, 208, 177, 208, 188, 17, 71, 0, 2, 208, 177, 208, 188, 209, 140, 0, 2, 208, 177, 209, 140, 0, 2, 208, 179, 0, 2, 208, 179, 17, 71, 0, 2, 208, 179, 209, 140, 0, 2, 208, 180, 0, 2, 208, 180, 17, 66, 0, 2, 208, 180, 17, 71, 0, 2, 208, 180, 209, 140, 0, 2, 208, 182, 0, 2, 208, 183, 0, 2, 208, 183, 17, 71, 0, 2, 208, 183, 209, 140, 0, 3, 95, 0, 8, 2, 32, 3, 95, 118, 0, 7, 6, 1, 43, 0, 3, 0, 8, 2, 32, 3, 47, 82, 38, 6, 126, 14, 16, 70, 113, 57, 86, 50, 6, 132, 49, 0, 2, 17, 71, 3, 57, 0, 7, 6, 1, 44, 0, 4, 3, 113, 0, 8, 2, 32, 0, 7, 6, 1, 45, 0, 3, 0, 2, 17, 71, 3, 57, 0, 8, 2, 32, 3, 111, 6, 118, 49, 38, 114, 57, 86, 50, 6, 132, 49, 0, 7, 6, 1, 46, 0, 8, 2, 32, 3, 36, 0, 4, 2, 32, 3, 120, 0, 8, 0, 3, 121, 0, 7, 6, 1, 47, 0, 1, 131, 209, 180, 208, 181, 208, 187, 208, 129, 209, 2, 209, 137, 3, 0, 3, 128, 0, 4, 1, 17, 65, 3, 129, 0, 1, 138, 209, 0, 1, 140, 209, 0, 8, 0, 8, 2, 32, 0, 7, 6, 1, 48, 0, 4, 1, 17, 65, 3, 118, 0, 1, 17, 65, 2, 32, 0, 1, 138, 209, 0, 1, 138, 209, 2, 32, 0, 1, 140, 209, 0, 1, 140, 209, 2, 32, 0, 8, 0, 8, 2, 32, 0, 4, 3, 124, 0, 2, 32, 0, 7, 6, 1, 50, 0, 8, 3, 6, 57, 126, 0, 4, 1, 136, 209, 3, 6, 125, 0, 1, 182, 208, 0, 3, 6, 126, 0, 8, 2, 32, 3, 57, 126, 0, 7, 6, 0, 36, 3, 70, 39, 55, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts50 = FileInMemory_createWithData (6157, reinterpret_cast (&espeakdata_dicts50_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ru_dict", L"ru"); Collection_addItem (me.peek(), espeakdata_dicts50.transfer()); static unsigned char espeakdata_dicts51_data[2251] = { 0, 4, 0, 0, 171, 7, 0, 0, 0, 0, 0, 0, 0, 6, 65, 4, 35, 12, 0, 0, 0, 0, 0, 7, 65, 8, 69, 35, 12, 0, 0, 0, 0, 0, 7, 65, 12, 78, 35, 12, 0, 0, 0, 0, 0, 7, 65, 16, 70, 35, 12, 0, 0, 0, 0, 0, 6, 65, 20, 36, 12, 0, 0, 0, 0, 0, 7, 65, 24, 81, 35, 12, 0, 0, 0, 0, 0, 7, 65, 28, 79, 35, 12, 0, 0, 0, 0, 0, 7, 65, 32, 105, 35, 12, 0, 0, 0, 0, 0, 6, 65, 36, 37, 12, 0, 0, 0, 0, 0, 7, 65, 40, 73, 35, 12, 0, 0, 0, 0, 0, 7, 65, 44, 49, 35, 12, 0, 0, 0, 0, 0, 7, 65, 48, 55, 35, 12, 0, 0, 0, 0, 0, 7, 65, 52, 63, 35, 12, 0, 0, 0, 0, 0, 10, 5, 95, 48, 1, 14, 4, 50, 35, 0, 7, 65, 56, 50, 35, 12, 0, 0, 0, 0, 0, 6, 65, 60, 39, 12, 0, 0, 0, 0, 0, 7, 65, 64, 48, 35, 12, 0, 0, 0, 0, 0, 8, 65, 68, 49, 58, 35, 12, 0, 0, 0, 0, 0, 7, 65, 72, 16, 35, 12, 0, 0, 0, 0, 0, 7, 65, 76, 87, 35, 12, 0, 0, 0, 0, 0, 7, 65, 80, 47, 35, 12, 0, 0, 0, 0, 0, 6, 65, 84, 40, 12, 0, 0, 0, 0, 0, 7, 65, 88, 82, 35, 12, 0, 0, 0, 0, 0, 7, 65, 92, 58, 35, 12, 0, 0, 0, 0, 0, 16, 4, 95, 49, 77, 49, 37, 77, 37, 105, 6, 40, 63, 69, 37, 0, 7, 65, 96, 36, 49, 87, 0, 0, 20, 4, 95, 49, 77, 50, 63, 37, 55, 37, 57, 6, 39, 50, 6, 37, 63, 58, 36, 0, 0, 0, 0, 7, 65, 100, 57, 35, 12, 0, 0, 0, 0, 0, 7, 65, 104, 86, 35, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 4, 95, 50, 77, 49, 37, 80, 37, 105, 6, 40, 63, 69, 37, 69, 37, 80, 6, 37, 16, 37, 0, 0, 22, 4, 95, 50, 77, 50, 63, 37, 55, 37, 57, 6, 39, 50, 36, 80, 57, 6, 37, 16, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 4, 16, 20, 10, 50, 37, 80, 6, 37, 74, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 4, 95, 51, 77, 49, 37, 80, 37, 105, 6, 40, 63, 69, 37, 69, 37, 47, 6, 35, 47, 40, 0, 0, 21, 4, 95, 51, 77, 50, 63, 37, 55, 37, 57, 6, 39, 50, 36, 89, 6, 35, 47, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23, 4, 95, 53, 77, 49, 37, 80, 37, 105, 6, 40, 63, 69, 37, 69, 37, 47, 6, 35, 50, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 51, 88, 63, 37, 16, 4, 39, 66, 79, 58, 37, 47, 6, 35, 47, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 49, 67, 37, 73, 6, 35, 50, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 50, 67, 63, 35, 79, 4, 35, 50, 35, 80, 6, 37, 16, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 51, 67, 63, 35, 79, 4, 35, 50, 35, 47, 6, 35, 47, 40, 0, 0, 0, 0, 26, 4, 95, 54, 77, 49, 37, 80, 37, 105, 6, 40, 63, 69, 37, 69, 37, 47, 35, 50, 70, 6, 35, 47, 40, 0, 0, 0, 0, 0, 22, 3, 95, 55, 88, 63, 37, 16, 4, 39, 66, 79, 58, 37, 16, 6, 37, 50, 70, 58, 37, 0, 0, 16, 3, 95, 52, 67, 63, 35, 79, 4, 35, 50, 6, 35, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 53, 67, 63, 35, 79, 4, 35, 50, 35, 47, 6, 35, 50, 40, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 49, 88, 37, 74, 6, 40, 63, 37, 0, 0, 21, 3, 95, 54, 67, 63, 35, 79, 4, 35, 50, 35, 47, 35, 50, 70, 6, 35, 47, 40, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 50, 88, 63, 35, 49, 40, 63, 57, 35, 80, 6, 37, 16, 37, 0, 0, 20, 3, 95, 55, 67, 63, 35, 79, 4, 35, 50, 35, 16, 6, 37, 50, 70, 58, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 56, 67, 63, 35, 79, 4, 35, 50, 37, 50, 6, 35, 50, 37, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 52, 88, 63, 37, 16, 4, 39, 66, 79, 58, 6, 37, 50, 36, 0, 0, 20, 3, 95, 57, 67, 63, 35, 79, 4, 35, 50, 35, 49, 57, 6, 36, 50, 70, 35, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 53, 88, 63, 37, 16, 4, 39, 66, 79, 58, 37, 47, 6, 35, 50, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 22, 3, 95, 54, 88, 63, 37, 16, 4, 39, 66, 79, 37, 47, 35, 50, 70, 6, 35, 47, 40, 0, 0, 0, 0, 0, 25, 4, 95, 55, 77, 49, 37, 80, 37, 105, 6, 40, 63, 69, 37, 69, 37, 16, 6, 37, 50, 70, 58, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 56, 88, 63, 37, 16, 4, 39, 66, 79, 58, 37, 50, 6, 35, 50, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 57, 88, 63, 37, 16, 4, 39, 66, 79, 58, 36, 57, 6, 36, 50, 70, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 48, 77, 50, 63, 37, 55, 37, 57, 6, 39, 50, 37, 0, 0, 0, 0, 16, 4, 95, 48, 77, 49, 37, 80, 37, 105, 6, 40, 63, 69, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 52, 77, 50, 63, 4, 37, 55, 37, 57, 6, 39, 50, 6, 36, 65, 36, 0, 0, 21, 4, 95, 52, 77, 49, 37, 80, 37, 105, 6, 40, 63, 69, 37, 69, 6, 37, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 2, 95, 51, 79, 35, 47, 6, 35, 47, 40, 0, 0, 12, 2, 95, 50, 49, 35, 80, 6, 37, 16, 37, 0, 0, 11, 2, 95, 49, 51, 6, 37, 63, 58, 36, 0, 0, 10, 2, 95, 48, 86, 6, 36, 16, 40, 0, 0, 14, 2, 95, 55, 49, 35, 16, 6, 37, 50, 70, 58, 37, 0, 0, 15, 2, 95, 54, 79, 35, 47, 35, 50, 70, 6, 35, 47, 40, 0, 0, 12, 2, 95, 53, 79, 35, 47, 6, 35, 50, 40, 0, 0, 10, 2, 95, 52, 49, 6, 35, 50, 36, 0, 0, 0, 0, 13, 2, 95, 57, 37, 49, 57, 6, 36, 50, 70, 35, 0, 0, 13, 2, 95, 56, 40, 63, 40, 50, 6, 35, 50, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 97, 0, 3, 35, 0, 7, 6, 98, 0, 4, 1, 109, 3, 69, 0, 8, 0, 3, 80, 0, 7, 6, 99, 0, 121, 3, 49, 57, 0, 3, 74, 0, 7, 6, 100, 0, 3, 70, 0, 7, 6, 101, 0, 3, 36, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 4, 2, 101, 3, 77, 0, 2, 105, 0, 3, 79, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 7, 6, 106, 0, 3, 73, 0, 121, 3, 77, 57, 0, 7, 6, 107, 0, 3, 49, 0, 4, 2, 101, 3, 78, 0, 2, 105, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 112, 3, 63, 105, 0, 7, 6, 110, 0, 3, 50, 0, 116, 3, 50, 105, 0, 4, 2, 103, 101, 3, 65, 0, 2, 103, 105, 0, 121, 0, 2, 103, 3, 66, 0, 107, 3, 66, 99, 0, 7, 6, 111, 0, 3, 39, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 102, 0, 7, 6, 114, 0, 3, 16, 0, 8, 3, 51, 0, 7, 6, 115, 0, 3, 87, 0, 104, 3, 89, 0, 104, 121, 3, 95, 0, 7, 6, 116, 0, 3, 47, 0, 7, 6, 117, 0, 3, 40, 0, 7, 6, 118, 0, 3, 78, 0, 7, 6, 119, 0, 3, 58, 0, 1, 98, 3, 79, 0, 7, 6, 120, 0, 3, 49, 87, 0, 8, 3, 86, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 36, 3, 70, 39, 55, 35, 16, 35, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts51 = FileInMemory_createWithData (2250, reinterpret_cast (&espeakdata_dicts51_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/rw_dict", L"rw"); Collection_addItem (me.peek(), espeakdata_dicts51.transfer()); static unsigned char espeakdata_dicts52_data[2455] = { 0, 4, 0, 0, 253, 5, 0, 0, 0, 0, 0, 0, 0, 6, 65, 4, 112, 57, 0, 0, 0, 0, 0, 6, 65, 8, 69, 110, 0, 0, 0, 0, 0, 6, 65, 12, 87, 110, 0, 0, 0, 0, 0, 6, 65, 16, 70, 110, 0, 0, 0, 0, 0, 5, 65, 20, 110, 0, 0, 0, 0, 0, 6, 65, 24, 114, 81, 0, 0, 0, 0, 0, 6, 65, 28, 73, 110, 0, 0, 0, 0, 0, 6, 65, 32, 112, 74, 0, 0, 0, 0, 0, 6, 65, 36, 116, 57, 0, 0, 13, 1, 37, 87, 37, 57, 13, 57, 13, 138, 13, 0, 27, 0, 0, 0, 7, 65, 40, 73, 112, 57, 0, 0, 0, 16, 1, 42, 147, 87, 138, 13, 34, 37, 87, 49, 13, 57, 13, 0, 27, 0, 0, 7, 65, 44, 49, 112, 57, 0, 0, 0, 0, 0, 6, 65, 48, 114, 55, 0, 0, 0, 0, 0, 6, 65, 52, 114, 63, 0, 0, 0, 0, 0, 6, 65, 56, 114, 50, 0, 0, 0, 0, 0, 5, 65, 60, 117, 0, 0, 0, 0, 0, 6, 65, 64, 48, 110, 0, 0, 0, 0, 0, 7, 65, 68, 49, 57, 121, 0, 0, 0, 0, 0, 6, 65, 72, 116, 34, 0, 0, 0, 0, 0, 6, 65, 76, 114, 87, 0, 0, 0, 0, 0, 6, 65, 80, 136, 110, 0, 0, 0, 0, 0, 6, 65, 84, 57, 121, 0, 0, 0, 0, 0, 6, 65, 88, 82, 110, 0, 0, 0, 0, 0, 11, 65, 92, 70, 35, 69, 35, 55, 57, 121, 0, 0, 0, 0, 0, 7, 65, 96, 114, 49, 87, 0, 0, 0, 0, 0, 7, 65, 100, 58, 116, 57, 0, 0, 0, 0, 0, 7, 65, 104, 86, 114, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 48, 67, 87, 37, 57, 13, 57, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 49, 57, 70, 35, 105, 13, 50, 35, 82, 13, 57, 13, 0, 0, 13, 3, 95, 49, 56, 70, 35, 105, 13, 35, 138, 13, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 49, 49, 36, 49, 39, 62, 13, 105, 13, 0, 0, 12, 3, 95, 49, 48, 70, 35, 105, 13, 57, 13, 0, 0, 14, 3, 95, 49, 51, 70, 35, 105, 13, 47, 40, 50, 13, 0, 0, 12, 3, 95, 49, 50, 70, 39, 62, 13, 105, 13, 0, 0, 14, 3, 95, 49, 53, 48, 35, 105, 13, 62, 39, 82, 13, 0, 0, 16, 3, 95, 49, 52, 70, 35, 105, 13, 105, 35, 47, 13, 34, 13, 0, 0, 14, 3, 95, 49, 55, 70, 35, 105, 13, 105, 35, 47, 13, 0, 0, 14, 3, 95, 49, 54, 70, 35, 105, 13, 87, 35, 57, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 50, 88, 82, 37, 87, 87, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 48, 77, 50, 63, 37, 55, 37, 57, 13, 50, 13, 57, 13, 0, 0, 17, 4, 95, 48, 77, 51, 69, 37, 55, 37, 57, 13, 50, 13, 57, 13, 0, 0, 0, 13, 4, 95, 48, 77, 49, 70, 35, 105, 13, 87, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 2, 95, 51, 47, 121, 50, 13, 0, 0, 9, 2, 95, 50, 70, 36, 49, 13, 0, 0, 8, 2, 95, 49, 36, 49, 13, 0, 0, 0, 9, 2, 95, 55, 105, 35, 47, 13, 0, 0, 9, 2, 95, 54, 105, 35, 57, 13, 0, 0, 9, 2, 95, 53, 48, 35, 105, 13, 0, 0, 11, 2, 95, 52, 105, 35, 47, 13, 34, 13, 0, 0, 16, 2, 95, 59, 47, 6, 37, 47, 49, 4, 39, 63, 116, 82, 13, 0, 0, 0, 11, 2, 95, 57, 50, 35, 82, 13, 57, 13, 0, 0, 8, 2, 95, 56, 35, 138, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 1, 6, 0, 3, 35, 0, 7, 6, 1, 7, 0, 3, 116, 0, 7, 6, 1, 8, 0, 3, 147, 0, 7, 6, 1, 9, 0, 3, 115, 0, 7, 6, 1, 10, 0, 3, 37, 0, 7, 6, 1, 11, 0, 3, 110, 0, 7, 6, 1, 12, 0, 3, 40, 0, 7, 6, 1, 13, 0, 3, 121, 0, 7, 6, 1, 14, 0, 3, 34, 40, 0, 7, 6, 1, 15, 0, 3, 34, 121, 0, 7, 6, 1, 16, 0, 3, 55, 37, 0, 7, 6, 1, 17, 0, 3, 55, 110, 0, 7, 6, 1, 18, 0, 3, 36, 0, 7, 6, 1, 19, 0, 3, 112, 0, 7, 6, 1, 20, 0, 3, 132, 0, 7, 6, 1, 21, 0, 3, 39, 0, 7, 6, 1, 22, 0, 3, 117, 0, 7, 6, 1, 23, 0, 3, 133, 0, 7, 6, 1, 27, 0, 2, 17, 66, 3, 49, 0, 3, 49, 35, 0, 7, 6, 1, 28, 0, 2, 17, 66, 3, 49, 0, 3, 49, 35, 0, 7, 6, 1, 29, 0, 2, 17, 66, 3, 79, 0, 3, 79, 35, 0, 7, 6, 1, 30, 0, 2, 17, 66, 3, 79, 0, 3, 79, 35, 0, 7, 6, 1, 31, 0, 2, 17, 66, 3, 66, 0, 3, 66, 35, 0, 7, 6, 1, 32, 0, 2, 17, 66, 3, 152, 79, 0, 3, 152, 79, 35, 0, 7, 6, 1, 33, 0, 2, 17, 66, 3, 74, 0, 3, 74, 35, 0, 7, 6, 1, 34, 0, 2, 17, 66, 3, 74, 0, 3, 74, 35, 0, 7, 6, 1, 35, 0, 2, 17, 66, 3, 73, 0, 3, 73, 35, 0, 7, 6, 1, 36, 0, 3, 73, 35, 0, 2, 17, 66, 3, 73, 105, 0, 7, 6, 1, 37, 0, 2, 17, 66, 3, 65, 0, 3, 65, 35, 0, 7, 6, 1, 38, 0, 2, 17, 66, 3, 79, 50, 0, 3, 79, 50, 35, 0, 7, 6, 1, 39, 0, 2, 17, 66, 3, 151, 73, 0, 3, 151, 73, 35, 0, 7, 6, 1, 40, 0, 2, 17, 66, 3, 138, 0, 3, 138, 35, 0, 7, 6, 1, 41, 0, 2, 17, 66, 3, 138, 0, 3, 138, 35, 0, 7, 6, 1, 42, 0, 2, 17, 66, 3, 139, 0, 3, 139, 35, 0, 7, 6, 1, 43, 0, 2, 17, 66, 3, 139, 0, 3, 139, 35, 0, 7, 6, 1, 44, 0, 2, 17, 66, 3, 64, 0, 3, 64, 35, 0, 7, 6, 1, 45, 0, 2, 17, 66, 3, 150, 139, 0, 3, 150, 139, 35, 0, 7, 6, 1, 46, 0, 2, 17, 66, 3, 47, 0, 3, 47, 35, 0, 7, 6, 1, 47, 0, 2, 17, 66, 3, 47, 0, 3, 47, 35, 0, 7, 6, 1, 48, 0, 2, 17, 66, 3, 70, 0, 3, 70, 35, 0, 7, 6, 1, 49, 0, 2, 17, 66, 3, 70, 0, 3, 70, 35, 0, 7, 6, 1, 50, 0, 2, 17, 66, 3, 50, 0, 3, 50, 35, 0, 7, 6, 1, 52, 0, 2, 17, 66, 3, 149, 70, 0, 3, 149, 70, 35, 0, 7, 6, 1, 53, 0, 2, 17, 66, 3, 48, 0, 3, 48, 35, 0, 7, 6, 1, 54, 0, 2, 17, 66, 3, 48, 0, 3, 48, 35, 0, 7, 6, 1, 55, 0, 2, 17, 66, 3, 69, 0, 3, 69, 35, 0, 7, 6, 1, 56, 0, 2, 17, 66, 3, 69, 0, 3, 69, 35, 0, 7, 6, 1, 57, 0, 2, 17, 66, 3, 63, 0, 3, 63, 35, 0, 7, 6, 1, 58, 0, 2, 17, 66, 3, 148, 69, 0, 3, 148, 69, 35, 0, 7, 6, 1, 59, 0, 2, 17, 66, 3, 57, 0, 3, 57, 35, 0, 7, 6, 1, 60, 0, 2, 17, 66, 3, 34, 0, 3, 34, 35, 0, 7, 6, 1, 62, 0, 2, 17, 66, 3, 55, 0, 3, 55, 35, 0, 7, 6, 1, 65, 0, 2, 17, 66, 3, 82, 0, 3, 82, 35, 0, 7, 6, 1, 66, 0, 2, 17, 66, 3, 89, 0, 3, 89, 35, 0, 7, 6, 1, 67, 0, 2, 17, 66, 3, 89, 0, 3, 89, 35, 0, 7, 6, 1, 68, 0, 2, 17, 66, 3, 87, 0, 3, 87, 35, 0, 7, 6, 1, 69, 0, 2, 17, 66, 3, 105, 0, 3, 105, 35, 0, 7, 6, 1, 70, 0, 2, 17, 66, 3, 62, 0, 3, 62, 35, 0, 7, 6, 1, 71, 0, 2, 17, 66, 3, 81, 0, 3, 81, 35, 0, 7, 6, 224, 164, 0, 3, 21, 104, 105, 0, 7, 6, 224, 165, 0, 3, 21, 104, 105, 0, 7, 6, 224, 174, 0, 3, 21, 116, 97, 0, 7, 6, 224, 175, 0, 3, 21, 116, 97, 0, 7, 6, 224, 182, 0, 131, 3, 50, 0, 130, 3, 63, 0, 7, 6, 224, 183, 0, 138, 3, 0, 152, 3, 34, 40, 0, 178, 3, 34, 121, 0, 153, 3, 36, 0, 146, 3, 37, 0, 156, 3, 39, 0, 148, 3, 40, 0, 159, 3, 55, 37, 0, 179, 3, 55, 110, 0, 147, 3, 110, 0, 154, 3, 112, 0, 145, 3, 115, 0, 143, 3, 116, 0, 157, 3, 117, 0, 150, 3, 121, 0, 155, 3, 132, 0, 158, 3, 133, 0, 144, 3, 147, 0, 7, 6, 0, 36, 3, 70, 117, 62, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts52 = FileInMemory_createWithData (2454, reinterpret_cast (&espeakdata_dicts52_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/si_dict", L"si"); Collection_addItem (me.peek(), espeakdata_dicts52.transfer()); static unsigned char espeakdata_dicts53_data[8715] = { 0, 4, 0, 0, 105, 18, 0, 0, 0, 10, 135, 197, 190, 9, 1, 4, 14, 9, 20, 0, 0, 0, 0, 6, 65, 4, 122, 0, 14, 5, 193, 4, 72, 8, 0, 0, 0, 0, 11, 136, 26, 18, 21, 196, 141, 14, 195, 173, 20, 6, 65, 8, 69, 121, 0, 0, 0, 0, 14, 139, 22, 197, 161, 5, 20, 5, 196, 141, 14, 195, 173, 20, 0, 6, 65, 12, 115, 121, 0, 0, 0, 18, 4, 95, 8, 1, 3, 87, 10, 63, 6, 36, 49, 74, 36, 65, 39, 63, 0, 0, 0, 6, 65, 16, 70, 121, 0, 0, 0, 0, 0, 5, 65, 20, 121, 0, 0, 0, 0, 7, 196, 80, 145, 84, 60, 20, 0, 6, 65, 24, 36, 81, 0, 0, 0, 0, 0, 6, 65, 28, 79, 121, 0, 0, 0, 0, 0, 6, 65, 32, 105, 122, 0, 0, 0, 0, 11, 1, 35, 49, 51, 119, 88, 37, 49, 0, 27, 0, 5, 65, 36, 119, 0, 0, 0, 13, 1, 38, 35, 63, 48, 36, 51, 87, 35, 50, 70, 0, 0, 0, 6, 65, 40, 57, 121, 0, 0, 0, 12, 1, 42, 105, 82, 37, 36, 86, 70, 35, 0, 27, 0, 9, 1, 43, 48, 55, 40, 87, 0, 27, 0, 7, 65, 44, 49, 122, 0, 14, 6, 65, 44, 49, 0, 28, 0, 0, 0, 12, 137, 12, 15, 7, 9, 19, 20, 195, 173, 11, 20, 0, 6, 65, 48, 36, 55, 0, 0, 0, 0, 7, 196, 32, 241, 14, 36, 20, 0, 7, 132, 9, 14, 195, 173, 20, 6, 65, 52, 36, 63, 0, 0, 0, 0, 0, 6, 65, 56, 36, 50, 0, 0, 0, 0, 0, 6, 65, 60, 123, 0, 14, 9, 65, 60, 39, 10, 0, 72, 28, 23, 0, 16, 141, 16, 18, 5, 19, 22, 5, 4, 196, 141, 5, 14, 195, 173, 20, 12, 1, 61, 51, 39, 82, 50, 122, 87, 35, 0, 27, 0, 0, 0, 11, 1, 64, 86, 35, 82, 37, 50, 122, 74, 0, 6, 65, 64, 48, 121, 0, 0, 0, 0, 0, 7, 65, 68, 49, 82, 121, 0, 0, 0, 6, 195, 36, 226, 84, 20, 0, 0, 6, 65, 72, 36, 51, 0, 0, 0, 0, 0, 15, 140, 21, 11, 18, 9, 197, 190, 15, 22, 1, 14, 195, 173, 20, 7, 65, 76, 36, 87, 0, 14, 7, 65, 76, 87, 10, 0, 8, 0, 7, 195, 36, 224, 75, 72, 8, 0, 0, 7, 196, 80, 82, 148, 60, 20, 0, 6, 65, 80, 47, 121, 0, 0, 0, 9, 134, 16, 5, 11, 14, 195, 173, 20, 0, 0, 5, 65, 84, 124, 0, 0, 12, 137, 22, 195, 161, 197, 190, 5, 14, 195, 173, 20, 0, 13, 138, 19, 195, 186, 196, 141, 1, 19, 14, 195, 173, 20, 0, 0, 7, 65, 88, 82, 121, 0, 14, 7, 65, 88, 82, 10, 0, 28, 0, 0, 0, 14, 4, 95, 49, 77, 52, 69, 6, 37, 55, 37, 123, 50, 0, 0, 15, 65, 92, 70, 82, 6, 39, 57, 37, 47, 121, 4, 82, 121, 0, 0, 0, 0, 16, 1, 95, 47, 82, 44, 70, 122, 63, 6, 36, 116, 36, 51, 35, 0, 0, 13, 4, 95, 49, 77, 49, 113, 6, 37, 87, 119, 115, 0, 7, 65, 96, 37, 49, 87, 0, 0, 14, 4, 95, 49, 77, 50, 63, 6, 37, 55, 37, 123, 50, 0, 0, 16, 4, 95, 49, 77, 51, 63, 6, 37, 55, 57, 35, 51, 70, 35, 0, 0, 0, 11, 65, 100, 37, 48, 87, 37, 55, 39, 50, 0, 0, 0, 0, 0, 8, 65, 104, 86, 36, 47, 0, 14, 7, 65, 104, 86, 10, 0, 28, 0, 0, 0, 0, 0, 0, 9, 134, 13, 195, 161, 14, 9, 1, 20, 0, 0, 7, 132, 15, 14, 195, 173, 20, 0, 0, 9, 134, 13, 195, 161, 14, 9, 5, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 40, 81, 5, 56, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 50, 77, 49, 70, 82, 6, 36, 113, 6, 37, 87, 119, 115, 0, 0, 0, 9, 134, 13, 195, 161, 14, 9, 21, 20, 20, 4, 95, 50, 77, 51, 70, 82, 6, 36, 63, 6, 37, 55, 57, 35, 51, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 22, 195, 173, 14, 5, 196, 141, 11, 15, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 13, 12, 1, 4, 195, 173, 20, 0, 0, 0, 0, 0, 0, 0, 6, 194, 4, 160, 72, 8, 0, 0, 7, 196, 89, 65, 68, 100, 20, 0, 0, 0, 0, 0, 0, 0, 6, 195, 80, 145, 64, 20, 0, 0, 0, 0, 0, 10, 135, 13, 195, 161, 14, 9, 15, 21, 20, 0, 0, 0, 0, 0, 0, 0, 9, 67, 88, 194, 192, 82, 45, 49, 0, 0, 16, 4, 95, 4, 16, 20, 9, 74, 57, 4, 35, 34, 49, 35, 10, 0, 0, 11, 136, 16, 18, 9, 10, 1, 20, 195, 173, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 35, 57, 47, 6, 35, 69, 0, 17, 4, 95, 20, 12, 4, 87, 10, 82, 6, 45, 50, 39, 82, 49, 127, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 2, 25, 197, 165, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 11, 1, 197, 190, 4, 5, 10, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 141, 9, 14, 20, 5, 12, 9, 7, 5, 14, 20, 14, 195, 173, 20, 0, 0, 0, 0, 0, 0, 0, 6, 195, 8, 243, 0, 76, 0, 7, 196, 88, 147, 133, 56, 20, 0, 0, 0, 7, 195, 8, 86, 128, 8, 23, 0, 0, 0, 0, 11, 136, 19, 1, 13, 15, 20, 14, 195, 173, 20, 15, 140, 9, 14, 20, 18, 15, 22, 5, 18, 20, 14, 195, 173, 20, 0, 7, 195, 8, 86, 143, 8, 23, 0, 0, 0, 0, 7, 196, 60, 180, 133, 52, 8, 0, 0, 0, 0, 9, 67, 16, 194, 0, 70, 45, 105, 0, 0, 0, 0, 0, 0, 9, 134, 22, 9, 14, 14, 195, 173, 20, 0, 0, 10, 3, 226, 130, 172, 36, 40, 51, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 50, 6, 70, 82, 6, 36, 0, 0, 9, 198, 52, 21, 11, 36, 226, 64, 20, 0, 0, 16, 141, 9, 14, 4, 9, 22, 9, 4, 21, 195, 161, 12, 14, 5, 20, 9, 133, 19, 195, 173, 3, 5, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 4, 95, 13, 3, 14, 87, 10, 63, 6, 35, 49, 51, 39, 50, 39, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 131, 196, 141, 15, 72, 8, 0, 0, 0, 13, 3, 226, 128, 176, 48, 51, 39, 63, 37, 55, 36, 0, 0, 0, 13, 138, 20, 5, 12, 5, 22, 195, 173, 26, 14, 5, 20, 0, 0, 0, 8, 133, 10, 195, 186, 14, 9, 20, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 51, 88, 47, 14, 16, 6, 37, 70, 87, 35, 113, 0, 0, 7, 196, 80, 84, 129, 104, 20, 10, 3, 95, 48, 67, 87, 47, 6, 39, 0, 0, 0, 0, 0, 0, 13, 138, 16, 18, 9, 5, 13, 5, 18, 14, 195, 173, 20, 0, 0, 0, 0, 0, 0, 6, 195, 77, 65, 64, 72, 0, 0, 0, 5, 194, 40, 80, 72, 16, 3, 95, 49, 57, 114, 6, 36, 82, 120, 47, 50, 122, 87, 113, 0, 0, 7, 195, 65, 34, 64, 8, 23, 15, 3, 95, 49, 56, 6, 39, 87, 36, 63, 50, 122, 87, 113, 0, 0, 7, 196, 20, 229, 5, 72, 20, 14, 3, 95, 50, 67, 70, 82, 6, 36, 87, 47, 6, 39, 0, 0, 0, 0, 0, 0, 11, 3, 226, 136, 146, 63, 119, 50, 40, 87, 0, 0, 15, 3, 95, 49, 49, 57, 6, 36, 70, 36, 50, 122, 87, 113, 0, 0, 12, 3, 95, 49, 48, 114, 6, 36, 87, 35, 113, 0, 0, 15, 3, 95, 49, 51, 47, 14, 16, 6, 37, 50, 122, 87, 113, 0, 0, 14, 3, 95, 49, 50, 70, 82, 6, 35, 50, 122, 87, 113, 0, 0, 14, 3, 95, 49, 53, 48, 6, 120, 47, 50, 122, 87, 113, 0, 0, 14, 3, 95, 49, 52, 89, 47, 44, 50, 6, 122, 87, 113, 0, 0, 16, 3, 95, 49, 55, 87, 6, 36, 114, 36, 63, 50, 122, 87, 113, 0, 0, 15, 3, 95, 49, 54, 89, 6, 36, 87, 47, 50, 122, 87, 113, 0, 0, 0, 18, 3, 95, 55, 88, 87, 6, 36, 114, 36, 63, 114, 36, 87, 57, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 4, 16, 12, 197, 165, 48, 45, 113, 0, 0, 0, 9, 134, 195, 173, 4, 5, 15, 21, 20, 0, 6, 195, 52, 145, 9, 20, 0, 0, 0, 0, 0, 0, 0, 0, 24, 11, 16, 15, 19, 20, 9, 8, 14, 21, 20, 195, 173, 48, 39, 87, 113, 37, 105, 50, 40, 47, 119, 0, 0, 14, 3, 95, 50, 88, 70, 82, 6, 35, 70, 87, 35, 113, 0, 0, 0, 0, 17, 5, 95, 48, 77, 65, 51, 63, 6, 37, 55, 57, 35, 51, 70, 37, 0, 0, 16, 5, 95, 48, 77, 65, 50, 63, 6, 37, 55, 37, 123, 50, 37, 0, 0, 0, 16, 5, 95, 48, 77, 65, 52, 69, 6, 37, 55, 37, 123, 50, 37, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 147, 79, 8, 12, 3, 95, 63, 63, 87, 37, 63, 69, 39, 55, 0, 0, 0, 0, 6, 195, 76, 209, 64, 72, 16, 3, 95, 52, 88, 89, 47, 6, 37, 16, 37, 70, 87, 35, 113, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 56, 16, 72, 23, 0, 16, 3, 95, 53, 88, 48, 6, 120, 113, 114, 36, 87, 57, 35, 47, 0, 0, 0, 0, 0, 11, 136, 15, 11, 15, 12, 9, 20, 195, 173, 20, 0, 7, 196, 64, 85, 5, 72, 20, 0, 0, 0, 17, 3, 95, 54, 88, 89, 6, 36, 87, 113, 114, 36, 87, 57, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 6, 195, 169, 14, 9, 24, 20, 0, 17, 3, 95, 56, 88, 6, 39, 87, 36, 63, 114, 36, 87, 57, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 32, 240, 76, 0, 18, 3, 95, 57, 88, 70, 6, 36, 82, 120, 113, 114, 36, 87, 57, 35, 47, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 63, 65, 86, 50, 35, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 15, 7, 15, 87, 10, 6, 39, 79, 39, 65, 49, 39, 63, 0, 0, 0, 8, 197, 52, 20, 148, 36, 224, 20, 0, 0, 0, 0, 11, 136, 15, 19, 20, 1, 20, 14, 195, 173, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 48, 77, 52, 69, 6, 37, 55, 37, 123, 50, 39, 40, 0, 0, 0, 16, 4, 95, 48, 77, 50, 63, 6, 37, 55, 37, 123, 50, 39, 40, 0, 0, 15, 4, 95, 48, 77, 51, 63, 6, 37, 55, 57, 35, 51, 47, 0, 0, 0, 13, 4, 95, 48, 77, 49, 113, 6, 37, 87, 119, 115, 0, 0, 13, 4, 95, 2, 18, 22, 69, 51, 6, 36, 82, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 195, 173, 4, 5, 1, 20, 0, 0, 0, 0, 8, 133, 195, 173, 4, 5, 5, 20, 0, 0, 0, 0, 8, 133, 195, 173, 4, 5, 9, 20, 0, 0, 0, 11, 136, 19, 3, 8, 15, 16, 14, 195, 173, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 195, 173, 4, 5, 21, 20, 0, 0, 0, 0, 8, 133, 195, 173, 4, 5, 25, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 15, 16, 1, 20, 18, 14, 195, 173, 20, 0, 0, 13, 138, 16, 18, 195, 173, 2, 21, 26, 14, 195, 173, 20, 0, 0, 0, 20, 4, 95, 3, 9, 18, 87, 6, 39, 87, 47, 51, 37, 38, 4, 36, 89, 49, 127, 0, 0, 0, 14, 139, 13, 9, 13, 15, 22, 12, 195, 161, 4, 14, 5, 20, 14, 139, 6, 12, 5, 24, 9, 2, 9, 12, 14, 195, 173, 20, 0, 0, 24, 3, 95, 194, 183, 69, 39, 70, 49, 35, 6, 82, 48, 51, 39, 87, 47, 51, 57, 36, 70, 49, 40, 0, 0, 11, 3, 95, 194, 180, 70, 133, 88, 36, 65, 0, 0, 0, 13, 3, 95, 194, 178, 50, 35, 70, 51, 40, 105, 124, 0, 0, 14, 3, 95, 194, 179, 50, 35, 47, 51, 36, 47, 57, 40, 0, 0, 0, 0, 0, 0, 24, 4, 95, 19, 20, 11, 87, 39, 10, 89, 6, 37, 49, 63, 119, 63, 70, 6, 133, 88, 65, 39, 63, 0, 0, 18, 3, 95, 194, 173, 63, 36, 49, 49, 122, 48, 39, 63, 45, 74, 49, 35, 0, 0, 19, 3, 95, 194, 170, 105, 39, 51, 50, 119, 37, 50, 70, 36, 49, 87, 6, 122, 0, 16, 4, 95, 1, 3, 21, 87, 10, 70, 6, 133, 88, 65, 39, 63, 0, 0, 28, 3, 95, 194, 171, 70, 82, 39, 57, 37, 47, 122, 55, 39, 63, 36, 50, 122, 15, 86, 122, 47, 82, 39, 51, 49, 35, 0, 0, 0, 0, 6, 195, 60, 225, 78, 20, 11, 136, 14, 1, 4, 195, 173, 19, 197, 165, 20, 21, 3, 95, 194, 166, 48, 51, 36, 51, 40, 89, 36, 50, 122, 6, 74, 37, 35, 51, 35, 0, 0, 12, 137, 16, 18, 5, 4, 195, 173, 19, 197, 165, 20, 5, 194, 76, 16, 76, 0, 0, 0, 0, 0, 17, 4, 95, 18, 14, 7, 87, 10, 49, 51, 6, 124, 89, 49, 39, 63, 0, 0, 24, 3, 95, 194, 161, 39, 69, 34, 122, 113, 36, 50, 119, 82, 6, 119, 49, 51, 37, 74, 65, 119, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 80, 81, 1, 20, 10, 135, 15, 4, 195, 173, 19, 197, 165, 20, 0, 11, 136, 16, 15, 4, 195, 173, 19, 197, 165, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 22, 3, 95, 194, 191, 39, 69, 51, 122, 113, 36, 50, 119, 6, 39, 47, 122, 86, 65, 37, 49, 0, 0, 0, 0, 0, 28, 3, 95, 194, 187, 70, 82, 39, 57, 37, 47, 122, 55, 39, 63, 36, 50, 122, 15, 86, 35, 47, 82, 39, 51, 37, 113, 0, 0, 12, 3, 95, 194, 184, 115, 36, 70, 37, 55, 35, 0, 0, 12, 3, 95, 194, 185, 50, 35, 48, 51, 82, 124, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 2, 195, 151, 49, 51, 122, 47, 0, 7, 2, 196, 143, 114, 121, 0, 0, 0, 7, 2, 196, 141, 74, 121, 0, 0, 0, 0, 0, 0, 0, 13, 2, 194, 167, 48, 35, 51, 35, 79, 51, 35, 81, 0, 0, 15, 2, 194, 164, 86, 50, 35, 74, 49, 35, 63, 36, 50, 37, 0, 0, 0, 11, 2, 194, 162, 115, 36, 50, 47, 39, 40, 0, 0, 11, 2, 194, 163, 55, 37, 69, 57, 36, 51, 0, 0, 7, 2, 197, 136, 36, 65, 0, 0, 0, 8, 2, 195, 166, 35, 6, 121, 0, 0, 0, 15, 2, 194, 172, 55, 39, 79, 37, 115, 49, 121, 50, 39, 47, 0, 19, 2, 195, 164, 6, 122, 48, 51, 36, 105, 55, 35, 87, 39, 82, 35, 50, 121, 0, 0, 0, 0, 5, 130, 196, 155, 43, 0, 0, 12, 2, 195, 161, 70, 4, 45, 105, 121, 6, 122, 0, 0, 8, 196, 4, 193, 66, 60, 72, 8, 0, 0, 0, 7, 2, 194, 181, 63, 124, 0, 12, 2, 195, 173, 70, 4, 45, 105, 121, 6, 119, 0, 0, 0, 0, 12, 2, 194, 176, 87, 47, 40, 48, 65, 39, 40, 0, 0, 15, 2, 194, 177, 48, 55, 40, 87, 6, 63, 119, 50, 40, 87, 0, 7, 2, 197, 153, 36, 131, 0, 12, 2, 195, 169, 70, 4, 45, 105, 121, 6, 121, 0, 0, 17, 2, 194, 190, 47, 34, 37, 10, 89, 47, 82, 44, 47, 37, 50, 37, 0, 0, 11, 2, 195, 183, 114, 36, 55, 36, 50, 39, 0, 0, 13, 2, 194, 188, 89, 47, 82, 44, 47, 37, 50, 35, 0, 16, 2, 195, 180, 6, 123, 87, 82, 4, 39, 49, 122, 65, 39, 63, 0, 0, 6, 195, 56, 145, 64, 72, 13, 2, 194, 189, 48, 39, 55, 39, 82, 37, 115, 35, 0, 7, 2, 197, 165, 113, 121, 0, 0, 17, 4, 95, 3, 5, 4, 87, 10, 115, 6, 36, 114, 37, 55, 55, 127, 0, 0, 12, 2, 195, 179, 70, 4, 45, 105, 121, 6, 123, 0, 0, 0, 9, 67, 64, 192, 200, 48, 45, 99, 0, 22, 4, 95, 12, 9, 7, 55, 6, 37, 79, 35, 47, 4, 124, 51, 39, 82, 4, 35, 50, 121, 0, 7, 2, 197, 161, 36, 89, 0, 0, 15, 2, 195, 190, 48, 39, 63, 45, 74, 49, 35, 50, 35, 70, 0, 0, 17, 2, 197, 175, 6, 124, 87, 10, 49, 51, 6, 124, 88, 49, 39, 63, 0, 0, 0, 18, 2, 195, 189, 70, 4, 45, 105, 121, 6, 37, 48, 87, 37, 55, 39, 50, 0, 0, 11, 2, 195, 186, 70, 45, 105, 121, 6, 124, 0, 0, 0, 0, 0, 7, 2, 196, 190, 36, 61, 0, 0, 0, 0, 9, 134, 18, 195, 180, 26, 14, 5, 20, 6, 195, 76, 243, 64, 72, 0, 8, 133, 20, 195, 173, 20, 15, 20, 13, 2, 196, 186, 70, 4, 45, 105, 121, 6, 36, 55, 0, 0, 0, 0, 0, 8, 2, 197, 190, 88, 36, 47, 0, 0, 0, 6, 195, 16, 83, 79, 20, 0, 0, 0, 0, 0, 0, 0, 12, 5, 19, 20, 196, 186, 16, 87, 47, 133, 48, 0, 0, 8, 133, 195, 186, 14, 9, 9, 20, 0, 0, 0, 0, 8, 133, 195, 186, 14, 9, 5, 20, 0, 0, 0, 0, 8, 133, 195, 186, 14, 9, 1, 20, 5, 194, 76, 144, 72, 6, 194, 64, 240, 8, 23, 5, 194, 76, 144, 76, 0, 7, 195, 64, 241, 0, 8, 23, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 14, 5, 7, 1, 20, 195, 173, 22, 14, 5, 20, 6, 2, 95, 1, 122, 0, 0, 0, 0, 8, 133, 195, 186, 14, 9, 21, 20, 0, 0, 7, 2, 95, 11, 49, 122, 0, 0, 0, 0, 0, 6, 2, 95, 15, 123, 0, 0, 0, 0, 0, 7, 2, 95, 19, 36, 87, 0, 0, 0, 0, 0, 0, 7, 2, 95, 22, 82, 121, 0, 0, 0, 0, 0, 8, 2, 95, 26, 86, 36, 47, 0, 0, 0, 7, 131, 197, 190, 5, 72, 8, 0, 11, 136, 1, 11, 20, 195, 173, 22, 14, 9, 20, 0, 0, 0, 14, 139, 4, 5, 16, 18, 5, 19, 195, 173, 22, 14, 9, 20, 0, 0, 13, 2, 95, 34, 124, 82, 39, 116, 39, 82, 49, 37, 0, 0, 14, 2, 95, 33, 82, 119, 49, 51, 37, 74, 65, 119, 49, 0, 0, 0, 10, 135, 16, 18, 5, 4, 5, 197, 136, 20, 13, 2, 95, 39, 35, 48, 39, 87, 47, 51, 39, 81, 0, 0, 0, 0, 10, 2, 95, 36, 70, 39, 55, 122, 51, 0, 0, 6, 195, 80, 83, 128, 20, 0, 12, 4, 95, 3, 1, 16, 82, 36, 61, 49, 121, 0, 0, 13, 2, 95, 41, 86, 35, 47, 82, 39, 51, 37, 113, 0, 0, 13, 2, 95, 40, 86, 122, 47, 82, 39, 51, 49, 35, 0, 0, 11, 2, 95, 47, 55, 39, 63, 36, 50, 39, 0, 0, 10, 2, 95, 46, 69, 39, 70, 49, 35, 0, 0, 12, 2, 95, 45, 48, 39, 63, 45, 74, 49, 35, 0, 0, 11, 2, 95, 44, 74, 37, 35, 51, 49, 35, 0, 0, 10, 2, 95, 51, 47, 6, 14, 16, 37, 0, 0, 9, 2, 95, 50, 70, 82, 6, 35, 0, 0, 11, 2, 95, 49, 57, 6, 36, 70, 36, 50, 0, 0, 10, 2, 95, 48, 50, 6, 40, 55, 35, 0, 0, 11, 2, 95, 55, 87, 6, 36, 114, 36, 63, 0, 0, 10, 2, 95, 54, 89, 6, 36, 87, 113, 0, 0, 9, 2, 95, 53, 48, 6, 120, 113, 0, 0, 11, 2, 95, 52, 89, 47, 6, 37, 16, 37, 0, 0, 16, 2, 95, 59, 69, 39, 70, 49, 39, 74, 37, 35, 51, 49, 35, 0, 0, 14, 2, 95, 58, 70, 82, 39, 57, 69, 39, 70, 49, 35, 0, 0, 11, 2, 95, 57, 114, 6, 36, 82, 120, 113, 0, 0, 10, 2, 95, 56, 6, 39, 87, 36, 63, 0, 0, 12, 2, 95, 63, 39, 47, 122, 86, 65, 37, 49, 0, 0, 10, 2, 95, 62, 82, 36, 74, 89, 119, 0, 0, 0, 10, 2, 95, 60, 63, 36, 50, 89, 119, 0, 0, 0, 7, 196, 80, 83, 69, 72, 20, 0, 0, 0, 13, 138, 15, 11, 9, 5, 14, 5, 196, 141, 11, 15, 20, 0, 24, 11, 4, 9, 1, 7, 14, 15, 19, 20, 195, 173, 11, 70, 37, 35, 79, 50, 39, 87, 47, 119, 49, 0, 0, 0, 0, 0, 0, 29, 4, 95, 226, 128, 163, 47, 51, 39, 57, 40, 105, 39, 55, 50, 119, 49, 39, 82, 122, 6, 39, 70, 51, 122, 88, 49, 35, 0, 0, 14, 4, 95, 226, 128, 162, 39, 70, 51, 122, 88, 49, 35, 0, 0, 18, 4, 95, 226, 128, 161, 70, 82, 39, 57, 37, 47, 119, 49, 51, 119, 88, 0, 0, 0, 8, 197, 52, 192, 68, 20, 160, 20, 0, 0, 0, 0, 0, 0, 21, 4, 95, 226, 128, 153, 48, 34, 35, 82, 122, 6, 124, 82, 39, 116, 39, 82, 49, 35, 0, 0, 20, 4, 95, 226, 128, 152, 61, 35, 82, 122, 6, 124, 82, 39, 116, 39, 82, 49, 35, 0, 15, 4, 95, 4, 15, 20, 87, 10, 69, 6, 39, 47, 49, 127, 0, 0, 10, 4, 20, 196, 186, 11, 47, 133, 49, 0, 0, 14, 139, 16, 18, 9, 16, 18, 1, 22, 5, 14, 195, 173, 20, 0, 6, 195, 4, 193, 64, 8, 21, 4, 95, 226, 128, 157, 70, 39, 55, 50, 121, 6, 124, 82, 39, 116, 39, 82, 49, 37, 0, 21, 2, 95, 91, 105, 51, 35, 50, 35, 47, 122, 15, 86, 122, 47, 82, 39, 51, 49, 35, 0, 0, 21, 4, 95, 226, 128, 156, 105, 39, 34, 50, 121, 6, 124, 82, 39, 116, 39, 82, 49, 37, 0, 0, 19, 4, 95, 226, 128, 147, 70, 45, 105, 122, 6, 48, 39, 63, 45, 74, 49, 35, 0, 0, 6, 194, 76, 240, 8, 23, 0, 18, 2, 95, 95, 48, 39, 70, 74, 37, 35, 51, 49, 50, 40, 47, 37, 36, 0, 0, 13, 2, 95, 94, 87, 47, 51, 37, 36, 88, 49, 35, 0, 0, 21, 2, 95, 93, 105, 51, 35, 50, 35, 47, 122, 15, 86, 35, 47, 82, 39, 51, 37, 113, 0, 0, 18, 2, 95, 92, 39, 48, 35, 74, 50, 121, 15, 55, 39, 63, 36, 50, 39, 0, 0, 0, 0, 0, 11, 2, 95, 96, 35, 49, 115, 36, 50, 47, 0, 0, 11, 136, 13, 1, 20, 11, 9, 14, 195, 173, 20, 0, 12, 137, 16, 15, 22, 5, 18, 5, 14, 195, 173, 20, 16, 141, 12, 5, 7, 9, 19, 12, 1, 20, 195, 173, 22, 14, 5, 20, 0, 0, 0, 7, 195, 4, 179, 192, 72, 8, 0, 0, 0, 27, 4, 95, 7, 18, 22, 87, 10, 6, 39, 69, 51, 122, 113, 4, 36, 50, 119, 63, 70, 6, 133, 88, 65, 39, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 16, 15, 21, 196, 141, 5, 14, 195, 173, 20, 0, 0, 0, 21, 2, 95, 123, 86, 55, 39, 88, 36, 50, 122, 15, 86, 122, 47, 82, 39, 51, 49, 35, 0, 19, 4, 95, 4, 9, 1, 87, 10, 48, 51, 6, 36, 105, 55, 122, 87, 49, 127, 0, 0, 0, 0, 8, 133, 22, 197, 161, 1, 11, 8, 0, 0, 12, 2, 95, 126, 82, 45, 50, 39, 82, 49, 35, 0, 0, 21, 2, 95, 125, 86, 55, 39, 88, 36, 50, 122, 15, 86, 35, 47, 82, 39, 51, 37, 113, 0, 0, 17, 2, 95, 124, 86, 82, 37, 87, 55, 122, 15, 74, 37, 35, 51, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 19, 195, 186, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 35, 51, 50, 6, 63, 36, 116, 36, 51, 35, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 64, 146, 129, 80, 146, 193, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 4, 196, 141, 12, 14, 74, 45, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 77, 97, 84, 21, 32, 20, 0, 0, 0, 0, 0, 6, 131, 20, 195, 173, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 15, 4, 5, 197, 136, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 197, 161, 20, 1, 20, 21, 20, 195, 161, 18, 14, 9, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 9, 4, 5, 195, 173, 20, 0, 0, 0, 0, 12, 137, 16, 15, 197, 190, 9, 1, 18, 14, 5, 20, 0, 0, 9, 134, 16, 15, 4, 5, 197, 136, 20, 0, 15, 140, 4, 5, 6, 9, 14, 9, 20, 195, 173, 22, 14, 5, 20, 0, 0, 6, 116, 101, 0, 4, 1, 97, 105, 2, 32, 3, 47, 36, 0, 1, 97, 105, 118, 97, 122, 0, 1, 101, 100, 2, 107, 0, 1, 101, 100, 2, 114, 109, 0, 1, 101, 109, 2, 114, 32, 0, 1, 110, 105, 2, 114, 0, 1, 110, 105, 2, 114, 110, 101, 0, 1, 115, 2, 114, 0, 1, 115, 2, 114, 32, 0, 1, 115, 161, 195, 110, 2, 32, 0, 1, 118, 2, 100, 97, 106, 197, 161, 0, 1, 120, 101, 2, 114, 0, 2, 104, 111, 32, 0, 2, 106, 32, 0, 2, 109, 97, 116, 105, 0, 2, 114, 97, 106, 197, 161, 0, 2, 114, 97, 122, 0, 2, 114, 109, 0, 2, 115, 32, 0, 2, 115, 116, 0, 2, 120, 0, 8, 2, 99, 104, 0, 8, 2, 100, 97, 106, 197, 161, 0, 8, 2, 108, 101, 99, 0, 8, 2, 108, 101, 102, 0, 8, 2, 108, 101, 103, 0, 8, 2, 108, 101, 107, 0, 8, 2, 108, 101, 109, 0, 8, 2, 108, 101, 111, 0, 8, 2, 108, 101, 112, 0, 8, 2, 108, 101, 114, 0, 8, 2, 108, 101, 115, 101, 110, 0, 8, 2, 108, 101, 115, 107, 0, 8, 2, 108, 101, 116, 101, 114, 0, 8, 2, 108, 101, 116, 101, 120, 116, 0, 8, 2, 108, 101, 118, 0, 8, 2, 108, 101, 120, 0, 8, 2, 109, 112, 0, 8, 2, 110, 100, 0, 8, 2, 110, 105, 115, 0, 8, 2, 110, 116, 111, 0, 8, 2, 111, 0, 8, 2, 114, 97, 112, 0, 8, 2, 114, 97, 115, 0, 8, 2, 114, 101, 122, 0, 8, 2, 114, 195, 169, 110, 0, 8, 2, 114, 195, 169, 122, 0, 8, 2, 114, 196, 141, 0, 8, 2, 120, 0, 8, 2, 195, 179, 0, 8, 97, 107, 2, 99, 104, 0, 8, 97, 107, 2, 100, 0, 8, 97, 107, 2, 103, 0, 8, 97, 109, 2, 109, 97, 116, 105, 0, 8, 97, 109, 2, 114, 105, 97, 0, 8, 97, 109, 2, 114, 105, 195, 161, 0, 8, 97, 112, 2, 110, 116, 0, 8, 97, 114, 116, 115, 2, 103, 0, 8, 101, 100, 2, 107, 116, 195, 173, 0, 8, 101, 108, 101, 116, 2, 114, 0, 8, 101, 112, 109, 111, 107, 2, 110, 0, 8, 101, 161, 197, 118, 2, 196, 141, 0, 8, 105, 104, 99, 114, 97, 2, 107, 0, 8, 105, 108, 2, 114, 0, 8, 107, 97, 114, 97, 104, 99, 2, 114, 0, 8, 107, 97, 114, 97, 104, 99, 2, 114, 0, 8, 108, 97, 2, 114, 0, 8, 108, 97, 2, 114, 110, 0, 8, 108, 97, 2, 114, 110, 97, 116, 195, 173, 118, 0, 8, 108, 97, 119, 2, 114, 0, 8, 110, 105, 2, 108, 0, 8, 110, 105, 2, 110, 0, 8, 110, 105, 101, 100, 0, 8, 110, 121, 115, 0, 8, 110, 121, 115, 2, 116, 105, 0, 8, 111, 104, 2, 108, 0, 8, 111, 112, 2, 110, 0, 8, 112, 101, 115, 2, 109, 98, 0, 8, 115, 2, 112, 0, 8, 115, 97, 112, 0, 8, 115, 105, 115, 97, 2, 110, 0, 8, 115, 105, 120, 101, 2, 110, 0, 8, 115, 121, 115, 2, 109, 0, 8, 169, 195, 2, 114, 0, 7, 6, 195, 161, 0, 3, 122, 0, 7, 6, 195, 164, 0, 3, 36, 0, 7, 6, 195, 169, 0, 3, 121, 0, 7, 6, 195, 173, 0, 3, 119, 0, 7, 6, 195, 179, 0, 3, 123, 0, 7, 6, 195, 180, 0, 3, 40, 39, 0, 7, 6, 195, 186, 0, 3, 124, 0, 7, 6, 195, 189, 0, 3, 119, 0, 7, 6, 196, 141, 0, 3, 74, 0, 7, 6, 196, 143, 0, 2, 32, 3, 113, 0, 4, 3, 114, 0, 2, 32, 17, 70, 0, 7, 6, 196, 186, 0, 3, 133, 0, 7, 6, 196, 190, 0, 3, 61, 0, 7, 6, 197, 136, 0, 3, 65, 0, 7, 6, 197, 149, 0, 3, 130, 0, 7, 6, 197, 153, 0, 3, 131, 0, 4, 1, 102, 3, 132, 0, 1, 107, 0, 1, 112, 0, 1, 116, 0, 7, 6, 197, 161, 0, 3, 89, 0, 7, 6, 197, 165, 0, 3, 113, 0, 7, 6, 197, 190, 0, 4, 3, 88, 0, 2, 32, 17, 70, 0, 2, 32, 3, 89, 0, 7, 6, 97, 0, 3, 35, 0, 7, 6, 98, 0, 101, 122, 111, 8, 2, 45, 14, 128, 132, 133, 3, 6, 69, 36, 86, 39, 0, 101, 122, 8, 2, 45, 14, 128, 132, 132, 3, 6, 69, 36, 87, 0, 2, 32, 3, 48, 0, 4, 3, 69, 0, 2, 32, 17, 70, 0, 7, 6, 99, 0, 104, 3, 99, 0, 3, 115, 0, 7, 6, 100, 0, 2, 32, 3, 47, 0, 4, 3, 70, 0, 1, 97, 2, 101, 0, 1, 97, 114, 116, 2, 105, 0, 1, 101, 109, 2, 105, 0, 1, 101, 114, 107, 2, 105, 0, 1, 101, 114, 107, 115, 105, 100, 2, 105, 0, 1, 105, 2, 101, 110, 0, 1, 105, 2, 101, 111, 0, 1, 110, 97, 109, 2, 105, 116, 0, 1, 110, 105, 2, 105, 0, 1, 111, 2, 105, 99, 0, 1, 111, 2, 105, 107, 0, 1, 111, 108, 101, 109, 2, 105, 0, 1, 111, 109, 2, 101, 114, 0, 1, 114, 111, 2, 105, 0, 1, 169, 195, 109, 2, 105, 0, 1, 179, 195, 108, 101, 109, 2, 105, 0, 2, 32, 17, 70, 0, 2, 101, 28, 17, 0, 2, 101, 99, 105, 0, 2, 101, 102, 0, 2, 101, 116, 101, 107, 0, 2, 101, 116, 101, 114, 109, 0, 2, 105, 28, 17, 0, 2, 105, 99, 107, 0, 2, 105, 100, 97, 107, 116, 105, 0, 2, 105, 102, 0, 2, 105, 107, 32, 0, 2, 105, 107, 116, 0, 2, 105, 111, 0, 2, 105, 114, 0, 2, 105, 115, 107, 114, 101, 0, 2, 105, 115, 107, 117, 0, 2, 105, 115, 112, 0, 2, 105, 115, 116, 0, 2, 105, 115, 116, 105, 99, 0, 2, 105, 122, 109, 117, 115, 0, 2, 105, 195, 179, 0, 2, 195, 173, 28, 17, 0, 8, 2, 101, 99, 101, 0, 8, 2, 101, 102, 105, 110, 105, 116, 195, 173, 118, 0, 8, 2, 101, 105, 110, 116, 101, 0, 8, 2, 101, 107, 111, 114, 0, 8, 2, 101, 107, 114, 101, 109, 101, 110, 116, 0, 8, 2, 101, 107, 114, 195, 169, 116, 0, 8, 2, 101, 107, 195, 161, 100, 0, 8, 2, 101, 107, 195, 179, 114, 0, 8, 2, 101, 108, 101, 103, 0, 8, 2, 101, 108, 105, 109, 0, 8, 2, 101, 112, 114, 101, 115, 0, 8, 2, 101, 115, 105, 103, 0, 8, 2, 101, 115, 116, 105, 0, 8, 2, 101, 116, 97, 105, 108, 0, 8, 2, 101, 116, 101, 107, 116, 195, 173, 0, 8, 2, 101, 118, 105, 122, 0, 8, 2, 101, 118, 195, 173, 122, 0, 8, 2, 101, 122, 0, 8, 2, 105, 97, 0, 8, 2, 105, 101, 99, 0, 8, 2, 105, 101, 116, 0, 8, 2, 105, 102, 116, 195, 173, 110, 0, 8, 2, 105, 103, 0, 8, 2, 105, 109, 101, 110, 0, 8, 2, 105, 112, 0, 8, 2, 105, 115, 0, 8, 2, 105, 115, 107, 0, 8, 2, 105, 118, 195, 173, 122, 0, 8, 2, 105, 195, 161, 0, 8, 2, 105, 195, 169, 0, 8, 97, 107, 2, 101, 116, 0, 8, 97, 110, 2, 195, 173, 100, 0, 8, 97, 110, 2, 195, 173, 196, 143, 0, 8, 97, 114, 2, 105, 107, 195, 161, 108, 0, 8, 97, 114, 116, 2, 195, 173, 0, 8, 97, 116, 161, 197, 2, 105, 0, 8, 101, 2, 105, 116, 0, 8, 101, 102, 2, 101, 114, 0, 8, 101, 112, 120, 101, 2, 105, 0, 8, 101, 114, 112, 2, 105, 122, 98, 0, 8, 101, 114, 112, 2, 105, 197, 161, 0, 8, 101, 114, 112, 2, 195, 173, 100, 0, 8, 101, 114, 112, 2, 195, 173, 196, 143, 0, 8, 105, 2, 101, 97, 0, 8, 105, 2, 101, 110, 116, 105, 0, 8, 105, 2, 101, 195, 161, 0, 8, 105, 2, 105, 108, 0, 8, 105, 2, 105, 111, 0, 8, 105, 108, 97, 118, 110, 105, 2, 105, 116, 0, 8, 105, 108, 97, 118, 110, 105, 2, 105, 122, 0, 8, 105, 118, 2, 101, 97, 0, 8, 105, 118, 2, 101, 111, 0, 8, 105, 118, 2, 101, 117, 0, 8, 105, 118, 101, 2, 101, 110, 0, 8, 105, 122, 101, 114, 112, 2, 101, 110, 116, 0, 8, 110, 97, 104, 2, 105, 0, 8, 110, 97, 107, 115, 2, 105, 0, 8, 110, 101, 112, 105, 116, 161, 197, 2, 105, 0, 8, 110, 105, 2, 101, 120, 0, 8, 110, 111, 112, 161, 197, 101, 114, 111, 107, 2, 101, 110, 0, 8, 111, 2, 105, 110, 0, 8, 111, 2, 105, 115, 0, 8, 111, 2, 105, 197, 161, 0, 8, 111, 2, 195, 173, 196, 143, 0, 8, 111, 107, 2, 105, 102, 105, 0, 8, 111, 109, 2, 101, 108, 0, 8, 111, 109, 2, 101, 109, 0, 8, 111, 109, 2, 105, 0, 8, 111, 112, 2, 195, 173, 100, 0, 8, 111, 112, 2, 195, 173, 196, 143, 0, 8, 111, 116, 101, 109, 2, 105, 0, 8, 114, 97, 100, 110, 97, 116, 161, 197, 2, 105, 122, 0, 8, 117, 97, 2, 105, 0, 8, 117, 97, 2, 105, 0, 8, 117, 116, 161, 197, 2, 101, 110, 0, 8, 117, 116, 161, 197, 2, 105, 0, 8, 161, 195, 116, 161, 197, 2, 105, 0, 8, 186, 195, 116, 161, 197, 2, 105, 0, 4, 197, 190, 3, 73, 0, 197, 190, 2, 32, 17, 70, 0, 197, 190, 2, 32, 3, 74, 0, 4, 2, 101, 3, 114, 0, 2, 105, 0, 2, 195, 173, 0, 122, 2, 32, 3, 115, 0, 4, 122, 3, 116, 0, 122, 2, 32, 17, 70, 0, 7, 6, 101, 0, 3, 36, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 2, 32, 3, 49, 0, 4, 3, 79, 0, 2, 32, 17, 70, 0, 7, 6, 104, 0, 2, 32, 3, 99, 0, 4, 3, 105, 0, 2, 32, 17, 70, 0, 7, 6, 105, 0, 97, 3, 2, 37, 35, 0, 101, 3, 2, 37, 36, 0, 117, 3, 2, 37, 40, 0, 3, 37, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 1, 25, 2, 25, 3, 45, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 97, 8, 2, 45, 14, 128, 132, 131, 3, 6, 50, 35, 0, 4, 3, 50, 0, 1, 17, 67, 21, 2, 101, 106, 32, 0, 1, 97, 2, 105, 109, 0, 1, 97, 103, 114, 111, 2, 105, 122, 0, 1, 97, 109, 2, 105, 0, 1, 97, 118, 122, 2, 101, 106, 32, 0, 1, 100, 97, 105, 114, 2, 101, 0, 1, 101, 103, 2, 101, 0, 1, 101, 108, 111, 118, 2, 195, 173, 0, 1, 103, 97, 109, 2, 101, 0, 1, 104, 99, 2, 105, 99, 0, 1, 104, 99, 2, 105, 107, 0, 1, 105, 2, 105, 99, 105, 0, 1, 108, 161, 195, 2, 105, 0, 1, 108, 161, 195, 105, 99, 111, 115, 2, 101, 0, 1, 108, 161, 195, 109, 114, 111, 102, 2, 101, 0, 1, 111, 2, 105, 99, 0, 1, 111, 2, 105, 107, 0, 1, 111, 2, 105, 115, 0, 1, 111, 102, 2, 105, 99, 0, 1, 111, 103, 2, 105, 0, 1, 111, 103, 97, 116, 2, 105, 115, 0, 1, 111, 109, 114, 97, 104, 2, 105, 0, 1, 111, 114, 2, 105, 99, 0, 1, 111, 114, 2, 105, 107, 0, 1, 111, 114, 100, 110, 101, 2, 105, 0, 1, 111, 114, 116, 2, 105, 0, 1, 114, 101, 116, 110, 105, 2, 101, 0, 1, 116, 161, 195, 116, 161, 197, 2, 101, 32, 0, 1, 117, 109, 2, 105, 107, 0, 1, 117, 109, 2, 105, 115, 0, 1, 118, 161, 195, 114, 112, 115, 2, 101, 0, 1, 118, 173, 195, 116, 97, 110, 2, 101, 0, 1, 122, 180, 195, 114, 2, 101, 0, 1, 169, 195, 114, 116, 2, 105, 0, 1, 173, 195, 108, 2, 105, 0, 1, 179, 195, 102, 2, 105, 0, 1, 179, 195, 103, 2, 105, 0, 1, 179, 195, 109, 114, 97, 104, 2, 105, 0, 2, 101, 28, 17, 0, 2, 101, 104, 111, 32, 0, 2, 101, 110, 116, 0, 2, 105, 28, 17, 0, 2, 105, 115, 116, 0, 2, 105, 122, 109, 117, 115, 32, 0, 2, 195, 173, 28, 17, 0, 8, 2, 101, 103, 0, 8, 2, 101, 103, 97, 116, 195, 173, 118, 0, 8, 2, 101, 103, 195, 161, 99, 0, 8, 2, 101, 111, 107, 108, 97, 115, 0, 8, 2, 101, 111, 112, 114, 195, 169, 110, 0, 8, 2, 101, 111, 114, 101, 0, 8, 2, 101, 114, 118, 0, 8, 2, 101, 117, 116, 114, 195, 161, 108, 0, 8, 2, 101, 120, 116, 0, 8, 2, 101, 195, 179, 110, 0, 8, 2, 105, 107, 111, 116, 0, 8, 97, 104, 99, 101, 109, 2, 105, 0, 8, 97, 112, 2, 101, 108, 0, 8, 97, 116, 111, 98, 2, 105, 0, 8, 100, 97, 105, 190, 197, 2, 101, 0, 8, 100, 122, 161, 195, 114, 112, 2, 101, 0, 8, 101, 2, 101, 114, 103, 0, 8, 101, 98, 2, 101, 102, 0, 8, 101, 103, 2, 105, 0, 8, 101, 109, 2, 101, 197, 190, 0, 8, 101, 114, 2, 101, 115, 0, 8, 101, 116, 2, 105, 115, 0, 8, 103, 105, 115, 2, 105, 0, 8, 104, 99, 101, 116, 2, 105, 0, 8, 105, 102, 101, 100, 2, 105, 116, 195, 173, 118, 0, 8, 105, 102, 101, 100, 2, 195, 173, 99, 0, 8, 105, 107, 116, 97, 109, 2, 101, 0, 8, 105, 108, 2, 101, 0, 8, 105, 109, 2, 105, 0, 8, 105, 109, 100, 97, 2, 105, 115, 116, 0, 8, 108, 161, 195, 101, 114, 2, 101, 0, 8, 108, 161, 195, 105, 99, 101, 112, 161, 197, 2, 101, 0, 8, 108, 161, 195, 110, 111, 115, 114, 101, 112, 2, 101, 0, 8, 108, 161, 195, 117, 116, 107, 97, 2, 101, 0, 8, 110, 105, 118, 2, 101, 0, 8, 111, 102, 2, 101, 0, 8, 111, 108, 111, 107, 2, 105, 0, 8, 111, 109, 2, 105, 0, 8, 114, 186, 195, 116, 108, 117, 107, 2, 101, 0, 8, 116, 114, 97, 112, 2, 101, 114, 0, 8, 116, 115, 101, 105, 109, 2, 101, 0, 8, 116, 161, 195, 116, 161, 197, 2, 101, 0, 8, 116, 169, 195, 114, 107, 110, 111, 107, 2, 101, 0, 8, 117, 2, 105, 0, 8, 117, 109, 2, 105, 0, 8, 117, 109, 105, 2, 105, 0, 8, 117, 109, 111, 107, 2, 105, 0, 8, 117, 116, 2, 105, 115, 0, 8, 118, 173, 195, 116, 97, 114, 116, 115, 105, 110, 105, 109, 100, 97, 2, 101, 0, 8, 169, 195, 103, 2, 105, 0, 8, 169, 195, 114, 116, 2, 101, 114, 0, 8, 179, 195, 108, 111, 107, 2, 105, 0, 8, 190, 197, 161, 195, 118, 2, 101, 0, 4, 2, 101, 3, 65, 0, 2, 105, 0, 2, 195, 173, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 7, 6, 111, 0, 3, 39, 0, 117, 3, 127, 0, 7, 6, 112, 0, 111, 8, 2, 45, 14, 128, 132, 131, 3, 6, 48, 39, 0, 111, 100, 8, 2, 45, 14, 128, 132, 132, 3, 6, 48, 39, 47, 0, 114, 105, 8, 2, 45, 14, 128, 132, 132, 3, 6, 48, 51, 37, 0, 3, 48, 0, 111, 118, 8, 2, 115, 116, 97, 17, 67, 3, 48, 39, 81, 0, 7, 6, 113, 0, 3, 49, 0, 117, 3, 49, 82, 0, 7, 6, 114, 0, 1, 25, 2, 25, 3, 44, 0, 4, 3, 51, 0, 114, 0, 7, 6, 115, 0, 111, 8, 2, 45, 14, 128, 132, 131, 3, 6, 87, 39, 0, 3, 87, 0, 7, 6, 116, 0, 4, 3, 47, 0, 1, 97, 2, 105, 99, 107, 0, 1, 97, 2, 105, 107, 195, 161, 0, 1, 97, 2, 105, 110, 0, 1, 97, 2, 105, 122, 0, 1, 97, 104, 99, 2, 105, 99, 0, 1, 97, 104, 99, 2, 105, 107, 0, 1, 97, 109, 2, 105, 99, 107, 0, 1, 97, 109, 2, 105, 107, 0, 1, 97, 109, 97, 2, 105, 99, 0, 1, 97, 109, 97, 2, 105, 107, 0, 1, 97, 109, 101, 2, 105, 0, 1, 97, 109, 101, 116, 2, 105, 0, 1, 101, 2, 105, 99, 0, 1, 101, 2, 105, 107, 0, 1, 101, 108, 112, 109, 111, 107, 2, 105, 122, 0, 1, 105, 2, 105, 99, 0, 1, 105, 2, 105, 107, 0, 1, 105, 108, 2, 105, 99, 0, 1, 107, 97, 2, 105, 0, 1, 107, 97, 2, 105, 107, 0, 1, 107, 97, 100, 105, 100, 2, 105, 0, 1, 107, 101, 2, 105, 0, 1, 107, 101, 2, 195, 173, 0, 1, 107, 114, 2, 105, 0, 1, 110, 2, 105, 99, 0, 1, 110, 2, 105, 110, 0, 1, 110, 97, 2, 105, 0, 1, 110, 101, 2, 105, 110, 0, 1, 110, 101, 118, 2, 105, 108, 0, 1, 111, 2, 105, 99, 0, 1, 111, 2, 105, 107, 0, 1, 111, 109, 2, 105, 118, 0, 1, 111, 114, 2, 105, 99, 0, 1, 111, 114, 2, 105, 107, 0, 1, 112, 101, 2, 105, 99, 0, 1, 112, 101, 2, 105, 107, 0, 1, 112, 111, 2, 105, 0, 1, 114, 97, 112, 2, 105, 0, 1, 115, 2, 105, 99, 0, 1, 115, 97, 2, 105, 99, 0, 1, 115, 101, 114, 112, 2, 105, 197, 190, 0, 1, 115, 101, 118, 110, 105, 2, 105, 0, 1, 115, 111, 2, 105, 99, 0, 1, 189, 195, 2, 105, 99, 0, 2, 101, 28, 17, 0, 2, 105, 28, 17, 0, 2, 105, 99, 107, 0, 2, 105, 107, 32, 0, 2, 105, 110, 103, 0, 2, 105, 115, 116, 0, 2, 105, 122, 109, 117, 115, 32, 0, 2, 195, 173, 28, 17, 0, 8, 2, 101, 114, 101, 115, 116, 114, 105, 0, 8, 2, 105, 109, 111, 116, 101, 106, 0, 8, 2, 105, 114, 97, 110, 0, 8, 2, 105, 116, 97, 110, 0, 8, 2, 105, 116, 117, 108, 0, 8, 97, 109, 101, 116, 97, 109, 2, 105, 0, 8, 97, 109, 111, 116, 117, 97, 2, 105, 0, 8, 97, 112, 97, 2, 105, 0, 8, 97, 112, 105, 116, 110, 97, 2, 105, 0, 8, 97, 115, 2, 105, 114, 0, 8, 97, 115, 2, 105, 115, 0, 8, 97, 116, 161, 197, 2, 105, 0, 8, 101, 109, 114, 101, 104, 2, 105, 0, 8, 101, 109, 122, 111, 107, 2, 105, 0, 8, 101, 110, 103, 97, 109, 2, 105, 0, 8, 101, 110, 111, 102, 2, 105, 0, 8, 101, 114, 107, 110, 111, 107, 2, 105, 122, 0, 8, 101, 116, 110, 121, 115, 2, 105, 0, 8, 105, 114, 107, 2, 105, 99, 0, 8, 105, 114, 107, 2, 105, 107, 0, 8, 105, 114, 107, 2, 105, 122, 0, 8, 105, 115, 110, 101, 115, 2, 105, 0, 8, 107, 97, 2, 105, 118, 0, 8, 107, 117, 100, 111, 114, 112, 2, 105, 0, 8, 108, 117, 107, 2, 105, 0, 8, 108, 117, 109, 2, 105, 0, 8, 110, 97, 2, 105, 0, 8, 110, 97, 108, 116, 97, 2, 105, 0, 8, 110, 101, 99, 2, 105, 0, 8, 110, 101, 100, 105, 2, 105, 0, 8, 110, 101, 118, 101, 114, 112, 2, 195, 173, 118, 0, 8, 110, 111, 107, 2, 105, 0, 8, 111, 97, 104, 99, 2, 105, 99, 0, 8, 111, 97, 104, 99, 2, 105, 107, 0, 8, 111, 107, 105, 110, 2, 105, 0, 8, 111, 120, 101, 2, 105, 0, 8, 114, 101, 99, 2, 105, 0, 8, 114, 101, 118, 2, 105, 0, 8, 115, 2, 105, 109, 117, 108, 0, 8, 115, 98, 97, 2, 105, 0, 8, 115, 101, 100, 2, 105, 0, 8, 115, 105, 108, 97, 98, 2, 105, 0, 8, 115, 105, 114, 101, 116, 107, 97, 114, 97, 104, 99, 2, 105, 0, 8, 115, 105, 114, 101, 116, 107, 97, 114, 97, 104, 99, 2, 195, 173, 107, 0, 8, 115, 105, 116, 97, 116, 161, 197, 2, 105, 0, 8, 115, 110, 105, 2, 105, 0, 8, 115, 110, 111, 107, 2, 105, 0, 8, 115, 111, 110, 103, 97, 105, 100, 2, 105, 0, 8, 115, 117, 106, 2, 105, 0, 8, 117, 101, 99, 97, 109, 114, 97, 102, 2, 105, 0, 8, 117, 112, 2, 105, 107, 0, 8, 120, 101, 116, 2, 105, 108, 0, 8, 161, 197, 2, 105, 112, 101, 110, 100, 105, 0, 8, 161, 197, 101, 114, 2, 105, 0, 8, 161, 197, 110, 105, 2, 105, 0, 8, 161, 197, 110, 105, 101, 100, 2, 105, 0, 8, 161, 197, 110, 111, 107, 2, 105, 0, 4, 195, 173, 1, 97, 2, 118, 3, 47, 119, 0, 195, 173, 1, 105, 2, 118, 0, 195, 173, 1, 107, 101, 112, 115, 2, 118, 0, 195, 173, 1, 111, 109, 2, 118, 0, 195, 173, 1, 114, 111, 2, 109, 0, 195, 173, 1, 115, 101, 108, 97, 2, 116, 0, 195, 173, 1, 117, 110, 107, 105, 118, 0, 195, 173, 8, 2, 109, 111, 118, 0, 195, 173, 8, 97, 103, 101, 110, 2, 118, 0, 195, 173, 8, 97, 110, 114, 101, 116, 108, 97, 2, 118, 0, 195, 173, 8, 102, 105, 100, 2, 110, 0, 195, 173, 8, 105, 100, 117, 97, 2, 118, 0, 195, 173, 8, 105, 110, 105, 102, 101, 100, 2, 118, 0, 195, 173, 8, 105, 115, 110, 101, 115, 0, 195, 173, 8, 107, 97, 2, 118, 0, 195, 173, 8, 107, 101, 116, 101, 100, 0, 195, 173, 8, 107, 117, 100, 111, 114, 112, 2, 118, 0, 195, 173, 8, 107, 117, 114, 116, 161, 197, 110, 111, 107, 2, 118, 0, 195, 173, 8, 115, 101, 108, 97, 112, 0, 195, 173, 8, 115, 117, 106, 0, 4, 2, 101, 3, 113, 0, 2, 105, 0, 2, 195, 173, 0, 7, 6, 117, 0, 3, 40, 0, 7, 6, 118, 0, 121, 8, 2, 21, 14, 128, 132, 130, 3, 6, 82, 37, 0, 1, 17, 65, 2, 25, 3, 58, 0, 4, 3, 82, 0, 1, 17, 65, 2, 108, 25, 0, 1, 17, 65, 2, 110, 0, 1, 17, 65, 2, 196, 186, 0, 1, 17, 65, 2, 197, 136, 0, 7, 6, 119, 0, 1, 17, 65, 2, 25, 3, 58, 0, 4, 3, 82, 0, 104, 2, 12, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 3, 37, 0, 7, 6, 122, 0, 4, 3, 86, 0, 2, 32, 17, 70, 0, 2, 32, 3, 87, 0, 7, 6, 0, 196, 155, 3, 36, 0, 37, 1, 32, 15, 3, 48, 36, 51, 115, 36, 50, 47, 0, 37, 3, 48, 36, 51, 115, 36, 50, 47, 39, 0, 36, 3, 70, 39, 55, 122, 51, 0, 197, 175, 3, 124, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts53 = FileInMemory_createWithData (8714, reinterpret_cast (&espeakdata_dicts53_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/sk_dict", L"sk"); Collection_addItem (me.peek(), espeakdata_dicts53.transfer()); static unsigned char espeakdata_dicts54_data[2691] = { 0, 4, 0, 0, 110, 8, 0, 0, 0, 0, 0, 0, 0, 6, 65, 4, 35, 0, 14, 4, 193, 4, 72, 0, 0, 0, 0, 6, 65, 8, 69, 13, 0, 0, 0, 0, 0, 6, 65, 12, 115, 13, 0, 0, 0, 0, 0, 6, 65, 16, 70, 13, 0, 0, 0, 0, 0, 5, 65, 20, 36, 0, 0, 0, 0, 0, 6, 65, 24, 81, 13, 0, 0, 0, 0, 0, 6, 65, 28, 79, 13, 0, 0, 0, 0, 0, 6, 65, 32, 105, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 40, 57, 13, 0, 0, 0, 0, 0, 7, 65, 44, 49, 13, 0, 14, 5, 65, 44, 49, 0, 0, 0, 0, 0, 6, 65, 48, 55, 13, 0, 0, 0, 0, 0, 6, 65, 52, 63, 13, 0, 0, 0, 0, 0, 10, 5, 95, 48, 1, 14, 4, 37, 50, 0, 6, 65, 56, 50, 13, 0, 0, 0, 0, 0, 6, 65, 60, 39, 0, 14, 4, 193, 60, 72, 0, 0, 0, 0, 6, 65, 64, 48, 13, 0, 0, 0, 0, 0, 6, 65, 68, 49, 40, 0, 0, 0, 0, 0, 6, 65, 72, 51, 13, 0, 0, 0, 0, 0, 7, 65, 76, 87, 13, 0, 14, 5, 65, 76, 87, 0, 0, 0, 0, 0, 6, 65, 80, 47, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 65, 88, 82, 13, 0, 14, 6, 65, 88, 58, 0, 23, 0, 0, 0, 18, 4, 95, 49, 77, 52, 6, 36, 50, 69, 37, 55, 37, 57, 6, 39, 50, 0, 0, 14, 65, 92, 70, 82, 6, 39, 57, 50, 37, 82, 4, 13, 0, 0, 0, 0, 0, 13, 4, 95, 49, 77, 49, 47, 6, 37, 87, 39, 74, 0, 7, 65, 96, 37, 49, 87, 0, 0, 18, 4, 95, 49, 77, 50, 6, 36, 50, 63, 37, 55, 37, 57, 6, 39, 50, 0, 0, 21, 4, 95, 49, 77, 51, 6, 36, 50, 35, 63, 37, 55, 37, 57, 6, 35, 51, 70, 35, 0, 0, 0, 12, 65, 100, 6, 37, 48, 87, 37, 55, 39, 50, 0, 0, 0, 0, 0, 7, 65, 104, 86, 13, 0, 14, 6, 65, 104, 86, 0, 23, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 50, 77, 52, 70, 82, 6, 35, 69, 37, 55, 37, 57, 6, 39, 50, 35, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 50, 77, 50, 70, 82, 6, 35, 63, 37, 55, 37, 57, 6, 39, 50, 35, 0, 0, 21, 4, 95, 50, 77, 51, 70, 82, 6, 36, 63, 37, 55, 37, 57, 6, 35, 51, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 8, 147, 0, 72, 0, 0, 0, 13, 4, 95, 4, 16, 20, 10, 115, 36, 55, 37, 105, 0, 0, 0, 0, 0, 22, 4, 95, 51, 77, 52, 47, 51, 6, 37, 57, 36, 69, 37, 55, 37, 57, 6, 39, 50, 37, 0, 0, 0, 0, 0, 0, 0, 22, 4, 95, 51, 77, 50, 47, 51, 6, 37, 57, 36, 63, 37, 55, 37, 57, 6, 39, 50, 37, 0, 0, 21, 4, 95, 51, 77, 51, 47, 51, 6, 37, 63, 37, 55, 37, 57, 6, 35, 51, 70, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 51, 88, 47, 51, 6, 37, 70, 36, 87, 36, 47, 0, 0, 9, 3, 95, 48, 67, 87, 47, 39, 0, 0, 0, 0, 6, 195, 77, 64, 64, 72, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 77, 65, 64, 72, 0, 0, 0, 5, 194, 40, 80, 72, 17, 3, 95, 49, 57, 70, 6, 36, 82, 36, 47, 50, 35, 57, 87, 47, 0, 0, 16, 3, 95, 49, 56, 6, 39, 87, 36, 63, 50, 35, 57, 87, 47, 0, 0, 13, 3, 95, 50, 67, 70, 82, 6, 36, 87, 47, 39, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 49, 49, 6, 36, 6, 50, 35, 57, 87, 47, 0, 0, 12, 3, 95, 49, 48, 70, 6, 36, 87, 36, 47, 0, 0, 15, 3, 95, 49, 51, 47, 51, 6, 37, 50, 35, 57, 87, 47, 0, 0, 15, 3, 95, 49, 50, 70, 82, 6, 35, 50, 35, 57, 87, 47, 0, 0, 15, 3, 95, 49, 53, 48, 6, 36, 47, 50, 35, 57, 87, 47, 0, 0, 17, 3, 95, 49, 52, 89, 47, 6, 37, 51, 37, 50, 35, 57, 87, 47, 0, 0, 17, 3, 95, 49, 55, 87, 6, 36, 70, 36, 63, 50, 35, 57, 87, 47, 0, 0, 16, 3, 95, 49, 54, 89, 6, 36, 87, 47, 50, 35, 57, 87, 47, 0, 0, 0, 17, 3, 95, 55, 88, 87, 6, 36, 70, 36, 63, 70, 36, 87, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 50, 88, 70, 82, 6, 35, 57, 87, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 52, 88, 89, 47, 6, 37, 51, 37, 70, 36, 87, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 53, 88, 48, 6, 36, 47, 70, 36, 87, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 54, 88, 89, 6, 36, 87, 47, 70, 36, 87, 36, 47, 0, 0, 0, 0, 0, 6, 195, 76, 83, 64, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 56, 88, 6, 39, 87, 36, 63, 70, 36, 87, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 57, 88, 70, 6, 36, 82, 36, 47, 70, 36, 87, 36, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 48, 77, 52, 69, 37, 55, 37, 57, 6, 39, 50, 39, 58, 0, 0, 0, 17, 4, 95, 48, 77, 50, 63, 37, 55, 37, 57, 6, 39, 50, 39, 58, 0, 0, 16, 4, 95, 48, 77, 51, 63, 37, 55, 37, 57, 6, 35, 51, 70, 0, 0, 0, 13, 4, 95, 48, 77, 49, 47, 6, 37, 87, 39, 74, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 76, 211, 192, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 77, 96, 64, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 8, 147, 1, 72, 0, 14, 2, 196, 135, 63, 6, 36, 105, 49, 37, 74, 4, 13, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 8, 147, 9, 72, 0, 0, 0, 7, 2, 196, 141, 74, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 2, 196, 145, 63, 6, 36, 105, 49, 37, 73, 4, 13, 0, 0, 0, 0, 5, 130, 195, 164, 43, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 130, 195, 171, 43, 0, 0, 0, 5, 130, 195, 182, 43, 0, 0, 0, 0, 0, 0, 0, 7, 2, 197, 161, 89, 13, 0, 0, 0, 0, 5, 130, 195, 188, 43, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 197, 190, 88, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 144, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 95, 11, 49, 13, 0, 0, 0, 0, 0, 6, 2, 95, 15, 39, 0, 0, 0, 0, 0, 7, 2, 95, 19, 87, 13, 0, 0, 0, 0, 0, 0, 7, 2, 95, 22, 82, 13, 0, 0, 0, 0, 0, 7, 2, 95, 26, 86, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 24, 4, 95, 52, 77, 52, 89, 47, 6, 37, 51, 37, 57, 36, 69, 37, 55, 37, 57, 6, 39, 50, 37, 0, 0, 23, 4, 95, 52, 77, 51, 89, 47, 6, 37, 51, 37, 63, 37, 55, 37, 57, 6, 35, 51, 70, 36, 0, 0, 24, 4, 95, 52, 77, 50, 89, 47, 6, 37, 51, 37, 57, 36, 63, 37, 55, 37, 57, 6, 39, 50, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 2, 95, 51, 47, 51, 6, 37, 0, 0, 9, 2, 95, 50, 70, 82, 6, 35, 0, 0, 9, 2, 95, 49, 6, 36, 50, 35, 0, 0, 9, 2, 95, 48, 50, 6, 37, 74, 0, 0, 11, 2, 95, 55, 87, 6, 36, 70, 36, 63, 0, 0, 10, 2, 95, 54, 89, 6, 36, 87, 47, 0, 0, 9, 2, 95, 53, 48, 6, 36, 47, 0, 0, 11, 2, 95, 52, 89, 47, 6, 37, 51, 37, 0, 0, 0, 0, 11, 2, 95, 57, 70, 6, 36, 82, 36, 47, 0, 0, 10, 2, 95, 56, 6, 39, 87, 36, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 240, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 4, 9, 1, 6, 40, 63, 55, 35, 58, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 197, 190, 0, 98, 0, 100, 0, 103, 0, 106, 0, 108, 0, 109, 0, 110, 0, 118, 0, 122, 0, 7, 6, 196, 141, 0, 3, 74, 0, 7, 6, 197, 161, 0, 3, 89, 0, 7, 6, 197, 190, 0, 3, 88, 0, 7, 6, 97, 0, 3, 35, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 115, 0, 7, 6, 100, 0, 3, 70, 0, 197, 190, 3, 73, 0, 122, 3, 116, 0, 7, 6, 101, 0, 3, 36, 0, 2, 32, 3, 107, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 3, 79, 0, 7, 6, 104, 0, 3, 99, 0, 4, 1, 105, 3, 105, 0, 2, 17, 69, 0, 7, 6, 105, 0, 3, 37, 0, 4, 2, 17, 65, 3, 57, 0, 2, 114, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 1, 25, 2, 25, 3, 13, 55, 0, 3, 55, 0, 106, 2, 17, 65, 3, 55, 57, 0, 2, 25, 3, 58, 0, 4, 106, 3, 61, 0, 106, 2, 105, 0, 7, 6, 109, 0, 1, 25, 2, 25, 3, 2, 13, 63, 0, 3, 63, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 7, 6, 110, 0, 1, 25, 2, 25, 3, 2, 13, 50, 0, 3, 50, 0, 106, 2, 17, 65, 3, 50, 57, 0, 4, 106, 3, 65, 0, 106, 2, 105, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 7, 6, 111, 0, 3, 39, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 117, 3, 49, 82, 0, 7, 6, 114, 0, 1, 25, 2, 25, 3, 13, 51, 0, 4, 3, 51, 0, 114, 0, 7, 6, 115, 0, 3, 87, 0, 7, 6, 116, 0, 3, 47, 0, 7, 6, 117, 0, 4, 3, 40, 0, 2, 114, 0, 4, 1, 17, 65, 2, 25, 3, 58, 0, 2, 17, 65, 0, 7, 6, 118, 0, 1, 25, 2, 25, 3, 2, 40, 0, 4, 1, 17, 65, 2, 25, 3, 58, 0, 1, 18, 66, 2, 17, 65, 0, 4, 3, 82, 0, 2, 45, 17, 65, 12, 0, 7, 6, 119, 0, 1, 17, 65, 2, 25, 3, 58, 0, 3, 82, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 1, 25, 2, 25, 3, 37, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 195, 170, 3, 6, 107, 12, 0, 195, 180, 3, 6, 109, 12, 0, 195, 173, 3, 6, 119, 0, 195, 169, 3, 6, 121, 0, 195, 161, 3, 6, 122, 0, 195, 179, 3, 6, 123, 0, 195, 186, 3, 6, 124, 0, 195, 182, 3, 13, 12, 0, 195, 159, 3, 21, 100, 101, 0, 36, 3, 70, 6, 39, 55, 35, 51, 0, 196, 145, 3, 73, 0, 196, 135, 3, 74, 0, 4, 195, 164, 3, 107, 0, 195, 168, 0, 195, 178, 3, 109, 0, 195, 188, 3, 110, 0, 197, 153, 3, 131, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts54 = FileInMemory_createWithData (2690, reinterpret_cast (&espeakdata_dicts54_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/sl_dict", L"sl"); Collection_addItem (me.peek(), espeakdata_dicts54.transfer()); static unsigned char espeakdata_dicts55_data[3215] = { 0, 4, 0, 0, 114, 9, 0, 0, 0, 0, 0, 0, 0, 9, 67, 53, 80, 74, 63, 40, 116, 0, 0, 0, 0, 0, 6, 65, 8, 69, 13, 0, 0, 0, 0, 0, 6, 65, 12, 123, 13, 0, 0, 0, 0, 0, 6, 65, 16, 70, 13, 0, 0, 0, 0, 0, 6, 65, 20, 36, 0, 14, 5, 193, 20, 76, 28, 0, 0, 0, 0, 6, 65, 24, 81, 13, 0, 0, 0, 0, 0, 6, 65, 28, 79, 13, 0, 0, 0, 0, 0, 6, 65, 32, 105, 13, 0, 0, 15, 1, 33, 48, 37, 49, 74, 40, 70, 6, 37, 123, 111, 0, 27, 0, 0, 7, 1, 35, 105, 35, 89, 0, 0, 17, 65, 36, 37, 10, 123, 6, 37, 121, 37, 0, 81, 99, 105, 108, 105, 32, 4, 193, 36, 76, 0, 13, 1, 37, 48, 13, 74, 37, 50, 70, 57, 35, 0, 27, 0, 7, 1, 38, 10, 84, 111, 0, 0, 0, 6, 65, 40, 57, 13, 0, 0, 0, 8, 1, 42, 114, 122, 37, 0, 27, 0, 9, 1, 43, 48, 122, 40, 87, 0, 27, 0, 6, 65, 44, 49, 13, 0, 0, 0, 8, 1, 46, 48, 37, 49, 0, 27, 0, 12, 1, 47, 48, 57, 6, 111, 87, 47, 37, 63, 0, 0, 6, 65, 48, 55, 13, 0, 0, 0, 0, 0, 6, 65, 52, 63, 13, 0, 0, 0, 0, 13, 68, 53, 80, 74, 36, 63, 6, 40, 116, 38, 37, 0, 0, 10, 5, 95, 48, 1, 14, 4, 2, 111, 0, 6, 65, 56, 50, 13, 0, 0, 0, 0, 0, 0, 13, 1, 61, 69, 35, 51, 35, 69, 6, 35, 51, 47, 0, 0, 0, 0, 9, 1, 64, 63, 35, 50, 49, 37, 0, 6, 65, 64, 48, 13, 0, 0, 0, 0, 0, 6, 65, 68, 78, 13, 0, 0, 0, 0, 0, 6, 65, 72, 51, 13, 0, 0, 0, 7, 195, 16, 129, 64, 76, 8, 0, 0, 6, 65, 76, 87, 13, 0, 0, 0, 0, 0, 6, 65, 80, 47, 13, 0, 0, 0, 0, 0, 4, 193, 84, 76, 0, 0, 0, 0, 6, 65, 88, 82, 13, 0, 0, 0, 0, 8, 133, 10, 1, 14, 195, 171, 76, 0, 6, 65, 92, 58, 13, 0, 0, 9, 133, 14, 195, 171, 19, 5, 76, 8, 0, 16, 1, 94, 87, 6, 37, 51, 49, 40, 63, 81, 122, 111, 49, 87, 0, 0, 0, 6, 65, 96, 124, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 104, 86, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 1, 126, 47, 37, 55, 70, 109, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 4, 16, 20, 10, 48, 51, 6, 36, 87, 57, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 95, 35, 57, 47, 35, 69, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 16, 128, 84, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 61, 49, 64, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 226, 130, 172, 111, 40, 51, 115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 44, 16, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 28, 160, 75, 13, 0, 0, 16, 3, 95, 51, 88, 47, 51, 6, 37, 84, 57, 36, 47, 2, 106, 0, 0, 11, 3, 95, 48, 67, 78, 4, 37, 50, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 16, 195, 171, 18, 76, 20, 3, 95, 49, 57, 50, 6, 107, 50, 47, 13, 63, 69, 106, 84, 57, 36, 47, 106, 0, 0, 19, 3, 95, 49, 56, 47, 6, 111, 47, 13, 63, 69, 106, 84, 57, 36, 47, 106, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 49, 49, 65, 6, 108, 63, 69, 106, 84, 57, 36, 47, 106, 0, 0, 12, 3, 95, 49, 48, 84, 57, 6, 111, 47, 106, 0, 0, 18, 3, 95, 49, 51, 47, 51, 6, 111, 63, 69, 106, 84, 57, 36, 47, 106, 0, 0, 17, 3, 95, 49, 50, 70, 6, 114, 63, 69, 106, 84, 57, 36, 47, 106, 0, 0, 19, 3, 95, 49, 53, 48, 6, 111, 87, 13, 63, 69, 106, 84, 57, 36, 47, 106, 0, 0, 20, 3, 95, 49, 52, 49, 6, 35, 47, 13, 34, 63, 69, 106, 84, 57, 36, 47, 106, 0, 0, 20, 3, 95, 49, 55, 89, 47, 6, 35, 47, 13, 63, 69, 106, 84, 57, 36, 47, 106, 0, 0, 20, 3, 95, 49, 54, 75, 6, 35, 89, 47, 13, 63, 69, 106, 84, 57, 36, 47, 106, 0, 0, 0, 18, 3, 95, 55, 88, 89, 47, 6, 35, 47, 106, 84, 57, 36, 47, 2, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 88, 65, 6, 108, 86, 111, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 56, 112, 64, 76, 0, 0, 0, 0, 0, 13, 3, 95, 63, 63, 89, 49, 51, 6, 115, 65, 35, 0, 0, 0, 0, 12, 3, 95, 52, 88, 70, 6, 114, 86, 111, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 53, 88, 48, 6, 111, 87, 106, 84, 57, 36, 47, 2, 106, 0, 0, 0, 0, 10, 135, 11, 195, 171, 19, 8, 20, 21, 66, 0, 0, 0, 0, 0, 18, 3, 95, 54, 88, 75, 6, 35, 89, 47, 106, 84, 57, 36, 47, 2, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 56, 88, 47, 6, 111, 47, 106, 84, 57, 36, 47, 2, 106, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 52, 80, 76, 0, 18, 3, 95, 57, 88, 50, 6, 107, 50, 47, 106, 84, 57, 36, 47, 2, 106, 0, 0, 6, 131, 13, 195, 171, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 48, 77, 50, 63, 37, 121, 37, 6, 115, 50, 0, 0, 15, 4, 95, 48, 77, 51, 63, 37, 121, 37, 6, 35, 34, 70, 0, 0, 0, 12, 4, 95, 48, 77, 49, 63, 4, 37, 57, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 14, 195, 171, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 48, 192, 122, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 135, 13, 9, 18, 195, 171, 16, 15, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 56, 160, 65, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 66, 73, 32, 51, 52, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 66, 76, 16, 87, 35, 63, 63, 0, 81, 109, 195, 171, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 76, 80, 76, 0, 0, 8, 196, 76, 146, 213, 72, 76, 8, 0, 0, 0, 0, 0, 7, 2, 195, 167, 74, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 76, 128, 89, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 17, 195, 171, 76, 6, 194, 76, 144, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 1, 35, 0, 0, 0, 0, 0, 6, 2, 95, 5, 36, 0, 0, 0, 0, 6, 2, 95, 9, 37, 0, 0, 7, 66, 80, 128, 85, 13, 0, 0, 6, 2, 95, 15, 115, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 81, 80, 74, 47, 40, 116, 0, 6, 2, 95, 21, 40, 0, 0, 0, 0, 0, 6, 2, 95, 25, 114, 0, 0, 0, 0, 0, 0, 0, 0, 13, 2, 95, 34, 35, 48, 115, 87, 47, 51, 115, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 3, 1, 16, 10, 111, 63, 6, 35, 84, 111, 0, 0, 27, 2, 95, 41, 49, 122, 6, 35, 48, 35, 111, 15, 82, 6, 115, 79, 13, 55, 111, 15, 70, 57, 6, 35, 85, 47, 0, 0, 19, 2, 95, 40, 49, 122, 6, 35, 48, 35, 111, 15, 82, 6, 115, 79, 13, 55, 0, 0, 0, 0, 11, 2, 95, 45, 63, 6, 37, 50, 40, 87, 0, 0, 11, 2, 95, 44, 48, 51, 36, 87, 57, 109, 0, 0, 9, 2, 95, 51, 47, 51, 6, 111, 0, 0, 8, 2, 95, 50, 70, 6, 114, 0, 0, 8, 2, 95, 49, 65, 6, 108, 0, 0, 10, 2, 95, 48, 86, 6, 111, 67, 115, 0, 0, 11, 2, 95, 55, 89, 47, 6, 35, 47, 106, 0, 0, 11, 2, 95, 54, 75, 6, 35, 89, 47, 106, 0, 0, 10, 2, 95, 53, 48, 6, 111, 87, 106, 0, 0, 11, 2, 95, 52, 49, 6, 35, 47, 13, 51, 0, 0, 14, 2, 95, 59, 48, 37, 49, 48, 51, 36, 87, 57, 109, 0, 0, 12, 2, 95, 58, 70, 114, 15, 48, 37, 49, 109, 0, 0, 11, 2, 95, 57, 50, 6, 107, 50, 47, 106, 0, 0, 10, 2, 95, 56, 47, 6, 111, 47, 106, 0, 0, 13, 2, 95, 63, 48, 37, 49, 48, 114, 47, 57, 111, 0, 0, 14, 2, 95, 62, 63, 6, 13, 111, 63, 6, 35, 84, 111, 0, 0, 0, 16, 2, 95, 60, 63, 6, 13, 111, 15, 82, 4, 115, 79, 111, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 2, 95, 91, 49, 122, 6, 35, 48, 35, 111, 15, 63, 6, 35, 84, 111, 0, 0, 0, 0, 0, 14, 2, 95, 95, 50, 4, 107, 50, 15, 82, 6, 37, 86, 0, 0, 0, 26, 2, 95, 93, 49, 122, 6, 35, 48, 35, 111, 15, 63, 6, 35, 84, 111, 111, 15, 70, 57, 6, 35, 85, 47, 0, 0, 17, 2, 95, 92, 82, 37, 86, 111, 63, 116, 47, 85, 6, 119, 87, 111, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 2, 95, 123, 49, 122, 6, 35, 48, 35, 111, 15, 63, 6, 111, 87, 63, 111, 0, 0, 6, 131, 19, 195, 171, 76, 0, 0, 0, 0, 0, 27, 2, 95, 125, 49, 122, 6, 35, 48, 35, 111, 15, 63, 6, 111, 87, 63, 111, 111, 15, 70, 57, 6, 35, 85, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 96, 128, 73, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 4, 95, 35, 51, 50, 87, 48, 117, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 12, 147, 1, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 12, 147, 9, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 20, 195, 171, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 104, 128, 88, 13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 18, 67, 103, 106, 0, 120, 104, 0, 98, 0, 100, 0, 103, 0, 7, 6, 18, 68, 100, 104, 0, 103, 106, 0, 108, 108, 0, 110, 106, 0, 114, 114, 0, 115, 104, 0, 116, 104, 0, 120, 104, 0, 122, 104, 0, 7, 6, 195, 167, 0, 3, 74, 0, 7, 6, 195, 171, 0, 1, 21, 2, 29, 3, 2, 107, 0, 116, 97, 1, 21, 2, 32, 3, 8, 13, 47, 35, 0, 118, 105, 1, 21, 2, 32, 3, 8, 13, 82, 37, 0, 118, 101, 1, 21, 2, 32, 3, 8, 13, 82, 111, 0, 115, 105, 1, 21, 2, 32, 3, 8, 13, 87, 37, 0, 115, 101, 1, 21, 2, 32, 3, 8, 13, 87, 111, 0, 115, 105, 115, 104, 116, 1, 21, 2, 32, 3, 8, 87, 113, 89, 47, 0, 4, 1, 17, 67, 17, 65, 2, 32, 3, 106, 0, 1, 17, 67, 106, 17, 65, 2, 32, 0, 1, 17, 67, 114, 17, 65, 2, 32, 0, 1, 18, 68, 17, 65, 2, 32, 0, 1, 116, 104, 17, 65, 2, 32, 0, 1, 116, 115, 17, 65, 2, 32, 0, 3, 107, 0, 1, 94, 110, 3, 108, 0, 7, 6, 97, 0, 116, 1, 21, 2, 32, 3, 8, 35, 47, 0, 110, 105, 1, 21, 2, 113, 32, 3, 8, 35, 50, 37, 0, 114, 195, 171, 118, 101, 1, 21, 2, 32, 3, 8, 35, 51, 13, 82, 111, 0, 118, 101, 1, 21, 2, 32, 3, 8, 35, 82, 111, 0, 3, 35, 0, 4, 2, 32, 3, 110, 0, 2, 114, 25, 0, 106, 3, 116, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 123, 0, 7, 6, 100, 0, 3, 70, 0, 104, 3, 84, 0, 7, 6, 101, 0, 116, 1, 21, 2, 32, 3, 8, 111, 47, 0, 110, 1, 21, 2, 32, 3, 8, 111, 50, 0, 118, 105, 1, 21, 2, 113, 32, 3, 8, 111, 82, 37, 0, 118, 101, 1, 21, 2, 32, 3, 8, 111, 82, 111, 0, 115, 1, 21, 2, 32, 3, 8, 111, 87, 0, 4, 1, 94, 110, 3, 36, 0, 1, 104, 115, 0, 1, 106, 0, 1, 108, 0, 1, 113, 0, 2, 106, 0, 2, 115, 104, 0, 2, 115, 106, 0, 4, 3, 111, 0, 1, 108, 108, 0, 106, 2, 25, 3, 117, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 106, 3, 75, 0, 3, 79, 0, 7, 6, 104, 0, 3, 105, 0, 2, 25, 3, 105, 105, 0, 7, 6, 105, 0, 4, 1, 99, 105, 21, 2, 32, 3, 6, 37, 0, 1, 114, 171, 195, 21, 2, 32, 0, 2, 117, 110, 32, 0, 1, 21, 2, 113, 32, 3, 8, 37, 0, 109, 1, 21, 2, 32, 3, 8, 37, 63, 0, 1, 21, 2, 116, 32, 3, 8, 113, 0, 110, 1, 21, 2, 32, 3, 8, 113, 50, 0, 3, 37, 0, 106, 2, 25, 3, 37, 12, 0, 101, 3, 57, 36, 0, 7, 6, 106, 0, 3, 57, 0, 7, 6, 107, 0, 3, 49, 0, 7, 6, 108, 0, 3, 121, 0, 108, 3, 122, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 106, 3, 65, 0, 7, 6, 111, 0, 118, 105, 2, 113, 32, 3, 8, 115, 82, 37, 0, 3, 115, 0, 4, 105, 2, 108, 32, 3, 118, 0, 106, 2, 25, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 78, 0, 7, 6, 114, 0, 114, 8, 3, 13, 52, 0, 114, 101, 8, 2, 103, 117, 108, 108, 97, 3, 13, 52, 6, 36, 0, 4, 3, 51, 0, 2, 25, 0, 114, 3, 51, 52, 0, 7, 6, 115, 0, 3, 87, 0, 104, 3, 89, 0, 7, 6, 116, 0, 3, 47, 0, 104, 3, 85, 0, 7, 6, 117, 0, 4, 1, 116, 2, 97, 110, 32, 3, 6, 40, 0, 2, 97, 114, 32, 0, 2, 97, 114, 97, 32, 0, 2, 101, 115, 118, 101, 32, 0, 4, 1, 21, 2, 110, 32, 3, 8, 40, 0, 1, 21, 2, 114, 32, 0, 3, 40, 0, 2, 97, 106, 25, 3, 58, 0, 97, 3, 58, 110, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 2, 32, 3, 49, 87, 0, 104, 3, 73, 0, 3, 124, 0, 7, 6, 121, 0, 3, 114, 0, 101, 3, 119, 0, 7, 6, 122, 0, 3, 86, 0, 104, 3, 88, 0, 7, 6, 0, 36, 3, 70, 115, 122, 35, 34, 37, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts55 = FileInMemory_createWithData (3214, reinterpret_cast (&espeakdata_dicts55_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/sq_dict", L"sq"); Collection_addItem (me.peek(), espeakdata_dicts55.transfer()); static unsigned char espeakdata_dicts56_data[9702] = { 0, 4, 0, 0, 211, 17, 0, 0, 10, 69, 25, 32, 77, 21, 48, 21, 0, 10, 0, 0, 11, 70, 32, 80, 68, 36, 225, 211, 21, 0, 10, 0, 9, 67, 52, 83, 128, 63, 109, 50, 0, 10, 67, 32, 243, 128, 105, 123, 50, 0, 72, 0, 0, 5, 65, 4, 120, 0, 0, 0, 0, 0, 6, 65, 8, 69, 108, 0, 0, 11, 70, 9, 35, 215, 76, 84, 128, 21, 0, 10, 0, 18, 70, 28, 83, 69, 57, 48, 77, 57, 109, 63, 6, 108, 50, 87, 35, 63, 0, 12, 67, 21, 64, 192, 108, 47, 108, 87, 6, 108, 0, 0, 0, 6, 65, 12, 87, 108, 0, 0, 0, 12, 4, 95, 8, 1, 3, 105, 6, 120, 49, 110, 0, 0, 0, 6, 65, 16, 70, 108, 0, 0, 0, 10, 67, 76, 147, 128, 87, 107, 50, 0, 76, 0, 6, 195, 76, 147, 129, 76, 0, 5, 65, 20, 108, 0, 0, 0, 0, 0, 6, 65, 24, 109, 81, 0, 0, 0, 0, 0, 6, 65, 28, 79, 108, 0, 0, 0, 11, 67, 44, 19, 128, 49, 6, 35, 50, 0, 72, 0, 0, 6, 65, 32, 105, 122, 0, 0, 0, 0, 0, 7, 65, 36, 106, 0, 72, 28, 5, 65, 36, 106, 0, 0, 0, 0, 0, 6, 65, 40, 57, 106, 0, 0, 0, 0, 0, 6, 65, 44, 49, 122, 0, 0, 0, 0, 0, 6, 65, 48, 109, 55, 0, 0, 15, 1, 49, 81, 6, 117, 91, 47, 110, 0, 82, 58, 32, 101, 32, 15, 1, 49, 81, 6, 117, 91, 47, 35, 0, 82, 58, 32, 97, 32, 0, 14, 1, 50, 35, 50, 70, 51, 35, 0, 82, 58, 32, 97, 32, 0, 15, 1, 51, 47, 51, 108, 70, 57, 110, 0, 82, 58, 32, 101, 32, 0, 15, 1, 52, 81, 57, 111, 51, 70, 110, 0, 82, 58, 32, 101, 32, 6, 65, 52, 109, 63, 0, 0, 14, 1, 53, 81, 109, 63, 47, 110, 0, 82, 58, 32, 101, 32, 0, 14, 1, 54, 125, 109, 47, 12, 110, 0, 82, 58, 32, 101, 32, 0, 14, 1, 55, 125, 118, 50, 70, 110, 0, 82, 58, 32, 101, 32, 0, 15, 69, 81, 33, 68, 40, 80, 47, 51, 6, 108, 70, 57, 110, 0, 16, 1, 56, 121, 47, 12, 121, 50, 70, 110, 0, 82, 58, 32, 101, 32, 6, 65, 56, 109, 50, 0, 0, 15, 1, 57, 50, 106, 121, 50, 70, 110, 0, 82, 58, 32, 101, 32, 0, 0, 0, 0, 0, 0, 0, 6, 65, 64, 48, 108, 0, 0, 11, 70, 64, 20, 211, 92, 244, 132, 21, 0, 10, 0, 9, 67, 76, 145, 192, 87, 109, 57, 0, 0, 0, 6, 65, 68, 49, 115, 0, 0, 8, 67, 80, 130, 83, 21, 0, 10, 0, 0, 0, 6, 65, 72, 109, 51, 0, 0, 11, 70, 52, 246, 137, 48, 192, 64, 21, 0, 10, 0, 0, 0, 6, 65, 76, 109, 87, 0, 0, 0, 10, 67, 48, 241, 192, 55, 6, 124, 79, 0, 0, 0, 6, 65, 80, 47, 108, 0, 0, 0, 0, 0, 0, 0, 0, 9, 68, 80, 16, 140, 20, 21, 0, 10, 9, 68, 48, 147, 139, 76, 21, 0, 10, 0, 14, 69, 8, 20, 143, 12, 176, 69, 35, 51, 6, 121, 49, 0, 6, 65, 88, 82, 108, 0, 0, 0, 0, 0, 12, 65, 92, 70, 6, 118, 69, 13, 55, 82, 108, 0, 0, 0, 0, 0, 7, 65, 96, 109, 49, 87, 0, 0, 14, 4, 95, 49, 77, 50, 63, 107, 55, 57, 6, 124, 50, 0, 0, 14, 4, 95, 49, 77, 51, 69, 107, 55, 57, 6, 124, 50, 0, 0, 21, 72, 80, 244, 147, 16, 17, 197, 57, 48, 47, 6, 124, 89, 70, 120, 79, 109, 50, 87, 0, 0, 5, 65, 100, 113, 0, 0, 16, 70, 77, 84, 193, 56, 224, 64, 87, 118, 87, 6, 35, 50, 35, 0, 0, 0, 0, 9, 65, 104, 87, 6, 111, 47, 35, 0, 0, 0, 11, 67, 20, 211, 212, 109, 63, 6, 124, 47, 0, 0, 0, 0, 15, 70, 77, 84, 193, 56, 225, 64, 87, 118, 87, 6, 35, 50, 0, 9, 198, 9, 37, 75, 4, 65, 64, 72, 0, 7, 195, 5, 69, 0, 72, 8, 0, 0, 0, 16, 70, 80, 244, 147, 16, 17, 192, 47, 6, 124, 89, 70, 120, 79, 0, 11, 66, 12, 16, 87, 6, 107, 51, 49, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 6, 14, 195, 165, 7, 18, 1, 50, 6, 122, 79, 51, 35, 0, 72, 0, 9, 68, 25, 32, 77, 20, 21, 0, 10, 0, 14, 69, 8, 245, 20, 20, 224, 69, 6, 121, 47, 109, 50, 0, 0, 0, 20, 71, 28, 83, 69, 57, 48, 77, 80, 57, 109, 63, 6, 108, 50, 87, 35, 63, 47, 0, 0, 0, 0, 11, 67, 80, 241, 211, 47, 6, 124, 79, 87, 0, 0, 0, 0, 0, 0, 0, 12, 68, 17, 81, 197, 72, 70, 115, 79, 109, 51, 0, 0, 0, 8, 66, 5, 96, 120, 82, 0, 72, 5, 194, 5, 96, 72, 0, 0, 0, 0, 0, 0, 11, 67, 32, 17, 5, 105, 35, 70, 109, 0, 72, 0, 0, 0, 0, 7, 196, 84, 225, 5, 72, 28, 0, 0, 0, 9, 67, 8, 85, 0, 69, 108, 47, 0, 7, 195, 80, 147, 12, 72, 28, 0, 12, 68, 4, 225, 1, 76, 35, 50, 70, 35, 87, 0, 0, 0, 0, 10, 67, 29, 33, 80, 79, 51, 108, 48, 0, 0, 0, 10, 69, 9, 85, 20, 60, 224, 21, 0, 10, 0, 0, 0, 9, 67, 4, 227, 133, 35, 50, 50, 0, 0, 0, 0, 0, 12, 68, 77, 67, 210, 80, 87, 47, 124, 51, 47, 0, 12, 68, 76, 17, 5, 76, 87, 120, 70, 109, 87, 0, 0, 17, 70, 80, 244, 147, 16, 17, 211, 47, 6, 124, 89, 70, 35, 79, 87, 0, 0, 0, 0, 14, 5, 21, 19, 1, 58, 19, 115, 109, 87, 6, 120, 87, 0, 13, 68, 72, 17, 5, 56, 51, 120, 70, 2, 109, 50, 0, 0, 0, 0, 0, 0, 10, 69, 72, 80, 68, 21, 32, 21, 0, 10, 0, 0, 0, 12, 68, 32, 243, 143, 52, 105, 121, 50, 121, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 52, 81, 1, 56, 8, 0, 0, 0, 0, 0, 0, 0, 6, 195, 16, 149, 20, 76, 0, 0, 0, 0, 8, 67, 72, 80, 68, 21, 0, 10, 10, 67, 76, 176, 64, 87, 49, 120, 0, 72, 10, 67, 76, 176, 64, 87, 49, 120, 0, 72, 0, 0, 0, 0, 0, 10, 67, 36, 227, 205, 107, 50, 121, 63, 0, 0, 10, 67, 20, 113, 78, 108, 79, 109, 50, 0, 0, 5, 194, 21, 32, 76, 0, 0, 0, 0, 0, 10, 67, 21, 37, 0, 108, 51, 47, 0, 76, 0, 10, 67, 4, 225, 197, 35, 50, 57, 108, 0, 7, 196, 28, 83, 143, 52, 28, 0, 0, 5, 194, 16, 80, 72, 0, 0, 7, 196, 88, 147, 12, 20, 72, 0, 0, 0, 10, 67, 16, 85, 0, 70, 108, 47, 0, 72, 0, 13, 68, 72, 17, 5, 72, 51, 120, 70, 2, 109, 51, 0, 13, 4, 95, 4, 16, 20, 48, 6, 118, 66, 49, 47, 0, 0, 0, 5, 194, 17, 80, 72, 0, 9, 67, 88, 83, 64, 82, 109, 63, 0, 9, 67, 24, 83, 64, 81, 109, 63, 0, 0, 0, 0, 17, 70, 65, 35, 199, 72, 19, 64, 48, 51, 123, 79, 51, 6, 35, 63, 0, 0, 8, 133, 195, 182, 22, 5, 18, 28, 0, 0, 0, 0, 16, 7, 6, 18, 1, 13, 195, 165, 20, 81, 51, 35, 63, 121, 47, 0, 0, 13, 4, 95, 20, 12, 4, 47, 6, 107, 55, 70, 110, 0, 9, 3, 95, 35, 57, 47, 35, 69, 0, 0, 0, 0, 0, 10, 67, 4, 228, 197, 35, 50, 87, 108, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 21, 69, 0, 6, 109, 47, 0, 6, 195, 21, 69, 0, 72, 0, 0, 8, 197, 9, 37, 75, 5, 32, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 61, 32, 193, 121, 51, 49, 35, 0, 0, 0, 8, 67, 48, 147, 139, 21, 0, 10, 0, 0, 0, 0, 7, 196, 36, 227, 129, 56, 28, 0, 0, 0, 0, 12, 68, 29, 33, 80, 76, 79, 51, 108, 48, 87, 0, 0, 0, 0, 0, 0, 0, 7, 66, 32, 16, 105, 120, 0, 0, 0, 0, 0, 0, 0, 11, 70, 12, 129, 67, 44, 81, 0, 21, 0, 10, 0, 14, 69, 25, 32, 77, 52, 80, 81, 51, 6, 35, 63, 109, 0, 0, 10, 67, 20, 115, 129, 108, 79, 50, 35, 0, 6, 195, 16, 147, 129, 76, 0, 10, 67, 16, 147, 128, 70, 107, 50, 0, 76, 10, 67, 32, 19, 128, 105, 35, 50, 0, 72, 0, 0, 0, 0, 9, 67, 16, 19, 128, 70, 120, 50, 0, 0, 0, 0, 0, 9, 67, 64, 20, 128, 48, 120, 51, 0, 10, 67, 32, 20, 128, 105, 120, 51, 0, 72, 6, 195, 32, 20, 128, 72, 0, 8, 196, 20, 195, 5, 72, 72, 8, 0, 11, 70, 76, 241, 148, 92, 20, 133, 21, 0, 10, 10, 69, 12, 19, 131, 20, 192, 21, 0, 10, 0, 0, 9, 67, 80, 20, 128, 47, 120, 51, 0, 0, 0, 0, 0, 0, 6, 195, 32, 19, 147, 76, 0, 0, 0, 0, 0, 16, 69, 8, 85, 1, 49, 64, 69, 6, 109, 47, 6, 120, 55, 47, 0, 0, 0, 0, 12, 68, 76, 243, 133, 56, 87, 122, 50, 109, 50, 0, 13, 68, 5, 34, 201, 88, 6, 35, 51, 49, 106, 82, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 6, 2, 195, 164, 19, 20, 5, 69, 6, 109, 87, 47, 109, 0, 0, 0, 0, 0, 0, 13, 67, 57, 97, 1, 109, 50, 82, 108, 70, 108, 120, 0, 0, 9, 67, 16, 145, 192, 70, 109, 57, 0, 0, 0, 0, 8, 67, 64, 17, 197, 21, 0, 10, 0, 0, 0, 0, 7, 66, 40, 16, 57, 120, 0, 0, 0, 0, 0, 0, 0, 14, 68, 8, 244, 132, 20, 69, 6, 124, 51, 70, 109, 0, 72, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 16, 17, 211, 70, 35, 49, 87, 0, 0, 8, 197, 32, 83, 142, 21, 48, 76, 0, 0, 8, 67, 32, 20, 192, 21, 0, 10, 0, 0, 14, 69, 77, 64, 68, 20, 224, 87, 47, 120, 70, 109, 50, 0, 0, 0, 9, 67, 80, 20, 192, 47, 120, 87, 0, 0, 13, 68, 16, 84, 129, 76, 70, 108, 51, 35, 87, 0, 76, 0, 0, 13, 4, 95, 13, 3, 14, 87, 47, 51, 6, 109, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 44, 192, 83, 49, 55, 120, 87, 0, 0, 8, 67, 16, 245, 0, 21, 0, 10, 10, 67, 44, 192, 82, 49, 55, 120, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 66, 20, 224, 109, 50, 0, 72, 0, 10, 67, 77, 64, 68, 87, 47, 120, 70, 0, 12, 3, 95, 51, 88, 47, 51, 6, 109, 47, 107, 0, 0, 13, 3, 95, 48, 67, 105, 6, 118, 50, 70, 51, 35, 0, 0, 0, 0, 9, 67, 17, 32, 64, 70, 51, 120, 0, 0, 0, 0, 0, 0, 0, 10, 67, 77, 64, 78, 87, 47, 120, 50, 0, 0, 0, 0, 0, 0, 12, 3, 95, 49, 57, 50, 6, 107, 47, 121, 50, 0, 0, 12, 3, 95, 49, 56, 6, 120, 51, 47, 121, 50, 0, 0, 0, 0, 0, 0, 10, 67, 17, 32, 83, 70, 51, 120, 87, 0, 0, 10, 67, 17, 32, 82, 70, 51, 120, 51, 0, 0, 11, 3, 95, 49, 49, 6, 109, 55, 82, 35, 0, 0, 11, 3, 95, 49, 48, 47, 6, 106, 38, 124, 0, 0, 9, 68, 48, 85, 133, 48, 21, 0, 10, 13, 3, 95, 49, 51, 47, 51, 6, 109, 47, 121, 50, 0, 0, 11, 3, 95, 49, 50, 47, 6, 121, 55, 82, 0, 0, 13, 3, 95, 49, 53, 81, 6, 109, 63, 47, 121, 50, 0, 0, 14, 3, 95, 49, 52, 81, 57, 6, 124, 51, 47, 121, 50, 0, 0, 12, 3, 95, 49, 55, 125, 6, 118, 47, 121, 50, 0, 0, 14, 3, 95, 49, 54, 87, 6, 109, 49, 87, 47, 121, 50, 0, 0, 0, 11, 3, 95, 55, 88, 125, 6, 118, 47, 107, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 20, 101, 5, 72, 28, 0, 9, 67, 52, 21, 0, 63, 120, 47, 0, 0, 0, 0, 0, 15, 2, 49, 49, 109, 55, 81, 47, 110, 0, 82, 58, 32, 101, 32, 0, 16, 2, 49, 48, 47, 106, 121, 50, 70, 110, 0, 82, 58, 32, 101, 32, 0, 11, 3, 95, 50, 88, 95, 6, 115, 79, 121, 0, 0, 16, 2, 49, 50, 47, 121, 55, 81, 47, 110, 0, 82, 58, 32, 101, 32, 0, 0, 8, 67, 81, 32, 89, 21, 0, 10, 0, 10, 67, 8, 245, 20, 69, 6, 123, 47, 0, 0, 0, 0, 0, 0, 0, 10, 69, 76, 52, 133, 20, 224, 21, 0, 10, 0, 0, 0, 15, 3, 95, 63, 63, 87, 6, 114, 63, 69, 124, 55, 110, 50, 0, 0, 0, 11, 70, 12, 243, 21, 52, 228, 192, 21, 0, 10, 0, 15, 5, 6, 18, 195, 165, 14, 81, 51, 6, 122, 50, 0, 72, 28, 12, 3, 95, 52, 88, 81, 6, 117, 51, 47, 107, 0, 0, 0, 9, 3, 195, 164, 14, 109, 50, 0, 72, 0, 0, 0, 0, 0, 0, 12, 3, 95, 53, 88, 81, 6, 109, 63, 47, 107, 0, 0, 0, 0, 0, 0, 0, 10, 69, 60, 97, 137, 12, 80, 21, 0, 10, 0, 0, 13, 3, 95, 54, 88, 87, 6, 109, 49, 87, 47, 107, 0, 0, 0, 0, 7, 132, 22, 195, 165, 18, 76, 0, 6, 195, 52, 149, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 67, 52, 18, 76, 21, 0, 10, 10, 3, 95, 56, 88, 6, 121, 47, 107, 0, 0, 0, 0, 0, 0, 0, 7, 195, 52, 81, 0, 72, 28, 0, 0, 11, 3, 95, 57, 88, 50, 6, 107, 47, 107, 0, 0, 0, 14, 69, 29, 34, 80, 56, 16, 79, 51, 106, 48, 50, 35, 0, 0, 0, 0, 0, 10, 3, 195, 164, 18, 6, 111, 51, 0, 72, 0, 16, 3, 95, 63, 65, 69, 6, 124, 49, 87, 47, 35, 82, 110, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 36, 224, 107, 50, 0, 0, 8, 67, 92, 80, 128, 21, 0, 10, 0, 0, 0, 0, 13, 4, 95, 15, 7, 15, 87, 82, 6, 35, 50, 87, 0, 0, 0, 15, 69, 76, 179, 204, 4, 224, 87, 49, 6, 124, 55, 35, 50, 0, 17, 7, 13, 195, 165, 19, 20, 5, 14, 63, 6, 121, 87, 47, 13, 50, 0, 0, 0, 12, 71, 52, 144, 210, 61, 51, 198, 80, 21, 0, 10, 10, 67, 76, 83, 148, 87, 108, 50, 47, 0, 0, 9, 68, 36, 208, 71, 20, 21, 0, 10, 0, 10, 67, 77, 67, 210, 87, 47, 124, 51, 0, 0, 0, 0, 11, 67, 60, 50, 0, 6, 121, 49, 0, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 52, 147, 128, 63, 107, 50, 0, 76, 0, 6, 195, 52, 147, 129, 76, 0, 0, 16, 4, 95, 48, 77, 50, 63, 107, 55, 57, 6, 124, 50, 109, 51, 0, 0, 9, 67, 61, 53, 0, 123, 87, 47, 0, 10, 67, 52, 19, 128, 63, 35, 50, 0, 72, 16, 4, 95, 48, 77, 51, 69, 107, 55, 57, 6, 124, 50, 109, 51, 0, 0, 0, 13, 4, 95, 48, 77, 49, 47, 6, 115, 87, 109, 50, 0, 0, 14, 4, 95, 2, 18, 22, 69, 51, 6, 108, 82, 106, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 67, 8, 244, 148, 69, 121, 51, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 66, 60, 96, 21, 0, 10, 7, 132, 2, 195, 182, 18, 72, 8, 132, 6, 195, 182, 18, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 52, 145, 192, 63, 109, 57, 0, 0, 0, 0, 0, 8, 67, 60, 225, 64, 21, 0, 10, 0, 0, 0, 11, 70, 77, 80, 141, 20, 229, 64, 21, 0, 10, 5, 194, 56, 144, 72, 0, 9, 67, 72, 17, 0, 51, 120, 70, 0, 0, 0, 11, 70, 16, 84, 203, 80, 244, 0, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 4, 95, 3, 9, 18, 87, 6, 107, 51, 49, 118, 63, 81, 55, 109, 49, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 8, 4, 195, 164, 18, 6, 195, 182, 18, 70, 6, 109, 51, 81, 116, 51, 0, 0, 0, 0, 0, 11, 70, 29, 32, 80, 32, 144, 192, 21, 0, 10, 0, 8, 67, 72, 245, 192, 21, 0, 10, 17, 4, 95, 19, 20, 11, 87, 50, 6, 108, 70, 87, 47, 51, 110, 49, 0, 0, 0, 12, 4, 95, 1, 3, 21, 6, 120, 49, 115, 47, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 4, 95, 18, 14, 7, 51, 6, 107, 66, 0, 0, 6, 131, 95, 195, 169, 43, 0, 11, 70, 29, 32, 80, 32, 144, 211, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 21, 32, 64, 76, 0, 0, 17, 7, 20, 25, 22, 195, 164, 18, 18, 47, 2, 114, 82, 6, 111, 51, 0, 11, 67, 21, 32, 78, 111, 51, 35, 50, 0, 76, 0, 0, 10, 67, 88, 19, 20, 82, 120, 55, 47, 0, 0, 0, 0, 18, 4, 95, 1, 3, 50, 70, 6, 118, 69, 110, 55, 6, 120, 49, 115, 47, 0, 0, 0, 0, 9, 134, 12, 195, 164, 14, 7, 19, 28, 0, 7, 66, 80, 16, 47, 120, 0, 0, 11, 67, 21, 32, 84, 111, 51, 35, 47, 0, 76, 0, 0, 10, 67, 45, 96, 82, 49, 82, 120, 51, 0, 0, 0, 6, 195, 88, 147, 12, 72, 7, 195, 52, 245, 0, 72, 28, 0, 0, 0, 8, 67, 72, 245, 211, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 69, 12, 243, 21, 52, 224, 21, 0, 10, 0, 0, 0, 10, 67, 32, 85, 1, 105, 108, 47, 35, 0, 0, 0, 0, 10, 67, 32, 83, 20, 105, 108, 55, 47, 0, 0, 0, 0, 7, 66, 56, 240, 21, 0, 10, 6, 194, 60, 208, 72, 8, 6, 194, 60, 208, 72, 28, 0, 0, 11, 67, 76, 86, 0, 87, 6, 109, 49, 87, 0, 12, 68, 4, 225, 197, 76, 35, 50, 57, 108, 87, 0, 0, 10, 67, 77, 96, 82, 87, 82, 120, 51, 0, 0, 0, 0, 12, 68, 4, 225, 197, 72, 35, 50, 57, 108, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 16, 195, 165, 72, 0, 0, 0, 0, 9, 68, 4, 67, 194, 20, 21, 0, 10, 0, 0, 0, 9, 67, 60, 229, 0, 123, 50, 47, 0, 0, 0, 0, 0, 0, 14, 4, 95, 3, 5, 4, 87, 6, 108, 70, 107, 55, 57, 0, 0, 0, 0, 16, 4, 95, 12, 9, 7, 55, 6, 106, 79, 35, 47, 4, 115, 51, 0, 0, 0, 0, 0, 10, 67, 88, 17, 0, 82, 120, 70, 0, 72, 0, 0, 0, 0, 0, 0, 0, 20, 8, 13, 15, 14, 5, 20, 195, 164, 18, 63, 4, 121, 50, 109, 47, 6, 111, 51, 0, 8, 133, 22, 195, 165, 18, 1, 76, 0, 7, 195, 76, 243, 64, 72, 8, 0, 8, 67, 56, 19, 69, 21, 0, 10, 0, 10, 69, 80, 16, 140, 21, 48, 21, 0, 10, 0, 0, 9, 67, 16, 83, 64, 70, 109, 63, 0, 0, 0, 14, 69, 4, 225, 18, 5, 48, 35, 50, 70, 51, 35, 87, 0, 0, 0, 0, 0, 8, 133, 22, 195, 165, 18, 20, 76, 0, 0, 0, 0, 0, 0, 0, 13, 72, 84, 228, 197, 48, 80, 212, 20, 64, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 45, 83, 132, 20, 72, 0, 0, 0, 0, 0, 0, 8, 67, 88, 145, 87, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 67, 85, 48, 64, 115, 109, 87, 6, 120, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 32, 82, 128, 105, 109, 57, 0, 0, 0, 8, 197, 76, 181, 76, 48, 80, 72, 0, 0, 0, 0, 0, 0, 9, 67, 76, 243, 128, 87, 122, 50, 0, 9, 67, 40, 19, 128, 57, 120, 50, 0, 0, 0, 0, 0, 10, 67, 16, 83, 128, 70, 109, 50, 0, 72, 0, 9, 68, 20, 208, 73, 48, 21, 0, 10, 13, 4, 95, 3, 1, 16, 87, 47, 6, 124, 51, 47, 0, 0, 0, 11, 67, 88, 20, 133, 82, 120, 51, 109, 0, 72, 0, 8, 67, 92, 244, 132, 21, 0, 10, 9, 67, 64, 84, 128, 48, 111, 51, 0, 0, 11, 2, 95, 46, 48, 6, 118, 66, 49, 47, 0, 0, 0, 0, 10, 67, 88, 20, 128, 82, 120, 51, 0, 72, 9, 67, 24, 20, 128, 81, 120, 51, 0, 10, 67, 88, 20, 128, 82, 120, 51, 0, 72, 9, 2, 95, 51, 47, 51, 6, 108, 0, 0, 9, 2, 95, 50, 47, 82, 6, 122, 0, 0, 8, 2, 95, 49, 6, 109, 47, 0, 0, 9, 2, 95, 48, 50, 6, 121, 55, 0, 0, 8, 2, 95, 55, 125, 6, 115, 0, 0, 10, 2, 95, 54, 87, 6, 109, 49, 87, 0, 0, 9, 2, 95, 53, 81, 6, 109, 63, 0, 0, 10, 2, 95, 52, 81, 6, 113, 51, 35, 0, 0, 0, 0, 9, 2, 95, 57, 50, 6, 106, 124, 0, 0, 9, 2, 95, 56, 6, 121, 47, 35, 0, 0, 0, 12, 67, 85, 48, 83, 115, 109, 87, 6, 120, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 67, 85, 49, 82, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 11, 67, 36, 64, 71, 107, 70, 4, 120, 79, 0, 0, 15, 6, 13, 195, 165, 19, 20, 5, 63, 6, 121, 87, 47, 13, 0, 0, 0, 0, 0, 0, 0, 10, 67, 40, 17, 192, 57, 120, 79, 0, 72, 0, 13, 4, 95, 4, 15, 20, 48, 6, 118, 66, 49, 47, 0, 0, 0, 0, 0, 0, 7, 195, 88, 145, 0, 72, 28, 0, 5, 194, 88, 144, 72, 0, 0, 0, 10, 69, 60, 227, 9, 56, 80, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 7, 18, 22, 79, 51, 6, 120, 82, 0, 0, 8, 67, 20, 66, 84, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 4, 9, 1, 6, 121, 63, 57, 115, 70, 0, 0, 0, 0, 0, 0, 12, 68, 4, 228, 197, 76, 35, 50, 87, 108, 87, 0, 6, 195, 16, 84, 211, 76, 0, 0, 0, 11, 70, 24, 148, 133, 24, 246, 0, 21, 0, 10, 0, 8, 67, 40, 21, 211, 21, 0, 10, 12, 68, 4, 228, 197, 72, 35, 50, 87, 108, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 67, 9, 32, 64, 69, 51, 120, 0, 0, 0, 0, 0, 19, 71, 80, 244, 147, 16, 17, 197, 56, 47, 6, 124, 89, 70, 120, 79, 109, 50, 0, 0, 0, 0, 11, 67, 25, 32, 77, 81, 51, 6, 35, 63, 0, 0, 0, 0, 0, 10, 67, 76, 17, 5, 87, 120, 70, 109, 0, 13, 4, 95, 35, 51, 50, 69, 55, 6, 35, 66, 49, 0, 0, 0, 0, 0, 16, 6, 14, 195, 165, 7, 15, 20, 50, 4, 122, 79, 121, 47, 0, 72, 0, 0, 0, 0, 0, 0, 16, 6, 14, 195, 165, 7, 15, 14, 50, 4, 122, 79, 121, 50, 0, 72, 0, 0, 0, 0, 11, 70, 21, 132, 12, 61, 33, 82, 21, 0, 10, 0, 0, 0, 0, 0, 0, 11, 70, 36, 229, 5, 72, 225, 84, 21, 0, 10, 0, 8, 67, 92, 149, 8, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 69, 28, 243, 199, 48, 80, 21, 0, 10, 0, 7, 131, 4, 195, 165, 72, 28, 0, 0, 0, 0, 0, 12, 71, 84, 224, 200, 20, 50, 197, 16, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 67, 80, 243, 84, 47, 6, 123, 63, 47, 0, 0, 0, 0, 11, 70, 32, 80, 68, 36, 225, 192, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 8, 67, 28, 18, 77, 21, 0, 10, 0, 12, 71, 52, 84, 211, 20, 225, 197, 72, 21, 0, 10, 10, 67, 80, 243, 64, 47, 6, 123, 63, 0, 6, 195, 76, 149, 20, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 70, 77, 64, 68, 20, 228, 192, 87, 47, 120, 70, 109, 50, 87, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 6, 1, 19, 20, 195, 164, 14, 8, 0, 11, 70, 48, 80, 86, 36, 225, 192, 21, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 164, 0, 4, 1, 102, 102, 3, 6, 111, 0, 1, 110, 111, 105, 2, 114, 0, 1, 116, 2, 114, 0, 114, 108, 2, 100, 3, 6, 111, 51, 0, 4, 1, 110, 2, 116, 116, 3, 109, 0, 1, 118, 2, 120, 0, 2, 17, 67, 17, 67, 0, 4, 3, 111, 0, 1, 98, 2, 114, 0, 1, 102, 2, 114, 100, 0, 1, 107, 115, 2, 114, 103, 0, 1, 108, 2, 115, 110, 0, 1, 108, 2, 115, 116, 0, 1, 110, 2, 116, 0, 1, 114, 2, 107, 0, 1, 114, 116, 2, 100, 0, 1, 118, 2, 108, 107, 0, 1, 118, 2, 114, 100, 0, 2, 114, 0, 2, 114, 100, 0, 7, 6, 195, 165, 0, 1, 108, 2, 115, 115, 3, 6, 121, 0, 4, 1, 104, 2, 114, 3, 6, 122, 0, 1, 108, 2, 115, 0, 1, 114, 116, 2, 100, 0, 1, 118, 2, 114, 0, 4, 1, 104, 2, 108, 108, 3, 121, 0, 2, 17, 67, 11, 0, 2, 110, 103, 0, 4, 3, 122, 0, 1, 104, 2, 108, 0, 1, 107, 115, 2, 108, 0, 1, 109, 2, 108, 0, 1, 110, 2, 108, 0, 1, 114, 2, 107, 0, 2, 17, 67, 17, 67, 0, 7, 6, 195, 182, 0, 1, 102, 2, 114, 107, 3, 2, 117, 0, 4, 1, 102, 2, 114, 100, 3, 6, 116, 0, 1, 102, 102, 0, 1, 108, 2, 115, 110, 0, 1, 108, 2, 115, 116, 0, 2, 118, 114, 0, 4, 1, 114, 2, 109, 3, 6, 117, 0, 2, 17, 67, 17, 67, 0, 3, 116, 0, 7, 6, 97, 0, 4, 1, 107, 2, 116, 97, 3, 2, 35, 0, 1, 107, 105, 0, 1, 108, 112, 2, 110, 101, 114, 97, 0, 1, 110, 2, 116, 105, 0, 1, 112, 101, 2, 114, 0, 1, 115, 2, 116, 105, 0, 1, 116, 2, 116, 105, 0, 8, 2, 114, 116, 0, 110, 115, 1, 21, 2, 32, 3, 6, 35, 50, 87, 0, 4, 1, 102, 2, 114, 108, 3, 6, 120, 0, 1, 102, 2, 114, 116, 0, 1, 107, 105, 2, 110, 115, 0, 1, 110, 2, 108, 32, 0, 1, 116, 2, 108, 32, 0, 1, 116, 2, 108, 32, 0, 1, 116, 111, 116, 2, 108, 0, 4, 1, 10, 3, 35, 0, 1, 98, 0, 1, 98, 2, 107, 116, 101, 0, 1, 98, 2, 114, 11, 0, 1, 98, 98, 2, 114, 32, 0, 1, 100, 2, 100, 0, 1, 100, 2, 103, 11, 0, 1, 100, 2, 110, 0, 1, 100, 100, 2, 17, 67, 0, 1, 100, 110, 2, 114, 0, 1, 100, 112, 112, 2, 116, 0, 1, 103, 101, 2, 110, 0, 1, 103, 110, 2, 100, 0, 1, 103, 165, 195, 2, 110, 0, 1, 106, 2, 110, 0, 1, 107, 2, 110, 0, 1, 107, 2, 110, 105, 0, 1, 107, 2, 115, 32, 0, 1, 108, 2, 103, 103, 0, 1, 108, 101, 2, 100, 0, 1, 108, 103, 2, 100, 11, 0, 1, 108, 103, 2, 115, 11, 0, 1, 108, 107, 105, 2, 114, 32, 0, 1, 108, 108, 2, 100, 101, 0, 1, 108, 108, 101, 109, 2, 110, 0, 1, 109, 2, 106, 0, 1, 109, 2, 110, 0, 1, 109, 2, 116, 101, 114, 0, 1, 109, 114, 111, 102, 2, 116, 105, 0, 1, 110, 2, 100, 0, 1, 110, 110, 2, 110, 0, 1, 112, 2, 100, 32, 0, 1, 112, 2, 110, 101, 108, 0, 1, 114, 2, 98, 97, 0, 1, 114, 100, 2, 100, 0, 1, 114, 100, 2, 116, 0, 1, 114, 101, 2, 100, 0, 1, 114, 101, 2, 116, 0, 1, 114, 101, 2, 116, 0, 1, 114, 103, 2, 109, 0, 1, 114, 116, 115, 0, 1, 115, 2, 100, 0, 1, 115, 2, 109, 97, 17, 67, 0, 1, 115, 2, 115, 0, 1, 115, 107, 2, 109, 0, 1, 115, 115, 97, 0, 1, 115, 116, 2, 109, 0, 1, 116, 2, 103, 11, 0, 1, 116, 2, 108, 11, 0, 1, 116, 2, 110, 0, 1, 116, 97, 0, 1, 116, 115, 2, 116, 32, 0, 1, 118, 2, 114, 105, 97, 0, 1, 118, 115, 2, 114, 116, 0, 2, 17, 67, 11, 0, 2, 17, 67, 17, 67, 0, 2, 32, 0, 2, 98, 111, 0, 2, 100, 101, 0, 2, 114, 32, 0, 2, 114, 101, 0, 2, 114, 110, 97, 0, 2, 115, 32, 0, 2, 116, 32, 0, 2, 117, 116, 111, 0, 2, 118, 97, 0, 2, 120, 0, 8, 107, 2, 21, 0, 110, 97, 108, 121, 3, 35, 50, 35, 55, 113, 0, 114, 98, 101, 116, 3, 35, 51, 69, 108, 47, 0, 108, 107, 111, 104, 111, 108, 3, 35, 55, 49, 123, 105, 122, 55, 0, 108, 108, 118, 97, 114, 3, 35, 55, 55, 82, 120, 51, 0, 109, 101, 114, 105, 107, 3, 35, 63, 109, 51, 107, 49, 0, 103, 101, 114, 97, 3, 35, 79, 108, 51, 35, 0, 115, 116, 3, 35, 87, 47, 0, 4, 3, 120, 0, 1, 98, 2, 107, 0, 1, 98, 2, 114, 0, 1, 98, 2, 114, 32, 0, 1, 100, 2, 103, 0, 1, 102, 2, 114, 101, 110, 0, 1, 107, 2, 107, 0, 1, 107, 115, 2, 100, 97, 0, 1, 107, 115, 2, 100, 101, 0, 1, 107, 115, 2, 112, 0, 1, 108, 2, 103, 0, 1, 108, 2, 114, 115, 0, 1, 108, 98, 2, 100, 0, 1, 108, 103, 2, 100, 0, 1, 108, 107, 2, 114, 0, 1, 108, 112, 109, 101, 120, 2, 114, 0, 1, 109, 111, 2, 116, 0, 1, 109, 115, 2, 114, 116, 0, 1, 114, 2, 116, 0, 1, 114, 100, 101, 2, 103, 0, 1, 114, 100, 101, 2, 114, 0, 1, 114, 100, 105, 0, 1, 115, 2, 107, 101, 0, 1, 115, 2, 107, 110, 0, 1, 115, 2, 107, 115, 0, 1, 116, 2, 103, 0, 1, 116, 2, 108, 17, 67, 0, 1, 116, 2, 108, 115, 0, 1, 116, 101, 114, 2, 103, 0, 1, 116, 108, 2, 116, 0, 1, 116, 108, 101, 100, 0, 1, 116, 110, 101, 2, 114, 0, 1, 116, 115, 2, 114, 116, 0, 1, 116, 116, 2, 103, 97, 0, 1, 116, 116, 2, 103, 101, 116, 0, 1, 116, 116, 2, 103, 105, 116, 0, 1, 118, 2, 108, 100, 0, 1, 118, 2, 108, 102, 0, 1, 118, 2, 114, 100, 0, 1, 118, 115, 2, 114, 0, 1, 118, 115, 110, 97, 2, 114, 0, 2, 114, 110, 0, 2, 114, 116, 32, 0, 2, 118, 98, 0, 2, 118, 100, 0, 2, 118, 103, 0, 2, 118, 115, 0, 8, 98, 2, 107, 0, 8, 107, 115, 2, 100, 0, 8, 108, 103, 2, 115, 0, 8, 118, 2, 110, 108, 0, 118, 116, 97, 8, 3, 120, 82, 47, 120, 0, 118, 103, 101, 8, 3, 120, 82, 57, 6, 108, 0, 117, 8, 2, 17, 67, 3, 121, 0, 117, 1, 104, 99, 2, 17, 67, 17, 67, 3, 122, 0, 7, 6, 98, 0, 2, 98, 3, 0, 3, 69, 0, 101, 116, 97, 108, 3, 69, 2, 109, 47, 6, 120, 55, 0, 114, 101, 100, 98, 97, 110, 100, 3, 69, 51, 108, 70, 69, 35, 50, 70, 0, 101, 103, 114, 105, 112, 3, 69, 109, 79, 51, 6, 106, 48, 0, 101, 103, 114, 97, 118, 3, 69, 109, 79, 51, 120, 82, 0, 101, 118, 97, 107, 110, 3, 69, 109, 82, 120, 49, 50, 0, 101, 115, 108, 97, 103, 3, 69, 109, 87, 55, 6, 120, 79, 0, 101, 115, 108, 97, 103, 116, 97, 3, 69, 109, 87, 55, 6, 120, 79, 47, 120, 0, 7, 6, 99, 0, 4, 108, 105, 99, 107, 3, 21, 0, 111, 109, 112, 117, 116, 101, 114, 0, 4, 3, 49, 0, 107, 0, 107, 2, 17, 65, 3, 49, 12, 0, 4, 99, 3, 49, 87, 0, 99, 2, 17, 65, 0, 4, 2, 101, 3, 87, 0, 2, 105, 0, 2, 121, 0, 2, 195, 164, 0, 2, 195, 182, 0, 104, 3, 89, 0, 104, 2, 101, 102, 3, 125, 0, 7, 6, 100, 0, 2, 100, 3, 0, 4, 101, 115, 105, 103, 110, 3, 21, 0, 111, 119, 110, 108, 111, 97, 100, 0, 106, 117, 3, 57, 6, 115, 0, 106, 117, 110, 103, 3, 57, 6, 118, 66, 0, 3, 70, 0, 97, 116, 111, 114, 101, 114, 3, 70, 35, 47, 6, 124, 51, 109, 51, 0, 114, 111, 103, 101, 110, 3, 70, 51, 122, 79, 109, 50, 0, 114, 111, 103, 101, 114, 3, 70, 51, 122, 79, 109, 51, 0, 105, 115, 107, 101, 3, 70, 107, 87, 49, 109, 0, 117, 109, 3, 70, 118, 63, 0, 97, 116, 97, 3, 70, 120, 47, 35, 0, 97, 116, 97, 98, 97, 115, 3, 70, 120, 47, 35, 69, 120, 87, 0, 97, 116, 111, 114, 3, 70, 120, 47, 121, 51, 0, 97, 103, 108, 105, 103, 3, 70, 120, 79, 55, 107, 79, 0, 97, 103, 101, 110, 3, 70, 120, 79, 109, 50, 0, 7, 6, 101, 0, 4, 1, 10, 3, 2, 109, 0, 1, 10, 2, 32, 0, 1, 98, 2, 102, 0, 1, 98, 2, 103, 0, 1, 98, 2, 104, 0, 1, 98, 2, 107, 0, 1, 98, 2, 108, 0, 1, 98, 2, 114, 0, 1, 98, 2, 115, 0, 1, 98, 2, 116, 0, 1, 98, 2, 118, 0, 1, 100, 2, 108, 115, 101, 0, 1, 103, 2, 110, 0, 1, 112, 109, 2, 108, 0, 1, 112, 115, 2, 99, 0, 1, 114, 2, 103, 0, 1, 114, 2, 116, 117, 114, 0, 1, 114, 112, 2, 99, 0, 1, 114, 112, 2, 110, 0, 1, 115, 2, 107, 0, 1, 115, 2, 112, 0, 2, 120, 101, 109, 112, 0, 116, 1, 10, 2, 32, 14, 128, 128, 130, 3, 2, 109, 47, 0, 110, 1, 10, 2, 32, 3, 2, 109, 50, 0, 110, 115, 1, 10, 2, 32, 3, 2, 109, 50, 87, 0, 114, 1, 10, 2, 32, 3, 2, 109, 51, 0, 115, 1, 10, 2, 32, 3, 2, 109, 87, 0, 110, 115, 1, 114, 101, 3, 6, 35, 50, 87, 0, 1, 116, 115, 2, 109, 17, 67, 3, 6, 108, 0, 107, 111, 110, 111, 109, 3, 6, 109, 49, 124, 50, 4, 121, 12, 63, 0, 110, 115, 1, 114, 101, 118, 182, 195, 3, 6, 109, 50, 87, 0, 108, 101, 107, 3, 6, 109, 55, 109, 49, 0, 109, 98, 101, 114, 3, 6, 109, 63, 69, 109, 51, 0, 115, 112, 101, 97, 107, 3, 21, 0, 4, 3, 108, 0, 1, 99, 2, 114, 0, 1, 100, 2, 108, 110, 0, 1, 100, 2, 108, 115, 0, 1, 100, 2, 108, 116, 0, 1, 100, 2, 108, 118, 0, 1, 100, 2, 114, 97, 0, 1, 102, 2, 114, 97, 0, 1, 103, 2, 110, 111, 109, 0, 1, 103, 2, 114, 97, 0, 1, 104, 2, 116, 101, 110, 0, 1, 104, 103, 2, 116, 0, 1, 104, 121, 110, 2, 116, 0, 1, 108, 2, 100, 97, 0, 1, 108, 2, 100, 110, 0, 1, 108, 2, 114, 97, 0, 1, 108, 2, 116, 97, 0, 1, 109, 2, 100, 100, 101, 0, 1, 109, 2, 100, 101, 108, 0, 1, 109, 2, 114, 97, 0, 1, 110, 2, 100, 115, 0, 1, 110, 2, 114, 97, 0, 1, 114, 2, 100, 110, 0, 1, 114, 2, 114, 97, 0, 1, 114, 2, 116, 97, 0, 1, 114, 98, 2, 118, 0, 1, 114, 116, 120, 2, 109, 0, 1, 115, 2, 114, 97, 0, 1, 116, 2, 114, 97, 0, 1, 116, 105, 2, 116, 0, 1, 116, 105, 2, 116, 32, 0, 1, 116, 111, 105, 108, 2, 107, 0, 1, 116, 115, 2, 107, 0, 1, 116, 115, 121, 2, 109, 0, 1, 118, 2, 107, 0, 1, 118, 2, 116, 97, 0, 2, 110, 98, 97, 114, 0, 2, 110, 108, 105, 0, 2, 114, 105, 110, 0, 2, 114, 115, 97, 116, 116, 0, 2, 114, 115, 195, 164, 0, 8, 104, 2, 116, 97, 0, 116, 1, 104, 2, 32, 3, 108, 47, 0, 110, 104, 101, 116, 3, 108, 50, 105, 108, 47, 0, 4, 1, 97, 107, 2, 108, 3, 109, 0, 1, 98, 2, 108, 32, 0, 1, 100, 2, 98, 97, 116, 0, 1, 100, 2, 99, 0, 1, 100, 101, 109, 2, 108, 0, 1, 104, 2, 109, 0, 1, 109, 2, 110, 121, 0, 1, 109, 2, 116, 111, 100, 0, 1, 112, 2, 100, 97, 0, 1, 112, 2, 114, 105, 0, 1, 114, 2, 99, 101, 0, 1, 114, 2, 100, 97, 107, 0, 1, 114, 2, 115, 117, 108, 0, 1, 114, 2, 115, 117, 114, 0, 1, 116, 2, 108, 101, 102, 0, 1, 118, 115, 2, 114, 0, 2, 17, 67, 17, 67, 0, 2, 103, 101, 110, 116, 0, 2, 106, 0, 2, 116, 97, 0, 2, 118, 101, 0, 2, 120, 0, 8, 2, 116, 105, 107, 0, 115, 101, 110, 116, 3, 109, 87, 6, 109, 50, 47, 0, 1, 104, 99, 2, 102, 3, 111, 0, 7, 6, 102, 0, 2, 102, 3, 0, 97, 99, 101, 3, 21, 0, 3, 81, 0, 97, 109, 105, 108, 106, 3, 81, 35, 63, 6, 107, 55, 57, 0, 111, 114, 109, 97, 100, 3, 81, 121, 51, 63, 35, 70, 0, 7, 6, 103, 0, 114, 111, 117, 112, 3, 21, 0, 2, 116, 3, 49, 0, 4, 1, 114, 111, 2, 97, 114, 3, 57, 0, 1, 114, 111, 2, 101, 110, 0, 2, 101, 0, 2, 105, 0, 2, 121, 0, 2, 195, 164, 0, 2, 195, 182, 0, 106, 0, 106, 111, 114, 3, 57, 124, 51, 0, 2, 110, 3, 66, 0, 4, 3, 79, 0, 1, 97, 2, 101, 0, 1, 97, 2, 105, 0, 1, 97, 108, 115, 0, 1, 105, 2, 105, 0, 1, 111, 108, 2, 105, 0, 1, 121, 2, 97, 0, 1, 121, 2, 101, 0, 1, 121, 2, 111, 0, 1, 164, 195, 108, 2, 101, 0, 1, 164, 195, 118, 0, 103, 0, 97, 114, 97, 110, 116, 3, 79, 2, 35, 51, 6, 35, 50, 47, 0, 117, 105, 100, 2, 101, 3, 79, 6, 35, 57, 70, 0, 97, 110, 105, 3, 79, 35, 50, 6, 107, 0, 97, 114, 97, 103, 101, 3, 79, 35, 51, 6, 120, 89, 0, 108, 195, 182, 109, 3, 79, 55, 117, 63, 0, 97, 116, 97, 3, 79, 120, 47, 35, 0, 7, 6, 104, 0, 2, 104, 3, 0, 101, 97, 100, 105, 110, 103, 3, 21, 0, 106, 3, 57, 0, 106, 195, 164, 108, 112, 3, 57, 109, 55, 48, 0, 3, 105, 0, 195, 182, 103, 3, 105, 116, 79, 0, 111, 110, 8, 2, 14, 128, 132, 131, 3, 105, 122, 66, 0, 7, 6, 105, 0, 4, 1, 108, 17, 67, 2, 107, 97, 17, 67, 3, 2, 107, 0, 2, 110, 102, 0, 2, 110, 115, 116, 114, 0, 4, 2, 110, 32, 3, 6, 106, 0, 2, 110, 101, 110, 0, 2, 110, 101, 114, 0, 4, 109, 97, 103, 3, 21, 0, 116, 101, 109, 0, 4, 3, 106, 0, 1, 99, 2, 115, 32, 0, 1, 108, 2, 107, 110, 97, 0, 1, 114, 100, 2, 118, 0, 1, 114, 107, 2, 115, 0, 1, 114, 107, 2, 115, 116, 0, 1, 114, 107, 115, 2, 118, 0, 1, 116, 2, 100, 0, 1, 116, 105, 114, 107, 2, 107, 32, 0, 1, 118, 2, 115, 110, 0, 8, 108, 102, 2, 107, 0, 4, 1, 99, 3, 107, 0, 1, 100, 2, 114, 0, 1, 107, 2, 103, 0, 1, 108, 2, 99, 0, 1, 114, 107, 2, 116, 101, 0, 1, 114, 107, 2, 116, 105, 0, 1, 115, 2, 116, 0, 1, 116, 2, 115, 0, 2, 17, 67, 17, 67, 0, 2, 103, 32, 0, 116, 117, 116, 2, 32, 3, 107, 47, 115, 47, 0, 107, 111, 110, 3, 107, 49, 6, 122, 50, 0, 98, 105, 108, 105, 3, 107, 69, 107, 55, 107, 0, 7, 6, 106, 0, 3, 57, 0, 97, 118, 97, 3, 57, 120, 82, 35, 0, 2, 117, 115, 116, 101, 114, 3, 125, 0, 111, 117, 2, 114, 3, 125, 123, 0, 7, 6, 107, 0, 4, 3, 49, 0, 8, 2, 105, 17, 67, 11, 0, 97, 116, 101, 103, 111, 114, 105, 3, 49, 35, 47, 109, 79, 4, 124, 51, 106, 0, 97, 108, 101, 110, 100, 3, 49, 35, 55, 6, 109, 50, 70, 0, 97, 114, 116, 97, 3, 49, 120, 51, 47, 35, 0, 111, 110, 116, 111, 114, 3, 49, 121, 50, 47, 6, 124, 51, 0, 111, 109, 109, 117, 110, 3, 49, 121, 63, 6, 115, 50, 0, 111, 109, 109, 117, 110, 105, 107, 97, 3, 49, 121, 63, 118, 50, 107, 49, 35, 0, 4, 2, 195, 164, 110, 100, 3, 95, 0, 2, 195, 164, 110, 110, 0, 2, 195, 164, 110, 116, 0, 2, 195, 182, 112, 0, 8, 2, 101, 0, 8, 2, 105, 0, 8, 2, 121, 0, 8, 2, 195, 164, 0, 8, 2, 195, 182, 0, 106, 0, 195, 164, 110, 115, 108, 3, 95, 109, 50, 87, 55, 0, 7, 6, 108, 0, 2, 108, 3, 0, 3, 55, 0, 195, 165, 103, 3, 55, 6, 122, 79, 0, 103, 2, 32, 3, 55, 57, 0, 105, 103, 101, 110, 3, 55, 107, 79, 109, 50, 0, 97, 103, 101, 114, 3, 55, 120, 79, 109, 51, 0, 106, 8, 3, 57, 0, 106, 117, 3, 57, 6, 115, 0, 7, 6, 109, 0, 2, 109, 3, 0, 101, 110, 117, 3, 21, 0, 3, 63, 0, 97, 114, 105, 101, 3, 63, 2, 35, 51, 6, 106, 0, 97, 114, 105, 97, 3, 63, 2, 35, 51, 6, 106, 35, 0, 101, 100, 108, 3, 63, 6, 108, 70, 55, 0, 195, 164, 110, 110, 105, 115, 107, 3, 63, 6, 109, 50, 107, 125, 4, 0, 111, 116, 111, 114, 101, 114, 3, 63, 6, 121, 47, 124, 51, 109, 51, 0, 111, 116, 111, 114, 3, 63, 6, 124, 47, 121, 51, 0, 97, 120, 105, 109, 101, 114, 97, 3, 63, 35, 49, 87, 106, 63, 6, 108, 51, 35, 0, 97, 103, 97, 3, 63, 35, 79, 35, 0, 97, 115, 107, 101, 114, 97, 3, 63, 35, 87, 49, 108, 51, 35, 0, 97, 115, 107, 101, 110, 3, 63, 35, 87, 49, 109, 50, 0, 97, 115, 107, 101, 114, 3, 63, 35, 87, 49, 109, 51, 0, 106, 117, 107, 3, 63, 57, 115, 49, 0, 105, 110, 105, 109, 101, 114, 97, 3, 63, 107, 50, 106, 63, 6, 108, 51, 35, 0, 101, 100, 98, 111, 114, 103, 3, 63, 108, 70, 69, 121, 51, 57, 0, 101, 100, 118, 101, 116, 3, 63, 108, 70, 82, 6, 108, 47, 0, 101, 110, 121, 3, 63, 109, 50, 6, 113, 0, 117, 115, 105, 107, 3, 63, 115, 87, 6, 106, 49, 0, 111, 98, 105, 108, 3, 63, 121, 69, 106, 55, 0, 111, 100, 101, 108, 3, 63, 121, 70, 6, 109, 55, 0, 111, 100, 101, 109, 3, 63, 121, 70, 108, 63, 0, 7, 6, 110, 0, 2, 110, 3, 0, 101, 116, 119, 111, 114, 107, 3, 21, 0, 3, 50, 0, 97, 118, 105, 103, 3, 50, 2, 35, 82, 2, 107, 79, 0, 97, 116, 117, 114, 3, 50, 6, 35, 47, 6, 115, 51, 0, 97, 108, 105, 3, 50, 35, 55, 107, 0, 103, 1, 117, 102, 2, 101, 114, 3, 50, 79, 0, 111, 114, 109, 97, 108, 3, 50, 121, 51, 63, 120, 55, 0, 4, 2, 107, 3, 66, 0, 103, 0, 7, 6, 111, 0, 4, 1, 102, 110, 105, 2, 114, 109, 97, 116, 105, 3, 2, 121, 0, 1, 107, 2, 108, 117, 0, 1, 110, 2, 118, 101, 108, 108, 0, 1, 112, 2, 108, 105, 115, 0, 1, 114, 112, 2, 98, 0, 1, 114, 112, 2, 99, 101, 110, 116, 0, 1, 114, 112, 2, 100, 0, 4, 1, 108, 2, 107, 3, 2, 123, 0, 1, 114, 112, 2, 99, 0, 1, 115, 2, 99, 105, 0, 4, 1, 98, 2, 120, 3, 6, 121, 0, 1, 102, 2, 114, 109, 0, 1, 107, 2, 112, 105, 0, 1, 108, 2, 103, 103, 0, 1, 110, 2, 114, 109, 0, 1, 115, 2, 114, 0, 99, 104, 3, 6, 121, 49, 0, 4, 1, 102, 2, 110, 3, 6, 122, 0, 1, 108, 2, 103, 0, 1, 108, 2, 118, 0, 2, 110, 105, 0, 4, 1, 107, 2, 107, 3, 6, 124, 0, 1, 108, 98, 2, 100, 0, 1, 109, 2, 116, 0, 4, 1, 17, 67, 2, 114, 115, 3, 121, 0, 1, 98, 2, 114, 116, 0, 1, 100, 2, 107, 0, 1, 100, 2, 110, 0, 1, 103, 2, 110, 0, 1, 103, 110, 2, 110, 0, 1, 107, 2, 110, 115, 0, 1, 107, 2, 114, 116, 0, 1, 107, 2, 114, 118, 0, 1, 108, 2, 110, 0, 1, 108, 108, 2, 110, 0, 1, 110, 2, 114, 32, 0, 1, 110, 110, 2, 110, 115, 0, 1, 112, 2, 112, 117, 0, 1, 112, 112, 2, 114, 116, 0, 1, 112, 115, 2, 114, 116, 0, 1, 114, 116, 114, 2, 110, 0, 1, 115, 2, 114, 32, 0, 1, 115, 115, 2, 110, 0, 1, 116, 2, 114, 32, 0, 1, 116, 115, 2, 114, 109, 0, 2, 17, 67, 17, 67, 0, 2, 98, 98, 0, 2, 99, 107, 0, 2, 100, 100, 0, 2, 102, 102, 0, 2, 108, 108, 0, 2, 109, 32, 0, 2, 109, 109, 0, 2, 112, 112, 0, 2, 114, 103, 0, 2, 114, 107, 0, 2, 114, 114, 0, 2, 115, 115, 0, 2, 116, 116, 0, 8, 2, 106, 0, 112, 101, 114, 97, 116, 3, 121, 48, 109, 51, 35, 47, 0, 106, 1, 114, 112, 3, 121, 125, 6, 0, 4, 1, 107, 2, 100, 3, 122, 0, 1, 107, 108, 2, 114, 0, 1, 112, 112, 117, 2, 114, 116, 0, 2, 114, 100, 101, 0, 4, 1, 103, 2, 114, 3, 123, 0, 2, 17, 67, 11, 0, 2, 110, 115, 0, 4, 3, 124, 0, 1, 98, 2, 107, 0, 1, 98, 2, 115, 116, 0, 1, 102, 2, 116, 98, 0, 1, 103, 2, 100, 0, 1, 114, 107, 2, 103, 0, 1, 114, 107, 2, 107, 0, 1, 114, 107, 2, 110, 0, 1, 114, 112, 2, 118, 0, 1, 115, 114, 2, 114, 100, 0, 2, 114, 17, 67, 0, 115, 112, 97, 114, 97, 116, 3, 124, 87, 48, 120, 51, 35, 47, 0, 7, 6, 112, 0, 2, 112, 3, 0, 3, 48, 0, 97, 107, 101, 116, 3, 48, 35, 49, 6, 108, 47, 0, 97, 114, 101, 110, 116, 101, 115, 3, 48, 35, 51, 13, 50, 47, 4, 108, 87, 0, 114, 105, 118, 97, 116, 3, 48, 51, 107, 82, 120, 47, 0, 105, 111, 110, 3, 48, 107, 38, 6, 124, 50, 0, 111, 116, 97, 116, 105, 115, 3, 48, 121, 47, 6, 120, 47, 107, 87, 0, 195, 165, 115, 116, 195, 165, 3, 48, 122, 87, 47, 122, 0, 7, 6, 113, 0, 2, 113, 3, 0, 3, 49, 0, 117, 3, 49, 58, 0, 7, 6, 114, 0, 4, 1, 114, 3, 0, 2, 116, 3, 0, 3, 51, 0, 101, 100, 105, 103, 101, 114, 3, 51, 2, 109, 70, 107, 125, 6, 108, 51, 0, 101, 115, 111, 114, 3, 51, 6, 108, 87, 121, 51, 0, 97, 100, 101, 114, 97, 3, 51, 35, 70, 6, 108, 51, 35, 0, 97, 102, 105, 107, 3, 51, 35, 81, 6, 106, 49, 0, 103, 2, 32, 3, 51, 57, 0, 105, 115, 107, 3, 51, 107, 87, 49, 0, 101, 103, 101, 108, 3, 51, 108, 79, 109, 55, 0, 101, 107, 111, 114, 100, 3, 51, 109, 49, 6, 122, 51, 70, 0, 117, 98, 114, 105, 107, 3, 51, 118, 69, 51, 6, 106, 49, 0, 115, 107, 2, 105, 3, 51, 125, 0, 115, 105, 2, 111, 3, 51, 125, 6, 0, 4, 115, 3, 91, 0, 115, 115, 0, 115, 107, 3, 91, 49, 0, 7, 6, 115, 0, 4, 101, 108, 101, 99, 116, 3, 21, 0, 119, 101, 100, 101, 110, 0, 4, 3, 87, 0, 1, 105, 102, 2, 107, 0, 1, 117, 102, 2, 107, 0, 2, 107, 105, 103, 0, 115, 0, 195, 164, 107, 101, 114, 104, 101, 116, 3, 87, 6, 111, 49, 13, 51, 105, 4, 108, 47, 0, 116, 195, 165, 116, 116, 3, 87, 47, 121, 47, 0, 112, 101, 108, 3, 87, 48, 108, 55, 0, 112, 101, 103, 108, 97, 3, 87, 48, 108, 79, 55, 35, 0, 112, 101, 103, 101, 108, 3, 87, 48, 108, 79, 109, 55, 0, 112, 97, 114, 97, 3, 87, 48, 120, 51, 35, 0, 107, 121, 112, 101, 3, 87, 49, 6, 35, 57, 48, 0, 107, 111, 108, 111, 114, 3, 87, 49, 124, 55, 121, 51, 0, 110, 101, 103, 108, 97, 3, 87, 50, 108, 79, 55, 35, 0, 108, 111, 103, 3, 87, 55, 6, 124, 79, 0, 106, 97, 99, 107, 3, 87, 57, 35, 49, 0, 118, 101, 114, 105, 103, 101, 3, 87, 82, 109, 51, 57, 109, 0, 118, 97, 114, 97, 3, 87, 82, 120, 51, 35, 0, 105, 111, 110, 105, 115, 116, 8, 3, 87, 106, 122, 50, 6, 107, 87, 47, 0, 101, 103, 108, 97, 3, 87, 108, 79, 55, 35, 0, 101, 103, 101, 108, 3, 87, 108, 79, 109, 55, 0, 195, 164, 103, 3, 87, 109, 57, 0, 101, 109, 101, 115, 116, 3, 87, 109, 63, 6, 109, 87, 47, 0, 101, 114, 118, 105, 99, 101, 3, 87, 116, 51, 82, 106, 87, 0, 99, 104, 3, 89, 0, 107, 106, 3, 95, 0, 4, 104, 8, 3, 125, 0, 106, 0, 107, 2, 101, 0, 107, 2, 105, 0, 107, 2, 121, 0, 107, 2, 195, 164, 0, 107, 2, 195, 182, 0, 116, 106, 0, 107, 195, 164, 114, 109, 3, 125, 6, 109, 51, 63, 0, 4, 105, 111, 2, 110, 3, 125, 6, 124, 0, 115, 105, 111, 2, 110, 0, 7, 6, 116, 0, 97, 115, 107, 3, 21, 0, 4, 3, 47, 0, 116, 0, 97, 108, 115, 121, 110, 116, 101, 115, 3, 47, 6, 120, 55, 87, 114, 50, 47, 4, 108, 87, 0, 97, 103, 105, 116, 3, 47, 6, 120, 79, 107, 47, 0, 116, 2, 17, 65, 3, 47, 12, 0, 97, 110, 103, 101, 110, 116, 3, 47, 35, 50, 57, 109, 50, 47, 0, 97, 98, 101, 108, 108, 3, 47, 35, 69, 6, 109, 55, 0, 101, 1, 17, 67, 10, 2, 32, 14, 128, 128, 130, 3, 47, 109, 0, 101, 107, 110, 105, 107, 3, 47, 109, 49, 50, 6, 106, 49, 0, 106, 3, 95, 0, 105, 2, 111, 110, 3, 125, 6, 0, 7, 6, 117, 0, 4, 1, 110, 105, 108, 2, 120, 3, 2, 118, 0, 2, 107, 116, 105, 0, 2, 110, 107, 17, 67, 0, 116, 109, 195, 164, 114, 107, 3, 6, 115, 47, 63, 13, 51, 49, 0, 112, 108, 111, 97, 100, 3, 21, 0, 4, 3, 115, 0, 1, 106, 2, 108, 0, 1, 106, 2, 110, 105, 0, 1, 106, 115, 2, 107, 0, 2, 116, 98, 0, 2, 116, 102, 0, 2, 116, 103, 0, 2, 116, 108, 0, 2, 116, 110, 0, 2, 116, 114, 0, 2, 116, 114, 0, 2, 116, 115, 0, 2, 116, 118, 0, 4, 1, 98, 2, 116, 105, 107, 3, 118, 0, 1, 116, 97, 100, 2, 109, 0, 1, 118, 2, 120, 0, 2, 17, 67, 17, 67, 0, 2, 110, 0, 2, 110, 103, 0, 1, 114, 2, 109, 32, 3, 118, 12, 0, 112, 112, 103, 101, 3, 118, 48, 57, 108, 0, 7, 6, 118, 0, 2, 118, 3, 0, 3, 82, 0, 97, 114, 97, 110, 100, 114, 97, 3, 82, 35, 51, 35, 50, 70, 51, 35, 0, 97, 108, 105, 3, 82, 35, 55, 107, 0, 101, 114, 107, 3, 82, 109, 51, 49, 0, 101, 114, 107, 116, 121, 103, 3, 82, 109, 51, 49, 47, 113, 79, 0, 97, 114, 97, 110, 3, 82, 120, 51, 35, 50, 0, 97, 114, 110, 3, 82, 120, 51, 50, 0, 7, 6, 119, 0, 4, 105, 110, 100, 111, 119, 3, 21, 0, 105, 114, 101, 0, 105, 115, 101, 0, 3, 82, 0, 7, 6, 120, 0, 2, 120, 3, 0, 3, 49, 87, 0, 7, 6, 121, 0, 1, 115, 2, 115, 3, 2, 114, 0, 4, 1, 116, 2, 100, 3, 6, 113, 0, 1, 116, 2, 103, 0, 4, 3, 113, 0, 1, 115, 2, 110, 115, 107, 97, 0, 2, 17, 67, 17, 67, 3, 114, 0, 7, 6, 122, 0, 122, 3, 86, 0, 3, 87, 0, 7, 6, 0, 4, 42, 1, 42, 2, 42, 3, 0, 4, 42, 42, 3, 0, 4, 45, 1, 45, 45, 3, 0, 46, 1, 46, 3, 0, 195, 169, 3, 6, 108, 0, 226, 130, 172, 3, 6, 109, 82, 51, 124, 0, 46, 2, 46, 3, 9, 0, 38, 3, 9, 6, 121, 49, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 42, 1, 42, 42, 2, 32, 3, 24, 0, 46, 3, 48, 6, 118, 66, 47, 0, 37, 3, 48, 51, 121, 87, 6, 109, 50, 47, 0, 43, 3, 48, 55, 118, 87, 0, 45, 8, 32, 2, 32, 15, 3, 63, 6, 106, 50, 118, 87, 0, 36, 3, 70, 6, 121, 55, 35, 51, 0, 47, 3, 87, 50, 6, 108, 70, 87, 47, 51, 109, 49, 0, 64, 3, 87, 50, 6, 120, 69, 109, 55, 120, 0, 42, 3, 125, 6, 111, 51, 50, 35, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts56 = FileInMemory_createWithData (9701, reinterpret_cast (&espeakdata_dicts56_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/sv_dict", L"sv"); Collection_addItem (me.peek(), espeakdata_dicts56.transfer()); static unsigned char espeakdata_dicts57_data[3005] = { 0, 4, 0, 0, 32, 10, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 56, 77, 49, 4, 36, 55, 81, 40, 50, 6, 35, 50, 36, 0, 0, 17, 4, 95, 56, 77, 50, 55, 6, 35, 49, 37, 50, 6, 35, 50, 36, 0, 0, 0, 0, 6, 65, 8, 69, 37, 0, 0, 0, 0, 0, 6, 65, 12, 87, 37, 0, 0, 0, 0, 7, 196, 100, 16, 78, 36, 8, 0, 6, 65, 16, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 24, 36, 81, 0, 0, 0, 0, 0, 9, 197, 12, 129, 78, 100, 80, 72, 28, 6, 65, 28, 77, 37, 0, 0, 0, 0, 0, 7, 65, 32, 36, 74, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 40, 77, 36, 0, 0, 0, 0, 0, 6, 65, 44, 49, 36, 0, 0, 0, 0, 0, 6, 65, 48, 36, 55, 0, 0, 0, 0, 0, 7, 65, 52, 36, 63, 0, 14, 4, 193, 52, 76, 0, 0, 0, 0, 11, 5, 95, 48, 1, 14, 4, 23, 50, 35, 0, 6, 65, 56, 36, 50, 0, 0, 0, 0, 0, 0, 0, 0, 8, 196, 104, 83, 153, 20, 72, 28, 8, 196, 100, 83, 153, 20, 72, 28, 8, 196, 92, 83, 153, 20, 72, 28, 0, 6, 65, 64, 48, 37, 0, 0, 0, 0, 0, 7, 65, 68, 49, 57, 40, 0, 0, 0, 0, 0, 6, 65, 72, 35, 51, 0, 0, 0, 0, 0, 6, 65, 76, 36, 87, 0, 0, 0, 0, 0, 6, 65, 80, 47, 37, 0, 0, 0, 6, 195, 92, 19, 192, 76, 0, 0, 4, 193, 84, 76, 0, 0, 0, 7, 195, 80, 242, 193, 72, 28, 0, 6, 65, 88, 82, 37, 0, 0, 0, 0, 0, 11, 65, 92, 70, 35, 69, 35, 55, 57, 40, 0, 0, 0, 0, 6, 195, 92, 18, 197, 76, 0, 17, 4, 95, 49, 77, 49, 4, 36, 55, 81, 40, 63, 6, 39, 77, 35, 0, 7, 65, 96, 36, 49, 87, 0, 0, 17, 4, 95, 49, 77, 50, 55, 6, 35, 49, 37, 63, 6, 39, 77, 35, 0, 0, 0, 6, 195, 76, 148, 201, 76, 0, 7, 65, 100, 57, 35, 37, 0, 0, 0, 0, 0, 8, 65, 104, 86, 36, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 5, 80, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 32, 17, 9, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 32, 147, 15, 76, 0, 0, 0, 0, 0, 0, 0, 8, 197, 45, 112, 86, 100, 240, 8, 0, 0, 0, 0, 19, 4, 95, 50, 77, 49, 4, 36, 55, 81, 40, 23, 63, 69, 6, 37, 55, 37, 0, 0, 19, 4, 95, 50, 77, 50, 55, 6, 35, 49, 37, 23, 63, 69, 6, 37, 55, 37, 0, 0, 0, 7, 196, 4, 145, 8, 4, 8, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 32, 21, 1, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 8, 144, 72, 28, 0, 0, 0, 0, 0, 6, 195, 32, 146, 64, 72, 0, 13, 4, 95, 4, 16, 20, 10, 50, 40, 49, 47, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 51, 77, 49, 4, 36, 55, 81, 40, 47, 6, 35, 47, 40, 0, 0, 17, 4, 95, 51, 77, 50, 55, 6, 35, 49, 37, 47, 6, 35, 47, 40, 0, 0, 0, 0, 0, 0, 0, 8, 196, 64, 147, 132, 36, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 37, 112, 80, 60, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 197, 89, 145, 78, 100, 80, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 53, 112, 64, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 45, 112, 76, 60, 8, 0, 0, 6, 194, 4, 240, 72, 8, 0, 0, 0, 9, 197, 53, 113, 78, 100, 80, 72, 28, 9, 197, 44, 21, 9, 44, 16, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 92, 19, 1, 44, 147, 137, 8, 0, 0, 0, 0, 0, 0, 17, 67, 41, 85, 64, 77, 4, 40, 12, 57, 106, 0, 8, 81, 121, 97, 32, 0, 8, 196, 80, 20, 129, 4, 76, 8, 10, 68, 80, 19, 135, 84, 89, 40, 0, 28, 0, 0, 0, 0, 0, 8, 197, 64, 19, 129, 64, 240, 8, 0, 0, 0, 0, 8, 197, 48, 18, 201, 56, 144, 8, 8, 197, 36, 225, 193, 92, 16, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 133, 49, 5, 14, 25, 5, 72, 28, 7, 196, 56, 19, 153, 36, 76, 0, 0, 6, 194, 24, 144, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 53, 77, 49, 4, 36, 55, 81, 40, 47, 6, 35, 50, 39, 0, 0, 0, 0, 17, 4, 95, 53, 77, 50, 55, 6, 35, 49, 37, 47, 6, 35, 50, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 51, 88, 85, 36, 55, 36, 85, 6, 37, 50, 37, 0, 0, 10, 3, 95, 48, 67, 63, 6, 37, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 49, 67, 63, 4, 37, 35, 63, 6, 39, 77, 35, 0, 0, 0, 0, 0, 0, 0, 6, 194, 48, 16, 72, 28, 0, 0, 17, 3, 95, 50, 67, 63, 4, 37, 35, 23, 63, 69, 6, 37, 55, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 51, 67, 63, 4, 37, 35, 47, 6, 35, 47, 40, 0, 0, 0, 0, 17, 4, 95, 54, 77, 49, 4, 36, 55, 81, 40, 87, 6, 37, 47, 35, 0, 0, 7, 196, 45, 112, 89, 20, 8, 0, 0, 17, 4, 95, 54, 77, 50, 55, 6, 35, 49, 37, 87, 6, 37, 47, 35, 0, 0, 13, 3, 95, 55, 88, 87, 35, 69, 6, 37, 50, 37, 0, 0, 14, 3, 95, 52, 67, 63, 4, 37, 35, 6, 42, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 53, 67, 63, 4, 37, 35, 47, 6, 35, 50, 39, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 88, 49, 6, 40, 63, 37, 0, 0, 15, 3, 95, 54, 67, 63, 4, 37, 35, 87, 6, 37, 47, 35, 0, 0, 0, 0, 0, 0, 0, 5, 194, 45, 80, 76, 0, 14, 3, 95, 50, 88, 37, 89, 37, 51, 6, 37, 50, 37, 0, 0, 15, 3, 95, 55, 67, 63, 4, 37, 35, 87, 6, 35, 69, 35, 0, 0, 0, 0, 0, 0, 0, 6, 195, 52, 147, 73, 76, 0, 0, 15, 3, 95, 56, 67, 63, 4, 37, 35, 50, 6, 35, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 52, 88, 35, 51, 39, 69, 35, 6, 37, 50, 37, 0, 0, 15, 3, 95, 57, 67, 63, 4, 37, 35, 47, 6, 37, 87, 35, 0, 0, 0, 0, 0, 0, 0, 6, 194, 56, 16, 72, 8, 0, 14, 3, 95, 53, 88, 105, 35, 63, 87, 6, 37, 50, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 54, 88, 87, 37, 47, 6, 37, 50, 37, 0, 0, 0, 0, 0, 17, 4, 95, 55, 77, 49, 4, 36, 55, 81, 40, 87, 6, 35, 69, 35, 0, 0, 0, 0, 17, 4, 95, 55, 77, 50, 55, 6, 35, 49, 37, 87, 6, 35, 69, 35, 0, 0, 10, 199, 36, 160, 80, 60, 181, 87, 4, 8, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 56, 88, 85, 36, 63, 35, 50, 6, 37, 50, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 57, 88, 47, 37, 87, 6, 37, 50, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 64, 16, 72, 28, 6, 194, 64, 16, 72, 28, 5, 194, 48, 144, 72, 0, 0, 0, 0, 0, 0, 0, 9, 197, 45, 112, 77, 8, 16, 72, 8, 0, 0, 7, 195, 52, 147, 128, 72, 28, 0, 16, 4, 95, 48, 77, 52, 23, 69, 37, 55, 37, 6, 39, 50, 37, 0, 0, 0, 0, 16, 4, 95, 48, 77, 51, 23, 63, 37, 55, 37, 6, 39, 50, 37, 0, 0, 0, 12, 4, 95, 48, 77, 49, 6, 36, 55, 81, 40, 0, 0, 0, 0, 8, 196, 8, 16, 68, 4, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 56, 144, 76, 0, 0, 0, 0, 0, 0, 6, 195, 100, 18, 197, 76, 0, 0, 0, 0, 0, 0, 17, 4, 95, 57, 77, 50, 55, 6, 35, 49, 37, 47, 6, 37, 87, 35, 0, 0, 0, 0, 17, 4, 95, 57, 77, 49, 4, 36, 55, 81, 40, 47, 6, 37, 87, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 92, 85, 197, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 45, 84, 213, 16, 144, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 4, 225, 193, 60, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 8, 147, 1, 72, 8, 0, 0, 0, 0, 7, 195, 8, 19, 9, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 45, 85, 193, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 40, 20, 15, 8, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 45, 80, 78, 104, 144, 64, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 56, 19, 73, 76, 0, 0, 5, 194, 81, 80, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 92, 16, 72, 28, 5, 194, 76, 144, 72, 0, 0, 6, 195, 56, 22, 69, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 36, 160, 80, 60, 8, 0, 0, 0, 0, 7, 195, 89, 144, 64, 72, 28, 0, 0, 7, 2, 95, 13, 36, 63, 0, 0, 0, 22, 67, 45, 112, 64, 49, 58, 35, 15, 49, 4, 40, 58, 106, 0, 8, 81, 107, 117, 119, 97, 32, 7, 195, 45, 112, 64, 72, 28, 7, 195, 45, 112, 64, 72, 28, 0, 7, 196, 44, 148, 200, 4, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 45, 112, 79, 8, 0, 0, 0, 0, 0, 0, 16, 4, 95, 52, 77, 50, 55, 6, 35, 49, 37, 6, 42, 50, 36, 0, 0, 16, 4, 95, 52, 77, 49, 4, 36, 55, 81, 40, 6, 42, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 2, 95, 51, 47, 6, 35, 47, 40, 0, 0, 12, 2, 95, 50, 23, 63, 69, 6, 37, 55, 37, 0, 0, 10, 2, 95, 49, 63, 6, 39, 77, 35, 0, 0, 12, 2, 95, 48, 87, 37, 81, 6, 40, 51, 37, 0, 0, 10, 2, 95, 55, 87, 6, 35, 69, 35, 0, 0, 10, 2, 95, 54, 87, 6, 37, 47, 35, 0, 0, 10, 2, 95, 53, 47, 6, 35, 50, 39, 0, 0, 9, 2, 95, 52, 6, 42, 50, 36, 0, 0, 0, 0, 10, 2, 95, 57, 47, 6, 37, 87, 35, 0, 0, 6, 194, 100, 16, 72, 28, 10, 2, 95, 56, 50, 6, 35, 50, 36, 0, 0, 0, 0, 8, 197, 57, 146, 78, 100, 144, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 36, 192, 64, 8, 7, 195, 12, 128, 64, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 104, 16, 72, 28, 0, 0, 0, 8, 197, 64, 19, 79, 40, 16, 8, 0, 6, 195, 104, 18, 197, 76, 0, 7, 195, 36, 194, 64, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 56, 19, 192, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 8, 20, 201, 76, 8, 6, 195, 56, 21, 197, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 101, 80, 72, 0, 0, 0, 0, 6, 195, 56, 20, 201, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 92, 19, 1, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 33, 82, 207, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 45, 112, 67, 32, 240, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 4, 208, 64, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 194, 104, 144, 72, 0, 0, 0, 0, 0, 10, 199, 36, 194, 75, 92, 19, 66, 4, 8, 0, 0, 9, 198, 8, 17, 1, 48, 22, 65, 8, 0, 7, 195, 44, 19, 65, 76, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 100, 86, 69, 76, 0, 0, 0, 0, 0, 0, 0, 6, 97, 0, 3, 35, 0, 97, 3, 35, 12, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 49, 0, 104, 3, 74, 0, 7, 6, 100, 0, 3, 70, 0, 104, 3, 84, 0, 7, 6, 101, 0, 3, 36, 0, 101, 3, 36, 12, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 3, 79, 0, 104, 3, 98, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 105, 3, 37, 12, 0, 7, 6, 106, 0, 3, 77, 0, 7, 6, 107, 0, 3, 49, 0, 104, 3, 99, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 4, 1, 25, 2, 21, 21, 3, 23, 63, 0, 1, 25, 2, 98, 21, 21, 0, 1, 25, 2, 118, 21, 21, 0, 1, 25, 2, 119, 21, 21, 0, 4, 1, 25, 2, 17, 67, 3, 41, 0, 8, 0, 4, 3, 63, 0, 2, 17, 65, 0, 7, 6, 110, 0, 8, 3, 42, 0, 4, 8, 2, 103, 3, 43, 0, 8, 2, 103, 21, 21, 0, 8, 2, 107, 0, 8, 2, 107, 21, 21, 0, 4, 3, 50, 0, 2, 17, 65, 0, 2, 21, 21, 0, 4, 2, 99, 104, 3, 65, 0, 2, 106, 0, 121, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 103, 39, 0, 7, 6, 111, 0, 3, 39, 0, 111, 3, 39, 12, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 7, 6, 114, 0, 1, 17, 67, 2, 17, 65, 3, 14, 16, 0, 4, 3, 51, 0, 1, 17, 65, 2, 17, 65, 0, 114, 3, 51, 51, 0, 7, 6, 115, 0, 3, 87, 0, 104, 3, 89, 0, 7, 6, 116, 0, 3, 47, 0, 104, 3, 85, 0, 7, 6, 117, 0, 3, 40, 0, 117, 3, 40, 12, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 4, 42, 1, 42, 2, 42, 3, 0, 42, 42, 3, 0, 42, 1, 42, 42, 2, 32, 3, 24, 0, 37, 3, 35, 87, 37, 55, 37, 63, 37, 35, 0, 42, 3, 65, 39, 47, 35, 0, 36, 3, 70, 39, 55, 35, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts57 = FileInMemory_createWithData (3004, reinterpret_cast (&espeakdata_dicts57_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/sw_dict", L"sw"); Collection_addItem (me.peek(), espeakdata_dicts57.transfer()); static unsigned char espeakdata_dicts58_data[78962] = { 0, 4, 0, 0, 130, 36, 0, 0, 9, 134, 224, 174, 164, 224, 174, 169, 20, 0, 18, 143, 224, 174, 154, 224, 174, 176, 224, 175, 141, 224, 174, 154, 224, 175, 141, 20, 0, 0, 0, 0, 6, 65, 4, 112, 57, 0, 0, 20, 12, 95, 35, 45, 224, 174, 181, 224, 174, 164, 224, 175, 129, 116, 82, 107, 70, 120, 0, 0, 24, 149, 224, 174, 154, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 169, 224, 175, 141, 20, 9, 134, 224, 174, 164, 224, 174, 181, 20, 0, 21, 146, 224, 174, 164, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 174, 224, 175, 141, 20, 0, 6, 65, 8, 69, 110, 0, 0, 0, 0, 0, 21, 6, 224, 174, 170, 224, 174, 191, 69, 37, 57, 112, 0, 24, 82, 46, 32, 224, 174, 143, 32, 6, 65, 12, 87, 110, 0, 0, 27, 152, 224, 174, 170, 224, 175, 139, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 174, 190, 224, 174, 175, 224, 175, 141, 20, 0, 0, 0, 6, 65, 16, 70, 110, 0, 0, 0, 15, 140, 224, 174, 149, 224, 175, 129, 224, 174, 164, 224, 174, 191, 20, 15, 140, 224, 174, 170, 224, 175, 139, 224, 174, 169, 224, 174, 191, 20, 9, 134, 224, 174, 170, 224, 174, 181, 20, 11, 6, 224, 174, 178, 224, 175, 141, 37, 55, 0, 0, 0, 18, 143, 224, 174, 170, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 190, 20, 5, 65, 20, 110, 0, 0, 12, 137, 224, 174, 149, 224, 174, 190, 224, 174, 169, 20, 0, 0, 13, 6, 224, 174, 170, 224, 174, 170, 48, 107, 48, 107, 0, 0, 15, 140, 224, 174, 170, 224, 175, 130, 224, 174, 174, 224, 175, 141, 20, 6, 65, 24, 114, 81, 0, 0, 0, 0, 18, 143, 224, 174, 170, 224, 175, 139, 224, 174, 149, 224, 174, 174, 224, 175, 141, 20, 0, 6, 65, 28, 73, 110, 0, 0, 0, 13, 4, 95, 54, 48, 15, 35, 51, 120, 69, 107, 70, 0, 0, 0, 6, 65, 32, 112, 74, 0, 0, 11, 1, 33, 82, 37, 57, 107, 48, 48, 120, 0, 0, 0, 8, 1, 35, 38, 36, 64, 0, 27, 0, 27, 152, 224, 174, 170, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 154, 224, 175, 141, 20, 6, 65, 36, 116, 57, 0, 0, 14, 1, 37, 82, 37, 90, 120, 49, 49, 116, 139, 120, 0, 27, 0, 10, 1, 38, 63, 107, 138, 51, 120, 63, 0, 0, 30, 155, 224, 174, 170, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 178, 224, 174, 190, 224, 174, 169, 20, 0, 7, 65, 40, 73, 112, 57, 0, 0, 0, 13, 1, 42, 48, 36, 34, 120, 49, 49, 107, 55, 0, 27, 0, 11, 1, 43, 49, 121, 138, 138, 107, 55, 0, 27, 0, 7, 65, 44, 49, 112, 57, 0, 0, 0, 0, 9, 1, 47, 87, 116, 57, 82, 120, 0, 0, 6, 65, 48, 114, 55, 0, 0, 15, 140, 224, 174, 170, 224, 175, 130, 224, 174, 174, 224, 174, 190, 20, 0, 15, 140, 224, 174, 170, 224, 175, 139, 224, 174, 149, 224, 174, 191, 20, 0, 0, 6, 65, 52, 114, 63, 0, 0, 0, 0, 33, 158, 224, 174, 170, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 174, 190, 20, 0, 6, 65, 56, 114, 50, 0, 0, 0, 0, 0, 10, 1, 60, 49, 40, 51, 132, 82, 120, 0, 5, 65, 60, 117, 0, 0, 14, 1, 61, 87, 35, 63, 107, 50, 48, 116, 139, 120, 0, 27, 0, 10, 1, 62, 63, 37, 79, 120, 70, 37, 0, 0, 0, 6, 65, 64, 48, 110, 0, 0, 0, 0, 0, 7, 65, 68, 49, 57, 121, 0, 0, 0, 15, 140, 224, 174, 149, 224, 175, 139, 224, 174, 178, 224, 174, 191, 20, 0, 0, 6, 65, 72, 116, 51, 0, 0, 15, 9, 224, 174, 149, 224, 174, 170, 224, 175, 141, 49, 107, 48, 0, 0, 0, 0, 15, 140, 224, 174, 149, 224, 174, 190, 224, 174, 159, 224, 175, 141, 20, 15, 140, 224, 174, 164, 224, 175, 138, 224, 174, 170, 224, 175, 141, 20, 18, 12, 224, 174, 170, 224, 175, 128, 224, 174, 170, 224, 175, 141, 69, 110, 48, 0, 6, 65, 76, 114, 87, 0, 0, 0, 0, 0, 6, 65, 80, 136, 110, 0, 0, 0, 11, 6, 224, 174, 185, 224, 175, 141, 37, 97, 0, 0, 0, 6, 65, 84, 57, 121, 0, 0, 0, 10, 4, 95, 49, 67, 15, 50, 121, 51, 0, 0, 0, 6, 65, 88, 82, 110, 0, 0, 12, 137, 224, 174, 149, 224, 174, 174, 224, 175, 141, 20, 0, 0, 19, 11, 95, 35, 224, 174, 181, 224, 174, 164, 224, 175, 129, 116, 82, 107, 70, 120, 0, 0, 15, 1, 92, 48, 6, 37, 50, 15, 87, 4, 116, 57, 82, 120, 0, 11, 65, 92, 70, 107, 69, 107, 55, 57, 121, 0, 0, 0, 14, 4, 95, 55, 48, 15, 38, 36, 90, 120, 69, 107, 70, 0, 0, 18, 143, 224, 174, 170, 224, 175, 135, 224, 174, 149, 224, 174, 174, 224, 175, 141, 20, 18, 143, 224, 174, 170, 224, 174, 190, 224, 174, 177, 224, 174, 174, 224, 175, 141, 20, 0, 7, 65, 96, 114, 49, 87, 0, 0, 18, 4, 95, 49, 77, 50, 39, 34, 120, 55, 107, 139, 74, 107, 47, 47, 120, 0, 0, 21, 146, 224, 174, 170, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 20, 15, 4, 95, 49, 77, 51, 39, 34, 120, 49, 117, 139, 37, 112, 0, 0, 0, 7, 65, 100, 58, 116, 57, 0, 0, 0, 0, 0, 15, 140, 224, 174, 149, 224, 174, 191, 224, 174, 159, 224, 175, 129, 20, 7, 65, 104, 86, 114, 70, 0, 0, 0, 0, 0, 15, 140, 224, 174, 149, 224, 174, 191, 224, 174, 163, 224, 175, 141, 20, 15, 140, 224, 174, 149, 224, 175, 129, 224, 174, 176, 224, 175, 129, 20, 15, 140, 224, 174, 170, 224, 175, 128, 224, 174, 154, 224, 175, 141, 20, 0, 0, 0, 0, 0, 0, 11, 6, 224, 174, 180, 224, 175, 141, 37, 90, 0, 0, 12, 137, 224, 174, 164, 224, 174, 191, 224, 174, 159, 20, 0, 0, 21, 146, 224, 174, 164, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 163, 224, 175, 136, 20, 0, 0, 0, 15, 140, 224, 174, 149, 224, 174, 191, 224, 174, 169, 224, 175, 141, 20, 15, 140, 224, 174, 170, 224, 174, 149, 224, 174, 164, 224, 175, 141, 20, 0, 0, 0, 0, 13, 1, 124, 87, 36, 66, 79, 120, 47, 47, 120, 0, 27, 0, 0, 0, 0, 0, 30, 21, 224, 174, 170, 224, 174, 191, 224, 174, 176, 224, 174, 154, 224, 174, 190, 224, 174, 176, 224, 175, 141, 48, 34, 107, 87, 116, 34, 0, 0, 0, 0, 0, 0, 16, 4, 95, 49, 57, 15, 48, 35, 47, 47, 39, 50, 69, 107, 70, 0, 0, 0, 0, 0, 0, 30, 155, 224, 174, 149, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 177, 224, 175, 129, 20, 0, 21, 146, 224, 174, 170, 224, 174, 176, 224, 175, 141, 224, 174, 174, 224, 174, 191, 224, 174, 175, 20, 0, 0, 21, 146, 224, 174, 170, 224, 175, 128, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 175, 129, 20, 0, 12, 137, 224, 174, 149, 224, 174, 164, 224, 174, 191, 20, 11, 4, 95, 49, 67, 48, 50, 121, 51, 120, 0, 0, 0, 0, 0, 0, 18, 143, 224, 174, 164, 224, 175, 135, 224, 174, 181, 224, 174, 164, 224, 174, 190, 20, 0, 18, 143, 224, 174, 170, 224, 174, 156, 224, 175, 141, 224, 174, 156, 224, 174, 191, 20, 0, 13, 4, 95, 50, 67, 15, 37, 34, 120, 50, 121, 51, 0, 0, 0, 21, 146, 224, 174, 149, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 20, 0, 21, 146, 224, 174, 170, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 136, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 154, 224, 174, 190, 224, 174, 175, 224, 174, 190, 20, 12, 137, 224, 174, 164, 224, 174, 191, 224, 174, 169, 20, 0, 15, 140, 224, 174, 149, 224, 175, 139, 224, 174, 170, 224, 174, 191, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 170, 224, 175, 141, 224, 174, 176, 224, 174, 190, 20, 15, 140, 224, 174, 170, 224, 174, 159, 224, 174, 181, 224, 174, 190, 20, 0, 0, 0, 0, 18, 143, 224, 174, 164, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 191, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 129, 20, 0, 0, 15, 4, 95, 49, 49, 15, 48, 35, 47, 37, 50, 39, 50, 51, 0, 11, 6, 224, 174, 183, 224, 175, 141, 37, 91, 0, 0, 0, 9, 134, 224, 174, 149, 224, 175, 139, 20, 0, 0, 9, 134, 224, 174, 149, 224, 174, 149, 20, 11, 6, 224, 174, 181, 224, 175, 141, 37, 82, 0, 11, 6, 224, 174, 149, 224, 175, 141, 37, 49, 0, 0, 15, 9, 224, 174, 147, 224, 174, 149, 224, 175, 139, 117, 106, 117, 0, 0, 0, 0, 0, 14, 4, 95, 50, 67, 48, 37, 34, 120, 50, 121, 51, 120, 0, 0, 15, 140, 224, 174, 164, 224, 174, 181, 224, 174, 149, 224, 175, 141, 20, 15, 140, 224, 174, 164, 224, 174, 159, 224, 174, 149, 224, 175, 141, 20, 0, 0, 0, 0, 9, 134, 224, 174, 149, 224, 174, 159, 20, 0, 0, 33, 158, 224, 174, 164, 224, 175, 138, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 177, 224, 175, 129, 20, 21, 146, 224, 174, 170, 224, 175, 128, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 20, 13, 4, 95, 51, 67, 15, 63, 40, 50, 50, 121, 51, 0, 0, 13, 4, 95, 4, 16, 20, 10, 48, 40, 62, 62, 37, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 224, 174, 149, 224, 174, 169, 20, 11, 4, 95, 49, 48, 15, 48, 35, 47, 47, 0, 0, 0, 0, 0, 0, 9, 134, 224, 174, 149, 224, 174, 174, 20, 0, 0, 24, 149, 224, 174, 164, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 175, 224, 175, 141, 20, 21, 146, 224, 174, 170, 224, 174, 181, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 20, 0, 0, 18, 143, 224, 174, 149, 224, 174, 174, 224, 175, 141, 224, 174, 169, 224, 175, 129, 20, 0, 0, 0, 0, 0, 27, 152, 224, 174, 149, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 169, 224, 175, 141, 20, 27, 152, 224, 174, 164, 224, 174, 181, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 169, 224, 175, 141, 20, 14, 5, 95, 48, 77, 50, 24, 55, 107, 139, 74, 107, 63, 0, 0, 24, 149, 224, 174, 149, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 175, 129, 224, 174, 169, 224, 175, 129, 20, 0, 16, 4, 95, 49, 50, 15, 48, 107, 50, 50, 37, 34, 107, 64, 139, 0, 0, 0, 23, 15, 224, 174, 170, 224, 175, 139, 224, 174, 169, 224, 175, 141, 224, 174, 178, 81, 117, 50, 55, 107, 0, 0, 0, 0, 0, 30, 6, 224, 174, 149, 224, 174, 191, 49, 37, 55, 117, 63, 110, 138, 138, 107, 34, 0, 24, 82, 46, 32, 224, 174, 174, 224, 175, 128, 32, 0, 0, 33, 158, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 175, 129, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 175, 129, 20, 21, 146, 224, 174, 164, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 20, 0, 0, 0, 15, 140, 224, 174, 164, 224, 174, 176, 224, 175, 129, 224, 174, 174, 20, 0, 27, 152, 224, 174, 164, 224, 175, 128, 224, 174, 176, 224, 174, 174, 224, 175, 129, 224, 174, 179, 224, 175, 141, 224, 174, 179, 20, 0, 12, 137, 224, 174, 149, 224, 175, 129, 224, 174, 163, 20, 0, 0, 0, 0, 24, 149, 224, 174, 164, 224, 175, 128, 224, 174, 170, 224, 174, 190, 224, 174, 181, 224, 174, 179, 224, 174, 191, 20, 0, 0, 0, 0, 0, 0, 14, 5, 95, 48, 77, 49, 24, 116, 57, 37, 34, 107, 63, 0, 0, 21, 146, 224, 174, 170, 224, 175, 139, 224, 174, 175, 224, 174, 191, 224, 174, 153, 224, 175, 141, 20, 0, 0, 15, 140, 224, 174, 164, 224, 174, 191, 224, 174, 159, 224, 175, 129, 20, 0, 0, 15, 140, 224, 174, 170, 224, 174, 190, 224, 174, 181, 224, 175, 135, 20, 0, 42, 167, 224, 174, 170, 224, 174, 178, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 169, 224, 175, 141, 20, 0, 27, 152, 224, 174, 170, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 169, 224, 175, 141, 20, 0, 0, 21, 146, 224, 174, 149, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 129, 20, 0, 15, 140, 224, 174, 149, 224, 174, 153, 224, 175, 141, 224, 174, 149, 20, 0, 27, 152, 224, 174, 149, 224, 175, 139, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 20, 27, 152, 224, 174, 149, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 175, 129, 20, 14, 4, 95, 51, 67, 48, 63, 40, 50, 50, 121, 51, 120, 0, 0, 0, 0, 0, 0, 12, 4, 95, 52, 67, 15, 50, 116, 50, 121, 51, 0, 12, 5, 95, 48, 77, 51, 24, 49, 117, 139, 37, 0, 0, 0, 24, 149, 224, 174, 170, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 178, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 12, 224, 174, 137, 224, 174, 170, 224, 175, 141, 224, 174, 170, 40, 69, 69, 107, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 170, 224, 174, 190, 224, 174, 183, 224, 174, 190, 20, 0, 0, 9, 3, 95, 49, 15, 39, 50, 51, 0, 0, 0, 0, 18, 12, 224, 174, 170, 224, 174, 191, 224, 174, 159, 224, 175, 141, 69, 37, 138, 0, 15, 140, 224, 174, 170, 224, 174, 191, 224, 174, 159, 224, 175, 141, 20, 0, 21, 146, 224, 174, 170, 224, 175, 139, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 20, 0, 0, 0, 0, 11, 3, 95, 50, 15, 37, 34, 107, 64, 139, 0, 13, 4, 95, 52, 67, 48, 50, 116, 50, 121, 51, 120, 0, 0, 0, 0, 0, 0, 27, 152, 224, 174, 164, 224, 175, 129, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 181, 224, 174, 191, 20, 11, 4, 95, 53, 67, 15, 132, 50, 121, 51, 0, 0, 0, 0, 10, 3, 95, 51, 15, 63, 121, 50, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 164, 224, 174, 190, 224, 174, 169, 224, 175, 129, 20, 13, 3, 95, 50, 48, 37, 34, 120, 69, 107, 70, 120, 0, 0, 0, 0, 0, 27, 152, 224, 174, 170, 224, 175, 139, 224, 174, 169, 224, 175, 141, 224, 174, 154, 224, 174, 190, 224, 174, 175, 224, 175, 141, 20, 0, 9, 3, 95, 53, 15, 132, 50, 70, 0, 0, 0, 0, 18, 12, 224, 174, 154, 224, 175, 134, 224, 174, 159, 224, 175, 141, 87, 36, 138, 0, 27, 152, 224, 174, 170, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 169, 224, 175, 141, 20, 13, 3, 95, 51, 48, 63, 40, 48, 48, 107, 70, 120, 0, 0, 0, 0, 0, 15, 140, 224, 174, 149, 224, 175, 140, 224, 174, 169, 224, 175, 141, 20, 0, 8, 3, 95, 54, 15, 116, 51, 0, 0, 0, 18, 143, 224, 174, 164, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 20, 0, 0, 0, 0, 0, 0, 9, 3, 95, 55, 15, 38, 112, 55, 0, 0, 0, 0, 0, 0, 0, 0, 18, 143, 224, 174, 170, 224, 175, 139, 224, 174, 164, 224, 174, 169, 224, 175, 136, 20, 0, 0, 0, 21, 146, 224, 174, 164, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 169, 224, 175, 136, 20, 0, 14, 3, 95, 51, 88, 63, 40, 48, 48, 107, 47, 47, 120, 0, 13, 3, 95, 54, 48, 35, 51, 120, 69, 107, 70, 120, 0, 0, 0, 0, 21, 146, 224, 174, 164, 224, 175, 128, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 175, 136, 20, 0, 0, 11, 3, 95, 57, 15, 39, 50, 69, 107, 139, 0, 0, 15, 140, 224, 174, 164, 224, 174, 190, 224, 174, 181, 224, 175, 135, 20, 0, 0, 14, 3, 95, 55, 48, 38, 36, 90, 120, 69, 107, 70, 120, 0, 0, 24, 149, 224, 174, 170, 224, 174, 178, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 20, 12, 3, 95, 49, 67, 50, 121, 138, 138, 51, 37, 0, 0, 0, 0, 0, 12, 4, 95, 53, 67, 48, 132, 50, 121, 51, 120, 0, 0, 0, 16, 3, 95, 49, 57, 48, 35, 47, 47, 39, 50, 69, 107, 70, 120, 0, 0, 0, 15, 3, 95, 50, 67, 37, 34, 120, 50, 121, 138, 138, 51, 37, 0, 0, 13, 4, 95, 54, 67, 15, 35, 51, 120, 50, 121, 51, 0, 0, 0, 0, 0, 24, 149, 224, 174, 149, 224, 175, 139, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 20, 15, 140, 224, 174, 170, 224, 174, 181, 224, 174, 169, 224, 174, 191, 20, 0, 15, 3, 95, 49, 49, 48, 35, 47, 37, 50, 39, 50, 51, 120, 0, 0, 11, 3, 95, 49, 48, 48, 35, 47, 47, 120, 0, 0, 15, 3, 95, 51, 67, 63, 40, 50, 50, 121, 138, 138, 51, 37, 0, 0, 13, 4, 95, 52, 48, 15, 50, 116, 51, 48, 107, 70, 0, 16, 3, 95, 49, 50, 48, 107, 50, 50, 37, 34, 107, 64, 139, 120, 0, 0, 0, 0, 10, 3, 95, 52, 15, 50, 116, 50, 79, 0, 0, 0, 0, 15, 3, 95, 55, 88, 38, 36, 90, 120, 69, 107, 47, 47, 120, 0, 0, 14, 3, 95, 52, 67, 50, 116, 50, 121, 138, 138, 51, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 53, 67, 132, 50, 121, 138, 138, 51, 37, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 52, 48, 50, 116, 51, 48, 107, 70, 120, 0, 11, 3, 95, 49, 88, 48, 35, 70, 37, 50, 0, 0, 15, 3, 95, 54, 67, 35, 51, 120, 50, 121, 138, 138, 51, 37, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 50, 88, 37, 34, 120, 69, 107, 47, 47, 120, 0, 12, 3, 95, 53, 48, 132, 63, 69, 107, 70, 120, 0, 0, 16, 3, 95, 55, 67, 38, 36, 90, 120, 50, 121, 138, 138, 51, 37, 0, 0, 0, 0, 0, 10, 3, 95, 56, 15, 38, 36, 138, 138, 0, 0, 0, 0, 0, 19, 12, 224, 174, 154, 224, 175, 128, 224, 174, 154, 224, 175, 128, 74, 110, 74, 110, 0, 15, 3, 95, 56, 67, 38, 36, 64, 64, 121, 138, 138, 51, 37, 0, 0, 0, 0, 0, 16, 3, 95, 63, 63, 49, 40, 51, 37, 57, 4, 110, 139, 120, 10, 0, 0, 0, 18, 143, 224, 174, 164, 224, 174, 175, 224, 174, 190, 224, 174, 179, 224, 175, 129, 20, 0, 28, 18, 224, 174, 159, 224, 174, 191, 224, 174, 170, 224, 175, 129, 224, 174, 159, 224, 174, 191, 139, 114, 48, 57, 120, 138, 37, 0, 14, 3, 95, 52, 88, 50, 116, 51, 48, 107, 47, 47, 120, 0, 0, 18, 3, 95, 57, 67, 47, 39, 62, 62, 116, 57, 37, 34, 107, 47, 47, 120, 0, 8, 3, 224, 174, 143, 57, 112, 0, 0, 0, 0, 18, 12, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 70, 37, 49, 0, 15, 140, 224, 174, 149, 224, 175, 135, 224, 174, 159, 224, 175, 141, 20, 15, 140, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 20, 15, 140, 224, 174, 170, 224, 174, 159, 224, 175, 129, 224, 174, 149, 20, 0, 14, 4, 95, 54, 67, 48, 35, 51, 120, 50, 121, 51, 120, 0, 0, 21, 146, 224, 174, 170, 224, 174, 190, 224, 174, 175, 224, 175, 141, 224, 174, 184, 224, 175, 141, 20, 0, 18, 143, 224, 174, 149, 224, 174, 179, 224, 174, 191, 224, 174, 178, 224, 175, 141, 20, 18, 143, 224, 174, 170, 224, 174, 178, 224, 174, 191, 224, 174, 149, 224, 175, 141, 20, 10, 3, 224, 175, 141, 39, 138, 51, 120, 0, 0, 13, 3, 95, 53, 88, 132, 63, 69, 107, 47, 47, 120, 0, 13, 3, 95, 56, 48, 38, 36, 64, 69, 107, 70, 120, 0, 8, 3, 224, 175, 140, 146, 133, 0, 0, 0, 14, 4, 95, 55, 67, 15, 38, 36, 90, 120, 50, 121, 51, 0, 11, 6, 224, 174, 159, 224, 175, 141, 37, 138, 0, 0, 0, 8, 3, 224, 175, 136, 146, 132, 0, 0, 9, 3, 224, 175, 139, 146, 117, 12, 0, 9, 3, 224, 174, 131, 107, 79, 106, 0, 0, 8, 3, 224, 175, 138, 18, 39, 0, 14, 3, 224, 174, 130, 107, 50, 120, 87, 82, 107, 51, 107, 0, 12, 6, 224, 174, 153, 224, 175, 141, 37, 66, 79, 0, 0, 0, 15, 140, 224, 174, 149, 224, 174, 191, 224, 174, 176, 224, 175, 141, 20, 33, 24, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 70, 37, 79, 70, 37, 79, 0, 14, 3, 95, 54, 88, 35, 51, 120, 69, 107, 47, 47, 120, 0, 13, 3, 95, 57, 48, 47, 39, 64, 64, 121, 51, 120, 0, 0, 9, 3, 224, 175, 135, 146, 112, 12, 0, 0, 12, 4, 95, 53, 48, 15, 132, 63, 69, 107, 70, 0, 8, 3, 224, 175, 134, 18, 36, 0, 0, 18, 143, 224, 174, 170, 224, 175, 139, 224, 174, 169, 224, 174, 184, 224, 175, 141, 20, 8, 3, 224, 175, 129, 18, 40, 0, 0, 9, 3, 224, 175, 128, 146, 110, 12, 0, 0, 0, 9, 3, 224, 175, 130, 146, 121, 12, 0, 0, 0, 18, 143, 224, 174, 149, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 20, 18, 143, 224, 174, 170, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 20, 0, 0, 18, 12, 224, 174, 149, 224, 174, 191, 224, 174, 176, 224, 175, 135, 79, 34, 112, 0, 11, 6, 224, 174, 163, 224, 175, 141, 37, 64, 0, 0, 11, 3, 224, 175, 185, 34, 121, 69, 116, 57, 0, 0, 0, 0, 21, 146, 224, 174, 164, 224, 175, 138, 224, 174, 170, 224, 175, 141, 224, 174, 169, 224, 175, 129, 20, 0, 0, 27, 152, 224, 174, 154, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 175, 224, 175, 141, 20, 15, 140, 224, 174, 170, 224, 175, 130, 224, 174, 159, 224, 175, 141, 20, 14, 3, 95, 56, 88, 38, 36, 64, 69, 107, 47, 47, 120, 0, 0, 0, 0, 18, 143, 224, 174, 170, 224, 174, 178, 224, 174, 149, 224, 175, 141, 224, 174, 149, 20, 0, 18, 12, 224, 174, 170, 224, 175, 136, 224, 174, 149, 224, 175, 141, 69, 132, 49, 0, 0, 0, 26, 18, 224, 174, 164, 224, 174, 190, 224, 174, 153, 224, 175, 141, 224, 174, 184, 224, 175, 141, 85, 116, 66, 49, 87, 0, 0, 18, 143, 224, 174, 149, 224, 174, 181, 224, 175, 129, 224, 174, 169, 224, 175, 141, 20, 30, 155, 224, 174, 164, 224, 175, 128, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 139, 224, 174, 159, 224, 175, 129, 20, 18, 143, 224, 174, 170, 224, 174, 178, 224, 175, 141, 224, 174, 170, 224, 175, 141, 20, 0, 27, 152, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 175, 129, 224, 174, 169, 224, 175, 129, 20, 15, 3, 95, 57, 88, 47, 39, 64, 64, 121, 138, 138, 51, 120, 0, 0, 0, 11, 6, 224, 174, 175, 224, 175, 141, 37, 57, 0, 0, 0, 15, 9, 224, 174, 134, 224, 174, 149, 224, 174, 190, 116, 106, 116, 0, 0, 0, 15, 140, 224, 174, 149, 224, 174, 191, 224, 174, 178, 224, 174, 191, 20, 19, 12, 224, 174, 159, 224, 174, 191, 224, 174, 181, 224, 174, 191, 138, 37, 82, 37, 0, 11, 6, 224, 174, 177, 224, 175, 141, 37, 51, 0, 11, 6, 224, 174, 169, 224, 175, 141, 37, 50, 0, 0, 15, 140, 224, 174, 164, 224, 175, 135, 224, 174, 181, 224, 174, 190, 20, 0, 36, 24, 224, 174, 170, 224, 174, 190, 224, 174, 164, 224, 174, 176, 224, 175, 129, 224, 174, 159, 224, 174, 169, 224, 175, 141, 81, 116, 70, 107, 34, 120, 139, 107, 50, 0, 0, 0, 0, 0, 0, 0, 27, 152, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 183, 224, 175, 141, 224, 174, 159, 224, 174, 191, 20, 0, 18, 143, 224, 174, 164, 224, 174, 178, 224, 174, 190, 224, 174, 175, 224, 175, 141, 20, 0, 0, 0, 21, 146, 224, 174, 164, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 169, 224, 175, 141, 20, 0, 0, 15, 140, 224, 174, 154, 224, 174, 190, 224, 174, 176, 224, 175, 129, 20, 0, 24, 149, 224, 174, 164, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 174, 174, 224, 175, 141, 20, 11, 6, 224, 174, 179, 224, 175, 141, 37, 62, 0, 0, 0, 0, 33, 24, 224, 174, 170, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 178, 224, 175, 141, 69, 132, 49, 49, 111, 55, 0, 0, 0, 21, 146, 224, 174, 170, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 20, 0, 0, 21, 146, 224, 174, 149, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 175, 135, 20, 0, 24, 149, 224, 174, 149, 224, 174, 179, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 20, 0, 15, 4, 95, 55, 67, 48, 38, 36, 90, 120, 50, 121, 51, 120, 0, 0, 24, 149, 224, 174, 149, 224, 174, 179, 224, 174, 191, 224, 174, 178, 224, 175, 135, 224, 174, 175, 224, 175, 135, 20, 0, 0, 13, 4, 95, 56, 67, 15, 38, 36, 64, 64, 121, 51, 0, 0, 18, 143, 224, 174, 170, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 149, 20, 0, 0, 24, 149, 224, 174, 170, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 224, 175, 141, 20, 0, 0, 33, 158, 224, 174, 149, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 20, 33, 158, 224, 174, 149, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 20, 33, 158, 224, 174, 170, 224, 175, 130, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 20, 0, 9, 3, 224, 174, 190, 146, 116, 12, 0, 0, 18, 143, 224, 174, 170, 224, 174, 190, 224, 174, 178, 224, 174, 191, 224, 174, 175, 20, 8, 3, 224, 174, 191, 18, 37, 0, 0, 0, 0, 11, 6, 224, 174, 159, 224, 174, 191, 138, 37, 0, 0, 15, 4, 95, 48, 77, 50, 55, 107, 139, 74, 107, 47, 47, 120, 0, 0, 27, 152, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 169, 224, 174, 191, 20, 12, 4, 95, 48, 77, 51, 49, 117, 139, 37, 112, 0, 0, 0, 21, 146, 224, 174, 170, 224, 175, 128, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 163, 20, 15, 4, 95, 48, 77, 49, 116, 57, 37, 34, 107, 47, 47, 120, 0, 0, 0, 15, 140, 224, 174, 149, 224, 174, 191, 224, 174, 176, 224, 174, 191, 20, 0, 0, 18, 143, 224, 174, 164, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 20, 0, 0, 0, 0, 0, 0, 0, 24, 149, 224, 174, 149, 224, 174, 190, 224, 174, 175, 224, 174, 164, 224, 175, 141, 224, 174, 176, 224, 174, 191, 20, 0, 18, 143, 224, 174, 170, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 178, 20, 0, 0, 12, 137, 224, 174, 170, 224, 174, 159, 224, 174, 190, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 146, 224, 174, 170, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 154, 224, 174, 191, 224, 174, 178, 224, 174, 191, 20, 11, 6, 224, 174, 184, 224, 175, 141, 37, 87, 0, 0, 0, 18, 143, 224, 174, 170, 224, 174, 159, 224, 175, 129, 224, 174, 181, 224, 174, 190, 20, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 56, 67, 48, 38, 36, 64, 64, 121, 51, 120, 0, 0, 0, 0, 0, 23, 15, 224, 174, 154, 224, 174, 191, 224, 174, 176, 224, 174, 174, 224, 175, 141, 87, 37, 34, 107, 63, 0, 0, 0, 0, 0, 0, 32, 20, 95, 35, 224, 174, 181, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 149, 116, 82, 107, 70, 120, 63, 116, 79, 107, 0, 0, 0, 0, 0, 0, 0, 0, 23, 68, 80, 19, 73, 48, 224, 174, 164, 224, 174, 174, 224, 174, 191, 224, 174, 180, 224, 175, 141, 0, 29, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 36, 24, 224, 174, 170, 224, 174, 190, 224, 174, 164, 224, 174, 176, 224, 174, 191, 224, 174, 159, 224, 174, 174, 224, 175, 141, 81, 116, 70, 107, 34, 37, 139, 107, 63, 0, 27, 152, 224, 174, 164, 224, 175, 129, 224, 174, 181, 224, 174, 174, 224, 175, 141, 224, 174, 154, 224, 174, 174, 224, 175, 141, 20, 27, 152, 224, 174, 170, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 170, 224, 175, 141, 20, 0, 0, 0, 0, 27, 152, 224, 174, 164, 224, 175, 138, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 224, 174, 169, 224, 175, 129, 20, 0, 0, 0, 0, 0, 0, 21, 146, 224, 174, 164, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 174, 224, 175, 141, 20, 21, 146, 224, 174, 170, 224, 174, 163, 224, 175, 141, 224, 174, 164, 224, 174, 174, 224, 175, 141, 20, 21, 146, 224, 174, 170, 224, 174, 190, 224, 174, 176, 224, 174, 164, 224, 174, 174, 224, 175, 141, 20, 0, 0, 0, 0, 0, 19, 12, 224, 174, 170, 224, 175, 136, 224, 174, 178, 224, 175, 136, 81, 132, 55, 132, 0, 0, 18, 12, 224, 174, 170, 224, 175, 129, 224, 174, 159, 224, 175, 141, 81, 40, 139, 0, 15, 140, 224, 174, 149, 224, 175, 129, 224, 174, 159, 224, 175, 141, 20, 0, 14, 9, 95, 35, 45, 224, 174, 178, 224, 175, 141, 37, 55, 0, 0, 0, 18, 143, 224, 174, 170, 224, 174, 149, 224, 174, 181, 224, 174, 164, 224, 175, 141, 20, 0, 18, 12, 224, 174, 170, 224, 175, 136, 224, 174, 178, 224, 175, 141, 81, 132, 55, 0, 15, 140, 224, 174, 164, 224, 174, 169, 224, 174, 174, 224, 175, 141, 20, 15, 140, 224, 174, 170, 224, 175, 129, 224, 174, 149, 224, 175, 141, 20, 0, 0, 0, 18, 143, 224, 174, 164, 224, 175, 134, 224, 174, 169, 224, 174, 174, 224, 175, 141, 20, 12, 137, 224, 174, 170, 224, 174, 178, 224, 175, 135, 20, 0, 0, 15, 140, 224, 174, 164, 224, 174, 174, 224, 175, 141, 224, 174, 174, 20, 24, 149, 224, 174, 170, 224, 175, 141, 224, 174, 175, 224, 175, 130, 224, 174, 169, 224, 174, 184, 224, 175, 141, 20, 0, 25, 18, 224, 174, 170, 224, 174, 191, 224, 174, 176, 224, 175, 135, 224, 174, 149, 224, 175, 141, 69, 34, 112, 49, 0, 27, 18, 95, 35, 45, 224, 174, 181, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 175, 141, 116, 82, 107, 70, 120, 63, 0, 0, 0, 27, 152, 224, 174, 170, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 141, 20, 27, 152, 224, 174, 170, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 164, 224, 175, 141, 20, 0, 0, 0, 0, 23, 15, 224, 174, 170, 224, 175, 135, 224, 174, 169, 224, 175, 141, 224, 174, 178, 81, 112, 50, 55, 107, 0, 0, 0, 0, 17, 4, 95, 57, 67, 48, 47, 39, 62, 62, 116, 57, 37, 34, 107, 63, 0, 0, 0, 0, 0, 12, 137, 224, 174, 170, 224, 174, 178, 224, 174, 191, 20, 0, 0, 0, 0, 0, 12, 137, 224, 174, 170, 224, 174, 176, 224, 174, 164, 20, 21, 146, 224, 174, 170, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 20, 0, 24, 149, 224, 174, 170, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 20, 0, 13, 4, 95, 56, 48, 15, 38, 36, 64, 69, 107, 70, 0, 0, 0, 0, 0, 12, 137, 224, 174, 149, 224, 174, 175, 224, 174, 190, 20, 0, 0, 0, 12, 137, 224, 174, 164, 224, 174, 190, 224, 174, 169, 20, 0, 0, 0, 0, 0, 12, 137, 224, 174, 170, 224, 174, 190, 224, 174, 178, 20, 0, 0, 12, 137, 224, 174, 170, 224, 174, 190, 224, 174, 176, 20, 0, 0, 0, 0, 0, 0, 12, 137, 224, 174, 170, 224, 174, 190, 224, 174, 170, 20, 0, 0, 0, 12, 137, 224, 174, 170, 224, 174, 190, 224, 174, 169, 20, 0, 0, 0, 0, 24, 149, 224, 174, 164, 224, 175, 128, 224, 174, 176, 224, 174, 174, 224, 174, 177, 224, 175, 141, 224, 174, 177, 20, 0, 0, 0, 27, 152, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 177, 224, 175, 141, 224, 174, 177, 20, 0, 18, 143, 224, 174, 170, 224, 174, 190, 224, 174, 178, 224, 175, 141, 224, 174, 175, 20, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 170, 224, 175, 128, 224, 174, 159, 224, 174, 190, 20, 0, 15, 140, 224, 174, 170, 224, 175, 128, 224, 174, 159, 224, 174, 191, 20, 15, 140, 224, 174, 170, 224, 175, 139, 224, 174, 164, 224, 174, 191, 20, 0, 0, 15, 140, 224, 174, 170, 224, 174, 190, 224, 174, 178, 224, 175, 129, 20, 0, 0, 0, 11, 2, 194, 190, 63, 40, 49, 49, 116, 55, 0, 0, 26, 18, 224, 174, 176, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 34, 36, 139, 139, 37, 0, 18, 143, 224, 174, 170, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 174, 190, 20, 13, 2, 195, 183, 82, 107, 79, 120, 47, 47, 107, 55, 0, 0, 8, 2, 194, 188, 49, 116, 55, 0, 0, 8, 2, 194, 189, 35, 34, 132, 0, 11, 6, 224, 174, 182, 224, 175, 141, 37, 89, 0, 0, 21, 146, 224, 174, 170, 224, 174, 190, 224, 174, 181, 224, 175, 141, 224, 174, 178, 224, 174, 190, 20, 0, 21, 146, 224, 174, 170, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 191, 20, 13, 8, 95, 35, 224, 174, 174, 224, 175, 141, 116, 63, 0, 0, 0, 0, 0, 15, 140, 224, 174, 164, 224, 174, 190, 224, 174, 178, 224, 175, 141, 20, 18, 12, 224, 174, 170, 224, 175, 128, 224, 174, 178, 224, 175, 141, 81, 110, 55, 0, 0, 0, 0, 18, 143, 224, 174, 170, 224, 174, 190, 224, 174, 163, 224, 174, 174, 224, 175, 141, 20, 0, 0, 0, 0, 0, 0, 24, 149, 224, 174, 170, 224, 174, 190, 224, 174, 149, 224, 174, 181, 224, 174, 164, 224, 174, 174, 224, 175, 141, 20, 33, 21, 95, 35, 45, 224, 174, 181, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 149, 116, 82, 107, 70, 120, 63, 116, 79, 107, 0, 0, 13, 4, 95, 57, 48, 15, 47, 39, 64, 64, 121, 51, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 149, 224, 174, 169, 224, 174, 174, 224, 175, 141, 20, 0, 0, 21, 146, 224, 174, 170, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 20, 0, 0, 0, 26, 17, 95, 35, 224, 174, 181, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 175, 141, 116, 82, 107, 70, 120, 63, 0, 0, 0, 12, 137, 224, 174, 164, 224, 175, 138, 224, 174, 179, 20, 0, 51, 36, 224, 174, 170, 224, 174, 190, 224, 174, 164, 224, 174, 176, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 224, 174, 174, 224, 174, 178, 224, 175, 141, 81, 116, 70, 107, 34, 37, 55, 55, 116, 63, 107, 55, 0, 0, 24, 149, 224, 174, 149, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 174, 224, 175, 141, 20, 0, 0, 0, 27, 152, 224, 174, 170, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 175, 141, 20, 27, 152, 224, 174, 170, 224, 174, 181, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 174, 224, 175, 141, 20, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 170, 224, 174, 191, 224, 174, 184, 224, 174, 191, 20, 0, 18, 143, 224, 174, 164, 224, 174, 190, 224, 174, 175, 224, 174, 174, 224, 175, 141, 20, 0, 0, 15, 140, 224, 174, 170, 224, 174, 190, 224, 174, 178, 224, 174, 190, 20, 0, 25, 18, 224, 174, 159, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 154, 224, 175, 141, 138, 116, 34, 74, 0, 0, 0, 0, 0, 0, 0, 21, 146, 224, 174, 149, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 191, 20, 21, 146, 224, 174, 170, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 178, 224, 174, 191, 20, 13, 8, 95, 35, 224, 174, 178, 224, 175, 141, 37, 55, 0, 0, 0, 0, 0, 15, 140, 224, 174, 170, 224, 174, 191, 224, 174, 178, 224, 175, 141, 20, 0, 0, 33, 158, 224, 174, 164, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 163, 224, 175, 141, 224, 174, 175, 224, 174, 174, 224, 175, 141, 20, 0, 18, 143, 224, 174, 170, 224, 174, 190, 224, 174, 149, 224, 174, 174, 224, 175, 141, 20, 0, 15, 140, 224, 174, 170, 224, 174, 190, 224, 174, 170, 224, 175, 129, 20, 0, 0, 26, 18, 224, 174, 170, 224, 175, 135, 224, 174, 169, 224, 174, 191, 224, 174, 178, 224, 175, 141, 81, 112, 50, 37, 55, 0, 26, 18, 224, 174, 170, 224, 175, 139, 224, 174, 169, 224, 174, 191, 224, 174, 178, 224, 175, 141, 81, 117, 50, 37, 55, 0, 0, 33, 158, 224, 174, 170, 224, 175, 139, 224, 174, 176, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 174, 20, 0, 0, 24, 149, 224, 174, 154, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 174, 224, 175, 141, 20, 0, 0, 0, 27, 152, 224, 174, 149, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 224, 175, 141, 20, 27, 152, 224, 174, 164, 224, 174, 181, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 178, 224, 175, 141, 20, 27, 152, 224, 174, 170, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 178, 224, 175, 141, 20, 0, 17, 5, 95, 49, 77, 50, 24, 39, 34, 120, 55, 107, 139, 74, 107, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 5, 95, 49, 77, 51, 24, 39, 34, 120, 49, 117, 139, 37, 0, 0, 19, 12, 224, 174, 170, 224, 174, 190, 224, 174, 170, 224, 174, 190, 69, 116, 69, 116, 0, 15, 140, 224, 174, 170, 224, 174, 190, 224, 174, 170, 224, 174, 190, 20, 0, 0, 39, 164, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 129, 224, 174, 174, 224, 175, 141, 20, 11, 2, 95, 34, 63, 112, 51, 79, 117, 62, 0, 0, 0, 0, 17, 2, 95, 39, 39, 138, 51, 132, 15, 63, 6, 112, 51, 79, 117, 62, 0, 0, 0, 13, 4, 95, 50, 48, 15, 37, 34, 120, 69, 107, 70, 0, 0, 0, 0, 14, 4, 95, 3, 1, 16, 49, 35, 48, 37, 138, 107, 55, 0, 0, 14, 2, 95, 41, 82, 107, 55, 107, 15, 48, 37, 51, 132, 0, 0, 13, 2, 95, 40, 37, 139, 107, 15, 48, 37, 51, 132, 0, 0, 0, 16, 2, 95, 46, 63, 40, 138, 51, 120, 15, 48, 40, 62, 62, 37, 0, 0, 12, 2, 95, 45, 37, 64, 132, 48, 48, 120, 79, 0, 0, 14, 2, 95, 44, 49, 116, 55, 15, 48, 40, 62, 62, 37, 0, 0, 10, 2, 95, 51, 63, 121, 50, 51, 120, 0, 0, 11, 2, 95, 50, 37, 34, 107, 64, 139, 120, 0, 0, 9, 2, 95, 49, 39, 50, 51, 120, 0, 0, 12, 2, 95, 48, 87, 40, 90, 37, 57, 107, 63, 0, 0, 9, 2, 95, 55, 38, 112, 90, 120, 0, 0, 8, 2, 95, 54, 116, 51, 120, 0, 0, 9, 2, 95, 53, 132, 50, 70, 120, 0, 0, 10, 2, 95, 52, 50, 116, 50, 79, 120, 0, 0, 15, 2, 95, 59, 116, 34, 132, 69, 15, 48, 40, 62, 62, 37, 0, 0, 17, 2, 95, 58, 63, 40, 49, 49, 116, 55, 15, 48, 40, 62, 62, 37, 0, 0, 11, 2, 95, 57, 39, 50, 69, 107, 139, 120, 0, 0, 18, 12, 224, 174, 170, 224, 174, 191, 224, 174, 176, 224, 174, 190, 69, 34, 116, 0, 10, 2, 95, 56, 38, 36, 138, 138, 120, 0, 0, 10, 2, 95, 63, 49, 112, 62, 82, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 170, 224, 174, 190, 224, 174, 174, 224, 174, 190, 20, 0, 0, 0, 0, 24, 149, 224, 174, 164, 224, 174, 175, 224, 174, 190, 224, 174, 168, 224, 174, 191, 224, 174, 164, 224, 174, 191, 20, 0, 0, 0, 0, 0, 15, 140, 224, 174, 164, 224, 174, 191, 224, 174, 174, 224, 175, 141, 20, 16, 2, 95, 91, 37, 139, 107, 15, 87, 35, 70, 120, 34, 107, 63, 0, 0, 0, 0, 18, 143, 224, 174, 170, 224, 174, 178, 224, 174, 174, 224, 174, 190, 224, 174, 149, 20, 0, 14, 2, 95, 95, 35, 139, 37, 79, 15, 49, 117, 139, 120, 0, 0, 0, 17, 2, 95, 93, 82, 107, 55, 107, 15, 87, 35, 70, 120, 34, 107, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 51, 48, 15, 63, 40, 48, 48, 107, 70, 0, 0, 0, 15, 140, 224, 174, 170, 224, 174, 178, 224, 174, 174, 224, 175, 141, 20, 0, 0, 15, 140, 224, 174, 149, 224, 175, 141, 224, 174, 176, 224, 175, 135, 20, 0, 0, 0, 0, 21, 146, 224, 174, 170, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 174, 224, 175, 141, 20, 21, 146, 224, 174, 170, 224, 174, 190, 224, 174, 164, 224, 174, 190, 224, 174, 174, 224, 175, 141, 20, 0, 0, 0, 24, 149, 224, 174, 164, 224, 174, 176, 224, 174, 191, 224, 174, 154, 224, 174, 169, 224, 174, 174, 224, 175, 141, 20, 0, 0, 21, 146, 224, 174, 154, 224, 175, 128, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 175, 128, 20, 0, 0, 0, 33, 158, 224, 174, 170, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 179, 224, 174, 191, 224, 174, 174, 224, 174, 190, 224, 174, 184, 224, 175, 141, 20, 0, 0, 18, 12, 224, 174, 164, 224, 175, 128, 224, 174, 170, 224, 175, 141, 70, 110, 48, 0, 15, 140, 224, 174, 149, 224, 174, 159, 224, 174, 174, 224, 175, 141, 20, 14, 2, 95, 123, 37, 139, 107, 15, 79, 107, 64, 107, 63, 0, 0, 0, 0, 18, 143, 224, 174, 170, 224, 174, 176, 224, 174, 164, 224, 174, 174, 224, 175, 141, 20, 0, 0, 0, 21, 146, 224, 174, 149, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 174, 224, 175, 141, 20, 15, 2, 95, 125, 82, 107, 55, 107, 15, 79, 107, 64, 107, 63, 0, 0, 0, 0, 0, 0, 0, 35, 24, 224, 174, 170, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 170, 224, 175, 141, 69, 107, 47, 47, 37, 34, 107, 48, 0, 15, 140, 224, 174, 170, 224, 174, 176, 224, 174, 164, 224, 175, 141, 20, 0, 0, 0, 0, 15, 140, 224, 174, 164, 224, 174, 191, 224, 174, 178, 224, 175, 141, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 27, 152, 224, 174, 170, 224, 175, 128, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 178, 224, 175, 141, 20, 27, 152, 224, 174, 170, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 224, 175, 141, 20, 0, 24, 149, 224, 174, 149, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 169, 20, 0, 0, 23, 15, 224, 174, 170, 224, 174, 190, 224, 174, 164, 224, 174, 176, 224, 175, 141, 81, 116, 70, 107, 34, 0, 0, 27, 152, 224, 174, 170, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 146, 224, 174, 170, 224, 175, 130, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 190, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 170, 224, 174, 191, 224, 174, 154, 224, 174, 191, 20, 0, 15, 140, 224, 174, 170, 224, 174, 178, 224, 174, 174, 224, 174, 190, 20, 0, 0, 0, 0, 0, 0, 0, 0, 24, 149, 224, 174, 149, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 190, 224, 174, 174, 224, 174, 191, 20, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 174, 154, 224, 175, 141, 37, 74, 0, 0, 0, 0, 0, 11, 6, 224, 174, 156, 224, 175, 141, 37, 73, 0, 0, 0, 0, 0, 0, 0, 15, 140, 224, 174, 149, 224, 175, 129, 224, 174, 170, 224, 175, 141, 20, 15, 140, 224, 174, 170, 224, 175, 135, 224, 174, 183, 224, 175, 141, 20, 0, 0, 21, 146, 224, 174, 170, 224, 174, 190, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 141, 20, 0, 0, 0, 0, 21, 146, 224, 174, 164, 224, 175, 136, 224, 174, 181, 224, 174, 164, 224, 174, 174, 224, 175, 141, 20, 11, 6, 224, 174, 158, 224, 175, 141, 37, 65, 0, 0, 0, 0, 14, 9, 95, 35, 45, 224, 174, 174, 224, 175, 141, 116, 63, 0, 0, 0, 0, 18, 12, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 138, 37, 49, 0, 18, 12, 224, 174, 154, 224, 174, 191, 224, 174, 149, 224, 175, 141, 74, 37, 49, 0, 9, 134, 224, 174, 154, 224, 175, 135, 20, 0, 0, 0, 18, 143, 224, 174, 170, 224, 175, 135, 224, 174, 164, 224, 174, 174, 224, 175, 141, 20, 0, 15, 140, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 20, 0, 0, 33, 158, 224, 174, 164, 224, 174, 181, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 169, 224, 174, 190, 224, 174, 178, 224, 175, 141, 20, 25, 18, 224, 174, 170, 224, 175, 141, 224, 174, 176, 224, 175, 135, 224, 174, 149, 224, 175, 141, 69, 34, 112, 49, 0, 0, 9, 134, 224, 174, 154, 224, 175, 128, 20, 0, 9, 134, 224, 174, 164, 224, 175, 139, 20, 0, 0, 11, 6, 224, 174, 170, 224, 175, 141, 37, 48, 0, 0, 0, 0, 24, 149, 224, 174, 149, 224, 174, 179, 224, 174, 191, 224, 174, 178, 224, 175, 129, 224, 174, 174, 224, 175, 141, 20, 24, 149, 224, 174, 164, 224, 175, 134, 224, 174, 169, 224, 174, 174, 224, 175, 129, 224, 174, 174, 224, 175, 141, 20, 24, 149, 224, 174, 164, 224, 175, 128, 224, 174, 176, 224, 174, 174, 224, 175, 129, 224, 174, 174, 224, 175, 141, 20, 0, 11, 6, 224, 174, 164, 224, 175, 141, 37, 47, 0, 0, 0, 18, 12, 224, 174, 170, 224, 175, 139, 224, 174, 169, 224, 175, 141, 81, 117, 50, 0, 21, 146, 224, 174, 154, 224, 175, 135, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 175, 135, 20, 27, 152, 224, 174, 164, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 174, 224, 175, 129, 224, 174, 174, 224, 175, 141, 20, 27, 152, 224, 174, 170, 224, 175, 130, 224, 174, 149, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 174, 224, 175, 141, 20, 0, 0, 0, 18, 143, 224, 174, 170, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 175, 141, 20, 0, 9, 134, 224, 174, 164, 224, 174, 159, 20, 15, 140, 224, 174, 170, 224, 175, 129, 224, 174, 184, 224, 175, 141, 20, 0, 0, 21, 146, 224, 174, 170, 224, 175, 128, 224, 174, 176, 224, 174, 191, 224, 174, 169, 224, 175, 141, 20, 21, 146, 224, 174, 170, 224, 175, 139, 224, 174, 184, 224, 174, 191, 224, 174, 169, 224, 175, 141, 20, 18, 143, 224, 174, 170, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 178, 20, 0, 0, 0, 0, 11, 6, 224, 174, 174, 224, 175, 141, 37, 63, 0, 0, 0, 32, 24, 224, 174, 159, 224, 174, 191, 224, 174, 176, 224, 175, 135, 224, 174, 175, 224, 174, 191, 224, 174, 169, 224, 175, 141, 138, 34, 112, 57, 50, 0, 0, 0, 33, 158, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 177, 224, 175, 129, 20, 12, 137, 224, 174, 170, 224, 175, 130, 224, 174, 164, 20, 11, 6, 224, 174, 176, 224, 175, 141, 37, 34, 0, 11, 6, 224, 174, 168, 224, 175, 141, 37, 50, 0, 0, 0, 0, 16, 6, 224, 174, 176, 224, 175, 130, 34, 121, 69, 116, 57, 0, 24, 9, 0, 6, 20, 230, 11, 0, 0, 48, 0, 0, 0, 231, 11, 0, 0, 49, 0, 0, 0, 232, 11, 0, 0, 50, 0, 0, 0, 233, 11, 0, 0, 51, 0, 0, 0, 234, 11, 0, 0, 52, 0, 0, 0, 235, 11, 0, 0, 53, 0, 0, 0, 236, 11, 0, 0, 54, 0, 0, 0, 237, 11, 0, 0, 55, 0, 0, 0, 238, 11, 0, 0, 56, 0, 0, 0, 239, 11, 0, 0, 57, 0, 0, 0, 198, 11, 190, 11, 202, 11, 0, 0, 199, 11, 190, 11, 203, 11, 0, 0, 198, 11, 215, 11, 204, 11, 0, 0, 0, 0, 0, 0, 6, 18, 66, 224, 174, 183, 224, 175, 141, 0, 224, 174, 184, 224, 175, 141, 0, 224, 174, 159, 224, 175, 141, 0, 7, 6, 18, 67, 224, 174, 159, 224, 175, 141, 0, 224, 174, 177, 224, 175, 141, 0, 224, 174, 183, 224, 175, 141, 0, 224, 174, 184, 224, 175, 141, 0, 7, 6, 18, 68, 224, 174, 135, 0, 224, 174, 142, 0, 224, 174, 133, 0, 7, 6, 18, 69, 224, 174, 154, 0, 224, 174, 184, 0, 7, 6, 18, 70, 224, 174, 176, 0, 224, 174, 177, 0, 7, 6, 18, 71, 224, 174, 149, 0, 224, 174, 185, 0, 7, 6, 18, 72, 224, 175, 134, 224, 174, 179, 0, 224, 175, 140, 0, 7, 6, 18, 73, 224, 174, 191, 0, 224, 175, 128, 0, 7, 6, 18, 74, 224, 174, 168, 0, 224, 174, 169, 0, 7, 6, 18, 75, 224, 174, 178, 0, 224, 174, 179, 0, 7, 6, 18, 76, 224, 174, 170, 0, 224, 174, 164, 0, 224, 174, 149, 0, 7, 6, 18, 77, 224, 174, 170, 224, 174, 191, 224, 174, 179, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 224, 174, 170, 224, 175, 141, 224, 174, 179, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 224, 174, 170, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 224, 174, 164, 224, 174, 163, 224, 175, 141, 224, 174, 163, 224, 175, 128, 224, 174, 176, 224, 175, 141, 0, 224, 174, 181, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 176, 224, 175, 141, 0, 224, 174, 149, 224, 174, 163, 224, 175, 141, 224, 174, 163, 224, 174, 190, 224, 174, 159, 224, 174, 191, 0, 224, 174, 174, 224, 174, 176, 224, 175, 129, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 175, 129, 0, 224, 174, 181, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 174, 191, 0, 224, 174, 149, 224, 174, 191, 224, 174, 179, 224, 174, 190, 224, 174, 184, 224, 175, 141, 0, 224, 174, 149, 224, 175, 141, 224, 174, 179, 224, 174, 190, 224, 174, 184, 224, 175, 141, 0, 224, 174, 154, 224, 174, 190, 224, 174, 176, 224, 174, 190, 224, 174, 175, 0, 224, 174, 164, 224, 174, 163, 224, 175, 141, 224, 174, 163, 224, 174, 191, 0, 224, 174, 170, 224, 175, 128, 224, 174, 176, 224, 175, 141, 0, 224, 174, 149, 224, 174, 178, 224, 174, 176, 224, 175, 141, 0, 224, 174, 154, 224, 175, 139, 224, 174, 159, 224, 174, 190, 0, 224, 174, 174, 224, 174, 164, 224, 175, 129, 0, 7, 6, 18, 78, 224, 174, 181, 224, 174, 190, 224, 174, 180, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 136, 0, 224, 174, 181, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 224, 174, 174, 224, 174, 169, 224, 174, 191, 224, 174, 164, 224, 174, 169, 0, 224, 174, 170, 224, 175, 130, 224, 174, 174, 224, 174, 191, 0, 7, 6, 18, 79, 224, 174, 168, 224, 175, 134, 224, 174, 176, 224, 175, 129, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 224, 174, 170, 224, 175, 141, 0, 224, 174, 168, 224, 175, 134, 224, 174, 176, 224, 175, 129, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 0, 224, 174, 164, 224, 175, 128, 224, 174, 170, 224, 175, 141, 0, 224, 174, 164, 224, 175, 128, 0, 7, 6, 18, 80, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 134, 224, 174, 159, 224, 175, 141, 0, 224, 174, 170, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 0, 224, 174, 174, 224, 175, 128, 224, 174, 178, 224, 175, 141, 224, 174, 184, 0, 224, 174, 149, 224, 174, 191, 224, 174, 179, 224, 174, 190, 224, 174, 184, 0, 224, 174, 159, 224, 174, 190, 224, 174, 184, 0, 7, 6, 18, 81, 224, 174, 174, 224, 175, 135, 224, 174, 177, 224, 175, 141, 0, 224, 174, 149, 224, 175, 129, 224, 174, 177, 224, 175, 136, 0, 224, 174, 174, 224, 175, 135, 224, 174, 178, 0, 7, 6, 18, 82, 224, 174, 149, 224, 175, 129, 224, 174, 180, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 175, 136, 0, 224, 174, 149, 224, 175, 129, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 224, 174, 149, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 175, 136, 0, 224, 174, 149, 224, 175, 129, 224, 174, 176, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 224, 174, 149, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 175, 136, 0, 224, 174, 149, 224, 174, 191, 224, 174, 179, 224, 174, 191, 0, 7, 6, 18, 83, 224, 174, 170, 224, 174, 191, 224, 174, 179, 224, 175, 141, 224, 174, 179, 224, 175, 136, 0, 224, 174, 170, 224, 175, 134, 224, 174, 163, 224, 175, 141, 0, 224, 174, 170, 224, 175, 136, 224, 174, 175, 224, 174, 169, 0, 7, 6, 18, 84, 224, 174, 164, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 191, 0, 224, 174, 164, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 7, 6, 18, 85, 224, 174, 170, 224, 174, 178, 224, 175, 141, 0, 224, 174, 170, 224, 174, 177, 224, 175, 141, 0, 224, 174, 170, 224, 175, 139, 224, 174, 176, 0, 7, 6, 1, 4, 0, 224, 174, 149, 2, 17, 66, 3, 79, 98, 0, 224, 174, 149, 3, 79, 98, 107, 0, 224, 174, 170, 2, 17, 66, 3, 81, 0, 224, 174, 170, 3, 81, 107, 0, 224, 174, 164, 2, 17, 66, 3, 98, 70, 0, 224, 174, 164, 3, 98, 70, 107, 0, 3, 105, 0, 7, 6, 1, 8, 0, 4, 2, 224, 174, 175, 224, 175, 135, 224, 174, 154, 3, 0, 4, 2, 224, 174, 176, 224, 174, 149, 224, 174, 154, 224, 174, 191, 224, 174, 175, 3, 0, 4, 2, 224, 174, 176, 224, 174, 149, 224, 175, 129, 3, 0, 4, 2, 224, 174, 176, 224, 174, 149, 224, 175, 129, 224, 174, 176, 224, 174, 190, 224, 174, 174, 3, 0, 4, 2, 224, 174, 176, 224, 174, 154, 224, 174, 169, 224, 175, 136, 3, 0, 4, 2, 224, 174, 176, 224, 174, 154, 224, 174, 190, 224, 174, 175, 224, 174, 169, 3, 0, 4, 2, 224, 174, 176, 224, 174, 154, 224, 174, 191, 224, 174, 149, 3, 0, 4, 2, 224, 174, 176, 224, 174, 154, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 3, 0, 4, 2, 224, 174, 176, 224, 174, 154, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 3, 0, 4, 2, 224, 174, 176, 224, 174, 164, 32, 3, 0, 4, 2, 224, 174, 176, 224, 174, 164, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 3, 0, 4, 2, 224, 174, 176, 224, 174, 164, 224, 174, 164, 224, 175, 141, 224, 174, 164, 3, 0, 4, 2, 224, 174, 176, 224, 174, 164, 224, 174, 174, 3, 0, 4, 2, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 3, 0, 4, 2, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 191, 224, 174, 175, 3, 0, 4, 2, 224, 174, 176, 224, 174, 175, 224, 174, 191, 224, 174, 178, 3, 0, 4, 2, 224, 174, 176, 224, 174, 181, 224, 175, 128, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 3, 0, 4, 2, 224, 174, 176, 224, 174, 181, 224, 175, 136, 224, 174, 149, 224, 174, 179, 3, 0, 4, 2, 224, 174, 176, 224, 174, 181, 224, 175, 136, 224, 174, 175, 224, 175, 136, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 154, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 156, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 164, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 183, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 174, 191, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 175, 129, 224, 174, 181, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 164, 224, 174, 190, 224, 174, 149, 224, 174, 191, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 164, 224, 174, 190, 224, 174, 181, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 170, 224, 175, 141, 32, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 175, 136, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 138, 224, 174, 180, 224, 175, 129, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 175, 224, 174, 170, 224, 175, 129, 224, 174, 176, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 163, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 3, 0, 4, 2, 224, 174, 176, 224, 174, 190, 224, 174, 183, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 176, 3, 0, 4, 2, 224, 174, 178, 224, 174, 149, 224, 175, 129, 224, 174, 181, 224, 174, 190, 224, 174, 149, 3, 0, 4, 2, 224, 174, 178, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 175, 141, 224, 174, 174, 224, 174, 163, 3, 0, 4, 2, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 149, 224, 175, 141, 3, 0, 4, 2, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 153, 224, 175, 141, 3, 0, 4, 2, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 163, 3, 0, 4, 2, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 164, 224, 175, 141, 3, 0, 4, 2, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 174, 3, 0, 4, 2, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 190, 3, 0, 4, 2, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 175, 3, 0, 4, 2, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 175, 129, 224, 174, 174, 224, 174, 163, 3, 0, 4, 2, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 175, 129, 224, 174, 174, 224, 174, 191, 3, 0, 4, 2, 224, 174, 178, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 169, 3, 0, 4, 2, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 128, 224, 174, 169, 3, 0, 4, 2, 224, 174, 178, 224, 174, 175, 224, 174, 191, 3, 0, 4, 2, 224, 174, 178, 224, 174, 181, 224, 174, 153, 224, 175, 141, 224, 174, 149, 3, 0, 4, 2, 224, 174, 178, 224, 174, 190, 224, 174, 170, 3, 0, 4, 2, 224, 174, 178, 224, 174, 190, 224, 174, 181, 224, 174, 163, 224, 175, 141, 224, 174, 175, 3, 0, 2, 224, 174, 178, 224, 175, 135, 224, 174, 154, 3, 0, 224, 174, 176, 224, 174, 170, 224, 175, 141, 224, 174, 170, 2, 224, 174, 176, 3, 34, 107, 69, 69, 107, 0, 224, 174, 176, 224, 174, 190, 224, 174, 158, 224, 175, 141, 224, 174, 154, 3, 34, 116, 65, 74, 147, 0, 4, 3, 37, 0, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 178, 224, 175, 141, 32, 0, 224, 174, 178, 224, 175, 135, 224, 174, 149, 224, 175, 141, 224, 174, 149, 2, 224, 174, 191, 224, 174, 175, 3, 55, 112, 79, 79, 0, 7, 6, 1, 22, 0, 1, 141, 175, 224, 177, 174, 224, 2, 17, 66, 3, 10, 49, 0, 1, 141, 175, 224, 177, 174, 224, 3, 10, 49, 107, 0, 4, 1, 18, 66, 2, 17, 66, 3, 49, 0, 1, 128, 175, 224, 174, 174, 224, 141, 175, 224, 178, 174, 224, 190, 174, 224, 181, 174, 224, 2, 224, 174, 191, 0, 1, 129, 175, 224, 164, 174, 224, 18, 68, 2, 224, 175, 129, 224, 174, 177, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 1, 129, 175, 224, 180, 174, 224, 133, 174, 224, 2, 224, 175, 129, 224, 174, 176, 224, 174, 178, 0, 1, 133, 174, 224, 2, 224, 175, 141, 224, 174, 159, 224, 175, 139, 224, 174, 170, 224, 174, 176, 0, 1, 134, 174, 224, 2, 224, 174, 190, 224, 174, 183, 0, 1, 134, 174, 224, 2, 224, 175, 141, 224, 174, 176, 224, 175, 139, 224, 174, 183, 0, 1, 135, 175, 224, 178, 174, 224, 176, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 190, 0, 1, 135, 175, 224, 181, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 169, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 1, 136, 175, 224, 176, 174, 224, 133, 174, 224, 2, 224, 175, 129, 224, 174, 177, 224, 175, 136, 0, 1, 136, 175, 224, 177, 174, 224, 133, 174, 224, 2, 224, 175, 130, 224, 174, 181, 0, 1, 141, 175, 224, 153, 174, 224, 133, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 190, 0, 1, 141, 175, 224, 153, 174, 224, 133, 174, 224, 2, 224, 174, 191, 224, 174, 179, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 175, 139, 224, 174, 170, 0, 1, 141, 175, 224, 169, 174, 224, 134, 175, 224, 164, 174, 224, 2, 224, 174, 191, 224, 174, 180, 0, 1, 141, 175, 224, 176, 174, 224, 128, 175, 224, 154, 174, 224, 2, 224, 175, 135, 224, 174, 159, 0, 1, 141, 175, 224, 178, 174, 224, 138, 175, 224, 164, 174, 224, 2, 224, 174, 190, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 0, 1, 141, 175, 224, 178, 174, 224, 191, 174, 224, 175, 174, 224, 139, 175, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 179, 224, 175, 136, 0, 1, 159, 174, 224, 141, 175, 224, 183, 174, 224, 133, 174, 224, 2, 224, 175, 139, 224, 174, 163, 224, 174, 178, 0, 1, 170, 174, 224, 133, 174, 224, 2, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 1, 174, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 175, 0, 1, 174, 174, 224, 190, 174, 224, 176, 174, 224, 135, 174, 224, 2, 224, 174, 190, 224, 174, 164, 224, 175, 136, 0, 1, 174, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 133, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 1, 175, 174, 224, 191, 174, 224, 176, 174, 224, 133, 174, 224, 2, 224, 175, 129, 224, 174, 159, 224, 174, 191, 0, 1, 178, 174, 224, 128, 175, 224, 168, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 174, 191, 0, 1, 178, 174, 224, 130, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 163, 0, 1, 178, 174, 224, 159, 174, 224, 141, 175, 224, 163, 174, 224, 129, 175, 224, 149, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 174, 191, 0, 1, 190, 174, 224, 178, 174, 224, 135, 174, 224, 2, 224, 174, 190, 0, 1, 191, 174, 224, 164, 174, 224, 134, 174, 224, 2, 224, 175, 129, 224, 174, 159, 224, 174, 191, 0, 1, 191, 174, 224, 169, 174, 224, 130, 175, 224, 175, 174, 224, 2, 224, 175, 139, 224, 174, 159, 0, 1, 191, 174, 224, 174, 174, 224, 190, 174, 224, 169, 174, 224, 133, 174, 224, 2, 224, 174, 190, 0, 1, 191, 174, 224, 178, 174, 224, 129, 175, 224, 170, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 174, 191, 0, 1, 191, 174, 224, 181, 174, 224, 2, 224, 175, 141, 224, 174, 176, 224, 174, 174, 0, 1, 191, 174, 224, 183, 174, 224, 134, 174, 224, 2, 224, 174, 190, 0, 2, 224, 174, 190, 224, 174, 176, 224, 174, 169, 0, 2, 224, 174, 191, 224, 174, 176, 224, 175, 129, 0, 2, 224, 175, 129, 224, 174, 174, 224, 174, 176, 224, 174, 169, 0, 2, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 176, 0, 2, 224, 175, 129, 224, 174, 178, 0, 2, 224, 175, 130, 224, 174, 159, 0, 2, 224, 175, 138, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 2, 224, 175, 138, 224, 174, 179, 224, 175, 141, 0, 8, 2, 17, 66, 0, 8, 2, 224, 175, 128, 224, 174, 164, 224, 174, 178, 0, 8, 2, 224, 175, 128, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 149, 224, 175, 129, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 32, 0, 8, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 169, 224, 175, 129, 224, 174, 174, 0, 8, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 0, 8, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 176, 224, 175, 129, 0, 8, 2, 224, 175, 139, 224, 174, 170, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 176, 32, 224, 174, 174, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 139, 224, 174, 176, 32, 224, 174, 174, 224, 175, 129, 224, 174, 159, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 139, 224, 174, 176, 32, 224, 174, 181, 224, 175, 135, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 129, 175, 224, 163, 174, 224, 135, 175, 224, 176, 174, 224, 2, 224, 174, 190, 0, 8, 129, 175, 224, 174, 174, 224, 2, 224, 175, 135, 224, 174, 183, 0, 8, 129, 175, 224, 178, 174, 224, 190, 174, 224, 164, 174, 224, 2, 224, 174, 190, 0, 8, 130, 175, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 176, 0, 8, 130, 175, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 191, 0, 8, 130, 175, 224, 178, 174, 224, 190, 174, 224, 164, 174, 224, 2, 224, 174, 190, 0, 8, 135, 175, 224, 176, 174, 224, 129, 175, 224, 175, 174, 224, 2, 224, 174, 190, 0, 8, 136, 175, 224, 159, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 176, 0, 8, 136, 175, 224, 159, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 191, 0, 8, 136, 175, 224, 178, 174, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 170, 224, 175, 141, 0, 8, 136, 175, 224, 179, 174, 224, 181, 174, 224, 2, 224, 175, 129, 224, 174, 159, 0, 8, 136, 175, 224, 181, 174, 224, 2, 224, 175, 139, 0, 8, 138, 175, 224, 178, 174, 224, 2, 224, 175, 135, 224, 174, 183, 224, 174, 169, 0, 8, 141, 175, 224, 153, 174, 224, 178, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 153, 174, 224, 178, 174, 224, 128, 175, 224, 176, 174, 224, 141, 175, 224, 184, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 153, 174, 224, 190, 174, 224, 185, 174, 224, 2, 224, 174, 190, 224, 174, 153, 224, 175, 141, 0, 8, 141, 175, 224, 156, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 174, 163, 0, 8, 141, 175, 224, 163, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 163, 224, 174, 190, 0, 8, 141, 175, 224, 169, 174, 224, 134, 175, 224, 164, 174, 224, 2, 224, 174, 190, 224, 174, 154, 224, 174, 191, 0, 8, 141, 175, 224, 176, 174, 224, 134, 175, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 176, 224, 174, 191, 0, 8, 141, 175, 224, 176, 174, 224, 135, 175, 224, 168, 174, 224, 2, 224, 174, 190, 224, 174, 163, 224, 174, 178, 0, 8, 141, 175, 224, 176, 174, 224, 149, 174, 224, 190, 174, 224, 168, 174, 224, 2, 224, 175, 139, 224, 174, 175, 224, 174, 191, 224, 174, 178, 0, 8, 141, 175, 224, 176, 174, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 179, 0, 8, 141, 175, 224, 178, 174, 224, 149, 174, 224, 2, 224, 174, 191, 0, 8, 141, 175, 224, 178, 174, 224, 175, 174, 224, 136, 175, 224, 164, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 176, 0, 8, 141, 175, 224, 178, 174, 224, 175, 174, 224, 136, 175, 224, 174, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 191, 0, 8, 141, 175, 224, 178, 174, 224, 190, 174, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 176, 0, 8, 141, 175, 224, 178, 174, 224, 190, 174, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 191, 0, 8, 141, 175, 224, 178, 174, 224, 190, 174, 224, 170, 174, 224, 2, 224, 175, 129, 224, 174, 159, 0, 8, 147, 174, 224, 2, 224, 175, 135, 0, 8, 159, 174, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 180, 0, 8, 164, 174, 224, 141, 175, 224, 149, 174, 224, 170, 174, 224, 2, 224, 175, 139, 224, 174, 159, 224, 174, 191, 0, 8, 164, 174, 224, 141, 175, 224, 164, 174, 224, 130, 175, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 159, 224, 174, 191, 0, 8, 174, 174, 224, 141, 175, 224, 169, 174, 224, 138, 175, 224, 164, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 8, 174, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 8, 174, 174, 224, 176, 174, 224, 170, 174, 224, 2, 224, 175, 129, 224, 174, 159, 224, 174, 191, 0, 8, 174, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 190, 224, 174, 164, 224, 175, 136, 0, 8, 181, 174, 224, 128, 175, 224, 156, 174, 224, 2, 224, 175, 139, 224, 174, 159, 224, 174, 191, 0, 8, 181, 174, 224, 135, 175, 224, 164, 174, 224, 2, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 181, 174, 224, 141, 175, 224, 176, 174, 224, 130, 175, 224, 170, 174, 224, 2, 224, 175, 129, 224, 174, 159, 224, 174, 191, 0, 8, 190, 174, 224, 170, 174, 224, 2, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 169, 0, 8, 190, 174, 224, 175, 174, 224, 191, 174, 224, 163, 174, 224, 141, 175, 224, 163, 174, 224, 149, 174, 224, 2, 224, 175, 129, 224, 174, 174, 224, 174, 176, 224, 174, 191, 0, 8, 190, 174, 224, 176, 174, 224, 2, 224, 175, 135, 224, 174, 183, 0, 8, 191, 174, 224, 18, 69, 141, 175, 224, 169, 174, 224, 185, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 159, 174, 224, 134, 175, 224, 154, 174, 224, 2, 224, 175, 138, 224, 174, 159, 224, 174, 191, 0, 8, 191, 174, 224, 159, 174, 224, 141, 175, 224, 163, 174, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 176, 0, 8, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 129, 175, 224, 176, 174, 224, 191, 174, 224, 149, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 141, 175, 224, 176, 174, 224, 128, 175, 224, 149, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 141, 175, 224, 176, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 164, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 168, 174, 224, 2, 224, 175, 139, 0, 8, 191, 174, 224, 169, 174, 224, 139, 175, 224, 174, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 169, 174, 224, 140, 175, 224, 174, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 176, 174, 224, 141, 175, 224, 164, 174, 224, 129, 175, 224, 174, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 176, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 154, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 181, 174, 224, 135, 175, 224, 164, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 181, 174, 224, 135, 175, 224, 164, 174, 224, 2, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 191, 174, 224, 181, 174, 224, 179, 174, 224, 190, 174, 224, 174, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 183, 174, 224, 2, 224, 175, 139, 0, 8, 191, 174, 224, 183, 174, 224, 135, 175, 224, 149, 174, 224, 2, 224, 174, 190, 0, 224, 174, 191, 1, 141, 175, 224, 184, 174, 224, 141, 175, 224, 149, 174, 224, 142, 174, 224, 2, 224, 174, 175, 224, 175, 130, 224, 174, 184, 0, 224, 174, 191, 1, 141, 175, 224, 184, 174, 224, 144, 174, 224, 2, 224, 174, 176, 224, 175, 128, 224, 174, 174, 0, 224, 174, 191, 2, 224, 174, 178, 224, 175, 135, 224, 174, 154, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 175, 130, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 164, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 175, 141, 224, 174, 170, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 174, 224, 174, 191, 224, 174, 169, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 128, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 128, 224, 174, 174, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 135, 224, 174, 175, 0, 224, 174, 191, 8, 2, 224, 174, 177, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 170, 224, 175, 141, 32, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 190, 18, 69, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 190, 18, 69, 224, 175, 129, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 190, 18, 69, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 191, 224, 174, 169, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 191, 224, 174, 175, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 175, 128, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 175, 135, 224, 174, 154, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 175, 136, 224, 174, 174, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 175, 140, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 164, 0, 224, 175, 141, 1, 140, 175, 224, 154, 174, 224, 133, 174, 224, 2, 224, 174, 175, 0, 224, 175, 141, 2, 32, 224, 174, 149, 0, 224, 175, 141, 2, 224, 174, 149, 0, 224, 175, 141, 2, 224, 174, 184, 0, 224, 175, 141, 8, 128, 175, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 174, 0, 224, 175, 141, 8, 128, 175, 224, 170, 174, 224, 141, 175, 224, 184, 174, 224, 136, 174, 224, 2, 32, 0, 224, 175, 141, 8, 129, 175, 224, 176, 174, 224, 2, 224, 174, 174, 224, 174, 163, 224, 174, 191, 0, 224, 175, 141, 8, 135, 175, 224, 181, 174, 224, 191, 174, 224, 181, 174, 224, 2, 32, 0, 224, 175, 141, 8, 136, 175, 224, 170, 174, 224, 2, 224, 174, 178, 32, 0, 224, 175, 141, 8, 136, 175, 224, 174, 174, 224, 0, 224, 175, 141, 8, 139, 175, 224, 156, 174, 224, 2, 32, 0, 224, 175, 141, 8, 140, 175, 224, 154, 174, 224, 2, 224, 174, 175, 0, 224, 175, 141, 8, 159, 174, 224, 0, 224, 175, 141, 8, 178, 174, 224, 2, 224, 174, 169, 224, 175, 139, 0, 224, 175, 141, 8, 190, 174, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 159, 224, 175, 128, 224, 174, 184, 0, 224, 175, 141, 8, 190, 174, 224, 183, 174, 224, 2, 32, 0, 4, 224, 174, 191, 224, 174, 176, 224, 175, 129, 2, 224, 174, 183, 224, 175, 141, 3, 49, 34, 37, 0, 224, 174, 191, 224, 174, 176, 224, 175, 129, 8, 2, 224, 174, 184, 224, 175, 141, 224, 174, 164, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 175, 139, 224, 174, 170, 8, 2, 224, 174, 176, 3, 49, 34, 37, 87, 138, 117, 81, 107, 0, 224, 175, 141, 224, 174, 176, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 175, 139, 224, 174, 170, 8, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 176, 224, 174, 170, 8, 154, 174, 224, 2, 224, 174, 190, 224, 174, 163, 224, 174, 191, 3, 49, 34, 107, 48, 0, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 170, 224, 175, 141, 8, 3, 49, 34, 116, 48, 0, 224, 175, 141, 224, 174, 176, 224, 175, 130, 224, 174, 159, 224, 175, 141, 8, 134, 175, 224, 176, 174, 224, 3, 49, 34, 150, 138, 0, 224, 175, 134, 224, 174, 159, 224, 175, 141, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 174, 174, 224, 3, 49, 36, 138, 0, 4, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 163, 224, 174, 191, 3, 49, 37, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 163, 224, 175, 141, 32, 0, 224, 175, 141, 224, 174, 170, 8, 139, 175, 224, 178, 174, 224, 2, 224, 174, 190, 224, 174, 178, 3, 49, 48, 0, 224, 175, 141, 224, 174, 149, 224, 175, 134, 224, 174, 159, 224, 175, 141, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 174, 174, 224, 3, 49, 49, 36, 138, 0, 224, 175, 141, 224, 174, 149, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 174, 174, 224, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 135, 224, 174, 175, 3, 49, 49, 107, 0, 224, 174, 191, 224, 174, 179, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 2, 224, 174, 169, 3, 49, 55, 37, 50, 138, 107, 0, 224, 174, 191, 224, 174, 179, 224, 174, 191, 224, 174, 175, 224, 175, 139, 224, 174, 170, 224, 174, 190, 224, 174, 159, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 3, 49, 55, 37, 57, 117, 48, 116, 47, 0, 224, 174, 191, 224, 174, 179, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 8, 3, 49, 55, 107, 34, 49, 0, 224, 174, 191, 224, 174, 179, 224, 174, 170, 224, 175, 141, 224, 174, 170, 8, 2, 224, 175, 129, 224, 174, 149, 224, 174, 179, 3, 49, 55, 107, 69, 69, 0, 224, 175, 141, 224, 174, 178, 224, 175, 139, 224, 174, 170, 1, 136, 175, 224, 154, 174, 224, 141, 175, 224, 169, 174, 224, 142, 174, 224, 2, 224, 175, 128, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 3, 49, 55, 117, 48, 0, 224, 174, 191, 224, 174, 179, 224, 175, 136, 224, 174, 175, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 3, 49, 55, 132, 57, 107, 64, 138, 147, 0, 224, 175, 141, 224, 174, 175, 224, 175, 130, 224, 174, 176, 224, 174, 191, 224, 174, 159, 8, 134, 175, 224, 154, 174, 224, 2, 224, 174, 191, 3, 49, 57, 150, 34, 37, 138, 0, 4, 224, 175, 129, 224, 174, 181, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 191, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 135, 224, 174, 183, 224, 174, 169, 3, 49, 58, 0, 224, 175, 141, 224, 174, 181, 8, 2, 17, 65, 0, 224, 175, 129, 224, 174, 181, 224, 174, 190, 224, 174, 178, 224, 174, 191, 224, 174, 159, 8, 2, 224, 174, 191, 3, 49, 58, 116, 55, 37, 138, 0, 4, 224, 174, 191, 224, 174, 179, 224, 174, 191, 224, 174, 170, 224, 175, 141, 8, 2, 32, 3, 49, 62, 37, 48, 0, 224, 174, 191, 224, 174, 179, 224, 174, 191, 224, 174, 170, 224, 175, 141, 8, 2, 224, 174, 178, 0, 224, 174, 191, 224, 174, 179, 224, 174, 191, 224, 174, 159, 8, 3, 49, 62, 37, 138, 147, 0, 4, 224, 174, 191, 224, 174, 179, 224, 174, 170, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 191, 224, 174, 178, 3, 49, 62, 107, 69, 69, 0, 224, 174, 191, 224, 174, 179, 224, 174, 170, 224, 175, 141, 224, 174, 170, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 0, 224, 174, 191, 224, 174, 179, 224, 174, 170, 224, 175, 141, 224, 174, 170, 8, 2, 224, 175, 136, 0, 224, 175, 141, 224, 174, 154, 1, 134, 174, 224, 2, 224, 175, 129, 224, 174, 181, 224, 174, 178, 3, 49, 74, 0, 4, 224, 175, 141, 224, 174, 154, 8, 134, 175, 224, 178, 174, 224, 2, 224, 174, 176, 3, 49, 74, 107, 0, 224, 175, 141, 224, 174, 154, 8, 191, 174, 224, 170, 174, 224, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 154, 8, 191, 174, 224, 174, 174, 224, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 149, 8, 136, 175, 224, 149, 174, 224, 2, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 174, 190, 224, 174, 176, 3, 49, 79, 107, 0, 4, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 149, 8, 134, 175, 224, 174, 174, 224, 2, 224, 175, 139, 3, 49, 87, 37, 49, 0, 224, 175, 141, 224, 174, 184, 224, 174, 191, 224, 174, 149, 8, 134, 175, 224, 174, 174, 224, 2, 224, 175, 139, 0, 224, 175, 141, 224, 174, 183, 2, 17, 66, 3, 49, 91, 0, 4, 224, 175, 141, 224, 174, 154, 8, 191, 174, 224, 181, 174, 224, 2, 224, 174, 169, 224, 174, 176, 224, 174, 191, 3, 49, 91, 107, 0, 224, 175, 141, 224, 174, 183, 0, 4, 1, 18, 66, 3, 49, 107, 0, 1, 129, 175, 224, 164, 174, 224, 174, 174, 224, 2, 224, 174, 176, 0, 1, 129, 175, 224, 176, 174, 224, 146, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 1, 129, 175, 224, 177, 174, 224, 174, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 1, 136, 175, 224, 178, 174, 224, 133, 174, 224, 2, 224, 174, 159, 224, 174, 178, 0, 1, 140, 175, 224, 154, 174, 224, 133, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 174, 164, 224, 175, 136, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 174, 181, 224, 174, 178, 224, 175, 136, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 1, 141, 175, 224, 178, 174, 224, 138, 175, 224, 149, 174, 224, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 190, 0, 1, 141, 175, 224, 178, 174, 224, 175, 174, 224, 136, 175, 224, 174, 174, 224, 154, 174, 224, 2, 224, 174, 159, 224, 175, 141, 0, 1, 141, 175, 224, 179, 174, 224, 137, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 1, 154, 174, 224, 141, 175, 224, 154, 174, 224, 137, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 1, 154, 174, 224, 141, 175, 224, 158, 174, 224, 170, 174, 224, 2, 224, 174, 178, 224, 175, 141, 224, 174, 175, 224, 174, 190, 224, 174, 163, 0, 1, 154, 174, 224, 141, 175, 224, 158, 174, 224, 170, 174, 224, 2, 224, 174, 181, 224, 175, 141, 224, 174, 175, 0, 1, 159, 174, 224, 149, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 181, 224, 174, 191, 0, 1, 169, 174, 224, 191, 174, 224, 164, 174, 224, 2, 224, 174, 176, 0, 1, 170, 174, 224, 141, 175, 224, 174, 174, 224, 176, 174, 224, 134, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 1, 178, 174, 224, 149, 174, 224, 154, 174, 224, 2, 224, 174, 178, 224, 174, 190, 0, 1, 181, 174, 224, 141, 175, 224, 184, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 176, 224, 175, 141, 224, 174, 174, 224, 174, 190, 0, 1, 190, 174, 224, 149, 174, 224, 174, 174, 224, 2, 224, 174, 181, 224, 174, 191, 0, 1, 190, 174, 224, 164, 174, 224, 129, 175, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 159, 0, 1, 190, 174, 224, 164, 174, 224, 129, 175, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 169, 0, 1, 190, 174, 224, 164, 174, 224, 129, 175, 224, 154, 174, 224, 2, 224, 174, 176, 224, 175, 141, 32, 0, 1, 190, 174, 224, 170, 174, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 176, 0, 1, 190, 174, 224, 181, 174, 224, 191, 174, 224, 164, 174, 224, 2, 224, 174, 176, 0, 1, 190, 174, 224, 185, 174, 224, 174, 174, 224, 2, 224, 174, 181, 224, 174, 191, 0, 2, 224, 174, 181, 224, 174, 191, 224, 174, 158, 0, 2, 224, 174, 181, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 175, 0, 8, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 176, 224, 175, 129, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 139, 175, 224, 178, 174, 224, 2, 224, 174, 178, 0, 8, 140, 175, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 8, 141, 175, 224, 153, 174, 224, 191, 174, 224, 178, 174, 224, 2, 224, 174, 169, 0, 8, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 174, 169, 224, 174, 181, 0, 8, 141, 175, 224, 163, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 177, 224, 175, 141, 0, 8, 141, 175, 224, 163, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 179, 0, 8, 141, 175, 224, 169, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 169, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 178, 174, 224, 129, 175, 224, 149, 174, 224, 2, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 191, 0, 8, 141, 175, 224, 178, 174, 224, 134, 175, 224, 181, 174, 224, 2, 224, 174, 174, 0, 8, 141, 175, 224, 178, 174, 224, 149, 174, 224, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 178, 174, 224, 149, 174, 224, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 190, 0, 8, 163, 174, 224, 176, 174, 224, 2, 224, 174, 179, 0, 8, 175, 174, 224, 141, 175, 224, 164, 174, 224, 154, 174, 224, 2, 224, 174, 178, 224, 174, 190, 0, 8, 175, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 154, 174, 224, 2, 224, 174, 178, 224, 174, 190, 0, 8, 175, 174, 224, 191, 174, 224, 176, 174, 224, 130, 175, 224, 154, 174, 224, 2, 224, 174, 178, 224, 174, 190, 0, 8, 176, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 178, 224, 174, 190, 0, 8, 176, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 154, 174, 224, 2, 224, 174, 178, 224, 174, 190, 0, 8, 178, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 181, 174, 224, 128, 175, 224, 156, 174, 224, 2, 224, 174, 178, 224, 175, 136, 0, 8, 191, 174, 224, 154, 174, 224, 154, 174, 224, 2, 224, 174, 178, 224, 174, 190, 0, 8, 191, 174, 224, 159, 174, 224, 134, 175, 224, 174, 174, 224, 2, 224, 174, 178, 0, 8, 191, 174, 224, 159, 174, 224, 141, 175, 224, 149, 174, 224, 190, 174, 224, 176, 174, 224, 141, 175, 224, 170, 174, 224, 2, 224, 174, 178, 0, 224, 174, 159, 8, 141, 175, 224, 153, 174, 224, 134, 175, 224, 181, 174, 224, 3, 49, 107, 138, 147, 0, 224, 175, 135, 224, 174, 159, 8, 138, 175, 224, 178, 174, 224, 3, 49, 112, 138, 147, 0, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 159, 8, 156, 174, 224, 3, 49, 116, 34, 138, 147, 0, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 8, 128, 175, 224, 176, 174, 224, 141, 175, 224, 184, 174, 224, 3, 49, 116, 50, 47, 147, 0, 224, 175, 139, 224, 174, 170, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 3, 49, 117, 69, 0, 224, 175, 129, 224, 174, 174, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 190, 174, 224, 159, 174, 224, 3, 49, 120, 63, 36, 64, 47, 147, 0, 224, 175, 140, 224, 174, 154, 224, 174, 191, 224, 174, 149, 8, 3, 49, 133, 87, 37, 49, 147, 0, 224, 175, 141, 224, 174, 159, 224, 175, 141, 3, 49, 138, 0, 224, 175, 141, 224, 174, 159, 224, 175, 141, 224, 174, 176, 224, 174, 191, 224, 174, 149, 8, 134, 175, 224, 178, 174, 224, 142, 174, 224, 2, 224, 174, 178, 3, 49, 138, 34, 37, 49, 107, 0, 224, 175, 141, 224, 174, 159, 3, 49, 138, 147, 0, 4, 1, 141, 175, 224, 149, 174, 224, 3, 49, 147, 0, 8, 141, 175, 224, 175, 174, 224, 190, 174, 224, 174, 174, 224, 156, 174, 224, 0, 8, 190, 174, 224, 159, 174, 224, 141, 175, 224, 184, 174, 224, 0, 8, 191, 174, 224, 170, 174, 224, 139, 175, 224, 149, 174, 224, 0, 4, 224, 175, 129, 1, 141, 175, 224, 163, 174, 224, 174, 174, 224, 133, 174, 224, 2, 224, 174, 159, 224, 174, 191, 3, 49, 149, 0, 224, 175, 129, 1, 141, 175, 224, 169, 174, 224, 174, 174, 224, 141, 175, 224, 174, 174, 224, 133, 174, 224, 2, 224, 174, 159, 224, 174, 191, 0, 224, 175, 129, 1, 141, 175, 224, 176, 174, 224, 190, 174, 224, 169, 174, 224, 141, 175, 224, 169, 174, 224, 174, 174, 224, 2, 224, 174, 159, 224, 174, 191, 0, 224, 175, 129, 1, 141, 175, 224, 176, 174, 224, 190, 174, 224, 175, 174, 224, 136, 175, 224, 159, 174, 224, 137, 174, 224, 2, 224, 174, 159, 224, 174, 191, 0, 224, 175, 129, 1, 175, 174, 224, 191, 174, 224, 176, 174, 224, 133, 174, 224, 2, 224, 174, 159, 224, 174, 191, 0, 224, 175, 129, 8, 174, 174, 224, 176, 174, 224, 170, 174, 224, 2, 224, 174, 159, 224, 174, 191, 0, 4, 1, 141, 175, 224, 149, 174, 224, 136, 175, 224, 178, 174, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 149, 224, 175, 136, 3, 79, 0, 1, 141, 175, 224, 149, 174, 224, 191, 174, 224, 177, 174, 224, 143, 174, 224, 2, 224, 175, 129, 224, 174, 164, 224, 174, 191, 0, 1, 141, 175, 224, 153, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 175, 129, 0, 1, 141, 175, 224, 153, 174, 224, 133, 174, 224, 2, 224, 175, 138, 0, 1, 141, 175, 224, 153, 174, 224, 135, 174, 224, 2, 224, 175, 138, 0, 1, 141, 175, 224, 177, 174, 224, 168, 174, 224, 2, 224, 175, 129, 224, 174, 163, 0, 1, 190, 174, 224, 176, 174, 224, 135, 174, 224, 2, 224, 175, 129, 224, 174, 178, 0, 2, 17, 66, 0, 2, 224, 175, 128, 224, 174, 164, 0, 8, 2, 17, 66, 28, 17, 12, 0, 8, 2, 224, 174, 190, 224, 174, 154, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 170, 224, 174, 190, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 174, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 149, 0, 8, 2, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 128, 224, 174, 170, 0, 8, 2, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 174, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 181, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 175, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 159, 224, 174, 169, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 131, 224, 174, 170, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 174, 191, 224, 174, 159, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 163, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 184, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 174, 191, 224, 174, 175, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 156, 224, 174, 190, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 164, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 149, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 181, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 175, 128, 224, 174, 183, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 149, 224, 174, 184, 224, 175, 141, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 149, 224, 174, 191, 224, 174, 176, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 185, 224, 174, 184, 224, 175, 141, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 175, 141, 224, 174, 176, 224, 175, 134, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 174, 168, 224, 174, 190, 224, 174, 164, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 174, 176, 224, 174, 190, 224, 174, 156, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 136, 0, 8, 2, 224, 175, 129, 224, 174, 156, 224, 174, 176, 224, 174, 190, 224, 174, 164, 0, 8, 2, 224, 175, 129, 224, 174, 156, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 175, 129, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 129, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 175, 129, 224, 174, 159, 224, 175, 129, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 154, 224, 175, 128, 224, 174, 178, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 154, 224, 175, 135, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 154, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 168, 224, 174, 178, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 170, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 174, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 181, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 181, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 149, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 175, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 129, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 130, 224, 174, 154, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 136, 0, 8, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 139, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 154, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 170, 224, 175, 128, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 170, 224, 175, 129, 224, 174, 149, 224, 175, 129, 224, 174, 170, 224, 175, 129, 0, 8, 2, 224, 175, 129, 224, 174, 170, 224, 175, 129, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 164, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 174, 224, 175, 129, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 129, 0, 8, 2, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 178, 0, 8, 2, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 190, 224, 174, 179, 0, 8, 2, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 191, 224, 174, 159, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 130, 224, 174, 163, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 175, 134, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 149, 224, 175, 129, 224, 174, 178, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 178, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 154, 224, 174, 190, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 156, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 164, 224, 175, 135, 224, 174, 181, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 168, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 170, 224, 175, 130, 224, 174, 156, 224, 175, 136, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 134, 224, 174, 175, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 176, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 174, 190, 224, 174, 175, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 174, 191, 224, 174, 159, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 174, 191, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 175, 129, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 175, 129, 224, 174, 159, 224, 175, 136, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 175, 136, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 175, 139, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 175, 139, 224, 174, 159, 0, 8, 2, 224, 175, 129, 224, 174, 178, 224, 174, 190, 224, 174, 170, 0, 8, 2, 224, 175, 129, 224, 174, 178, 224, 174, 190, 224, 174, 174, 0, 8, 2, 224, 175, 129, 224, 174, 178, 224, 175, 135, 224, 174, 170, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 174, 224, 175, 139, 18, 71, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 181, 224, 174, 185, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 184, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 175, 130, 224, 174, 149, 224, 174, 191, 224, 174, 179, 0, 8, 2, 224, 175, 130, 224, 174, 149, 224, 175, 129, 224, 174, 179, 0, 8, 2, 224, 175, 130, 224, 174, 159, 224, 174, 178, 224, 175, 130, 224, 174, 176, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 0, 8, 2, 224, 175, 134, 224, 174, 156, 0, 8, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 134, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 134, 224, 174, 184, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 136, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 224, 175, 129, 224, 174, 149, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 136, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 136, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 136, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 175, 135, 224, 174, 184, 224, 175, 141, 32, 224, 174, 154, 224, 174, 191, 224, 174, 178, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 8, 2, 224, 175, 135, 224, 174, 184, 224, 175, 141, 32, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 181, 224, 175, 141, 0, 8, 2, 224, 175, 136, 224, 174, 159, 0, 8, 2, 224, 175, 136, 224, 174, 169, 224, 174, 149, 0, 8, 2, 224, 175, 138, 224, 174, 163, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 138, 224, 174, 163, 224, 174, 174, 0, 8, 2, 224, 175, 138, 224, 174, 176, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 175, 129, 224, 174, 178, 0, 8, 2, 224, 175, 139, 224, 174, 154, 224, 174, 190, 224, 174, 178, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 190, 224, 174, 181, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 174, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 175, 141, 224, 174, 176, 224, 174, 190, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 175, 141, 224, 174, 176, 224, 175, 135, 224, 174, 156, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 139, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 170, 224, 174, 191, 224, 174, 154, 224, 175, 134, 224, 174, 159, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 170, 224, 174, 191, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 170, 224, 174, 191, 224, 174, 168, 224, 174, 190, 0, 8, 2, 224, 175, 139, 224, 174, 170, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 139, 224, 174, 170, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 175, 139, 224, 174, 174, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 174, 224, 174, 190, 224, 174, 164, 224, 174, 190, 0, 8, 2, 224, 175, 139, 224, 174, 174, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 139, 224, 174, 174, 224, 175, 129, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 174, 224, 175, 130, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 8, 2, 224, 175, 139, 224, 174, 175, 224, 174, 178, 0, 8, 2, 224, 175, 139, 224, 174, 176, 32, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 164, 224, 175, 141, 32, 224, 174, 164, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 170, 224, 175, 141, 32, 18, 85, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 177, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 178, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 139, 224, 174, 176, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 174, 0, 8, 2, 224, 175, 139, 224, 174, 178, 224, 174, 191, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 178, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 139, 224, 174, 178, 224, 175, 141, 224, 174, 149, 224, 175, 138, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 175, 139, 224, 174, 178, 224, 175, 141, 224, 174, 174, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 175, 139, 224, 174, 181, 224, 174, 190, 0, 8, 2, 224, 175, 139, 224, 174, 181, 224, 174, 191, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 139, 224, 174, 183, 0, 8, 2, 224, 175, 140, 224, 174, 169, 224, 175, 136, 0, 8, 2, 224, 175, 140, 224, 174, 169, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 175, 140, 224, 174, 176, 224, 174, 181, 0, 8, 2, 224, 175, 140, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 175, 140, 224, 174, 179, 224, 175, 136, 0, 8, 129, 175, 224, 176, 174, 224, 134, 175, 224, 174, 174, 224, 2, 224, 175, 130, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 149, 174, 224, 164, 174, 224, 174, 174, 224, 141, 175, 224, 169, 174, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 149, 224, 175, 136, 0, 8, 141, 175, 224, 153, 174, 224, 133, 174, 224, 2, 224, 175, 129, 224, 174, 178, 0, 8, 141, 175, 224, 177, 174, 224, 154, 174, 224, 2, 224, 175, 129, 224, 174, 163, 0, 8, 168, 174, 224, 2, 224, 175, 129, 224, 174, 178, 0, 8, 190, 174, 224, 176, 174, 224, 2, 224, 175, 129, 224, 174, 178, 0, 224, 174, 191, 1, 141, 175, 224, 153, 174, 224, 135, 174, 224, 2, 224, 174, 178, 224, 175, 128, 224, 174, 183, 224, 175, 141, 0, 224, 174, 191, 1, 141, 175, 224, 177, 174, 224, 138, 175, 224, 170, 174, 224, 2, 224, 174, 176, 224, 174, 163, 0, 224, 174, 191, 2, 224, 174, 176, 224, 174, 163, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 149, 224, 174, 163, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 181, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 185, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 139, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 178, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 128, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 128, 224, 174, 169, 224, 175, 141, 224, 174, 178, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 128, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 135, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 136, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 140, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 190, 224, 174, 184, 224, 175, 141, 32, 0, 224, 175, 129, 8, 2, 224, 174, 178, 224, 175, 139, 224, 174, 170, 224, 174, 178, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 190, 224, 174, 178, 224, 174, 191, 224, 174, 175, 224, 174, 176, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 181, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 139, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 128, 224, 174, 169, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 130, 224, 174, 170, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 140, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 8, 2, 224, 174, 179, 224, 174, 190, 224, 174, 184, 224, 175, 141, 32, 0, 224, 175, 141, 8, 2, 224, 174, 181, 224, 174, 190, 224, 174, 178, 224, 174, 191, 224, 174, 175, 224, 174, 176, 0, 224, 175, 141, 8, 142, 174, 224, 2, 224, 174, 184, 224, 174, 190, 224, 174, 174, 0, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 175, 136, 224, 174, 159, 8, 3, 79, 34, 116, 50, 132, 138, 147, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 131, 224, 174, 170, 224, 175, 136, 224, 174, 159, 8, 3, 79, 34, 116, 81, 132, 138, 147, 0, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 170, 224, 175, 136, 224, 174, 159, 8, 0, 224, 174, 191, 224, 174, 170, 224, 175, 141, 8, 2, 224, 174, 159, 3, 79, 37, 81, 0, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 164, 3, 79, 40, 34, 40, 48, 0, 224, 175, 129, 224, 174, 170, 224, 175, 141, 8, 2, 224, 174, 164, 3, 79, 40, 48, 0, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 3, 79, 40, 55, 49, 107, 0, 224, 175, 129, 224, 174, 163, 224, 174, 154, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 3, 79, 40, 64, 107, 74, 0, 4, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 178, 3, 79, 40, 64, 138, 147, 0, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 2, 224, 175, 130, 224, 174, 176, 0, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 159, 224, 174, 191, 3, 79, 40, 64, 139, 116, 50, 47, 107, 0, 4, 224, 175, 141, 224, 174, 149, 1, 18, 68, 2, 224, 175, 129, 224, 174, 149, 224, 175, 136, 3, 79, 79, 0, 224, 175, 141, 224, 174, 149, 1, 18, 68, 2, 224, 175, 129, 224, 174, 163, 0, 224, 175, 141, 224, 174, 149, 1, 18, 68, 2, 224, 175, 139, 224, 174, 170, 224, 175, 129, 224, 174, 176, 0, 224, 175, 141, 224, 174, 149, 1, 129, 175, 224, 163, 174, 224, 133, 174, 224, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 224, 174, 149, 1, 133, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 191, 0, 224, 175, 141, 224, 174, 149, 1, 134, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 136, 0, 224, 175, 141, 224, 174, 149, 1, 139, 175, 224, 175, 174, 224, 133, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 149, 1, 139, 175, 224, 176, 174, 224, 134, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 149, 1, 141, 175, 224, 176, 174, 224, 128, 175, 224, 164, 174, 224, 2, 224, 174, 190, 224, 174, 178, 224, 175, 139, 224, 174, 154, 224, 174, 168, 224, 175, 136, 0, 224, 175, 141, 224, 174, 149, 1, 169, 174, 224, 156, 174, 224, 2, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 178, 0, 224, 175, 141, 224, 174, 149, 1, 190, 174, 224, 156, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 136, 0, 224, 175, 141, 224, 174, 149, 1, 190, 174, 224, 170, 174, 224, 139, 175, 224, 149, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 191, 0, 224, 175, 141, 224, 174, 149, 1, 190, 174, 224, 176, 174, 224, 136, 175, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 149, 1, 190, 174, 224, 181, 174, 224, 141, 175, 224, 175, 174, 224, 134, 175, 224, 164, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 136, 0, 224, 175, 141, 224, 174, 149, 8, 129, 175, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 163, 0, 224, 175, 141, 224, 174, 149, 8, 135, 175, 224, 178, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 149, 8, 139, 175, 224, 175, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 149, 8, 141, 175, 224, 176, 174, 224, 139, 175, 224, 170, 174, 224, 2, 224, 175, 129, 224, 174, 163, 0, 224, 175, 141, 224, 174, 149, 8, 178, 174, 224, 2, 224, 174, 191, 224, 174, 169, 0, 224, 175, 141, 224, 174, 149, 8, 178, 174, 224, 2, 224, 175, 135, 224, 174, 156, 0, 224, 175, 141, 224, 174, 149, 8, 190, 174, 224, 164, 174, 224, 135, 175, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 191, 0, 224, 175, 141, 224, 174, 149, 8, 190, 174, 224, 164, 174, 224, 191, 174, 224, 181, 174, 224, 149, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 191, 0, 224, 175, 141, 224, 174, 149, 8, 190, 174, 224, 181, 174, 224, 135, 175, 224, 164, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 136, 0, 224, 175, 141, 224, 174, 149, 8, 191, 174, 224, 149, 174, 224, 141, 175, 224, 149, 174, 224, 190, 174, 224, 170, 174, 224, 141, 175, 224, 170, 174, 224, 129, 175, 224, 164, 174, 224, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 224, 174, 149, 8, 191, 174, 224, 159, 174, 224, 134, 175, 224, 181, 174, 224, 2, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 224, 174, 149, 8, 191, 174, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 174, 224, 175, 141, 32, 0, 224, 175, 141, 224, 174, 149, 8, 191, 174, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 174, 149, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 1, 18, 68, 2, 224, 174, 176, 224, 174, 149, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 1, 18, 68, 2, 224, 174, 176, 224, 174, 185, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 1, 129, 175, 224, 149, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 1, 129, 175, 224, 168, 174, 224, 133, 174, 224, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 1, 129, 175, 224, 169, 174, 224, 133, 174, 224, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 1, 133, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 1, 135, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 1, 190, 174, 224, 175, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 149, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 8, 170, 174, 224, 141, 175, 224, 170, 174, 224, 141, 175, 224, 176, 174, 224, 149, 174, 224, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 8, 179, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 8, 181, 174, 224, 168, 174, 224, 2, 224, 174, 176, 18, 71, 0, 224, 175, 141, 224, 174, 149, 224, 174, 191, 8, 191, 174, 224, 178, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 0, 4, 224, 175, 141, 224, 174, 149, 1, 141, 175, 224, 176, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 164, 224, 174, 191, 3, 79, 79, 107, 0, 224, 175, 141, 224, 174, 149, 8, 129, 175, 224, 180, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 181, 224, 174, 169, 0, 224, 175, 141, 224, 174, 149, 8, 136, 175, 224, 163, 174, 224, 129, 175, 224, 164, 174, 224, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 224, 174, 149, 8, 141, 175, 224, 176, 174, 224, 128, 175, 224, 164, 174, 224, 2, 224, 174, 174, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 149, 8, 141, 175, 224, 176, 174, 224, 128, 175, 224, 164, 174, 224, 2, 224, 174, 174, 224, 174, 190, 224, 174, 169, 0, 224, 175, 141, 224, 174, 149, 8, 191, 174, 224, 169, 174, 224, 164, 174, 224, 2, 224, 174, 181, 224, 174, 169, 0, 4, 224, 175, 141, 224, 174, 149, 1, 141, 175, 224, 176, 174, 224, 129, 175, 224, 164, 174, 224, 3, 79, 79, 147, 0, 224, 175, 141, 224, 174, 149, 1, 141, 175, 224, 176, 174, 224, 130, 175, 224, 174, 174, 224, 0, 224, 175, 141, 224, 174, 149, 1, 141, 175, 224, 176, 174, 224, 190, 174, 224, 174, 174, 224, 0, 224, 175, 141, 224, 174, 149, 8, 141, 175, 224, 176, 174, 224, 138, 175, 224, 154, 174, 224, 0, 224, 175, 141, 224, 174, 149, 8, 141, 175, 224, 176, 174, 224, 181, 174, 224, 0, 224, 175, 141, 224, 174, 149, 8, 141, 175, 224, 176, 174, 224, 181, 174, 224, 141, 175, 224, 184, 174, 224, 0, 224, 175, 141, 224, 174, 149, 8, 156, 174, 224, 0, 4, 3, 79, 107, 0, 2, 224, 174, 156, 0, 8, 2, 28, 17, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 170, 224, 174, 190, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 190, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 175, 130, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 175, 136, 0, 8, 2, 224, 174, 158, 224, 175, 141, 224, 174, 154, 224, 174, 190, 0, 8, 2, 224, 174, 159, 224, 174, 149, 224, 174, 159, 0, 8, 2, 224, 174, 159, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 159, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 159, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 174, 159, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 190, 224, 174, 176, 224, 175, 136, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 174, 159, 224, 175, 139, 224, 174, 164, 224, 175, 141, 224, 174, 149, 224, 174, 156, 0, 8, 2, 224, 174, 163, 224, 174, 170, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 163, 224, 175, 128, 224, 174, 176, 0, 8, 2, 224, 174, 163, 224, 175, 135, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 164, 224, 174, 190, 224, 174, 175, 224, 175, 129, 224, 174, 164, 0, 8, 2, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 174, 178, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 164, 224, 174, 191, 224, 174, 164, 224, 174, 190, 0, 8, 2, 224, 174, 164, 224, 174, 191, 224, 174, 174, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 154, 0, 8, 2, 224, 174, 164, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 174, 191, 224, 174, 178, 224, 175, 141, 0, 8, 2, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 175, 136, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 176, 224, 175, 141, 224, 174, 181, 0, 8, 2, 224, 174, 169, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 169, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 169, 224, 174, 170, 224, 174, 190, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 169, 224, 174, 174, 0, 8, 2, 224, 174, 169, 224, 174, 176, 224, 174, 149, 0, 8, 2, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 134, 0, 8, 2, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 176, 0, 8, 2, 224, 174, 174, 224, 174, 149, 224, 174, 174, 0, 8, 2, 224, 174, 174, 224, 174, 181, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 128, 224, 174, 176, 0, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 154, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 174, 175, 224, 175, 136, 0, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 156, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 159, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 156, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 170, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 181, 0, 8, 2, 224, 174, 178, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 178, 18, 73, 224, 174, 175, 224, 175, 139, 0, 8, 2, 224, 174, 178, 224, 175, 128, 224, 174, 154, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 178, 224, 175, 128, 224, 174, 176, 0, 8, 2, 224, 174, 178, 224, 175, 128, 224, 174, 178, 0, 8, 2, 224, 174, 179, 224, 175, 129, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 181, 224, 174, 163, 0, 8, 2, 224, 174, 181, 224, 174, 169, 0, 8, 2, 224, 174, 181, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 176, 0, 8, 2, 224, 174, 181, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 175, 141, 224, 174, 174, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 174, 181, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 174, 181, 224, 175, 129, 224, 174, 169, 224, 175, 136, 0, 8, 2, 224, 174, 181, 224, 175, 129, 224, 174, 169, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 181, 224, 175, 129, 224, 174, 176, 0, 8, 141, 175, 224, 149, 174, 224, 136, 175, 224, 178, 174, 224, 164, 174, 224, 2, 224, 174, 169, 0, 8, 141, 175, 224, 177, 174, 224, 168, 174, 224, 2, 224, 174, 164, 224, 174, 191, 0, 224, 174, 170, 224, 175, 141, 8, 2, 18, 69, 224, 174, 190, 3, 79, 107, 48, 0, 224, 174, 170, 224, 175, 141, 224, 174, 154, 8, 2, 224, 174, 191, 224, 174, 170, 224, 175, 141, 3, 79, 107, 48, 74, 0, 224, 174, 169, 224, 174, 149, 8, 2, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 164, 3, 79, 107, 50, 107, 49, 107, 0, 224, 174, 181, 224, 174, 176, 224, 175, 141, 224, 174, 174, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 3, 79, 107, 82, 107, 34, 63, 36, 64, 138, 147, 0, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 135, 224, 174, 149, 8, 2, 224, 174, 176, 3, 79, 116, 64, 139, 112, 49, 107, 0, 4, 224, 175, 139, 224, 174, 170, 2, 224, 174, 190, 224, 174, 178, 3, 79, 117, 48, 0, 224, 175, 139, 224, 174, 170, 8, 2, 224, 174, 191, 224, 174, 149, 224, 174, 190, 12, 0, 224, 175, 139, 224, 174, 149, 8, 2, 224, 174, 191, 224, 174, 178, 224, 174, 190, 3, 79, 117, 49, 0, 224, 175, 139, 224, 174, 149, 8, 2, 224, 174, 176, 3, 79, 117, 49, 107, 0, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 154, 8, 2, 224, 175, 135, 3, 79, 117, 139, 87, 0, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 190, 3, 79, 121, 34, 49, 0, 4, 224, 175, 134, 224, 174, 179, 8, 2, 224, 174, 164, 224, 174, 174, 3, 79, 133, 0, 224, 175, 134, 224, 174, 179, 8, 2, 224, 174, 176, 224, 174, 181, 0, 224, 175, 134, 224, 174, 179, 8, 2, 224, 174, 176, 224, 174, 191, 0, 224, 175, 140, 224, 174, 164, 8, 3, 79, 133, 47, 147, 0, 4, 224, 175, 141, 224, 174, 159, 1, 142, 174, 224, 2, 224, 175, 135, 3, 79, 139, 0, 224, 175, 141, 224, 174, 159, 8, 134, 175, 224, 185, 174, 224, 2, 224, 175, 135, 0, 4, 1, 139, 175, 224, 174, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 191, 3, 106, 0, 1, 174, 174, 224, 2, 224, 174, 190, 0, 1, 174, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 175, 129, 224, 174, 181, 224, 174, 176, 0, 1, 174, 174, 224, 2, 224, 175, 135, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 1, 174, 174, 224, 2, 224, 175, 135, 224, 174, 183, 224, 175, 141, 224, 174, 181, 0, 1, 174, 174, 224, 2, 224, 175, 135, 224, 174, 184, 224, 175, 141, 224, 174, 181, 224, 174, 176, 0, 8, 174, 174, 224, 2, 224, 174, 191, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 174, 174, 224, 2, 224, 174, 191, 224, 174, 174, 224, 175, 136, 0, 1, 139, 175, 224, 174, 174, 224, 2, 224, 174, 169, 3, 106, 107, 0, 7, 6, 1, 26, 0, 2, 17, 66, 3, 66, 0, 3, 66, 107, 0, 7, 6, 1, 27, 0, 1, 141, 175, 224, 158, 174, 224, 2, 17, 66, 3, 73, 0, 1, 141, 175, 224, 158, 174, 224, 3, 73, 107, 0, 4, 1, 32, 141, 175, 224, 154, 174, 224, 2, 17, 66, 3, 74, 0, 1, 134, 174, 224, 2, 224, 174, 190, 224, 174, 176, 32, 0, 1, 134, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 164, 224, 175, 141, 0, 1, 134, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 174, 0, 1, 141, 175, 224, 159, 174, 224, 2, 17, 66, 0, 1, 141, 175, 224, 177, 174, 224, 2, 17, 66, 0, 1, 170, 174, 224, 133, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 1, 170, 174, 224, 137, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 1, 170, 174, 224, 139, 175, 224, 156, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 1, 170, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 1, 190, 174, 224, 174, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 1, 190, 174, 224, 178, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 1, 191, 174, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 2, 224, 174, 190, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 2, 224, 175, 134, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 8, 2, 17, 66, 28, 17, 0, 8, 2, 224, 174, 190, 224, 174, 163, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 174, 190, 224, 174, 174, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 174, 190, 224, 174, 175, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 175, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 129, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 156, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 156, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 178, 224, 174, 184, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 179, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 169, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 169, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 149, 224, 175, 139, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 149, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 170, 224, 174, 190, 224, 174, 170, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 164, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 190, 0, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 181, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 130, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 176, 224, 174, 181, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 176, 224, 174, 190, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 177, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 179, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 175, 128, 224, 174, 169, 32, 0, 8, 2, 224, 175, 128, 224, 174, 169, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 0, 8, 2, 224, 175, 128, 224, 174, 169, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 175, 128, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 175, 128, 224, 174, 169, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 175, 128, 224, 174, 184, 224, 175, 129, 0, 8, 2, 224, 175, 128, 224, 174, 184, 224, 175, 136, 0, 8, 2, 224, 175, 128, 224, 174, 184, 224, 175, 141, 32, 0, 8, 2, 224, 175, 129, 224, 174, 159, 224, 174, 191, 224, 174, 164, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 175, 130, 224, 174, 175, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 174, 163, 0, 8, 2, 224, 175, 134, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 134, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 139, 18, 69, 0, 8, 2, 224, 175, 134, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 184, 0, 8, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 168, 224, 174, 190, 224, 174, 159, 0, 8, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 190, 224, 174, 179, 224, 175, 136, 224, 174, 175, 0, 8, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 191, 0, 8, 2, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 175, 136, 0, 8, 2, 224, 175, 134, 224, 174, 175, 224, 174, 191, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 175, 139, 224, 174, 170, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 149, 224, 175, 141, 32, 18, 82, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 179, 224, 174, 191, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 180, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 164, 224, 175, 141, 32, 18, 84, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 170, 224, 175, 141, 32, 18, 83, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 190, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 179, 224, 175, 141, 224, 174, 179, 224, 175, 136, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 134, 224, 174, 163, 224, 175, 141, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 136, 224, 174, 175, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 174, 224, 174, 190, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 174, 224, 175, 135, 32, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 175, 136, 224, 174, 175, 224, 174, 190, 0, 8, 2, 224, 175, 134, 224, 174, 184, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 158, 224, 175, 141, 224, 174, 154, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 169, 0, 8, 2, 224, 175, 135, 224, 174, 169, 224, 174, 178, 0, 8, 2, 224, 175, 135, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 175, 135, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 175, 135, 224, 174, 176, 224, 175, 141, 224, 174, 174, 224, 175, 135, 224, 174, 169, 0, 8, 2, 224, 175, 135, 224, 174, 178, 224, 174, 158, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 183, 224, 175, 141, 224, 174, 159, 224, 175, 136, 0, 8, 2, 224, 175, 136, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 136, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 175, 136, 224, 174, 169, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 175, 136, 224, 174, 169, 224, 175, 128, 224, 174, 184, 0, 8, 2, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 175, 140, 224, 174, 164, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 175, 140, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 175, 140, 224, 174, 185, 224, 174, 190, 224, 174, 169, 0, 8, 18, 71, 176, 174, 224, 191, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 8, 128, 175, 224, 176, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 156, 0, 8, 129, 175, 224, 154, 174, 224, 2, 224, 175, 128, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 8, 141, 175, 224, 184, 174, 224, 191, 174, 224, 159, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 156, 0, 8, 154, 174, 224, 2, 224, 174, 191, 224, 174, 169, 0, 8, 191, 174, 224, 170, 174, 224, 139, 175, 224, 149, 174, 224, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 224, 175, 141, 2, 32, 24, 0, 224, 175, 141, 224, 174, 154, 2, 17, 66, 3, 74, 12, 0, 224, 175, 141, 224, 174, 154, 3, 74, 12, 107, 0, 224, 175, 134, 224, 174, 149, 224, 175, 141, 8, 2, 32, 3, 74, 36, 49, 0, 224, 175, 134, 224, 174, 154, 224, 175, 141, 8, 2, 224, 174, 169, 224, 174, 191, 224, 174, 175, 224, 174, 190, 3, 74, 36, 74, 0, 4, 224, 175, 134, 224, 174, 154, 8, 2, 224, 174, 169, 224, 174, 191, 224, 174, 175, 224, 174, 190, 3, 74, 36, 74, 107, 0, 224, 175, 134, 224, 174, 154, 8, 2, 224, 174, 169, 224, 175, 141, 224, 174, 175, 224, 174, 190, 0, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 179, 224, 175, 136, 224, 174, 175, 3, 74, 36, 138, 138, 37, 48, 0, 224, 174, 191, 224, 174, 164, 1, 129, 175, 224, 154, 174, 224, 2, 224, 175, 141, 224, 174, 176, 224, 174, 190, 3, 74, 37, 47, 0, 224, 174, 191, 224, 174, 170, 224, 175, 141, 8, 2, 224, 174, 149, 224, 174, 179, 3, 74, 37, 48, 0, 4, 224, 174, 191, 224, 174, 149, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 139, 3, 74, 37, 49, 0, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 2, 224, 174, 174, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 224, 175, 130, 224, 174, 176, 0, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 2, 224, 174, 178, 224, 175, 134, 224, 174, 159, 224, 175, 141, 0, 4, 1, 32, 141, 175, 224, 154, 174, 224, 3, 74, 107, 0, 1, 141, 175, 224, 159, 174, 224, 0, 1, 141, 175, 224, 177, 174, 224, 0, 1, 190, 174, 224, 159, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 134, 175, 224, 181, 174, 224, 2, 224, 174, 178, 0, 1, 190, 174, 224, 159, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 135, 175, 224, 181, 174, 224, 2, 224, 174, 178, 0, 1, 190, 174, 224, 163, 174, 224, 129, 175, 224, 176, 174, 224, 133, 174, 224, 2, 224, 174, 178, 0, 1, 190, 174, 224, 164, 174, 224, 129, 175, 224, 176, 174, 224, 174, 174, 224, 2, 224, 174, 178, 0, 1, 190, 174, 224, 164, 174, 224, 135, 175, 224, 181, 174, 224, 2, 224, 174, 178, 0, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 176, 0, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 8, 2, 28, 17, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 224, 174, 181, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 18, 73, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 169, 224, 174, 191, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 169, 224, 174, 191, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 179, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 164, 224, 175, 129, 224, 174, 176, 224, 175, 141, 0, 8, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 8, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 176, 224, 175, 129, 0, 8, 2, 224, 174, 164, 224, 175, 141, 224, 174, 176, 224, 174, 170, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 164, 224, 175, 141, 224, 174, 176, 224, 175, 129, 0, 8, 2, 224, 174, 170, 224, 175, 141, 224, 174, 170, 18, 76, 224, 175, 141, 0, 8, 2, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 190, 0, 8, 2, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 0, 8, 2, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 0, 8, 2, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 134, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 175, 129, 0, 8, 2, 224, 174, 178, 224, 175, 139, 0, 8, 2, 224, 174, 181, 224, 174, 190, 224, 174, 169, 0, 8, 139, 175, 224, 174, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 169, 0, 8, 139, 175, 224, 174, 174, 224, 191, 174, 224, 181, 174, 224, 170, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 169, 0, 8, 139, 175, 224, 174, 174, 224, 191, 174, 224, 181, 174, 224, 181, 174, 224, 190, 174, 224, 170, 174, 224, 2, 224, 174, 169, 0, 8, 139, 175, 224, 178, 174, 224, 2, 224, 174, 169, 224, 174, 190, 0, 8, 139, 175, 224, 178, 174, 224, 169, 174, 224, 128, 175, 224, 174, 174, 224, 2, 224, 174, 169, 224, 174, 191, 0, 8, 139, 175, 224, 178, 174, 224, 178, 174, 224, 128, 175, 224, 168, 174, 224, 2, 224, 174, 169, 224, 174, 191, 0, 8, 141, 175, 224, 153, 174, 224, 170, 174, 224, 2, 224, 174, 176, 0, 8, 141, 175, 224, 169, 174, 224, 191, 174, 224, 159, 174, 224, 2, 224, 174, 176, 0, 8, 190, 174, 224, 149, 174, 224, 191, 174, 224, 163, 174, 224, 164, 174, 224, 2, 224, 174, 178, 0, 8, 190, 174, 224, 183, 174, 224, 135, 175, 224, 154, 174, 224, 2, 224, 174, 178, 0, 224, 174, 176, 224, 175, 141, 224, 174, 154, 8, 2, 224, 174, 191, 3, 74, 107, 34, 74, 0, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 170, 8, 2, 224, 174, 164, 224, 174, 191, 3, 74, 107, 47, 47, 37, 34, 107, 48, 107, 0, 224, 174, 149, 224, 175, 141, 8, 170, 174, 224, 3, 74, 107, 49, 0, 224, 174, 190, 8, 2, 224, 174, 169, 224, 174, 178, 3, 74, 112, 0, 224, 174, 190, 224, 174, 176, 224, 175, 129, 224, 174, 178, 224, 174, 164, 8, 2, 224, 174, 190, 3, 74, 116, 34, 120, 55, 107, 47, 0, 224, 174, 190, 224, 174, 170, 224, 175, 141, 8, 2, 224, 174, 179, 224, 174, 191, 224, 174, 169, 3, 74, 116, 48, 0, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 170, 8, 2, 224, 175, 128, 18, 69, 3, 74, 116, 49, 48, 0, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 178, 224, 175, 135, 224, 174, 159, 224, 175, 141, 8, 3, 74, 116, 49, 55, 112, 138, 0, 4, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 169, 3, 74, 116, 50, 70, 0, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 178, 0, 224, 174, 190, 224, 174, 174, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 191, 224, 174, 175, 224, 174, 169, 3, 74, 116, 63, 48, 0, 8, 141, 175, 224, 158, 174, 224, 190, 174, 224, 176, 174, 224, 3, 74, 147, 0, 4, 2, 17, 66, 3, 87, 0, 8, 2, 17, 66, 0, 8, 2, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 176, 224, 174, 174, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 174, 224, 174, 190, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 174, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 174, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 185, 224, 174, 190, 0, 8, 2, 224, 175, 128, 224, 174, 169, 224, 174, 191, 224, 174, 181, 224, 174, 190, 0, 8, 2, 224, 175, 136, 224, 174, 169, 224, 174, 190, 32, 224, 174, 168, 224, 175, 135, 224, 174, 181, 224, 174, 190, 224, 174, 178, 0, 8, 135, 175, 224, 164, 174, 224, 2, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 224, 174, 191, 2, 224, 174, 176, 224, 174, 174, 0, 224, 174, 191, 8, 2, 224, 174, 168, 224, 175, 135, 0, 224, 174, 191, 8, 2, 224, 174, 169, 224, 175, 135, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 178, 224, 174, 190, 224, 174, 149, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 178, 224, 175, 135, 224, 174, 159, 0, 224, 175, 129, 1, 128, 175, 224, 176, 174, 224, 190, 174, 224, 169, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 141, 175, 224, 176, 174, 224, 133, 174, 224, 2, 224, 174, 181, 0, 224, 175, 129, 1, 135, 175, 224, 149, 174, 224, 2, 224, 174, 181, 0, 224, 175, 129, 1, 135, 175, 224, 156, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 181, 224, 174, 176, 0, 224, 175, 129, 1, 135, 175, 224, 159, 174, 224, 141, 175, 224, 163, 174, 224, 190, 174, 224, 178, 174, 224, 191, 174, 224, 149, 174, 224, 133, 174, 224, 2, 224, 174, 181, 224, 174, 176, 0, 224, 175, 129, 1, 135, 175, 224, 163, 174, 224, 181, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 181, 224, 174, 176, 0, 224, 175, 129, 1, 135, 175, 224, 163, 174, 224, 181, 174, 224, 190, 174, 224, 176, 174, 224, 135, 174, 224, 2, 224, 174, 181, 224, 174, 176, 0, 224, 175, 129, 1, 135, 175, 224, 174, 174, 224, 2, 224, 174, 181, 0, 224, 175, 129, 1, 191, 174, 224, 181, 174, 224, 2, 224, 174, 181, 0, 224, 175, 129, 2, 224, 174, 181, 224, 174, 190, 224, 174, 164, 224, 175, 128, 224, 174, 169, 0, 224, 175, 129, 2, 224, 174, 181, 224, 174, 190, 224, 174, 174, 224, 174, 191, 0, 224, 175, 129, 2, 224, 174, 181, 224, 174, 190, 224, 174, 176, 224, 174, 184, 224, 175, 141, 224, 174, 175, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 164, 224, 174, 191, 0, 224, 175, 129, 8, 2, 224, 174, 178, 224, 175, 139, 224, 174, 149, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 176, 224, 175, 141, 224, 174, 163, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 190, 224, 174, 154, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 154, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 191, 224, 174, 184, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 175, 128, 224, 174, 159, 0, 224, 175, 129, 8, 128, 175, 224, 169, 174, 224, 154, 174, 224, 2, 224, 174, 181, 224, 174, 176, 0, 224, 175, 129, 8, 128, 175, 224, 178, 174, 224, 190, 174, 224, 170, 174, 224, 149, 174, 224, 2, 224, 174, 181, 0, 224, 175, 129, 8, 135, 175, 224, 159, 174, 224, 141, 175, 224, 163, 174, 224, 149, 174, 224, 178, 174, 224, 156, 174, 224, 2, 224, 174, 181, 0, 224, 175, 129, 8, 136, 174, 224, 0, 4, 224, 174, 191, 224, 174, 176, 224, 175, 129, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 176, 3, 87, 34, 37, 0, 224, 174, 191, 224, 174, 176, 224, 175, 129, 8, 2, 224, 174, 183, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 178, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 190, 3, 87, 34, 37, 55, 107, 66, 49, 0, 224, 175, 128, 2, 224, 174, 169, 224, 174, 191, 224, 174, 181, 224, 174, 190, 224, 174, 154, 3, 87, 34, 110, 0, 224, 175, 134, 224, 174, 175, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 159, 8, 3, 87, 36, 57, 37, 50, 138, 0, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 169, 224, 175, 141, 224, 174, 159, 8, 3, 87, 36, 57, 50, 138, 0, 224, 175, 129, 224, 174, 181, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 175, 139, 224, 174, 180, 224, 174, 191, 3, 87, 40, 82, 107, 34, 49, 49, 0, 224, 175, 129, 224, 174, 181, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 3, 87, 82, 107, 34, 79, 79, 147, 0, 4, 224, 175, 129, 224, 174, 181, 224, 174, 190, 224, 174, 176, 224, 174, 154, 224, 174, 191, 1, 133, 174, 224, 2, 224, 174, 175, 3, 87, 82, 116, 34, 107, 87, 0, 224, 175, 129, 224, 174, 181, 224, 174, 190, 224, 174, 176, 224, 174, 154, 224, 174, 191, 8, 2, 224, 174, 175, 0, 4, 3, 87, 107, 0, 1, 133, 174, 224, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 176, 224, 175, 141, 224, 174, 170, 0, 8, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 176, 224, 175, 141, 224, 174, 170, 0, 8, 141, 175, 224, 159, 174, 224, 185, 174, 224, 2, 224, 174, 169, 0, 8, 141, 175, 224, 159, 174, 224, 190, 174, 224, 181, 174, 224, 2, 224, 174, 169, 0, 8, 141, 175, 224, 159, 174, 224, 191, 174, 224, 181, 174, 224, 135, 175, 224, 159, 174, 224, 2, 224, 174, 169, 0, 224, 174, 176, 224, 174, 154, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 164, 224, 174, 191, 3, 87, 107, 34, 107, 87, 0, 4, 2, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 3, 91, 0, 2, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 170, 224, 174, 149, 0, 4, 2, 224, 174, 163, 224, 175, 141, 224, 174, 170, 224, 174, 149, 3, 91, 107, 0, 2, 224, 174, 163, 224, 175, 141, 224, 174, 174, 224, 175, 129, 0, 224, 174, 153, 224, 175, 141, 224, 174, 149, 2, 224, 174, 176, 3, 91, 107, 66, 49, 107, 0, 7, 6, 1, 29, 0, 4, 2, 17, 66, 3, 73, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 190, 224, 174, 178, 0, 3, 73, 107, 0, 8, 141, 175, 224, 169, 174, 224, 191, 174, 224, 159, 174, 224, 2, 224, 174, 176, 3, 74, 107, 0, 7, 6, 1, 31, 0, 4, 224, 175, 141, 224, 174, 154, 224, 175, 141, 1, 135, 174, 224, 3, 50, 74, 0, 224, 175, 141, 224, 174, 154, 224, 175, 141, 8, 191, 174, 224, 181, 174, 224, 0, 224, 175, 141, 224, 174, 154, 8, 190, 174, 224, 149, 174, 224, 2, 224, 174, 169, 3, 50, 74, 107, 0, 2, 17, 66, 3, 65, 0, 3, 65, 107, 0, 7, 6, 1, 32, 0, 4, 224, 174, 191, 1, 141, 175, 224, 184, 174, 224, 178, 174, 224, 138, 175, 224, 149, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 178, 3, 23, 138, 0, 224, 175, 141, 1, 141, 175, 224, 184, 174, 224, 2, 224, 174, 176, 0, 4, 224, 175, 141, 224, 174, 154, 224, 175, 129, 1, 178, 174, 224, 2, 224, 174, 174, 224, 174, 163, 3, 49, 91, 0, 224, 175, 141, 224, 174, 154, 224, 175, 129, 1, 178, 174, 224, 2, 224, 174, 174, 224, 174, 191, 0, 4, 1, 32, 141, 175, 224, 178, 174, 224, 129, 175, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 184, 3, 138, 0, 1, 129, 175, 224, 179, 174, 224, 2, 224, 175, 139, 224, 174, 169, 224, 174, 191, 224, 174, 175, 0, 1, 141, 175, 224, 163, 174, 224, 135, 174, 224, 2, 224, 175, 134, 0, 1, 141, 175, 224, 178, 174, 224, 133, 174, 224, 2, 224, 174, 190, 0, 1, 141, 175, 224, 178, 174, 224, 137, 174, 224, 2, 224, 174, 190, 0, 1, 141, 175, 224, 183, 174, 224, 2, 17, 66, 0, 1, 141, 175, 224, 184, 174, 224, 2, 17, 66, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 154, 224, 174, 190, 224, 174, 169, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 156, 224, 174, 190, 224, 174, 169, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 174, 224, 174, 190, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 131, 224, 174, 170, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 174, 191, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 174, 0, 8, 2, 224, 174, 191, 224, 174, 181, 224, 174, 191, 224, 174, 149, 0, 8, 2, 224, 174, 191, 224, 174, 181, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 191, 224, 174, 181, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 183, 224, 175, 141, 224, 174, 175, 0, 8, 2, 224, 175, 128, 0, 8, 2, 224, 175, 129, 224, 174, 169, 224, 174, 191, 224, 174, 154, 224, 174, 191, 224, 174, 175, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 169, 224, 174, 191, 224, 174, 184, 0, 8, 2, 224, 175, 129, 224, 174, 169, 224, 175, 128, 18, 69, 0, 8, 2, 224, 175, 129, 224, 174, 169, 224, 175, 128, 224, 174, 183, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 130, 224, 174, 176, 0, 8, 2, 224, 175, 134, 224, 174, 149, 224, 175, 141, 224, 174, 184, 224, 174, 190, 224, 174, 184, 0, 8, 2, 224, 175, 134, 224, 174, 149, 224, 175, 141, 224, 174, 184, 224, 175, 141, 0, 8, 2, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 8, 2, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 191, 224, 174, 184, 0, 8, 2, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 183, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 176, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 174, 191, 224, 174, 131, 224, 174, 170, 224, 175, 139, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 174, 191, 224, 174, 181, 224, 174, 191, 224, 174, 183, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 32, 224, 174, 133, 224, 174, 181, 224, 175, 128, 224, 174, 181, 0, 8, 2, 224, 175, 135, 224, 174, 170, 0, 8, 2, 224, 175, 135, 224, 174, 184, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 136, 224, 174, 174, 224, 175, 141, 32, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 169, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 175, 224, 175, 139, 0, 8, 2, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 178, 0, 8, 2, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 8, 32, 141, 175, 224, 169, 174, 224, 190, 174, 224, 178, 174, 224, 2, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 191, 224, 174, 184, 0, 8, 32, 141, 175, 224, 179, 174, 224, 191, 174, 224, 170, 174, 224, 135, 175, 224, 159, 174, 224, 2, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 191, 224, 174, 184, 0, 8, 130, 175, 224, 175, 174, 224, 141, 175, 224, 159, 174, 224, 2, 224, 174, 191, 0, 8, 130, 175, 224, 175, 174, 224, 191, 174, 224, 159, 174, 224, 2, 224, 174, 191, 0, 8, 140, 175, 224, 149, 174, 224, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 175, 0, 8, 141, 175, 224, 163, 174, 224, 135, 175, 224, 149, 174, 224, 2, 224, 175, 128, 224, 174, 169, 0, 8, 141, 175, 224, 163, 174, 224, 135, 175, 224, 170, 174, 224, 2, 224, 174, 191, 0, 8, 141, 175, 224, 163, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 175, 128, 224, 174, 169, 0, 8, 141, 175, 224, 170, 174, 224, 131, 174, 224, 135, 175, 224, 154, 174, 224, 2, 224, 174, 191, 0, 8, 141, 175, 224, 176, 174, 224, 139, 175, 224, 170, 174, 224, 2, 224, 174, 191, 224, 174, 149, 224, 175, 139, 0, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 175, 130, 224, 174, 169, 0, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 174, 174, 224, 2, 224, 174, 191, 224, 174, 169, 0, 8, 141, 175, 224, 178, 174, 224, 175, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 191, 0, 8, 141, 175, 224, 178, 174, 224, 181, 174, 224, 190, 174, 224, 168, 174, 224, 2, 224, 174, 191, 0, 8, 141, 175, 224, 178, 174, 224, 190, 174, 224, 174, 174, 224, 2, 224, 174, 190, 0, 8, 149, 174, 224, 134, 175, 224, 168, 174, 224, 2, 224, 174, 191, 224, 174, 181, 0, 8, 191, 174, 224, 156, 174, 224, 134, 175, 224, 181, 174, 224, 2, 224, 175, 135, 0, 8, 191, 174, 224, 176, 174, 224, 141, 175, 224, 170, 174, 224, 2, 224, 175, 139, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 8, 191, 174, 224, 178, 174, 224, 190, 174, 224, 181, 174, 224, 141, 175, 224, 149, 174, 224, 2, 224, 174, 191, 0, 224, 174, 191, 1, 141, 175, 224, 163, 174, 224, 135, 174, 224, 2, 224, 174, 176, 224, 175, 134, 224, 174, 184, 224, 175, 141, 224, 174, 159, 0, 224, 174, 191, 1, 141, 175, 224, 163, 174, 224, 149, 174, 224, 2, 224, 174, 176, 224, 175, 139, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 175, 130, 224, 174, 154, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 175, 130, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 175, 130, 224, 174, 170, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 175, 130, 224, 174, 183, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 153, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 170, 224, 174, 191, 224, 174, 179, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 156, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 131, 224, 174, 170, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 170, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 174, 224, 175, 128, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 178, 224, 175, 135, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 181, 224, 175, 135, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 178, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 175, 134, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 174, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 163, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 175, 224, 174, 191, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 178, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 135, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 136, 32, 224, 174, 154, 224, 175, 134, 224, 174, 158, 224, 175, 141, 224, 174, 154, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 136, 32, 224, 174, 154, 224, 175, 134, 224, 174, 175, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 136, 32, 224, 174, 170, 224, 174, 163, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 136, 224, 174, 175, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 136, 224, 174, 178, 224, 174, 176, 0, 224, 174, 191, 8, 141, 175, 224, 163, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 224, 175, 141, 1, 134, 174, 224, 2, 224, 174, 176, 224, 174, 190, 0, 224, 175, 141, 1, 134, 174, 224, 2, 224, 174, 177, 224, 174, 190, 0, 224, 175, 141, 1, 134, 175, 224, 168, 174, 224, 141, 175, 224, 176, 174, 224, 159, 174, 224, 141, 175, 224, 163, 174, 224, 135, 174, 224, 0, 224, 175, 141, 1, 135, 174, 224, 2, 224, 174, 178, 224, 174, 176, 0, 224, 175, 141, 1, 141, 175, 224, 163, 174, 224, 134, 175, 224, 174, 174, 224, 21, 0, 224, 175, 141, 1, 141, 175, 224, 163, 174, 224, 135, 174, 224, 2, 224, 174, 176, 224, 175, 135, 224, 174, 184, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 1, 141, 175, 224, 163, 174, 224, 142, 174, 224, 2, 224, 174, 176, 224, 174, 191, 0, 224, 175, 141, 1, 141, 175, 224, 163, 174, 224, 149, 174, 224, 2, 224, 174, 176, 224, 175, 139, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 175, 224, 175, 130, 224, 174, 154, 224, 174, 169, 0, 224, 175, 141, 8, 2, 224, 174, 175, 224, 175, 130, 224, 174, 169, 0, 224, 175, 141, 8, 2, 224, 174, 175, 224, 175, 130, 224, 174, 170, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 153, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 170, 224, 174, 191, 224, 174, 179, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 184, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 156, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 131, 224, 174, 170, 224, 174, 176, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 170, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 170, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 174, 224, 175, 128, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 178, 224, 175, 135, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 181, 224, 175, 135, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 178, 224, 174, 191, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 175, 134, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 174, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 163, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 178, 224, 174, 176, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 135, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 136, 32, 224, 174, 154, 224, 175, 134, 224, 174, 158, 224, 175, 141, 224, 174, 154, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 136, 32, 224, 174, 154, 224, 175, 134, 224, 174, 175, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 136, 32, 224, 174, 170, 224, 174, 163, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 136, 224, 174, 175, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 136, 224, 174, 178, 224, 174, 176, 0, 224, 175, 141, 8, 128, 175, 224, 168, 174, 224, 2, 224, 174, 176, 224, 174, 190, 0, 224, 175, 141, 8, 128, 175, 224, 168, 174, 224, 2, 224, 174, 177, 224, 174, 190, 0, 224, 175, 141, 8, 128, 175, 224, 181, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 128, 175, 224, 181, 174, 224, 129, 175, 224, 159, 174, 224, 168, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 130, 175, 224, 149, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 130, 175, 224, 175, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 0, 224, 175, 141, 8, 130, 175, 224, 175, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 169, 0, 224, 175, 141, 8, 130, 175, 224, 176, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 134, 175, 224, 170, 174, 224, 2, 224, 174, 176, 224, 175, 139, 0, 224, 175, 141, 8, 134, 175, 224, 174, 174, 224, 2, 224, 174, 176, 224, 175, 139, 0, 224, 175, 141, 8, 134, 175, 224, 174, 174, 224, 141, 175, 224, 178, 174, 224, 134, 175, 224, 185, 174, 224, 0, 224, 175, 141, 8, 135, 175, 224, 149, 174, 224, 2, 224, 174, 176, 224, 175, 129, 0, 224, 175, 141, 8, 135, 175, 224, 174, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 135, 175, 224, 178, 174, 224, 0, 224, 175, 141, 8, 139, 175, 224, 168, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 139, 175, 224, 170, 174, 224, 2, 224, 174, 176, 224, 175, 129, 0, 224, 175, 141, 8, 139, 175, 224, 176, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 139, 175, 224, 176, 174, 224, 129, 175, 224, 159, 174, 224, 168, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 141, 175, 224, 163, 174, 224, 135, 175, 224, 170, 174, 224, 0, 224, 175, 141, 8, 141, 175, 224, 163, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 224, 175, 141, 8, 164, 174, 224, 2, 224, 174, 176, 224, 174, 190, 0, 224, 175, 141, 8, 164, 174, 224, 2, 224, 174, 177, 224, 174, 190, 0, 224, 175, 141, 8, 164, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 190, 174, 224, 149, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 190, 174, 224, 168, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 190, 174, 224, 170, 174, 224, 2, 224, 174, 178, 0, 224, 175, 141, 8, 191, 174, 224, 181, 174, 224, 2, 224, 174, 176, 224, 175, 129, 0, 224, 175, 141, 8, 191, 174, 224, 185, 174, 224, 2, 224, 174, 178, 224, 174, 176, 0, 4, 224, 174, 191, 224, 174, 176, 224, 175, 134, 224, 174, 175, 224, 174, 191, 8, 2, 224, 174, 178, 224, 174, 176, 3, 138, 34, 36, 57, 0, 224, 175, 141, 224, 174, 176, 224, 175, 134, 224, 174, 175, 224, 174, 191, 8, 2, 224, 174, 178, 224, 174, 176, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 3, 138, 34, 37, 49, 0, 224, 175, 141, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 149, 8, 2, 224, 174, 176, 3, 138, 34, 37, 79, 79, 107, 0, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 176, 224, 174, 191, 224, 174, 149, 8, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 176, 0, 224, 174, 191, 224, 174, 176, 8, 2, 224, 174, 184, 224, 175, 141, 224, 174, 159, 3, 138, 34, 107, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 134, 224, 174, 159, 224, 175, 141, 8, 3, 138, 34, 107, 63, 48, 36, 138, 0, 224, 175, 141, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 134, 224, 174, 159, 224, 175, 141, 8, 0, 4, 224, 174, 191, 224, 174, 176, 224, 175, 128, 224, 174, 159, 224, 175, 141, 8, 3, 138, 34, 110, 138, 0, 224, 175, 141, 224, 174, 176, 224, 175, 128, 224, 174, 159, 224, 175, 141, 8, 0, 224, 174, 191, 224, 174, 176, 224, 175, 135, 224, 174, 175, 224, 174, 191, 224, 174, 169, 8, 2, 224, 175, 136, 3, 138, 34, 112, 57, 50, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 8, 3, 138, 34, 116, 49, 0, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 1, 133, 174, 224, 0, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 8, 0, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 8, 2, 224, 174, 184, 224, 175, 141, 224, 174, 170, 224, 174, 176, 224, 174, 163, 224, 175, 141, 224, 174, 159, 12, 12, 12, 3, 138, 34, 116, 50, 0, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 176, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 3, 138, 34, 116, 50, 87, 48, 37, 34, 107, 64, 138, 147, 0, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 176, 224, 174, 163, 224, 175, 141, 224, 174, 159, 3, 138, 34, 116, 50, 87, 48, 107, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 176, 3, 138, 34, 116, 50, 87, 81, 107, 0, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 176, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 131, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 3, 138, 34, 116, 81, 37, 49, 0, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 0, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 131, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 0, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 0, 224, 175, 134, 224, 174, 149, 224, 175, 141, 8, 2, 224, 174, 169, 224, 174, 190, 224, 174, 178, 224, 174, 156, 224, 174, 191, 3, 138, 36, 49, 0, 224, 175, 134, 224, 174, 149, 224, 175, 141, 224, 174, 169, 224, 174, 191, 224, 174, 149, 8, 3, 138, 36, 49, 50, 37, 49, 147, 0, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 154, 8, 2, 224, 174, 169, 3, 138, 36, 50, 91, 107, 0, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 159, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 176, 3, 138, 36, 50, 138, 120, 55, 49, 107, 0, 224, 175, 134, 224, 174, 178, 224, 174, 191, 224, 174, 170, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 2, 224, 174, 176, 3, 138, 36, 55, 37, 48, 34, 37, 50, 138, 107, 0, 224, 175, 134, 224, 174, 178, 224, 174, 191, 224, 174, 170, 224, 174, 164, 8, 2, 224, 174, 191, 3, 138, 36, 55, 37, 48, 107, 47, 0, 224, 175, 134, 224, 174, 178, 224, 174, 191, 224, 174, 149, 224, 175, 128, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 3, 138, 36, 55, 37, 79, 0, 224, 175, 134, 224, 174, 178, 224, 174, 191, 224, 174, 170, 2, 224, 175, 139, 224, 174, 169, 3, 138, 36, 55, 37, 81, 0, 224, 175, 134, 224, 174, 178, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 175, 139, 224, 174, 170, 224, 175, 141, 8, 3, 138, 36, 55, 107, 87, 49, 117, 48, 0, 224, 175, 134, 224, 174, 174, 224, 175, 141, 224, 174, 170, 8, 2, 224, 175, 139, 3, 138, 36, 63, 48, 0, 224, 175, 134, 224, 174, 174, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 176, 3, 138, 36, 63, 48, 107, 0, 224, 175, 134, 224, 174, 184, 224, 175, 141, 224, 174, 159, 8, 3, 138, 36, 87, 138, 147, 0, 224, 174, 191, 224, 174, 149, 224, 175, 141, 1, 141, 175, 224, 176, 174, 224, 134, 174, 224, 3, 138, 37, 49, 0, 224, 174, 191, 224, 174, 169, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 159, 1, 141, 175, 224, 169, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 178, 3, 138, 37, 50, 36, 50, 138, 107, 0, 224, 174, 191, 224, 174, 169, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 1, 141, 175, 224, 163, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 178, 3, 138, 37, 50, 36, 64, 138, 107, 0, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 153, 224, 175, 141, 3, 138, 37, 50, 49, 107, 0, 224, 174, 191, 224, 174, 174, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 141, 175, 224, 163, 174, 224, 134, 175, 224, 154, 174, 224, 3, 138, 37, 63, 36, 64, 138, 147, 0, 224, 174, 191, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 135, 224, 174, 159, 8, 141, 175, 224, 176, 174, 224, 154, 174, 224, 3, 138, 37, 81, 37, 79, 112, 138, 147, 0, 224, 174, 191, 224, 174, 170, 8, 2, 224, 174, 169, 3, 138, 37, 81, 107, 0, 224, 174, 191, 224, 174, 159, 8, 2, 224, 175, 139, 3, 138, 37, 138, 0, 224, 175, 138, 224, 174, 149, 224, 175, 141, 8, 3, 138, 39, 49, 0, 224, 175, 129, 224, 174, 159, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 178, 3, 138, 40, 138, 0, 224, 175, 141, 224, 174, 178, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 1, 133, 174, 224, 3, 138, 55, 116, 64, 138, 147, 0, 4, 224, 175, 129, 224, 174, 181, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 176, 3, 138, 58, 0, 224, 175, 141, 224, 174, 181, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 4, 224, 174, 191, 224, 174, 181, 224, 174, 191, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 191, 224, 174, 179, 3, 138, 58, 37, 66, 49, 0, 224, 175, 129, 224, 174, 181, 224, 174, 191, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 191, 224, 174, 179, 0, 224, 175, 141, 224, 174, 181, 224, 174, 191, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 191, 224, 174, 179, 0, 224, 175, 141, 224, 174, 174, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 1, 141, 175, 224, 163, 174, 224, 191, 174, 224, 175, 174, 224, 190, 174, 224, 170, 174, 224, 141, 175, 224, 170, 174, 224, 133, 174, 224, 3, 138, 63, 36, 64, 138, 147, 0, 4, 1, 135, 175, 224, 159, 174, 224, 141, 175, 224, 184, 174, 224, 2, 224, 174, 184, 3, 138, 107, 0, 1, 141, 175, 224, 153, 174, 224, 2, 224, 174, 169, 0, 1, 141, 175, 224, 163, 174, 224, 129, 175, 224, 181, 174, 224, 149, 174, 224, 141, 175, 224, 169, 174, 224, 142, 174, 224, 2, 224, 174, 176, 0, 1, 141, 175, 224, 163, 174, 224, 135, 174, 224, 2, 224, 174, 176, 224, 175, 141, 0, 1, 141, 175, 224, 163, 174, 224, 140, 175, 224, 149, 174, 224, 141, 175, 224, 169, 174, 224, 142, 174, 224, 2, 224, 174, 176, 0, 1, 141, 175, 224, 178, 174, 224, 191, 174, 224, 170, 174, 224, 131, 174, 224, 2, 224, 174, 176, 0, 1, 141, 175, 224, 183, 174, 224, 0, 1, 141, 175, 224, 184, 174, 224, 0, 1, 191, 174, 224, 169, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 174, 131, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 169, 224, 174, 178, 0, 8, 2, 224, 174, 169, 224, 175, 141, 0, 8, 2, 224, 174, 170, 224, 175, 141, 32, 0, 8, 2, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 134, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 141, 224, 174, 178, 224, 174, 176, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 141, 224, 174, 179, 224, 174, 176, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 179, 224, 174, 176, 0, 8, 2, 224, 174, 175, 224, 174, 176, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 175, 224, 174, 176, 224, 175, 129, 0, 8, 2, 224, 174, 175, 224, 174, 176, 224, 175, 141, 0, 8, 2, 224, 174, 181, 224, 174, 176, 0, 8, 2, 224, 174, 181, 224, 174, 178, 0, 8, 2, 224, 174, 181, 224, 175, 129, 224, 174, 169, 0, 8, 130, 175, 224, 149, 174, 224, 141, 175, 224, 184, 174, 224, 2, 224, 174, 176, 0, 8, 130, 175, 224, 175, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 169, 0, 8, 141, 175, 224, 163, 174, 224, 134, 175, 224, 154, 174, 224, 2, 224, 174, 176, 0, 8, 141, 175, 224, 163, 174, 224, 134, 175, 224, 174, 174, 224, 2, 224, 174, 178, 0, 8, 141, 175, 224, 163, 174, 224, 191, 174, 224, 176, 174, 224, 141, 175, 224, 170, 174, 224, 2, 224, 174, 176, 0, 8, 141, 175, 224, 178, 174, 224, 134, 175, 224, 183, 174, 224, 2, 224, 174, 176, 0, 8, 141, 175, 224, 178, 174, 224, 191, 174, 224, 174, 174, 224, 2, 224, 174, 169, 0, 8, 178, 174, 224, 191, 174, 224, 174, 174, 224, 2, 224, 174, 176, 224, 174, 191, 0, 8, 191, 174, 224, 178, 174, 224, 191, 174, 224, 174, 174, 224, 2, 224, 174, 176, 224, 174, 191, 0, 224, 174, 176, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 141, 175, 224, 163, 174, 224, 142, 174, 224, 2, 224, 174, 176, 224, 175, 136, 18, 69, 3, 138, 107, 34, 48, 0, 224, 174, 176, 224, 175, 141, 224, 174, 170, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 2, 224, 175, 136, 224, 174, 169, 3, 138, 107, 34, 48, 107, 64, 138, 0, 224, 174, 170, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 191, 224, 174, 178, 3, 138, 107, 69, 69, 0, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 170, 224, 175, 141, 8, 3, 138, 107, 74, 12, 107, 48, 0, 224, 175, 135, 224, 174, 149, 224, 175, 141, 8, 3, 138, 112, 49, 0, 224, 175, 135, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 176, 3, 138, 112, 66, 49, 107, 0, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 1, 141, 175, 224, 163, 174, 224, 133, 174, 224, 3, 138, 116, 34, 138, 37, 49, 147, 0, 224, 174, 190, 224, 174, 170, 224, 175, 141, 8, 3, 138, 116, 48, 0, 224, 174, 190, 224, 174, 170, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 3, 138, 116, 48, 37, 49, 0, 4, 224, 174, 190, 224, 174, 149, 8, 2, 224, 175, 141, 224, 174, 184, 224, 174, 191, 3, 138, 116, 49, 0, 224, 174, 190, 224, 174, 149, 224, 175, 141, 8, 2, 32, 0, 224, 174, 190, 224, 174, 169, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 3, 138, 116, 50, 37, 49, 0, 224, 174, 190, 224, 174, 175, 224, 175, 141, 224, 174, 178, 224, 175, 134, 224, 174, 159, 224, 175, 141, 8, 3, 138, 116, 57, 55, 36, 138, 0, 224, 174, 190, 224, 174, 175, 224, 175, 141, 224, 174, 178, 224, 174, 159, 224, 175, 141, 8, 3, 138, 116, 57, 55, 107, 138, 0, 224, 174, 190, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 191, 3, 138, 116, 66, 49, 0, 224, 174, 190, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 176, 3, 138, 116, 66, 49, 107, 0, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 1, 141, 175, 224, 163, 174, 224, 134, 175, 224, 170, 174, 224, 3, 138, 116, 87, 138, 37, 49, 0, 224, 174, 190, 224, 174, 159, 8, 2, 224, 174, 190, 3, 138, 116, 138, 0, 224, 175, 139, 224, 174, 176, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 2, 224, 175, 139, 3, 138, 117, 34, 107, 64, 138, 0, 224, 175, 130, 224, 174, 164, 224, 175, 141, 8, 3, 138, 121, 47, 0, 224, 175, 136, 224, 174, 170, 224, 175, 141, 8, 3, 138, 132, 48, 0, 224, 175, 136, 224, 174, 159, 8, 2, 224, 174, 191, 224, 174, 178, 3, 138, 132, 138, 0, 224, 175, 141, 224, 174, 159, 2, 17, 66, 3, 138, 138, 0, 224, 175, 141, 224, 174, 159, 3, 138, 138, 107, 0, 4, 1, 135, 175, 224, 175, 174, 224, 191, 174, 224, 159, 174, 224, 128, 175, 224, 174, 174, 224, 141, 175, 224, 176, 174, 224, 159, 174, 224, 141, 175, 224, 163, 174, 224, 135, 174, 224, 3, 138, 147, 0, 1, 141, 175, 224, 163, 174, 224, 134, 175, 224, 156, 174, 224, 141, 175, 224, 176, 174, 224, 133, 174, 224, 0, 1, 141, 175, 224, 163, 174, 224, 134, 175, 224, 174, 174, 224, 128, 175, 224, 176, 174, 224, 141, 175, 224, 149, 174, 224, 133, 174, 224, 0, 1, 141, 175, 224, 163, 174, 224, 156, 174, 224, 141, 175, 224, 176, 174, 224, 133, 174, 224, 0, 1, 141, 175, 224, 163, 174, 224, 176, 174, 224, 134, 175, 224, 170, 174, 224, 141, 175, 224, 184, 174, 224, 141, 175, 224, 169, 174, 224, 0, 1, 141, 175, 224, 163, 174, 224, 176, 174, 224, 170, 174, 224, 141, 175, 224, 184, 174, 224, 141, 175, 224, 169, 174, 224, 0, 1, 141, 175, 224, 178, 174, 224, 190, 174, 224, 18, 69, 133, 174, 224, 0, 8, 135, 175, 224, 159, 174, 224, 0, 8, 141, 175, 224, 163, 174, 224, 134, 175, 224, 174, 174, 224, 149, 174, 224, 0, 8, 141, 175, 224, 163, 174, 224, 135, 175, 224, 170, 174, 224, 0, 8, 141, 175, 224, 163, 174, 224, 175, 174, 224, 136, 175, 224, 179, 174, 224, 141, 175, 224, 149, 174, 224, 0, 8, 141, 175, 224, 163, 174, 224, 183, 174, 224, 135, 175, 224, 170, 174, 224, 0, 8, 141, 175, 224, 170, 174, 224, 131, 174, 224, 191, 174, 224, 183, 174, 224, 0, 8, 141, 175, 224, 176, 174, 224, 139, 175, 224, 170, 174, 224, 141, 175, 224, 170, 174, 224, 191, 174, 224, 176, 174, 224, 0, 8, 141, 175, 224, 178, 174, 224, 139, 175, 224, 181, 174, 224, 0, 8, 141, 175, 224, 178, 174, 224, 190, 174, 224, 181, 174, 224, 0, 4, 2, 17, 66, 3, 139, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 176, 0, 8, 2, 224, 175, 128, 224, 174, 154, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 129, 224, 174, 178, 224, 174, 190, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 136, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 136, 224, 174, 181, 0, 224, 175, 130, 8, 32, 141, 175, 224, 184, 174, 224, 179, 174, 224, 141, 175, 224, 170, 174, 224, 0, 224, 175, 130, 8, 32, 141, 175, 224, 184, 174, 224, 179, 174, 224, 191, 174, 224, 170, 174, 224, 0, 224, 174, 191, 224, 174, 176, 8, 2, 224, 174, 184, 3, 139, 34, 36, 0, 224, 174, 191, 224, 174, 175, 224, 175, 130, 224, 174, 159, 8, 2, 224, 174, 191, 3, 139, 57, 150, 138, 0, 4, 3, 139, 107, 0, 8, 2, 224, 174, 181, 224, 175, 129, 224, 174, 169, 224, 175, 141, 224, 174, 178, 224, 175, 139, 224, 174, 159, 0, 224, 175, 128, 224, 174, 154, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 3, 139, 110, 87, 107, 64, 138, 147, 0, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 3, 139, 116, 49, 49, 120, 63, 36, 64, 138, 147, 0, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 159, 8, 2, 224, 174, 176, 3, 139, 116, 49, 138, 107, 0, 4, 224, 175, 141, 224, 174, 159, 1, 135, 174, 224, 2, 224, 174, 191, 224, 174, 178, 224, 174, 191, 3, 139, 139, 0, 224, 175, 141, 224, 174, 159, 8, 134, 175, 224, 176, 174, 224, 2, 224, 174, 191, 224, 174, 175, 224, 174, 190, 0, 224, 175, 141, 224, 174, 159, 8, 178, 174, 224, 3, 139, 139, 147, 0, 7, 6, 1, 36, 0, 2, 17, 66, 3, 64, 0, 3, 64, 107, 0, 7, 6, 1, 37, 0, 4, 1, 141, 175, 224, 149, 174, 224, 2, 17, 66, 3, 47, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 175, 135, 224, 174, 181, 224, 175, 136, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 175, 138, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 175, 136, 0, 1, 141, 175, 224, 168, 174, 224, 154, 174, 224, 190, 174, 224, 181, 174, 224, 2, 224, 174, 191, 0, 1, 141, 175, 224, 168, 174, 224, 175, 174, 224, 134, 175, 224, 156, 174, 224, 2, 224, 174, 191, 0, 1, 141, 175, 224, 170, 174, 224, 2, 17, 66, 0, 1, 141, 175, 224, 184, 174, 224, 2, 17, 66, 0, 1, 142, 174, 224, 2, 224, 174, 191, 224, 174, 175, 224, 175, 139, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 175, 0, 1, 154, 174, 224, 2, 224, 175, 141, 224, 174, 175, 0, 1, 154, 174, 224, 2, 224, 175, 141, 224, 174, 176, 224, 175, 129, 0, 1, 159, 174, 224, 141, 175, 224, 159, 174, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 1, 164, 174, 224, 2, 224, 175, 141, 224, 174, 176, 224, 175, 130, 224, 174, 170, 0, 1, 178, 174, 224, 174, 174, 224, 135, 175, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 190, 0, 1, 181, 174, 224, 190, 174, 224, 170, 174, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 191, 0, 1, 190, 174, 224, 156, 174, 224, 129, 175, 224, 154, 174, 224, 2, 224, 174, 190, 0, 1, 190, 174, 224, 170, 174, 224, 2, 224, 175, 141, 224, 174, 176, 224, 175, 130, 224, 174, 174, 0, 1, 191, 174, 224, 154, 174, 224, 2, 224, 175, 141, 224, 174, 176, 224, 174, 190, 0, 1, 191, 174, 224, 168, 174, 224, 2, 224, 175, 141, 224, 174, 175, 0, 1, 191, 174, 224, 169, 174, 224, 133, 174, 224, 2, 224, 174, 190, 0, 1, 191, 174, 224, 178, 174, 224, 178, 174, 224, 2, 224, 174, 190, 0, 1, 191, 174, 224, 181, 174, 224, 170, 174, 224, 2, 224, 175, 141, 224, 174, 176, 224, 174, 190, 0, 2, 224, 175, 129, 224, 174, 177, 224, 175, 136, 0, 2, 224, 175, 130, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 17, 66, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 154, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 191, 224, 174, 175, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 32, 224, 174, 174, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 32, 224, 174, 181, 224, 174, 190, 224, 174, 175, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 175, 129, 32, 224, 174, 174, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 175, 129, 0, 8, 2, 224, 175, 128, 224, 174, 170, 224, 175, 141, 224, 174, 170, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 139, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 174, 164, 224, 175, 141, 32, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 181, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 138, 224, 174, 159, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 174, 169, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 174, 178, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 136, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 175, 141, 32, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 168, 224, 175, 141, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 181, 0, 8, 2, 224, 175, 135, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 135, 224, 174, 154, 224, 175, 141, 224, 174, 154, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 176, 224, 174, 191, 224, 174, 159, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 176, 224, 175, 129, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 176, 224, 175, 136, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 176, 224, 175, 141, 32, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 178, 32, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 178, 224, 175, 135, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 178, 224, 175, 136, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 191, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 191, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 175, 136, 0, 8, 128, 175, 224, 149, 174, 224, 2, 224, 174, 190, 0, 8, 128, 175, 224, 154, 174, 224, 2, 224, 174, 190, 0, 8, 128, 175, 224, 170, 174, 224, 154, 174, 224, 2, 224, 174, 190, 0, 8, 135, 175, 224, 168, 174, 224, 2, 224, 174, 190, 224, 174, 156, 224, 174, 191, 0, 8, 141, 175, 224, 168, 174, 224, 149, 174, 224, 129, 175, 224, 154, 174, 224, 2, 224, 174, 191, 0, 8, 141, 175, 224, 168, 174, 224, 154, 174, 224, 181, 174, 224, 2, 224, 174, 191, 0, 8, 141, 175, 224, 168, 174, 224, 156, 174, 224, 174, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 168, 174, 224, 175, 174, 224, 141, 175, 224, 183, 174, 224, 129, 175, 224, 164, 174, 224, 2, 224, 174, 191, 0, 8, 141, 175, 224, 168, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 191, 0, 8, 141, 175, 224, 169, 174, 224, 190, 174, 224, 164, 174, 224, 2, 224, 175, 139, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 8, 141, 175, 224, 174, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 156, 0, 8, 141, 175, 224, 174, 174, 224, 174, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 178, 174, 224, 129, 175, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 169, 0, 8, 141, 175, 224, 178, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 169, 0, 8, 149, 174, 224, 2, 18, 73, 224, 174, 156, 224, 174, 190, 0, 8, 174, 174, 224, 129, 175, 224, 154, 174, 224, 2, 224, 174, 191, 0, 8, 174, 174, 224, 139, 175, 224, 149, 174, 224, 2, 224, 174, 191, 0, 8, 176, 174, 224, 190, 174, 224, 170, 174, 224, 32, 141, 175, 224, 176, 174, 224, 190, 174, 224, 154, 174, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 191, 0, 8, 176, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 175, 128, 0, 8, 178, 174, 224, 2, 224, 174, 190, 0, 8, 178, 174, 224, 170, 174, 224, 141, 175, 224, 183, 174, 224, 129, 175, 224, 170, 174, 224, 2, 224, 174, 190, 0, 8, 181, 174, 224, 135, 175, 224, 176, 174, 224, 2, 224, 174, 191, 0, 8, 181, 174, 224, 141, 175, 224, 176, 174, 224, 190, 174, 224, 170, 174, 224, 2, 224, 174, 191, 0, 8, 191, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 8, 191, 174, 224, 164, 174, 224, 135, 175, 224, 181, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 164, 174, 224, 135, 175, 224, 181, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 175, 136, 0, 8, 191, 174, 224, 169, 174, 224, 129, 175, 224, 154, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 169, 174, 224, 181, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 169, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 170, 174, 224, 154, 174, 224, 2, 224, 174, 190, 0, 8, 191, 174, 224, 176, 174, 224, 185, 174, 224, 2, 224, 174, 190, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 178, 224, 175, 139, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 178, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 181, 224, 175, 135, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 140, 224, 174, 170, 224, 174, 164, 224, 174, 191, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 163, 0, 224, 175, 141, 1, 135, 174, 224, 2, 224, 174, 175, 224, 174, 190, 224, 174, 164, 224, 174, 191, 0, 224, 175, 141, 1, 191, 174, 224, 164, 174, 224, 134, 174, 224, 2, 224, 174, 175, 0, 224, 175, 141, 2, 32, 224, 174, 164, 0, 224, 175, 141, 8, 130, 175, 224, 154, 174, 224, 174, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 176, 0, 224, 175, 141, 8, 134, 175, 224, 156, 174, 224, 2, 224, 174, 174, 224, 174, 178, 224, 174, 190, 224, 174, 169, 224, 174, 191, 0, 224, 175, 141, 8, 136, 175, 224, 174, 174, 224, 2, 224, 174, 176, 224, 175, 135, 224, 174, 175, 0, 224, 175, 141, 8, 190, 174, 224, 181, 174, 224, 2, 224, 174, 154, 224, 174, 178, 224, 175, 141, 224, 174, 175, 0, 224, 175, 141, 8, 191, 174, 224, 174, 174, 224, 2, 224, 174, 176, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 3, 47, 34, 37, 48, 0, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 170, 8, 2, 224, 175, 139, 224, 174, 178, 224, 174, 191, 0, 224, 175, 141, 224, 174, 176, 224, 174, 170, 224, 174, 164, 224, 174, 191, 1, 154, 174, 224, 3, 47, 34, 107, 48, 107, 47, 37, 0, 224, 175, 141, 224, 174, 176, 224, 174, 178, 224, 175, 135, 224, 174, 149, 8, 191, 174, 224, 154, 174, 224, 2, 224, 174, 190, 3, 47, 34, 107, 55, 112, 49, 0, 4, 224, 174, 191, 224, 174, 149, 8, 139, 175, 224, 156, 174, 224, 2, 224, 174, 190, 3, 47, 37, 49, 0, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 149, 174, 224, 0, 224, 174, 191, 224, 174, 175, 224, 175, 139, 224, 174, 170, 1, 142, 174, 224, 2, 224, 174, 191, 224, 174, 175, 3, 47, 37, 57, 117, 48, 0, 4, 224, 175, 141, 224, 174, 164, 1, 129, 175, 224, 170, 174, 224, 2, 224, 174, 191, 224, 174, 176, 3, 47, 47, 0, 224, 175, 141, 224, 174, 164, 2, 17, 66, 0, 224, 175, 141, 224, 174, 164, 8, 190, 174, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 175, 32, 0, 224, 175, 141, 224, 174, 164, 8, 190, 174, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 175, 224, 174, 191, 224, 174, 176, 224, 175, 129, 0, 224, 175, 141, 8, 191, 174, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 190, 3, 47, 47, 37, 0, 224, 175, 141, 224, 174, 164, 3, 47, 47, 107, 0, 224, 175, 141, 224, 174, 149, 1, 135, 175, 224, 170, 174, 224, 141, 175, 224, 174, 174, 224, 133, 174, 224, 3, 47, 49, 147, 0, 224, 175, 141, 224, 174, 164, 224, 175, 129, 8, 154, 174, 224, 135, 175, 224, 164, 174, 224, 2, 224, 174, 176, 224, 175, 139, 224, 174, 149, 224, 174, 191, 3, 47, 70, 0, 4, 1, 136, 175, 224, 179, 174, 224, 141, 175, 224, 179, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 169, 3, 47, 107, 0, 1, 141, 175, 224, 149, 174, 224, 0, 1, 141, 175, 224, 170, 174, 224, 0, 1, 141, 175, 224, 179, 174, 224, 190, 174, 224, 159, 174, 224, 141, 175, 224, 159, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 169, 0, 1, 141, 175, 224, 184, 174, 224, 0, 8, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 191, 224, 174, 159, 0, 8, 140, 175, 224, 149, 174, 224, 2, 224, 174, 174, 0, 8, 140, 175, 224, 149, 174, 224, 2, 224, 174, 174, 224, 174, 191, 0, 8, 141, 175, 224, 163, 174, 224, 174, 174, 224, 2, 224, 174, 176, 224, 175, 136, 0, 8, 141, 175, 224, 168, 174, 224, 190, 174, 224, 154, 174, 224, 2, 32, 0, 8, 141, 175, 224, 178, 174, 224, 129, 175, 224, 170, 174, 224, 2, 224, 174, 176, 224, 175, 136, 0, 8, 141, 175, 224, 178, 174, 224, 135, 175, 224, 174, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 178, 174, 224, 170, 174, 224, 2, 224, 174, 159, 0, 8, 141, 175, 224, 180, 174, 224, 128, 175, 224, 149, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 170, 174, 224, 2, 224, 174, 158, 224, 175, 141, 224, 174, 154, 224, 174, 178, 224, 174, 191, 0, 4, 8, 141, 175, 224, 168, 174, 224, 154, 174, 224, 181, 174, 224, 3, 47, 147, 0, 8, 141, 175, 224, 168, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 141, 175, 224, 168, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 174, 0, 8, 141, 175, 224, 168, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 178, 224, 174, 191, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 8, 141, 175, 224, 168, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 169, 224, 175, 129, 0, 4, 2, 17, 66, 3, 70, 0, 8, 2, 17, 66, 28, 17, 12, 0, 8, 2, 18, 73, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 154, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 163, 224, 175, 141, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 190, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 175, 129, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 174, 224, 175, 139, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 174, 224, 175, 141, 32, 224, 174, 164, 224, 175, 130, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 175, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 190, 224, 174, 175, 224, 174, 164, 224, 175, 141, 224, 174, 164, 12, 0, 8, 2, 224, 174, 190, 224, 174, 175, 224, 174, 174, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 175, 224, 174, 190, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 163, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 190, 32, 224, 174, 154, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 139, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 190, 32, 224, 174, 154, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 190, 32, 224, 174, 183, 224, 174, 191, 224, 174, 149, 224, 175, 139, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 190, 224, 174, 154, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 190, 224, 174, 170, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 190, 224, 174, 179, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 163, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 175, 135, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 184, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 134, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 135, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 181, 224, 174, 191, 224, 174, 156, 224, 174, 175, 0, 8, 2, 224, 174, 191, 224, 174, 154, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 174, 149, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 174, 154, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 174, 170, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 174, 174, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 128, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 128, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 159, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 129, 224, 174, 174, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 129, 224, 174, 181, 224, 175, 134, 0, 8, 2, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 181, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 174, 149, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 174, 154, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 174, 168, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 174, 174, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 129, 224, 174, 154, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 135, 224, 174, 183, 0, 8, 2, 224, 174, 191, 224, 174, 170, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 174, 224, 175, 141, 224, 174, 174, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 181, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 181, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 175, 140, 224, 174, 170, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 224, 174, 149, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 175, 129, 32, 0, 8, 2, 224, 174, 191, 224, 174, 181, 224, 174, 154, 0, 8, 2, 224, 174, 191, 224, 174, 181, 224, 174, 190, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 181, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 181, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 181, 224, 175, 141, 224, 174, 175, 0, 8, 2, 224, 174, 191, 224, 174, 181, 224, 175, 141, 224, 174, 181, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 128, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 174, 191, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 163, 224, 175, 141, 224, 174, 175, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 164, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 175, 136, 0, 8, 2, 224, 175, 128, 224, 174, 170, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 180, 224, 174, 181, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 154, 224, 175, 141, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 159, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 169, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 174, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 174, 224, 175, 129, 224, 174, 159, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 191, 224, 174, 149, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 176, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 176, 224, 175, 136, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 174, 224, 174, 190, 0, 8, 2, 224, 175, 128, 224, 174, 181, 224, 174, 190, 224, 174, 179, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 129, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 174, 0, 8, 2, 224, 175, 129, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 190, 224, 174, 164, 224, 174, 169, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 156, 224, 174, 184, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 129, 224, 174, 170, 224, 174, 190, 224, 174, 175, 0, 8, 2, 224, 175, 129, 224, 174, 170, 224, 174, 190, 224, 174, 183, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 174, 224, 174, 179, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 175, 141, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 174, 164, 224, 174, 191, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 174, 190, 224, 174, 154, 224, 175, 136, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 175, 139, 224, 174, 164, 224, 174, 169, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 175, 139, 224, 174, 164, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 181, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 136, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 139, 224, 174, 163, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 183, 224, 175, 141, 0, 8, 2, 224, 175, 130, 224, 174, 154, 0, 8, 2, 224, 175, 130, 224, 174, 154, 224, 174, 191, 0, 8, 2, 224, 175, 130, 224, 174, 170, 0, 8, 2, 224, 175, 130, 224, 174, 174, 0, 8, 2, 224, 175, 130, 224, 174, 176, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 174, 176, 224, 175, 141, 224, 174, 183, 224, 174, 169, 0, 8, 2, 224, 175, 130, 224, 174, 183, 0, 8, 2, 224, 175, 130, 224, 174, 183, 224, 174, 163, 224, 175, 136, 0, 8, 2, 224, 175, 130, 224, 174, 183, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 181, 0, 8, 2, 224, 175, 135, 224, 174, 149, 0, 8, 2, 224, 175, 135, 224, 174, 154, 0, 8, 2, 224, 175, 135, 224, 174, 181, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 174, 178, 224, 174, 190, 224, 174, 174, 0, 8, 2, 224, 175, 135, 224, 174, 181, 224, 175, 135, 224, 174, 168, 224, 175, 141, 0, 8, 2, 224, 175, 136, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 138, 224, 174, 169, 224, 174, 191, 0, 8, 2, 224, 175, 138, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 175, 136, 0, 8, 2, 224, 175, 138, 224, 174, 170, 224, 174, 164, 224, 175, 138, 224, 174, 170, 0, 8, 2, 224, 175, 138, 224, 174, 170, 224, 175, 129, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 175, 138, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 224, 174, 169, 0, 8, 2, 224, 175, 138, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 134, 0, 8, 2, 224, 175, 138, 224, 174, 174, 224, 175, 141, 0, 8, 2, 224, 175, 138, 224, 174, 179, 224, 174, 164, 224, 175, 138, 224, 174, 179, 0, 8, 2, 224, 175, 138, 224, 174, 179, 224, 174, 181, 224, 175, 134, 0, 8, 2, 224, 175, 139, 224, 174, 154, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 183, 0, 8, 2, 224, 175, 139, 224, 174, 184, 224, 175, 141, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 185, 224, 174, 190, 0, 8, 2, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 159, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 149, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 168, 224, 175, 141, 224, 174, 164, 32, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 175, 135, 224, 174, 154, 0, 224, 175, 129, 8, 2, 224, 174, 181, 224, 175, 135, 224, 174, 183, 0, 224, 175, 141, 224, 174, 164, 224, 175, 129, 1, 133, 174, 224, 2, 224, 174, 181, 224, 174, 190, 224, 174, 169, 0, 224, 175, 141, 224, 174, 164, 224, 175, 129, 1, 191, 174, 224, 181, 174, 224, 2, 224, 174, 181, 224, 174, 190, 224, 174, 169, 0, 224, 175, 141, 224, 174, 164, 224, 175, 129, 8, 191, 174, 224, 176, 174, 224, 185, 174, 224, 2, 224, 174, 181, 224, 174, 190, 224, 174, 176, 0, 4, 224, 174, 191, 224, 174, 176, 224, 175, 129, 8, 2, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 190, 3, 70, 34, 37, 0, 224, 174, 191, 224, 174, 176, 224, 175, 129, 8, 2, 224, 174, 183, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 224, 174, 191, 224, 174, 178, 224, 174, 191, 224, 174, 170, 224, 175, 141, 8, 3, 70, 37, 55, 37, 48, 0, 224, 174, 191, 224, 174, 178, 224, 175, 128, 224, 174, 170, 224, 175, 141, 8, 3, 70, 37, 55, 110, 48, 0, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 175, 136, 3, 70, 37, 79, 69, 0, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 175, 224, 175, 134, 3, 70, 37, 79, 70, 0, 224, 174, 191, 224, 174, 159, 224, 174, 154, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 178, 224, 175, 141, 224, 174, 170, 8, 3, 70, 37, 139, 107, 87, 107, 66, 79, 107, 55, 48, 147, 0, 4, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 174, 191, 224, 174, 154, 224, 175, 136, 3, 70, 70, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 174, 191, 224, 174, 169, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 175, 129, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 175, 130, 224, 174, 154, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 175, 130, 224, 174, 176, 224, 174, 164, 224, 175, 141, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 175, 130, 224, 174, 176, 224, 174, 174, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 181, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 175, 135, 224, 174, 154, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 175, 135, 224, 174, 181, 224, 174, 164, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 175, 135, 224, 174, 181, 224, 174, 169, 0, 224, 175, 141, 224, 174, 164, 1, 18, 68, 2, 224, 175, 135, 224, 174, 181, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 1, 129, 175, 224, 159, 174, 224, 141, 175, 224, 159, 174, 224, 142, 174, 224, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 175, 141, 224, 174, 164, 1, 129, 175, 224, 170, 174, 224, 2, 224, 174, 191, 0, 224, 175, 141, 224, 174, 164, 1, 129, 175, 224, 170, 174, 224, 2, 224, 174, 191, 224, 174, 175, 224, 174, 191, 0, 224, 175, 141, 224, 174, 164, 1, 129, 175, 224, 174, 174, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 1, 133, 174, 224, 2, 224, 174, 190, 224, 174, 154, 224, 174, 191, 0, 224, 175, 141, 224, 174, 164, 1, 133, 174, 224, 2, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 181, 0, 224, 175, 141, 224, 174, 164, 1, 136, 175, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 164, 1, 137, 174, 224, 2, 224, 174, 191, 224, 174, 175, 224, 175, 139, 224, 174, 149, 0, 224, 175, 141, 224, 174, 164, 1, 137, 174, 224, 2, 224, 175, 135, 224, 174, 154, 0, 224, 175, 141, 224, 174, 164, 1, 139, 175, 224, 175, 174, 224, 133, 174, 224, 2, 224, 174, 191, 0, 224, 175, 141, 224, 174, 164, 1, 141, 175, 224, 176, 174, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 191, 0, 224, 175, 141, 224, 174, 164, 1, 174, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 164, 1, 178, 174, 224, 129, 175, 224, 149, 174, 224, 2, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 181, 0, 224, 175, 141, 224, 174, 164, 1, 178, 174, 224, 170, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 153, 224, 175, 141, 0, 224, 175, 141, 224, 174, 164, 1, 178, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 153, 224, 175, 141, 0, 224, 175, 141, 224, 174, 164, 1, 190, 174, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 164, 1, 190, 174, 224, 170, 174, 224, 137, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 164, 1, 190, 174, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 164, 1, 191, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 0, 224, 175, 141, 224, 174, 164, 1, 191, 174, 224, 181, 174, 224, 2, 224, 175, 136, 224, 174, 175, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 164, 1, 191, 174, 224, 181, 174, 224, 2, 224, 175, 136, 224, 174, 175, 224, 174, 190, 224, 174, 178, 224, 175, 141, 32, 0, 224, 175, 141, 224, 174, 164, 1, 191, 174, 224, 181, 174, 224, 2, 224, 175, 136, 224, 174, 175, 224, 174, 191, 0, 224, 175, 141, 224, 174, 164, 1, 191, 174, 224, 181, 174, 224, 2, 224, 175, 136, 224, 174, 175, 224, 175, 136, 0, 224, 175, 141, 224, 174, 164, 8, 129, 175, 224, 176, 174, 224, 2, 224, 174, 191, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 8, 130, 175, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 191, 0, 224, 175, 141, 224, 174, 164, 8, 130, 175, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 174, 169, 0, 224, 175, 141, 224, 174, 164, 8, 130, 175, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 174, 176, 224, 174, 191, 0, 224, 175, 141, 224, 174, 164, 8, 130, 175, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 174, 176, 224, 175, 141, 0, 224, 175, 141, 224, 174, 164, 8, 135, 175, 224, 181, 174, 224, 136, 175, 224, 168, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 164, 8, 136, 175, 224, 181, 174, 224, 2, 224, 174, 191, 32, 0, 224, 175, 141, 224, 174, 164, 8, 136, 175, 224, 181, 174, 224, 2, 224, 175, 128, 224, 174, 184, 224, 175, 141, 224, 174, 181, 0, 224, 175, 141, 224, 174, 164, 8, 140, 175, 224, 176, 174, 224, 2, 224, 174, 191, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 8, 170, 174, 224, 129, 175, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 8, 170, 174, 224, 137, 174, 224, 2, 224, 174, 191, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 8, 174, 174, 224, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 224, 175, 141, 224, 174, 164, 8, 191, 174, 224, 181, 174, 224, 2, 224, 175, 136, 224, 174, 149, 224, 174, 179, 0, 224, 175, 141, 224, 174, 164, 8, 191, 174, 224, 181, 174, 224, 2, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 164, 8, 191, 174, 224, 181, 174, 224, 2, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 224, 175, 141, 224, 174, 164, 8, 191, 174, 224, 181, 174, 224, 32, 141, 175, 224, 178, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 175, 136, 0, 224, 175, 141, 224, 174, 164, 8, 191, 174, 224, 181, 174, 224, 141, 175, 224, 178, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 175, 136, 0, 224, 175, 141, 224, 174, 164, 224, 174, 191, 1, 191, 174, 224, 164, 174, 224, 134, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 159, 0, 224, 175, 141, 224, 174, 164, 224, 175, 129, 1, 18, 68, 2, 224, 174, 181, 224, 174, 190, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 224, 175, 129, 1, 156, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 176, 224, 175, 139, 224, 174, 149, 0, 224, 175, 141, 224, 174, 164, 224, 175, 129, 8, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 181, 224, 174, 190, 224, 174, 176, 0, 4, 224, 175, 141, 224, 174, 164, 1, 129, 175, 224, 170, 174, 224, 2, 224, 174, 169, 3, 70, 70, 107, 0, 224, 175, 141, 224, 174, 164, 1, 129, 175, 224, 170, 174, 224, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 1, 141, 175, 224, 176, 174, 224, 133, 174, 224, 2, 18, 74, 224, 174, 190, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 8, 129, 175, 224, 159, 174, 224, 141, 175, 224, 159, 174, 224, 176, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 224, 175, 141, 224, 174, 164, 8, 129, 175, 224, 159, 174, 224, 141, 175, 224, 159, 174, 224, 176, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 176, 0, 224, 175, 141, 224, 174, 164, 8, 136, 175, 224, 177, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 169, 224, 175, 136, 0, 224, 175, 141, 224, 174, 164, 8, 141, 175, 224, 176, 174, 224, 181, 174, 224, 2, 224, 174, 174, 224, 174, 190, 224, 174, 169, 0, 224, 175, 141, 224, 174, 164, 224, 174, 176, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 1, 141, 175, 224, 176, 174, 224, 133, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 3, 70, 70, 107, 34, 116, 70, 70, 0, 224, 175, 141, 224, 174, 164, 224, 175, 128, 224, 174, 154, 224, 175, 129, 8, 136, 175, 224, 181, 174, 224, 2, 224, 174, 181, 3, 70, 70, 110, 87, 0, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 8, 191, 174, 224, 154, 174, 224, 3, 70, 70, 116, 50, 47, 147, 0, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 154, 8, 129, 175, 224, 176, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 178, 3, 70, 70, 116, 74, 107, 0, 4, 224, 175, 141, 224, 174, 164, 1, 129, 175, 224, 175, 174, 224, 3, 70, 70, 147, 0, 224, 175, 141, 224, 174, 164, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 176, 174, 224, 141, 175, 224, 184, 174, 224, 0, 224, 175, 141, 224, 174, 164, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 176, 174, 224, 191, 174, 224, 154, 174, 224, 0, 4, 224, 175, 129, 224, 174, 181, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 154, 224, 174, 191, 3, 70, 82, 0, 224, 175, 129, 224, 174, 181, 8, 2, 224, 174, 190, 224, 174, 176, 0, 224, 175, 129, 224, 174, 181, 8, 2, 224, 175, 136, 224, 174, 164, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 224, 175, 129, 224, 174, 181, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 176, 3, 70, 82, 116, 48, 107, 0, 4, 224, 175, 129, 224, 174, 181, 224, 175, 136, 224, 174, 164, 8, 2, 32, 3, 70, 82, 132, 47, 107, 0, 224, 175, 129, 224, 174, 181, 224, 175, 136, 224, 174, 164, 8, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 178, 0, 224, 175, 129, 224, 174, 181, 224, 175, 136, 224, 174, 164, 8, 2, 224, 174, 174, 0, 4, 3, 70, 107, 0, 8, 2, 18, 69, 224, 174, 190, 0, 8, 2, 28, 17, 0, 8, 2, 224, 174, 149, 224, 174, 164, 224, 174, 149, 0, 8, 2, 224, 174, 149, 224, 174, 169, 0, 8, 2, 224, 174, 149, 224, 174, 191, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 174, 191, 224, 174, 163, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 174, 191, 224, 174, 163, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 174, 191, 224, 174, 163, 224, 174, 190, 0, 8, 2, 224, 174, 154, 224, 174, 149, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 174, 154, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 174, 154, 224, 174, 176, 224, 174, 164, 0, 8, 2, 224, 174, 154, 224, 174, 176, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 174, 154, 224, 174, 176, 224, 174, 190, 0, 8, 2, 224, 174, 154, 224, 174, 190, 224, 174, 170, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 154, 224, 175, 136, 0, 8, 2, 224, 174, 159, 224, 174, 164, 224, 174, 159, 0, 8, 2, 224, 174, 159, 224, 174, 170, 224, 175, 129, 224, 174, 159, 224, 174, 178, 0, 8, 2, 224, 174, 159, 224, 174, 181, 224, 175, 134, 0, 8, 2, 224, 174, 159, 224, 174, 181, 224, 175, 136, 0, 8, 2, 224, 174, 159, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 159, 224, 174, 191, 23, 32, 224, 174, 170, 224, 174, 175, 224, 174, 178, 0, 8, 2, 224, 174, 159, 224, 174, 191, 23, 32, 224, 174, 170, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 149, 0, 8, 2, 224, 174, 159, 224, 174, 191, 23, 32, 224, 174, 174, 224, 174, 190, 224, 174, 159, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 174, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 174, 224, 174, 169, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 174, 224, 174, 190, 224, 174, 159, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 176, 0, 8, 2, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 154, 224, 175, 128, 224, 174, 178, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 169, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 163, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 169, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 170, 224, 174, 190, 224, 174, 163, 224, 174, 191, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 174, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 175, 224, 175, 129, 224, 174, 164, 224, 174, 170, 224, 174, 190, 224, 174, 163, 224, 174, 191, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 190, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 175, 129, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 128, 224, 174, 184, 224, 175, 141, 224, 174, 181, 224, 174, 176, 0, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 139, 224, 174, 176, 224, 174, 190, 0, 8, 2, 224, 174, 169, 224, 174, 149, 224, 175, 139, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 169, 224, 174, 154, 224, 175, 135, 224, 174, 149, 224, 174, 176, 224, 174, 169, 0, 8, 2, 224, 174, 169, 224, 174, 169, 224, 175, 141, 224, 174, 156, 224, 175, 134, 224, 174, 175, 224, 174, 169, 0, 8, 2, 224, 174, 169, 224, 174, 170, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 169, 224, 174, 176, 224, 174, 190, 224, 174, 154, 0, 8, 2, 224, 174, 169, 224, 174, 176, 224, 174, 190, 224, 174, 156, 0, 8, 2, 224, 174, 169, 224, 174, 178, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 175, 141, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 174, 169, 224, 174, 178, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 175, 129, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 174, 169, 224, 174, 181, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 169, 224, 175, 129, 224, 174, 154, 0, 8, 2, 224, 174, 169, 224, 175, 129, 224, 174, 183, 0, 8, 2, 224, 174, 169, 224, 175, 141, 224, 174, 174, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 174, 169, 224, 175, 141, 224, 174, 176, 224, 174, 190, 224, 174, 156, 0, 8, 2, 224, 174, 169, 224, 175, 141, 224, 174, 181, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 174, 174, 224, 174, 175, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 159, 224, 174, 191, 18, 76, 224, 175, 141, 0, 8, 2, 224, 174, 175, 224, 174, 181, 0, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 163, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 179, 0, 8, 2, 224, 174, 175, 224, 175, 136, 0, 8, 2, 224, 174, 176, 224, 174, 163, 224, 174, 191, 0, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 154, 224, 174, 169, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 154, 224, 174, 169, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 154, 224, 174, 191, 0, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 174, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 154, 224, 175, 135, 224, 174, 169, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 154, 224, 175, 141, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 169, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 170, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 174, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 176, 0, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 174, 190, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 170, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 170, 224, 175, 130, 224, 174, 154, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 170, 224, 175, 136, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 136, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 174, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 181, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 181, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 139, 224, 174, 178, 0, 8, 2, 224, 174, 181, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 181, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 181, 224, 174, 174, 0, 8, 141, 175, 224, 170, 174, 224, 154, 174, 224, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 141, 175, 224, 170, 174, 224, 154, 174, 224, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 141, 175, 224, 170, 174, 224, 154, 174, 224, 2, 224, 174, 174, 0, 4, 224, 174, 176, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 176, 32, 3, 70, 107, 34, 37, 70, 70, 0, 224, 174, 176, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 224, 174, 176, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 174, 224, 175, 141, 0, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 178, 3, 70, 107, 34, 40, 63, 107, 69, 0, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 170, 8, 2, 224, 175, 129, 224, 174, 176, 224, 174, 191, 3, 70, 107, 34, 120, 63, 107, 48, 0, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 128, 224, 174, 154, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 176, 3, 70, 107, 64, 139, 110, 87, 0, 224, 174, 170, 224, 174, 164, 224, 174, 170, 8, 3, 70, 107, 69, 107, 70, 107, 69, 147, 0, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 175, 224, 174, 190, 3, 70, 107, 70, 70, 0, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 190, 3, 70, 107, 79, 79, 0, 224, 174, 181, 224, 175, 129, 224, 174, 178, 224, 174, 164, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 164, 3, 70, 107, 82, 120, 55, 107, 70, 116, 69, 0, 4, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 164, 224, 174, 176, 224, 174, 191, 224, 174, 154, 3, 70, 110, 34, 79, 79, 107, 0, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 174, 224, 174, 191, 0, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 174, 224, 175, 141, 32, 0, 4, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 159, 224, 174, 169, 3, 70, 110, 34, 79, 79, 147, 0, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 174, 224, 175, 129, 224, 174, 179, 224, 175, 141, 224, 174, 179, 0, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 190, 224, 174, 175, 224, 175, 129, 0, 224, 175, 140, 224, 174, 178, 224, 174, 164, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 164, 3, 70, 133, 55, 107, 139, 116, 69, 0, 8, 141, 175, 224, 170, 174, 224, 154, 174, 224, 191, 174, 224, 168, 174, 224, 3, 70, 147, 0, 7, 6, 1, 41, 0, 4, 2, 17, 66, 3, 50, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 175, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 175, 130, 0, 3, 50, 107, 0, 7, 6, 1, 42, 0, 2, 17, 66, 3, 50, 0, 3, 50, 107, 0, 7, 6, 1, 43, 0, 8, 141, 175, 224, 170, 174, 224, 141, 175, 224, 180, 174, 224, 191, 174, 224, 174, 174, 224, 164, 174, 224, 2, 224, 174, 190, 224, 174, 183, 3, 10, 69, 0, 4, 1, 21, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 3, 48, 0, 1, 21, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 168, 224, 174, 190, 224, 174, 178, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 0, 1, 21, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 176, 224, 175, 141, 32, 0, 1, 21, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 190, 224, 174, 178, 224, 175, 141, 32, 0, 1, 128, 175, 224, 169, 174, 224, 2, 224, 174, 190, 0, 1, 128, 175, 224, 176, 174, 224, 2, 224, 174, 190, 0, 1, 129, 175, 224, 159, 174, 224, 136, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 1, 129, 175, 224, 159, 174, 224, 141, 175, 224, 163, 174, 224, 149, 174, 224, 2, 224, 174, 191, 224, 174, 159, 224, 174, 191, 0, 1, 129, 175, 224, 164, 174, 224, 129, 175, 224, 180, 174, 224, 138, 175, 224, 170, 174, 224, 2, 224, 175, 139, 224, 174, 149, 224, 175, 141, 0, 1, 129, 175, 224, 175, 174, 224, 190, 174, 224, 181, 174, 224, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 1, 129, 175, 224, 176, 174, 224, 135, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 1, 129, 175, 224, 176, 174, 224, 146, 174, 224, 2, 224, 174, 190, 224, 174, 164, 0, 1, 129, 175, 224, 176, 174, 224, 146, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 1, 129, 175, 224, 176, 174, 224, 146, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 175, 141, 224, 174, 154, 0, 1, 129, 175, 224, 177, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 179, 224, 175, 141, 224, 174, 179, 224, 175, 136, 0, 1, 133, 174, 224, 2, 224, 174, 190, 224, 174, 169, 0, 1, 136, 175, 224, 159, 174, 224, 142, 174, 224, 2, 224, 175, 139, 224, 174, 159, 0, 1, 136, 175, 224, 178, 174, 224, 133, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 174, 191, 0, 1, 136, 175, 224, 178, 174, 224, 138, 175, 224, 164, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 174, 191, 0, 1, 137, 174, 224, 2, 224, 174, 190, 224, 174, 154, 224, 174, 169, 224, 175, 136, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 175, 141, 224, 174, 154, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 0, 1, 141, 175, 224, 163, 174, 224, 134, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 1, 141, 175, 224, 163, 174, 224, 134, 174, 224, 2, 224, 174, 191, 224, 174, 179, 224, 175, 141, 224, 174, 179, 224, 175, 136, 0, 1, 141, 175, 224, 163, 174, 224, 134, 175, 224, 170, 174, 224, 2, 224, 174, 191, 224, 174, 179, 224, 175, 141, 224, 174, 179, 224, 175, 136, 0, 1, 141, 175, 224, 163, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 181, 224, 175, 136, 0, 1, 141, 175, 224, 163, 174, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 180, 224, 175, 129, 0, 1, 141, 175, 224, 169, 174, 224, 159, 174, 224, 137, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 1, 141, 175, 224, 169, 174, 224, 159, 174, 224, 137, 174, 224, 2, 224, 174, 191, 224, 174, 177, 0, 1, 141, 175, 224, 169, 174, 224, 164, 174, 224, 18, 68, 2, 224, 174, 190, 224, 174, 178, 0, 1, 141, 175, 224, 169, 174, 224, 174, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 1, 141, 175, 224, 169, 174, 224, 176, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 1, 141, 175, 224, 170, 174, 224, 2, 17, 66, 0, 1, 141, 175, 224, 174, 174, 224, 133, 174, 224, 2, 224, 175, 136, 224, 174, 175, 224, 174, 176, 0, 1, 141, 175, 224, 174, 174, 224, 135, 174, 224, 2, 224, 175, 128, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 178, 0, 1, 141, 175, 224, 174, 174, 224, 135, 174, 224, 2, 224, 175, 139, 224, 174, 154, 224, 174, 191, 224, 174, 183, 224, 174, 169, 0, 1, 141, 175, 224, 174, 174, 224, 142, 174, 224, 2, 224, 175, 139, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 178, 0, 1, 141, 175, 224, 174, 174, 224, 143, 174, 224, 2, 224, 174, 190, 32, 0, 1, 141, 175, 224, 174, 174, 224, 159, 174, 224, 135, 174, 224, 2, 224, 175, 134, 224, 174, 175, 224, 174, 176, 0, 1, 141, 175, 224, 174, 174, 224, 179, 174, 224, 135, 174, 224, 2, 224, 175, 134, 224, 174, 163, 224, 175, 141, 0, 1, 141, 175, 224, 174, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 175, 130, 224, 174, 176, 0, 1, 141, 175, 224, 175, 174, 224, 135, 175, 224, 164, 174, 224, 2, 224, 174, 191, 224, 174, 177, 224, 175, 136, 0, 1, 141, 175, 224, 176, 174, 224, 179, 174, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 177, 224, 175, 136, 0, 1, 141, 175, 224, 176, 174, 224, 191, 174, 224, 164, 174, 224, 142, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 1, 141, 175, 224, 176, 174, 224, 191, 174, 224, 174, 174, 224, 191, 174, 224, 164, 174, 224, 2, 224, 174, 191, 224, 174, 159, 224, 174, 191, 0, 1, 141, 175, 224, 178, 174, 224, 181, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 1, 141, 175, 224, 179, 174, 224, 134, 174, 224, 2, 224, 174, 191, 224, 174, 159, 224, 174, 191, 0, 1, 141, 175, 224, 184, 174, 224, 141, 175, 224, 169, 174, 224, 135, 174, 224, 2, 224, 175, 134, 224, 174, 149, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 1, 146, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 1, 149, 174, 224, 2, 224, 174, 190, 0, 1, 154, 174, 224, 141, 175, 224, 158, 174, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 1, 156, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 1, 159, 174, 224, 133, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 159, 174, 224, 141, 175, 224, 163, 174, 224, 164, 174, 224, 2, 224, 174, 190, 224, 174, 163, 224, 174, 191, 0, 1, 164, 174, 224, 2, 224, 174, 190, 0, 1, 170, 174, 224, 137, 174, 224, 2, 224, 175, 128, 224, 174, 159, 0, 1, 174, 174, 224, 2, 224, 174, 190, 0, 1, 174, 174, 224, 2, 224, 174, 190, 0, 1, 190, 174, 224, 149, 174, 224, 2, 224, 174, 190, 0, 1, 190, 174, 224, 154, 174, 224, 2, 224, 174, 190, 0, 1, 190, 174, 224, 164, 174, 224, 2, 224, 174, 190, 0, 1, 190, 174, 224, 164, 174, 224, 190, 174, 224, 181, 174, 224, 2, 224, 174, 191, 0, 1, 190, 174, 224, 174, 174, 224, 2, 224, 174, 190, 0, 1, 191, 174, 224, 18, 75, 146, 174, 224, 2, 224, 175, 134, 0, 1, 191, 174, 224, 149, 174, 224, 141, 175, 224, 149, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 175, 128, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 174, 190, 0, 1, 191, 174, 224, 159, 174, 224, 133, 174, 224, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 0, 1, 191, 174, 224, 159, 174, 224, 135, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 1, 191, 174, 224, 169, 174, 224, 2, 224, 174, 190, 0, 1, 191, 174, 224, 169, 174, 224, 141, 175, 224, 149, 174, 224, 133, 174, 224, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 1, 191, 174, 224, 169, 174, 224, 191, 174, 224, 149, 174, 224, 141, 175, 224, 149, 174, 224, 133, 174, 224, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 1, 191, 174, 224, 178, 174, 224, 141, 175, 224, 178, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 130, 224, 174, 176, 0, 1, 191, 174, 224, 178, 174, 224, 159, 174, 224, 190, 174, 224, 170, 174, 224, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 1, 191, 174, 224, 180, 174, 224, 138, 175, 224, 174, 174, 224, 2, 224, 175, 134, 224, 174, 175, 224, 174, 176, 224, 175, 141, 0, 2, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 2, 224, 174, 190, 224, 174, 179, 224, 175, 136, 224, 174, 175, 0, 2, 224, 174, 191, 224, 174, 177, 224, 174, 149, 224, 175, 129, 12, 0, 2, 224, 174, 191, 224, 174, 179, 224, 175, 141, 224, 174, 179, 224, 175, 136, 0, 2, 224, 175, 129, 224, 174, 176, 0, 2, 224, 175, 129, 224, 174, 177, 25, 0, 2, 224, 175, 130, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 191, 0, 2, 224, 175, 130, 224, 174, 176, 0, 2, 224, 175, 134, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 169, 0, 2, 224, 175, 134, 224, 174, 177, 0, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 136, 0, 2, 224, 175, 135, 224, 174, 176, 224, 174, 191, 224, 174, 178, 224, 175, 141, 32, 0, 2, 224, 175, 135, 224, 174, 176, 224, 175, 141, 32, 0, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 178, 224, 174, 190, 32, 12, 0, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 178, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 12, 0, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 178, 224, 175, 141, 32, 12, 0, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 224, 174, 174, 224, 174, 178, 224, 175, 141, 32, 12, 0, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 175, 129, 32, 12, 0, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 175, 135, 32, 12, 0, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 12, 0, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 175, 135, 32, 12, 0, 2, 224, 175, 138, 224, 174, 180, 224, 175, 129, 224, 174, 164, 224, 175, 139, 32, 12, 0, 2, 224, 175, 139, 224, 174, 149, 32, 0, 2, 224, 175, 139, 224, 174, 149, 224, 174, 181, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 175, 136, 32, 0, 2, 224, 175, 139, 224, 174, 149, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 2, 224, 175, 139, 224, 174, 149, 224, 174, 191, 224, 174, 177, 0, 2, 224, 175, 139, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 0, 2, 224, 175, 139, 224, 174, 164, 224, 174, 191, 224, 174, 178, 224, 175, 129, 224, 174, 174, 224, 175, 135, 32, 12, 0, 2, 224, 175, 139, 224, 174, 164, 224, 174, 191, 224, 174, 178, 224, 175, 129, 224, 174, 174, 224, 175, 141, 12, 0, 2, 224, 175, 139, 224, 174, 164, 224, 175, 129, 12, 0, 2, 224, 175, 139, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 175, 141, 12, 0, 2, 224, 175, 139, 224, 174, 164, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 12, 0, 2, 224, 175, 139, 224, 174, 164, 224, 175, 134, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 224, 174, 174, 224, 175, 141, 32, 0, 2, 224, 175, 139, 224, 174, 164, 224, 175, 135, 32, 12, 0, 2, 224, 175, 139, 224, 174, 164, 224, 175, 139, 32, 12, 0, 2, 224, 175, 139, 224, 174, 169, 32, 0, 2, 224, 175, 139, 224, 174, 169, 224, 174, 190, 0, 2, 224, 175, 139, 224, 174, 169, 224, 175, 141, 224, 174, 177, 12, 0, 2, 224, 175, 139, 224, 174, 175, 224, 174, 191, 224, 174, 176, 224, 175, 129, 0, 2, 224, 175, 139, 224, 174, 175, 224, 175, 141, 0, 2, 224, 175, 139, 224, 174, 178, 32, 0, 2, 224, 175, 139, 224, 174, 178, 224, 174, 149, 224, 175, 141, 32, 0, 2, 224, 175, 139, 224, 174, 178, 224, 174, 154, 224, 175, 141, 32, 0, 2, 224, 175, 139, 224, 174, 178, 224, 174, 164, 224, 175, 141, 32, 0, 2, 224, 175, 139, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 169, 224, 175, 141, 32, 12, 0, 2, 224, 175, 139, 224, 174, 178, 224, 174, 170, 224, 175, 141, 32, 0, 2, 224, 175, 139, 224, 174, 178, 224, 174, 181, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 0, 2, 224, 175, 139, 224, 174, 178, 224, 174, 181, 224, 175, 135, 32, 0, 2, 224, 175, 139, 224, 174, 178, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 0, 2, 224, 175, 139, 224, 174, 178, 224, 175, 141, 32, 12, 0, 2, 224, 175, 139, 224, 174, 181, 224, 174, 164, 0, 8, 2, 17, 66, 0, 8, 2, 224, 174, 190, 224, 174, 154, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 163, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 32, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 18, 81, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 224, 174, 149, 224, 175, 129, 224, 174, 177, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 224, 174, 174, 224, 175, 135, 224, 174, 177, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 224, 174, 174, 224, 175, 135, 224, 174, 177, 224, 175, 141, 224, 174, 170, 224, 174, 159, 224, 175, 141, 224, 174, 159, 32, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 224, 174, 174, 224, 175, 135, 224, 174, 178, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 135, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 159, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 190, 224, 174, 170, 224, 174, 191, 224, 174, 183, 224, 175, 135, 224, 174, 149, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 191, 224, 174, 169, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 129, 224, 174, 159, 224, 174, 169, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 141, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 136, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 191, 224, 174, 159, 0, 8, 2, 224, 175, 135, 224, 174, 183, 224, 174, 169, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 138, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 169, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 32, 129, 175, 224, 159, 174, 224, 134, 174, 224, 2, 224, 174, 190, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 135, 0, 8, 32, 129, 175, 224, 159, 174, 224, 190, 174, 224, 175, 174, 224, 136, 175, 224, 179, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 135, 0, 8, 128, 175, 224, 159, 174, 224, 2, 224, 174, 190, 224, 174, 175, 224, 175, 141, 0, 8, 128, 175, 224, 164, 174, 224, 2, 224, 174, 190, 0, 8, 129, 175, 224, 159, 174, 224, 141, 175, 224, 159, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 8, 129, 175, 224, 159, 174, 224, 191, 174, 224, 181, 174, 224, 164, 174, 224, 2, 224, 175, 138, 224, 174, 159, 224, 174, 191, 0, 8, 129, 175, 224, 177, 174, 224, 135, 175, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 8, 129, 175, 224, 177, 174, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 164, 0, 8, 129, 175, 224, 177, 174, 224, 174, 174, 224, 2, 224, 174, 191, 224, 174, 177, 0, 8, 129, 175, 224, 177, 174, 224, 174, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 175, 141, 224, 174, 154, 0, 8, 129, 175, 224, 177, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 164, 224, 175, 136, 0, 8, 130, 175, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 179, 224, 174, 174, 224, 175, 141, 32, 0, 8, 135, 175, 224, 159, 174, 224, 2, 224, 175, 141, 0, 8, 135, 175, 224, 168, 174, 224, 2, 224, 174, 190, 224, 174, 179, 0, 8, 136, 175, 224, 149, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 174, 191, 0, 8, 136, 175, 224, 159, 174, 224, 149, 174, 224, 2, 224, 174, 191, 224, 174, 159, 224, 174, 191, 0, 8, 136, 175, 224, 159, 174, 224, 164, 174, 224, 2, 224, 175, 139, 224, 174, 159, 0, 8, 136, 175, 224, 159, 174, 224, 168, 174, 224, 2, 224, 174, 190, 224, 174, 164, 224, 175, 136, 0, 8, 136, 175, 224, 159, 174, 224, 168, 174, 224, 2, 224, 175, 139, 224, 174, 159, 0, 8, 136, 175, 224, 177, 174, 224, 129, 175, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 8, 141, 175, 224, 149, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 12, 0, 8, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 175, 139, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 141, 175, 224, 163, 174, 224, 134, 175, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 8, 141, 175, 224, 169, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 0, 8, 141, 175, 224, 169, 174, 224, 134, 175, 224, 164, 174, 224, 2, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 163, 224, 175, 136, 0, 8, 141, 175, 224, 169, 174, 224, 134, 175, 224, 174, 174, 224, 2, 224, 175, 138, 224, 174, 176, 224, 175, 129, 0, 8, 141, 175, 224, 169, 174, 224, 181, 174, 224, 2, 224, 175, 138, 224, 174, 176, 224, 175, 129, 0, 8, 141, 175, 224, 174, 174, 224, 129, 175, 224, 164, 174, 224, 139, 175, 224, 170, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 174, 174, 224, 135, 175, 224, 176, 174, 224, 164, 174, 224, 2, 224, 174, 190, 32, 0, 8, 141, 175, 224, 174, 174, 224, 135, 175, 224, 176, 174, 224, 181, 174, 224, 2, 224, 174, 190, 32, 0, 8, 141, 175, 224, 174, 174, 224, 135, 175, 224, 177, 174, 224, 139, 175, 224, 170, 174, 224, 2, 224, 174, 190, 32, 0, 8, 141, 175, 224, 174, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 178, 224, 174, 190, 0, 8, 141, 175, 224, 174, 174, 224, 149, 174, 224, 2, 224, 175, 134, 224, 174, 169, 224, 174, 191, 0, 8, 141, 175, 224, 174, 174, 224, 149, 174, 224, 2, 224, 175, 139, 224, 174, 184, 0, 8, 141, 175, 224, 174, 174, 224, 149, 174, 224, 2, 224, 175, 140, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 174, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 154, 174, 224, 2, 224, 175, 139, 224, 174, 159, 0, 8, 141, 175, 224, 174, 174, 224, 178, 174, 224, 2, 224, 175, 130, 224, 174, 176, 0, 8, 141, 175, 224, 174, 174, 224, 178, 174, 224, 129, 175, 224, 170, 174, 224, 2, 224, 175, 134, 224, 174, 175, 224, 174, 176, 0, 8, 141, 175, 224, 174, 174, 224, 178, 174, 224, 190, 174, 224, 178, 174, 224, 139, 175, 224, 149, 174, 224, 2, 224, 175, 130, 224, 174, 176, 0, 8, 141, 175, 224, 174, 174, 224, 180, 174, 224, 170, 174, 224, 2, 224, 175, 138, 224, 174, 176, 224, 175, 129, 224, 174, 179, 0, 8, 141, 175, 224, 174, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 175, 139, 224, 174, 154, 224, 174, 191, 224, 174, 183, 224, 174, 169, 0, 8, 141, 175, 224, 174, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 175, 140, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 174, 174, 224, 190, 174, 224, 159, 174, 224, 141, 175, 224, 163, 174, 224, 135, 175, 224, 181, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 174, 174, 224, 190, 174, 224, 178, 174, 224, 139, 175, 224, 170, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 174, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 179, 0, 8, 141, 175, 224, 174, 174, 224, 191, 174, 224, 164, 174, 224, 2, 224, 175, 129, 0, 8, 141, 175, 224, 178, 174, 224, 134, 175, 224, 154, 174, 224, 2, 224, 175, 135, 224, 174, 154, 224, 174, 191, 0, 8, 141, 175, 224, 178, 174, 224, 138, 175, 224, 164, 174, 224, 2, 224, 175, 138, 224, 174, 176, 224, 175, 129, 224, 174, 179, 0, 8, 141, 175, 224, 178, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 141, 175, 224, 178, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 178, 174, 224, 191, 174, 224, 183, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 180, 174, 224, 190, 174, 224, 175, 174, 224, 2, 224, 174, 190, 224, 174, 163, 0, 8, 154, 174, 224, 141, 175, 224, 158, 174, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 0, 8, 159, 174, 224, 141, 175, 224, 159, 174, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 8, 159, 174, 224, 141, 175, 224, 159, 174, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 159, 174, 224, 141, 175, 224, 159, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 159, 224, 174, 190, 224, 174, 149, 0, 8, 159, 174, 224, 181, 174, 224, 2, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 163, 224, 175, 136, 0, 8, 174, 174, 224, 141, 175, 224, 176, 174, 224, 164, 174, 224, 2, 224, 175, 129, 224, 174, 176, 224, 174, 191, 0, 8, 175, 174, 224, 191, 174, 224, 178, 174, 224, 149, 174, 224, 2, 224, 175, 134, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 179, 0, 8, 176, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 175, 134, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 179, 0, 8, 176, 174, 224, 190, 174, 224, 174, 174, 224, 129, 175, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 179, 224, 175, 136, 224, 174, 175, 0, 8, 176, 174, 224, 191, 174, 224, 149, 174, 224, 141, 175, 224, 149, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 163, 224, 174, 191, 0, 8, 178, 174, 224, 170, 174, 224, 2, 224, 175, 135, 224, 174, 176, 0, 8, 178, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 175, 135, 224, 174, 176, 0, 8, 181, 174, 224, 168, 174, 224, 2, 224, 174, 190, 224, 174, 183, 0, 8, 190, 174, 224, 169, 174, 224, 141, 175, 224, 169, 174, 224, 149, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 190, 0, 8, 190, 174, 224, 170, 174, 224, 2, 224, 175, 129, 224, 174, 178, 224, 174, 176, 0, 8, 191, 174, 224, 154, 174, 224, 141, 175, 224, 169, 174, 224, 191, 174, 224, 176, 174, 224, 141, 175, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 8, 191, 174, 224, 176, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 8, 191, 174, 224, 177, 174, 224, 134, 175, 224, 181, 174, 224, 2, 224, 174, 191, 224, 174, 159, 224, 174, 191, 0, 8, 191, 174, 224, 180, 174, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 159, 0, 224, 174, 191, 1, 139, 175, 224, 176, 174, 224, 143, 174, 224, 2, 224, 174, 179, 224, 175, 135, 224, 174, 169, 0, 224, 174, 191, 1, 141, 175, 224, 159, 174, 224, 137, 174, 224, 2, 224, 174, 176, 224, 174, 149, 224, 174, 190, 224, 174, 176, 0, 224, 174, 191, 1, 141, 175, 224, 170, 174, 224, 129, 175, 224, 154, 174, 224, 176, 174, 224, 133, 174, 224, 2, 224, 174, 176, 224, 174, 164, 224, 174, 191, 224, 174, 168, 224, 174, 191, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 1, 141, 175, 224, 170, 174, 224, 156, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 176, 224, 174, 164, 224, 174, 191, 224, 174, 168, 224, 174, 191, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 1, 141, 175, 224, 170, 174, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 18, 68, 2, 224, 174, 176, 224, 174, 179, 224, 174, 175, 0, 224, 174, 191, 1, 141, 175, 224, 170, 174, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 18, 68, 2, 224, 174, 176, 224, 174, 190, 224, 174, 175, 0, 224, 174, 191, 1, 141, 175, 224, 170, 174, 224, 169, 174, 224, 156, 174, 224, 139, 175, 224, 170, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 176, 0, 224, 174, 191, 1, 141, 175, 224, 183, 174, 224, 129, 175, 224, 164, 174, 224, 2, 224, 174, 176, 224, 174, 175, 224, 175, 139, 224, 174, 149, 0, 224, 174, 191, 2, 224, 174, 176, 224, 174, 190, 224, 174, 175, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 149, 224, 174, 178, 224, 174, 190, 224, 174, 164, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 149, 224, 174, 190, 224, 174, 154, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 149, 224, 174, 190, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 149, 224, 175, 141, 224, 174, 158, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 153, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 169, 224, 175, 141, 224, 174, 168, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 169, 224, 175, 141, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 181, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 190, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 175, 129, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 169, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 190, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 169, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 156, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 163, 224, 174, 181, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 174, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 190, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 190, 224, 174, 170, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 175, 128, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 175, 135, 224, 174, 154, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 175, 135, 224, 174, 183, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 175, 135, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 170, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 174, 190, 224, 174, 163, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 174, 190, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 174, 190, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 175, 129, 224, 174, 149, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 175, 139, 224, 174, 183, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 175, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 175, 224, 174, 190, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 175, 224, 175, 139, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 175, 224, 175, 139, 224, 174, 154, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 175, 224, 175, 139, 224, 174, 156, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 178, 224, 174, 175, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 179, 224, 174, 175, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 181, 224, 175, 128, 224, 174, 163, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 181, 224, 175, 128, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 181, 224, 175, 135, 224, 174, 154, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 181, 224, 175, 135, 224, 174, 154, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 184, 224, 174, 190, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 184, 224, 175, 141, 224, 174, 164, 224, 174, 190, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 185, 224, 174, 178, 224, 174, 190, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 174, 190, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 163, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 174, 164, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 164, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 174, 153, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 174, 164, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 174, 174, 224, 175, 141, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 170, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 191, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 139, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 174, 224, 174, 191, 224, 174, 175, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 164, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 174, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 159, 224, 174, 174, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 181, 224, 175, 129, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 181, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 135, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 149, 224, 174, 191, 224, 174, 164, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 184, 224, 175, 141, 32, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 190, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 170, 224, 174, 190, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 175, 128, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 175, 135, 0, 224, 174, 191, 8, 141, 175, 224, 170, 174, 224, 169, 174, 224, 190, 174, 224, 164, 174, 224, 2, 224, 174, 176, 224, 174, 170, 0, 224, 174, 191, 8, 141, 175, 224, 170, 174, 224, 174, 174, 224, 141, 175, 224, 176, 174, 224, 164, 174, 224, 2, 224, 174, 176, 224, 174, 170, 0, 224, 174, 191, 8, 141, 175, 224, 170, 174, 224, 176, 174, 224, 181, 174, 224, 2, 224, 174, 176, 18, 69, 224, 174, 190, 224, 174, 164, 0, 224, 174, 191, 8, 141, 175, 224, 170, 174, 224, 190, 174, 224, 18, 71, 174, 174, 224, 2, 224, 174, 176, 224, 174, 170, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 149, 224, 174, 191, 224, 174, 164, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 169, 0, 224, 175, 129, 8, 2, 224, 174, 179, 224, 175, 129, 224, 174, 159, 224, 175, 139, 224, 174, 169, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 1, 139, 175, 224, 176, 174, 224, 143, 174, 224, 2, 224, 174, 179, 224, 175, 135, 224, 174, 169, 0, 224, 175, 141, 1, 141, 175, 224, 174, 174, 224, 135, 174, 224, 2, 224, 174, 176, 224, 175, 134, 224, 174, 184, 0, 224, 175, 141, 2, 32, 224, 174, 170, 0, 224, 175, 141, 2, 224, 174, 170, 0, 224, 175, 141, 2, 224, 174, 184, 0, 224, 175, 141, 8, 129, 175, 224, 154, 174, 224, 2, 224, 174, 176, 224, 175, 128, 224, 174, 174, 0, 224, 175, 141, 8, 135, 175, 224, 149, 174, 224, 2, 224, 174, 174, 224, 174, 190, 224, 174, 176, 224, 174, 191, 0, 224, 175, 141, 8, 139, 175, 224, 170, 174, 224, 0, 224, 175, 141, 8, 141, 175, 224, 174, 174, 224, 149, 174, 224, 2, 224, 174, 176, 224, 175, 134, 224, 174, 184, 0, 224, 175, 141, 8, 149, 174, 224, 190, 174, 224, 178, 174, 224, 0, 224, 175, 141, 8, 190, 174, 224, 159, 174, 224, 141, 175, 224, 149, 174, 224, 141, 175, 224, 184, 174, 224, 134, 175, 224, 159, 174, 224, 0, 224, 175, 141, 8, 190, 174, 224, 174, 174, 224, 2, 224, 174, 179, 0, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 178, 3, 48, 34, 37, 50, 87, 37, 48, 0, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 190, 3, 48, 34, 37, 57, 107, 66, 49, 0, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 2, 224, 174, 176, 3, 48, 34, 37, 64, 138, 107, 0, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 3, 48, 34, 37, 64, 138, 147, 0, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 159, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 191, 224, 174, 175, 3, 48, 34, 37, 138, 0, 4, 224, 175, 129, 224, 174, 176, 224, 174, 131, 224, 174, 170, 8, 2, 18, 69, 224, 174, 176, 3, 48, 34, 39, 81, 107, 0, 224, 175, 129, 224, 174, 176, 224, 174, 170, 8, 2, 18, 69, 224, 174, 176, 0, 224, 175, 129, 224, 174, 176, 224, 174, 170, 224, 175, 138, 8, 2, 224, 174, 154, 224, 174, 176, 0, 224, 175, 129, 224, 174, 176, 224, 175, 138, 224, 174, 170, 8, 2, 224, 174, 154, 224, 174, 176, 0, 224, 175, 129, 224, 174, 176, 224, 175, 138, 224, 174, 170, 224, 175, 138, 8, 2, 224, 174, 154, 224, 174, 176, 0, 224, 175, 141, 224, 174, 176, 224, 174, 170, 224, 175, 138, 8, 2, 224, 174, 154, 224, 174, 176, 0, 224, 175, 141, 224, 174, 176, 224, 175, 138, 224, 174, 170, 8, 2, 224, 174, 154, 224, 174, 176, 0, 224, 175, 141, 224, 174, 176, 224, 175, 138, 224, 174, 170, 224, 175, 138, 8, 2, 224, 174, 154, 224, 174, 176, 0, 224, 174, 191, 224, 174, 176, 224, 174, 164, 224, 175, 141, 8, 2, 224, 174, 175, 224, 175, 135, 224, 174, 149, 3, 48, 34, 107, 47, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 149, 2, 224, 174, 190, 224, 174, 183, 3, 48, 34, 107, 49, 0, 224, 174, 191, 224, 174, 176, 224, 174, 149, 8, 141, 175, 224, 170, 174, 224, 169, 174, 224, 190, 174, 224, 158, 174, 224, 2, 224, 174, 190, 0, 224, 174, 191, 224, 174, 176, 224, 174, 149, 8, 169, 174, 224, 190, 174, 224, 158, 174, 224, 2, 224, 174, 190, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 154, 1, 141, 175, 224, 170, 174, 224, 164, 174, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 176, 3, 48, 34, 107, 74, 0, 224, 174, 191, 224, 174, 176, 224, 174, 154, 8, 2, 224, 174, 190, 224, 174, 176, 0, 224, 174, 191, 224, 174, 176, 224, 174, 154, 8, 2, 224, 175, 141, 224, 174, 169, 224, 175, 136, 0, 224, 174, 191, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 8, 2, 224, 174, 178, 3, 48, 34, 116, 49, 138, 37, 49, 107, 0, 224, 175, 141, 224, 174, 176, 224, 175, 139, 224, 174, 159, 8, 2, 224, 174, 190, 224, 174, 169, 3, 48, 34, 117, 47, 0, 224, 175, 129, 224, 174, 176, 224, 175, 139, 224, 174, 159, 8, 2, 224, 174, 190, 224, 174, 169, 3, 48, 34, 117, 138, 0, 224, 174, 191, 224, 174, 176, 224, 175, 136, 224, 174, 181, 224, 175, 135, 224, 174, 159, 8, 3, 48, 34, 132, 82, 112, 138, 147, 0, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 176, 3, 48, 36, 64, 138, 107, 0, 4, 224, 175, 134, 224, 174, 158, 224, 175, 141, 224, 174, 154, 8, 2, 224, 174, 190, 32, 3, 48, 36, 65, 73, 0, 224, 175, 134, 224, 174, 158, 224, 175, 141, 224, 174, 154, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 129, 224, 174, 174, 0, 224, 174, 191, 224, 174, 159, 8, 190, 174, 224, 149, 174, 224, 2, 224, 174, 178, 3, 48, 37, 138, 107, 0, 224, 175, 129, 224, 174, 164, 224, 175, 141, 8, 2, 224, 174, 164, 23, 32, 224, 174, 170, 224, 175, 129, 224, 174, 164, 12, 3, 48, 40, 47, 0, 4, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 149, 3, 48, 40, 47, 47, 107, 0, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 174, 224, 175, 141, 32, 224, 174, 170, 224, 175, 129, 224, 174, 164, 224, 174, 191, 224, 174, 175, 0, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 174, 224, 175, 141, 32, 224, 174, 170, 224, 175, 129, 224, 174, 164, 224, 175, 129, 0, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 154, 224, 174, 191, 0, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 174, 224, 175, 141, 224, 174, 170, 8, 2, 224, 175, 129, 224, 174, 164, 3, 48, 40, 47, 47, 107, 63, 48, 0, 4, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 18, 68, 2, 224, 174, 176, 224, 174, 149, 224, 174, 190, 224, 174, 176, 3, 48, 48, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 18, 68, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 149, 174, 224, 133, 174, 224, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 149, 174, 224, 191, 174, 224, 164, 174, 224, 133, 174, 224, 2, 224, 174, 176, 224, 174, 154, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 154, 174, 224, 135, 175, 224, 164, 174, 224, 2, 224, 174, 176, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 164, 174, 224, 141, 175, 224, 164, 174, 224, 176, 174, 224, 135, 174, 224, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 164, 174, 224, 141, 175, 224, 164, 174, 224, 176, 174, 224, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 169, 174, 224, 174, 174, 224, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 178, 174, 224, 156, 174, 224, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 178, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 176, 224, 174, 170, 224, 175, 129, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 181, 174, 224, 164, 174, 224, 190, 174, 224, 175, 174, 224, 2, 224, 174, 176, 224, 174, 149, 224, 174, 190, 224, 174, 154, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 181, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 149, 224, 174, 190, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 191, 174, 224, 18, 75, 146, 174, 224, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 191, 174, 224, 163, 174, 224, 174, 174, 224, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 191, 174, 224, 164, 174, 224, 168, 174, 224, 2, 224, 174, 176, 224, 174, 181, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 191, 174, 224, 179, 174, 224, 134, 175, 224, 181, 174, 224, 2, 224, 174, 176, 224, 174, 149, 224, 174, 190, 224, 174, 176, 0, 224, 175, 141, 224, 174, 149, 8, 190, 174, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 169, 3, 48, 49, 0, 224, 175, 141, 224, 174, 175, 224, 175, 130, 224, 174, 159, 1, 141, 175, 224, 174, 174, 224, 149, 174, 224, 2, 224, 174, 176, 3, 48, 57, 150, 138, 107, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 8, 176, 174, 224, 170, 174, 224, 2, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 174, 3, 48, 69, 0, 4, 1, 21, 2, 224, 174, 159, 224, 175, 141, 224, 174, 154, 12, 3, 48, 107, 0, 1, 128, 175, 224, 169, 174, 224, 2, 25, 0, 1, 128, 175, 224, 176, 174, 224, 2, 25, 0, 1, 129, 175, 224, 169, 174, 224, 133, 174, 224, 2, 224, 174, 174, 224, 174, 190, 0, 1, 129, 175, 224, 169, 174, 224, 133, 174, 224, 2, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 181, 224, 174, 191, 0, 1, 129, 175, 224, 176, 174, 224, 135, 174, 224, 2, 224, 174, 149, 0, 1, 129, 175, 224, 176, 174, 224, 146, 174, 224, 2, 224, 174, 149, 0, 1, 129, 175, 224, 176, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 174, 224, 174, 190, 0, 1, 134, 174, 224, 2, 224, 174, 176, 224, 175, 135, 224, 174, 154, 224, 174, 169, 0, 1, 134, 174, 224, 2, 224, 174, 176, 224, 175, 135, 224, 174, 183, 224, 174, 169, 0, 1, 136, 175, 224, 164, 174, 224, 170, 174, 224, 2, 224, 174, 164, 224, 175, 136, 0, 1, 137, 174, 224, 2, 224, 174, 168, 224, 175, 141, 224, 174, 168, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 154, 0, 1, 139, 175, 224, 175, 174, 224, 191, 174, 224, 174, 174, 224, 2, 224, 174, 164, 224, 174, 191, 0, 1, 139, 175, 224, 178, 174, 224, 133, 174, 224, 2, 224, 174, 164, 224, 174, 191, 0, 1, 140, 175, 224, 176, 174, 224, 191, 174, 224, 164, 174, 224, 2, 224, 174, 164, 224, 174, 191, 0, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 174, 180, 224, 174, 191, 0, 1, 141, 175, 224, 169, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 149, 224, 174, 178, 0, 1, 141, 175, 224, 169, 174, 224, 134, 175, 224, 164, 174, 224, 2, 224, 174, 149, 224, 175, 129, 224, 174, 164, 224, 174, 191, 0, 1, 141, 175, 224, 169, 174, 224, 168, 174, 224, 2, 224, 174, 149, 224, 174, 178, 0, 1, 141, 175, 224, 169, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 149, 224, 174, 178, 0, 1, 141, 175, 224, 169, 174, 224, 191, 174, 224, 174, 174, 224, 2, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 12, 0, 1, 141, 175, 224, 170, 174, 224, 0, 1, 141, 175, 224, 174, 174, 224, 176, 174, 224, 149, 174, 224, 2, 224, 174, 159, 0, 1, 141, 175, 224, 174, 174, 224, 176, 174, 224, 149, 174, 224, 2, 224, 174, 177, 224, 175, 141, 0, 1, 141, 175, 224, 178, 174, 224, 133, 174, 224, 2, 224, 174, 164, 224, 175, 141, 0, 1, 141, 175, 224, 178, 174, 224, 133, 174, 224, 2, 224, 174, 174, 0, 1, 141, 175, 224, 178, 174, 224, 149, 174, 224, 2, 224, 174, 169, 224, 174, 190, 0, 1, 147, 174, 224, 2, 224, 174, 169, 0, 1, 149, 174, 224, 2, 25, 0, 1, 159, 174, 224, 181, 174, 224, 2, 224, 174, 149, 224, 175, 129, 224, 174, 164, 224, 174, 191, 0, 1, 159, 174, 224, 181, 174, 224, 2, 224, 174, 180, 0, 1, 164, 174, 224, 0, 1, 174, 174, 224, 0, 1, 174, 174, 224, 2, 25, 0, 1, 176, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 169, 224, 174, 191, 0, 1, 176, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 176, 224, 174, 174, 0, 1, 176, 174, 224, 191, 174, 224, 159, 174, 224, 141, 175, 224, 183, 174, 224, 190, 174, 224, 176, 174, 224, 135, 174, 224, 2, 224, 174, 164, 224, 174, 191, 0, 1, 190, 174, 224, 149, 174, 224, 2, 25, 0, 1, 190, 174, 224, 164, 174, 224, 2, 25, 0, 1, 190, 174, 224, 174, 174, 224, 2, 25, 0, 1, 191, 174, 224, 159, 174, 224, 133, 174, 224, 2, 224, 174, 163, 224, 174, 191, 0, 1, 191, 174, 224, 169, 174, 224, 2, 25, 0, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 25, 0, 2, 224, 174, 159, 0, 2, 224, 174, 159, 224, 174, 191, 0, 2, 224, 174, 177, 224, 175, 141, 224, 174, 177, 224, 174, 191, 32, 0, 8, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 169, 32, 0, 8, 2, 224, 174, 175, 224, 174, 164, 224, 175, 141, 224, 174, 164, 32, 0, 8, 2, 224, 174, 175, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 158, 224, 175, 141, 0, 8, 2, 224, 174, 175, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 174, 224, 175, 141, 32, 0, 8, 2, 224, 174, 175, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 164, 0, 8, 2, 224, 174, 175, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 181, 224, 175, 136, 0, 8, 32, 18, 79, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 32, 18, 79, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 164, 224, 175, 141, 0, 8, 32, 18, 79, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 174, 0, 8, 129, 175, 224, 149, 174, 224, 129, 175, 224, 170, 174, 224, 2, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 136, 0, 8, 129, 175, 224, 159, 174, 224, 130, 175, 224, 174, 174, 224, 2, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 149, 224, 175, 141, 0, 8, 129, 175, 224, 159, 174, 224, 138, 174, 224, 2, 224, 174, 175, 224, 174, 191, 224, 174, 176, 0, 8, 129, 175, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 181, 224, 174, 179, 0, 8, 129, 175, 224, 177, 174, 224, 174, 174, 224, 2, 224, 174, 149, 224, 175, 129, 224, 174, 164, 224, 174, 191, 0, 8, 129, 175, 224, 177, 174, 224, 174, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 154, 224, 175, 128, 224, 174, 178, 224, 174, 169, 224, 175, 136, 0, 8, 136, 175, 224, 159, 174, 224, 168, 174, 224, 2, 224, 174, 175, 224, 174, 191, 224, 174, 177, 224, 175, 141, 224, 174, 154, 224, 174, 191, 0, 8, 141, 175, 224, 169, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 164, 224, 174, 191, 224, 174, 181, 0, 8, 141, 175, 224, 169, 174, 224, 175, 174, 224, 170, 174, 224, 0, 8, 141, 175, 224, 169, 174, 224, 191, 174, 224, 164, 174, 224, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 174, 174, 224, 149, 174, 224, 2, 224, 174, 169, 224, 174, 191, 0, 8, 141, 175, 224, 174, 174, 224, 149, 174, 224, 2, 224, 174, 178, 224, 175, 141, 0, 8, 141, 175, 224, 174, 174, 224, 170, 174, 224, 2, 224, 174, 176, 224, 175, 141, 32, 0, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 176, 224, 175, 135, 224, 174, 183, 224, 174, 169, 0, 8, 141, 175, 224, 178, 174, 224, 149, 174, 224, 2, 224, 174, 164, 224, 174, 176, 224, 175, 129, 0, 8, 141, 175, 224, 178, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 149, 174, 224, 190, 174, 224, 168, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 169, 0, 8, 154, 174, 224, 190, 174, 224, 178, 174, 224, 136, 175, 224, 149, 174, 224, 2, 224, 174, 164, 224, 174, 191, 0, 8, 176, 174, 224, 191, 174, 224, 159, 174, 224, 141, 175, 224, 183, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 164, 224, 174, 191, 0, 8, 181, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 164, 0, 8, 190, 174, 224, 181, 174, 224, 2, 224, 174, 184, 0, 8, 191, 174, 224, 154, 174, 224, 191, 174, 224, 169, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 178, 0, 8, 191, 174, 224, 163, 174, 224, 174, 174, 224, 2, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 181, 0, 8, 191, 174, 224, 178, 174, 224, 146, 174, 224, 2, 224, 174, 176, 224, 174, 170, 224, 175, 141, 0, 8, 191, 174, 224, 179, 174, 224, 146, 174, 224, 2, 224, 174, 176, 224, 174, 170, 224, 175, 141, 0, 4, 224, 174, 164, 1, 129, 175, 224, 154, 174, 224, 170, 174, 224, 2, 224, 174, 191, 3, 48, 107, 47, 0, 224, 174, 164, 1, 190, 174, 224, 156, 174, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 191, 0, 4, 224, 174, 164, 224, 174, 191, 1, 129, 175, 224, 149, 174, 224, 176, 174, 224, 3, 48, 107, 47, 37, 0, 224, 174, 164, 224, 174, 191, 1, 129, 175, 224, 164, 174, 224, 135, 175, 224, 154, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 141, 175, 224, 184, 174, 224, 149, 174, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 156, 174, 224, 149, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 159, 174, 224, 129, 175, 224, 149, 174, 224, 174, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 159, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 135, 175, 224, 181, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 163, 174, 224, 149, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 190, 174, 224, 149, 174, 224, 191, 174, 224, 170, 174, 224, 141, 175, 224, 174, 174, 224, 133, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 190, 174, 224, 164, 174, 224, 128, 175, 224, 154, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 190, 174, 224, 175, 174, 224, 136, 175, 224, 179, 174, 224, 181, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 190, 174, 224, 175, 174, 224, 141, 175, 224, 164, 174, 224, 191, 174, 224, 181, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 191, 174, 224, 163, 174, 224, 176, 174, 224, 164, 174, 224, 0, 224, 174, 164, 224, 174, 191, 1, 191, 174, 224, 174, 174, 224, 141, 175, 224, 183, 174, 224, 141, 175, 224, 149, 174, 224, 178, 174, 224, 0, 4, 224, 174, 170, 2, 224, 174, 190, 3, 48, 107, 48, 0, 224, 174, 170, 224, 175, 141, 1, 141, 175, 224, 178, 174, 224, 133, 174, 224, 0, 224, 174, 170, 2, 25, 3, 48, 107, 48, 107, 0, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 174, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 1, 133, 174, 224, 3, 48, 116, 34, 63, 36, 50, 138, 147, 0, 224, 174, 190, 224, 174, 170, 2, 224, 174, 190, 3, 48, 116, 48, 0, 224, 174, 190, 224, 174, 170, 2, 25, 3, 48, 116, 48, 107, 0, 224, 174, 190, 224, 174, 175, 224, 174, 191, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 141, 224, 174, 174, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 1, 133, 174, 224, 3, 48, 116, 57, 37, 64, 138, 63, 36, 50, 138, 147, 0, 4, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 153, 224, 175, 141, 3, 48, 116, 69, 107, 0, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 164, 224, 175, 141, 0, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 174, 0, 224, 174, 190, 224, 174, 170, 224, 174, 181, 224, 174, 191, 224, 174, 174, 224, 175, 139, 224, 174, 154, 224, 174, 169, 8, 3, 48, 116, 69, 107, 82, 37, 63, 117, 74, 107, 0, 224, 174, 190, 224, 174, 154, 224, 174, 191, 224, 174, 159, 8, 134, 175, 224, 159, 174, 224, 3, 48, 116, 87, 37, 138, 147, 0, 224, 174, 190, 224, 174, 154, 224, 175, 129, 224, 174, 170, 8, 2, 224, 174, 164, 3, 48, 116, 87, 120, 48, 107, 0, 224, 175, 139, 224, 174, 176, 224, 175, 141, 224, 174, 159, 1, 141, 175, 224, 176, 174, 224, 143, 174, 224, 3, 48, 117, 34, 138, 147, 0, 224, 175, 141, 224, 174, 159, 1, 21, 3, 48, 138, 147, 0, 4, 1, 18, 67, 3, 48, 147, 0, 1, 141, 175, 224, 174, 174, 224, 191, 174, 224, 178, 174, 224, 146, 174, 224, 0, 1, 141, 175, 224, 176, 174, 224, 159, 174, 224, 135, 174, 224, 0, 1, 141, 175, 224, 178, 174, 224, 133, 174, 224, 2, 32, 0, 1, 141, 175, 224, 178, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 154, 174, 224, 0, 8, 128, 175, 224, 164, 174, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 0, 8, 141, 175, 224, 174, 174, 224, 135, 175, 224, 149, 174, 224, 0, 8, 141, 175, 224, 178, 174, 224, 138, 175, 224, 154, 174, 224, 0, 8, 141, 175, 224, 178, 174, 224, 149, 174, 224, 191, 174, 224, 181, 174, 224, 0, 4, 1, 32, 46, 32, 191, 174, 224, 170, 174, 224, 2, 224, 174, 191, 32, 46, 32, 224, 174, 154, 224, 174, 191, 3, 69, 0, 1, 32, 129, 175, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 129, 175, 224, 176, 174, 224, 191, 174, 224, 178, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 32, 129, 175, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 129, 175, 224, 176, 174, 224, 191, 174, 224, 178, 174, 224, 191, 174, 224, 179, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 32, 141, 175, 224, 169, 174, 224, 191, 174, 224, 179, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 32, 164, 174, 224, 141, 175, 224, 168, 174, 224, 129, 175, 224, 176, 174, 224, 191, 174, 224, 178, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 32, 164, 174, 224, 141, 175, 224, 168, 174, 224, 129, 175, 224, 176, 174, 224, 191, 174, 224, 178, 174, 224, 191, 174, 224, 179, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 32, 175, 174, 224, 136, 175, 224, 159, 174, 224, 129, 175, 224, 169, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 32, 175, 174, 224, 136, 175, 224, 159, 174, 224, 129, 175, 224, 169, 174, 224, 191, 174, 224, 179, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 133, 174, 224, 2, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 181, 0, 1, 141, 175, 224, 169, 174, 224, 133, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 0, 1, 141, 175, 224, 169, 174, 224, 135, 174, 224, 2, 224, 175, 129, 224, 174, 177, 0, 1, 141, 175, 224, 170, 174, 224, 191, 174, 224, 176, 174, 224, 191, 174, 224, 164, 174, 224, 137, 174, 224, 2, 224, 174, 190, 224, 174, 149, 0, 1, 141, 175, 224, 174, 174, 224, 2, 17, 66, 224, 174, 159, 0, 1, 141, 175, 224, 174, 174, 224, 2, 224, 174, 190, 0, 1, 141, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 179, 224, 175, 136, 224, 174, 175, 0, 1, 141, 175, 224, 174, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 0, 1, 141, 175, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 176, 224, 174, 190, 0, 1, 141, 175, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 176, 224, 174, 191, 0, 1, 141, 175, 224, 174, 174, 224, 2, 224, 175, 130, 224, 174, 176, 0, 1, 141, 175, 224, 174, 174, 224, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 136, 0, 1, 141, 175, 224, 174, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 133, 174, 224, 2, 224, 175, 135, 224, 174, 176, 224, 175, 141, 0, 1, 141, 175, 224, 176, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 0, 1, 141, 175, 224, 177, 174, 224, 164, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 149, 0, 1, 141, 175, 224, 177, 174, 224, 175, 174, 224, 135, 174, 224, 2, 224, 174, 191, 224, 174, 175, 224, 174, 178, 0, 1, 141, 175, 224, 183, 174, 224, 129, 175, 224, 149, 174, 224, 2, 224, 175, 129, 0, 1, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 1, 149, 174, 224, 141, 175, 224, 149, 174, 224, 18, 68, 2, 224, 174, 190, 224, 174, 178, 224, 174, 191, 0, 1, 164, 174, 224, 2, 17, 66, 0, 1, 174, 174, 224, 2, 17, 66, 0, 1, 174, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 190, 224, 174, 163, 0, 1, 190, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 176, 174, 224, 148, 174, 224, 2, 224, 174, 190, 224, 174, 164, 0, 1, 190, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 176, 174, 224, 179, 174, 224, 146, 174, 224, 2, 224, 174, 190, 224, 174, 164, 0, 1, 190, 174, 224, 149, 174, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 174, 164, 0, 1, 190, 174, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 191, 174, 224, 156, 174, 224, 2, 224, 174, 190, 224, 174, 164, 224, 175, 141, 0, 1, 190, 174, 224, 164, 174, 224, 174, 174, 224, 18, 71, 133, 174, 224, 2, 224, 174, 190, 224, 174, 164, 0, 1, 190, 174, 224, 164, 174, 224, 174, 174, 224, 134, 174, 224, 2, 224, 174, 190, 224, 174, 164, 0, 1, 190, 174, 224, 181, 174, 224, 168, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 0, 2, 17, 66, 0, 8, 2, 17, 66, 28, 17, 12, 0, 8, 2, 18, 72, 224, 174, 178, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 174, 181, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 128, 224, 174, 176, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 174, 190, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 190, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 154, 224, 175, 129, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 174, 191, 32, 224, 174, 170, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 174, 191, 224, 174, 175, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 178, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 224, 175, 129, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 224, 175, 129, 224, 174, 159, 224, 174, 169, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 190, 224, 174, 163, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 163, 224, 174, 174, 224, 175, 129, 0, 8, 2, 224, 174, 190, 224, 174, 163, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 163, 224, 174, 190, 224, 174, 154, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 163, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 135, 224, 174, 156, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 130, 224, 174, 159, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 178, 224, 174, 190, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 181, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 181, 224, 174, 191, 224, 174, 178, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 177, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 177, 224, 175, 129, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 134, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 224, 175, 136, 224, 174, 149, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 224, 175, 136, 224, 174, 175, 224, 175, 129, 224, 174, 174, 224, 175, 134, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 224, 175, 136, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 164, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 190, 224, 174, 149, 224, 174, 191, 224, 174, 177, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 169, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 177, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 224, 174, 179, 224, 175, 141, 224, 174, 179, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 175, 129, 224, 174, 183, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 175, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 176, 224, 175, 130, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 174, 224, 175, 129, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 176, 224, 175, 141, 224, 174, 156, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 174, 190, 224, 174, 154, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 175, 129, 0, 8, 2, 224, 174, 190, 224, 174, 169, 224, 175, 134, 224, 174, 159, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 170, 224, 174, 191, 224, 174, 178, 224, 175, 139, 224, 174, 169, 224, 174, 191, 224, 174, 175, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 170, 224, 175, 129, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 174, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 174, 224, 174, 191, 224, 174, 169, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 135, 0, 8, 2, 224, 174, 190, 224, 174, 175, 224, 175, 141, 224, 174, 178, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 174, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 181, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 18, 69, 224, 174, 178, 224, 175, 139, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 149, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 154, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 164, 224, 174, 163, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 169, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 174, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 190, 224, 174, 179, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 175, 224, 175, 141, 224, 174, 175, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 190, 224, 174, 154, 224, 175, 130, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 190, 224, 174, 156, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 190, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 191, 224, 174, 149, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 191, 224, 174, 175, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 174, 191, 224, 174, 181, 224, 175, 129, 224, 174, 159, 224, 175, 141, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 129, 224, 174, 154, 224, 174, 190, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 129, 224, 174, 154, 224, 175, 129, 224, 174, 181, 224, 174, 190, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 129, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 141, 32, 224, 174, 164, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 224, 175, 135, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 141, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 178, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 169, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 177, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 175, 139, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 164, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 164, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 164, 224, 175, 129, 0, 8, 2, 224, 174, 190, 224, 174, 181, 224, 175, 135, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 183, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 190, 224, 174, 183, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 174, 190, 224, 174, 183, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 183, 224, 175, 136, 0, 8, 2, 224, 174, 190, 224, 174, 183, 224, 175, 141, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 184, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 169, 0, 8, 2, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 174, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 191, 32, 46, 32, 224, 174, 170, 224, 174, 191, 32, 46, 32, 224, 174, 154, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 175, 130, 0, 8, 2, 224, 174, 191, 224, 174, 154, 224, 174, 191, 224, 174, 169, 224, 174, 184, 0, 8, 2, 224, 174, 191, 224, 174, 154, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 191, 224, 174, 156, 224, 174, 191, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 175, 129, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 174, 190, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 224, 174, 178, 224, 175, 135, 224, 174, 159, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 170, 224, 174, 191, 224, 174, 154, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 174, 224, 175, 141, 224, 174, 170, 0, 8, 2, 224, 174, 191, 224, 174, 175, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 149, 224, 174, 164, 224, 175, 128, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 149, 224, 174, 184, 224, 175, 141, 224, 174, 170, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 174, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 175, 136, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 169, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 163, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 149, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 149, 224, 174, 168, 224, 174, 179, 0, 8, 2, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 170, 224, 175, 130, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 159, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 0, 8, 2, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 184, 224, 174, 191, 224, 174, 169, 224, 174, 184, 0, 8, 2, 224, 174, 191, 224, 174, 184, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 174, 159, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 175, 134, 224, 174, 159, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 175, 139, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 174, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 174, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 0, 8, 2, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 178, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 181, 224, 174, 190, 224, 174, 184, 0, 8, 2, 224, 175, 128, 224, 174, 149, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 175, 128, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 175, 128, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 128, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 175, 129, 224, 174, 178, 0, 8, 2, 224, 175, 128, 224, 174, 156, 0, 8, 2, 224, 175, 128, 224, 174, 156, 224, 174, 191, 224, 174, 153, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 159, 224, 175, 136, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 129, 224, 174, 149, 224, 175, 136, 0, 8, 2, 224, 175, 128, 224, 174, 159, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 128, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 139, 224, 174, 181, 224, 174, 169, 0, 8, 2, 224, 175, 128, 224, 174, 169, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 175, 128, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 175, 138, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 175, 128, 224, 174, 174, 0, 8, 2, 224, 175, 128, 224, 174, 176, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 191, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 163, 224, 174, 176, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 175, 139, 0, 8, 2, 224, 175, 128, 224, 174, 176, 224, 175, 141, 224, 174, 170, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 175, 128, 224, 174, 185, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 136, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 178, 0, 8, 2, 224, 175, 129, 224, 174, 156, 0, 8, 2, 224, 175, 129, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 164, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 154, 224, 174, 190, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 129, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 175, 129, 224, 174, 176, 224, 175, 139, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 159, 224, 175, 139, 224, 174, 154, 224, 174, 176, 0, 8, 2, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 159, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 129, 224, 174, 181, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 184, 224, 175, 141, 224, 174, 181, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 175, 129, 224, 174, 184, 224, 175, 141, 224, 174, 184, 224, 175, 134, 0, 8, 2, 224, 175, 130, 224, 174, 149, 224, 174, 174, 224, 175, 141, 224, 174, 170, 0, 8, 2, 224, 175, 130, 224, 174, 149, 224, 175, 139, 224, 174, 178, 0, 8, 2, 224, 175, 130, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 130, 224, 174, 159, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 149, 224, 174, 163, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 149, 224, 174, 163, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 170, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 174, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 181, 224, 175, 129, 224, 174, 159, 224, 174, 174, 224, 175, 141, 224, 174, 170, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 190, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 190, 224, 174, 149, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 175, 135, 224, 174, 181, 224, 174, 191, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 175, 130, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 175, 130, 224, 174, 170, 224, 174, 169, 224, 175, 135, 0, 8, 2, 224, 175, 130, 224, 174, 170, 224, 174, 190, 224, 174, 179, 0, 8, 2, 224, 175, 130, 224, 174, 174, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 130, 224, 174, 174, 224, 174, 190, 224, 174, 164, 224, 174, 190, 0, 8, 2, 224, 175, 130, 224, 174, 174, 224, 174, 190, 224, 174, 164, 224, 175, 135, 224, 174, 181, 224, 174, 191, 0, 8, 2, 224, 175, 130, 224, 174, 174, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 175, 130, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 175, 130, 224, 174, 176, 224, 175, 141, 224, 174, 183, 0, 8, 2, 224, 175, 130, 224, 174, 178, 224, 175, 139, 224, 174, 149, 0, 8, 2, 224, 175, 130, 224, 174, 183, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 224, 175, 130, 224, 174, 176, 0, 8, 2, 224, 175, 134, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 175, 134, 224, 174, 158, 224, 175, 141, 224, 174, 154, 224, 174, 174, 224, 174, 191, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 176, 224, 175, 130, 224, 174, 174, 0, 8, 2, 224, 175, 134, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 178, 0, 8, 2, 224, 175, 134, 224, 174, 169, 224, 174, 154, 224, 175, 128, 224, 174, 176, 0, 8, 2, 224, 175, 134, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 183, 224, 174, 190, 0, 8, 2, 224, 175, 134, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 134, 224, 174, 176, 224, 175, 141, 224, 174, 174, 224, 175, 129, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 175, 134, 224, 174, 176, 224, 175, 141, 224, 174, 178, 224, 174, 191, 224, 174, 153, 0, 8, 2, 224, 175, 134, 224, 174, 176, 224, 175, 141, 224, 174, 178, 224, 174, 191, 224, 174, 169, 0, 8, 2, 224, 175, 134, 224, 174, 178, 224, 175, 141, 0, 8, 2, 224, 175, 134, 224, 174, 179, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 134, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 149, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 149, 224, 174, 174, 0, 8, 2, 224, 175, 135, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 175, 135, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 178, 224, 174, 176, 0, 8, 2, 224, 175, 135, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 178, 224, 174, 176, 0, 8, 2, 224, 175, 135, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 175, 129, 224, 174, 178, 224, 174, 176, 0, 8, 2, 224, 175, 135, 224, 174, 156, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 175, 135, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 164, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 164, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 175, 135, 224, 174, 164, 224, 174, 174, 224, 175, 129, 0, 8, 2, 224, 175, 135, 224, 174, 164, 224, 174, 178, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 135, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 175, 135, 224, 174, 169, 224, 174, 176, 0, 8, 2, 224, 175, 135, 224, 174, 170, 224, 174, 191, 0, 8, 2, 224, 175, 135, 224, 174, 174, 224, 174, 190, 224, 174, 169, 224, 174, 191, 0, 8, 2, 224, 175, 135, 224, 174, 178, 224, 174, 169, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 175, 135, 224, 174, 178, 224, 175, 141, 0, 8, 2, 224, 175, 135, 224, 174, 183, 224, 174, 190, 0, 8, 2, 224, 175, 136, 224, 174, 149, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 8, 2, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 177, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 175, 136, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 0, 8, 2, 224, 175, 136, 224, 174, 154, 224, 174, 169, 0, 8, 2, 224, 175, 136, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 136, 224, 174, 169, 224, 174, 190, 224, 174, 149, 0, 8, 2, 224, 175, 136, 224, 174, 169, 224, 174, 190, 224, 174, 174, 224, 174, 191, 0, 8, 2, 224, 175, 136, 224, 174, 170, 224, 174, 191, 224, 174, 179, 0, 8, 2, 224, 175, 136, 224, 174, 176, 224, 174, 169, 0, 8, 2, 224, 175, 136, 224, 174, 176, 224, 174, 181, 0, 8, 2, 224, 175, 136, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 174, 191, 0, 8, 2, 224, 175, 138, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 169, 0, 8, 2, 224, 175, 138, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 178, 0, 8, 2, 224, 175, 138, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 131, 224, 174, 170, 224, 175, 139, 224, 174, 176, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 149, 32, 18, 78, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 177, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 169, 224, 175, 141, 224, 174, 181, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 191, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 191, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 149, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 175, 139, 224, 174, 156, 0, 8, 2, 224, 175, 139, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 149, 224, 174, 169, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 169, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 191, 224, 174, 154, 224, 174, 164, 224, 175, 141, 224, 174, 181, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 191, 224, 174, 164, 224, 174, 176, 224, 175, 141, 224, 174, 174, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 191, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 174, 191, 224, 174, 175, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 175, 141, 224, 174, 184, 224, 175, 141, 224, 174, 178, 224, 175, 135, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 174, 224, 174, 178, 224, 174, 190, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 164, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 174, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 224, 174, 133, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 175, 141, 32, 224, 174, 133, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 169, 224, 175, 141, 32, 224, 174, 133, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 175, 141, 224, 174, 181, 224, 175, 134, 224, 174, 178, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 183, 224, 174, 191, 0, 8, 2, 224, 175, 139, 224, 174, 184, 224, 174, 191, 224, 174, 159, 0, 8, 2, 224, 175, 140, 224, 174, 164, 224, 174, 191, 224, 174, 149, 0, 8, 2, 224, 175, 140, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 175, 140, 224, 174, 178, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 175, 140, 224, 174, 183, 0, 8, 32, 18, 77, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 178, 0, 8, 32, 141, 175, 224, 159, 174, 224, 134, 175, 224, 159, 174, 224, 2, 224, 174, 190, 224, 174, 159, 224, 174, 191, 0, 8, 32, 141, 175, 224, 169, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 141, 175, 224, 169, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 149, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 141, 175, 224, 169, 174, 224, 191, 174, 224, 179, 174, 224, 149, 174, 224, 141, 175, 224, 153, 174, 224, 149, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 141, 175, 224, 174, 174, 224, 130, 175, 224, 176, 174, 224, 2, 224, 174, 190, 224, 174, 175, 0, 8, 32, 141, 175, 224, 176, 174, 224, 128, 175, 224, 154, 174, 224, 169, 174, 224, 134, 175, 224, 170, 174, 224, 2, 224, 175, 129, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 139, 0, 8, 32, 149, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 149, 174, 224, 135, 175, 224, 168, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 149, 174, 224, 135, 175, 224, 169, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 149, 174, 224, 190, 174, 224, 176, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 164, 174, 224, 141, 175, 224, 168, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 175, 174, 224, 135, 175, 224, 168, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 176, 174, 224, 164, 174, 224, 139, 175, 224, 149, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 181, 0, 8, 32, 176, 174, 224, 191, 174, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 154, 174, 224, 2, 224, 175, 139, 224, 174, 184, 0, 8, 133, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 0, 8, 141, 175, 224, 163, 174, 224, 170, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 0, 8, 141, 175, 224, 169, 174, 224, 129, 175, 224, 164, 174, 224, 2, 224, 175, 129, 224, 174, 177, 0, 8, 141, 175, 224, 169, 174, 224, 133, 174, 224, 2, 224, 175, 129, 224, 174, 159, 0, 8, 141, 175, 224, 170, 174, 224, 191, 174, 224, 179, 174, 224, 134, 175, 224, 181, 174, 224, 2, 224, 174, 190, 224, 174, 149, 0, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 159, 0, 8, 141, 175, 224, 176, 174, 224, 190, 174, 224, 174, 174, 224, 2, 224, 175, 139, 224, 174, 159, 0, 8, 141, 175, 224, 184, 174, 224, 134, 175, 224, 178, 174, 224, 2, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 8, 141, 175, 224, 184, 174, 224, 142, 174, 224, 129, 175, 224, 175, 174, 224, 2, 224, 174, 191, 0, 8, 149, 174, 224, 2, 224, 174, 190, 224, 174, 159, 224, 174, 170, 224, 175, 129, 224, 174, 176, 12, 0, 8, 149, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 8, 164, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 8, 174, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 149, 0, 8, 176, 174, 224, 174, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 0, 8, 176, 174, 224, 174, 174, 224, 2, 224, 175, 129, 224, 174, 176, 224, 174, 191, 224, 174, 174, 224, 175, 136, 0, 8, 181, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 190, 224, 174, 178, 224, 174, 169, 0, 8, 190, 174, 224, 149, 174, 224, 2, 224, 174, 190, 224, 174, 178, 224, 174, 191, 0, 8, 190, 174, 224, 176, 174, 224, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 0, 224, 174, 191, 1, 134, 174, 224, 2, 224, 174, 176, 224, 174, 149, 224, 174, 190, 224, 174, 174, 0, 224, 174, 191, 1, 134, 174, 224, 2, 224, 174, 176, 224, 174, 185, 224, 174, 190, 224, 174, 174, 0, 224, 174, 191, 1, 141, 175, 224, 163, 174, 224, 128, 175, 224, 181, 174, 224, 2, 224, 174, 176, 224, 174, 174, 224, 175, 136, 0, 224, 174, 191, 1, 141, 175, 224, 170, 174, 224, 164, 174, 224, 141, 175, 224, 164, 174, 224, 191, 174, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 174, 224, 175, 136, 0, 224, 174, 191, 1, 141, 175, 224, 170, 174, 224, 169, 174, 224, 174, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 1, 141, 175, 224, 170, 174, 224, 175, 174, 224, 170, 174, 224, 2, 224, 174, 176, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 2, 224, 174, 176, 224, 174, 164, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 175, 130, 224, 174, 169, 224, 174, 184, 224, 175, 141, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 149, 224, 174, 164, 224, 175, 128, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 149, 224, 174, 184, 224, 175, 141, 224, 174, 170, 224, 174, 164, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 178, 224, 175, 141, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 176, 224, 175, 141, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 176, 224, 175, 141, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 174, 191, 224, 174, 164, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 174, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 174, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 181, 224, 175, 129, 224, 174, 154, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 183, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 184, 224, 174, 178, 224, 175, 141, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 185, 224, 174, 164, 224, 175, 128, 224, 174, 154, 224, 175, 129, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 185, 224, 174, 164, 224, 175, 128, 224, 174, 184, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 185, 224, 174, 184, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 181, 224, 175, 135, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 141, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 175, 129, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 175, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 164, 224, 174, 191, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 163, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 163, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 175, 224, 175, 141, 224, 174, 178, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 177, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 174, 191, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 224, 175, 136, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 135, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 159, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 169, 224, 174, 191, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 149, 224, 175, 129, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 159, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 175, 224, 174, 191, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 135, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 135, 224, 174, 154, 224, 174, 191, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 136, 224, 174, 178, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 140, 224, 174, 154, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 140, 224, 174, 169, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 181, 224, 175, 129, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 175, 140, 224, 174, 184, 0, 224, 175, 128, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 174, 224, 174, 163, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 174, 181, 224, 175, 129, 224, 174, 154, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 169, 224, 174, 190, 224, 174, 175, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 140, 224, 174, 154, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 154, 224, 174, 178, 224, 175, 141, 224, 174, 184, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 174, 224, 175, 141, 224, 174, 174, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 181, 224, 175, 129, 224, 174, 154, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 183, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 184, 224, 174, 178, 224, 175, 141, 224, 174, 184, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 181, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 129, 224, 174, 169, 224, 174, 190, 224, 174, 175, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 159, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 175, 224, 174, 191, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 175, 224, 175, 141, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 135, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 135, 224, 174, 154, 224, 174, 191, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 136, 224, 174, 178, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 140, 224, 174, 154, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 140, 224, 174, 169, 0, 224, 175, 141, 8, 2, 224, 174, 179, 224, 174, 181, 224, 175, 129, 224, 174, 184, 0, 224, 175, 141, 8, 2, 224, 174, 179, 224, 175, 140, 224, 174, 184, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 129, 175, 224, 154, 174, 224, 2, 224, 174, 176, 224, 174, 174, 224, 174, 163, 224, 174, 191, 0, 4, 224, 174, 191, 224, 174, 176, 224, 175, 129, 8, 2, 224, 174, 149, 224, 174, 169, 224, 175, 141, 224, 174, 168, 224, 174, 179, 224, 175, 136, 3, 69, 34, 37, 0, 224, 174, 191, 224, 174, 176, 224, 175, 129, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 190, 0, 4, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 170, 8, 2, 224, 175, 135, 224, 174, 169, 3, 69, 34, 37, 87, 69, 0, 224, 175, 141, 224, 174, 176, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 170, 8, 2, 224, 175, 135, 224, 174, 169, 0, 224, 174, 191, 224, 174, 176, 224, 174, 174, 8, 2, 224, 174, 169, 3, 69, 34, 107, 63, 63, 107, 0, 224, 175, 134, 224, 174, 164, 224, 175, 141, 8, 2, 224, 174, 178, 3, 69, 36, 47, 0, 224, 175, 134, 224, 174, 158, 224, 175, 141, 224, 174, 154, 8, 2, 224, 174, 174, 224, 174, 191, 224, 174, 169, 3, 69, 36, 65, 73, 107, 0, 224, 175, 134, 224, 174, 158, 224, 175, 141, 224, 174, 154, 8, 3, 69, 36, 65, 74, 147, 0, 224, 175, 134, 224, 174, 170, 224, 175, 141, 224, 174, 170, 8, 2, 224, 175, 135, 3, 69, 36, 69, 69, 0, 224, 175, 134, 224, 174, 154, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 3, 69, 36, 87, 107, 64, 138, 147, 0, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 183, 224, 175, 128, 224, 174, 159, 224, 175, 141, 8, 3, 69, 36, 139, 91, 110, 138, 0, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 159, 8, 2, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 3, 69, 36, 139, 139, 0, 224, 174, 191, 224, 174, 170, 8, 2, 224, 174, 191, 3, 69, 37, 48, 0, 224, 174, 191, 224, 174, 183, 224, 174, 170, 224, 175, 141, 8, 3, 69, 37, 91, 107, 48, 0, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 175, 134, 224, 174, 159, 224, 175, 141, 8, 3, 69, 40, 55, 55, 36, 138, 0, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 25, 3, 69, 40, 70, 70, 107, 0, 224, 174, 191, 224, 174, 179, 224, 174, 190, 224, 174, 149, 224, 175, 141, 8, 3, 69, 55, 116, 49, 0, 4, 224, 175, 141, 224, 174, 170, 1, 18, 68, 2, 224, 175, 130, 224, 174, 164, 224, 174, 164, 224, 175, 141, 3, 69, 69, 0, 224, 175, 141, 224, 174, 170, 1, 18, 68, 2, 224, 175, 130, 224, 174, 164, 224, 174, 174, 0, 224, 175, 141, 224, 174, 170, 1, 129, 175, 224, 154, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 174, 174, 224, 174, 163, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 170, 1, 133, 174, 224, 2, 224, 174, 190, 224, 174, 184, 0, 224, 175, 141, 224, 174, 170, 1, 133, 174, 224, 2, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 154, 0, 224, 175, 141, 224, 174, 170, 1, 135, 174, 224, 2, 224, 175, 130, 224, 174, 174, 224, 174, 191, 0, 224, 175, 141, 224, 174, 170, 1, 137, 174, 224, 2, 224, 174, 191, 32, 0, 224, 175, 141, 224, 174, 170, 1, 137, 174, 224, 2, 224, 174, 191, 224, 174, 169, 32, 0, 224, 175, 141, 224, 174, 170, 1, 137, 174, 224, 2, 224, 174, 191, 224, 174, 170, 224, 175, 141, 0, 224, 175, 141, 224, 174, 170, 1, 137, 174, 224, 2, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 170, 1, 137, 174, 224, 2, 224, 175, 129, 224, 174, 154, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 224, 175, 141, 224, 174, 170, 1, 137, 174, 224, 2, 224, 175, 129, 224, 174, 154, 224, 174, 174, 0, 224, 175, 141, 224, 174, 170, 1, 141, 175, 224, 176, 174, 224, 129, 175, 224, 164, 174, 224, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 224, 174, 170, 1, 141, 175, 224, 176, 174, 224, 129, 175, 224, 164, 174, 224, 2, 224, 175, 139, 224, 174, 164, 224, 174, 169, 224, 175, 136, 0, 224, 175, 141, 224, 174, 170, 1, 141, 175, 224, 176, 174, 224, 134, 174, 224, 2, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 224, 174, 170, 1, 191, 174, 224, 159, 174, 224, 133, 174, 224, 2, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 1, 191, 174, 224, 164, 174, 224, 129, 175, 224, 177, 174, 224, 135, 174, 224, 2, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 8, 141, 175, 224, 176, 174, 224, 164, 174, 224, 2, 224, 175, 136, 0, 224, 175, 141, 224, 174, 170, 8, 149, 174, 224, 135, 175, 224, 164, 174, 224, 141, 175, 224, 168, 174, 224, 154, 174, 224, 2, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 224, 175, 141, 224, 174, 170, 8, 156, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 224, 175, 141, 224, 174, 170, 8, 156, 174, 224, 149, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 175, 129, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 224, 175, 141, 224, 174, 170, 8, 159, 174, 224, 2, 224, 174, 190, 0, 224, 175, 141, 224, 174, 170, 8, 178, 174, 224, 2, 224, 175, 136, 0, 224, 175, 141, 224, 174, 170, 8, 179, 174, 224, 141, 175, 224, 149, 174, 224, 2, 224, 175, 129, 224, 174, 149, 224, 174, 179, 0, 224, 175, 141, 224, 174, 170, 8, 185, 174, 224, 2, 224, 174, 191, 224, 174, 179, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 169, 174, 224, 174, 174, 224, 2, 224, 174, 176, 224, 174, 174, 224, 175, 136, 0, 4, 224, 175, 141, 224, 174, 170, 1, 18, 68, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 224, 174, 190, 3, 69, 69, 107, 0, 224, 175, 141, 224, 174, 170, 1, 18, 68, 2, 224, 174, 164, 224, 174, 191, 224, 174, 178, 0, 224, 175, 141, 224, 174, 170, 1, 18, 68, 2, 224, 174, 184, 0, 224, 175, 141, 224, 174, 170, 1, 141, 175, 224, 176, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 224, 175, 141, 224, 174, 170, 1, 141, 175, 224, 176, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 175, 0, 224, 175, 141, 224, 174, 170, 1, 141, 175, 224, 176, 174, 224, 191, 174, 224, 175, 174, 224, 137, 174, 224, 2, 224, 174, 178, 224, 174, 191, 0, 224, 175, 141, 224, 174, 170, 8, 176, 174, 224, 2, 224, 174, 176, 0, 224, 175, 141, 224, 174, 170, 8, 179, 174, 224, 149, 174, 224, 2, 224, 174, 178, 224, 174, 191, 0, 224, 175, 141, 224, 174, 170, 8, 191, 174, 224, 176, 174, 224, 2, 224, 174, 169, 0, 4, 224, 175, 141, 224, 174, 170, 1, 141, 175, 224, 176, 174, 224, 149, 174, 224, 3, 69, 69, 147, 0, 224, 175, 141, 224, 174, 170, 8, 129, 175, 224, 154, 174, 224, 0, 224, 175, 141, 224, 174, 170, 8, 129, 175, 224, 154, 174, 224, 174, 174, 224, 190, 174, 224, 176, 174, 224, 0, 224, 175, 141, 224, 174, 170, 8, 190, 174, 224, 181, 174, 224, 168, 174, 224, 0, 4, 3, 69, 107, 0, 1, 129, 175, 224, 177, 174, 224, 174, 174, 224, 2, 224, 174, 159, 224, 174, 191, 0, 1, 141, 175, 224, 170, 174, 224, 136, 175, 224, 159, 174, 224, 170, 174, 224, 2, 224, 174, 178, 0, 1, 141, 175, 224, 170, 174, 224, 136, 175, 224, 178, 174, 224, 135, 175, 224, 181, 174, 224, 2, 224, 174, 179, 224, 175, 129, 0, 1, 141, 175, 224, 170, 174, 224, 164, 174, 224, 129, 175, 224, 175, 174, 224, 134, 174, 224, 2, 224, 174, 178, 0, 1, 141, 175, 224, 174, 174, 224, 2, 224, 174, 159, 0, 1, 141, 175, 224, 174, 174, 224, 149, 174, 224, 141, 175, 224, 149, 174, 224, 133, 174, 224, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 1, 141, 175, 224, 184, 174, 224, 133, 174, 224, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 1, 149, 174, 224, 2, 224, 174, 159, 0, 1, 164, 174, 224, 2, 224, 174, 184, 0, 1, 174, 174, 224, 141, 175, 224, 164, 174, 224, 134, 174, 224, 2, 224, 174, 178, 0, 1, 174, 174, 224, 141, 175, 224, 169, 174, 224, 134, 174, 224, 2, 224, 174, 178, 0, 1, 174, 174, 224, 176, 174, 224, 170, 174, 224, 2, 224, 174, 149, 224, 175, 141, 224, 174, 164, 0, 1, 175, 174, 224, 191, 174, 224, 176, 174, 224, 134, 174, 224, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 0, 1, 190, 174, 224, 149, 174, 224, 2, 224, 174, 176, 0, 1, 190, 174, 224, 149, 174, 224, 190, 174, 224, 168, 174, 224, 2, 224, 174, 176, 224, 174, 163, 0, 1, 190, 174, 224, 164, 174, 224, 2, 224, 174, 174, 224, 175, 141, 0, 1, 190, 174, 224, 164, 174, 224, 141, 175, 224, 184, 174, 224, 2, 224, 174, 163, 0, 1, 190, 174, 224, 164, 174, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 1, 190, 174, 224, 164, 174, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 174, 0, 1, 191, 174, 224, 169, 174, 224, 2, 224, 174, 149, 224, 174, 181, 224, 174, 190, 224, 174, 169, 224, 175, 141, 0, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 8, 2, 18, 71, 224, 175, 129, 224, 174, 149, 224, 175, 129, 224, 174, 163, 224, 174, 190, 0, 8, 2, 18, 71, 224, 175, 129, 224, 174, 156, 0, 8, 2, 28, 17, 12, 0, 8, 2, 224, 174, 131, 224, 174, 170, 224, 175, 130, 224, 174, 169, 0, 8, 2, 224, 174, 149, 224, 174, 164, 224, 175, 130, 224, 174, 176, 0, 8, 2, 224, 174, 149, 224, 174, 164, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 149, 224, 174, 181, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 149, 224, 174, 181, 224, 174, 169, 0, 8, 2, 224, 174, 149, 224, 174, 181, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 149, 224, 174, 190, 224, 174, 154, 224, 175, 129, 224, 174, 176, 0, 8, 2, 224, 174, 149, 224, 174, 190, 224, 174, 154, 224, 175, 130, 224, 174, 176, 224, 174, 169, 0, 8, 2, 224, 174, 149, 224, 174, 190, 224, 174, 175, 0, 8, 2, 224, 174, 149, 224, 174, 191, 224, 174, 176, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 149, 224, 174, 191, 224, 174, 183, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 149, 224, 175, 128, 224, 174, 176, 0, 8, 2, 224, 174, 149, 224, 175, 129, 224, 174, 179, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 191, 224, 174, 153, 224, 175, 141, 18, 71, 224, 174, 190, 224, 174, 174, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 134, 224, 174, 159, 224, 175, 141, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 134, 224, 174, 169, 224, 175, 141, 224, 174, 177, 0, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 183, 224, 174, 163, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 174, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 224, 174, 190, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 190, 224, 174, 176, 0, 8, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 154, 224, 174, 181, 224, 174, 149, 224, 174, 178, 224, 175, 141, 224, 174, 175, 224, 174, 190, 224, 174, 163, 0, 8, 2, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 169, 0, 8, 2, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 156, 0, 8, 2, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 159, 224, 175, 129, 224, 174, 149, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 163, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 170, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 156, 224, 174, 159, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 156, 224, 175, 134, 224, 174, 159, 224, 175, 141, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 149, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 169, 0, 8, 2, 224, 174, 164, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 0, 8, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 176, 224, 174, 174, 224, 174, 190, 0, 8, 2, 224, 174, 164, 224, 175, 141, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 32, 224, 174, 170, 224, 174, 190, 224, 174, 154, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 174, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 181, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 181, 0, 8, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 175, 139, 224, 174, 170, 224, 174, 184, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 169, 224, 174, 190, 224, 174, 176, 224, 174, 184, 0, 8, 2, 224, 174, 169, 224, 174, 191, 224, 174, 175, 224, 174, 169, 0, 8, 2, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 174, 190, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 224, 174, 159, 224, 175, 128, 224, 174, 175, 224, 175, 129, 224, 174, 174, 224, 175, 141, 0, 8, 2, 224, 174, 169, 224, 175, 141, 224, 174, 176, 224, 175, 129, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 0, 8, 2, 224, 174, 170, 224, 175, 130, 224, 174, 169, 0, 8, 2, 224, 174, 170, 224, 175, 141, 224, 174, 179, 224, 174, 191, 224, 174, 174, 224, 174, 190, 224, 174, 184, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 176, 0, 8, 2, 224, 174, 174, 224, 175, 141, 224, 174, 170, 224, 174, 190, 224, 174, 175, 0, 8, 2, 224, 174, 175, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 175, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 174, 175, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 175, 224, 174, 168, 224, 175, 141, 0, 8, 2, 224, 174, 175, 224, 174, 170, 224, 174, 149, 224, 175, 141, 224, 174, 164, 224, 174, 191, 0, 8, 2, 224, 174, 175, 224, 174, 170, 224, 175, 141, 0, 8, 2, 224, 174, 175, 224, 174, 174, 0, 8, 2, 224, 174, 175, 224, 174, 190, 224, 174, 178, 224, 174, 156, 224, 174, 191, 0, 8, 2, 224, 174, 175, 224, 174, 191, 224, 174, 178, 224, 175, 141, 224, 174, 181, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 168, 224, 174, 190, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 169, 0, 8, 2, 224, 174, 176, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 159, 224, 174, 174, 0, 8, 2, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 0, 8, 2, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 181, 224, 174, 190, 224, 174, 156, 0, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 149, 224, 175, 141, 32, 224, 174, 146, 224, 174, 170, 224, 174, 190, 224, 174, 174, 224, 174, 190, 0, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 159, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 131, 224, 174, 170, 224, 174, 191, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 164, 224, 175, 141, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 190, 224, 174, 178, 224, 174, 190, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 174, 0, 8, 2, 224, 174, 178, 224, 174, 149, 224, 175, 128, 224, 174, 169, 0, 8, 2, 224, 174, 178, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 178, 224, 174, 154, 224, 174, 190, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 174, 178, 224, 174, 164, 224, 175, 135, 224, 174, 181, 0, 8, 2, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 178, 0, 8, 2, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 169, 224, 174, 190, 0, 8, 2, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 169, 224, 175, 129, 224, 174, 159, 0, 8, 2, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 154, 224, 175, 141, 0, 8, 2, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 224, 174, 159, 0, 8, 2, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 136, 0, 8, 2, 224, 174, 178, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 139, 224, 174, 159, 224, 175, 129, 0, 8, 2, 224, 174, 178, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 0, 8, 2, 224, 174, 178, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 159, 224, 175, 129, 0, 8, 2, 224, 174, 178, 224, 174, 170, 224, 175, 141, 224, 174, 170, 224, 174, 176, 224, 175, 128, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 175, 136, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 174, 163, 224, 175, 136, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 174, 190, 224, 174, 149, 17, 67, 224, 175, 141, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 174, 190, 224, 174, 149, 224, 174, 181, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 174, 190, 224, 174, 149, 224, 174, 181, 224, 175, 135, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 174, 190, 224, 174, 149, 224, 174, 191, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 174, 190, 224, 174, 154, 224, 175, 141, 224, 174, 154, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 174, 190, 224, 174, 175, 224, 175, 141, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 174, 191, 224, 174, 180, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 175, 129, 224, 174, 159, 224, 174, 169, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 175, 129, 224, 174, 159, 224, 175, 136, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 175, 129, 224, 174, 159, 224, 175, 136, 224, 174, 175, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 175, 129, 224, 174, 174, 0, 8, 2, 224, 174, 178, 224, 174, 174, 224, 175, 129, 224, 174, 179, 224, 175, 141, 224, 174, 179, 0, 8, 2, 224, 174, 178, 224, 174, 176, 224, 174, 190, 224, 174, 174, 0, 8, 2, 224, 174, 178, 224, 174, 181, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 178, 224, 174, 181, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 178, 224, 174, 181, 224, 175, 128, 224, 174, 169, 0, 8, 2, 224, 174, 178, 224, 174, 185, 224, 175, 128, 224, 174, 169, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 149, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 149, 224, 175, 138, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 174, 159, 224, 174, 190, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 224, 174, 154, 224, 175, 141, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 138, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 156, 224, 174, 190, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 170, 224, 175, 128, 224, 174, 159, 0, 8, 2, 224, 174, 178, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 178, 224, 175, 128, 224, 174, 156, 224, 174, 190, 0, 8, 2, 224, 174, 178, 224, 175, 130, 224, 174, 169, 0, 8, 2, 224, 174, 178, 224, 175, 141, 224, 174, 149, 224, 175, 135, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 178, 224, 175, 141, 224, 174, 170, 224, 175, 129, 0, 8, 2, 224, 174, 178, 224, 175, 141, 224, 174, 170, 224, 175, 136, 0, 8, 2, 224, 174, 179, 224, 175, 129, 0, 8, 2, 224, 174, 181, 224, 174, 169, 0, 8, 2, 224, 174, 181, 224, 174, 190, 224, 174, 163, 224, 174, 191, 0, 8, 2, 224, 174, 181, 224, 174, 190, 224, 174, 169, 224, 174, 191, 0, 8, 2, 224, 174, 181, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 181, 224, 175, 129, 224, 174, 178, 224, 174, 176, 0, 8, 2, 224, 174, 181, 224, 175, 129, 224, 174, 178, 224, 174, 191, 224, 174, 153, 224, 175, 141, 0, 8, 2, 224, 174, 181, 224, 175, 141, 224, 174, 175, 0, 8, 2, 224, 174, 183, 224, 175, 128, 224, 174, 176, 0, 8, 2, 224, 174, 184, 0, 8, 2, 224, 174, 185, 224, 174, 164, 224, 175, 130, 224, 174, 176, 0, 8, 2, 224, 174, 185, 224, 174, 190, 224, 174, 175, 0, 8, 2, 224, 174, 185, 224, 174, 191, 224, 174, 176, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 174, 185, 224, 174, 191, 224, 174, 176, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 174, 185, 224, 175, 141, 224, 174, 176, 224, 175, 134, 224, 174, 175, 0, 8, 32, 141, 175, 224, 174, 174, 224, 129, 175, 224, 175, 174, 224, 128, 175, 224, 159, 174, 224, 2, 224, 174, 169, 224, 175, 141, 224, 174, 169, 224, 175, 129, 224, 174, 174, 224, 175, 141, 32, 0, 8, 32, 164, 174, 224, 141, 175, 224, 168, 174, 224, 138, 175, 224, 154, 174, 224, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 129, 175, 224, 149, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 159, 224, 174, 191, 0, 8, 141, 175, 224, 163, 174, 224, 175, 174, 224, 170, 174, 224, 2, 224, 174, 159, 0, 8, 141, 175, 224, 170, 174, 224, 149, 174, 224, 141, 175, 224, 149, 174, 224, 170, 174, 224, 2, 224, 174, 178, 0, 8, 141, 175, 224, 178, 174, 224, 138, 175, 224, 154, 174, 224, 2, 224, 174, 181, 0, 8, 141, 175, 224, 184, 174, 224, 185, 174, 224, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 184, 174, 224, 191, 174, 224, 178, 174, 224, 2, 224, 174, 169, 0, 8, 149, 174, 224, 2, 224, 174, 164, 224, 175, 141, 0, 8, 149, 174, 224, 2, 224, 174, 174, 224, 175, 141, 32, 0, 8, 149, 174, 224, 2, 224, 174, 179, 224, 174, 191, 224, 174, 149, 224, 174, 176, 0, 8, 149, 174, 224, 135, 175, 224, 164, 174, 224, 2, 224, 174, 178, 0, 8, 149, 174, 224, 141, 175, 224, 149, 174, 224, 170, 174, 224, 2, 224, 174, 178, 0, 8, 159, 174, 224, 170, 174, 224, 2, 224, 174, 159, 0, 8, 164, 174, 224, 2, 224, 174, 154, 0, 8, 164, 174, 224, 141, 175, 224, 168, 174, 224, 138, 175, 224, 154, 174, 224, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 190, 174, 224, 149, 174, 224, 2, 224, 174, 168, 224, 175, 141, 224, 174, 164, 224, 175, 129, 0, 8, 190, 174, 224, 149, 174, 224, 174, 174, 224, 2, 224, 174, 178, 224, 174, 191, 0, 8, 190, 174, 224, 164, 174, 224, 2, 32, 0, 8, 190, 174, 224, 164, 174, 224, 2, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 190, 174, 224, 164, 174, 224, 2, 224, 174, 164, 224, 175, 141, 224, 174, 164, 0, 8, 190, 174, 224, 164, 174, 224, 2, 224, 174, 174, 0, 224, 175, 129, 8, 2, 224, 174, 176, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 174, 190, 0, 224, 174, 176, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 191, 3, 69, 107, 34, 81, 0, 224, 174, 176, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 175, 129, 8, 2, 224, 174, 181, 224, 174, 190, 224, 174, 156, 3, 69, 107, 34, 107, 47, 0, 4, 224, 174, 149, 224, 175, 141, 8, 2, 224, 174, 164, 3, 69, 107, 49, 0, 224, 174, 149, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 128, 224, 174, 164, 0, 224, 174, 168, 224, 175, 141, 224, 174, 164, 8, 2, 224, 175, 129, 224, 174, 178, 224, 175, 129, 3, 69, 107, 50, 47, 0, 224, 174, 178, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 190, 224, 174, 176, 3, 69, 107, 55, 116, 70, 49, 0, 224, 174, 178, 224, 175, 129, 224, 174, 154, 8, 2, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 169, 3, 69, 107, 55, 120, 74, 0, 224, 174, 178, 224, 175, 141, 224, 174, 159, 8, 2, 224, 174, 191, 3, 69, 107, 55, 138, 0, 224, 174, 175, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 175, 139, 224, 174, 170, 224, 175, 141, 8, 3, 69, 107, 57, 116, 87, 49, 117, 48, 0, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 176, 3, 69, 107, 66, 49, 107, 0, 224, 174, 164, 1, 141, 175, 224, 163, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 191, 224, 174, 178, 3, 69, 107, 70, 0, 4, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 149, 224, 174, 190, 224, 174, 179, 224, 174, 191, 3, 69, 107, 70, 70, 0, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 32, 0, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 224, 175, 129, 0, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 175, 0, 224, 174, 149, 8, 2, 224, 174, 191, 224, 174, 176, 224, 174, 163, 224, 175, 141, 224, 174, 159, 3, 69, 107, 79, 0, 224, 175, 128, 224, 174, 164, 8, 2, 224, 175, 139, 224, 174, 181, 224, 174, 169, 3, 69, 110, 47, 0, 224, 175, 128, 224, 174, 154, 224, 175, 141, 8, 2, 224, 174, 178, 3, 69, 110, 74, 0, 224, 175, 128, 224, 174, 159, 224, 175, 141, 224, 174, 176, 224, 175, 130, 224, 174, 159, 224, 175, 141, 8, 3, 69, 110, 138, 34, 121, 138, 0, 224, 175, 139, 8, 2, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 169, 3, 69, 116, 0, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 159, 224, 174, 190, 3, 69, 116, 34, 69, 107, 0, 224, 174, 190, 224, 174, 170, 224, 174, 164, 224, 174, 191, 1, 154, 174, 224, 3, 69, 116, 48, 107, 47, 37, 0, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 159, 8, 2, 224, 175, 128, 224, 174, 176, 224, 174, 191, 224, 174, 175, 224, 174, 190, 3, 69, 116, 49, 138, 0, 224, 174, 190, 224, 174, 178, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 169, 224, 174, 191, 3, 69, 116, 55, 49, 107, 0, 224, 174, 190, 224, 174, 178, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 159, 3, 69, 116, 55, 107, 48, 0, 224, 174, 190, 224, 174, 178, 224, 175, 141, 224, 174, 159, 8, 2, 224, 174, 191, 224, 174, 174, 224, 175, 139, 224, 174, 176, 3, 69, 116, 55, 138, 0, 224, 174, 190, 224, 174, 153, 224, 175, 141, 224, 174, 149, 8, 2, 224, 174, 190, 224, 174, 149, 224, 175, 141, 3, 69, 116, 66, 49, 0, 4, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 154, 224, 174, 190, 224, 174, 149, 224, 175, 135, 224, 174, 170, 224, 175, 141, 3, 69, 116, 69, 0, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 154, 224, 174, 190, 224, 174, 185, 224, 175, 135, 224, 174, 170, 224, 175, 141, 0, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 181, 0, 224, 174, 190, 224, 174, 170, 8, 141, 175, 224, 175, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 190, 0, 224, 174, 190, 224, 174, 170, 8, 191, 174, 224, 175, 174, 224, 190, 174, 224, 154, 174, 224, 2, 224, 174, 190, 0, 224, 174, 190, 224, 174, 170, 8, 2, 224, 174, 176, 3, 69, 116, 69, 107, 0, 4, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 175, 224, 174, 164, 224, 175, 136, 3, 69, 116, 70, 70, 0, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 175, 224, 174, 174, 224, 175, 141, 32, 0, 224, 174, 190, 224, 174, 149, 224, 175, 141, 224, 174, 164, 8, 2, 224, 174, 190, 224, 174, 164, 3, 69, 116, 79, 70, 0, 224, 175, 139, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 178, 3, 69, 117, 48, 0, 224, 175, 139, 224, 174, 170, 8, 2, 224, 175, 139, 224, 174, 176, 224, 175, 141, 3, 69, 117, 81, 0, 224, 175, 130, 224, 174, 164, 224, 175, 141, 8, 2, 32, 3, 69, 121, 47, 0, 224, 175, 130, 224, 174, 170, 8, 2, 224, 174, 164, 224, 174, 191, 3, 69, 121, 48, 107, 0, 224, 175, 130, 224, 174, 159, 8, 2, 224, 174, 190, 224, 174, 169, 3, 69, 121, 138, 0, 224, 175, 136, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 184, 3, 69, 132, 48, 0, 4, 1, 190, 174, 224, 164, 174, 224, 129, 175, 224, 168, 174, 224, 133, 174, 224, 2, 12, 3, 69, 147, 0, 1, 190, 174, 224, 164, 174, 224, 129, 175, 224, 169, 174, 224, 133, 174, 224, 2, 12, 0, 1, 190, 174, 224, 164, 174, 224, 141, 175, 224, 184, 174, 224, 169, 174, 224, 174, 174, 224, 2, 12, 0, 1, 190, 174, 224, 164, 174, 224, 141, 175, 224, 184, 174, 224, 176, 174, 224, 191, 174, 224, 170, 174, 224, 2, 12, 0, 1, 190, 174, 224, 164, 174, 224, 191, 174, 224, 176, 174, 224, 170, 174, 224, 2, 12, 0, 8, 190, 174, 224, 164, 174, 224, 141, 175, 224, 184, 174, 224, 2, 12, 0, 8, 190, 174, 224, 164, 174, 224, 149, 174, 224, 176, 174, 224, 191, 174, 224, 181, 174, 224, 2, 12, 0, 8, 190, 174, 224, 164, 174, 224, 190, 174, 224, 154, 174, 224, 141, 175, 224, 154, 174, 224, 170, 174, 224, 2, 12, 0, 4, 1, 134, 174, 224, 2, 224, 174, 191, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 3, 81, 0, 1, 139, 175, 224, 176, 174, 224, 141, 175, 224, 149, 174, 224, 136, 175, 224, 174, 174, 224, 2, 224, 175, 139, 224, 174, 169, 0, 1, 141, 175, 224, 169, 174, 224, 135, 174, 224, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 174, 0, 1, 141, 175, 224, 174, 174, 224, 135, 174, 224, 2, 224, 174, 190, 224, 174, 178, 0, 1, 141, 175, 224, 178, 174, 224, 134, 174, 224, 2, 224, 174, 190, 0, 1, 144, 174, 224, 2, 224, 175, 139, 224, 174, 169, 0, 1, 174, 174, 224, 190, 174, 224, 176, 174, 224, 191, 174, 224, 149, 174, 224, 2, 224, 175, 139, 224, 174, 169, 0, 1, 191, 174, 224, 178, 174, 224, 149, 174, 224, 2, 224, 175, 139, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 191, 224, 174, 175, 0, 8, 2, 224, 174, 190, 224, 174, 149, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 190, 224, 174, 164, 224, 175, 141, 224, 174, 164, 224, 174, 191, 224, 174, 174, 224, 174, 190, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 174, 18, 69, 224, 174, 191, 0, 8, 2, 224, 174, 190, 224, 174, 176, 224, 175, 141, 224, 174, 174, 224, 175, 129, 224, 174, 178, 0, 8, 2, 224, 174, 190, 224, 174, 185, 224, 174, 191, 224, 174, 175, 224, 174, 190, 224, 174, 169, 0, 8, 2, 224, 174, 191, 224, 174, 149, 224, 174, 176, 0, 8, 2, 224, 174, 191, 224, 174, 153, 224, 175, 141, 224, 174, 149, 224, 174, 176, 224, 175, 141, 32, 0, 8, 2, 224, 174, 191, 224, 174, 154, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 184, 0, 8, 2, 224, 174, 191, 224, 174, 159, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 174, 191, 224, 174, 183, 0, 8, 2, 224, 174, 191, 224, 174, 169, 224, 175, 141, 224, 174, 178, 224, 174, 190, 224, 174, 168, 224, 175, 141, 224, 174, 164, 0, 8, 2, 224, 174, 191, 224, 174, 170, 224, 175, 141, 224, 174, 176, 224, 174, 181, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 174, 191, 224, 174, 183, 224, 175, 141, 0, 8, 2, 224, 175, 129, 224, 174, 178, 224, 175, 141, 32, 18, 80, 0, 8, 2, 224, 175, 129, 224, 174, 178, 224, 175, 141, 224, 174, 178, 224, 174, 190, 32, 0, 8, 2, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 159, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 8, 2, 224, 175, 134, 224, 174, 164, 224, 174, 176, 0, 8, 2, 224, 175, 134, 224, 174, 170, 224, 175, 141, 224, 174, 176, 224, 174, 181, 224, 174, 176, 224, 174, 191, 0, 8, 2, 224, 175, 134, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 190, 224, 174, 163, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 134, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 159, 0, 8, 2, 224, 175, 135, 224, 174, 149, 224, 175, 141, 224, 174, 159, 224, 174, 176, 0, 8, 2, 224, 175, 135, 224, 174, 174, 224, 174, 191, 224, 174, 178, 224, 174, 191, 0, 8, 2, 224, 175, 135, 224, 174, 183, 224, 174, 169, 0, 8, 2, 224, 175, 136, 224, 174, 178, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 139, 32, 0, 8, 2, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 139, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 159, 224, 175, 141, 224, 174, 159, 224, 175, 139, 224, 174, 181, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 174, 191, 224, 174, 169, 224, 175, 141, 32, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 174, 191, 224, 174, 178, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 174, 191, 224, 174, 178, 224, 175, 129, 224, 174, 174, 224, 175, 141, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 175, 129, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 175, 129, 224, 174, 159, 224, 175, 136, 224, 174, 175, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 175, 129, 224, 174, 178, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 175, 136, 0, 8, 2, 224, 175, 139, 224, 174, 169, 224, 175, 141, 224, 174, 149, 224, 174, 179, 0, 8, 2, 224, 175, 139, 224, 174, 176, 224, 175, 141, 224, 174, 156, 224, 174, 176, 224, 174, 191, 0, 8, 128, 175, 224, 178, 174, 224, 149, 174, 224, 2, 224, 174, 190, 0, 8, 134, 174, 224, 2, 224, 174, 191, 224, 174, 154, 0, 8, 134, 174, 224, 2, 224, 174, 191, 224, 174, 184, 0, 8, 134, 174, 224, 2, 224, 175, 128, 224, 174, 154, 0, 8, 134, 174, 224, 2, 224, 175, 128, 224, 174, 184, 0, 8, 139, 175, 224, 154, 174, 224, 2, 224, 174, 190, 0, 8, 141, 175, 224, 159, 174, 224, 190, 174, 224, 179, 174, 224, 191, 174, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 176, 0, 8, 141, 175, 224, 169, 174, 224, 149, 174, 224, 2, 224, 174, 191, 224, 174, 149, 224, 174, 176, 0, 8, 141, 175, 224, 178, 174, 224, 134, 175, 224, 154, 174, 224, 2, 224, 175, 139, 224, 174, 169, 0, 8, 141, 175, 224, 178, 174, 224, 134, 175, 224, 170, 174, 224, 2, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 159, 0, 8, 141, 175, 224, 178, 174, 224, 134, 175, 224, 181, 174, 224, 2, 224, 175, 135, 224, 174, 176, 0, 8, 141, 175, 224, 178, 174, 224, 190, 174, 224, 159, 174, 224, 2, 224, 174, 191, 224, 174, 169, 0, 8, 149, 174, 224, 2, 224, 175, 135, 0, 8, 164, 174, 224, 141, 175, 224, 184, 174, 224, 129, 175, 224, 174, 174, 224, 2, 224, 174, 190, 0, 8, 190, 174, 224, 149, 174, 224, 2, 224, 174, 191, 0, 8, 190, 174, 224, 159, 174, 224, 149, 174, 224, 2, 224, 174, 191, 0, 8, 191, 174, 224, 154, 174, 224, 170, 174, 224, 2, 224, 174, 191, 224, 174, 149, 224, 175, 141, 0, 8, 191, 174, 224, 178, 174, 224, 149, 174, 224, 2, 224, 174, 190, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 153, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 159, 224, 174, 190, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 159, 224, 175, 141, 32, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 154, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 128, 224, 174, 175, 224, 174, 190, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 141, 224, 174, 184, 0, 224, 174, 191, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 183, 224, 175, 141, 0, 224, 174, 191, 8, 2, 224, 174, 178, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 176, 0, 224, 174, 191, 8, 2, 224, 174, 179, 224, 174, 190, 224, 174, 184, 224, 175, 141, 224, 174, 149, 224, 175, 141, 0, 224, 175, 129, 8, 2, 224, 174, 179, 224, 175, 139, 224, 174, 176, 224, 174, 169, 224, 175, 141, 224, 174, 184, 0, 224, 175, 129, 8, 2, 224, 174, 179, 224, 175, 139, 224, 174, 176, 224, 174, 191, 224, 174, 159, 224, 174, 190, 0, 224, 175, 141, 1, 134, 174, 224, 2, 224, 174, 149, 224, 174, 190, 224, 174, 169, 224, 174, 191, 224, 174, 175, 0, 224, 175, 141, 1, 134, 174, 224, 2, 224, 174, 149, 224, 174, 190, 224, 174, 169, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 164, 224, 174, 190, 224, 174, 169, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 153, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 159, 224, 174, 190, 224, 174, 149, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 159, 224, 175, 141, 32, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 154, 224, 174, 191, 224, 174, 184, 224, 175, 141, 224, 174, 149, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 174, 190, 224, 174, 169, 224, 175, 141, 224, 174, 184, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 128, 224, 174, 175, 224, 174, 190, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 158, 224, 175, 141, 224, 174, 154, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 176, 224, 175, 134, 224, 174, 183, 224, 175, 141, 0, 224, 175, 141, 8, 2, 224, 174, 178, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 154, 224, 174, 176, 0, 224, 175, 141, 8, 2, 224, 174, 179, 224, 175, 139, 224, 174, 176, 224, 174, 169, 224, 175, 141, 224, 174, 184, 0, 224, 175, 141, 8, 2, 224, 174, 179, 224, 175, 139, 224, 174, 176, 224, 174, 191, 224, 174, 159, 224, 174, 190, 0, 224, 175, 141, 8, 190, 174, 224, 154, 174, 224, 139, 175, 224, 176, 174, 224, 141, 175, 224, 149, 174, 224, 136, 175, 224, 174, 174, 224, 2, 224, 174, 159, 0, 224, 175, 141, 8, 191, 174, 224, 178, 174, 224, 2, 224, 174, 159, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 134, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 174, 191, 224, 174, 176, 8, 2, 224, 174, 163, 224, 175, 141, 224, 174, 159, 224, 175, 141, 224, 174, 184, 3, 81, 34, 36, 0, 224, 174, 191, 224, 174, 176, 224, 175, 134, 224, 174, 158, 224, 175, 141, 224, 174, 154, 8, 3, 81, 34, 36, 65, 74, 147, 0, 4, 224, 174, 191, 224, 174, 176, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 3, 81, 34, 36, 139, 34, 37, 49, 0, 224, 175, 141, 224, 174, 176, 224, 175, 134, 224, 174, 159, 224, 175, 141, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 8, 0, 224, 174, 191, 224, 174, 149, 1, 191, 174, 224, 178, 174, 224, 190, 174, 224, 181, 174, 224, 2, 224, 175, 135, 224, 174, 183, 224, 174, 169, 3, 81, 37, 49, 0, 224, 174, 191, 224, 174, 178, 224, 174, 191, 224, 174, 170, 8, 3, 81, 37, 55, 37, 48, 147, 0, 224, 175, 129, 224, 174, 159, 224, 175, 141, 224, 174, 170, 8, 2, 224, 174, 190, 224, 174, 178, 3, 81, 40, 138, 69, 0, 224, 175, 141, 224, 174, 159, 224, 175, 141, 8, 190, 174, 224, 154, 174, 224, 2, 224, 174, 181, 224, 175, 135, 224, 174, 176, 3, 81, 47, 0, 224, 174, 191, 224, 174, 179, 8, 2, 224, 175, 136, 224, 174, 159, 224, 175, 141, 3, 81, 62, 0, 4, 224, 174, 191, 224, 174, 179, 224, 174, 190, 224, 174, 170, 224, 175, 141, 8, 3, 81, 62, 116, 48, 0, 224, 175, 141, 224, 174, 179, 224, 174, 190, 224, 174, 170, 224, 175, 141, 8, 0, 4, 8, 2, 224, 174, 149, 224, 175, 141, 224, 174, 176, 224, 175, 129, 224, 174, 164, 224, 175, 128, 224, 174, 169, 3, 81, 107, 0, 8, 2, 224, 174, 169, 224, 174, 178, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 191, 224, 174, 154, 224, 175, 141, 224, 174, 154, 224, 174, 176, 0, 8, 2, 224, 174, 176, 224, 175, 141, 224, 174, 178, 224, 174, 190, 224, 174, 153, 224, 175, 141, 0, 8, 141, 175, 224, 169, 174, 224, 149, 174, 224, 2, 224, 174, 176, 224, 175, 141, 224, 174, 174, 0, 224, 175, 141, 224, 174, 170, 1, 134, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 1, 190, 174, 224, 169, 174, 224, 141, 175, 224, 169, 174, 224, 134, 175, 224, 164, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 175, 141, 224, 174, 170, 224, 174, 191, 1, 190, 174, 224, 169, 174, 224, 141, 175, 224, 169, 174, 224, 134, 175, 224, 164, 174, 224, 2, 224, 174, 176, 224, 174, 191, 224, 174, 149, 224, 175, 141, 224, 174, 149, 0, 224, 174, 176, 224, 175, 141, 224, 174, 169, 224, 174, 191, 224, 174, 154, 8, 2, 224, 174, 176, 3, 81, 107, 34, 50, 37, 74, 107, 0, 224, 174, 176, 224, 175, 130, 224, 174, 149, 224, 175, 141, 8, 3, 81, 107, 34, 150, 49, 0, 224, 174, 190, 224, 174, 164, 8, 2, 224, 174, 191, 224, 174, 174, 224, 174, 190, 3, 81, 116, 47, 0, 224, 174, 190, 224, 174, 178, 224, 175, 141, 224, 174, 159, 8, 191, 174, 224, 159, 174, 224, 3, 81, 116, 55, 138, 147, 0, 4, 224, 174, 181, 224, 175, 129, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 2, 224, 174, 169, 3, 81, 133, 64, 138, 107, 0, 224, 175, 140, 224, 174, 163, 224, 175, 141, 224, 174, 159, 8, 2, 224, 174, 169, 0, 4, 1, 141, 175, 224, 178, 174, 224, 190, 174, 224, 159, 174, 224, 133, 174, 224, 3, 81, 147, 0, 8, 128, 175, 224, 176, 174, 224, 134, 175, 224, 183, 174, 224, 2, 12, 0, 7, 6, 1, 47, 0, 4, 2, 17, 66, 3, 63, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 175, 130, 0, 224, 174, 191, 8, 18, 72, 154, 174, 224, 2, 224, 174, 175, 0, 3, 63, 107, 0, 7, 6, 1, 48, 0, 2, 17, 66, 3, 57, 0, 3, 57, 107, 0, 7, 6, 1, 49, 0, 4, 2, 17, 66, 3, 34, 0, 224, 174, 191, 8, 164, 174, 224, 191, 174, 224, 168, 174, 224, 2, 224, 174, 154, 224, 174, 169, 0, 224, 174, 191, 8, 174, 174, 224, 191, 174, 224, 181, 174, 224, 2, 224, 174, 154, 0, 224, 175, 129, 1, 191, 174, 224, 164, 174, 224, 133, 174, 224, 2, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 224, 175, 129, 8, 191, 174, 224, 164, 174, 224, 176, 174, 224, 129, 175, 224, 164, 174, 224, 2, 224, 174, 183, 224, 175, 141, 224, 174, 159, 0, 3, 34, 107, 0, 7, 6, 1, 50, 0, 2, 17, 66, 3, 51, 0, 3, 51, 107, 0, 224, 175, 141, 224, 174, 154, 3, 74, 12, 147, 0, 224, 175, 141, 2, 224, 174, 177, 3, 138, 0, 7, 6, 1, 51, 0, 224, 175, 141, 224, 174, 170, 8, 175, 174, 224, 134, 175, 224, 154, 174, 224, 3, 51, 48, 147, 0, 2, 17, 66, 3, 55, 0, 3, 55, 107, 0, 224, 175, 141, 8, 181, 174, 224, 190, 174, 224, 149, 174, 224, 2, 224, 174, 164, 224, 175, 129, 224, 174, 177, 224, 175, 136, 3, 138, 0, 7, 6, 1, 52, 0, 2, 17, 66, 3, 62, 0, 3, 62, 107, 0, 224, 175, 141, 1, 137, 174, 224, 2, 224, 174, 164, 224, 175, 129, 224, 174, 177, 224, 175, 136, 3, 138, 0, 224, 175, 141, 224, 174, 164, 8, 149, 174, 224, 141, 175, 224, 149, 174, 224, 174, 174, 224, 2, 224, 175, 138, 224, 174, 149, 224, 175, 136, 3, 138, 47, 0, 7, 6, 1, 53, 0, 2, 17, 66, 3, 90, 0, 3, 90, 107, 0, 7, 6, 1, 54, 0, 4, 2, 17, 66, 3, 82, 0, 224, 174, 191, 2, 224, 174, 175, 224, 175, 130, 224, 174, 149, 0, 224, 174, 191, 8, 2, 224, 174, 175, 224, 174, 190, 0, 3, 82, 107, 0, 7, 6, 1, 55, 0, 2, 17, 66, 3, 89, 0, 3, 89, 107, 0, 7, 6, 1, 56, 0, 2, 17, 66, 3, 91, 0, 3, 91, 107, 0, 7, 6, 1, 57, 0, 2, 17, 66, 3, 87, 0, 3, 87, 107, 0, 7, 6, 1, 58, 0, 2, 17, 66, 3, 106, 0, 3, 106, 107, 0, 7, 6, 1, 78, 0, 4, 3, 148, 0, 2, 32, 0, 7, 6, 224, 164, 0, 3, 21, 104, 105, 0, 7, 6, 224, 165, 0, 3, 21, 104, 105, 0, 7, 6, 224, 174, 0, 130, 3, 0, 137, 224, 174, 176, 224, 175, 129, 224, 174, 164, 224, 175, 141, 224, 174, 164, 2, 224, 174, 191, 224, 174, 176, 224, 174, 190, 3, 34, 120, 70, 70, 0, 133, 3, 35, 0, 142, 3, 36, 0, 191, 3, 37, 0, 142, 8, 3, 38, 36, 0, 143, 8, 3, 38, 112, 0, 142, 224, 174, 170, 2, 224, 175, 141, 224, 174, 176, 224, 174, 178, 3, 38, 112, 48, 0, 146, 3, 39, 0, 148, 224, 174, 191, 3, 39, 62, 37, 0, 137, 3, 40, 0, 136, 3, 110, 0, 143, 3, 112, 0, 4, 134, 3, 116, 0, 190, 0, 147, 3, 117, 0, 138, 3, 121, 0, 144, 3, 132, 0, 4, 146, 224, 174, 179, 2, 224, 174, 159, 224, 174, 164, 3, 133, 0, 146, 224, 174, 179, 2, 224, 174, 176, 224, 174, 153, 224, 175, 141, 224, 174, 149, 0, 146, 224, 174, 179, 2, 224, 174, 181, 224, 175, 136, 0, 146, 224, 174, 179, 2, 224, 174, 183, 224, 174, 164, 0, 148, 0, 7, 6, 224, 175, 0, 151, 3, 12, 0, 134, 3, 36, 0, 4, 140, 224, 174, 191, 1, 181, 174, 224, 3, 36, 62, 37, 0, 140, 224, 174, 191, 8, 164, 174, 224, 0, 138, 3, 39, 0, 129, 3, 40, 0, 128, 3, 110, 0, 135, 3, 112, 0, 139, 3, 117, 0, 130, 3, 121, 0, 136, 3, 132, 0, 4, 134, 224, 174, 179, 8, 154, 174, 224, 3, 133, 0, 134, 224, 174, 179, 8, 170, 174, 224, 0, 134, 224, 174, 179, 8, 174, 174, 224, 2, 224, 174, 169, 0, 134, 224, 174, 179, 8, 174, 174, 224, 2, 224, 174, 184, 0, 134, 224, 174, 179, 8, 181, 174, 224, 2, 224, 174, 181, 224, 174, 190, 224, 174, 178, 0, 140, 0, 7, 6, 0, 224, 175, 141, 3, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 46, 1, 15, 2, 15, 12, 3, 10, 48, 40, 62, 62, 37, 0, 114, 115, 1, 19, 2, 32, 46, 15, 3, 34, 121, 48, 110, 86, 0, 45, 8, 32, 2, 32, 15, 3, 49, 107, 90, 37, 47, 47, 107, 55, 0, 36, 3, 70, 39, 55, 107, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts58 = FileInMemory_createWithData (78961, reinterpret_cast (&espeakdata_dicts58_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ta_dict", L"ta"); Collection_addItem (me.peek(), espeakdata_dicts58.transfer()); static unsigned char espeakdata_dicts59_data[3365] = { 0, 4, 0, 0, 164, 9, 0, 0, 0, 0, 0, 0, 0, 6, 65, 4, 112, 57, 0, 0, 0, 0, 0, 6, 65, 8, 69, 110, 0, 0, 0, 0, 0, 6, 65, 12, 87, 110, 0, 0, 0, 0, 0, 6, 65, 16, 70, 110, 0, 0, 0, 0, 0, 5, 65, 20, 110, 0, 0, 0, 0, 0, 6, 65, 24, 114, 81, 0, 0, 0, 0, 0, 6, 65, 28, 73, 110, 0, 0, 0, 0, 0, 6, 65, 32, 112, 74, 0, 0, 0, 0, 0, 6, 65, 36, 116, 57, 0, 0, 9, 1, 37, 95, 116, 47, 35, 63, 0, 0, 0, 0, 7, 65, 40, 73, 112, 57, 0, 0, 0, 12, 1, 42, 50, 35, 49, 91, 35, 47, 34, 35, 0, 0, 10, 1, 43, 49, 121, 139, 37, 49, 35, 0, 0, 7, 65, 44, 49, 112, 57, 0, 0, 0, 0, 8, 1, 47, 87, 55, 116, 91, 0, 0, 6, 65, 48, 114, 55, 0, 0, 0, 0, 0, 6, 65, 52, 114, 63, 0, 0, 0, 0, 0, 6, 65, 56, 114, 50, 0, 0, 0, 0, 0, 5, 65, 60, 117, 0, 0, 0, 0, 0, 6, 65, 64, 48, 110, 0, 0, 0, 0, 0, 7, 65, 68, 49, 57, 121, 0, 0, 0, 0, 0, 6, 65, 72, 116, 34, 0, 0, 0, 0, 0, 6, 65, 76, 114, 87, 0, 0, 0, 0, 14, 4, 95, 48, 67, 48, 82, 35, 50, 70, 35, 55, 40, 0, 0, 6, 65, 80, 136, 110, 0, 0, 0, 0, 0, 6, 65, 84, 57, 121, 0, 0, 0, 0, 0, 6, 65, 88, 82, 110, 0, 0, 0, 0, 0, 13, 1, 92, 69, 57, 116, 49, 35, 87, 55, 116, 91, 0, 11, 65, 92, 70, 107, 69, 107, 55, 57, 121, 0, 0, 0, 0, 0, 15, 4, 95, 49, 77, 49, 39, 49, 35, 82, 36, 57, 57, 37, 0, 7, 65, 96, 114, 49, 87, 0, 0, 12, 4, 95, 49, 77, 50, 55, 35, 49, 91, 35, 0, 0, 11, 4, 95, 49, 77, 51, 49, 39, 47, 37, 0, 0, 0, 7, 65, 100, 58, 116, 57, 0, 0, 0, 0, 0, 7, 65, 104, 86, 114, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 4, 16, 20, 10, 70, 4, 35, 95, 116, 63, 49, 35, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 5, 95, 48, 77, 50, 24, 55, 35, 49, 91, 35, 55, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 176, 163, 224, 177, 141, 37, 64, 0, 11, 6, 224, 176, 155, 224, 177, 141, 37, 142, 0, 12, 5, 95, 48, 77, 49, 24, 82, 36, 55, 40, 0, 0, 0, 0, 0, 11, 6, 224, 176, 185, 224, 177, 141, 37, 105, 0, 11, 6, 224, 176, 161, 224, 177, 141, 37, 139, 0, 11, 6, 224, 176, 153, 224, 177, 141, 37, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 5, 95, 48, 77, 51, 24, 49, 39, 47, 55, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 176, 179, 224, 177, 141, 37, 62, 0, 11, 6, 224, 176, 171, 224, 177, 141, 37, 134, 0, 0, 0, 0, 0, 12, 6, 224, 177, 153, 224, 177, 141, 37, 70, 86, 0, 11, 6, 224, 176, 177, 224, 177, 141, 37, 34, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 176, 183, 224, 177, 141, 37, 91, 0, 11, 6, 224, 176, 159, 224, 177, 141, 37, 138, 0, 11, 6, 224, 176, 151, 224, 177, 141, 37, 79, 0, 0, 0, 0, 0, 11, 6, 224, 176, 181, 224, 177, 141, 37, 82, 0, 11, 6, 224, 176, 157, 224, 177, 141, 37, 143, 0, 11, 6, 224, 176, 149, 224, 177, 141, 37, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 95, 49, 1, 39, 49, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 176, 175, 224, 177, 141, 37, 57, 0, 11, 6, 224, 176, 167, 224, 177, 141, 37, 137, 0, 0, 0, 0, 0, 11, 6, 224, 176, 173, 224, 177, 141, 37, 135, 0, 11, 6, 224, 176, 165, 224, 177, 141, 37, 136, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 51, 88, 63, 40, 48, 48, 132, 0, 0, 13, 3, 95, 48, 67, 82, 35, 50, 70, 35, 55, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 49, 67, 39, 49, 35, 82, 35, 50, 70, 35, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 49, 57, 48, 35, 63, 70, 39, 63, 63, 35, 70, 37, 0, 0, 17, 3, 95, 49, 56, 48, 35, 70, 137, 36, 50, 37, 63, 37, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 49, 49, 48, 35, 70, 35, 49, 39, 50, 139, 40, 0, 0, 0, 14, 3, 95, 49, 51, 48, 35, 70, 35, 63, 121, 139, 121, 0, 0, 14, 3, 95, 49, 50, 48, 35, 50, 50, 36, 63, 139, 40, 0, 0, 14, 3, 95, 49, 53, 48, 35, 70, 37, 105, 112, 50, 40, 0, 0, 15, 3, 95, 49, 52, 48, 35, 137, 50, 116, 55, 40, 79, 40, 0, 0, 14, 3, 95, 49, 55, 48, 35, 70, 37, 105, 112, 139, 40, 0, 0, 14, 3, 95, 49, 54, 48, 35, 70, 35, 105, 116, 34, 40, 0, 0, 0, 11, 3, 95, 55, 88, 139, 36, 135, 69, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 49, 88, 48, 35, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 50, 88, 37, 34, 35, 82, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 63, 63, 35, 49, 91, 35, 34, 35, 63, 0, 0, 0, 0, 12, 3, 95, 52, 88, 50, 35, 55, 40, 135, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 95, 53, 88, 57, 116, 135, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 54, 88, 35, 34, 35, 82, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 56, 88, 57, 36, 50, 35, 135, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 57, 88, 47, 39, 63, 135, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 48, 77, 50, 55, 35, 49, 91, 35, 55, 35, 0, 0, 12, 4, 95, 48, 77, 51, 49, 39, 47, 55, 35, 0, 0, 0, 6, 131, 224, 176, 134, 76, 11, 4, 95, 48, 77, 49, 82, 36, 55, 35, 0, 0, 0, 8, 3, 224, 177, 140, 146, 133, 0, 0, 11, 3, 224, 177, 141, 82, 39, 47, 47, 40, 0, 6, 131, 224, 176, 133, 76, 0, 8, 3, 224, 177, 138, 18, 39, 0, 8, 3, 224, 176, 130, 35, 50, 0, 0, 9, 3, 224, 177, 139, 146, 117, 12, 0, 8, 3, 224, 176, 131, 35, 105, 0, 0, 8, 3, 224, 177, 136, 146, 132, 0, 0, 8, 3, 224, 176, 129, 35, 63, 0, 0, 8, 3, 224, 177, 134, 18, 36, 0, 0, 9, 3, 224, 177, 135, 146, 112, 12, 0, 0, 9, 3, 224, 177, 132, 146, 34, 121, 0, 0, 0, 9, 3, 224, 177, 130, 146, 121, 12, 0, 0, 9, 3, 224, 177, 131, 18, 34, 40, 0, 0, 9, 3, 224, 177, 128, 146, 110, 12, 0, 0, 8, 3, 224, 177, 129, 18, 40, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 224, 176, 166, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 224, 176, 190, 146, 116, 12, 0, 0, 8, 3, 224, 176, 191, 18, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 2, 194, 169, 49, 116, 48, 110, 34, 132, 138, 0, 0, 9, 2, 194, 182, 82, 112, 34, 116, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 176, 156, 224, 177, 141, 37, 77, 0, 0, 0, 0, 0, 11, 6, 224, 176, 162, 224, 177, 141, 37, 141, 0, 11, 6, 224, 176, 154, 224, 177, 141, 37, 78, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 176, 160, 224, 177, 141, 37, 140, 0, 0, 0, 0, 0, 17, 2, 95, 33, 116, 95, 78, 35, 34, 57, 116, 34, 136, 35, 49, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 6, 224, 176, 172, 224, 177, 141, 37, 69, 0, 11, 6, 224, 176, 164, 224, 177, 141, 37, 47, 0, 10, 2, 95, 45, 105, 132, 81, 35, 50, 0, 0, 9, 2, 95, 44, 49, 116, 63, 116, 0, 0, 9, 2, 95, 51, 63, 121, 139, 40, 0, 0, 10, 2, 95, 50, 34, 36, 50, 139, 40, 0, 0, 11, 6, 224, 176, 178, 224, 177, 141, 37, 55, 0, 11, 6, 224, 176, 170, 224, 177, 141, 37, 48, 0, 10, 2, 95, 49, 39, 49, 35, 138, 37, 0, 0, 10, 2, 95, 48, 87, 40, 50, 50, 35, 0, 0, 8, 2, 95, 55, 112, 139, 40, 0, 0, 8, 2, 95, 54, 116, 34, 40, 0, 0, 8, 2, 95, 53, 132, 70, 40, 0, 0, 10, 2, 95, 52, 50, 116, 55, 79, 40, 0, 0, 14, 2, 95, 59, 87, 36, 63, 110, 49, 117, 55, 35, 50, 0, 0, 10, 2, 95, 58, 49, 117, 55, 35, 50, 0, 0, 12, 2, 95, 57, 47, 39, 63, 63, 37, 70, 37, 0, 0, 13, 2, 95, 56, 38, 36, 50, 37, 63, 37, 70, 37, 0, 0, 16, 2, 95, 63, 48, 34, 35, 95, 50, 116, 34, 136, 35, 49, 35, 0, 0, 0, 12, 6, 224, 177, 152, 224, 177, 141, 37, 47, 87, 0, 11, 6, 224, 176, 184, 224, 177, 141, 37, 87, 0, 11, 6, 224, 176, 176, 224, 177, 141, 37, 34, 0, 11, 6, 224, 176, 152, 224, 177, 141, 37, 145, 0, 0, 0, 0, 0, 11, 6, 224, 176, 182, 224, 177, 141, 37, 95, 0, 11, 6, 224, 176, 158, 224, 177, 141, 37, 65, 0, 11, 6, 224, 176, 150, 224, 177, 141, 37, 144, 0, 9, 134, 224, 176, 146, 224, 176, 149, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 2, 95, 95, 35, 63, 139, 35, 34, 15, 87, 49, 117, 34, 0, 0, 0, 11, 6, 224, 176, 168, 224, 177, 141, 37, 50, 0, 0, 0, 0, 0, 11, 6, 224, 176, 174, 224, 177, 141, 37, 63, 0, 11, 6, 224, 176, 166, 224, 177, 141, 37, 70, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 102, 12, 0, 0, 48, 0, 0, 0, 103, 12, 0, 0, 49, 0, 0, 0, 104, 12, 0, 0, 50, 0, 0, 0, 105, 12, 0, 0, 51, 0, 0, 0, 106, 12, 0, 0, 52, 0, 0, 0, 107, 12, 0, 0, 53, 0, 0, 0, 108, 12, 0, 0, 54, 0, 0, 0, 109, 12, 0, 0, 55, 0, 0, 0, 110, 12, 0, 0, 56, 0, 0, 0, 111, 12, 0, 0, 57, 0, 0, 0, 0, 0, 0, 0, 6, 1, 6, 0, 3, 35, 0, 7, 6, 1, 7, 0, 3, 116, 0, 7, 6, 1, 8, 0, 3, 37, 0, 7, 6, 1, 9, 0, 3, 110, 0, 7, 6, 1, 10, 0, 3, 40, 0, 7, 6, 1, 11, 0, 3, 121, 0, 7, 6, 1, 12, 0, 3, 34, 40, 0, 7, 6, 1, 13, 0, 3, 45, 0, 7, 6, 1, 15, 0, 3, 36, 0, 8, 3, 38, 36, 0, 7, 6, 1, 16, 0, 3, 112, 0, 7, 6, 1, 17, 0, 3, 132, 0, 7, 6, 1, 19, 0, 3, 39, 0, 7, 6, 1, 20, 0, 3, 117, 0, 7, 6, 1, 21, 0, 3, 133, 0, 7, 6, 1, 22, 0, 2, 17, 66, 3, 49, 0, 3, 49, 35, 0, 7, 6, 1, 23, 0, 2, 17, 66, 3, 144, 0, 3, 144, 35, 0, 7, 6, 1, 24, 0, 2, 17, 66, 3, 79, 0, 3, 79, 35, 0, 7, 6, 1, 25, 0, 2, 17, 66, 3, 145, 0, 3, 145, 35, 0, 7, 6, 1, 26, 0, 2, 17, 66, 3, 66, 0, 3, 66, 35, 0, 7, 6, 1, 27, 0, 2, 17, 66, 3, 78, 0, 3, 78, 35, 0, 7, 6, 1, 28, 0, 2, 17, 66, 3, 142, 0, 3, 142, 35, 0, 7, 6, 1, 29, 0, 2, 17, 66, 3, 77, 0, 3, 77, 35, 0, 7, 6, 1, 30, 0, 2, 17, 66, 3, 143, 0, 3, 143, 35, 0, 7, 6, 1, 31, 0, 2, 17, 66, 3, 65, 0, 3, 65, 35, 0, 7, 6, 1, 32, 0, 2, 17, 66, 3, 138, 0, 3, 138, 35, 0, 7, 6, 1, 33, 0, 2, 17, 66, 3, 140, 0, 3, 140, 35, 0, 7, 6, 1, 34, 0, 2, 17, 66, 3, 139, 0, 3, 139, 35, 0, 7, 6, 1, 35, 0, 2, 17, 66, 3, 141, 0, 3, 141, 35, 0, 7, 6, 1, 36, 0, 2, 17, 66, 3, 64, 0, 3, 64, 35, 0, 7, 6, 1, 37, 0, 2, 17, 66, 3, 47, 0, 3, 47, 35, 0, 7, 6, 1, 38, 0, 2, 17, 66, 3, 136, 0, 3, 136, 35, 0, 7, 6, 1, 39, 0, 2, 17, 66, 3, 70, 0, 3, 70, 35, 0, 7, 6, 1, 40, 0, 2, 17, 66, 3, 137, 0, 3, 137, 35, 0, 7, 6, 1, 41, 0, 2, 17, 66, 3, 50, 0, 3, 50, 35, 0, 7, 6, 1, 43, 0, 2, 17, 66, 3, 48, 0, 3, 48, 35, 0, 7, 6, 1, 44, 0, 2, 17, 66, 3, 134, 0, 3, 134, 35, 0, 7, 6, 1, 45, 0, 2, 17, 66, 3, 69, 0, 3, 69, 35, 0, 7, 6, 1, 46, 0, 2, 17, 66, 3, 135, 0, 3, 135, 35, 0, 7, 6, 1, 47, 0, 2, 17, 66, 3, 63, 0, 3, 63, 35, 0, 7, 6, 1, 48, 0, 2, 17, 66, 3, 57, 0, 3, 57, 35, 0, 7, 6, 1, 49, 0, 2, 17, 66, 3, 34, 0, 3, 34, 35, 0, 7, 6, 1, 50, 0, 2, 17, 66, 3, 34, 0, 3, 34, 35, 0, 7, 6, 1, 51, 0, 2, 17, 66, 3, 55, 0, 3, 55, 35, 0, 7, 6, 1, 52, 0, 2, 17, 66, 3, 62, 0, 3, 62, 35, 0, 7, 6, 1, 54, 0, 2, 17, 66, 3, 82, 0, 3, 82, 35, 0, 7, 6, 1, 55, 0, 2, 17, 66, 3, 95, 0, 3, 95, 35, 0, 7, 6, 1, 56, 0, 2, 17, 66, 3, 91, 0, 3, 91, 35, 0, 7, 6, 1, 57, 0, 2, 17, 66, 3, 87, 0, 3, 87, 35, 0, 7, 6, 1, 58, 0, 2, 17, 66, 3, 105, 0, 3, 105, 35, 0, 7, 6, 1, 89, 0, 2, 17, 66, 3, 47, 87, 0, 3, 47, 87, 35, 0, 7, 6, 1, 90, 0, 2, 17, 66, 3, 70, 86, 0, 3, 70, 86, 35, 0, 7, 6, 1, 97, 0, 3, 34, 40, 0, 7, 6, 1, 98, 0, 3, 45, 0, 7, 6, 224, 164, 0, 3, 21, 104, 105, 0, 7, 6, 224, 165, 0, 3, 21, 104, 105, 0, 7, 6, 224, 176, 0, 191, 3, 37, 0, 130, 3, 63, 0, 131, 3, 105, 0, 190, 3, 116, 0, 7, 6, 224, 177, 0, 141, 3, 0, 4, 149, 3, 12, 0, 150, 0, 131, 3, 34, 40, 0, 134, 3, 36, 0, 138, 3, 39, 0, 129, 3, 40, 0, 132, 3, 44, 12, 0, 128, 3, 110, 0, 135, 3, 112, 0, 139, 3, 117, 0, 130, 3, 121, 0, 136, 3, 132, 0, 140, 3, 133, 0, 7, 6, 0, 36, 3, 139, 116, 55, 35, 34, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts59 = FileInMemory_createWithData (3364, reinterpret_cast (&espeakdata_dicts59_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/te_dict", L"te"); Collection_addItem (me.peek(), espeakdata_dicts59.transfer()); static unsigned char espeakdata_dicts60_data[3073] = { 0, 4, 0, 0, 24, 10, 0, 0, 0, 0, 0, 0, 0, 32, 4, 95, 56, 77, 49, 70, 37, 49, 6, 36, 47, 36, 6, 113, 36, 6, 69, 39, 6, 34, 39, 69, 35, 6, 69, 39, 69, 36, 70, 37, 0, 5, 65, 4, 35, 0, 0, 41, 4, 95, 56, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 6, 69, 39, 6, 34, 39, 69, 35, 6, 69, 39, 69, 36, 70, 37, 12, 0, 0, 0, 0, 9, 65, 8, 69, 37, 12, 37, 12, 0, 0, 0, 0, 0, 9, 65, 12, 87, 37, 12, 37, 12, 0, 0, 0, 0, 0, 9, 65, 16, 70, 37, 12, 37, 12, 0, 0, 0, 0, 0, 8, 65, 20, 37, 12, 37, 12, 0, 0, 0, 0, 0, 8, 65, 24, 36, 12, 81, 39, 0, 0, 0, 0, 0, 8, 65, 28, 79, 37, 12, 37, 0, 0, 0, 0, 7, 195, 44, 19, 129, 72, 8, 6, 195, 48, 243, 129, 76, 0, 8, 65, 32, 36, 37, 74, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 65, 40, 73, 6, 36, 37, 0, 0, 0, 0, 0, 7, 65, 44, 49, 36, 37, 0, 0, 0, 0, 0, 8, 65, 48, 36, 12, 55, 37, 0, 0, 0, 0, 0, 8, 65, 52, 6, 36, 63, 40, 0, 0, 0, 0, 0, 11, 5, 95, 48, 1, 14, 4, 23, 50, 35, 0, 8, 65, 56, 6, 36, 50, 37, 0, 0, 0, 0, 0, 8, 65, 60, 39, 12, 39, 12, 0, 0, 0, 0, 0, 10, 65, 64, 48, 6, 37, 12, 37, 12, 0, 0, 0, 0, 0, 7, 65, 68, 49, 57, 40, 0, 0, 0, 0, 0, 7, 65, 72, 35, 53, 36, 0, 0, 0, 0, 0, 9, 65, 76, 6, 36, 12, 87, 37, 0, 0, 0, 7, 195, 20, 225, 64, 76, 28, 0, 0, 10, 65, 80, 47, 6, 37, 12, 37, 12, 0, 0, 0, 0, 0, 8, 65, 84, 40, 12, 40, 12, 0, 0, 0, 0, 0, 10, 65, 88, 82, 6, 37, 12, 37, 12, 0, 0, 0, 0, 6, 195, 28, 18, 193, 76, 6, 195, 92, 18, 193, 76, 0, 11, 65, 92, 70, 35, 69, 39, 55, 57, 40, 0, 0, 0, 0, 0, 17, 4, 95, 49, 77, 49, 23, 6, 87, 20, 6, 37, 49, 36, 47, 36, 0, 10, 65, 96, 36, 49, 6, 36, 87, 36, 0, 0, 25, 4, 95, 49, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 55, 36, 49, 104, 6, 39, 12, 55, 39, 0, 0, 0, 0, 8, 65, 100, 58, 6, 35, 37, 0, 0, 0, 0, 0, 10, 65, 104, 86, 6, 36, 12, 47, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 4, 95, 49, 67, 48, 55, 36, 49, 104, 6, 39, 55, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 196, 44, 243, 148, 20, 72, 8, 7, 196, 48, 83, 142, 4, 76, 0, 0, 6, 195, 16, 147, 15, 76, 0, 0, 6, 195, 52, 243, 5, 76, 0, 0, 0, 0, 0, 19, 4, 95, 50, 77, 49, 70, 37, 49, 6, 36, 47, 36, 48, 6, 36, 70, 37, 0, 0, 30, 4, 95, 50, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 48, 6, 36, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 45, 112, 76, 4, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 24, 16, 72, 28, 6, 194, 24, 16, 72, 28, 0, 0, 0, 0, 0, 0, 19, 4, 95, 4, 16, 20, 81, 36, 12, 104, 36, 55, 40, 6, 35, 12, 50, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 51, 77, 49, 70, 37, 49, 6, 36, 47, 36, 47, 6, 35, 12, 53, 39, 0, 0, 31, 4, 95, 51, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 47, 6, 35, 12, 53, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 4, 240, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 100, 243, 129, 76, 28, 7, 195, 100, 243, 129, 76, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 56, 224, 64, 76, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 4, 95, 53, 77, 49, 70, 37, 49, 6, 36, 47, 36, 103, 6, 35, 12, 50, 39, 0, 0, 0, 0, 30, 4, 95, 53, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 103, 6, 35, 50, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 51, 88, 63, 35, 87, 6, 39, 12, 63, 36, 6, 35, 63, 35, 12, 53, 39, 0, 0, 14, 3, 95, 48, 67, 55, 36, 49, 104, 6, 39, 55, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 48, 16, 72, 28, 0, 0, 19, 3, 95, 50, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 48, 36, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 51, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 47, 6, 35, 12, 53, 39, 0, 0, 0, 0, 26, 4, 95, 54, 77, 49, 70, 37, 49, 6, 36, 47, 36, 113, 6, 36, 6, 47, 105, 6, 35, 47, 35, 34, 39, 0, 0, 0, 0, 35, 4, 95, 54, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 6, 47, 105, 6, 35, 6, 47, 35, 34, 39, 0, 0, 23, 3, 95, 55, 88, 63, 35, 87, 6, 39, 12, 63, 36, 6, 35, 6, 89, 6, 40, 12, 48, 35, 0, 0, 19, 3, 95, 52, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 6, 42, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 53, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 103, 6, 35, 12, 50, 39, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 49, 88, 55, 36, 87, 6, 39, 12, 63, 36, 0, 0, 24, 3, 95, 54, 67, 23, 63, 35, 49, 104, 6, 39, 55, 39, 6, 47, 105, 6, 35, 47, 35, 34, 39, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 50, 88, 63, 35, 87, 6, 39, 12, 63, 36, 48, 36, 70, 37, 0, 0, 20, 3, 95, 55, 67, 63, 35, 49, 104, 6, 39, 55, 39, 89, 6, 40, 12, 48, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 32, 3, 95, 56, 67, 63, 35, 49, 104, 6, 39, 55, 39, 6, 35, 6, 63, 35, 6, 34, 39, 69, 35, 6, 69, 39, 69, 36, 70, 37, 12, 0, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 52, 88, 63, 35, 87, 6, 39, 12, 63, 36, 6, 35, 63, 35, 12, 50, 36, 0, 0, 34, 3, 95, 57, 67, 63, 35, 49, 104, 6, 39, 55, 39, 6, 35, 6, 63, 35, 6, 34, 39, 69, 35, 6, 69, 39, 6, 50, 6, 50, 79, 58, 36, 0, 0, 0, 0, 0, 0, 0, 6, 194, 48, 80, 72, 8, 0, 24, 3, 95, 53, 88, 63, 35, 87, 6, 39, 12, 63, 36, 6, 35, 63, 35, 103, 6, 35, 12, 50, 39, 0, 0, 0, 0, 0, 0, 0, 0, 0, 24, 3, 95, 54, 88, 63, 35, 87, 6, 39, 12, 63, 36, 6, 35, 47, 105, 6, 35, 47, 35, 34, 39, 0, 0, 0, 0, 0, 19, 4, 95, 55, 77, 49, 70, 37, 49, 6, 36, 47, 36, 89, 40, 12, 48, 35, 0, 0, 0, 0, 30, 4, 95, 55, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 89, 40, 12, 48, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 29, 3, 95, 56, 88, 63, 35, 87, 6, 39, 12, 63, 36, 6, 35, 69, 39, 6, 34, 39, 69, 35, 6, 69, 36, 70, 37, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 29, 3, 95, 57, 88, 63, 35, 87, 6, 39, 12, 63, 36, 6, 35, 6, 34, 39, 69, 35, 6, 69, 39, 6, 50, 79, 58, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 72, 243, 129, 76, 7, 195, 92, 83, 129, 76, 28, 7, 195, 8, 243, 129, 72, 28, 16, 4, 95, 48, 77, 52, 23, 69, 37, 55, 37, 6, 39, 50, 37, 0, 0, 0, 0, 16, 4, 95, 48, 77, 51, 23, 63, 37, 55, 37, 6, 39, 50, 37, 0, 0, 0, 16, 4, 95, 48, 77, 49, 6, 87, 20, 6, 37, 49, 36, 47, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 81, 50, 1, 44, 16, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 4, 95, 3, 9, 18, 49, 6, 36, 81, 35, 0, 41, 4, 95, 57, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 6, 69, 39, 6, 34, 39, 69, 35, 6, 69, 39, 6, 50, 79, 58, 36, 0, 0, 0, 0, 33, 4, 95, 57, 77, 49, 70, 37, 49, 6, 36, 47, 36, 6, 113, 36, 6, 69, 39, 6, 34, 39, 69, 35, 6, 69, 39, 6, 50, 79, 58, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 52, 240, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 45, 85, 193, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 196, 57, 68, 215, 4, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 196, 44, 115, 204, 60, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 92, 16, 72, 28, 0, 0, 0, 0, 0, 0, 6, 195, 56, 22, 65, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 45, 112, 64, 72, 28, 7, 195, 45, 112, 64, 72, 28, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 28, 4, 95, 52, 77, 50, 70, 37, 49, 6, 36, 47, 36, 74, 36, 63, 35, 49, 104, 6, 39, 12, 55, 39, 42, 50, 36, 0, 0, 17, 4, 95, 52, 77, 49, 70, 37, 49, 6, 36, 47, 36, 42, 50, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 2, 95, 51, 47, 6, 35, 12, 53, 39, 0, 0, 10, 2, 95, 50, 48, 6, 36, 70, 37, 0, 0, 12, 2, 95, 49, 50, 6, 50, 79, 58, 36, 12, 0, 0, 13, 2, 95, 48, 55, 36, 81, 6, 36, 12, 55, 35, 0, 0, 11, 2, 95, 55, 87, 6, 40, 12, 48, 35, 0, 0, 13, 2, 95, 54, 47, 105, 6, 35, 47, 35, 34, 39, 0, 0, 11, 2, 95, 53, 103, 6, 35, 12, 50, 39, 0, 0, 9, 2, 95, 52, 6, 42, 50, 36, 0, 0, 0, 0, 16, 2, 95, 57, 34, 39, 69, 35, 6, 50, 6, 50, 79, 58, 36, 0, 0, 6, 194, 100, 16, 72, 28, 16, 2, 95, 56, 34, 39, 69, 35, 6, 69, 39, 69, 36, 70, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 52, 209, 64, 72, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 97, 0, 4, 3, 35, 0, 2, 32, 0, 8, 2, 17, 67, 0, 8, 17, 67, 0, 4, 2, 115, 3, 35, 12, 0, 97, 0, 7, 6, 98, 0, 3, 69, 0, 3, 80, 0, 7, 6, 99, 0, 3, 49, 0, 104, 3, 74, 0, 7, 6, 100, 0, 3, 70, 0, 104, 3, 84, 0, 7, 6, 101, 0, 3, 36, 0, 101, 3, 36, 12, 0, 1, 115, 3, 37, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 4, 3, 79, 0, 8, 107, 0, 104, 3, 98, 0, 7, 6, 104, 0, 108, 3, 103, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 105, 3, 37, 12, 0, 7, 6, 106, 0, 3, 77, 0, 7, 6, 107, 0, 3, 49, 0, 104, 3, 99, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 4, 1, 25, 2, 21, 21, 3, 23, 63, 0, 1, 25, 2, 98, 21, 21, 0, 1, 25, 2, 118, 21, 21, 0, 1, 25, 2, 119, 21, 21, 0, 4, 1, 25, 2, 17, 67, 3, 41, 0, 8, 0, 4, 3, 63, 0, 2, 17, 65, 0, 7, 6, 110, 0, 8, 3, 42, 0, 4, 8, 2, 103, 3, 43, 0, 8, 2, 103, 21, 21, 0, 8, 2, 107, 0, 8, 2, 107, 21, 21, 0, 4, 3, 50, 0, 2, 17, 65, 0, 2, 21, 21, 0, 4, 2, 99, 104, 3, 65, 0, 2, 106, 0, 121, 0, 4, 2, 103, 3, 66, 0, 2, 107, 0, 103, 39, 0, 7, 6, 111, 0, 3, 39, 0, 111, 3, 39, 12, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 7, 6, 114, 0, 1, 17, 67, 2, 17, 65, 3, 14, 16, 0, 3, 34, 0, 4, 3, 51, 0, 1, 17, 65, 2, 17, 65, 0, 114, 3, 51, 51, 0, 3, 53, 0, 7, 6, 115, 0, 3, 87, 0, 2, 101, 3, 87, 20, 0, 101, 8, 116, 3, 87, 37, 12, 0, 104, 3, 89, 0, 7, 6, 116, 0, 3, 47, 0, 104, 3, 85, 0, 108, 3, 103, 0, 115, 101, 110, 3, 113, 6, 36, 12, 50, 0, 108, 104, 3, 116, 0, 7, 6, 117, 0, 3, 40, 0, 4, 8, 100, 3, 40, 12, 0, 117, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 49, 87, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 4, 42, 1, 42, 2, 42, 3, 0, 42, 42, 3, 0, 42, 1, 42, 42, 2, 32, 3, 24, 0, 37, 3, 35, 87, 37, 55, 37, 63, 37, 35, 0, 42, 3, 65, 39, 47, 35, 0, 36, 3, 70, 39, 55, 35, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts60 = FileInMemory_createWithData (3072, reinterpret_cast (&espeakdata_dicts60_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/tn_dict", L"tn"); Collection_addItem (me.peek(), espeakdata_dicts60.transfer()); static unsigned char espeakdata_dicts61_data[5978] = { 0, 4, 0, 0, 77, 13, 0, 0, 0, 0, 0, 10, 135, 9, 19, 19, 22, 5, 195, 167, 65, 0, 0, 5, 65, 4, 35, 0, 0, 6, 194, 5, 0, 17, 9, 0, 10, 199, 44, 20, 212, 4, 211, 206, 84, 65, 0, 0, 6, 65, 8, 69, 36, 0, 0, 9, 198, 52, 19, 1, 81, 144, 64, 66, 0, 0, 0, 6, 65, 12, 73, 107, 0, 0, 0, 18, 4, 95, 8, 1, 3, 47, 6, 107, 51, 87, 89, 35, 48, 49, 6, 35, 0, 0, 0, 6, 65, 16, 70, 107, 0, 0, 0, 6, 195, 36, 209, 128, 17, 0, 0, 5, 65, 20, 107, 0, 0, 0, 0, 7, 196, 4, 102, 79, 56, 65, 0, 6, 65, 24, 81, 107, 0, 0, 0, 0, 8, 196, 100, 242, 211, 4, 72, 28, 0, 6, 65, 28, 77, 107, 0, 0, 0, 0, 0, 6, 65, 32, 105, 107, 0, 0, 0, 0, 0, 5, 65, 36, 37, 0, 0, 10, 1, 37, 57, 111, 86, 70, 107, 0, 27, 0, 8, 1, 38, 11, 82, 6, 107, 0, 0, 0, 6, 65, 40, 88, 107, 0, 0, 0, 12, 1, 42, 57, 6, 13, 55, 70, 13, 86, 0, 27, 0, 9, 1, 43, 35, 51, 47, 13, 0, 27, 0, 6, 65, 44, 49, 35, 0, 0, 0, 0, 0, 6, 65, 48, 55, 107, 0, 0, 0, 0, 0, 6, 65, 52, 63, 107, 0, 0, 0, 0, 0, 8, 197, 20, 66, 82, 56, 80, 66, 6, 65, 56, 50, 107, 0, 0, 0, 7, 195, 76, 150, 128, 76, 9, 0, 0, 5, 193, 60, 76, 9, 0, 9, 1, 61, 107, 89, 122, 47, 0, 27, 0, 0, 0, 6, 65, 64, 48, 107, 0, 0, 9, 198, 76, 147, 83, 37, 144, 72, 65, 6, 194, 4, 32, 17, 9, 0, 7, 195, 4, 33, 0, 17, 9, 0, 0, 7, 65, 68, 49, 82, 107, 0, 0, 0, 0, 0, 6, 65, 72, 51, 107, 0, 0, 0, 0, 0, 7, 132, 197, 159, 20, 9, 17, 6, 195, 36, 210, 194, 17, 6, 195, 36, 210, 194, 17, 6, 65, 76, 87, 107, 0, 0, 0, 0, 0, 6, 65, 80, 47, 107, 0, 0, 6, 195, 81, 0, 79, 17, 0, 0, 0, 5, 65, 84, 40, 0, 0, 0, 0, 0, 6, 65, 88, 82, 107, 0, 0, 7, 132, 1, 195, 182, 6, 17, 0, 0, 0, 12, 65, 92, 70, 40, 69, 107, 55, 82, 6, 107, 0, 0, 0, 0, 0, 7, 65, 96, 107, 49, 87, 0, 0, 0, 0, 0, 6, 65, 100, 57, 107, 0, 0, 0, 0, 0, 6, 65, 104, 86, 107, 0, 0, 0, 0, 0, 0, 0, 10, 135, 2, 9, 14, 7, 195, 182, 12, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 61, 33, 21, 65, 0, 0, 0, 0, 6, 195, 25, 64, 65, 17, 0, 0, 6, 195, 4, 100, 0, 17, 0, 0, 0, 6, 195, 80, 146, 22, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 16, 16, 72, 9, 0, 0, 0, 0, 9, 198, 32, 18, 203, 5, 34, 64, 65, 0, 0, 0, 0, 9, 198, 44, 22, 83, 21, 34, 64, 65, 6, 194, 9, 80, 76, 9, 0, 0, 0, 0, 0, 6, 195, 5, 99, 64, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 32, 149, 12, 21, 32, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 76, 147, 143, 64, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 52, 84, 147, 36, 224, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 16, 80, 72, 9, 0, 0, 0, 0, 6, 195, 4, 180, 0, 17, 0, 0, 16, 4, 95, 4, 16, 20, 10, 82, 37, 51, 79, 4, 111, 55, 23, 0, 0, 0, 0, 0, 11, 200, 36, 227, 135, 36, 197, 5, 72, 80, 67, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 44, 147, 9, 76, 65, 7, 196, 64, 244, 212, 4, 65, 13, 4, 95, 20, 12, 4, 47, 122, 55, 70, 6, 107, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 88, 86, 65, 72, 28, 0, 8, 197, 4, 208, 83, 100, 16, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 195, 8, 83, 128, 76, 9, 0, 7, 196, 8, 19, 139, 4, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 76, 19, 83, 84, 224, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 8, 149, 12, 37, 48, 65, 0, 0, 6, 195, 61, 48, 128, 17, 0, 7, 196, 72, 17, 25, 60, 65, 0, 0, 0, 0, 0, 0, 0, 10, 3, 226, 130, 172, 35, 82, 51, 108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 76, 149, 129, 76, 65, 6, 195, 21, 1, 11, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 5, 37, 22, 36, 224, 65, 0, 0, 0, 0, 0, 17, 4, 95, 13, 3, 14, 40, 86, 6, 35, 47, 63, 35, 37, 63, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 51, 88, 39, 47, 6, 40, 86, 0, 0, 10, 3, 95, 48, 67, 6, 57, 110, 86, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 44, 243, 153, 4, 65, 0, 0, 0, 0, 13, 3, 95, 50, 67, 6, 37, 78, 37, 57, 110, 86, 0, 0, 0, 9, 198, 81, 83, 131, 20, 194, 64, 65, 14, 139, 11, 196, 177, 18, 11, 12, 1, 18, 5, 12, 9, 65, 0, 0, 0, 0, 6, 195, 4, 146, 13, 17, 12, 3, 95, 49, 49, 6, 39, 50, 69, 37, 51, 0, 0, 9, 3, 95, 49, 48, 6, 39, 50, 0, 0, 0, 12, 3, 95, 49, 50, 6, 39, 50, 37, 78, 37, 0, 0, 0, 0, 0, 6, 195, 36, 129, 0, 17, 0, 0, 13, 3, 95, 55, 88, 57, 36, 47, 63, 6, 37, 89, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 32, 21, 1, 100, 65, 14, 139, 11, 196, 177, 19, 11, 196, 177, 22, 18, 1, 11, 65, 0, 0, 6, 195, 8, 243, 21, 65, 0, 0, 0, 0, 0, 9, 3, 95, 49, 88, 6, 39, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 88, 57, 37, 51, 63, 6, 37, 0, 0, 0, 0, 0, 0, 12, 137, 16, 195, 188, 20, 195, 188, 18, 7, 5, 66, 0, 0, 0, 8, 133, 196, 177, 13, 11, 2, 17, 0, 0, 10, 135, 9, 196, 159, 4, 196, 177, 18, 65, 0, 9, 198, 76, 18, 193, 73, 144, 64, 66, 0, 0, 13, 3, 95, 63, 63, 87, 107, 63, 69, 6, 108, 55, 0, 0, 0, 0, 11, 3, 95, 52, 88, 49, 6, 13, 51, 49, 0, 0, 0, 0, 0, 11, 136, 11, 195, 188, 20, 1, 8, 25, 1, 66, 0, 0, 0, 0, 11, 3, 95, 53, 88, 36, 55, 55, 6, 37, 0, 0, 0, 8, 197, 8, 241, 18, 84, 208, 65, 0, 0, 0, 0, 0, 0, 13, 3, 95, 54, 88, 35, 55, 47, 63, 6, 13, 89, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 199, 37, 52, 212, 4, 224, 149, 48, 66, 0, 0, 0, 0, 0, 0, 0, 8, 133, 21, 197, 159, 1, 11, 65, 0, 13, 3, 95, 56, 88, 87, 36, 49, 87, 6, 107, 50, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 44, 144, 72, 28, 0, 13, 3, 95, 57, 88, 70, 39, 49, 87, 6, 35, 50, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 53, 80, 72, 9, 10, 3, 95, 63, 65, 105, 35, 51, 81, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 52, 20, 132, 36, 224, 65, 0, 9, 198, 4, 195, 65, 57, 144, 64, 66, 0, 7, 131, 13, 195, 188, 72, 9, 14, 4, 95, 15, 7, 15, 39, 79, 39, 50, 6, 107, 49, 0, 0, 0, 0, 0, 0, 7, 131, 197, 159, 21, 76, 9, 0, 0, 0, 6, 195, 81, 49, 64, 17, 0, 0, 0, 0, 0, 7, 131, 13, 196, 177, 72, 9, 0, 0, 0, 6, 195, 81, 50, 64, 17, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 48, 77, 50, 63, 37, 55, 57, 6, 39, 50, 0, 0, 7, 195, 76, 83, 128, 76, 9, 14, 4, 95, 48, 77, 51, 63, 37, 55, 57, 6, 35, 34, 0, 0, 9, 198, 8, 83, 66, 21, 144, 90, 65, 0, 11, 4, 95, 48, 77, 49, 69, 6, 37, 50, 0, 0, 19, 4, 95, 2, 18, 22, 49, 13, 87, 6, 35, 55, 47, 63, 35, 37, 63, 122, 0, 0, 0, 0, 0, 0, 0, 0, 8, 197, 8, 21, 13, 4, 224, 65, 0, 0, 13, 138, 195, 167, 1, 14, 1, 11, 11, 1, 12, 5, 66, 7, 132, 195, 182, 19, 19, 17, 0, 0, 0, 9, 198, 8, 22, 66, 85, 37, 0, 65, 0, 0, 0, 8, 197, 100, 246, 135, 5, 64, 65, 0, 6, 194, 52, 144, 72, 9, 0, 6, 195, 81, 54, 68, 17, 0, 0, 0, 7, 132, 195, 182, 20, 22, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 4, 195, 188, 13, 4, 195, 188, 26, 65, 0, 0, 0, 0, 9, 198, 52, 84, 136, 4, 32, 64, 65, 0, 6, 195, 60, 80, 196, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 1, 196, 159, 18, 196, 177, 65, 0, 0, 0, 0, 0, 0, 11, 136, 19, 1, 16, 19, 1, 18, 196, 177, 65, 0, 13, 4, 95, 3, 9, 18, 89, 35, 48, 49, 6, 35, 0, 0, 13, 138, 195, 167, 1, 14, 11, 196, 177, 18, 196, 177, 65, 0, 0, 0, 0, 0, 0, 0, 9, 198, 84, 180, 129, 100, 224, 64, 66, 0, 0, 7, 196, 76, 146, 82, 80, 65, 0, 0, 0, 0, 7, 196, 29, 54, 73, 32, 17, 0, 16, 4, 95, 1, 3, 21, 82, 109, 51, 79, 6, 109, 37, 63, 122, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 18, 14, 7, 105, 35, 55, 49, 6, 35, 0, 0, 0, 0, 9, 198, 16, 83, 137, 104, 194, 64, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 1, 25, 4, 196, 177, 14, 65, 0, 0, 0, 0, 0, 0, 0, 9, 134, 13, 21, 196, 159, 12, 1, 65, 8, 133, 195, 182, 196, 177, 2, 17, 0, 0, 0, 21, 4, 95, 1, 3, 50, 74, 6, 122, 81, 47, 82, 109, 51, 79, 6, 109, 37, 63, 122, 0, 0, 0, 0, 0, 6, 194, 80, 16, 72, 9, 0, 7, 132, 195, 182, 25, 11, 17, 0, 0, 0, 0, 0, 0, 8, 197, 5, 100, 149, 64, 16, 65, 0, 0, 7, 132, 195, 182, 6, 11, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 80, 211, 79, 8, 17, 0, 0, 0, 11, 136, 197, 159, 196, 177, 18, 14, 1, 11, 65, 0, 0, 0, 0, 0, 0, 12, 2, 194, 167, 74, 107, 50, 77, 6, 107, 55, 0, 0, 0, 0, 7, 132, 195, 182, 4, 16, 17, 0, 0, 0, 0, 0, 17, 2, 196, 159, 57, 40, 63, 40, 89, 6, 35, 49, 15, 77, 6, 107, 0, 7, 2, 195, 167, 74, 107, 0, 0, 9, 198, 52, 20, 205, 5, 98, 64, 65, 8, 133, 195, 182, 19, 25, 13, 17, 0, 0, 0, 0, 0, 0, 14, 2, 194, 182, 48, 35, 16, 35, 79, 51, 6, 35, 81, 0, 0, 7, 2, 197, 159, 89, 107, 0, 0, 0, 0, 0, 0, 6, 195, 84, 36, 0, 17, 12, 2, 194, 176, 70, 36, 16, 36, 73, 6, 107, 0, 0, 9, 134, 14, 9, 196, 159, 4, 5, 65, 0, 6, 2, 195, 182, 123, 0, 0, 0, 0, 0, 12, 4, 95, 3, 5, 4, 105, 6, 35, 51, 81, 0, 0, 8, 197, 9, 84, 132, 85, 32, 65, 0, 0, 0, 6, 195, 85, 33, 129, 65, 0, 0, 6, 194, 80, 80, 72, 9, 6, 2, 195, 188, 110, 0, 0, 0, 0, 10, 135, 2, 1, 18, 20, 196, 177, 14, 65, 0, 0, 6, 2, 196, 177, 13, 0, 0, 0, 8, 197, 4, 226, 193, 72, 16, 65, 0, 6, 195, 4, 33, 211, 17, 0, 6, 195, 85, 49, 0, 17, 0, 0, 0, 0, 6, 195, 100, 179, 64, 17, 6, 195, 4, 179, 64, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 195, 182, 9, 2, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 80, 242, 193, 80, 65, 12, 137, 11, 21, 18, 20, 21, 12, 21, 197, 159, 65, 0, 0, 0, 0, 0, 0, 0, 0, 6, 2, 95, 15, 108, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 194, 88, 80, 72, 28, 0, 0, 0, 0, 0, 11, 2, 95, 35, 70, 37, 57, 6, 107, 86, 0, 0, 20, 2, 95, 34, 47, 13, 51, 50, 6, 35, 49, 37, 89, 35, 16, 36, 47, 6, 122, 0, 0, 19, 2, 95, 33, 111, 50, 55, 6, 107, 63, 37, 89, 35, 16, 36, 47, 4, 122, 0, 0, 0, 14, 2, 95, 39, 35, 48, 108, 87, 47, 51, 6, 108, 81, 0, 0, 16, 2, 95, 38, 82, 6, 107, 37, 89, 35, 16, 36, 47, 6, 122, 0, 0, 0, 7, 132, 195, 182, 9, 22, 17, 0, 0, 13, 4, 95, 3, 1, 16, 69, 110, 57, 6, 111, 49, 0, 0, 18, 2, 95, 41, 49, 35, 48, 35, 48, 35, 16, 35, 50, 47, 6, 107, 86, 0, 0, 16, 2, 95, 40, 35, 74, 48, 35, 16, 35, 50, 47, 6, 107, 86, 0, 0, 16, 2, 95, 47, 36, 57, 6, 122, 49, 74, 122, 86, 79, 6, 122, 0, 0, 11, 2, 95, 46, 50, 108, 49, 47, 6, 35, 0, 0, 16, 2, 95, 45, 49, 6, 13, 87, 35, 74, 122, 86, 79, 6, 122, 0, 0, 9, 198, 53, 81, 1, 57, 144, 64, 66, 9, 198, 4, 229, 1, 49, 144, 64, 66, 12, 2, 95, 44, 82, 122, 51, 77, 6, 111, 55, 0, 0, 7, 195, 8, 148, 128, 76, 9, 8, 2, 95, 51, 6, 110, 74, 0, 0, 9, 2, 95, 50, 37, 78, 6, 37, 0, 0, 9, 134, 195, 167, 15, 18, 21, 13, 65, 9, 198, 64, 84, 208, 20, 208, 133, 65, 9, 2, 95, 49, 69, 6, 37, 51, 0, 0, 11, 2, 95, 48, 87, 13, 81, 6, 13, 51, 0, 0, 10, 2, 95, 55, 57, 36, 70, 6, 37, 0, 0, 10, 2, 95, 54, 35, 55, 47, 6, 13, 0, 0, 9, 2, 95, 53, 69, 6, 107, 89, 0, 0, 10, 2, 95, 52, 70, 6, 123, 51, 47, 0, 0, 20, 2, 95, 59, 50, 108, 49, 47, 35, 55, 6, 13, 82, 122, 51, 77, 6, 111, 55, 0, 0, 15, 2, 95, 58, 37, 49, 6, 122, 50, 108, 49, 47, 6, 35, 0, 0, 11, 2, 95, 57, 70, 6, 39, 49, 40, 86, 0, 0, 6, 195, 72, 150, 133, 65, 11, 2, 95, 56, 87, 36, 78, 6, 122, 86, 0, 0, 18, 2, 95, 63, 87, 39, 51, 6, 109, 37, 89, 35, 16, 36, 47, 4, 122, 0, 0, 0, 0, 0, 7, 195, 8, 150, 128, 76, 9, 0, 0, 0, 16, 2, 95, 64, 49, 109, 57, 51, 109, 49, 55, 6, 109, 6, 35, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 4, 95, 226, 128, 166, 6, 111, 74, 50, 108, 49, 47, 6, 35, 0, 0, 0, 0, 0, 0, 6, 195, 20, 177, 192, 17, 17, 4, 95, 226, 128, 153, 47, 107, 49, 47, 13, 51, 50, 6, 35, 49, 0, 0, 12, 137, 4, 15, 19, 4, 15, 196, 159, 18, 21, 65, 17, 4, 95, 226, 128, 152, 47, 107, 49, 47, 13, 51, 50, 6, 35, 49, 0, 16, 4, 95, 4, 15, 20, 111, 87, 47, 50, 108, 49, 47, 6, 35, 0, 0, 0, 0, 7, 195, 36, 193, 64, 72, 9, 0, 0, 18, 4, 95, 226, 128, 147, 6, 40, 86, 109, 50, 74, 122, 86, 79, 6, 122, 0, 0, 0, 15, 2, 95, 95, 4, 35, 55, 47, 74, 122, 86, 79, 6, 122, 0, 0, 22, 2, 95, 94, 122, 50, 73, 6, 107, 55, 47, 63, 107, 37, 89, 35, 16, 36, 47, 6, 122, 0, 0, 0, 22, 2, 95, 92, 47, 6, 107, 51, 87, 15, 36, 57, 4, 122, 49, 74, 122, 86, 79, 6, 122, 0, 0, 0, 0, 0, 0, 6, 195, 80, 211, 192, 17, 0, 0, 17, 142, 11, 196, 177, 16, 11, 196, 177, 18, 13, 196, 177, 26, 196, 177, 65, 0, 0, 0, 0, 0, 16, 4, 95, 7, 18, 22, 6, 35, 49, 87, 35, 50, 37, 63, 122, 0, 0, 6, 195, 60, 116, 192, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 4, 95, 4, 9, 1, 109, 63, 55, 35, 6, 109, 47, 0, 0, 0, 0, 0, 0, 14, 2, 95, 126, 57, 35, 49, 55, 35, 89, 6, 13, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 201, 37, 52, 203, 20, 225, 5, 73, 83, 128, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 198, 37, 52, 1, 73, 64, 64, 66, 0, 0, 0, 8, 197, 37, 166, 141, 37, 32, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 5, 67, 64, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 196, 9, 84, 147, 4, 65, 0, 9, 134, 4, 195, 188, 26, 3, 5, 65, 0, 0, 0, 0, 0, 0, 7, 195, 4, 208, 64, 28, 65, 0, 0, 0, 0, 0, 0, 8, 197, 52, 244, 205, 61, 32, 65, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 137, 20, 5, 11, 9, 18, 4, 1, 196, 159, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 138, 19, 196, 177, 13, 19, 196, 177, 3, 1, 11, 65, 0, 0, 0, 0, 6, 195, 5, 69, 128, 17, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 195, 167, 0, 197, 159, 0, 102, 0, 104, 0, 107, 0, 112, 0, 113, 0, 115, 0, 116, 0, 7, 6, 20, 0, 96, 0, 0, 0, 39, 0, 0, 0, 0, 0, 0, 0, 6, 195, 167, 0, 3, 74, 0, 7, 6, 195, 182, 0, 3, 123, 0, 7, 6, 195, 188, 0, 110, 195, 188, 122, 1, 21, 2, 32, 14, 128, 128, 132, 3, 2, 110, 50, 110, 86, 0, 109, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 110, 63, 0, 122, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 110, 86, 0, 4, 3, 110, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 110, 1, 21, 2, 32, 14, 128, 128, 130, 3, 110, 50, 0, 121, 111, 114, 1, 21, 2, 32, 14, 128, 128, 132, 3, 110, 57, 2, 39, 51, 0, 7, 6, 196, 159, 0, 1, 17, 65, 3, 12, 15, 0, 4, 1, 101, 3, 57, 0, 1, 105, 0, 3, 98, 0, 5, 1, 1, 17, 65, 3, 124, 0, 7, 6, 196, 177, 0, 110, 196, 177, 122, 1, 21, 2, 32, 14, 128, 128, 132, 3, 2, 13, 50, 13, 86, 0, 109, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 13, 63, 0, 122, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 13, 86, 0, 4, 3, 13, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 110, 1, 21, 2, 32, 14, 128, 128, 130, 3, 13, 50, 0, 121, 111, 114, 1, 21, 2, 32, 14, 128, 128, 132, 3, 13, 57, 2, 39, 51, 0, 7, 6, 197, 159, 0, 3, 89, 0, 7, 6, 97, 0, 4, 3, 35, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 108, 196, 177, 109, 1, 21, 2, 32, 14, 128, 128, 132, 3, 35, 55, 13, 63, 0, 121, 196, 177, 109, 1, 21, 2, 32, 14, 128, 128, 132, 3, 35, 57, 13, 63, 0, 99, 97, 107, 1, 21, 2, 32, 14, 128, 128, 132, 3, 35, 73, 35, 49, 0, 99, 97, 107, 109, 196, 177, 197, 159, 1, 21, 2, 32, 14, 128, 128, 135, 3, 35, 73, 35, 49, 63, 2, 13, 89, 0, 118, 114, 117, 1, 21, 2, 112, 97, 3, 35, 82, 34, 6, 40, 0, 115, 196, 177, 110, 1, 21, 2, 32, 14, 128, 128, 132, 3, 35, 87, 13, 50, 0, 7, 6, 98, 0, 3, 69, 0, 7, 6, 99, 0, 3, 73, 0, 7, 6, 100, 0, 196, 177, 114, 2, 32, 14, 128, 128, 131, 3, 2, 70, 13, 51, 0, 105, 114, 2, 32, 14, 128, 128, 131, 3, 2, 70, 37, 51, 0, 117, 114, 2, 32, 14, 128, 128, 131, 3, 2, 70, 40, 51, 0, 195, 188, 114, 2, 32, 14, 128, 128, 131, 3, 2, 70, 110, 51, 0, 8, 2, 101, 196, 159, 105, 108, 3, 6, 70, 0, 3, 70, 0, 196, 177, 2, 32, 14, 128, 128, 130, 3, 70, 13, 0, 196, 177, 107, 2, 32, 14, 128, 128, 131, 3, 70, 13, 49, 0, 196, 177, 110, 2, 32, 14, 128, 128, 131, 3, 70, 13, 50, 0, 196, 177, 110, 196, 177, 122, 2, 32, 14, 128, 128, 133, 3, 70, 13, 50, 13, 86, 0, 196, 177, 108, 97, 114, 2, 32, 14, 128, 128, 133, 3, 70, 13, 55, 35, 51, 0, 196, 177, 109, 2, 32, 14, 128, 128, 131, 3, 70, 13, 63, 0, 97, 2, 32, 14, 128, 128, 130, 3, 70, 35, 0, 97, 110, 2, 32, 14, 128, 128, 131, 3, 70, 35, 50, 0, 101, 2, 32, 14, 128, 128, 130, 3, 70, 36, 0, 101, 110, 2, 32, 14, 128, 128, 131, 3, 70, 36, 50, 0, 105, 2, 32, 14, 128, 128, 130, 3, 70, 37, 0, 105, 107, 2, 32, 14, 128, 128, 131, 3, 70, 37, 49, 0, 105, 110, 2, 32, 14, 128, 128, 131, 3, 70, 37, 50, 0, 105, 110, 105, 122, 2, 32, 14, 128, 128, 133, 3, 70, 37, 50, 37, 86, 0, 105, 108, 101, 114, 2, 32, 14, 128, 128, 133, 3, 70, 37, 55, 36, 51, 0, 105, 109, 2, 32, 14, 128, 128, 131, 3, 70, 37, 63, 0, 117, 2, 32, 14, 128, 128, 130, 3, 70, 40, 0, 117, 107, 2, 32, 14, 128, 128, 131, 3, 70, 40, 49, 0, 117, 110, 2, 32, 14, 128, 128, 131, 3, 70, 40, 50, 0, 117, 110, 117, 122, 2, 32, 14, 128, 128, 133, 3, 70, 40, 50, 40, 86, 0, 117, 108, 97, 114, 2, 32, 14, 128, 128, 133, 3, 70, 40, 55, 35, 34, 0, 117, 109, 2, 32, 14, 128, 128, 131, 3, 70, 40, 63, 0, 195, 188, 2, 32, 14, 128, 128, 130, 3, 70, 110, 0, 195, 188, 107, 2, 32, 14, 128, 128, 131, 3, 70, 110, 49, 0, 195, 188, 110, 2, 32, 14, 128, 128, 131, 3, 70, 110, 50, 0, 195, 188, 110, 195, 188, 122, 2, 32, 14, 128, 128, 133, 3, 70, 110, 50, 110, 86, 0, 195, 188, 108, 101, 114, 2, 32, 14, 128, 128, 133, 3, 70, 110, 55, 36, 34, 0, 195, 188, 109, 2, 32, 14, 128, 128, 131, 3, 70, 110, 63, 0, 7, 6, 101, 0, 4, 3, 36, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 108, 105, 109, 1, 21, 2, 32, 14, 128, 128, 132, 3, 36, 55, 37, 63, 0, 121, 105, 109, 1, 21, 2, 32, 14, 128, 128, 132, 3, 36, 57, 37, 63, 0, 99, 101, 107, 1, 21, 2, 32, 14, 128, 128, 132, 3, 36, 73, 36, 49, 0, 99, 101, 107, 109, 105, 197, 159, 1, 21, 2, 32, 14, 128, 128, 135, 3, 36, 73, 36, 49, 63, 2, 37, 89, 0, 115, 105, 110, 1, 21, 2, 32, 14, 128, 128, 132, 3, 36, 87, 37, 50, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 4, 2, 101, 3, 77, 0, 2, 105, 0, 2, 195, 182, 0, 2, 195, 188, 0, 3, 79, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 110, 105, 122, 1, 21, 2, 32, 14, 128, 128, 132, 3, 2, 37, 50, 37, 86, 0, 109, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 37, 63, 0, 122, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 37, 86, 0, 4, 3, 37, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 110, 1, 21, 2, 32, 14, 128, 128, 130, 3, 37, 50, 0, 121, 111, 114, 1, 21, 2, 32, 14, 128, 128, 132, 3, 37, 57, 2, 39, 51, 0, 7, 6, 106, 0, 3, 88, 0, 7, 6, 107, 0, 101, 110, 2, 32, 14, 128, 128, 131, 3, 2, 78, 36, 50, 0, 3, 49, 0, 4, 2, 101, 3, 78, 0, 2, 105, 0, 2, 195, 182, 0, 2, 195, 188, 0, 7, 6, 108, 0, 97, 2, 32, 14, 128, 128, 130, 3, 2, 55, 35, 0, 101, 2, 32, 14, 128, 128, 130, 3, 2, 55, 36, 0, 3, 55, 0, 196, 177, 2, 32, 14, 128, 128, 130, 3, 55, 13, 0, 196, 177, 107, 2, 32, 14, 128, 128, 131, 3, 55, 13, 49, 0, 97, 114, 2, 32, 14, 128, 128, 131, 3, 55, 35, 51, 0, 101, 114, 2, 32, 14, 128, 128, 131, 3, 55, 36, 51, 0, 105, 2, 32, 14, 128, 128, 130, 3, 55, 37, 0, 105, 107, 2, 32, 14, 128, 128, 131, 3, 55, 37, 49, 0, 117, 2, 32, 14, 128, 128, 130, 3, 55, 40, 0, 117, 107, 2, 32, 14, 128, 128, 131, 3, 55, 40, 49, 0, 195, 188, 2, 32, 14, 128, 128, 130, 3, 55, 110, 0, 195, 188, 107, 2, 32, 14, 128, 128, 131, 3, 55, 110, 49, 0, 7, 6, 109, 0, 97, 2, 32, 14, 128, 128, 130, 3, 2, 63, 35, 0, 101, 2, 32, 14, 128, 128, 130, 3, 2, 63, 36, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 196, 177, 110, 2, 32, 14, 128, 128, 131, 3, 50, 13, 50, 0, 105, 110, 2, 32, 14, 128, 128, 131, 3, 50, 37, 50, 0, 117, 110, 2, 32, 14, 128, 128, 131, 3, 50, 40, 50, 0, 100, 97, 8, 2, 32, 3, 50, 70, 35, 0, 100, 97, 110, 8, 2, 32, 3, 50, 70, 35, 50, 0, 100, 101, 8, 2, 32, 3, 50, 70, 36, 0, 100, 101, 110, 8, 2, 32, 3, 50, 70, 36, 50, 0, 195, 188, 110, 2, 32, 14, 128, 128, 131, 3, 50, 110, 50, 0, 7, 6, 111, 0, 3, 39, 0, 7, 6, 112, 0, 3, 48, 0, 7, 6, 113, 0, 3, 49, 0, 7, 6, 114, 0, 97, 2, 32, 14, 128, 128, 130, 3, 2, 51, 35, 0, 101, 2, 32, 14, 128, 128, 130, 3, 2, 51, 36, 0, 1, 17, 65, 2, 17, 65, 3, 16, 0, 3, 51, 0, 97, 2, 32, 24, 3, 51, 35, 0, 101, 2, 32, 24, 3, 51, 36, 0, 7, 6, 115, 0, 196, 177, 110, 196, 177, 122, 2, 32, 14, 128, 128, 133, 3, 2, 87, 13, 50, 13, 86, 0, 97, 2, 32, 14, 128, 128, 130, 3, 2, 87, 35, 0, 97, 107, 2, 32, 14, 128, 128, 131, 3, 2, 87, 35, 49, 0, 97, 110, 2, 32, 14, 128, 128, 131, 3, 2, 87, 35, 50, 0, 97, 110, 196, 177, 122, 2, 32, 14, 128, 128, 133, 3, 2, 87, 35, 50, 13, 86, 0, 97, 109, 2, 32, 14, 128, 128, 131, 3, 2, 87, 35, 63, 0, 101, 2, 32, 14, 128, 128, 130, 3, 2, 87, 36, 0, 101, 107, 2, 32, 14, 128, 128, 131, 3, 2, 87, 36, 49, 0, 101, 110, 2, 32, 14, 128, 128, 131, 3, 2, 87, 36, 50, 0, 101, 110, 105, 122, 2, 32, 14, 128, 128, 133, 3, 2, 87, 36, 50, 37, 86, 0, 101, 109, 2, 32, 14, 128, 128, 131, 3, 2, 87, 36, 63, 0, 105, 110, 105, 122, 2, 32, 14, 128, 128, 133, 3, 2, 87, 37, 50, 37, 86, 0, 117, 110, 117, 122, 2, 32, 14, 128, 128, 133, 3, 2, 87, 40, 50, 40, 86, 0, 195, 188, 110, 195, 188, 122, 2, 32, 14, 128, 128, 133, 3, 2, 87, 110, 50, 110, 86, 0, 3, 87, 0, 7, 6, 116, 0, 196, 177, 114, 1, 18, 66, 2, 32, 14, 128, 128, 131, 3, 2, 47, 13, 51, 0, 105, 114, 1, 18, 66, 2, 32, 14, 128, 128, 131, 3, 2, 47, 37, 51, 0, 117, 114, 1, 18, 66, 2, 32, 14, 128, 128, 131, 3, 2, 47, 40, 51, 0, 195, 188, 114, 1, 18, 66, 2, 32, 14, 128, 128, 131, 3, 2, 47, 110, 51, 0, 3, 47, 0, 97, 2, 32, 14, 128, 128, 130, 3, 47, 35, 0, 97, 110, 2, 32, 14, 128, 128, 131, 3, 47, 35, 50, 0, 101, 2, 32, 14, 128, 128, 130, 3, 47, 36, 0, 101, 110, 2, 32, 14, 128, 128, 131, 3, 47, 36, 50, 0, 7, 6, 117, 0, 110, 117, 122, 1, 21, 2, 32, 14, 128, 128, 132, 3, 2, 40, 50, 40, 86, 0, 109, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 40, 63, 0, 122, 1, 21, 2, 32, 14, 128, 128, 130, 3, 2, 40, 86, 0, 4, 3, 40, 0, 1, 21, 2, 32, 14, 128, 128, 129, 0, 110, 1, 21, 2, 32, 14, 128, 128, 130, 3, 40, 50, 0, 121, 111, 114, 1, 21, 2, 32, 14, 128, 128, 132, 3, 40, 57, 2, 39, 51, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 49, 87, 0, 1, 25, 3, 86, 0, 7, 6, 121, 0, 196, 177, 110, 196, 177, 122, 2, 32, 14, 128, 128, 133, 3, 2, 57, 13, 50, 13, 86, 0, 196, 177, 109, 2, 32, 14, 128, 128, 131, 3, 2, 57, 13, 63, 0, 196, 177, 122, 2, 32, 14, 128, 128, 131, 3, 2, 57, 13, 86, 0, 105, 110, 105, 122, 2, 32, 14, 128, 128, 133, 3, 2, 57, 37, 50, 37, 86, 0, 105, 109, 2, 32, 14, 128, 128, 131, 3, 2, 57, 37, 63, 0, 105, 122, 2, 32, 14, 128, 128, 131, 3, 2, 57, 37, 86, 0, 117, 110, 117, 122, 2, 32, 14, 128, 128, 133, 3, 2, 57, 40, 50, 40, 86, 0, 117, 109, 2, 32, 14, 128, 128, 131, 3, 2, 57, 40, 63, 0, 117, 122, 2, 32, 14, 128, 128, 131, 3, 2, 57, 40, 86, 0, 108, 97, 2, 32, 14, 128, 128, 131, 3, 2, 57, 55, 35, 0, 108, 101, 2, 32, 14, 128, 128, 131, 3, 2, 57, 55, 36, 0, 195, 188, 110, 195, 188, 122, 2, 32, 14, 128, 128, 133, 3, 2, 57, 110, 50, 110, 86, 0, 195, 188, 109, 2, 32, 14, 128, 128, 131, 3, 2, 57, 110, 63, 0, 195, 188, 122, 2, 32, 14, 128, 128, 131, 3, 2, 57, 110, 86, 0, 3, 57, 0, 196, 177, 2, 32, 14, 128, 128, 130, 3, 57, 13, 0, 97, 2, 32, 14, 128, 128, 130, 3, 57, 35, 0, 97, 108, 196, 177, 109, 2, 32, 14, 128, 128, 133, 3, 57, 35, 55, 13, 63, 0, 97, 121, 196, 177, 109, 2, 32, 14, 128, 128, 133, 3, 57, 35, 57, 13, 63, 0, 97, 99, 97, 107, 2, 32, 14, 128, 128, 133, 3, 57, 35, 73, 35, 49, 0, 97, 99, 97, 107, 109, 196, 177, 197, 159, 2, 32, 14, 128, 128, 136, 3, 57, 35, 73, 35, 49, 63, 2, 13, 89, 0, 97, 115, 196, 177, 110, 2, 32, 14, 128, 128, 133, 3, 57, 35, 87, 13, 50, 0, 101, 2, 32, 14, 128, 128, 130, 3, 57, 36, 0, 101, 108, 105, 109, 2, 32, 14, 128, 128, 133, 3, 57, 36, 55, 37, 63, 0, 101, 121, 105, 109, 2, 32, 14, 128, 128, 133, 3, 57, 36, 57, 37, 63, 0, 101, 99, 101, 107, 2, 32, 14, 128, 128, 133, 3, 57, 36, 73, 36, 49, 0, 101, 99, 101, 107, 109, 105, 197, 159, 2, 32, 14, 128, 128, 136, 3, 57, 36, 73, 36, 49, 63, 2, 37, 89, 0, 101, 115, 105, 110, 2, 32, 14, 128, 128, 133, 3, 57, 36, 87, 37, 50, 0, 105, 2, 32, 14, 128, 128, 130, 3, 57, 37, 0, 117, 2, 32, 14, 128, 128, 130, 3, 57, 40, 0, 107, 101, 110, 2, 32, 14, 128, 128, 132, 3, 57, 78, 2, 36, 50, 0, 195, 188, 2, 32, 14, 128, 128, 130, 3, 57, 110, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 39, 2, 14, 130, 132, 128, 3, 0, 36, 3, 70, 39, 55, 35, 34, 0, 4, 195, 164, 3, 107, 0, 201, 153, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts61 = FileInMemory_createWithData (5977, reinterpret_cast (&espeakdata_dicts61_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/tr_dict", L"tr"); Collection_addItem (me.peek(), espeakdata_dicts61.transfer()); static unsigned char espeakdata_dicts62_data[3403] = { 0, 4, 0, 0, 174, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 4, 16, 20, 10, 111, 89, 35, 51, 111, 6, 111, 35, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 51, 57, 120, 50, 47, 116, 55, 6, 110, 87, 0, 12, 3, 95, 50, 49, 111, 49, 49, 6, 110, 87, 0, 0, 12, 3, 95, 51, 56, 35, 51, 47, 6, 110, 87, 0, 10, 3, 95, 50, 48, 69, 6, 110, 87, 0, 0, 11, 3, 95, 50, 51, 47, 112, 6, 110, 87, 0, 0, 11, 3, 95, 50, 50, 69, 116, 6, 110, 87, 0, 0, 13, 3, 95, 50, 53, 48, 35, 78, 78, 6, 110, 87, 0, 0, 12, 3, 95, 50, 52, 78, 133, 69, 6, 110, 87, 0, 0, 14, 3, 95, 50, 55, 87, 35, 47, 12, 116, 6, 110, 87, 0, 0, 13, 3, 95, 50, 54, 142, 35, 69, 69, 6, 110, 87, 0, 0, 12, 3, 95, 51, 49, 37, 49, 47, 6, 110, 87, 0, 0, 10, 3, 95, 51, 48, 47, 6, 110, 87, 0, 0, 13, 3, 95, 51, 51, 47, 132, 66, 47, 6, 110, 87, 0, 0, 13, 3, 95, 51, 50, 69, 35, 47, 12, 6, 110, 87, 0, 0, 13, 3, 95, 51, 53, 48, 132, 66, 47, 6, 110, 87, 0, 0, 13, 3, 95, 51, 52, 78, 133, 66, 47, 6, 110, 87, 0, 0, 13, 3, 95, 51, 55, 87, 132, 66, 47, 6, 110, 87, 0, 0, 13, 3, 95, 51, 54, 142, 35, 47, 12, 6, 110, 87, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 55, 57, 120, 50, 50, 116, 87, 6, 110, 0, 12, 3, 95, 54, 49, 6, 111, 49, 87, 35, 136, 0, 0, 15, 3, 95, 55, 56, 35, 136, 106, 35, 47, 12, 6, 35, 51, 0, 10, 3, 95, 54, 48, 87, 6, 116, 136, 0, 0, 9, 3, 95, 48, 67, 87, 6, 133, 0, 13, 3, 95, 54, 51, 47, 6, 111, 51, 87, 35, 136, 0, 0, 12, 3, 95, 54, 50, 69, 6, 116, 87, 35, 136, 0, 0, 13, 3, 95, 54, 53, 48, 6, 132, 66, 87, 35, 136, 0, 0, 12, 3, 95, 54, 52, 78, 6, 133, 87, 35, 136, 0, 0, 13, 3, 95, 54, 55, 87, 6, 35, 51, 87, 35, 136, 0, 0, 14, 3, 95, 54, 54, 142, 111, 57, 6, 116, 87, 35, 136, 0, 0, 15, 3, 95, 55, 49, 111, 49, 106, 35, 47, 12, 6, 35, 51, 0, 0, 13, 3, 95, 55, 48, 87, 35, 47, 12, 6, 35, 51, 0, 0, 15, 3, 95, 55, 51, 47, 111, 106, 35, 47, 12, 6, 35, 51, 0, 0, 15, 3, 95, 55, 50, 69, 35, 106, 35, 47, 12, 6, 35, 51, 0, 0, 15, 3, 95, 55, 53, 48, 35, 142, 35, 47, 12, 6, 35, 51, 0, 0, 15, 3, 95, 55, 52, 78, 133, 106, 35, 47, 12, 6, 35, 51, 0, 0, 15, 3, 95, 55, 55, 87, 35, 136, 35, 47, 12, 6, 35, 51, 0, 0, 15, 3, 95, 55, 54, 142, 111, 106, 35, 47, 12, 6, 35, 51, 0, 0, 12, 3, 95, 49, 57, 6, 120, 50, 50, 110, 87, 0, 0, 13, 3, 95, 49, 56, 35, 136, 6, 116, 51, 35, 106, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 50, 57, 120, 50, 47, 6, 110, 87, 0, 13, 3, 95, 49, 49, 79, 57, 6, 116, 51, 35, 106, 0, 0, 12, 3, 95, 50, 56, 87, 136, 116, 6, 110, 87, 0, 10, 3, 95, 49, 48, 70, 6, 35, 87, 0, 0, 12, 3, 95, 49, 51, 47, 6, 112, 51, 35, 106, 0, 0, 12, 3, 95, 49, 50, 69, 6, 116, 51, 35, 106, 0, 0, 14, 3, 95, 49, 53, 48, 6, 35, 50, 70, 51, 35, 106, 0, 0, 12, 3, 95, 49, 52, 78, 6, 133, 70, 35, 106, 0, 0, 13, 3, 95, 49, 55, 87, 6, 35, 47, 51, 35, 106, 0, 0, 12, 3, 95, 49, 54, 87, 6, 117, 55, 35, 106, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 52, 57, 120, 50, 78, 6, 116, 87, 0, 0, 14, 3, 95, 52, 56, 35, 51, 47, 116, 55, 6, 110, 87, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 53, 57, 120, 50, 87, 6, 35, 136, 0, 14, 3, 95, 52, 49, 111, 49, 47, 116, 55, 6, 110, 87, 0, 0, 13, 3, 95, 53, 56, 35, 136, 6, 116, 82, 35, 50, 0, 12, 3, 95, 52, 48, 78, 116, 55, 6, 110, 87, 0, 0, 15, 3, 95, 52, 51, 47, 112, 66, 47, 116, 55, 6, 110, 87, 0, 0, 14, 3, 95, 52, 50, 69, 35, 57, 116, 55, 6, 110, 87, 0, 0, 15, 3, 95, 52, 53, 48, 132, 66, 47, 116, 55, 6, 110, 87, 0, 0, 14, 3, 95, 52, 52, 78, 35, 82, 116, 55, 6, 110, 87, 0, 0, 15, 3, 95, 52, 55, 87, 132, 66, 47, 116, 55, 6, 110, 87, 0, 0, 14, 3, 95, 52, 54, 142, 111, 57, 116, 55, 6, 110, 87, 0, 0, 16, 3, 95, 54, 57, 120, 50, 106, 4, 35, 47, 12, 6, 35, 51, 0, 13, 3, 95, 53, 49, 111, 49, 6, 116, 82, 35, 50, 0, 0, 12, 3, 95, 54, 56, 6, 35, 51, 87, 35, 136, 0, 12, 3, 95, 53, 48, 48, 35, 78, 6, 116, 87, 0, 0, 13, 3, 95, 53, 51, 47, 6, 111, 51, 48, 35, 50, 0, 0, 12, 3, 95, 53, 50, 69, 6, 116, 82, 35, 50, 0, 0, 13, 3, 95, 53, 53, 48, 6, 35, 78, 48, 35, 50, 0, 0, 12, 3, 95, 53, 52, 78, 6, 133, 82, 35, 50, 0, 0, 15, 3, 95, 53, 55, 87, 35, 47, 12, 6, 116, 82, 35, 50, 0, 0, 13, 3, 95, 53, 54, 142, 6, 35, 48, 48, 35, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 95, 56, 57, 50, 35, 82, 116, 87, 6, 110, 0, 0, 12, 3, 95, 56, 56, 35, 136, 116, 87, 6, 110, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 57, 57, 50, 111, 50, 57, 6, 116, 50, 82, 112, 0, 12, 3, 95, 56, 49, 111, 49, 116, 87, 6, 110, 0, 0, 14, 3, 95, 57, 56, 35, 136, 12, 6, 116, 50, 82, 112, 0, 11, 3, 95, 56, 48, 35, 87, 87, 6, 110, 0, 0, 13, 3, 95, 56, 51, 47, 111, 51, 116, 87, 6, 110, 0, 0, 13, 3, 95, 56, 50, 69, 35, 57, 116, 87, 6, 110, 0, 0, 13, 3, 95, 56, 53, 48, 35, 78, 116, 87, 6, 110, 0, 0, 13, 3, 95, 56, 52, 78, 133, 51, 116, 87, 6, 110, 0, 0, 14, 3, 95, 56, 55, 87, 35, 47, 12, 116, 87, 6, 110, 0, 0, 13, 3, 95, 56, 54, 142, 111, 57, 116, 87, 6, 110, 0, 0, 14, 3, 95, 57, 49, 111, 49, 57, 6, 116, 50, 82, 112, 0, 0, 12, 3, 95, 57, 48, 50, 35, 82, 82, 6, 112, 0, 0, 14, 3, 95, 57, 51, 47, 111, 85, 6, 116, 50, 82, 112, 0, 0, 12, 3, 95, 57, 50, 69, 6, 116, 50, 82, 112, 0, 0, 14, 3, 95, 57, 53, 48, 35, 78, 6, 116, 50, 82, 112, 0, 0, 14, 3, 95, 57, 52, 78, 133, 51, 6, 116, 50, 82, 112, 0, 0, 15, 3, 95, 57, 55, 87, 35, 47, 12, 6, 116, 50, 82, 112, 0, 0, 14, 3, 95, 57, 54, 142, 111, 57, 6, 116, 50, 82, 112, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 3, 239, 174, 168, 142, 117, 47, 110, 15, 106, 112, 0, 0, 12, 4, 95, 48, 77, 52, 6, 35, 51, 35, 69, 0, 0, 0, 11, 4, 95, 48, 77, 50, 55, 6, 116, 144, 0, 0, 13, 4, 95, 48, 77, 51, 49, 35, 51, 6, 117, 51, 0, 0, 0, 13, 4, 95, 48, 77, 49, 106, 35, 86, 6, 116, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 70, 40, 243, 129, 80, 128, 78, 73, 6, 119, 50, 35, 136, 35, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 2, 95, 51, 47, 6, 110, 50, 0, 0, 8, 2, 95, 50, 6, 70, 117, 0, 0, 8, 2, 95, 49, 6, 112, 49, 0, 0, 11, 2, 95, 48, 87, 6, 111, 81, 35, 51, 0, 0, 9, 2, 95, 55, 87, 6, 116, 47, 0, 0, 8, 2, 95, 54, 142, 6, 132, 0, 0, 10, 2, 95, 53, 48, 6, 116, 66, 78, 0, 0, 9, 2, 95, 52, 78, 6, 116, 51, 0, 0, 0, 0, 8, 2, 95, 57, 50, 6, 133, 0, 0, 8, 2, 95, 56, 6, 116, 136, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 2, 217, 134, 50, 121, 50, 0, 0, 8, 2, 217, 133, 63, 110, 63, 0, 0, 8, 2, 217, 132, 55, 116, 63, 0, 0, 0, 8, 2, 217, 130, 102, 116, 81, 0, 0, 7, 2, 217, 129, 81, 112, 0, 0, 0, 8, 2, 217, 143, 48, 112, 89, 0, 0, 10, 2, 217, 142, 86, 13, 69, 13, 51, 0, 0, 0, 0, 0, 0, 0, 8, 2, 217, 136, 82, 116, 119, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 2, 217, 144, 86, 112, 51, 0, 0, 9, 2, 216, 167, 35, 55, 111, 81, 0, 0, 0, 0, 12, 2, 219, 140, 142, 117, 138, 110, 15, 57, 112, 0, 0, 0, 0, 11, 2, 216, 161, 106, 35, 63, 86, 35, 106, 0, 7, 2, 218, 145, 68, 112, 0, 0, 0, 8, 2, 216, 175, 139, 116, 55, 0, 8, 2, 216, 175, 70, 116, 55, 0, 0, 7, 2, 216, 174, 99, 112, 0, 0, 12, 2, 216, 173, 69, 35, 68, 110, 15, 106, 112, 0, 0, 7, 2, 216, 172, 78, 112, 0, 8, 2, 216, 172, 77, 110, 63, 0, 0, 7, 2, 216, 171, 87, 112, 0, 0, 12, 2, 219, 146, 69, 35, 68, 110, 15, 57, 112, 0, 7, 2, 216, 170, 47, 112, 0, 0, 0, 7, 2, 218, 152, 88, 112, 0, 7, 2, 216, 168, 69, 112, 0, 0, 8, 2, 216, 183, 47, 119, 112, 0, 0, 9, 2, 216, 182, 86, 120, 116, 70, 0, 0, 9, 2, 216, 181, 87, 120, 116, 70, 0, 0, 8, 2, 216, 180, 89, 110, 50, 0, 0, 8, 2, 216, 179, 87, 110, 50, 0, 0, 7, 2, 216, 178, 86, 112, 0, 0, 7, 2, 216, 177, 51, 112, 0, 0, 8, 2, 216, 176, 86, 116, 55, 0, 0, 8, 2, 218, 175, 79, 116, 81, 0, 0, 0, 0, 0, 0, 8, 2, 216, 186, 98, 132, 50, 0, 0, 8, 2, 218, 169, 49, 116, 81, 0, 7, 2, 216, 185, 132, 50, 0, 0, 8, 2, 216, 184, 86, 119, 112, 0, 0, 0, 7, 2, 217, 190, 48, 112, 0, 0, 0, 0, 0, 0, 7, 2, 217, 185, 138, 112, 0, 0, 0, 0, 16, 2, 218, 190, 70, 119, 15, 78, 35, 89, 63, 110, 15, 106, 112, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 96, 6, 0, 0, 48, 0, 0, 0, 97, 6, 0, 0, 49, 0, 0, 0, 98, 6, 0, 0, 50, 0, 0, 0, 99, 6, 0, 0, 51, 0, 0, 0, 100, 6, 0, 0, 52, 0, 0, 0, 101, 6, 0, 0, 53, 0, 0, 0, 102, 6, 0, 0, 54, 0, 0, 0, 103, 6, 0, 0, 55, 0, 0, 0, 104, 6, 0, 0, 56, 0, 0, 0, 105, 6, 0, 0, 57, 0, 0, 0, 0, 0, 0, 0, 6, 18, 66, 217, 142, 0, 217, 144, 0, 217, 143, 0, 217, 136, 0, 219, 140, 0, 216, 185, 0, 216, 167, 0, 7, 6, 1, 34, 0, 3, 0, 7, 6, 1, 35, 0, 3, 116, 0, 7, 6, 1, 36, 0, 3, 0, 7, 6, 1, 37, 0, 3, 133, 0, 7, 6, 1, 39, 0, 3, 0, 7, 6, 1, 40, 0, 8, 2, 18, 66, 3, 0, 8, 3, 35, 0, 219, 140, 8, 3, 110, 0, 3, 116, 0, 217, 136, 8, 3, 121, 0, 7, 6, 1, 41, 0, 3, 69, 0, 218, 190, 3, 135, 0, 7, 6, 1, 43, 0, 3, 47, 0, 218, 190, 3, 136, 0, 7, 6, 1, 44, 0, 3, 87, 0, 7, 6, 1, 45, 0, 3, 77, 0, 218, 190, 3, 143, 0, 7, 6, 1, 46, 0, 3, 106, 0, 7, 6, 1, 47, 0, 3, 99, 0, 7, 6, 1, 48, 0, 3, 70, 0, 218, 190, 3, 137, 0, 7, 6, 1, 49, 0, 3, 84, 0, 7, 6, 1, 50, 0, 3, 51, 0, 7, 6, 1, 51, 0, 3, 86, 0, 7, 6, 1, 52, 0, 3, 87, 0, 7, 6, 1, 53, 0, 3, 89, 0, 7, 6, 1, 54, 0, 3, 91, 0, 7, 6, 1, 55, 0, 3, 86, 0, 7, 6, 1, 56, 0, 3, 47, 0, 218, 190, 3, 136, 0, 7, 6, 1, 57, 0, 3, 90, 0, 7, 6, 1, 58, 0, 8, 3, 35, 0, 4, 3, 116, 0, 216, 167, 0, 7, 6, 1, 59, 0, 3, 98, 0, 7, 6, 1, 66, 0, 3, 81, 0, 7, 6, 1, 67, 0, 3, 102, 0, 7, 6, 1, 69, 0, 3, 55, 0, 7, 6, 1, 70, 0, 3, 63, 0, 7, 6, 1, 71, 0, 3, 50, 0, 7, 6, 1, 73, 0, 4, 2, 18, 66, 3, 82, 0, 8, 0, 3, 117, 0, 4, 217, 143, 3, 121, 0, 217, 151, 0, 7, 6, 1, 79, 0, 3, 35, 0, 4, 219, 140, 3, 114, 0, 219, 146, 0, 216, 185, 3, 116, 0, 217, 136, 3, 119, 0, 7, 6, 1, 80, 0, 216, 185, 3, 119, 0, 3, 120, 0, 217, 136, 3, 121, 0, 7, 6, 1, 81, 0, 4, 216, 185, 3, 110, 0, 219, 140, 0, 3, 111, 0, 7, 6, 1, 122, 0, 3, 138, 0, 218, 190, 3, 140, 0, 7, 6, 1, 127, 0, 3, 48, 0, 218, 190, 3, 134, 0, 7, 6, 218, 134, 0, 3, 78, 0, 218, 190, 3, 142, 0, 7, 6, 218, 136, 0, 3, 139, 0, 218, 190, 3, 141, 0, 7, 6, 218, 145, 0, 3, 68, 0, 7, 6, 218, 152, 0, 3, 88, 0, 7, 6, 218, 169, 0, 3, 49, 0, 218, 190, 3, 144, 0, 7, 6, 218, 175, 0, 3, 79, 0, 218, 190, 3, 145, 0, 7, 6, 218, 186, 0, 3, 50, 0, 7, 6, 218, 190, 0, 3, 106, 0, 7, 6, 219, 129, 0, 2, 32, 3, 35, 0, 3, 106, 0, 7, 6, 219, 140, 0, 4, 2, 18, 66, 3, 57, 0, 8, 0, 2, 32, 3, 110, 0, 3, 112, 0, 7, 6, 219, 146, 0, 3, 112, 0, 7, 6, 224, 164, 0, 3, 21, 104, 105, 0, 7, 6, 224, 165, 0, 3, 21, 104, 105, 0, 7, 6, 0, 36, 3, 70, 117, 55, 13, 51, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts62 = FileInMemory_createWithData (3402, reinterpret_cast (&espeakdata_dicts62_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/ur_dict", L"ur"); Collection_addItem (me.peek(), espeakdata_dicts62.transfer()); static unsigned char espeakdata_dicts63_data[5837] = { 0, 4, 0, 0, 100, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 8, 69, 36, 0, 0, 0, 0, 0, 6, 65, 12, 87, 36, 0, 0, 0, 0, 0, 6, 65, 16, 70, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 65, 24, 113, 107, 48, 0, 0, 0, 0, 0, 8, 65, 28, 84, 6, 36, 111, 0, 0, 0, 0, 0, 8, 65, 32, 105, 35, 107, 47, 0, 0, 0, 7, 132, 196, 145, 195, 163, 72, 0, 14, 1, 35, 77, 6, 132, 107, 47, 6, 35, 111, 66, 0, 27, 0, 17, 1, 36, 77, 6, 132, 107, 10, 70, 6, 39, 17, 55, 6, 112, 111, 0, 0, 15, 1, 37, 81, 6, 13, 106, 50, 78, 34, 6, 35, 111, 63, 0, 0, 12, 1, 38, 77, 6, 132, 107, 82, 4, 112, 106, 0, 0, 0, 6, 65, 40, 79, 37, 0, 0, 0, 13, 1, 42, 77, 6, 132, 107, 91, 6, 128, 111, 0, 27, 0, 14, 1, 43, 77, 6, 132, 107, 49, 6, 39, 110, 66, 0, 27, 0, 6, 65, 44, 49, 112, 0, 0, 0, 0, 0, 8, 65, 48, 113, 55, 116, 106, 0, 0, 0, 6, 131, 22, 195, 172, 72, 0, 0, 8, 65, 52, 113, 63, 116, 106, 0, 0, 0, 0, 0, 12, 5, 95, 48, 1, 14, 4, 55, 4, 37, 65, 0, 8, 65, 56, 113, 50, 116, 106, 0, 0, 0, 0, 0, 0, 15, 1, 61, 77, 6, 132, 107, 10, 69, 6, 35, 106, 66, 0, 27, 0, 6, 131, 22, 195, 160, 72, 0, 0, 11, 1, 64, 112, 17, 49, 6, 114, 106, 66, 0, 6, 65, 64, 48, 36, 0, 0, 0, 0, 0, 7, 65, 68, 49, 58, 37, 0, 0, 8, 133, 13, 225, 187, 151, 9, 72, 0, 0, 0, 8, 65, 72, 113, 90, 116, 106, 0, 0, 0, 0, 0, 7, 65, 76, 113, 107, 87, 0, 0, 0, 0, 0, 6, 65, 80, 47, 36, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 65, 88, 82, 36, 0, 0, 0, 0, 0, 12, 65, 92, 82, 6, 36, 49, 4, 113, 107, 48, 0, 0, 0, 12, 1, 94, 77, 6, 132, 107, 63, 6, 40, 109, 0, 0, 0, 14, 1, 96, 77, 6, 132, 107, 105, 58, 6, 134, 106, 50, 0, 7, 65, 96, 37, 107, 78, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 65, 104, 86, 113, 107, 47, 0, 0, 0, 0, 0, 7, 132, 19, 225, 186, 189, 72, 0, 7, 132, 3, 195, 178, 14, 72, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 13, 225, 187, 141, 9, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 1, 126, 77, 6, 132, 107, 66, 6, 112, 109, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 14, 8, 225, 187, 175, 14, 7, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 20, 8, 195, 172, 72, 7, 132, 14, 8, 198, 176, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 4, 16, 20, 10, 81, 4, 119, 108, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 8, 15, 225, 186, 183, 3, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 135, 3, 8, 225, 186, 179, 14, 7, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 14, 8, 198, 176, 14, 7, 72, 0, 0, 0, 0, 0, 0, 0, 21, 3, 95, 50, 49, 105, 6, 118, 15, 63, 6, 135, 111, 57, 15, 63, 6, 39, 107, 72, 0, 0, 0, 0, 0, 21, 3, 95, 50, 53, 105, 6, 118, 15, 63, 6, 135, 111, 57, 15, 55, 6, 35, 111, 63, 0, 0, 0, 0, 0, 22, 3, 95, 51, 49, 10, 69, 6, 112, 15, 63, 6, 135, 111, 57, 15, 63, 6, 39, 107, 72, 0, 0, 0, 0, 0, 22, 3, 95, 51, 53, 10, 69, 6, 112, 15, 63, 6, 135, 111, 57, 15, 55, 6, 35, 111, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 22, 3, 95, 54, 49, 91, 6, 127, 107, 15, 63, 6, 135, 111, 57, 15, 63, 6, 39, 107, 72, 0, 0, 16, 3, 95, 51, 88, 10, 69, 6, 112, 15, 63, 6, 135, 111, 57, 0, 0, 11, 3, 95, 48, 67, 78, 34, 6, 35, 63, 0, 0, 0, 22, 3, 95, 54, 53, 91, 6, 127, 107, 15, 63, 6, 135, 111, 57, 15, 55, 6, 35, 111, 63, 0, 0, 0, 0, 0, 23, 3, 95, 55, 49, 10, 69, 6, 117, 108, 15, 63, 6, 135, 111, 57, 15, 63, 6, 39, 107, 72, 0, 0, 0, 0, 0, 23, 3, 95, 55, 53, 10, 69, 6, 117, 108, 15, 63, 6, 135, 111, 57, 15, 55, 6, 35, 111, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 14, 195, 170, 14, 72, 0, 17, 3, 95, 55, 88, 10, 69, 6, 117, 108, 15, 63, 6, 135, 111, 57, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 24, 3, 95, 52, 49, 10, 69, 6, 39, 107, 50, 15, 63, 6, 135, 111, 57, 15, 63, 6, 39, 107, 72, 0, 0, 11, 3, 95, 49, 88, 63, 6, 135, 106, 57, 0, 0, 0, 9, 134, 16, 8, 225, 186, 163, 9, 72, 0, 24, 3, 95, 52, 53, 10, 69, 6, 39, 107, 50, 15, 63, 6, 135, 111, 57, 15, 55, 6, 35, 111, 63, 0, 0, 0, 0, 0, 22, 3, 95, 53, 49, 50, 6, 35, 63, 15, 63, 6, 135, 111, 57, 15, 63, 6, 39, 107, 72, 0, 0, 6, 131, 12, 195, 160, 72, 15, 3, 95, 50, 88, 105, 6, 118, 15, 63, 6, 135, 111, 57, 0, 0, 0, 0, 8, 133, 196, 145, 225, 187, 131, 72, 22, 3, 95, 53, 53, 50, 6, 35, 63, 15, 63, 6, 135, 111, 57, 15, 55, 6, 35, 111, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 3, 95, 52, 88, 10, 69, 6, 39, 107, 50, 15, 63, 6, 135, 111, 57, 0, 0, 0, 0, 0, 0, 0, 0, 23, 3, 95, 56, 49, 72, 6, 112, 107, 63, 15, 63, 6, 135, 111, 57, 15, 63, 6, 39, 107, 72, 0, 0, 16, 3, 95, 53, 88, 50, 6, 35, 63, 15, 63, 6, 135, 111, 57, 0, 0, 0, 0, 23, 3, 95, 56, 53, 72, 6, 112, 107, 63, 15, 63, 6, 135, 111, 57, 15, 55, 6, 35, 111, 63, 0, 0, 0, 0, 0, 23, 3, 95, 57, 49, 78, 6, 37, 107, 50, 15, 63, 6, 135, 111, 57, 15, 63, 6, 39, 107, 72, 0, 0, 16, 3, 95, 54, 88, 91, 6, 127, 107, 15, 63, 6, 135, 111, 57, 0, 0, 0, 0, 23, 3, 95, 57, 53, 78, 6, 37, 107, 50, 15, 63, 6, 135, 111, 57, 15, 55, 6, 35, 111, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 3, 95, 56, 88, 72, 6, 112, 107, 63, 15, 63, 6, 135, 111, 57, 0, 0, 0, 0, 0, 0, 8, 133, 4, 225, 186, 171, 21, 72, 0, 0, 0, 17, 3, 95, 57, 88, 78, 6, 37, 107, 50, 15, 63, 6, 135, 111, 57, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 13, 195, 160, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 22, 225, 187, 155, 9, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 12, 195, 186, 3, 72, 0, 0, 0, 0, 0, 0, 0, 13, 4, 95, 48, 77, 50, 78, 34, 6, 134, 110, 58, 0, 0, 11, 4, 95, 48, 77, 51, 72, 6, 37, 108, 0, 0, 0, 12, 4, 95, 48, 77, 49, 66, 6, 112, 106, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 136, 11, 8, 15, 225, 186, 163, 14, 7, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 11, 8, 195, 180, 14, 7, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 20, 225, 187, 171, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 20, 225, 187, 155, 9, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 2, 196, 145, 70, 116, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 132, 2, 225, 187, 139, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 14, 225, 186, 191, 21, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 196, 145, 1, 14, 7, 72, 0, 0, 0, 19, 2, 95, 33, 77, 6, 132, 107, 78, 6, 13, 107, 63, 47, 6, 112, 111, 50, 0, 0, 0, 6, 195, 12, 243, 128, 72, 17, 2, 95, 39, 66, 58, 6, 35, 110, 137, 10, 70, 6, 116, 111, 50, 0, 0, 0, 11, 136, 196, 145, 198, 176, 225, 187, 163, 3, 72, 0, 0, 0, 0, 17, 2, 95, 41, 10, 70, 6, 114, 107, 66, 66, 58, 6, 35, 110, 137, 0, 0, 15, 2, 95, 40, 63, 6, 116, 108, 66, 58, 6, 35, 110, 137, 0, 0, 14, 2, 95, 47, 87, 6, 39, 108, 78, 34, 6, 118, 107, 0, 0, 10, 2, 95, 46, 78, 6, 13, 107, 63, 0, 0, 15, 2, 95, 45, 98, 6, 112, 110, 78, 66, 6, 112, 111, 66, 0, 0, 9, 2, 95, 44, 81, 6, 119, 108, 0, 0, 9, 2, 95, 51, 10, 69, 6, 112, 0, 0, 8, 133, 3, 8, 198, 176, 1, 72, 8, 2, 95, 50, 105, 6, 118, 0, 0, 10, 2, 95, 49, 63, 6, 39, 110, 72, 0, 0, 10, 2, 95, 48, 99, 4, 39, 17, 66, 0, 0, 10, 2, 95, 55, 10, 69, 6, 117, 108, 0, 0, 9, 2, 95, 54, 91, 6, 127, 107, 0, 0, 9, 2, 95, 53, 50, 6, 35, 63, 0, 0, 11, 2, 95, 52, 10, 69, 6, 39, 107, 50, 0, 0, 14, 2, 95, 59, 78, 6, 13, 107, 63, 81, 6, 119, 108, 0, 0, 14, 2, 95, 58, 105, 6, 118, 17, 78, 6, 13, 107, 63, 0, 0, 10, 2, 95, 57, 78, 6, 37, 107, 50, 0, 0, 10, 2, 95, 56, 72, 6, 112, 107, 63, 0, 0, 14, 2, 95, 63, 105, 6, 123, 108, 78, 6, 13, 107, 63, 0, 0, 15, 2, 95, 62, 55, 6, 116, 107, 50, 105, 6, 116, 111, 50, 0, 0, 0, 14, 2, 95, 60, 65, 6, 114, 108, 105, 6, 116, 111, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 133, 22, 225, 186, 171, 14, 72, 0, 0, 0, 0, 0, 0, 0, 0, 20, 2, 95, 91, 63, 6, 116, 108, 66, 58, 6, 35, 110, 137, 82, 6, 136, 111, 66, 0, 0, 18, 4, 95, 226, 128, 156, 66, 58, 6, 35, 110, 137, 49, 6, 113, 107, 48, 0, 0, 0, 0, 15, 2, 95, 95, 98, 6, 112, 110, 78, 77, 6, 135, 107, 57, 0, 0, 0, 22, 2, 95, 93, 10, 70, 6, 114, 107, 66, 66, 58, 6, 35, 110, 137, 82, 6, 136, 111, 66, 0, 0, 13, 2, 95, 92, 87, 6, 39, 108, 81, 4, 118, 108, 0, 0, 6, 195, 44, 130, 64, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 2, 95, 123, 63, 6, 116, 108, 66, 58, 6, 35, 110, 137, 65, 6, 114, 110, 50, 0, 0, 0, 0, 0, 0, 0, 22, 2, 95, 125, 10, 70, 6, 114, 107, 66, 66, 58, 6, 35, 110, 137, 65, 6, 114, 110, 50, 0, 0, 14, 2, 95, 124, 87, 6, 39, 108, 47, 6, 35, 108, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 70, 36, 229, 5, 72, 225, 84, 37, 50, 47, 116, 50, 6, 113, 107, 47, 0, 0, 0, 0, 0, 0, 0, 8, 133, 2, 225, 187, 159, 9, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 131, 4, 195, 185, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 12, 131, 192, 72, 0, 8, 133, 3, 225, 187, 167, 1, 72, 0, 0, 0, 7, 132, 3, 195, 161, 9, 72, 0, 0, 0, 0, 0, 0, 7, 132, 3, 195, 161, 3, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 134, 196, 145, 225, 186, 191, 14, 72, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 20, 0, 0, 97, 0, 0, 3, 224, 0, 0, 0, 97, 0, 1, 3, 225, 0, 0, 0, 97, 0, 9, 3, 163, 30, 0, 0, 97, 0, 3, 3, 227, 0, 0, 0, 97, 0, 35, 3, 161, 30, 0, 0, 3, 1, 0, 3, 177, 30, 0, 0, 3, 1, 1, 3, 175, 30, 0, 0, 3, 1, 9, 3, 179, 30, 0, 0, 3, 1, 3, 3, 181, 30, 0, 0, 3, 1, 35, 3, 183, 30, 0, 0, 226, 0, 0, 3, 167, 30, 0, 0, 226, 0, 1, 3, 165, 30, 0, 0, 226, 0, 9, 3, 169, 30, 0, 0, 226, 0, 3, 3, 171, 30, 0, 0, 226, 0, 35, 3, 173, 30, 0, 0, 101, 0, 0, 3, 232, 0, 0, 0, 101, 0, 1, 3, 233, 0, 0, 0, 101, 0, 9, 3, 187, 30, 0, 0, 101, 0, 3, 3, 189, 30, 0, 0, 101, 0, 35, 3, 185, 30, 0, 0, 234, 0, 0, 3, 193, 30, 0, 0, 234, 0, 1, 3, 191, 30, 0, 0, 234, 0, 9, 3, 195, 30, 0, 0, 234, 0, 3, 3, 197, 30, 0, 0, 234, 0, 35, 3, 199, 30, 0, 0, 105, 0, 0, 3, 236, 0, 0, 0, 105, 0, 1, 3, 237, 0, 0, 0, 105, 0, 9, 3, 201, 30, 0, 0, 105, 0, 3, 3, 41, 1, 0, 0, 105, 0, 35, 3, 203, 30, 0, 0, 111, 0, 0, 3, 242, 0, 0, 0, 111, 0, 1, 3, 243, 0, 0, 0, 111, 0, 9, 3, 207, 30, 0, 0, 111, 0, 3, 3, 245, 0, 0, 0, 111, 0, 35, 3, 205, 30, 0, 0, 244, 0, 0, 3, 211, 30, 0, 0, 244, 0, 1, 3, 209, 30, 0, 0, 244, 0, 9, 3, 213, 30, 0, 0, 244, 0, 3, 3, 215, 30, 0, 0, 244, 0, 35, 3, 217, 30, 0, 0, 161, 1, 0, 3, 221, 30, 0, 0, 161, 1, 1, 3, 219, 30, 0, 0, 161, 1, 9, 3, 223, 30, 0, 0, 161, 1, 3, 3, 225, 30, 0, 0, 161, 1, 35, 3, 227, 30, 0, 0, 117, 0, 0, 3, 249, 0, 0, 0, 117, 0, 1, 3, 250, 0, 0, 0, 117, 0, 9, 3, 231, 30, 0, 0, 117, 0, 3, 3, 105, 1, 0, 0, 117, 0, 35, 3, 229, 30, 0, 0, 176, 1, 0, 3, 235, 30, 0, 0, 176, 1, 1, 3, 233, 30, 0, 0, 176, 1, 9, 3, 237, 30, 0, 0, 176, 1, 3, 3, 239, 30, 0, 0, 176, 1, 35, 3, 241, 30, 0, 0, 121, 0, 0, 3, 243, 30, 0, 0, 121, 0, 1, 3, 253, 0, 0, 0, 121, 0, 9, 3, 247, 30, 0, 0, 121, 0, 3, 3, 249, 30, 0, 0, 121, 0, 35, 3, 245, 30, 0, 0, 0, 0, 0, 0, 6, 195, 160, 0, 3, 112, 106, 0, 121, 3, 117, 106, 0, 105, 3, 118, 106, 0, 117, 3, 127, 106, 0, 111, 3, 128, 106, 0, 7, 6, 195, 161, 0, 3, 112, 107, 0, 121, 3, 117, 107, 0, 105, 3, 118, 107, 0, 117, 3, 127, 107, 0, 111, 3, 128, 107, 0, 7, 6, 195, 162, 0, 3, 13, 0, 121, 3, 119, 0, 117, 3, 132, 0, 7, 6, 195, 163, 0, 3, 112, 109, 0, 121, 3, 117, 109, 0, 105, 3, 118, 109, 0, 117, 3, 127, 109, 0, 111, 3, 128, 109, 0, 7, 6, 195, 168, 0, 3, 113, 106, 0, 111, 3, 130, 106, 0, 7, 6, 195, 169, 0, 3, 113, 107, 0, 111, 3, 130, 107, 0, 7, 6, 195, 170, 0, 3, 36, 0, 117, 3, 129, 0, 7, 6, 195, 172, 0, 3, 37, 106, 0, 2, 17, 65, 3, 57, 106, 0, 117, 3, 131, 106, 0, 97, 3, 134, 106, 0, 7, 6, 195, 173, 0, 3, 37, 107, 0, 2, 17, 65, 3, 57, 107, 0, 117, 3, 131, 107, 0, 97, 3, 134, 107, 0, 7, 6, 195, 177, 0, 3, 65, 0, 7, 6, 195, 178, 0, 2, 17, 65, 3, 58, 106, 0, 3, 114, 106, 0, 105, 3, 123, 106, 0, 7, 6, 195, 179, 0, 2, 17, 65, 3, 58, 107, 0, 3, 114, 107, 0, 105, 3, 123, 107, 0, 7, 6, 195, 180, 0, 3, 39, 0, 105, 3, 124, 0, 7, 6, 195, 181, 0, 2, 17, 65, 3, 58, 109, 0, 3, 114, 109, 0, 105, 3, 123, 109, 0, 7, 6, 195, 185, 0, 3, 40, 106, 0, 2, 17, 65, 3, 58, 106, 0, 105, 3, 125, 106, 0, 97, 3, 136, 106, 0, 7, 6, 195, 186, 0, 3, 40, 107, 0, 2, 17, 65, 3, 58, 107, 0, 105, 3, 125, 107, 0, 97, 3, 136, 107, 0, 7, 6, 195, 189, 0, 3, 37, 107, 0, 2, 17, 65, 3, 57, 107, 0, 97, 3, 134, 107, 0, 7, 6, 196, 131, 0, 3, 35, 0, 7, 6, 196, 145, 0, 8, 3, 10, 70, 0, 3, 70, 0, 7, 6, 196, 169, 0, 3, 37, 109, 0, 2, 17, 65, 3, 57, 109, 0, 117, 3, 131, 109, 0, 97, 3, 134, 109, 0, 7, 6, 197, 169, 0, 3, 40, 109, 0, 2, 17, 65, 3, 58, 109, 0, 105, 3, 125, 109, 0, 97, 3, 136, 109, 0, 7, 6, 198, 161, 0, 3, 116, 0, 105, 3, 120, 0, 117, 3, 133, 0, 7, 6, 198, 176, 0, 3, 115, 0, 117, 3, 115, 58, 0, 105, 3, 126, 0, 4, 97, 3, 135, 0, 198, 161, 0, 198, 161, 105, 3, 135, 57, 0, 225, 187, 157, 105, 3, 135, 57, 106, 0, 225, 187, 155, 105, 3, 135, 57, 107, 0, 225, 187, 159, 105, 3, 135, 57, 108, 0, 225, 187, 161, 105, 3, 135, 57, 109, 0, 225, 187, 163, 105, 3, 135, 57, 110, 0, 198, 161, 117, 3, 135, 58, 0, 225, 187, 157, 117, 3, 135, 58, 106, 0, 225, 187, 155, 117, 3, 135, 58, 107, 0, 225, 187, 159, 117, 3, 135, 58, 108, 0, 225, 187, 161, 117, 3, 135, 58, 109, 0, 225, 187, 163, 117, 3, 135, 58, 110, 0, 225, 187, 157, 3, 135, 106, 0, 225, 187, 155, 3, 135, 107, 0, 225, 187, 159, 3, 135, 108, 0, 225, 187, 161, 3, 135, 109, 0, 225, 187, 163, 3, 135, 110, 0, 7, 6, 225, 186, 0, 163, 3, 112, 108, 0, 163, 121, 3, 117, 108, 0, 163, 105, 3, 118, 108, 0, 163, 117, 3, 127, 108, 0, 163, 111, 3, 128, 108, 0, 161, 3, 112, 110, 0, 161, 121, 3, 117, 110, 0, 161, 105, 3, 118, 110, 0, 161, 117, 3, 127, 110, 0, 161, 111, 3, 128, 110, 0, 177, 3, 35, 106, 0, 175, 3, 35, 107, 0, 179, 3, 35, 108, 0, 181, 3, 35, 109, 0, 183, 3, 35, 110, 0, 167, 3, 13, 106, 0, 167, 121, 3, 119, 106, 0, 167, 117, 3, 132, 106, 0, 165, 3, 13, 107, 0, 165, 121, 3, 119, 107, 0, 165, 117, 3, 132, 107, 0, 169, 3, 13, 108, 0, 169, 121, 3, 119, 108, 0, 169, 117, 3, 132, 108, 0, 171, 3, 13, 109, 0, 171, 121, 3, 119, 109, 0, 171, 117, 3, 132, 109, 0, 173, 3, 13, 110, 0, 173, 121, 3, 119, 110, 0, 173, 117, 3, 132, 110, 0, 187, 3, 113, 108, 0, 187, 111, 3, 130, 108, 0, 189, 3, 113, 109, 0, 189, 111, 3, 130, 109, 0, 185, 3, 113, 110, 0, 185, 111, 3, 130, 110, 0, 191, 3, 36, 107, 0, 191, 117, 3, 129, 107, 0, 7, 6, 225, 187, 0, 129, 3, 36, 106, 0, 129, 117, 3, 129, 106, 0, 131, 3, 36, 108, 0, 131, 117, 3, 129, 108, 0, 133, 3, 36, 109, 0, 133, 117, 3, 129, 109, 0, 135, 3, 36, 110, 0, 135, 117, 3, 129, 110, 0, 137, 3, 37, 108, 0, 137, 2, 17, 65, 3, 57, 108, 0, 137, 117, 3, 131, 108, 0, 137, 97, 3, 134, 108, 0, 139, 3, 37, 110, 0, 139, 2, 17, 65, 3, 57, 110, 0, 139, 117, 3, 131, 110, 0, 139, 97, 3, 134, 110, 0, 143, 2, 17, 65, 3, 58, 108, 0, 143, 3, 114, 108, 0, 143, 105, 3, 123, 108, 0, 141, 2, 17, 65, 3, 58, 110, 0, 141, 3, 114, 110, 0, 141, 105, 3, 123, 110, 0, 147, 3, 39, 106, 0, 147, 105, 3, 124, 106, 0, 145, 3, 39, 107, 0, 145, 105, 3, 124, 107, 0, 149, 3, 39, 108, 0, 149, 105, 3, 124, 108, 0, 151, 3, 39, 109, 0, 151, 105, 3, 124, 109, 0, 153, 3, 39, 110, 0, 153, 105, 3, 124, 110, 0, 157, 3, 116, 106, 0, 157, 105, 3, 120, 106, 0, 157, 117, 3, 133, 106, 0, 155, 3, 116, 107, 0, 155, 105, 3, 120, 107, 0, 155, 117, 3, 133, 107, 0, 159, 3, 116, 108, 0, 159, 105, 3, 120, 108, 0, 159, 117, 3, 133, 108, 0, 161, 3, 116, 109, 0, 161, 105, 3, 120, 109, 0, 161, 117, 3, 133, 109, 0, 163, 3, 116, 110, 0, 163, 105, 3, 120, 110, 0, 163, 117, 3, 133, 110, 0, 167, 3, 40, 108, 0, 167, 2, 17, 65, 3, 58, 108, 0, 167, 105, 3, 125, 108, 0, 167, 97, 3, 136, 108, 0, 165, 3, 40, 110, 0, 165, 2, 17, 65, 3, 58, 110, 0, 165, 105, 3, 125, 110, 0, 165, 97, 3, 136, 110, 0, 171, 117, 3, 115, 58, 106, 0, 171, 3, 115, 106, 0, 171, 105, 3, 126, 106, 0, 171, 97, 3, 135, 106, 0, 169, 117, 3, 115, 58, 107, 0, 169, 3, 115, 107, 0, 169, 105, 3, 126, 107, 0, 169, 97, 3, 135, 107, 0, 173, 117, 3, 115, 58, 108, 0, 173, 3, 115, 108, 0, 173, 105, 3, 126, 108, 0, 173, 97, 3, 135, 108, 0, 175, 117, 3, 115, 58, 109, 0, 175, 3, 115, 109, 0, 175, 105, 3, 126, 109, 0, 175, 97, 3, 135, 109, 0, 177, 117, 3, 115, 58, 110, 0, 177, 3, 115, 110, 0, 177, 105, 3, 126, 110, 0, 177, 97, 3, 135, 110, 0, 179, 3, 37, 106, 0, 179, 2, 17, 65, 3, 57, 106, 0, 179, 97, 3, 134, 106, 0, 183, 3, 37, 108, 0, 183, 2, 17, 65, 3, 57, 108, 0, 183, 97, 3, 134, 108, 0, 185, 3, 37, 109, 0, 185, 2, 17, 65, 3, 57, 109, 0, 185, 97, 3, 134, 109, 0, 181, 3, 37, 110, 0, 181, 2, 17, 65, 3, 57, 110, 0, 181, 97, 3, 134, 110, 0, 7, 6, 97, 0, 3, 112, 0, 121, 3, 117, 0, 225, 187, 179, 3, 117, 106, 0, 195, 189, 3, 117, 107, 0, 225, 187, 183, 3, 117, 108, 0, 225, 187, 185, 3, 117, 109, 0, 225, 187, 181, 3, 117, 110, 0, 105, 3, 118, 0, 195, 172, 3, 118, 106, 0, 195, 173, 3, 118, 107, 0, 225, 187, 137, 3, 118, 108, 0, 196, 169, 3, 118, 109, 0, 225, 187, 139, 3, 118, 110, 0, 117, 3, 127, 0, 195, 185, 3, 127, 106, 0, 195, 186, 3, 127, 107, 0, 225, 187, 167, 3, 127, 108, 0, 197, 169, 3, 127, 109, 0, 225, 187, 165, 3, 127, 110, 0, 111, 3, 128, 0, 195, 178, 3, 128, 106, 0, 195, 179, 3, 128, 107, 0, 225, 187, 143, 3, 128, 108, 0, 195, 181, 3, 128, 109, 0, 225, 187, 141, 3, 128, 110, 0, 7, 6, 98, 0, 8, 3, 10, 69, 0, 3, 69, 0, 7, 6, 99, 0, 3, 49, 0, 104, 3, 78, 0, 2, 32, 3, 137, 0, 7, 6, 100, 0, 3, 77, 0, 7, 6, 101, 0, 3, 113, 0, 111, 3, 130, 0, 195, 178, 3, 130, 106, 0, 195, 179, 3, 130, 107, 0, 225, 187, 143, 3, 130, 108, 0, 225, 187, 151, 3, 130, 109, 0, 225, 187, 141, 3, 130, 110, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 4, 2, 105, 3, 84, 0, 2, 195, 172, 0, 2, 195, 173, 0, 2, 196, 169, 0, 2, 225, 187, 137, 0, 2, 225, 187, 139, 0, 105, 0, 4, 3, 98, 0, 104, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 2, 17, 65, 3, 57, 0, 117, 3, 131, 0, 195, 185, 3, 131, 106, 0, 195, 186, 3, 131, 107, 0, 225, 187, 167, 3, 131, 108, 0, 197, 169, 3, 131, 109, 0, 225, 187, 165, 3, 131, 110, 0, 4, 97, 3, 134, 0, 195, 170, 0, 4, 195, 160, 3, 134, 106, 0, 225, 187, 129, 0, 4, 195, 161, 3, 134, 107, 0, 225, 186, 191, 0, 4, 225, 186, 163, 3, 134, 108, 0, 225, 187, 131, 0, 4, 195, 163, 3, 134, 109, 0, 225, 187, 133, 0, 4, 225, 186, 161, 3, 134, 110, 0, 225, 187, 135, 0, 7, 6, 106, 0, 3, 88, 0, 7, 6, 107, 0, 3, 49, 0, 104, 3, 99, 0, 2, 32, 3, 137, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 3, 63, 0, 7, 6, 110, 0, 3, 50, 0, 104, 3, 65, 0, 4, 103, 3, 66, 0, 103, 104, 0, 7, 6, 111, 0, 2, 17, 65, 3, 58, 0, 3, 114, 0, 105, 3, 123, 0, 195, 172, 3, 123, 106, 0, 195, 173, 3, 123, 107, 0, 225, 187, 137, 3, 123, 108, 0, 196, 169, 3, 123, 109, 0, 225, 187, 139, 3, 123, 110, 0, 7, 6, 112, 0, 3, 48, 0, 104, 3, 81, 0, 7, 6, 113, 0, 3, 49, 0, 117, 3, 49, 58, 0, 2, 32, 3, 137, 0, 7, 6, 114, 0, 3, 90, 0, 7, 6, 115, 0, 3, 91, 0, 7, 6, 116, 0, 104, 3, 47, 0, 3, 72, 0, 114, 3, 78, 34, 0, 7, 6, 117, 0, 3, 40, 0, 4, 1, 17, 65, 3, 58, 0, 2, 17, 65, 0, 105, 3, 125, 0, 195, 172, 3, 125, 106, 0, 195, 173, 3, 125, 107, 0, 225, 187, 137, 3, 125, 108, 0, 196, 169, 3, 125, 109, 0, 225, 187, 139, 3, 125, 110, 0, 4, 97, 3, 136, 0, 195, 180, 0, 195, 180, 105, 3, 136, 57, 0, 225, 187, 147, 105, 3, 136, 57, 106, 0, 225, 187, 145, 105, 3, 136, 57, 107, 0, 225, 187, 149, 105, 3, 136, 57, 108, 0, 225, 187, 151, 105, 3, 136, 57, 109, 0, 225, 187, 153, 105, 3, 136, 57, 110, 0, 4, 195, 160, 3, 136, 106, 0, 225, 187, 147, 0, 4, 195, 161, 3, 136, 107, 0, 225, 187, 145, 0, 4, 225, 186, 163, 3, 136, 108, 0, 225, 187, 149, 0, 4, 195, 163, 3, 136, 109, 0, 225, 187, 151, 0, 4, 225, 186, 161, 3, 136, 110, 0, 225, 187, 153, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 87, 0, 7, 6, 121, 0, 3, 37, 0, 2, 17, 65, 3, 57, 0, 4, 97, 3, 134, 0, 195, 170, 0, 4, 195, 160, 3, 134, 106, 0, 225, 187, 129, 0, 4, 195, 161, 3, 134, 107, 0, 225, 186, 191, 0, 4, 225, 186, 163, 3, 134, 108, 0, 225, 187, 131, 0, 4, 195, 163, 3, 134, 109, 0, 225, 187, 133, 0, 4, 225, 186, 161, 3, 134, 110, 0, 225, 187, 135, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 206, 0, 4, 174, 3, 36, 17, 23, 72, 6, 112, 17, 0, 183, 0, 4, 175, 3, 37, 17, 23, 6, 39, 17, 23, 72, 6, 112, 17, 0, 185, 0, 191, 3, 39, 17, 23, 63, 6, 37, 17, 23, 49, 90, 6, 114, 111, 50, 0, 184, 3, 47, 6, 36, 17, 23, 72, 6, 112, 17, 0, 186, 3, 49, 6, 112, 17, 48, 23, 48, 6, 112, 17, 0, 189, 3, 50, 58, 6, 37, 17, 0, 187, 3, 55, 6, 35, 17, 63, 23, 10, 70, 6, 112, 17, 0, 188, 3, 63, 58, 6, 37, 17, 0, 178, 3, 69, 6, 36, 17, 23, 72, 6, 112, 17, 0, 180, 3, 77, 6, 113, 17, 50, 23, 72, 6, 112, 17, 0, 182, 3, 84, 6, 36, 17, 23, 72, 6, 112, 17, 0, 190, 3, 87, 6, 37, 111, 0, 179, 3, 98, 6, 112, 17, 23, 63, 6, 112, 17, 0, 4, 172, 3, 112, 17, 50, 23, 81, 6, 112, 17, 0, 177, 0, 4, 173, 3, 113, 17, 48, 23, 87, 6, 37, 17, 23, 55, 6, 114, 17, 50, 0, 181, 0, 7, 6, 207, 0, 4, 137, 3, 39, 17, 23, 63, 6, 36, 17, 23, 98, 6, 112, 111, 0, 142, 0, 140, 3, 39, 17, 23, 63, 6, 37, 17, 23, 49, 90, 6, 114, 111, 50, 0, 4, 133, 3, 40, 17, 48, 23, 87, 6, 37, 17, 23, 55, 6, 114, 17, 50, 0, 141, 0, 128, 3, 48, 6, 37, 17, 0, 136, 3, 48, 87, 6, 37, 17, 0, 132, 3, 72, 6, 39, 17, 0, 135, 3, 78, 6, 37, 17, 0, 134, 3, 81, 6, 37, 17, 0, 4, 130, 3, 87, 6, 37, 107, 78, 23, 63, 6, 112, 17, 0, 131, 0, 129, 3, 90, 6, 39, 17, 0, 7, 6, 0, 4, 33, 2, 33, 3, 0, 46, 1, 46, 3, 0, 46, 2, 46, 3, 9, 0, 33, 3, 9, 78, 6, 13, 107, 63, 23, 47, 6, 112, 111, 50, 9, 0, 4, 45, 1, 32, 17, 65, 2, 32, 15, 3, 10, 0, 45, 1, 32, 17, 67, 2, 32, 15, 0, 62, 61, 3, 55, 6, 116, 107, 50, 23, 105, 6, 116, 17, 50, 23, 105, 58, 4, 35, 110, 137, 10, 69, 6, 35, 106, 66, 0, 60, 61, 3, 65, 6, 114, 108, 23, 105, 6, 116, 17, 50, 23, 105, 58, 4, 35, 110, 137, 10, 69, 6, 35, 106, 66, 0, 36, 3, 70, 6, 39, 15, 55, 6, 35, 0, 46, 3, 78, 6, 13, 107, 63, 10, 0, 45, 8, 32, 2, 32, 15, 3, 78, 34, 6, 115, 106, 0, 37, 3, 81, 6, 13, 106, 50, 15, 76, 6, 35, 63, 0, 104, 1, 32, 15, 2, 32, 15, 15, 32, 3, 84, 6, 116, 106, 0, 33, 61, 3, 99, 4, 39, 17, 66, 23, 10, 69, 6, 35, 106, 66, 10, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts63 = FileInMemory_createWithData (5836, reinterpret_cast (&espeakdata_dicts63_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/vi_dict", L"vi"); Collection_addItem (me.peek(), espeakdata_dicts63.transfer()); static unsigned char espeakdata_dicts64_data[1735] = { 0, 4, 0, 0, 85, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 5, 95, 48, 1, 14, 4, 2, 35, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 51, 88, 65, 6, 109, 47, 12, 81, 40, 49, 12, 0, 0, 12, 3, 95, 48, 67, 47, 6, 108, 63, 108, 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, 12, 3, 95, 49, 67, 47, 6, 108, 63, 108, 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19, 3, 95, 55, 88, 77, 6, 40, 52, 114, 63, 65, 111, 52, 81, 40, 49, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 95, 49, 88, 81, 6, 40, 49, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 3, 95, 50, 88, 65, 6, 111, 52, 81, 40, 49, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 15, 3, 95, 52, 88, 65, 6, 110, 50, 47, 81, 40, 49, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 3, 95, 53, 88, 77, 6, 40, 52, 114, 63, 81, 40, 49, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 54, 88, 77, 6, 40, 52, 114, 63, 69, 109, 50, 12, 81, 40, 49, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 56, 88, 77, 6, 40, 52, 114, 63, 65, 109, 47, 12, 81, 40, 49, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 3, 95, 57, 88, 77, 6, 40, 52, 114, 63, 65, 110, 50, 47, 81, 40, 49, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 17, 4, 95, 48, 77, 50, 47, 6, 35, 63, 50, 70, 35, 52, 110, 47, 0, 0, 0, 0, 13, 4, 95, 48, 77, 49, 77, 6, 40, 50, 12, 37, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 2, 95, 51, 65, 6, 109, 47, 12, 0, 0, 9, 2, 95, 50, 65, 6, 111, 52, 0, 0, 10, 2, 95, 49, 69, 6, 109, 50, 12, 0, 0, 9, 2, 95, 48, 47, 6, 40, 87, 0, 0, 14, 2, 95, 55, 77, 6, 40, 52, 114, 63, 65, 111, 52, 0, 0, 15, 2, 95, 54, 77, 6, 40, 52, 114, 63, 69, 109, 50, 12, 0, 0, 11, 2, 95, 53, 77, 6, 40, 52, 114, 63, 0, 0, 10, 2, 95, 52, 65, 6, 110, 50, 47, 0, 0, 0, 0, 15, 2, 95, 57, 77, 6, 40, 52, 114, 63, 65, 110, 50, 47, 0, 0, 15, 2, 95, 56, 77, 6, 40, 52, 114, 63, 65, 109, 47, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 195, 169, 0, 3, 36, 0, 4, 101, 3, 108, 0, 195, 169, 0, 7, 6, 195, 171, 0, 3, 13, 0, 4, 101, 3, 106, 0, 195, 171, 0, 7, 6, 195, 177, 0, 3, 65, 0, 7, 6, 195, 179, 0, 3, 39, 0, 4, 111, 3, 114, 0, 195, 179, 0, 7, 6, 197, 139, 0, 1, 25, 2, 25, 3, 43, 0, 3, 66, 0, 197, 139, 3, 66, 12, 0, 7, 6, 97, 0, 3, 35, 0, 97, 3, 111, 0, 7, 6, 98, 0, 3, 69, 0, 98, 3, 69, 12, 0, 7, 6, 99, 0, 3, 78, 0, 99, 3, 78, 12, 0, 7, 6, 100, 0, 3, 70, 0, 100, 3, 70, 12, 0, 7, 6, 101, 0, 3, 109, 0, 101, 3, 110, 0, 7, 6, 102, 0, 3, 81, 0, 7, 6, 103, 0, 3, 79, 0, 103, 3, 79, 12, 0, 7, 6, 104, 0, 3, 105, 0, 7, 6, 105, 0, 3, 37, 0, 105, 3, 107, 0, 7, 6, 106, 0, 3, 77, 0, 3, 77, 12, 0, 7, 6, 107, 0, 3, 49, 0, 107, 3, 49, 12, 0, 7, 6, 108, 0, 3, 55, 0, 7, 6, 109, 0, 1, 25, 2, 25, 3, 41, 0, 3, 63, 0, 109, 3, 63, 12, 0, 7, 6, 110, 0, 1, 25, 2, 25, 3, 42, 0, 3, 50, 0, 110, 3, 50, 12, 0, 7, 6, 111, 0, 3, 112, 0, 111, 3, 113, 0, 7, 6, 112, 0, 3, 48, 0, 112, 3, 48, 12, 0, 7, 6, 113, 0, 3, 102, 0, 113, 3, 102, 12, 0, 7, 6, 114, 0, 2, 114, 3, 51, 0, 3, 52, 0, 7, 6, 115, 0, 3, 87, 0, 115, 3, 87, 116, 0, 7, 6, 116, 0, 3, 47, 0, 116, 3, 47, 12, 0, 7, 6, 117, 0, 3, 40, 0, 117, 3, 115, 0, 7, 6, 118, 0, 3, 82, 0, 7, 6, 119, 0, 3, 58, 0, 7, 6, 120, 0, 3, 99, 0, 7, 6, 121, 0, 3, 57, 0, 7, 6, 122, 0, 3, 86, 0, 7, 6, 0, 36, 3, 70, 112, 55, 35, 52, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts64 = FileInMemory_createWithData (1734, reinterpret_cast (&espeakdata_dicts64_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/wo_dict", L"wo"); Collection_addItem (me.peek(), espeakdata_dicts64.transfer()); static unsigned char espeakdata_dicts65_data[41828] = { 0, 4, 0, 0, 94, 157, 0, 0, 10, 3, 229, 185, 178, 103, 97, 110, 49, 0, 12, 3, 232, 172, 138, 104, 117, 97, 110, 103, 51, 0, 10, 3, 233, 165, 146, 114, 97, 111, 50, 0, 10, 3, 232, 175, 162, 120, 117, 110, 50, 0, 11, 3, 233, 164, 138, 121, 97, 110, 103, 51, 0, 0, 10, 3, 230, 178, 185, 121, 111, 117, 50, 0, 10, 3, 232, 175, 161, 103, 117, 105, 51, 0, 9, 3, 230, 189, 145, 112, 111, 53, 0, 12, 3, 233, 166, 153, 120, 105, 97, 110, 103, 49, 0, 0, 10, 3, 231, 181, 144, 106, 105, 101, 50, 0, 9, 3, 233, 154, 184, 108, 105, 52, 0, 9, 3, 230, 176, 168, 97, 110, 49, 0, 11, 3, 229, 186, 184, 121, 111, 110, 103, 49, 0, 10, 3, 233, 153, 176, 121, 105, 110, 49, 0, 10, 3, 230, 177, 176, 116, 97, 105, 52, 0, 9, 3, 231, 183, 160, 100, 105, 52, 0, 10, 3, 230, 178, 184, 102, 101, 105, 52, 0, 12, 3, 232, 161, 176, 115, 104, 117, 97, 105, 49, 0, 0, 9, 3, 232, 179, 128, 104, 101, 52, 0, 11, 3, 231, 189, 144, 103, 117, 97, 110, 52, 0, 0, 9, 3, 232, 183, 161, 106, 105, 49, 0, 10, 3, 231, 178, 185, 99, 117, 105, 52, 0, 10, 3, 230, 184, 169, 119, 101, 110, 49, 0, 11, 3, 231, 189, 145, 119, 97, 110, 103, 51, 0, 10, 3, 232, 169, 177, 104, 117, 97, 52, 0, 0, 10, 3, 232, 169, 178, 103, 97, 105, 49, 0, 11, 3, 232, 168, 170, 102, 97, 110, 103, 51, 0, 10, 3, 232, 180, 138, 122, 97, 110, 52, 0, 7, 65, 4, 129, 113, 0, 29, 0, 11, 3, 231, 187, 131, 108, 105, 97, 110, 52, 0, 12, 3, 232, 169, 179, 120, 105, 97, 110, 103, 50, 0, 11, 3, 231, 176, 171, 120, 105, 97, 111, 49, 0, 9, 3, 231, 177, 179, 109, 105, 51, 0, 0, 9, 3, 233, 173, 148, 109, 111, 50, 0, 9, 3, 232, 170, 188, 121, 105, 52, 0, 10, 3, 232, 181, 148, 112, 101, 105, 50, 0, 9, 3, 231, 187, 132, 122, 117, 51, 0, 9, 3, 230, 184, 172, 99, 101, 52, 0, 0, 11, 3, 231, 187, 133, 115, 104, 101, 110, 49, 0, 10, 3, 232, 168, 173, 115, 104, 101, 52, 0, 9, 3, 233, 161, 181, 121, 101, 52, 0, 10, 3, 233, 160, 173, 116, 111, 117, 50, 0, 0, 11, 3, 233, 161, 182, 100, 105, 110, 103, 51, 0, 11, 3, 231, 178, 190, 106, 105, 110, 103, 49, 0, 9, 3, 231, 187, 134, 120, 105, 52, 0, 10, 3, 232, 181, 150, 108, 97, 105, 52, 0, 11, 3, 231, 188, 142, 100, 117, 97, 110, 52, 0, 8, 65, 8, 48, 37, 113, 0, 29, 0, 11, 3, 232, 182, 159, 116, 97, 110, 103, 52, 0, 9, 3, 232, 179, 135, 122, 105, 49, 0, 10, 3, 231, 187, 135, 122, 104, 105, 49, 0, 11, 3, 232, 170, 191, 100, 105, 97, 111, 52, 0, 11, 3, 230, 184, 175, 103, 97, 110, 103, 51, 0, 11, 3, 233, 161, 183, 113, 105, 110, 103, 51, 0, 0, 12, 3, 231, 187, 136, 122, 104, 111, 110, 103, 49, 0, 10, 3, 232, 183, 168, 107, 117, 97, 52, 0, 10, 3, 233, 160, 176, 106, 105, 97, 50, 0, 11, 3, 233, 175, 168, 106, 105, 110, 103, 49, 0, 0, 11, 3, 231, 190, 161, 120, 105, 97, 110, 52, 0, 9, 3, 232, 168, 177, 120, 117, 51, 0, 12, 3, 233, 161, 185, 120, 105, 97, 110, 103, 52, 0, 0, 12, 3, 232, 181, 154, 122, 104, 117, 97, 110, 52, 0, 11, 3, 233, 161, 186, 115, 104, 117, 110, 52, 0, 10, 3, 232, 179, 138, 122, 101, 105, 50, 0, 9, 3, 233, 173, 154, 121, 117, 50, 0, 9, 3, 233, 170, 130, 109, 97, 52, 0, 10, 3, 232, 183, 170, 103, 117, 105, 52, 0, 9, 3, 231, 189, 154, 102, 97, 50, 0, 8, 65, 12, 87, 129, 115, 0, 29, 0, 11, 3, 231, 188, 147, 104, 117, 97, 110, 51, 0, 9, 3, 233, 161, 187, 120, 117, 49, 0, 10, 3, 231, 177, 187, 108, 101, 105, 52, 0, 9, 3, 232, 182, 163, 113, 117, 52, 0, 10, 3, 232, 181, 155, 115, 97, 105, 52, 0, 0, 9, 3, 230, 184, 180, 107, 101, 51, 0, 10, 3, 231, 190, 164, 113, 117, 110, 50, 0, 9, 3, 231, 188, 148, 100, 105, 52, 0, 9, 3, 232, 168, 180, 115, 117, 53, 0, 11, 3, 233, 170, 132, 106, 105, 97, 111, 49, 0, 0, 10, 3, 233, 161, 189, 119, 97, 110, 50, 0, 9, 3, 231, 177, 189, 122, 105, 51, 0, 11, 3, 231, 187, 141, 115, 104, 97, 111, 52, 0, 9, 3, 231, 188, 149, 108, 118, 51, 0, 0, 10, 3, 232, 181, 158, 122, 97, 110, 52, 0, 11, 3, 231, 188, 150, 98, 105, 97, 110, 49, 0, 10, 3, 230, 185, 190, 119, 97, 110, 49, 0, 9, 3, 233, 161, 190, 103, 117, 52, 0, 10, 3, 233, 170, 134, 108, 117, 111, 52, 0, 8, 65, 16, 47, 37, 113, 0, 29, 0, 11, 3, 231, 187, 143, 106, 105, 110, 103, 49, 0, 9, 3, 232, 183, 175, 108, 117, 52, 0, 10, 3, 233, 161, 191, 100, 117, 110, 52, 0, 10, 3, 230, 185, 191, 115, 104, 105, 49, 0, 0, 9, 3, 232, 182, 168, 113, 117, 49, 0, 11, 3, 231, 188, 152, 121, 117, 97, 110, 50, 0, 11, 3, 233, 160, 184, 106, 105, 110, 103, 51, 0, 9, 3, 231, 176, 184, 98, 111, 51, 0, 10, 3, 230, 184, 184, 121, 111, 117, 50, 0, 11, 3, 231, 190, 168, 120, 105, 97, 110, 52, 0, 0, 9, 3, 231, 190, 169, 121, 105, 52, 0, 11, 3, 231, 187, 145, 98, 97, 110, 103, 51, 0, 10, 3, 232, 177, 129, 104, 117, 111, 49, 0, 10, 3, 231, 185, 129, 102, 97, 110, 50, 0, 0, 9, 3, 231, 188, 154, 102, 117, 52, 0, 9, 3, 231, 189, 162, 98, 97, 53, 0, 11, 3, 230, 184, 186, 109, 105, 97, 111, 51, 0, 11, 3, 232, 168, 186, 122, 104, 101, 110, 51, 0, 11, 3, 231, 187, 146, 114, 111, 110, 103, 50, 0, 8, 65, 20, 57, 37, 113, 0, 29, 0, 10, 3, 231, 187, 147, 106, 105, 101, 50, 0, 11, 3, 232, 183, 179, 116, 105, 97, 111, 52, 0, 11, 3, 231, 185, 131, 98, 101, 110, 103, 51, 0, 10, 3, 233, 160, 187, 112, 105, 110, 50, 0, 10, 3, 232, 179, 147, 98, 105, 110, 49, 0, 0, 10, 3, 233, 170, 140, 121, 97, 110, 52, 0, 9, 3, 231, 186, 140, 120, 117, 52, 0, 10, 3, 232, 178, 140, 109, 97, 111, 52, 0, 12, 3, 232, 168, 188, 122, 104, 101, 110, 103, 52, 0, 9, 3, 233, 171, 148, 116, 105, 51, 0, 10, 3, 232, 181, 164, 99, 104, 105, 52, 0, 0, 10, 3, 231, 187, 149, 114, 97, 111, 52, 0, 9, 3, 233, 169, 133, 113, 117, 49, 0, 11, 3, 231, 188, 157, 102, 101, 110, 103, 52, 0, 10, 3, 232, 180, 157, 98, 101, 105, 52, 0, 11, 3, 231, 176, 189, 113, 105, 97, 110, 49, 0, 11, 3, 232, 183, 181, 106, 105, 97, 110, 52, 0, 0, 11, 3, 233, 174, 174, 120, 105, 97, 110, 49, 0, 10, 3, 232, 177, 134, 100, 111, 117, 52, 0, 10, 3, 230, 184, 190, 104, 117, 110, 50, 0, 8, 65, 24, 125, 111, 81, 0, 29, 0, 11, 3, 231, 186, 143, 99, 104, 97, 110, 50, 0, 9, 3, 232, 180, 159, 102, 117, 52, 0, 0, 9, 3, 232, 177, 136, 113, 105, 51, 0, 10, 3, 233, 171, 152, 103, 97, 111, 49, 0, 10, 3, 231, 187, 152, 104, 117, 105, 52, 0, 11, 3, 231, 188, 160, 99, 104, 97, 110, 50, 0, 0, 11, 3, 232, 176, 129, 115, 104, 117, 105, 50, 0, 11, 3, 231, 189, 169, 122, 104, 97, 111, 52, 0, 11, 3, 231, 191, 185, 113, 105, 97, 111, 52, 0, 9, 3, 233, 170, 145, 113, 105, 50, 0, 11, 3, 232, 180, 161, 103, 111, 110, 103, 52, 0, 10, 3, 231, 187, 153, 103, 101, 105, 51, 0, 0, 11, 3, 231, 187, 154, 120, 117, 97, 110, 52, 0, 10, 3, 232, 180, 162, 99, 97, 105, 50, 0, 10, 3, 232, 183, 186, 100, 117, 111, 52, 0, 10, 3, 231, 189, 170, 122, 117, 105, 52, 0, 8, 65, 28, 122, 37, 113, 0, 29, 0, 11, 3, 232, 176, 131, 100, 105, 97, 111, 52, 0, 9, 3, 232, 180, 163, 122, 101, 50, 0, 9, 3, 232, 182, 179, 122, 117, 50, 0, 10, 3, 232, 178, 147, 109, 97, 111, 49, 0, 10, 3, 231, 191, 187, 102, 97, 110, 49, 0, 0, 10, 3, 231, 187, 156, 108, 117, 111, 52, 0, 9, 3, 232, 182, 180, 112, 97, 49, 0, 10, 3, 232, 177, 140, 119, 97, 110, 49, 0, 9, 3, 231, 191, 188, 121, 105, 52, 0, 0, 10, 3, 232, 180, 165, 98, 97, 105, 52, 0, 12, 3, 232, 176, 133, 108, 105, 97, 110, 103, 52, 0, 10, 3, 231, 187, 157, 106, 117, 101, 50, 0, 0, 12, 3, 232, 179, 158, 115, 104, 97, 110, 103, 51, 0, 11, 3, 231, 186, 150, 120, 105, 97, 110, 49, 0, 10, 3, 232, 177, 142, 115, 104, 117, 52, 0, 10, 3, 231, 189, 174, 122, 104, 105, 52, 0, 8, 65, 32, 129, 111, 123, 0, 29, 0, 11, 3, 233, 170, 151, 112, 105, 97, 110, 52, 0, 11, 3, 231, 187, 159, 116, 111, 110, 103, 51, 0, 10, 3, 232, 180, 167, 104, 117, 111, 52, 0, 10, 3, 233, 172, 167, 110, 97, 111, 52, 0, 0, 10, 3, 231, 182, 184, 108, 117, 110, 50, 0, 9, 3, 232, 173, 176, 121, 105, 52, 0, 11, 3, 231, 178, 152, 122, 104, 97, 110, 49, 0, 9, 3, 233, 160, 136, 120, 117, 49, 0, 9, 3, 233, 162, 152, 116, 105, 50, 0, 10, 3, 230, 189, 176, 107, 117, 105, 52, 0, 10, 3, 233, 165, 176, 115, 104, 105, 52, 0, 9, 3, 232, 168, 136, 106, 105, 52, 0, 10, 3, 232, 170, 152, 121, 111, 117, 52, 0, 11, 3, 233, 164, 168, 103, 117, 97, 110, 51, 0, 9, 3, 232, 174, 184, 120, 117, 51, 0, 0, 10, 3, 233, 165, 177, 98, 97, 111, 51, 0, 11, 3, 231, 181, 177, 116, 111, 110, 103, 51, 0, 10, 3, 230, 187, 161, 109, 97, 110, 51, 0, 11, 3, 231, 191, 129, 119, 101, 110, 103, 49, 0, 11, 3, 230, 188, 169, 120, 117, 97, 110, 50, 0, 0, 9, 3, 233, 163, 162, 106, 105, 49, 0, 9, 3, 233, 165, 178, 115, 105, 52, 0, 10, 3, 232, 168, 138, 120, 117, 110, 52, 0, 10, 3, 232, 174, 186, 108, 117, 110, 52, 0, 9, 3, 231, 181, 178, 115, 105, 49, 0, 7, 65, 36, 125, 113, 0, 29, 0, 10, 3, 230, 188, 171, 109, 97, 110, 52, 0, 10, 3, 232, 183, 131, 121, 117, 101, 52, 0, 9, 3, 231, 180, 171, 122, 105, 51, 0, 0, 11, 3, 232, 174, 188, 115, 111, 110, 103, 52, 0, 11, 3, 232, 173, 180, 113, 105, 97, 110, 51, 0, 11, 3, 233, 160, 140, 115, 111, 110, 103, 52, 0, 10, 3, 230, 186, 156, 108, 105, 117, 49, 0, 10, 3, 233, 162, 156, 121, 97, 110, 50, 0, 10, 3, 232, 172, 172, 109, 105, 117, 52, 0, 11, 3, 231, 178, 156, 116, 105, 97, 111, 52, 0, 0, 10, 3, 230, 187, 165, 108, 97, 110, 52, 0, 11, 3, 232, 169, 149, 112, 105, 110, 103, 50, 0, 10, 3, 231, 191, 133, 99, 104, 105, 52, 0, 8, 3, 233, 162, 157, 101, 50, 0, 10, 3, 230, 186, 157, 103, 111, 117, 49, 0, 11, 3, 232, 174, 189, 102, 101, 110, 103, 51, 0, 0, 10, 3, 232, 174, 190, 115, 104, 101, 52, 0, 9, 3, 232, 170, 158, 121, 117, 51, 0, 10, 3, 233, 165, 182, 114, 97, 111, 50, 0, 10, 3, 232, 168, 142, 116, 97, 111, 51, 0, 9, 3, 230, 185, 150, 104, 117, 50, 0, 8, 65, 40, 122, 129, 113, 0, 29, 0, 9, 3, 232, 173, 183, 104, 117, 52, 0, 12, 3, 231, 179, 167, 108, 105, 97, 110, 103, 50, 0, 11, 3, 231, 182, 191, 109, 105, 97, 110, 50, 0, 11, 3, 232, 174, 191, 102, 97, 110, 103, 51, 0, 10, 3, 231, 180, 175, 108, 101, 105, 52, 0, 0, 9, 3, 231, 180, 176, 120, 105, 52, 0, 12, 3, 232, 170, 160, 99, 104, 101, 110, 103, 50, 0, 11, 3, 230, 184, 144, 106, 105, 97, 110, 52, 0, 10, 3, 230, 187, 168, 98, 105, 110, 49, 0, 9, 3, 233, 160, 144, 121, 117, 52, 0, 11, 3, 233, 162, 160, 100, 105, 97, 110, 49, 0, 0, 11, 3, 232, 182, 129, 99, 104, 101, 110, 52, 0, 10, 3, 233, 160, 145, 119, 97, 110, 50, 0, 10, 3, 232, 170, 161, 106, 105, 101, 52, 0, 9, 3, 233, 175, 137, 108, 105, 51, 0, 11, 3, 231, 181, 185, 106, 117, 97, 110, 52, 0, 10, 3, 230, 187, 169, 116, 97, 110, 49, 0, 0, 11, 3, 233, 165, 186, 106, 105, 97, 111, 51, 0, 12, 3, 230, 188, 178, 122, 104, 97, 110, 103, 51, 0, 10, 3, 233, 160, 146, 98, 97, 110, 49, 0, 8, 65, 44, 118, 129, 113, 0, 29, 0, 10, 3, 233, 160, 147, 100, 117, 110, 52, 0, 9, 3, 232, 170, 163, 119, 117, 49, 0, 11, 3, 231, 180, 179, 115, 104, 101, 110, 49, 0, 10, 3, 232, 168, 147, 120, 117, 110, 52, 0, 11, 3, 233, 161, 155, 100, 105, 97, 110, 49, 0, 0, 9, 3, 230, 184, 148, 121, 117, 50, 0, 11, 3, 233, 162, 164, 99, 104, 97, 110, 52, 0, 11, 3, 233, 165, 188, 98, 105, 110, 103, 51, 0, 9, 3, 232, 170, 164, 119, 117, 52, 0, 10, 3, 232, 183, 140, 100, 105, 101, 49, 0, 0, 11, 3, 232, 182, 133, 99, 104, 97, 111, 49, 0, 9, 3, 232, 173, 189, 121, 117, 52, 0, 11, 3, 231, 178, 165, 122, 104, 111, 117, 49, 0, 0, 9, 3, 232, 169, 158, 99, 105, 50, 0, 10, 3, 233, 161, 158, 108, 101, 105, 52, 0, 11, 3, 232, 170, 166, 115, 111, 110, 103, 52, 0, 8, 65, 48, 125, 111, 55, 0, 29, 0, 8, 3, 233, 165, 191, 101, 52, 0, 11, 3, 230, 184, 151, 115, 104, 101, 110, 52, 0, 10, 3, 233, 163, 175, 102, 97, 110, 52, 0, 9, 3, 233, 160, 151, 112, 111, 49, 0, 0, 11, 3, 233, 160, 152, 108, 105, 110, 103, 51, 0, 11, 3, 230, 188, 184, 106, 105, 97, 110, 52, 0, 11, 3, 233, 162, 168, 102, 101, 110, 103, 49, 0, 11, 3, 231, 177, 160, 108, 111, 110, 103, 50, 0, 9, 3, 232, 168, 152, 106, 105, 52, 0, 0, 11, 3, 231, 180, 185, 115, 104, 97, 111, 52, 0, 10, 3, 232, 183, 145, 112, 97, 111, 51, 0, 10, 3, 232, 172, 185, 106, 105, 110, 51, 0, 0, 10, 3, 233, 173, 130, 104, 117, 110, 50, 0, 11, 3, 232, 170, 170, 115, 104, 117, 111, 49, 0, 9, 3, 231, 191, 146, 120, 105, 50, 0, 10, 3, 232, 169, 162, 120, 117, 110, 50, 0, 9, 3, 230, 186, 170, 120, 105, 49, 0, 10, 3, 233, 163, 178, 121, 105, 110, 51, 0, 10, 3, 232, 182, 138, 121, 117, 101, 52, 0, 11, 3, 231, 190, 138, 121, 97, 110, 103, 50, 0, 11, 3, 230, 187, 178, 115, 104, 101, 110, 52, 0, 10, 3, 231, 178, 170, 102, 101, 110, 52, 0, 8, 65, 52, 125, 111, 63, 0, 29, 0, 11, 3, 230, 184, 155, 106, 105, 97, 110, 51, 0, 9, 3, 232, 182, 139, 113, 117, 49, 0, 10, 3, 230, 186, 171, 119, 101, 110, 49, 0, 0, 9, 3, 233, 173, 132, 112, 111, 52, 0, 9, 3, 232, 181, 132, 122, 105, 49, 0, 9, 3, 230, 187, 180, 100, 105, 49, 0, 12, 3, 231, 191, 148, 120, 105, 97, 110, 103, 50, 0, 0, 9, 3, 232, 168, 157, 121, 97, 52, 0, 0, 10, 3, 231, 190, 142, 109, 101, 105, 51, 0, 11, 3, 230, 188, 190, 121, 97, 110, 103, 52, 0, 10, 3, 232, 169, 166, 115, 104, 105, 52, 0, 12, 3, 231, 178, 174, 108, 105, 97, 110, 103, 50, 0, 11, 3, 231, 179, 182, 116, 105, 97, 111, 52, 0, 8, 65, 56, 13, 50, 115, 0, 29, 0, 12, 3, 230, 188, 191, 106, 105, 97, 110, 103, 49, 0, 9, 3, 233, 161, 167, 103, 117, 52, 0, 11, 3, 232, 171, 183, 102, 101, 110, 103, 51, 0, 11, 3, 232, 168, 159, 115, 111, 110, 103, 52, 0, 0, 10, 3, 232, 171, 184, 122, 104, 117, 49, 0, 9, 3, 230, 184, 160, 113, 117, 50, 0, 11, 3, 231, 188, 128, 122, 104, 117, 105, 53, 0, 11, 3, 231, 191, 152, 113, 105, 97, 111, 52, 0, 11, 3, 232, 170, 176, 115, 104, 117, 105, 50, 0, 0, 10, 3, 232, 169, 169, 115, 104, 105, 49, 0, 11, 3, 231, 176, 161, 106, 105, 97, 110, 51, 0, 9, 3, 230, 184, 161, 100, 117, 52, 0, 0, 9, 3, 232, 170, 178, 107, 101, 52, 0, 7, 65, 60, 138, 115, 0, 29, 0, 9, 3, 232, 183, 155, 98, 111, 51, 0, 9, 3, 231, 179, 187, 120, 105, 52, 0, 11, 3, 233, 161, 171, 99, 104, 97, 110, 52, 0, 10, 3, 230, 184, 163, 122, 104, 97, 49, 0, 10, 3, 232, 169, 171, 99, 104, 97, 52, 0, 0, 9, 3, 232, 181, 140, 100, 117, 51, 0, 10, 3, 231, 190, 148, 103, 97, 111, 49, 0, 9, 3, 233, 163, 188, 115, 105, 52, 0, 9, 3, 231, 177, 172, 108, 105, 50, 0, 0, 9, 3, 232, 183, 157, 106, 117, 52, 0, 10, 3, 232, 182, 149, 103, 97, 110, 51, 0, 10, 3, 232, 169, 173, 103, 117, 105, 51, 0, 10, 3, 233, 163, 189, 98, 97, 111, 51, 0, 0, 10, 3, 233, 163, 190, 115, 104, 105, 52, 0, 9, 3, 230, 184, 166, 119, 111, 49, 0, 10, 3, 231, 179, 190, 106, 105, 117, 49, 0, 11, 3, 230, 186, 182, 114, 111, 110, 103, 50, 0, 10, 3, 230, 187, 190, 103, 117, 110, 51, 0, 10, 3, 231, 177, 174, 108, 117, 111, 50, 0, 8, 65, 64, 116, 37, 113, 0, 29, 0, 10, 3, 230, 187, 191, 109, 97, 110, 51, 0, 10, 3, 232, 183, 159, 103, 101, 110, 49, 0, 11, 3, 233, 161, 175, 120, 105, 97, 110, 51, 0, 11, 3, 230, 185, 175, 116, 97, 110, 103, 49, 0, 12, 3, 232, 181, 143, 115, 104, 97, 110, 103, 51, 0, 0, 10, 3, 232, 176, 168, 106, 105, 110, 51, 0, 10, 3, 231, 186, 184, 122, 104, 105, 51, 0, 10, 3, 233, 169, 176, 99, 104, 105, 50, 0, 9, 3, 232, 187, 128, 113, 117, 49, 0, 0, 11, 3, 233, 181, 145, 106, 117, 97, 110, 49, 0, 9, 3, 233, 180, 137, 121, 97, 49, 0, 9, 3, 233, 169, 177, 113, 117, 49, 0, 10, 3, 231, 186, 185, 119, 101, 110, 50, 0, 10, 3, 232, 188, 137, 122, 97, 105, 52, 0, 0, 11, 3, 231, 186, 186, 102, 97, 110, 103, 51, 0, 8, 65, 68, 118, 136, 115, 0, 29, 0, 10, 3, 232, 178, 187, 102, 101, 105, 52, 0, 11, 3, 231, 184, 171, 102, 101, 110, 103, 52, 0, 9, 3, 233, 169, 179, 98, 111, 50, 0, 11, 3, 231, 185, 179, 106, 105, 97, 111, 51, 0, 10, 3, 232, 190, 155, 120, 105, 110, 49, 0, 0, 10, 3, 232, 176, 172, 109, 105, 117, 52, 0, 8, 3, 233, 179, 132, 101, 52, 0, 9, 3, 233, 170, 188, 103, 101, 50, 0, 9, 3, 233, 169, 180, 108, 118, 50, 0, 9, 3, 232, 190, 156, 103, 117, 49, 0, 10, 3, 232, 178, 188, 116, 105, 101, 49, 0, 0, 10, 3, 231, 186, 189, 110, 105, 117, 51, 0, 0, 9, 3, 232, 190, 158, 99, 105, 50, 0, 10, 3, 231, 184, 174, 115, 117, 111, 49, 0, 10, 3, 233, 169, 182, 115, 104, 105, 51, 0, 7, 65, 72, 127, 111, 0, 29, 0, 10, 3, 232, 178, 191, 109, 97, 111, 52, 0, 9, 3, 232, 190, 159, 112, 105, 52, 0, 11, 3, 231, 186, 191, 120, 105, 97, 110, 52, 0, 0, 11, 3, 233, 168, 176, 116, 101, 110, 103, 50, 0, 0, 9, 3, 233, 169, 185, 106, 117, 49, 0, 10, 3, 232, 186, 129, 122, 97, 111, 52, 0, 10, 3, 232, 177, 185, 98, 97, 111, 52, 0, 11, 3, 231, 184, 177, 122, 111, 110, 103, 52, 0, 0, 10, 3, 232, 187, 138, 99, 104, 101, 49, 0, 11, 3, 232, 177, 186, 99, 104, 97, 105, 50, 0, 8, 65, 76, 125, 111, 87, 0, 29, 0, 9, 3, 232, 191, 171, 112, 111, 52, 0, 10, 3, 233, 169, 187, 122, 104, 117, 52, 0, 9, 3, 232, 190, 163, 108, 97, 52, 0, 9, 3, 232, 187, 139, 121, 97, 52, 0, 0, 10, 3, 233, 169, 188, 116, 117, 111, 53, 0, 9, 3, 232, 188, 148, 102, 117, 51, 0, 9, 3, 231, 185, 188, 106, 105, 52, 0, 10, 3, 232, 187, 140, 103, 117, 105, 51, 0, 11, 3, 232, 176, 180, 113, 105, 97, 110, 51, 0, 0, 11, 3, 232, 188, 149, 113, 105, 110, 103, 49, 0, 10, 3, 232, 187, 141, 106, 117, 110, 49, 0, 8, 3, 233, 181, 157, 101, 50, 0, 0, 10, 3, 233, 169, 190, 106, 105, 97, 52, 0, 10, 3, 232, 190, 166, 98, 97, 110, 52, 0, 8, 65, 80, 117, 37, 113, 0, 29, 0, 11, 3, 232, 189, 159, 104, 111, 110, 103, 49, 0, 9, 3, 231, 184, 183, 108, 118, 51, 0, 10, 3, 232, 186, 135, 99, 104, 117, 50, 0, 9, 3, 232, 176, 183, 103, 117, 51, 0, 0, 10, 3, 232, 191, 176, 115, 104, 117, 52, 0, 11, 3, 232, 190, 168, 98, 105, 97, 110, 52, 0, 0, 11, 3, 232, 190, 169, 98, 105, 97, 110, 52, 0, 0, 11, 3, 232, 186, 138, 99, 104, 111, 117, 50, 0, 8, 65, 84, 57, 136, 115, 0, 29, 0, 12, 3, 232, 188, 155, 108, 105, 97, 110, 103, 52, 0, 11, 3, 232, 190, 171, 98, 105, 97, 110, 52, 0, 0, 9, 3, 232, 185, 132, 116, 105, 50, 0, 0, 10, 3, 232, 188, 157, 104, 117, 105, 49, 0, 11, 3, 231, 184, 189, 122, 111, 110, 103, 51, 0, 10, 3, 232, 186, 141, 121, 117, 101, 52, 0, 9, 3, 232, 190, 173, 99, 105, 50, 0, 0, 11, 3, 232, 190, 174, 98, 105, 97, 110, 52, 0, 10, 3, 233, 168, 190, 108, 117, 111, 50, 0, 9, 3, 231, 184, 190, 106, 105, 49, 0, 10, 3, 232, 189, 166, 99, 104, 101, 49, 0, 8, 65, 88, 82, 129, 115, 0, 29, 0, 9, 3, 232, 191, 183, 109, 105, 50, 0, 11, 3, 232, 190, 175, 98, 105, 97, 110, 52, 0, 9, 3, 232, 189, 167, 121, 97, 52, 0, 0, 10, 3, 232, 185, 136, 100, 97, 111, 51, 0, 10, 3, 232, 189, 168, 103, 117, 105, 51, 0, 0, 11, 3, 233, 183, 185, 121, 105, 110, 103, 49, 0, 9, 3, 232, 191, 185, 106, 105, 49, 0, 9, 3, 232, 190, 177, 114, 117, 51, 0, 0, 9, 3, 233, 181, 170, 97, 110, 49, 0, 11, 3, 232, 190, 178, 110, 111, 110, 103, 50, 0, 11, 65, 92, 47, 35, 111, 48, 55, 136, 0, 29, 0, 9, 3, 232, 185, 139, 116, 97, 52, 0, 0, 12, 3, 232, 189, 172, 122, 104, 117, 97, 110, 51, 0, 0, 11, 3, 232, 191, 189, 122, 104, 117, 105, 49, 0, 0, 10, 3, 232, 189, 174, 108, 117, 110, 50, 0, 9, 65, 96, 125, 111, 49, 87, 0, 29, 0, 11, 3, 232, 187, 159, 114, 117, 97, 110, 51, 0, 11, 3, 232, 189, 175, 114, 117, 97, 110, 51, 0, 0, 10, 3, 232, 179, 160, 112, 101, 105, 50, 0, 10, 3, 232, 176, 136, 116, 97, 110, 50, 0, 9, 3, 231, 189, 176, 102, 97, 50, 0, 10, 3, 232, 181, 176, 122, 111, 117, 51, 0, 10, 3, 232, 180, 168, 122, 104, 105, 52, 0, 0, 10, 3, 232, 180, 169, 102, 97, 110, 52, 0, 10, 3, 231, 188, 169, 115, 117, 111, 49, 0, 11, 3, 232, 191, 129, 113, 105, 97, 110, 49, 0, 0, 9, 3, 232, 176, 138, 121, 105, 52, 0, 10, 3, 231, 189, 178, 115, 104, 117, 51, 0, 11, 3, 231, 187, 162, 106, 117, 97, 110, 52, 0, 10, 3, 232, 180, 170, 116, 97, 110, 49, 0, 8, 65, 100, 58, 142, 113, 0, 29, 0, 10, 3, 231, 187, 163, 120, 105, 117, 52, 0, 10, 3, 232, 176, 139, 109, 111, 117, 50, 0, 10, 3, 232, 180, 171, 112, 105, 110, 50, 0, 10, 3, 232, 179, 163, 109, 97, 105, 52, 0, 0, 10, 3, 231, 185, 148, 122, 104, 105, 49, 0, 11, 3, 232, 179, 164, 106, 105, 97, 110, 52, 0, 9, 3, 232, 181, 180, 102, 117, 52, 0, 0, 10, 3, 232, 191, 133, 120, 117, 110, 52, 0, 11, 3, 233, 169, 149, 106, 105, 97, 111, 49, 0, 10, 3, 232, 178, 157, 98, 101, 105, 52, 0, 10, 3, 232, 180, 173, 103, 111, 117, 52, 0, 9, 3, 231, 189, 181, 109, 97, 52, 0, 9, 3, 231, 190, 189, 121, 117, 51, 0, 0, 10, 3, 233, 171, 166, 109, 97, 111, 50, 0, 12, 3, 232, 176, 142, 104, 117, 97, 110, 103, 51, 0, 10, 3, 232, 181, 182, 103, 97, 110, 51, 0, 9, 3, 233, 168, 142, 113, 105, 50, 0, 8, 65, 104, 86, 37, 113, 0, 29, 0, 10, 3, 233, 169, 151, 121, 97, 110, 52, 0, 9, 3, 231, 189, 183, 98, 97, 53, 0, 10, 3, 232, 191, 135, 103, 117, 111, 52, 0, 9, 3, 232, 181, 183, 113, 105, 51, 0, 9, 3, 231, 187, 167, 106, 105, 52, 0, 11, 3, 232, 180, 175, 103, 117, 97, 110, 52, 0, 0, 10, 3, 231, 186, 160, 106, 105, 117, 49, 0, 12, 3, 231, 188, 176, 106, 105, 97, 110, 103, 49, 0, 9, 3, 232, 178, 160, 102, 117, 52, 0, 10, 3, 232, 191, 136, 109, 97, 105, 52, 0, 0, 10, 3, 233, 170, 161, 108, 117, 111, 50, 0, 10, 3, 232, 178, 161, 99, 97, 105, 50, 0, 11, 3, 232, 180, 177, 106, 105, 97, 110, 52, 0, 9, 3, 231, 187, 169, 106, 105, 49, 0, 0, 9, 3, 231, 187, 170, 120, 117, 52, 0, 11, 3, 232, 178, 162, 103, 111, 110, 103, 52, 0, 11, 3, 233, 169, 154, 106, 105, 110, 103, 49, 0, 11, 3, 231, 186, 162, 104, 111, 110, 103, 50, 0, 10, 3, 232, 179, 170, 122, 104, 105, 52, 0, 0, 10, 3, 232, 176, 147, 119, 101, 105, 52, 0, 11, 3, 232, 190, 131, 106, 105, 97, 111, 52, 0, 0, 11, 3, 231, 188, 180, 106, 105, 97, 111, 51, 0, 11, 3, 233, 170, 164, 122, 104, 111, 117, 52, 0, 10, 3, 232, 180, 180, 116, 105, 101, 49, 0, 11, 3, 231, 186, 164, 120, 105, 97, 110, 49, 0, 0, 10, 3, 232, 180, 181, 103, 117, 105, 52, 0, 9, 3, 231, 187, 173, 120, 117, 52, 0, 9, 3, 232, 179, 173, 100, 117, 51, 0, 9, 3, 232, 190, 133, 102, 117, 51, 0, 0, 11, 3, 232, 191, 142, 121, 105, 110, 103, 50, 0, 10, 3, 231, 185, 158, 114, 97, 111, 52, 0, 10, 3, 231, 186, 166, 121, 117, 101, 49, 0, 12, 3, 232, 190, 134, 108, 105, 97, 110, 103, 52, 0, 0, 9, 3, 231, 186, 167, 106, 105, 50, 0, 11, 3, 233, 169, 159, 122, 104, 111, 117, 52, 0, 10, 3, 232, 178, 167, 112, 105, 110, 50, 0, 0, 11, 3, 231, 188, 184, 103, 97, 110, 103, 49, 0, 10, 3, 232, 178, 168, 104, 117, 111, 52, 0, 10, 3, 232, 191, 144, 121, 117, 110, 52, 0, 10, 3, 232, 190, 136, 98, 101, 105, 52, 0, 9, 3, 233, 170, 168, 103, 117, 51, 0, 10, 3, 232, 180, 184, 109, 97, 111, 52, 0, 0, 10, 3, 232, 190, 137, 104, 117, 105, 49, 0, 11, 3, 233, 168, 153, 112, 105, 97, 110, 52, 0, 10, 3, 232, 178, 169, 102, 97, 110, 52, 0, 10, 3, 232, 180, 185, 102, 101, 105, 52, 0, 12, 3, 232, 177, 161, 120, 105, 97, 110, 103, 52, 0, 11, 3, 233, 182, 137, 99, 104, 117, 110, 53, 0, 10, 3, 231, 185, 161, 120, 105, 117, 52, 0, 10, 3, 232, 191, 145, 106, 105, 110, 52, 0, 0, 9, 3, 232, 180, 186, 104, 101, 52, 0, 9, 3, 233, 169, 162, 108, 118, 50, 0, 9, 3, 231, 186, 170, 106, 105, 52, 0, 10, 3, 232, 178, 170, 116, 97, 110, 49, 0, 10, 3, 231, 188, 186, 113, 117, 101, 49, 0, 0, 9, 3, 231, 184, 155, 102, 117, 52, 0, 11, 3, 232, 178, 171, 103, 117, 97, 110, 52, 0, 12, 3, 231, 187, 179, 115, 104, 101, 110, 103, 50, 0, 0, 10, 3, 231, 186, 172, 119, 101, 105, 51, 0, 10, 3, 232, 180, 188, 122, 101, 105, 50, 0, 10, 3, 232, 179, 180, 108, 97, 105, 52, 0, 10, 3, 233, 172, 188, 103, 117, 105, 51, 0, 10, 3, 232, 191, 148, 102, 97, 110, 51, 0, 10, 3, 231, 187, 180, 119, 101, 105, 50, 0, 9, 3, 232, 178, 172, 122, 101, 50, 0, 0, 11, 3, 231, 187, 181, 109, 105, 97, 110, 50, 0, 0, 0, 11, 3, 231, 186, 175, 99, 104, 117, 110, 50, 0, 9, 3, 233, 183, 151, 111, 117, 49, 0, 11, 3, 231, 187, 183, 98, 101, 110, 103, 51, 0, 0, 9, 3, 232, 190, 144, 102, 117, 50, 0, 11, 3, 231, 187, 184, 99, 104, 111, 117, 50, 0, 10, 3, 232, 191, 152, 104, 97, 105, 50, 0, 0, 12, 3, 231, 185, 169, 115, 104, 101, 110, 103, 50, 0, 12, 3, 232, 189, 137, 122, 104, 117, 97, 110, 51, 0, 10, 3, 232, 191, 153, 122, 104, 101, 52, 0, 10, 3, 231, 186, 177, 115, 104, 97, 49, 0, 9, 3, 232, 190, 145, 106, 105, 53, 0, 0, 10, 3, 232, 177, 170, 104, 97, 111, 50, 0, 10, 3, 232, 176, 162, 120, 105, 101, 52, 0, 10, 3, 231, 185, 170, 104, 117, 105, 52, 0, 12, 3, 232, 179, 186, 122, 104, 117, 97, 110, 52, 0, 11, 3, 231, 186, 178, 103, 97, 110, 103, 49, 0, 0, 9, 3, 232, 177, 171, 121, 117, 52, 0, 11, 3, 232, 188, 131, 106, 105, 97, 111, 52, 0, 10, 3, 232, 176, 163, 121, 97, 111, 50, 0, 9, 3, 231, 186, 179, 110, 97, 52, 0, 11, 3, 231, 184, 163, 120, 105, 97, 110, 52, 0, 10, 3, 232, 191, 155, 106, 105, 110, 52, 0, 10, 3, 232, 190, 147, 115, 104, 117, 49, 0, 0, 11, 3, 232, 191, 156, 121, 117, 97, 110, 51, 0, 9, 3, 233, 169, 172, 109, 97, 51, 0, 11, 3, 231, 187, 188, 122, 111, 110, 103, 49, 0, 10, 3, 232, 178, 180, 103, 117, 105, 52, 0, 10, 3, 232, 177, 172, 122, 104, 117, 49, 0, 10, 3, 232, 179, 188, 103, 111, 117, 52, 0, 0, 11, 3, 231, 186, 181, 122, 111, 110, 103, 52, 0, 10, 3, 232, 191, 157, 119, 101, 105, 50, 0, 10, 3, 232, 179, 189, 115, 97, 105, 52, 0, 11, 3, 231, 185, 173, 106, 105, 97, 110, 51, 0, 0, 10, 3, 233, 169, 174, 116, 117, 111, 50, 0, 11, 3, 232, 191, 158, 108, 105, 97, 110, 50, 0, 10, 3, 231, 186, 182, 108, 117, 110, 50, 0, 11, 3, 232, 176, 166, 113, 105, 97, 110, 49, 0, 11, 3, 232, 189, 142, 106, 105, 97, 111, 52, 0, 0, 10, 3, 231, 186, 183, 102, 101, 110, 49, 0, 9, 3, 231, 187, 191, 108, 118, 52, 0, 10, 3, 232, 178, 183, 109, 97, 105, 51, 0, 10, 3, 232, 191, 159, 99, 104, 105, 50, 0, 0, 11, 3, 233, 178, 184, 106, 105, 110, 103, 49, 0, 0, 10, 3, 232, 184, 169, 99, 97, 105, 51, 0, 0, 11, 3, 232, 186, 186, 116, 97, 110, 103, 51, 0, 10, 3, 232, 185, 178, 100, 117, 110, 49, 0, 11, 3, 232, 184, 170, 122, 111, 110, 103, 49, 0, 0, 0, 0, 0, 11, 3, 232, 184, 174, 100, 105, 97, 110, 51, 0, 0, 8, 3, 233, 177, 183, 101, 52, 0, 0, 0, 10, 3, 232, 184, 177, 100, 117, 111, 50, 0, 0, 0, 0, 9, 3, 233, 177, 188, 121, 117, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 232, 189, 176, 104, 111, 110, 103, 49, 0, 9, 3, 233, 180, 168, 121, 97, 49, 0, 0, 11, 3, 232, 190, 185, 98, 105, 97, 110, 49, 0, 10, 3, 232, 188, 169, 98, 101, 105, 52, 0, 0, 10, 3, 232, 188, 170, 108, 117, 110, 50, 0, 10, 3, 233, 181, 178, 113, 117, 101, 53, 0, 0, 0, 11, 3, 232, 189, 180, 122, 104, 111, 117, 50, 0, 11, 3, 233, 178, 156, 120, 105, 97, 110, 49, 0, 11, 3, 232, 184, 140, 99, 104, 111, 117, 50, 0, 0, 11, 3, 232, 190, 189, 108, 105, 97, 111, 50, 0, 11, 3, 233, 179, 165, 110, 105, 97, 111, 51, 0, 0, 9, 3, 232, 190, 190, 100, 97, 50, 0, 0, 9, 3, 233, 179, 167, 102, 117, 50, 0, 9, 3, 232, 184, 143, 116, 97, 52, 0, 9, 3, 232, 188, 175, 106, 105, 53, 0, 0, 11, 3, 232, 184, 144, 106, 105, 97, 110, 52, 0, 0, 0, 0, 11, 3, 232, 189, 187, 113, 105, 110, 103, 49, 0, 0, 9, 3, 233, 178, 164, 108, 105, 51, 0, 0, 10, 3, 232, 189, 189, 122, 97, 105, 52, 0, 0, 0, 11, 3, 232, 189, 191, 106, 105, 97, 111, 52, 0, 0, 10, 3, 232, 188, 184, 115, 104, 117, 49, 0, 0, 0, 0, 9, 3, 232, 188, 187, 102, 117, 50, 0, 11, 3, 232, 186, 171, 115, 104, 101, 110, 49, 0, 11, 3, 233, 179, 179, 102, 101, 110, 103, 52, 0, 0, 11, 3, 233, 179, 180, 109, 105, 110, 103, 50, 0, 11, 3, 232, 186, 172, 103, 111, 110, 103, 49, 0, 11, 3, 232, 185, 164, 122, 111, 110, 103, 49, 0, 0, 0, 11, 3, 232, 185, 166, 98, 101, 110, 103, 52, 0, 0, 9, 3, 232, 188, 191, 121, 117, 50, 0, 9, 3, 232, 186, 175, 113, 117, 49, 0, 9, 3, 233, 180, 191, 103, 101, 49, 0, 0, 11, 3, 232, 187, 184, 122, 104, 111, 117, 50, 0, 0, 0, 9, 3, 232, 184, 162, 116, 105, 49, 0, 10, 3, 232, 186, 178, 100, 117, 111, 51, 0, 0, 0, 11, 3, 232, 185, 172, 100, 101, 110, 103, 49, 0, 0, 11, 3, 232, 185, 173, 99, 101, 110, 103, 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 233, 185, 130, 108, 105, 50, 0, 0, 11, 3, 233, 185, 131, 106, 117, 97, 110, 49, 0, 0, 0, 8, 3, 233, 185, 133, 101, 50, 0, 0, 0, 0, 0, 0, 10, 3, 233, 185, 138, 113, 117, 101, 53, 0, 0, 0, 9, 3, 233, 185, 140, 97, 110, 49, 0, 0, 0, 0, 0, 0, 11, 3, 233, 185, 145, 99, 104, 117, 110, 53, 0, 0, 0, 12, 3, 233, 187, 131, 104, 117, 97, 110, 103, 50, 0, 0, 12, 3, 233, 187, 132, 104, 117, 97, 110, 103, 50, 0, 0, 9, 3, 233, 184, 157, 108, 105, 50, 0, 0, 0, 11, 3, 233, 184, 159, 110, 105, 97, 111, 51, 0, 0, 0, 9, 3, 233, 184, 161, 106, 105, 49, 0, 0, 0, 11, 3, 233, 184, 163, 109, 105, 110, 103, 50, 0, 0, 0, 9, 3, 233, 184, 165, 111, 117, 49, 0, 0, 9, 3, 233, 187, 142, 108, 105, 50, 0, 9, 3, 233, 184, 166, 121, 97, 49, 0, 0, 11, 3, 233, 187, 143, 110, 105, 97, 110, 50, 0, 9, 3, 233, 186, 151, 108, 105, 52, 0, 0, 0, 10, 3, 233, 187, 145, 104, 101, 105, 49, 0, 0, 0, 0, 0, 9, 3, 233, 184, 173, 121, 97, 49, 0, 0, 0, 0, 9, 3, 233, 187, 152, 109, 111, 52, 0, 0, 0, 9, 3, 233, 189, 138, 113, 105, 50, 0, 0, 9, 3, 233, 188, 147, 103, 117, 51, 0, 0, 11, 3, 233, 190, 132, 108, 105, 110, 103, 50, 0, 0, 10, 3, 233, 186, 165, 109, 97, 105, 52, 0, 0, 11, 3, 233, 187, 158, 100, 105, 97, 110, 51, 0, 10, 3, 233, 186, 166, 109, 97, 105, 52, 0, 0, 0, 11, 3, 233, 185, 176, 121, 105, 110, 103, 49, 0, 9, 3, 233, 189, 144, 113, 105, 50, 0, 0, 0, 10, 3, 233, 189, 146, 99, 104, 105, 51, 0, 0, 0, 0, 11, 3, 233, 190, 141, 108, 111, 110, 103, 50, 0, 9, 3, 233, 184, 189, 103, 101, 49, 0, 0, 0, 0, 0, 11, 3, 233, 190, 144, 112, 97, 110, 103, 50, 0, 11, 3, 233, 187, 168, 100, 97, 110, 103, 51, 0, 10, 3, 233, 188, 160, 115, 104, 117, 51, 0, 0, 0, 0, 10, 3, 233, 185, 189, 121, 97, 110, 50, 0, 0, 11, 3, 233, 185, 188, 106, 105, 97, 110, 51, 0, 0, 9, 3, 233, 187, 175, 97, 110, 52, 0, 9, 3, 233, 185, 191, 108, 117, 52, 0, 0, 0, 11, 3, 233, 190, 153, 108, 111, 110, 103, 50, 0, 11, 3, 233, 189, 161, 108, 105, 110, 103, 50, 0, 0, 0, 9, 3, 233, 186, 187, 109, 97, 50, 0, 0, 0, 0, 9, 3, 233, 186, 188, 109, 101, 53, 0, 10, 3, 233, 190, 156, 103, 117, 105, 49, 0, 10, 3, 233, 187, 180, 109, 101, 105, 50, 0, 0, 10, 3, 233, 190, 159, 103, 117, 105, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 233, 188, 187, 98, 105, 50, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 233, 189, 191, 99, 104, 105, 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 227, 132, 133, 48, 39, 115, 0, 29, 0, 0, 10, 3, 227, 132, 135, 63, 39, 115, 0, 29, 0, 10, 3, 227, 132, 134, 116, 39, 115, 0, 29, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 3, 227, 132, 165, 13, 66, 115, 0, 29, 0, 10, 3, 227, 132, 164, 124, 66, 115, 0, 29, 0, 10, 3, 227, 132, 167, 57, 37, 115, 0, 29, 0, 9, 3, 227, 132, 166, 127, 115, 0, 29, 0, 9, 3, 227, 132, 161, 138, 115, 0, 29, 0, 9, 3, 227, 132, 160, 126, 115, 0, 29, 0, 10, 3, 227, 132, 163, 13, 50, 115, 0, 29, 0, 10, 3, 227, 132, 162, 35, 50, 115, 0, 29, 0, 9, 3, 227, 132, 157, 128, 115, 0, 29, 0, 9, 3, 227, 132, 156, 137, 115, 0, 29, 0, 9, 3, 227, 132, 159, 129, 115, 0, 29, 0, 9, 3, 227, 132, 158, 125, 115, 0, 29, 0, 10, 3, 227, 132, 153, 87, 130, 115, 0, 29, 0, 10, 3, 227, 132, 152, 121, 130, 115, 0, 29, 0, 9, 3, 227, 132, 155, 39, 115, 0, 29, 0, 9, 3, 227, 132, 154, 124, 115, 0, 29, 0, 10, 3, 227, 132, 149, 91, 131, 115, 0, 29, 0, 10, 3, 227, 132, 148, 123, 131, 115, 0, 29, 0, 10, 3, 227, 132, 151, 120, 130, 115, 0, 29, 0, 10, 3, 227, 132, 150, 90, 131, 115, 0, 29, 0, 10, 3, 227, 132, 145, 119, 37, 115, 0, 29, 0, 10, 3, 227, 132, 144, 76, 37, 115, 0, 29, 0, 10, 3, 227, 132, 147, 122, 131, 115, 0, 29, 0, 10, 3, 227, 132, 146, 95, 37, 115, 0, 29, 0, 10, 3, 227, 132, 141, 49, 137, 115, 0, 29, 0, 10, 3, 227, 132, 140, 55, 13, 115, 0, 29, 0, 10, 3, 227, 132, 143, 99, 137, 115, 0, 29, 0, 10, 3, 227, 132, 142, 118, 137, 115, 0, 29, 0, 10, 3, 227, 132, 137, 47, 13, 115, 0, 29, 0, 10, 3, 227, 132, 136, 81, 39, 115, 0, 29, 0, 10, 3, 227, 132, 139, 50, 13, 115, 0, 29, 0, 10, 3, 227, 132, 138, 117, 13, 115, 0, 29, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 3, 227, 132, 169, 146, 115, 0, 29, 0, 10, 3, 227, 132, 168, 58, 40, 115, 0, 29, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 3, 229, 135, 157, 110, 105, 110, 103, 50, 0, 11, 3, 229, 133, 141, 109, 105, 97, 110, 51, 0, 0, 9, 3, 229, 132, 132, 121, 105, 52, 0, 0, 0, 0, 12, 3, 229, 133, 137, 103, 117, 97, 110, 103, 49, 0, 0, 9, 3, 229, 132, 128, 121, 105, 50, 0, 11, 3, 229, 133, 136, 120, 105, 97, 110, 49, 0, 0, 9, 3, 229, 133, 139, 107, 101, 52, 0, 10, 3, 95, 63, 63, 13, 12, 106, 0, 29, 0, 10, 3, 229, 134, 146, 109, 97, 111, 52, 0, 0, 12, 3, 229, 133, 133, 99, 104, 111, 110, 103, 49, 0, 10, 3, 229, 134, 141, 122, 97, 105, 52, 0, 0, 9, 3, 229, 134, 140, 99, 101, 52, 0, 12, 3, 229, 133, 132, 120, 105, 111, 110, 103, 49, 0, 0, 0, 0, 10, 3, 229, 135, 145, 99, 111, 117, 52, 0, 10, 3, 229, 133, 129, 121, 117, 110, 51, 0, 0, 11, 3, 229, 134, 136, 103, 97, 110, 103, 49, 0, 0, 11, 3, 229, 133, 131, 121, 117, 97, 110, 50, 0, 0, 9, 3, 229, 134, 138, 99, 101, 52, 0, 0, 10, 3, 229, 134, 133, 110, 101, 105, 52, 0, 11, 3, 229, 135, 141, 100, 111, 110, 103, 52, 0, 0, 0, 11, 3, 229, 135, 143, 106, 105, 97, 110, 51, 0, 0, 0, 12, 3, 229, 135, 137, 108, 105, 97, 110, 103, 50, 0, 0, 0, 0, 0, 0, 9, 3, 229, 135, 132, 113, 105, 49, 0, 0, 0, 11, 3, 229, 135, 134, 122, 104, 117, 110, 51, 0, 0, 0, 11, 3, 229, 135, 128, 106, 105, 110, 103, 52, 0, 0, 0, 0, 10, 3, 229, 133, 173, 108, 105, 117, 52, 0, 12, 3, 229, 134, 181, 107, 117, 97, 110, 103, 52, 0, 0, 11, 3, 229, 133, 172, 103, 111, 110, 103, 49, 0, 0, 10, 3, 229, 135, 191, 122, 97, 111, 50, 0, 11, 3, 229, 129, 143, 112, 105, 97, 110, 49, 0, 11, 3, 229, 134, 183, 108, 101, 110, 103, 51, 0, 0, 9, 3, 229, 134, 182, 121, 101, 51, 0, 10, 3, 229, 128, 134, 108, 105, 97, 51, 0, 10, 3, 229, 129, 142, 119, 101, 105, 49, 0, 0, 9, 3, 229, 135, 185, 97, 111, 49, 0, 10, 3, 229, 129, 137, 119, 101, 105, 51, 0, 12, 3, 229, 133, 169, 108, 105, 97, 110, 103, 51, 0, 0, 9, 3, 229, 135, 184, 116, 117, 49, 0, 11, 3, 229, 133, 168, 113, 117, 97, 110, 50, 0, 11, 3, 229, 134, 176, 98, 105, 110, 103, 49, 0, 0, 10, 3, 229, 134, 179, 106, 117, 101, 50, 0, 9, 3, 229, 135, 187, 106, 105, 49, 0, 9, 3, 229, 133, 171, 98, 97, 49, 0, 0, 11, 3, 229, 131, 154, 108, 105, 97, 111, 50, 0, 12, 3, 229, 134, 178, 99, 104, 111, 110, 103, 49, 0, 10, 3, 229, 135, 186, 99, 104, 117, 49, 0, 0, 9, 3, 229, 133, 165, 114, 117, 52, 0, 11, 3, 229, 130, 141, 98, 97, 110, 103, 52, 0, 0, 11, 3, 229, 134, 172, 100, 111, 110, 103, 49, 0, 0, 10, 3, 229, 133, 167, 110, 101, 105, 52, 0, 12, 3, 229, 132, 159, 99, 104, 97, 110, 103, 50, 0, 10, 3, 229, 129, 135, 106, 105, 97, 51, 0, 0, 12, 3, 229, 135, 182, 120, 105, 111, 110, 103, 49, 0, 0, 0, 12, 3, 229, 135, 176, 104, 117, 97, 110, 103, 50, 0, 0, 11, 3, 229, 135, 179, 100, 101, 110, 103, 52, 0, 0, 0, 11, 3, 229, 135, 173, 112, 105, 110, 103, 50, 0, 9, 3, 229, 130, 133, 102, 117, 53, 0, 0, 10, 3, 229, 133, 156, 100, 111, 117, 49, 0, 11, 3, 229, 134, 164, 121, 117, 97, 110, 49, 0, 0, 12, 3, 229, 131, 143, 120, 105, 97, 110, 103, 52, 0, 0, 0, 0, 0, 9, 3, 229, 135, 171, 102, 117, 50, 0, 0, 11, 3, 229, 133, 154, 100, 97, 110, 103, 51, 0, 0, 10, 3, 229, 131, 133, 106, 105, 110, 51, 0, 0, 11, 3, 229, 134, 156, 110, 111, 110, 103, 50, 0, 11, 3, 229, 135, 164, 102, 101, 110, 103, 52, 0, 9, 3, 229, 133, 148, 116, 117, 52, 0, 0, 0, 0, 11, 3, 229, 132, 137, 106, 105, 97, 110, 51, 0, 10, 3, 229, 135, 161, 102, 97, 110, 50, 0, 10, 3, 229, 134, 153, 120, 105, 101, 51, 0, 0, 9, 3, 229, 135, 160, 106, 105, 51, 0, 0, 10, 3, 229, 134, 155, 106, 117, 110, 49, 0, 0, 8, 3, 229, 133, 146, 114, 53, 0, 0, 11, 3, 230, 133, 142, 115, 104, 101, 110, 52, 0, 11, 3, 229, 140, 134, 99, 111, 110, 103, 49, 0, 10, 3, 229, 141, 142, 104, 117, 97, 50, 0, 11, 3, 229, 128, 166, 106, 117, 97, 110, 52, 0, 0, 10, 3, 229, 141, 143, 120, 105, 101, 50, 0, 12, 3, 229, 130, 183, 115, 104, 97, 110, 103, 49, 0, 0, 12, 3, 230, 133, 140, 104, 117, 97, 110, 103, 49, 0, 0, 11, 3, 229, 130, 181, 122, 104, 97, 105, 52, 0, 9, 3, 229, 142, 149, 99, 101, 52, 0, 10, 3, 229, 140, 133, 98, 97, 111, 49, 0, 0, 9, 3, 229, 130, 178, 97, 111, 52, 0, 10, 3, 229, 141, 138, 98, 97, 110, 52, 0, 0, 10, 3, 229, 143, 155, 112, 97, 110, 52, 0, 12, 3, 229, 130, 179, 99, 104, 117, 97, 110, 50, 0, 10, 3, 230, 133, 139, 116, 97, 105, 52, 0, 0, 9, 3, 229, 141, 136, 119, 117, 51, 0, 10, 3, 229, 140, 128, 121, 117, 110, 50, 0, 11, 3, 229, 143, 152, 98, 105, 97, 110, 52, 0, 9, 3, 230, 133, 136, 99, 105, 50, 0, 11, 3, 230, 134, 144, 108, 105, 97, 110, 50, 0, 0, 10, 3, 229, 131, 185, 106, 105, 97, 52, 0, 9, 3, 229, 143, 153, 120, 117, 52, 0, 11, 3, 230, 134, 145, 112, 105, 110, 103, 50, 0, 12, 3, 229, 128, 161, 99, 104, 97, 110, 103, 52, 0, 11, 3, 230, 132, 129, 99, 104, 111, 117, 50, 0, 0, 9, 3, 229, 143, 150, 113, 117, 51, 0, 0, 11, 3, 229, 143, 151, 115, 104, 111, 117, 52, 0, 10, 3, 229, 128, 159, 106, 105, 101, 52, 0, 9, 3, 229, 132, 191, 101, 114, 50, 0, 12, 3, 229, 141, 135, 115, 104, 101, 110, 103, 49, 0, 0, 10, 3, 229, 130, 172, 99, 117, 105, 49, 0, 10, 3, 229, 142, 140, 121, 97, 110, 52, 0, 10, 3, 229, 143, 148, 115, 104, 117, 49, 0, 0, 12, 3, 229, 131, 181, 106, 105, 97, 110, 103, 49, 0, 11, 3, 229, 129, 165, 106, 105, 97, 110, 52, 0, 0, 9, 3, 229, 128, 154, 121, 105, 51, 0, 10, 3, 230, 135, 146, 108, 97, 110, 51, 0, 0, 9, 3, 229, 142, 139, 121, 97, 49, 0, 10, 3, 230, 134, 139, 98, 105, 101, 49, 0, 11, 3, 229, 141, 131, 113, 105, 97, 110, 49, 0, 0, 10, 3, 229, 130, 168, 99, 104, 117, 51, 0, 11, 3, 229, 128, 152, 116, 97, 110, 103, 51, 0, 9, 3, 229, 141, 128, 113, 117, 49, 0, 0, 9, 3, 229, 142, 137, 108, 105, 52, 0, 9, 3, 229, 131, 177, 103, 117, 52, 0, 9, 3, 229, 143, 145, 102, 97, 49, 0, 10, 3, 229, 141, 129, 115, 104, 105, 50, 0, 10, 3, 229, 128, 153, 104, 111, 117, 52, 0, 0, 9, 3, 229, 142, 134, 108, 105, 52, 0, 0, 0, 11, 3, 229, 133, 188, 106, 105, 97, 110, 49, 0, 13, 3, 229, 143, 140, 115, 104, 117, 97, 110, 103, 49, 0, 11, 3, 229, 129, 156, 116, 105, 110, 103, 50, 0, 0, 11, 3, 229, 142, 133, 116, 105, 110, 103, 49, 0, 11, 3, 229, 133, 189, 115, 104, 111, 117, 52, 0, 10, 3, 229, 143, 141, 102, 97, 110, 51, 0, 0, 12, 3, 229, 142, 130, 99, 104, 97, 110, 103, 51, 0, 10, 3, 229, 129, 154, 122, 117, 111, 52, 0, 10, 3, 230, 134, 130, 121, 111, 117, 49, 0, 9, 3, 229, 143, 138, 106, 105, 50, 0, 10, 3, 229, 132, 178, 99, 104, 117, 51, 0, 10, 3, 229, 128, 146, 100, 97, 111, 52, 0, 0, 11, 3, 229, 133, 187, 121, 97, 110, 103, 51, 0, 10, 3, 229, 143, 139, 121, 111, 117, 53, 0, 0, 11, 3, 229, 133, 184, 100, 105, 97, 110, 51, 0, 10, 3, 229, 143, 136, 121, 111, 117, 52, 0, 0, 10, 3, 229, 128, 145, 109, 101, 110, 53, 0, 11, 3, 230, 135, 137, 121, 105, 110, 103, 49, 0, 0, 9, 3, 229, 133, 182, 113, 105, 50, 0, 0, 10, 3, 230, 135, 135, 107, 101, 110, 51, 0, 9, 3, 229, 133, 183, 106, 117, 52, 0, 0, 11, 3, 229, 133, 180, 120, 105, 110, 103, 52, 0, 0, 11, 3, 229, 133, 181, 98, 105, 110, 103, 49, 0, 10, 3, 229, 128, 141, 98, 101, 105, 52, 0, 0, 10, 3, 229, 143, 130, 99, 97, 110, 49, 0, 10, 3, 229, 132, 170, 121, 111, 117, 49, 0, 11, 3, 230, 135, 130, 100, 111, 110, 103, 51, 0, 0, 11, 3, 229, 133, 179, 103, 117, 97, 110, 49, 0, 10, 3, 229, 143, 131, 99, 97, 110, 49, 0, 11, 3, 229, 134, 187, 100, 111, 110, 103, 52, 0, 9, 3, 229, 128, 139, 103, 101, 53, 0, 0, 10, 3, 229, 130, 152, 115, 97, 110, 51, 0, 0, 10, 3, 229, 130, 153, 98, 101, 105, 52, 0, 11, 3, 229, 133, 177, 103, 111, 110, 103, 52, 0, 11, 3, 229, 128, 137, 99, 97, 110, 103, 49, 0, 0, 10, 3, 229, 136, 134, 102, 101, 110, 49, 0, 9, 3, 230, 133, 174, 108, 118, 52, 0, 10, 3, 229, 137, 142, 115, 104, 97, 49, 0, 9, 3, 230, 134, 182, 121, 105, 52, 0, 10, 3, 229, 139, 158, 108, 97, 111, 50, 0, 0, 10, 3, 230, 132, 167, 107, 117, 105, 52, 0, 10, 3, 229, 136, 135, 113, 105, 101, 52, 0, 10, 3, 230, 131, 159, 119, 101, 105, 50, 0, 0, 10, 3, 230, 130, 148, 104, 117, 105, 51, 0, 11, 3, 229, 143, 188, 100, 105, 97, 111, 49, 0, 9, 3, 230, 131, 156, 120, 105, 49, 0, 10, 3, 230, 132, 164, 102, 101, 110, 52, 0, 9, 3, 230, 135, 188, 106, 117, 52, 0, 0, 12, 3, 230, 129, 141, 104, 117, 97, 110, 103, 51, 0, 12, 3, 229, 139, 157, 115, 104, 101, 110, 103, 52, 0, 11, 3, 229, 137, 141, 113, 105, 97, 110, 50, 0, 0, 9, 3, 229, 142, 178, 108, 105, 52, 0, 10, 3, 229, 137, 138, 120, 117, 101, 49, 0, 9, 3, 230, 131, 154, 104, 117, 49, 0, 11, 3, 230, 134, 178, 120, 105, 97, 110, 52, 0, 0, 10, 3, 229, 141, 171, 119, 101, 105, 52, 0, 11, 3, 230, 132, 163, 108, 101, 110, 103, 52, 0, 11, 3, 230, 129, 139, 108, 105, 97, 110, 52, 0, 0, 11, 3, 230, 135, 184, 120, 117, 97, 110, 50, 0, 10, 3, 230, 133, 168, 107, 97, 105, 51, 0, 10, 3, 229, 136, 128, 100, 97, 111, 49, 0, 10, 3, 229, 139, 152, 107, 97, 110, 49, 0, 12, 3, 229, 140, 160, 106, 105, 97, 110, 103, 53, 0, 9, 3, 229, 143, 184, 115, 105, 49, 0, 11, 3, 230, 128, 128, 104, 117, 97, 105, 50, 0, 0, 10, 3, 230, 128, 129, 116, 97, 105, 52, 0, 9, 3, 229, 138, 145, 106, 105, 52, 0, 10, 3, 229, 143, 185, 116, 97, 110, 52, 0, 9, 3, 229, 139, 153, 119, 117, 53, 0, 0, 10, 3, 230, 135, 182, 108, 97, 110, 51, 0, 11, 3, 230, 129, 134, 104, 101, 110, 103, 50, 0, 9, 3, 229, 143, 182, 121, 101, 52, 0, 11, 3, 229, 128, 190, 113, 105, 110, 103, 49, 0, 0, 10, 3, 230, 133, 167, 104, 117, 105, 52, 0, 10, 3, 229, 143, 183, 104, 97, 111, 52, 0, 9, 3, 229, 137, 135, 122, 101, 50, 0, 10, 3, 230, 132, 159, 103, 97, 110, 51, 0, 11, 3, 230, 135, 183, 104, 117, 97, 105, 50, 0, 9, 3, 229, 141, 167, 119, 111, 52, 0, 0, 10, 3, 229, 128, 188, 122, 104, 105, 50, 0, 11, 3, 230, 134, 172, 106, 105, 110, 103, 51, 0, 0, 11, 3, 229, 139, 149, 100, 111, 110, 103, 52, 0, 9, 3, 230, 131, 149, 116, 105, 52, 0, 10, 3, 229, 142, 173, 121, 97, 110, 52, 0, 11, 3, 229, 138, 141, 106, 105, 97, 110, 52, 0, 0, 9, 3, 229, 137, 130, 106, 105, 52, 0, 11, 3, 229, 128, 186, 122, 104, 97, 105, 52, 0, 12, 3, 230, 135, 178, 99, 104, 101, 110, 103, 50, 0, 9, 3, 230, 132, 154, 121, 117, 50, 0, 10, 3, 229, 143, 178, 115, 104, 105, 51, 0, 10, 3, 230, 133, 162, 109, 97, 110, 52, 0, 9, 3, 229, 139, 146, 108, 101, 52, 0, 0, 10, 3, 229, 143, 179, 121, 111, 117, 52, 0, 11, 3, 230, 133, 163, 103, 117, 97, 110, 52, 0, 9, 3, 230, 132, 155, 97, 105, 52, 0, 0, 10, 3, 229, 143, 176, 116, 97, 105, 50, 0, 11, 3, 229, 141, 160, 122, 104, 97, 110, 52, 0, 9, 3, 229, 138, 136, 112, 105, 49, 0, 10, 3, 229, 142, 168, 99, 104, 117, 50, 0, 0, 10, 3, 229, 140, 153, 115, 104, 105, 53, 0, 9, 3, 230, 130, 137, 120, 105, 49, 0, 9, 3, 229, 141, 161, 107, 97, 51, 0, 10, 3, 230, 131, 145, 104, 117, 111, 52, 0, 0, 11, 3, 229, 143, 174, 100, 105, 110, 103, 49, 0, 10, 3, 229, 140, 150, 104, 117, 97, 52, 0, 10, 3, 229, 142, 166, 115, 104, 97, 52, 0, 0, 9, 3, 229, 138, 135, 106, 117, 52, 0, 12, 3, 229, 129, 191, 99, 104, 97, 110, 103, 50, 0, 10, 3, 229, 140, 151, 98, 101, 105, 51, 0, 9, 3, 229, 143, 175, 107, 101, 51, 0, 12, 3, 230, 134, 167, 99, 104, 111, 110, 103, 49, 0, 0, 11, 3, 229, 143, 172, 122, 104, 97, 111, 52, 0, 11, 3, 230, 130, 132, 113, 105, 97, 111, 49, 0, 9, 3, 229, 141, 156, 98, 111, 53, 0, 10, 3, 230, 134, 164, 102, 101, 110, 52, 0, 0, 8, 3, 230, 132, 149, 101, 52, 0, 10, 3, 229, 129, 189, 119, 101, 105, 51, 0, 9, 3, 229, 143, 173, 98, 97, 53, 0, 10, 3, 230, 130, 133, 121, 117, 101, 52, 0, 0, 12, 3, 229, 142, 162, 120, 105, 97, 110, 103, 49, 0, 10, 3, 229, 143, 170, 122, 104, 105, 51, 0, 10, 3, 230, 133, 154, 99, 97, 110, 50, 0, 9, 3, 229, 141, 154, 98, 111, 50, 0, 11, 3, 230, 131, 138, 106, 105, 110, 103, 49, 0, 0, 10, 3, 230, 131, 139, 119, 97, 110, 51, 0, 11, 3, 229, 143, 171, 106, 105, 97, 111, 52, 0, 0, 10, 3, 230, 133, 152, 99, 97, 110, 51, 0, 0, 11, 3, 229, 139, 137, 109, 105, 97, 110, 51, 0, 0, 10, 3, 229, 141, 150, 109, 97, 105, 52, 0, 9, 3, 229, 129, 182, 111, 117, 51, 0, 11, 3, 229, 143, 166, 108, 105, 110, 103, 52, 0, 11, 3, 229, 130, 190, 113, 105, 110, 103, 49, 0, 0, 10, 3, 229, 129, 183, 116, 111, 117, 49, 0, 10, 3, 229, 141, 151, 110, 97, 110, 50, 0, 11, 3, 229, 139, 135, 121, 111, 110, 103, 51, 0, 11, 3, 229, 142, 159, 121, 117, 97, 110, 50, 0, 9, 3, 230, 132, 143, 121, 105, 52, 0, 0, 9, 3, 229, 129, 180, 99, 101, 52, 0, 10, 3, 229, 141, 148, 120, 105, 101, 50, 0, 9, 3, 229, 143, 164, 103, 117, 51, 0, 0, 9, 3, 230, 133, 149, 109, 117, 52, 0, 9, 3, 229, 143, 165, 106, 117, 52, 0, 10, 3, 229, 141, 149, 100, 97, 110, 49, 0, 11, 3, 230, 131, 133, 113, 105, 110, 103, 50, 0, 11, 3, 229, 129, 181, 122, 104, 101, 110, 49, 0, 0, 10, 3, 229, 142, 154, 104, 111, 117, 52, 0, 11, 3, 229, 143, 162, 99, 111, 110, 103, 50, 0, 0, 9, 3, 229, 139, 131, 98, 111, 50, 0, 10, 3, 229, 143, 163, 107, 111, 117, 51, 0, 10, 3, 229, 130, 187, 115, 104, 97, 51, 0, 0, 10, 3, 229, 143, 160, 100, 105, 101, 50, 0, 9, 3, 230, 132, 136, 121, 117, 52, 0, 9, 3, 229, 142, 152, 108, 105, 50, 0, 0, 9, 3, 230, 132, 137, 121, 117, 50, 0, 10, 3, 229, 139, 129, 106, 105, 110, 52, 0, 10, 3, 229, 141, 145, 98, 101, 105, 49, 0, 0, 11, 3, 231, 133, 142, 106, 105, 97, 110, 49, 0, 10, 3, 230, 130, 182, 109, 101, 110, 52, 0, 11, 3, 230, 141, 142, 115, 104, 97, 111, 49, 0, 11, 3, 230, 128, 166, 112, 101, 110, 103, 49, 0, 10, 3, 229, 139, 190, 103, 111, 117, 49, 0, 0, 9, 3, 230, 129, 175, 120, 105, 53, 0, 11, 3, 231, 135, 159, 121, 105, 110, 103, 50, 0, 10, 3, 230, 141, 143, 110, 105, 101, 49, 0, 11, 3, 229, 148, 135, 99, 104, 117, 110, 50, 0, 9, 3, 229, 137, 175, 102, 117, 52, 0, 10, 3, 229, 149, 143, 119, 101, 110, 52, 0, 11, 3, 230, 128, 167, 120, 105, 110, 103, 52, 0, 10, 3, 230, 140, 135, 122, 104, 105, 51, 0, 0, 10, 3, 229, 136, 164, 112, 97, 110, 52, 0, 12, 3, 231, 133, 140, 104, 117, 97, 110, 103, 50, 0, 11, 3, 231, 134, 148, 114, 111, 110, 103, 50, 0, 8, 3, 229, 150, 148, 111, 49, 0, 10, 3, 229, 148, 132, 98, 101, 105, 53, 0, 0, 10, 3, 230, 141, 141, 104, 97, 110, 52, 0, 9, 3, 230, 128, 165, 106, 105, 50, 0, 10, 3, 229, 136, 165, 98, 105, 101, 50, 0, 0, 10, 3, 230, 142, 146, 112, 97, 105, 50, 0, 8, 3, 229, 149, 138, 97, 53, 0, 11, 3, 230, 143, 154, 121, 97, 110, 103, 50, 0, 10, 3, 230, 130, 178, 98, 101, 105, 49, 0, 10, 3, 230, 140, 130, 103, 117, 97, 52, 0, 11, 3, 229, 137, 170, 106, 105, 97, 110, 51, 0, 9, 3, 229, 151, 154, 119, 117, 49, 0, 10, 3, 229, 138, 178, 106, 105, 110, 52, 0, 0, 10, 3, 229, 138, 179, 108, 97, 111, 50, 0, 10, 3, 229, 139, 187, 121, 117, 110, 50, 0, 11, 3, 230, 143, 155, 104, 117, 97, 110, 52, 0, 0, 10, 3, 230, 129, 168, 104, 101, 110, 52, 0, 10, 3, 230, 142, 144, 113, 105, 97, 49, 0, 11, 3, 229, 139, 184, 113, 117, 97, 110, 52, 0, 0, 9, 3, 230, 131, 185, 114, 101, 51, 0, 12, 3, 229, 137, 169, 115, 104, 101, 110, 103, 52, 0, 10, 3, 230, 140, 129, 99, 104, 105, 50, 0, 9, 3, 229, 138, 177, 108, 105, 52, 0, 11, 3, 230, 141, 137, 122, 104, 117, 111, 49, 0, 11, 3, 231, 135, 153, 116, 97, 110, 103, 52, 0, 11, 3, 231, 133, 137, 108, 105, 97, 110, 52, 0, 0, 10, 3, 230, 141, 134, 107, 117, 110, 51, 0, 12, 3, 229, 149, 134, 115, 104, 97, 110, 103, 49, 0, 11, 3, 229, 140, 190, 98, 105, 97, 110, 51, 0, 12, 3, 230, 131, 182, 104, 117, 97, 110, 103, 50, 0, 0, 10, 3, 231, 134, 143, 120, 117, 110, 49, 0, 9, 3, 229, 137, 167, 106, 117, 52, 0, 11, 3, 230, 132, 191, 121, 117, 97, 110, 52, 0, 10, 3, 230, 142, 143, 116, 97, 111, 49, 0, 0, 11, 3, 230, 128, 156, 108, 105, 97, 110, 50, 0, 11, 3, 230, 130, 172, 120, 117, 97, 110, 50, 0, 12, 3, 230, 142, 140, 122, 104, 97, 110, 103, 51, 0, 11, 3, 229, 149, 132, 122, 104, 117, 111, 50, 0, 0, 10, 3, 229, 136, 157, 99, 104, 117, 49, 0, 9, 3, 229, 137, 165, 98, 111, 49, 0, 9, 3, 230, 128, 157, 115, 105, 49, 0, 9, 3, 229, 139, 181, 108, 105, 52, 0, 10, 3, 230, 129, 165, 99, 104, 105, 51, 0, 10, 3, 231, 135, 149, 121, 97, 110, 52, 0, 0, 12, 3, 231, 134, 138, 120, 105, 111, 110, 103, 50, 0, 10, 3, 229, 150, 138, 104, 97, 110, 51, 0, 10, 3, 230, 143, 146, 99, 104, 97, 49, 0, 9, 3, 229, 138, 170, 110, 117, 51, 0, 9, 3, 230, 141, 130, 119, 117, 51, 0, 10, 3, 230, 129, 162, 104, 117, 105, 49, 0, 11, 3, 231, 135, 146, 115, 104, 97, 111, 49, 0, 9, 3, 229, 140, 186, 113, 117, 49, 0, 11, 3, 229, 136, 154, 103, 97, 110, 103, 49, 0, 0, 13, 3, 229, 136, 155, 99, 104, 117, 97, 110, 103, 52, 0, 9, 3, 229, 140, 187, 121, 105, 49, 0, 10, 3, 229, 149, 131, 107, 101, 110, 51, 0, 12, 3, 230, 131, 179, 120, 105, 97, 110, 103, 51, 0, 11, 3, 229, 151, 147, 115, 97, 110, 103, 51, 0, 0, 9, 3, 230, 143, 144, 116, 105, 50, 0, 10, 3, 230, 130, 168, 110, 105, 110, 50, 0, 10, 3, 229, 151, 144, 104, 97, 105, 52, 0, 11, 3, 229, 138, 168, 100, 111, 110, 103, 52, 0, 11, 3, 230, 142, 136, 115, 104, 111, 117, 52, 0, 0, 9, 3, 229, 136, 153, 122, 101, 50, 0, 11, 3, 230, 142, 137, 100, 105, 97, 111, 52, 0, 10, 3, 230, 131, 177, 110, 97, 111, 51, 0, 9, 3, 229, 140, 185, 112, 105, 51, 0, 10, 3, 229, 138, 169, 122, 104, 117, 52, 0, 10, 3, 229, 150, 137, 104, 111, 117, 50, 0, 0, 10, 3, 230, 130, 166, 121, 117, 101, 52, 0, 9, 3, 230, 128, 150, 98, 117, 52, 0, 9, 3, 229, 151, 142, 109, 97, 53, 0, 0, 10, 3, 229, 136, 151, 108, 105, 101, 52, 0, 11, 3, 230, 143, 143, 109, 105, 97, 111, 50, 0, 9, 3, 229, 150, 135, 108, 97, 51, 0, 11, 3, 230, 131, 175, 103, 117, 97, 110, 52, 0, 0, 10, 3, 230, 142, 132, 108, 117, 110, 49, 0, 12, 3, 230, 128, 148, 122, 104, 101, 110, 103, 49, 0, 9, 3, 231, 134, 132, 120, 105, 49, 0, 11, 3, 229, 150, 132, 115, 104, 97, 110, 52, 0, 0, 9, 3, 230, 128, 149, 112, 97, 52, 0, 9, 3, 229, 137, 157, 98, 111, 49, 0, 10, 3, 230, 131, 173, 99, 97, 110, 50, 0, 10, 3, 230, 143, 141, 122, 111, 117, 52, 0, 0, 10, 3, 229, 136, 146, 104, 117, 97, 52, 0, 10, 3, 229, 150, 130, 119, 101, 105, 52, 0, 9, 3, 230, 128, 146, 110, 117, 52, 0, 0, 10, 3, 229, 150, 131, 110, 97, 110, 50, 0, 10, 3, 229, 141, 187, 113, 117, 101, 52, 0, 11, 3, 229, 137, 155, 103, 97, 110, 103, 49, 0, 10, 3, 229, 138, 163, 108, 105, 101, 52, 0, 10, 3, 230, 142, 131, 115, 97, 111, 51, 0, 11, 3, 230, 130, 163, 104, 117, 97, 110, 52, 0, 0, 11, 3, 231, 135, 136, 100, 101, 110, 103, 49, 0, 10, 3, 229, 138, 160, 106, 105, 97, 49, 0, 11, 3, 230, 142, 128, 120, 105, 97, 110, 49, 0, 10, 3, 230, 130, 160, 121, 111, 117, 49, 0, 10, 3, 229, 141, 184, 120, 105, 101, 52, 0, 10, 3, 230, 131, 168, 99, 97, 110, 51, 0, 0, 10, 3, 230, 143, 137, 114, 111, 117, 50, 0, 9, 3, 229, 138, 161, 119, 117, 53, 0, 12, 3, 230, 131, 169, 99, 104, 101, 110, 103, 50, 0, 11, 3, 229, 136, 145, 120, 105, 110, 103, 50, 0, 0, 10, 3, 229, 138, 158, 98, 97, 110, 52, 0, 10, 3, 230, 128, 142, 122, 101, 110, 51, 0, 11, 3, 230, 133, 182, 113, 105, 110, 103, 52, 0, 11, 3, 230, 131, 166, 100, 105, 97, 110, 52, 0, 10, 3, 230, 134, 190, 104, 97, 110, 52, 0, 10, 3, 229, 137, 150, 112, 111, 117, 49, 0, 0, 10, 3, 229, 140, 175, 104, 117, 105, 52, 0, 9, 3, 230, 130, 159, 119, 117, 52, 0, 9, 3, 230, 131, 167, 106, 117, 52, 0, 11, 3, 229, 141, 183, 106, 117, 97, 110, 51, 0, 11, 3, 229, 138, 159, 103, 111, 110, 103, 49, 0, 11, 3, 230, 133, 183, 107, 97, 110, 103, 49, 0, 11, 3, 229, 142, 191, 120, 105, 97, 110, 52, 0, 0, 10, 3, 229, 141, 180, 113, 117, 101, 52, 0, 9, 3, 229, 137, 148, 116, 105, 49, 0, 10, 3, 229, 139, 164, 113, 105, 110, 50, 0, 0, 11, 3, 229, 138, 157, 113, 117, 97, 110, 52, 0, 11, 3, 229, 141, 181, 108, 117, 97, 110, 51, 0, 10, 3, 229, 151, 133, 120, 105, 117, 52, 0, 0, 10, 3, 229, 140, 170, 102, 101, 105, 51, 0, 11, 3, 230, 129, 146, 104, 101, 110, 103, 50, 0, 10, 3, 229, 139, 162, 115, 104, 105, 52, 0, 10, 3, 229, 136, 138, 107, 97, 110, 49, 0, 0, 9, 3, 229, 142, 187, 113, 117, 52, 0, 9, 3, 229, 141, 179, 106, 105, 50, 0, 10, 3, 231, 135, 131, 114, 97, 110, 50, 0, 9, 3, 229, 138, 155, 108, 105, 52, 0, 0, 11, 3, 230, 143, 128, 106, 105, 97, 110, 51, 0, 10, 3, 229, 141, 176, 121, 105, 110, 52, 0, 10, 3, 230, 133, 176, 119, 101, 105, 52, 0, 11, 3, 230, 129, 144, 107, 111, 110, 103, 51, 0, 0, 11, 3, 229, 137, 145, 106, 105, 97, 110, 52, 0, 10, 3, 229, 141, 177, 119, 101, 105, 49, 0, 8, 3, 230, 131, 161, 101, 52, 0, 0, 9, 3, 229, 146, 150, 107, 97, 49, 0, 10, 3, 231, 133, 174, 122, 104, 117, 51, 0, 10, 3, 230, 137, 142, 122, 104, 97, 49, 0, 10, 3, 230, 138, 150, 100, 111, 117, 51, 0, 10, 3, 229, 144, 134, 121, 97, 111, 49, 0, 9, 3, 230, 141, 174, 106, 117, 52, 0, 11, 3, 231, 132, 166, 106, 105, 97, 111, 49, 0, 0, 11, 3, 230, 138, 151, 107, 97, 110, 103, 52, 0, 9, 3, 230, 139, 159, 110, 105, 51, 0, 10, 3, 230, 142, 183, 122, 104, 105, 52, 0, 9, 3, 229, 147, 159, 121, 111, 49, 0, 10, 3, 231, 131, 159, 121, 97, 110, 49, 0, 10, 3, 229, 150, 183, 112, 101, 110, 49, 0, 0, 10, 3, 230, 139, 156, 98, 97, 105, 52, 0, 11, 3, 231, 129, 140, 103, 117, 97, 110, 52, 0, 9, 3, 230, 140, 164, 106, 105, 51, 0, 9, 3, 229, 144, 132, 103, 101, 52, 0, 11, 3, 229, 148, 164, 104, 117, 97, 110, 52, 0, 0, 10, 3, 229, 151, 189, 115, 111, 117, 53, 0, 10, 3, 230, 138, 149, 116, 111, 117, 50, 0, 10, 3, 230, 137, 141, 99, 97, 105, 50, 0, 10, 3, 230, 140, 165, 104, 117, 105, 49, 0, 9, 3, 229, 146, 149, 103, 117, 53, 0, 11, 3, 231, 130, 149, 107, 97, 110, 103, 52, 0, 0, 10, 3, 229, 145, 138, 103, 97, 111, 52, 0, 11, 3, 231, 130, 146, 99, 104, 97, 111, 51, 0, 11, 3, 229, 146, 146, 122, 104, 111, 117, 52, 0, 9, 3, 229, 149, 170, 112, 97, 49, 0, 9, 3, 229, 150, 178, 121, 111, 49, 0, 0, 10, 3, 231, 131, 155, 122, 104, 117, 50, 0, 11, 3, 230, 137, 139, 115, 104, 111, 117, 51, 0, 11, 3, 230, 138, 147, 122, 104, 117, 97, 49, 0, 10, 3, 229, 144, 131, 99, 104, 105, 49, 0, 11, 3, 230, 139, 155, 122, 104, 97, 111, 49, 0, 12, 3, 230, 140, 163, 122, 104, 101, 110, 103, 49, 0, 0, 10, 3, 230, 142, 176, 98, 97, 105, 49, 0, 11, 3, 230, 136, 128, 108, 105, 97, 110, 52, 0, 12, 3, 229, 145, 136, 99, 104, 101, 110, 103, 50, 0, 9, 3, 230, 139, 152, 106, 117, 49, 0, 9, 3, 229, 146, 144, 102, 117, 53, 0, 11, 3, 231, 131, 152, 104, 111, 110, 103, 49, 0, 0, 9, 3, 231, 134, 177, 114, 101, 52, 0, 11, 3, 230, 140, 161, 100, 97, 110, 103, 51, 0, 9, 3, 229, 144, 129, 120, 117, 49, 0, 9, 3, 231, 132, 161, 119, 117, 50, 0, 9, 3, 230, 138, 145, 121, 105, 52, 0, 10, 3, 231, 133, 169, 102, 97, 110, 50, 0, 0, 10, 3, 229, 145, 134, 100, 97, 105, 49, 0, 10, 3, 230, 139, 150, 116, 117, 111, 49, 0, 10, 3, 231, 130, 142, 121, 97, 110, 50, 0, 9, 3, 229, 149, 166, 108, 97, 53, 0, 10, 3, 229, 150, 174, 100, 97, 110, 49, 0, 0, 10, 3, 230, 140, 159, 120, 105, 101, 50, 0, 11, 3, 231, 133, 167, 122, 104, 97, 111, 52, 0, 10, 3, 229, 147, 151, 104, 117, 97, 49, 0, 11, 3, 230, 137, 135, 115, 104, 97, 110, 52, 0, 11, 3, 230, 141, 167, 112, 101, 110, 103, 51, 0, 0, 10, 3, 231, 133, 164, 109, 101, 105, 50, 0, 9, 3, 230, 139, 148, 98, 97, 50, 0, 9, 3, 229, 149, 164, 112, 105, 50, 0, 9, 3, 231, 134, 172, 97, 111, 50, 0, 11, 3, 230, 143, 180, 121, 117, 97, 110, 50, 0, 9, 3, 229, 146, 140, 104, 101, 50, 0, 0, 10, 3, 229, 149, 165, 115, 104, 97, 52, 0, 0, 11, 3, 229, 150, 170, 115, 97, 110, 103, 52, 0, 9, 3, 230, 138, 138, 98, 97, 51, 0, 11, 3, 230, 141, 162, 104, 117, 97, 110, 52, 0, 10, 3, 230, 142, 170, 99, 117, 111, 52, 0, 9, 3, 229, 136, 186, 99, 105, 52, 0, 11, 3, 231, 130, 138, 99, 104, 117, 105, 49, 0, 9, 3, 230, 139, 146, 106, 117, 52, 0, 0, 9, 3, 229, 136, 187, 107, 101, 52, 0, 8, 3, 229, 145, 131, 101, 52, 0, 9, 3, 229, 146, 139, 122, 97, 51, 0, 11, 3, 230, 128, 187, 122, 111, 110, 103, 51, 0, 10, 3, 230, 141, 163, 100, 97, 111, 51, 0, 0, 10, 3, 230, 137, 128, 115, 117, 111, 51, 0, 11, 3, 230, 139, 144, 103, 117, 97, 105, 51, 0, 9, 3, 229, 145, 128, 121, 97, 53, 0, 10, 3, 230, 142, 168, 116, 117, 105, 49, 0, 0, 10, 3, 230, 142, 169, 121, 97, 110, 51, 0, 10, 3, 229, 149, 161, 102, 101, 105, 49, 0, 10, 3, 229, 136, 185, 115, 104, 97, 49, 0, 11, 3, 230, 137, 129, 98, 105, 97, 110, 51, 0, 9, 3, 231, 130, 137, 108, 117, 50, 0, 11, 3, 230, 141, 161, 106, 105, 97, 110, 51, 0, 9, 3, 229, 147, 145, 121, 97, 51, 0, 0, 10, 3, 229, 146, 134, 112, 97, 111, 50, 0, 10, 3, 230, 143, 174, 104, 117, 105, 49, 0, 10, 3, 231, 133, 158, 115, 104, 97, 52, 0, 9, 3, 229, 149, 158, 121, 97, 51, 0, 9, 3, 230, 140, 150, 119, 97, 49, 0, 10, 3, 230, 141, 158, 108, 97, 111, 49, 0, 9, 3, 229, 147, 142, 97, 105, 49, 0, 10, 3, 229, 136, 182, 122, 104, 105, 52, 0, 0, 9, 3, 229, 151, 175, 110, 103, 50, 0, 10, 3, 230, 141, 159, 115, 117, 110, 51, 0, 11, 3, 229, 136, 183, 115, 104, 117, 97, 49, 0, 11, 3, 230, 142, 167, 107, 111, 110, 103, 52, 0, 11, 3, 229, 137, 191, 106, 105, 97, 111, 51, 0, 9, 3, 229, 149, 159, 113, 105, 51, 0, 9, 3, 231, 131, 143, 119, 117, 49, 0, 10, 3, 229, 147, 143, 103, 101, 110, 50, 0, 0, 10, 3, 230, 139, 140, 98, 97, 110, 52, 0, 10, 3, 230, 129, 188, 110, 97, 111, 51, 0, 9, 3, 229, 151, 172, 104, 101, 49, 0, 11, 3, 230, 138, 132, 99, 104, 97, 111, 49, 0, 0, 10, 3, 231, 135, 173, 122, 104, 117, 50, 0, 12, 3, 229, 147, 141, 120, 105, 97, 110, 103, 51, 0, 10, 3, 230, 142, 165, 106, 105, 101, 49, 0, 10, 3, 230, 143, 173, 106, 105, 101, 49, 0, 10, 3, 230, 139, 141, 112, 97, 105, 49, 0, 0, 10, 3, 230, 142, 162, 116, 97, 110, 52, 0, 10, 3, 230, 143, 170, 106, 105, 117, 49, 0, 9, 3, 229, 146, 130, 122, 97, 49, 0, 0, 10, 3, 230, 139, 139, 112, 97, 111, 49, 0, 0, 9, 3, 230, 138, 128, 106, 105, 52, 0, 10, 3, 229, 151, 168, 104, 97, 105, 49, 0, 10, 3, 229, 136, 176, 100, 97, 111, 52, 0, 10, 3, 230, 142, 160, 108, 118, 101, 52, 0, 9, 3, 229, 146, 128, 106, 117, 51, 0, 9, 3, 229, 147, 136, 104, 97, 49, 0, 10, 3, 231, 131, 136, 108, 105, 101, 52, 0, 0, 11, 3, 230, 140, 145, 116, 105, 97, 111, 49, 0, 10, 3, 230, 143, 169, 107, 97, 105, 49, 0, 10, 3, 231, 133, 153, 121, 97, 110, 49, 0, 9, 3, 230, 139, 137, 108, 97, 49, 0, 0, 10, 3, 231, 135, 166, 99, 97, 110, 52, 0, 10, 3, 229, 151, 166, 115, 117, 111, 53, 0, 10, 3, 229, 147, 134, 100, 117, 111, 49, 0, 10, 3, 229, 136, 174, 103, 117, 97, 49, 0, 8, 3, 230, 129, 182, 101, 52, 0, 11, 3, 230, 139, 134, 99, 104, 97, 105, 49, 0, 10, 3, 230, 140, 142, 107, 117, 97, 52, 0, 0, 9, 3, 229, 147, 135, 119, 97, 53, 0, 10, 3, 230, 128, 175, 113, 105, 101, 52, 0, 10, 3, 231, 134, 159, 115, 104, 117, 50, 0, 10, 3, 229, 138, 191, 115, 104, 105, 52, 0, 9, 3, 230, 139, 135, 109, 117, 53, 0, 0, 11, 3, 229, 147, 132, 104, 111, 110, 103, 49, 0, 9, 3, 229, 150, 156, 120, 105, 51, 0, 10, 3, 230, 130, 188, 100, 97, 111, 52, 0, 10, 3, 230, 139, 132, 122, 104, 117, 51, 0, 0, 10, 3, 230, 139, 133, 100, 97, 110, 49, 0, 9, 3, 229, 150, 157, 104, 101, 49, 0, 13, 3, 229, 137, 181, 99, 104, 117, 97, 110, 103, 52, 0, 9, 3, 230, 141, 149, 98, 117, 51, 0, 10, 3, 231, 135, 165, 122, 97, 111, 52, 0, 0, 11, 3, 229, 150, 154, 104, 117, 97, 110, 52, 0, 9, 3, 229, 137, 178, 103, 101, 49, 0, 11, 3, 230, 128, 170, 103, 117, 97, 105, 52, 0, 10, 3, 231, 131, 130, 108, 97, 110, 52, 0, 10, 3, 231, 132, 138, 104, 97, 110, 52, 0, 0, 10, 3, 229, 136, 171, 98, 105, 101, 50, 0, 10, 3, 230, 142, 155, 103, 117, 97, 52, 0, 12, 3, 230, 143, 163, 99, 104, 117, 97, 105, 49, 0, 10, 3, 230, 129, 179, 107, 101, 110, 51, 0, 0, 9, 3, 229, 147, 128, 97, 105, 49, 0, 11, 3, 230, 128, 168, 121, 117, 97, 110, 52, 0, 12, 3, 229, 150, 152, 99, 104, 117, 97, 110, 51, 0, 10, 3, 230, 129, 176, 113, 105, 97, 52, 0, 11, 3, 230, 141, 144, 106, 117, 97, 110, 49, 0, 10, 3, 229, 136, 168, 112, 97, 111, 50, 0, 10, 3, 230, 142, 152, 106, 117, 101, 50, 0, 0, 12, 3, 230, 142, 153, 122, 104, 101, 110, 103, 49, 0, 11, 3, 229, 151, 161, 119, 101, 110, 103, 49, 0, 9, 3, 229, 136, 169, 108, 105, 52, 0, 9, 3, 230, 140, 137, 97, 110, 52, 0, 9, 3, 230, 143, 161, 119, 111, 52, 0, 11, 3, 231, 131, 129, 115, 104, 117, 111, 52, 0, 10, 3, 229, 147, 129, 112, 105, 110, 51, 0, 0, 11, 3, 229, 156, 134, 121, 117, 97, 110, 50, 0, 10, 3, 230, 137, 174, 98, 97, 110, 53, 0, 10, 3, 229, 157, 142, 107, 97, 110, 51, 0, 10, 3, 232, 132, 134, 99, 117, 105, 52, 0, 12, 3, 231, 141, 142, 106, 105, 97, 110, 103, 51, 0, 10, 3, 229, 144, 166, 102, 111, 117, 51, 0, 10, 3, 230, 139, 190, 115, 104, 105, 53, 0, 11, 3, 230, 148, 134, 110, 105, 97, 110, 51, 0, 0, 11, 3, 231, 129, 175, 100, 101, 110, 103, 49, 0, 11, 3, 229, 157, 143, 104, 117, 97, 105, 52, 0, 9, 3, 230, 139, 191, 110, 97, 50, 0, 11, 3, 232, 135, 159, 122, 97, 110, 103, 52, 0, 9, 3, 229, 159, 159, 121, 117, 52, 0, 10, 3, 230, 137, 175, 99, 104, 101, 51, 0, 10, 3, 230, 149, 143, 109, 105, 110, 51, 0, 9, 3, 229, 144, 167, 98, 97, 53, 0, 10, 3, 230, 150, 151, 100, 111, 117, 52, 0, 0, 10, 3, 230, 139, 188, 112, 105, 110, 49, 0, 11, 3, 230, 137, 172, 121, 97, 110, 103, 50, 0, 9, 3, 230, 149, 140, 100, 105, 50, 0, 11, 3, 229, 147, 188, 104, 101, 110, 103, 49, 0, 0, 9, 3, 230, 138, 181, 100, 105, 51, 0, 10, 3, 232, 132, 133, 120, 105, 101, 50, 0, 10, 3, 231, 129, 173, 109, 105, 101, 52, 0, 11, 3, 229, 147, 189, 103, 101, 110, 103, 51, 0, 10, 3, 230, 137, 173, 110, 105, 117, 51, 0, 0, 10, 3, 229, 158, 146, 108, 101, 105, 51, 0, 10, 3, 232, 132, 130, 122, 104, 105, 49, 0, 9, 3, 229, 147, 186, 98, 117, 51, 0, 11, 3, 229, 157, 138, 102, 97, 110, 103, 53, 0, 0, 10, 3, 231, 129, 171, 104, 117, 111, 51, 0, 10, 3, 230, 137, 171, 115, 97, 111, 51, 0, 10, 3, 229, 146, 179, 104, 97, 105, 49, 0, 0, 10, 3, 230, 148, 128, 112, 97, 110, 49, 0, 11, 3, 229, 145, 168, 122, 104, 111, 117, 49, 0, 11, 3, 230, 149, 136, 120, 105, 97, 111, 52, 0, 11, 3, 232, 133, 136, 106, 105, 110, 103, 49, 0, 0, 10, 3, 230, 137, 169, 107, 117, 111, 52, 0, 10, 3, 230, 138, 177, 98, 97, 111, 52, 0, 10, 3, 229, 146, 177, 122, 97, 110, 50, 0, 0, 10, 3, 229, 148, 190, 116, 117, 111, 52, 0, 10, 3, 229, 144, 158, 116, 117, 110, 49, 0, 10, 3, 230, 140, 190, 120, 105, 101, 50, 0, 10, 3, 231, 130, 174, 112, 97, 111, 52, 0, 0, 10, 3, 232, 134, 143, 103, 97, 111, 49, 0, 12, 3, 231, 130, 175, 106, 105, 111, 110, 103, 51, 0, 10, 3, 229, 144, 159, 121, 105, 110, 50, 0, 10, 3, 230, 137, 167, 122, 104, 105, 50, 0, 9, 3, 230, 151, 151, 113, 105, 50, 0, 10, 3, 229, 157, 135, 106, 117, 110, 49, 0, 0, 10, 3, 230, 138, 172, 116, 97, 105, 50, 0, 9, 3, 231, 141, 132, 121, 117, 52, 0, 10, 3, 229, 146, 172, 121, 97, 111, 51, 0, 12, 3, 230, 139, 180, 115, 104, 117, 97, 110, 49, 0, 0, 9, 3, 230, 149, 133, 103, 117, 52, 0, 10, 3, 231, 130, 173, 116, 97, 110, 52, 0, 10, 3, 230, 140, 189, 119, 97, 110, 51, 0, 10, 3, 231, 141, 133, 115, 104, 105, 49, 0, 9, 3, 231, 128, 157, 108, 105, 52, 0, 0, 10, 3, 229, 147, 178, 122, 104, 101, 50, 0, 9, 3, 232, 134, 138, 98, 111, 53, 0, 9, 3, 229, 145, 162, 110, 101, 53, 0, 11, 3, 230, 140, 186, 116, 105, 110, 103, 51, 0, 9, 3, 230, 136, 154, 113, 105, 53, 0, 0, 11, 3, 229, 158, 139, 120, 105, 110, 103, 50, 0, 11, 3, 231, 142, 139, 119, 97, 110, 103, 50, 0, 11, 3, 230, 139, 179, 113, 117, 97, 110, 50, 0, 10, 3, 231, 129, 163, 119, 97, 110, 49, 0, 10, 3, 229, 144, 155, 106, 117, 110, 49, 0, 10, 3, 230, 137, 163, 107, 111, 117, 52, 0, 9, 3, 230, 138, 171, 112, 105, 49, 0, 0, 10, 3, 229, 157, 128, 122, 104, 105, 51, 0, 11, 3, 230, 136, 152, 122, 104, 97, 110, 52, 0, 0, 11, 3, 230, 139, 177, 103, 111, 110, 103, 51, 0, 9, 3, 231, 142, 137, 121, 117, 52, 0, 11, 3, 231, 143, 145, 108, 111, 110, 103, 50, 0, 0, 9, 3, 229, 146, 166, 121, 105, 50, 0, 10, 3, 229, 149, 190, 106, 105, 117, 49, 0, 10, 3, 230, 136, 150, 104, 117, 111, 52, 0, 11, 3, 229, 147, 174, 120, 105, 97, 111, 49, 0, 12, 3, 229, 159, 142, 99, 104, 101, 110, 103, 50, 0, 10, 3, 231, 132, 182, 114, 97, 110, 50, 0, 0, 9, 3, 230, 151, 143, 122, 117, 50, 0, 9, 3, 231, 142, 135, 108, 118, 52, 0, 10, 3, 229, 146, 167, 108, 105, 101, 53, 0, 9, 3, 229, 144, 151, 109, 97, 53, 0, 10, 3, 230, 150, 135, 119, 101, 110, 50, 0, 0, 9, 3, 229, 149, 188, 116, 105, 50, 0, 11, 3, 229, 158, 132, 108, 111, 110, 103, 51, 0, 10, 3, 230, 139, 172, 107, 117, 111, 52, 0, 9, 3, 229, 145, 156, 119, 117, 49, 0, 9, 3, 230, 138, 164, 104, 117, 52, 0, 0, 10, 3, 230, 138, 165, 98, 97, 111, 52, 0, 10, 3, 230, 139, 173, 115, 104, 105, 52, 0, 9, 3, 231, 131, 173, 114, 101, 52, 0, 9, 3, 229, 147, 173, 107, 117, 49, 0, 11, 3, 231, 143, 141, 122, 104, 101, 110, 49, 0, 0, 11, 3, 229, 158, 130, 99, 104, 117, 105, 50, 0, 10, 3, 230, 136, 146, 106, 105, 101, 52, 0, 9, 3, 229, 147, 170, 110, 97, 51, 0, 11, 3, 231, 143, 138, 115, 104, 97, 110, 49, 0, 12, 3, 230, 138, 162, 113, 105, 97, 110, 103, 51, 0, 0, 11, 3, 230, 141, 187, 110, 105, 97, 110, 51, 0, 9, 3, 230, 150, 131, 98, 105, 52, 0, 11, 3, 231, 131, 171, 116, 97, 110, 103, 52, 0, 11, 3, 230, 137, 155, 107, 97, 110, 103, 50, 0, 11, 3, 230, 151, 139, 120, 117, 97, 110, 50, 0, 10, 3, 229, 144, 147, 120, 105, 97, 52, 0, 9, 3, 229, 158, 131, 108, 97, 49, 0, 10, 3, 229, 159, 139, 109, 97, 105, 50, 0, 0, 10, 3, 231, 129, 152, 116, 97, 110, 49, 0, 11, 3, 229, 145, 152, 121, 117, 97, 110, 50, 0, 10, 3, 231, 132, 176, 121, 97, 110, 52, 0, 11, 3, 229, 148, 176, 115, 104, 117, 97, 49, 0, 12, 3, 230, 136, 144, 99, 104, 101, 110, 103, 50, 0, 11, 3, 229, 149, 184, 120, 105, 97, 111, 52, 0, 9, 3, 230, 139, 168, 98, 111, 49, 0, 10, 3, 230, 137, 152, 116, 117, 111, 49, 0, 11, 3, 232, 134, 128, 98, 97, 110, 103, 51, 0, 9, 3, 229, 144, 144, 116, 117, 51, 0, 11, 3, 229, 147, 168, 115, 104, 97, 111, 52, 0, 0, 10, 3, 230, 138, 161, 108, 117, 110, 49, 0, 12, 3, 229, 144, 145, 120, 105, 97, 110, 103, 52, 0, 9, 3, 231, 128, 145, 112, 117, 52, 0, 9, 3, 229, 147, 169, 108, 105, 53, 0, 12, 3, 229, 148, 177, 99, 104, 97, 110, 103, 52, 0, 9, 3, 230, 136, 145, 119, 111, 51, 0, 11, 3, 232, 135, 137, 108, 105, 97, 110, 51, 0, 9, 3, 230, 139, 169, 122, 101, 50, 0, 0, 11, 3, 229, 148, 174, 115, 104, 111, 117, 52, 0, 11, 3, 230, 141, 182, 99, 104, 117, 105, 50, 0, 10, 3, 229, 144, 142, 104, 111, 117, 52, 0, 10, 3, 230, 139, 166, 108, 97, 110, 50, 0, 10, 3, 231, 131, 166, 102, 97, 110, 50, 0, 8, 3, 229, 147, 166, 111, 50, 0, 0, 11, 3, 230, 140, 175, 122, 104, 101, 110, 52, 0, 9, 3, 230, 136, 143, 120, 105, 52, 0, 10, 3, 230, 141, 183, 106, 105, 101, 50, 0, 10, 3, 229, 147, 167, 99, 104, 105, 49, 0, 11, 3, 231, 131, 167, 115, 104, 97, 111, 49, 0, 10, 3, 229, 148, 175, 119, 101, 105, 50, 0, 11, 3, 230, 139, 167, 110, 105, 110, 103, 50, 0, 10, 3, 229, 145, 151, 98, 101, 105, 53, 0, 0, 11, 3, 229, 144, 140, 116, 111, 110, 103, 50, 0, 10, 3, 231, 131, 164, 107, 97, 111, 51, 0, 11, 3, 230, 137, 148, 114, 101, 110, 103, 49, 0, 9, 3, 229, 148, 172, 104, 117, 53, 0, 0, 11, 3, 230, 139, 165, 121, 111, 110, 103, 49, 0, 10, 3, 229, 150, 189, 108, 111, 117, 53, 0, 11, 3, 229, 144, 141, 109, 105, 110, 103, 50, 0, 9, 3, 229, 147, 165, 103, 101, 49, 0, 9, 3, 230, 151, 133, 108, 118, 51, 0, 0, 9, 3, 230, 137, 146, 98, 97, 49, 0, 9, 3, 230, 138, 154, 102, 117, 51, 0, 11, 3, 229, 144, 138, 100, 105, 97, 111, 52, 0, 11, 3, 230, 139, 162, 108, 111, 110, 103, 51, 0, 9, 3, 232, 135, 130, 98, 105, 52, 0, 0, 11, 3, 230, 139, 163, 106, 105, 97, 110, 51, 0, 9, 3, 229, 159, 131, 97, 105, 49, 0, 10, 3, 230, 140, 171, 99, 117, 111, 52, 0, 11, 3, 229, 146, 155, 110, 105, 110, 103, 50, 0, 9, 3, 230, 137, 147, 100, 97, 51, 0, 10, 3, 230, 138, 155, 112, 97, 111, 49, 0, 0, 9, 3, 230, 140, 168, 97, 105, 49, 0, 9, 3, 229, 144, 136, 104, 101, 50, 0, 10, 3, 230, 138, 152, 122, 104, 101, 50, 0, 9, 3, 229, 145, 144, 110, 101, 53, 0, 0, 11, 3, 230, 151, 129, 112, 97, 110, 103, 50, 0, 11, 3, 229, 146, 153, 108, 111, 110, 103, 50, 0, 9, 3, 230, 137, 145, 112, 117, 49, 0, 9, 3, 229, 144, 137, 106, 105, 50, 0, 11, 3, 229, 147, 161, 121, 117, 97, 110, 50, 0, 0, 11, 3, 231, 143, 190, 120, 105, 97, 110, 52, 0, 10, 3, 231, 136, 134, 98, 97, 111, 52, 0, 10, 3, 229, 152, 134, 116, 97, 110, 52, 0, 10, 3, 232, 131, 158, 98, 97, 111, 49, 0, 10, 3, 232, 133, 174, 115, 97, 105, 49, 0, 11, 3, 232, 130, 150, 120, 105, 97, 111, 52, 0, 10, 3, 229, 155, 158, 104, 117, 105, 50, 0, 0, 9, 3, 229, 157, 175, 112, 105, 49, 0, 11, 3, 230, 150, 183, 100, 117, 97, 110, 52, 0, 0, 11, 3, 230, 149, 172, 106, 105, 110, 103, 52, 0, 10, 3, 232, 129, 140, 122, 104, 105, 50, 0, 10, 3, 231, 137, 140, 112, 97, 105, 50, 0, 10, 3, 230, 148, 164, 116, 97, 110, 49, 0, 12, 3, 232, 131, 156, 115, 104, 101, 110, 103, 52, 0, 0, 11, 3, 230, 144, 133, 106, 105, 97, 111, 51, 0, 11, 3, 230, 148, 165, 122, 117, 97, 110, 52, 0, 10, 3, 232, 128, 133, 122, 104, 101, 51, 0, 9, 3, 230, 146, 149, 115, 105, 49, 0, 0, 10, 3, 230, 145, 138, 116, 97, 110, 49, 0, 11, 3, 231, 142, 178, 108, 105, 110, 103, 50, 0, 10, 3, 230, 148, 162, 122, 97, 110, 51, 0, 9, 3, 230, 146, 146, 115, 97, 49, 0, 9, 3, 229, 159, 186, 106, 105, 49, 0, 11, 3, 232, 129, 138, 108, 105, 97, 111, 50, 0, 9, 3, 230, 147, 154, 106, 117, 52, 0, 11, 3, 230, 151, 186, 119, 97, 110, 103, 52, 0, 10, 3, 230, 144, 130, 108, 111, 117, 51, 0, 0, 10, 3, 232, 128, 131, 107, 97, 111, 51, 0, 9, 3, 229, 155, 155, 115, 105, 52, 0, 12, 3, 229, 156, 163, 115, 104, 101, 110, 103, 52, 0, 12, 3, 232, 133, 171, 122, 104, 111, 110, 103, 51, 0, 0, 11, 3, 231, 142, 176, 120, 105, 97, 110, 52, 0, 9, 3, 229, 152, 128, 100, 105, 50, 0, 10, 3, 230, 150, 176, 120, 105, 110, 49, 0, 12, 3, 230, 146, 144, 99, 104, 101, 110, 103, 49, 0, 10, 3, 232, 128, 128, 121, 97, 111, 52, 0, 9, 3, 231, 141, 168, 100, 117, 50, 0, 11, 3, 230, 144, 128, 99, 104, 97, 110, 49, 0, 10, 3, 231, 137, 136, 98, 97, 110, 51, 0, 0, 10, 3, 232, 128, 129, 108, 97, 111, 51, 0, 12, 3, 230, 146, 145, 99, 104, 101, 110, 103, 49, 0, 9, 3, 230, 144, 129, 103, 101, 49, 0, 10, 3, 229, 159, 185, 112, 101, 105, 50, 0, 0, 10, 3, 230, 151, 182, 115, 104, 105, 50, 0, 10, 3, 229, 157, 166, 116, 97, 110, 51, 0, 10, 3, 230, 145, 134, 98, 97, 105, 51, 0, 10, 3, 229, 158, 174, 107, 117, 97, 51, 0, 11, 3, 232, 131, 150, 112, 97, 110, 103, 52, 0, 12, 3, 231, 137, 134, 113, 105, 97, 110, 103, 50, 0, 10, 3, 232, 133, 166, 110, 97, 111, 51, 0, 0, 9, 3, 229, 156, 159, 116, 117, 51, 0, 10, 3, 229, 159, 183, 122, 104, 105, 50, 0, 11, 3, 231, 137, 135, 112, 105, 97, 110, 52, 0, 9, 3, 230, 150, 175, 115, 105, 49, 0, 12, 3, 230, 151, 183, 107, 117, 97, 110, 103, 52, 0, 11, 3, 230, 136, 191, 102, 97, 110, 103, 50, 0, 10, 3, 231, 139, 151, 103, 111, 117, 51, 0, 10, 3, 230, 145, 135, 121, 97, 111, 50, 0, 11, 3, 231, 142, 175, 104, 117, 97, 110, 50, 0, 0, 10, 3, 232, 135, 180, 122, 104, 105, 52, 0, 10, 3, 230, 147, 148, 100, 97, 110, 49, 0, 10, 3, 229, 144, 188, 104, 111, 117, 51, 0, 10, 3, 230, 148, 156, 120, 105, 101, 50, 0, 9, 3, 232, 130, 140, 106, 105, 49, 0, 10, 3, 230, 145, 132, 115, 104, 101, 52, 0, 10, 3, 231, 140, 156, 99, 97, 105, 49, 0, 0, 11, 3, 230, 150, 173, 100, 117, 97, 110, 52, 0, 11, 3, 232, 133, 165, 120, 105, 110, 103, 49, 0, 10, 3, 230, 148, 157, 115, 104, 101, 52, 0, 0, 11, 3, 232, 132, 154, 106, 105, 97, 111, 51, 0, 10, 3, 230, 149, 162, 103, 97, 110, 51, 0, 0, 11, 3, 229, 158, 171, 100, 105, 97, 110, 52, 0, 11, 3, 231, 140, 155, 109, 101, 110, 103, 51, 0, 10, 3, 230, 149, 163, 115, 97, 110, 52, 0, 10, 3, 229, 144, 187, 119, 101, 110, 51, 0, 10, 3, 232, 135, 179, 122, 104, 105, 52, 0, 0, 11, 3, 232, 134, 168, 112, 101, 110, 103, 50, 0, 11, 3, 229, 156, 152, 116, 117, 97, 110, 50, 0, 10, 3, 230, 146, 136, 108, 97, 111, 49, 0, 11, 3, 229, 157, 160, 122, 104, 117, 105, 52, 0, 9, 3, 229, 144, 184, 120, 105, 49, 0, 9, 3, 231, 139, 144, 104, 117, 50, 0, 0, 10, 3, 231, 142, 169, 119, 97, 110, 50, 0, 11, 3, 230, 148, 153, 99, 104, 97, 110, 49, 0, 10, 3, 229, 155, 145, 122, 104, 117, 51, 0, 10, 3, 232, 130, 137, 114, 111, 117, 52, 0, 10, 3, 230, 151, 177, 104, 97, 110, 52, 0, 9, 3, 229, 157, 161, 112, 111, 49, 0, 11, 3, 229, 144, 185, 99, 104, 117, 105, 49, 0, 0, 12, 3, 230, 149, 158, 99, 104, 97, 110, 103, 53, 0, 9, 3, 229, 144, 182, 110, 101, 53, 0, 9, 3, 229, 156, 150, 116, 117, 50, 0, 11, 3, 230, 137, 190, 122, 104, 97, 111, 51, 0, 9, 3, 232, 132, 150, 98, 111, 50, 0, 10, 3, 232, 131, 142, 116, 97, 105, 49, 0, 9, 3, 230, 136, 182, 104, 117, 52, 0, 10, 3, 229, 158, 166, 107, 101, 110, 51, 0, 10, 3, 231, 129, 190, 122, 97, 105, 49, 0, 0, 10, 3, 229, 154, 135, 120, 105, 97, 52, 0, 10, 3, 231, 129, 191, 99, 97, 110, 52, 0, 10, 3, 229, 157, 159, 102, 101, 110, 50, 0, 9, 3, 230, 136, 183, 104, 117, 52, 0, 12, 3, 230, 137, 191, 99, 104, 101, 110, 103, 50, 0, 9, 3, 230, 150, 167, 102, 117, 51, 0, 0, 10, 3, 230, 136, 180, 100, 97, 105, 52, 0, 10, 3, 230, 150, 164, 106, 105, 110, 49, 0, 10, 3, 230, 148, 148, 108, 97, 110, 50, 0, 9, 3, 229, 145, 188, 104, 117, 49, 0, 10, 3, 232, 131, 140, 98, 101, 105, 52, 0, 10, 3, 230, 151, 172, 120, 117, 110, 50, 0, 0, 9, 3, 229, 157, 157, 98, 97, 52, 0, 11, 3, 229, 144, 181, 99, 104, 97, 111, 51, 0, 10, 3, 230, 147, 141, 99, 97, 111, 49, 0, 10, 3, 231, 129, 189, 122, 97, 105, 49, 0, 11, 3, 229, 145, 189, 109, 105, 110, 103, 52, 0, 11, 3, 232, 135, 173, 99, 104, 111, 117, 52, 0, 10, 3, 231, 143, 173, 98, 97, 110, 49, 0, 9, 3, 232, 130, 133, 115, 117, 52, 0, 10, 3, 230, 150, 165, 99, 104, 105, 52, 0, 10, 3, 230, 146, 133, 106, 117, 101, 49, 0, 0, 9, 3, 230, 136, 178, 120, 105, 52, 0, 10, 3, 230, 148, 146, 122, 97, 110, 51, 0, 11, 3, 230, 146, 130, 108, 105, 97, 111, 52, 0, 9, 3, 232, 135, 170, 122, 105, 52, 0, 11, 3, 229, 156, 146, 121, 117, 97, 110, 50, 0, 11, 3, 229, 157, 154, 106, 105, 97, 110, 49, 0, 9, 3, 230, 147, 138, 106, 105, 49, 0, 0, 11, 3, 230, 147, 139, 100, 97, 110, 103, 51, 0, 11, 3, 229, 156, 147, 121, 117, 97, 110, 50, 0, 11, 3, 229, 145, 187, 115, 104, 101, 110, 49, 0, 9, 3, 232, 130, 131, 115, 117, 52, 0, 0, 10, 3, 229, 145, 184, 112, 101, 105, 49, 0, 9, 3, 231, 138, 128, 120, 105, 49, 0, 11, 3, 229, 154, 128, 110, 105, 110, 103, 50, 0, 9, 3, 230, 149, 152, 120, 117, 52, 0, 10, 3, 231, 139, 136, 98, 101, 105, 52, 0, 10, 3, 232, 135, 168, 108, 105, 110, 50, 0, 11, 3, 230, 136, 176, 122, 104, 97, 110, 52, 0, 11, 3, 232, 134, 160, 106, 105, 97, 111, 49, 0, 0, 9, 3, 230, 137, 185, 112, 105, 49, 0, 10, 3, 230, 151, 169, 122, 97, 111, 51, 0, 9, 3, 231, 138, 129, 108, 105, 50, 0, 11, 3, 230, 149, 153, 106, 105, 97, 111, 52, 0, 10, 3, 232, 132, 145, 110, 97, 111, 51, 0, 0, 10, 3, 230, 151, 166, 100, 97, 110, 52, 0, 10, 3, 232, 131, 134, 100, 97, 110, 51, 0, 10, 3, 231, 129, 182, 122, 97, 111, 52, 0, 10, 3, 231, 140, 142, 108, 105, 101, 52, 0, 9, 3, 230, 137, 182, 102, 117, 50, 0, 0, 10, 3, 230, 149, 151, 98, 97, 105, 52, 0, 9, 3, 229, 144, 175, 113, 105, 51, 0, 9, 3, 230, 147, 135, 122, 101, 50, 0, 11, 3, 232, 132, 143, 122, 97, 110, 103, 52, 0, 10, 3, 230, 151, 167, 106, 105, 117, 52, 0, 11, 3, 229, 157, 151, 107, 117, 97, 105, 52, 0, 10, 3, 230, 138, 191, 109, 105, 110, 51, 0, 11, 3, 230, 148, 143, 108, 111, 110, 103, 51, 0, 0, 9, 3, 230, 138, 188, 121, 97, 49, 0, 11, 3, 229, 144, 172, 116, 105, 110, 103, 49, 0, 10, 3, 230, 150, 156, 120, 105, 101, 50, 0, 9, 3, 232, 134, 156, 109, 111, 50, 0, 12, 3, 232, 133, 148, 113, 105, 97, 110, 103, 49, 0, 11, 3, 231, 130, 188, 108, 105, 97, 110, 52, 0, 0, 10, 3, 229, 146, 189, 121, 97, 110, 52, 0, 9, 3, 232, 134, 157, 120, 105, 49, 0, 10, 3, 229, 156, 141, 119, 101, 105, 50, 0, 9, 3, 232, 135, 165, 119, 111, 52, 0, 11, 3, 230, 138, 189, 99, 104, 111, 117, 49, 0, 11, 3, 229, 144, 173, 107, 101, 110, 103, 49, 0, 11, 3, 231, 129, 181, 108, 105, 110, 103, 50, 0, 8, 3, 229, 145, 181, 97, 49, 0, 9, 3, 230, 151, 165, 114, 105, 52, 0, 0, 9, 3, 230, 151, 162, 106, 105, 52, 0, 9, 3, 232, 134, 154, 102, 117, 49, 0, 9, 3, 232, 132, 138, 106, 105, 50, 0, 10, 3, 231, 130, 186, 119, 101, 105, 52, 0, 10, 3, 230, 136, 170, 106, 105, 101, 50, 0, 12, 3, 231, 139, 130, 107, 117, 97, 110, 103, 50, 0, 0, 10, 3, 230, 137, 179, 98, 97, 110, 49, 0, 10, 3, 229, 144, 171, 104, 97, 110, 50, 0, 11, 3, 232, 135, 163, 99, 104, 101, 110, 50, 0, 10, 3, 229, 156, 139, 103, 117, 111, 50, 0, 10, 3, 229, 145, 179, 119, 101, 105, 52, 0, 11, 3, 232, 134, 155, 116, 97, 110, 103, 50, 0, 10, 3, 232, 131, 131, 119, 101, 105, 52, 0, 0, 11, 3, 229, 156, 136, 113, 117, 97, 110, 49, 0, 10, 3, 230, 137, 176, 114, 97, 111, 51, 0, 10, 3, 231, 143, 160, 122, 104, 117, 49, 0, 12, 3, 232, 131, 128, 122, 104, 97, 110, 103, 52, 0, 9, 3, 229, 159, 160, 98, 117, 52, 0, 9, 3, 232, 133, 144, 102, 117, 51, 0, 10, 3, 229, 144, 168, 100, 117, 110, 49, 0, 10, 3, 231, 129, 176, 104, 117, 105, 49, 0, 9, 3, 230, 151, 160, 119, 117, 50, 0, 10, 3, 229, 157, 144, 122, 117, 111, 52, 0, 10, 3, 231, 130, 184, 122, 104, 97, 52, 0, 13, 3, 231, 139, 128, 122, 104, 117, 97, 110, 103, 52, 0, 11, 3, 229, 146, 184, 120, 105, 97, 110, 50, 0, 10, 3, 232, 132, 136, 109, 97, 105, 52, 0, 0, 10, 3, 230, 149, 145, 106, 105, 117, 52, 0, 11, 3, 231, 130, 185, 100, 105, 97, 110, 51, 0, 10, 3, 232, 132, 137, 109, 97, 105, 52, 0, 11, 3, 230, 150, 153, 108, 105, 97, 111, 52, 0, 10, 3, 232, 131, 129, 120, 105, 101, 50, 0, 9, 3, 230, 138, 185, 109, 111, 51, 0, 11, 3, 229, 157, 145, 107, 101, 110, 103, 49, 0, 11, 3, 230, 147, 129, 121, 111, 110, 103, 49, 0, 10, 3, 229, 144, 169, 102, 101, 110, 49, 0, 0, 10, 3, 230, 147, 190, 114, 97, 111, 51, 0, 9, 3, 230, 157, 142, 108, 105, 51, 0, 13, 3, 231, 138, 182, 122, 104, 117, 97, 110, 103, 52, 0, 11, 3, 232, 142, 150, 106, 105, 110, 103, 49, 0, 9, 3, 229, 155, 190, 116, 117, 50, 0, 0, 11, 3, 229, 154, 183, 114, 97, 110, 103, 51, 0, 10, 3, 229, 164, 135, 98, 101, 105, 52, 0, 10, 3, 230, 158, 151, 108, 105, 110, 50, 0, 11, 3, 232, 129, 175, 108, 105, 97, 110, 50, 0, 10, 3, 231, 149, 143, 119, 101, 105, 52, 0, 10, 3, 229, 165, 143, 122, 111, 117, 52, 0, 11, 3, 231, 150, 151, 108, 105, 97, 111, 50, 0, 0, 10, 3, 232, 143, 156, 99, 97, 105, 52, 0, 11, 3, 231, 139, 188, 108, 97, 110, 103, 50, 0, 10, 3, 232, 140, 132, 106, 105, 97, 49, 0, 10, 3, 230, 159, 156, 103, 117, 105, 52, 0, 10, 3, 231, 149, 140, 106, 105, 101, 52, 0, 10, 3, 229, 154, 180, 121, 97, 110, 50, 0, 10, 3, 229, 164, 132, 99, 104, 117, 52, 0, 12, 3, 229, 167, 156, 106, 105, 97, 110, 103, 49, 0, 0, 11, 3, 233, 135, 157, 122, 104, 101, 110, 49, 0, 10, 3, 231, 139, 189, 98, 101, 105, 52, 0, 10, 3, 229, 155, 189, 103, 117, 111, 50, 0, 11, 3, 230, 146, 181, 110, 105, 97, 110, 51, 0, 10, 3, 232, 140, 133, 109, 97, 111, 50, 0, 11, 3, 232, 131, 189, 110, 101, 110, 103, 50, 0, 11, 3, 230, 158, 149, 122, 104, 101, 110, 51, 0, 10, 3, 233, 133, 141, 112, 101, 105, 52, 0, 0, 9, 3, 229, 155, 186, 103, 117, 52, 0, 9, 3, 232, 130, 178, 121, 117, 52, 0, 11, 3, 232, 129, 170, 99, 111, 110, 103, 49, 0, 9, 3, 230, 146, 178, 112, 117, 49, 0, 10, 3, 230, 147, 186, 98, 97, 105, 51, 0, 10, 3, 229, 153, 170, 122, 97, 111, 52, 0, 10, 3, 232, 140, 130, 109, 97, 111, 52, 0, 11, 3, 233, 134, 146, 120, 105, 110, 103, 51, 0, 0, 10, 3, 230, 156, 131, 104, 117, 105, 52, 0, 10, 3, 232, 140, 131, 102, 97, 110, 52, 0, 11, 3, 231, 151, 155, 116, 111, 110, 103, 52, 0, 10, 3, 229, 165, 139, 102, 101, 110, 52, 0, 0, 11, 3, 233, 135, 152, 100, 105, 110, 103, 49, 0, 9, 3, 230, 158, 144, 120, 105, 49, 0, 9, 3, 231, 139, 184, 108, 105, 53, 0, 12, 3, 232, 131, 184, 120, 105, 111, 110, 103, 49, 0, 10, 3, 230, 156, 128, 122, 117, 105, 52, 0, 9, 3, 229, 153, 168, 113, 105, 52, 0, 10, 3, 229, 165, 136, 110, 97, 105, 52, 0, 0, 9, 3, 231, 137, 169, 119, 117, 52, 0, 10, 3, 232, 141, 137, 99, 97, 111, 51, 0, 11, 3, 230, 157, 137, 115, 104, 97, 110, 49, 0, 11, 3, 232, 140, 129, 122, 104, 117, 111, 50, 0, 9, 3, 231, 150, 145, 121, 105, 50, 0, 10, 3, 231, 139, 185, 120, 105, 97, 50, 0, 9, 3, 230, 145, 169, 109, 111, 50, 0, 11, 3, 229, 165, 137, 102, 101, 110, 103, 52, 0, 0, 11, 3, 230, 148, 190, 102, 97, 110, 103, 52, 0, 10, 3, 230, 157, 134, 103, 97, 110, 49, 0, 10, 3, 230, 144, 158, 103, 97, 111, 51, 0, 9, 3, 232, 132, 190, 112, 105, 50, 0, 10, 3, 231, 140, 190, 104, 117, 97, 50, 0, 9, 3, 229, 156, 190, 106, 105, 49, 0, 11, 3, 232, 131, 182, 106, 105, 97, 111, 49, 0, 10, 3, 231, 137, 166, 109, 97, 111, 50, 0, 0, 11, 3, 231, 140, 191, 121, 117, 97, 110, 50, 0, 9, 3, 229, 165, 135, 113, 105, 50, 0, 10, 3, 232, 130, 175, 107, 101, 110, 51, 0, 10, 3, 231, 150, 143, 115, 104, 117, 49, 0, 9, 3, 231, 137, 167, 109, 117, 52, 0, 12, 3, 230, 148, 191, 122, 104, 101, 110, 103, 52, 0, 10, 3, 231, 138, 175, 102, 97, 110, 52, 0, 10, 3, 230, 145, 167, 99, 117, 105, 49, 0, 0, 11, 3, 231, 138, 172, 113, 117, 97, 110, 51, 0, 10, 3, 230, 144, 156, 115, 111, 117, 49, 0, 10, 3, 230, 147, 180, 107, 117, 111, 52, 0, 10, 3, 229, 167, 148, 119, 101, 105, 51, 0, 10, 3, 229, 155, 180, 119, 101, 105, 50, 0, 10, 3, 230, 159, 148, 114, 111, 117, 50, 0, 0, 12, 3, 231, 149, 133, 99, 104, 97, 110, 103, 52, 0, 9, 3, 230, 146, 173, 98, 111, 49, 0, 10, 3, 231, 151, 149, 104, 101, 110, 50, 0, 0, 10, 3, 231, 150, 138, 100, 105, 101, 50, 0, 10, 3, 230, 147, 178, 122, 104, 105, 52, 0, 10, 3, 231, 137, 162, 108, 97, 111, 50, 0, 8, 3, 229, 153, 162, 111, 49, 0, 9, 3, 230, 157, 130, 122, 97, 50, 0, 11, 3, 232, 130, 170, 102, 97, 110, 103, 50, 0, 11, 3, 231, 151, 146, 121, 97, 110, 103, 51, 0, 12, 3, 229, 156, 186, 99, 104, 97, 110, 103, 51, 0, 13, 3, 232, 142, 138, 122, 104, 117, 97, 110, 103, 49, 0, 0, 10, 3, 231, 136, 155, 108, 97, 110, 52, 0, 9, 3, 229, 152, 155, 109, 97, 53, 0, 10, 3, 230, 159, 147, 114, 97, 110, 51, 0, 9, 3, 230, 146, 171, 102, 117, 51, 0, 11, 3, 230, 148, 187, 103, 111, 110, 103, 49, 0, 9, 3, 232, 131, 179, 103, 101, 49, 0, 11, 3, 229, 167, 147, 120, 105, 110, 103, 52, 0, 11, 3, 230, 157, 131, 113, 117, 97, 110, 50, 0, 9, 3, 233, 134, 139, 99, 117, 52, 0, 0, 10, 3, 230, 159, 144, 109, 111, 117, 51, 0, 9, 3, 229, 166, 136, 109, 97, 49, 0, 11, 3, 230, 147, 176, 110, 105, 110, 103, 50, 0, 10, 3, 229, 167, 144, 106, 105, 101, 53, 0, 11, 3, 229, 154, 168, 108, 111, 110, 103, 50, 0, 10, 3, 230, 157, 128, 115, 104, 97, 49, 0, 9, 3, 229, 152, 152, 120, 117, 49, 0, 11, 3, 232, 132, 184, 108, 105, 97, 110, 51, 0, 10, 3, 229, 155, 176, 107, 117, 110, 52, 0, 0, 9, 3, 231, 139, 177, 121, 117, 52, 0, 11, 3, 229, 155, 177, 99, 111, 110, 103, 49, 0, 11, 3, 232, 130, 169, 106, 105, 97, 110, 49, 0, 10, 3, 230, 148, 185, 103, 97, 105, 51, 0, 9, 3, 229, 167, 145, 103, 117, 49, 0, 11, 3, 230, 146, 169, 108, 105, 97, 111, 49, 0, 12, 3, 232, 132, 185, 122, 104, 97, 110, 103, 52, 0, 10, 3, 233, 135, 145, 106, 105, 110, 49, 0, 11, 3, 230, 158, 137, 119, 97, 110, 103, 53, 0, 10, 3, 233, 134, 137, 122, 117, 105, 52, 0, 9, 3, 230, 147, 177, 103, 101, 49, 0, 9, 3, 231, 137, 161, 109, 117, 51, 0, 0, 10, 3, 231, 140, 182, 121, 111, 117, 50, 0, 12, 3, 231, 150, 134, 106, 105, 97, 110, 103, 49, 0, 11, 3, 232, 133, 190, 116, 101, 110, 103, 50, 0, 11, 3, 230, 148, 182, 115, 104, 111, 117, 49, 0, 9, 3, 233, 135, 142, 121, 101, 51, 0, 10, 3, 232, 129, 158, 119, 101, 110, 50, 0, 10, 3, 230, 144, 150, 121, 97, 111, 50, 0, 10, 3, 231, 139, 174, 115, 104, 105, 49, 0, 0, 9, 3, 231, 138, 167, 120, 105, 49, 0, 10, 3, 232, 133, 191, 116, 117, 105, 51, 0, 12, 3, 229, 152, 151, 99, 104, 97, 110, 103, 50, 0, 10, 3, 230, 145, 159, 108, 111, 117, 51, 0, 12, 3, 233, 135, 143, 108, 105, 97, 110, 103, 52, 0, 10, 3, 230, 159, 143, 98, 97, 105, 51, 0, 10, 3, 232, 128, 151, 104, 97, 111, 52, 0, 9, 3, 229, 166, 135, 102, 117, 52, 0, 10, 3, 230, 144, 151, 100, 97, 111, 51, 0, 0, 9, 3, 232, 130, 164, 102, 117, 49, 0, 10, 3, 232, 143, 140, 106, 117, 110, 49, 0, 10, 3, 230, 158, 132, 103, 111, 117, 52, 0, 9, 3, 231, 139, 172, 100, 117, 50, 0, 10, 3, 231, 140, 180, 104, 111, 117, 50, 0, 10, 3, 230, 146, 164, 99, 104, 101, 52, 0, 10, 3, 230, 144, 148, 115, 97, 111, 49, 0, 9, 3, 233, 135, 140, 108, 105, 51, 0, 11, 3, 229, 166, 132, 119, 97, 110, 103, 52, 0, 9, 3, 230, 147, 172, 110, 105, 51, 0, 0, 12, 3, 233, 135, 141, 122, 104, 111, 110, 103, 52, 0, 10, 3, 231, 139, 173, 120, 105, 97, 50, 0, 11, 3, 229, 155, 173, 121, 117, 97, 110, 50, 0, 11, 3, 232, 128, 149, 103, 101, 110, 103, 49, 0, 9, 3, 230, 146, 165, 98, 111, 49, 0, 10, 3, 232, 130, 165, 102, 101, 105, 50, 0, 0, 11, 3, 229, 155, 170, 99, 111, 110, 103, 49, 0, 9, 3, 229, 167, 138, 122, 105, 51, 0, 10, 3, 232, 130, 162, 122, 104, 105, 49, 0, 10, 3, 233, 135, 138, 115, 104, 105, 52, 0, 9, 3, 232, 129, 154, 106, 117, 52, 0, 9, 3, 229, 166, 130, 114, 117, 50, 0, 9, 3, 232, 143, 138, 106, 117, 50, 0, 0, 11, 3, 231, 141, 187, 120, 105, 97, 110, 52, 0, 10, 3, 231, 137, 155, 110, 105, 117, 50, 0, 10, 3, 233, 135, 139, 115, 104, 105, 52, 0, 10, 3, 229, 167, 139, 115, 104, 105, 51, 0, 10, 3, 230, 144, 147, 99, 117, 111, 49, 0, 0, 11, 3, 230, 145, 152, 122, 104, 97, 105, 49, 0, 12, 3, 232, 133, 184, 99, 104, 97, 110, 103, 50, 0, 9, 3, 231, 136, 144, 108, 117, 50, 0, 10, 3, 230, 149, 184, 115, 104, 117, 52, 0, 9, 3, 229, 156, 176, 100, 101, 53, 0, 10, 3, 232, 128, 144, 110, 97, 105, 52, 0, 12, 3, 232, 130, 160, 99, 104, 97, 110, 103, 50, 0, 11, 3, 231, 141, 184, 115, 104, 111, 117, 52, 0, 0, 9, 3, 231, 137, 153, 121, 97, 50, 0, 9, 3, 232, 133, 185, 102, 117, 52, 0, 9, 3, 232, 130, 161, 103, 117, 51, 0, 10, 3, 232, 132, 177, 116, 117, 111, 49, 0, 9, 3, 230, 158, 129, 106, 105, 50, 0, 0, 12, 3, 232, 129, 150, 115, 104, 101, 110, 103, 52, 0, 9, 3, 229, 167, 134, 109, 117, 51, 0, 11, 3, 231, 140, 174, 120, 105, 97, 110, 52, 0, 13, 3, 230, 146, 158, 122, 104, 117, 97, 110, 103, 52, 0, 9, 3, 230, 147, 166, 99, 97, 49, 0, 0, 11, 3, 232, 131, 167, 108, 111, 110, 103, 50, 0, 9, 3, 232, 143, 135, 103, 117, 53, 0, 12, 3, 231, 151, 135, 122, 104, 101, 110, 103, 52, 0, 10, 3, 230, 148, 175, 122, 104, 105, 49, 0, 9, 3, 230, 144, 143, 98, 111, 50, 0, 9, 3, 230, 149, 183, 102, 117, 49, 0, 9, 3, 232, 132, 175, 112, 117, 50, 0, 10, 3, 233, 135, 135, 99, 97, 105, 51, 0, 0, 9, 3, 232, 128, 140, 101, 114, 50, 0, 12, 3, 230, 149, 180, 122, 104, 101, 110, 103, 51, 0, 12, 3, 230, 145, 148, 115, 104, 117, 97, 105, 49, 0, 11, 3, 232, 129, 148, 108, 105, 97, 110, 50, 0, 11, 3, 230, 159, 132, 98, 105, 110, 103, 51, 0, 10, 3, 231, 140, 172, 119, 101, 105, 53, 0, 0, 10, 3, 229, 152, 141, 108, 111, 117, 53, 0, 11, 3, 231, 136, 141, 115, 104, 117, 111, 52, 0, 10, 3, 232, 134, 189, 100, 97, 110, 51, 0, 9, 3, 230, 149, 181, 100, 105, 50, 0, 10, 3, 230, 150, 189, 115, 104, 105, 49, 0, 10, 3, 232, 130, 157, 103, 97, 110, 49, 0, 10, 3, 230, 144, 141, 115, 117, 110, 51, 0, 10, 3, 231, 141, 181, 108, 105, 101, 52, 0, 11, 3, 232, 128, 141, 115, 104, 117, 97, 51, 0, 11, 3, 231, 151, 133, 98, 105, 110, 103, 52, 0, 0, 10, 3, 231, 140, 170, 122, 104, 117, 49, 0, 10, 3, 231, 141, 178, 104, 117, 111, 52, 0, 11, 3, 229, 155, 162, 116, 117, 97, 110, 50, 0, 9, 3, 232, 130, 154, 100, 117, 52, 0, 11, 3, 230, 148, 170, 106, 105, 97, 111, 51, 0, 11, 3, 230, 149, 178, 113, 105, 97, 111, 49, 0, 0, 9, 3, 231, 142, 187, 98, 111, 49, 0, 10, 3, 231, 140, 171, 109, 97, 111, 49, 0, 11, 3, 232, 133, 179, 106, 105, 97, 111, 51, 0, 10, 3, 232, 132, 171, 116, 117, 111, 49, 0, 9, 3, 229, 153, 147, 120, 117, 49, 0, 10, 3, 231, 138, 155, 109, 97, 111, 50, 0, 0, 10, 3, 229, 156, 168, 122, 97, 105, 52, 0, 9, 3, 230, 147, 160, 106, 105, 51, 0, 10, 3, 232, 133, 176, 121, 97, 111, 49, 0, 10, 3, 229, 152, 136, 99, 97, 111, 50, 0, 10, 3, 230, 149, 176, 115, 104, 117, 52, 0, 12, 3, 233, 135, 128, 110, 105, 97, 110, 103, 52, 0, 10, 3, 231, 139, 160, 104, 101, 110, 51, 0, 10, 3, 229, 155, 160, 121, 105, 110, 49, 0, 0, 11, 3, 231, 139, 161, 106, 105, 97, 111, 51, 0, 9, 3, 232, 131, 161, 104, 117, 50, 0, 11, 3, 230, 150, 185, 102, 97, 110, 103, 49, 0, 11, 3, 231, 140, 169, 120, 105, 110, 103, 49, 0, 0, 10, 3, 229, 165, 174, 102, 101, 110, 52, 0, 10, 3, 230, 152, 134, 107, 117, 110, 49, 0, 11, 3, 229, 163, 158, 104, 117, 97, 105, 52, 0, 9, 3, 232, 136, 134, 121, 117, 50, 0, 11, 3, 230, 156, 166, 109, 101, 110, 103, 50, 0, 11, 3, 230, 154, 150, 110, 117, 97, 110, 51, 0, 9, 3, 231, 144, 134, 108, 105, 51, 0, 10, 3, 233, 129, 142, 103, 117, 111, 52, 0, 10, 3, 229, 160, 134, 100, 117, 105, 49, 0, 10, 3, 230, 158, 182, 106, 105, 97, 52, 0, 0, 10, 3, 232, 142, 183, 104, 117, 111, 52, 0, 9, 3, 229, 164, 167, 100, 97, 52, 0, 9, 3, 230, 154, 151, 97, 110, 52, 0, 9, 3, 229, 167, 191, 122, 105, 49, 0, 11, 3, 230, 156, 167, 108, 111, 110, 103, 50, 0, 10, 3, 232, 141, 175, 121, 97, 111, 52, 0, 11, 3, 229, 163, 159, 108, 111, 110, 103, 51, 0, 9, 3, 232, 136, 135, 121, 117, 51, 0, 10, 3, 230, 157, 175, 98, 101, 105, 49, 0, 11, 3, 232, 140, 167, 106, 105, 97, 110, 51, 0, 0, 9, 3, 229, 161, 140, 116, 97, 49, 0, 11, 3, 233, 133, 172, 99, 104, 111, 117, 53, 0, 10, 3, 231, 147, 156, 103, 117, 97, 49, 0, 12, 3, 230, 153, 140, 115, 104, 97, 110, 103, 51, 0, 0, 11, 3, 229, 160, 133, 106, 105, 97, 110, 49, 0, 11, 3, 233, 129, 141, 98, 105, 97, 110, 52, 0, 10, 3, 232, 136, 133, 106, 105, 117, 52, 0, 0, 11, 3, 229, 161, 138, 107, 117, 97, 105, 52, 0, 11, 3, 229, 164, 162, 109, 101, 110, 103, 52, 0, 11, 3, 231, 148, 162, 99, 104, 97, 110, 51, 0, 10, 3, 231, 149, 170, 102, 97, 110, 49, 0, 10, 3, 230, 152, 130, 97, 110, 103, 50, 0, 10, 3, 229, 165, 170, 100, 117, 111, 50, 0, 10, 3, 233, 128, 130, 115, 104, 105, 52, 0, 9, 3, 231, 150, 178, 112, 105, 50, 0, 11, 3, 232, 138, 146, 109, 97, 110, 103, 50, 0, 9, 3, 231, 151, 186, 98, 105, 52, 0, 11, 3, 229, 160, 130, 116, 97, 110, 103, 50, 0, 0, 10, 3, 233, 128, 131, 116, 97, 111, 50, 0, 10, 3, 231, 144, 131, 113, 105, 117, 50, 0, 10, 3, 229, 167, 187, 121, 105, 110, 49, 0, 10, 3, 231, 149, 171, 104, 117, 97, 52, 0, 9, 3, 229, 162, 147, 109, 117, 52, 0, 10, 3, 233, 129, 139, 121, 117, 110, 52, 0, 0, 10, 3, 229, 164, 160, 103, 111, 117, 52, 0, 10, 3, 232, 136, 128, 121, 97, 111, 51, 0, 10, 3, 233, 128, 128, 116, 117, 105, 52, 0, 11, 3, 230, 157, 168, 121, 97, 110, 103, 50, 0, 10, 3, 229, 163, 152, 108, 101, 105, 51, 0, 0, 11, 3, 233, 128, 129, 115, 111, 110, 103, 52, 0, 9, 3, 231, 151, 185, 98, 105, 52, 0, 10, 3, 230, 154, 145, 115, 104, 117, 51, 0, 0, 9, 3, 231, 136, 190, 101, 114, 51, 0, 0, 9, 3, 230, 156, 159, 113, 105, 49, 0, 11, 3, 232, 137, 135, 116, 105, 110, 103, 51, 0, 10, 3, 233, 130, 143, 108, 117, 111, 50, 0, 11, 3, 231, 150, 175, 102, 101, 110, 103, 49, 0, 12, 3, 231, 148, 159, 115, 104, 101, 110, 103, 49, 0, 9, 3, 233, 129, 135, 121, 117, 52, 0, 10, 3, 229, 164, 159, 103, 111, 117, 52, 0, 11, 3, 232, 139, 151, 109, 105, 97, 111, 50, 0, 10, 3, 229, 152, 191, 104, 101, 105, 49, 0, 9, 3, 230, 158, 175, 107, 117, 49, 0, 0, 9, 3, 229, 164, 156, 121, 101, 52, 0, 11, 3, 231, 148, 156, 116, 105, 97, 110, 50, 0, 12, 3, 233, 134, 172, 106, 105, 97, 110, 103, 52, 0, 11, 3, 230, 159, 180, 99, 104, 97, 105, 50, 0, 0, 10, 3, 231, 149, 165, 108, 118, 101, 52, 0, 13, 3, 231, 136, 189, 115, 104, 117, 97, 110, 103, 51, 0, 11, 3, 230, 156, 157, 99, 104, 97, 111, 50, 0, 10, 3, 230, 157, 165, 108, 97, 105, 50, 0, 10, 3, 229, 163, 149, 104, 97, 111, 50, 0, 10, 3, 232, 128, 189, 100, 97, 110, 49, 0, 0, 10, 3, 230, 144, 186, 120, 105, 101, 50, 0, 10, 3, 230, 153, 130, 115, 104, 105, 50, 0, 9, 3, 231, 136, 186, 121, 101, 53, 0, 12, 3, 230, 158, 170, 113, 105, 97, 110, 103, 49, 0, 10, 3, 229, 164, 154, 100, 117, 111, 49, 0, 11, 3, 233, 130, 138, 98, 105, 97, 110, 49, 0, 11, 3, 231, 148, 154, 115, 104, 101, 110, 50, 0, 11, 3, 229, 162, 138, 100, 105, 97, 110, 52, 0, 9, 3, 231, 149, 162, 98, 105, 52, 0, 0, 9, 3, 229, 152, 187, 120, 105, 49, 0, 11, 3, 230, 156, 155, 119, 97, 110, 103, 52, 0, 9, 3, 232, 142, 171, 109, 111, 52, 0, 10, 3, 230, 159, 179, 108, 105, 117, 51, 0, 11, 3, 232, 141, 163, 114, 111, 110, 103, 50, 0, 9, 3, 229, 163, 147, 121, 97, 49, 0, 12, 3, 230, 153, 131, 104, 117, 97, 110, 103, 53, 0, 9, 3, 231, 150, 171, 121, 105, 52, 0, 9, 3, 233, 134, 171, 121, 105, 49, 0, 10, 3, 232, 128, 187, 99, 104, 105, 51, 0, 0, 11, 3, 232, 128, 184, 115, 111, 110, 103, 51, 0, 11, 3, 229, 166, 168, 102, 97, 110, 103, 50, 0, 10, 3, 231, 148, 152, 103, 97, 110, 49, 0, 10, 3, 230, 154, 136, 121, 117, 110, 49, 0, 10, 3, 231, 151, 176, 116, 97, 110, 50, 0, 11, 3, 229, 165, 160, 100, 105, 97, 110, 52, 0, 9, 3, 231, 136, 184, 98, 97, 52, 0, 0, 10, 3, 230, 159, 177, 122, 104, 117, 52, 0, 9, 3, 233, 132, 153, 98, 105, 51, 0, 10, 3, 231, 136, 185, 100, 105, 101, 49, 0, 12, 3, 233, 131, 145, 122, 104, 101, 110, 103, 52, 0, 11, 3, 232, 141, 161, 100, 97, 110, 103, 52, 0, 11, 3, 230, 157, 161, 116, 105, 97, 111, 50, 0, 0, 12, 3, 230, 144, 182, 113, 105, 97, 110, 103, 51, 0, 9, 3, 231, 136, 182, 102, 117, 52, 0, 9, 3, 229, 152, 182, 115, 105, 49, 0, 10, 3, 229, 164, 150, 119, 97, 105, 52, 0, 0, 9, 3, 232, 139, 143, 115, 117, 49, 0, 10, 3, 230, 157, 159, 115, 104, 117, 52, 0, 9, 3, 231, 136, 183, 121, 101, 53, 0, 11, 3, 230, 156, 151, 108, 97, 110, 103, 51, 0, 9, 3, 232, 128, 183, 100, 97, 49, 0, 11, 3, 231, 147, 143, 108, 111, 110, 103, 50, 0, 10, 3, 232, 143, 175, 104, 117, 97, 50, 0, 0, 10, 3, 231, 149, 156, 99, 104, 117, 52, 0, 10, 3, 233, 130, 132, 104, 97, 105, 50, 0, 10, 3, 229, 152, 180, 122, 117, 105, 51, 0, 9, 3, 230, 157, 156, 100, 117, 52, 0, 11, 3, 230, 154, 132, 120, 117, 97, 110, 49, 0, 0, 11, 3, 232, 129, 189, 116, 105, 110, 103, 49, 0, 9, 3, 229, 164, 149, 120, 105, 49, 0, 9, 3, 231, 149, 157, 109, 117, 51, 0, 11, 3, 232, 139, 141, 99, 97, 110, 103, 49, 0, 10, 3, 229, 166, 165, 116, 117, 111, 51, 0, 11, 3, 231, 137, 189, 113, 105, 97, 110, 49, 0, 0, 11, 3, 229, 152, 178, 99, 104, 97, 111, 50, 0, 10, 3, 230, 158, 162, 115, 104, 117, 49, 0, 11, 3, 233, 131, 138, 106, 105, 97, 111, 49, 0, 9, 3, 231, 137, 186, 120, 105, 49, 0, 10, 3, 232, 138, 130, 106, 105, 101, 50, 0, 10, 3, 230, 154, 130, 122, 97, 110, 52, 0, 0, 9, 3, 232, 128, 179, 101, 114, 51, 0, 10, 3, 230, 158, 163, 122, 97, 111, 51, 0, 11, 3, 229, 162, 131, 106, 105, 110, 103, 52, 0, 9, 3, 231, 146, 131, 108, 105, 50, 0, 0, 9, 3, 230, 145, 184, 109, 111, 49, 0, 9, 3, 229, 167, 168, 121, 105, 50, 0, 10, 3, 229, 153, 184, 100, 117, 110, 49, 0, 10, 3, 233, 130, 128, 121, 97, 111, 49, 0, 0, 9, 3, 231, 137, 185, 116, 101, 52, 0, 9, 3, 232, 143, 169, 112, 117, 50, 0, 10, 3, 233, 130, 129, 109, 97, 105, 52, 0, 10, 3, 231, 149, 153, 108, 105, 117, 50, 0, 10, 3, 229, 152, 177, 122, 104, 117, 51, 0, 11, 3, 230, 155, 137, 120, 105, 97, 111, 51, 0, 9, 3, 231, 136, 177, 97, 105, 52, 0, 0, 11, 3, 232, 140, 142, 106, 105, 110, 103, 49, 0, 12, 3, 229, 165, 150, 106, 105, 97, 110, 103, 51, 0, 0, 10, 3, 229, 165, 151, 116, 97, 111, 52, 0, 11, 3, 230, 146, 191, 106, 105, 97, 110, 51, 0, 12, 3, 232, 130, 191, 122, 104, 111, 110, 103, 51, 0, 10, 3, 232, 139, 135, 119, 101, 105, 51, 0, 11, 3, 229, 152, 175, 120, 105, 97, 111, 52, 0, 10, 3, 229, 164, 143, 120, 105, 97, 52, 0, 10, 3, 232, 129, 183, 122, 104, 105, 50, 0, 0, 9, 3, 232, 141, 148, 108, 105, 52, 0, 10, 3, 229, 154, 188, 106, 117, 101, 50, 0, 10, 3, 230, 144, 172, 98, 97, 110, 49, 0, 10, 3, 230, 146, 188, 104, 97, 110, 52, 0, 9, 3, 231, 136, 172, 112, 97, 50, 0, 10, 3, 230, 158, 156, 103, 117, 111, 51, 0, 10, 3, 229, 153, 180, 112, 101, 110, 49, 0, 10, 3, 229, 165, 148, 98, 101, 110, 49, 0, 10, 3, 231, 149, 148, 112, 97, 110, 52, 0, 0, 12, 3, 231, 136, 173, 122, 104, 101, 110, 103, 49, 0, 9, 3, 230, 156, 141, 102, 117, 50, 0, 11, 3, 231, 137, 181, 113, 105, 97, 110, 49, 0, 10, 3, 230, 159, 165, 99, 104, 97, 50, 0, 9, 3, 230, 144, 173, 100, 97, 49, 0, 10, 3, 230, 158, 157, 122, 104, 105, 49, 0, 9, 3, 229, 164, 141, 102, 117, 52, 0, 0, 12, 3, 232, 141, 146, 104, 117, 97, 110, 103, 49, 0, 12, 3, 231, 137, 178, 115, 104, 101, 110, 103, 49, 0, 11, 3, 230, 144, 170, 116, 97, 110, 103, 50, 0, 10, 3, 232, 130, 186, 102, 101, 105, 52, 0, 10, 3, 230, 158, 154, 109, 101, 105, 50, 0, 10, 3, 233, 133, 146, 106, 105, 117, 51, 0, 12, 3, 232, 129, 178, 115, 104, 101, 110, 103, 49, 0, 11, 3, 231, 136, 170, 122, 104, 97, 111, 51, 0, 0, 11, 3, 233, 135, 163, 100, 105, 97, 111, 52, 0, 11, 3, 230, 156, 139, 112, 101, 110, 103, 50, 0, 11, 3, 232, 129, 179, 115, 111, 110, 103, 51, 0, 0, 10, 3, 230, 156, 136, 121, 117, 101, 52, 0, 10, 3, 230, 157, 144, 99, 97, 105, 50, 0, 11, 3, 232, 141, 144, 106, 105, 97, 110, 52, 0, 11, 3, 232, 129, 176, 99, 111, 110, 103, 49, 0, 0, 12, 3, 233, 132, 137, 120, 105, 97, 110, 103, 49, 0, 10, 3, 229, 152, 169, 104, 117, 97, 49, 0, 9, 3, 231, 150, 153, 103, 101, 49, 0, 11, 3, 229, 166, 153, 109, 105, 97, 111, 52, 0, 9, 3, 233, 131, 129, 121, 117, 52, 0, 10, 3, 230, 156, 137, 121, 111, 117, 51, 0, 10, 3, 230, 157, 145, 99, 117, 110, 49, 0, 10, 3, 231, 138, 185, 121, 111, 117, 50, 0, 9, 3, 229, 163, 129, 98, 105, 52, 0, 0, 10, 3, 230, 152, 167, 109, 101, 105, 52, 0, 9, 3, 230, 155, 191, 116, 105, 52, 0, 11, 3, 229, 174, 151, 122, 111, 110, 103, 49, 0, 10, 3, 229, 175, 159, 99, 104, 97, 50, 0, 11, 3, 230, 153, 175, 106, 105, 110, 103, 51, 0, 11, 3, 233, 143, 159, 99, 104, 97, 110, 51, 0, 12, 3, 232, 137, 175, 108, 105, 97, 110, 103, 50, 0, 0, 9, 3, 229, 175, 158, 109, 111, 52, 0, 9, 3, 230, 153, 174, 112, 117, 51, 0, 10, 3, 233, 129, 174, 122, 104, 101, 49, 0, 10, 3, 233, 142, 150, 115, 117, 111, 51, 0, 11, 3, 230, 155, 190, 99, 101, 110, 103, 50, 0, 0, 9, 3, 232, 151, 157, 121, 105, 52, 0, 10, 3, 233, 129, 173, 122, 97, 111, 49, 0, 11, 3, 230, 166, 149, 114, 111, 110, 103, 50, 0, 9, 3, 230, 164, 133, 121, 105, 51, 0, 9, 3, 233, 141, 141, 100, 117, 52, 0, 11, 3, 230, 152, 165, 99, 104, 117, 110, 49, 0, 10, 3, 233, 131, 189, 100, 111, 117, 49, 0, 11, 3, 229, 163, 189, 115, 104, 111, 117, 52, 0, 0, 9, 3, 233, 140, 132, 108, 117, 52, 0, 9, 3, 229, 160, 164, 100, 105, 49, 0, 10, 3, 230, 154, 180, 98, 97, 111, 52, 0, 0, 10, 3, 233, 141, 139, 103, 117, 111, 49, 0, 11, 3, 229, 161, 171, 116, 105, 97, 110, 50, 0, 10, 3, 230, 167, 155, 107, 97, 110, 51, 0, 11, 3, 233, 128, 163, 108, 105, 97, 110, 50, 0, 10, 3, 231, 159, 155, 109, 97, 111, 50, 0, 10, 3, 229, 162, 179, 102, 101, 110, 50, 0, 0, 10, 3, 231, 158, 146, 109, 97, 110, 50, 0, 11, 3, 230, 165, 138, 121, 97, 110, 103, 50, 0, 9, 3, 229, 163, 186, 104, 117, 50, 0, 11, 3, 233, 128, 162, 102, 101, 110, 103, 50, 0, 10, 3, 231, 144, 162, 122, 117, 111, 50, 0, 0, 12, 3, 231, 156, 129, 115, 104, 101, 110, 103, 51, 0, 10, 3, 232, 138, 177, 104, 117, 97, 49, 0, 10, 3, 229, 160, 161, 98, 97, 111, 51, 0, 11, 3, 231, 145, 169, 121, 105, 110, 103, 50, 0, 11, 3, 232, 149, 137, 106, 105, 97, 111, 49, 0, 10, 3, 233, 129, 169, 115, 104, 105, 52, 0, 11, 3, 232, 139, 185, 112, 105, 110, 103, 50, 0, 0, 11, 3, 231, 146, 176, 104, 117, 97, 110, 50, 0, 11, 3, 230, 152, 160, 121, 105, 110, 103, 52, 0, 10, 3, 230, 155, 184, 115, 104, 117, 49, 0, 11, 3, 230, 153, 168, 99, 104, 101, 110, 53, 0, 10, 3, 233, 128, 160, 122, 97, 111, 52, 0, 0, 10, 3, 231, 159, 151, 99, 104, 117, 52, 0, 9, 3, 233, 128, 159, 115, 117, 52, 0, 9, 3, 231, 147, 183, 99, 105, 50, 0, 11, 3, 232, 136, 159, 122, 104, 111, 117, 49, 0, 11, 3, 229, 174, 143, 104, 111, 110, 103, 50, 0, 11, 3, 230, 152, 159, 120, 105, 110, 103, 49, 0, 10, 3, 232, 138, 175, 120, 105, 110, 49, 0, 0, 10, 3, 229, 164, 190, 106, 105, 97, 49, 0, 10, 3, 231, 158, 142, 120, 105, 97, 49, 0, 11, 3, 232, 137, 166, 106, 105, 97, 110, 52, 0, 9, 3, 232, 136, 158, 119, 117, 51, 0, 9, 3, 229, 163, 182, 104, 117, 50, 0, 10, 3, 233, 130, 174, 121, 111, 117, 50, 0, 11, 3, 231, 147, 182, 112, 105, 110, 103, 50, 0, 0, 10, 3, 233, 131, 181, 121, 111, 117, 50, 0, 10, 3, 230, 156, 189, 120, 105, 117, 51, 0, 10, 3, 233, 129, 165, 121, 97, 111, 50, 0, 10, 3, 233, 128, 157, 115, 104, 105, 52, 0, 0, 9, 3, 231, 158, 140, 107, 101, 49, 0, 10, 3, 229, 174, 140, 119, 97, 110, 50, 0, 11, 3, 230, 155, 180, 103, 101, 110, 103, 52, 0, 0, 10, 3, 231, 145, 163, 115, 117, 111, 51, 0, 11, 3, 233, 129, 163, 113, 105, 97, 110, 51, 0, 9, 3, 229, 175, 147, 121, 117, 52, 0, 9, 3, 229, 163, 179, 107, 101, 50, 0, 10, 3, 231, 148, 187, 104, 117, 97, 52, 0, 12, 3, 233, 128, 155, 103, 117, 97, 110, 103, 52, 0, 10, 3, 230, 154, 171, 122, 97, 110, 52, 0, 0, 11, 3, 233, 128, 154, 116, 111, 110, 103, 49, 0, 10, 3, 229, 175, 146, 104, 97, 110, 50, 0, 10, 3, 229, 164, 186, 100, 117, 111, 50, 0, 9, 3, 230, 155, 178, 113, 117, 49, 0, 9, 3, 230, 156, 186, 106, 105, 49, 0, 0, 10, 3, 229, 164, 185, 106, 105, 97, 49, 0, 10, 3, 229, 162, 169, 100, 117, 110, 49, 0, 9, 3, 229, 174, 137, 97, 110, 49, 0, 11, 3, 232, 139, 177, 121, 105, 110, 103, 49, 0, 10, 3, 233, 128, 153, 122, 104, 101, 52, 0, 12, 3, 231, 157, 129, 122, 104, 101, 110, 103, 49, 0, 0, 9, 3, 229, 162, 168, 109, 111, 52, 0, 11, 3, 232, 140, 184, 114, 111, 110, 103, 49, 0, 12, 3, 229, 163, 176, 115, 104, 101, 110, 103, 49, 0, 11, 3, 230, 167, 144, 104, 117, 97, 105, 50, 0, 11, 3, 231, 148, 184, 100, 105, 97, 110, 52, 0, 10, 3, 231, 157, 128, 122, 104, 101, 53, 0, 10, 3, 229, 164, 184, 107, 117, 97, 49, 0, 11, 3, 229, 174, 136, 115, 104, 111, 117, 51, 0, 10, 3, 230, 155, 176, 121, 117, 101, 49, 0, 11, 3, 233, 129, 160, 121, 117, 97, 110, 51, 0, 0, 10, 3, 231, 148, 183, 110, 97, 110, 50, 0, 12, 3, 233, 133, 191, 110, 105, 97, 110, 103, 52, 0, 9, 3, 229, 174, 135, 121, 117, 51, 0, 9, 3, 231, 158, 135, 109, 105, 49, 0, 11, 3, 232, 151, 143, 99, 97, 110, 103, 50, 0, 10, 3, 233, 128, 151, 100, 111, 117, 52, 0, 10, 3, 230, 157, 191, 98, 97, 110, 51, 0, 13, 3, 229, 163, 175, 122, 104, 117, 97, 110, 103, 52, 0, 0, 13, 3, 229, 163, 174, 122, 104, 117, 97, 110, 103, 52, 0, 11, 3, 233, 130, 166, 98, 97, 110, 103, 49, 0, 10, 3, 232, 140, 182, 99, 104, 97, 50, 0, 9, 3, 233, 129, 158, 100, 105, 52, 0, 11, 3, 230, 157, 190, 115, 111, 110, 103, 49, 0, 9, 3, 232, 138, 166, 108, 117, 50, 0, 10, 3, 229, 161, 158, 115, 97, 105, 49, 0, 0, 10, 3, 232, 151, 141, 108, 97, 110, 50, 0, 12, 3, 230, 167, 141, 113, 105, 97, 110, 103, 49, 0, 11, 3, 231, 148, 181, 100, 105, 97, 110, 52, 0, 11, 3, 229, 174, 133, 122, 104, 97, 105, 50, 0, 11, 3, 231, 158, 133, 99, 104, 111, 117, 51, 0, 10, 3, 229, 165, 189, 104, 97, 111, 51, 0, 11, 3, 230, 153, 157, 122, 104, 111, 117, 52, 0, 10, 3, 230, 156, 181, 100, 117, 111, 53, 0, 0, 11, 3, 231, 158, 132, 109, 105, 97, 111, 50, 0, 9, 3, 229, 175, 140, 102, 117, 52, 0, 9, 3, 230, 156, 180, 112, 117, 51, 0, 11, 3, 232, 136, 148, 116, 105, 97, 110, 51, 0, 10, 3, 233, 129, 156, 120, 117, 110, 52, 0, 10, 3, 232, 150, 132, 98, 97, 111, 50, 0, 10, 3, 229, 164, 180, 116, 111, 117, 50, 0, 9, 3, 233, 128, 148, 116, 117, 50, 0, 0, 10, 3, 229, 163, 171, 115, 104, 105, 52, 0, 10, 3, 230, 167, 139, 103, 111, 117, 52, 0, 11, 3, 231, 148, 179, 115, 104, 101, 110, 49, 0, 9, 3, 229, 174, 131, 116, 97, 49, 0, 9, 3, 233, 130, 163, 110, 97, 52, 0, 9, 3, 230, 152, 147, 121, 105, 52, 0, 0, 10, 3, 232, 136, 146, 115, 104, 117, 49, 0, 9, 3, 231, 145, 154, 104, 117, 50, 0, 10, 3, 233, 142, 130, 109, 101, 105, 51, 0, 10, 3, 230, 166, 130, 103, 97, 105, 52, 0, 9, 3, 233, 128, 146, 100, 105, 52, 0, 10, 3, 230, 153, 154, 119, 97, 110, 51, 0, 10, 3, 231, 148, 178, 106, 105, 97, 51, 0, 12, 3, 230, 154, 162, 99, 104, 97, 110, 103, 52, 0, 0, 11, 3, 232, 137, 153, 99, 97, 110, 103, 49, 0, 9, 3, 229, 163, 169, 98, 97, 52, 0, 10, 3, 229, 164, 177, 115, 104, 105, 49, 0, 10, 3, 231, 148, 177, 121, 111, 117, 50, 0, 11, 3, 229, 174, 129, 110, 105, 110, 103, 50, 0, 10, 3, 233, 129, 153, 121, 97, 111, 50, 0, 9, 3, 229, 165, 185, 116, 97, 49, 0, 0, 11, 3, 229, 161, 152, 116, 97, 110, 103, 50, 0, 11, 3, 231, 148, 176, 116, 105, 97, 110, 50, 0, 11, 3, 233, 133, 184, 115, 117, 97, 110, 49, 0, 11, 3, 229, 165, 184, 106, 105, 97, 110, 49, 0, 10, 3, 233, 132, 176, 108, 105, 110, 50, 0, 9, 3, 233, 131, 168, 98, 117, 52, 0, 10, 3, 233, 128, 144, 122, 104, 117, 50, 0, 10, 3, 231, 144, 144, 115, 117, 111, 51, 0, 11, 3, 233, 143, 136, 108, 105, 97, 110, 52, 0, 10, 3, 232, 137, 152, 115, 111, 117, 49, 0, 0, 10, 3, 229, 175, 135, 107, 111, 117, 52, 0, 10, 3, 230, 156, 175, 115, 104, 117, 52, 0, 9, 3, 232, 141, 183, 104, 101, 50, 0, 10, 3, 230, 152, 143, 104, 117, 110, 49, 0, 9, 3, 233, 129, 151, 121, 105, 50, 0, 9, 3, 233, 133, 183, 107, 117, 52, 0, 10, 3, 233, 128, 143, 116, 111, 117, 52, 0, 0, 11, 3, 229, 164, 174, 121, 97, 110, 103, 49, 0, 9, 3, 232, 139, 166, 107, 117, 51, 0, 11, 3, 229, 162, 158, 122, 101, 110, 103, 49, 0, 10, 3, 230, 156, 174, 115, 104, 117, 52, 0, 11, 3, 230, 152, 142, 109, 105, 110, 103, 50, 0, 10, 3, 229, 165, 182, 110, 97, 105, 51, 0, 11, 3, 231, 149, 182, 100, 97, 110, 103, 49, 0, 9, 3, 231, 147, 166, 119, 97, 51, 0, 10, 3, 233, 133, 182, 109, 101, 105, 50, 0, 9, 3, 229, 175, 134, 109, 105, 52, 0, 9, 3, 231, 150, 190, 106, 105, 50, 0, 0, 10, 3, 230, 153, 149, 121, 117, 110, 49, 0, 10, 3, 232, 139, 165, 114, 117, 111, 52, 0, 11, 3, 233, 133, 181, 106, 105, 97, 111, 52, 0, 10, 3, 232, 136, 141, 115, 104, 101, 51, 0, 12, 3, 233, 132, 173, 122, 104, 101, 110, 103, 52, 0, 10, 3, 233, 129, 149, 119, 101, 105, 50, 0, 11, 3, 231, 148, 173, 98, 101, 110, 103, 50, 0, 10, 3, 232, 138, 157, 122, 104, 105, 49, 0, 0, 11, 3, 229, 163, 164, 114, 97, 110, 103, 51, 0, 9, 3, 229, 165, 180, 110, 117, 50, 0, 9, 3, 229, 161, 148, 116, 97, 51, 0, 9, 3, 229, 175, 132, 106, 105, 52, 0, 11, 3, 231, 150, 188, 116, 101, 110, 103, 50, 0, 9, 3, 233, 129, 148, 100, 97, 50, 0, 11, 3, 229, 162, 156, 122, 104, 117, 105, 52, 0, 10, 3, 230, 156, 172, 98, 101, 110, 51, 0, 10, 3, 232, 136, 140, 115, 104, 101, 50, 0, 0, 10, 3, 232, 136, 139, 120, 105, 110, 52, 0, 9, 3, 229, 165, 179, 110, 118, 51, 0, 11, 3, 232, 140, 171, 109, 97, 110, 103, 50, 0, 10, 3, 233, 129, 147, 100, 97, 111, 52, 0, 9, 3, 230, 156, 171, 109, 111, 52, 0, 10, 3, 231, 147, 163, 98, 97, 110, 52, 0, 11, 3, 230, 153, 147, 120, 105, 97, 111, 51, 0, 9, 3, 229, 166, 187, 113, 105, 49, 0, 9, 3, 229, 164, 171, 102, 117, 53, 0, 9, 3, 231, 148, 171, 102, 117, 53, 0, 0, 11, 3, 231, 147, 162, 112, 105, 97, 111, 50, 0, 10, 3, 233, 128, 138, 120, 117, 110, 52, 0, 11, 3, 230, 153, 146, 115, 104, 97, 105, 52, 0, 9, 3, 229, 175, 130, 106, 105, 52, 0, 10, 3, 230, 156, 170, 119, 101, 105, 52, 0, 10, 3, 232, 136, 138, 106, 105, 117, 52, 0, 10, 3, 229, 164, 170, 116, 97, 105, 52, 0, 0, 12, 3, 233, 133, 177, 106, 105, 97, 110, 103, 52, 0, 9, 3, 229, 161, 145, 115, 117, 52, 0, 9, 3, 232, 136, 137, 106, 117, 51, 0, 12, 3, 231, 148, 169, 115, 104, 117, 97, 105, 51, 0, 11, 3, 229, 164, 169, 116, 105, 97, 110, 49, 0, 12, 3, 229, 162, 153, 113, 105, 97, 110, 103, 50, 0, 11, 3, 232, 142, 185, 121, 105, 110, 103, 50, 0, 10, 3, 229, 166, 185, 109, 101, 105, 52, 0, 11, 3, 233, 128, 137, 120, 117, 97, 110, 51, 0, 11, 3, 230, 157, 177, 100, 111, 110, 103, 49, 0, 0, 9, 3, 230, 156, 168, 109, 117, 52, 0, 10, 3, 230, 157, 176, 106, 105, 101, 50, 0, 11, 3, 231, 148, 168, 121, 111, 110, 103, 52, 0, 11, 3, 232, 136, 136, 120, 105, 110, 103, 52, 0, 9, 3, 231, 149, 176, 121, 105, 52, 0, 12, 3, 230, 155, 160, 107, 117, 97, 110, 103, 52, 0, 0, 11, 3, 230, 160, 135, 98, 105, 97, 111, 49, 0, 11, 3, 231, 155, 159, 109, 101, 110, 103, 50, 0, 11, 3, 229, 168, 135, 106, 105, 97, 111, 49, 0, 11, 3, 230, 162, 151, 103, 101, 110, 103, 51, 0, 12, 3, 231, 159, 191, 107, 117, 97, 110, 103, 52, 0, 11, 3, 229, 175, 191, 115, 104, 111, 117, 52, 0, 0, 10, 3, 233, 140, 166, 106, 105, 110, 51, 0, 11, 3, 231, 155, 158, 122, 104, 97, 110, 51, 0, 10, 3, 229, 174, 182, 106, 105, 97, 49, 0, 0, 10, 3, 230, 167, 189, 99, 97, 111, 50, 0, 11, 3, 232, 148, 165, 99, 111, 110, 103, 49, 0, 11, 3, 229, 174, 181, 120, 105, 97, 111, 49, 0, 10, 3, 232, 147, 157, 108, 97, 110, 50, 0, 9, 3, 230, 165, 173, 121, 101, 52, 0, 10, 3, 233, 143, 189, 120, 105, 117, 52, 0, 0, 10, 3, 231, 155, 156, 100, 97, 111, 52, 0, 11, 3, 230, 161, 140, 122, 104, 117, 111, 49, 0, 10, 3, 230, 166, 180, 108, 105, 117, 50, 0, 10, 3, 229, 175, 188, 100, 97, 111, 51, 0, 9, 3, 231, 153, 140, 97, 105, 50, 0, 10, 3, 229, 174, 180, 121, 97, 110, 52, 0, 11, 3, 233, 141, 172, 113, 105, 97, 111, 49, 0, 10, 3, 232, 144, 132, 116, 97, 111, 50, 0, 0, 10, 3, 231, 157, 171, 106, 105, 101, 50, 0, 10, 3, 229, 173, 171, 115, 117, 110, 49, 0, 12, 3, 231, 155, 155, 115, 104, 101, 110, 103, 52, 0, 10, 3, 229, 174, 179, 104, 97, 105, 52, 0, 9, 3, 229, 168, 131, 119, 97, 50, 0, 10, 3, 229, 175, 187, 120, 117, 110, 50, 0, 0, 11, 3, 230, 163, 154, 112, 101, 110, 103, 50, 0, 11, 3, 233, 140, 162, 113, 105, 97, 110, 50, 0, 0, 9, 3, 232, 151, 185, 97, 105, 51, 0, 10, 3, 229, 173, 169, 104, 97, 105, 50, 0, 11, 3, 232, 149, 169, 100, 97, 110, 103, 52, 0, 10, 3, 229, 168, 129, 119, 101, 105, 49, 0, 10, 3, 229, 175, 185, 100, 117, 105, 52, 0, 9, 3, 232, 145, 137, 121, 101, 52, 0, 0, 10, 3, 229, 174, 176, 122, 97, 105, 51, 0, 10, 3, 231, 155, 152, 112, 97, 110, 50, 0, 9, 3, 230, 161, 136, 97, 110, 52, 0, 11, 3, 231, 156, 160, 109, 105, 97, 110, 50, 0, 10, 3, 229, 175, 184, 99, 117, 110, 52, 0, 11, 3, 233, 140, 160, 100, 105, 110, 103, 52, 0, 10, 2, 95, 51, 87, 35, 50, 115, 0, 29, 0, 11, 3, 231, 156, 159, 122, 104, 101, 110, 49, 0, 10, 3, 232, 150, 175, 115, 104, 117, 51, 0, 10, 3, 230, 163, 151, 122, 97, 111, 51, 0, 10, 3, 231, 155, 151, 100, 97, 111, 52, 0, 8, 2, 95, 50, 127, 113, 0, 29, 0, 11, 3, 233, 142, 174, 122, 104, 101, 110, 52, 0, 10, 3, 229, 173, 166, 120, 117, 101, 50, 0, 11, 3, 230, 152, 190, 120, 105, 97, 110, 51, 0, 10, 3, 231, 155, 150, 103, 97, 105, 52, 0, 12, 3, 230, 161, 134, 107, 117, 97, 110, 103, 49, 0, 11, 3, 229, 174, 174, 103, 111, 110, 103, 49, 0, 10, 3, 229, 175, 182, 98, 97, 111, 51, 0, 9, 3, 229, 169, 134, 112, 111, 50, 0, 11, 3, 230, 166, 174, 114, 111, 110, 103, 50, 0, 9, 2, 95, 49, 57, 37, 115, 0, 29, 0, 10, 3, 230, 161, 133, 119, 101, 105, 50, 0, 11, 3, 231, 158, 173, 108, 105, 97, 111, 51, 0, 10, 2, 95, 48, 55, 37, 66, 111, 0, 29, 0, 9, 3, 229, 173, 164, 103, 117, 49, 0, 9, 3, 233, 128, 188, 98, 105, 49, 0, 10, 3, 231, 155, 148, 107, 117, 105, 49, 0, 11, 3, 230, 152, 188, 122, 104, 111, 117, 52, 0, 9, 2, 95, 55, 119, 37, 115, 0, 29, 0, 11, 3, 229, 174, 171, 103, 111, 110, 103, 49, 0, 10, 3, 230, 161, 131, 116, 97, 111, 50, 0, 10, 3, 231, 159, 179, 115, 104, 105, 50, 0, 9, 3, 229, 173, 163, 106, 105, 52, 0, 10, 3, 233, 128, 187, 108, 117, 111, 50, 0, 12, 3, 230, 167, 179, 106, 105, 97, 110, 103, 51, 0, 9, 3, 231, 157, 163, 100, 117, 49, 0, 9, 2, 95, 54, 55, 136, 113, 0, 29, 0, 11, 3, 231, 153, 130, 108, 105, 97, 111, 50, 0, 10, 3, 232, 150, 170, 120, 105, 110, 49, 0, 11, 3, 230, 163, 146, 98, 97, 110, 103, 52, 0, 11, 3, 233, 139, 146, 102, 101, 110, 103, 49, 0, 11, 3, 229, 174, 170, 120, 105, 97, 110, 52, 0, 11, 3, 231, 158, 170, 100, 101, 110, 103, 52, 0, 9, 3, 231, 155, 146, 104, 101, 50, 0, 9, 2, 95, 53, 58, 40, 108, 0, 29, 0, 12, 3, 232, 136, 185, 99, 104, 117, 97, 110, 50, 0, 11, 3, 231, 155, 145, 106, 105, 97, 110, 49, 0, 11, 3, 231, 157, 161, 115, 104, 117, 105, 52, 0, 9, 3, 232, 150, 169, 115, 97, 52, 0, 9, 2, 95, 52, 87, 130, 113, 0, 29, 0, 11, 3, 233, 140, 152, 99, 104, 117, 105, 50, 0, 10, 3, 231, 155, 144, 121, 97, 110, 50, 0, 0, 12, 3, 231, 154, 135, 104, 117, 97, 110, 103, 50, 0, 11, 3, 231, 155, 143, 122, 104, 97, 110, 51, 0, 11, 3, 231, 158, 167, 113, 105, 97, 111, 50, 0, 9, 3, 233, 129, 191, 98, 105, 52, 0, 10, 3, 232, 148, 151, 122, 104, 101, 53, 0, 0, 11, 3, 230, 162, 134, 98, 97, 110, 103, 49, 0, 9, 3, 231, 159, 174, 97, 105, 51, 0, 12, 3, 230, 153, 190, 108, 105, 97, 110, 103, 52, 0, 10, 3, 231, 154, 134, 106, 105, 101, 49, 0, 9, 3, 232, 136, 182, 98, 111, 50, 0, 9, 2, 95, 57, 95, 136, 108, 0, 29, 0, 11, 3, 233, 138, 133, 116, 111, 110, 103, 50, 0, 10, 3, 230, 163, 141, 103, 117, 110, 52, 0, 9, 3, 229, 160, 181, 100, 117, 51, 0, 10, 3, 231, 158, 165, 112, 105, 101, 49, 0, 11, 3, 231, 159, 173, 100, 117, 97, 110, 51, 0, 10, 3, 230, 162, 133, 109, 101, 105, 50, 0, 9, 2, 95, 56, 48, 124, 115, 0, 29, 0, 11, 3, 229, 171, 140, 120, 105, 97, 110, 50, 0, 10, 3, 229, 174, 164, 115, 104, 105, 52, 0, 11, 3, 229, 175, 172, 107, 117, 97, 110, 49, 0, 12, 3, 231, 157, 156, 122, 104, 101, 110, 103, 49, 0, 10, 3, 231, 144, 180, 113, 105, 110, 50, 0, 11, 3, 233, 129, 188, 108, 105, 97, 111, 50, 0, 12, 3, 229, 160, 180, 99, 104, 97, 110, 103, 51, 0, 9, 3, 231, 154, 132, 100, 101, 53, 0, 0, 11, 3, 233, 141, 155, 100, 117, 97, 110, 52, 0, 9, 3, 230, 163, 139, 113, 105, 50, 0, 11, 3, 231, 157, 155, 106, 105, 110, 103, 53, 0, 10, 3, 232, 147, 139, 103, 97, 105, 52, 0, 11, 3, 229, 174, 163, 120, 117, 97, 110, 49, 0, 10, 3, 229, 175, 171, 120, 105, 101, 51, 0, 0, 9, 3, 229, 174, 162, 107, 101, 52, 0, 11, 3, 230, 164, 146, 106, 105, 97, 111, 49, 0, 9, 3, 233, 129, 186, 121, 105, 50, 0, 10, 3, 230, 165, 154, 99, 104, 117, 53, 0, 9, 3, 231, 155, 138, 121, 105, 52, 0, 10, 3, 230, 153, 186, 122, 104, 105, 52, 0, 10, 3, 231, 154, 130, 122, 97, 111, 52, 0, 9, 3, 232, 137, 186, 121, 105, 52, 0, 10, 3, 233, 128, 178, 106, 105, 110, 52, 0, 0, 11, 3, 229, 175, 169, 115, 104, 101, 110, 51, 0, 9, 3, 231, 159, 169, 106, 117, 53, 0, 12, 3, 230, 162, 129, 108, 105, 97, 110, 103, 50, 0, 10, 3, 229, 173, 153, 115, 117, 110, 49, 0, 10, 3, 229, 160, 177, 98, 97, 111, 52, 0, 11, 3, 230, 163, 137, 109, 105, 97, 110, 50, 0, 11, 3, 232, 136, 177, 99, 97, 110, 103, 49, 0, 11, 3, 229, 174, 161, 115, 104, 101, 110, 51, 0, 10, 3, 232, 148, 145, 109, 105, 101, 52, 0, 0, 11, 3, 232, 136, 176, 106, 105, 97, 110, 52, 0, 10, 3, 233, 138, 128, 121, 105, 110, 50, 0, 11, 3, 233, 129, 184, 120, 117, 97, 110, 51, 0, 10, 3, 229, 173, 152, 99, 117, 110, 50, 0, 10, 3, 229, 160, 176, 121, 97, 110, 52, 0, 0, 11, 3, 229, 175, 167, 110, 105, 110, 103, 50, 0, 10, 3, 232, 137, 183, 121, 97, 110, 52, 0, 9, 3, 229, 173, 151, 122, 105, 52, 0, 10, 3, 230, 152, 175, 115, 104, 105, 52, 0, 11, 3, 233, 129, 183, 113, 105, 97, 110, 49, 0, 0, 10, 3, 229, 174, 158, 115, 104, 105, 50, 0, 10, 3, 231, 158, 158, 109, 97, 110, 50, 0, 10, 3, 229, 175, 166, 115, 104, 105, 50, 0, 10, 3, 231, 155, 134, 112, 101, 110, 50, 0, 10, 3, 233, 128, 174, 100, 97, 105, 51, 0, 10, 3, 229, 162, 190, 107, 101, 110, 51, 0, 11, 3, 230, 153, 182, 106, 105, 110, 103, 49, 0, 0, 10, 3, 233, 139, 133, 120, 105, 110, 49, 0, 10, 3, 231, 159, 165, 122, 104, 105, 49, 0, 10, 3, 232, 151, 165, 121, 97, 111, 52, 0, 10, 3, 233, 129, 181, 122, 117, 110, 49, 0, 10, 3, 230, 164, 141, 122, 104, 105, 50, 0, 10, 3, 229, 174, 157, 98, 97, 111, 51, 0, 9, 3, 232, 138, 189, 121, 97, 50, 0, 11, 3, 229, 161, 181, 99, 104, 101, 110, 50, 0, 0, 11, 3, 232, 151, 164, 116, 101, 110, 103, 50, 0, 9, 3, 230, 163, 132, 113, 105, 52, 0, 11, 3, 230, 166, 156, 98, 97, 110, 103, 51, 0, 11, 3, 229, 173, 148, 107, 111, 110, 103, 51, 0, 9, 3, 232, 147, 132, 120, 117, 52, 0, 9, 3, 229, 174, 156, 121, 105, 53, 0, 11, 3, 229, 172, 140, 106, 105, 97, 111, 49, 0, 11, 3, 230, 153, 180, 113, 105, 110, 103, 50, 0, 10, 3, 232, 136, 172, 98, 97, 110, 49, 0, 0, 10, 3, 233, 130, 187, 108, 105, 110, 50, 0, 10, 3, 232, 137, 179, 121, 97, 110, 52, 0, 10, 3, 231, 156, 139, 107, 97, 110, 52, 0, 0, 9, 3, 232, 137, 178, 115, 101, 52, 0, 10, 3, 229, 160, 170, 107, 97, 110, 49, 0, 11, 3, 232, 136, 170, 104, 97, 110, 103, 50, 0, 11, 3, 229, 174, 154, 100, 105, 110, 103, 52, 0, 10, 3, 233, 129, 178, 99, 104, 105, 50, 0, 10, 3, 229, 171, 130, 115, 97, 111, 51, 0, 0, 11, 3, 229, 174, 153, 122, 104, 111, 117, 52, 0, 9, 3, 233, 139, 129, 108, 118, 51, 0, 10, 3, 229, 171, 129, 106, 105, 97, 52, 0, 10, 3, 231, 156, 137, 109, 101, 105, 50, 0, 10, 3, 229, 175, 161, 103, 117, 97, 51, 0, 11, 3, 233, 143, 161, 106, 105, 110, 103, 52, 0, 11, 3, 232, 137, 177, 106, 105, 97, 110, 49, 0, 0, 9, 3, 230, 153, 176, 120, 105, 49, 0, 11, 3, 230, 163, 128, 106, 105, 97, 110, 51, 0, 11, 3, 232, 137, 176, 106, 105, 97, 110, 49, 0, 9, 3, 229, 173, 144, 122, 105, 53, 0, 10, 3, 230, 152, 168, 122, 117, 111, 50, 0, 11, 3, 229, 174, 152, 103, 117, 97, 110, 49, 0, 0, 9, 3, 231, 167, 159, 122, 117, 49, 0, 10, 3, 228, 189, 143, 122, 104, 117, 52, 0, 11, 3, 233, 138, 183, 120, 105, 97, 111, 49, 0, 12, 3, 229, 180, 135, 99, 104, 111, 110, 103, 50, 0, 0, 11, 3, 231, 152, 166, 115, 104, 111, 117, 52, 0, 9, 3, 228, 189, 142, 100, 105, 49, 0, 11, 3, 229, 183, 158, 122, 104, 111, 117, 49, 0, 10, 3, 231, 155, 190, 100, 117, 110, 52, 0, 10, 3, 230, 174, 150, 122, 104, 105, 50, 0, 0, 10, 3, 228, 189, 141, 119, 101, 105, 52, 0, 10, 3, 233, 148, 133, 103, 117, 111, 49, 0, 11, 3, 232, 144, 165, 121, 105, 110, 103, 50, 0, 10, 3, 228, 191, 157, 98, 97, 111, 51, 0, 0, 10, 3, 231, 155, 188, 112, 97, 110, 52, 0, 10, 3, 230, 172, 132, 108, 97, 110, 50, 0, 11, 3, 233, 139, 188, 103, 97, 110, 103, 49, 0, 11, 3, 229, 181, 140, 113, 105, 97, 110, 52, 0, 9, 3, 232, 157, 140, 107, 101, 49, 0, 11, 3, 233, 151, 156, 103, 117, 97, 110, 49, 0, 11, 3, 232, 145, 172, 122, 97, 110, 103, 52, 0, 10, 3, 233, 148, 132, 99, 104, 117, 50, 0, 11, 3, 232, 144, 164, 121, 105, 110, 103, 50, 0, 9, 3, 230, 173, 140, 103, 101, 49, 0, 0, 10, 3, 233, 138, 179, 114, 117, 105, 52, 0, 9, 3, 232, 145, 171, 104, 117, 50, 0, 9, 3, 229, 170, 179, 120, 105, 50, 0, 11, 3, 233, 150, 147, 106, 105, 97, 110, 49, 0, 10, 3, 230, 175, 155, 109, 97, 111, 50, 0, 10, 3, 233, 136, 163, 103, 97, 105, 52, 0, 10, 3, 230, 162, 179, 115, 104, 117, 49, 0, 0, 11, 3, 230, 163, 186, 103, 117, 97, 110, 49, 0, 11, 3, 232, 156, 130, 102, 101, 110, 103, 49, 0, 0, 9, 3, 228, 188, 129, 113, 105, 51, 0, 11, 3, 233, 150, 145, 120, 105, 97, 110, 50, 0, 9, 3, 230, 175, 153, 98, 105, 52, 0, 11, 3, 232, 157, 137, 99, 104, 97, 110, 50, 0, 11, 3, 230, 173, 137, 113, 105, 97, 110, 52, 0, 11, 3, 231, 154, 177, 122, 104, 111, 117, 52, 0, 11, 3, 230, 160, 161, 120, 105, 97, 111, 52, 0, 13, 3, 230, 161, 169, 122, 104, 117, 97, 110, 103, 49, 0, 10, 3, 233, 148, 129, 115, 117, 111, 51, 0, 0, 12, 3, 230, 161, 168, 106, 105, 97, 110, 103, 51, 0, 9, 3, 233, 139, 184, 106, 117, 52, 0, 9, 3, 231, 167, 152, 109, 105, 52, 0, 10, 3, 230, 162, 176, 120, 105, 101, 52, 0, 11, 3, 233, 148, 128, 120, 105, 97, 111, 49, 0, 12, 3, 231, 155, 184, 120, 105, 97, 110, 103, 49, 0, 9, 3, 228, 191, 152, 102, 117, 50, 0, 0, 9, 3, 228, 191, 151, 115, 117, 50, 0, 9, 3, 230, 162, 175, 116, 105, 49, 0, 11, 3, 233, 149, 135, 122, 104, 101, 110, 52, 0, 9, 3, 231, 166, 143, 102, 117, 50, 0, 10, 3, 230, 173, 135, 120, 105, 101, 49, 0, 11, 3, 232, 157, 135, 121, 105, 110, 103, 53, 0, 0, 10, 3, 228, 189, 134, 100, 97, 110, 52, 0, 10, 3, 232, 145, 166, 119, 101, 105, 51, 0, 9, 3, 231, 154, 174, 112, 105, 50, 0, 10, 3, 230, 161, 166, 104, 117, 97, 52, 0, 13, 3, 233, 151, 150, 99, 104, 117, 97, 110, 103, 51, 0, 12, 3, 231, 156, 190, 122, 104, 111, 110, 103, 52, 0, 9, 3, 229, 169, 166, 102, 117, 52, 0, 0, 10, 3, 228, 190, 141, 115, 104, 105, 52, 0, 11, 3, 232, 158, 141, 114, 111, 110, 103, 50, 0, 9, 3, 230, 163, 181, 107, 101, 49, 0, 9, 3, 230, 175, 149, 98, 105, 52, 0, 9, 3, 232, 148, 189, 98, 105, 52, 0, 10, 3, 231, 166, 141, 104, 117, 111, 52, 0, 11, 3, 230, 161, 165, 113, 105, 97, 111, 50, 0, 10, 3, 232, 144, 157, 108, 117, 111, 50, 0, 0, 9, 3, 232, 148, 188, 97, 105, 51, 0, 10, 3, 231, 155, 180, 122, 104, 105, 50, 0, 10, 3, 233, 137, 164, 103, 111, 117, 49, 0, 9, 3, 230, 175, 148, 98, 105, 51, 0, 10, 3, 231, 156, 188, 121, 97, 110, 51, 0, 0, 9, 3, 228, 190, 139, 108, 105, 52, 0, 10, 3, 230, 174, 139, 99, 97, 110, 50, 0, 9, 3, 229, 168, 155, 121, 117, 50, 0, 11, 3, 230, 161, 163, 100, 97, 110, 103, 52, 0, 10, 3, 233, 150, 139, 107, 97, 105, 49, 0, 11, 3, 228, 189, 131, 100, 105, 97, 110, 52, 0, 0, 9, 3, 230, 175, 146, 100, 117, 50, 0, 10, 3, 230, 174, 138, 115, 104, 117, 49, 0, 11, 3, 231, 155, 178, 109, 97, 110, 103, 50, 0, 11, 3, 229, 183, 146, 108, 117, 97, 110, 50, 0, 11, 3, 231, 167, 146, 109, 105, 97, 111, 51, 0, 11, 3, 231, 156, 186, 116, 105, 97, 111, 52, 0, 0, 9, 3, 231, 167, 145, 107, 101, 49, 0, 10, 3, 233, 149, 129, 109, 101, 105, 51, 0, 9, 3, 232, 145, 161, 112, 117, 50, 0, 9, 3, 233, 150, 137, 98, 105, 52, 0, 0, 9, 3, 230, 162, 168, 108, 105, 50, 0, 11, 3, 229, 172, 184, 115, 104, 101, 110, 51, 0, 9, 3, 233, 149, 128, 100, 117, 52, 0, 12, 3, 229, 168, 152, 110, 105, 97, 110, 103, 53, 0, 0, 11, 3, 231, 155, 175, 100, 105, 110, 103, 49, 0, 10, 3, 230, 175, 143, 109, 101, 105, 51, 0, 9, 3, 229, 182, 135, 113, 117, 49, 0, 10, 3, 231, 153, 159, 98, 105, 101, 51, 0, 0, 12, 3, 231, 156, 182, 107, 117, 97, 110, 103, 52, 0, 11, 3, 230, 162, 166, 109, 101, 110, 103, 52, 0, 10, 3, 230, 163, 174, 115, 101, 110, 49, 0, 9, 3, 231, 155, 174, 109, 117, 52, 0, 10, 3, 228, 190, 134, 108, 97, 105, 50, 0, 0, 12, 3, 231, 167, 141, 122, 104, 111, 110, 103, 51, 0, 10, 3, 229, 183, 141, 119, 101, 105, 49, 0, 9, 3, 230, 175, 141, 109, 117, 51, 0, 0, 10, 3, 230, 165, 188, 108, 111, 117, 50, 0, 11, 3, 233, 136, 148, 99, 104, 97, 111, 49, 0, 11, 3, 229, 182, 132, 122, 104, 97, 110, 51, 0, 11, 3, 232, 147, 172, 112, 101, 110, 103, 50, 0, 0, 11, 3, 233, 137, 155, 113, 105, 97, 110, 49, 0, 10, 3, 231, 167, 139, 113, 105, 117, 49, 0, 11, 3, 233, 150, 131, 115, 104, 97, 110, 51, 0, 9, 3, 232, 159, 139, 120, 105, 49, 0, 0, 10, 3, 233, 151, 138, 107, 117, 111, 52, 0, 11, 3, 230, 162, 162, 115, 104, 97, 111, 49, 0, 9, 3, 233, 139, 170, 112, 117, 52, 0, 10, 3, 229, 169, 154, 104, 117, 110, 49, 0, 0, 10, 3, 230, 160, 145, 115, 104, 117, 52, 0, 10, 3, 231, 166, 129, 106, 105, 110, 52, 0, 10, 3, 229, 171, 169, 110, 101, 110, 52, 0, 0, 10, 3, 233, 150, 128, 109, 101, 110, 50, 0, 11, 3, 229, 172, 176, 121, 105, 110, 103, 49, 0, 10, 3, 229, 173, 184, 120, 117, 101, 50, 0, 0, 11, 3, 233, 137, 151, 113, 105, 97, 110, 50, 0, 9, 3, 231, 156, 175, 109, 105, 49, 0, 10, 3, 233, 140, 175, 99, 117, 111, 52, 0, 10, 3, 232, 145, 151, 122, 104, 101, 53, 0, 10, 3, 230, 160, 143, 108, 97, 110, 50, 0, 9, 3, 229, 174, 191, 115, 117, 52, 0, 0, 10, 3, 231, 167, 134, 103, 97, 110, 51, 0, 10, 3, 229, 174, 190, 98, 105, 110, 49, 0, 9, 3, 232, 159, 134, 109, 97, 53, 0, 0, 11, 3, 230, 162, 157, 116, 105, 97, 111, 50, 0, 9, 3, 230, 165, 181, 106, 105, 50, 0, 9, 3, 230, 175, 133, 121, 105, 52, 0, 9, 3, 229, 173, 181, 102, 117, 49, 0, 11, 3, 229, 174, 189, 107, 117, 97, 110, 49, 0, 11, 3, 233, 141, 181, 106, 105, 97, 110, 52, 0, 10, 3, 230, 164, 173, 116, 117, 111, 51, 0, 0, 11, 3, 233, 138, 156, 120, 105, 97, 110, 50, 0, 10, 3, 232, 148, 172, 115, 104, 117, 49, 0, 11, 3, 232, 146, 156, 115, 117, 97, 110, 52, 0, 10, 3, 231, 155, 164, 112, 97, 110, 50, 0, 9, 3, 230, 161, 148, 106, 117, 50, 0, 8, 3, 228, 191, 132, 101, 50, 0, 10, 3, 233, 139, 164, 99, 104, 117, 50, 0, 10, 3, 232, 149, 180, 121, 117, 110, 52, 0, 0, 11, 3, 231, 155, 163, 106, 105, 97, 110, 49, 0, 9, 3, 233, 140, 171, 120, 105, 49, 0, 11, 3, 231, 158, 187, 122, 104, 97, 110, 49, 0, 9, 3, 228, 191, 131, 99, 117, 52, 0, 11, 3, 231, 152, 139, 102, 101, 110, 103, 49, 0, 9, 3, 231, 167, 131, 116, 117, 49, 0, 0, 0, 11, 3, 230, 161, 145, 115, 97, 110, 103, 49, 0, 11, 3, 229, 174, 185, 114, 111, 110, 103, 50, 0, 9, 3, 231, 167, 129, 115, 105, 49, 0, 11, 3, 232, 146, 153, 109, 101, 110, 103, 50, 0, 10, 3, 231, 155, 161, 106, 105, 110, 51, 0, 10, 3, 230, 175, 129, 104, 117, 105, 51, 0, 0, 10, 3, 230, 175, 128, 104, 117, 105, 51, 0, 10, 3, 231, 156, 168, 122, 104, 97, 51, 0, 12, 3, 232, 159, 128, 115, 104, 117, 97, 105, 52, 0, 10, 3, 231, 167, 128, 120, 105, 117, 52, 0, 0, 12, 3, 229, 176, 135, 106, 105, 97, 110, 103, 49, 0, 11, 3, 229, 177, 143, 112, 105, 110, 103, 50, 0, 9, 3, 230, 172, 167, 111, 117, 49, 0, 9, 3, 232, 153, 143, 108, 117, 51, 0, 10, 3, 231, 162, 151, 119, 97, 110, 51, 0, 10, 3, 228, 184, 135, 119, 97, 110, 52, 0, 11, 3, 229, 178, 151, 103, 97, 110, 103, 51, 0, 9, 3, 232, 152, 135, 115, 117, 49, 0, 9, 3, 228, 185, 143, 102, 97, 50, 0, 0, 9, 3, 229, 178, 150, 113, 117, 49, 0, 9, 3, 232, 153, 142, 104, 117, 51, 0, 9, 3, 228, 185, 142, 104, 117, 53, 0, 9, 3, 232, 152, 134, 108, 117, 50, 0, 10, 3, 233, 148, 166, 106, 105, 110, 51, 0, 10, 3, 229, 183, 190, 106, 105, 110, 49, 0, 12, 3, 229, 176, 134, 106, 105, 97, 110, 103, 49, 0, 10, 3, 229, 177, 142, 115, 104, 105, 51, 0, 12, 3, 231, 164, 166, 107, 117, 97, 110, 103, 52, 0, 0, 10, 3, 232, 154, 149, 99, 97, 110, 50, 0, 9, 3, 233, 147, 157, 108, 118, 51, 0, 10, 3, 228, 190, 181, 113, 105, 110, 49, 0, 11, 3, 230, 174, 181, 100, 117, 97, 110, 52, 0, 11, 3, 228, 186, 149, 106, 105, 110, 103, 51, 0, 0, 12, 3, 228, 188, 164, 115, 104, 97, 110, 103, 49, 0, 10, 3, 229, 176, 132, 115, 104, 101, 52, 0, 9, 3, 228, 185, 140, 119, 117, 49, 0, 11, 3, 233, 148, 164, 99, 104, 117, 105, 50, 0, 11, 3, 233, 147, 156, 116, 111, 110, 103, 50, 0, 11, 3, 230, 170, 148, 100, 97, 110, 103, 52, 0, 9, 3, 228, 186, 148, 119, 117, 51, 0, 0, 10, 3, 233, 151, 187, 119, 101, 110, 50, 0, 11, 3, 230, 169, 139, 113, 105, 97, 111, 50, 0, 10, 3, 232, 154, 147, 121, 105, 110, 51, 0, 10, 3, 228, 185, 139, 122, 104, 105, 49, 0, 10, 3, 233, 148, 163, 108, 117, 111, 50, 0, 11, 3, 233, 147, 155, 100, 97, 110, 103, 53, 0, 9, 3, 231, 167, 187, 121, 105, 50, 0, 9, 3, 232, 159, 187, 121, 105, 51, 0, 11, 3, 233, 146, 147, 100, 105, 97, 111, 52, 0, 9, 3, 229, 177, 139, 119, 117, 49, 0, 10, 3, 230, 172, 163, 120, 105, 110, 49, 0, 10, 3, 232, 155, 155, 122, 104, 117, 49, 0, 9, 3, 228, 184, 131, 113, 105, 49, 0, 0, 10, 3, 229, 177, 138, 106, 105, 101, 52, 0, 11, 3, 230, 174, 178, 106, 105, 97, 110, 49, 0, 9, 3, 228, 191, 186, 97, 110, 51, 0, 9, 3, 230, 168, 130, 108, 101, 52, 0, 12, 3, 231, 163, 154, 122, 104, 117, 97, 110, 49, 0, 10, 3, 233, 151, 186, 103, 117, 105, 49, 0, 11, 3, 230, 172, 162, 104, 117, 97, 110, 53, 0, 9, 3, 228, 186, 146, 104, 117, 52, 0, 10, 3, 231, 160, 130, 115, 104, 97, 49, 0, 10, 3, 230, 173, 170, 119, 97, 105, 49, 0, 0, 9, 3, 228, 185, 137, 121, 105, 52, 0, 9, 3, 230, 172, 161, 99, 105, 52, 0, 10, 3, 231, 162, 145, 98, 101, 105, 49, 0, 10, 3, 233, 151, 185, 110, 97, 111, 52, 0, 11, 3, 229, 176, 129, 102, 101, 110, 103, 49, 0, 10, 3, 228, 189, 169, 112, 101, 105, 52, 0, 9, 3, 231, 160, 129, 109, 97, 51, 0, 9, 3, 232, 156, 161, 108, 97, 52, 0, 10, 3, 233, 150, 177, 121, 117, 101, 52, 0, 9, 3, 232, 155, 153, 119, 97, 49, 0, 9, 3, 229, 177, 137, 116, 105, 53, 0, 10, 3, 228, 186, 145, 121, 117, 110, 50, 0, 11, 3, 228, 184, 129, 100, 105, 110, 103, 49, 0, 13, 3, 230, 168, 129, 122, 104, 117, 97, 110, 103, 49, 0, 9, 3, 233, 148, 161, 120, 105, 49, 0, 11, 3, 228, 187, 153, 120, 105, 97, 110, 53, 0, 0, 10, 3, 230, 170, 144, 121, 97, 110, 50, 0, 11, 3, 231, 165, 168, 112, 105, 97, 111, 52, 0, 10, 3, 233, 151, 184, 122, 104, 97, 50, 0, 9, 3, 228, 184, 128, 121, 105, 49, 0, 9, 3, 229, 177, 136, 113, 117, 49, 0, 9, 3, 228, 187, 152, 102, 117, 52, 0, 12, 3, 228, 188, 160, 99, 104, 117, 97, 110, 50, 0, 11, 3, 230, 172, 160, 113, 105, 97, 110, 52, 0, 9, 3, 228, 185, 136, 109, 101, 53, 0, 0, 10, 3, 228, 188, 159, 119, 101, 105, 51, 0, 10, 3, 228, 186, 143, 107, 117, 105, 49, 0, 12, 3, 229, 183, 183, 120, 105, 97, 110, 103, 52, 0, 12, 3, 228, 187, 151, 122, 104, 97, 110, 103, 52, 0, 10, 3, 233, 151, 183, 109, 101, 110, 52, 0, 0, 9, 3, 228, 186, 142, 121, 117, 50, 0, 9, 3, 230, 173, 166, 119, 117, 51, 0, 10, 3, 233, 136, 190, 121, 111, 117, 50, 0, 10, 3, 229, 177, 134, 106, 105, 101, 52, 0, 10, 3, 232, 157, 166, 120, 105, 97, 49, 0, 9, 3, 228, 187, 150, 116, 97, 49, 0, 9, 3, 228, 190, 174, 119, 117, 51, 0, 10, 3, 231, 162, 142, 115, 117, 105, 52, 0, 9, 3, 231, 166, 174, 108, 105, 51, 0, 10, 3, 228, 188, 158, 115, 97, 110, 51, 0, 0, 12, 3, 231, 165, 165, 120, 105, 97, 110, 103, 50, 0, 10, 3, 228, 185, 133, 106, 105, 117, 51, 0, 9, 3, 231, 162, 141, 97, 105, 52, 0, 9, 3, 230, 173, 165, 98, 117, 52, 0, 9, 3, 231, 163, 149, 107, 101, 49, 0, 10, 3, 230, 160, 189, 122, 97, 105, 49, 0, 10, 3, 231, 161, 133, 103, 117, 105, 49, 0, 10, 3, 232, 144, 189, 108, 117, 111, 52, 0, 9, 3, 229, 177, 133, 106, 117, 49, 0, 0, 9, 3, 230, 173, 164, 99, 105, 51, 0, 11, 3, 233, 151, 180, 106, 105, 97, 110, 49, 0, 9, 3, 230, 160, 188, 103, 101, 50, 0, 9, 3, 229, 183, 180, 98, 97, 53, 0, 9, 3, 228, 186, 140, 101, 114, 52, 0, 9, 3, 228, 187, 148, 122, 105, 51, 0, 9, 3, 232, 156, 156, 109, 105, 52, 0, 10, 3, 233, 145, 132, 122, 104, 117, 52, 0, 9, 3, 231, 162, 140, 108, 117, 52, 0, 0, 11, 3, 228, 187, 147, 99, 97, 110, 103, 49, 0, 10, 3, 228, 185, 131, 110, 97, 105, 51, 0, 10, 3, 228, 186, 139, 115, 104, 105, 52, 0, 12, 3, 230, 173, 163, 122, 104, 101, 110, 103, 52, 0, 0, 11, 3, 233, 151, 178, 120, 105, 97, 110, 50, 0, 10, 3, 228, 188, 154, 104, 117, 105, 52, 0, 10, 3, 232, 154, 138, 119, 101, 110, 50, 0, 9, 3, 229, 183, 178, 121, 105, 51, 0, 10, 3, 230, 173, 162, 122, 104, 105, 51, 0, 11, 3, 229, 177, 130, 99, 101, 110, 103, 50, 0, 0, 9, 3, 229, 177, 129, 112, 105, 52, 0, 9, 3, 231, 164, 153, 97, 105, 52, 0, 12, 3, 228, 186, 137, 122, 104, 101, 110, 103, 49, 0, 10, 3, 233, 148, 153, 99, 117, 111, 52, 0, 9, 3, 228, 191, 177, 106, 117, 52, 0, 10, 3, 228, 188, 153, 104, 117, 111, 51, 0, 11, 3, 233, 146, 137, 100, 105, 110, 103, 49, 0, 11, 3, 230, 173, 161, 104, 117, 97, 110, 53, 0, 9, 3, 229, 183, 177, 106, 105, 51, 0, 10, 3, 230, 160, 185, 103, 101, 110, 49, 0, 0, 10, 3, 228, 188, 152, 121, 111, 117, 49, 0, 10, 3, 233, 150, 168, 103, 117, 105, 49, 0, 9, 3, 232, 157, 160, 102, 117, 50, 0, 9, 3, 228, 189, 160, 110, 105, 51, 0, 11, 3, 233, 146, 136, 122, 104, 101, 110, 49, 0, 9, 3, 230, 160, 184, 104, 101, 50, 0, 10, 3, 232, 156, 152, 122, 104, 105, 49, 0, 12, 3, 231, 167, 176, 99, 104, 101, 110, 103, 49, 0, 9, 3, 228, 186, 136, 121, 117, 51, 0, 9, 3, 229, 177, 128, 106, 117, 50, 0, 10, 3, 231, 161, 128, 99, 104, 117, 51, 0, 0, 11, 3, 229, 180, 151, 103, 97, 110, 103, 51, 0, 9, 3, 231, 167, 175, 106, 105, 49, 0, 9, 3, 233, 136, 183, 103, 117, 51, 0, 10, 3, 232, 157, 159, 119, 101, 105, 53, 0, 13, 3, 233, 151, 175, 99, 104, 117, 97, 110, 103, 51, 0, 9, 3, 228, 190, 167, 99, 101, 52, 0, 12, 3, 228, 188, 151, 122, 104, 111, 110, 103, 52, 0, 10, 3, 230, 175, 175, 116, 97, 110, 51, 0, 9, 3, 228, 191, 175, 102, 117, 51, 0, 11, 3, 230, 160, 183, 121, 97, 110, 103, 52, 0, 9, 3, 232, 156, 151, 119, 111, 49, 0, 0, 10, 3, 228, 191, 174, 120, 105, 117, 49, 0, 11, 3, 228, 187, 142, 99, 111, 110, 103, 50, 0, 11, 3, 231, 165, 158, 115, 104, 101, 110, 50, 0, 10, 3, 231, 153, 190, 98, 97, 105, 51, 0, 10, 3, 229, 183, 174, 99, 104, 97, 52, 0, 9, 3, 228, 186, 134, 108, 101, 53, 0, 11, 3, 228, 190, 166, 122, 104, 101, 110, 49, 0, 9, 3, 229, 168, 182, 113, 117, 51, 0, 9, 3, 229, 180, 150, 121, 97, 50, 0, 10, 3, 233, 151, 174, 119, 101, 110, 52, 0, 0, 9, 3, 233, 151, 173, 98, 105, 52, 0, 10, 3, 231, 165, 157, 122, 104, 117, 52, 0, 11, 3, 228, 191, 173, 106, 105, 97, 110, 51, 0, 11, 3, 228, 187, 141, 114, 101, 110, 103, 50, 0, 9, 3, 233, 150, 165, 102, 97, 50, 0, 10, 3, 231, 153, 189, 98, 97, 105, 50, 0, 0, 11, 3, 232, 159, 172, 99, 104, 97, 110, 50, 0, 11, 3, 233, 136, 180, 108, 105, 110, 103, 50, 0, 9, 3, 231, 153, 188, 102, 97, 49, 0, 11, 3, 233, 149, 156, 106, 105, 110, 103, 52, 0, 10, 3, 228, 189, 156, 122, 117, 111, 52, 0, 0, 11, 3, 232, 156, 147, 116, 105, 110, 103, 50, 0, 9, 3, 228, 189, 155, 102, 117, 50, 0, 10, 3, 228, 187, 139, 106, 105, 101, 52, 0, 11, 3, 231, 153, 187, 100, 101, 110, 103, 49, 0, 10, 3, 230, 175, 171, 104, 97, 111, 50, 0, 10, 3, 232, 155, 139, 100, 97, 110, 52, 0, 0, 9, 3, 229, 178, 130, 113, 105, 51, 0, 11, 3, 232, 158, 162, 121, 105, 110, 103, 50, 0, 10, 3, 228, 187, 138, 106, 105, 110, 49, 0, 11, 3, 233, 151, 170, 115, 104, 97, 110, 51, 0, 9, 3, 232, 154, 130, 109, 97, 51, 0, 11, 3, 228, 186, 130, 108, 117, 97, 110, 52, 0, 10, 3, 231, 163, 138, 108, 101, 105, 51, 0, 0, 10, 3, 228, 188, 145, 120, 105, 117, 49, 0, 10, 3, 229, 178, 129, 115, 117, 105, 52, 0, 10, 3, 228, 191, 169, 108, 105, 97, 51, 0, 11, 3, 232, 157, 153, 98, 105, 97, 110, 49, 0, 9, 3, 228, 189, 153, 121, 117, 50, 0, 11, 3, 229, 183, 169, 103, 111, 110, 103, 51, 0, 10, 3, 231, 167, 169, 122, 104, 105, 52, 0, 9, 3, 232, 154, 129, 121, 105, 51, 0, 9, 3, 229, 168, 177, 121, 117, 50, 0, 0, 9, 3, 229, 183, 168, 106, 117, 52, 0, 10, 3, 233, 151, 168, 109, 101, 110, 50, 0, 10, 3, 232, 154, 128, 115, 104, 105, 50, 0, 10, 3, 233, 148, 144, 114, 117, 105, 52, 0, 9, 3, 228, 188, 144, 102, 97, 50, 0, 0, 9, 3, 228, 188, 143, 102, 117, 50, 0, 11, 3, 229, 183, 167, 113, 105, 97, 111, 51, 0, 11, 3, 231, 167, 167, 121, 97, 110, 103, 49, 0, 10, 3, 232, 155, 135, 115, 104, 101, 50, 0, 12, 3, 232, 157, 151, 104, 117, 97, 110, 103, 50, 0, 11, 3, 228, 187, 135, 99, 104, 111, 117, 50, 0, 0, 10, 3, 229, 183, 166, 122, 117, 111, 51, 0, 9, 3, 232, 158, 158, 109, 97, 51, 0, 10, 3, 231, 164, 142, 99, 104, 117, 51, 0, 11, 3, 230, 161, 182, 116, 111, 110, 103, 51, 0, 9, 3, 229, 180, 142, 113, 105, 50, 0, 9, 3, 231, 165, 150, 122, 117, 51, 0, 9, 3, 232, 155, 134, 113, 117, 49, 0, 11, 3, 229, 169, 182, 115, 104, 101, 110, 51, 0, 0, 10, 3, 228, 187, 133, 106, 105, 110, 51, 0, 9, 3, 228, 188, 141, 119, 117, 53, 0, 9, 3, 229, 170, 189, 109, 97, 49, 0, 9, 3, 228, 189, 149, 104, 101, 50, 0, 10, 3, 232, 145, 181, 107, 117, 105, 50, 0, 11, 3, 231, 163, 133, 98, 97, 110, 103, 52, 0, 11, 3, 233, 147, 133, 113, 105, 97, 110, 49, 0, 9, 3, 228, 190, 157, 121, 105, 49, 0, 11, 3, 229, 183, 165, 103, 111, 110, 103, 49, 0, 10, 3, 232, 157, 149, 115, 104, 105, 50, 0, 0, 10, 3, 233, 148, 140, 120, 105, 110, 49, 0, 10, 3, 232, 144, 172, 119, 97, 110, 52, 0, 12, 3, 231, 167, 164, 99, 104, 101, 110, 103, 52, 0, 11, 3, 233, 137, 180, 106, 105, 97, 110, 52, 0, 11, 3, 229, 169, 180, 121, 105, 110, 103, 49, 0, 11, 3, 232, 146, 188, 99, 97, 110, 103, 49, 0, 0, 11, 3, 228, 190, 155, 103, 111, 110, 103, 49, 0, 11, 3, 233, 148, 139, 102, 101, 110, 103, 49, 0, 9, 3, 228, 189, 147, 116, 105, 51, 0, 11, 3, 233, 147, 131, 108, 105, 110, 103, 50, 0, 0, 11, 3, 230, 172, 138, 113, 117, 97, 110, 50, 0, 9, 3, 228, 188, 138, 121, 105, 49, 0, 11, 3, 229, 183, 162, 99, 104, 97, 111, 50, 0, 11, 3, 231, 154, 186, 122, 104, 111, 117, 52, 0, 10, 3, 230, 160, 170, 122, 104, 117, 49, 0, 10, 3, 231, 152, 170, 98, 105, 101, 51, 0, 0, 10, 3, 229, 183, 161, 120, 117, 110, 50, 0, 11, 3, 233, 151, 161, 99, 104, 97, 110, 51, 0, 11, 3, 232, 145, 177, 99, 111, 110, 103, 49, 0, 9, 3, 231, 152, 169, 100, 97, 53, 0, 10, 3, 233, 147, 129, 116, 105, 101, 51, 0, 10, 3, 228, 191, 161, 120, 105, 110, 52, 0, 11, 3, 230, 175, 161, 122, 104, 97, 110, 49, 0, 10, 3, 228, 189, 145, 121, 111, 117, 52, 0, 9, 3, 231, 163, 129, 99, 105, 50, 0, 0, 10, 3, 233, 150, 152, 122, 104, 97, 50, 0, 9, 3, 232, 144, 168, 115, 97, 52, 0, 10, 3, 233, 147, 128, 121, 111, 117, 50, 0, 9, 3, 232, 156, 136, 119, 117, 50, 0, 10, 3, 232, 155, 128, 122, 104, 117, 52, 0, 9, 3, 230, 173, 144, 111, 117, 49, 0, 12, 3, 232, 146, 184, 122, 104, 101, 110, 103, 49, 0, 11, 3, 228, 187, 128, 115, 104, 101, 110, 50, 0, 10, 3, 233, 148, 136, 120, 105, 117, 52, 0, 10, 3, 230, 174, 152, 99, 97, 110, 50, 0, 0, 9, 3, 232, 164, 135, 102, 117, 52, 0, 11, 3, 228, 184, 167, 115, 97, 110, 103, 52, 0, 11, 3, 231, 174, 151, 115, 117, 97, 110, 52, 0, 9, 3, 229, 190, 151, 100, 101, 53, 0, 11, 3, 228, 187, 191, 102, 97, 110, 103, 51, 0, 11, 3, 233, 156, 135, 122, 104, 101, 110, 52, 0, 0, 9, 3, 230, 181, 142, 106, 105, 52, 0, 11, 3, 233, 147, 190, 108, 105, 97, 110, 52, 0, 10, 3, 232, 166, 150, 115, 104, 105, 52, 0, 9, 3, 231, 172, 134, 98, 97, 53, 0, 10, 3, 229, 189, 142, 119, 97, 110, 49, 0, 8, 3, 232, 155, 190, 101, 50, 0, 10, 3, 231, 161, 174, 113, 117, 101, 52, 0, 0, 9, 3, 230, 182, 149, 116, 105, 52, 0, 10, 3, 228, 187, 189, 102, 101, 110, 52, 0, 10, 3, 228, 184, 165, 121, 97, 110, 50, 0, 10, 3, 229, 179, 189, 120, 105, 97, 50, 0, 0, 12, 3, 228, 184, 164, 108, 105, 97, 110, 103, 51, 0, 11, 3, 229, 188, 132, 110, 111, 110, 103, 52, 0, 9, 3, 233, 146, 180, 103, 117, 51, 0, 10, 3, 229, 176, 164, 121, 111, 117, 50, 0, 10, 3, 229, 177, 172, 115, 104, 117, 51, 0, 11, 3, 231, 161, 172, 121, 105, 110, 103, 52, 0, 9, 3, 229, 189, 140, 109, 105, 50, 0, 0, 9, 3, 229, 188, 131, 113, 105, 52, 0, 10, 3, 229, 179, 187, 106, 117, 110, 52, 0, 10, 3, 231, 161, 171, 108, 105, 117, 50, 0, 10, 3, 231, 173, 139, 106, 105, 110, 49, 0, 11, 3, 230, 168, 163, 121, 97, 110, 103, 52, 0, 11, 3, 233, 146, 179, 113, 105, 97, 110, 50, 0, 10, 3, 228, 187, 187, 114, 101, 110, 52, 0, 12, 3, 232, 153, 171, 99, 104, 111, 110, 103, 50, 0, 11, 3, 230, 169, 171, 104, 101, 110, 103, 50, 0, 9, 3, 230, 181, 139, 99, 101, 52, 0, 10, 3, 231, 162, 179, 116, 97, 110, 52, 0, 0, 9, 3, 229, 190, 146, 116, 117, 50, 0, 10, 3, 232, 164, 130, 103, 117, 97, 52, 0, 11, 3, 230, 181, 138, 122, 104, 117, 111, 50, 0, 10, 3, 228, 184, 162, 100, 105, 117, 49, 0, 12, 3, 231, 163, 186, 104, 117, 97, 110, 103, 50, 0, 9, 3, 229, 188, 130, 121, 105, 52, 0, 10, 3, 230, 183, 154, 108, 101, 105, 52, 0, 9, 3, 233, 147, 186, 112, 117, 52, 0, 10, 3, 228, 186, 178, 113, 105, 110, 49, 0, 0, 11, 3, 229, 191, 153, 109, 97, 110, 103, 50, 0, 11, 3, 231, 173, 137, 100, 101, 110, 103, 51, 0, 10, 3, 230, 180, 129, 106, 105, 101, 50, 0, 11, 3, 233, 146, 177, 113, 105, 97, 110, 50, 0, 11, 3, 231, 162, 177, 106, 105, 97, 110, 51, 0, 9, 3, 230, 168, 161, 109, 111, 50, 0, 11, 3, 229, 190, 145, 106, 105, 110, 103, 52, 0, 0, 10, 3, 229, 189, 136, 100, 97, 110, 52, 0, 10, 3, 230, 183, 152, 116, 97, 111, 50, 0, 11, 3, 233, 157, 136, 108, 105, 110, 103, 50, 0, 11, 3, 231, 162, 176, 112, 101, 110, 103, 52, 0, 9, 3, 229, 190, 144, 120, 117, 50, 0, 10, 3, 233, 147, 184, 122, 104, 117, 52, 0, 10, 3, 229, 188, 128, 107, 97, 105, 49, 0, 11, 3, 229, 191, 152, 119, 97, 110, 103, 52, 0, 9, 3, 233, 156, 128, 120, 117, 49, 0, 0, 10, 3, 229, 191, 151, 122, 104, 105, 52, 0, 10, 3, 232, 153, 167, 107, 117, 105, 49, 0, 10, 3, 232, 166, 143, 103, 117, 105, 49, 0, 11, 3, 230, 181, 135, 106, 105, 97, 111, 49, 0, 10, 3, 231, 163, 183, 108, 105, 110, 50, 0, 11, 3, 233, 158, 143, 103, 111, 110, 103, 51, 0, 12, 3, 230, 168, 159, 122, 104, 97, 110, 103, 49, 0, 10, 3, 232, 154, 175, 113, 105, 117, 49, 0, 10, 3, 228, 184, 159, 100, 105, 117, 49, 0, 10, 3, 228, 187, 183, 106, 105, 97, 52, 0, 0, 10, 3, 231, 164, 190, 115, 104, 101, 52, 0, 9, 3, 231, 173, 134, 98, 105, 51, 0, 12, 3, 228, 186, 174, 108, 105, 97, 110, 103, 52, 0, 11, 3, 228, 187, 182, 106, 105, 97, 110, 52, 0, 11, 3, 230, 172, 190, 107, 117, 97, 110, 51, 0, 12, 3, 230, 181, 134, 106, 105, 97, 110, 103, 49, 0, 10, 3, 233, 147, 182, 121, 105, 110, 50, 0, 10, 3, 230, 168, 158, 115, 104, 117, 49, 0, 10, 3, 229, 179, 182, 100, 97, 111, 51, 0, 10, 3, 228, 185, 166, 115, 104, 117, 49, 0, 0, 11, 3, 229, 178, 173, 108, 105, 110, 103, 51, 0, 11, 3, 230, 181, 133, 113, 105, 97, 110, 51, 0, 9, 3, 228, 184, 157, 115, 105, 49, 0, 10, 3, 230, 172, 189, 113, 105, 110, 49, 0, 11, 3, 228, 186, 173, 116, 105, 110, 103, 50, 0, 12, 3, 229, 176, 157, 99, 104, 97, 110, 103, 50, 0, 10, 3, 229, 180, 189, 122, 97, 105, 51, 0, 0, 11, 3, 230, 182, 140, 121, 111, 110, 103, 51, 0, 11, 3, 229, 177, 164, 99, 101, 110, 103, 50, 0, 9, 3, 231, 164, 188, 108, 105, 51, 0, 11, 3, 228, 184, 156, 100, 111, 110, 103, 49, 0, 9, 3, 228, 188, 188, 115, 105, 52, 0, 0, 9, 3, 229, 190, 139, 108, 118, 52, 0, 11, 3, 228, 184, 155, 99, 111, 110, 103, 50, 0, 11, 3, 232, 156, 187, 113, 105, 110, 103, 49, 0, 10, 3, 233, 158, 139, 120, 105, 101, 50, 0, 11, 3, 233, 148, 187, 100, 117, 97, 110, 52, 0, 11, 3, 232, 166, 139, 106, 105, 97, 110, 52, 0, 12, 3, 228, 186, 171, 120, 105, 97, 110, 103, 51, 0, 0, 10, 3, 232, 154, 170, 100, 111, 117, 51, 0, 10, 3, 230, 169, 162, 116, 117, 111, 51, 0, 10, 3, 231, 164, 186, 115, 104, 105, 52, 0, 11, 3, 233, 147, 178, 99, 104, 97, 110, 51, 0, 12, 3, 229, 176, 154, 115, 104, 97, 110, 103, 52, 0, 11, 3, 229, 190, 138, 104, 117, 97, 105, 50, 0, 9, 3, 230, 183, 146, 113, 105, 49, 0, 9, 3, 230, 172, 186, 113, 105, 49, 0, 11, 3, 232, 167, 146, 106, 105, 97, 111, 51, 0, 9, 3, 228, 188, 186, 99, 105, 52, 0, 9, 3, 228, 184, 154, 121, 101, 52, 0, 0, 10, 3, 233, 146, 169, 103, 111, 117, 49, 0, 10, 3, 230, 181, 129, 108, 105, 117, 50, 0, 11, 3, 233, 148, 185, 113, 105, 97, 111, 49, 0, 10, 3, 229, 178, 169, 121, 97, 110, 50, 0, 11, 3, 230, 168, 153, 98, 105, 97, 111, 49, 0, 11, 3, 228, 184, 153, 98, 105, 110, 103, 51, 0, 12, 3, 228, 185, 161, 120, 105, 97, 110, 103, 49, 0, 12, 3, 230, 169, 161, 120, 105, 97, 110, 103, 52, 0, 10, 3, 232, 154, 169, 99, 104, 105, 49, 0, 9, 3, 228, 186, 169, 109, 117, 51, 0, 10, 3, 230, 182, 137, 115, 104, 101, 52, 0, 0, 9, 3, 228, 185, 160, 120, 105, 50, 0, 12, 3, 233, 144, 152, 122, 104, 111, 110, 103, 49, 0, 11, 3, 228, 188, 184, 115, 104, 101, 110, 49, 0, 11, 3, 229, 176, 152, 99, 104, 101, 110, 50, 0, 11, 3, 229, 179, 176, 102, 101, 110, 103, 49, 0, 11, 3, 230, 182, 136, 120, 105, 97, 111, 49, 0, 9, 3, 229, 177, 160, 116, 117, 50, 0, 10, 3, 228, 184, 152, 113, 105, 117, 49, 0, 11, 3, 228, 187, 176, 121, 97, 110, 103, 51, 0, 10, 3, 229, 190, 136, 104, 101, 110, 51, 0, 0, 11, 3, 228, 186, 167, 99, 104, 97, 110, 51, 0, 12, 3, 233, 149, 191, 99, 104, 97, 110, 103, 50, 0, 10, 3, 232, 153, 159, 104, 97, 111, 52, 0, 9, 3, 231, 162, 167, 98, 105, 52, 0, 10, 3, 228, 189, 191, 115, 104, 105, 51, 0, 9, 3, 228, 185, 159, 121, 101, 51, 0, 9, 3, 230, 169, 159, 106, 105, 49, 0, 0, 11, 3, 228, 188, 182, 108, 105, 110, 103, 53, 0, 10, 3, 228, 184, 150, 115, 104, 105, 52, 0, 9, 3, 232, 166, 134, 102, 117, 52, 0, 10, 3, 233, 146, 166, 113, 105, 110, 49, 0, 9, 3, 228, 186, 166, 121, 105, 52, 0, 11, 3, 229, 176, 150, 106, 105, 97, 110, 49, 0, 12, 3, 231, 160, 150, 122, 104, 117, 97, 110, 49, 0, 10, 3, 229, 177, 158, 115, 104, 117, 51, 0, 0, 11, 3, 231, 161, 157, 120, 105, 97, 111, 49, 0, 10, 3, 229, 190, 133, 100, 97, 105, 52, 0, 10, 3, 228, 185, 157, 106, 105, 117, 51, 0, 11, 3, 229, 179, 173, 113, 105, 97, 111, 52, 0, 10, 3, 229, 191, 141, 114, 101, 110, 51, 0, 10, 3, 233, 146, 165, 121, 97, 111, 52, 0, 0, 10, 3, 228, 184, 148, 113, 105, 101, 51, 0, 10, 3, 228, 187, 172, 109, 101, 110, 53, 0, 10, 3, 233, 159, 140, 114, 101, 110, 52, 0, 11, 3, 229, 190, 132, 106, 105, 110, 103, 52, 0, 9, 3, 232, 153, 156, 108, 117, 51, 0, 10, 3, 228, 188, 180, 98, 97, 110, 52, 0, 10, 3, 231, 160, 148, 121, 97, 110, 50, 0, 11, 3, 230, 173, 188, 106, 105, 97, 110, 49, 0, 9, 3, 229, 176, 148, 101, 114, 51, 0, 11, 3, 230, 183, 140, 116, 97, 110, 103, 51, 0, 9, 3, 229, 177, 156, 116, 105, 53, 0, 11, 3, 228, 186, 164, 106, 105, 97, 111, 49, 0, 0, 9, 3, 230, 173, 187, 115, 105, 51, 0, 11, 3, 232, 154, 163, 103, 111, 110, 103, 53, 0, 10, 3, 230, 183, 139, 108, 105, 110, 50, 0, 9, 3, 232, 153, 155, 120, 117, 49, 0, 12, 3, 228, 184, 147, 122, 104, 117, 97, 110, 49, 0, 10, 3, 230, 168, 147, 108, 111, 117, 50, 0, 0, 9, 3, 228, 187, 170, 121, 105, 50, 0, 11, 3, 233, 146, 162, 103, 97, 110, 103, 49, 0, 9, 3, 230, 172, 178, 121, 117, 52, 0, 9, 3, 230, 182, 130, 116, 117, 53, 0, 11, 3, 230, 170, 162, 106, 105, 97, 110, 51, 0, 9, 3, 232, 153, 154, 120, 117, 49, 0, 0, 9, 3, 228, 185, 153, 121, 105, 51, 0, 10, 3, 232, 166, 129, 121, 97, 111, 52, 0, 11, 3, 229, 176, 145, 115, 104, 97, 111, 51, 0, 11, 3, 228, 186, 161, 119, 97, 110, 103, 50, 0, 9, 3, 232, 152, 145, 109, 111, 50, 0, 11, 3, 228, 184, 145, 99, 104, 111, 117, 51, 0, 11, 3, 229, 178, 161, 103, 97, 110, 103, 49, 0, 10, 3, 232, 167, 137, 106, 117, 101, 50, 0, 12, 3, 229, 190, 129, 122, 104, 101, 110, 103, 49, 0, 0, 10, 3, 231, 165, 184, 104, 117, 111, 52, 0, 11, 3, 231, 174, 128, 106, 105, 97, 110, 51, 0, 10, 3, 232, 167, 136, 108, 97, 110, 51, 0, 11, 3, 229, 190, 128, 119, 97, 110, 103, 51, 0, 9, 3, 230, 169, 152, 106, 117, 50, 0, 12, 3, 228, 185, 152, 99, 104, 101, 110, 103, 50, 0, 9, 3, 232, 157, 184, 119, 111, 49, 0, 9, 3, 228, 188, 176, 103, 117, 49, 0, 10, 3, 230, 173, 184, 103, 117, 105, 49, 0, 9, 3, 231, 163, 168, 109, 111, 50, 0, 8, 3, 229, 179, 168, 101, 50, 0, 0, 11, 3, 231, 175, 135, 112, 105, 97, 110, 49, 0, 9, 3, 228, 188, 175, 98, 111, 50, 0, 10, 3, 231, 162, 159, 100, 105, 101, 50, 0, 9, 3, 230, 173, 183, 108, 105, 52, 0, 12, 3, 233, 146, 159, 122, 104, 111, 110, 103, 49, 0, 9, 3, 231, 166, 191, 116, 117, 49, 0, 11, 3, 229, 176, 143, 120, 105, 97, 111, 51, 0, 12, 3, 233, 149, 183, 99, 104, 97, 110, 103, 50, 0, 9, 3, 233, 148, 175, 106, 117, 52, 0, 11, 3, 228, 190, 191, 98, 105, 97, 110, 52, 0, 11, 3, 230, 174, 191, 100, 105, 97, 110, 52, 0, 0, 9, 3, 228, 186, 158, 121, 97, 52, 0, 10, 3, 232, 167, 134, 115, 104, 105, 52, 0, 10, 3, 229, 176, 142, 100, 97, 111, 51, 0, 10, 3, 232, 157, 182, 100, 105, 101, 50, 0, 11, 3, 233, 148, 174, 106, 105, 97, 110, 52, 0, 9, 3, 228, 184, 142, 121, 117, 51, 0, 12, 3, 233, 149, 182, 120, 105, 97, 110, 103, 49, 0, 11, 3, 229, 179, 166, 108, 117, 97, 110, 50, 0, 11, 3, 233, 146, 158, 99, 104, 97, 111, 49, 0, 9, 3, 229, 191, 134, 121, 105, 52, 0, 11, 3, 228, 185, 150, 103, 117, 97, 105, 49, 0, 0, 9, 3, 228, 184, 141, 98, 117, 52, 0, 9, 3, 228, 187, 165, 121, 105, 51, 0, 10, 3, 232, 153, 149, 99, 104, 117, 52, 0, 9, 3, 229, 191, 133, 98, 105, 52, 0, 11, 3, 233, 148, 173, 100, 105, 110, 103, 52, 0, 10, 3, 229, 176, 141, 100, 117, 105, 52, 0, 10, 3, 231, 160, 141, 107, 97, 110, 51, 0, 11, 3, 229, 177, 149, 122, 104, 97, 110, 51, 0, 11, 3, 229, 180, 173, 122, 104, 97, 110, 51, 0, 0, 9, 3, 232, 154, 156, 121, 97, 50, 0, 9, 3, 231, 160, 140, 113, 105, 52, 0, 10, 3, 232, 167, 132, 103, 117, 105, 49, 0, 9, 3, 230, 174, 188, 107, 101, 50, 0, 9, 3, 232, 157, 180, 104, 117, 50, 0, 11, 3, 228, 187, 164, 108, 105, 110, 103, 52, 0, 9, 3, 232, 155, 164, 104, 97, 50, 0, 9, 3, 229, 182, 188, 121, 117, 51, 0, 0, 10, 3, 228, 187, 163, 100, 97, 105, 52, 0, 11, 3, 232, 152, 139, 112, 105, 110, 103, 50, 0, 10, 3, 229, 191, 131, 120, 105, 110, 49, 0, 10, 3, 228, 184, 139, 120, 105, 97, 52, 0, 10, 3, 229, 178, 155, 100, 97, 111, 51, 0, 10, 3, 228, 189, 179, 106, 105, 97, 49, 0, 11, 3, 228, 185, 147, 112, 97, 110, 103, 49, 0, 9, 3, 231, 166, 187, 108, 105, 50, 0, 9, 3, 231, 164, 171, 108, 105, 52, 0, 10, 3, 229, 176, 139, 120, 117, 110, 50, 0, 10, 3, 228, 186, 155, 120, 105, 101, 49, 0, 0, 11, 3, 228, 185, 146, 112, 105, 110, 103, 49, 0, 10, 3, 228, 188, 170, 119, 101, 105, 51, 0, 11, 3, 229, 182, 186, 108, 105, 110, 103, 51, 0, 9, 3, 228, 186, 154, 121, 97, 52, 0, 10, 3, 229, 176, 138, 122, 117, 110, 49, 0, 10, 3, 230, 173, 178, 115, 117, 105, 52, 0, 10, 3, 232, 152, 138, 121, 117, 110, 52, 0, 10, 3, 230, 174, 186, 115, 104, 97, 49, 0, 11, 3, 232, 167, 130, 103, 117, 97, 110, 49, 0, 11, 3, 233, 145, 146, 106, 105, 97, 110, 52, 0, 12, 3, 228, 184, 138, 115, 104, 97, 110, 103, 52, 0, 0, 10, 3, 229, 177, 145, 120, 105, 101, 52, 0, 10, 3, 233, 146, 153, 103, 97, 105, 52, 0, 11, 3, 229, 180, 169, 98, 101, 110, 103, 49, 0, 10, 3, 228, 184, 137, 115, 97, 110, 49, 0, 11, 3, 232, 167, 129, 106, 105, 97, 110, 52, 0, 12, 3, 233, 159, 129, 106, 105, 97, 110, 103, 49, 0, 10, 3, 229, 179, 161, 120, 105, 97, 50, 0, 9, 3, 232, 153, 145, 108, 118, 52, 0, 0, 10, 3, 231, 175, 128, 106, 105, 101, 50, 0, 12, 3, 229, 176, 136, 122, 104, 117, 97, 110, 49, 0, 9, 3, 228, 185, 144, 108, 101, 52, 0, 11, 3, 230, 183, 128, 100, 105, 97, 110, 52, 0, 11, 3, 233, 149, 176, 108, 105, 97, 110, 50, 0, 12, 3, 228, 184, 136, 122, 104, 97, 110, 103, 52, 0, 11, 3, 232, 167, 128, 103, 117, 97, 110, 49, 0, 0, 13, 3, 231, 170, 151, 99, 104, 117, 97, 110, 103, 49, 0, 11, 3, 229, 186, 151, 100, 105, 97, 110, 52, 0, 11, 3, 232, 165, 175, 99, 104, 101, 110, 52, 0, 11, 3, 229, 187, 159, 109, 105, 97, 111, 52, 0, 11, 3, 231, 171, 159, 106, 105, 110, 103, 52, 0, 9, 3, 229, 190, 183, 100, 101, 50, 0, 10, 3, 229, 191, 191, 102, 101, 110, 52, 0, 12, 3, 233, 159, 191, 120, 105, 97, 110, 103, 51, 0, 9, 3, 233, 156, 167, 119, 117, 52, 0, 0, 12, 3, 230, 178, 150, 99, 104, 111, 110, 103, 49, 0, 10, 3, 229, 184, 134, 102, 97, 110, 49, 0, 9, 3, 230, 181, 174, 102, 117, 50, 0, 11, 3, 231, 169, 142, 121, 105, 110, 103, 51, 0, 10, 3, 232, 162, 150, 120, 105, 117, 52, 0, 11, 3, 229, 188, 166, 120, 105, 97, 110, 50, 0, 9, 3, 231, 172, 166, 102, 117, 50, 0, 11, 3, 231, 170, 150, 106, 105, 97, 111, 52, 0, 9, 3, 233, 155, 158, 106, 105, 49, 0, 11, 3, 231, 171, 158, 106, 105, 110, 103, 52, 0, 0, 10, 3, 232, 161, 141, 121, 97, 110, 51, 0, 13, 3, 232, 163, 157, 122, 104, 117, 97, 110, 103, 49, 0, 10, 3, 230, 180, 165, 106, 105, 110, 49, 0, 11, 3, 232, 160, 133, 121, 105, 110, 103, 53, 0, 9, 3, 229, 186, 149, 100, 105, 51, 0, 12, 3, 229, 184, 133, 115, 104, 117, 97, 105, 52, 0, 11, 3, 231, 168, 133, 115, 104, 117, 105, 52, 0, 9, 3, 229, 191, 189, 104, 117, 49, 0, 12, 3, 233, 153, 141, 106, 105, 97, 110, 103, 52, 0, 9, 3, 231, 169, 141, 106, 105, 49, 0, 10, 3, 233, 152, 133, 121, 117, 101, 52, 0, 9, 3, 229, 188, 165, 109, 105, 50, 0, 0, 11, 3, 232, 161, 140, 120, 105, 110, 103, 50, 0, 9, 3, 233, 155, 156, 122, 97, 50, 0, 9, 3, 233, 154, 148, 103, 101, 50, 0, 9, 3, 233, 153, 140, 109, 111, 52, 0, 9, 3, 232, 163, 156, 98, 117, 51, 0, 11, 3, 229, 186, 148, 121, 105, 110, 103, 49, 0, 0, 10, 3, 230, 179, 155, 102, 97, 110, 52, 0, 9, 3, 229, 186, 147, 107, 117, 52, 0, 10, 3, 233, 153, 139, 108, 111, 117, 52, 0, 11, 3, 230, 183, 187, 116, 105, 97, 110, 49, 0, 9, 3, 229, 184, 131, 98, 117, 52, 0, 0, 10, 3, 229, 187, 154, 99, 104, 117, 50, 0, 9, 3, 232, 165, 170, 119, 97, 52, 0, 10, 3, 230, 178, 146, 109, 101, 105, 50, 0, 11, 3, 230, 181, 170, 108, 97, 110, 103, 52, 0, 10, 3, 229, 184, 130, 115, 104, 105, 52, 0, 9, 3, 230, 182, 178, 121, 101, 52, 0, 11, 3, 230, 183, 186, 113, 105, 97, 110, 51, 0, 0, 10, 3, 232, 163, 153, 113, 117, 110, 50, 0, 9, 3, 233, 157, 169, 103, 101, 50, 0, 10, 3, 230, 183, 185, 121, 97, 110, 49, 0, 10, 3, 229, 189, 169, 99, 97, 105, 51, 0, 13, 3, 233, 155, 153, 115, 104, 117, 97, 110, 103, 49, 0, 10, 3, 230, 177, 137, 104, 97, 110, 52, 0, 12, 3, 231, 174, 177, 120, 105, 97, 110, 103, 49, 0, 10, 3, 231, 170, 145, 121, 97, 111, 50, 0, 9, 3, 229, 184, 129, 98, 105, 52, 0, 10, 3, 230, 181, 169, 104, 97, 111, 52, 0, 11, 3, 231, 171, 153, 122, 104, 97, 110, 52, 0, 0, 9, 3, 233, 152, 128, 102, 97, 50, 0, 10, 3, 232, 167, 184, 99, 104, 117, 52, 0, 9, 3, 231, 168, 128, 120, 105, 49, 0, 10, 3, 233, 154, 144, 121, 105, 110, 51, 0, 11, 3, 233, 153, 136, 99, 104, 101, 110, 50, 0, 12, 3, 229, 188, 160, 122, 104, 97, 110, 103, 49, 0, 0, 9, 3, 230, 178, 143, 113, 105, 49, 0, 9, 3, 229, 188, 159, 100, 105, 52, 0, 11, 3, 231, 175, 183, 112, 101, 110, 103, 53, 0, 11, 3, 229, 176, 191, 110, 105, 97, 111, 52, 0, 9, 3, 229, 186, 143, 120, 117, 52, 0, 10, 3, 230, 183, 183, 104, 117, 110, 52, 0, 10, 3, 232, 152, 191, 108, 117, 111, 50, 0, 10, 3, 230, 177, 135, 104, 117, 105, 52, 0, 10, 3, 233, 154, 143, 115, 117, 105, 50, 0, 0, 10, 3, 233, 155, 150, 115, 117, 105, 49, 0, 10, 3, 231, 171, 150, 115, 104, 117, 52, 0, 9, 3, 228, 184, 190, 106, 117, 51, 0, 10, 3, 229, 190, 174, 119, 101, 105, 49, 0, 10, 3, 233, 154, 142, 106, 105, 101, 49, 0, 11, 3, 230, 180, 158, 100, 111, 110, 103, 52, 0, 10, 3, 233, 156, 158, 120, 105, 97, 50, 0, 9, 3, 233, 153, 134, 108, 117, 52, 0, 9, 3, 231, 160, 190, 108, 105, 52, 0, 9, 3, 231, 169, 134, 109, 117, 52, 0, 10, 3, 229, 176, 190, 119, 101, 105, 51, 0, 0, 10, 3, 232, 162, 141, 112, 97, 111, 50, 0, 11, 3, 229, 191, 181, 110, 105, 97, 110, 52, 0, 9, 3, 228, 184, 189, 108, 105, 52, 0, 9, 3, 233, 153, 133, 106, 105, 52, 0, 9, 3, 229, 185, 133, 102, 117, 50, 0, 11, 3, 233, 155, 149, 100, 105, 97, 111, 49, 0, 11, 3, 233, 158, 173, 98, 105, 97, 110, 49, 0, 9, 3, 230, 179, 149, 102, 97, 51, 0, 10, 3, 229, 176, 189, 106, 105, 110, 52, 0, 10, 3, 232, 161, 133, 120, 105, 110, 52, 0, 11, 3, 231, 174, 173, 106, 105, 97, 110, 52, 0, 9, 3, 232, 163, 149, 121, 117, 52, 0, 0, 9, 3, 233, 153, 132, 102, 117, 52, 0, 13, 3, 233, 156, 156, 115, 104, 117, 97, 110, 103, 49, 0, 0, 10, 3, 228, 184, 187, 122, 104, 117, 51, 0, 10, 3, 233, 159, 179, 121, 105, 110, 49, 0, 10, 3, 229, 187, 147, 107, 117, 111, 52, 0, 10, 3, 232, 162, 139, 100, 97, 105, 52, 0, 11, 3, 231, 174, 171, 120, 105, 97, 111, 49, 0, 9, 3, 231, 172, 155, 100, 105, 50, 0, 11, 3, 230, 183, 179, 99, 104, 117, 110, 50, 0, 0, 10, 3, 229, 176, 186, 99, 104, 105, 51, 0, 11, 3, 233, 157, 162, 109, 105, 97, 110, 52, 0, 10, 3, 233, 154, 138, 100, 117, 105, 52, 0, 13, 3, 229, 186, 138, 99, 104, 117, 97, 110, 103, 50, 0, 10, 3, 232, 166, 170, 113, 105, 110, 49, 0, 11, 3, 229, 189, 162, 120, 105, 110, 103, 50, 0, 11, 3, 233, 144, 186, 100, 97, 110, 103, 53, 0, 10, 3, 230, 168, 186, 104, 117, 97, 52, 0, 10, 3, 229, 190, 170, 120, 117, 110, 50, 0, 10, 3, 228, 184, 186, 119, 101, 105, 52, 0, 10, 3, 230, 177, 130, 113, 105, 117, 50, 0, 0, 10, 3, 230, 177, 129, 122, 104, 105, 49, 0, 10, 3, 231, 174, 169, 108, 117, 111, 50, 0, 9, 3, 231, 175, 177, 108, 105, 50, 0, 11, 3, 229, 191, 177, 99, 104, 101, 110, 50, 0, 10, 3, 228, 184, 185, 100, 97, 110, 49, 0, 10, 3, 230, 168, 185, 115, 104, 117, 52, 0, 11, 3, 230, 178, 137, 99, 104, 101, 110, 50, 0, 11, 3, 230, 183, 177, 115, 104, 101, 110, 49, 0, 0, 10, 3, 233, 157, 160, 107, 97, 111, 52, 0, 9, 3, 231, 160, 184, 122, 97, 50, 0, 12, 3, 230, 182, 168, 122, 104, 97, 110, 103, 51, 0, 10, 3, 229, 176, 184, 115, 104, 105, 49, 0, 10, 3, 232, 161, 128, 120, 117, 101, 52, 0, 11, 3, 232, 152, 184, 122, 104, 97, 110, 52, 0, 10, 3, 228, 184, 184, 119, 97, 110, 50, 0, 0, 9, 3, 230, 180, 151, 120, 105, 51, 0, 9, 3, 229, 177, 191, 121, 117, 51, 0, 10, 3, 233, 145, 191, 122, 97, 111, 50, 0, 10, 3, 232, 165, 159, 106, 105, 110, 49, 0, 0, 10, 3, 232, 153, 190, 120, 105, 97, 49, 0, 10, 3, 231, 175, 174, 108, 97, 110, 50, 0, 10, 3, 230, 182, 166, 114, 117, 110, 52, 0, 11, 3, 229, 186, 134, 113, 105, 110, 103, 52, 0, 10, 3, 233, 157, 158, 102, 101, 105, 49, 0, 11, 3, 233, 154, 134, 108, 111, 110, 103, 50, 0, 0, 11, 3, 233, 145, 189, 122, 117, 97, 110, 49, 0, 10, 3, 233, 144, 181, 116, 105, 101, 51, 0, 10, 3, 232, 153, 189, 115, 117, 105, 49, 0, 10, 3, 229, 188, 149, 121, 105, 110, 51, 0, 0, 9, 3, 232, 162, 132, 97, 111, 51, 0, 10, 3, 228, 184, 180, 108, 105, 110, 50, 0, 9, 3, 231, 172, 148, 98, 105, 51, 0, 9, 3, 233, 155, 140, 99, 105, 50, 0, 9, 3, 230, 179, 140, 109, 105, 52, 0, 9, 3, 231, 160, 180, 112, 111, 52, 0, 10, 3, 233, 145, 188, 108, 117, 111, 50, 0, 9, 3, 230, 182, 164, 100, 105, 50, 0, 11, 3, 231, 170, 132, 122, 104, 97, 105, 51, 0, 11, 3, 233, 157, 156, 106, 105, 110, 103, 52, 0, 13, 3, 229, 186, 132, 122, 104, 117, 97, 110, 103, 49, 0, 0, 11, 3, 229, 188, 147, 103, 111, 110, 103, 49, 0, 10, 3, 231, 170, 131, 113, 105, 101, 52, 0, 11, 3, 231, 173, 155, 115, 104, 97, 105, 49, 0, 9, 3, 231, 171, 139, 108, 105, 52, 0, 9, 3, 230, 178, 131, 119, 111, 52, 0, 11, 3, 229, 191, 171, 107, 117, 97, 105, 52, 0, 0, 12, 3, 228, 184, 178, 99, 104, 117, 97, 110, 52, 0, 9, 3, 230, 180, 146, 115, 97, 51, 0, 10, 3, 231, 171, 138, 113, 105, 101, 52, 0, 9, 3, 230, 179, 138, 112, 111, 49, 0, 0, 9, 3, 230, 182, 161, 119, 111, 49, 0, 11, 3, 231, 172, 145, 120, 105, 97, 111, 52, 0, 11, 3, 233, 157, 153, 106, 105, 110, 103, 52, 0, 11, 3, 231, 175, 169, 115, 104, 97, 105, 49, 0, 10, 3, 229, 176, 177, 106, 105, 117, 52, 0, 11, 3, 230, 179, 137, 113, 117, 97, 110, 50, 0, 11, 3, 231, 174, 161, 103, 117, 97, 110, 51, 0, 9, 3, 229, 190, 161, 121, 117, 52, 0, 9, 3, 231, 170, 129, 116, 117, 49, 0, 9, 3, 229, 177, 185, 121, 105, 52, 0, 11, 3, 229, 187, 137, 108, 105, 97, 110, 50, 0, 0, 9, 3, 233, 158, 160, 106, 117, 49, 0, 11, 3, 230, 183, 168, 106, 105, 110, 103, 52, 0, 10, 3, 229, 187, 136, 115, 104, 97, 52, 0, 9, 3, 232, 164, 144, 104, 101, 52, 0, 11, 3, 228, 184, 176, 102, 101, 110, 103, 49, 0, 11, 3, 231, 160, 176, 112, 101, 110, 103, 49, 0, 0, 10, 3, 229, 191, 167, 121, 111, 117, 49, 0, 10, 3, 233, 159, 167, 114, 101, 110, 52, 0, 10, 3, 229, 188, 143, 115, 104, 105, 52, 0, 9, 3, 228, 186, 191, 121, 105, 52, 0, 9, 3, 233, 155, 135, 103, 117, 52, 0, 0, 9, 3, 231, 173, 150, 99, 101, 52, 0, 11, 3, 229, 190, 158, 99, 111, 110, 103, 50, 0, 10, 3, 232, 167, 166, 99, 104, 117, 52, 0, 10, 3, 233, 156, 142, 115, 104, 97, 52, 0, 11, 3, 231, 162, 190, 110, 105, 97, 110, 51, 0, 11, 3, 233, 144, 174, 108, 105, 97, 110, 50, 0, 9, 3, 233, 155, 134, 106, 105, 50, 0, 9, 3, 232, 165, 150, 97, 111, 51, 0, 0, 12, 3, 228, 184, 173, 122, 104, 111, 110, 103, 49, 0, 9, 3, 229, 189, 149, 108, 117, 52, 0, 13, 3, 232, 163, 133, 122, 104, 117, 97, 110, 103, 49, 0, 0, 10, 3, 230, 179, 132, 120, 105, 101, 52, 0, 9, 3, 231, 173, 148, 100, 97, 50, 0, 9, 3, 231, 162, 188, 109, 97, 51, 0, 11, 3, 231, 171, 132, 99, 117, 97, 110, 52, 0, 12, 3, 233, 155, 132, 120, 105, 111, 110, 103, 50, 0, 0, 9, 3, 228, 184, 171, 121, 97, 49, 0, 11, 3, 233, 146, 187, 122, 117, 97, 110, 49, 0, 11, 3, 230, 180, 139, 121, 97, 110, 103, 50, 0, 9, 3, 228, 185, 179, 114, 117, 51, 0, 11, 3, 230, 181, 147, 110, 111, 110, 103, 50, 0, 10, 3, 232, 167, 163, 106, 105, 101, 51, 0, 10, 3, 230, 182, 155, 116, 97, 111, 49, 0, 10, 3, 230, 170, 187, 107, 97, 110, 51, 0, 11, 3, 229, 189, 147, 100, 97, 110, 103, 49, 0, 0, 10, 3, 232, 163, 130, 108, 105, 101, 52, 0, 11, 3, 233, 157, 146, 113, 105, 110, 103, 49, 0, 10, 3, 229, 189, 146, 103, 117, 105, 49, 0, 11, 3, 231, 173, 146, 116, 111, 110, 103, 51, 0, 10, 3, 228, 186, 186, 114, 101, 110, 50, 0, 12, 3, 233, 145, 178, 120, 105, 97, 110, 103, 49, 0, 12, 3, 229, 187, 130, 120, 105, 97, 110, 103, 49, 0, 9, 3, 228, 184, 170, 103, 101, 53, 0, 10, 3, 231, 162, 186, 113, 117, 101, 52, 0, 11, 3, 230, 168, 170, 104, 101, 110, 103, 50, 0, 0, 10, 3, 230, 183, 161, 100, 97, 110, 52, 0, 11, 3, 229, 177, 177, 115, 104, 97, 110, 49, 0, 10, 3, 230, 181, 145, 104, 117, 110, 50, 0, 9, 3, 229, 187, 129, 99, 101, 52, 0, 10, 3, 232, 163, 129, 99, 97, 105, 50, 0, 11, 3, 228, 185, 177, 108, 117, 97, 110, 52, 0, 10, 3, 231, 173, 145, 122, 104, 117, 52, 0, 10, 3, 233, 156, 137, 109, 101, 105, 50, 0, 12, 3, 230, 179, 129, 107, 117, 97, 110, 103, 52, 0, 0, 10, 3, 228, 185, 176, 109, 97, 105, 51, 0, 12, 3, 229, 191, 160, 122, 104, 111, 110, 103, 49, 0, 10, 3, 233, 155, 128, 113, 117, 101, 52, 0, 12, 3, 231, 173, 144, 107, 117, 97, 110, 103, 49, 0, 9, 3, 229, 178, 184, 97, 110, 52, 0, 10, 3, 233, 145, 176, 121, 97, 111, 52, 0, 10, 3, 229, 190, 152, 112, 97, 105, 50, 0, 0, 11, 3, 229, 186, 183, 107, 97, 110, 103, 49, 0, 9, 3, 232, 173, 143, 106, 105, 49, 0, 10, 3, 231, 171, 191, 103, 97, 110, 49, 0, 11, 3, 229, 187, 191, 110, 105, 97, 110, 52, 0, 9, 3, 230, 191, 159, 106, 105, 52, 0, 11, 3, 230, 176, 167, 121, 97, 110, 103, 51, 0, 0, 11, 3, 233, 166, 150, 115, 104, 111, 117, 51, 0, 10, 3, 229, 184, 166, 100, 97, 105, 52, 0, 9, 3, 230, 188, 134, 113, 105, 49, 0, 10, 3, 232, 175, 158, 100, 97, 110, 52, 0, 11, 3, 231, 183, 158, 100, 117, 97, 110, 52, 0, 9, 3, 233, 155, 190, 119, 117, 52, 0, 9, 3, 233, 154, 182, 108, 105, 52, 0, 0, 10, 3, 233, 167, 157, 116, 117, 111, 53, 0, 11, 3, 233, 164, 133, 98, 105, 110, 103, 51, 0, 9, 3, 231, 171, 189, 121, 117, 50, 0, 11, 3, 231, 180, 133, 104, 111, 110, 103, 50, 0, 10, 3, 232, 175, 157, 104, 117, 97, 52, 0, 12, 3, 229, 184, 165, 115, 104, 117, 97, 105, 52, 0, 0, 11, 3, 232, 161, 172, 99, 104, 101, 110, 52, 0, 9, 3, 230, 179, 188, 112, 111, 53, 0, 10, 3, 231, 180, 132, 121, 117, 101, 49, 0, 0, 9, 3, 230, 176, 163, 113, 105, 52, 0, 11, 3, 231, 182, 147, 106, 105, 110, 103, 49, 0, 10, 3, 233, 167, 155, 115, 104, 105, 51, 0, 11, 3, 232, 161, 171, 115, 104, 97, 110, 49, 0, 11, 3, 233, 164, 131, 106, 105, 97, 111, 51, 0, 11, 3, 229, 185, 171, 98, 97, 110, 103, 49, 0, 11, 3, 233, 155, 187, 100, 105, 97, 110, 52, 0, 11, 3, 232, 174, 147, 114, 97, 110, 103, 52, 0, 9, 3, 230, 178, 179, 104, 101, 50, 0, 0, 11, 3, 229, 187, 186, 106, 105, 97, 110, 52, 0, 11, 3, 230, 177, 170, 119, 97, 110, 103, 49, 0, 12, 3, 232, 175, 154, 99, 104, 101, 110, 103, 50, 0, 11, 3, 230, 188, 130, 112, 105, 97, 111, 52, 0, 11, 3, 231, 183, 154, 120, 105, 97, 110, 52, 0, 10, 3, 233, 153, 170, 112, 101, 105, 50, 0, 10, 3, 232, 172, 130, 119, 101, 105, 52, 0, 11, 3, 230, 176, 162, 113, 105, 110, 103, 49, 0, 10, 3, 233, 166, 146, 109, 97, 110, 50, 0, 0, 9, 3, 230, 188, 129, 121, 117, 50, 0, 10, 3, 231, 169, 169, 119, 101, 110, 51, 0, 10, 3, 233, 154, 177, 121, 105, 110, 51, 0, 11, 3, 233, 153, 169, 120, 105, 97, 110, 51, 0, 10, 3, 232, 163, 185, 103, 117, 111, 51, 0, 10, 3, 231, 171, 185, 122, 104, 117, 50, 0, 9, 3, 232, 162, 177, 102, 117, 53, 0, 10, 3, 233, 155, 185, 98, 97, 111, 50, 0, 0, 9, 3, 231, 180, 128, 106, 105, 52, 0, 11, 3, 231, 168, 160, 99, 104, 111, 117, 50, 0, 11, 3, 232, 161, 168, 98, 105, 97, 111, 51, 0, 10, 3, 232, 172, 128, 109, 111, 117, 50, 0, 0, 9, 3, 232, 160, 159, 108, 97, 52, 0, 10, 3, 232, 175, 151, 115, 104, 105, 49, 0, 10, 3, 233, 155, 183, 108, 101, 105, 50, 0, 10, 3, 231, 170, 175, 121, 97, 111, 50, 0, 10, 3, 233, 152, 159, 100, 117, 105, 52, 0, 0, 10, 3, 230, 180, 190, 112, 97, 105, 52, 0, 12, 3, 231, 170, 174, 113, 105, 111, 110, 103, 50, 0, 11, 3, 233, 155, 182, 108, 105, 110, 103, 50, 0, 11, 3, 230, 190, 142, 112, 101, 110, 103, 49, 0, 10, 3, 229, 187, 182, 121, 97, 110, 50, 0, 11, 3, 231, 171, 182, 106, 105, 110, 103, 52, 0, 0, 10, 3, 232, 175, 149, 115, 104, 105, 52, 0, 9, 3, 229, 184, 157, 100, 105, 52, 0, 11, 3, 230, 179, 181, 98, 101, 110, 103, 52, 0, 10, 3, 230, 191, 149, 115, 104, 105, 49, 0, 9, 3, 232, 162, 173, 120, 105, 50, 0, 10, 3, 233, 165, 133, 109, 97, 110, 50, 0, 11, 3, 229, 186, 173, 116, 105, 110, 103, 50, 0, 10, 3, 233, 167, 149, 106, 105, 97, 52, 0, 9, 3, 232, 161, 165, 98, 117, 51, 0, 0, 11, 3, 230, 177, 164, 116, 97, 110, 103, 49, 0, 10, 3, 229, 184, 156, 122, 104, 105, 52, 0, 10, 3, 233, 153, 164, 99, 104, 117, 50, 0, 11, 3, 231, 172, 188, 108, 111, 110, 103, 50, 0, 9, 3, 231, 181, 132, 122, 117, 51, 0, 0, 10, 3, 232, 162, 171, 98, 101, 105, 52, 0, 11, 3, 229, 187, 179, 116, 105, 110, 103, 49, 0, 9, 3, 232, 161, 163, 121, 105, 49, 0, 9, 3, 230, 178, 171, 109, 111, 52, 0, 10, 3, 230, 176, 155, 102, 101, 110, 49, 0, 9, 3, 229, 185, 163, 98, 105, 52, 0, 11, 3, 230, 179, 179, 121, 111, 110, 103, 51, 0, 11, 3, 233, 153, 163, 122, 104, 101, 110, 52, 0, 10, 3, 230, 180, 187, 104, 117, 111, 50, 0, 12, 3, 232, 163, 179, 115, 104, 97, 110, 103, 53, 0, 9, 3, 229, 186, 171, 107, 117, 52, 0, 11, 3, 233, 166, 139, 99, 104, 97, 110, 50, 0, 0, 11, 3, 233, 154, 170, 120, 105, 97, 110, 51, 0, 11, 3, 233, 153, 162, 121, 117, 97, 110, 52, 0, 9, 3, 231, 183, 146, 120, 117, 52, 0, 9, 3, 233, 167, 146, 106, 117, 49, 0, 12, 3, 231, 181, 130, 122, 104, 111, 110, 103, 49, 0, 12, 3, 229, 188, 186, 113, 105, 97, 110, 103, 50, 0, 11, 3, 229, 184, 154, 122, 104, 111, 117, 53, 0, 10, 3, 231, 168, 154, 122, 104, 105, 52, 0, 11, 3, 232, 174, 138, 98, 105, 97, 110, 52, 0, 0, 9, 3, 230, 177, 161, 119, 117, 49, 0, 11, 3, 232, 161, 161, 104, 101, 110, 103, 50, 0, 10, 3, 229, 188, 185, 100, 97, 110, 52, 0, 9, 3, 231, 170, 169, 119, 111, 49, 0, 9, 3, 232, 175, 145, 121, 105, 52, 0, 10, 3, 233, 153, 161, 100, 111, 117, 51, 0, 0, 9, 3, 233, 156, 184, 98, 97, 52, 0, 10, 3, 230, 177, 160, 99, 104, 105, 50, 0, 11, 3, 229, 184, 152, 108, 105, 97, 110, 50, 0, 10, 3, 233, 154, 168, 115, 117, 105, 50, 0, 10, 3, 233, 167, 144, 122, 104, 117, 52, 0, 0, 9, 3, 232, 165, 191, 120, 105, 53, 0, 10, 3, 229, 186, 167, 122, 117, 111, 52, 0, 10, 3, 233, 154, 167, 115, 117, 105, 52, 0, 11, 3, 231, 171, 175, 100, 117, 97, 110, 49, 0, 12, 3, 230, 177, 159, 106, 105, 97, 110, 103, 49, 0, 12, 3, 229, 188, 183, 113, 105, 97, 110, 103, 50, 0, 10, 3, 229, 185, 159, 122, 104, 105, 52, 0, 0, 11, 3, 233, 166, 134, 103, 117, 97, 110, 51, 0, 12, 3, 230, 180, 182, 120, 105, 111, 110, 103, 49, 0, 9, 3, 229, 186, 166, 100, 117, 52, 0, 11, 3, 231, 173, 190, 113, 105, 97, 110, 49, 0, 11, 3, 230, 190, 134, 106, 105, 97, 111, 49, 0, 11, 3, 230, 177, 158, 103, 111, 110, 103, 51, 0, 0, 11, 3, 233, 166, 133, 120, 105, 97, 110, 52, 0, 10, 3, 231, 171, 173, 106, 105, 101, 50, 0, 9, 3, 232, 160, 149, 114, 117, 50, 0, 9, 3, 230, 178, 165, 108, 105, 52, 0, 9, 3, 229, 184, 149, 112, 97, 52, 0, 9, 3, 232, 175, 141, 99, 105, 50, 0, 12, 3, 229, 188, 181, 122, 104, 97, 110, 103, 49, 0, 0, 10, 3, 233, 152, 148, 107, 117, 111, 52, 0, 9, 3, 230, 176, 148, 113, 105, 52, 0, 9, 3, 229, 189, 188, 98, 105, 51, 0, 0, 10, 3, 229, 189, 187, 99, 104, 101, 52, 0, 11, 3, 230, 176, 147, 109, 97, 110, 103, 50, 0, 10, 3, 230, 177, 155, 120, 117, 110, 52, 0, 10, 3, 232, 161, 155, 119, 101, 105, 52, 0, 0, 9, 3, 233, 156, 178, 108, 117, 52, 0, 10, 3, 231, 183, 138, 106, 105, 110, 51, 0, 10, 3, 233, 155, 170, 120, 117, 101, 51, 0, 10, 3, 230, 179, 170, 108, 101, 105, 52, 0, 9, 3, 232, 164, 178, 107, 117, 52, 0, 11, 3, 230, 180, 178, 122, 104, 111, 117, 49, 0, 11, 3, 232, 175, 138, 122, 104, 101, 110, 51, 0, 0, 10, 3, 229, 188, 177, 114, 117, 111, 52, 0, 10, 3, 230, 176, 145, 109, 105, 110, 50, 0, 9, 3, 232, 175, 137, 115, 117, 53, 0, 11, 3, 231, 182, 129, 98, 97, 110, 103, 51, 0, 9, 3, 229, 189, 185, 121, 105, 52, 0, 10, 3, 230, 178, 161, 109, 101, 105, 50, 0, 9, 3, 232, 161, 153, 121, 97, 50, 0, 0, 9, 3, 232, 174, 128, 100, 117, 50, 0, 9, 3, 233, 155, 168, 121, 117, 51, 0, 11, 3, 233, 152, 144, 99, 104, 97, 110, 51, 0, 10, 3, 230, 181, 184, 106, 105, 110, 52, 0, 12, 3, 229, 184, 144, 122, 104, 97, 110, 103, 52, 0, 10, 3, 230, 179, 168, 122, 104, 117, 52, 0, 0, 10, 3, 229, 188, 175, 119, 97, 110, 49, 0, 10, 3, 230, 178, 159, 103, 111, 117, 49, 0, 11, 3, 231, 173, 183, 107, 117, 97, 105, 52, 0, 10, 3, 231, 169, 151, 115, 117, 105, 52, 0, 10, 3, 232, 161, 151, 106, 105, 101, 49, 0, 9, 3, 231, 170, 159, 107, 117, 49, 0, 10, 3, 230, 176, 143, 115, 104, 105, 52, 0, 10, 3, 229, 186, 159, 102, 101, 105, 52, 0, 10, 3, 230, 181, 183, 104, 97, 105, 51, 0, 10, 3, 230, 177, 151, 104, 97, 110, 52, 0, 0, 11, 3, 229, 186, 158, 112, 97, 110, 103, 50, 0, 10, 3, 232, 175, 134, 115, 104, 105, 53, 0, 11, 3, 231, 168, 142, 115, 104, 117, 105, 52, 0, 0, 11, 3, 231, 168, 141, 115, 104, 97, 111, 49, 0, 10, 3, 232, 166, 189, 108, 97, 110, 51, 0, 11, 3, 231, 171, 165, 116, 111, 110, 103, 50, 0, 9, 3, 229, 185, 149, 109, 117, 52, 0, 9, 3, 231, 170, 157, 119, 111, 49, 0, 9, 3, 230, 179, 165, 110, 105, 50, 0, 0, 12, 3, 233, 154, 156, 122, 104, 97, 110, 103, 52, 0, 9, 3, 232, 163, 164, 107, 117, 52, 0, 10, 3, 233, 157, 180, 120, 117, 101, 49, 0, 9, 3, 229, 186, 156, 102, 117, 51, 0, 11, 3, 231, 170, 156, 99, 117, 97, 110, 52, 0, 9, 3, 232, 162, 156, 119, 97, 52, 0, 9, 3, 229, 184, 140, 120, 105, 49, 0, 11, 3, 232, 175, 132, 112, 105, 110, 103, 50, 0, 12, 3, 230, 182, 188, 108, 105, 97, 110, 103, 50, 0, 11, 3, 232, 161, 148, 120, 105, 97, 110, 50, 0, 9, 3, 231, 172, 172, 100, 105, 52, 0, 0, 12, 3, 229, 187, 163, 103, 117, 97, 110, 103, 51, 0, 11, 3, 230, 191, 131, 110, 111, 110, 103, 50, 0, 10, 3, 230, 178, 155, 112, 101, 105, 52, 0, 10, 3, 233, 155, 163, 110, 97, 110, 50, 0, 12, 3, 231, 168, 139, 99, 104, 101, 110, 103, 50, 0, 9, 3, 233, 154, 155, 106, 105, 52, 0, 9, 3, 230, 179, 163, 113, 105, 52, 0, 0, 9, 3, 230, 179, 162, 98, 111, 49, 0, 10, 3, 232, 166, 186, 106, 117, 101, 50, 0, 9, 3, 232, 165, 178, 120, 105, 50, 0, 10, 3, 229, 187, 162, 102, 101, 105, 52, 0, 11, 3, 230, 180, 170, 104, 111, 110, 103, 50, 0, 9, 3, 233, 155, 162, 108, 105, 50, 0, 0, 10, 3, 229, 190, 185, 99, 104, 101, 52, 0, 10, 3, 230, 178, 153, 115, 104, 97, 49, 0, 9, 3, 233, 167, 129, 98, 111, 50, 0, 9, 3, 232, 163, 161, 108, 105, 53, 0, 11, 3, 230, 191, 129, 122, 104, 117, 111, 50, 0, 9, 3, 233, 154, 153, 120, 105, 52, 0, 11, 3, 229, 186, 153, 109, 105, 97, 111, 52, 0, 12, 3, 232, 175, 129, 122, 104, 101, 110, 103, 52, 0, 10, 3, 230, 179, 161, 112, 97, 111, 52, 0, 11, 3, 229, 189, 177, 121, 105, 110, 103, 51, 0, 0, 11, 3, 233, 153, 144, 120, 105, 97, 110, 52, 0, 9, 3, 230, 191, 128, 106, 105, 49, 0, 10, 3, 231, 172, 168, 98, 101, 110, 52, 0, 11, 3, 230, 176, 136, 122, 104, 97, 110, 49, 0, 10, 3, 231, 168, 136, 103, 97, 110, 51, 0, 9, 3, 233, 154, 152, 97, 105, 52, 0, 10, 3, 229, 184, 136, 115, 104, 105, 49, 0, 12, 3, 231, 171, 160, 122, 104, 97, 110, 103, 49, 0, 12, 3, 229, 187, 160, 99, 104, 97, 110, 103, 51, 0, 0, 10, 3, 231, 180, 167, 106, 105, 110, 51, 0, 10, 3, 233, 161, 143, 121, 97, 110, 50, 0, 9, 3, 231, 176, 135, 99, 117, 52, 0, 9, 3, 231, 178, 151, 99, 117, 49, 0, 10, 3, 233, 163, 159, 115, 104, 105, 50, 0, 9, 3, 232, 173, 175, 121, 105, 52, 0, 9, 3, 233, 162, 151, 107, 101, 49, 0, 10, 3, 231, 179, 159, 122, 97, 111, 49, 0, 0, 10, 3, 233, 163, 158, 102, 101, 105, 49, 0, 10, 3, 233, 165, 174, 121, 105, 110, 51, 0, 10, 3, 231, 179, 158, 102, 101, 110, 52, 0, 11, 3, 233, 162, 150, 121, 105, 110, 103, 51, 0, 9, 3, 232, 175, 190, 107, 101, 52, 0, 9, 3, 232, 174, 182, 121, 97, 52, 0, 11, 3, 230, 189, 174, 99, 104, 97, 111, 50, 0, 11, 3, 233, 160, 134, 115, 104, 117, 110, 52, 0, 0, 10, 3, 232, 170, 149, 100, 97, 110, 52, 0, 10, 3, 230, 189, 173, 116, 97, 110, 50, 0, 8, 3, 233, 161, 141, 101, 50, 0, 9, 3, 231, 177, 141, 106, 105, 50, 0, 12, 3, 233, 160, 133, 120, 105, 97, 110, 103, 52, 0, 11, 3, 230, 184, 133, 113, 105, 110, 103, 49, 0, 10, 3, 233, 165, 173, 102, 97, 110, 52, 0, 0, 11, 3, 231, 182, 180, 122, 104, 117, 105, 53, 0, 9, 3, 233, 161, 140, 116, 105, 50, 0, 9, 3, 232, 173, 172, 112, 105, 52, 0, 0, 11, 3, 233, 160, 131, 113, 105, 110, 103, 51, 0, 10, 3, 232, 170, 147, 115, 104, 105, 52, 0, 10, 3, 233, 166, 179, 99, 104, 105, 50, 0, 10, 3, 233, 163, 155, 102, 101, 105, 49, 0, 9, 3, 232, 175, 187, 100, 117, 50, 0, 0, 10, 3, 230, 187, 154, 103, 117, 110, 51, 0, 11, 3, 232, 168, 130, 100, 105, 110, 103, 52, 0, 10, 3, 231, 180, 162, 115, 117, 111, 51, 0, 9, 3, 231, 178, 146, 108, 105, 52, 0, 11, 3, 230, 191, 186, 106, 105, 97, 110, 52, 0, 12, 3, 232, 174, 178, 106, 105, 97, 110, 103, 51, 0, 11, 3, 233, 160, 130, 100, 105, 110, 103, 51, 0, 10, 3, 230, 185, 138, 99, 111, 117, 52, 0, 11, 3, 231, 182, 178, 119, 97, 110, 103, 51, 0, 10, 3, 230, 188, 162, 104, 97, 110, 52, 0, 9, 3, 232, 170, 146, 101, 105, 50, 0, 0, 11, 3, 231, 182, 177, 103, 97, 110, 103, 49, 0, 9, 3, 233, 160, 129, 121, 101, 52, 0, 10, 3, 233, 162, 145, 112, 105, 110, 50, 0, 10, 3, 233, 166, 177, 116, 117, 111, 50, 0, 10, 3, 231, 179, 153, 99, 97, 111, 49, 0, 11, 3, 230, 190, 177, 100, 105, 97, 110, 52, 0, 11, 3, 231, 180, 161, 102, 97, 110, 103, 51, 0, 11, 3, 233, 164, 161, 120, 105, 97, 110, 52, 0, 0, 9, 3, 231, 180, 160, 115, 117, 52, 0, 11, 3, 230, 186, 144, 121, 117, 97, 110, 50, 0, 10, 3, 232, 168, 128, 121, 97, 110, 50, 0, 11, 3, 231, 181, 168, 114, 111, 110, 103, 50, 0, 9, 3, 232, 174, 176, 106, 105, 52, 0, 9, 3, 230, 188, 160, 109, 111, 52, 0, 11, 3, 233, 163, 152, 112, 105, 97, 111, 49, 0, 10, 3, 232, 175, 184, 122, 104, 117, 49, 0, 10, 3, 232, 172, 160, 121, 97, 111, 50, 0, 0, 11, 3, 232, 175, 183, 113, 105, 110, 103, 51, 0, 10, 3, 232, 174, 175, 120, 117, 110, 52, 0, 8, 3, 233, 152, 191, 97, 49, 0, 10, 3, 231, 168, 191, 103, 97, 111, 51, 0, 0, 9, 3, 232, 174, 174, 121, 105, 52, 0, 9, 3, 233, 161, 134, 107, 101, 49, 0, 10, 3, 232, 171, 150, 108, 117, 110, 52, 0, 11, 3, 232, 173, 166, 106, 105, 110, 103, 51, 0, 10, 3, 231, 181, 166, 103, 101, 105, 51, 0, 11, 3, 231, 179, 150, 116, 97, 110, 103, 50, 0, 9, 3, 232, 175, 182, 101, 105, 50, 0, 0, 10, 3, 232, 172, 157, 120, 105, 101, 52, 0, 10, 3, 229, 184, 189, 109, 97, 111, 52, 0, 10, 3, 231, 182, 173, 119, 101, 105, 50, 0, 9, 3, 233, 165, 165, 106, 105, 49, 0, 11, 3, 232, 175, 181, 115, 111, 110, 103, 52, 0, 10, 3, 232, 170, 141, 114, 101, 110, 52, 0, 10, 3, 232, 174, 173, 120, 117, 110, 52, 0, 10, 3, 231, 179, 149, 103, 97, 111, 49, 0, 0, 10, 3, 230, 189, 164, 114, 117, 110, 52, 0, 11, 3, 231, 183, 180, 108, 105, 97, 110, 52, 0, 11, 3, 232, 175, 180, 115, 104, 117, 111, 49, 0, 10, 3, 230, 187, 148, 116, 97, 111, 49, 0, 10, 3, 231, 168, 188, 106, 105, 97, 53, 0, 9, 3, 233, 166, 172, 109, 97, 51, 0, 0, 10, 3, 231, 168, 187, 100, 97, 111, 52, 0, 10, 3, 231, 177, 131, 108, 97, 110, 50, 0, 12, 3, 232, 172, 155, 106, 105, 97, 110, 103, 51, 0, 9, 3, 233, 152, 187, 122, 117, 51, 0, 10, 3, 230, 185, 131, 112, 97, 105, 52, 0, 10, 3, 231, 180, 155, 102, 101, 110, 49, 0, 0, 12, 3, 232, 171, 146, 108, 105, 97, 110, 103, 52, 0, 9, 3, 231, 180, 154, 106, 105, 50, 0, 10, 3, 233, 162, 138, 106, 105, 97, 50, 0, 11, 3, 231, 181, 162, 120, 117, 97, 110, 52, 0, 0, 10, 3, 231, 180, 153, 122, 104, 105, 51, 0, 10, 3, 230, 186, 137, 103, 97, 105, 52, 0, 10, 3, 232, 175, 177, 121, 111, 117, 52, 0, 9, 3, 232, 170, 137, 121, 117, 52, 0, 10, 3, 230, 191, 177, 98, 105, 110, 49, 0, 10, 3, 231, 181, 161, 108, 117, 111, 52, 0, 10, 3, 230, 187, 145, 104, 117, 97, 50, 0, 11, 3, 232, 174, 169, 114, 97, 110, 103, 52, 0, 10, 3, 231, 178, 137, 102, 101, 110, 51, 0, 10, 3, 233, 167, 177, 108, 117, 111, 52, 0, 11, 3, 232, 172, 153, 113, 105, 97, 110, 49, 0, 0, 11, 3, 233, 162, 136, 106, 105, 110, 103, 51, 0, 11, 3, 230, 176, 184, 121, 111, 110, 103, 51, 0, 10, 3, 232, 174, 168, 116, 97, 111, 51, 0, 12, 3, 229, 184, 184, 99, 104, 97, 110, 103, 50, 0, 0, 10, 3, 231, 180, 151, 115, 104, 97, 49, 0, 10, 3, 231, 183, 175, 119, 101, 105, 51, 0, 12, 3, 231, 169, 191, 99, 104, 117, 97, 110, 49, 0, 12, 3, 229, 185, 191, 103, 117, 97, 110, 103, 51, 0, 9, 3, 232, 175, 175, 119, 117, 52, 0, 9, 3, 233, 162, 135, 112, 111, 49, 0, 0, 10, 3, 232, 160, 182, 99, 97, 110, 50, 0, 11, 3, 233, 165, 158, 99, 104, 97, 110, 50, 0, 9, 3, 229, 185, 190, 106, 105, 51, 0, 11, 3, 233, 162, 134, 108, 105, 110, 103, 51, 0, 10, 3, 233, 152, 182, 106, 105, 101, 49, 0, 11, 3, 233, 163, 142, 102, 101, 110, 103, 49, 0, 10, 3, 229, 184, 182, 100, 97, 105, 52, 0, 0, 9, 3, 232, 174, 165, 106, 105, 49, 0, 9, 3, 230, 177, 189, 113, 105, 52, 0, 11, 3, 230, 186, 133, 106, 105, 97, 110, 52, 0, 11, 3, 233, 153, 189, 121, 97, 110, 103, 50, 0, 11, 3, 233, 152, 181, 122, 104, 101, 110, 52, 0, 9, 3, 232, 175, 173, 121, 117, 51, 0, 0, 9, 3, 232, 175, 172, 119, 117, 49, 0, 9, 3, 233, 162, 132, 121, 117, 52, 0, 9, 3, 230, 187, 140, 100, 105, 50, 0, 10, 3, 232, 174, 164, 114, 101, 110, 52, 0, 10, 3, 230, 188, 148, 121, 97, 110, 51, 0, 10, 3, 229, 185, 188, 121, 111, 117, 52, 0, 10, 3, 233, 152, 180, 121, 105, 110, 49, 0, 11, 3, 230, 189, 156, 113, 105, 97, 110, 50, 0, 11, 3, 230, 176, 180, 115, 104, 117, 105, 51, 0, 11, 3, 231, 180, 148, 99, 104, 117, 110, 50, 0, 0, 10, 3, 230, 186, 131, 107, 117, 105, 52, 0, 11, 3, 230, 189, 155, 113, 105, 97, 110, 50, 0, 9, 3, 230, 187, 139, 122, 105, 49, 0, 12, 3, 229, 184, 179, 122, 104, 97, 110, 103, 52, 0, 10, 3, 231, 168, 179, 119, 101, 110, 51, 0, 10, 3, 232, 175, 171, 106, 105, 101, 52, 0, 8, 3, 233, 164, 147, 101, 52, 0, 11, 3, 229, 185, 187, 104, 117, 97, 110, 52, 0, 11, 3, 233, 152, 179, 121, 97, 110, 103, 50, 0, 10, 3, 230, 191, 171, 108, 97, 110, 52, 0, 11, 3, 232, 171, 139, 113, 105, 110, 103, 51, 0, 0, 11, 3, 233, 162, 130, 115, 111, 110, 103, 52, 0, 10, 3, 230, 177, 186, 106, 117, 101, 50, 0, 11, 3, 232, 174, 162, 100, 105, 110, 103, 52, 0, 11, 3, 233, 152, 178, 102, 97, 110, 103, 50, 0, 11, 3, 231, 182, 162, 99, 104, 111, 117, 50, 0, 11, 3, 231, 169, 186, 107, 111, 110, 103, 49, 0, 9, 3, 231, 179, 138, 104, 117, 53, 0, 0, 10, 3, 233, 162, 129, 98, 97, 110, 49, 0, 10, 3, 230, 190, 161, 122, 97, 111, 51, 0, 12, 3, 230, 177, 185, 120, 105, 111, 110, 103, 49, 0, 11, 3, 231, 183, 169, 104, 117, 97, 110, 51, 0, 9, 3, 232, 174, 161, 106, 105, 52, 0, 12, 3, 231, 168, 177, 99, 104, 101, 110, 103, 49, 0, 0, 10, 3, 231, 180, 144, 110, 105, 117, 51, 0, 11, 3, 231, 183, 168, 98, 105, 97, 110, 49, 0, 10, 3, 233, 164, 144, 99, 97, 110, 49, 0, 11, 3, 229, 185, 184, 120, 105, 110, 103, 52, 0, 10, 3, 232, 173, 152, 115, 104, 105, 53, 0, 9, 3, 233, 153, 184, 108, 117, 52, 0, 9, 3, 231, 182, 160, 108, 118, 52, 0, 0, 12, 3, 231, 169, 183, 113, 105, 111, 110, 103, 50, 0, 10, 3, 230, 178, 191, 121, 97, 110, 50, 0, 10, 3, 232, 175, 167, 99, 104, 97, 52, 0, 10, 3, 230, 188, 143, 108, 111, 117, 52, 0, 11, 3, 233, 153, 183, 120, 105, 97, 110, 52, 0, 11, 3, 231, 170, 191, 108, 111, 110, 103, 53, 0, 10, 3, 232, 171, 135, 116, 97, 110, 50, 0, 0, 12, 3, 231, 168, 174, 122, 104, 111, 110, 103, 51, 0, 11, 3, 229, 184, 174, 98, 97, 110, 103, 49, 0, 10, 3, 233, 154, 190, 110, 97, 110, 50, 0, 10, 3, 233, 153, 182, 116, 97, 111, 50, 0, 11, 3, 230, 178, 190, 122, 104, 97, 110, 49, 0, 10, 3, 230, 176, 174, 100, 97, 110, 52, 0, 11, 3, 229, 185, 182, 98, 105, 110, 103, 52, 0, 12, 3, 232, 175, 166, 120, 105, 97, 110, 103, 50, 0, 10, 3, 231, 169, 182, 106, 105, 117, 49, 0, 0, 10, 3, 232, 175, 165, 103, 97, 105, 49, 0, 10, 3, 231, 181, 149, 106, 117, 101, 50, 0, 11, 3, 233, 153, 181, 108, 105, 110, 103, 50, 0, 9, 3, 229, 184, 173, 120, 105, 50, 0, 10, 3, 230, 187, 133, 109, 105, 101, 52, 0, 9, 3, 231, 180, 141, 110, 97, 52, 0, 0, 11, 3, 231, 182, 156, 122, 111, 110, 103, 49, 0, 11, 3, 233, 163, 132, 112, 105, 97, 111, 49, 0, 10, 3, 230, 189, 148, 106, 105, 101, 50, 0, 11, 3, 229, 185, 180, 110, 105, 97, 110, 50, 0, 10, 3, 230, 191, 164, 116, 97, 111, 49, 0, 0, 10, 3, 229, 184, 171, 115, 104, 105, 49, 0, 11, 3, 233, 153, 179, 99, 104, 101, 110, 50, 0, 10, 3, 231, 180, 139, 119, 101, 110, 50, 0, 11, 3, 229, 185, 179, 112, 105, 110, 103, 50, 0, 10, 3, 230, 178, 187, 122, 104, 105, 52, 0, 11, 3, 230, 176, 171, 113, 105, 110, 103, 49, 0, 11, 3, 231, 183, 163, 121, 117, 97, 110, 50, 0, 0, 6, 20, 201, 2, 0, 0, 49, 0, 0, 0, 202, 2, 0, 0, 50, 0, 0, 0, 199, 2, 0, 0, 51, 0, 0, 0, 203, 2, 0, 0, 52, 0, 0, 0, 1, 1, 0, 0, 97, 0, 49, 0, 225, 0, 0, 0, 97, 0, 50, 0, 3, 1, 0, 0, 97, 0, 51, 0, 206, 1, 0, 0, 97, 0, 51, 0, 224, 0, 0, 0, 97, 0, 52, 0, 77, 1, 0, 0, 111, 0, 49, 0, 243, 0, 0, 0, 111, 0, 50, 0, 79, 1, 0, 0, 111, 0, 51, 0, 210, 1, 0, 0, 111, 0, 51, 0, 242, 0, 0, 0, 111, 0, 52, 0, 234, 0, 0, 0, 101, 0, 97, 0, 19, 1, 0, 0, 101, 0, 49, 0, 233, 0, 0, 0, 101, 0, 50, 0, 21, 1, 0, 0, 101, 0, 51, 0, 27, 1, 0, 0, 101, 0, 51, 0, 232, 0, 0, 0, 101, 0, 52, 0, 43, 1, 0, 0, 105, 0, 49, 0, 237, 0, 0, 0, 105, 0, 50, 0, 45, 1, 0, 0, 105, 0, 51, 0, 208, 1, 0, 0, 105, 0, 51, 0, 236, 0, 0, 0, 105, 0, 52, 0, 107, 1, 0, 0, 117, 0, 49, 0, 250, 0, 0, 0, 117, 0, 50, 0, 212, 1, 0, 0, 117, 0, 51, 0, 249, 0, 0, 0, 117, 0, 52, 0, 214, 1, 0, 0, 252, 0, 49, 0, 216, 1, 0, 0, 252, 0, 50, 0, 109, 1, 0, 0, 117, 0, 51, 0, 218, 1, 0, 0, 252, 0, 51, 0, 220, 1, 0, 0, 252, 0, 52, 0, 75, 1, 0, 0, 110, 0, 103, 0, 81, 2, 0, 0, 97, 0, 0, 0, 97, 2, 0, 0, 103, 0, 0, 0, 145, 30, 0, 0, 122, 0, 104, 0, 9, 1, 0, 0, 99, 0, 104, 0, 93, 1, 0, 0, 115, 0, 104, 0, 0, 0, 0, 0, 6, 18, 66, 106, 0, 113, 0, 120, 0, 121, 0, 7, 6, 195, 188, 0, 3, 146, 0, 101, 3, 149, 0, 7, 6, 97, 0, 4, 1, 104, 99, 2, 52, 110, 103, 25, 3, 35, 0, 1, 104, 99, 2, 110, 103, 52, 25, 0, 2, 15, 110, 25, 0, 4, 3, 124, 0, 1, 104, 99, 2, 15, 110, 103, 25, 0, 1, 107, 2, 15, 110, 103, 25, 0, 8, 2, 15, 110, 103, 25, 0, 105, 3, 125, 0, 51, 105, 3, 125, 108, 0, 50, 105, 3, 125, 111, 0, 52, 105, 3, 125, 113, 0, 49, 105, 3, 125, 115, 0, 4, 111, 3, 126, 0, 111, 1, 121, 0, 4, 51, 111, 3, 126, 108, 0, 51, 111, 1, 121, 0, 4, 50, 111, 3, 126, 111, 0, 50, 111, 1, 121, 0, 4, 52, 111, 3, 126, 113, 0, 52, 111, 1, 121, 0, 4, 49, 111, 3, 126, 115, 0, 49, 111, 1, 121, 0, 4, 1, 121, 3, 132, 0, 1, 121, 2, 15, 110, 103, 25, 0, 1, 121, 2, 15, 110, 25, 3, 134, 0, 7, 6, 98, 0, 1, 21, 2, 25, 3, 21, 0, 3, 48, 0, 7, 6, 99, 0, 1, 21, 2, 25, 3, 21, 0, 3, 121, 0, 104, 2, 12, 3, 123, 0, 7, 6, 100, 0, 1, 21, 2, 25, 3, 21, 0, 3, 47, 0, 7, 6, 101, 0, 4, 1, 100, 3, 13, 0, 1, 108, 0, 1, 110, 0, 1, 116, 0, 2, 15, 110, 0, 114, 2, 25, 3, 127, 0, 51, 114, 2, 25, 3, 127, 108, 0, 50, 114, 2, 25, 3, 127, 111, 0, 52, 114, 2, 25, 3, 127, 113, 0, 49, 114, 2, 25, 3, 127, 115, 0, 97, 3, 128, 0, 105, 3, 129, 0, 51, 105, 3, 129, 108, 0, 50, 105, 3, 129, 111, 0, 52, 105, 3, 129, 113, 0, 49, 105, 3, 129, 115, 0, 1, 121, 3, 134, 0, 3, 137, 0, 7, 6, 102, 0, 1, 21, 2, 25, 3, 21, 0, 3, 81, 0, 7, 6, 103, 0, 1, 21, 2, 25, 3, 21, 0, 3, 49, 0, 7, 6, 104, 0, 1, 21, 2, 25, 3, 21, 0, 3, 99, 0, 7, 6, 105, 0, 3, 37, 0, 111, 1, 113, 2, 15, 110, 103, 25, 3, 40, 0, 97, 111, 3, 57, 126, 0, 97, 51, 111, 3, 57, 126, 108, 0, 97, 50, 111, 3, 57, 126, 111, 0, 97, 52, 111, 3, 57, 126, 113, 0, 97, 49, 111, 3, 57, 126, 115, 0, 4, 1, 99, 3, 130, 0, 1, 115, 0, 1, 122, 0, 4, 1, 104, 3, 131, 0, 1, 114, 0, 4, 97, 3, 132, 0, 97, 2, 15, 110, 103, 25, 0, 4, 97, 2, 15, 110, 25, 3, 134, 0, 101, 0, 117, 3, 136, 0, 111, 2, 15, 110, 103, 25, 3, 146, 0, 7, 6, 106, 0, 1, 21, 2, 25, 3, 21, 0, 3, 76, 0, 7, 6, 107, 0, 1, 21, 2, 25, 3, 21, 0, 3, 118, 0, 7, 6, 108, 0, 1, 21, 2, 25, 3, 21, 0, 4, 3, 55, 0, 1, 21, 2, 118, 0, 7, 6, 109, 0, 1, 21, 2, 25, 3, 21, 0, 3, 63, 0, 7, 6, 110, 0, 103, 8, 2, 25, 3, 43, 0, 3, 50, 0, 103, 2, 25, 3, 66, 0, 7, 6, 111, 0, 3, 39, 0, 1, 121, 3, 135, 0, 117, 1, 121, 3, 136, 0, 51, 117, 1, 121, 3, 136, 108, 0, 50, 117, 1, 121, 3, 136, 111, 0, 52, 117, 1, 121, 3, 136, 113, 0, 49, 117, 1, 121, 3, 136, 115, 0, 117, 3, 138, 0, 51, 117, 3, 138, 108, 0, 50, 117, 3, 138, 111, 0, 52, 117, 3, 138, 113, 0, 49, 117, 3, 138, 115, 0, 110, 103, 2, 25, 3, 139, 0, 51, 110, 103, 2, 25, 3, 139, 108, 0, 50, 110, 103, 2, 25, 3, 139, 111, 0, 52, 110, 103, 2, 25, 3, 139, 113, 0, 49, 110, 103, 2, 25, 3, 139, 115, 0, 7, 6, 112, 0, 1, 21, 2, 25, 3, 21, 0, 3, 116, 0, 7, 6, 113, 0, 1, 21, 2, 25, 3, 21, 0, 3, 119, 0, 7, 6, 114, 0, 3, 90, 0, 2, 25, 3, 127, 106, 0, 7, 6, 115, 0, 1, 21, 2, 25, 3, 21, 0, 3, 87, 0, 104, 2, 12, 3, 91, 0, 7, 6, 116, 0, 1, 21, 2, 25, 3, 21, 0, 3, 117, 0, 7, 6, 117, 0, 105, 1, 104, 115, 3, 34, 129, 0, 3, 40, 0, 4, 97, 1, 103, 2, 15, 110, 25, 3, 58, 35, 0, 97, 1, 107, 2, 15, 110, 25, 0, 111, 1, 104, 115, 3, 58, 39, 0, 4, 97, 3, 58, 124, 0, 97, 2, 15, 110, 103, 25, 0, 105, 1, 104, 115, 3, 58, 129, 0, 1, 104, 115, 2, 15, 110, 25, 3, 58, 137, 0, 4, 1, 107, 2, 15, 110, 25, 3, 58, 143, 0, 1, 116, 2, 15, 110, 25, 0, 8, 104, 2, 15, 110, 25, 0, 97, 2, 15, 110, 25, 3, 141, 0, 97, 105, 3, 142, 0, 97, 51, 105, 3, 142, 108, 0, 97, 50, 105, 3, 142, 111, 0, 97, 52, 105, 3, 142, 113, 0, 97, 49, 105, 3, 142, 115, 0, 2, 15, 110, 25, 3, 143, 0, 105, 3, 144, 0, 111, 3, 145, 0, 1, 18, 66, 3, 146, 0, 97, 1, 18, 66, 2, 15, 110, 25, 3, 148, 0, 4, 101, 3, 149, 0, 101, 1, 18, 66, 0, 1, 18, 66, 2, 15, 110, 25, 3, 150, 0, 1, 113, 2, 15, 110, 25, 12, 3, 151, 0, 7, 6, 118, 0, 3, 82, 0, 4, 1, 108, 3, 146, 0, 1, 110, 0, 4, 101, 1, 108, 3, 149, 0, 101, 1, 110, 0, 7, 6, 119, 0, 1, 21, 2, 25, 3, 21, 0, 111, 3, 58, 39, 0, 117, 3, 58, 40, 0, 97, 3, 58, 124, 0, 97, 105, 3, 58, 125, 0, 97, 51, 105, 3, 58, 125, 108, 0, 97, 50, 105, 3, 58, 125, 111, 0, 97, 52, 105, 3, 58, 125, 113, 0, 97, 49, 105, 3, 58, 125, 115, 0, 101, 105, 3, 58, 129, 0, 101, 51, 105, 3, 58, 129, 108, 0, 101, 50, 105, 3, 58, 129, 111, 0, 101, 52, 105, 3, 58, 129, 113, 0, 101, 49, 105, 3, 58, 129, 115, 0, 101, 3, 58, 143, 0, 7, 6, 120, 0, 1, 21, 2, 25, 3, 21, 0, 3, 95, 0, 7, 6, 121, 0, 2, 117, 3, 0, 1, 21, 2, 25, 3, 21, 0, 2, 25, 3, 37, 0, 4, 2, 117, 15, 110, 3, 38, 0, 2, 117, 25, 0, 3, 57, 0, 111, 2, 15, 110, 103, 25, 3, 147, 0, 7, 6, 122, 0, 1, 21, 2, 25, 3, 21, 0, 3, 120, 0, 104, 2, 12, 3, 122, 0, 7, 6, 0, 124, 3, 23, 0, 53, 3, 106, 0, 51, 3, 108, 0, 50, 3, 111, 0, 52, 3, 113, 0, 49, 3, 115, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts65 = FileInMemory_createWithData (41827, reinterpret_cast (&espeakdata_dicts65_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/zh_dict", L"zh"); Collection_addItem (me.peek(), espeakdata_dicts65.transfer()); static unsigned char espeakdata_dicts66_data[1557] = { 0, 4, 0, 0, 8, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 97, 0, 5, 1, 3, 21, 0, 5, 2, 3, 35, 0, 97, 5, 2, 3, 112, 0, 97, 105, 5, 2, 3, 113, 0, 97, 117, 5, 2, 3, 114, 0, 97, 110, 103, 5, 2, 3, 116, 0, 105, 5, 2, 3, 117, 0, 117, 5, 2, 3, 118, 0, 7, 6, 98, 0, 5, 1, 3, 21, 0, 5, 2, 3, 69, 0, 7, 6, 99, 0, 5, 1, 3, 21, 0, 104, 5, 2, 3, 74, 0, 5, 2, 3, 78, 0, 7, 6, 100, 0, 5, 1, 3, 21, 0, 5, 2, 3, 70, 0, 7, 6, 101, 0, 5, 1, 3, 21, 0, 5, 2, 3, 36, 0, 105, 5, 2, 3, 119, 0, 117, 5, 2, 3, 121, 0, 111, 5, 2, 3, 132, 0, 111, 105, 5, 2, 3, 133, 0, 7, 6, 102, 0, 5, 1, 3, 21, 0, 5, 2, 3, 81, 0, 7, 6, 103, 0, 5, 1, 3, 21, 0, 5, 2, 3, 79, 0, 7, 6, 104, 0, 5, 1, 3, 21, 0, 5, 2, 3, 105, 0, 7, 6, 105, 0, 5, 1, 3, 21, 0, 5, 2, 3, 37, 0, 117, 5, 2, 3, 123, 0, 7, 6, 106, 0, 5, 1, 3, 21, 0, 5, 2, 3, 57, 0, 7, 6, 107, 0, 5, 1, 3, 21, 0, 5, 2, 3, 49, 0, 7, 6, 108, 0, 5, 1, 3, 21, 0, 5, 2, 3, 55, 0, 7, 6, 109, 0, 5, 1, 3, 21, 0, 5, 2, 3, 63, 0, 7, 6, 110, 0, 5, 1, 3, 21, 0, 5, 2, 3, 50, 0, 103, 5, 2, 3, 66, 0, 7, 6, 111, 0, 5, 1, 3, 21, 0, 5, 2, 3, 39, 0, 105, 5, 2, 3, 126, 0, 117, 5, 2, 3, 127, 0, 110, 103, 5, 2, 3, 128, 0, 101, 5, 2, 3, 131, 0, 7, 6, 112, 0, 5, 1, 3, 21, 0, 5, 2, 3, 48, 0, 7, 6, 113, 0, 5, 1, 3, 21, 0, 5, 2, 3, 49, 0, 117, 5, 2, 3, 49, 58, 0, 7, 6, 114, 0, 5, 1, 3, 21, 0, 5, 2, 3, 34, 0, 7, 6, 115, 0, 5, 1, 3, 21, 0, 5, 2, 3, 87, 0, 7, 6, 116, 0, 5, 1, 3, 21, 0, 5, 2, 3, 47, 0, 7, 6, 117, 0, 5, 1, 3, 21, 0, 5, 2, 3, 40, 0, 105, 5, 2, 3, 130, 0, 7, 6, 118, 0, 5, 1, 3, 21, 0, 5, 2, 3, 82, 0, 7, 6, 119, 0, 5, 1, 3, 21, 0, 5, 2, 3, 58, 0, 7, 6, 120, 0, 5, 1, 3, 21, 0, 5, 2, 3, 49, 87, 0, 7, 6, 121, 0, 5, 1, 3, 21, 0, 5, 2, 3, 57, 0, 117, 5, 2, 3, 134, 0, 7, 6, 122, 0, 5, 1, 3, 21, 0, 5, 2, 3, 86, 0, 7, 6, 0, 49, 3, 17, 0, 50, 3, 106, 0, 51, 3, 107, 0, 52, 3, 108, 0, 53, 3, 109, 0, 54, 3, 110, 0, 55, 3, 111, 0, 7, 0, 0}; autoFileInMemory espeakdata_dicts66 = FileInMemory_createWithData (1556, reinterpret_cast (&espeakdata_dicts66_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/zhy_dict", L"zhy"); Collection_addItem (me.peek(), espeakdata_dicts66.transfer()); return me.transfer(); } catch (MelderError) { Melder_throw (L"FilesInMemory not created."); } } sources_5316/external/espeak/numbers.cpp0000644000176700017670000013544111721443315017205 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2011 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" #define M_NAME 0 #define M_SMALLCAP 1 #define M_TURNED 2 #define M_REVERSED 3 #define M_CURL 4 #define M_ACUTE 5 #define M_BREVE 6 #define M_CARON 7 #define M_CEDILLA 8 #define M_CIRCUMFLEX 9 #define M_DIAERESIS 10 #define M_DOUBLE_ACUTE 11 #define M_DOT_ABOVE 12 #define M_GRAVE 13 #define M_MACRON 14 #define M_OGONEK 15 #define M_RING 16 #define M_STROKE 17 #define M_TILDE 18 #define M_BAR 19 #define M_RETROFLEX 20 #define M_HOOK 21 #define M_MIDDLE_DOT M_DOT_ABOVE // duplicate of M_DOT_ABOVE #define M_IMPLOSIVE M_HOOK static int n_digit_lookup; static char *digit_lookup; static int speak_missing_thousands; static int number_control; typedef struct { const char *name; int flags; } ACCENTS; // these are tokens to look up in the *_list file. static ACCENTS accents_tab[] = { {"_lig", 1}, {"_smc", 1}, // smallcap {"_tur", 1}, // turned {"_rev", 1}, // reversed {"_crl", 0}, // curl {"_acu", 0}, // acute {"_brv", 0}, // breve {"_hac", 0}, // caron/hacek {"_ced", 0}, // cedilla {"_cir", 0}, // circumflex {"_dia", 0}, // diaeresis {"_ac2", 0}, // double acute {"_dot", 0}, // dot {"_grv", 0}, // grave {"_mcn", 0}, // macron {"_ogo", 0}, // ogonek {"_rng", 0}, // ring {"_stk", 0}, // stroke {"_tld", 0}, // tilde {"_bar", 0}, // bar {"_rfx", 0}, // retroflex {"_hok", 0}, // hook }; #define CAPITAL 0 #define LETTER(ch,mod1,mod2) (ch-59)+(mod1 << 6)+(mod2 << 11) #define LIGATURE(ch1,ch2,mod1) (ch1-59)+((ch2-59) << 6)+(mod1 << 12)+0x8000 #define L_ALPHA 60 // U+3B1 #define L_SCHWA 61 // U+259 #define L_OPEN_E 62 // U+25B #define L_GAMMA 63 // U+3B3 #define L_IOTA 64 // U+3B9 #define L_OE 65 // U+153 #define L_OMEGA 66 // U+3C9 #define L_PHI 67 // U+3C6 #define L_ESH 68 // U+283 #define L_UPSILON 69 // U+3C5 #define L_EZH 70 // U+292 #define L_GLOTTAL 71 // U+294 #define L_RTAP 72 // U+27E static const short non_ascii_tab[] = { 0, 0x3b1, 0x259, 0x25b, 0x3b3, 0x3b9, 0x153, 0x3c9, 0x3c6, 0x283, 0x3c5, 0x292, 0x294, 0x27e }; // characters U+00e0 to U+017f static const unsigned short letter_accents_0e0[] = { LETTER('a',M_GRAVE,0), // U+00e0 LETTER('a',M_ACUTE,0), LETTER('a',M_CIRCUMFLEX,0), LETTER('a',M_TILDE,0), LETTER('a',M_DIAERESIS,0), LETTER('a',M_RING,0), LIGATURE('a','e',0), LETTER('c',M_CEDILLA,0), LETTER('e',M_GRAVE,0), LETTER('e',M_ACUTE,0), LETTER('e',M_CIRCUMFLEX,0), LETTER('e',M_DIAERESIS,0), LETTER('i',M_GRAVE,0), LETTER('i',M_ACUTE,0), LETTER('i',M_CIRCUMFLEX,0), LETTER('i',M_DIAERESIS,0), LETTER('d',M_NAME,0), // eth // U+00f0 LETTER('n',M_TILDE,0), LETTER('o',M_GRAVE,0), LETTER('o',M_ACUTE,0), LETTER('o',M_CIRCUMFLEX,0), LETTER('o',M_TILDE,0), LETTER('o',M_DIAERESIS,0), 0, // division sign LETTER('o',M_STROKE,0), LETTER('u',M_GRAVE,0), LETTER('u',M_ACUTE,0), LETTER('u',M_CIRCUMFLEX,0), LETTER('u',M_DIAERESIS,0), LETTER('y',M_ACUTE,0), LETTER('t',M_NAME,0), // thorn LETTER('y',M_DIAERESIS,0), CAPITAL, // U+0100 LETTER('a',M_MACRON,0), CAPITAL, LETTER('a',M_BREVE,0), CAPITAL, LETTER('a',M_OGONEK,0), CAPITAL, LETTER('c',M_ACUTE,0), CAPITAL, LETTER('c',M_CIRCUMFLEX,0), CAPITAL, LETTER('c',M_DOT_ABOVE,0), CAPITAL, LETTER('c',M_CARON,0), CAPITAL, LETTER('d',M_CARON,0), CAPITAL, // U+0110 LETTER('d',M_STROKE,0), CAPITAL, LETTER('e',M_MACRON,0), CAPITAL, LETTER('e',M_BREVE,0), CAPITAL, LETTER('e',M_DOT_ABOVE,0), CAPITAL, LETTER('e',M_OGONEK,0), CAPITAL, LETTER('e',M_CARON,0), CAPITAL, LETTER('g',M_CIRCUMFLEX,0), CAPITAL, LETTER('g',M_BREVE,0), CAPITAL, // U+0120 LETTER('g',M_DOT_ABOVE,0), CAPITAL, LETTER('g',M_CEDILLA,0), CAPITAL, LETTER('h',M_CIRCUMFLEX,0), CAPITAL, LETTER('h',M_STROKE,0), CAPITAL, LETTER('i',M_TILDE,0), CAPITAL, LETTER('i',M_MACRON,0), CAPITAL, LETTER('i',M_BREVE,0), CAPITAL, LETTER('i',M_OGONEK,0), CAPITAL, // U+0130 LETTER('i',M_NAME,0), // dotless i CAPITAL, LIGATURE('i','j',0), CAPITAL, LETTER('j',M_CIRCUMFLEX,0), CAPITAL, LETTER('k',M_CEDILLA,0), LETTER('k',M_NAME,0), // kra CAPITAL, LETTER('l',M_ACUTE,0), CAPITAL, LETTER('l',M_CEDILLA,0), CAPITAL, LETTER('l',M_CARON,0), CAPITAL, LETTER('l',M_MIDDLE_DOT,0), // U+0140 CAPITAL, LETTER('l',M_STROKE,0), CAPITAL, LETTER('n',M_ACUTE,0), CAPITAL, LETTER('n',M_CEDILLA,0), CAPITAL, LETTER('n',M_CARON,0), LETTER('n',M_NAME,0), // apostrophe n CAPITAL, LETTER('n',M_NAME,0), // eng CAPITAL, LETTER('o',M_MACRON,0), CAPITAL, LETTER('o',M_BREVE,0), CAPITAL, // U+0150 LETTER('o',M_DOUBLE_ACUTE,0), CAPITAL, LIGATURE('o','e',0), CAPITAL, LETTER('r',M_ACUTE,0), CAPITAL, LETTER('r',M_CEDILLA,0), CAPITAL, LETTER('r',M_CARON,0), CAPITAL, LETTER('s',M_ACUTE,0), CAPITAL, LETTER('s',M_CIRCUMFLEX,0), CAPITAL, LETTER('s',M_CEDILLA,0), CAPITAL, // U+0160 LETTER('s',M_CARON,0), CAPITAL, LETTER('t',M_CEDILLA,0), CAPITAL, LETTER('t',M_CARON,0), CAPITAL, LETTER('t',M_STROKE,0), CAPITAL, LETTER('u',M_TILDE,0), CAPITAL, LETTER('u',M_MACRON,0), CAPITAL, LETTER('u',M_BREVE,0), CAPITAL, LETTER('u',M_RING,0), CAPITAL, // U+0170 LETTER('u',M_DOUBLE_ACUTE,0), CAPITAL, LETTER('u',M_OGONEK,0), CAPITAL, LETTER('w',M_CIRCUMFLEX,0), CAPITAL, LETTER('y',M_CIRCUMFLEX,0), CAPITAL, // Y-DIAERESIS CAPITAL, LETTER('z',M_ACUTE,0), CAPITAL, LETTER('z',M_DOT_ABOVE,0), CAPITAL, LETTER('z',M_CARON,0), LETTER('s',M_NAME,0), // long-s // U+17f }; // characters U+0250 to U+029F static const unsigned short letter_accents_250[] = { LETTER('a',M_TURNED,0), // U+250 LETTER(L_ALPHA,0,0), LETTER(L_ALPHA,M_TURNED,0), LETTER('b',M_IMPLOSIVE,0), 0, // open-o LETTER('c',M_CURL,0), LETTER('d',M_RETROFLEX,0), LETTER('d',M_IMPLOSIVE,0), LETTER('e',M_REVERSED,0), // U+258 0, // schwa LETTER(L_SCHWA,M_HOOK,0), 0, // open-e LETTER(L_OPEN_E,M_REVERSED,0), LETTER(L_OPEN_E,M_HOOK,M_REVERSED), 0,//LETTER(L_OPEN_E,M_CLOSED,M_REVERSED), LETTER('j',M_BAR,0), LETTER('g',M_IMPLOSIVE,0), // U+260 LETTER('g',0,0), LETTER('g',M_SMALLCAP,0), LETTER(L_GAMMA,0,0), 0, // ramshorn LETTER('h',M_TURNED,0), LETTER('h',M_HOOK,0), 0,//LETTER(L_HENG,M_HOOK,0), LETTER('i',M_BAR,0), // U+268 LETTER(L_IOTA,0,0), LETTER('i',M_SMALLCAP,0), LETTER('l',M_TILDE,0), LETTER('l',M_BAR,0), LETTER('l',M_RETROFLEX,0), LIGATURE('l','z',0), LETTER('m',M_TURNED,0), 0,//LETTER('m',M_TURNED,M_LEG), // U+270 LETTER('m',M_HOOK,0), 0,//LETTER('n',M_LEFTHOOK,0), LETTER('n',M_RETROFLEX,0), LETTER('n',M_SMALLCAP,0), LETTER('o',M_BAR,0), LIGATURE('o','e',M_SMALLCAP), 0,//LETTER(L_OMEGA,M_CLOSED,0), LETTER(L_PHI,0,0), // U+278 LETTER('r',M_TURNED,0), 0,//LETTER('r',M_TURNED,M_LEG), LETTER('r',M_RETROFLEX,M_TURNED), 0,//LETTER('r',M_LEG,0), LETTER('r',M_RETROFLEX,0), 0, // r-tap LETTER(L_RTAP,M_REVERSED,0), LETTER('r',M_SMALLCAP,0), // U+280 LETTER('r',M_TURNED,M_SMALLCAP), LETTER('s',M_RETROFLEX,0), 0, // esh 0,//LETTER('j',M_BAR,L_IMPLOSIVE), LETTER(L_ESH,M_REVERSED,0), LETTER(L_ESH,M_CURL,0), LETTER('t',M_TURNED,0), LETTER('t',M_RETROFLEX,0), // U+288 LETTER('u',M_BAR,0), LETTER(L_UPSILON,0,0), LETTER('v',M_HOOK,0), LETTER('v',M_TURNED,0), LETTER('w',M_TURNED,0), LETTER('y',M_TURNED,0), LETTER('y',M_SMALLCAP,0), LETTER('z',M_RETROFLEX,0), // U+290 LETTER('z',M_CURL,0), 0, // ezh LETTER(L_EZH,M_CURL,0), 0, // glottal stop LETTER(L_GLOTTAL,M_REVERSED,0), LETTER(L_GLOTTAL,M_TURNED,0), 0,//LETTER('c',M_LONG,0), 0, // bilabial click // U+298 LETTER('b',M_SMALLCAP,0), 0,//LETTER(L_OPEN_E,M_CLOSED,0), LETTER('g',M_IMPLOSIVE,M_SMALLCAP), LETTER('h',M_SMALLCAP,0), LETTER('j',M_CURL,0), LETTER('k',M_TURNED,0), LETTER('l',M_SMALLCAP,0), LETTER('q',M_HOOK,0), // U+2a0 LETTER(L_GLOTTAL,M_STROKE,0), LETTER(L_GLOTTAL,M_STROKE,M_REVERSED), LIGATURE('d','z',0), 0, // dezh LIGATURE('d','z',M_CURL), LIGATURE('t','s',0), 0, // tesh LIGATURE('t','s',M_CURL), }; static int LookupLetter2(Translator *tr, unsigned int letter, char *ph_buf) {//======================================================================== int len; char single_letter[10]; single_letter[0] = 0; single_letter[1] = '_'; len = utf8_out(letter, &single_letter[2]); single_letter[len+2] = ' '; single_letter[len+3] = 0; if(Lookup(tr, &single_letter[1], ph_buf) == 0) { single_letter[1] = ' '; if(Lookup(tr, &single_letter[2], ph_buf) == 0) { TranslateRules(tr, &single_letter[2], ph_buf, 20, NULL,0,NULL); } } return(ph_buf[0]); } void LookupAccentedLetter(Translator *tr, unsigned int letter, char *ph_buf) {//========================================================================= // lookup the character in the accents table int accent_data = 0; int accent1 = 0; int accent2 = 0; int basic_letter; int letter2=0; char ph_letter1[30]; char ph_letter2[30]; char ph_accent1[30]; char ph_accent2[30]; ph_accent2[0] = 0; if((letter >= 0xe0) && (letter < 0x17f)) { accent_data = letter_accents_0e0[letter - 0xe0]; } else if((letter >= 0x250) && (letter <= 0x2a8)) { accent_data = letter_accents_250[letter - 0x250]; } if(accent_data != 0) { basic_letter = (accent_data & 0x3f) + 59; if(basic_letter < 'a') basic_letter = non_ascii_tab[basic_letter-59]; if(accent_data & 0x8000) { letter2 = (accent_data >> 6) & 0x3f; letter2 += 59; accent2 = (accent_data >> 12) & 0x7; } else { accent1 = (accent_data >> 6) & 0x1f; accent2 = (accent_data >> 11) & 0xf; } if(Lookup(tr, accents_tab[accent1].name, ph_accent1) != 0) { if(LookupLetter2(tr, basic_letter, ph_letter1) != 0) { if(accent2 != 0) { if(Lookup(tr, accents_tab[accent2].name, ph_accent2) == 0) { // break; } if(accents_tab[accent2].flags & 1) { strcpy(ph_buf,ph_accent2); ph_buf += strlen(ph_buf); ph_accent2[0] = 0; } } if(letter2 != 0) { //ligature LookupLetter2(tr, letter2, ph_letter2); sprintf(ph_buf,"%s%c%s%c%s%s",ph_accent1, phonPAUSE_VSHORT, ph_letter1, phonSTRESS_P, ph_letter2, ph_accent2); } else { if(accent1 == 0) strcpy(ph_buf, ph_letter1); else if((tr->langopts.accents & 1) || (accents_tab[accent1].flags & 1)) sprintf(ph_buf,"%s%c%c%s", ph_accent1, phonPAUSE_VSHORT, phonSTRESS_P, ph_letter1); else sprintf(ph_buf,"%c%s%c%s%c", phonSTRESS_2, ph_letter1, phonPAUSE_VSHORT, ph_accent1, phonPAUSE_VSHORT); } } } } } // end of LookupAccentedLetter void LookupLetter(Translator *tr, unsigned int letter, int next_byte, char *ph_buf1, int control) {//============================================================================================== // control, bit 0: not the first letter of a word int len; static char single_letter[10] = {0,0}; unsigned int dict_flags[2]; char ph_buf3[40]; ph_buf1[0] = 0; len = utf8_out(letter,&single_letter[2]); single_letter[len+2] = ' '; if(next_byte == -1) { // speaking normal text, not individual characters if(Lookup(tr, &single_letter[2], ph_buf1) != 0) return; single_letter[1] = '_'; if(Lookup(tr, &single_letter[1], ph_buf3) != 0) return; // the character is specified as _* so ignore it when speaking normal text // check whether this character is specified for English if(tr->translator_name == L('e','n')) return; // we are already using English SetTranslator2("en"); if(Lookup(translator2, &single_letter[2], ph_buf3) != 0) { // yes, switch to English and re-translate the word sprintf(ph_buf1,"%c",phonSWITCH); } SelectPhonemeTable(voice->phoneme_tab_ix); // revert to original phoneme table return; } if((letter <= 32) || iswspace(letter)) { // lookup space as _&32 etc. sprintf(&single_letter[1],"_#%d ",letter); Lookup(tr, &single_letter[1], ph_buf1); return; } if(next_byte != ' ') next_byte = RULE_SPELLING; single_letter[3+len] = next_byte; // follow by space-space if the end of the word, or space-31 single_letter[1] = '_'; // if the $accent flag is set for this letter, use the accents table (below) dict_flags[1] = 0; if(Lookup(tr, &single_letter[1], ph_buf3) == 0) { single_letter[1] = ' '; if(Lookup(tr, &single_letter[2], ph_buf3) == 0) { TranslateRules(tr, &single_letter[2], ph_buf3, sizeof(ph_buf3), NULL,FLAG_NO_TRACE,NULL); } } if(ph_buf3[0] == 0) { LookupAccentedLetter(tr, letter, ph_buf3); } strcpy(ph_buf1, ph_buf3); if((ph_buf1[0] == 0) || (ph_buf1[0] == phonSWITCH)) { return; } dict_flags[0] = 0; dict_flags[1] = 0; SetWordStress(tr, ph_buf1, dict_flags, -1, control & 1); } // end of LookupLetter int TranslateLetter(Translator *tr, char *word, char *phonemes, int control) {//========================================================================= // get pronunciation for an isolated letter // return number of bytes used by the letter // control bit 0: a non-initial letter in a word // bit 1: say 'capital' int n_bytes; int letter; int len; int save_option_phonemes; char *p2; char *pbuf; char capital[20]; char ph_buf[60]; char ph_buf2[60]; char hexbuf[6]; ph_buf[0] = 0; capital[0] = 0; n_bytes = utf8_in(&letter,word); if((letter & 0xfff00) == 0x0e000) { letter &= 0xff; // uncode private usage area } if(control & 2) { // include CAPITAL information if(iswupper(letter)) { Lookup(tr, "_cap", capital); } } letter = towlower2(letter); LookupLetter(tr, letter, word[n_bytes], ph_buf, control & 1); if(ph_buf[0] == phonSWITCH) { strcpy(phonemes,ph_buf); return(0); } if((ph_buf[0] == 0) && (tr->translator_name != L('e','n'))) { // speak as English, check whether there is a translation for this character SetTranslator2("en"); save_option_phonemes = option_phonemes; option_phonemes = 0; LookupLetter(translator2, letter, word[n_bytes], ph_buf, control & 1); SelectPhonemeTable(voice->phoneme_tab_ix); // revert to original phoneme table option_phonemes = save_option_phonemes; if(ph_buf[0] != 0) { sprintf(phonemes,"%cen",phonSWITCH); return(0); } } if(ph_buf[0] == 0) { // character name not found if(iswalpha(letter)) Lookup(tr, "_?A", ph_buf); if((ph_buf[0]==0) && !iswspace(letter)) Lookup(tr, "_??", ph_buf); if(ph_buf[0] != 0) { // speak the hexadecimal number of the character code sprintf(hexbuf,"%x",letter); pbuf = ph_buf; for(p2 = hexbuf; *p2 != 0; p2++) { pbuf += strlen(pbuf); *pbuf++ = phonPAUSE_VSHORT; LookupLetter(tr, *p2, 0, pbuf, 1); } } } len = strlen(phonemes); if(tr->langopts.accents & 2) sprintf(ph_buf2,"%c%s%s",0xff,ph_buf,capital); else sprintf(ph_buf2,"%c%s%s",0xff,capital,ph_buf); // the 0xff marker will be removed or replaced in SetSpellingStress() if((len + strlen(ph_buf2)) < N_WORD_PHONEMES) { strcpy(&phonemes[len],ph_buf2); } return(n_bytes); } // end of TranslateLetter void SetSpellingStress(Translator *tr, char *phonemes, int control, int n_chars) {//============================================================================= // Individual letter names, reduce the stress of some. int ix; unsigned int c; int n_stress=0; int count; unsigned char buf[N_WORD_PHONEMES]; for(ix=0; (c = phonemes[ix]) != 0; ix++) { if(c == phonSTRESS_P) { n_stress++; } buf[ix] = c; } buf[ix] = 0; count = 0; for(ix=0; (c = buf[ix]) != 0; ix++) { if((c == phonSTRESS_P) && (n_chars > 1)) { count++; if(tr->langopts.spelling_stress == 1) { // stress on initial letter when spelling if(count > 1) c = phonSTRESS_3; } else { if(count != n_stress) { if(((count % 3) != 0) || (count == n_stress-1)) c = phonSTRESS_3; // reduce to secondary stress } } } else if(c == 0xff) { if((control < 2) || (ix==0)) continue; // don't insert pauses if(control == 4) c = phonPAUSE; // pause after each character if(((count % 3) == 0) || (control > 2)) c = phonPAUSE_NOLINK; // pause following a primary stress else c = phonPAUSE_VSHORT; // else // continue; // remove marker } *phonemes++ = c; } if(control >= 2) *phonemes++ = phonPAUSE_NOLINK; *phonemes = 0; } // end of SetSpellingStress // Numbers static char ph_ordinal2[12]; static int CheckDotOrdinal(Translator *tr, char *word, char *word_end, WORD_TAB *wtab, int roman) {//============================================================================================== int ordinal = 0; int c2; int nextflags; if((tr->langopts.numbers & NUM_ORDINAL_DOT) && ((word_end[0] == '.') || (wtab[0].flags & FLAG_HAS_DOT)) && !(wtab[1].flags & FLAG_NOSPACE)) { if(roman || !(wtab[1].flags & FLAG_FIRST_UPPER)) { if(word_end[0] == '.') utf8_in(&c2, &word_end[2]); else utf8_in(&c2, &word_end[0]); if((word_end[0] != 0) && (word_end[1] != 0) && ((c2 == 0) || (wtab[0].flags & FLAG_COMMA_AFTER) || IsAlpha(c2))) { // ordinal number is indicated by dot after the number // but not if the next word starts with an upper-case letter // (c2 == 0) is for cases such as, "2.," ordinal = 2; if(word_end[0] == '.') word_end[0] = ' '; if((roman==0) && (tr->translator_name == L('h','u'))) { // lang=hu don't treat dot as ordinal indicator if the next word is a month name ($alt). It may have a suffix. nextflags = 0; if(IsAlpha(c2)) { nextflags = TranslateWord(tr, &word_end[2], 0, NULL); } if((tr->prev_dict_flags & FLAG_ALT_TRANS) && ((c2 == 0) || (wtab[0].flags & FLAG_COMMA_AFTER) || iswdigit(c2))) ordinal = 0; // TEST 09.02.10 if(nextflags & FLAG_ALT_TRANS) ordinal = 0; if(nextflags & FLAG_ALT3_TRANS) { if(word[-2] == '-') ordinal = 0; // eg. december 2-5. között if(tr->prev_dict_flags & (FLAG_ALT_TRANS | FLAG_ALT3_TRANS)) ordinal = 0x22; } } } } } return(ordinal); } // end of CheckDotOrdinal static int hu_number_e(const char *word, int thousandplex, int value) {//================================================================== // lang-hu: variant form of numbers when followed by hyphen and a suffix starting with 'a' or 'e' (but not a, e, az, ez, azt, ezt, att. ett if((word[0] == 'a') || (word[0] == 'e')) { if((word[1] == ' ') || (word[1] == 'z') || ((word[1] == 't') && (word[2] == 't'))) return(0); if(((thousandplex==1) || ((value % 1000) == 0)) && (word[1] == 'l')) return(0); // 1000-el return(1); } return(0); } // end of hu_numnber_e int TranslateRoman(Translator *tr, char *word, char *ph_out, WORD_TAB *wtab) {//========================================================================= int c; char *p; const char *p2; int acc; int prev; int value; int subtract; int repeat = 0; int n_digits = 0; char *word_start; int num_control = 0; unsigned int flags[2]; char ph_roman[30]; char number_chars[N_WORD_BYTES]; static const char *roman_numbers = "ixcmvld"; static int roman_values[] = {1,10,100,1000,5,50,500}; acc = 0; prev = 0; subtract = 0x7fff; ph_out[0] = 0; flags[0] = 0; flags[1] = 0; if(((tr->langopts.numbers & NUM_ROMAN_CAPITALS) && !(wtab[0].flags & FLAG_ALL_UPPER)) || isdigit(word[-2])) return(0); // not '2xx' word_start = word; while((c = *word++) != ' ') { if((p2 = strchr(roman_numbers,c)) == NULL) return(0); value = roman_values[p2 - roman_numbers]; if(value == prev) { repeat++; if(repeat >= 3) return(0); } else repeat = 0; if((prev > 1) && (prev != 10) && (prev != 100)) { if(value >= prev) return(0); } if((prev != 0) && (prev < value)) { if(((acc % 10) != 0) || ((prev*10) < value)) return(0); subtract = prev; value -= subtract; } else if(value >= subtract) return(0); else acc += prev; prev = value; n_digits++; } if(isdigit(word[0])) return(0); // eg. 'xx2' acc += prev; if(acc < tr->langopts.min_roman) return(0); if(acc > tr->langopts.max_roman) return(0); Lookup(tr, "_roman",ph_roman); // precede by "roman" if _rom is defined in *_list p = &ph_out[0]; if((tr->langopts.numbers & NUM_ROMAN_AFTER) == 0) { strcpy(ph_out,ph_roman); p = &ph_out[strlen(ph_roman)]; } sprintf(number_chars," %d ",acc); if(word[0] == '.') { // dot has not been removed. This implies that there was no space after it return(0); } if(CheckDotOrdinal(tr, word_start, word, wtab, 1)) wtab[0].flags |= FLAG_ORDINAL; if(tr->langopts.numbers & NUM_ROMAN_ORDINAL) { if(tr->translator_name == L('h','u')) { if(!(wtab[0].flags & FLAG_ORDINAL)) { if((wtab[0].flags & FLAG_HYPHEN_AFTER) && hu_number_e(word, 0, acc)) { // should use the 'e' form of the number num_control |= 1; } else return(0); } } else { wtab[0].flags |= FLAG_ORDINAL; } } tr->prev_dict_flags = 0; TranslateNumber(tr, &number_chars[2], p, flags, wtab, num_control); if(tr->langopts.numbers & NUM_ROMAN_AFTER) strcat(ph_out,ph_roman); return(1); } // end of TranslateRoman static const char *M_Variant(int value) {//==================================== // returns M, or perhaps MA for some cases if((translator->langopts.numbers2 & 0x100) && (value >= 2) && (value <= 4)) return("0MA"); // Czech, Slovak else if(((value % 100) < 10) || ((value % 100) > 20)) // but not teens, 10 to 19 { if ((translator->langopts.numbers2 & 0x40) && ((value % 10)>=2) && ((value % 10)<=4)) { // for Polish language - two forms of plural! return("0MA"); } if((translator->langopts.numbers2 & 0x80) && ((value % 10)==1)) { return("1MA"); } } return("0M"); } static int LookupThousands(Translator *tr, int value, int thousandplex, int thousands_exact, char *ph_out) {//======================================================================================================= // thousands_exact: bit 0 no hundreds,tens,or units, bit 1 ordinal numberr int found; int found_value=0; char string[12]; char ph_of[12]; char ph_thousands[40]; char ph_buf[40]; ph_of[0] = 0; // first look for a match with the exact value of thousands if(value > 0) { if(thousands_exact & 1) { if(thousands_exact & 2) { // ordinal number sprintf(string,"_%dM%do",value,thousandplex); found_value = Lookup(tr, string, ph_thousands); } if(!found_value & (number_control & 1)) { // look for the 'e' variant sprintf(string,"_%dM%de",value,thousandplex); found_value = Lookup(tr, string, ph_thousands); } if(!found_value) { // is there a different pronunciation if there are no hundreds,tens,or units ? (LANG=ta) sprintf(string,"_%dM%dx",value,thousandplex); found_value = Lookup(tr, string, ph_thousands); } } if(found_value == 0) { sprintf(string,"_%dM%d",value,thousandplex); found_value = Lookup(tr, string, ph_thousands); } } if(found_value == 0) { if((value % 100) >= 20) { Lookup(tr, "_0of", ph_of); } found = 0; if(thousands_exact & 1) { if(thousands_exact & 2) { // ordinal number sprintf(string,"_%s%do",M_Variant(value), thousandplex); found = Lookup(tr, string, ph_thousands); } if(!found && (number_control & 1)) { // look for the 'e' variant sprintf(string,"_%s%de",M_Variant(value), thousandplex); found = Lookup(tr, string, ph_thousands); } if(!found) { // is there a different pronunciation if there are no hundreds,tens,or units ? sprintf(string,"_%s%dx",M_Variant(value), thousandplex); found = Lookup(tr, string, ph_thousands); } } if(found == 0) { sprintf(string,"_%s%d",M_Variant(value), thousandplex); if(Lookup(tr, string, ph_thousands) == 0) { if(thousandplex > 3) { sprintf(string,"_0M%d", thousandplex-1); if(Lookup(tr, string, ph_buf) == 0) { // say "millions" if this name is not available and neither is the next lower Lookup(tr, "_0M2", ph_thousands); speak_missing_thousands = 3; } } if(ph_thousands[0] == 0) { // repeat "thousand" if higher order names are not available sprintf(string,"_%dM1",value); if((found_value = Lookup(tr, string, ph_thousands)) == 0) Lookup(tr, "_0M1", ph_thousands); speak_missing_thousands = 2; } } } } sprintf(ph_out,"%s%s",ph_of,ph_thousands); if((value == 1) && (thousandplex == 1) && (tr->langopts.numbers & NUM_OMIT_1_THOUSAND)) return(1); return(found_value); } // end f LookupThousands static int LookupNum2(Translator *tr, int value, int control, char *ph_out) {//======================================================================== // Lookup a 2 digit number // control bit 0: ordinal number // control bit 1: final tens and units (not number of thousands) (use special form of '1', LANG=de "eins") // control bit 2: tens and units only, no higher digits // control bit 3: use feminine form of '2' (for thousands // control bit 4: speak zero tens // control bit 5: variant of ordinal number (lang=hu) int found; int ix; int units; int tens; int used_and=0; int found_ordinal = 0; int next_phtype; int ord_type = 'o'; char string[12]; // for looking up entries in *_list char ph_ordinal[20]; char ph_tens[50]; char ph_digits[50]; char ph_and[12]; units = value % 10; tens = value / 10; found = 0; ph_ordinal[0] = 0; ph_tens[0] = 0; ph_digits[0] = 0; ph_and[0] = 0; if(control & 0x20) { ord_type = 'q'; } if((control & 2) && (n_digit_lookup == 2)) { // pronunciation of the final 2 digits has already been found strcpy(ph_out, digit_lookup); } else { if(digit_lookup[0] == 0) { // is there a special pronunciation for this 2-digit number if(control & 8) { sprintf(string,"_%df",value); found = Lookup(tr, string, ph_digits); } else if(control & 1) { strcpy(ph_ordinal, ph_ordinal2); if(control & 4) { sprintf(string,"_%d%cx",value,ord_type); // LANG=hu, special word for 1. 2. when there are no higher digits found = Lookup(tr, string, ph_digits); } if(found == 0) { sprintf(string,"_%d%c",value,ord_type); found = Lookup(tr, string, ph_digits); } found_ordinal = found; } if(found == 0) { if(control & 2) { // the final tens and units of a number if(number_control & 1) { // look for 'e' variant sprintf(string,"_%de",value); found = Lookup(tr, string, ph_digits); } } else { // followed by hundreds or thousands etc sprintf(string,"_%da",value); found = Lookup(tr, string, ph_digits); } if(!found) { sprintf(string,"_%d",value); found = Lookup(tr, string, ph_digits); } } } // no, speak as tens+units if((control & 0x10) && (value < 10)) { // speak leading zero Lookup(tr, "_0", ph_tens); } else { if(found) { ph_tens[0] = 0; } else { if((control & 1) && ((units == 0) || (tr->langopts.numbers & NUM_SWAP_TENS) || (tr->langopts.numbers2 & NUM2_MULTIPLE_ORDINAL))) { sprintf(string,"_%dX%c", tens, ord_type); if(Lookup(tr, string, ph_tens) != 0) { found_ordinal = 1; if((units != 0) && (tr->langopts.numbers2 & NUM2_MULTIPLE_ORDINAL)) { // Use the ordinal form of tens as well as units. Add the ordinal ending strcat(ph_tens, ph_ordinal2); } } } if(found_ordinal == 0) { sprintf(string,"_%dX", tens); Lookup(tr, string, ph_tens); } if((ph_tens[0] == 0) && (tr->langopts.numbers & NUM_VIGESIMAL)) { // tens not found, (for example) 73 is 60+13 units = (value % 20); sprintf(string,"_%dX", tens & 0xfe); Lookup(tr, string, ph_tens); } ph_digits[0] = 0; if(units > 0) { found = 0; if((control & 2) && (digit_lookup[0] != 0)) { // we have an entry for this digit (possibly together with the next word) strcpy(ph_digits, digit_lookup); found_ordinal = 1; ph_ordinal[0] = 0; } else { if(control & 8) { // is there a variant form of this number? sprintf(string,"_%df",units); found = Lookup(tr, string, ph_digits); } if((control & 1) && ((tr->langopts.numbers & NUM_SWAP_TENS) == 0)) { // ordinal sprintf(string,"_%d%c",units,ord_type); if((found = Lookup(tr, string, ph_digits)) != 0) { found_ordinal = 1; } } if(found == 0) { if((number_control & 1) && (control & 2)) { // look for 'e' variant sprintf(string,"_%de",units); found = Lookup(tr, string, ph_digits); } else if(((control & 2) == 0) || ((tr->langopts.numbers & NUM_SWAP_TENS) != 0)) { // followed by hundreds or thousands (or tens) sprintf(string,"_%da",units); found = Lookup(tr, string, ph_digits); } } if(found == 0) { sprintf(string,"_%d",units); Lookup(tr, string, ph_digits); } } } } } if((control & 1) && (found_ordinal == 0) && (ph_ordinal[0] == 0)) { if((value >= 20) && (((value % 10) == 0) || (tr->langopts.numbers & NUM_SWAP_TENS))) Lookup(tr, "_ord20", ph_ordinal); if(ph_ordinal[0] == 0) Lookup(tr, "_ord", ph_ordinal); } if((tr->langopts.numbers & (NUM_SWAP_TENS | NUM_AND_UNITS)) && (ph_tens[0] != 0) && (ph_digits[0] != 0)) { Lookup(tr, "_0and", ph_and); if((control & 1) && (tr->langopts.numbers2 & NUM2_MULTIPLE_ORDINAL)) ph_and[0] = 0; if(tr->langopts.numbers & NUM_SWAP_TENS) sprintf(ph_out,"%s%s%s%s",ph_digits, ph_and, ph_tens, ph_ordinal); else sprintf(ph_out,"%s%s%s%s",ph_tens, ph_and, ph_digits, ph_ordinal); used_and = 1; } else { if(tr->langopts.numbers & NUM_SINGLE_VOWEL) { // remove vowel from the end of tens if units starts with a vowel (LANG=Italian) if(((ix = strlen(ph_tens)-1) >= 0) && (ph_digits[0] != 0)) { if((next_phtype = phoneme_tab[(unsigned int)(ph_digits[0])]->type) == phSTRESS) next_phtype = phoneme_tab[(unsigned int)(ph_digits[1])]->type; if((phoneme_tab[(unsigned int)(ph_tens[ix])]->type == phVOWEL) && (next_phtype == phVOWEL)) ph_tens[ix] = 0; } } sprintf(ph_out,"%s%s%s",ph_tens, ph_digits, ph_ordinal); } } if(tr->langopts.numbers & NUM_SINGLE_STRESS) { // only one primary stress found = 0; for(ix=strlen(ph_out)-1; ix>=0; ix--) { if(ph_out[ix] == phonSTRESS_P) { if(found) ph_out[ix] = phonSTRESS_3; else found = 1; } } } return(used_and); } // end of LookupNum2 static int LookupNum3(Translator *tr, int value, char *ph_out, int suppress_null, int thousandplex, int control) {//============================================================================================================= // Translate a 3 digit number // control bit 0, previous thousands // bit 1, ordinal number // bit 5 variant form of ordinal number int found; int hundreds; int tensunits; int x; int ix; int exact; int ordinal; int say_zero_hundred=0; char string[12]; // for looking up entries in **_list char buf1[100]; char buf2[100]; char ph_100[20]; char ph_10T[20]; char ph_digits[50]; char ph_thousands[50]; char ph_hundred_and[12]; char ph_thousand_and[12]; ordinal = control & 0x22; hundreds = value / 100; tensunits = value % 100; buf1[0] = 0; ph_thousands[0] = 0; ph_thousand_and[0] = 0; if((tr->langopts.numbers & NUM_ZERO_HUNDRED) && ((control & 1) || (hundreds >= 10))) { say_zero_hundred = 1; // lang=vi } if((hundreds > 0) || say_zero_hundred) { found = 0; if(ordinal && (tensunits == 0)) { // ordinal number, with no tens or units found = Lookup(tr, "_0Co", ph_100); } if(found == 0) { if(tensunits==0) { // special form for exact hundreds? found = Lookup(tr, "_0C0", ph_100); } if(!found) { Lookup(tr, "_0C", ph_100); } } if(((tr->langopts.numbers & NUM_1900) != 0) && (hundreds == 19)) { // speak numbers such as 1984 as years: nineteen-eighty-four // ph_100[0] = 0; // don't say "hundred", we also need to surpess "and" } else if(hundreds >= 10) { ph_digits[0] = 0; exact = 0; if ((value % 1000) == 0) exact = 1; if(LookupThousands(tr, hundreds / 10, thousandplex+1, exact | ordinal, ph_10T) == 0) { x = 0; if(tr->langopts.numbers2 & (1 << (thousandplex+1))) x = 8; // use variant (feminine) for before thousands and millions LookupNum2(tr, hundreds/10, x, ph_digits); } if(tr->langopts.numbers2 & 0x200) sprintf(ph_thousands,"%s%s",ph_10T,ph_digits); // say "thousands" before its number, not after else sprintf(ph_thousands,"%s%s",ph_digits,ph_10T); hundreds %= 10; if((hundreds == 0) && (say_zero_hundred == 0)) ph_100[0] = 0; suppress_null = 1; } ph_digits[0] = 0; if((hundreds > 0) || say_zero_hundred) { if((tr->langopts.numbers & NUM_AND_HUNDRED) && ((control & 1) || (ph_thousands[0] != 0))) { Lookup(tr, "_0and", ph_thousand_and); } suppress_null = 1; found = 0; if((ordinal) && ((tensunits == 0) || (tr->langopts.numbers2 & NUM2_MULTIPLE_ORDINAL))) { // ordinal number sprintf(string, "_%dCo", hundreds); found = Lookup(tr, string, ph_digits); if((tr->langopts.numbers2 & NUM2_MULTIPLE_ORDINAL) && (tensunits > 0)) { // Use ordinal form of hundreds, as well as for tens and units // Add ordinal suffix to the hundreds strcat(ph_digits, ph_ordinal2); } } if((hundreds == 0) && say_zero_hundred) { Lookup(tr, "_0", ph_digits); } else { if((!found) && (tensunits == 0)) { // is there a special pronunciation for exactly n00 ? sprintf(string,"_%dC0",hundreds); found = Lookup(tr, string, ph_digits); } if(!found) { sprintf(string,"_%dC",hundreds); found = Lookup(tr, string, ph_digits); // is there a specific pronunciation for n-hundred ? } if(found) { ph_100[0] = 0; } else { if((hundreds > 1) || ((tr->langopts.numbers & NUM_OMIT_1_HUNDRED) == 0)) { LookupNum2(tr, hundreds, 0, ph_digits); } } } } sprintf(buf1,"%s%s%s%s",ph_thousands,ph_thousand_and,ph_digits,ph_100); } ph_hundred_and[0] = 0; if(tensunits > 0) { if((value > 100) || ((control & 1) && (thousandplex==0))) { if((tr->langopts.numbers & NUM_HUNDRED_AND) || ((tr->langopts.numbers & NUM_HUNDRED_AND_DIGIT) && (tensunits < 10))) { Lookup(tr, "_0and", ph_hundred_and); } } if((tr->langopts.numbers & NUM_THOUSAND_AND) && (hundreds == 0) && ((control & 1) || (ph_thousands[0] != 0))) { Lookup(tr, "_0and", ph_hundred_and); } } buf2[0] = 0; if((tensunits != 0) || (suppress_null == 0)) { x = 0; if(thousandplex==0) { x = 2; // allow "eins" for 1 rather than "ein" if(ordinal) x = 3; // ordinal number if((value < 100) && !(control & 1)) x |= 4; // tens and units only, no higher digits if(ordinal & 0x20) x |= 0x20; // variant form of ordinal number } else { if(tr->langopts.numbers2 & (1 << thousandplex)) x = 8; // use variant (feminine) for before thousands and millions } if(LookupNum2(tr, tensunits, x, buf2) != 0) { if(tr->langopts.numbers & NUM_SINGLE_AND) ph_hundred_and[0] = 0; // don't put 'and' after 'hundred' if there's 'and' between tens and units } } else { if(ph_ordinal2[0] != 0) { ix = strlen(buf1); if((ix > 0) && (buf1[ix-1] == phonPAUSE_SHORT)) buf1[ix-1] = 0; // remove pause before addding ordinal suffix strcpy(buf2, ph_ordinal2); } } sprintf(ph_out,"%s%s%s",buf1,ph_hundred_and,buf2); return(0); } // end of LookupNum3 static int TranslateNumber_1(Translator *tr, char *word, char *ph_out, unsigned int *flags, WORD_TAB *wtab, int control) {//===================================================================================================================== // Number translation with various options // the "word" may be up to 4 digits // "words" of 3 digits may be preceded by another number "word" for thousands or millions int n_digits; int value; int ix; int digix; unsigned char c; int suppress_null = 0; int decimal_point = 0; int thousandplex = 0; int thousands_exact = 1; int thousands_inc = 0; int prev_thousands = 0; int ordinal = 0; int dot_ordinal; int this_value; int decimal_count; int max_decimal_count; int decimal_mode; int suffix_ix; int skipwords = 0; char *p; char string[32]; // for looking up entries in **_list char buf1[100]; char ph_append[50]; char ph_buf[200]; char ph_buf2[50]; char ph_zeros[50]; char suffix[30]; // string[] must be long enough for sizeof(suffix)+2 char buf_digit_lookup[50]; static const char str_pause[2] = {phonPAUSE_NOLINK,0}; *flags = 0; n_digit_lookup = 0; buf_digit_lookup[0] = 0; digit_lookup = buf_digit_lookup; number_control = control; for(ix=0; isdigit(word[ix]); ix++) ; n_digits = ix; value = this_value = atoi(word); // is there a previous thousands part (as a previous "word") ? if((n_digits == 3) && (word[-2] == tr->langopts.thousands_sep) && isdigit(word[-3])) { prev_thousands = 1; } else if((tr->langopts.thousands_sep == ' ') || (tr->langopts.numbers & NUM_ALLOW_SPACE)) { // thousands groups can be separated by spaces if((n_digits == 3) && !(wtab->flags & FLAG_MULTIPLE_SPACES) && isdigit(word[-2])) { prev_thousands = 1; } } if(prev_thousands == 0) { speak_missing_thousands = 0; } ph_ordinal2[0] = 0; ph_zeros[0] = 0; if(prev_thousands || (word[0] != '0')) { // don't check for ordinal if the number has a leading zero if((ordinal = CheckDotOrdinal(tr, word, &word[ix], wtab, 0)) != 0) dot_ordinal = 1; } if((word[ix] == '.') && !isdigit(word[ix+1]) && !isdigit(word[ix+2]) && !(wtab[1].flags & FLAG_NOSPACE)) { // remove dot unless followed by another number word[ix] = 0; } if((ordinal == 0) || (tr->translator_name == L('h','u'))) { // NOTE lang=hu, allow both dot and ordinal suffix, eg. "december 21.-én" // look for an ordinal number suffix after the number ix++; p = suffix; if(wtab[0].flags & FLAG_HYPHEN_AFTER) { *p++ = '-'; ix++; } while((word[ix] != 0) && (word[ix] != ' ') && (ix < (int)(sizeof(suffix)-1))) { *p++ = word[ix++]; } *p = 0; if(suffix[0] != 0) { if((tr->langopts.ordinal_indicator != NULL) && (strcmp(suffix, tr->langopts.ordinal_indicator) == 0)) { ordinal = 2; } else if(!isdigit(suffix[0])) // not _#9 (tab) { sprintf(string,"_#%s",suffix); if(Lookup(tr, string, ph_ordinal2)) { // this is an ordinal suffix ordinal = 2; flags[0] |= FLAG_SKIPWORDS; skipwords = 1; } } } } if(wtab[0].flags & FLAG_ORDINAL) ordinal = 2; ph_append[0] = 0; ph_buf2[0] = 0; if((word[0] == '0') && (prev_thousands == 0) && (word[1] != ' ') && (word[1] != tr->langopts.decimal_sep)) { if((n_digits == 2) && (word[3] == ':') && isdigit(word[5]) && isspace(word[7])) { // looks like a time 02:30, omit the leading zero } else { if(n_digits > 3) { flags[0] &= ~FLAG_SKIPWORDS; return(0); // long number string with leading zero, speak as individual digits } // speak leading zeros for(ix=0; (word[ix] == '0') && (ix < (n_digits-1)); ix++) { Lookup(tr, "_0", &ph_zeros[strlen(ph_zeros)]); } } } if((tr->langopts.numbers & NUM_ALLOW_SPACE) && (word[n_digits] == ' ')) thousands_inc = 1; else if(word[n_digits] == tr->langopts.thousands_sep) thousands_inc = 2; suffix_ix = n_digits+2; if(thousands_inc > 0) { // if the following "words" are three-digit groups, count them and add // a "thousand"/"million" suffix to this one digix = n_digits + thousands_inc; while(((wtab[thousandplex+1].flags & FLAG_MULTIPLE_SPACES) == 0) && isdigit(word[digix]) && isdigit(word[digix+1]) && isdigit(word[digix+2]) && !isdigit(word[digix+3]) && !isdigit(word[digix-1])) { if((word[digix] != '0') || (word[digix+1] != '0') || (word[digix+2] != '0')) thousands_exact = 0; thousandplex++; digix += 3; if((word[digix] == tr->langopts.thousands_sep) || ((tr->langopts.numbers & NUM_ALLOW_SPACE) && (word[digix] == ' '))) { suffix_ix = digix+2; digix += thousands_inc; } else break; } } if((value == 0) && prev_thousands) { suppress_null = 1; } if(tr->translator_name == L('h','u')) { // variant form of numbers when followed by hyphen and a suffix starting with 'a' or 'e' (but not a, e, az, ez, azt, ezt if((wtab[thousandplex].flags & FLAG_HYPHEN_AFTER) && (thousands_exact==1) && hu_number_e(&word[suffix_ix], thousandplex, value)) { number_control |= 1; // use _1e variant of number } } if((word[n_digits] == tr->langopts.decimal_sep) && isdigit(word[n_digits+1])) { // this "word" ends with a decimal point Lookup(tr, "_dpt", ph_append); decimal_point = 1; } else if(suppress_null == 0) { if(thousands_inc > 0) { if((thousandplex > 0) && (value < 1000)) { if((suppress_null == 0) && (LookupThousands(tr,value,thousandplex, thousands_exact, ph_append))) { // found an exact match for N thousand value = 0; suppress_null = 1; } } } } else if(speak_missing_thousands == 1) { // speak this thousandplex if there was no word for the previous thousandplex sprintf(string,"_0M%d",thousandplex+1); if(Lookup(tr, string, buf1)==0) { sprintf(string,"_0M%d",thousandplex); Lookup(tr, string, ph_append); } } if((ph_append[0] == 0) && (word[n_digits] == '.') && (thousandplex == 0)) { Lookup(tr, "_.", ph_append); } if(thousandplex == 0) { char *p2; // look for combinations of the number with the next word p = word; while(isdigit(p[1])) p++; // just use the last digit if(isdigit(p[-1])) { p2 = p - 1; if(LookupDictList(tr, &p2, buf_digit_lookup, flags, FLAG_SUFX, wtab)) // lookup 2 digits { n_digit_lookup = 2; } } // if((buf_digit_lookup[0] == 0) && (*p != '0') && (dot_ordinal==0)) if((buf_digit_lookup[0] == 0) && (*p != '0')) { // not found, lookup only the last digit (?? but not if dot-ordinal has been found) if(LookupDictList(tr, &p, buf_digit_lookup, flags, FLAG_SUFX, wtab)) // don't match '0', or entries with $only { n_digit_lookup = 1; } } } LookupNum3(tr, value, ph_buf, suppress_null, thousandplex, prev_thousands | ordinal); if((thousandplex > 0) && (tr->langopts.numbers2 & 0x200)) sprintf(ph_out,"%s%s%s%s",ph_zeros,ph_append,ph_buf2,ph_buf); // say "thousands" before its number else sprintf(ph_out,"%s%s%s%s",ph_zeros,ph_buf2,ph_buf,ph_append); while(decimal_point) { n_digits++; decimal_count = 0; while(isdigit(word[n_digits+decimal_count])) decimal_count++; // if(decimal_count > 1) { max_decimal_count = 2; switch(decimal_mode = (tr->langopts.numbers & 0xe000)) { case NUM_DFRACTION_4: max_decimal_count = 5; case NUM_DFRACTION_2: // French/Polish decimal fraction while(word[n_digits] == '0') { Lookup(tr, "_0", buf1); strcat(ph_out,buf1); decimal_count--; n_digits++; } if((decimal_count <= max_decimal_count) && isdigit(word[n_digits])) { LookupNum3(tr, atoi(&word[n_digits]), buf1, 0,0,0); strcat(ph_out,buf1); n_digits += decimal_count; } break; case NUM_DFRACTION_1: // italian, say "hundredths" if leading zero case NUM_DFRACTION_5: // hungarian, always say "tenths" etc. case NUM_DFRACTION_6: // kazakh, always say "tenths" etc, before the decimal fraction LookupNum3(tr, atoi(&word[n_digits]), ph_buf, 0,0,0); if((word[n_digits]=='0') || (decimal_mode != NUM_DFRACTION_1)) { // decimal part has leading zeros, so add a "hundredths" or "thousandths" suffix sprintf(string,"_0Z%d",decimal_count); if(Lookup(tr, string, buf1) == 0) break; // revert to speaking single digits if(decimal_mode == NUM_DFRACTION_6) strcat(ph_out, buf1); else strcat(ph_buf, buf1); } strcat(ph_out,ph_buf); n_digits += decimal_count; break; case NUM_DFRACTION_3: // Romanian decimal fractions if((decimal_count <= 4) && (word[n_digits] != '0')) { LookupNum3(tr, atoi(&word[n_digits]), buf1, 0,0,0); strcat(ph_out,buf1); n_digits += decimal_count; } break; } } while(isdigit(c = word[n_digits]) && (strlen(ph_out) < (N_WORD_PHONEMES - 10))) { // speak any remaining decimal fraction digits individually value = word[n_digits++] - '0'; LookupNum2(tr, value, 2, buf1); strcat(ph_out,buf1); } // something after the decimal part ? if(Lookup(tr, "_dpt2", buf1)) strcat(ph_out,buf1); if((c == tr->langopts.decimal_sep) && isdigit(word[n_digits+1])) { Lookup(tr, "_dpt", buf1); strcat(ph_out,buf1); } else { decimal_point = 0; } } if((ph_out[0] != 0) && (ph_out[0] != phonSWITCH)) { int next_char; char *p; p = &word[n_digits+1]; p += utf8_in(&next_char,p); if((tr->langopts.numbers & NUM_NOPAUSE) && (next_char == ' ')) utf8_in(&next_char,p); if(!iswalpha(next_char) && !((wtab[thousandplex].flags & FLAG_HYPHEN_AFTER) && (thousands_exact != 0))) strcat(ph_out,str_pause); // don't add pause for 100s, 6th, etc. } *flags |= FLAG_FOUND; speak_missing_thousands--; if(skipwords) dictionary_skipwords = skipwords; return(1); } // end of TranslateNumber_1 int TranslateNumber(Translator *tr, char *word1, char *ph_out, unsigned int *flags, WORD_TAB *wtab, int control) {//============================================================================================================= if((option_sayas == SAYAS_DIGITS1) || (wtab[0].flags & FLAG_INDIVIDUAL_DIGITS)) return(0); // speak digits individually if(tr->langopts.numbers != 0) return(TranslateNumber_1(tr, word1, ph_out, flags, wtab, control)); return(0); } // end of TranslateNumber sources_5316/external/espeak/sonic.h0000775000176700017670000001520211723710247016312 0ustar paulpaul/* Sonic library Copyright 2010 Bill Cox This file is part of the Sonic Library. The Sonic Library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. The GNU C Library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with the GNU C Library; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. */ /* The Sonic Library implements Pitch Based Resampling, which is a new algorithm invented by Bill Cox for the specific purpose of speeding up speech by high factors at high quality. It generates smooth speech at speed up factors as high as 6X, possibly more. It is also capable of slowing down speech, and generates high quality results regardless of the speed up or slow down factor. For speeding up speech by 2X or more, the following equation is used: newSamples = period/(speed - 1.0) scale = 1.0/newSamples; where period is the current pitch period, determined using AMDF or any other pitch estimator, and speed is the speedup factor. If the current position in the input stream is pointed to by "samples", and the current output stream position is pointed to by "out", then newSamples number of samples can be generated with: out[t] = (samples[t]*(newSamples - t) + samples[t + period]*t)/newSamples; where t = 0 to newSamples - 1. For speed factors < 2X, an algorithm similar to PICOLA is used. The above algorithm is first used to double the speed of one pitch period. Then, enough input is directly copied from the input to the output to achieve the desired speed up facter, where 1.0 < speed < 2.0. The amount of data copied is derived: speed = (2*period + length)/(period + length) speed*length + speed*period = 2*period + length length(speed - 1) = 2*period - speed*period length = period*(2 - speed)/(speed - 1) For slowing down speech where 0.5 < speed < 1.0, a pitch period is inserted into the output twice, and length of input is copied from the input to the output until the output desired speed is reached. The length of data copied is: length = period*(speed - 0.5)/(1 - speed) For slow down factors between 0.5 and 0.5, no data is copied, and an algorithm similar to high speed factors is used. */ #ifdef __cplusplus extern "C" { #endif /* This specifies the range of voice pitches we try to match. Note that if we go lower than 65, we could overflow in findPitchInRange */ #define SONIC_MIN_PITCH 65 #define SONIC_MAX_PITCH 400 /* These are used to down-sample some inputs to improve speed */ #define SONIC_AMDF_FREQ 4000 struct sonicStreamStruct; typedef struct sonicStreamStruct *sonicStream; /* For all of the following functions, numChannels is multiplied by numSamples to determine the actual number of values read or returned. */ /* Create a sonic stream. Return NULL only if we are out of memory and cannot allocate the stream. Set numChannels to 1 for mono, and 2 for stereo. */ sonicStream sonicCreateStream(int sampleRate, int numChannels); /* Destroy the sonic stream. */ void sonicDestroyStream(sonicStream stream); /* Use this to write floating point data to be speed up or down into the stream. Values must be between -1 and 1. Return 0 if memory realloc failed, otherwise 1 */ int sonicWriteFloatToStream(sonicStream stream, float *samples, int numSamples); /* Use this to write 16-bit data to be speed up or down into the stream. Return 0 if memory realloc failed, otherwise 1 */ int sonicWriteShortToStream(sonicStream stream, short *samples, int numSamples); /* Use this to write 8-bit unsigned data to be speed up or down into the stream. Return 0 if memory realloc failed, otherwise 1 */ int sonicWriteUnsignedCharToStream(sonicStream stream, unsigned char *samples, int numSamples); /* Use this to read floating point data out of the stream. Sometimes no data will be available, and zero is returned, which is not an error condition. */ int sonicReadFloatFromStream(sonicStream stream, float *samples, int maxSamples); /* Use this to read 16-bit data out of the stream. Sometimes no data will be available, and zero is returned, which is not an error condition. */ int sonicReadShortFromStream(sonicStream stream, short *samples, int maxSamples); /* Use this to read 8-bit unsigned data out of the stream. Sometimes no data will be available, and zero is returned, which is not an error condition. */ int sonicReadUnsignedCharFromStream(sonicStream stream, unsigned char *samples, int maxSamples); /* Force the sonic stream to generate output using whatever data it currently has. No extra delay will be added to the output, but flushing in the middle of words could introduce distortion. */ int sonicFlushStream(sonicStream stream); /* Return the number of samples in the output buffer */ int sonicSamplesAvailable(sonicStream stream); /* Get the speed of the stream. */ float sonicGetSpeed(sonicStream stream); /* Set the speed of the stream. */ void sonicSetSpeed(sonicStream stream, float speed); /* Get the pitch of the stream. */ float sonicGetPitch(sonicStream stream); /* Set the pitch of the stream. */ void sonicSetPitch(sonicStream stream, float pitch); /* Get the scaling factor of the stream. */ float sonicGetVolume(sonicStream stream); /* Set the scaling factor of the stream. */ void sonicSetVolume(sonicStream stream, float volume); /* Get the sample rate of the stream. */ int sonicGetSampleRate(sonicStream stream); /* Get the number of channels. */ int sonicGetNumChannels(sonicStream stream); /* This is a non-stream oriented interface to just change the speed of a sound sample. It works in-place on the sample array, so there must be at least speed*numSamples available space in the array. Returns the new number of samples. */ int sonicChangeFloatSpeed(float *samples, int numSamples, float speed, float pitch, float volume, int sampleRate, int numChannels); /* This is a non-stream oriented interface to just change the speed of a sound sample. It works in-place on the sample array, so there must be at least speed*numSamples available space in the array. Returns the new number of samples. */ int sonicChangeShortSpeed(short *samples, int numSamples, float speed, float pitch, float volume, int sampleRate, int numChannels); #ifdef __cplusplus } #endif sources_5316/external/espeak/sintab.h0000644000176700017670000003316411721443315016456 0ustar paulpaulshort int sin_tab[2048] = { 0, -25, -50, -75, -100, -125, -150, -175, -201, -226, -251, -276, -301, -326, -351, -376, -401, -427, -452, -477, -502, -527, -552, -577, -602, -627, -652, -677, -702, -727, -752, -777, -802, -827, -852, -877, -902, -927, -952, -977, -1002, -1027, -1052, -1077, -1102, -1127, -1152, -1177, -1201, -1226, -1251, -1276, -1301, -1326, -1350, -1375, -1400, -1425, -1449, -1474, -1499, -1523, -1548, -1573, -1597, -1622, -1647, -1671, -1696, -1721, -1745, -1770, -1794, -1819, -1843, -1868, -1892, -1917, -1941, -1965, -1990, -2014, -2038, -2063, -2087, -2111, -2136, -2160, -2184, -2208, -2233, -2257, -2281, -2305, -2329, -2353, -2377, -2401, -2425, -2449, -2473, -2497, -2521, -2545, -2569, -2593, -2617, -2640, -2664, -2688, -2712, -2735, -2759, -2783, -2806, -2830, -2853, -2877, -2900, -2924, -2947, -2971, -2994, -3018, -3041, -3064, -3088, -3111, -3134, -3157, -3180, -3204, -3227, -3250, -3273, -3296, -3319, -3342, -3365, -3388, -3410, -3433, -3456, -3479, -3502, -3524, -3547, -3570, -3592, -3615, -3637, -3660, -3682, -3705, -3727, -3749, -3772, -3794, -3816, -3839, -3861, -3883, -3905, -3927, -3949, -3971, -3993, -4015, -4037, -4059, -4080, -4102, -4124, -4146, -4167, -4189, -4211, -4232, -4254, -4275, -4296, -4318, -4339, -4360, -4382, -4403, -4424, -4445, -4466, -4487, -4508, -4529, -4550, -4571, -4592, -4613, -4633, -4654, -4675, -4695, -4716, -4736, -4757, -4777, -4798, -4818, -4838, -4859, -4879, -4899, -4919, -4939, -4959, -4979, -4999, -5019, -5039, -5059, -5078, -5098, -5118, -5137, -5157, -5176, -5196, -5215, -5235, -5254, -5273, -5292, -5311, -5331, -5350, -5369, -5388, -5406, -5425, -5444, -5463, -5482, -5500, -5519, -5537, -5556, -5574, -5593, -5611, -5629, -5648, -5666, -5684, -5702, -5720, -5738, -5756, -5774, -5791, -5809, -5827, -5844, -5862, -5880, -5897, -5914, -5932, -5949, -5966, -5984, -6001, -6018, -6035, -6052, -6069, -6085, -6102, -6119, -6136, -6152, -6169, -6185, -6202, -6218, -6235, -6251, -6267, -6283, -6299, -6315, -6331, -6347, -6363, -6379, -6395, -6410, -6426, -6441, -6457, -6472, -6488, -6503, -6518, -6533, -6549, -6564, -6579, -6594, -6608, -6623, -6638, -6653, -6667, -6682, -6696, -6711, -6725, -6739, -6754, -6768, -6782, -6796, -6810, -6824, -6838, -6852, -6865, -6879, -6893, -6906, -6920, -6933, -6946, -6960, -6973, -6986, -6999, -7012, -7025, -7038, -7051, -7064, -7076, -7089, -7101, -7114, -7126, -7139, -7151, -7163, -7175, -7187, -7199, -7211, -7223, -7235, -7247, -7259, -7270, -7282, -7293, -7305, -7316, -7327, -7338, -7349, -7361, -7372, -7382, -7393, -7404, -7415, -7425, -7436, -7446, -7457, -7467, -7478, -7488, -7498, -7508, -7518, -7528, -7538, -7548, -7557, -7567, -7577, -7586, -7596, -7605, -7614, -7623, -7633, -7642, -7651, -7660, -7668, -7677, -7686, -7695, -7703, -7712, -7720, -7728, -7737, -7745, -7753, -7761, -7769, -7777, -7785, -7793, -7800, -7808, -7816, -7823, -7830, -7838, -7845, -7852, -7859, -7866, -7873, -7880, -7887, -7894, -7900, -7907, -7914, -7920, -7926, -7933, -7939, -7945, -7951, -7957, -7963, -7969, -7975, -7980, -7986, -7991, -7997, -8002, -8008, -8013, -8018, -8023, -8028, -8033, -8038, -8043, -8047, -8052, -8057, -8061, -8066, -8070, -8074, -8078, -8082, -8086, -8090, -8094, -8098, -8102, -8105, -8109, -8113, -8116, -8119, -8123, -8126, -8129, -8132, -8135, -8138, -8141, -8143, -8146, -8149, -8151, -8153, -8156, -8158, -8160, -8162, -8164, -8166, -8168, -8170, -8172, -8174, -8175, -8177, -8178, -8179, -8181, -8182, -8183, -8184, -8185, -8186, -8187, -8187, -8188, -8189, -8189, -8190, -8190, -8190, -8190, -8190, -8191, -8190, -8190, -8190, -8190, -8190, -8189, -8189, -8188, -8187, -8187, -8186, -8185, -8184, -8183, -8182, -8181, -8179, -8178, -8177, -8175, -8174, -8172, -8170, -8168, -8166, -8164, -8162, -8160, -8158, -8156, -8153, -8151, -8149, -8146, -8143, -8141, -8138, -8135, -8132, -8129, -8126, -8123, -8119, -8116, -8113, -8109, -8105, -8102, -8098, -8094, -8090, -8086, -8082, -8078, -8074, -8070, -8066, -8061, -8057, -8052, -8047, -8043, -8038, -8033, -8028, -8023, -8018, -8013, -8008, -8002, -7997, -7991, -7986, -7980, -7975, -7969, -7963, -7957, -7951, -7945, -7939, -7933, -7926, -7920, -7914, -7907, -7900, -7894, -7887, -7880, -7873, -7866, -7859, -7852, -7845, -7838, -7830, -7823, -7816, -7808, -7800, -7793, -7785, -7777, -7769, -7761, -7753, -7745, -7737, -7728, -7720, -7712, -7703, -7695, -7686, -7677, -7668, -7660, -7651, -7642, -7633, -7623, -7614, -7605, -7596, -7586, -7577, -7567, -7557, -7548, -7538, -7528, -7518, -7508, -7498, -7488, -7478, -7467, -7457, -7446, -7436, -7425, -7415, -7404, -7393, -7382, -7372, -7361, -7349, -7338, -7327, -7316, -7305, -7293, -7282, -7270, -7259, -7247, -7235, -7223, -7211, -7199, -7187, -7175, -7163, -7151, -7139, -7126, -7114, -7101, -7089, -7076, -7064, -7051, -7038, -7025, -7012, -6999, -6986, -6973, -6960, -6946, -6933, -6920, -6906, -6893, -6879, -6865, -6852, -6838, -6824, -6810, -6796, -6782, -6768, -6754, -6739, -6725, -6711, -6696, -6682, -6667, -6653, -6638, -6623, -6608, -6594, -6579, -6564, -6549, -6533, -6518, -6503, -6488, -6472, -6457, -6441, -6426, -6410, -6395, -6379, -6363, -6347, -6331, -6315, -6299, -6283, -6267, -6251, -6235, -6218, -6202, -6185, -6169, -6152, -6136, -6119, -6102, -6085, -6069, -6052, -6035, -6018, -6001, -5984, -5966, -5949, -5932, -5914, -5897, -5880, -5862, -5844, -5827, -5809, -5791, -5774, -5756, -5738, -5720, -5702, -5684, -5666, -5648, -5629, -5611, -5593, -5574, -5556, -5537, -5519, -5500, -5482, -5463, -5444, -5425, -5406, -5388, -5369, -5350, -5331, -5311, -5292, -5273, -5254, -5235, -5215, -5196, -5176, -5157, -5137, -5118, -5098, -5078, -5059, -5039, -5019, -4999, -4979, -4959, -4939, -4919, -4899, -4879, -4859, -4838, -4818, -4798, -4777, -4757, -4736, -4716, -4695, -4675, -4654, -4633, -4613, -4592, -4571, -4550, -4529, -4508, -4487, -4466, -4445, -4424, -4403, -4382, -4360, -4339, -4318, -4296, -4275, -4254, -4232, -4211, -4189, -4167, -4146, -4124, -4102, -4080, -4059, -4037, -4015, -3993, -3971, -3949, -3927, -3905, -3883, -3861, -3839, -3816, -3794, -3772, -3749, -3727, -3705, -3682, -3660, -3637, -3615, -3592, -3570, -3547, -3524, -3502, -3479, -3456, -3433, -3410, -3388, -3365, -3342, -3319, -3296, -3273, -3250, -3227, -3204, -3180, -3157, -3134, -3111, -3088, -3064, -3041, -3018, -2994, -2971, -2947, -2924, -2900, -2877, -2853, -2830, -2806, -2783, -2759, -2735, -2712, -2688, -2664, -2640, -2617, -2593, -2569, -2545, -2521, -2497, -2473, -2449, -2425, -2401, -2377, -2353, -2329, -2305, -2281, -2257, -2233, -2208, -2184, -2160, -2136, -2111, -2087, -2063, -2038, -2014, -1990, -1965, -1941, -1917, -1892, -1868, -1843, -1819, -1794, -1770, -1745, -1721, -1696, -1671, -1647, -1622, -1597, -1573, -1548, -1523, -1499, -1474, -1449, -1425, -1400, -1375, -1350, -1326, -1301, -1276, -1251, -1226, -1201, -1177, -1152, -1127, -1102, -1077, -1052, -1027, -1002, -977, -952, -927, -902, -877, -852, -827, -802, -777, -752, -727, -702, -677, -652, -627, -602, -577, -552, -527, -502, -477, -452, -427, -401, -376, -351, -326, -301, -276, -251, -226, -201, -175, -150, -125, -100, -75, -50, -25, 0, 25, 50, 75, 100, 125, 150, 175, 201, 226, 251, 276, 301, 326, 351, 376, 401, 427, 452, 477, 502, 527, 552, 577, 602, 627, 652, 677, 702, 727, 752, 777, 802, 827, 852, 877, 902, 927, 952, 977, 1002, 1027, 1052, 1077, 1102, 1127, 1152, 1177, 1201, 1226, 1251, 1276, 1301, 1326, 1350, 1375, 1400, 1425, 1449, 1474, 1499, 1523, 1548, 1573, 1597, 1622, 1647, 1671, 1696, 1721, 1745, 1770, 1794, 1819, 1843, 1868, 1892, 1917, 1941, 1965, 1990, 2014, 2038, 2063, 2087, 2111, 2136, 2160, 2184, 2208, 2233, 2257, 2281, 2305, 2329, 2353, 2377, 2401, 2425, 2449, 2473, 2497, 2521, 2545, 2569, 2593, 2617, 2640, 2664, 2688, 2712, 2735, 2759, 2783, 2806, 2830, 2853, 2877, 2900, 2924, 2947, 2971, 2994, 3018, 3041, 3064, 3088, 3111, 3134, 3157, 3180, 3204, 3227, 3250, 3273, 3296, 3319, 3342, 3365, 3388, 3410, 3433, 3456, 3479, 3502, 3524, 3547, 3570, 3592, 3615, 3637, 3660, 3682, 3705, 3727, 3749, 3772, 3794, 3816, 3839, 3861, 3883, 3905, 3927, 3949, 3971, 3993, 4015, 4037, 4059, 4080, 4102, 4124, 4146, 4167, 4189, 4211, 4232, 4254, 4275, 4296, 4318, 4339, 4360, 4382, 4403, 4424, 4445, 4466, 4487, 4508, 4529, 4550, 4571, 4592, 4613, 4633, 4654, 4675, 4695, 4716, 4736, 4757, 4777, 4798, 4818, 4838, 4859, 4879, 4899, 4919, 4939, 4959, 4979, 4999, 5019, 5039, 5059, 5078, 5098, 5118, 5137, 5157, 5176, 5196, 5215, 5235, 5254, 5273, 5292, 5311, 5331, 5350, 5369, 5388, 5406, 5425, 5444, 5463, 5482, 5500, 5519, 5537, 5556, 5574, 5593, 5611, 5629, 5648, 5666, 5684, 5702, 5720, 5738, 5756, 5774, 5791, 5809, 5827, 5844, 5862, 5880, 5897, 5914, 5932, 5949, 5966, 5984, 6001, 6018, 6035, 6052, 6069, 6085, 6102, 6119, 6136, 6152, 6169, 6185, 6202, 6218, 6235, 6251, 6267, 6283, 6299, 6315, 6331, 6347, 6363, 6379, 6395, 6410, 6426, 6441, 6457, 6472, 6488, 6503, 6518, 6533, 6549, 6564, 6579, 6594, 6608, 6623, 6638, 6653, 6667, 6682, 6696, 6711, 6725, 6739, 6754, 6768, 6782, 6796, 6810, 6824, 6838, 6852, 6865, 6879, 6893, 6906, 6920, 6933, 6946, 6960, 6973, 6986, 6999, 7012, 7025, 7038, 7051, 7064, 7076, 7089, 7101, 7114, 7126, 7139, 7151, 7163, 7175, 7187, 7199, 7211, 7223, 7235, 7247, 7259, 7270, 7282, 7293, 7305, 7316, 7327, 7338, 7349, 7361, 7372, 7382, 7393, 7404, 7415, 7425, 7436, 7446, 7457, 7467, 7478, 7488, 7498, 7508, 7518, 7528, 7538, 7548, 7557, 7567, 7577, 7586, 7596, 7605, 7614, 7623, 7633, 7642, 7651, 7660, 7668, 7677, 7686, 7695, 7703, 7712, 7720, 7728, 7737, 7745, 7753, 7761, 7769, 7777, 7785, 7793, 7800, 7808, 7816, 7823, 7830, 7838, 7845, 7852, 7859, 7866, 7873, 7880, 7887, 7894, 7900, 7907, 7914, 7920, 7926, 7933, 7939, 7945, 7951, 7957, 7963, 7969, 7975, 7980, 7986, 7991, 7997, 8002, 8008, 8013, 8018, 8023, 8028, 8033, 8038, 8043, 8047, 8052, 8057, 8061, 8066, 8070, 8074, 8078, 8082, 8086, 8090, 8094, 8098, 8102, 8105, 8109, 8113, 8116, 8119, 8123, 8126, 8129, 8132, 8135, 8138, 8141, 8143, 8146, 8149, 8151, 8153, 8156, 8158, 8160, 8162, 8164, 8166, 8168, 8170, 8172, 8174, 8175, 8177, 8178, 8179, 8181, 8182, 8183, 8184, 8185, 8186, 8187, 8187, 8188, 8189, 8189, 8190, 8190, 8190, 8190, 8190, 8191, 8190, 8190, 8190, 8190, 8190, 8189, 8189, 8188, 8187, 8187, 8186, 8185, 8184, 8183, 8182, 8181, 8179, 8178, 8177, 8175, 8174, 8172, 8170, 8168, 8166, 8164, 8162, 8160, 8158, 8156, 8153, 8151, 8149, 8146, 8143, 8141, 8138, 8135, 8132, 8129, 8126, 8123, 8119, 8116, 8113, 8109, 8105, 8102, 8098, 8094, 8090, 8086, 8082, 8078, 8074, 8070, 8066, 8061, 8057, 8052, 8047, 8043, 8038, 8033, 8028, 8023, 8018, 8013, 8008, 8002, 7997, 7991, 7986, 7980, 7975, 7969, 7963, 7957, 7951, 7945, 7939, 7933, 7926, 7920, 7914, 7907, 7900, 7894, 7887, 7880, 7873, 7866, 7859, 7852, 7845, 7838, 7830, 7823, 7816, 7808, 7800, 7793, 7785, 7777, 7769, 7761, 7753, 7745, 7737, 7728, 7720, 7712, 7703, 7695, 7686, 7677, 7668, 7660, 7651, 7642, 7633, 7623, 7614, 7605, 7596, 7586, 7577, 7567, 7557, 7548, 7538, 7528, 7518, 7508, 7498, 7488, 7478, 7467, 7457, 7446, 7436, 7425, 7415, 7404, 7393, 7382, 7372, 7361, 7349, 7338, 7327, 7316, 7305, 7293, 7282, 7270, 7259, 7247, 7235, 7223, 7211, 7199, 7187, 7175, 7163, 7151, 7139, 7126, 7114, 7101, 7089, 7076, 7064, 7051, 7038, 7025, 7012, 6999, 6986, 6973, 6960, 6946, 6933, 6920, 6906, 6893, 6879, 6865, 6852, 6838, 6824, 6810, 6796, 6782, 6768, 6754, 6739, 6725, 6711, 6696, 6682, 6667, 6653, 6638, 6623, 6608, 6594, 6579, 6564, 6549, 6533, 6518, 6503, 6488, 6472, 6457, 6441, 6426, 6410, 6395, 6379, 6363, 6347, 6331, 6315, 6299, 6283, 6267, 6251, 6235, 6218, 6202, 6185, 6169, 6152, 6136, 6119, 6102, 6085, 6069, 6052, 6035, 6018, 6001, 5984, 5966, 5949, 5932, 5914, 5897, 5880, 5862, 5844, 5827, 5809, 5791, 5774, 5756, 5738, 5720, 5702, 5684, 5666, 5648, 5629, 5611, 5593, 5574, 5556, 5537, 5519, 5500, 5482, 5463, 5444, 5425, 5406, 5388, 5369, 5350, 5331, 5311, 5292, 5273, 5254, 5235, 5215, 5196, 5176, 5157, 5137, 5118, 5098, 5078, 5059, 5039, 5019, 4999, 4979, 4959, 4939, 4919, 4899, 4879, 4859, 4838, 4818, 4798, 4777, 4757, 4736, 4716, 4695, 4675, 4654, 4633, 4613, 4592, 4571, 4550, 4529, 4508, 4487, 4466, 4445, 4424, 4403, 4382, 4360, 4339, 4318, 4296, 4275, 4254, 4232, 4211, 4189, 4167, 4146, 4124, 4102, 4080, 4059, 4037, 4015, 3993, 3971, 3949, 3927, 3905, 3883, 3861, 3839, 3816, 3794, 3772, 3749, 3727, 3705, 3682, 3660, 3637, 3615, 3592, 3570, 3547, 3524, 3502, 3479, 3456, 3433, 3410, 3388, 3365, 3342, 3319, 3296, 3273, 3250, 3227, 3204, 3180, 3157, 3134, 3111, 3088, 3064, 3041, 3018, 2994, 2971, 2947, 2924, 2900, 2877, 2853, 2830, 2806, 2783, 2759, 2735, 2712, 2688, 2664, 2640, 2617, 2593, 2569, 2545, 2521, 2497, 2473, 2449, 2425, 2401, 2377, 2353, 2329, 2305, 2281, 2257, 2233, 2208, 2184, 2160, 2136, 2111, 2087, 2063, 2038, 2014, 1990, 1965, 1941, 1917, 1892, 1868, 1843, 1819, 1794, 1770, 1745, 1721, 1696, 1671, 1647, 1622, 1597, 1573, 1548, 1523, 1499, 1474, 1449, 1425, 1400, 1375, 1350, 1326, 1301, 1276, 1251, 1226, 1201, 1177, 1152, 1127, 1102, 1077, 1052, 1027, 1002, 977, 952, 927, 902, 877, 852, 827, 802, 777, 752, 727, 702, 677, 652, 627, 602, 577, 552, 527, 502, 477, 452, 427, 401, 376, 351, 326, 301, 276, 251, 226, 201, 175, 150, 125, 100, 75, 50, 25, }; sources_5316/external/espeak/klatt.h0000644000176700017670000001135111721443315016307 0ustar paulpaul #define CASCADE_PARALLEL 1 /* Type of synthesis model */ #define ALL_PARALLEL 2 #define IMPULSIVE 1 /* Type of voicing source */ #define NATURAL 2 #define SAMPLED 3 #define PI 3.1415927 /* typedef's that need to be exported */ typedef long flag; /* Resonator Structure */ typedef struct { double a; double b; double c; double p1; double p2; double a_inc; double b_inc; double c_inc; } resonator_t, *resonator_ptr; /* Structure for Klatt Globals */ typedef struct { flag synthesis_model; /* cascade-parallel or all-parallel */ flag outsl; /* Output waveform selector */ long samrate; /* Number of output samples per second */ long FLPhz ; /* Frequeny of glottal downsample low-pass filter */ long BLPhz ; /* Bandwidth of glottal downsample low-pass filter */ flag glsource; /* Type of glottal source */ int f0_flutter; /* Percentage of f0 flutter 0-100 */ long nspfr; /* number of samples per frame */ long nper; /* Counter for number of samples in a pitch period */ long ns; long T0; /* Fundamental period in output samples times 4 */ long nopen; /* Number of samples in open phase of period */ long nmod; /* Position in period to begin noise amp. modul */ long nrand; /* Varible used by random number generator */ double pulse_shape_a; /* Makes waveshape of glottal pulse when open */ double pulse_shape_b; /* Makes waveshape of glottal pulse when open */ double minus_pi_t; double two_pi_t; double onemd; double decay; double amp_bypas; /* AB converted to linear gain */ double amp_voice; /* AVdb converted to linear gain */ double par_amp_voice; /* AVpdb converted to linear gain */ double amp_aspir; /* AP converted to linear gain */ double amp_frica; /* AF converted to linear gain */ double amp_breth; /* ATURB converted to linear gain */ double amp_gain0; /* G0 converted to linear gain */ int num_samples; /* number of glottal samples */ double sample_factor; /* multiplication factor for glottal samples */ short *natural_samples; /* pointer to an array of glottal samples */ long original_f0; /* original value of f0 not modified by flutter */ int fadeout; // set to 64 to cause fadeout over 64 samples int scale_wav; // depends on the voicing source #define N_RSN 20 #define Rnz 0 // nasal zero, anti-resonator #define R1c 1 #define R2c 2 #define R3c 3 #define R4c 4 #define R5c 5 #define R6c 6 #define R7c 7 #define R8c 8 #define Rnpc 9 // nasal pole #define Rparallel 10 #define Rnpp 10 #define R1p 11 #define R2p 12 #define R3p 13 #define R4p 14 #define R5p 15 #define R6p 16 #define RGL 17 #define RLP 18 #define Rout 19 resonator_t rsn[N_RSN]; // internal storage for resonators resonator_t rsn_next[N_RSN]; } klatt_global_t, *klatt_global_ptr; /* Structure for Klatt Parameters */ #define F_NZ 0 // nasal zero formant #define F1 1 #define F2 2 #define F3 3 #define F4 4 #define F5 5 #define F6 6 #define F_NP 9 // nasal pole formant typedef struct { int F0hz10; /* Voicing fund freq in Hz */ int AVdb; /* Amp of voicing in dB, 0 to 70 */ int Fhz[10]; // formant Hz, F_NZ to F6 to F_NP int Bhz[10]; int Ap[10]; /* Amp of parallel formants in dB, 0 to 80 */ int Bphz[10]; /* Parallel formants bw in Hz, 40 to 1000 */ int ASP; /* Amp of aspiration in dB, 0 to 70 */ int Kopen; /* # of samples in open period, 10 to 65 */ int Aturb; /* Breathiness in voicing, 0 to 80 */ int TLTdb; /* Voicing spectral tilt in dB, 0 to 24 */ int AF; /* Amp of frication in dB, 0 to 80 */ int Kskew; /* Skewness of alternate periods, 0 to 40 in sample#/2 */ int AB; /* Amp of bypass fric. in dB, 0 to 80 */ int AVpdb; /* Amp of voicing, par in dB, 0 to 70 */ int Gain0; /* Overall gain, 60 dB is unity, 0 to 60 */ int AVdb_tmp; //copy of AVdb, which is changed within parwave() int Fhz_next[10]; // Fhz for the next chunk, so we can do interpolation of resonator (a,b,c) parameters int Bhz_next[10]; } klatt_frame_t, *klatt_frame_ptr; typedef struct { int freq; // Hz int bw; // klatt bandwidth int ap; // parallel amplitude int bp; // parallel bandwidth DOUBLEX freq1; // floating point versions of the above DOUBLEX bw1; DOUBLEX ap1; DOUBLEX bp1; DOUBLEX freq_inc; // increment by this every 64 samples DOUBLEX bw_inc; DOUBLEX ap_inc; DOUBLEX bp_inc; } klatt_peaks_t; sources_5316/external/espeak/event.h0000644000176700017670000000265211721443315016315 0ustar paulpaul#ifndef EVENT_H #define EVENT_H /* Manage events (sentence, word, mark, end,...), is responsible of calling the external callback as soon as the relevant audio sample is played. The audio stream is composed of samples from synthetised messages or audio icons. Each event is associated to a sample. Scenario: - event_declare is called for each expected event. - A timeout is started for the first pending event. - When the timeout happens, the synth_callback is called. Note: the timeout is checked against the real progress of the audio stream, which depends on pauses or underruns. If the real progress is lower than the expected one, a new timeout starts. */ #include "speak_lib.h" // Initialize the event component. // First function to be called. // the callback will be called when the event actually occurs. // The callback is detailled in speak_lib.h . void event_init(void); void event_set_callback(t_espeak_callback* cb); // Clear any pending event. // // Return: EE_OK: operation achieved // EE_INTERNAL_ERROR. espeak_ERROR event_clear_all (); // Declare a future event // // Return: EE_OK: operation achieved // EE_BUFFER_FULL: the event can not be buffered; // you may try after a while to call the function again. // EE_INTERNAL_ERROR. espeak_ERROR event_declare (espeak_EVENT* event); // Terminate the event component. // Last function to be called. void event_terminate(); #endif sources_5316/external/espeak/mbrowrap.cpp0000775000176700017670000003125711674622653017403 0ustar paulpaul/* * mbrowrap -- A wrapper library around the mbrola binary * providing a subset of the API from the Windows mbrola DLL. * * Copyright (C) 2010 by Nicolas Pitre * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. */ #include "speech.h" #ifdef INCLUDE_MBROLA #include #include #include #include #include #include #include #include #include #include #include #include "mbrowrap.h" /* * mbrola instance parameters */ enum mbr_state { MBR_INACTIVE = 0, MBR_IDLE, MBR_NEWDATA, MBR_AUDIO, MBR_WEDGED }; static enum mbr_state mbr_state; static char *mbr_voice_path; static int mbr_cmd_fd, mbr_audio_fd, mbr_error_fd, mbr_proc_stat; static pid_t mbr_pid; static int mbr_samplerate; static float mbr_volume = 1.0; static char mbr_errorbuf[160]; struct datablock { struct datablock *next; int done; int size; char buffer[1]; /* 1 or more, dynamically allocated */ }; static struct datablock *mbr_pending_data_head, *mbr_pending_data_tail; /* * Private support code. */ static void log(const char *msg, ...) { va_list params; va_start(params, msg); vfprintf(stderr, msg, params); fputc('\n', stderr); va_end(params); } static void err(const char *errmsg, ...) { va_list params; va_start(params, errmsg); vsnprintf(mbr_errorbuf, sizeof(mbr_errorbuf), errmsg, params); va_end(params); log("mbrowrap error: %s", mbr_errorbuf); } static int create_pipes(int p1[2], int p2[2], int p3[2]) { int error; if (pipe(p1) != -1) { if (pipe(p2) != -1) { if (pipe(p3) != -1) { return 0; } else error = errno; close(p2[0]); close(p2[1]); } else error = errno; close(p1[0]); close(p1[1]); } else error = errno; err("pipe(): %s", strerror(error)); return -1; } static void close_pipes(int p1[2], int p2[2], int p3[2]) { close(p1[0]); close(p1[1]); close(p2[0]); close(p2[1]); close(p3[0]); close(p3[1]); } static int start_mbrola(const char *voice_path) { int error, p_stdin[2], p_stdout[2], p_stderr[2]; ssize_t written; char charbuf[20]; if (mbr_state != MBR_INACTIVE) { err("mbrola init request when already initialized"); return -1; } error = create_pipes(p_stdin, p_stdout, p_stderr); if (error) return -1; mbr_pid = fork(); if (mbr_pid == -1) { error = errno; close_pipes(p_stdin, p_stdout, p_stderr); err("fork(): %s", strerror(error)); return -1; } if (mbr_pid == 0) { int i; if (dup2(p_stdin[0], 0) == -1 || dup2(p_stdout[1], 1) == -1 || dup2(p_stderr[1], 2) == -1) { snprintf(mbr_errorbuf, sizeof(mbr_errorbuf), "dup2(): %s\n", strerror(errno)); written = write(p_stderr[1], mbr_errorbuf, strlen(mbr_errorbuf)); (void)written; // suppress 'variable not used' warning _exit(1); } for (i = p_stderr[1]; i > 2; i--) close(i); signal(SIGHUP, SIG_IGN); signal(SIGINT, SIG_IGN); signal(SIGQUIT, SIG_IGN); signal(SIGTERM, SIG_IGN); snprintf(charbuf, sizeof(charbuf), "%g", mbr_volume); execlp("mbrola", "mbrola", "-e", "-v", charbuf, voice_path, "-", "-.wav", (char *)NULL); /* if execution reaches this point then the exec() failed */ snprintf(mbr_errorbuf, sizeof(mbr_errorbuf), "mbrola: %s\n", strerror(errno)); written = write(2, mbr_errorbuf, strlen(mbr_errorbuf)); (void)written; // suppress 'variable not used' warning _exit(1); } snprintf(charbuf, sizeof(charbuf), "/proc/%d/stat", mbr_pid); mbr_proc_stat = open(charbuf, O_RDONLY); if (mbr_proc_stat == -1) { error = errno; close_pipes(p_stdin, p_stdout, p_stderr); waitpid(mbr_pid, NULL, 0); mbr_pid = 0; err("/proc is unaccessible: %s", strerror(error)); return -1; } signal(SIGPIPE, SIG_IGN); if (fcntl(p_stdin[1], F_SETFL, O_NONBLOCK) == -1 || fcntl(p_stdout[0], F_SETFL, O_NONBLOCK) == -1 || fcntl(p_stderr[0], F_SETFL, O_NONBLOCK) == -1) { error = errno; close_pipes(p_stdin, p_stdout, p_stderr); waitpid(mbr_pid, NULL, 0); mbr_pid = 0; err("fcntl(): %s", strerror(error)); return -1; } mbr_cmd_fd = p_stdin[1]; mbr_audio_fd = p_stdout[0]; mbr_error_fd = p_stderr[0]; close(p_stdin[0]); close(p_stdout[1]); close(p_stderr[1]); mbr_state = MBR_IDLE; return 0; } static void stop_mbrola(void) { if (mbr_state == MBR_INACTIVE) return; close(mbr_proc_stat); close(mbr_cmd_fd); close(mbr_audio_fd); close(mbr_error_fd); if (mbr_pid) { kill(mbr_pid, SIGTERM); waitpid(mbr_pid, NULL, 0); mbr_pid = 0; } mbr_state = MBR_INACTIVE; } static void free_pending_data(void) { struct datablock *p, *head = mbr_pending_data_head; while (head) { p = head; head = head->next; free(p); } mbr_pending_data_head = NULL; mbr_pending_data_tail = NULL; } static int mbrola_died(void) { pid_t pid; int status, len; const char *msg; char msgbuf[80]; pid = waitpid(mbr_pid, &status, WNOHANG); if (!pid) { msg = "mbrola closed stderr and did not exit"; } else if (pid != mbr_pid) { msg = "waitpid() is confused"; } else { mbr_pid = 0; if (WIFSIGNALED(status)) { int sig = WTERMSIG(status); snprintf(msgbuf, sizeof(msgbuf), "mbrola died by signal %d", sig); msg = msgbuf; } else if (WIFEXITED(status)) { int exst = WEXITSTATUS(status); snprintf(msgbuf, sizeof(msgbuf), "mbrola exited with status %d", exst); msg = msgbuf; } else { msg = "mbrola died and wait status is weird"; } } log("mbrowrap error: %s", msg); len = strlen(mbr_errorbuf); if (!len) snprintf(mbr_errorbuf, sizeof(mbr_errorbuf), "%s", msg); else snprintf(mbr_errorbuf + len, sizeof(mbr_errorbuf) - len, ", (%s)", msg); return -1; } static int mbrola_has_errors(void) { int result; char buffer[256]; char *buf_ptr, *lf; buf_ptr = buffer; for (;;) { result = read(mbr_error_fd, buf_ptr, sizeof(buffer) - (buf_ptr - buffer) - 1); if (result == -1) { if (errno == EAGAIN) return 0; err("read(error): %s", strerror(errno)); return -1; } if (result == 0) { /* EOF on stderr, assume mbrola died. */ return mbrola_died(); } buf_ptr[result] = 0; for (; (lf = strchr(buf_ptr, '\n')); buf_ptr = lf + 1) { /* inhibit the reset signal messages */ if (strncmp(buf_ptr, "Got a reset signal", 18) == 0 || strncmp(buf_ptr, "Input Flush Signal", 18) == 0) continue; *lf = 0; log("mbrola: %s", buf_ptr); /* is this the last line? */ if (lf == &buf_ptr[result - 1]) { snprintf(mbr_errorbuf, sizeof(mbr_errorbuf), "%s", buf_ptr); /* don't consider this fatal at this point */ return 0; } } memmove(buffer, buf_ptr, result); buf_ptr = buffer + result; } } static int send_to_mbrola(const char *cmd) { ssize_t result; int len; if (!mbr_pid) return -1; len = strlen(cmd); result = write(mbr_cmd_fd, cmd, len); if (result == -1) { int error = errno; if (error == EPIPE && mbrola_has_errors()) { return -1; } else if (error == EAGAIN) { result = 0; } else { err("write(): %s", strerror(error)); return -1; } } if (result != len) { struct datablock *data; data = (struct datablock *)malloc(sizeof(*data) + len - result); if (data) { data->next = NULL; data->done = 0; data->size = len - result; memcpy(data->buffer, cmd + result, len - result); result = len; if (!mbr_pending_data_head) mbr_pending_data_head = data; else mbr_pending_data_tail->next = data; mbr_pending_data_tail = data; } } return result; } static int mbrola_is_idle(void) { char *p; char buffer[20]; /* looking for "12345 (mbrola) S" so 20 is plenty*/ /* look in /proc to determine if mbrola is still running or sleeping */ if (lseek(mbr_proc_stat, 0, SEEK_SET) != 0) return 0; if (read(mbr_proc_stat, buffer, sizeof(buffer)) != sizeof(buffer)) return 0; p = (char *)memchr(buffer, ')', sizeof(buffer)); if (!p || (unsigned)(p - buffer) >= sizeof(buffer) - 2) return 0; return (p[1] == ' ' && p[2] == 'S'); } static ssize_t receive_from_mbrola(void *buffer, size_t bufsize) { int result, wait = 1; size_t cursize = 0; if (!mbr_pid) return -1; do { struct pollfd pollfd[3]; nfds_t nfds = 0; int idle; pollfd[0].fd = mbr_audio_fd; pollfd[0].events = POLLIN; nfds++; pollfd[1].fd = mbr_error_fd; pollfd[1].events = POLLIN; nfds++; if (mbr_pending_data_head) { pollfd[2].fd = mbr_cmd_fd; pollfd[2].events = POLLOUT; nfds++; } idle = mbrola_is_idle(); result = poll(pollfd, nfds, idle ? 0 : wait); if (result == -1) { err("poll(): %s", strerror(errno)); return -1; } if (result == 0) { if (idle) { mbr_state = MBR_IDLE; break; } else { if (wait >= 5000 * (4-1)/4) { mbr_state = MBR_WEDGED; err("mbrola process is stalled"); break; } else { wait *= 4; continue; } } } wait = 1; if (pollfd[1].revents && mbrola_has_errors()) return -1; if (mbr_pending_data_head && pollfd[2].revents) { struct datablock *head = mbr_pending_data_head; char *data = head->buffer + head->done; int left = head->size - head->done; result = write(mbr_cmd_fd, data, left); if (result == -1) { int error = errno; if (error == EPIPE && mbrola_has_errors()) return -1; err("write(): %s", strerror(error)); return -1; } if (result != left) { head->done += result; } else { mbr_pending_data_head = head->next; free(head); if (!mbr_pending_data_head) mbr_pending_data_tail = NULL; else continue; } } if (pollfd[0].revents) { char *curpos = (char *)buffer + cursize; size_t space = bufsize - cursize; ssize_t obtained = read(mbr_audio_fd, curpos, space); if (obtained == -1) { err("read(): %s", strerror(errno)); return -1; } cursize += obtained; mbr_state = MBR_AUDIO; } } while (cursize < bufsize); return cursize; } /* * API functions. */ int init_MBR(const char *voice_path) { int error, result; unsigned char wavhdr[45]; error = start_mbrola(voice_path); if (error) return -1; result = send_to_mbrola("#\n"); if (result != 2) { stop_mbrola(); return -1; } /* we should actually be getting only 44 bytes */ result = receive_from_mbrola(wavhdr, 45); if (result != 44) { if (result >= 0) err("unable to get .wav header from mbrola"); stop_mbrola(); return -1; } /* parse wavhdr to get mbrola voice samplerate */ if (memcmp(wavhdr, "RIFF", 4) != 0 || memcmp(wavhdr+8, "WAVEfmt ", 8) != 0) { err("mbrola did not return a .wav header"); stop_mbrola(); return -1; } mbr_samplerate = wavhdr[24] + (wavhdr[25]<<8) + (wavhdr[26]<<16) + (wavhdr[27]<<24); //log("mbrowrap: voice samplerate = %d", mbr_samplerate); /* remember the voice path for setVolumeRatio_MBR() */ if (mbr_voice_path != voice_path) { free(mbr_voice_path); mbr_voice_path = strdup(voice_path); } return 0; } void close_MBR(void) { stop_mbrola(); free_pending_data(); free(mbr_voice_path); mbr_voice_path = NULL; mbr_volume = 1.0; } int reset_MBR() { int result, success = 1; char dummybuf[4096]; if (mbr_state == MBR_IDLE) return 1; if (!mbr_pid) return 0; if (kill(mbr_pid, SIGUSR1) == -1) success = 0; free_pending_data(); result = write(mbr_cmd_fd, "\n#\n", 3); if (result != 3) success = 0; do { result = read(mbr_audio_fd, dummybuf, sizeof(dummybuf)); } while (result > 0); if (result != -1 || errno != EAGAIN) success = 0; if (!mbrola_has_errors() && success) mbr_state = MBR_IDLE; return success; } int read_MBR(void *buffer, int nb_samples) { int result = receive_from_mbrola(buffer, nb_samples * 2); if (result > 0) result /= 2; return result; } int write_MBR(const char *data) { mbr_state = MBR_NEWDATA; return send_to_mbrola(data); } int flush_MBR(void) { return send_to_mbrola("\n#\n") == 3; } int getFreq_MBR(void) { return mbr_samplerate; } void setVolumeRatio_MBR(float value) { if (value == mbr_volume) return; mbr_volume = value; if (mbr_state != MBR_IDLE) return; /* * We have no choice but to kill and restart mbrola with * the new argument here. */ stop_mbrola(); init_MBR(mbr_voice_path); } int lastErrorStr_MBR(char *buffer, int bufsize) { int result; if (mbr_pid) mbrola_has_errors(); result = snprintf(buffer, bufsize, "%s", mbr_errorbuf); return result >= bufsize ? (bufsize - 1) : result; } void resetError_MBR(void) { mbr_errorbuf[0] = 0; } #endif // INCLUDE_MBROLA sources_5316/external/espeak/event.cpp0000664000176700017670000004064311674622653016667 0ustar paulpaul/*************************************************************************** * Copyright (C) 2007, Gilles Casse * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ #include "speech.h" #ifdef USE_ASYNC // This source file is only used for asynchronious modes // #include #include #include #include #include #include #include #include "speak_lib.h" #include "event.h" #include "wave.h" #include "debug.h" //> // // // event=%s\n","NULL"); } else { static const char* label[] = { "LIST_TERMINATED", "WORD", "SENTENCE", "MARK", "PLAY", "END", "MSG_TERMINATED" }; SHOW("event_display > event=0x%x\n",event); SHOW("event_display > type=%s\n",label[event->type]); SHOW("event_display > uid=%d\n",event->unique_identifier); SHOW("event_display > text_position=%d\n",event->text_position); SHOW("event_display > length=%d\n",event->length); SHOW("event_display > audio_position=%d\n",event->audio_position); SHOW("event_display > sample=%d\n",event->sample); SHOW("event_display > user_data=0x%x\n",event->user_data); } #endif } //> //type) { case espeakEVENT_MARK: case espeakEVENT_PLAY: if (event->id.name) { a_event->id.name = strdup(event->id.name); } break; default: break; } } event_display(a_event); return a_event; } //> //type = espeakEVENT_SENTENCE // * 0, 1 or several calls: event->type = espeakEVENT_WORD // * Last call: event->type = espeakEVENT_MSG_TERMINATED // static void event_notify(espeak_EVENT* event) { ENTER("event_notify"); static unsigned int a_old_uid = 0; espeak_EVENT events[2]; memcpy(&events[0],event,sizeof(espeak_EVENT)); // the event parameter in the callback function should be an array of eventd memcpy(&events[1],event,sizeof(espeak_EVENT)); events[1].type = espeakEVENT_LIST_TERMINATED; // ... terminated by an event type=0 if (event && my_callback) { event_display(event); switch(event->type) { case espeakEVENT_SENTENCE: my_callback(NULL, 0, events); a_old_uid = event->unique_identifier; break; case espeakEVENT_MSG_TERMINATED: case espeakEVENT_MARK: case espeakEVENT_WORD: case espeakEVENT_END: case espeakEVENT_PHONEME: { // jonsd - I'm not sure what this is for. gilles says it's for when Gnome Speech reads a file of blank lines if (a_old_uid != event->unique_identifier) { espeak_EVENT_TYPE a_new_type = events[0].type; events[0].type = espeakEVENT_SENTENCE; my_callback(NULL, 0, events); events[0].type = a_new_type; usleep(50000); } my_callback(NULL, 0, events); a_old_uid = event->unique_identifier; } break; default: case espeakEVENT_LIST_TERMINATED: case espeakEVENT_PLAY: break; } } } //> //type) { case espeakEVENT_MSG_TERMINATED: event_notify(event); break; case espeakEVENT_MARK: case espeakEVENT_PLAY: if(event->id.name) { free((void*)(event->id.name)); } break; default: break; } free(event); return 1; } //> // locked\n"); espeak_EVENT* a_event = event_copy(event); a_error = push(a_event); if (a_error != EE_OK) { event_delete(a_event); } SHOW_TIME("event_declare > unlocking\n"); a_status = pthread_mutex_unlock(&my_mutex); } // TBD: remove the comment // reminder: code in comment. // This wait can lead to an underrun // // if (!a_status && !my_event_is_running && (a_error == EE_OK)) // { // // quit when command is actually started // // (for possible forthcoming 'end of command' checks) SHOW_TIME("event_declare > post my_sem_start_is_required\n"); sem_post(&my_sem_start_is_required); // int val=1; // while (val) // { // usleep(50000); // TBD: event? // sem_getvalue(&my_sem_start_is_required, &val); // } // } if (a_status != 0) { a_error = EE_INTERNAL_ERROR; } return a_error; } //> // locked\n"); if (a_status != 0) { return EE_INTERNAL_ERROR; } if (my_event_is_running) { SHOW_TIME("event_stop > post my_sem_stop_is_required\n"); sem_post(&my_sem_stop_is_required); a_event_is_running = 1; } else { init(); // clear pending events } SHOW_TIME("event_stop > unlocking\n"); a_status = pthread_mutex_unlock(&my_mutex); if (a_status != 0) { return EE_INTERNAL_ERROR; } if (a_event_is_running) { SHOW_TIME("event_stop > wait for my_sem_stop_is_acknowledged\n"); while ((sem_wait(&my_sem_stop_is_acknowledged) == -1) && errno == EINTR) { continue; // Restart when interrupted by handler } SHOW_TIME("event_stop > get my_sem_stop_is_acknowledged\n"); } SHOW_TIME("LEAVE event_stop\n"); return EE_OK; } //> // sleep_until_timeout_or_stop_request > start sem_timedwait from %d.%09lu to %d.%09lu \n", to.tv_sec, to.tv_nsec, ts.tv_sec, ts.tv_nsec); while ((err = sem_timedwait(&my_sem_stop_is_required, &ts)) == -1 && errno == EINTR) { continue; // Restart when interrupted by handler } assert (gettimeofday(&tv, NULL) != -1); SHOW("polling_thread > sleep_until_timeout_or_stop_request > stop sem_timedwait %d.%09lu \n", tv.tv_sec, tv.tv_usec*1000); if (err == 0) { SHOW("polling_thread > sleep_until_timeout_or_stop_request > %s\n","stop required!"); a_stop_is_required=1; // stop required } return a_stop_is_required; } //> // // locking\n"); int a_status = pthread_mutex_lock(&my_mutex); SHOW_TIME("polling_thread > locked (my_event_is_running = 0)\n"); my_event_is_running = 0; pthread_mutex_unlock(&my_mutex); SHOW_TIME("polling_thread > unlocked\n"); SHOW_TIME("polling_thread > wait for my_sem_start_is_required\n"); while ((sem_wait(&my_sem_start_is_required) == -1) && errno == EINTR) { continue; // Restart when interrupted by handler } SHOW_TIME("polling_thread > get my_sem_start_is_required\n"); a_status = pthread_mutex_lock(&my_mutex); SHOW_TIME("polling_thread > locked (my_event_is_running = 1)\n"); my_event_is_running = 1; pthread_mutex_unlock(&my_mutex); SHOW_TIME("polling_thread > unlocked\n"); a_stop_is_required=0; a_status = sem_getvalue(&my_sem_stop_is_required, &a_stop_is_required); if ((a_status==0) && a_stop_is_required) { SHOW("polling_thread > stop required (%d)\n", __LINE__); while(0 == sem_trywait(&my_sem_stop_is_required)) { }; } else { a_stop_is_required=0; } // In this loop, my_event_is_running = 1 while (head && !a_stop_is_required) { SHOW_TIME("polling_thread > check head\n"); while(0 == sem_trywait(&my_sem_start_is_required)) { }; espeak_EVENT* event = (espeak_EVENT*)(head->data); assert(event); uint32_t time_in_ms = 0; int err = get_remaining_time((uint32_t)event->sample, &time_in_ms, &a_stop_is_required); if (a_stop_is_required) { break; } else if (err != 0) { // No available time: the event is deleted. SHOW("polling_thread > %s\n","audio device down"); a_status = pthread_mutex_lock(&my_mutex); SHOW_TIME("polling_thread > locked\n"); event_delete( (espeak_EVENT*)pop()); a_status = pthread_mutex_unlock(&my_mutex); SHOW_TIME("polling_thread > unlocked\n"); } else if (time_in_ms==0) { // the event is already reached. if (my_callback) { event_notify(event); // the user_data (and the type) are cleaned to be sure // that MSG_TERMINATED is called twice (at delete time too). event->type=espeakEVENT_LIST_TERMINATED; event->user_data=NULL; } a_status = pthread_mutex_lock(&my_mutex); SHOW_TIME("polling_thread > locked\n"); event_delete( (espeak_EVENT*)pop()); a_status = pthread_mutex_unlock(&my_mutex); SHOW_TIME("polling_thread > unlocked\n"); a_stop_is_required=0; a_status = sem_getvalue(&my_sem_stop_is_required, &a_stop_is_required); if ((a_status==0) && a_stop_is_required) { SHOW("polling_thread > stop required (%d)\n", __LINE__); while(0 == sem_trywait(&my_sem_stop_is_required)) { }; } else { a_stop_is_required=0; } } else { // The event will be notified soon: sleep until timeout or stop request a_stop_is_required = sleep_until_timeout_or_stop_request(time_in_ms); } } a_status = pthread_mutex_lock(&my_mutex); SHOW_TIME("polling_thread > locked\n"); SHOW_TIME("polling_thread > my_event_is_running = 0\n"); my_event_is_running = 0; if(!a_stop_is_required) { a_status = sem_getvalue(&my_sem_stop_is_required, &a_stop_is_required); if ((a_status==0) && a_stop_is_required) { SHOW("polling_thread > stop required (%d)\n", __LINE__); while(0 == sem_trywait(&my_sem_stop_is_required)) { }; } else { a_stop_is_required=0; } } a_status = pthread_mutex_unlock(&my_mutex); SHOW_TIME("polling_thread > unlocked\n"); if (a_stop_is_required) { SHOW("polling_thread > %s\n","stop required!"); // no mutex required since the stop command is synchronous // and waiting for my_sem_stop_is_acknowledged init(); // acknowledge the stop request SHOW_TIME("polling_thread > post my_sem_stop_is_acknowledged\n"); a_status = sem_post(&my_sem_stop_is_acknowledged); } } return NULL; } //> // push"); assert((!head && !tail) || (head && tail)); if (the_data == NULL) { SHOW("event > push > event=0x%x\n", NULL); return EE_INTERNAL_ERROR; } if (node_counter >= MAX_NODE_COUNTER) { SHOW("event > push > %s\n", "EE_BUFFER_FULL"); return EE_BUFFER_FULL; } node *n = (node *)malloc(sizeof(node)); if (n == NULL) { return EE_INTERNAL_ERROR; } if (head == NULL) { head = n; tail = n; } else { tail->next = n; tail = n; } tail->next = NULL; tail->data = the_data; node_counter++; SHOW("event > push > counter=%d (uid=%d)\n",node_counter,((espeak_EVENT*)the_data)->unique_identifier); return EE_OK; } static void* pop() { ENTER("event > pop"); void* the_data = NULL; assert((!head && !tail) || (head && tail)); if (head != NULL) { node* n = head; the_data = n->data; head = n->next; free(n); node_counter--; SHOW("event > pop > event=0x%x (counter=%d, uid=%d)\n",the_data, node_counter,((espeak_EVENT*)the_data)->unique_identifier); } if(head == NULL) { tail = NULL; } return the_data; } static void init() { ENTER("event > init"); while (event_delete( (espeak_EVENT*)pop() )) {} node_counter = 0; } //> // sources_5316/external/espeak/wave.cpp0000664000176700017670000010042511674622653016503 0ustar paulpaul/*************************************************************************** * Copyright (C) 2007, Gilles Casse * * based on AudioIO.cc (Audacity-1.2.4b) and wavegen.cpp * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ #include "speech.h" #ifdef USE_ASYNC // This source file is only used for asynchronious modes #include #include #include #include #include #include #include #include "portaudio.h" #ifndef PLATFORM_WINDOWS #include #endif #include "wave.h" #include "debug.h" // // myRead=0x%x, myWrite=0x%x, BUFFER_LENGTH=0x%x, myReadPosition = myWritePosition = 0\n", (int)myRead, (int)myWrite, BUFFER_LENGTH); } static unsigned int get_used_mem() { char* aRead = myRead; char* aWrite = myWrite; unsigned int used = 0; assert ((aRead >= myBuffer) && (aRead <= myBuffer + BUFFER_LENGTH) && (aWrite >= myBuffer) && (aWrite <= myBuffer + BUFFER_LENGTH)); if (aRead < aWrite) { used = aWrite - aRead; } else { used = aWrite + BUFFER_LENGTH - aRead; } SHOW("get_used_mem > %d\n", used); return used; } //> // Pa_StartStream=%d (%s)\n", err, Pa_GetErrorText(err)); #if USE_PORTAUDIO == 19 if(err == paStreamIsNotStopped) { SHOW_TIME("start_stream > restart stream (begin)"); // not sure why we need this, but PA v19 seems to need it err = Pa_StopStream(pa_stream); SHOW("start_stream > Pa_StopStream=%d (%s)\n", err, Pa_GetErrorText(err)); err = Pa_StartStream(pa_stream); SHOW("start_stream > Pa_StartStream=%d (%s)\n", err, Pa_GetErrorText(err)); SHOW_TIME("start_stream > restart stream (end)"); } #endif } //> // myReadPosition=%u, framesPerBuffer=%lu (n=0x%x) \n",(int)myReadPosition, framesPerBuffer, n); if (aWrite >= myRead) { if((size_t)(aWrite - myRead) >= n) { memcpy(outputBuffer, myRead, n); myRead += n; } else { SHOW_TIME("pa_callback > underflow"); aResult=1; // paComplete; mInCallbackFinishedState = true; size_t aUsedMem=0; aUsedMem = (size_t)(aWrite - myRead); if (aUsedMem) { memcpy(outputBuffer, myRead, aUsedMem); } char* p = (char*)outputBuffer + aUsedMem; memset(p, 0, n - aUsedMem); // myReadPosition += aUsedMem/(out_channels*sizeof(uint16_t)); myRead = aWrite; } } else // myRead > aWrite { if ((size_t)(myBuffer + BUFFER_LENGTH - myRead) >= n) { memcpy(outputBuffer, myRead, n); myRead += n; } else if ((size_t)(aWrite + BUFFER_LENGTH - myRead) >= n) { int aTopMem = myBuffer + BUFFER_LENGTH - myRead; if (aTopMem) { SHOW("pa_callback > myRead=0x%x, aTopMem=0x%x\n",(int)myRead, (int)aTopMem); memcpy(outputBuffer, myRead, aTopMem); } int aRest = n - aTopMem; if (aRest) { SHOW("pa_callback > myRead=0x%x, aRest=0x%x\n",(int)myRead, (int)aRest); char* p = (char*)outputBuffer + aTopMem; memcpy(p, myBuffer, aRest); } myRead = myBuffer + aRest; } else { SHOW_TIME("pa_callback > underflow"); aResult=1; // paComplete; int aTopMem = myBuffer + BUFFER_LENGTH - myRead; if (aTopMem) { SHOW("pa_callback > myRead=0x%x, aTopMem=0x%x\n",(int)myRead, (int)aTopMem); memcpy(outputBuffer, myRead, aTopMem); } int aRest = aWrite - myBuffer; if (aRest) { SHOW("pa_callback > myRead=0x%x, aRest=0x%x\n",(int)myRead, (int)aRest); char* p = (char*)outputBuffer + aTopMem; memcpy(p, myBuffer, aRest); } size_t aUsedMem = aTopMem + aRest; char* p = (char*)outputBuffer + aUsedMem; memset(p, 0, n - aUsedMem); // myReadPosition += aUsedMem/(out_channels*sizeof(uint16_t)); myRead = aWrite; } } SHOW("pa_callback > myRead=%x\n",(int)myRead); // #if USE_PORTAUDIO == 18 // if(aBufferEmpty) // { // static int end_timer = 0; // if(end_timer == 0) // end_timer = 4; // if(end_timer > 0) // { // end_timer--; // if(end_timer == 0) // return(1); // } // } // return(0); // #else #ifdef ARCH_BIG { // BIG-ENDIAN, swap the order of bytes in each sound sample in the portaudio buffer int c; unsigned char *out_ptr; unsigned char *out_end; out_ptr = (unsigned char *)outputBuffer; out_end = out_ptr + framesPerBuffer*2 * out_channels; while(out_ptr < out_end) { c = out_ptr[0]; out_ptr[0] = out_ptr[1]; out_ptr[1] = c; out_ptr += 2; } } #endif return(aResult); //#endif } // end of WaveCallBack //> void wave_flush(void* theHandler) { ENTER("wave_flush"); if (my_stream_could_start) { // #define buf 1024 // static char a_buffer[buf*2]; // memset(a_buffer,0,buf*2); // wave_write(theHandler, a_buffer, buf*2); start_stream(); } } // already active"); return(0); } if(active < 0) { out_channels = 1; #if USE_PORTAUDIO == 18 // err = Pa_OpenDefaultStream(&pa_stream,0,1,paInt16,wave_samplerate,FRAMES_PER_BUFFER,N_WAV_BUF,pa_callback,(void *)userdata); PaDeviceID playbackDevice = Pa_GetDefaultOutputDeviceID(); PaError err = Pa_OpenStream( &pa_stream, /* capture parameters */ paNoDevice, 0, paInt16, NULL, /* playback parameters */ playbackDevice, out_channels, paInt16, NULL, /* general parameters */ wave_samplerate, FRAMES_PER_BUFFER, 0, //paClipOff | paDitherOff, paNoFlag, pa_callback, (void *)userdata); SHOW("wave_open_sound > Pa_OpenDefaultStream(1): err=%d (%s)\n",err, Pa_GetErrorText(err)); if(err == paInvalidChannelCount) { SHOW_TIME("wave_open_sound > try stereo"); // failed to open with mono, try stereo out_channels = 2; // myOutputParameters.channelCount = out_channels; PaError err = Pa_OpenStream( &pa_stream, /* capture parameters */ paNoDevice, 0, paInt16, NULL, /* playback parameters */ playbackDevice, out_channels, paInt16, NULL, /* general parameters */ wave_samplerate, FRAMES_PER_BUFFER, 0, //paClipOff | paDitherOff, paNoFlag, pa_callback, (void *)userdata); // err = Pa_OpenDefaultStream(&pa_stream,0,2,paInt16, // wave_samplerate, // FRAMES_PER_BUFFER, // N_WAV_BUF,pa_callback,(void *)userdata); SHOW("wave_open_sound > Pa_OpenDefaultStream(2): err=%d (%s)\n",err, Pa_GetErrorText(err)); err=0; // avoid warning } mInCallbackFinishedState = false; // v18 only #else myOutputParameters.channelCount = out_channels; unsigned long framesPerBuffer = paFramesPerBufferUnspecified; err = Pa_OpenStream( &pa_stream, NULL, /* no input */ &myOutputParameters, wave_samplerate, framesPerBuffer, paNoFlag, // paClipOff | paDitherOff, pa_callback, (void *)userdata); if ((err!=paNoError) && (err!=paInvalidChannelCount)) //err==paUnanticipatedHostError { fprintf(stderr, "wave_open_sound > Pa_OpenStream : err=%d (%s)\n",err,Pa_GetErrorText(err)); framesPerBuffer = FRAMES_PER_BUFFER; err = Pa_OpenStream( &pa_stream, NULL, /* no input */ &myOutputParameters, wave_samplerate, framesPerBuffer, paNoFlag, // paClipOff | paDitherOff, pa_callback, (void *)userdata); } if(err == paInvalidChannelCount) { SHOW_TIME("wave_open_sound > try stereo"); // failed to open with mono, try stereo out_channels = 2; myOutputParameters.channelCount = out_channels; err = Pa_OpenStream( &pa_stream, NULL, /* no input */ &myOutputParameters, wave_samplerate, framesPerBuffer, paNoFlag, // paClipOff | paDitherOff, pa_callback, (void *)userdata); // err = Pa_OpenDefaultStream(&pa_stream,0,2,paInt16,(double)wave_samplerate,FRAMES_PER_BUFFER,pa_callback,(void *)userdata); } mInCallbackFinishedState = false; #endif } SHOW("wave_open_sound > %s\n","LEAVE"); return (err != paNoError); } //> //maxOutputChannels; myOutputParameters.channelCount = 1; myOutputParameters.sampleFormat = paInt16; // Latency greater than 100ms for avoiding glitches // (e.g. when moving a window in a graphical desktop) // deviceInfo = Pa_GetDeviceInfo(selectedDevice); if (deviceInfo) { double aLatency = deviceInfo->defaultLowOutputLatency; // double aCoeff = round(0.100 / aLatency); // myOutputParameters.suggestedLatency = aCoeff * aLatency; // to avoid glitches ? myOutputParameters.suggestedLatency = aLatency; // for faster response ? SHOW("Device=%d, myOutputParameters.suggestedLatency=%f, aCoeff=%f\n", selectedDevice, myOutputParameters.suggestedLatency, aCoeff); } else { myOutputParameters.suggestedLatency = (double)0.1; // 100ms SHOW("Device=%d, myOutputParameters.suggestedLatency=%f (default)\n", selectedDevice, myOutputParameters.suggestedLatency); } //pdi->defaultLowOutputLatency; myOutputParameters.hostApiSpecificStreamInfo = NULL; } #endif static void select_device(const char* the_api) { ENTER("select_device"); #if (USE_PORTAUDIO == 19) int numDevices = Pa_GetDeviceCount(); if( numDevices < 0 ) { SHOW( "ERROR: Pa_CountDevices returned 0x%x\n", numDevices ); assert(0); } PaDeviceIndex i=0, selectedIndex=0, defaultAlsaIndex=numDevices; const PaDeviceInfo *deviceInfo=NULL; const PaDeviceInfo *selectedDeviceInfo=NULL; if(option_device_number >= 0) { selectedIndex = option_device_number; selectedDeviceInfo = Pa_GetDeviceInfo(selectedIndex); } if(selectedDeviceInfo == NULL) { for( i=0; ihostApi ); if (hostInfo && hostInfo->type == paALSA) { // Check (once) the default output device if (defaultAlsaIndex == numDevices) { defaultAlsaIndex = hostInfo->defaultOutputDevice; const PaDeviceInfo *deviceInfo = Pa_GetDeviceInfo( defaultAlsaIndex ); update_output_parameters(defaultAlsaIndex, deviceInfo); if (Pa_IsFormatSupported(NULL, &myOutputParameters, wave_samplerate) == 0) { SHOW( "select_device > ALSA (default), name=%s (#%d)\n", deviceInfo->name, defaultAlsaIndex); selectedIndex = defaultAlsaIndex; selectedDeviceInfo = deviceInfo; break; } } // if the default output device does not match, // look for the device with the highest number of output channels SHOW( "select_device > ALSA, i=%d (numDevices=%d)\n", i, numDevices); update_output_parameters(i, deviceInfo); if (Pa_IsFormatSupported(NULL, &myOutputParameters, wave_samplerate) == 0) { SHOW( "select_device > ALSA, name=%s (#%d)\n", deviceInfo->name, i); if (!selectedDeviceInfo || (selectedDeviceInfo->maxOutputChannels < deviceInfo->maxOutputChannels)) { selectedIndex = i; selectedDeviceInfo = deviceInfo; } } } } } if (selectedDeviceInfo) { update_output_parameters(selectedIndex, selectedDeviceInfo); } else { i = Pa_GetDefaultOutputDevice(); deviceInfo = Pa_GetDeviceInfo( i ); update_output_parameters(i, deviceInfo); } #endif } //> // int wave_Close(void* theHandler) // { // SHOW_TIME("WaveCloseSound"); // // PaError active; // // check whether speaking has finished, and close the stream // if(pa_stream != NULL) // { // Pa_CloseStream(pa_stream); // pa_stream = NULL; // init_buffer(); // // #if USE_PORTAUDIO == 18 // // active = Pa_StreamActive(pa_stream); // // #else // // active = Pa_IsStreamActive(pa_stream); // // #endif // // if(active == 0) // // { // // SHOW_TIME("WaveCloseSound > ok, not active"); // // Pa_CloseStream(pa_stream); // // pa_stream = NULL; // // return(1); // // } // } // return(0); // } // // Failed to initialise the PortAudio sound"); } } //> // // 1 channel > memcpy %x (%d bytes)\n", (int)myWrite, theSizeInBytes); memcpy(dest, src, theSizeInBytes); bytes_written = theSizeInBytes; } else // copy for 2 channels (stereo) { SHOW("copyBuffer > 2 channels > memcpy %x (%d bytes)\n", (int)myWrite, theSizeInBytes); i = 0; a_dest = (uint16_t* )dest; a_src = (uint16_t* )src; for(i=0; i // wave_open_sound\n"); if (0 != wave_open_sound()) { SHOW_TIME("wave_write > wave_open_sound fails!"); return 0; } my_stream_could_start=1; } else if (!wave_is_busy(NULL)) { my_stream_could_start = 1; } assert(BUFFER_LENGTH >= bytes_to_write); if (myWrite >= myBuffer + BUFFER_LENGTH) { myWrite = myBuffer; } // end if (myWrite >= myBuffer + BUFFER_LENGTH) size_t aTotalFreeMem=0; char* aRead = myRead; SHOW("wave_write > aRead=%x, myWrite=%x\n", (int)aRead, (int)myWrite); while (1) { if (my_callback_is_output_enabled && (0==my_callback_is_output_enabled())) { SHOW_TIME("wave_write > my_callback_is_output_enabled: no!"); return 0; } aRead = myRead; // write pointer is before read pointer? if (myWrite >= aRead) { aTotalFreeMem = aRead + BUFFER_LENGTH - myWrite; } else // read pointer is before write pointer! { aTotalFreeMem = aRead - myWrite; } // end if (myWrite >= aRead) if (aTotalFreeMem>1) { // -1 because myWrite must be different of aRead // otherwise buffer would be considered as empty aTotalFreeMem -= 1; } // end if (aTotalFreeMem>1) if (aTotalFreeMem >= bytes_to_write) { break; } // end if (aTotalFreeMem >= bytes_to_write) //SHOW_TIME("wave_write > wait"); SHOW("wave_write > wait: aTotalFreeMem=%d\n", aTotalFreeMem); SHOW("wave_write > aRead=%x, myWrite=%x\n", (int)aRead, (int)myWrite); usleep(10000); } // end while (1) aRead = myRead; // write pointer is ahead the read pointer? if (myWrite >= aRead) { SHOW_TIME("wave_write > myWrite >= aRead"); // determine remaining free memory to the end of the ringbuffer size_t aFreeMem = myBuffer + BUFFER_LENGTH - myWrite; // is enough linear space available (regardless 1 or 2 channels)? if (aFreeMem >= bytes_to_write) { // copy direct - no wrap around at end of ringbuffer needed myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer, theSize); } else // not enough linear space available { // 2 channels (stereo)? if (out_channels == 2) { // copy with wrap around at the end of ringbuffer copyBuffer(myWrite, theMono16BitsWaveBuffer, aFreeMem/2); myWrite = myBuffer; myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer+aFreeMem/2, theSize - aFreeMem/2); } else // 1 channel (mono) { // copy with wrap around at the end of ringbuffer copyBuffer(myWrite, theMono16BitsWaveBuffer, aFreeMem); myWrite = myBuffer; myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer+aFreeMem, theSize - aFreeMem); } // end if (out_channels == 2) } // end if (aFreeMem >= bytes_to_write) } // if (myWrite >= aRead) else // read pointer is ahead the write pointer { SHOW_TIME("wave_write > myWrite <= aRead"); myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer, theSize); } // end if (myWrite >= aRead) bytes_written = bytes_to_write; myWritePosition += theSize/sizeof(uint16_t); // add number of samples if (my_stream_could_start && (get_used_mem() >= out_channels * sizeof(uint16_t) * FRAMES_PER_BUFFER)) { start_stream(); } // end if (my_stream_could_start && (get_used_mem() >= out_channels * sizeof(uint16_t) * FRAMES_PER_BUFFER)) SHOW_TIME("wave_write > LEAVE"); return bytes_written; } //> // ENTER"); static int aStopStreamCount = 0; #if (USE_PORTAUDIO == 19) if( pa_stream == NULL ) { SHOW_TIME("wave_close > LEAVE (NULL stream)"); return 0; } if( Pa_IsStreamStopped( pa_stream ) ) { SHOW_TIME("wave_close > LEAVE (stopped)"); return 0; } #else if( pa_stream == NULL ) { SHOW_TIME("wave_close > LEAVE (NULL stream)"); return 0; } if( Pa_StreamActive( pa_stream ) == false && mInCallbackFinishedState == false ) { SHOW_TIME("wave_close > LEAVE (not active)"); return 0; } #endif // Avoid race condition by making sure this function only // gets called once at a time aStopStreamCount++; if (aStopStreamCount != 1) { SHOW_TIME("wave_close > LEAVE (stopStreamCount)"); return 0; } // Comment from Audacity-1.2.4b adapted to the eSpeak context. // // We got here in one of two ways: // // 1. The calling program calls the espeak_Cancel function and we // therefore want to stop as quickly as possible. // So we use AbortStream(). If this is // the case the portaudio stream is still in the Running state // (see PortAudio state machine docs). // // 2. The callback told PortAudio to stop the stream since it had // reached the end of the selection. // The event polling thread discovered this by noticing that // wave_is_busy() returned false. // wave_is_busy() (which calls Pa_GetStreamActive()) will not return // false until all buffers have finished playing, so we can call // AbortStream without losing any samples. If this is the case // we are in the "callback finished state" (see PortAudio state // machine docs). // // The moral of the story: We can call AbortStream safely, without // losing samples. // // DMM: This doesn't seem to be true; it seems to be necessary to // call StopStream if the callback brought us here, and AbortStream // if the user brought us here. // #if (USE_PORTAUDIO == 19) if (pa_stream) { Pa_AbortStream( pa_stream ); SHOW_TIME("wave_close > Pa_AbortStream (end)"); Pa_CloseStream( pa_stream ); SHOW_TIME("wave_close > Pa_CloseStream (end)"); pa_stream = NULL; mInCallbackFinishedState = false; } #else if (pa_stream) { if (mInCallbackFinishedState) { Pa_StopStream( pa_stream ); SHOW_TIME("wave_close > Pa_StopStream (end)"); } else { Pa_AbortStream( pa_stream ); SHOW_TIME("wave_close > Pa_AbortStream (end)"); } Pa_CloseStream( pa_stream ); SHOW_TIME("wave_close > Pa_CloseStream (end)"); pa_stream = NULL; mInCallbackFinishedState = false; } #endif init_buffer(); aStopStreamCount = 0; // last action SHOW_TIME("wave_close > LEAVE"); return 0; } // int wave_close(void* theHandler) // { // ENTER("wave_close"); // if(pa_stream != NULL) // { // PaError err = Pa_AbortStream(pa_stream); // SHOW_TIME("wave_close > Pa_AbortStream (end)"); // SHOW("wave_close Pa_AbortStream > err=%d\n",err); // while(1) // { // PaError active; // #if USE_PORTAUDIO == 18 // active = Pa_StreamActive(pa_stream); // #else // active = Pa_IsStreamActive(pa_stream); // #endif // if (active != 1) // { // break; // } // SHOW("wave_close > active=%d\n",err); // usleep(10000); /* sleep until playback has finished */ // } // err = Pa_CloseStream( pa_stream ); // SHOW_TIME("wave_close > Pa_CloseStream (end)"); // SHOW("wave_close Pa_CloseStream > err=%d\n",err); // pa_stream = NULL; // init_buffer(); // } // return 0; // } //> // // // myReadPosition=%u\n", myReadPosition); return myReadPosition; } uint32_t wave_get_write_position(void* theHandler) { SHOW("wave_get_write_position > myWritePosition=%u\n", myWritePosition); return myWritePosition; } int wave_get_remaining_time(uint32_t sample, uint32_t* time) { double a_time=0; if (!time || !pa_stream) { SHOW("event get_remaining_time> %s\n","audio device not available"); return -1; } if (sample > myReadPosition) { // TBD: take in account time suplied by portaudio V18 API a_time = sample - myReadPosition; a_time = 0.5 + (a_time * 1000.0) / wave_samplerate; } else { a_time = 0; } SHOW("wave_get_remaining_time > sample=%d, time=%d\n", sample, (uint32_t)a_time); *time = (uint32_t)a_time; return 0; } //> // //tv_sec = tv.tv_sec; ts->tv_nsec = tv.tv_usec*1000; } void add_time_in_ms(struct timespec *ts, int time_in_ms) { if (!ts) { return; } uint64_t t_ns = (uint64_t)ts->tv_nsec + 1000000 * (uint64_t)time_in_ms; while(t_ns >= ONE_BILLION) { SHOW("event > add_time_in_ms ns: %d sec %Lu nsec \n", ts->tv_sec, t_ns); ts->tv_sec += 1; t_ns -= ONE_BILLION; } ts->tv_nsec = (long int)t_ns; } #endif // USE_ASYNC //> sources_5316/external/espeak/espeak_command.h0000644000176700017670000000743611721443315020147 0ustar paulpaul#ifndef ESPEAK_COMMAND_H #define ESPEAK_COMMAND_H #ifndef PLATFORM_WINDOWS #include #endif #include "speak_lib.h" enum t_espeak_type { ET_TEXT, ET_MARK, ET_KEY, ET_CHAR, ET_PARAMETER, ET_PUNCTUATION_LIST, ET_VOICE_NAME, ET_VOICE_SPEC, ET_TERMINATED_MSG }; typedef struct { unsigned int unique_identifier; void* text; size_t size; unsigned int position; espeak_POSITION_TYPE position_type; unsigned int end_position; unsigned int flags; void* user_data; } t_espeak_text; typedef struct { unsigned int unique_identifier; void* text; size_t size; const char* index_mark; unsigned int end_position; unsigned int flags; void* user_data; } t_espeak_mark; typedef struct { unsigned int unique_identifier; void* user_data; wchar_t character; } t_espeak_character; typedef struct { unsigned int unique_identifier; void* user_data; const char* key_name; } t_espeak_key; typedef struct { unsigned int unique_identifier; void* user_data; } t_espeak_terminated_msg; typedef struct { espeak_PARAMETER parameter; int value; int relative; } t_espeak_parameter; enum t_command_state { CS_UNDEFINED, // The command has just been created CS_PENDING, // stored in the fifo CS_PROCESSED // processed }; typedef struct { enum t_espeak_type type; t_command_state state; union command { t_espeak_text my_text; t_espeak_mark my_mark; t_espeak_key my_key; t_espeak_character my_char; t_espeak_parameter my_param; const wchar_t* my_punctuation_list; const char *my_voice_name; espeak_VOICE my_voice_spec; t_espeak_terminated_msg my_terminated_msg; } u; } t_espeak_command; t_espeak_command* create_espeak_text(const void *text, size_t size, unsigned int position, espeak_POSITION_TYPE position_type, unsigned int end_position, unsigned int flags, void* user_data); t_espeak_command* create_espeak_mark(const void *text, size_t size, const char *index_mark, unsigned int end_position, unsigned int flags, void* user_data); t_espeak_command* create_espeak_terminated_msg(unsigned int unique_identifier, void* user_data); t_espeak_command* create_espeak_key(const char *key_name, void *user_data); t_espeak_command* create_espeak_char(wchar_t character, void *user_data); t_espeak_command* create_espeak_parameter(espeak_PARAMETER parameter, int value, int relative); t_espeak_command* create_espeak_punctuation_list(const wchar_t *punctlist); t_espeak_command* create_espeak_voice_name(const char *name); t_espeak_command* create_espeak_voice_spec(espeak_VOICE *voice_spec); void process_espeak_command( t_espeak_command* the_command); int delete_espeak_command( t_espeak_command* the_command); void display_espeak_command(t_espeak_command* the_command); espeak_ERROR sync_espeak_Synth(unsigned int unique_identifier, const void *text, size_t size, unsigned int position, espeak_POSITION_TYPE position_type, unsigned int end_position, unsigned int flags, void* user_data); espeak_ERROR sync_espeak_Synth_Mark(unsigned int unique_identifier, const void *text, size_t size, const char *index_mark, unsigned int end_position, unsigned int flags, void* user_data); void sync_espeak_Key(const char *key); void sync_espeak_Char(wchar_t character); void sync_espeak_SetPunctuationList(const wchar_t *punctlist); void sync_espeak_SetParameter(espeak_PARAMETER parameter, int value, int relative); int sync_espeak_SetVoiceByName(const char *name); int sync_espeak_SetVoiceByProperties(espeak_VOICE *voice_selector); espeak_ERROR SetVoiceByName(const char *name); espeak_ERROR SetVoiceByProperties(espeak_VOICE *voice_selector); void SetParameter(int parameter, int value, int relative); int sync_espeak_terminated_msg(unsigned int unique_identifier, void* user_data); //> #endif sources_5316/external/espeak/portaudio.h0000664000176700017670000003700511674622653017217 0ustar paulpaul// NOTE: Copy this file to portaudio.h in order to compile with V18 portaudio #ifndef PORT_AUDIO_H #define PORT_AUDIO_H #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ /* * $Id: portaudio.h,v 1.5 2002/03/26 18:04:22 philburk Exp $ * PortAudio Portable Real-Time Audio Library * PortAudio API Header File * Latest version available at: http://www.audiomulch.com/portaudio/ * * Copyright (c) 1999-2000 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. * */ typedef int PaError; typedef enum { paNoError = 0, paHostError = -10000, paInvalidChannelCount, paInvalidSampleRate, paInvalidDeviceId, paInvalidFlag, paSampleFormatNotSupported, paBadIODeviceCombination, paInsufficientMemory, paBufferTooBig, paBufferTooSmall, paNullCallback, paBadStreamPtr, paTimedOut, paInternalError, paDeviceUnavailable } PaErrorNum; /* Pa_Initialize() is the library initialisation function - call this before using the library. */ PaError Pa_Initialize( void ); /* Pa_Terminate() is the library termination function - call this after using the library. */ PaError Pa_Terminate( void ); /* Pa_GetHostError() returns a host specific error code. This can be called after receiving a PortAudio error code of paHostError. */ long Pa_GetHostError( void ); /* Pa_GetErrorText() translates the supplied PortAudio error number into a human readable message. */ const char *Pa_GetErrorText( PaError errnum ); /* Sample formats These are formats used to pass sound data between the callback and the stream. Each device has a "native" format which may be used when optimum efficiency or control over conversion is required. Formats marked "always available" are supported (emulated) by all PortAudio implementations. The floating point representation (paFloat32) uses +1.0 and -1.0 as the maximum and minimum respectively. paUInt8 is an unsigned 8 bit format where 128 is considered "ground" */ typedef unsigned long PaSampleFormat; #define paFloat32 ((PaSampleFormat) (1<<0)) /*always available*/ #define paInt16 ((PaSampleFormat) (1<<1)) /*always available*/ #define paInt32 ((PaSampleFormat) (1<<2)) /*always available*/ #define paInt24 ((PaSampleFormat) (1<<3)) #define paPackedInt24 ((PaSampleFormat) (1<<4)) #define paInt8 ((PaSampleFormat) (1<<5)) #define paUInt8 ((PaSampleFormat) (1<<6)) #define paCustomFormat ((PaSampleFormat) (1<<16)) /* Device enumeration mechanism. Device ids range from 0 to Pa_CountDevices()-1. Devices may support input, output or both. */ typedef int PaDeviceID; #define paNoDevice -1 int Pa_CountDevices( void ); typedef struct { int structVersion; const char *name; int maxInputChannels; int maxOutputChannels; /* Number of discrete rates, or -1 if range supported. */ int numSampleRates; /* Array of supported sample rates, or {min,max} if range supported. */ const double *sampleRates; PaSampleFormat nativeSampleFormats; } PaDeviceInfo; /* Pa_GetDefaultInputDeviceID(), Pa_GetDefaultOutputDeviceID() return the default device ids for input and output respectively, or paNoDevice if no device is available. The result can be passed to Pa_OpenStream(). On the PC, the user can specify a default device by setting an environment variable. For example, to use device #1. set PA_RECOMMENDED_OUTPUT_DEVICE=1 The user should first determine the available device ids by using the supplied application "pa_devs". */ PaDeviceID Pa_GetDefaultInputDeviceID( void ); PaDeviceID Pa_GetDefaultOutputDeviceID( void ); /* Pa_GetDeviceInfo() returns a pointer to an immutable PaDeviceInfo structure for the device specified. If the device parameter is out of range the function returns NULL. PortAudio manages the memory referenced by the returned pointer, the client must not manipulate or free the memory. The pointer is only guaranteed to be valid between calls to Pa_Initialize() and Pa_Terminate(). */ const PaDeviceInfo* Pa_GetDeviceInfo( PaDeviceID device ); /* PaTimestamp is used to represent a continuous sample clock with arbitrary start time that can be used for syncronization. The type is used for the outTime argument to the PortAudioCallback and as the result of Pa_StreamTime() */ typedef double PaTimestamp; /* PortAudioCallback is implemented by PortAudio clients. inputBuffer and outputBuffer are arrays of interleaved samples, the format, packing and number of channels used by the buffers are determined by parameters to Pa_OpenStream() (see below). framesPerBuffer is the number of sample frames to be processed by the callback. outTime is the time in samples when the buffer(s) processed by this callback will begin being played at the audio output. See also Pa_StreamTime() userData is the value of a user supplied pointer passed to Pa_OpenStream() intended for storing synthesis data etc. return value: The callback can return a non-zero value to stop the stream. This may be useful in applications such as soundfile players where a specific duration of output is required. However, it is not necessary to utilise this mechanism as StopStream() will also terminate the stream. A callback returning a non-zero value must fill the entire outputBuffer. NOTE: None of the other stream functions may be called from within the callback function except for Pa_GetCPULoad(). */ typedef int (PortAudioCallback)( void *inputBuffer, void *outputBuffer, unsigned long framesPerBuffer, PaTimestamp outTime, void *userData ); /* Stream flags These flags may be supplied (ored together) in the streamFlags argument to the Pa_OpenStream() function. */ #define paNoFlag (0) #define paClipOff (1<<0) /* disable default clipping of out of range samples */ #define paDitherOff (1<<1) /* disable default dithering */ #define paPlatformSpecificFlags (0x00010000) typedef unsigned long PaStreamFlags; /* A single PortAudioStream provides multiple channels of real-time input and output audio streaming to a client application. Pointers to PortAudioStream objects are passed between PortAudio functions. */ typedef void PortAudioStream; #define PaStream PortAudioStream /* Pa_OpenStream() opens a stream for either input, output or both. stream is the address of a PortAudioStream pointer which will receive a pointer to the newly opened stream. inputDevice is the id of the device used for input (see PaDeviceID above.) inputDevice may be paNoDevice to indicate that an input device is not required. numInputChannels is the number of channels of sound to be delivered to the callback. It can range from 1 to the value of maxInputChannels in the PaDeviceInfo record for the device specified by the inputDevice parameter. If inputDevice is paNoDevice numInputChannels is ignored. inputSampleFormat is the sample format of inputBuffer provided to the callback function. inputSampleFormat may be any of the formats described by the PaSampleFormat enumeration (see above). PortAudio guarantees support for the device's native formats (nativeSampleFormats in the device info record) and additionally 16 and 32 bit integer and 32 bit floating point formats. Support for other formats is implementation defined. inputDriverInfo is a pointer to an optional driver specific data structure containing additional information for device setup or stream processing. inputDriverInfo is never required for correct operation. If not used inputDriverInfo should be NULL. outputDevice is the id of the device used for output (see PaDeviceID above.) outputDevice may be paNoDevice to indicate that an output device is not required. numOutputChannels is the number of channels of sound to be supplied by the callback. See the definition of numInputChannels above for more details. outputSampleFormat is the sample format of the outputBuffer filled by the callback function. See the definition of inputSampleFormat above for more details. outputDriverInfo is a pointer to an optional driver specific data structure containing additional information for device setup or stream processing. outputDriverInfo is never required for correct operation. If not used outputDriverInfo should be NULL. sampleRate is the desired sampleRate. For full-duplex streams it is the sample rate for both input and output framesPerBuffer is the length in sample frames of all internal sample buffers used for communication with platform specific audio routines. Wherever possible this corresponds to the framesPerBuffer parameter passed to the callback function. numberOfBuffers is the number of buffers used for multibuffered communication with the platform specific audio routines. If you pass zero, then an optimum value will be chosen for you internally. This parameter is provided only as a guide - and does not imply that an implementation must use multibuffered i/o when reliable double buffering is available (such as SndPlayDoubleBuffer() on the Macintosh.) streamFlags may contain a combination of flags ORed together. These flags modify the behaviour of the streaming process. Some flags may only be relevant to certain buffer formats. callback is a pointer to a client supplied function that is responsible for processing and filling input and output buffers (see above for details.) userData is a client supplied pointer which is passed to the callback function. It could for example, contain a pointer to instance data necessary for processing the audio buffers. return value: Upon success Pa_OpenStream() returns PaNoError and places a pointer to a valid PortAudioStream in the stream argument. The stream is inactive (stopped). If a call to Pa_OpenStream() fails a non-zero error code is returned (see PaError above) and the value of stream is invalid. */ PaError Pa_OpenStream( PortAudioStream** stream, PaDeviceID inputDevice, int numInputChannels, PaSampleFormat inputSampleFormat, void *inputDriverInfo, PaDeviceID outputDevice, int numOutputChannels, PaSampleFormat outputSampleFormat, void *outputDriverInfo, double sampleRate, unsigned long framesPerBuffer, unsigned long numberOfBuffers, PaStreamFlags streamFlags, PortAudioCallback *callback, void *userData ); /* Pa_OpenDefaultStream() is a simplified version of Pa_OpenStream() that opens the default input and/or output devices. Most parameters have identical meaning to their Pa_OpenStream() counterparts, with the following exceptions: If either numInputChannels or numOutputChannels is 0 the respective device is not opened. This has the same effect as passing paNoDevice in the device arguments to Pa_OpenStream(). sampleFormat applies to both the input and output buffers. */ PaError Pa_OpenDefaultStream( PortAudioStream** stream, int numInputChannels, int numOutputChannels, PaSampleFormat sampleFormat, double sampleRate, unsigned long framesPerBuffer, unsigned long numberOfBuffers, PortAudioCallback *callback, void *userData ); /* Pa_CloseStream() closes an audio stream, flushing any pending buffers. */ PaError Pa_CloseStream( PortAudioStream* ); /* Pa_StartStream() and Pa_StopStream() begin and terminate audio processing. Pa_StopStream() waits until all pending audio buffers have been played. Pa_AbortStream() stops playing immediately without waiting for pending buffers to complete. */ PaError Pa_StartStream( PortAudioStream *stream ); PaError Pa_StopStream( PortAudioStream *stream ); PaError Pa_AbortStream( PortAudioStream *stream ); /* Pa_StreamActive() returns one (1) when the stream is active (ie playing or recording audio), zero (0) when not playing, or a negative error number if the stream is invalid. The stream is active between calls to Pa_StartStream() and Pa_StopStream(), but may also become inactive if the callback returns a non-zero value. In the latter case, the stream is considered inactive after the last buffer has finished playing. */ PaError Pa_StreamActive( PortAudioStream *stream ); /* Pa_StreamTime() returns the current output time in samples for the stream. This time may be used as a time reference (for example synchronizing audio to MIDI). */ PaTimestamp Pa_StreamTime( PortAudioStream *stream ); /* Pa_GetCPULoad() returns the CPU Load for the stream. The "CPU Load" is a fraction of total CPU time consumed by the stream's audio processing routines including, but not limited to the client supplied callback. A value of 0.5 would imply that PortAudio and the sound generating callback was consuming roughly 50% of the available CPU time. This function may be called from the callback function or the application. */ double Pa_GetCPULoad( PortAudioStream* stream ); /* Pa_GetMinNumBuffers() returns the minimum number of buffers required by the current host based on minimum latency. On the PC, for the DirectSound implementation, latency can be optionally set by user by setting an environment variable. For example, to set latency to 200 msec, put: set PA_MIN_LATENCY_MSEC=200 in the AUTOEXEC.BAT file and reboot. If the environment variable is not set, then the latency will be determined based on the OS. Windows NT has higher latency than Win95. */ int Pa_GetMinNumBuffers( int framesPerBuffer, double sampleRate ); /* Pa_Sleep() puts the caller to sleep for at least 'msec' milliseconds. You may sleep longer than the requested time so don't rely on this for accurate musical timing. Pa_Sleep() is provided as a convenience for authors of portable code (such as the tests and examples in the PortAudio distribution.) */ void Pa_Sleep( long msec ); /* Pa_GetSampleSize() returns the size in bytes of a single sample in the supplied PaSampleFormat, or paSampleFormatNotSupported if the format is no supported. */ PaError Pa_GetSampleSize( PaSampleFormat format ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PORT_AUDIO_H */ sources_5316/external/espeak/fifo.cpp0000664000176700017670000003354611674622653016475 0ustar paulpaul/*************************************************************************** * Copyright (C) 2007, Gilles Casse * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ #include "speech.h" #ifdef USE_ASYNC // This source file is only used for asynchronious modes // #include #include #include #include #include #include #include #include #include #include "fifo.h" #include "wave.h" #include "debug.h" //> // // wait for my_sem_stop_is_acknowledged\n"); while ((sem_wait(&my_sem_stop_is_acknowledged) == -1) && errno == EINTR) { continue; // Restart when interrupted by handler } SHOW_TIME("fifo > get my_sem_stop_is_acknowledged\n"); } //> // locked\n"); a_error = push(the_command); SHOW_TIME("fifo_add_command > unlocking\n"); a_status = pthread_mutex_unlock(&my_mutex); } if (!a_status && !my_command_is_running && (a_error == EE_OK)) { // quit when command is actually started // (for possible forthcoming 'end of command' checks) SHOW_TIME("fifo_add_command > post my_sem_start_is_required\n"); sem_post(&my_sem_start_is_required); int val=1; while (val) { usleep(50000); // TBD: event? sem_getvalue(&my_sem_start_is_required, &val); } } if (a_status != 0) { a_error = EE_INTERNAL_ERROR; } SHOW_TIME("LEAVE fifo_add_command"); return a_error; } //> // locked\n"); if (node_counter+1 >= MAX_NODE_COUNTER) { SHOW("push > %s\n", "EE_BUFFER_FULL"); a_error = EE_BUFFER_FULL; } else { push(command1); push(command2); } SHOW_TIME("fifo_add_command > unlocking\n"); a_status = pthread_mutex_unlock(&my_mutex); } if (!a_status && !my_command_is_running && (a_error == EE_OK)) { // quit when one command is actually started // (for possible forthcoming 'end of command' checks) SHOW_TIME("fifo_add_command > post my_sem_start_is_required\n"); sem_post(&my_sem_start_is_required); int val=1; while (val) { usleep(50000); // TBD: event? sem_getvalue(&my_sem_start_is_required, &val); } } if (a_status != 0) { a_error = EE_INTERNAL_ERROR; } SHOW_TIME("LEAVE fifo_add_commands"); return a_error; } //> // locked\n"); if (a_status != 0) { return EE_INTERNAL_ERROR; } if (my_command_is_running) { a_command_is_running = 1; my_stop_is_required = 1; SHOW_TIME("fifo_stop > my_stop_is_required = 1\n"); } SHOW_TIME("fifo_stop > unlocking\n"); a_status = pthread_mutex_unlock(&my_mutex); if (a_status != 0) { return EE_INTERNAL_ERROR; } if (a_command_is_running) { SHOW_TIME("fifo_stop > wait for my_sem_stop_is_acknowledged\n"); while ((sem_wait(&my_sem_stop_is_acknowledged) == -1) && errno == EINTR) { continue; // Restart when interrupted by handler } SHOW_TIME("fifo_stop > get my_sem_stop_is_acknowledged\n"); } SHOW_TIME("fifo_stop > my_stop_is_required = 0\n"); my_stop_is_required = 0; SHOW_TIME("LEAVE fifo_stop\n"); return EE_OK; } //> // aResult = %d\n",my_command_is_running); return my_command_is_running; } // int pause () // { // ENTER("pause"); // // TBD // // if (espeakPause (espeakHandle, 1)) // return true; // } // int resume () // { // ENTER("resume"); // // TBD // // if (espeakPause (espeakHandle, 0)) // return true; // } //> // sleep_until_start_request_or_inactivity > ENTER"); int a_start_is_required=0; // Wait for the start request (my_sem_start_is_required). // Besides this, if the audio stream is still busy, // check from time to time its end. // The end of the stream is confirmed by several checks // for filtering underflow. // int i=0; while((i<= MAX_INACTIVITY_CHECK) && !a_start_is_required) { if (wave_is_busy( NULL) ) { i = 0; } else { i++; } int err=0; struct timespec ts; struct timeval tv; clock_gettime2( &ts); #ifdef DEBUG_ENABLED struct timespec to; to.tv_sec = ts.tv_sec; to.tv_nsec = ts.tv_nsec; #endif add_time_in_ms( &ts, INACTIVITY_TIMEOUT); SHOW("fifo > sleep_until_start_request_or_inactivity > start sem_timedwait (start_is_required) from %d.%09lu to %d.%09lu \n", to.tv_sec, to.tv_nsec, ts.tv_sec, ts.tv_nsec); while ((err = sem_timedwait(&my_sem_start_is_required, &ts)) == -1 && errno == EINTR) { continue; } assert (gettimeofday(&tv, NULL) != -1); SHOW("fifo > sleep_until_start_request_or_inactivity > stop sem_timedwait (start_is_required, err=%d) %d.%09lu \n", err, tv.tv_sec, tv.tv_usec*1000); if (err==0) { a_start_is_required = 1; } } SHOW_TIME("fifo > sleep_until_start_request_or_inactivity > LEAVE"); return a_start_is_required; } //> // close_stream > ENTER\n"); // Warning: a wave_close can be already required by // an external command (espeak_Cancel + fifo_stop), if so: // my_stop_is_required = 1; int a_status = pthread_mutex_lock(&my_mutex); assert (!a_status); int a_stop_is_required = my_stop_is_required; if (!a_stop_is_required) { my_command_is_running = 1; } a_status = pthread_mutex_unlock(&my_mutex); if (!a_stop_is_required) { wave_close(NULL); int a_status = pthread_mutex_lock(&my_mutex); assert (!a_status); my_command_is_running = 0; a_stop_is_required = my_stop_is_required; a_status = pthread_mutex_unlock(&my_mutex); if (a_stop_is_required) { // acknowledge the stop request SHOW_TIME("fifo > close_stream > post my_sem_stop_is_acknowledged\n"); int a_status = sem_post(&my_sem_stop_is_acknowledged); assert( a_status != -1); } } SHOW_TIME("fifo > close_stream > LEAVE\n"); } //> // post my_sem_stop_is_acknowledged\n"); // announce that thread is started sem_post(&my_sem_stop_is_acknowledged); int look_for_inactivity=0; while(1) { SHOW_TIME("say_thread > wait for my_sem_start_is_required\n"); int a_start_is_required = 0; if (look_for_inactivity) { a_start_is_required = sleep_until_start_request_or_inactivity(); if (!a_start_is_required) { close_stream(); } } look_for_inactivity = 1; if (!a_start_is_required) { while ((sem_wait(&my_sem_start_is_required) == -1) && errno == EINTR) { continue; // Restart when interrupted by handler } } SHOW_TIME("say_thread > get my_sem_start_is_required\n"); SHOW_TIME("say_thread > my_command_is_running = 1\n"); my_command_is_running = 1; while( my_command_is_running) { SHOW_TIME("say_thread > locking\n"); int a_status = pthread_mutex_lock(&my_mutex); assert (!a_status); t_espeak_command* a_command = (t_espeak_command*)pop(); if (a_command == NULL) { SHOW_TIME("say_thread > text empty (talking=0) \n"); a_status = pthread_mutex_unlock(&my_mutex); SHOW_TIME("say_thread > unlocked\n"); SHOW_TIME("say_thread > my_command_is_running = 0\n"); my_command_is_running = 0; } else { display_espeak_command(a_command); // purge start semaphore SHOW_TIME("say_thread > purge my_sem_start_is_required\n"); while(0 == sem_trywait(&my_sem_start_is_required)) { }; if (my_stop_is_required) { SHOW_TIME("say_thread > my_command_is_running = 0\n"); my_command_is_running = 0; } SHOW_TIME("say_thread > unlocking\n"); a_status = pthread_mutex_unlock(&my_mutex); if (my_command_is_running) { process_espeak_command(a_command); } delete_espeak_command(a_command); } } if (my_stop_is_required) { // no mutex required since the stop command is synchronous // and waiting for my_sem_stop_is_acknowledged init(); // purge start semaphore SHOW_TIME("say_thread > purge my_sem_start_is_required\n"); while(0==sem_trywait(&my_sem_start_is_required)) { }; // acknowledge the stop request SHOW_TIME("say_thread > post my_sem_stop_is_acknowledged\n"); int a_status = sem_post(&my_sem_stop_is_acknowledged); assert( a_status != -1); } // and wait for the next start SHOW_TIME("say_thread > wait for my_sem_start_is_required\n"); } return NULL; } int fifo_is_command_enabled() { SHOW("ENTER fifo_is_command_enabled=%d\n",(int)(0 == my_stop_is_required)); return (0 == my_stop_is_required); } //> // push"); assert((!head && !tail) || (head && tail)); if (the_command == NULL) { SHOW("push > command=0x%x\n", NULL); return EE_INTERNAL_ERROR; } if (node_counter >= MAX_NODE_COUNTER) { SHOW("push > %s\n", "EE_BUFFER_FULL"); return EE_BUFFER_FULL; } node *n = (node *)malloc(sizeof(node)); if (n == NULL) { return EE_INTERNAL_ERROR; } if (head == NULL) { head = n; tail = n; } else { tail->next = n; tail = n; } tail->next = NULL; tail->data = the_command; node_counter++; SHOW("push > counter=%d\n",node_counter); the_command->state = CS_PENDING; display_espeak_command(the_command); return EE_OK; } static t_espeak_command* pop() { ENTER("fifo > pop"); t_espeak_command* the_command = NULL; assert((!head && !tail) || (head && tail)); if (head != NULL) { node* n = head; the_command = n->data; head = n->next; free(n); node_counter--; SHOW("pop > command=0x%x (counter=%d)\n",the_command, node_counter); } if(head == NULL) { tail = NULL; } display_espeak_command(the_command); return the_command; } static void init() { ENTER("fifo > init"); while (delete_espeak_command( pop() )) {} node_counter = 0; } //> // sources_5316/external/espeak/espeak.cpp0000664000176700017670000004255111674622653017016 0ustar paulpaul/*************************************************************************** * Copyright (C) 2006 to 2007 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #include #include #include #ifndef NEED_GETOPT #include #endif #include #include #include "speak_lib.h" // This version of the command-line speak program uses the // libespeak.so.1 library static const char *help_text = "\nespeak [options] [\"\"]\n\n" "-f Text file to speak\n" "--stdin Read text input from stdin instead of a file\n\n" "If neither -f nor --stdin, then are spoken, or if none then text\n" "is spoken from stdin, each line separately.\n\n" "-a \n" "\t Amplitude, 0 to 200, default is 100\n" "-g \n" "\t Word gap. Pause between words, units of 10mS at the default speed\n" "-k \n" "\t Indicate capital letters with: 1=sound, 2=the word \"capitals\",\n" "\t higher values indicate a pitch increase (try -k20).\n" "-l \n" "\t Line length. If not zero (which is the default), consider\n" "\t lines less than this length as end-of-clause\n" "-p \n" "\t Pitch adjustment, 0 to 99, default is 50\n" "-s \n" "\t Speed in words per minute, 80 to 450, default is 175\n" "-v \n" "\t Use voice file of this name from espeak-data/voices\n" "-w \n" "\t Write speech to this WAV file, rather than speaking it directly\n" "-b\t Input text encoding, 1=UTF8, 2=8 bit, 4=16 bit \n" "-m\t Interpret SSML markup, and ignore other < > tags\n" "-q\t Quiet, don't produce any speech (may be useful with -x)\n" "-x\t Write phoneme mnemonics to stdout\n" "-X\t Write phonemes mnemonics and translation trace to stdout\n" "-z\t No final sentence pause at the end of the text\n" "--compile=\n" "\t Compile pronunciation rules and dictionary from the current\n" "\t directory. specifies the language\n" "--ipa Write phonemes to stdout using International Phonetic Alphabet\n" "--path=\"\"\n" "\t Specifies the directory containing the espeak-data directory\n" "--pho Write mbrola phoneme data (.pho) to stdout or to the file in --phonout\n" "--phonout=\"\"\n" "\t Write phoneme output from -x -X --ipa and --pho to this file\n" "--punct=\"\"\n" "\t Speak the names of punctuation characters during speaking. If\n" "\t = is omitted, all punctuation is spoken.\n" "--split=\"\"\n" "\t Starts a new WAV file every . Used with -w\n" "--stdout Write speech output to stdout\n" "--voices=\n" "\t List the available voices for the specified language.\n" "\t If is omitted, then list all voices.\n"; int samplerate; int quiet = 0; unsigned int samples_total = 0; unsigned int samples_split = 0; unsigned int samples_split_seconds = 0; unsigned int wavefile_count = 0; FILE *f_wavfile = NULL; char filetype[5]; char wavefile[200]; int GetFileLength(const char *filename) {//==================================== struct stat statbuf; if(stat(filename,&statbuf) != 0) return(0); if((statbuf.st_mode & S_IFMT) == S_IFDIR) return(-2); // a directory return(statbuf.st_size); } // end of GetFileLength void strncpy0(char *dest, const char *source, int size) {//==================================================== if(source!=NULL) { strncpy(dest,source,size); dest[size-1] = 0; } } void DisplayVoices(FILE *f_out, char *language) {//============================================ int ix; const char *p; int len; int count; const espeak_VOICE *v; const char *lang_name; char age_buf[12]; const espeak_VOICE **voices; espeak_VOICE voice_select; static char genders[4] = {' ','M','F',' '}; if((language != NULL) && (language[0] != 0)) { // display only voices for the specified language, in order of priority voice_select.languages = language; voice_select.age = 0; voice_select.gender = 0; voice_select.name = NULL; voices = espeak_ListVoices(&voice_select); } else { voices = espeak_ListVoices(NULL); } fprintf(f_out,"Pty Language Age/Gender VoiceName File Other Langs\n"); for(ix=0; (v = voices[ix]) != NULL; ix++) { count = 0; p = v->languages; while(*p != 0) { len = strlen(p+1); lang_name = p+1; if(v->age == 0) strcpy(age_buf," "); else sprintf(age_buf,"%3d",v->age); if(count==0) { fprintf(f_out,"%2d %-12s%s%c %-17s %-11s ", p[0],lang_name,age_buf,genders[v->gender],v->name,v->identifier); } else { fprintf(f_out,"(%s %d)",lang_name,p[0]); } count++; p += len+2; } fputc('\n',f_out); } } // end of DisplayVoices static void Write4Bytes(FILE *f, int value) {//================================= // Write 4 bytes to a file, least significant first int ix; for(ix=0; ix<4; ix++) { fputc(value & 0xff,f); value = value >> 8; } } int OpenWavFile(char *path, int rate) //=================================== { static unsigned char wave_hdr[44] = { 'R','I','F','F',0x24,0xf0,0xff,0x7f,'W','A','V','E','f','m','t',' ', 0x10,0,0,0,1,0,1,0, 9,0x3d,0,0,0x12,0x7a,0,0, 2,0,0x10,0,'d','a','t','a', 0x00,0xf0,0xff,0x7f}; if(path == NULL) return(2); if(path[0] == 0) return(0); if(strcmp(path,"stdout")==0) f_wavfile = stdout; else f_wavfile = fopen(path,"wb"); if(f_wavfile == NULL) { fprintf(stderr,"Can't write to: '%s'\n",path); return(1); } fwrite(wave_hdr,1,24,f_wavfile); Write4Bytes(f_wavfile,rate); Write4Bytes(f_wavfile,rate * 2); fwrite(&wave_hdr[32],1,12,f_wavfile); return(0); } // end of OpenWavFile static void CloseWavFile() //======================== { unsigned int pos; if((f_wavfile==NULL) || (f_wavfile == stdout)) return; fflush(f_wavfile); pos = ftell(f_wavfile); fseek(f_wavfile,4,SEEK_SET); Write4Bytes(f_wavfile,pos - 8); fseek(f_wavfile,40,SEEK_SET); Write4Bytes(f_wavfile,pos - 44); fclose(f_wavfile); f_wavfile = NULL; } // end of CloseWavFile static int SynthCallback(short *wav, int numsamples, espeak_EVENT *events) {//======================================================================== char fname[210]; if(quiet) return(0); // -q quiet mode if(wav == NULL) { CloseWavFile(); return(0); } while(events->type != 0) { if(events->type == espeakEVENT_SAMPLERATE) { samplerate = events->id.number; samples_split = samples_split_seconds * samplerate; } else if(events->type == espeakEVENT_SENTENCE) { // start a new WAV file when the limit is reached, at this sentence boundary if((samples_split > 0) && (samples_total > samples_split)) { CloseWavFile(); samples_total = 0; wavefile_count++; } } events++; } if(f_wavfile == NULL) { if(samples_split > 0) { sprintf(fname,"%s_%.2d%s",wavefile,wavefile_count+1,filetype); if(OpenWavFile(fname, samplerate) != 0) return(1); } else { if(OpenWavFile(wavefile, samplerate) != 0) return(1); } } if(numsamples > 0) { samples_total += numsamples; fwrite(wav,numsamples*2,1,f_wavfile); } return(0); } #ifdef NEED_GETOPT struct option { char *name; int has_arg; int *flag; int val; }; int optind; static int optional_argument; static const char *arg_opts = "abfgklpsvw"; // which options have arguments static char *opt_string=""; #define no_argument 0 #define required_argument 1 #define optional_argument 2 #endif int main (int argc, char **argv) //============================== { static struct option long_options[] = { /* These options set a flag. */ // {"verbose", no_argument, &verbose_flag, 1}, // {"brief", no_argument, &verbose_flag, 0}, /* These options don't set a flag. We distinguish them by their indices. */ {"help", no_argument, 0, 'h'}, {"stdin", no_argument, 0, 0x100}, {"compile-debug", optional_argument, 0, 0x101}, {"compile", optional_argument, 0, 0x102}, {"punct", optional_argument, 0, 0x103}, {"voices", optional_argument, 0, 0x104}, {"stdout", no_argument, 0, 0x105}, {"split", optional_argument, 0, 0x106}, {"path", required_argument, 0, 0x107}, {"phonout", required_argument, 0, 0x108}, {"pho", no_argument, 0, 0x109}, {"ipa", no_argument, 0, 0x10a}, {0, 0, 0, 0} }; static const char* err_load = "Failed to read "; FILE *f_text=NULL; char *p_text=NULL; FILE *f_phonemes_out = stdout; char *data_path = NULL; // use default path for espeak-data int option_index = 0; int c; int ix; char *optarg2; int value; int flag_stdin = 0; int flag_compile = 0; int filesize = 0; int synth_flags = espeakCHARS_AUTO | espeakPHONEMES | espeakENDPAUSE; int volume = -1; int speed = -1; int pitch = -1; int wordgap = -1; int option_capitals = -1; int option_punctuation = -1; int option_phonemes = 0; int option_mbrola_phonemes = 0; int option_linelength = 0; int option_waveout = 0; espeak_VOICE voice_select; char filename[200]; char voicename[40]; #define N_PUNCTLIST 100 wchar_t option_punctlist[N_PUNCTLIST]; voicename[0] = 0; wavefile[0] = 0; filename[0] = 0; option_punctlist[0] = 0; #ifdef NEED_GETOPT optind = 1; opt_string = ""; while(optind < argc) { int len; char *p; if((c = *opt_string) == 0) { opt_string = argv[optind]; if(opt_string[0] != '-') break; optind++; opt_string++; c = *opt_string; } opt_string++; p = optarg2 = opt_string; if(c == '-') { if(p[0] == 0) break; // -- means don't interpret further - as commands opt_string=""; for(ix=0; ;ix++) { if(long_options[ix].name == 0) break; len = strlen(long_options[ix].name); if(memcmp(long_options[ix].name,p,len)==0) { c = long_options[ix].val; optarg2 = NULL; if((long_options[ix].has_arg != 0) && (p[len]=='=')) { optarg2 = &p[len+1]; } break; } } } else if(strchr(arg_opts,c) != NULL) { opt_string=""; if(optarg2[0]==0) { // the option's value is in the next argument optarg2 = argv[optind++]; } } #else while(true) { c = getopt_long (argc, argv, "a:b:f:g:hk:l:mp:qs:v:w:xXz", long_options, &option_index); /* Detect the end of the options. */ if (c == -1) break; optarg2 = optarg; #endif switch (c) { case 'b': // input character encoding, 8bit, 16bit, UTF8 if((sscanf(optarg2,"%d",&value) == 1) && (value <= 4)) synth_flags |= value; else synth_flags |= espeakCHARS_8BIT; break; case 'h': { const char *version; const char *path_data; espeak_Initialize(AUDIO_OUTPUT_SYNCHRONOUS, 0, data_path, espeakINITIALIZE_DONT_EXIT); version = espeak_Info(&path_data); printf("\n"); printf("eSpeak text-to-speech: %s Data at: %s\n%s", version, path_data, help_text); exit(0); } break; case 'k': option_capitals = atoi(optarg2); break; case 'x': option_phonemes = 1; break; case 'X': option_phonemes = 2; break; case 'm': synth_flags |= espeakSSML; break; case 'p': pitch = atoi(optarg2); break; case 'q': quiet = 1; break; case 'f': strncpy0(filename,optarg2,sizeof(filename)); break; case 'l': option_linelength = atoi(optarg2); break; case 'a': volume = atoi(optarg2); break; case 's': speed = atoi(optarg2); break; case 'g': wordgap = atoi(optarg2); break; case 'v': strncpy0(voicename,optarg2,sizeof(voicename)); break; case 'w': option_waveout = 1; strncpy0(wavefile,optarg2,sizeof(filename)); break; case 'z': // remove pause from the end of a sentence synth_flags &= ~espeakENDPAUSE; break; case 0x100: // --stdin flag_stdin = 1; break; case 0x105: // --stdout option_waveout = 1; strcpy(wavefile,"stdout"); break; case 0x101: // --compile-debug case 0x102: // --compile strncpy0(voicename,optarg2,sizeof(voicename)); flag_compile = c; quiet = 1; break; case 0x103: // --punct option_punctuation = 1; if(optarg2 != NULL) { ix = 0; while((ix < N_PUNCTLIST) && ((option_punctlist[ix] = optarg2[ix]) != 0)) ix++; option_punctlist[N_PUNCTLIST-1] = 0; option_punctuation = 2; } break; case 0x104: // --voices espeak_Initialize(AUDIO_OUTPUT_SYNCHRONOUS,0,data_path,0); DisplayVoices(stdout,optarg2); exit(0); case 0x106: // -- split if(optarg2 == NULL) samples_split_seconds = 30 * 60; // default 30 minutes else samples_split_seconds = atoi(optarg2) * 60; break; case 0x107: // --path data_path = optarg2; break; case 0x108: // --phonout if((f_phonemes_out = fopen(optarg2,"w")) == NULL) { fprintf(stderr,"Can't write to: %s\n",optarg2); } break; case 0x109: // --pho option_mbrola_phonemes = 16; break; case 0x10a: // --ipa option_phonemes = 3; break; default: exit(0); } } if(option_waveout || quiet) { // writing to a file (or no output), we can use synchronous mode samplerate = espeak_Initialize(AUDIO_OUTPUT_SYNCHRONOUS,0,data_path,0); samples_split = samplerate * samples_split_seconds; espeak_SetSynthCallback(SynthCallback); if(samples_split) { char *extn; extn = strrchr(wavefile,'.'); if((extn != NULL) && ((wavefile + strlen(wavefile) - extn) <= 4)) { strcpy(filetype,extn); *extn = 0; } } } else { // play the sound output samplerate = espeak_Initialize(AUDIO_OUTPUT_PLAYBACK,0,data_path,0); } if(voicename[0] == 0) strcpy(voicename,"default"); if(espeak_SetVoiceByName(voicename) != EE_OK) { memset(&voice_select,0,sizeof(voice_select)); voice_select.languages = voicename; if(espeak_SetVoiceByProperties(&voice_select) != EE_OK) { fprintf(stderr,"%svoice '%s'\n",err_load,voicename); exit(2); } } if(flag_compile) { // This must be done after the voice is set espeak_CompileDictionary("", stderr, flag_compile & 0x1); exit(0); } // set any non-default values of parameters. This must be done after espeak_Initialize() if(speed > 0) espeak_SetParameter(espeakRATE,speed,0); if(volume >= 0) espeak_SetParameter(espeakVOLUME,volume,0); if(pitch >= 0) espeak_SetParameter(espeakPITCH,pitch,0); if(option_capitals >= 0) espeak_SetParameter(espeakCAPITALS,option_capitals,0); if(option_punctuation >= 0) espeak_SetParameter(espeakPUNCTUATION,option_punctuation,0); if(wordgap >= 0) espeak_SetParameter(espeakWORDGAP,wordgap,0); if(option_linelength > 0) espeak_SetParameter(espeakLINELENGTH,option_linelength,0); if(option_punctuation == 2) espeak_SetPunctuationList(option_punctlist); espeak_SetPhonemeTrace(option_phonemes | option_mbrola_phonemes,f_phonemes_out); if(filename[0]==0) { if((optind < argc) && (flag_stdin == 0)) { // there's a non-option parameter, and no -f or --stdin // use it as text p_text = argv[optind]; } else { f_text = stdin; if(flag_stdin == 0) { flag_stdin = 2; } } } else { filesize = GetFileLength(filename); f_text = fopen(filename,"r"); } if((f_text == NULL) && (p_text == NULL)) { fprintf(stderr,"%sfile '%s'\n",err_load,filename); exit(1); } if(p_text != NULL) { int size; size = strlen(p_text); espeak_Synth(p_text,size+1,0,POS_CHARACTER,0,synth_flags,NULL,NULL); } else if(flag_stdin) { int max = 1000; p_text = (char *)malloc(max); if(flag_stdin == 2) { // line by line input on stdin while(fgets(p_text,max,stdin) != NULL) { p_text[max-1] = 0; espeak_Synth(p_text,max,0,POS_CHARACTER,0,synth_flags,NULL,NULL); } } else { // bulk input on stdin ix = 0; while(!feof(stdin)) { p_text[ix++] = fgetc(stdin); if(ix >= (max-1)) { max += 1000; p_text = (char *)realloc(p_text,max); } } if(ix > 0) { p_text[ix-1] = 0; espeak_Synth(p_text,ix+1,0,POS_CHARACTER,0,synth_flags,NULL,NULL); } } } else if(f_text != NULL) { if((p_text = (char *)malloc(filesize+1)) == NULL) { fprintf(stderr,"Failed to allocate memory %d bytes",filesize); exit(3); } fread(p_text,1,filesize,f_text); p_text[filesize]=0; espeak_Synth(p_text,filesize+1,0,POS_CHARACTER,0,synth_flags,NULL,NULL); fclose(f_text); } espeak_Synchronize(); if(f_phonemes_out != stdout) fclose(f_phonemes_out); // needed for WinCE return(0); } sources_5316/external/espeak/espeakdata_variants.cpp0000664000176700017670000006460111723710247021547 0ustar paulpaul/* File espeakdata_variants.cpp was generated automatically on Thu Feb 23 14:34:18 2012 from files in espeak-data/voices/!v */ #include "espeakdata_FileInMemory.h" #include "Collection.h" #include "FileInMemory.h" #include "melder.h" FilesInMemory create_espeakdata_variants () { try { autoFilesInMemory me = FilesInMemory_create (); static unsigned char espeakdata_variants1_data[94] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 99, 114, 111, 97, 107, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 32, 55, 48, 10, 10, 112, 105, 116, 99, 104, 32, 56, 53, 32, 49, 49, 55, 10, 102, 108, 117, 116, 116, 101, 114, 32, 50, 48, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 56, 48, 32, 49, 49, 48, 10, 10, 10, 10, 0}; autoFileInMemory espeakdata_variants1 = FileInMemory_createWithData (93, reinterpret_cast (&espeakdata_variants1_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/croak", L"croak"); Collection_addItem (me.peek(), espeakdata_variants1.transfer()); static unsigned char espeakdata_variants2_data[325] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 102, 101, 109, 97, 108, 101, 49, 10, 103, 101, 110, 100, 101, 114, 32, 102, 101, 109, 97, 108, 101, 32, 55, 48, 10, 10, 112, 105, 116, 99, 104, 32, 49, 52, 48, 32, 50, 48, 48, 10, 102, 108, 117, 116, 116, 101, 114, 32, 56, 10, 114, 111, 117, 103, 104, 110, 101, 115, 115, 32, 52, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 49, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 50, 48, 32, 32, 56, 48, 32, 49, 56, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 48, 48, 32, 32, 55, 48, 32, 49, 53, 48, 32, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 49, 53, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 49, 48, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 49, 48, 32, 32, 57, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 48, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 45, 49, 48, 32, 45, 49, 48, 32, 45, 50, 48, 32, 45, 50, 48, 32, 48, 32, 48, 32, 52, 48, 32, 54, 48, 10, 0}; autoFileInMemory espeakdata_variants2 = FileInMemory_createWithData (324, reinterpret_cast (&espeakdata_variants2_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/f1", L"f1"); Collection_addItem (me.peek(), espeakdata_variants2.transfer()); static unsigned char espeakdata_variants3_data[358] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 102, 101, 109, 97, 108, 101, 50, 10, 103, 101, 110, 100, 101, 114, 32, 102, 101, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 49, 52, 50, 32, 50, 50, 48, 10, 114, 111, 117, 103, 104, 110, 101, 115, 115, 32, 51, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 49, 48, 32, 32, 56, 48, 32, 49, 54, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 49, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 49, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 48, 32, 48, 32, 45, 49, 48, 32, 45, 49, 48, 32, 48, 32, 48, 32, 49, 48, 32, 52, 48, 10, 98, 114, 101, 97, 116, 104, 32, 48, 32, 50, 32, 51, 32, 51, 32, 51, 32, 51, 32, 51, 32, 50, 10, 101, 99, 104, 111, 32, 49, 52, 48, 32, 49, 48, 10, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 32, 49, 50, 53, 32, 49, 50, 53, 10, 0}; autoFileInMemory espeakdata_variants3 = FileInMemory_createWithData (357, reinterpret_cast (&espeakdata_variants3_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/f2", L"f2"); Collection_addItem (me.peek(), espeakdata_variants3.transfer()); static unsigned char espeakdata_variants4_data[376] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 102, 101, 109, 97, 108, 101, 51, 10, 103, 101, 110, 100, 101, 114, 32, 102, 101, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 49, 52, 48, 32, 50, 52, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 50, 48, 32, 32, 55, 53, 32, 49, 53, 48, 32, 45, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 51, 53, 32, 32, 55, 48, 32, 49, 53, 48, 32, 45, 50, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 50, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 50, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 50, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 50, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 109, 112, 32, 49, 56, 32, 49, 56, 32, 50, 48, 32, 50, 48, 32, 50, 48, 32, 50, 48, 32, 50, 48, 32, 50, 48, 10, 47, 47, 98, 114, 101, 97, 116, 104, 32, 48, 32, 50, 32, 52, 32, 52, 32, 52, 32, 52, 32, 52, 32, 52, 10, 98, 114, 101, 97, 116, 104, 32, 48, 32, 50, 32, 51, 32, 51, 32, 51, 32, 51, 32, 51, 32, 50, 10, 101, 99, 104, 111, 32, 49, 50, 48, 32, 49, 48, 10, 114, 111, 117, 103, 104, 110, 101, 115, 115, 32, 52, 10, 10, 10, 0}; autoFileInMemory espeakdata_variants4 = FileInMemory_createWithData (375, reinterpret_cast (&espeakdata_variants4_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/f3", L"f3"); Collection_addItem (me.peek(), espeakdata_variants4.transfer()); static unsigned char espeakdata_variants5_data[351] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 102, 101, 109, 97, 108, 101, 52, 10, 103, 101, 110, 100, 101, 114, 32, 102, 101, 109, 97, 108, 101, 10, 10, 101, 99, 104, 111, 32, 49, 51, 48, 32, 49, 53, 10, 112, 105, 116, 99, 104, 32, 49, 52, 50, 32, 50, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 50, 48, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 49, 53, 32, 32, 56, 48, 32, 49, 54, 48, 32, 45, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 51, 48, 32, 32, 55, 53, 32, 49, 53, 48, 32, 45, 50, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 50, 51, 32, 32, 55, 53, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 50, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 50, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 49, 48, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 49, 48, 32, 32, 55, 53, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 49, 48, 32, 32, 55, 53, 32, 49, 53, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 45, 50, 48, 32, 45, 50, 48, 32, 45, 50, 48, 32, 45, 50, 48, 32, 48, 32, 48, 32, 50, 48, 32, 49, 50, 48, 10, 115, 116, 114, 101, 115, 115, 65, 109, 112, 32, 49, 56, 32, 49, 54, 32, 50, 48, 32, 50, 48, 32, 50, 48, 32, 50, 48, 32, 50, 48, 32, 50, 48, 10, 0}; autoFileInMemory espeakdata_variants5 = FileInMemory_createWithData (350, reinterpret_cast (&espeakdata_variants5_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/f4", L"f4"); Collection_addItem (me.peek(), espeakdata_variants5.transfer()); static unsigned char espeakdata_variants6_data[426] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 32, 10, 110, 97, 109, 101, 32, 102, 101, 109, 97, 108, 101, 53, 10, 103, 101, 110, 100, 101, 114, 32, 102, 101, 109, 97, 108, 101, 32, 10, 10, 112, 105, 116, 99, 104, 32, 49, 54, 48, 32, 50, 50, 56, 10, 114, 111, 117, 103, 104, 110, 101, 115, 115, 32, 48, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 53, 32, 32, 56, 48, 32, 49, 53, 48, 32, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 49, 48, 32, 32, 56, 48, 32, 49, 54, 48, 32, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 32, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 32, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 49, 53, 32, 32, 56, 48, 32, 50, 48, 48, 32, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 49, 53, 32, 32, 56, 48, 32, 49, 48, 48, 32, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 32, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 48, 48, 32, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 32, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 48, 32, 48, 32, 45, 49, 48, 32, 45, 49, 48, 32, 48, 32, 48, 32, 49, 48, 32, 52, 48, 32, 10, 98, 114, 101, 97, 116, 104, 32, 48, 32, 52, 32, 32, 54, 32, 32, 32, 54, 32, 32, 32, 54, 32, 32, 32, 54, 32, 32, 48, 32, 49, 48, 32, 10, 101, 99, 104, 111, 32, 49, 52, 48, 32, 49, 48, 32, 10, 118, 111, 105, 99, 105, 110, 103, 32, 55, 53, 32, 10, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 32, 49, 53, 48, 32, 49, 53, 48, 10, 98, 114, 101, 97, 116, 104, 119, 32, 49, 53, 48, 32, 49, 53, 48, 32, 50, 48, 48, 32, 50, 48, 48, 32, 52, 48, 48, 32, 52, 48, 48, 32, 10, 0}; autoFileInMemory espeakdata_variants6 = FileInMemory_createWithData (425, reinterpret_cast (&espeakdata_variants6_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/f5", L"f5"); Collection_addItem (me.peek(), espeakdata_variants6.transfer()); static unsigned char espeakdata_variants7_data[39] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 107, 108, 97, 116, 116, 10, 107, 108, 97, 116, 116, 32, 49, 10, 32, 10, 0}; autoFileInMemory espeakdata_variants7 = FileInMemory_createWithData (38, reinterpret_cast (&espeakdata_variants7_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/klatt", L"klatt"); Collection_addItem (me.peek(), espeakdata_variants7.transfer()); static unsigned char espeakdata_variants8_data[39] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 107, 108, 97, 116, 116, 50, 10, 107, 108, 97, 116, 116, 32, 50, 10, 10, 0}; autoFileInMemory espeakdata_variants8 = FileInMemory_createWithData (38, reinterpret_cast (&espeakdata_variants8_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/klatt2", L"klatt2"); Collection_addItem (me.peek(), espeakdata_variants8.transfer()); static unsigned char espeakdata_variants9_data[40] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 107, 108, 97, 116, 116, 51, 10, 107, 108, 97, 116, 116, 32, 51, 10, 32, 10, 0}; autoFileInMemory espeakdata_variants9 = FileInMemory_createWithData (39, reinterpret_cast (&espeakdata_variants9_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/klatt3", L"klatt3"); Collection_addItem (me.peek(), espeakdata_variants9.transfer()); static unsigned char espeakdata_variants10_data[336] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 109, 97, 108, 101, 49, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 32, 55, 48, 10, 10, 112, 105, 116, 99, 104, 32, 55, 53, 32, 49, 48, 57, 10, 102, 108, 117, 116, 116, 101, 114, 32, 53, 10, 114, 111, 117, 103, 104, 110, 101, 115, 115, 32, 52, 10, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 32, 56, 48, 32, 49, 48, 48, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 32, 57, 56, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 32, 57, 55, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 32, 57, 55, 32, 32, 57, 53, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 32, 57, 55, 32, 32, 57, 53, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 32, 57, 55, 32, 32, 56, 53, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 48, 53, 32, 32, 56, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 32, 57, 53, 32, 32, 56, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 48, 48, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 48, 48, 32, 49, 48, 48, 32, 49, 48, 48, 10, 10, 47, 47, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 45, 49, 48, 32, 45, 49, 48, 32, 45, 50, 48, 32, 45, 50, 48, 32, 48, 32, 48, 32, 52, 48, 32, 55, 48, 10, 0}; autoFileInMemory espeakdata_variants10 = FileInMemory_createWithData (335, reinterpret_cast (&espeakdata_variants10_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/m1", L"m1"); Collection_addItem (me.peek(), espeakdata_variants10.transfer()); static unsigned char espeakdata_variants11_data[265] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 109, 97, 108, 101, 50, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 56, 56, 32, 49, 49, 53, 10, 101, 99, 104, 111, 32, 49, 51, 48, 32, 49, 53, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 32, 56, 48, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 32, 57, 48, 32, 32, 56, 53, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 49, 48, 32, 32, 56, 53, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 48, 53, 32, 32, 57, 48, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 48, 48, 32, 32, 57, 48, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 48, 48, 32, 32, 57, 48, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 48, 48, 32, 32, 57, 48, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 48, 48, 32, 32, 57, 48, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 48, 48, 32, 32, 57, 48, 32, 49, 50, 48, 10, 0}; autoFileInMemory espeakdata_variants11 = FileInMemory_createWithData (264, reinterpret_cast (&espeakdata_variants11_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/m2", L"m2"); Collection_addItem (me.peek(), espeakdata_variants11.transfer()); static unsigned char espeakdata_variants12_data[286] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 109, 97, 108, 101, 51, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 56, 48, 32, 49, 50, 50, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 32, 57, 54, 32, 32, 57, 55, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 32, 57, 54, 32, 32, 57, 55, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 32, 57, 54, 32, 49, 48, 51, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 32, 57, 53, 32, 49, 48, 51, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 32, 57, 53, 32, 49, 48, 51, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 48, 48, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 48, 48, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 48, 48, 32, 49, 48, 48, 32, 49, 48, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 49, 48, 32, 49, 48, 32, 48, 32, 48, 32, 48, 32, 48, 32, 45, 51, 48, 32, 45, 51, 48, 10, 0}; autoFileInMemory espeakdata_variants12 = FileInMemory_createWithData (285, reinterpret_cast (&espeakdata_variants12_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/m3", L"m3"); Collection_addItem (me.peek(), espeakdata_variants12.transfer()); static unsigned char espeakdata_variants13_data[291] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 109, 97, 108, 101, 52, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 55, 48, 32, 49, 49, 48, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 51, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 48, 51, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 48, 51, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 48, 51, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 48, 54, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 48, 54, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 48, 54, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 48, 51, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 48, 51, 32, 49, 48, 48, 32, 49, 48, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 45, 49, 48, 32, 45, 49, 48, 32, 45, 51, 48, 32, 45, 51, 48, 32, 48, 32, 48, 32, 54, 48, 32, 57, 48, 10, 0}; autoFileInMemory espeakdata_variants13 = FileInMemory_createWithData (290, reinterpret_cast (&espeakdata_variants13_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/m4", L"m4"); Collection_addItem (me.peek(), espeakdata_variants13.transfer()); static unsigned char espeakdata_variants14_data[263] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 109, 97, 108, 101, 53, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 32, 56, 53, 32, 49, 51, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 32, 57, 48, 32, 32, 56, 53, 32, 49, 51, 48, 32, 32, 52, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 32, 56, 48, 32, 32, 56, 53, 32, 49, 51, 48, 32, 32, 51, 49, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 48, 53, 32, 32, 56, 53, 32, 49, 51, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 48, 53, 32, 32, 56, 53, 32, 49, 51, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 48, 53, 32, 32, 56, 53, 32, 49, 51, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 48, 53, 32, 32, 56, 53, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 48, 53, 32, 32, 56, 53, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 48, 53, 32, 32, 56, 53, 32, 49, 53, 48, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 50, 10, 0}; autoFileInMemory espeakdata_variants14 = FileInMemory_createWithData (262, reinterpret_cast (&espeakdata_variants14_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/m5", L"m5"); Collection_addItem (me.peek(), espeakdata_variants14.transfer()); static unsigned char espeakdata_variants15_data[189] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 109, 97, 108, 101, 54, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 56, 50, 32, 49, 49, 55, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 32, 57, 48, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 48, 48, 32, 32, 57, 48, 32, 49, 52, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 48, 48, 32, 32, 55, 48, 32, 49, 52, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 48, 48, 32, 32, 55, 53, 32, 49, 52, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 48, 48, 32, 32, 56, 48, 32, 49, 52, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 48, 48, 32, 32, 56, 48, 32, 49, 52, 48, 10, 10, 0}; autoFileInMemory espeakdata_variants15 = FileInMemory_createWithData (188, reinterpret_cast (&espeakdata_variants15_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/m6", L"m6"); Collection_addItem (me.peek(), espeakdata_variants15.transfer()); static unsigned char espeakdata_variants16_data[255] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 109, 97, 108, 101, 55, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 32, 55, 53, 32, 49, 50, 53, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 49, 50, 53, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 48, 48, 32, 57, 48, 32, 56, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 48, 48, 32, 55, 48, 32, 57, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 48, 48, 32, 54, 48, 32, 57, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 48, 48, 32, 54, 48, 32, 57, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 32, 55, 53, 32, 53, 48, 32, 57, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 32, 57, 48, 32, 53, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 48, 48, 32, 53, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 48, 48, 32, 53, 48, 32, 49, 48, 48, 10, 118, 111, 105, 99, 105, 110, 103, 32, 49, 53, 53, 10, 10, 0}; autoFileInMemory espeakdata_variants16 = FileInMemory_createWithData (254, reinterpret_cast (&espeakdata_variants16_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/m7", L"m7"); Collection_addItem (me.peek(), espeakdata_variants16.transfer()); static unsigned char espeakdata_variants17_data[187] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 119, 104, 105, 115, 112, 101, 114, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 56, 50, 32, 49, 49, 55, 10, 102, 108, 117, 116, 116, 101, 114, 32, 50, 48, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 32, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 48, 48, 32, 56, 48, 32, 49, 48, 48, 10, 10, 118, 111, 105, 99, 105, 110, 103, 32, 49, 55, 10, 98, 114, 101, 97, 116, 104, 32, 32, 32, 55, 53, 32, 32, 55, 53, 32, 32, 53, 48, 32, 32, 52, 48, 32, 32, 49, 53, 32, 32, 49, 48, 10, 98, 114, 101, 97, 116, 104, 119, 32, 49, 53, 48, 32, 49, 53, 48, 32, 50, 48, 48, 32, 50, 48, 48, 32, 52, 48, 48, 32, 52, 48, 48, 10, 0}; autoFileInMemory espeakdata_variants17 = FileInMemory_createWithData (186, reinterpret_cast (&espeakdata_variants17_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/whisper", L"whisper"); Collection_addItem (me.peek(), espeakdata_variants17.transfer()); static unsigned char espeakdata_variants18_data[393] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 97, 114, 105, 97, 110, 116, 10, 110, 97, 109, 101, 32, 102, 101, 109, 97, 108, 101, 95, 119, 104, 105, 115, 112, 101, 114, 10, 103, 101, 110, 100, 101, 114, 32, 102, 101, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 49, 54, 48, 32, 50, 50, 48, 10, 114, 111, 117, 103, 104, 110, 101, 115, 115, 32, 51, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 53, 32, 32, 32, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 49, 49, 48, 32, 32, 52, 48, 32, 49, 54, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 49, 49, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 49, 49, 53, 32, 32, 56, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 54, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 55, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 56, 32, 49, 49, 48, 32, 32, 55, 48, 32, 49, 53, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 48, 32, 48, 32, 45, 49, 48, 32, 45, 49, 48, 32, 48, 32, 48, 32, 49, 48, 32, 52, 48, 10, 10, 47, 47, 32, 119, 104, 105, 115, 112, 101, 114, 10, 118, 111, 105, 99, 105, 110, 103, 32, 50, 48, 10, 98, 114, 101, 97, 116, 104, 32, 55, 53, 32, 55, 53, 32, 53, 48, 32, 52, 48, 32, 49, 53, 32, 49, 48, 10, 98, 114, 101, 97, 116, 104, 119, 32, 49, 53, 48, 32, 49, 53, 48, 32, 50, 48, 48, 32, 50, 48, 48, 32, 52, 48, 48, 32, 52, 48, 48, 10, 32, 10, 0}; autoFileInMemory espeakdata_variants18 = FileInMemory_createWithData (392, reinterpret_cast (&espeakdata_variants18_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/!v/whisperf", L"whisperf"); Collection_addItem (me.peek(), espeakdata_variants18.transfer()); return me.transfer(); } catch (MelderError) { Melder_throw (L"FilesInMemory not created."); } } sources_5316/external/espeak/synth_mbrola.cpp0000644000176700017670000004175611721443315020240 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2007 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "translate.h" #include "voice.h" int option_mbrola_phonemes; #ifdef INCLUDE_MBROLA extern int Read4Bytes(FILE *f); extern void SetPitch2(voice_t *voice, int pitch1, int pitch2, int *pitch_base, int *pitch_range); extern unsigned char *outbuf; #ifndef PLATFORM_WINDOWS #include "mbrowrap.h" #else #include typedef void (WINAPI *PROCVV)(void); typedef void (WINAPI *PROCVI)(int); typedef void (WINAPI *PROCVF)(float); typedef int (WINAPI *PROCIV)(); typedef int (WINAPI *PROCIC) (char *); typedef int (WINAPI *PROCISI)(short *,int); typedef char* (WINAPI *PROCVCI)(char *,int); PROCIC init_MBR; PROCIC write_MBR; PROCIV flush_MBR; PROCISI read_MBR; PROCVV close_MBR; PROCVV reset_MBR; PROCIV lastError_MBR; PROCVCI lastErrorStr_MBR; PROCVI setNoError_MBR; PROCIV getFreq_MBR; PROCVF setVolumeRatio_MBR; HINSTANCE hinstDllMBR = NULL; BOOL load_MBR() { if(hinstDllMBR != NULL) return TRUE; // already loaded if ((hinstDllMBR=LoadLibraryA("mbrola.dll")) == 0) return FALSE; init_MBR =(PROCIC) GetProcAddress(hinstDllMBR,"init_MBR"); write_MBR =(PROCIC) GetProcAddress(hinstDllMBR,"write_MBR"); flush_MBR =(PROCIV) GetProcAddress(hinstDllMBR,"flush_MBR"); read_MBR =(PROCISI) GetProcAddress(hinstDllMBR,"read_MBR"); close_MBR =(PROCVV) GetProcAddress(hinstDllMBR,"close_MBR"); reset_MBR =(PROCVV) GetProcAddress(hinstDllMBR,"reset_MBR"); lastError_MBR =(PROCIV) GetProcAddress(hinstDllMBR,"lastError_MBR"); lastErrorStr_MBR =(PROCVCI) GetProcAddress(hinstDllMBR,"lastErrorStr_MBR"); setNoError_MBR =(PROCVI) GetProcAddress(hinstDllMBR,"setNoError_MBR"); setVolumeRatio_MBR =(PROCVF) GetProcAddress(hinstDllMBR,"setVolumeRatio_MBR"); return TRUE; } void unload_MBR() { if (hinstDllMBR) { FreeLibrary (hinstDllMBR); hinstDllMBR=NULL; } } #endif // windows static MBROLA_TAB *mbrola_tab = NULL; static int mbrola_control = 0; static int mbr_name_prefix = 0; espeak_ERROR LoadMbrolaTable(const char *mbrola_voice, const char *phtrans, int srate) {//=================================================================================== // Load a phoneme name translation table from espeak-data/mbrola int size; int ix; int *pw; FILE *f_in; char path[sizeof(path_home)+15]; mbrola_name[0] = 0; mbrola_delay = 0; mbr_name_prefix = 0; if(mbrola_voice == NULL) { samplerate = samplerate_native; SetParameter(espeakVOICETYPE,0,0); return(EE_OK); } sprintf(path,"%s/mbrola/%s",path_home,mbrola_voice); #ifdef PLATFORM_POSIX // if not found, then also look in // usr/share/mbrola/xx, /usr/share/mbrola/xx/xx, /usr/share/mbrola/voices/xx if(GetFileLength(path) <= 0) { sprintf(path,"/usr/share/mbrola/%s",mbrola_voice); if(GetFileLength(path) <= 0) { sprintf(path,"/usr/share/mbrola/%s/%s",mbrola_voice,mbrola_voice); if(GetFileLength(path) <= 0) { sprintf(path,"/usr/share/mbrola/voices/%s",mbrola_voice); } } } close_MBR(); #endif #ifdef PLATFORM_WINDOWS if(load_MBR() == FALSE) // load mbrola.dll { fprintf(stderr, "Can't load mbrola.dll\n"); return(EE_INTERNAL_ERROR); } #endif if(init_MBR(path) != 0) // initialise the required mbrola voice return(EE_NOT_FOUND); setNoError_MBR(1); // don't stop on phoneme errors // read eSpeak's mbrola phoneme translation data, eg. en1_phtrans sprintf(path,"%s/mbrola_ph/%s",path_home,phtrans); size = GetFileLength(path); if((f_in = fopen(path,"rb")) == NULL) { close_MBR(); return(EE_NOT_FOUND); } if((mbrola_tab = (MBROLA_TAB *)realloc(mbrola_tab,size)) == NULL) { fclose(f_in); close_MBR(); return(EE_INTERNAL_ERROR); } mbrola_control = Read4Bytes(f_in); pw = (int *)mbrola_tab; for(ix=4; ixmnemonic; pr = mbrola_tab; while(pr->name != 0) { if(mnem == pr->name) { if(pr->next_phoneme == 0) found = 1; else if((pr->next_phoneme == ':') && (plist->synthflags & SFLAG_LENGTHEN)) { found = 1; } else { if(pr->control & 2) other_ph = ph_prev; else if((pr->control & 8) && ((plist+1)->newword)) other_ph = phoneme_tab[phPAUSE]; // don't match the next phoneme over a word boundary else other_ph = ph_next; if((pr->next_phoneme == other_ph->mnemonic) || ((pr->next_phoneme == 2) && (other_ph->type == phVOWEL)) || ((pr->next_phoneme == '_') && (other_ph->type == phPAUSE))) { found = 1; } } if((pr->control & 4) && (plist->newword == 0)) // only at start of word found = 0; if((pr->control & 0x40) && (plist[1].newword == 0)) // only at the end of a word found = 0; if((pr->control & 0x20) && (plist->stresslevel < plist->wordstress)) found = 0; // only in stressed syllables if(found) { *name2 = pr->mbr_name2; *split = pr->percent; *control = pr->control; if(pr->control & 0x10) { mbr_name_prefix = pr->mbr_name; return(0); } mnem = pr->mbr_name; break; } } pr++; } if(mbr_name_prefix != 0) { mnem = (mnem << 8) | (mbr_name_prefix & 0xff); } mbr_name_prefix = 0; return(mnem); } static char *WritePitch(int env, int pitch1, int pitch2, int split, int final) {//=========================================================================== // final=1: only give the final pitch value. int x; int ix; int pitch_base; int pitch_range; int p1,p2,p_end; unsigned char *pitch_env; int max = -1; int min = 999; int y_max=0; int y_min=0; int env100 = 80; // apply the pitch change only over this proportion of the mbrola phoneme(s) int y2; int y[4]; int env_split; char buf[50]; static char output[50]; output[0] = 0; pitch_env = envelope_data[env]; SetPitch2(voice, pitch1, pitch2, &pitch_base, &pitch_range); env_split = (split * 128)/100; if(env_split < 0) env_split = 0-env_split; // find max and min in the pitch envelope for(x=0; x<128; x++) { if(pitch_env[x] > max) { max = pitch_env[x]; y_max = x; } if(pitch_env[x] < min) { min = pitch_env[x]; y_min = x; } } // set an additional pitch point half way through the phoneme. // but look for a maximum or a minimum and use that instead y[2] = 64; if((y_max > 0) && (y_max < 127)) { y[2] = y_max; } if((y_min > 0) && (y_min < 127)) { y[2] = y_min; } y[1] = y[2] / 2; y[3] = y[2] + (127 - y[2])/2; // set initial pitch p1 = ((pitch_env[0]*pitch_range)>>8) + pitch_base; // Hz << 12 p_end = ((pitch_env[127]*pitch_range)>>8) + pitch_base; if(split >= 0) { sprintf(buf," 0 %d",p1/4096); strcat(output,buf); } // don't use intermediate pitch points for linear rise and fall if(env > 1) { for(ix=1; ix<4; ix++) { p2 = ((pitch_env[y[ix]]*pitch_range)>>8) + pitch_base; if(split > 0) { y2 = (y[ix] * env100)/env_split; } else if(split < 0) { y2 = ((y[ix]-env_split) * env100)/env_split; } else { y2 = (y[ix] * env100)/128; } if((y2 > 0) && (y2 <= env100)) { sprintf(buf," %d %d",y2,p2/4096); strcat(output,buf); } } } p_end = p_end/4096; if(split <= 0) { sprintf(buf," %d %d",env100,p_end); strcat(output,buf); } if(env100 < 100) { sprintf(buf," %d %d",100,p_end); strcat(output,buf); } strcat(output,"\n"); if(final) sprintf(output,"\t100 %d\n",p_end); return(output); } // end of WritePitch int MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, int resume, FILE *f_mbrola) {//================================================================================= // Generate a mbrola pho file unsigned int name; int len; int len1; PHONEME_TAB *ph; PHONEME_TAB *ph_next; PHONEME_TAB *ph_prev; PHONEME_LIST *p; PHONEME_LIST *next; PHONEME_DATA phdata; FMT_PARAMS fmtp; int pause = 0; int released; int name2; int control; int done; int len_percent; const char *final_pitch; char *ptr; char mbr_buf[120]; static int phix; static int embedded_ix; static int word_count; if (!resume) { phix = 1; embedded_ix = 0; word_count = 0; } while (phix < n_phonemes) { if (WcmdqFree() < MIN_WCMDQ) return 1; ptr = mbr_buf; p = &plist[phix]; next = &plist[phix+1]; ph = p->ph; ph_prev = plist[phix-1].ph; ph_next = plist[phix+1].ph; if(p->synthflags & SFLAG_EMBEDDED) { DoEmbedded(&embedded_ix, p->sourceix); } if(p->newword & 4) DoMarker(espeakEVENT_SENTENCE, (p->sourceix & 0x7ff) + clause_start_char, 0, count_sentences); if(p->newword & 1) DoMarker(espeakEVENT_WORD, (p->sourceix & 0x7ff) + clause_start_char, p->sourceix >> 11, clause_start_word + word_count++); name = GetMbrName(p,ph,ph_prev,ph_next,&name2,&len_percent,&control); if(control & 1) phix++; if(name == 0) { phix++; continue; // ignore this phoneme } if((ph->type == phPAUSE) && (name == ph->mnemonic)) { // a pause phoneme, which has not been changed by the translation name = '_'; len = (p->length * speed.pause_factor)/256; // if(len == 0) continue; if(len == 0) len = 1; } else len = (80 * speed.wav_factor)/256; if(ph->code != phonEND_WORD) { char phoneme_name[16]; WritePhMnemonic(phoneme_name, p->ph, p, option_phoneme_events & espeakINITIALIZE_PHONEME_IPA); DoPhonemeMarker(espeakEVENT_PHONEME, (p->sourceix & 0x7ff) + clause_start_char, 0, phoneme_name); } ptr += sprintf(ptr,"%s\t",WordToString(name)); if(name2 == '_') { // add a pause after this phoneme pause = len_percent; name2 = 0; } done = 0; final_pitch = ""; switch(ph->type) { case phVOWEL: len = ph->std_length; if(p->synthflags & SFLAG_LENGTHEN) len += phoneme_tab[phonLENGTHEN]->std_length; // phoneme was followed by an extra : symbol if(ph_next->type == phPAUSE) len += 50; // lengthen vowels before a pause len = (len * p->length)/256; if(name2 == 0) { char *pitch = WritePitch(p->env,p->pitch1,p->pitch2,0,0); ptr += sprintf(ptr,"%d\t%s", len, pitch); } else { char *pitch; pitch = WritePitch(p->env,p->pitch1,p->pitch2,len_percent,0); len1 = (len * len_percent)/100; ptr += sprintf(ptr,"%d\t%s", len1, pitch); pitch = WritePitch(p->env,p->pitch1,p->pitch2,-len_percent,0); ptr += sprintf(ptr,"%s\t%d\t%s", WordToString(name2), len-len1, pitch); } done = 1; break; case phSTOP: released = 0; if(next->type==phVOWEL) released = 1; if(next->type==phLIQUID && !next->newword) released = 1; if(released == 0) p->synthflags |= SFLAG_NEXT_PAUSE; InterpretPhoneme(NULL, 0, p, &phdata); len = DoSample3(&phdata, 0, -1); len = (len * 1000)/samplerate; // convert to mS len += PauseLength(p->prepause,1); break; case phVSTOP: len = (80 * speed.wav_factor)/256; break; case phFRICATIVE: len = 0; InterpretPhoneme(NULL, 0, p, &phdata); if(p->synthflags & SFLAG_LENGTHEN) len = DoSample3(&phdata, p->length, -1); // play it twice for [s:] etc. len += DoSample3(&phdata, p->length, -1); len = (len * 1000)/samplerate; // convert to mS break; case phNASAL: if(next->type != phVOWEL) { memset(&fmtp, 0, sizeof(fmtp)); InterpretPhoneme(NULL, 0, p, &phdata); fmtp.fmt_addr = phdata.sound_addr[pd_FMT]; len = DoSpect2(p->ph, 0, &fmtp, p, -1); // len = DoSpect(p->ph,prev->ph,phoneme_tab[phonPAUSE],2,p,-1); len = (len * 1000)/samplerate; if(next->type == phPAUSE) len += 50; final_pitch = WritePitch(p->env,p->pitch1,p->pitch2,0,1); } break; case phLIQUID: if(next->type == phPAUSE) { len += 50; final_pitch = WritePitch(p->env,p->pitch1,p->pitch2,0,1); } break; } if(!done) { if(name2 != 0) { len1 = (len * len_percent)/100; ptr += sprintf(ptr,"%d\n%s\t",len1,WordToString(name2)); len -= len1; } ptr += sprintf(ptr,"%d%s\n",len,final_pitch); } if(pause) { len += PauseLength(pause,0); ptr += sprintf(ptr,"_ \t%d\n",PauseLength(pause,0)); pause = 0; } if(f_mbrola) { fwrite(mbr_buf,1,(ptr-mbr_buf),f_mbrola); // write .pho to a file } else { int res = write_MBR(mbr_buf); if (res < 0) return 0; /* don't get stuck on error */ if (res == 0) return 1; wcmdq[wcmdq_tail][0] = WCMD_MBROLA_DATA; wcmdq[wcmdq_tail][1] = len; WcmdqInc(); } phix++; } if(!f_mbrola) { flush_MBR(); // flush the mbrola output buffer wcmdq[wcmdq_tail][0] = WCMD_MBROLA_DATA; wcmdq[wcmdq_tail][1] = 500; WcmdqInc(); } return 0; } // end of MbrolaTranslate int MbrolaGenerate(PHONEME_LIST *phoneme_list, int *n_ph, int resume) {//================================================================== FILE *f_mbrola = NULL; if(*n_ph == 0) return(0); if(option_mbrola_phonemes) { // send mbrola data to a file, not to the mbrola library f_mbrola = f_trans; } int again = MbrolaTranslate(phoneme_list, *n_ph, resume, f_mbrola); if (!again) *n_ph = 0; return again; } int MbrolaFill(int length, int resume, int amplitude) {//================================================== // Read audio data from Mbrola (length is in millisecs) static int n_samples; int req_samples, result; int ix; short value16; int value; if (!resume) n_samples = samplerate * length / 1000; req_samples = (out_end - out_ptr)/2; if (req_samples > n_samples) req_samples = n_samples; result = read_MBR((short *)out_ptr, req_samples); if (result <= 0) return 0; for(ix=0; ix < result; ix++) { value16 = out_ptr[0] + (out_ptr[1] << 8); value = value16 * amplitude; value = value / 40; // adjust this constant to give a suitable amplitude for mbrola voices if(value > 0x7fff) value = 0x7fff; if(value < -0x8000) value = 0x8000; out_ptr[0] = value; out_ptr[1] = value >> 8; out_ptr += 2; } n_samples -= result; return n_samples ? 1 : 0; } void MbrolaReset(void) {//=================== // Reset the Mbrola engine and flush the pending audio reset_MBR(); } #else // INCLUDE_MBROLA // mbrola interface is not compiled, provide dummy functions. espeak_ERROR LoadMbrolaTable(const char *mbrola_voice, const char *phtrans, int srate) { return(EE_INTERNAL_ERROR); } int MbrolaGenerate(PHONEME_LIST *phoneme_list, int *n_ph, int resume) { return(0); } int MbrolaFill(int length, int resume, int amplitude) { return(0); } void MbrolaReset(void) { } #endif // INCLUDE_MBROLA sources_5316/external/espeak/phoneme.h0000644000176700017670000001421311721443315016623 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2010 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, see: * * . * ***************************************************************************/ // phoneme types #define phPAUSE 0 #define phSTRESS 1 #define phVOWEL 2 #define phLIQUID 3 #define phSTOP 4 #define phVSTOP 5 #define phFRICATIVE 6 #define phVFRICATIVE 7 #define phNASAL 8 #define phVIRTUAL 9 #define phDELETED 14 #define phINVALID 15 // phoneme properties // bits 16-19 give place of articulation #define phARTICULATION 0xf0000 #define phWAVE 0x01 #define phUNSTRESSED 0x02 #define phFORTIS 0x08 #define phVOICED 0x10 #define phSIBILANT 0x20 #define phNOLINK 0x40 #define phTRILL 0x80 #define phVOWEL2 0x100 // liquid that is considered a vowel #define phPALATAL 0x200 #define phSINGLE_INSTN 0x1000 // this phoneme has a single instruction program, with an implicit Return #define phBRKAFTER 0x4000 // [*] add a post-pause #define phNONSYLLABIC 0x100000 // don't count this vowel as a syllable when finding the stress position #define phLONG 0x200000 #define phLENGTHENSTOP 0x400000 // make the pre-pause slightly longer #define phRHOTIC 0x800000 // bit 23 #define phNOPAUSE 0x1000000 #define phPREVOICE 0x2000000 // for voiced stops #define phFLAG1 0x10000000 #define phFLAG2 0x20000000 #define phFLAG3 0x40000000 #define phLOCAL 0x80000000 // used during compilation // fixed phoneme code numbers, these can be used from the program code #define phonCONTROL 1 #define phonSTRESS_U 2 #define phonSTRESS_D 3 #define phonSTRESS_2 4 #define phonSTRESS_3 5 #define phonSTRESS_P 6 #define phonSTRESS_P2 7 // priority stress within a word #define phonSTRESS_PREV 8 #define phonPAUSE 9 #define phonPAUSE_SHORT 10 #define phonPAUSE_NOLINK 11 #define phonLENGTHEN 12 #define phonSCHWA 13 #define phonSCHWA_SHORT 14 #define phonEND_WORD 15 #define phonDEFAULTTONE 17 #define phonCAPITAL 18 #define phonGLOTTALSTOP 19 #define phonSYLLABIC 20 #define phonSWITCH 21 #define phonX1 22 // a language specific action #define phonPAUSE_VSHORT 23 #define phonPAUSE_LONG 24 #define phonT_REDUCED 25 #define phonSTRESS_TONIC 26 #define phonPAUSE_CLAUSE 27 #define phonVOWELTYPES 28 // 28 to 33 extern const unsigned char pause_phonemes[8]; // 0, vshort, short, pause, long, glottalstop // place of articulation #define phPLACE 0xf0000 #define phPLACE_blb 0x10000 #define phPLACE_pla 0x60000 #define N_PHONEME_TABS 100 // number of phoneme tables #define N_PHONEME_TAB 256 // max phonemes in a phoneme table #define N_PHONEME_TAB_NAME 32 // must be multiple of 4 // main table of phonemes, index by phoneme number (1-254) typedef struct { unsigned int mnemonic; // Up to 4 characters. The first char is in the l.s.byte unsigned int phflags; // bits 16-19 place of articulation unsigned short program; // index into phondata file unsigned char code; // the phoneme number unsigned char type; // phVOWEL, phPAUSE, phSTOP etc unsigned char start_type; unsigned char end_type; unsigned char std_length; // for vowels, in mS/2; for phSTRESS phonemes, this is the stress/tone type unsigned char length_mod; // a length_mod group number, used to access length_mod_tab } PHONEME_TAB; // Several phoneme tables may be loaded into memory. phoneme_tab points to // one for the current voice extern int n_phoneme_tab; extern int current_phoneme_table; extern PHONEME_TAB *phoneme_tab[N_PHONEME_TAB]; extern unsigned char phoneme_tab_flags[N_PHONEME_TAB]; // bit 0: not inherited typedef struct { char name[N_PHONEME_TAB_NAME]; PHONEME_TAB *phoneme_tab_ptr; int n_phonemes; int includes; // also include the phonemes from this other phoneme table int equivalence_tables; // lists of equivalent phonemes to match other languages, byte index into phondata } PHONEME_TAB_LIST; // table of phonemes to be replaced with different phonemes, for the current voice #define N_REPLACE_PHONEMES 60 typedef struct { unsigned char old_ph; unsigned char new_ph; char type; // 0=always replace, 1=only at end of word } REPLACE_PHONEMES; extern int n_replace_phonemes; extern REPLACE_PHONEMES replace_phonemes[N_REPLACE_PHONEMES]; // Table of phoneme programs and lengths. Used by MakeVowelLists typedef struct { unsigned int addr; unsigned int length; } PHONEME_PROG_LOG; #define PH(c1,c2) (c2<<8)+c1 // combine two characters into an integer for phoneme name #define PH3(c1,c2,c3) (c3<<16)+(c2<<8)+c1 #define PhonemeCode2(c1,c2) PhonemeCode((c2<<8)+c1) int LookupPhonemeString(const char *string); int PhonemeCode(unsigned int mnem); char *EncodePhonemes(char *p, char *outptr, unsigned char *bad_phoneme); void DecodePhonemes(const char *inptr, char *outptr); extern const char *WordToString(unsigned int word); extern PHONEME_TAB_LIST phoneme_tab_list[N_PHONEME_TABS]; extern int phoneme_tab_number; sources_5316/external/espeak/translate.h0000644000176700017670000007126711721443315017201 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2011 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, see: * * . * ***************************************************************************/ #define L(c1,c2) (c1<<8)+c2 // combine two characters into an integer for translator name #define CTRL_EMBEDDED 0x01 // control character at the start of an embedded command #define REPLACED_E 'E' // 'e' replaced by silent e #define N_WORD_PHONEMES 160 // max phonemes in a word #define N_WORD_BYTES 160 // max bytes for the UTF8 characters in a word #define N_CLAUSE_WORDS 300 // max words in a clause #define N_RULE_GROUP2 120 // max num of two-letter rule chains #define N_HASH_DICT 1024 #define N_CHARSETS 20 #define N_LETTER_GROUPS 26 /* dictionary flags, word 1 */ // bits 0-3 stressed syllable, bit 6=unstressed #define FLAG_SKIPWORDS 0x80 #define FLAG_PREPAUSE 0x100 #define FLAG_ONLY 0x200 #define FLAG_ONLY_S 0x400 #define BITNUM_FLAG_ONLY 9 // bit 9 is set #define BITNUM_FLAG_ONLY_S 10 // bit 10 is set #define FLAG_STRESS_END 0x800 /* full stress if at end of clause */ #define FLAG_STRESS_END2 0x1000 /* full stress if at end of clause, or only followed by unstressed */ #define FLAG_UNSTRESS_END 0x2000 /* reduce stress at end of clause */ #define FLAG_ATEND 0x4000 /* use this pronunciation if at end of clause */ #define FLAG_ATSTART 0x8000 // use this pronunciation if at start of clause #define FLAG_SPELLWORD 0x10000 // re-translate the word as individual letters, separated by spaces #define FLAG_ABBREV 0x20000 // spell as letters, even with a vowel, OR use specified pronunciation rather than split into letters #define FLAG_STEM 0x40000 // must have a suffix #define FLAG_DOUBLING 0x80000 // doubles the following consonant #define BITNUM_FLAG_ALT 19 // bit number of FLAG_ALT_TRANS - 1 #define FLAG_ALT_TRANS 0x100000 // language specific #define FLAG_ALT2_TRANS 0x200000 // language specific #define FLAG_ALT3_TRANS 0x400000 // language specific #define FLAG_COMBINE 0x800000 // combine with the next word #define FLAG_ALLOW_DOT 0x01000000 // ignore '.' after word (abbreviation) #define FLAG_NEEDS_DOT 0x02000000 // only if the word is followed by a dot #define FLAG_WAS_UNPRONOUNCABLE 0x04000000 // the unpronounceable routine was used #define FLAG_MAX3 0x08000000 // limit to 3 repeats #define FLAG_PAUSE1 0x10000000 // shorter prepause #define FLAG_TEXTMODE 0x20000000 // word translates to replacement text, not phonemes #define BITNUM_FLAG_TEXTMODE 29 #define FLAG_FOUND_ATTRIBUTES 0x40000000 // word was found in the dictionary list (has attributes) #define FLAG_FOUND 0x80000000 // pronunciation was found in the dictionary list // dictionary flags, word 2 #define FLAG_VERBF 0x1 /* verb follows */ #define FLAG_VERBSF 0x2 /* verb follows, may have -s suffix */ #define FLAG_NOUNF 0x4 /* noun follows */ #define FLAG_PASTF 0x8 /* past tense follows */ #define FLAG_VERB 0x10 /* pronunciation for verb */ #define FLAG_NOUN 0x20 /* pronunciation for noun */ #define FLAG_PAST 0x40 /* pronunciation for past tense */ #define FLAG_VERB_EXT 0x100 /* extend the 'verb follows' */ #define FLAG_CAPITAL 0x200 /* pronunciation if initial letter is upper case */ #define FLAG_ALLCAPS 0x400 // only if the word is all capitals #define FLAG_ACCENT 0x800 // character name is base-character name + accent name #define FLAG_HYPHENATED 0x1000 // multiple-words, but needs hyphen between parts 1 and 2 #define FLAG_SENTENCE 0x2000 // only if the clause is a sentence #define BITNUM_FLAG_ALLCAPS 0x2a #define BITNUM_FLAG_HYPHENATED 0x2c // wordflags, flags in source word #define FLAG_ALL_UPPER 0x1 /* no lower case letters in the word */ #define FLAG_FIRST_UPPER 0x2 /* first letter is upper case */ #define FLAG_UPPERS 0x3 // FLAG_ALL_UPPER | FLAG_FIRST_UPPER #define FLAG_HAS_PLURAL 0x4 /* upper-case word with s or 's lower-case ending */ #define FLAG_PHONEMES 0x8 /* word is phonemes */ #define FLAG_LAST_WORD 0x10 /* last word in clause */ #define FLAG_EMBEDDED 0x40 /* word is preceded by embedded commands */ #define FLAG_HYPHEN 0x80 #define FLAG_NOSPACE 0x100 // word is not seperated from previous word by a space #define FLAG_FIRST_WORD 0x200 // first word in clause #define FLAG_FOCUS 0x400 // the focus word of a clause #define FLAG_EMPHASIZED 0x800 #define FLAG_EMPHASIZED2 0xc00 // FLAG_FOCUS | FLAG_EMPHASIZED #define FLAG_DONT_SWITCH_TRANSLATOR 0x1000 #define FLAG_SUFFIX_REMOVED 0x2000 #define FLAG_HYPHEN_AFTER 0x4000 #define FLAG_ORDINAL 0x8000 // passed to TranslateNumber() to indicate an ordinal number #define FLAG_HAS_DOT 0x10000 // dot after this word #define FLAG_COMMA_AFTER 0x20000 // comma after this word #define FLAG_MULTIPLE_SPACES 0x40000 // word is preceded by multiple spaces, newline, or tab #define FLAG_INDIVIDUAL_DIGITS 0x80000 // speak number as individual digits #define FLAG_DELETE_WORD 0x100000 // don't speak this word, it has been spoken as part of the previous word #define FLAG_SUFFIX_VOWEL 0x08000000 // remember an initial vowel from the suffix #define FLAG_NO_TRACE 0x10000000 // passed to TranslateRules() to suppress dictionary lookup printout #define FLAG_NO_PREFIX 0x20000000 #define FLAG_UNPRON_TEST 0x80000000 // do unpronounability test on the beginning of the word // prefix/suffix flags (bits 8 to 14, bits 16 to 22) don't use 0x8000, 0x800000 #define SUFX_E 0x0100 // e may have been added #define SUFX_I 0x0200 // y may have been changed to i #define SUFX_P 0x0400 // prefix #define SUFX_V 0x0800 // suffix means use the verb form pronunciation #define SUFX_D 0x1000 // previous letter may have been doubled #define SUFX_F 0x2000 // verb follows #define SUFX_Q 0x4000 // don't retranslate #define SUFX_T 0x10000 // don't affect the stress position in the stem #define SUFX_B 0x20000 // break, this character breaks the word into stem and suffix (used with SUFX_P) #define SUFX_A 0x40000 // remember that the suffix starts with a vowel #define SUFX_UNPRON 0x8000 // used to return $unpron flag from *_rules #define FLAG_ALLOW_TEXTMODE 0x02 // allow dictionary to translate to text rather than phonemes #define FLAG_SUFX 0x04 #define FLAG_SUFX_S 0x08 #define FLAG_SUFX_E_ADDED 0x10 // codes in dictionary rules #define RULE_PRE 1 #define RULE_POST 2 #define RULE_PHONEMES 3 #define RULE_PH_COMMON 4 // At start of rule. Its phoneme string is used by subsequent rules #define RULE_CONDITION 5 // followed by condition number (byte) #define RULE_GROUP_START 6 #define RULE_GROUP_END 7 #define RULE_PRE_ATSTART 8 // as RULE_PRE but also match with 'start of word' #define RULE_LINENUM 9 // next 2 bytes give a line number, for debugging purposes #define RULE_SPACE 32 // ascii space #define RULE_SYLLABLE 21 // @ #define RULE_STRESSED 10 // & #define RULE_DOUBLE 11 // % #define RULE_INC_SCORE 12 // + #define RULE_DEL_FWD 13 // # #define RULE_ENDING 14 // S #define RULE_DIGIT 15 // D digit #define RULE_NONALPHA 16 // Z non-alpha #define RULE_LETTERGP 17 // A B C H F G Y letter group number #define RULE_LETTERGP2 18 // L + letter group number #define RULE_CAPITAL 19 // ! word starts with a capital letter #define RULE_REPLACEMENTS 20 // section for character replacements #define RULE_SKIPCHARS 23 // J #define RULE_NO_SUFFIX 24 // N #define RULE_NOTVOWEL 25 // K #define RULE_IFVERB 26 // V #define RULE_DOLLAR 28 // $ commands #define RULE_NOVOWELS 29 // X no vowels up to word boundary #define RULE_SPELLING 31 // W while spelling letter-by-letter #define RULE_LAST_RULE 31 #define LETTERGP_A 0 #define LETTERGP_B 1 #define LETTERGP_C 2 #define LETTERGP_H 3 #define LETTERGP_F 4 #define LETTERGP_G 5 #define LETTERGP_Y 6 #define LETTERGP_VOWEL2 7 // Punctuation types returned by ReadClause() // bits 0-7 pause x 10mS, bits 12-14 intonation type, // bits12-14 intonation type // bit 15- don't need space after the punctuation // bit 19=sentence, bit 18=clause, bits 17=voice change // bit 16 used to distinguish otherwise identical types // bit 20= punctuation character can be inside a word (Armenian) // bit 21= speak the name of the punctuation character // bit 22= dot after the last word #define CLAUSE_BIT_SENTENCE 0x80000 #define CLAUSE_BIT_CLAUSE 0x40000 #define CLAUSE_BIT_VOICE 0x20000 #define CLAUSE_BITS_INTONATION 0x7000 #define PUNCT_IN_WORD 0x100000 #define PUNCT_SAY_NAME 0x200000 #define CLAUSE_DOT 0x400000 #define CLAUSE_NONE ( 0 + 0x04000) #define CLAUSE_PARAGRAPH (70 + 0x80000) #define CLAUSE_EOF (40 + 0x90000) #define CLAUSE_VOICE ( 0 + 0x24000) #define CLAUSE_PERIOD (40 + 0x80000) #define CLAUSE_COMMA (20 + 0x41000) #define CLAUSE_SHORTCOMMA ( 4 + 0x41000) #define CLAUSE_SHORTFALL ( 4 + 0x40000) #define CLAUSE_QUESTION (40 + 0x82000) #define CLAUSE_EXCLAMATION (45 + 0x83000) #define CLAUSE_COLON (30 + 0x40000) #define CLAUSE_SEMICOLON (30 + 0x41000) #define SAYAS_CHARS 0x12 #define SAYAS_GLYPHS 0x13 #define SAYAS_SINGLE_CHARS 0x14 #define SAYAS_KEY 0x24 #define SAYAS_DIGITS 0x40 // + number of digits #define SAYAS_DIGITS1 0xc1 #define CHAR_EMPHASIS 0x0530 // this is an unused character code #define CHAR_COMMA_BREAK 0x0557 // unused character code // Rule: // [4] [match] [1 pre] [2 post] [3 phonemes] 0 // match 1 pre 2 post 0 - use common phoneme string // match 1 pre 2 post 3 0 - empty phoneme string typedef const char * constcharptr; typedef struct { int points; const char *phonemes; int end_type; char *del_fwd; } MatchRecord; // used to mark words with the source[] buffer typedef struct{ unsigned int flags; unsigned short start; unsigned short sourceix; unsigned char pre_pause; unsigned char wmark; unsigned char length; } WORD_TAB; typedef struct { int type; int parameter[N_SPEECH_PARAM]; } PARAM_STACK; extern PARAM_STACK param_stack[]; extern const int param_defaults[N_SPEECH_PARAM]; #define N_LOPTS 20 #define LOPT_DIERESES 1 // 1=remove [:] from unstressed syllables, 2= remove from unstressed or non-penultimate syllables // bit 4=0, if stress < 4, bit 4=1, if not the highest stress in the word #define LOPT_IT_LENGTHEN 2 // 1=german #define LOPT_PREFIXES 3 // non-zero, change voiced/unoiced to match last consonant in a cluster // bit 0=use regressive voicing // bit 1=LANG=cz,bg don't propagate over [v] // bit 2=don't propagate acress word boundaries // bit 3=LANG=pl, propagate over liquids and nasals // bit 4=LANG=cz,sk don't progagate to [v] // bit 8=devoice word-final consonants #define LOPT_REGRESSIVE_VOICING 4 // 0=default, 1=no check, other allow this character as an extra initial letter (default is 's') #define LOPT_UNPRONOUNCABLE 5 // select length_mods tables, (length_mod_tab) + (length_mod_tab0 * 100) #define LOPT_LENGTH_MODS 6 // increase this to prevent sonorants being shortened before shortened (eg. unstressed) vowels #define LOPT_SONORANT_MIN 7 // bit 0: don't break vowels at word boundary #define LOPT_WORD_MERGE 8 // max. amplitude for vowel at the end of a clause #define LOPT_MAXAMP_EOC 9 // bit 0=reduce even if phonemes are specified in the **_list file // bit 1=don't reduce the strongest vowel in a word which is marked 'unstressed' #define LOPT_REDUCE 10 // LANG=cs,sk combine some prepositions with the following word, if the combination has N or fewer syllables // bits 0-3 N syllables // bit 4=only if the second word has $alt attribute // bit 5=not if the second word is end-of-sentence #define LOPT_COMBINE_WORDS 11 // change [t] when followed by unstressed vowel #define LOPT_REDUCE_T 12 // 1 = allow capitals inside a word // 2 = stressed syllable is indicated by capitals #define LOPT_CAPS_IN_WORD 13 // bit 0=Italian "syntactic doubling" of consoants in the word after a word marked with $double attribute // bit 1=also after a word which ends with a stressed vowel #define LOPT_IT_DOUBLING 14 // Call ApplySpecialAttributes() if $alt or $alt2 is set for a word // bit 1: stressed syllable: $alt change [e],[o] to [E],[O], $alt2 change [E],[O] to [e],[o] #define LOPT_ALT 15 // pause for bracket (default=4), pause when annoucing bracket names (default=2) #define LOPT_BRACKET_PAUSE 16 // bit 1, don't break clause before annoucning . ? ! #define LOPT_ANNOUNCE_PUNCT 17 // recognize long vowels (0 = don't recognize) #define LOPT_LONG_VOWEL_THRESHOLD 18 // bit 0: Don't allow suffices if there is no previous syllable #define LOPT_SUFFIX 19 // stress_rule #define STRESSPOSN_1L 0 // 1st syllable #define STRESSPOSN_2L 1 // 2nd syllable #define STRESSPOSN_2R 2 // penultimate #define STRESSPOSN_1R 3 // final syllable #define STRESSPOSN_3R 4 // antipenultimate typedef struct { // bits0-2 separate words with (1=pause_vshort, 2=pause_short, 3=pause, 4=pause_long 5=[?] phonemme) // bit 3=don't use linking phoneme // bit4=longer pause before STOP, VSTOP,FRIC // bit5=length of a final vowel doesn't depend on the next phoneme int word_gap; int vowel_pause; int stress_rule; // 1=first syllable, 2=penultimate, 3=last #define S_NO_DIM 0x02 #define S_FINAL_DIM 0x04 #define S_FINAL_NO_2 0x10 #define S_NO_AUTO_2 0x20 #define S_2_TO_HEAVY 0x40 #define S_FIRST_PRIMARY 0x80 #define S_2_SYL_2 0x1000 #define S_INITIAL_2 0x2000 #define S_NO_AUTO_DIM 0x10000 #define S_HYPEN_UNSTRESS 0x100000 #define S_NO_EOC_LENGTHEN 0x200000 // bit0=don't stress monosyllables, except at end of clause // bit1=don't set diminished stress, // bit2=mark unstressed final syllables as diminished // bit3=set consecutive unstressed syllables in unstressed words to diminished, but not in stressed words // bit4=don't allow secondary stress on last syllable // bit5-don't use automatic secondary stress // bit6=light syllable followed by heavy, move secondary stress to the heavy syllable. LANG=Finnish // bit7=if more than one primary stress, make the subsequent primaries to secondary stress // bit8=stress last syllable if it doesn't end in a vowel // bit9=stress last syllable if it doesn't end in vowel or "s" or "n" LANG=Spanish // bit12= In a 2-syllable word, if one has primary stress then give the other secondary stress // bit13= If there is only one syllable before the primary stress, give it a secondary stress // bit15= Give stress to the first unstressed syllable // bit16= Don't diminish consecutive syllables within a word. // bit17= "priority" stress reduces other primary stress to "unstressed" not "secondary" // bit18= don't lengthen short vowels more than long vowels at end-of-clause // bit19=stress on final syllable if it has a long vowel, but previous syllable has a short vowel // bit20= hyphenated words, 2nd part is unstressed // bit21= don't lengthen vowels at end-of-clause int stress_flags; int unstressed_wd1; // stress for $u word of 1 syllable int unstressed_wd2; // stress for $u word of >1 syllable int param[N_LOPTS]; int param2[N_LOPTS]; unsigned char *length_mods; unsigned char *length_mods0; #define NUM_THOUS_SPACE 0x4 #define NUM_DECIMAL_COMMA 0x8 #define NUM_SWAP_TENS 0x10 #define NUM_AND_UNITS 0x20 #define NUM_HUNDRED_AND 0x40 #define NUM_SINGLE_AND 0x80 #define NUM_SINGLE_STRESS 0x100 #define NUM_SINGLE_VOWEL 0x200 #define NUM_OMIT_1_HUNDRED 0x400 #define NUM_1900 0x800 #define NUM_ALLOW_SPACE 0x1000 #define NUM_DFRACTION_1 0x2000 #define NUM_DFRACTION_2 0x4000 #define NUM_DFRACTION_3 0x6000 #define NUM_DFRACTION_4 0x8000 #define NUM_DFRACTION_5 0xa000 #define NUM_DFRACTION_6 0xc000 #define NUM_ORDINAL_DOT 0x10000 #define NUM_NOPAUSE 0x20000 #define NUM_AND_HUNDRED 0x40000 #define NUM_THOUSAND_AND 0x80000 #define NUM_VIGESIMAL 0x100000 #define NUM_OMIT_1_THOUSAND 0x200000 #define NUM_ZERO_HUNDRED 0x400000 #define NUM_HUNDRED_AND_DIGIT 0x800000 #define NUM_ROMAN 0x1000000 #define NUM_ROMAN_CAPITALS 0x2000000 #define NUM_ROMAN_AFTER 0x4000000 #define NUM_ROMAN_ORDINAL 0x8000000 // bits0-1=which numbers routine to use. // bit2= thousands separator must be space // bit3= , decimal separator, not . // bit4=use three-and-twenty rather than twenty-three // bit5='and' between tens and units // bit6=add "and" after hundred or thousand // bit7=don't have "and" both after hundreds and also between tens and units // bit8=only one primary stress in tens+units // bit9=only one vowel betwen tens and units // bit10=omit "one" before "hundred" // bit11=say 19** as nineteen hundred // bit12=allow space as thousands separator (in addition to langopts.thousands_sep) // bits13-15 post-decimal-digits 0=single digits, 1=(LANG=it) 2=(LANG=pl) 3=(LANG=ro) // bit16= dot after number indicates ordinal // bit17= don't add pause after a number // bit18= 'and' before hundreds // bit19= 'and' after thousands if there are no hundreds // bit20= vigesimal number, if tens are not found // bit21= omit "one" before "thousand" // bit22= say "zero" before hundred // bit23= add "and" after hundreds and thousands, only if there are digits and no tens // bit24= recognize roman numbers // bit25= Roman numbers only if upper case // bit26= say "roman" after the number, not before // bit27= Roman numbers are ordinal numbers int numbers; #define NUM2_MULTIPLE_ORDINAL 0x1000 // bits 1-4 use variant form of numbers before thousands,millions,etc. // bit6=(LANG=pl) two forms of plural, M or MA // bit7=(LANG-ru) use MB for 1 thousand, million, etc // bit8=(LANG=cs,sk) two forms of plural, M or MA // bit9=(LANG=rw) say "thousand" and "million" before its number, not after // bit12=(LANG=el,es) use ordinal form of hundreds and tens as well as units int numbers2; #define BREAK_THOUSANDS 0x49249248 int break_numbers; // which digits to break the number into thousands, millions, etc (Hindi has 100,000 not 1,000,000) int max_roman; int min_roman; int thousands_sep; int decimal_sep; int max_digits; // max number of digits which can be spoken as an integer number (rather than individual digits) const char *ordinal_indicator; // UTF-8 string // bit 0, accent name before the letter name, bit 1 "capital" after letter name int accents; int tone_language; // 1=tone language int intonation_group; unsigned char tunes[6]; int long_stop; // extra mS pause for a lengthened stop int phoneme_change; // TEST, change phonemes, after translation char max_initial_consonants; char spelling_stress; // 0=default, 1=stress first letter char tone_numbers; char ideographs; // treat as separate words char textmode; // the meaning of FLAG_TEXTMODE is reversed (to save data when *_list file is compiled) int testing; // testing options: bit 1= specify stressed syllable in the form: "outdoor/2" int listx; // compile *_listx after *list const unsigned int *replace_chars; // characters to be substitutes const char *ascii_language; // switch to this language for Latin characters int max_lengthmod; int lengthen_tonic; // lengthen the tonic syllable int suffix_add_e; // replace a suffix (which has the SUFX_E flag) with this character } LANGUAGE_OPTIONS; // a parameter of ChangePhonemes() typedef struct { int flags; unsigned char stress; // stress level of this vowel unsigned char stress_highest; // the highest stress level of a vowel in this word unsigned char n_vowels; // number of vowels in the word unsigned char vowel_this; // syllable number of this vowel (counting from 1) unsigned char vowel_stressed; // syllable number of the highest stressed vowel } CHANGEPH; typedef struct {//=========== LANGUAGE_OPTIONS langopts; int translator_name; int transpose_max; int transpose_min; char dictionary_name[40]; char phon_out[400]; char phonemes_repeat[20]; int phonemes_repeat_count; int phoneme_tab_ix; unsigned char stress_amps[8]; unsigned char stress_amps_r[8]; short stress_lengths[8]; int dict_condition; // conditional apply some pronunciation rules and dict.lookups const unsigned short *charset_a0; // unicodes for characters 0xa0 to oxff const wchar_t *char_plus_apostrophe; // single chars + apostrophe treated as words const wchar_t *punct_within_word; // allow these punctuation characters within words // holds properties of characters: vowel, consonant, etc for pronunciation rules unsigned char letter_bits[256]; int letter_bits_offset; const wchar_t *letter_groups[8]; /* index1=option, index2 by 0=. 1=, 2=?, 3=! 4=none */ #define INTONATION_TYPES 8 #define PUNCT_INTONATIONS 6 unsigned char punct_to_tone[INTONATION_TYPES][PUNCT_INTONATIONS]; char *data_dictrules; // language_1 translation rules file char *data_dictlist; // language_2 dictionary lookup file char *dict_hashtab[N_HASH_DICT]; // hash table to index dictionary lookup file char *letterGroups[N_LETTER_GROUPS]; // groups1 and groups2 are indexes into data_dictrules, set up by InitGroups() // the two-letter rules for each letter must be consecutive in the language_rules source char *groups1[256]; // translation rule lists, index by single letter char *groups3[128]; // index by offset letter char *groups2[N_RULE_GROUP2]; // translation rule lists, indexed by two-letter pairs unsigned int groups2_name[N_RULE_GROUP2]; // the two letter pairs for groups2[] int n_groups2; // number of groups2[] entries used unsigned char groups2_count[256]; // number of 2 letter groups for this initial letter unsigned char groups2_start[256]; // index into groups2 const short *frequent_pairs; // list of frequent pairs of letters, for use in compressed *_list int expect_verb; int expect_past; // expect past tense int expect_verb_s; int expect_noun; int prev_last_stress; char *clause_end; int word_vowel_count; // number of vowels so far int word_stressed_count; // number of vowels so far which could be stressed int clause_upper_count; // number of upper case letters in the clause int clause_lower_count; // number of lower case letters in the clause int prepause_timeout; int end_stressed_vowel; // word ends with stressed vowel int prev_dict_flags; // dictionary flags from previous word int clause_terminator; } Translator; extern int option_tone2; #define OPTION_EMPHASIZE_ALLCAPS 0x100 #define OPTION_EMPHASIZE_PENULTIMATE 0x200 extern int option_tone_flags; extern int option_waveout; extern int option_quiet; extern int option_phonemes; extern int option_mbrola_phonemes; extern int option_phoneme_events; extern int option_linelength; // treat lines shorter than this as end-of-clause extern int option_multibyte; extern int option_capitals; extern int option_punctuation; extern int option_endpause; extern int option_ssml; extern int option_phoneme_input; // allow [[phonemes]] in input text extern int option_phoneme_variants; extern int option_sayas; extern int option_wordgap; extern int count_characters; extern int count_words; extern int count_sentences; extern int skip_characters; extern int skip_words; extern int skip_sentences; extern int skipping_text; extern int end_character_position; extern int clause_start_char; extern int clause_start_word; extern char *namedata; extern int pre_pause; #define N_MARKER_LENGTH 50 // max.length of a mark name extern char skip_marker[N_MARKER_LENGTH]; #define N_PUNCTLIST 60 extern wchar_t option_punctlist[N_PUNCTLIST]; // which punctuation characters to announce extern unsigned char punctuation_to_tone[INTONATION_TYPES][PUNCT_INTONATIONS]; extern Translator *translator; extern Translator *translator2; extern const unsigned short *charsets[N_CHARSETS]; extern char dictionary_name[40]; extern char ctrl_embedded; // to allow an alternative CTRL for embedded commands extern unsigned char *p_textinput; extern wchar_t *p_wchar_input; extern int dictionary_skipwords; extern int (* uri_callback)(int, const char *, const char *); extern int (* phoneme_callback)(const char *); extern void SetLengthMods(Translator *tr, int value); void LoadConfig(void); int TransposeAlphabet(Translator *tr, char *text); int utf8_in(int *c, const char *buf); int utf8_in2(int *c, const char *buf, int backwards); int utf8_out(unsigned int c, char *buf); int utf8_nbytes(const char *buf); int lookupwchar(const unsigned short *list,int c); int Eof(void); char *strchr_w(const char *s, int c); int IsBracket(int c); void InitNamedata(void); void InitText(int flags); void InitText2(void); int IsDigit(unsigned int c); int IsAlpha(unsigned int c); int isspace2(unsigned int c); int towlower2(unsigned int c); void GetTranslatedPhonemeString(char *phon_out, int n_phon_out, int use_ipa); Translator *SelectTranslator(const char *name); int SetTranslator2(const char *name); void DeleteTranslator(Translator *tr); int Lookup(Translator *tr, const char *word, char *ph_out); int LookupFlags(Translator *tr, const char *word); int TranslateNumber(Translator *tr, char *word1, char *ph_out, unsigned int *flags, WORD_TAB *wtab, int control); int TranslateRoman(Translator *tr, char *word, char *ph_out, WORD_TAB *wtab); void ChangeWordStress(Translator *tr, char *word, int new_stress); void SetSpellingStress(Translator *tr, char *phonemes, int control, int n_chars); int TranslateLetter(Translator *tr, char *letter, char *phonemes, int control); void LookupLetter(Translator *tr, unsigned int letter, int next_byte, char *ph_buf, int control); void LookupAccentedLetter(Translator *tr, unsigned int letter, char *ph_buf); int LoadDictionary(Translator *tr, const char *name, int no_error); int LookupDictList(Translator *tr, char **wordptr, char *ph_out, unsigned int *flags, int end_flags, WORD_TAB *wtab); void MakePhonemeList(Translator *tr, int post_pause, int new_sentence); int ChangePhonemes_ru(Translator *tr, PHONEME_LIST2 *phlist, int n_ph, int index, PHONEME_TAB *ph, CHANGEPH *ch); void ApplySpecialAttribute(Translator *tr, char *phonemes, int dict_flags); void ApplySpecialAttribute2(Translator *tr, char *phonemes, int dict_flags); void AppendPhonemes(Translator *tr, char *string, int size, const char *ph); void CalcLengths(Translator *tr); void CalcPitches(Translator *tr, int clause_tone); int RemoveEnding(Translator *tr, char *word, int end_type, char *word_copy); int Unpronouncable(Translator *tr, char *word, int posn); void SetWordStress(Translator *tr, char *output, unsigned int *dictionary_flags, int tonic, int prev_stress); int TranslateRules(Translator *tr, char *p, char *phonemes, int size, char *end_phonemes, int end_flags, unsigned int *dict_flags); int TranslateWord(Translator *tr, char *word1, int next_pause, WORD_TAB *wtab); void *TranslateClause(Translator *tr, FILE *f_text, const void *vp_input, int *tone, char **voice_change); int ReadClause(Translator *tr, FILE *f_in, char *buf, short *charix, int *charix_top, int n_buf, int *tone_type, char *voice_change); void SetVoiceStack(espeak_VOICE *v, const char *variant_name); void InterpretPhoneme(Translator *tr, int control, PHONEME_LIST *plist, PHONEME_DATA *phdata); void InterpretPhoneme2(int phcode, PHONEME_DATA *phdata); char *WritePhMnemonic(char *phon_out, PHONEME_TAB *ph, PHONEME_LIST *plist, int use_ipa); extern FILE *f_trans; // for logging extern FILE *f_logespeak; extern int logging_type; // from config file sources_5316/external/espeak/intonation.cpp0000644000176700017670000011266311721443315017715 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2007 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" /* Note this module is mostly old code that needs to be rewritten to provide a more flexible intonation system. */ // bits in SYLLABLE.flags #define SYL_RISE 1 #define SYL_EMPHASIS 2 #define SYL_END_CLAUSE 4 typedef struct { char stress; char env; char flags; //bit 0=pitch rising, bit1=emnphasized, bit2=end of clause char nextph_type; unsigned char pitch1; unsigned char pitch2; } SYLLABLE; static SYLLABLE *syllable_tab; static int tone_pitch_env; /* used to return pitch envelope */ /* Pitch data for tone types */ /*****************************/ #define PITCHfall 0 #define PITCHrise 2 #define PITCHfrise 4 // and 3 must be for the variant preceded by 'r' #define PITCHfrise2 6 // and 5 must be the 'r' variant #define PITCHrisefall 8 /* 0 fall */ unsigned char env_fall[128] = { 0xff, 0xfd, 0xfa, 0xf8, 0xf6, 0xf4, 0xf2, 0xf0, 0xee, 0xec, 0xea, 0xe8, 0xe6, 0xe4, 0xe2, 0xe0, 0xde, 0xdc, 0xda, 0xd8, 0xd6, 0xd4, 0xd2, 0xd0, 0xce, 0xcc, 0xca, 0xc8, 0xc6, 0xc4, 0xc2, 0xc0, 0xbe, 0xbc, 0xba, 0xb8, 0xb6, 0xb4, 0xb2, 0xb0, 0xae, 0xac, 0xaa, 0xa8, 0xa6, 0xa4, 0xa2, 0xa0, 0x9e, 0x9c, 0x9a, 0x98, 0x96, 0x94, 0x92, 0x90, 0x8e, 0x8c, 0x8a, 0x88, 0x86, 0x84, 0x82, 0x80, 0x7e, 0x7c, 0x7a, 0x78, 0x76, 0x74, 0x72, 0x70, 0x6e, 0x6c, 0x6a, 0x68, 0x66, 0x64, 0x62, 0x60, 0x5e, 0x5c, 0x5a, 0x58, 0x56, 0x54, 0x52, 0x50, 0x4e, 0x4c, 0x4a, 0x48, 0x46, 0x44, 0x42, 0x40, 0x3e, 0x3c, 0x3a, 0x38, 0x36, 0x34, 0x32, 0x30, 0x2e, 0x2c, 0x2a, 0x28, 0x26, 0x24, 0x22, 0x20, 0x1e, 0x1c, 0x1a, 0x18, 0x16, 0x14, 0x12, 0x10, 0x0e, 0x0c, 0x0a, 0x08, 0x06, 0x04, 0x02, 0x00 }; /* 1 rise */ unsigned char env_rise[128] = { 0x00, 0x02, 0x04, 0x06, 0x08, 0x0a, 0x0c, 0x0e, 0x10, 0x12, 0x14, 0x16, 0x18, 0x1a, 0x1c, 0x1e, 0x20, 0x22, 0x24, 0x26, 0x28, 0x2a, 0x2c, 0x2e, 0x30, 0x32, 0x34, 0x36, 0x38, 0x3a, 0x3c, 0x3e, 0x40, 0x42, 0x44, 0x46, 0x48, 0x4a, 0x4c, 0x4e, 0x50, 0x52, 0x54, 0x56, 0x58, 0x5a, 0x5c, 0x5e, 0x60, 0x62, 0x64, 0x66, 0x68, 0x6a, 0x6c, 0x6e, 0x70, 0x72, 0x74, 0x76, 0x78, 0x7a, 0x7c, 0x7e, 0x80, 0x82, 0x84, 0x86, 0x88, 0x8a, 0x8c, 0x8e, 0x90, 0x92, 0x94, 0x96, 0x98, 0x9a, 0x9c, 0x9e, 0xa0, 0xa2, 0xa4, 0xa6, 0xa8, 0xaa, 0xac, 0xae, 0xb0, 0xb2, 0xb4, 0xb6, 0xb8, 0xba, 0xbc, 0xbe, 0xc0, 0xc2, 0xc4, 0xc6, 0xc8, 0xca, 0xcc, 0xce, 0xd0, 0xd2, 0xd4, 0xd6, 0xd8, 0xda, 0xdc, 0xde, 0xe0, 0xe2, 0xe4, 0xe6, 0xe8, 0xea, 0xec, 0xee, 0xf0, 0xf2, 0xf4, 0xf6, 0xf8, 0xfa, 0xfd, 0xff }; unsigned char env_frise[128] = { 0xff, 0xf4, 0xea, 0xe0, 0xd6, 0xcc, 0xc3, 0xba, 0xb1, 0xa8, 0x9f, 0x97, 0x8f, 0x87, 0x7f, 0x78, 0x71, 0x6a, 0x63, 0x5c, 0x56, 0x50, 0x4a, 0x44, 0x3f, 0x39, 0x34, 0x2f, 0x2b, 0x26, 0x22, 0x1e, 0x1a, 0x17, 0x13, 0x10, 0x0d, 0x0b, 0x08, 0x06, 0x04, 0x02, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x07, 0x08, 0x0a, 0x0c, 0x0e, 0x10, 0x13, 0x15, 0x17, 0x1a, 0x1d, 0x1f, 0x22, 0x25, 0x28, 0x2c, 0x2e, 0x30, 0x32, 0x34, 0x36, 0x39, 0x3b, 0x3d, 0x40, 0x42, 0x45, 0x47, 0x4a, 0x4c, 0x4f, 0x51, 0x54, 0x57, 0x5a, 0x5d, 0x5f, 0x62, 0x65, 0x68, 0x6b, 0x6e, 0x71, 0x74, 0x78, 0x7b, 0x7e, 0x81, 0x85, 0x88, 0x8b, 0x8f, 0x92, 0x96, 0x99, 0x9d, 0xa0, 0xa4, 0xa8, 0xac, 0xaf, 0xb3, 0xb7, 0xbb, 0xbf, 0xc3, 0xc7, 0xcb, 0xcf, 0xd3, 0xd7, 0xdb, 0xe0 }; static unsigned char env_r_frise[128] = { 0xcf, 0xcc, 0xc9, 0xc6, 0xc3, 0xc0, 0xbd, 0xb9, 0xb4, 0xb0, 0xab, 0xa7, 0xa2, 0x9c, 0x97, 0x92, 0x8c, 0x86, 0x81, 0x7b, 0x75, 0x6f, 0x69, 0x63, 0x5d, 0x57, 0x50, 0x4a, 0x44, 0x3e, 0x38, 0x33, 0x2d, 0x27, 0x22, 0x1c, 0x17, 0x12, 0x0d, 0x08, 0x04, 0x02, 0x02, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x02, 0x03, 0x04, 0x05, 0x07, 0x08, 0x0a, 0x0c, 0x0d, 0x0f, 0x12, 0x14, 0x16, 0x19, 0x1b, 0x1e, 0x21, 0x24, 0x27, 0x2a, 0x2d, 0x30, 0x34, 0x36, 0x38, 0x3a, 0x3c, 0x3f, 0x41, 0x43, 0x46, 0x48, 0x4b, 0x4d, 0x50, 0x52, 0x55, 0x58, 0x5a, 0x5d, 0x60, 0x63, 0x66, 0x69, 0x6c, 0x6f, 0x72, 0x75, 0x78, 0x7b, 0x7e, 0x81, 0x85, 0x88, 0x8b, 0x8f, 0x92, 0x96, 0x99, 0x9d, 0xa0, 0xa4, 0xa8, 0xac, 0xaf, 0xb3, 0xb7, 0xbb, 0xbf, 0xc3, 0xc7, 0xcb, 0xcf, 0xd3, 0xd7, 0xdb, 0xe0 }; static unsigned char env_frise2[128] = { 0xff, 0xf9, 0xf4, 0xee, 0xe9, 0xe4, 0xdf, 0xda, 0xd5, 0xd0, 0xcb, 0xc6, 0xc1, 0xbd, 0xb8, 0xb3, 0xaf, 0xaa, 0xa6, 0xa1, 0x9d, 0x99, 0x95, 0x90, 0x8c, 0x88, 0x84, 0x80, 0x7d, 0x79, 0x75, 0x71, 0x6e, 0x6a, 0x67, 0x63, 0x60, 0x5d, 0x59, 0x56, 0x53, 0x50, 0x4d, 0x4a, 0x47, 0x44, 0x41, 0x3e, 0x3c, 0x39, 0x37, 0x34, 0x32, 0x2f, 0x2d, 0x2b, 0x28, 0x26, 0x24, 0x22, 0x20, 0x1e, 0x1c, 0x1a, 0x19, 0x17, 0x15, 0x14, 0x12, 0x11, 0x0f, 0x0e, 0x0d, 0x0c, 0x0a, 0x09, 0x08, 0x07, 0x06, 0x05, 0x05, 0x04, 0x03, 0x02, 0x02, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x02, 0x02, 0x03, 0x04, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0e, 0x0f, 0x10, 0x12, 0x13, 0x15, 0x17, 0x18, 0x1a, 0x1c, 0x1e, 0x20 }; static unsigned char env_r_frise2[128] = { 0xd0, 0xce, 0xcd, 0xcc, 0xca, 0xc8, 0xc7, 0xc5, 0xc3, 0xc1, 0xc0, 0xbd, 0xbb, 0xb8, 0xb5, 0xb3, 0xb0, 0xad, 0xaa, 0xa7, 0xa3, 0xa0, 0x9d, 0x99, 0x96, 0x92, 0x8f, 0x8b, 0x87, 0x84, 0x80, 0x7c, 0x78, 0x74, 0x70, 0x6d, 0x69, 0x65, 0x61, 0x5d, 0x59, 0x55, 0x51, 0x4d, 0x4a, 0x46, 0x42, 0x3e, 0x3b, 0x37, 0x34, 0x31, 0x2f, 0x2d, 0x2a, 0x28, 0x26, 0x24, 0x22, 0x20, 0x1e, 0x1c, 0x1a, 0x19, 0x17, 0x15, 0x14, 0x12, 0x11, 0x0f, 0x0e, 0x0d, 0x0c, 0x0a, 0x09, 0x08, 0x07, 0x06, 0x05, 0x05, 0x04, 0x03, 0x02, 0x02, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x02, 0x02, 0x03, 0x04, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0e, 0x0f, 0x10, 0x12, 0x13, 0x15, 0x17, 0x18, 0x1a, 0x1c, 0x1e, 0x20 }; static unsigned char env_risefall[128] = { 0x98, 0x99, 0x99, 0x9a, 0x9c, 0x9d, 0x9f, 0xa1, 0xa4, 0xa7, 0xa9, 0xac, 0xb0, 0xb3, 0xb6, 0xba, 0xbe, 0xc1, 0xc5, 0xc9, 0xcd, 0xd1, 0xd4, 0xd8, 0xdc, 0xdf, 0xe3, 0xe6, 0xea, 0xed, 0xf0, 0xf2, 0xf5, 0xf7, 0xf9, 0xfb, 0xfc, 0xfd, 0xfe, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xfd, 0xfb, 0xfa, 0xf8, 0xf6, 0xf3, 0xf1, 0xee, 0xec, 0xe9, 0xe6, 0xe4, 0xe0, 0xdd, 0xda, 0xd7, 0xd3, 0xd0, 0xcc, 0xc8, 0xc4, 0xc0, 0xbc, 0xb8, 0xb4, 0xb0, 0xac, 0xa7, 0xa3, 0x9f, 0x9a, 0x96, 0x91, 0x8d, 0x88, 0x84, 0x7f, 0x7b, 0x76, 0x72, 0x6d, 0x69, 0x65, 0x60, 0x5c, 0x58, 0x54, 0x50, 0x4c, 0x48, 0x44, 0x40, 0x3c, 0x39, 0x35, 0x32, 0x2f, 0x2b, 0x28, 0x26, 0x23, 0x20, 0x1d, 0x1a, 0x17, 0x15, 0x12, 0x0f, 0x0d, 0x0a, 0x08, 0x07, 0x05, 0x03, 0x02, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00 }; static unsigned char env_rise2[128] = { 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x01, 0x02, 0x02, 0x03, 0x03, 0x04, 0x04, 0x05, 0x06, 0x06, 0x07, 0x08, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x16, 0x17, 0x18, 0x19, 0x1b, 0x1c, 0x1d, 0x1f, 0x20, 0x22, 0x23, 0x25, 0x26, 0x28, 0x29, 0x2b, 0x2d, 0x2f, 0x30, 0x32, 0x34, 0x36, 0x38, 0x3a, 0x3c, 0x3e, 0x40, 0x42, 0x44, 0x47, 0x49, 0x4b, 0x4e, 0x50, 0x52, 0x55, 0x57, 0x5a, 0x5d, 0x5f, 0x62, 0x65, 0x67, 0x6a, 0x6d, 0x70, 0x73, 0x76, 0x79, 0x7c, 0x7f, 0x82, 0x86, 0x89, 0x8c, 0x90, 0x93, 0x96, 0x9a, 0x9d, 0xa0, 0xa3, 0xa6, 0xa9, 0xac, 0xaf, 0xb2, 0xb5, 0xb8, 0xbb, 0xbe, 0xc1, 0xc4, 0xc7, 0xca, 0xcd, 0xd0, 0xd3, 0xd6, 0xd9, 0xdc, 0xdf, 0xe2, 0xe4, 0xe7, 0xe9, 0xec, 0xee, 0xf0, 0xf2, 0xf4, 0xf6, 0xf8, 0xfa, 0xfb, 0xfd }; static unsigned char env_fall2[128] = { 0xfe, 0xfe, 0xfd, 0xfd, 0xfc, 0xfb, 0xfb, 0xfa, 0xfa, 0xf9, 0xf8, 0xf8, 0xf7, 0xf7, 0xf6, 0xf6, 0xf5, 0xf4, 0xf4, 0xf3, 0xf3, 0xf2, 0xf2, 0xf1, 0xf0, 0xf0, 0xef, 0xee, 0xee, 0xed, 0xec, 0xeb, 0xea, 0xea, 0xe9, 0xe8, 0xe7, 0xe6, 0xe5, 0xe4, 0xe3, 0xe2, 0xe1, 0xe0, 0xde, 0xdd, 0xdc, 0xdb, 0xd9, 0xd8, 0xd6, 0xd5, 0xd3, 0xd2, 0xd0, 0xce, 0xcc, 0xcb, 0xc9, 0xc7, 0xc5, 0xc3, 0xc0, 0xbe, 0xbc, 0xb9, 0xb7, 0xb5, 0xb2, 0xaf, 0xad, 0xaa, 0xa7, 0xa4, 0xa1, 0x9e, 0x9a, 0x97, 0x94, 0x90, 0x8d, 0x89, 0x85, 0x81, 0x7d, 0x79, 0x75, 0x71, 0x6d, 0x68, 0x64, 0x61, 0x5e, 0x5b, 0x57, 0x54, 0x51, 0x4d, 0x4a, 0x46, 0x43, 0x40, 0x3c, 0x39, 0x35, 0x32, 0x2e, 0x2a, 0x27, 0x23, 0x1f, 0x1c, 0x18, 0x14, 0x11, 0x0d, 0x0b, 0x09, 0x07, 0x05, 0x04, 0x03, 0x02, 0x01, 0x00, 0x00, 0x00, 0x00 }; static unsigned char env_fallrise3[128] = { 0xfe, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xfd, 0xfc, 0xfa, 0xf8, 0xf6, 0xf4, 0xf1, 0xee, 0xeb, 0xe8, 0xe5, 0xe1, 0xde, 0xda, 0xd6, 0xd2, 0xcd, 0xc9, 0xc4, 0xbf, 0xba, 0xb6, 0xb0, 0xab, 0xa6, 0xa1, 0x9c, 0x96, 0x91, 0x8b, 0x86, 0x80, 0x7b, 0x75, 0x6f, 0x6a, 0x64, 0x5f, 0x59, 0x54, 0x4f, 0x49, 0x44, 0x3f, 0x3a, 0x35, 0x30, 0x2b, 0x26, 0x22, 0x1d, 0x19, 0x15, 0x11, 0x0d, 0x0a, 0x07, 0x04, 0x03, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x02, 0x04, 0x05, 0x07, 0x09, 0x0b, 0x0d, 0x10, 0x12, 0x15, 0x18, 0x1b, 0x1e, 0x22, 0x25, 0x29, 0x2d, 0x31, 0x35, 0x3a, 0x3e, 0x43, 0x48, 0x4c, 0x51, 0x57, 0x5b, 0x5e, 0x62, 0x65, 0x68, 0x6b, 0x6e, 0x71, 0x74, 0x76, 0x78, 0x7b, 0x7c, 0x7e, 0x80, 0x81, 0x82, 0x83, 0x83, 0x84, 0x84, 0x83, 0x83, 0x82, 0x81 }; static unsigned char env_fallrise4[128] = { 0x72, 0x72, 0x71, 0x71, 0x70, 0x6f, 0x6d, 0x6c, 0x6a, 0x68, 0x66, 0x64, 0x61, 0x5f, 0x5c, 0x5a, 0x57, 0x54, 0x51, 0x4e, 0x4b, 0x48, 0x45, 0x42, 0x3f, 0x3b, 0x38, 0x35, 0x32, 0x2f, 0x2c, 0x29, 0x26, 0x23, 0x20, 0x1d, 0x1b, 0x18, 0x16, 0x14, 0x12, 0x10, 0x0e, 0x0c, 0x0b, 0x0a, 0x09, 0x08, 0x07, 0x07, 0x07, 0x07, 0x07, 0x06, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x06, 0x07, 0x07, 0x08, 0x09, 0x0a, 0x0c, 0x0d, 0x0f, 0x10, 0x12, 0x14, 0x16, 0x18, 0x1b, 0x1d, 0x20, 0x23, 0x26, 0x29, 0x2c, 0x2f, 0x33, 0x37, 0x3b, 0x3f, 0x43, 0x47, 0x4c, 0x51, 0x56, 0x5b, 0x60, 0x65, 0x6a, 0x6f, 0x74, 0x79, 0x7f, 0x84, 0x89, 0x8f, 0x95, 0x9b, 0xa1, 0xa7, 0xad, 0xb3, 0xba, 0xc0, 0xc7, 0xce, 0xd5, 0xdc, 0xe3, 0xea, 0xf1, 0xf5, 0xf7, 0xfa, 0xfc, 0xfd, 0xfe, 0xff, 0xff }; static unsigned char env_risefallrise[128] = { 0x7f, 0x7f, 0x7f, 0x80, 0x81, 0x83, 0x84, 0x87, 0x89, 0x8c, 0x8f, 0x92, 0x96, 0x99, 0x9d, 0xa1, 0xa5, 0xaa, 0xae, 0xb2, 0xb7, 0xbb, 0xc0, 0xc5, 0xc9, 0xcd, 0xd2, 0xd6, 0xda, 0xde, 0xe2, 0xe6, 0xea, 0xed, 0xf0, 0xf3, 0xf5, 0xf8, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xfe, 0xfd, 0xfc, 0xfb, 0xf9, 0xf7, 0xf4, 0xf0, 0xec, 0xe7, 0xe2, 0xdc, 0xd5, 0xce, 0xc6, 0xbd, 0xb4, 0xa9, 0x9e, 0x92, 0x88, 0x82, 0x7d, 0x77, 0x72, 0x6c, 0x66, 0x60, 0x5a, 0x54, 0x4e, 0x49, 0x42, 0x3c, 0x37, 0x32, 0x2d, 0x28, 0x24, 0x1f, 0x1b, 0x18, 0x14, 0x11, 0x0e, 0x0c, 0x09, 0x07, 0x06, 0x05, 0x04, 0x04, 0x04, 0x04, 0x05, 0x06, 0x08, 0x0a, 0x0d, 0x10, 0x14, 0x18, 0x1d, 0x23, 0x29, 0x2f, 0x37, 0x3e, 0x47, 0x50, 0x5a, 0x64, 0x70, 0x7c, 0x83, 0x85, 0x88, 0x8a, 0x8c, 0x8e, 0x8f, 0x91, 0x92, 0x93, 0x93 }; unsigned char *envelope_data[N_ENVELOPE_DATA] = { env_fall, env_fall, env_rise, env_rise, env_frise, env_r_frise, env_frise2, env_r_frise2, env_risefall, env_risefall, env_fallrise3, env_fallrise3, env_fallrise4, env_fallrise4, env_fall2, env_fall2, env_rise2, env_rise2, env_risefallrise, env_risefallrise }; /* indexed by stress */ static int min_drop[] = {6,7,9,9,20,20,20,25}; // pitch change during the main part of the clause static int drops_0[8] = {9,9,16,16,16,23,55,32}; // overflow table values are 64ths of the body pitch range (between body_start and body_end) static signed char oflow[] = {0, 40, 24, 8, 0}; static signed char oflow_emf[] = {10, 52, 32, 20, 10}; static signed char oflow_less[] = {6, 38, 24, 14, 4}; #define N_TONE_HEAD_TABLE 13 #define N_TONE_NUCLEUS_TABLE 13 typedef struct { unsigned char pre_start; unsigned char pre_end; unsigned char body_start; unsigned char body_end; int *body_drops; unsigned char body_max_steps; char body_lower_u; unsigned char n_overflow; signed char *overflow; } TONE_HEAD; typedef struct { unsigned char pitch_env0; /* pitch envelope, tonic syllable at end */ unsigned char tonic_max0; unsigned char tonic_min0; unsigned char pitch_env1; /* followed by unstressed */ unsigned char tonic_max1; unsigned char tonic_min1; short *backwards; unsigned char tail_start; unsigned char tail_end; unsigned char flags; } TONE_NUCLEUS; #define T_EMPH 1 static TONE_HEAD tone_head_table[N_TONE_HEAD_TABLE] = { {46, 57, 78, 50, drops_0, 3, 7, 5, oflow}, // 0 statement {46, 57, 78, 46, drops_0, 3, 7, 5, oflow}, // 1 comma {46, 57, 78, 46, drops_0, 3, 7, 5, oflow}, // 2 question {46, 57, 90, 50, drops_0, 3, 9, 5, oflow_emf}, // 3 exclamation {46, 57, 78, 50, drops_0, 3, 7, 5, oflow}, // 4 statement, emphatic {46, 57, 74, 55, drops_0, 4, 7, 5, oflow_less}, // 5 statement, less intonation {46, 57, 74, 55, drops_0, 4, 7, 5, oflow_less}, // 6 comma, less intonation {46, 57, 74, 55, drops_0, 4, 7, 5, oflow_less}, // 7 comma, less intonation, less rise {46, 57, 78, 50, drops_0, 3, 7, 5, oflow}, // 8 pitch raises at end of sentence {46, 57, 78, 46, drops_0, 3, 7, 5, oflow}, // 9 comma {46, 57, 78, 50, drops_0, 3, 7, 5, oflow}, // 10 question {34, 41, 41, 32, drops_0, 3, 7, 5, oflow_less}, // 11 test {46, 57, 55, 50, drops_0, 3, 7, 5, oflow_less}, // 12 test }; static TONE_NUCLEUS tone_nucleus_table[N_TONE_NUCLEUS_TABLE] = { {PITCHfall, 64, 8, PITCHfall, 70,18, NULL, 24, 12, 0}, // 0 statement {PITCHfrise, 80,18, PITCHfrise2, 78,22, NULL, 34, 52, 0}, // 1 comma {PITCHfrise, 88,22, PITCHfrise2, 82,22, NULL, 34, 64, 0}, // 2 question {PITCHfall, 92, 8, PITCHfall, 92,80, NULL, 76, 8, T_EMPH}, // 3 exclamation {PITCHfall, 86, 4, PITCHfall, 94,66, NULL, 34, 10, 0}, // 4 statement, emphatic {PITCHfall, 62,10, PITCHfall, 62,20, NULL, 28, 16, 0}, // 5 statement, less intonation {PITCHfrise, 68,18, PITCHfrise2, 68,22, NULL, 30, 44, 0}, // 6 comma, less intonation {PITCHfrise2, 64,16, PITCHfall, 66,32, NULL, 32, 18, 0}, // 7 comma, less intonation, less rise {PITCHrise, 68,46, PITCHfall, 42,32, NULL, 46, 58, 0}, // 8 pitch raises at end of sentence {PITCHfrise, 78,24, PITCHfrise2, 72,22, NULL, 42, 52, 0}, // 9 comma {PITCHfrise, 88,34, PITCHfall, 64,32, NULL, 46, 82, 0}, // 10 question {PITCHfall, 56,12, PITCHfall, 56,20, NULL, 24, 12, 0}, // 11 test {PITCHfall, 70,18, PITCHfall, 70,24, NULL, 32, 20, 0}, // 12 test }; /* index by 0=. 1=, 2=?, 3=! 4=none, 5=emphasized */ unsigned char punctuation_to_tone[INTONATION_TYPES][PUNCT_INTONATIONS] = { {0,1,2,3,0,4}, {0,1,2,3,0,4}, {5,6,2,3,0,4}, {5,7,1,3,0,4}, {8,9,10,3,0,0}, {8,8,10,3,0,0}, {11,11,11,11,0,0}, // 6 test {12,12,12,12,0,0} }; int n_tunes = 0; TUNE *tunes = NULL; #define SECONDARY 3 #define PRIMARY 4 #define PRIMARY_STRESSED 6 #define PRIMARY_LAST 7 static int number_pre; static int number_body; static int number_tail; static int last_primary; static int tone_posn; static int tone_posn2; static int no_tonic; static void count_pitch_vowels(int start, int end, int clause_end) /****************************************************************/ { int ix; int stress; int max_stress = 0; int max_stress_posn = 0; // last syllable ot the highest stress int max_stress_posn2 = 0; // penuntimate syllable of the highest stress number_pre = -1; /* number of vowels before 1st primary stress */ number_body = 0; number_tail = 0; /* number between tonic syllable and next primary */ last_primary = -1; for(ix=start; ix= max_stress) { if(stress > max_stress) { max_stress_posn2 = ix; } else { max_stress_posn2 = max_stress_posn; } max_stress_posn = ix; max_stress = stress; } if(stress >= PRIMARY) { if(number_pre < 0) number_pre = ix - start; last_primary = ix; } } if(number_pre < 0) number_pre = end; number_tail = end - max_stress_posn - 1; tone_posn = max_stress_posn; tone_posn2 = max_stress_posn2; if(no_tonic) { tone_posn = tone_posn2 = end; // next position after the end of the truncated clause } else if(last_primary >= 0) { if(end == clause_end) { syllable_tab[last_primary].stress = PRIMARY_LAST; } } else { // no primary stress. Use the highest stress syllable_tab[tone_posn].stress = PRIMARY_LAST; } } /* end of count_pitch_vowels */ static int count_increments(int ix, int end_ix, int min_stress) /*************************************************************/ /* Count number of primary stresses up to tonic syllable or body_reset */ { int count = 0; int stress; while(ix < end_ix) { stress = syllable_tab[ix++].stress; if(stress >= PRIMARY_LAST) break; if(stress >= min_stress) count++; } return(count); } /* end of count_increments */ static void set_pitch(SYLLABLE *syl, int base, int drop) /******************************************************/ // Set the pitch of a vowel in syllable_tab { int pitch1, pitch2; int flags = 0; if(base < 0) base = 0; pitch2 = base; if(drop < 0) { flags = SYL_RISE; drop = -drop; } pitch1 = pitch2 + drop; if(pitch1 < 0) pitch1 = 0; if(pitch1 > 254) pitch1 = 254; if(pitch2 > 254) pitch2 = 254; syl->pitch1 = pitch1; syl->pitch2 = pitch2; syl->flags |= flags; } /* end of set_pitch */ static int CountUnstressed(int start, int end, int limit) {//====================================================== int ix; for(ix=start; ix <= end; ix++) { if(syllable_tab[ix].stress >= limit) break; } return(ix - start); } static int SetHeadIntonation(TUNE *tune, int syl_ix, int end_ix, int control) {//========================================================================== int stress; SYLLABLE *syl; int ix; int pitch=0; int increment=0; int n_steps=0; int stage; // onset, head, last int initial; int overflow_ix=0; int pitch_range; int pitch_range_abs; int *drops; int n_unstressed=0; int unstressed_ix=0; int unstressed_inc; int used_onset = 0; int head_final = end_ix; int secondary=2; // 2 pitch_range = (tune->head_end - tune->head_start) << 8; pitch_range_abs = abs(pitch_range); drops = drops_0; // this should be controled by tune->head_drops initial = 1; stage = 0; if(tune->onset == 255) stage = 1; // no onset specified if(tune->head_last != 255) { // find the last primary stress in the body for(ix = end_ix-1; ix >= syl_ix; ix--) { if(syllable_tab[ix].stress >= 4) { head_final = ix; break; } } } while(syl_ix < end_ix) { syl = &syllable_tab[syl_ix]; stress = syl->stress; if(initial || (stress >= 4)) { // a primary stress if((initial) || (stress == 5)) { initial = 0; overflow_ix = 0; if(tune->onset == 255) { n_steps = count_increments(syl_ix, head_final, 4); pitch = tune->head_start << 8; } else { // a pitch has been specified for the onset syllable, don't include it in the pitch incrementing n_steps = count_increments(syl_ix+1, head_final, 4); pitch = tune->onset << 8; used_onset = 1; } if(n_steps > tune->head_max_steps) n_steps = tune->head_max_steps; if(n_steps > 1) { increment = pitch_range / (n_steps -1); } else increment = 0; } else if(syl_ix == head_final) { // a pitch has been specified for the last primary stress before the nucleus pitch = tune->head_last << 8; stage = 2; } else { if(used_onset) { stage = 1; used_onset = 0; pitch = tune->head_start << 8; n_steps++; } else if(n_steps > 0) pitch += increment; else { pitch = (tune->head_end << 8) + (pitch_range_abs * tune->head_extend[overflow_ix++])/64; if(overflow_ix >= tune->n_head_extend) { overflow_ix = 0; } } } n_steps--; } if(stress >= PRIMARY) { n_unstressed = CountUnstressed(syl_ix+1, end_ix, secondary); unstressed_ix = 0; syl->stress = PRIMARY_STRESSED; syl->env = tune->stressed_env; set_pitch(syl,(pitch >> 8), tune->stressed_drop); } else if(stress >= secondary) { n_unstressed = CountUnstressed(syl_ix+1, end_ix, secondary); unstressed_ix = 0; set_pitch(syl,(pitch >> 8),drops[stress]); } else { if(n_unstressed > 1) unstressed_inc = (tune->unstr_end[stage] - tune->unstr_start[stage]) / (n_unstressed - 1); else unstressed_inc = 0; set_pitch(syl, (pitch >> 8) + tune->unstr_start[stage] + (unstressed_inc * unstressed_ix), drops[stress]); unstressed_ix++; } syl_ix++; } return(syl_ix); } // end of SetBodyIntonation static int calc_pitch_segment(int ix, int end_ix, TONE_HEAD *th, TONE_NUCLEUS *tn, int min_stress, int continuing) /**********************************************************************************************/ /* Calculate pitches until next RESET or tonic syllable, or end. Increment pitch if stress is >= min_stress. Used for tonic segment */ { int stress; int pitch=0; int increment=0; int n_primary=0; int n_steps=0; int initial; int overflow=0; int n_overflow; int pitch_range; int pitch_range_abs; int *drops; signed char *overflow_tab; SYLLABLE *syl; static signed char continue_tab[5] = {-26, 32, 20, 8, 0}; drops = th->body_drops; pitch_range = (th->body_end - th->body_start) << 8; pitch_range_abs = abs(pitch_range); if(continuing) { initial =0; overflow = 0; n_overflow = 5; overflow_tab = continue_tab; increment = pitch_range / (th->body_max_steps -1); } else { n_overflow = th->n_overflow; overflow_tab = th->overflow; initial = 1; } while(ix < end_ix) { syl = &syllable_tab[ix]; stress = syl->stress; // if(stress == PRIMARY_MARKED) // initial = 1; // reset the intonation pattern if(initial || (stress >= min_stress)) { // a primary stress if((initial) || (stress == 5)) { initial = 0; overflow = 0; n_steps = n_primary = count_increments(ix,end_ix,min_stress); if(n_steps > th->body_max_steps) n_steps = th->body_max_steps; if(n_steps > 1) { increment = pitch_range / (n_steps -1); } else increment = 0; pitch = th->body_start << 8; } else { if(n_steps > 0) pitch += increment; else { pitch = (th->body_end << 8) + (pitch_range_abs * overflow_tab[overflow++])/64; if(overflow >= n_overflow) { overflow = 0; overflow_tab = th->overflow; } } } n_steps--; n_primary--; if((tn->backwards) && (n_primary < 2)) { pitch = tn->backwards[n_primary] << 8; } } if(stress >= PRIMARY) { syl->stress = PRIMARY_STRESSED; set_pitch(syl,(pitch >> 8),drops[stress]); } else if(stress >= SECONDARY) { set_pitch(syl,(pitch >> 8),drops[stress]); } else { /* unstressed, drop pitch if preceded by PRIMARY */ if((syllable_tab[ix-1].stress & 0x3f) >= SECONDARY) set_pitch(syl,(pitch >> 8) - th->body_lower_u, drops[stress]); else set_pitch(syl,(pitch >> 8),drops[stress]); } ix++; } return(ix); } /* end of calc_pitch_segment */ static void SetPitchGradient(int start_ix, int end_ix, int start_pitch, int end_pitch) {//==================================================================================== // Set a linear pitch change over a number of syllables. // Used for pre-head, unstressed syllables in the body, and the tail int ix; int stress; int pitch; int increment; int n_increments; int drop; SYLLABLE *syl; increment = (end_pitch - start_pitch) << 8; n_increments = end_ix - start_ix; if(n_increments <= 0) return; if(n_increments > 1) { increment = increment / n_increments; } pitch = start_pitch << 8; for(ix=start_ix; ix < end_ix; ix++) { syl = &syllable_tab[ix]; stress = syl->stress; if(increment > 0) { set_pitch(syl,(pitch >> 8),-(increment >> 8)); pitch += increment; } else { drop = -(increment >> 8); if(drop < min_drop[stress]) drop = min_drop[stress]; pitch += increment; if(drop > 18) drop = 18; set_pitch(syl, (pitch >> 8), drop); } } } // end of SetPitchGradient static int calc_pitches2(int start, int end, int tune_number) //============================================================ // Calculate pitch values for the vowels in this tone group { int ix; TUNE *tune; int drop; tune = &tunes[tune_number]; ix = start; /* vowels before the first primary stress */ /******************************************/ SetPitchGradient(ix, ix+number_pre, tune->prehead_start, tune->prehead_end); ix += number_pre; /* body of tonic segment */ /*************************/ if(option_tone_flags & OPTION_EMPHASIZE_PENULTIMATE) { tone_posn = tone_posn2; // put tone on the penultimate stressed word } ix = SetHeadIntonation(tune, ix, tone_posn, 0); if(no_tonic) return(0); /* tonic syllable */ /******************/ // if(tn->flags & T_EMPH) // { // syllable_tab[ix].flags |= SYL_EMPHASIS; // } if(number_tail == 0) { tone_pitch_env = tune->nucleus0_env; drop = tune->nucleus0_max - tune->nucleus0_min; set_pitch(&syllable_tab[ix++],tune->nucleus0_min, drop); } else { tone_pitch_env = tune->nucleus1_env; drop = tune->nucleus1_max - tune->nucleus1_min; set_pitch(&syllable_tab[ix++],tune->nucleus1_min, drop); } syllable_tab[tone_posn].env = tone_pitch_env; if(syllable_tab[tone_posn].stress == PRIMARY) syllable_tab[tone_posn].stress = PRIMARY_STRESSED; /* tail, after the tonic syllable */ /**********************************/ SetPitchGradient(ix, end, tune->tail_start, tune->tail_end); return(tone_pitch_env); } /* end of calc_pitches2 */ static int calc_pitches(int control, int start, int end, int tune_number) //======================================================================== // Calculate pitch values for the vowels in this tone group { int ix; TONE_HEAD *th; TONE_NUCLEUS *tn; int drop; int continuing = 0; if(control == 0) { return(calc_pitches2(start, end, tune_number)); } if(start > 0) continuing = 1; th = &tone_head_table[tune_number]; tn = &tone_nucleus_table[tune_number]; ix = start; /* vowels before the first primary stress */ /******************************************/ SetPitchGradient(ix, ix+number_pre, th->pre_start, th->pre_end); ix += number_pre; /* body of tonic segment */ /*************************/ if(option_tone_flags & OPTION_EMPHASIZE_PENULTIMATE) { tone_posn = tone_posn2; // put tone on the penultimate stressed word } ix = calc_pitch_segment(ix,tone_posn, th, tn, PRIMARY, continuing); // ix = SetBodyIntonation(&tunes[0], ix, tone_posn, 0); if(no_tonic) return(0); /* tonic syllable */ /******************/ if(tn->flags & T_EMPH) { syllable_tab[ix].flags |= SYL_EMPHASIS; } if(number_tail == 0) { tone_pitch_env = tn->pitch_env0; drop = tn->tonic_max0 - tn->tonic_min0; set_pitch(&syllable_tab[ix++],tn->tonic_min0, drop); } else { tone_pitch_env = tn->pitch_env1; drop = tn->tonic_max1 - tn->tonic_min1; set_pitch(&syllable_tab[ix++],tn->tonic_min1, drop); } syllable_tab[tone_posn].env = tone_pitch_env; if(syllable_tab[tone_posn].stress == PRIMARY) syllable_tab[tone_posn].stress = PRIMARY_STRESSED; /* tail, after the tonic syllable */ /**********************************/ SetPitchGradient(ix, end, tn->tail_start, tn->tail_end); return(tone_pitch_env); } /* end of calc_pitches */ static void CalcPitches_Tone(Translator *tr, int clause_tone) {//========================================================== // clause_tone: 0=. 1=, 2=?, 3=! 4=none PHONEME_LIST *p; int ix; int count_stressed=0; int final_stressed=0; int tone_ph; int pause; int tone_promoted; PHONEME_TAB *tph; PHONEME_TAB *prev_tph; // forget across word boundary PHONEME_TAB *prevw_tph; // remember across word boundary // PHONEME_TAB *prev2_tph; // 2 tones previous PHONEME_LIST *prev_p; int pitch_adjust = 0; // pitch gradient through the clause - inital value int pitch_decrement = 0; // decrease by this for each stressed syllable int pitch_low = 0; // until it drops to this int pitch_high = 0; // then reset to this // count number of stressed syllables p = &phoneme_list[0]; for(ix=0; ixtype == phVOWEL) && (p->stresslevel >= 4)) { if(count_stressed == 0) final_stressed = ix; if(p->stresslevel >= 4) { final_stressed = ix; count_stressed++; } } } phoneme_list[final_stressed].stresslevel = 7; // language specific, changes to tones if(tr->translator_name == L('v','i')) { // LANG=vi p = &phoneme_list[final_stressed]; if(p->tone_ph == 0) p->tone_ph = PhonemeCode('7'); // change default tone (tone 1) to falling tone at end of clause } pause = 1; tone_promoted = 0; prev_p = p = &phoneme_list[0]; prev_tph = prevw_tph = phoneme_tab[phonPAUSE]; // perform tone sandhi for(ix=0; ixtype == phPAUSE) && (p->ph->std_length > 50)) { pause = 1; // there is a pause since the previous vowel prevw_tph = phoneme_tab[phonPAUSE]; // forget previous tone } if(p->newword) { prev_tph = phoneme_tab[phonPAUSE]; // forget across word boundaries } if(p->synthflags & SFLAG_SYLLABLE) { tone_ph = p->tone_ph; tph = phoneme_tab[tone_ph]; // Mandarin if(tr->translator_name == L('z','h')) { if(tone_ph == 0) { if(pause || tone_promoted) { tone_ph = PhonemeCode2('5','5'); // no previous vowel, use tone 1 tone_promoted = 1; } else { tone_ph = PhonemeCode2('1','1'); // default tone 5 } p->tone_ph = tone_ph; tph = phoneme_tab[tone_ph]; } else { tone_promoted = 0; } if(ix == final_stressed) { if((tph->mnemonic == 0x3535 ) || (tph->mnemonic == 0x3135)) { // change sentence final tone 1 or 4 to stress 6, not 7 phoneme_list[final_stressed].stresslevel = 6; } } if(prevw_tph->mnemonic == 0x343132) // [214] { if(tph->mnemonic == 0x343132) // [214] prev_p->tone_ph = PhonemeCode2('3','5'); else prev_p->tone_ph = PhonemeCode2('2','1'); } if((prev_tph->mnemonic == 0x3135) && (tph->mnemonic == 0x3135)) // [51] + [51] { prev_p->tone_ph = PhonemeCode2('5','3'); } if(tph->mnemonic == 0x3131) // [11] Tone 5 { // tone 5, change its level depending on the previous tone (across word boundaries) if(prevw_tph->mnemonic == 0x3535) p->tone_ph = PhonemeCode2('2','2'); if(prevw_tph->mnemonic == 0x3533) p->tone_ph = PhonemeCode2('3','3'); if(prevw_tph->mnemonic == 0x343132) p->tone_ph = PhonemeCode2('4','4'); // tone 5 is unstressed (shorter) p->stresslevel = 0; // diminished stress } } prev_p = p; // prev2_tph = prevw_tph; prevw_tph = prev_tph = tph; pause = 0; } } // convert tone numbers to pitch p = &phoneme_list[0]; for(ix=0; ixsynthflags & SFLAG_SYLLABLE) { tone_ph = p->tone_ph; if(p->stresslevel != 0) // TEST, consider all syllables as stressed { if(ix == final_stressed) { // the last stressed syllable pitch_adjust = pitch_low; } else { pitch_adjust -= pitch_decrement; if(pitch_adjust <= pitch_low) pitch_adjust = pitch_high; } } if(tone_ph ==0) { tone_ph = phonDEFAULTTONE; // no tone specified, use default tone 1 p->tone_ph = tone_ph; } p->pitch1 = pitch_adjust + phoneme_tab[tone_ph]->start_type; p->pitch2 = pitch_adjust + phoneme_tab[tone_ph]->end_type; } } } // end of Translator::CalcPitches_Tone void CalcPitches(Translator *tr, int clause_type) {//============================================== // clause_type: 0=. 1=, 2=?, 3=! 4=none PHONEME_LIST *p; SYLLABLE *syl; int ix; int x; int st_ix; int n_st; int option; int group_tone; int group_tone_emph; int group_tone_comma; int ph_start=0; int st_start; int st_clause_end; int count; int n_primary; int count_primary; PHONEME_TAB *ph; int ph_end=n_phoneme_list; SYLLABLE syllable_tab2[N_PHONEME_LIST]; syllable_tab = syllable_tab2; // don't use permanent storage. it's only needed during the call of CalcPitches() n_st = 0; n_primary = 0; for(ix=0; ix<(n_phoneme_list-1); ix++) { p = &phoneme_list[ix]; if(p->synthflags & SFLAG_SYLLABLE) { syllable_tab[n_st].flags = 0; syllable_tab[n_st].env = PITCHfall; syllable_tab[n_st].nextph_type = phoneme_list[ix+1].type; syllable_tab[n_st++].stress = p->stresslevel; if(p->stresslevel >= 4) n_primary++; } else if((p->ph->code == phonPAUSE_CLAUSE) && (n_st > 0)) { syllable_tab[n_st-1].flags |= SYL_END_CLAUSE; } } syllable_tab[n_st].stress = 0; // extra 0 entry at the end if(n_st == 0) return; // nothing to do if(tr->langopts.tone_language == 1) { CalcPitches_Tone(tr,clause_type); return; } option = tr->langopts.intonation_group; if(option >= INTONATION_TYPES) option = 1; if(option == 0) { group_tone = tr->langopts.tunes[clause_type]; group_tone_emph = tr->langopts.tunes[5]; group_tone_comma = tr->langopts.tunes[1]; } else { group_tone = tr->punct_to_tone[option][clause_type]; group_tone_emph = tr->punct_to_tone[option][5]; // emphatic form of statement group_tone_comma = tr->punct_to_tone[option][1]; // emphatic form of statement } if(clause_type == 4) no_tonic = 1; /* incomplete clause, used for abbreviations such as Mr. Dr. Mrs. */ else no_tonic = 0; st_start = 0; count_primary=0; for(st_ix=0; st_ixstress >= 4) count_primary++; if(syl->stress == 6) { // reduce the stress of the previous stressed syllable (review only the previous few syllables) for(ix=st_ix-1; ix>=st_start && ix>=(st_ix-3); ix--) { if(syllable_tab[ix].stress == 6) break; if(syllable_tab[ix].stress == 4) { syllable_tab[ix].stress = 3; break; } } // are the next primary syllables also emphasized ? for(ix=st_ix+1; ixstress = 5; break; } } } if(syl->stress == 6) { // an emphasized syllable, end the tone group after the next primary stress syllable_tab[st_ix].flags = SYL_EMPHASIS; count = 0; if((n_primary - count_primary) > 1) count =1; for(ix=st_ix+1; ix 4) break; if(syllable_tab[ix].stress == 4) { count++; if(count > 1) break; } } count_pitch_vowels(st_start, ix, n_st); if((ix < n_st) || (clause_type == 0)) calc_pitches(option, st_start, ix, group_tone_emph); // split into > 1 tone groups, use emphatic tone else calc_pitches(option, st_start, ix, group_tone); st_start = ix; } if((st_start < st_ix) && (syl->flags & SYL_END_CLAUSE)) { // end of clause after this syllable, indicated by a phonPAUSE_CLAUSE phoneme st_clause_end = st_ix+1; count_pitch_vowels(st_start, st_clause_end, st_clause_end); calc_pitches(option, st_start, st_clause_end, group_tone_comma); st_start = st_clause_end; } } if(st_start < st_ix) { count_pitch_vowels(st_start, st_ix, n_st); calc_pitches(option, st_start, st_ix, group_tone); } // unpack pitch data st_ix=0; for(ix=ph_start; ix < ph_end; ix++) { p = &phoneme_list[ix]; p->stresslevel = syllable_tab[st_ix].stress; if(p->synthflags & SFLAG_SYLLABLE) { syl = &syllable_tab[st_ix]; p->pitch1 = syl->pitch1; p->pitch2 = syl->pitch2; p->env = PITCHfall; if(syl->flags & SYL_RISE) { p->env = PITCHrise; } else if(p->stresslevel > 5) p->env = syl->env; if(p->pitch1 > p->pitch2) { // swap so that pitch2 is the higher x = p->pitch1; p->pitch1 = p->pitch2; p->pitch2 = x; } if(p->tone_ph) { ph = phoneme_tab[p->tone_ph]; x = (p->pitch1 + p->pitch2)/2; p->pitch2 = x + ph->end_type; p->pitch1 = x + ph->start_type; } if(syl->flags & SYL_EMPHASIS) { p->stresslevel |= 8; // emphasized } st_ix++; } } } // end of CalcPitches sources_5316/external/espeak/portaudio19.h0000664000176700017670000012351511674622653017373 0ustar paulpaul// NOTE: Copy this file to portaudio.h in order to compile with V19 portaudio #ifndef PORTAUDIO_H #define PORTAUDIO_H /* * $Id: portaudio.h 1061 2006-06-19 22:46:41Z lschwardt $ * PortAudio Portable Real-Time Audio Library * PortAudio API Header File * Latest version available at: http://www.portaudio.com/ * * Copyright (c) 1999-2002 Ross Bencina and Phil Burk * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files * (the "Software"), to deal in the Software without restriction, * including without limitation the rights to use, copy, modify, merge, * publish, distribute, sublicense, and/or sell copies of the Software, * and to permit persons to whom the Software is furnished to do so, * subject to the following conditions: * * The above copyright notice and this permission notice shall be * included in all copies or substantial portions of the Software. * * Any person wishing to distribute modifications to the Software is * requested to send the modifications to the original developer so that * they can be incorporated into the canonical version. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ /** @file @brief The PortAudio API. */ #ifdef __cplusplus extern "C" { #endif /* __cplusplus */ /** Retrieve the release number of the currently running PortAudio build, eg 1900. */ int Pa_GetVersion( void ); /** Retrieve a textual description of the current PortAudio build, eg "PortAudio V19-devel 13 October 2002". */ const char* Pa_GetVersionText( void ); /** Error codes returned by PortAudio functions. Note that with the exception of paNoError, all PaErrorCodes are negative. */ typedef int PaError; typedef enum PaErrorCode { paNoError = 0, paNotInitialized = -10000, paUnanticipatedHostError, paInvalidChannelCount, paInvalidSampleRate, paInvalidDevice, paInvalidFlag, paSampleFormatNotSupported, paBadIODeviceCombination, paInsufficientMemory, paBufferTooBig, paBufferTooSmall, paNullCallback, paBadStreamPtr, paTimedOut, paInternalError, paDeviceUnavailable, paIncompatibleHostApiSpecificStreamInfo, paStreamIsStopped, paStreamIsNotStopped, paInputOverflowed, paOutputUnderflowed, paHostApiNotFound, paInvalidHostApi, paCanNotReadFromACallbackStream, /**< @todo review error code name */ paCanNotWriteToACallbackStream, /**< @todo review error code name */ paCanNotReadFromAnOutputOnlyStream, /**< @todo review error code name */ paCanNotWriteToAnInputOnlyStream, /**< @todo review error code name */ paIncompatibleStreamHostApi, paBadBufferPtr } PaErrorCode; /** Translate the supplied PortAudio error code into a human readable message. */ const char *Pa_GetErrorText( PaError errorCode ); /** Library initialization function - call this before using PortAudio. This function initialises internal data structures and prepares underlying host APIs for use. This function MUST be called before using any other PortAudio API functions. If Pa_Initialize() is called multiple times, each successful call must be matched with a corresponding call to Pa_Terminate(). Pairs of calls to Pa_Initialize()/Pa_Terminate() may overlap, and are not required to be fully nested. Note that if Pa_Initialize() returns an error code, Pa_Terminate() should NOT be called. @return paNoError if successful, otherwise an error code indicating the cause of failure. @see Pa_Terminate */ PaError Pa_Initialize( void ); /** Library termination function - call this when finished using PortAudio. This function deallocates all resources allocated by PortAudio since it was initializied by a call to Pa_Initialize(). In cases where Pa_Initialise() has been called multiple times, each call must be matched with a corresponding call to Pa_Terminate(). The final matching call to Pa_Terminate() will automatically close any PortAudio streams that are still open. Pa_Terminate() MUST be called before exiting a program which uses PortAudio. Failure to do so may result in serious resource leaks, such as audio devices not being available until the next reboot. @return paNoError if successful, otherwise an error code indicating the cause of failure. @see Pa_Initialize */ PaError Pa_Terminate( void ); /** The type used to refer to audio devices. Values of this type usually range from 0 to (Pa_DeviceCount-1), and may also take on the PaNoDevice and paUseHostApiSpecificDeviceSpecification values. @see Pa_DeviceCount, paNoDevice, paUseHostApiSpecificDeviceSpecification */ typedef int PaDeviceIndex; /** A special PaDeviceIndex value indicating that no device is available, or should be used. @see PaDeviceIndex */ #define paNoDevice ((PaDeviceIndex)-1) /** A special PaDeviceIndex value indicating that the device(s) to be used are specified in the host api specific stream info structure. @see PaDeviceIndex */ #define paUseHostApiSpecificDeviceSpecification ((PaDeviceIndex)-2) /* Host API enumeration mechanism */ /** The type used to enumerate to host APIs at runtime. Values of this type range from 0 to (Pa_GetHostApiCount()-1). @see Pa_GetHostApiCount */ typedef int PaHostApiIndex; /** Retrieve the number of available host APIs. Even if a host API is available it may have no devices available. @return A non-negative value indicating the number of available host APIs or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. @see PaHostApiIndex */ PaHostApiIndex Pa_GetHostApiCount( void ); /** Retrieve the index of the default host API. The default host API will be the lowest common denominator host API on the current platform and is unlikely to provide the best performance. @return A non-negative value ranging from 0 to (Pa_GetHostApiCount()-1) indicating the default host API index or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. */ PaHostApiIndex Pa_GetDefaultHostApi( void ); /** Unchanging unique identifiers for each supported host API. This type is used in the PaHostApiInfo structure. The values are guaranteed to be unique and to never change, thus allowing code to be written that conditionally uses host API specific extensions. New type ids will be allocated when support for a host API reaches "public alpha" status, prior to that developers should use the paInDevelopment type id. @see PaHostApiInfo */ typedef enum PaHostApiTypeId { paInDevelopment=0, /* use while developing support for a new host API */ paDirectSound=1, paMME=2, paASIO=3, paSoundManager=4, paCoreAudio=5, paOSS=7, paALSA=8, paAL=9, paBeOS=10, paWDMKS=11, paJACK=12, paWASAPI=13, paAudioScienceHPI=14 } PaHostApiTypeId; /** A structure containing information about a particular host API. */ typedef struct PaHostApiInfo { /** this is struct version 1 */ int structVersion; /** The well known unique identifier of this host API @see PaHostApiTypeId */ PaHostApiTypeId type; /** A textual description of the host API for display on user interfaces. */ const char *name; /** The number of devices belonging to this host API. This field may be used in conjunction with Pa_HostApiDeviceIndexToDeviceIndex() to enumerate all devices for this host API. @see Pa_HostApiDeviceIndexToDeviceIndex */ int deviceCount; /** The default input device for this host API. The value will be a device index ranging from 0 to (Pa_GetDeviceCount()-1), or paNoDevice if no default input device is available. */ PaDeviceIndex defaultInputDevice; /** The default output device for this host API. The value will be a device index ranging from 0 to (Pa_GetDeviceCount()-1), or paNoDevice if no default output device is available. */ PaDeviceIndex defaultOutputDevice; } PaHostApiInfo; /** Retrieve a pointer to a structure containing information about a specific host Api. @param hostApi A valid host API index ranging from 0 to (Pa_GetHostApiCount()-1) @return A pointer to an immutable PaHostApiInfo structure describing a specific host API. If the hostApi parameter is out of range or an error is encountered, the function returns NULL. The returned structure is owned by the PortAudio implementation and must not be manipulated or freed. The pointer is only guaranteed to be valid between calls to Pa_Initialize() and Pa_Terminate(). */ const PaHostApiInfo * Pa_GetHostApiInfo( PaHostApiIndex hostApi ); /** Convert a static host API unique identifier, into a runtime host API index. @param type A unique host API identifier belonging to the PaHostApiTypeId enumeration. @return A valid PaHostApiIndex ranging from 0 to (Pa_GetHostApiCount()-1) or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. The paHostApiNotFound error code indicates that the host API specified by the type parameter is not available. @see PaHostApiTypeId */ PaHostApiIndex Pa_HostApiTypeIdToHostApiIndex( PaHostApiTypeId type ); /** Convert a host-API-specific device index to standard PortAudio device index. This function may be used in conjunction with the deviceCount field of PaHostApiInfo to enumerate all devices for the specified host API. @param hostApi A valid host API index ranging from 0 to (Pa_GetHostApiCount()-1) @param hostApiDeviceIndex A valid per-host device index in the range 0 to (Pa_GetHostApiInfo(hostApi)->deviceCount-1) @return A non-negative PaDeviceIndex ranging from 0 to (Pa_GetDeviceCount()-1) or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. A paInvalidHostApi error code indicates that the host API index specified by the hostApi parameter is out of range. A paInvalidDevice error code indicates that the hostApiDeviceIndex parameter is out of range. @see PaHostApiInfo */ PaDeviceIndex Pa_HostApiDeviceIndexToDeviceIndex( PaHostApiIndex hostApi, int hostApiDeviceIndex ); /** Structure used to return information about a host error condition. */ typedef struct PaHostErrorInfo{ PaHostApiTypeId hostApiType; /**< the host API which returned the error code */ long errorCode; /**< the error code returned */ const char *errorText; /**< a textual description of the error if available, otherwise a zero-length string */ }PaHostErrorInfo; /** Return information about the last host error encountered. The error information returned by Pa_GetLastHostErrorInfo() will never be modified asyncronously by errors occurring in other PortAudio owned threads (such as the thread that manages the stream callback.) This function is provided as a last resort, primarily to enhance debugging by providing clients with access to all available error information. @return A pointer to an immutable structure constaining information about the host error. The values in this structure will only be valid if a PortAudio function has previously returned the paUnanticipatedHostError error code. */ const PaHostErrorInfo* Pa_GetLastHostErrorInfo( void ); /* Device enumeration and capabilities */ /** Retrieve the number of available devices. The number of available devices may be zero. @return A non-negative value indicating the number of available devices or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. */ PaDeviceIndex Pa_GetDeviceCount( void ); /** Retrieve the index of the default input device. The result can be used in the inputDevice parameter to Pa_OpenStream(). @return The default input device index for the default host API, or paNoDevice if no default input device is available or an error was encountered. */ PaDeviceIndex Pa_GetDefaultInputDevice( void ); /** Retrieve the index of the default output device. The result can be used in the outputDevice parameter to Pa_OpenStream(). @return The default output device index for the defualt host API, or paNoDevice if no default output device is available or an error was encountered. @note On the PC, the user can specify a default device by setting an environment variable. For example, to use device #1.
 set PA_RECOMMENDED_OUTPUT_DEVICE=1
The user should first determine the available device ids by using the supplied application "pa_devs". */ PaDeviceIndex Pa_GetDefaultOutputDevice( void ); /** The type used to represent monotonic time in seconds that can be used for syncronisation. The type is used for the outTime argument to the PaStreamCallback and as the result of Pa_GetStreamTime(). @see PaStreamCallback, Pa_GetStreamTime */ typedef double PaTime; /** A type used to specify one or more sample formats. Each value indicates a possible format for sound data passed to and from the stream callback, Pa_ReadStream and Pa_WriteStream. The standard formats paFloat32, paInt16, paInt32, paInt24, paInt8 and aUInt8 are usually implemented by all implementations. The floating point representation (paFloat32) uses +1.0 and -1.0 as the maximum and minimum respectively. paUInt8 is an unsigned 8 bit format where 128 is considered "ground" The paNonInterleaved flag indicates that a multichannel buffer is passed as a set of non-interleaved pointers. @see Pa_OpenStream, Pa_OpenDefaultStream, PaDeviceInfo @see paFloat32, paInt16, paInt32, paInt24, paInt8 @see paUInt8, paCustomFormat, paNonInterleaved */ typedef unsigned long PaSampleFormat; #define paFloat32 ((PaSampleFormat) 0x00000001) /**< @see PaSampleFormat */ #define paInt32 ((PaSampleFormat) 0x00000002) /**< @see PaSampleFormat */ #define paInt24 ((PaSampleFormat) 0x00000004) /**< Packed 24 bit format. @see PaSampleFormat */ #define paInt16 ((PaSampleFormat) 0x00000008) /**< @see PaSampleFormat */ #define paInt8 ((PaSampleFormat) 0x00000010) /**< @see PaSampleFormat */ #define paUInt8 ((PaSampleFormat) 0x00000020) /**< @see PaSampleFormat */ #define paCustomFormat ((PaSampleFormat) 0x00010000)/**< @see PaSampleFormat */ #define paNonInterleaved ((PaSampleFormat) 0x80000000) /** A structure providing information and capabilities of PortAudio devices. Devices may support input, output or both input and output. */ typedef struct PaDeviceInfo { int structVersion; /* this is struct version 2 */ const char *name; PaHostApiIndex hostApi; /* note this is a host API index, not a type id*/ int maxInputChannels; int maxOutputChannels; /* Default latency values for interactive performance. */ PaTime defaultLowInputLatency; PaTime defaultLowOutputLatency; /* Default latency values for robust non-interactive applications (eg. playing sound files). */ PaTime defaultHighInputLatency; PaTime defaultHighOutputLatency; double defaultSampleRate; } PaDeviceInfo; /** Retrieve a pointer to a PaDeviceInfo structure containing information about the specified device. @return A pointer to an immutable PaDeviceInfo structure. If the device parameter is out of range the function returns NULL. @param device A valid device index in the range 0 to (Pa_GetDeviceCount()-1) @note PortAudio manages the memory referenced by the returned pointer, the client must not manipulate or free the memory. The pointer is only guaranteed to be valid between calls to Pa_Initialize() and Pa_Terminate(). @see PaDeviceInfo, PaDeviceIndex */ const PaDeviceInfo* Pa_GetDeviceInfo( PaDeviceIndex device ); /** Parameters for one direction (input or output) of a stream. */ typedef struct PaStreamParameters { /** A valid device index in the range 0 to (Pa_GetDeviceCount()-1) specifying the device to be used or the special constant paUseHostApiSpecificDeviceSpecification which indicates that the actual device(s) to use are specified in hostApiSpecificStreamInfo. This field must not be set to paNoDevice. */ PaDeviceIndex device; /** The number of channels of sound to be delivered to the stream callback or accessed by Pa_ReadStream() or Pa_WriteStream(). It can range from 1 to the value of maxInputChannels in the PaDeviceInfo record for the device specified by the device parameter. */ int channelCount; /** The sample format of the buffer provided to the stream callback, a_ReadStream() or Pa_WriteStream(). It may be any of the formats described by the PaSampleFormat enumeration. */ PaSampleFormat sampleFormat; /** The desired latency in seconds. Where practical, implementations should configure their latency based on these parameters, otherwise they may choose the closest viable latency instead. Unless the suggested latency is greater than the absolute upper limit for the device implementations should round the suggestedLatency up to the next practial value - ie to provide an equal or higher latency than suggestedLatency wherever possibe. Actual latency values for an open stream may be retrieved using the inputLatency and outputLatency fields of the PaStreamInfo structure returned by Pa_GetStreamInfo(). @see default*Latency in PaDeviceInfo, *Latency in PaStreamInfo */ PaTime suggestedLatency; /** An optional pointer to a host api specific data structure containing additional information for device setup and/or stream processing. hostApiSpecificStreamInfo is never required for correct operation, if not used it should be set to NULL. */ void *hostApiSpecificStreamInfo; } PaStreamParameters; /** Return code for Pa_IsFormatSupported indicating success. */ #define paFormatIsSupported (0) /** Determine whether it would be possible to open a stream with the specified parameters. @param inputParameters A structure that describes the input parameters used to open a stream. The suggestedLatency field is ignored. See PaStreamParameters for a description of these parameters. inputParameters must be NULL for output-only streams. @param outputParameters A structure that describes the output parameters used to open a stream. The suggestedLatency field is ignored. See PaStreamParameters for a description of these parameters. outputParameters must be NULL for input-only streams. @param sampleRate The required sampleRate. For full-duplex streams it is the sample rate for both input and output @return Returns 0 if the format is supported, and an error code indicating why the format is not supported otherwise. The constant paFormatIsSupported is provided to compare with the return value for success. @see paFormatIsSupported, PaStreamParameters */ PaError Pa_IsFormatSupported( const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate ); /* Streaming types and functions */ /** A single PaStream can provide multiple channels of real-time streaming audio input and output to a client application. A stream provides access to audio hardware represented by one or more PaDevices. Depending on the underlying Host API, it may be possible to open multiple streams using the same device, however this behavior is implementation defined. Portable applications should assume that a PaDevice may be simultaneously used by at most one PaStream. Pointers to PaStream objects are passed between PortAudio functions that operate on streams. @see Pa_OpenStream, Pa_OpenDefaultStream, Pa_OpenDefaultStream, Pa_CloseStream, Pa_StartStream, Pa_StopStream, Pa_AbortStream, Pa_IsStreamActive, Pa_GetStreamTime, Pa_GetStreamCpuLoad */ typedef void PaStream; /** Can be passed as the framesPerBuffer parameter to Pa_OpenStream() or Pa_OpenDefaultStream() to indicate that the stream callback will accept buffers of any size. */ #define paFramesPerBufferUnspecified (0) /** Flags used to control the behavior of a stream. They are passed as parameters to Pa_OpenStream or Pa_OpenDefaultStream. Multiple flags may be ORed together. @see Pa_OpenStream, Pa_OpenDefaultStream @see paNoFlag, paClipOff, paDitherOff, paNeverDropInput, paPrimeOutputBuffersUsingStreamCallback, paPlatformSpecificFlags */ typedef unsigned long PaStreamFlags; /** @see PaStreamFlags */ #define paNoFlag ((PaStreamFlags) 0) /** Disable default clipping of out of range samples. @see PaStreamFlags */ #define paClipOff ((PaStreamFlags) 0x00000001) /** Disable default dithering. @see PaStreamFlags */ #define paDitherOff ((PaStreamFlags) 0x00000002) /** Flag requests that where possible a full duplex stream will not discard overflowed input samples without calling the stream callback. This flag is only valid for full duplex callback streams and only when used in combination with the paFramesPerBufferUnspecified (0) framesPerBuffer parameter. Using this flag incorrectly results in a paInvalidFlag error being returned from Pa_OpenStream and Pa_OpenDefaultStream. @see PaStreamFlags, paFramesPerBufferUnspecified */ #define paNeverDropInput ((PaStreamFlags) 0x00000004) /** Call the stream callback to fill initial output buffers, rather than the default behavior of priming the buffers with zeros (silence). This flag has no effect for input-only and blocking read/write streams. @see PaStreamFlags */ #define paPrimeOutputBuffersUsingStreamCallback ((PaStreamFlags) 0x00000008) /** A mask specifying the platform specific bits. @see PaStreamFlags */ #define paPlatformSpecificFlags ((PaStreamFlags)0xFFFF0000) /** Timing information for the buffers passed to the stream callback. */ typedef struct PaStreamCallbackTimeInfo{ PaTime inputBufferAdcTime; PaTime currentTime; PaTime outputBufferDacTime; } PaStreamCallbackTimeInfo; /** Flag bit constants for the statusFlags to PaStreamCallback. @see paInputUnderflow, paInputOverflow, paOutputUnderflow, paOutputOverflow, paPrimingOutput */ typedef unsigned long PaStreamCallbackFlags; /** In a stream opened with paFramesPerBufferUnspecified, indicates that input data is all silence (zeros) because no real data is available. In a stream opened without paFramesPerBufferUnspecified, it indicates that one or more zero samples have been inserted into the input buffer to compensate for an input underflow. @see PaStreamCallbackFlags */ #define paInputUnderflow ((PaStreamCallbackFlags) 0x00000001) /** In a stream opened with paFramesPerBufferUnspecified, indicates that data prior to the first sample of the input buffer was discarded due to an overflow, possibly because the stream callback is using too much CPU time. Otherwise indicates that data prior to one or more samples in the input buffer was discarded. @see PaStreamCallbackFlags */ #define paInputOverflow ((PaStreamCallbackFlags) 0x00000002) /** Indicates that output data (or a gap) was inserted, possibly because the stream callback is using too much CPU time. @see PaStreamCallbackFlags */ #define paOutputUnderflow ((PaStreamCallbackFlags) 0x00000004) /** Indicates that output data will be discarded because no room is available. @see PaStreamCallbackFlags */ #define paOutputOverflow ((PaStreamCallbackFlags) 0x00000008) /** Some of all of the output data will be used to prime the stream, input data may be zero. @see PaStreamCallbackFlags */ #define paPrimingOutput ((PaStreamCallbackFlags) 0x00000010) /** Allowable return values for the PaStreamCallback. @see PaStreamCallback */ typedef enum PaStreamCallbackResult { paContinue=0, paComplete=1, paAbort=2 } PaStreamCallbackResult; /** Functions of type PaStreamCallback are implemented by PortAudio clients. They consume, process or generate audio in response to requests from an active PortAudio stream. @param input and @param output are arrays of interleaved samples, the format, packing and number of channels used by the buffers are determined by parameters to Pa_OpenStream(). @param frameCount The number of sample frames to be processed by the stream callback. @param timeInfo The time in seconds when the first sample of the input buffer was received at the audio input, the time in seconds when the first sample of the output buffer will begin being played at the audio output, and the time in seconds when the stream callback was called. See also Pa_GetStreamTime() @param statusFlags Flags indicating whether input and/or output buffers have been inserted or will be dropped to overcome underflow or overflow conditions. @param userData The value of a user supplied pointer passed to Pa_OpenStream() intended for storing synthesis data etc. @return The stream callback should return one of the values in the PaStreamCallbackResult enumeration. To ensure that the callback continues to be called, it should return paContinue (0). Either paComplete or paAbort can be returned to finish stream processing, after either of these values is returned the callback will not be called again. If paAbort is returned the stream will finish as soon as possible. If paComplete is returned, the stream will continue until all buffers generated by the callback have been played. This may be useful in applications such as soundfile players where a specific duration of output is required. However, it is not necessary to utilise this mechanism as Pa_StopStream(), Pa_AbortStream() or Pa_CloseStream() can also be used to stop the stream. The callback must always fill the entire output buffer irrespective of its return value. @see Pa_OpenStream, Pa_OpenDefaultStream @note With the exception of Pa_GetStreamCpuLoad() it is not permissable to call PortAudio API functions from within the stream callback. */ typedef int PaStreamCallback( const void *input, void *output, unsigned long frameCount, const PaStreamCallbackTimeInfo* timeInfo, PaStreamCallbackFlags statusFlags, void *userData ); /** Opens a stream for either input, output or both. @param stream The address of a PaStream pointer which will receive a pointer to the newly opened stream. @param inputParameters A structure that describes the input parameters used by the opened stream. See PaStreamParameters for a description of these parameters. inputParameters must be NULL for output-only streams. @param outputParameters A structure that describes the output parameters used by the opened stream. See PaStreamParameters for a description of these parameters. outputParameters must be NULL for input-only streams. @param sampleRate The desired sampleRate. For full-duplex streams it is the sample rate for both input and output @param framesPerBuffer The number of frames passed to the stream callback function, or the preferred block granularity for a blocking read/write stream. The special value paFramesPerBufferUnspecified (0) may be used to request that the stream callback will recieve an optimal (and possibly varying) number of frames based on host requirements and the requested latency settings. Note: With some host APIs, the use of non-zero framesPerBuffer for a callback stream may introduce an additional layer of buffering which could introduce additional latency. PortAudio guarantees that the additional latency will be kept to the theoretical minimum however, it is strongly recommended that a non-zero framesPerBuffer value only be used when your algorithm requires a fixed number of frames per stream callback. @param streamFlags Flags which modify the behaviour of the streaming process. This parameter may contain a combination of flags ORed together. Some flags may only be relevant to certain buffer formats. @param streamCallback A pointer to a client supplied function that is responsible for processing and filling input and output buffers. If this parameter is NULL the stream will be opened in 'blocking read/write' mode. In blocking mode, the client can receive sample data using Pa_ReadStream and write sample data using Pa_WriteStream, the number of samples that may be read or written without blocking is returned by Pa_GetStreamReadAvailable and Pa_GetStreamWriteAvailable respectively. @param userData A client supplied pointer which is passed to the stream callback function. It could for example, contain a pointer to instance data necessary for processing the audio buffers. This parameter is ignored if streamCallback is NULL. @return Upon success Pa_OpenStream() returns paNoError and places a pointer to a valid PaStream in the stream argument. The stream is inactive (stopped). If a call to Pa_OpenStream() fails, a non-zero error code is returned (see PaError for possible error codes) and the value of stream is invalid. @see PaStreamParameters, PaStreamCallback, Pa_ReadStream, Pa_WriteStream, Pa_GetStreamReadAvailable, Pa_GetStreamWriteAvailable */ PaError Pa_OpenStream( PaStream** stream, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData ); /** A simplified version of Pa_OpenStream() that opens the default input and/or output devices. @param stream The address of a PaStream pointer which will receive a pointer to the newly opened stream. @param numInputChannels The number of channels of sound that will be supplied to the stream callback or returned by Pa_ReadStream. It can range from 1 to the value of maxInputChannels in the PaDeviceInfo record for the default input device. If 0 the stream is opened as an output-only stream. @param numOutputChannels The number of channels of sound to be delivered to the stream callback or passed to Pa_WriteStream. It can range from 1 to the value of maxOutputChannels in the PaDeviceInfo record for the default output dvice. If 0 the stream is opened as an output-only stream. @param sampleFormat The sample format of both the input and output buffers provided to the callback or passed to and from Pa_ReadStream and Pa_WriteStream. sampleFormat may be any of the formats described by the PaSampleFormat enumeration. @param sampleRate Same as Pa_OpenStream parameter of the same name. @param framesPerBuffer Same as Pa_OpenStream parameter of the same name. @param streamCallback Same as Pa_OpenStream parameter of the same name. @param userData Same as Pa_OpenStream parameter of the same name. @return As for Pa_OpenStream @see Pa_OpenStream, PaStreamCallback */ PaError Pa_OpenDefaultStream( PaStream** stream, int numInputChannels, int numOutputChannels, PaSampleFormat sampleFormat, double sampleRate, unsigned long framesPerBuffer, PaStreamCallback *streamCallback, void *userData ); /** Closes an audio stream. If the audio stream is active it discards any pending buffers as if Pa_AbortStream() had been called. */ PaError Pa_CloseStream( PaStream *stream ); /** Functions of type PaStreamFinishedCallback are implemented by PortAudio clients. They can be registered with a stream using the Pa_SetStreamFinishedCallback function. Once registered they are called when the stream becomes inactive (ie once a call to Pa_StopStream() will not block). A stream will become inactive after the stream callback returns non-zero, or when Pa_StopStream or Pa_AbortStream is called. For a stream providing audio output, if the stream callback returns paComplete, or Pa_StopStream is called, the stream finished callback will not be called until all generated sample data has been played. @param userData The userData parameter supplied to Pa_OpenStream() @see Pa_SetStreamFinishedCallback */ typedef void PaStreamFinishedCallback( void *userData ); /** Register a stream finished callback function which will be called when the stream becomes inactive. See the description of PaStreamFinishedCallback for further details about when the callback will be called. @param stream a pointer to a PaStream that is in the stopped state - if the stream is not stopped, the stream's finished callback will remain unchanged and an error code will be returned. @param streamFinishedCallback a pointer to a function with the same signature as PaStreamFinishedCallback, that will be called when the stream becomes inactive. Passing NULL for this parameter will un-register a previously registered stream finished callback function. @return on success returns paNoError, otherwise an error code indicating the cause of the error. @see PaStreamFinishedCallback */ PaError Pa_SetStreamFinishedCallback( PaStream *stream, PaStreamFinishedCallback* streamFinishedCallback ); /** Commences audio processing. */ PaError Pa_StartStream( PaStream *stream ); /** Terminates audio processing. It waits until all pending audio buffers have been played before it returns. */ PaError Pa_StopStream( PaStream *stream ); /** Terminates audio processing immediately without waiting for pending buffers to complete. */ PaError Pa_AbortStream( PaStream *stream ); /** Determine whether the stream is stopped. A stream is considered to be stopped prior to a successful call to Pa_StartStream and after a successful call to Pa_StopStream or Pa_AbortStream. If a stream callback returns a value other than paContinue the stream is NOT considered to be stopped. @return Returns one (1) when the stream is stopped, zero (0) when the stream is running or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. @see Pa_StopStream, Pa_AbortStream, Pa_IsStreamActive */ PaError Pa_IsStreamStopped( PaStream *stream ); /** Determine whether the stream is active. A stream is active after a successful call to Pa_StartStream(), until it becomes inactive either as a result of a call to Pa_StopStream() or Pa_AbortStream(), or as a result of a return value other than paContinue from the stream callback. In the latter case, the stream is considered inactive after the last buffer has finished playing. @return Returns one (1) when the stream is active (ie playing or recording audio), zero (0) when not playing or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. @see Pa_StopStream, Pa_AbortStream, Pa_IsStreamStopped */ PaError Pa_IsStreamActive( PaStream *stream ); /** A structure containing unchanging information about an open stream. @see Pa_GetStreamInfo */ typedef struct PaStreamInfo { /** this is struct version 1 */ int structVersion; /** The input latency of the stream in seconds. This value provides the most accurate estimate of input latency available to the implementation. It may differ significantly from the suggestedLatency value passed to Pa_OpenStream(). The value of this field will be zero (0.) for output-only streams. @see PaTime */ PaTime inputLatency; /** The output latency of the stream in seconds. This value provides the most accurate estimate of output latency available to the implementation. It may differ significantly from the suggestedLatency value passed to Pa_OpenStream(). The value of this field will be zero (0.) for input-only streams. @see PaTime */ PaTime outputLatency; /** The sample rate of the stream in Hertz (samples per second). In cases where the hardware sample rate is inaccurate and PortAudio is aware of it, the value of this field may be different from the sampleRate parameter passed to Pa_OpenStream(). If information about the actual hardware sample rate is not available, this field will have the same value as the sampleRate parameter passed to Pa_OpenStream(). */ double sampleRate; } PaStreamInfo; /** Retrieve a pointer to a PaStreamInfo structure containing information about the specified stream. @return A pointer to an immutable PaStreamInfo structure. If the stream parameter invalid, or an error is encountered, the function returns NULL. @param stream A pointer to an open stream previously created with Pa_OpenStream. @note PortAudio manages the memory referenced by the returned pointer, the client must not manipulate or free the memory. The pointer is only guaranteed to be valid until the specified stream is closed. @see PaStreamInfo */ const PaStreamInfo* Pa_GetStreamInfo( PaStream *stream ); /** Determine the current time for the stream according to the same clock used to generate buffer timestamps. This time may be used for syncronising other events to the audio stream, for example synchronizing audio to MIDI. @return The stream's current time in seconds, or 0 if an error occurred. @see PaTime, PaStreamCallback */ PaTime Pa_GetStreamTime( PaStream *stream ); /** Retrieve CPU usage information for the specified stream. The "CPU Load" is a fraction of total CPU time consumed by a callback stream's audio processing routines including, but not limited to the client supplied stream callback. This function does not work with blocking read/write streams. This function may be called from the stream callback function or the application. @return A floating point value, typically between 0.0 and 1.0, where 1.0 indicates that the stream callback is consuming the maximum number of CPU cycles possible to maintain real-time operation. A value of 0.5 would imply that PortAudio and the stream callback was consuming roughly 50% of the available CPU time. The return value may exceed 1.0. A value of 0.0 will always be returned for a blocking read/write stream, or if an error occurrs. */ double Pa_GetStreamCpuLoad( PaStream* stream ); /** Read samples from an input stream. The function doesn't return until the entire buffer has been filled - this may involve waiting for the operating system to supply the data. @param stream A pointer to an open stream previously created with Pa_OpenStream. @param buffer A pointer to a buffer of sample frames. The buffer contains samples in the format specified by the inputParameters->sampleFormat field used to open the stream, and the number of channels specified by inputParameters->numChannels. If non-interleaved samples were requested, buffer is a pointer to the first element of an array of non-interleaved buffer pointers, one for each channel. @param frames The number of frames to be read into buffer. This parameter is not constrained to a specific range, however high performance applications will want to match this parameter to the framesPerBuffer parameter used when opening the stream. @return On success PaNoError will be returned, or PaInputOverflowed if input data was discarded by PortAudio after the previous call and before this call. */ PaError Pa_ReadStream( PaStream* stream, void *buffer, unsigned long frames ); /** Write samples to an output stream. This function doesn't return until the entire buffer has been consumed - this may involve waiting for the operating system to consume the data. @param stream A pointer to an open stream previously created with Pa_OpenStream. @param buffer A pointer to a buffer of sample frames. The buffer contains samples in the format specified by the outputParameters->sampleFormat field used to open the stream, and the number of channels specified by outputParameters->numChannels. If non-interleaved samples were requested, buffer is a pointer to the first element of an array of non-interleaved buffer pointers, one for each channel. @param frames The number of frames to be written from buffer. This parameter is not constrained to a specific range, however high performance applications will want to match this parameter to the framesPerBuffer parameter used when opening the stream. @return On success PaNoError will be returned, or paOutputUnderflowed if additional output data was inserted after the previous call and before this call. */ PaError Pa_WriteStream( PaStream* stream, const void *buffer, unsigned long frames ); /** Retrieve the number of frames that can be read from the stream without waiting. @return Returns a non-negative value representing the maximum number of frames that can be read from the stream without blocking or busy waiting or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. */ signed long Pa_GetStreamReadAvailable( PaStream* stream ); /** Retrieve the number of frames that can be written to the stream without waiting. @return Returns a non-negative value representing the maximum number of frames that can be written to the stream without blocking or busy waiting or, a PaErrorCode (which are always negative) if PortAudio is not initialized or an error is encountered. */ signed long Pa_GetStreamWriteAvailable( PaStream* stream ); /* Miscellaneous utilities */ /** Retrieve the size of a given sample format in bytes. @return The size in bytes of a single sample in the specified format, or paSampleFormatNotSupported if the format is not supported. */ PaError Pa_GetSampleSize( PaSampleFormat format ); /** Put the caller to sleep for at least 'msec' milliseconds. This function is provided only as a convenience for authors of portable code (such as the tests and examples in the PortAudio distribution.) The function may sleep longer than requested so don't rely on this for accurate musical timing. */ void Pa_Sleep( long msec ); #ifdef __cplusplus } #endif /* __cplusplus */ #endif /* PORTAUDIO_H */ sources_5316/external/espeak/klatt.cpp0000664000176700017670000010267311723710247016657 0ustar paulpaul /*************************************************************************** * Copyright (C) 2008 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * Based on a re-implementation by: * * (c) 1993,94 Jon Iles and Nick Ing-Simmons * * of the Klatt cascade-parallel formant synthesizer * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, see: * * . * ***************************************************************************/ // See URL: ftp://svr-ftp.eng.cam.ac.uk/pub/comp.speech/synthesis/klatt.3.04.tar.gz #include "StdAfx.h" #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "klatt.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #ifdef INCLUDE_KLATT // conditional compilation for the whole file extern unsigned char *out_ptr; // **JSD extern unsigned char *out_start; extern unsigned char *out_end; extern WGEN_DATA wdata; static int nsamples; static int sample_count; #ifdef _MSC_VER #define getrandom(min,max) ((rand()%(int)(((max)+1)-(min)))+(min)) #else #define getrandom(min,max) ((rand()%(long)(((max)+1)-(min)))+(min)) #endif /* function prototypes for functions private to this file */ static void flutter(klatt_frame_ptr); static double sampled_source (void); static double impulsive_source (void); static double natural_source (void); static void pitch_synch_par_reset (klatt_frame_ptr); static double gen_noise (double); static double DBtoLIN (long); static void frame_init (klatt_frame_ptr); static void setabc (long,long,resonator_ptr); static void setzeroabc (long,long,resonator_ptr); static klatt_frame_t kt_frame; static klatt_global_t kt_globals; /* function RESONATOR This is a generic resonator function. Internal memory for the resonator is stored in the globals structure. */ static double resonator(resonator_ptr r, double input) { double x; x = (double) ((double)r->a * (double)input + (double)r->b * (double)r->p1 + (double)r->c * (double)r->p2); r->p2 = (double)r->p1; r->p1 = (double)x; return (double)x; } static double resonator2(resonator_ptr r, double input) { double x; x = (double) ((double)r->a * (double)input + (double)r->b * (double)r->p1 + (double)r->c * (double)r->p2); r->p2 = (double)r->p1; r->p1 = (double)x; r->a += r->a_inc; r->b += r->b_inc; r->c += r->c_inc; return (double)x; } /* function ANTIRESONATOR This is a generic anti-resonator function. The code is the same as resonator except that a,b,c need to be set with setzeroabc() and we save inputs in p1/p2 rather than outputs. There is currently only one of these - "rnz" Output = (rnz.a * input) + (rnz.b * oldin1) + (rnz.c * oldin2) */ #ifdef deleted static double antiresonator(resonator_ptr r, double input) { register double x = (double)r->a * (double)input + (double)r->b * (double)r->p1 + (double)r->c * (double)r->p2; r->p2 = (double)r->p1; r->p1 = (double)input; return (double)x; } #endif static double antiresonator2(resonator_ptr r, double input) { register double x = (double)r->a * (double)input + (double)r->b * (double)r->p1 + (double)r->c * (double)r->p2; r->p2 = (double)r->p1; r->p1 = (double)input; r->a += r->a_inc; r->b += r->b_inc; r->c += r->c_inc; return (double)x; } /* function FLUTTER This function adds F0 flutter, as specified in: "Analysis, synthesis and perception of voice quality variations among female and male talkers" D.H. Klatt and L.C. Klatt JASA 87(2) February 1990. Flutter is added by applying a quasi-random element constructed from three slowly varying sine waves. */ static void flutter(klatt_frame_ptr frame) { static int time_count; double delta_f0; double fla,flb,flc,fld,fle; fla = (double) kt_globals.f0_flutter / 50; flb = (double) kt_globals.original_f0 / 100; // flc = sin(2*PI*12.7*time_count); // fld = sin(2*PI*7.1*time_count); // fle = sin(2*PI*4.7*time_count); flc = sin(PI*12.7*time_count); // because we are calling flutter() more frequently, every 2.9mS fld = sin(PI*7.1*time_count); fle = sin(PI*4.7*time_count); delta_f0 = fla * flb * (flc + fld + fle) * 10; frame->F0hz10 = frame->F0hz10 + (long) delta_f0; time_count++; } /* function SAMPLED_SOURCE Allows the use of a glottal excitation waveform sampled from a real voice. */ static double sampled_source() { int itemp; double ftemp; double result; double diff_value; int current_value; int next_value; double temp_diff; if(kt_globals.T0!=0) { ftemp = (double) kt_globals.nper; ftemp = ftemp / kt_globals.T0; ftemp = ftemp * kt_globals.num_samples; itemp = (int) ftemp; temp_diff = ftemp - (double) itemp; current_value = kt_globals.natural_samples[itemp]; next_value = kt_globals.natural_samples[itemp+1]; diff_value = (double) next_value - (double) current_value; diff_value = diff_value * temp_diff; result = kt_globals.natural_samples[itemp] + diff_value; result = result * kt_globals.sample_factor; } else { result = 0; } return(result); } /* function PARWAVE Converts synthesis parameters to a waveform. */ static int parwave(klatt_frame_ptr frame) { double temp; int value; double outbypas; double out; long n4; double frics; double glotout; double aspiration; double casc_next_in; double par_glotout; static double noise; static double voice; static double vlast; static double glotlast; static double sourc; int ix; flutter(frame); /* add f0 flutter */ #ifdef LOG_FRAMES if(option_log_frames) { FILE *f; f=fopen("log-klatt","a"); fprintf(f,"%4dhz %2dAV %4d %3d, %4d %3d, %4d %3d, %4d %3d, %4d, %3d, FNZ=%3d TLT=%2d\n",frame->F0hz10,frame->AVdb, frame->Fhz[1],frame->Bhz[1],frame->Fhz[2],frame->Bhz[2],frame->Fhz[3],frame->Bhz[3],frame->Fhz[4],frame->Bhz[4],frame->Fhz[5],frame->Bhz[5],frame->Fhz[0],frame->TLTdb); fclose(f); } #endif /* MAIN LOOP, for each output sample of current frame: */ for (kt_globals.ns=0; kt_globals.ns kt_globals.nmod) { noise *= (double) 0.5; } /* Compute frication noise */ frics = kt_globals.amp_frica * noise; /* Compute voicing waveform. Run glottal source simulation at 4 times normal sample rate to minimize quantization noise in period of female voice. */ for (n4=0; n4<4; n4++) { switch(kt_globals.glsource) { case IMPULSIVE: voice = impulsive_source(); break; case NATURAL: voice = natural_source(); break; case SAMPLED: voice = sampled_source(); break; } /* Reset period when counter 'nper' reaches T0 */ if (kt_globals.nper >= kt_globals.T0) { kt_globals.nper = 0; pitch_synch_par_reset(frame); } /* Low-pass filter voicing waveform before downsampling from 4*samrate to samrate samples/sec. Resonator f=.09*samrate, bw=.06*samrate */ voice = resonator(&(kt_globals.rsn[RLP]),voice); /* Increment counter that keeps track of 4*samrate samples per sec */ kt_globals.nper++; } /* Tilt spectrum of voicing source down by soft low-pass filtering, amount of tilt determined by TLTdb */ voice = (voice * kt_globals.onemd) + (vlast * kt_globals.decay); vlast = voice; /* Add breathiness during glottal open phase. Amount of breathiness determined by parameter Aturb Use nrand rather than noise because noise is low-passed. */ if (kt_globals.nper < kt_globals.nopen) { voice += kt_globals.amp_breth * kt_globals.nrand; } /* Set amplitude of voicing */ glotout = kt_globals.amp_voice * voice; par_glotout = kt_globals.par_amp_voice * voice; /* Compute aspiration amplitude and add to voicing source */ aspiration = kt_globals.amp_aspir * noise; glotout += aspiration; par_glotout += aspiration; /* Cascade vocal tract, excited by laryngeal sources. Nasal antiresonator, then formants FNP, F5, F4, F3, F2, F1 */ out=0; if(kt_globals.synthesis_model != ALL_PARALLEL) { casc_next_in = antiresonator2(&(kt_globals.rsn[Rnz]),glotout); casc_next_in = resonator(&(kt_globals.rsn[Rnpc]),casc_next_in); casc_next_in = resonator(&(kt_globals.rsn[R8c]),casc_next_in); casc_next_in = resonator(&(kt_globals.rsn[R7c]),casc_next_in); casc_next_in = resonator(&(kt_globals.rsn[R6c]),casc_next_in); casc_next_in = resonator2(&(kt_globals.rsn[R5c]),casc_next_in); casc_next_in = resonator2(&(kt_globals.rsn[R4c]),casc_next_in); casc_next_in = resonator2(&(kt_globals.rsn[R3c]),casc_next_in); casc_next_in = resonator2(&(kt_globals.rsn[R2c]),casc_next_in); out = resonator2(&(kt_globals.rsn[R1c]),casc_next_in); } /* Excite parallel F1 and FNP by voicing waveform */ sourc = par_glotout; /* Source is voicing plus aspiration */ /* Standard parallel vocal tract Formants F6,F5,F4,F3,F2, outputs added with alternating sign. Sound source for other parallel resonators is frication plus first difference of voicing waveform. */ out += resonator(&(kt_globals.rsn[R1p]),sourc); out += resonator(&(kt_globals.rsn[Rnpp]),sourc); sourc = frics + par_glotout - glotlast; glotlast = par_glotout; for(ix=R2p; ix<=R6p; ix++) { out = resonator(&(kt_globals.rsn[ix]),sourc) - out; } outbypas = kt_globals.amp_bypas * sourc; out = outbypas - out; #ifdef deleted // for testing if (kt_globals.outsl != 0) { switch(kt_globals.outsl) { case 1: out = voice; break; case 2: out = aspiration; break; case 3: out = frics; break; case 4: out = glotout; break; case 5: out = par_glotout; break; case 6: out = outbypas; break; case 7: out = sourc; break; } } #endif out = resonator(&(kt_globals.rsn[Rout]),out); temp = (int)(out * wdata.amplitude * kt_globals.amp_gain0) ; /* Convert back to integer */ // mix with a recorded WAV if required for this phoneme { int z2; signed char c; int sample; z2 = 0; if(wdata.mix_wavefile_ix < wdata.n_mix_wavefile) { if(wdata.mix_wave_scale == 0) { // a 16 bit sample c = wdata.mix_wavefile[wdata.mix_wavefile_ix+1]; sample = wdata.mix_wavefile[wdata.mix_wavefile_ix] + (c * 256); wdata.mix_wavefile_ix += 2; } else { // a 8 bit sample, scaled sample = (signed char)wdata.mix_wavefile[wdata.mix_wavefile_ix++] * wdata.mix_wave_scale; } z2 = sample * wdata.amplitude_v / 1024; z2 = (z2 * wdata.mix_wave_amp)/40; temp += z2; } } // if fadeout is set, fade to zero over 64 samples, to avoid clicks at end of synthesis if(kt_globals.fadeout > 0) { kt_globals.fadeout--; temp = (temp * kt_globals.fadeout) / 64; } value = (int)temp + ((echo_buf[echo_tail++]*echo_amp) >> 8); if(echo_tail >= N_ECHO_BUF) echo_tail=0; if (value < -32768) { value = -32768; } if (value > 32767) { value = 32767; } *out_ptr++ = value; *out_ptr++ = value >> 8; echo_buf[echo_head++] = value; if(echo_head >= N_ECHO_BUF) echo_head = 0; sample_count++; if(out_ptr >= out_end) { return(1); } } return(0); } // end of parwave void KlattReset(int control) { int r_ix; if(control == 2) { //Full reset kt_globals.FLPhz = (950 * kt_globals.samrate) / 10000; kt_globals.BLPhz = (630 * kt_globals.samrate) / 10000; kt_globals.minus_pi_t = -PI / kt_globals.samrate; kt_globals.two_pi_t = -2.0 * kt_globals.minus_pi_t; setabc(kt_globals.FLPhz,kt_globals.BLPhz,&(kt_globals.rsn[RLP])); } if(control > 0) { kt_globals.nper = 0; kt_globals.T0 = 0; kt_globals.nopen = 0; kt_globals.nmod = 0; for(r_ix=RGL; r_ix < N_RSN; r_ix++) { kt_globals.rsn[r_ix].p1 = 0; kt_globals.rsn[r_ix].p2 = 0; } } for(r_ix=0; r_ix <= R6p; r_ix++) { kt_globals.rsn[r_ix].p1 = 0; kt_globals.rsn[r_ix].p2 = 0; } } /* function FRAME_INIT Use parameters from the input frame to set up resonator coefficients. */ static void frame_init(klatt_frame_ptr frame) { double amp_par[7]; static double amp_par_factor[7] = {0.6, 0.4, 0.15, 0.06, 0.04, 0.022, 0.03}; long Gain0_tmp; int ix; kt_globals.original_f0 = frame->F0hz10 / 10; frame->AVdb_tmp = frame->AVdb - 7; if (frame->AVdb_tmp < 0) { frame->AVdb_tmp = 0; } kt_globals.amp_aspir = DBtoLIN(frame->ASP) * 0.05; kt_globals.amp_frica = DBtoLIN(frame->AF) * 0.25; kt_globals.par_amp_voice = DBtoLIN(frame->AVpdb); kt_globals.amp_bypas = DBtoLIN(frame->AB) * 0.05; for(ix=0; ix <= 6; ix++) { // parallel amplitudes F1 to F6, and parallel nasal pole amp_par[ix] = DBtoLIN(frame->Ap[ix]) * amp_par_factor[ix]; } Gain0_tmp = frame->Gain0 - 3; if (Gain0_tmp <= 0) { Gain0_tmp = 57; } kt_globals.amp_gain0 = DBtoLIN(Gain0_tmp) / kt_globals.scale_wav; /* Set coefficients of variable cascade resonators */ for(ix=1; ix<=9; ix++) { // formants 1 to 8, plus nasal pole setabc(frame->Fhz[ix],frame->Bhz[ix],&(kt_globals.rsn[ix])); if(ix <= 5) { setabc(frame->Fhz_next[ix],frame->Bhz_next[ix],&(kt_globals.rsn_next[ix])); kt_globals.rsn[ix].a_inc = (kt_globals.rsn_next[ix].a - kt_globals.rsn[ix].a) / 64.0; kt_globals.rsn[ix].b_inc = (kt_globals.rsn_next[ix].b - kt_globals.rsn[ix].b) / 64.0; kt_globals.rsn[ix].c_inc = (kt_globals.rsn_next[ix].c - kt_globals.rsn[ix].c) / 64.0; } } // nasal zero anti-resonator setzeroabc(frame->Fhz[F_NZ],frame->Bhz[F_NZ],&(kt_globals.rsn[Rnz])); setzeroabc(frame->Fhz_next[F_NZ],frame->Bhz_next[F_NZ],&(kt_globals.rsn_next[Rnz])); kt_globals.rsn[F_NZ].a_inc = (kt_globals.rsn_next[F_NZ].a - kt_globals.rsn[F_NZ].a) / 64.0; kt_globals.rsn[F_NZ].b_inc = (kt_globals.rsn_next[F_NZ].b - kt_globals.rsn[F_NZ].b) / 64.0; kt_globals.rsn[F_NZ].c_inc = (kt_globals.rsn_next[F_NZ].c - kt_globals.rsn[F_NZ].c) / 64.0; /* Set coefficients of parallel resonators, and amplitude of outputs */ for(ix=0; ix<=6; ix++) { setabc(frame->Fhz[ix],frame->Bphz[ix],&(kt_globals.rsn[Rparallel+ix])); kt_globals.rsn[Rparallel+ix].a *= amp_par[ix]; } /* output low-pass filter */ setabc((long)0.0,(long)(kt_globals.samrate/2),&(kt_globals.rsn[Rout])); } /* function IMPULSIVE_SOURCE Generate a low pass filtered train of impulses as an approximation of a natural excitation waveform. Low-pass filter the differentiated impulse with a critically-damped second-order filter, time constant proportional to Kopen. */ static double impulsive_source() { static double doublet[] = {0.0,13000000.0,-13000000.0}; static double vwave; if (kt_globals.nper < 3) { vwave = doublet[kt_globals.nper]; } else { vwave = 0.0; } return(resonator(&(kt_globals.rsn[RGL]),vwave)); } /* function NATURAL_SOURCE Vwave is the differentiated glottal flow waveform, there is a weak spectral zero around 800 Hz, magic constants a,b reset pitch synchronously. */ static double natural_source() { double lgtemp; static double vwave; if (kt_globals.nper < kt_globals.nopen) { kt_globals.pulse_shape_a -= kt_globals.pulse_shape_b; vwave += kt_globals.pulse_shape_a; lgtemp=vwave * 0.028; return(lgtemp); } else { vwave = 0.0; return(0.0); } } /* function PITCH_SYNC_PAR_RESET Reset selected parameters pitch-synchronously. Constant B0 controls shape of glottal pulse as a function of desired duration of open phase N0 (Note that N0 is specified in terms of 40,000 samples/sec of speech) Assume voicing waveform V(t) has form: k1 t**2 - k2 t**3 If the radiation characterivative, a temporal derivative is folded in, and we go from continuous time to discrete integers n: dV/dt = vwave[n] = sum over i=1,2,...,n of { a - (i * b) } = a n - b/2 n**2 where the constants a and b control the detailed shape and amplitude of the voicing waveform over the open potion of the voicing cycle "nopen". Let integral of dV/dt have no net dc flow --> a = (b * nopen) / 3 Let maximum of dUg(n)/dn be constant --> b = gain / (nopen * nopen) meaning as nopen gets bigger, V has bigger peak proportional to n Thus, to generate the table below for 40 <= nopen <= 263: B0[nopen - 40] = 1920000 / (nopen * nopen) */ static void pitch_synch_par_reset(klatt_frame_ptr frame) { long temp; double temp1; static long skew; static short B0[224] = { 1200,1142,1088,1038, 991, 948, 907, 869, 833, 799, 768, 738, 710, 683, 658, 634, 612, 590, 570, 551, 533, 515, 499, 483, 468, 454, 440, 427, 415, 403, 391, 380, 370, 360, 350, 341, 332, 323, 315, 307, 300, 292, 285, 278, 272, 265, 259, 253, 247, 242, 237, 231, 226, 221, 217, 212, 208, 204, 199, 195, 192, 188, 184, 180, 177, 174, 170, 167, 164, 161, 158, 155, 153, 150, 147, 145, 142, 140, 137, 135, 133, 131, 128, 126, 124, 122, 120, 119, 117, 115, 113,111, 110, 108, 106, 105, 103, 102, 100, 99, 97, 96, 95, 93, 92, 91, 90, 88, 87, 86, 85, 84, 83, 82, 80, 79, 78, 77, 76, 75, 75, 74, 73, 72, 71, 70, 69, 68, 68, 67, 66, 65, 64, 64, 63, 62, 61, 61, 60, 59, 59, 58, 57, 57, 56, 56, 55, 55, 54, 54, 53, 53, 52, 52, 51, 51, 50, 50, 49, 49, 48, 48, 47, 47, 46, 46, 45, 45, 44, 44, 43, 43, 42, 42, 41, 41, 41, 41, 40, 40, 39, 39, 38, 38, 38, 38, 37, 37, 36, 36, 36, 36, 35, 35, 35, 35, 34, 34,33, 33, 33, 33, 32, 32, 32, 32, 31, 31, 31, 31, 30, 30, 30, 30, 29, 29, 29, 29, 28, 28, 28, 28, 27, 27 }; if (frame->F0hz10 > 0) { /* T0 is 4* the number of samples in one pitch period */ kt_globals.T0 = (40 * kt_globals.samrate) / frame->F0hz10; kt_globals.amp_voice = DBtoLIN(frame->AVdb_tmp); /* Duration of period before amplitude modulation */ kt_globals.nmod = kt_globals.T0; if (frame->AVdb_tmp > 0) { kt_globals.nmod >>= 1; } /* Breathiness of voicing waveform */ kt_globals.amp_breth = DBtoLIN(frame->Aturb) * 0.1; /* Set open phase of glottal period where 40 <= open phase <= 263 */ kt_globals.nopen = 4 * frame->Kopen; if ((kt_globals.glsource == IMPULSIVE) && (kt_globals.nopen > 263)) { kt_globals.nopen = 263; } if (kt_globals.nopen >= (kt_globals.T0-1)) { // printf("Warning: glottal open period cannot exceed T0, truncated\n"); kt_globals.nopen = kt_globals.T0 - 2; } if (kt_globals.nopen < 40) { /* F0 max = 1000 Hz */ // printf("Warning: minimum glottal open period is 10 samples.\n"); // printf("truncated, nopen = %d\n",kt_globals.nopen); kt_globals.nopen = 40; } /* Reset a & b, which determine shape of "natural" glottal waveform */ kt_globals.pulse_shape_b = B0[kt_globals.nopen-40]; kt_globals.pulse_shape_a = (kt_globals.pulse_shape_b * kt_globals.nopen) * 0.333; /* Reset width of "impulsive" glottal pulse */ temp = kt_globals.samrate / kt_globals.nopen; setabc((long)0,temp,&(kt_globals.rsn[RGL])); /* Make gain at F1 about constant */ temp1 = kt_globals.nopen *.00833; kt_globals.rsn[RGL].a *= temp1 * temp1; /* Truncate skewness so as not to exceed duration of closed phase of glottal period. */ temp = kt_globals.T0 - kt_globals.nopen; if (frame->Kskew > temp) { // printf("Kskew duration=%d > glottal closed period=%d, truncate\n", frame->Kskew, kt_globals.T0 - kt_globals.nopen); frame->Kskew = temp; } if (skew >= 0) { skew = frame->Kskew; } else { skew = - frame->Kskew; } /* Add skewness to closed portion of voicing period */ kt_globals.T0 = kt_globals.T0 + skew; skew = - skew; } else { kt_globals.T0 = 4; /* Default for f0 undefined */ kt_globals.amp_voice = 0.0; kt_globals.nmod = kt_globals.T0; kt_globals.amp_breth = 0.0; kt_globals.pulse_shape_a = 0.0; kt_globals.pulse_shape_b = 0.0; } /* Reset these pars pitch synchronously or at update rate if f0=0 */ if ((kt_globals.T0 != 4) || (kt_globals.ns == 0)) { /* Set one-pole low-pass filter that tilts glottal source */ kt_globals.decay = (0.033 * frame->TLTdb); if (kt_globals.decay > 0.0) { kt_globals.onemd = 1.0 - kt_globals.decay; } else { kt_globals.onemd = 1.0; } } } /* function SETABC Convert formant freqencies and bandwidth into resonator difference equation constants. */ static void setabc(long int f, long int bw, resonator_ptr rp) { double r; double arg; /* Let r = exp(-pi bw t) */ arg = kt_globals.minus_pi_t * bw; r = exp(arg); /* Let c = -r**2 */ rp->c = -(r * r); /* Let b = r * 2*cos(2 pi f t) */ arg = kt_globals.two_pi_t * f; rp->b = r * cos(arg) * 2.0; /* Let a = 1.0 - b - c */ rp->a = 1.0 - rp->b - rp->c; } /* function SETZEROABC Convert formant freqencies and bandwidth into anti-resonator difference equation constants. */ static void setzeroabc(long int f, long int bw, resonator_ptr rp) { double r; double arg; f = -f; //NOTE, changes made 30.09.2011 for Reece Dunn // fix a sound spike when f=0 /* First compute ordinary resonator coefficients */ /* Let r = exp(-pi bw t) */ arg = kt_globals.minus_pi_t * bw; r = exp(arg); /* Let c = -r**2 */ rp->c = -(r * r); /* Let b = r * 2*cos(2 pi f t) */ arg = kt_globals.two_pi_t * f; rp->b = r * cos(arg) * 2.; /* Let a = 1.0 - b - c */ rp->a = 1.0 - rp->b - rp->c; /* Now convert to antiresonator coefficients (a'=1/a, b'=b/a, c'=c/a) */ /* If f == 0 then rp->a gets set to 0 which makes a'=1/a set a', b' and c' to * INF, causing an audible sound spike when triggered (e.g. apiration with the * nasal register set to f=0, bw=0). */ if (rp->a != 0) { /* Now convert to antiresonator coefficients (a'=1/a, b'=b/a, c'=c/a) */ rp->a = 1.0 / rp->a; rp->c *= -rp->a; rp->b *= -rp->a; } } /* function GEN_NOISE Random number generator (return a number between -8191 and +8191) Noise spectrum is tilted down by soft low-pass filter having a pole near the origin in the z-plane, i.e. output = input + (0.75 * lastoutput) */ static double gen_noise(double noisedummy) // repaired ppgb 20111223 { long temp; static double nlast = 0.0; temp = (long) getrandom (-8191, 8191); kt_globals.nrand = (long) temp; double noise = kt_globals.nrand + (0.75 * nlast); nlast = noise; return(noise); } /* function DBTOLIN Convert from decibels to a linear scale factor Conversion table, db to linear, 87 dB --> 32767 86 dB --> 29491 (1 dB down = 0.5**1/6) ... 81 dB --> 16384 (6 dB down = 0.5) ... 0 dB --> 0 The just noticeable difference for a change in intensity of a vowel is approximately 1 dB. Thus all amplitudes are quantized to 1 dB steps. */ static double DBtoLIN(long dB) { static short amptable[88] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 6, 7, 8, 9, 10, 11, 13, 14, 16, 18, 20, 22, 25, 28, 32, 35, 40, 45, 51, 57, 64, 71, 80, 90, 101, 114, 128, 142, 159, 179, 202, 227, 256, 284, 318, 359, 405, 455, 512, 568, 638, 719, 881, 911, 1024, 1137, 1276, 1438, 1622, 1823, 2048, 2273, 2552, 2875, 3244, 3645, 4096, 4547, 5104, 5751, 6488, 7291, 8192, 9093, 10207, 11502, 12976, 14582, 16384, 18350, 20644, 23429, 26214, 29491, 32767 }; if ((dB < 0) || (dB > 87)) { return(0); } return((double)(amptable[dB]) * 0.001); } extern voice_t *wvoice; static klatt_peaks_t peaks[N_PEAKS]; static int end_wave; static int klattp[N_KLATTP]; static double klattp1[N_KLATTP]; static double klattp_inc[N_KLATTP]; static int scale_wav_tab[] = {45,38,45,45}; // scale output from different voicing sources int Wavegen_Klatt(int resume) {//========================== int pk; int x; int ix; int fade; if(resume==0) { sample_count = 0; } while(sample_count < nsamples) { kt_frame.F0hz10 = (wdata.pitch * 10) / 4096; // formants F6,F7,F8 are fixed values for cascade resonators, set in KlattInit() // but F6 is used for parallel resonator // F0 is used for the nasal zero for(ix=0; ix < 6; ix++) { kt_frame.Fhz[ix] = peaks[ix].freq; if(ix < 4) { kt_frame.Bhz[ix] = peaks[ix].bw; } } for(ix=1; ix < 7; ix++) { kt_frame.Ap[ix] = 0; } kt_frame.AVdb = klattp[KLATT_AV]; kt_frame.AVpdb = klattp[KLATT_AVp]; kt_frame.AF = klattp[KLATT_Fric]; kt_frame.AB = klattp[KLATT_FricBP]; kt_frame.ASP = klattp[KLATT_Aspr]; kt_frame.Aturb = klattp[KLATT_Turb]; kt_frame.Kskew = klattp[KLATT_Skew]; kt_frame.TLTdb = klattp[KLATT_Tilt]; kt_frame.Kopen = klattp[KLATT_Kopen]; // advance formants for(pk=0; pk>8) > 127) ix = 127; x = wdata.pitch_env[ix] * wdata.pitch_range; wdata.pitch = (x>>8) + wdata.pitch_base; kt_globals.nspfr = (nsamples - sample_count); if(kt_globals.nspfr > STEPSIZE) kt_globals.nspfr = STEPSIZE; frame_init(&kt_frame); /* get parameters for next frame of speech */ if(parwave(&kt_frame) == 1) { return(1); // output buffer is full } } if(end_wave > 0) { #ifdef deleted if(end_wave == 2) { fade = (kt_globals.T0 - kt_globals.nper)/4; // samples until end of current cycle if(fade < 64) fade = 64; } else #endif { fade = 64; // not followd by formant synthesis } // fade out to avoid a click kt_globals.fadeout = fade; end_wave = 0; sample_count -= fade; kt_globals.nspfr = fade; if(parwave(&kt_frame) == 1) { return(1); // output buffer is full } } return(0); } void SetSynth_Klatt(int length, int modn, frame_t *fr1, frame_t *fr2, voice_t *v, int control) {//=========================================================================================== int ix; DOUBLEX next; int qix; int cmd; frame_t *fr3; static frame_t prev_fr; if(wvoice != NULL) { if((wvoice->klattv[0] > 0) && (wvoice->klattv[0] <=3 )) { kt_globals.glsource = wvoice->klattv[0]; kt_globals.scale_wav = scale_wav_tab[kt_globals.glsource]; } kt_globals.f0_flutter = wvoice->flutter/32; } end_wave = 0; if(control & 2) { end_wave = 1; // fadeout at the end } if(control & 1) { end_wave = 1; for(qix=wcmdq_head+1;;qix++) { if(qix >= N_WCMDQ) qix = 0; if(qix == wcmdq_tail) break; cmd = wcmdq[qix][0]; if(cmd==WCMD_KLATT) { end_wave = 0; // next wave generation is from another spectrum fr3 = (frame_t *)wcmdq[qix][2]; for(ix=1; ix<6; ix++) { if(fr3->ffreq[ix] != fr2->ffreq[ix]) { // there is a discontinuity in formants end_wave = 2; break; } } break; } if((cmd==WCMD_WAVE) || (cmd==WCMD_PAUSE)) break; // next is not from spectrum, so continue until end of wave cycle } } #ifdef LOG_FRAMES if(option_log_frames) { FILE *f_log; f_log=fopen("log-espeakedit","a"); if(f_log != NULL) { fprintf(f_log,"K %3dmS %3d %3d %4d %4d %4d %4d (%2d) to %3d %3d %4d %4d %4d %4d (%2d)\n",length*1000/samplerate, fr1->klattp[KLATT_FNZ]*2,fr1->ffreq[1],fr1->ffreq[2],fr1->ffreq[3],fr1->ffreq[4],fr1->ffreq[5], fr1->klattp[KLATT_AV], fr2->klattp[KLATT_FNZ]*2,fr2->ffreq[1],fr2->ffreq[2],fr2->ffreq[3],fr1->ffreq[4],fr1->ffreq[5], fr2->klattp[KLATT_AV] ); fclose(f_log); } f_log=fopen("log-klatt","a"); if(f_log != NULL) { fprintf(f_log,"K %3dmS %3d %3d %4d %4d (%2d) to %3d %3d %4d %4d (%2d)\n",length*1000/samplerate, fr1->klattp[KLATT_FNZ]*2,fr1->ffreq[1],fr1->ffreq[2],fr1->ffreq[3], fr1->klattp[KLATT_AV], fr2->klattp[KLATT_FNZ]*2,fr2->ffreq[1],fr2->ffreq[2],fr2->ffreq[3], fr2->klattp[KLATT_AV] ); fclose(f_log); } } #endif if(control & 1) { for(ix=1; ix<6; ix++) { if(prev_fr.ffreq[ix] != fr1->ffreq[ix]) { // Discontinuity in formants. // end_wave was set in SetSynth_Klatt() to fade out the previous frame KlattReset(0); break; } } memcpy(&prev_fr,fr2,sizeof(prev_fr)); } for(ix=0; ix= 5) && ((fr1->frflags & FRFLAG_KLATT) == 0)) { klattp1[ix] = klattp[ix] = 0; klattp_inc[ix] = 0; } else { klattp1[ix] = klattp[ix] = fr1->klattp[ix]; klattp_inc[ix] = (double)((fr2->klattp[ix] - klattp[ix]) * STEPSIZE)/length; } // get klatt parameter adjustments for the voice // if((ix>0) && (ix < KLATT_AVp)) // klattp1[ix] = klattp[ix] = (klattp[ix] + wvoice->klattv[ix]); } nsamples = length; for(ix=1; ix < 6; ix++) { peaks[ix].freq1 = (fr1->ffreq[ix] * v->freq[ix] / 256.0) + v->freqadd[ix]; peaks[ix].freq = (int)peaks[ix].freq1; next = (fr2->ffreq[ix] * v->freq[ix] / 256.0) + v->freqadd[ix]; peaks[ix].freq_inc = ((next - peaks[ix].freq1) * STEPSIZE) / length; if(ix < 4) { // klatt bandwidth for f1, f2, f3 (others are fixed) peaks[ix].bw1 = fr1->bw[ix] * 2; peaks[ix].bw = (int)peaks[ix].bw1; next = fr2->bw[ix] * 2; peaks[ix].bw_inc = ((next - peaks[ix].bw1) * STEPSIZE) / length; } } // nasal zero frequency peaks[0].freq1 = fr1->klattp[KLATT_FNZ] * 2; if(peaks[0].freq1 == 0) peaks[0].freq1 = kt_frame.Fhz[F_NP]; // if no nasal zero, set it to same freq as nasal pole peaks[0].freq = (int)peaks[0].freq1; next = fr2->klattp[KLATT_FNZ] * 2; if(next == 0) next = kt_frame.Fhz[F_NP]; peaks[0].freq_inc = ((next - peaks[0].freq1) * STEPSIZE) / length; peaks[0].bw1 = 89; peaks[0].bw = 89; peaks[0].bw_inc = 0; if(fr1->frflags & FRFLAG_KLATT) { // the frame contains additional parameters for parallel resonators for(ix=1; ix < 7; ix++) { peaks[ix].bp1 = fr1->klatt_bp[ix] * 4; // parallel bandwidth peaks[ix].bp = (int)peaks[ix].bp1; next = fr2->klatt_bp[ix] * 2; peaks[ix].bp_inc = ((next - peaks[ix].bp1) * STEPSIZE) / length; peaks[ix].ap1 = fr1->klatt_ap[ix]; // parallal amplitude peaks[ix].ap = (int)peaks[ix].ap1; next = fr2->klatt_ap[ix] * 2; peaks[ix].ap_inc = ((next - peaks[ix].ap1) * STEPSIZE) / length; } } } // end of SetSynth_Klatt int Wavegen_Klatt2(int length, int modulation, int resume, frame_t *fr1, frame_t *fr2) {//=================================================================================== if(resume==0) SetSynth_Klatt(length, modulation, fr1, fr2, wvoice, 1); return(Wavegen_Klatt(resume)); } void KlattInit() { #define NUMBER_OF_SAMPLES 100 static short natural_samples[NUMBER_OF_SAMPLES]= { -310,-400,530,356,224,89,23,-10,-58,-16,461,599,536,701,770, 605,497,461,560,404,110,224,131,104,-97,155,278,-154,-1165, -598,737,125,-592,41,11,-247,-10,65,92,80,-304,71,167,-1,122, 233,161,-43,278,479,485,407,266,650,134,80,236,68,260,269,179, 53,140,275,293,296,104,257,152,311,182,263,245,125,314,140,44, 203,230,-235,-286,23,107,92,-91,38,464,443,176,98,-784,-2449, -1891,-1045,-1600,-1462,-1384,-1261,-949,-730 }; static short formant_hz[10] = {280,688,1064,2806,3260,3700,6500,7000,8000,280}; static short bandwidth[10] = {89,160,70,160,200,200,500,500,500,89}; static short parallel_amp[10] = { 0,59,59,59,59,59,59,0,0,0}; static short parallel_bw[10] = {59,59,89,149,200,200,500,0,0,0}; int ix; sample_count=0; kt_globals.synthesis_model = CASCADE_PARALLEL; kt_globals.samrate = 22050; kt_globals.glsource = IMPULSIVE; // IMPULSIVE, NATURAL, SAMPLED kt_globals.scale_wav = scale_wav_tab[kt_globals.glsource]; kt_globals.natural_samples = natural_samples; kt_globals.num_samples = NUMBER_OF_SAMPLES; kt_globals.sample_factor = 3.0; kt_globals.nspfr = (kt_globals.samrate * 10) / 1000; kt_globals.outsl = 0; kt_globals.f0_flutter = 20; KlattReset(2); // set default values for frame parameters for(ix=0; ix<=9; ix++) { kt_frame.Fhz[ix] = formant_hz[ix]; kt_frame.Bhz[ix] = bandwidth[ix]; kt_frame.Ap[ix] = parallel_amp[ix]; kt_frame.Bphz[ix] = parallel_bw[ix]; } kt_frame.Bhz_next[F_NZ] = bandwidth[F_NZ]; kt_frame.F0hz10 = 1000; kt_frame.AVdb = 59; // 59 kt_frame.ASP = 0; kt_frame.Kopen = 40; // 40 kt_frame.Aturb = 0; kt_frame.TLTdb = 0; kt_frame.AF =50; kt_frame.Kskew = 0; kt_frame.AB = 0; kt_frame.AVpdb = 0; kt_frame.Gain0 = 62; // 60 } // end of KlattInit #endif // INCLUDE_KLATT sources_5316/external/espeak/synthesize.cpp0000664000176700017670000012732011723710247017741 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2010 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" extern FILE *f_log; static void SmoothSpect(void); // list of phonemes in a clause int n_phoneme_list=0; PHONEME_LIST phoneme_list[N_PHONEME_LIST]; int mbrola_delay; char mbrola_name[20]; SPEED_FACTORS speed; static int last_pitch_cmd; static int last_amp_cmd; static frame_t *last_frame; static int last_wcmdq; static int pitch_length; static int amp_length; static int modn_flags; static int fmt_amplitude=0; static int syllable_start; static int syllable_end; static int syllable_centre; static voice_t *new_voice=NULL; int n_soundicon_tab=N_SOUNDICON_SLOTS; SOUND_ICON soundicon_tab[N_SOUNDICON_TAB]; #define RMS_GLOTTAL1 35 // vowel before glottal stop #define RMS_START 28 // 28 #define VOWEL_FRONT_LENGTH 50 // a dummy phoneme_list entry which looks like a pause static PHONEME_LIST next_pause; const char *WordToString(unsigned int word) {//======================================== // Convert a phoneme mnemonic word into a string int ix; static char buf[5]; for(ix=0; ix<3; ix++) buf[ix] = word >> (ix*8); buf[4] = 0; return(buf); } void SynthesizeInit() {//================== last_pitch_cmd = 0; last_amp_cmd = 0; last_frame = NULL; syllable_centre = -1; // initialise next_pause, a dummy phoneme_list entry // next_pause.ph = phoneme_tab[phonPAUSE]; // this must be done after voice selection next_pause.type = phPAUSE; next_pause.newword = 0; } static void EndAmplitude(void) {//=========================== if(amp_length > 0) { if(wcmdq[last_amp_cmd][1] == 0) wcmdq[last_amp_cmd][1] = amp_length; amp_length = 0; } } static void EndPitch(int voice_break) {//================================== // posssible end of pitch envelope, fill in the length if((pitch_length > 0) && (last_pitch_cmd >= 0)) { if(wcmdq[last_pitch_cmd][1] == 0) wcmdq[last_pitch_cmd][1] = pitch_length; pitch_length = 0; } if(voice_break) { last_wcmdq = -1; last_frame = NULL; syllable_end = wcmdq_tail; SmoothSpect(); syllable_centre = -1; memset(vowel_transition,0,sizeof(vowel_transition)); } } // end of EndPitch static void DoAmplitude(int amp, unsigned char *amp_env) {//===================================================== long64 *q; last_amp_cmd = wcmdq_tail; amp_length = 0; // total length of vowel with this amplitude envelope q = wcmdq[wcmdq_tail]; q[0] = WCMD_AMPLITUDE; q[1] = 0; // fill in later from amp_length q[2] = (long64)amp_env; q[3] = amp; WcmdqInc(); } // end of DoAmplitude static void DoPitch(unsigned char *env, int pitch1, int pitch2) {//============================================================ long64 *q; EndPitch(0); if(pitch1 == 255) { // pitch was not set pitch1 = 55; pitch2 = 76; env = envelope_data[PITCHfall]; } last_pitch_cmd = wcmdq_tail; pitch_length = 0; // total length of spect with this pitch envelope if(pitch2 < 0) pitch2 = 0; q = wcmdq[wcmdq_tail]; q[0] = WCMD_PITCH; q[1] = 0; // length, fill in later from pitch_length q[2] = (long64)env; q[3] = (pitch1 << 16) + pitch2; WcmdqInc(); } // end of DoPitch int PauseLength(int pause, int control) {//==================================== int len; if(control == 0) { if(pause >= 200) len = (pause * speed.clause_pause_factor)/256; else len = (pause * speed.pause_factor)/256; } else len = (pause * speed.wav_factor)/256; if(len < speed.min_pause) { len = speed.min_pause; // mS, limit the amount to which pauses can be shortened } return(len); } static void DoPause(int length, int control) {//========================================= // control = 1, less shortening at fast speeds int len; if(length == 0) len = 0; else { len = PauseLength(length, control); len = (len * samplerate) / 1000; // convert from mS to number of samples } EndPitch(1); wcmdq[wcmdq_tail][0] = WCMD_PAUSE; wcmdq[wcmdq_tail][1] = len; WcmdqInc(); last_frame = NULL; if(fmt_amplitude != 0) { wcmdq[wcmdq_tail][0] = WCMD_FMT_AMPLITUDE; wcmdq[wcmdq_tail][1] = fmt_amplitude = 0; WcmdqInc(); } } // end of DoPause extern int seq_len_adjust; // temporary fix to advance the start point for playing the wav sample static int DoSample2(int index, int which, int std_length, int control, int length_mod, int amp) {//============================================================================================= int length; int wav_length; int wav_scale; int min_length; int x; int len4; long64 *q; unsigned char *p; index = index & 0x7fffff; p = &wavefile_data[index]; wav_scale = p[2]; wav_length = (p[1] * 256); wav_length += p[0]; // length in bytes if(wav_length == 0) return(0); min_length = speed.min_sample_len; if(wav_scale==0) min_length *= 2; // 16 bit samples else { // increase consonant amplitude at high speeds, depending on the peak consonant amplitude // x = ((35 - wav_scale) * speed.loud_consonants); // if(x < 0) x = 0; // wav_scale = (wav_scale * (x+256))/256; } if(std_length > 0) { std_length = (std_length * samplerate)/1000; if(wav_scale == 0) std_length *= 2; x = (min_length * std_length)/wav_length; if(x > min_length) min_length = x; } else { // no length specified, use the length of the stored sound std_length = wav_length; } if(length_mod > 0) { std_length = (std_length * length_mod)/256; } length = (std_length * speed.wav_factor)/256; if(control & pd_DONTLENGTHEN) { // this option is used for Stops, with short noise bursts. // Don't change their length much. if(length > std_length) { // don't let length exceed std_length length = std_length; } else { // reduce the reduction in length // length = (length + std_length)/2; } } if(length < min_length) length = min_length; if(wav_scale == 0) { // 16 bit samples length /= 2; wav_length /= 2; } if(amp < 0) return(length); len4 = wav_length / 4; index += 4; if(which & 0x100) { // mix this with synthesised wave last_wcmdq = wcmdq_tail; q = wcmdq[wcmdq_tail]; q[0] = WCMD_WAVE2; q[1] = length | (wav_length << 16); // length in samples q[2] = long64(&wavefile_data[index]); q[3] = wav_scale + (amp << 8); WcmdqInc(); return(length); } if(length > wav_length) { x = len4*3; length -= x; } else { x = length; length = 0; } last_wcmdq = wcmdq_tail; q = wcmdq[wcmdq_tail]; q[0] = WCMD_WAVE; q[1] = x; // length in samples q[2] = long64(&wavefile_data[index]); q[3] = wav_scale + (amp << 8); WcmdqInc(); while(length > len4*3) { x = len4; if(wav_scale == 0) x *= 2; last_wcmdq = wcmdq_tail; q = wcmdq[wcmdq_tail]; q[0] = WCMD_WAVE; q[1] = len4*2; // length in samples q[2] = long64(&wavefile_data[index+x]); q[3] = wav_scale + (amp << 8); WcmdqInc(); length -= len4*2; } if(length > 0) { x = wav_length - length; if(wav_scale == 0) x *= 2; last_wcmdq = wcmdq_tail; q = wcmdq[wcmdq_tail]; q[0] = WCMD_WAVE; q[1] = length; // length in samples q[2] = long64(&wavefile_data[index+x]); q[3] = wav_scale + (amp << 8); WcmdqInc(); } return(length); } // end of DoSample2 int DoSample3(PHONEME_DATA *phdata, int length_mod, int amp) {//========================================================= int amp2; int len; EndPitch(1); if(amp == -1) { // just get the length, don't produce sound amp2 = amp; } else { amp2 = phdata->sound_param[pd_WAV]; if(amp2 == 0) amp2 = 100; amp2 = (amp2 * 32)/100; } seq_len_adjust=0; if(phdata->sound_addr[pd_WAV] == 0) { len = 0; } else { len = DoSample2(phdata->sound_addr[pd_WAV], 2, phdata->pd_param[pd_LENGTHMOD]*2, phdata->pd_control, length_mod, amp2); } last_frame = NULL; return(len); } // end of DoSample3 static frame_t *AllocFrame() {//========================= // Allocate a temporary spectrum frame for the wavegen queue. Use a pool which is big // enough to use a round-robin without checks. // Only needed for modifying spectra for blending to consonants #define N_FRAME_POOL N_WCMDQ static int ix=0; static frame_t frame_pool[N_FRAME_POOL]; ix++; if(ix >= N_FRAME_POOL) ix = 0; return(&frame_pool[ix]); } static void set_frame_rms(frame_t *fr, int new_rms) {//================================================= // Each frame includes its RMS amplitude value, so to set a new // RMS just adjust the formant amplitudes by the appropriate ratio int x; int h; int ix; static const short sqrt_tab[200] = { 0, 64, 90,110,128,143,156,169,181,192,202,212,221,230,239,247, 256,263,271,278,286,293,300,306,313,320,326,332,338,344,350,356, 362,367,373,378,384,389,394,399,404,409,414,419,424,429,434,438, 443,448,452,457,461,465,470,474,478,483,487,491,495,499,503,507, 512,515,519,523,527,531,535,539,543,546,550,554,557,561,565,568, 572,576,579,583,586,590,593,596,600,603,607,610,613,617,620,623, 627,630,633,636,640,643,646,649,652,655,658,662,665,668,671,674, 677,680,683,686,689,692,695,698,701,704,706,709,712,715,718,721, 724,726,729,732,735,738,740,743,746,749,751,754,757,759,762,765, 768,770,773,775,778,781,783,786,789,791,794,796,799,801,804,807, 809,812,814,817,819,822,824,827,829,832,834,836,839,841,844,846, 849,851,853,856,858,861,863,865,868,870,872,875,877,879,882,884, 886,889,891,893,896,898,900,902}; if(voice->klattv[0]) { if(new_rms == -1) { fr->klattp[KLATT_AV] = 50; } return; } if(fr->rms == 0) return; // check for divide by zero x = (new_rms * 64)/fr->rms; if(x >= 200) x = 199; x = sqrt_tab[x]; // sqrt(new_rms/fr->rms)*0x200; for(ix=0; ix < 8; ix++) { h = fr->fheight[ix] * x; fr->fheight[ix] = h/0x200; } } /* end of set_frame_rms */ static void formants_reduce_hf(frame_t *fr, int level) {//==================================================== // change height of peaks 2 to 8, percentage int ix; int x; if(voice->klattv[0]) return; for(ix=2; ix < 8; ix++) { x = fr->fheight[ix] * level; fr->fheight[ix] = x/100; } } static frame_t *CopyFrame(frame_t *frame1, int copy) {//================================================= // create a copy of the specified frame in temporary buffer frame_t *frame2; if((copy==0) && (frame1->frflags & FRFLAG_COPIED)) { // this frame has already been copied in temporary rw memory return(frame1); } frame2 = AllocFrame(); if(frame2 != NULL) { memcpy(frame2,frame1,sizeof(frame_t)); frame2->length = 0; frame2->frflags |= FRFLAG_COPIED; } return(frame2); } static frame_t *DuplicateLastFrame(frameref_t *seq, int n_frames, int length) {//========================================================================== frame_t *fr; seq[n_frames-1].length = length; fr = CopyFrame(seq[n_frames-1].frame,1); seq[n_frames].frame = fr; seq[n_frames].length = 0; return fr; } static void AdjustFormants(frame_t *fr, int target, int min, int max, int f1_adj, int f3_adj, int hf_reduce, int flags) {//==================================================================================================================== int x; //hf_reduce = 70; // ?? using fixed amount rather than the parameter?? target = (target * voice->formant_factor)/256; x = (target - fr->ffreq[2]) / 2; if(x > max) x = max; if(x < min) x = min; fr->ffreq[2] += x; fr->ffreq[3] += f3_adj; if(flags & 0x20) { f3_adj = -f3_adj; //. reverse direction for f4,f5 change } fr->ffreq[4] += f3_adj; fr->ffreq[5] += f3_adj; if(f1_adj==1) { x = (235 - fr->ffreq[1]); if(x < -100) x = -100; if(x > -60) x = -60; fr->ffreq[1] += x; } if(f1_adj==2) { x = (235 - fr->ffreq[1]); if(x < -300) x = -300; if(x > -150) x = -150; fr->ffreq[1] += x; fr->ffreq[0] += x; } if(f1_adj==3) { x = (100 - fr->ffreq[1]); if(x < -400) x = -400; if(x > -300) x = -400; fr->ffreq[1] += x; fr->ffreq[0] += x; } formants_reduce_hf(fr,hf_reduce); } static int VowelCloseness(frame_t *fr) {//=================================== // return a value 0-3 depending on the vowel's f1 int f1; if((f1 = fr->ffreq[1]) < 300) return(3); if(f1 < 400) return(2); if(f1 < 500) return(1); return(0); } int FormantTransition2(frameref_t *seq, int &n_frames, unsigned int data1, unsigned int data2, PHONEME_TAB *other_ph, int which) {//============================================================================================================================== int ix; int formant; int next_rms; int len; int rms; int f1; int f2; int f2_min; int f2_max; int f3_adj; int f3_amp; int flags; int vcolour; #define N_VCOLOUR 2 // percentage change for each formant in 256ths static short vcolouring[N_VCOLOUR][5] = { {243,272,256,256,256}, // palatal consonant follows {256,256,240,240,240}, // retroflex }; frame_t *fr = NULL; if(n_frames < 2) return(0); len = (data1 & 0x3f) * 2; rms = (data1 >> 6) & 0x3f; flags = (data1 >> 12); f2 = (data2 & 0x3f) * 50; f2_min = (((data2 >> 6) & 0x1f) - 15) * 50; f2_max = (((data2 >> 11) & 0x1f) - 15) * 50; f3_adj = (((data2 >> 16) & 0x1f) - 15) * 50; f3_amp = ((data2 >> 21) & 0x1f) * 8; f1 = ((data2 >> 26) & 0x7); vcolour = (data2 >> 29); // fprintf(stderr,"FMT%d %3s %3d-%3d f1=%d f2=%4d %4d %4d f3=%4d %3d\n", // which,WordToString(other_ph->mnemonic),len,rms,f1,f2,f2_min,f2_max,f3_adj,f3_amp); if((other_ph != NULL) && (other_ph->mnemonic == '?')) flags |= 8; if(which == 1) { /* entry to vowel */ fr = CopyFrame(seq[0].frame,0); seq[0].frame = fr; seq[0].length = VOWEL_FRONT_LENGTH; if(len > 0) seq[0].length = len; seq[0].frflags |= FRFLAG_LEN_MOD2; // reduce length modification fr->frflags |= FRFLAG_LEN_MOD2; next_rms = seq[1].frame->rms; if(voice->klattv[0]) { // fr->klattp[KLATT_AV] = 53; // reduce the amplituide of the start of a vowel fr->klattp[KLATT_AV] = seq[1].frame->klattp[KLATT_AV] - 4; } if(f2 != 0) { if(rms & 0x20) { set_frame_rms(fr,(next_rms * (rms & 0x1f))/30); } AdjustFormants(fr, f2, f2_min, f2_max, f1, f3_adj, f3_amp, flags); if((rms & 0x20) == 0) { set_frame_rms(fr,rms*2); } } else { if(flags & 8) set_frame_rms(fr,(next_rms*24)/32); else set_frame_rms(fr,RMS_START); } if(flags & 8) { // set_frame_rms(fr,next_rms - 5); modn_flags = 0x800 + (VowelCloseness(fr) << 8); } } else { // exit from vowel rms = rms*2; if((f2 != 0) || (flags != 0)) { if(flags & 8) { fr = CopyFrame(seq[n_frames-1].frame,0); seq[n_frames-1].frame = fr; rms = RMS_GLOTTAL1; // degree of glottal-stop effect depends on closeness of vowel (indicated by f1 freq) modn_flags = 0x400 + (VowelCloseness(fr) << 8); } else { fr = DuplicateLastFrame(seq,n_frames++,len); if(len > 36) seq_len_adjust += (len - 36); if(f2 != 0) { AdjustFormants(fr, f2, f2_min, f2_max, f1, f3_adj, f3_amp, flags); } } set_frame_rms(fr,rms); if((vcolour > 0) && (vcolour <= N_VCOLOUR)) { for(ix=0; ixffreq[formant] * vcolouring[vcolour-1][formant-1]; fr->ffreq[formant] = x / 256; } } } } } if(fr != NULL) { if(flags & 4) fr->frflags |= FRFLAG_FORMANT_RATE; if(flags & 2) fr->frflags |= FRFLAG_BREAK; // don't merge with next frame } if(flags & 0x40) DoPause(20,0); // add a short pause after the consonant if(flags & 16) return(len); return(0); } // end of FormantTransition2 static void SmoothSpect(void) {//========================== // Limit the rate of frequence change of formants, to reduce chirping long64 *q; frame_t *frame; frame_t *frame2; frame_t *frame1; frame_t *frame_centre; int ix; int len; int pk; int modified; int allowed; int diff; if(syllable_start == syllable_end) return; if((syllable_centre < 0) || (syllable_centre == syllable_start)) { syllable_start = syllable_end; return; } q = wcmdq[syllable_centre]; frame_centre = (frame_t *)q[2]; // backwards ix = syllable_centre -1; frame = frame2 = frame_centre; for(;;) { if(ix < 0) ix = N_WCMDQ-1; q = wcmdq[ix]; if(q[0] == WCMD_PAUSE || q[0] == WCMD_WAVE) break; if(q[0] <= WCMD_SPECT2) { len = q[1] & 0xffff; frame1 = (frame_t *)q[3]; if(frame1 == frame) { q[3] = (long64)frame2; frame1 = frame2; } else break; // doesn't follow on from previous frame frame = frame2 = (frame_t *)q[2]; modified = 0; if(frame->frflags & FRFLAG_BREAK) break; if(frame->frflags & FRFLAG_FORMANT_RATE) len = (len * 12)/10; // allow slightly greater rate of change for this frame (was 12/10) for(pk=0; pk<6; pk++) { int f1, f2; if((frame->frflags & FRFLAG_BREAK_LF) && (pk < 3)) continue; f1 = frame1->ffreq[pk]; f2 = frame->ffreq[pk]; // backwards if((diff = f2 - f1) > 0) { allowed = f1*2 + f2; } else { allowed = f1 + f2*2; } // the allowed change is specified as percentage (%*10) of the frequency // take "frequency" as 1/3 from the lower freq allowed = (allowed * formant_rate[pk])/3000; allowed = (allowed * len)/256; if(diff > allowed) { if(modified == 0) { frame2 = CopyFrame(frame,0); modified = 1; } frame2->ffreq[pk] = frame1->ffreq[pk] + allowed; q[2] = (long64)frame2; } else if(diff < -allowed) { if(modified == 0) { frame2 = CopyFrame(frame,0); modified = 1; } frame2->ffreq[pk] = frame1->ffreq[pk] - allowed; q[2] = (long64)frame2; } } } if(ix == syllable_start) break; ix--; } // forwards ix = syllable_centre; frame = NULL; for(;;) { q = wcmdq[ix]; if(q[0] == WCMD_PAUSE || q[0] == WCMD_WAVE) break; if(q[0] <= WCMD_SPECT2) { len = q[1] & 0xffff; frame1 = (frame_t *)q[2]; if(frame != NULL) { if(frame1 == frame) { q[2] = (long64)frame2; frame1 = frame2; } else break; // doesn't follow on from previous frame } frame = frame2 = (frame_t *)q[3]; modified = 0; if(frame1->frflags & FRFLAG_BREAK) break; if(frame1->frflags & FRFLAG_FORMANT_RATE) len = (len *6)/5; // allow slightly greater rate of change for this frame for(pk=0; pk<6; pk++) { int f1, f2; f1 = frame1->ffreq[pk]; f2 = frame->ffreq[pk]; // forwards if((diff = f2 - f1) > 0) { allowed = f1*2 + f2; } else { allowed = f1 + f2*2; } allowed = (allowed * formant_rate[pk])/3000; allowed = (allowed * len)/256; if(diff > allowed) { if(modified == 0) { frame2 = CopyFrame(frame,0); modified = 1; } frame2->ffreq[pk] = frame1->ffreq[pk] + allowed; q[3] = (long64)frame2; } else if(diff < -allowed) { if(modified == 0) { frame2 = CopyFrame(frame,0); modified = 1; } frame2->ffreq[pk] = frame1->ffreq[pk] - allowed; q[3] = (long64)frame2; } } } ix++; if(ix >= N_WCMDQ) ix = 0; if(ix == syllable_end) break; } syllable_start = syllable_end; } // end of SmoothSpect static void StartSyllable(void) {//============================ // start of syllable, if not already started if(syllable_end == syllable_start) syllable_end = wcmdq_tail; } int DoSpect2(PHONEME_TAB *this_ph, int which, FMT_PARAMS *fmt_params, PHONEME_LIST *plist, int modulation) {//======================================================================================================== // which: 0 not a vowel, 1 start of vowel, 2 body and end of vowel // length_mod: 256 = 100% // modulation: -1 = don't write to wcmdq int n_frames; frameref_t *frames; int frameix; frame_t *frame1; frame_t *frame2; frame_t *fr; int ix; long64 *q; int len; int frame_length; int length_factor; int length_mod; int length_sum; int length_min; int total_len = 0; static int wave_flag = 0; int wcmd_spect = WCMD_SPECT; int frame_lengths[N_SEQ_FRAMES]; if(fmt_params->fmt_addr == 0) return(0); length_mod = plist->length; if(length_mod==0) length_mod=256; length_min = (samplerate/70); // greater than one cycle at low pitch (Hz) if(which==2) { if((translator->langopts.param[LOPT_LONG_VOWEL_THRESHOLD] > 0) && ((this_ph->std_length >= translator->langopts.param[LOPT_LONG_VOWEL_THRESHOLD]) || (plist->synthflags & SFLAG_LENGTHEN) || (this_ph->phflags & phLONG))) length_min *= 2; // ensure long vowels are longer } if(which==1) { // limit the shortening of sonorants before shortened (eg. unstressed vowels) if((this_ph->type==phLIQUID) || (plist[-1].type==phLIQUID) || (plist[-1].type==phNASAL)) { if(length_mod < (len = translator->langopts.param[LOPT_SONORANT_MIN])) { length_mod = len; } } } modn_flags = 0; frames = LookupSpect(this_ph, which, fmt_params, &n_frames, plist); if(frames == NULL) return(0); // not found if(fmt_params->fmt_amp != fmt_amplitude) { // an amplitude adjustment is specified for this sequence q = wcmdq[wcmdq_tail]; q[0] = WCMD_FMT_AMPLITUDE; q[1] = fmt_amplitude = fmt_params->fmt_amp; WcmdqInc(); } frame1 = frames[0].frame; if(voice->klattv[0]) wcmd_spect = WCMD_KLATT; wavefile_ix = fmt_params->wav_addr; if(fmt_params->wav_amp == 0) wavefile_amp = 32; else wavefile_amp = (fmt_params->wav_amp * 32)/100; if(wavefile_ix == 0) { if(wave_flag) { // cancel any wavefile that was playing previously wcmd_spect = WCMD_SPECT2; if(voice->klattv[0]) wcmd_spect = WCMD_KLATT2; wave_flag = 0; } else { wcmd_spect = WCMD_SPECT; if(voice->klattv[0]) wcmd_spect = WCMD_KLATT; } } if(last_frame != NULL) { if(((last_frame->length < 2) || (last_frame->frflags & FRFLAG_VOWEL_CENTRE)) && !(last_frame->frflags & FRFLAG_BREAK)) { // last frame of previous sequence was zero-length, replace with first of this sequence wcmdq[last_wcmdq][3] = (long64)frame1; if(last_frame->frflags & FRFLAG_BREAK_LF) { // but flag indicates keep HF peaks in last segment fr = CopyFrame(frame1,1); for(ix=3; ix < 8; ix++) { if(ix < 7) fr->ffreq[ix] = last_frame->ffreq[ix]; fr->fheight[ix] = last_frame->fheight[ix]; } wcmdq[last_wcmdq][3] = (long64)fr; } } } if((this_ph->type == phVOWEL) && (which == 2)) { SmoothSpect(); // process previous syllable // remember the point in the output queue of the centre of the vowel syllable_centre = wcmdq_tail; } length_sum = 0; for(frameix=1; frameix < n_frames; frameix++) { length_factor = length_mod; if(frames[frameix-1].frflags & FRFLAG_LEN_MOD) // reduce effect of length mod { length_factor = (length_mod*(256-speed.lenmod_factor) + 256*speed.lenmod_factor)/256; } else if(frames[frameix-1].frflags & FRFLAG_LEN_MOD2) // reduce effect of length mod, used for the start of a vowel { length_factor = (length_mod*(256-speed.lenmod2_factor) + 256*speed.lenmod2_factor)/256; } frame_length = frames[frameix-1].length; len = (frame_length * samplerate)/1000; len = (len * length_factor)/256; length_sum += len; frame_lengths[frameix] = len; } if((length_sum > 0) && (length_sum < length_min)) { // lengthen, so that the sequence is greater than one cycle at low pitch for(frameix=1; frameix < n_frames; frameix++) { frame_lengths[frameix] = (frame_lengths[frameix] * length_min) / length_sum; } } for(frameix=1; frameixwav_addr != 0) && ((frame1->frflags & FRFLAG_DEFER_WAV)==0)) { // there is a wave file to play along with this synthesis seq_len_adjust = 0; DoSample2(fmt_params->wav_addr, which+0x100, 0, fmt_params->fmt_control, 0, wavefile_amp); wave_flag = 1; wavefile_ix = 0; fmt_params->wav_addr = 0; } if(modulation >= 0) { if(frame1->frflags & FRFLAG_MODULATE) { modulation = 6; } if((frameix == n_frames-1) && (modn_flags & 0xf00)) modulation |= modn_flags; // before or after a glottal stop } len = frame_lengths[frameix]; pitch_length += len; amp_length += len; if(len == 0) { last_frame = NULL; frame1 = frame2; } else { last_wcmdq = wcmdq_tail; if(modulation >= 0) { q = wcmdq[wcmdq_tail]; q[0] = wcmd_spect; q[1] = len + (modulation << 16); q[2] = (long64)frame1; q[3] = (long64)frame2; WcmdqInc(); } last_frame = frame1 = frame2; total_len += len; } } if((which != 1) && (fmt_amplitude != 0)) { q = wcmdq[wcmdq_tail]; q[0] = WCMD_FMT_AMPLITUDE; q[1] = fmt_amplitude = 0; WcmdqInc(); } return(total_len); } // end of DoSpect void DoMarker(int type, int char_posn, int length, int value) {//========================================================== // This could be used to return an index to the word currently being spoken // Type 1=word, 2=sentence, 3=named marker, 4=play audio, 5=end if(WcmdqFree() > 5) { wcmdq[wcmdq_tail][0] = WCMD_MARKER + (type << 8); wcmdq[wcmdq_tail][1] = (char_posn & 0xffffff) | (length << 24); wcmdq[wcmdq_tail][2] = value; WcmdqInc(); } } // end of DoMarker void DoPhonemeMarker(int type, int char_posn, int length, char *name) {//================================================================== // This could be used to return an index to the word currently being spoken // Type 7=phoneme int *p; if(WcmdqFree() > 5) { wcmdq[wcmdq_tail][0] = WCMD_MARKER + (type << 8); wcmdq[wcmdq_tail][1] = (char_posn & 0xffffff) | (length << 24); p = (int *)name; wcmdq[wcmdq_tail][2] = p[0]; // up to 8 bytes of UTF8 characters wcmdq[wcmdq_tail][3] = p[1]; WcmdqInc(); } } // end of DoMarker void DoSonicSpeed(int value) {//========================= // value, multiplier * 1024 wcmdq[wcmdq_tail][0] = WCMD_SONIC_SPEED; wcmdq[wcmdq_tail][1] = value; WcmdqInc(); } // end of DoSonicSpeed void DoVoiceChange(voice_t *v) {//=========================== // allocate memory for a copy of the voice data, and free it in wavegenfill() voice_t *v2; v2 = (voice_t *)malloc(sizeof(voice_t)); memcpy(v2,v,sizeof(voice_t)); wcmdq[wcmdq_tail][0] = WCMD_VOICE; wcmdq[wcmdq_tail][2] = (long64)v2; WcmdqInc(); } void DoEmbedded(int *embix, int sourceix) {//====================================== // There were embedded commands in the text at this point unsigned int word; // bit 7=last command for this word, bits 5,6 sign, bits 0-4 command unsigned int value; int command; do { word = embedded_list[*embix]; value = word >> 8; command = word & 0x7f; if(command == 0) return; // error (*embix)++; switch(command & 0x1f) { case EMBED_S: // speed SetEmbedded((command & 0x60) + EMBED_S2,value); // adjusts embedded_value[EMBED_S2] SetSpeed(2); break; case EMBED_I: // play dynamically loaded wav data (sound icon) if((int)value < n_soundicon_tab) { if(soundicon_tab[value].length != 0) { DoPause(10,0); // ensure a break in the speech wcmdq[wcmdq_tail][0] = WCMD_WAVE; wcmdq[wcmdq_tail][1] = soundicon_tab[value].length; wcmdq[wcmdq_tail][2] = (long64)soundicon_tab[value].data + 44; // skip WAV header wcmdq[wcmdq_tail][3] = 0x1500; // 16 bit data, amp=21 WcmdqInc(); } } break; case EMBED_M: // named marker DoMarker(espeakEVENT_MARK, (sourceix & 0x7ff) + clause_start_char, 0, value); break; case EMBED_U: // play sound DoMarker(espeakEVENT_PLAY, count_characters+1, 0, value); // always occurs at end of clause break; default: DoPause(10,0); // ensure a break in the speech wcmdq[wcmdq_tail][0] = WCMD_EMBEDDED; wcmdq[wcmdq_tail][1] = command; wcmdq[wcmdq_tail][2] = value; WcmdqInc(); break; } } while ((word & 0x80) == 0); } int Generate(PHONEME_LIST *phoneme_list, int *n_ph, int resume) {//============================================================ static int ix; static int embedded_ix; static int word_count; PHONEME_LIST *prev; PHONEME_LIST *next; PHONEME_LIST *next2; PHONEME_LIST *p; int released; int stress; int modulation; int pre_voiced; int free_min; unsigned char *pitch_env=NULL; unsigned char *amp_env; PHONEME_TAB *ph; int use_ipa=0; int done_phoneme_marker; char phoneme_name[16]; static int sourceix=0; PHONEME_DATA phdata; PHONEME_DATA phdata_prev; PHONEME_DATA phdata_next; PHONEME_DATA phdata_tone; FMT_PARAMS fmtp; if(option_quiet) return(0); if(option_phoneme_events & espeakINITIALIZE_PHONEME_IPA) use_ipa = 1; if(mbrola_name[0] != 0) return(MbrolaGenerate(phoneme_list,n_ph,resume)); if(resume == 0) { ix = 1; embedded_ix=0; word_count = 0; pitch_length = 0; amp_length = 0; last_frame = NULL; last_wcmdq = -1; syllable_start = wcmdq_tail; syllable_end = wcmdq_tail; syllable_centre = -1; last_pitch_cmd = -1; memset(vowel_transition,0,sizeof(vowel_transition)); DoPause(0,0); // isolate from the previous clause } while(ix < (*n_ph)) { p = &phoneme_list[ix]; if(p->type == phPAUSE) free_min = 10; else if(p->type != phVOWEL) free_min = 15; // we need less Q space for non-vowels, and we need to generate phonemes after a vowel so that the pitch_length is filled in else free_min = MIN_WCMDQ; // 25 if(WcmdqFree() <= free_min) return(1); // wait prev = &phoneme_list[ix-1]; next = &phoneme_list[ix+1]; next2 = &phoneme_list[ix+2]; if(p->synthflags & SFLAG_EMBEDDED) { DoEmbedded(&embedded_ix, p->sourceix); } if(p->newword) { if(((p->type == phVOWEL) && (translator->langopts.param[LOPT_WORD_MERGE] & 1)) || (p->ph->phflags & phNOPAUSE)) { } else { last_frame = NULL; } sourceix = (p->sourceix & 0x7ff) + clause_start_char; if(p->newword & 4) DoMarker(espeakEVENT_SENTENCE, sourceix, 0, count_sentences); // start of sentence // if(p->newword & 2) // DoMarker(espeakEVENT_END, count_characters, 0, count_sentences); // end of clause if(p->newword & 1) DoMarker(espeakEVENT_WORD, sourceix, p->sourceix >> 11, clause_start_word + word_count++); // NOTE, this count doesn't include multiple-word pronunciations in *_list. eg (of a) } EndAmplitude(); if(p->prepause > 0) DoPause(p->prepause,1); done_phoneme_marker = 0; if(option_phoneme_events && (p->ph->code != phonEND_WORD)) { if((p->type == phVOWEL) && (prev->type==phLIQUID || prev->type==phNASAL)) { // For vowels following a liquid or nasal, do the phoneme event after the vowel-start } else { WritePhMnemonic(phoneme_name, p->ph, p, use_ipa); DoPhonemeMarker(espeakEVENT_PHONEME, sourceix, 0, phoneme_name); done_phoneme_marker = 1; } } switch(p->type) { case phPAUSE: DoPause(p->length,0); break; case phSTOP: released = 0; if(next->type==phVOWEL) { released = 1; } else if(!next->newword) { if(next->type==phLIQUID) released = 1; // if(((p->ph->phflags & phPLACE) == phPLACE_blb) && (next->ph->phflags & phSIBILANT)) released = 1; } if(released == 0) p->synthflags |= SFLAG_NEXT_PAUSE; InterpretPhoneme(NULL, 0, p, &phdata); phdata.pd_control |= pd_DONTLENGTHEN; DoSample3(&phdata, 0, 0); break; case phFRICATIVE: InterpretPhoneme(NULL, 0, p, &phdata); if(p->synthflags & SFLAG_LENGTHEN) { DoSample3(&phdata, p->length, 0); // play it twice for [s:] etc. } DoSample3(&phdata, p->length, 0); break; case phVSTOP: ph = p->ph; memset(&fmtp, 0, sizeof(fmtp)); fmtp.fmt_control = pd_DONTLENGTHEN; pre_voiced = 0; if(next->type==phVOWEL) { DoAmplitude(p->amp,NULL); DoPitch(envelope_data[p->env],p->pitch1,p->pitch2); pre_voiced = 1; } else if((next->type==phLIQUID) && !next->newword) { DoAmplitude(next->amp,NULL); DoPitch(envelope_data[next->env],next->pitch1,next->pitch2); pre_voiced = 1; } else { if(last_pitch_cmd < 0) { DoAmplitude(next->amp,NULL); DoPitch(envelope_data[p->env],p->pitch1,p->pitch2); } } if((prev->type==phVOWEL) || (prev->ph->phflags & phVOWEL2) || (ph->phflags & phPREVOICE)) { // a period of voicing before the release InterpretPhoneme(NULL, 0x01, p, &phdata); fmtp.fmt_addr = phdata.sound_addr[pd_FMT]; fmtp.fmt_amp = phdata.sound_param[pd_FMT]; DoSpect2(ph, 0, &fmtp, p, 0); if(p->synthflags & SFLAG_LENGTHEN) { DoPause(25,1); DoSpect2(ph, 0, &fmtp, p, 0); } } else { if(p->synthflags & SFLAG_LENGTHEN) { DoPause(50,0); } } if(pre_voiced) { // followed by a vowel, or liquid + vowel StartSyllable(); } else { p->synthflags |= SFLAG_NEXT_PAUSE; } InterpretPhoneme(NULL,0, p, &phdata); fmtp.fmt_addr = phdata.sound_addr[pd_FMT]; fmtp.fmt_amp = phdata.sound_param[pd_FMT]; fmtp.wav_addr = phdata.sound_addr[pd_ADDWAV]; fmtp.wav_amp = phdata.sound_param[pd_ADDWAV]; DoSpect2(ph, 0, &fmtp, p, 0); if((p->newword == 0) && (next2->newword == 0)) { if(next->type == phVFRICATIVE) DoPause(20,0); if(next->type == phFRICATIVE) DoPause(12,0); } break; case phVFRICATIVE: if(next->type==phVOWEL) { DoAmplitude(p->amp,NULL); DoPitch(envelope_data[p->env],p->pitch1,p->pitch2); } else if(next->type==phLIQUID) { DoAmplitude(next->amp,NULL); DoPitch(envelope_data[next->env],next->pitch1,next->pitch2); } else { if(last_pitch_cmd < 0) { DoAmplitude(p->amp,NULL); DoPitch(envelope_data[p->env],p->pitch1,p->pitch2); } } if((next->type==phVOWEL) || ((next->type==phLIQUID) && (next->newword==0))) // ?? test 14.Aug.2007 { StartSyllable(); } else { p->synthflags |= SFLAG_NEXT_PAUSE; } InterpretPhoneme(NULL,0, p, &phdata); memset(&fmtp, 0, sizeof(fmtp)); fmtp.std_length = phdata.pd_param[i_SET_LENGTH]*2; fmtp.fmt_addr = phdata.sound_addr[pd_FMT]; fmtp.fmt_amp = phdata.sound_param[pd_FMT]; fmtp.wav_addr = phdata.sound_addr[pd_ADDWAV]; fmtp.wav_amp = phdata.sound_param[pd_ADDWAV]; if(p->synthflags & SFLAG_LENGTHEN) DoSpect2(p->ph, 0, &fmtp, p, 0); DoSpect2(p->ph, 0, &fmtp, p, 0); break; case phNASAL: memset(&fmtp, 0, sizeof(fmtp)); if(!(p->synthflags & SFLAG_SEQCONTINUE)) { DoAmplitude(p->amp,NULL); DoPitch(envelope_data[p->env],p->pitch1,p->pitch2); } if(prev->type==phNASAL) { last_frame = NULL; } InterpretPhoneme(NULL,0, p, &phdata); fmtp.std_length = phdata.pd_param[i_SET_LENGTH]*2; fmtp.fmt_addr = phdata.sound_addr[pd_FMT]; fmtp.fmt_amp = phdata.sound_param[pd_FMT]; if(next->type==phVOWEL) { StartSyllable(); DoSpect2(p->ph, 0, &fmtp, p, 0); } else if(prev->type==phVOWEL && (p->synthflags & SFLAG_SEQCONTINUE)) { DoSpect2(p->ph, 0, &fmtp, p, 0); } else { last_frame = NULL; // only for nasal ? DoSpect2(p->ph, 0, &fmtp, p, 0); last_frame = NULL; } break; case phLIQUID: memset(&fmtp, 0, sizeof(fmtp)); modulation = 0; if(p->ph->phflags & phTRILL) modulation = 5; if(!(p->synthflags & SFLAG_SEQCONTINUE)) { DoAmplitude(p->amp,NULL); DoPitch(envelope_data[p->env],p->pitch1,p->pitch2); } if(prev->type==phNASAL) { last_frame = NULL; } if(next->type==phVOWEL) { StartSyllable(); } InterpretPhoneme(NULL, 0, p, &phdata); fmtp.std_length = phdata.pd_param[i_SET_LENGTH]*2; fmtp.fmt_addr = phdata.sound_addr[pd_FMT]; fmtp.fmt_amp = phdata.sound_param[pd_FMT]; fmtp.wav_addr = phdata.sound_addr[pd_ADDWAV]; fmtp.wav_amp = phdata.sound_param[pd_ADDWAV]; DoSpect2(p->ph, 0, &fmtp, p, modulation); break; case phVOWEL: ph = p->ph; stress = p->stresslevel & 0xf; memset(&fmtp, 0, sizeof(fmtp)); InterpretPhoneme(NULL, 0, p, &phdata); fmtp.std_length = phdata.pd_param[i_SET_LENGTH] * 2; if(((fmtp.fmt_addr = phdata.sound_addr[pd_VWLSTART]) != 0) && ((phdata.pd_control & pd_FORNEXTPH) == 0)) { // a vowel start has been specified by the Vowel program fmtp.fmt_length = phdata.sound_param[pd_VWLSTART]; } else if(prev->type != phPAUSE) { // check the previous phoneme InterpretPhoneme(NULL, 0, prev, &phdata_prev); if((fmtp.fmt_addr = phdata_prev.sound_addr[pd_VWLSTART]) != 0) { // a vowel start has been specified by the Vowel program fmtp.fmt2_lenadj = phdata_prev.sound_param[pd_VWLSTART]; } fmtp.transition0 = phdata_prev.vowel_transition[0]; fmtp.transition1 = phdata_prev.vowel_transition[1]; } if(fmtp.fmt_addr == 0) { // use the default start for this vowel fmtp.use_vowelin = 1; fmtp.fmt_control = 1; fmtp.fmt_addr = phdata.sound_addr[pd_FMT]; } fmtp.fmt_amp = phdata.sound_param[pd_FMT]; pitch_env = envelope_data[p->env]; amp_env = NULL; if(p->tone_ph != 0) { InterpretPhoneme2(p->tone_ph, &phdata_tone); pitch_env = GetEnvelope(phdata_tone.pitch_env); if(phdata_tone.amp_env > 0) amp_env = GetEnvelope(phdata_tone.amp_env); } StartSyllable(); modulation = 2; if(stress <= 1) modulation = 1; // 16ths else if(stress >= 7) modulation = 3; if(prev->type == phVSTOP || prev->type == phVFRICATIVE) { DoAmplitude(p->amp,amp_env); DoPitch(pitch_env,p->pitch1,p->pitch2); // don't use prevocalic rising tone DoSpect2(ph, 1, &fmtp, p, modulation); } else if(prev->type==phLIQUID || prev->type==phNASAL) { DoAmplitude(p->amp,amp_env); DoSpect2(ph, 1, &fmtp, p, modulation); // continue with pre-vocalic rising tone DoPitch(pitch_env,p->pitch1,p->pitch2); } else { if(!(p->synthflags & SFLAG_SEQCONTINUE)) { DoAmplitude(p->amp,amp_env); DoPitch(pitch_env,p->pitch1,p->pitch2); } DoSpect2(ph, 1, &fmtp, p, modulation); } if((option_phoneme_events) && (done_phoneme_marker == 0)) { WritePhMnemonic(phoneme_name, p->ph, p, use_ipa); DoPhonemeMarker(espeakEVENT_PHONEME, sourceix, 0, phoneme_name); } fmtp.fmt_addr = phdata.sound_addr[pd_FMT]; fmtp.fmt_amp = phdata.sound_param[pd_FMT]; fmtp.transition0 = 0; fmtp.transition1 = 0; if((fmtp.fmt2_addr = phdata.sound_addr[pd_VWLEND]) != 0) { fmtp.fmt2_lenadj = phdata.sound_param[pd_VWLEND]; } else if(next->type != phPAUSE) { fmtp.fmt2_lenadj = 0; InterpretPhoneme(NULL, 0, next, &phdata_next); fmtp.use_vowelin = 1; fmtp.transition0 = phdata_next.vowel_transition[2]; // always do vowel_transition, even if ph_VWLEND ?? consider [N] fmtp.transition1 = phdata_next.vowel_transition[3]; if((fmtp.fmt2_addr = phdata_next.sound_addr[pd_VWLEND]) != 0) { fmtp.fmt2_lenadj = phdata_next.sound_param[pd_VWLEND]; } } DoSpect2(ph, 2, &fmtp, p, modulation); break; } ix++; } EndPitch(1); if(*n_ph > 0) { DoMarker(espeakEVENT_END, count_characters, 0, count_sentences); // end of clause *n_ph = 0; } return(0); // finished the phoneme list } // end of Generate static int timer_on = 0; static int paused = 0; int SynthOnTimer() {//=============== if(!timer_on) { return(WavegenCloseSound()); } do { if(WcmdqUsed() > 0) WavegenOpenSound(); if(Generate(phoneme_list,&n_phoneme_list,1)==0) { SpeakNextClause(NULL,NULL,1); } } while(skipping_text); return(0); } int SynthStatus() {//============== return(timer_on | paused); } int SpeakNextClause(FILE *f_in, const void *text_in, int control) {//============================================================== // Speak text from file (f_in) or memory (text_in) // control 0: start // either f_in or text_in is set, the other must be NULL // The other calls have f_in and text_in = NULL // control 1: speak next text // 2: stop // 3: pause (toggle) // 4: is file being read (0=no, 1=yes) // 5: interrupt and flush current text. int clause_tone; char *voice_change; static FILE *f_text=NULL; static const void *p_text=NULL; if(control == 4) { if((f_text == NULL) && (p_text == NULL)) return(0); else return(1); } if(control == 2) { // stop speaking timer_on = 0; p_text = NULL; if(f_text != NULL) { fclose(f_text); f_text=NULL; } n_phoneme_list = 0; WcmdqStop(); embedded_value[EMBED_T] = 0; return(0); } if(control == 3) { // toggle pause if(paused == 0) { timer_on = 0; paused = 2; } else { WavegenOpenSound(); timer_on = 1; paused = 0; Generate(phoneme_list,&n_phoneme_list,0); // re-start from beginning of clause } return(0); } if(control == 5) { // stop speaking, but continue looking for text n_phoneme_list = 0; WcmdqStop(); return(0); } if((f_in != NULL) || (text_in != NULL)) { f_text = f_in; p_text = text_in; timer_on = 1; paused = 0; } if((f_text==NULL) && (p_text==NULL)) { skipping_text = 0; timer_on = 0; return(0); } if((f_text != NULL) && feof(f_text)) { timer_on = 0; fclose(f_text); f_text=NULL; return(0); } if(current_phoneme_table != voice->phoneme_tab_ix) { SelectPhonemeTable(voice->phoneme_tab_ix); } // read the next clause from the input text file, translate it, and generate // entries in the wavegen command queue p_text = TranslateClause(translator, f_text, p_text, &clause_tone, &voice_change); CalcPitches(translator, clause_tone); CalcLengths(translator); if((option_phonemes > 0) || (phoneme_callback != NULL)) { int use_ipa = 0; if(option_phonemes == 3) use_ipa = 1; GetTranslatedPhonemeString(translator->phon_out, sizeof(translator->phon_out), use_ipa); if(option_phonemes > 0) { fprintf(f_trans,"%s\n",translator->phon_out); if(!iswalpha(0x010d)) { // check that c-caron is recognized as an alphabetic character fprintf(stderr,"Warning: Accented letters are not recognized, eg: U+010D\nSet LC_CTYPE to a UTF-8 locale\n"); } } if(phoneme_callback != NULL) { phoneme_callback(translator->phon_out); } } if(skipping_text) { n_phoneme_list = 0; return(1); } Generate(phoneme_list,&n_phoneme_list,0); WavegenOpenSound(); if(voice_change != NULL) { // voice change at the end of the clause (i.e. clause was terminated by a voice change) new_voice = LoadVoiceVariant(voice_change,0); // add a Voice instruction to wavegen at the end of the clause } if(new_voice) { // finished the current clause, now change the voice if there was an embedded // change voice command at the end of it (i.e. clause was broken at the change voice command) DoVoiceChange(voice); new_voice = NULL; } return(1); } // end of SpeakNextClause sources_5316/external/espeak/espeakdata_FileInMemory.cpp0000664000176700017670000001444211723710247022255 0ustar paulpaul/* espeakdata_FileInMemory.c * * Copyright (C) David Weenink 2012 * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ // The glue between Praat and espeak #include "speech.h" #include FilesInMemory espeakdata_variants; FilesInMemory espeakdata_dicts; FilesInMemory espeakdata_phons; FilesInMemory espeakdata_voices; Strings espeakdata_voices_names; Strings espeakdata_voices_names_short; Strings espeakdata_variants_names; static void FilesInMemory_and_Strings_changeIds (FilesInMemory me, Strings thee) { try { if (my size != thy numberOfStrings) return; // do nothing for (long i = 1; i <= my size; i++) { FileInMemory_setId ((FileInMemory) my item[i], thy strings[i]); } } catch (MelderError) { Melder_throw (me, "Ids not changed."); } } static Strings espeak_voices_sort () { try { autoTable names = espeakdata_voices_to_Table (espeakdata_voices); autoStrings fullnames = espeakdata_voices_getNames (names.peek(), 2); FilesInMemory_and_Strings_changeIds (espeakdata_voices, fullnames.peek()); espeakdata_voices -> d_sortKey = 1; // sort id's Sorted_sort (espeakdata_voices); Table_sortRows_string (names.peek(), L"name"); //They hopefully sort the same way autoStrings neworder = espeakdata_voices_getNames (names.peek(), 2); autoStrings names_short = espeakdata_voices_getNames (names.peek(), 1); FilesInMemory_and_Strings_changeIds (espeakdata_voices, names_short.peek()); return neworder.transfer(); } catch (MelderError) { Melder_throw ("Espeak voices not sorted."); } } static Strings Strings_insertAndExpand (Strings me, long position, const wchar_t *newstring) { try { if (position == 0) position = my numberOfStrings + 1; Melder_assert (position >= 1); Melder_assert (position <= my numberOfStrings + 1); autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, my numberOfStrings + 1); for (long i = 1, from = 1; i <= my numberOfStrings + 1; i++, from++) { const wchar *to_copy = my strings[from]; if (i == position) { to_copy = newstring; from--; } thy strings[i] = Melder_wcsdup (to_copy); } thy numberOfStrings = my numberOfStrings + 1; return thee.transfer(); } catch (MelderError) { Melder_throw (me, " not expanded."); } } void espeakdata_praat_init () { try { espeakdata_variants = create_espeakdata_variants (); autoStrings vnames = FilesInMemory_to_Strings_id (espeakdata_variants); espeakdata_variants_names = Strings_insertAndExpand (vnames.peek(), 1, L"default"); espeakdata_dicts = create_espeakdata_dicts (); espeakdata_phons = create_espeakdata_phons (); espeakdata_voices = create_espeakdata_voices (); espeakdata_voices_names = espeak_voices_sort (); autoTable names_table = espeakdata_voices_to_Table (espeakdata_voices); } catch (MelderError) { Melder_throw ("Espeakdata initialization not performed."); } } #define ESPEAK_ISSPACE(c) (c == ' ' || c == '\t' || c == '\r' || c == '\n') // imitates fgets_strip for file in memory const char * espeakdata_get_voicedata (const char *data, long ndata, char *buf, long nbuf, long *index) { if (ndata <= 0 || nbuf <= 0 || *index >= ndata) { return 0; } long i = 0; while (i < nbuf && *index < ndata && ((buf[i] = data[i]) != '\n')) { i++; (*index)++; } long idata = i + 1; buf[i] = '\0'; while (--i >= 0 && ESPEAK_ISSPACE (buf[i])) { buf[i] = 0; } char *p = strstr (buf, "//"); if (p != 0) { *p = 0; } return &data[idata]; } Table espeakdata_voices_to_Table (FilesInMemory me) { try { autoTable thee = Table_createWithColumnNames (my size, L"id name"); for (long ifile = 1; ifile <= my size; ifile++) { FileInMemory fim = (FileInMemory) my item[ifile]; Table_setStringValue (thee.peek(), ifile, 1, fim -> d_id); const char *p = strstr (fim -> d_data, "name"); if (p == NULL) continue; // copy the name part to the following new line char buf[40], *bufp = buf; long len = 0; while ((*bufp++ = *p++) != '\n' && len < 39) { len++; } // remove trailing white space *bufp = 0; while (ESPEAK_ISSPACE (buf[len]) && len > 0) { buf[len] = 0; len--; } // skip leading white space bufp = & buf[4]; while (ESPEAK_ISSPACE (*bufp)) { *bufp++; } Table_setStringValue (thee.peek(), ifile, 2, Melder_peekUtf8ToWcs (bufp)); TableRow row = static_cast (thy rows -> item [ifile]); wint_t c0 = row -> cells [2]. string[0]; row -> cells [2]. string[0] = towupper (c0); } return thee.transfer(); } catch (MelderError) { Melder_throw ("Espeakdata: voice table not initialized."); } } Strings espeakdata_voices_getNames (Table me, long column) { try { if (column < 0 || column > 2) { Melder_throw ("Illegal columnn."); } autoStrings thee = Thing_new (Strings); thy strings = NUMvector (1, my rows -> size); thy numberOfStrings = 0; for (long irow = 1; irow <= my rows -> size; irow++) { thy strings[irow] = Melder_wcsdup (Table_getStringValue_Assert (me, irow, column)); thy numberOfStrings++; } return thee.transfer(); } catch (MelderError) { Melder_throw ("Espeakdata: voices not initialized."); } } char * espeakdata_get_dict_data (const char *name, unsigned int *size) { long lsize; char *data = FilesInMemory_getCopyOfData (espeakdata_dicts, Melder_peekUtf8ToWcs (name), &lsize); *size = (unsigned int) lsize; return data; } const char * espeakdata_get_voice (const char *vname, long *numberOfBytes) { return FilesInMemory_getData (espeakdata_voices, Melder_peekUtf8ToWcs (vname), numberOfBytes); } const char * espeakdata_get_voiceVariant (const char *vname, long *numberOfBytes) { return FilesInMemory_getData (espeakdata_variants, Melder_peekUtf8ToWcs (vname), numberOfBytes); } /* End of file espeakdata_FileInMemory.cpp */sources_5316/external/espeak/mbrowrap.h0000664000176700017670000000636511674622653017047 0ustar paulpaul/* * mbrowrap -- A wrapper library around the mbrola binary * providing a subset of the API from the Windows mbrola DLL. * * Copyright (C) 2010 by Nicolas Pitre * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. */ #ifndef MBROWRAP_H #define MBROWRAP_H #ifdef __cplusplus extern "C" { #endif /* * Initialize mbrola. The 'voice_path' argument must contain the * path and file name to the mbrola voice database to be used. Returned * value is 0 on success, or an error code otherwise (currently only -1 * is returned. If not successful, lastErrorStr_MBR() will provide the * error reason. If this is successful, then close_MBR() must be called * before init_MBR() can be called again. */ int init_MBR(const char *voice_path); /* * Stop mbrola and release any resources. It is necessary to call * this after a successful call to init_MBR() before init_MBR() can be * called again. */ void close_MBR(void); /* * Stop any ongoing processing and flush all buffers. After this call * any synthesis request will start afresh. A non-zero value is returned * on success, or 0 on failure. If not successful, lastErrorStr_MBR() will * provide the error reason. */ int reset_MBR(); /* * Return at most 'nb_samples' audio samples into 'buffer'. The returned * value is the actual number of samples returned, or -1 on error. * If not successful, lastErrorStr_MBR() will provide the error reason. * Samples are always 16-bit little endian. */ int read_MBR(void *buffer, int nb_samples); /* * Write a NULL terminated string of phoneme in the input buffer. * Return the number of chars actually written, or -1 on error. * If not successful, lastErrorStr_MBR() will provide the error reason. */ int write_MBR(const char *data); /* * Send a flush command to the mbrola input stream. * This is currently similar to write_MBR("#\n"). Return 1 on success * or 0 on failure. If not successful, lastErrorStr_MBR() will provide * the error reason. */ int flush_MBR(void); /* * Return the audio sample frequency of the used voice database. */ int getFreq_MBR(void); /* * Overall volume. */ void setVolumeRatio_MBR(float value); /* * Copy into 'buffer' at most 'bufsize' bytes from the latest error * message. This may also contain non-fatal errors from mbrola. The * returned value is the actual number of bytes copied. When no error * message is pending then an empty string is returned. Consecutive * calls to lastErrorStr_MBR() will return the same message unless it * is explicitly cleared with resetError_MBR(). */ int lastErrorStr_MBR(char *buffer, int bufsize); /* * Clear any pending error message. */ void resetError_MBR(void); /* * Tolerance to missing diphones (always active so this is ignored) */ static inline void setNoError_MBR(int no_error) { } #ifdef __cplusplus } #endif #endif sources_5316/external/espeak/synthesize.h0000664000176700017670000004355511723710247017415 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2007 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #define espeakINITIALIZE_PHONEME_IPA 0x0002 // move this to speak_lib.h, after eSpeak version 1.46.02 #define N_PHONEME_LIST 1000 // enough for source[N_TR_SOURCE] full of text, else it will truncate #define MAX_HARMONIC 400 // 400 * 50Hz = 20 kHz, more than enough #define N_SEQ_FRAMES 25 // max frames in a spectrum sequence (real max is ablut 8) #define STEPSIZE 64 // 2.9mS at 22 kHz sample rate // flags set for frames within a spectrum sequence #define FRFLAG_KLATT 0x01 // this frame includes extra data for Klatt synthesizer #define FRFLAG_VOWEL_CENTRE 0x02 // centre point of vowel #define FRFLAG_LEN_MOD 0x04 // reduce effect of length adjustment #define FRFLAG_BREAK_LF 0x08 // but keep f3 upwards #define FRFLAG_BREAK 0x10 // don't merge with next frame #define FRFLAG_BREAK_2 0x18 // FRFLAG_BREAK_LF or FRFLAG_BREAK #define FRFLAG_FORMANT_RATE 0x20 // Flag5 allow increased rate of change of formant freq #define FRFLAG_MODULATE 0x40 // Flag6 modulate amplitude of some cycles to give trill #define FRFLAG_DEFER_WAV 0x80 // Flag7 defer mixing WAV until the next frame #define FRFLAG_LEN_MOD2 0x4000 // reduce effect of length adjustment, used for the start of a vowel #define FRFLAG_COPIED 0x8000 // This frame has been copied into temporary rw memory #define SFLAG_SEQCONTINUE 0x01 // a liquid or nasal after a vowel, but not followed by a vowel #define SFLAG_EMBEDDED 0x02 // there are embedded commands before this phoneme #define SFLAG_SYLLABLE 0x04 // vowel or syllabic consonant #define SFLAG_LENGTHEN 0x08 // lengthen symbol : included after this phoneme #define SFLAG_DICTIONARY 0x10 // the pronunciation of this word was listed in the xx_list dictionary #define SFLAG_SWITCHED_LANG 0x20 // this word uses phonemes from a different language #define SFLAG_PROMOTE_STRESS 0x40 // this unstressed word can be promoted to stressed #define SFLAG_PREV_PAUSE 0x1000 // consider previous phoneme as pause #define SFLAG_NEXT_PAUSE 0x2000 // consider next phoneme as pause // embedded command numbers #define EMBED_P 1 // pitch #define EMBED_S 2 // speed (used in setlengths) #define EMBED_A 3 // amplitude/volume #define EMBED_R 4 // pitch range/expression #define EMBED_H 5 // echo/reverberation #define EMBED_T 6 // different tone for announcing punctuation #define EMBED_I 7 // sound icon #define EMBED_S2 8 // speed (used in synthesize) #define EMBED_Y 9 // say-as commands #define EMBED_M 10 // mark name #define EMBED_U 11 // audio uri #define EMBED_B 12 // break #define EMBED_F 13 // emphasis #define EMBED_C 14 // capital letter indication #define N_EMBEDDED_VALUES 15 extern int embedded_value[N_EMBEDDED_VALUES]; extern int embedded_default[N_EMBEDDED_VALUES]; #define N_PEAKS 9 #define N_MARKERS 8 #define N_KLATTP 10 // this affects the phoneme data file format #define N_KLATTP2 14 // used in vowel files, with extra parameters for future extensions #define KLATT_AV 0 #define KLATT_FNZ 1 // nasal zero freq #define KLATT_Tilt 2 #define KLATT_Aspr 3 #define KLATT_Skew 4 #define KLATT_Kopen 5 #define KLATT_AVp 6 #define KLATT_Fric 7 #define KLATT_FricBP 8 #define KLATT_Turb 9 typedef struct { // 64 bytes short frflags; short ffreq[7]; unsigned char length; unsigned char rms; unsigned char fheight[8]; unsigned char fwidth[6]; // width/4 f0-5 unsigned char fright[3]; // width/4 f0-2 unsigned char bw[4]; // Klatt bandwidth BNZ /2, f1,f2,f3 unsigned char klattp[5]; // AV, FNZ, Tilt, Aspr, Skew unsigned char klattp2[5]; // continuation of klattp[], Avp, Fric, FricBP, Turb unsigned char klatt_ap[7]; // Klatt parallel amplitude unsigned char klatt_bp[7]; // Klatt parallel bandwidth /2 unsigned char spare; // pad to multiple of 4 bytes } frame_t; // with extra Klatt parameters for parallel resonators typedef struct { // 44 bytes short frflags; short ffreq[7]; unsigned char length; unsigned char rms; unsigned char fheight[8]; unsigned char fwidth[6]; // width/4 f0-5 unsigned char fright[3]; // width/4 f0-2 unsigned char bw[4]; // Klatt bandwidth BNZ /2, f1,f2,f3 unsigned char klattp[5]; // AV, FNZ, Tilt, Aspr, Skew } frame_t2; // without the extra Klatt parameters // formant data used by wavegen typedef struct { int freq; // Hz<<16 int height; // height<<15 int left; // Hz<<16 int right; // Hz<<16 DOUBLEX freq1; // floating point versions of the above DOUBLEX height1; DOUBLEX left1; DOUBLEX right1; DOUBLEX freq_inc; // increment by this every 64 samples DOUBLEX height_inc; DOUBLEX left_inc; DOUBLEX right_inc; } wavegen_peaks_t; typedef struct { unsigned char *pitch_env; int pitch; // pitch Hz*256 int pitch_ix; // index into pitch envelope (*256) int pitch_inc; // increment to pitch_ix int pitch_base; // Hz*256 low, before modified by envelope int pitch_range; // Hz*256 range of envelope unsigned char *mix_wavefile; // wave file to be added to synthesis int n_mix_wavefile; // length in bytes int mix_wave_scale; // 0=2 byte samples int mix_wave_amp; int mix_wavefile_ix; int mix_wavefile_max; // length of available WAV data (in bytes) int mix_wavefile_offset; int amplitude; int amplitude_v; int amplitude_fmt; // percentage amplitude adjustment for formant synthesis } WGEN_DATA; typedef struct { double a; double b; double c; double x1; double x2; } RESONATOR; typedef struct { short length_total; // not used unsigned char n_frames; unsigned char sqflags; frame_t2 frame[N_SEQ_FRAMES]; // max. frames in a spectrum sequence } SPECT_SEQ; // sequence of espeak formant frames typedef struct { short length_total; // not used unsigned char n_frames; unsigned char sqflags; frame_t frame[N_SEQ_FRAMES]; // max. frames in a spectrum sequence } SPECT_SEQK; // sequence of klatt formants frames typedef struct { short length; short frflags; frame_t *frame; } frameref_t; // a clause translated into phoneme codes (first stage) typedef struct { unsigned char phcode; unsigned char stresslevel; unsigned char wordstress; unsigned char tone_ph; // tone phoneme to use with this vowel unsigned short synthflags; unsigned short sourceix; // ix into the original source text string, only set at the start of a word } PHONEME_LIST2; typedef struct { // The first section is a copy of PHONEME_LIST2 unsigned char phcode; unsigned char stresslevel; unsigned char wordstress; // the highest level stress in this word unsigned char tone_ph; // tone phoneme to use with this vowel unsigned short synthflags; unsigned short sourceix; // ix into the original source text string, only set at the start of a word PHONEME_TAB *ph; short length; // length_mod unsigned char env; // pitch envelope number unsigned char type; unsigned char prepause; unsigned char postpause; unsigned char amp; unsigned char newword; // bit 0=start of word, bit 1=end of clause, bit 2=start of sentence unsigned char pitch1; unsigned char pitch2; } PHONEME_LIST; #define pd_FMT 0 #define pd_WAV 1 #define pd_VWLSTART 2 #define pd_VWLEND 3 #define pd_ADDWAV 4 #define N_PHONEME_DATA_PARAM 16 #define pd_INSERTPHONEME i_INSERT_PHONEME #define pd_APPENDPHONEME i_APPEND_PHONEME #define pd_CHANGEPHONEME i_CHANGE_PHONEME #define pd_LENGTHMOD i_SET_LENGTH #define pd_FORNEXTPH 0x2 #define pd_DONTLENGTHEN 0x4 #define pd_REDUCELENGTHCHANGE 0x8 typedef struct { int pd_control; int pd_param[N_PHONEME_DATA_PARAM]; // set from group 0 instructions int sound_addr[5]; int sound_param[5]; int vowel_transition[4]; int pitch_env; int amp_env; char ipa_string[18]; } PHONEME_DATA; typedef struct { int fmt_control; int use_vowelin; int fmt_addr; int fmt_length; int fmt_amp; int fmt2_addr; int fmt2_lenadj; int wav_addr; int wav_amp; int transition0; int transition1; int std_length; } FMT_PARAMS; // instructions #define i_RETURN 0x0001 #define i_CONTINUE 0x0002 // Group 0 instrcutions with 8 bit operand. These values go into bits 8-15 of the instruction #define i_CHANGE_PHONEME 0x01 #define i_REPLACE_NEXT_PHONEME 0x02 #define i_INSERT_PHONEME 0x03 #define i_APPEND_PHONEME 0x04 #define i_APPEND_IFNEXTVOWEL 0x05 #define i_VOICING_SWITCH 0x06 #define i_PAUSE_BEFORE 0x07 #define i_PAUSE_AFTER 0x08 #define i_LENGTH_MOD 0x09 #define i_SET_LENGTH 0x0a #define i_LONG_LENGTH 0x0b #define i_CHANGE_PHONEME2 0x0c // not yet used #define i_IPA_NAME 0x0d #define i_CHANGE_IF 0x10 // 0x10 to 0x14 #define i_ADD_LENGTH 0x0c // conditions and jumps #define i_CONDITION 0x2000 #define i_OR 0x1000 // added to i_CONDITION #define i_JUMP 0x6000 #define i_JUMP_FALSE 0x6800 #define i_SWITCH_NEXTVOWEL 0x6a00 #define i_SWITCH_PREVVOWEL 0x6c00 #define MAX_JUMP 255 // max jump distance // multi-word instructions #define i_CALLPH 0x9100 #define i_PITCHENV 0x9200 #define i_AMPENV 0x9300 #define i_VOWELIN 0xa100 #define i_VOWELOUT 0xa200 #define i_FMT 0xb000 #define i_WAV 0xc000 #define i_VWLSTART 0xd000 #define i_VWLENDING 0xe000 #define i_WAVADD 0xf000 // conditions #define i_isDiminished 0x80 #define i_isUnstressed 0x81 #define i_isNotStressed 0x82 #define i_isStressed 0x83 #define i_isMaxStress 0x84 #define i_isBreak 0x85 #define i_isWordStart 0x86 #define i_notWordStart 0x87 #define i_isWordEnd 0x88 #define i_isAfterStress 0x89 #define i_isNotVowel 0x8a #define i_isFinalVowel 0x8b #define i_isVoiced 0x8c #define i_isFirstVowel 0x8d #define i_isSecondVowel 0x8e #define i_isSeqFlag1 0x8f #define i_IsTranslationGiven 0x90 // place of articulation #define i_isVel 0x28 // phflags #define i_isSibilant 0x45 // bit 5 in phflags #define i_isPalatal 0x49 // bit 9 in phflags #define i_isRhotic 0x57 // bit 23 in phflags #define i_isFlag1 0x5c #define i_isFlag2 0x5d #define i_isFlag3 0x5e #define i_StressLevel 0x800 typedef struct { int name; int length; char *data; char *filename; } SOUND_ICON; typedef struct { int name; unsigned int next_phoneme; int mbr_name; int mbr_name2; int percent; // percentage length of first component int control; } MBROLA_TAB; typedef struct { int pause_factor; int clause_pause_factor; int min_pause; int wav_factor; int lenmod_factor; int lenmod2_factor; int min_sample_len; int loud_consonants; int fast_settings[8]; } SPEED_FACTORS; typedef struct { char name[12]; unsigned char flags[4]; signed char head_extend[8]; unsigned char prehead_start; unsigned char prehead_end; unsigned char stressed_env; unsigned char stressed_drop; unsigned char secondary_drop; unsigned char unstressed_shape; unsigned char onset; unsigned char head_start; unsigned char head_end; unsigned char head_last; unsigned char head_max_steps; unsigned char n_head_extend; signed char unstr_start[3]; // for: onset, head, last signed char unstr_end[3]; unsigned char nucleus0_env; // pitch envelope, tonic syllable is at end, no tail unsigned char nucleus0_max; unsigned char nucleus0_min; unsigned char nucleus1_env; // when followed by a tail unsigned char nucleus1_max; unsigned char nucleus1_min; unsigned char tail_start; unsigned char tail_end; unsigned char split_nucleus_env; unsigned char split_nucleus_max; unsigned char split_nucleus_min; unsigned char split_tail_start; unsigned char split_tail_end; unsigned char split_tune; unsigned char spare[8]; int spare2; // the struct length should be a multiple of 4 bytes } TUNE; extern int n_tunes; extern TUNE *tunes; // phoneme table extern PHONEME_TAB *phoneme_tab[N_PHONEME_TAB]; // list of phonemes in a clause extern int n_phoneme_list; extern PHONEME_LIST phoneme_list[N_PHONEME_LIST]; extern unsigned int embedded_list[]; extern unsigned char env_fall[128]; extern unsigned char env_rise[128]; extern unsigned char env_frise[128]; #define MAX_PITCH_VALUE 101 extern unsigned char pitch_adjust_tab[MAX_PITCH_VALUE+1]; // queue of commands for wavegen #define WCMD_KLATT 1 #define WCMD_KLATT2 2 #define WCMD_SPECT 3 #define WCMD_SPECT2 4 #define WCMD_PAUSE 5 #define WCMD_WAVE 6 #define WCMD_WAVE2 7 #define WCMD_AMPLITUDE 8 #define WCMD_PITCH 9 #define WCMD_MARKER 10 #define WCMD_VOICE 11 #define WCMD_EMBEDDED 12 #define WCMD_MBROLA_DATA 13 #define WCMD_FMT_AMPLITUDE 14 #define WCMD_SONIC_SPEED 15 #define N_WCMDQ 170 #define MIN_WCMDQ 25 // need this many free entries before adding new phoneme extern long64 wcmdq[N_WCMDQ][4]; extern int wcmdq_head; extern int wcmdq_tail; // from Wavegen file int WcmdqFree(); void WcmdqStop(); int WcmdqUsed(); void WcmdqInc(); int WavegenOpenSound(); int WavegenCloseSound(); int WavegenInitSound(); void WavegenInit(int rate, int wavemult_fact); float polint(float xa[],float ya[],int n,float x); int WavegenFill(int fill_zeros); void MarkerEvent(int type, unsigned int char_position, int value, int value2, unsigned char *out_ptr); extern unsigned char *wavefile_data; extern int samplerate; extern int samplerate_native; extern int wavefile_ix; extern int wavefile_amp; extern int wavefile_ix2; extern int wavefile_amp2; extern int vowel_transition[4]; extern int vowel_transition0, vowel_transition1; #define N_ECHO_BUF 5500 // max of 250mS at 22050 Hz extern int echo_head; extern int echo_tail; extern int echo_amp; extern short echo_buf[N_ECHO_BUF]; extern int mbrola_delay; extern char mbrola_name[20]; // from synthdata file unsigned int LookupSound(PHONEME_TAB *ph1, PHONEME_TAB *ph2, int which, int *match_level, int control); frameref_t *LookupSpect(PHONEME_TAB *this_ph, int which, FMT_PARAMS *fmt_params, int *n_frames, PHONEME_LIST *plist); unsigned char *LookupEnvelope(int ix); int LoadPhData(); void SynthesizeInit(void); int Generate(PHONEME_LIST *phoneme_list, int *n_ph, int resume); void MakeWave2(PHONEME_LIST *p, int n_ph); int SynthOnTimer(void); int SpeakNextClause(FILE *f_text, const void *text_in, int control); int SynthStatus(void); void SetSpeed(int control); void SetEmbedded(int control, int value); void SelectPhonemeTable(int number); int SelectPhonemeTableName(const char *name); void Write4Bytes(FILE *f, int value); int Read4Bytes(FILE *f); int Reverse4Bytes(int word); int CompileDictionary(const char *dsource, const char *dict_name, FILE *log, char *err_name,int flags); #define ENV_LEN 128 // length of pitch envelopes #define PITCHfall 0 // standard pitch envelopes #define PITCHrise 2 #define N_ENVELOPE_DATA 20 extern unsigned char *envelope_data[N_ENVELOPE_DATA]; extern int formant_rate[]; // max rate of change of each formant extern SPEED_FACTORS speed; extern long count_samples; extern int outbuf_size; extern unsigned char *out_ptr; extern unsigned char *out_start; extern unsigned char *out_end; extern int event_list_ix; extern espeak_EVENT *event_list; extern t_espeak_callback* synth_callback; extern int option_log_frames; extern const char *version_string; extern const int version_phdata; extern double sonicSpeed; #define N_SOUNDICON_TAB 80 // total entries in soundicon_tab #define N_SOUNDICON_SLOTS 4 // number of slots reserved for dynamic loading of audio files extern int n_soundicon_tab; extern SOUND_ICON soundicon_tab[N_SOUNDICON_TAB]; espeak_ERROR SetVoiceByName(const char *name); espeak_ERROR SetVoiceByProperties(espeak_VOICE *voice_selector); espeak_ERROR LoadMbrolaTable(const char *mbrola_voice, const char *phtrans, int srate); void SetParameter(int parameter, int value, int relative); int MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, int resume, FILE *f_mbrola); int MbrolaGenerate(PHONEME_LIST *phoneme_list, int *n_ph, int resume); int MbrolaFill(int length, int resume, int amplitude); void MbrolaReset(void); void DoEmbedded(int *embix, int sourceix); void DoMarker(int type, int char_posn, int length, int value); void DoPhonemeMarker(int type, int char_posn, int length, char *name); int DoSample3(PHONEME_DATA *phdata, int length_mod, int amp); int DoSpect2(PHONEME_TAB *this_ph, int which, FMT_PARAMS *fmt_params, PHONEME_LIST *plist, int modulation); int PauseLength(int pause, int control); int LookupPhonemeTable(const char *name); unsigned char *GetEnvelope(int index); void InitBreath(void); void KlattInit(); void KlattReset(int control); int Wavegen_Klatt2(int length, int modulation, int resume, frame_t *fr1, frame_t *fr2); sources_5316/external/espeak/readclause.cpp0000775000176700017670000020126111723710247017644 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2011 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" #ifdef PLATFORM_POSIX #include #endif #include #define N_XML_BUF 256 static const char *xmlbase = ""; // base URL from static int namedata_ix=0; static int n_namedata = 0; char *namedata = NULL; static FILE *f_input = NULL; static int ungot_char2 = 0; unsigned char *p_textinput; wchar_t *p_wchar_input; static int ungot_char; static const char *ungot_word = NULL; static int end_of_input; static int ignore_text=0; // set during ... to ignore text which has been replaced by an alias static int audio_text=0; // set during static int clear_skipping_text = 0; // next clause should clear the skipping_text flag int count_characters = 0; static int sayas_mode; static int sayas_start; static int ssml_ignore_l_angle = 0; // alter tone for announce punctuation or capitals //static const char *tone_punct_on = "\0016T"; // add reverberation, lower pitch //static const char *tone_punct_off = "\001T\001P"; // ignore these characters static const unsigned short chars_ignore[] = { 0x200c, // zero width non-joiner 0x200d, // zero width joiner 0 }; // punctuations symbols that can end a clause static const unsigned short punct_chars[] = {',','.','?','!',':',';', 0x2013, // en-dash 0x2014, // em-dash 0x2026, // elipsis 0x037e, // Greek question mark (looks like semicolon) 0x0387, // Greek semicolon, ano teleia 0x0964, // Devanagari Danda (fullstop) 0x0589, // Armenian period 0x055d, // Armenian comma 0x055c, // Armenian exclamation 0x055e, // Armenian question 0x055b, // Armenian emphasis mark 0x0b1b, // Arabic ; 0x061f, // Arabic ? 0x0f0d, // Tibet Shad 0x0f0e, 0x1362, // Ethiopic period 0x1363, 0x1364, 0x1365, 0x1366, 0x1367, 0x1368, 0x10fb, // Georgian paragraph 0x3001, // ideograph comma 0x3002, // ideograph period 0xff01, // fullwidth exclamation 0xff0c, // fullwidth comma 0xff0e, // fullwidth period 0xff1a, // fullwidth colon 0xff1b, // fullwidth semicolon 0xff1f, // fullwidth question mark 0}; // indexed by (entry num. in punct_chars) + 1 // bits 0-7 pause x 10mS, bits 12-14 intonation type, bit 15 don't need following space or bracket static const unsigned int punct_attributes [] = { 0, CLAUSE_COMMA, CLAUSE_PERIOD, CLAUSE_QUESTION, CLAUSE_EXCLAMATION, CLAUSE_COLON, CLAUSE_SEMICOLON, CLAUSE_SEMICOLON, // en-dash CLAUSE_SEMICOLON, // em-dash CLAUSE_SEMICOLON | PUNCT_SAY_NAME | 0x8000, // elipsis CLAUSE_QUESTION, // Greek question mark CLAUSE_SEMICOLON, // Greek semicolon CLAUSE_PERIOD | 0x8000, // Devanagari Danda (fullstop) CLAUSE_PERIOD | 0x8000, // Armenian period CLAUSE_COMMA, // Armenian comma CLAUSE_EXCLAMATION | PUNCT_IN_WORD, // Armenian exclamation CLAUSE_QUESTION | PUNCT_IN_WORD, // Armenian question CLAUSE_PERIOD | PUNCT_IN_WORD, // Armenian emphasis mark CLAUSE_SEMICOLON, // Arabic ; CLAUSE_QUESTION, // Arabic question mark CLAUSE_PERIOD+0x8000, // Tibet period CLAUSE_PARAGRAPH, CLAUSE_PERIOD, // Ethiopic period CLAUSE_COMMA, // Ethiopic comma CLAUSE_SEMICOLON, // Ethiopic semicolon CLAUSE_COLON, // Ethiopic colon CLAUSE_COLON, // Ethiopic preface colon CLAUSE_QUESTION, // Ethiopic question mark CLAUSE_PARAGRAPH, // Ethiopic paragraph CLAUSE_PARAGRAPH, // Georgian paragraph CLAUSE_COMMA+0x8000, // ideograph comma CLAUSE_PERIOD+0x8000, // ideograph period CLAUSE_EXCLAMATION+0x8000, // fullwidth CLAUSE_COMMA+0x8000, CLAUSE_PERIOD+0x8000, CLAUSE_COLON+0x8000, CLAUSE_SEMICOLON+0x8000, CLAUSE_QUESTION+0x8000, CLAUSE_SEMICOLON, // spare 0 }; // stack for language and voice properties // frame 0 is for the defaults, before any ssml tags. typedef struct { int tag_type; int voice_variant_number; int voice_gender; int voice_age; char voice_name[40]; char language[20]; } SSML_STACK; #define N_SSML_STACK 20 static int n_ssml_stack; static SSML_STACK ssml_stack[N_SSML_STACK]; static espeak_VOICE base_voice; static char base_voice_variant_name[40] = {0}; static char current_voice_id[40] = {0}; #define N_PARAM_STACK 20 static int n_param_stack; PARAM_STACK param_stack[N_PARAM_STACK]; static int speech_parameters[N_SPEECH_PARAM]; // current values, from param_stack int saved_parameters[N_SPEECH_PARAM]; //Parameters saved on synthesis start const int param_defaults[N_SPEECH_PARAM] = { 0, // silence (internal use) 175, // rate wpm 100, // volume 50, // pitch 50, // range 0, // punctuation 0, // capital letters 0, // wordgap 0, // options 0, // intonation 0, 0, 0, // emphasis 0, // line length 0, // voice type }; #ifdef NEED_WCHAR_FUNCTIONS // additional Latin characters beyond the Latin1 character set #define MAX_WALPHA 0x233 // indexed by character - 0x100 // 0=not alphabetic, 0xff=lower case, 0xfe=special case // other=value to add to upper case to convert to lower case static unsigned char walpha_tab[MAX_WALPHA-0xff] = { 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 100 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 110 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 120 0xfe,0xff, 1,0xff, 1,0xff, 1,0xff,0xff, 1,0xff, 1,0xff, 1,0xff, 1, // 130 0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff,0xff, 1,0xff, 1,0xff, 1,0xff, // 140 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 150 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 160 1,0xff, 1,0xff, 1,0xff, 1,0xff,0xff, 1,0xff, 1,0xff, 1,0xff,0xff, // 170 0xff, 210, 1,0xff, 1,0xff, 206, 1,0xff, 205, 205, 1,0xff,0xff, 79, 202, // 180 203, 1,0xff, 205, 207,0xff, 211, 209, 1,0xff,0xff,0xff, 211, 213,0xff, 214, // 190 1,0xff, 1,0xff, 1,0xff, 218, 1,0xff, 218,0xff,0xff, 1,0xff, 218, 1, // 1a0 0xff, 217, 217, 1,0xff, 1,0xff, 219, 1,0xff,0xff,0xff, 1,0xff,0xff,0xff, // 1b0 0xff,0xff,0xff,0xff, 2, 1,0xff, 2, 1,0xff, 2, 1,0xff, 1,0xff, 1, // 1c0 0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff,0xff, 1,0xff, // 1d0 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 1e0 0xff, 2, 1,0xff, 1,0xff,0xff,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 1f0 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 200 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 210 0xff, 0, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, 1,0xff, // 220 1,0xff, 1,0xff }; // 230 // use ctype.h functions for Latin1 (character < 0x100) int iswalpha(int c) { if(c < 0x100) return(isalpha(c)); if((c > 0x3040) && (c <= 0xa700)) return(1); // japanese, chinese characters if(c > MAX_WALPHA) return(0); return(walpha_tab[c-0x100]); } int iswdigit(int c) { if(c < 0x100) return(isdigit(c)); return(0); } int iswalnum(int c) { if(iswdigit(c)) return(1); return(iswalpha(c)); } int towlower(int c) { int x; if(c < 0x100) return(tolower(c)); if((c > MAX_WALPHA) || ((x = walpha_tab[c-0x100])==0xff)) return(c); // already lower case if(x == 0xfe) { // special cases if(c == 0x130) // uppercase i-dot return('i'); } return(c + x); // convert to lower case } int towupper(int c) { // check whether the previous character code is the upper-case equivalent of this character if(tolower(c-1) == c) return(c-1); // yes, use it return(c); // no } int iswupper(int c) { int x; if(c < 0x100) return(isupper(c)); if(((c > MAX_WALPHA) || (x = walpha_tab[c-0x100])==0) || (x == 0xff)) return(0); return(1); } int iswlower(int c) { if(c < 0x100) return(islower(c)); if((c > MAX_WALPHA) || (walpha_tab[c-0x100] != 0xff)) return(0); return(1); } int iswspace(int c) { if(c < 0x100) return(isspace(c)); return(0); } int iswpunct(int c) { if(c < 0x100) return(ispunct(c)); return(0); } const wchar_t *wcschr(const wchar_t *str, int c) { while(*str != 0) { if(*str == c) return(str); str++; } return(NULL); } #ifndef WINCE // wcslen() is provided by WINCE, but not the other wchar functions const int wcslen(const wchar_t *str) { int ix=0; while(*str != 0) { ix++; } return(ix); } #endif float wcstod(const wchar_t *str, wchar_t **tailptr) { int ix; char buf[80]; while(isspace(*str)) str++; for(ix=0; ix<80; ix++) { buf[ix] = str[ix]; if(isspace(buf[ix])) break; } *tailptr = (wchar_t *)&str[ix]; return(atof(buf)); } #endif int towlower2(unsigned int c) { // check for non-standard upper to lower case conversions if(c == 'I') { if(translator->translator_name == L('t','r')) { c = 0x131; // I -> ı } } #ifdef __WIN32__ if(c == 0x130) // uppercase i-dot return('i'); #endif return(towlower(c)); } static int IsRomanU(unsigned int c) {//================================ if((c=='I') || (c=='V') || (c=='X') || (c=='L')) return(1); return(0); } static void GetC_unget(int c) {//========================== // This is only called with UTF8 input, not wchar input if(f_input != NULL) ungetc(c,f_input); else { p_textinput--; *p_textinput = c; end_of_input = 0; } } int Eof(void) {//========== if(ungot_char != 0) return(0); if(f_input != 0) return(feof(f_input)); return(end_of_input); } static int GetC_get(void) {//====================== unsigned int c; unsigned int c2; if(f_input != NULL) { c = fgetc(f_input); if(feof(f_input)) c = ' '; if(option_multibyte == espeakCHARS_16BIT) { c2 = fgetc(f_input); if(feof(f_input)) c2 = 0; c = c + (c2 << 8); } return(c); } if(option_multibyte == espeakCHARS_WCHAR) { if(*p_wchar_input == 0) { end_of_input = 1; return(0); } if(!end_of_input) return(*p_wchar_input++); } else { if(*p_textinput == 0) { end_of_input = 1; return(0); } if(!end_of_input) { if(option_multibyte == espeakCHARS_16BIT) { c = p_textinput[0] + (p_textinput[1] << 8); p_textinput += 2; return(c); } return(*p_textinput++ & 0xff); } } return(0); } static int GetC(void) {//================== // Returns a unicode wide character // Performs UTF8 checking and conversion int c; int c1; int c2; int cbuf[4]; int ix; int n_bytes; static int ungot2 = 0; static const unsigned char mask[4] = {0xff,0x1f,0x0f,0x07}; if((c1 = ungot_char) != 0) { ungot_char = 0; return(c1); } if(ungot2 != 0) { c1 = ungot2; ungot2 = 0; } else { c1 = GetC_get(); } if((option_multibyte == espeakCHARS_WCHAR) || (option_multibyte == espeakCHARS_16BIT)) { count_characters++; return(c1); // wchar_t text } if((option_multibyte < 2) && (c1 & 0x80)) { // multi-byte utf8 encoding, convert to unicode n_bytes = 0; if(((c1 & 0xe0) == 0xc0) && ((c1 & 0x1e) != 0)) n_bytes = 1; else if((c1 & 0xf0) == 0xe0) n_bytes = 2; else if(((c1 & 0xf8) == 0xf0) && ((c1 & 0x0f) <= 4)) n_bytes = 3; if((ix = n_bytes) > 0) { c = c1 & mask[ix]; while(ix > 0) { if((c2 = cbuf[ix] = GetC_get()) == 0) { if(option_multibyte==espeakCHARS_AUTO) option_multibyte=espeakCHARS_8BIT; // change "auto" option to "no" GetC_unget(' '); break; } if((c2 & 0xc0) != 0x80) { // This is not UTF8. Change to 8-bit characterset. if((n_bytes == 2) && (ix == 1)) ungot2 = cbuf[2]; GetC_unget(c2); break; } c = (c << 6) + (c2 & 0x3f); ix--; } if(ix == 0) { count_characters++; return(c); } } // top-bit-set character is not utf8, drop through to 8bit charset case if((option_multibyte==espeakCHARS_AUTO) && !Eof()) option_multibyte=espeakCHARS_8BIT; // change "auto" option to "no" } // 8 bit character set, convert to unicode if count_characters++; if(c1 >= 0xa0) return(translator->charset_a0[c1-0xa0]); return(c1); } // end of GetC static void UngetC(int c) {//====================== ungot_char = c; } static const char *WordToString2(unsigned int word) {//================================================ // Convert a language mnemonic word into a string int ix; static char buf[5]; char *p; p = buf; for(ix=3; ix>=0; ix--) { if((*p = word >> (ix*8)) != 0) p++; } *p = 0; return(buf); } static const char *LookupSpecial(Translator *tr, const char *string, char* text_out) {//================================================================================= unsigned int flags[2]; char phonemes[55]; char phonemes2[55]; char *string1 = (char *)string; flags[0] = flags[1] = 0; if(LookupDictList(tr,&string1,phonemes,flags,0,NULL)) { SetWordStress(tr, phonemes, flags, -1, 0); DecodePhonemes(phonemes,phonemes2); sprintf(text_out,"[\002%s]]",phonemes2); return(text_out); } return(NULL); } static const char *LookupCharName(Translator *tr, int c, int only) {//=============================================================== // Find the phoneme string (in ascii) to speak the name of character c // Used for punctuation characters and symbols int ix; unsigned int flags[2]; char single_letter[24]; char phonemes[60]; char phonemes2[60]; const char *lang_name = NULL; char *string; static char buf[60]; buf[0] = 0; flags[0] = 0; flags[1] = 0; single_letter[0] = 0; single_letter[1] = '_'; ix = utf8_out(c,&single_letter[2]); single_letter[2+ix]=0; if(only) { string = &single_letter[2]; LookupDictList(tr, &string, phonemes, flags, 0, NULL); } else { string = &single_letter[1]; if(LookupDictList(tr, &string, phonemes, flags, 0, NULL) == 0) { // try _* then * string = &single_letter[2]; if(LookupDictList(tr, &string, phonemes, flags, 0, NULL) == 0) { // now try the rules single_letter[1] = ' '; TranslateRules(tr, &single_letter[2], phonemes, sizeof(phonemes), NULL,0,NULL); } } } if((only==0) && (phonemes[0] == 0) && (tr->translator_name != L('e','n'))) { // not found, try English SetTranslator2("en"); string = &single_letter[1]; single_letter[1] = '_'; if(LookupDictList(translator2, &string, phonemes, flags, 0, NULL) == 0) { string = &single_letter[2]; LookupDictList(translator2, &string, phonemes, flags, 0, NULL); } if(phonemes[0]) { lang_name = "en"; } else { SelectPhonemeTable(voice->phoneme_tab_ix); // revert to original phoneme table } } if(phonemes[0]) { if(lang_name) { SetWordStress(translator2, phonemes, flags, -1, 0); DecodePhonemes(phonemes,phonemes2); sprintf(buf,"[\002_^_%s %s _^_%s]]","en",phonemes2,WordToString2(tr->translator_name)); SelectPhonemeTable(voice->phoneme_tab_ix); // revert to original phoneme table } else { SetWordStress(tr, phonemes, flags, -1, 0); DecodePhonemes(phonemes,phonemes2); sprintf(buf,"[\002%s]] ",phonemes2); } } else if(only == 0) { strcpy(buf,"[\002(X1)(X1)(X1)]]"); } return(buf); } int Read4Bytes(FILE *f) {//==================== // Read 4 bytes (least significant first) into a word int ix; unsigned char c; int acc=0; for(ix=0; ix<4; ix++) { c = fgetc(f) & 0xff; acc += (c << (ix*8)); } return(acc); } static int LoadSoundFile(const char *fname, int index) {//=================================================== FILE *f; char *p; int *ip; int length; char fname_temp[100]; char fname2[sizeof(path_home)+13+40]; if(fname == NULL) { // filename is already in the table fname = soundicon_tab[index].filename; } if(fname==NULL) return(1); if(fname[0] != '/') { // a relative path, look in espeak-data/soundicons sprintf(fname2,"%s%csoundicons%c%s",path_home,PATHSEP,PATHSEP,fname); fname = fname2; } f = NULL; #ifdef PLATFORM_POSIX if((f = fopen(fname,"rb")) != NULL) { int ix; int fd_temp; const char *resample; int header[3]; char command[sizeof(fname2)+sizeof(fname2)+40]; fseek(f,20,SEEK_SET); for(ix=0; ix<3; ix++) header[ix] = Read4Bytes(f); // if the sound file is not mono, 16 bit signed, at the correct sample rate, then convert it if((header[0] != 0x10001) || (header[1] != samplerate) || (header[2] != samplerate*2)) { fclose(f); f = NULL; if(header[2] == samplerate) resample = ""; else resample = "polyphase"; strcpy(fname_temp,"/tmp/espeakXXXXXX"); if((fd_temp = mkstemp(fname_temp)) >= 0) { close(fd_temp); // sprintf(fname_temp,"%s.wav",tmpnam(NULL)); sprintf(command,"sox \"%s\" -r %d -w -s -c1 %s %s\n", fname, samplerate, fname_temp, resample); if(system(command) == 0) { fname = fname_temp; } } } } #endif if(f == NULL) { f = fopen(fname,"rb"); if(f == NULL) { // fprintf(stderr,"Can't read temp file: %s\n",fname); return(3); } } length = GetFileLength(fname); fseek(f,0,SEEK_SET); if((p = (char *)realloc(soundicon_tab[index].data, length)) == NULL) { fclose(f); return(4); } length = fread(p,1,length,f); fclose(f); remove(fname_temp); ip = (int *)(&p[40]); soundicon_tab[index].length = (*ip) / 2; // length in samples soundicon_tab[index].data = p; return(0); } // end of LoadSoundFile static int LookupSoundicon(int c) {//============================== // Find the sound icon number for a punctuation chatacter int ix; for(ix=N_SOUNDICON_SLOTS; ix= N_SOUNDICON_SLOTS) slot = 0; if(LoadSoundFile(fname, slot) != 0) return(-1); soundicon_tab[slot].filename = (char *)realloc(soundicon_tab[ix].filename, strlen(fname)+1); strcpy(soundicon_tab[slot].filename, fname); return(slot); } static int AnnouncePunctuation(Translator *tr, int c1, int *c2_ptr, char *output, int *bufix, int end_clause) {//========================================================================================================== // announce punctuation names // c1: the punctuation character // c2: the following character int punct_count; const char *punctname; int found = 0; int soundicon; int attributes; int short_pause; int c2; int len; int bufix1; char buf[200]; char buf2[80]; c2 = *c2_ptr; buf[0] = 0; if((soundicon = LookupSoundicon(c1)) >= 0) { // add an embedded command to play the soundicon sprintf(buf,"\001%dI ",soundicon); UngetC(c2); found = 1; } else if((punctname = LookupCharName(tr, c1, 0)) != NULL) { found = 1; if((*bufix==0) || (end_clause ==0) || (tr->langopts.param[LOPT_ANNOUNCE_PUNCT] & 2)) { punct_count=1; while((c2 == c1) && (c1 != '<')) // don't eat extra '<', it can miss XML tags { punct_count++; c2 = GetC(); } *c2_ptr = c2; if(end_clause) { UngetC(c2); } if(punct_count==1) { // sprintf(buf,"%s %s %s",tone_punct_on,punctname,tone_punct_off); sprintf(buf," %s",punctname); // we need the space before punctname, to ensure it doesn't merge with the previous word (eg. "2.-a") } else if(punct_count < 4) { buf[0] = 0; if(embedded_value[EMBED_S] < 300) sprintf(buf,"\001+10S"); // Speak punctuation name faster, unless we are already speaking fast. It would upset Sonic SpeedUp while(punct_count-- > 0) { sprintf(buf2," %s",punctname); strcat(buf, buf2); } if(embedded_value[EMBED_S] < 300) { sprintf(buf2," \001-10S"); strcat(buf, buf2); } } else { sprintf(buf," %s %d %s", punctname,punct_count,punctname); } } else { // end the clause now and pick up the punctuation next time UngetC(c2); if(option_ssml) { if((c1 == '<') || (c1 == '&')) ssml_ignore_l_angle = c1; // this was < which was converted to <, don't pick it up again as < } ungot_char2 = c1; buf[0] = ' '; buf[1] = 0; } } if(found == 0) return(-1); bufix1 = *bufix; len = strlen(buf); strcpy(&output[*bufix],buf); *bufix += len; if(end_clause==0) return(-1); if(c1 == '-') return(CLAUSE_NONE); // no pause attributes = punct_attributes[lookupwchar(punct_chars,c1)]; short_pause = CLAUSE_SHORTFALL; if((attributes & CLAUSE_BITS_INTONATION) == 0x1000) short_pause = CLAUSE_SHORTCOMMA; if((bufix1 > 0) && !(tr->langopts.param[LOPT_ANNOUNCE_PUNCT] & 2)) { if((attributes & ~0x8000) == CLAUSE_SEMICOLON) return(CLAUSE_SHORTFALL); return(short_pause); } if(attributes & CLAUSE_BIT_SENTENCE) return(attributes); return(short_pause); } // end of AnnouncePunctuation #define SSML_SPEAK 1 #define SSML_VOICE 2 #define SSML_PROSODY 3 #define SSML_SAYAS 4 #define SSML_MARK 5 #define SSML_SENTENCE 6 #define SSML_PARAGRAPH 7 #define SSML_PHONEME 8 #define SSML_SUB 9 #define SSML_STYLE 10 #define SSML_AUDIO 11 #define SSML_EMPHASIS 12 #define SSML_BREAK 13 #define SSML_IGNORE_TEXT 14 #define HTML_BREAK 15 #define HTML_NOSPACE 16 // don't insert a space for this element, so it doesn't break a word #define SSML_CLOSE 0x20 // for a closing tag, OR this with the tag type // these tags have no effect if they are self-closing, eg. static char ignore_if_self_closing[] = {0,1,1,1,1,0,0,0,0,1,1,0,1,0,1,0,0,0,0}; static MNEM_TAB ssmltags[] = { {"speak", SSML_SPEAK}, {"voice", SSML_VOICE}, {"prosody", SSML_PROSODY}, {"say-as", SSML_SAYAS}, {"mark", SSML_MARK}, {"s", SSML_SENTENCE}, {"p", SSML_PARAGRAPH}, {"phoneme", SSML_PHONEME}, {"sub", SSML_SUB}, {"tts:style", SSML_STYLE}, {"audio", SSML_AUDIO}, {"emphasis", SSML_EMPHASIS}, {"break", SSML_BREAK}, {"metadata", SSML_IGNORE_TEXT}, {"br", HTML_BREAK}, {"li", HTML_BREAK}, {"dd", HTML_BREAK}, {"img", HTML_BREAK}, {"td", HTML_BREAK}, {"h1", SSML_PARAGRAPH}, {"h2", SSML_PARAGRAPH}, {"h3", SSML_PARAGRAPH}, {"h4", SSML_PARAGRAPH}, {"hr", SSML_PARAGRAPH}, {"script", SSML_IGNORE_TEXT}, {"style", SSML_IGNORE_TEXT}, {"font", HTML_NOSPACE}, {"b", HTML_NOSPACE}, {"i", HTML_NOSPACE}, {"strong", HTML_NOSPACE}, {"em", HTML_NOSPACE}, {"code", HTML_NOSPACE}, {NULL,0}}; static const char *VoiceFromStack() {//================================ // Use the voice properties from the SSML stack to choose a voice, and switch // to that voice if it's not the current voice int ix; const char *p; SSML_STACK *sp; const char *v_id; int voice_name_specified; int voice_found; espeak_VOICE voice_select; static char voice_name[40]; char language[40]; char buf[80]; strcpy(voice_name,ssml_stack[0].voice_name); strcpy(language,ssml_stack[0].language); voice_select.age = ssml_stack[0].voice_age; voice_select.gender = ssml_stack[0].voice_gender; voice_select.variant = ssml_stack[0].voice_variant_number; voice_select.identifier = NULL; for(ix=0; ixvoice_name[0] != 0) && (SelectVoiceByName(NULL,sp->voice_name) != NULL)) { voice_name_specified = 1; strcpy(voice_name, sp->voice_name); language[0] = 0; voice_select.gender = 0; voice_select.age = 0; voice_select.variant = 0; } if(sp->language[0] != 0) { strcpy(language, sp->language); // is this language provided by the base voice? p = base_voice.languages; while(*p++ != 0) { if(strcmp(p, language) == 0) { // yes, change the language to the main language of the base voice strcpy(language, &base_voice.languages[1]); break; } p += (strlen(p) + 1); } if(voice_name_specified == 0) voice_name[0] = 0; // forget a previous voice name if a language is specified } if(sp->voice_gender != 0) { voice_select.gender = sp->voice_gender; } if(sp->voice_age != 0) voice_select.age = sp->voice_age; if(sp->voice_variant_number != 0) voice_select.variant = sp->voice_variant_number; } voice_select.name = voice_name; voice_select.languages = language; v_id = SelectVoice(&voice_select, &voice_found); if(v_id == NULL) return("default"); if((strchr(v_id, '+') == NULL) && ((voice_select.gender == 0) || (voice_select.gender == base_voice.gender)) && (base_voice_variant_name[0] != 0)) { // a voice variant has not been selected, use the original voice variant sprintf(buf, "%s+%s", v_id, base_voice_variant_name); strncpy0(voice_name, buf, sizeof(voice_name)); return(voice_name); } return(v_id); } // end of VoiceFromStack static void ProcessParamStack(char *outbuf, int &outix) {//==================================================== // Set the speech parameters from the parameter stack int param; int ix; int value; char buf[20]; int new_parameters[N_SPEECH_PARAM]; static char cmd_letter[N_SPEECH_PARAM] = {0, 'S','A','P','R', 0, 'C', 0, 0, 0, 0, 0, 'F'}; // embedded command letters for(param=0; param= 0) new_parameters[param] = param_stack[ix].parameter[param]; } } for(param=0; paramtype = tag_type; for(ix=0; ixparameter[ix] = -1; } return(sp); } // end of PushParamStack static void PopParamStack(int tag_type, char *outbuf, int &outix) {//============================================================== // unwind the stack up to and including the previous tag of this type int ix; int top = 0; if(tag_type >= SSML_CLOSE) tag_type -= SSML_CLOSE; for(ix=0; ix 0) { n_param_stack = top; } ProcessParamStack(outbuf, outix); } // end of PopParamStack static wchar_t *GetSsmlAttribute(wchar_t *pw, const char *name) {//============================================================ // Gets the value string for an attribute. // Returns NULL if the attribute is not present int ix; static wchar_t empty[1] = {0}; while(*pw != 0) { if(iswspace(pw[-1])) { ix = 0; while(*pw == name[ix]) { pw++; ix++; } if(name[ix]==0) { // found the attribute, now get the value while(iswspace(*pw)) pw++; if(*pw == '=') pw++; while(iswspace(*pw)) pw++; if((*pw == '"') || (*pw == '\'')) // allow single-quotes ? return(pw+1); else return(empty); } } pw++; } return(NULL); } // end of GetSsmlAttribute static int attrcmp(const wchar_t *string1, const char *string2) {//============================================================ int ix; if(string1 == NULL) return(1); for(ix=0; (string1[ix] == string2[ix]) && (string1[ix] != 0); ix++) { } if(((string1[ix]=='"') || (string1[ix]=='\'')) && (string2[ix]==0)) return(0); return(1); } static int attrlookup(const wchar_t *string1, const MNEM_TAB *mtab) {//================================================================ int ix; for(ix=0; mtab[ix].mnem != NULL; ix++) { if(attrcmp(string1,mtab[ix].mnem) == 0) return(mtab[ix].value); } return(mtab[ix].value); } static int attrnumber(const wchar_t *pw, int default_value, int type) {//================================================================== int value = 0; if((pw == NULL) || !isdigit(*pw)) return(default_value); while(isdigit(*pw)) { value = value*10 + *pw++ - '0'; } if((type==1) && (towlower(*pw)=='s')) { // time: seconds rather than ms value *= 1000; } return(value); } // end of attrnumber static int attrcopy_utf8(char *buf, const wchar_t *pw, int len) {//============================================================ // Convert attribute string into utf8, write to buf, and return its utf8 length unsigned int c; int ix = 0; int n; int prev_c = 0; if(pw != NULL) { while((ix < (len-4)) && ((c = *pw++) != 0)) { if((c=='"') && (prev_c != '\\')) break; // " indicates end of attribute, unless preceded by backstroke n = utf8_out(c,&buf[ix]); ix += n; prev_c = c; } } buf[ix] = 0; return(ix); } // end of attrcopy_utf8 static int attr_prosody_value(int param_type, const wchar_t *pw, int *value_out) {//============================================================================= int sign = 0; wchar_t *tail; double value; while(iswspace(*pw)) pw++; if(*pw == '+') { pw++; sign = 1; } if(*pw == '-') { pw++; sign = -1; } value = (double)wcstod(pw,&tail); if(tail == pw) { // failed to find a number, return 100% *value_out = 100; return(2); } if(*tail == '%') { if(sign != 0) value = 100 + (sign * value); *value_out = (int)value; return(2); // percentage } if((tail[0]=='s') && (tail[1]=='t')) { double x; // convert from semitones to a frequency percentage x = pow(double(2.0),double((value*sign)/12)) * 100; *value_out = (int)x; return(2); // percentage } if(param_type == espeakRATE) { if(sign == 0) *value_out = (int)(value * 100); else *value_out = 100 + (int)(sign * value * 100); return(2); // percentage } *value_out = (int)value; return(sign); // -1, 0, or 1 } // end of attr_prosody_value int AddNameData(const char *name, int wide) {//======================================== // Add the name to the namedata and return its position // (Used by the Windows SAPI wrapper) int ix; int len; void *vp; if(wide) { len = (wcslen((const wchar_t *)name)+1)*sizeof(wchar_t); n_namedata = (n_namedata + sizeof(wchar_t) - 1) % sizeof(wchar_t); // round to wchar_t boundary } else { len = strlen(name)+1; } if(namedata_ix+len >= n_namedata) { // allocate more space for marker names if((vp = realloc(namedata, namedata_ix+len + 1000)) == NULL) return(-1); // failed to allocate, original data is unchanged but ignore this new name // !!! Bug?? If the allocated data shifts position, then pointers given to user application will be invalid namedata = (char *)vp; n_namedata = namedata_ix+len + 1000; } memcpy(&namedata[ix = namedata_ix],name,len); namedata_ix += len; return(ix); } // end of AddNameData void SetVoiceStack(espeak_VOICE *v, const char *variant_name) {//========================================================== SSML_STACK *sp; sp = &ssml_stack[0]; if(v == NULL) { memset(sp,0,sizeof(ssml_stack[0])); return; } if(v->languages != NULL) strcpy(sp->language,v->languages); if(v->name != NULL) strncpy0(sp->voice_name, v->name, sizeof(sp->voice_name)); sp->voice_variant_number = v->variant; sp->voice_age = v->age; sp->voice_gender = v->gender; if(memcmp(variant_name, "!v", 2) == 0) variant_name += 3;// strip variant directory name, !v plus PATHSEP strncpy0(base_voice_variant_name, variant_name, sizeof(base_voice_variant_name)); memcpy(&base_voice, ¤t_voice_selected, sizeof(base_voice)); } static int GetVoiceAttributes(wchar_t *pw, int tag_type) {//===================================================== // Determines whether voice attribute are specified in this tag, and if so, whether this means // a voice change. // If it's a closing tag, delete the top frame of the stack and determine whether this implies // a voice change. // Returns CLAUSE_BIT_VOICE if there is a voice change wchar_t *lang; wchar_t *gender; wchar_t *name; wchar_t *age; wchar_t *variant; const char *new_voice_id; SSML_STACK *ssml_sp; static const MNEM_TAB mnem_gender[] = { {"male", 1}, {"female", 2}, {"neutral", 3}, {NULL, 0}}; if(tag_type & SSML_CLOSE) { // delete a stack frame if(n_ssml_stack > 1) { n_ssml_stack--; } } else { // add a stack frame if any voice details are specified lang = GetSsmlAttribute(pw,"xml:lang"); if(tag_type != SSML_VOICE) { // only expect an xml:lang attribute name = NULL; variant = NULL; age = NULL; gender = NULL; } else { name = GetSsmlAttribute(pw,"name"); variant = GetSsmlAttribute(pw,"variant"); age = GetSsmlAttribute(pw,"age"); gender = GetSsmlAttribute(pw,"gender"); } if((tag_type != SSML_VOICE) && (lang==NULL)) return(0); // or

without language spec, nothing to do ssml_sp = &ssml_stack[n_ssml_stack++]; attrcopy_utf8(ssml_sp->language,lang,sizeof(ssml_sp->language)); attrcopy_utf8(ssml_sp->voice_name,name,sizeof(ssml_sp->voice_name)); ssml_sp->voice_variant_number = attrnumber(variant,1,0)-1; ssml_sp->voice_age = attrnumber(age,0,0); ssml_sp->voice_gender = attrlookup(gender,mnem_gender); ssml_sp->tag_type = tag_type; } new_voice_id = VoiceFromStack(); if(strcmp(new_voice_id,current_voice_id) != 0) { // add an embedded command to change the voice strcpy(current_voice_id,new_voice_id); return(CLAUSE_BIT_VOICE); // change of voice } return(0); } // end of GetVoiceAttributes static void SetProsodyParameter(int param_type, wchar_t *attr1, PARAM_STACK *sp) {//============================================================================= int value; int sign; static const MNEM_TAB mnem_volume[] = { {"default",100}, {"silent",0}, {"x-soft",30}, {"soft",65}, {"medium",100}, {"loud",150}, {"x-loud",230}, {NULL, -1}}; static const MNEM_TAB mnem_rate[] = { {"default",100}, {"x-slow",60}, {"slow",80}, {"medium",100}, {"fast",125}, {"x-fast",160}, {NULL, -1}}; static const MNEM_TAB mnem_pitch[] = { {"default",100}, {"x-low",70}, {"low",85}, {"medium",100}, {"high",110}, {"x-high",120}, {NULL, -1}}; static const MNEM_TAB mnem_range[] = { {"default",100}, {"x-low",20}, {"low",50}, {"medium",100}, {"high",140}, {"x-high",180}, {NULL, -1}}; static const MNEM_TAB *mnem_tabs[5] = { NULL, mnem_rate, mnem_volume, mnem_pitch, mnem_range }; if((value = attrlookup(attr1,mnem_tabs[param_type])) >= 0) { // mnemonic specifies a value as a percentage of the base pitch/range/rate/volume sp->parameter[param_type] = (param_stack[0].parameter[param_type] * value)/100; } else { sign = attr_prosody_value(param_type,attr1,&value); if(sign == 0) sp->parameter[param_type] = value; // absolute value in Hz else if(sign == 2) { // change specified as percentage or in semitones sp->parameter[param_type] = (speech_parameters[param_type] * value)/100; } else { // change specified as plus or minus Hz sp->parameter[param_type] = speech_parameters[param_type] + (value*sign); } } } // end of SetProsodyParemeter static int ReplaceKeyName(char *outbuf, int index, int &outix) {//=========================================================== // Replace some key-names by single characters, so they can be pronounced in different languages MNEM_TAB keynames[] = { {"space ",0xe020}, {"tab ", 0xe009}, {"underscore ", 0xe05f}, {"double-quote ", '"'}, {NULL, 0}}; int ix; int letter; char *p; p = &outbuf[index]; if((letter = LookupMnem(keynames, p)) != 0) { ix = utf8_out(letter, p); outix = index + ix; return(letter); } return(0); } static int ProcessSsmlTag(wchar_t *xml_buf, char *outbuf, int &outix, int n_outbuf, int self_closing) {//================================================================================================== // xml_buf is the tag and attributes with a zero terminator in place of the original '>' // returns a clause terminator value. unsigned int ix; int index; int c; int tag_type; int value; int value2; int value3; int voice_change_flag; wchar_t *px; wchar_t *attr1; wchar_t *attr2; wchar_t *attr3; int terminator; char *uri; int param_type; char tag_name[40]; char buf[80]; PARAM_STACK *sp; SSML_STACK *ssml_sp; static const MNEM_TAB mnem_punct[] = { {"none", 1}, {"all", 2}, {"some", 3}, {NULL, -1}}; static const MNEM_TAB mnem_capitals[] = { {"no", 0}, {"spelling", 2}, {"icon", 1}, {"pitch", 20}, // this is the amount by which to raise the pitch {NULL, -1}}; static const MNEM_TAB mnem_interpret_as[] = { {"characters",SAYAS_CHARS}, {"tts:char",SAYAS_SINGLE_CHARS}, {"tts:key",SAYAS_KEY}, {"tts:digits",SAYAS_DIGITS}, {"telephone",SAYAS_DIGITS1}, {NULL, -1}}; static const MNEM_TAB mnem_sayas_format[] = { {"glyphs",1}, {NULL, -1}}; static const MNEM_TAB mnem_break[] = { {"none",0}, {"x-weak",1}, {"weak",2}, {"medium",3}, {"strong",4}, {"x-strong",5}, {NULL,-1}}; static const MNEM_TAB mnem_emphasis[] = { {"none",1}, {"reduced",2}, {"moderate",3}, {"strong",4}, {"x-strong",5}, {NULL,-1}}; static const char *prosody_attr[5] = { NULL, "rate", "volume", "pitch", "range" }; for(ix=0; ix<(sizeof(tag_name)-1); ix++) { if(((c = xml_buf[ix]) == 0) || iswspace(c)) break; tag_name[ix] = tolower((char)c); } tag_name[ix] = 0; px = &xml_buf[ix]; // the tag's attributes if(tag_name[0] == '/') { // closing tag if((tag_type = LookupMnem(ssmltags,&tag_name[1])) != HTML_NOSPACE) { outbuf[outix++] = ' '; } tag_type += SSML_CLOSE; } else { if((tag_type = LookupMnem(ssmltags,tag_name)) != HTML_NOSPACE) { // separate SSML tags from the previous word (but not HMTL tags such as which can occur inside a word) outbuf[outix++] = ' '; } if(self_closing && ignore_if_self_closing[tag_type]) return(0); } voice_change_flag = 0; terminator = CLAUSE_NONE; ssml_sp = &ssml_stack[n_ssml_stack-1]; switch(tag_type) { case SSML_STYLE: sp = PushParamStack(tag_type); attr1 = GetSsmlAttribute(px,"field"); attr2 = GetSsmlAttribute(px,"mode"); if(attrcmp(attr1,"punctuation")==0) { value = attrlookup(attr2,mnem_punct); sp->parameter[espeakPUNCTUATION] = value; } else if(attrcmp(attr1,"capital_letters")==0) { value = attrlookup(attr2,mnem_capitals); sp->parameter[espeakCAPITALS] = value; } ProcessParamStack(outbuf, outix); break; case SSML_PROSODY: sp = PushParamStack(tag_type); // look for attributes: rate, volume, pitch, range for(param_type=espeakRATE; param_type <= espeakRANGE; param_type++) { if((attr1 = GetSsmlAttribute(px,prosody_attr[param_type])) != NULL) { SetProsodyParameter(param_type, attr1, sp); } } ProcessParamStack(outbuf, outix); break; case SSML_EMPHASIS: sp = PushParamStack(tag_type); value = 3; // default is "moderate" if((attr1 = GetSsmlAttribute(px,"level")) != NULL) { value = attrlookup(attr1,mnem_emphasis); } if(translator->langopts.tone_language == 1) { static unsigned char emphasis_to_pitch_range[] = {50,50,40,70,90,100}; static unsigned char emphasis_to_volume[] = {100,100,70,110,135,150}; // tone language (eg.Chinese) do emphasis by increasing the pitch range. sp->parameter[espeakRANGE] = emphasis_to_pitch_range[value]; sp->parameter[espeakVOLUME] = emphasis_to_volume[value]; } else { static unsigned char emphasis_to_volume2[] = {100,100,75,100,120,150}; sp->parameter[espeakVOLUME] = emphasis_to_volume2[value]; sp->parameter[espeakEMPHASIS] = value; } ProcessParamStack(outbuf, outix); break; case SSML_STYLE + SSML_CLOSE: case SSML_PROSODY + SSML_CLOSE: case SSML_EMPHASIS + SSML_CLOSE: PopParamStack(tag_type, outbuf, outix); break; case SSML_SAYAS: attr1 = GetSsmlAttribute(px,"interpret-as"); attr2 = GetSsmlAttribute(px,"format"); attr3 = GetSsmlAttribute(px,"detail"); value = attrlookup(attr1,mnem_interpret_as); value2 = attrlookup(attr2,mnem_sayas_format); if(value2 == 1) value = SAYAS_GLYPHS; value3 = attrnumber(attr3,0,0); if(value == SAYAS_DIGITS) { if(value3 <= 1) value = SAYAS_DIGITS1; else value = SAYAS_DIGITS + value3; } sprintf(buf,"%c%dY",CTRL_EMBEDDED,value); strcpy(&outbuf[outix],buf); outix += strlen(buf); sayas_start = outix; sayas_mode = value; // punctuation doesn't end clause during SAY-AS break; case SSML_SAYAS + SSML_CLOSE: if(sayas_mode == SAYAS_KEY) { outbuf[outix] = 0; ReplaceKeyName(outbuf, sayas_start, outix); } outbuf[outix++] = CTRL_EMBEDDED; outbuf[outix++] = 'Y'; sayas_mode = 0; break; case SSML_SUB: if((attr1 = GetSsmlAttribute(px,"alias")) != NULL) { // use the alias rather than the text ignore_text = 1; outix += attrcopy_utf8(&outbuf[outix],attr1,n_outbuf-outix); } break; case SSML_IGNORE_TEXT: ignore_text = 1; break; case SSML_SUB + SSML_CLOSE: case SSML_IGNORE_TEXT + SSML_CLOSE: ignore_text = 0; break; case SSML_MARK: if((attr1 = GetSsmlAttribute(px,"name")) != NULL) { // add name to circular buffer of marker names attrcopy_utf8(buf,attr1,sizeof(buf)); if(strcmp(skip_marker,buf)==0) { // This is the marker we are waiting for before starting to speak clear_skipping_text = 1; skip_marker[0] = 0; return(CLAUSE_NONE); } if((index = AddNameData(buf,0)) >= 0) { sprintf(buf,"%c%dM",CTRL_EMBEDDED,index); strcpy(&outbuf[outix],buf); outix += strlen(buf); } } break; case SSML_AUDIO: sp = PushParamStack(tag_type); if((attr1 = GetSsmlAttribute(px,"src")) != NULL) { char fname[256]; attrcopy_utf8(buf,attr1,sizeof(buf)); if(uri_callback == NULL) { if((xmlbase != NULL) && (buf[0] != '/')) { sprintf(fname,"%s/%s",xmlbase,buf); index = LoadSoundFile2(fname); } else { index = LoadSoundFile2(buf); } if(index >= 0) { sprintf(buf,"%c%dI",CTRL_EMBEDDED,index); strcpy(&outbuf[outix],buf); outix += strlen(buf); sp->parameter[espeakSILENCE] = 1; } } else { if((index = AddNameData(buf,0)) >= 0) { uri = &namedata[index]; if(uri_callback(1,uri,xmlbase) == 0) { sprintf(buf,"%c%dU",CTRL_EMBEDDED,index); strcpy(&outbuf[outix],buf); outix += strlen(buf); sp->parameter[espeakSILENCE] = 1; } } } } ProcessParamStack(outbuf, outix); if(self_closing) PopParamStack(tag_type, outbuf, outix); else audio_text = 1; return(CLAUSE_NONE); case SSML_AUDIO + SSML_CLOSE: PopParamStack(tag_type, outbuf, outix); audio_text = 0; return(CLAUSE_NONE); case SSML_BREAK: value = 21; terminator = CLAUSE_NONE; if((attr1 = GetSsmlAttribute(px,"strength")) != NULL) { static int break_value[6] = {0,7,14,21,40,80}; // *10mS value = attrlookup(attr1,mnem_break); if(value < 3) { // adjust prepause on the following word sprintf(&outbuf[outix],"%c%dB",CTRL_EMBEDDED,value); outix += 3; terminator = 0; } value = break_value[value]; } if((attr2 = GetSsmlAttribute(px,"time")) != NULL) { value = (attrnumber(attr2,0,1) * 25) / speed.pause_factor; // compensate for speaking speed to keep constant pause length if(terminator == 0) terminator = CLAUSE_NONE; } if(terminator) { if(value > 0xfff) value = 0xfff; return(terminator + value); } break; case SSML_SPEAK: if((attr1 = GetSsmlAttribute(px,"xml:base")) != NULL) { attrcopy_utf8(buf,attr1,sizeof(buf)); if((index = AddNameData(buf,0)) >= 0) { xmlbase = &namedata[index]; } } if(GetVoiceAttributes(px, tag_type) == 0) return(0); // no voice change return(CLAUSE_VOICE); case SSML_VOICE: if(GetVoiceAttributes(px, tag_type) == 0) return(0); // no voice change return(CLAUSE_VOICE); case SSML_SPEAK + SSML_CLOSE: // unwind stack until the previous or tag while((n_ssml_stack > 1) && (ssml_stack[n_ssml_stack-1].tag_type != SSML_SPEAK)) { n_ssml_stack--; } return(CLAUSE_PERIOD + GetVoiceAttributes(px, tag_type)); case SSML_VOICE + SSML_CLOSE: // unwind stack until the previous or tag while((n_ssml_stack > 1) && (ssml_stack[n_ssml_stack-1].tag_type != SSML_VOICE)) { n_ssml_stack--; } terminator=0; // ?? Sentence intonation, but no pause ?? return(terminator + GetVoiceAttributes(px, tag_type)); case HTML_BREAK: case HTML_BREAK + SSML_CLOSE: return(CLAUSE_COLON); case SSML_SENTENCE: if(ssml_sp->tag_type == SSML_SENTENCE) { // new sentence implies end-of-sentence voice_change_flag = GetVoiceAttributes(px, SSML_SENTENCE+SSML_CLOSE); } voice_change_flag |= GetVoiceAttributes(px, tag_type); return(CLAUSE_PARAGRAPH + voice_change_flag); case SSML_PARAGRAPH: if(ssml_sp->tag_type == SSML_SENTENCE) { // new paragraph implies end-of-sentence or end-of-paragraph voice_change_flag = GetVoiceAttributes(px, SSML_SENTENCE+SSML_CLOSE); } if(ssml_sp->tag_type == SSML_PARAGRAPH) { // new paragraph implies end-of-sentence or end-of-paragraph voice_change_flag |= GetVoiceAttributes(px, SSML_PARAGRAPH+SSML_CLOSE); } voice_change_flag |= GetVoiceAttributes(px, tag_type); return(CLAUSE_PARAGRAPH + voice_change_flag); case SSML_SENTENCE + SSML_CLOSE: if(ssml_sp->tag_type == SSML_SENTENCE) { // end of a sentence which specified a language voice_change_flag = GetVoiceAttributes(px, tag_type); } return(CLAUSE_PERIOD + voice_change_flag); case SSML_PARAGRAPH + SSML_CLOSE: if((ssml_sp->tag_type == SSML_SENTENCE) || (ssml_sp->tag_type == SSML_PARAGRAPH)) { // End of a paragraph which specified a language. // (End-of-paragraph also implies end-of-sentence) return(GetVoiceAttributes(px, tag_type) + CLAUSE_PARAGRAPH); } return(CLAUSE_PARAGRAPH); } return(0); } // end of ProcessSsmlTag static void RemoveChar(char *p) {//======================= // Replace a UTF-8 character by spaces int c; memset(p, ' ', utf8_in(&c, p)); } // end of RemoveChar static MNEM_TAB xml_char_mnemonics[] = { {"gt",'>'}, {"lt", 0xe000 + '<'}, // private usage area, to avoid confusion with XML tag {"amp", '&'}, {"quot", '"'}, {"nbsp", ' '}, {"apos", '\''}, {NULL,-1}}; int ReadClause(Translator *tr, FILE *f_in, char *buf, short *charix, int *charix_top, int n_buf, int *tone_type, char *voice_change) {//================================================================================================================================= /* Find the end of the current clause. Write the clause into buf returns: clause type (bits 0-7: pause x10mS, bits 8-11 intonation type) Also checks for blank line (paragraph) as end-of-clause indicator. Does not end clause for: punctuation immediately followed by alphanumeric eg. 1.23 !Speak :path repeated punctuation, eg. ... !!! */ int c1=' '; // current character int c2; // next character int cprev=' '; // previous character int cprev2=' '; int c_next; int parag; int ix = 0; int j; int nl_count; int linelength = 0; int phoneme_mode = 0; int n_xml_buf; int terminator; int punct; int found; int any_alnum = 0; int self_closing; int punct_data = 0; int is_end_clause; int announced_punctuation = 0; int stressed_word = 0; int end_clause_after_tag = 0; int end_clause_index = 0; wchar_t xml_buf[N_XML_BUF+1]; #define N_XML_BUF2 20 char xml_buf2[N_XML_BUF2+2]; // for & and & sequences static char ungot_string[N_XML_BUF2+4]; static int ungot_string_ix = -1; if(clear_skipping_text) { skipping_text = 0; clear_skipping_text = 0; } tr->phonemes_repeat_count = 0; tr->clause_upper_count = 0; tr->clause_lower_count = 0; end_of_input = 0; *tone_type = 0; *voice_change = 0; f_input = f_in; // for GetC etc if(ungot_word != NULL) { strcpy(buf,ungot_word); ix += strlen(ungot_word); ungot_word = NULL; } if(ungot_char2 != 0) { c2 = ungot_char2; } else { c2 = GetC(); } while(!Eof() || (ungot_char != 0) || (ungot_char2 != 0) || (ungot_string_ix >= 0)) { if(!iswalnum(c1)) { if((end_character_position > 0) && (count_characters > end_character_position)) { end_of_input = 1; return(CLAUSE_EOF); } if((skip_characters > 0) && (count_characters > skip_characters)) { // reached the specified start position // don't break a word clear_skipping_text = 1; skip_characters = 0; UngetC(c2); return(CLAUSE_NONE); } } cprev2 = cprev; cprev = c1; c1 = c2; if(ungot_string_ix >= 0) { if(ungot_string[ungot_string_ix] == 0) ungot_string_ix = -1; } if((ungot_string_ix == 0) && (ungot_char2 == 0)) { c1 = ungot_string[ungot_string_ix++]; } if(ungot_string_ix >= 0) { c2 = ungot_string[ungot_string_ix++]; } else { c2 = GetC(); if(Eof()) { c2 = ' '; } } ungot_char2 = 0; if((option_ssml) && (phoneme_mode==0)) { if((ssml_ignore_l_angle != '&') && (c1 == '&') && ((c2=='#') || ((c2 >= 'a') && (c2 <= 'z')))) { n_xml_buf = 0; c1 = c2; while(!Eof() && (iswalnum(c1) || (c1=='#')) && (n_xml_buf < N_XML_BUF2)) { xml_buf2[n_xml_buf++] = c1; c1 = GetC(); } xml_buf2[n_xml_buf] = 0; c2 = GetC(); sprintf(ungot_string,"%s%c%c",&xml_buf2[0],c1,c2); if(c1 == ';') { if(xml_buf2[0] == '#') { // character code number if(xml_buf2[1] == 'x') found = sscanf(&xml_buf2[2],"%x",(unsigned int *)(&c1)); else found = sscanf(&xml_buf2[1],"%d",&c1); } else { if((found = LookupMnem(xml_char_mnemonics,xml_buf2)) != -1) { c1 = found; if(c2 == 0) c2 = ' '; } } } else { found = -1; } if(found <= 0) { ungot_string_ix = 0; c1 = '&'; c2 = ' '; } if((c1 <= 0x20) && ((sayas_mode == SAYAS_SINGLE_CHARS) || (sayas_mode == SAYAS_KEY))) { c1 += 0xe000; // move into unicode private usage area } } else if((c1 == '<') && (ssml_ignore_l_angle != '<')) { if(c2 == '!') { // a comment, ignore until closing '<' while(!Eof() && (c1 != '>')) { c1 = GetC(); } c2 = ' '; } else if((c2 == '/') || iswalpha(c2)) { // check for space in the output buffer for embedded commands produced by the SSML tag if(ix > (n_buf - 20)) { // Perhaps not enough room, end the clause before the SSML tag UngetC(c2); ungot_char2 = c1; buf[ix] = ' '; buf[ix+1] = 0; return(CLAUSE_NONE); } // SSML Tag n_xml_buf = 0; c1 = c2; while(!Eof() && (c1 != '>') && (n_xml_buf < N_XML_BUF)) { xml_buf[n_xml_buf++] = c1; c1 = GetC(); } xml_buf[n_xml_buf] = 0; c2 = ' '; self_closing = 0; if(xml_buf[n_xml_buf-1] == '/') { // a self-closing tag xml_buf[n_xml_buf-1] = ' '; self_closing = 1; } terminator = ProcessSsmlTag(xml_buf,buf,ix,n_buf,self_closing); if(terminator != 0) { if(end_clause_after_tag) ix = end_clause_index; buf[ix] = ' '; buf[ix++] = 0; if(terminator & CLAUSE_BIT_VOICE) { strcpy(voice_change, current_voice_id); } return(terminator); } c1 = ' '; c2 = GetC(); continue; } } } ssml_ignore_l_angle=0; if(ignore_text) continue; if((c2=='\n') && (option_linelength == -1)) { // single-line mode, return immediately on NL if((punct = lookupwchar(punct_chars,c1)) == 0) { charix[ix] = count_characters - clause_start_char; *charix_top = ix; ix += utf8_out(c1,&buf[ix]); terminator = CLAUSE_PERIOD; // line doesn't end in punctuation, assume period } else { terminator = punct_attributes[punct]; } buf[ix] = ' '; buf[ix+1] = 0; return(terminator); } if((c1 == CTRL_EMBEDDED) || (c1 == ctrl_embedded)) { // an embedded command. If it's a voice change, end the clause if(c2 == 'V') { buf[ix++] = 0; // end the clause at this point while(!iswspace(c1 = GetC()) && !Eof() && (ix < (n_buf-1))) buf[ix++] = c1; // add voice name to end of buffer, after the text buf[ix++] = 0; return(CLAUSE_VOICE); } else if(c2 == 'B') { // set the punctuation option from an embedded command // B0 B1 B strcpy(&buf[ix]," "); ix += 3; if((c2 = GetC()) == '0') option_punctuation = 0; else { option_punctuation = 1; option_punctlist[0] = 0; if(c2 != '1') { // a list of punctuation characters to be spoken, terminated by space j = 0; while(!iswspace(c2) && !Eof()) { option_punctlist[j++] = c2; c2 = GetC(); buf[ix++] = ' '; } option_punctlist[j] = 0; // terminate punctuation list option_punctuation = 2; } } c2 = GetC(); continue; } } linelength++; if(iswalnum(c1)) any_alnum = 1; else { if(stressed_word) { stressed_word = 0; c1 = CHAR_EMPHASIS; // indicate this word is stressed UngetC(c2); c2 = ' '; } if(lookupwchar(chars_ignore,c1)) { // ignore this character (eg. zero-width-non-joiner U+200C) continue; } if(c1 == 0xf0b) c1 = ' '; // Tibet inter-syllabic mark, ?? replace by space ?? if(iswspace(c1)) { char *p_word; if(tr->translator_name == 0x6a626f) { // language jbo : lojban // treat "i" or ".i" as end-of-sentence p_word = &buf[ix-1]; if(p_word[0] == 'i') { if(p_word[-1] == '.') p_word--; if(p_word[-1] == ' ') { ungot_word = "i "; UngetC(c2); p_word[0] = 0; return(CLAUSE_PERIOD); } } } } if(c1 == 0xd4d) { // Malayalam virama, check if next character is Zero-width-joiner if(c2 == 0x200d) { c1 = 0xd4e; // use this unofficial code for chillu-virama } } } if(iswupper(c1)) { tr->clause_upper_count++; if((option_capitals == 2) && (sayas_mode == 0) && !iswupper(cprev)) { char text_buf[40]; char text_buf2[30]; if(LookupSpecial(tr, "_cap", text_buf2) != NULL) { sprintf(text_buf,"%s",text_buf2); j = strlen(text_buf); if((ix + j) < n_buf) { strcpy(&buf[ix],text_buf); ix += j; } } } } else if(iswalpha(c1)) tr->clause_lower_count++; if(option_phoneme_input) { if(phoneme_mode > 0) phoneme_mode--; else if((c1 == '[') && (c2 == '[')) phoneme_mode = -1; // input is phoneme mnemonics, so don't look for punctuation else if((c1 == ']') && (c2 == ']')) phoneme_mode = 2; // set phoneme_mode to zero after the next two characters } if(c1 == '\n') { parag = 0; // count consecutive newlines, ignoring other spaces while(!Eof() && iswspace(c2)) { if(c2 == '\n') parag++; c2 = GetC(); } if(parag > 0) { // 2nd newline, assume paragraph UngetC(c2); if(end_clause_after_tag) { RemoveChar(&buf[end_clause_index]); // delete clause-end punctiation } buf[ix] = ' '; buf[ix+1] = 0; if(parag > 3) parag = 3; if(option_ssml) parag=1; return((CLAUSE_PARAGRAPH-30) + 30*parag); // several blank lines, longer pause } if(linelength <= option_linelength) { // treat lines shorter than a specified length as end-of-clause UngetC(c2); buf[ix] = ' '; buf[ix+1] = 0; return(CLAUSE_COLON); } linelength = 0; } announced_punctuation = 0; if((phoneme_mode==0) && (sayas_mode==0)) { is_end_clause = 0; if(end_clause_after_tag) { // Because of an xml tag, we are waiting for the // next non-blank character to decide whether to end the clause // i.e. is dot followed by an upper-case letter? if(!iswspace(c1)) { if(!IsAlpha(c1) || !iswlower(c1)) // if(iswdigit(c1) || (IsAlpha(c1) && !iswlower(c1))) { UngetC(c2); ungot_char2 = c1; buf[end_clause_index] = ' '; // delete the end-clause punctuation buf[end_clause_index+1] = 0; return(end_clause_after_tag); } end_clause_after_tag = 0; } } if((c1 == '.') && (c2 == '.')) { while((c_next = GetC()) == '.') { // 3 or more dots, replace by elipsis c1 = 0x2026; c2 = ' '; } if(c1 == 0x2026) c2 = c_next; else UngetC(c_next); } punct_data = 0; if((punct = lookupwchar(punct_chars,c1)) != 0) { punct_data = punct_attributes[punct]; if(punct_data & PUNCT_IN_WORD) { // Armenian punctuation inside a word stressed_word = 1; *tone_type = punct_data >> 12 & 0xf; // override the end-of-sentence type continue; } if((iswspace(c2) || (punct_data & 0x8000) || IsBracket(c2) || (c2=='?') || Eof() || (c2 == ctrl_embedded))) // don't check for '-' because it prevents recognizing ':-)' // if((iswspace(c2) || (punct_data & 0x8000) || IsBracket(c2) || (c2=='?') || (c2=='-') || Eof())) { // note: (c2='?') is for when a smart-quote has been replaced by '?' is_end_clause = 1; } } // don't announce punctuation for the alternative text inside inside if(c1 == 0xe000+'<') c1 = '<'; if(option_punctuation && iswpunct(c1) && (audio_text == 0)) { // option is set to explicitly speak punctuation characters // if a list of allowed punctuation has been set up, check whether the character is in it if((option_punctuation == 1) || (wcschr(option_punctlist,c1) != NULL)) { tr->phonemes_repeat_count = 0; if((terminator = AnnouncePunctuation(tr, c1, &c2, buf, &ix, is_end_clause)) >= 0) return(terminator); announced_punctuation = c1; } } if((punct_data & PUNCT_SAY_NAME) && (announced_punctuation == 0)) { // used for elipsis (and 3 dots) if a pronunciation for elipsis is given in *_list char *p2; p2 = &buf[ix]; sprintf(p2,"%s",LookupCharName(tr, c1, 1)); if(p2[0] != 0) { ix += strlen(p2); announced_punctuation = c1; punct_data = punct_data & ~CLAUSE_BITS_INTONATION; // change intonation type to 0 (full-stop) } } if(is_end_clause) { nl_count = 0; c_next = c2; if(iswspace(c_next)) { while(!Eof() && iswspace(c_next)) { if(c_next == '\n') nl_count++; c_next = GetC(); // skip past space(s) } } if((c1 == '.') && (nl_count < 2)) { punct_data |= CLAUSE_DOT; } if(nl_count==0) { if((c1 == ',') && (cprev == '.') && (tr->translator_name == L('h','u')) && iswdigit(cprev2) && (iswdigit(c_next) || (iswlower(c_next)))) { // lang=hu, fix for ordinal numbers, eg: "december 2., szerda", ignore ',' after ordinal number c1 = CHAR_COMMA_BREAK; is_end_clause = 0; } if(c1 == '.') { if((tr->langopts.numbers & NUM_ORDINAL_DOT) && (iswdigit(cprev) || (IsRomanU(cprev) && (IsRomanU(cprev2) || iswspace(cprev2))))) // lang=hu { // dot after a number indicates an ordinal number if(!iswdigit(cprev)) { is_end_clause = 0; // Roman number followed by dot } else { if (iswlower(c_next) || (c_next=='-')) // hyphen is needed for lang-hu (eg. 2.-kal) is_end_clause = 0; // only if followed by lower-case, (or if there is a XML tag) } } else if(c_next == '\'') { is_end_clause = 0; // eg. u.s.a.'s } if(iswlower(c_next)) { // next word has no capital letter, this dot is probably from an abbreviation // c1 = ' '; is_end_clause = 0; } if(any_alnum==0) { // no letters or digits yet, so probably not a sentence terminator // Here, dot is followed by space or bracket c1 = ' '; is_end_clause = 0; } } else { if(any_alnum==0) { // no letters or digits yet, so probably not a sentence terminator is_end_clause = 0; } } if(is_end_clause && (c1 == '.') && (c_next == '<') && option_ssml) { // wait until after the end of the xml tag, then look for upper-case letter is_end_clause = 0; end_clause_index = ix; end_clause_after_tag = punct_data; } } if(is_end_clause) { UngetC(c_next); buf[ix] = ' '; buf[ix+1] = 0; if(iswdigit(cprev) && !IsAlpha(c_next)) // ???? { punct_data &= ~CLAUSE_DOT; } if(nl_count > 1) { if((punct_data == CLAUSE_QUESTION) || (punct_data == CLAUSE_EXCLAMATION)) return(punct_data + 35); // with a longer pause return(CLAUSE_PARAGRAPH); } return(punct_data); // only recognise punctuation if followed by a blank or bracket/quote } else { if(!Eof()) { if(iswspace(c2)) UngetC(c_next); } } } } if(speech_parameters[espeakSILENCE]==1) continue; if(c1 == announced_punctuation) { // This character has already been announced, so delete it so that it isn't spoken a second time. // Unless it's a hyphen or apostrophe (which is used by TranslateClause() ) if(IsBracket(c1)) { c1 = 0xe000 + '('; // Unicode private useage area. So TranslateRules() knows the bracket name has been spoken } else if(c1 != '-') { c1 = ' '; } } j = ix+1; if(c1 == 0xe000 + '<') c1 = '<'; ix += utf8_out(c1,&buf[ix]); // buf[ix++] = c1; if(!iswspace(c1) && !IsBracket(c1)) { charix[ix] = count_characters - clause_start_char; while(j < ix) charix[j++] = -1; // subsequent bytes of a multibyte character } *charix_top = ix; if(((ix > (n_buf-75)) && !IsAlpha(c1) && !iswdigit(c1)) || (ix >= (n_buf-4))) { // clause too long, getting near end of buffer, so break here // try to break at a word boundary (unless we actually reach the end of buffer). // (n_buf-4) is to allow for 3 bytes of multibyte character plus terminator. buf[ix] = ' '; buf[ix+1] = 0; UngetC(c2); return(CLAUSE_NONE); } } if(stressed_word) { ix += utf8_out(CHAR_EMPHASIS, &buf[ix]); } if(end_clause_after_tag) { RemoveChar(&buf[end_clause_index]); // delete clause-end punctiation } buf[ix] = ' '; buf[ix+1] = 0; return(CLAUSE_EOF); // end of file } // end of ReadClause void InitNamedata(void) {//==================== namedata_ix = 0; if(namedata != NULL) { free(namedata); namedata = NULL; n_namedata = 0; } } void InitText2(void) {//================= int param; ungot_char = 0; ungot_char2 = 0; n_ssml_stack =1; n_param_stack = 1; ssml_stack[0].tag_type = 0; for(param=0; param. * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" #include "wave.h" const char *version_string = "1.46.14 22.Feb.12"; const int version_phdata = 0x014600; int option_device_number = -1; FILE *f_logespeak = NULL; int logging_type; // copy the current phoneme table into here int n_phoneme_tab; int current_phoneme_table; PHONEME_TAB *phoneme_tab[N_PHONEME_TAB]; unsigned char phoneme_tab_flags[N_PHONEME_TAB]; // bit 0: not inherited USHORT *phoneme_index=NULL; char *phondata_ptr=NULL; unsigned char *wavefile_data=NULL; static unsigned char *phoneme_tab_data = NULL; int n_phoneme_tables; PHONEME_TAB_LIST phoneme_tab_list[N_PHONEME_TABS]; int phoneme_tab_number = 0; int wavefile_ix; // a wavefile to play along with the synthesis int wavefile_amp; int wavefile_ix2; int wavefile_amp2; int seq_len_adjust; int vowel_transition[4]; int vowel_transition0; int vowel_transition1; int FormantTransition2(frameref_t *seq, int &n_frames, unsigned int data1, unsigned int data2, PHONEME_TAB *other_ph, int which); static char *ReadPhFile(void *ptr, const char *fname, int *size) {//============================================================= FILE *f_in; char *p; unsigned int length; char buf[sizeof(path_home)+40]; sprintf(buf,"%s%c%s",path_home,PATHSEP,fname); length = GetFileLength(buf); if((f_in = fopen(buf,"rb")) == NULL) { fprintf(stderr,"Can't read data file: '%s'\n",buf); return(NULL); } if(ptr != NULL) Free(ptr); if((p = Alloc(length)) == NULL) { fclose(f_in); return(NULL); } if(fread(p,1,length,f_in) != length) { fclose(f_in); return(NULL); } fclose(f_in); if(size != NULL) *size = length; return(p); } // end of ReadPhFile int LoadPhData() {//============= int ix; int n_phonemes; int version; int result = 1; int length; unsigned char *p; int *pw; #ifdef DATA_FROM_SOURCECODE_FILES long llength; phoneme_tab_data = (unsigned char *) FilesInMemory_getData (espeakdata_phons, L"phontab", &llength); phoneme_index = (USHORT *) FilesInMemory_getData (espeakdata_phons, L"phonindex", &llength); phondata_ptr = (char *) FilesInMemory_getData (espeakdata_phons, L"phondata", &llength); tunes = (TUNE *) FilesInMemory_getData (espeakdata_phons, L"intonations", &llength); length = llength; #else if((phoneme_tab_data = (unsigned char *)ReadPhFile((void *)(phoneme_tab_data),"phontab",NULL)) == NULL) return(-1); if((phoneme_index = (USHORT *)ReadPhFile((void *)(phoneme_index),"phonindex",NULL)) == NULL) return(-1); if((phondata_ptr = ReadPhFile((void *)(phondata_ptr),"phondata",NULL)) == NULL) return(-1); if((tunes = (TUNE *)ReadPhFile((void *)(tunes),"intonations",&length)) == NULL) return(-1); #endif wavefile_data = (unsigned char *)phondata_ptr; n_tunes = length / sizeof(TUNE); // read the version number from the first 4 bytes of phondata version = 0; for(ix=0; ix<4; ix++) { version += (wavefile_data[ix] << (ix*8)); } if(version != version_phdata) { result = version; } // set up phoneme tables p = phoneme_tab_data; n_phoneme_tables = p[0]; p+=4; for(ix=0; ix= n_phoneme_tables) phoneme_tab_number = 0; return(result); } // end of LoadPhData void FreePhData(void) {//================== #ifndef DATA_FROM_SOURCECODE_FILES Free(phoneme_tab_data); Free(phoneme_index); Free(phondata_ptr); Free(tunes); #endif phoneme_tab_data=NULL; phoneme_index=NULL; phondata_ptr=NULL; tunes=NULL; } int PhonemeCode(unsigned int mnem) {//=============================== int ix; for(ix=0; ixmnemonic == mnem) return(phoneme_tab[ix]->code); } return(0); } int LookupPhonemeString(const char *string) {//======================================== int ix; unsigned char c; unsigned int mnem; // Pack up to 4 characters into a word mnem = 0; for(ix=0; ix<4; ix++) { if(string[ix]==0) break; c = string[ix]; mnem |= (c << (ix*8)); } return(PhonemeCode(mnem)); } frameref_t *LookupSpect(PHONEME_TAB *this_ph, int which, FMT_PARAMS *fmt_params, int *n_frames, PHONEME_LIST *plist) {//=================================================================================================================== int ix; int nf; int nf1; int seq_break; frameref_t *frames; int length1; int length_std; int length_factor; SPECT_SEQ *seq, *seq2; SPECT_SEQK *seqk, *seqk2; frame_t *frame; static frameref_t frames_buf[N_SEQ_FRAMES]; seq = (SPECT_SEQ *)(&phondata_ptr[fmt_params->fmt_addr]); seqk = (SPECT_SEQK *)seq; nf = seq->n_frames; if(nf >= N_SEQ_FRAMES) nf = N_SEQ_FRAMES - 1; seq_len_adjust = fmt_params->fmt2_lenadj + fmt_params->fmt_length; seq_break = 0; for(ix=0; ixframe[0].frflags & FRFLAG_KLATT) frame = &seqk->frame[ix]; else frame = (frame_t *)&seq->frame[ix]; frames_buf[ix].frame = frame; frames_buf[ix].frflags = frame->frflags; frames_buf[ix].length = frame->length; if(frame->frflags & FRFLAG_VOWEL_CENTRE) seq_break = ix; } frames = &frames_buf[0]; if(seq_break > 0) { if(which==1) { nf = seq_break + 1; } else { frames = &frames_buf[seq_break]; // body of vowel, skip past initial frames nf -= seq_break; } } // do we need to modify a frame for blending with a consonant? if((this_ph->type == phVOWEL) && (fmt_params->fmt2_addr == 0) && (fmt_params->use_vowelin)) { seq_len_adjust += FormantTransition2(frames,nf,fmt_params->transition0,fmt_params->transition1,NULL,which); } length1 = 0; nf1 = nf - 1; for(ix=0; ixfmt2_addr != 0) { // a secondary reference has been returned, which is not a wavefile // add these spectra to the main sequence seq2 = (SPECT_SEQ *)(&phondata_ptr[fmt_params->fmt2_addr]); seqk2 = (SPECT_SEQK *)seq2; // first frame of the addition just sets the length of the last frame of the main seq nf--; for(ix=0; ixn_frames; ix++) { if(seq2->frame[0].frflags & FRFLAG_KLATT) frame = &seqk2->frame[ix]; else frame = (frame_t *)&seq2->frame[ix]; frames[nf].length = frame->length; if(ix > 0) { frames[nf].frame = frame; frames[nf].frflags = frame->frflags; } nf++; } wavefile_ix = 0; } if(length1 > 0) { if(which==2) { // adjust the length of the main part to match the standard length specified for the vowel // less the front part of the vowel and any added suffix length_std = fmt_params->std_length + seq_len_adjust - 45; if(length_std < 10) length_std = 10; if(plist->synthflags & SFLAG_LENGTHEN) length_std += (phoneme_tab[phonLENGTHEN]->std_length * 2); // phoneme was followed by an extra : symbol // can adjust vowel length for stressed syllables here length_factor = (length_std * 256)/ length1; for(ix=0; ixfmt_control == 1) { // This is the default start of a vowel. // Allow very short vowels to have shorter front parts if(fmt_params->std_length < 130) frames[0].length = (frames[0].length * fmt_params->std_length)/130; } } else { //not a vowel if(fmt_params->std_length > 0) { seq_len_adjust += (fmt_params->std_length - length1); } } if(seq_len_adjust != 0) { length_factor = ((length1 + seq_len_adjust) * 256)/length1; for(ix=0; ix 0) { // recursively include base phoneme tables SetUpPhonemeTable(includes-1,1); } // now add the phonemes from this table phtab = phoneme_tab_list[number].phoneme_tab_ptr; for(ix=0; ix n_phoneme_tab) n_phoneme_tab = ph_code; if(recursing == 0) phoneme_tab_flags[ph_code] |= 1; // not inherited } } // end of SetUpPhonemeTable void SelectPhonemeTable(int number) {//================================ n_phoneme_tab = 0; SetUpPhonemeTable(number,0); // recursively for included phoneme tables n_phoneme_tab++; current_phoneme_table = number; } // end of SelectPhonemeTable int LookupPhonemeTable(const char *name) {//===================================== int ix; for(ix=0; ixmnemonic)); } static bool StressCondition(Translator *tr, PHONEME_LIST *plist, int condition, int control) {//======================================================================================== // condition: // 0 if diminished, 1 if unstressed, 2 if not stressed, 3 if stressed, 4 if max stress int stress_level; PHONEME_LIST *pl; static int condition_level[4] = {1,2,4,15}; if(phoneme_tab[plist[0].phcode]->type == phVOWEL) { pl = plist; } else { // consonant, get stress from the following vowel if(phoneme_tab[plist[1].phcode]->type == phVOWEL) { pl = &plist[1]; } else return(false); // no stress elevel for this consonant } stress_level = pl->stresslevel & 0xf; if(tr != NULL) { if((control & 1) && (plist->synthflags & SFLAG_DICTIONARY) && ((tr->langopts.param[LOPT_REDUCE] & 1)==0)) { // change phoneme. Don't change phonemes which are given for the word in the dictionary. return(false); } if((tr->langopts.param[LOPT_REDUCE] & 0x2) && (stress_level >= pl->wordstress)) { // treat the most stressed syllable in an unstressed word as stressed stress_level = 4; } } if(condition == 4) { return(stress_level >= pl->wordstress); } if(condition == 3) { // if stressed if(stress_level > 3) return(true); } else { if(stress_level < condition_level[condition]) return(true); } return(false); } // end of StressCondition static int CountVowelPosition(PHONEME_LIST *plist) {//=============================================== int count = 0; for(;;) { if(plist->ph->type == phVOWEL) count++; if(plist->sourceix != 0) break; plist--; } return(count); } // end of CoundVowelPosition static bool InterpretCondition(Translator *tr, int control, PHONEME_LIST *plist, int instn) {//======================================================================================== int which; unsigned int data; int instn2; int count; PHONEME_TAB *ph; PHONEME_LIST *plist_this; static int ph_position[8] = {0, 1, 2, 3, 2, 0, 1, 3}; // prevPh, thisPh, nextPh, next2Ph, nextPhW, prevPhW, nextVowel, (other conditions) // instruction: 2xxx, 3xxx // bits 8-10 = 0 to 6, which phoneme // bit 11 = 0, bits 0-7 are a phoneme code // bit 11 = 1, bits 5-7 type of data, bits 0-4 data value // bits 8-10 = 7, other conditions data = instn & 0xff; instn2 = instn >> 8; if(instn2 < 14) { which = (instn2) % 7; if(which==4) { // nextPh not word boundary if(plist[1].sourceix) return(false); } if(which==5) { // prevPh, not word boundary if(plist[0].sourceix) return(false); } if(which==6) { // nextVowel, not word boundary for(which=2;;which++) { if(plist[which-1].sourceix) return(false); if(phoneme_tab[plist[which-1].phcode]->type == phVOWEL) break; } } else { which = ph_position[which]; } plist_this = plist; plist = &plist[which-1]; if(which == 0) { if(plist->phcode == 1) { // This is a NULL phoneme, a phoneme has been deleted so look at the previous phoneme plist = &plist[-1]; } } if(control & 0x100) { // "change phonemes" pass plist->ph = phoneme_tab[plist->phcode]; } ph = plist->ph; if(instn2 < 7) { // 'data' is a phoneme number if((phoneme_tab[data]->mnemonic == ph->mnemonic) == true) return(true); if((which == 0) && (ph->type == phVOWEL)) return(data == ph->end_type); // prevPh() match on end_type return(data == ph->start_type); // thisPh() or nextPh(), match on start_type } data = instn & 0x1f; switch(instn & 0xe0) { case 0x00: // phoneme type, vowel, nasal, fricative, etc return(ph->type == data); break; case 0x20: // place of articulation return(((ph->phflags >> 16) & 0xf) == data); break; case 0x40: // is a bit set in phoneme flags return((ph->phflags & (1 << data)) != 0); break; case 0x80: switch(data) { case 0: case 1: case 2: case 3: case 4: return(StressCondition(tr, plist, data, 0)); case 5: // isBreak, Either pause phoneme, or (stop/vstop/vfric not followed by vowel or (liquid in same word)) return((ph->type == phPAUSE) || (plist_this->synthflags & SFLAG_NEXT_PAUSE)); case 6: // isWordStart return(plist->sourceix != 0); case 7: // notWordStart return(plist->sourceix == 0); case 8: // isWordEnd return(plist[1].sourceix || (plist[1].ph->type == phPAUSE)); break; case 9: // isAfterStress if(plist->sourceix != 0) return(false); do { plist--; if((plist->stresslevel & 0xf) >= 4) return(true); } while (plist->sourceix == 0); break; case 10: // isNotVowel return(ph->type != phVOWEL); case 11: // isFinalVowel for(;;) { plist++; plist->ph = phoneme_tab[plist->phcode]; if(plist->sourceix != 0) return(true); // start of next word, without finding another vowel if(plist->ph->type == phVOWEL) return(false); } break; case 12: // isVoiced return((ph->type == phVOWEL) || (ph->type == phLIQUID) || (ph->phflags & phVOICED)); case 13: // isFirstVowel return(CountVowelPosition(plist)==1); case 14: // isSecondVowel return(CountVowelPosition(plist)==2); case 15: // isSeqFlag1 // is this preceded by a sequence if 1 or more vowels which have 'flag1' ? (lang=hi) if(plist->sourceix != 0) return(false); // this is the first phoneme in the word, so no. count = 0; for(;;) { plist--; if(plist->ph->type == phVOWEL) { if(plist->ph->phflags & phFLAG1) count++; else break; // stop when we find a vowel without flag1 } if(plist->sourceix != 0) break; } return(count > 0); case 0x10: // isTranslationGiven return((plist->synthflags & SFLAG_DICTIONARY) != 0); } break; } return(false); } else if(instn2 == 0xf) { // Other conditions switch(data) { case 1: // PreVoicing return(control & 1); case 2: // KlattSynth return(voice->klattv[0] != 0); case 3: // MbrolaSynth return(mbrola_name[0] != 0); } } return(false); } // end of InterpretCondition static void SwitchVowelType(PHONEME_LIST *plist, PHONEME_DATA *phdata, USHORT **p_prog, int instn_type) {//===================================================================================================== USHORT *prog; int voweltype; signed char x; if(instn_type == 2) { phdata->pd_control |= pd_FORNEXTPH; voweltype = plist[1].ph->start_type; // SwitchNextVowelType } else { voweltype = plist[-1].ph->end_type; // SwitchPrevVowelType } voweltype -= phonVOWELTYPES; if((voweltype >= 0) && (voweltype < 6)) { prog = *p_prog + voweltype*2; phdata->sound_addr[instn_type] = (((prog[1] & 0xf) << 16) + prog[2]) * 4; x = (prog[1] >> 4) & 0xff; phdata->sound_param[instn_type] = x; // sign extend } *p_prog += 12; } // end of SwitchVowelType static int NumInstnWords(USHORT *prog) {//=================================== int instn; int instn2; int instn_type; static char n_words[11] = {1,1,1,1,1,1,1,1,1,2,4}; instn = *prog; instn_type = instn >> 12; if(instn_type < 11) return(n_words[instn_type]); // 11 to 15, 2 words instn2 = prog[2]; if((instn2 >> 12) == 0xf) { // addWav(), 2 more words return(4); } if(instn2 == i_CONTINUE) { return(3); } return(2); } // end of NumInstnWords void InterpretPhoneme(Translator *tr, int control, PHONEME_LIST *plist, PHONEME_DATA *phdata) {//========================================================================================== // control: //bit 0: PreVoicing //bit 8: change phonemes PHONEME_TAB *ph; USHORT *prog; USHORT instn; int instn2; int or_flag; bool truth; int data; int end_flag; int ix; signed char param_sc; #define N_RETURN 10 int n_return=0; USHORT *return_addr[N_RETURN]; // return address stack ph = plist->ph; memset(phdata, 0, sizeof(PHONEME_DATA)); phdata->pd_param[i_SET_LENGTH] = ph->std_length; phdata->pd_param[i_LENGTH_MOD] = ph->length_mod; if(ph->program == 0) return; end_flag = 0; for(prog = &phoneme_index[ph->program]; end_flag != 1; prog++) { instn = *prog; instn2 = (instn >> 8) & 0xf; or_flag = 0; switch(instn >> 12) { case 0: // 0xxx data = instn & 0xff; if(instn2 == 0) { // instructions with no operand switch(data) { case i_RETURN: end_flag = 1; break; case i_CONTINUE: break; default: InvalidInstn(ph,instn); break; } } else if(instn2 == i_APPEND_IFNEXTVOWEL) { if(phoneme_tab[plist[1].phcode]->type == phVOWEL) phdata->pd_param[i_APPEND_PHONEME] = data; } else if(instn2 == i_IPA_NAME) { // followed by utf-8 characters, 2 per instn word for(ix=0; (ix < data) && (ix < 16); ix += 2) { prog++; phdata->ipa_string[ix] = prog[0] >> 8; phdata->ipa_string[ix+1] = prog[0] & 0xff; } phdata->ipa_string[ix] = 0; } else if(instn2 < N_PHONEME_DATA_PARAM) { if(instn2 == i_CHANGE_PHONEME2) { phdata->pd_param[i_CHANGE_PHONEME] = data; // also set ChangePhoneme } phdata->pd_param[instn2] = data; if((instn2 == i_CHANGE_PHONEME) && (control & 0x100)) { // found ChangePhoneme() in PhonemeList mode, exit end_flag = 1; } } else { InvalidInstn(ph,instn); } break; case 1: if(tr == NULL) break; // ignore if in synthesis stage if(instn2 < 8) { // ChangeIf if(StressCondition(tr, plist, instn2 & 7, 1)) { phdata->pd_param[i_CHANGE_PHONEME] = instn & 0xff; end_flag = 1; // change phoneme, exit } } break; case 2: case 3: // conditions or_flag = 0; truth = true; while((instn & 0xe000) == 0x2000) { // process a sequence of conditions, using boolean accumulator if(or_flag) truth = (truth || InterpretCondition(tr, control, plist, instn & 0xfff)); else truth = (truth && InterpretCondition(tr, control, plist, instn & 0xfff)); or_flag = instn & 0x1000; instn = *(++prog); } if(truth == false) { if((instn & 0xf800) == i_JUMP_FALSE) { prog += instn & 0xff; } else { // instruction after a condition is not JUMP_FALSE, so skip the instruction. prog += NumInstnWords(prog); if((prog[0] & 0xfe00) == 0x6000) prog++; // and skip ELSE jump } } prog--; break; case 6: // JUMP switch(instn2 >> 1) { case 0: prog += (instn & 0xff) - 1; break; case 4: // conditional jumps should have been processed in the Condition section break; case 5: // NexttVowelStarts SwitchVowelType(plist, phdata, &prog, 2); break; case 6: // PrevVowelTypeEndings SwitchVowelType(plist, phdata, &prog, 3); break; } break; case 9: data = ((instn & 0xf) << 16) + prog[1]; prog++; switch(instn2) { case 1: // call a procedure or another phoneme if(n_return < N_RETURN) { return_addr[n_return++] = prog; prog = &phoneme_index[data] - 1; } break; case 2: // pitch envelope phdata->pitch_env = data; break; case 3: // amplitude envelope phdata->amp_env = data; break; } break; case 10: // Vowelin, Vowelout if(instn2 == 1) ix = 0; else ix = 2; phdata->vowel_transition[ix] = ((prog[0] & 0xff) << 16) + prog[1]; phdata->vowel_transition[ix+1] = (prog[2] << 16) + prog[3]; prog += 3; break; case 11: // FMT case 12: // WAV case 13: // VowelStart case 14: // VowelEnd case 15: // addWav instn2 = (instn >> 12) - 11; phdata->sound_addr[instn2] = ((instn & 0xf) << 18) + (prog[1] << 2); param_sc = phdata->sound_param[instn2] = (instn >> 4) & 0xff; prog++; if(prog[1] != i_CONTINUE) { if(instn2 < 2) { // FMT() and WAV() imply Return end_flag = 1; if((prog[1] >> 12) == 0xf) { // Return after the following addWav() end_flag = 2; } } else if(instn2 ==pd_ADDWAV) { // addWav(), return if previous instruction was FMT() or WAV() end_flag--; } if((instn2 == pd_VWLSTART) || (instn2 == pd_VWLEND)) { // VowelStart or VowelEnding. phdata->sound_param[instn2] = param_sc; // sign extend } } break; default: InvalidInstn(ph,instn); break; } if(ph->phflags & phSINGLE_INSTN) { end_flag = 1; // this phoneme has a one-instruction program, with an implicit Return } if((end_flag == 1) && (n_return > 0)) { // return from called procedure or phoneme end_flag = 0; prog = return_addr[--n_return]; } } } // end of InterpretPhoneme void InterpretPhoneme2(int phcode, PHONEME_DATA *phdata) {//===================================================== // Examine the program of a single isolated phoneme int ix; PHONEME_LIST plist[4]; memset(plist, 0, sizeof(plist)); for(ix=0; ix<4; ix++) { plist[ix].phcode = phonPAUSE; plist[ix].ph = phoneme_tab[phonPAUSE]; } plist[1].phcode = phcode; plist[1].ph = phoneme_tab[phcode]; plist[2].sourceix = 1; InterpretPhoneme(NULL, 0, &plist[1], phdata); } // end of InterpretPhoneme2 sources_5316/external/espeak/compiledict.cpp0000644000176700017670000012002511725414516020023 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2010 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "translate.h" extern void Write4Bytes(FILE *f, int value); int HashDictionary(const char *string); static FILE *f_log = NULL; extern char *dir_dictionary; extern char word_phonemes[N_WORD_PHONEMES]; // a word translated into phoneme codes static int linenum; static int error_count; static int text_mode = 0; static int debug_flag = 0; static int error_need_dictionary = 0; static int hash_counts[N_HASH_DICT]; static char *hash_chains[N_HASH_DICT]; static char letterGroupsDefined[N_LETTER_GROUPS]; MNEM_TAB mnem_rules[] = { {"unpr", 0x01}, {"w_alt2", 0x12}, {"w_alt3", 0x13}, {"w_alt", 0x11}, // note: put longer names before their sub-strings {"p_alt2", 0x22}, {"p_alt3", 0x23}, {"p_alt", 0x21}, {NULL, -1} }; MNEM_TAB mnem_flags[] = { // these in the first group put a value in bits0-3 of dictionary_flags {"$1", 0x41}, // stress on 1st syllable {"$2", 0x42}, // stress on 2nd syllable {"$3", 0x43}, {"$4", 0x44}, {"$5", 0x45}, {"$6", 0x46}, {"$7", 0x47}, {"$u", 0x48}, // reduce to unstressed {"$u1", 0x49}, {"$u2", 0x4a}, {"$u3", 0x4b}, {"$u+", 0x4c}, // reduce to unstressed, but stress at end of clause {"$u1+", 0x4d}, {"$u2+", 0x4e}, {"$u3+", 0x4f}, // these set the corresponding numbered bit if dictionary_flags {"$pause", 8}, /* ensure pause before this word */ {"$only", 9}, /* only match on this word without suffix */ {"$onlys", 10}, /* only match with none, or with 's' suffix */ {"$strend", 11}, /* full stress if at end of clause */ {"$strend2", 12}, /* full stress if at end of clause, or only followed by unstressed */ {"$unstressend",13}, /* reduce stress at end of clause */ {"$atend", 14}, /* use this pronunciation if at end of clause */ {"$atstart", 15}, // use this pronunciation at start of clause {"$abbrev", 17}, /* use this pronuciation rather than split into letters */ {"$stem", 18}, // must have a suffix // language specific {"$double", 19}, // IT double the initial consonant of next word {"$alt", 20}, // use alternative pronunciation {"$alt1", 20}, // synonym for $alt {"$alt2", 21}, {"$alt3", 22}, {"$combine", 23}, // Combine with the next word {"$dot", 24}, // ignore '.' after this word (abbreviation) {"$hasdot", 25}, // use this pronunciation if there is a dot after the word {"$max3", 27}, // limit to 3 repetitions {"$brk", 28}, // a shorter $pause {"$text", 29}, // word translates to replcement text, not phonemes // flags in dictionary word 2 {"$verbf", 0x20}, /* verb follows */ {"$verbsf", 0x21}, /* verb follows, allow -s suffix */ {"$nounf", 0x22}, /* noun follows */ {"$pastf", 0x23}, /* past tense follows */ {"$verb", 0x24}, /* use this pronunciation when its a verb */ {"$noun", 0x25}, /* use this pronunciation when its a noun */ {"$past", 0x26}, /* use this pronunciation when its past tense */ {"$verbextend",0x28}, /* extend influence of 'verb follows' */ {"$capital", 0x29}, /* use this pronunciation if initial letter is upper case */ {"$allcaps", 0x2a}, /* use this pronunciation if initial letter is upper case */ {"$accent", 0x2b}, // character name is base-character name + accent name {"$sentence",0x2d}, // only if this clause is a sentence (i.e. terminator is {. ? !} not {, ; :} // doesn't set dictionary_flags {"$?", 100}, // conditional rule, followed by byte giving the condition number {"$textmode", 200}, {"$phonememode", 201}, {NULL, -1} }; #define LEN_GROUP_NAME 12 typedef struct { char name[LEN_GROUP_NAME+1]; unsigned int start; unsigned int length; int group3_ix; } RGROUP; int isspace2(unsigned int c) {//========================= // can't use isspace() because on Windows, isspace(0xe1) gives TRUE ! int c2; if(((c2 = (c & 0xff)) == 0) || (c > ' ')) return(0); return(1); } static FILE *fopen_log(const char *fname,const char *access) {//================================================== // performs fopen, but produces error message to f_log if it fails FILE *f; if((f = fopen(fname,access)) == NULL) { if(f_log != NULL) fprintf(f_log,"Can't access (%s) file '%s'\n",access,fname); } return(f); } const char *LookupMnemName(MNEM_TAB *table, const int value) //========================================================== /* Lookup a mnemonic string in a table, return its name */ { while(table->mnem != NULL) { if(table->value==value) return(table->mnem); table++; } return(""); /* not found */ } /* end of LookupMnemValue */ char *print_dictionary_flags(unsigned int *flags) {//============================================== static char buf[20]; sprintf(buf,"%s 0x%x/%x",LookupMnemName(mnem_flags,(flags[0] & 0xf)+0x40), flags[0], flags[1]); return(buf); } char *DecodeRule(const char *group_chars, int group_length, char *rule, int control) {//================================================================================= /* Convert compiled match template to ascii */ unsigned char rb; unsigned char c; char *p; int ix; int match_type; int finished=0; int value; int linenum=0; int flags; int suffix_char; int condition_num=0; int at_start = 0; const char *name; char buf[60]; char buf_pre[60]; char suffix[20]; static char output[60]; static char symbols[] = {' ',' ',' ',' ',' ',' ',' ',' ',' ',' ', '&','%','+','#','S','D','Z','A','L','!',' ','@','?','J','N','K','V','?','T','X','?','W'}; static char symbols_lg[] = {'A','B','C','H','F','G','Y'}; match_type = 0; buf_pre[0] = 0; for(ix=0; ix> 8)) suffix_char = 'P'; sprintf(suffix,"%c%d",suffix_char,rule[2] & 0x7f); rule += 3; for(ix=0;ix<9;ix++) { if(flags & 1) sprintf(&suffix[strlen(suffix)],"%c",flag_chars[ix]); flags = (flags >> 1); } strcpy(p,suffix); p += strlen(suffix); c = ' '; } else if(rb == RULE_LETTERGP) { c = symbols_lg[*rule++ - 'A']; } else if(rb == RULE_LETTERGP2) { value = *rule++ - 'A'; p[0] = 'L'; p[1] = (value / 10) + '0'; c = (value % 10) + '0'; if(match_type == RULE_PRE) { p[0] = c; c = 'L'; } p+=2; } else if(rb <= RULE_LAST_RULE) c = symbols[rb]; else if(rb == RULE_SPACE) c = '_'; else c = rb; *p++ = c; } *p = 0; p = output; if(linenum > 0) { sprintf(p,"%5d:\t",linenum); p += 7; } if(condition_num > 0) { sprintf(p,"?%d ",condition_num); p = &p[strlen(p)]; } if(((ix = strlen(buf_pre)) > 0) || at_start) { if(at_start) *p++ = '_'; while(--ix >= 0) *p++ = buf_pre[ix]; *p++ = ')'; *p++ = ' '; } *p = 0; strcat(p,buf); ix = strlen(output); while(ix < 8) output[ix++]=' '; output[ix]=0; return(output); } /* end of DecodeRule */ static int compile_line(char *linebuf, char *dict_line, int *hash) {//=============================================================== // Compile a line in the language_list file unsigned char c; char *p; char *word; char *phonetic; unsigned int ix; int step; unsigned int n_flag_codes = 0; int flagnum; int flag_offset; int length; int multiple_words = 0; int multiple_numeric_hyphen = 0; char *multiple_string = NULL; char *multiple_string_end = NULL; int len_word; int len_phonetic; int text_not_phonemes; // this word specifies replacement text, not phonemes unsigned int wc; int all_upper_case; char *mnemptr; unsigned char flag_codes[100]; char encoded_ph[200]; unsigned char bad_phoneme[4]; static char nullstring[] = {0}; text_not_phonemes = 0; phonetic = word = nullstring; p = linebuf; // while(isspace2(*p)) p++; #ifdef deleted if(*p == '$') { if(memcmp(p,"$textmode",9) == 0) { text_mode = 1; return(0); } if(memcmp(p,"$phonememode",12) == 0) { text_mode = 0; return(0); } } #endif step = 0; c = 0; while(c != '\n') { c = *p; if((c == '?') && (step==0)) { // conditional rule, allow only if the numbered condition is set for the voice flag_offset = 100; p++; if(*p == '!') { // allow only if the numbered condition is NOT set flag_offset = 132; p++; } ix = 0; if(isdigit(*p)) { ix += (*p-'0'); p++; } if(isdigit(*p)) { ix = ix*10 + (*p-'0'); p++; } flag_codes[n_flag_codes++] = ix + flag_offset; c = *p; } if((c == '$') && isalnum(p[1])) { /* read keyword parameter */ mnemptr = p; while(!isspace2(c = *p)) p++; *p = 0; flagnum = LookupMnem(mnem_flags,mnemptr); if(flagnum > 0) { if(flagnum == 200) { text_mode = 1; } else if(flagnum == 201) { text_mode = 0; } else if(flagnum == BITNUM_FLAG_TEXTMODE) { text_not_phonemes = 1; } else { flag_codes[n_flag_codes++] = flagnum; } } else { fprintf(f_log,"%5d: Unknown keyword: %s\n",linenum,mnemptr); error_count++; } } if((c == '/') && (p[1] == '/') && (multiple_words==0)) { c = '\n'; /* "//" treat comment as end of line */ } switch(step) { case 0: if(c == '(') { multiple_words = 1; word = p+1; step = 1; } else if(!isspace2(c)) { word = p; step = 1; } break; case 1: if((c == '-') && multiple_words) { if(isdigit(word[0])) { multiple_numeric_hyphen = 1; } // else // ??? { flag_codes[n_flag_codes++] = BITNUM_FLAG_HYPHENATED; } c = ' '; } if(isspace2(c)) { p[0] = 0; /* terminate english word */ if(multiple_words) { multiple_string = multiple_string_end = p+1; step = 2; } else { step = 3; } } else if(c == ')') { if(multiple_words) { p[0] = 0; multiple_words = 0; step = 3; } else if(word[0] != '_') { fprintf(f_log, "%5d: Missing '('\n", linenum); error_count++; step = 3; } } break; case 2: if(isspace2(c)) { multiple_words++; } else if(c == ')') { p[0] = ' '; // terminate extra string multiple_string_end = p+1; step = 3; } break; case 3: if(!isspace2(c)) { phonetic = p; step = 4; } break; case 4: if(isspace2(c)) { p[0] = 0; /* terminate phonetic */ step = 5; } break; case 5: break; } p++; } if(word[0] == 0) { return(0); /* blank line */ } if(text_mode) text_not_phonemes = 1; if(text_not_phonemes) { if(word[0] == '_') { // This is a special word, used by eSpeak. Translate this into phonemes now strcat(phonetic, " "); // need a space to indicate word-boundary // PROBLEM vowel reductions are not applied to the translated phonemes // condition rules are not applied TranslateWord(translator,phonetic,0,NULL); text_not_phonemes = 0; strncpy0(encoded_ph, word_phonemes, N_WORD_BYTES-4); if((word_phonemes[0] == 0) && (error_need_dictionary < 3)) { // the dictionary was not loaded, we need a second attempt error_need_dictionary++; fprintf(f_log,"%5d: Need to compile dictionary again\n",linenum); } { //char decoded_phonemes[128]; //DecodePhonemes(word_phonemes,decoded_phonemes); //printf("Translator %x %s [%s] [%s]\n",translator->translator_name,word,phonetic,decoded_phonemes); } } else { // this is replacement text, so don't encode as phonemes. Restrict the length of the replacement word strncpy0(encoded_ph,phonetic,N_WORD_BYTES-4); } } else { EncodePhonemes(phonetic,encoded_ph,bad_phoneme); if(strchr(encoded_ph,phonSWITCH) != 0) { flag_codes[n_flag_codes++] = BITNUM_FLAG_ONLY_S; // don't match on suffixes (except 's') when switching languages } // check for errors in the phonemes codes if(bad_phoneme[0] != 0) { // unrecognised phoneme, report error fprintf(f_log,"%5d: Bad phoneme [%c] (0x%x) in: %s %s\n",linenum,bad_phoneme[0],bad_phoneme[0],word,phonetic); error_count++; } } if(text_not_phonemes != translator->langopts.textmode) { flag_codes[n_flag_codes++] = BITNUM_FLAG_TEXTMODE; } if(sscanf(word,"U+%x",&wc) == 1) { // Character code ix = utf8_out(wc, word); word[ix] = 0; } else if(word[0] != '_') { // convert to lower case, and note if the word is all-capitals int c2; all_upper_case = 1; p = word; for(p=word;;) { // this assumes that the lower case char is the same length as the upper case char // OK, except for Turkish "I", but use towlower() rather than towlower2() ix = utf8_in(&c2,p); if(c2 == 0) break; if(iswupper(c2)) { utf8_out(towlower(c2),p); } else { all_upper_case = 0; } p += ix; } if(all_upper_case) { flag_codes[n_flag_codes++] = BITNUM_FLAG_ALLCAPS; } } len_word = strlen(word); if(translator->transpose_min > 0) { len_word = TransposeAlphabet(translator, word); } *hash = HashDictionary(word); len_phonetic = strlen(encoded_ph); dict_line[1] = len_word; // bit 6 indicates whether the word has been compressed len_word &= 0x3f; memcpy(&dict_line[2],word,len_word); if(len_phonetic == 0) { // no phonemes specified. set bit 7 dict_line[1] |= 0x80; length = len_word + 2; } else { length = len_word + len_phonetic + 3; strcpy(&dict_line[(len_word)+2],encoded_ph); } for(ix=0; ix 0)) { if(multiple_words > 10) { fprintf(f_log,"%5d: Two many parts in a multi-word entry: %d\n",linenum,multiple_words); error_count++; } else { dict_line[length++] = 80 + multiple_words; ix = multiple_string_end - multiple_string; if(multiple_numeric_hyphen) { dict_line[length++] = ' '; // ??? } memcpy(&dict_line[length],multiple_string,ix); length += ix; } } dict_line[0] = length; return(length); } /* end of compile_line */ static void compile_dictlist_start(void) {//===================================== // initialise dictionary list int ix; char *p; char *p2; for(ix=0; ix= '0') && (c <= '9')) return(c - '0'); if((c >= 'a') && (c <= 'f')) return(c - 'a' + 10); if((c >= 'A') && (c <= 'F')) return(c - 'A' + 10); return(-1); } static void copy_rule_string(char *string, int &state) {//=================================================== // state 0: conditional, 1=pre, 2=match, 3=post, 4=phonemes static char *outbuf[5] = {rule_cond, rule_pre, rule_match, rule_post, rule_phonemes}; static int next_state[5] = {2,2,4,4,4}; char *output; char *p; int ix; int len; char c; int c2, c3; int sxflags; int value; int literal; int hexdigit_input = 0; MNEM_TAB *mr; if(string[0] == 0) return; output = outbuf[state]; if(state==4) { // append to any previous phoneme string, i.e. allow spaces in the phoneme string len = strlen(rule_phonemes); if(len > 0) rule_phonemes[len++] = ' '; output = &rule_phonemes[len]; } sxflags = 0x808000; // to ensure non-zero bytes for(p=string,ix=0;;) { literal = 0; c = *p++; if((c == '0') && (p[0] == 'x') && (isHexDigit(p[1]) >= 0) && (isHexDigit(p[2]) >= 0)) { hexdigit_input = 1; c = p[1]; p+= 2; } if(c == '\\') { c = *p++; // treat next character literally //#ifdef deleted if((c >= '0') && (c <= '3') && (p[0] >= '0') && (p[0] <= '7') && (p[1] >= '0') && (p[1] <= '7')) { // character code given by 3 digit octal value; c = (c-'0')*64 + (p[0]-'0')*8 + (p[1]-'0'); p += 2; } //endif literal = 1; } if(hexdigit_input) { if(((c2 = isHexDigit(c)) >= 0) && ((c3 = isHexDigit(p[0])) >= 0)) { c = c2 * 16 + c3; literal = 1; p++; } else { hexdigit_input = 0; } } if((state==1) || (state==3)) { // replace special characters (note: 'E' is reserved for a replaced silent 'e') if(literal == 0) { static const char lettergp_letters[9] = {LETTERGP_A,LETTERGP_B,LETTERGP_C,0,0,LETTERGP_F,LETTERGP_G,LETTERGP_H,LETTERGP_Y}; switch(c) { case '_': c = RULE_SPACE; break; case 'Y': c = 'I'; // drop through to next case case 'A': // vowel case 'B': case 'C': case 'H': case 'F': case 'G': if(state == 1) { // pre-rule, put the number before the RULE_LETTERGP; output[ix++] = lettergp_letters[c-'A'] + 'A'; c = RULE_LETTERGP; } else { output[ix++] = RULE_LETTERGP; c = lettergp_letters[c-'A'] + 'A'; } break; case 'D': c = RULE_DIGIT; break; case 'K': c = RULE_NOTVOWEL; break; case 'N': c = RULE_NO_SUFFIX; break; case 'V': c = RULE_IFVERB; break; case 'Z': c = RULE_NONALPHA; break; case '+': c = RULE_INC_SCORE; break; case '@': c = RULE_SYLLABLE; break; case '&': c = RULE_STRESSED; break; case '%': c = RULE_DOUBLE; break; case '#': c = RULE_DEL_FWD; break; case '!': c = RULE_CAPITAL; break; case 'T': output[ix++] = RULE_DOLLAR; c = 0x11; break; case 'W': c = RULE_SPELLING; break; case 'X': c = RULE_NOVOWELS; break; case 'J': c = RULE_SKIPCHARS; break; case 'L': // expect two digits c = *p++ - '0'; value = *p++ - '0'; c = c * 10 + value; if((value < 0) || (value > 9)) { c = 0; fprintf(f_log,"%5d: Expected 2 digits after 'L'\n",linenum); error_count++; } else if((c <= 0) || (c >= N_LETTER_GROUPS) || (letterGroupsDefined[(int)c] == 0)) { fprintf(f_log,"%5d: Letter group L%.2d not defined\n",linenum,c); error_count++; } c += 'A'; if(state == 1) { // pre-rule, put the group number before the RULE_LETTERGP command output[ix++] = c; c = RULE_LETTERGP2; } else { output[ix++] = RULE_LETTERGP2; } break; case '$': output[ix++] = RULE_DOLLAR; c = 0; mr = mnem_rules; while(mr->mnem != NULL) { len = strlen(mr->mnem); if(memcmp(p, mr->mnem, len) == 0) { c = mr->value; p += len; break; } mr++; } if(c == 0) { fprintf(f_log,"%5d: $ command not recognized\n",linenum); error_count++; } break; case 'P': sxflags |= SUFX_P; // Prefix, now drop through to Suffix case 'S': output[ix++] = RULE_ENDING; value = 0; while(!isspace2(c = *p++) && (c != 0)) { switch(c) { case 'e': sxflags |= SUFX_E; break; case 'i': sxflags |= SUFX_I; break; case 'p': // obsolete, replaced by 'P' above sxflags |= SUFX_P; break; case 'v': sxflags |= SUFX_V; break; case 'd': sxflags |= SUFX_D; break; case 'f': sxflags |= SUFX_F; break; case 'q': sxflags |= SUFX_Q; break; case 't': sxflags |= SUFX_T; break; case 'b': sxflags |= SUFX_B; break; case 'a': sxflags |= SUFX_A; break; default: if(isdigit(c)) value = (value*10) + (c - '0'); break; } } p--; output[ix++] = sxflags >> 16; output[ix++] = sxflags >> 8; c = value | 0x80; break; } } } output[ix++] = c; if(c == 0) break; } state = next_state[state]; } // end of copy_rule_string static char *compile_rule(char *input) {//=================================== int ix; unsigned char c; int wc; char *p; char *prule; int len; int len_name; int start; int state=2; int finish=0; char buf[80]; char output[150]; unsigned char bad_phoneme[4]; buf[0]=0; rule_cond[0]=0; rule_pre[0]=0; rule_post[0]=0; rule_match[0]=0; rule_phonemes[0]=0; p = buf; for(ix=0; finish==0; ix++) { c = input[ix]; switch(c = input[ix]) { case ')': // end of prefix section *p = 0; state = 1; copy_rule_string(buf,state); p = buf; break; case '(': // start of suffix section *p = 0; state = 2; copy_rule_string(buf,state); state = 3; p = buf; if(input[ix+1] == ' ') { fprintf(f_log,"%5d: Syntax error. Space after (\n",linenum); error_count++; } break; case '\n': // end of line case '\r': case 0: // end of line *p = 0; copy_rule_string(buf,state); finish=1; break; case '\t': // end of section section case ' ': *p = 0; copy_rule_string(buf,state); p = buf; break; case '?': if(state==2) state=0; else *p++ = c; break; default: *p++ = c; break; } } if(strcmp(rule_match,"$group")==0) strcpy(rule_match,group_name); if(rule_match[0]==0) { if(rule_post[0] != 0) { fprintf(f_log,"%5d: Syntax error\n",linenum); error_count++; } return(NULL); } EncodePhonemes(rule_phonemes,buf,bad_phoneme); if(bad_phoneme[0] != 0) { fprintf(f_log,"%5d: Bad phoneme [%c] in %s\n",linenum,bad_phoneme[0],input); error_count++; } strcpy(output,buf); len = strlen(buf)+1; len_name = strlen(group_name); if((len_name > 0) && (memcmp(rule_match,group_name,len_name) != 0)) { utf8_in(&wc,rule_match); if((group_name[0] == '9') && IsDigit(wc)) { // numeric group, rule_match starts with a digit, so OK } else { fprintf(f_log,"%5d: Wrong initial letters '%s' for group '%s'\n",linenum,rule_match,group_name); error_count++; } } strcpy(&output[len],rule_match); len += strlen(rule_match); if(debug_flag) { output[len] = RULE_LINENUM; output[len+1] = (linenum % 255) + 1; output[len+2] = (linenum / 255) + 1; len+=3; } if(rule_cond[0] != 0) { ix = -1; if(rule_cond[0] == '!') { // allow the rule only if the condition number is NOT set for the voice ix = atoi(&rule_cond[1]) + 32; } else { // allow the rule only if the condition number is set for the voice ix = atoi(rule_cond); } if((ix > 0) && (ix < 255)) { output[len++] = RULE_CONDITION; output[len++] = ix; } else { fprintf(f_log,"%5d: bad condition number ?%d\n",linenum,ix); error_count++; } } if(rule_pre[0] != 0) { start = 0; if(rule_pre[0] == RULE_SPACE) { // omit '_' at the beginning of the pre-string and imply it by using RULE_PRE_ATSTART c = RULE_PRE_ATSTART; start = 1; } else { c = RULE_PRE; } output[len++] = c; // output PRE string in reverse order for(ix = strlen(rule_pre)-1; ix>=start; ix--) output[len++] = rule_pre[ix]; } if(rule_post[0] != 0) { sprintf(&output[len],"%c%s",RULE_POST,rule_post); len += (strlen(rule_post)+1); } output[len++]=0; prule = (char *)malloc(len); memcpy(prule,output,len); return(prule); } // end of compile_rule int string_sorter(char **a, char **b) {//=========================================== char *pa, *pb; int ix; if((ix = strcmp(pa = *a,pb = *b)) != 0) return(ix); pa += (strlen(pa)+1); pb += (strlen(pb)+1); return(strcmp(pa,pb)); } /* end of string_sorter */ static int rgroup_sorter(RGROUP *a, RGROUP *b) {//=================================================== // Sort long names before short names int ix; ix = strlen(b->name) - strlen(a->name); if(ix != 0) return(ix); ix = strcmp(a->name,b->name); if(ix != 0) return(ix); return(a->start-b->start); } #ifdef OUTPUT_FORMAT static void print_rule_group(FILE *f_out, int n_rules, char **rules, char *name) {//============================================================================= int rule; int ix; unsigned char c; int len1; int len2; int spaces; char *p; char *pout; int condition; char buf[80]; char suffix[12]; static unsigned char symbols[] = {'@','&','%','+','#','$','D','Z','A','B','C','F'}; fprintf(f_out,"\n$group %s\n",name); for(rule=0; rule 0) { sprintf(buf,"?%d ",condition); spaces -= strlen(buf); fprintf(f_out,"%s",buf); } if(rule_pre[0] != 0) { p = buf; for(ix=strlen(rule_pre)-1;ix>=0;ix--) *p++ = rule_pre[ix]; sprintf(p,") "); spaces -= strlen(buf); for(ix=0; ix 30) printf("Group %s %c %d\n",name,ix,nextchar_count[ix]); } #endif } // end of output_rule_group static int compile_lettergroup(char *input, FILE *f_out) {//===================================================== char *p; char *p_start; int group; int ix; int n_items; int length; int max_length = 0; #define N_LETTERGP_ITEMS 200 char *items[N_LETTERGP_ITEMS]; char item_length[N_LETTERGP_ITEMS]; p = input; if(!isdigit(p[0]) || !isdigit(p[1])) { fprintf(f_log,"%5d: Expected 2 digits after '.L'\n",linenum); error_count++; return(1); } group = atoi(&p[0]); if(group >= N_LETTER_GROUPS) { fprintf(f_log,"%5d: lettergroup out of range (01-%.2d)\n",linenum,N_LETTER_GROUPS-1); error_count++; return(1); } while(!isspace2(*p)) p++; fputc(RULE_GROUP_START,f_out); fputc(RULE_LETTERGP2,f_out); fputc(group + 'A', f_out); if(letterGroupsDefined[group] != 0) { fprintf(f_log,"%5d: lettergroup L%.2d is already defined\n",linenum,group); error_count++; } letterGroupsDefined[group] = 1; n_items = 0; while(n_items < N_LETTERGP_ITEMS) { while(isspace2(*p)) p++; if(*p == 0) break; items[n_items] = p_start = p; while((*p & 0xff) > ' ') { p++; } *p++ = 0; length = p - p_start; if(length > max_length) max_length = length; item_length[n_items++] = length; } // write out the items, longest first while(max_length > 1) { for(ix=0; ix < n_items; ix++) { if(item_length[ix] == max_length) { fwrite(items[ix],1,max_length,f_out); } } max_length--; } fputc(RULE_GROUP_END,f_out); return(0); } static int compile_dictrules(FILE *f_in, FILE *f_out, char *fname_temp) {//==================================================================== char *prule; unsigned char *p; int ix; int c; int gp; FILE *f_temp; int n_rules=0; int count=0; int different; int wc; const char *prev_rgroup_name; unsigned int char_code; int compile_mode=0; char *buf; char buf1[500]; char *rules[N_RULES]; int n_rgroups = 0; int n_groups3 = 0; RGROUP rgroup[N_RULE_GROUP2]; linenum = 0; group_name[0] = 0; if((f_temp = fopen_log(fname_temp,"wb")) == NULL) return(1); for(;;) { linenum++; buf = fgets(buf1,sizeof(buf1),f_in); if(buf != NULL) { if((p = (unsigned char *)strstr(buf,"//")) != NULL) *p = 0; if(buf[0] == '\r') buf++; // ignore extra \r in \r\n } if((buf == NULL) || (buf[0] == '.')) { // next .group or end of file, write out the previous group if(n_rules > 0) { strcpy(rgroup[n_rgroups].name,group_name); rgroup[n_rgroups].group3_ix = group3_ix; rgroup[n_rgroups].start = ftell(f_temp); output_rule_group(f_temp,n_rules,rules,group_name); rgroup[n_rgroups].length = ftell(f_temp) - rgroup[n_rgroups].start; n_rgroups++; count += n_rules; } n_rules = 0; if(compile_mode == 2) { // end of the character replacements section fwrite(&n_rules,1,4,f_out); // write a zero word to terminate the replacemenmt list compile_mode = 0; } if(buf == NULL) break; // end of file if(memcmp(buf,".L",2)==0) { compile_lettergroup(&buf[2], f_out); continue; } if(memcmp(buf,".replace",8)==0) { compile_mode = 2; fputc(RULE_GROUP_START,f_out); fputc(RULE_REPLACEMENTS,f_out); // advance to next word boundary while((ftell(f_out) & 3) != 0) fputc(0,f_out); } if(memcmp(buf,".group",6)==0) { compile_mode = 1; p = (unsigned char *)&buf[6]; while((p[0]==' ') || (p[0]=='\t')) p++; // Note: Windows isspace(0xe1) gives TRUE ! ix = 0; while((*p > ' ') && (ix < LEN_GROUP_NAME)) group_name[ix++] = *p++; group_name[ix]=0; group3_ix = 0; if(sscanf(group_name,"0x%x",&char_code)==1) { // group character is given as a character code (max 16 bits) p = (unsigned char *)group_name; if(char_code > 0x100) { *p++ = (char_code >> 8); } *p++ = char_code; *p = 0; } else { if(translator->letter_bits_offset > 0) { utf8_in(&wc, group_name); if(((ix = (wc - translator->letter_bits_offset)) >= 0) && (ix < 128)) { group3_ix = ix+1; // not zero } } } if((group3_ix == 0) && (strlen(group_name) > 2)) { if(utf8_in(&c,group_name) < 2) { fprintf(f_log,"%5d: Group name longer than 2 bytes (UTF8)",linenum); error_count++; } group_name[2] = 0; } } continue; } switch(compile_mode) { case 1: // .group prule = compile_rule(buf); if((prule != NULL) && (n_rules < N_RULES)) { rules[n_rules++] = prule; } break; case 2: // .replace { int replace1; int replace2; char *p; p = buf; replace1 = 0; replace2 = 0; while(isspace2(*p)) p++; ix = 0; while((unsigned char)(*p) > 0x20) // not space or zero-byte { p += utf8_in(&c,p); replace1 += (c << ix); ix += 16; } while(isspace2(*p)) p++; ix = 0; while((unsigned char)(*p) > 0x20) { p += utf8_in(&c,p); replace2 += (c << ix); ix += 16; } if(replace1 != 0) { Write4Bytes(f_out,replace1); // write as little-endian Write4Bytes(f_out,replace2); // if big-endian, reverse the bytes in LoadDictionary() } } break; } } fclose(f_temp); qsort((void *)rgroup,n_rgroups,sizeof(rgroup[0]),(int (*)(const void *,const void *))rgroup_sorter); if((f_temp = fopen(fname_temp,"rb"))==NULL) return(2); prev_rgroup_name = "\n"; for(gp = 0; gp < n_rgroups; gp++) { fseek(f_temp,rgroup[gp].start,SEEK_SET); if((different = strcmp(rgroup[gp].name, prev_rgroup_name)) != 0) { // not the same as the previous group if(gp > 0) fputc(RULE_GROUP_END,f_out); fputc(RULE_GROUP_START,f_out); if(rgroup[gp].group3_ix != 0) { n_groups3++; fputc(1,f_out); fputc(rgroup[gp].group3_ix, f_out); } else { fprintf(f_out, "%s", prev_rgroup_name = rgroup[gp].name); } fputc(0,f_out); } for(ix=rgroup[gp].length; ix>0; ix--) { c = fgetc(f_temp); fputc(c,f_out); } if(different) { } } fputc(RULE_GROUP_END,f_out); fputc(0,f_out); fclose(f_temp); remove(fname_temp); fprintf(f_log,"\t%d rules, %d groups (%d)\n\n",count,n_rgroups,n_groups3); return(0); } // end of compile_dictrules int CompileDictionary(const char *dsource, const char *dict_name, FILE *log, char *fname_err, int flags) {//===================================================================================================== // fname: space to write the filename in case of error // flags: bit 0: include source line number information, for debug purposes. FILE *f_in; FILE *f_out; int offset_rules=0; int value; char fname_in[sizeof(path_home)+45]; char fname_out[sizeof(path_home)+15]; char fname_temp[sizeof(path_home)+15]; char path[sizeof(path_home)+40]; // path_dsource+20 error_count = 0; error_need_dictionary = 0; memset(letterGroupsDefined,0,sizeof(letterGroupsDefined)); debug_flag = flags & 1; if(dsource == NULL) dsource = ""; f_log = log; //f_log = fopen("log2.txt","w"); if(f_log == NULL) f_log = stderr; // try with and without '.txt' extension sprintf(path,"%s%s_",dsource,dict_name); sprintf(fname_in,"%srules.txt",path); if((f_in = fopen(fname_in,"r")) == NULL) { sprintf(fname_in,"%srules",path); if((f_in = fopen_log(fname_in,"r")) == NULL) { if(fname_err) strcpy(fname_err,fname_in); return(-1); } } sprintf(fname_out,"%s%c%s_dict",path_home,PATHSEP,dict_name); if((f_out = fopen_log(fname_out,"wb+")) == NULL) { if(fname_err) strcpy(fname_err,fname_in); return(-1); } sprintf(fname_temp,"%s%ctemp",path_home,PATHSEP); value = N_HASH_DICT; Write4Bytes(f_out,value); Write4Bytes(f_out,offset_rules); compile_dictlist_start(); fprintf(f_log,"Using phonemetable: '%s'\n",phoneme_tab_list[phoneme_tab_number].name); compile_dictlist_file(path,"roots"); if(translator->langopts.listx) { compile_dictlist_file(path,"list"); compile_dictlist_file(path,"listx"); } else { compile_dictlist_file(path,"listx"); compile_dictlist_file(path,"list"); } compile_dictlist_file(path,"extra"); compile_dictlist_end(f_out); offset_rules = ftell(f_out); fprintf(f_log,"Compiling: '%s'\n",fname_in); compile_dictrules(f_in,f_out,fname_temp); fclose(f_in); fseek(f_out,4,SEEK_SET); Write4Bytes(f_out,offset_rules); fclose(f_out); LoadDictionary(translator, dict_name, 0); return(error_count); } // end of compile_dictionary sources_5316/external/espeak/espeak_command.cpp0000664000176700017670000003746011674622653020517 0ustar paulpaul/*************************************************************************** * Copyright (C) 2007, Gilles Casse * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ #include "speech.h" #ifdef USE_ASYNC // This source file is only used for asynchronious modes #include "espeak_command.h" #include #include #include #include #include "debug.h" static unsigned int my_current_text_id=0; //type = ET_TEXT; a_command->state = CS_UNDEFINED; data = &(a_command->u.my_text); data->unique_identifier = ++my_current_text_id; data->text = a_text; data->size = size; data->position = position; data->position_type = position_type; data->end_position = end_position; data->flags = flags; data->user_data = user_data; a_error=0; SHOW("ET_TEXT malloc text=%x, command=%x (uid=%d)\n", a_text, a_command, data->unique_identifier); text_error: if (a_error) { if (a_text) { free (a_text); } if (a_command) { free (a_command); } a_command = NULL; } SHOW("command=0x%x\n", a_command); return a_command; } //> t_espeak_command* create_espeak_terminated_msg(unsigned int unique_identifier, void* user_data) { ENTER("create_espeak_terminated_msg"); int a_error=1; t_espeak_terminated_msg* data = NULL; t_espeak_command* a_command = (t_espeak_command*)malloc(sizeof(t_espeak_command)); if (!a_command) { goto msg_error; } a_command->type = ET_TERMINATED_MSG; a_command->state = CS_UNDEFINED; data = &(a_command->u.my_terminated_msg); data->unique_identifier = unique_identifier; data->user_data = user_data; a_error=0; SHOW("ET_TERMINATED_MSG command=%x (uid=%d, user_data=0x%x)\n", a_command, unique_identifier, (int)user_data); msg_error: if (a_error) { if (a_command) { free (a_command); } a_command = NULL; } SHOW("command=0x%x\n", a_command); return a_command; } //type = ET_MARK; a_command->state = CS_UNDEFINED; data = &(a_command->u.my_mark); data->unique_identifier = ++my_current_text_id; data->text = a_text; data->size = size; data->index_mark = a_index_mark; data->end_position = end_position; data->flags = flags; data->user_data = user_data; a_error=0; mark_error: if (a_error) { if (a_text) { free (a_text); } if (a_command) { free (a_command); } a_command = NULL; if (a_index_mark) { free (a_index_mark); } } SHOW("ET_MARK malloc text=%x, command=%x (uid=%d)\n", a_text, a_command, data->unique_identifier); return a_command; } //> //< create_espeak_key, create_espeak_char t_espeak_command* create_espeak_key(const char *key_name, void *user_data) { ENTER("create_espeak_key"); int a_error=1; t_espeak_command* a_command = (t_espeak_command*)malloc(sizeof(t_espeak_command)); if (!key_name || !a_command) { goto key_error; } a_command->type = ET_KEY; a_command->state = CS_UNDEFINED; a_command->u.my_key.user_data = user_data; a_command->u.my_key.unique_identifier = ++my_current_text_id; a_command->u.my_key.key_name = strdup( key_name); a_error=0; key_error: if (a_error) { if (a_command) { free (a_command); } a_command = NULL; } SHOW("command=0x%x\n", a_command); return a_command; } t_espeak_command* create_espeak_char(wchar_t character, void* user_data) { ENTER("create_espeak_char"); int a_error=1; t_espeak_command* a_command = (t_espeak_command*)malloc(sizeof(t_espeak_command)); if (!a_command) { goto char_error; } a_command->type = ET_CHAR; a_command->state = CS_UNDEFINED; a_command->u.my_char.user_data = user_data; a_command->u.my_char.unique_identifier = ++my_current_text_id; a_command->u.my_char.character = character; a_error=0; char_error: if (a_error) { if (a_command) { free (a_command); } a_command = NULL; } SHOW("command=0x%x\n", a_command); return a_command; } //> //< create_espeak_parameter t_espeak_command* create_espeak_parameter(espeak_PARAMETER parameter, int value, int relative) { ENTER("create_espeak_parameter"); int a_error=1; t_espeak_parameter* data = NULL; t_espeak_command* a_command = (t_espeak_command*)malloc(sizeof(t_espeak_command)); if (!a_command) { goto param_error; } a_command->type = ET_PARAMETER; a_command->state = CS_UNDEFINED; data = &(a_command->u.my_param); data->parameter = parameter; data->value = value; data->relative = relative; a_error=0; param_error: if (a_error) { if (a_command) { free (a_command); } a_command = NULL; } SHOW("command=0x%x\n", a_command); return a_command; } //> //< create_espeak_punctuation_list t_espeak_command* create_espeak_punctuation_list(const wchar_t *punctlist) { ENTER("create_espeak_punctuation_list"); int a_error=1; // wchar_t *a_list = NULL; t_espeak_command* a_command = (t_espeak_command*)malloc(sizeof(t_espeak_command)); if (!punctlist || !a_command) { goto list_error; } a_command->type = ET_PUNCTUATION_LIST; a_command->state = CS_UNDEFINED; { size_t len = (wcslen(punctlist) + 1)*sizeof(wchar_t); wchar_t* a_list = (wchar_t*)malloc(len); memcpy(a_list, punctlist, len); a_command->u.my_punctuation_list = a_list; } a_error=0; list_error: if (a_error) { if (a_command) { free (a_command); } a_command = NULL; } SHOW("command=0x%x\n", a_command); return a_command; } //> //< create_espeak_voice_name, create_espeak_voice_spec t_espeak_command* create_espeak_voice_name(const char *name) { ENTER("create_espeak_voice_name"); int a_error=1; t_espeak_command* a_command = (t_espeak_command*)malloc(sizeof(t_espeak_command)); if (!name || !a_command) { goto name_error; } a_command->type = ET_VOICE_NAME; a_command->state = CS_UNDEFINED; a_command->u.my_voice_name = strdup( name); a_error=0; name_error: if (a_error) { if (a_command) { free (a_command); } a_command = NULL; } SHOW("command=0x%x\n", a_command); return a_command; } t_espeak_command* create_espeak_voice_spec(espeak_VOICE *voice) { ENTER("create_espeak_voice_spec"); int a_error=1; t_espeak_command* a_command = (t_espeak_command*)malloc(sizeof(t_espeak_command)); if (!voice || !a_command) { goto spec_error; } a_command->type = ET_VOICE_SPEC; a_command->state = CS_UNDEFINED; { espeak_VOICE* data = &(a_command->u.my_voice_spec); memcpy(data, voice, sizeof(espeak_VOICE)); if (voice->name) { data->name = strdup(voice->name); } if (voice->languages) { data->languages = strdup(voice->languages); } if (voice->identifier) { data->identifier = strdup(voice->identifier); } a_error=0; } spec_error: if (a_error) { if (a_command) { free (a_command); } a_command = NULL; } SHOW("command=0x%x\n", a_command); return a_command; } //> //< delete_espeak_command int delete_espeak_command( t_espeak_command* the_command) { ENTER("delete_espeak_command"); int a_status = 0; if (the_command) { switch(the_command->type) { case ET_TEXT: if (the_command->u.my_text.text) { SHOW("delete_espeak_command > ET_TEXT free text=%x, command=%x, uid=%d\n", the_command->u.my_text.text, the_command, the_command->u.my_text.unique_identifier); free(the_command->u.my_text.text); } break; case ET_MARK: if (the_command->u.my_mark.text) { free(the_command->u.my_mark.text); } if (the_command->u.my_mark.index_mark) { free((void*)(the_command->u.my_mark.index_mark)); } break; case ET_TERMINATED_MSG: { // if the terminated msg is pending, // it must be processed here for informing the calling program // that its message is finished. // This can be important for cleaning the related user data. t_espeak_terminated_msg* data = &(the_command->u.my_terminated_msg); if (the_command->state == CS_PENDING) { the_command->state = CS_PROCESSED; SHOW("delete_espeak_command > ET_TERMINATED_MSG callback (command=0x%x, uid=%d) \n", the_command, data->unique_identifier); sync_espeak_terminated_msg( data->unique_identifier, data->user_data); } } break; case ET_KEY: if (the_command->u.my_key.key_name) { free((void*)(the_command->u.my_key.key_name)); } break; case ET_CHAR: case ET_PARAMETER: // No allocation break; case ET_PUNCTUATION_LIST: if (the_command->u.my_punctuation_list) { free((void*)(the_command->u.my_punctuation_list)); } break; case ET_VOICE_NAME: if (the_command->u.my_voice_name) { free((void*)(the_command->u.my_voice_name)); } break; case ET_VOICE_SPEC: { espeak_VOICE* data = &(the_command->u.my_voice_spec); if (data->name) { free((void *)data->name); } if (data->languages) { free((void *)data->languages); } if (data->identifier) { free((void *)data->identifier); } } break; default: assert(0); } SHOW("delete_espeak_command > free command=0x%x\n", the_command); free(the_command); a_status = 1; } return a_status; } //> //< process_espeak_command void process_espeak_command( t_espeak_command* the_command) { ENTER("process_espeak_command"); SHOW("command=0x%x\n", the_command); if (the_command == NULL) { return; } the_command->state = CS_PROCESSED; switch(the_command->type) { case ET_TEXT: { t_espeak_text* data = &(the_command->u.my_text); sync_espeak_Synth( data->unique_identifier, data->text, data->size, data->position, data->position_type, data->end_position, data->flags, data->user_data); } break; case ET_MARK: { t_espeak_mark* data = &(the_command->u.my_mark); sync_espeak_Synth_Mark( data->unique_identifier, data->text, data->size, data->index_mark, data->end_position, data->flags, data->user_data); } break; case ET_TERMINATED_MSG: { t_espeak_terminated_msg* data = &(the_command->u.my_terminated_msg); sync_espeak_terminated_msg( data->unique_identifier, data->user_data); } break; case ET_KEY: { const char* data = the_command->u.my_key.key_name; sync_espeak_Key(data); } break; case ET_CHAR: { const wchar_t data = the_command->u.my_char.character; sync_espeak_Char( data); } break; case ET_PARAMETER: { t_espeak_parameter* data = &(the_command->u.my_param); SetParameter( data->parameter, data->value, data->relative); } break; case ET_PUNCTUATION_LIST: { const wchar_t* data = the_command->u.my_punctuation_list; sync_espeak_SetPunctuationList( data); } break; case ET_VOICE_NAME: { const char* data = the_command->u.my_voice_name; SetVoiceByName( data); } break; case ET_VOICE_SPEC: { espeak_VOICE* data = &(the_command->u.my_voice_spec); SetVoiceByProperties(data); } break; default: assert(0); break; } } //> //< process_espeak_command void display_espeak_command( t_espeak_command* the_command) { ENTER("display_espeak_command"); #ifdef DEBUG_ENABLED if (the_command == NULL) { SHOW("display_espeak_command > command=%s\n","NULL"); return; } SHOW("display_espeak_command > state=%d\n",the_command->state); switch(the_command->type) { case ET_TEXT: { t_espeak_text* data = &(the_command->u.my_text); SHOW("display_espeak_command > (0x%x) uid=%d, TEXT=%s, user_data=0x%x\n", the_command, data->unique_identifier, (char*)data->text, (int)(data->user_data)); } break; case ET_MARK: { t_espeak_mark* data = &(the_command->u.my_mark); SHOW("display_espeak_command > (0x%x) uid=%d, MARK=%s, user_data=0x%x\n", the_command, data->unique_identifier, (char*)data->text, (int)(data->user_data)); } break; case ET_KEY: { const char* data = the_command->u.my_key.key_name; SHOW("display_espeak_command > (0x%x) KEY=%c\n", the_command, data); } break; case ET_TERMINATED_MSG: { t_espeak_terminated_msg* data = &(the_command->u.my_terminated_msg); SHOW("display_espeak_command > (0x%x) TERMINATED_MSG uid=%d, user_data=0x%x, state=%d\n", the_command, data->unique_identifier, data->user_data, the_command->state); } break; case ET_CHAR: { const wchar_t data = the_command->u.my_char.character; SHOW("display_espeak_command > (0x%x) CHAR=%c\n", the_command, (char)data); } break; case ET_PARAMETER: { t_espeak_parameter* data = &(the_command->u.my_param); SHOW("display_espeak_command > (0x%x) PARAMETER=%d, value=%d, relative=%d\n", the_command, data->parameter, data->value, data->relative); } break; case ET_PUNCTUATION_LIST: { const wchar_t* data = the_command->u.my_punctuation_list; sync_espeak_SetPunctuationList( data); SHOW("display_espeak_command > (0x%x) PUNCTLIST=%s\n", the_command, (char*)data); } break; case ET_VOICE_NAME: { const char* data = the_command->u.my_voice_name; SHOW("display_espeak_command > (0x%x) VOICE_NAME=%s\n", the_command, data); } break; case ET_VOICE_SPEC: { SHOW("display_espeak_command > (0x%x) VOICE_SPEC", the_command); } break; default: assert(0); break; } #endif } #endif //> sources_5316/external/espeak/speak_lib.cpp0000664000176700017670000007553711723710247017501 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2011 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #include "StdAfx.h" #include "stdio.h" #include "ctype.h" #include "string.h" #include "stdlib.h" #include "wchar.h" #include "locale.h" #include #include #include "speech.h" #include #ifndef PLATFORM_WINDOWS #include #endif #include "speak_lib.h" #include "phoneme.h" #include "synthesize.h" #include "voice.h" #include "translate.h" #include "debug.h" #include "fifo.h" #include "event.h" #include "wave.h" unsigned char *outbuf=NULL; espeak_EVENT *event_list=NULL; int event_list_ix=0; int n_event_list; long count_samples; void* my_audio=NULL; static unsigned int my_unique_identifier=0; static void* my_user_data=NULL; static espeak_AUDIO_OUTPUT my_mode=AUDIO_OUTPUT_SYNCHRONOUS; static int synchronous_mode = 1; static int out_samplerate = 0; static int voice_samplerate = 22050; t_espeak_callback* synth_callback = NULL; int (* uri_callback)(int, const char *, const char *) = NULL; int (* phoneme_callback)(const char *) = NULL; char path_home[N_PATH_HOME]; // this is the espeak-data directory extern int saved_parameters[N_SPEECH_PARAM]; //Parameters saved on synthesis start void WVoiceChanged(voice_t *wvoice) {//================================= // Voice change in wavegen voice_samplerate = wvoice->samplerate; } #ifdef USE_ASYNC static int dispatch_audio(short* outbuf, int length, espeak_EVENT* event) {//====================================================================== ENTER("dispatch_audio"); int a_wave_can_be_played = fifo_is_command_enabled(); #ifdef DEBUG_ENABLED SHOW("*** dispatch_audio > uid=%d, [write=%p (%d bytes)], sample=%d, a_wave_can_be_played = %d\n", (event) ? event->unique_identifier : 0, wave_test_get_write_buffer(), 2*length, (event) ? event->sample : 0, a_wave_can_be_played); #endif switch(my_mode) { case AUDIO_OUTPUT_PLAYBACK: { int event_type=0; if(event) { event_type = event->type; } if(event_type == espeakEVENT_SAMPLERATE) { voice_samplerate = event->id.number; if(out_samplerate != voice_samplerate) { if(out_samplerate != 0) { // sound was previously open with a different sample rate wave_close(my_audio); sleep(1); } out_samplerate = voice_samplerate; wave_init(voice_samplerate); wave_set_callback_is_output_enabled( fifo_is_command_enabled); my_audio = wave_open("alsa"); event_init(); } } if (outbuf && length && a_wave_can_be_played) { wave_write (my_audio, (char*)outbuf, 2*length); } while(a_wave_can_be_played) { // TBD: some event are filtered here but some insight might be given // TBD: in synthesise.cpp for avoiding to create WORDs with size=0. // TBD: For example sentence "or ALT)." returns three words // "or", "ALT" and "". // TBD: the last one has its size=0. if (event && (event->type == espeakEVENT_WORD) && (event->length==0)) { break; } espeak_ERROR a_error = event_declare(event); if (a_error != EE_BUFFER_FULL) { break; } SHOW_TIME("dispatch_audio > EE_BUFFER_FULL\n"); usleep(10000); a_wave_can_be_played = fifo_is_command_enabled(); } } break; case AUDIO_OUTPUT_RETRIEVAL: if (synth_callback) { synth_callback(outbuf, length, event); } break; case AUDIO_OUTPUT_SYNCHRONOUS: case AUDIO_OUTPUT_SYNCH_PLAYBACK: break; } if (!a_wave_can_be_played) { SHOW_TIME("dispatch_audio > synth must be stopped!\n"); } SHOW_TIME("LEAVE dispatch_audio\n"); return (a_wave_can_be_played==0); // 1 = stop synthesis } static int create_events(short* outbuf, int length, espeak_EVENT* event, uint32_t the_write_pos) {//===================================================================== int finished; int i=0; // The audio data are written to the output device. // The list of events in event_list (index: event_list_ix) is read: // Each event is declared to the "event" object which stores them internally. // The event object is responsible of calling the external callback // as soon as the relevant audio sample is played. do { // for each event espeak_EVENT* event; if (event_list_ix == 0) { event = NULL; } else { event = event_list + i; #ifdef DEBUG_ENABLED SHOW("Synthesize: event->sample(%d) + %d = %d\n", event->sample, the_write_pos, event->sample + the_write_pos); #endif event->sample += the_write_pos; } #ifdef DEBUG_ENABLED SHOW("*** Synthesize: i=%d (event_list_ix=%d), length=%d\n",i,event_list_ix,length); #endif finished = dispatch_audio((short *)outbuf, length, event); length = 0; // the wave data are played once. i++; } while((i < event_list_ix) && !finished); return finished; } int sync_espeak_terminated_msg( uint32_t unique_identifier, void* user_data) {//===================================================================== ENTER("sync_espeak_terminated_msg"); int finished=0; memset(event_list, 0, 2*sizeof(espeak_EVENT)); event_list[0].type = espeakEVENT_MSG_TERMINATED; event_list[0].unique_identifier = unique_identifier; event_list[0].user_data = user_data; event_list[1].type = espeakEVENT_LIST_TERMINATED; event_list[1].unique_identifier = unique_identifier; event_list[1].user_data = user_data; if (my_mode==AUDIO_OUTPUT_PLAYBACK) { while(1) { espeak_ERROR a_error = event_declare(event_list); if (a_error != EE_BUFFER_FULL) { break; } SHOW_TIME("sync_espeak_terminated_msg > EE_BUFFER_FULL\n"); usleep(10000); } } else { if (synth_callback) { finished=synth_callback(NULL,0,event_list); } } return finished; } #endif static void select_output(espeak_AUDIO_OUTPUT output_type) {//======================================================= my_mode = output_type; my_audio = NULL; synchronous_mode = 1; option_waveout = 1; // inhibit portaudio callback from wavegen.cpp out_samplerate = 0; switch(my_mode) { case AUDIO_OUTPUT_PLAYBACK: // wave_init() is now called just before the first wave_write() synchronous_mode = 0; break; case AUDIO_OUTPUT_RETRIEVAL: synchronous_mode = 0; break; case AUDIO_OUTPUT_SYNCHRONOUS: break; case AUDIO_OUTPUT_SYNCH_PLAYBACK: option_waveout = 0; WavegenInitSound(); break; } } // end of select_output int GetFileLength(const char *filename) {//==================================== struct stat statbuf; if(stat(filename,&statbuf) != 0) return(0); if((statbuf.st_mode & S_IFMT) == S_IFDIR) // if(S_ISDIR(statbuf.st_mode)) return(-2); // a directory return(statbuf.st_size); } // end of GetFileLength char *Alloc(int size) {//================== char *p; if((p = (char *)malloc(size)) == NULL) fprintf(stderr,"Can't allocate memory\n"); // I was told that size+1 fixes a crash on 64-bit systems return(p); } void Free(void *ptr) {//================= if(ptr != NULL) free(ptr); } #ifdef DATA_FROM_SOURCECODE_FILES static void init_path(const char *path) { (void) path; } #else static void init_path(const char *path) {//==================================== #ifdef PLATFORM_WINDOWS HKEY RegKey; unsigned long size; unsigned long var_type; char *env; unsigned char buf[sizeof(path_home)-13]; if(path != NULL) { sprintf(path_home,"%s/espeak-data",path); return; } if((env = getenv("ESPEAK_DATA_PATH")) != NULL) { sprintf(path_home,"%s/espeak-data",env); if(GetFileLength(path_home) == -2) return; // an espeak-data directory exists } buf[0] = 0; RegOpenKeyExA(HKEY_LOCAL_MACHINE, "Software\\Microsoft\\Speech\\Voices\\Tokens\\eSpeak", 0, KEY_READ, &RegKey); size = sizeof(buf); var_type = REG_SZ; RegQueryValueExA(RegKey, "path", 0, &var_type, buf, &size); sprintf(path_home,"%s\\espeak-data",buf); #else char *env; if(path != NULL) { snprintf(path_home,sizeof(path_home),"%s/espeak-data",path); return; } // check for environment variable if((env = getenv("ESPEAK_DATA_PATH")) != NULL) { snprintf(path_home,sizeof(path_home),"%s/espeak-data",env); if(GetFileLength(path_home) == -2) return; // an espeak-data directory exists } snprintf(path_home,sizeof(path_home),"%s/espeak-data",getenv("HOME")); if(access(path_home,R_OK) != 0) { strcpy(path_home,PATH_ESPEAK_DATA); } #endif } #endif static int initialise(int control) {//=============================== int param; int result; LoadConfig(); WavegenInit(22050,0); // 22050 if((result = LoadPhData()) != 1) { if(result == -1) { fprintf(stderr,"Failed to load espeak-data\n"); if((control & espeakINITIALIZE_DONT_EXIT) == 0) { exit(1); } } else fprintf(stderr,"Wrong version of espeak-data 0x%x (expects 0x%x) at %s\n",result,version_phdata,path_home); } memset(¤t_voice_selected,0,sizeof(current_voice_selected)); SetVoiceStack(NULL, ""); SynthesizeInit(); InitNamedata(); for(param=0; param uid=%d, flags=%d, >>>text=%s<<<\n", unique_identifier, flags, text); } #endif if((outbuf==NULL) || (event_list==NULL)) return(EE_INTERNAL_ERROR); // espeak_Initialize() has not been called option_multibyte = flags & 7; option_ssml = flags & espeakSSML; option_phoneme_input = flags & espeakPHONEMES; option_endpause = flags & espeakENDPAUSE; count_samples = 0; #ifdef USE_ASYNC if(my_mode == AUDIO_OUTPUT_PLAYBACK) { a_write_pos = wave_get_write_position(my_audio); } #endif if(translator == NULL) { SetVoiceByName("default"); } SpeakNextClause(NULL,text,0); if(my_mode == AUDIO_OUTPUT_SYNCH_PLAYBACK) { for(;;) { #ifdef PLATFORM_WINDOWS Sleep(300); // 0.3s #else #ifdef USE_NANOSLEEP struct timespec period; struct timespec remaining; period.tv_sec = 0; period.tv_nsec = 300000000; // 0.3 sec nanosleep(&period,&remaining); #else // sleep(1); #endif #endif if(SynthOnTimer() != 0) break; } return(EE_OK); } for(;;) { #ifdef DEBUG_ENABLED SHOW("Synthesize > %s\n","for (next)"); #endif out_ptr = outbuf; out_end = &outbuf[outbuf_size]; event_list_ix = 0; WavegenFill(0); length = (out_ptr - outbuf)/2; count_samples += length; event_list[event_list_ix].type = espeakEVENT_LIST_TERMINATED; // indicates end of event list event_list[event_list_ix].unique_identifier = my_unique_identifier; event_list[event_list_ix].user_data = my_user_data; count_buffers++; if (my_mode==AUDIO_OUTPUT_PLAYBACK) { #ifdef USE_ASYNC finished = create_events((short *)outbuf, length, event_list, a_write_pos); length = 0; // the wave data are played once. #endif } else { finished = synth_callback((short *)outbuf, length, event_list); } if(finished) { SpeakNextClause(NULL,0,2); // stop break; } if(Generate(phoneme_list,&n_phoneme_list,1)==0) { if(WcmdqUsed() == 0) { // don't process the next clause until the previous clause has finished generating speech. // This ensures that

:=# _x§xx‚_x,-F‚;(*ø¶1¶úhhHd H (`(B+)+  _x§xx‚_x,-F‚;(*ø¶¼hW¶@ú¾¨À|à <æ2*;52/"£w…xxx‚wx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¨À|à <æPE&LEA=,£w…xxx‚wx,-F‚;(˜h¿Å.–¶ú¨À|à <æ<8"E>:7'£w…xxx‚wx,-F‚;(*ø¶1¶ú¨À|à <æ 4/,) £w…xxx‚wx,-F‚;(*ø¶¼hW¶@ú¹”0î< * 2`-%6930!  oxxx‚ox,-F‚;(r•¶¨h¿ÅHø¶°ú–¶”0î< * 2`KAHLD@, oxxx‚ox,-F‚;(˜h¿Å.–¶ú”( \ * 2`A0=@96% oxxx‚ox,-F‚;(*ø¶1¶ú”( Œ * 2` +.)'  oxxx‚ox,-F‚;(*ø¶¼hW¶@úi°  ” xX-*0:%" ¥~‘xxx¥s‚,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¨  ” xX3/3¶x……Ž¡»}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶•ÏÖ p †*<8F:5: ¶x……Ž¡»}‰,-F‚;(˜h¿Å.–¶ú•ÏÖ p †*21>/.1¶x……Ž¡»}‰,-F‚;(*ø¶1¶ú•ÏÖ p †*-;-,/¶x……Ž¡»}‰,-F‚;(*ø¶¼hW¶@ú}°È  îÀ-*8?$ ¥”‡xxx§Ž‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶°È  îÀ(\$R]5,% ¥”‡xxx§Ž‡,-F‚;(˜h¿Å.–¶ú°È  îÀ#K JT0'! ¥”‡xxx§Ž‡,-F‚;(*ø¶1¶úõ–V å ÑkP>EF+$ ¤Œxxx§Ž‡,-F‚;(*ø¶¼hW¶@úº‰„ Ÿ ‹¤(0=&£†šxxx§Ž‡,-F‚;(hW¶¨i¿M|V¶@ú¸p„ì ” ˆ 2¢…›xxx¢¥,-F‚;(ßúæHˆ(´ p ¿ --@7" Ï–ixxxí¥¥,AF‚62r•¶¨h¿ÅHø¶°ú–¶Hˆ(´ p ¿ Fg-aS4- Ï–ixxxí¥¥,AF‚62˜h¿Å.–¶ú7dŒ  t ½ FP(XN0( Ërxxxí¥¥,!!§““xxx§Ž‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ð°$ ¼ \W(`I\00+ §““xxx§Ž‡,-F‚;(˜h¿Å.–¶úè” L È hW#NBQ++& §““xxx§Ž‡,-F‚;(*ø¶1¶úÈ ¬Ü ø œWPJBK++& §““xxx§Ž‡,-F‚;(*ø¶¼hW¶@úº‰„ Ÿ ‹¤(1=&£†šxxx§Ž‡,-F‚;(hW¶¨i¿M|V¶@ú¸p„ì ” ˆ 2¢…›xxx¢¥,-F‚;(ßúÿ¨\X h  -84@'$ §‡–xxx§‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¨\X h  FlIY62§‡–xxx§‡‡,-F‚;(˜h¿Å.–¶ú¨ð\< ’ žPZGQ1-¨†‘xxx§‡‡,-F‚;(*ø¶1¶ú°8\8 <<5O+! ±}fxxx±}u,-F‚;(*ø¶¼hW¶@ú°8\8 <!># ±}fxxx±}u,-F‚;(hW¶¨i¿M|V¶@úúÈ̉РРEh-..1% ¸l€xxx¹k,-F‚;(r•¶¨h¿ÅHø¶°ú–¶È̉РРEhPGL=J9, ·m•xxx¹k–,-F‚;(*ø¶1¶ú²G³? 0¦A*G% ²|gxxx¹k,-F‚;(*ø¶¼hW¶@ú²G³? 0¦< ²|gxxx¹k,-F‚;(hW¶¨i¿M|V¶@ú˜(˜ \ ‡ -.))* §ixxxx§Zx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶˜(„ \ ‡ <>NFFG"§ixxxx§Zx,-F‚;(˜h¿Å.–¶ú›+¼à Q }žP5L6==!¨k–xxx§Z˜,-F‚;(*ø¶1¶ú®>ÇP  @‘#'G$ °{gxxx§Zx,-F‚;(*ø¶¼hW¶@ú°@˜8 <(%C! ±}fxxx±}u,-F‚;(hW¶¨i¿M|V¶@ú°@˜8 << ±}fxxx±}u,-F‚;(ßúú(èðÄ p (™-*9<+# ׊xxxí¥¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶(èðÄ p (™PQ)OS<0% ׊xxxí¥¥,-F‚;(˜h¿Å.–¶úº´ b GP@#GH5+" Ò…Žxxxí¥¥,-F‚;(*ø¶1¶ú„(¸$ ä `d-*=)#&# ¥Z‡xxx¥‡‡,-F‚;(*ø¶¼hW¶@ú„(¸$ ä `d0! ¥Z‡xxx¥‡‡,-F‚;(hW¶¨i¿M|V¶@úúô#?è & °-.-0%Êvxxx‡´–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ô#?è & °PR(OMQ?. Êvxxx‡´–,-F‚;(˜h¿Å.–¶úô#?è & °PI&KHM<+ Êvxxx‡´–,-F‚;(*ø¶1¶ú„¸$ ä `d-/?+%($ ¥Z‡xxx¥‡‡,-F‚;(*ø¶¼hW¶@ú„¸$ ä `d2"  ¥Z‡xxx¥‡‡,-F‚;(hW¶¨i¿M|V¶@úúzÀðt ä ö_-1;E)+ª…‡z|€Åƒx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶zÀðt ä ö_PO$KX47&ª…‡z|€Åƒx,-F‚;(˜h¿Å.–¶úzÀðt ä ö_P@ DO/1#ª…‡z|€Åƒx,-F‚;(*ø¶1¶ú„¸$ ä `d-/?+%($ ¥Z‡xxx¥‡‡,-F‚;(*ø¶¼hW¶@ú„¸$ ä `d2"  ¥Z‡xxx¥‡‡,-F‚;(hW¶¨i¿M|V¶@úú!˜ à 4  --B;;<¯ixxxx¯Zx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶˜è 4  PH SIJK$§ixxxx§Zx,-F‚;(˜h¿Å.–¶ú˜è Ø@P- <+IZ\eK ,2 ïØÐâæ§—ÕßáéÜê *"%G$1öâøåîÓîáúùÌî "+!-@.$<< õæäßÚ¢ÚÇÙëâ'ô"ò ,ðóçÒÐÝüîî̹ööÝ #í)( FgF2JD1& ûîÜ™µÔ×Ñ«¥áïÌÎàÌøñÿ1: í0#%Üà*îçó ,X2õñÅðóɸôîÔãí7 Þø_HäÄßÿ çý(/ÜâA="! )ýòøû×ÅÎĨ¤ÉÎÞõºã5ZÛ'+ ìÍôÿéÙ$úêþìG7%+è óïìæóòèõ÷×¾×ÞÝýÿð=0 ñ!öÿçÖûûäûþ×öñéþ.;:1öñ&ñ¯¸ÍèüÁœÎýïÏå .FELE<"A7ÿ¶ÍüþîϺÔîÖÝÌô.(óý'!òåèàýÙý õþüû8èñõ üî 0@'.eÛ)êÈÛôÎÞ æêó"#;P813 òÄØÒÁÁ¡à±žÝóö× .!3#7$ÿضÕÜÐÖÖÊÚüýþü&þB+>iIAM:1(ñè"ï´íê½êþâòþ5=>=% ù ðÅÝóÌàâÓ#ûê ò%1Ì U-úî ô÷  *îüüø¶Ô1)ïëïáÇã½ÐÛÖ ñÙ1&7a0+ÆÝÆËëÃçí´î" 5lP.4..# òæûΛ¾Ö»ÐÙà ç!(+îåîÈï"""ûÍê8#ç5%!ûô3æéÑ÷çØ§Úä¿ÝçÛÛú,=ü!>.ö òìçäóãÛ >(jF]h7òÄ·Ýé°ˆœÀ³·¸ž½ãõôû8B'øíÿøçÑÜÞì!/"5;(**/'ÜϲšÃس²Á× ë:CG] 06 õ!Øß%BCøâ  áãáåÜåû%áæâòþòô ü èÿôéÿñËåûâîñï äù= â!*ò,û"ÿúõã ! Ç×óÍоÓøÏðüâí2J/W6 A.ýïóúæáîÜþÈÌó"èç(&ûO-à8 õ»ô*ÛïòéòÜÍôì×ÿí %.75:7$øùëçýÏ¡ÐòÝÒì ãØóùû/.G`.2#çÈïüüḴ¾ÓèáÝÿ.!;0$ôþíìøð÷äÔ½¤²Þþ.C7û&.,:(  êÖóä´­ºÒóÝÀèøö á ;-# 6*  öÚùðÆÙëôúêç #õ×ääßÑÛÜÎÓá×À×õø @54JP^V3)ñÝõéÝ áôêØþÓ > íýþ ,ù ñ÷ÕÁæòÖØíò%3 Í×þý÷îò×ãûúöõ #ñÐþùßãÖßü û÷ý #(÷íÚÐ׿çøäýþç ô( ñýõÙÜèý üí4)%@ó ßüõø(íèßÇÒóÒÌîåèõöôû*EHó-íäéöðÖãþ÷ôëàú þéó, ,5%"ùûÿçùýÿßõùÖÞ÷øûìéãîîø $ê8(-!ãéôòûþúø ÿùåçÿóÔêóÆØóì÷÷úîî!/4/H-ù÷ñí÷ûóÝÒâ èï ôáööòòðöóÕàÿø÷ &*2'% ùóíÐßñäæäÙëìÚïþßå ((,0 ïõýÞâòçÝÓÈäíÓÍÕñ#$".=94#0'ïÞîë˽À»ÌäÒÍê"  2#  ùõôøõãöïåüîÎåøô ÿ # ìêúáÉÕ̺ËÜÜðòîü4?%&C:ïüÿíàÌ×ñÕÇÝÞßþø41=81IL3&Ý£xxx–£–,-F‚;(˜h¿Å.–¶úÈP,œ 4 (?$BN6,!Ý£xxx–£–,-F‚;(*ø¶1¶úÈP,œ 4 !26(! Ý£xxx–£–,-F‚;(*ø¶¼hW¶@ú ¬@ÏÖ p †*2*=3/3¶x……Ž¡»}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¬@ÏÖ p †*<6E:5:¶x……Ž¡»}‰,-F‚;(˜h¿Å.–¶ú¬@ÏÖ p †*2/=/.1¶x……Ž¡»}‰,-F‚;(*ø¶1¶ú¬@ÏÖ p †*" 5)(* ¶x……Ž¡»}‰,-F‚;(*ø¶¼hW¶@úÃ!˜$ @ „ d 2+A555 §ixxxx§Zx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶˜$ @ „ d KB PAAA#§ixxxx§Zx,-F‚;(˜h¿Å.–¶ú˜$ T „ d F6 I;;;§ixxxx§Zx,-F‚;(*ø¶1¶úvð# , H <p0*)* «ipxxx¯‡x,-F‚;(*ø¶¼hW¶@úÃxP œ ä dZ- 33,& ¨p”xxxkpx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶xP œ ä dZK.<<5-&¨p”xxxkpx,-F‚;(˜h¿Å.–¶úxP œ ä dZK)992+$¨p”xxxkpx,-F‚;(*ø¶1¶úxP œ ä dZ 33,& ¨p”xxxkpx,-F‚;(*ø¶¼hW¶@úx°@48 <2#=$ ±}fxxx±}u,-F‚;(r•¶¨h¿ÅHø¶°ú–¶°@48 <F;P0( ±}fxxx±}u,-F‚;(˜h¿Å.–¶ú°@48 <2$>% ±}fxxx±}u,-F‚;(*ø¶1¶ú°@48 <2 ±}fxxx±}u,-F‚;(*ø¶¼hW¶@ú¯¬(ä` <-(C0 ±udxxx±us,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¬(ä` <F?T< $ ±udxxx±us,-F‚;(˜h¿Å.–¶ú¬(ä` <<8O9" ±udxxx±us,-F‚;(*ø¶1¶ú¬(ä` <&A. ±udxxx±us,-F‚;(*ø¶¼hW¶@ú}°h\8 l <-+E, ±}nxxx±}},-F‚;(r•¶¨h¿ÅHø¶°ú–¶°h\8 l <PFX8  ±}nxxx±}},-F‚;(˜h¿Å.–¶ú°h\8 l <F9O2 ±}nxxx±}},-F‚;(*ø¶1¶ú°h\8 l <&A) ±}nxxx±}},-F‚;(*ø¶¼hW¶@ú¥´ÀÄÔ” â-"33$$ª}‘xxx¢}‘,-F‚;(r•¶¨h¿ÅHø¶°ú–¶´ÀÄÔ” âF< DD00( ª}‘xxx¢}‘,-F‚;(˜h¿Å.–¶ú´ÀÄÔ” â26@@--& ª}‘xxx¢}‘,-F‚;(*ø¶1¶ú´ÀÄÔ” â//!!ª}‘xxx¢}‘,-F‚;(*ø¶¼hW¶@ú¯tÐtP 0 Ä`-(99%"§–‡xxxÅxx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶tÐtP 0 Ä`FO PP40,§–‡xxxÅxx,-F‚;(˜h¿Å.–¶útÐtP 0 Ä`<@HH.+'§–‡xxxÅxx,-F‚;(*ø¶1¶útÐtP 0 Ä`#55" §–‡xxxÅxx,-F‚;(*ø¶¼hW¶@útŒt ¼ tX(,9E'(§–‡xxxÅxx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶tŒt ¼ tXBa+Tf9<. §–‡xxxÅxx,-F‚;(˜h¿Å.–¶ú|ô(¬ è ~€^2 vjGxwumr >vjUI 1=qqyA!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!>}eoyih#$ALS:tè4Œ h|: ÈÔ»ÿÿ¯ÈÔ»,-F‚;(r•¶¨h¿ÅHø¶°ú–¶tè4Œ h| ÈÔ»ÿÿ¯ÈÔ»,-F‚;(˜h¿Å.–¶útè4Œ h| ÈÔ»ÿÿ¯ÈÔ»,-F‚;(*ø¶1¶úøþó  ’¶7Bìõúãÿ$çþýñóèç ü÷òýâÜ'øóèâú ù Øäü !ßÞú ý ÓüüµÄ D éìç(ýíç2÷êá&þÿÞÀóC/"÷À+æïäþÚÒò$ý Ö6Þöòøæ=*š F¢ Øè1"ÍìWßáá<µ×`GÂáa¡ÇAØ T¶Ü,øõÌ0NÐýà ñåÒ"(óñÙü×!(íØÞÁ/'ãîò=+£ì)GîÐáÿ$â%)õÛú ãí,Bæ¦÷<'1²¯:2ò²Ý`1èÎÛî65­úüùÐöP òîÛ$âÿ%þ$Æ0 äÁü5# ÞÍ,1àÒ*ýáëEïÓ ´írÛÿïÓë>áî , ÙÚò1õËå5ù2Ý×àù<%ç2•ì7-Úëõÿ,%üÊ"èé)ü¿á$OóçðÒ¸6RôôÖê×ö-íòëù!5¤…`` ¦'Ö¸ýI!ù¶Ú!+ ÙêEì²ú3íèå 2 íýõ³ 3IÑöøóÎÿ&ùðöÌäó$KèÑó&óÿÌñ97Þà & ÐÖíû7íÖ¾2ßüßÝô  ?ðßÿòîÌð2D8¥æ Ñ(Æ9%ûžÉLËÕB÷Ùúå Ù@öòëúÖÿ(íùWÄ÷ôíñü8%àúõÖ÷ú6ìÀDéã%Åîî'JÙÞèÐêCMùÑ)ÚÎÞô\2ÉçåÖ/#¹Ò4åô)7 ¤èÆðNh4륪+ üÑä îáî ý õñüé&ãÒú ëéÉæ ,6æ¤Ñ$*ïúìÊì 'ôÞÅ+ï.+ýìÞÔ#û'ààñú%=òÄÊî 2&üÚáêþ2#ãúâüíê%ûìùðöøïó ýýìñ-ôÞøÿñùíüîòð"éßÂÉ-L(üúêõúìá(#ý éîÏë*%;ï𲿠=Q.ÕÞéðî , ×Ôð!ýÖÙå7?çÌÉð)"í¶Ó5 ÝæôÿöùãÚ$åÚà 2óÖúðþ*äÎî&òãý ñôóõòó æé! ôêæñï % Ôßû õ ?+ßÖð'øçñ  èÜü}žÜ´¦ g `¢}+™s€xxx¥‡‡,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶ú<üZæ © ¸`< ÁˆŒxxx‡´–,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶úAÜn8´ BøA ¤€xxxi¹”,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶ú_?¶P@ ‹ !`P--0D#& ݇›xxx–´–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶%ͤÈ, ) }ô% š‹xxx–´–,-F‚8(˜h¿Å.–¶ú%¸ °( ê `à(  F¯–xxxU‚»,-F‚5(*ø¶1¶ú_¸ˆ¼  X °ŸP..9$ ±dƒxxxi‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶%¸ °( ê `à "  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶ú%¸ °( ê `à(  ŽŒzxxx¬n˜,-F‚5(*ø¶1¶úZ–<)¦ S j Z  ›‘€xxxÅxx,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶úAìâìZ ­ A ´“qxxx÷ª¥,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶úF¬D; { c0F #2,.$ £~}xxx¹u,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶ú2²ÖÀÿ ­ s…2(!#! ¢‚~ƒŒ»}‰,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶ú(¬F Ç w€((.! ™‰ˆxxx¥‡‡,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶ú2´Öò° { Î82% „pxxx±}u,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶úJ%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶@H h à"03/$ ô„Ÿxxx‡´–,-F‚;(˜h¿Å.–¶úJ%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶€(¡` ¼ t`$3?# §–‡xxxÅxx,-F‚;(˜h¿Å.–¶úK%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶pÀ@ 0 $*00(º¯‡xxxi¹”,-F‚;(˜h¿Å.–¶úK%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶?¶P@ ‹ !`--0D#& ݇›xxx–´–,-F‚;(˜h¿Å.–¶úJ%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶„¸$ ä `dCL3,0, §Z‡xxx§‡‡,-F‚;(˜h¿Å.–¶úJ%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶À³\ü¸ < +Q xRZxxxKRZ,-F‚5(˜h¿Å.–¶úK%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ˆ¼  X °Ÿ..9$ ±dƒxxxi‡‡,-F‚;(˜h¿Å.–¶úd%¸ °( ê `àd(  F¯–––xU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶œc®  \  '(%§Z‡xxxzxx,-F‚9(˜h¿Å.–¶úJ%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶p ¡$ ¼ t`<"BP-/$§–‡xxxÅxx,-F‚;(˜h¿Å.–¶úK%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶ X(Œ p ¿ 5E9* Ù›ixxx÷ª¥,AK‚62˜h¿Å.–¶úJ%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶ èÆì e€)8;:." ¹pxxx¹u,-F‚;(˜h¿Å.–¶úd%¸ °( ê `àd(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¬@ÏÖ p †*1)&) ¶x……Ž¡»}‰,-F‚;(˜h¿Å.–¶úJ%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶™œøx ” °ô#4% ¥~‘xxx¥s‚,-F‚;(˜h¿Å.–¶úJ%¸ °( ê `àK(  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶°@48 <#=$ ±}fxxx±}u,-F‚;(˜h¿Å.–¶ú ¸ °( ê `à (  F¯–xxxU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à(  F¯–xxxU‚»,-F‚5(˜h¿Å.–¶ú<È °( ê `à  –¯¯xxxd}},-F‚5(r•¶¨h¿ÅHø¶°ú–¶È °( ê `à  –¯¯xxxd}},-F‚5(˜h¿Å.–¶úÈ °( ê `à –¯¯xxxd}},-F‚5(*ø¶1¶ú7È °( ê `à7  –¯¯xxxd}},-F‚;(r•¶¨h¿ÅHø¶°ú–¶È °( ê `à  –¯¯xxxd}},-F‚;(˜h¿Å.–¶úZt ¡$ ¼ t`Z$.§–‡xxxÅxx,-F‚7(r•¶¨h¿ÅHø¶°ú–¶¸l°( ê `à # F¯–––xU‚»,-F‚5(˜h¿Å.–¶úA X(Œ p ¿ A# 50 Ù›ixxx÷ª¥,AK‚52r•¶¨h¿ÅHø¶°ú–¶¸l°( ê `à # F¯–––xU‚»,-F‚5(˜h¿Å.–¶ú<@H h à<+1'& ô„Ÿxxx‡´–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¸l°( ê `à # F¯–––xU‚»,-F‚5(˜h¿Å.–¶ú2¬@ÏÖ p †*2/A626¶x……Ž¡»}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¸l°( ê `à # F¯–––xU‚»,-F‚5(˜h¿Å.–¶ú(  „Ø ¤  (W"BT3.¥‡–xxx¥‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¸l°( ê `à # F¯–––xU‚»,-F‚5(˜h¿Å.–¶ú2°@48 <2$>% ±}fxxx±}u,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¸l°( ê `à # F¯–––xU‚»,-F‚5(˜h¿Å.–¶ú(„¸$ ä `d(+<(#&# §Z‡xxx§‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¸l°( ê `à # F¯–––xU‚»,-F‚5(˜h¿Å.–¶ú/%¸l°( ê `à  F¯–––xU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶%¬†°P ê `à "  jˆ‡‡xU‚»,-F‚5(˜h¿Å.–¶ú  °x ê `à ŽŒzxxx¬n˜,-F‚5(*ø¶1¶ú-%¸l°( ê `à- # F¯–––xU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¸l°( ê `à  F¯–––xU‚»,-F‚5(˜h¿Å.–¶ú/¸ °( ê `à  F¯–––xU‚‰,#2<5(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à  F¯–––xU‚»,-F‚5(˜h¿Å.–¶ú¸ °( ê `à # F¯–––xU‚»,-F‚5(*ø¶1¶ú¸ °( ê `à % F¯–––xU‚»,-F‚5(*ø¶¼hW¶@ú-  L( ê `à/& F¯–––xU‚»,-F‚5(r•¶¨h¿ÅHø¶°ú–¶¬ ~( ê `à#*" ŽŒzxxx¬n˜,-F‚5(˜h¿Å.–¶ú¸ °( ê `à(  F¯–xxxU‚»,-F‚5(*ø¶1¶ú¸ °( ê `à(  F¯–xxxU‚»,-F‚5(*ø¶¼hW¶@ú-”xdT ‡à-# :$(3 fixxxfZ,-F‚4(r•¶¨h¿ÅHø¶°ú–¶|ÑpT D ¿ BNF00xxxxxxKxx,-F‚;(˜h¿Å.–¶úbjæ< %rK- ›pxxx ‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶@½T 4 ë€0  –‡xxxxxQ=xx–xxxKZi,-F‚7(˜h¿Å.–¶ú X(Œ p ¿ 5E9* Ù›ixxx÷ª¥,AK‚62*ø¶1¶ú´?¶P@ ‹ !`2%(+=# ݇›xxx–´–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶?¶P@ ‹ !`(C7;R+/ ݇›xxx–´–,-F‚;(˜h¿Å.–¶ú?¶P@ ‹ !`2615J&* ݇›xxx–´–,-F‚;(*ø¶1¶ú?¶P@ ‹ !`(0.2F$( ݇›xxx–´–,-F‚;(*ø¶¼hW¶@ú?¶P@ ‹ !`!.݇›xxx–´–,-F‚;(hW¶¨i¿M|V¶@úȸX¼< X °Ÿ2%)3 ±dƒxxxi‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¸X¼< X °Ÿ2:#3@  ±dƒxxxi‡‡,-F‚;(˜h¿Å.–¶ú¸X¼< X °Ÿ2:#3@  ±dƒxxxi‡‡,-F‚;(*ø¶1¶ú¸X¼< X °Ÿ23!0= ±dƒxxxi‡‡,-F‚;(*ø¶¼hW¶@ú¸X¼< X °Ÿ%)3 ±dƒxxxi‡‡,-F‚;(hW¶¨i¿M|V¶@ú:tÈfè |0  ÈÔ»ÿÿ¯ÈÔ»,7A2<r•¶¨h¿ÅHø¶°ú–¶tØûÊf |  ÈÔ»ÿÿ¯ÈÔ»,7A2<˜h¿Å.–¶ú¸ °( ê `à(  F¯–xxxU‚»,-F‚5(*ø¶1¶ú#tèü< è |#ÈÔ»ÿÿ¯ÈÔ»,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¸ °( ê `à F¯–xxxU‚»,-F‚5(˜h¿Å.–¶ú:tÐh( è |0 ÈÔ»ÿÿ¯ÈÔ»,2U2<r•¶¨h¿ÅHø¶°ú–¶~Ô"« f |  ÈÔ»ÿÿ¯ÈÔ»,2U2<˜h¿Å.–¶úˆØÜ. ä | ÈÔ»ÿÿ¯ÈÔ»,2U6(*ø¶1¶ú:tÈÐ" è |0  ÈÔ»ÿÿ¯ÈÔ»,KŒ0<r•¶¨h¿ÅHø¶°ú–¶tÈÖ( f |  ÈÔ»ÿÿ¯ÈÔ»,KŒ0<˜h¿Å.–¶útÈÜ. ä |  ÈÔ»ÿÿ¯ÈÔ»,2U6(*ø¶1¶ú#tÈÆ" è | d–––––d––,KŒ8(r•¶¨h¿ÅHø¶°ú–¶–´;¥ é <®  U¢–‡‡‡d––,2U6(˜h¿Å.–¶ú¸ °( ê `à(  F¯–xxxU‚»,-F‚5(*ø¶1¶ú¼3ÿžæ92 þãÝéþëçêóþ úöõù ÷ûøúÿûúùö Ù“¢êARCäÐÓõ*4.˪Àõ#9- ìçÔï"" ôÝÕ÷" õóÄÚé8"öåàõûçìäô üïýï ýõú÷ ÿöúì  ðòúùú  üëÔÐñ"%þå׿ôù"/=êÐÝîáø17ëÆæûîóòÿü ëóþýþ  ùþþÐÙãþ(ûðòúæäðúþÿüüýöÛè ÿÿýùÿ ;ʃ¡òðRDØ ÷ìß;(¦õßüù õ.1ä;)ù, öEñ$/Ùøñ .ûîCæ#/ )UHï9Fõ $'KÙ =ý9Bß&M$ëòB<í40Ð=-êã DÊòaãü^Øð2ÿü)ëQëû@ÖÕPïÒP!¹'â%ïà/ÿ$&>þ *ï0ï<õDÝð6êÔý_1’YÊ fäóTøNëà&%ÄKÑ>ê÷ ô8 í#:éûC$Ö5=Mì:/ û *à ñ2ËîH< ú5î)<ÿý)ìÊ;IËÿ»M™ý`mÍÃB7 ìÀ),Ë)aï×üE5ôâU_·ÐH@òçõ 3ë ü1 ¡@NðøH4ê-âî(ôþøòúï Ý ×P ø(&"Òõ"ýF × "/æÚD3$ì 2·»×êõ5ïÆ$í$"×7õ[;,(íHx@'B/G9ü FÈ éæ$3A-ùí)úHWËðUÙ %)xÃøC ¸×<+Öx1Ñß(­ö5ýùùÕ,z}ps"~s " ssqsrsts7ux|# }#"v# ‡#9#9"Ž#9"…#:#: ”own–$Šn "ˆn tx{o|% ‹%"Œ% "}€} “'‚}"ƒ}"‰}9†~•rs(„("{Œ‘%"’s","j/:ƒ´? |@ ‹ !`2&%%B)# ÝÈ›xxx–õ–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶? |@ ‹ !`(G22Y7/ ÝÈ›xxx–õ–,-F‚;(˜h¿Å.–¶ú? |@ ‹ !`29--P1* ÝÈ›xxx–õ–,-F‚;(*ø¶1¶ú? |@ ‹ !`(-((G,% ÝÈ›xxx–õ–,-F‚;(*ø¶¼hW¶@ú? |@ ‹ !`2ÝÈ›xxx–õ–,-F‚;(hW¶¨i¿M|V¶@ú¯aD† ò ÐB-':1/0 §d|xxx§Zx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶aD† ò ÐBFKQDBB& §d|xxx§Zx,-F‚;(˜h¿Å.–¶úaD† ò ÐB<=I=;<" §d|xxx§Zx,-F‚;(*ø¶1¶úaD† ò ÐB"7.-- §d|xxx§Zx,-F‚;(*ø¶¼hW¶@ú× \Àf ž v-#8:%"Ñ¥¤‚xx§i¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ \Àf ž v! ±dƒxxxi‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ÀÀH& Ð /Ÿ2M#?W- ±dƒxxxi‡‡,-F‚;(˜h¿Å.–¶úÀÀH& Ð /Ÿ2M#?W- ±dƒxxxi‡‡,-F‚;(*ø¶1¶úÀÀH& Ð /Ÿ(15B' ±dƒxxxi‡‡,-F‚;(*ø¶¼hW¶@úÀÀH& Ð /Ÿ-)! ±dƒxxxi‡‡,-F‚;(hW¶¨i¿M|V¶@úd°H„8 <2$:+±¯fxxx±¯u,-F‚;(r•¶¨h¿ÅHø¶°ú–¶°H„8 <2=L8( ±¯fxxx±¯u,-F‚;(˜h¿Å.–¶ú°H„8 <F-@1#±´fxxx±´u,-F‚;(*ø¶1¶ú°H„8 <-# ±Èfxxx±Èu,-F‚;(*ø¶¼hW¶@únÔjÈ  îÀ-:>J(! ¥”‡xxx§Ž‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ÔjÈ  îÀA‰*_r>3+¥”‡xxx§Ž‡,-F‚;(˜h¿Å.–¶úÔjÈ  îÀ(o&Vf7.'¥”‡xxx§Ž‡,-F‚;(*ø¶1¶úÚxè¡ m G<2^G]5*%¦‘‰xxx§Ž‡,-F‚;(*ø¶¼hW¶@úØ Ä þ Ø(KDD/+£xxxx¥s‚,-F‚;(hW¶¨i¿M|V¶@úØ Ä þ Ø599($£xxxx¥s‚,-F‚;(ßú-t褰 ˜ <|-  ÈÔ»ÿÿ¯ÈÔ»,-F‚;(r•¶¨h¿ÅHø¶°ú–¶tè¤Ø À P|  ÈÔ»ÿÿ¯ÈÔ»,-F‚;(˜h¿Å.–¶útè¤Ø À P|  ÈÔ»ÿÿ¯ÈÔ»,-F‚;(*ø¶1¶ú:tèüð è |:  ÈÔ»ÿÿ¯ÈÔ»,-F‚;(r•¶¨h¿ÅHø¶°ú–¶tèüð è |  ÈÔ»ÿÿ¯ÈÔ»,-F‚;(˜h¿Å.–¶útèüð è |  ÈÔ»ÿÿ¯ÈÔ»,-F‚;(*ø¶1¶ú*^$*,-*"æÄ«¦³ÌæùÞ¹¤¨Ãàó/PffO, ôâ騦»æD[abd`K"~–Ÿ®¿Õõ Nq}pQ, êÈ¥‰ƒ™Æû'F[jrnW.üʨ™™£´ÌïGhtjR5õЫ‰š»ä (@R\[I(ÿؼ®ª¬´Æå 0KUPB.úظ¡š¦Àá9M[^R7ôÛËÁ½ÁÎå3=>7*íÕûÀÎáõ)46-õåÙÒÏÒÜëÿ ()&øçÛÖÙâîû'(!úîåàßáéô !üðèäæëóý  ÿöîéçèîö  ýõîëëïõü ûöòððóùÿ  ûøõõöùü ýûúúûýÿÿþþþÿ¯ BÄ‚ p 0 -1A:& º˜xxxxÀ›‡,-F‚:(r•¶¨h¿ÅHø¶°ú–¶ BÄ‚ p 0 Fd+\S7+ º˜xxxxÀ›‡,-F‚9(˜h¿Å.–¶ú BÄ‚ p 0 62* ­o…yy‚»~‰,-F‚;(˜h¿Å.–¶ú…]¤òÐ rF9D71-& ­o…yy‚»~‰,-F‚;(*ø¶1¶ú…]¤òÐ r#6,&# ­o…yy‚»~‰,-F‚;(*ø¶¼hW¶@úõHˆ(Œ p ¿ -2 C;" Ï–ixxxí¥¥,-F‚8-r•¶¨h¿ÅHø¶°ú–¶Hˆ(Œ p ¿ (e+`U1+ Ï–ixxxí¥¥,-F‚9-˜h¿Å.–¶ú7d€Œ t ½ KR)XN0( Ërxxxí¥¥,-F‚8-*ø¶1¶ú˜08 ¤ è Ü (;DD=6 §nxxxx§nx,-F‚7(*ø¶¼hW¶@úi08 ¤ è Ü]-33/. ¬jmxxx§nx,-F‚7(hW¶¨i¿M|V¶@úi08 ¤ è Ü]33/. ¬jmxxx§nx,-F‚6(ßúªåØ# ã éÖ25=E'* ½Ÿˆxxxí¥¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶åØ# ã éÖFR&MV05½Ÿˆxxxí¥¥,-F‚;(˜h¿Å.–¶úåØ# ã éÖ2D#FN,0½Ÿˆxxxí¥¥,-F‚;(*ø¶1¶úåà# ã éÖ&67"% ½Ÿˆxxxí¥¥,-F‚;(*ø¶¼hW¶@úsˆàt ø ð_-,9B')ª‰‡z|€Å‰x,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ˆàt ø Ü_FG"HS14ª‰‡z|€Å‰x,-F‚;(˜h¿Å.–¶úˆê\ ã _F@!EO/2ª‰‡z|€Å‰x,-F‚;(*ø¶1¶úˆð$ ² _$4;#&ª‰‡z|€Å‰x,-F‚;(*ø¶¼hW¶@úÇðt ˜ #@359H&'᥇xxxáx‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ðt H ¿@K_"QX37%§¥¥xxx§i¥,-F‚;(˜h¿Å.–¶úðÄÈ H ¿@M MS04#§¥¥xxx§i¥,-F‚;(*ø¶1¶ú!Äàùè¼ ÷ @!';6-,-§–´xxx§x‡,-F‚;(*ø¶¼hW¶@úÁР­  å@()921+( §i´xxx§x‡,-F‚;(hW¶¨i¿M|V¶@úÀ¨ÐÄ @2,,&" §d´xxx‰U–,-F‚;(ßúá±u%f 2 7”-& 51 ¢•xxx¢¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶±u%f 2 7”2< B= ¢•xxx¢¥,-F‚;(˜h¿Å.–¶ú½¨T€ D ¹2@;H%"£‚“xxx¢¥,-F‚;(*ø¶1¶úô€$ð ” )`(^Ka2..§Ž‡xxx§Ž‡,-F‚;(*ø¶¼hW¶@úô€$ð ” )`(TG\/,,§Ž‡xxx§Ž‡,-F‚;(hW¶¨i¿M|V¶@úô€$ð ” )`-5@$!! §Ž‡xxx§Ž‡,-F‚;(ßúú˜è 4  -3-.. §ixxxx§Zx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶˜è 4  PA NFFG"§ixxxx§Zx,-F‚;(˜h¿Å.–¶ú¡C Ï $ ÐA0 B;>; ¦iyxxx§Zx,-F‚;(*ø¶1¶úHô h à<&471& ô„Ÿxxx‡´–,-F‚;(*ø¶¼hW¶@úHô h à!03.# ô„Ÿxxx‡´–,-F‚;(hW¶¨i¿M|V¶@úÉ%îé ôè üîþúûûèôùîô÷ ùúùóòóòøõ øï å øÞüùíãëï#òøô ï!Õùã#'ðÜ óòå úõ÷ÜïêÓò îà)Ãç÷¼ìêçü#üì:ÿè")ÿüü.ëîJ½ ëéìäýíïêçñòìï&äêDîØ(ðÿ÷ ïÿãó,àý Ø÷3È$úÚù-Õ ±åèÐ7Â*Ú;óûü÷óý ÿ üèøúòóöÞ!üô ýÝÿ&úÉ7÷Ö úÙÚû3ÒÌ!7íÙ" èPäÿ:Ò(â3öí% ÿêË$ÝíúÝí#ððåý ôõé.ûÒøî! Ëàüõúìí6ÝÎ÷÷»3Þ#é Ûþ-õýí#ìâ+Îî4âìùôô6ßÌ Åð5Úè5Ò ûô ÿùñ&ùÙ ûÚ7Ç Æ&Ý&ÿã +à×>ë*Ôó+ýýàô ßû3âïá Õî çèðî é÷íúØÞ$ Óþ%.×Ü2æðúöèè ó*ïýéÜ0Òõ íûÙ/!Ͼ òÚ" ³4Þìöó ï·ô Ãñ>¼ ùöèX«1"á GÅÙ]þÕðàß$óÜ9òÛÚ& ¬â³9)¤ôBÐûøê"Ã-øú ê!/Ð?Ï"¹üØþ$ ÙÜ"ûÙõFµ#Ü`¡\¥ü*þ ä öðëëáö#¸àAûñö èê0¿éZçâ+¿>ÎÝ&½üHÚÞEÐ.õÑ5ú´6ÆLÂ)ëððí3ÇípÙ±4Þîñ7Ù·;:Ðñ#ÖÿÛé6÷ä×5ÈùîSþŽ}ì™(6ýÎþ1$Ͷ3K߬ ÷0õðûâèüü òBï¸&áõñÛ ãú&ø¼ØM@»ðEæË9'óð'Ðøêøø úÝÚ, úËòþÊÙ1ññî æý,ßVéö'ö ê&íßß2åÓúþöéÛ.ú¼(ïô*é0Ê åÚõ# îß: ÍÝJº "ôÞú5È%þüã üüØÌ2êá#æû í*ñÔ& ã Ñ îÒøçù !ì" ã ùâõàÄÄò %êó(úü ÑñFøùåì@Ö ýðïØ öïèÞñ òîÿ ãòøô øô# í âçàïôéööô ýòñþ÷ùó óÛì,øó0ñò üú ð÷ýíçöñüü÷ ý èþúíõþ÷üóüøü¥à Œ ä xX-37;#  ¥ƒ‘xxx¥n‚,-F‚;(r•¶¨h¿ÅHø¶°ú–¶à Œ ä xX<^ KP/,¥ƒ‘xxx¥n‚,-F‚;(˜h¿Å.–¶úà Œ ä xX ëþ þû üñòõ  ûý  ðô& ëéü ü ü  ÿ.(!(! óéíñ÷òñ $!ëâÔÃÍåóþÿ&GL+ /' %+ÿÝó&ÿÌÓùôâö *#êöõùõÝø"&çü#ËÝ"ÇÇ!LñK:þüÛÊñ ö ,0!îåöê¾Ìòóèù" úíëö øú-ðòïõüòì÷üóüöãÞàÝÝçüÿöüÞèøíë ÿö*E-ùúÿþôöö×Îÿ+!ûìûíêýùÔ¶Îþýàì îïöâü%/ìîÝôêÇÑýïö ýôþê×Ùê 1!öçàßðèÊÃÐåû ñËÉô ùýïɺâ ùôëäúöÓÏÚè üøíøúîåú  òçùþïçàæøýãØçøþýñääæï÷Ûè óüáìüé  ú÷0îÝäîäê Úâ $ú×èçÔéûâÏë#7 ìþüïðó÷ " îòÿÛÚïöóö÷íæð øí×½Ùéé÷÷çðÿ ýêêõ ùÞ/6àÄæêàðÛ½Èß"êùÿêßÞæéî#2- ÷çîóãÑÒåûôðêäÝÛØÚìùúîåèàáò09ùã×Ùóÿ÷êðÛËë ýãï óæÇÛå×Ùê5&üø!óÞÛÕËßÿóÓà42ù ñÝØÃ±Òúð×Þ90ñçñíéÖÀã#AG$öÍ¢®ÃÌßë&4ïïþÖœ»ü -0ðõ%5ÏÅÖÖÖéøúóö>&äØô þèÚïûù äæ .+ÿÞíèÇÖíãï"åó)%Þ¼âïíü  !2ÞåõþíÄÍíåðþÜä0D8úëÿÌÅÏËïêó:*öãìóóåàñóê÷ ÷ ýûëãìäæñûýðêýþøþõïøó÷ûùõâÞøõûòíøðãåêùýêò úþÿøéûôýðå þÿøõäíÜð$ ÕÖ ÿÒæÿúôòAÞùãÑäïÙã *9þúæØÎÚî1- ðìðíèáÚÖÑð/?ðêýþÞÕíòæì -&ýøÔÓãçìÿ3%íäÞÓØèëåçÿýú"ÿÐÏçåãò ûAþ ñÌßöâàûúïíðçÕßþ öïðàîü ôì'%ó÷õøøãÚÝâø *" úéàáÚÚêóõû)ýôÞßü òè ýý èÕõíâðüÿ÷ûýæÞ3 ÿñæÖÊÜöúøþæáâëÿ ù þøëßýìÛù #1ÿ îÍÂÊçÿ)) îÖÍØæîôô÷  ýüúèìíáßñ. òåëîèëô ûìãòý÷üìàõùñúúý".$ëÝÓÔèýûý15ùè×ÌÓäåÞô#?0þíÝÛàéôÿ ý õåëùòæô ýàÕÍÈî  .ÿçêý÷èíòýòüøÿ õýôéùóëäþ ôð÷ð ï % îýãù úûõð ìøðçöéãöþý öõþôñó÷ù   üþôéïòðñðòýý÷þþþúú¯Ðˆ  Ø\-&79.  ¨‡xxxÈ¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶Ðˆ  Ø\F=&FI:) ¨‡xxxÈ¥,-F‚;(˜h¿Å.–¶úʈŒ  Ä\<2#?C3% ¨ˆ™xxxÈ¥,-F‚;(*ø¶1¶úʈŒ  Ä\.1% ¨ˆ™xxxÈ¥,-F‚;(*ø¶¼hW¶@úÃÀ˜( ô ÄŸ-88D""¬Š‡xxx§Š‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶À˜( ô ÄŸPo(P`00¬Š‡xxx§Š‡,-F‚;(˜h¿Å.–¶úÀ˜( ô ÄŸF`&H[--¬Š‡xxx§Š‡,-F‚;(*ø¶1¶úÀ˜( ô ÄŸ/2@  ¬Š‡xxx§Š‡,-F‚;(*ø¶¼hW¶@ú¾¨˜àì H ´£2* >14, ¡b~xxx‚kx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¨˜àì H ´£PC(N=B7(¡b~xxx‚kx,-F‚;(˜h¿Å.–¶ú¨˜àì H ´£<8%G8=3%¡b~xxx‚kx,-F‚;(*ø¶1¶ú¨˜àì H ´£ 6*.& ¡b~xxx‚kx,-F‚;(*ø¶¼hW¶@ú¹º°TP À d 2)'6B*!´–}xxxÈxx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶º°TP À d 2?0BQ4(!´–}xxxÈxx,-F‚;(˜h¿Å.–¶úº TP À d -/*4K-$´–}xxxÈxx,-F‚;(*ø¶1¶ú¼"96 ú ÎÅ-%%* ´wzxxxÈxx,-F‚;(*ø¶¼hW¶@úÀ‡Þ  ô((´Qwxxxi‡‡,-F‚;(hW¶¨i¿M|V¶@úÀ‡Þ  ô"´Qwxxxi‡‡,-F‚;(ßúôä(€x  Ø2=çÝd·ÿ)ëòõdï–4 ýøÎÓâ@(*—Â2Öàñô-ÿæÿõöÕñ.èìM9# ú ÝÿÕâñîÐÓ êô¼ýöÓðìáçé.1 ó" ó68  $èüÿäúöúôâëòìíÕç òáòûú     õó1&ö÷÷ýÝå ÷ðí èåü!íùä%âÖ)'Ùóó Ûòþøöøüñýüðýü÷ô ÙÒ'ïùøûðÝ$1ôà â÷  úëóúõúóô öåñ"ýÛÕ4"àé÷üøéíá ûóàëð Ô× øí÷úÞ åäøþ ýûãê& æûö ÿê'ÏÕæBîòß÷ &æéÿïú$ ïìÿ ÿøðòúü'Õ þíæ2<ðùÔôïÜä#Ýï 4ÒåÈ&ì!×Ïý4 þãÙ,ô«á( #ßÔóßíçë9Hî¦Þø-4ªü6ùÜÆ+×&ñõ ÓÃ7Iúâ%âÇ/?Ô . »ìfë ÝB©2ÕùuòôíÝ$ ñÛöAÚ×! Ñ úáóK-¿ßß!Bм 'öÝ&ä#åóÔOüåðÉÜR×çóïöëûóÝæ÷ûàä#)íÍDóÛëðóÚáÿ  ý üï ûå ëæôüóüñ "æïï"ùïöôüÉ%÷ôûÒ÷VúÅï*ÝöÅ2ÏÓ/õþØ0õ¯ÇKB-ѳññG\ßËÍÿôòïò -þåÍëT-ÞËÜBÔóð ì $üçìä/èèï Èî#"#îàåÞù9B¹½ô:7âýôè ËÔ2$*çÎÏ0-üìÜ*ÉèI-÷Ôï)ãê ñüìì÷ úúéüû Òíåó üôñý èÍè-a ÓÐî# ç&öäÜ1êàÜ -1ú¹ã41ò²í, Ñ÷ã"óCÊ <ÿå¼ýH ìç·ÿNôÁû.1ãÏÆ">èõ ìäíÖéùýñîÿþÊó ÁÿòöØà2ðêäÛ(_­á?*ñûðßî.'ÛÉõ  ÛÃÿ3ÖÆ)%þÆÐ×4J$û¿Î-6éññëè&$ ýéÓÿ1 Þ8÷еó7ðÔý!Éá'DþÁÔüüùøþÿ  ÿóÿ òíÊXßËÕ)÷Ìúó/,×Í (èýëñ ðñêÚ W%ã²ÊAýÝÌï(1ØÊ÷ 0,ûË×UÒ«ö?Tá¸ú"þõø-ßãã2J û¹Â&ø;ýêÄçäØÑLÈÿ:ÒÛ õ\áÃêEáò2çÖ ÷Û;;ãǼ5UõíÚÖ,2íÖ .éûûòû%ØÓ;ÙåüüóÞó)ëÖ *âÈì''ïßí+ìÈ3ëÙæ0ûÉÖ'ìÏû0 øë÷þýýûùúü  úíéîú&ùØõ+½Ð%ÕÈÜ'BüòÛø âÁþ=%æÇê2þùÝ $øõ áá;èñäÏÚ%9ðÕÿéõüçüäý 4)çôìÓ5ÞÏàKàÜý0ÊÞ.?ÆÑ/ ãé'êöûðü .òÓû%!óÚûüûøòûïüüÞè÷äü  ôÚå$ð ÿÿåúñ éÙÝöÿõåð%òÑôðÜê0ëÚà'÷öôîñýþñèý ÿÒã 2Úðô$+òâÞÿ#/ýÕØõ!'÷îý ÿç÷í íò üÙýèïþ÷æé÷ñó ôùüÿçÜ%úèî$!úýâø$Ûêõ &îÓÿ üïèì üòþøðóýìð ÷ûÿþúÿþü% çìñõÿ öô  îò ïð úþëöøëñþóêîõýèéþý øôöÜ õòøùü÷ÿ  ÷íæûäõôëþü>üÐÛÝGýÕûî$$çÔøè*NµÑ(ê;ñ¶ë&ÕÊ5 á´OâÏ´êBSÄÚñ ë»C'ç½ë(3ÍÑ  ôÜò -èÚ÷äÒ6-öÉë(øèõ÷ûú     ÿú þòñ÷ùùôôô÷öéäòõíêããñõìâðÿòéßæóþÿúõçïõÚë ÷ìåü öðûþýýúøùûüü ô,Þÿ  æÚ3çÞý7Ûý ïòç ÷Ôö+ ßû$Ýð  ðæüçÖòûæúüûüü ýüýùû  #74ü  $"  ôëUp˜Ø®7 \¥‰‰–¯\¥‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶p˜Ø®\¥‰‰–¯\¥‰,-F‚;(˜h¿Å.–¶ú p˜Ø® \¥‰‰–¯\¥‰,-F‚;(*ø¶1¶úð¸H¬ ¤ 5 -=>J%# ­Ž‡xxx¶ix,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¸H¬ ¤ 5 Kv$Vg31­Ž‡xxx¶ix,-F‚;(˜h¿Å.–¶ú¸4žð ¨ =À<`!O[.+¬Œ‡xxx¶ix,-F‚;(*ø¶1¶úÀx ¬Ì à+éÚëýæÖÿ,  æÄÜìê ÷èÀèáë%#òòòñ (åõðâ ÷ÖÓ2÷ *ÆÕ þø0'ûìþíÌáøñú!@$ïÝï üòò÷øö#  þìåòþüùüðþþÞðìßÿ %×Ãç ÿö÷þîïõ üþéù ðú ý õôûðíóíó"÷îþâôíúóðñ õäï?Òà)æðüãí ÿþüØÕ 6'íïúÝúý ÓÇÿ,-øØá ýÏØ6JМ ~°ß, æËê%úïÿôÓé åú$õøÔàû á÷!Óç"ÑÆ$OøÁ>þ½àæç5òîëýðüÎÚ)DúéÙÙÕï&3äù þùøéÝôÿ ûìãèý ùö% ûéÏÔü#&îë áÛýíÞêBBçÉØñçÛH_-ìÍÚçßð%ñäð  óàÝîÿ88 èÝȼé(4ÿäÔà ;>ûÃàäêþ#ïÐåýöúý1·¶ü*æ÷#, äÕß!ÿáÞ÷%龯ò" ñì  ɪå05ë ' ßá ñÛö ÿò "÷ÆÉ.åC ¸Ì$G#÷âÖÊÙKW*úÛÉÌ÷-&îÙïòéJ<þØãøôæï   úC!¾Á99ý÷÷îò %ñØðߺõ]j ÌóêÜÚî'óÞðøÚéý÷òäAª«A6 ìäêü)O,× µ÷0< ÙÅç#>$öØÛéì*0ü øÍÁî&9#úÙÝ'ûõ æßýû×ç8f-ØÈî óèð ÷åìíåúþöü!ý;â:ðô ìÉÛý ðû 'ÞÝõü÷úþÝÕó' çÖä ýîÆá-BðåÜåæÑÚ 1#õäòù"ôûõãßû õò  ëÞîíà J1âÖ7ØØ ÝÍ8"û !þÐáþÞÒð#1 øÝðêÑä 3G ³Û,-÷Ö¿ä>j7îÙÓÆØ+- òæìéëD4ñÈËÞý04*û°¤î13ûóàÙ='ÝÖÿü ûÞï/P̨¾â Jp:Õ©Ïòïÿ.GÝÃÕ ;/ïûúãäýþúÿüóúýúøý# æÞõöù  í×ß ßåÿ ç×÷óäõö  ùϨÀPNáØé0!ïÉÒðÿû&:)þâðøëóûùû*öîíçðÿöø.ùïùúíßâý"5&êêù åÛøþç÷ïÓÞø îå'ïãôúñù"ûòõôÿïç&,ùìñóìõýÞî÷ó÷õõý÷úúìï ðçîý  çãü  õ÷üþ ùÿñßæü÷ÿ ïåôùðú çÜì ÷âê, îîXÿÿþýþþþÿþþÿÿ þæßçø  ûûÿÿÿüü õçàêÿÿÿÿþþÿþþýýþÿÿÿÿ ÷ëìö  þúûýÿÿüüþÿÿýýþÿÿ ÿûüüöøÿ ÿùú#3/öáÖÛñ ÿ÷üýüÿõå÷ éê ôäóùäßûèð ýûûüòôù ÿîãøñï#û×ðòéüùäö îòýðõóöúçü åíéì ôõðûóáýîËë()ñÜö éï ùìÿ ùñööô (åÞ÷èïûî ôò+þÏâ% úÜÏÿéÜì,úÎæàÜ÷# ñàÛô$. úöêîÿýø5³Ç*DþÜøçýöÝñ%#ÝÀû1#òòòïùÜÃE¾ÝAPó¾òÿÝ K.Ñ·ñúó-þÀè@5êÍñçè(î¼è5:ãÓÔ=,÷íòßð'/ýÖáòæÿ"õâËðAV®¶N ¾Ô'óãö÷ü%Á±6uË/¿¤'~©Ñ&ßj.¸°èë7Cä°C Ëõ!ùÞ çå"ìÐïíë ÿúõ×í%ÝÕ6êñîÖò$ øñèâô÷äõ øÕ÷B-¸”j)¾ÞD,¿Æ8VúÂò å2/òÅì1-öç ïÍô;ÅÕ66ãàâò æÜ)õñ$Ûù&Û'ÿå.øÍù2ÙÚ*Ü· I Ïö. °ÎGJíí.¯ÜQJÜÅ ôö÷áñ#ê×õêõâ 0÷Äý4ùûíè îÀÓ#O#Ü´Ð I ìàáð üÚë óù øìð îõðÜ#ñã÷ôÞÅøSNî¸Ý "(ì¾ñ-ð0ä±ÿFÍÎ % ÿ ùÖó0#ææúï&ÿöäéóô(#åÐô(ÖÛ#ûå * ×Ñ'àÍ.ãÿüýõñø $ôÚïþôèô úòÔà ðýáüÖèôñøáö ôÚ"òÊ9æñùîõ÷å%òîñò ó×Ü;0úŽõ50íéäö!ãåú úñüöëÞç#éí ýõÚÙ#Z ÆÁö &ËÎ%÷ü/¹Î6AðÅð$ÿ éÞ3Ýúîü# óýïÚü#ç 1 Ôß-ãËó àô&#ôÓù1Éó8!äéûûýñìý*Þà ùßâ ùôñÌò ìè!ØÝýöÞÆD/ÖÎ ÒèQJäÊóùø'îÏÞ>éÛãï/ã×ï)ã×è !ôÜý2&èÐð íâÿúüþ÷ö1ÓÓ*ûìúæü""çëûÛæ%óä%þÛø!äñãöãÿ$Ôþ4äÙïíØ0ÓòùÕ(æ ðÚüêõ ÙÜ0ùÓà åå2õÄâ"õÙÝø-áÔøàÚö üó÷ ÿÜØ0%÷Þì  ÷ò ôüøüÿú öçù ú óíû öö íð*ùäáøûüúþ îç÷ þùýøöëóýíô  ôèåö!øò÷óïÿ õçñ  úíò ÿõ÷ ûöðö ùô÷ÿ þìò ùìðÿòó þüûÿýöø øøùöú ýîðûÿüüýýþ ùø üëô  þøöüÿþýüýúôòôûýøþÿùóõý þþ øô÷ ûôù þúùøùû z7ýþÿÿÿÿþÿþýÿúÿ ýÿÿþøøþ ýøúÿ úóýÿþÿýüÿûøý ÷íøüõù þøûúÿ üìû øë ûýûú ÿçéêó%öéð  ëä÷ü ôîôù  ìæîø õõùúþûÝî ï÷ú öð úìëüïñþ ýèñ üõî ìîõ ýÞòøôÿþýùæõþèÛñ"ßÔý)& òÜæ%õãä*üâÚù(üÞæýßà"ïÛä'/üÀÕ0*ÃÊ-IüÕôýû  æáùÓè,:úÇÍ=2íÑóÿ5Éß' ý+;ëÛõïãöû÷ åÜ÷ öï¸Ì35ùÚ¼ÂZÖë 2ÃÞ!. ÝÍôDRúÀÜ0 Óãðõ ëöúèü ý<ׄüsSꜯC)÷õ ÿëê0(ÞØõ )IÖÑÔìßøþêòëÿ ïúôçüõ+7ùÛÙæL$ÔËûò(ÛÐð7'ñÈÚ 19½Í ;1ê­ä>3 éËê'ÜÇüÿúò íô-+ûëàæ)úäå *Þ¿ß6"×Ý èÏç -2Òáúéû ëø42àÆ÷"ÿÑÙ,!øÌâ(ÚÑBàííóüÑè#9î×Üü Ñå"3!ÿÇÄü!÷Úï ûÙãÿ*êðè åÇù5& ýÛÐû1À¸LâÂÜ(CäÐÝ=)üÙÒö!!ó ßÊC=÷ÍÝô8éôëøõï ÿï äíðî6¾ÁET ÇÔæû0@ñíÜð(/øàô ÿö7*ÙªÇV4Ù¼(õÿðêáëËä%0åßñ#5úéåÿ çÚ'íÐñ  òóâýòÖë!ùãèþñâïõ$ üÕËW+ÇØ /÷ÉÅ 62ÐÀLÿÜüïï/#ÆÔ""ʺ øò&àãÞÎ9ðÿã$!é¥ÐFyF뙣þ:E(Ü¡Ù1+!ª¯AìÕá-9Ö¼9ìÌè(P'ÝÔï"çîòü30ÉÆû#$ ãÝ#áÒéÞÿ-@Ì›Ä82ܳêEW¡Þ=Nêòðì ýÛËõ-ÖÖÜÔ.=ÜÎ  íýçúéê ëøìþëìû ÷æ  õß3ßå$ùïøòî #ëßý!ûðãä üòÿ 3ëÈþôÿûíýô ùð ê÷ôß7ËÔ ôþçé$çüüéë,êæ#ÔéöÒ -æØ(ëë òéýäõþð òÐ ï1ÑðþøçëõíæäôÝüÚüüèà3àç  ûÀæ0ìôâ÷ö'5×Å)õêõ"ûÛùóä&.ãçòñ9úÄõôäÜ  îóöê ùúýóì0ðÞ îïä çÚ8üÙî$÷Ü#íÒë07ûÒùåä-9õßâå÷C áÞëÿ÷îí+ûúÿêû#õçøÿøò#ü×ê úÜôôÀÏ3ß öúêè ïã äü!úæâ'øúèÿ/èÕ(4ÝÎ çî#ûÎ ôì !ݯP ã ßüü"÷Ëè*4èÒ&8ãÑ%Ó÷H Íñ& øÌå6$Ú 9ÌÂ#òÖ èèÂõ àþùëéõéî(å *âÔ.óÐö5öä#ôÐ)ïäÿå ùè )ê»Eðá Ýó!úúß  íÉþ( ýÚðô÷ö * ÔÜ! áüõ÷ïêó$ØùFñÎ%üí8Ïùé ÐMÒäýÛÍ+ÿÙü ÷ãýÿ ý úÞðñÿ$þÂî éÑ û÷üúðÞ Þê ø àñ ùû ÞúÏïEÇþ÷*óµ(TѲDßß#*ãÈQñÒ*Òë÷5¼îBÀØAêå!ð÷õò +ííýß"÷ØÝ =òéîÿÝã ôØõ"&ð¿÷þ0ãªGöäîÛý!ûÍ üêá ßÕ 5êÏþó)Þ#Äè:CïÕ""¿×-!$ßÇ$ Ô;Äç Ï Uñ»÷-òâ+½û úíÖÃá? ¿ÿ üÑ?ò¾1çîÐ KÍ  Û®0QîË*ùÑá  ÙÑò ýêó,õÜ ï"åî ýúÛü7 Óò; Éà.,Þò"Õß6ÿÃ?àôïç )Ôþ,ïñúé&3àÑ-éÖê1ì×%Ûá0+üÝÙúú+ÍÃ.õåIBŸ¥D0éûç$M¿—5\îÝ <üËÚL^º äð4>µ×Hð  åË Z!åÒööè&QÍÄò#!øÔØõ0EÂÜ!"þï+ñÀ%Híá) âôì"Þ>å¦Vú±4êáõ ãê( Àç!ûá,¯Íè\¾Ïá ùç×ü6Äì õôéÍí+åÓðüïùðÐ6=Äâ$õÌéüûùüØ3åÅê8*úûØìÿÿ*ÈÃ1=ÓÜ# çù2#ÌÙøê ûÕ DìÐ úâì:Óú"ÃÕV4ÛÍøéùí%úçßMµÒ+þýö§_ ±2áÐî#- ÐÜ/û² EðÄûNþ£ùI Êä&&éñ òÜ.úîú úÞð2=òÇý!óé <ÙÓH½?ûÒñý$ùêøÊ#r"±Ð)ûÝÓç *ÖÔ=îÍ/êY/óöðñöë1:æ¸û îÀKû¥=ê æ(Ý¿õ=öÏ óþïÛ+î&ø·8Ì%×ò(ê×/#Úàûýí²$<Éü;ô Ü/ì÷,¡äj(·Û5?»Ç@/îéÌ+uâ¤KêÅÞ0HéßüÂÖ2K×­1GÆÀ<öËì&2áºa–äT9À¿#ºÙ9%æðÐÔÿõ¿³!TúòþÏàåøM4ÁËëûGò  ,ýæÝNE“–a[ÊÃê$ôÇÌ64å©û6'ÃÚ.ù3Þ=ëã1 Aÿ´SÝâa¬ .êáõí(åÇ'2Úó2Æü&$ãÎc¯GôË>/Úéé EÑÑ Þ HÓˆ sÊ¡OWÏMÓùù³ûLù¾üôåîÿ&ÎÕB_ì¤ýR‰ w­ÿÈÉ|jŽ FÎý38÷©Ò/5ðä×Ý'ó¾ B÷ßä4òÂE ÜÒþ9ÒÝ!ÛÝ<)á8øìÑêF@ê çæ ((Ùßì6þáû ÐÔHAÓÕ+êÓ!û½õßÎ,<εXæœ/GÁÈêõ õôâé0 àÛþ#û %˺ÿ$ѳ_Ø ÚÛ-ý%ë¼$ûîàûÖÕ:+ÐÓúö ÒÙ"ù éøúàOä ë×*ùüê™ói*åíèýùO·ó?ïûíìÆ "Õú,ßæåÿ*æò!Îõ8Aó²Ø,=ÿ¹Lº‰,ZÀõôý!øç' Ãø=#ôÚþßç=HâäD4ÇØ>>éÑö"úù'¾è âþô62ùÞñôøôô Óä,"Ôðÿúäâ !¿Üñø, ÉÇ$ûÛÜüØ'CëÙü êï;*²ÒDÈ8÷ßÄ(aúÕÕÚ FÒÜúó4äÔ +ßë)þùèè$"ÜïÚì!èåý ïë)úÇó,Öé6ýËð úæ ,æÑ #ùæù õû Óáýæéñîúû ââþ#èèøþíýôø îë$ýóò úï *×õ ûâ éÿ*ßö æì üùûøãù,)ÜÓ þ øÿë ëèþëñüíû ïùþ ßò þð÷Ð1úê"ãü  ñôûýìõ , ÒêîôÚ öôþýíû ñëþüýóú æÝþöûûïìÿ êÓþöæ÷öðöôyø êÖÝòü"$/ùàèòã×ô +6)!(õââÞÅÜÿþ9$0:ëûÔôü"&** ÷éæÛÈò 0=.'ìáüáÌÙéí5!0,ÿÜßæÈÖõ51&ßàùÛËþ  "þÔÑæÚÉÙ %1ôÔëôàßþ 'áÛôãê óçõýÿì÷þðóøò ýý ÿíñìÔñ 82%¸Àß³´!I]B)) àÙÖ»½Óó$ "ãòßÎëâá , þàÑÏÉÉÖô&36GÛÀß×Üîë . &)õÝÐÛèäö.+ ßÚìÍÍêù#(U:ϵÍÎÊ LR6î¼âгÜéö 'CE*;Ò±¶Â¸ß 4\N?+ÙÕÕ¼Ë×÷/8%'ðÝÐîðâó0"+ßÈÒàá÷ôð"'*;ó÷ÓÙË×36%ßåÏÇäîó'/,?:!øÝÑÉ×ÖÂï!=0 êáæï% $.;÷êìËÕìÎÖ /@2ÿçúà¶ÂÛÚó1#!V@3Áâé±Äúûí!6. ïüÛÛÎÔ0@ àÊæÛà%%.Ò¿äʨíûø*/ 15þôéÑÐÚÞð6& ðüÜÆÜôü>1û ÙÛÜÙèó1C- ,ï×ÏÐÝçéôù(>6ÜÍÑÓåÙì);>)+6è騲²Øèõ)$?D(èñÈŸ¶âç÷,?@FCþ°¦ëà´:A&-)øÚàÞÀÚéßý='6C+ÔÕÕÅÒùø83")úѹËöÒÕ*. NJ#;çðÙ¡ªÌèò*->E ïßã«Å÷Ùõ09üóéäã)%ðæïâäù*Þøëïߨ)Ù: çÚëéáüæó7L' ÙàíáÀçüø' 0ë÷óîÝÅÝûíÙ?*1ýôíàûáÓðû ï?/(ÂáÞ ó*B óâþ ôî ëüòíþ üñ÷óýúóßá íÍý(='5øÄãÍ¯ÌæØ4!4A óÙ× óØê )+ïáäåìååð'-) íñìÏ×èåê -+-:åÈßâÌÜøÿù/*øö ÛåäØá  ÏÚðÜÿ2æüõ ìÚíùÏç )6)úãâÎØõô1Ó´÷Òä4ýäJ4J"ÔÖáçÓ éÓA%Ú5èòÍ´üðãü)3î îùïÿ$4(êëïÐÔôÎß.õ0Fîñã¾üøÚý #ñÐ13Åò-øúõùáÓÝ øé6-'&  æÄÇÁËàMN-BéÖÛšÉÿë û$IÖÉ×Ñ×?ZÌ ÒËó)ùCÿøC(ìËÌÝÊâ 57#IÃ÷è¦ÔåèóG2%Úÿ ÊÜóÔÝ86öøèËçëâü /EÚý͹ÒF=þüÎÍê×Óòæö#''6äêñëÖö õçèÿðñ &*øí ôïßÞ 26&0øåôãÀÖñ!8D4$ã·»ÂÐæ#;DF/$ç³ÄÕ²Ö ?7*,óÈ»¶É×ê038A ÷ÎÏÅÉØíõôObOL2÷ÛǘŸ´ÈÛL^gY@7 âÔκŒ¬ê .eN]^̬œœ¼ÄÀ9T^?ø›ÇË•Àï}^4Y.ÍáǯËÜ+1C8 "'ÖÍýéÛ,CìíÛÆþãH7&öðñ×ÛüøýÿøæñÁTôá+Ûæøìíýýÿ "åæðåÞÜó'(ôÌéñÃÑñ QW 'ùÊñܼëýãÿ/#ýûûÞáüúô÷ýPæ ÒÄæöèü/+# èáÝÈËîòúPf++P#ÓÓæÀ˜¹ñûYN*^[äø³•·®±äû5h>Mo'èæÆš¢×çã,gCFe1 óפ¡Ïâî/4!OE᢯αØ%aT!$è´¨±Åºâ-[FDfW#þç̸­ÁÝú;9>pb!íÝäÎÈäñ1A9)/ ûÎÑãÜÖÝý;@ ýìäíàïøßÿ4%)ûáßãÒÛèèô/)) Þèäåõêô  ñþóÞæìåÒøô 1 &ëûìÍí÷û (# ÿñüùÝÎ÷õØö! #'> êÑÖ»·øçø)!+C*󨨾ÁÖÛå$+66 èÉ×Ú²ç&"c4 H÷ÇËìÌð !/ÿ éáåæÝù""( üçÍäýëæ) ôçÞýé )úÿðÙêùòöL ² ö÷øò ïï ýüõú  òçö ùðþ ÿ õØôîô ýèòçìýôéý÷ëòú%ÝÛøø×Ì1 ïôÕû øìõõ ñöþÿýø÷öúùúìøÿý øØñþù ûÝõ òò ðë  ðñý ñý-ÂÎ#5øâúæþ úò öè* ææþþúúûôô û÷Þí ýý÷áý"îعF%öéóõú çá èô).ðÊðî(åÙûú ÔÝþ éëú# çáñ îè÷ÿõæð üýãö ñ ôæ-Ûë ãà 'ë êïîëþô"èóùþ ÿôèþþ÷ò÷ $ÌÞ* îîðð(çÙþüþ ýòþ ÿáç îë  ñèôü õåú þýùêû êìõæ÷þý÷ðÿöæö òß? ÎÛ(+ÚÏ9Õß#íí èç *ÝìÙ 6â×ø%×ñìè þõþèòÿíþéôû÷ï×ö Û×,éò$¼Û1@Ììö  ýÖá!$ùóÙå ðáç ÿ "÷Ïè áì üÙÞù õåû'!éå î÷ íîþþæÅõ+(ýøíÛ ÿìðù þß÷è õáè1Ùý)ûÖ÷ ýþâû' éõÿýêý÷Þþæüÿ ðí ëóîãè ÷ñ àíîä+ðÈò0åôà ûùøî ðíí5àî "Ìá!/åí ÷ïý  öôê,Òä .öØÿ÷ùãéøù ûîù ÿòôåùôÿúîýëõ,úÅî.$êÉ>Üá (Þû ì×7×ëûÎïõÖû öèÿ õûûì÷õõîè"úñÙàAÖê÷ä îã èâõßòÚ4ßã úôïù÷+öÊî' ëß Üî/'ÕÇ+LߨúK"×ë æöäçùõ òü öû øïîìëÝ.óÕ7÷¶òI(ÚØñâ ÷ÿÜæì éàþ÷øñü÷ø ðð  æçôî èþþÔü5þëÐþ.øêî óüð!"êã ÷ùôõûöåó"Ôà(øÚû$äë é õáå* ðèýüØ=!ؾö2)èíðËô?1èÏþ ùíë"÷Ù#íçøàþ2ÈÚ",îù ÿõ úõÝÇ=ããÒÿ,ìé/Ï¡ h+æßâôôìôôøÙà 7ÜÝ ïå - ß÷üôþøáó!êÿßß ÿ ìà/öäýì¿ BÿÙÞ$Øõ ÑÉ#=ûá'Þ¸Q­í^%ÍÙ ëñ ñðúÚð Úá6 Øê ü ðñ ôöñÿò ôÿôÜ+(åÎ& ðð ñ ïùî õïõèï+üçôõ ÿò÷"Èß5"ÚÍT©Ú9>ݱbû­é<>ѵ1CÔÉ 4Øá) Ô-äæü ÚÑ*ñê'ÚõðÛö$$öÛöþØâ&Gú¿í.Ôé(ïêæ2üÔ ìï%ß×&äÛ  õå üøèà %øåó÷ç6ú¶öM Òà'ÅûJÔ×ü.ò êíüÿãáãûôþ ñÎÿ>ãî ðî&%ÕÔ*òÊî. éâ.&Í»D ÝÛ#üßæ +ôùÔöÞÜ &öÎÿï#þá× ' ÿïþ õó øÝ7 Åã îë çð ôõ ééå@Åäíõ âé$&éÓû9Óëê éó íåø èÝÿ- ò ÛÚ%ú %ص_¹Ï%/òß ýýåò%(òÞùÒøEØõ ýôûêâ üÙð#öìïçîù/Ôá!ÔÛAQçžîEÍï îðÛø8ïžïeKŰ+Sß´O½é'ãÙ*0ÌìJ ¹¼@óç ßòó ÔËMËÓ7ôËû=ÌÏ.îð üïêñ ñæE°Ã1DöÉ=¹Û2%øØã äÿFÀÌ&.àã5%ÊÈC¹àA:ν.õðñÜùïâúå$íâî éïâþòÏY ¦È@Õá'Üï!%øËí5Öü ìÔõ:-àÔ !âÂ[¸æ6Êø3,ö®ÛO5Ðà!Øë.!éèéú +ÀÎ87Ôá!öØû#êÆøi2œ±QgÕ‚r ³ñ; ØÈEòÆ.ôÑý;É×!òÒ#ùé%ÞÑ6ÝÊ FÇø<ý®ýS ÏêúìíÕH¶î0 ×é8 Øïûìü.Ì÷% ôîîøC$À«T#»ÞU.¯º4\ÿªÚ5 éíæØ#$åÊ3úÐô(:äîÀó81ùÙ.õÖ+ØÜúöëï<4Ž.üç3æ›ó`0ÄÏ!F´à4øöÔ &ߨ+LæÉ&ÌÇ-K åäÚÿ>Û¿ð?*àÖ%ì!&ÊÙ(ÓL"°Â54ã×7òÀí#*ýÞ$èׯÑ5W «²#\ÏÞÞõ:ÊÚ.öûöæíòøôüÿòå(­áW=Ùºò "òÌC¥ÜY(ÎÜ8ýÃû%þáþ úà1 Ðö' õÌä:*ÍÖ"8 Öä"Ýï$Ïå/#ñìö úõÙê,àû3ÈÙ5Üø úø÷îÿ#ÝÞùòÌó-'ùÚô+ýÓ÷öÚÓ:Ñò ÷òþòôþßô0àïðÎ)çé àù !Üá&ÿàô âê!&öÚó$ Þç (Ûì&èéçé !ßÕ9Úòþý ÷ü úðõêôõ ! òöùóãïüò ýïïõ ÷üüûôïú Óü6 äû îì)èé ôú 'éýûãñ, ðéàø#! ïÛó õäã,óæíü üùûùüóýùÿïêüÿìï þîûö øòÿùéñ þýüþ ù ÞÞ"÷øó üô ôóýýþ øõÿ¶Eôâí÷ ú÷ÿíòëáô ö÷òí÷ôÞï öÿûïôøûýûíåâ ýð÷ ûìÿñàåá ã ððÿôöùø ëõøýñúî÷îóòøóèþêúéû#Êîïæòêý×5öÐü óÿôäé óäï õèòëÜáðýèîëëï ðçÿæûÿñ üõ×ÿ(ßíþýÙí  ëòéå õéòòúäåôöäÿ ùüøæù* Õêúýÿàñêã åõýíðø áå êñø îÓü"â÷òâ&ïãý ÿð÷öúóíôþùÿùõ üéô üû÷ôýéøõîæòúîýåéãñçðí üùöú íûöáýüûÔæ$Ôç&àñ ü÷ãÞ5Û×ý üû ëâù óù ûëõæ÷ýÕëëëà èî ëïìäò"öÐöøýù ÷ìùùëÿ&ÙÛíôà ùöÞü òååÛñð öù ÿåü ïãäë óøÿðù Ùê  áêüàåãøñõ ôòçóðú%âðþé ÿêüúñ ðëð òïð íÔ2äÍ0áÄ7íÓ÷ööôìæ*íâòóÉï+>ûÉéõý1)ô°¿*,ðîðê@Ô ãößî ûåÿúõñøóìÚûåö×Ó63õéûÿðää øóÄò/ñú¿õ:Ùøðõ éõðØöæ.#Ä©6-éÊÜ ,Öð"õÄP—éXÛõ ýù èóõà2 Ìåõ÷×î20ùÂÙ$Ýëôþ Ý»þ7Cë›ð0 ñ%Ö° ^ ÁÜ#ßÔ æÜ õóü Ø.ÝÔ/ÚÇ $+êµÃV.òìøé¾üd1εí# ïúûØý+ ãÑü- ðáâò '-ç×ëÜüN0Ûìöõäý çÛ 3þéòìú20ÞÅÙ÷91é¾éö$à зZ"êî°·&q_ó‚ &DÏÈöõê #,æ³ÇäYVÿÇ  =ýÐü'¨­ÕæÚüè W.³—ýAê6AÈˆØ Êì0Úø7ûÊ4êéìý ùÿñ$Ýõ öý þñýÕñ8Øß%+ÜÙ3Ëõ#ñä!ððýýîôßûøèþç.íÅ )ïâ ýï èïúìþïùìý ñß)ïÒ-àú ÿõëÿõ íû õ íþ÷õÙÕ/E×´"EðÄAüÓ÷ïëÕó-âá $÷å ñ ðîâò*Ûÿúù èì"óíõé&÷Ñþ(î!àÃMÃë öæ "òßù ÿçø+ Õÿ.á íÞ /Óú3Ñë2àï.ÈÓ23éØ)Ñ+ÿÚ(óÏ6Ð÷(Ùõäû íõóòûá 'ëß á%âæ . Ýòøïèï þó #Î÷6Í3ñÐ1çÑ )Ûú$æóñå üò ðì áþ/Ðü1 Ýù èõû÷ôö ÿüý øëéøõù öñïúâü áïèò èúÿ÷á!,  úü÷íáÚíçëöñ öðïèæÛàåâëíìöø÷õô÷ñìéßÙÜÚÑÏÒÖÞæëíóûÿÿüüýýúú "&)+28679=OLIKCA;/   $!# ýõéÜÕÈÅÀÀÆÀÅÔ×ßçìïìñìÞàÚ×ÔÎÍÌÐÝÛãçòý þçݲ°;)-XQbr}Pè×ÕžªÆ÷,U[}kU<+%ñÞÔÄàáÞïþÿõâòõü÷äëööúíçääëÙÚÕÍÝØÞëêòëìëâçÕÌÐÎÍËÍÑÙëõù %)1<;A?>B?DB??:;;=8**-(/%úóíóôóôçæìàæÛÓÓÔÖÓÍÑÅÊ¿»ÂÃËÊÎÙÙåìÛÚËÏÑÑÚÝéø #üþù $2G`bnxrhgT@+ ùêÛ×âäîøþ$*"þïݶ³µÅÖì1;B@-#öÞßàè+5C<1%ýêÙÉ¿¾¿ÁÌÖßëòñðéáÕÌ»³«¤  ²Òâô÷ïðàÙáÙæölÄrTüX [ F.& }<‡xxxPKx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ÄrTüX [ /& }<‡xxxPKx,-F‚;(˜h¿Å.–¶úظ©` € BÀ ($! xixxxxi–,-F‚;(*ø¶1¶úÔ³›` ä Ø %"(xi´xxx`c,-F‚;(*ø¶¼hW¶@úȤ n@_?]aaL-xixxxxKK,-F‚;(hW¶¨i¿M|V¶@úŒ”€¨Ä ä 2`2 \xxx‚_x,-F‚;(r•¶¨h¿ÅHø¶°ú–¶”€¨Ä ä 2`Z \xxx‚_x,-F‚;(˜h¿Å.–¶ú”P < * 2`   \xxx‚_x,-F‚;(*ø¶1¶ú¯hhHx 4 (`-6M202  _x§xx‚_x,-F‚;(r•¶¨h¿ÅHø¶°ú–¶hhHx 4 (`Fx(tLHK, _x§xx‚_x,-F‚;(˜h¿Å.–¶úhhHx 4 (`=$ ®szz„»‚‰,-F‚;(*ø¶1¶úT ¬  h" 7+11 ®szz„»‚‰,-F‚;(*ø¶¼hW¶@úªMÿá h à2 03/$ ô„Ÿxxx‡´–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶Mÿá h à–xxx-\Z,-F‚;(r•¶¨h¿ÅHø¶°ú–¶Äåˆ$  t2% 5B31xx–xxxKix,-F‚;(˜h¿Å.–¶úô+ð ” )`;~It4--§¥‡xxx§x‡,-F‚;(*ø¶1¶úä ð 4 )à:tRa796 §‡–xxx§Z‡,-F‚;(*ø¶¼hW¶@úäóÿ  ” )à&G"CW%)&§‡xxxx§K‡,-F‚;(hW¶¨i¿M|V¶@ú¤b ” )à(<;§xxxxxãii,-F‚;(ßúšø‰(Œ p # 2<"FE( Ò–ixxxÿ´–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶H(Œ p ¿ (B*KA1+ Ï–ixxxí¥¥,-F‚;(˜h¿Å.–¶úH(Œ p ¿ AH)PC8* Ò–ixxxð¥¥,-F‚;(*ø¶1¶ú€<d p ¿ 6#F?%! Ò‡ixxxÿ¥¥,-F‚;(*ø¶¼hW¶@úšø‰(Œ p # 2<"FE( Ò–ixxxÿ´–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶H(Œ p ¿ (f*_U1+ Ï–ixxxí¥¥,-F‚;(˜h¿Å.–¶úH(Œ p ¿ Aa)]S8* Ò–ixxxð¥¥,-F‚;(*ø¶1¶ú€<d p ¿ 6#F?%! Ò‡ixxxÿ¥¥,-F‚;(*ø¶¼hW¶@ú2܈ :Øà( –}‰‰–¯–}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶Üˆ :Øà   –}‰‰–¯–}‰,-F‚;(˜h¿Å.–¶úÜ :Øà  –}‰‰–¯–}‰,-F‚;(*ø¶1¶úÜ  :Øà  –}‰‰–¯–}‰,-F‚;(*ø¶¼hW¶@úýÁþüÿ   þûûûüüûüüüüüüüüüýûõìâÚרÝãêîðïíêçåäæêîòöü    ÿÿþþþþýüú÷óðíëêëíïòôöøùúûüýþþÿýüûüþþýûúúûýÿÿÿÿÿýüýþþýüûúúüÿÿÿÿýüüýýýüüýüûúüýüúû   '(ýÑ¦Š‚Ž§Ååÿ ñçäçìòøý $5CID6" ýòïôÿ ùðêæåãàÛ×ÔÖÜæðùþÿúóëåäèñü  øðêåäåèìðòôõö÷øúýÿ  þúõñííîòöü   üùùûÿÿüú÷õöùüþþüüüÿ     ùêÝÕÖßíþ üóíîôþüüü÷íâÚרÝãêïðïîëèæåçêïó÷ü    ÿþþþþþýú÷ôñîëêëíðòôöøúûüüýþÿþüûüÿÿýûúûüþÿÿþýýÿÿýüûúûýÿÿþüd°¸ @ x2&6' ¢–xxx¢¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶°¸ @ x2&6' ¢–xxx¢¥,-F‚;(˜h¿Å.–¶ú°¸ @ x!2$ ¢–xxx¢¥,-F‚;(*ø¶1¶úZ°¸ @ x+ ¢–xxx¢¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶°¸ @ x(!2$ ¢–xxx¢¥,-F‚;(˜h¿Å.–¶ú°¸ @ x2 ¢–xxx¢¥,-F‚;(*ø¶1¶ú°¸ @ x!2$ ¢–xxx¢¥,-F‚;(*ø¶¼hW¶@ú2°¸ @ x!2$ ¢–xxx¢¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶°¸ @ x2 ¢–xxx¢¥,-F‚;(˜h¿Å.–¶ú°¸ @ x.! ¢–xxx¢¥,-F‚;(*ø¶1¶ú2„èä `d-#6%"" §Z‡xxx§‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶„èä `d2DL400, §Z‡xxx§‡‡,-F‚;(˜h¿Å.–¶ú„èä `dU7D.++' §Z‡xxx§‡‡,-F‚;(*ø¶1¶ú„èä `d(+<)&&# §Z‡xxx§‡‡,-F‚;(*ø¶¼hW¶@ú„Ôä `d2" §Z‡xxx§‡‡,-F‚;(hW¶¨i¿M|V¶@úëô#0è & °-.-0%Êvxxx‡´–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ô#0è & °PR(OMQ?. Êvxxx‡´–,-F‚;(˜h¿Å.–¶úîæÖ  zPH%JGI:) Ævxxx‡´–,-F‚;(*ø¶1¶ú¸xÀ. à ˆ0;/% ¢z›xxx¢x§,-F‚;(*ø¶¼hW¶@ú¸xÔ8 à ˆ-'  ¢}›xxx¢x¥,-F‚;(hW¶¨i¿M|V¶@úŒ8Iö V Ó\2/0Ó|xxxí¥¥,-F‚9(r•¶¨h¿ÅHø¶°ú–¶8Iö V Ó\[)XY8- Ó|xxxí¥¥,-F‚9(˜h¿Å.–¶ú8Iö V Ó\AW(VW6, Ó|xxxí¥¥,-F‚9(*ø¶1¶ú8Iö V Ó\01Ó|xxxí¥¥,-F‚8(*ø¶¼hW¶@ú0¨ èØ H ¨j  a}‰‰–¯a}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ ¨ èØ H ¨j a}‰‰–¯a}‰,-F‚;(˜h¿Å.–¶ú¨ èØ H ¨j a}‰‰–¯a}‰,-F‚;(*ø¶1¶ú¯`Œ „ Œ -,>5( Ù›ixxx÷ª¥,AK‚62r•¶¨h¿ÅHø¶°ú–¶`Œ „ Œ F](ZL:+ Ù›ixxx÷ª¥,AK‚62˜h¿Å.–¶ú`Œ „ Œ )DR/%´–}xxxÈxx,-F‚;(˜h¿Å.–¶úº’€œ ø  P1$'ºSzxxxi‡‡,-F‚;(*ø¶¼hW¶@úЈ Ø ê  ºSzxxxi‡‡,-F‚;(hW¶¨i¿M|V¶@úÎÈH& Ð /Ÿ22E$ ±dƒxxxi‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ÎÈH& Ð /Ÿ7N#?W- ±dƒxxxi‡‡,-F‚;(˜h¿Å.–¶úÎÈH& Ð /ŸAF!§ixxxx§Zx,-F‚;(*ø¶1¶ú˜è 4  ,A9:: §ixxxx§Zx,-F‚;(*ø¶¼hW¶@ú˜ü 4  0> MDEE!§ixxxx§Zx,-F‚;(hW¶¨i¿M|V¶@ú˜ü Ø@<, ::=>! §ixxxx§ix,-F‚;(ßúTÈ^  <@()&' ¯iixxx¯‡x,-F‚;(*ø¶øi¿¼hW¶@úúPôì  h-( <553 ®szz„»‚‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶Pôì  hP@ LDDA' ®szz„»‚‰,-F‚;(˜h¿Å.–¶úBt3  mŸP0 @;<:" ¬q}yy»‚‰,-F‚;(*ø¶1¶ú˜è Ø@-' 77:; §ixxxx§ix,-F‚;(*ø¶¼hW¶@úTÈ^  <@))'( ¯iixxx¯‡x,-F‚;(hW¶¨i¿M|V¶@úTh´Ô” )@*3H9((% ¢–‡xxxf‡x,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ThŒÔ” tÀ(OWRI94§‡‡xxxkZx,-F‚;(˜h¿Å.–¶úX`x¬” tÀ2JYDF42§x‡xxxkZx,-F‚;(*ø¶1¶úm@q» yôC1 D9)%!¥‡Šxxx¢x¥,-F‚;(*ø¶¼hW¶@úT"ÿ¬ tÀ9# ¥‡‡xxxiZx,-F‚;(hW¶¨i¿M|V¶@úÿ@ÿá h à-%372' ô„Ÿxxx‡´–,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ Ìÿ | !œF:%DG=0# õŠŸ|xx‡´–,-F‚;(˜h¿Å.–¶úòaÄz Ì mŒPN+TQ8,ú¦£Žxx‡´–,-F‚;(*ø¶1¶ú쀠Œ Ø xfJ+'©‹xxxŇx,-F‚;(hW¶¨i¿M|V¶@ú¢Ø : °y&1;"©‹xxxŇx,-F‚;(ßúÿóÈØ  ª¤-$065) Öxxxx¹k,-F‚;(r•¶¨h¿ÅHø¶°ú–¶íÄ®Ê  ·tF9>C?1& ÒxŒxxx¹k,-F‚;(˜h¿Å.–¶ú· {G  .ÁPRWG ( µ|qxxx¹k,-F‚;(*ø¶1¶ú°X 8 <<@V2$ ±}nxxx±}},-F‚;(*ø¶¼hW¶@ú°X 8 <<# ±}nxxx±}},-F‚;(hW¶¨i¿M|V¶@úÿ¨pX h  -43?&# §‡–xxx§‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ÜDl a ë<FS"KR4-É•›‚xx§‡‡,-F‚;(˜h¿Å.–¶úçi}ˆ ² iaPN+UR6,ö§¢xx§‡‡,-F‚;(*ø¶1¶ú쀠Œ Ø xf'þþþ #"!# öÞÑÉÇÆÃÉá  æãáÓÏÝæí +,#97÷ì÷þöåï(.()$ óÝÛæèäç÷ ÷ýþçåùýúÿ 66 þæÒÔÞçû !,73ùåØâêÝÑåùöýûöóû þíô    (ôÒÆÓÜàñ).ëßãïëêý')%ìêóõø /.ýëÒÉÇÓäóù  ùçØÚåêëû !$ûóýîÖÝ&(%ôÛÓÕÙêøý(ãéýÜÒêý  øîòûü *8&  êâÚÕÖêðâà#,7RMéÚϵ«¹Â¼Ø>5(AVP2ÿäÙÖÊÄà &+2DP>ùæÛ۬¼Ôø/+1CDéßíéÓÇÑç"*$?K+öàããÑÍ×çú ',$ ÿýûìÜËÀ¿Õðüþ$:?7-(! ßÃÓóõÔÓü#%" ìæíÞÂÅäóý0+(8-îþûÜÍÖÖÓì*"÷åçùùìëû  !'2$èßèéàÕè1?.óÓÇÐÍ´Âõ!#)#òÚàôíÑÚ ,8))6 ôêöçÇÀÓãü"0&*KP%ðéï༶Ìáô  88îíðäÜæââø"ÿýø õõöóïääò *"ôÊ­¨®¾ÛëúU}rD)Ú½´¨¬Ï "$4`nT'â̳¢¨×&/<;1õÕ¿¾ÅÍÑÝÿ*PTC0#þäͼÂßôô34380úÙÀÉÓÚØåÿ+,'-82 ëãçÜÄ¿ÄÆÛ>2$FiJÙ³ºÒËÓõ *C9+óïî×ÀÂàôû  ûõü ûõ÷ý.+üîÙÒÛéåÙä /.ûåÔÊÓó ý5*ÿ÷ïÛØïö72 áÍÚðö÷ùÿ$õöùØÖõôð%éÖàèÝÚë+<8"$$ ïàÜÕÔÒà*4"(8:ñÛÎÄÍÙ×Ôé  %* ÿðôóæØïû%#ú ù ÿüøèäöóï-& ýñìèàÕé.(ýëÝÉÄàþ)1(!ûàÞååæóú ùëíêÝ÷ þ  õô ëÚßðÿ # ýñéçë÷ÿûÿöÿ óäãìöúùö ! óìïáÍÔð#3.#îäéæÜâøøêéèÜÖßí÷ ,( ûîããçâãú)/4:6$ ñÒÇÐÖÏÖý$1..$ ßÃÊÛÒÄÕô*-üÿöäßí+& óéî÷ûíÝæ ÷ððìãæõøüüóäÛàîý!24%öêÝÏÈÒî"076,þõã×áìóü%)ùúí×ÉÃÈÙðõñù!  úîø þ ''&1& öäâßÙãùþòòýôðìîùýøøù &üûïìñ " ôêéäÛÔÕâöûÿóæàäôÿ*-$ þý  û÷ô÷üÿ õçâßÙ×ÙÜßæìòûûöôû   #" óéÞÖÙë " ôáÒÇÅÌÙæô(12,$ùêäëõ!9A2 ìãèòú# üõíÞËÁ¿ÅÎ×Ûèþ ýéÚÛåðú#7>6+& þúÿ)$ þìÖÇÅÌÓÓÓÙäèß×¹“îº  Q-) >404 §e{xxx§Zx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶“îº  QFKTGAF' §e{xxx§Zx,-F‚;(˜h¿Å.–¶ú“îº  QF= L?:?# §e{xxx§Zx,-F‚;(*ø¶1¶ú“îº  Q6-)- §e{xxx§Zx,-F‚;(*ø¶¼hW¶@ú¥ ø<¬ä ö_-+7@+(ª…z|€Åƒ,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ ø<¬ä ö_DO/+#ª…z|€Åƒ,-F‚;(*ø¶1¶úz˜O™ä ö_'69%" ª…z|€Åƒ,-F‚;(*ø¶¼hW¶@ú¥øìÄ p (™-09?.% ׊xxxí¥¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶øìÄ p (™("%" §Z‡xxx§‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶„ð4ä `dL1*-) §Z‡xxx§‡‡,-F‚;(*ø¶1¶ú„Hä `d#)>("%" §Z‡xxx§‡‡,-F‚;(*ø¶¼hW¶@ú„Hä `d$:% #  §Z‡xxx§‡‡,-F‚;(hW¶¨i¿M|V¶@úë<ì ¿@-5"BH++§‡¥xxx§‡¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶<ì ¿@Pg0\d<<,§‡¥xxx§‡¥,-F‚;(˜h¿Å.–¶úþÞ’ü , ½VF\.X_<:+§‚¨xxx§‡¥,-F‚;(*ø¶1¶úœc˜Œ ˜ ¦ (+ 71:-! §ZÃxxxzx‡,-F‚;(*ø¶¼hW¶@úœc®  \  ,-)&§Z‡xxxzxx,-F‚;(hW¶¨i¿M|V¶@úúzðŒ„ä ö_-&6<%'ª…z|€Åƒ,-F‚;(r•¶¨h¿ÅHø¶°ú–¶zðŒ„ä ö_KJ$LT47&ª…z|€Åƒ,-F‚;(˜h¿Å.–¶ú}ÚÖ¿ì ÷L>,ÏÖõ!> úüâÊÏñ/»¯äòìó äдÂë.ÞÜòúÊ×/Øåýìô÷ò!åÁöýìÜî$ûÊÑ øò%ÁÐõ ðþäÀÝ&ôýôÑß('ñï óã ,(íæóý1?ùÐîþ# öøû  þüóð & öûû)"èç þ/0 âõæè#,ñã÷øÍëüëÇÕý èÙø'âø ÞÅû,øì--ÜØû!üØóÿÿÿõóõáÔññýåéþãêôîìûíò÷ê÷øñîëÿÿøðÏ?êò àÙ5ìô ðòþÝïÞÑòåæòèâþ ðÞóèÛîòíÿõþÝë òÝåõçøÎÒ;ËÙ Ìâ ñ÷÷ûöËì ù &áúë #öíðõïç Óßüùò÷áíøþü  íóäöíööü÷þ þÿçðü÷üúýúîôþ éóîîÞõïÙêêÓÝ0þûû ìòßòôå ûÚÛñç*91 #& )îéíÞöÿùêú÷ÛÒêôó ýíò " ûö òèãðÿùæÞòûëä öàæóôëíóüþúïîÚÕò÷êø÷ÝçðÝÊÉÎßêùûöááäÔ×îúîõ üâäòñâåüú üýçõöòñ4ëØÔèÝÚò êèêðëäëäîû ôÞâíö:6! ùìàü-íìíâÓ×åïø üγÛåã-$ ìãßç  1öèáÕàíåýü üöÛâþú9* úøåî 21 ñåèÝØå þöÛâñüòßò ýþöáò û #!  óòïðï óçäÌËÃá'# äÆÅÞóíô"LG&+*íëö8*öááâ÷øøíÛñøãÓæûâõ$þ îÈé1*-Øëóå - äÝñܺÔ÷ 0Ü¿·¿½ÁD7 åÂÂßü -2)øäåÛÞçÏÆÌÜÞ%)((îóôáÝæ÷ïì # úëï÷òóúëòùãÊèððûÞç !0ýãíðâ üêõñ÷îÚäÞ÷ ùèäãàùðÞØàæáø++ æßù!òí óæôóîÓÍïô þâÛññëìú ùÞ! ûÿéßäÜç )üåêåÜäñúö èàÕÔæåðï ìÚñú .þëìôëäÙéòó þùþ÷óüÿ.% ÷äÞí -3ñìãÓå ÎÊÛòøÜõ'üýïÒÇ×é70*& ãÔÖÝ÷ 0-ýúõÚÅÊì! úÙÎÖâÿ/J.ôìêèú 'ZW4 ç¾Çàô(-ïÚǾâ,/<ßÌéëÜÜ*2ïèÙÖï '*/õâêñô  êÝÕçõüûó ûòýïÓÎæôñ ëÞÐÎô +ýîïëíëó ôáÞõ'!ãáöÔºæ!ÿå×Çßûü=;&úçÞÚèù &9#ùïãÕÝ$+$ëÖÚÞÓÔýèÔËÕéú/õàÐñøòòÿùúüý÷ïßÍçþõþúùÜíþÞè÷æö ùéö ýÿü÷øéñðû.+ùìÝÚÜîûîüáÏÝü ãÝëéî (*ñÙÚÙæ !8/ÿâÕÌÒÔç&úõÒÇØêý õçÓÚù  ðåâë"(èäôü ÷ôÓÚú ùòõòÛâÿûôîìý%& âçþùÿ#% ìÔâùûü@(õðñÖÈã( öîèòóü  ìð  ú÷øîðúþ !# ìáï é õïþçÙðû  úè÷ùþøèðýûëâõýóý$êÜäõ õ÷þóàæîö ùíû úÿðúýñó ÿþóçù úæßûþ "$üóõïôÿóÞÜìóñáïúü øððñ÷üüü úþ÷ð#  ýïïóüíéíèåãïýøòäðùö! úðæïôú!ïæîõú *3ôåîæØç ëäÚÀ·Þ%ôíâáø*8) òæçòù24øôéáäî+-øçÛÕá'õçÙÒáý-ìäïïðù%õñùõóüúÿñãæûûû üçÛäðüýòêñ ÿ÷êø Z%¸pH ¼ ˆZ }‰‰–¯}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¸pøì ¼ ƒ}‰‰–¯}‰,-F‚;(˜h¿Å.–¶ú !#%')+-/13579;=?ACEGIKMOQSUWY[]_acegikmoqsuwy{}ƒ…‡‰‹‘“•—™›Ÿ¡£¥§©«­¯±³µ·¹»½¿ÁÃÅÇÉËÍÏÑÓÕ×ÙÛÝßáãåçéëíïñóõ÷ùûýþþýüûúù÷öõôóñðïíìêéçæäâáßÝÜÚØÖÔÒÑÏÍËÉÇÅÃÁ¿½º¸¶´²°®«©§¥¢ žœ™—•“ŽŒ‰‡…ƒ€~|ywurpnligec`^\ZXUSQOMKIFDB@>;97531.,*(&#!   !"#$$%&'(()*++,-./0012345678:;<>?@BDEGIKMOQSUXZ]_behknruy|€„ˆŒ‘•šŸ£¦ª®±µ¸¼ÀÃÇÊÎÑÕØÛßâåèëîñóõ÷ùúüýþÿÿÿÿÿÿÿþûøõòîêæãÞÚÖÒÍÉÄ¿»¶±¬§¢˜“މ„zupkfa\WRNIE@<83/+($   $).4:AHOV^gpuz„‰Ž“˜¢§¬±¶»¿ÄÉÍÒÖÚÞãæêîòõøû{vrniea^ZVROKHDA>;852/,*'%"    "%(*-037:=ADHLPTX]aeimquz~‚†‹”˜¢¦«°µº¿ÄÉÎÓÙÞãéîóù˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜˜—ˆ€yrle_ZUQMIFDBAABCEHLQV]emw‚Ž˜˜˜˜————––––••••””””““““’’’’‘‘‘‘ŽŽŽŽŒŒŒþûøôñíéåáÝÙÕÐÌÇþ¹´°«¦¡œ—’ˆƒ~yupkfa]XSOJFB=951-*&#   "%'*-/1469;=?ACEGIJLMNPPQRRRSRRRQPOMLJGEB|xtplhea^[XVTRPNMLKKKLLNOQTVZ^bglrxW¯™€àÈ ” °ô-6@1!(¥~‘xxx¥s‚,-F‚;(r•¶°ú–™€àÈ ” °ôF[T@,4$ ¥~‘xxx¥s‚,-F‚;(˜h¿Å.–¶ú™€àÈ ” °ô<[T@,4$ ¥~‘xxx¥s‚,-F‚;(*ø¶1¶ú™€àÈ ” °ô[T@,4$ ¥~‘xxx¥s‚,-F‚;(*ø¶¼hW¶@ú ‚0$ —-(:+"( §`xxxÅx,-F‚;(r•¶°ú–‚0$ —FEL8-4( §`xxxÅx,-F‚;(˜h¿Å.–¶ú‚0$ —-8D2(.$ §`xxxÅx,-F‚;(*ø¶1¶ú‚0$ —EL8-4( §`xxxÅx,-F‚;(*ø¶¼hW¶@ú¹pô„$ ¼ t`-)6B!'§–‡xxxÅxx,-F‚;(r•¶°ú–tô„ ¼ t`PC"BX,7(§–‡xxxÅxx,-F‚;(˜h¿Å.–¶útô„ ¼ t`<6;O'1$§–‡xxxÅxx,-F‚;(*ø¶1¶útô„$ ¼ t` /:$ §–‡xxxÅxx,-F‚;(*ø¶¼hW¶@ú´ ´~ é t°()!4D,' ®‘xxxÈxx,-F‚;(r•¶°ú–´ ´~ é t°2\2NeA:/®‘xxxÈxx,-F‚;(˜h¿Å.–¶ú´ ´~ é t°2E,DX92)®‘xxxÈxx,-F‚;(*ø¶1¶ú®h?à  €Ì;J*&" §““xxx§Ž‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ú°(ö ¼ \W##Ti<61§““xxx§Ž‡,-F‚;(˜h¿Å.–¶úú°(ö ¼ \W#Ti<61§““xxx§Ž‡,-F‚;(*ø¶1¶úú Lö ¼ \W+v#Ti<61§““xxx§Ž‡,-F‚;(*ø¶¼hW¶@úÌ]ü< ¨ 2(5=!( §¥–xxx§´x,-F‚;(hW¶¨i¿M|V¶@ú˜È  ´Ÿ $ ,$ ¬Ž‡xxx§‡‡,-F‚;(ßú˜HÐ ÈŸ$¬Ž‡xxx§‡‡,-F‚;(*ø¶øi¿¼hW¶@ú˜HÐ ÈŸ+$¬Ž‡xxx§‡‡,-F‚;(*ø¶¼µ¶ ­Hhú÷¶˜HÐ ÈŸ$¬Ž‡xxx§‡‡,-F‚;(_÷¶1¶X—Hˆú˜¿äà´Ä D ØP-.7B,$ ¬Ž´xxxÿx¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶äà´Ä D ØPBS"KZ<1+¬Ž´xxxÿx¥,-F‚;(˜h¿Å.–¶úÞà(` b L÷)I?T.4#¨|Ìxxxÿx¥,-F‚;(*ø¶1¶ú`W 0 )€(@=M#4$í~Àxxx~“,-F‚;(*ø¶¼hW¶@úн  )`(A$D;#ÍZ´xxx‘x‡,-F‚;(hW¶¨i¿M|V¶@ú¬È˜À¨ <`2* ÈZxxxxÈx‡,-F‚;(ßú"Èľr ² à ô 8(HD@ »}‰‰–¯»}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ÈÉÅd 0ô B(PL@»}‰‰–¯»}‰,-F‚;(˜h¿Å.–¶úÈÈÀb Z ƒô 8(HH<( »}‰‰–¯»}‰,-F‚;(*ø¶1¶úÈŸa K ®ô3$DD80 »}‰‰–¯»}‰,-F‚;(*ø¶¼hW¶@úȶ™l C Üô$0$D<0, »}‰‰–¯»}‰,-F‚;(hW¶¨i¿M|V¶@ú˜È  ´Ÿ $ ,$ ¬Ž‡xxx§‡‡,-F‚;(ßú˜HÐ ÈŸ$$¬Ž‡xxx§‡‡,-F‚;(*ø¶øi¿¼hW¶@ú˜HÐ ÈŸ$¬Ž‡xxx§‡‡,-F‚;(*ø¶¼µ¶ ­Hhú÷¶Y Èh&b  ô 790*' »}‰‰–¯»}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶Ȉæ0  ô o$\@@8$ »}‰‰–¯»}‰,-F‚;(˜h¿Å.–¶úȈß.  &ô n(X@@8(»}‰‰–¯»}‰,-F‚;(*ø¶1¶úȈà0  (ô a$T<<8$ »}‰‰–¯»}‰,-F‚;(*ø¶¼hW¶@úÈõ< + Tô D(<888( »}‰‰–¯»}‰,-F‚;(hW¶¨i¿M|V¶@ú˜È˜Œ ´Ÿ$ $$ ¬Ž‡xxx§‡‡,-F‚;(ßú¨`ÌÄ °0ô*%,($ }}‰‰–¯}}‰,-F‚;(*ø¶øi¿¼hW¶@ú¨`ÌÄ °Dô%,($ }}‰‰–¯}}‰,-F‚;(*ø¶¼µ¶ ­Hhú÷¶¨`ÌÄ °Dô(  }}‰‰–¯}}‰,-F‚;(_÷¶1¶X—Hˆú˜¿È&~ ˜ ýô[840, »}‰‰–¯»}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶È:%Œ ® ô3J04($  »}‰‰–¯»}‰,-F‚;(˜h¿Å.–¶úÈ*ô9 U ×ôb;0( »}‰‰–¯»}‰,-F‚;(*ø¶1¶ú˜HÐ ÈŸh44$¬Ž‡xxx§‡‡,-F‚;(*ø¶¼hW¶@ú˜HÐ ÈŸ$¬Ž‡xxx§‡‡,-F‚;(hW¶¨i¿M|V¶@úÈ¿åV Ñ ìôI$HL(( »}‰‰–¯»}‰,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ÈÁèY Ú öôF HL,,$»}‰‰–¯»}‰,-F‚;(˜h¿Å.–¶úÈÂñU Ñ ïô 7 @<$$»}‰‰–¯»}‰,-F‚;(*ø¶1¶úÈÈw’  Vô &$0(  »}‰‰–¯»}‰,-F‚;(*ø¶¼hW¶@ú˜È  ´Ÿ$',$,$ ¬Ž‡xxx§‡‡,-F‚;(hW¶¨i¿M|V¶@ú˜HÐ ÈŸ0$¬Ž‡xxx§‡‡,-F‚;(ßú˜HÐ ÈŸ$¬Ž‡xxx§‡‡,-F‚;(*ø¶øi¿¼hW¶@ú˜8„, À xŸ->C: ¬Ž‡xxx§‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶˜8„, À xŸTt(\P,(¬Ž‡xxx§‡‡,-F‚;(˜h¿Å.–¶ú˜H\ è ŒŸ(p(PP,(¬Ž‡xxx§‡‡,-F‚;(*ø¶1¶ú˜È  ´Ÿ7 $ ,$ ¬Ž‡xxx§‡‡,-F‚;(*ø¶¼hW¶@ú˜HÐ ÈŸ<$¬Ž‡xxx§‡‡,-F‚;(hW¶¨i¿M|V¶@ú˜HÐ ÈŸ$¬Ž‡xxx§‡‡,-F‚;(ßú˜8„, À xŸ7t(\P,(¬Ž‡xxx§‡‡,-F‚;(r•¶¨h¿ÅHø¶°ú–¶˜8„, À xŸJt(\P,(¬Ž‡xxx§‡‡,-F‚;(˜h¿Å.–¶ú°8\8 <.N`4( ±}fxxx±}u,-F‚;(*ø¶1¶ú˜È  ´Ÿ $ ,$ ¬Ž‡xxx§‡‡,-F‚;(*ø¶¼hW¶@ú˜HÐ ÈŸ$¬Ž‡xxx§‡‡,-F‚;(hW¶¨i¿M|V¶@ú˜HÐ ÈŸ$¬Ž‡xxx§‡‡,-F‚;(ßú¯tèˆì ¨ œ`-0?<"%§–‡xxxÅxx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶tèˆì ¨ œ`F]&XT04+§–‡xxxÅxx,-F‚;(˜h¿Å.–¶útèˆì ¨ œ`/$ùø 2IL, 3ûâáý ! ,óÞÙÒÌÌý".6AHG.(4%ÿö/8$/317ÿ++(*òÞ ñâ %#.QS3-J<)A7**÷³’•š’åóXi}vDLüÜÌÏÃÚü;,ó¿ÎÙ¦™«ÓäûWvgmTAÿèúüý +U`X;00õ¿ÍÝ#'+íèôø×ÃÔÍÚì*  öáåÿ39K((((((((('''''('''&'&&&&&&&%%$$$$$##$##"#""!!!!!!!!!  !!!!!!"""""""""""####$$$$$$%%$$$%%%%%&%%%&&&&&&''&'(('''())))********)********+++++,++++,,,,------,,-----.---.----------,,,---,,,,,,,,,,,,,,,,,,,,,,,,,,,,++++++**********++**********)))))***)*******)*)))))))**))(((('''''&&&&&&''''&&&&&&&%%&%$$$$$$$########$#" !"""!  !  !îÃàFxH õë÷*TH ûA= "01! !-0#$,* !,+!&$ !   !&!  %! %# $& *)"'+"!(*& !)/(&/.&- -."!'$#)*%"#"#+.%!(*"%.( +0!-4*! &,,.1)!49($54$ .6,%.-!*:4%$&&0:0 *23*"+6.$,-"*<3+:%/>/*-! 6;'$-7.+5:3!,=;'""*6/!$," =F =@B-þÿ:R2#(0<-.) JF*&$14.-#&?7%$//22!<:"",0M7/I8'0/#!**!&%+4+".%",)$4;'þ..>5ó3!:) !&** ,. -7 ! ?3ÿö6)!#ÿ %14(ñ9F) ÿBHÿ#,)"'3,0 *0# $0' 00 '6&$#.* ð*02!50 -((9!)5 -0ÿEN"þ1'2Iõ+S+ý2B4%=K4%G?# (J:,>/+<;# 0HE0";E!J0!0@:!(997" ;J6%þJG1*I>">E)90+.!$2-,5!&"(! 11)*:/ $7) "9+$ '3 .%+-&'.&"$( 0' (, !6.2-%* 0924 &&#" -,##%!+. 0,)!"("")$,*#++-$-)*1,%!",%-/"$% !+.$! *2+$..%! +:5)48,%5;**32**:9*#27/" &)+/.%$*+*/.!)81#"%&,3.%$%%(..')0-)& '.,))&"#(+,,&!)*($'.*+*%*+$%)!(,#")' %**$ !!")-&!%#"&(%!"&&%%$""$$$# %/)!&)+$$(*'#$&'!"!#$ "!$$!# !  """ $"#!"! "!!    "!!"  ! !!  ! #$!!"#!!#$"!!"""""!!!!"###"!!"###"#%%$##$%''&$$$&'%%&&%%&&&&&'&%&'&%&&%%&&&%%&''&&'('''''&'))'%'((()(&'(()*(&''))'&&(*(''(((; 2ûú ýöýá!äïîÿù þüúñçïøê ýòü îýþÕýëþüèõí!þáÿöüê ë ýòóïñ0õÓì øêôûõìåþôðö ðåàô ðü"ýÎ2ëå íó ïìþþô÷ýôñ ø ì èôÙ &þßà+(óÞîìï Öá÷ñ øÜÙË'8Þíý îã  òòò5Ï-ÿäÿÜ -úùôëýñÔù('ôáø ÿÙ*ûé×êýúî#ÝÑ$í úä óã÷Øó.çüôþùùÿúüö½! éöó ùÝ(Òüÿ.Üí éÑ,Ûæîý#ÿìûýþ0Ž2 "¿"ì÷òö#+çØ %¾÷@Øóñ;íÅ8Ïßý%-×Î 3èà %åÞû+âÛû÷ ýûðâè%þÙêöèõ÷Øçâ7úÚ 9ØÎQÿÇ,3ÝÆø:á×ó0ï¼/4ºò-íËUñ¾ë1!§ÿbÔñ.Â0ì Þ#èù ã%.ð«é. áäçø!×ñ#ñEß— HÇE¼Ç#.óâ"Èö."ÿùçç)ÓÜ&óþÍó8þâô ô÷6ïÞñ.÷Ìì õîüõÒ"ãôJíÊó,$õù ñîè;7Å]<Ìú±ôRÇ#Åê6 Øå ÿµüIýììö3!êà øëêàÇì.üêï0öØâÙù44ñÎÏ' ÿ÷Â3ÒÉ7Zä»ùþöùâ óý"îñöî'8èÒãý!äÖ78ÐÕüÙÞgÅèûäé`õ×õò"Ê´þ#AØÛ05üŸÍ1QѶàNçÿîÈî úCÜ¥@&þÖ×!2þêÌ='òÖöÚ  ÷³äa#ÄÔ"×á4Öõ÷ïïð"2é°ïE0ÒËú6RÑÈ)ðóòñôÿî öúíã éúþûõÐ <ûÆÇ([ ´Õ0éðùÿ$ óÓâ.0ñóïÏá&QÕï'Üáù ö!$øó÷øîåðßXÊÓôÙ MßÜ+òç&¯Õ! ñúöì ýÏø öÊí9"ãÇó ô*0òÞÝ+"ÅÈ HôÞ½ "%&ÂÂ/ú³}«øÛ2@ÇÕM,ô¨à[Þ (ïøù úîà%÷öÀæcEºÉ" ðò(Êýüßóþøæíù$ñÁò$ìôÒâUNãËËú/3#öêÂÐ6*Óâöì.ëÎØ+ Ãû ìæìÝç;2éÈ>ïÜ)ðð'Þô0)ôßòûØö>àõÜèç ñãí*,æôïî"êÄ×%Ö$ÿÀ¹2[+ýÚâôúó)ó âõòö?!ïÔÊ %5 üåÐóü%;éâÓä!&÷åóÝàSJÒÆÊ>õèÒLñ¹PìÉäN'ð¹È8L íßÈö0 ûù 'Ç« O,ñ¦µ%B!òÝéðü'ØùÂÝ4(óÛã0Îñ Ùþ+ñÝ 1ʲã )3ØÐû"íæð*öÏÕRóÂÜ * æÐ?<Àïû"/å Ç>/ø¾Åý%7ç—%GÂÖ*üü  òûñßø$=ÿ»Ëö 'ìýè 4ÊÇD*ñìÿùóü<&׸ç%B"åí ôþýÔûÞù(èðìòÿøîúüôóÔõÞ8õ×ðÞ*HßÕê! ê ÷íüíûÿ ûÖï ) ´Ö4îø÷Ø(øðóéöõî"4ùüýÝñ#åÚ )ëíéüüöõõÛþ5ù áõÿ%ÿÖàùêàýúùãéÿ6,áÑÑè<_ï¬Þü ü %#à´ö7/ çÕ%çÀè)ò÷ý'ìÔô-ôõÝüý æØ#!ó õæñ  þöêóú!,ÙÖî2 ×ÓþêÛ%Úóÿéö û !ß®<ðøèþл 20×ßüûý)@ÜÈîê0;òÎß½ÿS2ùÚÅãúìì $çË!ûùÛÝó3!óðß3ü¿D òîèá >ÎéÝø 9.ãÊ×ë;/ôË!ëÐç$ýñä öø/ Öå× 7óÈì 4/ÕÔãü%Eöáç 1;îÒó 7ý©Ãï -?ÛÀÿö ù&4&íëê @$ÿíû ôåö1#æ²Éð"%öÉéÔÔ#<'üº²ý)-C äâÃÓ4h.áîôøíè;E¿©û2C!ýèÔìõþüòõÝÁöýÍ7Å9ûÑ1á+ôãô Ýõ/êó0ùÁ% Ò "þ ô× É»&Ì( Ô òæÜ-åìùý þòïðæ)ØÞ >ÛÊ0õØ,Õåý é üþü(ñû æù îñûøçëõ%ýÝéõCáÜ7çÂJæËOí´LèçtßÒ.®ðD´"2¹('¢&Ù)ÈÈ &Â-ô çÓ#Ùð þúõü à,Ì ß%øÂM³8«%¸/â8çÌNçÇEëÒ?åäRÝ×U¿ØVåáZÜÑ3öÓ; Þ/ù³? YŸB‚7À <Ñ8è÷*óâ!óÆ Ø$ÉûÿõúÒ í2 É-Ï$ûï%î×1Þ8Òûõì"îÍì2óØ.Û Ü%×àøÚì$Ò ,¶\¨óIÔñ<âí+Ôú$üþÜÚ àD#¦¿1*Ü ööÈOÐ;–é1Ô4èýÒä ùÖ%ûÇ)à$¹Ð!4ÏÚî0ÈýÕ)ß÷æòøëôï õïâ: ÎôïLýÒþþíù) äùýì(Ò÷ óïèö ð%Õ)Ä÷.éíòîù þîøíôîò ûáÿÝô óýìö#óó÷øí#çöõöçèäýõ"ûúðç!ûð ä÷!ß,øý ü!ùö÷ñ ýåæøê Þà&ÙÎ/Î6Ï ÌCÑí1Ñä<ÙåBñÖ2 à&× ç$ßÜ'Ò×:ïÌ3þÉ!ËÞ&Óì/Üñ(ýí/+Ö5ð/ü*ô ôüâõôý%õáòß ñé Ýþ ÝÓóùòûäñúì óúý÷÷Ú ù ùÿÿ( ùûôïý ýü÷éûãäôêùÿü ï öýúòëóõ÷ôöû þÿ  ÿ ú  ìû úÿ÷ùýý ÿíûöøõîúþüýñíðèøøíòè÷þòúúüûû è -       *:"ú     ùåÕâ%w> ñÐÈä ,FUM1ïÝâø #.7=3 Ö¶Ï0<=7% þý*.$ÿóö  ÷ãÖß C_L%ÿùîõ64)&ïãú !  úû   "óôü" ýý  þ þù$ û   ûð$   ï-#û'óé/*ù     ! ðï ,0÷÷+   úó*íð-ð#  ýí 94é"  *0ñô,'÷ô?,øùúø üÝØò7\g<ñúôäü/6 D\!ØÈû- 7O á) '÷áû=L"öü !/%ï<ô+í8!ûñ :C ò ö &öø! ï2#ÿù("êE+ñû%3ÏÓ ZJæí,) ìý#$ 2&ÔÌ2^ä" ýù@/ìï,ý(ï )' åÞ).! òÜ;)üü  )&üê0ìë<"äî7CÍÐUBýäð'5ýèõ02øë@ÑÂ'j¿î8/ýó öù+!òü) þõ $/èè2áø#-×ï@PÒñú + öô õû*!üþúö/ ó % üðþ6!ðÖþCFòÈ.$ýä"  $íþ%ù%÷è/ óý 40ýëõ).ñÝX;ØÁ"báþ ø U%Ùæ&ÿð(òK2òãò 8; òý(' úý28Þ))éô/-%  "6&þíõ=7 ö ,!üíE6îá:üîô2aÉç%+0)ñé#%þ;Ïù,?DÞÕ%5,ð+-ìø#ó (ëëN=þáð&7ûý  þÿ!6õÿ0îô4öê -!ô./ï úû% áú/$ýð ú ÿü&â S3×Ç80î #÷ þ    òþóï62 òý&òô #/æñ$)êÖ:þý ÷ )óò,ýø7ñ &û#ïç<0 ú×öS^ÒáóUIúÎî&@âÞ T"ËÚ?JìÑB$øíñ9=Þù/6à÷#( ÷@âî*÷ü1.÷Ýö!95 åø*+ï -/ çý"þ, ò!øý!,ýø %÷æ=& .' ôë :( &ò/,ö$ 2'ú òC  "8#÷ð$  ï67öþý-þÿ ùý02é÷  "ý$ï 6.õÿ,- ð !ö##ýó÷4;úÙþ òñ& !÷ó   ü& ÷"ðÝ# þñ $÷ú-ïÿ îò  ÷ ü ÷ù%5Ûõ"'÷  èø  #þ ö ù  ÿý.0 ìð ðû#5ïÞû&3üñ!! ýü $" ÿ   ô(,ññ+ 'ñû *ðë &" ù1ðþ   %ý%! &ýñ&þ  þ*  '.êñ" öò #" úÿ)ÿ )þü(!  )òø*#øò# ÿ  $ø  ü(ø         ÿ    ÿ ý                      Ú ßÃÉ÷*JR?ïÒ¹Åó+íC[ýÛ !!-6ù.Nå$O@îø&3$4ïE:÷ì/@*Pñþ;;'ë'C)'. íÿ/QE )"#;9þîDO ÿ#-G^(ÙöE:û\;óJåKaÝC3*7ð$4"7*NåüRz(Ïå;G !?"ö6Y>ïò%9:A )(þÿ".>>óX5þüC] ñ"7ÿ5;$ 3?÷$L-%)-;+)ü!F@! ò@3$I&ëí'0'%7ê $&% û'!# ,&îZ8ëþ!E7öõ%A êó;GÝ*,*ü) ú +,%&0ÿþû @F Üó#ôG-ïñ þA*ëá-8#ûè'ù.û# þ '6Êâ9G.ãõ-ð (ú 0-ýþ ')úçC8õ÷ùäæ øé+; ì÷1I% # $$/þ='úö$!ü'%" " .?4÷-B,"#./ü 98ý!&!%" 2(ÿ;=!!&ø== '") 8þ* 9*'<&GE),#%,B% $3:*#1" 85)"$!<=*û8E"!(*"+1*0,6# ?GøLNç59'üV617 BM* "'D0 )/#BD ö 8.#>4 ôJK 3&û(0!&,%F7-()"'-2AÝ:445ú5H%ûïE81-ü÷974÷8M&ïú+KKßWQíô$D(ÿ EB!öHF +0@L÷ý]G :2%0$ $!+272úIB"'#,!('0Kî14 $) &86ù B üAòù6P/ %2)$ð6D)  þ/-% 6=ø*>0 %$ *?/ =:''$8&*6K%ùô BHø&&)2#ÿ063@(.%C)3$%,@#":1" 31*%();7/( 3K* -" ,B3K4( º˜‡xxxÀ›–,-F‚;(*ø¶¼hW¶@úœx ˜ < +2=*! º˜‡xxxÀ›–,-F‚;(\i˜¿ûúé¶ËÈõ$ º ¥ô=@X8,0$»}‰‰–¯»}‰,-F‚;(r•¶°ú–È"¥F n OôFU(XD@(»}‰‰–¯»}‰,-F‚;(˜h¿Å.–¶úÈ Ðñ < ÂôHc4`\0, »}‰‰–¯»}‰,-F‚;(*ø¶1¶úÔjÈ  îÀ=Œ4_r>3+¥”‡xxx§Ž‡,-F‚;(*ø¶¼hW¶@úÈ‘äv á 8ô<0lD(,»}‰‰–¯»}‰,-F‚;(\i˜¿ûúé¶È-9Ñ  zôj.V6$ »}‰‰–¯»}‰,-F‚;(ß0ú0×!­@œÜ B ä-, <<;8 ¶i€xxx§ix,-F‚;(r•¶°ú–­@œÜ B ä(8DDB@ ¶i€xxx§ix,-F‚;(˜h¿Å.–¶úôålR Y "Z:CBA7# Ýz“xxx§ix,-F‚;(*ø¶1¶úHÌ h à(+887* ô„Ÿxxx‡´–,-F‚;(*ø¶¼hW¶@úHÌ h à 00/$ ô„Ÿxxx‡´–,-F‚;(\i˜¿ûúé¶áˆ,` ” )- 8,% xxixxx€-b<[D& »}‰‰–¯»}‰,-F‚;(*ø¶1¶úȰX„ H ‚ôЦ & Ë(#B%”~PxxxKZZ,-F‚;(r•¶°ú–Ž>Ц & Ë('E'”~PxxxKZZ,-F‚;(˜h¿Å.–¶ú“UŸ¹  Á%(& D+ —UxxxKZZ,-F‚;(*ø¶1¶úÀ(\d ¤ `ŸFcJQ-+¬Ž‡xxx§‡‡,-F‚;(*ø¶¼hW¶@ú¸H¬ ¤ 5 2QGV*)­Ž‡xxx¶ix,-F‚;(\i˜¿ûú鶸H¬ ¤ 5 .6@  ­Ž‡xxx¶ix,-F‚;(ß0ú0Í„¸$ ä `d-0!  Z‡xxx ‡‡,-F‚;(r•¶°ú–„¸$ ä `d(&:'!$!  Z‡xxx ‡‡,-F‚;(˜h¿Å.–¶úŽSœJ ü |—P5E2)+& ©b‰zxx ‡‡,-F‚;(*ø¶1¶úèh   Ø xf(T,NR6,ÿª£‘xxÿ®­,-F‚;(*ø¶¼hW¶@úèh   Ø xf- 9<(  ÿª£‘xxÿ®­,-F‚;(\i˜¿ûúé¶Í“îº  Q-& <3/2 §e{xxx§Zx,-F‚;(r•¶°ú–„èä `d(:'$$! §Z‡xxx§‡‡,-F‚;(˜h¿Å.–¶ú“6º: ñ q½P6D1+,' ¨^‰xxx ‡‡,-F‚;(*ø¶1¶úÈØ P ï?2="D@>2& ä|šxxx ‡‡,-F‚;(*ø¶¼hW¶@úHÌ h à#321& ô„Ÿxxx‡´–,-F‚;(\i˜¿ûúé¶„èä `d('9'$$! §Z‡xxx§‡‡,-F‚;(r•¶°ú–„èä `dA=H1--) §Z‡xxx§‡‡,-F‚;(˜h¿Å.–¶ú€4Û Ú ñá2;F6-.' §i‡xxx§‡‡,-F‚;(*ø¶1¶út T` ¼ ¤X(!03"%§–‡xxxÅxx,-F‚;(*ø¶¼hW¶@útà,t àX02"" §–‡xxxÅxx,-F‚;(\i˜¿ûúé¶®ˆÈØ` d œ ,'7:"!¥xxx¢¥,-F‚;(r•¶¨h¿ÅHø¶°ú–¶ˆÈØ` d œ P:CG)(¥xxx¢¥,-F‚;(˜h¿Å.–¶úˆÈØ` d œ 24?C'&¥xxx¢¥,-F‚;(*ø¶1¶úˆÈØ` d œ #47  ¥xxx¢¥,-F‚;(*ø¶¼hW¶@ú Ž4ˆ  ¼ ìc2*9',$ #( âÉ꺘…¢ÅÁ¢Â'ðñõ÷ï*;79Ma;) ïÊÔÞÒÕÛì÷îéæÐÓÂĺÁÈÅÍèþ 1' ! !î÷ìçáîõßÜâ÷òâûù&1% /'#+ûößôúíðòöù ÿûÛðõ $*($!üòüú/þîæ×ÞäëûøèÂÈè»ÕÄ ñãæÒÖÎîòéó %ïÄÇ´Õ¾çý,C6J'êÓÔÔáé /;0: óÕÜÕÉèô #þúåÐ×½Ïßô,;%(þòøø-9J;GOH%òôø )+76?0%üïÎçãÛü #1('#íæäÚàáçûýàéàéÏÌÀßÈÃÉÚÙØééíôìö  !+&!÷÷ùçöôôíüøÿ ýóûêþíëâóà÷ï û÷úõóì÷÷õùóåìãíìýô þ "/%#$)"'"õäüÜçüéÖùèíóêúóÎëÝíóàîöü  ñþîìòóøýüíûßúÙíäâóï  %%ÿøùøëöÿùïù øÿûþ!'$&0+0H0'1/!%(ûÿñÚßÕÎÝÙâÑîñ÷ýèñòôëð $ çèâßìÌû×ïüòûìîùÑÜʽËÄÁÐÒìä ÿ øþø0B@M,<5  íýÿ÷úüüõ üþåóîúïúêøîùóóüôþôùøæýïñôòû ôøþçßíÓ×ÑåñåèïãöÝèçèèàî÷ýò ûþ ûø    ! #&üýþý # þ ÿ öóîûøêòÿùöû÷ïïåòãóÙÛäÙâãàòãùúâÿ÷óùî îîòèüäåòþû"    ÷û÷þöøùåùçôïöýü÷ûöøñìõáÝôâîöñÿ  ûçùøðý ý÷íñëãçéêùý þÿ úøöüóëïêéîûýôúóù   þóôû # !! üõûýýüþüùýôÿöþôûþíôþõýü þìëåáßÚéàï÷ýùýþüøÿøøûüýûþÿøûúùòîïøèðûÿ þýúþ÷ÿïÿþïçëïõø      þïþëóïÿÿý ÿ  ô÷ ü üýúþýëóîóæøôïñþ òñÿùöíô÷ø÷ü÷÷øüÿÿÿþíþöÿøþ øûöîôóïõú  ñòôïòðÿöûóÿöþÿ  üøøþòôüôüöø   ûüýýüþüùýôÿöþôûþíôþõýü þìëåáßÚéàï÷ýùýþüøÿøøûüýûþÿøûúùòîïøèðûÿ þýúþ÷ÿïÿþïçëïõø      þïþëóïÿÿý ÿ  ô÷ ü üýúþýëóîóæøôïñþ òñÿùöíô÷ø÷ü÷÷øüÿÿÿþíþöÿøþ $+29?FLSY_ekpv{†‹•™ž¢§«¯³·»¾ÂÅÉÌÏÒÕ×ÚÜßáãåçèêìíîïðñòóóôôôôôôôóóòñðïîíìêèçåãáßÜÚ×ÕÒÏÌÉž»·³¯«§¢ž™•‹†{vpke_YSLF?92+$Ìžü< ¨ (/ 4G'/ ª¥–xxxª´x,-F‚;(r•¶¨h¿ÅHø¶°ú–¶Ì]Ð< ¨ 2s-Ye8C!ª¥–xxxª´x,-F‚;(˜h¿Å.–¶úÌ]Ð< ¨ h*T`5@ ª¥–xxxª´x,-F‚;(*ø¶1¶ú¾ òT ð ì KE%GM37©Ž£xxxª´x,-F‚;(*ø¶¼hW¶@úœ˜Œ ˜ ¦ %6/9, §ZÃxxxzx‡,-F‚;(hW¶¨i¿M|V¶@úœ®  \  11-*! §Z‡xxxzxx,-F‚;(ßúÿÿÿÿÿÿÿÿþÿÿþýûùõîæàåû&"üêåëü úìñ÷þ ôèëþ úóòû÷ïôêÉÁì<^A ÞÑÀ¸ÝL@ëÚÍÈÞ>> îéäïï úùßö÷þ#úÝëñèû( òÚçø  øíìðúôíéùðîõ÷ø%ýòïøùéê(R'êÍêýøõûüéùø ùðýô"ùìóú éäê0êÛö!1ýíèçïù$AßÛùöî üýæõ÷ &) àÛåËËü+A.õàÇÉç$%ýñäÜþ  ñïûüðò þüÿòðòù ííú ÷ê÷ üììü þôèïüúÿ ÷òüúóêòÿôù Ýâü  òìôüóøó÷ ú÷þ÷ùüýù ÷éðú*ðõú  ýôñû ýïà'õÿöôÐã æöÙöõìïõ8=ððÔý÷!"ÖïÚû:'+ܪ# øäþîãÕÏâB=åù  âÜõ ÿÜíùè4øÜð-%þùñåÙú ÷÷ ôôùÖÙ óüöõñÜáÿ ÿÝðÿ ÕÜü$ÕÁè!òðúÚß#ò÷äãôíøüõÿöãù òäöø+ òÛéøýöóýå  öèãò #8ñ úèú2úä  ÛÙ=ßÿïÔWÚßäýOYë©é0ÍñLSÉ·ß91í÷ô 5âï /8÷ÕßÚë3z9ßéûȵQ>í úÜè $øø üöñÑÏ B`%ÐáùêàÜTH:ÜÉÑä%ò$õ×åÚø øôøñèè íÎÔ!öÝÂÏÿ% ùðÌ×íù-×ÒÑì ( ÕÊÑ  ùèºê&&ÿâîæîô-âó ÿò%ðÜÜ. ãÃø!/ ÝÇó>&ïýúàìB6ñãúùüú öñöóò7Bõ¼Á8(õÇËê1-#à·Ê4Pæõêä÷0<ùÞìÿ7ß½¼ Y2àÙÜ¿ûK(ùüüêü#úì ù×ïÿ/+òÏóÝâ6h"¹¦A Ñú/ðåöçé1õÁÔ4Yù¹þ,îíþ óýýÝöÿåý-Ο­û9eFïÄÑú÷ñ äÔÛ'õê6ÂÌ .Øßû$ Ò½ 2ÒË #þòõ#2ùÝç /¯±_a ÐÎ×é 1=6 ßÏÆë,P,ù âÃÝ!ME ÚÞàâ&#èº×5LÙü×Î6rÍÃïæö þ(òÈÊô8>ÔÇ # çæýí<7þí üåøú)(ì×ö"êÖTHüø,úê D"ÒÕîîö!þÝí úõ/B åÖ¿ð@:"%ü¦®ýA=8μ¼çú lpÓµÕü#LãáÉô//òîøï õ "åÁÝú÷÷ÿûâÅÕ8 ÷ÿíçßø/íñ ì/ÙäýñÛëêÝøæäõüþýùþýùö þìðúö öéìûùöõüêõ íéûóæø'ëì$ñß ýü ûóò ÷ææ-çÅð  !*ðÒÛ/ø&ÂÊ'0ìèÿÊå0< ÐÝ ÝÝ  íã ëã0úå /4óß!(ôÛýõ#"çÝãÎù>p ÃÐïö úþíß 7¼À!" çúÈÛ1éÛ÷ ðúòáçòñ+ Øá ÛÆà 2ôüð×Çç!ùÿæçøòï÷üûùáðþëôÿæÉäùë ÝÒÿìêõæóÿúêóõéíîÝû öèý Õá÷ñ úõåà4êçñóú0üûìýó&6òÎé ,éÒè þôðéæïFï ðÒÿ52 í)0úëò# øàÏõPN!ûíÖ× :1Ú§´÷B^2ôþ ãÖý ó>X"ѱì(#ðø÷êþùý íÃ×!ÿÝÏí âÏßüþûæÍÙòöùåØÖóäéûòîôúúý ñÇÊù'ÚêýþÕÅå øåÒáèö×ÙÿùôøâøìóöÛòíõüæùõÜÓö"×Ôâ'ÿ þÎçþ) þÑ×<;ÿÝÑ óüû #þíúú÷$ôñôþû'*ôëö  öøü (ÙÉ'úîáú ÿ ÿúíòÿ/2 äÅÙ-üõüôóýôû ìÆâ  ßÞþøÿý#øîåÉû ú î¿Ì,#öâñûÓàöäóïïõïàâ ñçâê þÿüöñÝæ ó÷ÿïéñýìîÛßãÝñ÷íîô çíþó óÞô ÷ûÿäíø ôÜõ  çâöíù ÷ùëß !ïü-êäý þôì %ÿ õ) ÿ Ýì%'ëç)ý ÿô ûì!  õëû úýóó7)õî×Ù 3+ìãîñò÷ íåÿîùéúõîêâ $ Úß)ýåóøä ÷øÿ÷þ÷øæ÷÷õ'óñø þþ öèôùîðÛé4 ìæõùêú2æëñ úáñ îûûôúû ú÷öýõüøêöü%ãáæ÷( îëðÞ+åðþö üñøõôûÿ øãþõí$ûæðü ïàùôü ýñô ÿóÿ ú ÿæÈì':õ äØööñú  ôíÿýô"îì çÿí÷þööúïò øú ïô öùø ü ÿûûöüÿ üðêøçð îäééÿÿÿÿý îãÿüóáðòú àèùñ  öð òûô-ÿæ÷ æÚ8ãßîì'ôûðåüóâõüð÷#ñíïéú"!ýðöóùóîöûø ïòúöþ óö úô÷ùü ýûþÿû÷ òñþ õó üíþúíÿëð) ïèö ÿðöùù!ìéÿ ïü  õõ ýýþõóùèßï%üëðÿøõ  ÷òîí ûêæí ÿôïñòèçêÿ ïçïüúíåùû ûùäÞ& úõûø çØúîõýøúó èóùé ùøù ñ÷ö÷ÿ ÿýöðùúðÿþúþçõ  þëôîúõêù ÷ôù ûþôøüõ÷ üëð òý üðùûðû ÿïüùù÷ðþ üóù ýõñýù ÷óü ÷øööþ÷öñùû öôûùîø òîüýú øæé ÿ÷óèÿù ùèò ôøõóùý ÿûûùûþøÿ óõøûùú ö÷ýúøò÷ö úèï !÷õøöÿ ýààõùðäôÿø þêÿö÷ÿÿ  ÷ëèö"÷òòüûÿðöÿüý ÿðûøñïü ÷ûþ ïøÿÿùú îöüûþöùÿøù ûêüþóõ øóõîþ ùùýøï÷ ýúîòöîù ðïü öðô òïüò üõöðü üþüþüýúú ùö üüþüþ ÷ðþü ìô úõöýûýù ø÷ þýûø þ üôû ÷ õöþ öÿ ûþ÷ÿ üþüøýø þôóí öýÿôþõþ ÷æø úùÿíý  ïó ÿýóõýùïö ûñü ûüùöüúøûÿþþ ÿôðö øñý üøôú úôøýûûøøþùú÷þ÷û òöúúøõýüöùöûüýúÿû÷ýøøúþýýôøú úøúûý þþýûýÿþ ýöþýÿÿøõ ûþñîû  ÿ÷õü  ÿ÷ÿþþö÷  ööý þøþþ ûóÿ ÷ö  ûðÿüþ ôùù÷ü ùýÿ ÿøÿ þõùþúþîòÿùúú  ýõûýü  ûûøô ùõóú ùøûüùü üøüùñþ úðöýùý úõïö üùüþ ÿòñý üý öîú ÿýúø ÷øýþýøüÿÿýýÿüÿùúýüùýüûýùÿúþþýþýùùÿÿþÿüÿüúÿÿýüù÷üûþøöÿ õóú ýôöÿ øùøü úóööü  üôóñù ýüóïü õíñû  õñõþ øîñ ýù÷ø  ýþüõü øöûÿ üô÷ý ýùöøûÿùøü ÿýùûþûüþþ ýøúüüúý ûûþûùý ýýüþ ùóùýúúû þÿÿÿÿþúûÿþûÿþüÿþÿûùþ ûú þýûûÿÿüüÿûûÿÿ ÿúüýûûÿÿøøþþûýþÿ ýúú þþûýøõýûúý ÿøùûÿûúþ ÿýüüûþÿþþþÿýþþþþÿþýþÿûûþüÿþúþÿþûþÿþûýýýýÿýüýýûüÿûûÿýýþÿÿüþÿþùþÿýÿÈ¿´, | Ø€2)685*" ¹k‰xxx¹k,-F‚;(r•¶¨h¿ÅHø¶°ú–¶¿´, | Ø€PM#KMI9/ ¹k‰xxx¹k,-F‚;(˜h¿Å.–¶ú¿´, | Ø€FA EGC5+ ¹k‰xxx¹k,-F‚;(*ø¶1¶ú¿´, | Ø€.0-# ¹k‰xxx¹k,-F‚;(*ø¶¼hW¶@ú¼0üýýøûøøü÷ÿûóù÷öüúýÿüýûùü öìüøöñ ýñøþóõ êê ðð ÿíõüìòú óÔêúöïï þóýôèù#ÿÔ/èÕþ'$îãðå,?òÊä /$÷ÑÏ/üîÕë!8ÕÍë,îîð õîô $Öã #ðÒ<ÛÙ 1çâô#?ݪ IÃÆæEJÕËæ0üûÈÊm[΢GðÞÒ87þÝ ã.íûÓ Gõ¶¸[UíÊÔ&1Éø4šÚL7Ì åçìýêJäIMܲ'3ÛÚ ÙJþªÝ0±¥KZ%ñ“×F3ýÉÙUâúûÞÚ/"íåä2øÛü3üññ' ÿɱMYíÄÞý<:ÐÖÎ3Kœ¢'iô¸ÌÎ;?³Ôâ6%Ä"Òçïèýµþ6 ë£>5䙸. ý ¼ Üû. Ãó"»ÁGÐú(ñîÝÉRS¹Ë$¡ÿlú³Ð3/µà)(4—ÝY|·ÀÉÙZ}èºÐº9S5îŠæ6ðÇí M"ѳ¶#q:ÇµÚ 9Wä™À(T!øžê? ûäãôù#GÛ•"07¸× UÂûãá<[ÙÑÊÙmIÎÈ÷öô½ý^ Ä ìÿî ïÿé&½3øíÙC-ÏÝì 4$çá üúÜÙE,åÜäì03ç8éÂÜ"\0¿®C2ùæêçAíï÷þßL»ãYA×¢Äû.T8ûÕ¿Ý;.æö éÿþèôúà /üáæ!ßê -#ìÊÖý/>âÞô øôàþ6#óðûøÿ*øÕè&þãï êêçù)/÷è×é+=êÙÛø/!øòþ#øÑå ( ûàÛõ & ññåò) ÷ðöùùþ  ûøöùö ó÷ÿøúáãý úþñòÿ øþøýóè÷ö÷øÿÿöðÿýóó ùöñø øòýúüþöðýþÿ ÿùþýùøûþðòý ýùûúüÿù÷ þüûù÷ôû ÷õûþþ ýùøöýüýûûþûþþüþÿüûþÿ þûüÿüýÿÿýÿÿÿüþþÿüÿÿþüüÿþþÿÿÿÿÿÿÿýÿýÿþþüÿþþÿþÿÿÿþþÿÿ¬‚ . ŶÖ7-!ðÞ ÿÕÏæZd§ãó&`ƒèKÊ"óÿïÖ)  ëÓâ÷# ØØÿ45ÿùò÷ÿùèÏé )êüû9÷ÎÜè6'Þðï1%Þß%ðíù õÔã4 ôâæ)-ÔÙçîÚïþùÿâ÷éÙî(@òçöú  ûÙë   æÞç ûüþççñÿ öþ ìîá  ö ùïçã Q9úÈÖáý  ûæèú ÷ùöùýÿðëø* øåï÷ÿø ôäîþ üýùû øé÷ úí÷ÿùùûú üüú  ûÿýôúýóöúûõÿûô÷ûûøþÿýú ÿ úûý ÿýþ ü ýöüüýÿýýÿþýÿÿÿÿþüÿÿÿþýýþÿûûþÿÿÿÿÿÿÿþþÿÿÿþþþÿÿÿþÿÿÿþþÿþÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿÿû÷÷û þüùúøÿ ÿþýÿþÿÿþþþüþþþþþÿÿþûüÿýüýþþÿÿÿÿþýÿþýÿþýÿÿÿÿÿÿÿýûûýþýüüýÿþþÿÿÿÿÿÿÿÿÿþÿÿÿþýýýþÿûûýÿÿþüüÿþþÿÿÿÿÿÿÿþýüþÿýþÿÿÿÿÿÿþþÿ¥tŒt ¼ tXnV)O`68+§–‡xxxÅxx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶tˆ X X7+. §–‡xxxÅxx,-F‚;(˜h¿Å.–¶útHxÐà ˜ X+% §–‡xxxÅxx,-F‚;(*ø¶1¶útŒt ¼ tX22E*, ¦‘…xxxÅxx,-F‚;(r•¶¨h¿ÅHø¶°ú–¶{µ° Æ ˆ&ZX(S\8:+¦‘…xxxÅxx,-F‚;(˜h¿Å.–¶ú{µ° Æ ˆ&*9?&(¦‘…xxxÅxx,-F‚;(*ø¶1¶úsources_5316/external/espeak/espeak-data/tr_dict0000644000176700017670000001353111663004331020547 0ustar paulpaulM ‡ çAA# Ç,ÔÓÎTAAE$ Æ4Q@BA Ik_/k3WY#01#AFkÃ$Ñ€AkÄfO8AAQkÄdòÓHAMkA ikA$% %9oVFk& RkA(Xk *9 7F V +#3/ A,1#A07kA4?kÅBR8PBA82kÃL–€L Á7tk2ito2_=7tk2it2i:#n‰ E#jB<=Arlit2i:#n‰ E#jB$F'7#.N k? -  N"sj%Q j2L#?h   Ttj!=c'B E#jB sources_5316/external/espeak/espeak-data/no_dict0000644000176700017670000001014511663004331020534 0ustar paulpaulö Ã4S€HAvAEsA WsAFsÃL“€L_0Ci{2F3 FjÃL“…LAqQAOsÃ,€LA ix#2{?? 3/qB2A$lÁ$H%03zWq2/&w OA(9s *W]#32j +07{WA,1x/W13wW/3 1A0q7A4q?Ã4S“Ã4S“H _0zOA8q2 =#37l1 @13o77u7QuA@0sAD1|AHr3ÃÁ@LALqWAP/s F ó”$åE Ã4QÀLAXRs\w?Rq2F/W13wW/3 1A\FwE q7Rs^Wk31{?Q7q1W_1M1q//|W 2A`q1W_1M2s2?k77l&z2ÃÂRLAhWq/Â@HÅ-SŽ@LÄ Hà ôÀHEM”ÔÐWmW/s?_192k/ 2FjÂ`HÄTáHÃã€H_18u/ 2FjÄ SŽL EHPD  à HÕL_11q77qR/jB r3BPFlL CUFsL_13/3q/ 2Fj _1w??uÂPLà @L _ /k7Fj_15Qq?/ 2FjB@q/H_12/w7R/j_17Wm/ 2FjÃL°LL_14Q9y3/ ?Fj Cáj2F ÄSŽL_16Wq1W/ 2Fj LÂLÄ0‡LH_0M1/|W 2FjÓ€Là €LÓ…Là €HÄÃHH E ƒÀ Äô„$Ä$ã…8à “LÂHÄT…LL _1Qo3W/j C(QÀ9rkL _2u2F3j _3/3qF9j _ 2FjÅ SŽ0LÄô8 _5Qq?/j _6Yq/ jÂàH _3X/3q/ l _0Ci{2F3j_1Cq/i{2F3j _192k/ 2 _18u/ 2 _11q7Rj _10/l_13/3q/ 2 _12/w7R _15Qq?/ 2_14Q9y3/ 2 _4Q9t3j _17Wm/ 2_16Wq1W/ 2Ã=4ÀL _7XWm/ l _2X]|j_8w/ 2Fj EL4…à _4XQp3/l C8ñ@2y j _5XQq?/l EW/o3 q2 _=#37l1_7kE%iF#4%_<1(4#BF#4% _Fl/_[1(4(BW%1(__O#4%WE#:#i_]1(4(BW%1(/(/(0 _O4#R_{1(4(B1(4#:#7 _ (?7p/_}1(4(B1(4#:#7/(/(0Ã@UHÅ@L€Ha A#aua#upisbEenE ecJhhdFjIe Akek fQfgOhii A%i%ejIk1 en1 ehcl7lm?e? empe? ?0 n2yAgBo A'o'e(rlp0pe0 hQq1u1:re34sWseW jayt/er/ 3el/ 7jJu A(u(vRw:x1WVy9zV******** -  /#2F#1(4#B*E%2/#B$Fl7#3sources_5316/external/espeak/espeak-data/nci_dict0000644000176700017670000000277611663004331020704 0ustar paulpaulû_20W$?0l :#77%_30W$?0l :#77%'??#/7#1/7%_3XW$?0l :#77%'??#/7#1/7%'2_10?#/7#1/7%_1X?#/7#1/7%'2_2XW$?0l :#77%'2 _3$ 9% _2l ?$_1W$ _0#/7$ _7J%Nl ?$ _6J%1:#W$ _5?# 1:% 77% _42# :%_9J%:12# :% _8J%:1$ 9%BēīeiÄ# Ä“ $ $ Ä«% Å' a#c1u1:hJBWe$hu:i%l7m?n2o'p0qu1t/u'q1A:hc:1xYy9zW# k1r3w:bEdFgOfQvRsWçjcsources_5316/external/espeak/espeak-data/bg_dict0000644000176700017670000006451211663004330020516 0ustar paulpaulªcÅ@õ0BÅ7¦QQ0BÅ2âPQ0CÅ/4Ñ­0B ÆX”“<ÃÄC ÆW£k<ÃÄD Æ2M<ÃÄD ƨ‹Ó<ÃÄDÅ4ËBÃO€HBįc‰4CÄJ1TDBÄCa‹LBÄA‰ AÅB”:0CÄôÔdBÁHÅ•K0CÃK JB ÉDIäLCA(%HÅ =Œ<@CÃZRBÃMsB ÆB”Æ-$ÀBÃ,sB*VR$VF%J1#ÄCÐE$H +07(W ÆTôÝ<£BÃM}B ÆA>Ï´îDA,1 ÅXÏOVàCÅI<8% CÅÂWïCźC- Æ4qà”€D Æ, <ÞÀC ƽ2Dìò€DÃÝÌBÃDBÄ# E$H/2#1w'2$2#J$"/#Ä¥SìCÄDI¼CÃ<"=BÄ6âsìDÄ4dÆôCÃRYBA07 ÅE²ø% CÃVBż±“wÐC ÆÁ‹Oa@CÃÛÓB ÆñHÉÀC ÇBѳLóE Ç4dÆôóE ÆBPN±BA4? Å ¡ŒPCÅDQ`AÃ[£oBÃ@ñ“B Æ[cUC ÆL”UC ÆA[WUB ÆBÑUD Æ0”ÏUC Æ/¤ÏUC Æ3UCÄSaÁ(CÄ7GìCA82 ÅHOP°CÅ4$°BÅñ6àCðó{CÃ.ôóBÃô’BÅU´“l°B Æ@űSCÅ `ȰB Æè”“±SD=$"#R2'2# ÆD %&ÌAÄaA8B ÆI6Ë3‚RCÄHbéLBÃK UBÄCf LAÄ,õFÄCÄìdÉ,C ÆQŒ ’Aú™B @17'?E#A@0 ÃL™NB ÆÆ="øD Æ€¥ÆCmED ÆMÂãmEDÄ_úÄAÃUM‘B ÈI:PLóI_DÄI3É,BÄÔSÍìCÄ CÌBATQ ÆJTÉI2KC Æ/5ÆHœûE Æ´“îC“C ÆK¢ÏTC Æ@Ñ'¥€C ÇTôýSìE ÆTôÏUC ÆO³OUC ÆcOUC ÆMBRCCAXc Ã"cÊB ÆPÂX8’ÀA ÆLoFL’ÀD ÆASÀ’ÀA ÇcÇ¢T4CÄP€†,B ÈMBJN$°B ÈI<$Î$°AÄÜ5 BÄ,ôÌÌBÃ"cÅB\'E"#/2#2#1w'2$2#J$"/#A\s ÅLððCÅØÐ$PC ÉDI=1–8’ÀE ÉA"VàÏ0ñEÅ@‘“0CÅ@‹¨ÀBÅŒŽŽ$°AÅŒNÎ$°AÅ,BQBÅb$°Bų0CÅWå90C ÆMÒCÔüC Æ,Ï0’ÀC×B ^1'7%E1#ÃN’=B_1M1a%7#F#A`J ÅL`†gÀCÅEFC0BÃ7>–BÅ,m=0CÃB Æ$ƒFUH_1M2$F%2?%7%'2 Æ[c‰-ß@C ÆHMß@C Æ/Æ-ÀD ÆÅ<ÛÀC_1M3$F%2?%7%#"F Ç0mR¹NLDÄ[µ*4CÄT’ ,BÄLa0BÄJQIÌCÄ@ð(BÄÅ% ÄCAdY É/5ûLÐJI?@BÅ ²ô@BÅ C<@BÃcÓBÄ=1'ôAÄô‘1´DAhY/ ÅDPàBÅÔSÌ CŽ?6ðD Æ,0EDÀB Æd ”ÀBÃI´€HÃ<#pBĆ\BÄ PðB Al$"O'7#?Å\cVðCÅXñA” CÅLcW0CŰ$°BÅ9BÌCÅ$Ü$°A ÆI>/œa@D ÆHcp8’ÀA Æ0‘&8’ÀA Ç:sÂ<@edEÄ[F,B ÆÜÙ CCÄ,`@BÅTÃÓ'°C ÆI@’MSB ÆI4[ âKBÅ,{O0CÄI´¥ BÄK HC At$"?#w 1Å #ÒÔPCÅ"¼çPDÃCeoBÃ$ÓÓBv Ç/1O7T4C È@óDPDÄókÄCÄðÆ`Bx ÅD”Î$°B Æ,;Ó%1“C ÆXdÓD’ÀB ÆL’ÃÀ’ÀA Æ-´EÒ`AÃO@B Ç¡fS‰,BÃŒ’ÀB ÆÓòD Æ/4Ñ RCÄĕɴDÅX…P°B ÉI¶ $ÃÀ’ÀB ÆÁ‹Oc{DÃ,ÏH ÆX”8>S@D ÆH±L’ÀB Æ4dÏ’ÀCÃO@B Æ4¼òC ÆOc(%CÅOcP0BÅ8”Ñ0BÃ5MÎB ÆÁ‹Oc€CÃà• AÄ,e8BÃÈÅBÅUHwÐB ÆMM@Ì@B ÆD“L€ì@AÃSoCÃBñŒBüœÀCÄõ>CÄ4›:CÄ7¢Ô`BÄbéLBÅPÒRlÀAÅCdì<ÀCÅB4“ØàBÅ¡M‡ DÅ, ”ÀCű‚ CÃbq‹B Æ_ä€B Æ¥0BÄÔSã CÃuBÅTô•0BÅB•F-0BÅ´í0BÅ ñG0BÃ4ó#BÃ2q—B ÆU<ÛÀCê1“CÃ<#ÈB È4mË<б0EÄ/¤ BÅD <ÀBÃ<#ÊBÃiJWBÃFjB Æ5B .ôÀC ÆM=\ÀC Æ\ILdÀD Æ™?ILdÀD Ç4’OÓ,CÃ.“ÌBÄJQïLB ÆCdÉÕAzD È@ó LôÅÀDÄC±AXBÄ,ò0BÅ`€BÅ7í<@DÅ,ó<€BÅ“ØÀB B `Ri'/ Æ´L<#ÌCà @H ÇH1““ï0CÅ cF7°CÃîB ÆOƒÄD@C ÆAOLeÀC Æ8’ë eÀA Æ5´S eÀB Æ0aOXñ@C ÆDD@C Æ™3ÄD@CÃVâHB Æ/4Ñ<=DÄWÍÀCÄQD¼CÄJTÔLBÄ ¡T,BÄ´% ÄCÅ7GQCÅ´ SÙ C ÆD0ñ@BÃR@A ÇH`û<’°Dà *EHÃ`BÄØƒzÄC È@óBô‰Ï°FÃàUBÄôç¼CÅHü$°CÅ4ôøPCà INBÂPH ÆHÅ@B Æ/=Ñ\• B Ç ²&S‰,B dz¸<[É,C ÆUË4ÎC ÆDI=€RDÄ¡!’ìCÄ7¡:ÄCÄ dé\BÅYð$°AÅ@óp$°CÅ@ñB$0A Æ0b‹â4“C Æ@aAñCÃ-,3B ÆD DA Ç-õ$ƒ CÄC¢ÆLBÅ61ppCÅ.1ppAÅ,‹0B ÆÝE˜AÃ@3BÃ7Û@BÄOÓO BÄC*8BÄ4öHBÄ/cIBÅVþ‰=0DŤ… •0CÅB‘M0BÅ#¢&0C ÉÁ‹OcsMß@EÅM½0CÅò‹=0B H ÆÁ‹OaðD ƽ=<ÃÄD ÆaBÔ8UC ÇI±qoÄBÃILDBà ¬ÀBħSìCÄ@ò A È´‹Q ½0D È™3ÓFôõ0DÅMBPàBÅAHF°A ÆTôÏJTÀC ÆPâCìÐDD ÆA@»LdÀC Æ4’ö D€CÄT“ÌBÖ2BÄ0a ÌC È/4ÑMòÐEÄ,øÄÀCÄð‰ AÄ"\BÅI¤àCÅ5< B ÆdË1@€B ÆMW dÀB ÊLcTôÏLGÃZWB ÆÓ× dÀCà FsB ÆéE’ÀC ÇTôÏLEÃjˆBÃVâmCÄQ`GôCÄI3ÆBÄBùLÌCÄ,óBÄ õDBÅBs.ðCÃ0“sB Æ+³Ä0•@C ÇK¹ÛÎÏEÄVôÏ4BÄMOBÃCƒ1BÄ7¢É Bà =BÄ BÆLBÄyHCÄ"ÆLBÄèÐD¼C É/3ÄD@EуBÃÅ[ÓBÄCa)HBÄ@aoLBÄ6ñzÄCÅJªlPC ÆB”“E@ïCÅAŽP°BÅEpBÅBP°B ÆX‘v0ñC ÆUDdr`A ÆÏ0ñDÃ=!ŒBÃ/„ýB ÆW£A\`ÓCÅJ3p$°A B0$/#YÃCdóBà 0³B ÇHbé•ALE ÇCc•ALE ÆßS%'}DÄ[ÅB ÆŒ$õnDÅEpB ÆA"V<ÃÄC Æ4’öVã@C Æb;Mß@CÃQ@B Ç.ÑŠô‹àD ÇM5C ÈI—&ÒH½0EÄE³FBÃ7ÕqBÅ@ÅpBÅ/ ³0CÅ´õ0BÅ”‹½0BŲC0C ÆLeŽ<ÃÄCÃ@”;Bá3B BÀE7'1Ñ MBà ¶ÑBÅI´P@BÅ-DI<€C ÆHlÍ=ŒD ÆeÉcC Æ4CÃ`LB Æ,óP0bÓBÃèLÀBÄMSÌBÄ=RWìC Æ,óP0bÒBÄÄRjCÄ´,OHCÅ]´CPÀB ÆXF0lÀDärMB Æ8–A´@C Æ/4Ñ$ÀB ÆPŒÀD Æ ´Hà”€CÃHÑ€HÃKºˆB ÇDär`B ÆT‘$°SC ÈX”[1Q$°D ÈACmð$°BÃàSC Æ0dŽ%ŠCÄ/³ÒÄCÄBÁLBÅ CSpB É@óT‘$°SE Æ4ãÇ%1ŒA Æ d“œò€CÃ-³@HÃ=+€B Æ/5ðMSCà Ë@Bà ²HÄN“ôBÄHÛDBÄAT,BÅH1“pBÅ@õƒ0B Æ@$°YAÅ6ðROÀCÅ›F-0CÃbúAÅ‚MQ0AÃbýBÃÄ|;CÄ(ÔLAÅ,óP=0BűÅpBÃ/íB ÆCbÔKB Ç0bçÆ=2PDÃ/£qB ÆŒ$óoDÄ[µÏBÄ<ÓLBÄ4ó\BÃ/¢{CÄ.ÕÔ8BÄ"kI€AÅO³OWÐCÅ”£¸% CÅA¸% CÅ5D†3CÃ[³ñC ÆD="øD ÆÐï="øD Æ›F-2KDÄTdÉdBÄLûFLCÄdÆBÄ MÄBÄQLBÅ4aW0CÅ-³‹wÐB Æ C¡@C Ǥ¸ÍQÉ€BÃBþÀBÃ.”ðB Æ\’Ì=$îCÄWÓALBÄQ¦ÑBÄKÆ BÄ4´BÃ.”óBÃ/ SB â„–2'?$" Æ`†0ó{D ÆÝrO0ñDÄ@™DôCÄ=2ÏHBÄ,cdBÄèóALCÄS|´CÅPâKPÐAÅHÞPBÅDØÐBÅ%$ý$°C Æb I<CÅèžÄèPD Æ@ó \€C Ç4ó L< ,BÄXÛDBÄD5BÄ-CF\BÄ,óLBÄ.4hLBÄ,”BÄ,MðBÄ Ô4BÅD%0AŽòS0D ÆTd“$;@CÃ=4=B ÆD’l1“C ÆCbÁKB ÆÁ‹MKCÄc´ÆBÄTÅ B ÆCdÉÔ1’DÄÄ;ICÅAC0BÅeF-0BÅJD0CÃZÒUBí7}BÄÅ^‹LBƒâ€¦Å5D¥8@B ÆKI,ÀC Æ.ñIÀC ÆÅ1Œ´ÀCÅVëÓÙC ÇI;CÅKº“wÐCÅ0dø% CÃ6ñ-BÃ= ðHÄH4[XHÄD”Ô´CÃ@–§B Æ4’Ï0ñCÃ6ñ/B ÉA´Ædd“KC ÆAF ’ÀC Æ5Ò8’ÀB Æ/¤ÂŒæ@BüB ÆÔÁŠóAÃ<Å B Æ4”Ï0ñCÃ/¡oBÄ HBà DóBÄcLB ÆX‘vUC ÉM´lFÌ8’ÀC ÆLcUCäùNC ÉAlFÌ8’ÀC Éq!˜8’ÀCżCVàC ÆVÅ8’ÀA ÆMÀ’ÀA ÆIµÀ’ÀD Æ@ó L’ÀC Æ4#ÀD Æ,ów4óCÃXc@H ÈM[³$°BÄH»Å´BÄ@òôBÄ4LBÄÒRLBÅHƒ½0B É@dÏlFÌ8’ÀCÅš“0DÅ,”¥pAÅ/’/€CÅ,cCÀC Æ4a-<ÛÀD Ɖ`³ÀAÄ4EôCÄ/ÔÆBÄhÓÄCÄ1Ô¼CÅJS…é0BÅB3™0BÅ@“0BÅÃÒ/€Cųҕ0D ÆBñIe ÀCÀ‰üC ÆJ›DâKA ÆHcl1“C Æ@FLâKA ÈI3Í3Ò/€DÄC`ã,A È4%3Ò/€DÅØ¼ØÀC Æ,óBªCÅ,KšÐCÅ.ÓÂFðCÅéb{ DÅÄ C Æ’Ó=\ÀC ÆcÀC ÇI²Ãé?/LD Æ-ßU%‘‹A Çd†Lð(DÄHÅBĤô¥LC ÈDI="DÀEÄC¥Æ0BÄ/¤Æ0BÄ$ÔHBÄ”ÄCÅ,< CÅ,“ØàB Æ$„0³ÍC É ñG>6´ÀEÅbØ B ÆLc@ÀC Æ,ôÎdÀC Æ´ÌÀC Æ  9<@C Ç 4AI< ,DÄOeF(BÄI=†B ÆTc7¦mA ÆI´†2±BÅIDðwÐCÅH¿P'0CÅ@°CÅ‘Ì0D Æ4ºQÁDÅ, g0C ÉÁ‹OaOÀDÅ`‰OÐAðÁH ÆJTÏH¾C Æ@ó L’ïDÃ6ò{CÃÞBÄèLæLCÅXa70CÅVùHwÐCÅ1 wÐBÅ£‰#0C ÆJ1O0a@CÃ6ðUBÃܳÌBÃ=$ðB Æô±’MÓC ÆÔYÛE1‡DÄCdÉ HÄ,ÄCÄ´Æ@BÄ+ÏHC ÅÑ’LðHÅD$0AÅ@ñVÀD ÆHÑ™8’ÀB Ç@óñDÅ4û&ÐDÅ-X<ÀBÄCd“ôBÅ8’ÏOC ÆYøÛQ@D ÆOƒ8ÛQ@DêSqC Æ E6ËAÃ[ÓsBÄOcBÌBÄôT,B Æc³Á…CÅO³IÐCÅLa %€BÅKÃÍ`CÃØÛÒBÅZd3DÂ4H B007$R#ñ"EBÃ/1}B ÇUHóD ÇБ$óD È5C$ۉϰFÄ¥8BÄJM¼CÅÞ4IPÐBÅAJ<ÐBÅ7£mPC´H Æ7{1²ÀC ÆC7°SDÃTôóB ÈHÆÎ`ñ PCÄDLBÃ@”óBÃ/>BÃèd“BÅX‘$PBÅC V.=0D Æ,ó,©C@B ƳÅEC@DÃ-C|Bÿ4€B ÈX“K<б0DÄTô„ÀBÄLeSìB ÈID;Tô•0DÄÜÉ,BÄD ìBÄ@dö0BÄ7£ÅìCÅ@KPÀBÅ@ÐC ÆTbŒ<ÀC ÆH“TŒäÀCžÐB Æ5DATdÀC ÆûJôÀC ƨ-‚<ÀD Ç4hÎXó ,D Ç/1 <ÞÁLDÄ@fLBÄ4”DBÄ/4ÔDBÅI~7BÅDI.ÐCÅ@‘  BÅ@“ÀBÅ,$€B_4XJ$/%"%F$W$/ Ç,óIK¢ALEÄJåLCÄ4¥@BÄ/¤ÏTBñƒBÅ¥S- B Æ S…C ÆW3ÄD@C Æ-ÒLeÀBÄ0ð”LBÄöF,BÅH•n% AÅ0•Æ7°CÅÆÕwÐB ÆA´u•ÀC ÆCbHXñ@C Æ,”Œôñ@C_5X0$/F$W$/ Æ@ó ÃÓC Ç@ñRºeDAÄTLB ÈD¤`CÄCdÆÄCÄ4BÄ/ T0CÄÔ£‰,B Å Ñ’LðHÅ`•L$°BÅW1“$°CÅMD$°BÅ@ñIPÐA ÆBþ$µ BÅ5¶0$°CÅ0ñ8PCÃŒBÄ<.ÓÌA ÅñFLðHÅ1ñOPCÃ-EzAÅa $°B Ƙ“Í=N”ÀDà°@A Æ,0EFâsDÄD0BÄ0•ð BÄ/5T BÄ,ð”DBÃ/=JBÅÅ1„FÐCÃñnBÂ5@HÃBíB Æ8ùQ%D€B Æ´Ï0dÀC_8X'W$?F$W$/ó3BÄ$¼Ï4CÅOƒ7°CÅD= BÅCË»DÅLw0C ÆC DD@C Æ4‹è@C Æ 6ÎLaÀB ÆcÄD@CÄ$„HÄ7Ï0BÄÄBÄÌÅÄBÃÓB ÉTôìé3ÄD@EÅC¤ÎwÐBÅ dö7°CÅ+ÒwÐCŬ0MëDÂ$ÐHÑ*EH ÆaAÅÀeÀC ÆJ'´aÀD Æ<$A eÀC_9XF$R$/F$W$/ Æ/4Ñ_RCÃ/¤óBÅ~ð$°B ÆTÏ%r`A Æ@‘…)LD Æ´r`A Æ” <ÐSCÄCÔÉìCÄLCÅHÉýPCÅ@ÃÚPB Æ,‹W}CÅ‘}PCÃO¿@BÄ\‘/ÄAÄUDDÌBÄO³q´CÃJRïBÄ¡Dö8CÄ5ELÌBÄ-DB¼BÄôBÅ[ÒHÍ0CÅMT5PBÅ¥$ý½0CÅd•0CÅ ±‹0CÃ.:™B Æ™3Í<+€Dä‹€BÕ“BÃ@œûCÄ,›DBà ÐïBÅKçpAÅHbå90BÅ@ñLpB Æ4’/OdCÅ/4”10BÅd=0BÅ”Q0BÅ$<½0CÃDzA Æ@óW@D ÆBâDD“@CòSA Æ4(LõsDà âsCà ÒóBшBÄ ´VPHĦ„¯HCĤŒïHCÃC EBÄ.4‰,Bô% BÅ”ÂR6ðCÅC BÀCÅ,ó'<€CÃÁŠBÃbóBäŒÀBÄXðLB ÈI3Í3Ì<@D È =3Ì<@EÅTa{ ÐAÅFñF6ðCÅ,ò<<@AÅ’(àB Æ #Ò,ÌÀC Æ,âDà”€CÄ\‘/ôCÄÃÒAdDÃHkÒBÅ@ñR30B ÆA ÆËCÃ4sB Æ‚Kœa@Dà ÒïB ÇXÏg<_OEÄScCÄMDË´BÄH¿F\B ÉCbHÔT“KCŤrRwÐCÅ@óO0C Æ4”‹ÄÆËCÅ,ñϰCÅä9 CÂ0H Æ1CXñ@C Æq…±@D Æ döXñ@Cà ÔóB Ç ´û$óEhttp$9J/% /% 0% Q:// Ä=3 AÃ.ÀqCÃÀUBÅD <ÐBÅ,Y$°BÅHÆ=[D ÇB‘R–¤Æ0BÄ´A(HÄUDNðB È4’ö“Ì<@EÄ-Dd BÄ$„ LAÄ ¢SÌC Æ4’/I|C Æ-O” Å CųÌ<@Cà ÛÒB Æ_ÔDœÀDÃÞC“BÃá2KB Æ6òU$ÀC Ç‘[I3‰,AÄIDÉÀCÄ´¥ BÄè+FLCÅ\d3C ÆT‘$»ÓC ÆÜPE˜AÅ,óP B Æ“dI2KCÅB×'0Dà1‡BÃ/°ïB Æ9ò½-‹ñBÄŒÔÆBÄ/Ó‰ BÄcÄBÃDJBÅB•I- BÅ4ð‰W0A Æ,ÂM2KCÅ“'0CÂ4H Æ•{ÁrmE ÇM‚$óEÄX”é\B ÈI3ͼð†O0EÃC UBÄÀ–:ÄBÄ DK¼B ÆHTD€CÃB˜ÓB Æ“0B Çc ,ÆHDĤŒÝôCÄ/ ‰BÓÅB ÆILâKBÅ4eð0C Æ4iU$‚KD Æ,óHâKC Æ$Õ%1“D ÇI@ûÀ”ÆLEÃ/Á˜B Ç©"Ï ”ÆLD ÉA´u$„Ï`âKCÄ@ñF4BÄC±0BÄŒ/oLCÄ-O” BÄÕ)\BÄô¥8BĽ2DÀCÅW¢R C ÉPÄÑÒKÙ"øEÃJñmBÄ<%LCÅDÀBÅCbHÔÀCÅ/¥I<ÀCÅóðC ÆA"VàÀC Æ0bÓôÀC Æ/5L$´ÀB Æ,óP½ÜÀCÂKBà úKB ÇI³IdÌ ,B Æ-BÔEBCÄ 'ôA ÉDI=1Œ\ÀF Æ@óA"òKBÅBòé C&_«7&#R#FR'%2#/"% O#72#W1'E# Ç4Q,C É`dü%±0âKDÄBÆHBÄ7>0CÄÆ\B ȨQLcW0FļÏ4C_¦0"$1 W2#/#J$"/# É0”û56 a@FÅ‘ wÐBÃ.B ÆI;<#pDÃNıBÃ4ýBÄ0‘ÄBÄ/9KLBÅK$°C ÆBÑ™8’ÀA Æ”½.ÀC ÆA2W6ÅC ÆC¨ÍÁ7}DÅ53B Æ©qß-E Ç’ÃTALCÄMC4BÄC`‰ AÄ"ýLBÄ”#8BÃ!mB ÉA"V>ûIL’ÀF Æ4mÅ<"CCÅ,ýÐPCÅ,P°B ÉóOQf%1ŒDÅ1N$°BÅÔ^6ÔPDBI0W/'/%21% Æ`”“8’ÀB ƬF4’ÀD Ç¡ ‹á+É,C Æ<ÂD=ZND È´‹Q'Õ¤€CñoB ÆébP1D Ç@ó$ROLE Ƶ• BÄc0BÄO³ ,BÄHaFTB ÆDFLcC Æ@ôŒRCÄ6ñALBÄ-@ûLBÄ.ôóìCÄ´MÌBıTBÄšñ:CÅVãÌ<@CÅB‘L<@BÅ`†ŒàCÅ´³Ö<ÀCô›ÒC Æ´“F´ÀB ÆÙ3II6ÑAïÑ@BÄ5B(BÄ/ 0BÄ,FLBĬ;oCÃHoBÅB4“»CÅŒ$AÐCÅ-D‹Q BÅâG½ C ÆA´CÀeÀCÃBÃ3B ÇH¸ÅQÉ€AÄ[¡TìA É4ò(°E˜BÄ,“ôBÅMÒW°BÅLó;½ CÅIEI- B ÆHd“GKA Æ,óF›ÓDÅ,ó BÅБ'0CÂ8ðHÃB9NBÅ@c°BÅ"n°$°BŽ2PïHCÄB•£HBÃ.ÑBÄ¢oLCÄ»ÌCÅCd°$°CÍ=1˜$ÃÀõv99Æ\FÅ4”“$°BÅ7MPÐAÅ4iL$°CŨ>‰PÐBŬ>‰PÐB ÆLeŽ$µ A Ç@Á‹H‘#HCÄ¥re0CÃT”îBÅIC0BÅC¢S0C Æd¥Bq—BÅ BpBÅ™;0C ÆIqMß@BÃB±“BÄ4aÅPH ÈX‘vIC0DÄJÆ\BÄHT8BÃD•ñBÄ ŒÌBÅI°‘0B ÆI@“ÙKC ÆAYÁ—CB@À07'Y/#/ÃOZWB Æ$ÑKÀCÄ-DIìCĤÉìC ÈÁ‹OaPDĬ>†0CÅ<"X CÅ/ÒU C Æ\•{ 4ÀA ÆVµ LdÀC Æ@U0dÀB Æ/4ÑÔÀCÃ’3BÃ=XB ÈB‘P‚SÀBÄ7>#8Cľ#8DÅCÕÆŒàCÅ:ÁAPàAÅ “< B Æ"¼øØbÓEÅ¡{< CÅÔSÅÀCÅ C ÆÅ4IôÀCÃ/SB ÇI°é7‰,BÄJ=ÄCÄ<%BÄŒŽ†LCÄ ©Æ\AÃ9ûÒBÅ4b,éCÅ.àÁO°AÅMwÐB ÆÔ£‰,ÆËCÅc' C ÆHÖÑaÀB Æ5HœeÀA ÆŒáDD@B Æ.ÒDD@C Æ ± ìñ@C ÇS%& €AÄ4aF\BÄ=i CÃTÎBÅ$Ô1 BÅ$— BÂHH ÆH´I@eÀB Æ@”Ï4eÀAÃC©¯C ƶ eÀA Æ G´eÀCÕ5 B ÆÅ>ä\œíFÄXóOLBÄX“I,BÄT”0BÄÝã8CÃ¥5BÄ=2 AÅ@ml°C ÆTò»²ÀA ÇCÃÓc‰,D ÈA´u5¶0$°EÄCÔì´CÃ2Å BÄ,‰ìCÅTÅ=$PCÅ4eŒÐBÅ-DYPÐBÅ/ MVàCÃ/ÑsBÃ%¡—BÃOËÀB ÆICÒEC ÇDI³5ûLE Ç@Ñ'¥LDÃ/Û@BÄ@bÓÄBÄÔ^CÅAC‹OÀBÅ8Æ3ÀCÅ4I=0CÅS0CÃ,ö/B Æ.ãÄD@C ÆÁ3Í<ÃÄDÃW@B Ç6òU)NLD ÈPâCí"S0E ÈI—&ÒS0EÃ.âMBÅX£)PB Æ4‹èÆËCÅÂKKÀCÅR/€C Æ$$Id“@CÃ.ÖÐBÄLcF0BÄ@ñ64BÄC«F0CÄ@DBÃ7}B ÆD’ÏddÀC ÆD=\ÀD Æ,PPÄÀCÄ`d ,BÄ”´É,BÄ/5ûLBÃ.ÖÕBÄbÁHBÄ™;# CÅ-R”ÀB ÆHO0dÀC Æ<Ó‰ D€A Æ4’ö€‰üEëÓBÃb¶ÌB ÇK´ÉT’ÁLD ÇHbÔ8SÍìD ÇCcIdÌ ,B Æ,ó C Ç,ó-rsìE Ç´—Á4I,CÄCîìAÃR=BÃ,óqB ÆMÒC«ÓCÃ,dºA Æ<ÓÄD@C Æ4iL<‘@D Æ“ÄD@C Ç,âD<ðÀDüñ@BÄ@’ÆLBÄÅ>ÆHCÄ ÐRLB ÆUC‹\œûDÅO´0OCÅ@ñN= BÅC¢ÆOCÅC E± C É0bÒ$³ÄD@DÅ ³ëAÂLHÂPpHÂ@ðH Æ$û<‘@D ÆÑ‹ãmEEÄQŒ ,CÄ•WìCÄ¥^ÁLCÄB2ÁLBÃC¥íBÄ/5û8BÅU³…l°BÅMõL°BÅM´Ml°BÅAKŒPBÅB~ð$°B Æ,ÁLóoCÅ´Q–$PCÃWÀBÄBk‰ÌDÄ5±i\BÃ/ÑB È ± Q}r`A Æ@ör`A Æ5Eer`A Æ!°óC Æ´ÃÀ’ÀA _"1#R%J1%ÄWc“ÌBÃ3ÂKBÄ`ÄðBÄÞɼDÃSBà òûB Æ$ö0ñC_!(F%R%/$7$2ÅIôSP°B ÉB‘Y$ÃÀ’ÀB ÆBôÏUCÅ1Iè°A ÆVÄ“ìžÀDä¿EB Æ,•cr`A_'#0'W/"'Q ÇJ0à8õOD ÇHc-rsìEÃ2Ë@B Ç´uð‰ Cà ûÀB_&#?0$"W#2/Ã8–oBÄ  ”8BÅIC%‘0CÅJâK0CÅCdÆI0BÅC YQ0CÃŒ…B Æ-Ä<@CÃ.k@BÄ`“YðB È/4ÑPD=0DÄ‘ŒÌCÄë`B_)r#W2#W1'E#ÅYB¥pB_(7&#R#W1'E# ÆWÔ@C Æ´“ìŸ@D Æ$ö8ó@C _./'J1#Ä\’ÌàBÄXôÆ0BÃKÎBÄFµHBÄ4e”DB _-/%"$Å ½Œ<@Cņ(àB_,V#0$/#9# Æ0bÒ$¼ÀC Æ4I DÀC ƼCTð€C _3/"%Ã"¼ÀBÃÜÀB ÇÅXôÆ0C _2FR$Ä@d“¸B Æ-R;‚RCÄ.òB´CÄ AXBÄÐJ0BÄñÔDB _1$F2'ÅQcÂ<ÀCÅ@”‹PàBÅ“PàB _02(w#Ã@c1B Æ,Q ”€A _7W$F$? ÆIcãI2KCÃ7«0C _6Y$W/ÄL“P¼BÄHF\BÄB4ÆBÄÅ>ôCĬ;æLC _50$/ ÆL`SØ1…DÅDŸÐAÅ@ó 0CųQ€B _4J$/%"%_;/'J1#%V#0$/#9# Ç=YL4óD_:FR($/'J%$ Èc ð†O0E _9F$R$/ÅB•{½ CÅCW»DÅBòKwÐCÅ,óP¥ BÅ17°C _8'W$?ÃB_?R 0"'W%/$7$2 Ç4Á‹<‰D ÇIò,D_>0'O'7&#?'ĤäÉìCÃCÀSBİ ÌDÄ,óALBÄ,ñFÄC Æ$Q0ñDÄóALBÃNÅBÅAH°AÅ/bÏàCÅBpBÅ´»O$PD_<0'?#71'ÃO¼B Æ c0aBÀC Ç,óPÀRT4BÀA ÈÁ‹Od6ÔPE Æ_ÏUC ÆI|UC ÆI<UC Æ@d“%rECÃÔ»@BÄ”¥T8BÃH•sBÄ4’öBÄ1Cq´CÄ0dÆBÄ.4ôBÄ3LBįÑ]ôCÅ¥$-0BÅ.£“0BÅ$-0B ÇMPƒÉDÔ+ÀBÃKÀBÃ0a0B Æ,†LõsDÄC DÌCÅH¿BQ0B BPÀ(7%s# Ƴo=[€D _‡ Ã@@B _† ÄPâw8CÄ@ñBôBÄ4ôÆ0BÄ,ôÆ0BÄ,IÌCÃ.k{C ÆSD®DÄd¯LBÅJS‰<ÀC_…?2'O'/'J%$ ÆQf%1ŒB ÆB‘I,ÀC ÆclDÀC ÆfA4cCÃêñýC ƽ2S±,@D Ç¡"ø=#‰,B Ç$„˜”Æ0BÃéœ@BÄLôÆ4BÄ@dÆ0BÃ/a‡BÄ,ÌÄCÃ"ûBÅX“I.ÐCÅ@ñM<ÀBÅ7²E&ðD É ± bEDÀD ÆDDÀB Ê@ñP¤T†Æ0A ÆÅ[“DÀCÃ`bHBÄA³(BÄ4’ö8BÄ4dÆBÄcO0BÄ艀BÅ“ax% DÅ4’öW0CżìKDÃJ‘@H_[7&#R#1R#F"#/2#W1'E# ÆH•n%2KDírHBÃW sC È Ñ“4’OÐB_–1 W'/%"$ Æ4ŒãmEDÅ@ŒwÐBůd“%`CÅ™3ÂQ C ÊA"V=RH$óF__F'72#J$"/# ǤäÄÀóDÂQ/CÃ"ÒCA_]r#W2#1R#F"#/2#W1'E#ÅùN$°C ÆN’À’ÀA ÆMôK<CÖ6@BàVÄB Æ””1PSC_—F 7O'/%"$ Æ[c0ñCÄ@dÄBÄ<$I AÄ<$ALBÄ ºÄC Æ ´HÌñCÅAH$0AÅB”“$pBÅcl°BÅ$”DPB _`O"#Q ÆMDͼ’ÀA Æ‚R8’ÀA ÇH¿OI3‰,A ÇABlÁ:ÄB Ç.”I3‰,AÃ/ÛÀBÃX»BÄ@óPÌBÑeBÅUDK0BÅC²R/€CÅ™3ÒO€CÃa@íBÃ@f-BÃ7¦mBÃHÙB ÇI‹Od‹àC Æ@d0âKC ÇÁ‹Od‹àD Æ0BôâKBÄ0’ÝôBÄ,ÆLBÄ ÄôBÅI:LpBÅHÁpBÅDÕBÅñ•CżbÅ=0CÂ``H ÆDI=o@D Æ/4ö1ß@C Ç¡DÑ´”ÆLEÄTd“ÌBÄ/1)HBÄ,“IÌCÃJB É@ñTA‰LcAÅ6A” C Æ™3ÍÍ7}DÃñmB Æ$ö4ÀCÃC¼ÀB Æ4ôÏMsD Æ,óBÄb3DÄY³°Aį`LCÅD< BÅ ñ{<ÀC Æd“¸ÀC Æ ý‹DÀC ÆébS´ÀCÃV¿B ÇHÆÎ`ð‘¼CÄB4Æ\BÅM´BQ`BÅ.0ÆKCÔ¶ÍB _{7&#R#R 72''E"#V2#W1'E# Æ$„Ï`âKAÄN™ôCÃC4óBÄàbÔ8C Æ7¢ÆOAÅ/ BǰDÅóOW0CÃé,BÃ.ðPBø’ÀB_~R 72%J1# ÈÁ‹OlGðF Æéa0ñD _}r#W2#R 72''E"#V2#W1'E#ÅXó;$°C_|R$"/%1#72#J$"/#ÃTÅ=BÃK}B ÆC«IL’ÀD Æ6½† ’ÀD Æ ¦%1ŒB ÉÁ‹O`D¤@SFÃP^€A ÇMT6¤ALDÄBÄA(HÄBtALBÃ=q“BÄ4“oHBÄ4T0BÄ,oHB _0and % Æ@d“8’ÀB Æ‘ X8’ÀA ÆÆÇ8’ÀB ÇH“P<‚T4B ÆCbøJòKB Æ@ôŒ#'C Ç"“I3‰,AÄQ$XBÄ”åÝôB ÈD“À‘ƒlPEÄ0dÆ\BÄ/Ô†LBÄ,[dBÄ”ôBÄ èLBÄ ¬ÆLC ÈHÑ“,G&AÅKº“Q0C ÉDLõ0’ÀE É@ñP<Âç8’ÀAÅŽ1G&A Æ II³A ÆA±PlVËC ÆA†âKAÄ=T†LBÃ3ÚBÄ/¡q´CÄÂD¼B ÈBÑQG&BÅ5D‹0B ÆXc ="øD ÇXbÓÀB Ç’0ÓÓôD ÆdóœòDÄI@ððCÃCÒCAÄBÄI AÄBô‰ÌCÃ0e{B ÅI`4ðHÅöRÌl°CÅ-³“pBÅ-S$°BÅU¸ÐCÃîBþðRC Æ@ó-ÄCÃ@amB ƱÅ<ÞÀC ÆÑ‹<ÞÀDà e|BäUBÄCÕÉÌCÄ4dÉHBÄ,F BÄ,Q¸B Æ,AI=ŽC È$‚ÔI=CPD È$ÆI=CPDÃÕsBÅcÊÌl°CÅI:MpB Æ4ñF0žÀDÃ)B ÆI²ÀCÃCÃÄBÃ.û@BÄ`dÆ\BÄTcÅ´CÄVÕÆLBÄCÅLCÄ4TLB È@ñ64G&B É4PáG¹²ÀD ɨQ”0b€EÅ %PCÅ™3Í0C Æc<%C@BÃCÌXBÃb’HÄKÉ4C È4ôÏ\’Ì0DÄ74ÝôBÅLc{Q0CÅJ1K%BÅCaT-0BÅ-D 0BÅ ñPBÅq“»DÅZR½0CÂh`H ÆXc ==DÃ.w}BÃJ–”H Æ-ÒO†ÓCðóH ÈHbH4ñPDÄd»LB ÆGü@AÃ3ÌBÄ$€Û8HÃÝoBÄÜÁALBÄJñ[,BÄJ½ÕÌCĤº†4CÄC¶4BÅB”“< BÅ@ÑPÀBÅ̳Ì<@Cõ6ÎB ÆLdÓÈC Æ@ó4€CÃ@ò=BÃ7íC Æ$¼ÏJT€DÃìLB ÆAH¼@CÄ7LCÄ0•Æ(B È0bÒ$³Ì<@DÄBÌBÅ,{'°DÅ ó'°D ÆšùE˜B ÆÔSÏOQ@DÄVã÷TCÔÔ3BÄ/Ä `BÄ/Á B È%mLð†O0EÃE²æBŦµÉϰEÅD `BÅ-+W0CÃ,BÃKPBÃ.îÀBÃW³oBÄ$ROLCÅI´BpBÅC`ŒÐBÅ,”ð$°AÅ ²ÉôDÃA“BÄ Ô”,BÅ4a&0CÅ-´0BÃé,-C ÇPÄÑ€Ô,C Æ@”“<Á“CÄ”"FLC ÈDI<:0FÄ5C…ðBÄ-¾FB ÆMUCÅÅ<½0CÅ Í  A ÆDN“BÃÓÙB Ƙ“Í=?@EÃCÕ|BòPBÄIFHÃV2óBÄJALD Æ ³èõnD Æ@ô“R4ÀCÂâÐB Æ,>“òôÀC Æd)JôÀCÃ[@BÃCÌÀB Ç‘‘’L< ,BÄ$„I AÄÜ ,AÄ C ¼BÄÔSÆ4CÃbÖÍB ÆT‘FôÀCÃH²}B ÆD dÀB Æ,óILdÀC ÆbÒM@B Æ“Í%|@D ÇVÖIT’ÁLD ÆK°† ÆËC Ç4Æ4É,DÄT–F,BÄM´èBÃØ#ÓBÅ/5ã°A Æ/1ˆ˜ñ@D Æ,”†0eÀA Æó4eÀCÄ6öFLBÄ,ÏBÄÅ% LB ÈÁ‹OcOOÐEÃW9NBÅ0a ϰDÅ,ô±Q AÃBàUB Æ/ MóC Æ™3Șñ@DÃCÙLB ƽ2UD’CÄ1‹HBÅ$C0$°CÅ <'Ws"$? _%2$W(7 O _€$("'__#7 71"n0W _]7u0$/#R1#2F%7%2$W(7 O BPà/w2kR _O"jR%WC@ÔÀ0$#?%W$7/ _ /w0%F_{#7tW/#R7qO$7%2$W(7 O_}7u0$/#R7qO$7%2$W(7 O _#32/{i%1C4À?%=9'2%/ÃC@**Ä<ÁMH ä?wW WC ÀEnEnW%n** äwW WÃ4REHC,‚À1%im71'2FÄ<ÁTH CL•W%/ Æ<ÁKL“€HÃE€**BijCbdfghjlmnrsvDlmnrEõäöüabcdefghijklmnopqrstuvFõäöüaeilmnoruäe wlowqu wsäC wxä äxi } wi}õauje uli unouqu usõC uvõ õvuuu(öayjeylöC yzö özyi~üüC {|ü ü|{mbri{?E"%iüjaüa9aaC #ja e #li #no#qu #saj#mbi#?E%iA9#ua:#uuuµÃCAkCACb0Ece/Wi1hJeWityW%/%d/FBB Bƒea $jeC $le i $no$qel$iA9$ua:$uuuµÃCAmCACfQg1OhialtiiiiiC %ni in%CAoCACjazz/XwW 9j9 umbu9(?E(k1auge1#sO$AD1 AAFDAFkamba1#?E#imbatus1%?E#/(Wimbu1%?E(l7BBli7 li B= dB gB kB ni s i si tiss l i= lA p= m? bA  b??n2A lBBBni 2 ni22ni BA dB si t  tist n iA  gB kgknA pA oa'je 'li 'noC 'qo oq'iiiA9'CArCACp0AAF0 DA pq1q1 u1Rr"ekge33µÃkgersW lB nBBBümboliseerW{?E'7%Wl"ombuW'?E(siWWsisW€chYhsA p  B diAtis it/BsiBAD/ AAFam a ttitiambu/#?E(umba/(?E#A sip‚tA p‚  B‚ lB nBt i‚ ui (nuC (su us(iiiA9(CAtCACvRabariiR#E#"%%embuR$?E(wRxx1 W1Wy%i9%y|zz/WVhX- A  - C -  ?n2(WžXÅ¡Ysources_5316/external/espeak/espeak-data/phontab0000644000176700017670000010125411663004330020551 0ustar paulpaulMkbase_%%%,,,'''=_: %_ _!@ : #@ F@-Z|| *@„€1#X1(<?H - _^_ _X1 _| _:: Kt#'!_;_ d#@ #a #e #i #o #u! r€H"a#Ze$Ui%U;”&o' Uu!(!!Um-#)Un--*UN-7+_r->,nl-C-dr/€f.té/FpÏ0Ek-1OnÖ2R€x3R2€Š4R3€˜5r" ¶6lÐ7l/ø8jw9wT:l/2;l/3'<l^8=2l.P>m®?n.û@2n^!ANIB**„pCr.®Db¸E0dF/d[GHt[þHGdZ03IJtS( JIdZ;0HKLtS;(LKJ0lMNc NMgO1B¢PQf^QRvÀRQv#åSQDôTUTgUTz0VWs(tWVZ0XYS(†YXz.0=Z[s.(“[Zz;0]\]s;(¢]\Z;0q^_S;(±_^J^…`aCÔaQ“bcxácbQ^±dQ" Ãeq Nfl#ÀgX îheh ói consonantsts( jkdz0kjp-+lEph>mEt-NnFc2([ok-hpOkhuqOs2(…rbase2aŽ#Ze—$Ui›%Kož' Uu¢(!!PtÓ/FpÀ0Ekû1OdàF/a/•jZE™kUO l UU¤m!!Py¦nPY¨oPaUªp!‡eU¬q!‚iU®r!xaI°s}eI²t}EI´usoI¶v xuI¸w!xw2ºxts( y5en@u Ft#a#Pi«%Fr-€Y,l77t2éjd#-kz#(2lg-Dmz/20mnI2¥oA3{pF@2€q<@5„rFU¶s K@L‰t7Pa#–uKaašv\EŸwFI¢xAI#¨yA0°z FV³{FA:¸|sA@»}s3:Á~ii:ÅWO:Ë€ sOÎ dO@Ñ‚ xo@׃ }u:Ý„!!iaUâ…!soUä†!naIé‡xeIíˆiOIï‰ se@ñŠsi@ô‹}i@3÷Œ}U@ú!daI@ŽŒaI3ŒaU@ŒIR‘_VR’io:“ nA~”‚O~ • xe:"–i@#$—A!en-na/#Fi;%KN&BI28oF3*pFUFs Ua#HuFaaVvKE2wKI5xA0>z KVA{ FA:M|xA@P}}3:Z~si:^WO:d€ xOt KO@h‚ xo@nƒ xu:w„!!daUy…!soU~† naIƒ‡seI…ˆiOIЉ se@ŒŠni@‹xU@’!daI@•ŽŒaI3˜ŒaU@šŒ'en-us@¢ Aa±#iiÇ%Ur/.t[ /FI2ÄoP3pi@2¨q<UÕs H@L¬t7Pa#¹uKaa±viE½waIÀxP0ÊzdVÒ{UA:×|iA@Ü}Z3:é~xi:ìUO:ï€ iO  dO@õ‚ }o@ ƒ }u: „!!_aU … uoU †!saI ‡}eI ˆsOI ‰ Že@ ŠŒi@) ‹}i@3+ ŒŒU@5 }aI@? Ž–aI3F –aU@M –@/¦˜A(en-sc@{ Fr€€< "a #di® %Kr/: .I2« o73~ pF@2† q<@5Š rFU¹ s!!F@L3 t7Pa#– uFaa› vnE  wUI£ x70³ z dV¶ {FA:½ |nA@Ç }}3:Í ~ii:Ó AO:Ü € dOì  KO@â ‚ so@ç ƒ su:ï „!!PaUû …!doU † !_aI ‡_eI ˆ_OI ‰ ie@ Šni@3 ŒnU@ !ZaI@. އaI31 ŒaU@+ ‡a/“ ˜PaI2 ™x"en-rp@A FaU #Wic %FI2` oA3G pF@2L q<@5P rFUl s Ka#n uKaa| vdEZ wFI] xA0f z FVi {FA:s |xA@v }x3: ~ii: … WO:‹ € sO•  KO@ ‚ su:˜ „!!_aUš …!soUœ †!naI¡ ‡seI¦ ˆnOI¨ ‰ se@ª Šni@­ ‹xU@° !saI@¶ އaI3¹ ŒaU@» ‡en-wma #PiÏ %nN¾ BI2È oFUÚ s!!Ka#Ý uFaaê vPEÅ wKIÈ xF0Ò z FVÕ { FA:á |xA@ä }x3:î ~}i:ò nO:÷ € xO  KO@û ‚ xu: „!!daU …!soU †!naI ‡ xeI ˆxOI ‰ se@" Šxi@( ‹xU@+ !daI@. ŽŒaI31 ŒaU@3 Œen-wi@6 Fa= #PiH %KlÐ7I2E oF@29 q<UO s Ka#Q uFaaX viE? wUIB xF0K zFVM { FA:S |xA@U }‚3:Z ~ xi:] _O:` € xOh  KO@b ‚ xo@e ƒ xu:j „!!_aUl …!soUn † saIp ‡seIr ˆiOIt ‰ se@v Šni@y ‹x'af: F@| Fr€€ñ "aƒ #Fi® %2u– (!!7r/ .l77c NOE‡ jFI‰ kFO’ l FW” mF&˜ nK&: oŒ@L¢ p7PA:§ qŒe@© rso@± s!}y¶ tZiu¸ u!n@Uº v!UaI¼ wnAI¿ x›eI yUOIÈ z soIË { ‘uIÑ |!xYyÔ }nY@× ~iaUÙ !se:Û €iO:Ý  Œ3:ß ‚sA~á ƒxe~ã „xo~å … xx2ç †cyr€q "a #Kg} O1E" jKI$ kKY( lKO* m KU, n!!KV. oKi:0 pZy:3 qZu:9 r!!_e:< sio:? t iA:B usAYE v}aIJ wiaYL xiaUQ y!i@IS zi@YU {ieUZ |!iIu\ }!iYu^ ~!iOIc  iOYe € iuIj !iuYl ‚!i)¬Íde@’ <r„) "až #7l/û 8j 9b0_ E0dd F/gi O13š jPE¢ k<E2¦ l<I« m<I:° n_O² o <U¶ p!!<URV q!ZA:À r}A s}i:Å tZi2Ê uZu:Ð v!!_aUÒ w!naIÔ xiEIÖ yiOYØ z nE:Ú {de:Ü |do:Þ } iy:à ~!!dyâ !!7Y:è €ZWê Kts( ‚pFî ƒg#ö „r2 ; …7V#I †oU ‡!sA~[ ˆ‚l2] ‰ eoan #Zep $Uir %Uou ' Uuz (!!UaU| j!}eU~ k!}aI€ l}eI‚ m}oI„ n }uI† o!}ts( pjboeˆ $Unci: –eŠ $U)fi: Pr€x"a— #Ue“ $KiŒ %Fo› ' MuŸ (!!Ftþ/FpÀ0Ekû1OR2€Ë 4dæ F/vÙ RQh iI jF&• kKa2™ lUY mMu1¡ n!!FU£ o!!Fy¥ p!!Kai § q›&i © r‘oi « s Œei ­ tŒYi ¯ u‡ui ± v!‡yi ³ w!‡au µ x!–ou · y !Œeu ¹ z!Œiu » {!Œ&y ½ |!Œey ¿ }!ŒYy Á ~!‡iy à !‚uo Å €! Œie Ç ŒyY É ‚!Œs2(…ƒ(et: Pr€"a#Ue$Pi!%Fo)' Pu/(!!HtCX/FpÀ0EkŠ1OdeF/vKRQh ¤ia:jªA1ke:l E1mxi:#nŒI1%oii1'po:+q  O1-r pu:1s!!‘U13t!!m85uR8:7v¥&9wW&:;x¯Y=yRY:?z¥yA{!!Hy:C|!!‘&i E}Yi G~˜yi I!Žs2(…€s^(¸Vt^‚ƒd^σ‚@89fr: @ô U@-öArŠA"kaø#Ze$Zi%Zo;' ZuR(!!Zr/ŠZ.ktµ/lFpp0lEk*1lOnC2l7jl/Æ8jwl:!!Zl/2à;jb­El0dáFl/g Ol1fQlRvÞRlQ-z0ÿVWs(”WVS(¦YlX#lj #rk #cFRl y[m!!ZE nZA~¢o_E~¤p_W~«q_O~©r _WfsZj/,t(r/2Іukr2ŠSvka-þwAa#–xKe- yAE-zAI¢{AI2¥|AOE} UoUä~!nu:Y!!xy-d€!!AW2h2Yj‚Uw/ƒn2j„UR…!!Zy"[†!!ZE: ‡ZAøˆZp2ˆ‰t2ÇŠt3Ö‹VüŒFz20z30Ž fr-ca: #u)(!!WR€83E'nRE~+p`I-{OU0…!!Ky"2†!!FE:4‡sA6ˆS9hi: 2@B Aa „#Aez$Air%soˆ' Atþ/Fp+0kh1Ob¸EdF/J0lMc NgO1våRQH ójVHkA@3llA@2jmAi: onsIuo2e: xpnE: |qnE~rA&: €sna: ‚tso: †u nO: Šv iOŒw AUŽx!!<u: y!!si~ ’znI~ ”{Ue~ –|nE~ ˜}sa~ š~}V~ œ}O~ ž€ so~   nU~¢‚!!Uu~ ¤ƒ!!saI ¦„xaU ¨…!xph>†bhª‡†th¹ˆFdhƉˆt.ÕŠ‹d.th.áŒdh.Œch(ŽKJh0Žkhu‘gh+‘#X2(@’ta: @B AaD#AeU$AiY%Aoa' Aue(!!7tÓ/vÀRVGkAi:_n‡e:Wp}a:St–o:cu –Ujx!!7u:ny!!ŒaIx„ŒaUz…!‡V#N“A#|” u2h•!!7U:t–!!‡kn@~ Ar€H"a €#Ae†$AiŠ%AoŽ' Au’(!!7dšFHvÀRi:Œn‡e:ˆp‡a:„t–o:u –u:”y!!ŒaI –„ŒaU ˜…!‡ml@µ Ar@„€"a»#AeÎ$AiÒ%AoØ' AuÜ(!!7R€Š3vÀRi: Ön‡IÔoAe: Ðp‡a: Ìt–o: Úu –u: Þy!!ŒaI à„ŒaU â…!‡y·“(a#Ê”Zd#•huiè%Foë' Auí(!!At /Fp+0Ekh1Ol87dF/c([NMAäj FEækFYïlAyñm!!Ai:ónne:õoxa:÷p‡o:ùq ‚u:ûr!!xy:ýs!!xY:ÿt‚ts(udz0vut2ws2(…xlv@K <a[#<eS$<iM%7od' <uh(!!7tD•/Fp¢0Ek²1OR2€|4i:Pj–e:Uk¥&Wl<&:Ym¥a#`n<a:^o¯o:fp ¥u:jq!!¥ai lr›ei ns–au pt!–uo ru!–oi tv ‘ui vw!‘ie xx‘iu zy!‘ts(Dˆzs2(Æ{#nl@Ð >r€Š"aï#KiÒ%AuÚ(!!Kt&/Fp:0Ekh1bCE0d/F/z0WVWs(NWVQ bcIÔjAyÖk!!Z8Øl!!FEÜmFE2ÞnFOáo FO:ãp ia:åqiAñrKA~¢s_O~öt _e:øu_e#úv_Y:ýwno:ÿx !KEIyiWyz!nVU{ neU|!nyU }!!n!#~ plab#_ip%Uuu(!!Zt/FR€3wé:d§F/fïQRa#ejUEikZE#nlZOsm ZywnZE~{o!}O~}p }t;šqrd;Ârqts( stdz0Ýtsts;(ãuvdz;0Hvuska#<e$<iû%2o' <u(!!7r-!,dl-K-FtV/Fpc0Ekû1l77wº:i:þw‚&x<e:y‘a: z‘o:{ ‘u:|!!ŒaU}!‡eU~!‚oU !‚aI€‡eI‚r:&‚–R^0,ƒR^/0;„l:P…}cses$<ow' <r-},<a:uz‘u:y|!!ŒoU{ !‚hr@ß Faã#Peì$Fiî%<oõ' Fu÷(!!Ftþ/FR€x3d F/dZ0¶IJtS(JIdZ;0ËKLtS;(˜LKZ0¤XYS(‚YXx&cbEêkF&èxFaIü€}@2á†FAæ‡PIòˆ<Uú‰!!Fr*0ŠmkdZ;0?KLk^5‹srth/FduF/dZ0ŸIJtS(¼JIdZ;0®KLtS;(ÂLKZ0ËXYS(ÝYX&VxFISˆ<r*€ZŠx#Š‹h#“Œ1rurÀ„C"(a#2eØ$2iz%ZoÆ' 2uÏ(!!(t/p+0kh1l 7l^ =(d§FdZ;0KKLtS;(YLKgêO1s(Ws;(t]xÿcn_Öjn#kts( lt;šmd;Ânm;_oI^sp#y…q2I#r(I‡s(I2t(I3–u(jaévZE¡w2E#£x2E2¬y(E3¼z(E%Ä{ZV|(OÉ} (8Õ~ 2u#Ñ!!(u"Ó€!!Kjuç!!_ja#ñ‚ZV#øƒ(A„2Y…!!Fa#%†2R4'‡bg@> Fr€Š"aC#Ke9$Fi3%AoO' FuT(!!Fl77xácuLYwg#êxg;by1it: aw#Ze|$Ui‰%Fo’' UuŸ(!!Pl^8=Fa/zjZE†kUOœl UU¢m!!PaU¤p ‡aI¦s}oI¨v se/zUi#Œ{FI|Ko/•} Ulaaª#Up+0El77E¬jUI®kKO±l PU³m!!Pa:µn‡e:·o‚i:¹pxo:»q }u:½r!!}y¿sKy:Át}aUÃu!‡aIÅv‡eIÇw‡EUÉx!‡OIËy } Ízesr@„X"aã#Zeå$_ié%Uoì' _uð(!!ZbEdFgòO1v#DSQD)TUs(2WVEçk_Oîl _&es-la &caa`#Zeg$Uor' Uuw(!!Pl77EjkZOol UUum!!Pa#czUE2m{Zpt*Õe¢$Pu®(!!Pr-€Y,l77x€ÂcE kUO¬l UU°m!!Fy¤n7eU¾q!saIµsseI¸tiIzz-e~|{xi~~|xo~} xu~ƒ~!!Z&~…Z&U~Š€!xoI~‘ ‚&˜‚Z&/šƒZAž„di/§…KOI»† sEUÀ‡!ss#(ЈV)pt-ptað#Ze$Pi %Ko' Uu(!!PR€H3wº:x€ cEÿkUOl UUm!!7yn7&~óx&U~ø€!x&æ‚Z&/êƒZi/ …2EU‡!ns#(,ˆX$ro@N Ur€j"aL#ZeF$ZoP' UuR(!!Pz;0\]s;(´]\Z;0^_S;(¾_^yHnZYToZI^1z#l;ƒ{m;Š|n;‘}i/B~K@IV}@UX€!‚oUZ !‚iI\‚}yI^ƒiyU`„!seab…}eod† ‡e[uf‡!}Oahˆ }p;˜‰Et;ŸŠFts;(¦‹f;­ŒRb;ȉd;ÖŽŠ*;áv;óŒ elr€˜"a%#Fe.$Fi0%Fo3' Ku5(!!Pt7/FkD1OdF/ grc: 2eY$Fo]' FfiQE[kKO_l KyWnPEUaz!sOIc{ sOUe| !syIg}ssva”#Fi:ojZIukAe:xliEzmFE-‚nFE:}onE3pFy:†q!!nyˆr!!Fu-Šs!!dY:ŽtnWuF8’v!!F&šwFA:œx}Ožy Fo: z iU¢{!!Fu:¤|!!isx¦}no@° <aÌ#<a#²j<I´k2i:·lsy½m!!<y:¿n!!‚WÁo<Y:Ãp‚EÅq<E:Èr‡e:Ês}a:Ît‡AÐuAA:ÒvŒOÔw <o:Öx ‡UØy!!<u:Úz!!xu-Ü{!!<u-:à|!!‚AIå}‡aIè~‡OIë ‡u-Iî€!‡Yyô!‡aUö‚!‡*is: 7a #Aiø%Au(!!Ab“EdFgªOvåRQl#|gi:ûjsIÿkAI:lsEmAE:nAa: osOp AO:q su:r!!sysAy:tsWuAW: vAaI#wUaI:%xseI(yUeI:*zsaU-{!UaU:/|!soU2} !UoU:4~ !sYy7KYy:9€nOI< iyI>‚Zm#@ƒn#H„n^#]…N#f†tl#€‡r#ˆs2(…‰)vi@æ A1· aÐ#AeÖ$diØ%_oà' duâ(!!dl72ºj3½k24Àl5Ãm:6Èn(%7Ío(a:ÒpŒEÔqdOÞr dyäs!!d@:ètŒaIêu}a:Iìv}@Iîw}@:Iðx}eIòydEIôzdOIö{ doIø| duIú}!dyIü~!daUþ!ia:U€!‡eU!dEU‚!diUƒ!d@U„!d@:U …!‡i@ †xy@‡du@ˆ!dkh‰)zhy1"22aˆ#KeŽ$ni–%_o§' Uu±(!!Utq/pd0kJ1c(ANz(7V2%j23(k4+l 5.m 61n74o2aa~psaai€q‡aau‚r!‚ang„snaang†t‡aiŠudauŒv!deiwneng’xneu”y!‚ingŸzniu¡{!dng£|¯oeng©} Œoi«~ dou­ !dong¯€ nung·!!dui¹‚!noe»ƒseo½„Ueoi¿…nyuÁ†!!n@zh@Ñ daÃ#}iÜ%}oò' }uý(!!}N-Á+BB}tJ/p00k ^1ná2l7j9N÷BtS;(rLfDQs.(Œ[S;(„_11Ãj 21Æk 214Él*22Ìm33Ïn 35Òo244Õp&)51Øq 253Ûr255Þs27ph:tthTukh hvtS;h({wts(™xtsh(£yts.(­zts.h(·{AÈ|}aiÍ}}AuÏ~!}@rÖ¯EØ€}eiÚ}i[ä‚}i.æƒ}iAè„}iAuê…!}iEì†}ioî‡ }iouðˆ!}o-÷‰ }ouùŠ !}ongû‹ úuA Œ!}ua !}uai Ž!}u@ !suei !}uo ‘! Œy ’!}yu “!}y& ”}yE •}y@ –}yi —} swa# #Ze $Zi %Ro& ' Zu( (!!UtÓ/dàFa/! jZtr: F@f KaV #_eF $Zi* %Koj ' _uX (!!Kl77J… Mcx NER kZOv l _Ud m!!Ky8 n!!MYD o!!MI6 zKWT {ZG€f|kua§ #ie¡ $niš %_o« ' nu¯ (!!dJÐ MNcà NMx¹ cE£ kKU­ m!!Ay± n!!PeUµ qŒeI³ tŒIœ z7E#¥ {F8© |PV· }Pid@ß Faá #Zeé $Zië %Zoð ' Zuò (!!ZdF/Eä kZOî l ZaUø p!xaIô sxeIö txE2ç zZ@Uú {!x!sq@ü Ka !#Ue!$Ui!%Fu5!(!!Ptþ/Fph!0Ekµ!1Owd!:dx!F/dZ;0¡!KLc(NKz0“!VW@/þ j2V!kUI#!lUa/!mUA!nUE!oUE#!pUI,!qFy.!r!!PO0!s UaI7!tneI9!unOI;!v nyE=!w!xl/4?!xLC!yllW!zts( {|dz0|{hy@Â! Pt#éaÊ!#deÈ!$ZiÄ!%PoÌ!' ZuÎ!(!!Ztþ/p+0kh1c([NQ ÃbyÆ!jPWÐ!kZaIÒ!lxeIÔ!mxi@Ö!nxp#>ots#( pk#uqdz0rsts(Ø!sda@â! Ar ""añ!#Keé!$Kiæ!%Ko÷!' Kuõ!(!!Kt>"/Fp$"0ER"3l "7våRQs("WV3ä!jAEë!kK&í!lK&#ï!m<Aó!nKOù!o KVû!pK0ý!q Kyÿ!rKY"sKW"tKW#"uKaI"v}ka@M" <t#ér€x"aV"#ZeQ"$ZiO"%PoX"' ZuZ"(!!ZtN/p+0kh1c([NQ Ãbp#>jts#( kk#\"lOdz0mnts(l"nrw: <av"#Zeƒ"$Ui‰"%Ko"' Uu•"(!!Pa/}"jZa#›"z2e#Ÿ"{2i#£"|2o#§"} 2u#«"~!!2+¯"+2²"€nea Ç"#seÅ"$ZiÂ"%PoÉ"' ZuË"(!!PVµ"kP@3»"lFaI Í"„xaU Ï"…!x@/½"“AeI Ñ"”xeU Ó"•!xVI Õ"–xVU ×"—!xoI Ù"˜ xoU Û"™ !xuI Ý"š!xpa@â" Aa ÷"#ne ó"$ni í"%nu ÿ"(!!nvÀRVç"kAIð"oKE õ"rdo: û"u nO ù"w dUý"x!!K+ß"“prsi#%Uo#' Uu #(!!UE#jUA#kZeI #liaU#m!s sl@# Fa##Ue#$Pi#%Fo#' Pu#(!!FvåRE#kPO#m Ugdt¹/k-1b“EdþFghO nsoa%##Ze##$Zi!#%7o'#' Zu)#(!!UtÓ/dàFU¤j!!PE™kUK+#lx2ç m hta=##Ue?#$UiC#%PoF#' UuJ#(!!ZEA#nUA~L#odE~N#pdO~P#r dOH#} U 5az@b# Pa`##deT#$PiR#%Po^#' Pu\#(!!PyX#n!!dWZ#{Z&V#}Pakal##Ueh#$Uif#%Uop#' Uur#(!!UEj#jUOn#k Uam@‚# nr€Š"a}##new#$nit#%do‡#' nu‰#(!!nb•#Ex»#cyy#jZp`‹#kEt`›#lFtS`(¨#mIk`±#nwo@Á# FaÓ##FeË#$FiÅ#%FoÛ#' Fuß#(!!F@:Ã#j‡i:È#k‡e:Í#l‡EÏ#mFE:Ñ#n‡a:Õ#o‡O×#p FO:Ù#q ‡o:Ý#r ‡u:á#s!!‡s2(…tdvaã##Aeè#$Aiì#%Aoð#' Auô#(!!7tÓ/vÀRi:î#n‡e:ê#p}a:æ#t–o:ò#u –u:ö#y!!‘aIø#„Œte@ú# Ar€Š"a ü##Ae$$Ai$%Ao$' Au $(!!7vÀRi:$n‡e:$p‡a:þ#t–o: $u –u:$y!!ŒaI $„ŒaU $…!‡si@$ Ar€H"a $#Ae!$$Ai%$%Ao)$' Au-$(!!7tÓ/vÀRi:'$n‡e:#$p‡&:$s‡a:$t–o:+$u –u:/$y!!ŒaI 1$„ŒaU 3$…!‡&$“Am#®”n#Ö•n.#û–2n^#!—N#I˜tn@T$ Fr€€Ñ$"ao$#Zec$$Zi[$%Uo{$' Zu~$(!!Ur-€@$,r/í$.tÓ/l77dàFtS(ö$JItS;(ÿ$LKI]$jAI2`$kAe@f$lsEl$mFA@s$nsOy$o FU€$p Kts(‚$qkh$rOk-Ÿ$sOK¬$tph¾$uE mt: Pa%#Ue%$Ki "%%‘o%' Mu%(!!FpÀ0Ekû1OdO%F/vB%RQh j%iI%jAY%kMU%l!!Fy%m!!Kai %n›oi $%o Œei &%pŒYi (%q‡ui *%r!‡yi ,%s!‡au .%t!–ou 0%u !Œeu 2%v!Œiu 4%w!Œey 6%x!ŒYy 8%y!‡iy :%z!‚uo <%{! Œie >%|ŒyY @%}!Œ boa~%#Ze€%$Zi‚%%Zo„%' Zu†%(!!Zts(ˆ%“”dz0•%”“tsh(ª%•”dzh0·%–“sources_5316/external/espeak/espeak-data/ta_dict0000644000176700017670000021422111663004331020525 0ustar paulpaul×# †à®¤à®©சரà¯à®šà¯Ap9 _#-வதà¯tRkFx•சிகà¯à®•ன௠†à®¤à®µAEnபிE%9pR. à® A Wn˜à®ªà¯‹à®©à¯à®¸à®¾à®¯à¯AFnŒà®•à¯à®¤à®¿Œà®ªà¯‹à®©à®¿ †à®ªà®µ லà¯%7பநà¯à®¤à®¾An ‰à®•ான பப0k0kŒà®ªà¯‚à®®à¯ArQபோகமà¯AIn _60#3xEkFA pJ !R%9k00x#&$@˜à®ªà®¾à®•à¯à®•ிசà¯A$t9%R%Zx11t‹x &?kŠ3x?›à®ªà®²à®¤à¯à®¤à®¾à®²à®¾à®©A(Ip9 *0$"x11k7 +1yŠŠk7A,1p9 /Wt9RxA0r7Œà®ªà¯‹à®•ிA4r?!žà®ªà®¾à®¤à®¿à®•à¯à®•à¯à®®à®¾A8r2 <1(3„RxA?%OxF%A@0nAD19yŒà®•ோலிAHt3 கபà¯1k0Œà®•ாடௌதொப௠பீபà¯En0ALrWAPˆn ஹà¯%aAT9y _1C2y3AXRn ‰à®•ம௠_#வதà¯tRkFx\0%2Wt9Rx A\FkEk79y_70&$ZxEkFபேகமà¯பாறமà¯A`r1W_1M2'"x7k‹Jk//x’பீரà¯à®®à¯_1M3'"x1u‹%pAd:t9Œà®•ிடà¯AhVrFŒà®•ிணௌகà¯à®°à¯Œà®ªà¯€à®šà¯ à®´à¯%Z ‰à®¤à®¿à®Ÿ’தடà¯à®šà®£à¯ˆŒà®•ினௌபகதௌபீர௠|W$BOx//xபிரசாரà¯0"kWt"_190#//'2EkF›à®•à®®à¯à®®à¯†à®©à¯à®±à¯’பரà¯à®®à®¿à®¯’பீசà¯à®šà¯ ‰à®•தி _1C02y3xதேவதாபஜà¯à®œà®¿ _2C%"x2y3’காநà¯à®¤à®¿’பைகà¯à®•ைŒà®šà®¾à®¯à®¾ ‰à®¤à®¿à®©Œà®•ோபிŒà®ªà¯à®°à®¾Œà®ªà®Ÿà®µà®¾தராவிŒà®ªà®¿à®•à¯_110#/%2'23 à®·à¯%[ †à®•ோ †à®•க வà¯%R கà¯%1 ஓகோuju_2C0%"x2y3xŒà®¤à®µà®•ௌதடக௠†à®•ட!žà®¤à¯Šà®ªà¯à®ªà¯†à®©à¯à®±à¯’பீடிக௠_3C?(22y3 _ 0(>>% †à®•ன _100#// †à®•à®®•தடியாய௒பவà¯à®¤à¯à®¤கமà¯à®©à¯˜à®•ேடà¯à®Ÿà®¿à®©à¯˜à®¤à®µà®¤à¯à®¤à®¿à®©à¯_0M27k‹Jk?•கமà¯à®®à¯à®©à¯_120k22%"k@‹போனà¯à®²Qu27kகி1%7u?nŠŠk"R. மீ !žà®•à¯à®®à¯à®®à¯à®©à¯à®©à¯’தடிகà¯à®•Œà®¤à®°à¯à®®˜à®¤à¯€à®°à®®à¯à®³à¯à®³ ‰à®•à¯à®£•தீபாவளி_0M1t9%"k?’போயிஙௌதிடௌபாவே*§à®ªà®²à®¿à®•à¯à®•à¯à®¤à¯à®¤à®¾à®©à¯˜à®ªà®²à®¤à¯à®¤à®¿à®©à¯’காணà¯à®Ÿà¯˜à®•ோபிகà¯à®•௘கà¯à®°à¯à®©à¯à®©à¯_3C0?(22y3x _4C2t2y3 _0M31u‹%•பைகà¯à®•à¯à®²Œà®ªà®¾à®·à®¾ _1'23 பிடà¯E%ŠŒà®ªà®¿à®Ÿà¯’போணà¯à®Ÿà®¾ _2%"k@‹ _4C02t2y3x˜à®¤à¯à®¨à¯à®¤à¯à®µà®¿ _5C„2y3 _3?y23Œà®¤à®¾à®©à¯ _20%"xEkFx˜à®ªà¯‹à®©à¯à®šà®¾à®¯à¯ _5„2F செடà¯W$Š˜à®ªà¯†à®Ÿà¯à®Ÿà®¿à®©à¯ _30?(00kFxŒà®•ௌனà¯_6t3தà¯à®°à¯à®µ _7&p7போதனை’தணà¯à®Ÿà®©à¯ˆ_3X?(00k//x _60#3xEkFx’தீகà¯à®·à¯ˆ _9'2Ek‹Œà®¤à®¾à®µà¯‡_70&$ZxEkFx•பலிகà¯à®•௠_1C2yŠŠ3% _5C0„2y3x_190#//'2EkFx_2C%"x2yŠŠ3% _6C#3x2y3•கோதà¯à®¤à®¿à®°Œà®ªà®µà®©à®¿_110#/%2'23x _100#//x_3C?(22yŠŠ3% _402t30kF_120k22%"k@‹x _42t2O_7X&$ZxEk//x_4C2t2yŠŠ3% _5C„2yŠŠ3% _402t30kFx _1X0#F%2_6C#3x2yŠŠ3%_2X%"xEk//x _50„?EkFx_7C&$Zx2yŠŠ3% _8&$ŠŠ சீசீJnJn_8C&$@@yŠŠ3%_??1(3%9n‹x தயாளà¯டிபà¯à®Ÿà®¿‹r09xŠ%_4X2t30k//x_9C/'>>t9%"k//xà®9p திகà¯F%1Œà®•ேடௌதிகௌபடà¯à®•_6C0#3x2y3xகளிலà¯பலிக௠à¯'Š3x _5X„?Ek//x _80&$@EkFxௌ’…_7C&$Zx2y3 டà¯%Šை’„ ோ’u ஃkOjொ'ஂk2xWRk3k à®™à¯%BOŒà®•ிரà¯!திகà¯à®¤à®¿à®•à¯F%OF%O_6X#3xEk//x _90/'@@y3x ே’p _50„?EkFெ$போனஸà¯à¯( ீ’n ூ’y பலதà¯à®¤ கிரேO"p ணà¯%@ ௹"yEt9’தொபà¯à®©à¯˜à®šà®¿à®Ÿà¯à®Ÿà®¾à®¯à¯Œà®ªà¯‚டà¯_8X&$@Ek//x பைகà¯E„1தாஙà¯à®¸à¯UtB1Wகவà¯à®©à¯›à®¤à¯€à®°à®¤à¯à®¤à¯‹à®Ÿà¯பலà¯à®ªà¯˜à®•à¯à®®à¯à®®à¯à®©à¯_9X/'@@yŠŠ3x யà¯%9 ஆகாtjtŒà®•ிலி டிவிŠ%R% à®±à¯%3 னà¯%2Œà®¤à¯‡à®µà®¾$பாதரà¯à®Ÿà®©à¯QtFk"x‹k2˜à®¤à®¿à®°à¯à®·à¯à®Ÿà®¿தலாய௒தடியனௌசார௕தà¯à®°à¯à®µà®®à¯ ளà¯%>!பைகà¯à®•ிலà¯E„11o7’பà¯à®•à¯à®•௒கà¯à®°à¯à®µà¯‡•களà¯à®•à¯à®•à¯_7C0&$Zx2y3x•களிலேயே _8C&$@@y3பைகà¯à®•!žà®•ேடà¯à®Ÿà¯à®•à¯à®•à¯!žà®•à¯à®°à¯à®µà¯à®•à¯à®•à¯!žà®ªà¯‚தà¯à®¤à¯à®•à¯à®•௠ா’t பாலியி% டிŠ%_0M27k‹Jk//x˜à®ªà®¿à®•à¯à®•ினி _0M31u‹%p’பீராமண_0M1t9%"k//xŒà®•ிரிதடியா•காயதà¯à®°à®¿பைகà¯à®² ‰à®ªà®Ÿà®¾’பாகà¯à®•ிŒà®šà®¿à®²à®¿ ஸà¯%Wபடà¯à®µà®¾_8C0&$@@y3xசிரமà¯W%"k? _#வதà¯à®®à®¾à®•tRkFx?tOkDPI0தமிழà¯பானம௠‰à®¤à¯‡à®µ$பாதரிடமà¯QtFk"%‹k?˜à®¤à¯à®µà®®à¯à®šà®®à¯˜à®ªà®¾à®•à¯à®•ிப௘தொபà¯à®ªà¯à®©à¯’தரà¯à®®à®®à¯’பணà¯à®¤à®®à¯’பாரதம௠பைலைQ„7„Œà®•à¯à®Ÿà¯ _#-லà¯%7பகவத௠பைலà¯Q„7Œà®¤à®©à®®à¯Œà®ªà¯à®•à¯தெனம௠‰à®ªà®²à¯‡•பà¯à®¯à¯‚னஸà¯பிரேகà¯E"p1_#-வதà¯à®®à¯tRkFx?˜à®ªà¯à®°à®¾à®£à¯à®Ÿà¯˜à®ªà®¾à®•à¯à®•ிதà¯பேனà¯à®²Qp27k_9C0/'>>t9%"k? ‰à®ªà®²à®¿ ‰à®ªà®°à®¤’பà¯à®¤à¯à®¤à®¿ _80&$@EkF ‰à®•யா ‰à®ªà®¾à®² ‰à®ªà®¾à®° ‰à®ªà®¾à®ª ‰à®ªà®¾à®©•தீரமறà¯à®±˜à®¤à®¿à®•à¯à®•à®±à¯à®±பாலà¯à®¯Œà®ªà¯€à®Ÿà®¾Œà®ªà¯€à®Ÿà®¿Œà®ªà¯‹à®¤à®¿Œà®ªà®¾à®²à¯ காபி1tQ% ¾?(11t7ரெடà¯à®Ÿà®¿"$‹‹%படà¯à®•ா ÷RkOx//k7¼1t7½#"„ à®¶à¯%Y’பாவà¯à®²à®¾’பிலà¯à®²à®¿ _#à®®à¯t?Œà®¤à®¾à®²à¯ பீலà¯Qn7பாணம௕பாகவதமà¯!_#-வதà¯à®®à®¾à®•tRkFx?tOk _90/'@@y3Œà®•னம௒பெனà¯à®¸à¯தானமà¯_#வதà¯à®®à¯tRkFx? ‰à®¤à¯Šà®³3$பாதரிலà¯à®²à®¾à®®à®²à¯QtFk"%77t?k7•காநà¯à®¤à®®à¯˜à®ªà®µà¯à®¤à¯à®¤à®®à¯Œà®ªà®¿à®¸à®¿Œà®ªà®¾à®²à®¾டாரà¯à®šà¯Št"J’கிலà¯à®²à®¿’பாரà¯à®²à®¿ _#லà¯%7Œà®ªà®¿à®²à¯!žà®¤à®¾à®Ÿà¯à®šà®£à¯à®¯à®®à¯பாகமௌபாபà¯பேனிலà¯Qp2%7போனிலà¯Qu2%7!žà®ªà¯‹à®°à®Ÿà®¿à®•à¯à®•ாம•செலà¯à®²à®®à¯˜à®•ேடà¯à®Ÿà®¿à®²à¯˜à®¤à®µà®¤à¯à®¤à®¿à®²à¯˜à®ªà®²à®¤à¯à®¤à®¿à®²à¯_1M2'"x7k‹Jk?_1M3'"x1u‹% பாபாEtEtŒà®ªà®¾à®ªà®¾'¤à®¤à®¿à®•à¯à®•ெடà¯à®Ÿà¯à®®à¯ _"?p3Ou>_''Š3„?p3Ou> _20%"xEkF_1#0%Šk7_)Rk7k0%3„ _(%‹k0%3„_.?(Š3x0(>>% _-%@„00xO_,1t70(>>% _3?y23x _2%"k@‹x _1'23x _0W(Z%9k? _7&pZx_6t3x _5„2Fx _42t2Ox_;t"„E0(>>%_:?(11t70(>>% _9'2Ek‹x பிராE"t _8&$ŠŠx _?1p>R%Œà®ªà®¾à®®à®¾•தயாநிதிŒà®¤à®¿à®®à¯_[%‹kW#Fx"k?பலமாக__#‹%O1u‹x_]Rk7kW#Fx"k? _30?(00kFŒà®ªà®²à®®à¯Œà®•à¯à®°à¯‡’பஙà¯à®•ம௒பாதாம௕தரிசனம௒சீசà¯à®šà¯€!žà®ªà®®à¯à®ªà®³à®¿à®®à®¾à®¸à¯ தீபà¯Fn0Œà®•டமà¯_{%‹kOk@k?பரதம௒கணà¯à®Ÿà®®à¯_}Rk7kOk@k?#பதà¯à®¤à®¿à®°à®ªà¯Ek//%"k0Œà®ªà®°à®¤à¯Œà®¤à®¿à®²à¯˜à®ªà¯€à®šà¯à®šà®¿à®²à¯˜à®ªà¯†à®Ÿà¯à®Ÿà®¿à®²à¯•கà¯à®£à¯à®Ÿà®¾à®©பாதரà¯QtFk"˜à®ªà®¾à®¤à®¿à®ªà¯à®ªà¯Œà®ªà®¿à®šà®¿Œà®ªà®²à®®à®¾•கசà¯à®šà®¾à®®à®¿ சà¯%J ஜà¯%IŒà®•à¯à®ªà¯Œà®ªà¯‡à®·à¯’பாமà¯à®ªà¯’தைவதம௠ஞà¯%A _#-à®®à¯t? டிகொ%1 சிகà¯J%1 †à®šà¯‡பேதமௌகà¯à®®à¯!žà®¤à®µà®¤à¯à®¤à®¿à®©à®¾à®²à¯பà¯à®°à¯‡à®•à¯E"p1 †à®šà¯€ †à®¤à¯‹ பà¯%0•களிலà¯à®®à¯•தெனமà¯à®®à¯•தீரமà¯à®®à¯ தà¯%/ போனà¯Qu2’சேசà¯à®šà¯‡˜à®¤à®°à¯à®®à®®à¯à®®à¯˜à®ªà¯‚கமà¯à®ªà®®à¯பநà¯à®¤à¯ †à®¤à®ŸŒà®ªà¯à®¸à¯!žà®ªà®¾à®¤à®¿à®•à¯à®•à¯à®®à¯’பீரின௒போஸினà¯பெடà¯à®² à®®à¯%? டிரேயினொ"p92!žà®•à¯à®®à¯à®®à¯†à®©à¯à®±à¯ ‰à®ªà¯‚த à®°à¯%" நà¯%2ரூ"yEt9 æ 0ç 1è 2é 3ê 4ë 5ì 6í 7î 8ï 9Æ ¾ Ê Ç ¾ Ë Æ × Ì Bà®·à¯à®¸à¯à®Ÿà¯Cடà¯à®±à¯à®·à¯à®¸à¯DஇஎஅEசஸFà®°à®±GகஹHெளௌIிீJநனKலளLபதகMபிளாஸà¯à®Ÿà®¿à®•à¯à®ªà¯à®³à®¾à®¸à¯à®Ÿà®¿à®•à¯à®ªà®¿à®°à®¾à®¨à¯à®¤à®¿à®¤à®£à¯à®£à¯€à®°à¯à®µà®¾à®Ÿà¯à®Ÿà®°à¯à®•ணà¯à®£à®¾à®Ÿà®¿à®®à®°à¯à®¨à¯à®¤à¯à®µà®¿à®¸à¯à®•ிகிளாஸà¯à®•à¯à®³à®¾à®¸à¯à®šà®¾à®°à®¾à®¯à®¤à®£à¯à®£à®¿à®ªà¯€à®°à¯à®•லரà¯à®šà¯‹à®Ÿà®¾à®®à®¤à¯Nவாழà¯à®•à¯à®•ைவிரà¯à®¨à¯à®¤à®®à®©à®¿à®¤à®©à®ªà¯‚மிOநெரà¯à®ªà¯à®ªà¯à®ªà¯à®¨à¯†à®°à¯à®ªà¯à®ªà¯à®¤à¯€à®ªà¯à®¤à¯€Pடிகà¯à®•ெடà¯à®ªà®¾à®Ÿà¯à®Ÿà®¿à®²à®®à¯€à®²à¯à®¸à®•ிளாஸடாஸகBObகObkபBQபQkதBbFதbFkiயேசரகசியரகà¯à®®à®¾à®©ரகà¯à®°à®¾à®®ரசனைரசாயனரசிகரசிகà¯à®•ரசிதà¯à®¤ரத ரதஙà¯à®•ளரததà¯à®¤ரதமரதà¯à®¤à®°à®®à¯à®®à®¿à®¯ரயிலரவீநà¯à®¤à®¿à®°ராகராசராஜராடà¯à®šà®¤ராடà¯à®šà®·ராணிராணà¯à®µராதாகிராதாவராதà¯à®¤ராப௠ராபà¯à®ªà®¿à®šà¯à®šà¯ˆராபà¯à®ªà¯Šà®´à¯ராமராயபà¯à®°ராவணராவà¯à®¤à¯à®¤ராஷà¯à®Ÿà®¿à®°லகà¯à®µà®¾à®•லகà¯à®·à¯à®®à®£லடà¯à®šà®•à¯லடà¯à®šà®™à¯லடà¯à®šà®£லடà¯à®šà®¤à¯லடà¯à®šà®®லடà¯à®šà®¾லடà¯à®šà®¿à®¯லடà¯à®šà¯à®®à®£லடà¯à®šà¯à®®à®¿லணà¯à®Ÿà®©லதà¯à®¤à¯€à®©லயிலவஙà¯à®•லாபலேசரபà¯à®ªà®°"kEEk%ராமல௠லேகà¯à®•ிய7pOO¯à±®àB 1¯à±®à 1kBB1€¯à®®à¯à²®à¾®àµ®àி¯à¤®àDà¯à®±à®¿à®¤à¯à®¤¯à´®à…®àà¯à®°à®²…®àà¯à®Ÿà¯‹à®ªà®°†®àாஷ†®àà¯à®°à¯‹à®·‡¯àµ®à¿®àµ®àானநà¯à®¤ˆ¯à°®à…®àà¯à®±à¯ˆˆ¯à±®à…®àூவ¯à™®à…®àிள¯à£®à€¯àµ®àோப¯à©®à†¯à¤®àிழ¯à°®à€¯àš®àேட¯à²®àŠ¯à¤®àாபà¯à®ªà®¿¯à²®à¿®à¯®à‹¯à•®àாளைŸ®à¯à·®à…®àோணலª®à…®àீரà¯à®¤à¯à®¤à®¿®®à¾®à°®àாவிய®®à¾®à°®à‡®àாதை®®à¿®à¤®à¯à¨®à…®àால¯®à¿®à°®à…®àà¯à®Ÿà®¿²®à€¯à¨®àேசி²®à‚¯à®®àாரண²®àŸ®à¯à£®à¯à•®àேசி¾®à²®à‡®àா¿®à¤®à†®àà¯à®Ÿà®¿¿®à©®à‚¯à¯®àோட¿®à®®à¾®à©®à…®àா¿®à²®à¯àª®àேசி¿®àµ®àà¯à®°à®®¿®à·®à†®àாாரனிரà¯à¯à®®à®¾à®°à¯à®²ூடொணà¯à®Ÿொளà¯Bீதலீதà¯à®¤ெடà¯à®Ÿà®¿à®•à¯à®• ெடà¯à®Ÿà®¿à®•à¯à®•னà¯à®®ெடà¯à®Ÿà®¿à®•à¯à®•ிெடà¯à®Ÿà®¿à®°à¯ோபபà¯ோர மாடà¯à®Ÿோர à®®à¯à®Ÿà®¿à®¯ோர வேணà¯à®Ÿோரபà¯à®ªà®Ÿோரபà¯à®ªà¯‹à®•ோரபà¯à®ªà¯‹à®µ¯à£®à‡¯à°®àா¯à®®àேஷ¯à²®à¾®à¤®àா‚¯àª®àாரர‚¯àª®àாரி‚¯à²®à¾®à¤®àா‡¯à°®à¯à¯®àாˆ¯àŸ®à•®àாரரˆ¯àŸ®à•®àாரிˆ¯à²®àµ®àாபை¯à³®àµ®àà¯à®Ÿˆ¯àµ®àோŠ¯à²®àேஷன¯à™®à²®àா¯à™®à²®à€¯à°®à¯à¸®àா¯à™®à¾®à¹®àாஙà¯¯àœ®à¾®à°®àிரண¯à£®à•®àாணா¯à©®à†¯à¤®àாசி¯à°®à†¯à®®àà¯à®°à®¿¯à°®à‡¯à¨®àாணல¯à°®à•®à¾®à¨®àோயில¯à°®àš®àிள¯à²®à•®àி¯à²®à¯®àˆ¯à¤®àாரர¯à²®à¯®àˆ¯à®®àš®àாரி¯à²®à¾®àª®àாரர¯à²®à¾®àª®àாரி¯à²®à¾®àª®àà¯à®Ÿ®àாதசி“®àேŸ®àµ®àிழ¤®à¯à¤®à‚¯à®®àà¯à®Ÿà®¿®®à¯à©®àŠ¯à¤®àால®®àš®àால®®à°®àª®àà¯à®Ÿà®¿®®à¾®à°®àாதைµ®à¯à°®à‚¯àª®àà¯à®Ÿà®¿¾®àª®àிஸà¯à®¤à®¾à®©¾®à¯®à¿®à£®à¯à£®à•®àà¯à®®à®°à®¿¾®à°®àேஷ¿®àE¯à©®à¹®àா¿®àŸ®à†¯àš®àொடி¿®àŸ®à¯à£®àµ®àாரர¿®à¤®à¯à¤®à¯à°®à¿®à•®àா¿®à¤®à¯à¤®à¯à°®à€¯à•®àா¿®à¤®à¯à¤®à¯à°®à¾®à•®àா¿®à¤®à¾®à°®àா¿®à©®à‹¯à®®àா¿®à©®àŒ¯à®®àா¿®à°®à¯à¤®à¯à®®à¾®àš®àா¿®à°®à¿®à¤®à¯à¨®àš®àா¿®àµ®à‡¯à¤®àா¿®àµ®à³®à¾®à®®àா¿®à·®àோ¿®à·®à‡¯à•®àாி¯à¸®à¯à•®àŽ®àயூஸி¯à¸®à®àரீமிலேசியூிராதகிராமà¯à®ªà®¿ரிதà¯à®¤à®¿ரிமினலிரியா ிரிஸà¯à®Ÿà®¿ரிஸà¯à®¤à®¿ரீடிரீமிரேயிளப௠ிளாEிிளாEà¯à®¿ளாEைிளினிகà¯à®¿ளிபà¯à®ªà®¿à®²à®¿ளிபà¯à®ªà¯ˆà®¿ளியரிளீனிளேசிளைமாகà¯à®¸à®¿ளௌà¯ரோதௌ¯àš®à…®àய௠கà¯கà¯ஸீ¯àª®à¯à¸®àˆ®à ௯మàமணிே¯àµ®à¿®àµ®à ை¯àª®àல ை¯à®®àோ¯àœ®à ௌ¯àš®àய௟®à௲®àனோ௾®à·®à ிரà¯à®·à¯1"%ிரà¯ஸà¯à®¤ிரிஸà¯à®Ÿà¯‹à®ªà®°1"%WŠuQkà¯à®°à®¿à®¸à¯à®Ÿà¯‹à®ªà®°à¯à®°à®ªš®àாணி1"k0ிராபà¯1"t0à¯à®°à¯‚டெ¯à°®à1"–Šிரணி1%ிரண௠à¯à®ª‹¯à²®àால10ிளிணà¯à®Ÿன17%2Škிளியோபாடà¯ரா17%9u0t/ிளரà¯à®•à¯17k"1à¯à®²à¯‹à®ªˆ¯àš®à¯à©®àŽ®àீடியா17u0ிளையணà¯à®Ÿ17„9k@Š“à¯à®¯à¯‚ரிட†¯àš®àி19–"%Šà¯à®µாலிபிகேஷன1:à¯à®µAà¯à®µà®¾à®²à®¿à®Ÿி1:t7%Šிளிப௠1>%0ிளிபà¯லிளிட1>%Š“ிளபà¯à®ªில1>kEEிளபà¯à®ªà¯à®•à¯à®¿à®³à®ªà¯à®ªைà¯à®š†®àà¯à®µà®²1Jà¯à®š†¯à²®àà®°1Jkà¯à®š¿®àª®àà®°à¯à®š¿®à®®àà®°à¯à®•ˆ¯à•®àடிகார1Okà¯à®šà®¿à®•†¯à®®àோ1W%1à¯à®¸à®¿à®•†¯à®®àோà¯à®·B1[à¯à®š¿®àµ®àனரி1[kà¯à®·B1k¯à¤®à®®àà®°¯à°®à’®àடà¯à®Ÿ¯à±®à®®àடà¯à®Ÿˆ¯à²®à…®àடலŒ¯àš®à…®àரிய¯à£®à€¯àµ®àதை¯à£®à€¯àµ®àவலை¯à£®à€¯àµ®àà®·à¯à®Ÿ¯à²®àŠ¯à•®àதà¯à®¤à®¾¯à²®à¯®àˆ¯à®®àš®àட௚®à¯àš®à‰®àடà¯à®Ÿš®à¯àž®àª®àலà¯à®¯à®¾à®£š®à¯àž®àª®àவà¯à®¯Ÿ®à•®à¿®àµ®àவி©®à¿®à¤®àà®°ª®à¯à®®à°®à†®àடà¯à®Ÿ²®à•®àš®àலாµ®à¯à¸®à¿®àµ®àà®°à¯à®®à®¾¾®à•®à®®àவி¾®à¤®à¯àš®àரிட¾®à¤®à¯àš®àரின¾®à¤®à¯àš®àர௠¾®àª®à°®à¿®àª®àà®°¾®àµ®à¿®à¤®àà®°¾®à¹®à®®àவிவிஞவிராயà®™à¯à®•ாரà¯ணà¯à®Ÿà®™à¯à®•தà¯à®¤‹¯à²®àலŒ¯àš®àரிய¯à™®à¿®à²®àன¯à£®à€¯àµ®àனவ¯à£®à¿®àµ®àற௯࣮࿮൮àள¯à²®à¯à•®àà®°à¯à®©à®¿¯à²®à†¯àµ®àà®®¯à²®à•®àணà¯à®Ÿ¯à²®à•®àதà¯à®¤à®¾£®à°®àள¯®à¯à¤®àš®àலா¯®à¿®à¤®à¯à¤®àš®àலா¯®à¿®à°®à‚¯àš®àலா°®à¿®à¤®à¯à¤®à¿®àš®àலா°®à¿®à¤®à¯à¨®àš®àலா²®à¾®à•®àடà¯à®Ÿµ®à€¯àœ®àலை¿®àš®àš®àலா¿®àŸ®à†¯à®®àல¿®àŸ®à¯à•®à¾®à°®à¯àª®àலட¯à™®à†¯àµ®à1kŠ“à¯‡à®ŸŠ¯à²®à1pŠ“à®¾à®¨à¯à®¤€¯à°®à¯à¸®à1t2/“ோபிதà¯à®¤à¯1uEà¯à®®à¯†à®£à¯à®Ÿ¾®àŸ®à1x?$@/“ௌசிக1…W%1“à¯à®Ÿà¯1Šà¯à®Ÿà¯à®°à®¿à®•†¯à²®àŽ®àல1Š"%1kà¯à®Ÿ1Š“¯à•®à1“¾®àŸ®à¯à¸®à¿®àª®à‹¯à•®à௯మྮ੮à¯à©®à®®àடி1•௯®à¿®à°®à…®àடி௮®à°®àª®àடி¯à•®àˆ¯à²®à®®àà¯à®•ைO¯à•®à¿®à±®à®àà¯à®¤à®¿¯à™®àிரà¯¯à™®à…®àொ¯à™®à‡®àொ¯à±®à¨®àà¯à®£BீதB ாணà¯à®Ÿà®¾à®®à®¿à®°à¯à®•ாணà¯à®Ÿà¯€à®ªாநà¯à®¤à®™à¯ாநà¯à®¤à®¤à¯ாநà¯à®¤à®¿ானஙà¯ானதà¯à®¤ானமானவிதà¯à®¤à¯ˆானாாயதà¯à®¤à®¿à®°à®¿ாரà¯à®Ÿà®©ிஃபà¯à®Ÿிடà¯à®•ிடà¯ிணà¯à®£à¯†à®©à¯à®±ினà¯à®©à®¸ினà¯à®©à¯†à®©à¯à®±ியரிரிகà¯à®•ாிரிஜாிரிதரிரியாகிரியாலிரியிிரியà¯ிரீஷிரà¯à®•ஸà¯à®¤à®°ிரà¯à®•ிரà¯ிரà¯à®¹à®¸à¯à®¤à®°ிரà¯à®°à¯†à¯à®•நாதà¯à®•னà¯à®•ராஜà¯à®•ைà¯à®œà®°à®¾à®¤à¯à®œà®¾à®²à¯à®Ÿà®¿à®¯à®¾à®¤à¯à®¤à¯à®Ÿà¯à®•à¯à®Ÿà¯à¯à®£à®™à¯à¯à®£à®šà¯€à®²à¯à®£à®šà¯‡à®•à®°à¯à®£à®šà¯à¯à®£à®¤à¯à¯à®£à®¨à®²à¯à®£à®ªà®°à¯à®£à®ªà¯à®ªà®Ÿà¯à®£à®®à¯à®£à®µà®¤à®¿à¯à®£à®µà®¾à®©à¯à®£à®¾à¯à®£à¯à®Ÿà®Ÿà®¿à¯à®£à¯à®Ÿà®©à¯à®£à¯à®Ÿà®®à¯à®®à®¾à¯à®£à¯à®Ÿà®°à¯à®£à¯à®Ÿà®¾à®•à¯à®£à¯à®Ÿà®¾à®¯à¯à®£à¯à®Ÿà®¿à®©à¯à®£à¯à®Ÿà¯à¯à®£à¯à®Ÿà¯‚சிà¯à®£à¯à®Ÿà¯ˆà¯à®£à¯à®Ÿà¯‹à®¤à®°à¯à®¤à®¿à®•à¯à¯à®¤à®¿à®šà¯à¯à®¤à®¿à®¤à¯à¯à®¤à®¿à®ªà¯à¯à®ªà¯€à®°à¯à®ªà¯à®•à¯à®ªà¯à¯à®ªà¯à®•à¯à¯à®ªà¯‡à®°à¯à®ªà¯à®ªà¯†à®©à¯à®±à¯à®®à®¾à®¸à¯à®¤à®¾à¯à®®à¯à®•à¯à®®à¯à¯à®®à¯à®ªà®²à¯à®®à¯à®®à®¾à®³à¯à®®à¯à®®à®¿à®Ÿà®¿à®ªà¯à®ªà¯‚ணà¯à¯à®®à¯à®®à®¿à®°à¯à®Ÿà¯à®Ÿà¯à®®à¯à®®à¯†à¯à®°à¯à®•à¯à®²à¯à®°à¯à®•à¯à®•ளà¯à®°à¯à®•à¯à®•à¯à®²à¯à®°à¯à®šà®¾à®®à®¿à¯à®°à¯à®œà®¿à¯à®°à¯à®¤à¯‡à®µà¯à®°à¯à®¨à®¾à¯à®°à¯à®ªà¯‚ஜைà¯à®°à¯à®ªà¯à®ªà¯†à®¯à®°à¯à®°à¯à®®à®¾à®°à¯à®°à¯à®®à¯‚à®°à¯à®¤à¯à®¤à®¿à¯à®°à¯à®°à®¾à¯à®°à¯à®µà®¾à¯à®°à¯à®µà®¾à®¯à¯à®°à¯à®µà®¿à®Ÿà¯à®°à¯à®µà®¿à®©à¯à®°à¯à®µà¯à¯à®°à¯à®µà¯à®Ÿà¯ˆà¯à®°à¯à®µà¯ˆà¯à®°à¯à®µà¯‹à¯à®°à¯à®µà¯‹à®Ÿà¯à®²à®¾à®ªà¯à®²à®¾à®®à¯à®²à¯‡à®ªà®¾à¯à®²à¯à®®à¯‹Gà®°à¯à®µà®¹à®¾à®¤à¯à®¤à®¿à¯à®¸à¯à®¤à®¿ூகிளூகà¯à®³ூடலூரூரà¯à®•à¯à®•à®°ூரà¯à®•à¯à®•ாெஜெடà¯à®Ÿà®¿ெதà¯ெஸà¯à®Ÿேடà¯à®Ÿà®£à¯à®Ÿà¯ˆேடà¯à®Ÿà®¿à®²à®¿à®°à¯à®¨à¯à®¤ேடà¯à®Ÿà¯à®•à¯à®•à®°à¯à®•ேடà¯à®Ÿà¯à®•à¯à®•à¯à®ªà¯ேடà¯à®Ÿà¯ˆà®•à¯ேடà¯à®Ÿà¯ˆà®¤à¯ேடà¯à®Ÿà¯ˆà®ªà¯ேலிேஸ௠சிலிணà¯à®Ÿà®°ேஸ௠ஸà¯à®Ÿà®µà¯ைடொணதà¯ொணமொரிலோகà¯à®²ோசாலைோதாவரிோதà¯à®®à¯ˆோதà¯à®¤à®¿à®°à®™à¯ோதà¯à®¤à®¿à®°à®¤à¯ோதà¯à®¤à®¿à®°à®®ோதà¯à®°à®¾ோதà¯à®°à¯‡à®œà¯ோநà¯à®¤à¯ோபிகைோபிசெடà¯ோபிசà¯à®šà¯†à®Ÿà¯à®Ÿà®¿ோபிநாோபியோபà¯à®°ோமதிோமாதாோமியோமூதà¯à®¤à®¿à®°ோயலோர ோரகோரதோரபோரமோலிகோலியோலà¯à®•ொணà¯à®Ÿà®¾ோலà¯à®®à®¾à®²ோவாோவிநà¯à®¤ோஷௌனைௌனà¯à®•ளௌரவௌரி¯à°®à†¯à®®àூடà¯à®Ÿ¯à•®à¤®à®®à¯à©®à®®àà¯à®•ை¯à™®à…®àà¯à®²¯à±®àš®àà¯à®£¨®àà¯à®²à®¿¯à™®à‡®àலீஷà¯à®¿¯à±®àŠ¯àª®àரணிரணிரகிரகணிரநà¯à®¤à®¿ரவà¯à®£à¯à®Ÿà®¿ரஹிராகà¯à®•ிிராமிரிகோரியிரிலà¯à®¿ரீனிரீனà¯à®²à®¾à®¨à¯à®¤à®¿ரீஸிரேகà¯à®•ிரைணà¯à®Ÿà®°à®¿ரௌணà¯à®Ÿà®¿ளாஸ௠à¯லோபலà¯வாலியரà¯ரவà¯à®£à¯à®Ÿà¯ரிகோரியà¯ரீனà¯ரூபà¯ரௌணà¯à®Ÿà¯ளாஸ௠à¯வாலியரிபà¯டO%Qà¯à®°à¯à®ªாதO("(0à¯à®ªà¯தO(0à¯à®²à¯à®•நà¯à®¤O(71kà¯à®£à®šிதà¯à®¤à®¿à®°O(@kJà¯à®£à¯à®Ÿà®¾à®¨à¯à®¤டிO(@‹t2/kà¯à®•Dà¯à®•ைOOà¯à®•Dà¯à®£à¯à®•Dோபà¯à®°à¯à®•¯à£®à…®àà¯à®£à¯à®Ÿà¯à®•…®àினிà¯à®•†®àினைà¯à®•‹¯à¯®à…®àியà¯à®•‹¯à°®à†®àியà¯à®•¯à°®à€¯à¤®àாலோசநைà¯à®•©®àœ®àà¯à®®à¯à®ªà®²à¯à®•¾®àœ®à¾®à°®àினைà¯à®•¾®àª®à‹¯à•®àினிà¯à®•¾®à°®àˆ¯àµ®àியà¯à®•¾®àµ®à¯à¯®à†¯à¤®àினைà¯à®•¯à®®àà¯à®£à¯à®•‡¯à²®àியà¯à®•‹¯à¯®àியà¯à®•¯à°®à‹¯àª®àà¯à®£à¯à®•²®àினà¯à®•²®àேஜà¯à®•¾®à¤®à‡¯àµ®àினிà¯à®•¾®à¤®à¿®àµ®à•®àினிà¯à®•¾®àµ®à‡¯à¤®àினைà¯à®•¿®à•®à¯à•®à¾®àª®à¯àª®à¯à¤®àà¯à®£à¯à®Ÿà¯à®•¿®àŸ®à†¯àµ®àà¯à®£à¯à®Ÿà¯à®•¿®àµ®àினம௠à¯à®•¿®àµ®àிரகà¯à®•ிDரகà¯à®•ிDரஹà¯à®•ி¯à•®àராமà¯à®•ி¯à¨®à…®àà®°à¯à®•ி¯à©®à…®àà®°à¯à®•ி…®àராமà¯à®•ி‡®àராமà¯à®•ி¾®à¯®à¿®à¤®à¯à¤®àš®àரகà¯à®•ிµ®à¨®àà®°Gà¯à®•¯à°®à¿®à¨®àதிOOkà¯à®•ˆ¯à£®à¯à¤®àணà¯à®Ÿà¯à®•¯à°®à€¯à¤®àமாகà¯à®•¯à°®à¯à¤®àOO“à¯à®•¯à°®à‚¯à®®àà¯à®•¯à°®à¾®à®®àà¯à®•¯à°®àŠ¯àš®àà¯à®•¯à°®àµ®àà¯à®•¯à°®àµ®à¯à¸®àà¯à®•œ®àOkஜà®™à¯à®•ாà®™à¯à®•ைஞà¯à®šà®¾டகடடதà¯à®¤à®¿à®²டதà¯à®¤à¯à®•à¯à®•டதà¯à®¤à¯ˆடபà¯à®ªà®¾à®°à¯ˆடிகாரடோதà¯à®•ஜணபதிணீரணேணà¯à®Ÿà®™à¯ணà¯à®Ÿà®¤à¯à®¤தாயà¯à®¤திகலஙà¯திகà¯திதாதிமோடà¯à®šதியதியிலà¯தியைநà¯à®¤à®°à¯à®µனகà¯à®•னதà¯னபாடினமபà¯à®ªà¯†பà¯à®ªà¯†à®©à¯à®°மகமமவெனà¯à®±à®®à¯à®ªà¯€à®°யானாயாவராஜà®°à¯à®Ÿà®°à¯à®œà®°à¯à®ªà®°à¯à®µலாடà¯à®Ÿà®¾லிலIயோலீரலீலளà¯à®•à¯வணவனவரà¯à®©à®°வரà¯à®©à¯à®®à¯†à®£à¯à®Ÿவாஸà¯à®•à®°வà¯à®©à¯ˆவà¯à®©à¯à®•ளவà¯à®°¯à•®àˆ¯à²®à¤®àன¯à±®à¨®àதிபà¯EாOk0பà¯à®šிபà¯Ok0Jவரà¯à®®à¯†à®£à¯à®ŸOkRk"?$@Š“à®¾à®£à¯à®Ÿà¯‡à®•à®°Ot@‹p1kோபாலOu0ோபிகா ோகிலாOu1ோடà¯à®šேOu‹Wூரà¯à®•ாOy"1ெளதமO…ெளரவெளரிௌதO…/“à¯à®ŸŽ®àேO‹à¯à®Ÿ†¯à¹®àே‹¯à®®àினிj®®àா®®àேசà¯à®µà®°®®àேநà¯à®¤à®¿à®°®®àேஷà¯à®µ®®àேஸà¯à®µà®°®®àிநà¯à®¤®®àிமை‹¯à®®àனjkBBBk¯àž®àBI¯àž®àIk ¯àš®àBJ†®àார †®àாரதெ®àாரம¯àŸ®àB¯à±®àBª®à…®àாரª®à‰®àாரª®à‹¯àœ®à¾®à°®àாரª®à¿®àµ®àார¾®à®®àš®àார¾®à²®à•®àார¿®àµ®àிதà¯à®¤à®¿à®°ாரியெஸà¯à®Ÿà®°Bாணகà¯à®•ியானà¯à®¸ாமà¯à®£à¯à®Ÿாயாவாயà¯à®¸ாரà¯à®µாரà¯à®œà¯ˆாரà¯à®œà¯ ாரà¯à®²à®¸ாரà¯à®²à®¿ாளà¯à®•à¯à®•ியிகà¯à®•னà¯ிகà¯à®•னைிகà¯à®•னà¯à®©à®¾ிகà¯à®•ாகோிடà¯à®Ÿà®¾à®•ிடà¯à®Ÿà®¾à®Ÿà¯à®Ÿிடà¯à®Ÿà®¿à®ªà®¾à®ªà¯ிடà¯à®Ÿà¯ிடà¯à®²ிதமà¯à®ªà®°ிதà¯à®¤à®ªà¯à®ªà®©ிதà¯à®¤à®ªà¯à®ªà®¾ிதà¯à®¤à®¿à®°ிதà¯à®¤à®¿à®°à®µà®¤à¯ˆிதà¯à®¤à¯‚à®°ிதà¯à®°à®µà®¤à¯ˆிதà¯à®°à®¾ினà¯ிபà¯à®ªà¯ிபà¯à®ªà¯ˆிபà¯à®¸ிறà¯à®±à®®à¯à®ªà®²ிலியிலà¯à®±ிலà¯à®²à®±à¯ˆிளà¯à®±ீன ீனதà¯à®¤à¯ீனபà¯ீனாீனாவà¯à®Ÿà®¿à®¤à®¾à®°à¯à®Ÿà¯à®Ÿà®¿à®ªà¯ூரணெகà¯à®•ோEெஙà¯à®•ிஸெடà¯à®Ÿà®¿à®¨à®¾à®Ÿெடà¯à®Ÿà®¿à®ªà¯à®ªà®¾à®³à¯ˆà®¯ெடà¯à®Ÿà®¿à®¯à®¾à®°ெனà¯à®©à®¿ெனà¯à®©à¯ˆெயினெயà¯à®©ெரà¯à®©à¯‹à®ªà®¿à®²ெலà¯à®²à®•à¯à®•ிளிெலà¯à®²à®•à¯à®•à¯à®Ÿà¯à®Ÿà®¿ெலà¯à®²à®•à¯à®•à¯à®´à®¨à¯à®¤ெலà¯à®²à®¤à¯à®¤à¯à®•à¯à®•à¯ெலà¯à®²à®¤à¯à®¤à¯ˆெலà¯à®²à®ªà¯à®ªà®©ெலà¯à®²à®ªà¯à®ªà®¾ெலà¯à®²à®ªà¯à®ªà®¿à®³à¯à®³à¯ˆெலà¯à®²à®ªà¯à®ªà¯†à®£à¯ெலà¯à®²à®ªà¯à®ªà¯ˆà®¯à®©ெலà¯à®²à®®à®¾ெலà¯à®²à®®à¯‡ ெலà¯à®²à¯ˆà®¯à®¾ெஸà¯ேஞà¯à®šேடà¯à®Ÿà®©ேனலேரிேரà¯à®•ளேரà¯à®®à¯‡à®©ேலஞà¯ேஷà¯à®Ÿà¯ˆைதà¯à®¤à®¿à®¯ைனாைனாவைனீஸௌதரிௌதிரிௌஹானG°®à¿®à•®àார€¯à°®àாரà¯à®œ¯àš®àீநà¯à®¤à®¿à®°¯à¸®à¿®àŸ®àாரà¯à®œš®àின¿®àª®à‹¯à•®àெடà¯à®Ÿà®¿à¯ à¯à®šBJ à¯à®šJ kெக௠J$1ெசà¯னியாJ$JெசனியாJ$Jkெசனà¯à®¯à®¾à¯†à®Ÿà¯à®Ÿà®¿à®ªாளையJ$ŠŠ%0ித¯àš®àà¯à®°à®¾J%/ிபà¯களJ%0ிகாகோJ%1ிகà¯மஙà¯à®•ளூரிகà¯லெட௠¯àš®àJk¯àŸ®à¯à±®à¾®àŸ®à•®à¯à™®à†¯àµ®àல¾®àŸ®à•®à¯à™®à‡¯àµ®àல¾®à£®à¯à°®à…®àல¾®à¤®à¯à°®à®®àல¾®à¤®à‡¯àµ®àலநà¯à®¤à®°நà¯à®¤à®¿à®°கà¯à®•ரவரà¯à®¤à¯à®¤à®¿கà¯à®•ிலிடà¯à®Ÿà®¿à®©à®¿டà¯à®©à®¿ணà¯à®Ÿà®¾à®³தà¯à®°à¯தà¯à®¤à®¿à®°தà¯à®¤à¯à®°à¯தà¯à®°à®ªà®¤à®¿தà¯à®°à¯பà¯à®ªLà¯பà¯à®ªà®¾பà¯à®ªà®¿பà¯à®ªà¯à®°à¯à®šà¯à®šà®¿à®²à®°à¯à®šà¯à®šà¯வான‹¯à®®à¿®àµ®àன‹¯à®®à¿®àµ®àª®à¾®àš®àன‹¯à®®à¿®àµ®àµ®à¾®àª®àன¯à™®àª®àà®°¯à©®à¿®àŸ®àà®°¾®à•®à¿®à£®à¤®àல¾®à·®à‡¯àš®àலரà¯à®šிJk"Jதà¯à®¤à®¿à®°à®ªதிJk//%"k0kானலJpாரà¯à®²à®¤ாJt"x7k/ாபà¯ளினJt0ாகà¯à®ªீEJt10ாகà¯à®²à¯‡à®Ÿà¯Jt17pŠாநà¯à®¤ினJt2Fாநà¯à®¤ிலாமà¯à®ªியனJt?0BWBிதà¯à®¤à®ªà¯à®ªà®¿à®°à®®à¯ˆினà¯à®¹à®¾ீனிவாைனா நேவால‡¯à¤®àாநà¯à®¤à®¿à®°à®¿ரமிநேினேிராரà¯à®¤à¯à®¤à®¿லாகிிலேடே¯à•®àவே¯à£®àµ®à¾®à°®àவரே¯à£®àµ®à¾®à°®à‡®àவரே¯à®®àவ௿®àµ®àவà¯வாதீனà¯வாமிà¯வாரஸà¯à®¯à¯à®°à¯à®¤à®¿à¯லோகà¯வரà¯à®£à¯வாசà¯விடà¯à®šà¯விஸà¯வீடீ¯à©®àš®àவரை®àிரà¯à®™à¯à®•ாரW"%ிரà¯à®·à¯à®Ÿà®¿à®¿à®°à®¿à®²à®™à¯à®•ாW"%7kB1ீனிவாசW"nெயினà¯à®ŸW$9%2Šà¯†à®¯à¯à®©à¯à®ŸW$92Šà¯à®µà®°à¯à®•à¯à®•ோழிW(Rk"11à¯à®µà®°à¯à®•à¯à®•WRk"OO“à¯à®µà®¾à®°à®šà®¿…®àயWRt"kWà¯à®µà®¾à®°à®šà®¿யWkநà¯à®¤à®°à¯à®ª¯àŸ®à¹®àன¯àŸ®à¾®àµ®àன¯àŸ®à¿®àµ®à‡¯àŸ®àனரசà¯வதிWk"kWாநà¯à®¤à®¿[ெணà¯à®ªà®•ணà¯à®ªà®•[kணà¯à®®à¯à®™à¯à®•à®°[kB1kBIà¯வாலIk¯à©®à¿®àŸ®àà®°Jkà¯à®šà¯‡®à2Jà¯à®šà¯¿®àµ®àà¯à®š¾®à•®àனா2JkBAAk ி¯à¸®à²®àŠ¯à•®àராலŠà¯¯à¸®àà®°à¯à®šà¯²®àமண1[à¯à®šà¯²®àமி ¯à²®à¯àª®àாஸŠ¯à³®àோனிய¯à£®à‡®àெ¯à²®à…®àா¯à²®à‰®àா¯à·®àB¯à¸®àBாகà¯à®•ானà¯à®šà®¾à®©à®¿à®¯ானà¯à®œà®¾à®©à®¿à®¯ாமிாரà¯à®šà¯à®šà®°ாலமிாலà¯à®¸à¯à®Ÿà®¾à®¯ாஸà¯à®®à®¾à®•à¯ிஃபனிகà¯à®•ினà¯ிபà¯à®¸ிராமிவிகிவியிவிலிஷà¯à®¯ீà¯à®©à®¿à®šà®¿à®¯à®¾à¯à®©à®¿à®¸à¯à®©à¯€Eà¯à®©à¯€à®·à®¿à®¯ூரெகà¯à®¸à®¾à®¸ெகà¯à®¸à¯ெணà¯à®Ÿà®°ெணà¯à®Ÿà¯à®²à¯à®•à®°ெனà¯à®©à®¿à®¸à¯ கோரà¯à®Ÿெனà¯à®©à®¿à®¸à¯ பநà¯à®¤ெனà¯à®©à®¿à®¸à¯ மேசà¯ெனà¯à®·à®©ெரெலிஃபோனெலிவிஷனெல௠அவீவேபேஸà¯à®Ÿைம௠ோகà¯à®•னோகà¯à®•ியோோடà¯à®Ÿà®²à¯à®°à®¾à®©à¯à®šà®¿à®¸à¯à®Ÿà®° ¯à©®à¾®à²®àெனà¯à®©à®¿à®¸ ¯à³®à¿®àª®à‡¯àŸ®àெனà¯à®©à®¿à®¸‚¯à¯®à¯àŸ®àி‚¯à¯®à¿®àŸ®àிŒ¯à•®àிலà¯à®¯¯à£®à‡¯à•®àீன¯à£®à‡¯àª®àி¯à£®à¾®à•®àீன¯àª®àƒ®à‡¯àš®àி¯à°®à‹¯àª®àிகோ¯à°®à¾®à•®àூன¯à°®à¾®à®®àின¯à²®à¯®à¾®à°®àி¯à²®àµ®à¾®à¨®àி¯à²®à¾®à®®àா•®à†¯à¨®àிவ¿®àœ®à†¯àµ®àே¿®à°®à¯àª®àோரிய¿®à²®à¾®àµ®à¯à•®àிி¯à£®à‡®àரெஸà¯à®Ÿà®¿¯à£®à•®àரோலியூசனியூனியூபியூஷனிà®°à®™à¯à®¿à®°à®™à¯à®•à¯à®¿ரபிளிராஜிரானà¯à®šà®¿à®¸à¯à®Ÿà®°à®¿ரானà¯à®¸à¯à®ƒà®ªà®°à®¿ரானà¯à®¸à¯à®ªà®¿ரானà¯à®¸à¯à®®à¯€à®Ÿà¯à®Ÿà®°à®¿ரானà¯à®¸à¯à®²à¯‡à®¿ரானà¯à®¸à¯à®µà¯‡à®²à®¿ராலிிராவலிராவெலிரிமà¯à®¿ரிலà¯à®²à®¿à®¯à®©à®¿ரெணà¯à®¿ரெயினிரெயà¯à®²à®°à®¿ரேிரை செஞà¯à®šà®¿ரை செயà¯à®¿ரை பணà¯à®¿ரையலிரைலரி¯à£®à¾®à•®àராகà¯à®Ÿà®°à¯†®àராெ®àறாெ¯à¨®à¯à°®àŸ®à¯à£®à‡®àே®àலரà¯¯à£®à†¯à®®àà¯¯à£®à‡®àரேஸà¯à®Ÿà¯¯à£®àŽ®àரிà¯¯à£®à•®àரோலà¯யூசனà¯யூனà¯யூபà¯à®°à®™à¯à¯à®°à®™à¯à®•à¯à¯ரபிளà¯ரஸà¯à®Ÿà¯ராஜà¯ரானà¯à®¸à¯à®ƒà®ªà®°à¯ரானà¯à®¸à¯à®ªà¯ரானà¯à®¸à¯à®ªà®¾à®£à¯à®Ÿà®°à¯ரானà¯à®¸à¯à®®à¯€à®Ÿà¯à®Ÿà®°à¯ரானà¯à®¸à¯à®²à¯‡à¯ரானà¯à®¸à¯à®µà¯‡à®²à¯ராலிà¯ராவலà¯ராவெலà¯ரிமà¯à¯ரிலà¯à®²à®¿à®¯à®©à¯ரெணà¯à¯ரெயà¯à®²à®°à¯ரேà¯ரை செஞà¯à®šà¯ரை செயà¯à¯ரை பணà¯à¯ரையலà¯ரைலரீ¯à¨®àராீ¯à¨®àறாீ¯àµ®àலீ¯àµ®à¯àŸ®à¨®àலூ¯à•®àலூ¯à¯®à¿®à¨®àரானூ¯à°®àலெ¯àª®àரோெ¯à®®àரோே¯à•®àà®°à¯à¯‡¯à®®àலோ¯à¨®àலோ¯àª®àà®°à¯à¯‹¯à°®àலோ¯à°®à¯àŸ®à¨®àலà¯¯à£®à‡¯àª®àà¯¯à£®à¾®à•®àராகà¯à®Ÿà®°à¯¤®àரா௤®àறா௤®àல௾®à•®àல௾®à¨®àல௾®àª®àல௿®àµ®àà®°à¯à¯¿®à¹®àலரிரெயிலரŠ"$9à¯à®°à¯†à®¯à®¿லரிரிகொ"%1à¯à®°à®¿à®•à¯ிரிகà®°Š"%OOkிரிகà¯à®•à®°à¯à®°à®¿à®•à®°à¯à®°à®¿à®•à¯à®•ரிரஸà¯à®ŸŠ"kிரமà¯à®ªà¯†à®Ÿà¯Š"k?0$Šà¯à®°à®®à¯à®ªà¯†à®Ÿà¯ிரீடொ"nŠà¯à®°à¯€à®Ÿà¯ிரேயினைŠ"p92ிராகொ"t1à¯à®°à®¾à®•௅®àà¯à®°à®¾à®•à¯ிரானà¯ஸà¯à®ªà®°à®£à¯à®Ÿ Š"t2à¯à®°à®¾à®©à¯à®¸à¯à®ªà®¿à®°à®£à¯à®ŸŠ"t2W0%"k@Š“ிரானà¯à®¸à¯à®ªà®°Š"t2WQkà¯à®°à®¾à®©à¯à®¸à¯à®ªà®°ிராஃபிகொ"tQ%1ிராபிகà¯à¯à®°à®¾à®ƒà®ªà®¿à®•à¯à¯à®°à®¾à®ªà®¿à®•à¯ெகà¯னாலஜிŠ$1ெகà¯à®©à®¿à®•லŠ$12%1kெனà¯à®Ÿà¯à®²à¯à®•à®°Š$2Šx71kெலிபிரிணà¯à®Ÿà®°Š$7%0"%2ŠkெலிபதிŠ$7%0k/ெலிகீராமŠ$7%OெலிபோனŠ$7%Qெலஸà¯à®•ோபொ$7kW1u0ெமà¯à®ªோŠ$?0ெமà¯à®ªà®°Š$?0kெஸà¯à®ŸŠ$WŠ“à®¿à®•à¯¯à°®à†®àŠ%1ினெனà¯à®Ÿ¯à©®à¾®à•®àலŠ%2$2Škினெணà¯à®Ÿ¯à£®à¾®à•®àலŠ%2$@Škினà¯à®•ரிஙொ%21kிமெணà¯à®Ÿ¯à£®à†¯àš®àŠ%?$@Š“à®¿à®ªà®¿à®•à¯‡à®Ÿ¯à°®àš®àŠ%Q%OpŠ“à®¿à®ªனŠ%Qkொகொ'1à¯à®²à®¾à®£à¯à®Ÿ…®àŠ7t@Š“à¯à®µிடà¯à®Ÿà®°Š:à¯à®µிடà¯à®Ÿà®°ிவிஙà¯à®•ிளŠ:%B1à¯à®µà®¿à®™à¯à®•ிளà¯à®µà®¿à®™à¯à®•ிளà¯à®®à¯†à®£à¯à®Ÿ¯à£®à¿®à¯®à¾®àª®à¯àª®à…®àŠ?$@Š“‡¯àŸ®à¯à¸®àஸŠk¯à™®àன¯à£®à¯àµ®à•®à¯à©®àŽ®àà®°¯à£®à‡®àà®°à¯¯à£®àŒ¯à•®à¯à©®àŽ®àà®°¯à²®à¿®àª®àƒ®àà®°¯à·®à¯à¸®à¿®à©®à¾®àš®àரிஃபà¯கà¯கà¯à®•à®°சà¯à®šà®¿à®™à¯னலனà¯ப௠பà¯à®ªà¯†à®®à¯à®ªà¯à®²à®°à®®à¯à®ªà¯à®³à®°à®®à¯à®³à®°யரிலயரà¯யரà¯வரவலவà¯à®©‚¯à•®à¯à¸®àà®°‚¯à¯®à¿®à¨®àன¯à£®à†¯àš®àà®°¯à£®à†¯à®®àல¯à£®à¿®à°®à¯àª®àà®°¯à²®à†¯à·®àà®°¯à²®à¿®à®®àன²®à¿®à®®àரி¿®à²®à¿®à®®àரிரà¯à®ªà®¿¯à£®àŽ®àரைEŠk"0பà¯à®ªிலŠkEEசà¯à®šà®ªà¯ŠkJ k0ேகொp1ேஙà¯à®•à®°ŠpB1kாரà¯à®Ÿà®¿à®•¯à£®à…®àŠt"Š%1“ாபொt0ாபிகொt0%1ாகà¯à®¸à®¿Št1ாக௠ானிகொt2%1ாயà¯à®²à¯†à®Ÿà¯Št97$Šà®¾à®¯à¯à®²à®Ÿà¯Št97kŠà®¾à®™à¯à®•ிŠtB1ாஙà¯à®•à®°ŠtB1kாஸà¯à®Ÿà®¿à®•à¯¯à£®à†¯àª®àŠtWŠ%1ாடாŠtŠà¯‹à®°à®£à¯à®ŸோŠu"k@Šà¯‚தொy/ைபொ„0ைடிலŠ„Šà¯à®ŸBŠŠà¯à®ŸŠŠk‡¯à¯®à¿®àŸ®à€¯à®®à¯à°®àŸ®à¯à£®à‡®àŠ“¯à£®à†¯àœ®à¯à°®à…®à¯à£®à†¯à®®à€¯à°®à¯à•®à…®à¯à£®àœ®à¯à°®à…®à¯à£®à°®à†¯àª®à¯à¸®à¯à©®à¯à£®à°®àª®à¯à¸®à¯à©®à¯à²®à¾®àE…®à¯à£®à†¯à®®à•®à¯à£®à¯®àˆ¯à³®à¯à•®à¯à£®à·®à‡¯àª®à¯àª®àƒ®à¿®à·®à¯à°®à‹¯àª®à¯àª®à¿®à°®à¯à²®à¾®àµ®àB‹ீசலிராகà¯à®²à®¾à®¿ரிஙà¯à®•à¯à®¿ரெஸிரை ிரைவிரஸ‹"$ியூடி‹9–Š‹kீசணà¯à®Ÿ‹nWk@Š“à®¾à®•à¯à®Ÿà®°‹t1Škà¯à®Ÿ‡®àிலி‹‹à¯à®Ÿ†¯à°®àியாà¯à®Ÿ²®à‹‹“$B@@k%¯à•®àB/¯à£®à€¯àµ®àேவை¯à£®à€¯àµ®àொலà¯à®²à¯ˆ¯à¨®àš®à¾®àµ®àி¯à¨®à¯®à†¯àœ®àி¯àª®àB¯à¸®àBš®àà¯à®¯š®àà¯à®°à¯Ÿ®à¯àŸ®àš®àிடà¯à®Ÿ¤®àà¯à®°à¯‚ப²®à®®à‡¯à°®à¿®àª®àாµ®à¾®àª®à°®à¿®àª®àி¾®àœ®à¯àš®àா¾®àª®àà¯à®°à¯‚à®®¿®àš®àà¯à®°à®¾¿®à¨®àà¯à®¯¿®à©®à…®àா¿®à²®à²®àா¿®àµ®àª®àà¯à®°à®¾à¯à®±à¯ˆBாகà¯à®•ாதாகà¯à®•ாமாகà¯à®•ாவிடà¯à®Ÿà®¾ாசிலà¯à®¤à®¾à®°ானியஙà¯à®•ிிகà¯à®•௠மà¯à®•à¯à®•ிகà¯à®•௠வாயிகà¯à®•à¯à®®à¯à®•à¯à®•ாிலà¯à®²à¯ à®®à¯à®²à¯à®²à¯ீபà¯à®ªீரà¯à®•à¯à®•ூரத௠ூரதà¯à®¤à¯à®µூரதà¯à®¤à¯Šà®Ÿூரனூரலூரிகைூர௠ூரà¯à®¨à¯ூரà¯à®µேகà¯à®•ேசà¯à®šேவிடியா€¯à•®àா€¯àš®àா€¯àª®àš®àா‡¯à¨®àாஜி¯à¨®à•®à¯àš®àி¯à¨®àš®àµ®àி¯à¨®àœ®à®®àா¯à¨®à¯®à¯à·®à¯à¤®àி¯à¨®à¾®àš®àி¯à®®à¯à®®àாஜ¯à®®à®®àா¯à²®à¯àš®àான¯à²®à¯à®®àான•®àIஜா®®à¯àš®àி®®à‹¯à•®àி°®à¾®àª®à ¯à°®à¾®àš®à°®à¿®àª®àி°®à¿®àª®àீ²®àா²®àª®à¯à·®à¯àª®àாµ®à‡¯à°®àிµ®à¯à°®à¾®àª®àி¿®à¤®à‡¯àµ®à¿®à¨®àா¿®à¤®à‡¯àµ®à¿®à¨®àை¿®à©®à¯àš®àா¿®à©®àµ®àா¿®à©®à¿®àµ®àா¿®àª®àš®àா¿®à°®à¹®àாியாகியேடà¯à®Ÿà®°à®¿ராணிிரிலோகிரிலà¯à®¿ரிவேதிிரௌபதிà¯ரோணே®àயாதி௠தூ¯àš®à®®à¾®à•®àரெ¯àœ®àமலானிை¯à®®àரேய௿®à®®àà®°ிரிபாதி/"%0ிரிபோலிà¯à®°à®ªà®¤à®¿š®à/"k0k/%ிக‹¯àœ®àா/%1ிகà¯¯à°®à¾®à•®àியோபŽ®àிய/%9u0à¯à®¤¯àª®àிர//à¯à®¤Bà¯à®¤¾®àš®àிய à¯à®¤¾®àš®àியிரà¯à¯¿®àš®àரா//%à¯à®¤//kà¯à®•‡¯àª®à¯à®®à…®à/1“à¯à®¤à¯š®à‡¯à¤®àரோகி/Fˆ¯à³®à¯à³®à¿®àª®àன/k¯à•®à¯àª®à¯à³®à¾®àŸ®à¯àŸ®à¯à®®àன¯à¸®àà®°à¯à®®à®¿à®ŸŒ¯à•®àà®®Œ¯à•®àமி¯à²®à‡¯à®®àடà¯à®Ÿ¯à´®à€¯à•®àடà¯à®Ÿª®àஞà¯à®šà®²à®¿¯à¨®àš®àµ®à/“BFB Iனாாகà¯à®•ாாசாடிாடà¯à®šà®£à¯à®¯ாடà¯à®šà®¾à®¯ாதாானஙà¯ானதà¯ானபà¯ானமாானியானà¯à®µாமோதராம௠தூமாயாதிாரணிாரா சிகà¯à®•ோாரா சிஙà¯ாரா ஷிகோாராசà¯à®°ாராபà¯à®°ாராளாராவிாவணிாவாாவேயாஸிகமà¯à®ªà®°ிகிலிகà¯à®¤à®¿à®•à¯ிகà¯à®•ிலிகà¯à®•à¯ிகà¯à®•ெனிகà¯à®•ேிகà¯à®•ைிகà¯à®µà®¿à®œà®¯ிசைிடகாதà¯à®¤à®¿à®°ிடசிதà¯à®¤ிடபிடமிடீிடீரிடà¯à®•à¯ிடà¯à®¤à®¿à®Ÿà¯ிடà¯à®¤à®¿à®ªà¯ிடà¯à®®ிடà¯à®µà¯†ிணà¯à®Ÿà®¿à®µà®©ிணà¯à®Ÿà¯à®•à¯à®•லினகினஙà¯ினசரிினதà¯ினநà¯ினபà¯à®ªà®Ÿà®¿ினமினà¯à®šினேஷிபà¯à®¤à®¿à®ªà¯ிமà¯à®®ிரவிரவியிரௌபதிிலà¯à®²à®¾à®•ிலà¯à®²à®¿ிலà¯à®²à¯ ிவசிவாகரிவானிவாலிவà¯à®¯ிவà¯à®µà®¿à®¯ீகà¯à®·à®¿à®¤à®°ீடà¯à®šà®£à¯à®¯ீடà¯à®šà®¿à®¤ீடà¯à®šà¯ˆீபீரகà¯à®•ிழவீரசà¯ீரதà¯à®¤à¯à®Ÿீரனீரமிலà¯à®²ீரமà¯à®Ÿீரமà¯à®®à®¿à®•ீரரீரரைீரà¯à®•ீரà¯à®•à¯à®•மாà¯à®•à¯à®•à¯à®šà¯à®šà®®à¯à®šà¯à®šà®¾à®¤à®©à®©à¯à®Ÿà¯à®Ÿà¯à®ªà®¾à®¯à¯à®ªà®¾à®·à®¿à¯à®ªà¯à®ªà®Ÿà¯à®Ÿà®¾à¯à®®à®³à®¿à¯à®°à®¤à®¿à®°à¯à®·à¯à®Ÿà¯à®°à®¤à®¿à®°à¯à®·à¯à®Ÿà¯à®°à®¤à®¿à®·à¯à®Ÿà¯à®°à®¾à®šà¯ˆà¯à®°à®¿à®¯à¯‹à®¤à®©à®©à¯à®°à®¿à®¯à¯‹à®¤à®©à®¾à¯à®°à¯à®µà®™à¯à¯à®°à¯à®µà®¤à¯à¯à®°à¯à®µà®ªà¯à¯à®°à¯ˆà¯à®°à¯‹à®£à¯à®°à¯à¯à®·à¯ூசூசிூபூமூரூஷணைூஷிதà¯à®¤ெணà¯à®Ÿெயà¯à®µேகேசேவகானேவகிேவகà¯à®®à®¾à®°ேவகà¯à®°à¯ேவகà¯à®²ேவகà¯ேவசேனேவதூதேவதைேவநேயேவனேவராஜேவராடà¯à®Ÿà®¿ேவராணிேவராளேவரà¯à®²à®•ேவரà¯à®•ேவலோகேவஸà¯à®¤à®¾à®©ேவாதிேவாமிரà¯à®¤ேவாமà¯à®šேவாரேவாலயேவிேவேநà¯ைரியொனிொனà¯à®©à¯ˆொபதொபொபà¯à®•à¯ொபà¯à®ªà¯à®©ொபà¯à®ªà¯†ொமà¯ொளதொளொளவெோசைோஷோஸà¯à®¤à¯ோஹாà¯à®°à®¾à®Ÿà¯à®šà¯ˆà®¿யானிராடà¯à®šà¯ˆà®¿ராவிடà¯ரோகà¯வநà¯à®¤ à¯வேசà¯வேஷà¯à®¤à¯…®àவானà¯à®¤à¯¿®àµ®àவானிரà¯திராF"%ிரà¯à®·à¯à®Ÿà®¿à®¿à®²à®¿à®ªà¯F%7%0ிலீபà¯F%7n0ிகà¯à®ªà®¿ரமைF%OEிகà¯à®¤ிகà¯à®¯à¯†F%OFிடசஙà¯à®•லà¯à®ªF%‹kWkBOk70“à¯à®¤DிசைFFà¯à®¤Dினà¯à®¤Dà¯à®°à¯à®•à¯à®•à¯à®¤Dூசà¯à®¤Dெயà¯à®µà¯à®¤Dேசà¯à®¤Dேவதà¯à®¤Dேவனà¯à®¤Dேவரà¯à®¤¯àŸ®à¯àŸ®àŽ®àிகà¯à®•à¯à®¤¯àª®àிà¯à®¤¯àª®àியிà¯à®¤¯à®®àš®àிரà¯à®¤…®àாசிà¯à®¤…®àெயà¯à®µà¯à®¤ˆ¯àµ®àியà¯à®¤‰®àியோகà¯à®¤‰®àேசà¯à®¤‹¯à¯®à…®àிà¯à®¤®®àியà¯à®¤²®à¯à•®àெயà¯à®µà¯à®¤²®àª®àினஙà¯à¯à®¤²®à¿®àš®àினஙà¯à¯à®¤¾®àš®àியà¯à®¤¾®àµ®àியà¯à®¤¿®àš®àாரà¯à¯à®¤¿®àµ®àையாகà¯à®¤¿®àµ®àையால௠à¯à®¤¿®àµ®àையிà¯à®¤¿®àµ®àையைà¯à®¤¯à°®àிரà¯à®¤‚¯àš®àிரனà¯à®¤‚¯àš®àிரரிà¯à®¤‚¯àš®àிரரà¯à¯à®¤ˆ¯àµ®àி à¯à®¤ˆ¯àµ®àீஸà¯à®µà¯à®¤Œ¯à°®àிரà¯à®¤ª®à¯àš®àிரà¯à®¤ª®à‰®àிரà¯à®¤®®àிகà¯à®•à¯à¯à®¤¿®àµ®àைகளà¯à®¤¿®àµ®àைகà¯à®•ாகà¯à®¤¿®àµ®àைகà¯à®•à¯à¯à®¤¿®àµ®à ¯à²®à¿®àµ®àைà¯à®¤¿®àµ®à¯à²®à¿®àµ®àைà¯à®¤à®¿¿®à¤®à†®àராவிடà¯à®¤à¯œ®à¾®à°®àரோகà¯à®¤à¯•®à¯à®®àவாரà¯à®¤¯àª®àனFFkà¯à®¤¯àª®àà®°à¯à®¤¯à°®à…®àJாரà¯à®¤¯àŸ®à¯àŸ®à°®à¯à®®àடியனà¯à®¤¯àŸ®à¯àŸ®à°®à¯à®®àடியரà¯à®¤ˆ¯à±®à¿®àš®àணà¯à®Ÿà®©à¯ˆà¯à®¤¯à°®àµ®àமானà¯à®¤à¯€à®šà¯ˆ¯àµ®àவFFnWà¯à®¤à®¾à®¨à¯à®¤¿®àš®àFFt2/“à¯à®¤à®¾à®š¯à°®à¿®àµ®àலFFtJkà¯à®¤¯à¯®àFF“à¯à®¤¯à°®à¾®à°®à¯à¸®àà¯à®¤¯à°®à¾®à°®à¿®àš®àà¯à®µாதசிFRà¯à®µாரà¯à®µைததà¯à®¤à¯à®µà®¾à®ªà®°FRt0kà¯à®µà¯ˆà®¤ FR„/kà¯à®µà¯ˆà®¤தà¯à®¤à®¿à®²à¯à®µà¯ˆà®¤à®®FkEாவதாரகதககனகிகà¯à®•à¯à®·à®¿à®£கà¯à®·à®¿à®£கà¯à®·à®¿à®£à®¾சகணà¯à®Ÿசமிசரதசரதரசராசாபà¯à®¤சைடதடடபà¯à®Ÿà®²டவெடவைடாலடி பயலடி பà¯à®¤à¯à®¤à®•டி மாடடிகà¯à®•ாமடிகà¯à®•à¯à®®டிதà¯à®¤டிபà¯டிமனடிமாடடியனடியரடியானடà¯à®šà®šà¯€à®²டà¯à®šà®©டà¯à®šà®¿à®£ணà¯à®Ÿà®•à¯ணà¯à®Ÿà®¤à¯ணà¯à®Ÿà®©ணà¯à®Ÿà®ªà®¾à®£à®¿ணà¯à®Ÿà®®ணà¯à®Ÿà®¾à®¯à¯à®¤à®ªà®¾à®£à®¿ணà¯à®Ÿà®¿à®•à¯à®•ணà¯à®Ÿà®¿à®¤à¯ணà¯à®Ÿà®¿à®ªà¯à®ªணà¯à®Ÿà®¿à®ªà¯à®ªà®¾ணà¯à®Ÿà®¿à®¯à¯à®™à¯à®•ளணà¯à®Ÿà¯‹à®°à®¾னகோடினசேகரனனனà¯à®œà¯†à®¯à®©னபாலனராசனராஜனலகà¯à®·à¯à®®à®¿னலடà¯à®šà¯à®®à®¿னவநà¯à®¤னà¯à®·னà¯à®®à®¨à¯à®¤à®¿à®°à®¿னà¯à®°à®¾à®œனà¯à®µà®¨à¯à®¤à®°à®¿மயநà¯à®¤à®¿à®®à¯à®ªà®¤à®¿à®®à¯à®ªà®¿à®Ÿà®¿யவயாணநà¯à®¤யாலயாளயைரணிராவியரிசனஙà¯ரிசனதà¯ரிசிரிதà¯à®¤à®¿à®°à®®à®°à¯à®®à®™à¯à®°à¯à®®à®šà¯à®°à¯à®®à®¤à¯à®°à¯à®®à®©à®°à¯à®®à®ªà¯à®°à®°à¯à®®à®ªà¯à®°à¯à®®à®®à®°à¯à®®à®°à®°à¯à®®à®¿à®°à¯à®•ாà®°à¯à®ªà®¾à®°à®°à¯à®ªà¯‚சà®°à¯à®ªà¯ˆà®°à¯à®®லிதà¯வகà¯à®•ாலவகà¯à®•ோலவதà¯à®¤வபà¯வமரà¯à®®à®ªாலFk"(?kEà®°à¯à®®à®ªà¯à®°à®¿Fk"x?k0பதபFkEkFkE“தà¯à®¤ியாFkFFà®°à¯à®•à¯à®•ாFkOOவà¯à®²à®¤à®¾à®ªாதFkRx7kFtEீரà¯à®•à¯à®•தரிசFn"OOkீரà¯à®•à¯à®•மிீரà¯à®•à¯à®•ம௠ௌலதாபாதF…7k‹tE)B2ியாயியூ2k*B22k+¯àª®à¯à´®à¿®à®®à¤®àாஷ Eின௠0ினà¯à®¨à®¾à®²à¯à®®à¯ ினà¯à®©à®°à¯ ினà¯à®©à®¾à®²à¯ €¯à©®àா€¯à°®àா¯àŸ®àˆ®àாட¯àŸ®à¯à£®à•®àிடி¯à¤®à¯à´®àŠ¯àª®àோக௯௮ྮ൮àà¯à®¤à¯à®¤à®¿à®°¯à°®à‡®àால¯à°®à’®àாத¯à°®à’®àால¯à°®à’®àேசà¯à®š¯à±®à¿®àš®àிளà¯à®³à¯ˆˆ¯à²®à…®àேசிˆ¯à²®àŠ¯à¤®àேசி‰®àாசனை¯à£®à€¯àµ®àாவ¯à£®à€¯àµ®àேசà¯à®š¯à£®à€¯àµ®àொழà¯à®¤¯à£®à†®àால¯à£®à†®àிளà¯à®³à¯ˆ¯à£®à†¯àª®àிளà¯à®³à¯ˆ¯à£®à•®àாரà¯à®µà¯ˆ¯à£®à®®àà¯à®´à¯¯à©®àŸ®à‰®àிற¯à©®à¤®àDால¯à©®à®®àš®àாட¯à©®à°®à¯à®®àாட¯àª®àB¯à®®à…®àையர¯à®®à‡®àோசிஷன¯à®®à®àா ¯à®®àŸ®à‡®àெயர¯à®®à³®à‡®àெண௯மྮమàூர¯à¯®à‡¯à¤®àிறை¯à°®à³®àµ®àிறை¯à°®à¿®à¤®àŽ®àார¯à°®à¿®à®®à¿®à¤®àிடி¯à²®àµ®à¾®à°®àிணà¯à®Ÿà®¿¯à¸®à¯à©®à‡®àெகà¯à®Ÿà®°’®àினியன•®àாš®à¯àž®àª®àாணà¯à®Ÿœ®à¾®à°®à‡®àாளையŸ®à…®àாவŸ®à¯à£®à¤®àாணி¤®àா®®àா®®àா¾®à•®àா¾®àš®àா¾®à¤®àா¾®à¤®à¾®àµ®àி¾®à®®àா¿®à•®à¯à•®à¿®àµ®àீடியா¿®àŸ®à…®àாவி¿®à©®àா¿®à©®à¯à•®à…®àà¯à®¤à¯à®¤à®¿à®°¿®à©®à¿®à•®à¯à•®à…®àà¯à®¤à¯à®¤à®¿à®°¿®à²®à¯à²®à¿®àµ®àà¯à®¤à¯à®¤à¯‚à®°¿®à²®àŸ®à¾®àª®àà¯à®¤à¯à®¤à®¿à®°¿®à´®àŠ¯à®®àெயரà¯ாணà¯à®Ÿà®¿ிறக௠ிளà¯à®³à¯ˆà¯à®°à¯à®±ூசà¯à®šà®¿ூரெரà¯à®®à®¾à®©ெறேரில௠ேர௠ொழà¯à®¤à®¿à®²à®¾ ொழà¯à®¤à®¿à®²à¯à®®à¯ ொழà¯à®¤à®¿à®²à¯ ொழà¯à®¤à®¿à®²à¯à®²à®¾à®®à®²à¯ ொழà¯à®¤à¯ ொழà¯à®¤à¯à®®à¯ ோக ோகவிலà¯à®²à¯ˆ ோகினà¯à®±ோகிறோகà¯à®®à¯ ோதிலà¯à®®à¯‡ ோதிலà¯à®®à¯ ோத௠ோதà¯à®®à¯ ோதà¯à®®à¯ ோதெலà¯à®²à®¾à®®à¯ ோதே ோன ோனாோனà¯à®± ோயிரà¯ோயà¯ோல ோலக௠ோலச௠ோலத௠ோலப௠ோலவà¯à®®à¯ ோலவே ோலà¯à®®à¯ ோல௠ோவதBாசà¯à®°ாதிகà¯à®•ணà¯ாதிகà¯à®•ாலாதிகà¯à®•௠ாதிகà¯à®•à¯à®®à¯ கà¯à®±à¯ˆாதிகà¯à®•à¯à®®à¯ மேறà¯ாதிகà¯à®•à¯à®®à¯ மேறà¯à®ªà®Ÿà¯à®Ÿ ாதிகà¯à®•à¯à®®à¯ மேலாதிபà¯à®ªà¯‡à®°ாரமà¯à®ªà®°à®¿à®¯ாலகà¯ாலகà¯à®•ாடாலாபிஷேகாலினà¯ாலà¯à®Ÿà®©à¯ாலà¯à®®à¯ ாலைாலà¯ீடிகைீடிதà¯à®¤ொமà¯à®®à®©à®¾à®Ÿà¯à®Ÿà®¿ ¯àŸ®à†®àாமà¯à®ªà¯‡ ¯àŸ®à¾®à¯®àˆ¯à³®à¿®àµ®àாமà¯à®ªà¯‡€¯àŸ®àாயீ¯à¤®àா¯àŸ®à¿®àµ®à¤®àொடி¯à±®à‡¯àµ®àாட¯à±®à®®àாத¯à±®à®®àிற¯à±®à®®àேசà¯à®š‚¯àª®àாளம௠‡¯àŸ®àே¯à¨®àாளˆ¯à•®àேசி¯à•®à¿®àª®àாகà¯à®• ¯à£®à€¯àµ®àோகà¯à®•¯à£®à†¯àª®àால¯à©®à¯à®®àின௠¯à©®à†¯à¤®àெணà¯à®£à¯ˆ¯à©®à†¯à®®àொர௯੮൮àொர௯மà¯à¤®à‹¯àª®àா¯à®®à‡¯à°®à¤®àா ¯à®®à‡¯à°®àµ®àா ¯à®®à‡¯à±®à‹¯àª®àா ¯à®®à•®àாலா¯à®®à•®àெனி¯à®®à•®àோஸ¯à®®à¤®à¯à¤®àš®àோட¯à®®à²®àூர¯à®®à²®à¯àª®àெயர¯à®®à²®à¾®à²®à‹¯à•®àூர¯à®®à´®àª®àொரà¯à®³¯à®®à¾®à•®àோசிஷன¯à®®à¾®àŸ®à¯à£®à‡¯àµ®àா¯à®®à¾®à²®à‹¯àª®àா¯à®®à¿®àš®àிள¯à®®à¿®à¤®àà¯¯à²®à†¯àš®àேசி¯à²®àŠ¯à¤®àொரà¯à®³¯à²®à•®àாகà¯à®•¯à²®à¿®àš®àா¯à²®à¿®à·®àா¯à´®à¾®à¯®àாணš®à¯àž®àª®àாதà¯à®¤à®¿à®°œ®à¾®à°®àாளையŸ®à¯àŸ®àª®àாடà¯à®ŸŸ®à¯àŸ®à¿®àµ®àாடாகŸ®àµ®àெணà¯à®£à¯ˆ®®à¯à°®à¤®àà¯à®°à®¿¯®à¿®à²®à•®àெரà¯à®®à®¾à®³°®à€¯àµ®àெரà¯à®®à®¾à®³°®à¾®à®®à¯à•®àாளைய°®à¿®à•®à¯à•®àš®àாணி²®àª®àேர²®à¿®àš®àேரµ®à¨®àாஷ¾®à©®à¯à©®à•®àினà¯à®©à®¾¿®àš®à¯à©®à¿®à°®à¯àª®àால¿®à°®àš®àார¿®à´®àµ®àாடி‹¯à°®à®àளேனி¯àª®à¯àš®à°®à…®àரதிநிதிி¯àª®àœ®à¾®à°®àரதிநிதிி¯àª®à¤®à¯à¨®àDரளயி¯àª®à¤®à¯à¨®àDராயி¯àª®à©®àœ®à‹¯àª®àரியரி¯à·®à¯à¤®àரயோகிரதிராயிரகலாதனிரகாசிரகாரிரகà¯à®žà¯ˆà®¿ரசஙà¯à®¿ரசனà¯à®¨à®¿ரசனà¯à®©à®¿ரசவிரசாதிரசாநà¯à®¤à®¿à®¿ரசிதà¯à®¤à®¿ரசிதà¯à®¤à®¿à®¿ரசà¯à®°à®¿ரசà¯à®šà®©à¯ˆà®¿ரசà¯à®šà®¾à®°à®¿ரசà¯à®šà®¿à®©à¯ˆà®¿ரஜிரணவிரதமிரதீிரதேசிரபிரமாணிரமாதிரமானிà®°à®®à¯à®•ரிரமோஷனிரயதà¯à®¤à®©à®¿ரயாிரயோகிரயோசனிரயோஜனிரலயிரளயிரவாகிரவீணிரவீனிரவேசிரவேசிிà®°à®·à¯à®Ÿà®¿ரஸாதிரஸà¯à®¤à®¾à®¿ரஹலாதிராகாரிராகிரà¯à®¤à®¿ராண ிராணதà¯à®¿ராணனிராணிிராணà¯à®Ÿà®¿ராதிதà¯à®¿ராநà¯à®¤à®¿à®¯à®™à¯à®¿ராநà¯à®¤à®¿à®¯à®¤à¯à®¿ராநà¯à®¤à®¿à®¯à®®à¯ ிராபà¯à®¿ராமிஸிராரà¯à®¤à®©à®¿ராரà¯à®¤à®¿à®¿ராரà¯à®¤à¯à®¤à®¿ரிடà¯à®Ÿà¯‹à®°à®¿à®¯à®¿ரிமியிரியதரிரியனிரியபà¯à®ªà®Ÿà®¿ரியமிரியரிரியா ிரியாவிடமிரியாவினிரியாவà¯à®¿ரியாவைிரேிரோகிதரிளஸிளஸ௠ிளாிளாடà¯à®ªà®¾à®°à®¿ளீஸிளேி¯àª®à©®à¾®à¤®àரபி¯àª®à®®à¯à°®à¤®àரபி¯àª®à°®àµ®àà®°Eாதி¯àª®à¾®àG®®àரபà¯ரோகிதà¯ளà¯à®Ÿà¯‹à®©à®¿à®¯à¯‹¯à°®à®àளேனà¯¯à®®à‡®àரெஸ௠பà¯பà¯ஸà¯¯àš®àரீமோ¯àª®àà¯¯à®®à•®àரெஸ௕®à¾®à²®à௾®àŸ®à¯à•®à¯à¸®à†¯àŸ®à௾®à®®àளிரினà¯à®šà®¿à®ªால0"%2W%0ிரியஙà¯à®•ா0"%9kB1ிரிணà¯à®Ÿà®°0"%@Škிரிடோரிய0"%Šà¯à®°à®ƒà®ªEà®°0"'Qkà¯à®°à®ªEà®°à¯à®°à®ªà¯Šசரà¯à®°à¯Šà®ªசரà¯à®°à¯Šà®ªà¯Šசரà¯à®°à®ªà¯Šசரà¯à®°à¯Šà®ªசரà¯à®°à¯Šà®ªà¯Šசரிரகாஷ0"k1ிரக¯àª®à©®à¾®àž®àாிரக©®à¾®àž®àாிரச¯àª®à¤®à®®àார0"kJிரசாரிரசà¯à®©à¯ˆà®¿à®°à®¾à®•à¯à®Ÿà®¿à®•ல0"t1Š%1kà¯à®°à¯‹à®Ÿான0"u/à¯à®°à¯‹à®Ÿான0"uŠà®¿à®°à¯ˆà®µà¯‡à®Ÿ0"„RpŠ“à¯†à®£à¯à®Ÿ¯à°®à¾®à•®àà®°0$@Škெஞà¯à®šா 0$AIெஞà¯à®šாலà¯à®®à®¿à®Ÿ¾®à•®àல0%Škà¯à®¤à¯த பà¯à®¤ 0(/à¯à®¤à¯à®¤க0(//kà¯à®¤à¯à®¤ம௠பà¯à®¤à®¿à®¯à¯à®¤à¯à®¤ம௠பà¯à®¤à¯à¯à®¤à¯à®¤ரிசிà¯à®¤à¯à®¤à®®à¯à®ªà¯à®¤0(//k?0à¯à®ªà®¿Dரவாக00à¯à®ªà®¿•®à…®àரவாகà¯à®ªà®¿•®à¿®à¤®à…®àரசஙà¯à®•à¯à®ªà®¿š®à‡¯à¤®àà®°à®·à¯à®Ÿà¯à®ªà®¿¤®à¯à¤®à°®à‡®àரவாகà¯à®ªà®¿¤®à¯à¤®à°®àரவாகà¯à®ªà®¿©®à®®àரவாகà¯à®ªà®¿²®àœ®àரவாகà¯à®ªà®¿²®à¿®à¨®àரபà¯à¯à®ªà®¿µ®à¤®à¾®à¯®àரகாசà¯à®ªà®¿µ®à¿®àš®àரகாà¯à®ªà®¿¿®àK’®àரவாகà¯à®ªà®¿¿®à£®à®®àரவாà¯à®ªà®¿¿®à¤®à¨®àரவாகà¯à®•¾®àª®àாரà¯à®©01à¯à®¯à¯‚ட¯à®®à•®àà®°09–Škà¯à®ªà®¿°®àª®àà®°à®®à¯à®®0Eடà¯à®š 0k€¯à©®à€¯à°®à¯à©®à…®àமா¯à°®à¿®à¨®àமா†®àரேசன†®àரேஷனˆ¯à¤®àª®àதை‰®àநà¯à®¨à®¿à®¯à®¾à®š‹¯à¯®à¿®à®®àதி‹¯à²®à…®àதிŒ¯à°®à¿®à¤®àதி¯à£®à€¯àµ®àழி¯à©®à¯à®®àகல¯à©®à†¯à¤®àகà¯à®¤à®¿¯à©®à¨®àகல¯à©®à¿®àª®àகல¯à©®à¿®à®®àதிபà¯à®ª ¯àª®à¯à®®à°®à•®àட¯à®®à°®à•®àà®±à¯¯à²®à…®àதà¯¯à²®à…®àà®®¯à²®à•®àனா“®àன•®àŸ®àµ®àகà¯à®¤à®¿Ÿ®àµ®àà®´¤®à®®à®®à°®à€¯àµ®àதà¯à®¤à®¿à®©à®¿°®à€¯àµ®àராகà¯à®•ிரம°®à¿®àŸ®à¯à·®à¾®à°®à‡®àதி¾®à•®à¾®à¤®à¾®à®®à¿®àŸ®à…®àணி¿®à©®àகà¯à®•டடிà®±à¯à®±à®¿ டà¯à®Ÿà®© யதà¯à®¤ யதà¯à®¤à®žà¯யதà¯à®¤à®®à¯ யபà¯à®ªà®¤யபà¯à®ªà®µà¯ˆ Oநà¯à®¤à®™à¯à®•ள Oநà¯à®¤à®¤à¯ Oநà¯à®¤à®®¯à•®à¯àª®àதிகை¯àŸ®à‚¯à®®àலà¯à®²à®•à¯¯àŸ®àŠ®àயிர¯à±®à®®àரிசீலனை¯à©®à¯à®®àதிவ¯à©®à¯®àª®à¯à©®à¿®à¤®àணà¯à®Ÿ¯à®®à•®àனி¯à®®àª®àர௠¯à°®à¾®à•®àரேஷன¯à²®à•®àதரà¯¯à²®à¾®à•®àநà¯à®¤š®à¾®à²®àˆ¯à•®àதி°®à¿®àŸ®à¯à·®à¾®à°®àதிµ®à¿®àš®àத¾®àµ®àஸ¿®àš®à¿®à©®à¯à®®àல¿®à²®à’®àரப௿®à³®à’®àரபà¯த¯àš®àª®àி0k/த¾®àœ®à°®à¿®àª®àிதி¯à•®à°®à0k/%தி¯à¤®à‡¯àš®àதி¯à¸®à•®à°®à¿®àª®àதிœ®à•®àதிŸ®à¯à•®à®®àதிŸ®à•®à¯à™®à‡¯àµ®àதி£®à•®àதி¾®à•®à¿®àª®à¯à®®à…®àதி¾®à¤®à€¯àš®àதி¾®à¯®àˆ¯à³®àµ®àதி¾®à¯®à¯à¤®à¿®àµ®àதி¿®à£®à°®à¤®àதி¿®à®®à¯à·®à¯à•®à²®àபா0k0பà¯¯à²®à…®àப0k0kாரà¯à®®à¯†à®£à¯à®Ÿ…®à0t"?$2Š“à®¾à®ªா0t0ாப0t0kாயிணà¯à®Ÿà¯à®®à¯†à®£à¯à®Ÿ…®à0t9%@Š?$2Š“ாபà®™à¯0tEkாபதà¯à®¾à®ªமாபவிமோசன0tEkR%?uJkோரà¯à®Ÿ¯à°®à®à0u"Š“à¯à®Ÿ0Š“C0“¯à®®à¿®à²®à’®à¯à°®àŸ®à‡®à¯à²®à…®à ¯à²®à•®à¯à™®àš®à€¯à¤®à°®à¿®àª®à¯à²®àŠ¯àš®à¯à²®à•®à¿®àµ®à . ¿®àª®àி . சிE ¯à¤®à¯à¨®à¯à°®à¿®à²®à¿®à¤®à¯à¤®à•®à¯à®®àாவ ¯à¤®à¯à¨®à¯à°®à¿®à²®à¿®à³®à•®à¯à™®à•®à¯à®®àாவ ¯à©®à¿®à³®à•®à¯à™®à•®à¯à®®àாவ ¤®à¯à¨®à¯à°®à¿®à²®à¿®à¤®à¯à¤®à•®à¯à®®àாவ ¤®à¯à¨®à¯à°®à¿®à²®à¿®à³®à•®à¯à™®à•®à¯à®®àாவ ¯®àˆ¯àŸ®à¯à©®à¿®à¤®à¯à¤®à•®à¯à®®àாவ ¯®àˆ¯àŸ®à¯à©®à¿®à³®à•®à¯à™®à•®à¯à®®àாவ…®àூரà¯à®µ¯à©®à…®àினà¯¯à©®à‡®àà¯à®±¯àª®à¿®à°®à¿®à¤®à‰®àாக¯à®®àBட¯à®®àா¯à®®àின௠¯à®®àà¯à®°à®¾¯à®®àூர¯à®®à¿®à¤®à¯à¤®à…®àேர௯మàின௠¯à±®à¤®à¯à®®àாக¯à±®à¯®à‡®àியல¯à·®à¯à•®à௕®à¯à®®àாவ•®à¯à•®àDாலி¤®àB®®àB®®à¾®à°®àாண¾®à•®à¯à™®à°®à”®àாத¾®à•®à¯à™®à°®à³®à’®àாத¾®à•®à®®àாரத¾®à¤®à¯à¨®à¿®àœ®àாத௾®à¤®à®®àG…®àாத¾®à¤®à®®à†®àாதBB Hலராகஙà¯à®•ாகதாகபà¯ாகமாகவதராகீரதிாகà¯à®•ிகà¯ாகà¯à®•ியாகà¯à®¯ாகà¯à®¸ாஙà¯à®•ிலாஙà¯à®•à¯ாசà¯ாடி பிலà¯à®Ÿà®¿à®™à¯ாடிகà¯à®•à¯ாடியைாடà¯à®Ÿà®²à®¿à®¯à®©ாடà¯à®Ÿà®¿à®²à®¿ாடà¯à®Ÿà®¿à®²à¯à®•à¯ாடà¯à®Ÿà®¿à®²à¯à®Ÿà®©ாடà¯à®Ÿà®¿à®²à¯ˆாடà¯à®Ÿà®¿à®²à¯à®•ளாணஙà¯ாணமà¯ாணிாதிகà¯à®•கà¯à®•ூடாதிகà¯à®•பà¯à®ªà®Ÿாதிகà¯à®•பà¯à®ªà®Ÿாதிகà¯à®•லாமாதிகà¯à®•வாாதிகà¯à®•விலà¯ாதிகà¯à®•à¯à®®à®¾à®©ாதிகà¯à®•à¯à®®à®¾à®µாதிகà¯à®•à¯à®®à¯†ாதிதà¯à®¤ாதிபà¯à®ªà®Ÿà¯ˆà®•ிாதிபà¯à®ªà®Ÿà¯ˆà®¯à¯à®®à¯†ாதிபà¯à®ªà®Ÿà¯ˆà®µாதிபà¯à®ªà®¤à®¾ாதிபà¯à®ªà®¤à¯ˆாதிபà¯à®ªà®¿à®©à®¾à®²ாதிபà¯à®ªà®¿à®±à¯à®•ாதிபà¯à®ªà®¿à®²ாதிபà¯à®ªà¯à®•à¯ாதிபà¯à®ªà¯à®®ாதிபà¯à®ªà¯ˆாதà¯à®·à®¾ாதà¯à®¯à®¤à¯ˆாதà¯à®°à¯‚à®®ானஙà¯à®•ளானதà¯à®¤ானமà¯ானà¯ானெடà¯ாபிலோனியாாபà¯à®µாமாவாமினிாமà¯à®ªà¯‡ாரதாரதிாரதà¯à®¤ாரமாரவிாராமà¯à®²à¯à®²à®¾ாரிஸà¯à®Ÿà®°ாரà¯Eலோனாாரà¯à®•வாரà¯à®Ÿà®°ாலகாலசாலதணà¯ாலனாலமà¯à®°ாலயà¯à®¯à®¾ாலாஜிாலாமà¯à®ªà®¿à®•ாலாவாலியதà¯à®¤ாலிவà¯à®Ÿà¯ாலà¯à®šà®¾à®®à®¿ாலà¯à®µால௠தாகà¯à®•ரோலà¯à®¯ாவனாாவனைாவிகà¯à®•பà¯à®ªà®Ÿாவிகà¯à®•ினà¯à®±ாவிகà¯à®•ிறாவிகà¯à®•à¯à®®à¯à®ªà¯‹à®¤ாவிதà¯à®¤ாவிபà¯à®ªà®¤ாவிபà¯à®ªà®¤à®¾ாவிபà¯à®ªà®¤à®¿ாவிபà¯à®ªà®¤à¯ாவேயாஷாகà¯à®•ளாஷாவாஷைாஷà¯à®¯ாஸà¯à®•à®°ாஸà¯à®•ிாஸà¯à®Ÿà®©ாஸà¯à®®à®¤à®¿ி . பி . சிிகிலிகà¯à®•à¯ிகà¯à®·à¯ிகà¯à®·à¯‚ிசினஸிசியிஜிலிிடà¯à®šà¯ிடà¯à®Ÿà®Ÿà®¿ினாமிின௠லேடனிபிசிிமà¯à®ªிரகதீிரகஸà¯à®ªà®¤à®¿ிரமà¯à®®ிரமà¯à®®à¯ˆிரிதà¯à®¤à®¾à®©à®¿ிரியாணிிரà¯à®•ணà¯à®Ÿà®¿ிரà¯à®•நளிலாஸà¯à®ªà¯‚à®°ிலà¯à®Ÿà®ªà¯ிலà¯à®Ÿà®¿à®™à¯ிலà¯à®²à®¿à®¯à®©ிஸினஸிஸியிஸà¯à®•டà¯ிஸà¯à®•ெடà¯ிஸà¯à®•ோதà¯ிஸà¯à®®à®¾à®°à¯à®•à¯ிஸà¯à®®à®¿à®²à¯à®²à®¾ிஸà¯à®²à®°à®¿ிஸà¯à®µà®¾à®¸ீகாரீசà¯à®šà®¿à®²ீசà¯à®šà¯à®•à¯à®•ீசà¯à®šà¯à®²ீஜீஜிஙீடாகà¯à®•ீடாவீடிகளீடிகà¯à®•டைீடிபà¯à®ªà¯à®•ைீடியீதà¯à®¤à¯‹à®µà®©ீனà¯à®¸ீபà¯à®ªà¯Šà®²à®¿ீமீரஙà¯à®•ிீராமணரீரைீரோீரà¯à®ªà®¾à®²ீஹாரà¯à®•à¯à®•ிஙà¯à¯à®•à¯à®•ிலà¯à®•à¯à®•ெனà¯à®±à¯à®•à¯à®•ைà¯à®•à¯à®¤à®¿à¯à®•à¯à®²à¯à®œà¯à®Ÿà¯à®Ÿà®¿à¯à®¤à®©à¯à®¤à¯à®¤à®¿à®•à¯à¯à®¤à¯à®¤à®¿à®šà®¾à®²à®¿à¯à®¤à¯à®¤à®¿à®¯à¯à®°à¯à®Ÿà®¾à¯à®°à¯‹à®•à¯à®•à®°à¯à®²à¯à®Ÿà¯‹à®šà®°à¯à®²à¯à®²à®Ÿà¯à¯à®²à¯à®²à®¾à®•à¯à®•à¯à®µà®©à¯à®¸à¯à®µà®¾à®©à¯à®¸à¯à®¸à¯†ூகமà¯à®ªூகோலூசà¯à®šà®¾à®£à¯à®Ÿà®¿ூடà¯à®¸ூதகணஙà¯à®•ூதஙà¯ூததà¯ூதபாணà¯à®Ÿà®¿à®¯ூதமூதவà¯à®Ÿà®®à¯à®ªூதாகாரூதானூதேவிூதà¯à®¤à®¿à®²ூதà¯à®¤à¯à®•ளூதà¯à®¤à¯à®•à¯à®•ாூதà¯à®¤à¯à®•à¯à®•ிடà¯à®Ÿூதà¯à®¤à¯à®•à¯à®•à¯à®ªà¯ூதà¯à®¤à¯ˆூபாளூமதà¯à®¤à®¿à®¯ூமாதாூமாதேவிூமிூரà¯à®·ூலோகூஷனெஙà¯à®•ளூரெஙà¯à®•ாலெஞà¯à®šà®®à®¿à®©ெடà¯à®°à¯‚à®®ெனசீரெரà¯à®©à®¾à®Ÿà¯à®·à®¾ெரà¯à®©à®¾à®°à¯à®Ÿெரà¯à®®à¯à®Ÿà®¾ெரà¯à®²à®¿à®™ெரà¯à®²à®¿à®©ெலà¯ெளதà¯à®¤ெஸà¯à®Ÿà¯ேகதà¯ேகமேகà¯à®•ரிேஙà¯à®•à¯ேசà¯à®šà®²à®°ேசà¯à®šà®¿à®²à®°ேசà¯à®šà¯à®²à®°ேஜாரேடà¯à®Ÿà®°à®¿ேடà¯à®Ÿà®¾ேடà¯à®Ÿà®¿à®™à¯ேதஙà¯ேதமிேதமà¯ேதலிதà¯à®¤ேதிேனரேபிேமானிேலனà¯à®¸ேலà¯ேஷாைகà¯à®•à¯à®•ளைசனைணà¯à®Ÿைனாகைனாமிைபிளைரவொமà¯à®®à®©ொமà¯à®®à®²ொமà¯à®®à¯ˆோஃபோரà¯ோக Nோகஙà¯à®•ோகதà¯à®¤ோகதà¯à®¤à®¿à®±à¯à®•ோகதà¯à®¤à®¿à®²ோகதà¯à®¤à¯à®•à¯à®•ோகதà¯à®¤à¯ˆோகரோகிதà¯ோகிபà¯ோகியோஜோணà¯à®Ÿà®¿ோதகனோதகரோதனோதிகà¯à®•ோதிசதà¯à®µோதிதரà¯à®®ோதிதà¯ோதிபà¯à®ªோதியிோதியைோதைோனியாகோனà¯à®¸à¯à®²à¯‡ோரடிகà¯à®•ாமலாோரடிகà¯à®•à¯à®¤ோரடிகà¯à®•à¯à®®ோரà¯à®®à¯ அடிோர௠அடிோரà¯à®¤à®¾à®©à¯ அடிோரà¯à®µà¯†à®²à¯ோஷிோஸிடௌதிகௌதà¯à®¤ௌலிங௠Mாடà¯à®Ÿà®¿à®² ¯àŸ®à†¯àŸ®àாடி ¯à©®à¿®à¤®à¯à¤®à•®à¯à®®àாவ ¯à©®à¿®à¤®à¯à¤®à•®à¾®à°®àாவ ¯à©®à¿®à³®à•®à¯à™®à•®à¾®à°®àாவ ¯à®®à‚¯à°®àாய ¯à°®à€¯àš®à©®à†¯àª®àà¯à®Ÿà¯à®Ÿà¯‹ •®à¯à®®àாவ •®à‡¯à¨®à¿®àš®àாவ •®à‡¯à©®à¿®àš®àாவ •®à¾®à°®àாவ ¤®à¯à¨®à¾®àš®àாவ ¯®à‡¯à¨®àாவ °®à¤®à‹¯à•®àš®àாவ °®à¿®à¤®à¯à¨®àš®àோஸ…®àின௠¯à£®àª®àின௯੮à¯à¤®àà¯à®±¯à©®à…®àà¯à®Ÿ¯àª®à¿®à³®à†¯àµ®àாக¯à°®à¾®à®®àà¯à®Ÿ¯à°®à¾®à®®àோட¯à¸®à†¯à²®àியன•®àாடபà¯à®° •®àால¤®àால®®àš®àாக°®à®®àின௰®à®®àà¯à®°à®¿à®®à¯ˆµ®à¿®àš®àாலன¾®à•®àாலி¾®à°®àின௠ி†®àரகாமி†®àரஹாமி¯à£®à€¯àµ®àரமைி¯àª®à¤®à¯à¤®à¿®àš®àரமைி¯àª®à©®à®®àராநà¯à®¤à®¿à®¿¯àª®à¯®àª®àராநà¯à®¤à®¿à®¿யூனஸ௠ிரகதீிரகஸà¯à®ªà®¤à®¿à®¿ரசலà¯à®¸à®¿ரதர௠ிரதர௠ிரமாணà¯à®Ÿà®¿ரமிகà¯à®•ிரமிதà¯à®¿ரமிபà¯à®ªà®¿ரமைிà®°à®®à¯à®®à®¿à®°à®®à¯à®®à®©à®¿à®°à®®à¯à®®à¯ˆà®¿ரவà¯à®šà®¿à®°à®·à¯à®¿ரஸலà¯à®¸à®¿ராகà¯à®•ளிராடà¯à®µà¯‡à®¿ராணà¯à®Ÿà¯ ிராதà¯à®¤à®²à®¿ராநà¯à®¤à®¿ ிராநà¯à®¤à®¿à®¯à¯à®¿ராநà¯à®¤à®¿à®¯à¯ˆà®¿ரானà¯à®¤à®¿ ிராமணிராமணனிராமிிராமிகà¯à®¿ராமின௠ிராவிராவினிராவிறà¯à®¿ராவிலிராவà¯à®•à¯à®•à¯à®¿ராவைிரிகேடிரிடிரிதà¯à®¤à®¾à®©à®¿à®¿ரிஸà¯à®Ÿà®²à®¿à®°à¯à®•à¯à®¿ரெடà¯à®¿ரெயிலிரெயà¯à®²à®¿ரேகà¯à®•ிரேசிலிரைலிரௌசிரௌனிளவà¯à®¸à®¿ளௌஸீராமணà¯ரவà¯à®šà¯à®°à¯à®©à®¾à®¯à¯ரோகà¯à®•à®°à¯ரௌசà¯ரசலà¯à®¸à¯à®°à®®à¯à®®à¯ரவà¯à®šà¯à®°à®·à¯à¯ரஸலà¯à®¸à¯ராதà¯à®¤à®²à¯ராவà¯à®°à¯à®©à®¾à®¯à¯ரெடà¯à¯ரெயிலà¯ரெயà¯à®²à¯ரேகà¯à®•à¯ரேசிலà¯ரைலà¯ரோகà¯à®•à®°à¯ரௌசà¯ரௌனà¯ளவà¯à®¸à¯ளௌஸà¯à®ªà®¿¯àš®àரமணிிரà¯கனà¯à®¨à®³à¯ˆE"%ிரà¯நà¯à®¤à®¾ிரிஸà¯à®ªேனE"%WEà¯à®°à®¿à®¸à¯à®ªேனெதà¯லE$/ெஞà¯à®šமினE$AIkெஞà¯à®šE$AJ“ெபà¯à®ªேE$EEெடà¯à®Ÿà¯à®•à¯à®•à¯E$‹‹à®¿à®ªிE%0ிஷபà¯E%[k0à¯à®¤à¯à®¤E(FFkà¯à®ª¯àš®àிரமணியEEà¯à®ª…®àாஸà¯à®ª…®àியாசà¯à®ª‡®àூமிà¯à®ª‰®àி à¯à®ª‰®àின à¯à®ª‰®àிபà¯à¯à®ª‰®àியà¯à®ª‰®àà¯à®šà®¤à¯à®¤à¯à®ª‰®àà¯à®šà®®à¯à®ª¯à°®à¯à¤®àாகà¯à®•ியà¯à®ª¯à°®à¯à¤®àோதனைà¯à®ª¯à°®à†®àாடà¯à®Ÿà¯à®ª¿®àŸ®à…®àாகà¯à®ª¿®à¤®à¯à±®à‡®àாகà¯à®ª•®à‡¯à¤®à¯à¨®àš®àà¯à®¤à¯à®¤à®¿à¯à®ªœ®àாரà¯à®ª²®àைà¯à®ª¹®àிளà¯à®ªà®¿©®à®®àரமைà¯à®ªDà®™à¯à®•ளாEEkà¯à®ªDதிலà¯à®ª¯à°®à¿®à¨®àநà¯à®¤à¯à®ª¯à°®à¿®à¨®àயà¯à®ª¯à°®à¿®à¯®à‰®àலிà¯à®ª°®àà®°à¯à®ª¿®à°®àனà¯à®ª¯à°®à•®àEE“à¯à®ª¯àš®àà¯à®ª¯àš®à®®à¾®à°®àà¯à®ª¾®àµ®à¨®àEk¯à±®à®®àடி¯àª®àˆ¯àŸ®àª®àல¯àª®àˆ¯à²®à‡¯àµ®àள௯મमà¯à¯®à†®àல¯à®®àட¯à®®à•®à¯à•®à…®àகà¯à®•¯à¸®à…®àணà¯à®Ÿ•®àட®®à¯à¤®à†®àல®®à¯à©®à†®àல®®à°®àª®àகà¯à®¤¯®à¿®à°®à†®àடà¯à®Ÿà®¾¾®à•®àà®°¾®à•®à¾®à¨®àரண¾®à¤®àம௾®à¤®à¯à¸®àண¾®à¤®à°®à¿®àª®àà®™à¯à®•ள¾®à¤®à°®à¿®àª®àà®®டà¯à®Ÿà®°Gà¯à®•à¯à®£à®¾Gà¯à®œ ஃபூனகதூரகதà¯à®šà®¿à®™à¯கவதிகவனகவானகாசà¯à®°காசூரனகிரஙà¯à®•கிஷà¯à®•கீரகà¯à®³கà¯à®•ிஙà¯Gாமகà¯à®•ெடà¯கà¯à®•ெனà¯à®±கà¯à®·à®£à®™à¯à®•மஙà¯à®•ளாà®™à¯à®•ாரà®™à¯à®•à¯சவகலà¯à®¯à®¾à®£சà¯à®šà®©சà¯à®šà®¾à®©ஜடà¯à®•ாகà¯à®•ளடà¯à®•ாவடà¯à®šà®£டà¯à®šà®¿à®•à¯à®•டà¯à®šà®¿à®ªà¯à®ªடà¯à®œà®Ÿடà¯à®œà¯†à®Ÿà¯டà¯à®Ÿà®•à¯à®¸டà¯à®Ÿà®©திலதà¯à®¤à®¿à®°à®ªà¯à®ªà®Ÿதà¯à®¤à®¿à®°à®®à®¾நà¯à®¤ பாசநà¯à®¤à®™à¯à®•ளநà¯à®¤à®¤à¯நà¯à®¤à®ªà¯நà¯à®¤à®®நà¯à®¤à®¾à®µநà¯à®¤à¯à®•à¯à®•ளநà¯à®¤à¯à®µநà¯à®¤à¯‹à®ªà®¸à¯à®¤னாரஸனியனனà¯à®©à®¾à®°à®¿னà¯à®©à¯à®®à¯ டீயà¯à®®à¯னà¯à®°à¯à®Ÿà¯à®Ÿà®¿பூனபà¯à®³à®¿à®®à®¾à®¸à®®à¯à®ªà®°à®®à¯à®ªà®¾à®¯யஙà¯யஙà¯à®•à®°யதà¯யநà¯யபகà¯à®¤à®¿யபà¯யமயாலஜியிலà¯à®µà®¾à®©ரதநாடà¯à®Ÿà®¿à®¯ரதனரதரரதà¯à®¤à®¿à®Ÿà®®ரதà¯à®¤à¯ரதà¯à®µà®¾à®œராக௠ஒபாமாரோடà®°à¯à®•à®°à®°à¯à®¤à¯à®°à¯à®©à®¾à®²à®¾à®°à¯à®®லகீனலஙà¯லசாலிலதேவலதà¯à®¤à®¾à®²லதà¯à®¤à®¿à®©à®¾லதà¯à®¤à®¿à®©à¯à®Ÿலதà¯à®¤à¯à®Ÿலதà¯à®¤à¯ˆலபà¯à®ªà®Ÿலபà¯à®ªà®Ÿà¯லபà¯à®ªà®°à¯€à®Ÿà¯à®šà¯ˆலமணைதà¯à®¤லமாகCà¯லமாகவேலமாகிலமாசà¯à®šலமானலமாயà¯லமிழலமà¯à®Ÿà®©லமà¯à®Ÿà¯ˆà®¨à¯à®¤லமà¯à®Ÿà¯ˆà®¯லமà¯à®®லராமலவநà¯à®¤லவானலவீனலஹீனலிகடாலிகà¯à®•டாலிகà¯à®•à¯à®šà¯லிகà¯à®•ொலிஜாலிபீடலியலீஜாலூனலà¯à®•ேரியலà¯à®ªà¯லà¯à®ªà¯ˆளà¯வனவாணிவானிவà¯à®¤à¯à®¤à®¤à¯à®¤à®¿à®²வà¯à®²à®°வà¯à®²à®¿à®™à¯வà¯à®¯ஷீரஸஹதூரஹிரஙà¯à®•ஹிரணà¯à®Ÿஹà¯à®°à¯†à®¯ ¯à®®à¯à¯®à€¯àŸ®àனà¯à®©à¯à®®à¯  ¤®à¯à¨®àŠ¯àš®àநà¯à®¤¯à•®à¾®àš®àடி¯à£®à¯®àª®àட¯àª®à•®à¯à•®àª®àல¯à¸®à¹®àணà¯à®Ÿ¯à¸®à¿®à²®àன•®àத௕®àம௠•®àளிகர•®à‡¯à¤®àல•®à¯à•®àª®àலŸ®àª®àட¤®à¯à¨®àŠ¯àš®àநà¯à®¤¾®à•®àநà¯à®¤à¯¾®à•®à®®àலி¾®à¤®à ¾®à¤®àà®™à¯à®•ள¾®à¤®àதà¯à®¤¾®à¤®àமரதà¯à®¤à¯வாஜEk"k/கà¯தEk1கà¯ரீதநà¯à®¤à¯à®²à¯Ek2/லாதà¯à®•ாரEk7tF1லà¯à®šிஸà¯à®¤à®¾à®©Ek7xJலà¯à®ŸிEk7Šà®¯à®¾à®¸à¯à®•ோபà¯Ek9tW1u0à®™à¯à®•à®°EkB1kத¯à£®à¾®à•®àிலEkFதà¯à®¤ிரகாளிEkFFகிரணà¯à®ŸEkOீதோவனEn/ீசà¯லEnJீடà¯à®°à¯‚டà¯EnŠ"yŠà¯‹ஸà¯à®Ÿà®©Etாரà¯à®ªடாEt"Ekாபதிš®àEt0k/%ாகà¯à®ŸீரியாEt1Šà®¾à®²à¯à®•னிEt71kாலபாடEt7k0ாஙà¯à®•ாகà¯EtB1ாபாசாகேபà¯EtEாபாசாஹேபà¯à®¾à®ªாவாப¯à¯®à¾®àš®àாாப¿®à¯®à¾®àš®àாாபà®°EtEkாதà¯à®¤ியதைEtFFாதà¯à®¤ியம௠ாகà¯à®¤ாதEtOFோபாலEu0ோபோரà¯EuQூத௠Ey/ூபதிEy0kூடானEyо®à¤®à¯à¨®à…®à E“¾®à¤®à¯à©®à…®à ¾®à¤®à¯à¸®à©®à®®à ¾®à¤®à¯à¸®à°®à¿®àª®à ¾®à¤®à¿®à°®àª®à ¾®à¤®à¯à¸®à ¾®à¤®à•®à°®à¿®àµ®à ¾®à¤®à¾®àš®à¯àš®àª®à †®àிரிகà¯à®•Q‹¯à°®à¯à•®àˆ¯à®®àோன¯à®®à‡®àால¯à²®à†®àா®àோன®®à¾®à°®à¿®à•®àோன¿®à²®à•®àோரà¯à®©à®¿à®¯ாகியானாதà¯à®¤à®¿à®®à®¾ாரà¯à®®Eிாரà¯à®®à¯à®²ாஹியானிகரிஙà¯à®•ர௠ிசிகà¯à®¸ிடிலினிஷினà¯à®²à®¾à®¨à¯à®¤ிபà¯à®°à®µà®°à®¿ிஷà¯à¯à®²à¯ Pà¯à®²à¯à®²à®¾ ெணà¯à®Ÿà®¾à®¸à¯à®Ÿà®¿à®•à¯ெதரெபà¯à®°à®µà®°à®¿ெரà¯à®©à®¾à®©à¯à®Ÿேகà¯à®Ÿà®°ேமிலிேஷனைலà¯à®•ளோடà¯à®Ÿà¯‹ ோடà¯à®Ÿà¯‹à®•à¯à®•ோடà¯à®Ÿà¯‹à®µோனின௠ோனிலோனிலà¯à®®à¯ோனà¯à®•à¯à®•ோனà¯à®Ÿà¯ˆà®¯ோனà¯à®²ோனைோனà¯à®•ளோரà¯à®œà®°à®¿€¯à²®à•®àா†®àிச†®àிஸ†®àீச†®àீஸ‹¯àš®àா¯àŸ®à¾®à³®à¿®àª®àார¯à©®à•®àிகர¯à²®à†¯àš®àோன¯à²®à†¯àµ®àேர¯à²®à¾®àŸ®àின•®àே¤®à¯à¸®à¯à®®àா¾®à•®àியை¾®àŸ®à•®àி¿®àš®àª®àிக௿®à²®à•®àாிராஙà¯à®¿ராடாகிராட௠ிரானà¯à®šà®¿ரானà¯à®¸à®¿ரீயாிரெணà¯à®Ÿà¯à®¸à®¿ரெஷà¯à®¿லெடà¯à®šà®°à®¿ளாஸà¯à®•à¯à¯ளோரனà¯à®¸à¯ளோரிடாெ®àகானியெ®àகானிஸà¯à®¤à®¾à®©à¯ராஙà¯à¯ராடாகà¯ராட௠à¯ரானà¯à®šà®¿à®¸à¯à®•à¯ரானà¯à®¸à¯ரீயாà¯ரெஞà¯à®šà¯à¯ரெஷà¯à¯லெடà¯à®šà®°à¯ளோரனà¯à®¸à¯ளோரிடா௾®àš®à‹¯à°®à¯à•®àˆ¯à®®àட௿®à²®àடà¯à®ªà®¿†®àரிகà¯à®•ிரணà¯à®Ÿà¯à®¸Q"$ிரெஞà¯à®šQ"$AJ“ிரெடà¯à®°à®¿à®•à¯Q"$‹"%1à¯à®°à¯†à®Ÿà¯à®°à®¿à®•à¯ிக¿®à²®à¾®àµ®àேஷனQ%1ிலிபQ%7%0“à¯à®Ÿà¯¾®àš®àவேரQ/ிளைடà¯Q>கà¯à®°à¯à®¤à¯€à®©Qkனலà®°à¯à®©à®¿à®šà¯à®šà®°à®°à¯à®²à®¾à®™à¯à¯à®ª†®àரிகà¯à®•à¯à®ª¾®à©®à¯à©®à†¯à¤®àரிகà¯à®•à¯à®ªà®¿¾®à©®à¯à©®à†¯à¤®àரிகà¯à®•à®°à¯à®©à®¿à®šà®°Qk"2%Jkரூகà¯Qk"–1ாதிமாQt/ாலà¯à®Ÿ¿®àŸ®àQt7Š“வà¯à®£à¯à®ŸனQ…@Škௌணà¯à®Ÿன¯à²®à¾®àŸ®à…®àQ“€¯à°®à†¯à·®à /B?ியூிHš®àய?k0B99k1B"ி¤®à¿®à¨®àசனி®®à¿®àµ®àச௿®à¤®à…®àà®·à¯à®Ÿà¯¿®à¤®à°®à¯à¤®àà®·à¯à®Ÿ"k2B33kà¯à®šJ “à¯à®±Š3à¯à®ª¯®à†¯àš®à30“B77k௵®à¾®à•®àதà¯à®±à¯ˆŠ4B>>k௉®àதà¯à®±à¯ˆŠà¯à®¤•®à¯à•®à®®àொகைŠ/5BZZk6BRியூகியாRk7BYYk8B[[k9BWWk:BjjkN” à¤hià¥hiஂ‰à®°à¯à®¤à¯à®¤ிரா"xFF…#Ž$¿%Ž&$&pŽà®ªà¯à®°à®²&p0’'”ி'>%‰(ˆnp†t¾“uŠy„’ளடத…’ளà®°à®™à¯à®•’ளவை’ளஷத”ௗ †$Œà®¿µ®à$>%Œà®¿¤®àŠ'(€n‡p‹u‚yˆ„†à®³š®à…†à®³ª®à†à®³®®àன†à®³®®àஸŒà¯- A  - C .  0(>>%rs ."y0nV-  1kZ%//k7$F'7ksources_5316/external/espeak/espeak-data/eo_dict0000644000176700017670000001107411663004331020525 0ustar paulpaul  C9#À2(?$3'_i#J$1#Ã,€HÄ5 LL †Å­L%0'p$2/'& 1lÃ@ô€L*#W/$3%W1'B-1'?0#"( /'E7%1R'  .1l#7%l .1lp$/$3$ =$O#7#Ä5LL@ J$ Ã,“ÀL .1lW%?%7$AXR' \F$17%R'A`%1W' _1M1?%7 |F(1/'W%O2' ~/%7F' '7#ÂLÅ­#(O(W/'Ã@ôÔLB `E'2R'7(Ã0@LÃP@Ã0JLBPF$7#HQla ÂPL _ 1'?' _##BÀ#77#HQla ÂÀL _#9/#E' _ /%7F# HCäÔ#2W/#/j.2'/(E'2$ÃPMCP€Q$E(#3'à ‰LÂ$HÄ ‰LL…Å  LÃ8RÀHÄ4ULLÄ@õLLÃP“ÀL C)S€%(2%'BÀ$77#HQla ÂÀLÄ4U LL ..1l/%$707( _#-#2ƒÄ‰L_ W/%#…Ä  L _#- lÂðÄ LL. 0'W/1%W/'Bà$27#HQla ÂàL_3X/%F$1 _0Cp$2/ÃQ @HÄ LL.0'W/#W1%E' _1Cp$2/Â(PHB07#ÃA"@LƒÄ‰ HÂ)PHƒÄ‰H C)S%(7%' _7XW$0F$1Ä4ULLÄULL„Å LC-D1l/%$707( ÃDLÂ,PH _1XF$1Ä$åHL _2XF(F$1. #2/j1%W/'Ã4@L _??7%/$3'_4X1R#3F$1Ã4JLB,p1%7'O#?nCLTW$0/$?E'_5X1R%2F$1ÄULL _6XW$WF$1C€#0%7'CMD€W/#/'ÄU‰LL _8X'1F$1 _9X2jF$1ƒÄ HÄ4ULL_W(Ei'1#ÄU•LLÂ0HÂ8PL C4€?l'ÃA#ÀLÃ#H_0M4F(%7%'2'_0M2?%7%'2'ÃLS€L_0M3?%7%#"F' _0M1?%7 _i'1# C4€?#/'Â4HB,Ð1%7'?$/nƒÅ HBA00'W/#W1%E'ÃMP€LÂ8HÃ<â@H C@Â@07%_ p%31(?Q7$1W#Ã-S€LÃMT€L_ W/$1#_F$1W/#1'32#_«F('E7#1#?0'./%'$W/#W C@ÁJ07m _3%2O#./%$72'?#/#_2F('E7#1'32#ñÃ% SLC<µ'1/'E'_»Q$3?#F('E7#1#?0'Ã%"SLÂ<ÀLÂLPHÃLQHÃ%%SL _# l2 ©1'0%3l/'ÃX@LÃ8@LÄ$ÂA(L °O"#FnÃ8JL_p$F%7#_ 7%O#/(3# Ä0#I' _##2 _# lÂLHÄ@õ•LLÃ5 LÃXJL„ Å­LÄPE8ƒÅ­HÄ@õ‰LL _"p%/'_! 1%W%O2' C(€%#2(#3'_'#0'W/'Q'ÃS@H_?l(W17#_)Q$3?#0#"$2/$V'C…Q#$F$LQde _(0#"$2/$V'Ã@T€L _.0(21/'_-F%R%F'W/$1'C@T…0$$F$LQde _,1'?' _3/"%Ã%#ÓL_2F( _1(2(_02(7 _7W$0 _6W$W _51R%2 _41R#3_;0(21/'1'?' _:F(0(21/'_92j_8'1C¶€$1V$?07$,Qe C¶€$1V$?07$_?F$?#2F'W%O2'_>Q$3?##2O(71#?0'_<#2O(71#?0'CPÀF$p$?E'Ä@õLL_0(21/#_[3$1/#1#?0' _#- l2BXR%HÂT°__W(EW/$1'_]Q$3?#3$1/#1#?0'Ã$ÂALÃ$Â@H C²À#7%2'?$_?#7F$1W/#1'32#ÃTÀH_{1(3E#1#?0'_ F(0(21/#_}Q$3?#1(3E#1#?0'„ĉHÄ,•J8 _#32W0#p'„Ä L _#-# ÅA!T L  .%#„Ä LÃ,‘LLÄ5LLÃ,@LÃL@Là @LÃTP@ÃLJLà JLÃ,‘@LÄ5LLÃ,MLÃ,•NÃ,•JLƒĉÃ,•@Lcx gxhx%jx5sx]uxma# Å­jjlbE E'chJhh J'p p'dF-rinoF'1/' F'-roF'1/'e$ Å­kjmfQ Q'-inoQ3j7-loQ3jghIO O'hhci i'i% j9 9'hCXk1-dino1#?#3#-ino1#?#3#F-do1#?#3# 1'l7l  7'm? ?'n2 €€ 2'-ro2(?$o- '- n- '2n- j- nj- ' jnp0 0'hQhq1 1:'u1RrA3AA 3'r33sW-inoW%29'3-ta W#21-aninoW#?%F$-ano-roW%29' W'hYhh Y't/a- /# /'hUhu( jovR R'w:h F('E7#R'x %1W'1WVy% %0W%7'2'9zV V''---- a.... - A  - C £  0(2Fn $  F'7#3n .0(21/'£0(2F'+07(W ++ 07(W07(WÅ­:Å­ :'-?%2(W -  $F'7#3'ÄIÄ I'ĉJĉ J'-  W/$1$/' ĵXĵ X'ÅYÅ Y'Ä¥cÄ¥ c'sources_5316/external/espeak/espeak-data/da_dict0000644000176700017670000056713511663004330020523 0ustar paulpaulæØ ÉO"ˆ/ T#2E@NL°OF#2W1E0ðÁ0P7†1v7 ERNOx2% EÁPQ W|F EPÁPFw1ˆF _=1:tVFó…Fz2oO€7 CS™Fo2‡ _<7wWT#2D\õL:sFi#R/rJ Rhave to D\õL:sFi#R#Qhave D\õL:sFiuR#Qhave Ä\õLL DÓA8u?|2 DBOL#T9“WEQ"A8/"#2%ELóPPWz79„/ÅP•8°B Æå 4ó™B _@#/W‡2G…BTw1W/" F‡/HA#Ê5 0P0" Iw1/tg D0u0€7F 0“…1#" 7‡2FSI8“…Qw? 2x2 E4ÅM0uWwWFX•4“€R‡/ ?x2gFPT’“€/ "ˆ2F"Fó€O"xQ 2KHPÏ8àIM0N P"o1z2xW 2W C0QÏ7wO† DqÒ<#O"†F4ÈÃ?oYw7 E5 #W/7%F 0“1#" 7‡2 ÆTÐ’ÃBFPô”$Ã/‚/uEMP”1W{/ 7x FHQ‰8T™"oQ‡2 "x ñ0A#/uV E4õT!0?…TV Éô…LƒÒPS€BF ó”H™1z2/" "x _‣Es7o/ Æ ó S€BF#ÎPS„Q"{2/w2F¶¶0#" O"#QW _•Es7o/ C@@ˆF _‡F{EtF#Op D0ÅH7ˆVp D“ÒQ‚FFËáE#1w2F _†F#Op C\N:w2 C\N:w2 FA!NPÅ0"w2/xWE$ÓÇàx? I 2ÅQÅàBFáÅ0TÀ#2I 7VçQ W|F_…x7x0WxW F RL$B1ˆ7%ÃU0€ _‥/„Fz/W D4”È?Y _․Fz/EÁ’@#7Q"oF CÀN#7 2 EHRN@"ˆ2FE @iˆ/"yF_‛7wQ/1:†/F4SP ”À?w?QoW _‚7†1:†/FLCNW€W0 2_’"‡/1:†/DòNO†xB CÁC#7x1F0SÐ!7w0 F DGOˆI_‘7wQ/1:†/_:xTFz/uE{RELPÁ9@W1 2/E„I@w1W0~/ EÓÕ9@u?…2/_‟7wQ/1:†/WFQ"BTàL/"‡E9„2t C8‰2v/WxF”a@Io"vQ C@M#F ?_„7†1:†/W CL@YH !_â€"‡/1:†/W_[7wQ/E"#1o/FA!C0"Ww0/ È4NPN B D RSPi‡W/_“7wQ/1:†/W C0SÎ7z2F4”Ó=T‰?xV"%F<"TT™zExJx CANF 2F“Pô™Fx7 / "xE I@1uR‚/ _–F#YFLóE<á@W{?:{2jFLóE<á@W{?:z2BLðW†?{JQmuch BLðW†?w2%Qmany BLðW†Q} Qfar BLðW† F!D$S”O"F‹2/FP Á@FˆE|1tÂX*ÂT° _‒F#Y F d 7 _‑i‡Q 2__{2FpW1ƒ DH”Å8"xV 2 DHUd"/"‡ C ‚CY1 CÀSu7#W _â‚ 9"† _â€i‡Q 2_^W‘1{?Q7w1Wi_^W~1{?Q7w1WÃLóÎ EPÁ4PEx1ˆ?J CANˆF 2 C$3·1z2 E ‰8P1ˆ2‡2_]"‡/E"#1o/ C@T•0 "„F8R<"@2‡"†E%F Q@TÔE„F 0wW/FMS„$W{2FŽ7 CL‚AY J4Ò<ô‡âS4?‡1"†‚O 2xV ?_‖F{EtE}_―iz"oVz2/tE}D õL1sFi#R/rJ Rhave to D õL1sFi#R#Qhave D õL1sFuR#Qhave D õL1sF HA#ÐpN0"z0 O#2F D<ÉL†ˆWoW DSO8F? 2 D óEH1{?p D ñUH1~ _—w?F#YFLA9BW ?#2U EHU 8"w/x2 EHQÉ4P"ˆX?F8T9B2o0w2U%E5UPP?9„/ˆ/IÅHàTÆ@€7/~2 /7x Æ=U2ÀA _`E#10"‡?GLõN"TW…2FE‡/ C<‚O†i‡† D R<1‡"† Æ=U =5A DÁ0EˆWtH"T ÑT$0u"xU? /x1C RYŠE4ôM0?z"#WF”Ã%FxW‡0t E”‚U0ŠE{W _30U~/‹ CQS/9„2 FÃÕH”ÈQ7~oYgFÃÕH”ÈQ7{"oY CH“À"† Æ ó4%SB C0SÀ7†G T…PÁ0io"w/o1tF"N“‡Q"x2IxB É ƒHô 5ACÃ@|?HEPT#I1: /~2 "x D õÔ=O"ˆ/ ‚1:tðTþUßWçžXÅŸYÅ¡äwëêw ö~éeïü„éˆsources_5316/external/espeak/espeak-data/ca_dict0000644000176700017670000001012111663004330020474 0ustar paulpaul. A#ÁHAE$ÃЀA W$ _1#Cl2AF$AkQzAM$ †àLA #1#1m9_%2k/A$%Á$H%0 3W 2/#K & %& zB7kVzA(^l/z CDÀ$yL*#W/$%W1 +?$WA,1$ -?kAW /E#3#A0k7zA4k?zA8k2zA<'Á?z^' 1 _ _87Wk/ tWnल7 _86Žo9tWnभ‡ _91o19t2 :pबE _902kE p य9 Hय9 _93/o"t2 :pम? _92Et2 :p_950 Nt2 :pन2 _94Nv"t? :pफ† _97W / t2 :pप0 _96Žo9t2 :p _0M4k" E _0M5k" E _0M27t _0M3N"'"$ _0M1i Vt" ‰à¤¹à¥ˆà¤‚H †à¤¤à¥‚Hउसà¥à¤¸à¥‡Hइसà¥à¤¸à¥‡H˜à¤¤à¥à¤®à¥à¤¹à¤¾à¤°à¥‡H˜à¤¤à¥à¤®à¥à¤¹à¤¾à¤°à¥€H ‰à¤¹à¥‚à¤H ‰à¤¥à¥€à¤‚H ‰à¤®à¥ˆà¤‚H †à¤¸à¥‡H †à¤¤à¤•Hअगरचे ख़c ˜à¤¤à¥à¤®à¥à¤¹à¤¾à¤°à¤¾H †à¤ªà¤° ज़V †à¤”रHŒà¤¬à¤¿à¤¨à¤¾H †à¤†à¤ªH _3/n2_2Fu_1p1 _0Yy@9k _7Wt/_6Žm _50t2N _4Nt" _92…g_92v_8tŒŒà¤®à¥‡à¤°à¥‡HŒà¤®à¥‡à¤°à¥€H ‰à¤¯à¤¦à¤¿HहमारेHहमारीHŒà¤¤à¥‡à¤°à¤¾HŒà¤®à¥‡à¤°à¤¾HसायबरW„E "हमाराHf 0g 1h 2i 3j 4k 5l 6m 7n 8o 922प?फबभमट@ठडढणचAछजà¤ञयकBखगघङहjk¹¤à…¤àrहto  %n x yःं "o -r$pqà¤}ं„w'uà¤ंvऀं…B1à¥à¤¯1 1k़Bf़fk़Bc़ckBkBOOk़Bb़bkB‘‘kBB¥à B BkBNà¥à¤¯N NkBŽŽkBMMk़BV़VkBk¥à ABAk BŠà¥à¤¯Š Šk!BŒŒk"़BD़DkB‹‹k#़BDi़DikBk$B@¥à @ @k%B/à¥à¤¯/ /k&Bˆˆk'BFFk(B‰‰k)¥à°¤à 2B¥à 2 2k*2 +B0à¥à¤¯0 0k,़BQ़QkB††k-BEEk.B‡‡k/¥à¨¤à ?¥à°¤à B¥à ? ?k0B9¥à 9 9k1B"¥à " "k2B"¥à " "k3B7¥à 7 7k4B>¥à > >k5B>¥à > >k6B::kBRà¥Rk7BYYk8B[[k9BWWk:Bjjk> ?tव…@oA %nBxCyःंD"oE"oFrG$HpIqà¤}ं„JwK'Luà¤ंMvऀं…NQ?YBffkZBcck[Bbbk\BVVk]BDDk^BDiDik_BQQk`B99kak""b- c-d- of     ?$%0kWr2/$Fw7ksources_5316/external/espeak/espeak-data/hbs_dict0000644000176700017670000001627711663004331020710 0ustar paulpaul‹ÃUQ@ ÃÑ€ A#ÁHAE Ã92@ A s Ã)1@ ÃÑ€ _1R#JˆsxAF Ã9!ÀÅ8SA)PLAQ Ã90@ Ã9 À AO A c !(VRˆJ2ˆ1f!(W17ˆJ2ˆ1 #EŠ'9 A$%Á$H %0'W/' & $2FA(9†Ã=@ *VR9$VF%sxà  +07(Wà A,1 à Ã%EÀ  ./#J1xh ./'J1x /1Š'V A07 Ã9%À A4? Ã5@ Ã\–€ A82 Ã9$À :FR'/xJ1xh :FR'/'J1xA<'ÁR$J%'F _=9$F2x1' _=9$F2x1'ÃT” _@Lsources_5316/external/espeak/espeak-data/mbrola_ph/tr1_phtrans0000644000176700017670000000055411401275202023325 0ustar paulpauliIEeOoUuW@'YyRr*r**rl/2lckJgQGwv”®¿A€ý¶@àsources_5316/external/espeak/espeak-data/mbrola_ph/it3_phtrans0000644000176700017670000000157411566706373023345 0ustar paulpaulr/rw/wl/lj/i;@-*rRr_|_p:pp2b:bb2t:tt2d:dd2k:kk2g:gg2dzdzn^Jl^LNngnfnfw2waIa1i<aUa1u<oIo1i<ii1Iiee1e/eEE1aa1a/aOO1oo1o/ouu1Uu>@Lsources_5316/external/espeak/espeak-data/mbrola_ph/ptbr4_phtrans0000644000176700017670000000446411400042643023656 0ustar paulpaull/wl/2wll/2jll/2wr/r2r-rw/wj/y;g-@-*jr*r*r2:SxZjtStdZdl^lhn^nhNnxrrz_s2ssswssjsss2s#ss#s2rrrr2Rrjya/aAa&a&/a&~Nan &~anEeeeImen eINen i/iiNin i~Nin i~inoNon o~j/oni< o~Non o~onOoou~j/uni< u~Nun u~unUwyyIyaIay<eIey<EIeey<oIoy<OIooy<uIuy<aUaw7&U~@eUew7EUeew7iUiw7@@TtDz0oVaI2yA:aA@ar<o:oO:oO@or<o@or<i:ii@ia<i@3ir<u:uU@ur<3er<3:er<@Lel(a#aaaae@eroUoOIoi<aI@ae<aU@at2t8µ¿ sources_5316/external/espeak/espeak-data/mbrola_ph/vz_phtrans0000644000176700017670000000435411662006606023271 0ustar paulpaull/2ll/lr/rr-rl-lw/wj/j;g-@-*r:**rRs_rrRt_rrRrrR2v#bvbjjJLJ^Ln^JNnbBdDgGBBDDQGzsssstsss2xhtS_tStStStS_tSaa* ee* ii* oo* uu* iiiiji;jiiiijuuuuwuuuuwa/aEeOoaIaj<eIej<oIoj<aUaw<eUew<dZtSSsj<Zsj<@e@2e@5u0oVaUuIiI2iA:aA@ar<o:oO:oO@or<o@or<i:ii@ia<i@3ir<u:uU@ur<3er<3:er<@Lel(a#aaaae@eroUoOIoj<aI@ar<aU@at2th@¯€1>ó¶S袶Lȇ¶sources_5316/external/espeak/espeak-data/mbrola_ph/ic1_phtrans0000644000176700017670000000215411356414536023307 0ustar paulpaulr/r#l/2ll/lr/rr-rl-lw/uj/j;g-@-***yYy:Y:W9W:9:eIeieI:ei:aIaiaI:ai:oUouoU:ou:aUauaU:au:Yy9yYy:9y:OIOiyiYi_|R_r0RrR2rQGm#m0n#n0N#N0n^Jn^#J0l#l0r#r0JJ-s2hl#l0hn#n0hr#r0>@Vsources_5316/external/espeak/espeak-data/mbrola_ph/us3_phtrans0000644000176700017670000000207411651233473023343 0ustar paulpaula#@@2@@5@@/@3r=I2Ia{aa{@Ll=l/2lr/rr-rw/w;g-xk@-aI@AI@<aI3AIr=<aU@aUrK*4t#ntt#43:r=IRr=VRr=i:iA:Au:ua{eIEIaIAIoU@UO:O0AOOO@Or2o@Or2A@Ar2e@Er2U@Ur2i@I@2i@3ir<t2t>@Qsources_5316/external/espeak/espeak-data/mbrola_ph/mx1_phtrans0000644000176700017670000000341411662016040023324 0ustar paulpaull/2ll/lr/rr-rl-lw/wj/i;g-@-*r:**rRs_rrRt_rrRrrR2v#bvbjiJjjJ^jjn^JNnBbDdQgzsuuuuwuuuuwjia/aEeOoaIai<eIei<oIoi<aUaw<eUew<Ssi<Zsi<@e@2e@5u0oVaUuIiI2iA:aA@ar<o:oO:oO@or<o@or<i:ii@ia<i@3ir<u:uU@ur<3er<3:er<@Lel(a#aaaae@eroUoOIoi<aI@ar<aU@at2thذ4ª°°4lÏÚ¿sources_5316/external/espeak/espeak-data/mbrola_ph/sv2_phtrans0000644000176700017670000000303411566716263023350 0ustar paulpaull/2ll/lr/rr-rRrl-lw/wj/j;g-@-*rS;CsxSSrs2s.rs2u-}:Y:2:yY8u0W2EeE-e@Nea#aE:r{:Y:r9:Er{Wr9pphtthkkh@2@@5@I2IVu0aaa0A:3@3:2:aIaj<eIej<OIOj<aUaU<oUo:i@i:@<i@3i:@<e@E:o@o:@FO@O@FO:OA@A:U@U@<@L@l(aI@a@FaU@A:u0FTthTtDdwvzstSts2dZds2Zsx-ê¿Lê¿ÊÿPŽsources_5316/external/espeak/espeak-data/mbrola_ph/grc-de6_phtrans0000644000176700017670000000074410745657171024072 0ustar paulpaulii:ee:EE:aa:a/a:OOoo:yYaIa:j<EIE:jFOIOjFoIo:j<yIYj<aUaUeUe:w<EUE:wFOUOwFl/lfpfzRsources_5316/external/espeak/espeak-data/mbrola_ph/ee1_phtrans0000644000176700017670000000264411603314051023273 0ustar paulpaulAaA1aa:aa2EeE1ee:ee2IiI1ii1ii:ii2OoO1oo:oo2UuU1uu:uu2878:772&{&:{{2Y2Y:222y:yy28u7u2&i{i2Yi2i2yiyi2b:p:d:t:d^d'd^:d'g:k:h:h:j:j:k:k:l:l:l/ll^l'l^:l'm:m:n:n:n^n'n^:n'N:N:p:p:RrR:r:b:p:s2sss^s's^:s'S:S:t:t:t^t't^:t'v:v:wvZSzs*@sources_5316/external/espeak/espeak-data/mbrola_ph/hu1_phtrans0000644000176700017670000000264411566705340023333 0ustar paulpaull/2ll/lr/rr-rl-lw/wj/j;i;j-g-@-*rR2ree:AOY2Y:2:ct'Jd'n^nj<NnCxs2st2t@2eIe:j<aUa:u<oUo@L2l(@22@5232a#a:I2iIiaa:aaa:VOUu0OA:O3:2aIa:j<OIoj<i@i2<i@3i2<e@e:2Fo@o2FO@O2FO:OA:OA@O2FU@u2<aI@a:2FaU@O2FTtDzwvè~õ¿!tv¶@¯ª(õ¿sources_5316/external/espeak/espeak-data/mbrola_ph/pt_phtrans0000644000176700017670000000405411060015576023250 0ustar paulpaull/wl/2wll/2jll/2wr/rr-rw/wj/j;g-@-*jr*r*r:tStdZdl^Ln^JNnxRs#SrrrrRra/aAa&6&/6&~N6~ &~6~EeeeIm6~j~ eIN6~j~ i/ii~Ni~ i~i~o~j/o~i< o~No~ o~o~Ooou~j/u~i< u~Nu~ u~u~Uuy@I@aIaj<eIej<EIEj<oIoj<OIOj<uIuj<aUaw7&U~@eUew7EUeew7iUiw7@@TtDz0oVaI2@A:aA@ar<o:oO:oO@or<o@or<i:ii@ia<i@3ir<u:uU@ur<3er<3:er<@Lel(a2aaaae@eroUoOIoi<aI@ae<aU@at2tsources_5316/external/espeak/espeak-data/mbrola_ph/nl_phtrans0000644000176700017670000000322411537451473023245 0ustar paulpaull/2Ll/Lr/Rr-rl-lw/Wj/J;g-@-*rt;tjctjd;djJdjn^njv#ws;SCxQG8Ye:r/I:e:eY:r/Y:Y:2o:r/O:o:oa:aEIEiWy9yVUAueUeWFyUyWFE2Ei:iu:ueIEiaUAuoUo@L@l(@2@@5@3@a#@I2IaaaV2Uu0O3:2aIAJ<OIOJ<e@Ei@i@<i@3i@<e@E@<o@o@FO@O@FO:OA:AA@A@FU@u@<aI@a@FaU@Au@FdZdjdZtjtStjTtDz8=‹¿Žɶ`4Pæ7¶X=‹¿sources_5316/external/espeak/espeak-data/mbrola_ph/gr2_phtrans0000644000176700017670000000424411566714713023332 0ustar paulpaull/2ll/lr/rr_rpRrbRrtRrdRrkRrgRrmRrnRrl/2RrfRrvRrTRrsRrzRr3r_r/rRzRRrr-rl-lw/wj/j;i;j-g-@-*R@-*rNgVNJVNnJqQGm;Mn^Nl^LtsSdzZdzZksXpsYs;sz;zaIai<oIoi<a/a3er<@aeIei<aUau<oUo@Lel(@2e@5e3ra#aI2iIiaaaaaVaUu0oi:iu:uA:a3:er<OIoj<i@ir<i@3ir<e@erFo@orFO@orFOoO:aA:aA@arFU@ur<aI@arFaU@aEewvhxtSctSSdZqdZZ¸ê¿PLS¶L¯HkT¶èê¿sources_5316/external/espeak/espeak-data/mbrola_ph/en1_phtrans0000644000176700017670000000143411400042550023275 0ustar paulpauloU@Ua#@@2@@5@@/@3@I2IiIa{aa{0QEeOO:O@O:o@O:A@A:i@I@i@3I@IR3:VR3:@L5l/25r/rr-rw/w;g-@-aI@aI@<aU@aU@Kxkt2tÀsó¶ðµ¿EURODSKRQHPsources_5316/external/espeak/espeak-data/mbrola_ph/pt1_phtrans0000644000176700017670000000405411566707167023350 0ustar paulpaull/wl/2wll/2jll/2wr/rr-rw/wj/j;g-@-*jr*r*r:tStdZdl^Ln^JNnxRs#SrrrrRra/aAa&6&/6&~N6~ &~6~EEeIm6~j~ eIN6~j~ i/ii~Ni~ i~i~o~j/o~i< o~No~ o~o~Ooou~j/u~i< u~Nu~ u~u~Uuy@I@aIaj<eIej<EIEj<oIoj<OIOj<uIuj<aUaw7&U~@eUew7EUeew7iUiw7@@TtDz0oVaI2@A:aA@ar<o:oO:oO@or<o@or<i:ii@ia<i@3ir<u:uU@ur<3er<3:er<@Lel(a#aaaae@eroUoOIoi<aI@ae<aU@at2t ëÄsDÿÄsDÿÿsources_5316/external/espeak/espeak-data/mbrola_ph/la1_phtrans0000644000176700017670000000135410745657232023314 0ustar paulpaulr/rw/w;@-*rR*r:Rrpp_htt_hkk_hp:p:b:b:t:t:d:d:k:k:g:g:fff: sss: zzz: mmm: nnn: j/jj: j/jl/ll/2ll: l/2laIaEaUaUoIoEEUEU<aì+ò¶ p-sources_5316/external/espeak/espeak-data/mbrola_ph/de4_phtrans0000644000176700017670000000314411566714255023313 0ustar paulpaulTrtleILloULloULl@LLll/2LleILreIrroUrroUrr@Lrrl/2r3D@3T@3@L@3oU@3w@3eI@l/2Ll/lr/6r-rl-lw/wj/j;g-@-*RV#RURUR<E2EyYW9A:a:Aa:Y:2:OIOY36pFpfrReIEIoU@UW~E~A~a~O~o~_|?@LL@2@@5@a#@I2IaaaVa:0O3:@i@i:@<i@3i:@<e@E@<o@o:6FO@O6FO:OA@a:6FU@U@<aI@aI@FaU@aU@FdZtSˆê¿/­âµü,b„ê¿lê¿sources_5316/external/espeak/espeak-data/mbrola_ph/es_phtrans0000644000176700017670000000325411400042554023227 0ustar paulpaull/2ll/lr/rr-rl-lw/wj/i;g-@-*r:**rRrrR2v#bvbjiJLJ^Ln^JNnBbDdQgzsTssTssa/aEeOoaIai<eIei<oIoi<aUau<eUeu<dZtSSsjj<Zsjj<@e@2e@5u0oVaUuIiI2iA:aA@ar<o:oO:oO@or<o@or<i:ii@ia<i@3ir<u:uU@ur<3er<3:er<@Lel(a#aaaae@eroUoOIoi<aI@ae<aU@at2thÿPV½¶X µ¿_c¶Äœ€sources_5316/external/espeak/espeak-data/mbrola_ph/sv_phtrans0000644000176700017670000000303411566716253023265 0ustar paulpaull/2ll/lr/rr-rRrl-lw/wj/j;g-@-*rS;CsxSSrss.rsu-}:Y:2:yY8u0W2EeE-e@Nea#aE:r{:Y:r9:Er{Wr9pphtthkkh@2@@5@I2IVu0aaa0A:3@3:2:aIaj<eIej<OIOj<aUaU<oUo:i@i:@<i@3i:@<e@E:o@o:@FO@O@FO:OA@A:U@U@<@L@l(aI@a@FaU@A:u0FTthTtDdwvzstStrs2dZdrs2Zrsx-ê¿Lê¿ÊÿPŽsources_5316/external/espeak/espeak-data/mbrola_ph/fr1_phtrans0000644000176700017670000000355411566704204023325 0ustar paulpaull/2ll/ll2lr/Rr/2Rr-Rl-lw/wj/j;g-@-@3*R:Y2W9W29E2Eo2oA~a~E~e~O~o~W~9~w^iHi2wAwa2rRn^njKckIiUuy"yE:Ehn2np2pr2Rt2tt3tz2zz3zi:ii-iu:ueIEj<aUaw<oUoo3oo-o@L@l(@2@@5@3@a#aI2iaaaV@0O3:9aIaj<OIOj<e@Ei@i@<i@3i@<e@E@<o@o@FO@O@FO:OO2OA:aA@a@FU@u@<aI@a@FaU@adZdZ(tStS(TtDz@¸€õ¿Eﵘõ¿sources_5316/external/espeak/espeak-data/mbrola_ph/de2_phtrans0000644000176700017670000000272411403503773023303 0ustar paulpaulI;i:36R<bbbpdddtgggkzzzsl/2ll/lr/6r-Rl-lw/Uj/j;g-@-*j6*RE2EyYW9A:a:Aa:Y:2:OIOY36_|_pFpfrRV#RURUR<eIEj<oUo:W~E~A~a~O~o~@L@l2@2@@5@a#@I2IaaaVa:0O3:@i@i:@<i@3i:@<e@E@<o@o:6FO@O6FO:OA@a:6FU@U@<aI@aI@FaU@aU@FdZtSwv8ñVt1e~·sources_5316/external/espeak/espeak-data/mbrola_ph/ptbr_phtrans0000644000176700017670000000470411566710554023607 0ustar paulpaull/wl/2wll/2jll/2wr/r2r-rw/wj/y;g-@-*jr*r*r2:SxZjtStdZdl^hn^nhNnxrrz_s2ssswssjsss2s#ss#s2rrrr2RrjykskiZktkiZpspiZptpiZbsbiZa/aAa&a&/a&~Nam &~amEeeeImem eINem i/iiNim i~Nim i~imoNom o~j/omi< o~Nom o~omOoou~j/umi< u~Num u~umUoyiaIay<eIey<EIeey<oIoy<OIooy<uIuy<aUaw7&U~@w<eUew7EUeew7iUiw7@@TtDz0oVaIiI2iA:aA@ar<o:oO:oO@or<o@or<i:ii@ia<i@3ir<u:uU@ur<3er<3:er<@Lel(a#aaaae@eroUoOIoi<aI@ae<aU@at2th˜jDÀÓk¶ ê¿øê¿sources_5316/external/espeak/espeak-data/mbrola_ph/pl1_phtrans0000644000176700017670000000303411400042617023310 0ustar paulpaull/2EIl(l/2ll/lr/rr-rRrl-lw/wj/j;i;j-g-@-*ra#ayIEeOoO~o~E~e~S;s'Z;z'ts;ts'dz;dz'n^n'ckQxd;dt;thx@Ii:iu:ueIej<aUaw<oUo@LIl(@2I@5I3Ia#aI2IaaaVaUu0oA:a3:IaIaj<OIoj<i@iI<i@3iI<e@eo@oIFO@oIFO:oA:aA@aU@uI<aI@aIFaU@aTtDzÌ µ¿0Š/ù7 ÓÃp¶øµ¿sources_5316/external/espeak/espeak-data/mbrola_ph/ca1_phtrans0000644000176700017670000000253410603271625023273 0ustar paulpaull/2ll/lr/Rr-Rl-lw/wj/j;g-@-*RY2W9A~a~E~e~O~o~W~9~w^iHn^Jy"YE:3ht2tz2zi:iu:ueIEj<aUaw<oUo@L@l(@2@@5@3@a2@I2IaaaV@0O3:9aIAj<OIOj<e@Ei@i@<e@E@<o@o@FO@O@FO:OA:AA@A@FU@u@<aI@a@FaU@A@dZdZ(tStS(TtDzØA°FÔEÇ¿¨EÇ¿:œF`'/sources_5316/external/espeak/espeak-data/mbrola_ph/cr1_phtrans0000644000176700017670000000416411566704017023322 0ustar paulpaull/2ll/lr/rr_r3r_r/rRrr-rl-lw/wj/j;i;j-g-@-*rr*R2rIiUu8oEe&aAa@e@2eaIaj<iIij<a:ae:ei:io:ou:utS;tS'dZ;dZ'l^Ln^JNnhxddd_sss_zzz_ttt_mmm_nnn_rrr_kkk_eee_ooo_aaa_&aa_3rr_@aeIej<aUau<oUo@Lel(@2e@5e3ra#aI2iIiaaaaaVaUu0oi:iu:uA:a3:raIaj<OIoj<i@ir<i@3ir<e@erFo@orFO@orFOoO:aA:aA@arFU@ur<aI@arFaU@aTtDzwv úú¶Øõ¿sources_5316/external/espeak/espeak-data/mbrola_ph/mx2_phtrans0000644000176700017670000000344411662017743023343 0ustar paulpaull/2ll/lr/rr-rl-lw/wj/i;g-@-*r:**rRs_rrRt_rrRrrR2v#bvbjiJdZJ^dZn^nyNnBbDdQgzsxjuuuuwuuuuwjia/aEeOoaIai<eIei<oIoi<aUaw<eUew<Ssi<Zsi<@e@2e@5u0oVaUuIiI2iA:aA@ar<o:oO:oO@or<o@or<i:ii@ia<i@3ir<u:uU@ur<3er<3:er<@Lel(a#aaaae@eroUoOIoi<aI@ar<aU@at2th̿ڿ°°4ذ4sources_5316/external/espeak/espeak-data/mbrola_ph/cs_phtrans0000644000176700017670000000110410745657130023232 0ustar paulpaull/2lr/rr-rRrl-lw/wj/j;g-@-*rJd'hh\n^n'R^r'R^/r'ct'eIei<aUau<eUeu<oUou<NnQx€»6ÈÅMXŠ8p·6 ¸6sources_5316/external/espeak/espeak-data/mbrola_ph/id1_phtrans0000644000176700017670000000157411566705606023321 0ustar paulpauleEe_sss_?kk_ttt_mmm_nnn_ppp_l/ll_l/2ll/lr/rr-rl-lw/wj/ja/V;i;-g-@-*R2rRraVEeiIoQOQuUn^nY?kSsj<vfRrxh>@Lsources_5316/external/espeak/espeak-data/mbrola_ph/af1_phtrans0000644000176700017670000000314411660663161023300 0ustar paulpaull/2ll/lr/rr-rRrw/wj/j;g-@-*rx2xSsZz_!?e@eA:ao@oY@2aAI@&{W9eI&@U$Yy}A~Ae~Eo~OaIAj<AIajKOIOj<oIujFuIuj<aUAu<iuiu2e:Ei:iu:u@2@@5@I2ia#aaaa0OA@ai@ei@3ee@E@<o@O@FO@O@FU@u@<O:OoU$@2@3@3:@UuVaaI@{@<aU@A@F@LlTtDzdZdz(tSts(ckˆ<Þ¿ïèc¶@°†Š¶sources_5316/external/espeak/espeak-data/mbrola_ph/in1_phtrans0000644000176700017670000000234411114760753023320 0ustar paulpaull/2ll/lr/rr-rl-lw/wj/j;g-@-*r@aVaaa@2a@3a@4aiiii:iiIiie:eeeE:aiEaiE~ai&:aia:aao:oooOoO:auUuuu:uuaIaiaUauo~on<O~aun<u~uun<Hht.Tt.hThd.Dd.hDhJjJhjhn.Nn^NjySshs.shl.l´ ¿j.Mõ2sources_5316/external/espeak/espeak-data/mbrola_ph/ro1_phtrans0000644000176700017670000000416411400042651023320 0ustar paulpauli/iy1l/ll/2lr/rr-rg-wuw/u*r;aea_aa@-jij/jI^_II^I_@U@w<aUaw<eUeuPiUiw<yU1w<oUow<@I@j<iIij<aIaj<eIeidoIoj<uIuj<yI1j<eaEa2eoEo2e[uEu2OaOa2Y@ZJtsTtS_TtSCdZGl;lm;mn;np;pt;tts;Tf;fs;sS;Sb;bd;d*;rv;vz;zZ;Jw2wNni:iu:uIiEe@L@l(@2@@5@3@a#@I2iaaaV@Uu0o3:@OIoJ<i@i@<i@3i@<e@e@<o@o@FO@o@FO:oOoA:eA@a@FU@u@<aI@a@FaU@aTtDzxkhµ¿´"sources_5316/external/espeak/espeak-data/mbrola_ph/de6_phtrans0000644000176700017670000000234411537465522023314 0ustar paulpaulwi:vl/2l(l/lr/6r-Rl-lw/wj/j;g-@-*RE2EyYW9A:a:Aa:Y:2:OIOY36_|?_!?pFpfrRV#RURUR<eIEj<oU@w<W~E~A~a~O~o~@L@l(@2@@5@a#@I2IaaaVa:0a:3:@i@i:@<i@3i:@<e@E@<o@o:6FO@o:6FO:OA@a:6FU@U@<aI@aI@FaU@aU@FdZtS*@Hsources_5316/external/espeak/espeak-data/mbrola/0000755000176700017670000000000011411724742020453 5ustar paulpaulsources_5316/external/espeak/espeak-data/pl_dict0000644000176700017670000011501011663004331020530 0ustar paulpaul)y„ć  A#7#Qla ÁH Š Ä™ A…ć ÄhÂCh ‡źÄ…Ž  Ä™ BAEk ‰Ä…„Å›G €R4USY#3?kVBC@Àksk/k3#Ä\‘Sh C …1#QkB  ęćA ‡ Å› A sk ÆL´šd6€„ źG ‚HTJ%:#:# _i#Jk1…Å›… Ä…„ żE@òR=@0(:#3mAFk †ąż ‡Ä…Å› ‡ Ä… ‡żÄ… †ąż †Ä… ˆÄ…Ä\‘RhÄL°M0 D T’d1#3n ŠÄ…Å5&…M Å&…M  ˆÄ…A%?k97mRkQmailowe A%?k97mRkOmQmailowego A%?k97mRnQmailowy A%?k97m?Qmailom A%?k97%Qmaili A%?k97kQmaile A%?k97k?Qmailem A%?k97#Qmaila A%?k97Qmail AkÃ\’€…ć CER@1R%03m1RmCRpro quo ‰żżą Æ!RQNA DH‘ÈP3#9/AkQ ˆ óÅ‚…ź…Ä™Ä] ‰(Ä,ÉDA&…h0YkVA&kQnie DA&…h0YkVA%iQnich DA&…h0YkVR#WQwas DA&…h0YkW/niQtych DA&…h0YkW/mQto DA&…h0YkW/kQte DA&…h0YkW/pQtÄ… DA&…h0YkVA&pQniÄ… DA&…h0YkV2#WQnas „ż ‡Å› AO9k ‡ Å› ‡Å‚Å›L ˆ łśLÄh@Rh †ż A c#… Ä… † Ä™ †Ä… ‡ Ä…Ä4³‰(#i#YÅh$  ÅL5KI Á$H…żÄ…é àFkX#R%Qvue é àFkX#R%Qvu %03msk2/ †Å¼Ä…Ãi6PF † Å‚Äh@ShÄ,É( † śćA(9m/ ‡ źć ‡ źć CL”€Wk3*OR&#W/1# ‰ ąść +07(WÅP2$ ÅL2$ Ã‚ É „‰MCÐ T€AA,1# †Ä……Ä……Ä… ‰ ź ÇS”0SA8A .13m01#…Ä……Ä……Ä……Ä… CL”…W%3 /W7kYÅ]2Ï  … ż„Ä…A0k7 ‡Ä… †Å‚ż… Ä… † ąż ‡ąż ˆąż… ó… Ä… ‡źÄ™ÅhAP   †  Ä… † żą †żąA4k? ‰Ä™… Ä™ †Ä™ †Ä™ÄhÓÃh ‡ Ä™Ä &$ ˆÄ™A8k2 Æ\‘Sh6€B92#0Yn1:#F…źÃ,C@ö0mV#A%?Qnim C@ö0mV#A&pQniÄ… C@ö0mV#?2pQmnÄ…   é?k/3kFm/k7Qd'hotel A<mR#WQwas A<m/n? Qtym A<m/niQtych A<m/mQto A<m/kQte A<m/pQtÄ… A<mA&pQniÄ… A<mA&kQnie A<mA%?Qnim A<mA&k9Qniej A<m2#WQnas A<m?A&kQmnie Á:&kB1Yk ‰Å‚źń ˆÅ›  Æ@ÅSh6€ Æ4“h6€ _? o?#To_19(V##2O'7' ÈQT‚< C Æ@”M1NB È ó”H B ÆU CÎC ÆMBPá ÃHõÅHÁ0PA Å@à PB Æ=%92ABÅ4“ PPAÅ0”HA Å0à PBÅS…L ÅPÁPAÅ ó“  Æ óPá Å SB_<#0$3/##2O'7' ÆhB2@ Æ=%92@ Æ‘R2@Aà ô”ÄPAHA ÈHU$ÂNðC Æ8ÅHBÄ“EHA È‘L0L$DÄAHA È C ÅHBÄÓÒ$ÅLQ 0PBÅL„$B ÉA2C<2N2@Å@’<0A É@ 8qN2@CÅ0ô“$0Å0‘ÎðAÅ0TÓ$0 Æ0R2ACÅ$ÂAPBÅ5LAÅ ôŽAÅ O@PAÅ 0PB ÉáÉ0'O'7$?''FвR _=$F2x1R' _=$F2x1R'бE а#а#H_<0'?#7''Fп0 н2 ŠÐ½ÐµÐ¼Ð°ÑˆL_@/,O'RW1'#м? л7 к1 и%  и% H \\Ek1W7kY_‚'/R'3$22#R'F2ˆ1_’$F%2$J$22#R'F2ˆ1_‘'/R'3$22#R'F2ˆ1_„V#/R'3$22#R'F2ˆ1 _['/R'3$2xW3$F2xV#O#Fx_â€V#/R'3$22#R'F2ˆ1_“'/R'3$22#R'F2ˆ1_–k2s,/x __s,/x!_]V#/R'3$2xW3$F2xV#O#Fx_—k?s,/x ŠÐ½ÐµÑмеL †ÑмеH _`O#R%WŒÐ½ÐµÐ¼Ð°Ð¼ÐµL ŠÐ½ÐµÐ¼Ð°Ð¼L_‹'/R'3$22#R'F2ˆ1 _{'/R'3$2xO'7$?xV#O#Fx"_}V#/R'3$2xO'7$?#xV#O#Fx_|R$3/%1#72xs,/x„ÑеH„ÑиH ÑоW  †Ð±ÐµÐ°H_1MA3?%7%#"F#_1MA2?%7%'2_1MA1%79#Fx„воHa0b1cF[ Gd~_dzUd4Re5fDg3hEi8jXk:ljYl;m<njZn=o>p?r@sAaHtBuCv2z7~6S\ćLÄJÄ‘KÅ¡YžXа#бEв QRгOдFе$жXзVи%% к1л7м?н2о'п0Ñ€CC",A3AA Ñ€ÑWÑ‚/у(Ñ„QÑ…iцsчLшYÑ“KÑ•tј9Ñ™=ÑšAÑœ‹ÑŸIa#j‡rbEcsdFžIztexe .$1W$j$jkfQgOhciini .%2%%j9A 9 k1l-7j =m?n2jAgBko'up0q1u1Rr,A3AA rsWt/u(vRwRx1Wy%9zVα#7Qx¬#7Qx/'2'W·$/x®$/x/'2'Wµ$0Wˆ7'2­$0Wˆ7'2/'2'W¿'?ˆ1'2 ¸/c$/xº1#0x¾1W%½2%»7#?Fx¹9'/x¯9'/x/'2'W¼?%²E$/x´F$7/x³O#?x¶V$/xω'?$OxŽ'?$Ox/'2'WŒ'?ˆ1'2/'2'W„/#(€0%ˆ0W%3'O,J1%%0Wˆ7'2/'2'W…O,J1%%0Wˆ7'2‚O,J1'V#R,Y2'W%O?x†Q%ƒW%O?x‡c%*****---..=======$F2x1R'.. - A  - C ßdeäöü*** === ./'J1x-  ?%2(W$F'7x3*tR$VF%J1xíwéyázó{ú|sources_5316/external/espeak/espeak-data/is_dict0000644000176700017670000001253411663004331020537 0ustar paulpaul„ðLÄ”‰HLAE9n † í LA W9nÃáAF9nÃL“ŽLAmQÅQÎTÐAO9nA i| #?k77# †ö HA(9qT +E7rWA,1| /W1{WFˆkOA0m‡…þðL…þðH †  ðL ‡ððHA4m? ‰öððH…ðHÄ4“ŽL ‡Ã¾ LA8m2ƒæLƒæL _0qb=Wo?#Wm??m"ˆ1k ‡Ã¾  LA@09nÃ5S€LÄ4“ $AD1rAHm"ˆÃdbRÃ5S‰LALmWÅ5“„% L„ óLAP/9nÄ4“Ž$LAXR#QA\/RvR#7FR#QA`ncW_1M2z2?kF79}2AdsQW%7p2l †Ã¾ L †Ã¾ LAhWn/# †Ã¾LÄTá HHÃ5S”LÃ5S•LÃÔL †Ã¾L † í LÂ`L †á L ‡ðH ‡é LÃRÀÄ “ŽLÅ5S„TÐL_2M2/Rx"ˆ?kF79}2 Dó Ep77#…þ LÄMSUHLÄ “Ž$Là •L † íL †Ã¡Ã°Â HÃ%HÅ “Ž LÃ8R@L ‡ð H_ 1p??# …þ LÃ8SAÅãI0„þL„þH Æ8òËU#€L_3M2Uˆ9|"ˆ?kF79}2Ä “‰HL ‡ðH…á LÄ „„ ðL„þ LÃL„áLÂ`L… íL †í Là H ‡Ã¾Ã­ L… íL ‡ðL„ ðL„ ðH…áLà “ŽL… íLà ŽHà Là “Là “€LÃXTHÄ Q•HHÄ “HLà “•L ˆð ðHà ““L † ðHÅ8òËHLÃUL…íL †Ã¾Ã­L„ áL… í ÄS‡TL _1yiF † ðLÄe HL _2/Rv _3Uˆ9r_4Q9vbs"ˆÄ “•4LÂàL_3XUˆ9|/%&s_0Cis2FsT †Ã¡ L_1CyiFis2F3#TÅ8òËU L Æ8òËU%L _192jF9{2 _18|F9{2ÄXôHL_2C/Rvis2F3sT_11mF7mRs _10/j&s_3CUˆ9ris2F3sT_13UˆmiF{2 _12/}gQ _15Qk?/{2_14Q9}"ˆ/{2 _17W€F9{2_16WmcWF{2 ˆÃ¾ L_7XW9v/%&s †Ã¡ L_4CQ9vbs"ˆis2F3sTÃUL…þ L…þ L_2X/siFsbs †íL ‡Ã¾Ã­L…þ L…þ HÄ!cÒP„æL _??/{Oi„_4XQ9v3s/%&sÅ4“Ž L ói#77}_5XQk?/%&s_6XWmcWF%&sÃLS@LÃ4•L_8X{iF#/%&s ‡ ðL_9X2j&s/%&sÃ4“ŽL † ð †  ðL † ðH…þLƒÃ¡L„úHÄU4L_0M2?kF79}2_0M1UrWs2F D5“ ?k77# Æ8òËH€LÃXô€LÄUHLÃXôL Æ8òËH”€LƒÃ©H„ ðL…þ ðHƒéÄXQÎÄXQÎÄd²ÕHLÄ<²ÕHLÃQÎÄ5S„$LÃ4‘ÀLÑÁLÅ5S„% L †ð H…ðHÂpFO7pRk7q1#WFÅS‡TÐL _?sl"ÅPPP _=%O:pf _=%O:#7e _2?1W@ὺ( hὺi( há½¶ivá½¶v'Ï…( hÏ…i( hιivιvA0B3CWDWE/Fhá½¶i}á½¶}hιi}nι}GQHcI0WJhá½¶i{ hὺi| á½¶{ ὺ| hιi{ hÏ…i| l ι{ Ï…| K%Lhá½¶i}á½¶}hιi}nι}a#upisbEdFe$i$ uqfQggBOOhii%j9k1hcl7m?n2o'u( ivp0hQqk iu uz r3sWt/hUuni}vRwl i{u|xcyni}zVá½°#á½²$á½¶%ῒὸ'á½´k á½¼l ὺnῢᾲs á¿‚u ῲ{ 'á¾³s ῃu ῳ{ sources_5316/external/espeak/espeak-data/phonindex0000644000176700017670000004563011663004330021117 0ustar paulpaulF¡Õƒ¢‚À°U ™É4"$h  °†°·°ø&°9°z°» Ìm©†(_ /°ü°] Ìn©†(_ /°¾° ‹Å©Ì°`Àñ Ìr©°4 Ìl©°… ¹ÉŠ).j߯ß÷ß(ßYߊß»'àìì'° /0001 °>°_2"h°ð±/0001 °‡ Š'°¸ °é ð± r4$h ¡K`ª¢"K `ª° ô;  r¡Ibª¢"I bª°þ ó? r¡@ vZ¢@ bZj߯ß÷ß(ßYߊß»'àìì°þ ðÚ €ÊŠ)h°ë ó,°ë°ô,jÐîÐÐ@`ßaÐ’ÐÓŠ)8Š)hl@ì€íE î† î·€íø€íI°Š‘ àì«`'€í«'°Ì/ °ý8 °°?)7l@ì€íE î† î·€íø€íI9%°†:%°†°Š)7‘Â9%°`:%°‘l@ìÒàì€í` îTàì•€í‘)7làæàà(àIàzÀî«°Š ŽÊ¢RjÐÌÐýÐ.Ð_ÐÐÑ'°°S ­É°”)hjÐÅÐöÐ'ÐXЉк îë'h° °  `¢ h°=°~+hjЯÐðÐ1 Ðr У Ðô î%!'h°F!`¢#°g! h Š)jИ!ÐÉ!Ðú!Ð+"Ð\"Ð" €íÎ"'°ï"¢"K TA/ h¡KÔr…)h°#°Q#jÐ’#ÐÓ#Ð$ÐU$Ц$Ðç$Š'+°(%'°Y%Š)°z%¢’2M b¢/h¡OÞš°«%jÐì%Ð-&Ðn&Я&Ðð&Ð1'Š'+°r'72 °£'Š)°Ä' ³É¡™EIX¢¢’2EIX¢/°õ'jÐì%Ð-&Ðn&Я&Ðð&Ð1'Š'+°r'7@ °6(Š)°W( ²É¢rQ rÍ/hЈ(°©(jÐê(ÐK)М)Ðý)Ð^*ÐÏ*'°0+Š) hA$h% `A%h2 °Q+¢”2K n½/h¡O*¬°¢+jÐã+Ð,ÐE,Ðv,Ч,ÐØ, €í -Š'+°:-'°[-Š)°|- ¾É¢ˆI `ª¡ M `ª0 °­-°þ- ¾É%h r2" h¡K^ª°O.`ù±°O.`ù±¡K ^ª"h°€.€ü±""°Á.¢™K Þ©¡K^ª°€.€ü±¢ˆGMÜ©¡ G Ü©°â.¢"I TI/°3//h¡ÕITI…)h°d/ð•/°d/ð›0…)h°ô0ð•/"h°%1ð›0"h°f1ð›0"h°§1ð›0"h°è1ð›0"h°)2ð›0 "h°j2ð›0!"h°«2ð›0°ì2ð›0¡ÕMbª¢"M bª/°-3…)h°^3ð3°™4ðÊ4¡ÕL ^ª¢L ^ª/°-3…)h°^3ð3""h°Á.@öQ5°™4@öQ5¡ÕQ î¼¢"Q .­/° 6…)h°;6ðl6°ú8ð+9 Êd‘¡ãSU öÝ¢U öÝ/° 6/ h…)h°;6ðl6°ú8ð.:…)h°;6ðl6°ú8ð.:¡ãSU öÝ¢U)öÝ/°F;/ h…)h°w;0ò+9°¨;Ðò+9…)h°Ù;0ò+9° <Ðò+9¡ÕI "I .­/°;<…)h°l<ð<°=`ù¾=¡­ TZ¢ TI/ h…)h°`>ð‘>°Ñ@ð‘>…)h°Að‘>°3Að‘>¡©TZ¢ TI/h¢2 TI…)h°`>ð‘>°dA`ù‘>…)h°Að‘>†(+# °•Að‘> ‹Ê¡©TZ¢ TI…)°ÖA°B¢ bª/¡Zª…)h°HBðyB°»DðyB¢ bª/ h¡\ª¢2 \ª…)h°ìD`ôE°ÊGPõE¡Kè«¢"K è«/ h…)h°ûGð,H°†J ø,H…)h°·Jð,H°èJ ø,H Ê¡Id«¢"I d«/ h…)h°ûGðK°†JðK…)h°·JðK°èJðK ‘Ê¡#SU öÝ¢"I .­…)h°=MõnM°/Põ`P ‘Ê¡#SU öÝ¢"I .­…)h°=Mð®R°/Põ`U Ê¡3öÝ¢23öݰ­WñîW¡M î¼¢"I .­/ h…)h°´YðåY°è[ð\…)h°^ðåY°M^ð\¡S öÝ¢"S 6Ü…)h°^ðåY°M^ð\ Ê…)h°~^Àó¿^°~^õ¿^¡ÕKTs¢ÒITA…)À~a""`Ä‚c324"À‚c"À”d7"À_eÀ]f¡ÕMbª¢’Mb¢…)À9g"2324"Àih" ÃAj ÅEk¡Mž¢¢’M^¢…)0ÂAj`ÄRl¡ÕMî¼…)À9mÀ‰o Ét•¡ãSUöÝ…)ÀqÀq¡ãSUöÝ¢3%öÝ…)àÁÚr`Éís¡ÕK’Kn½/¢’K)À™t"2324"ÀÈu2&"ÀXw7"ÀÊx"`ÄVzÀ‹{¡ÕI⛢’Ib›…)€ÂÀ|!"Å}ÃÀ|¢KTA)Àc}À€¡Mbª¢’Mb¢)À‚À3„¡Mbª¢’Mb¢)ÀE02/21"ÀY†À…ˆ¡Mj¬¢Mj¬)ÀmŠÀ ‚Ê¡Id«¢Id«)ÀÃ… Å… ‚Ê¡#S3öÝ¢#R3öÝ)ÀnMÀ`P •É¡#S3öÝ¢B3öÝ)À®RÀ`U ¬ÉjÐîÐÐ@`ßaÐ’ÐÓ'€í«ÀÃì‘¡3öÝ¢’3öÝ)À}”ÀîW¡Mî¼¢’Mn½)€ÇÇ–Á ™)`Ä¿^À¿^ h"Àe›"Àºœ"ÀYž"ÀþŸ "Àd¡!"À£`Äܤ¡ÕMbª¢’Mb¢…)À‡¦Àߨ¡ÙMbª¢M bª/°-3…)h°ìDÀ󇦰v«Àøß¨¡ÕKTs¢ÒITA7"À_eW)À‚c…)ŧ«À”d¡ÕKTs¢ÒITA…)À~a7"À_eÀö«¡ÕMbª¢’Mb¢…)À9gÀ7­¡ãSUöÝ¢U!öÝ…)ÀÈ­ Åù®¡ÕL’Ln½…) ÃVzÀÃVz¡ÕL’Ln½…) ÃÆ¯7"ÀÊx ÅƯ¡Mbª…)ÀEÀ‡±€(hj°s³°´³°s³°ø°õ³&°9°F´°—´°Ø´°µ°Zµ°«µ°ìµ°M¶°ž¶°ÿ¶°P·°¡·°¸°s¸‘T)°Ä¸¡ÕKTs¢ÒITA…)ŧ«W)À‚c7"À_eÀ”d¡ÕM`ª¢’M`¢…)àÁAjÀÃõ¸¡ÕL ^ª¢L ^ª/°-3…)h°^3ð3W)h°Á.àöQ5°™4àöQ5¡ÕMî¼¢’Mn½…)À™tW)ÀÈu2&"ÀXw7"ÀÊx`ÄVz ¾É¡ÕMbª¢M bª/ h/h°‹¹°¼¹`ôÊ4/°í¹°º`ôÊ4Œ'F`/Œ'V`W+h`790: h;`8‘СÕI "I .­/°;<…)h°l<ðOº°=ðOº ¹ÉjÐ?»Ðp»Ð¡»Ðâ»Ð¼ÐD¼'@ìì°_E'oŒ'h`WV,ˆ(°u¼°U‘u ™É)o°U9)s°U ™Él‘°¶¼u(°ç¼°· ɰ(½ a,°·o°i½&°ª½&°ë½&o ªÉ&°,¾ °m¾ °®¾°ï¾,°0¿ ‘ÉË,°0¿, °‘¿&: Ðâ¿°#À °tÀ °tÀ ”ÉË,°tÀ ”ÉË,°tÀ;"°ÅÀ°Á°gÁ ™ÉŠÊ°ÈÁ"&°)°¡·°šÂ,°õ³,° Ã,° Ã,(°lð½Ã,°ÄŽ,°Ä ™É¹É,$h ™É,°ðÄ ŒÊ¹É,$h ŒÊ,°AŰF´°’ŰãŰø°4Æm‘I ™É,°eÆu°·o°–Æ&°×Æ&°×Æ&°Ç °YÇ ŠÊ °šÇ°ï¾ É,°(½,°ÛÇ ‘ÉË,°ÛÇ a°·, °,È&: Ðâ¿°9, °}È ”ÉË,°ÎÈ ”ÉË,°ÎÈ °tÀ°É ¦ÃŠÊ°`É Ëo°F´°±É Ëe°ø°šÂ,°Ê,°cÊ,°½Ã,°ÄŽ,°Ä šÉ,°ÔÊW)p°˰FË)o°FË ™Él°¶¼ ¦Ãu)°w˰ÈË ɰ(½o° Ì&o°ë½&°JÌ&°‹Ì ‘ÉË ""€°ÌÌ ° ͰNÍ""°Í°ÌÌ ‘É˹É,"h ‘ÉË‚ ,°Í,°ðÍ&°#À ""°Aΰ’Î ”É˹É"$h ”ÉË"°AÎ Ëoɹ"$h Ëo"°ÓÎ °$ϰeϰ¶Ï°Ð2 "&°Xа¹Ð° Ñ ›É¹É"$h ›É"°[Ѱ à ªÉ¹É"$h ªÉ"°¼Ñ ŠÊ¹É,$h ŠÊ,°Ò Éaɪ™,°nÒ Éaɪš,°ÏÒ ÉaʪɊ¹"$h ÉaʪŠ"°0Ó<2% h+)h2#‡*h`¡ÕMbª¢’Mb¢…)À9g"2324"Àih" ÃAj ÅEk,°4Æ) ,)°AŰ¡Ó)o°4Æ9)s°4Æu˜°âÓu°âÓ É,°s³ :a,°âÓo°#Ô;"h îÒ°4ưdÔ‘£  e&°¥Ô °æÔ °'Õ ‰Ê°hÕ :a,""h} °©Õ°âÓ Ëa"°©Õ’ e"°Ö&: Ðâ¿9)Z °kÖ ""°Óΰz ”É"°¬Ö o"°íÖ °’Î ‰ÊË)d )hd °hÕ°N× ŒÊ‰Ê°× Ëo°à×9)™;"°!ذ‚ذ‚Ø Ëe°ãذ$Ù e"°Ö ªÉ"°…Ù ‰Ê¹É,"h ‰Êx ,°ÖÙ,°Ä,°!ØŽ ™Él‘°'Ú°Š).‘H,ˆ(°hÚ°U‘A  ™É)o°hÚ9)s°hÚ ¦Ãu°™Úo°ÚÚ&°×Æ&°×Æ&°‹Ì °’Î °Û°\Û É,°hÚ,°Û ‘ÉË,°Û ‘ÉË°Û ,°îÛ&: Ðâ¿°9 ,°}È ”ÉË,°}È °tÀ°?ܰ€Ü ™ÉŠÊ°áÜ2 "&°2ݰ£Ý°ôÝ,°UÞ,°¦Þ ”ÉË,°ß,°ÄŽ,°Hßm‘Iu°·o°ø&72;"°×ư©ß&°9 °—´ ŠÊ °šÇ°ï¾ ɰ(½,°ÛÇ ‘ÉË,°ÛÇ a°· ,°«µ ie&°Úß ,°}È ”ÉË,°}È °}È ™Éu°+à ¦ÃŠÊ°`É ŒÊŠÊ°|à ”ɪɰôÝ Ëe°Ýà Éoª°¸ œÉË,°‘¿,°.á,°½Ã,°áŽ,°Ä,°â)o°â°´³o°ø&°©ß&°©ß&°9°$ϰ—´°Aâ°s³°´³,°´³°´³,°—´&°‚â°z,°z,°Ãâ°z°»°ã°F´°ÿ¶°ø°$Ù,°Ö,°eã."h_ °¶ã°çã ɰ®¾°ä ™É."h_ °¶ã°Yä°Šä°»ä°ìä;" îå°Nå;" îå°Nå ™Él°¶¼°å Éi™°Àå&°!æ ŠÊ™É°bæ°Ãæ°ç°uç&°Öç&°7è ›ÉªÉ&°¨è&°ùè ŠÊªÉ&°jé&°Ûé&°<ê°ê°gÁ°ø°}Ȱ‘¿°îê°?밀롭’­n½ÀÃÑë¡@ vZ¢@ bZj߯ß÷ß(ßYߊß»'àìì°þ @öÚ 0k h`°é ð±¡ÕSöÝ¢’SöÝÀXw°·°'î ¨É°hî°©î°æÔ°Ø´°Uk°9 ¨ÉËl°êîn°»j°øm°+ï#°0¿ ‘ɨɰ7è°) Éa¨°)°쵰¨è ™É¨É°¨è°M¶°|ï ¨Éu°|ﰚ ”ɨɰšÂ°Íï Éu¨°Íï¡K`ª¢"K `ª° ô; ¡ÕI "I .­/°;<…)h°l<Àø<°=`ù¾=""h*h`j°Ë‹(i °(½W)> °·"C °ä "C °ä"C &°×Æ°×Æ"C °z"C ""h*h`q°µ°.ð#°.ð: Ðâ¿°ðm: Ðâ¿°ð°»°Àð°!ñ°¡·°¸°rñ°ãذF´°Zµ Ê"9 °³ñ°«µ"P °»ä fp¢KTAÀ€Œ+O`a)7l@ì€íE î† î·€íø€íI°ôñ)hjЯÐðÐ1 Ðr У Ðô î%!'h°ò`¢#°g!%h `+ h,h3`/%h`\'‘€ €Ê+h°ë ó,\'h`†+" É0k °6ò! °gò°˜ò ŠÊɰÉò°ó7‰"0‘¸‰"/‘‰"1‘°´³°ä&°9ˆ(°F´°}Ȱ»°ìµ°M¶°ÿ¶°oó°ùè°s¸°ä°ä&j°Àó&°hî°ä°™Ú°ô°$ϰ}Ȱ«µ°Ø´°Bô°ƒô°Zµ°Äô°%õ°šÂ°oó°võ°Çõ°ö°iö°Êö°÷°l÷°Í÷°ø°oø°Àø°ù°eã°bù r¡Ibª¢"I bª°³ù ó?¡©TZ¢ TI…)°A°•A¡ÕO b›¢’O b›/°-3…)h°^3ð3""h°Á.ÀóQ5°™4ÀóQ5"Àe›"Àºœ"ÀYž"ÀþŸ "`Äôù!"Åôù`Äܤ°ô°0ü°Ḭ̀dÔ°qü°²ü°óü°4ý°hî°uý°ß°F´°—´°¶ý°÷ý°8þ°yþ°ºþ°™Ú°™Ú°«µ°«µ°Zµ°Zµ°%õ°ûþ°ö¡©TZ¢ TI…)°A°•A¡Mž¢¢’M^¢…)ÀÃAjÅRl¡ÕO b›¢’O b›/°-3…)h°^3ð3""h°Á.ÀóQ5°™4ÀóQ52"h°ð±°é ð±¡ÕMî¼¢’Mn½)ÀVz2="€ÂXw7"€ÂÊx""€ÂÈu1" ÀVz@ÁVz"Àe›"Àºœ"ÀYž"ÀþŸ "Àd¡!"À£`Äܤ¡Mbª¢’Mb¢ÀLÿ¡ãSUöÝ¢3%öÝ…)ÀÃÚrÅRl¡èSS öÝ¢2RS)öÝ/°Î…)h°^3òÿW)h°Á.õÿ°™4õÿm à!`n à%`o àF`p0q àg`r à˜`'hlàÉàêà à,àMànn"Ð.`s"а*`o"ÐÑ&`p2q"Ðò!`m"Ð`:"Ð4`r"ÐU`92t"Ðv`)hjЗиÐÙÐúÐÐ<¡GÞ¹ ÊŠ).`Š7'u‘ê‘°] ÊŠ)`" Ê/5051%h°~ðð±Š'h°¯ðð±làÐàñàà3àTàum à–)h°·@ñ±k" °è@ñ±¡GÞ¹ Ê‘Q51505W5/5Y%° l%°J ( °]Š)8`l%;jÐî`ßß@ßaaß‹ ÀÞÓ àì«`'€í«7†(°ÌW7'°Ì/ °ý8 °°?)7m%ଠ`,hlàæàà(àIàzà«k °Ì°ŠŠ)8jÐî`ßß@ßa`ß’ÀÞÓ/ °ý°?°Í °Í +n `U µþ µþ 8"Àî«`)d `U °rñ°rñ9$_ `U °ÚÚ°ÚÚu5;%h+hx `k%+h$hn &`t`+9`K &°óüjЯÐðÐ1 Ðr У Ðô °? )n `U ‹(°€ °F´‹(°Ñ j$Š*°Ñ k$Š*°Ñ °ß99"n `Z °¶ý°¶ýp4$h7 µZµZ °Zµ°Zµ°u¼°u¼°«µk0j%hjÐÅÐ Ð'ÐXЉк`ƒ)hjÐÅÐ Ð'ÐXЉк îë'h° °  `¢ h°=°~°ó„"°ÚÚ°C °” °C ¡Õ­ TZ¢"I TI/h¡ÕITI…)h°d/ð•/°d/ð›0/hk$h°å °3/…97"h°ô0ð•/8"°ì2k"h° ó›0°ì2`ô›0¡Mbª¢M bª/hk$h°7 °-3…)h°^3 ó3k$h°Á. ó3°™4€òÊ4¢«TA)Àc}Å€¡ÕI "I.­/hk$h°h °;<…)h°l<ð†(+# `ƒ4k$ °•AÀó‘> °®¾¢ bªV$°-3…9)h°ìDÐòE/% °ÊGÐòE9ƒ29"h# °ÊG€ò…ˆ)W`9ƒ"V`°ÚÚ°Ø´°{&°×ưAâ°Ì° °0ü¡GÞ¹Š).°^€÷±j"°hÚ°Ÿ‚(hj h ˆ(h\-h `(h`(h`I'l `" m`‚(h j"h°hÚ°Û°hÚ°4Æ&°‚â&°à&°hî°ãذãØ°!°ÚÚ°™Ú°ô°(½°+ï°F´°—´°m¾°Aâ°Ø´°r°³°?ë°w˰ô°E°ãۆ°×°×°%õ°¡ÕKTs¢ÒITA/°3/°%1`ôö«¡M^ª¢’M^¢…)0ÂAj ÃAj¡ÕM^ª¢’M^¢/°-3°y€òAj ˆÊ¡ÕGdª¢’GAd¢À7­ ˆÊh¡ÕGdª¢’GAd¢ÀEk –É¡ÕGdª¢GEdª/°7 …)h°^3ð3°Á.ðÊ4 –Éh¡ÕGdª¢GEdª/°7 °Á.ðEk‘ hc¡ãSUöÝ¢U!öÝ/°F;°F;ðq¡•L’Ln½/°ª…)h°ª0òƯ°ª óƯÁÃÛ°®¾k°· ŒÊˆ)?" °Û;”$k°§°ø°øˆ(‚(°è°à°9°F´°F´x°?ܰ?Ü ‰Ê°)(,h`–°?Ü ‰Ê°)°j°gÁ°U ɰ˰âÓ°ø°ø°à°9°F´°F´°Aâ°Aâ°ÿ¶°¡ÕL ^ª¢L ^ª/°-3…)h°^3ð3""h°Á.@öQ5 ³™4Àóõ¸°hÚ ¨ÉµhÕ Ƀ88ˆ(°Ë ?"ˆ)h °(½#°§°ø°ø°à°×ư9°F´°F´°»°»°ÿ¶°°’ΰÚÚ&°Àó°ß°Aâ° °³ñ°9°ǰ·°+ï°Ø´°Zµ°«µ¡ÕMbª¢’Mb¢Àߨ¡ÕM`ª¢’M`¢…)ÐÂAj ÃAj/"À/¡ÕL ^ª¢L ^ª/°-3…)h°^3ðQ5""h°Á.àöQ5°™4àöQ5Š)8‘ àì«`'€í«'°Ì/ °ý°?°yþ&°à&°à°ÚÚ°ÚÚ°™Ú°™Ún°âÓ°âÓ ɰ Ͱ}Ȱ}Ȱ»°»°M°oó°iö°®°šÂ°s¸°°l÷¡Ibª¢"I bª°þ ó?¡ÕMbª¢’Mb¢…)À‡¦¡Å`¡ÕMbª¢’Mb¢…)À9g0Ç7­¡ÕKTs¢ÒITA…)ŧ«7"À_e€Ç”d¡ÕMî¼¢’Mn½…)À™t2="ÀXw7"ÀÊxÀÃVz¡Mbª¢’Mb¢À‡±°˰ð°×ưZµ°«µ°Ø´°ä °'î°”°”(hˆ(h°Ë°Õ°·°´³(°Ë°Ḭ̀ãŰP· u°°W°¡·°Í÷°ã°M¶°¨¡I "I .­c%Œ+h`c…)h°^ðåY° Áø: ˆ(h/2F"h~‘Nˆ(h/2F"h~~ /‘ˆ(h02E"h~‘+ˆ(h02E"h~~ 0‘¸ˆ(hW2V"h~‘tˆ(hW2V"h~~ W‘j°· ɰË)°õ³°ÚÚ°m&°4ý°®°Ø´ ¨É°ï°0°‘ r¡Ibª¢"I bª°þ ó?¡ÕM`ª¢’M`¢…)0ÂAjÀÃAj¡ãSUöÝ¢3%öÝ…)àÁÚrÀÃÚr¡ÕL ^ª¢L ^ª/°-3…)h°^3ð3W)h°Á.àöQ5°™4àöQ5¡èSS öÝ¢2RS)öÝ/°Î…)h°^3òÿW)h°Á.õÿ°™4õÿ‘ Êd‘‘ Ét•‘T)°Ä¸¢KTA…)Àc}W"Ê€ÀÈ€&°hî&°!æ°ò°ä°ÚÚˆ((°ç¼°·°·°}Ȱ}ȰBô°Ø´°ìµ°M¶°#°ÿ¶°t Ìr©°4 ÌrË©°4 Ìr¡Ibª¢"I bª°èJ!óÅ ÌrÌŠ¡Ibª¢"I bª°p ‘ñÅ Ìl©°… ÌlË©°…¡ÕMbª¢’Mb¢…)À9gÀ7­¡ÕKTs¢ÒITA…)Å”d7"À_e€Ç”d°ÚÚ°âÓ°æÔ°»°¡  Ìr©°4¡Mj¬¢Mj¬…)¡Åò áÆò ¡ÕMfœ…)ÂW#!ÃW# Ét•¡ãSUrÍ…)!Ã%!Ã%¡Kè«¢"K è«…)h°·Jõò °èJaùò ¡ÕQ f¬¢"Q f¬/° 6…)h°;6!óW#°º&õW# Êd‘¡ãSU rÍ/° 6…)h°;6!ó%°º&õ%°Í °âx°·°·°Ë°ÚÚ°øˆ&°à&°hî°}ȉ°Ø´°Bô°ÿ¶¡ÕM`ª¢’M`¢…)0ÂAj ÃAj¡M bª¢M bª/°-3…)h°^3ð3""h°Á.ðÊ4°™4 óÊ4¡Mî¼¢’Mn½Ð ™ °†¡ÕWöÝ¢’WöÝÀXw Êd‘¡ãSU öÝ/° 6…)h°;6ðl6°ú8ð.:&°©ß ɰs³ r¡Ibª¢"I bª°þ ó?¡ÕM`ª¢’M`¢…)1Âë&!Ãë&¡M bª¢M bª/°-3…)h°¹'ðë&°¹'!óë&2"Àê')Àâ*aÄâ*"Àe›2"Àê')Àâ*aÄâ*¡ÕQ î¼¢"Q .­/° 6°ú8ð- Êd‘¡ãSU öÝ/° 6°ú8ðÖ/¡ÕMî¼!ÃÅ1 Ét•¡ãSUöÝÀÖ/¡Kè«¢"K è«…)h°èJ!ó-°èJÁó-¡Mj¬¢Mj¬…)ÁÃ-aÄ-¡ÕI "I .­/°;<…)h°l<ð<°=¡õ 4¡Mî¼¢’Mn½àÁ ™ ­É°” ­É°”¡Mbª¢’Mb¢À…ˆ ²É¢rQ rÍ/hЈ(°©(jÐê(ÐK)М)Ðý)Ð^*ÐÏ*'°0+Š) hA$h% `A%h2 °Q+,h`µþ ó?¡ãSU öÝ/° 6…)h°;6ðl6¡ãSUöÝÀq¢"K TA/ h¡KÔr…)h°#°Q#ÐU$°(%)&o °…4°Ö4X q °5„-s„(%°H5°y5„(h9%h#`%°5„($I,s°5„(h9%h$`vI,s°5°º5„(h9%h$`w°û5„-h9 hu`x„(h9%h$`w°<6„-s„($I,y°<6x|°}6I,~„('°¾6°ï6°07°7|°Ò7X hqwY hqwl hqw%°8°T8„(hd °•8° Ä(°™ÚI,hs„(h9%h„`vI,|°®¾°©î°ö89%h `„(hI,hv`„`I,hsˆ(°(½°79„-#„(h9%h#`„°®¾°(½¡™7K^ª¢K ^ª°x9!ó¹9&‚(°è°à‚(°ä°ÚÚ‚(°¡Ó°Ÿ‚( hƒ-h°Õ ɰÛ°·‚(°ß°z‚(°Bô°Ø´Š);íz:'°«:°ì:¡ÕUn­¢"U%n­/°;<…)h°l<ð<°=`ù¾=j°·°§z°ãØ;+°ä°øz°ÚÚ&°9%&°Àó}°F´;+°}ȰF´}°—´m°Ø´°Ø´°¶Ï°ÿ¶°¸°§°õ³&°è°F´°»°âÓ°ø°ð°+ï°¶ý°Zµ°;°ã° °P·°n;°¸ °Ê"Àe›"Àºœ"ÀYž"ÀþŸ "Àd¡!"À£`Äܤ°¿;°ä°ÚÚ&°9°F´°z°¶ý¡ÕI "I .­9W9)h7'h`b/°;<…)h°l<ð<°=ð¾=9W99"h777 h`T‘à9W9)h7'h`P‘¸‘ô…)h°HB€òyB¡Mbª¢’Mb¢)ÀÃE02/21"ÀY†Å…ˆ ‹Ê¡©TZ¢ TI…)h°Aõ‘>°<õ‘> ¾É;/$C‘€z°1< ɰ(½ °ø °ÚÚ°ÚÚm°zm°F´°µm°Ø´°©ß°?ë&°r<°†°× Ƀ̰³< Ƀ̊ʃ̰ô< ÌoɃ̪ƒ°E=°(½)°(½°´³°Nå°ø&°©ß)9&°©ß°m¾°Ø´ˆ():°Aâ&°ÿ¶&°P·&°¶=°M¶°'> r¡Ibª¢"I bª°þ ó?‘t s ¾É¡ÕObª¢O bª/°í¹°º€òÊ4 ɰ(½ É)°(½‚°´³ Ƀ̰wË Ƀ̊ʃ̰ô&°9 ¨É)&°x>°YÇ(°F´°?Ü):°?ܰn; Ê¡GÞ¹Š).°¹>€÷±‘† ƒÊ ²Ê)&{ h °ú>| °…4} °;?°|?z&°9°ä ¨É°x>°´³°hÚ°­?°Bô°«µ°Ýà°î?°#°O@°À@°A°bA°³A°B°eBŠ).j߯ß÷ß(ßYߊß»'àìì/0001 °‡ °¸ ‘Т ‘®¢"S)TA‘Ö¢’2S)b¢‘À¢ÒI!TA‘Ó¢’O!b¤‘ ¢’M!b¢‘^¢K!TA¡Mbª¢’M!b¢ Ã`P¡Mj¬¢M!j¬À`U¢"I)TI"h°)2ð›0°ì2ð›0‘à¡ÕO b¬¢O)b¬¢ˆI-bª" h¡Gbª°¶Bð±°çB𱡩TZ¢ !TI…)h°Að‘>°•Að‘>¢ !bª…)h°ìDðE°ÊGðE¡K!è«¢"K è«…)h°·Jð,H°èJð,Hˆ(‚(#"€(°¿;°´³°ä&°9°z°Ø´¡ÕM`ª¢’M`¢…)ÀCÀC¡ÕMî¼¢’Mn½…)À™tW)ÀÈu7"ÀÊx`ÄVz°³ñ°ø°õ³°F´°m¾°'>°¶=°¡ °ö¢KTAÀ€&: Ðâ¿°ð&°hî°ãØn°–ưõ³ °ò ™É°²ü°[C°¬C ‰Ê°íC° °.D°NÍ‚(ˆ(°Ë°§°™Ú°_D°z°F´°ƒô°Ø´¡³n½¢’³n½ÁàD°˰hÚ&°hî&: Ðâ¿°9°Ì°²F°óF°4G °ÚÚ°õ³°ãذuG°uG°0ü°0ü°z°+ï°Aâ°Ø´ ‰Ê°¶G ‰Ê˰÷G&°$Ù&°HH&°šÂ ‰ÊªÉ&°ö°™H°êH&°©ß&%°Àó&°×Æ&k°×ưÚÚ°#Ô°Ë#°Ḭ̀®p°Ãâ°Bô(°Ø´°[Is°³ñ°œIu°œI°‚Øw°‚ذP·y°P·°iö{°iö°ÝI}°ÝI°J°J°¸°³ñ #m¢"K TA°oJ #n¢’2M b¢jÐì%Ð-&Ðn&Я&Ðð&Ð1'°°J ²É#¢bQ n½°ñJ ‹Å#¢”2K n½jÐã+Ð,ÐE,Ðv,Ч,ÐØ,°2K #lÁì‘ lt#¡ÕMbª¢’Mb¢!ÃsK #r°ÍMð±¡ÕKTZ¢"I TJÀ›0¡ÕM bª¢M bª…)À3ÅÊ4¡ÕI "I .­…)À<`ɾ=’¸7’88’¸8’89’¸9“8:’¸:“8;’88°¿;°1<°Nå°ø&:%ÐX°Àó°_D°+ï°îN°/O°pO°pO°±O°ÿ¶°ûþ°ûþ°P·°¡·°¶=°¸°s¸°P°cP°gÁ°M¶°'>°ž¶°+à°+à°ÄP°bù°½Ã¡Sî¼¢’Sn½ ÃÇ–Š);‘°%Q’¸7’¸8’¸7’88’¸8’¸7’88¡ÕMbª¢’Mb¢Àߨ¡ÕMî¼…)À9mÀ‰o¡ÕK’Kn½…)À"ÀXw"23"ÀÈu7"ÀÊx"`ÄVzÀ‹{¡ÕKTs¢ÒITA…)ÀÀ]f¡ÕQbª¢’Mb¢…)ÀÀEk°0ü°M°ã°fQ°çQ°(½°Ýà°xR°õ³°P·°ÙR°'>&14B$hK °×ư9°ZS°ž¶)B°ëS°z°Wm0$"%s" _=$O#7 _?#`l"1$ _h?sCs @1C1 AiCi BrCr C6C6 DNCN EC  ??C C? FiCi GC  22C C2 HÕ¿ YYCY I'Õµ ÕµA'9Ö‚(Õµ(9Ö‚ARR'JJCJ K0C0 LICI MCCC NB WWCW ORCR P/C/ QC  ""C C" RpCp SRCR TC0 oUqCq V'WQCQ $F'7 sources_5316/external/espeak/espeak-data/ru_dict0000644000176700017670000001401511663004331020546 0ustar paulpaulŒ ÁÁHA RwA RH _dpt % #"$Yw/1#Å@ðœMÐJA$%H $F'77#" %0"|lw2/&#?0$"W#2F *VR$VF# +07W /W7wYÃ$ÆIÃ$ÝI Æ@ð”DÀJ ="#R2' @W'E#1#AHwWAHWHAP(Hà à Ià ÃIÅHÓÇ0I \Ew1W7wY ^1"qY1# _0'FL~"1 ~/%7F#Á€HÄ AF4IÁHà ATIÄ AFLIÁ HÃ4öHÃ4ñ#J_dpt2 ns]#/…cÃ4ñJÅHÓÇÐIà ÃIÄ ATLI Æ@ð”c@JÄa3ÂpÅ AFL`IÅHÓÄ0J â„–2'?$"à ÄÝI Æ@ð”f]JÃIDÝIÃHÓÄIÃÈH_3X/"&%/l|m _0CW/'_19nyR&s/2„/l|m_18R}]s?2„/l|m_2CFR&$]msÅHÓÄ0ðJ_11}n%22|/l|m _10n$]sm_3C/"&%W/#_13/3&s2„/l|m_12FR&s2„/l|m_150&s/2„/l|m_14l&s/q2|/l|m_17]s?2„/l|m_16YxW/2„/l|m_7X]$?ny]|/Ä4ñ $J_4Cl&s/q"&yW/# Æ@ð”dÀJ Æ@ð”dÆJ_5C0&smW'/ _1f'F2#_6CYx]mW'/ _2fFR&$_2XFR„/l|mÄ4ñ E'7&Yw _ (&espeakdata_voices1_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//af", L"af"); Collection_addItem (me.peek(), espeakdata_voices1.transfer()); static unsigned char espeakdata_voices2_data[116] = { 110, 97, 109, 101, 32, 98, 117, 108, 103, 97, 114, 105, 97, 110, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 98, 103, 10, 10, 115, 116, 114, 101, 115, 115, 65, 109, 112, 32, 49, 51, 32, 49, 50, 32, 49, 55, 32, 49, 55, 32, 50, 48, 32, 50, 50, 32, 50, 50, 32, 50, 49, 32, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 49, 56, 48, 32, 49, 55, 48, 32, 32, 50, 48, 48, 32, 50, 48, 48, 32, 32, 50, 48, 48, 32, 50, 48, 48, 32, 32, 50, 49, 48, 32, 50, 50, 48, 0}; autoFileInMemory espeakdata_voices2 = FileInMemory_createWithData (115, reinterpret_cast (&espeakdata_voices2_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//bg", L"bg"); Collection_addItem (me.peek(), espeakdata_voices2.transfer()); static unsigned char espeakdata_voices3_data[258] = { 110, 97, 109, 101, 32, 98, 111, 115, 110, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 98, 115, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 104, 114, 10, 100, 105, 99, 116, 105, 111, 110, 97, 114, 121, 32, 104, 98, 115, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 105, 116, 99, 104, 32, 56, 49, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 32, 57, 55, 32, 32, 57, 55, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 32, 57, 55, 32, 32, 57, 55, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 32, 57, 55, 32, 49, 48, 50, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 32, 57, 55, 32, 49, 48, 50, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 32, 57, 55, 32, 49, 48, 50, 32, 49, 48, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 49, 48, 32, 49, 48, 32, 48, 32, 48, 32, 48, 32, 48, 32, 45, 51, 48, 32, 45, 51, 48, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 51, 32, 52, 10, 0}; autoFileInMemory espeakdata_voices3 = FileInMemory_createWithData (257, reinterpret_cast (&espeakdata_voices3_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//bs", L"bs"); Collection_addItem (me.peek(), espeakdata_voices3.transfer()); static unsigned char espeakdata_voices4_data[39] = { 110, 97, 109, 101, 32, 99, 97, 116, 97, 108, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 99, 97, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices4 = FileInMemory_createWithData (38, reinterpret_cast (&espeakdata_voices4_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//ca", L"ca"); Collection_addItem (me.peek(), espeakdata_voices4.transfer()); static unsigned char espeakdata_voices5_data[37] = { 110, 97, 109, 101, 32, 99, 122, 101, 99, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 99, 115, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices5 = FileInMemory_createWithData (36, reinterpret_cast (&espeakdata_voices5_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//cs", L"cs"); Collection_addItem (me.peek(), espeakdata_voices5.transfer()); static unsigned char espeakdata_voices6_data[55] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 99, 121, 10, 110, 97, 109, 101, 32, 119, 101, 108, 115, 104, 45, 116, 101, 115, 116, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 52, 10, 0}; autoFileInMemory espeakdata_voices6 = FileInMemory_createWithData (54, reinterpret_cast (&espeakdata_voices6_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//cy", L"cy"); Collection_addItem (me.peek(), espeakdata_voices6.transfer()); static unsigned char espeakdata_voices7_data[58] = { 110, 97, 109, 101, 32, 100, 97, 110, 105, 115, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 100, 97, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 116, 117, 110, 101, 115, 32, 115, 50, 32, 99, 50, 32, 113, 50, 32, 101, 50, 10, 10, 10, 0}; autoFileInMemory espeakdata_voices7 = FileInMemory_createWithData (57, reinterpret_cast (&espeakdata_voices7_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//da", L"da"); Collection_addItem (me.peek(), espeakdata_voices7.transfer()); static unsigned char espeakdata_voices8_data[39] = { 110, 97, 109, 101, 32, 103, 101, 114, 109, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 100, 101, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 10, 0}; autoFileInMemory espeakdata_voices8 = FileInMemory_createWithData (38, reinterpret_cast (&espeakdata_voices8_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//de", L"de"); Collection_addItem (me.peek(), espeakdata_voices8.transfer()); static unsigned char espeakdata_voices9_data[39] = { 110, 97, 109, 101, 32, 100, 101, 102, 97, 117, 108, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices9 = FileInMemory_createWithData (38, reinterpret_cast (&espeakdata_voices9_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//default", L"default"); Collection_addItem (me.peek(), espeakdata_voices9.transfer()); static unsigned char espeakdata_voices10_data[38] = { 110, 97, 109, 101, 32, 103, 114, 101, 101, 107, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 108, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 10, 0}; autoFileInMemory espeakdata_voices10 = FileInMemory_createWithData (37, reinterpret_cast (&espeakdata_voices10_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//el", L"el"); Collection_addItem (me.peek(), espeakdata_voices10.transfer()); static unsigned char espeakdata_voices11_data[40] = { 110, 97, 109, 101, 32, 101, 115, 112, 101, 114, 97, 110, 116, 111, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 111, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 0}; autoFileInMemory espeakdata_voices11 = FileInMemory_createWithData (39, reinterpret_cast (&espeakdata_voices11_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//eo", L"eo"); Collection_addItem (me.peek(), espeakdata_voices11.transfer()); static unsigned char espeakdata_voices12_data[67] = { 110, 97, 109, 101, 32, 115, 112, 97, 110, 105, 115, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 115, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 49, 10, 47, 47, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 51, 10, 10, 0}; autoFileInMemory espeakdata_voices12 = FileInMemory_createWithData (66, reinterpret_cast (&espeakdata_voices12_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//es", L"es"); Collection_addItem (me.peek(), espeakdata_voices12.transfer()); static unsigned char espeakdata_voices13_data[188] = { 110, 97, 109, 101, 32, 115, 112, 97, 110, 105, 115, 104, 45, 108, 97, 116, 105, 110, 45, 97, 109, 101, 114, 105, 99, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 115, 45, 108, 97, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 115, 45, 109, 120, 32, 54, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 115, 32, 54, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 101, 115, 45, 108, 97, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 50, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 50, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 49, 55, 48, 32, 50, 48, 48, 32, 32, 50, 51, 48, 32, 49, 56, 48, 32, 32, 48, 32, 48, 32, 32, 50, 53, 48, 32, 50, 56, 48, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 84, 32, 115, 10, 0}; autoFileInMemory espeakdata_voices13 = FileInMemory_createWithData (187, reinterpret_cast (&espeakdata_voices13_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//es-la", L"es-la"); Collection_addItem (me.peek(), espeakdata_voices13.transfer()); static unsigned char espeakdata_voices14_data[28] = { 110, 97, 109, 101, 32, 101, 115, 116, 111, 110, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 116, 10, 10, 0}; autoFileInMemory espeakdata_voices14 = FileInMemory_createWithData (27, reinterpret_cast (&espeakdata_voices14_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//et", L"et"); Collection_addItem (me.peek(), espeakdata_voices14.transfer()); static unsigned char espeakdata_voices15_data[39] = { 110, 97, 109, 101, 32, 102, 105, 110, 110, 105, 115, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 102, 105, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices15 = FileInMemory_createWithData (38, reinterpret_cast (&espeakdata_voices15_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//fi", L"fi"); Collection_addItem (me.peek(), espeakdata_voices15.transfer()); static unsigned char espeakdata_voices16_data[83] = { 110, 97, 109, 101, 32, 102, 114, 101, 110, 99, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 102, 114, 45, 102, 114, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 102, 114, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 49, 10, 116, 117, 110, 101, 115, 32, 115, 51, 32, 99, 51, 32, 113, 51, 32, 101, 51, 10, 0}; autoFileInMemory espeakdata_voices16 = FileInMemory_createWithData (82, reinterpret_cast (&espeakdata_voices16_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//fr", L"fr"); Collection_addItem (me.peek(), espeakdata_voices16.transfer()); static unsigned char espeakdata_voices17_data[97] = { 110, 97, 109, 101, 32, 102, 114, 101, 110, 99, 104, 32, 40, 66, 101, 108, 103, 105, 117, 109, 41, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 102, 114, 45, 98, 101, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 102, 114, 32, 56, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 50, 10, 116, 117, 110, 101, 115, 32, 115, 51, 32, 99, 51, 32, 113, 51, 32, 101, 51, 10, 10, 10, 0}; autoFileInMemory espeakdata_voices17 = FileInMemory_createWithData (96, reinterpret_cast (&espeakdata_voices17_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//fr-be", L"fr-be"); Collection_addItem (me.peek(), espeakdata_voices17.transfer()); static unsigned char espeakdata_voices18_data[36] = { 110, 97, 109, 101, 32, 104, 105, 110, 100, 105, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 104, 105, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 0}; autoFileInMemory espeakdata_voices18 = FileInMemory_createWithData (35, reinterpret_cast (&espeakdata_voices18_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//hi", L"hi"); Collection_addItem (me.peek(), espeakdata_voices18.transfer()); static unsigned char espeakdata_voices19_data[291] = { 110, 97, 109, 101, 32, 99, 114, 111, 97, 116, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 104, 114, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 104, 98, 115, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 100, 105, 99, 116, 105, 111, 110, 97, 114, 121, 32, 104, 98, 115, 10, 10, 47, 47, 32, 97, 116, 116, 114, 105, 98, 117, 116, 101, 115, 32, 116, 111, 119, 97, 114, 100, 115, 32, 33, 118, 97, 114, 105, 97, 110, 116, 51, 10, 112, 105, 116, 99, 104, 32, 56, 49, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 32, 57, 55, 32, 32, 57, 55, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 32, 57, 55, 32, 32, 57, 55, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 32, 57, 55, 32, 49, 48, 50, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 32, 57, 55, 32, 49, 48, 50, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 32, 57, 55, 32, 49, 48, 50, 32, 49, 48, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 49, 48, 32, 49, 48, 32, 48, 32, 48, 32, 48, 32, 48, 32, 45, 51, 48, 32, 45, 51, 48, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 49, 10, 0}; autoFileInMemory espeakdata_voices19 = FileInMemory_createWithData (290, reinterpret_cast (&espeakdata_voices19_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//hr", L"hr"); Collection_addItem (me.peek(), espeakdata_voices19.transfer()); static unsigned char espeakdata_voices20_data[74] = { 110, 97, 109, 101, 32, 104, 117, 110, 103, 97, 114, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 104, 117, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 111, 112, 116, 105, 111, 110, 32, 98, 114, 97, 99, 107, 101, 116, 32, 48, 32, 48, 10, 112, 105, 116, 99, 104, 32, 56, 49, 32, 49, 49, 55, 10, 10, 10, 0}; autoFileInMemory espeakdata_voices20 = FileInMemory_createWithData (73, reinterpret_cast (&espeakdata_voices20_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//hu", L"hu"); Collection_addItem (me.peek(), espeakdata_voices20.transfer()); static unsigned char espeakdata_voices21_data[39] = { 110, 97, 109, 101, 32, 97, 114, 109, 101, 110, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 104, 121, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 0}; autoFileInMemory espeakdata_voices21 = FileInMemory_createWithData (38, reinterpret_cast (&espeakdata_voices21_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//hy", L"hy"); Collection_addItem (me.peek(), espeakdata_voices21.transfer()); static unsigned char espeakdata_voices22_data[327] = { 110, 97, 109, 101, 32, 97, 114, 109, 101, 110, 105, 97, 110, 45, 119, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 104, 121, 45, 119, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 104, 121, 32, 32, 56, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 47, 47, 32, 99, 104, 97, 110, 103, 101, 32, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 32, 102, 111, 114, 32, 87, 101, 115, 116, 32, 65, 114, 109, 101, 110, 105, 97, 110, 32, 112, 114, 111, 110, 117, 110, 99, 105, 97, 116, 105, 111, 110, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 98, 32, 32, 112, 35, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 100, 32, 32, 116, 35, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 100, 122, 32, 116, 115, 35, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 100, 90, 32, 116, 83, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 103, 32, 32, 107, 35, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 112, 32, 32, 98, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 116, 32, 32, 100, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 116, 115, 32, 100, 122, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 99, 32, 32, 100, 90, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 107, 32, 32, 103, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 42, 42, 32, 82, 32, 32, 47, 47, 32, 63, 63, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 114, 32, 32, 82, 10, 0}; autoFileInMemory espeakdata_voices22 = FileInMemory_createWithData (326, reinterpret_cast (&espeakdata_voices22_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//hy-west", L"hy-west"); Collection_addItem (me.peek(), espeakdata_voices22.transfer()); static unsigned char espeakdata_voices23_data[152] = { 110, 97, 109, 101, 32, 105, 110, 100, 111, 110, 101, 115, 105, 97, 110, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 105, 100, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 49, 54, 48, 32, 50, 48, 48, 32, 32, 49, 56, 48, 32, 49, 56, 48, 32, 32, 48, 32, 48, 32, 32, 50, 50, 48, 32, 50, 52, 48, 10, 115, 116, 114, 101, 115, 115, 65, 109, 112, 32, 32, 32, 32, 49, 54, 32, 32, 49, 56, 32, 32, 32, 49, 56, 32, 32, 49, 56, 32, 32, 32, 48, 32, 48, 32, 32, 50, 50, 32, 32, 50, 49, 10, 10, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 32, 56, 48, 32, 56, 48, 10, 0}; autoFileInMemory espeakdata_voices23 = FileInMemory_createWithData (151, reinterpret_cast (&espeakdata_voices23_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//id", L"id"); Collection_addItem (me.peek(), espeakdata_voices23.transfer()); static unsigned char espeakdata_voices24_data[46] = { 110, 97, 109, 101, 32, 105, 99, 101, 108, 97, 110, 100, 105, 99, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 105, 115, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices24 = FileInMemory_createWithData (45, reinterpret_cast (&espeakdata_voices24_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//is", L"is"); Collection_addItem (me.peek(), espeakdata_voices24.transfer()); static unsigned char espeakdata_voices25_data[55] = { 110, 97, 109, 101, 32, 105, 116, 97, 108, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 105, 116, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 105, 32, 73, 10, 10, 0}; autoFileInMemory espeakdata_voices25 = FileInMemory_createWithData (54, reinterpret_cast (&espeakdata_voices25_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//it", L"it"); Collection_addItem (me.peek(), espeakdata_voices25.transfer()); static unsigned char espeakdata_voices26_data[32] = { 110, 97, 109, 101, 32, 103, 101, 111, 114, 103, 105, 97, 110, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 107, 97, 10, 0}; autoFileInMemory espeakdata_voices26 = FileInMemory_createWithData (31, reinterpret_cast (&espeakdata_voices26_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//ka", L"ka"); Collection_addItem (me.peek(), espeakdata_voices26.transfer()); static unsigned char espeakdata_voices27_data[56] = { 110, 97, 109, 101, 32, 107, 97, 110, 110, 97, 100, 97, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 107, 110, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 50, 10, 47, 47, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 32, 56, 48, 10, 0}; autoFileInMemory espeakdata_voices27 = FileInMemory_createWithData (55, reinterpret_cast (&espeakdata_voices27_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//kn", L"kn"); Collection_addItem (me.peek(), espeakdata_voices27.transfer()); static unsigned char espeakdata_voices28_data[53] = { 110, 97, 109, 101, 32, 107, 117, 114, 100, 105, 115, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 107, 117, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 47, 47, 119, 111, 114, 100, 115, 32, 49, 32, 52, 56, 10, 10, 0}; autoFileInMemory espeakdata_voices28 = FileInMemory_createWithData (52, reinterpret_cast (&espeakdata_voices28_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//ku", L"ku"); Collection_addItem (me.peek(), espeakdata_voices28.transfer()); static unsigned char espeakdata_voices29_data[299] = { 110, 97, 109, 101, 32, 108, 97, 116, 105, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 108, 97, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 115, 116, 114, 101, 115, 115, 114, 117, 108, 101, 32, 50, 32, 51, 51, 32, 48, 32, 50, 10, 47, 47, 32, 114, 117, 108, 101, 61, 112, 101, 110, 117, 108, 116, 105, 109, 97, 116, 101, 10, 47, 47, 32, 102, 108, 97, 103, 115, 61, 48, 49, 48, 48, 48, 48, 49, 32, 40, 110, 111, 32, 97, 117, 116, 111, 109, 97, 116, 105, 99, 32, 115, 101, 99, 111, 110, 100, 97, 114, 121, 32, 115, 116, 114, 101, 115, 115, 32, 43, 32, 100, 111, 110, 39, 116, 32, 115, 116, 114, 101, 115, 32, 109, 111, 110, 111, 115, 121, 108, 108, 97, 98, 108, 101, 115, 41, 10, 47, 47, 32, 117, 110, 115, 116, 114, 101, 115, 115, 101, 100, 95, 119, 100, 49, 61, 48, 10, 47, 47, 32, 117, 110, 115, 116, 114, 101, 115, 115, 101, 100, 95, 119, 100, 50, 61, 50, 10, 10, 47, 47, 32, 115, 104, 111, 114, 116, 32, 103, 97, 112, 32, 98, 101, 116, 119, 101, 101, 110, 32, 119, 111, 114, 100, 115, 10, 119, 111, 114, 100, 115, 32, 50, 10, 10, 47, 47, 32, 78, 111, 116, 101, 58, 32, 84, 104, 101, 32, 76, 97, 116, 105, 110, 32, 118, 111, 105, 99, 101, 32, 110, 101, 101, 100, 115, 32, 108, 111, 110, 103, 32, 118, 111, 119, 101, 108, 115, 32, 116, 111, 32, 98, 101, 32, 109, 97, 114, 107, 101, 100, 32, 119, 105, 116, 104, 32, 109, 97, 99, 114, 111, 110, 115, 10, 0}; autoFileInMemory espeakdata_voices29 = FileInMemory_createWithData (298, reinterpret_cast (&espeakdata_voices29_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//la", L"la"); Collection_addItem (me.peek(), espeakdata_voices29.transfer()); static unsigned char espeakdata_voices30_data[58] = { 110, 97, 109, 101, 32, 108, 97, 116, 118, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 108, 118, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 32, 111, 32, 32, 111, 58, 10, 10, 0}; autoFileInMemory espeakdata_voices30 = FileInMemory_createWithData (57, reinterpret_cast (&espeakdata_voices30_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//lv", L"lv"); Collection_addItem (me.peek(), espeakdata_voices30.transfer()); static unsigned char espeakdata_voices31_data[47] = { 110, 97, 109, 101, 32, 109, 97, 99, 101, 100, 111, 110, 105, 97, 110, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 109, 107, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices31 = FileInMemory_createWithData (46, reinterpret_cast (&espeakdata_voices31_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//mk", L"mk"); Collection_addItem (me.peek(), espeakdata_voices31.transfer()); static unsigned char espeakdata_voices32_data[70] = { 110, 97, 109, 101, 32, 109, 97, 108, 97, 121, 97, 108, 97, 109, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 109, 108, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 50, 10, 47, 47, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 32, 56, 48, 10, 0}; autoFileInMemory espeakdata_voices32 = FileInMemory_createWithData (69, reinterpret_cast (&espeakdata_voices32_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//ml", L"ml"); Collection_addItem (me.peek(), espeakdata_voices32.transfer()); static unsigned char espeakdata_voices33_data[41] = { 108, 97, 110, 103, 117, 97, 103, 101, 32, 110, 108, 10, 110, 97, 109, 101, 32, 100, 117, 116, 99, 104, 45, 116, 101, 115, 116, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 0}; autoFileInMemory espeakdata_voices33 = FileInMemory_createWithData (40, reinterpret_cast (&espeakdata_voices33_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//nl", L"nl"); Collection_addItem (me.peek(), espeakdata_voices33.transfer()); static unsigned char espeakdata_voices34_data[66] = { 110, 97, 109, 101, 32, 110, 111, 114, 119, 101, 103, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 110, 111, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 110, 98, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 52, 10, 0}; autoFileInMemory espeakdata_voices34 = FileInMemory_createWithData (65, reinterpret_cast (&espeakdata_voices34_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//no", L"no"); Collection_addItem (me.peek(), espeakdata_voices34.transfer()); static unsigned char espeakdata_voices35_data[51] = { 110, 97, 109, 101, 32, 112, 111, 108, 105, 115, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 112, 108, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 50, 10, 0}; autoFileInMemory espeakdata_voices35 = FileInMemory_createWithData (50, reinterpret_cast (&espeakdata_voices35_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//pl", L"pl"); Collection_addItem (me.peek(), espeakdata_voices35.transfer()); static unsigned char espeakdata_voices36_data[66] = { 110, 97, 109, 101, 32, 98, 114, 97, 122, 105, 108, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 112, 116, 45, 98, 114, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 112, 116, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 50, 10, 10, 0}; autoFileInMemory espeakdata_voices36 = FileInMemory_createWithData (65, reinterpret_cast (&espeakdata_voices36_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//pt", L"pt"); Collection_addItem (me.peek(), espeakdata_voices36.transfer()); static unsigned char espeakdata_voices37_data[97] = { 110, 97, 109, 101, 32, 112, 111, 114, 116, 117, 103, 97, 108, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 112, 116, 45, 112, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 112, 116, 32, 54, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 112, 116, 45, 112, 116, 10, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 49, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 50, 10, 0}; autoFileInMemory espeakdata_voices37 = FileInMemory_createWithData (96, reinterpret_cast (&espeakdata_voices37_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//pt-pt", L"pt-pt"); Collection_addItem (me.peek(), espeakdata_voices37.transfer()); static unsigned char espeakdata_voices38_data[41] = { 110, 97, 109, 101, 32, 114, 111, 109, 97, 110, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 114, 111, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 10, 0}; autoFileInMemory espeakdata_voices38 = FileInMemory_createWithData (40, reinterpret_cast (&espeakdata_voices38_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//ro", L"ro"); Collection_addItem (me.peek(), espeakdata_voices38.transfer()); static unsigned char espeakdata_voices39_data[61] = { 110, 97, 109, 101, 32, 114, 117, 115, 115, 105, 97, 110, 95, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 114, 117, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 97, 32, 97, 35, 10, 10, 0}; autoFileInMemory espeakdata_voices39 = FileInMemory_createWithData (60, reinterpret_cast (&espeakdata_voices39_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//ru", L"ru"); Collection_addItem (me.peek(), espeakdata_voices39.transfer()); static unsigned char espeakdata_voices40_data[38] = { 110, 97, 109, 101, 32, 115, 108, 111, 118, 97, 107, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 115, 107, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices40 = FileInMemory_createWithData (37, reinterpret_cast (&espeakdata_voices40_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//sk", L"sk"); Collection_addItem (me.peek(), espeakdata_voices40.transfer()); static unsigned char espeakdata_voices41_data[116] = { 110, 97, 109, 101, 32, 97, 108, 98, 97, 110, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 115, 113, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 47, 47, 32, 97, 100, 100, 32, 116, 104, 105, 115, 32, 108, 105, 110, 101, 32, 116, 111, 32, 114, 101, 109, 111, 118, 101, 32, 39, 195, 171, 39, 32, 97, 116, 32, 116, 104, 101, 32, 101, 110, 100, 32, 111, 102, 32, 119, 111, 114, 100, 115, 10, 47, 47, 32, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 32, 64, 47, 32, 32, 78, 85, 76, 76, 10, 0}; autoFileInMemory espeakdata_voices41 = FileInMemory_createWithData (115, reinterpret_cast (&espeakdata_voices41_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//sq", L"sq"); Collection_addItem (me.peek(), espeakdata_voices41.transfer()); static unsigned char espeakdata_voices42_data[278] = { 110, 97, 109, 101, 32, 115, 101, 114, 98, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 115, 114, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 100, 105, 99, 116, 105, 111, 110, 97, 114, 121, 32, 104, 98, 115, 10, 10, 47, 47, 32, 97, 116, 116, 114, 105, 98, 117, 116, 101, 115, 32, 116, 111, 119, 97, 114, 100, 115, 32, 33, 118, 97, 114, 105, 97, 110, 116, 51, 32, 112, 105, 116, 99, 104, 32, 56, 48, 32, 49, 50, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 48, 32, 49, 48, 48, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 32, 57, 55, 32, 32, 57, 55, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 32, 57, 55, 32, 32, 57, 55, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 51, 32, 32, 57, 55, 32, 49, 48, 50, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 52, 32, 32, 57, 55, 32, 49, 48, 50, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 53, 32, 32, 57, 55, 32, 49, 48, 50, 32, 49, 48, 48, 10, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 49, 48, 32, 49, 48, 32, 48, 32, 48, 32, 48, 32, 48, 32, 45, 51, 48, 32, 45, 51, 48, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 50, 32, 52, 10, 0}; autoFileInMemory espeakdata_voices42 = FileInMemory_createWithData (277, reinterpret_cast (&espeakdata_voices42_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//sr", L"sr"); Collection_addItem (me.peek(), espeakdata_voices42.transfer()); static unsigned char espeakdata_voices43_data[39] = { 110, 97, 109, 101, 32, 115, 119, 101, 100, 105, 115, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 115, 118, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices43 = FileInMemory_createWithData (38, reinterpret_cast (&espeakdata_voices43_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//sv", L"sv"); Collection_addItem (me.peek(), espeakdata_voices43.transfer()); static unsigned char espeakdata_voices44_data[44] = { 110, 97, 109, 101, 32, 115, 119, 97, 104, 105, 108, 105, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 115, 119, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices44 = FileInMemory_createWithData (43, reinterpret_cast (&espeakdata_voices44_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//sw", L"sw"); Collection_addItem (me.peek(), espeakdata_voices44.transfer()); static unsigned char espeakdata_voices45_data[64] = { 110, 97, 109, 101, 32, 116, 97, 109, 105, 108, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 116, 97, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 50, 10, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 32, 56, 48, 10, 0}; autoFileInMemory espeakdata_voices45 = FileInMemory_createWithData (63, reinterpret_cast (&espeakdata_voices45_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//ta", L"ta"); Collection_addItem (me.peek(), espeakdata_voices45.transfer()); static unsigned char espeakdata_voices46_data[39] = { 110, 97, 109, 101, 32, 116, 117, 114, 107, 105, 115, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 116, 114, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 0}; autoFileInMemory espeakdata_voices46 = FileInMemory_createWithData (38, reinterpret_cast (&espeakdata_voices46_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//tr", L"tr"); Collection_addItem (me.peek(), espeakdata_voices46.transfer()); static unsigned char espeakdata_voices47_data[60] = { 110, 97, 109, 101, 32, 118, 105, 101, 116, 110, 97, 109, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 118, 105, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 119, 111, 114, 100, 115, 32, 49, 10, 112, 105, 116, 99, 104, 32, 56, 48, 32, 49, 49, 56, 10, 0}; autoFileInMemory espeakdata_voices47 = FileInMemory_createWithData (59, reinterpret_cast (&espeakdata_voices47_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//vi", L"vi"); Collection_addItem (me.peek(), espeakdata_voices47.transfer()); static unsigned char espeakdata_voices48_data[595] = { 110, 97, 109, 101, 32, 77, 97, 110, 100, 97, 114, 105, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 122, 104, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 119, 111, 114, 100, 115, 32, 49, 10, 112, 105, 116, 99, 104, 32, 56, 48, 32, 49, 49, 56, 10, 10, 47, 47, 102, 111, 114, 32, 115, 111, 109, 101, 32, 100, 105, 97, 108, 101, 99, 116, 115, 10, 10, 47, 47, 91, 101, 110, 93, 58, 32, 114, 101, 112, 108, 97, 99, 101, 32, 110, 103, 32, 119, 105, 116, 104, 32, 110, 10, 47, 47, 91, 122, 104, 93, 58, 32, 239, 191, 189, 222, 186, 239, 191, 189, 239, 191, 189, 239, 191, 189, 239, 191, 189, 239, 191, 189, 239, 191, 189, 239, 191, 189, 110, 103, 239, 191, 189, 239, 191, 189, 239, 191, 189, 110, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 32, 78, 32, 110, 10, 10, 47, 47, 91, 101, 110, 93, 58, 32, 114, 101, 112, 108, 97, 99, 101, 32, 114, 102, 120, 32, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 10, 47, 47, 91, 122, 104, 93, 58, 32, 239, 191, 189, 222, 190, 239, 191, 189, 239, 191, 189, 239, 191, 189, 239, 191, 189, 239, 191, 189, 239, 191, 189, 239, 191, 189, 114, 239, 191, 189, 239, 191, 189, 239, 191, 189, 108, 239, 191, 189, 239, 191, 189, 122, 239, 191, 189, 239, 191, 189, 101, 114, 239, 191, 189, 239, 191, 189, 239, 191, 189, 101, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 32, 116, 115, 46, 104, 32, 116, 115, 104, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 32, 116, 115, 46, 32, 116, 115, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 32, 115, 46, 32, 115, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 32, 105, 46, 32, 105, 91, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 32, 122, 46, 32, 108, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 32, 122, 46, 32, 122, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 32, 64, 114, 32, 64, 10, 10, 47, 47, 91, 101, 110, 93, 58, 32, 114, 101, 112, 108, 97, 99, 101, 32, 98, 101, 103, 105, 110, 110, 105, 110, 103, 32, 110, 32, 111, 114, 32, 108, 10, 47, 47, 91, 122, 104, 93, 58, 32, 239, 191, 189, 239, 191, 189, 239, 191, 189, 239, 191, 189, 110, 108, 239, 191, 189, 239, 191, 189, 110, 239, 191, 189, 239, 191, 189, 239, 191, 189, 108, 239, 191, 189, 239, 191, 189, 108, 239, 191, 189, 239, 191, 189, 239, 191, 189, 110, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 50, 32, 110, 32, 108, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 50, 32, 108, 32, 110, 10, 10, 47, 47, 91, 101, 110, 93, 58, 32, 114, 101, 112, 108, 97, 99, 101, 32, 98, 101, 103, 105, 110, 110, 105, 110, 103, 32, 119, 32, 119, 105, 116, 104, 32, 118, 10, 47, 47, 91, 122, 104, 93, 58, 32, 119, 239, 191, 189, 239, 191, 189, 239, 191, 189, 118, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 32, 119, 32, 32, 118, 0}; autoFileInMemory espeakdata_voices48 = FileInMemory_createWithData (594, reinterpret_cast (&espeakdata_voices48_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//zh", L"zh"); Collection_addItem (me.peek(), espeakdata_voices48.transfer()); static unsigned char espeakdata_voices49_data[196] = { 110, 97, 109, 101, 32, 99, 97, 110, 116, 111, 110, 101, 115, 101, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 122, 104, 45, 121, 117, 101, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 121, 117, 101, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 122, 104, 121, 10, 10, 116, 114, 97, 110, 115, 108, 97, 116, 111, 114, 32, 122, 104, 121, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 122, 104, 121, 10, 100, 105, 99, 116, 105, 111, 110, 97, 114, 121, 32, 122, 104, 121, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 47, 47, 32, 105, 110, 116, 101, 114, 112, 114, 101, 116, 32, 69, 110, 103, 108, 105, 115, 104, 32, 108, 101, 116, 116, 101, 114, 115, 32, 97, 115, 32, 49, 61, 69, 110, 103, 108, 105, 115, 104, 32, 119, 111, 114, 100, 115, 44, 32, 50, 61, 106, 121, 117, 116, 112, 105, 110, 103, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 49, 10, 10, 119, 111, 114, 100, 115, 32, 49, 10, 0}; autoFileInMemory espeakdata_voices49 = FileInMemory_createWithData (195, reinterpret_cast (&espeakdata_voices49_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices//zh-yue", L"zh-yue"); Collection_addItem (me.peek(), espeakdata_voices49.transfer()); static unsigned char espeakdata_voices50_data[143] = { 110, 97, 109, 101, 32, 101, 110, 103, 108, 105, 115, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 117, 107, 32, 32, 50, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 103, 98, 32, 32, 50, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 32, 50, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 32, 105, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 50, 32, 105, 10, 10, 47, 47, 112, 105, 116, 99, 104, 32, 56, 48, 32, 49, 49, 56, 10, 10, 116, 117, 110, 101, 115, 32, 115, 49, 32, 99, 49, 32, 113, 49, 32, 101, 49, 10, 0}; autoFileInMemory espeakdata_voices50 = FileInMemory_createWithData (142, reinterpret_cast (&espeakdata_voices50_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/en/en", L"en"); Collection_addItem (me.peek(), espeakdata_voices50.transfer()); static unsigned char espeakdata_voices51_data[217] = { 110, 97, 109, 101, 32, 108, 97, 110, 99, 97, 115, 104, 105, 114, 101, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 117, 107, 45, 110, 111, 114, 116, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 117, 107, 32, 32, 51, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 32, 53, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 101, 110, 45, 110, 10, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 49, 54, 48, 32, 49, 53, 48, 32, 32, 49, 56, 48, 32, 49, 56, 48, 32, 32, 50, 50, 48, 32, 50, 50, 48, 32, 32, 50, 57, 48, 32, 50, 57, 48, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 105, 64, 51, 32, 105, 64, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 78, 32, 110, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 32, 32, 105, 10, 47, 47, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 50, 32, 105, 10, 10, 0}; autoFileInMemory espeakdata_voices51 = FileInMemory_createWithData (216, reinterpret_cast (&espeakdata_voices51_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/en/en-n", L"en-n"); Collection_addItem (me.peek(), espeakdata_voices51.transfer()); static unsigned char espeakdata_voices52_data[195] = { 110, 97, 109, 101, 32, 101, 110, 103, 108, 105, 115, 104, 95, 114, 112, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 117, 107, 45, 114, 112, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 117, 107, 32, 32, 52, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 32, 53, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 101, 110, 45, 114, 112, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 32, 111, 64, 32, 32, 79, 64, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 105, 64, 51, 32, 105, 64, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 32, 105, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 50, 32, 105, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 64, 32, 97, 35, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 51, 32, 97, 35, 10, 0}; autoFileInMemory espeakdata_voices52 = FileInMemory_createWithData (194, reinterpret_cast (&espeakdata_voices52_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/en/en-rp", L"en-rp"); Collection_addItem (me.peek(), espeakdata_voices52.transfer()); static unsigned char espeakdata_voices53_data[247] = { 110, 97, 109, 101, 32, 101, 110, 45, 115, 99, 111, 116, 116, 105, 115, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 115, 99, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 32, 52, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 101, 110, 45, 115, 99, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 53, 32, 54, 32, 55, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 32, 49, 56, 48, 32, 49, 51, 48, 32, 50, 48, 48, 32, 50, 48, 48, 32, 48, 32, 48, 32, 50, 53, 48, 32, 50, 55, 48, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 64, 32, 86, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 32, 105, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 50, 32, 105, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 49, 32, 97, 73, 32, 97, 73, 50, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 50, 32, 97, 32, 97, 47, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 50, 32, 117, 58, 32, 85, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 50, 32, 51, 58, 32, 86, 82, 10, 0}; autoFileInMemory espeakdata_voices53 = FileInMemory_createWithData (246, reinterpret_cast (&espeakdata_voices53_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/en/en-sc", L"en-sc"); Collection_addItem (me.peek(), espeakdata_voices53.transfer()); static unsigned char espeakdata_voices54_data[281] = { 47, 47, 32, 109, 111, 118, 105, 110, 103, 32, 116, 111, 119, 97, 114, 100, 115, 32, 85, 83, 32, 69, 110, 103, 108, 105, 115, 104, 10, 110, 97, 109, 101, 32, 101, 110, 103, 108, 105, 115, 104, 45, 117, 115, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 117, 115, 32, 50, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 114, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 32, 51, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 101, 110, 45, 117, 115, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 51, 32, 54, 10, 111, 112, 116, 105, 111, 110, 32, 114, 101, 100, 117, 99, 101, 95, 116, 32, 49, 10, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 49, 52, 53, 32, 49, 50, 53, 32, 49, 57, 48, 32, 49, 55, 48, 32, 48, 32, 48, 32, 50, 54, 48, 32, 51, 48, 48, 10, 115, 116, 114, 101, 115, 115, 65, 109, 112, 32, 32, 49, 55, 32, 49, 54, 32, 32, 49, 57, 32, 49, 57, 32, 32, 49, 57, 32, 49, 57, 32, 32, 50, 49, 32, 49, 57, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 32, 32, 105, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 73, 50, 32, 105, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 64, 32, 32, 64, 47, 10, 0}; autoFileInMemory espeakdata_voices54 = FileInMemory_createWithData (280, reinterpret_cast (&espeakdata_voices54_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/en/en-us", L"en-us"); Collection_addItem (me.peek(), espeakdata_voices54.transfer()); static unsigned char espeakdata_voices55_data[317] = { 110, 97, 109, 101, 32, 101, 110, 45, 119, 101, 115, 116, 105, 110, 100, 105, 101, 115, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 119, 105, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 117, 107, 32, 32, 52, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 32, 49, 48, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 101, 110, 45, 119, 105, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 56, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 49, 55, 53, 32, 49, 55, 53, 32, 32, 49, 55, 53, 32, 49, 55, 53, 32, 32, 50, 50, 48, 32, 50, 50, 48, 32, 32, 50, 53, 48, 32, 50, 57, 48, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 68, 32, 100, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 84, 32, 116, 91, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 85, 64, 32, 111, 64, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 105, 64, 51, 32, 105, 64, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 64, 32, 97, 35, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 51, 32, 97, 35, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 51, 32, 78, 32, 110, 10, 10, 102, 111, 114, 109, 97, 110, 116, 32, 49, 32, 32, 57, 56, 32, 32, 49, 48, 48, 32, 49, 48, 48, 10, 102, 111, 114, 109, 97, 110, 116, 32, 50, 32, 32, 57, 56, 32, 32, 49, 48, 48, 32, 49, 48, 48, 10, 0}; autoFileInMemory espeakdata_voices55 = FileInMemory_createWithData (316, reinterpret_cast (&espeakdata_voices55_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/en/en-wi", L"en-wi"); Collection_addItem (me.peek(), espeakdata_voices55.transfer()); static unsigned char espeakdata_voices56_data[206] = { 110, 97, 109, 101, 32, 101, 110, 103, 108, 105, 115, 104, 95, 119, 109, 105, 100, 115, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 117, 107, 45, 119, 109, 105, 100, 115, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 45, 117, 107, 32, 57, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 101, 110, 32, 57, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 101, 110, 45, 119, 109, 10, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 104, 32, 78, 85, 76, 76, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 111, 64, 32, 79, 64, 10, 114, 101, 112, 108, 97, 99, 101, 32, 48, 48, 32, 105, 64, 51, 32, 105, 64, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 54, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 52, 10, 115, 116, 114, 101, 115, 115, 65, 100, 100, 32, 48, 32, 48, 32, 48, 32, 48, 32, 48, 32, 48, 32, 48, 32, 50, 48, 10, 0}; autoFileInMemory espeakdata_voices56 = FileInMemory_createWithData (205, reinterpret_cast (&espeakdata_voices56_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/en/en-wm", L"en-wm"); Collection_addItem (me.peek(), espeakdata_voices56.transfer()); static unsigned char espeakdata_voices57_data[44] = { 110, 97, 109, 101, 32, 97, 107, 97, 110, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 97, 107, 10, 116, 114, 97, 110, 115, 108, 97, 116, 111, 114, 32, 115, 119, 10, 32, 10, 0}; autoFileInMemory espeakdata_voices57 = FileInMemory_createWithData (43, reinterpret_cast (&espeakdata_voices57_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/ak", L"ak"); Collection_addItem (me.peek(), espeakdata_voices57.transfer()); static unsigned char espeakdata_voices58_data[32] = { 110, 97, 109, 101, 32, 97, 109, 104, 97, 114, 105, 99, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 97, 109, 10, 10, 0}; autoFileInMemory espeakdata_voices58 = FileInMemory_createWithData (31, reinterpret_cast (&espeakdata_voices58_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/am", L"am"); Collection_addItem (me.peek(), espeakdata_voices58.transfer()); static unsigned char espeakdata_voices59_data[36] = { 110, 97, 109, 101, 32, 97, 122, 101, 114, 98, 97, 105, 106, 97, 110, 105, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 97, 122, 10, 10, 0}; autoFileInMemory espeakdata_voices59 = FileInMemory_createWithData (35, reinterpret_cast (&espeakdata_voices59_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/az", L"az"); Collection_addItem (me.peek(), espeakdata_voices59.transfer()); static unsigned char espeakdata_voices60_data[116] = { 110, 97, 109, 101, 32, 98, 117, 108, 103, 97, 114, 105, 97, 110, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 98, 103, 10, 10, 115, 116, 114, 101, 115, 115, 65, 109, 112, 32, 49, 51, 32, 49, 50, 32, 49, 55, 32, 49, 55, 32, 50, 48, 32, 50, 50, 32, 50, 50, 32, 50, 49, 32, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 49, 56, 48, 32, 49, 55, 48, 32, 32, 50, 48, 48, 32, 50, 48, 48, 32, 32, 50, 48, 48, 32, 50, 48, 48, 32, 32, 50, 49, 48, 32, 50, 50, 48, 0}; autoFileInMemory espeakdata_voices60 = FileInMemory_createWithData (115, reinterpret_cast (&espeakdata_voices60_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/bg", L"bg"); Collection_addItem (me.peek(), espeakdata_voices60.transfer()); static unsigned char espeakdata_voices61_data[31] = { 110, 97, 109, 101, 32, 100, 105, 118, 101, 104, 105, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 100, 118, 10, 10, 0}; autoFileInMemory espeakdata_voices61 = FileInMemory_createWithData (30, reinterpret_cast (&espeakdata_voices61_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/dv", L"dv"); Collection_addItem (me.peek(), espeakdata_voices61.transfer()); static unsigned char espeakdata_voices62_data[111] = { 110, 97, 109, 101, 32, 103, 114, 101, 101, 107, 45, 97, 110, 99, 105, 101, 110, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 103, 114, 99, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 49, 55, 48, 32, 49, 55, 48, 32, 32, 49, 57, 48, 32, 49, 57, 48, 32, 32, 48, 32, 48, 32, 32, 50, 51, 48, 32, 50, 52, 48, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 49, 10, 119, 111, 114, 100, 115, 32, 51, 10, 10, 0}; autoFileInMemory espeakdata_voices62 = FileInMemory_createWithData (110, reinterpret_cast (&espeakdata_voices62_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/grc", L"grc"); Collection_addItem (me.peek(), espeakdata_voices62.transfer()); static unsigned char espeakdata_voices63_data[28] = { 110, 97, 109, 101, 32, 104, 97, 105, 116, 105, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 104, 116, 10, 32, 10, 0}; autoFileInMemory espeakdata_voices63 = FileInMemory_createWithData (27, reinterpret_cast (&espeakdata_voices63_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/ht", L"ht"); Collection_addItem (me.peek(), espeakdata_voices63.transfer()); static unsigned char espeakdata_voices64_data[70] = { 110, 97, 109, 101, 32, 108, 111, 106, 98, 97, 110, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 106, 98, 111, 10, 10, 115, 112, 101, 101, 100, 32, 56, 48, 32, 32, 32, 47, 47, 32, 115, 112, 101, 101, 100, 32, 97, 100, 106, 117, 115, 116, 109, 101, 110, 116, 44, 32, 112, 101, 114, 99, 101, 110, 116, 97, 103, 101, 10, 0}; autoFileInMemory espeakdata_voices64 = FileInMemory_createWithData (69, reinterpret_cast (&espeakdata_voices64_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/jbo", L"jbo"); Collection_addItem (me.peek(), espeakdata_voices64.transfer()); static unsigned char espeakdata_voices65_data[27] = { 110, 97, 109, 101, 32, 107, 97, 122, 97, 107, 104, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 107, 107, 10, 32, 10, 0}; autoFileInMemory espeakdata_voices65 = FileInMemory_createWithData (26, reinterpret_cast (&espeakdata_voices65_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/kk", L"kk"); Collection_addItem (me.peek(), espeakdata_voices65.transfer()); static unsigned char espeakdata_voices66_data[33] = { 110, 97, 109, 101, 32, 109, 97, 108, 116, 101, 115, 101, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 109, 116, 10, 32, 10, 0}; autoFileInMemory espeakdata_voices66 = FileInMemory_createWithData (32, reinterpret_cast (&espeakdata_voices66_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/mt", L"mt"); Collection_addItem (me.peek(), espeakdata_voices66.transfer()); static unsigned char espeakdata_voices67_data[127] = { 110, 97, 109, 101, 32, 110, 97, 104, 117, 97, 116, 108, 32, 45, 32, 99, 108, 97, 115, 115, 105, 99, 97, 108, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 110, 99, 105, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 51, 10, 115, 116, 114, 101, 115, 115, 114, 117, 108, 101, 32, 50, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 32, 49, 57, 48, 32, 32, 49, 57, 48, 32, 32, 50, 48, 48, 32, 32, 50, 48, 48, 32, 32, 48, 32, 32, 48, 32, 32, 50, 50, 48, 32, 32, 50, 52, 48, 10, 0}; autoFileInMemory espeakdata_voices67 = FileInMemory_createWithData (126, reinterpret_cast (&espeakdata_voices67_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/nci", L"nci"); Collection_addItem (me.peek(), espeakdata_voices67.transfer()); static unsigned char espeakdata_voices68_data[55] = { 110, 97, 109, 101, 32, 110, 101, 112, 97, 108, 105, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 110, 101, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 10, 100, 105, 99, 116, 114, 117, 108, 101, 115, 32, 49, 10, 0}; autoFileInMemory espeakdata_voices68 = FileInMemory_createWithData (54, reinterpret_cast (&espeakdata_voices68_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/ne", L"ne"); Collection_addItem (me.peek(), espeakdata_voices68.transfer()); static unsigned char espeakdata_voices69_data[48] = { 110, 97, 109, 101, 32, 110, 111, 114, 116, 104, 101, 114, 110, 45, 115, 111, 116, 104, 111, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 110, 115, 111, 10, 116, 114, 97, 110, 115, 108, 97, 116, 111, 114, 32, 115, 119, 10, 0}; autoFileInMemory espeakdata_voices69 = FileInMemory_createWithData (47, reinterpret_cast (&espeakdata_voices69_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/nso", L"nso"); Collection_addItem (me.peek(), espeakdata_voices69.transfer()); static unsigned char espeakdata_voices70_data[31] = { 110, 97, 109, 101, 32, 112, 117, 110, 106, 97, 98, 105, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 112, 97, 10, 0}; autoFileInMemory espeakdata_voices70 = FileInMemory_createWithData (30, reinterpret_cast (&espeakdata_voices70_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/pa", L"pa"); Collection_addItem (me.peek(), espeakdata_voices70.transfer()); static unsigned char espeakdata_voices71_data[52] = { 110, 97, 109, 101, 32, 112, 97, 112, 105, 97, 109, 101, 110, 116, 111, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 112, 97, 112, 10, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 98, 97, 115, 101, 50, 10, 10, 0}; autoFileInMemory espeakdata_voices71 = FileInMemory_createWithData (51, reinterpret_cast (&espeakdata_voices71_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/pap", L"pap"); Collection_addItem (me.peek(), espeakdata_voices71.transfer()); static unsigned char espeakdata_voices72_data[58] = { 110, 97, 109, 101, 32, 100, 97, 114, 105, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 112, 114, 115, 10, 10, 116, 114, 97, 110, 115, 108, 97, 116, 111, 114, 32, 102, 97, 10, 115, 116, 114, 101, 115, 115, 114, 117, 108, 101, 32, 49, 48, 10, 0}; autoFileInMemory espeakdata_voices72 = FileInMemory_createWithData (57, reinterpret_cast (&espeakdata_voices72_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/prs", L"prs"); Collection_addItem (me.peek(), espeakdata_voices72.transfer()); static unsigned char espeakdata_voices73_data[49] = { 110, 97, 109, 101, 32, 107, 105, 110, 121, 97, 114, 119, 97, 110, 100, 97, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 114, 119, 10, 103, 101, 110, 100, 101, 114, 32, 109, 97, 108, 101, 10, 32, 10, 0}; autoFileInMemory espeakdata_voices73 = FileInMemory_createWithData (48, reinterpret_cast (&espeakdata_voices73_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/rw", L"rw"); Collection_addItem (me.peek(), espeakdata_voices73.transfer()); static unsigned char espeakdata_voices74_data[40] = { 110, 97, 109, 101, 32, 115, 105, 110, 104, 97, 108, 97, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 115, 105, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 50, 10, 0}; autoFileInMemory espeakdata_voices74 = FileInMemory_createWithData (39, reinterpret_cast (&espeakdata_voices74_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/si", L"si"); Collection_addItem (me.peek(), espeakdata_voices74.transfer()); static unsigned char espeakdata_voices75_data[84] = { 110, 97, 109, 101, 32, 115, 108, 111, 118, 101, 110, 105, 97, 110, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 115, 108, 10, 32, 10, 115, 116, 114, 101, 115, 115, 76, 101, 110, 103, 116, 104, 32, 32, 32, 49, 54, 48, 32, 49, 53, 48, 32, 32, 50, 52, 48, 32, 50, 52, 48, 32, 32, 50, 52, 48, 32, 50, 52, 48, 32, 32, 51, 48, 48, 32, 51, 50, 48, 0}; autoFileInMemory espeakdata_voices75 = FileInMemory_createWithData (83, reinterpret_cast (&espeakdata_voices75_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/sl", L"sl"); Collection_addItem (me.peek(), espeakdata_voices75.transfer()); static unsigned char espeakdata_voices76_data[55] = { 110, 97, 109, 101, 32, 116, 101, 108, 117, 103, 117, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 116, 101, 10, 10, 105, 110, 116, 111, 110, 97, 116, 105, 111, 110, 32, 50, 10, 47, 47, 99, 111, 110, 115, 111, 110, 97, 110, 116, 115, 32, 56, 48, 10, 0}; autoFileInMemory espeakdata_voices76 = FileInMemory_createWithData (54, reinterpret_cast (&espeakdata_voices76_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/te", L"te"); Collection_addItem (me.peek(), espeakdata_voices76.transfer()); static unsigned char espeakdata_voices77_data[34] = { 110, 97, 109, 101, 32, 115, 101, 116, 115, 119, 97, 110, 97, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 116, 110, 10, 32, 10, 0}; autoFileInMemory espeakdata_voices77 = FileInMemory_createWithData (33, reinterpret_cast (&espeakdata_voices77_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/tn", L"tn"); Collection_addItem (me.peek(), espeakdata_voices77.transfer()); static unsigned char espeakdata_voices78_data[55] = { 110, 97, 109, 101, 32, 117, 114, 100, 117, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 117, 114, 10, 10, 112, 104, 111, 110, 101, 109, 101, 115, 32, 104, 105, 10, 115, 116, 114, 101, 115, 115, 114, 117, 108, 101, 32, 54, 10, 10, 0}; autoFileInMemory espeakdata_voices78 = FileInMemory_createWithData (54, reinterpret_cast (&espeakdata_voices78_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/ur", L"ur"); Collection_addItem (me.peek(), espeakdata_voices78.transfer()); static unsigned char espeakdata_voices79_data[32] = { 110, 97, 109, 101, 32, 119, 111, 108, 111, 102, 45, 116, 101, 115, 116, 10, 108, 97, 110, 103, 117, 97, 103, 101, 32, 119, 111, 10, 10, 32, 10, 0}; autoFileInMemory espeakdata_voices79 = FileInMemory_createWithData (31, reinterpret_cast (&espeakdata_voices79_data), L"/home/david/praat/src/espeak-work/espeak-1.46.14/espeak-data/voices/test/wo", L"wo"); Collection_addItem (me.peek(), espeakdata_voices79.transfer()); return me.transfer(); } catch (MelderError) { Melder_throw (L"FilesInMemory not created."); } } sources_5316/external/espeak/StdAfx.h0000644000176700017670000000010711721443315016356 0ustar paulpaul// This is a dummy file. // A file of this name is needed on Windows sources_5316/external/espeak/wave_pulse.cpp0000664000176700017670000005610611674622653017721 0ustar paulpaul/*************************************************************************** * Copyright (C) 2007, Gilles Casse * * eSpeak driver for PulseAudio * * based on the XMMS PulseAudio Plugin * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ // TBD: // * ARCH_BIG // * uint64? a_timing_info.read_index // * prebuf,... size? // * 0.9.6: pb pulse_free using tlength=8820 (max size never returned -> tlength=10000 ok, but higher drain). // #include "speech.h" #ifdef USE_ASYNC // This source file is only used for asynchronious modes #include #include #include #include #include #include #include #include #include #ifndef PLATFORM_WINDOWS #include #endif #include "wave.h" #include "debug.h" // int is_pulse_running() { pa_sample_spec ss; ss.format = ESPEAK_FORMAT; ss.rate = SAMPLE_RATE; ss.channels = ESPEAK_CHANNEL; pa_simple *s = pa_simple_new(NULL, "eSpeak", PA_STREAM_PLAYBACK, NULL, "is_pulse_running", &ss, NULL, NULL, NULL); if (s) { pa_simple_free(s); return 1; } else return 0; } #endif // USE_PORTAUDIO static pthread_mutex_t pulse_mutex; static pa_context *context = NULL; static pa_stream *stream = NULL; static pa_threaded_mainloop *mainloop = NULL; static int do_trigger = 0; static uint64_t written = 0; static int time_offset_msec = 0; static int just_flushed = 0; static int connected = 0; static int wave_samplerate; #define CHECK_DEAD_GOTO(label, warn) do { \ if (!mainloop || \ !context || pa_context_get_state(context) != PA_CONTEXT_READY || \ !stream || pa_stream_get_state(stream) != PA_STREAM_READY) { \ if (warn) \ SHOW("Connection died: %s\n", context ? pa_strerror(pa_context_errno(context)) : "NULL"); \ goto label; \ } \ } while(0); #define CHECK_CONNECTED(retval) \ do { \ if (!connected) return retval; \ } while (0); #define CHECK_CONNECTED_NO_RETVAL(id) \ do { \ if (!connected){ SHOW("CHECK_CONNECTED_NO_RETVAL: !pulse_connected\n", ""); return; } \ } while (0); //> // static void display_timing_info(const pa_timing_info* the_time) // { // const struct timeval *tv=&(the_time->timestamp); // SHOW_TIME("ti>"); // SHOW("ti> timestamp=%03d.%03dms\n",(int)(tv->tv_sec%1000), (int)(tv->tv_usec/1000)); // SHOW("ti> synchronized_clocks=%d\n",the_time->synchronized_clocks); // SHOW("ti> sink_usec=%ld\n",the_time->sink_usec); // SHOW("ti> source_usec=%ld\n",the_time->source_usec); // SHOW("ti> transport=%ld\n",the_time->transport_usec); // SHOW("ti> playing=%d\n",the_time->playing); // SHOW("ti> write_index_corrupt=%d\n",the_time->write_index_corrupt); // SHOW("ti> write_index=0x%lx\n",the_time->write_index); // SHOW("ti> read_index_corrupt=%d\n",the_time->read_index_corrupt); // SHOW("ti> read_index=0x%lx\n",the_time->read_index); // } static void subscribe_cb(struct pa_context *c, enum pa_subscription_event_type t, uint32_t index, void *userdata) { ENTER(__FUNCTION__); assert(c); if (!stream || index != pa_stream_get_index(stream) || (t != (PA_SUBSCRIPTION_EVENT_SINK_INPUT|PA_SUBSCRIPTION_EVENT_CHANGE) && t != (PA_SUBSCRIPTION_EVENT_SINK_INPUT|PA_SUBSCRIPTION_EVENT_NEW))) return; } static void context_state_cb(pa_context *c, void *userdata) { ENTER(__FUNCTION__); assert(c); switch (pa_context_get_state(c)) { case PA_CONTEXT_READY: case PA_CONTEXT_TERMINATED: case PA_CONTEXT_FAILED: pa_threaded_mainloop_signal(mainloop, 0); break; case PA_CONTEXT_UNCONNECTED: case PA_CONTEXT_CONNECTING: case PA_CONTEXT_AUTHORIZING: case PA_CONTEXT_SETTING_NAME: break; } } static void stream_state_cb(pa_stream *s, void * userdata) { ENTER(__FUNCTION__); assert(s); switch (pa_stream_get_state(s)) { case PA_STREAM_READY: case PA_STREAM_FAILED: case PA_STREAM_TERMINATED: pa_threaded_mainloop_signal(mainloop, 0); break; case PA_STREAM_UNCONNECTED: case PA_STREAM_CREATING: break; } } static void stream_success_cb(pa_stream *s, int success, void *userdata) { ENTER(__FUNCTION__); assert(s); if (userdata) *(int*) userdata = success; pa_threaded_mainloop_signal(mainloop, 0); } static void context_success_cb(pa_context *c, int success, void *userdata) { ENTER(__FUNCTION__); assert(c); if (userdata) *(int*) userdata = success; pa_threaded_mainloop_signal(mainloop, 0); } static void stream_request_cb(pa_stream *s, size_t length, void *userdata) { ENTER(__FUNCTION__); assert(s); pa_threaded_mainloop_signal(mainloop, 0); } static void stream_latency_update_cb(pa_stream *s, void *userdata) { // ENTER(__FUNCTION__); assert(s); pa_threaded_mainloop_signal(mainloop, 0); } static int pulse_free(void) { ENTER(__FUNCTION__); size_t l = 0; pa_operation *o = NULL; CHECK_CONNECTED(0); SHOW("pulse_free: %s (call)\n", "pa_threaded_main_loop_lock"); pa_threaded_mainloop_lock(mainloop); CHECK_DEAD_GOTO(fail, 1); if ((l = pa_stream_writable_size(stream)) == (size_t) -1) { SHOW("pa_stream_writable_size() failed: %s", pa_strerror(pa_context_errno(context))); l = 0; goto fail; } SHOW("pulse_free: %s (ret=%d)\n", "pa_stream_writable_size", l); /* If this function is called twice with no pulse_write() call in * between this means we should trigger the playback */ if (do_trigger) { int success = 0; SHOW("pulse_free: %s (call)\n", "pa_stream_trigger"); if (!(o = pa_stream_trigger(stream, stream_success_cb, &success))) { SHOW("pa_stream_trigger() failed: %s", pa_strerror(pa_context_errno(context))); goto fail; } SHOW("pulse_free: %s (call)\n", "pa_threaded_main_loop"); while (pa_operation_get_state(o) != PA_OPERATION_DONE) { CHECK_DEAD_GOTO(fail, 1); pa_threaded_mainloop_wait(mainloop); } SHOW("pulse_free: %s (ret)\n", "pa_threaded_main_loop"); if (!success) SHOW("pa_stream_trigger() failed: %s", pa_strerror(pa_context_errno(context))); } fail: SHOW("pulse_free: %s (call)\n", "pa_operation_unref"); if (o) pa_operation_unref(o); SHOW("pulse_free: %s (call)\n", "pa_threaded_main_loop_unlock"); pa_threaded_mainloop_unlock(mainloop); do_trigger = !!l; SHOW("pulse_free: %d (ret)\n", (int)l); return (int) l; } static int pulse_playing(const pa_timing_info *the_timing_info) { ENTER(__FUNCTION__); int r = 0; const pa_timing_info *i; assert(the_timing_info); CHECK_CONNECTED(0); pa_threaded_mainloop_lock(mainloop); for (;;) { CHECK_DEAD_GOTO(fail, 1); if ((i = pa_stream_get_timing_info(stream))) { break; } if (pa_context_errno(context) != PA_ERR_NODATA) { SHOW("pa_stream_get_timing_info() failed: %s", pa_strerror(pa_context_errno(context))); goto fail; } pa_threaded_mainloop_wait(mainloop); } r = i->playing; memcpy((void*)the_timing_info, (void*)i, sizeof(pa_timing_info)); // display_timing_info(i); fail: pa_threaded_mainloop_unlock(mainloop); return r; } // static void pulse_flush(int time) { // ENTER(__FUNCTION__); // pa_operation *o = NULL; // int success = 0; // CHECK_CONNECTED(); // pa_threaded_mainloop_lock(mainloop); // CHECK_DEAD_GOTO(fail, 1); // if (!(o = pa_stream_flush(stream, stream_success_cb, &success))) { // SHOW("pa_stream_flush() failed: %s", pa_strerror(pa_context_errno(context))); // goto fail; // } // while (pa_operation_get_state(o) != PA_OPERATION_DONE) { // CHECK_DEAD_GOTO(fail, 1); // pa_threaded_mainloop_wait(mainloop); // } // if (!success) // SHOW("pa_stream_flush() failed: %s", pa_strerror(pa_context_errno(context))); // written = (uint64_t) (((double) time * pa_bytes_per_second(pa_stream_get_sample_spec(stream))) / 1000); // just_flushed = 1; // time_offset_msec = time; // fail: // if (o) // pa_operation_unref(o); // pa_threaded_mainloop_unlock(mainloop); // } static void pulse_write(void* ptr, int length) { ENTER(__FUNCTION__); SHOW("pulse_write > length=%d\n", length); CHECK_CONNECTED_NO_RETVAL(); pa_threaded_mainloop_lock(mainloop); CHECK_DEAD_GOTO(fail, 1); if (pa_stream_write(stream, ptr, length, NULL, PA_SEEK_RELATIVE, (pa_seek_mode_t)0) < 0) { SHOW("pa_stream_write() failed: %s", pa_strerror(pa_context_errno(context))); goto fail; } do_trigger = 0; written += length; fail: pa_threaded_mainloop_unlock(mainloop); } static int drain(void) { pa_operation *o = NULL; int success = 0; int ret = PULSE_ERROR; ENTER(__FUNCTION__); CHECK_CONNECTED(ret); pa_threaded_mainloop_lock(mainloop); CHECK_DEAD_GOTO(fail, 0); SHOW_TIME("pa_stream_drain (call)"); if (!(o = pa_stream_drain(stream, stream_success_cb, &success))) { SHOW("pa_stream_drain() failed: %s\n", pa_strerror(pa_context_errno(context))); goto fail; } SHOW_TIME("pa_threaded_mainloop_wait (call)"); while (pa_operation_get_state(o) != PA_OPERATION_DONE) { CHECK_DEAD_GOTO(fail, 1); pa_threaded_mainloop_wait(mainloop); } SHOW_TIME("pa_threaded_mainloop_wait (ret)"); if (!success) { SHOW("pa_stream_drain() failed: %s\n", pa_strerror(pa_context_errno(context))); } else { ret = PULSE_OK; } fail: SHOW_TIME("pa_operation_unref (call)"); if (o) pa_operation_unref(o); pa_threaded_mainloop_unlock(mainloop); SHOW_TIME("drain (ret)"); return ret; } static void pulse_close(void) { ENTER(__FUNCTION__); drain(); connected = 0; if (mainloop) pa_threaded_mainloop_stop(mainloop); connected = 0; if (context) { SHOW_TIME("pa_context_disconnect (call)"); pa_context_disconnect(context); pa_context_unref(context); context = NULL; } if (mainloop) { SHOW_TIME("pa_threaded_mainloop_free (call)"); pa_threaded_mainloop_free(mainloop); mainloop = NULL; } SHOW_TIME("pulse_close (ret)"); } static int pulse_open() { ENTER(__FUNCTION__); pa_sample_spec ss; pa_operation *o = NULL; int success; int ret = PULSE_ERROR; assert(!mainloop); assert(!context); assert(!stream); assert(!connected); pthread_mutex_init( &pulse_mutex, (const pthread_mutexattr_t *)NULL); ss.format = ESPEAK_FORMAT; ss.rate = wave_samplerate; ss.channels = ESPEAK_CHANNEL; if (!pa_sample_spec_valid(&ss)) return false; SHOW_TIME("pa_threaded_mainloop_new (call)"); if (!(mainloop = pa_threaded_mainloop_new())) { SHOW("Failed to allocate main loop\n",""); goto fail; } pa_threaded_mainloop_lock(mainloop); SHOW_TIME("pa_context_new (call)"); if (!(context = pa_context_new(pa_threaded_mainloop_get_api(mainloop), "eSpeak"))) { SHOW("Failed to allocate context\n",""); goto unlock_and_fail; } pa_context_set_state_callback(context, context_state_cb, NULL); pa_context_set_subscribe_callback(context, subscribe_cb, NULL); SHOW_TIME("pa_context_connect (call)"); if (pa_context_connect(context, NULL, (pa_context_flags_t)0, NULL) < 0) { SHOW("Failed to connect to server: %s", pa_strerror(pa_context_errno(context))); ret = PULSE_NO_CONNECTION; goto unlock_and_fail; } SHOW_TIME("pa_threaded_mainloop_start (call)"); if (pa_threaded_mainloop_start(mainloop) < 0) { SHOW("Failed to start main loop",""); goto unlock_and_fail; } /* Wait until the context is ready */ SHOW_TIME("pa_threaded_mainloop_wait"); pa_threaded_mainloop_wait(mainloop); if (pa_context_get_state(context) != PA_CONTEXT_READY) { SHOW("Failed to connect to server: %s", pa_strerror(pa_context_errno(context))); ret = PULSE_NO_CONNECTION; if (mainloop) pa_threaded_mainloop_stop(mainloop); goto unlock_and_fail; } SHOW_TIME("pa_stream_new"); if (!(stream = pa_stream_new(context, "unknown", &ss, NULL))) { SHOW("Failed to create stream: %s", pa_strerror(pa_context_errno(context))); goto unlock_and_fail; } pa_stream_set_state_callback(stream, stream_state_cb, NULL); pa_stream_set_write_callback(stream, stream_request_cb, NULL); pa_stream_set_latency_update_callback(stream, stream_latency_update_cb, NULL); pa_buffer_attr a_attr; a_attr.maxlength = MAXLENGTH; a_attr.tlength = TLENGTH; a_attr.prebuf = PREBUF; a_attr.minreq = MINREQ; a_attr.fragsize = 0; SHOW_TIME("pa_connect_playback"); if (pa_stream_connect_playback(stream, NULL, &a_attr, (pa_stream_flags_t)(PA_STREAM_INTERPOLATE_TIMING|PA_STREAM_AUTO_TIMING_UPDATE), NULL, NULL) < 0) { SHOW("Failed to connect stream: %s", pa_strerror(pa_context_errno(context))); goto unlock_and_fail; } /* Wait until the stream is ready */ SHOW_TIME("pa_threaded_mainloop_wait"); pa_threaded_mainloop_wait(mainloop); if (pa_stream_get_state(stream) != PA_STREAM_READY) { SHOW("Failed to connect stream: %s", pa_strerror(pa_context_errno(context))); goto unlock_and_fail; } /* Now subscribe to events */ SHOW_TIME("pa_context_subscribe"); if (!(o = pa_context_subscribe(context, PA_SUBSCRIPTION_MASK_SINK_INPUT, context_success_cb, &success))) { SHOW("pa_context_subscribe() failed: %s", pa_strerror(pa_context_errno(context))); goto unlock_and_fail; } success = 0; SHOW_TIME("pa_threaded_mainloop_wait"); while (pa_operation_get_state(o) != PA_OPERATION_DONE) { CHECK_DEAD_GOTO(fail, 1); pa_threaded_mainloop_wait(mainloop); } pa_operation_unref(o); if (!success) { SHOW("pa_context_subscribe() failed: %s", pa_strerror(pa_context_errno(context))); goto unlock_and_fail; } do_trigger = 0; written = 0; time_offset_msec = 0; just_flushed = 0; connected = 1; pa_threaded_mainloop_unlock(mainloop); SHOW_TIME("pulse_open (ret true)"); return PULSE_OK; unlock_and_fail: if (o) pa_operation_unref(o); pa_threaded_mainloop_unlock(mainloop); fail: // pulse_close(); if (ret == PULSE_NO_CONNECTION) { if (context) { SHOW_TIME("pa_context_disconnect (call)"); pa_context_disconnect(context); pa_context_unref(context); context = NULL; } if (mainloop) { SHOW_TIME("pa_threaded_mainloop_free (call)"); pa_threaded_mainloop_free(mainloop); mainloop = NULL; } } else { pulse_close(); } SHOW_TIME("pulse_open (ret false)"); return ret; } void wave_flush(void* theHandler) { ENTER("wave_flush"); // if (my_stream_could_start) // { // // #define buf 1024 // // static char a_buffer[buf*2]; // // memset(a_buffer,0,buf*2); // // wave_write(theHandler, a_buffer, buf*2); // start_stream(); // } } // // // // my_callback_is_output_enabled: no!"); theSize=0; goto terminate; } aTotalFreeMem = pulse_free(); if (aTotalFreeMem >= bytes_to_write) { SHOW("wave_write > aTotalFreeMem(%d) >= bytes_to_write(%d)\n", aTotalFreeMem, bytes_to_write); break; } // TBD: check if really helpful if (aTotalFreeMem >= MAXLENGTH*2) { aTotalFreeMem = MAXLENGTH*2; } SHOW("wave_write > wait: aTotalFreeMem(%d) < bytes_to_write(%d)\n", aTotalFreeMem, bytes_to_write); // 500: threshold for avoiding too many calls to pulse_write if (aTotalFreeMem>500) { pulse_write(aBuffer, aTotalFreeMem); bytes_to_write -= aTotalFreeMem; aBuffer += aTotalFreeMem; } usleep(10000); } pulse_write(aBuffer, bytes_to_write); terminate: pthread_mutex_unlock(&pulse_mutex); SHOW("wave_write: theSize=%d", theSize); SHOW_TIME("wave_write > LEAVE"); return theSize; } //> // ENTER"); int a_status = pthread_mutex_lock(&pulse_mutex); if (a_status) { SHOW("Error: pulse_mutex lock=%d (%s)\n", a_status, __FUNCTION__); return PULSE_ERROR; } drain(); pthread_mutex_unlock(&pulse_mutex); SHOW_TIME("wave_close (ret)"); return PULSE_OK; } //> // // // %lx\n", a_timing_info.read_index); return a_timing_info.read_index; } uint32_t wave_get_write_position(void* theHandler) { pa_timing_info a_timing_info; pulse_playing(&a_timing_info); SHOW("wave_get_read_position > %lx\n", a_timing_info.write_index); return a_timing_info.write_index; } int wave_get_remaining_time(uint32_t sample, uint32_t* time) { double a_time=0; if (!time || !stream) { SHOW("event get_remaining_time> %s\n","audio device not available"); return -1; } pa_timing_info a_timing_info; pulse_playing(&a_timing_info); if (sample > a_timing_info.read_index) { // TBD: take in account time suplied by portaudio V18 API a_time = sample - a_timing_info.read_index; a_time = 0.5 + (a_time * 1000.0) / wave_samplerate; } else { a_time = 0; } SHOW("wave_get_remaining_time > sample=%d, time=%d\n", sample, (uint32_t)a_time); *time = (uint32_t)a_time; return 0; } //> // //tv_sec = tv.tv_sec; ts->tv_nsec = tv.tv_usec*1000; } void add_time_in_ms(struct timespec *ts, int time_in_ms) { if (!ts) { return; } uint64_t t_ns = (uint64_t)ts->tv_nsec + 1000000 * (uint64_t)time_in_ms; while(t_ns >= ONE_BILLION) { SHOW("event > add_time_in_ms ns: %d sec %Lu nsec \n", ts->tv_sec, t_ns); ts->tv_sec += 1; t_ns -= ONE_BILLION; } ts->tv_nsec = (long int)t_ns; } #endif // ifndef USE_PORTAUDIO #endif // USE_ASYNC //> sources_5316/external/espeak/tr_languages.cpp0000644000176700017670000016707311721443315020213 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2011 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, see: * * . * ***************************************************************************/ #include "StdAfx.h" #include #include #include #include #include #include #include #include "speak_lib.h" #include "speech.h" #include "phoneme.h" #include "synthesize.h" #include "translate.h" #define L_qa 0x716100 #define L_grc 0x677263 // grc Ancient Greek #define L_jbo 0x6a626f // jbo Lojban #define L_pap 0x706170 // pap Papiamento] #define L_qvi 0x717669 // qvi Kichwa #define L_shs 0x736873 // shs Shuswap / Secwepemctsin #define L_zhy 0x7a6879 // zhy // start of unicode pages for character sets #define OFFSET_GREEK 0x380 #define OFFSET_CYRILLIC 0x420 #define OFFSET_ARMENIAN 0x530 #define OFFSET_ARABIC 0x600 #define OFFSET_THAANA 0x780 // Divehi/Maldives #define OFFSET_DEVANAGARI 0x900 #define OFFSET_BENGALI 0x980 #define OFFSET_GURMUKHI 0xa00 #define OFFSET_GUJARATI 0xa80 #define OFFSET_ORIYA 0xb00 #define OFFSET_TAMIL 0xb80 #define OFFSET_TELUGU 0xc00 #define OFFSET_KANNADA 0xc80 #define OFFSET_MALAYALAM 0xd00 #define OFFSET_SINHALA 0x0d80 #define OFFSET_TIBET 0x0f00 #define OFFSET_GEORGIAN 0x1080 #define OFFSET_KOREAN 0x1100 #define OFFSET_ETHIOPIC 0x1200 static void Translator_Russian(Translator *tr); static void SetLetterVowel(Translator *tr, int c) {//============================================== tr->letter_bits[c] = (tr->letter_bits[c] & 0x40) | 0x81; // keep value for group 6 (front vowels e,i,y) } static void ResetLetterBits(Translator *tr, int groups) {//==================================================== // Clear all the specified groups unsigned int ix; unsigned int mask; mask = ~groups; for(ix=0; ixletter_bits); ix++) { tr->letter_bits[ix] &= mask; } } static void SetLetterBits(Translator *tr, int group, const char *string) {//===================================================================== int bits; unsigned char c; bits = (1L << group); while((c = *string++) != 0) tr->letter_bits[c] |= bits; } static void SetLetterBitsRange(Translator *tr, int group, int first, int last) {//=========================================================================== int bits; int ix; bits = (1L << group); for(ix=first; ix<=last; ix++) { tr->letter_bits[ix] |= bits; } } static Translator* NewTranslator(void) {//=================================== Translator *tr; int ix; static const unsigned char stress_amps2[] = {18,18, 20,20, 20,22, 22,20 }; static const short stress_lengths2[8] = {182,140, 220,220, 220,240, 260,280}; static const wchar_t empty_wstring[1] = {0}; static const wchar_t punct_in_word[2] = {'\'', 0}; // allow hyphen within words static const unsigned char default_tunes[6] = {0, 1, 2, 3, 0, 0}; tr = (Translator *)Alloc(sizeof(Translator)); if(tr == NULL) return(NULL); tr->charset_a0 = charsets[1]; // ISO-8859-1, this is for when the input is not utf8 dictionary_name[0] = 0; tr->dict_condition=0; tr->data_dictrules = NULL; // language_1 translation rules file tr->data_dictlist = NULL; // language_2 dictionary lookup file tr->transpose_min = 'a'; tr->transpose_max = 'z'; tr->frequent_pairs = NULL; // only need lower case tr->letter_bits_offset = 0; memset(tr->letter_bits,0,sizeof(tr->letter_bits)); memset(tr->letter_groups,0,sizeof(tr->letter_groups)); // 0-6 sets of characters matched by A B C H F G Y in pronunciation rules // these may be set differently for different languages SetLetterBits(tr,0,"aeiou"); // A vowels, except y SetLetterBits(tr,1,"bcdfgjklmnpqstvxz"); // B hard consonants, excluding h,r,w SetLetterBits(tr,2,"bcdfghjklmnpqrstvwxz"); // C all consonants SetLetterBits(tr,3,"hlmnr"); // H 'soft' consonants SetLetterBits(tr,4,"cfhkpqstx"); // F voiceless consonants SetLetterBits(tr,5,"bdgjlmnrvwyz"); // G voiced SetLetterBits(tr,6,"eiy"); // Letter group Y, front vowels SetLetterBits(tr,7,"aeiouy"); // vowels, including y tr->char_plus_apostrophe = empty_wstring; tr->punct_within_word = punct_in_word; for(ix=0; ix<8; ix++) { tr->stress_amps[ix] = stress_amps2[ix]; tr->stress_amps_r[ix] = stress_amps2[ix] - 1; tr->stress_lengths[ix] = stress_lengths2[ix]; } memset(&(tr->langopts),0,sizeof(tr->langopts)); tr->langopts.max_lengthmod = 500; tr->langopts.lengthen_tonic = 20; tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.unstressed_wd1 = 1; tr->langopts.unstressed_wd2 = 3; tr->langopts.param[LOPT_SONORANT_MIN] = 95; tr->langopts.param[LOPT_LONG_VOWEL_THRESHOLD] = 190/2; tr->langopts.param[LOPT_MAXAMP_EOC] = 19; tr->langopts.param[LOPT_UNPRONOUNCABLE] = 's'; // don't count this character at start of word tr->langopts.param[LOPT_BRACKET_PAUSE] = 4; // pause at bracket tr->langopts.param2[LOPT_BRACKET_PAUSE] = 2; // pauses when announcing bracket names tr->langopts.max_initial_consonants = 3; tr->langopts.replace_chars = NULL; tr->langopts.ascii_language = ""; // Non-Latin alphabet languages, use this language to speak Latin words, default is English SetLengthMods(tr,201); // tr->langopts.length_mods = length_mods_en; // tr->langopts.length_mods0 = length_mods_en0; tr->langopts.long_stop = 100; tr->langopts.max_roman = 49; tr->langopts.min_roman = 2; tr->langopts.thousands_sep = ','; tr->langopts.decimal_sep = '.'; tr->langopts.break_numbers = BREAK_THOUSANDS; // 1000, 1000,000 1,000,000 etc tr->langopts.max_digits = 14; memcpy(tr->punct_to_tone, punctuation_to_tone, sizeof(tr->punct_to_tone)); memcpy(tr->langopts.tunes, default_tunes, sizeof(tr->langopts.tunes)); return(tr); } // common letter pairs, encode these as a single byte // 2 bytes, using the transposed character codes static const short pairs_ru[] = { 0x010c, // ла 21052 0x23 0x010e, // на 18400 0x0113, // та 14254 0x0301, // ав 31083 0x030f, // ов 13420 0x060e, // не 21798 0x0611, // ре 19458 0x0903, // ви 16226 0x0b01, // ак 14456 0x0b0f, // ок 17836 0x0c01, // ал 13324 0x0c09, // ил 16877 0x0e01, // ан 15359 0x0e06, // ен 13543 0x30 0x0e09, // ин 17168 0x0e0e, // нн 15973 0x0e0f, // он 22373 0x0e1c, // ын 15052 0x0f03, // во 24947 0x0f11, // ро 13552 0x0f12, // Ñо 16368 0x100f, // оп 19054 0x1011, // рп 17067 0x1101, // ар 23967 0x1106, // ер 18795 0x1109, // ир 13797 0x110f, // ор 21737 0x1213, // Ñ‚Ñ 25076 0x1220, // ÑÑ 14310 0x7fff}; //0x040f ог 12976 //0x1306 ет 12826 //0x0f0d мо 12688 static const unsigned int replace_cyrillic_latin[] = {0x430,'a', 0x431,'b', 0x446,'c', 0x45b,0x107, 0x447,0x10d, 0x45f,'d'+(0x17e<<16), 0x455,'d'+('z'<<16), 0x434,'d', 0x452,0x111, 0x435,'e', 0x444,'f', 0x433,'g', 0x445,'h', 0x438,'i', 0x458,'j', 0x43a,'k', 0x459,'l'+('j'<<16), 0x43b,'l', 0x43c,'m', 0x45a,'n'+('j'<<16), 0x43d,'n', 0x43e,'o', 0x43f,'p', 0x440,'r', 0x441,'s', 0x448,0x161, 0x442,'t', 0x443,'u', 0x432,'v', 0x437,'z', 0x436,0x17e, 0x453,0x111, 0x45c,0x107, 0}; // Ñ“ Ñ• Ñœ static const unsigned char ru_vowels[] = {0x10,0x15,0x31,0x18,0x1e,0x23,0x2b,0x2d,0x2e,0x2f, 0xb9,0xc9,0x91,0x8f,0x36,0}; //also kazakh static const unsigned char ru_consonants[] = {0x11,0x12,0x13,0x14,0x16,0x17,0x19,0x1a,0x1b,0x1c,0x1d,0x1f,0x20,0x21,0x22,0x24,0x25,0x26,0x27,0x28,0x29,0x2a,0x2c, 0x73,0x7b,0x83,0x9b,0}; static void SetCyrillicLetters(Translator *tr) {//=========================================== // character codes offset by 0x420 static const char ru_soft[] = {0x2c,0x19,0x27,0x29,0}; // letter group B [k ts; s;] static const char ru_hard[] = {0x2a,0x16,0x26,0x28,0}; // letter group H [S Z ts] static const char ru_nothard[] = {0x11,0x12,0x13,0x14,0x17,0x19,0x1a,0x1b,0x1c,0x1d,0x1f,0x20,0x21,0x22,0x24,0x25,0x27,0x29,0x2c,0}; static const char ru_voiced[] = {0x11,0x12,0x13,0x14,0x16,0x17,0}; // letter group G (voiced obstruents) static const char ru_ivowels[] = {0x2c,0x2e,0x2f,0x31,0}; // letter group Y (iotated vowels & soft-sign) tr->charset_a0 = charsets[18]; // KOI8-R tr->transpose_min = 0x430; // convert cyrillic from unicode into range 0x01 to 0x22 tr->transpose_max = 0x451; tr->frequent_pairs = pairs_ru; tr->letter_bits_offset = OFFSET_CYRILLIC; memset(tr->letter_bits,0,sizeof(tr->letter_bits)); SetLetterBits(tr,LETTERGP_A,(char *)ru_vowels); SetLetterBits(tr,1,ru_soft); SetLetterBits(tr,2,(char *)ru_consonants); SetLetterBits(tr,3,ru_hard); SetLetterBits(tr,4,ru_nothard); SetLetterBits(tr,5,ru_voiced); SetLetterBits(tr,6,ru_ivowels); SetLetterBits(tr,LETTERGP_VOWEL2,(char *)ru_vowels); } // end of SetCyrillicLetters void SetIndicLetters(Translator *tr) {//================================= // Set letter types for Indic scripts, Devanagari, Tamill, etc static const char dev_consonants2[] = {0x02,0x03,0x58,0x59,0x5a,0x5b,0x5c,0x5d,0x5e,0x5f}; memset(tr->letter_bits,0,sizeof(tr->letter_bits)); SetLetterBitsRange(tr,LETTERGP_A,0x04,0x14); // vowel letters SetLetterBitsRange(tr,LETTERGP_A,0x3e,0x4d); // + vowel signs, and virama SetLetterBitsRange(tr,LETTERGP_A,0x55,0x57); // + vowel signs SetLetterBitsRange(tr,LETTERGP_B,0x3e,0x4d); // vowel signs, and virama SetLetterBitsRange(tr,LETTERGP_B,0x55,0x57); // + vowel signs SetLetterBitsRange(tr,LETTERGP_C,0x15,0x39); // the main consonant range SetLetterBits(tr,LETTERGP_C,dev_consonants2); // + additional consonants SetLetterBitsRange(tr,LETTERGP_Y,0x04,0x14); // vowel letters SetLetterBitsRange(tr,LETTERGP_Y,0x3e,0x4c); // + vowel signs SetLetterBitsRange(tr,LETTERGP_Y,0x55,0x57); // + vowel signs tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words tr->langopts.suffix_add_e = tr->letter_bits_offset + 0x4d; //virama } void SetupTranslator(Translator *tr, const short *lengths, const unsigned char *amps) {//================================================================================== if(lengths != NULL) memcpy(tr->stress_lengths,lengths,sizeof(tr->stress_lengths)); if(amps != NULL) memcpy(tr->stress_amps,amps,sizeof(tr->stress_amps)); } Translator *SelectTranslator(const char *name) {//=========================================== int name2 = 0; Translator *tr; static const short stress_lengths_fr[8] = {190, 170, 190, 200, 0, 0, 190, 240}; static const unsigned char stress_amps_fr[8] = {18,16, 18,18, 18,18, 18,18 }; static const unsigned char stress_amps_sk[8] = {17,16, 20,20, 20,22, 22,21 }; static const short stress_lengths_sk[8] = {190,190, 210,210, 0,0, 210,210}; static const short stress_lengths_ta[8] = {200, 200, 210, 210, 0, 0, 230, 230}; static const unsigned char stress_amps_ta[8] = {18,18, 18,18, 20,20, 22,22 }; // convert name string into a word of up to 4 characters, for the switch() while(*name != 0) name2 = (name2 << 8) + *name++; tr = NewTranslator(); switch(name2) { case L('a','f'): { static const short stress_lengths_af[8] = {170,140, 220,220, 0, 0, 250,270}; SetupTranslator(tr,stress_lengths_af,NULL); tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.vowel_pause = 0x30; tr->langopts.param[LOPT_DIERESES] = 1; tr->langopts.param[LOPT_PREFIXES] = 1; SetLetterVowel(tr,'y'); // add 'y' to vowels tr->langopts.numbers = NUM_SWAP_TENS | NUM_HUNDRED_AND | NUM_SINGLE_AND | NUM_ROMAN | NUM_1900; tr->langopts.accents = 1; } break; case L('a','m'): // Amharic, Ethiopia { SetupTranslator(tr,stress_lengths_fr,stress_amps_fr); tr->letter_bits_offset = OFFSET_ETHIOPIC; tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x0024; // don't use secondary stress tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words tr->langopts.numbers = NUM_OMIT_1_HUNDRED; } break; case L('a','r'): // Arabic tr->letter_bits_offset = OFFSET_ARABIC; tr->langopts.numbers = NUM_SWAP_TENS | NUM_AND_UNITS | NUM_HUNDRED_AND | NUM_OMIT_1_HUNDRED | NUM_AND_HUNDRED | NUM_THOUSAND_AND | NUM_OMIT_1_THOUSAND; tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words break; case L('b','g'): //Bulgarian { SetCyrillicLetters(tr); SetLetterVowel(tr,0x2a); tr->langopts.param[LOPT_UNPRONOUNCABLE] = 0x432; // [v] don't count this character at start of word tr->langopts.param[LOPT_REGRESSIVE_VOICING] = 0x107; // devoice at end of word, and change voicing to match a following consonant (except v) tr->langopts.param[LOPT_REDUCE] = 2; tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_ALLOW_SPACE | NUM_OMIT_1_HUNDRED | NUM_HUNDRED_AND | NUM_AND_UNITS | NUM_SINGLE_AND | NUM_ROMAN | NUM_ROMAN_ORDINAL | NUM_ROMAN_CAPITALS ; tr->langopts.thousands_sep = ' '; // don't allow dot as thousands separator } break; case L('b','n'): // Bengali { static const short stress_lengths_bn[8] = {180, 180, 210, 210, 0, 0, 230, 240}; static const unsigned char stress_amps_bn[8] = {18,18, 18,18, 20,20, 22,22 }; SetupTranslator(tr,stress_lengths_bn,stress_amps_bn); tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x10004; // use 'diminished' for unstressed final syllable tr->letter_bits_offset = OFFSET_BENGALI; SetIndicLetters(tr); // call this after setting OFFSET_BENGALI SetLetterBitsRange(tr,LETTERGP_F,0x3e,0x4c); // vowel signs, but not virama tr->langopts.numbers = 0x1; tr->langopts.break_numbers = 0x24924aa8; // for languages which have numbers for 100,000 and 100,00,000, eg Hindi } break; case L('b','o'): // Tibet { tr->langopts.stress_rule = STRESSPOSN_1L; tr->letter_bits_offset = OFFSET_TIBET; SetLetterBitsRange(tr,LETTERGP_A,0x71,0x7d); // vowel signs SetLetterBitsRange(tr,LETTERGP_B,0x71,0x81); // vowel signs and subjoined letters SetLetterBitsRange(tr,LETTERGP_B,0x90,0xbc); SetLetterBitsRange(tr,LETTERGP_C,0x40,0x6c); // consonant letters (not subjoined) tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words tr->langopts.numbers = 1; } break; case L('c','y'): // Welsh { static const short stress_lengths_cy[8] = {170,220, 180,180, 0, 0, 250,270}; static const unsigned char stress_amps_cy[8] = {17,15, 18,18, 0,0, 22,20 }; // 'diminished' is used to mark a quieter, final unstressed syllable SetupTranslator(tr,stress_lengths_cy,stress_amps_cy); tr->charset_a0 = charsets[14]; // ISO-8859-14 // tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = STRESSPOSN_2R; // tr->langopts.intonation_group = 4; // 'diminished' is an unstressed final syllable tr->langopts.stress_flags = 0x6 | 0x10; tr->langopts.unstressed_wd1 = 0; tr->langopts.unstressed_wd2 = 2; tr->langopts.param[LOPT_SONORANT_MIN] = 120; // limit the shortening of sonorants before short vowels tr->langopts.numbers = NUM_OMIT_1_HUNDRED; SetLetterVowel(tr,'w'); // add letter to vowels and remove from consonants SetLetterVowel(tr,'y'); } break; case L('d','a'): // Danish { static const short stress_lengths_da[8] = {160,140, 200,200, 0,0, 220,230}; SetupTranslator(tr,stress_lengths_da,NULL); tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.param[LOPT_PREFIXES] = 1; SetLetterVowel(tr,'y'); tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_SWAP_TENS | NUM_HUNDRED_AND | NUM_OMIT_1_HUNDRED | NUM_ORDINAL_DOT | NUM_1900 | NUM_ROMAN | NUM_ROMAN_CAPITALS | NUM_ROMAN_ORDINAL; } break; case L('d','e'): { static const short stress_lengths_de[8] = {150,130, 200,200, 0, 0, 270,270}; static const unsigned char stress_amps_de[] = {20,20, 20,20, 20,22, 22,20 }; SetupTranslator(tr, stress_lengths_de, stress_amps_de); tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.word_gap = 0x8; // don't use linking phonemes tr->langopts.vowel_pause = 0x30; tr->langopts.param[LOPT_PREFIXES] = 1; tr->langopts.param[LOPT_REGRESSIVE_VOICING] = 0x100; // devoice at end of word tr->langopts.param[LOPT_LONG_VOWEL_THRESHOLD] = 175/2; tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_SWAP_TENS | NUM_ALLOW_SPACE | NUM_ORDINAL_DOT | NUM_ROMAN; // tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_SWAP_TENS | NUM_OMIT_1_HUNDRED | NUM_OMIT_1_THOUSAND | NUM_ALLOW_SPACE | NUM_ORDINAL_DOT | NUM_ROMAN; SetLetterVowel(tr,'y'); tr->langopts.param[LOPT_UNPRONOUNCABLE] = 2; // use de_rules for unpronouncable rules } break; case L('d','v'): // Divehi (Maldives) { SetupTranslator(tr,stress_lengths_ta,stress_amps_ta); tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->letter_bits_offset = OFFSET_THAANA; tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x10004; // use 'diminished' for unstressed final syllable SetLetterBitsRange(tr,LETTERGP_B,0x26,0x30); // vowel signs, and virama tr->langopts.break_numbers = 0x14a8; // 1000, 100,000 10,000,000 tr->langopts.numbers = 1; } break; case L('e','n'): { static const short stress_lengths_en[8] = {182,140, 220,220, 0,0, 248,275}; SetupTranslator(tr,stress_lengths_en,NULL); tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x08; tr->langopts.numbers = NUM_HUNDRED_AND | NUM_ROMAN | NUM_1900; tr->langopts.param[LOPT_COMBINE_WORDS] = 2; // allow "mc" to cmbine with the following word tr->langopts.suffix_add_e = 'e'; tr->langopts.param[LOPT_UNPRONOUNCABLE] = 2; // use en_rules for unpronouncable rules SetLetterBits(tr,6,"aeiouy"); // Group Y: vowels, including y } break; case L('e','l'): // Greek case L_grc: // Ancient Greek { static const short stress_lengths_el[8] = {155, 180, 210, 210, 0, 0, 270, 300}; static const unsigned char stress_amps_el[8] = {15,12, 20,20, 20,22, 22,21 }; // 'diminished' is used to mark a quieter, final unstressed syllable // character codes offset by 0x380 static const char el_vowels[] = {0x10,0x2c,0x2d,0x2e,0x2f,0x30,0x31,0x35,0x37,0x39,0x3f,0x45,0x49,0x4a,0x4b,0x4c,0x4d,0x4e,0x4f,0}; static const char el_fvowels[] = {0x2d,0x2e,0x2f,0x35,0x37,0x39,0x45,0x4d,0}; // ε η ι Ï… έ ή ί Ï static const char el_voiceless[]= {0x38,0x3a,0x3e,0x40,0x42,0x43,0x44,0x46,0x47,0}; // θ κ ξ Ï€ Ï‚ σ Ï„ φ χ static const char el_consonants[]={0x32,0x33,0x34,0x36,0x38,0x3a,0x3b,0x3c,0x3d,0x3e,0x40,0x41,0x42,0x43,0x44,0x46,0x47,0x48,0}; static const wchar_t el_char_apostrophe[] = {0x3c3,0}; // σ SetupTranslator(tr,stress_lengths_el,stress_amps_el); tr->charset_a0 = charsets[7]; // ISO-8859-7 tr->char_plus_apostrophe = el_char_apostrophe; tr->letter_bits_offset = OFFSET_GREEK; memset(tr->letter_bits,0,sizeof(tr->letter_bits)); SetLetterBits(tr,LETTERGP_A,el_vowels); SetLetterBits(tr,LETTERGP_VOWEL2,el_vowels); SetLetterBits(tr,LETTERGP_B,el_voiceless); SetLetterBits(tr,LETTERGP_C,el_consonants); SetLetterBits(tr,LETTERGP_Y,el_fvowels); // front vowels: ε η ι Ï… tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x6; // mark unstressed final syllables as diminished tr->langopts.unstressed_wd1 = 0; tr->langopts.unstressed_wd2 = 2; tr->langopts.param[LOPT_SONORANT_MIN] = 130; // limit the shortening of sonorants before short vowels tr->langopts.numbers = NUM_SINGLE_STRESS | NUM_DECIMAL_COMMA; tr->langopts.numbers2 = 0x2 | NUM2_MULTIPLE_ORDINAL; // variant form of numbers before thousands if(name2 == L_grc) { // ancient greek tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; } } break; case L('e','o'): { static const short stress_lengths_eo[8] = {150, 150, 230, 180, 0, 0, 300, 320}; static const unsigned char stress_amps_eo[] = {16,14, 20,20, 20,22, 22,21 }; static const wchar_t eo_char_apostrophe[2] = {'l',0}; SetupTranslator(tr,stress_lengths_eo,stress_amps_eo); tr->charset_a0 = charsets[3]; // ISO-8859-3 tr->char_plus_apostrophe = eo_char_apostrophe; // tr->langopts.word_gap = 1; tr->langopts.vowel_pause = 2; tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x6 | 0x10; // tr->langopts.unstressed_wd1 = 3; tr->langopts.unstressed_wd2 = 2; tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_OMIT_1_HUNDRED | NUM_ALLOW_SPACE | NUM_ROMAN; } break; case L('e','s'): // Spanish case L('c','a'): // Catalan case L_pap: // Papiamento { static const short stress_lengths_es[8] = {180, 190, 230, 180, 0, 0, 240, 270}; static const unsigned char stress_amps_es[8] = {16,12, 18,18, 20,20, 20,20 }; // 'diminished' is used to mark a quieter, final unstressed syllable static const wchar_t ca_punct_within_word[] = {'\'',0xb7,0}; // ca: allow middle-dot within word SetupTranslator(tr,stress_lengths_es,stress_amps_es); tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = STRESSPOSN_2R; // stress last syllable if it doesn't end in vowel or "s" or "n" // 'diminished' is an unstressed final syllable tr->langopts.stress_flags = 0x200 | 0x6 | 0x10; tr->langopts.unstressed_wd1 = 0; tr->langopts.unstressed_wd2 = 2; tr->langopts.param[LOPT_SONORANT_MIN] = 120; // limit the shortening of sonorants before short vowels tr->langopts.numbers = NUM_SINGLE_STRESS | NUM_DECIMAL_COMMA | NUM_AND_UNITS | NUM_OMIT_1_HUNDRED | NUM_OMIT_1_THOUSAND | NUM_ROMAN | NUM_ROMAN_AFTER; tr->langopts.numbers2 = NUM2_MULTIPLE_ORDINAL; if(name2 == L('c','a')) { tr->punct_within_word = ca_punct_within_word; tr->langopts.stress_flags = 0x200 | 0x6 | 0x30; // stress last syllable unless word ends with a vowel } else if(name2 == L_pap) { tr->langopts.stress_flags = 0x100 | 0x6 | 0x30; // stress last syllable unless word ends with a vowel } else { tr->langopts.param[LOPT_UNPRONOUNCABLE] = 2; // use es_rules for unpronouncable rules } } break; case L('e','u'): // basque { static const short stress_lengths_eu[8] = {200, 200, 200, 200, 0, 0, 210, 230}; // very weak stress static const unsigned char stress_amps_eu[8] = {16,16, 18,18, 18,18, 18,18 }; SetupTranslator(tr,stress_lengths_eu,stress_amps_eu); tr->langopts.stress_rule = STRESSPOSN_2L; // ?? second syllable ?? tr->langopts.numbers = NUM_SINGLE_STRESS | NUM_DECIMAL_COMMA | NUM_AND_UNITS | NUM_HUNDRED_AND | NUM_OMIT_1_HUNDRED | NUM_VIGESIMAL; } break; case L('f','a'): // Farsi { tr->letter_bits_offset = OFFSET_ARABIC; tr->langopts.numbers = NUM_AND_UNITS | NUM_HUNDRED_AND; tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words } break; case L('e','t'): // Estonian tr->charset_a0 = charsets[4]; // ISO-8859-4 // drop through to Finnish case L('f','i'): // Finnish { static const unsigned char stress_amps_fi[8] = {18,16, 22,22, 20,22, 22,22 }; static const short stress_lengths_fi[8] = {150,180, 200,200, 0,0, 210,250}; SetupTranslator(tr,stress_lengths_fi,stress_amps_fi); tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x56; // move secondary stress from light to a following heavy syllable tr->langopts.param[LOPT_IT_DOUBLING] = 1; tr->langopts.long_stop = 130; tr->langopts.numbers = NUM_DECIMAL_COMMA + NUM_ALLOW_SPACE; SetLetterVowel(tr,'y'); // tr->langopts.max_initial_consonants = 2; // BUT foreign words may have 3 tr->langopts.spelling_stress = 1; tr->langopts.intonation_group = 3; // less intonation, don't raise pitch at comma } break; case L('f','r'): // french { SetupTranslator(tr,stress_lengths_fr,stress_amps_fr); tr->langopts.stress_rule = STRESSPOSN_1R; // stress on final syllable tr->langopts.stress_flags = 0x0024; // don't use secondary stress tr->langopts.param[LOPT_IT_LENGTHEN] = 1; // remove lengthen indicator from unstressed syllables tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.accents = 2; // Say "Capital" after the letter. tr->langopts.numbers = NUM_SINGLE_STRESS | NUM_DECIMAL_COMMA | NUM_ALLOW_SPACE | NUM_OMIT_1_HUNDRED | NUM_NOPAUSE | NUM_ROMAN | NUM_ROMAN_CAPITALS | NUM_ROMAN_AFTER | NUM_VIGESIMAL | NUM_DFRACTION_4; SetLetterVowel(tr,'y'); } break; case L('h','i'): // Hindi case L('n','e'): // Nepali case L('p','a'): // Punjabi { static const short stress_lengths_hi[8] = {190, 190, 210, 210, 0, 0, 230, 250}; static const unsigned char stress_amps_hi[8] = {17,14, 20,19, 20,22, 22,21 }; SetupTranslator(tr,stress_lengths_hi,stress_amps_hi); tr->charset_a0 = charsets[19]; // ISCII tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = 6; // stress on last heaviest syllable, excluding final syllable tr->langopts.stress_flags = 0x10004; // use 'diminished' for unstressed final syllable tr->langopts.numbers = NUM_SWAP_TENS; tr->langopts.break_numbers = 0x14aa8; // for languages which have numbers for 100,000 and 100,00,000, eg Hindi tr->letter_bits_offset = OFFSET_DEVANAGARI; if(name2 == L('p','a')) { tr->letter_bits_offset = OFFSET_GURMUKHI; } SetIndicLetters(tr); } break; case L('h','r'): // Croatian case L('b','s'): // Bosnian case L('s','r'): // Serbian { static const unsigned char stress_amps_hr[8] = {17,17, 20,20, 20,22, 22,21 }; static const short stress_lengths_hr[8] = {180,160, 200,200, 0,0, 220,230}; static const short stress_lengths_sr[8] = {160,150, 200,200, 0,0, 250,260}; if(name2 == L('s','r')) SetupTranslator(tr,stress_lengths_sr,stress_amps_hr); else SetupTranslator(tr,stress_lengths_hr,stress_amps_hr); tr->charset_a0 = charsets[2]; // ISO-8859-2 tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x10; tr->langopts.param[LOPT_REGRESSIVE_VOICING] = 0x3; tr->langopts.max_initial_consonants = 5; tr->langopts.spelling_stress = 1; tr->langopts.accents = 1; tr->langopts.numbers = NUM_SINGLE_STRESS | NUM_HUNDRED_AND | NUM_OMIT_1_HUNDRED | NUM_DECIMAL_COMMA | NUM_THOUS_SPACE | NUM_DFRACTION_2 | NUM_ROMAN_CAPITALS; tr->langopts.numbers2 = 0x4a; // variant numbers before thousands,milliards tr->langopts.replace_chars = replace_cyrillic_latin; SetLetterVowel(tr,'y'); SetLetterVowel(tr,'r'); } break; case L('h','t'): // Haitian Creole // memcpy(tr->stress_lengths,stress_lengths_fr,sizeof(tr->stress_lengths)); tr->langopts.stress_rule = STRESSPOSN_1R; // stress on final syllable tr->langopts.stress_flags = 0x0024; // don't use secondary stress tr->langopts.numbers = NUM_SINGLE_STRESS | NUM_OMIT_1_HUNDRED | NUM_NOPAUSE | NUM_ROMAN | NUM_VIGESIMAL | NUM_DFRACTION_4; break; case L('h','u'): // Hungarian { static const unsigned char stress_amps_hu[8] = {17,17, 19,19, 20,22, 22,21 }; static const short stress_lengths_hu[8] = {185,195, 195,190, 0,0, 210,220}; SetupTranslator(tr,stress_lengths_hu,stress_amps_hu); tr->charset_a0 = charsets[2]; // ISO-8859-2 tr->langopts.vowel_pause = 0x20; tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x8036 | S_HYPEN_UNSTRESS; tr->langopts.unstressed_wd1 = 2; tr->langopts.param[LOPT_IT_DOUBLING] = 1; tr->langopts.param[LOPT_ANNOUNCE_PUNCT] = 2; // don't break clause before announcing . ? ! tr->langopts.numbers = NUM_DFRACTION_5 | NUM_ALLOW_SPACE | NUM_ROMAN | NUM_ROMAN_ORDINAL | NUM_ROMAN_CAPITALS | NUM_ORDINAL_DOT | NUM_OMIT_1_HUNDRED | NUM_OMIT_1_THOUSAND; tr->langopts.thousands_sep = ' '; // don't allow dot as thousands separator tr->langopts.decimal_sep = ','; tr->langopts.max_roman = 899; tr->langopts.min_roman = 1; SetLetterVowel(tr,'y'); tr->langopts.spelling_stress = 1; SetLengthMods(tr,3); // all equal } break; case L('h','y'): // Armenian { static const short stress_lengths_hy[8] = {250, 200, 250, 250, 0, 0, 250, 250}; static const char hy_vowels[] = {0x31, 0x35, 0x37, 0x38, 0x3b, 0x48, 0x55, 0}; static const char hy_consonants[] = {0x32,0x33,0x34,0x36,0x39,0x3a,0x3c,0x3d,0x3e,0x3f, 0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47,0x49,0x4a,0x4b,0x4c,0x4d,0x4e,0x4f,0x50,0x51,0x52,0x53,0x54,0x56,0}; SetupTranslator(tr,stress_lengths_hy,NULL); tr->langopts.stress_rule = STRESSPOSN_1R; // default stress on final syllable tr->letter_bits_offset = OFFSET_ARMENIAN; memset(tr->letter_bits,0,sizeof(tr->letter_bits)); SetLetterBits(tr,LETTERGP_A,hy_vowels); SetLetterBits(tr,LETTERGP_VOWEL2,hy_vowels); SetLetterBits(tr,LETTERGP_C,hy_consonants); tr->langopts.max_initial_consonants = 6; tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_OMIT_1_HUNDRED; // tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words } break; case L('i','d'): // Indonesian { static const short stress_lengths_id[8] = {160, 200, 180, 180, 0, 0, 220, 240}; static const unsigned char stress_amps_id[8] = {16,18, 18,18, 20,22, 22,21 }; SetupTranslator(tr,stress_lengths_id,stress_amps_id); tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_ALLOW_SPACE | NUM_ROMAN; tr->langopts.stress_flags = 0x6 | 0x10; tr->langopts.accents = 2; // "capital" after letter name } break; case L('i','s'): // Icelandic { static const short stress_lengths_is[8] = {180,160, 200,200, 0,0, 240,250}; static const wchar_t is_lettergroup_B[] = {'c','f','h','k','p','t','x',0xfe,0}; // voiceless conants, including 'þ' ?? 's' SetupTranslator(tr,stress_lengths_is,NULL); tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x10; tr->langopts.param[LOPT_IT_LENGTHEN] = 0x11; // remove lengthen indicator from unstressed vowels tr->langopts.param[LOPT_REDUCE] = 2; ResetLetterBits(tr,0x18); SetLetterBits(tr,4,"kpst"); // Letter group F SetLetterBits(tr,3,"jvr"); // Letter group H tr->letter_groups[1] = is_lettergroup_B; SetLetterVowel(tr,'y'); tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_SINGLE_AND | NUM_HUNDRED_AND | NUM_AND_UNITS | NUM_1900; tr->langopts.numbers2 = 0x2; } break; case L('i','t'): // Italian { static const short stress_lengths_it[8] = {150, 140, 170, 170, 0, 0, 300, 330}; static const unsigned char stress_amps_it[8] = {15,14, 19,19, 20,22, 22,20 }; SetupTranslator(tr,stress_lengths_it,stress_amps_it); tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x10 | 0x20000; tr->langopts.vowel_pause = 1; tr->langopts.unstressed_wd1 = 2; tr->langopts.unstressed_wd2 = 2; tr->langopts.param[LOPT_IT_LENGTHEN] = 2; // remove lengthen indicator from unstressed or non-penultimate syllables tr->langopts.param[LOPT_IT_DOUBLING] = 2; // double the first consonant if the previous word ends in a stressed vowel tr->langopts.param[LOPT_SONORANT_MIN] = 130; // limit the shortening of sonorants before short vowels tr->langopts.param[LOPT_REDUCE] = 1; // reduce vowels even if phonemes are specified in it_list tr->langopts.param[LOPT_ALT] = 2; // call ApplySpecialAttributes2() if a word has $alt or $alt2 tr->langopts.numbers = NUM_SINGLE_VOWEL | NUM_OMIT_1_HUNDRED |NUM_DECIMAL_COMMA | NUM_ROMAN | NUM_DFRACTION_1; tr->langopts.accents = 2; // Say "Capital" after the letter. SetLetterVowel(tr,'y'); } break; case L_jbo: // Lojban { static const short stress_lengths_jbo[8] = {145,145, 170,160, 0,0, 330,350}; static const wchar_t jbo_punct_within_word[] = {'.',',','\'',0x2c8,0}; // allow period and comma within a word, also stress marker (from LOPT_CAPS_IN_WORD) SetupTranslator(tr,stress_lengths_jbo,NULL); tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.vowel_pause = 0x20c; // pause before a word which starts with a vowel, or after a word which ends in a consonant // tr->langopts.word_gap = 1; tr->punct_within_word = jbo_punct_within_word; tr->langopts.param[LOPT_CAPS_IN_WORD] = 2; // capitals indicate stressed syllables SetLetterVowel(tr,'y'); tr->langopts.max_lengthmod = 368; } break; case L('k','a'): // Georgian { // character codes offset by 0x1080 static const char ka_vowels[] = {0x50,0x54,0x58,0x5d,0x63,0x75,0x77,0}; static const char ka_consonants[] = {0x51,0x52,0x53,0x55,0x56,0x57,0x59,0x5a,0x5b,0x5c,0x5e,0x5f,0x60,0x61,0x62,0x64,0x65,0x66,0x67,0x68,0x69,0x6a,0x6b,0x6c,0x6d,0x6e,0x6f,0x70,0x71,0x72,0x73,0x74,0x76,0}; SetupTranslator(tr,stress_lengths_ta,stress_amps_ta); memset(tr->letter_bits,0,sizeof(tr->letter_bits)); SetLetterBits(tr,LETTERGP_A,ka_vowels); SetLetterBits(tr,LETTERGP_C,ka_consonants); SetLetterBits(tr,LETTERGP_VOWEL2,ka_vowels); tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = S_FINAL_NO_2; tr->letter_bits_offset = OFFSET_GEORGIAN; // tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words tr->langopts.max_initial_consonants = 7; tr->langopts.numbers = NUM_VIGESIMAL | NUM_AND_UNITS | NUM_OMIT_1_HUNDRED |NUM_OMIT_1_THOUSAND | NUM_DFRACTION_5; } break; case L('k','k'): // Kazakh { static const unsigned char stress_amps_tr[8] = {18,16, 20,21, 20,21, 21,20 }; static const short stress_lengths_tr[8] = {190,180, 230,230, 0,0, 250,250}; tr->letter_bits_offset = OFFSET_CYRILLIC; memset(tr->letter_bits,0,sizeof(tr->letter_bits)); SetLetterBits(tr,LETTERGP_A,(char *)ru_vowels); SetLetterBits(tr,LETTERGP_C,(char *)ru_consonants); SetLetterBits(tr,LETTERGP_VOWEL2,(char *)ru_vowels); SetupTranslator(tr,stress_lengths_tr,stress_amps_tr); tr->langopts.stress_rule = 7; // stress on the last syllable, before any explicitly unstressed syllable tr->langopts.stress_flags = S_NO_AUTO_2 + S_NO_EOC_LENGTHEN; //no automatic secondary stress, don't lengthen at end-of-clause tr->langopts.lengthen_tonic = 0; tr->langopts.param[LOPT_SUFFIX] = 1; tr->langopts.numbers = NUM_OMIT_1_HUNDRED | NUM_DFRACTION_6 ; tr->langopts.max_initial_consonants = 2; SetLengthMods(tr,3); // all equal } break; case L('k','o'): // Korean, TEST { static const char ko_ivowels[] = {0x63,0x64,0x67,0x68,0x6d,0x72,0x74,0x75,0}; // y and i vowels static const unsigned char ko_voiced[] = {0x02,0x05,0x06,0xab,0xaf,0xb7,0xbc,0}; // voiced consonants, l,m,n,N tr->letter_bits_offset = OFFSET_KOREAN; memset(tr->letter_bits,0,sizeof(tr->letter_bits)); SetLetterBitsRange(tr,LETTERGP_A,0x61,0x75); SetLetterBits(tr,LETTERGP_Y,ko_ivowels); SetLetterBits(tr,LETTERGP_G,(const char *)ko_voiced); tr->langopts.stress_rule = 8; // ?? 1st syllable if it is heavy, else 2nd syllable tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words tr->langopts.numbers = NUM_OMIT_1_HUNDRED; } break; case L('k','u'): // Kurdish { static const unsigned char stress_amps_ku[8] = {18,18, 20,20, 20,22, 22,21 }; static const short stress_lengths_ku[8] = {180,180, 190,180, 0,0, 230,240}; SetupTranslator(tr,stress_lengths_ku,stress_amps_ku); tr->charset_a0 = charsets[9]; // ISO-8859-9 - Latin5 tr->langopts.stress_rule = 7; // stress on the last syllable, before any explicitly unstressed syllable tr->langopts.numbers = NUM_HUNDRED_AND | NUM_AND_UNITS | NUM_OMIT_1_HUNDRED | NUM_AND_HUNDRED; tr->langopts.max_initial_consonants = 2; } break; case L('l','a'): //Latin { tr->charset_a0 = charsets[4]; // ISO-8859-4, includes a,e,i,o,u-macron tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x20; tr->langopts.unstressed_wd1 = 0; tr->langopts.unstressed_wd2 = 2; tr->langopts.param[LOPT_DIERESES] = 1; tr->langopts.numbers = NUM_ROMAN; tr->langopts.max_roman = 5000; } break; case L('l','v'): // latvian { static const unsigned char stress_amps_lv[8] = {17,13, 20,20, 20,22, 22,21 }; static const short stress_lengths_lv[8] = {180,130, 210,210, 0,0, 210,210}; SetupTranslator(tr,stress_lengths_lv,stress_amps_lv); tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.spelling_stress = 1; tr->charset_a0 = charsets[4]; // ISO-8859-4 tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_OMIT_1_HUNDRED | NUM_DFRACTION_4 | NUM_ORDINAL_DOT; tr->langopts.stress_flags = 0x16 + 0x40000; } break; case L('m','k'): // Macedonian { static wchar_t vowels_cyrillic[] = {0x440, // also include 'Ñ€' [R] 0x430,0x435,0x438,0x439,0x43e,0x443,0x44b,0x44d,0x44e,0x44f,0x450,0x451,0x456,0x457,0x45d,0x45e,0}; static const unsigned char stress_amps_mk[8] = {17,17, 20,20, 20,22, 22,21 }; static const short stress_lengths_mk[8] = {180,160, 200,200, 0,0, 220,230}; SetupTranslator(tr,stress_lengths_mk,stress_amps_mk); tr->charset_a0 = charsets[5]; // ISO-8859-5 tr->letter_groups[0] = tr->letter_groups[7] = vowels_cyrillic; tr->langopts.stress_rule = STRESSPOSN_3R; // antipenultimate tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_AND_UNITS | NUM_OMIT_1_HUNDRED | NUM_OMIT_1_THOUSAND | NUM_DFRACTION_2; tr->langopts.numbers2 = 0x8a; // variant numbers before thousands,milliards } break; case L('m','t'): // Maltese { tr->charset_a0 = charsets[3]; // ISO-8859-3 tr->langopts.param[LOPT_REGRESSIVE_VOICING] = 0x100; // devoice at end of word tr->langopts.stress_rule = STRESSPOSN_2R; // penultimate tr->langopts.numbers = 1; } break; case L('n','l'): // Dutch { static const short stress_lengths_nl[8] = {160,135, 210,210, 0, 0, 260,280}; tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.vowel_pause = 0x30; // ?? tr->langopts.param[LOPT_DIERESES] = 1; tr->langopts.param[LOPT_PREFIXES] = 1; tr->langopts.param[LOPT_REGRESSIVE_VOICING] = 0x100; // devoice at end of word SetLetterVowel(tr,'y'); tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_SWAP_TENS | NUM_OMIT_1_HUNDRED | NUM_OMIT_1_THOUSAND | NUM_ALLOW_SPACE | NUM_1900 | NUM_ORDINAL_DOT; tr->langopts.ordinal_indicator = "e"; tr->langopts.stress_flags = S_FIRST_PRIMARY; memcpy(tr->stress_lengths,stress_lengths_nl,sizeof(tr->stress_lengths)); } break; case L('n','o'): // Norwegian { static const short stress_lengths_no[8] = {160,140, 200,200, 0,0, 220,230}; SetupTranslator(tr,stress_lengths_no,NULL); tr->langopts.stress_rule = STRESSPOSN_1L; SetLetterVowel(tr,'y'); tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_HUNDRED_AND | NUM_ALLOW_SPACE | NUM_1900 | NUM_ORDINAL_DOT; } break; case L('o','m'): { static const unsigned char stress_amps_om[] = {18,15, 20,20, 20,22, 22,22 }; static const short stress_lengths_om[8] = {200,200, 200,200, 0,0, 200,200}; SetupTranslator(tr,stress_lengths_om,stress_amps_om); tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x16 + 0x80000; } break; case L('p','l'): // Polish { static const short stress_lengths_pl[8] = {160, 190, 175, 175, 0, 0, 200, 210}; static const unsigned char stress_amps_pl[8] = {17,13, 19,19, 20,22, 22,21 }; // 'diminished' is used to mark a quieter, final unstressed syllable SetupTranslator(tr,stress_lengths_pl,stress_amps_pl); tr->charset_a0 = charsets[2]; // ISO-8859-2 tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x6; // mark unstressed final syllables as diminished tr->langopts.param[LOPT_REGRESSIVE_VOICING] = 0x9; tr->langopts.max_initial_consonants = 7; // for example: wchrzczony :) tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_ALLOW_SPACE | NUM_DFRACTION_2; tr->langopts.numbers2 = 0x40; tr->langopts.param[LOPT_COMBINE_WORDS] = 4 + 0x100; // combine 'nie' (marked with $alt2) with some 1-syllable (and 2-syllable) words (marked with $alt) SetLetterVowel(tr,'y'); } break; case L('p','t'): // Portuguese { static const short stress_lengths_pt[8] = {170, 115, 210, 240, 0, 0, 260, 280}; static const unsigned char stress_amps_pt[8] = {16,11, 19,21, 20,22, 22,21 }; // 'diminished' is used to mark a quieter, final unstressed syllable SetupTranslator(tr,stress_lengths_pt,stress_amps_pt); tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = STRESSPOSN_1R; // stress on final syllable tr->langopts.stress_flags = 0x6 | 0x10 | 0x2000 | 0x20000; tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_DFRACTION_2 | NUM_HUNDRED_AND | NUM_AND_UNITS | NUM_ROMAN; SetLetterVowel(tr,'y'); ResetLetterBits(tr,0x2); SetLetterBits(tr,1,"bcdfgjkmnpqstvxz"); // B hard consonants, excluding h,l,r,w,y tr->langopts.param[LOPT_ALT] = 2; // call ApplySpecialAttributes2() if a word has $alt or $alt2 } break; case L('r','o'): // Romanian { static const short stress_lengths_ro[8] = {170, 170, 180, 180, 0, 0, 240, 260}; static const unsigned char stress_amps_ro[8] = {15,13, 18,18, 20,22, 22,21 }; SetupTranslator(tr,stress_lengths_ro,stress_amps_ro); tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x100 + 0x6; tr->charset_a0 = charsets[2]; // ISO-8859-2 tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_ALLOW_SPACE | NUM_DFRACTION_3 | NUM_AND_UNITS | NUM_ROMAN; tr->langopts.numbers2 = 0x1e; // variant numbers before all thousandplex } break; case L('r','u'): // Russian Translator_Russian(tr); break; case L('r','w'): // Kiryarwanda { tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x16; tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.numbers = NUM_HUNDRED_AND | NUM_AND_UNITS | NUM_DFRACTION_2 | NUM_AND_HUNDRED; tr->langopts.numbers2 = 0x200; // say "thousands" before its number } break; case L('s','k'): // Slovak case L('c','s'): // Czech { static const char *sk_voiced = "bdgjlmnrvwzaeiouy"; SetupTranslator(tr,stress_lengths_sk,stress_amps_sk); tr->charset_a0 = charsets[2]; // ISO-8859-2 tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x16; tr->langopts.param[LOPT_REGRESSIVE_VOICING] = 0x3; tr->langopts.max_initial_consonants = 5; tr->langopts.spelling_stress = 1; tr->langopts.param[LOPT_COMBINE_WORDS] = 4; // combine some prepositions with the following word tr->langopts.numbers = NUM_OMIT_1_HUNDRED | NUM_DFRACTION_2 | NUM_ROMAN; tr->langopts.numbers2 = 0x100; tr->langopts.thousands_sep = STRESSPOSN_1L; //no thousands separator tr->langopts.decimal_sep = ','; if(name2 == L('c','s')) { tr->langopts.numbers2 = 0x108; // variant numbers before milliards } SetLetterVowel(tr,'y'); SetLetterVowel(tr,'r'); ResetLetterBits(tr,0x20); SetLetterBits(tr,5,sk_voiced); } break; case L('s','i'): // Sinhala { SetupTranslator(tr,stress_lengths_ta,stress_amps_ta); tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = S_FINAL_DIM | S_NO_AUTO_DIM | S_FINAL_NO_2; tr->langopts.spelling_stress = 1; tr->letter_bits_offset = OFFSET_SINHALA; memset(tr->letter_bits,0,sizeof(tr->letter_bits)); SetLetterBitsRange(tr,LETTERGP_A,0x05,0x16); // vowel letters SetLetterBitsRange(tr,LETTERGP_A,0x4a,0x73); // + vowel signs, and virama SetLetterBitsRange(tr,LETTERGP_B,0x4a,0x73); // vowel signs, and virama SetLetterBitsRange(tr,LETTERGP_C,0x1a,0x46); // the main consonant range tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words tr->langopts.suffix_add_e = tr->letter_bits_offset + 0x4a; //virama tr->langopts.numbers = NUM_OMIT_1_THOUSAND ; } break; case L('s','l'): // Slovenian tr->charset_a0 = charsets[2]; // ISO-8859-2 tr->langopts.stress_rule = STRESSPOSN_2R; // Temporary tr->langopts.stress_flags = 0x20; tr->langopts.param[LOPT_REGRESSIVE_VOICING] = 0x103; tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_ALLOW_SPACE | NUM_SWAP_TENS | NUM_OMIT_1_HUNDRED | NUM_DFRACTION_2 | NUM_ORDINAL_DOT | NUM_ROMAN; tr->langopts.numbers2 = 0x100; // plural forms of millions etc tr->langopts.thousands_sep = ' '; // don't allow dot as thousands separator SetLetterVowel(tr,'r'); break; case L('s','q'): // Albanian { static const short stress_lengths_sq[8] = {150, 150, 180, 180, 0, 0, 300, 300}; static const unsigned char stress_amps_sq[8] = {16,12, 16,16, 20,20, 21,19 }; SetupTranslator(tr,stress_lengths_sq,stress_amps_sq); tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x16 + 0x100; SetLetterVowel(tr,'y'); tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_HUNDRED_AND | NUM_AND_UNITS | NUM_DFRACTION_4; tr->langopts.accents = 2; // "capital" after letter name } break; case L('s','v'): // Swedish { static const unsigned char stress_amps_sv[] = {16,16, 20,20, 20,22, 22,21 }; static const short stress_lengths_sv[8] = {160,135, 220,220, 0,0, 250,280}; SetupTranslator(tr,stress_lengths_sv,stress_amps_sv); tr->langopts.stress_rule = STRESSPOSN_1L; SetLetterVowel(tr,'y'); tr->langopts.numbers = NUM_SINGLE_STRESS | NUM_DECIMAL_COMMA | NUM_ALLOW_SPACE | NUM_1900; tr->langopts.accents = 1; } break; case L('s','w'): // Swahili case L('t','n'): // Setswana { static const short stress_lengths_sw[8] = {160, 170, 200, 200, 0, 0, 320, 340}; static const unsigned char stress_amps_sw[] = {16,12, 19,19, 20,22, 22,21 }; SetupTranslator(tr,stress_lengths_sw,stress_amps_sw); tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.vowel_pause = 1; tr->langopts.stress_rule = STRESSPOSN_2R; tr->langopts.stress_flags = 0x6 | 0x10; tr->langopts.numbers = NUM_AND_UNITS | NUM_HUNDRED_AND | NUM_SINGLE_AND | NUM_OMIT_1_HUNDRED; tr->langopts.break_numbers = 0x49249268; // for languages which have numbers for 100,000 and 1,000,000 } break; case L('t','a'): // Tamil case L('m','l'): // Malayalam case L('k','n'): // Kannada case L('m','r'): // Marathi case L('t','e'): // Telugu { SetupTranslator(tr,stress_lengths_ta,stress_amps_ta); tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.stress_flags = 0x10004; // use 'diminished' for unstressed final syllable tr->langopts.spelling_stress = 1; tr->langopts.break_numbers = 0x14a8; // 1000, 100,000 10,000,000 if(name2 == L('t','a')) { tr->letter_bits_offset = OFFSET_TAMIL; tr->langopts.numbers = NUM_OMIT_1_THOUSAND ; } if(name2 == L('m','r')) { tr->letter_bits_offset = OFFSET_DEVANAGARI; } else if(name2 == L('m','l')) { tr->letter_bits_offset = OFFSET_MALAYALAM; tr->langopts.numbers = NUM_OMIT_1_THOUSAND; } else if(name2 == L('k','n')) { tr->letter_bits_offset = OFFSET_KANNADA; tr->langopts.numbers = 0x1; } else if(name2 == L('t','e')) { tr->letter_bits_offset = OFFSET_TELUGU; tr->langopts.numbers = 0x1; } tr->langopts.param[LOPT_WORD_MERGE] = 1; // don't break vowels betwen words SetIndicLetters(tr); // call this after setting OFFSET_ SetLetterBitsRange(tr,LETTERGP_B,0x4e,0x4e); // chillu-virama (unofficial) } break; #ifdef deleted case L('t','h'): // Thai { static const short stress_lengths_th[8] = {230,150, 230,230, 230,0, 230,250}; static const unsigned char stress_amps_th[] = {22,16, 22,22, 22,22, 22,22 }; SetupTranslator(tr,stress_lengths_th,stress_amps_th); tr->langopts.stress_rule = 0; // stress on final syllable of a "word" tr->langopts.stress_flags = 2; // don't automatically set diminished stress (may be set in the intonation module) tr->langopts.tone_language = 1; // Tone language, use CalcPitches_Tone() rather than CalcPitches() tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable // tr->langopts.tone_numbers = 1; // a number after letters indicates a tone number (eg. pinyin or jyutping) tr->langopts.word_gap = 0x21; // length of a final vowel is less dependent on the next consonant, don't merge consonant with next word } break; #endif case L('t','r'): // Turkish case L('a','z'): // Azerbaijan { static const unsigned char stress_amps_tr[8] = {18,16, 20,21, 20,21, 21,20 }; static const short stress_lengths_tr[8] = {190,180, 200,230, 0,0, 240,250}; SetupTranslator(tr,stress_lengths_tr,stress_amps_tr); tr->charset_a0 = charsets[9]; // ISO-8859-9 - Latin5 tr->langopts.stress_rule = 7; // stress on the last syllable, before any explicitly unstressed syllable tr->langopts.stress_flags = 0x20; //no automatic secondary stress tr->langopts.param[LOPT_SUFFIX] = 1; if(name2 == L('a','z')) { tr->langopts.numbers = NUM_SINGLE_STRESS | NUM_DECIMAL_COMMA | NUM_ALLOW_SPACE | NUM_OMIT_1_HUNDRED | NUM_OMIT_1_THOUSAND | NUM_DFRACTION_2; } else { tr->langopts.numbers = NUM_SINGLE_STRESS | NUM_DECIMAL_COMMA | NUM_OMIT_1_HUNDRED | NUM_OMIT_1_THOUSAND | NUM_DFRACTION_2; } tr->langopts.max_initial_consonants = 2; } break; case L('u','k'): // Ukrainian { SetCyrillicLetters(tr); tr->langopts.param[LOPT_UNPRONOUNCABLE] = 0x432; // [v] don't count this character at start of word } break; case L('u','r'): // Urdu tr->letter_bits_offset = OFFSET_ARABIC; tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words tr->langopts.numbers = NUM_SWAP_TENS; tr->langopts.break_numbers = 0x52a8; // for languages which have numbers for 100,000 and 100,00,000, eg Hindi break; case L('v','i'): // Vietnamese { static const short stress_lengths_vi[8] = {150, 150, 180, 180, 210, 230, 230, 240}; static const unsigned char stress_amps_vi[] = {16,16, 16,16, 22,22, 22,22 }; static wchar_t vowels_vi[] = { 0x61, 0xe0, 0xe1, 0x1ea3, 0xe3, 0x1ea1, // a 0x103, 0x1eb1, 0x1eaf, 0x1eb3, 0x1eb5, 0x1eb7, // ă 0xe2, 0x1ea7, 0x1ea5, 0x1ea9, 0x1eab, 0x1ead, // â 0x65, 0xe8, 0xe9, 0x1ebb, 0x1ebd, 0x1eb9, // e 0xea, 0x1ec1, 0x1ebf, 0x1ec3, 0x1ec5, 0x1ec7, // i 0x69, 0xec, 0xed, 0x1ec9, 0x129, 0x1ecb, // i 0x6f, 0xf2, 0xf3, 0x1ecf, 0xf5, 0x1ecd, // o 0xf4, 0x1ed3, 0x1ed1, 0x1ed5, 0x1ed7, 0x1ed9, // ô 0x1a1, 0x1edd, 0x1edb, 0x1edf, 0x1ee1, 0x1ee3, // Æ¡ 0x75, 0xf9, 0xfa, 0x1ee7, 0x169, 0x1ee5, // u 0x1b0, 0x1eeb, 0x1ee9, 0x1eed, 0x1eef, 0x1ef1, // ư 0x79, 0x1ef3, 0xfd, 0x1ef7, 0x1ef9, 0x1e, 0 }; // y SetupTranslator(tr,stress_lengths_vi,stress_amps_vi); tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.word_gap = 0x21; // length of a final vowel is less dependent on the next consonant, don't merge consonant with next word // tr->langopts.vowel_pause = 4; tr->letter_groups[0] = tr->letter_groups[7] = vowels_vi; tr->langopts.tone_language = 1; // Tone language, use CalcPitches_Tone() rather than CalcPitches() tr->langopts.unstressed_wd1 = 2; tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_HUNDRED_AND_DIGIT | NUM_DFRACTION_4 | NUM_ZERO_HUNDRED; } break; case L('w','o'): tr->langopts.stress_rule = STRESSPOSN_1L; tr->langopts.numbers = NUM_AND_UNITS | NUM_HUNDRED_AND | NUM_OMIT_1_HUNDRED | NUM_OMIT_1_THOUSAND | NUM_SINGLE_STRESS; break; case L('z','h'): case L_zhy: { static const short stress_lengths_zh[8] = {230,150, 230,230, 230,0, 240,250}; // 1=tone5. end-of-sentence, 6=tone 1&4, 7=tone 2&3 static const unsigned char stress_amps_zh[] = {22,16, 22,22, 22,22, 22,22 }; SetupTranslator(tr,stress_lengths_zh,stress_amps_zh); tr->langopts.stress_rule = STRESSPOSN_1R; // stress on final syllable of a "word" tr->langopts.stress_flags = 2; // don't automatically set diminished stress (may be set in the intonation module) tr->langopts.vowel_pause = 0; tr->langopts.tone_language = 1; // Tone language, use CalcPitches_Tone() rather than CalcPitches() tr->langopts.length_mods0 = tr->langopts.length_mods; // don't lengthen vowels in the last syllable tr->langopts.tone_numbers = 1; // a number after letters indicates a tone number (eg. pinyin or jyutping) tr->langopts.ideographs = 1; tr->langopts.word_gap = 0x21; // length of a final vowel is less dependent on the next consonant, don't merge consonant with next word if(name2 == L('z','h')) { tr->langopts.textmode = 1; tr->langopts.listx = 1; // compile zh_listx after zh_list } } break; default: tr->langopts.param[LOPT_UNPRONOUNCABLE] = 1; // disable check for unpronouncable words break; } tr->translator_name = name2; if(tr->langopts.numbers & NUM_DECIMAL_COMMA) { // use . and ; for thousands and decimal separators tr->langopts.thousands_sep = '.'; tr->langopts.decimal_sep = ','; } if(tr->langopts.numbers & NUM_THOUS_SPACE) { tr->langopts.thousands_sep = 0; // don't allow thousands separator, except space } return(tr); } // end of SelectTranslator //********************************************************************************************************** static void Translator_Russian(Translator *tr) {//=========================================== static const unsigned char stress_amps_ru[] = {16,16, 18,18, 20,24, 24,22 }; static const short stress_lengths_ru[8] = {150,140, 220,220, 0,0, 260,280}; static const char ru_ivowels2[] = {0x2c,0x15,0x18,0x2e,0x2f,0}; // add more vowels to letter group Y (iotated vowels & soft-sign) SetupTranslator(tr,stress_lengths_ru,stress_amps_ru); SetCyrillicLetters(tr); SetLetterBits(tr,6,ru_ivowels2); tr->langopts.param[LOPT_UNPRONOUNCABLE] = 0x432; // [v] don't count this character at start of word tr->langopts.param[LOPT_REGRESSIVE_VOICING] = 1; tr->langopts.param[LOPT_REDUCE] = 2; tr->langopts.stress_rule = 5; tr->langopts.stress_flags = 0x0020; // waas 0x1010 tr->langopts.numbers = NUM_DECIMAL_COMMA | NUM_OMIT_1_HUNDRED; tr->langopts.numbers2 = 0xc2; // variant numbers before thousands tr->langopts.phoneme_change = 1; tr->langopts.testing = 2; } // end of Translator_Russian /* typedef struct { int flags; unsigned char stress; // stress level of this vowel unsigned char stress_highest; // the highest stress level of a vowel in this word unsigned char n_vowels; // number of vowels in the word unsigned char vowel_this; // syllable number of this vowel (counting from 1) unsigned char vowel_stressed; // syllable number of the highest stressed vowel } CHANGEPH; */ #ifdef RUSSIAN2 // This is now done in the phoneme data, ph_russian int ChangePhonemes_ru(Translator *tr, PHONEME_LIST2 *phlist, int n_ph, int index, PHONEME_TAB *ph, CHANGEPH *ch) {//============================================================================================================= // Called for each phoneme in the phoneme list, to allow a language to make changes // ph The current phoneme int variant; int vowelix; PHONEME_TAB *prev, *next; if(ch->flags & 8) return(0); // full phoneme translation has already been given // Russian vowel softening and reduction rules if(ph->type == phVOWEL) { int prestressed = ch->vowel_stressed==ch->vowel_this+1; // the next vowel after this has the main stress #define N_VOWELS_RU 11 static unsigned int vowels_ru[N_VOWELS_RU] = {'a','V','O','I',PH('I','#'),PH('E','#'),PH('E','2'), PH('V','#'),PH('I','3'),PH('I','2'),PH('E','3')}; static unsigned int vowel_replace[N_VOWELS_RU][6] = { // stressed, soft, soft-stressed, j+stressed, j+soft, j+soft-stressed /*0*/ {'A', 'I', PH('j','a'), 'a', 'a', 'a'}, // a Uses 3,4,5 columns. /*1*/ {'A', 'V', PH('j','a'), 'a', 'V', 'a'}, // V Uses 3,4,5 columns. /*2*/ {'o', '8', '8', 'o', '8', '8'}, // O /*3*/ {'i', 'I', 'i', 'a', 'I', 'a'}, // I Uses 3,4,5 columns. /*4*/ {'i', PH('I','#'), 'i', 'i', PH('I','#'), 'i'}, // I# /*5*/ {'E', PH('E','#'), 'E', 'e', PH('E','#'), 'e'}, // E# /*6*/ {'E', PH('E','2'), 'E', 'e', PH('E','2'), 'e'}, // E2 Uses 3,4,5 columns. /*7*/ {PH('j','a'), 'V', PH('j','a'), 'A', 'V', 'A'}, // V# /*8*/ {PH('j','a'), 'I', PH('j','a'), 'e', 'I', 'e'}, // I3 Uses 3,4,5 columns. /*9*/ {'e', 'I', 'e', 'e', 'I', 'e'}, // I2 /*10*/ {'e', PH('E', '2'), 'e', 'e', PH('E','2'), 'e'} // E3 }; prev = phoneme_tab[phlist[index-1].phcode]; next = phoneme_tab[phlist[index+1].phcode]; // lookup the vowel name to get an index into the vowel_replace[] table for(vowelix=0; vowelixmnemonic) break; } if(vowelix == N_VOWELS_RU) return(0); if(prestressed) { if((vowelix==6)&&(prev->mnemonic=='j')) vowelix=8; if(vowelix==1) vowelix=0; if(vowelix==4) vowelix=3; if(vowelix==6) vowelix=5; if(vowelix==7) vowelix=8; if(vowelix==10) vowelix=9; } // do we need a variant of this vowel, depending on the stress and adjacent phonemes ? variant = -1; int stressed = ch->flags & 2; int soft=prev->phflags & phPALATAL; if (soft && stressed) variant = 2; else if (stressed) variant = 0; else if (soft) variant = 1; if(variant >= 0) { if(prev->mnemonic == 'j') variant += 3; phlist[index].phcode = PhonemeCode(vowel_replace[vowelix][variant]); } else { phlist[index].phcode = PhonemeCode(vowels_ru[vowelix]); } } return(0); } #endif sources_5316/external/espeak/sonic.cpp0000775000176700017670000006544011723710247016656 0ustar paulpaul/* Sonic library Copyright 2010 Bill Cox This file is part of the Sonic Library. The Sonic Library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. The GNU C Library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with the GNU C Library; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. */ #include "StdAfx.h" #include #include #include #include #include "sonic.h" struct sonicStreamStruct { short *inputBuffer; short *outputBuffer; short *pitchBuffer; short *downSampleBuffer; float speed; float volume; float pitch; int numChannels; int inputBufferSize; int pitchBufferSize; int outputBufferSize; int numInputSamples; int numOutputSamples; int numPitchSamples; int minPeriod; int maxPeriod; int maxRequired; int remainingInputToCopy; int sampleRate; int prevPeriod; int prevMaxDiff; int prevMinDiff; }; /* Just used for debugging */ void sonicMSG(char *format, ...) { char buffer[4096]; va_list ap; FILE *file; va_start(ap, format); vsprintf((char *)buffer, (char *)format, ap); va_end(ap); file=fopen("/tmp/sonic.log", "a"); fprintf(file, "%s", buffer); fclose(file); } /* Scale the samples by the factor. */ static void scaleSamples( short *samples, int numSamples, float volume) { int fixedPointVolume = volume*4096.0f; int value; while(numSamples--) { value = (*samples*fixedPointVolume) >> 12; if(value > 32767) { value = 32767; } else if(value < -32767) { value = -32767; } *samples++ = value; } } /* Get the speed of the stream. */ float sonicGetSpeed( sonicStream stream) { return stream->speed; } /* Set the speed of the stream. */ void sonicSetSpeed( sonicStream stream, float speed) { stream->speed = speed; } /* Get the pitch of the stream. */ float sonicGetPitch( sonicStream stream) { return stream->pitch; } /* Set the pitch of the stream. */ void sonicSetPitch( sonicStream stream, float pitch) { stream->pitch = pitch; } /* Get the scaling factor of the stream. */ float sonicGetVolume( sonicStream stream) { return stream->volume; } /* Set the scaling factor of the stream. */ void sonicSetVolume( sonicStream stream, float volume) { stream->volume = volume; } /* Get the sample rate of the stream. */ int sonicGetSampleRate( sonicStream stream) { return stream->sampleRate; } /* Get the number of channels. */ int sonicGetNumChannels( sonicStream stream) { return stream->numChannels; } /* Destroy the sonic stream. */ void sonicDestroyStream( sonicStream stream) { if(stream->inputBuffer != NULL) { free(stream->inputBuffer); } if(stream->outputBuffer != NULL) { free(stream->outputBuffer); } if(stream->pitchBuffer != NULL) { free(stream->pitchBuffer); } if(stream->downSampleBuffer != NULL) { free(stream->downSampleBuffer); } free(stream); } /* Create a sonic stream. Return NULL only if we are out of memory and cannot allocate the stream. */ sonicStream sonicCreateStream( int sampleRate, int numChannels) { sonicStream stream = (sonicStream)calloc(1, sizeof(struct sonicStreamStruct)); int minPeriod = sampleRate/SONIC_MAX_PITCH; int maxPeriod = sampleRate/SONIC_MIN_PITCH; int maxRequired = 2*maxPeriod; if(stream == NULL) { return NULL; } stream->inputBufferSize = maxRequired; stream->inputBuffer = (short *)calloc(maxRequired, sizeof(short)*numChannels); if(stream->inputBuffer == NULL) { sonicDestroyStream(stream); return NULL; } stream->outputBufferSize = maxRequired; stream->outputBuffer = (short *)calloc(maxRequired, sizeof(short)*numChannels); if(stream->outputBuffer == NULL) { sonicDestroyStream(stream); return NULL; } stream->pitchBufferSize = maxRequired; stream->pitchBuffer = (short *)calloc(maxRequired, sizeof(short)*numChannels); if(stream->pitchBuffer == NULL) { sonicDestroyStream(stream); return NULL; } stream->downSampleBuffer = (short *)calloc(maxRequired, sizeof(short)); stream->speed = 1.0f; stream->pitch = 1.0f; stream->volume = 1.0f; stream->sampleRate = sampleRate; stream->numChannels = numChannels; stream->minPeriod = minPeriod; stream->maxPeriod = maxPeriod; stream->maxRequired = maxRequired; return stream; } /* Enlarge the output buffer if needed. */ static int enlargeOutputBufferIfNeeded( sonicStream stream, int numSamples) { if(stream->numOutputSamples + numSamples > stream->outputBufferSize) { stream->outputBufferSize += (stream->outputBufferSize >> 1) + numSamples; stream->outputBuffer = (short *)realloc(stream->outputBuffer, stream->outputBufferSize*sizeof(short)*stream->numChannels); if(stream->outputBuffer == NULL) { return 0; } } return 1; } /* Enlarge the input buffer if needed. */ static int enlargeInputBufferIfNeeded( sonicStream stream, int numSamples) { if(stream->numInputSamples + numSamples > stream->inputBufferSize) { stream->inputBufferSize += (stream->inputBufferSize >> 1) + numSamples; stream->inputBuffer = (short *)realloc(stream->inputBuffer, stream->inputBufferSize*sizeof(short)*stream->numChannels); if(stream->inputBuffer == NULL) { return 0; } } return 1; } /* Add the input samples to the input buffer. */ static int addFloatSamplesToInputBuffer( sonicStream stream, float *samples, int numSamples) { short *buffer; int count = numSamples*stream->numChannels; if(numSamples == 0) { return 1; } if(!enlargeInputBufferIfNeeded(stream, numSamples)) { return 0; } buffer = stream->inputBuffer + stream->numInputSamples*stream->numChannels; while(count--) { *buffer++ = (*samples++)*32767.0f; } stream->numInputSamples += numSamples; return 1; } /* Add the input samples to the input buffer. */ static int addShortSamplesToInputBuffer( sonicStream stream, short *samples, int numSamples) { if(numSamples == 0) { return 1; } if(!enlargeInputBufferIfNeeded(stream, numSamples)) { return 0; } memcpy(stream->inputBuffer + stream->numInputSamples*stream->numChannels, samples, numSamples*sizeof(short)*stream->numChannels); stream->numInputSamples += numSamples; return 1; } /* Add the input samples to the input buffer. */ static int addUnsignedCharSamplesToInputBuffer( sonicStream stream, unsigned char *samples, int numSamples) { short *buffer; int count = numSamples*stream->numChannels; if(numSamples == 0) { return 1; } if(!enlargeInputBufferIfNeeded(stream, numSamples)) { return 0; } buffer = stream->inputBuffer + stream->numInputSamples*stream->numChannels; while(count--) { *buffer++ = (*samples++ - 128) << 8; } stream->numInputSamples += numSamples; return 1; } /* Remove input samples that we have already processed. */ static void removeInputSamples( sonicStream stream, int position) { int remainingSamples = stream->numInputSamples - position; if(remainingSamples > 0) { memmove(stream->inputBuffer, stream->inputBuffer + position*stream->numChannels, remainingSamples*sizeof(short)*stream->numChannels); } stream->numInputSamples = remainingSamples; } /* Just copy from the array to the output buffer */ static int copyToOutput( sonicStream stream, short *samples, int numSamples) { if(!enlargeOutputBufferIfNeeded(stream, numSamples)) { return 0; } memcpy(stream->outputBuffer + stream->numOutputSamples*stream->numChannels, samples, numSamples*sizeof(short)*stream->numChannels); stream->numOutputSamples += numSamples; return numSamples; } /* Just copy from the input buffer to the output buffer. Return 0 if we fail to resize the output buffer. Otherwise, return numSamples */ static int copyInputToOutput( sonicStream stream, int position) { int numSamples = stream->remainingInputToCopy; if(numSamples > stream->maxRequired) { numSamples = stream->maxRequired; } if(!copyToOutput(stream, stream->inputBuffer + position*stream->numChannels, numSamples)) { return 0; } stream->remainingInputToCopy -= numSamples; return numSamples; } /* Read data out of the stream. Sometimes no data will be available, and zero is returned, which is not an error condition. */ int sonicReadFloatFromStream( sonicStream stream, float *samples, int maxSamples) { int numSamples = stream->numOutputSamples; int remainingSamples = 0; short *buffer; int count; if(numSamples == 0) { return 0; } if(numSamples > maxSamples) { remainingSamples = numSamples - maxSamples; numSamples = maxSamples; } buffer = stream->outputBuffer; count = numSamples*stream->numChannels; while(count--) { *samples++ = (*buffer++)/32767.0f; } if(remainingSamples > 0) { memmove(stream->outputBuffer, stream->outputBuffer + numSamples*stream->numChannels, remainingSamples*sizeof(short)*stream->numChannels); } stream->numOutputSamples = remainingSamples; return numSamples; } /* Read short data out of the stream. Sometimes no data will be available, and zero is returned, which is not an error condition. */ int sonicReadShortFromStream( sonicStream stream, short *samples, int maxSamples) { int numSamples = stream->numOutputSamples; int remainingSamples = 0; if(numSamples == 0) { return 0; } if(numSamples > maxSamples) { remainingSamples = numSamples - maxSamples; numSamples = maxSamples; } memcpy(samples, stream->outputBuffer, numSamples*sizeof(short)*stream->numChannels); if(remainingSamples > 0) { memmove(stream->outputBuffer, stream->outputBuffer + numSamples*stream->numChannels, remainingSamples*sizeof(short)*stream->numChannels); } stream->numOutputSamples = remainingSamples; return numSamples; } /* Read unsigned char data out of the stream. Sometimes no data will be available, and zero is returned, which is not an error condition. */ int sonicReadUnsignedCharFromStream( sonicStream stream, unsigned char *samples, int maxSamples) { int numSamples = stream->numOutputSamples; int remainingSamples = 0; short *buffer; int count; if(numSamples == 0) { return 0; } if(numSamples > maxSamples) { remainingSamples = numSamples - maxSamples; numSamples = maxSamples; } buffer = stream->outputBuffer; count = numSamples*stream->numChannels; while(count--) { *samples++ = (char)((*buffer++) >> 8) + 128; } if(remainingSamples > 0) { memmove(stream->outputBuffer, stream->outputBuffer + numSamples*stream->numChannels, remainingSamples*sizeof(short)*stream->numChannels); } stream->numOutputSamples = remainingSamples; return numSamples; } /* Force the sonic stream to generate output using whatever data it currently has. No extra delay will be added to the output, but flushing in the middle of words could introduce distortion. */ int sonicFlushStream( sonicStream stream) { int maxRequired = stream->maxRequired; int numSamples = stream->numInputSamples; int remainingSpace, numOutputSamples, expectedSamples; if(numSamples == 0) { return 1; } if(numSamples >= maxRequired && !sonicWriteShortToStream(stream, NULL, 0)) { return 0; } numSamples = stream->numInputSamples; /* Now numSamples < maxRequired */ if(numSamples == 0) { return 1; } remainingSpace = maxRequired - numSamples; memset(stream->inputBuffer + numSamples*stream->numChannels, 0, remainingSpace*sizeof(short)*stream->numChannels); stream->numInputSamples = maxRequired; numOutputSamples = stream->numOutputSamples; if(!sonicWriteShortToStream(stream, NULL, 0)) { return 0; } /* Throw away any extra samples we generated due to the silence we added */ expectedSamples = (int)(numSamples*stream->speed + 0.5); if(stream->numOutputSamples > numOutputSamples + expectedSamples) { stream->numOutputSamples = numOutputSamples + expectedSamples; } return 1; } /* Return the number of samples in the output buffer */ int sonicSamplesAvailable( sonicStream stream) { return stream->numOutputSamples; } /* If skip is greater than one, average skip samples togther and write them to the down-sample buffer. If numChannels is greater than one, mix the channels together as we down sample. */ static void downSampleInput( sonicStream stream, short *samples, int skip) { int numSamples = stream->maxRequired/skip; int samplesPerValue = stream->numChannels*skip; int i, j; int value; short *downSamples = stream->downSampleBuffer; for(i = 0; i < numSamples; i++) { value = 0; for(j = 0; j < samplesPerValue; j++) { value += *samples++; } value /= samplesPerValue; *downSamples++ = value; } } /* Find the best frequency match in the range, and given a sample skip multiple. For now, just find the pitch of the first channel. */ static int findPitchPeriodInRange( short *samples, int minPeriod, int maxPeriod, int *retMinDiff, int *retMaxDiff) { int period, bestPeriod = 0; short *s, *p, sVal, pVal; unsigned long diff, minDiff = 1, maxDiff = 0; int i; for(period = minPeriod; period <= maxPeriod; period++) { diff = 0; s = samples; p = samples + period; for(i = 0; i < period; i++) { sVal = *s++; pVal = *p++; diff += sVal >= pVal? (unsigned short)(sVal - pVal) : (unsigned short)(pVal - sVal); } /* Note that the highest number of samples we add into diff will be less than 256, since we skip samples. Thus, diff is a 24 bit number, and we can safely multiply by numSamples without overflow */ if(diff*bestPeriod < minDiff*period) { minDiff = diff; bestPeriod = period; } if(diff*bestPeriod > maxDiff*period) { maxDiff = diff; } } *retMinDiff = minDiff; *retMaxDiff = maxDiff; return bestPeriod; } /* At abrupt ends of voiced words, we can have pitch periods that are better aproximated by the previous pitch period estimate. Try to detect this case. */ static int prevPeriodBetter( sonicStream stream, int period, int minDiff, int maxDiff) { if(maxDiff*3/2 < stream->prevMaxDiff && (maxDiff*3.0f)*stream->prevMinDiff < (float)stream->prevMaxDiff*minDiff*2) { return 1; } return 0; } /* Find the pitch period. This is a critical step, and we may have to try multiple ways to get a good answer. This version uses AMDF. To improve speed, we down sample by an integer factor get in the 11KHz range, and then do it again with a narrower frequency range without down sampling */ static int findPitchPeriod( sonicStream stream, short *samples) { int minPeriod = stream->minPeriod; int maxPeriod = stream->maxPeriod; int sampleRate = stream->sampleRate; int minDiff, maxDiff, retPeriod; int skip = 1; int period; if(sampleRate > SONIC_AMDF_FREQ) { skip = sampleRate/SONIC_AMDF_FREQ; } if(stream->numChannels == 1 && skip == 1) { period = findPitchPeriodInRange(samples, minPeriod, maxPeriod, &minDiff, &maxDiff); } else { downSampleInput(stream, samples, skip); period = findPitchPeriodInRange(stream->downSampleBuffer, minPeriod/skip, maxPeriod/skip, &minDiff, &maxDiff); if(skip != 1) { period *= skip; minPeriod = period - (skip << 2); maxPeriod = period + (skip << 2); if(minPeriod < stream->minPeriod) { minPeriod = stream->minPeriod; } if(maxPeriod > stream->maxPeriod) { maxPeriod = stream->maxPeriod; } if(stream->numChannels == 1) { period = findPitchPeriodInRange(samples, minPeriod, maxPeriod, &minDiff, &maxDiff); } else { downSampleInput(stream, samples, 1); period = findPitchPeriodInRange(stream->downSampleBuffer, minPeriod, maxPeriod, &minDiff, &maxDiff); } } } if(prevPeriodBetter(stream, period, minDiff, maxDiff)) { retPeriod = stream->prevPeriod; } else { retPeriod = period; } stream->prevMinDiff = minDiff; stream->prevMaxDiff = maxDiff; stream->prevPeriod = period; return retPeriod; } /* Overlap two sound segments, ramp the volume of one down, while ramping the other one from zero up, and add them, storing the result at the output. */ static void overlapAdd( int numSamples, int numChannels, short *out, short *rampDown, short *rampUp) { short *o, *u, *d; int i, t; for(i = 0; i < numChannels; i++) { o = out + i; u = rampUp + i; d = rampDown + i; for(t = 0; t < numSamples; t++) { *o = (*d*(numSamples - t) + *u*t)/numSamples; o += numChannels; d += numChannels; u += numChannels; } } } /* Overlap two sound segments, ramp the volume of one down, while ramping the other one from zero up, and add them, storing the result at the output. */ static void overlapAddWithSeparation( int numSamples, int numChannels, int separation, short *out, short *rampDown, short *rampUp) { short *o, *u, *d; int i, t; for(i = 0; i < numChannels; i++) { o = out + i; u = rampUp + i; d = rampDown + i; for(t = 0; t < numSamples + separation; t++) { if(t < separation) { *o = *d*(numSamples - t)/numSamples; d += numChannels; } else if(t < numSamples) { *o = (*d*(numSamples - t) + *u*(t - separation))/numSamples; d += numChannels; u += numChannels; } else { *o = *u*(t - separation)/numSamples; u += numChannels; } o += numChannels; } } } /* Just move the new samples in the output buffer to the pitch bufer */ static int moveNewSamplesToPitchBuffer( sonicStream stream, int originalNumOutputSamples) { int numSamples = stream->numOutputSamples - originalNumOutputSamples; int numChannels = stream->numChannels; if(stream->numPitchSamples + numSamples > stream->pitchBufferSize) { stream->pitchBufferSize += (stream->pitchBufferSize >> 1) + numSamples; stream->pitchBuffer = (short *)realloc(stream->pitchBuffer, stream->pitchBufferSize*sizeof(short)*numChannels); if(stream->pitchBuffer == NULL) { return 0; } } memcpy(stream->pitchBuffer + stream->numPitchSamples*numChannels, stream->outputBuffer + originalNumOutputSamples*numChannels, numSamples*sizeof(short)*numChannels); stream->numOutputSamples = originalNumOutputSamples; stream->numPitchSamples += numSamples; return 1; } /* Remove processed samples from the pitch buffer. */ static void removePitchSamples( sonicStream stream, int numSamples) { int numChannels = stream->numChannels; short *source = stream->pitchBuffer + numSamples*numChannels; if(numSamples == 0) { return; } if(numSamples != stream->numPitchSamples) { memmove(stream->pitchBuffer, source, (stream->numPitchSamples - numSamples)*sizeof(short)*numChannels); } stream->numPitchSamples -= numSamples; } /* Change the pitch. The latency this introduces could be reduced by looking at past samples to determine pitch, rather than future. */ static int adjustPitch( sonicStream stream, int originalNumOutputSamples) { float pitch = stream->pitch; int numChannels = stream->numChannels; int period, newPeriod, separation; int position = 0; short *out, *rampDown, *rampUp; if(stream->numOutputSamples == originalNumOutputSamples) { return 1; } if(!moveNewSamplesToPitchBuffer(stream, originalNumOutputSamples)) { return 0; } while(stream->numPitchSamples - position >= stream->maxRequired) { period = findPitchPeriod(stream, stream->pitchBuffer + position*numChannels); newPeriod = period/pitch; if(!enlargeOutputBufferIfNeeded(stream, newPeriod)) { return 0; } out = stream->outputBuffer + stream->numOutputSamples*numChannels; if(pitch >= 1.0f) { rampDown = stream->pitchBuffer + position*numChannels; rampUp = stream->pitchBuffer + (position + period - newPeriod)*numChannels; overlapAdd(newPeriod, numChannels, out, rampDown, rampUp); } else { rampDown = stream->pitchBuffer + position*numChannels; rampUp = stream->pitchBuffer + position*numChannels; separation = newPeriod - period; overlapAddWithSeparation(period, numChannels, separation, out, rampDown, rampUp); } stream->numOutputSamples += newPeriod; position += period; } removePitchSamples(stream, position); return 1; } /* Skip over a pitch period, and copy period/speed samples to the output */ static int skipPitchPeriod( sonicStream stream, short *samples, float speed, int period) { long newSamples; int numChannels = stream->numChannels; if(speed >= 2.0f) { newSamples = period/(speed - 1.0f); } else if(speed > 1.0f) { newSamples = period; stream->remainingInputToCopy = period*(2.0f - speed)/(speed - 1.0f); } if(!enlargeOutputBufferIfNeeded(stream, newSamples)) { return 0; } overlapAdd(newSamples, numChannels, stream->outputBuffer + stream->numOutputSamples*numChannels, samples, samples + period*numChannels); stream->numOutputSamples += newSamples; return newSamples; } /* Insert a pitch period, and determine how much input to copy directly. */ static int insertPitchPeriod( sonicStream stream, short *samples, float speed, int period) { long newSamples; short *out; int numChannels = stream->numChannels; if(speed < 0.5f) { newSamples = period*speed/(1.0f - speed); } else { newSamples = period; stream->remainingInputToCopy = period*(2.0f*speed - 1.0f)/(1.0f - speed); } if(!enlargeOutputBufferIfNeeded(stream, period + newSamples)) { return 0; } out = stream->outputBuffer + stream->numOutputSamples*numChannels; memcpy(out, samples, period*sizeof(short)*numChannels); out = stream->outputBuffer + (stream->numOutputSamples + period)*numChannels; overlapAdd(newSamples, numChannels, out, samples + period*numChannels, samples); stream->numOutputSamples += period + newSamples; return newSamples; } /* Resample as many pitch periods as we have buffered on the input. Return 0 if we fail to resize an input or output buffer. Also scale the output by the volume. */ static int changeSpeed( sonicStream stream, float speed) { short *samples; int numSamples = stream->numInputSamples; int position = 0, period, newSamples; int maxRequired = stream->maxRequired; if(stream->numInputSamples < maxRequired) { return 1; } do { if(stream->remainingInputToCopy > 0) { newSamples = copyInputToOutput(stream, position); position += newSamples; } else { samples = stream->inputBuffer + position*stream->numChannels; period = findPitchPeriod(stream, samples); if(speed > 1.0) { newSamples = skipPitchPeriod(stream, samples, speed, period); position += period + newSamples; } else { newSamples = insertPitchPeriod(stream, samples, speed, period); position += newSamples; } } if(newSamples == 0) { return 0; /* Failed to resize output buffer */ } } while(position + maxRequired <= numSamples); removeInputSamples(stream, position); return 1; } /* Resample as many pitch periods as we have buffered on the input. Return 0 if we fail to resize an input or output buffer. Also scale the output by the volume. */ static int processStreamInput( sonicStream stream) { int originalNumOutputSamples = stream->numOutputSamples; float speed = stream->speed/stream->pitch; if(speed > 1.00001 || speed < 0.99999) { changeSpeed(stream, speed); } else { if(!copyToOutput(stream, stream->inputBuffer, stream->numInputSamples)) { return 0; } stream->numInputSamples = 0; } if(stream->pitch != 1.0f) { if(!adjustPitch(stream, originalNumOutputSamples)) { return 0; } } if(stream->volume != 1.0f) { /* Adjust output volume. */ scaleSamples(stream->outputBuffer + originalNumOutputSamples*stream->numChannels, (stream->numOutputSamples - originalNumOutputSamples)*stream->numChannels, stream->volume); } return 1; } /* Write floating point data to the input buffer and process it. */ int sonicWriteFloatToStream( sonicStream stream, float *samples, int numSamples) { if(!addFloatSamplesToInputBuffer(stream, samples, numSamples)) { return 0; } return processStreamInput(stream); } /* Simple wrapper around sonicWriteFloatToStream that does the short to float conversion for you. */ int sonicWriteShortToStream( sonicStream stream, short *samples, int numSamples) { if(!addShortSamplesToInputBuffer(stream, samples, numSamples)) { return 0; } return processStreamInput(stream); } /* Simple wrapper around sonicWriteFloatToStream that does the unsigned char to float conversion for you. */ int sonicWriteUnsignedCharToStream( sonicStream stream, unsigned char *samples, int numSamples) { if(!addUnsignedCharSamplesToInputBuffer(stream, samples, numSamples)) { return 0; } return processStreamInput(stream); } /* This is a non-stream oriented interface to just change the speed of a sound sample */ int sonicChangeFloatSpeed( float *samples, int numSamples, float speed, float pitch, float volume, int sampleRate, int numChannels) { sonicStream stream = sonicCreateStream(sampleRate, numChannels); sonicSetSpeed(stream, speed); sonicSetPitch(stream, pitch); sonicSetVolume(stream, volume); sonicWriteFloatToStream(stream, samples, numSamples); sonicFlushStream(stream); numSamples = sonicSamplesAvailable(stream); sonicReadFloatFromStream(stream, samples, numSamples); sonicDestroyStream(stream); return numSamples; } /* This is a non-stream oriented interface to just change the speed of a sound sample */ int sonicChangeShortSpeed( short *samples, int numSamples, float speed, float pitch, float volume, int sampleRate, int numChannels) { sonicStream stream = sonicCreateStream(sampleRate, numChannels); sonicSetSpeed(stream, speed); sonicSetPitch(stream, pitch); sonicSetVolume(stream, volume); sonicWriteShortToStream(stream, samples, numSamples); sonicFlushStream(stream); numSamples = sonicSamplesAvailable(stream); sonicReadShortFromStream(stream, samples, numSamples); sonicDestroyStream(stream); return numSamples; } sources_5316/external/espeak/speech.h0000664000176700017670000000632611725414672016457 0ustar paulpaul/*************************************************************************** * Copyright (C) 2005 to 2007 by Jonathan Duddington * * email: jonsd@users.sourceforge.net * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 3 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write see: * * . * ***************************************************************************/ #ifndef SPEECH_H #define SPEECH_H #include #include "espeakdata_FileInMemory.h" #define DATA_FROM_SOURCECODE_FILES // conditional compilation options #define INCLUDE_KLATT /* ppgb, 23 December 2011 */ #undef INCLUDE_MBROLA #if defined(BYTE_ORDER) && BYTE_ORDER == BIG_ENDIAN #define ARCH_BIG #endif #ifdef __QNX__ #define NEED_GETOPT #define NO_VARIADIC_MACROS #endif /* ppgb, 23 December 2011 */ #undef PLATFORM_POSIX #undef PLATFORM_WINDOWS #define PATHSEP '/' // USE_PORTAUDIO or USE_PULSEAUDIO are now defined in the makefile //#define USE_PORTAUDIO //#define USE_PULSEAUDIO /* ppgb, 23 December 2011 */ #undef USE_NANOSLEEP //#define ESPEAK_API extern "C" #ifdef LIBRARY #define USE_ASYNC #endif #ifdef _ESPEAKEDIT #define USE_PORTAUDIO #define USE_ASYNC #define LOG_FRAMES // write keyframe info to log-espeakedit #endif // will look for espeak_data directory here, and also in user's home directory #ifndef PATH_ESPEAK_DATA #define PATH_ESPEAK_DATA "/usr/share/espeak-data" #endif typedef unsigned short USHORT; typedef unsigned char UCHAR; typedef double DOUBLEX; typedef uint64_t long64; // use this for conversion between pointers and integers template T *align_address (T *p) { union { T* ptr; size_t integer; }; const size_t bit_mask = ~(_align_to - 1); ptr = p; Melder_assert (sizeof (size_t) == sizeof (void *)); integer &= bit_mask; return ptr; } typedef struct { const char *mnem; int value; } MNEM_TAB; int LookupMnem(MNEM_TAB *table, const char *string); #ifdef PLATFORM_WINDOWS #define N_PATH_HOME 220 #else #define N_PATH_HOME 150 #endif extern char path_home[N_PATH_HOME]; // this is the espeak-data directory extern void strncpy0(char *to,const char *from, int size); int GetFileLength(const char *filename); char *Alloc(int size); void Free(void *ptr); #endif // SPEECH_Hsources_5316/external/espeak/READ_ME.TXT0000664000176700017670000001423011723710247016520 0ustar paulpaulREAD_ME.TXT djmw 20120130 Espeak Version 1.46 The Espeak program and its library use the espeak-data directory as a supply for the data the synthesizer needs. The synthesizer needs the location of this directory to work correctly. The synthesizer's version and the espeak-data version have to match. This is not exceptable in Praat since we don't want these potential mismatches between the internal version of the synthesizer and the external espeak-data directory to occur at all. We have therefore "removed" espeak's dependency on the external espeak-data directory and we have moved all the data to memory. This means that some of the espeak code had to be modified a little bit to accomplish this. ***** Step 1: Use the (private) script "espeakdata_to_code.praat to 1. copy the necessary files from the current espeak distribution to the espeak-work/espeak directory 2. copy files espeakdata_FileInMemory.cpp, espeakdata_FileInMemory.h and Makefile from espeak-work to /espeak-work/espeak 3. Create the files - espeakdata_phons.cpp // phondata, phonindex, phontab, intonations - espeakdata_dicts.cpp // all **_dict files - espeakdata_voices.cpp // all voices in voices/ and subdirs except voices/mb and voices/!v - espeakdata_variants.cpp // all files in voices/!v ***** Step 2 Modify some espeak files >> Adapt speech.h ******* #include "espeakdata_FileInMemory.h" #undef INCLUDE_MBROLA #undef PLATFORM_POSIX #undef PLATFORM_WINDOWS #undef USE_NANOSLEEP #define DATA_FROM_SOURCECODE_FILES #ifdef _WIN32 wchar_t * Melder_peekUtf8ToWcs (const char *string); const uint16_t * Melder_peekWcsToUtf16 (const wchar_t *string); #endif >> voices.cpp : voice_t *LoadVoice(const char *vname, int control) #ifdef DATA_FROM_SOURCECODE_FILES long numberOfBytes; const char * data; if (tone_only) { data = espeakdata_get_voiceVariant (vname, &numberOfBytes); } else { language_type = "en"; data = espeakdata_get_voice (vname, &numberOfBytes); language_type = vname; } if (data == 0) { language_type = "en"; // default data = espeakdata_get_voice ("en/en", &numberOfBytes); } #else ... endif #ifdef DATA_FROM_SOURCECODE_FILES long index = 1; const char *start = data; while (start = espeakdata_get_voicedata (start, numberOfBytes, buf, sizeof(buf), &index)) { #else while((f_voice != NULL) && (fgets_strip(buf,sizeof(buf),f_voice) != NULL)) { #endif >> synthdata : int LoadPhData() #ifdef DATA_FROM_SOURCECODE_FILES long llength; phoneme_tab_data = (unsigned char *) FilesInMemory_getData (espeakdata_phons, L"phontab", &llength); phoneme_index = (USHORT *) FilesInMemory_getData (espeakdata_phons, L"phonindex", &llength); phondata_ptr = (char *) FilesInMemory_getData (espeakdata_phons, L"phondata", &llength); tunes = (TUNE *) FilesInMemory_getData (espeakdata_phons, L"intonations", &llength); length = llength; #else if((phoneme_tab_data = (unsigned char *)ReadPhFile((void *)(phoneme_tab_data),"phontab",NULL)) == NULL) return(-1); if((phoneme_index = (USHORT *)ReadPhFile((void *)(phoneme_index),"phonindex",NULL)) == NULL) return(-1); if((phondata_ptr = ReadPhFile((void *)(phondata_ptr),"phondata",NULL)) == NULL) return(-1); if((tunes = (TUNE *)ReadPhFile((void *)(tunes),"intonations",&length)) == NULL) return(-1); #endif void FreePhData(void) {//================== #ifndef DATA_FROM_SOURCECODE_FILES Free(phoneme_tab_data); Free(phoneme_index); Free(phondata_ptr); Free(tunes); #endif phoneme_tab_data=NULL; phoneme_index=NULL; phondata_ptr=NULL; tunes=NULL; } >> speak_lib.cpp #ifdef DATA_FROM_SOURCECODE_FILES static void init_path(const char *path) { (void) path; } #else static void init_path(const char *path) {//==================================== #ifdef PLATFORM_WINDOWS near line 464: sleep is not a WIN64 function, but luckily we don't need it. // sleep(1) >> dictionary.cpp #ifdef DATA_FROM_SOURCECODE_FILES int LoadDictionary(Translator *tr, const char *name, int no_error) { strcpy (dictionary_name, name); // currently loaded dictionary name strcpy (tr -> dictionary_name, name); // Load a pronunciation data file into memory // bytes 0-3: offset to rules data // bytes 4-7: number of hash table entries if(tr -> data_dictlist != NULL) { Free (tr -> data_dictlist); tr -> data_dictlist = NULL; } unsigned int size; tr -> data_dictlist = (char *) espeakdata_get_dict_data (name, &size); if (tr -> data_dictlist == 0) { return 1; } int *pw = reinterpret_cast (tr -> data_dictlist); int length = Reverse4Bytes (pw[1]); // was int really written with 4 bytes? if (size <= (N_HASH_DICT + sizeof(int)*2)) { Melder_error_ (L"Empty _dict: ", Melder_utf8ToWcs(name), L"_dict."); return(2); } if((Reverse4Bytes(pw[0]) != N_HASH_DICT) || (length <= 0) || (length > 0x8000000)) { Melder_error_ (L"Bad data in dict: ", Melder_utf8ToWcs(name), L" ", Melder_integer (Reverse4Bytes(pw[0])), L" ", Melder_integer (length)); return (2); } tr -> data_dictrules = &(tr->data_dictlist[length]); // set up indices into data_dictrules InitGroups(tr); if (tr -> groups1[0] == NULL) { Melder_error_ (L"Error in ", Melder_peekUtf8ToWcs (name), L"_rules, no default rule group."); } // set up hash table for data_dictlist char *p = &(tr -> data_dictlist[8]); for (int hash = 0; hash < N_HASH_DICT; hash++) { tr -> dict_hashtab[hash] = p; while ((length = *p) != 0) { p += length; } p++; // skip over the zero which terminates the list for this hash value } return (0); } // end of LoadDictionary #else int LoadDictionary_old(Translator *tr, const char *name, int no_error) ************ klatt.cpp *************** replace the gen_noise with the corrected version: static double gen_noise(double noisedummy) // repaired ppgb 20111223 { long temp; static double nlast = 0.0; temp = (long) getrandom (-8191, 8191); kt_globals.nrand = (long) temp; double noise = kt_globals.nrand + (0.75 * nlast); nlast = noise; return(noise); } ??? template T *align_address (T *p) { union { T* ptr; size_t integer; }; const size_t bit_mask = ~(_align_to - 1); ptr = p; Melder_assert (sizeof (size_t) == sizeof (void *)); integer &= bit_mask; return ptr; } sources_5316/external/espeak/fifo.h0000644000176700017670000000357211721443315016121 0ustar paulpaul#ifndef FIFO_H #define FIFO_H // Helps to add espeak commands in a first-in first-out queue // and run them asynchronously. #include "espeak_command.h" #include "speak_lib.h" // Initialize the fifo component. // First function to be called. void fifo_init(); // Add an espeak command. // // Note: this function fails if too many commands are already buffered. // In such a case, the calling function could wait and then add again its command. // // Return: EE_OK: operation achieved // EE_BUFFER_FULL: the command can not be buffered; // you may try after a while to call the function again. // EE_INTERNAL_ERROR. espeak_ERROR fifo_add_command (t_espeak_command* c); // Add two espeak commands in a single transaction. // // Note: this function fails if too many commands are already buffered. // In such a case, the calling function could wait and then add again these commands. // // Return: EE_OK: operation achieved // EE_BUFFER_FULL: at least one command can not be buffered; // you may try after a while to call the function again. // EE_INTERNAL_ERROR. espeak_ERROR fifo_add_commands (t_espeak_command* c1, t_espeak_command* c2); // The current running command must be stopped and the awaiting commands are cleared. // Return: EE_OK: operation achieved // EE_INTERNAL_ERROR. espeak_ERROR fifo_stop (); // Is there a running command? // Returns 1 if yes; 0 otherwise. int fifo_is_busy (); // Terminate the fifo component. // Last function to be called. void fifo_terminate(); // Indicates if the running command is still enabled. // // Note: this function is mainly called by the SynthCallback (speak_lib.cpp) // It indicates if the actual wave sample can still be played. It is helpful for // stopping speech as soon as a cancel command is applied. // // Returns 1 if yes, or 0 otherwise. int fifo_is_command_enabled(); #endif sources_5316/external/mp3/0000755000176700017670000000000011631437236014252 5ustar paulpaulsources_5316/external/mp3/mad_imdct_s.dat0000644000176700017670000000503710627342357017217 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: imdct_s.dat,v 1.8 2004/01/23 09:41:32 rob Exp $ */ /* 0 */ { MAD_F(0x09bd7ca0) /* 0.608761429 */, -MAD_F(0x0ec835e8) /* -0.923879533 */, -MAD_F(0x0216a2a2) /* -0.130526192 */, MAD_F(0x0fdcf549) /* 0.991444861 */, -MAD_F(0x061f78aa) /* -0.382683432 */, -MAD_F(0x0cb19346) /* -0.793353340 */ }, /* 6 */ { -MAD_F(0x0cb19346) /* -0.793353340 */, MAD_F(0x061f78aa) /* 0.382683432 */, MAD_F(0x0fdcf549) /* 0.991444861 */, MAD_F(0x0216a2a2) /* 0.130526192 */, -MAD_F(0x0ec835e8) /* -0.923879533 */, -MAD_F(0x09bd7ca0) /* -0.608761429 */ }, /* 1 */ { MAD_F(0x061f78aa) /* 0.382683432 */, -MAD_F(0x0ec835e8) /* -0.923879533 */, MAD_F(0x0ec835e8) /* 0.923879533 */, -MAD_F(0x061f78aa) /* -0.382683432 */, -MAD_F(0x061f78aa) /* -0.382683432 */, MAD_F(0x0ec835e8) /* 0.923879533 */ }, /* 7 */ { -MAD_F(0x0ec835e8) /* -0.923879533 */, -MAD_F(0x061f78aa) /* -0.382683432 */, MAD_F(0x061f78aa) /* 0.382683432 */, MAD_F(0x0ec835e8) /* 0.923879533 */, MAD_F(0x0ec835e8) /* 0.923879533 */, MAD_F(0x061f78aa) /* 0.382683432 */ }, /* 2 */ { MAD_F(0x0216a2a2) /* 0.130526192 */, -MAD_F(0x061f78aa) /* -0.382683432 */, MAD_F(0x09bd7ca0) /* 0.608761429 */, -MAD_F(0x0cb19346) /* -0.793353340 */, MAD_F(0x0ec835e8) /* 0.923879533 */, -MAD_F(0x0fdcf549) /* -0.991444861 */ }, /* 8 */ { -MAD_F(0x0fdcf549) /* -0.991444861 */, -MAD_F(0x0ec835e8) /* -0.923879533 */, -MAD_F(0x0cb19346) /* -0.793353340 */, -MAD_F(0x09bd7ca0) /* -0.608761429 */, -MAD_F(0x061f78aa) /* -0.382683432 */, -MAD_F(0x0216a2a2) /* -0.130526192 */ } sources_5316/external/mp3/mad_version.c0000644000176700017670000000411510627342357016730 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: version.c,v 1.15 2004/01/23 09:41:33 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # include "mad_version.h" char const mad_version[] = "MPEG Audio Decoder " MAD_VERSION; char const mad_copyright[] = "Copyright (C) " MAD_PUBLISHYEAR " " MAD_AUTHOR; char const mad_author[] = MAD_AUTHOR " <" MAD_EMAIL ">"; char const mad_build[] = "" # if defined(DEBUG) "DEBUG " # elif defined(NDEBUG) "NDEBUG " # endif # if defined(EXPERIMENTAL) "EXPERIMENTAL " # endif # if defined(FPM_64BIT) "FPM_64BIT " # elif defined(FPM_INTEL) "FPM_INTEL " # elif defined(FPM_ARM) "FPM_ARM " # elif defined(FPM_MIPS) "FPM_MIPS " # elif defined(FPM_SPARC) "FPM_SPARC " # elif defined(FPM_PPC) "FPM_PPC " # elif defined(FPM_DEFAULT) "FPM_DEFAULT " # endif # if defined(ASO_IMDCT) "ASO_IMDCT " # endif # if defined(ASO_INTERLEAVE1) "ASO_INTERLEAVE1 " # endif # if defined(ASO_INTERLEAVE2) "ASO_INTERLEAVE2 " # endif # if defined(ASO_ZEROCHECK) "ASO_ZEROCHECK " # endif # if defined(OPT_SPEED) "OPT_SPEED " # elif defined(OPT_ACCURACY) "OPT_ACCURACY " # endif # if defined(OPT_SSO) "OPT_SSO " # endif # if defined(OPT_DCTO) /* never defined here */ "OPT_DCTO " # endif # if defined(OPT_STRICT) "OPT_STRICT " # endif ; sources_5316/external/mp3/mp3.h0000644000176700017670000000372711614424562015132 0ustar paulpaul#ifndef __MP3_H #define __MP3_H /* * Praat wrappers for libMAD (MPEG Audio Decoder) * Copyright 2007 Erez Volk * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include /* The following function is used to identify MP3 files */ int mp3_recognize (int nread, const char *data); /* Actual decoding is done with an MP3_FILE object */ typedef struct _MP3_FILE *MP3_FILE; typedef int MP3F_SAMPLE; #if defined (_OFF_T) || defined (__off_t_defined) typedef off_t MP3F_OFFSET; #else typedef unsigned long MP3F_OFFSET; #endif #define MP3F_MAX_CHANNELS 2 #define MP3F_MAX_SAMPLES 1152 /* Per callback */ typedef void (*MP3F_CALLBACK) ( const MP3F_SAMPLE *channels[MP3F_MAX_CHANNELS], long num_samples, void *context); MP3_FILE mp3f_new (void); void mp3f_delete (MP3_FILE mp3f); void mp3f_set_file (MP3_FILE mp3f, FILE *f); int mp3f_analyze (MP3_FILE mp3f); unsigned mp3f_channels (MP3_FILE mp3f); unsigned mp3f_frequency (MP3_FILE mp3f); MP3F_OFFSET mp3f_samples (MP3_FILE mp3f); void mp3f_set_callback (MP3_FILE mp3f, MP3F_CALLBACK callback, void *context); int mp3f_seek (MP3_FILE mp3f, MP3F_OFFSET sample); int mp3f_read (MP3_FILE mp3f, MP3F_OFFSET num_samples); #define mp3f_sample_to_float(s) ((float)((s) / (float)(1L << 28))) short mp3f_sample_to_short (MP3F_SAMPLE sample); #endif /* __MP3_H */ sources_5316/external/mp3/mad_synth.h0000644000176700017670000000364610627342357016425 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: synth.h,v 1.15 2004/01/23 09:41:33 rob Exp $ */ # ifndef LIBMAD_SYNTH_H # define LIBMAD_SYNTH_H # include "mad_fixed.h" # include "mad_frame.h" struct mad_pcm { unsigned int samplerate; /* sampling frequency (Hz) */ unsigned short channels; /* number of channels */ unsigned short length; /* number of samples per channel */ mad_fixed_t samples[2][1152]; /* PCM output samples [ch][sample] */ }; struct mad_synth { mad_fixed_t filter[2][2][2][16][8]; /* polyphase filterbank outputs */ /* [ch][eo][peo][s][v] */ unsigned int phase; /* current processing phase */ struct mad_pcm pcm; /* PCM output */ }; /* single channel PCM selector */ enum { MAD_PCM_CHANNEL_SINGLE = 0 }; /* dual channel PCM selector */ enum { MAD_PCM_CHANNEL_DUAL_1 = 0, MAD_PCM_CHANNEL_DUAL_2 = 1 }; /* stereo PCM selector */ enum { MAD_PCM_CHANNEL_STEREO_LEFT = 0, MAD_PCM_CHANNEL_STEREO_RIGHT = 1 }; void mad_synth_init(struct mad_synth *); # define mad_synth_finish(synth) /* nothing */ void mad_synth_mute(struct mad_synth *); void mad_synth_frame(struct mad_synth *, struct mad_frame const *); # endif sources_5316/external/mp3/Makefile0000644000176700017670000000104111631437236015706 0ustar paulpaul# Makefile of the library "audio/mp3" # Erez Volk, 24 May 2007 # Paul Boersma, 6 September 2011 include ../../makefile.defs CPPFLAGS = -I ../../sys OBJECTS = mp3.o \ mad_bit.o \ mad_decoder.o \ mad_fixed.o \ mad_frame.o \ mad_huffman.o \ mad_layer12.o \ mad_layer3.o \ mad_stream.o \ mad_synth.o \ mad_timer.o \ mad_version.o .PHONY: all clean all: libmp3.a clean: $(RM) $(OBJECTS) $(RM) libmp3.a libmp3.a: $(OBJECTS) touch libmp3.a rm libmp3.a ar cq libmp3.a $(OBJECTS) $(RANLIB) libmp3.a $(OBJECTS): *.h ../../sys/*.h sources_5316/external/mp3/mad_qc_table.dat0000644000176700017670000000762310627342357017352 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: qc_table.dat,v 1.7 2004/01/23 09:41:32 rob Exp $ */ /* * These are the Layer II classes of quantization. * The table is derived from Table B.4 of ISO/IEC 11172-3. */ { 3, 2, 5, MAD_F(0x15555555) /* 1.33333333333 => 1.33333333209, e 0.00000000124 */, MAD_F(0x08000000) /* 0.50000000000 => 0.50000000000, e 0.00000000000 */ }, { 5, 3, 7, MAD_F(0x1999999a) /* 1.60000000000 => 1.60000000149, e -0.00000000149 */, MAD_F(0x08000000) /* 0.50000000000 => 0.50000000000, e 0.00000000000 */ }, { 7, 0, 3, MAD_F(0x12492492) /* 1.14285714286 => 1.14285714179, e 0.00000000107 */, MAD_F(0x04000000) /* 0.25000000000 => 0.25000000000, e 0.00000000000 */ }, { 9, 4, 10, MAD_F(0x1c71c71c) /* 1.77777777777 => 1.77777777612, e 0.00000000165 */, MAD_F(0x08000000) /* 0.50000000000 => 0.50000000000, e 0.00000000000 */ }, { 15, 0, 4, MAD_F(0x11111111) /* 1.06666666666 => 1.06666666642, e 0.00000000024 */, MAD_F(0x02000000) /* 0.12500000000 => 0.12500000000, e 0.00000000000 */ }, { 31, 0, 5, MAD_F(0x10842108) /* 1.03225806452 => 1.03225806355, e 0.00000000097 */, MAD_F(0x01000000) /* 0.06250000000 => 0.06250000000, e 0.00000000000 */ }, { 63, 0, 6, MAD_F(0x10410410) /* 1.01587301587 => 1.01587301493, e 0.00000000094 */, MAD_F(0x00800000) /* 0.03125000000 => 0.03125000000, e 0.00000000000 */ }, { 127, 0, 7, MAD_F(0x10204081) /* 1.00787401575 => 1.00787401572, e 0.00000000003 */, MAD_F(0x00400000) /* 0.01562500000 => 0.01562500000, e 0.00000000000 */ }, { 255, 0, 8, MAD_F(0x10101010) /* 1.00392156863 => 1.00392156839, e 0.00000000024 */, MAD_F(0x00200000) /* 0.00781250000 => 0.00781250000, e 0.00000000000 */ }, { 511, 0, 9, MAD_F(0x10080402) /* 1.00195694716 => 1.00195694715, e 0.00000000001 */, MAD_F(0x00100000) /* 0.00390625000 => 0.00390625000, e 0.00000000000 */ }, { 1023, 0, 10, MAD_F(0x10040100) /* 1.00097751711 => 1.00097751617, e 0.00000000094 */, MAD_F(0x00080000) /* 0.00195312500 => 0.00195312500, e 0.00000000000 */ }, { 2047, 0, 11, MAD_F(0x10020040) /* 1.00048851979 => 1.00048851967, e 0.00000000012 */, MAD_F(0x00040000) /* 0.00097656250 => 0.00097656250, e 0.00000000000 */ }, { 4095, 0, 12, MAD_F(0x10010010) /* 1.00024420024 => 1.00024420023, e 0.00000000001 */, MAD_F(0x00020000) /* 0.00048828125 => 0.00048828125, e 0.00000000000 */ }, { 8191, 0, 13, MAD_F(0x10008004) /* 1.00012208522 => 1.00012208521, e 0.00000000001 */, MAD_F(0x00010000) /* 0.00024414063 => 0.00024414062, e 0.00000000000 */ }, { 16383, 0, 14, MAD_F(0x10004001) /* 1.00006103888 => 1.00006103888, e -0.00000000000 */, MAD_F(0x00008000) /* 0.00012207031 => 0.00012207031, e -0.00000000000 */ }, { 32767, 0, 15, MAD_F(0x10002000) /* 1.00003051851 => 1.00003051758, e 0.00000000093 */, MAD_F(0x00004000) /* 0.00006103516 => 0.00006103516, e 0.00000000000 */ }, { 65535, 0, 16, MAD_F(0x10001000) /* 1.00001525902 => 1.00001525879, e 0.00000000023 */, MAD_F(0x00002000) /* 0.00003051758 => 0.00003051758, e 0.00000000000 */ } sources_5316/external/mp3/mp3.cpp0000644000176700017670000003745111606370702015463 0ustar paulpaul/* * Praat wrappers for libMAD (MPEG Audio Decoder) Copyright 2007 Erez Volk * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * * * * Exact seeking in an MP3 file turns out to be quite complex. * * For constant bit rate (CBR) files, frame size is fixed and we can calculate * in advance the location of every frame. * * For variable bit rate (VBR) files, no option gives us more than a rough * estimate of where every percent of the file is lcoated, with no way of * checking (after we make a seek) where we ended up. The only reliable way we * have, then, is to scan the entire file in advance and keep a table with the * offsets of all (or some) frames. In the worst case, we will have to scan * the file *twice*, since we can't know the exact number of frames. * * What's worse, there is no guaranteed standard way of checking whether an MP3 * file is CBR or VBR. We therefore use the following compromise, which is * guaranteed to work on all files: * * - If there is a Xing header, read it to get the number of frames. * - Otherwise *estimate* the number of frames. * - Keep a reasonably (?) sized table of "key" offsets. * - Scan all the headers and keep required offsets in the table. * - After the scan, we also know the precise number of frames and samples. * * TODO: Find exactly what the encoder delay is. * (see http://mp3decoders.mp3-tech.org/decoders_lame.html) * TODO: Compensate for end padding. * TODO: Better conversion to short. * */ /*#define MP3_DEBUG*/ #include #include "mp3.h" #include "melder.h" extern "C" { #include "mad_config.h" #include "mad_decoder.h" } #define MP3F_BUFFER_SIZE (8 * 1024) #define MP3F_MAX_LOCATIONS 1024 /* * MP3 encoders and decoders add a number of silent samples at the beginning. * I don't know of any reliable way to detect these delays in an MP3 file. * The numbers below are (hopefully reasonable) estimates based on LAME and * some testing; it is more important to preserve all the meaningful samples * than to eliminate all silent ones. */ #define MP3F_DECODER_DELAY 529 /*#define MP3F_ENCODER_DELAY 576*/ #define MP3F_ENCODER_DELAY 96 #ifdef MP3_DEBUG # define MP3_DPRINTF(x) printf x # define MP3_PERCENT(base, value) (((float)(value) - (float)(base)) * 100.0 / (float)(base)) #else /* !MP3_DEBUG */ # define MP3_DPRINTF(x) #endif /* MP3_DEBUG */ struct _MP3_FILE { struct mad_decoder decoder; FILE *f; unsigned char buffer [MP3F_BUFFER_SIZE]; int xing; unsigned channels; unsigned frequency; unsigned frames; unsigned samples_per_frame; MP3F_OFFSET samples; MP3F_OFFSET locations[MP3F_MAX_LOCATIONS]; unsigned num_locations; unsigned frames_per_location; unsigned delay; MP3F_CALLBACK callback; void *context; MP3F_OFFSET next_read_position; MP3F_OFFSET read_amount; MP3F_OFFSET first_offset; unsigned skip_amount; int need_seek; }; static enum mad_flow mp3f_mad_error (void *context, struct mad_stream *stream, struct mad_frame *frame); static enum mad_flow mp3f_mad_input (void *context, struct mad_stream *stream); static enum mad_flow mp3f_mad_first_header (void *context, struct mad_header const *header); static enum mad_flow mp3f_mad_first_filter (void *context, struct mad_stream const *stream, struct mad_frame *frame); static int mp3f_check_xing (MP3_FILE mp3f, struct mad_stream const *stream); static enum mad_flow mp3f_mad_scan_header (void *context, struct mad_header const *header); static enum mad_flow mp3f_mad_report_samples (void *context, struct mad_header const *header, struct mad_pcm *pcm); int mp3_recognize (int nread, const char *data) { const unsigned char *bytes = (const unsigned char *)data; if (nread < 3) return 0; /* MP3 files can start with an ID3 tag */ if (bytes [0] == 'I' && bytes [1] == 'D' && bytes [2] == '3') return 1; /* Otherwise the beginning of the file must be an MP3 frame */ if (bytes [0] != 0xFF) return 0; /* This is not a foolproof check, but it is similar to file(1) */ return ((bytes [1] & 0xFE) == 0xFA) || /* MPEG ADTS, layer III, v1 */ ((bytes [1] & 0xFE) == 0xFC) || /* MPEG ADTS, layer II, v1 */ ((bytes [1] & 0xFE) == 0xFE) || /* MPEG ADTS, layer I, v1 */ ((bytes [1] & 0xFE) == 0xF2) || /* MPEG ADTS, layer III, v2 */ ((bytes [1] & 0xFE) == 0xF4) || /* MPEG ADTS, layer II, v2 */ ((bytes [1] & 0xFE) == 0xF6) || /* MPEG ADTS, layer I, v2 */ ((bytes [1] & 0xFE) == 0xE2); /* MPEG ADTS, layer III, v2.5 */ } MP3_FILE mp3f_new (void) { try { return Melder_calloc (struct _MP3_FILE, 1); } catch (MelderError) { Melder_throw ("Cannot create MP3 file object."); } } void mp3f_delete (MP3_FILE mp3f) { Melder_free (mp3f); } void mp3f_set_file (MP3_FILE mp3f, FILE *f) { mp3f -> f = f; if (! f) return; fseek (f, 0, SEEK_SET); mp3f -> next_read_position = 0; mp3f -> need_seek = 0; mp3f -> delay = MP3F_DECODER_DELAY + MP3F_ENCODER_DELAY; mp3f -> skip_amount = mp3f -> delay; mp3f -> first_offset = 0; } int mp3f_analyze (MP3_FILE mp3f) { struct mad_decoder *decoder = & mp3f -> decoder; int status; #ifdef MP3_DEBUG unsigned estimate, last; #endif /* MP3_DEBUG */ if (! mp3f || ! mp3f -> f) return 0; fseek (mp3f -> f, 0, SEEK_SET); mp3f -> xing = 0; mp3f -> channels = 0; mp3f -> frequency = 0; mp3f -> frames = 0; mp3f -> samples = 0; mp3f -> samples_per_frame = 0; mp3f -> num_locations = 0; /* Read first frames to get basic parameters and hopefully Xing */ mad_decoder_init (decoder, mp3f, mp3f_mad_input, mp3f_mad_first_header, mp3f_mad_first_filter, NULL /* Output: Don't actually decode for now */, mp3f_mad_error, NULL /* Message */); status = mad_decoder_run (decoder, MAD_DECODER_MODE_SYNC); if (status != 0) goto end; /* * If we don't have a Xing header we need to estimate the frame count. * This doesn't have to be accurate since we're going to count them * later when we scan for header offsets. */ if (! mp3f -> xing) { MP3F_OFFSET file_size, frame_size; /* Take size of first frame */ frame_size = mp3f -> locations [1] - mp3f -> locations[0]; /* For file size, seek to end */ fseek (mp3f -> f, 0, SEEK_END); file_size = ftell (mp3f -> f); /* This estimate will be pretty accurate for CBR */ mp3f -> frames = file_size / frame_size; MP3_DPRINTF (("File size: %lu bytes\n", (unsigned long)file_size)); MP3_DPRINTF (("First frame size: %lu bytes\n", (unsigned long)frame_size)); MP3_DPRINTF (("Estimated frames: %lu\n", (unsigned long)mp3f -> frames)); } /* Calculate how many frames can fit in a "location" */ if (mp3f -> frames <= MP3F_MAX_LOCATIONS) mp3f -> frames_per_location = 1; else mp3f -> frames_per_location = (mp3f -> frames + MP3F_MAX_LOCATIONS - 1) / MP3F_MAX_LOCATIONS; MP3_DPRINTF (("MP3: Each location is %u frame(s) (%.3fs), each %u samples\n", mp3f -> frames_per_location, mp3f -> frames_per_location * mp3f -> samples_per_frame / (float)mp3f -> frequency, mp3f -> samples_per_frame)); /* Read all frames to get offsets*/ #ifdef MP3_DEBUG estimate = mp3f -> frames; #endif /* MP3_DEBUG */ mp3f -> num_locations = 0; mp3f -> frames = 0; mp3f -> samples = 0; fseek (mp3f -> f, 0, SEEK_SET); mad_decoder_init (decoder, mp3f, mp3f_mad_input, mp3f_mad_scan_header, NULL /* Filter */, NULL /* Output */, mp3f_mad_error, NULL /* Message */); status = mad_decoder_run (decoder, MAD_DECODER_MODE_SYNC); MP3_DPRINTF (("MP3 Frames: %u, estimated %u (%+.2f%%)\n", mp3f -> frames, estimate, MP3_PERCENT (mp3f -> frames, estimate))); #ifdef MP3_DEBUG last = mp3f -> frames - (mp3f -> frames_per_location * (mp3f -> num_locations - 1)); MP3_DPRINTF (("MP3F: Last location frames = %u (%+.2f%%) = %.3fs\n", last, MP3_PERCENT (mp3f -> frames_per_location, last), last * mp3f -> samples_per_frame / (float)mp3f -> frequency)); #endif /* MP3_DEBUG */ mp3f_seek (mp3f, 0); end: mad_decoder_finish (decoder); return (status == 0); } unsigned mp3f_channels (MP3_FILE mp3f) { return mp3f -> channels; } unsigned mp3f_frequency (MP3_FILE mp3f) { return mp3f -> frequency; } MP3F_OFFSET mp3f_samples (MP3_FILE mp3f) { return mp3f -> samples - mp3f -> delay; } void mp3f_set_callback (MP3_FILE mp3f, MP3F_CALLBACK callback, void *context) { mp3f -> callback = callback; mp3f -> context = context; } int mp3f_seek (MP3_FILE mp3f, MP3F_OFFSET sample) { MP3F_OFFSET frame, location, base, offset; if (! mp3f || ! mp3f -> f) return 0; if (! mp3f -> frames_per_location) if (! mp3f_analyze (mp3f)) return 0; /* Compensate for initial empty frames */ sample += mp3f -> delay; /* Calculate where we need to seek */ frame = sample / mp3f -> samples_per_frame; if ( frame ) /* libMAD can skip the first frame... */ -- frame; if ( frame ) /* ...and the first frame it decodes is useless */ -- frame; location = frame / mp3f -> frames_per_location; if (location >= mp3f -> num_locations) location = mp3f -> num_locations - 1; frame = location * mp3f -> frames_per_location; base = frame * mp3f -> samples_per_frame; offset = mp3f -> locations [location]; if (fseek (mp3f -> f, offset, SEEK_SET) < 0) return 0; mp3f -> first_offset = offset; mp3f -> skip_amount = sample - base; mp3f -> need_seek = 0; MP3_DPRINTF (("SEEK to %lu (%lu + %u): Frame %lu, location %lu, offset %lu, base %lu, skip %u\n", (unsigned long)sample, (unsigned long)sample - mp3f -> delay, mp3f -> delay, (unsigned long)frame, (unsigned long)location, (unsigned long)offset, (unsigned long)base, mp3f -> skip_amount)); return 1; } int mp3f_read (MP3_FILE mp3f, MP3F_OFFSET num_samples) { int status; struct mad_decoder *decoder = &(mp3f -> decoder); if (! mp3f || ! mp3f -> f || ! mp3f -> callback) return 0; /* Seek if the last read left us in mid-frame */ if (mp3f -> need_seek) if (! mp3f_seek (mp3f, mp3f -> next_read_position)) return 0; mad_decoder_init (decoder, mp3f, mp3f_mad_input, NULL /* Header */, NULL /* Filter */, mp3f_mad_report_samples, mp3f_mad_error, NULL /* Message */); mp3f -> read_amount = num_samples; status = mad_decoder_run (decoder, MAD_DECODER_MODE_SYNC); mad_decoder_finish (decoder); mp3f -> next_read_position += num_samples; return (status == 0); } static enum mad_flow mp3f_mad_report_samples (void *context, struct mad_header const *header, struct mad_pcm *pcm) { MP3_FILE mp3f = (MP3_FILE) context; const int *channels [] = { pcm -> samples [0], pcm -> samples [1] }; unsigned length = pcm -> length; if (! mp3f || ! mp3f -> callback) return MAD_FLOW_BREAK; if (mp3f -> first_offset) { /* libMAD can decide to skip the first frame */ if (header -> offset > mp3f -> first_offset) { MP3_DPRINTF (("Skip %u of %lu\n", length, mp3f -> skip_amount)); mp3f -> skip_amount -= length; } mp3f -> first_offset = 0; } if (mp3f -> skip_amount >= length) { mp3f -> skip_amount -= length; return MAD_FLOW_IGNORE; } if (mp3f -> skip_amount > 0) { channels [0] += mp3f -> skip_amount; channels [1] += mp3f -> skip_amount; length -= mp3f -> skip_amount; mp3f -> skip_amount = 0; } if (length > mp3f -> read_amount) { length = mp3f -> read_amount; mp3f -> need_seek = 1; } if (length > 0) mp3f -> callback (channels, length, mp3f -> context); mp3f -> read_amount -= length; return (mp3f -> read_amount > 0) ? MAD_FLOW_CONTINUE : MAD_FLOW_STOP; } /* This conversion function was taken from minimad, and it could be better */ short mp3f_sample_to_short (MP3F_SAMPLE sample) { /* round */ sample += (1L << (MAD_F_FRACBITS - 16)); /* clip */ if (sample >= MAD_F_ONE) sample = MAD_F_ONE - 1; else if (sample < -MAD_F_ONE) sample = -MAD_F_ONE; /* quantize */ return sample >> (MAD_F_FRACBITS + 1 - 16); } /* This function was adapted from libmad */ static enum mad_flow mp3f_mad_error(void *context, struct mad_stream *stream, struct mad_frame *frame) { (void) context; (void) stream; (void) frame; return MAD_FLOW_CONTINUE; } /* This function was adapted from Audacity */ static enum mad_flow mp3f_mad_input(void *context, struct mad_stream *stream) { MP3_FILE mp3f = (MP3_FILE) context; FILE *f = mp3f -> f; unsigned char *buffer = NULL; unsigned nthrown = 0, ncopied = 0, size = 0; size_t nread = 0; MP3F_OFFSET offset; if (feof (f)) return MAD_FLOW_STOP; if (stream -> next_frame) { nthrown = stream -> next_frame - mp3f -> buffer; ncopied = MP3F_BUFFER_SIZE - nthrown; memmove (mp3f -> buffer, stream -> next_frame, ncopied); } buffer = mp3f -> buffer + ncopied; size = MP3F_BUFFER_SIZE - ncopied; offset = ftell (f) - ncopied; if (size > 0) nread = fread (buffer, 1, size, f); mad_stream_buffer_offset (stream, mp3f -> buffer, nread + ncopied, offset); return MAD_FLOW_CONTINUE; } static enum mad_flow mp3f_mad_first_header(void *context, struct mad_header const *header) { MP3_FILE mp3f = (MP3_FILE) context; mp3f -> channels = MAD_NCHANNELS (header); mp3f -> frequency = header -> samplerate; mp3f -> samples_per_frame = 32 * MAD_NSBSAMPLES (header); /* Just in case there is no Xing header: */ mp3f -> locations [mp3f -> num_locations ++] = header -> offset; return MAD_FLOW_CONTINUE; } static enum mad_flow mp3f_mad_first_filter (void *context, struct mad_stream const *stream, struct mad_frame *frame) { MP3_FILE mp3f = (MP3_FILE) context; (void) frame; mp3f -> xing = mp3f_check_xing (mp3f, stream); /* Xing? No need to look further */ if (mp3f -> xing) return MAD_FLOW_STOP; /* Otherwise, read two frames for size estimate */ return (mp3f -> num_locations < 2) ? MAD_FLOW_IGNORE : MAD_FLOW_STOP; } static enum mad_flow mp3f_mad_scan_header(void *context, struct mad_header const *header) { MP3_FILE mp3f = (MP3_FILE) context; /* Some sanity checks */ if (mp3f -> channels != MAD_NCHANNELS (header)) return MAD_FLOW_BREAK; if (mp3f -> frequency != header -> samplerate) return MAD_FLOW_BREAK; if (mp3f -> samples_per_frame != 32 * MAD_NSBSAMPLES (header)) return MAD_FLOW_BREAK; /* Check whether to log this offset in the table */ if ((mp3f -> frames % mp3f -> frames_per_location) == 0 && mp3f -> num_locations < MP3F_MAX_LOCATIONS) mp3f -> locations [mp3f -> num_locations ++] = header -> offset; /* Count this frame */ ++ mp3f -> frames; mp3f -> samples += mp3f -> samples_per_frame; return MAD_FLOW_IGNORE; } /* * Identify a Xing VBR header. * This was adapted from madplay. */ # define XING_VBR_MAGIC (('X' << 24) | ('i' << 16) | ('n' << 8) | 'g') # define XING_CBR_MAGIC (('I' << 24) | ('n' << 16) | ('f' << 8) | 'o') enum { XING_FLAGS_FRAMES = 0x00000001L, XING_FLAGS_BYTES = 0x00000002L, XING_FLAGS_TOC = 0x00000004L, XING_FLAGS_SCALE = 0x00000008L }; static int mp3f_check_xing (MP3_FILE mp3f, struct mad_stream const *stream) { struct mad_bitptr ptr = stream -> anc_ptr; unsigned long magic, flags; /* When we get here we have the following data from the header: * channels * frequency * samples_per_frame * We need to calculate the total number of frames and samples. */ magic = mad_bit_read (&ptr, 32); if (magic != XING_CBR_MAGIC && magic != XING_VBR_MAGIC) return 0; flags = mad_bit_read (&ptr, 32); if ((flags & XING_FLAGS_FRAMES) != XING_FLAGS_FRAMES) return 0; mp3f -> frames = mad_bit_read (&ptr, 32); mp3f -> samples = mp3f -> samples_per_frame * mp3f -> frames; return 1; } sources_5316/external/mp3/mad_decoder.c0000644000176700017670000002663510627342357016663 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: decoder.c,v 1.22 2004/01/23 09:41:32 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # ifdef HAVE_SYS_TYPES_H # include # endif # ifdef HAVE_SYS_WAIT_H # include # endif # ifdef HAVE_UNISTD_H # include # endif # ifdef HAVE_FCNTL_H # include # endif # include # ifdef HAVE_ERRNO_H # include # endif # include "mad_stream.h" # include "mad_frame.h" # include "mad_synth.h" # include "mad_decoder.h" /* * NAME: decoder->init() * DESCRIPTION: initialize a decoder object with callback routines */ void mad_decoder_init(struct mad_decoder *decoder, void *data, enum mad_flow (*input_func)(void *, struct mad_stream *), enum mad_flow (*header_func)(void *, struct mad_header const *), enum mad_flow (*filter_func)(void *, struct mad_stream const *, struct mad_frame *), enum mad_flow (*output_func)(void *, struct mad_header const *, struct mad_pcm *), enum mad_flow (*error_func)(void *, struct mad_stream *, struct mad_frame *), enum mad_flow (*message_func)(void *, void *, unsigned int *)) { decoder->mode = -1; decoder->options = 0; decoder->async.pid = 0; decoder->async.in = -1; decoder->async.out = -1; decoder->sync = 0; decoder->cb_data = data; decoder->input_func = input_func; decoder->header_func = header_func; decoder->filter_func = filter_func; decoder->output_func = output_func; decoder->error_func = error_func; decoder->message_func = message_func; } int mad_decoder_finish(struct mad_decoder *decoder) { # if defined(USE_ASYNC) if (decoder->mode == MAD_DECODER_MODE_ASYNC && decoder->async.pid) { pid_t pid; int status; close(decoder->async.in); do pid = waitpid(decoder->async.pid, &status, 0); while (pid == -1 && errno == EINTR); decoder->mode = -1; close(decoder->async.out); decoder->async.pid = 0; decoder->async.in = -1; decoder->async.out = -1; if (pid == -1) return -1; return (!WIFEXITED(status) || WEXITSTATUS(status)) ? -1 : 0; } # else (void) decoder; # endif return 0; } # if defined(USE_ASYNC) static enum mad_flow send_io(int fd, void const *data, size_t len) { char const *ptr = data; ssize_t count; while (len) { do count = write(fd, ptr, len); while (count == -1 && errno == EINTR); if (count == -1) return MAD_FLOW_BREAK; len -= count; ptr += count; } return MAD_FLOW_CONTINUE; } static enum mad_flow receive_io(int fd, void *buffer, size_t len) { char *ptr = buffer; ssize_t count; while (len) { do count = read(fd, ptr, len); while (count == -1 && errno == EINTR); if (count == -1) return (errno == EAGAIN) ? MAD_FLOW_IGNORE : MAD_FLOW_BREAK; else if (count == 0) return MAD_FLOW_STOP; len -= count; ptr += count; } return MAD_FLOW_CONTINUE; } static enum mad_flow receive_io_blocking(int fd, void *buffer, size_t len) { int flags, blocking; enum mad_flow result; flags = fcntl(fd, F_GETFL); if (flags == -1) return MAD_FLOW_BREAK; blocking = flags & ~O_NONBLOCK; if (blocking != flags && fcntl(fd, F_SETFL, blocking) == -1) return MAD_FLOW_BREAK; result = receive_io(fd, buffer, len); if (flags != blocking && fcntl(fd, F_SETFL, flags) == -1) return MAD_FLOW_BREAK; return result; } static enum mad_flow send(int fd, void const *message, unsigned int size) { enum mad_flow result; /* send size */ result = send_io(fd, &size, sizeof(size)); /* send message */ if (result == MAD_FLOW_CONTINUE) result = send_io(fd, message, size); return result; } static enum mad_flow receive(int fd, void **message, unsigned int *size) { enum mad_flow result; unsigned int actual; if (*message == 0) *size = 0; /* receive size */ result = receive_io(fd, &actual, sizeof(actual)); /* receive message */ if (result == MAD_FLOW_CONTINUE) { if (actual > *size) actual -= *size; else { *size = actual; actual = 0; } if (*size > 0) { if (*message == 0) { *message = malloc(*size); if (*message == 0) return MAD_FLOW_BREAK; } result = receive_io_blocking(fd, *message, *size); } /* throw away remainder of message */ while (actual && result == MAD_FLOW_CONTINUE) { char sink[256]; unsigned int len; len = actual > sizeof(sink) ? sizeof(sink) : actual; result = receive_io_blocking(fd, sink, len); actual -= len; } } return result; } static enum mad_flow check_message(struct mad_decoder *decoder) { enum mad_flow result; void *message = 0; unsigned int size; result = receive(decoder->async.in, &message, &size); if (result == MAD_FLOW_CONTINUE) { if (decoder->message_func == 0) size = 0; else { result = decoder->message_func(decoder->cb_data, message, &size); if (result == MAD_FLOW_IGNORE || result == MAD_FLOW_BREAK) size = 0; } if (send(decoder->async.out, message, size) != MAD_FLOW_CONTINUE) result = MAD_FLOW_BREAK; } if (message) free(message); return result; } # endif static enum mad_flow error_default(void *data, struct mad_stream *stream, struct mad_frame *frame) { int *bad_last_frame = data; switch (stream->error) { case MAD_ERROR_BADCRC: if (*bad_last_frame) mad_frame_mute(frame); else *bad_last_frame = 1; return MAD_FLOW_IGNORE; default: return MAD_FLOW_CONTINUE; } } static int run_sync(struct mad_decoder *decoder) { enum mad_flow (*error_func)(void *, struct mad_stream *, struct mad_frame *); void *error_data; int bad_last_frame = 0; struct mad_stream *stream; struct mad_frame *frame; struct mad_synth *synth; int result = 0; if (decoder->input_func == 0) return 0; if (decoder->error_func) { error_func = decoder->error_func; error_data = decoder->cb_data; } else { error_func = error_default; error_data = &bad_last_frame; } stream = &decoder->sync->stream; frame = &decoder->sync->frame; synth = &decoder->sync->synth; mad_stream_init(stream); mad_frame_init(frame); mad_synth_init(synth); mad_stream_options(stream, decoder->options); do { switch (decoder->input_func(decoder->cb_data, stream)) { case MAD_FLOW_STOP: goto done; case MAD_FLOW_BREAK: goto fail; case MAD_FLOW_IGNORE: continue; case MAD_FLOW_CONTINUE: break; } while (1) { # if defined(USE_ASYNC) if (decoder->mode == MAD_DECODER_MODE_ASYNC) { switch (check_message(decoder)) { case MAD_FLOW_IGNORE: case MAD_FLOW_CONTINUE: break; case MAD_FLOW_BREAK: goto fail; case MAD_FLOW_STOP: goto done; } } # endif if (decoder->header_func) { if (mad_header_decode(&frame->header, stream) == -1) { if (!MAD_RECOVERABLE(stream->error)) break; switch (error_func(error_data, stream, frame)) { case MAD_FLOW_STOP: goto done; case MAD_FLOW_BREAK: goto fail; case MAD_FLOW_IGNORE: case MAD_FLOW_CONTINUE: default: continue; } } switch (decoder->header_func(decoder->cb_data, &frame->header)) { case MAD_FLOW_STOP: goto done; case MAD_FLOW_BREAK: goto fail; case MAD_FLOW_IGNORE: continue; case MAD_FLOW_CONTINUE: break; } } if (mad_frame_decode(frame, stream) == -1) { if (!MAD_RECOVERABLE(stream->error)) break; switch (error_func(error_data, stream, frame)) { case MAD_FLOW_STOP: goto done; case MAD_FLOW_BREAK: goto fail; case MAD_FLOW_IGNORE: break; case MAD_FLOW_CONTINUE: default: continue; } } else bad_last_frame = 0; if (decoder->filter_func) { switch (decoder->filter_func(decoder->cb_data, stream, frame)) { case MAD_FLOW_STOP: goto done; case MAD_FLOW_BREAK: goto fail; case MAD_FLOW_IGNORE: continue; case MAD_FLOW_CONTINUE: break; } } mad_synth_frame(synth, frame); if (decoder->output_func) { switch (decoder->output_func(decoder->cb_data, &frame->header, &synth->pcm)) { case MAD_FLOW_STOP: goto done; case MAD_FLOW_BREAK: goto fail; case MAD_FLOW_IGNORE: case MAD_FLOW_CONTINUE: break; } } } } while (stream->error == MAD_ERROR_BUFLEN); fail: result = -1; done: mad_synth_finish(synth); mad_frame_finish(frame); mad_stream_finish(stream); return result; } # if defined(USE_ASYNC) static int run_async(struct mad_decoder *decoder) { pid_t pid; int ptoc[2], ctop[2], flags; if (pipe(ptoc) == -1) return -1; if (pipe(ctop) == -1) { close(ptoc[0]); close(ptoc[1]); return -1; } flags = fcntl(ptoc[0], F_GETFL); if (flags == -1 || fcntl(ptoc[0], F_SETFL, flags | O_NONBLOCK) == -1) { close(ctop[0]); close(ctop[1]); close(ptoc[0]); close(ptoc[1]); return -1; } pid = fork(); if (pid == -1) { close(ctop[0]); close(ctop[1]); close(ptoc[0]); close(ptoc[1]); return -1; } decoder->async.pid = pid; if (pid) { /* parent */ close(ptoc[0]); close(ctop[1]); decoder->async.in = ctop[0]; decoder->async.out = ptoc[1]; return 0; } /* child */ close(ptoc[1]); close(ctop[0]); decoder->async.in = ptoc[0]; decoder->async.out = ctop[1]; _exit(run_sync(decoder)); /* not reached */ return -1; } # endif /* * NAME: decoder->run() * DESCRIPTION: run the decoder thread either synchronously or asynchronously */ int mad_decoder_run(struct mad_decoder *decoder, enum mad_decoder_mode mode) { int result; int (*run)(struct mad_decoder *) = 0; switch (decoder->mode = mode) { case MAD_DECODER_MODE_SYNC: run = run_sync; break; case MAD_DECODER_MODE_ASYNC: # if defined(USE_ASYNC) run = run_async; # endif break; } if (run == 0) return -1; decoder->sync = malloc(sizeof(*decoder->sync)); if (decoder->sync == 0) return -1; result = run(decoder); free(decoder->sync); decoder->sync = 0; return result; } /* * NAME: decoder->message() * DESCRIPTION: send a message to and receive a reply from the decoder process */ int mad_decoder_message(struct mad_decoder *decoder, void *message, unsigned int *len) { # if defined(USE_ASYNC) if (decoder->mode != MAD_DECODER_MODE_ASYNC || send(decoder->async.out, message, *len) != MAD_FLOW_CONTINUE || receive(decoder->async.in, &message, len) != MAD_FLOW_CONTINUE) return -1; return 0; # else (void) decoder; (void) message; (void) len; return -1; # endif } sources_5316/external/mp3/mad_layer3.c0000644000176700017670000021106310627342357016444 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: layer3.c,v 1.43 2004/01/23 09:41:32 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # include # include # ifdef HAVE_ASSERT_H # include # endif # ifdef HAVE_LIMITS_H # include # else # define CHAR_BIT 8 # endif # include "mad_fixed.h" # include "mad_bit.h" # include "mad_stream.h" # include "mad_frame.h" # include "mad_huffman.h" # include "mad_layer3.h" /* --- Layer III ----------------------------------------------------------- */ enum { count1table_select = 0x01, scalefac_scale = 0x02, preflag = 0x04, mixed_block_flag = 0x08 }; enum { I_STEREO = 0x1, MS_STEREO = 0x2 }; struct sideinfo { unsigned int main_data_begin; unsigned int private_bits; unsigned char scfsi[2]; struct granule { struct channel { /* from side info */ unsigned short part2_3_length; unsigned short big_values; unsigned short global_gain; unsigned short scalefac_compress; unsigned char flags; unsigned char block_type; unsigned char table_select[3]; unsigned char subblock_gain[3]; unsigned char region0_count; unsigned char region1_count; /* from main_data */ unsigned char scalefac[39]; /* scalefac_l and/or scalefac_s */ } ch[2]; } gr[2]; }; /* * scalefactor bit lengths * derived from section 2.4.2.7 of ISO/IEC 11172-3 */ static struct { unsigned char slen1; unsigned char slen2; } const sflen_table[16] = { { 0, 0 }, { 0, 1 }, { 0, 2 }, { 0, 3 }, { 3, 0 }, { 1, 1 }, { 1, 2 }, { 1, 3 }, { 2, 1 }, { 2, 2 }, { 2, 3 }, { 3, 1 }, { 3, 2 }, { 3, 3 }, { 4, 2 }, { 4, 3 } }; /* * number of LSF scalefactor band values * derived from section 2.4.3.2 of ISO/IEC 13818-3 */ static unsigned char const nsfb_table[6][3][4] = { { { 6, 5, 5, 5 }, { 9, 9, 9, 9 }, { 6, 9, 9, 9 } }, { { 6, 5, 7, 3 }, { 9, 9, 12, 6 }, { 6, 9, 12, 6 } }, { { 11, 10, 0, 0 }, { 18, 18, 0, 0 }, { 15, 18, 0, 0 } }, { { 7, 7, 7, 0 }, { 12, 12, 12, 0 }, { 6, 15, 12, 0 } }, { { 6, 6, 6, 3 }, { 12, 9, 9, 6 }, { 6, 12, 9, 6 } }, { { 8, 8, 5, 0 }, { 15, 12, 9, 0 }, { 6, 18, 9, 0 } } }; /* * MPEG-1 scalefactor band widths * derived from Table B.8 of ISO/IEC 11172-3 */ static unsigned char const sfb_48000_long[] = { 4, 4, 4, 4, 4, 4, 6, 6, 6, 8, 10, 12, 16, 18, 22, 28, 34, 40, 46, 54, 54, 192 }; static unsigned char const sfb_44100_long[] = { 4, 4, 4, 4, 4, 4, 6, 6, 8, 8, 10, 12, 16, 20, 24, 28, 34, 42, 50, 54, 76, 158 }; static unsigned char const sfb_32000_long[] = { 4, 4, 4, 4, 4, 4, 6, 6, 8, 10, 12, 16, 20, 24, 30, 38, 46, 56, 68, 84, 102, 26 }; static unsigned char const sfb_48000_short[] = { 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 6, 6, 6, 6, 6, 6, 10, 10, 10, 12, 12, 12, 14, 14, 14, 16, 16, 16, 20, 20, 20, 26, 26, 26, 66, 66, 66 }; static unsigned char const sfb_44100_short[] = { 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 6, 6, 6, 8, 8, 8, 10, 10, 10, 12, 12, 12, 14, 14, 14, 18, 18, 18, 22, 22, 22, 30, 30, 30, 56, 56, 56 }; static unsigned char const sfb_32000_short[] = { 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 6, 6, 6, 8, 8, 8, 12, 12, 12, 16, 16, 16, 20, 20, 20, 26, 26, 26, 34, 34, 34, 42, 42, 42, 12, 12, 12 }; static unsigned char const sfb_48000_mixed[] = { /* long */ 4, 4, 4, 4, 4, 4, 6, 6, /* short */ 4, 4, 4, 6, 6, 6, 6, 6, 6, 10, 10, 10, 12, 12, 12, 14, 14, 14, 16, 16, 16, 20, 20, 20, 26, 26, 26, 66, 66, 66 }; static unsigned char const sfb_44100_mixed[] = { /* long */ 4, 4, 4, 4, 4, 4, 6, 6, /* short */ 4, 4, 4, 6, 6, 6, 8, 8, 8, 10, 10, 10, 12, 12, 12, 14, 14, 14, 18, 18, 18, 22, 22, 22, 30, 30, 30, 56, 56, 56 }; static unsigned char const sfb_32000_mixed[] = { /* long */ 4, 4, 4, 4, 4, 4, 6, 6, /* short */ 4, 4, 4, 6, 6, 6, 8, 8, 8, 12, 12, 12, 16, 16, 16, 20, 20, 20, 26, 26, 26, 34, 34, 34, 42, 42, 42, 12, 12, 12 }; /* * MPEG-2 scalefactor band widths * derived from Table B.2 of ISO/IEC 13818-3 */ static unsigned char const sfb_24000_long[] = { 6, 6, 6, 6, 6, 6, 8, 10, 12, 14, 16, 18, 22, 26, 32, 38, 46, 54, 62, 70, 76, 36 }; static unsigned char const sfb_22050_long[] = { 6, 6, 6, 6, 6, 6, 8, 10, 12, 14, 16, 20, 24, 28, 32, 38, 46, 52, 60, 68, 58, 54 }; # define sfb_16000_long sfb_22050_long static unsigned char const sfb_24000_short[] = { 4, 4, 4, 4, 4, 4, 4, 4, 4, 6, 6, 6, 8, 8, 8, 10, 10, 10, 12, 12, 12, 14, 14, 14, 18, 18, 18, 24, 24, 24, 32, 32, 32, 44, 44, 44, 12, 12, 12 }; static unsigned char const sfb_22050_short[] = { 4, 4, 4, 4, 4, 4, 4, 4, 4, 6, 6, 6, 6, 6, 6, 8, 8, 8, 10, 10, 10, 14, 14, 14, 18, 18, 18, 26, 26, 26, 32, 32, 32, 42, 42, 42, 18, 18, 18 }; static unsigned char const sfb_16000_short[] = { 4, 4, 4, 4, 4, 4, 4, 4, 4, 6, 6, 6, 8, 8, 8, 10, 10, 10, 12, 12, 12, 14, 14, 14, 18, 18, 18, 24, 24, 24, 30, 30, 30, 40, 40, 40, 18, 18, 18 }; static unsigned char const sfb_24000_mixed[] = { /* long */ 6, 6, 6, 6, 6, 6, /* short */ 6, 6, 6, 8, 8, 8, 10, 10, 10, 12, 12, 12, 14, 14, 14, 18, 18, 18, 24, 24, 24, 32, 32, 32, 44, 44, 44, 12, 12, 12 }; static unsigned char const sfb_22050_mixed[] = { /* long */ 6, 6, 6, 6, 6, 6, /* short */ 6, 6, 6, 6, 6, 6, 8, 8, 8, 10, 10, 10, 14, 14, 14, 18, 18, 18, 26, 26, 26, 32, 32, 32, 42, 42, 42, 18, 18, 18 }; static unsigned char const sfb_16000_mixed[] = { /* long */ 6, 6, 6, 6, 6, 6, /* short */ 6, 6, 6, 8, 8, 8, 10, 10, 10, 12, 12, 12, 14, 14, 14, 18, 18, 18, 24, 24, 24, 30, 30, 30, 40, 40, 40, 18, 18, 18 }; /* * MPEG 2.5 scalefactor band widths * derived from public sources */ # define sfb_12000_long sfb_16000_long # define sfb_11025_long sfb_12000_long static unsigned char const sfb_8000_long[] = { 12, 12, 12, 12, 12, 12, 16, 20, 24, 28, 32, 40, 48, 56, 64, 76, 90, 2, 2, 2, 2, 2 }; # define sfb_12000_short sfb_16000_short # define sfb_11025_short sfb_12000_short static unsigned char const sfb_8000_short[] = { 8, 8, 8, 8, 8, 8, 8, 8, 8, 12, 12, 12, 16, 16, 16, 20, 20, 20, 24, 24, 24, 28, 28, 28, 36, 36, 36, 2, 2, 2, 2, 2, 2, 2, 2, 2, 26, 26, 26 }; # define sfb_12000_mixed sfb_16000_mixed # define sfb_11025_mixed sfb_12000_mixed /* the 8000 Hz short block scalefactor bands do not break after the first 36 frequency lines, so this is probably wrong */ static unsigned char const sfb_8000_mixed[] = { /* long */ 12, 12, 12, /* short */ 4, 4, 4, 8, 8, 8, 12, 12, 12, 16, 16, 16, 20, 20, 20, 24, 24, 24, 28, 28, 28, 36, 36, 36, 2, 2, 2, 2, 2, 2, 2, 2, 2, 26, 26, 26 }; static struct { unsigned char const *l; unsigned char const *s; unsigned char const *m; } const sfbwidth_table[9] = { { sfb_48000_long, sfb_48000_short, sfb_48000_mixed }, { sfb_44100_long, sfb_44100_short, sfb_44100_mixed }, { sfb_32000_long, sfb_32000_short, sfb_32000_mixed }, { sfb_24000_long, sfb_24000_short, sfb_24000_mixed }, { sfb_22050_long, sfb_22050_short, sfb_22050_mixed }, { sfb_16000_long, sfb_16000_short, sfb_16000_mixed }, { sfb_12000_long, sfb_12000_short, sfb_12000_mixed }, { sfb_11025_long, sfb_11025_short, sfb_11025_mixed }, { sfb_8000_long, sfb_8000_short, sfb_8000_mixed } }; /* * scalefactor band preemphasis (used only when preflag is set) * derived from Table B.6 of ISO/IEC 11172-3 */ static unsigned char const pretab[22] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 3, 3, 3, 2, 0 }; /* * table for requantization * * rq_table[x].mantissa * 2^(rq_table[x].exponent) = x^(4/3) */ static struct fixedfloat { unsigned long mantissa : 27; unsigned short exponent : 5; } const rq_table[8207] = { # include "mad_rq_table.dat" }; /* * fractional powers of two * used for requantization and joint stereo decoding * * root_table[3 + x] = 2^(x/4) */ static mad_fixed_t const root_table[7] = { MAD_F(0x09837f05) /* 2^(-3/4) == 0.59460355750136 */, MAD_F(0x0b504f33) /* 2^(-2/4) == 0.70710678118655 */, MAD_F(0x0d744fcd) /* 2^(-1/4) == 0.84089641525371 */, MAD_F(0x10000000) /* 2^( 0/4) == 1.00000000000000 */, MAD_F(0x1306fe0a) /* 2^(+1/4) == 1.18920711500272 */, MAD_F(0x16a09e66) /* 2^(+2/4) == 1.41421356237310 */, MAD_F(0x1ae89f99) /* 2^(+3/4) == 1.68179283050743 */ }; /* * coefficients for aliasing reduction * derived from Table B.9 of ISO/IEC 11172-3 * * c[] = { -0.6, -0.535, -0.33, -0.185, -0.095, -0.041, -0.0142, -0.0037 } * cs[i] = 1 / sqrt(1 + c[i]^2) * ca[i] = c[i] / sqrt(1 + c[i]^2) */ static mad_fixed_t const cs[8] = { +MAD_F(0x0db84a81) /* +0.857492926 */, +MAD_F(0x0e1b9d7f) /* +0.881741997 */, +MAD_F(0x0f31adcf) /* +0.949628649 */, +MAD_F(0x0fbba815) /* +0.983314592 */, +MAD_F(0x0feda417) /* +0.995517816 */, +MAD_F(0x0ffc8fc8) /* +0.999160558 */, +MAD_F(0x0fff964c) /* +0.999899195 */, +MAD_F(0x0ffff8d3) /* +0.999993155 */ }; static mad_fixed_t const ca[8] = { -MAD_F(0x083b5fe7) /* -0.514495755 */, -MAD_F(0x078c36d2) /* -0.471731969 */, -MAD_F(0x05039814) /* -0.313377454 */, -MAD_F(0x02e91dd1) /* -0.181913200 */, -MAD_F(0x0183603a) /* -0.094574193 */, -MAD_F(0x00a7cb87) /* -0.040965583 */, -MAD_F(0x003a2847) /* -0.014198569 */, -MAD_F(0x000f27b4) /* -0.003699975 */ }; /* * IMDCT coefficients for short blocks * derived from section 2.4.3.4.10.2 of ISO/IEC 11172-3 * * imdct_s[i/even][k] = cos((PI / 24) * (2 * (i / 2) + 7) * (2 * k + 1)) * imdct_s[i /odd][k] = cos((PI / 24) * (2 * (6 + (i-1)/2) + 7) * (2 * k + 1)) */ static mad_fixed_t const imdct_s[6][6] = { # include "mad_imdct_s.dat" }; # if !defined(ASO_IMDCT) /* * windowing coefficients for long blocks * derived from section 2.4.3.4.10.3 of ISO/IEC 11172-3 * * window_l[i] = sin((PI / 36) * (i + 1/2)) */ static mad_fixed_t const window_l[36] = { MAD_F(0x00b2aa3e) /* 0.043619387 */, MAD_F(0x0216a2a2) /* 0.130526192 */, MAD_F(0x03768962) /* 0.216439614 */, MAD_F(0x04cfb0e2) /* 0.300705800 */, MAD_F(0x061f78aa) /* 0.382683432 */, MAD_F(0x07635284) /* 0.461748613 */, MAD_F(0x0898c779) /* 0.537299608 */, MAD_F(0x09bd7ca0) /* 0.608761429 */, MAD_F(0x0acf37ad) /* 0.675590208 */, MAD_F(0x0bcbe352) /* 0.737277337 */, MAD_F(0x0cb19346) /* 0.793353340 */, MAD_F(0x0d7e8807) /* 0.843391446 */, MAD_F(0x0e313245) /* 0.887010833 */, MAD_F(0x0ec835e8) /* 0.923879533 */, MAD_F(0x0f426cb5) /* 0.953716951 */, MAD_F(0x0f9ee890) /* 0.976296007 */, MAD_F(0x0fdcf549) /* 0.991444861 */, MAD_F(0x0ffc19fd) /* 0.999048222 */, MAD_F(0x0ffc19fd) /* 0.999048222 */, MAD_F(0x0fdcf549) /* 0.991444861 */, MAD_F(0x0f9ee890) /* 0.976296007 */, MAD_F(0x0f426cb5) /* 0.953716951 */, MAD_F(0x0ec835e8) /* 0.923879533 */, MAD_F(0x0e313245) /* 0.887010833 */, MAD_F(0x0d7e8807) /* 0.843391446 */, MAD_F(0x0cb19346) /* 0.793353340 */, MAD_F(0x0bcbe352) /* 0.737277337 */, MAD_F(0x0acf37ad) /* 0.675590208 */, MAD_F(0x09bd7ca0) /* 0.608761429 */, MAD_F(0x0898c779) /* 0.537299608 */, MAD_F(0x07635284) /* 0.461748613 */, MAD_F(0x061f78aa) /* 0.382683432 */, MAD_F(0x04cfb0e2) /* 0.300705800 */, MAD_F(0x03768962) /* 0.216439614 */, MAD_F(0x0216a2a2) /* 0.130526192 */, MAD_F(0x00b2aa3e) /* 0.043619387 */, }; # endif /* ASO_IMDCT */ /* * windowing coefficients for short blocks * derived from section 2.4.3.4.10.3 of ISO/IEC 11172-3 * * window_s[i] = sin((PI / 12) * (i + 1/2)) */ static mad_fixed_t const window_s[12] = { MAD_F(0x0216a2a2) /* 0.130526192 */, MAD_F(0x061f78aa) /* 0.382683432 */, MAD_F(0x09bd7ca0) /* 0.608761429 */, MAD_F(0x0cb19346) /* 0.793353340 */, MAD_F(0x0ec835e8) /* 0.923879533 */, MAD_F(0x0fdcf549) /* 0.991444861 */, MAD_F(0x0fdcf549) /* 0.991444861 */, MAD_F(0x0ec835e8) /* 0.923879533 */, MAD_F(0x0cb19346) /* 0.793353340 */, MAD_F(0x09bd7ca0) /* 0.608761429 */, MAD_F(0x061f78aa) /* 0.382683432 */, MAD_F(0x0216a2a2) /* 0.130526192 */, }; /* * coefficients for intensity stereo processing * derived from section 2.4.3.4.9.3 of ISO/IEC 11172-3 * * is_ratio[i] = tan(i * (PI / 12)) * is_table[i] = is_ratio[i] / (1 + is_ratio[i]) */ static mad_fixed_t const is_table[7] = { MAD_F(0x00000000) /* 0.000000000 */, MAD_F(0x0361962f) /* 0.211324865 */, MAD_F(0x05db3d74) /* 0.366025404 */, MAD_F(0x08000000) /* 0.500000000 */, MAD_F(0x0a24c28c) /* 0.633974596 */, MAD_F(0x0c9e69d1) /* 0.788675135 */, MAD_F(0x10000000) /* 1.000000000 */ }; /* * coefficients for LSF intensity stereo processing * derived from section 2.4.3.2 of ISO/IEC 13818-3 * * is_lsf_table[0][i] = (1 / sqrt(sqrt(2)))^(i + 1) * is_lsf_table[1][i] = (1 / sqrt(2)) ^(i + 1) */ static mad_fixed_t const is_lsf_table[2][15] = { { MAD_F(0x0d744fcd) /* 0.840896415 */, MAD_F(0x0b504f33) /* 0.707106781 */, MAD_F(0x09837f05) /* 0.594603558 */, MAD_F(0x08000000) /* 0.500000000 */, MAD_F(0x06ba27e6) /* 0.420448208 */, MAD_F(0x05a8279a) /* 0.353553391 */, MAD_F(0x04c1bf83) /* 0.297301779 */, MAD_F(0x04000000) /* 0.250000000 */, MAD_F(0x035d13f3) /* 0.210224104 */, MAD_F(0x02d413cd) /* 0.176776695 */, MAD_F(0x0260dfc1) /* 0.148650889 */, MAD_F(0x02000000) /* 0.125000000 */, MAD_F(0x01ae89fa) /* 0.105112052 */, MAD_F(0x016a09e6) /* 0.088388348 */, MAD_F(0x01306fe1) /* 0.074325445 */ }, { MAD_F(0x0b504f33) /* 0.707106781 */, MAD_F(0x08000000) /* 0.500000000 */, MAD_F(0x05a8279a) /* 0.353553391 */, MAD_F(0x04000000) /* 0.250000000 */, MAD_F(0x02d413cd) /* 0.176776695 */, MAD_F(0x02000000) /* 0.125000000 */, MAD_F(0x016a09e6) /* 0.088388348 */, MAD_F(0x01000000) /* 0.062500000 */, MAD_F(0x00b504f3) /* 0.044194174 */, MAD_F(0x00800000) /* 0.031250000 */, MAD_F(0x005a827a) /* 0.022097087 */, MAD_F(0x00400000) /* 0.015625000 */, MAD_F(0x002d413d) /* 0.011048543 */, MAD_F(0x00200000) /* 0.007812500 */, MAD_F(0x0016a09e) /* 0.005524272 */ } }; /* * NAME: III_sideinfo() * DESCRIPTION: decode frame side information from a bitstream */ static enum mad_error III_sideinfo(struct mad_bitptr *ptr, unsigned int nch, int lsf, struct sideinfo *si, unsigned int *data_bitlen, unsigned int *priv_bitlen) { unsigned int ngr, gr, ch, i; enum mad_error result = MAD_ERROR_NONE; *data_bitlen = 0; *priv_bitlen = lsf ? ((nch == 1) ? 1 : 2) : ((nch == 1) ? 5 : 3); si->main_data_begin = mad_bit_read(ptr, lsf ? 8 : 9); si->private_bits = mad_bit_read(ptr, *priv_bitlen); ngr = 1; if (!lsf) { ngr = 2; for (ch = 0; ch < nch; ++ch) si->scfsi[ch] = mad_bit_read(ptr, 4); } for (gr = 0; gr < ngr; ++gr) { struct granule *granule = &si->gr[gr]; for (ch = 0; ch < nch; ++ch) { struct channel *channel = &granule->ch[ch]; channel->part2_3_length = mad_bit_read(ptr, 12); channel->big_values = mad_bit_read(ptr, 9); channel->global_gain = mad_bit_read(ptr, 8); channel->scalefac_compress = mad_bit_read(ptr, lsf ? 9 : 4); *data_bitlen += channel->part2_3_length; if (channel->big_values > 288 && result == 0) result = MAD_ERROR_BADBIGVALUES; channel->flags = 0; /* window_switching_flag */ if (mad_bit_read(ptr, 1)) { channel->block_type = mad_bit_read(ptr, 2); if (channel->block_type == 0 && result == 0) result = MAD_ERROR_BADBLOCKTYPE; if (!lsf && channel->block_type == 2 && si->scfsi[ch] && result == 0) result = MAD_ERROR_BADSCFSI; channel->region0_count = 7; channel->region1_count = 36; if (mad_bit_read(ptr, 1)) channel->flags |= mixed_block_flag; else if (channel->block_type == 2) channel->region0_count = 8; for (i = 0; i < 2; ++i) channel->table_select[i] = mad_bit_read(ptr, 5); # if defined(DEBUG) channel->table_select[2] = 4; /* not used */ # endif for (i = 0; i < 3; ++i) channel->subblock_gain[i] = mad_bit_read(ptr, 3); } else { channel->block_type = 0; for (i = 0; i < 3; ++i) channel->table_select[i] = mad_bit_read(ptr, 5); channel->region0_count = mad_bit_read(ptr, 4); channel->region1_count = mad_bit_read(ptr, 3); } /* [preflag,] scalefac_scale, count1table_select */ channel->flags |= mad_bit_read(ptr, lsf ? 2 : 3); } } return result; } /* * NAME: III_scalefactors_lsf() * DESCRIPTION: decode channel scalefactors for LSF from a bitstream */ static unsigned int III_scalefactors_lsf(struct mad_bitptr *ptr, struct channel *channel, struct channel *gr1ch, int mode_extension) { struct mad_bitptr start; unsigned int scalefac_compress, index, slen[4], part, n, i; unsigned char const *nsfb; start = *ptr; scalefac_compress = channel->scalefac_compress; index = (channel->block_type == 2) ? ((channel->flags & mixed_block_flag) ? 2 : 1) : 0; if (!((mode_extension & I_STEREO) && gr1ch)) { if (scalefac_compress < 400) { slen[0] = (scalefac_compress >> 4) / 5; slen[1] = (scalefac_compress >> 4) % 5; slen[2] = (scalefac_compress % 16) >> 2; slen[3] = scalefac_compress % 4; nsfb = nsfb_table[0][index]; } else if (scalefac_compress < 500) { scalefac_compress -= 400; slen[0] = (scalefac_compress >> 2) / 5; slen[1] = (scalefac_compress >> 2) % 5; slen[2] = scalefac_compress % 4; slen[3] = 0; nsfb = nsfb_table[1][index]; } else { scalefac_compress -= 500; slen[0] = scalefac_compress / 3; slen[1] = scalefac_compress % 3; slen[2] = 0; slen[3] = 0; channel->flags |= preflag; nsfb = nsfb_table[2][index]; } n = 0; for (part = 0; part < 4; ++part) { for (i = 0; i < nsfb[part]; ++i) channel->scalefac[n++] = mad_bit_read(ptr, slen[part]); } while (n < 39) channel->scalefac[n++] = 0; } else { /* (mode_extension & I_STEREO) && gr1ch (i.e. ch == 1) */ scalefac_compress >>= 1; if (scalefac_compress < 180) { slen[0] = scalefac_compress / 36; slen[1] = (scalefac_compress % 36) / 6; slen[2] = (scalefac_compress % 36) % 6; slen[3] = 0; nsfb = nsfb_table[3][index]; } else if (scalefac_compress < 244) { scalefac_compress -= 180; slen[0] = (scalefac_compress % 64) >> 4; slen[1] = (scalefac_compress % 16) >> 2; slen[2] = scalefac_compress % 4; slen[3] = 0; nsfb = nsfb_table[4][index]; } else { scalefac_compress -= 244; slen[0] = scalefac_compress / 3; slen[1] = scalefac_compress % 3; slen[2] = 0; slen[3] = 0; nsfb = nsfb_table[5][index]; } n = 0; for (part = 0; part < 4; ++part) { unsigned int max, is_pos; max = (1 << slen[part]) - 1; for (i = 0; i < nsfb[part]; ++i) { is_pos = mad_bit_read(ptr, slen[part]); channel->scalefac[n] = is_pos; gr1ch->scalefac[n++] = (is_pos == max); } } while (n < 39) { channel->scalefac[n] = 0; gr1ch->scalefac[n++] = 0; /* apparently not illegal */ } } return mad_bit_length(&start, ptr); } /* * NAME: III_scalefactors() * DESCRIPTION: decode channel scalefactors of one granule from a bitstream */ static unsigned int III_scalefactors(struct mad_bitptr *ptr, struct channel *channel, struct channel const *gr0ch, unsigned int scfsi) { struct mad_bitptr start; unsigned int slen1, slen2, sfbi; start = *ptr; slen1 = sflen_table[channel->scalefac_compress].slen1; slen2 = sflen_table[channel->scalefac_compress].slen2; if (channel->block_type == 2) { unsigned int nsfb; sfbi = 0; nsfb = (channel->flags & mixed_block_flag) ? 8 + 3 * 3 : 6 * 3; while (nsfb--) channel->scalefac[sfbi++] = mad_bit_read(ptr, slen1); nsfb = 6 * 3; while (nsfb--) channel->scalefac[sfbi++] = mad_bit_read(ptr, slen2); nsfb = 1 * 3; while (nsfb--) channel->scalefac[sfbi++] = 0; } else { /* channel->block_type != 2 */ if (scfsi & 0x8) { for (sfbi = 0; sfbi < 6; ++sfbi) channel->scalefac[sfbi] = gr0ch->scalefac[sfbi]; } else { for (sfbi = 0; sfbi < 6; ++sfbi) channel->scalefac[sfbi] = mad_bit_read(ptr, slen1); } if (scfsi & 0x4) { for (sfbi = 6; sfbi < 11; ++sfbi) channel->scalefac[sfbi] = gr0ch->scalefac[sfbi]; } else { for (sfbi = 6; sfbi < 11; ++sfbi) channel->scalefac[sfbi] = mad_bit_read(ptr, slen1); } if (scfsi & 0x2) { for (sfbi = 11; sfbi < 16; ++sfbi) channel->scalefac[sfbi] = gr0ch->scalefac[sfbi]; } else { for (sfbi = 11; sfbi < 16; ++sfbi) channel->scalefac[sfbi] = mad_bit_read(ptr, slen2); } if (scfsi & 0x1) { for (sfbi = 16; sfbi < 21; ++sfbi) channel->scalefac[sfbi] = gr0ch->scalefac[sfbi]; } else { for (sfbi = 16; sfbi < 21; ++sfbi) channel->scalefac[sfbi] = mad_bit_read(ptr, slen2); } channel->scalefac[21] = 0; } return mad_bit_length(&start, ptr); } /* * The Layer III formula for requantization and scaling is defined by * section 2.4.3.4.7.1 of ISO/IEC 11172-3, as follows: * * long blocks: * xr[i] = sign(is[i]) * abs(is[i])^(4/3) * * 2^((1/4) * (global_gain - 210)) * * 2^-(scalefac_multiplier * * (scalefac_l[sfb] + preflag * pretab[sfb])) * * short blocks: * xr[i] = sign(is[i]) * abs(is[i])^(4/3) * * 2^((1/4) * (global_gain - 210 - 8 * subblock_gain[w])) * * 2^-(scalefac_multiplier * scalefac_s[sfb][w]) * * where: * scalefac_multiplier = (scalefac_scale + 1) / 2 * * The routines III_exponents() and III_requantize() facilitate this * calculation. */ /* * NAME: III_exponents() * DESCRIPTION: calculate scalefactor exponents */ static void III_exponents(struct channel const *channel, unsigned char const *sfbwidth, signed int exponents[39]) { signed int gain; unsigned int scalefac_multiplier, sfbi; gain = (signed int) channel->global_gain - 210; scalefac_multiplier = (channel->flags & scalefac_scale) ? 2 : 1; if (channel->block_type == 2) { unsigned int l; signed int gain0, gain1, gain2; sfbi = l = 0; if (channel->flags & mixed_block_flag) { unsigned int premask; premask = (channel->flags & preflag) ? ~0 : 0; /* long block subbands 0-1 */ while (l < 36) { exponents[sfbi] = gain - (signed int) ((channel->scalefac[sfbi] + (pretab[sfbi] & premask)) << scalefac_multiplier); l += sfbwidth[sfbi++]; } } /* this is probably wrong for 8000 Hz short/mixed blocks */ gain0 = gain - 8 * (signed int) channel->subblock_gain[0]; gain1 = gain - 8 * (signed int) channel->subblock_gain[1]; gain2 = gain - 8 * (signed int) channel->subblock_gain[2]; while (l < 576) { exponents[sfbi + 0] = gain0 - (signed int) (channel->scalefac[sfbi + 0] << scalefac_multiplier); exponents[sfbi + 1] = gain1 - (signed int) (channel->scalefac[sfbi + 1] << scalefac_multiplier); exponents[sfbi + 2] = gain2 - (signed int) (channel->scalefac[sfbi + 2] << scalefac_multiplier); l += 3 * sfbwidth[sfbi]; sfbi += 3; } } else { /* channel->block_type != 2 */ if (channel->flags & preflag) { for (sfbi = 0; sfbi < 22; ++sfbi) { exponents[sfbi] = gain - (signed int) ((channel->scalefac[sfbi] + pretab[sfbi]) << scalefac_multiplier); } } else { for (sfbi = 0; sfbi < 22; ++sfbi) { exponents[sfbi] = gain - (signed int) (channel->scalefac[sfbi] << scalefac_multiplier); } } } } /* * NAME: III_requantize() * DESCRIPTION: requantize one (positive) value */ static mad_fixed_t III_requantize(unsigned int value, signed int exp) { mad_fixed_t requantized; signed int frac; struct fixedfloat const *power; frac = exp % 4; /* assumes sign(frac) == sign(exp) */ exp /= 4; power = &rq_table[value]; requantized = power->mantissa; exp += power->exponent; if (exp < 0) { if (-exp >= sizeof(mad_fixed_t) * CHAR_BIT) { /* underflow */ requantized = 0; } else { requantized += 1L << (-exp - 1); requantized >>= -exp; } } else { if (exp >= 5) { /* overflow */ # if defined(DEBUG) fprintf(stderr, "requantize overflow (%f * 2^%d)\n", mad_f_todouble(requantized), exp); # endif requantized = MAD_F_MAX; } else requantized <<= exp; } return frac ? mad_f_mul(requantized, root_table[3 + frac]) : requantized; } /* we must take care that sz >= bits and sz < sizeof(long) lest bits == 0 */ # define MASK(cache, sz, bits) \ (((cache) >> ((sz) - (bits))) & ((1 << (bits)) - 1)) # define MASK1BIT(cache, sz) \ ((cache) & (1 << ((sz) - 1))) /* * NAME: III_huffdecode() * DESCRIPTION: decode Huffman code words of one channel of one granule */ static enum mad_error III_huffdecode(struct mad_bitptr *ptr, mad_fixed_t xr[576], struct channel *channel, unsigned char const *sfbwidth, unsigned int part2_length) { signed int exponents[39], exp; signed int const *expptr; struct mad_bitptr peek; signed int bits_left, cachesz; register mad_fixed_t *xrptr; mad_fixed_t const *sfbound; register unsigned long bitcache; bits_left = (signed) channel->part2_3_length - (signed) part2_length; if (bits_left < 0) return MAD_ERROR_BADPART3LEN; III_exponents(channel, sfbwidth, exponents); peek = *ptr; mad_bit_skip(ptr, bits_left); /* align bit reads to byte boundaries */ cachesz = mad_bit_bitsleft(&peek); cachesz += ((32 - 1 - 24) + (24 - cachesz)) & ~7; bitcache = mad_bit_read(&peek, cachesz); bits_left -= cachesz; xrptr = &xr[0]; /* big_values */ { unsigned int region, rcount; struct hufftable const *entry; union huffpair const *table; unsigned int linbits, startbits, big_values, reqhits; mad_fixed_t reqcache[16]; sfbound = xrptr + *sfbwidth++; rcount = channel->region0_count + 1; entry = &mad_huff_pair_table[channel->table_select[region = 0]]; table = entry->table; linbits = entry->linbits; startbits = entry->startbits; if (table == 0) return MAD_ERROR_BADHUFFTABLE; expptr = &exponents[0]; exp = *expptr++; reqhits = 0; big_values = channel->big_values; while (big_values-- && cachesz + bits_left > 0) { union huffpair const *pair; unsigned int clumpsz, value; register mad_fixed_t requantized; if (xrptr == sfbound) { sfbound += *sfbwidth++; /* change table if region boundary */ if (--rcount == 0) { if (region == 0) rcount = channel->region1_count + 1; else rcount = 0; /* all remaining */ entry = &mad_huff_pair_table[channel->table_select[++region]]; table = entry->table; linbits = entry->linbits; startbits = entry->startbits; if (table == 0) return MAD_ERROR_BADHUFFTABLE; } if (exp != *expptr) { exp = *expptr; reqhits = 0; } ++expptr; } if (cachesz < 21) { unsigned int bits; bits = ((32 - 1 - 21) + (21 - cachesz)) & ~7; bitcache = (bitcache << bits) | mad_bit_read(&peek, bits); cachesz += bits; bits_left -= bits; } /* hcod (0..19) */ clumpsz = startbits; pair = &table[MASK(bitcache, cachesz, clumpsz)]; while (!pair->final) { cachesz -= clumpsz; clumpsz = pair->ptr.bits; pair = &table[pair->ptr.offset + MASK(bitcache, cachesz, clumpsz)]; } cachesz -= pair->value.hlen; if (linbits) { /* x (0..14) */ value = pair->value.x; switch (value) { case 0: xrptr[0] = 0; break; case 15: if (cachesz < linbits + 2) { bitcache = (bitcache << 16) | mad_bit_read(&peek, 16); cachesz += 16; bits_left -= 16; } value += MASK(bitcache, cachesz, linbits); cachesz -= linbits; requantized = III_requantize(value, exp); goto x_final; default: if (reqhits & (1 << value)) requantized = reqcache[value]; else { reqhits |= (1 << value); requantized = reqcache[value] = III_requantize(value, exp); } x_final: xrptr[0] = MASK1BIT(bitcache, cachesz--) ? -requantized : requantized; } /* y (0..14) */ value = pair->value.y; switch (value) { case 0: xrptr[1] = 0; break; case 15: if (cachesz < linbits + 1) { bitcache = (bitcache << 16) | mad_bit_read(&peek, 16); cachesz += 16; bits_left -= 16; } value += MASK(bitcache, cachesz, linbits); cachesz -= linbits; requantized = III_requantize(value, exp); goto y_final; default: if (reqhits & (1 << value)) requantized = reqcache[value]; else { reqhits |= (1 << value); requantized = reqcache[value] = III_requantize(value, exp); } y_final: xrptr[1] = MASK1BIT(bitcache, cachesz--) ? -requantized : requantized; } } else { /* x (0..1) */ value = pair->value.x; if (value == 0) xrptr[0] = 0; else { if (reqhits & (1 << value)) requantized = reqcache[value]; else { reqhits |= (1 << value); requantized = reqcache[value] = III_requantize(value, exp); } xrptr[0] = MASK1BIT(bitcache, cachesz--) ? -requantized : requantized; } /* y (0..1) */ value = pair->value.y; if (value == 0) xrptr[1] = 0; else { if (reqhits & (1 << value)) requantized = reqcache[value]; else { reqhits |= (1 << value); requantized = reqcache[value] = III_requantize(value, exp); } xrptr[1] = MASK1BIT(bitcache, cachesz--) ? -requantized : requantized; } } xrptr += 2; } } if (cachesz + bits_left < 0) return MAD_ERROR_BADHUFFDATA; /* big_values overrun */ /* count1 */ { union huffquad const *table; register mad_fixed_t requantized; table = mad_huff_quad_table[channel->flags & count1table_select]; requantized = III_requantize(1, exp); while (cachesz + bits_left > 0 && xrptr <= &xr[572]) { union huffquad const *quad; /* hcod (1..6) */ if (cachesz < 10) { bitcache = (bitcache << 16) | mad_bit_read(&peek, 16); cachesz += 16; bits_left -= 16; } quad = &table[MASK(bitcache, cachesz, 4)]; /* quad tables guaranteed to have at most one extra lookup */ if (!quad->final) { cachesz -= 4; quad = &table[quad->ptr.offset + MASK(bitcache, cachesz, quad->ptr.bits)]; } cachesz -= quad->value.hlen; if (xrptr == sfbound) { sfbound += *sfbwidth++; if (exp != *expptr) { exp = *expptr; requantized = III_requantize(1, exp); } ++expptr; } /* v (0..1) */ xrptr[0] = quad->value.v ? (MASK1BIT(bitcache, cachesz--) ? -requantized : requantized) : 0; /* w (0..1) */ xrptr[1] = quad->value.w ? (MASK1BIT(bitcache, cachesz--) ? -requantized : requantized) : 0; xrptr += 2; if (xrptr == sfbound) { sfbound += *sfbwidth++; if (exp != *expptr) { exp = *expptr; requantized = III_requantize(1, exp); } ++expptr; } /* x (0..1) */ xrptr[0] = quad->value.x ? (MASK1BIT(bitcache, cachesz--) ? -requantized : requantized) : 0; /* y (0..1) */ xrptr[1] = quad->value.y ? (MASK1BIT(bitcache, cachesz--) ? -requantized : requantized) : 0; xrptr += 2; } if (cachesz + bits_left < 0) { # if 0 && defined(DEBUG) fprintf(stderr, "huffman count1 overrun (%d bits)\n", -(cachesz + bits_left)); # endif /* technically the bitstream is misformatted, but apparently some encoders are just a bit sloppy with stuffing bits */ xrptr -= 4; } } assert(-bits_left <= MAD_BUFFER_GUARD * CHAR_BIT); # if 0 && defined(DEBUG) if (bits_left < 0) fprintf(stderr, "read %d bits too many\n", -bits_left); else if (cachesz + bits_left > 0) fprintf(stderr, "%d stuffing bits\n", cachesz + bits_left); # endif /* rzero */ while (xrptr < &xr[576]) { xrptr[0] = 0; xrptr[1] = 0; xrptr += 2; } return MAD_ERROR_NONE; } # undef MASK # undef MASK1BIT /* * NAME: III_reorder() * DESCRIPTION: reorder frequency lines of a short block into subband order */ static void III_reorder(mad_fixed_t xr[576], struct channel const *channel, unsigned char const sfbwidth[39]) { mad_fixed_t tmp[32][3][6]; unsigned int sb, l, f, w, sbw[3], sw[3]; /* this is probably wrong for 8000 Hz mixed blocks */ sb = 0; if (channel->flags & mixed_block_flag) { sb = 2; l = 0; while (l < 36) l += *sfbwidth++; } for (w = 0; w < 3; ++w) { sbw[w] = sb; sw[w] = 0; } f = *sfbwidth++; w = 0; for (l = 18 * sb; l < 576; ++l) { if (f-- == 0) { f = *sfbwidth++ - 1; w = (w + 1) % 3; } tmp[sbw[w]][w][sw[w]++] = xr[l]; if (sw[w] == 6) { sw[w] = 0; ++sbw[w]; } } memcpy(&xr[18 * sb], &tmp[sb], (576 - 18 * sb) * sizeof(mad_fixed_t)); } /* * NAME: III_stereo() * DESCRIPTION: perform joint stereo processing on a granule */ static enum mad_error III_stereo(mad_fixed_t xr[2][576], struct granule const *granule, struct mad_header *header, unsigned char const *sfbwidth) { short modes[39]; unsigned int sfbi, l, n, i; if (granule->ch[0].block_type != granule->ch[1].block_type || (granule->ch[0].flags & mixed_block_flag) != (granule->ch[1].flags & mixed_block_flag)) return MAD_ERROR_BADSTEREO; for (i = 0; i < 39; ++i) modes[i] = header->mode_extension; /* intensity stereo */ if (header->mode_extension & I_STEREO) { struct channel const *right_ch = &granule->ch[1]; mad_fixed_t const *right_xr = xr[1]; unsigned int is_pos; header->flags |= MAD_FLAG_I_STEREO; /* first determine which scalefactor bands are to be processed */ if (right_ch->block_type == 2) { unsigned int lower, start, max, bound[3], w; lower = start = max = bound[0] = bound[1] = bound[2] = 0; sfbi = l = 0; if (right_ch->flags & mixed_block_flag) { while (l < 36) { n = sfbwidth[sfbi++]; for (i = 0; i < n; ++i) { if (right_xr[i]) { lower = sfbi; break; } } right_xr += n; l += n; } start = sfbi; } w = 0; while (l < 576) { n = sfbwidth[sfbi++]; for (i = 0; i < n; ++i) { if (right_xr[i]) { max = bound[w] = sfbi; break; } } right_xr += n; l += n; w = (w + 1) % 3; } if (max) lower = start; /* long blocks */ for (i = 0; i < lower; ++i) modes[i] = header->mode_extension & ~I_STEREO; /* short blocks */ w = 0; for (i = start; i < max; ++i) { if (i < bound[w]) modes[i] = header->mode_extension & ~I_STEREO; w = (w + 1) % 3; } } else { /* right_ch->block_type != 2 */ unsigned int bound; bound = 0; for (sfbi = l = 0; l < 576; l += n) { n = sfbwidth[sfbi++]; for (i = 0; i < n; ++i) { if (right_xr[i]) { bound = sfbi; break; } } right_xr += n; } for (i = 0; i < bound; ++i) modes[i] = header->mode_extension & ~I_STEREO; } /* now do the actual processing */ if (header->flags & MAD_FLAG_LSF_EXT) { unsigned char const *illegal_pos = granule[1].ch[1].scalefac; mad_fixed_t const *lsf_scale; /* intensity_scale */ lsf_scale = is_lsf_table[right_ch->scalefac_compress & 0x1]; for (sfbi = l = 0; l < 576; ++sfbi, l += n) { n = sfbwidth[sfbi]; if (!(modes[sfbi] & I_STEREO)) continue; if (illegal_pos[sfbi]) { modes[sfbi] &= ~I_STEREO; continue; } is_pos = right_ch->scalefac[sfbi]; for (i = 0; i < n; ++i) { register mad_fixed_t left; left = xr[0][l + i]; if (is_pos == 0) xr[1][l + i] = left; else { register mad_fixed_t opposite; opposite = mad_f_mul(left, lsf_scale[(is_pos - 1) / 2]); if (is_pos & 1) { xr[0][l + i] = opposite; xr[1][l + i] = left; } else xr[1][l + i] = opposite; } } } } else { /* !(header->flags & MAD_FLAG_LSF_EXT) */ for (sfbi = l = 0; l < 576; ++sfbi, l += n) { n = sfbwidth[sfbi]; if (!(modes[sfbi] & I_STEREO)) continue; is_pos = right_ch->scalefac[sfbi]; if (is_pos >= 7) { /* illegal intensity position */ modes[sfbi] &= ~I_STEREO; continue; } for (i = 0; i < n; ++i) { register mad_fixed_t left; left = xr[0][l + i]; xr[0][l + i] = mad_f_mul(left, is_table[ is_pos]); xr[1][l + i] = mad_f_mul(left, is_table[6 - is_pos]); } } } } /* middle/side stereo */ if (header->mode_extension & MS_STEREO) { register mad_fixed_t invsqrt2; header->flags |= MAD_FLAG_MS_STEREO; invsqrt2 = root_table[3 + -2]; for (sfbi = l = 0; l < 576; ++sfbi, l += n) { n = sfbwidth[sfbi]; if (modes[sfbi] != MS_STEREO) continue; for (i = 0; i < n; ++i) { register mad_fixed_t m, s; m = xr[0][l + i]; s = xr[1][l + i]; xr[0][l + i] = mad_f_mul(m + s, invsqrt2); /* l = (m + s) / sqrt(2) */ xr[1][l + i] = mad_f_mul(m - s, invsqrt2); /* r = (m - s) / sqrt(2) */ } } } return MAD_ERROR_NONE; } /* * NAME: III_aliasreduce() * DESCRIPTION: perform frequency line alias reduction */ static void III_aliasreduce(mad_fixed_t xr[576], int lines) { mad_fixed_t const *bound; int i; bound = &xr[lines]; for (xr += 18; xr < bound; xr += 18) { for (i = 0; i < 8; ++i) { register mad_fixed_t a, b; register mad_fixed64hi_t hi; register mad_fixed64lo_t lo; a = xr[-1 - i]; b = xr[ i]; # if defined(ASO_ZEROCHECK) if (a | b) { # endif MAD_F_ML0(hi, lo, a, cs[i]); MAD_F_MLA(hi, lo, -b, ca[i]); xr[-1 - i] = MAD_F_MLZ(hi, lo); MAD_F_ML0(hi, lo, b, cs[i]); MAD_F_MLA(hi, lo, a, ca[i]); xr[ i] = MAD_F_MLZ(hi, lo); # if defined(ASO_ZEROCHECK) } # endif } } } # if defined(ASO_IMDCT) void III_imdct_l(mad_fixed_t const [18], mad_fixed_t [36], unsigned int); # else # if 1 static void fastsdct(mad_fixed_t const x[9], mad_fixed_t y[18]) { mad_fixed_t a0, a1, a2, a3, a4, a5, a6, a7, a8, a9, a10, a11, a12; mad_fixed_t a13, a14, a15, a16, a17, a18, a19, a20, a21, a22, a23, a24, a25; mad_fixed_t m0, m1, m2, m3, m4, m5, m6, m7; enum { c0 = MAD_F(0x1f838b8d), /* 2 * cos( 1 * PI / 18) */ c1 = MAD_F(0x1bb67ae8), /* 2 * cos( 3 * PI / 18) */ c2 = MAD_F(0x18836fa3), /* 2 * cos( 4 * PI / 18) */ c3 = MAD_F(0x1491b752), /* 2 * cos( 5 * PI / 18) */ c4 = MAD_F(0x0af1d43a), /* 2 * cos( 7 * PI / 18) */ c5 = MAD_F(0x058e86a0), /* 2 * cos( 8 * PI / 18) */ c6 = -MAD_F(0x1e11f642) /* 2 * cos(16 * PI / 18) */ }; a0 = x[3] + x[5]; a1 = x[3] - x[5]; a2 = x[6] + x[2]; a3 = x[6] - x[2]; a4 = x[1] + x[7]; a5 = x[1] - x[7]; a6 = x[8] + x[0]; a7 = x[8] - x[0]; a8 = a0 + a2; a9 = a0 - a2; a10 = a0 - a6; a11 = a2 - a6; a12 = a8 + a6; a13 = a1 - a3; a14 = a13 + a7; a15 = a3 + a7; a16 = a1 - a7; a17 = a1 + a3; m0 = mad_f_mul(a17, -c3); m1 = mad_f_mul(a16, -c0); m2 = mad_f_mul(a15, -c4); m3 = mad_f_mul(a14, -c1); m4 = mad_f_mul(a5, -c1); m5 = mad_f_mul(a11, -c6); m6 = mad_f_mul(a10, -c5); m7 = mad_f_mul(a9, -c2); a18 = x[4] + a4; a19 = 2 * x[4] - a4; a20 = a19 + m5; a21 = a19 - m5; a22 = a19 + m6; a23 = m4 + m2; a24 = m4 - m2; a25 = m4 + m1; /* output to every other slot for convenience */ y[ 0] = a18 + a12; y[ 2] = m0 - a25; y[ 4] = m7 - a20; y[ 6] = m3; y[ 8] = a21 - m6; y[10] = a24 - m1; y[12] = a12 - 2 * a18; y[14] = a23 + m0; y[16] = a22 + m7; } static inline void sdctII(mad_fixed_t const x[18], mad_fixed_t X[18]) { mad_fixed_t tmp[9]; int i; /* scale[i] = 2 * cos(PI * (2 * i + 1) / (2 * 18)) */ static mad_fixed_t const scale[9] = { MAD_F(0x1fe0d3b4), MAD_F(0x1ee8dd47), MAD_F(0x1d007930), MAD_F(0x1a367e59), MAD_F(0x16a09e66), MAD_F(0x125abcf8), MAD_F(0x0d8616bc), MAD_F(0x08483ee1), MAD_F(0x02c9fad7) }; /* divide the 18-point SDCT-II into two 9-point SDCT-IIs */ /* even input butterfly */ for (i = 0; i < 9; i += 3) { tmp[i + 0] = x[i + 0] + x[18 - (i + 0) - 1]; tmp[i + 1] = x[i + 1] + x[18 - (i + 1) - 1]; tmp[i + 2] = x[i + 2] + x[18 - (i + 2) - 1]; } fastsdct(tmp, &X[0]); /* odd input butterfly and scaling */ for (i = 0; i < 9; i += 3) { tmp[i + 0] = mad_f_mul(x[i + 0] - x[18 - (i + 0) - 1], scale[i + 0]); tmp[i + 1] = mad_f_mul(x[i + 1] - x[18 - (i + 1) - 1], scale[i + 1]); tmp[i + 2] = mad_f_mul(x[i + 2] - x[18 - (i + 2) - 1], scale[i + 2]); } fastsdct(tmp, &X[1]); /* output accumulation */ for (i = 3; i < 18; i += 8) { X[i + 0] -= X[(i + 0) - 2]; X[i + 2] -= X[(i + 2) - 2]; X[i + 4] -= X[(i + 4) - 2]; X[i + 6] -= X[(i + 6) - 2]; } } static inline void dctIV(mad_fixed_t const y[18], mad_fixed_t X[18]) { mad_fixed_t tmp[18]; int i; /* scale[i] = 2 * cos(PI * (2 * i + 1) / (4 * 18)) */ static mad_fixed_t const scale[18] = { MAD_F(0x1ff833fa), MAD_F(0x1fb9ea93), MAD_F(0x1f3dd120), MAD_F(0x1e84d969), MAD_F(0x1d906bcf), MAD_F(0x1c62648b), MAD_F(0x1afd100f), MAD_F(0x1963268b), MAD_F(0x1797c6a4), MAD_F(0x159e6f5b), MAD_F(0x137af940), MAD_F(0x11318ef3), MAD_F(0x0ec6a507), MAD_F(0x0c3ef153), MAD_F(0x099f61c5), MAD_F(0x06ed12c5), MAD_F(0x042d4544), MAD_F(0x0165547c) }; /* scaling */ for (i = 0; i < 18; i += 3) { tmp[i + 0] = mad_f_mul(y[i + 0], scale[i + 0]); tmp[i + 1] = mad_f_mul(y[i + 1], scale[i + 1]); tmp[i + 2] = mad_f_mul(y[i + 2], scale[i + 2]); } /* SDCT-II */ sdctII(tmp, X); /* scale reduction and output accumulation */ X[0] /= 2; for (i = 1; i < 17; i += 4) { X[i + 0] = X[i + 0] / 2 - X[(i + 0) - 1]; X[i + 1] = X[i + 1] / 2 - X[(i + 1) - 1]; X[i + 2] = X[i + 2] / 2 - X[(i + 2) - 1]; X[i + 3] = X[i + 3] / 2 - X[(i + 3) - 1]; } X[17] = X[17] / 2 - X[16]; } /* * NAME: imdct36 * DESCRIPTION: perform X[18]->x[36] IMDCT using Szu-Wei Lee's fast algorithm */ static inline void imdct36(mad_fixed_t const x[18], mad_fixed_t y[36]) { mad_fixed_t tmp[18]; int i; /* DCT-IV */ dctIV(x, tmp); /* convert 18-point DCT-IV to 36-point IMDCT */ for (i = 0; i < 9; i += 3) { y[i + 0] = tmp[9 + (i + 0)]; y[i + 1] = tmp[9 + (i + 1)]; y[i + 2] = tmp[9 + (i + 2)]; } for (i = 9; i < 27; i += 3) { y[i + 0] = -tmp[36 - (9 + (i + 0)) - 1]; y[i + 1] = -tmp[36 - (9 + (i + 1)) - 1]; y[i + 2] = -tmp[36 - (9 + (i + 2)) - 1]; } for (i = 27; i < 36; i += 3) { y[i + 0] = -tmp[(i + 0) - 27]; y[i + 1] = -tmp[(i + 1) - 27]; y[i + 2] = -tmp[(i + 2) - 27]; } } # else /* * NAME: imdct36 * DESCRIPTION: perform X[18]->x[36] IMDCT */ static inline void imdct36(mad_fixed_t const X[18], mad_fixed_t x[36]) { mad_fixed_t t0, t1, t2, t3, t4, t5, t6, t7; mad_fixed_t t8, t9, t10, t11, t12, t13, t14, t15; register mad_fixed64hi_t hi; register mad_fixed64lo_t lo; MAD_F_ML0(hi, lo, X[4], MAD_F(0x0ec835e8)); MAD_F_MLA(hi, lo, X[13], MAD_F(0x061f78aa)); t6 = MAD_F_MLZ(hi, lo); MAD_F_MLA(hi, lo, (t14 = X[1] - X[10]), -MAD_F(0x061f78aa)); MAD_F_MLA(hi, lo, (t15 = X[7] + X[16]), -MAD_F(0x0ec835e8)); t0 = MAD_F_MLZ(hi, lo); MAD_F_MLA(hi, lo, (t8 = X[0] - X[11] - X[12]), MAD_F(0x0216a2a2)); MAD_F_MLA(hi, lo, (t9 = X[2] - X[9] - X[14]), MAD_F(0x09bd7ca0)); MAD_F_MLA(hi, lo, (t10 = X[3] - X[8] - X[15]), -MAD_F(0x0cb19346)); MAD_F_MLA(hi, lo, (t11 = X[5] - X[6] - X[17]), -MAD_F(0x0fdcf549)); x[7] = MAD_F_MLZ(hi, lo); x[10] = -x[7]; MAD_F_ML0(hi, lo, t8, -MAD_F(0x0cb19346)); MAD_F_MLA(hi, lo, t9, MAD_F(0x0fdcf549)); MAD_F_MLA(hi, lo, t10, MAD_F(0x0216a2a2)); MAD_F_MLA(hi, lo, t11, -MAD_F(0x09bd7ca0)); x[19] = x[34] = MAD_F_MLZ(hi, lo) - t0; t12 = X[0] - X[3] + X[8] - X[11] - X[12] + X[15]; t13 = X[2] + X[5] - X[6] - X[9] - X[14] - X[17]; MAD_F_ML0(hi, lo, t12, -MAD_F(0x0ec835e8)); MAD_F_MLA(hi, lo, t13, MAD_F(0x061f78aa)); x[22] = x[31] = MAD_F_MLZ(hi, lo) + t0; MAD_F_ML0(hi, lo, X[1], -MAD_F(0x09bd7ca0)); MAD_F_MLA(hi, lo, X[7], MAD_F(0x0216a2a2)); MAD_F_MLA(hi, lo, X[10], -MAD_F(0x0fdcf549)); MAD_F_MLA(hi, lo, X[16], MAD_F(0x0cb19346)); t1 = MAD_F_MLZ(hi, lo) + t6; MAD_F_ML0(hi, lo, X[0], MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[3], -MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[5], -MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[6], MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[8], -MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[9], MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[11], MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[14], MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[15], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x0f9ee890)); x[6] = MAD_F_MLZ(hi, lo) + t1; x[11] = -x[6]; MAD_F_ML0(hi, lo, X[0], -MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[2], -MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[3], MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[5], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[6], MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[8], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[9], -MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[14], MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[15], MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[17], MAD_F(0x04cfb0e2)); x[23] = x[30] = MAD_F_MLZ(hi, lo) + t1; MAD_F_ML0(hi, lo, X[0], -MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[3], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[5], MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[6], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[8], -MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[9], -MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[11], MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[14], MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[15], MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x0acf37ad)); x[18] = x[35] = MAD_F_MLZ(hi, lo) - t1; MAD_F_ML0(hi, lo, X[4], MAD_F(0x061f78aa)); MAD_F_MLA(hi, lo, X[13], -MAD_F(0x0ec835e8)); t7 = MAD_F_MLZ(hi, lo); MAD_F_MLA(hi, lo, X[1], -MAD_F(0x0cb19346)); MAD_F_MLA(hi, lo, X[7], MAD_F(0x0fdcf549)); MAD_F_MLA(hi, lo, X[10], MAD_F(0x0216a2a2)); MAD_F_MLA(hi, lo, X[16], -MAD_F(0x09bd7ca0)); t2 = MAD_F_MLZ(hi, lo); MAD_F_MLA(hi, lo, X[0], MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[3], -MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[5], MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[6], -MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[8], -MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[9], MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[12], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[14], MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[15], MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[17], MAD_F(0x0f426cb5)); x[5] = MAD_F_MLZ(hi, lo); x[12] = -x[5]; MAD_F_ML0(hi, lo, X[0], MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[2], -MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[3], MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[5], -MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[6], -MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[8], MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[9], -MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[11], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[14], MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[15], MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x0bcbe352)); x[0] = MAD_F_MLZ(hi, lo) + t2; x[17] = -x[0]; MAD_F_ML0(hi, lo, X[0], -MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[2], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[3], -MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[5], MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[6], MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[8], MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[9], MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[14], -MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[15], -MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x03768962)); x[24] = x[29] = MAD_F_MLZ(hi, lo) + t2; MAD_F_ML0(hi, lo, X[1], -MAD_F(0x0216a2a2)); MAD_F_MLA(hi, lo, X[7], -MAD_F(0x09bd7ca0)); MAD_F_MLA(hi, lo, X[10], MAD_F(0x0cb19346)); MAD_F_MLA(hi, lo, X[16], MAD_F(0x0fdcf549)); t3 = MAD_F_MLZ(hi, lo) + t7; MAD_F_ML0(hi, lo, X[0], MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[3], -MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[5], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[6], MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[8], MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[9], -MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[12], MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[14], MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[15], -MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x0ffc19fd)); x[8] = MAD_F_MLZ(hi, lo) + t3; x[9] = -x[8]; MAD_F_ML0(hi, lo, X[0], -MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[3], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[5], -MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[6], -MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[8], MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[9], MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[14], -MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[15], MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[17], MAD_F(0x07635284)); x[21] = x[32] = MAD_F_MLZ(hi, lo) + t3; MAD_F_ML0(hi, lo, X[0], -MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[3], MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[5], -MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[6], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[8], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[9], MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[12], MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[14], MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[15], -MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x0898c779)); x[20] = x[33] = MAD_F_MLZ(hi, lo) - t3; MAD_F_ML0(hi, lo, t14, -MAD_F(0x0ec835e8)); MAD_F_MLA(hi, lo, t15, MAD_F(0x061f78aa)); t4 = MAD_F_MLZ(hi, lo) - t7; MAD_F_ML0(hi, lo, t12, MAD_F(0x061f78aa)); MAD_F_MLA(hi, lo, t13, MAD_F(0x0ec835e8)); x[4] = MAD_F_MLZ(hi, lo) + t4; x[13] = -x[4]; MAD_F_ML0(hi, lo, t8, MAD_F(0x09bd7ca0)); MAD_F_MLA(hi, lo, t9, -MAD_F(0x0216a2a2)); MAD_F_MLA(hi, lo, t10, MAD_F(0x0fdcf549)); MAD_F_MLA(hi, lo, t11, -MAD_F(0x0cb19346)); x[1] = MAD_F_MLZ(hi, lo) + t4; x[16] = -x[1]; MAD_F_ML0(hi, lo, t8, -MAD_F(0x0fdcf549)); MAD_F_MLA(hi, lo, t9, -MAD_F(0x0cb19346)); MAD_F_MLA(hi, lo, t10, -MAD_F(0x09bd7ca0)); MAD_F_MLA(hi, lo, t11, -MAD_F(0x0216a2a2)); x[25] = x[28] = MAD_F_MLZ(hi, lo) + t4; MAD_F_ML0(hi, lo, X[1], -MAD_F(0x0fdcf549)); MAD_F_MLA(hi, lo, X[7], -MAD_F(0x0cb19346)); MAD_F_MLA(hi, lo, X[10], -MAD_F(0x09bd7ca0)); MAD_F_MLA(hi, lo, X[16], -MAD_F(0x0216a2a2)); t5 = MAD_F_MLZ(hi, lo) - t6; MAD_F_ML0(hi, lo, X[0], MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[3], MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[5], MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[6], MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[8], -MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[9], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[12], MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[14], -MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[15], MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x0d7e8807)); x[2] = MAD_F_MLZ(hi, lo) + t5; x[15] = -x[2]; MAD_F_ML0(hi, lo, X[0], MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[2], MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[3], MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[5], MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[6], -MAD_F(0x00b2aa3e)); MAD_F_MLA(hi, lo, X[8], MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[9], -MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[11], MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[14], MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[15], -MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[17], MAD_F(0x0e313245)); x[3] = MAD_F_MLZ(hi, lo) + t5; x[14] = -x[3]; MAD_F_ML0(hi, lo, X[0], -MAD_F(0x0ffc19fd)); MAD_F_MLA(hi, lo, X[2], -MAD_F(0x0f9ee890)); MAD_F_MLA(hi, lo, X[3], -MAD_F(0x0f426cb5)); MAD_F_MLA(hi, lo, X[5], -MAD_F(0x0e313245)); MAD_F_MLA(hi, lo, X[6], -MAD_F(0x0d7e8807)); MAD_F_MLA(hi, lo, X[8], -MAD_F(0x0bcbe352)); MAD_F_MLA(hi, lo, X[9], -MAD_F(0x0acf37ad)); MAD_F_MLA(hi, lo, X[11], -MAD_F(0x0898c779)); MAD_F_MLA(hi, lo, X[12], -MAD_F(0x07635284)); MAD_F_MLA(hi, lo, X[14], -MAD_F(0x04cfb0e2)); MAD_F_MLA(hi, lo, X[15], -MAD_F(0x03768962)); MAD_F_MLA(hi, lo, X[17], -MAD_F(0x00b2aa3e)); x[26] = x[27] = MAD_F_MLZ(hi, lo) + t5; } # endif /* * NAME: III_imdct_l() * DESCRIPTION: perform IMDCT and windowing for long blocks */ static void III_imdct_l(mad_fixed_t const X[18], mad_fixed_t z[36], unsigned int block_type) { unsigned int i; /* IMDCT */ imdct36(X, z); /* windowing */ switch (block_type) { case 0: /* normal window */ # if defined(ASO_INTERLEAVE1) { register mad_fixed_t tmp1, tmp2; tmp1 = window_l[0]; tmp2 = window_l[1]; for (i = 0; i < 34; i += 2) { z[i + 0] = mad_f_mul(z[i + 0], tmp1); tmp1 = window_l[i + 2]; z[i + 1] = mad_f_mul(z[i + 1], tmp2); tmp2 = window_l[i + 3]; } z[34] = mad_f_mul(z[34], tmp1); z[35] = mad_f_mul(z[35], tmp2); } # elif defined(ASO_INTERLEAVE2) { register mad_fixed_t tmp1, tmp2; tmp1 = z[0]; tmp2 = window_l[0]; for (i = 0; i < 35; ++i) { z[i] = mad_f_mul(tmp1, tmp2); tmp1 = z[i + 1]; tmp2 = window_l[i + 1]; } z[35] = mad_f_mul(tmp1, tmp2); } # elif 1 for (i = 0; i < 36; i += 4) { z[i + 0] = mad_f_mul(z[i + 0], window_l[i + 0]); z[i + 1] = mad_f_mul(z[i + 1], window_l[i + 1]); z[i + 2] = mad_f_mul(z[i + 2], window_l[i + 2]); z[i + 3] = mad_f_mul(z[i + 3], window_l[i + 3]); } # else for (i = 0; i < 36; ++i) z[i] = mad_f_mul(z[i], window_l[i]); # endif break; case 1: /* start block */ for (i = 0; i < 18; i += 3) { z[i + 0] = mad_f_mul(z[i + 0], window_l[i + 0]); z[i + 1] = mad_f_mul(z[i + 1], window_l[i + 1]); z[i + 2] = mad_f_mul(z[i + 2], window_l[i + 2]); } /* (i = 18; i < 24; ++i) z[i] unchanged */ for (i = 24; i < 30; ++i) z[i] = mad_f_mul(z[i], window_s[i - 18]); for (i = 30; i < 36; ++i) z[i] = 0; break; case 3: /* stop block */ for (i = 0; i < 6; ++i) z[i] = 0; for (i = 6; i < 12; ++i) z[i] = mad_f_mul(z[i], window_s[i - 6]); /* (i = 12; i < 18; ++i) z[i] unchanged */ for (i = 18; i < 36; i += 3) { z[i + 0] = mad_f_mul(z[i + 0], window_l[i + 0]); z[i + 1] = mad_f_mul(z[i + 1], window_l[i + 1]); z[i + 2] = mad_f_mul(z[i + 2], window_l[i + 2]); } break; } } # endif /* ASO_IMDCT */ /* * NAME: III_imdct_s() * DESCRIPTION: perform IMDCT and windowing for short blocks */ static void III_imdct_s(mad_fixed_t const X[18], mad_fixed_t z[36]) { mad_fixed_t y[36], *yptr; mad_fixed_t const *wptr; int w, i; register mad_fixed64hi_t hi; register mad_fixed64lo_t lo; /* IMDCT */ yptr = &y[0]; for (w = 0; w < 3; ++w) { register mad_fixed_t const (*s)[6]; s = imdct_s; for (i = 0; i < 3; ++i) { MAD_F_ML0(hi, lo, X[0], (*s)[0]); MAD_F_MLA(hi, lo, X[1], (*s)[1]); MAD_F_MLA(hi, lo, X[2], (*s)[2]); MAD_F_MLA(hi, lo, X[3], (*s)[3]); MAD_F_MLA(hi, lo, X[4], (*s)[4]); MAD_F_MLA(hi, lo, X[5], (*s)[5]); yptr[i + 0] = MAD_F_MLZ(hi, lo); yptr[5 - i] = -yptr[i + 0]; ++s; MAD_F_ML0(hi, lo, X[0], (*s)[0]); MAD_F_MLA(hi, lo, X[1], (*s)[1]); MAD_F_MLA(hi, lo, X[2], (*s)[2]); MAD_F_MLA(hi, lo, X[3], (*s)[3]); MAD_F_MLA(hi, lo, X[4], (*s)[4]); MAD_F_MLA(hi, lo, X[5], (*s)[5]); yptr[ i + 6] = MAD_F_MLZ(hi, lo); yptr[11 - i] = yptr[i + 6]; ++s; } yptr += 12; X += 6; } /* windowing, overlapping and concatenation */ yptr = &y[0]; wptr = &window_s[0]; for (i = 0; i < 6; ++i) { z[i + 0] = 0; z[i + 6] = mad_f_mul(yptr[ 0 + 0], wptr[0]); MAD_F_ML0(hi, lo, yptr[ 0 + 6], wptr[6]); MAD_F_MLA(hi, lo, yptr[12 + 0], wptr[0]); z[i + 12] = MAD_F_MLZ(hi, lo); MAD_F_ML0(hi, lo, yptr[12 + 6], wptr[6]); MAD_F_MLA(hi, lo, yptr[24 + 0], wptr[0]); z[i + 18] = MAD_F_MLZ(hi, lo); z[i + 24] = mad_f_mul(yptr[24 + 6], wptr[6]); z[i + 30] = 0; ++yptr; ++wptr; } } /* * NAME: III_overlap() * DESCRIPTION: perform overlap-add of windowed IMDCT outputs */ static void III_overlap(mad_fixed_t const output[36], mad_fixed_t overlap[18], mad_fixed_t sample[18][32], unsigned int sb) { unsigned int i; # if defined(ASO_INTERLEAVE2) { register mad_fixed_t tmp1, tmp2; tmp1 = overlap[0]; tmp2 = overlap[1]; for (i = 0; i < 16; i += 2) { sample[i + 0][sb] = output[i + 0 + 0] + tmp1; overlap[i + 0] = output[i + 0 + 18]; tmp1 = overlap[i + 2]; sample[i + 1][sb] = output[i + 1 + 0] + tmp2; overlap[i + 1] = output[i + 1 + 18]; tmp2 = overlap[i + 3]; } sample[16][sb] = output[16 + 0] + tmp1; overlap[16] = output[16 + 18]; sample[17][sb] = output[17 + 0] + tmp2; overlap[17] = output[17 + 18]; } # elif 0 for (i = 0; i < 18; i += 2) { sample[i + 0][sb] = output[i + 0 + 0] + overlap[i + 0]; overlap[i + 0] = output[i + 0 + 18]; sample[i + 1][sb] = output[i + 1 + 0] + overlap[i + 1]; overlap[i + 1] = output[i + 1 + 18]; } # else for (i = 0; i < 18; ++i) { sample[i][sb] = output[i + 0] + overlap[i]; overlap[i] = output[i + 18]; } # endif } /* * NAME: III_overlap_z() * DESCRIPTION: perform "overlap-add" of zero IMDCT outputs */ static inline void III_overlap_z(mad_fixed_t overlap[18], mad_fixed_t sample[18][32], unsigned int sb) { unsigned int i; # if defined(ASO_INTERLEAVE2) { register mad_fixed_t tmp1, tmp2; tmp1 = overlap[0]; tmp2 = overlap[1]; for (i = 0; i < 16; i += 2) { sample[i + 0][sb] = tmp1; overlap[i + 0] = 0; tmp1 = overlap[i + 2]; sample[i + 1][sb] = tmp2; overlap[i + 1] = 0; tmp2 = overlap[i + 3]; } sample[16][sb] = tmp1; overlap[16] = 0; sample[17][sb] = tmp2; overlap[17] = 0; } # else for (i = 0; i < 18; ++i) { sample[i][sb] = overlap[i]; overlap[i] = 0; } # endif } /* * NAME: III_freqinver() * DESCRIPTION: perform subband frequency inversion for odd sample lines */ static void III_freqinver(mad_fixed_t sample[18][32], unsigned int sb) { unsigned int i; # if 1 || defined(ASO_INTERLEAVE1) || defined(ASO_INTERLEAVE2) { register mad_fixed_t tmp1, tmp2; tmp1 = sample[1][sb]; tmp2 = sample[3][sb]; for (i = 1; i < 13; i += 4) { sample[i + 0][sb] = -tmp1; tmp1 = sample[i + 4][sb]; sample[i + 2][sb] = -tmp2; tmp2 = sample[i + 6][sb]; } sample[13][sb] = -tmp1; tmp1 = sample[17][sb]; sample[15][sb] = -tmp2; sample[17][sb] = -tmp1; } # else for (i = 1; i < 18; i += 2) sample[i][sb] = -sample[i][sb]; # endif } /* * NAME: III_decode() * DESCRIPTION: decode frame main_data */ static enum mad_error III_decode(struct mad_bitptr *ptr, struct mad_frame *frame, struct sideinfo *si, unsigned int nch) { struct mad_header *header = &frame->header; unsigned int sfreqi, ngr, gr; { unsigned int sfreq; sfreq = header->samplerate; if (header->flags & MAD_FLAG_MPEG_2_5_EXT) sfreq *= 2; /* 48000 => 0, 44100 => 1, 32000 => 2, 24000 => 3, 22050 => 4, 16000 => 5 */ sfreqi = ((sfreq >> 7) & 0x000f) + ((sfreq >> 15) & 0x0001) - 8; if (header->flags & MAD_FLAG_MPEG_2_5_EXT) sfreqi += 3; } /* scalefactors, Huffman decoding, requantization */ ngr = (header->flags & MAD_FLAG_LSF_EXT) ? 1 : 2; for (gr = 0; gr < ngr; ++gr) { struct granule *granule = &si->gr[gr]; unsigned char const *sfbwidth[2]; mad_fixed_t xr[2][576]; unsigned int ch; enum mad_error error; for (ch = 0; ch < nch; ++ch) { struct channel *channel = &granule->ch[ch]; unsigned int part2_length; sfbwidth[ch] = sfbwidth_table[sfreqi].l; if (channel->block_type == 2) { sfbwidth[ch] = (channel->flags & mixed_block_flag) ? sfbwidth_table[sfreqi].m : sfbwidth_table[sfreqi].s; } if (header->flags & MAD_FLAG_LSF_EXT) { part2_length = III_scalefactors_lsf(ptr, channel, ch == 0 ? 0 : &si->gr[1].ch[1], header->mode_extension); } else { part2_length = III_scalefactors(ptr, channel, &si->gr[0].ch[ch], gr == 0 ? 0 : si->scfsi[ch]); } error = III_huffdecode(ptr, xr[ch], channel, sfbwidth[ch], part2_length); if (error) return error; } /* joint stereo processing */ if (header->mode == MAD_MODE_JOINT_STEREO && header->mode_extension) { error = III_stereo(xr, granule, header, sfbwidth[0]); if (error) return error; } /* reordering, alias reduction, IMDCT, overlap-add, frequency inversion */ for (ch = 0; ch < nch; ++ch) { struct channel const *channel = &granule->ch[ch]; mad_fixed_t (*sample)[32] = &frame->sbsample[ch][18 * gr]; unsigned int sb, l, i, sblimit; mad_fixed_t output[36]; if (channel->block_type == 2) { III_reorder(xr[ch], channel, sfbwidth[ch]); # if !defined(OPT_STRICT) /* * According to ISO/IEC 11172-3, "Alias reduction is not applied for * granules with block_type == 2 (short block)." However, other * sources suggest alias reduction should indeed be performed on the * lower two subbands of mixed blocks. Most other implementations do * this, so by default we will too. */ if (channel->flags & mixed_block_flag) III_aliasreduce(xr[ch], 36); # endif } else III_aliasreduce(xr[ch], 576); l = 0; /* subbands 0-1 */ if (channel->block_type != 2 || (channel->flags & mixed_block_flag)) { unsigned int block_type; block_type = channel->block_type; if (channel->flags & mixed_block_flag) block_type = 0; /* long blocks */ for (sb = 0; sb < 2; ++sb, l += 18) { III_imdct_l(&xr[ch][l], output, block_type); III_overlap(output, (*frame->overlap)[ch][sb], sample, sb); } } else { /* short blocks */ for (sb = 0; sb < 2; ++sb, l += 18) { III_imdct_s(&xr[ch][l], output); III_overlap(output, (*frame->overlap)[ch][sb], sample, sb); } } III_freqinver(sample, 1); /* (nonzero) subbands 2-31 */ i = 576; while (i > 36 && xr[ch][i - 1] == 0) --i; sblimit = 32 - (576 - i) / 18; if (channel->block_type != 2) { /* long blocks */ for (sb = 2; sb < sblimit; ++sb, l += 18) { III_imdct_l(&xr[ch][l], output, channel->block_type); III_overlap(output, (*frame->overlap)[ch][sb], sample, sb); if (sb & 1) III_freqinver(sample, sb); } } else { /* short blocks */ for (sb = 2; sb < sblimit; ++sb, l += 18) { III_imdct_s(&xr[ch][l], output); III_overlap(output, (*frame->overlap)[ch][sb], sample, sb); if (sb & 1) III_freqinver(sample, sb); } } /* remaining (zero) subbands */ for (sb = sblimit; sb < 32; ++sb) { III_overlap_z((*frame->overlap)[ch][sb], sample, sb); if (sb & 1) III_freqinver(sample, sb); } } } return MAD_ERROR_NONE; } /* * NAME: layer->III() * DESCRIPTION: decode a single Layer III frame */ int mad_layer_III(struct mad_stream *stream, struct mad_frame *frame) { struct mad_header *header = &frame->header; unsigned int nch, priv_bitlen, next_md_begin = 0; unsigned int si_len, data_bitlen, md_len; unsigned int frame_space, frame_used, frame_free; struct mad_bitptr ptr; struct sideinfo si; enum mad_error error; int result = 0; /* allocate Layer III dynamic structures */ if (stream->main_data == 0) { stream->main_data = malloc(MAD_BUFFER_MDLEN); if (stream->main_data == 0) { stream->error = MAD_ERROR_NOMEM; return -1; } } if (frame->overlap == 0) { frame->overlap = calloc(2 * 32 * 18, sizeof(mad_fixed_t)); if (frame->overlap == 0) { stream->error = MAD_ERROR_NOMEM; return -1; } } nch = MAD_NCHANNELS(header); si_len = (header->flags & MAD_FLAG_LSF_EXT) ? (nch == 1 ? 9 : 17) : (nch == 1 ? 17 : 32); /* check frame sanity */ if (stream->next_frame - mad_bit_nextbyte(&stream->ptr) < (signed int) si_len) { stream->error = MAD_ERROR_BADFRAMELEN; stream->md_len = 0; return -1; } /* check CRC word */ if (header->flags & MAD_FLAG_PROTECTION) { header->crc_check = mad_bit_crc(stream->ptr, si_len * CHAR_BIT, header->crc_check); if (header->crc_check != header->crc_target && !(frame->options & MAD_OPTION_IGNORECRC)) { stream->error = MAD_ERROR_BADCRC; result = -1; } } /* decode frame side information */ error = III_sideinfo(&stream->ptr, nch, header->flags & MAD_FLAG_LSF_EXT, &si, &data_bitlen, &priv_bitlen); if (error && result == 0) { stream->error = error; result = -1; } header->flags |= priv_bitlen; header->private_bits |= si.private_bits; /* find main_data of next frame */ { struct mad_bitptr peek; unsigned long header; mad_bit_init(&peek, stream->next_frame); header = mad_bit_read(&peek, 32); if ((header & 0xffe60000L) /* syncword | layer */ == 0xffe20000L) { if (!(header & 0x00010000L)) /* protection_bit */ mad_bit_skip(&peek, 16); /* crc_check */ next_md_begin = mad_bit_read(&peek, (header & 0x00080000L) /* ID */ ? 9 : 8); } mad_bit_finish(&peek); } /* find main_data of this frame */ frame_space = stream->next_frame - mad_bit_nextbyte(&stream->ptr); if (next_md_begin > si.main_data_begin + frame_space) next_md_begin = 0; md_len = si.main_data_begin + frame_space - next_md_begin; frame_used = 0; if (si.main_data_begin == 0) { ptr = stream->ptr; stream->md_len = 0; frame_used = md_len; } else { if (si.main_data_begin > stream->md_len) { if (result == 0) { stream->error = MAD_ERROR_BADDATAPTR; result = -1; } } else { mad_bit_init(&ptr, *stream->main_data + stream->md_len - si.main_data_begin); if (md_len > si.main_data_begin) { assert(stream->md_len + md_len - si.main_data_begin <= MAD_BUFFER_MDLEN); memcpy(*stream->main_data + stream->md_len, mad_bit_nextbyte(&stream->ptr), frame_used = md_len - si.main_data_begin); stream->md_len += frame_used; } } } frame_free = frame_space - frame_used; /* decode main_data */ if (result == 0) { error = III_decode(&ptr, frame, &si, nch); if (error) { stream->error = error; result = -1; } /* designate ancillary bits */ stream->anc_ptr = ptr; stream->anc_bitlen = md_len * CHAR_BIT - data_bitlen; } # if 0 && defined(DEBUG) fprintf(stderr, "main_data_begin:%u, md_len:%u, frame_free:%u, " "data_bitlen:%u, anc_bitlen: %u\n", si.main_data_begin, md_len, frame_free, data_bitlen, stream->anc_bitlen); # endif /* preload main_data buffer with up to 511 bytes for next frame(s) */ if (frame_free >= next_md_begin) { memcpy(*stream->main_data, stream->next_frame - next_md_begin, next_md_begin); stream->md_len = next_md_begin; } else { if (md_len < si.main_data_begin) { unsigned int extra; extra = si.main_data_begin - md_len; if (extra + frame_free > next_md_begin) extra = next_md_begin - frame_free; if (extra < stream->md_len) { memmove(*stream->main_data, *stream->main_data + stream->md_len - extra, extra); stream->md_len = extra; } } else stream->md_len = 0; memcpy(*stream->main_data + stream->md_len, stream->next_frame - frame_free, frame_free); stream->md_len += frame_free; } return result; } sources_5316/external/mp3/mad_fixed.h0000644000176700017670000003237010627342357016353 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: fixed.h,v 1.38 2004/02/17 02:02:03 rob Exp $ */ # ifndef LIBMAD_FIXED_H # define LIBMAD_FIXED_H # if SIZEOF_INT >= 4 typedef signed int mad_fixed_t; typedef signed int mad_fixed64hi_t; typedef unsigned int mad_fixed64lo_t; # else typedef signed long mad_fixed_t; typedef signed long mad_fixed64hi_t; typedef unsigned long mad_fixed64lo_t; # endif # if defined(_MSC_VER) # define mad_fixed64_t signed __int64 # elif 1 || defined(__GNUC__) # define mad_fixed64_t signed long long # endif # if defined(FPM_FLOAT) typedef double mad_sample_t; # else typedef mad_fixed_t mad_sample_t; # endif /* * Fixed-point format: 0xABBBBBBB * A == whole part (sign + 3 bits) * B == fractional part (28 bits) * * Values are signed two's complement, so the effective range is: * 0x80000000 to 0x7fffffff * -8.0 to +7.9999999962747097015380859375 * * The smallest representable value is: * 0x00000001 == 0.0000000037252902984619140625 (i.e. about 3.725e-9) * * 28 bits of fractional accuracy represent about * 8.6 digits of decimal accuracy. * * Fixed-point numbers can be added or subtracted as normal * integers, but multiplication requires shifting the 64-bit result * from 56 fractional bits back to 28 (and rounding.) * * Changing the definition of MAD_F_FRACBITS is only partially * supported, and must be done with care. */ # define MAD_F_FRACBITS 28 # if MAD_F_FRACBITS == 28 # define MAD_F(x) ((mad_fixed_t) (x##L)) # else # if MAD_F_FRACBITS < 28 # warning "MAD_F_FRACBITS < 28" # define MAD_F(x) ((mad_fixed_t) \ (((x##L) + \ (1L << (28 - MAD_F_FRACBITS - 1))) >> \ (28 - MAD_F_FRACBITS))) # elif MAD_F_FRACBITS > 28 # error "MAD_F_FRACBITS > 28 not currently supported" # define MAD_F(x) ((mad_fixed_t) \ ((x##L) << (MAD_F_FRACBITS - 28))) # endif # endif # define MAD_F_MIN ((mad_fixed_t) -0x80000000L) # define MAD_F_MAX ((mad_fixed_t) +0x7fffffffL) # define MAD_F_ONE MAD_F(0x10000000) # define mad_f_tofixed(x) ((mad_fixed_t) \ ((x) * (double) (1L << MAD_F_FRACBITS) + 0.5)) # define mad_f_todouble(x) ((double) \ ((x) / (double) (1L << MAD_F_FRACBITS))) # define mad_f_intpart(x) ((x) >> MAD_F_FRACBITS) # define mad_f_fracpart(x) ((x) & ((1L << MAD_F_FRACBITS) - 1)) /* (x should be positive) */ # define mad_f_fromint(x) ((x) << MAD_F_FRACBITS) # define mad_f_add(x, y) ((x) + (y)) # define mad_f_sub(x, y) ((x) - (y)) # if defined(FPM_FLOAT) # error "FPM_FLOAT not yet supported" # undef MAD_F # define MAD_F(x) mad_f_todouble(x) # define mad_f_mul(x, y) ((x) * (y)) # define mad_f_scale64 # undef ASO_ZEROCHECK # elif defined(FPM_64BIT) /* * This version should be the most accurate if 64-bit types are supported by * the compiler, although it may not be the most efficient. */ # if defined(OPT_ACCURACY) # define mad_f_mul(x, y) \ ((mad_fixed_t) \ ((((mad_fixed64_t) (x) * (y)) + \ (1L << (MAD_F_SCALEBITS - 1))) >> MAD_F_SCALEBITS)) # else # define mad_f_mul(x, y) \ ((mad_fixed_t) (((mad_fixed64_t) (x) * (y)) >> MAD_F_SCALEBITS)) # endif # define MAD_F_SCALEBITS MAD_F_FRACBITS /* --- Intel --------------------------------------------------------------- */ # elif defined(FPM_INTEL) # if defined(_MSC_VER) # pragma warning(push) # pragma warning(disable: 4035) /* no return value */ static __forceinline mad_fixed_t mad_f_mul_inline(mad_fixed_t x, mad_fixed_t y) { enum { fracbits = MAD_F_FRACBITS }; __asm { mov eax, x imul y shrd eax, edx, fracbits } /* implicit return of eax */ } # pragma warning(pop) # define mad_f_mul mad_f_mul_inline # define mad_f_scale64 # else /* * This Intel version is fast and accurate; the disposition of the least * significant bit depends on OPT_ACCURACY via mad_f_scale64(). */ # define MAD_F_MLX(hi, lo, x, y) \ asm ("imull %3" \ : "=a" (lo), "=d" (hi) \ : "%a" (x), "rm" (y) \ : "cc") # if defined(OPT_ACCURACY) /* * This gives best accuracy but is not very fast. */ # define MAD_F_MLA(hi, lo, x, y) \ ({ mad_fixed64hi_t __hi; \ mad_fixed64lo_t __lo; \ MAD_F_MLX(__hi, __lo, (x), (y)); \ asm ("addl %2,%0\n\t" \ "adcl %3,%1" \ : "=rm" (lo), "=rm" (hi) \ : "r" (__lo), "r" (__hi), "0" (lo), "1" (hi) \ : "cc"); \ }) # endif /* OPT_ACCURACY */ # if defined(OPT_ACCURACY) /* * Surprisingly, this is faster than SHRD followed by ADC. */ # define mad_f_scale64(hi, lo) \ ({ mad_fixed64hi_t __hi_; \ mad_fixed64lo_t __lo_; \ mad_fixed_t __result; \ asm ("addl %4,%2\n\t" \ "adcl %5,%3" \ : "=rm" (__lo_), "=rm" (__hi_) \ : "0" (lo), "1" (hi), \ "ir" (1L << (MAD_F_SCALEBITS - 1)), "ir" (0) \ : "cc"); \ asm ("shrdl %3,%2,%1" \ : "=rm" (__result) \ : "0" (__lo_), "r" (__hi_), "I" (MAD_F_SCALEBITS) \ : "cc"); \ __result; \ }) # elif defined(OPT_INTEL) /* * Alternate Intel scaling that may or may not perform better. */ # define mad_f_scale64(hi, lo) \ ({ mad_fixed_t __result; \ asm ("shrl %3,%1\n\t" \ "shll %4,%2\n\t" \ "orl %2,%1" \ : "=rm" (__result) \ : "0" (lo), "r" (hi), \ "I" (MAD_F_SCALEBITS), "I" (32 - MAD_F_SCALEBITS) \ : "cc"); \ __result; \ }) # else # define mad_f_scale64(hi, lo) \ ({ mad_fixed_t __result; \ asm ("shrdl %3,%2,%1" \ : "=rm" (__result) \ : "0" (lo), "r" (hi), "I" (MAD_F_SCALEBITS) \ : "cc"); \ __result; \ }) # endif /* OPT_ACCURACY */ # define MAD_F_SCALEBITS MAD_F_FRACBITS # endif /* --- ARM ----------------------------------------------------------------- */ # elif defined(FPM_ARM) /* * This ARM V4 version is as accurate as FPM_64BIT but much faster. The * least significant bit is properly rounded at no CPU cycle cost! */ # if 1 /* * This is faster than the default implementation via MAD_F_MLX() and * mad_f_scale64(). */ # define mad_f_mul(x, y) \ ({ mad_fixed64hi_t __hi; \ mad_fixed64lo_t __lo; \ mad_fixed_t __result; \ asm ("smull %0, %1, %3, %4\n\t" \ "movs %0, %0, lsr %5\n\t" \ "adc %2, %0, %1, lsl %6" \ : "=&r" (__lo), "=&r" (__hi), "=r" (__result) \ : "%r" (x), "r" (y), \ "M" (MAD_F_SCALEBITS), "M" (32 - MAD_F_SCALEBITS) \ : "cc"); \ __result; \ }) # endif # define MAD_F_MLX(hi, lo, x, y) \ asm ("smull %0, %1, %2, %3" \ : "=&r" (lo), "=&r" (hi) \ : "%r" (x), "r" (y)) # define MAD_F_MLA(hi, lo, x, y) \ asm ("smlal %0, %1, %2, %3" \ : "+r" (lo), "+r" (hi) \ : "%r" (x), "r" (y)) # define MAD_F_MLN(hi, lo) \ asm ("rsbs %0, %2, #0\n\t" \ "rsc %1, %3, #0" \ : "=r" (lo), "=r" (hi) \ : "0" (lo), "1" (hi) \ : "cc") # define mad_f_scale64(hi, lo) \ ({ mad_fixed_t __result; \ asm ("movs %0, %1, lsr %3\n\t" \ "adc %0, %0, %2, lsl %4" \ : "=&r" (__result) \ : "r" (lo), "r" (hi), \ "M" (MAD_F_SCALEBITS), "M" (32 - MAD_F_SCALEBITS) \ : "cc"); \ __result; \ }) # define MAD_F_SCALEBITS MAD_F_FRACBITS /* --- MIPS ---------------------------------------------------------------- */ # elif defined(FPM_MIPS) /* * This MIPS version is fast and accurate; the disposition of the least * significant bit depends on OPT_ACCURACY via mad_f_scale64(). */ # define MAD_F_MLX(hi, lo, x, y) \ asm ("mult %2,%3" \ : "=l" (lo), "=h" (hi) \ : "%r" (x), "r" (y)) # if defined(HAVE_MADD_ASM) # define MAD_F_MLA(hi, lo, x, y) \ asm ("madd %2,%3" \ : "+l" (lo), "+h" (hi) \ : "%r" (x), "r" (y)) # elif defined(HAVE_MADD16_ASM) /* * This loses significant accuracy due to the 16-bit integer limit in the * multiply/accumulate instruction. */ # define MAD_F_ML0(hi, lo, x, y) \ asm ("mult %2,%3" \ : "=l" (lo), "=h" (hi) \ : "%r" ((x) >> 12), "r" ((y) >> 16)) # define MAD_F_MLA(hi, lo, x, y) \ asm ("madd16 %2,%3" \ : "+l" (lo), "+h" (hi) \ : "%r" ((x) >> 12), "r" ((y) >> 16)) # define MAD_F_MLZ(hi, lo) ((mad_fixed_t) (lo)) # endif # if defined(OPT_SPEED) # define mad_f_scale64(hi, lo) \ ((mad_fixed_t) ((hi) << (32 - MAD_F_SCALEBITS))) # define MAD_F_SCALEBITS MAD_F_FRACBITS # endif /* --- SPARC --------------------------------------------------------------- */ # elif defined(FPM_SPARC) /* * This SPARC V8 version is fast and accurate; the disposition of the least * significant bit depends on OPT_ACCURACY via mad_f_scale64(). */ # define MAD_F_MLX(hi, lo, x, y) \ asm ("smul %2, %3, %0\n\t" \ "rd %%y, %1" \ : "=r" (lo), "=r" (hi) \ : "%r" (x), "rI" (y)) /* --- PowerPC ------------------------------------------------------------- */ # elif defined(FPM_PPC) /* * This PowerPC version is fast and accurate; the disposition of the least * significant bit depends on OPT_ACCURACY via mad_f_scale64(). */ # define MAD_F_MLX(hi, lo, x, y) \ do { \ asm ("mullw %0,%1,%2" \ : "=r" (lo) \ : "%r" (x), "r" (y)); \ asm ("mulhw %0,%1,%2" \ : "=r" (hi) \ : "%r" (x), "r" (y)); \ } \ while (0) # if defined(OPT_ACCURACY) /* * This gives best accuracy but is not very fast. */ # define MAD_F_MLA(hi, lo, x, y) \ ({ mad_fixed64hi_t __hi; \ mad_fixed64lo_t __lo; \ MAD_F_MLX(__hi, __lo, (x), (y)); \ asm ("addc %0,%2,%3\n\t" \ "adde %1,%4,%5" \ : "=r" (lo), "=r" (hi) \ : "%r" (lo), "r" (__lo), \ "%r" (hi), "r" (__hi) \ : "xer"); \ }) # endif # if defined(OPT_ACCURACY) /* * This is slower than the truncating version below it. */ # define mad_f_scale64(hi, lo) \ ({ mad_fixed_t __result, __round; \ asm ("rotrwi %0,%1,%2" \ : "=r" (__result) \ : "r" (lo), "i" (MAD_F_SCALEBITS)); \ asm ("extrwi %0,%1,1,0" \ : "=r" (__round) \ : "r" (__result)); \ asm ("insrwi %0,%1,%2,0" \ : "+r" (__result) \ : "r" (hi), "i" (MAD_F_SCALEBITS)); \ asm ("add %0,%1,%2" \ : "=r" (__result) \ : "%r" (__result), "r" (__round)); \ __result; \ }) # else # define mad_f_scale64(hi, lo) \ ({ mad_fixed_t __result; \ asm ("rotrwi %0,%1,%2" \ : "=r" (__result) \ : "r" (lo), "i" (MAD_F_SCALEBITS)); \ asm ("insrwi %0,%1,%2,0" \ : "+r" (__result) \ : "r" (hi), "i" (MAD_F_SCALEBITS)); \ __result; \ }) # endif # define MAD_F_SCALEBITS MAD_F_FRACBITS /* --- Default ------------------------------------------------------------- */ # elif defined(FPM_DEFAULT) /* * This version is the most portable but it loses significant accuracy. * Furthermore, accuracy is biased against the second argument, so care * should be taken when ordering operands. * * The scale factors are constant as this is not used with SSO. * * Pre-rounding is required to stay within the limits of compliance. */ # if defined(OPT_SPEED) # define mad_f_mul(x, y) (((x) >> 12) * ((y) >> 16)) # else # define mad_f_mul(x, y) ((((x) + (1L << 11)) >> 12) * \ (((y) + (1L << 15)) >> 16)) # endif /* ------------------------------------------------------------------------- */ # else # error "no FPM selected" # endif /* default implementations */ # if !defined(mad_f_mul) # define mad_f_mul(x, y) \ ({ register mad_fixed64hi_t __hi; \ register mad_fixed64lo_t __lo; \ MAD_F_MLX(__hi, __lo, (x), (y)); \ mad_f_scale64(__hi, __lo); \ }) # endif # if !defined(MAD_F_MLA) # define MAD_F_ML0(hi, lo, x, y) ((lo) = mad_f_mul((x), (y))) # define MAD_F_MLA(hi, lo, x, y) ((lo) += mad_f_mul((x), (y))) # define MAD_F_MLN(hi, lo) ((lo) = -(lo)) # define MAD_F_MLZ(hi, lo) ((void) (hi), (mad_fixed_t) (lo)) # endif # if !defined(MAD_F_ML0) # define MAD_F_ML0(hi, lo, x, y) MAD_F_MLX((hi), (lo), (x), (y)) # endif # if !defined(MAD_F_MLN) # define MAD_F_MLN(hi, lo) ((hi) = ((lo) = -(lo)) ? ~(hi) : -(hi)) # endif # if !defined(MAD_F_MLZ) # define MAD_F_MLZ(hi, lo) mad_f_scale64((hi), (lo)) # endif # if !defined(mad_f_scale64) # if defined(OPT_ACCURACY) # define mad_f_scale64(hi, lo) \ ((((mad_fixed_t) \ (((hi) << (32 - (MAD_F_SCALEBITS - 1))) | \ ((lo) >> (MAD_F_SCALEBITS - 1)))) + 1) >> 1) # else # define mad_f_scale64(hi, lo) \ ((mad_fixed_t) \ (((hi) << (32 - MAD_F_SCALEBITS)) | \ ((lo) >> MAD_F_SCALEBITS))) # endif # define MAD_F_SCALEBITS MAD_F_FRACBITS # endif /* C routines */ mad_fixed_t mad_f_abs(mad_fixed_t); mad_fixed_t mad_f_div(mad_fixed_t, mad_fixed_t); # endif sources_5316/external/mp3/mad_rq_table.dat0000644000176700017670000166476710627342357017414 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: rq_table.dat,v 1.7 2004/01/23 09:41:32 rob Exp $ */ /* * This is the lookup table used to compute x^(4/3) for Layer III * requantization. To maintain the best possible accuracy, the value is * stored as a normalized mantissa with exponent. The requantization * algorithm recombines these parts with appropriate scaling. */ /* 0 */ { MAD_F(0x00000000) /* 0.000000000 */, 0 }, /* 1 */ { MAD_F(0x04000000) /* 0.250000000 */, 2 }, /* 2 */ { MAD_F(0x050a28be) /* 0.314980262 */, 3 }, /* 3 */ { MAD_F(0x0453a5cd) /* 0.270421794 */, 4 }, /* 4 */ { MAD_F(0x06597fa9) /* 0.396850263 */, 4 }, /* 5 */ { MAD_F(0x04466275) /* 0.267183742 */, 5 }, /* 6 */ { MAD_F(0x05738c72) /* 0.340710111 */, 5 }, /* 7 */ { MAD_F(0x06b1fc81) /* 0.418453696 */, 5 }, /* 8 */ { MAD_F(0x04000000) /* 0.250000000 */, 6 }, /* 9 */ { MAD_F(0x04ae20d7) /* 0.292511788 */, 6 }, /* 10 */ { MAD_F(0x0562d694) /* 0.336630420 */, 6 }, /* 11 */ { MAD_F(0x061dae96) /* 0.382246578 */, 6 }, /* 12 */ { MAD_F(0x06de47f4) /* 0.429267841 */, 6 }, /* 13 */ { MAD_F(0x07a44f7a) /* 0.477614858 */, 6 }, /* 14 */ { MAD_F(0x0437be65) /* 0.263609310 */, 7 }, /* 15 */ { MAD_F(0x049fc824) /* 0.289009227 */, 7 }, /* 16 */ { MAD_F(0x050a28be) /* 0.314980262 */, 7 }, /* 17 */ { MAD_F(0x0576c6f5) /* 0.341498336 */, 7 }, /* 18 */ { MAD_F(0x05e58c0b) /* 0.368541759 */, 7 }, /* 19 */ { MAD_F(0x06566361) /* 0.396090870 */, 7 }, /* 20 */ { MAD_F(0x06c93a2e) /* 0.424127753 */, 7 }, /* 21 */ { MAD_F(0x073dff3e) /* 0.452635998 */, 7 }, /* 22 */ { MAD_F(0x07b4a2bc) /* 0.481600510 */, 7 }, /* 23 */ { MAD_F(0x04168b05) /* 0.255503674 */, 8 }, /* 24 */ { MAD_F(0x0453a5cd) /* 0.270421794 */, 8 }, /* 25 */ { MAD_F(0x04919b6a) /* 0.285548607 */, 8 }, /* 26 */ { MAD_F(0x04d065fb) /* 0.300878507 */, 8 }, /* 27 */ { MAD_F(0x05100000) /* 0.316406250 */, 8 }, /* 28 */ { MAD_F(0x05506451) /* 0.332126919 */, 8 }, /* 29 */ { MAD_F(0x05918e15) /* 0.348035890 */, 8 }, /* 30 */ { MAD_F(0x05d378bb) /* 0.364128809 */, 8 }, /* 31 */ { MAD_F(0x06161ff3) /* 0.380401563 */, 8 }, /* 32 */ { MAD_F(0x06597fa9) /* 0.396850263 */, 8 }, /* 33 */ { MAD_F(0x069d9400) /* 0.413471222 */, 8 }, /* 34 */ { MAD_F(0x06e2594c) /* 0.430260942 */, 8 }, /* 35 */ { MAD_F(0x0727cc11) /* 0.447216097 */, 8 }, /* 36 */ { MAD_F(0x076de8fc) /* 0.464333519 */, 8 }, /* 37 */ { MAD_F(0x07b4ace3) /* 0.481610189 */, 8 }, /* 38 */ { MAD_F(0x07fc14bf) /* 0.499043224 */, 8 }, /* 39 */ { MAD_F(0x04220ed7) /* 0.258314934 */, 9 }, /* 40 */ { MAD_F(0x04466275) /* 0.267183742 */, 9 }, /* 41 */ { MAD_F(0x046b03e7) /* 0.276126771 */, 9 }, /* 42 */ { MAD_F(0x048ff1e8) /* 0.285142811 */, 9 }, /* 43 */ { MAD_F(0x04b52b3f) /* 0.294230696 */, 9 }, /* 44 */ { MAD_F(0x04daaec0) /* 0.303389310 */, 9 }, /* 45 */ { MAD_F(0x05007b49) /* 0.312617576 */, 9 }, /* 46 */ { MAD_F(0x05268fc6) /* 0.321914457 */, 9 }, /* 47 */ { MAD_F(0x054ceb2a) /* 0.331278957 */, 9 }, /* 48 */ { MAD_F(0x05738c72) /* 0.340710111 */, 9 }, /* 49 */ { MAD_F(0x059a72a5) /* 0.350206992 */, 9 }, /* 50 */ { MAD_F(0x05c19cd3) /* 0.359768701 */, 9 }, /* 51 */ { MAD_F(0x05e90a12) /* 0.369394372 */, 9 }, /* 52 */ { MAD_F(0x0610b982) /* 0.379083164 */, 9 }, /* 53 */ { MAD_F(0x0638aa48) /* 0.388834268 */, 9 }, /* 54 */ { MAD_F(0x0660db91) /* 0.398646895 */, 9 }, /* 55 */ { MAD_F(0x06894c90) /* 0.408520284 */, 9 }, /* 56 */ { MAD_F(0x06b1fc81) /* 0.418453696 */, 9 }, /* 57 */ { MAD_F(0x06daeaa1) /* 0.428446415 */, 9 }, /* 58 */ { MAD_F(0x07041636) /* 0.438497744 */, 9 }, /* 59 */ { MAD_F(0x072d7e8b) /* 0.448607009 */, 9 }, /* 60 */ { MAD_F(0x075722ef) /* 0.458773552 */, 9 }, /* 61 */ { MAD_F(0x078102b8) /* 0.468996735 */, 9 }, /* 62 */ { MAD_F(0x07ab1d3e) /* 0.479275937 */, 9 }, /* 63 */ { MAD_F(0x07d571e0) /* 0.489610555 */, 9 }, /* 64 */ { MAD_F(0x04000000) /* 0.250000000 */, 10 }, /* 65 */ { MAD_F(0x04156381) /* 0.255221850 */, 10 }, /* 66 */ { MAD_F(0x042ae32a) /* 0.260470548 */, 10 }, /* 67 */ { MAD_F(0x04407eb1) /* 0.265745823 */, 10 }, /* 68 */ { MAD_F(0x045635cf) /* 0.271047409 */, 10 }, /* 69 */ { MAD_F(0x046c083e) /* 0.276375048 */, 10 }, /* 70 */ { MAD_F(0x0481f5bb) /* 0.281728487 */, 10 }, /* 71 */ { MAD_F(0x0497fe03) /* 0.287107481 */, 10 }, /* 72 */ { MAD_F(0x04ae20d7) /* 0.292511788 */, 10 }, /* 73 */ { MAD_F(0x04c45df6) /* 0.297941173 */, 10 }, /* 74 */ { MAD_F(0x04dab524) /* 0.303395408 */, 10 }, /* 75 */ { MAD_F(0x04f12624) /* 0.308874267 */, 10 }, /* 76 */ { MAD_F(0x0507b0bc) /* 0.314377532 */, 10 }, /* 77 */ { MAD_F(0x051e54b1) /* 0.319904987 */, 10 }, /* 78 */ { MAD_F(0x053511cb) /* 0.325456423 */, 10 }, /* 79 */ { MAD_F(0x054be7d4) /* 0.331031635 */, 10 }, /* 80 */ { MAD_F(0x0562d694) /* 0.336630420 */, 10 }, /* 81 */ { MAD_F(0x0579ddd8) /* 0.342252584 */, 10 }, /* 82 */ { MAD_F(0x0590fd6c) /* 0.347897931 */, 10 }, /* 83 */ { MAD_F(0x05a8351c) /* 0.353566275 */, 10 }, /* 84 */ { MAD_F(0x05bf84b8) /* 0.359257429 */, 10 }, /* 85 */ { MAD_F(0x05d6ec0e) /* 0.364971213 */, 10 }, /* 86 */ { MAD_F(0x05ee6aef) /* 0.370707448 */, 10 }, /* 87 */ { MAD_F(0x0606012b) /* 0.376465960 */, 10 }, /* 88 */ { MAD_F(0x061dae96) /* 0.382246578 */, 10 }, /* 89 */ { MAD_F(0x06357302) /* 0.388049134 */, 10 }, /* 90 */ { MAD_F(0x064d4e43) /* 0.393873464 */, 10 }, /* 91 */ { MAD_F(0x0665402d) /* 0.399719406 */, 10 }, /* 92 */ { MAD_F(0x067d4896) /* 0.405586801 */, 10 }, /* 93 */ { MAD_F(0x06956753) /* 0.411475493 */, 10 }, /* 94 */ { MAD_F(0x06ad9c3d) /* 0.417385331 */, 10 }, /* 95 */ { MAD_F(0x06c5e72b) /* 0.423316162 */, 10 }, /* 96 */ { MAD_F(0x06de47f4) /* 0.429267841 */, 10 }, /* 97 */ { MAD_F(0x06f6be73) /* 0.435240221 */, 10 }, /* 98 */ { MAD_F(0x070f4a80) /* 0.441233161 */, 10 }, /* 99 */ { MAD_F(0x0727ebf7) /* 0.447246519 */, 10 }, /* 100 */ { MAD_F(0x0740a2b2) /* 0.453280160 */, 10 }, /* 101 */ { MAD_F(0x07596e8d) /* 0.459333946 */, 10 }, /* 102 */ { MAD_F(0x07724f64) /* 0.465407744 */, 10 }, /* 103 */ { MAD_F(0x078b4514) /* 0.471501425 */, 10 }, /* 104 */ { MAD_F(0x07a44f7a) /* 0.477614858 */, 10 }, /* 105 */ { MAD_F(0x07bd6e75) /* 0.483747918 */, 10 }, /* 106 */ { MAD_F(0x07d6a1e2) /* 0.489900479 */, 10 }, /* 107 */ { MAD_F(0x07efe9a1) /* 0.496072418 */, 10 }, /* 108 */ { MAD_F(0x0404a2c9) /* 0.251131807 */, 11 }, /* 109 */ { MAD_F(0x04115aca) /* 0.254236974 */, 11 }, /* 110 */ { MAD_F(0x041e1cc4) /* 0.257351652 */, 11 }, /* 111 */ { MAD_F(0x042ae8a7) /* 0.260475783 */, 11 }, /* 112 */ { MAD_F(0x0437be65) /* 0.263609310 */, 11 }, /* 113 */ { MAD_F(0x04449dee) /* 0.266752177 */, 11 }, /* 114 */ { MAD_F(0x04518733) /* 0.269904329 */, 11 }, /* 115 */ { MAD_F(0x045e7a26) /* 0.273065710 */, 11 }, /* 116 */ { MAD_F(0x046b76b9) /* 0.276236269 */, 11 }, /* 117 */ { MAD_F(0x04787cdc) /* 0.279415952 */, 11 }, /* 118 */ { MAD_F(0x04858c83) /* 0.282604707 */, 11 }, /* 119 */ { MAD_F(0x0492a59f) /* 0.285802482 */, 11 }, /* 120 */ { MAD_F(0x049fc824) /* 0.289009227 */, 11 }, /* 121 */ { MAD_F(0x04acf402) /* 0.292224893 */, 11 }, /* 122 */ { MAD_F(0x04ba292e) /* 0.295449429 */, 11 }, /* 123 */ { MAD_F(0x04c7679a) /* 0.298682788 */, 11 }, /* 124 */ { MAD_F(0x04d4af3a) /* 0.301924921 */, 11 }, /* 125 */ { MAD_F(0x04e20000) /* 0.305175781 */, 11 }, /* 126 */ { MAD_F(0x04ef59e0) /* 0.308435322 */, 11 }, /* 127 */ { MAD_F(0x04fcbcce) /* 0.311703498 */, 11 }, /* 128 */ { MAD_F(0x050a28be) /* 0.314980262 */, 11 }, /* 129 */ { MAD_F(0x05179da4) /* 0.318265572 */, 11 }, /* 130 */ { MAD_F(0x05251b73) /* 0.321559381 */, 11 }, /* 131 */ { MAD_F(0x0532a220) /* 0.324861647 */, 11 }, /* 132 */ { MAD_F(0x054031a0) /* 0.328172327 */, 11 }, /* 133 */ { MAD_F(0x054dc9e7) /* 0.331491377 */, 11 }, /* 134 */ { MAD_F(0x055b6ae9) /* 0.334818756 */, 11 }, /* 135 */ { MAD_F(0x0569149c) /* 0.338154423 */, 11 }, /* 136 */ { MAD_F(0x0576c6f5) /* 0.341498336 */, 11 }, /* 137 */ { MAD_F(0x058481e9) /* 0.344850455 */, 11 }, /* 138 */ { MAD_F(0x0592456d) /* 0.348210741 */, 11 }, /* 139 */ { MAD_F(0x05a01176) /* 0.351579152 */, 11 }, /* 140 */ { MAD_F(0x05ade5fa) /* 0.354955651 */, 11 }, /* 141 */ { MAD_F(0x05bbc2ef) /* 0.358340200 */, 11 }, /* 142 */ { MAD_F(0x05c9a84a) /* 0.361732758 */, 11 }, /* 143 */ { MAD_F(0x05d79601) /* 0.365133291 */, 11 }, /* 144 */ { MAD_F(0x05e58c0b) /* 0.368541759 */, 11 }, /* 145 */ { MAD_F(0x05f38a5d) /* 0.371958126 */, 11 }, /* 146 */ { MAD_F(0x060190ee) /* 0.375382356 */, 11 }, /* 147 */ { MAD_F(0x060f9fb3) /* 0.378814413 */, 11 }, /* 148 */ { MAD_F(0x061db6a5) /* 0.382254261 */, 11 }, /* 149 */ { MAD_F(0x062bd5b8) /* 0.385701865 */, 11 }, /* 150 */ { MAD_F(0x0639fce4) /* 0.389157191 */, 11 }, /* 151 */ { MAD_F(0x06482c1f) /* 0.392620204 */, 11 }, /* 152 */ { MAD_F(0x06566361) /* 0.396090870 */, 11 }, /* 153 */ { MAD_F(0x0664a2a0) /* 0.399569155 */, 11 }, /* 154 */ { MAD_F(0x0672e9d4) /* 0.403055027 */, 11 }, /* 155 */ { MAD_F(0x068138f3) /* 0.406548452 */, 11 }, /* 156 */ { MAD_F(0x068f8ff5) /* 0.410049398 */, 11 }, /* 157 */ { MAD_F(0x069deed1) /* 0.413557833 */, 11 }, /* 158 */ { MAD_F(0x06ac557f) /* 0.417073724 */, 11 }, /* 159 */ { MAD_F(0x06bac3f6) /* 0.420597041 */, 11 }, /* 160 */ { MAD_F(0x06c93a2e) /* 0.424127753 */, 11 }, /* 161 */ { MAD_F(0x06d7b81f) /* 0.427665827 */, 11 }, /* 162 */ { MAD_F(0x06e63dc0) /* 0.431211234 */, 11 }, /* 163 */ { MAD_F(0x06f4cb09) /* 0.434763944 */, 11 }, /* 164 */ { MAD_F(0x07035ff3) /* 0.438323927 */, 11 }, /* 165 */ { MAD_F(0x0711fc75) /* 0.441891153 */, 11 }, /* 166 */ { MAD_F(0x0720a087) /* 0.445465593 */, 11 }, /* 167 */ { MAD_F(0x072f4c22) /* 0.449047217 */, 11 }, /* 168 */ { MAD_F(0x073dff3e) /* 0.452635998 */, 11 }, /* 169 */ { MAD_F(0x074cb9d3) /* 0.456231906 */, 11 }, /* 170 */ { MAD_F(0x075b7bdb) /* 0.459834914 */, 11 }, /* 171 */ { MAD_F(0x076a454c) /* 0.463444993 */, 11 }, /* 172 */ { MAD_F(0x07791620) /* 0.467062117 */, 11 }, /* 173 */ { MAD_F(0x0787ee50) /* 0.470686258 */, 11 }, /* 174 */ { MAD_F(0x0796cdd4) /* 0.474317388 */, 11 }, /* 175 */ { MAD_F(0x07a5b4a5) /* 0.477955481 */, 11 }, /* 176 */ { MAD_F(0x07b4a2bc) /* 0.481600510 */, 11 }, /* 177 */ { MAD_F(0x07c39812) /* 0.485252449 */, 11 }, /* 178 */ { MAD_F(0x07d294a0) /* 0.488911273 */, 11 }, /* 179 */ { MAD_F(0x07e1985f) /* 0.492576954 */, 11 }, /* 180 */ { MAD_F(0x07f0a348) /* 0.496249468 */, 11 }, /* 181 */ { MAD_F(0x07ffb554) /* 0.499928790 */, 11 }, /* 182 */ { MAD_F(0x0407673f) /* 0.251807447 */, 12 }, /* 183 */ { MAD_F(0x040ef75e) /* 0.253653877 */, 12 }, /* 184 */ { MAD_F(0x04168b05) /* 0.255503674 */, 12 }, /* 185 */ { MAD_F(0x041e2230) /* 0.257356825 */, 12 }, /* 186 */ { MAD_F(0x0425bcdd) /* 0.259213318 */, 12 }, /* 187 */ { MAD_F(0x042d5b07) /* 0.261073141 */, 12 }, /* 188 */ { MAD_F(0x0434fcad) /* 0.262936282 */, 12 }, /* 189 */ { MAD_F(0x043ca1c9) /* 0.264802730 */, 12 }, /* 190 */ { MAD_F(0x04444a5a) /* 0.266672472 */, 12 }, /* 191 */ { MAD_F(0x044bf65d) /* 0.268545497 */, 12 }, /* 192 */ { MAD_F(0x0453a5cd) /* 0.270421794 */, 12 }, /* 193 */ { MAD_F(0x045b58a9) /* 0.272301352 */, 12 }, /* 194 */ { MAD_F(0x04630eed) /* 0.274184158 */, 12 }, /* 195 */ { MAD_F(0x046ac896) /* 0.276070203 */, 12 }, /* 196 */ { MAD_F(0x047285a2) /* 0.277959474 */, 12 }, /* 197 */ { MAD_F(0x047a460c) /* 0.279851960 */, 12 }, /* 198 */ { MAD_F(0x048209d3) /* 0.281747652 */, 12 }, /* 199 */ { MAD_F(0x0489d0f4) /* 0.283646538 */, 12 }, /* 200 */ { MAD_F(0x04919b6a) /* 0.285548607 */, 12 }, /* 201 */ { MAD_F(0x04996935) /* 0.287453849 */, 12 }, /* 202 */ { MAD_F(0x04a13a50) /* 0.289362253 */, 12 }, /* 203 */ { MAD_F(0x04a90eba) /* 0.291273810 */, 12 }, /* 204 */ { MAD_F(0x04b0e66e) /* 0.293188507 */, 12 }, /* 205 */ { MAD_F(0x04b8c16c) /* 0.295106336 */, 12 }, /* 206 */ { MAD_F(0x04c09faf) /* 0.297027285 */, 12 }, /* 207 */ { MAD_F(0x04c88135) /* 0.298951346 */, 12 }, /* 208 */ { MAD_F(0x04d065fb) /* 0.300878507 */, 12 }, /* 209 */ { MAD_F(0x04d84dff) /* 0.302808759 */, 12 }, /* 210 */ { MAD_F(0x04e0393e) /* 0.304742092 */, 12 }, /* 211 */ { MAD_F(0x04e827b6) /* 0.306678497 */, 12 }, /* 212 */ { MAD_F(0x04f01963) /* 0.308617963 */, 12 }, /* 213 */ { MAD_F(0x04f80e44) /* 0.310560480 */, 12 }, /* 214 */ { MAD_F(0x05000655) /* 0.312506041 */, 12 }, /* 215 */ { MAD_F(0x05080195) /* 0.314454634 */, 12 }, /* 216 */ { MAD_F(0x05100000) /* 0.316406250 */, 12 }, /* 217 */ { MAD_F(0x05180194) /* 0.318360880 */, 12 }, /* 218 */ { MAD_F(0x0520064f) /* 0.320318516 */, 12 }, /* 219 */ { MAD_F(0x05280e2d) /* 0.322279147 */, 12 }, /* 220 */ { MAD_F(0x0530192e) /* 0.324242764 */, 12 }, /* 221 */ { MAD_F(0x0538274e) /* 0.326209359 */, 12 }, /* 222 */ { MAD_F(0x0540388a) /* 0.328178922 */, 12 }, /* 223 */ { MAD_F(0x05484ce2) /* 0.330151445 */, 12 }, /* 224 */ { MAD_F(0x05506451) /* 0.332126919 */, 12 }, /* 225 */ { MAD_F(0x05587ed5) /* 0.334105334 */, 12 }, /* 226 */ { MAD_F(0x05609c6e) /* 0.336086683 */, 12 }, /* 227 */ { MAD_F(0x0568bd17) /* 0.338070956 */, 12 }, /* 228 */ { MAD_F(0x0570e0cf) /* 0.340058145 */, 12 }, /* 229 */ { MAD_F(0x05790793) /* 0.342048241 */, 12 }, /* 230 */ { MAD_F(0x05813162) /* 0.344041237 */, 12 }, /* 231 */ { MAD_F(0x05895e39) /* 0.346037122 */, 12 }, /* 232 */ { MAD_F(0x05918e15) /* 0.348035890 */, 12 }, /* 233 */ { MAD_F(0x0599c0f4) /* 0.350037532 */, 12 }, /* 234 */ { MAD_F(0x05a1f6d5) /* 0.352042040 */, 12 }, /* 235 */ { MAD_F(0x05aa2fb5) /* 0.354049405 */, 12 }, /* 236 */ { MAD_F(0x05b26b92) /* 0.356059619 */, 12 }, /* 237 */ { MAD_F(0x05baaa69) /* 0.358072674 */, 12 }, /* 238 */ { MAD_F(0x05c2ec39) /* 0.360088563 */, 12 }, /* 239 */ { MAD_F(0x05cb3100) /* 0.362107278 */, 12 }, /* 240 */ { MAD_F(0x05d378bb) /* 0.364128809 */, 12 }, /* 241 */ { MAD_F(0x05dbc368) /* 0.366153151 */, 12 }, /* 242 */ { MAD_F(0x05e41105) /* 0.368180294 */, 12 }, /* 243 */ { MAD_F(0x05ec6190) /* 0.370210231 */, 12 }, /* 244 */ { MAD_F(0x05f4b507) /* 0.372242955 */, 12 }, /* 245 */ { MAD_F(0x05fd0b68) /* 0.374278458 */, 12 }, /* 246 */ { MAD_F(0x060564b1) /* 0.376316732 */, 12 }, /* 247 */ { MAD_F(0x060dc0e0) /* 0.378357769 */, 12 }, /* 248 */ { MAD_F(0x06161ff3) /* 0.380401563 */, 12 }, /* 249 */ { MAD_F(0x061e81e8) /* 0.382448106 */, 12 }, /* 250 */ { MAD_F(0x0626e6bc) /* 0.384497391 */, 12 }, /* 251 */ { MAD_F(0x062f4e6f) /* 0.386549409 */, 12 }, /* 252 */ { MAD_F(0x0637b8fd) /* 0.388604155 */, 12 }, /* 253 */ { MAD_F(0x06402666) /* 0.390661620 */, 12 }, /* 254 */ { MAD_F(0x064896a7) /* 0.392721798 */, 12 }, /* 255 */ { MAD_F(0x065109be) /* 0.394784681 */, 12 }, /* 256 */ { MAD_F(0x06597fa9) /* 0.396850263 */, 12 }, /* 257 */ { MAD_F(0x0661f867) /* 0.398918536 */, 12 }, /* 258 */ { MAD_F(0x066a73f5) /* 0.400989493 */, 12 }, /* 259 */ { MAD_F(0x0672f252) /* 0.403063128 */, 12 }, /* 260 */ { MAD_F(0x067b737c) /* 0.405139433 */, 12 }, /* 261 */ { MAD_F(0x0683f771) /* 0.407218402 */, 12 }, /* 262 */ { MAD_F(0x068c7e2f) /* 0.409300027 */, 12 }, /* 263 */ { MAD_F(0x069507b5) /* 0.411384303 */, 12 }, /* 264 */ { MAD_F(0x069d9400) /* 0.413471222 */, 12 }, /* 265 */ { MAD_F(0x06a6230f) /* 0.415560778 */, 12 }, /* 266 */ { MAD_F(0x06aeb4e0) /* 0.417652964 */, 12 }, /* 267 */ { MAD_F(0x06b74971) /* 0.419747773 */, 12 }, /* 268 */ { MAD_F(0x06bfe0c0) /* 0.421845199 */, 12 }, /* 269 */ { MAD_F(0x06c87acc) /* 0.423945235 */, 12 }, /* 270 */ { MAD_F(0x06d11794) /* 0.426047876 */, 12 }, /* 271 */ { MAD_F(0x06d9b714) /* 0.428153114 */, 12 }, /* 272 */ { MAD_F(0x06e2594c) /* 0.430260942 */, 12 }, /* 273 */ { MAD_F(0x06eafe3a) /* 0.432371356 */, 12 }, /* 274 */ { MAD_F(0x06f3a5dc) /* 0.434484348 */, 12 }, /* 275 */ { MAD_F(0x06fc5030) /* 0.436599912 */, 12 }, /* 276 */ { MAD_F(0x0704fd35) /* 0.438718042 */, 12 }, /* 277 */ { MAD_F(0x070dacea) /* 0.440838732 */, 12 }, /* 278 */ { MAD_F(0x07165f4b) /* 0.442961975 */, 12 }, /* 279 */ { MAD_F(0x071f1459) /* 0.445087765 */, 12 }, /* 280 */ { MAD_F(0x0727cc11) /* 0.447216097 */, 12 }, /* 281 */ { MAD_F(0x07308671) /* 0.449346964 */, 12 }, /* 282 */ { MAD_F(0x07394378) /* 0.451480360 */, 12 }, /* 283 */ { MAD_F(0x07420325) /* 0.453616280 */, 12 }, /* 284 */ { MAD_F(0x074ac575) /* 0.455754717 */, 12 }, /* 285 */ { MAD_F(0x07538a67) /* 0.457895665 */, 12 }, /* 286 */ { MAD_F(0x075c51fa) /* 0.460039119 */, 12 }, /* 287 */ { MAD_F(0x07651c2c) /* 0.462185072 */, 12 }, /* 288 */ { MAD_F(0x076de8fc) /* 0.464333519 */, 12 }, /* 289 */ { MAD_F(0x0776b867) /* 0.466484455 */, 12 }, /* 290 */ { MAD_F(0x077f8a6d) /* 0.468637872 */, 12 }, /* 291 */ { MAD_F(0x07885f0b) /* 0.470793767 */, 12 }, /* 292 */ { MAD_F(0x07913641) /* 0.472952132 */, 12 }, /* 293 */ { MAD_F(0x079a100c) /* 0.475112962 */, 12 }, /* 294 */ { MAD_F(0x07a2ec6c) /* 0.477276252 */, 12 }, /* 295 */ { MAD_F(0x07abcb5f) /* 0.479441997 */, 12 }, /* 296 */ { MAD_F(0x07b4ace3) /* 0.481610189 */, 12 }, /* 297 */ { MAD_F(0x07bd90f6) /* 0.483780825 */, 12 }, /* 298 */ { MAD_F(0x07c67798) /* 0.485953899 */, 12 }, /* 299 */ { MAD_F(0x07cf60c7) /* 0.488129404 */, 12 }, /* 300 */ { MAD_F(0x07d84c81) /* 0.490307336 */, 12 }, /* 301 */ { MAD_F(0x07e13ac5) /* 0.492487690 */, 12 }, /* 302 */ { MAD_F(0x07ea2b92) /* 0.494670459 */, 12 }, /* 303 */ { MAD_F(0x07f31ee6) /* 0.496855639 */, 12 }, /* 304 */ { MAD_F(0x07fc14bf) /* 0.499043224 */, 12 }, /* 305 */ { MAD_F(0x0402868e) /* 0.250616605 */, 13 }, /* 306 */ { MAD_F(0x040703ff) /* 0.251712795 */, 13 }, /* 307 */ { MAD_F(0x040b82b0) /* 0.252810180 */, 13 }, /* 308 */ { MAD_F(0x041002a1) /* 0.253908756 */, 13 }, /* 309 */ { MAD_F(0x041483d1) /* 0.255008523 */, 13 }, /* 310 */ { MAD_F(0x04190640) /* 0.256109476 */, 13 }, /* 311 */ { MAD_F(0x041d89ed) /* 0.257211614 */, 13 }, /* 312 */ { MAD_F(0x04220ed7) /* 0.258314934 */, 13 }, /* 313 */ { MAD_F(0x042694fe) /* 0.259419433 */, 13 }, /* 314 */ { MAD_F(0x042b1c60) /* 0.260525110 */, 13 }, /* 315 */ { MAD_F(0x042fa4fe) /* 0.261631960 */, 13 }, /* 316 */ { MAD_F(0x04342ed7) /* 0.262739982 */, 13 }, /* 317 */ { MAD_F(0x0438b9e9) /* 0.263849174 */, 13 }, /* 318 */ { MAD_F(0x043d4635) /* 0.264959533 */, 13 }, /* 319 */ { MAD_F(0x0441d3b9) /* 0.266071056 */, 13 }, /* 320 */ { MAD_F(0x04466275) /* 0.267183742 */, 13 }, /* 321 */ { MAD_F(0x044af269) /* 0.268297587 */, 13 }, /* 322 */ { MAD_F(0x044f8393) /* 0.269412589 */, 13 }, /* 323 */ { MAD_F(0x045415f3) /* 0.270528746 */, 13 }, /* 324 */ { MAD_F(0x0458a989) /* 0.271646056 */, 13 }, /* 325 */ { MAD_F(0x045d3e53) /* 0.272764515 */, 13 }, /* 326 */ { MAD_F(0x0461d451) /* 0.273884123 */, 13 }, /* 327 */ { MAD_F(0x04666b83) /* 0.275004875 */, 13 }, /* 328 */ { MAD_F(0x046b03e7) /* 0.276126771 */, 13 }, /* 329 */ { MAD_F(0x046f9d7e) /* 0.277249808 */, 13 }, /* 330 */ { MAD_F(0x04743847) /* 0.278373983 */, 13 }, /* 331 */ { MAD_F(0x0478d440) /* 0.279499294 */, 13 }, /* 332 */ { MAD_F(0x047d716a) /* 0.280625739 */, 13 }, /* 333 */ { MAD_F(0x04820fc3) /* 0.281753315 */, 13 }, /* 334 */ { MAD_F(0x0486af4c) /* 0.282882021 */, 13 }, /* 335 */ { MAD_F(0x048b5003) /* 0.284011853 */, 13 }, /* 336 */ { MAD_F(0x048ff1e8) /* 0.285142811 */, 13 }, /* 337 */ { MAD_F(0x049494fb) /* 0.286274891 */, 13 }, /* 338 */ { MAD_F(0x0499393a) /* 0.287408091 */, 13 }, /* 339 */ { MAD_F(0x049ddea5) /* 0.288542409 */, 13 }, /* 340 */ { MAD_F(0x04a2853c) /* 0.289677844 */, 13 }, /* 341 */ { MAD_F(0x04a72cfe) /* 0.290814392 */, 13 }, /* 342 */ { MAD_F(0x04abd5ea) /* 0.291952051 */, 13 }, /* 343 */ { MAD_F(0x04b08000) /* 0.293090820 */, 13 }, /* 344 */ { MAD_F(0x04b52b3f) /* 0.294230696 */, 13 }, /* 345 */ { MAD_F(0x04b9d7a7) /* 0.295371678 */, 13 }, /* 346 */ { MAD_F(0x04be8537) /* 0.296513762 */, 13 }, /* 347 */ { MAD_F(0x04c333ee) /* 0.297656947 */, 13 }, /* 348 */ { MAD_F(0x04c7e3cc) /* 0.298801231 */, 13 }, /* 349 */ { MAD_F(0x04cc94d1) /* 0.299946611 */, 13 }, /* 350 */ { MAD_F(0x04d146fb) /* 0.301093085 */, 13 }, /* 351 */ { MAD_F(0x04d5fa4b) /* 0.302240653 */, 13 }, /* 352 */ { MAD_F(0x04daaec0) /* 0.303389310 */, 13 }, /* 353 */ { MAD_F(0x04df6458) /* 0.304539056 */, 13 }, /* 354 */ { MAD_F(0x04e41b14) /* 0.305689888 */, 13 }, /* 355 */ { MAD_F(0x04e8d2f3) /* 0.306841804 */, 13 }, /* 356 */ { MAD_F(0x04ed8bf5) /* 0.307994802 */, 13 }, /* 357 */ { MAD_F(0x04f24618) /* 0.309148880 */, 13 }, /* 358 */ { MAD_F(0x04f7015d) /* 0.310304037 */, 13 }, /* 359 */ { MAD_F(0x04fbbdc3) /* 0.311460269 */, 13 }, /* 360 */ { MAD_F(0x05007b49) /* 0.312617576 */, 13 }, /* 361 */ { MAD_F(0x050539ef) /* 0.313775954 */, 13 }, /* 362 */ { MAD_F(0x0509f9b4) /* 0.314935403 */, 13 }, /* 363 */ { MAD_F(0x050eba98) /* 0.316095920 */, 13 }, /* 364 */ { MAD_F(0x05137c9a) /* 0.317257503 */, 13 }, /* 365 */ { MAD_F(0x05183fba) /* 0.318420150 */, 13 }, /* 366 */ { MAD_F(0x051d03f7) /* 0.319583859 */, 13 }, /* 367 */ { MAD_F(0x0521c950) /* 0.320748629 */, 13 }, /* 368 */ { MAD_F(0x05268fc6) /* 0.321914457 */, 13 }, /* 369 */ { MAD_F(0x052b5757) /* 0.323081342 */, 13 }, /* 370 */ { MAD_F(0x05302003) /* 0.324249281 */, 13 }, /* 371 */ { MAD_F(0x0534e9ca) /* 0.325418273 */, 13 }, /* 372 */ { MAD_F(0x0539b4ab) /* 0.326588316 */, 13 }, /* 373 */ { MAD_F(0x053e80a6) /* 0.327759407 */, 13 }, /* 374 */ { MAD_F(0x05434db9) /* 0.328931546 */, 13 }, /* 375 */ { MAD_F(0x05481be5) /* 0.330104730 */, 13 }, /* 376 */ { MAD_F(0x054ceb2a) /* 0.331278957 */, 13 }, /* 377 */ { MAD_F(0x0551bb85) /* 0.332454225 */, 13 }, /* 378 */ { MAD_F(0x05568cf8) /* 0.333630533 */, 13 }, /* 379 */ { MAD_F(0x055b5f81) /* 0.334807879 */, 13 }, /* 380 */ { MAD_F(0x05603321) /* 0.335986261 */, 13 }, /* 381 */ { MAD_F(0x056507d6) /* 0.337165677 */, 13 }, /* 382 */ { MAD_F(0x0569dda0) /* 0.338346125 */, 13 }, /* 383 */ { MAD_F(0x056eb47f) /* 0.339527604 */, 13 }, /* 384 */ { MAD_F(0x05738c72) /* 0.340710111 */, 13 }, /* 385 */ { MAD_F(0x05786578) /* 0.341893646 */, 13 }, /* 386 */ { MAD_F(0x057d3f92) /* 0.343078205 */, 13 }, /* 387 */ { MAD_F(0x05821abf) /* 0.344263788 */, 13 }, /* 388 */ { MAD_F(0x0586f6fd) /* 0.345450393 */, 13 }, /* 389 */ { MAD_F(0x058bd44e) /* 0.346638017 */, 13 }, /* 390 */ { MAD_F(0x0590b2b0) /* 0.347826659 */, 13 }, /* 391 */ { MAD_F(0x05959222) /* 0.349016318 */, 13 }, /* 392 */ { MAD_F(0x059a72a5) /* 0.350206992 */, 13 }, /* 393 */ { MAD_F(0x059f5438) /* 0.351398678 */, 13 }, /* 394 */ { MAD_F(0x05a436da) /* 0.352591376 */, 13 }, /* 395 */ { MAD_F(0x05a91a8c) /* 0.353785083 */, 13 }, /* 396 */ { MAD_F(0x05adff4c) /* 0.354979798 */, 13 }, /* 397 */ { MAD_F(0x05b2e51a) /* 0.356175519 */, 13 }, /* 398 */ { MAD_F(0x05b7cbf5) /* 0.357372244 */, 13 }, /* 399 */ { MAD_F(0x05bcb3de) /* 0.358569972 */, 13 }, /* 400 */ { MAD_F(0x05c19cd3) /* 0.359768701 */, 13 }, /* 401 */ { MAD_F(0x05c686d5) /* 0.360968429 */, 13 }, /* 402 */ { MAD_F(0x05cb71e2) /* 0.362169156 */, 13 }, /* 403 */ { MAD_F(0x05d05dfb) /* 0.363370878 */, 13 }, /* 404 */ { MAD_F(0x05d54b1f) /* 0.364573594 */, 13 }, /* 405 */ { MAD_F(0x05da394d) /* 0.365777304 */, 13 }, /* 406 */ { MAD_F(0x05df2885) /* 0.366982004 */, 13 }, /* 407 */ { MAD_F(0x05e418c7) /* 0.368187694 */, 13 }, /* 408 */ { MAD_F(0x05e90a12) /* 0.369394372 */, 13 }, /* 409 */ { MAD_F(0x05edfc66) /* 0.370602036 */, 13 }, /* 410 */ { MAD_F(0x05f2efc2) /* 0.371810684 */, 13 }, /* 411 */ { MAD_F(0x05f7e426) /* 0.373020316 */, 13 }, /* 412 */ { MAD_F(0x05fcd992) /* 0.374230929 */, 13 }, /* 413 */ { MAD_F(0x0601d004) /* 0.375442522 */, 13 }, /* 414 */ { MAD_F(0x0606c77d) /* 0.376655093 */, 13 }, /* 415 */ { MAD_F(0x060bbffd) /* 0.377868641 */, 13 }, /* 416 */ { MAD_F(0x0610b982) /* 0.379083164 */, 13 }, /* 417 */ { MAD_F(0x0615b40c) /* 0.380298661 */, 13 }, /* 418 */ { MAD_F(0x061aaf9c) /* 0.381515130 */, 13 }, /* 419 */ { MAD_F(0x061fac2f) /* 0.382732569 */, 13 }, /* 420 */ { MAD_F(0x0624a9c7) /* 0.383950977 */, 13 }, /* 421 */ { MAD_F(0x0629a863) /* 0.385170352 */, 13 }, /* 422 */ { MAD_F(0x062ea802) /* 0.386390694 */, 13 }, /* 423 */ { MAD_F(0x0633a8a3) /* 0.387611999 */, 13 }, /* 424 */ { MAD_F(0x0638aa48) /* 0.388834268 */, 13 }, /* 425 */ { MAD_F(0x063dacee) /* 0.390057497 */, 13 }, /* 426 */ { MAD_F(0x0642b096) /* 0.391281687 */, 13 }, /* 427 */ { MAD_F(0x0647b53f) /* 0.392506834 */, 13 }, /* 428 */ { MAD_F(0x064cbae9) /* 0.393732939 */, 13 }, /* 429 */ { MAD_F(0x0651c193) /* 0.394959999 */, 13 }, /* 430 */ { MAD_F(0x0656c93d) /* 0.396188012 */, 13 }, /* 431 */ { MAD_F(0x065bd1e7) /* 0.397416978 */, 13 }, /* 432 */ { MAD_F(0x0660db91) /* 0.398646895 */, 13 }, /* 433 */ { MAD_F(0x0665e639) /* 0.399877761 */, 13 }, /* 434 */ { MAD_F(0x066af1df) /* 0.401109575 */, 13 }, /* 435 */ { MAD_F(0x066ffe84) /* 0.402342335 */, 13 }, /* 436 */ { MAD_F(0x06750c26) /* 0.403576041 */, 13 }, /* 437 */ { MAD_F(0x067a1ac6) /* 0.404810690 */, 13 }, /* 438 */ { MAD_F(0x067f2a62) /* 0.406046281 */, 13 }, /* 439 */ { MAD_F(0x06843afb) /* 0.407282813 */, 13 }, /* 440 */ { MAD_F(0x06894c90) /* 0.408520284 */, 13 }, /* 441 */ { MAD_F(0x068e5f21) /* 0.409758693 */, 13 }, /* 442 */ { MAD_F(0x069372ae) /* 0.410998038 */, 13 }, /* 443 */ { MAD_F(0x06988735) /* 0.412238319 */, 13 }, /* 444 */ { MAD_F(0x069d9cb7) /* 0.413479532 */, 13 }, /* 445 */ { MAD_F(0x06a2b333) /* 0.414721679 */, 13 }, /* 446 */ { MAD_F(0x06a7caa9) /* 0.415964756 */, 13 }, /* 447 */ { MAD_F(0x06ace318) /* 0.417208762 */, 13 }, /* 448 */ { MAD_F(0x06b1fc81) /* 0.418453696 */, 13 }, /* 449 */ { MAD_F(0x06b716e2) /* 0.419699557 */, 13 }, /* 450 */ { MAD_F(0x06bc323b) /* 0.420946343 */, 13 }, /* 451 */ { MAD_F(0x06c14e8d) /* 0.422194054 */, 13 }, /* 452 */ { MAD_F(0x06c66bd6) /* 0.423442686 */, 13 }, /* 453 */ { MAD_F(0x06cb8a17) /* 0.424692240 */, 13 }, /* 454 */ { MAD_F(0x06d0a94e) /* 0.425942714 */, 13 }, /* 455 */ { MAD_F(0x06d5c97c) /* 0.427194106 */, 13 }, /* 456 */ { MAD_F(0x06daeaa1) /* 0.428446415 */, 13 }, /* 457 */ { MAD_F(0x06e00cbb) /* 0.429699640 */, 13 }, /* 458 */ { MAD_F(0x06e52fca) /* 0.430953779 */, 13 }, /* 459 */ { MAD_F(0x06ea53cf) /* 0.432208832 */, 13 }, /* 460 */ { MAD_F(0x06ef78c8) /* 0.433464796 */, 13 }, /* 461 */ { MAD_F(0x06f49eb6) /* 0.434721671 */, 13 }, /* 462 */ { MAD_F(0x06f9c597) /* 0.435979455 */, 13 }, /* 463 */ { MAD_F(0x06feed6d) /* 0.437238146 */, 13 }, /* 464 */ { MAD_F(0x07041636) /* 0.438497744 */, 13 }, /* 465 */ { MAD_F(0x07093ff2) /* 0.439758248 */, 13 }, /* 466 */ { MAD_F(0x070e6aa0) /* 0.441019655 */, 13 }, /* 467 */ { MAD_F(0x07139641) /* 0.442281965 */, 13 }, /* 468 */ { MAD_F(0x0718c2d3) /* 0.443545176 */, 13 }, /* 469 */ { MAD_F(0x071df058) /* 0.444809288 */, 13 }, /* 470 */ { MAD_F(0x07231ecd) /* 0.446074298 */, 13 }, /* 471 */ { MAD_F(0x07284e34) /* 0.447340205 */, 13 }, /* 472 */ { MAD_F(0x072d7e8b) /* 0.448607009 */, 13 }, /* 473 */ { MAD_F(0x0732afd2) /* 0.449874708 */, 13 }, /* 474 */ { MAD_F(0x0737e209) /* 0.451143300 */, 13 }, /* 475 */ { MAD_F(0x073d1530) /* 0.452412785 */, 13 }, /* 476 */ { MAD_F(0x07424946) /* 0.453683161 */, 13 }, /* 477 */ { MAD_F(0x07477e4b) /* 0.454954427 */, 13 }, /* 478 */ { MAD_F(0x074cb43e) /* 0.456226581 */, 13 }, /* 479 */ { MAD_F(0x0751eb20) /* 0.457499623 */, 13 }, /* 480 */ { MAD_F(0x075722ef) /* 0.458773552 */, 13 }, /* 481 */ { MAD_F(0x075c5bac) /* 0.460048365 */, 13 }, /* 482 */ { MAD_F(0x07619557) /* 0.461324062 */, 13 }, /* 483 */ { MAD_F(0x0766cfee) /* 0.462600642 */, 13 }, /* 484 */ { MAD_F(0x076c0b72) /* 0.463878102 */, 13 }, /* 485 */ { MAD_F(0x077147e2) /* 0.465156443 */, 13 }, /* 486 */ { MAD_F(0x0776853e) /* 0.466435663 */, 13 }, /* 487 */ { MAD_F(0x077bc385) /* 0.467715761 */, 13 }, /* 488 */ { MAD_F(0x078102b8) /* 0.468996735 */, 13 }, /* 489 */ { MAD_F(0x078642d6) /* 0.470278584 */, 13 }, /* 490 */ { MAD_F(0x078b83de) /* 0.471561307 */, 13 }, /* 491 */ { MAD_F(0x0790c5d1) /* 0.472844904 */, 13 }, /* 492 */ { MAD_F(0x079608ae) /* 0.474129372 */, 13 }, /* 493 */ { MAD_F(0x079b4c74) /* 0.475414710 */, 13 }, /* 494 */ { MAD_F(0x07a09124) /* 0.476700918 */, 13 }, /* 495 */ { MAD_F(0x07a5d6bd) /* 0.477987994 */, 13 }, /* 496 */ { MAD_F(0x07ab1d3e) /* 0.479275937 */, 13 }, /* 497 */ { MAD_F(0x07b064a8) /* 0.480564746 */, 13 }, /* 498 */ { MAD_F(0x07b5acfb) /* 0.481854420 */, 13 }, /* 499 */ { MAD_F(0x07baf635) /* 0.483144957 */, 13 }, /* 500 */ { MAD_F(0x07c04056) /* 0.484436356 */, 13 }, /* 501 */ { MAD_F(0x07c58b5f) /* 0.485728617 */, 13 }, /* 502 */ { MAD_F(0x07cad74e) /* 0.487021738 */, 13 }, /* 503 */ { MAD_F(0x07d02424) /* 0.488315717 */, 13 }, /* 504 */ { MAD_F(0x07d571e0) /* 0.489610555 */, 13 }, /* 505 */ { MAD_F(0x07dac083) /* 0.490906249 */, 13 }, /* 506 */ { MAD_F(0x07e0100a) /* 0.492202799 */, 13 }, /* 507 */ { MAD_F(0x07e56078) /* 0.493500203 */, 13 }, /* 508 */ { MAD_F(0x07eab1ca) /* 0.494798460 */, 13 }, /* 509 */ { MAD_F(0x07f00401) /* 0.496097570 */, 13 }, /* 510 */ { MAD_F(0x07f5571d) /* 0.497397530 */, 13 }, /* 511 */ { MAD_F(0x07faab1c) /* 0.498698341 */, 13 }, /* 512 */ { MAD_F(0x04000000) /* 0.250000000 */, 14 }, /* 513 */ { MAD_F(0x0402aae3) /* 0.250651254 */, 14 }, /* 514 */ { MAD_F(0x04055638) /* 0.251302930 */, 14 }, /* 515 */ { MAD_F(0x040801ff) /* 0.251955030 */, 14 }, /* 516 */ { MAD_F(0x040aae37) /* 0.252607552 */, 14 }, /* 517 */ { MAD_F(0x040d5ae0) /* 0.253260495 */, 14 }, /* 518 */ { MAD_F(0x041007fa) /* 0.253913860 */, 14 }, /* 519 */ { MAD_F(0x0412b586) /* 0.254567645 */, 14 }, /* 520 */ { MAD_F(0x04156381) /* 0.255221850 */, 14 }, /* 521 */ { MAD_F(0x041811ee) /* 0.255876475 */, 14 }, /* 522 */ { MAD_F(0x041ac0cb) /* 0.256531518 */, 14 }, /* 523 */ { MAD_F(0x041d7018) /* 0.257186980 */, 14 }, /* 524 */ { MAD_F(0x04201fd5) /* 0.257842860 */, 14 }, /* 525 */ { MAD_F(0x0422d003) /* 0.258499157 */, 14 }, /* 526 */ { MAD_F(0x042580a0) /* 0.259155872 */, 14 }, /* 527 */ { MAD_F(0x042831ad) /* 0.259813002 */, 14 }, /* 528 */ { MAD_F(0x042ae32a) /* 0.260470548 */, 14 }, /* 529 */ { MAD_F(0x042d9516) /* 0.261128510 */, 14 }, /* 530 */ { MAD_F(0x04304772) /* 0.261786886 */, 14 }, /* 531 */ { MAD_F(0x0432fa3d) /* 0.262445676 */, 14 }, /* 532 */ { MAD_F(0x0435ad76) /* 0.263104880 */, 14 }, /* 533 */ { MAD_F(0x0438611f) /* 0.263764497 */, 14 }, /* 534 */ { MAD_F(0x043b1536) /* 0.264424527 */, 14 }, /* 535 */ { MAD_F(0x043dc9bc) /* 0.265084969 */, 14 }, /* 536 */ { MAD_F(0x04407eb1) /* 0.265745823 */, 14 }, /* 537 */ { MAD_F(0x04433414) /* 0.266407088 */, 14 }, /* 538 */ { MAD_F(0x0445e9e5) /* 0.267068763 */, 14 }, /* 539 */ { MAD_F(0x0448a024) /* 0.267730848 */, 14 }, /* 540 */ { MAD_F(0x044b56d1) /* 0.268393343 */, 14 }, /* 541 */ { MAD_F(0x044e0dec) /* 0.269056248 */, 14 }, /* 542 */ { MAD_F(0x0450c575) /* 0.269719560 */, 14 }, /* 543 */ { MAD_F(0x04537d6b) /* 0.270383281 */, 14 }, /* 544 */ { MAD_F(0x045635cf) /* 0.271047409 */, 14 }, /* 545 */ { MAD_F(0x0458ee9f) /* 0.271711944 */, 14 }, /* 546 */ { MAD_F(0x045ba7dd) /* 0.272376886 */, 14 }, /* 547 */ { MAD_F(0x045e6188) /* 0.273042234 */, 14 }, /* 548 */ { MAD_F(0x04611ba0) /* 0.273707988 */, 14 }, /* 549 */ { MAD_F(0x0463d625) /* 0.274374147 */, 14 }, /* 550 */ { MAD_F(0x04669116) /* 0.275040710 */, 14 }, /* 551 */ { MAD_F(0x04694c74) /* 0.275707677 */, 14 }, /* 552 */ { MAD_F(0x046c083e) /* 0.276375048 */, 14 }, /* 553 */ { MAD_F(0x046ec474) /* 0.277042822 */, 14 }, /* 554 */ { MAD_F(0x04718116) /* 0.277710999 */, 14 }, /* 555 */ { MAD_F(0x04743e25) /* 0.278379578 */, 14 }, /* 556 */ { MAD_F(0x0476fb9f) /* 0.279048558 */, 14 }, /* 557 */ { MAD_F(0x0479b984) /* 0.279717940 */, 14 }, /* 558 */ { MAD_F(0x047c77d6) /* 0.280387722 */, 14 }, /* 559 */ { MAD_F(0x047f3693) /* 0.281057905 */, 14 }, /* 560 */ { MAD_F(0x0481f5bb) /* 0.281728487 */, 14 }, /* 561 */ { MAD_F(0x0484b54e) /* 0.282399469 */, 14 }, /* 562 */ { MAD_F(0x0487754c) /* 0.283070849 */, 14 }, /* 563 */ { MAD_F(0x048a35b6) /* 0.283742628 */, 14 }, /* 564 */ { MAD_F(0x048cf68a) /* 0.284414805 */, 14 }, /* 565 */ { MAD_F(0x048fb7c8) /* 0.285087379 */, 14 }, /* 566 */ { MAD_F(0x04927972) /* 0.285760350 */, 14 }, /* 567 */ { MAD_F(0x04953b85) /* 0.286433717 */, 14 }, /* 568 */ { MAD_F(0x0497fe03) /* 0.287107481 */, 14 }, /* 569 */ { MAD_F(0x049ac0eb) /* 0.287781640 */, 14 }, /* 570 */ { MAD_F(0x049d843e) /* 0.288456194 */, 14 }, /* 571 */ { MAD_F(0x04a047fa) /* 0.289131142 */, 14 }, /* 572 */ { MAD_F(0x04a30c20) /* 0.289806485 */, 14 }, /* 573 */ { MAD_F(0x04a5d0af) /* 0.290482221 */, 14 }, /* 574 */ { MAD_F(0x04a895a8) /* 0.291158351 */, 14 }, /* 575 */ { MAD_F(0x04ab5b0b) /* 0.291834873 */, 14 }, /* 576 */ { MAD_F(0x04ae20d7) /* 0.292511788 */, 14 }, /* 577 */ { MAD_F(0x04b0e70c) /* 0.293189094 */, 14 }, /* 578 */ { MAD_F(0x04b3adaa) /* 0.293866792 */, 14 }, /* 579 */ { MAD_F(0x04b674b1) /* 0.294544881 */, 14 }, /* 580 */ { MAD_F(0x04b93c21) /* 0.295223360 */, 14 }, /* 581 */ { MAD_F(0x04bc03fa) /* 0.295902229 */, 14 }, /* 582 */ { MAD_F(0x04becc3b) /* 0.296581488 */, 14 }, /* 583 */ { MAD_F(0x04c194e4) /* 0.297261136 */, 14 }, /* 584 */ { MAD_F(0x04c45df6) /* 0.297941173 */, 14 }, /* 585 */ { MAD_F(0x04c72771) /* 0.298621598 */, 14 }, /* 586 */ { MAD_F(0x04c9f153) /* 0.299302411 */, 14 }, /* 587 */ { MAD_F(0x04ccbb9d) /* 0.299983611 */, 14 }, /* 588 */ { MAD_F(0x04cf864f) /* 0.300665198 */, 14 }, /* 589 */ { MAD_F(0x04d25169) /* 0.301347172 */, 14 }, /* 590 */ { MAD_F(0x04d51ceb) /* 0.302029532 */, 14 }, /* 591 */ { MAD_F(0x04d7e8d4) /* 0.302712277 */, 14 }, /* 592 */ { MAD_F(0x04dab524) /* 0.303395408 */, 14 }, /* 593 */ { MAD_F(0x04dd81dc) /* 0.304078923 */, 14 }, /* 594 */ { MAD_F(0x04e04efb) /* 0.304762823 */, 14 }, /* 595 */ { MAD_F(0x04e31c81) /* 0.305447106 */, 14 }, /* 596 */ { MAD_F(0x04e5ea6e) /* 0.306131773 */, 14 }, /* 597 */ { MAD_F(0x04e8b8c2) /* 0.306816823 */, 14 }, /* 598 */ { MAD_F(0x04eb877c) /* 0.307502256 */, 14 }, /* 599 */ { MAD_F(0x04ee569d) /* 0.308188071 */, 14 }, /* 600 */ { MAD_F(0x04f12624) /* 0.308874267 */, 14 }, /* 601 */ { MAD_F(0x04f3f612) /* 0.309560845 */, 14 }, /* 602 */ { MAD_F(0x04f6c666) /* 0.310247804 */, 14 }, /* 603 */ { MAD_F(0x04f99721) /* 0.310935143 */, 14 }, /* 604 */ { MAD_F(0x04fc6841) /* 0.311622862 */, 14 }, /* 605 */ { MAD_F(0x04ff39c7) /* 0.312310961 */, 14 }, /* 606 */ { MAD_F(0x05020bb3) /* 0.312999439 */, 14 }, /* 607 */ { MAD_F(0x0504de05) /* 0.313688296 */, 14 }, /* 608 */ { MAD_F(0x0507b0bc) /* 0.314377532 */, 14 }, /* 609 */ { MAD_F(0x050a83d8) /* 0.315067145 */, 14 }, /* 610 */ { MAD_F(0x050d575b) /* 0.315757136 */, 14 }, /* 611 */ { MAD_F(0x05102b42) /* 0.316447504 */, 14 }, /* 612 */ { MAD_F(0x0512ff8e) /* 0.317138249 */, 14 }, /* 613 */ { MAD_F(0x0515d440) /* 0.317829370 */, 14 }, /* 614 */ { MAD_F(0x0518a956) /* 0.318520867 */, 14 }, /* 615 */ { MAD_F(0x051b7ed1) /* 0.319212739 */, 14 }, /* 616 */ { MAD_F(0x051e54b1) /* 0.319904987 */, 14 }, /* 617 */ { MAD_F(0x05212af5) /* 0.320597609 */, 14 }, /* 618 */ { MAD_F(0x0524019e) /* 0.321290606 */, 14 }, /* 619 */ { MAD_F(0x0526d8ab) /* 0.321983976 */, 14 }, /* 620 */ { MAD_F(0x0529b01d) /* 0.322677720 */, 14 }, /* 621 */ { MAD_F(0x052c87f2) /* 0.323371837 */, 14 }, /* 622 */ { MAD_F(0x052f602c) /* 0.324066327 */, 14 }, /* 623 */ { MAD_F(0x053238ca) /* 0.324761189 */, 14 }, /* 624 */ { MAD_F(0x053511cb) /* 0.325456423 */, 14 }, /* 625 */ { MAD_F(0x0537eb30) /* 0.326152028 */, 14 }, /* 626 */ { MAD_F(0x053ac4f9) /* 0.326848005 */, 14 }, /* 627 */ { MAD_F(0x053d9f25) /* 0.327544352 */, 14 }, /* 628 */ { MAD_F(0x054079b5) /* 0.328241070 */, 14 }, /* 629 */ { MAD_F(0x054354a8) /* 0.328938157 */, 14 }, /* 630 */ { MAD_F(0x05462ffe) /* 0.329635614 */, 14 }, /* 631 */ { MAD_F(0x05490bb7) /* 0.330333440 */, 14 }, /* 632 */ { MAD_F(0x054be7d4) /* 0.331031635 */, 14 }, /* 633 */ { MAD_F(0x054ec453) /* 0.331730198 */, 14 }, /* 634 */ { MAD_F(0x0551a134) /* 0.332429129 */, 14 }, /* 635 */ { MAD_F(0x05547e79) /* 0.333128427 */, 14 }, /* 636 */ { MAD_F(0x05575c20) /* 0.333828093 */, 14 }, /* 637 */ { MAD_F(0x055a3a2a) /* 0.334528126 */, 14 }, /* 638 */ { MAD_F(0x055d1896) /* 0.335228525 */, 14 }, /* 639 */ { MAD_F(0x055ff764) /* 0.335929290 */, 14 }, /* 640 */ { MAD_F(0x0562d694) /* 0.336630420 */, 14 }, /* 641 */ { MAD_F(0x0565b627) /* 0.337331916 */, 14 }, /* 642 */ { MAD_F(0x0568961b) /* 0.338033777 */, 14 }, /* 643 */ { MAD_F(0x056b7671) /* 0.338736002 */, 14 }, /* 644 */ { MAD_F(0x056e5729) /* 0.339438592 */, 14 }, /* 645 */ { MAD_F(0x05713843) /* 0.340141545 */, 14 }, /* 646 */ { MAD_F(0x057419be) /* 0.340844862 */, 14 }, /* 647 */ { MAD_F(0x0576fb9a) /* 0.341548541 */, 14 }, /* 648 */ { MAD_F(0x0579ddd8) /* 0.342252584 */, 14 }, /* 649 */ { MAD_F(0x057cc077) /* 0.342956988 */, 14 }, /* 650 */ { MAD_F(0x057fa378) /* 0.343661754 */, 14 }, /* 651 */ { MAD_F(0x058286d9) /* 0.344366882 */, 14 }, /* 652 */ { MAD_F(0x05856a9b) /* 0.345072371 */, 14 }, /* 653 */ { MAD_F(0x05884ebe) /* 0.345778221 */, 14 }, /* 654 */ { MAD_F(0x058b3342) /* 0.346484431 */, 14 }, /* 655 */ { MAD_F(0x058e1827) /* 0.347191002 */, 14 }, /* 656 */ { MAD_F(0x0590fd6c) /* 0.347897931 */, 14 }, /* 657 */ { MAD_F(0x0593e311) /* 0.348605221 */, 14 }, /* 658 */ { MAD_F(0x0596c917) /* 0.349312869 */, 14 }, /* 659 */ { MAD_F(0x0599af7d) /* 0.350020876 */, 14 }, /* 660 */ { MAD_F(0x059c9643) /* 0.350729240 */, 14 }, /* 661 */ { MAD_F(0x059f7d6a) /* 0.351437963 */, 14 }, /* 662 */ { MAD_F(0x05a264f0) /* 0.352147044 */, 14 }, /* 663 */ { MAD_F(0x05a54cd6) /* 0.352856481 */, 14 }, /* 664 */ { MAD_F(0x05a8351c) /* 0.353566275 */, 14 }, /* 665 */ { MAD_F(0x05ab1dc2) /* 0.354276426 */, 14 }, /* 666 */ { MAD_F(0x05ae06c7) /* 0.354986932 */, 14 }, /* 667 */ { MAD_F(0x05b0f02b) /* 0.355697795 */, 14 }, /* 668 */ { MAD_F(0x05b3d9f0) /* 0.356409012 */, 14 }, /* 669 */ { MAD_F(0x05b6c413) /* 0.357120585 */, 14 }, /* 670 */ { MAD_F(0x05b9ae95) /* 0.357832512 */, 14 }, /* 671 */ { MAD_F(0x05bc9977) /* 0.358544794 */, 14 }, /* 672 */ { MAD_F(0x05bf84b8) /* 0.359257429 */, 14 }, /* 673 */ { MAD_F(0x05c27057) /* 0.359970419 */, 14 }, /* 674 */ { MAD_F(0x05c55c56) /* 0.360683761 */, 14 }, /* 675 */ { MAD_F(0x05c848b3) /* 0.361397456 */, 14 }, /* 676 */ { MAD_F(0x05cb356e) /* 0.362111504 */, 14 }, /* 677 */ { MAD_F(0x05ce2289) /* 0.362825904 */, 14 }, /* 678 */ { MAD_F(0x05d11001) /* 0.363540655 */, 14 }, /* 679 */ { MAD_F(0x05d3fdd8) /* 0.364255759 */, 14 }, /* 680 */ { MAD_F(0x05d6ec0e) /* 0.364971213 */, 14 }, /* 681 */ { MAD_F(0x05d9daa1) /* 0.365687018 */, 14 }, /* 682 */ { MAD_F(0x05dcc993) /* 0.366403174 */, 14 }, /* 683 */ { MAD_F(0x05dfb8e2) /* 0.367119680 */, 14 }, /* 684 */ { MAD_F(0x05e2a890) /* 0.367836535 */, 14 }, /* 685 */ { MAD_F(0x05e5989b) /* 0.368553740 */, 14 }, /* 686 */ { MAD_F(0x05e88904) /* 0.369271294 */, 14 }, /* 687 */ { MAD_F(0x05eb79cb) /* 0.369989197 */, 14 }, /* 688 */ { MAD_F(0x05ee6aef) /* 0.370707448 */, 14 }, /* 689 */ { MAD_F(0x05f15c70) /* 0.371426047 */, 14 }, /* 690 */ { MAD_F(0x05f44e4f) /* 0.372144994 */, 14 }, /* 691 */ { MAD_F(0x05f7408b) /* 0.372864289 */, 14 }, /* 692 */ { MAD_F(0x05fa3324) /* 0.373583930 */, 14 }, /* 693 */ { MAD_F(0x05fd261b) /* 0.374303918 */, 14 }, /* 694 */ { MAD_F(0x0600196e) /* 0.375024253 */, 14 }, /* 695 */ { MAD_F(0x06030d1e) /* 0.375744934 */, 14 }, /* 696 */ { MAD_F(0x0606012b) /* 0.376465960 */, 14 }, /* 697 */ { MAD_F(0x0608f595) /* 0.377187332 */, 14 }, /* 698 */ { MAD_F(0x060bea5c) /* 0.377909049 */, 14 }, /* 699 */ { MAD_F(0x060edf7f) /* 0.378631110 */, 14 }, /* 700 */ { MAD_F(0x0611d4fe) /* 0.379353516 */, 14 }, /* 701 */ { MAD_F(0x0614cada) /* 0.380076266 */, 14 }, /* 702 */ { MAD_F(0x0617c112) /* 0.380799360 */, 14 }, /* 703 */ { MAD_F(0x061ab7a6) /* 0.381522798 */, 14 }, /* 704 */ { MAD_F(0x061dae96) /* 0.382246578 */, 14 }, /* 705 */ { MAD_F(0x0620a5e3) /* 0.382970701 */, 14 }, /* 706 */ { MAD_F(0x06239d8b) /* 0.383695167 */, 14 }, /* 707 */ { MAD_F(0x0626958f) /* 0.384419975 */, 14 }, /* 708 */ { MAD_F(0x06298def) /* 0.385145124 */, 14 }, /* 709 */ { MAD_F(0x062c86aa) /* 0.385870615 */, 14 }, /* 710 */ { MAD_F(0x062f7fc1) /* 0.386596448 */, 14 }, /* 711 */ { MAD_F(0x06327934) /* 0.387322621 */, 14 }, /* 712 */ { MAD_F(0x06357302) /* 0.388049134 */, 14 }, /* 713 */ { MAD_F(0x06386d2b) /* 0.388775988 */, 14 }, /* 714 */ { MAD_F(0x063b67b0) /* 0.389503182 */, 14 }, /* 715 */ { MAD_F(0x063e6290) /* 0.390230715 */, 14 }, /* 716 */ { MAD_F(0x06415dcb) /* 0.390958588 */, 14 }, /* 717 */ { MAD_F(0x06445960) /* 0.391686799 */, 14 }, /* 718 */ { MAD_F(0x06475551) /* 0.392415349 */, 14 }, /* 719 */ { MAD_F(0x064a519c) /* 0.393144238 */, 14 }, /* 720 */ { MAD_F(0x064d4e43) /* 0.393873464 */, 14 }, /* 721 */ { MAD_F(0x06504b44) /* 0.394603028 */, 14 }, /* 722 */ { MAD_F(0x0653489f) /* 0.395332930 */, 14 }, /* 723 */ { MAD_F(0x06564655) /* 0.396063168 */, 14 }, /* 724 */ { MAD_F(0x06594465) /* 0.396793743 */, 14 }, /* 725 */ { MAD_F(0x065c42d0) /* 0.397524655 */, 14 }, /* 726 */ { MAD_F(0x065f4195) /* 0.398255903 */, 14 }, /* 727 */ { MAD_F(0x066240b4) /* 0.398987487 */, 14 }, /* 728 */ { MAD_F(0x0665402d) /* 0.399719406 */, 14 }, /* 729 */ { MAD_F(0x06684000) /* 0.400451660 */, 14 }, /* 730 */ { MAD_F(0x066b402d) /* 0.401184249 */, 14 }, /* 731 */ { MAD_F(0x066e40b3) /* 0.401917173 */, 14 }, /* 732 */ { MAD_F(0x06714194) /* 0.402650431 */, 14 }, /* 733 */ { MAD_F(0x067442ce) /* 0.403384024 */, 14 }, /* 734 */ { MAD_F(0x06774462) /* 0.404117949 */, 14 }, /* 735 */ { MAD_F(0x067a464f) /* 0.404852209 */, 14 }, /* 736 */ { MAD_F(0x067d4896) /* 0.405586801 */, 14 }, /* 737 */ { MAD_F(0x06804b36) /* 0.406321726 */, 14 }, /* 738 */ { MAD_F(0x06834e2f) /* 0.407056983 */, 14 }, /* 739 */ { MAD_F(0x06865181) /* 0.407792573 */, 14 }, /* 740 */ { MAD_F(0x0689552c) /* 0.408528495 */, 14 }, /* 741 */ { MAD_F(0x068c5931) /* 0.409264748 */, 14 }, /* 742 */ { MAD_F(0x068f5d8e) /* 0.410001332 */, 14 }, /* 743 */ { MAD_F(0x06926245) /* 0.410738247 */, 14 }, /* 744 */ { MAD_F(0x06956753) /* 0.411475493 */, 14 }, /* 745 */ { MAD_F(0x06986cbb) /* 0.412213070 */, 14 }, /* 746 */ { MAD_F(0x069b727b) /* 0.412950976 */, 14 }, /* 747 */ { MAD_F(0x069e7894) /* 0.413689213 */, 14 }, /* 748 */ { MAD_F(0x06a17f05) /* 0.414427779 */, 14 }, /* 749 */ { MAD_F(0x06a485cf) /* 0.415166674 */, 14 }, /* 750 */ { MAD_F(0x06a78cf1) /* 0.415905897 */, 14 }, /* 751 */ { MAD_F(0x06aa946b) /* 0.416645450 */, 14 }, /* 752 */ { MAD_F(0x06ad9c3d) /* 0.417385331 */, 14 }, /* 753 */ { MAD_F(0x06b0a468) /* 0.418125540 */, 14 }, /* 754 */ { MAD_F(0x06b3acea) /* 0.418866076 */, 14 }, /* 755 */ { MAD_F(0x06b6b5c4) /* 0.419606940 */, 14 }, /* 756 */ { MAD_F(0x06b9bef6) /* 0.420348132 */, 14 }, /* 757 */ { MAD_F(0x06bcc880) /* 0.421089650 */, 14 }, /* 758 */ { MAD_F(0x06bfd261) /* 0.421831494 */, 14 }, /* 759 */ { MAD_F(0x06c2dc9a) /* 0.422573665 */, 14 }, /* 760 */ { MAD_F(0x06c5e72b) /* 0.423316162 */, 14 }, /* 761 */ { MAD_F(0x06c8f213) /* 0.424058985 */, 14 }, /* 762 */ { MAD_F(0x06cbfd52) /* 0.424802133 */, 14 }, /* 763 */ { MAD_F(0x06cf08e9) /* 0.425545607 */, 14 }, /* 764 */ { MAD_F(0x06d214d7) /* 0.426289405 */, 14 }, /* 765 */ { MAD_F(0x06d5211c) /* 0.427033528 */, 14 }, /* 766 */ { MAD_F(0x06d82db8) /* 0.427777975 */, 14 }, /* 767 */ { MAD_F(0x06db3aaa) /* 0.428522746 */, 14 }, /* 768 */ { MAD_F(0x06de47f4) /* 0.429267841 */, 14 }, /* 769 */ { MAD_F(0x06e15595) /* 0.430013259 */, 14 }, /* 770 */ { MAD_F(0x06e4638d) /* 0.430759001 */, 14 }, /* 771 */ { MAD_F(0x06e771db) /* 0.431505065 */, 14 }, /* 772 */ { MAD_F(0x06ea807f) /* 0.432251452 */, 14 }, /* 773 */ { MAD_F(0x06ed8f7b) /* 0.432998162 */, 14 }, /* 774 */ { MAD_F(0x06f09ecc) /* 0.433745193 */, 14 }, /* 775 */ { MAD_F(0x06f3ae75) /* 0.434492546 */, 14 }, /* 776 */ { MAD_F(0x06f6be73) /* 0.435240221 */, 14 }, /* 777 */ { MAD_F(0x06f9cec8) /* 0.435988217 */, 14 }, /* 778 */ { MAD_F(0x06fcdf72) /* 0.436736534 */, 14 }, /* 779 */ { MAD_F(0x06fff073) /* 0.437485172 */, 14 }, /* 780 */ { MAD_F(0x070301ca) /* 0.438234130 */, 14 }, /* 781 */ { MAD_F(0x07061377) /* 0.438983408 */, 14 }, /* 782 */ { MAD_F(0x0709257a) /* 0.439733006 */, 14 }, /* 783 */ { MAD_F(0x070c37d2) /* 0.440482924 */, 14 }, /* 784 */ { MAD_F(0x070f4a80) /* 0.441233161 */, 14 }, /* 785 */ { MAD_F(0x07125d84) /* 0.441983717 */, 14 }, /* 786 */ { MAD_F(0x071570de) /* 0.442734592 */, 14 }, /* 787 */ { MAD_F(0x0718848d) /* 0.443485785 */, 14 }, /* 788 */ { MAD_F(0x071b9891) /* 0.444237296 */, 14 }, /* 789 */ { MAD_F(0x071eaceb) /* 0.444989126 */, 14 }, /* 790 */ { MAD_F(0x0721c19a) /* 0.445741273 */, 14 }, /* 791 */ { MAD_F(0x0724d69e) /* 0.446493738 */, 14 }, /* 792 */ { MAD_F(0x0727ebf7) /* 0.447246519 */, 14 }, /* 793 */ { MAD_F(0x072b01a6) /* 0.447999618 */, 14 }, /* 794 */ { MAD_F(0x072e17a9) /* 0.448753033 */, 14 }, /* 795 */ { MAD_F(0x07312e01) /* 0.449506765 */, 14 }, /* 796 */ { MAD_F(0x073444ae) /* 0.450260813 */, 14 }, /* 797 */ { MAD_F(0x07375bb0) /* 0.451015176 */, 14 }, /* 798 */ { MAD_F(0x073a7307) /* 0.451769856 */, 14 }, /* 799 */ { MAD_F(0x073d8ab2) /* 0.452524850 */, 14 }, /* 800 */ { MAD_F(0x0740a2b2) /* 0.453280160 */, 14 }, /* 801 */ { MAD_F(0x0743bb06) /* 0.454035784 */, 14 }, /* 802 */ { MAD_F(0x0746d3af) /* 0.454791723 */, 14 }, /* 803 */ { MAD_F(0x0749ecac) /* 0.455547976 */, 14 }, /* 804 */ { MAD_F(0x074d05fe) /* 0.456304543 */, 14 }, /* 805 */ { MAD_F(0x07501fa3) /* 0.457061423 */, 14 }, /* 806 */ { MAD_F(0x0753399d) /* 0.457818618 */, 14 }, /* 807 */ { MAD_F(0x075653eb) /* 0.458576125 */, 14 }, /* 808 */ { MAD_F(0x07596e8d) /* 0.459333946 */, 14 }, /* 809 */ { MAD_F(0x075c8983) /* 0.460092079 */, 14 }, /* 810 */ { MAD_F(0x075fa4cc) /* 0.460850524 */, 14 }, /* 811 */ { MAD_F(0x0762c06a) /* 0.461609282 */, 14 }, /* 812 */ { MAD_F(0x0765dc5b) /* 0.462368352 */, 14 }, /* 813 */ { MAD_F(0x0768f8a0) /* 0.463127733 */, 14 }, /* 814 */ { MAD_F(0x076c1538) /* 0.463887426 */, 14 }, /* 815 */ { MAD_F(0x076f3224) /* 0.464647430 */, 14 }, /* 816 */ { MAD_F(0x07724f64) /* 0.465407744 */, 14 }, /* 817 */ { MAD_F(0x07756cf7) /* 0.466168370 */, 14 }, /* 818 */ { MAD_F(0x07788add) /* 0.466929306 */, 14 }, /* 819 */ { MAD_F(0x077ba916) /* 0.467690552 */, 14 }, /* 820 */ { MAD_F(0x077ec7a3) /* 0.468452108 */, 14 }, /* 821 */ { MAD_F(0x0781e683) /* 0.469213973 */, 14 }, /* 822 */ { MAD_F(0x078505b5) /* 0.469976148 */, 14 }, /* 823 */ { MAD_F(0x0788253b) /* 0.470738632 */, 14 }, /* 824 */ { MAD_F(0x078b4514) /* 0.471501425 */, 14 }, /* 825 */ { MAD_F(0x078e653f) /* 0.472264527 */, 14 }, /* 826 */ { MAD_F(0x079185be) /* 0.473027937 */, 14 }, /* 827 */ { MAD_F(0x0794a68f) /* 0.473791655 */, 14 }, /* 828 */ { MAD_F(0x0797c7b2) /* 0.474555681 */, 14 }, /* 829 */ { MAD_F(0x079ae929) /* 0.475320014 */, 14 }, /* 830 */ { MAD_F(0x079e0af1) /* 0.476084655 */, 14 }, /* 831 */ { MAD_F(0x07a12d0c) /* 0.476849603 */, 14 }, /* 832 */ { MAD_F(0x07a44f7a) /* 0.477614858 */, 14 }, /* 833 */ { MAD_F(0x07a7723a) /* 0.478380420 */, 14 }, /* 834 */ { MAD_F(0x07aa954c) /* 0.479146288 */, 14 }, /* 835 */ { MAD_F(0x07adb8b0) /* 0.479912463 */, 14 }, /* 836 */ { MAD_F(0x07b0dc67) /* 0.480678943 */, 14 }, /* 837 */ { MAD_F(0x07b4006f) /* 0.481445729 */, 14 }, /* 838 */ { MAD_F(0x07b724ca) /* 0.482212820 */, 14 }, /* 839 */ { MAD_F(0x07ba4976) /* 0.482980216 */, 14 }, /* 840 */ { MAD_F(0x07bd6e75) /* 0.483747918 */, 14 }, /* 841 */ { MAD_F(0x07c093c5) /* 0.484515924 */, 14 }, /* 842 */ { MAD_F(0x07c3b967) /* 0.485284235 */, 14 }, /* 843 */ { MAD_F(0x07c6df5a) /* 0.486052849 */, 14 }, /* 844 */ { MAD_F(0x07ca059f) /* 0.486821768 */, 14 }, /* 845 */ { MAD_F(0x07cd2c36) /* 0.487590991 */, 14 }, /* 846 */ { MAD_F(0x07d0531e) /* 0.488360517 */, 14 }, /* 847 */ { MAD_F(0x07d37a57) /* 0.489130346 */, 14 }, /* 848 */ { MAD_F(0x07d6a1e2) /* 0.489900479 */, 14 }, /* 849 */ { MAD_F(0x07d9c9be) /* 0.490670914 */, 14 }, /* 850 */ { MAD_F(0x07dcf1ec) /* 0.491441651 */, 14 }, /* 851 */ { MAD_F(0x07e01a6a) /* 0.492212691 */, 14 }, /* 852 */ { MAD_F(0x07e3433a) /* 0.492984033 */, 14 }, /* 853 */ { MAD_F(0x07e66c5a) /* 0.493755677 */, 14 }, /* 854 */ { MAD_F(0x07e995cc) /* 0.494527623 */, 14 }, /* 855 */ { MAD_F(0x07ecbf8e) /* 0.495299870 */, 14 }, /* 856 */ { MAD_F(0x07efe9a1) /* 0.496072418 */, 14 }, /* 857 */ { MAD_F(0x07f31405) /* 0.496845266 */, 14 }, /* 858 */ { MAD_F(0x07f63eba) /* 0.497618416 */, 14 }, /* 859 */ { MAD_F(0x07f969c0) /* 0.498391866 */, 14 }, /* 860 */ { MAD_F(0x07fc9516) /* 0.499165616 */, 14 }, /* 861 */ { MAD_F(0x07ffc0bc) /* 0.499939666 */, 14 }, /* 862 */ { MAD_F(0x04017659) /* 0.250357008 */, 15 }, /* 863 */ { MAD_F(0x04030c7d) /* 0.250744333 */, 15 }, /* 864 */ { MAD_F(0x0404a2c9) /* 0.251131807 */, 15 }, /* 865 */ { MAD_F(0x0406393d) /* 0.251519431 */, 15 }, /* 866 */ { MAD_F(0x0407cfd9) /* 0.251907204 */, 15 }, /* 867 */ { MAD_F(0x0409669d) /* 0.252295127 */, 15 }, /* 868 */ { MAD_F(0x040afd89) /* 0.252683198 */, 15 }, /* 869 */ { MAD_F(0x040c949e) /* 0.253071419 */, 15 }, /* 870 */ { MAD_F(0x040e2bda) /* 0.253459789 */, 15 }, /* 871 */ { MAD_F(0x040fc33e) /* 0.253848307 */, 15 }, /* 872 */ { MAD_F(0x04115aca) /* 0.254236974 */, 15 }, /* 873 */ { MAD_F(0x0412f27e) /* 0.254625790 */, 15 }, /* 874 */ { MAD_F(0x04148a5a) /* 0.255014755 */, 15 }, /* 875 */ { MAD_F(0x0416225d) /* 0.255403867 */, 15 }, /* 876 */ { MAD_F(0x0417ba89) /* 0.255793128 */, 15 }, /* 877 */ { MAD_F(0x041952dc) /* 0.256182537 */, 15 }, /* 878 */ { MAD_F(0x041aeb57) /* 0.256572095 */, 15 }, /* 879 */ { MAD_F(0x041c83fa) /* 0.256961800 */, 15 }, /* 880 */ { MAD_F(0x041e1cc4) /* 0.257351652 */, 15 }, /* 881 */ { MAD_F(0x041fb5b6) /* 0.257741653 */, 15 }, /* 882 */ { MAD_F(0x04214ed0) /* 0.258131801 */, 15 }, /* 883 */ { MAD_F(0x0422e811) /* 0.258522097 */, 15 }, /* 884 */ { MAD_F(0x04248179) /* 0.258912540 */, 15 }, /* 885 */ { MAD_F(0x04261b0a) /* 0.259303130 */, 15 }, /* 886 */ { MAD_F(0x0427b4c2) /* 0.259693868 */, 15 }, /* 887 */ { MAD_F(0x04294ea1) /* 0.260084752 */, 15 }, /* 888 */ { MAD_F(0x042ae8a7) /* 0.260475783 */, 15 }, /* 889 */ { MAD_F(0x042c82d6) /* 0.260866961 */, 15 }, /* 890 */ { MAD_F(0x042e1d2b) /* 0.261258286 */, 15 }, /* 891 */ { MAD_F(0x042fb7a8) /* 0.261649758 */, 15 }, /* 892 */ { MAD_F(0x0431524c) /* 0.262041376 */, 15 }, /* 893 */ { MAD_F(0x0432ed17) /* 0.262433140 */, 15 }, /* 894 */ { MAD_F(0x0434880a) /* 0.262825051 */, 15 }, /* 895 */ { MAD_F(0x04362324) /* 0.263217107 */, 15 }, /* 896 */ { MAD_F(0x0437be65) /* 0.263609310 */, 15 }, /* 897 */ { MAD_F(0x043959cd) /* 0.264001659 */, 15 }, /* 898 */ { MAD_F(0x043af55d) /* 0.264394153 */, 15 }, /* 899 */ { MAD_F(0x043c9113) /* 0.264786794 */, 15 }, /* 900 */ { MAD_F(0x043e2cf1) /* 0.265179580 */, 15 }, /* 901 */ { MAD_F(0x043fc8f6) /* 0.265572511 */, 15 }, /* 902 */ { MAD_F(0x04416522) /* 0.265965588 */, 15 }, /* 903 */ { MAD_F(0x04430174) /* 0.266358810 */, 15 }, /* 904 */ { MAD_F(0x04449dee) /* 0.266752177 */, 15 }, /* 905 */ { MAD_F(0x04463a8f) /* 0.267145689 */, 15 }, /* 906 */ { MAD_F(0x0447d756) /* 0.267539347 */, 15 }, /* 907 */ { MAD_F(0x04497445) /* 0.267933149 */, 15 }, /* 908 */ { MAD_F(0x044b115a) /* 0.268327096 */, 15 }, /* 909 */ { MAD_F(0x044cae96) /* 0.268721187 */, 15 }, /* 910 */ { MAD_F(0x044e4bf9) /* 0.269115423 */, 15 }, /* 911 */ { MAD_F(0x044fe983) /* 0.269509804 */, 15 }, /* 912 */ { MAD_F(0x04518733) /* 0.269904329 */, 15 }, /* 913 */ { MAD_F(0x0453250a) /* 0.270298998 */, 15 }, /* 914 */ { MAD_F(0x0454c308) /* 0.270693811 */, 15 }, /* 915 */ { MAD_F(0x0456612d) /* 0.271088768 */, 15 }, /* 916 */ { MAD_F(0x0457ff78) /* 0.271483869 */, 15 }, /* 917 */ { MAD_F(0x04599dea) /* 0.271879114 */, 15 }, /* 918 */ { MAD_F(0x045b3c82) /* 0.272274503 */, 15 }, /* 919 */ { MAD_F(0x045cdb41) /* 0.272670035 */, 15 }, /* 920 */ { MAD_F(0x045e7a26) /* 0.273065710 */, 15 }, /* 921 */ { MAD_F(0x04601932) /* 0.273461530 */, 15 }, /* 922 */ { MAD_F(0x0461b864) /* 0.273857492 */, 15 }, /* 923 */ { MAD_F(0x046357bd) /* 0.274253597 */, 15 }, /* 924 */ { MAD_F(0x0464f73c) /* 0.274649846 */, 15 }, /* 925 */ { MAD_F(0x046696e2) /* 0.275046238 */, 15 }, /* 926 */ { MAD_F(0x046836ae) /* 0.275442772 */, 15 }, /* 927 */ { MAD_F(0x0469d6a0) /* 0.275839449 */, 15 }, /* 928 */ { MAD_F(0x046b76b9) /* 0.276236269 */, 15 }, /* 929 */ { MAD_F(0x046d16f7) /* 0.276633232 */, 15 }, /* 930 */ { MAD_F(0x046eb75c) /* 0.277030337 */, 15 }, /* 931 */ { MAD_F(0x047057e8) /* 0.277427584 */, 15 }, /* 932 */ { MAD_F(0x0471f899) /* 0.277824973 */, 15 }, /* 933 */ { MAD_F(0x04739971) /* 0.278222505 */, 15 }, /* 934 */ { MAD_F(0x04753a6f) /* 0.278620179 */, 15 }, /* 935 */ { MAD_F(0x0476db92) /* 0.279017995 */, 15 }, /* 936 */ { MAD_F(0x04787cdc) /* 0.279415952 */, 15 }, /* 937 */ { MAD_F(0x047a1e4c) /* 0.279814051 */, 15 }, /* 938 */ { MAD_F(0x047bbfe2) /* 0.280212292 */, 15 }, /* 939 */ { MAD_F(0x047d619e) /* 0.280610675 */, 15 }, /* 940 */ { MAD_F(0x047f0380) /* 0.281009199 */, 15 }, /* 941 */ { MAD_F(0x0480a588) /* 0.281407864 */, 15 }, /* 942 */ { MAD_F(0x048247b6) /* 0.281806670 */, 15 }, /* 943 */ { MAD_F(0x0483ea0a) /* 0.282205618 */, 15 }, /* 944 */ { MAD_F(0x04858c83) /* 0.282604707 */, 15 }, /* 945 */ { MAD_F(0x04872f22) /* 0.283003936 */, 15 }, /* 946 */ { MAD_F(0x0488d1e8) /* 0.283403307 */, 15 }, /* 947 */ { MAD_F(0x048a74d3) /* 0.283802818 */, 15 }, /* 948 */ { MAD_F(0x048c17e3) /* 0.284202470 */, 15 }, /* 949 */ { MAD_F(0x048dbb1a) /* 0.284602263 */, 15 }, /* 950 */ { MAD_F(0x048f5e76) /* 0.285002195 */, 15 }, /* 951 */ { MAD_F(0x049101f8) /* 0.285402269 */, 15 }, /* 952 */ { MAD_F(0x0492a59f) /* 0.285802482 */, 15 }, /* 953 */ { MAD_F(0x0494496c) /* 0.286202836 */, 15 }, /* 954 */ { MAD_F(0x0495ed5f) /* 0.286603329 */, 15 }, /* 955 */ { MAD_F(0x04979177) /* 0.287003963 */, 15 }, /* 956 */ { MAD_F(0x049935b5) /* 0.287404737 */, 15 }, /* 957 */ { MAD_F(0x049ada19) /* 0.287805650 */, 15 }, /* 958 */ { MAD_F(0x049c7ea1) /* 0.288206703 */, 15 }, /* 959 */ { MAD_F(0x049e2350) /* 0.288607895 */, 15 }, /* 960 */ { MAD_F(0x049fc824) /* 0.289009227 */, 15 }, /* 961 */ { MAD_F(0x04a16d1d) /* 0.289410699 */, 15 }, /* 962 */ { MAD_F(0x04a3123b) /* 0.289812309 */, 15 }, /* 963 */ { MAD_F(0x04a4b77f) /* 0.290214059 */, 15 }, /* 964 */ { MAD_F(0x04a65ce8) /* 0.290615948 */, 15 }, /* 965 */ { MAD_F(0x04a80277) /* 0.291017976 */, 15 }, /* 966 */ { MAD_F(0x04a9a82b) /* 0.291420143 */, 15 }, /* 967 */ { MAD_F(0x04ab4e04) /* 0.291822449 */, 15 }, /* 968 */ { MAD_F(0x04acf402) /* 0.292224893 */, 15 }, /* 969 */ { MAD_F(0x04ae9a26) /* 0.292627476 */, 15 }, /* 970 */ { MAD_F(0x04b0406e) /* 0.293030197 */, 15 }, /* 971 */ { MAD_F(0x04b1e6dc) /* 0.293433057 */, 15 }, /* 972 */ { MAD_F(0x04b38d6f) /* 0.293836055 */, 15 }, /* 973 */ { MAD_F(0x04b53427) /* 0.294239192 */, 15 }, /* 974 */ { MAD_F(0x04b6db05) /* 0.294642466 */, 15 }, /* 975 */ { MAD_F(0x04b88207) /* 0.295045879 */, 15 }, /* 976 */ { MAD_F(0x04ba292e) /* 0.295449429 */, 15 }, /* 977 */ { MAD_F(0x04bbd07a) /* 0.295853118 */, 15 }, /* 978 */ { MAD_F(0x04bd77ec) /* 0.296256944 */, 15 }, /* 979 */ { MAD_F(0x04bf1f82) /* 0.296660907 */, 15 }, /* 980 */ { MAD_F(0x04c0c73d) /* 0.297065009 */, 15 }, /* 981 */ { MAD_F(0x04c26f1d) /* 0.297469248 */, 15 }, /* 982 */ { MAD_F(0x04c41722) /* 0.297873624 */, 15 }, /* 983 */ { MAD_F(0x04c5bf4c) /* 0.298278137 */, 15 }, /* 984 */ { MAD_F(0x04c7679a) /* 0.298682788 */, 15 }, /* 985 */ { MAD_F(0x04c9100d) /* 0.299087576 */, 15 }, /* 986 */ { MAD_F(0x04cab8a6) /* 0.299492500 */, 15 }, /* 987 */ { MAD_F(0x04cc6163) /* 0.299897562 */, 15 }, /* 988 */ { MAD_F(0x04ce0a44) /* 0.300302761 */, 15 }, /* 989 */ { MAD_F(0x04cfb34b) /* 0.300708096 */, 15 }, /* 990 */ { MAD_F(0x04d15c76) /* 0.301113568 */, 15 }, /* 991 */ { MAD_F(0x04d305c5) /* 0.301519176 */, 15 }, /* 992 */ { MAD_F(0x04d4af3a) /* 0.301924921 */, 15 }, /* 993 */ { MAD_F(0x04d658d2) /* 0.302330802 */, 15 }, /* 994 */ { MAD_F(0x04d80290) /* 0.302736820 */, 15 }, /* 995 */ { MAD_F(0x04d9ac72) /* 0.303142973 */, 15 }, /* 996 */ { MAD_F(0x04db5679) /* 0.303549263 */, 15 }, /* 997 */ { MAD_F(0x04dd00a4) /* 0.303955689 */, 15 }, /* 998 */ { MAD_F(0x04deaaf3) /* 0.304362251 */, 15 }, /* 999 */ { MAD_F(0x04e05567) /* 0.304768948 */, 15 }, /* 1000 */ { MAD_F(0x04e20000) /* 0.305175781 */, 15 }, /* 1001 */ { MAD_F(0x04e3aabd) /* 0.305582750 */, 15 }, /* 1002 */ { MAD_F(0x04e5559e) /* 0.305989854 */, 15 }, /* 1003 */ { MAD_F(0x04e700a3) /* 0.306397094 */, 15 }, /* 1004 */ { MAD_F(0x04e8abcd) /* 0.306804470 */, 15 }, /* 1005 */ { MAD_F(0x04ea571c) /* 0.307211980 */, 15 }, /* 1006 */ { MAD_F(0x04ec028e) /* 0.307619626 */, 15 }, /* 1007 */ { MAD_F(0x04edae25) /* 0.308027406 */, 15 }, /* 1008 */ { MAD_F(0x04ef59e0) /* 0.308435322 */, 15 }, /* 1009 */ { MAD_F(0x04f105bf) /* 0.308843373 */, 15 }, /* 1010 */ { MAD_F(0x04f2b1c3) /* 0.309251558 */, 15 }, /* 1011 */ { MAD_F(0x04f45dea) /* 0.309659879 */, 15 }, /* 1012 */ { MAD_F(0x04f60a36) /* 0.310068333 */, 15 }, /* 1013 */ { MAD_F(0x04f7b6a6) /* 0.310476923 */, 15 }, /* 1014 */ { MAD_F(0x04f9633a) /* 0.310885647 */, 15 }, /* 1015 */ { MAD_F(0x04fb0ff2) /* 0.311294505 */, 15 }, /* 1016 */ { MAD_F(0x04fcbcce) /* 0.311703498 */, 15 }, /* 1017 */ { MAD_F(0x04fe69ce) /* 0.312112625 */, 15 }, /* 1018 */ { MAD_F(0x050016f3) /* 0.312521885 */, 15 }, /* 1019 */ { MAD_F(0x0501c43b) /* 0.312931280 */, 15 }, /* 1020 */ { MAD_F(0x050371a7) /* 0.313340809 */, 15 }, /* 1021 */ { MAD_F(0x05051f37) /* 0.313750472 */, 15 }, /* 1022 */ { MAD_F(0x0506cceb) /* 0.314160269 */, 15 }, /* 1023 */ { MAD_F(0x05087ac2) /* 0.314570199 */, 15 }, /* 1024 */ { MAD_F(0x050a28be) /* 0.314980262 */, 15 }, /* 1025 */ { MAD_F(0x050bd6de) /* 0.315390460 */, 15 }, /* 1026 */ { MAD_F(0x050d8521) /* 0.315800790 */, 15 }, /* 1027 */ { MAD_F(0x050f3388) /* 0.316211255 */, 15 }, /* 1028 */ { MAD_F(0x0510e213) /* 0.316621852 */, 15 }, /* 1029 */ { MAD_F(0x051290c2) /* 0.317032582 */, 15 }, /* 1030 */ { MAD_F(0x05143f94) /* 0.317443446 */, 15 }, /* 1031 */ { MAD_F(0x0515ee8a) /* 0.317854442 */, 15 }, /* 1032 */ { MAD_F(0x05179da4) /* 0.318265572 */, 15 }, /* 1033 */ { MAD_F(0x05194ce1) /* 0.318676834 */, 15 }, /* 1034 */ { MAD_F(0x051afc42) /* 0.319088229 */, 15 }, /* 1035 */ { MAD_F(0x051cabc7) /* 0.319499756 */, 15 }, /* 1036 */ { MAD_F(0x051e5b6f) /* 0.319911417 */, 15 }, /* 1037 */ { MAD_F(0x05200b3a) /* 0.320323209 */, 15 }, /* 1038 */ { MAD_F(0x0521bb2a) /* 0.320735134 */, 15 }, /* 1039 */ { MAD_F(0x05236b3d) /* 0.321147192 */, 15 }, /* 1040 */ { MAD_F(0x05251b73) /* 0.321559381 */, 15 }, /* 1041 */ { MAD_F(0x0526cbcd) /* 0.321971703 */, 15 }, /* 1042 */ { MAD_F(0x05287c4a) /* 0.322384156 */, 15 }, /* 1043 */ { MAD_F(0x052a2cea) /* 0.322796742 */, 15 }, /* 1044 */ { MAD_F(0x052bddae) /* 0.323209460 */, 15 }, /* 1045 */ { MAD_F(0x052d8e96) /* 0.323622309 */, 15 }, /* 1046 */ { MAD_F(0x052f3fa1) /* 0.324035290 */, 15 }, /* 1047 */ { MAD_F(0x0530f0cf) /* 0.324448403 */, 15 }, /* 1048 */ { MAD_F(0x0532a220) /* 0.324861647 */, 15 }, /* 1049 */ { MAD_F(0x05345395) /* 0.325275023 */, 15 }, /* 1050 */ { MAD_F(0x0536052d) /* 0.325688530 */, 15 }, /* 1051 */ { MAD_F(0x0537b6e8) /* 0.326102168 */, 15 }, /* 1052 */ { MAD_F(0x053968c6) /* 0.326515938 */, 15 }, /* 1053 */ { MAD_F(0x053b1ac8) /* 0.326929839 */, 15 }, /* 1054 */ { MAD_F(0x053ccced) /* 0.327343870 */, 15 }, /* 1055 */ { MAD_F(0x053e7f35) /* 0.327758033 */, 15 }, /* 1056 */ { MAD_F(0x054031a0) /* 0.328172327 */, 15 }, /* 1057 */ { MAD_F(0x0541e42e) /* 0.328586751 */, 15 }, /* 1058 */ { MAD_F(0x054396df) /* 0.329001306 */, 15 }, /* 1059 */ { MAD_F(0x054549b4) /* 0.329415992 */, 15 }, /* 1060 */ { MAD_F(0x0546fcab) /* 0.329830808 */, 15 }, /* 1061 */ { MAD_F(0x0548afc6) /* 0.330245755 */, 15 }, /* 1062 */ { MAD_F(0x054a6303) /* 0.330660832 */, 15 }, /* 1063 */ { MAD_F(0x054c1663) /* 0.331076039 */, 15 }, /* 1064 */ { MAD_F(0x054dc9e7) /* 0.331491377 */, 15 }, /* 1065 */ { MAD_F(0x054f7d8d) /* 0.331906845 */, 15 }, /* 1066 */ { MAD_F(0x05513156) /* 0.332322443 */, 15 }, /* 1067 */ { MAD_F(0x0552e542) /* 0.332738170 */, 15 }, /* 1068 */ { MAD_F(0x05549951) /* 0.333154028 */, 15 }, /* 1069 */ { MAD_F(0x05564d83) /* 0.333570016 */, 15 }, /* 1070 */ { MAD_F(0x055801d8) /* 0.333986133 */, 15 }, /* 1071 */ { MAD_F(0x0559b64f) /* 0.334402380 */, 15 }, /* 1072 */ { MAD_F(0x055b6ae9) /* 0.334818756 */, 15 }, /* 1073 */ { MAD_F(0x055d1fa6) /* 0.335235262 */, 15 }, /* 1074 */ { MAD_F(0x055ed486) /* 0.335651898 */, 15 }, /* 1075 */ { MAD_F(0x05608988) /* 0.336068662 */, 15 }, /* 1076 */ { MAD_F(0x05623ead) /* 0.336485556 */, 15 }, /* 1077 */ { MAD_F(0x0563f3f5) /* 0.336902579 */, 15 }, /* 1078 */ { MAD_F(0x0565a960) /* 0.337319732 */, 15 }, /* 1079 */ { MAD_F(0x05675eed) /* 0.337737013 */, 15 }, /* 1080 */ { MAD_F(0x0569149c) /* 0.338154423 */, 15 }, /* 1081 */ { MAD_F(0x056aca6f) /* 0.338571962 */, 15 }, /* 1082 */ { MAD_F(0x056c8064) /* 0.338989630 */, 15 }, /* 1083 */ { MAD_F(0x056e367b) /* 0.339407426 */, 15 }, /* 1084 */ { MAD_F(0x056fecb5) /* 0.339825351 */, 15 }, /* 1085 */ { MAD_F(0x0571a311) /* 0.340243405 */, 15 }, /* 1086 */ { MAD_F(0x05735990) /* 0.340661587 */, 15 }, /* 1087 */ { MAD_F(0x05751032) /* 0.341079898 */, 15 }, /* 1088 */ { MAD_F(0x0576c6f5) /* 0.341498336 */, 15 }, /* 1089 */ { MAD_F(0x05787ddc) /* 0.341916903 */, 15 }, /* 1090 */ { MAD_F(0x057a34e4) /* 0.342335598 */, 15 }, /* 1091 */ { MAD_F(0x057bec0f) /* 0.342754421 */, 15 }, /* 1092 */ { MAD_F(0x057da35d) /* 0.343173373 */, 15 }, /* 1093 */ { MAD_F(0x057f5acc) /* 0.343592452 */, 15 }, /* 1094 */ { MAD_F(0x0581125e) /* 0.344011659 */, 15 }, /* 1095 */ { MAD_F(0x0582ca12) /* 0.344430993 */, 15 }, /* 1096 */ { MAD_F(0x058481e9) /* 0.344850455 */, 15 }, /* 1097 */ { MAD_F(0x058639e2) /* 0.345270045 */, 15 }, /* 1098 */ { MAD_F(0x0587f1fd) /* 0.345689763 */, 15 }, /* 1099 */ { MAD_F(0x0589aa3a) /* 0.346109608 */, 15 }, /* 1100 */ { MAD_F(0x058b629a) /* 0.346529580 */, 15 }, /* 1101 */ { MAD_F(0x058d1b1b) /* 0.346949679 */, 15 }, /* 1102 */ { MAD_F(0x058ed3bf) /* 0.347369906 */, 15 }, /* 1103 */ { MAD_F(0x05908c85) /* 0.347790260 */, 15 }, /* 1104 */ { MAD_F(0x0592456d) /* 0.348210741 */, 15 }, /* 1105 */ { MAD_F(0x0593fe77) /* 0.348631348 */, 15 }, /* 1106 */ { MAD_F(0x0595b7a3) /* 0.349052083 */, 15 }, /* 1107 */ { MAD_F(0x059770f1) /* 0.349472945 */, 15 }, /* 1108 */ { MAD_F(0x05992a61) /* 0.349893933 */, 15 }, /* 1109 */ { MAD_F(0x059ae3f3) /* 0.350315048 */, 15 }, /* 1110 */ { MAD_F(0x059c9da8) /* 0.350736290 */, 15 }, /* 1111 */ { MAD_F(0x059e577e) /* 0.351157658 */, 15 }, /* 1112 */ { MAD_F(0x05a01176) /* 0.351579152 */, 15 }, /* 1113 */ { MAD_F(0x05a1cb90) /* 0.352000773 */, 15 }, /* 1114 */ { MAD_F(0x05a385cc) /* 0.352422520 */, 15 }, /* 1115 */ { MAD_F(0x05a5402a) /* 0.352844394 */, 15 }, /* 1116 */ { MAD_F(0x05a6faa9) /* 0.353266393 */, 15 }, /* 1117 */ { MAD_F(0x05a8b54b) /* 0.353688519 */, 15 }, /* 1118 */ { MAD_F(0x05aa700e) /* 0.354110771 */, 15 }, /* 1119 */ { MAD_F(0x05ac2af3) /* 0.354533148 */, 15 }, /* 1120 */ { MAD_F(0x05ade5fa) /* 0.354955651 */, 15 }, /* 1121 */ { MAD_F(0x05afa123) /* 0.355378281 */, 15 }, /* 1122 */ { MAD_F(0x05b15c6d) /* 0.355801035 */, 15 }, /* 1123 */ { MAD_F(0x05b317d9) /* 0.356223916 */, 15 }, /* 1124 */ { MAD_F(0x05b4d367) /* 0.356646922 */, 15 }, /* 1125 */ { MAD_F(0x05b68f16) /* 0.357070053 */, 15 }, /* 1126 */ { MAD_F(0x05b84ae7) /* 0.357493310 */, 15 }, /* 1127 */ { MAD_F(0x05ba06da) /* 0.357916692 */, 15 }, /* 1128 */ { MAD_F(0x05bbc2ef) /* 0.358340200 */, 15 }, /* 1129 */ { MAD_F(0x05bd7f25) /* 0.358763832 */, 15 }, /* 1130 */ { MAD_F(0x05bf3b7c) /* 0.359187590 */, 15 }, /* 1131 */ { MAD_F(0x05c0f7f5) /* 0.359611472 */, 15 }, /* 1132 */ { MAD_F(0x05c2b490) /* 0.360035480 */, 15 }, /* 1133 */ { MAD_F(0x05c4714c) /* 0.360459613 */, 15 }, /* 1134 */ { MAD_F(0x05c62e2a) /* 0.360883870 */, 15 }, /* 1135 */ { MAD_F(0x05c7eb29) /* 0.361308252 */, 15 }, /* 1136 */ { MAD_F(0x05c9a84a) /* 0.361732758 */, 15 }, /* 1137 */ { MAD_F(0x05cb658c) /* 0.362157390 */, 15 }, /* 1138 */ { MAD_F(0x05cd22ef) /* 0.362582145 */, 15 }, /* 1139 */ { MAD_F(0x05cee074) /* 0.363007026 */, 15 }, /* 1140 */ { MAD_F(0x05d09e1b) /* 0.363432030 */, 15 }, /* 1141 */ { MAD_F(0x05d25be2) /* 0.363857159 */, 15 }, /* 1142 */ { MAD_F(0x05d419cb) /* 0.364282412 */, 15 }, /* 1143 */ { MAD_F(0x05d5d7d5) /* 0.364707789 */, 15 }, /* 1144 */ { MAD_F(0x05d79601) /* 0.365133291 */, 15 }, /* 1145 */ { MAD_F(0x05d9544e) /* 0.365558916 */, 15 }, /* 1146 */ { MAD_F(0x05db12bc) /* 0.365984665 */, 15 }, /* 1147 */ { MAD_F(0x05dcd14c) /* 0.366410538 */, 15 }, /* 1148 */ { MAD_F(0x05de8ffc) /* 0.366836535 */, 15 }, /* 1149 */ { MAD_F(0x05e04ece) /* 0.367262655 */, 15 }, /* 1150 */ { MAD_F(0x05e20dc1) /* 0.367688900 */, 15 }, /* 1151 */ { MAD_F(0x05e3ccd5) /* 0.368115267 */, 15 }, /* 1152 */ { MAD_F(0x05e58c0b) /* 0.368541759 */, 15 }, /* 1153 */ { MAD_F(0x05e74b61) /* 0.368968373 */, 15 }, /* 1154 */ { MAD_F(0x05e90ad9) /* 0.369395111 */, 15 }, /* 1155 */ { MAD_F(0x05eaca72) /* 0.369821973 */, 15 }, /* 1156 */ { MAD_F(0x05ec8a2b) /* 0.370248957 */, 15 }, /* 1157 */ { MAD_F(0x05ee4a06) /* 0.370676065 */, 15 }, /* 1158 */ { MAD_F(0x05f00a02) /* 0.371103295 */, 15 }, /* 1159 */ { MAD_F(0x05f1ca1f) /* 0.371530649 */, 15 }, /* 1160 */ { MAD_F(0x05f38a5d) /* 0.371958126 */, 15 }, /* 1161 */ { MAD_F(0x05f54abc) /* 0.372385725 */, 15 }, /* 1162 */ { MAD_F(0x05f70b3c) /* 0.372813448 */, 15 }, /* 1163 */ { MAD_F(0x05f8cbdc) /* 0.373241292 */, 15 }, /* 1164 */ { MAD_F(0x05fa8c9e) /* 0.373669260 */, 15 }, /* 1165 */ { MAD_F(0x05fc4d81) /* 0.374097350 */, 15 }, /* 1166 */ { MAD_F(0x05fe0e84) /* 0.374525563 */, 15 }, /* 1167 */ { MAD_F(0x05ffcfa8) /* 0.374953898 */, 15 }, /* 1168 */ { MAD_F(0x060190ee) /* 0.375382356 */, 15 }, /* 1169 */ { MAD_F(0x06035254) /* 0.375810936 */, 15 }, /* 1170 */ { MAD_F(0x060513da) /* 0.376239638 */, 15 }, /* 1171 */ { MAD_F(0x0606d582) /* 0.376668462 */, 15 }, /* 1172 */ { MAD_F(0x0608974a) /* 0.377097408 */, 15 }, /* 1173 */ { MAD_F(0x060a5934) /* 0.377526476 */, 15 }, /* 1174 */ { MAD_F(0x060c1b3d) /* 0.377955667 */, 15 }, /* 1175 */ { MAD_F(0x060ddd68) /* 0.378384979 */, 15 }, /* 1176 */ { MAD_F(0x060f9fb3) /* 0.378814413 */, 15 }, /* 1177 */ { MAD_F(0x0611621f) /* 0.379243968 */, 15 }, /* 1178 */ { MAD_F(0x061324ac) /* 0.379673646 */, 15 }, /* 1179 */ { MAD_F(0x0614e759) /* 0.380103444 */, 15 }, /* 1180 */ { MAD_F(0x0616aa27) /* 0.380533365 */, 15 }, /* 1181 */ { MAD_F(0x06186d16) /* 0.380963407 */, 15 }, /* 1182 */ { MAD_F(0x061a3025) /* 0.381393570 */, 15 }, /* 1183 */ { MAD_F(0x061bf354) /* 0.381823855 */, 15 }, /* 1184 */ { MAD_F(0x061db6a5) /* 0.382254261 */, 15 }, /* 1185 */ { MAD_F(0x061f7a15) /* 0.382684788 */, 15 }, /* 1186 */ { MAD_F(0x06213da7) /* 0.383115436 */, 15 }, /* 1187 */ { MAD_F(0x06230158) /* 0.383546205 */, 15 }, /* 1188 */ { MAD_F(0x0624c52a) /* 0.383977096 */, 15 }, /* 1189 */ { MAD_F(0x0626891d) /* 0.384408107 */, 15 }, /* 1190 */ { MAD_F(0x06284d30) /* 0.384839239 */, 15 }, /* 1191 */ { MAD_F(0x062a1164) /* 0.385270492 */, 15 }, /* 1192 */ { MAD_F(0x062bd5b8) /* 0.385701865 */, 15 }, /* 1193 */ { MAD_F(0x062d9a2c) /* 0.386133359 */, 15 }, /* 1194 */ { MAD_F(0x062f5ec1) /* 0.386564974 */, 15 }, /* 1195 */ { MAD_F(0x06312376) /* 0.386996709 */, 15 }, /* 1196 */ { MAD_F(0x0632e84b) /* 0.387428565 */, 15 }, /* 1197 */ { MAD_F(0x0634ad41) /* 0.387860541 */, 15 }, /* 1198 */ { MAD_F(0x06367257) /* 0.388292637 */, 15 }, /* 1199 */ { MAD_F(0x0638378d) /* 0.388724854 */, 15 }, /* 1200 */ { MAD_F(0x0639fce4) /* 0.389157191 */, 15 }, /* 1201 */ { MAD_F(0x063bc25b) /* 0.389589648 */, 15 }, /* 1202 */ { MAD_F(0x063d87f2) /* 0.390022225 */, 15 }, /* 1203 */ { MAD_F(0x063f4da9) /* 0.390454922 */, 15 }, /* 1204 */ { MAD_F(0x06411380) /* 0.390887739 */, 15 }, /* 1205 */ { MAD_F(0x0642d978) /* 0.391320675 */, 15 }, /* 1206 */ { MAD_F(0x06449f8f) /* 0.391753732 */, 15 }, /* 1207 */ { MAD_F(0x064665c7) /* 0.392186908 */, 15 }, /* 1208 */ { MAD_F(0x06482c1f) /* 0.392620204 */, 15 }, /* 1209 */ { MAD_F(0x0649f297) /* 0.393053619 */, 15 }, /* 1210 */ { MAD_F(0x064bb92f) /* 0.393487154 */, 15 }, /* 1211 */ { MAD_F(0x064d7fe8) /* 0.393920808 */, 15 }, /* 1212 */ { MAD_F(0x064f46c0) /* 0.394354582 */, 15 }, /* 1213 */ { MAD_F(0x06510db8) /* 0.394788475 */, 15 }, /* 1214 */ { MAD_F(0x0652d4d0) /* 0.395222488 */, 15 }, /* 1215 */ { MAD_F(0x06549c09) /* 0.395656619 */, 15 }, /* 1216 */ { MAD_F(0x06566361) /* 0.396090870 */, 15 }, /* 1217 */ { MAD_F(0x06582ad9) /* 0.396525239 */, 15 }, /* 1218 */ { MAD_F(0x0659f271) /* 0.396959728 */, 15 }, /* 1219 */ { MAD_F(0x065bba29) /* 0.397394336 */, 15 }, /* 1220 */ { MAD_F(0x065d8201) /* 0.397829062 */, 15 }, /* 1221 */ { MAD_F(0x065f49f9) /* 0.398263907 */, 15 }, /* 1222 */ { MAD_F(0x06611211) /* 0.398698871 */, 15 }, /* 1223 */ { MAD_F(0x0662da49) /* 0.399133954 */, 15 }, /* 1224 */ { MAD_F(0x0664a2a0) /* 0.399569155 */, 15 }, /* 1225 */ { MAD_F(0x06666b17) /* 0.400004475 */, 15 }, /* 1226 */ { MAD_F(0x066833ae) /* 0.400439913 */, 15 }, /* 1227 */ { MAD_F(0x0669fc65) /* 0.400875470 */, 15 }, /* 1228 */ { MAD_F(0x066bc53c) /* 0.401311145 */, 15 }, /* 1229 */ { MAD_F(0x066d8e32) /* 0.401746938 */, 15 }, /* 1230 */ { MAD_F(0x066f5748) /* 0.402182850 */, 15 }, /* 1231 */ { MAD_F(0x0671207e) /* 0.402618879 */, 15 }, /* 1232 */ { MAD_F(0x0672e9d4) /* 0.403055027 */, 15 }, /* 1233 */ { MAD_F(0x0674b349) /* 0.403491293 */, 15 }, /* 1234 */ { MAD_F(0x06767cde) /* 0.403927676 */, 15 }, /* 1235 */ { MAD_F(0x06784692) /* 0.404364178 */, 15 }, /* 1236 */ { MAD_F(0x067a1066) /* 0.404800797 */, 15 }, /* 1237 */ { MAD_F(0x067bda5a) /* 0.405237535 */, 15 }, /* 1238 */ { MAD_F(0x067da46d) /* 0.405674390 */, 15 }, /* 1239 */ { MAD_F(0x067f6ea0) /* 0.406111362 */, 15 }, /* 1240 */ { MAD_F(0x068138f3) /* 0.406548452 */, 15 }, /* 1241 */ { MAD_F(0x06830365) /* 0.406985660 */, 15 }, /* 1242 */ { MAD_F(0x0684cdf6) /* 0.407422985 */, 15 }, /* 1243 */ { MAD_F(0x068698a8) /* 0.407860427 */, 15 }, /* 1244 */ { MAD_F(0x06886378) /* 0.408297987 */, 15 }, /* 1245 */ { MAD_F(0x068a2e68) /* 0.408735664 */, 15 }, /* 1246 */ { MAD_F(0x068bf978) /* 0.409173458 */, 15 }, /* 1247 */ { MAD_F(0x068dc4a7) /* 0.409611370 */, 15 }, /* 1248 */ { MAD_F(0x068f8ff5) /* 0.410049398 */, 15 }, /* 1249 */ { MAD_F(0x06915b63) /* 0.410487544 */, 15 }, /* 1250 */ { MAD_F(0x069326f0) /* 0.410925806 */, 15 }, /* 1251 */ { MAD_F(0x0694f29c) /* 0.411364185 */, 15 }, /* 1252 */ { MAD_F(0x0696be68) /* 0.411802681 */, 15 }, /* 1253 */ { MAD_F(0x06988a54) /* 0.412241294 */, 15 }, /* 1254 */ { MAD_F(0x069a565e) /* 0.412680024 */, 15 }, /* 1255 */ { MAD_F(0x069c2288) /* 0.413118870 */, 15 }, /* 1256 */ { MAD_F(0x069deed1) /* 0.413557833 */, 15 }, /* 1257 */ { MAD_F(0x069fbb3a) /* 0.413996912 */, 15 }, /* 1258 */ { MAD_F(0x06a187c1) /* 0.414436108 */, 15 }, /* 1259 */ { MAD_F(0x06a35468) /* 0.414875420 */, 15 }, /* 1260 */ { MAD_F(0x06a5212f) /* 0.415314849 */, 15 }, /* 1261 */ { MAD_F(0x06a6ee14) /* 0.415754393 */, 15 }, /* 1262 */ { MAD_F(0x06a8bb18) /* 0.416194054 */, 15 }, /* 1263 */ { MAD_F(0x06aa883c) /* 0.416633831 */, 15 }, /* 1264 */ { MAD_F(0x06ac557f) /* 0.417073724 */, 15 }, /* 1265 */ { MAD_F(0x06ae22e1) /* 0.417513734 */, 15 }, /* 1266 */ { MAD_F(0x06aff062) /* 0.417953859 */, 15 }, /* 1267 */ { MAD_F(0x06b1be03) /* 0.418394100 */, 15 }, /* 1268 */ { MAD_F(0x06b38bc2) /* 0.418834457 */, 15 }, /* 1269 */ { MAD_F(0x06b559a1) /* 0.419274929 */, 15 }, /* 1270 */ { MAD_F(0x06b7279e) /* 0.419715518 */, 15 }, /* 1271 */ { MAD_F(0x06b8f5bb) /* 0.420156222 */, 15 }, /* 1272 */ { MAD_F(0x06bac3f6) /* 0.420597041 */, 15 }, /* 1273 */ { MAD_F(0x06bc9251) /* 0.421037977 */, 15 }, /* 1274 */ { MAD_F(0x06be60cb) /* 0.421479027 */, 15 }, /* 1275 */ { MAD_F(0x06c02f63) /* 0.421920193 */, 15 }, /* 1276 */ { MAD_F(0x06c1fe1b) /* 0.422361475 */, 15 }, /* 1277 */ { MAD_F(0x06c3ccf1) /* 0.422802871 */, 15 }, /* 1278 */ { MAD_F(0x06c59be7) /* 0.423244383 */, 15 }, /* 1279 */ { MAD_F(0x06c76afb) /* 0.423686010 */, 15 }, /* 1280 */ { MAD_F(0x06c93a2e) /* 0.424127753 */, 15 }, /* 1281 */ { MAD_F(0x06cb0981) /* 0.424569610 */, 15 }, /* 1282 */ { MAD_F(0x06ccd8f2) /* 0.425011582 */, 15 }, /* 1283 */ { MAD_F(0x06cea881) /* 0.425453669 */, 15 }, /* 1284 */ { MAD_F(0x06d07830) /* 0.425895871 */, 15 }, /* 1285 */ { MAD_F(0x06d247fe) /* 0.426338188 */, 15 }, /* 1286 */ { MAD_F(0x06d417ea) /* 0.426780620 */, 15 }, /* 1287 */ { MAD_F(0x06d5e7f5) /* 0.427223166 */, 15 }, /* 1288 */ { MAD_F(0x06d7b81f) /* 0.427665827 */, 15 }, /* 1289 */ { MAD_F(0x06d98868) /* 0.428108603 */, 15 }, /* 1290 */ { MAD_F(0x06db58cf) /* 0.428551493 */, 15 }, /* 1291 */ { MAD_F(0x06dd2955) /* 0.428994497 */, 15 }, /* 1292 */ { MAD_F(0x06def9fa) /* 0.429437616 */, 15 }, /* 1293 */ { MAD_F(0x06e0cabe) /* 0.429880849 */, 15 }, /* 1294 */ { MAD_F(0x06e29ba0) /* 0.430324197 */, 15 }, /* 1295 */ { MAD_F(0x06e46ca1) /* 0.430767659 */, 15 }, /* 1296 */ { MAD_F(0x06e63dc0) /* 0.431211234 */, 15 }, /* 1297 */ { MAD_F(0x06e80efe) /* 0.431654924 */, 15 }, /* 1298 */ { MAD_F(0x06e9e05b) /* 0.432098728 */, 15 }, /* 1299 */ { MAD_F(0x06ebb1d6) /* 0.432542647 */, 15 }, /* 1300 */ { MAD_F(0x06ed8370) /* 0.432986678 */, 15 }, /* 1301 */ { MAD_F(0x06ef5529) /* 0.433430824 */, 15 }, /* 1302 */ { MAD_F(0x06f12700) /* 0.433875084 */, 15 }, /* 1303 */ { MAD_F(0x06f2f8f5) /* 0.434319457 */, 15 }, /* 1304 */ { MAD_F(0x06f4cb09) /* 0.434763944 */, 15 }, /* 1305 */ { MAD_F(0x06f69d3c) /* 0.435208545 */, 15 }, /* 1306 */ { MAD_F(0x06f86f8d) /* 0.435653259 */, 15 }, /* 1307 */ { MAD_F(0x06fa41fd) /* 0.436098087 */, 15 }, /* 1308 */ { MAD_F(0x06fc148b) /* 0.436543029 */, 15 }, /* 1309 */ { MAD_F(0x06fde737) /* 0.436988083 */, 15 }, /* 1310 */ { MAD_F(0x06ffba02) /* 0.437433251 */, 15 }, /* 1311 */ { MAD_F(0x07018ceb) /* 0.437878533 */, 15 }, /* 1312 */ { MAD_F(0x07035ff3) /* 0.438323927 */, 15 }, /* 1313 */ { MAD_F(0x07053319) /* 0.438769435 */, 15 }, /* 1314 */ { MAD_F(0x0707065d) /* 0.439215056 */, 15 }, /* 1315 */ { MAD_F(0x0708d9c0) /* 0.439660790 */, 15 }, /* 1316 */ { MAD_F(0x070aad41) /* 0.440106636 */, 15 }, /* 1317 */ { MAD_F(0x070c80e1) /* 0.440552596 */, 15 }, /* 1318 */ { MAD_F(0x070e549f) /* 0.440998669 */, 15 }, /* 1319 */ { MAD_F(0x0710287b) /* 0.441444855 */, 15 }, /* 1320 */ { MAD_F(0x0711fc75) /* 0.441891153 */, 15 }, /* 1321 */ { MAD_F(0x0713d08d) /* 0.442337564 */, 15 }, /* 1322 */ { MAD_F(0x0715a4c4) /* 0.442784088 */, 15 }, /* 1323 */ { MAD_F(0x07177919) /* 0.443230724 */, 15 }, /* 1324 */ { MAD_F(0x07194d8c) /* 0.443677473 */, 15 }, /* 1325 */ { MAD_F(0x071b221e) /* 0.444124334 */, 15 }, /* 1326 */ { MAD_F(0x071cf6ce) /* 0.444571308 */, 15 }, /* 1327 */ { MAD_F(0x071ecb9b) /* 0.445018394 */, 15 }, /* 1328 */ { MAD_F(0x0720a087) /* 0.445465593 */, 15 }, /* 1329 */ { MAD_F(0x07227591) /* 0.445912903 */, 15 }, /* 1330 */ { MAD_F(0x07244ab9) /* 0.446360326 */, 15 }, /* 1331 */ { MAD_F(0x07262000) /* 0.446807861 */, 15 }, /* 1332 */ { MAD_F(0x0727f564) /* 0.447255509 */, 15 }, /* 1333 */ { MAD_F(0x0729cae7) /* 0.447703268 */, 15 }, /* 1334 */ { MAD_F(0x072ba087) /* 0.448151139 */, 15 }, /* 1335 */ { MAD_F(0x072d7646) /* 0.448599122 */, 15 }, /* 1336 */ { MAD_F(0x072f4c22) /* 0.449047217 */, 15 }, /* 1337 */ { MAD_F(0x0731221d) /* 0.449495424 */, 15 }, /* 1338 */ { MAD_F(0x0732f835) /* 0.449943742 */, 15 }, /* 1339 */ { MAD_F(0x0734ce6c) /* 0.450392173 */, 15 }, /* 1340 */ { MAD_F(0x0736a4c1) /* 0.450840715 */, 15 }, /* 1341 */ { MAD_F(0x07387b33) /* 0.451289368 */, 15 }, /* 1342 */ { MAD_F(0x073a51c4) /* 0.451738133 */, 15 }, /* 1343 */ { MAD_F(0x073c2872) /* 0.452187010 */, 15 }, /* 1344 */ { MAD_F(0x073dff3e) /* 0.452635998 */, 15 }, /* 1345 */ { MAD_F(0x073fd628) /* 0.453085097 */, 15 }, /* 1346 */ { MAD_F(0x0741ad30) /* 0.453534308 */, 15 }, /* 1347 */ { MAD_F(0x07438456) /* 0.453983630 */, 15 }, /* 1348 */ { MAD_F(0x07455b9a) /* 0.454433063 */, 15 }, /* 1349 */ { MAD_F(0x074732fc) /* 0.454882607 */, 15 }, /* 1350 */ { MAD_F(0x07490a7b) /* 0.455332262 */, 15 }, /* 1351 */ { MAD_F(0x074ae218) /* 0.455782029 */, 15 }, /* 1352 */ { MAD_F(0x074cb9d3) /* 0.456231906 */, 15 }, /* 1353 */ { MAD_F(0x074e91ac) /* 0.456681894 */, 15 }, /* 1354 */ { MAD_F(0x075069a3) /* 0.457131993 */, 15 }, /* 1355 */ { MAD_F(0x075241b7) /* 0.457582203 */, 15 }, /* 1356 */ { MAD_F(0x075419e9) /* 0.458032524 */, 15 }, /* 1357 */ { MAD_F(0x0755f239) /* 0.458482956 */, 15 }, /* 1358 */ { MAD_F(0x0757caa7) /* 0.458933498 */, 15 }, /* 1359 */ { MAD_F(0x0759a332) /* 0.459384151 */, 15 }, /* 1360 */ { MAD_F(0x075b7bdb) /* 0.459834914 */, 15 }, /* 1361 */ { MAD_F(0x075d54a1) /* 0.460285788 */, 15 }, /* 1362 */ { MAD_F(0x075f2d85) /* 0.460736772 */, 15 }, /* 1363 */ { MAD_F(0x07610687) /* 0.461187867 */, 15 }, /* 1364 */ { MAD_F(0x0762dfa6) /* 0.461639071 */, 15 }, /* 1365 */ { MAD_F(0x0764b8e3) /* 0.462090387 */, 15 }, /* 1366 */ { MAD_F(0x0766923e) /* 0.462541812 */, 15 }, /* 1367 */ { MAD_F(0x07686bb6) /* 0.462993348 */, 15 }, /* 1368 */ { MAD_F(0x076a454c) /* 0.463444993 */, 15 }, /* 1369 */ { MAD_F(0x076c1eff) /* 0.463896749 */, 15 }, /* 1370 */ { MAD_F(0x076df8d0) /* 0.464348615 */, 15 }, /* 1371 */ { MAD_F(0x076fd2be) /* 0.464800591 */, 15 }, /* 1372 */ { MAD_F(0x0771acca) /* 0.465252676 */, 15 }, /* 1373 */ { MAD_F(0x077386f3) /* 0.465704872 */, 15 }, /* 1374 */ { MAD_F(0x0775613a) /* 0.466157177 */, 15 }, /* 1375 */ { MAD_F(0x07773b9e) /* 0.466609592 */, 15 }, /* 1376 */ { MAD_F(0x07791620) /* 0.467062117 */, 15 }, /* 1377 */ { MAD_F(0x077af0bf) /* 0.467514751 */, 15 }, /* 1378 */ { MAD_F(0x077ccb7c) /* 0.467967495 */, 15 }, /* 1379 */ { MAD_F(0x077ea656) /* 0.468420349 */, 15 }, /* 1380 */ { MAD_F(0x0780814d) /* 0.468873312 */, 15 }, /* 1381 */ { MAD_F(0x07825c62) /* 0.469326384 */, 15 }, /* 1382 */ { MAD_F(0x07843794) /* 0.469779566 */, 15 }, /* 1383 */ { MAD_F(0x078612e3) /* 0.470232857 */, 15 }, /* 1384 */ { MAD_F(0x0787ee50) /* 0.470686258 */, 15 }, /* 1385 */ { MAD_F(0x0789c9da) /* 0.471139767 */, 15 }, /* 1386 */ { MAD_F(0x078ba581) /* 0.471593386 */, 15 }, /* 1387 */ { MAD_F(0x078d8146) /* 0.472047114 */, 15 }, /* 1388 */ { MAD_F(0x078f5d28) /* 0.472500951 */, 15 }, /* 1389 */ { MAD_F(0x07913927) /* 0.472954896 */, 15 }, /* 1390 */ { MAD_F(0x07931543) /* 0.473408951 */, 15 }, /* 1391 */ { MAD_F(0x0794f17d) /* 0.473863115 */, 15 }, /* 1392 */ { MAD_F(0x0796cdd4) /* 0.474317388 */, 15 }, /* 1393 */ { MAD_F(0x0798aa48) /* 0.474771769 */, 15 }, /* 1394 */ { MAD_F(0x079a86d9) /* 0.475226259 */, 15 }, /* 1395 */ { MAD_F(0x079c6388) /* 0.475680858 */, 15 }, /* 1396 */ { MAD_F(0x079e4053) /* 0.476135565 */, 15 }, /* 1397 */ { MAD_F(0x07a01d3c) /* 0.476590381 */, 15 }, /* 1398 */ { MAD_F(0x07a1fa42) /* 0.477045306 */, 15 }, /* 1399 */ { MAD_F(0x07a3d765) /* 0.477500339 */, 15 }, /* 1400 */ { MAD_F(0x07a5b4a5) /* 0.477955481 */, 15 }, /* 1401 */ { MAD_F(0x07a79202) /* 0.478410731 */, 15 }, /* 1402 */ { MAD_F(0x07a96f7d) /* 0.478866089 */, 15 }, /* 1403 */ { MAD_F(0x07ab4d14) /* 0.479321555 */, 15 }, /* 1404 */ { MAD_F(0x07ad2ac8) /* 0.479777130 */, 15 }, /* 1405 */ { MAD_F(0x07af089a) /* 0.480232813 */, 15 }, /* 1406 */ { MAD_F(0x07b0e688) /* 0.480688604 */, 15 }, /* 1407 */ { MAD_F(0x07b2c494) /* 0.481144503 */, 15 }, /* 1408 */ { MAD_F(0x07b4a2bc) /* 0.481600510 */, 15 }, /* 1409 */ { MAD_F(0x07b68102) /* 0.482056625 */, 15 }, /* 1410 */ { MAD_F(0x07b85f64) /* 0.482512848 */, 15 }, /* 1411 */ { MAD_F(0x07ba3de4) /* 0.482969179 */, 15 }, /* 1412 */ { MAD_F(0x07bc1c80) /* 0.483425618 */, 15 }, /* 1413 */ { MAD_F(0x07bdfb39) /* 0.483882164 */, 15 }, /* 1414 */ { MAD_F(0x07bfda0f) /* 0.484338818 */, 15 }, /* 1415 */ { MAD_F(0x07c1b902) /* 0.484795580 */, 15 }, /* 1416 */ { MAD_F(0x07c39812) /* 0.485252449 */, 15 }, /* 1417 */ { MAD_F(0x07c5773f) /* 0.485709426 */, 15 }, /* 1418 */ { MAD_F(0x07c75689) /* 0.486166511 */, 15 }, /* 1419 */ { MAD_F(0x07c935ef) /* 0.486623703 */, 15 }, /* 1420 */ { MAD_F(0x07cb1573) /* 0.487081002 */, 15 }, /* 1421 */ { MAD_F(0x07ccf513) /* 0.487538409 */, 15 }, /* 1422 */ { MAD_F(0x07ced4d0) /* 0.487995923 */, 15 }, /* 1423 */ { MAD_F(0x07d0b4aa) /* 0.488453544 */, 15 }, /* 1424 */ { MAD_F(0x07d294a0) /* 0.488911273 */, 15 }, /* 1425 */ { MAD_F(0x07d474b3) /* 0.489369108 */, 15 }, /* 1426 */ { MAD_F(0x07d654e4) /* 0.489827051 */, 15 }, /* 1427 */ { MAD_F(0x07d83530) /* 0.490285101 */, 15 }, /* 1428 */ { MAD_F(0x07da159a) /* 0.490743258 */, 15 }, /* 1429 */ { MAD_F(0x07dbf620) /* 0.491201522 */, 15 }, /* 1430 */ { MAD_F(0x07ddd6c3) /* 0.491659892 */, 15 }, /* 1431 */ { MAD_F(0x07dfb783) /* 0.492118370 */, 15 }, /* 1432 */ { MAD_F(0x07e1985f) /* 0.492576954 */, 15 }, /* 1433 */ { MAD_F(0x07e37958) /* 0.493035645 */, 15 }, /* 1434 */ { MAD_F(0x07e55a6e) /* 0.493494443 */, 15 }, /* 1435 */ { MAD_F(0x07e73ba0) /* 0.493953348 */, 15 }, /* 1436 */ { MAD_F(0x07e91cef) /* 0.494412359 */, 15 }, /* 1437 */ { MAD_F(0x07eafe5a) /* 0.494871476 */, 15 }, /* 1438 */ { MAD_F(0x07ecdfe2) /* 0.495330701 */, 15 }, /* 1439 */ { MAD_F(0x07eec187) /* 0.495790031 */, 15 }, /* 1440 */ { MAD_F(0x07f0a348) /* 0.496249468 */, 15 }, /* 1441 */ { MAD_F(0x07f28526) /* 0.496709012 */, 15 }, /* 1442 */ { MAD_F(0x07f46720) /* 0.497168662 */, 15 }, /* 1443 */ { MAD_F(0x07f64937) /* 0.497628418 */, 15 }, /* 1444 */ { MAD_F(0x07f82b6a) /* 0.498088280 */, 15 }, /* 1445 */ { MAD_F(0x07fa0dba) /* 0.498548248 */, 15 }, /* 1446 */ { MAD_F(0x07fbf026) /* 0.499008323 */, 15 }, /* 1447 */ { MAD_F(0x07fdd2af) /* 0.499468503 */, 15 }, /* 1448 */ { MAD_F(0x07ffb554) /* 0.499928790 */, 15 }, /* 1449 */ { MAD_F(0x0400cc0b) /* 0.250194591 */, 16 }, /* 1450 */ { MAD_F(0x0401bd7a) /* 0.250424840 */, 16 }, /* 1451 */ { MAD_F(0x0402aef7) /* 0.250655143 */, 16 }, /* 1452 */ { MAD_F(0x0403a083) /* 0.250885498 */, 16 }, /* 1453 */ { MAD_F(0x0404921c) /* 0.251115906 */, 16 }, /* 1454 */ { MAD_F(0x040583c4) /* 0.251346367 */, 16 }, /* 1455 */ { MAD_F(0x0406757a) /* 0.251576880 */, 16 }, /* 1456 */ { MAD_F(0x0407673f) /* 0.251807447 */, 16 }, /* 1457 */ { MAD_F(0x04085911) /* 0.252038066 */, 16 }, /* 1458 */ { MAD_F(0x04094af1) /* 0.252268738 */, 16 }, /* 1459 */ { MAD_F(0x040a3ce0) /* 0.252499463 */, 16 }, /* 1460 */ { MAD_F(0x040b2edd) /* 0.252730240 */, 16 }, /* 1461 */ { MAD_F(0x040c20e8) /* 0.252961071 */, 16 }, /* 1462 */ { MAD_F(0x040d1301) /* 0.253191953 */, 16 }, /* 1463 */ { MAD_F(0x040e0529) /* 0.253422889 */, 16 }, /* 1464 */ { MAD_F(0x040ef75e) /* 0.253653877 */, 16 }, /* 1465 */ { MAD_F(0x040fe9a1) /* 0.253884918 */, 16 }, /* 1466 */ { MAD_F(0x0410dbf3) /* 0.254116011 */, 16 }, /* 1467 */ { MAD_F(0x0411ce53) /* 0.254347157 */, 16 }, /* 1468 */ { MAD_F(0x0412c0c1) /* 0.254578356 */, 16 }, /* 1469 */ { MAD_F(0x0413b33d) /* 0.254809606 */, 16 }, /* 1470 */ { MAD_F(0x0414a5c7) /* 0.255040910 */, 16 }, /* 1471 */ { MAD_F(0x0415985f) /* 0.255272266 */, 16 }, /* 1472 */ { MAD_F(0x04168b05) /* 0.255503674 */, 16 }, /* 1473 */ { MAD_F(0x04177db9) /* 0.255735135 */, 16 }, /* 1474 */ { MAD_F(0x0418707c) /* 0.255966648 */, 16 }, /* 1475 */ { MAD_F(0x0419634c) /* 0.256198213 */, 16 }, /* 1476 */ { MAD_F(0x041a562a) /* 0.256429831 */, 16 }, /* 1477 */ { MAD_F(0x041b4917) /* 0.256661501 */, 16 }, /* 1478 */ { MAD_F(0x041c3c11) /* 0.256893223 */, 16 }, /* 1479 */ { MAD_F(0x041d2f1a) /* 0.257124998 */, 16 }, /* 1480 */ { MAD_F(0x041e2230) /* 0.257356825 */, 16 }, /* 1481 */ { MAD_F(0x041f1555) /* 0.257588704 */, 16 }, /* 1482 */ { MAD_F(0x04200888) /* 0.257820635 */, 16 }, /* 1483 */ { MAD_F(0x0420fbc8) /* 0.258052619 */, 16 }, /* 1484 */ { MAD_F(0x0421ef17) /* 0.258284654 */, 16 }, /* 1485 */ { MAD_F(0x0422e273) /* 0.258516742 */, 16 }, /* 1486 */ { MAD_F(0x0423d5de) /* 0.258748882 */, 16 }, /* 1487 */ { MAD_F(0x0424c956) /* 0.258981074 */, 16 }, /* 1488 */ { MAD_F(0x0425bcdd) /* 0.259213318 */, 16 }, /* 1489 */ { MAD_F(0x0426b071) /* 0.259445614 */, 16 }, /* 1490 */ { MAD_F(0x0427a414) /* 0.259677962 */, 16 }, /* 1491 */ { MAD_F(0x042897c4) /* 0.259910362 */, 16 }, /* 1492 */ { MAD_F(0x04298b83) /* 0.260142814 */, 16 }, /* 1493 */ { MAD_F(0x042a7f4f) /* 0.260375318 */, 16 }, /* 1494 */ { MAD_F(0x042b7329) /* 0.260607874 */, 16 }, /* 1495 */ { MAD_F(0x042c6711) /* 0.260840481 */, 16 }, /* 1496 */ { MAD_F(0x042d5b07) /* 0.261073141 */, 16 }, /* 1497 */ { MAD_F(0x042e4f0b) /* 0.261305852 */, 16 }, /* 1498 */ { MAD_F(0x042f431d) /* 0.261538616 */, 16 }, /* 1499 */ { MAD_F(0x0430373d) /* 0.261771431 */, 16 }, /* 1500 */ { MAD_F(0x04312b6b) /* 0.262004297 */, 16 }, /* 1501 */ { MAD_F(0x04321fa6) /* 0.262237216 */, 16 }, /* 1502 */ { MAD_F(0x043313f0) /* 0.262470186 */, 16 }, /* 1503 */ { MAD_F(0x04340847) /* 0.262703208 */, 16 }, /* 1504 */ { MAD_F(0x0434fcad) /* 0.262936282 */, 16 }, /* 1505 */ { MAD_F(0x0435f120) /* 0.263169407 */, 16 }, /* 1506 */ { MAD_F(0x0436e5a1) /* 0.263402584 */, 16 }, /* 1507 */ { MAD_F(0x0437da2f) /* 0.263635813 */, 16 }, /* 1508 */ { MAD_F(0x0438cecc) /* 0.263869093 */, 16 }, /* 1509 */ { MAD_F(0x0439c377) /* 0.264102425 */, 16 }, /* 1510 */ { MAD_F(0x043ab82f) /* 0.264335808 */, 16 }, /* 1511 */ { MAD_F(0x043bacf5) /* 0.264569243 */, 16 }, /* 1512 */ { MAD_F(0x043ca1c9) /* 0.264802730 */, 16 }, /* 1513 */ { MAD_F(0x043d96ab) /* 0.265036267 */, 16 }, /* 1514 */ { MAD_F(0x043e8b9b) /* 0.265269857 */, 16 }, /* 1515 */ { MAD_F(0x043f8098) /* 0.265503498 */, 16 }, /* 1516 */ { MAD_F(0x044075a3) /* 0.265737190 */, 16 }, /* 1517 */ { MAD_F(0x04416abc) /* 0.265970933 */, 16 }, /* 1518 */ { MAD_F(0x04425fe3) /* 0.266204728 */, 16 }, /* 1519 */ { MAD_F(0x04435518) /* 0.266438574 */, 16 }, /* 1520 */ { MAD_F(0x04444a5a) /* 0.266672472 */, 16 }, /* 1521 */ { MAD_F(0x04453fab) /* 0.266906421 */, 16 }, /* 1522 */ { MAD_F(0x04463508) /* 0.267140421 */, 16 }, /* 1523 */ { MAD_F(0x04472a74) /* 0.267374472 */, 16 }, /* 1524 */ { MAD_F(0x04481fee) /* 0.267608575 */, 16 }, /* 1525 */ { MAD_F(0x04491575) /* 0.267842729 */, 16 }, /* 1526 */ { MAD_F(0x044a0b0a) /* 0.268076934 */, 16 }, /* 1527 */ { MAD_F(0x044b00ac) /* 0.268311190 */, 16 }, /* 1528 */ { MAD_F(0x044bf65d) /* 0.268545497 */, 16 }, /* 1529 */ { MAD_F(0x044cec1b) /* 0.268779856 */, 16 }, /* 1530 */ { MAD_F(0x044de1e7) /* 0.269014265 */, 16 }, /* 1531 */ { MAD_F(0x044ed7c0) /* 0.269248726 */, 16 }, /* 1532 */ { MAD_F(0x044fcda8) /* 0.269483238 */, 16 }, /* 1533 */ { MAD_F(0x0450c39c) /* 0.269717800 */, 16 }, /* 1534 */ { MAD_F(0x0451b99f) /* 0.269952414 */, 16 }, /* 1535 */ { MAD_F(0x0452afaf) /* 0.270187079 */, 16 }, /* 1536 */ { MAD_F(0x0453a5cd) /* 0.270421794 */, 16 }, /* 1537 */ { MAD_F(0x04549bf9) /* 0.270656561 */, 16 }, /* 1538 */ { MAD_F(0x04559232) /* 0.270891379 */, 16 }, /* 1539 */ { MAD_F(0x04568879) /* 0.271126247 */, 16 }, /* 1540 */ { MAD_F(0x04577ece) /* 0.271361166 */, 16 }, /* 1541 */ { MAD_F(0x04587530) /* 0.271596136 */, 16 }, /* 1542 */ { MAD_F(0x04596ba0) /* 0.271831157 */, 16 }, /* 1543 */ { MAD_F(0x045a621e) /* 0.272066229 */, 16 }, /* 1544 */ { MAD_F(0x045b58a9) /* 0.272301352 */, 16 }, /* 1545 */ { MAD_F(0x045c4f42) /* 0.272536525 */, 16 }, /* 1546 */ { MAD_F(0x045d45e9) /* 0.272771749 */, 16 }, /* 1547 */ { MAD_F(0x045e3c9d) /* 0.273007024 */, 16 }, /* 1548 */ { MAD_F(0x045f335e) /* 0.273242350 */, 16 }, /* 1549 */ { MAD_F(0x04602a2e) /* 0.273477726 */, 16 }, /* 1550 */ { MAD_F(0x0461210b) /* 0.273713153 */, 16 }, /* 1551 */ { MAD_F(0x046217f5) /* 0.273948630 */, 16 }, /* 1552 */ { MAD_F(0x04630eed) /* 0.274184158 */, 16 }, /* 1553 */ { MAD_F(0x046405f3) /* 0.274419737 */, 16 }, /* 1554 */ { MAD_F(0x0464fd06) /* 0.274655366 */, 16 }, /* 1555 */ { MAD_F(0x0465f427) /* 0.274891046 */, 16 }, /* 1556 */ { MAD_F(0x0466eb55) /* 0.275126776 */, 16 }, /* 1557 */ { MAD_F(0x0467e291) /* 0.275362557 */, 16 }, /* 1558 */ { MAD_F(0x0468d9db) /* 0.275598389 */, 16 }, /* 1559 */ { MAD_F(0x0469d132) /* 0.275834270 */, 16 }, /* 1560 */ { MAD_F(0x046ac896) /* 0.276070203 */, 16 }, /* 1561 */ { MAD_F(0x046bc009) /* 0.276306185 */, 16 }, /* 1562 */ { MAD_F(0x046cb788) /* 0.276542218 */, 16 }, /* 1563 */ { MAD_F(0x046daf15) /* 0.276778302 */, 16 }, /* 1564 */ { MAD_F(0x046ea6b0) /* 0.277014435 */, 16 }, /* 1565 */ { MAD_F(0x046f9e58) /* 0.277250619 */, 16 }, /* 1566 */ { MAD_F(0x0470960e) /* 0.277486854 */, 16 }, /* 1567 */ { MAD_F(0x04718dd1) /* 0.277723139 */, 16 }, /* 1568 */ { MAD_F(0x047285a2) /* 0.277959474 */, 16 }, /* 1569 */ { MAD_F(0x04737d80) /* 0.278195859 */, 16 }, /* 1570 */ { MAD_F(0x0474756c) /* 0.278432294 */, 16 }, /* 1571 */ { MAD_F(0x04756d65) /* 0.278668780 */, 16 }, /* 1572 */ { MAD_F(0x0476656b) /* 0.278905316 */, 16 }, /* 1573 */ { MAD_F(0x04775d7f) /* 0.279141902 */, 16 }, /* 1574 */ { MAD_F(0x047855a1) /* 0.279378538 */, 16 }, /* 1575 */ { MAD_F(0x04794dd0) /* 0.279615224 */, 16 }, /* 1576 */ { MAD_F(0x047a460c) /* 0.279851960 */, 16 }, /* 1577 */ { MAD_F(0x047b3e56) /* 0.280088747 */, 16 }, /* 1578 */ { MAD_F(0x047c36ae) /* 0.280325583 */, 16 }, /* 1579 */ { MAD_F(0x047d2f12) /* 0.280562470 */, 16 }, /* 1580 */ { MAD_F(0x047e2784) /* 0.280799406 */, 16 }, /* 1581 */ { MAD_F(0x047f2004) /* 0.281036393 */, 16 }, /* 1582 */ { MAD_F(0x04801891) /* 0.281273429 */, 16 }, /* 1583 */ { MAD_F(0x0481112b) /* 0.281510516 */, 16 }, /* 1584 */ { MAD_F(0x048209d3) /* 0.281747652 */, 16 }, /* 1585 */ { MAD_F(0x04830288) /* 0.281984838 */, 16 }, /* 1586 */ { MAD_F(0x0483fb4b) /* 0.282222075 */, 16 }, /* 1587 */ { MAD_F(0x0484f41b) /* 0.282459361 */, 16 }, /* 1588 */ { MAD_F(0x0485ecf8) /* 0.282696697 */, 16 }, /* 1589 */ { MAD_F(0x0486e5e3) /* 0.282934082 */, 16 }, /* 1590 */ { MAD_F(0x0487dedb) /* 0.283171518 */, 16 }, /* 1591 */ { MAD_F(0x0488d7e1) /* 0.283409003 */, 16 }, /* 1592 */ { MAD_F(0x0489d0f4) /* 0.283646538 */, 16 }, /* 1593 */ { MAD_F(0x048aca14) /* 0.283884123 */, 16 }, /* 1594 */ { MAD_F(0x048bc341) /* 0.284121757 */, 16 }, /* 1595 */ { MAD_F(0x048cbc7c) /* 0.284359441 */, 16 }, /* 1596 */ { MAD_F(0x048db5c4) /* 0.284597175 */, 16 }, /* 1597 */ { MAD_F(0x048eaf1a) /* 0.284834959 */, 16 }, /* 1598 */ { MAD_F(0x048fa87d) /* 0.285072792 */, 16 }, /* 1599 */ { MAD_F(0x0490a1ed) /* 0.285310675 */, 16 }, /* 1600 */ { MAD_F(0x04919b6a) /* 0.285548607 */, 16 }, /* 1601 */ { MAD_F(0x049294f5) /* 0.285786589 */, 16 }, /* 1602 */ { MAD_F(0x04938e8d) /* 0.286024621 */, 16 }, /* 1603 */ { MAD_F(0x04948833) /* 0.286262702 */, 16 }, /* 1604 */ { MAD_F(0x049581e5) /* 0.286500832 */, 16 }, /* 1605 */ { MAD_F(0x04967ba5) /* 0.286739012 */, 16 }, /* 1606 */ { MAD_F(0x04977573) /* 0.286977242 */, 16 }, /* 1607 */ { MAD_F(0x04986f4d) /* 0.287215521 */, 16 }, /* 1608 */ { MAD_F(0x04996935) /* 0.287453849 */, 16 }, /* 1609 */ { MAD_F(0x049a632a) /* 0.287692227 */, 16 }, /* 1610 */ { MAD_F(0x049b5d2c) /* 0.287930654 */, 16 }, /* 1611 */ { MAD_F(0x049c573c) /* 0.288169131 */, 16 }, /* 1612 */ { MAD_F(0x049d5159) /* 0.288407657 */, 16 }, /* 1613 */ { MAD_F(0x049e4b83) /* 0.288646232 */, 16 }, /* 1614 */ { MAD_F(0x049f45ba) /* 0.288884857 */, 16 }, /* 1615 */ { MAD_F(0x04a03ffe) /* 0.289123530 */, 16 }, /* 1616 */ { MAD_F(0x04a13a50) /* 0.289362253 */, 16 }, /* 1617 */ { MAD_F(0x04a234af) /* 0.289601026 */, 16 }, /* 1618 */ { MAD_F(0x04a32f1b) /* 0.289839847 */, 16 }, /* 1619 */ { MAD_F(0x04a42995) /* 0.290078718 */, 16 }, /* 1620 */ { MAD_F(0x04a5241b) /* 0.290317638 */, 16 }, /* 1621 */ { MAD_F(0x04a61eaf) /* 0.290556607 */, 16 }, /* 1622 */ { MAD_F(0x04a71950) /* 0.290795626 */, 16 }, /* 1623 */ { MAD_F(0x04a813fe) /* 0.291034693 */, 16 }, /* 1624 */ { MAD_F(0x04a90eba) /* 0.291273810 */, 16 }, /* 1625 */ { MAD_F(0x04aa0982) /* 0.291512975 */, 16 }, /* 1626 */ { MAD_F(0x04ab0458) /* 0.291752190 */, 16 }, /* 1627 */ { MAD_F(0x04abff3b) /* 0.291991453 */, 16 }, /* 1628 */ { MAD_F(0x04acfa2b) /* 0.292230766 */, 16 }, /* 1629 */ { MAD_F(0x04adf528) /* 0.292470128 */, 16 }, /* 1630 */ { MAD_F(0x04aef032) /* 0.292709539 */, 16 }, /* 1631 */ { MAD_F(0x04afeb4a) /* 0.292948998 */, 16 }, /* 1632 */ { MAD_F(0x04b0e66e) /* 0.293188507 */, 16 }, /* 1633 */ { MAD_F(0x04b1e1a0) /* 0.293428065 */, 16 }, /* 1634 */ { MAD_F(0x04b2dcdf) /* 0.293667671 */, 16 }, /* 1635 */ { MAD_F(0x04b3d82b) /* 0.293907326 */, 16 }, /* 1636 */ { MAD_F(0x04b4d384) /* 0.294147031 */, 16 }, /* 1637 */ { MAD_F(0x04b5ceea) /* 0.294386784 */, 16 }, /* 1638 */ { MAD_F(0x04b6ca5e) /* 0.294626585 */, 16 }, /* 1639 */ { MAD_F(0x04b7c5de) /* 0.294866436 */, 16 }, /* 1640 */ { MAD_F(0x04b8c16c) /* 0.295106336 */, 16 }, /* 1641 */ { MAD_F(0x04b9bd06) /* 0.295346284 */, 16 }, /* 1642 */ { MAD_F(0x04bab8ae) /* 0.295586281 */, 16 }, /* 1643 */ { MAD_F(0x04bbb463) /* 0.295826327 */, 16 }, /* 1644 */ { MAD_F(0x04bcb024) /* 0.296066421 */, 16 }, /* 1645 */ { MAD_F(0x04bdabf3) /* 0.296306564 */, 16 }, /* 1646 */ { MAD_F(0x04bea7cf) /* 0.296546756 */, 16 }, /* 1647 */ { MAD_F(0x04bfa3b8) /* 0.296786996 */, 16 }, /* 1648 */ { MAD_F(0x04c09faf) /* 0.297027285 */, 16 }, /* 1649 */ { MAD_F(0x04c19bb2) /* 0.297267623 */, 16 }, /* 1650 */ { MAD_F(0x04c297c2) /* 0.297508009 */, 16 }, /* 1651 */ { MAD_F(0x04c393df) /* 0.297748444 */, 16 }, /* 1652 */ { MAD_F(0x04c49009) /* 0.297988927 */, 16 }, /* 1653 */ { MAD_F(0x04c58c41) /* 0.298229459 */, 16 }, /* 1654 */ { MAD_F(0x04c68885) /* 0.298470039 */, 16 }, /* 1655 */ { MAD_F(0x04c784d6) /* 0.298710668 */, 16 }, /* 1656 */ { MAD_F(0x04c88135) /* 0.298951346 */, 16 }, /* 1657 */ { MAD_F(0x04c97da0) /* 0.299192071 */, 16 }, /* 1658 */ { MAD_F(0x04ca7a18) /* 0.299432846 */, 16 }, /* 1659 */ { MAD_F(0x04cb769e) /* 0.299673668 */, 16 }, /* 1660 */ { MAD_F(0x04cc7330) /* 0.299914539 */, 16 }, /* 1661 */ { MAD_F(0x04cd6fcf) /* 0.300155459 */, 16 }, /* 1662 */ { MAD_F(0x04ce6c7b) /* 0.300396426 */, 16 }, /* 1663 */ { MAD_F(0x04cf6935) /* 0.300637443 */, 16 }, /* 1664 */ { MAD_F(0x04d065fb) /* 0.300878507 */, 16 }, /* 1665 */ { MAD_F(0x04d162ce) /* 0.301119620 */, 16 }, /* 1666 */ { MAD_F(0x04d25fae) /* 0.301360781 */, 16 }, /* 1667 */ { MAD_F(0x04d35c9b) /* 0.301601990 */, 16 }, /* 1668 */ { MAD_F(0x04d45995) /* 0.301843247 */, 16 }, /* 1669 */ { MAD_F(0x04d5569c) /* 0.302084553 */, 16 }, /* 1670 */ { MAD_F(0x04d653b0) /* 0.302325907 */, 16 }, /* 1671 */ { MAD_F(0x04d750d1) /* 0.302567309 */, 16 }, /* 1672 */ { MAD_F(0x04d84dff) /* 0.302808759 */, 16 }, /* 1673 */ { MAD_F(0x04d94b3a) /* 0.303050257 */, 16 }, /* 1674 */ { MAD_F(0x04da4881) /* 0.303291804 */, 16 }, /* 1675 */ { MAD_F(0x04db45d6) /* 0.303533399 */, 16 }, /* 1676 */ { MAD_F(0x04dc4337) /* 0.303775041 */, 16 }, /* 1677 */ { MAD_F(0x04dd40a6) /* 0.304016732 */, 16 }, /* 1678 */ { MAD_F(0x04de3e21) /* 0.304258471 */, 16 }, /* 1679 */ { MAD_F(0x04df3ba9) /* 0.304500257 */, 16 }, /* 1680 */ { MAD_F(0x04e0393e) /* 0.304742092 */, 16 }, /* 1681 */ { MAD_F(0x04e136e0) /* 0.304983975 */, 16 }, /* 1682 */ { MAD_F(0x04e2348f) /* 0.305225906 */, 16 }, /* 1683 */ { MAD_F(0x04e3324b) /* 0.305467885 */, 16 }, /* 1684 */ { MAD_F(0x04e43013) /* 0.305709911 */, 16 }, /* 1685 */ { MAD_F(0x04e52de9) /* 0.305951986 */, 16 }, /* 1686 */ { MAD_F(0x04e62bcb) /* 0.306194108 */, 16 }, /* 1687 */ { MAD_F(0x04e729ba) /* 0.306436279 */, 16 }, /* 1688 */ { MAD_F(0x04e827b6) /* 0.306678497 */, 16 }, /* 1689 */ { MAD_F(0x04e925bf) /* 0.306920763 */, 16 }, /* 1690 */ { MAD_F(0x04ea23d4) /* 0.307163077 */, 16 }, /* 1691 */ { MAD_F(0x04eb21f7) /* 0.307405438 */, 16 }, /* 1692 */ { MAD_F(0x04ec2026) /* 0.307647848 */, 16 }, /* 1693 */ { MAD_F(0x04ed1e62) /* 0.307890305 */, 16 }, /* 1694 */ { MAD_F(0x04ee1cab) /* 0.308132810 */, 16 }, /* 1695 */ { MAD_F(0x04ef1b01) /* 0.308375362 */, 16 }, /* 1696 */ { MAD_F(0x04f01963) /* 0.308617963 */, 16 }, /* 1697 */ { MAD_F(0x04f117d3) /* 0.308860611 */, 16 }, /* 1698 */ { MAD_F(0x04f2164f) /* 0.309103306 */, 16 }, /* 1699 */ { MAD_F(0x04f314d8) /* 0.309346050 */, 16 }, /* 1700 */ { MAD_F(0x04f4136d) /* 0.309588841 */, 16 }, /* 1701 */ { MAD_F(0x04f51210) /* 0.309831679 */, 16 }, /* 1702 */ { MAD_F(0x04f610bf) /* 0.310074565 */, 16 }, /* 1703 */ { MAD_F(0x04f70f7b) /* 0.310317499 */, 16 }, /* 1704 */ { MAD_F(0x04f80e44) /* 0.310560480 */, 16 }, /* 1705 */ { MAD_F(0x04f90d19) /* 0.310803509 */, 16 }, /* 1706 */ { MAD_F(0x04fa0bfc) /* 0.311046586 */, 16 }, /* 1707 */ { MAD_F(0x04fb0aeb) /* 0.311289710 */, 16 }, /* 1708 */ { MAD_F(0x04fc09e7) /* 0.311532881 */, 16 }, /* 1709 */ { MAD_F(0x04fd08ef) /* 0.311776100 */, 16 }, /* 1710 */ { MAD_F(0x04fe0805) /* 0.312019366 */, 16 }, /* 1711 */ { MAD_F(0x04ff0727) /* 0.312262680 */, 16 }, /* 1712 */ { MAD_F(0x05000655) /* 0.312506041 */, 16 }, /* 1713 */ { MAD_F(0x05010591) /* 0.312749449 */, 16 }, /* 1714 */ { MAD_F(0x050204d9) /* 0.312992905 */, 16 }, /* 1715 */ { MAD_F(0x0503042e) /* 0.313236408 */, 16 }, /* 1716 */ { MAD_F(0x0504038f) /* 0.313479959 */, 16 }, /* 1717 */ { MAD_F(0x050502fe) /* 0.313723556 */, 16 }, /* 1718 */ { MAD_F(0x05060279) /* 0.313967202 */, 16 }, /* 1719 */ { MAD_F(0x05070200) /* 0.314210894 */, 16 }, /* 1720 */ { MAD_F(0x05080195) /* 0.314454634 */, 16 }, /* 1721 */ { MAD_F(0x05090136) /* 0.314698420 */, 16 }, /* 1722 */ { MAD_F(0x050a00e3) /* 0.314942255 */, 16 }, /* 1723 */ { MAD_F(0x050b009e) /* 0.315186136 */, 16 }, /* 1724 */ { MAD_F(0x050c0065) /* 0.315430064 */, 16 }, /* 1725 */ { MAD_F(0x050d0039) /* 0.315674040 */, 16 }, /* 1726 */ { MAD_F(0x050e0019) /* 0.315918063 */, 16 }, /* 1727 */ { MAD_F(0x050f0006) /* 0.316162133 */, 16 }, /* 1728 */ { MAD_F(0x05100000) /* 0.316406250 */, 16 }, /* 1729 */ { MAD_F(0x05110006) /* 0.316650414 */, 16 }, /* 1730 */ { MAD_F(0x05120019) /* 0.316894625 */, 16 }, /* 1731 */ { MAD_F(0x05130039) /* 0.317138884 */, 16 }, /* 1732 */ { MAD_F(0x05140065) /* 0.317383189 */, 16 }, /* 1733 */ { MAD_F(0x0515009e) /* 0.317627541 */, 16 }, /* 1734 */ { MAD_F(0x051600e3) /* 0.317871941 */, 16 }, /* 1735 */ { MAD_F(0x05170135) /* 0.318116387 */, 16 }, /* 1736 */ { MAD_F(0x05180194) /* 0.318360880 */, 16 }, /* 1737 */ { MAD_F(0x051901ff) /* 0.318605421 */, 16 }, /* 1738 */ { MAD_F(0x051a0277) /* 0.318850008 */, 16 }, /* 1739 */ { MAD_F(0x051b02fc) /* 0.319094642 */, 16 }, /* 1740 */ { MAD_F(0x051c038d) /* 0.319339323 */, 16 }, /* 1741 */ { MAD_F(0x051d042a) /* 0.319584051 */, 16 }, /* 1742 */ { MAD_F(0x051e04d4) /* 0.319828826 */, 16 }, /* 1743 */ { MAD_F(0x051f058b) /* 0.320073647 */, 16 }, /* 1744 */ { MAD_F(0x0520064f) /* 0.320318516 */, 16 }, /* 1745 */ { MAD_F(0x0521071f) /* 0.320563431 */, 16 }, /* 1746 */ { MAD_F(0x052207fb) /* 0.320808393 */, 16 }, /* 1747 */ { MAD_F(0x052308e4) /* 0.321053402 */, 16 }, /* 1748 */ { MAD_F(0x052409da) /* 0.321298457 */, 16 }, /* 1749 */ { MAD_F(0x05250adc) /* 0.321543560 */, 16 }, /* 1750 */ { MAD_F(0x05260bea) /* 0.321788709 */, 16 }, /* 1751 */ { MAD_F(0x05270d06) /* 0.322033904 */, 16 }, /* 1752 */ { MAD_F(0x05280e2d) /* 0.322279147 */, 16 }, /* 1753 */ { MAD_F(0x05290f62) /* 0.322524436 */, 16 }, /* 1754 */ { MAD_F(0x052a10a3) /* 0.322769771 */, 16 }, /* 1755 */ { MAD_F(0x052b11f0) /* 0.323015154 */, 16 }, /* 1756 */ { MAD_F(0x052c134a) /* 0.323260583 */, 16 }, /* 1757 */ { MAD_F(0x052d14b0) /* 0.323506058 */, 16 }, /* 1758 */ { MAD_F(0x052e1623) /* 0.323751580 */, 16 }, /* 1759 */ { MAD_F(0x052f17a2) /* 0.323997149 */, 16 }, /* 1760 */ { MAD_F(0x0530192e) /* 0.324242764 */, 16 }, /* 1761 */ { MAD_F(0x05311ac6) /* 0.324488426 */, 16 }, /* 1762 */ { MAD_F(0x05321c6b) /* 0.324734134 */, 16 }, /* 1763 */ { MAD_F(0x05331e1c) /* 0.324979889 */, 16 }, /* 1764 */ { MAD_F(0x05341fda) /* 0.325225690 */, 16 }, /* 1765 */ { MAD_F(0x053521a4) /* 0.325471538 */, 16 }, /* 1766 */ { MAD_F(0x0536237b) /* 0.325717432 */, 16 }, /* 1767 */ { MAD_F(0x0537255e) /* 0.325963372 */, 16 }, /* 1768 */ { MAD_F(0x0538274e) /* 0.326209359 */, 16 }, /* 1769 */ { MAD_F(0x0539294a) /* 0.326455392 */, 16 }, /* 1770 */ { MAD_F(0x053a2b52) /* 0.326701472 */, 16 }, /* 1771 */ { MAD_F(0x053b2d67) /* 0.326947598 */, 16 }, /* 1772 */ { MAD_F(0x053c2f89) /* 0.327193770 */, 16 }, /* 1773 */ { MAD_F(0x053d31b6) /* 0.327439989 */, 16 }, /* 1774 */ { MAD_F(0x053e33f1) /* 0.327686254 */, 16 }, /* 1775 */ { MAD_F(0x053f3637) /* 0.327932565 */, 16 }, /* 1776 */ { MAD_F(0x0540388a) /* 0.328178922 */, 16 }, /* 1777 */ { MAD_F(0x05413aea) /* 0.328425326 */, 16 }, /* 1778 */ { MAD_F(0x05423d56) /* 0.328671776 */, 16 }, /* 1779 */ { MAD_F(0x05433fce) /* 0.328918272 */, 16 }, /* 1780 */ { MAD_F(0x05444253) /* 0.329164814 */, 16 }, /* 1781 */ { MAD_F(0x054544e4) /* 0.329411403 */, 16 }, /* 1782 */ { MAD_F(0x05464781) /* 0.329658038 */, 16 }, /* 1783 */ { MAD_F(0x05474a2b) /* 0.329904718 */, 16 }, /* 1784 */ { MAD_F(0x05484ce2) /* 0.330151445 */, 16 }, /* 1785 */ { MAD_F(0x05494fa4) /* 0.330398218 */, 16 }, /* 1786 */ { MAD_F(0x054a5273) /* 0.330645037 */, 16 }, /* 1787 */ { MAD_F(0x054b554e) /* 0.330891903 */, 16 }, /* 1788 */ { MAD_F(0x054c5836) /* 0.331138814 */, 16 }, /* 1789 */ { MAD_F(0x054d5b2a) /* 0.331385771 */, 16 }, /* 1790 */ { MAD_F(0x054e5e2b) /* 0.331632774 */, 16 }, /* 1791 */ { MAD_F(0x054f6138) /* 0.331879824 */, 16 }, /* 1792 */ { MAD_F(0x05506451) /* 0.332126919 */, 16 }, /* 1793 */ { MAD_F(0x05516776) /* 0.332374060 */, 16 }, /* 1794 */ { MAD_F(0x05526aa8) /* 0.332621247 */, 16 }, /* 1795 */ { MAD_F(0x05536de6) /* 0.332868480 */, 16 }, /* 1796 */ { MAD_F(0x05547131) /* 0.333115759 */, 16 }, /* 1797 */ { MAD_F(0x05557487) /* 0.333363084 */, 16 }, /* 1798 */ { MAD_F(0x055677ea) /* 0.333610455 */, 16 }, /* 1799 */ { MAD_F(0x05577b5a) /* 0.333857872 */, 16 }, /* 1800 */ { MAD_F(0x05587ed5) /* 0.334105334 */, 16 }, /* 1801 */ { MAD_F(0x0559825e) /* 0.334352843 */, 16 }, /* 1802 */ { MAD_F(0x055a85f2) /* 0.334600397 */, 16 }, /* 1803 */ { MAD_F(0x055b8992) /* 0.334847997 */, 16 }, /* 1804 */ { MAD_F(0x055c8d3f) /* 0.335095642 */, 16 }, /* 1805 */ { MAD_F(0x055d90f9) /* 0.335343334 */, 16 }, /* 1806 */ { MAD_F(0x055e94be) /* 0.335591071 */, 16 }, /* 1807 */ { MAD_F(0x055f9890) /* 0.335838854 */, 16 }, /* 1808 */ { MAD_F(0x05609c6e) /* 0.336086683 */, 16 }, /* 1809 */ { MAD_F(0x0561a058) /* 0.336334557 */, 16 }, /* 1810 */ { MAD_F(0x0562a44f) /* 0.336582477 */, 16 }, /* 1811 */ { MAD_F(0x0563a851) /* 0.336830443 */, 16 }, /* 1812 */ { MAD_F(0x0564ac60) /* 0.337078454 */, 16 }, /* 1813 */ { MAD_F(0x0565b07c) /* 0.337326511 */, 16 }, /* 1814 */ { MAD_F(0x0566b4a3) /* 0.337574614 */, 16 }, /* 1815 */ { MAD_F(0x0567b8d7) /* 0.337822762 */, 16 }, /* 1816 */ { MAD_F(0x0568bd17) /* 0.338070956 */, 16 }, /* 1817 */ { MAD_F(0x0569c163) /* 0.338319195 */, 16 }, /* 1818 */ { MAD_F(0x056ac5bc) /* 0.338567480 */, 16 }, /* 1819 */ { MAD_F(0x056bca20) /* 0.338815811 */, 16 }, /* 1820 */ { MAD_F(0x056cce91) /* 0.339064186 */, 16 }, /* 1821 */ { MAD_F(0x056dd30e) /* 0.339312608 */, 16 }, /* 1822 */ { MAD_F(0x056ed798) /* 0.339561075 */, 16 }, /* 1823 */ { MAD_F(0x056fdc2d) /* 0.339809587 */, 16 }, /* 1824 */ { MAD_F(0x0570e0cf) /* 0.340058145 */, 16 }, /* 1825 */ { MAD_F(0x0571e57d) /* 0.340306748 */, 16 }, /* 1826 */ { MAD_F(0x0572ea37) /* 0.340555397 */, 16 }, /* 1827 */ { MAD_F(0x0573eefd) /* 0.340804091 */, 16 }, /* 1828 */ { MAD_F(0x0574f3d0) /* 0.341052830 */, 16 }, /* 1829 */ { MAD_F(0x0575f8ae) /* 0.341301615 */, 16 }, /* 1830 */ { MAD_F(0x0576fd99) /* 0.341550445 */, 16 }, /* 1831 */ { MAD_F(0x05780290) /* 0.341799321 */, 16 }, /* 1832 */ { MAD_F(0x05790793) /* 0.342048241 */, 16 }, /* 1833 */ { MAD_F(0x057a0ca3) /* 0.342297207 */, 16 }, /* 1834 */ { MAD_F(0x057b11be) /* 0.342546219 */, 16 }, /* 1835 */ { MAD_F(0x057c16e6) /* 0.342795275 */, 16 }, /* 1836 */ { MAD_F(0x057d1c1a) /* 0.343044377 */, 16 }, /* 1837 */ { MAD_F(0x057e2159) /* 0.343293524 */, 16 }, /* 1838 */ { MAD_F(0x057f26a6) /* 0.343542717 */, 16 }, /* 1839 */ { MAD_F(0x05802bfe) /* 0.343791954 */, 16 }, /* 1840 */ { MAD_F(0x05813162) /* 0.344041237 */, 16 }, /* 1841 */ { MAD_F(0x058236d2) /* 0.344290564 */, 16 }, /* 1842 */ { MAD_F(0x05833c4f) /* 0.344539937 */, 16 }, /* 1843 */ { MAD_F(0x058441d8) /* 0.344789356 */, 16 }, /* 1844 */ { MAD_F(0x0585476c) /* 0.345038819 */, 16 }, /* 1845 */ { MAD_F(0x05864d0d) /* 0.345288327 */, 16 }, /* 1846 */ { MAD_F(0x058752ba) /* 0.345537880 */, 16 }, /* 1847 */ { MAD_F(0x05885873) /* 0.345787479 */, 16 }, /* 1848 */ { MAD_F(0x05895e39) /* 0.346037122 */, 16 }, /* 1849 */ { MAD_F(0x058a640a) /* 0.346286811 */, 16 }, /* 1850 */ { MAD_F(0x058b69e7) /* 0.346536545 */, 16 }, /* 1851 */ { MAD_F(0x058c6fd1) /* 0.346786323 */, 16 }, /* 1852 */ { MAD_F(0x058d75c6) /* 0.347036147 */, 16 }, /* 1853 */ { MAD_F(0x058e7bc8) /* 0.347286015 */, 16 }, /* 1854 */ { MAD_F(0x058f81d5) /* 0.347535929 */, 16 }, /* 1855 */ { MAD_F(0x059087ef) /* 0.347785887 */, 16 }, /* 1856 */ { MAD_F(0x05918e15) /* 0.348035890 */, 16 }, /* 1857 */ { MAD_F(0x05929447) /* 0.348285939 */, 16 }, /* 1858 */ { MAD_F(0x05939a84) /* 0.348536032 */, 16 }, /* 1859 */ { MAD_F(0x0594a0ce) /* 0.348786170 */, 16 }, /* 1860 */ { MAD_F(0x0595a724) /* 0.349036353 */, 16 }, /* 1861 */ { MAD_F(0x0596ad86) /* 0.349286580 */, 16 }, /* 1862 */ { MAD_F(0x0597b3f4) /* 0.349536853 */, 16 }, /* 1863 */ { MAD_F(0x0598ba6e) /* 0.349787170 */, 16 }, /* 1864 */ { MAD_F(0x0599c0f4) /* 0.350037532 */, 16 }, /* 1865 */ { MAD_F(0x059ac786) /* 0.350287939 */, 16 }, /* 1866 */ { MAD_F(0x059bce25) /* 0.350538391 */, 16 }, /* 1867 */ { MAD_F(0x059cd4cf) /* 0.350788887 */, 16 }, /* 1868 */ { MAD_F(0x059ddb85) /* 0.351039428 */, 16 }, /* 1869 */ { MAD_F(0x059ee247) /* 0.351290014 */, 16 }, /* 1870 */ { MAD_F(0x059fe915) /* 0.351540645 */, 16 }, /* 1871 */ { MAD_F(0x05a0efef) /* 0.351791320 */, 16 }, /* 1872 */ { MAD_F(0x05a1f6d5) /* 0.352042040 */, 16 }, /* 1873 */ { MAD_F(0x05a2fdc7) /* 0.352292804 */, 16 }, /* 1874 */ { MAD_F(0x05a404c5) /* 0.352543613 */, 16 }, /* 1875 */ { MAD_F(0x05a50bcf) /* 0.352794467 */, 16 }, /* 1876 */ { MAD_F(0x05a612e5) /* 0.353045365 */, 16 }, /* 1877 */ { MAD_F(0x05a71a07) /* 0.353296308 */, 16 }, /* 1878 */ { MAD_F(0x05a82135) /* 0.353547296 */, 16 }, /* 1879 */ { MAD_F(0x05a9286f) /* 0.353798328 */, 16 }, /* 1880 */ { MAD_F(0x05aa2fb5) /* 0.354049405 */, 16 }, /* 1881 */ { MAD_F(0x05ab3707) /* 0.354300526 */, 16 }, /* 1882 */ { MAD_F(0x05ac3e65) /* 0.354551691 */, 16 }, /* 1883 */ { MAD_F(0x05ad45ce) /* 0.354802901 */, 16 }, /* 1884 */ { MAD_F(0x05ae4d44) /* 0.355054156 */, 16 }, /* 1885 */ { MAD_F(0x05af54c6) /* 0.355305455 */, 16 }, /* 1886 */ { MAD_F(0x05b05c53) /* 0.355556799 */, 16 }, /* 1887 */ { MAD_F(0x05b163ed) /* 0.355808187 */, 16 }, /* 1888 */ { MAD_F(0x05b26b92) /* 0.356059619 */, 16 }, /* 1889 */ { MAD_F(0x05b37343) /* 0.356311096 */, 16 }, /* 1890 */ { MAD_F(0x05b47b00) /* 0.356562617 */, 16 }, /* 1891 */ { MAD_F(0x05b582c9) /* 0.356814182 */, 16 }, /* 1892 */ { MAD_F(0x05b68a9e) /* 0.357065792 */, 16 }, /* 1893 */ { MAD_F(0x05b7927f) /* 0.357317446 */, 16 }, /* 1894 */ { MAD_F(0x05b89a6c) /* 0.357569145 */, 16 }, /* 1895 */ { MAD_F(0x05b9a265) /* 0.357820887 */, 16 }, /* 1896 */ { MAD_F(0x05baaa69) /* 0.358072674 */, 16 }, /* 1897 */ { MAD_F(0x05bbb27a) /* 0.358324506 */, 16 }, /* 1898 */ { MAD_F(0x05bcba96) /* 0.358576381 */, 16 }, /* 1899 */ { MAD_F(0x05bdc2be) /* 0.358828301 */, 16 }, /* 1900 */ { MAD_F(0x05becaf2) /* 0.359080265 */, 16 }, /* 1901 */ { MAD_F(0x05bfd332) /* 0.359332273 */, 16 }, /* 1902 */ { MAD_F(0x05c0db7e) /* 0.359584326 */, 16 }, /* 1903 */ { MAD_F(0x05c1e3d6) /* 0.359836423 */, 16 }, /* 1904 */ { MAD_F(0x05c2ec39) /* 0.360088563 */, 16 }, /* 1905 */ { MAD_F(0x05c3f4a9) /* 0.360340748 */, 16 }, /* 1906 */ { MAD_F(0x05c4fd24) /* 0.360592977 */, 16 }, /* 1907 */ { MAD_F(0x05c605ab) /* 0.360845251 */, 16 }, /* 1908 */ { MAD_F(0x05c70e3e) /* 0.361097568 */, 16 }, /* 1909 */ { MAD_F(0x05c816dd) /* 0.361349929 */, 16 }, /* 1910 */ { MAD_F(0x05c91f87) /* 0.361602335 */, 16 }, /* 1911 */ { MAD_F(0x05ca283e) /* 0.361854784 */, 16 }, /* 1912 */ { MAD_F(0x05cb3100) /* 0.362107278 */, 16 }, /* 1913 */ { MAD_F(0x05cc39ce) /* 0.362359815 */, 16 }, /* 1914 */ { MAD_F(0x05cd42a8) /* 0.362612397 */, 16 }, /* 1915 */ { MAD_F(0x05ce4b8d) /* 0.362865022 */, 16 }, /* 1916 */ { MAD_F(0x05cf547f) /* 0.363117692 */, 16 }, /* 1917 */ { MAD_F(0x05d05d7c) /* 0.363370405 */, 16 }, /* 1918 */ { MAD_F(0x05d16685) /* 0.363623163 */, 16 }, /* 1919 */ { MAD_F(0x05d26f9a) /* 0.363875964 */, 16 }, /* 1920 */ { MAD_F(0x05d378bb) /* 0.364128809 */, 16 }, /* 1921 */ { MAD_F(0x05d481e7) /* 0.364381698 */, 16 }, /* 1922 */ { MAD_F(0x05d58b1f) /* 0.364634632 */, 16 }, /* 1923 */ { MAD_F(0x05d69463) /* 0.364887608 */, 16 }, /* 1924 */ { MAD_F(0x05d79db3) /* 0.365140629 */, 16 }, /* 1925 */ { MAD_F(0x05d8a70f) /* 0.365393694 */, 16 }, /* 1926 */ { MAD_F(0x05d9b076) /* 0.365646802 */, 16 }, /* 1927 */ { MAD_F(0x05dab9e9) /* 0.365899955 */, 16 }, /* 1928 */ { MAD_F(0x05dbc368) /* 0.366153151 */, 16 }, /* 1929 */ { MAD_F(0x05dcccf2) /* 0.366406390 */, 16 }, /* 1930 */ { MAD_F(0x05ddd689) /* 0.366659674 */, 16 }, /* 1931 */ { MAD_F(0x05dee02b) /* 0.366913001 */, 16 }, /* 1932 */ { MAD_F(0x05dfe9d8) /* 0.367166372 */, 16 }, /* 1933 */ { MAD_F(0x05e0f392) /* 0.367419787 */, 16 }, /* 1934 */ { MAD_F(0x05e1fd57) /* 0.367673246 */, 16 }, /* 1935 */ { MAD_F(0x05e30728) /* 0.367926748 */, 16 }, /* 1936 */ { MAD_F(0x05e41105) /* 0.368180294 */, 16 }, /* 1937 */ { MAD_F(0x05e51aed) /* 0.368433883 */, 16 }, /* 1938 */ { MAD_F(0x05e624e1) /* 0.368687517 */, 16 }, /* 1939 */ { MAD_F(0x05e72ee1) /* 0.368941193 */, 16 }, /* 1940 */ { MAD_F(0x05e838ed) /* 0.369194914 */, 16 }, /* 1941 */ { MAD_F(0x05e94304) /* 0.369448678 */, 16 }, /* 1942 */ { MAD_F(0x05ea4d27) /* 0.369702485 */, 16 }, /* 1943 */ { MAD_F(0x05eb5756) /* 0.369956336 */, 16 }, /* 1944 */ { MAD_F(0x05ec6190) /* 0.370210231 */, 16 }, /* 1945 */ { MAD_F(0x05ed6bd6) /* 0.370464169 */, 16 }, /* 1946 */ { MAD_F(0x05ee7628) /* 0.370718151 */, 16 }, /* 1947 */ { MAD_F(0x05ef8085) /* 0.370972177 */, 16 }, /* 1948 */ { MAD_F(0x05f08aee) /* 0.371226245 */, 16 }, /* 1949 */ { MAD_F(0x05f19563) /* 0.371480358 */, 16 }, /* 1950 */ { MAD_F(0x05f29fe3) /* 0.371734513 */, 16 }, /* 1951 */ { MAD_F(0x05f3aa6f) /* 0.371988712 */, 16 }, /* 1952 */ { MAD_F(0x05f4b507) /* 0.372242955 */, 16 }, /* 1953 */ { MAD_F(0x05f5bfab) /* 0.372497241 */, 16 }, /* 1954 */ { MAD_F(0x05f6ca5a) /* 0.372751570 */, 16 }, /* 1955 */ { MAD_F(0x05f7d514) /* 0.373005943 */, 16 }, /* 1956 */ { MAD_F(0x05f8dfdb) /* 0.373260359 */, 16 }, /* 1957 */ { MAD_F(0x05f9eaad) /* 0.373514819 */, 16 }, /* 1958 */ { MAD_F(0x05faf58a) /* 0.373769322 */, 16 }, /* 1959 */ { MAD_F(0x05fc0073) /* 0.374023868 */, 16 }, /* 1960 */ { MAD_F(0x05fd0b68) /* 0.374278458 */, 16 }, /* 1961 */ { MAD_F(0x05fe1669) /* 0.374533091 */, 16 }, /* 1962 */ { MAD_F(0x05ff2175) /* 0.374787767 */, 16 }, /* 1963 */ { MAD_F(0x06002c8d) /* 0.375042486 */, 16 }, /* 1964 */ { MAD_F(0x060137b0) /* 0.375297249 */, 16 }, /* 1965 */ { MAD_F(0x060242df) /* 0.375552055 */, 16 }, /* 1966 */ { MAD_F(0x06034e19) /* 0.375806904 */, 16 }, /* 1967 */ { MAD_F(0x0604595f) /* 0.376061796 */, 16 }, /* 1968 */ { MAD_F(0x060564b1) /* 0.376316732 */, 16 }, /* 1969 */ { MAD_F(0x0606700f) /* 0.376571710 */, 16 }, /* 1970 */ { MAD_F(0x06077b77) /* 0.376826732 */, 16 }, /* 1971 */ { MAD_F(0x060886ec) /* 0.377081797 */, 16 }, /* 1972 */ { MAD_F(0x0609926c) /* 0.377336905 */, 16 }, /* 1973 */ { MAD_F(0x060a9df8) /* 0.377592057 */, 16 }, /* 1974 */ { MAD_F(0x060ba98f) /* 0.377847251 */, 16 }, /* 1975 */ { MAD_F(0x060cb532) /* 0.378102489 */, 16 }, /* 1976 */ { MAD_F(0x060dc0e0) /* 0.378357769 */, 16 }, /* 1977 */ { MAD_F(0x060ecc9a) /* 0.378613093 */, 16 }, /* 1978 */ { MAD_F(0x060fd860) /* 0.378868460 */, 16 }, /* 1979 */ { MAD_F(0x0610e431) /* 0.379123870 */, 16 }, /* 1980 */ { MAD_F(0x0611f00d) /* 0.379379322 */, 16 }, /* 1981 */ { MAD_F(0x0612fbf5) /* 0.379634818 */, 16 }, /* 1982 */ { MAD_F(0x061407e9) /* 0.379890357 */, 16 }, /* 1983 */ { MAD_F(0x061513e8) /* 0.380145939 */, 16 }, /* 1984 */ { MAD_F(0x06161ff3) /* 0.380401563 */, 16 }, /* 1985 */ { MAD_F(0x06172c09) /* 0.380657231 */, 16 }, /* 1986 */ { MAD_F(0x0618382b) /* 0.380912942 */, 16 }, /* 1987 */ { MAD_F(0x06194458) /* 0.381168695 */, 16 }, /* 1988 */ { MAD_F(0x061a5091) /* 0.381424492 */, 16 }, /* 1989 */ { MAD_F(0x061b5cd5) /* 0.381680331 */, 16 }, /* 1990 */ { MAD_F(0x061c6925) /* 0.381936213 */, 16 }, /* 1991 */ { MAD_F(0x061d7581) /* 0.382192138 */, 16 }, /* 1992 */ { MAD_F(0x061e81e8) /* 0.382448106 */, 16 }, /* 1993 */ { MAD_F(0x061f8e5a) /* 0.382704117 */, 16 }, /* 1994 */ { MAD_F(0x06209ad8) /* 0.382960171 */, 16 }, /* 1995 */ { MAD_F(0x0621a761) /* 0.383216267 */, 16 }, /* 1996 */ { MAD_F(0x0622b3f6) /* 0.383472406 */, 16 }, /* 1997 */ { MAD_F(0x0623c096) /* 0.383728588 */, 16 }, /* 1998 */ { MAD_F(0x0624cd42) /* 0.383984813 */, 16 }, /* 1999 */ { MAD_F(0x0625d9f9) /* 0.384241080 */, 16 }, /* 2000 */ { MAD_F(0x0626e6bc) /* 0.384497391 */, 16 }, /* 2001 */ { MAD_F(0x0627f38a) /* 0.384753744 */, 16 }, /* 2002 */ { MAD_F(0x06290064) /* 0.385010139 */, 16 }, /* 2003 */ { MAD_F(0x062a0d49) /* 0.385266578 */, 16 }, /* 2004 */ { MAD_F(0x062b1a3a) /* 0.385523059 */, 16 }, /* 2005 */ { MAD_F(0x062c2736) /* 0.385779582 */, 16 }, /* 2006 */ { MAD_F(0x062d343d) /* 0.386036149 */, 16 }, /* 2007 */ { MAD_F(0x062e4150) /* 0.386292758 */, 16 }, /* 2008 */ { MAD_F(0x062f4e6f) /* 0.386549409 */, 16 }, /* 2009 */ { MAD_F(0x06305b99) /* 0.386806104 */, 16 }, /* 2010 */ { MAD_F(0x063168ce) /* 0.387062840 */, 16 }, /* 2011 */ { MAD_F(0x0632760f) /* 0.387319620 */, 16 }, /* 2012 */ { MAD_F(0x0633835b) /* 0.387576442 */, 16 }, /* 2013 */ { MAD_F(0x063490b2) /* 0.387833306 */, 16 }, /* 2014 */ { MAD_F(0x06359e15) /* 0.388090213 */, 16 }, /* 2015 */ { MAD_F(0x0636ab83) /* 0.388347163 */, 16 }, /* 2016 */ { MAD_F(0x0637b8fd) /* 0.388604155 */, 16 }, /* 2017 */ { MAD_F(0x0638c682) /* 0.388861190 */, 16 }, /* 2018 */ { MAD_F(0x0639d413) /* 0.389118267 */, 16 }, /* 2019 */ { MAD_F(0x063ae1af) /* 0.389375386 */, 16 }, /* 2020 */ { MAD_F(0x063bef56) /* 0.389632548 */, 16 }, /* 2021 */ { MAD_F(0x063cfd09) /* 0.389889752 */, 16 }, /* 2022 */ { MAD_F(0x063e0ac7) /* 0.390146999 */, 16 }, /* 2023 */ { MAD_F(0x063f1891) /* 0.390404289 */, 16 }, /* 2024 */ { MAD_F(0x06402666) /* 0.390661620 */, 16 }, /* 2025 */ { MAD_F(0x06413446) /* 0.390918994 */, 16 }, /* 2026 */ { MAD_F(0x06424232) /* 0.391176411 */, 16 }, /* 2027 */ { MAD_F(0x06435029) /* 0.391433869 */, 16 }, /* 2028 */ { MAD_F(0x06445e2b) /* 0.391691371 */, 16 }, /* 2029 */ { MAD_F(0x06456c39) /* 0.391948914 */, 16 }, /* 2030 */ { MAD_F(0x06467a52) /* 0.392206500 */, 16 }, /* 2031 */ { MAD_F(0x06478877) /* 0.392464128 */, 16 }, /* 2032 */ { MAD_F(0x064896a7) /* 0.392721798 */, 16 }, /* 2033 */ { MAD_F(0x0649a4e2) /* 0.392979511 */, 16 }, /* 2034 */ { MAD_F(0x064ab328) /* 0.393237266 */, 16 }, /* 2035 */ { MAD_F(0x064bc17a) /* 0.393495063 */, 16 }, /* 2036 */ { MAD_F(0x064ccfd8) /* 0.393752902 */, 16 }, /* 2037 */ { MAD_F(0x064dde40) /* 0.394010784 */, 16 }, /* 2038 */ { MAD_F(0x064eecb4) /* 0.394268707 */, 16 }, /* 2039 */ { MAD_F(0x064ffb33) /* 0.394526673 */, 16 }, /* 2040 */ { MAD_F(0x065109be) /* 0.394784681 */, 16 }, /* 2041 */ { MAD_F(0x06521854) /* 0.395042732 */, 16 }, /* 2042 */ { MAD_F(0x065326f5) /* 0.395300824 */, 16 }, /* 2043 */ { MAD_F(0x065435a1) /* 0.395558959 */, 16 }, /* 2044 */ { MAD_F(0x06554459) /* 0.395817135 */, 16 }, /* 2045 */ { MAD_F(0x0656531c) /* 0.396075354 */, 16 }, /* 2046 */ { MAD_F(0x065761ea) /* 0.396333615 */, 16 }, /* 2047 */ { MAD_F(0x065870c4) /* 0.396591918 */, 16 }, /* 2048 */ { MAD_F(0x06597fa9) /* 0.396850263 */, 16 }, /* 2049 */ { MAD_F(0x065a8e99) /* 0.397108650 */, 16 }, /* 2050 */ { MAD_F(0x065b9d95) /* 0.397367079 */, 16 }, /* 2051 */ { MAD_F(0x065cac9c) /* 0.397625550 */, 16 }, /* 2052 */ { MAD_F(0x065dbbae) /* 0.397884063 */, 16 }, /* 2053 */ { MAD_F(0x065ecacb) /* 0.398142619 */, 16 }, /* 2054 */ { MAD_F(0x065fd9f4) /* 0.398401216 */, 16 }, /* 2055 */ { MAD_F(0x0660e928) /* 0.398659855 */, 16 }, /* 2056 */ { MAD_F(0x0661f867) /* 0.398918536 */, 16 }, /* 2057 */ { MAD_F(0x066307b1) /* 0.399177259 */, 16 }, /* 2058 */ { MAD_F(0x06641707) /* 0.399436024 */, 16 }, /* 2059 */ { MAD_F(0x06652668) /* 0.399694831 */, 16 }, /* 2060 */ { MAD_F(0x066635d4) /* 0.399953679 */, 16 }, /* 2061 */ { MAD_F(0x0667454c) /* 0.400212570 */, 16 }, /* 2062 */ { MAD_F(0x066854ce) /* 0.400471503 */, 16 }, /* 2063 */ { MAD_F(0x0669645c) /* 0.400730477 */, 16 }, /* 2064 */ { MAD_F(0x066a73f5) /* 0.400989493 */, 16 }, /* 2065 */ { MAD_F(0x066b839a) /* 0.401248551 */, 16 }, /* 2066 */ { MAD_F(0x066c9349) /* 0.401507651 */, 16 }, /* 2067 */ { MAD_F(0x066da304) /* 0.401766793 */, 16 }, /* 2068 */ { MAD_F(0x066eb2ca) /* 0.402025976 */, 16 }, /* 2069 */ { MAD_F(0x066fc29b) /* 0.402285202 */, 16 }, /* 2070 */ { MAD_F(0x0670d278) /* 0.402544469 */, 16 }, /* 2071 */ { MAD_F(0x0671e25f) /* 0.402803777 */, 16 }, /* 2072 */ { MAD_F(0x0672f252) /* 0.403063128 */, 16 }, /* 2073 */ { MAD_F(0x06740250) /* 0.403322520 */, 16 }, /* 2074 */ { MAD_F(0x0675125a) /* 0.403581954 */, 16 }, /* 2075 */ { MAD_F(0x0676226e) /* 0.403841430 */, 16 }, /* 2076 */ { MAD_F(0x0677328e) /* 0.404100947 */, 16 }, /* 2077 */ { MAD_F(0x067842b9) /* 0.404360506 */, 16 }, /* 2078 */ { MAD_F(0x067952ef) /* 0.404620107 */, 16 }, /* 2079 */ { MAD_F(0x067a6330) /* 0.404879749 */, 16 }, /* 2080 */ { MAD_F(0x067b737c) /* 0.405139433 */, 16 }, /* 2081 */ { MAD_F(0x067c83d4) /* 0.405399159 */, 16 }, /* 2082 */ { MAD_F(0x067d9436) /* 0.405658926 */, 16 }, /* 2083 */ { MAD_F(0x067ea4a4) /* 0.405918735 */, 16 }, /* 2084 */ { MAD_F(0x067fb51d) /* 0.406178585 */, 16 }, /* 2085 */ { MAD_F(0x0680c5a2) /* 0.406438477 */, 16 }, /* 2086 */ { MAD_F(0x0681d631) /* 0.406698410 */, 16 }, /* 2087 */ { MAD_F(0x0682e6cb) /* 0.406958385 */, 16 }, /* 2088 */ { MAD_F(0x0683f771) /* 0.407218402 */, 16 }, /* 2089 */ { MAD_F(0x06850822) /* 0.407478460 */, 16 }, /* 2090 */ { MAD_F(0x068618de) /* 0.407738559 */, 16 }, /* 2091 */ { MAD_F(0x068729a5) /* 0.407998700 */, 16 }, /* 2092 */ { MAD_F(0x06883a77) /* 0.408258883 */, 16 }, /* 2093 */ { MAD_F(0x06894b55) /* 0.408519107 */, 16 }, /* 2094 */ { MAD_F(0x068a5c3d) /* 0.408779372 */, 16 }, /* 2095 */ { MAD_F(0x068b6d31) /* 0.409039679 */, 16 }, /* 2096 */ { MAD_F(0x068c7e2f) /* 0.409300027 */, 16 }, /* 2097 */ { MAD_F(0x068d8f39) /* 0.409560417 */, 16 }, /* 2098 */ { MAD_F(0x068ea04e) /* 0.409820848 */, 16 }, /* 2099 */ { MAD_F(0x068fb16e) /* 0.410081321 */, 16 }, /* 2100 */ { MAD_F(0x0690c299) /* 0.410341834 */, 16 }, /* 2101 */ { MAD_F(0x0691d3cf) /* 0.410602390 */, 16 }, /* 2102 */ { MAD_F(0x0692e511) /* 0.410862986 */, 16 }, /* 2103 */ { MAD_F(0x0693f65d) /* 0.411123624 */, 16 }, /* 2104 */ { MAD_F(0x069507b5) /* 0.411384303 */, 16 }, /* 2105 */ { MAD_F(0x06961917) /* 0.411645024 */, 16 }, /* 2106 */ { MAD_F(0x06972a85) /* 0.411905785 */, 16 }, /* 2107 */ { MAD_F(0x06983bfe) /* 0.412166588 */, 16 }, /* 2108 */ { MAD_F(0x06994d82) /* 0.412427433 */, 16 }, /* 2109 */ { MAD_F(0x069a5f11) /* 0.412688318 */, 16 }, /* 2110 */ { MAD_F(0x069b70ab) /* 0.412949245 */, 16 }, /* 2111 */ { MAD_F(0x069c8250) /* 0.413210213 */, 16 }, /* 2112 */ { MAD_F(0x069d9400) /* 0.413471222 */, 16 }, /* 2113 */ { MAD_F(0x069ea5bb) /* 0.413732273 */, 16 }, /* 2114 */ { MAD_F(0x069fb781) /* 0.413993364 */, 16 }, /* 2115 */ { MAD_F(0x06a0c953) /* 0.414254497 */, 16 }, /* 2116 */ { MAD_F(0x06a1db2f) /* 0.414515671 */, 16 }, /* 2117 */ { MAD_F(0x06a2ed16) /* 0.414776886 */, 16 }, /* 2118 */ { MAD_F(0x06a3ff09) /* 0.415038142 */, 16 }, /* 2119 */ { MAD_F(0x06a51106) /* 0.415299440 */, 16 }, /* 2120 */ { MAD_F(0x06a6230f) /* 0.415560778 */, 16 }, /* 2121 */ { MAD_F(0x06a73522) /* 0.415822157 */, 16 }, /* 2122 */ { MAD_F(0x06a84741) /* 0.416083578 */, 16 }, /* 2123 */ { MAD_F(0x06a9596a) /* 0.416345040 */, 16 }, /* 2124 */ { MAD_F(0x06aa6b9f) /* 0.416606542 */, 16 }, /* 2125 */ { MAD_F(0x06ab7ddf) /* 0.416868086 */, 16 }, /* 2126 */ { MAD_F(0x06ac9029) /* 0.417129671 */, 16 }, /* 2127 */ { MAD_F(0x06ada27f) /* 0.417391297 */, 16 }, /* 2128 */ { MAD_F(0x06aeb4e0) /* 0.417652964 */, 16 }, /* 2129 */ { MAD_F(0x06afc74b) /* 0.417914672 */, 16 }, /* 2130 */ { MAD_F(0x06b0d9c2) /* 0.418176420 */, 16 }, /* 2131 */ { MAD_F(0x06b1ec43) /* 0.418438210 */, 16 }, /* 2132 */ { MAD_F(0x06b2fed0) /* 0.418700041 */, 16 }, /* 2133 */ { MAD_F(0x06b41168) /* 0.418961912 */, 16 }, /* 2134 */ { MAD_F(0x06b5240a) /* 0.419223825 */, 16 }, /* 2135 */ { MAD_F(0x06b636b8) /* 0.419485778 */, 16 }, /* 2136 */ { MAD_F(0x06b74971) /* 0.419747773 */, 16 }, /* 2137 */ { MAD_F(0x06b85c34) /* 0.420009808 */, 16 }, /* 2138 */ { MAD_F(0x06b96f03) /* 0.420271884 */, 16 }, /* 2139 */ { MAD_F(0x06ba81dc) /* 0.420534001 */, 16 }, /* 2140 */ { MAD_F(0x06bb94c1) /* 0.420796159 */, 16 }, /* 2141 */ { MAD_F(0x06bca7b0) /* 0.421058358 */, 16 }, /* 2142 */ { MAD_F(0x06bdbaaa) /* 0.421320597 */, 16 }, /* 2143 */ { MAD_F(0x06becdb0) /* 0.421582878 */, 16 }, /* 2144 */ { MAD_F(0x06bfe0c0) /* 0.421845199 */, 16 }, /* 2145 */ { MAD_F(0x06c0f3db) /* 0.422107561 */, 16 }, /* 2146 */ { MAD_F(0x06c20702) /* 0.422369964 */, 16 }, /* 2147 */ { MAD_F(0x06c31a33) /* 0.422632407 */, 16 }, /* 2148 */ { MAD_F(0x06c42d6f) /* 0.422894891 */, 16 }, /* 2149 */ { MAD_F(0x06c540b6) /* 0.423157416 */, 16 }, /* 2150 */ { MAD_F(0x06c65408) /* 0.423419982 */, 16 }, /* 2151 */ { MAD_F(0x06c76765) /* 0.423682588 */, 16 }, /* 2152 */ { MAD_F(0x06c87acc) /* 0.423945235 */, 16 }, /* 2153 */ { MAD_F(0x06c98e3f) /* 0.424207923 */, 16 }, /* 2154 */ { MAD_F(0x06caa1bd) /* 0.424470652 */, 16 }, /* 2155 */ { MAD_F(0x06cbb545) /* 0.424733421 */, 16 }, /* 2156 */ { MAD_F(0x06ccc8d9) /* 0.424996230 */, 16 }, /* 2157 */ { MAD_F(0x06cddc77) /* 0.425259081 */, 16 }, /* 2158 */ { MAD_F(0x06cef020) /* 0.425521972 */, 16 }, /* 2159 */ { MAD_F(0x06d003d4) /* 0.425784903 */, 16 }, /* 2160 */ { MAD_F(0x06d11794) /* 0.426047876 */, 16 }, /* 2161 */ { MAD_F(0x06d22b5e) /* 0.426310889 */, 16 }, /* 2162 */ { MAD_F(0x06d33f32) /* 0.426573942 */, 16 }, /* 2163 */ { MAD_F(0x06d45312) /* 0.426837036 */, 16 }, /* 2164 */ { MAD_F(0x06d566fd) /* 0.427100170 */, 16 }, /* 2165 */ { MAD_F(0x06d67af2) /* 0.427363345 */, 16 }, /* 2166 */ { MAD_F(0x06d78ef3) /* 0.427626561 */, 16 }, /* 2167 */ { MAD_F(0x06d8a2fe) /* 0.427889817 */, 16 }, /* 2168 */ { MAD_F(0x06d9b714) /* 0.428153114 */, 16 }, /* 2169 */ { MAD_F(0x06dacb35) /* 0.428416451 */, 16 }, /* 2170 */ { MAD_F(0x06dbdf61) /* 0.428679828 */, 16 }, /* 2171 */ { MAD_F(0x06dcf398) /* 0.428943246 */, 16 }, /* 2172 */ { MAD_F(0x06de07d9) /* 0.429206704 */, 16 }, /* 2173 */ { MAD_F(0x06df1c26) /* 0.429470203 */, 16 }, /* 2174 */ { MAD_F(0x06e0307d) /* 0.429733743 */, 16 }, /* 2175 */ { MAD_F(0x06e144df) /* 0.429997322 */, 16 }, /* 2176 */ { MAD_F(0x06e2594c) /* 0.430260942 */, 16 }, /* 2177 */ { MAD_F(0x06e36dc4) /* 0.430524603 */, 16 }, /* 2178 */ { MAD_F(0x06e48246) /* 0.430788304 */, 16 }, /* 2179 */ { MAD_F(0x06e596d4) /* 0.431052045 */, 16 }, /* 2180 */ { MAD_F(0x06e6ab6c) /* 0.431315826 */, 16 }, /* 2181 */ { MAD_F(0x06e7c00f) /* 0.431579648 */, 16 }, /* 2182 */ { MAD_F(0x06e8d4bd) /* 0.431843511 */, 16 }, /* 2183 */ { MAD_F(0x06e9e976) /* 0.432107413 */, 16 }, /* 2184 */ { MAD_F(0x06eafe3a) /* 0.432371356 */, 16 }, /* 2185 */ { MAD_F(0x06ec1308) /* 0.432635339 */, 16 }, /* 2186 */ { MAD_F(0x06ed27e2) /* 0.432899362 */, 16 }, /* 2187 */ { MAD_F(0x06ee3cc6) /* 0.433163426 */, 16 }, /* 2188 */ { MAD_F(0x06ef51b4) /* 0.433427530 */, 16 }, /* 2189 */ { MAD_F(0x06f066ae) /* 0.433691674 */, 16 }, /* 2190 */ { MAD_F(0x06f17bb3) /* 0.433955859 */, 16 }, /* 2191 */ { MAD_F(0x06f290c2) /* 0.434220083 */, 16 }, /* 2192 */ { MAD_F(0x06f3a5dc) /* 0.434484348 */, 16 }, /* 2193 */ { MAD_F(0x06f4bb01) /* 0.434748653 */, 16 }, /* 2194 */ { MAD_F(0x06f5d030) /* 0.435012998 */, 16 }, /* 2195 */ { MAD_F(0x06f6e56b) /* 0.435277383 */, 16 }, /* 2196 */ { MAD_F(0x06f7fab0) /* 0.435541809 */, 16 }, /* 2197 */ { MAD_F(0x06f91000) /* 0.435806274 */, 16 }, /* 2198 */ { MAD_F(0x06fa255a) /* 0.436070780 */, 16 }, /* 2199 */ { MAD_F(0x06fb3ac0) /* 0.436335326 */, 16 }, /* 2200 */ { MAD_F(0x06fc5030) /* 0.436599912 */, 16 }, /* 2201 */ { MAD_F(0x06fd65ab) /* 0.436864538 */, 16 }, /* 2202 */ { MAD_F(0x06fe7b31) /* 0.437129204 */, 16 }, /* 2203 */ { MAD_F(0x06ff90c2) /* 0.437393910 */, 16 }, /* 2204 */ { MAD_F(0x0700a65d) /* 0.437658657 */, 16 }, /* 2205 */ { MAD_F(0x0701bc03) /* 0.437923443 */, 16 }, /* 2206 */ { MAD_F(0x0702d1b4) /* 0.438188269 */, 16 }, /* 2207 */ { MAD_F(0x0703e76f) /* 0.438453136 */, 16 }, /* 2208 */ { MAD_F(0x0704fd35) /* 0.438718042 */, 16 }, /* 2209 */ { MAD_F(0x07061306) /* 0.438982988 */, 16 }, /* 2210 */ { MAD_F(0x070728e2) /* 0.439247975 */, 16 }, /* 2211 */ { MAD_F(0x07083ec9) /* 0.439513001 */, 16 }, /* 2212 */ { MAD_F(0x070954ba) /* 0.439778067 */, 16 }, /* 2213 */ { MAD_F(0x070a6ab6) /* 0.440043173 */, 16 }, /* 2214 */ { MAD_F(0x070b80bc) /* 0.440308320 */, 16 }, /* 2215 */ { MAD_F(0x070c96ce) /* 0.440573506 */, 16 }, /* 2216 */ { MAD_F(0x070dacea) /* 0.440838732 */, 16 }, /* 2217 */ { MAD_F(0x070ec310) /* 0.441103997 */, 16 }, /* 2218 */ { MAD_F(0x070fd942) /* 0.441369303 */, 16 }, /* 2219 */ { MAD_F(0x0710ef7e) /* 0.441634649 */, 16 }, /* 2220 */ { MAD_F(0x071205c5) /* 0.441900034 */, 16 }, /* 2221 */ { MAD_F(0x07131c17) /* 0.442165460 */, 16 }, /* 2222 */ { MAD_F(0x07143273) /* 0.442430925 */, 16 }, /* 2223 */ { MAD_F(0x071548da) /* 0.442696430 */, 16 }, /* 2224 */ { MAD_F(0x07165f4b) /* 0.442961975 */, 16 }, /* 2225 */ { MAD_F(0x071775c8) /* 0.443227559 */, 16 }, /* 2226 */ { MAD_F(0x07188c4f) /* 0.443493184 */, 16 }, /* 2227 */ { MAD_F(0x0719a2e0) /* 0.443758848 */, 16 }, /* 2228 */ { MAD_F(0x071ab97d) /* 0.444024552 */, 16 }, /* 2229 */ { MAD_F(0x071bd024) /* 0.444290296 */, 16 }, /* 2230 */ { MAD_F(0x071ce6d6) /* 0.444556079 */, 16 }, /* 2231 */ { MAD_F(0x071dfd92) /* 0.444821902 */, 16 }, /* 2232 */ { MAD_F(0x071f1459) /* 0.445087765 */, 16 }, /* 2233 */ { MAD_F(0x07202b2b) /* 0.445353668 */, 16 }, /* 2234 */ { MAD_F(0x07214207) /* 0.445619610 */, 16 }, /* 2235 */ { MAD_F(0x072258ee) /* 0.445885592 */, 16 }, /* 2236 */ { MAD_F(0x07236fe0) /* 0.446151614 */, 16 }, /* 2237 */ { MAD_F(0x072486dc) /* 0.446417675 */, 16 }, /* 2238 */ { MAD_F(0x07259de3) /* 0.446683776 */, 16 }, /* 2239 */ { MAD_F(0x0726b4f4) /* 0.446949917 */, 16 }, /* 2240 */ { MAD_F(0x0727cc11) /* 0.447216097 */, 16 }, /* 2241 */ { MAD_F(0x0728e338) /* 0.447482317 */, 16 }, /* 2242 */ { MAD_F(0x0729fa69) /* 0.447748576 */, 16 }, /* 2243 */ { MAD_F(0x072b11a5) /* 0.448014875 */, 16 }, /* 2244 */ { MAD_F(0x072c28ec) /* 0.448281214 */, 16 }, /* 2245 */ { MAD_F(0x072d403d) /* 0.448547592 */, 16 }, /* 2246 */ { MAD_F(0x072e5799) /* 0.448814010 */, 16 }, /* 2247 */ { MAD_F(0x072f6f00) /* 0.449080467 */, 16 }, /* 2248 */ { MAD_F(0x07308671) /* 0.449346964 */, 16 }, /* 2249 */ { MAD_F(0x07319ded) /* 0.449613501 */, 16 }, /* 2250 */ { MAD_F(0x0732b573) /* 0.449880076 */, 16 }, /* 2251 */ { MAD_F(0x0733cd04) /* 0.450146692 */, 16 }, /* 2252 */ { MAD_F(0x0734e4a0) /* 0.450413347 */, 16 }, /* 2253 */ { MAD_F(0x0735fc46) /* 0.450680041 */, 16 }, /* 2254 */ { MAD_F(0x073713f7) /* 0.450946775 */, 16 }, /* 2255 */ { MAD_F(0x07382bb2) /* 0.451213548 */, 16 }, /* 2256 */ { MAD_F(0x07394378) /* 0.451480360 */, 16 }, /* 2257 */ { MAD_F(0x073a5b49) /* 0.451747213 */, 16 }, /* 2258 */ { MAD_F(0x073b7324) /* 0.452014104 */, 16 }, /* 2259 */ { MAD_F(0x073c8b0a) /* 0.452281035 */, 16 }, /* 2260 */ { MAD_F(0x073da2fa) /* 0.452548005 */, 16 }, /* 2261 */ { MAD_F(0x073ebaf5) /* 0.452815015 */, 16 }, /* 2262 */ { MAD_F(0x073fd2fa) /* 0.453082064 */, 16 }, /* 2263 */ { MAD_F(0x0740eb0a) /* 0.453349152 */, 16 }, /* 2264 */ { MAD_F(0x07420325) /* 0.453616280 */, 16 }, /* 2265 */ { MAD_F(0x07431b4a) /* 0.453883447 */, 16 }, /* 2266 */ { MAD_F(0x0744337a) /* 0.454150653 */, 16 }, /* 2267 */ { MAD_F(0x07454bb4) /* 0.454417899 */, 16 }, /* 2268 */ { MAD_F(0x074663f8) /* 0.454685184 */, 16 }, /* 2269 */ { MAD_F(0x07477c48) /* 0.454952508 */, 16 }, /* 2270 */ { MAD_F(0x074894a2) /* 0.455219872 */, 16 }, /* 2271 */ { MAD_F(0x0749ad06) /* 0.455487275 */, 16 }, /* 2272 */ { MAD_F(0x074ac575) /* 0.455754717 */, 16 }, /* 2273 */ { MAD_F(0x074bddee) /* 0.456022198 */, 16 }, /* 2274 */ { MAD_F(0x074cf672) /* 0.456289719 */, 16 }, /* 2275 */ { MAD_F(0x074e0f01) /* 0.456557278 */, 16 }, /* 2276 */ { MAD_F(0x074f279a) /* 0.456824877 */, 16 }, /* 2277 */ { MAD_F(0x0750403e) /* 0.457092516 */, 16 }, /* 2278 */ { MAD_F(0x075158ec) /* 0.457360193 */, 16 }, /* 2279 */ { MAD_F(0x075271a4) /* 0.457627909 */, 16 }, /* 2280 */ { MAD_F(0x07538a67) /* 0.457895665 */, 16 }, /* 2281 */ { MAD_F(0x0754a335) /* 0.458163460 */, 16 }, /* 2282 */ { MAD_F(0x0755bc0d) /* 0.458431294 */, 16 }, /* 2283 */ { MAD_F(0x0756d4f0) /* 0.458699167 */, 16 }, /* 2284 */ { MAD_F(0x0757eddd) /* 0.458967079 */, 16 }, /* 2285 */ { MAD_F(0x075906d5) /* 0.459235030 */, 16 }, /* 2286 */ { MAD_F(0x075a1fd7) /* 0.459503021 */, 16 }, /* 2287 */ { MAD_F(0x075b38e3) /* 0.459771050 */, 16 }, /* 2288 */ { MAD_F(0x075c51fa) /* 0.460039119 */, 16 }, /* 2289 */ { MAD_F(0x075d6b1c) /* 0.460307226 */, 16 }, /* 2290 */ { MAD_F(0x075e8448) /* 0.460575373 */, 16 }, /* 2291 */ { MAD_F(0x075f9d7f) /* 0.460843559 */, 16 }, /* 2292 */ { MAD_F(0x0760b6c0) /* 0.461111783 */, 16 }, /* 2293 */ { MAD_F(0x0761d00b) /* 0.461380047 */, 16 }, /* 2294 */ { MAD_F(0x0762e961) /* 0.461648350 */, 16 }, /* 2295 */ { MAD_F(0x076402c1) /* 0.461916691 */, 16 }, /* 2296 */ { MAD_F(0x07651c2c) /* 0.462185072 */, 16 }, /* 2297 */ { MAD_F(0x076635a2) /* 0.462453492 */, 16 }, /* 2298 */ { MAD_F(0x07674f22) /* 0.462721950 */, 16 }, /* 2299 */ { MAD_F(0x076868ac) /* 0.462990448 */, 16 }, /* 2300 */ { MAD_F(0x07698240) /* 0.463258984 */, 16 }, /* 2301 */ { MAD_F(0x076a9be0) /* 0.463527560 */, 16 }, /* 2302 */ { MAD_F(0x076bb589) /* 0.463796174 */, 16 }, /* 2303 */ { MAD_F(0x076ccf3d) /* 0.464064827 */, 16 }, /* 2304 */ { MAD_F(0x076de8fc) /* 0.464333519 */, 16 }, /* 2305 */ { MAD_F(0x076f02c5) /* 0.464602250 */, 16 }, /* 2306 */ { MAD_F(0x07701c98) /* 0.464871020 */, 16 }, /* 2307 */ { MAD_F(0x07713676) /* 0.465139829 */, 16 }, /* 2308 */ { MAD_F(0x0772505e) /* 0.465408676 */, 16 }, /* 2309 */ { MAD_F(0x07736a51) /* 0.465677563 */, 16 }, /* 2310 */ { MAD_F(0x0774844e) /* 0.465946488 */, 16 }, /* 2311 */ { MAD_F(0x07759e55) /* 0.466215452 */, 16 }, /* 2312 */ { MAD_F(0x0776b867) /* 0.466484455 */, 16 }, /* 2313 */ { MAD_F(0x0777d283) /* 0.466753496 */, 16 }, /* 2314 */ { MAD_F(0x0778ecaa) /* 0.467022577 */, 16 }, /* 2315 */ { MAD_F(0x077a06db) /* 0.467291696 */, 16 }, /* 2316 */ { MAD_F(0x077b2117) /* 0.467560854 */, 16 }, /* 2317 */ { MAD_F(0x077c3b5d) /* 0.467830050 */, 16 }, /* 2318 */ { MAD_F(0x077d55ad) /* 0.468099285 */, 16 }, /* 2319 */ { MAD_F(0x077e7008) /* 0.468368560 */, 16 }, /* 2320 */ { MAD_F(0x077f8a6d) /* 0.468637872 */, 16 }, /* 2321 */ { MAD_F(0x0780a4dc) /* 0.468907224 */, 16 }, /* 2322 */ { MAD_F(0x0781bf56) /* 0.469176614 */, 16 }, /* 2323 */ { MAD_F(0x0782d9da) /* 0.469446043 */, 16 }, /* 2324 */ { MAD_F(0x0783f469) /* 0.469715510 */, 16 }, /* 2325 */ { MAD_F(0x07850f02) /* 0.469985016 */, 16 }, /* 2326 */ { MAD_F(0x078629a5) /* 0.470254561 */, 16 }, /* 2327 */ { MAD_F(0x07874453) /* 0.470524145 */, 16 }, /* 2328 */ { MAD_F(0x07885f0b) /* 0.470793767 */, 16 }, /* 2329 */ { MAD_F(0x078979ce) /* 0.471063427 */, 16 }, /* 2330 */ { MAD_F(0x078a949a) /* 0.471333126 */, 16 }, /* 2331 */ { MAD_F(0x078baf72) /* 0.471602864 */, 16 }, /* 2332 */ { MAD_F(0x078cca53) /* 0.471872641 */, 16 }, /* 2333 */ { MAD_F(0x078de53f) /* 0.472142456 */, 16 }, /* 2334 */ { MAD_F(0x078f0035) /* 0.472412309 */, 16 }, /* 2335 */ { MAD_F(0x07901b36) /* 0.472682201 */, 16 }, /* 2336 */ { MAD_F(0x07913641) /* 0.472952132 */, 16 }, /* 2337 */ { MAD_F(0x07925156) /* 0.473222101 */, 16 }, /* 2338 */ { MAD_F(0x07936c76) /* 0.473492108 */, 16 }, /* 2339 */ { MAD_F(0x079487a0) /* 0.473762155 */, 16 }, /* 2340 */ { MAD_F(0x0795a2d4) /* 0.474032239 */, 16 }, /* 2341 */ { MAD_F(0x0796be13) /* 0.474302362 */, 16 }, /* 2342 */ { MAD_F(0x0797d95c) /* 0.474572524 */, 16 }, /* 2343 */ { MAD_F(0x0798f4af) /* 0.474842724 */, 16 }, /* 2344 */ { MAD_F(0x079a100c) /* 0.475112962 */, 16 }, /* 2345 */ { MAD_F(0x079b2b74) /* 0.475383239 */, 16 }, /* 2346 */ { MAD_F(0x079c46e7) /* 0.475653554 */, 16 }, /* 2347 */ { MAD_F(0x079d6263) /* 0.475923908 */, 16 }, /* 2348 */ { MAD_F(0x079e7dea) /* 0.476194300 */, 16 }, /* 2349 */ { MAD_F(0x079f997b) /* 0.476464731 */, 16 }, /* 2350 */ { MAD_F(0x07a0b516) /* 0.476735200 */, 16 }, /* 2351 */ { MAD_F(0x07a1d0bc) /* 0.477005707 */, 16 }, /* 2352 */ { MAD_F(0x07a2ec6c) /* 0.477276252 */, 16 }, /* 2353 */ { MAD_F(0x07a40827) /* 0.477546836 */, 16 }, /* 2354 */ { MAD_F(0x07a523eb) /* 0.477817459 */, 16 }, /* 2355 */ { MAD_F(0x07a63fba) /* 0.478088119 */, 16 }, /* 2356 */ { MAD_F(0x07a75b93) /* 0.478358818 */, 16 }, /* 2357 */ { MAD_F(0x07a87777) /* 0.478629555 */, 16 }, /* 2358 */ { MAD_F(0x07a99364) /* 0.478900331 */, 16 }, /* 2359 */ { MAD_F(0x07aaaf5c) /* 0.479171145 */, 16 }, /* 2360 */ { MAD_F(0x07abcb5f) /* 0.479441997 */, 16 }, /* 2361 */ { MAD_F(0x07ace76b) /* 0.479712887 */, 16 }, /* 2362 */ { MAD_F(0x07ae0382) /* 0.479983816 */, 16 }, /* 2363 */ { MAD_F(0x07af1fa3) /* 0.480254782 */, 16 }, /* 2364 */ { MAD_F(0x07b03bcf) /* 0.480525787 */, 16 }, /* 2365 */ { MAD_F(0x07b15804) /* 0.480796831 */, 16 }, /* 2366 */ { MAD_F(0x07b27444) /* 0.481067912 */, 16 }, /* 2367 */ { MAD_F(0x07b3908e) /* 0.481339032 */, 16 }, /* 2368 */ { MAD_F(0x07b4ace3) /* 0.481610189 */, 16 }, /* 2369 */ { MAD_F(0x07b5c941) /* 0.481881385 */, 16 }, /* 2370 */ { MAD_F(0x07b6e5aa) /* 0.482152620 */, 16 }, /* 2371 */ { MAD_F(0x07b8021d) /* 0.482423892 */, 16 }, /* 2372 */ { MAD_F(0x07b91e9b) /* 0.482695202 */, 16 }, /* 2373 */ { MAD_F(0x07ba3b22) /* 0.482966551 */, 16 }, /* 2374 */ { MAD_F(0x07bb57b4) /* 0.483237938 */, 16 }, /* 2375 */ { MAD_F(0x07bc7450) /* 0.483509362 */, 16 }, /* 2376 */ { MAD_F(0x07bd90f6) /* 0.483780825 */, 16 }, /* 2377 */ { MAD_F(0x07beada7) /* 0.484052326 */, 16 }, /* 2378 */ { MAD_F(0x07bfca61) /* 0.484323865 */, 16 }, /* 2379 */ { MAD_F(0x07c0e726) /* 0.484595443 */, 16 }, /* 2380 */ { MAD_F(0x07c203f5) /* 0.484867058 */, 16 }, /* 2381 */ { MAD_F(0x07c320cf) /* 0.485138711 */, 16 }, /* 2382 */ { MAD_F(0x07c43db2) /* 0.485410402 */, 16 }, /* 2383 */ { MAD_F(0x07c55aa0) /* 0.485682131 */, 16 }, /* 2384 */ { MAD_F(0x07c67798) /* 0.485953899 */, 16 }, /* 2385 */ { MAD_F(0x07c7949a) /* 0.486225704 */, 16 }, /* 2386 */ { MAD_F(0x07c8b1a7) /* 0.486497547 */, 16 }, /* 2387 */ { MAD_F(0x07c9cebd) /* 0.486769429 */, 16 }, /* 2388 */ { MAD_F(0x07caebde) /* 0.487041348 */, 16 }, /* 2389 */ { MAD_F(0x07cc0909) /* 0.487313305 */, 16 }, /* 2390 */ { MAD_F(0x07cd263e) /* 0.487585300 */, 16 }, /* 2391 */ { MAD_F(0x07ce437d) /* 0.487857333 */, 16 }, /* 2392 */ { MAD_F(0x07cf60c7) /* 0.488129404 */, 16 }, /* 2393 */ { MAD_F(0x07d07e1b) /* 0.488401513 */, 16 }, /* 2394 */ { MAD_F(0x07d19b79) /* 0.488673660 */, 16 }, /* 2395 */ { MAD_F(0x07d2b8e1) /* 0.488945845 */, 16 }, /* 2396 */ { MAD_F(0x07d3d653) /* 0.489218067 */, 16 }, /* 2397 */ { MAD_F(0x07d4f3cf) /* 0.489490328 */, 16 }, /* 2398 */ { MAD_F(0x07d61156) /* 0.489762626 */, 16 }, /* 2399 */ { MAD_F(0x07d72ee6) /* 0.490034962 */, 16 }, /* 2400 */ { MAD_F(0x07d84c81) /* 0.490307336 */, 16 }, /* 2401 */ { MAD_F(0x07d96a26) /* 0.490579748 */, 16 }, /* 2402 */ { MAD_F(0x07da87d5) /* 0.490852198 */, 16 }, /* 2403 */ { MAD_F(0x07dba58f) /* 0.491124686 */, 16 }, /* 2404 */ { MAD_F(0x07dcc352) /* 0.491397211 */, 16 }, /* 2405 */ { MAD_F(0x07dde120) /* 0.491669774 */, 16 }, /* 2406 */ { MAD_F(0x07defef7) /* 0.491942375 */, 16 }, /* 2407 */ { MAD_F(0x07e01cd9) /* 0.492215014 */, 16 }, /* 2408 */ { MAD_F(0x07e13ac5) /* 0.492487690 */, 16 }, /* 2409 */ { MAD_F(0x07e258bc) /* 0.492760404 */, 16 }, /* 2410 */ { MAD_F(0x07e376bc) /* 0.493033156 */, 16 }, /* 2411 */ { MAD_F(0x07e494c6) /* 0.493305946 */, 16 }, /* 2412 */ { MAD_F(0x07e5b2db) /* 0.493578773 */, 16 }, /* 2413 */ { MAD_F(0x07e6d0f9) /* 0.493851638 */, 16 }, /* 2414 */ { MAD_F(0x07e7ef22) /* 0.494124541 */, 16 }, /* 2415 */ { MAD_F(0x07e90d55) /* 0.494397481 */, 16 }, /* 2416 */ { MAD_F(0x07ea2b92) /* 0.494670459 */, 16 }, /* 2417 */ { MAD_F(0x07eb49d9) /* 0.494943475 */, 16 }, /* 2418 */ { MAD_F(0x07ec682a) /* 0.495216529 */, 16 }, /* 2419 */ { MAD_F(0x07ed8686) /* 0.495489620 */, 16 }, /* 2420 */ { MAD_F(0x07eea4eb) /* 0.495762748 */, 16 }, /* 2421 */ { MAD_F(0x07efc35b) /* 0.496035915 */, 16 }, /* 2422 */ { MAD_F(0x07f0e1d4) /* 0.496309119 */, 16 }, /* 2423 */ { MAD_F(0x07f20058) /* 0.496582360 */, 16 }, /* 2424 */ { MAD_F(0x07f31ee6) /* 0.496855639 */, 16 }, /* 2425 */ { MAD_F(0x07f43d7e) /* 0.497128956 */, 16 }, /* 2426 */ { MAD_F(0x07f55c20) /* 0.497402310 */, 16 }, /* 2427 */ { MAD_F(0x07f67acc) /* 0.497675702 */, 16 }, /* 2428 */ { MAD_F(0x07f79982) /* 0.497949132 */, 16 }, /* 2429 */ { MAD_F(0x07f8b842) /* 0.498222598 */, 16 }, /* 2430 */ { MAD_F(0x07f9d70c) /* 0.498496103 */, 16 }, /* 2431 */ { MAD_F(0x07faf5e1) /* 0.498769645 */, 16 }, /* 2432 */ { MAD_F(0x07fc14bf) /* 0.499043224 */, 16 }, /* 2433 */ { MAD_F(0x07fd33a8) /* 0.499316841 */, 16 }, /* 2434 */ { MAD_F(0x07fe529a) /* 0.499590496 */, 16 }, /* 2435 */ { MAD_F(0x07ff7197) /* 0.499864188 */, 16 }, /* 2436 */ { MAD_F(0x0400484f) /* 0.250068959 */, 17 }, /* 2437 */ { MAD_F(0x0400d7d7) /* 0.250205842 */, 17 }, /* 2438 */ { MAD_F(0x04016764) /* 0.250342744 */, 17 }, /* 2439 */ { MAD_F(0x0401f6f7) /* 0.250479665 */, 17 }, /* 2440 */ { MAD_F(0x0402868e) /* 0.250616605 */, 17 }, /* 2441 */ { MAD_F(0x0403162b) /* 0.250753563 */, 17 }, /* 2442 */ { MAD_F(0x0403a5cc) /* 0.250890540 */, 17 }, /* 2443 */ { MAD_F(0x04043573) /* 0.251027536 */, 17 }, /* 2444 */ { MAD_F(0x0404c51e) /* 0.251164550 */, 17 }, /* 2445 */ { MAD_F(0x040554cf) /* 0.251301583 */, 17 }, /* 2446 */ { MAD_F(0x0405e484) /* 0.251438635 */, 17 }, /* 2447 */ { MAD_F(0x0406743f) /* 0.251575706 */, 17 }, /* 2448 */ { MAD_F(0x040703ff) /* 0.251712795 */, 17 }, /* 2449 */ { MAD_F(0x040793c3) /* 0.251849903 */, 17 }, /* 2450 */ { MAD_F(0x0408238d) /* 0.251987029 */, 17 }, /* 2451 */ { MAD_F(0x0408b35b) /* 0.252124174 */, 17 }, /* 2452 */ { MAD_F(0x0409432f) /* 0.252261338 */, 17 }, /* 2453 */ { MAD_F(0x0409d308) /* 0.252398520 */, 17 }, /* 2454 */ { MAD_F(0x040a62e5) /* 0.252535721 */, 17 }, /* 2455 */ { MAD_F(0x040af2c8) /* 0.252672941 */, 17 }, /* 2456 */ { MAD_F(0x040b82b0) /* 0.252810180 */, 17 }, /* 2457 */ { MAD_F(0x040c129c) /* 0.252947436 */, 17 }, /* 2458 */ { MAD_F(0x040ca28e) /* 0.253084712 */, 17 }, /* 2459 */ { MAD_F(0x040d3284) /* 0.253222006 */, 17 }, /* 2460 */ { MAD_F(0x040dc280) /* 0.253359319 */, 17 }, /* 2461 */ { MAD_F(0x040e5281) /* 0.253496651 */, 17 }, /* 2462 */ { MAD_F(0x040ee286) /* 0.253634001 */, 17 }, /* 2463 */ { MAD_F(0x040f7291) /* 0.253771369 */, 17 }, /* 2464 */ { MAD_F(0x041002a1) /* 0.253908756 */, 17 }, /* 2465 */ { MAD_F(0x041092b5) /* 0.254046162 */, 17 }, /* 2466 */ { MAD_F(0x041122cf) /* 0.254183587 */, 17 }, /* 2467 */ { MAD_F(0x0411b2ed) /* 0.254321030 */, 17 }, /* 2468 */ { MAD_F(0x04124311) /* 0.254458491 */, 17 }, /* 2469 */ { MAD_F(0x0412d339) /* 0.254595971 */, 17 }, /* 2470 */ { MAD_F(0x04136367) /* 0.254733470 */, 17 }, /* 2471 */ { MAD_F(0x0413f399) /* 0.254870987 */, 17 }, /* 2472 */ { MAD_F(0x041483d1) /* 0.255008523 */, 17 }, /* 2473 */ { MAD_F(0x0415140d) /* 0.255146077 */, 17 }, /* 2474 */ { MAD_F(0x0415a44f) /* 0.255283650 */, 17 }, /* 2475 */ { MAD_F(0x04163495) /* 0.255421241 */, 17 }, /* 2476 */ { MAD_F(0x0416c4e1) /* 0.255558851 */, 17 }, /* 2477 */ { MAD_F(0x04175531) /* 0.255696480 */, 17 }, /* 2478 */ { MAD_F(0x0417e586) /* 0.255834127 */, 17 }, /* 2479 */ { MAD_F(0x041875e1) /* 0.255971792 */, 17 }, /* 2480 */ { MAD_F(0x04190640) /* 0.256109476 */, 17 }, /* 2481 */ { MAD_F(0x041996a4) /* 0.256247179 */, 17 }, /* 2482 */ { MAD_F(0x041a270d) /* 0.256384900 */, 17 }, /* 2483 */ { MAD_F(0x041ab77b) /* 0.256522639 */, 17 }, /* 2484 */ { MAD_F(0x041b47ef) /* 0.256660397 */, 17 }, /* 2485 */ { MAD_F(0x041bd867) /* 0.256798174 */, 17 }, /* 2486 */ { MAD_F(0x041c68e4) /* 0.256935969 */, 17 }, /* 2487 */ { MAD_F(0x041cf966) /* 0.257073782 */, 17 }, /* 2488 */ { MAD_F(0x041d89ed) /* 0.257211614 */, 17 }, /* 2489 */ { MAD_F(0x041e1a79) /* 0.257349465 */, 17 }, /* 2490 */ { MAD_F(0x041eab0a) /* 0.257487334 */, 17 }, /* 2491 */ { MAD_F(0x041f3b9f) /* 0.257625221 */, 17 }, /* 2492 */ { MAD_F(0x041fcc3a) /* 0.257763127 */, 17 }, /* 2493 */ { MAD_F(0x04205cda) /* 0.257901051 */, 17 }, /* 2494 */ { MAD_F(0x0420ed7f) /* 0.258038994 */, 17 }, /* 2495 */ { MAD_F(0x04217e28) /* 0.258176955 */, 17 }, /* 2496 */ { MAD_F(0x04220ed7) /* 0.258314934 */, 17 }, /* 2497 */ { MAD_F(0x04229f8a) /* 0.258452932 */, 17 }, /* 2498 */ { MAD_F(0x04233043) /* 0.258590948 */, 17 }, /* 2499 */ { MAD_F(0x0423c100) /* 0.258728983 */, 17 }, /* 2500 */ { MAD_F(0x042451c3) /* 0.258867036 */, 17 }, /* 2501 */ { MAD_F(0x0424e28a) /* 0.259005108 */, 17 }, /* 2502 */ { MAD_F(0x04257356) /* 0.259143198 */, 17 }, /* 2503 */ { MAD_F(0x04260428) /* 0.259281307 */, 17 }, /* 2504 */ { MAD_F(0x042694fe) /* 0.259419433 */, 17 }, /* 2505 */ { MAD_F(0x042725d9) /* 0.259557579 */, 17 }, /* 2506 */ { MAD_F(0x0427b6b9) /* 0.259695742 */, 17 }, /* 2507 */ { MAD_F(0x0428479e) /* 0.259833924 */, 17 }, /* 2508 */ { MAD_F(0x0428d888) /* 0.259972124 */, 17 }, /* 2509 */ { MAD_F(0x04296976) /* 0.260110343 */, 17 }, /* 2510 */ { MAD_F(0x0429fa6a) /* 0.260248580 */, 17 }, /* 2511 */ { MAD_F(0x042a8b63) /* 0.260386836 */, 17 }, /* 2512 */ { MAD_F(0x042b1c60) /* 0.260525110 */, 17 }, /* 2513 */ { MAD_F(0x042bad63) /* 0.260663402 */, 17 }, /* 2514 */ { MAD_F(0x042c3e6a) /* 0.260801712 */, 17 }, /* 2515 */ { MAD_F(0x042ccf77) /* 0.260940041 */, 17 }, /* 2516 */ { MAD_F(0x042d6088) /* 0.261078388 */, 17 }, /* 2517 */ { MAD_F(0x042df19e) /* 0.261216754 */, 17 }, /* 2518 */ { MAD_F(0x042e82b9) /* 0.261355137 */, 17 }, /* 2519 */ { MAD_F(0x042f13d9) /* 0.261493540 */, 17 }, /* 2520 */ { MAD_F(0x042fa4fe) /* 0.261631960 */, 17 }, /* 2521 */ { MAD_F(0x04303628) /* 0.261770399 */, 17 }, /* 2522 */ { MAD_F(0x0430c757) /* 0.261908856 */, 17 }, /* 2523 */ { MAD_F(0x0431588b) /* 0.262047331 */, 17 }, /* 2524 */ { MAD_F(0x0431e9c3) /* 0.262185825 */, 17 }, /* 2525 */ { MAD_F(0x04327b01) /* 0.262324337 */, 17 }, /* 2526 */ { MAD_F(0x04330c43) /* 0.262462867 */, 17 }, /* 2527 */ { MAD_F(0x04339d8a) /* 0.262601416 */, 17 }, /* 2528 */ { MAD_F(0x04342ed7) /* 0.262739982 */, 17 }, /* 2529 */ { MAD_F(0x0434c028) /* 0.262878568 */, 17 }, /* 2530 */ { MAD_F(0x0435517e) /* 0.263017171 */, 17 }, /* 2531 */ { MAD_F(0x0435e2d9) /* 0.263155792 */, 17 }, /* 2532 */ { MAD_F(0x04367439) /* 0.263294432 */, 17 }, /* 2533 */ { MAD_F(0x0437059e) /* 0.263433090 */, 17 }, /* 2534 */ { MAD_F(0x04379707) /* 0.263571767 */, 17 }, /* 2535 */ { MAD_F(0x04382876) /* 0.263710461 */, 17 }, /* 2536 */ { MAD_F(0x0438b9e9) /* 0.263849174 */, 17 }, /* 2537 */ { MAD_F(0x04394b61) /* 0.263987905 */, 17 }, /* 2538 */ { MAD_F(0x0439dcdf) /* 0.264126655 */, 17 }, /* 2539 */ { MAD_F(0x043a6e61) /* 0.264265422 */, 17 }, /* 2540 */ { MAD_F(0x043affe8) /* 0.264404208 */, 17 }, /* 2541 */ { MAD_F(0x043b9174) /* 0.264543012 */, 17 }, /* 2542 */ { MAD_F(0x043c2305) /* 0.264681834 */, 17 }, /* 2543 */ { MAD_F(0x043cb49a) /* 0.264820674 */, 17 }, /* 2544 */ { MAD_F(0x043d4635) /* 0.264959533 */, 17 }, /* 2545 */ { MAD_F(0x043dd7d4) /* 0.265098410 */, 17 }, /* 2546 */ { MAD_F(0x043e6979) /* 0.265237305 */, 17 }, /* 2547 */ { MAD_F(0x043efb22) /* 0.265376218 */, 17 }, /* 2548 */ { MAD_F(0x043f8cd0) /* 0.265515149 */, 17 }, /* 2549 */ { MAD_F(0x04401e83) /* 0.265654099 */, 17 }, /* 2550 */ { MAD_F(0x0440b03b) /* 0.265793066 */, 17 }, /* 2551 */ { MAD_F(0x044141f7) /* 0.265932052 */, 17 }, /* 2552 */ { MAD_F(0x0441d3b9) /* 0.266071056 */, 17 }, /* 2553 */ { MAD_F(0x04426580) /* 0.266210078 */, 17 }, /* 2554 */ { MAD_F(0x0442f74b) /* 0.266349119 */, 17 }, /* 2555 */ { MAD_F(0x0443891b) /* 0.266488177 */, 17 }, /* 2556 */ { MAD_F(0x04441af0) /* 0.266627254 */, 17 }, /* 2557 */ { MAD_F(0x0444acca) /* 0.266766349 */, 17 }, /* 2558 */ { MAD_F(0x04453ea9) /* 0.266905462 */, 17 }, /* 2559 */ { MAD_F(0x0445d08d) /* 0.267044593 */, 17 }, /* 2560 */ { MAD_F(0x04466275) /* 0.267183742 */, 17 }, /* 2561 */ { MAD_F(0x0446f463) /* 0.267322909 */, 17 }, /* 2562 */ { MAD_F(0x04478655) /* 0.267462094 */, 17 }, /* 2563 */ { MAD_F(0x0448184c) /* 0.267601298 */, 17 }, /* 2564 */ { MAD_F(0x0448aa48) /* 0.267740519 */, 17 }, /* 2565 */ { MAD_F(0x04493c49) /* 0.267879759 */, 17 }, /* 2566 */ { MAD_F(0x0449ce4f) /* 0.268019017 */, 17 }, /* 2567 */ { MAD_F(0x044a6059) /* 0.268158293 */, 17 }, /* 2568 */ { MAD_F(0x044af269) /* 0.268297587 */, 17 }, /* 2569 */ { MAD_F(0x044b847d) /* 0.268436899 */, 17 }, /* 2570 */ { MAD_F(0x044c1696) /* 0.268576229 */, 17 }, /* 2571 */ { MAD_F(0x044ca8b4) /* 0.268715577 */, 17 }, /* 2572 */ { MAD_F(0x044d3ad7) /* 0.268854943 */, 17 }, /* 2573 */ { MAD_F(0x044dccff) /* 0.268994328 */, 17 }, /* 2574 */ { MAD_F(0x044e5f2b) /* 0.269133730 */, 17 }, /* 2575 */ { MAD_F(0x044ef15d) /* 0.269273150 */, 17 }, /* 2576 */ { MAD_F(0x044f8393) /* 0.269412589 */, 17 }, /* 2577 */ { MAD_F(0x045015ce) /* 0.269552045 */, 17 }, /* 2578 */ { MAD_F(0x0450a80e) /* 0.269691520 */, 17 }, /* 2579 */ { MAD_F(0x04513a53) /* 0.269831013 */, 17 }, /* 2580 */ { MAD_F(0x0451cc9c) /* 0.269970523 */, 17 }, /* 2581 */ { MAD_F(0x04525eeb) /* 0.270110052 */, 17 }, /* 2582 */ { MAD_F(0x0452f13e) /* 0.270249599 */, 17 }, /* 2583 */ { MAD_F(0x04538396) /* 0.270389163 */, 17 }, /* 2584 */ { MAD_F(0x045415f3) /* 0.270528746 */, 17 }, /* 2585 */ { MAD_F(0x0454a855) /* 0.270668347 */, 17 }, /* 2586 */ { MAD_F(0x04553abb) /* 0.270807965 */, 17 }, /* 2587 */ { MAD_F(0x0455cd27) /* 0.270947602 */, 17 }, /* 2588 */ { MAD_F(0x04565f97) /* 0.271087257 */, 17 }, /* 2589 */ { MAD_F(0x0456f20c) /* 0.271226930 */, 17 }, /* 2590 */ { MAD_F(0x04578486) /* 0.271366620 */, 17 }, /* 2591 */ { MAD_F(0x04581705) /* 0.271506329 */, 17 }, /* 2592 */ { MAD_F(0x0458a989) /* 0.271646056 */, 17 }, /* 2593 */ { MAD_F(0x04593c11) /* 0.271785800 */, 17 }, /* 2594 */ { MAD_F(0x0459ce9e) /* 0.271925563 */, 17 }, /* 2595 */ { MAD_F(0x045a6130) /* 0.272065343 */, 17 }, /* 2596 */ { MAD_F(0x045af3c7) /* 0.272205142 */, 17 }, /* 2597 */ { MAD_F(0x045b8663) /* 0.272344958 */, 17 }, /* 2598 */ { MAD_F(0x045c1903) /* 0.272484793 */, 17 }, /* 2599 */ { MAD_F(0x045caba9) /* 0.272624645 */, 17 }, /* 2600 */ { MAD_F(0x045d3e53) /* 0.272764515 */, 17 }, /* 2601 */ { MAD_F(0x045dd102) /* 0.272904403 */, 17 }, /* 2602 */ { MAD_F(0x045e63b6) /* 0.273044310 */, 17 }, /* 2603 */ { MAD_F(0x045ef66e) /* 0.273184234 */, 17 }, /* 2604 */ { MAD_F(0x045f892b) /* 0.273324176 */, 17 }, /* 2605 */ { MAD_F(0x04601bee) /* 0.273464136 */, 17 }, /* 2606 */ { MAD_F(0x0460aeb5) /* 0.273604113 */, 17 }, /* 2607 */ { MAD_F(0x04614180) /* 0.273744109 */, 17 }, /* 2608 */ { MAD_F(0x0461d451) /* 0.273884123 */, 17 }, /* 2609 */ { MAD_F(0x04626727) /* 0.274024154 */, 17 }, /* 2610 */ { MAD_F(0x0462fa01) /* 0.274164204 */, 17 }, /* 2611 */ { MAD_F(0x04638ce0) /* 0.274304271 */, 17 }, /* 2612 */ { MAD_F(0x04641fc4) /* 0.274444356 */, 17 }, /* 2613 */ { MAD_F(0x0464b2ac) /* 0.274584459 */, 17 }, /* 2614 */ { MAD_F(0x0465459a) /* 0.274724580 */, 17 }, /* 2615 */ { MAD_F(0x0465d88c) /* 0.274864719 */, 17 }, /* 2616 */ { MAD_F(0x04666b83) /* 0.275004875 */, 17 }, /* 2617 */ { MAD_F(0x0466fe7f) /* 0.275145050 */, 17 }, /* 2618 */ { MAD_F(0x0467917f) /* 0.275285242 */, 17 }, /* 2619 */ { MAD_F(0x04682485) /* 0.275425452 */, 17 }, /* 2620 */ { MAD_F(0x0468b78f) /* 0.275565681 */, 17 }, /* 2621 */ { MAD_F(0x04694a9e) /* 0.275705926 */, 17 }, /* 2622 */ { MAD_F(0x0469ddb2) /* 0.275846190 */, 17 }, /* 2623 */ { MAD_F(0x046a70ca) /* 0.275986472 */, 17 }, /* 2624 */ { MAD_F(0x046b03e7) /* 0.276126771 */, 17 }, /* 2625 */ { MAD_F(0x046b970a) /* 0.276267088 */, 17 }, /* 2626 */ { MAD_F(0x046c2a31) /* 0.276407423 */, 17 }, /* 2627 */ { MAD_F(0x046cbd5c) /* 0.276547776 */, 17 }, /* 2628 */ { MAD_F(0x046d508d) /* 0.276688147 */, 17 }, /* 2629 */ { MAD_F(0x046de3c2) /* 0.276828535 */, 17 }, /* 2630 */ { MAD_F(0x046e76fc) /* 0.276968942 */, 17 }, /* 2631 */ { MAD_F(0x046f0a3b) /* 0.277109366 */, 17 }, /* 2632 */ { MAD_F(0x046f9d7e) /* 0.277249808 */, 17 }, /* 2633 */ { MAD_F(0x047030c7) /* 0.277390267 */, 17 }, /* 2634 */ { MAD_F(0x0470c414) /* 0.277530745 */, 17 }, /* 2635 */ { MAD_F(0x04715766) /* 0.277671240 */, 17 }, /* 2636 */ { MAD_F(0x0471eabc) /* 0.277811753 */, 17 }, /* 2637 */ { MAD_F(0x04727e18) /* 0.277952284 */, 17 }, /* 2638 */ { MAD_F(0x04731178) /* 0.278092832 */, 17 }, /* 2639 */ { MAD_F(0x0473a4dd) /* 0.278233399 */, 17 }, /* 2640 */ { MAD_F(0x04743847) /* 0.278373983 */, 17 }, /* 2641 */ { MAD_F(0x0474cbb5) /* 0.278514584 */, 17 }, /* 2642 */ { MAD_F(0x04755f29) /* 0.278655204 */, 17 }, /* 2643 */ { MAD_F(0x0475f2a1) /* 0.278795841 */, 17 }, /* 2644 */ { MAD_F(0x0476861d) /* 0.278936496 */, 17 }, /* 2645 */ { MAD_F(0x0477199f) /* 0.279077169 */, 17 }, /* 2646 */ { MAD_F(0x0477ad25) /* 0.279217860 */, 17 }, /* 2647 */ { MAD_F(0x047840b0) /* 0.279358568 */, 17 }, /* 2648 */ { MAD_F(0x0478d440) /* 0.279499294 */, 17 }, /* 2649 */ { MAD_F(0x047967d5) /* 0.279640037 */, 17 }, /* 2650 */ { MAD_F(0x0479fb6e) /* 0.279780799 */, 17 }, /* 2651 */ { MAD_F(0x047a8f0c) /* 0.279921578 */, 17 }, /* 2652 */ { MAD_F(0x047b22af) /* 0.280062375 */, 17 }, /* 2653 */ { MAD_F(0x047bb657) /* 0.280203189 */, 17 }, /* 2654 */ { MAD_F(0x047c4a03) /* 0.280344021 */, 17 }, /* 2655 */ { MAD_F(0x047cddb4) /* 0.280484871 */, 17 }, /* 2656 */ { MAD_F(0x047d716a) /* 0.280625739 */, 17 }, /* 2657 */ { MAD_F(0x047e0524) /* 0.280766624 */, 17 }, /* 2658 */ { MAD_F(0x047e98e4) /* 0.280907527 */, 17 }, /* 2659 */ { MAD_F(0x047f2ca8) /* 0.281048447 */, 17 }, /* 2660 */ { MAD_F(0x047fc071) /* 0.281189385 */, 17 }, /* 2661 */ { MAD_F(0x0480543e) /* 0.281330341 */, 17 }, /* 2662 */ { MAD_F(0x0480e811) /* 0.281471315 */, 17 }, /* 2663 */ { MAD_F(0x04817be8) /* 0.281612306 */, 17 }, /* 2664 */ { MAD_F(0x04820fc3) /* 0.281753315 */, 17 }, /* 2665 */ { MAD_F(0x0482a3a4) /* 0.281894341 */, 17 }, /* 2666 */ { MAD_F(0x04833789) /* 0.282035386 */, 17 }, /* 2667 */ { MAD_F(0x0483cb73) /* 0.282176447 */, 17 }, /* 2668 */ { MAD_F(0x04845f62) /* 0.282317527 */, 17 }, /* 2669 */ { MAD_F(0x0484f355) /* 0.282458624 */, 17 }, /* 2670 */ { MAD_F(0x0485874d) /* 0.282599738 */, 17 }, /* 2671 */ { MAD_F(0x04861b4a) /* 0.282740871 */, 17 }, /* 2672 */ { MAD_F(0x0486af4c) /* 0.282882021 */, 17 }, /* 2673 */ { MAD_F(0x04874352) /* 0.283023188 */, 17 }, /* 2674 */ { MAD_F(0x0487d75d) /* 0.283164373 */, 17 }, /* 2675 */ { MAD_F(0x04886b6d) /* 0.283305576 */, 17 }, /* 2676 */ { MAD_F(0x0488ff82) /* 0.283446796 */, 17 }, /* 2677 */ { MAD_F(0x0489939b) /* 0.283588034 */, 17 }, /* 2678 */ { MAD_F(0x048a27b9) /* 0.283729290 */, 17 }, /* 2679 */ { MAD_F(0x048abbdc) /* 0.283870563 */, 17 }, /* 2680 */ { MAD_F(0x048b5003) /* 0.284011853 */, 17 }, /* 2681 */ { MAD_F(0x048be42f) /* 0.284153161 */, 17 }, /* 2682 */ { MAD_F(0x048c7860) /* 0.284294487 */, 17 }, /* 2683 */ { MAD_F(0x048d0c96) /* 0.284435831 */, 17 }, /* 2684 */ { MAD_F(0x048da0d0) /* 0.284577192 */, 17 }, /* 2685 */ { MAD_F(0x048e350f) /* 0.284718570 */, 17 }, /* 2686 */ { MAD_F(0x048ec953) /* 0.284859966 */, 17 }, /* 2687 */ { MAD_F(0x048f5d9b) /* 0.285001380 */, 17 }, /* 2688 */ { MAD_F(0x048ff1e8) /* 0.285142811 */, 17 }, /* 2689 */ { MAD_F(0x0490863a) /* 0.285284259 */, 17 }, /* 2690 */ { MAD_F(0x04911a91) /* 0.285425726 */, 17 }, /* 2691 */ { MAD_F(0x0491aeec) /* 0.285567209 */, 17 }, /* 2692 */ { MAD_F(0x0492434c) /* 0.285708711 */, 17 }, /* 2693 */ { MAD_F(0x0492d7b0) /* 0.285850229 */, 17 }, /* 2694 */ { MAD_F(0x04936c1a) /* 0.285991766 */, 17 }, /* 2695 */ { MAD_F(0x04940088) /* 0.286133319 */, 17 }, /* 2696 */ { MAD_F(0x049494fb) /* 0.286274891 */, 17 }, /* 2697 */ { MAD_F(0x04952972) /* 0.286416480 */, 17 }, /* 2698 */ { MAD_F(0x0495bdee) /* 0.286558086 */, 17 }, /* 2699 */ { MAD_F(0x0496526f) /* 0.286699710 */, 17 }, /* 2700 */ { MAD_F(0x0496e6f5) /* 0.286841351 */, 17 }, /* 2701 */ { MAD_F(0x04977b7f) /* 0.286983010 */, 17 }, /* 2702 */ { MAD_F(0x0498100e) /* 0.287124686 */, 17 }, /* 2703 */ { MAD_F(0x0498a4a1) /* 0.287266380 */, 17 }, /* 2704 */ { MAD_F(0x0499393a) /* 0.287408091 */, 17 }, /* 2705 */ { MAD_F(0x0499cdd7) /* 0.287549820 */, 17 }, /* 2706 */ { MAD_F(0x049a6278) /* 0.287691566 */, 17 }, /* 2707 */ { MAD_F(0x049af71f) /* 0.287833330 */, 17 }, /* 2708 */ { MAD_F(0x049b8bca) /* 0.287975111 */, 17 }, /* 2709 */ { MAD_F(0x049c207a) /* 0.288116909 */, 17 }, /* 2710 */ { MAD_F(0x049cb52e) /* 0.288258725 */, 17 }, /* 2711 */ { MAD_F(0x049d49e7) /* 0.288400559 */, 17 }, /* 2712 */ { MAD_F(0x049ddea5) /* 0.288542409 */, 17 }, /* 2713 */ { MAD_F(0x049e7367) /* 0.288684278 */, 17 }, /* 2714 */ { MAD_F(0x049f082f) /* 0.288826163 */, 17 }, /* 2715 */ { MAD_F(0x049f9cfa) /* 0.288968067 */, 17 }, /* 2716 */ { MAD_F(0x04a031cb) /* 0.289109987 */, 17 }, /* 2717 */ { MAD_F(0x04a0c6a0) /* 0.289251925 */, 17 }, /* 2718 */ { MAD_F(0x04a15b7a) /* 0.289393881 */, 17 }, /* 2719 */ { MAD_F(0x04a1f059) /* 0.289535854 */, 17 }, /* 2720 */ { MAD_F(0x04a2853c) /* 0.289677844 */, 17 }, /* 2721 */ { MAD_F(0x04a31a24) /* 0.289819851 */, 17 }, /* 2722 */ { MAD_F(0x04a3af10) /* 0.289961876 */, 17 }, /* 2723 */ { MAD_F(0x04a44401) /* 0.290103919 */, 17 }, /* 2724 */ { MAD_F(0x04a4d8f7) /* 0.290245979 */, 17 }, /* 2725 */ { MAD_F(0x04a56df2) /* 0.290388056 */, 17 }, /* 2726 */ { MAD_F(0x04a602f1) /* 0.290530150 */, 17 }, /* 2727 */ { MAD_F(0x04a697f5) /* 0.290672262 */, 17 }, /* 2728 */ { MAD_F(0x04a72cfe) /* 0.290814392 */, 17 }, /* 2729 */ { MAD_F(0x04a7c20b) /* 0.290956538 */, 17 }, /* 2730 */ { MAD_F(0x04a8571d) /* 0.291098703 */, 17 }, /* 2731 */ { MAD_F(0x04a8ec33) /* 0.291240884 */, 17 }, /* 2732 */ { MAD_F(0x04a9814e) /* 0.291383083 */, 17 }, /* 2733 */ { MAD_F(0x04aa166e) /* 0.291525299 */, 17 }, /* 2734 */ { MAD_F(0x04aaab93) /* 0.291667532 */, 17 }, /* 2735 */ { MAD_F(0x04ab40bc) /* 0.291809783 */, 17 }, /* 2736 */ { MAD_F(0x04abd5ea) /* 0.291952051 */, 17 }, /* 2737 */ { MAD_F(0x04ac6b1c) /* 0.292094337 */, 17 }, /* 2738 */ { MAD_F(0x04ad0053) /* 0.292236640 */, 17 }, /* 2739 */ { MAD_F(0x04ad958f) /* 0.292378960 */, 17 }, /* 2740 */ { MAD_F(0x04ae2ad0) /* 0.292521297 */, 17 }, /* 2741 */ { MAD_F(0x04aec015) /* 0.292663652 */, 17 }, /* 2742 */ { MAD_F(0x04af555e) /* 0.292806024 */, 17 }, /* 2743 */ { MAD_F(0x04afeaad) /* 0.292948414 */, 17 }, /* 2744 */ { MAD_F(0x04b08000) /* 0.293090820 */, 17 }, /* 2745 */ { MAD_F(0x04b11557) /* 0.293233244 */, 17 }, /* 2746 */ { MAD_F(0x04b1aab4) /* 0.293375686 */, 17 }, /* 2747 */ { MAD_F(0x04b24015) /* 0.293518144 */, 17 }, /* 2748 */ { MAD_F(0x04b2d57a) /* 0.293660620 */, 17 }, /* 2749 */ { MAD_F(0x04b36ae4) /* 0.293803113 */, 17 }, /* 2750 */ { MAD_F(0x04b40053) /* 0.293945624 */, 17 }, /* 2751 */ { MAD_F(0x04b495c7) /* 0.294088151 */, 17 }, /* 2752 */ { MAD_F(0x04b52b3f) /* 0.294230696 */, 17 }, /* 2753 */ { MAD_F(0x04b5c0bc) /* 0.294373259 */, 17 }, /* 2754 */ { MAD_F(0x04b6563d) /* 0.294515838 */, 17 }, /* 2755 */ { MAD_F(0x04b6ebc3) /* 0.294658435 */, 17 }, /* 2756 */ { MAD_F(0x04b7814e) /* 0.294801049 */, 17 }, /* 2757 */ { MAD_F(0x04b816dd) /* 0.294943680 */, 17 }, /* 2758 */ { MAD_F(0x04b8ac71) /* 0.295086329 */, 17 }, /* 2759 */ { MAD_F(0x04b9420a) /* 0.295228995 */, 17 }, /* 2760 */ { MAD_F(0x04b9d7a7) /* 0.295371678 */, 17 }, /* 2761 */ { MAD_F(0x04ba6d49) /* 0.295514378 */, 17 }, /* 2762 */ { MAD_F(0x04bb02ef) /* 0.295657095 */, 17 }, /* 2763 */ { MAD_F(0x04bb989a) /* 0.295799830 */, 17 }, /* 2764 */ { MAD_F(0x04bc2e4a) /* 0.295942582 */, 17 }, /* 2765 */ { MAD_F(0x04bcc3fe) /* 0.296085351 */, 17 }, /* 2766 */ { MAD_F(0x04bd59b7) /* 0.296228138 */, 17 }, /* 2767 */ { MAD_F(0x04bdef74) /* 0.296370941 */, 17 }, /* 2768 */ { MAD_F(0x04be8537) /* 0.296513762 */, 17 }, /* 2769 */ { MAD_F(0x04bf1afd) /* 0.296656600 */, 17 }, /* 2770 */ { MAD_F(0x04bfb0c9) /* 0.296799455 */, 17 }, /* 2771 */ { MAD_F(0x04c04699) /* 0.296942327 */, 17 }, /* 2772 */ { MAD_F(0x04c0dc6d) /* 0.297085217 */, 17 }, /* 2773 */ { MAD_F(0x04c17247) /* 0.297228124 */, 17 }, /* 2774 */ { MAD_F(0x04c20824) /* 0.297371048 */, 17 }, /* 2775 */ { MAD_F(0x04c29e07) /* 0.297513989 */, 17 }, /* 2776 */ { MAD_F(0x04c333ee) /* 0.297656947 */, 17 }, /* 2777 */ { MAD_F(0x04c3c9da) /* 0.297799922 */, 17 }, /* 2778 */ { MAD_F(0x04c45fca) /* 0.297942915 */, 17 }, /* 2779 */ { MAD_F(0x04c4f5bf) /* 0.298085925 */, 17 }, /* 2780 */ { MAD_F(0x04c58bb8) /* 0.298228951 */, 17 }, /* 2781 */ { MAD_F(0x04c621b6) /* 0.298371996 */, 17 }, /* 2782 */ { MAD_F(0x04c6b7b9) /* 0.298515057 */, 17 }, /* 2783 */ { MAD_F(0x04c74dc0) /* 0.298658135 */, 17 }, /* 2784 */ { MAD_F(0x04c7e3cc) /* 0.298801231 */, 17 }, /* 2785 */ { MAD_F(0x04c879dd) /* 0.298944343 */, 17 }, /* 2786 */ { MAD_F(0x04c90ff2) /* 0.299087473 */, 17 }, /* 2787 */ { MAD_F(0x04c9a60c) /* 0.299230620 */, 17 }, /* 2788 */ { MAD_F(0x04ca3c2a) /* 0.299373784 */, 17 }, /* 2789 */ { MAD_F(0x04cad24d) /* 0.299516965 */, 17 }, /* 2790 */ { MAD_F(0x04cb6874) /* 0.299660163 */, 17 }, /* 2791 */ { MAD_F(0x04cbfea0) /* 0.299803378 */, 17 }, /* 2792 */ { MAD_F(0x04cc94d1) /* 0.299946611 */, 17 }, /* 2793 */ { MAD_F(0x04cd2b06) /* 0.300089860 */, 17 }, /* 2794 */ { MAD_F(0x04cdc140) /* 0.300233127 */, 17 }, /* 2795 */ { MAD_F(0x04ce577f) /* 0.300376411 */, 17 }, /* 2796 */ { MAD_F(0x04ceedc2) /* 0.300519711 */, 17 }, /* 2797 */ { MAD_F(0x04cf8409) /* 0.300663029 */, 17 }, /* 2798 */ { MAD_F(0x04d01a55) /* 0.300806364 */, 17 }, /* 2799 */ { MAD_F(0x04d0b0a6) /* 0.300949716 */, 17 }, /* 2800 */ { MAD_F(0x04d146fb) /* 0.301093085 */, 17 }, /* 2801 */ { MAD_F(0x04d1dd55) /* 0.301236472 */, 17 }, /* 2802 */ { MAD_F(0x04d273b4) /* 0.301379875 */, 17 }, /* 2803 */ { MAD_F(0x04d30a17) /* 0.301523295 */, 17 }, /* 2804 */ { MAD_F(0x04d3a07f) /* 0.301666733 */, 17 }, /* 2805 */ { MAD_F(0x04d436eb) /* 0.301810187 */, 17 }, /* 2806 */ { MAD_F(0x04d4cd5c) /* 0.301953659 */, 17 }, /* 2807 */ { MAD_F(0x04d563d1) /* 0.302097147 */, 17 }, /* 2808 */ { MAD_F(0x04d5fa4b) /* 0.302240653 */, 17 }, /* 2809 */ { MAD_F(0x04d690ca) /* 0.302384175 */, 17 }, /* 2810 */ { MAD_F(0x04d7274d) /* 0.302527715 */, 17 }, /* 2811 */ { MAD_F(0x04d7bdd5) /* 0.302671271 */, 17 }, /* 2812 */ { MAD_F(0x04d85461) /* 0.302814845 */, 17 }, /* 2813 */ { MAD_F(0x04d8eaf2) /* 0.302958436 */, 17 }, /* 2814 */ { MAD_F(0x04d98187) /* 0.303102044 */, 17 }, /* 2815 */ { MAD_F(0x04da1821) /* 0.303245668 */, 17 }, /* 2816 */ { MAD_F(0x04daaec0) /* 0.303389310 */, 17 }, /* 2817 */ { MAD_F(0x04db4563) /* 0.303532969 */, 17 }, /* 2818 */ { MAD_F(0x04dbdc0a) /* 0.303676645 */, 17 }, /* 2819 */ { MAD_F(0x04dc72b7) /* 0.303820337 */, 17 }, /* 2820 */ { MAD_F(0x04dd0967) /* 0.303964047 */, 17 }, /* 2821 */ { MAD_F(0x04dda01d) /* 0.304107774 */, 17 }, /* 2822 */ { MAD_F(0x04de36d7) /* 0.304251517 */, 17 }, /* 2823 */ { MAD_F(0x04decd95) /* 0.304395278 */, 17 }, /* 2824 */ { MAD_F(0x04df6458) /* 0.304539056 */, 17 }, /* 2825 */ { MAD_F(0x04dffb20) /* 0.304682850 */, 17 }, /* 2826 */ { MAD_F(0x04e091ec) /* 0.304826662 */, 17 }, /* 2827 */ { MAD_F(0x04e128bc) /* 0.304970491 */, 17 }, /* 2828 */ { MAD_F(0x04e1bf92) /* 0.305114336 */, 17 }, /* 2829 */ { MAD_F(0x04e2566b) /* 0.305258199 */, 17 }, /* 2830 */ { MAD_F(0x04e2ed4a) /* 0.305402078 */, 17 }, /* 2831 */ { MAD_F(0x04e3842d) /* 0.305545974 */, 17 }, /* 2832 */ { MAD_F(0x04e41b14) /* 0.305689888 */, 17 }, /* 2833 */ { MAD_F(0x04e4b200) /* 0.305833818 */, 17 }, /* 2834 */ { MAD_F(0x04e548f1) /* 0.305977765 */, 17 }, /* 2835 */ { MAD_F(0x04e5dfe6) /* 0.306121729 */, 17 }, /* 2836 */ { MAD_F(0x04e676df) /* 0.306265710 */, 17 }, /* 2837 */ { MAD_F(0x04e70dde) /* 0.306409708 */, 17 }, /* 2838 */ { MAD_F(0x04e7a4e0) /* 0.306553723 */, 17 }, /* 2839 */ { MAD_F(0x04e83be7) /* 0.306697755 */, 17 }, /* 2840 */ { MAD_F(0x04e8d2f3) /* 0.306841804 */, 17 }, /* 2841 */ { MAD_F(0x04e96a04) /* 0.306985869 */, 17 }, /* 2842 */ { MAD_F(0x04ea0118) /* 0.307129952 */, 17 }, /* 2843 */ { MAD_F(0x04ea9832) /* 0.307274051 */, 17 }, /* 2844 */ { MAD_F(0x04eb2f50) /* 0.307418168 */, 17 }, /* 2845 */ { MAD_F(0x04ebc672) /* 0.307562301 */, 17 }, /* 2846 */ { MAD_F(0x04ec5d99) /* 0.307706451 */, 17 }, /* 2847 */ { MAD_F(0x04ecf4c5) /* 0.307850618 */, 17 }, /* 2848 */ { MAD_F(0x04ed8bf5) /* 0.307994802 */, 17 }, /* 2849 */ { MAD_F(0x04ee2329) /* 0.308139003 */, 17 }, /* 2850 */ { MAD_F(0x04eeba63) /* 0.308283220 */, 17 }, /* 2851 */ { MAD_F(0x04ef51a0) /* 0.308427455 */, 17 }, /* 2852 */ { MAD_F(0x04efe8e2) /* 0.308571706 */, 17 }, /* 2853 */ { MAD_F(0x04f08029) /* 0.308715974 */, 17 }, /* 2854 */ { MAD_F(0x04f11774) /* 0.308860260 */, 17 }, /* 2855 */ { MAD_F(0x04f1aec4) /* 0.309004561 */, 17 }, /* 2856 */ { MAD_F(0x04f24618) /* 0.309148880 */, 17 }, /* 2857 */ { MAD_F(0x04f2dd71) /* 0.309293216 */, 17 }, /* 2858 */ { MAD_F(0x04f374cf) /* 0.309437568 */, 17 }, /* 2859 */ { MAD_F(0x04f40c30) /* 0.309581938 */, 17 }, /* 2860 */ { MAD_F(0x04f4a397) /* 0.309726324 */, 17 }, /* 2861 */ { MAD_F(0x04f53b02) /* 0.309870727 */, 17 }, /* 2862 */ { MAD_F(0x04f5d271) /* 0.310015147 */, 17 }, /* 2863 */ { MAD_F(0x04f669e5) /* 0.310159583 */, 17 }, /* 2864 */ { MAD_F(0x04f7015d) /* 0.310304037 */, 17 }, /* 2865 */ { MAD_F(0x04f798da) /* 0.310448507 */, 17 }, /* 2866 */ { MAD_F(0x04f8305c) /* 0.310592994 */, 17 }, /* 2867 */ { MAD_F(0x04f8c7e2) /* 0.310737498 */, 17 }, /* 2868 */ { MAD_F(0x04f95f6c) /* 0.310882018 */, 17 }, /* 2869 */ { MAD_F(0x04f9f6fb) /* 0.311026556 */, 17 }, /* 2870 */ { MAD_F(0x04fa8e8f) /* 0.311171110 */, 17 }, /* 2871 */ { MAD_F(0x04fb2627) /* 0.311315681 */, 17 }, /* 2872 */ { MAD_F(0x04fbbdc3) /* 0.311460269 */, 17 }, /* 2873 */ { MAD_F(0x04fc5564) /* 0.311604874 */, 17 }, /* 2874 */ { MAD_F(0x04fced0a) /* 0.311749495 */, 17 }, /* 2875 */ { MAD_F(0x04fd84b4) /* 0.311894133 */, 17 }, /* 2876 */ { MAD_F(0x04fe1c62) /* 0.312038788 */, 17 }, /* 2877 */ { MAD_F(0x04feb415) /* 0.312183460 */, 17 }, /* 2878 */ { MAD_F(0x04ff4bcd) /* 0.312328148 */, 17 }, /* 2879 */ { MAD_F(0x04ffe389) /* 0.312472854 */, 17 }, /* 2880 */ { MAD_F(0x05007b49) /* 0.312617576 */, 17 }, /* 2881 */ { MAD_F(0x0501130e) /* 0.312762314 */, 17 }, /* 2882 */ { MAD_F(0x0501aad8) /* 0.312907070 */, 17 }, /* 2883 */ { MAD_F(0x050242a6) /* 0.313051842 */, 17 }, /* 2884 */ { MAD_F(0x0502da78) /* 0.313196631 */, 17 }, /* 2885 */ { MAD_F(0x0503724f) /* 0.313341437 */, 17 }, /* 2886 */ { MAD_F(0x05040a2b) /* 0.313486259 */, 17 }, /* 2887 */ { MAD_F(0x0504a20b) /* 0.313631098 */, 17 }, /* 2888 */ { MAD_F(0x050539ef) /* 0.313775954 */, 17 }, /* 2889 */ { MAD_F(0x0505d1d8) /* 0.313920827 */, 17 }, /* 2890 */ { MAD_F(0x050669c5) /* 0.314065716 */, 17 }, /* 2891 */ { MAD_F(0x050701b7) /* 0.314210622 */, 17 }, /* 2892 */ { MAD_F(0x050799ae) /* 0.314355545 */, 17 }, /* 2893 */ { MAD_F(0x050831a9) /* 0.314500484 */, 17 }, /* 2894 */ { MAD_F(0x0508c9a8) /* 0.314645440 */, 17 }, /* 2895 */ { MAD_F(0x050961ac) /* 0.314790413 */, 17 }, /* 2896 */ { MAD_F(0x0509f9b4) /* 0.314935403 */, 17 }, /* 2897 */ { MAD_F(0x050a91c1) /* 0.315080409 */, 17 }, /* 2898 */ { MAD_F(0x050b29d2) /* 0.315225432 */, 17 }, /* 2899 */ { MAD_F(0x050bc1e8) /* 0.315370472 */, 17 }, /* 2900 */ { MAD_F(0x050c5a02) /* 0.315515528 */, 17 }, /* 2901 */ { MAD_F(0x050cf221) /* 0.315660601 */, 17 }, /* 2902 */ { MAD_F(0x050d8a44) /* 0.315805690 */, 17 }, /* 2903 */ { MAD_F(0x050e226c) /* 0.315950797 */, 17 }, /* 2904 */ { MAD_F(0x050eba98) /* 0.316095920 */, 17 }, /* 2905 */ { MAD_F(0x050f52c9) /* 0.316241059 */, 17 }, /* 2906 */ { MAD_F(0x050feafe) /* 0.316386216 */, 17 }, /* 2907 */ { MAD_F(0x05108337) /* 0.316531388 */, 17 }, /* 2908 */ { MAD_F(0x05111b75) /* 0.316676578 */, 17 }, /* 2909 */ { MAD_F(0x0511b3b8) /* 0.316821784 */, 17 }, /* 2910 */ { MAD_F(0x05124bff) /* 0.316967007 */, 17 }, /* 2911 */ { MAD_F(0x0512e44a) /* 0.317112247 */, 17 }, /* 2912 */ { MAD_F(0x05137c9a) /* 0.317257503 */, 17 }, /* 2913 */ { MAD_F(0x051414ee) /* 0.317402775 */, 17 }, /* 2914 */ { MAD_F(0x0514ad47) /* 0.317548065 */, 17 }, /* 2915 */ { MAD_F(0x051545a5) /* 0.317693371 */, 17 }, /* 2916 */ { MAD_F(0x0515de06) /* 0.317838693 */, 17 }, /* 2917 */ { MAD_F(0x0516766d) /* 0.317984033 */, 17 }, /* 2918 */ { MAD_F(0x05170ed7) /* 0.318129388 */, 17 }, /* 2919 */ { MAD_F(0x0517a746) /* 0.318274761 */, 17 }, /* 2920 */ { MAD_F(0x05183fba) /* 0.318420150 */, 17 }, /* 2921 */ { MAD_F(0x0518d832) /* 0.318565555 */, 17 }, /* 2922 */ { MAD_F(0x051970ae) /* 0.318710978 */, 17 }, /* 2923 */ { MAD_F(0x051a092f) /* 0.318856416 */, 17 }, /* 2924 */ { MAD_F(0x051aa1b5) /* 0.319001872 */, 17 }, /* 2925 */ { MAD_F(0x051b3a3f) /* 0.319147344 */, 17 }, /* 2926 */ { MAD_F(0x051bd2cd) /* 0.319292832 */, 17 }, /* 2927 */ { MAD_F(0x051c6b60) /* 0.319438338 */, 17 }, /* 2928 */ { MAD_F(0x051d03f7) /* 0.319583859 */, 17 }, /* 2929 */ { MAD_F(0x051d9c92) /* 0.319729398 */, 17 }, /* 2930 */ { MAD_F(0x051e3532) /* 0.319874952 */, 17 }, /* 2931 */ { MAD_F(0x051ecdd7) /* 0.320020524 */, 17 }, /* 2932 */ { MAD_F(0x051f6680) /* 0.320166112 */, 17 }, /* 2933 */ { MAD_F(0x051fff2d) /* 0.320311716 */, 17 }, /* 2934 */ { MAD_F(0x052097df) /* 0.320457337 */, 17 }, /* 2935 */ { MAD_F(0x05213095) /* 0.320602975 */, 17 }, /* 2936 */ { MAD_F(0x0521c950) /* 0.320748629 */, 17 }, /* 2937 */ { MAD_F(0x0522620f) /* 0.320894300 */, 17 }, /* 2938 */ { MAD_F(0x0522fad3) /* 0.321039987 */, 17 }, /* 2939 */ { MAD_F(0x0523939b) /* 0.321185691 */, 17 }, /* 2940 */ { MAD_F(0x05242c68) /* 0.321331411 */, 17 }, /* 2941 */ { MAD_F(0x0524c538) /* 0.321477148 */, 17 }, /* 2942 */ { MAD_F(0x05255e0e) /* 0.321622901 */, 17 }, /* 2943 */ { MAD_F(0x0525f6e8) /* 0.321768671 */, 17 }, /* 2944 */ { MAD_F(0x05268fc6) /* 0.321914457 */, 17 }, /* 2945 */ { MAD_F(0x052728a9) /* 0.322060260 */, 17 }, /* 2946 */ { MAD_F(0x0527c190) /* 0.322206079 */, 17 }, /* 2947 */ { MAD_F(0x05285a7b) /* 0.322351915 */, 17 }, /* 2948 */ { MAD_F(0x0528f36b) /* 0.322497768 */, 17 }, /* 2949 */ { MAD_F(0x05298c5f) /* 0.322643636 */, 17 }, /* 2950 */ { MAD_F(0x052a2558) /* 0.322789522 */, 17 }, /* 2951 */ { MAD_F(0x052abe55) /* 0.322935424 */, 17 }, /* 2952 */ { MAD_F(0x052b5757) /* 0.323081342 */, 17 }, /* 2953 */ { MAD_F(0x052bf05d) /* 0.323227277 */, 17 }, /* 2954 */ { MAD_F(0x052c8968) /* 0.323373228 */, 17 }, /* 2955 */ { MAD_F(0x052d2277) /* 0.323519196 */, 17 }, /* 2956 */ { MAD_F(0x052dbb8a) /* 0.323665180 */, 17 }, /* 2957 */ { MAD_F(0x052e54a2) /* 0.323811180 */, 17 }, /* 2958 */ { MAD_F(0x052eedbe) /* 0.323957197 */, 17 }, /* 2959 */ { MAD_F(0x052f86de) /* 0.324103231 */, 17 }, /* 2960 */ { MAD_F(0x05302003) /* 0.324249281 */, 17 }, /* 2961 */ { MAD_F(0x0530b92d) /* 0.324395347 */, 17 }, /* 2962 */ { MAD_F(0x0531525b) /* 0.324541430 */, 17 }, /* 2963 */ { MAD_F(0x0531eb8d) /* 0.324687530 */, 17 }, /* 2964 */ { MAD_F(0x053284c4) /* 0.324833646 */, 17 }, /* 2965 */ { MAD_F(0x05331dff) /* 0.324979778 */, 17 }, /* 2966 */ { MAD_F(0x0533b73e) /* 0.325125926 */, 17 }, /* 2967 */ { MAD_F(0x05345082) /* 0.325272091 */, 17 }, /* 2968 */ { MAD_F(0x0534e9ca) /* 0.325418273 */, 17 }, /* 2969 */ { MAD_F(0x05358317) /* 0.325564471 */, 17 }, /* 2970 */ { MAD_F(0x05361c68) /* 0.325710685 */, 17 }, /* 2971 */ { MAD_F(0x0536b5be) /* 0.325856916 */, 17 }, /* 2972 */ { MAD_F(0x05374f17) /* 0.326003163 */, 17 }, /* 2973 */ { MAD_F(0x0537e876) /* 0.326149427 */, 17 }, /* 2974 */ { MAD_F(0x053881d9) /* 0.326295707 */, 17 }, /* 2975 */ { MAD_F(0x05391b40) /* 0.326442003 */, 17 }, /* 2976 */ { MAD_F(0x0539b4ab) /* 0.326588316 */, 17 }, /* 2977 */ { MAD_F(0x053a4e1b) /* 0.326734645 */, 17 }, /* 2978 */ { MAD_F(0x053ae78f) /* 0.326880990 */, 17 }, /* 2979 */ { MAD_F(0x053b8108) /* 0.327027352 */, 17 }, /* 2980 */ { MAD_F(0x053c1a85) /* 0.327173730 */, 17 }, /* 2981 */ { MAD_F(0x053cb407) /* 0.327320125 */, 17 }, /* 2982 */ { MAD_F(0x053d4d8d) /* 0.327466536 */, 17 }, /* 2983 */ { MAD_F(0x053de717) /* 0.327612963 */, 17 }, /* 2984 */ { MAD_F(0x053e80a6) /* 0.327759407 */, 17 }, /* 2985 */ { MAD_F(0x053f1a39) /* 0.327905867 */, 17 }, /* 2986 */ { MAD_F(0x053fb3d0) /* 0.328052344 */, 17 }, /* 2987 */ { MAD_F(0x05404d6c) /* 0.328198837 */, 17 }, /* 2988 */ { MAD_F(0x0540e70c) /* 0.328345346 */, 17 }, /* 2989 */ { MAD_F(0x054180b1) /* 0.328491871 */, 17 }, /* 2990 */ { MAD_F(0x05421a5a) /* 0.328638413 */, 17 }, /* 2991 */ { MAD_F(0x0542b407) /* 0.328784971 */, 17 }, /* 2992 */ { MAD_F(0x05434db9) /* 0.328931546 */, 17 }, /* 2993 */ { MAD_F(0x0543e76f) /* 0.329078137 */, 17 }, /* 2994 */ { MAD_F(0x0544812a) /* 0.329224744 */, 17 }, /* 2995 */ { MAD_F(0x05451ae9) /* 0.329371367 */, 17 }, /* 2996 */ { MAD_F(0x0545b4ac) /* 0.329518007 */, 17 }, /* 2997 */ { MAD_F(0x05464e74) /* 0.329664663 */, 17 }, /* 2998 */ { MAD_F(0x0546e840) /* 0.329811336 */, 17 }, /* 2999 */ { MAD_F(0x05478211) /* 0.329958024 */, 17 }, /* 3000 */ { MAD_F(0x05481be5) /* 0.330104730 */, 17 }, /* 3001 */ { MAD_F(0x0548b5bf) /* 0.330251451 */, 17 }, /* 3002 */ { MAD_F(0x05494f9c) /* 0.330398189 */, 17 }, /* 3003 */ { MAD_F(0x0549e97e) /* 0.330544943 */, 17 }, /* 3004 */ { MAD_F(0x054a8364) /* 0.330691713 */, 17 }, /* 3005 */ { MAD_F(0x054b1d4f) /* 0.330838499 */, 17 }, /* 3006 */ { MAD_F(0x054bb73e) /* 0.330985302 */, 17 }, /* 3007 */ { MAD_F(0x054c5132) /* 0.331132121 */, 17 }, /* 3008 */ { MAD_F(0x054ceb2a) /* 0.331278957 */, 17 }, /* 3009 */ { MAD_F(0x054d8526) /* 0.331425808 */, 17 }, /* 3010 */ { MAD_F(0x054e1f26) /* 0.331572676 */, 17 }, /* 3011 */ { MAD_F(0x054eb92b) /* 0.331719560 */, 17 }, /* 3012 */ { MAD_F(0x054f5334) /* 0.331866461 */, 17 }, /* 3013 */ { MAD_F(0x054fed42) /* 0.332013377 */, 17 }, /* 3014 */ { MAD_F(0x05508754) /* 0.332160310 */, 17 }, /* 3015 */ { MAD_F(0x0551216b) /* 0.332307260 */, 17 }, /* 3016 */ { MAD_F(0x0551bb85) /* 0.332454225 */, 17 }, /* 3017 */ { MAD_F(0x055255a4) /* 0.332601207 */, 17 }, /* 3018 */ { MAD_F(0x0552efc8) /* 0.332748205 */, 17 }, /* 3019 */ { MAD_F(0x055389f0) /* 0.332895219 */, 17 }, /* 3020 */ { MAD_F(0x0554241c) /* 0.333042249 */, 17 }, /* 3021 */ { MAD_F(0x0554be4c) /* 0.333189296 */, 17 }, /* 3022 */ { MAD_F(0x05555881) /* 0.333336359 */, 17 }, /* 3023 */ { MAD_F(0x0555f2ba) /* 0.333483438 */, 17 }, /* 3024 */ { MAD_F(0x05568cf8) /* 0.333630533 */, 17 }, /* 3025 */ { MAD_F(0x0557273a) /* 0.333777645 */, 17 }, /* 3026 */ { MAD_F(0x0557c180) /* 0.333924772 */, 17 }, /* 3027 */ { MAD_F(0x05585bcb) /* 0.334071916 */, 17 }, /* 3028 */ { MAD_F(0x0558f61a) /* 0.334219076 */, 17 }, /* 3029 */ { MAD_F(0x0559906d) /* 0.334366253 */, 17 }, /* 3030 */ { MAD_F(0x055a2ac5) /* 0.334513445 */, 17 }, /* 3031 */ { MAD_F(0x055ac521) /* 0.334660654 */, 17 }, /* 3032 */ { MAD_F(0x055b5f81) /* 0.334807879 */, 17 }, /* 3033 */ { MAD_F(0x055bf9e6) /* 0.334955120 */, 17 }, /* 3034 */ { MAD_F(0x055c944f) /* 0.335102377 */, 17 }, /* 3035 */ { MAD_F(0x055d2ebd) /* 0.335249651 */, 17 }, /* 3036 */ { MAD_F(0x055dc92e) /* 0.335396941 */, 17 }, /* 3037 */ { MAD_F(0x055e63a5) /* 0.335544246 */, 17 }, /* 3038 */ { MAD_F(0x055efe1f) /* 0.335691568 */, 17 }, /* 3039 */ { MAD_F(0x055f989e) /* 0.335838906 */, 17 }, /* 3040 */ { MAD_F(0x05603321) /* 0.335986261 */, 17 }, /* 3041 */ { MAD_F(0x0560cda8) /* 0.336133631 */, 17 }, /* 3042 */ { MAD_F(0x05616834) /* 0.336281018 */, 17 }, /* 3043 */ { MAD_F(0x056202c4) /* 0.336428421 */, 17 }, /* 3044 */ { MAD_F(0x05629d59) /* 0.336575840 */, 17 }, /* 3045 */ { MAD_F(0x056337f2) /* 0.336723275 */, 17 }, /* 3046 */ { MAD_F(0x0563d28f) /* 0.336870726 */, 17 }, /* 3047 */ { MAD_F(0x05646d30) /* 0.337018193 */, 17 }, /* 3048 */ { MAD_F(0x056507d6) /* 0.337165677 */, 17 }, /* 3049 */ { MAD_F(0x0565a280) /* 0.337313176 */, 17 }, /* 3050 */ { MAD_F(0x05663d2f) /* 0.337460692 */, 17 }, /* 3051 */ { MAD_F(0x0566d7e1) /* 0.337608224 */, 17 }, /* 3052 */ { MAD_F(0x05677298) /* 0.337755772 */, 17 }, /* 3053 */ { MAD_F(0x05680d54) /* 0.337903336 */, 17 }, /* 3054 */ { MAD_F(0x0568a814) /* 0.338050916 */, 17 }, /* 3055 */ { MAD_F(0x056942d8) /* 0.338198513 */, 17 }, /* 3056 */ { MAD_F(0x0569dda0) /* 0.338346125 */, 17 }, /* 3057 */ { MAD_F(0x056a786d) /* 0.338493753 */, 17 }, /* 3058 */ { MAD_F(0x056b133e) /* 0.338641398 */, 17 }, /* 3059 */ { MAD_F(0x056bae13) /* 0.338789059 */, 17 }, /* 3060 */ { MAD_F(0x056c48ed) /* 0.338936736 */, 17 }, /* 3061 */ { MAD_F(0x056ce3cb) /* 0.339084429 */, 17 }, /* 3062 */ { MAD_F(0x056d7ead) /* 0.339232138 */, 17 }, /* 3063 */ { MAD_F(0x056e1994) /* 0.339379863 */, 17 }, /* 3064 */ { MAD_F(0x056eb47f) /* 0.339527604 */, 17 }, /* 3065 */ { MAD_F(0x056f4f6e) /* 0.339675361 */, 17 }, /* 3066 */ { MAD_F(0x056fea62) /* 0.339823134 */, 17 }, /* 3067 */ { MAD_F(0x0570855a) /* 0.339970924 */, 17 }, /* 3068 */ { MAD_F(0x05712056) /* 0.340118729 */, 17 }, /* 3069 */ { MAD_F(0x0571bb56) /* 0.340266550 */, 17 }, /* 3070 */ { MAD_F(0x0572565b) /* 0.340414388 */, 17 }, /* 3071 */ { MAD_F(0x0572f164) /* 0.340562242 */, 17 }, /* 3072 */ { MAD_F(0x05738c72) /* 0.340710111 */, 17 }, /* 3073 */ { MAD_F(0x05742784) /* 0.340857997 */, 17 }, /* 3074 */ { MAD_F(0x0574c29a) /* 0.341005899 */, 17 }, /* 3075 */ { MAD_F(0x05755db4) /* 0.341153816 */, 17 }, /* 3076 */ { MAD_F(0x0575f8d3) /* 0.341301750 */, 17 }, /* 3077 */ { MAD_F(0x057693f6) /* 0.341449700 */, 17 }, /* 3078 */ { MAD_F(0x05772f1d) /* 0.341597666 */, 17 }, /* 3079 */ { MAD_F(0x0577ca49) /* 0.341745648 */, 17 }, /* 3080 */ { MAD_F(0x05786578) /* 0.341893646 */, 17 }, /* 3081 */ { MAD_F(0x057900ad) /* 0.342041659 */, 17 }, /* 3082 */ { MAD_F(0x05799be5) /* 0.342189689 */, 17 }, /* 3083 */ { MAD_F(0x057a3722) /* 0.342337735 */, 17 }, /* 3084 */ { MAD_F(0x057ad263) /* 0.342485797 */, 17 }, /* 3085 */ { MAD_F(0x057b6da8) /* 0.342633875 */, 17 }, /* 3086 */ { MAD_F(0x057c08f2) /* 0.342781969 */, 17 }, /* 3087 */ { MAD_F(0x057ca440) /* 0.342930079 */, 17 }, /* 3088 */ { MAD_F(0x057d3f92) /* 0.343078205 */, 17 }, /* 3089 */ { MAD_F(0x057ddae9) /* 0.343226347 */, 17 }, /* 3090 */ { MAD_F(0x057e7644) /* 0.343374505 */, 17 }, /* 3091 */ { MAD_F(0x057f11a3) /* 0.343522679 */, 17 }, /* 3092 */ { MAD_F(0x057fad06) /* 0.343670869 */, 17 }, /* 3093 */ { MAD_F(0x0580486e) /* 0.343819075 */, 17 }, /* 3094 */ { MAD_F(0x0580e3da) /* 0.343967296 */, 17 }, /* 3095 */ { MAD_F(0x05817f4a) /* 0.344115534 */, 17 }, /* 3096 */ { MAD_F(0x05821abf) /* 0.344263788 */, 17 }, /* 3097 */ { MAD_F(0x0582b638) /* 0.344412058 */, 17 }, /* 3098 */ { MAD_F(0x058351b5) /* 0.344560343 */, 17 }, /* 3099 */ { MAD_F(0x0583ed36) /* 0.344708645 */, 17 }, /* 3100 */ { MAD_F(0x058488bc) /* 0.344856963 */, 17 }, /* 3101 */ { MAD_F(0x05852446) /* 0.345005296 */, 17 }, /* 3102 */ { MAD_F(0x0585bfd4) /* 0.345153646 */, 17 }, /* 3103 */ { MAD_F(0x05865b67) /* 0.345302011 */, 17 }, /* 3104 */ { MAD_F(0x0586f6fd) /* 0.345450393 */, 17 }, /* 3105 */ { MAD_F(0x05879298) /* 0.345598790 */, 17 }, /* 3106 */ { MAD_F(0x05882e38) /* 0.345747203 */, 17 }, /* 3107 */ { MAD_F(0x0588c9dc) /* 0.345895632 */, 17 }, /* 3108 */ { MAD_F(0x05896583) /* 0.346044077 */, 17 }, /* 3109 */ { MAD_F(0x058a0130) /* 0.346192538 */, 17 }, /* 3110 */ { MAD_F(0x058a9ce0) /* 0.346341015 */, 17 }, /* 3111 */ { MAD_F(0x058b3895) /* 0.346489508 */, 17 }, /* 3112 */ { MAD_F(0x058bd44e) /* 0.346638017 */, 17 }, /* 3113 */ { MAD_F(0x058c700b) /* 0.346786542 */, 17 }, /* 3114 */ { MAD_F(0x058d0bcd) /* 0.346935082 */, 17 }, /* 3115 */ { MAD_F(0x058da793) /* 0.347083639 */, 17 }, /* 3116 */ { MAD_F(0x058e435d) /* 0.347232211 */, 17 }, /* 3117 */ { MAD_F(0x058edf2b) /* 0.347380799 */, 17 }, /* 3118 */ { MAD_F(0x058f7afe) /* 0.347529403 */, 17 }, /* 3119 */ { MAD_F(0x059016d5) /* 0.347678023 */, 17 }, /* 3120 */ { MAD_F(0x0590b2b0) /* 0.347826659 */, 17 }, /* 3121 */ { MAD_F(0x05914e8f) /* 0.347975311 */, 17 }, /* 3122 */ { MAD_F(0x0591ea73) /* 0.348123979 */, 17 }, /* 3123 */ { MAD_F(0x0592865b) /* 0.348272662 */, 17 }, /* 3124 */ { MAD_F(0x05932247) /* 0.348421362 */, 17 }, /* 3125 */ { MAD_F(0x0593be37) /* 0.348570077 */, 17 }, /* 3126 */ { MAD_F(0x05945a2c) /* 0.348718808 */, 17 }, /* 3127 */ { MAD_F(0x0594f625) /* 0.348867555 */, 17 }, /* 3128 */ { MAD_F(0x05959222) /* 0.349016318 */, 17 }, /* 3129 */ { MAD_F(0x05962e24) /* 0.349165097 */, 17 }, /* 3130 */ { MAD_F(0x0596ca2a) /* 0.349313892 */, 17 }, /* 3131 */ { MAD_F(0x05976634) /* 0.349462702 */, 17 }, /* 3132 */ { MAD_F(0x05980242) /* 0.349611528 */, 17 }, /* 3133 */ { MAD_F(0x05989e54) /* 0.349760370 */, 17 }, /* 3134 */ { MAD_F(0x05993a6b) /* 0.349909228 */, 17 }, /* 3135 */ { MAD_F(0x0599d686) /* 0.350058102 */, 17 }, /* 3136 */ { MAD_F(0x059a72a5) /* 0.350206992 */, 17 }, /* 3137 */ { MAD_F(0x059b0ec9) /* 0.350355897 */, 17 }, /* 3138 */ { MAD_F(0x059baaf1) /* 0.350504818 */, 17 }, /* 3139 */ { MAD_F(0x059c471d) /* 0.350653756 */, 17 }, /* 3140 */ { MAD_F(0x059ce34d) /* 0.350802708 */, 17 }, /* 3141 */ { MAD_F(0x059d7f81) /* 0.350951677 */, 17 }, /* 3142 */ { MAD_F(0x059e1bba) /* 0.351100662 */, 17 }, /* 3143 */ { MAD_F(0x059eb7f7) /* 0.351249662 */, 17 }, /* 3144 */ { MAD_F(0x059f5438) /* 0.351398678 */, 17 }, /* 3145 */ { MAD_F(0x059ff07e) /* 0.351547710 */, 17 }, /* 3146 */ { MAD_F(0x05a08cc7) /* 0.351696758 */, 17 }, /* 3147 */ { MAD_F(0x05a12915) /* 0.351845821 */, 17 }, /* 3148 */ { MAD_F(0x05a1c567) /* 0.351994901 */, 17 }, /* 3149 */ { MAD_F(0x05a261be) /* 0.352143996 */, 17 }, /* 3150 */ { MAD_F(0x05a2fe18) /* 0.352293107 */, 17 }, /* 3151 */ { MAD_F(0x05a39a77) /* 0.352442233 */, 17 }, /* 3152 */ { MAD_F(0x05a436da) /* 0.352591376 */, 17 }, /* 3153 */ { MAD_F(0x05a4d342) /* 0.352740534 */, 17 }, /* 3154 */ { MAD_F(0x05a56fad) /* 0.352889708 */, 17 }, /* 3155 */ { MAD_F(0x05a60c1d) /* 0.353038898 */, 17 }, /* 3156 */ { MAD_F(0x05a6a891) /* 0.353188103 */, 17 }, /* 3157 */ { MAD_F(0x05a7450a) /* 0.353337325 */, 17 }, /* 3158 */ { MAD_F(0x05a7e186) /* 0.353486562 */, 17 }, /* 3159 */ { MAD_F(0x05a87e07) /* 0.353635814 */, 17 }, /* 3160 */ { MAD_F(0x05a91a8c) /* 0.353785083 */, 17 }, /* 3161 */ { MAD_F(0x05a9b715) /* 0.353934367 */, 17 }, /* 3162 */ { MAD_F(0x05aa53a2) /* 0.354083667 */, 17 }, /* 3163 */ { MAD_F(0x05aaf034) /* 0.354232983 */, 17 }, /* 3164 */ { MAD_F(0x05ab8cca) /* 0.354382314 */, 17 }, /* 3165 */ { MAD_F(0x05ac2964) /* 0.354531662 */, 17 }, /* 3166 */ { MAD_F(0x05acc602) /* 0.354681025 */, 17 }, /* 3167 */ { MAD_F(0x05ad62a5) /* 0.354830403 */, 17 }, /* 3168 */ { MAD_F(0x05adff4c) /* 0.354979798 */, 17 }, /* 3169 */ { MAD_F(0x05ae9bf7) /* 0.355129208 */, 17 }, /* 3170 */ { MAD_F(0x05af38a6) /* 0.355278634 */, 17 }, /* 3171 */ { MAD_F(0x05afd559) /* 0.355428075 */, 17 }, /* 3172 */ { MAD_F(0x05b07211) /* 0.355577533 */, 17 }, /* 3173 */ { MAD_F(0x05b10ecd) /* 0.355727006 */, 17 }, /* 3174 */ { MAD_F(0x05b1ab8d) /* 0.355876494 */, 17 }, /* 3175 */ { MAD_F(0x05b24851) /* 0.356025999 */, 17 }, /* 3176 */ { MAD_F(0x05b2e51a) /* 0.356175519 */, 17 }, /* 3177 */ { MAD_F(0x05b381e6) /* 0.356325054 */, 17 }, /* 3178 */ { MAD_F(0x05b41eb7) /* 0.356474606 */, 17 }, /* 3179 */ { MAD_F(0x05b4bb8c) /* 0.356624173 */, 17 }, /* 3180 */ { MAD_F(0x05b55866) /* 0.356773756 */, 17 }, /* 3181 */ { MAD_F(0x05b5f543) /* 0.356923354 */, 17 }, /* 3182 */ { MAD_F(0x05b69225) /* 0.357072969 */, 17 }, /* 3183 */ { MAD_F(0x05b72f0b) /* 0.357222598 */, 17 }, /* 3184 */ { MAD_F(0x05b7cbf5) /* 0.357372244 */, 17 }, /* 3185 */ { MAD_F(0x05b868e3) /* 0.357521905 */, 17 }, /* 3186 */ { MAD_F(0x05b905d6) /* 0.357671582 */, 17 }, /* 3187 */ { MAD_F(0x05b9a2cd) /* 0.357821275 */, 17 }, /* 3188 */ { MAD_F(0x05ba3fc8) /* 0.357970983 */, 17 }, /* 3189 */ { MAD_F(0x05badcc7) /* 0.358120707 */, 17 }, /* 3190 */ { MAD_F(0x05bb79ca) /* 0.358270446 */, 17 }, /* 3191 */ { MAD_F(0x05bc16d2) /* 0.358420201 */, 17 }, /* 3192 */ { MAD_F(0x05bcb3de) /* 0.358569972 */, 17 }, /* 3193 */ { MAD_F(0x05bd50ee) /* 0.358719758 */, 17 }, /* 3194 */ { MAD_F(0x05bdee02) /* 0.358869560 */, 17 }, /* 3195 */ { MAD_F(0x05be8b1a) /* 0.359019378 */, 17 }, /* 3196 */ { MAD_F(0x05bf2837) /* 0.359169211 */, 17 }, /* 3197 */ { MAD_F(0x05bfc558) /* 0.359319060 */, 17 }, /* 3198 */ { MAD_F(0x05c0627d) /* 0.359468925 */, 17 }, /* 3199 */ { MAD_F(0x05c0ffa6) /* 0.359618805 */, 17 }, /* 3200 */ { MAD_F(0x05c19cd3) /* 0.359768701 */, 17 }, /* 3201 */ { MAD_F(0x05c23a05) /* 0.359918612 */, 17 }, /* 3202 */ { MAD_F(0x05c2d73a) /* 0.360068540 */, 17 }, /* 3203 */ { MAD_F(0x05c37474) /* 0.360218482 */, 17 }, /* 3204 */ { MAD_F(0x05c411b2) /* 0.360368440 */, 17 }, /* 3205 */ { MAD_F(0x05c4aef5) /* 0.360518414 */, 17 }, /* 3206 */ { MAD_F(0x05c54c3b) /* 0.360668404 */, 17 }, /* 3207 */ { MAD_F(0x05c5e986) /* 0.360818409 */, 17 }, /* 3208 */ { MAD_F(0x05c686d5) /* 0.360968429 */, 17 }, /* 3209 */ { MAD_F(0x05c72428) /* 0.361118466 */, 17 }, /* 3210 */ { MAD_F(0x05c7c17f) /* 0.361268517 */, 17 }, /* 3211 */ { MAD_F(0x05c85eda) /* 0.361418585 */, 17 }, /* 3212 */ { MAD_F(0x05c8fc3a) /* 0.361568668 */, 17 }, /* 3213 */ { MAD_F(0x05c9999e) /* 0.361718766 */, 17 }, /* 3214 */ { MAD_F(0x05ca3706) /* 0.361868881 */, 17 }, /* 3215 */ { MAD_F(0x05cad472) /* 0.362019010 */, 17 }, /* 3216 */ { MAD_F(0x05cb71e2) /* 0.362169156 */, 17 }, /* 3217 */ { MAD_F(0x05cc0f57) /* 0.362319316 */, 17 }, /* 3218 */ { MAD_F(0x05ccaccf) /* 0.362469493 */, 17 }, /* 3219 */ { MAD_F(0x05cd4a4c) /* 0.362619685 */, 17 }, /* 3220 */ { MAD_F(0x05cde7cd) /* 0.362769892 */, 17 }, /* 3221 */ { MAD_F(0x05ce8552) /* 0.362920115 */, 17 }, /* 3222 */ { MAD_F(0x05cf22dc) /* 0.363070354 */, 17 }, /* 3223 */ { MAD_F(0x05cfc069) /* 0.363220608 */, 17 }, /* 3224 */ { MAD_F(0x05d05dfb) /* 0.363370878 */, 17 }, /* 3225 */ { MAD_F(0x05d0fb91) /* 0.363521163 */, 17 }, /* 3226 */ { MAD_F(0x05d1992b) /* 0.363671464 */, 17 }, /* 3227 */ { MAD_F(0x05d236c9) /* 0.363821780 */, 17 }, /* 3228 */ { MAD_F(0x05d2d46c) /* 0.363972112 */, 17 }, /* 3229 */ { MAD_F(0x05d37212) /* 0.364122459 */, 17 }, /* 3230 */ { MAD_F(0x05d40fbd) /* 0.364272822 */, 17 }, /* 3231 */ { MAD_F(0x05d4ad6c) /* 0.364423200 */, 17 }, /* 3232 */ { MAD_F(0x05d54b1f) /* 0.364573594 */, 17 }, /* 3233 */ { MAD_F(0x05d5e8d6) /* 0.364724004 */, 17 }, /* 3234 */ { MAD_F(0x05d68691) /* 0.364874429 */, 17 }, /* 3235 */ { MAD_F(0x05d72451) /* 0.365024869 */, 17 }, /* 3236 */ { MAD_F(0x05d7c215) /* 0.365175325 */, 17 }, /* 3237 */ { MAD_F(0x05d85fdc) /* 0.365325796 */, 17 }, /* 3238 */ { MAD_F(0x05d8fda8) /* 0.365476283 */, 17 }, /* 3239 */ { MAD_F(0x05d99b79) /* 0.365626786 */, 17 }, /* 3240 */ { MAD_F(0x05da394d) /* 0.365777304 */, 17 }, /* 3241 */ { MAD_F(0x05dad726) /* 0.365927837 */, 17 }, /* 3242 */ { MAD_F(0x05db7502) /* 0.366078386 */, 17 }, /* 3243 */ { MAD_F(0x05dc12e3) /* 0.366228950 */, 17 }, /* 3244 */ { MAD_F(0x05dcb0c8) /* 0.366379530 */, 17 }, /* 3245 */ { MAD_F(0x05dd4eb1) /* 0.366530125 */, 17 }, /* 3246 */ { MAD_F(0x05ddec9e) /* 0.366680736 */, 17 }, /* 3247 */ { MAD_F(0x05de8a90) /* 0.366831362 */, 17 }, /* 3248 */ { MAD_F(0x05df2885) /* 0.366982004 */, 17 }, /* 3249 */ { MAD_F(0x05dfc67f) /* 0.367132661 */, 17 }, /* 3250 */ { MAD_F(0x05e0647d) /* 0.367283334 */, 17 }, /* 3251 */ { MAD_F(0x05e1027f) /* 0.367434022 */, 17 }, /* 3252 */ { MAD_F(0x05e1a085) /* 0.367584725 */, 17 }, /* 3253 */ { MAD_F(0x05e23e8f) /* 0.367735444 */, 17 }, /* 3254 */ { MAD_F(0x05e2dc9e) /* 0.367886179 */, 17 }, /* 3255 */ { MAD_F(0x05e37ab0) /* 0.368036929 */, 17 }, /* 3256 */ { MAD_F(0x05e418c7) /* 0.368187694 */, 17 }, /* 3257 */ { MAD_F(0x05e4b6e2) /* 0.368338475 */, 17 }, /* 3258 */ { MAD_F(0x05e55501) /* 0.368489271 */, 17 }, /* 3259 */ { MAD_F(0x05e5f324) /* 0.368640082 */, 17 }, /* 3260 */ { MAD_F(0x05e6914c) /* 0.368790909 */, 17 }, /* 3261 */ { MAD_F(0x05e72f77) /* 0.368941752 */, 17 }, /* 3262 */ { MAD_F(0x05e7cda7) /* 0.369092610 */, 17 }, /* 3263 */ { MAD_F(0x05e86bda) /* 0.369243483 */, 17 }, /* 3264 */ { MAD_F(0x05e90a12) /* 0.369394372 */, 17 }, /* 3265 */ { MAD_F(0x05e9a84e) /* 0.369545276 */, 17 }, /* 3266 */ { MAD_F(0x05ea468e) /* 0.369696195 */, 17 }, /* 3267 */ { MAD_F(0x05eae4d3) /* 0.369847130 */, 17 }, /* 3268 */ { MAD_F(0x05eb831b) /* 0.369998080 */, 17 }, /* 3269 */ { MAD_F(0x05ec2168) /* 0.370149046 */, 17 }, /* 3270 */ { MAD_F(0x05ecbfb8) /* 0.370300027 */, 17 }, /* 3271 */ { MAD_F(0x05ed5e0d) /* 0.370451024 */, 17 }, /* 3272 */ { MAD_F(0x05edfc66) /* 0.370602036 */, 17 }, /* 3273 */ { MAD_F(0x05ee9ac3) /* 0.370753063 */, 17 }, /* 3274 */ { MAD_F(0x05ef3924) /* 0.370904105 */, 17 }, /* 3275 */ { MAD_F(0x05efd78a) /* 0.371055163 */, 17 }, /* 3276 */ { MAD_F(0x05f075f3) /* 0.371206237 */, 17 }, /* 3277 */ { MAD_F(0x05f11461) /* 0.371357326 */, 17 }, /* 3278 */ { MAD_F(0x05f1b2d3) /* 0.371508430 */, 17 }, /* 3279 */ { MAD_F(0x05f25148) /* 0.371659549 */, 17 }, /* 3280 */ { MAD_F(0x05f2efc2) /* 0.371810684 */, 17 }, /* 3281 */ { MAD_F(0x05f38e40) /* 0.371961834 */, 17 }, /* 3282 */ { MAD_F(0x05f42cc3) /* 0.372113000 */, 17 }, /* 3283 */ { MAD_F(0x05f4cb49) /* 0.372264181 */, 17 }, /* 3284 */ { MAD_F(0x05f569d3) /* 0.372415377 */, 17 }, /* 3285 */ { MAD_F(0x05f60862) /* 0.372566589 */, 17 }, /* 3286 */ { MAD_F(0x05f6a6f5) /* 0.372717816 */, 17 }, /* 3287 */ { MAD_F(0x05f7458b) /* 0.372869058 */, 17 }, /* 3288 */ { MAD_F(0x05f7e426) /* 0.373020316 */, 17 }, /* 3289 */ { MAD_F(0x05f882c5) /* 0.373171589 */, 17 }, /* 3290 */ { MAD_F(0x05f92169) /* 0.373322877 */, 17 }, /* 3291 */ { MAD_F(0x05f9c010) /* 0.373474181 */, 17 }, /* 3292 */ { MAD_F(0x05fa5ebb) /* 0.373625500 */, 17 }, /* 3293 */ { MAD_F(0x05fafd6b) /* 0.373776834 */, 17 }, /* 3294 */ { MAD_F(0x05fb9c1e) /* 0.373928184 */, 17 }, /* 3295 */ { MAD_F(0x05fc3ad6) /* 0.374079549 */, 17 }, /* 3296 */ { MAD_F(0x05fcd992) /* 0.374230929 */, 17 }, /* 3297 */ { MAD_F(0x05fd7852) /* 0.374382325 */, 17 }, /* 3298 */ { MAD_F(0x05fe1716) /* 0.374533735 */, 17 }, /* 3299 */ { MAD_F(0x05feb5de) /* 0.374685162 */, 17 }, /* 3300 */ { MAD_F(0x05ff54aa) /* 0.374836603 */, 17 }, /* 3301 */ { MAD_F(0x05fff37b) /* 0.374988060 */, 17 }, /* 3302 */ { MAD_F(0x0600924f) /* 0.375139532 */, 17 }, /* 3303 */ { MAD_F(0x06013128) /* 0.375291019 */, 17 }, /* 3304 */ { MAD_F(0x0601d004) /* 0.375442522 */, 17 }, /* 3305 */ { MAD_F(0x06026ee5) /* 0.375594040 */, 17 }, /* 3306 */ { MAD_F(0x06030dca) /* 0.375745573 */, 17 }, /* 3307 */ { MAD_F(0x0603acb3) /* 0.375897122 */, 17 }, /* 3308 */ { MAD_F(0x06044ba0) /* 0.376048685 */, 17 }, /* 3309 */ { MAD_F(0x0604ea91) /* 0.376200265 */, 17 }, /* 3310 */ { MAD_F(0x06058987) /* 0.376351859 */, 17 }, /* 3311 */ { MAD_F(0x06062880) /* 0.376503468 */, 17 }, /* 3312 */ { MAD_F(0x0606c77d) /* 0.376655093 */, 17 }, /* 3313 */ { MAD_F(0x0607667f) /* 0.376806733 */, 17 }, /* 3314 */ { MAD_F(0x06080585) /* 0.376958389 */, 17 }, /* 3315 */ { MAD_F(0x0608a48f) /* 0.377110059 */, 17 }, /* 3316 */ { MAD_F(0x0609439c) /* 0.377261745 */, 17 }, /* 3317 */ { MAD_F(0x0609e2ae) /* 0.377413446 */, 17 }, /* 3318 */ { MAD_F(0x060a81c4) /* 0.377565163 */, 17 }, /* 3319 */ { MAD_F(0x060b20df) /* 0.377716894 */, 17 }, /* 3320 */ { MAD_F(0x060bbffd) /* 0.377868641 */, 17 }, /* 3321 */ { MAD_F(0x060c5f1f) /* 0.378020403 */, 17 }, /* 3322 */ { MAD_F(0x060cfe46) /* 0.378172181 */, 17 }, /* 3323 */ { MAD_F(0x060d9d70) /* 0.378323973 */, 17 }, /* 3324 */ { MAD_F(0x060e3c9f) /* 0.378475781 */, 17 }, /* 3325 */ { MAD_F(0x060edbd1) /* 0.378627604 */, 17 }, /* 3326 */ { MAD_F(0x060f7b08) /* 0.378779442 */, 17 }, /* 3327 */ { MAD_F(0x06101a43) /* 0.378931296 */, 17 }, /* 3328 */ { MAD_F(0x0610b982) /* 0.379083164 */, 17 }, /* 3329 */ { MAD_F(0x061158c5) /* 0.379235048 */, 17 }, /* 3330 */ { MAD_F(0x0611f80c) /* 0.379386947 */, 17 }, /* 3331 */ { MAD_F(0x06129757) /* 0.379538862 */, 17 }, /* 3332 */ { MAD_F(0x061336a6) /* 0.379690791 */, 17 }, /* 3333 */ { MAD_F(0x0613d5fa) /* 0.379842736 */, 17 }, /* 3334 */ { MAD_F(0x06147551) /* 0.379994696 */, 17 }, /* 3335 */ { MAD_F(0x061514ad) /* 0.380146671 */, 17 }, /* 3336 */ { MAD_F(0x0615b40c) /* 0.380298661 */, 17 }, /* 3337 */ { MAD_F(0x06165370) /* 0.380450666 */, 17 }, /* 3338 */ { MAD_F(0x0616f2d8) /* 0.380602687 */, 17 }, /* 3339 */ { MAD_F(0x06179243) /* 0.380754723 */, 17 }, /* 3340 */ { MAD_F(0x061831b3) /* 0.380906774 */, 17 }, /* 3341 */ { MAD_F(0x0618d127) /* 0.381058840 */, 17 }, /* 3342 */ { MAD_F(0x0619709f) /* 0.381210921 */, 17 }, /* 3343 */ { MAD_F(0x061a101b) /* 0.381363018 */, 17 }, /* 3344 */ { MAD_F(0x061aaf9c) /* 0.381515130 */, 17 }, /* 3345 */ { MAD_F(0x061b4f20) /* 0.381667257 */, 17 }, /* 3346 */ { MAD_F(0x061beea8) /* 0.381819399 */, 17 }, /* 3347 */ { MAD_F(0x061c8e34) /* 0.381971556 */, 17 }, /* 3348 */ { MAD_F(0x061d2dc5) /* 0.382123728 */, 17 }, /* 3349 */ { MAD_F(0x061dcd59) /* 0.382275916 */, 17 }, /* 3350 */ { MAD_F(0x061e6cf2) /* 0.382428118 */, 17 }, /* 3351 */ { MAD_F(0x061f0c8f) /* 0.382580336 */, 17 }, /* 3352 */ { MAD_F(0x061fac2f) /* 0.382732569 */, 17 }, /* 3353 */ { MAD_F(0x06204bd4) /* 0.382884817 */, 17 }, /* 3354 */ { MAD_F(0x0620eb7d) /* 0.383037080 */, 17 }, /* 3355 */ { MAD_F(0x06218b2a) /* 0.383189358 */, 17 }, /* 3356 */ { MAD_F(0x06222adb) /* 0.383341652 */, 17 }, /* 3357 */ { MAD_F(0x0622ca90) /* 0.383493960 */, 17 }, /* 3358 */ { MAD_F(0x06236a49) /* 0.383646284 */, 17 }, /* 3359 */ { MAD_F(0x06240a06) /* 0.383798623 */, 17 }, /* 3360 */ { MAD_F(0x0624a9c7) /* 0.383950977 */, 17 }, /* 3361 */ { MAD_F(0x0625498d) /* 0.384103346 */, 17 }, /* 3362 */ { MAD_F(0x0625e956) /* 0.384255730 */, 17 }, /* 3363 */ { MAD_F(0x06268923) /* 0.384408129 */, 17 }, /* 3364 */ { MAD_F(0x062728f5) /* 0.384560544 */, 17 }, /* 3365 */ { MAD_F(0x0627c8ca) /* 0.384712973 */, 17 }, /* 3366 */ { MAD_F(0x062868a4) /* 0.384865418 */, 17 }, /* 3367 */ { MAD_F(0x06290881) /* 0.385017878 */, 17 }, /* 3368 */ { MAD_F(0x0629a863) /* 0.385170352 */, 17 }, /* 3369 */ { MAD_F(0x062a4849) /* 0.385322842 */, 17 }, /* 3370 */ { MAD_F(0x062ae832) /* 0.385475347 */, 17 }, /* 3371 */ { MAD_F(0x062b8820) /* 0.385627867 */, 17 }, /* 3372 */ { MAD_F(0x062c2812) /* 0.385780402 */, 17 }, /* 3373 */ { MAD_F(0x062cc808) /* 0.385932953 */, 17 }, /* 3374 */ { MAD_F(0x062d6802) /* 0.386085518 */, 17 }, /* 3375 */ { MAD_F(0x062e0800) /* 0.386238098 */, 17 }, /* 3376 */ { MAD_F(0x062ea802) /* 0.386390694 */, 17 }, /* 3377 */ { MAD_F(0x062f4808) /* 0.386543304 */, 17 }, /* 3378 */ { MAD_F(0x062fe812) /* 0.386695930 */, 17 }, /* 3379 */ { MAD_F(0x06308820) /* 0.386848570 */, 17 }, /* 3380 */ { MAD_F(0x06312832) /* 0.387001226 */, 17 }, /* 3381 */ { MAD_F(0x0631c849) /* 0.387153897 */, 17 }, /* 3382 */ { MAD_F(0x06326863) /* 0.387306582 */, 17 }, /* 3383 */ { MAD_F(0x06330881) /* 0.387459283 */, 17 }, /* 3384 */ { MAD_F(0x0633a8a3) /* 0.387611999 */, 17 }, /* 3385 */ { MAD_F(0x063448ca) /* 0.387764730 */, 17 }, /* 3386 */ { MAD_F(0x0634e8f4) /* 0.387917476 */, 17 }, /* 3387 */ { MAD_F(0x06358923) /* 0.388070237 */, 17 }, /* 3388 */ { MAD_F(0x06362955) /* 0.388223013 */, 17 }, /* 3389 */ { MAD_F(0x0636c98c) /* 0.388375804 */, 17 }, /* 3390 */ { MAD_F(0x063769c6) /* 0.388528610 */, 17 }, /* 3391 */ { MAD_F(0x06380a05) /* 0.388681431 */, 17 }, /* 3392 */ { MAD_F(0x0638aa48) /* 0.388834268 */, 17 }, /* 3393 */ { MAD_F(0x06394a8e) /* 0.388987119 */, 17 }, /* 3394 */ { MAD_F(0x0639ead9) /* 0.389139985 */, 17 }, /* 3395 */ { MAD_F(0x063a8b28) /* 0.389292866 */, 17 }, /* 3396 */ { MAD_F(0x063b2b7b) /* 0.389445762 */, 17 }, /* 3397 */ { MAD_F(0x063bcbd1) /* 0.389598674 */, 17 }, /* 3398 */ { MAD_F(0x063c6c2c) /* 0.389751600 */, 17 }, /* 3399 */ { MAD_F(0x063d0c8b) /* 0.389904541 */, 17 }, /* 3400 */ { MAD_F(0x063dacee) /* 0.390057497 */, 17 }, /* 3401 */ { MAD_F(0x063e4d55) /* 0.390210468 */, 17 }, /* 3402 */ { MAD_F(0x063eedc0) /* 0.390363455 */, 17 }, /* 3403 */ { MAD_F(0x063f8e2f) /* 0.390516456 */, 17 }, /* 3404 */ { MAD_F(0x06402ea2) /* 0.390669472 */, 17 }, /* 3405 */ { MAD_F(0x0640cf19) /* 0.390822503 */, 17 }, /* 3406 */ { MAD_F(0x06416f94) /* 0.390975549 */, 17 }, /* 3407 */ { MAD_F(0x06421013) /* 0.391128611 */, 17 }, /* 3408 */ { MAD_F(0x0642b096) /* 0.391281687 */, 17 }, /* 3409 */ { MAD_F(0x0643511d) /* 0.391434778 */, 17 }, /* 3410 */ { MAD_F(0x0643f1a8) /* 0.391587884 */, 17 }, /* 3411 */ { MAD_F(0x06449237) /* 0.391741005 */, 17 }, /* 3412 */ { MAD_F(0x064532ca) /* 0.391894141 */, 17 }, /* 3413 */ { MAD_F(0x0645d361) /* 0.392047292 */, 17 }, /* 3414 */ { MAD_F(0x064673fc) /* 0.392200458 */, 17 }, /* 3415 */ { MAD_F(0x0647149c) /* 0.392353638 */, 17 }, /* 3416 */ { MAD_F(0x0647b53f) /* 0.392506834 */, 17 }, /* 3417 */ { MAD_F(0x064855e6) /* 0.392660045 */, 17 }, /* 3418 */ { MAD_F(0x0648f691) /* 0.392813271 */, 17 }, /* 3419 */ { MAD_F(0x06499740) /* 0.392966511 */, 17 }, /* 3420 */ { MAD_F(0x064a37f4) /* 0.393119767 */, 17 }, /* 3421 */ { MAD_F(0x064ad8ab) /* 0.393273038 */, 17 }, /* 3422 */ { MAD_F(0x064b7966) /* 0.393426323 */, 17 }, /* 3423 */ { MAD_F(0x064c1a25) /* 0.393579623 */, 17 }, /* 3424 */ { MAD_F(0x064cbae9) /* 0.393732939 */, 17 }, /* 3425 */ { MAD_F(0x064d5bb0) /* 0.393886269 */, 17 }, /* 3426 */ { MAD_F(0x064dfc7b) /* 0.394039614 */, 17 }, /* 3427 */ { MAD_F(0x064e9d4b) /* 0.394192974 */, 17 }, /* 3428 */ { MAD_F(0x064f3e1e) /* 0.394346349 */, 17 }, /* 3429 */ { MAD_F(0x064fdef5) /* 0.394499739 */, 17 }, /* 3430 */ { MAD_F(0x06507fd0) /* 0.394653144 */, 17 }, /* 3431 */ { MAD_F(0x065120b0) /* 0.394806564 */, 17 }, /* 3432 */ { MAD_F(0x0651c193) /* 0.394959999 */, 17 }, /* 3433 */ { MAD_F(0x0652627a) /* 0.395113448 */, 17 }, /* 3434 */ { MAD_F(0x06530366) /* 0.395266913 */, 17 }, /* 3435 */ { MAD_F(0x0653a455) /* 0.395420392 */, 17 }, /* 3436 */ { MAD_F(0x06544548) /* 0.395573886 */, 17 }, /* 3437 */ { MAD_F(0x0654e640) /* 0.395727395 */, 17 }, /* 3438 */ { MAD_F(0x0655873b) /* 0.395880919 */, 17 }, /* 3439 */ { MAD_F(0x0656283a) /* 0.396034458 */, 17 }, /* 3440 */ { MAD_F(0x0656c93d) /* 0.396188012 */, 17 }, /* 3441 */ { MAD_F(0x06576a45) /* 0.396341581 */, 17 }, /* 3442 */ { MAD_F(0x06580b50) /* 0.396495164 */, 17 }, /* 3443 */ { MAD_F(0x0658ac5f) /* 0.396648763 */, 17 }, /* 3444 */ { MAD_F(0x06594d73) /* 0.396802376 */, 17 }, /* 3445 */ { MAD_F(0x0659ee8a) /* 0.396956004 */, 17 }, /* 3446 */ { MAD_F(0x065a8fa5) /* 0.397109647 */, 17 }, /* 3447 */ { MAD_F(0x065b30c4) /* 0.397263305 */, 17 }, /* 3448 */ { MAD_F(0x065bd1e7) /* 0.397416978 */, 17 }, /* 3449 */ { MAD_F(0x065c730f) /* 0.397570666 */, 17 }, /* 3450 */ { MAD_F(0x065d143a) /* 0.397724368 */, 17 }, /* 3451 */ { MAD_F(0x065db569) /* 0.397878085 */, 17 }, /* 3452 */ { MAD_F(0x065e569c) /* 0.398031818 */, 17 }, /* 3453 */ { MAD_F(0x065ef7d3) /* 0.398185565 */, 17 }, /* 3454 */ { MAD_F(0x065f990e) /* 0.398339326 */, 17 }, /* 3455 */ { MAD_F(0x06603a4e) /* 0.398493103 */, 17 }, /* 3456 */ { MAD_F(0x0660db91) /* 0.398646895 */, 17 }, /* 3457 */ { MAD_F(0x06617cd8) /* 0.398800701 */, 17 }, /* 3458 */ { MAD_F(0x06621e23) /* 0.398954522 */, 17 }, /* 3459 */ { MAD_F(0x0662bf72) /* 0.399108358 */, 17 }, /* 3460 */ { MAD_F(0x066360c5) /* 0.399262209 */, 17 }, /* 3461 */ { MAD_F(0x0664021c) /* 0.399416075 */, 17 }, /* 3462 */ { MAD_F(0x0664a377) /* 0.399569955 */, 17 }, /* 3463 */ { MAD_F(0x066544d6) /* 0.399723851 */, 17 }, /* 3464 */ { MAD_F(0x0665e639) /* 0.399877761 */, 17 }, /* 3465 */ { MAD_F(0x066687a0) /* 0.400031686 */, 17 }, /* 3466 */ { MAD_F(0x0667290b) /* 0.400185625 */, 17 }, /* 3467 */ { MAD_F(0x0667ca79) /* 0.400339580 */, 17 }, /* 3468 */ { MAD_F(0x06686bec) /* 0.400493549 */, 17 }, /* 3469 */ { MAD_F(0x06690d63) /* 0.400647534 */, 17 }, /* 3470 */ { MAD_F(0x0669aede) /* 0.400801533 */, 17 }, /* 3471 */ { MAD_F(0x066a505d) /* 0.400955546 */, 17 }, /* 3472 */ { MAD_F(0x066af1df) /* 0.401109575 */, 17 }, /* 3473 */ { MAD_F(0x066b9366) /* 0.401263618 */, 17 }, /* 3474 */ { MAD_F(0x066c34f1) /* 0.401417676 */, 17 }, /* 3475 */ { MAD_F(0x066cd67f) /* 0.401571749 */, 17 }, /* 3476 */ { MAD_F(0x066d7812) /* 0.401725837 */, 17 }, /* 3477 */ { MAD_F(0x066e19a9) /* 0.401879939 */, 17 }, /* 3478 */ { MAD_F(0x066ebb43) /* 0.402034056 */, 17 }, /* 3479 */ { MAD_F(0x066f5ce2) /* 0.402188188 */, 17 }, /* 3480 */ { MAD_F(0x066ffe84) /* 0.402342335 */, 17 }, /* 3481 */ { MAD_F(0x0670a02a) /* 0.402496497 */, 17 }, /* 3482 */ { MAD_F(0x067141d5) /* 0.402650673 */, 17 }, /* 3483 */ { MAD_F(0x0671e383) /* 0.402804864 */, 17 }, /* 3484 */ { MAD_F(0x06728535) /* 0.402959070 */, 17 }, /* 3485 */ { MAD_F(0x067326ec) /* 0.403113291 */, 17 }, /* 3486 */ { MAD_F(0x0673c8a6) /* 0.403267526 */, 17 }, /* 3487 */ { MAD_F(0x06746a64) /* 0.403421776 */, 17 }, /* 3488 */ { MAD_F(0x06750c26) /* 0.403576041 */, 17 }, /* 3489 */ { MAD_F(0x0675adec) /* 0.403730320 */, 17 }, /* 3490 */ { MAD_F(0x06764fb6) /* 0.403884615 */, 17 }, /* 3491 */ { MAD_F(0x0676f184) /* 0.404038924 */, 17 }, /* 3492 */ { MAD_F(0x06779356) /* 0.404193247 */, 17 }, /* 3493 */ { MAD_F(0x0678352c) /* 0.404347586 */, 17 }, /* 3494 */ { MAD_F(0x0678d706) /* 0.404501939 */, 17 }, /* 3495 */ { MAD_F(0x067978e4) /* 0.404656307 */, 17 }, /* 3496 */ { MAD_F(0x067a1ac6) /* 0.404810690 */, 17 }, /* 3497 */ { MAD_F(0x067abcac) /* 0.404965087 */, 17 }, /* 3498 */ { MAD_F(0x067b5e95) /* 0.405119499 */, 17 }, /* 3499 */ { MAD_F(0x067c0083) /* 0.405273926 */, 17 }, /* 3500 */ { MAD_F(0x067ca275) /* 0.405428368 */, 17 }, /* 3501 */ { MAD_F(0x067d446a) /* 0.405582824 */, 17 }, /* 3502 */ { MAD_F(0x067de664) /* 0.405737295 */, 17 }, /* 3503 */ { MAD_F(0x067e8861) /* 0.405891781 */, 17 }, /* 3504 */ { MAD_F(0x067f2a62) /* 0.406046281 */, 17 }, /* 3505 */ { MAD_F(0x067fcc68) /* 0.406200796 */, 17 }, /* 3506 */ { MAD_F(0x06806e71) /* 0.406355326 */, 17 }, /* 3507 */ { MAD_F(0x0681107e) /* 0.406509870 */, 17 }, /* 3508 */ { MAD_F(0x0681b28f) /* 0.406664429 */, 17 }, /* 3509 */ { MAD_F(0x068254a4) /* 0.406819003 */, 17 }, /* 3510 */ { MAD_F(0x0682f6bd) /* 0.406973592 */, 17 }, /* 3511 */ { MAD_F(0x068398da) /* 0.407128195 */, 17 }, /* 3512 */ { MAD_F(0x06843afb) /* 0.407282813 */, 17 }, /* 3513 */ { MAD_F(0x0684dd20) /* 0.407437445 */, 17 }, /* 3514 */ { MAD_F(0x06857f49) /* 0.407592093 */, 17 }, /* 3515 */ { MAD_F(0x06862176) /* 0.407746754 */, 17 }, /* 3516 */ { MAD_F(0x0686c3a6) /* 0.407901431 */, 17 }, /* 3517 */ { MAD_F(0x068765db) /* 0.408056122 */, 17 }, /* 3518 */ { MAD_F(0x06880814) /* 0.408210828 */, 17 }, /* 3519 */ { MAD_F(0x0688aa50) /* 0.408365549 */, 17 }, /* 3520 */ { MAD_F(0x06894c90) /* 0.408520284 */, 17 }, /* 3521 */ { MAD_F(0x0689eed5) /* 0.408675034 */, 17 }, /* 3522 */ { MAD_F(0x068a911d) /* 0.408829798 */, 17 }, /* 3523 */ { MAD_F(0x068b3369) /* 0.408984577 */, 17 }, /* 3524 */ { MAD_F(0x068bd5b9) /* 0.409139371 */, 17 }, /* 3525 */ { MAD_F(0x068c780e) /* 0.409294180 */, 17 }, /* 3526 */ { MAD_F(0x068d1a66) /* 0.409449003 */, 17 }, /* 3527 */ { MAD_F(0x068dbcc1) /* 0.409603840 */, 17 }, /* 3528 */ { MAD_F(0x068e5f21) /* 0.409758693 */, 17 }, /* 3529 */ { MAD_F(0x068f0185) /* 0.409913560 */, 17 }, /* 3530 */ { MAD_F(0x068fa3ed) /* 0.410068441 */, 17 }, /* 3531 */ { MAD_F(0x06904658) /* 0.410223338 */, 17 }, /* 3532 */ { MAD_F(0x0690e8c8) /* 0.410378249 */, 17 }, /* 3533 */ { MAD_F(0x06918b3c) /* 0.410533174 */, 17 }, /* 3534 */ { MAD_F(0x06922db3) /* 0.410688114 */, 17 }, /* 3535 */ { MAD_F(0x0692d02e) /* 0.410843069 */, 17 }, /* 3536 */ { MAD_F(0x069372ae) /* 0.410998038 */, 17 }, /* 3537 */ { MAD_F(0x06941531) /* 0.411153022 */, 17 }, /* 3538 */ { MAD_F(0x0694b7b8) /* 0.411308021 */, 17 }, /* 3539 */ { MAD_F(0x06955a43) /* 0.411463034 */, 17 }, /* 3540 */ { MAD_F(0x0695fcd2) /* 0.411618062 */, 17 }, /* 3541 */ { MAD_F(0x06969f65) /* 0.411773104 */, 17 }, /* 3542 */ { MAD_F(0x069741fb) /* 0.411928161 */, 17 }, /* 3543 */ { MAD_F(0x0697e496) /* 0.412083232 */, 17 }, /* 3544 */ { MAD_F(0x06988735) /* 0.412238319 */, 17 }, /* 3545 */ { MAD_F(0x069929d7) /* 0.412393419 */, 17 }, /* 3546 */ { MAD_F(0x0699cc7e) /* 0.412548535 */, 17 }, /* 3547 */ { MAD_F(0x069a6f28) /* 0.412703664 */, 17 }, /* 3548 */ { MAD_F(0x069b11d6) /* 0.412858809 */, 17 }, /* 3549 */ { MAD_F(0x069bb489) /* 0.413013968 */, 17 }, /* 3550 */ { MAD_F(0x069c573f) /* 0.413169142 */, 17 }, /* 3551 */ { MAD_F(0x069cf9f9) /* 0.413324330 */, 17 }, /* 3552 */ { MAD_F(0x069d9cb7) /* 0.413479532 */, 17 }, /* 3553 */ { MAD_F(0x069e3f78) /* 0.413634750 */, 17 }, /* 3554 */ { MAD_F(0x069ee23e) /* 0.413789982 */, 17 }, /* 3555 */ { MAD_F(0x069f8508) /* 0.413945228 */, 17 }, /* 3556 */ { MAD_F(0x06a027d5) /* 0.414100489 */, 17 }, /* 3557 */ { MAD_F(0x06a0caa7) /* 0.414255765 */, 17 }, /* 3558 */ { MAD_F(0x06a16d7c) /* 0.414411055 */, 17 }, /* 3559 */ { MAD_F(0x06a21055) /* 0.414566359 */, 17 }, /* 3560 */ { MAD_F(0x06a2b333) /* 0.414721679 */, 17 }, /* 3561 */ { MAD_F(0x06a35614) /* 0.414877012 */, 17 }, /* 3562 */ { MAD_F(0x06a3f8f9) /* 0.415032361 */, 17 }, /* 3563 */ { MAD_F(0x06a49be2) /* 0.415187723 */, 17 }, /* 3564 */ { MAD_F(0x06a53ece) /* 0.415343101 */, 17 }, /* 3565 */ { MAD_F(0x06a5e1bf) /* 0.415498493 */, 17 }, /* 3566 */ { MAD_F(0x06a684b4) /* 0.415653899 */, 17 }, /* 3567 */ { MAD_F(0x06a727ac) /* 0.415809320 */, 17 }, /* 3568 */ { MAD_F(0x06a7caa9) /* 0.415964756 */, 17 }, /* 3569 */ { MAD_F(0x06a86da9) /* 0.416120206 */, 17 }, /* 3570 */ { MAD_F(0x06a910ad) /* 0.416275670 */, 17 }, /* 3571 */ { MAD_F(0x06a9b3b5) /* 0.416431149 */, 17 }, /* 3572 */ { MAD_F(0x06aa56c1) /* 0.416586643 */, 17 }, /* 3573 */ { MAD_F(0x06aaf9d1) /* 0.416742151 */, 17 }, /* 3574 */ { MAD_F(0x06ab9ce5) /* 0.416897673 */, 17 }, /* 3575 */ { MAD_F(0x06ac3ffc) /* 0.417053210 */, 17 }, /* 3576 */ { MAD_F(0x06ace318) /* 0.417208762 */, 17 }, /* 3577 */ { MAD_F(0x06ad8637) /* 0.417364328 */, 17 }, /* 3578 */ { MAD_F(0x06ae295b) /* 0.417519909 */, 17 }, /* 3579 */ { MAD_F(0x06aecc82) /* 0.417675504 */, 17 }, /* 3580 */ { MAD_F(0x06af6fad) /* 0.417831113 */, 17 }, /* 3581 */ { MAD_F(0x06b012dc) /* 0.417986737 */, 17 }, /* 3582 */ { MAD_F(0x06b0b60f) /* 0.418142376 */, 17 }, /* 3583 */ { MAD_F(0x06b15946) /* 0.418298029 */, 17 }, /* 3584 */ { MAD_F(0x06b1fc81) /* 0.418453696 */, 17 }, /* 3585 */ { MAD_F(0x06b29fbf) /* 0.418609378 */, 17 }, /* 3586 */ { MAD_F(0x06b34302) /* 0.418765075 */, 17 }, /* 3587 */ { MAD_F(0x06b3e648) /* 0.418920786 */, 17 }, /* 3588 */ { MAD_F(0x06b48992) /* 0.419076511 */, 17 }, /* 3589 */ { MAD_F(0x06b52ce0) /* 0.419232251 */, 17 }, /* 3590 */ { MAD_F(0x06b5d032) /* 0.419388005 */, 17 }, /* 3591 */ { MAD_F(0x06b67388) /* 0.419543774 */, 17 }, /* 3592 */ { MAD_F(0x06b716e2) /* 0.419699557 */, 17 }, /* 3593 */ { MAD_F(0x06b7ba3f) /* 0.419855355 */, 17 }, /* 3594 */ { MAD_F(0x06b85da1) /* 0.420011167 */, 17 }, /* 3595 */ { MAD_F(0x06b90106) /* 0.420166994 */, 17 }, /* 3596 */ { MAD_F(0x06b9a470) /* 0.420322835 */, 17 }, /* 3597 */ { MAD_F(0x06ba47dd) /* 0.420478690 */, 17 }, /* 3598 */ { MAD_F(0x06baeb4e) /* 0.420634560 */, 17 }, /* 3599 */ { MAD_F(0x06bb8ec3) /* 0.420790445 */, 17 }, /* 3600 */ { MAD_F(0x06bc323b) /* 0.420946343 */, 17 }, /* 3601 */ { MAD_F(0x06bcd5b8) /* 0.421102257 */, 17 }, /* 3602 */ { MAD_F(0x06bd7939) /* 0.421258184 */, 17 }, /* 3603 */ { MAD_F(0x06be1cbd) /* 0.421414127 */, 17 }, /* 3604 */ { MAD_F(0x06bec045) /* 0.421570083 */, 17 }, /* 3605 */ { MAD_F(0x06bf63d1) /* 0.421726054 */, 17 }, /* 3606 */ { MAD_F(0x06c00761) /* 0.421882040 */, 17 }, /* 3607 */ { MAD_F(0x06c0aaf5) /* 0.422038039 */, 17 }, /* 3608 */ { MAD_F(0x06c14e8d) /* 0.422194054 */, 17 }, /* 3609 */ { MAD_F(0x06c1f229) /* 0.422350082 */, 17 }, /* 3610 */ { MAD_F(0x06c295c8) /* 0.422506125 */, 17 }, /* 3611 */ { MAD_F(0x06c3396c) /* 0.422662183 */, 17 }, /* 3612 */ { MAD_F(0x06c3dd13) /* 0.422818255 */, 17 }, /* 3613 */ { MAD_F(0x06c480be) /* 0.422974341 */, 17 }, /* 3614 */ { MAD_F(0x06c5246d) /* 0.423130442 */, 17 }, /* 3615 */ { MAD_F(0x06c5c820) /* 0.423286557 */, 17 }, /* 3616 */ { MAD_F(0x06c66bd6) /* 0.423442686 */, 17 }, /* 3617 */ { MAD_F(0x06c70f91) /* 0.423598830 */, 17 }, /* 3618 */ { MAD_F(0x06c7b34f) /* 0.423754988 */, 17 }, /* 3619 */ { MAD_F(0x06c85712) /* 0.423911161 */, 17 }, /* 3620 */ { MAD_F(0x06c8fad8) /* 0.424067348 */, 17 }, /* 3621 */ { MAD_F(0x06c99ea2) /* 0.424223550 */, 17 }, /* 3622 */ { MAD_F(0x06ca4270) /* 0.424379765 */, 17 }, /* 3623 */ { MAD_F(0x06cae641) /* 0.424535996 */, 17 }, /* 3624 */ { MAD_F(0x06cb8a17) /* 0.424692240 */, 17 }, /* 3625 */ { MAD_F(0x06cc2df0) /* 0.424848499 */, 17 }, /* 3626 */ { MAD_F(0x06ccd1ce) /* 0.425004772 */, 17 }, /* 3627 */ { MAD_F(0x06cd75af) /* 0.425161060 */, 17 }, /* 3628 */ { MAD_F(0x06ce1994) /* 0.425317362 */, 17 }, /* 3629 */ { MAD_F(0x06cebd7d) /* 0.425473678 */, 17 }, /* 3630 */ { MAD_F(0x06cf6169) /* 0.425630009 */, 17 }, /* 3631 */ { MAD_F(0x06d0055a) /* 0.425786354 */, 17 }, /* 3632 */ { MAD_F(0x06d0a94e) /* 0.425942714 */, 17 }, /* 3633 */ { MAD_F(0x06d14d47) /* 0.426099088 */, 17 }, /* 3634 */ { MAD_F(0x06d1f143) /* 0.426255476 */, 17 }, /* 3635 */ { MAD_F(0x06d29543) /* 0.426411878 */, 17 }, /* 3636 */ { MAD_F(0x06d33947) /* 0.426568295 */, 17 }, /* 3637 */ { MAD_F(0x06d3dd4e) /* 0.426724726 */, 17 }, /* 3638 */ { MAD_F(0x06d4815a) /* 0.426881172 */, 17 }, /* 3639 */ { MAD_F(0x06d52569) /* 0.427037632 */, 17 }, /* 3640 */ { MAD_F(0x06d5c97c) /* 0.427194106 */, 17 }, /* 3641 */ { MAD_F(0x06d66d93) /* 0.427350594 */, 17 }, /* 3642 */ { MAD_F(0x06d711ae) /* 0.427507097 */, 17 }, /* 3643 */ { MAD_F(0x06d7b5cd) /* 0.427663614 */, 17 }, /* 3644 */ { MAD_F(0x06d859f0) /* 0.427820146 */, 17 }, /* 3645 */ { MAD_F(0x06d8fe16) /* 0.427976692 */, 17 }, /* 3646 */ { MAD_F(0x06d9a240) /* 0.428133252 */, 17 }, /* 3647 */ { MAD_F(0x06da466f) /* 0.428289826 */, 17 }, /* 3648 */ { MAD_F(0x06daeaa1) /* 0.428446415 */, 17 }, /* 3649 */ { MAD_F(0x06db8ed6) /* 0.428603018 */, 17 }, /* 3650 */ { MAD_F(0x06dc3310) /* 0.428759635 */, 17 }, /* 3651 */ { MAD_F(0x06dcd74d) /* 0.428916267 */, 17 }, /* 3652 */ { MAD_F(0x06dd7b8f) /* 0.429072913 */, 17 }, /* 3653 */ { MAD_F(0x06de1fd4) /* 0.429229573 */, 17 }, /* 3654 */ { MAD_F(0x06dec41d) /* 0.429386248 */, 17 }, /* 3655 */ { MAD_F(0x06df686a) /* 0.429542937 */, 17 }, /* 3656 */ { MAD_F(0x06e00cbb) /* 0.429699640 */, 17 }, /* 3657 */ { MAD_F(0x06e0b10f) /* 0.429856357 */, 17 }, /* 3658 */ { MAD_F(0x06e15567) /* 0.430013089 */, 17 }, /* 3659 */ { MAD_F(0x06e1f9c4) /* 0.430169835 */, 17 }, /* 3660 */ { MAD_F(0x06e29e24) /* 0.430326595 */, 17 }, /* 3661 */ { MAD_F(0x06e34287) /* 0.430483370 */, 17 }, /* 3662 */ { MAD_F(0x06e3e6ef) /* 0.430640159 */, 17 }, /* 3663 */ { MAD_F(0x06e48b5b) /* 0.430796962 */, 17 }, /* 3664 */ { MAD_F(0x06e52fca) /* 0.430953779 */, 17 }, /* 3665 */ { MAD_F(0x06e5d43d) /* 0.431110611 */, 17 }, /* 3666 */ { MAD_F(0x06e678b4) /* 0.431267457 */, 17 }, /* 3667 */ { MAD_F(0x06e71d2f) /* 0.431424317 */, 17 }, /* 3668 */ { MAD_F(0x06e7c1ae) /* 0.431581192 */, 17 }, /* 3669 */ { MAD_F(0x06e86630) /* 0.431738080 */, 17 }, /* 3670 */ { MAD_F(0x06e90ab7) /* 0.431894983 */, 17 }, /* 3671 */ { MAD_F(0x06e9af41) /* 0.432051900 */, 17 }, /* 3672 */ { MAD_F(0x06ea53cf) /* 0.432208832 */, 17 }, /* 3673 */ { MAD_F(0x06eaf860) /* 0.432365778 */, 17 }, /* 3674 */ { MAD_F(0x06eb9cf6) /* 0.432522737 */, 17 }, /* 3675 */ { MAD_F(0x06ec418f) /* 0.432679712 */, 17 }, /* 3676 */ { MAD_F(0x06ece62d) /* 0.432836700 */, 17 }, /* 3677 */ { MAD_F(0x06ed8ace) /* 0.432993703 */, 17 }, /* 3678 */ { MAD_F(0x06ee2f73) /* 0.433150720 */, 17 }, /* 3679 */ { MAD_F(0x06eed41b) /* 0.433307751 */, 17 }, /* 3680 */ { MAD_F(0x06ef78c8) /* 0.433464796 */, 17 }, /* 3681 */ { MAD_F(0x06f01d78) /* 0.433621856 */, 17 }, /* 3682 */ { MAD_F(0x06f0c22c) /* 0.433778929 */, 17 }, /* 3683 */ { MAD_F(0x06f166e4) /* 0.433936017 */, 17 }, /* 3684 */ { MAD_F(0x06f20ba0) /* 0.434093120 */, 17 }, /* 3685 */ { MAD_F(0x06f2b060) /* 0.434250236 */, 17 }, /* 3686 */ { MAD_F(0x06f35523) /* 0.434407367 */, 17 }, /* 3687 */ { MAD_F(0x06f3f9eb) /* 0.434564512 */, 17 }, /* 3688 */ { MAD_F(0x06f49eb6) /* 0.434721671 */, 17 }, /* 3689 */ { MAD_F(0x06f54385) /* 0.434878844 */, 17 }, /* 3690 */ { MAD_F(0x06f5e857) /* 0.435036032 */, 17 }, /* 3691 */ { MAD_F(0x06f68d2e) /* 0.435193233 */, 17 }, /* 3692 */ { MAD_F(0x06f73208) /* 0.435350449 */, 17 }, /* 3693 */ { MAD_F(0x06f7d6e6) /* 0.435507679 */, 17 }, /* 3694 */ { MAD_F(0x06f87bc8) /* 0.435664924 */, 17 }, /* 3695 */ { MAD_F(0x06f920ae) /* 0.435822182 */, 17 }, /* 3696 */ { MAD_F(0x06f9c597) /* 0.435979455 */, 17 }, /* 3697 */ { MAD_F(0x06fa6a85) /* 0.436136741 */, 17 }, /* 3698 */ { MAD_F(0x06fb0f76) /* 0.436294042 */, 17 }, /* 3699 */ { MAD_F(0x06fbb46b) /* 0.436451358 */, 17 }, /* 3700 */ { MAD_F(0x06fc5964) /* 0.436608687 */, 17 }, /* 3701 */ { MAD_F(0x06fcfe60) /* 0.436766031 */, 17 }, /* 3702 */ { MAD_F(0x06fda361) /* 0.436923388 */, 17 }, /* 3703 */ { MAD_F(0x06fe4865) /* 0.437080760 */, 17 }, /* 3704 */ { MAD_F(0x06feed6d) /* 0.437238146 */, 17 }, /* 3705 */ { MAD_F(0x06ff9279) /* 0.437395547 */, 17 }, /* 3706 */ { MAD_F(0x07003788) /* 0.437552961 */, 17 }, /* 3707 */ { MAD_F(0x0700dc9c) /* 0.437710389 */, 17 }, /* 3708 */ { MAD_F(0x070181b3) /* 0.437867832 */, 17 }, /* 3709 */ { MAD_F(0x070226ce) /* 0.438025289 */, 17 }, /* 3710 */ { MAD_F(0x0702cbed) /* 0.438182760 */, 17 }, /* 3711 */ { MAD_F(0x0703710f) /* 0.438340245 */, 17 }, /* 3712 */ { MAD_F(0x07041636) /* 0.438497744 */, 17 }, /* 3713 */ { MAD_F(0x0704bb60) /* 0.438655258 */, 17 }, /* 3714 */ { MAD_F(0x0705608e) /* 0.438812785 */, 17 }, /* 3715 */ { MAD_F(0x070605c0) /* 0.438970327 */, 17 }, /* 3716 */ { MAD_F(0x0706aaf5) /* 0.439127883 */, 17 }, /* 3717 */ { MAD_F(0x0707502f) /* 0.439285453 */, 17 }, /* 3718 */ { MAD_F(0x0707f56c) /* 0.439443037 */, 17 }, /* 3719 */ { MAD_F(0x07089aad) /* 0.439600635 */, 17 }, /* 3720 */ { MAD_F(0x07093ff2) /* 0.439758248 */, 17 }, /* 3721 */ { MAD_F(0x0709e53a) /* 0.439915874 */, 17 }, /* 3722 */ { MAD_F(0x070a8a86) /* 0.440073515 */, 17 }, /* 3723 */ { MAD_F(0x070b2fd7) /* 0.440231170 */, 17 }, /* 3724 */ { MAD_F(0x070bd52a) /* 0.440388839 */, 17 }, /* 3725 */ { MAD_F(0x070c7a82) /* 0.440546522 */, 17 }, /* 3726 */ { MAD_F(0x070d1fde) /* 0.440704219 */, 17 }, /* 3727 */ { MAD_F(0x070dc53d) /* 0.440861930 */, 17 }, /* 3728 */ { MAD_F(0x070e6aa0) /* 0.441019655 */, 17 }, /* 3729 */ { MAD_F(0x070f1007) /* 0.441177395 */, 17 }, /* 3730 */ { MAD_F(0x070fb571) /* 0.441335148 */, 17 }, /* 3731 */ { MAD_F(0x07105ae0) /* 0.441492916 */, 17 }, /* 3732 */ { MAD_F(0x07110052) /* 0.441650697 */, 17 }, /* 3733 */ { MAD_F(0x0711a5c8) /* 0.441808493 */, 17 }, /* 3734 */ { MAD_F(0x07124b42) /* 0.441966303 */, 17 }, /* 3735 */ { MAD_F(0x0712f0bf) /* 0.442124127 */, 17 }, /* 3736 */ { MAD_F(0x07139641) /* 0.442281965 */, 17 }, /* 3737 */ { MAD_F(0x07143bc6) /* 0.442439817 */, 17 }, /* 3738 */ { MAD_F(0x0714e14f) /* 0.442597683 */, 17 }, /* 3739 */ { MAD_F(0x071586db) /* 0.442755564 */, 17 }, /* 3740 */ { MAD_F(0x07162c6c) /* 0.442913458 */, 17 }, /* 3741 */ { MAD_F(0x0716d200) /* 0.443071366 */, 17 }, /* 3742 */ { MAD_F(0x07177798) /* 0.443229289 */, 17 }, /* 3743 */ { MAD_F(0x07181d34) /* 0.443387226 */, 17 }, /* 3744 */ { MAD_F(0x0718c2d3) /* 0.443545176 */, 17 }, /* 3745 */ { MAD_F(0x07196877) /* 0.443703141 */, 17 }, /* 3746 */ { MAD_F(0x071a0e1e) /* 0.443861120 */, 17 }, /* 3747 */ { MAD_F(0x071ab3c9) /* 0.444019113 */, 17 }, /* 3748 */ { MAD_F(0x071b5977) /* 0.444177119 */, 17 }, /* 3749 */ { MAD_F(0x071bff2a) /* 0.444335140 */, 17 }, /* 3750 */ { MAD_F(0x071ca4e0) /* 0.444493175 */, 17 }, /* 3751 */ { MAD_F(0x071d4a9a) /* 0.444651224 */, 17 }, /* 3752 */ { MAD_F(0x071df058) /* 0.444809288 */, 17 }, /* 3753 */ { MAD_F(0x071e9619) /* 0.444967365 */, 17 }, /* 3754 */ { MAD_F(0x071f3bde) /* 0.445125456 */, 17 }, /* 3755 */ { MAD_F(0x071fe1a8) /* 0.445283561 */, 17 }, /* 3756 */ { MAD_F(0x07208774) /* 0.445441680 */, 17 }, /* 3757 */ { MAD_F(0x07212d45) /* 0.445599814 */, 17 }, /* 3758 */ { MAD_F(0x0721d319) /* 0.445757961 */, 17 }, /* 3759 */ { MAD_F(0x072278f1) /* 0.445916122 */, 17 }, /* 3760 */ { MAD_F(0x07231ecd) /* 0.446074298 */, 17 }, /* 3761 */ { MAD_F(0x0723c4ad) /* 0.446232487 */, 17 }, /* 3762 */ { MAD_F(0x07246a90) /* 0.446390690 */, 17 }, /* 3763 */ { MAD_F(0x07251077) /* 0.446548908 */, 17 }, /* 3764 */ { MAD_F(0x0725b662) /* 0.446707139 */, 17 }, /* 3765 */ { MAD_F(0x07265c51) /* 0.446865385 */, 17 }, /* 3766 */ { MAD_F(0x07270244) /* 0.447023644 */, 17 }, /* 3767 */ { MAD_F(0x0727a83a) /* 0.447181918 */, 17 }, /* 3768 */ { MAD_F(0x07284e34) /* 0.447340205 */, 17 }, /* 3769 */ { MAD_F(0x0728f431) /* 0.447498507 */, 17 }, /* 3770 */ { MAD_F(0x07299a33) /* 0.447656822 */, 17 }, /* 3771 */ { MAD_F(0x072a4038) /* 0.447815152 */, 17 }, /* 3772 */ { MAD_F(0x072ae641) /* 0.447973495 */, 17 }, /* 3773 */ { MAD_F(0x072b8c4e) /* 0.448131853 */, 17 }, /* 3774 */ { MAD_F(0x072c325e) /* 0.448290224 */, 17 }, /* 3775 */ { MAD_F(0x072cd873) /* 0.448448609 */, 17 }, /* 3776 */ { MAD_F(0x072d7e8b) /* 0.448607009 */, 17 }, /* 3777 */ { MAD_F(0x072e24a7) /* 0.448765422 */, 17 }, /* 3778 */ { MAD_F(0x072ecac6) /* 0.448923850 */, 17 }, /* 3779 */ { MAD_F(0x072f70e9) /* 0.449082291 */, 17 }, /* 3780 */ { MAD_F(0x07301710) /* 0.449240746 */, 17 }, /* 3781 */ { MAD_F(0x0730bd3b) /* 0.449399216 */, 17 }, /* 3782 */ { MAD_F(0x0731636a) /* 0.449557699 */, 17 }, /* 3783 */ { MAD_F(0x0732099c) /* 0.449716196 */, 17 }, /* 3784 */ { MAD_F(0x0732afd2) /* 0.449874708 */, 17 }, /* 3785 */ { MAD_F(0x0733560c) /* 0.450033233 */, 17 }, /* 3786 */ { MAD_F(0x0733fc49) /* 0.450191772 */, 17 }, /* 3787 */ { MAD_F(0x0734a28b) /* 0.450350325 */, 17 }, /* 3788 */ { MAD_F(0x073548d0) /* 0.450508892 */, 17 }, /* 3789 */ { MAD_F(0x0735ef18) /* 0.450667473 */, 17 }, /* 3790 */ { MAD_F(0x07369565) /* 0.450826068 */, 17 }, /* 3791 */ { MAD_F(0x07373bb5) /* 0.450984677 */, 17 }, /* 3792 */ { MAD_F(0x0737e209) /* 0.451143300 */, 17 }, /* 3793 */ { MAD_F(0x07388861) /* 0.451301937 */, 17 }, /* 3794 */ { MAD_F(0x07392ebc) /* 0.451460588 */, 17 }, /* 3795 */ { MAD_F(0x0739d51c) /* 0.451619252 */, 17 }, /* 3796 */ { MAD_F(0x073a7b7f) /* 0.451777931 */, 17 }, /* 3797 */ { MAD_F(0x073b21e5) /* 0.451936623 */, 17 }, /* 3798 */ { MAD_F(0x073bc850) /* 0.452095330 */, 17 }, /* 3799 */ { MAD_F(0x073c6ebe) /* 0.452254050 */, 17 }, /* 3800 */ { MAD_F(0x073d1530) /* 0.452412785 */, 17 }, /* 3801 */ { MAD_F(0x073dbba6) /* 0.452571533 */, 17 }, /* 3802 */ { MAD_F(0x073e621f) /* 0.452730295 */, 17 }, /* 3803 */ { MAD_F(0x073f089c) /* 0.452889071 */, 17 }, /* 3804 */ { MAD_F(0x073faf1d) /* 0.453047861 */, 17 }, /* 3805 */ { MAD_F(0x074055a2) /* 0.453206665 */, 17 }, /* 3806 */ { MAD_F(0x0740fc2a) /* 0.453365483 */, 17 }, /* 3807 */ { MAD_F(0x0741a2b6) /* 0.453524315 */, 17 }, /* 3808 */ { MAD_F(0x07424946) /* 0.453683161 */, 17 }, /* 3809 */ { MAD_F(0x0742efd9) /* 0.453842020 */, 17 }, /* 3810 */ { MAD_F(0x07439671) /* 0.454000894 */, 17 }, /* 3811 */ { MAD_F(0x07443d0c) /* 0.454159781 */, 17 }, /* 3812 */ { MAD_F(0x0744e3aa) /* 0.454318683 */, 17 }, /* 3813 */ { MAD_F(0x07458a4d) /* 0.454477598 */, 17 }, /* 3814 */ { MAD_F(0x074630f3) /* 0.454636527 */, 17 }, /* 3815 */ { MAD_F(0x0746d79d) /* 0.454795470 */, 17 }, /* 3816 */ { MAD_F(0x07477e4b) /* 0.454954427 */, 17 }, /* 3817 */ { MAD_F(0x074824fc) /* 0.455113397 */, 17 }, /* 3818 */ { MAD_F(0x0748cbb1) /* 0.455272382 */, 17 }, /* 3819 */ { MAD_F(0x0749726a) /* 0.455431381 */, 17 }, /* 3820 */ { MAD_F(0x074a1927) /* 0.455590393 */, 17 }, /* 3821 */ { MAD_F(0x074abfe7) /* 0.455749419 */, 17 }, /* 3822 */ { MAD_F(0x074b66ab) /* 0.455908459 */, 17 }, /* 3823 */ { MAD_F(0x074c0d73) /* 0.456067513 */, 17 }, /* 3824 */ { MAD_F(0x074cb43e) /* 0.456226581 */, 17 }, /* 3825 */ { MAD_F(0x074d5b0d) /* 0.456385663 */, 17 }, /* 3826 */ { MAD_F(0x074e01e0) /* 0.456544759 */, 17 }, /* 3827 */ { MAD_F(0x074ea8b7) /* 0.456703868 */, 17 }, /* 3828 */ { MAD_F(0x074f4f91) /* 0.456862992 */, 17 }, /* 3829 */ { MAD_F(0x074ff66f) /* 0.457022129 */, 17 }, /* 3830 */ { MAD_F(0x07509d51) /* 0.457181280 */, 17 }, /* 3831 */ { MAD_F(0x07514437) /* 0.457340445 */, 17 }, /* 3832 */ { MAD_F(0x0751eb20) /* 0.457499623 */, 17 }, /* 3833 */ { MAD_F(0x0752920d) /* 0.457658816 */, 17 }, /* 3834 */ { MAD_F(0x075338fd) /* 0.457818022 */, 17 }, /* 3835 */ { MAD_F(0x0753dff2) /* 0.457977243 */, 17 }, /* 3836 */ { MAD_F(0x075486ea) /* 0.458136477 */, 17 }, /* 3837 */ { MAD_F(0x07552de6) /* 0.458295725 */, 17 }, /* 3838 */ { MAD_F(0x0755d4e5) /* 0.458454987 */, 17 }, /* 3839 */ { MAD_F(0x07567be8) /* 0.458614262 */, 17 }, /* 3840 */ { MAD_F(0x075722ef) /* 0.458773552 */, 17 }, /* 3841 */ { MAD_F(0x0757c9fa) /* 0.458932855 */, 17 }, /* 3842 */ { MAD_F(0x07587108) /* 0.459092172 */, 17 }, /* 3843 */ { MAD_F(0x0759181a) /* 0.459251503 */, 17 }, /* 3844 */ { MAD_F(0x0759bf30) /* 0.459410848 */, 17 }, /* 3845 */ { MAD_F(0x075a664a) /* 0.459570206 */, 17 }, /* 3846 */ { MAD_F(0x075b0d67) /* 0.459729579 */, 17 }, /* 3847 */ { MAD_F(0x075bb488) /* 0.459888965 */, 17 }, /* 3848 */ { MAD_F(0x075c5bac) /* 0.460048365 */, 17 }, /* 3849 */ { MAD_F(0x075d02d5) /* 0.460207779 */, 17 }, /* 3850 */ { MAD_F(0x075daa01) /* 0.460367206 */, 17 }, /* 3851 */ { MAD_F(0x075e5130) /* 0.460526648 */, 17 }, /* 3852 */ { MAD_F(0x075ef864) /* 0.460686103 */, 17 }, /* 3853 */ { MAD_F(0x075f9f9b) /* 0.460845572 */, 17 }, /* 3854 */ { MAD_F(0x076046d6) /* 0.461005055 */, 17 }, /* 3855 */ { MAD_F(0x0760ee14) /* 0.461164552 */, 17 }, /* 3856 */ { MAD_F(0x07619557) /* 0.461324062 */, 17 }, /* 3857 */ { MAD_F(0x07623c9d) /* 0.461483586 */, 17 }, /* 3858 */ { MAD_F(0x0762e3e6) /* 0.461643124 */, 17 }, /* 3859 */ { MAD_F(0x07638b34) /* 0.461802676 */, 17 }, /* 3860 */ { MAD_F(0x07643285) /* 0.461962242 */, 17 }, /* 3861 */ { MAD_F(0x0764d9d9) /* 0.462121821 */, 17 }, /* 3862 */ { MAD_F(0x07658132) /* 0.462281414 */, 17 }, /* 3863 */ { MAD_F(0x0766288e) /* 0.462441021 */, 17 }, /* 3864 */ { MAD_F(0x0766cfee) /* 0.462600642 */, 17 }, /* 3865 */ { MAD_F(0x07677751) /* 0.462760276 */, 17 }, /* 3866 */ { MAD_F(0x07681eb9) /* 0.462919924 */, 17 }, /* 3867 */ { MAD_F(0x0768c624) /* 0.463079586 */, 17 }, /* 3868 */ { MAD_F(0x07696d92) /* 0.463239262 */, 17 }, /* 3869 */ { MAD_F(0x076a1505) /* 0.463398951 */, 17 }, /* 3870 */ { MAD_F(0x076abc7b) /* 0.463558655 */, 17 }, /* 3871 */ { MAD_F(0x076b63f4) /* 0.463718372 */, 17 }, /* 3872 */ { MAD_F(0x076c0b72) /* 0.463878102 */, 17 }, /* 3873 */ { MAD_F(0x076cb2f3) /* 0.464037847 */, 17 }, /* 3874 */ { MAD_F(0x076d5a78) /* 0.464197605 */, 17 }, /* 3875 */ { MAD_F(0x076e0200) /* 0.464357377 */, 17 }, /* 3876 */ { MAD_F(0x076ea98c) /* 0.464517163 */, 17 }, /* 3877 */ { MAD_F(0x076f511c) /* 0.464676962 */, 17 }, /* 3878 */ { MAD_F(0x076ff8b0) /* 0.464836776 */, 17 }, /* 3879 */ { MAD_F(0x0770a047) /* 0.464996603 */, 17 }, /* 3880 */ { MAD_F(0x077147e2) /* 0.465156443 */, 17 }, /* 3881 */ { MAD_F(0x0771ef80) /* 0.465316298 */, 17 }, /* 3882 */ { MAD_F(0x07729723) /* 0.465476166 */, 17 }, /* 3883 */ { MAD_F(0x07733ec9) /* 0.465636048 */, 17 }, /* 3884 */ { MAD_F(0x0773e672) /* 0.465795943 */, 17 }, /* 3885 */ { MAD_F(0x07748e20) /* 0.465955853 */, 17 }, /* 3886 */ { MAD_F(0x077535d1) /* 0.466115776 */, 17 }, /* 3887 */ { MAD_F(0x0775dd85) /* 0.466275713 */, 17 }, /* 3888 */ { MAD_F(0x0776853e) /* 0.466435663 */, 17 }, /* 3889 */ { MAD_F(0x07772cfa) /* 0.466595627 */, 17 }, /* 3890 */ { MAD_F(0x0777d4ba) /* 0.466755605 */, 17 }, /* 3891 */ { MAD_F(0x07787c7d) /* 0.466915597 */, 17 }, /* 3892 */ { MAD_F(0x07792444) /* 0.467075602 */, 17 }, /* 3893 */ { MAD_F(0x0779cc0f) /* 0.467235621 */, 17 }, /* 3894 */ { MAD_F(0x077a73dd) /* 0.467395654 */, 17 }, /* 3895 */ { MAD_F(0x077b1baf) /* 0.467555701 */, 17 }, /* 3896 */ { MAD_F(0x077bc385) /* 0.467715761 */, 17 }, /* 3897 */ { MAD_F(0x077c6b5f) /* 0.467875835 */, 17 }, /* 3898 */ { MAD_F(0x077d133c) /* 0.468035922 */, 17 }, /* 3899 */ { MAD_F(0x077dbb1d) /* 0.468196023 */, 17 }, /* 3900 */ { MAD_F(0x077e6301) /* 0.468356138 */, 17 }, /* 3901 */ { MAD_F(0x077f0ae9) /* 0.468516267 */, 17 }, /* 3902 */ { MAD_F(0x077fb2d5) /* 0.468676409 */, 17 }, /* 3903 */ { MAD_F(0x07805ac5) /* 0.468836565 */, 17 }, /* 3904 */ { MAD_F(0x078102b8) /* 0.468996735 */, 17 }, /* 3905 */ { MAD_F(0x0781aaaf) /* 0.469156918 */, 17 }, /* 3906 */ { MAD_F(0x078252aa) /* 0.469317115 */, 17 }, /* 3907 */ { MAD_F(0x0782faa8) /* 0.469477326 */, 17 }, /* 3908 */ { MAD_F(0x0783a2aa) /* 0.469637550 */, 17 }, /* 3909 */ { MAD_F(0x07844aaf) /* 0.469797788 */, 17 }, /* 3910 */ { MAD_F(0x0784f2b8) /* 0.469958040 */, 17 }, /* 3911 */ { MAD_F(0x07859ac5) /* 0.470118305 */, 17 }, /* 3912 */ { MAD_F(0x078642d6) /* 0.470278584 */, 17 }, /* 3913 */ { MAD_F(0x0786eaea) /* 0.470438877 */, 17 }, /* 3914 */ { MAD_F(0x07879302) /* 0.470599183 */, 17 }, /* 3915 */ { MAD_F(0x07883b1e) /* 0.470759503 */, 17 }, /* 3916 */ { MAD_F(0x0788e33d) /* 0.470919836 */, 17 }, /* 3917 */ { MAD_F(0x07898b60) /* 0.471080184 */, 17 }, /* 3918 */ { MAD_F(0x078a3386) /* 0.471240545 */, 17 }, /* 3919 */ { MAD_F(0x078adbb0) /* 0.471400919 */, 17 }, /* 3920 */ { MAD_F(0x078b83de) /* 0.471561307 */, 17 }, /* 3921 */ { MAD_F(0x078c2c10) /* 0.471721709 */, 17 }, /* 3922 */ { MAD_F(0x078cd445) /* 0.471882125 */, 17 }, /* 3923 */ { MAD_F(0x078d7c7e) /* 0.472042554 */, 17 }, /* 3924 */ { MAD_F(0x078e24ba) /* 0.472202996 */, 17 }, /* 3925 */ { MAD_F(0x078eccfb) /* 0.472363453 */, 17 }, /* 3926 */ { MAD_F(0x078f753e) /* 0.472523923 */, 17 }, /* 3927 */ { MAD_F(0x07901d86) /* 0.472684406 */, 17 }, /* 3928 */ { MAD_F(0x0790c5d1) /* 0.472844904 */, 17 }, /* 3929 */ { MAD_F(0x07916e20) /* 0.473005414 */, 17 }, /* 3930 */ { MAD_F(0x07921672) /* 0.473165939 */, 17 }, /* 3931 */ { MAD_F(0x0792bec8) /* 0.473326477 */, 17 }, /* 3932 */ { MAD_F(0x07936722) /* 0.473487029 */, 17 }, /* 3933 */ { MAD_F(0x07940f80) /* 0.473647594 */, 17 }, /* 3934 */ { MAD_F(0x0794b7e1) /* 0.473808173 */, 17 }, /* 3935 */ { MAD_F(0x07956045) /* 0.473968765 */, 17 }, /* 3936 */ { MAD_F(0x079608ae) /* 0.474129372 */, 17 }, /* 3937 */ { MAD_F(0x0796b11a) /* 0.474289991 */, 17 }, /* 3938 */ { MAD_F(0x0797598a) /* 0.474450625 */, 17 }, /* 3939 */ { MAD_F(0x079801fd) /* 0.474611272 */, 17 }, /* 3940 */ { MAD_F(0x0798aa74) /* 0.474771932 */, 17 }, /* 3941 */ { MAD_F(0x079952ee) /* 0.474932606 */, 17 }, /* 3942 */ { MAD_F(0x0799fb6d) /* 0.475093294 */, 17 }, /* 3943 */ { MAD_F(0x079aa3ef) /* 0.475253995 */, 17 }, /* 3944 */ { MAD_F(0x079b4c74) /* 0.475414710 */, 17 }, /* 3945 */ { MAD_F(0x079bf4fd) /* 0.475575439 */, 17 }, /* 3946 */ { MAD_F(0x079c9d8a) /* 0.475736181 */, 17 }, /* 3947 */ { MAD_F(0x079d461b) /* 0.475896936 */, 17 }, /* 3948 */ { MAD_F(0x079deeaf) /* 0.476057705 */, 17 }, /* 3949 */ { MAD_F(0x079e9747) /* 0.476218488 */, 17 }, /* 3950 */ { MAD_F(0x079f3fe2) /* 0.476379285 */, 17 }, /* 3951 */ { MAD_F(0x079fe881) /* 0.476540095 */, 17 }, /* 3952 */ { MAD_F(0x07a09124) /* 0.476700918 */, 17 }, /* 3953 */ { MAD_F(0x07a139ca) /* 0.476861755 */, 17 }, /* 3954 */ { MAD_F(0x07a1e274) /* 0.477022606 */, 17 }, /* 3955 */ { MAD_F(0x07a28b22) /* 0.477183470 */, 17 }, /* 3956 */ { MAD_F(0x07a333d3) /* 0.477344348 */, 17 }, /* 3957 */ { MAD_F(0x07a3dc88) /* 0.477505239 */, 17 }, /* 3958 */ { MAD_F(0x07a48541) /* 0.477666144 */, 17 }, /* 3959 */ { MAD_F(0x07a52dfd) /* 0.477827062 */, 17 }, /* 3960 */ { MAD_F(0x07a5d6bd) /* 0.477987994 */, 17 }, /* 3961 */ { MAD_F(0x07a67f80) /* 0.478148940 */, 17 }, /* 3962 */ { MAD_F(0x07a72847) /* 0.478309899 */, 17 }, /* 3963 */ { MAD_F(0x07a7d112) /* 0.478470871 */, 17 }, /* 3964 */ { MAD_F(0x07a879e1) /* 0.478631857 */, 17 }, /* 3965 */ { MAD_F(0x07a922b3) /* 0.478792857 */, 17 }, /* 3966 */ { MAD_F(0x07a9cb88) /* 0.478953870 */, 17 }, /* 3967 */ { MAD_F(0x07aa7462) /* 0.479114897 */, 17 }, /* 3968 */ { MAD_F(0x07ab1d3e) /* 0.479275937 */, 17 }, /* 3969 */ { MAD_F(0x07abc61f) /* 0.479436991 */, 17 }, /* 3970 */ { MAD_F(0x07ac6f03) /* 0.479598058 */, 17 }, /* 3971 */ { MAD_F(0x07ad17eb) /* 0.479759139 */, 17 }, /* 3972 */ { MAD_F(0x07adc0d6) /* 0.479920233 */, 17 }, /* 3973 */ { MAD_F(0x07ae69c6) /* 0.480081341 */, 17 }, /* 3974 */ { MAD_F(0x07af12b8) /* 0.480242463 */, 17 }, /* 3975 */ { MAD_F(0x07afbbaf) /* 0.480403598 */, 17 }, /* 3976 */ { MAD_F(0x07b064a8) /* 0.480564746 */, 17 }, /* 3977 */ { MAD_F(0x07b10da6) /* 0.480725908 */, 17 }, /* 3978 */ { MAD_F(0x07b1b6a7) /* 0.480887083 */, 17 }, /* 3979 */ { MAD_F(0x07b25fac) /* 0.481048272 */, 17 }, /* 3980 */ { MAD_F(0x07b308b5) /* 0.481209475 */, 17 }, /* 3981 */ { MAD_F(0x07b3b1c1) /* 0.481370691 */, 17 }, /* 3982 */ { MAD_F(0x07b45ad0) /* 0.481531920 */, 17 }, /* 3983 */ { MAD_F(0x07b503e4) /* 0.481693163 */, 17 }, /* 3984 */ { MAD_F(0x07b5acfb) /* 0.481854420 */, 17 }, /* 3985 */ { MAD_F(0x07b65615) /* 0.482015690 */, 17 }, /* 3986 */ { MAD_F(0x07b6ff33) /* 0.482176973 */, 17 }, /* 3987 */ { MAD_F(0x07b7a855) /* 0.482338270 */, 17 }, /* 3988 */ { MAD_F(0x07b8517b) /* 0.482499580 */, 17 }, /* 3989 */ { MAD_F(0x07b8faa4) /* 0.482660904 */, 17 }, /* 3990 */ { MAD_F(0x07b9a3d0) /* 0.482822242 */, 17 }, /* 3991 */ { MAD_F(0x07ba4d01) /* 0.482983592 */, 17 }, /* 3992 */ { MAD_F(0x07baf635) /* 0.483144957 */, 17 }, /* 3993 */ { MAD_F(0x07bb9f6c) /* 0.483306335 */, 17 }, /* 3994 */ { MAD_F(0x07bc48a7) /* 0.483467726 */, 17 }, /* 3995 */ { MAD_F(0x07bcf1e6) /* 0.483629131 */, 17 }, /* 3996 */ { MAD_F(0x07bd9b28) /* 0.483790549 */, 17 }, /* 3997 */ { MAD_F(0x07be446e) /* 0.483951980 */, 17 }, /* 3998 */ { MAD_F(0x07beedb8) /* 0.484113426 */, 17 }, /* 3999 */ { MAD_F(0x07bf9705) /* 0.484274884 */, 17 }, /* 4000 */ { MAD_F(0x07c04056) /* 0.484436356 */, 17 }, /* 4001 */ { MAD_F(0x07c0e9aa) /* 0.484597842 */, 17 }, /* 4002 */ { MAD_F(0x07c19302) /* 0.484759341 */, 17 }, /* 4003 */ { MAD_F(0x07c23c5e) /* 0.484920853 */, 17 }, /* 4004 */ { MAD_F(0x07c2e5bd) /* 0.485082379 */, 17 }, /* 4005 */ { MAD_F(0x07c38f20) /* 0.485243918 */, 17 }, /* 4006 */ { MAD_F(0x07c43887) /* 0.485405471 */, 17 }, /* 4007 */ { MAD_F(0x07c4e1f1) /* 0.485567037 */, 17 }, /* 4008 */ { MAD_F(0x07c58b5f) /* 0.485728617 */, 17 }, /* 4009 */ { MAD_F(0x07c634d0) /* 0.485890210 */, 17 }, /* 4010 */ { MAD_F(0x07c6de45) /* 0.486051817 */, 17 }, /* 4011 */ { MAD_F(0x07c787bd) /* 0.486213436 */, 17 }, /* 4012 */ { MAD_F(0x07c83139) /* 0.486375070 */, 17 }, /* 4013 */ { MAD_F(0x07c8dab9) /* 0.486536717 */, 17 }, /* 4014 */ { MAD_F(0x07c9843c) /* 0.486698377 */, 17 }, /* 4015 */ { MAD_F(0x07ca2dc3) /* 0.486860051 */, 17 }, /* 4016 */ { MAD_F(0x07cad74e) /* 0.487021738 */, 17 }, /* 4017 */ { MAD_F(0x07cb80dc) /* 0.487183438 */, 17 }, /* 4018 */ { MAD_F(0x07cc2a6e) /* 0.487345152 */, 17 }, /* 4019 */ { MAD_F(0x07ccd403) /* 0.487506879 */, 17 }, /* 4020 */ { MAD_F(0x07cd7d9c) /* 0.487668620 */, 17 }, /* 4021 */ { MAD_F(0x07ce2739) /* 0.487830374 */, 17 }, /* 4022 */ { MAD_F(0x07ced0d9) /* 0.487992142 */, 17 }, /* 4023 */ { MAD_F(0x07cf7a7d) /* 0.488153923 */, 17 }, /* 4024 */ { MAD_F(0x07d02424) /* 0.488315717 */, 17 }, /* 4025 */ { MAD_F(0x07d0cdcf) /* 0.488477525 */, 17 }, /* 4026 */ { MAD_F(0x07d1777e) /* 0.488639346 */, 17 }, /* 4027 */ { MAD_F(0x07d22130) /* 0.488801181 */, 17 }, /* 4028 */ { MAD_F(0x07d2cae5) /* 0.488963029 */, 17 }, /* 4029 */ { MAD_F(0x07d3749f) /* 0.489124890 */, 17 }, /* 4030 */ { MAD_F(0x07d41e5c) /* 0.489286765 */, 17 }, /* 4031 */ { MAD_F(0x07d4c81c) /* 0.489448653 */, 17 }, /* 4032 */ { MAD_F(0x07d571e0) /* 0.489610555 */, 17 }, /* 4033 */ { MAD_F(0x07d61ba8) /* 0.489772470 */, 17 }, /* 4034 */ { MAD_F(0x07d6c573) /* 0.489934398 */, 17 }, /* 4035 */ { MAD_F(0x07d76f42) /* 0.490096340 */, 17 }, /* 4036 */ { MAD_F(0x07d81915) /* 0.490258295 */, 17 }, /* 4037 */ { MAD_F(0x07d8c2eb) /* 0.490420263 */, 17 }, /* 4038 */ { MAD_F(0x07d96cc4) /* 0.490582245 */, 17 }, /* 4039 */ { MAD_F(0x07da16a2) /* 0.490744240 */, 17 }, /* 4040 */ { MAD_F(0x07dac083) /* 0.490906249 */, 17 }, /* 4041 */ { MAD_F(0x07db6a67) /* 0.491068271 */, 17 }, /* 4042 */ { MAD_F(0x07dc144f) /* 0.491230306 */, 17 }, /* 4043 */ { MAD_F(0x07dcbe3b) /* 0.491392355 */, 17 }, /* 4044 */ { MAD_F(0x07dd682a) /* 0.491554417 */, 17 }, /* 4045 */ { MAD_F(0x07de121d) /* 0.491716492 */, 17 }, /* 4046 */ { MAD_F(0x07debc13) /* 0.491878581 */, 17 }, /* 4047 */ { MAD_F(0x07df660d) /* 0.492040683 */, 17 }, /* 4048 */ { MAD_F(0x07e0100a) /* 0.492202799 */, 17 }, /* 4049 */ { MAD_F(0x07e0ba0c) /* 0.492364928 */, 17 }, /* 4050 */ { MAD_F(0x07e16410) /* 0.492527070 */, 17 }, /* 4051 */ { MAD_F(0x07e20e19) /* 0.492689225 */, 17 }, /* 4052 */ { MAD_F(0x07e2b824) /* 0.492851394 */, 17 }, /* 4053 */ { MAD_F(0x07e36234) /* 0.493013576 */, 17 }, /* 4054 */ { MAD_F(0x07e40c47) /* 0.493175772 */, 17 }, /* 4055 */ { MAD_F(0x07e4b65e) /* 0.493337981 */, 17 }, /* 4056 */ { MAD_F(0x07e56078) /* 0.493500203 */, 17 }, /* 4057 */ { MAD_F(0x07e60a95) /* 0.493662438 */, 17 }, /* 4058 */ { MAD_F(0x07e6b4b7) /* 0.493824687 */, 17 }, /* 4059 */ { MAD_F(0x07e75edc) /* 0.493986949 */, 17 }, /* 4060 */ { MAD_F(0x07e80904) /* 0.494149225 */, 17 }, /* 4061 */ { MAD_F(0x07e8b330) /* 0.494311514 */, 17 }, /* 4062 */ { MAD_F(0x07e95d60) /* 0.494473816 */, 17 }, /* 4063 */ { MAD_F(0x07ea0793) /* 0.494636131 */, 17 }, /* 4064 */ { MAD_F(0x07eab1ca) /* 0.494798460 */, 17 }, /* 4065 */ { MAD_F(0x07eb5c04) /* 0.494960802 */, 17 }, /* 4066 */ { MAD_F(0x07ec0642) /* 0.495123158 */, 17 }, /* 4067 */ { MAD_F(0x07ecb084) /* 0.495285526 */, 17 }, /* 4068 */ { MAD_F(0x07ed5ac9) /* 0.495447908 */, 17 }, /* 4069 */ { MAD_F(0x07ee0512) /* 0.495610304 */, 17 }, /* 4070 */ { MAD_F(0x07eeaf5e) /* 0.495772712 */, 17 }, /* 4071 */ { MAD_F(0x07ef59ae) /* 0.495935134 */, 17 }, /* 4072 */ { MAD_F(0x07f00401) /* 0.496097570 */, 17 }, /* 4073 */ { MAD_F(0x07f0ae58) /* 0.496260018 */, 17 }, /* 4074 */ { MAD_F(0x07f158b3) /* 0.496422480 */, 17 }, /* 4075 */ { MAD_F(0x07f20311) /* 0.496584955 */, 17 }, /* 4076 */ { MAD_F(0x07f2ad72) /* 0.496747444 */, 17 }, /* 4077 */ { MAD_F(0x07f357d8) /* 0.496909945 */, 17 }, /* 4078 */ { MAD_F(0x07f40240) /* 0.497072460 */, 17 }, /* 4079 */ { MAD_F(0x07f4acad) /* 0.497234989 */, 17 }, /* 4080 */ { MAD_F(0x07f5571d) /* 0.497397530 */, 17 }, /* 4081 */ { MAD_F(0x07f60190) /* 0.497560085 */, 17 }, /* 4082 */ { MAD_F(0x07f6ac07) /* 0.497722653 */, 17 }, /* 4083 */ { MAD_F(0x07f75682) /* 0.497885235 */, 17 }, /* 4084 */ { MAD_F(0x07f80100) /* 0.498047829 */, 17 }, /* 4085 */ { MAD_F(0x07f8ab82) /* 0.498210437 */, 17 }, /* 4086 */ { MAD_F(0x07f95607) /* 0.498373058 */, 17 }, /* 4087 */ { MAD_F(0x07fa0090) /* 0.498535693 */, 17 }, /* 4088 */ { MAD_F(0x07faab1c) /* 0.498698341 */, 17 }, /* 4089 */ { MAD_F(0x07fb55ac) /* 0.498861002 */, 17 }, /* 4090 */ { MAD_F(0x07fc0040) /* 0.499023676 */, 17 }, /* 4091 */ { MAD_F(0x07fcaad7) /* 0.499186364 */, 17 }, /* 4092 */ { MAD_F(0x07fd5572) /* 0.499349064 */, 17 }, /* 4093 */ { MAD_F(0x07fe0010) /* 0.499511778 */, 17 }, /* 4094 */ { MAD_F(0x07feaab2) /* 0.499674506 */, 17 }, /* 4095 */ { MAD_F(0x07ff5557) /* 0.499837246 */, 17 }, /* 4096 */ { MAD_F(0x04000000) /* 0.250000000 */, 18 }, /* 4097 */ { MAD_F(0x04005556) /* 0.250081384 */, 18 }, /* 4098 */ { MAD_F(0x0400aaae) /* 0.250162774 */, 18 }, /* 4099 */ { MAD_F(0x04010008) /* 0.250244170 */, 18 }, /* 4100 */ { MAD_F(0x04015563) /* 0.250325574 */, 18 }, /* 4101 */ { MAD_F(0x0401aac1) /* 0.250406984 */, 18 }, /* 4102 */ { MAD_F(0x04020020) /* 0.250488400 */, 18 }, /* 4103 */ { MAD_F(0x04025581) /* 0.250569824 */, 18 }, /* 4104 */ { MAD_F(0x0402aae3) /* 0.250651254 */, 18 }, /* 4105 */ { MAD_F(0x04030048) /* 0.250732690 */, 18 }, /* 4106 */ { MAD_F(0x040355ae) /* 0.250814133 */, 18 }, /* 4107 */ { MAD_F(0x0403ab16) /* 0.250895583 */, 18 }, /* 4108 */ { MAD_F(0x04040080) /* 0.250977039 */, 18 }, /* 4109 */ { MAD_F(0x040455eb) /* 0.251058502 */, 18 }, /* 4110 */ { MAD_F(0x0404ab59) /* 0.251139971 */, 18 }, /* 4111 */ { MAD_F(0x040500c8) /* 0.251221448 */, 18 }, /* 4112 */ { MAD_F(0x04055638) /* 0.251302930 */, 18 }, /* 4113 */ { MAD_F(0x0405abab) /* 0.251384420 */, 18 }, /* 4114 */ { MAD_F(0x0406011f) /* 0.251465916 */, 18 }, /* 4115 */ { MAD_F(0x04065696) /* 0.251547418 */, 18 }, /* 4116 */ { MAD_F(0x0406ac0e) /* 0.251628927 */, 18 }, /* 4117 */ { MAD_F(0x04070187) /* 0.251710443 */, 18 }, /* 4118 */ { MAD_F(0x04075703) /* 0.251791965 */, 18 }, /* 4119 */ { MAD_F(0x0407ac80) /* 0.251873494 */, 18 }, /* 4120 */ { MAD_F(0x040801ff) /* 0.251955030 */, 18 }, /* 4121 */ { MAD_F(0x04085780) /* 0.252036572 */, 18 }, /* 4122 */ { MAD_F(0x0408ad02) /* 0.252118121 */, 18 }, /* 4123 */ { MAD_F(0x04090287) /* 0.252199676 */, 18 }, /* 4124 */ { MAD_F(0x0409580d) /* 0.252281238 */, 18 }, /* 4125 */ { MAD_F(0x0409ad95) /* 0.252362807 */, 18 }, /* 4126 */ { MAD_F(0x040a031e) /* 0.252444382 */, 18 }, /* 4127 */ { MAD_F(0x040a58aa) /* 0.252525963 */, 18 }, /* 4128 */ { MAD_F(0x040aae37) /* 0.252607552 */, 18 }, /* 4129 */ { MAD_F(0x040b03c6) /* 0.252689147 */, 18 }, /* 4130 */ { MAD_F(0x040b5957) /* 0.252770748 */, 18 }, /* 4131 */ { MAD_F(0x040baee9) /* 0.252852356 */, 18 }, /* 4132 */ { MAD_F(0x040c047e) /* 0.252933971 */, 18 }, /* 4133 */ { MAD_F(0x040c5a14) /* 0.253015592 */, 18 }, /* 4134 */ { MAD_F(0x040cafab) /* 0.253097220 */, 18 }, /* 4135 */ { MAD_F(0x040d0545) /* 0.253178854 */, 18 }, /* 4136 */ { MAD_F(0x040d5ae0) /* 0.253260495 */, 18 }, /* 4137 */ { MAD_F(0x040db07d) /* 0.253342143 */, 18 }, /* 4138 */ { MAD_F(0x040e061c) /* 0.253423797 */, 18 }, /* 4139 */ { MAD_F(0x040e5bbd) /* 0.253505457 */, 18 }, /* 4140 */ { MAD_F(0x040eb15f) /* 0.253587125 */, 18 }, /* 4141 */ { MAD_F(0x040f0703) /* 0.253668799 */, 18 }, /* 4142 */ { MAD_F(0x040f5ca9) /* 0.253750479 */, 18 }, /* 4143 */ { MAD_F(0x040fb251) /* 0.253832166 */, 18 }, /* 4144 */ { MAD_F(0x041007fa) /* 0.253913860 */, 18 }, /* 4145 */ { MAD_F(0x04105da6) /* 0.253995560 */, 18 }, /* 4146 */ { MAD_F(0x0410b353) /* 0.254077266 */, 18 }, /* 4147 */ { MAD_F(0x04110901) /* 0.254158980 */, 18 }, /* 4148 */ { MAD_F(0x04115eb2) /* 0.254240700 */, 18 }, /* 4149 */ { MAD_F(0x0411b464) /* 0.254322426 */, 18 }, /* 4150 */ { MAD_F(0x04120a18) /* 0.254404159 */, 18 }, /* 4151 */ { MAD_F(0x04125fce) /* 0.254485899 */, 18 }, /* 4152 */ { MAD_F(0x0412b586) /* 0.254567645 */, 18 }, /* 4153 */ { MAD_F(0x04130b3f) /* 0.254649397 */, 18 }, /* 4154 */ { MAD_F(0x041360fa) /* 0.254731157 */, 18 }, /* 4155 */ { MAD_F(0x0413b6b7) /* 0.254812922 */, 18 }, /* 4156 */ { MAD_F(0x04140c75) /* 0.254894695 */, 18 }, /* 4157 */ { MAD_F(0x04146236) /* 0.254976474 */, 18 }, /* 4158 */ { MAD_F(0x0414b7f8) /* 0.255058259 */, 18 }, /* 4159 */ { MAD_F(0x04150dbc) /* 0.255140051 */, 18 }, /* 4160 */ { MAD_F(0x04156381) /* 0.255221850 */, 18 }, /* 4161 */ { MAD_F(0x0415b949) /* 0.255303655 */, 18 }, /* 4162 */ { MAD_F(0x04160f12) /* 0.255385467 */, 18 }, /* 4163 */ { MAD_F(0x041664dd) /* 0.255467285 */, 18 }, /* 4164 */ { MAD_F(0x0416baaa) /* 0.255549110 */, 18 }, /* 4165 */ { MAD_F(0x04171078) /* 0.255630941 */, 18 }, /* 4166 */ { MAD_F(0x04176648) /* 0.255712779 */, 18 }, /* 4167 */ { MAD_F(0x0417bc1a) /* 0.255794624 */, 18 }, /* 4168 */ { MAD_F(0x041811ee) /* 0.255876475 */, 18 }, /* 4169 */ { MAD_F(0x041867c3) /* 0.255958332 */, 18 }, /* 4170 */ { MAD_F(0x0418bd9b) /* 0.256040196 */, 18 }, /* 4171 */ { MAD_F(0x04191374) /* 0.256122067 */, 18 }, /* 4172 */ { MAD_F(0x0419694e) /* 0.256203944 */, 18 }, /* 4173 */ { MAD_F(0x0419bf2b) /* 0.256285828 */, 18 }, /* 4174 */ { MAD_F(0x041a1509) /* 0.256367718 */, 18 }, /* 4175 */ { MAD_F(0x041a6ae9) /* 0.256449615 */, 18 }, /* 4176 */ { MAD_F(0x041ac0cb) /* 0.256531518 */, 18 }, /* 4177 */ { MAD_F(0x041b16ae) /* 0.256613428 */, 18 }, /* 4178 */ { MAD_F(0x041b6c94) /* 0.256695344 */, 18 }, /* 4179 */ { MAD_F(0x041bc27b) /* 0.256777267 */, 18 }, /* 4180 */ { MAD_F(0x041c1863) /* 0.256859197 */, 18 }, /* 4181 */ { MAD_F(0x041c6e4e) /* 0.256941133 */, 18 }, /* 4182 */ { MAD_F(0x041cc43a) /* 0.257023076 */, 18 }, /* 4183 */ { MAD_F(0x041d1a28) /* 0.257105025 */, 18 }, /* 4184 */ { MAD_F(0x041d7018) /* 0.257186980 */, 18 }, /* 4185 */ { MAD_F(0x041dc60a) /* 0.257268942 */, 18 }, /* 4186 */ { MAD_F(0x041e1bfd) /* 0.257350911 */, 18 }, /* 4187 */ { MAD_F(0x041e71f2) /* 0.257432886 */, 18 }, /* 4188 */ { MAD_F(0x041ec7e9) /* 0.257514868 */, 18 }, /* 4189 */ { MAD_F(0x041f1de1) /* 0.257596856 */, 18 }, /* 4190 */ { MAD_F(0x041f73dc) /* 0.257678851 */, 18 }, /* 4191 */ { MAD_F(0x041fc9d8) /* 0.257760852 */, 18 }, /* 4192 */ { MAD_F(0x04201fd5) /* 0.257842860 */, 18 }, /* 4193 */ { MAD_F(0x042075d5) /* 0.257924875 */, 18 }, /* 4194 */ { MAD_F(0x0420cbd6) /* 0.258006895 */, 18 }, /* 4195 */ { MAD_F(0x042121d9) /* 0.258088923 */, 18 }, /* 4196 */ { MAD_F(0x042177de) /* 0.258170957 */, 18 }, /* 4197 */ { MAD_F(0x0421cde5) /* 0.258252997 */, 18 }, /* 4198 */ { MAD_F(0x042223ed) /* 0.258335044 */, 18 }, /* 4199 */ { MAD_F(0x042279f7) /* 0.258417097 */, 18 }, /* 4200 */ { MAD_F(0x0422d003) /* 0.258499157 */, 18 }, /* 4201 */ { MAD_F(0x04232611) /* 0.258581224 */, 18 }, /* 4202 */ { MAD_F(0x04237c20) /* 0.258663297 */, 18 }, /* 4203 */ { MAD_F(0x0423d231) /* 0.258745376 */, 18 }, /* 4204 */ { MAD_F(0x04242844) /* 0.258827462 */, 18 }, /* 4205 */ { MAD_F(0x04247e58) /* 0.258909555 */, 18 }, /* 4206 */ { MAD_F(0x0424d46e) /* 0.258991654 */, 18 }, /* 4207 */ { MAD_F(0x04252a87) /* 0.259073760 */, 18 }, /* 4208 */ { MAD_F(0x042580a0) /* 0.259155872 */, 18 }, /* 4209 */ { MAD_F(0x0425d6bc) /* 0.259237990 */, 18 }, /* 4210 */ { MAD_F(0x04262cd9) /* 0.259320115 */, 18 }, /* 4211 */ { MAD_F(0x042682f8) /* 0.259402247 */, 18 }, /* 4212 */ { MAD_F(0x0426d919) /* 0.259484385 */, 18 }, /* 4213 */ { MAD_F(0x04272f3b) /* 0.259566529 */, 18 }, /* 4214 */ { MAD_F(0x04278560) /* 0.259648680 */, 18 }, /* 4215 */ { MAD_F(0x0427db86) /* 0.259730838 */, 18 }, /* 4216 */ { MAD_F(0x042831ad) /* 0.259813002 */, 18 }, /* 4217 */ { MAD_F(0x042887d7) /* 0.259895173 */, 18 }, /* 4218 */ { MAD_F(0x0428de02) /* 0.259977350 */, 18 }, /* 4219 */ { MAD_F(0x0429342f) /* 0.260059533 */, 18 }, /* 4220 */ { MAD_F(0x04298a5e) /* 0.260141723 */, 18 }, /* 4221 */ { MAD_F(0x0429e08e) /* 0.260223920 */, 18 }, /* 4222 */ { MAD_F(0x042a36c0) /* 0.260306123 */, 18 }, /* 4223 */ { MAD_F(0x042a8cf4) /* 0.260388332 */, 18 }, /* 4224 */ { MAD_F(0x042ae32a) /* 0.260470548 */, 18 }, /* 4225 */ { MAD_F(0x042b3962) /* 0.260552771 */, 18 }, /* 4226 */ { MAD_F(0x042b8f9b) /* 0.260635000 */, 18 }, /* 4227 */ { MAD_F(0x042be5d6) /* 0.260717235 */, 18 }, /* 4228 */ { MAD_F(0x042c3c12) /* 0.260799477 */, 18 }, /* 4229 */ { MAD_F(0x042c9251) /* 0.260881725 */, 18 }, /* 4230 */ { MAD_F(0x042ce891) /* 0.260963980 */, 18 }, /* 4231 */ { MAD_F(0x042d3ed3) /* 0.261046242 */, 18 }, /* 4232 */ { MAD_F(0x042d9516) /* 0.261128510 */, 18 }, /* 4233 */ { MAD_F(0x042deb5c) /* 0.261210784 */, 18 }, /* 4234 */ { MAD_F(0x042e41a3) /* 0.261293065 */, 18 }, /* 4235 */ { MAD_F(0x042e97ec) /* 0.261375352 */, 18 }, /* 4236 */ { MAD_F(0x042eee36) /* 0.261457646 */, 18 }, /* 4237 */ { MAD_F(0x042f4482) /* 0.261539946 */, 18 }, /* 4238 */ { MAD_F(0x042f9ad1) /* 0.261622253 */, 18 }, /* 4239 */ { MAD_F(0x042ff120) /* 0.261704566 */, 18 }, /* 4240 */ { MAD_F(0x04304772) /* 0.261786886 */, 18 }, /* 4241 */ { MAD_F(0x04309dc5) /* 0.261869212 */, 18 }, /* 4242 */ { MAD_F(0x0430f41a) /* 0.261951545 */, 18 }, /* 4243 */ { MAD_F(0x04314a71) /* 0.262033884 */, 18 }, /* 4244 */ { MAD_F(0x0431a0c9) /* 0.262116229 */, 18 }, /* 4245 */ { MAD_F(0x0431f723) /* 0.262198581 */, 18 }, /* 4246 */ { MAD_F(0x04324d7f) /* 0.262280940 */, 18 }, /* 4247 */ { MAD_F(0x0432a3dd) /* 0.262363305 */, 18 }, /* 4248 */ { MAD_F(0x0432fa3d) /* 0.262445676 */, 18 }, /* 4249 */ { MAD_F(0x0433509e) /* 0.262528054 */, 18 }, /* 4250 */ { MAD_F(0x0433a701) /* 0.262610438 */, 18 }, /* 4251 */ { MAD_F(0x0433fd65) /* 0.262692829 */, 18 }, /* 4252 */ { MAD_F(0x043453cc) /* 0.262775227 */, 18 }, /* 4253 */ { MAD_F(0x0434aa34) /* 0.262857630 */, 18 }, /* 4254 */ { MAD_F(0x0435009d) /* 0.262940040 */, 18 }, /* 4255 */ { MAD_F(0x04355709) /* 0.263022457 */, 18 }, /* 4256 */ { MAD_F(0x0435ad76) /* 0.263104880 */, 18 }, /* 4257 */ { MAD_F(0x043603e5) /* 0.263187310 */, 18 }, /* 4258 */ { MAD_F(0x04365a56) /* 0.263269746 */, 18 }, /* 4259 */ { MAD_F(0x0436b0c9) /* 0.263352188 */, 18 }, /* 4260 */ { MAD_F(0x0437073d) /* 0.263434637 */, 18 }, /* 4261 */ { MAD_F(0x04375db3) /* 0.263517093 */, 18 }, /* 4262 */ { MAD_F(0x0437b42a) /* 0.263599554 */, 18 }, /* 4263 */ { MAD_F(0x04380aa4) /* 0.263682023 */, 18 }, /* 4264 */ { MAD_F(0x0438611f) /* 0.263764497 */, 18 }, /* 4265 */ { MAD_F(0x0438b79c) /* 0.263846979 */, 18 }, /* 4266 */ { MAD_F(0x04390e1a) /* 0.263929466 */, 18 }, /* 4267 */ { MAD_F(0x0439649b) /* 0.264011960 */, 18 }, /* 4268 */ { MAD_F(0x0439bb1d) /* 0.264094461 */, 18 }, /* 4269 */ { MAD_F(0x043a11a1) /* 0.264176968 */, 18 }, /* 4270 */ { MAD_F(0x043a6826) /* 0.264259481 */, 18 }, /* 4271 */ { MAD_F(0x043abead) /* 0.264342001 */, 18 }, /* 4272 */ { MAD_F(0x043b1536) /* 0.264424527 */, 18 }, /* 4273 */ { MAD_F(0x043b6bc1) /* 0.264507060 */, 18 }, /* 4274 */ { MAD_F(0x043bc24d) /* 0.264589599 */, 18 }, /* 4275 */ { MAD_F(0x043c18dc) /* 0.264672145 */, 18 }, /* 4276 */ { MAD_F(0x043c6f6c) /* 0.264754697 */, 18 }, /* 4277 */ { MAD_F(0x043cc5fd) /* 0.264837255 */, 18 }, /* 4278 */ { MAD_F(0x043d1c91) /* 0.264919820 */, 18 }, /* 4279 */ { MAD_F(0x043d7326) /* 0.265002392 */, 18 }, /* 4280 */ { MAD_F(0x043dc9bc) /* 0.265084969 */, 18 }, /* 4281 */ { MAD_F(0x043e2055) /* 0.265167554 */, 18 }, /* 4282 */ { MAD_F(0x043e76ef) /* 0.265250144 */, 18 }, /* 4283 */ { MAD_F(0x043ecd8b) /* 0.265332741 */, 18 }, /* 4284 */ { MAD_F(0x043f2429) /* 0.265415345 */, 18 }, /* 4285 */ { MAD_F(0x043f7ac8) /* 0.265497955 */, 18 }, /* 4286 */ { MAD_F(0x043fd169) /* 0.265580571 */, 18 }, /* 4287 */ { MAD_F(0x0440280c) /* 0.265663194 */, 18 }, /* 4288 */ { MAD_F(0x04407eb1) /* 0.265745823 */, 18 }, /* 4289 */ { MAD_F(0x0440d557) /* 0.265828459 */, 18 }, /* 4290 */ { MAD_F(0x04412bff) /* 0.265911101 */, 18 }, /* 4291 */ { MAD_F(0x044182a9) /* 0.265993749 */, 18 }, /* 4292 */ { MAD_F(0x0441d955) /* 0.266076404 */, 18 }, /* 4293 */ { MAD_F(0x04423002) /* 0.266159065 */, 18 }, /* 4294 */ { MAD_F(0x044286b1) /* 0.266241733 */, 18 }, /* 4295 */ { MAD_F(0x0442dd61) /* 0.266324407 */, 18 }, /* 4296 */ { MAD_F(0x04433414) /* 0.266407088 */, 18 }, /* 4297 */ { MAD_F(0x04438ac8) /* 0.266489775 */, 18 }, /* 4298 */ { MAD_F(0x0443e17e) /* 0.266572468 */, 18 }, /* 4299 */ { MAD_F(0x04443835) /* 0.266655168 */, 18 }, /* 4300 */ { MAD_F(0x04448eef) /* 0.266737874 */, 18 }, /* 4301 */ { MAD_F(0x0444e5aa) /* 0.266820587 */, 18 }, /* 4302 */ { MAD_F(0x04453c66) /* 0.266903306 */, 18 }, /* 4303 */ { MAD_F(0x04459325) /* 0.266986031 */, 18 }, /* 4304 */ { MAD_F(0x0445e9e5) /* 0.267068763 */, 18 }, /* 4305 */ { MAD_F(0x044640a7) /* 0.267151501 */, 18 }, /* 4306 */ { MAD_F(0x0446976a) /* 0.267234246 */, 18 }, /* 4307 */ { MAD_F(0x0446ee30) /* 0.267316997 */, 18 }, /* 4308 */ { MAD_F(0x044744f7) /* 0.267399755 */, 18 }, /* 4309 */ { MAD_F(0x04479bc0) /* 0.267482518 */, 18 }, /* 4310 */ { MAD_F(0x0447f28a) /* 0.267565289 */, 18 }, /* 4311 */ { MAD_F(0x04484956) /* 0.267648065 */, 18 }, /* 4312 */ { MAD_F(0x0448a024) /* 0.267730848 */, 18 }, /* 4313 */ { MAD_F(0x0448f6f4) /* 0.267813638 */, 18 }, /* 4314 */ { MAD_F(0x04494dc5) /* 0.267896434 */, 18 }, /* 4315 */ { MAD_F(0x0449a498) /* 0.267979236 */, 18 }, /* 4316 */ { MAD_F(0x0449fb6d) /* 0.268062045 */, 18 }, /* 4317 */ { MAD_F(0x044a5243) /* 0.268144860 */, 18 }, /* 4318 */ { MAD_F(0x044aa91c) /* 0.268227681 */, 18 }, /* 4319 */ { MAD_F(0x044afff6) /* 0.268310509 */, 18 }, /* 4320 */ { MAD_F(0x044b56d1) /* 0.268393343 */, 18 }, /* 4321 */ { MAD_F(0x044badaf) /* 0.268476184 */, 18 }, /* 4322 */ { MAD_F(0x044c048e) /* 0.268559031 */, 18 }, /* 4323 */ { MAD_F(0x044c5b6f) /* 0.268641885 */, 18 }, /* 4324 */ { MAD_F(0x044cb251) /* 0.268724744 */, 18 }, /* 4325 */ { MAD_F(0x044d0935) /* 0.268807611 */, 18 }, /* 4326 */ { MAD_F(0x044d601b) /* 0.268890483 */, 18 }, /* 4327 */ { MAD_F(0x044db703) /* 0.268973362 */, 18 }, /* 4328 */ { MAD_F(0x044e0dec) /* 0.269056248 */, 18 }, /* 4329 */ { MAD_F(0x044e64d7) /* 0.269139139 */, 18 }, /* 4330 */ { MAD_F(0x044ebbc4) /* 0.269222037 */, 18 }, /* 4331 */ { MAD_F(0x044f12b3) /* 0.269304942 */, 18 }, /* 4332 */ { MAD_F(0x044f69a3) /* 0.269387853 */, 18 }, /* 4333 */ { MAD_F(0x044fc095) /* 0.269470770 */, 18 }, /* 4334 */ { MAD_F(0x04501788) /* 0.269553694 */, 18 }, /* 4335 */ { MAD_F(0x04506e7e) /* 0.269636624 */, 18 }, /* 4336 */ { MAD_F(0x0450c575) /* 0.269719560 */, 18 }, /* 4337 */ { MAD_F(0x04511c6e) /* 0.269802503 */, 18 }, /* 4338 */ { MAD_F(0x04517368) /* 0.269885452 */, 18 }, /* 4339 */ { MAD_F(0x0451ca64) /* 0.269968408 */, 18 }, /* 4340 */ { MAD_F(0x04522162) /* 0.270051370 */, 18 }, /* 4341 */ { MAD_F(0x04527862) /* 0.270134338 */, 18 }, /* 4342 */ { MAD_F(0x0452cf63) /* 0.270217312 */, 18 }, /* 4343 */ { MAD_F(0x04532666) /* 0.270300293 */, 18 }, /* 4344 */ { MAD_F(0x04537d6b) /* 0.270383281 */, 18 }, /* 4345 */ { MAD_F(0x0453d472) /* 0.270466275 */, 18 }, /* 4346 */ { MAD_F(0x04542b7a) /* 0.270549275 */, 18 }, /* 4347 */ { MAD_F(0x04548284) /* 0.270632281 */, 18 }, /* 4348 */ { MAD_F(0x0454d98f) /* 0.270715294 */, 18 }, /* 4349 */ { MAD_F(0x0455309c) /* 0.270798313 */, 18 }, /* 4350 */ { MAD_F(0x045587ab) /* 0.270881339 */, 18 }, /* 4351 */ { MAD_F(0x0455debc) /* 0.270964371 */, 18 }, /* 4352 */ { MAD_F(0x045635cf) /* 0.271047409 */, 18 }, /* 4353 */ { MAD_F(0x04568ce3) /* 0.271130454 */, 18 }, /* 4354 */ { MAD_F(0x0456e3f9) /* 0.271213505 */, 18 }, /* 4355 */ { MAD_F(0x04573b10) /* 0.271296562 */, 18 }, /* 4356 */ { MAD_F(0x04579229) /* 0.271379626 */, 18 }, /* 4357 */ { MAD_F(0x0457e944) /* 0.271462696 */, 18 }, /* 4358 */ { MAD_F(0x04584061) /* 0.271545772 */, 18 }, /* 4359 */ { MAD_F(0x0458977f) /* 0.271628855 */, 18 }, /* 4360 */ { MAD_F(0x0458ee9f) /* 0.271711944 */, 18 }, /* 4361 */ { MAD_F(0x045945c1) /* 0.271795040 */, 18 }, /* 4362 */ { MAD_F(0x04599ce5) /* 0.271878142 */, 18 }, /* 4363 */ { MAD_F(0x0459f40a) /* 0.271961250 */, 18 }, /* 4364 */ { MAD_F(0x045a4b31) /* 0.272044365 */, 18 }, /* 4365 */ { MAD_F(0x045aa259) /* 0.272127486 */, 18 }, /* 4366 */ { MAD_F(0x045af984) /* 0.272210613 */, 18 }, /* 4367 */ { MAD_F(0x045b50b0) /* 0.272293746 */, 18 }, /* 4368 */ { MAD_F(0x045ba7dd) /* 0.272376886 */, 18 }, /* 4369 */ { MAD_F(0x045bff0d) /* 0.272460033 */, 18 }, /* 4370 */ { MAD_F(0x045c563e) /* 0.272543185 */, 18 }, /* 4371 */ { MAD_F(0x045cad71) /* 0.272626344 */, 18 }, /* 4372 */ { MAD_F(0x045d04a5) /* 0.272709510 */, 18 }, /* 4373 */ { MAD_F(0x045d5bdc) /* 0.272792681 */, 18 }, /* 4374 */ { MAD_F(0x045db313) /* 0.272875859 */, 18 }, /* 4375 */ { MAD_F(0x045e0a4d) /* 0.272959044 */, 18 }, /* 4376 */ { MAD_F(0x045e6188) /* 0.273042234 */, 18 }, /* 4377 */ { MAD_F(0x045eb8c5) /* 0.273125431 */, 18 }, /* 4378 */ { MAD_F(0x045f1004) /* 0.273208635 */, 18 }, /* 4379 */ { MAD_F(0x045f6745) /* 0.273291844 */, 18 }, /* 4380 */ { MAD_F(0x045fbe87) /* 0.273375060 */, 18 }, /* 4381 */ { MAD_F(0x046015cb) /* 0.273458283 */, 18 }, /* 4382 */ { MAD_F(0x04606d10) /* 0.273541511 */, 18 }, /* 4383 */ { MAD_F(0x0460c457) /* 0.273624747 */, 18 }, /* 4384 */ { MAD_F(0x04611ba0) /* 0.273707988 */, 18 }, /* 4385 */ { MAD_F(0x046172eb) /* 0.273791236 */, 18 }, /* 4386 */ { MAD_F(0x0461ca37) /* 0.273874490 */, 18 }, /* 4387 */ { MAD_F(0x04622185) /* 0.273957750 */, 18 }, /* 4388 */ { MAD_F(0x046278d5) /* 0.274041017 */, 18 }, /* 4389 */ { MAD_F(0x0462d026) /* 0.274124290 */, 18 }, /* 4390 */ { MAD_F(0x0463277a) /* 0.274207569 */, 18 }, /* 4391 */ { MAD_F(0x04637ece) /* 0.274290855 */, 18 }, /* 4392 */ { MAD_F(0x0463d625) /* 0.274374147 */, 18 }, /* 4393 */ { MAD_F(0x04642d7d) /* 0.274457445 */, 18 }, /* 4394 */ { MAD_F(0x046484d7) /* 0.274540749 */, 18 }, /* 4395 */ { MAD_F(0x0464dc33) /* 0.274624060 */, 18 }, /* 4396 */ { MAD_F(0x04653390) /* 0.274707378 */, 18 }, /* 4397 */ { MAD_F(0x04658aef) /* 0.274790701 */, 18 }, /* 4398 */ { MAD_F(0x0465e250) /* 0.274874031 */, 18 }, /* 4399 */ { MAD_F(0x046639b2) /* 0.274957367 */, 18 }, /* 4400 */ { MAD_F(0x04669116) /* 0.275040710 */, 18 }, /* 4401 */ { MAD_F(0x0466e87c) /* 0.275124059 */, 18 }, /* 4402 */ { MAD_F(0x04673fe3) /* 0.275207414 */, 18 }, /* 4403 */ { MAD_F(0x0467974d) /* 0.275290775 */, 18 }, /* 4404 */ { MAD_F(0x0467eeb7) /* 0.275374143 */, 18 }, /* 4405 */ { MAD_F(0x04684624) /* 0.275457517 */, 18 }, /* 4406 */ { MAD_F(0x04689d92) /* 0.275540897 */, 18 }, /* 4407 */ { MAD_F(0x0468f502) /* 0.275624284 */, 18 }, /* 4408 */ { MAD_F(0x04694c74) /* 0.275707677 */, 18 }, /* 4409 */ { MAD_F(0x0469a3e7) /* 0.275791076 */, 18 }, /* 4410 */ { MAD_F(0x0469fb5c) /* 0.275874482 */, 18 }, /* 4411 */ { MAD_F(0x046a52d3) /* 0.275957894 */, 18 }, /* 4412 */ { MAD_F(0x046aaa4b) /* 0.276041312 */, 18 }, /* 4413 */ { MAD_F(0x046b01c5) /* 0.276124737 */, 18 }, /* 4414 */ { MAD_F(0x046b5941) /* 0.276208167 */, 18 }, /* 4415 */ { MAD_F(0x046bb0bf) /* 0.276291605 */, 18 }, /* 4416 */ { MAD_F(0x046c083e) /* 0.276375048 */, 18 }, /* 4417 */ { MAD_F(0x046c5fbf) /* 0.276458498 */, 18 }, /* 4418 */ { MAD_F(0x046cb741) /* 0.276541954 */, 18 }, /* 4419 */ { MAD_F(0x046d0ec5) /* 0.276625416 */, 18 }, /* 4420 */ { MAD_F(0x046d664b) /* 0.276708885 */, 18 }, /* 4421 */ { MAD_F(0x046dbdd3) /* 0.276792360 */, 18 }, /* 4422 */ { MAD_F(0x046e155c) /* 0.276875841 */, 18 }, /* 4423 */ { MAD_F(0x046e6ce7) /* 0.276959328 */, 18 }, /* 4424 */ { MAD_F(0x046ec474) /* 0.277042822 */, 18 }, /* 4425 */ { MAD_F(0x046f1c02) /* 0.277126322 */, 18 }, /* 4426 */ { MAD_F(0x046f7392) /* 0.277209829 */, 18 }, /* 4427 */ { MAD_F(0x046fcb24) /* 0.277293341 */, 18 }, /* 4428 */ { MAD_F(0x047022b8) /* 0.277376860 */, 18 }, /* 4429 */ { MAD_F(0x04707a4d) /* 0.277460385 */, 18 }, /* 4430 */ { MAD_F(0x0470d1e4) /* 0.277543917 */, 18 }, /* 4431 */ { MAD_F(0x0471297c) /* 0.277627455 */, 18 }, /* 4432 */ { MAD_F(0x04718116) /* 0.277710999 */, 18 }, /* 4433 */ { MAD_F(0x0471d8b2) /* 0.277794549 */, 18 }, /* 4434 */ { MAD_F(0x04723050) /* 0.277878106 */, 18 }, /* 4435 */ { MAD_F(0x047287ef) /* 0.277961669 */, 18 }, /* 4436 */ { MAD_F(0x0472df90) /* 0.278045238 */, 18 }, /* 4437 */ { MAD_F(0x04733733) /* 0.278128813 */, 18 }, /* 4438 */ { MAD_F(0x04738ed7) /* 0.278212395 */, 18 }, /* 4439 */ { MAD_F(0x0473e67d) /* 0.278295983 */, 18 }, /* 4440 */ { MAD_F(0x04743e25) /* 0.278379578 */, 18 }, /* 4441 */ { MAD_F(0x047495ce) /* 0.278463178 */, 18 }, /* 4442 */ { MAD_F(0x0474ed79) /* 0.278546785 */, 18 }, /* 4443 */ { MAD_F(0x04754526) /* 0.278630398 */, 18 }, /* 4444 */ { MAD_F(0x04759cd4) /* 0.278714018 */, 18 }, /* 4445 */ { MAD_F(0x0475f484) /* 0.278797643 */, 18 }, /* 4446 */ { MAD_F(0x04764c36) /* 0.278881275 */, 18 }, /* 4447 */ { MAD_F(0x0476a3ea) /* 0.278964914 */, 18 }, /* 4448 */ { MAD_F(0x0476fb9f) /* 0.279048558 */, 18 }, /* 4449 */ { MAD_F(0x04775356) /* 0.279132209 */, 18 }, /* 4450 */ { MAD_F(0x0477ab0e) /* 0.279215866 */, 18 }, /* 4451 */ { MAD_F(0x047802c8) /* 0.279299529 */, 18 }, /* 4452 */ { MAD_F(0x04785a84) /* 0.279383199 */, 18 }, /* 4453 */ { MAD_F(0x0478b242) /* 0.279466875 */, 18 }, /* 4454 */ { MAD_F(0x04790a01) /* 0.279550557 */, 18 }, /* 4455 */ { MAD_F(0x047961c2) /* 0.279634245 */, 18 }, /* 4456 */ { MAD_F(0x0479b984) /* 0.279717940 */, 18 }, /* 4457 */ { MAD_F(0x047a1149) /* 0.279801641 */, 18 }, /* 4458 */ { MAD_F(0x047a690f) /* 0.279885348 */, 18 }, /* 4459 */ { MAD_F(0x047ac0d6) /* 0.279969061 */, 18 }, /* 4460 */ { MAD_F(0x047b18a0) /* 0.280052781 */, 18 }, /* 4461 */ { MAD_F(0x047b706b) /* 0.280136507 */, 18 }, /* 4462 */ { MAD_F(0x047bc837) /* 0.280220239 */, 18 }, /* 4463 */ { MAD_F(0x047c2006) /* 0.280303978 */, 18 }, /* 4464 */ { MAD_F(0x047c77d6) /* 0.280387722 */, 18 }, /* 4465 */ { MAD_F(0x047ccfa8) /* 0.280471473 */, 18 }, /* 4466 */ { MAD_F(0x047d277b) /* 0.280555230 */, 18 }, /* 4467 */ { MAD_F(0x047d7f50) /* 0.280638994 */, 18 }, /* 4468 */ { MAD_F(0x047dd727) /* 0.280722764 */, 18 }, /* 4469 */ { MAD_F(0x047e2eff) /* 0.280806540 */, 18 }, /* 4470 */ { MAD_F(0x047e86d9) /* 0.280890322 */, 18 }, /* 4471 */ { MAD_F(0x047edeb5) /* 0.280974110 */, 18 }, /* 4472 */ { MAD_F(0x047f3693) /* 0.281057905 */, 18 }, /* 4473 */ { MAD_F(0x047f8e72) /* 0.281141706 */, 18 }, /* 4474 */ { MAD_F(0x047fe653) /* 0.281225513 */, 18 }, /* 4475 */ { MAD_F(0x04803e35) /* 0.281309326 */, 18 }, /* 4476 */ { MAD_F(0x04809619) /* 0.281393146 */, 18 }, /* 4477 */ { MAD_F(0x0480edff) /* 0.281476972 */, 18 }, /* 4478 */ { MAD_F(0x048145e7) /* 0.281560804 */, 18 }, /* 4479 */ { MAD_F(0x04819dd0) /* 0.281644643 */, 18 }, /* 4480 */ { MAD_F(0x0481f5bb) /* 0.281728487 */, 18 }, /* 4481 */ { MAD_F(0x04824da7) /* 0.281812338 */, 18 }, /* 4482 */ { MAD_F(0x0482a595) /* 0.281896195 */, 18 }, /* 4483 */ { MAD_F(0x0482fd85) /* 0.281980059 */, 18 }, /* 4484 */ { MAD_F(0x04835577) /* 0.282063928 */, 18 }, /* 4485 */ { MAD_F(0x0483ad6a) /* 0.282147804 */, 18 }, /* 4486 */ { MAD_F(0x0484055f) /* 0.282231686 */, 18 }, /* 4487 */ { MAD_F(0x04845d56) /* 0.282315574 */, 18 }, /* 4488 */ { MAD_F(0x0484b54e) /* 0.282399469 */, 18 }, /* 4489 */ { MAD_F(0x04850d48) /* 0.282483370 */, 18 }, /* 4490 */ { MAD_F(0x04856544) /* 0.282567277 */, 18 }, /* 4491 */ { MAD_F(0x0485bd41) /* 0.282651190 */, 18 }, /* 4492 */ { MAD_F(0x04861540) /* 0.282735109 */, 18 }, /* 4493 */ { MAD_F(0x04866d40) /* 0.282819035 */, 18 }, /* 4494 */ { MAD_F(0x0486c543) /* 0.282902967 */, 18 }, /* 4495 */ { MAD_F(0x04871d47) /* 0.282986905 */, 18 }, /* 4496 */ { MAD_F(0x0487754c) /* 0.283070849 */, 18 }, /* 4497 */ { MAD_F(0x0487cd54) /* 0.283154800 */, 18 }, /* 4498 */ { MAD_F(0x0488255d) /* 0.283238757 */, 18 }, /* 4499 */ { MAD_F(0x04887d67) /* 0.283322720 */, 18 }, /* 4500 */ { MAD_F(0x0488d574) /* 0.283406689 */, 18 }, /* 4501 */ { MAD_F(0x04892d82) /* 0.283490665 */, 18 }, /* 4502 */ { MAD_F(0x04898591) /* 0.283574646 */, 18 }, /* 4503 */ { MAD_F(0x0489dda3) /* 0.283658634 */, 18 }, /* 4504 */ { MAD_F(0x048a35b6) /* 0.283742628 */, 18 }, /* 4505 */ { MAD_F(0x048a8dca) /* 0.283826629 */, 18 }, /* 4506 */ { MAD_F(0x048ae5e1) /* 0.283910635 */, 18 }, /* 4507 */ { MAD_F(0x048b3df9) /* 0.283994648 */, 18 }, /* 4508 */ { MAD_F(0x048b9612) /* 0.284078667 */, 18 }, /* 4509 */ { MAD_F(0x048bee2e) /* 0.284162692 */, 18 }, /* 4510 */ { MAD_F(0x048c464b) /* 0.284246723 */, 18 }, /* 4511 */ { MAD_F(0x048c9e69) /* 0.284330761 */, 18 }, /* 4512 */ { MAD_F(0x048cf68a) /* 0.284414805 */, 18 }, /* 4513 */ { MAD_F(0x048d4eac) /* 0.284498855 */, 18 }, /* 4514 */ { MAD_F(0x048da6cf) /* 0.284582911 */, 18 }, /* 4515 */ { MAD_F(0x048dfef5) /* 0.284666974 */, 18 }, /* 4516 */ { MAD_F(0x048e571c) /* 0.284751042 */, 18 }, /* 4517 */ { MAD_F(0x048eaf44) /* 0.284835117 */, 18 }, /* 4518 */ { MAD_F(0x048f076f) /* 0.284919198 */, 18 }, /* 4519 */ { MAD_F(0x048f5f9b) /* 0.285003285 */, 18 }, /* 4520 */ { MAD_F(0x048fb7c8) /* 0.285087379 */, 18 }, /* 4521 */ { MAD_F(0x04900ff8) /* 0.285171479 */, 18 }, /* 4522 */ { MAD_F(0x04906829) /* 0.285255584 */, 18 }, /* 4523 */ { MAD_F(0x0490c05b) /* 0.285339697 */, 18 }, /* 4524 */ { MAD_F(0x04911890) /* 0.285423815 */, 18 }, /* 4525 */ { MAD_F(0x049170c6) /* 0.285507939 */, 18 }, /* 4526 */ { MAD_F(0x0491c8fd) /* 0.285592070 */, 18 }, /* 4527 */ { MAD_F(0x04922137) /* 0.285676207 */, 18 }, /* 4528 */ { MAD_F(0x04927972) /* 0.285760350 */, 18 }, /* 4529 */ { MAD_F(0x0492d1ae) /* 0.285844499 */, 18 }, /* 4530 */ { MAD_F(0x049329ed) /* 0.285928655 */, 18 }, /* 4531 */ { MAD_F(0x0493822c) /* 0.286012816 */, 18 }, /* 4532 */ { MAD_F(0x0493da6e) /* 0.286096984 */, 18 }, /* 4533 */ { MAD_F(0x049432b1) /* 0.286181158 */, 18 }, /* 4534 */ { MAD_F(0x04948af6) /* 0.286265338 */, 18 }, /* 4535 */ { MAD_F(0x0494e33d) /* 0.286349525 */, 18 }, /* 4536 */ { MAD_F(0x04953b85) /* 0.286433717 */, 18 }, /* 4537 */ { MAD_F(0x049593cf) /* 0.286517916 */, 18 }, /* 4538 */ { MAD_F(0x0495ec1b) /* 0.286602121 */, 18 }, /* 4539 */ { MAD_F(0x04964468) /* 0.286686332 */, 18 }, /* 4540 */ { MAD_F(0x04969cb7) /* 0.286770550 */, 18 }, /* 4541 */ { MAD_F(0x0496f508) /* 0.286854773 */, 18 }, /* 4542 */ { MAD_F(0x04974d5a) /* 0.286939003 */, 18 }, /* 4543 */ { MAD_F(0x0497a5ae) /* 0.287023239 */, 18 }, /* 4544 */ { MAD_F(0x0497fe03) /* 0.287107481 */, 18 }, /* 4545 */ { MAD_F(0x0498565a) /* 0.287191729 */, 18 }, /* 4546 */ { MAD_F(0x0498aeb3) /* 0.287275983 */, 18 }, /* 4547 */ { MAD_F(0x0499070e) /* 0.287360244 */, 18 }, /* 4548 */ { MAD_F(0x04995f6a) /* 0.287444511 */, 18 }, /* 4549 */ { MAD_F(0x0499b7c8) /* 0.287528784 */, 18 }, /* 4550 */ { MAD_F(0x049a1027) /* 0.287613063 */, 18 }, /* 4551 */ { MAD_F(0x049a6889) /* 0.287697348 */, 18 }, /* 4552 */ { MAD_F(0x049ac0eb) /* 0.287781640 */, 18 }, /* 4553 */ { MAD_F(0x049b1950) /* 0.287865937 */, 18 }, /* 4554 */ { MAD_F(0x049b71b6) /* 0.287950241 */, 18 }, /* 4555 */ { MAD_F(0x049bca1e) /* 0.288034551 */, 18 }, /* 4556 */ { MAD_F(0x049c2287) /* 0.288118867 */, 18 }, /* 4557 */ { MAD_F(0x049c7af2) /* 0.288203190 */, 18 }, /* 4558 */ { MAD_F(0x049cd35f) /* 0.288287518 */, 18 }, /* 4559 */ { MAD_F(0x049d2bce) /* 0.288371853 */, 18 }, /* 4560 */ { MAD_F(0x049d843e) /* 0.288456194 */, 18 }, /* 4561 */ { MAD_F(0x049ddcaf) /* 0.288540541 */, 18 }, /* 4562 */ { MAD_F(0x049e3523) /* 0.288624894 */, 18 }, /* 4563 */ { MAD_F(0x049e8d98) /* 0.288709253 */, 18 }, /* 4564 */ { MAD_F(0x049ee60e) /* 0.288793619 */, 18 }, /* 4565 */ { MAD_F(0x049f3e87) /* 0.288877990 */, 18 }, /* 4566 */ { MAD_F(0x049f9701) /* 0.288962368 */, 18 }, /* 4567 */ { MAD_F(0x049fef7c) /* 0.289046752 */, 18 }, /* 4568 */ { MAD_F(0x04a047fa) /* 0.289131142 */, 18 }, /* 4569 */ { MAD_F(0x04a0a079) /* 0.289215538 */, 18 }, /* 4570 */ { MAD_F(0x04a0f8f9) /* 0.289299941 */, 18 }, /* 4571 */ { MAD_F(0x04a1517c) /* 0.289384349 */, 18 }, /* 4572 */ { MAD_F(0x04a1a9ff) /* 0.289468764 */, 18 }, /* 4573 */ { MAD_F(0x04a20285) /* 0.289553185 */, 18 }, /* 4574 */ { MAD_F(0x04a25b0c) /* 0.289637612 */, 18 }, /* 4575 */ { MAD_F(0x04a2b395) /* 0.289722045 */, 18 }, /* 4576 */ { MAD_F(0x04a30c20) /* 0.289806485 */, 18 }, /* 4577 */ { MAD_F(0x04a364ac) /* 0.289890930 */, 18 }, /* 4578 */ { MAD_F(0x04a3bd3a) /* 0.289975382 */, 18 }, /* 4579 */ { MAD_F(0x04a415c9) /* 0.290059840 */, 18 }, /* 4580 */ { MAD_F(0x04a46e5a) /* 0.290144304 */, 18 }, /* 4581 */ { MAD_F(0x04a4c6ed) /* 0.290228774 */, 18 }, /* 4582 */ { MAD_F(0x04a51f81) /* 0.290313250 */, 18 }, /* 4583 */ { MAD_F(0x04a57818) /* 0.290397733 */, 18 }, /* 4584 */ { MAD_F(0x04a5d0af) /* 0.290482221 */, 18 }, /* 4585 */ { MAD_F(0x04a62949) /* 0.290566716 */, 18 }, /* 4586 */ { MAD_F(0x04a681e4) /* 0.290651217 */, 18 }, /* 4587 */ { MAD_F(0x04a6da80) /* 0.290735724 */, 18 }, /* 4588 */ { MAD_F(0x04a7331f) /* 0.290820237 */, 18 }, /* 4589 */ { MAD_F(0x04a78bbf) /* 0.290904756 */, 18 }, /* 4590 */ { MAD_F(0x04a7e460) /* 0.290989281 */, 18 }, /* 4591 */ { MAD_F(0x04a83d03) /* 0.291073813 */, 18 }, /* 4592 */ { MAD_F(0x04a895a8) /* 0.291158351 */, 18 }, /* 4593 */ { MAD_F(0x04a8ee4f) /* 0.291242894 */, 18 }, /* 4594 */ { MAD_F(0x04a946f7) /* 0.291327444 */, 18 }, /* 4595 */ { MAD_F(0x04a99fa1) /* 0.291412001 */, 18 }, /* 4596 */ { MAD_F(0x04a9f84c) /* 0.291496563 */, 18 }, /* 4597 */ { MAD_F(0x04aa50fa) /* 0.291581131 */, 18 }, /* 4598 */ { MAD_F(0x04aaa9a8) /* 0.291665706 */, 18 }, /* 4599 */ { MAD_F(0x04ab0259) /* 0.291750286 */, 18 }, /* 4600 */ { MAD_F(0x04ab5b0b) /* 0.291834873 */, 18 }, /* 4601 */ { MAD_F(0x04abb3bf) /* 0.291919466 */, 18 }, /* 4602 */ { MAD_F(0x04ac0c74) /* 0.292004065 */, 18 }, /* 4603 */ { MAD_F(0x04ac652b) /* 0.292088670 */, 18 }, /* 4604 */ { MAD_F(0x04acbde4) /* 0.292173281 */, 18 }, /* 4605 */ { MAD_F(0x04ad169e) /* 0.292257899 */, 18 }, /* 4606 */ { MAD_F(0x04ad6f5a) /* 0.292342522 */, 18 }, /* 4607 */ { MAD_F(0x04adc818) /* 0.292427152 */, 18 }, /* 4608 */ { MAD_F(0x04ae20d7) /* 0.292511788 */, 18 }, /* 4609 */ { MAD_F(0x04ae7998) /* 0.292596430 */, 18 }, /* 4610 */ { MAD_F(0x04aed25a) /* 0.292681078 */, 18 }, /* 4611 */ { MAD_F(0x04af2b1e) /* 0.292765732 */, 18 }, /* 4612 */ { MAD_F(0x04af83e4) /* 0.292850392 */, 18 }, /* 4613 */ { MAD_F(0x04afdcac) /* 0.292935058 */, 18 }, /* 4614 */ { MAD_F(0x04b03575) /* 0.293019731 */, 18 }, /* 4615 */ { MAD_F(0x04b08e40) /* 0.293104409 */, 18 }, /* 4616 */ { MAD_F(0x04b0e70c) /* 0.293189094 */, 18 }, /* 4617 */ { MAD_F(0x04b13fda) /* 0.293273785 */, 18 }, /* 4618 */ { MAD_F(0x04b198aa) /* 0.293358482 */, 18 }, /* 4619 */ { MAD_F(0x04b1f17b) /* 0.293443185 */, 18 }, /* 4620 */ { MAD_F(0x04b24a4e) /* 0.293527894 */, 18 }, /* 4621 */ { MAD_F(0x04b2a322) /* 0.293612609 */, 18 }, /* 4622 */ { MAD_F(0x04b2fbf9) /* 0.293697331 */, 18 }, /* 4623 */ { MAD_F(0x04b354d1) /* 0.293782058 */, 18 }, /* 4624 */ { MAD_F(0x04b3adaa) /* 0.293866792 */, 18 }, /* 4625 */ { MAD_F(0x04b40685) /* 0.293951532 */, 18 }, /* 4626 */ { MAD_F(0x04b45f62) /* 0.294036278 */, 18 }, /* 4627 */ { MAD_F(0x04b4b840) /* 0.294121029 */, 18 }, /* 4628 */ { MAD_F(0x04b51120) /* 0.294205788 */, 18 }, /* 4629 */ { MAD_F(0x04b56a02) /* 0.294290552 */, 18 }, /* 4630 */ { MAD_F(0x04b5c2e6) /* 0.294375322 */, 18 }, /* 4631 */ { MAD_F(0x04b61bcb) /* 0.294460098 */, 18 }, /* 4632 */ { MAD_F(0x04b674b1) /* 0.294544881 */, 18 }, /* 4633 */ { MAD_F(0x04b6cd99) /* 0.294629669 */, 18 }, /* 4634 */ { MAD_F(0x04b72683) /* 0.294714464 */, 18 }, /* 4635 */ { MAD_F(0x04b77f6f) /* 0.294799265 */, 18 }, /* 4636 */ { MAD_F(0x04b7d85c) /* 0.294884072 */, 18 }, /* 4637 */ { MAD_F(0x04b8314b) /* 0.294968885 */, 18 }, /* 4638 */ { MAD_F(0x04b88a3b) /* 0.295053704 */, 18 }, /* 4639 */ { MAD_F(0x04b8e32d) /* 0.295138529 */, 18 }, /* 4640 */ { MAD_F(0x04b93c21) /* 0.295223360 */, 18 }, /* 4641 */ { MAD_F(0x04b99516) /* 0.295308197 */, 18 }, /* 4642 */ { MAD_F(0x04b9ee0d) /* 0.295393041 */, 18 }, /* 4643 */ { MAD_F(0x04ba4706) /* 0.295477890 */, 18 }, /* 4644 */ { MAD_F(0x04baa000) /* 0.295562746 */, 18 }, /* 4645 */ { MAD_F(0x04baf8fc) /* 0.295647608 */, 18 }, /* 4646 */ { MAD_F(0x04bb51fa) /* 0.295732476 */, 18 }, /* 4647 */ { MAD_F(0x04bbaaf9) /* 0.295817349 */, 18 }, /* 4648 */ { MAD_F(0x04bc03fa) /* 0.295902229 */, 18 }, /* 4649 */ { MAD_F(0x04bc5cfc) /* 0.295987115 */, 18 }, /* 4650 */ { MAD_F(0x04bcb600) /* 0.296072008 */, 18 }, /* 4651 */ { MAD_F(0x04bd0f06) /* 0.296156906 */, 18 }, /* 4652 */ { MAD_F(0x04bd680d) /* 0.296241810 */, 18 }, /* 4653 */ { MAD_F(0x04bdc116) /* 0.296326721 */, 18 }, /* 4654 */ { MAD_F(0x04be1a21) /* 0.296411637 */, 18 }, /* 4655 */ { MAD_F(0x04be732d) /* 0.296496560 */, 18 }, /* 4656 */ { MAD_F(0x04becc3b) /* 0.296581488 */, 18 }, /* 4657 */ { MAD_F(0x04bf254a) /* 0.296666423 */, 18 }, /* 4658 */ { MAD_F(0x04bf7e5b) /* 0.296751364 */, 18 }, /* 4659 */ { MAD_F(0x04bfd76e) /* 0.296836311 */, 18 }, /* 4660 */ { MAD_F(0x04c03083) /* 0.296921264 */, 18 }, /* 4661 */ { MAD_F(0x04c08999) /* 0.297006223 */, 18 }, /* 4662 */ { MAD_F(0x04c0e2b0) /* 0.297091188 */, 18 }, /* 4663 */ { MAD_F(0x04c13bca) /* 0.297176159 */, 18 }, /* 4664 */ { MAD_F(0x04c194e4) /* 0.297261136 */, 18 }, /* 4665 */ { MAD_F(0x04c1ee01) /* 0.297346120 */, 18 }, /* 4666 */ { MAD_F(0x04c2471f) /* 0.297431109 */, 18 }, /* 4667 */ { MAD_F(0x04c2a03f) /* 0.297516105 */, 18 }, /* 4668 */ { MAD_F(0x04c2f960) /* 0.297601106 */, 18 }, /* 4669 */ { MAD_F(0x04c35283) /* 0.297686114 */, 18 }, /* 4670 */ { MAD_F(0x04c3aba8) /* 0.297771128 */, 18 }, /* 4671 */ { MAD_F(0x04c404ce) /* 0.297856147 */, 18 }, /* 4672 */ { MAD_F(0x04c45df6) /* 0.297941173 */, 18 }, /* 4673 */ { MAD_F(0x04c4b720) /* 0.298026205 */, 18 }, /* 4674 */ { MAD_F(0x04c5104b) /* 0.298111243 */, 18 }, /* 4675 */ { MAD_F(0x04c56978) /* 0.298196287 */, 18 }, /* 4676 */ { MAD_F(0x04c5c2a7) /* 0.298281337 */, 18 }, /* 4677 */ { MAD_F(0x04c61bd7) /* 0.298366393 */, 18 }, /* 4678 */ { MAD_F(0x04c67508) /* 0.298451456 */, 18 }, /* 4679 */ { MAD_F(0x04c6ce3c) /* 0.298536524 */, 18 }, /* 4680 */ { MAD_F(0x04c72771) /* 0.298621598 */, 18 }, /* 4681 */ { MAD_F(0x04c780a7) /* 0.298706679 */, 18 }, /* 4682 */ { MAD_F(0x04c7d9df) /* 0.298791765 */, 18 }, /* 4683 */ { MAD_F(0x04c83319) /* 0.298876858 */, 18 }, /* 4684 */ { MAD_F(0x04c88c55) /* 0.298961956 */, 18 }, /* 4685 */ { MAD_F(0x04c8e592) /* 0.299047061 */, 18 }, /* 4686 */ { MAD_F(0x04c93ed1) /* 0.299132172 */, 18 }, /* 4687 */ { MAD_F(0x04c99811) /* 0.299217288 */, 18 }, /* 4688 */ { MAD_F(0x04c9f153) /* 0.299302411 */, 18 }, /* 4689 */ { MAD_F(0x04ca4a97) /* 0.299387540 */, 18 }, /* 4690 */ { MAD_F(0x04caa3dc) /* 0.299472675 */, 18 }, /* 4691 */ { MAD_F(0x04cafd23) /* 0.299557816 */, 18 }, /* 4692 */ { MAD_F(0x04cb566b) /* 0.299642963 */, 18 }, /* 4693 */ { MAD_F(0x04cbafb5) /* 0.299728116 */, 18 }, /* 4694 */ { MAD_F(0x04cc0901) /* 0.299813275 */, 18 }, /* 4695 */ { MAD_F(0x04cc624e) /* 0.299898440 */, 18 }, /* 4696 */ { MAD_F(0x04ccbb9d) /* 0.299983611 */, 18 }, /* 4697 */ { MAD_F(0x04cd14ee) /* 0.300068789 */, 18 }, /* 4698 */ { MAD_F(0x04cd6e40) /* 0.300153972 */, 18 }, /* 4699 */ { MAD_F(0x04cdc794) /* 0.300239161 */, 18 }, /* 4700 */ { MAD_F(0x04ce20e9) /* 0.300324357 */, 18 }, /* 4701 */ { MAD_F(0x04ce7a40) /* 0.300409558 */, 18 }, /* 4702 */ { MAD_F(0x04ced399) /* 0.300494765 */, 18 }, /* 4703 */ { MAD_F(0x04cf2cf3) /* 0.300579979 */, 18 }, /* 4704 */ { MAD_F(0x04cf864f) /* 0.300665198 */, 18 }, /* 4705 */ { MAD_F(0x04cfdfad) /* 0.300750424 */, 18 }, /* 4706 */ { MAD_F(0x04d0390c) /* 0.300835656 */, 18 }, /* 4707 */ { MAD_F(0x04d0926d) /* 0.300920893 */, 18 }, /* 4708 */ { MAD_F(0x04d0ebcf) /* 0.301006137 */, 18 }, /* 4709 */ { MAD_F(0x04d14533) /* 0.301091387 */, 18 }, /* 4710 */ { MAD_F(0x04d19e99) /* 0.301176643 */, 18 }, /* 4711 */ { MAD_F(0x04d1f800) /* 0.301261904 */, 18 }, /* 4712 */ { MAD_F(0x04d25169) /* 0.301347172 */, 18 }, /* 4713 */ { MAD_F(0x04d2aad4) /* 0.301432446 */, 18 }, /* 4714 */ { MAD_F(0x04d30440) /* 0.301517726 */, 18 }, /* 4715 */ { MAD_F(0x04d35dae) /* 0.301603012 */, 18 }, /* 4716 */ { MAD_F(0x04d3b71d) /* 0.301688304 */, 18 }, /* 4717 */ { MAD_F(0x04d4108e) /* 0.301773602 */, 18 }, /* 4718 */ { MAD_F(0x04d46a01) /* 0.301858906 */, 18 }, /* 4719 */ { MAD_F(0x04d4c375) /* 0.301944216 */, 18 }, /* 4720 */ { MAD_F(0x04d51ceb) /* 0.302029532 */, 18 }, /* 4721 */ { MAD_F(0x04d57662) /* 0.302114854 */, 18 }, /* 4722 */ { MAD_F(0x04d5cfdb) /* 0.302200182 */, 18 }, /* 4723 */ { MAD_F(0x04d62956) /* 0.302285516 */, 18 }, /* 4724 */ { MAD_F(0x04d682d2) /* 0.302370856 */, 18 }, /* 4725 */ { MAD_F(0x04d6dc50) /* 0.302456203 */, 18 }, /* 4726 */ { MAD_F(0x04d735d0) /* 0.302541555 */, 18 }, /* 4727 */ { MAD_F(0x04d78f51) /* 0.302626913 */, 18 }, /* 4728 */ { MAD_F(0x04d7e8d4) /* 0.302712277 */, 18 }, /* 4729 */ { MAD_F(0x04d84258) /* 0.302797648 */, 18 }, /* 4730 */ { MAD_F(0x04d89bde) /* 0.302883024 */, 18 }, /* 4731 */ { MAD_F(0x04d8f566) /* 0.302968406 */, 18 }, /* 4732 */ { MAD_F(0x04d94eef) /* 0.303053794 */, 18 }, /* 4733 */ { MAD_F(0x04d9a87a) /* 0.303139189 */, 18 }, /* 4734 */ { MAD_F(0x04da0207) /* 0.303224589 */, 18 }, /* 4735 */ { MAD_F(0x04da5b95) /* 0.303309995 */, 18 }, /* 4736 */ { MAD_F(0x04dab524) /* 0.303395408 */, 18 }, /* 4737 */ { MAD_F(0x04db0eb6) /* 0.303480826 */, 18 }, /* 4738 */ { MAD_F(0x04db6849) /* 0.303566251 */, 18 }, /* 4739 */ { MAD_F(0x04dbc1dd) /* 0.303651681 */, 18 }, /* 4740 */ { MAD_F(0x04dc1b73) /* 0.303737117 */, 18 }, /* 4741 */ { MAD_F(0x04dc750b) /* 0.303822560 */, 18 }, /* 4742 */ { MAD_F(0x04dccea5) /* 0.303908008 */, 18 }, /* 4743 */ { MAD_F(0x04dd2840) /* 0.303993463 */, 18 }, /* 4744 */ { MAD_F(0x04dd81dc) /* 0.304078923 */, 18 }, /* 4745 */ { MAD_F(0x04dddb7a) /* 0.304164390 */, 18 }, /* 4746 */ { MAD_F(0x04de351a) /* 0.304249862 */, 18 }, /* 4747 */ { MAD_F(0x04de8ebc) /* 0.304335340 */, 18 }, /* 4748 */ { MAD_F(0x04dee85f) /* 0.304420825 */, 18 }, /* 4749 */ { MAD_F(0x04df4203) /* 0.304506315 */, 18 }, /* 4750 */ { MAD_F(0x04df9baa) /* 0.304591812 */, 18 }, /* 4751 */ { MAD_F(0x04dff552) /* 0.304677314 */, 18 }, /* 4752 */ { MAD_F(0x04e04efb) /* 0.304762823 */, 18 }, /* 4753 */ { MAD_F(0x04e0a8a6) /* 0.304848337 */, 18 }, /* 4754 */ { MAD_F(0x04e10253) /* 0.304933858 */, 18 }, /* 4755 */ { MAD_F(0x04e15c01) /* 0.305019384 */, 18 }, /* 4756 */ { MAD_F(0x04e1b5b1) /* 0.305104917 */, 18 }, /* 4757 */ { MAD_F(0x04e20f63) /* 0.305190455 */, 18 }, /* 4758 */ { MAD_F(0x04e26916) /* 0.305275999 */, 18 }, /* 4759 */ { MAD_F(0x04e2c2cb) /* 0.305361550 */, 18 }, /* 4760 */ { MAD_F(0x04e31c81) /* 0.305447106 */, 18 }, /* 4761 */ { MAD_F(0x04e37639) /* 0.305532669 */, 18 }, /* 4762 */ { MAD_F(0x04e3cff3) /* 0.305618237 */, 18 }, /* 4763 */ { MAD_F(0x04e429ae) /* 0.305703811 */, 18 }, /* 4764 */ { MAD_F(0x04e4836b) /* 0.305789392 */, 18 }, /* 4765 */ { MAD_F(0x04e4dd29) /* 0.305874978 */, 18 }, /* 4766 */ { MAD_F(0x04e536e9) /* 0.305960571 */, 18 }, /* 4767 */ { MAD_F(0x04e590ab) /* 0.306046169 */, 18 }, /* 4768 */ { MAD_F(0x04e5ea6e) /* 0.306131773 */, 18 }, /* 4769 */ { MAD_F(0x04e64433) /* 0.306217383 */, 18 }, /* 4770 */ { MAD_F(0x04e69df9) /* 0.306303000 */, 18 }, /* 4771 */ { MAD_F(0x04e6f7c1) /* 0.306388622 */, 18 }, /* 4772 */ { MAD_F(0x04e7518b) /* 0.306474250 */, 18 }, /* 4773 */ { MAD_F(0x04e7ab56) /* 0.306559885 */, 18 }, /* 4774 */ { MAD_F(0x04e80523) /* 0.306645525 */, 18 }, /* 4775 */ { MAD_F(0x04e85ef2) /* 0.306731171 */, 18 }, /* 4776 */ { MAD_F(0x04e8b8c2) /* 0.306816823 */, 18 }, /* 4777 */ { MAD_F(0x04e91293) /* 0.306902481 */, 18 }, /* 4778 */ { MAD_F(0x04e96c67) /* 0.306988145 */, 18 }, /* 4779 */ { MAD_F(0x04e9c63b) /* 0.307073816 */, 18 }, /* 4780 */ { MAD_F(0x04ea2012) /* 0.307159492 */, 18 }, /* 4781 */ { MAD_F(0x04ea79ea) /* 0.307245174 */, 18 }, /* 4782 */ { MAD_F(0x04ead3c4) /* 0.307330862 */, 18 }, /* 4783 */ { MAD_F(0x04eb2d9f) /* 0.307416556 */, 18 }, /* 4784 */ { MAD_F(0x04eb877c) /* 0.307502256 */, 18 }, /* 4785 */ { MAD_F(0x04ebe15b) /* 0.307587962 */, 18 }, /* 4786 */ { MAD_F(0x04ec3b3b) /* 0.307673674 */, 18 }, /* 4787 */ { MAD_F(0x04ec951c) /* 0.307759392 */, 18 }, /* 4788 */ { MAD_F(0x04ecef00) /* 0.307845115 */, 18 }, /* 4789 */ { MAD_F(0x04ed48e5) /* 0.307930845 */, 18 }, /* 4790 */ { MAD_F(0x04eda2cb) /* 0.308016581 */, 18 }, /* 4791 */ { MAD_F(0x04edfcb3) /* 0.308102323 */, 18 }, /* 4792 */ { MAD_F(0x04ee569d) /* 0.308188071 */, 18 }, /* 4793 */ { MAD_F(0x04eeb088) /* 0.308273824 */, 18 }, /* 4794 */ { MAD_F(0x04ef0a75) /* 0.308359584 */, 18 }, /* 4795 */ { MAD_F(0x04ef6464) /* 0.308445350 */, 18 }, /* 4796 */ { MAD_F(0x04efbe54) /* 0.308531121 */, 18 }, /* 4797 */ { MAD_F(0x04f01846) /* 0.308616899 */, 18 }, /* 4798 */ { MAD_F(0x04f07239) /* 0.308702682 */, 18 }, /* 4799 */ { MAD_F(0x04f0cc2e) /* 0.308788472 */, 18 }, /* 4800 */ { MAD_F(0x04f12624) /* 0.308874267 */, 18 }, /* 4801 */ { MAD_F(0x04f1801d) /* 0.308960068 */, 18 }, /* 4802 */ { MAD_F(0x04f1da16) /* 0.309045876 */, 18 }, /* 4803 */ { MAD_F(0x04f23412) /* 0.309131689 */, 18 }, /* 4804 */ { MAD_F(0x04f28e0f) /* 0.309217508 */, 18 }, /* 4805 */ { MAD_F(0x04f2e80d) /* 0.309303334 */, 18 }, /* 4806 */ { MAD_F(0x04f3420d) /* 0.309389165 */, 18 }, /* 4807 */ { MAD_F(0x04f39c0f) /* 0.309475002 */, 18 }, /* 4808 */ { MAD_F(0x04f3f612) /* 0.309560845 */, 18 }, /* 4809 */ { MAD_F(0x04f45017) /* 0.309646694 */, 18 }, /* 4810 */ { MAD_F(0x04f4aa1e) /* 0.309732549 */, 18 }, /* 4811 */ { MAD_F(0x04f50426) /* 0.309818410 */, 18 }, /* 4812 */ { MAD_F(0x04f55e30) /* 0.309904277 */, 18 }, /* 4813 */ { MAD_F(0x04f5b83b) /* 0.309990150 */, 18 }, /* 4814 */ { MAD_F(0x04f61248) /* 0.310076028 */, 18 }, /* 4815 */ { MAD_F(0x04f66c56) /* 0.310161913 */, 18 }, /* 4816 */ { MAD_F(0x04f6c666) /* 0.310247804 */, 18 }, /* 4817 */ { MAD_F(0x04f72078) /* 0.310333700 */, 18 }, /* 4818 */ { MAD_F(0x04f77a8b) /* 0.310419603 */, 18 }, /* 4819 */ { MAD_F(0x04f7d4a0) /* 0.310505511 */, 18 }, /* 4820 */ { MAD_F(0x04f82eb7) /* 0.310591426 */, 18 }, /* 4821 */ { MAD_F(0x04f888cf) /* 0.310677346 */, 18 }, /* 4822 */ { MAD_F(0x04f8e2e9) /* 0.310763272 */, 18 }, /* 4823 */ { MAD_F(0x04f93d04) /* 0.310849205 */, 18 }, /* 4824 */ { MAD_F(0x04f99721) /* 0.310935143 */, 18 }, /* 4825 */ { MAD_F(0x04f9f13f) /* 0.311021087 */, 18 }, /* 4826 */ { MAD_F(0x04fa4b5f) /* 0.311107037 */, 18 }, /* 4827 */ { MAD_F(0x04faa581) /* 0.311192993 */, 18 }, /* 4828 */ { MAD_F(0x04faffa4) /* 0.311278955 */, 18 }, /* 4829 */ { MAD_F(0x04fb59c9) /* 0.311364923 */, 18 }, /* 4830 */ { MAD_F(0x04fbb3ef) /* 0.311450897 */, 18 }, /* 4831 */ { MAD_F(0x04fc0e17) /* 0.311536877 */, 18 }, /* 4832 */ { MAD_F(0x04fc6841) /* 0.311622862 */, 18 }, /* 4833 */ { MAD_F(0x04fcc26c) /* 0.311708854 */, 18 }, /* 4834 */ { MAD_F(0x04fd1c99) /* 0.311794851 */, 18 }, /* 4835 */ { MAD_F(0x04fd76c7) /* 0.311880855 */, 18 }, /* 4836 */ { MAD_F(0x04fdd0f7) /* 0.311966864 */, 18 }, /* 4837 */ { MAD_F(0x04fe2b29) /* 0.312052880 */, 18 }, /* 4838 */ { MAD_F(0x04fe855c) /* 0.312138901 */, 18 }, /* 4839 */ { MAD_F(0x04fedf91) /* 0.312224928 */, 18 }, /* 4840 */ { MAD_F(0x04ff39c7) /* 0.312310961 */, 18 }, /* 4841 */ { MAD_F(0x04ff93ff) /* 0.312397000 */, 18 }, /* 4842 */ { MAD_F(0x04ffee38) /* 0.312483045 */, 18 }, /* 4843 */ { MAD_F(0x05004874) /* 0.312569096 */, 18 }, /* 4844 */ { MAD_F(0x0500a2b0) /* 0.312655153 */, 18 }, /* 4845 */ { MAD_F(0x0500fcef) /* 0.312741216 */, 18 }, /* 4846 */ { MAD_F(0x0501572e) /* 0.312827284 */, 18 }, /* 4847 */ { MAD_F(0x0501b170) /* 0.312913359 */, 18 }, /* 4848 */ { MAD_F(0x05020bb3) /* 0.312999439 */, 18 }, /* 4849 */ { MAD_F(0x050265f8) /* 0.313085526 */, 18 }, /* 4850 */ { MAD_F(0x0502c03e) /* 0.313171618 */, 18 }, /* 4851 */ { MAD_F(0x05031a86) /* 0.313257716 */, 18 }, /* 4852 */ { MAD_F(0x050374cf) /* 0.313343820 */, 18 }, /* 4853 */ { MAD_F(0x0503cf1a) /* 0.313429931 */, 18 }, /* 4854 */ { MAD_F(0x05042967) /* 0.313516047 */, 18 }, /* 4855 */ { MAD_F(0x050483b5) /* 0.313602168 */, 18 }, /* 4856 */ { MAD_F(0x0504de05) /* 0.313688296 */, 18 }, /* 4857 */ { MAD_F(0x05053856) /* 0.313774430 */, 18 }, /* 4858 */ { MAD_F(0x050592a9) /* 0.313860570 */, 18 }, /* 4859 */ { MAD_F(0x0505ecfd) /* 0.313946715 */, 18 }, /* 4860 */ { MAD_F(0x05064754) /* 0.314032867 */, 18 }, /* 4861 */ { MAD_F(0x0506a1ab) /* 0.314119024 */, 18 }, /* 4862 */ { MAD_F(0x0506fc04) /* 0.314205187 */, 18 }, /* 4863 */ { MAD_F(0x0507565f) /* 0.314291357 */, 18 }, /* 4864 */ { MAD_F(0x0507b0bc) /* 0.314377532 */, 18 }, /* 4865 */ { MAD_F(0x05080b1a) /* 0.314463713 */, 18 }, /* 4866 */ { MAD_F(0x05086579) /* 0.314549900 */, 18 }, /* 4867 */ { MAD_F(0x0508bfdb) /* 0.314636092 */, 18 }, /* 4868 */ { MAD_F(0x05091a3d) /* 0.314722291 */, 18 }, /* 4869 */ { MAD_F(0x050974a2) /* 0.314808496 */, 18 }, /* 4870 */ { MAD_F(0x0509cf08) /* 0.314894706 */, 18 }, /* 4871 */ { MAD_F(0x050a296f) /* 0.314980923 */, 18 }, /* 4872 */ { MAD_F(0x050a83d8) /* 0.315067145 */, 18 }, /* 4873 */ { MAD_F(0x050ade43) /* 0.315153373 */, 18 }, /* 4874 */ { MAD_F(0x050b38af) /* 0.315239607 */, 18 }, /* 4875 */ { MAD_F(0x050b931d) /* 0.315325847 */, 18 }, /* 4876 */ { MAD_F(0x050bed8d) /* 0.315412093 */, 18 }, /* 4877 */ { MAD_F(0x050c47fe) /* 0.315498345 */, 18 }, /* 4878 */ { MAD_F(0x050ca271) /* 0.315584603 */, 18 }, /* 4879 */ { MAD_F(0x050cfce5) /* 0.315670866 */, 18 }, /* 4880 */ { MAD_F(0x050d575b) /* 0.315757136 */, 18 }, /* 4881 */ { MAD_F(0x050db1d2) /* 0.315843411 */, 18 }, /* 4882 */ { MAD_F(0x050e0c4b) /* 0.315929693 */, 18 }, /* 4883 */ { MAD_F(0x050e66c5) /* 0.316015980 */, 18 }, /* 4884 */ { MAD_F(0x050ec141) /* 0.316102273 */, 18 }, /* 4885 */ { MAD_F(0x050f1bbf) /* 0.316188572 */, 18 }, /* 4886 */ { MAD_F(0x050f763e) /* 0.316274877 */, 18 }, /* 4887 */ { MAD_F(0x050fd0bf) /* 0.316361187 */, 18 }, /* 4888 */ { MAD_F(0x05102b42) /* 0.316447504 */, 18 }, /* 4889 */ { MAD_F(0x051085c6) /* 0.316533826 */, 18 }, /* 4890 */ { MAD_F(0x0510e04b) /* 0.316620155 */, 18 }, /* 4891 */ { MAD_F(0x05113ad3) /* 0.316706489 */, 18 }, /* 4892 */ { MAD_F(0x0511955b) /* 0.316792829 */, 18 }, /* 4893 */ { MAD_F(0x0511efe6) /* 0.316879175 */, 18 }, /* 4894 */ { MAD_F(0x05124a72) /* 0.316965527 */, 18 }, /* 4895 */ { MAD_F(0x0512a4ff) /* 0.317051885 */, 18 }, /* 4896 */ { MAD_F(0x0512ff8e) /* 0.317138249 */, 18 }, /* 4897 */ { MAD_F(0x05135a1f) /* 0.317224618 */, 18 }, /* 4898 */ { MAD_F(0x0513b4b1) /* 0.317310994 */, 18 }, /* 4899 */ { MAD_F(0x05140f45) /* 0.317397375 */, 18 }, /* 4900 */ { MAD_F(0x051469da) /* 0.317483762 */, 18 }, /* 4901 */ { MAD_F(0x0514c471) /* 0.317570155 */, 18 }, /* 4902 */ { MAD_F(0x05151f0a) /* 0.317656554 */, 18 }, /* 4903 */ { MAD_F(0x051579a4) /* 0.317742959 */, 18 }, /* 4904 */ { MAD_F(0x0515d440) /* 0.317829370 */, 18 }, /* 4905 */ { MAD_F(0x05162edd) /* 0.317915786 */, 18 }, /* 4906 */ { MAD_F(0x0516897c) /* 0.318002209 */, 18 }, /* 4907 */ { MAD_F(0x0516e41c) /* 0.318088637 */, 18 }, /* 4908 */ { MAD_F(0x05173ebe) /* 0.318175071 */, 18 }, /* 4909 */ { MAD_F(0x05179962) /* 0.318261511 */, 18 }, /* 4910 */ { MAD_F(0x0517f407) /* 0.318347957 */, 18 }, /* 4911 */ { MAD_F(0x05184eae) /* 0.318434409 */, 18 }, /* 4912 */ { MAD_F(0x0518a956) /* 0.318520867 */, 18 }, /* 4913 */ { MAD_F(0x05190400) /* 0.318607330 */, 18 }, /* 4914 */ { MAD_F(0x05195eab) /* 0.318693800 */, 18 }, /* 4915 */ { MAD_F(0x0519b958) /* 0.318780275 */, 18 }, /* 4916 */ { MAD_F(0x051a1407) /* 0.318866756 */, 18 }, /* 4917 */ { MAD_F(0x051a6eb7) /* 0.318953243 */, 18 }, /* 4918 */ { MAD_F(0x051ac969) /* 0.319039736 */, 18 }, /* 4919 */ { MAD_F(0x051b241c) /* 0.319126235 */, 18 }, /* 4920 */ { MAD_F(0x051b7ed1) /* 0.319212739 */, 18 }, /* 4921 */ { MAD_F(0x051bd987) /* 0.319299250 */, 18 }, /* 4922 */ { MAD_F(0x051c3440) /* 0.319385766 */, 18 }, /* 4923 */ { MAD_F(0x051c8ef9) /* 0.319472288 */, 18 }, /* 4924 */ { MAD_F(0x051ce9b4) /* 0.319558816 */, 18 }, /* 4925 */ { MAD_F(0x051d4471) /* 0.319645350 */, 18 }, /* 4926 */ { MAD_F(0x051d9f2f) /* 0.319731890 */, 18 }, /* 4927 */ { MAD_F(0x051df9ef) /* 0.319818435 */, 18 }, /* 4928 */ { MAD_F(0x051e54b1) /* 0.319904987 */, 18 }, /* 4929 */ { MAD_F(0x051eaf74) /* 0.319991544 */, 18 }, /* 4930 */ { MAD_F(0x051f0a38) /* 0.320078107 */, 18 }, /* 4931 */ { MAD_F(0x051f64ff) /* 0.320164676 */, 18 }, /* 4932 */ { MAD_F(0x051fbfc6) /* 0.320251251 */, 18 }, /* 4933 */ { MAD_F(0x05201a90) /* 0.320337832 */, 18 }, /* 4934 */ { MAD_F(0x0520755b) /* 0.320424419 */, 18 }, /* 4935 */ { MAD_F(0x0520d027) /* 0.320511011 */, 18 }, /* 4936 */ { MAD_F(0x05212af5) /* 0.320597609 */, 18 }, /* 4937 */ { MAD_F(0x052185c5) /* 0.320684213 */, 18 }, /* 4938 */ { MAD_F(0x0521e096) /* 0.320770823 */, 18 }, /* 4939 */ { MAD_F(0x05223b69) /* 0.320857439 */, 18 }, /* 4940 */ { MAD_F(0x0522963d) /* 0.320944061 */, 18 }, /* 4941 */ { MAD_F(0x0522f113) /* 0.321030688 */, 18 }, /* 4942 */ { MAD_F(0x05234bea) /* 0.321117322 */, 18 }, /* 4943 */ { MAD_F(0x0523a6c3) /* 0.321203961 */, 18 }, /* 4944 */ { MAD_F(0x0524019e) /* 0.321290606 */, 18 }, /* 4945 */ { MAD_F(0x05245c7a) /* 0.321377257 */, 18 }, /* 4946 */ { MAD_F(0x0524b758) /* 0.321463913 */, 18 }, /* 4947 */ { MAD_F(0x05251237) /* 0.321550576 */, 18 }, /* 4948 */ { MAD_F(0x05256d18) /* 0.321637244 */, 18 }, /* 4949 */ { MAD_F(0x0525c7fb) /* 0.321723919 */, 18 }, /* 4950 */ { MAD_F(0x052622df) /* 0.321810599 */, 18 }, /* 4951 */ { MAD_F(0x05267dc4) /* 0.321897285 */, 18 }, /* 4952 */ { MAD_F(0x0526d8ab) /* 0.321983976 */, 18 }, /* 4953 */ { MAD_F(0x05273394) /* 0.322070674 */, 18 }, /* 4954 */ { MAD_F(0x05278e7e) /* 0.322157377 */, 18 }, /* 4955 */ { MAD_F(0x0527e96a) /* 0.322244087 */, 18 }, /* 4956 */ { MAD_F(0x05284457) /* 0.322330802 */, 18 }, /* 4957 */ { MAD_F(0x05289f46) /* 0.322417523 */, 18 }, /* 4958 */ { MAD_F(0x0528fa37) /* 0.322504249 */, 18 }, /* 4959 */ { MAD_F(0x05295529) /* 0.322590982 */, 18 }, /* 4960 */ { MAD_F(0x0529b01d) /* 0.322677720 */, 18 }, /* 4961 */ { MAD_F(0x052a0b12) /* 0.322764465 */, 18 }, /* 4962 */ { MAD_F(0x052a6609) /* 0.322851215 */, 18 }, /* 4963 */ { MAD_F(0x052ac101) /* 0.322937971 */, 18 }, /* 4964 */ { MAD_F(0x052b1bfb) /* 0.323024732 */, 18 }, /* 4965 */ { MAD_F(0x052b76f7) /* 0.323111500 */, 18 }, /* 4966 */ { MAD_F(0x052bd1f4) /* 0.323198273 */, 18 }, /* 4967 */ { MAD_F(0x052c2cf2) /* 0.323285052 */, 18 }, /* 4968 */ { MAD_F(0x052c87f2) /* 0.323371837 */, 18 }, /* 4969 */ { MAD_F(0x052ce2f4) /* 0.323458628 */, 18 }, /* 4970 */ { MAD_F(0x052d3df7) /* 0.323545425 */, 18 }, /* 4971 */ { MAD_F(0x052d98fc) /* 0.323632227 */, 18 }, /* 4972 */ { MAD_F(0x052df403) /* 0.323719036 */, 18 }, /* 4973 */ { MAD_F(0x052e4f0b) /* 0.323805850 */, 18 }, /* 4974 */ { MAD_F(0x052eaa14) /* 0.323892670 */, 18 }, /* 4975 */ { MAD_F(0x052f051f) /* 0.323979496 */, 18 }, /* 4976 */ { MAD_F(0x052f602c) /* 0.324066327 */, 18 }, /* 4977 */ { MAD_F(0x052fbb3a) /* 0.324153165 */, 18 }, /* 4978 */ { MAD_F(0x0530164a) /* 0.324240008 */, 18 }, /* 4979 */ { MAD_F(0x0530715b) /* 0.324326857 */, 18 }, /* 4980 */ { MAD_F(0x0530cc6e) /* 0.324413712 */, 18 }, /* 4981 */ { MAD_F(0x05312783) /* 0.324500572 */, 18 }, /* 4982 */ { MAD_F(0x05318299) /* 0.324587439 */, 18 }, /* 4983 */ { MAD_F(0x0531ddb0) /* 0.324674311 */, 18 }, /* 4984 */ { MAD_F(0x053238ca) /* 0.324761189 */, 18 }, /* 4985 */ { MAD_F(0x053293e4) /* 0.324848073 */, 18 }, /* 4986 */ { MAD_F(0x0532ef01) /* 0.324934963 */, 18 }, /* 4987 */ { MAD_F(0x05334a1e) /* 0.325021858 */, 18 }, /* 4988 */ { MAD_F(0x0533a53e) /* 0.325108760 */, 18 }, /* 4989 */ { MAD_F(0x0534005f) /* 0.325195667 */, 18 }, /* 4990 */ { MAD_F(0x05345b81) /* 0.325282580 */, 18 }, /* 4991 */ { MAD_F(0x0534b6a5) /* 0.325369498 */, 18 }, /* 4992 */ { MAD_F(0x053511cb) /* 0.325456423 */, 18 }, /* 4993 */ { MAD_F(0x05356cf2) /* 0.325543353 */, 18 }, /* 4994 */ { MAD_F(0x0535c81b) /* 0.325630290 */, 18 }, /* 4995 */ { MAD_F(0x05362345) /* 0.325717232 */, 18 }, /* 4996 */ { MAD_F(0x05367e71) /* 0.325804179 */, 18 }, /* 4997 */ { MAD_F(0x0536d99f) /* 0.325891133 */, 18 }, /* 4998 */ { MAD_F(0x053734ce) /* 0.325978092 */, 18 }, /* 4999 */ { MAD_F(0x05378ffe) /* 0.326065057 */, 18 }, /* 5000 */ { MAD_F(0x0537eb30) /* 0.326152028 */, 18 }, /* 5001 */ { MAD_F(0x05384664) /* 0.326239005 */, 18 }, /* 5002 */ { MAD_F(0x0538a199) /* 0.326325988 */, 18 }, /* 5003 */ { MAD_F(0x0538fcd0) /* 0.326412976 */, 18 }, /* 5004 */ { MAD_F(0x05395808) /* 0.326499970 */, 18 }, /* 5005 */ { MAD_F(0x0539b342) /* 0.326586970 */, 18 }, /* 5006 */ { MAD_F(0x053a0e7d) /* 0.326673976 */, 18 }, /* 5007 */ { MAD_F(0x053a69ba) /* 0.326760988 */, 18 }, /* 5008 */ { MAD_F(0x053ac4f9) /* 0.326848005 */, 18 }, /* 5009 */ { MAD_F(0x053b2039) /* 0.326935028 */, 18 }, /* 5010 */ { MAD_F(0x053b7b7b) /* 0.327022057 */, 18 }, /* 5011 */ { MAD_F(0x053bd6be) /* 0.327109092 */, 18 }, /* 5012 */ { MAD_F(0x053c3203) /* 0.327196132 */, 18 }, /* 5013 */ { MAD_F(0x053c8d49) /* 0.327283178 */, 18 }, /* 5014 */ { MAD_F(0x053ce891) /* 0.327370231 */, 18 }, /* 5015 */ { MAD_F(0x053d43da) /* 0.327457288 */, 18 }, /* 5016 */ { MAD_F(0x053d9f25) /* 0.327544352 */, 18 }, /* 5017 */ { MAD_F(0x053dfa72) /* 0.327631421 */, 18 }, /* 5018 */ { MAD_F(0x053e55c0) /* 0.327718497 */, 18 }, /* 5019 */ { MAD_F(0x053eb10f) /* 0.327805578 */, 18 }, /* 5020 */ { MAD_F(0x053f0c61) /* 0.327892665 */, 18 }, /* 5021 */ { MAD_F(0x053f67b3) /* 0.327979757 */, 18 }, /* 5022 */ { MAD_F(0x053fc308) /* 0.328066855 */, 18 }, /* 5023 */ { MAD_F(0x05401e5e) /* 0.328153960 */, 18 }, /* 5024 */ { MAD_F(0x054079b5) /* 0.328241070 */, 18 }, /* 5025 */ { MAD_F(0x0540d50e) /* 0.328328185 */, 18 }, /* 5026 */ { MAD_F(0x05413068) /* 0.328415307 */, 18 }, /* 5027 */ { MAD_F(0x05418bc4) /* 0.328502434 */, 18 }, /* 5028 */ { MAD_F(0x0541e722) /* 0.328589567 */, 18 }, /* 5029 */ { MAD_F(0x05424281) /* 0.328676706 */, 18 }, /* 5030 */ { MAD_F(0x05429de2) /* 0.328763850 */, 18 }, /* 5031 */ { MAD_F(0x0542f944) /* 0.328851001 */, 18 }, /* 5032 */ { MAD_F(0x054354a8) /* 0.328938157 */, 18 }, /* 5033 */ { MAD_F(0x0543b00d) /* 0.329025319 */, 18 }, /* 5034 */ { MAD_F(0x05440b74) /* 0.329112486 */, 18 }, /* 5035 */ { MAD_F(0x054466dd) /* 0.329199660 */, 18 }, /* 5036 */ { MAD_F(0x0544c247) /* 0.329286839 */, 18 }, /* 5037 */ { MAD_F(0x05451db2) /* 0.329374024 */, 18 }, /* 5038 */ { MAD_F(0x0545791f) /* 0.329461215 */, 18 }, /* 5039 */ { MAD_F(0x0545d48e) /* 0.329548411 */, 18 }, /* 5040 */ { MAD_F(0x05462ffe) /* 0.329635614 */, 18 }, /* 5041 */ { MAD_F(0x05468b70) /* 0.329722822 */, 18 }, /* 5042 */ { MAD_F(0x0546e6e3) /* 0.329810036 */, 18 }, /* 5043 */ { MAD_F(0x05474258) /* 0.329897255 */, 18 }, /* 5044 */ { MAD_F(0x05479dce) /* 0.329984481 */, 18 }, /* 5045 */ { MAD_F(0x0547f946) /* 0.330071712 */, 18 }, /* 5046 */ { MAD_F(0x054854c0) /* 0.330158949 */, 18 }, /* 5047 */ { MAD_F(0x0548b03b) /* 0.330246191 */, 18 }, /* 5048 */ { MAD_F(0x05490bb7) /* 0.330333440 */, 18 }, /* 5049 */ { MAD_F(0x05496735) /* 0.330420694 */, 18 }, /* 5050 */ { MAD_F(0x0549c2b5) /* 0.330507954 */, 18 }, /* 5051 */ { MAD_F(0x054a1e36) /* 0.330595220 */, 18 }, /* 5052 */ { MAD_F(0x054a79b9) /* 0.330682491 */, 18 }, /* 5053 */ { MAD_F(0x054ad53d) /* 0.330769768 */, 18 }, /* 5054 */ { MAD_F(0x054b30c3) /* 0.330857051 */, 18 }, /* 5055 */ { MAD_F(0x054b8c4b) /* 0.330944340 */, 18 }, /* 5056 */ { MAD_F(0x054be7d4) /* 0.331031635 */, 18 }, /* 5057 */ { MAD_F(0x054c435e) /* 0.331118935 */, 18 }, /* 5058 */ { MAD_F(0x054c9eea) /* 0.331206241 */, 18 }, /* 5059 */ { MAD_F(0x054cfa78) /* 0.331293553 */, 18 }, /* 5060 */ { MAD_F(0x054d5607) /* 0.331380870 */, 18 }, /* 5061 */ { MAD_F(0x054db197) /* 0.331468193 */, 18 }, /* 5062 */ { MAD_F(0x054e0d2a) /* 0.331555522 */, 18 }, /* 5063 */ { MAD_F(0x054e68bd) /* 0.331642857 */, 18 }, /* 5064 */ { MAD_F(0x054ec453) /* 0.331730198 */, 18 }, /* 5065 */ { MAD_F(0x054f1fe9) /* 0.331817544 */, 18 }, /* 5066 */ { MAD_F(0x054f7b82) /* 0.331904896 */, 18 }, /* 5067 */ { MAD_F(0x054fd71c) /* 0.331992254 */, 18 }, /* 5068 */ { MAD_F(0x055032b7) /* 0.332079617 */, 18 }, /* 5069 */ { MAD_F(0x05508e54) /* 0.332166986 */, 18 }, /* 5070 */ { MAD_F(0x0550e9f3) /* 0.332254361 */, 18 }, /* 5071 */ { MAD_F(0x05514593) /* 0.332341742 */, 18 }, /* 5072 */ { MAD_F(0x0551a134) /* 0.332429129 */, 18 }, /* 5073 */ { MAD_F(0x0551fcd8) /* 0.332516521 */, 18 }, /* 5074 */ { MAD_F(0x0552587c) /* 0.332603919 */, 18 }, /* 5075 */ { MAD_F(0x0552b423) /* 0.332691323 */, 18 }, /* 5076 */ { MAD_F(0x05530fca) /* 0.332778732 */, 18 }, /* 5077 */ { MAD_F(0x05536b74) /* 0.332866147 */, 18 }, /* 5078 */ { MAD_F(0x0553c71f) /* 0.332953568 */, 18 }, /* 5079 */ { MAD_F(0x055422cb) /* 0.333040995 */, 18 }, /* 5080 */ { MAD_F(0x05547e79) /* 0.333128427 */, 18 }, /* 5081 */ { MAD_F(0x0554da29) /* 0.333215865 */, 18 }, /* 5082 */ { MAD_F(0x055535da) /* 0.333303309 */, 18 }, /* 5083 */ { MAD_F(0x0555918c) /* 0.333390759 */, 18 }, /* 5084 */ { MAD_F(0x0555ed40) /* 0.333478214 */, 18 }, /* 5085 */ { MAD_F(0x055648f6) /* 0.333565675 */, 18 }, /* 5086 */ { MAD_F(0x0556a4ad) /* 0.333653142 */, 18 }, /* 5087 */ { MAD_F(0x05570066) /* 0.333740615 */, 18 }, /* 5088 */ { MAD_F(0x05575c20) /* 0.333828093 */, 18 }, /* 5089 */ { MAD_F(0x0557b7dc) /* 0.333915577 */, 18 }, /* 5090 */ { MAD_F(0x05581399) /* 0.334003067 */, 18 }, /* 5091 */ { MAD_F(0x05586f58) /* 0.334090562 */, 18 }, /* 5092 */ { MAD_F(0x0558cb19) /* 0.334178063 */, 18 }, /* 5093 */ { MAD_F(0x055926db) /* 0.334265570 */, 18 }, /* 5094 */ { MAD_F(0x0559829e) /* 0.334353083 */, 18 }, /* 5095 */ { MAD_F(0x0559de63) /* 0.334440601 */, 18 }, /* 5096 */ { MAD_F(0x055a3a2a) /* 0.334528126 */, 18 }, /* 5097 */ { MAD_F(0x055a95f2) /* 0.334615655 */, 18 }, /* 5098 */ { MAD_F(0x055af1bb) /* 0.334703191 */, 18 }, /* 5099 */ { MAD_F(0x055b4d87) /* 0.334790732 */, 18 }, /* 5100 */ { MAD_F(0x055ba953) /* 0.334878279 */, 18 }, /* 5101 */ { MAD_F(0x055c0522) /* 0.334965832 */, 18 }, /* 5102 */ { MAD_F(0x055c60f1) /* 0.335053391 */, 18 }, /* 5103 */ { MAD_F(0x055cbcc3) /* 0.335140955 */, 18 }, /* 5104 */ { MAD_F(0x055d1896) /* 0.335228525 */, 18 }, /* 5105 */ { MAD_F(0x055d746a) /* 0.335316100 */, 18 }, /* 5106 */ { MAD_F(0x055dd040) /* 0.335403682 */, 18 }, /* 5107 */ { MAD_F(0x055e2c17) /* 0.335491269 */, 18 }, /* 5108 */ { MAD_F(0x055e87f0) /* 0.335578861 */, 18 }, /* 5109 */ { MAD_F(0x055ee3cb) /* 0.335666460 */, 18 }, /* 5110 */ { MAD_F(0x055f3fa7) /* 0.335754064 */, 18 }, /* 5111 */ { MAD_F(0x055f9b85) /* 0.335841674 */, 18 }, /* 5112 */ { MAD_F(0x055ff764) /* 0.335929290 */, 18 }, /* 5113 */ { MAD_F(0x05605344) /* 0.336016911 */, 18 }, /* 5114 */ { MAD_F(0x0560af27) /* 0.336104538 */, 18 }, /* 5115 */ { MAD_F(0x05610b0a) /* 0.336192171 */, 18 }, /* 5116 */ { MAD_F(0x056166f0) /* 0.336279809 */, 18 }, /* 5117 */ { MAD_F(0x0561c2d7) /* 0.336367453 */, 18 }, /* 5118 */ { MAD_F(0x05621ebf) /* 0.336455103 */, 18 }, /* 5119 */ { MAD_F(0x05627aa9) /* 0.336542759 */, 18 }, /* 5120 */ { MAD_F(0x0562d694) /* 0.336630420 */, 18 }, /* 5121 */ { MAD_F(0x05633281) /* 0.336718087 */, 18 }, /* 5122 */ { MAD_F(0x05638e70) /* 0.336805760 */, 18 }, /* 5123 */ { MAD_F(0x0563ea60) /* 0.336893439 */, 18 }, /* 5124 */ { MAD_F(0x05644651) /* 0.336981123 */, 18 }, /* 5125 */ { MAD_F(0x0564a244) /* 0.337068813 */, 18 }, /* 5126 */ { MAD_F(0x0564fe39) /* 0.337156508 */, 18 }, /* 5127 */ { MAD_F(0x05655a2f) /* 0.337244209 */, 18 }, /* 5128 */ { MAD_F(0x0565b627) /* 0.337331916 */, 18 }, /* 5129 */ { MAD_F(0x05661220) /* 0.337419629 */, 18 }, /* 5130 */ { MAD_F(0x05666e1a) /* 0.337507347 */, 18 }, /* 5131 */ { MAD_F(0x0566ca17) /* 0.337595071 */, 18 }, /* 5132 */ { MAD_F(0x05672614) /* 0.337682801 */, 18 }, /* 5133 */ { MAD_F(0x05678214) /* 0.337770537 */, 18 }, /* 5134 */ { MAD_F(0x0567de15) /* 0.337858278 */, 18 }, /* 5135 */ { MAD_F(0x05683a17) /* 0.337946025 */, 18 }, /* 5136 */ { MAD_F(0x0568961b) /* 0.338033777 */, 18 }, /* 5137 */ { MAD_F(0x0568f220) /* 0.338121535 */, 18 }, /* 5138 */ { MAD_F(0x05694e27) /* 0.338209299 */, 18 }, /* 5139 */ { MAD_F(0x0569aa30) /* 0.338297069 */, 18 }, /* 5140 */ { MAD_F(0x056a063a) /* 0.338384844 */, 18 }, /* 5141 */ { MAD_F(0x056a6245) /* 0.338472625 */, 18 }, /* 5142 */ { MAD_F(0x056abe52) /* 0.338560412 */, 18 }, /* 5143 */ { MAD_F(0x056b1a61) /* 0.338648204 */, 18 }, /* 5144 */ { MAD_F(0x056b7671) /* 0.338736002 */, 18 }, /* 5145 */ { MAD_F(0x056bd283) /* 0.338823806 */, 18 }, /* 5146 */ { MAD_F(0x056c2e96) /* 0.338911616 */, 18 }, /* 5147 */ { MAD_F(0x056c8aab) /* 0.338999431 */, 18 }, /* 5148 */ { MAD_F(0x056ce6c1) /* 0.339087252 */, 18 }, /* 5149 */ { MAD_F(0x056d42d9) /* 0.339175078 */, 18 }, /* 5150 */ { MAD_F(0x056d9ef2) /* 0.339262910 */, 18 }, /* 5151 */ { MAD_F(0x056dfb0d) /* 0.339350748 */, 18 }, /* 5152 */ { MAD_F(0x056e5729) /* 0.339438592 */, 18 }, /* 5153 */ { MAD_F(0x056eb347) /* 0.339526441 */, 18 }, /* 5154 */ { MAD_F(0x056f0f66) /* 0.339614296 */, 18 }, /* 5155 */ { MAD_F(0x056f6b87) /* 0.339702157 */, 18 }, /* 5156 */ { MAD_F(0x056fc7aa) /* 0.339790023 */, 18 }, /* 5157 */ { MAD_F(0x057023cd) /* 0.339877895 */, 18 }, /* 5158 */ { MAD_F(0x05707ff3) /* 0.339965773 */, 18 }, /* 5159 */ { MAD_F(0x0570dc1a) /* 0.340053656 */, 18 }, /* 5160 */ { MAD_F(0x05713843) /* 0.340141545 */, 18 }, /* 5161 */ { MAD_F(0x0571946d) /* 0.340229440 */, 18 }, /* 5162 */ { MAD_F(0x0571f098) /* 0.340317340 */, 18 }, /* 5163 */ { MAD_F(0x05724cc5) /* 0.340405246 */, 18 }, /* 5164 */ { MAD_F(0x0572a8f4) /* 0.340493158 */, 18 }, /* 5165 */ { MAD_F(0x05730524) /* 0.340581075 */, 18 }, /* 5166 */ { MAD_F(0x05736156) /* 0.340668999 */, 18 }, /* 5167 */ { MAD_F(0x0573bd89) /* 0.340756927 */, 18 }, /* 5168 */ { MAD_F(0x057419be) /* 0.340844862 */, 18 }, /* 5169 */ { MAD_F(0x057475f4) /* 0.340932802 */, 18 }, /* 5170 */ { MAD_F(0x0574d22c) /* 0.341020748 */, 18 }, /* 5171 */ { MAD_F(0x05752e65) /* 0.341108699 */, 18 }, /* 5172 */ { MAD_F(0x05758aa0) /* 0.341196656 */, 18 }, /* 5173 */ { MAD_F(0x0575e6dc) /* 0.341284619 */, 18 }, /* 5174 */ { MAD_F(0x0576431a) /* 0.341372587 */, 18 }, /* 5175 */ { MAD_F(0x05769f59) /* 0.341460562 */, 18 }, /* 5176 */ { MAD_F(0x0576fb9a) /* 0.341548541 */, 18 }, /* 5177 */ { MAD_F(0x057757dd) /* 0.341636527 */, 18 }, /* 5178 */ { MAD_F(0x0577b421) /* 0.341724518 */, 18 }, /* 5179 */ { MAD_F(0x05781066) /* 0.341812515 */, 18 }, /* 5180 */ { MAD_F(0x05786cad) /* 0.341900517 */, 18 }, /* 5181 */ { MAD_F(0x0578c8f5) /* 0.341988525 */, 18 }, /* 5182 */ { MAD_F(0x0579253f) /* 0.342076539 */, 18 }, /* 5183 */ { MAD_F(0x0579818b) /* 0.342164558 */, 18 }, /* 5184 */ { MAD_F(0x0579ddd8) /* 0.342252584 */, 18 }, /* 5185 */ { MAD_F(0x057a3a27) /* 0.342340614 */, 18 }, /* 5186 */ { MAD_F(0x057a9677) /* 0.342428651 */, 18 }, /* 5187 */ { MAD_F(0x057af2c8) /* 0.342516693 */, 18 }, /* 5188 */ { MAD_F(0x057b4f1c) /* 0.342604741 */, 18 }, /* 5189 */ { MAD_F(0x057bab70) /* 0.342692794 */, 18 }, /* 5190 */ { MAD_F(0x057c07c6) /* 0.342780853 */, 18 }, /* 5191 */ { MAD_F(0x057c641e) /* 0.342868918 */, 18 }, /* 5192 */ { MAD_F(0x057cc077) /* 0.342956988 */, 18 }, /* 5193 */ { MAD_F(0x057d1cd2) /* 0.343045064 */, 18 }, /* 5194 */ { MAD_F(0x057d792e) /* 0.343133146 */, 18 }, /* 5195 */ { MAD_F(0x057dd58c) /* 0.343221233 */, 18 }, /* 5196 */ { MAD_F(0x057e31eb) /* 0.343309326 */, 18 }, /* 5197 */ { MAD_F(0x057e8e4c) /* 0.343397425 */, 18 }, /* 5198 */ { MAD_F(0x057eeaae) /* 0.343485529 */, 18 }, /* 5199 */ { MAD_F(0x057f4712) /* 0.343573639 */, 18 }, /* 5200 */ { MAD_F(0x057fa378) /* 0.343661754 */, 18 }, /* 5201 */ { MAD_F(0x057fffde) /* 0.343749876 */, 18 }, /* 5202 */ { MAD_F(0x05805c47) /* 0.343838003 */, 18 }, /* 5203 */ { MAD_F(0x0580b8b1) /* 0.343926135 */, 18 }, /* 5204 */ { MAD_F(0x0581151c) /* 0.344014273 */, 18 }, /* 5205 */ { MAD_F(0x05817189) /* 0.344102417 */, 18 }, /* 5206 */ { MAD_F(0x0581cdf7) /* 0.344190566 */, 18 }, /* 5207 */ { MAD_F(0x05822a67) /* 0.344278722 */, 18 }, /* 5208 */ { MAD_F(0x058286d9) /* 0.344366882 */, 18 }, /* 5209 */ { MAD_F(0x0582e34c) /* 0.344455049 */, 18 }, /* 5210 */ { MAD_F(0x05833fc0) /* 0.344543221 */, 18 }, /* 5211 */ { MAD_F(0x05839c36) /* 0.344631398 */, 18 }, /* 5212 */ { MAD_F(0x0583f8ae) /* 0.344719582 */, 18 }, /* 5213 */ { MAD_F(0x05845527) /* 0.344807771 */, 18 }, /* 5214 */ { MAD_F(0x0584b1a1) /* 0.344895965 */, 18 }, /* 5215 */ { MAD_F(0x05850e1e) /* 0.344984165 */, 18 }, /* 5216 */ { MAD_F(0x05856a9b) /* 0.345072371 */, 18 }, /* 5217 */ { MAD_F(0x0585c71a) /* 0.345160583 */, 18 }, /* 5218 */ { MAD_F(0x0586239b) /* 0.345248800 */, 18 }, /* 5219 */ { MAD_F(0x0586801d) /* 0.345337023 */, 18 }, /* 5220 */ { MAD_F(0x0586dca1) /* 0.345425251 */, 18 }, /* 5221 */ { MAD_F(0x05873926) /* 0.345513485 */, 18 }, /* 5222 */ { MAD_F(0x058795ac) /* 0.345601725 */, 18 }, /* 5223 */ { MAD_F(0x0587f235) /* 0.345689970 */, 18 }, /* 5224 */ { MAD_F(0x05884ebe) /* 0.345778221 */, 18 }, /* 5225 */ { MAD_F(0x0588ab49) /* 0.345866478 */, 18 }, /* 5226 */ { MAD_F(0x058907d6) /* 0.345954740 */, 18 }, /* 5227 */ { MAD_F(0x05896464) /* 0.346043008 */, 18 }, /* 5228 */ { MAD_F(0x0589c0f4) /* 0.346131281 */, 18 }, /* 5229 */ { MAD_F(0x058a1d85) /* 0.346219560 */, 18 }, /* 5230 */ { MAD_F(0x058a7a18) /* 0.346307845 */, 18 }, /* 5231 */ { MAD_F(0x058ad6ac) /* 0.346396135 */, 18 }, /* 5232 */ { MAD_F(0x058b3342) /* 0.346484431 */, 18 }, /* 5233 */ { MAD_F(0x058b8fd9) /* 0.346572733 */, 18 }, /* 5234 */ { MAD_F(0x058bec72) /* 0.346661040 */, 18 }, /* 5235 */ { MAD_F(0x058c490c) /* 0.346749353 */, 18 }, /* 5236 */ { MAD_F(0x058ca5a8) /* 0.346837671 */, 18 }, /* 5237 */ { MAD_F(0x058d0246) /* 0.346925996 */, 18 }, /* 5238 */ { MAD_F(0x058d5ee4) /* 0.347014325 */, 18 }, /* 5239 */ { MAD_F(0x058dbb85) /* 0.347102661 */, 18 }, /* 5240 */ { MAD_F(0x058e1827) /* 0.347191002 */, 18 }, /* 5241 */ { MAD_F(0x058e74ca) /* 0.347279348 */, 18 }, /* 5242 */ { MAD_F(0x058ed16f) /* 0.347367700 */, 18 }, /* 5243 */ { MAD_F(0x058f2e15) /* 0.347456058 */, 18 }, /* 5244 */ { MAD_F(0x058f8abd) /* 0.347544422 */, 18 }, /* 5245 */ { MAD_F(0x058fe766) /* 0.347632791 */, 18 }, /* 5246 */ { MAD_F(0x05904411) /* 0.347721165 */, 18 }, /* 5247 */ { MAD_F(0x0590a0be) /* 0.347809546 */, 18 }, /* 5248 */ { MAD_F(0x0590fd6c) /* 0.347897931 */, 18 }, /* 5249 */ { MAD_F(0x05915a1b) /* 0.347986323 */, 18 }, /* 5250 */ { MAD_F(0x0591b6cc) /* 0.348074720 */, 18 }, /* 5251 */ { MAD_F(0x0592137e) /* 0.348163123 */, 18 }, /* 5252 */ { MAD_F(0x05927032) /* 0.348251531 */, 18 }, /* 5253 */ { MAD_F(0x0592cce8) /* 0.348339945 */, 18 }, /* 5254 */ { MAD_F(0x0593299f) /* 0.348428365 */, 18 }, /* 5255 */ { MAD_F(0x05938657) /* 0.348516790 */, 18 }, /* 5256 */ { MAD_F(0x0593e311) /* 0.348605221 */, 18 }, /* 5257 */ { MAD_F(0x05943fcd) /* 0.348693657 */, 18 }, /* 5258 */ { MAD_F(0x05949c8a) /* 0.348782099 */, 18 }, /* 5259 */ { MAD_F(0x0594f948) /* 0.348870547 */, 18 }, /* 5260 */ { MAD_F(0x05955608) /* 0.348959000 */, 18 }, /* 5261 */ { MAD_F(0x0595b2ca) /* 0.349047459 */, 18 }, /* 5262 */ { MAD_F(0x05960f8c) /* 0.349135923 */, 18 }, /* 5263 */ { MAD_F(0x05966c51) /* 0.349224393 */, 18 }, /* 5264 */ { MAD_F(0x0596c917) /* 0.349312869 */, 18 }, /* 5265 */ { MAD_F(0x059725de) /* 0.349401350 */, 18 }, /* 5266 */ { MAD_F(0x059782a7) /* 0.349489837 */, 18 }, /* 5267 */ { MAD_F(0x0597df72) /* 0.349578329 */, 18 }, /* 5268 */ { MAD_F(0x05983c3e) /* 0.349666827 */, 18 }, /* 5269 */ { MAD_F(0x0598990c) /* 0.349755331 */, 18 }, /* 5270 */ { MAD_F(0x0598f5db) /* 0.349843840 */, 18 }, /* 5271 */ { MAD_F(0x059952ab) /* 0.349932355 */, 18 }, /* 5272 */ { MAD_F(0x0599af7d) /* 0.350020876 */, 18 }, /* 5273 */ { MAD_F(0x059a0c51) /* 0.350109402 */, 18 }, /* 5274 */ { MAD_F(0x059a6926) /* 0.350197933 */, 18 }, /* 5275 */ { MAD_F(0x059ac5fc) /* 0.350286470 */, 18 }, /* 5276 */ { MAD_F(0x059b22d4) /* 0.350375013 */, 18 }, /* 5277 */ { MAD_F(0x059b7fae) /* 0.350463562 */, 18 }, /* 5278 */ { MAD_F(0x059bdc89) /* 0.350552116 */, 18 }, /* 5279 */ { MAD_F(0x059c3965) /* 0.350640675 */, 18 }, /* 5280 */ { MAD_F(0x059c9643) /* 0.350729240 */, 18 }, /* 5281 */ { MAD_F(0x059cf323) /* 0.350817811 */, 18 }, /* 5282 */ { MAD_F(0x059d5004) /* 0.350906388 */, 18 }, /* 5283 */ { MAD_F(0x059dace6) /* 0.350994970 */, 18 }, /* 5284 */ { MAD_F(0x059e09cb) /* 0.351083557 */, 18 }, /* 5285 */ { MAD_F(0x059e66b0) /* 0.351172150 */, 18 }, /* 5286 */ { MAD_F(0x059ec397) /* 0.351260749 */, 18 }, /* 5287 */ { MAD_F(0x059f2080) /* 0.351349353 */, 18 }, /* 5288 */ { MAD_F(0x059f7d6a) /* 0.351437963 */, 18 }, /* 5289 */ { MAD_F(0x059fda55) /* 0.351526579 */, 18 }, /* 5290 */ { MAD_F(0x05a03742) /* 0.351615200 */, 18 }, /* 5291 */ { MAD_F(0x05a09431) /* 0.351703827 */, 18 }, /* 5292 */ { MAD_F(0x05a0f121) /* 0.351792459 */, 18 }, /* 5293 */ { MAD_F(0x05a14e12) /* 0.351881097 */, 18 }, /* 5294 */ { MAD_F(0x05a1ab05) /* 0.351969740 */, 18 }, /* 5295 */ { MAD_F(0x05a207fa) /* 0.352058389 */, 18 }, /* 5296 */ { MAD_F(0x05a264f0) /* 0.352147044 */, 18 }, /* 5297 */ { MAD_F(0x05a2c1e7) /* 0.352235704 */, 18 }, /* 5298 */ { MAD_F(0x05a31ee1) /* 0.352324369 */, 18 }, /* 5299 */ { MAD_F(0x05a37bdb) /* 0.352413041 */, 18 }, /* 5300 */ { MAD_F(0x05a3d8d7) /* 0.352501718 */, 18 }, /* 5301 */ { MAD_F(0x05a435d5) /* 0.352590400 */, 18 }, /* 5302 */ { MAD_F(0x05a492d4) /* 0.352679088 */, 18 }, /* 5303 */ { MAD_F(0x05a4efd4) /* 0.352767782 */, 18 }, /* 5304 */ { MAD_F(0x05a54cd6) /* 0.352856481 */, 18 }, /* 5305 */ { MAD_F(0x05a5a9da) /* 0.352945186 */, 18 }, /* 5306 */ { MAD_F(0x05a606df) /* 0.353033896 */, 18 }, /* 5307 */ { MAD_F(0x05a663e5) /* 0.353122612 */, 18 }, /* 5308 */ { MAD_F(0x05a6c0ed) /* 0.353211333 */, 18 }, /* 5309 */ { MAD_F(0x05a71df7) /* 0.353300061 */, 18 }, /* 5310 */ { MAD_F(0x05a77b02) /* 0.353388793 */, 18 }, /* 5311 */ { MAD_F(0x05a7d80e) /* 0.353477531 */, 18 }, /* 5312 */ { MAD_F(0x05a8351c) /* 0.353566275 */, 18 }, /* 5313 */ { MAD_F(0x05a8922c) /* 0.353655024 */, 18 }, /* 5314 */ { MAD_F(0x05a8ef3c) /* 0.353743779 */, 18 }, /* 5315 */ { MAD_F(0x05a94c4f) /* 0.353832540 */, 18 }, /* 5316 */ { MAD_F(0x05a9a963) /* 0.353921306 */, 18 }, /* 5317 */ { MAD_F(0x05aa0678) /* 0.354010077 */, 18 }, /* 5318 */ { MAD_F(0x05aa638f) /* 0.354098855 */, 18 }, /* 5319 */ { MAD_F(0x05aac0a8) /* 0.354187637 */, 18 }, /* 5320 */ { MAD_F(0x05ab1dc2) /* 0.354276426 */, 18 }, /* 5321 */ { MAD_F(0x05ab7add) /* 0.354365220 */, 18 }, /* 5322 */ { MAD_F(0x05abd7fa) /* 0.354454019 */, 18 }, /* 5323 */ { MAD_F(0x05ac3518) /* 0.354542824 */, 18 }, /* 5324 */ { MAD_F(0x05ac9238) /* 0.354631635 */, 18 }, /* 5325 */ { MAD_F(0x05acef5a) /* 0.354720451 */, 18 }, /* 5326 */ { MAD_F(0x05ad4c7d) /* 0.354809272 */, 18 }, /* 5327 */ { MAD_F(0x05ada9a1) /* 0.354898100 */, 18 }, /* 5328 */ { MAD_F(0x05ae06c7) /* 0.354986932 */, 18 }, /* 5329 */ { MAD_F(0x05ae63ee) /* 0.355075771 */, 18 }, /* 5330 */ { MAD_F(0x05aec117) /* 0.355164615 */, 18 }, /* 5331 */ { MAD_F(0x05af1e41) /* 0.355253464 */, 18 }, /* 5332 */ { MAD_F(0x05af7b6d) /* 0.355342319 */, 18 }, /* 5333 */ { MAD_F(0x05afd89b) /* 0.355431180 */, 18 }, /* 5334 */ { MAD_F(0x05b035c9) /* 0.355520046 */, 18 }, /* 5335 */ { MAD_F(0x05b092fa) /* 0.355608917 */, 18 }, /* 5336 */ { MAD_F(0x05b0f02b) /* 0.355697795 */, 18 }, /* 5337 */ { MAD_F(0x05b14d5f) /* 0.355786677 */, 18 }, /* 5338 */ { MAD_F(0x05b1aa94) /* 0.355875566 */, 18 }, /* 5339 */ { MAD_F(0x05b207ca) /* 0.355964460 */, 18 }, /* 5340 */ { MAD_F(0x05b26502) /* 0.356053359 */, 18 }, /* 5341 */ { MAD_F(0x05b2c23b) /* 0.356142264 */, 18 }, /* 5342 */ { MAD_F(0x05b31f76) /* 0.356231175 */, 18 }, /* 5343 */ { MAD_F(0x05b37cb2) /* 0.356320091 */, 18 }, /* 5344 */ { MAD_F(0x05b3d9f0) /* 0.356409012 */, 18 }, /* 5345 */ { MAD_F(0x05b4372f) /* 0.356497940 */, 18 }, /* 5346 */ { MAD_F(0x05b4946f) /* 0.356586872 */, 18 }, /* 5347 */ { MAD_F(0x05b4f1b2) /* 0.356675811 */, 18 }, /* 5348 */ { MAD_F(0x05b54ef5) /* 0.356764754 */, 18 }, /* 5349 */ { MAD_F(0x05b5ac3a) /* 0.356853704 */, 18 }, /* 5350 */ { MAD_F(0x05b60981) /* 0.356942659 */, 18 }, /* 5351 */ { MAD_F(0x05b666c9) /* 0.357031619 */, 18 }, /* 5352 */ { MAD_F(0x05b6c413) /* 0.357120585 */, 18 }, /* 5353 */ { MAD_F(0x05b7215e) /* 0.357209557 */, 18 }, /* 5354 */ { MAD_F(0x05b77eab) /* 0.357298534 */, 18 }, /* 5355 */ { MAD_F(0x05b7dbf9) /* 0.357387516 */, 18 }, /* 5356 */ { MAD_F(0x05b83948) /* 0.357476504 */, 18 }, /* 5357 */ { MAD_F(0x05b89699) /* 0.357565498 */, 18 }, /* 5358 */ { MAD_F(0x05b8f3ec) /* 0.357654497 */, 18 }, /* 5359 */ { MAD_F(0x05b95140) /* 0.357743502 */, 18 }, /* 5360 */ { MAD_F(0x05b9ae95) /* 0.357832512 */, 18 }, /* 5361 */ { MAD_F(0x05ba0bec) /* 0.357921528 */, 18 }, /* 5362 */ { MAD_F(0x05ba6945) /* 0.358010550 */, 18 }, /* 5363 */ { MAD_F(0x05bac69f) /* 0.358099576 */, 18 }, /* 5364 */ { MAD_F(0x05bb23fa) /* 0.358188609 */, 18 }, /* 5365 */ { MAD_F(0x05bb8157) /* 0.358277647 */, 18 }, /* 5366 */ { MAD_F(0x05bbdeb6) /* 0.358366690 */, 18 }, /* 5367 */ { MAD_F(0x05bc3c16) /* 0.358455739 */, 18 }, /* 5368 */ { MAD_F(0x05bc9977) /* 0.358544794 */, 18 }, /* 5369 */ { MAD_F(0x05bcf6da) /* 0.358633854 */, 18 }, /* 5370 */ { MAD_F(0x05bd543e) /* 0.358722920 */, 18 }, /* 5371 */ { MAD_F(0x05bdb1a4) /* 0.358811991 */, 18 }, /* 5372 */ { MAD_F(0x05be0f0b) /* 0.358901067 */, 18 }, /* 5373 */ { MAD_F(0x05be6c74) /* 0.358990150 */, 18 }, /* 5374 */ { MAD_F(0x05bec9df) /* 0.359079237 */, 18 }, /* 5375 */ { MAD_F(0x05bf274a) /* 0.359168331 */, 18 }, /* 5376 */ { MAD_F(0x05bf84b8) /* 0.359257429 */, 18 }, /* 5377 */ { MAD_F(0x05bfe226) /* 0.359346534 */, 18 }, /* 5378 */ { MAD_F(0x05c03f97) /* 0.359435644 */, 18 }, /* 5379 */ { MAD_F(0x05c09d08) /* 0.359524759 */, 18 }, /* 5380 */ { MAD_F(0x05c0fa7c) /* 0.359613880 */, 18 }, /* 5381 */ { MAD_F(0x05c157f0) /* 0.359703006 */, 18 }, /* 5382 */ { MAD_F(0x05c1b566) /* 0.359792138 */, 18 }, /* 5383 */ { MAD_F(0x05c212de) /* 0.359881276 */, 18 }, /* 5384 */ { MAD_F(0x05c27057) /* 0.359970419 */, 18 }, /* 5385 */ { MAD_F(0x05c2cdd2) /* 0.360059567 */, 18 }, /* 5386 */ { MAD_F(0x05c32b4e) /* 0.360148721 */, 18 }, /* 5387 */ { MAD_F(0x05c388cb) /* 0.360237881 */, 18 }, /* 5388 */ { MAD_F(0x05c3e64b) /* 0.360327046 */, 18 }, /* 5389 */ { MAD_F(0x05c443cb) /* 0.360416216 */, 18 }, /* 5390 */ { MAD_F(0x05c4a14d) /* 0.360505392 */, 18 }, /* 5391 */ { MAD_F(0x05c4fed1) /* 0.360594574 */, 18 }, /* 5392 */ { MAD_F(0x05c55c56) /* 0.360683761 */, 18 }, /* 5393 */ { MAD_F(0x05c5b9dc) /* 0.360772953 */, 18 }, /* 5394 */ { MAD_F(0x05c61764) /* 0.360862152 */, 18 }, /* 5395 */ { MAD_F(0x05c674ed) /* 0.360951355 */, 18 }, /* 5396 */ { MAD_F(0x05c6d278) /* 0.361040564 */, 18 }, /* 5397 */ { MAD_F(0x05c73005) /* 0.361129779 */, 18 }, /* 5398 */ { MAD_F(0x05c78d93) /* 0.361218999 */, 18 }, /* 5399 */ { MAD_F(0x05c7eb22) /* 0.361308225 */, 18 }, /* 5400 */ { MAD_F(0x05c848b3) /* 0.361397456 */, 18 }, /* 5401 */ { MAD_F(0x05c8a645) /* 0.361486693 */, 18 }, /* 5402 */ { MAD_F(0x05c903d9) /* 0.361575935 */, 18 }, /* 5403 */ { MAD_F(0x05c9616e) /* 0.361665183 */, 18 }, /* 5404 */ { MAD_F(0x05c9bf05) /* 0.361754436 */, 18 }, /* 5405 */ { MAD_F(0x05ca1c9d) /* 0.361843695 */, 18 }, /* 5406 */ { MAD_F(0x05ca7a37) /* 0.361932959 */, 18 }, /* 5407 */ { MAD_F(0x05cad7d2) /* 0.362022229 */, 18 }, /* 5408 */ { MAD_F(0x05cb356e) /* 0.362111504 */, 18 }, /* 5409 */ { MAD_F(0x05cb930d) /* 0.362200785 */, 18 }, /* 5410 */ { MAD_F(0x05cbf0ac) /* 0.362290071 */, 18 }, /* 5411 */ { MAD_F(0x05cc4e4d) /* 0.362379362 */, 18 }, /* 5412 */ { MAD_F(0x05ccabf0) /* 0.362468660 */, 18 }, /* 5413 */ { MAD_F(0x05cd0994) /* 0.362557962 */, 18 }, /* 5414 */ { MAD_F(0x05cd6739) /* 0.362647271 */, 18 }, /* 5415 */ { MAD_F(0x05cdc4e0) /* 0.362736584 */, 18 }, /* 5416 */ { MAD_F(0x05ce2289) /* 0.362825904 */, 18 }, /* 5417 */ { MAD_F(0x05ce8033) /* 0.362915228 */, 18 }, /* 5418 */ { MAD_F(0x05ceddde) /* 0.363004559 */, 18 }, /* 5419 */ { MAD_F(0x05cf3b8b) /* 0.363093894 */, 18 }, /* 5420 */ { MAD_F(0x05cf9939) /* 0.363183236 */, 18 }, /* 5421 */ { MAD_F(0x05cff6e9) /* 0.363272582 */, 18 }, /* 5422 */ { MAD_F(0x05d0549a) /* 0.363361935 */, 18 }, /* 5423 */ { MAD_F(0x05d0b24d) /* 0.363451292 */, 18 }, /* 5424 */ { MAD_F(0x05d11001) /* 0.363540655 */, 18 }, /* 5425 */ { MAD_F(0x05d16db7) /* 0.363630024 */, 18 }, /* 5426 */ { MAD_F(0x05d1cb6e) /* 0.363719398 */, 18 }, /* 5427 */ { MAD_F(0x05d22927) /* 0.363808778 */, 18 }, /* 5428 */ { MAD_F(0x05d286e1) /* 0.363898163 */, 18 }, /* 5429 */ { MAD_F(0x05d2e49d) /* 0.363987554 */, 18 }, /* 5430 */ { MAD_F(0x05d3425a) /* 0.364076950 */, 18 }, /* 5431 */ { MAD_F(0x05d3a018) /* 0.364166352 */, 18 }, /* 5432 */ { MAD_F(0x05d3fdd8) /* 0.364255759 */, 18 }, /* 5433 */ { MAD_F(0x05d45b9a) /* 0.364345171 */, 18 }, /* 5434 */ { MAD_F(0x05d4b95d) /* 0.364434589 */, 18 }, /* 5435 */ { MAD_F(0x05d51721) /* 0.364524013 */, 18 }, /* 5436 */ { MAD_F(0x05d574e7) /* 0.364613442 */, 18 }, /* 5437 */ { MAD_F(0x05d5d2af) /* 0.364702877 */, 18 }, /* 5438 */ { MAD_F(0x05d63078) /* 0.364792317 */, 18 }, /* 5439 */ { MAD_F(0x05d68e42) /* 0.364881762 */, 18 }, /* 5440 */ { MAD_F(0x05d6ec0e) /* 0.364971213 */, 18 }, /* 5441 */ { MAD_F(0x05d749db) /* 0.365060669 */, 18 }, /* 5442 */ { MAD_F(0x05d7a7aa) /* 0.365150131 */, 18 }, /* 5443 */ { MAD_F(0x05d8057a) /* 0.365239599 */, 18 }, /* 5444 */ { MAD_F(0x05d8634c) /* 0.365329072 */, 18 }, /* 5445 */ { MAD_F(0x05d8c11f) /* 0.365418550 */, 18 }, /* 5446 */ { MAD_F(0x05d91ef4) /* 0.365508034 */, 18 }, /* 5447 */ { MAD_F(0x05d97cca) /* 0.365597523 */, 18 }, /* 5448 */ { MAD_F(0x05d9daa1) /* 0.365687018 */, 18 }, /* 5449 */ { MAD_F(0x05da387a) /* 0.365776518 */, 18 }, /* 5450 */ { MAD_F(0x05da9655) /* 0.365866024 */, 18 }, /* 5451 */ { MAD_F(0x05daf431) /* 0.365955536 */, 18 }, /* 5452 */ { MAD_F(0x05db520e) /* 0.366045052 */, 18 }, /* 5453 */ { MAD_F(0x05dbafed) /* 0.366134574 */, 18 }, /* 5454 */ { MAD_F(0x05dc0dce) /* 0.366224102 */, 18 }, /* 5455 */ { MAD_F(0x05dc6baf) /* 0.366313635 */, 18 }, /* 5456 */ { MAD_F(0x05dcc993) /* 0.366403174 */, 18 }, /* 5457 */ { MAD_F(0x05dd2778) /* 0.366492718 */, 18 }, /* 5458 */ { MAD_F(0x05dd855e) /* 0.366582267 */, 18 }, /* 5459 */ { MAD_F(0x05dde346) /* 0.366671822 */, 18 }, /* 5460 */ { MAD_F(0x05de412f) /* 0.366761383 */, 18 }, /* 5461 */ { MAD_F(0x05de9f1a) /* 0.366850949 */, 18 }, /* 5462 */ { MAD_F(0x05defd06) /* 0.366940520 */, 18 }, /* 5463 */ { MAD_F(0x05df5af3) /* 0.367030097 */, 18 }, /* 5464 */ { MAD_F(0x05dfb8e2) /* 0.367119680 */, 18 }, /* 5465 */ { MAD_F(0x05e016d3) /* 0.367209267 */, 18 }, /* 5466 */ { MAD_F(0x05e074c5) /* 0.367298861 */, 18 }, /* 5467 */ { MAD_F(0x05e0d2b8) /* 0.367388459 */, 18 }, /* 5468 */ { MAD_F(0x05e130ad) /* 0.367478064 */, 18 }, /* 5469 */ { MAD_F(0x05e18ea4) /* 0.367567673 */, 18 }, /* 5470 */ { MAD_F(0x05e1ec9c) /* 0.367657288 */, 18 }, /* 5471 */ { MAD_F(0x05e24a95) /* 0.367746909 */, 18 }, /* 5472 */ { MAD_F(0x05e2a890) /* 0.367836535 */, 18 }, /* 5473 */ { MAD_F(0x05e3068c) /* 0.367926167 */, 18 }, /* 5474 */ { MAD_F(0x05e3648a) /* 0.368015804 */, 18 }, /* 5475 */ { MAD_F(0x05e3c289) /* 0.368105446 */, 18 }, /* 5476 */ { MAD_F(0x05e4208a) /* 0.368195094 */, 18 }, /* 5477 */ { MAD_F(0x05e47e8c) /* 0.368284747 */, 18 }, /* 5478 */ { MAD_F(0x05e4dc8f) /* 0.368374406 */, 18 }, /* 5479 */ { MAD_F(0x05e53a94) /* 0.368464070 */, 18 }, /* 5480 */ { MAD_F(0x05e5989b) /* 0.368553740 */, 18 }, /* 5481 */ { MAD_F(0x05e5f6a3) /* 0.368643415 */, 18 }, /* 5482 */ { MAD_F(0x05e654ac) /* 0.368733096 */, 18 }, /* 5483 */ { MAD_F(0x05e6b2b7) /* 0.368822782 */, 18 }, /* 5484 */ { MAD_F(0x05e710c4) /* 0.368912473 */, 18 }, /* 5485 */ { MAD_F(0x05e76ed2) /* 0.369002170 */, 18 }, /* 5486 */ { MAD_F(0x05e7cce1) /* 0.369091873 */, 18 }, /* 5487 */ { MAD_F(0x05e82af2) /* 0.369181581 */, 18 }, /* 5488 */ { MAD_F(0x05e88904) /* 0.369271294 */, 18 }, /* 5489 */ { MAD_F(0x05e8e718) /* 0.369361013 */, 18 }, /* 5490 */ { MAD_F(0x05e9452d) /* 0.369450737 */, 18 }, /* 5491 */ { MAD_F(0x05e9a343) /* 0.369540467 */, 18 }, /* 5492 */ { MAD_F(0x05ea015c) /* 0.369630202 */, 18 }, /* 5493 */ { MAD_F(0x05ea5f75) /* 0.369719942 */, 18 }, /* 5494 */ { MAD_F(0x05eabd90) /* 0.369809688 */, 18 }, /* 5495 */ { MAD_F(0x05eb1bad) /* 0.369899440 */, 18 }, /* 5496 */ { MAD_F(0x05eb79cb) /* 0.369989197 */, 18 }, /* 5497 */ { MAD_F(0x05ebd7ea) /* 0.370078959 */, 18 }, /* 5498 */ { MAD_F(0x05ec360b) /* 0.370168727 */, 18 }, /* 5499 */ { MAD_F(0x05ec942d) /* 0.370258500 */, 18 }, /* 5500 */ { MAD_F(0x05ecf251) /* 0.370348279 */, 18 }, /* 5501 */ { MAD_F(0x05ed5076) /* 0.370438063 */, 18 }, /* 5502 */ { MAD_F(0x05edae9d) /* 0.370527853 */, 18 }, /* 5503 */ { MAD_F(0x05ee0cc5) /* 0.370617648 */, 18 }, /* 5504 */ { MAD_F(0x05ee6aef) /* 0.370707448 */, 18 }, /* 5505 */ { MAD_F(0x05eec91a) /* 0.370797254 */, 18 }, /* 5506 */ { MAD_F(0x05ef2746) /* 0.370887065 */, 18 }, /* 5507 */ { MAD_F(0x05ef8574) /* 0.370976882 */, 18 }, /* 5508 */ { MAD_F(0x05efe3a4) /* 0.371066704 */, 18 }, /* 5509 */ { MAD_F(0x05f041d5) /* 0.371156532 */, 18 }, /* 5510 */ { MAD_F(0x05f0a007) /* 0.371246365 */, 18 }, /* 5511 */ { MAD_F(0x05f0fe3b) /* 0.371336203 */, 18 }, /* 5512 */ { MAD_F(0x05f15c70) /* 0.371426047 */, 18 }, /* 5513 */ { MAD_F(0x05f1baa7) /* 0.371515897 */, 18 }, /* 5514 */ { MAD_F(0x05f218df) /* 0.371605751 */, 18 }, /* 5515 */ { MAD_F(0x05f27719) /* 0.371695612 */, 18 }, /* 5516 */ { MAD_F(0x05f2d554) /* 0.371785477 */, 18 }, /* 5517 */ { MAD_F(0x05f33390) /* 0.371875348 */, 18 }, /* 5518 */ { MAD_F(0x05f391cf) /* 0.371965225 */, 18 }, /* 5519 */ { MAD_F(0x05f3f00e) /* 0.372055107 */, 18 }, /* 5520 */ { MAD_F(0x05f44e4f) /* 0.372144994 */, 18 }, /* 5521 */ { MAD_F(0x05f4ac91) /* 0.372234887 */, 18 }, /* 5522 */ { MAD_F(0x05f50ad5) /* 0.372324785 */, 18 }, /* 5523 */ { MAD_F(0x05f5691b) /* 0.372414689 */, 18 }, /* 5524 */ { MAD_F(0x05f5c761) /* 0.372504598 */, 18 }, /* 5525 */ { MAD_F(0x05f625aa) /* 0.372594513 */, 18 }, /* 5526 */ { MAD_F(0x05f683f3) /* 0.372684433 */, 18 }, /* 5527 */ { MAD_F(0x05f6e23f) /* 0.372774358 */, 18 }, /* 5528 */ { MAD_F(0x05f7408b) /* 0.372864289 */, 18 }, /* 5529 */ { MAD_F(0x05f79ed9) /* 0.372954225 */, 18 }, /* 5530 */ { MAD_F(0x05f7fd29) /* 0.373044167 */, 18 }, /* 5531 */ { MAD_F(0x05f85b7a) /* 0.373134114 */, 18 }, /* 5532 */ { MAD_F(0x05f8b9cc) /* 0.373224066 */, 18 }, /* 5533 */ { MAD_F(0x05f91820) /* 0.373314024 */, 18 }, /* 5534 */ { MAD_F(0x05f97675) /* 0.373403987 */, 18 }, /* 5535 */ { MAD_F(0x05f9d4cc) /* 0.373493956 */, 18 }, /* 5536 */ { MAD_F(0x05fa3324) /* 0.373583930 */, 18 }, /* 5537 */ { MAD_F(0x05fa917e) /* 0.373673910 */, 18 }, /* 5538 */ { MAD_F(0x05faefd9) /* 0.373763895 */, 18 }, /* 5539 */ { MAD_F(0x05fb4e36) /* 0.373853885 */, 18 }, /* 5540 */ { MAD_F(0x05fbac94) /* 0.373943881 */, 18 }, /* 5541 */ { MAD_F(0x05fc0af3) /* 0.374033882 */, 18 }, /* 5542 */ { MAD_F(0x05fc6954) /* 0.374123889 */, 18 }, /* 5543 */ { MAD_F(0x05fcc7b7) /* 0.374213901 */, 18 }, /* 5544 */ { MAD_F(0x05fd261b) /* 0.374303918 */, 18 }, /* 5545 */ { MAD_F(0x05fd8480) /* 0.374393941 */, 18 }, /* 5546 */ { MAD_F(0x05fde2e7) /* 0.374483970 */, 18 }, /* 5547 */ { MAD_F(0x05fe414f) /* 0.374574003 */, 18 }, /* 5548 */ { MAD_F(0x05fe9fb9) /* 0.374664042 */, 18 }, /* 5549 */ { MAD_F(0x05fefe24) /* 0.374754087 */, 18 }, /* 5550 */ { MAD_F(0x05ff5c91) /* 0.374844137 */, 18 }, /* 5551 */ { MAD_F(0x05ffbaff) /* 0.374934192 */, 18 }, /* 5552 */ { MAD_F(0x0600196e) /* 0.375024253 */, 18 }, /* 5553 */ { MAD_F(0x060077df) /* 0.375114319 */, 18 }, /* 5554 */ { MAD_F(0x0600d651) /* 0.375204391 */, 18 }, /* 5555 */ { MAD_F(0x060134c5) /* 0.375294468 */, 18 }, /* 5556 */ { MAD_F(0x0601933b) /* 0.375384550 */, 18 }, /* 5557 */ { MAD_F(0x0601f1b1) /* 0.375474638 */, 18 }, /* 5558 */ { MAD_F(0x0602502a) /* 0.375564731 */, 18 }, /* 5559 */ { MAD_F(0x0602aea3) /* 0.375654830 */, 18 }, /* 5560 */ { MAD_F(0x06030d1e) /* 0.375744934 */, 18 }, /* 5561 */ { MAD_F(0x06036b9b) /* 0.375835043 */, 18 }, /* 5562 */ { MAD_F(0x0603ca19) /* 0.375925158 */, 18 }, /* 5563 */ { MAD_F(0x06042898) /* 0.376015278 */, 18 }, /* 5564 */ { MAD_F(0x06048719) /* 0.376105404 */, 18 }, /* 5565 */ { MAD_F(0x0604e59c) /* 0.376195535 */, 18 }, /* 5566 */ { MAD_F(0x0605441f) /* 0.376285671 */, 18 }, /* 5567 */ { MAD_F(0x0605a2a5) /* 0.376375813 */, 18 }, /* 5568 */ { MAD_F(0x0606012b) /* 0.376465960 */, 18 }, /* 5569 */ { MAD_F(0x06065fb4) /* 0.376556113 */, 18 }, /* 5570 */ { MAD_F(0x0606be3d) /* 0.376646271 */, 18 }, /* 5571 */ { MAD_F(0x06071cc8) /* 0.376736434 */, 18 }, /* 5572 */ { MAD_F(0x06077b55) /* 0.376826603 */, 18 }, /* 5573 */ { MAD_F(0x0607d9e3) /* 0.376916777 */, 18 }, /* 5574 */ { MAD_F(0x06083872) /* 0.377006957 */, 18 }, /* 5575 */ { MAD_F(0x06089703) /* 0.377097141 */, 18 }, /* 5576 */ { MAD_F(0x0608f595) /* 0.377187332 */, 18 }, /* 5577 */ { MAD_F(0x06095429) /* 0.377277528 */, 18 }, /* 5578 */ { MAD_F(0x0609b2be) /* 0.377367729 */, 18 }, /* 5579 */ { MAD_F(0x060a1155) /* 0.377457935 */, 18 }, /* 5580 */ { MAD_F(0x060a6fed) /* 0.377548147 */, 18 }, /* 5581 */ { MAD_F(0x060ace86) /* 0.377638364 */, 18 }, /* 5582 */ { MAD_F(0x060b2d21) /* 0.377728587 */, 18 }, /* 5583 */ { MAD_F(0x060b8bbe) /* 0.377818815 */, 18 }, /* 5584 */ { MAD_F(0x060bea5c) /* 0.377909049 */, 18 }, /* 5585 */ { MAD_F(0x060c48fb) /* 0.377999288 */, 18 }, /* 5586 */ { MAD_F(0x060ca79c) /* 0.378089532 */, 18 }, /* 5587 */ { MAD_F(0x060d063e) /* 0.378179781 */, 18 }, /* 5588 */ { MAD_F(0x060d64e1) /* 0.378270036 */, 18 }, /* 5589 */ { MAD_F(0x060dc387) /* 0.378360297 */, 18 }, /* 5590 */ { MAD_F(0x060e222d) /* 0.378450563 */, 18 }, /* 5591 */ { MAD_F(0x060e80d5) /* 0.378540834 */, 18 }, /* 5592 */ { MAD_F(0x060edf7f) /* 0.378631110 */, 18 }, /* 5593 */ { MAD_F(0x060f3e29) /* 0.378721392 */, 18 }, /* 5594 */ { MAD_F(0x060f9cd6) /* 0.378811680 */, 18 }, /* 5595 */ { MAD_F(0x060ffb83) /* 0.378901972 */, 18 }, /* 5596 */ { MAD_F(0x06105a33) /* 0.378992270 */, 18 }, /* 5597 */ { MAD_F(0x0610b8e3) /* 0.379082574 */, 18 }, /* 5598 */ { MAD_F(0x06111795) /* 0.379172883 */, 18 }, /* 5599 */ { MAD_F(0x06117649) /* 0.379263197 */, 18 }, /* 5600 */ { MAD_F(0x0611d4fe) /* 0.379353516 */, 18 }, /* 5601 */ { MAD_F(0x061233b4) /* 0.379443841 */, 18 }, /* 5602 */ { MAD_F(0x0612926c) /* 0.379534172 */, 18 }, /* 5603 */ { MAD_F(0x0612f125) /* 0.379624507 */, 18 }, /* 5604 */ { MAD_F(0x06134fe0) /* 0.379714848 */, 18 }, /* 5605 */ { MAD_F(0x0613ae9c) /* 0.379805195 */, 18 }, /* 5606 */ { MAD_F(0x06140d5a) /* 0.379895547 */, 18 }, /* 5607 */ { MAD_F(0x06146c19) /* 0.379985904 */, 18 }, /* 5608 */ { MAD_F(0x0614cada) /* 0.380076266 */, 18 }, /* 5609 */ { MAD_F(0x0615299c) /* 0.380166634 */, 18 }, /* 5610 */ { MAD_F(0x0615885f) /* 0.380257008 */, 18 }, /* 5611 */ { MAD_F(0x0615e724) /* 0.380347386 */, 18 }, /* 5612 */ { MAD_F(0x061645ea) /* 0.380437770 */, 18 }, /* 5613 */ { MAD_F(0x0616a4b2) /* 0.380528160 */, 18 }, /* 5614 */ { MAD_F(0x0617037b) /* 0.380618555 */, 18 }, /* 5615 */ { MAD_F(0x06176246) /* 0.380708955 */, 18 }, /* 5616 */ { MAD_F(0x0617c112) /* 0.380799360 */, 18 }, /* 5617 */ { MAD_F(0x06181fdf) /* 0.380889771 */, 18 }, /* 5618 */ { MAD_F(0x06187eae) /* 0.380980187 */, 18 }, /* 5619 */ { MAD_F(0x0618dd7e) /* 0.381070609 */, 18 }, /* 5620 */ { MAD_F(0x06193c50) /* 0.381161036 */, 18 }, /* 5621 */ { MAD_F(0x06199b24) /* 0.381251468 */, 18 }, /* 5622 */ { MAD_F(0x0619f9f8) /* 0.381341906 */, 18 }, /* 5623 */ { MAD_F(0x061a58ce) /* 0.381432349 */, 18 }, /* 5624 */ { MAD_F(0x061ab7a6) /* 0.381522798 */, 18 }, /* 5625 */ { MAD_F(0x061b167f) /* 0.381613251 */, 18 }, /* 5626 */ { MAD_F(0x061b7559) /* 0.381703711 */, 18 }, /* 5627 */ { MAD_F(0x061bd435) /* 0.381794175 */, 18 }, /* 5628 */ { MAD_F(0x061c3313) /* 0.381884645 */, 18 }, /* 5629 */ { MAD_F(0x061c91f1) /* 0.381975120 */, 18 }, /* 5630 */ { MAD_F(0x061cf0d2) /* 0.382065601 */, 18 }, /* 5631 */ { MAD_F(0x061d4fb3) /* 0.382156087 */, 18 }, /* 5632 */ { MAD_F(0x061dae96) /* 0.382246578 */, 18 }, /* 5633 */ { MAD_F(0x061e0d7b) /* 0.382337075 */, 18 }, /* 5634 */ { MAD_F(0x061e6c61) /* 0.382427577 */, 18 }, /* 5635 */ { MAD_F(0x061ecb48) /* 0.382518084 */, 18 }, /* 5636 */ { MAD_F(0x061f2a31) /* 0.382608597 */, 18 }, /* 5637 */ { MAD_F(0x061f891b) /* 0.382699115 */, 18 }, /* 5638 */ { MAD_F(0x061fe807) /* 0.382789638 */, 18 }, /* 5639 */ { MAD_F(0x062046f4) /* 0.382880167 */, 18 }, /* 5640 */ { MAD_F(0x0620a5e3) /* 0.382970701 */, 18 }, /* 5641 */ { MAD_F(0x062104d3) /* 0.383061241 */, 18 }, /* 5642 */ { MAD_F(0x062163c4) /* 0.383151786 */, 18 }, /* 5643 */ { MAD_F(0x0621c2b7) /* 0.383242336 */, 18 }, /* 5644 */ { MAD_F(0x062221ab) /* 0.383332891 */, 18 }, /* 5645 */ { MAD_F(0x062280a1) /* 0.383423452 */, 18 }, /* 5646 */ { MAD_F(0x0622df98) /* 0.383514018 */, 18 }, /* 5647 */ { MAD_F(0x06233e91) /* 0.383604590 */, 18 }, /* 5648 */ { MAD_F(0x06239d8b) /* 0.383695167 */, 18 }, /* 5649 */ { MAD_F(0x0623fc86) /* 0.383785749 */, 18 }, /* 5650 */ { MAD_F(0x06245b83) /* 0.383876337 */, 18 }, /* 5651 */ { MAD_F(0x0624ba82) /* 0.383966930 */, 18 }, /* 5652 */ { MAD_F(0x06251981) /* 0.384057528 */, 18 }, /* 5653 */ { MAD_F(0x06257883) /* 0.384148132 */, 18 }, /* 5654 */ { MAD_F(0x0625d785) /* 0.384238741 */, 18 }, /* 5655 */ { MAD_F(0x06263689) /* 0.384329355 */, 18 }, /* 5656 */ { MAD_F(0x0626958f) /* 0.384419975 */, 18 }, /* 5657 */ { MAD_F(0x0626f496) /* 0.384510600 */, 18 }, /* 5658 */ { MAD_F(0x0627539e) /* 0.384601230 */, 18 }, /* 5659 */ { MAD_F(0x0627b2a8) /* 0.384691866 */, 18 }, /* 5660 */ { MAD_F(0x062811b3) /* 0.384782507 */, 18 }, /* 5661 */ { MAD_F(0x062870c0) /* 0.384873153 */, 18 }, /* 5662 */ { MAD_F(0x0628cfce) /* 0.384963805 */, 18 }, /* 5663 */ { MAD_F(0x06292ede) /* 0.385054462 */, 18 }, /* 5664 */ { MAD_F(0x06298def) /* 0.385145124 */, 18 }, /* 5665 */ { MAD_F(0x0629ed01) /* 0.385235792 */, 18 }, /* 5666 */ { MAD_F(0x062a4c15) /* 0.385326465 */, 18 }, /* 5667 */ { MAD_F(0x062aab2a) /* 0.385417143 */, 18 }, /* 5668 */ { MAD_F(0x062b0a41) /* 0.385507827 */, 18 }, /* 5669 */ { MAD_F(0x062b6959) /* 0.385598516 */, 18 }, /* 5670 */ { MAD_F(0x062bc873) /* 0.385689211 */, 18 }, /* 5671 */ { MAD_F(0x062c278e) /* 0.385779910 */, 18 }, /* 5672 */ { MAD_F(0x062c86aa) /* 0.385870615 */, 18 }, /* 5673 */ { MAD_F(0x062ce5c8) /* 0.385961326 */, 18 }, /* 5674 */ { MAD_F(0x062d44e8) /* 0.386052041 */, 18 }, /* 5675 */ { MAD_F(0x062da408) /* 0.386142762 */, 18 }, /* 5676 */ { MAD_F(0x062e032a) /* 0.386233489 */, 18 }, /* 5677 */ { MAD_F(0x062e624e) /* 0.386324221 */, 18 }, /* 5678 */ { MAD_F(0x062ec173) /* 0.386414958 */, 18 }, /* 5679 */ { MAD_F(0x062f209a) /* 0.386505700 */, 18 }, /* 5680 */ { MAD_F(0x062f7fc1) /* 0.386596448 */, 18 }, /* 5681 */ { MAD_F(0x062fdeeb) /* 0.386687201 */, 18 }, /* 5682 */ { MAD_F(0x06303e16) /* 0.386777959 */, 18 }, /* 5683 */ { MAD_F(0x06309d42) /* 0.386868723 */, 18 }, /* 5684 */ { MAD_F(0x0630fc6f) /* 0.386959492 */, 18 }, /* 5685 */ { MAD_F(0x06315b9e) /* 0.387050266 */, 18 }, /* 5686 */ { MAD_F(0x0631bacf) /* 0.387141045 */, 18 }, /* 5687 */ { MAD_F(0x06321a01) /* 0.387231830 */, 18 }, /* 5688 */ { MAD_F(0x06327934) /* 0.387322621 */, 18 }, /* 5689 */ { MAD_F(0x0632d869) /* 0.387413416 */, 18 }, /* 5690 */ { MAD_F(0x0633379f) /* 0.387504217 */, 18 }, /* 5691 */ { MAD_F(0x063396d7) /* 0.387595023 */, 18 }, /* 5692 */ { MAD_F(0x0633f610) /* 0.387685835 */, 18 }, /* 5693 */ { MAD_F(0x0634554a) /* 0.387776652 */, 18 }, /* 5694 */ { MAD_F(0x0634b486) /* 0.387867474 */, 18 }, /* 5695 */ { MAD_F(0x063513c3) /* 0.387958301 */, 18 }, /* 5696 */ { MAD_F(0x06357302) /* 0.388049134 */, 18 }, /* 5697 */ { MAD_F(0x0635d242) /* 0.388139972 */, 18 }, /* 5698 */ { MAD_F(0x06363184) /* 0.388230816 */, 18 }, /* 5699 */ { MAD_F(0x063690c7) /* 0.388321665 */, 18 }, /* 5700 */ { MAD_F(0x0636f00b) /* 0.388412519 */, 18 }, /* 5701 */ { MAD_F(0x06374f51) /* 0.388503378 */, 18 }, /* 5702 */ { MAD_F(0x0637ae99) /* 0.388594243 */, 18 }, /* 5703 */ { MAD_F(0x06380de1) /* 0.388685113 */, 18 }, /* 5704 */ { MAD_F(0x06386d2b) /* 0.388775988 */, 18 }, /* 5705 */ { MAD_F(0x0638cc77) /* 0.388866869 */, 18 }, /* 5706 */ { MAD_F(0x06392bc4) /* 0.388957755 */, 18 }, /* 5707 */ { MAD_F(0x06398b12) /* 0.389048646 */, 18 }, /* 5708 */ { MAD_F(0x0639ea62) /* 0.389139542 */, 18 }, /* 5709 */ { MAD_F(0x063a49b4) /* 0.389230444 */, 18 }, /* 5710 */ { MAD_F(0x063aa906) /* 0.389321352 */, 18 }, /* 5711 */ { MAD_F(0x063b085a) /* 0.389412264 */, 18 }, /* 5712 */ { MAD_F(0x063b67b0) /* 0.389503182 */, 18 }, /* 5713 */ { MAD_F(0x063bc707) /* 0.389594105 */, 18 }, /* 5714 */ { MAD_F(0x063c265f) /* 0.389685033 */, 18 }, /* 5715 */ { MAD_F(0x063c85b9) /* 0.389775967 */, 18 }, /* 5716 */ { MAD_F(0x063ce514) /* 0.389866906 */, 18 }, /* 5717 */ { MAD_F(0x063d4471) /* 0.389957850 */, 18 }, /* 5718 */ { MAD_F(0x063da3cf) /* 0.390048800 */, 18 }, /* 5719 */ { MAD_F(0x063e032f) /* 0.390139755 */, 18 }, /* 5720 */ { MAD_F(0x063e6290) /* 0.390230715 */, 18 }, /* 5721 */ { MAD_F(0x063ec1f2) /* 0.390321681 */, 18 }, /* 5722 */ { MAD_F(0x063f2156) /* 0.390412651 */, 18 }, /* 5723 */ { MAD_F(0x063f80bb) /* 0.390503628 */, 18 }, /* 5724 */ { MAD_F(0x063fe022) /* 0.390594609 */, 18 }, /* 5725 */ { MAD_F(0x06403f8a) /* 0.390685596 */, 18 }, /* 5726 */ { MAD_F(0x06409ef3) /* 0.390776588 */, 18 }, /* 5727 */ { MAD_F(0x0640fe5e) /* 0.390867585 */, 18 }, /* 5728 */ { MAD_F(0x06415dcb) /* 0.390958588 */, 18 }, /* 5729 */ { MAD_F(0x0641bd38) /* 0.391049596 */, 18 }, /* 5730 */ { MAD_F(0x06421ca7) /* 0.391140609 */, 18 }, /* 5731 */ { MAD_F(0x06427c18) /* 0.391231627 */, 18 }, /* 5732 */ { MAD_F(0x0642db8a) /* 0.391322651 */, 18 }, /* 5733 */ { MAD_F(0x06433afd) /* 0.391413680 */, 18 }, /* 5734 */ { MAD_F(0x06439a72) /* 0.391504714 */, 18 }, /* 5735 */ { MAD_F(0x0643f9e9) /* 0.391595754 */, 18 }, /* 5736 */ { MAD_F(0x06445960) /* 0.391686799 */, 18 }, /* 5737 */ { MAD_F(0x0644b8d9) /* 0.391777849 */, 18 }, /* 5738 */ { MAD_F(0x06451854) /* 0.391868905 */, 18 }, /* 5739 */ { MAD_F(0x064577d0) /* 0.391959966 */, 18 }, /* 5740 */ { MAD_F(0x0645d74d) /* 0.392051032 */, 18 }, /* 5741 */ { MAD_F(0x064636cc) /* 0.392142103 */, 18 }, /* 5742 */ { MAD_F(0x0646964c) /* 0.392233180 */, 18 }, /* 5743 */ { MAD_F(0x0646f5ce) /* 0.392324262 */, 18 }, /* 5744 */ { MAD_F(0x06475551) /* 0.392415349 */, 18 }, /* 5745 */ { MAD_F(0x0647b4d5) /* 0.392506442 */, 18 }, /* 5746 */ { MAD_F(0x0648145b) /* 0.392597540 */, 18 }, /* 5747 */ { MAD_F(0x064873e3) /* 0.392688643 */, 18 }, /* 5748 */ { MAD_F(0x0648d36b) /* 0.392779751 */, 18 }, /* 5749 */ { MAD_F(0x064932f6) /* 0.392870865 */, 18 }, /* 5750 */ { MAD_F(0x06499281) /* 0.392961984 */, 18 }, /* 5751 */ { MAD_F(0x0649f20e) /* 0.393053108 */, 18 }, /* 5752 */ { MAD_F(0x064a519c) /* 0.393144238 */, 18 }, /* 5753 */ { MAD_F(0x064ab12c) /* 0.393235372 */, 18 }, /* 5754 */ { MAD_F(0x064b10be) /* 0.393326513 */, 18 }, /* 5755 */ { MAD_F(0x064b7050) /* 0.393417658 */, 18 }, /* 5756 */ { MAD_F(0x064bcfe4) /* 0.393508809 */, 18 }, /* 5757 */ { MAD_F(0x064c2f7a) /* 0.393599965 */, 18 }, /* 5758 */ { MAD_F(0x064c8f11) /* 0.393691126 */, 18 }, /* 5759 */ { MAD_F(0x064ceea9) /* 0.393782292 */, 18 }, /* 5760 */ { MAD_F(0x064d4e43) /* 0.393873464 */, 18 }, /* 5761 */ { MAD_F(0x064dadde) /* 0.393964641 */, 18 }, /* 5762 */ { MAD_F(0x064e0d7a) /* 0.394055823 */, 18 }, /* 5763 */ { MAD_F(0x064e6d18) /* 0.394147011 */, 18 }, /* 5764 */ { MAD_F(0x064eccb8) /* 0.394238204 */, 18 }, /* 5765 */ { MAD_F(0x064f2c59) /* 0.394329402 */, 18 }, /* 5766 */ { MAD_F(0x064f8bfb) /* 0.394420605 */, 18 }, /* 5767 */ { MAD_F(0x064feb9e) /* 0.394511814 */, 18 }, /* 5768 */ { MAD_F(0x06504b44) /* 0.394603028 */, 18 }, /* 5769 */ { MAD_F(0x0650aaea) /* 0.394694247 */, 18 }, /* 5770 */ { MAD_F(0x06510a92) /* 0.394785472 */, 18 }, /* 5771 */ { MAD_F(0x06516a3b) /* 0.394876702 */, 18 }, /* 5772 */ { MAD_F(0x0651c9e6) /* 0.394967937 */, 18 }, /* 5773 */ { MAD_F(0x06522992) /* 0.395059177 */, 18 }, /* 5774 */ { MAD_F(0x06528940) /* 0.395150423 */, 18 }, /* 5775 */ { MAD_F(0x0652e8ef) /* 0.395241673 */, 18 }, /* 5776 */ { MAD_F(0x0653489f) /* 0.395332930 */, 18 }, /* 5777 */ { MAD_F(0x0653a851) /* 0.395424191 */, 18 }, /* 5778 */ { MAD_F(0x06540804) /* 0.395515458 */, 18 }, /* 5779 */ { MAD_F(0x065467b9) /* 0.395606730 */, 18 }, /* 5780 */ { MAD_F(0x0654c76f) /* 0.395698007 */, 18 }, /* 5781 */ { MAD_F(0x06552726) /* 0.395789289 */, 18 }, /* 5782 */ { MAD_F(0x065586df) /* 0.395880577 */, 18 }, /* 5783 */ { MAD_F(0x0655e699) /* 0.395971870 */, 18 }, /* 5784 */ { MAD_F(0x06564655) /* 0.396063168 */, 18 }, /* 5785 */ { MAD_F(0x0656a612) /* 0.396154472 */, 18 }, /* 5786 */ { MAD_F(0x065705d0) /* 0.396245780 */, 18 }, /* 5787 */ { MAD_F(0x06576590) /* 0.396337094 */, 18 }, /* 5788 */ { MAD_F(0x0657c552) /* 0.396428414 */, 18 }, /* 5789 */ { MAD_F(0x06582514) /* 0.396519738 */, 18 }, /* 5790 */ { MAD_F(0x065884d9) /* 0.396611068 */, 18 }, /* 5791 */ { MAD_F(0x0658e49e) /* 0.396702403 */, 18 }, /* 5792 */ { MAD_F(0x06594465) /* 0.396793743 */, 18 }, /* 5793 */ { MAD_F(0x0659a42e) /* 0.396885089 */, 18 }, /* 5794 */ { MAD_F(0x065a03f7) /* 0.396976440 */, 18 }, /* 5795 */ { MAD_F(0x065a63c3) /* 0.397067796 */, 18 }, /* 5796 */ { MAD_F(0x065ac38f) /* 0.397159157 */, 18 }, /* 5797 */ { MAD_F(0x065b235d) /* 0.397250524 */, 18 }, /* 5798 */ { MAD_F(0x065b832d) /* 0.397341896 */, 18 }, /* 5799 */ { MAD_F(0x065be2fe) /* 0.397433273 */, 18 }, /* 5800 */ { MAD_F(0x065c42d0) /* 0.397524655 */, 18 }, /* 5801 */ { MAD_F(0x065ca2a3) /* 0.397616043 */, 18 }, /* 5802 */ { MAD_F(0x065d0279) /* 0.397707436 */, 18 }, /* 5803 */ { MAD_F(0x065d624f) /* 0.397798834 */, 18 }, /* 5804 */ { MAD_F(0x065dc227) /* 0.397890237 */, 18 }, /* 5805 */ { MAD_F(0x065e2200) /* 0.397981646 */, 18 }, /* 5806 */ { MAD_F(0x065e81db) /* 0.398073059 */, 18 }, /* 5807 */ { MAD_F(0x065ee1b7) /* 0.398164479 */, 18 }, /* 5808 */ { MAD_F(0x065f4195) /* 0.398255903 */, 18 }, /* 5809 */ { MAD_F(0x065fa174) /* 0.398347333 */, 18 }, /* 5810 */ { MAD_F(0x06600154) /* 0.398438767 */, 18 }, /* 5811 */ { MAD_F(0x06606136) /* 0.398530207 */, 18 }, /* 5812 */ { MAD_F(0x0660c119) /* 0.398621653 */, 18 }, /* 5813 */ { MAD_F(0x066120fd) /* 0.398713103 */, 18 }, /* 5814 */ { MAD_F(0x066180e3) /* 0.398804559 */, 18 }, /* 5815 */ { MAD_F(0x0661e0cb) /* 0.398896020 */, 18 }, /* 5816 */ { MAD_F(0x066240b4) /* 0.398987487 */, 18 }, /* 5817 */ { MAD_F(0x0662a09e) /* 0.399078958 */, 18 }, /* 5818 */ { MAD_F(0x06630089) /* 0.399170435 */, 18 }, /* 5819 */ { MAD_F(0x06636077) /* 0.399261917 */, 18 }, /* 5820 */ { MAD_F(0x0663c065) /* 0.399353404 */, 18 }, /* 5821 */ { MAD_F(0x06642055) /* 0.399444897 */, 18 }, /* 5822 */ { MAD_F(0x06648046) /* 0.399536395 */, 18 }, /* 5823 */ { MAD_F(0x0664e039) /* 0.399627898 */, 18 }, /* 5824 */ { MAD_F(0x0665402d) /* 0.399719406 */, 18 }, /* 5825 */ { MAD_F(0x0665a022) /* 0.399810919 */, 18 }, /* 5826 */ { MAD_F(0x06660019) /* 0.399902438 */, 18 }, /* 5827 */ { MAD_F(0x06666011) /* 0.399993962 */, 18 }, /* 5828 */ { MAD_F(0x0666c00b) /* 0.400085491 */, 18 }, /* 5829 */ { MAD_F(0x06672006) /* 0.400177026 */, 18 }, /* 5830 */ { MAD_F(0x06678003) /* 0.400268565 */, 18 }, /* 5831 */ { MAD_F(0x0667e000) /* 0.400360110 */, 18 }, /* 5832 */ { MAD_F(0x06684000) /* 0.400451660 */, 18 }, /* 5833 */ { MAD_F(0x0668a000) /* 0.400543216 */, 18 }, /* 5834 */ { MAD_F(0x06690003) /* 0.400634776 */, 18 }, /* 5835 */ { MAD_F(0x06696006) /* 0.400726342 */, 18 }, /* 5836 */ { MAD_F(0x0669c00b) /* 0.400817913 */, 18 }, /* 5837 */ { MAD_F(0x066a2011) /* 0.400909489 */, 18 }, /* 5838 */ { MAD_F(0x066a8019) /* 0.401001071 */, 18 }, /* 5839 */ { MAD_F(0x066ae022) /* 0.401092657 */, 18 }, /* 5840 */ { MAD_F(0x066b402d) /* 0.401184249 */, 18 }, /* 5841 */ { MAD_F(0x066ba039) /* 0.401275847 */, 18 }, /* 5842 */ { MAD_F(0x066c0046) /* 0.401367449 */, 18 }, /* 5843 */ { MAD_F(0x066c6055) /* 0.401459057 */, 18 }, /* 5844 */ { MAD_F(0x066cc065) /* 0.401550670 */, 18 }, /* 5845 */ { MAD_F(0x066d2076) /* 0.401642288 */, 18 }, /* 5846 */ { MAD_F(0x066d8089) /* 0.401733911 */, 18 }, /* 5847 */ { MAD_F(0x066de09e) /* 0.401825540 */, 18 }, /* 5848 */ { MAD_F(0x066e40b3) /* 0.401917173 */, 18 }, /* 5849 */ { MAD_F(0x066ea0cb) /* 0.402008812 */, 18 }, /* 5850 */ { MAD_F(0x066f00e3) /* 0.402100457 */, 18 }, /* 5851 */ { MAD_F(0x066f60fd) /* 0.402192106 */, 18 }, /* 5852 */ { MAD_F(0x066fc118) /* 0.402283761 */, 18 }, /* 5853 */ { MAD_F(0x06702135) /* 0.402375420 */, 18 }, /* 5854 */ { MAD_F(0x06708153) /* 0.402467086 */, 18 }, /* 5855 */ { MAD_F(0x0670e173) /* 0.402558756 */, 18 }, /* 5856 */ { MAD_F(0x06714194) /* 0.402650431 */, 18 }, /* 5857 */ { MAD_F(0x0671a1b6) /* 0.402742112 */, 18 }, /* 5858 */ { MAD_F(0x067201da) /* 0.402833798 */, 18 }, /* 5859 */ { MAD_F(0x067261ff) /* 0.402925489 */, 18 }, /* 5860 */ { MAD_F(0x0672c226) /* 0.403017186 */, 18 }, /* 5861 */ { MAD_F(0x0673224e) /* 0.403108887 */, 18 }, /* 5862 */ { MAD_F(0x06738277) /* 0.403200594 */, 18 }, /* 5863 */ { MAD_F(0x0673e2a2) /* 0.403292306 */, 18 }, /* 5864 */ { MAD_F(0x067442ce) /* 0.403384024 */, 18 }, /* 5865 */ { MAD_F(0x0674a2fc) /* 0.403475746 */, 18 }, /* 5866 */ { MAD_F(0x0675032b) /* 0.403567474 */, 18 }, /* 5867 */ { MAD_F(0x0675635b) /* 0.403659207 */, 18 }, /* 5868 */ { MAD_F(0x0675c38d) /* 0.403750945 */, 18 }, /* 5869 */ { MAD_F(0x067623c0) /* 0.403842688 */, 18 }, /* 5870 */ { MAD_F(0x067683f4) /* 0.403934437 */, 18 }, /* 5871 */ { MAD_F(0x0676e42a) /* 0.404026190 */, 18 }, /* 5872 */ { MAD_F(0x06774462) /* 0.404117949 */, 18 }, /* 5873 */ { MAD_F(0x0677a49b) /* 0.404209714 */, 18 }, /* 5874 */ { MAD_F(0x067804d5) /* 0.404301483 */, 18 }, /* 5875 */ { MAD_F(0x06786510) /* 0.404393258 */, 18 }, /* 5876 */ { MAD_F(0x0678c54d) /* 0.404485037 */, 18 }, /* 5877 */ { MAD_F(0x0679258c) /* 0.404576822 */, 18 }, /* 5878 */ { MAD_F(0x067985cb) /* 0.404668613 */, 18 }, /* 5879 */ { MAD_F(0x0679e60c) /* 0.404760408 */, 18 }, /* 5880 */ { MAD_F(0x067a464f) /* 0.404852209 */, 18 }, /* 5881 */ { MAD_F(0x067aa693) /* 0.404944014 */, 18 }, /* 5882 */ { MAD_F(0x067b06d8) /* 0.405035825 */, 18 }, /* 5883 */ { MAD_F(0x067b671f) /* 0.405127642 */, 18 }, /* 5884 */ { MAD_F(0x067bc767) /* 0.405219463 */, 18 }, /* 5885 */ { MAD_F(0x067c27b1) /* 0.405311290 */, 18 }, /* 5886 */ { MAD_F(0x067c87fc) /* 0.405403122 */, 18 }, /* 5887 */ { MAD_F(0x067ce848) /* 0.405494959 */, 18 }, /* 5888 */ { MAD_F(0x067d4896) /* 0.405586801 */, 18 }, /* 5889 */ { MAD_F(0x067da8e5) /* 0.405678648 */, 18 }, /* 5890 */ { MAD_F(0x067e0935) /* 0.405770501 */, 18 }, /* 5891 */ { MAD_F(0x067e6987) /* 0.405862359 */, 18 }, /* 5892 */ { MAD_F(0x067ec9da) /* 0.405954222 */, 18 }, /* 5893 */ { MAD_F(0x067f2a2f) /* 0.406046090 */, 18 }, /* 5894 */ { MAD_F(0x067f8a85) /* 0.406137963 */, 18 }, /* 5895 */ { MAD_F(0x067feadd) /* 0.406229842 */, 18 }, /* 5896 */ { MAD_F(0x06804b36) /* 0.406321726 */, 18 }, /* 5897 */ { MAD_F(0x0680ab90) /* 0.406413615 */, 18 }, /* 5898 */ { MAD_F(0x06810beb) /* 0.406505509 */, 18 }, /* 5899 */ { MAD_F(0x06816c49) /* 0.406597408 */, 18 }, /* 5900 */ { MAD_F(0x0681cca7) /* 0.406689313 */, 18 }, /* 5901 */ { MAD_F(0x06822d07) /* 0.406781223 */, 18 }, /* 5902 */ { MAD_F(0x06828d68) /* 0.406873138 */, 18 }, /* 5903 */ { MAD_F(0x0682edcb) /* 0.406965058 */, 18 }, /* 5904 */ { MAD_F(0x06834e2f) /* 0.407056983 */, 18 }, /* 5905 */ { MAD_F(0x0683ae94) /* 0.407148914 */, 18 }, /* 5906 */ { MAD_F(0x06840efb) /* 0.407240850 */, 18 }, /* 5907 */ { MAD_F(0x06846f63) /* 0.407332791 */, 18 }, /* 5908 */ { MAD_F(0x0684cfcd) /* 0.407424737 */, 18 }, /* 5909 */ { MAD_F(0x06853038) /* 0.407516688 */, 18 }, /* 5910 */ { MAD_F(0x068590a4) /* 0.407608645 */, 18 }, /* 5911 */ { MAD_F(0x0685f112) /* 0.407700606 */, 18 }, /* 5912 */ { MAD_F(0x06865181) /* 0.407792573 */, 18 }, /* 5913 */ { MAD_F(0x0686b1f2) /* 0.407884545 */, 18 }, /* 5914 */ { MAD_F(0x06871264) /* 0.407976522 */, 18 }, /* 5915 */ { MAD_F(0x068772d7) /* 0.408068505 */, 18 }, /* 5916 */ { MAD_F(0x0687d34c) /* 0.408160492 */, 18 }, /* 5917 */ { MAD_F(0x068833c2) /* 0.408252485 */, 18 }, /* 5918 */ { MAD_F(0x06889439) /* 0.408344483 */, 18 }, /* 5919 */ { MAD_F(0x0688f4b2) /* 0.408436486 */, 18 }, /* 5920 */ { MAD_F(0x0689552c) /* 0.408528495 */, 18 }, /* 5921 */ { MAD_F(0x0689b5a8) /* 0.408620508 */, 18 }, /* 5922 */ { MAD_F(0x068a1625) /* 0.408712527 */, 18 }, /* 5923 */ { MAD_F(0x068a76a4) /* 0.408804551 */, 18 }, /* 5924 */ { MAD_F(0x068ad724) /* 0.408896580 */, 18 }, /* 5925 */ { MAD_F(0x068b37a5) /* 0.408988614 */, 18 }, /* 5926 */ { MAD_F(0x068b9827) /* 0.409080653 */, 18 }, /* 5927 */ { MAD_F(0x068bf8ac) /* 0.409172698 */, 18 }, /* 5928 */ { MAD_F(0x068c5931) /* 0.409264748 */, 18 }, /* 5929 */ { MAD_F(0x068cb9b8) /* 0.409356803 */, 18 }, /* 5930 */ { MAD_F(0x068d1a40) /* 0.409448863 */, 18 }, /* 5931 */ { MAD_F(0x068d7aca) /* 0.409540928 */, 18 }, /* 5932 */ { MAD_F(0x068ddb54) /* 0.409632999 */, 18 }, /* 5933 */ { MAD_F(0x068e3be1) /* 0.409725074 */, 18 }, /* 5934 */ { MAD_F(0x068e9c6f) /* 0.409817155 */, 18 }, /* 5935 */ { MAD_F(0x068efcfe) /* 0.409909241 */, 18 }, /* 5936 */ { MAD_F(0x068f5d8e) /* 0.410001332 */, 18 }, /* 5937 */ { MAD_F(0x068fbe20) /* 0.410093428 */, 18 }, /* 5938 */ { MAD_F(0x06901eb4) /* 0.410185530 */, 18 }, /* 5939 */ { MAD_F(0x06907f48) /* 0.410277637 */, 18 }, /* 5940 */ { MAD_F(0x0690dfde) /* 0.410369748 */, 18 }, /* 5941 */ { MAD_F(0x06914076) /* 0.410461865 */, 18 }, /* 5942 */ { MAD_F(0x0691a10f) /* 0.410553988 */, 18 }, /* 5943 */ { MAD_F(0x069201a9) /* 0.410646115 */, 18 }, /* 5944 */ { MAD_F(0x06926245) /* 0.410738247 */, 18 }, /* 5945 */ { MAD_F(0x0692c2e2) /* 0.410830385 */, 18 }, /* 5946 */ { MAD_F(0x06932380) /* 0.410922528 */, 18 }, /* 5947 */ { MAD_F(0x06938420) /* 0.411014676 */, 18 }, /* 5948 */ { MAD_F(0x0693e4c1) /* 0.411106829 */, 18 }, /* 5949 */ { MAD_F(0x06944563) /* 0.411198987 */, 18 }, /* 5950 */ { MAD_F(0x0694a607) /* 0.411291151 */, 18 }, /* 5951 */ { MAD_F(0x069506ad) /* 0.411383320 */, 18 }, /* 5952 */ { MAD_F(0x06956753) /* 0.411475493 */, 18 }, /* 5953 */ { MAD_F(0x0695c7fc) /* 0.411567672 */, 18 }, /* 5954 */ { MAD_F(0x069628a5) /* 0.411659857 */, 18 }, /* 5955 */ { MAD_F(0x06968950) /* 0.411752046 */, 18 }, /* 5956 */ { MAD_F(0x0696e9fc) /* 0.411844240 */, 18 }, /* 5957 */ { MAD_F(0x06974aaa) /* 0.411936440 */, 18 }, /* 5958 */ { MAD_F(0x0697ab59) /* 0.412028645 */, 18 }, /* 5959 */ { MAD_F(0x06980c09) /* 0.412120855 */, 18 }, /* 5960 */ { MAD_F(0x06986cbb) /* 0.412213070 */, 18 }, /* 5961 */ { MAD_F(0x0698cd6e) /* 0.412305290 */, 18 }, /* 5962 */ { MAD_F(0x06992e23) /* 0.412397516 */, 18 }, /* 5963 */ { MAD_F(0x06998ed9) /* 0.412489746 */, 18 }, /* 5964 */ { MAD_F(0x0699ef90) /* 0.412581982 */, 18 }, /* 5965 */ { MAD_F(0x069a5049) /* 0.412674223 */, 18 }, /* 5966 */ { MAD_F(0x069ab103) /* 0.412766469 */, 18 }, /* 5967 */ { MAD_F(0x069b11bf) /* 0.412858720 */, 18 }, /* 5968 */ { MAD_F(0x069b727b) /* 0.412950976 */, 18 }, /* 5969 */ { MAD_F(0x069bd33a) /* 0.413043238 */, 18 }, /* 5970 */ { MAD_F(0x069c33f9) /* 0.413135505 */, 18 }, /* 5971 */ { MAD_F(0x069c94ba) /* 0.413227776 */, 18 }, /* 5972 */ { MAD_F(0x069cf57d) /* 0.413320053 */, 18 }, /* 5973 */ { MAD_F(0x069d5641) /* 0.413412335 */, 18 }, /* 5974 */ { MAD_F(0x069db706) /* 0.413504623 */, 18 }, /* 5975 */ { MAD_F(0x069e17cc) /* 0.413596915 */, 18 }, /* 5976 */ { MAD_F(0x069e7894) /* 0.413689213 */, 18 }, /* 5977 */ { MAD_F(0x069ed95e) /* 0.413781515 */, 18 }, /* 5978 */ { MAD_F(0x069f3a28) /* 0.413873823 */, 18 }, /* 5979 */ { MAD_F(0x069f9af4) /* 0.413966136 */, 18 }, /* 5980 */ { MAD_F(0x069ffbc2) /* 0.414058454 */, 18 }, /* 5981 */ { MAD_F(0x06a05c91) /* 0.414150778 */, 18 }, /* 5982 */ { MAD_F(0x06a0bd61) /* 0.414243106 */, 18 }, /* 5983 */ { MAD_F(0x06a11e32) /* 0.414335440 */, 18 }, /* 5984 */ { MAD_F(0x06a17f05) /* 0.414427779 */, 18 }, /* 5985 */ { MAD_F(0x06a1dfda) /* 0.414520122 */, 18 }, /* 5986 */ { MAD_F(0x06a240b0) /* 0.414612471 */, 18 }, /* 5987 */ { MAD_F(0x06a2a187) /* 0.414704826 */, 18 }, /* 5988 */ { MAD_F(0x06a3025f) /* 0.414797185 */, 18 }, /* 5989 */ { MAD_F(0x06a36339) /* 0.414889549 */, 18 }, /* 5990 */ { MAD_F(0x06a3c414) /* 0.414981919 */, 18 }, /* 5991 */ { MAD_F(0x06a424f1) /* 0.415074294 */, 18 }, /* 5992 */ { MAD_F(0x06a485cf) /* 0.415166674 */, 18 }, /* 5993 */ { MAD_F(0x06a4e6ae) /* 0.415259059 */, 18 }, /* 5994 */ { MAD_F(0x06a5478f) /* 0.415351449 */, 18 }, /* 5995 */ { MAD_F(0x06a5a871) /* 0.415443844 */, 18 }, /* 5996 */ { MAD_F(0x06a60955) /* 0.415536244 */, 18 }, /* 5997 */ { MAD_F(0x06a66a3a) /* 0.415628650 */, 18 }, /* 5998 */ { MAD_F(0x06a6cb20) /* 0.415721061 */, 18 }, /* 5999 */ { MAD_F(0x06a72c08) /* 0.415813476 */, 18 }, /* 6000 */ { MAD_F(0x06a78cf1) /* 0.415905897 */, 18 }, /* 6001 */ { MAD_F(0x06a7eddb) /* 0.415998324 */, 18 }, /* 6002 */ { MAD_F(0x06a84ec7) /* 0.416090755 */, 18 }, /* 6003 */ { MAD_F(0x06a8afb4) /* 0.416183191 */, 18 }, /* 6004 */ { MAD_F(0x06a910a3) /* 0.416275633 */, 18 }, /* 6005 */ { MAD_F(0x06a97193) /* 0.416368079 */, 18 }, /* 6006 */ { MAD_F(0x06a9d284) /* 0.416460531 */, 18 }, /* 6007 */ { MAD_F(0x06aa3377) /* 0.416552988 */, 18 }, /* 6008 */ { MAD_F(0x06aa946b) /* 0.416645450 */, 18 }, /* 6009 */ { MAD_F(0x06aaf561) /* 0.416737917 */, 18 }, /* 6010 */ { MAD_F(0x06ab5657) /* 0.416830389 */, 18 }, /* 6011 */ { MAD_F(0x06abb750) /* 0.416922867 */, 18 }, /* 6012 */ { MAD_F(0x06ac1849) /* 0.417015349 */, 18 }, /* 6013 */ { MAD_F(0x06ac7944) /* 0.417107837 */, 18 }, /* 6014 */ { MAD_F(0x06acda41) /* 0.417200330 */, 18 }, /* 6015 */ { MAD_F(0x06ad3b3e) /* 0.417292828 */, 18 }, /* 6016 */ { MAD_F(0x06ad9c3d) /* 0.417385331 */, 18 }, /* 6017 */ { MAD_F(0x06adfd3e) /* 0.417477839 */, 18 }, /* 6018 */ { MAD_F(0x06ae5e40) /* 0.417570352 */, 18 }, /* 6019 */ { MAD_F(0x06aebf43) /* 0.417662871 */, 18 }, /* 6020 */ { MAD_F(0x06af2047) /* 0.417755394 */, 18 }, /* 6021 */ { MAD_F(0x06af814d) /* 0.417847923 */, 18 }, /* 6022 */ { MAD_F(0x06afe255) /* 0.417940457 */, 18 }, /* 6023 */ { MAD_F(0x06b0435e) /* 0.418032996 */, 18 }, /* 6024 */ { MAD_F(0x06b0a468) /* 0.418125540 */, 18 }, /* 6025 */ { MAD_F(0x06b10573) /* 0.418218089 */, 18 }, /* 6026 */ { MAD_F(0x06b16680) /* 0.418310643 */, 18 }, /* 6027 */ { MAD_F(0x06b1c78e) /* 0.418403203 */, 18 }, /* 6028 */ { MAD_F(0x06b2289e) /* 0.418495767 */, 18 }, /* 6029 */ { MAD_F(0x06b289af) /* 0.418588337 */, 18 }, /* 6030 */ { MAD_F(0x06b2eac1) /* 0.418680911 */, 18 }, /* 6031 */ { MAD_F(0x06b34bd5) /* 0.418773491 */, 18 }, /* 6032 */ { MAD_F(0x06b3acea) /* 0.418866076 */, 18 }, /* 6033 */ { MAD_F(0x06b40e00) /* 0.418958666 */, 18 }, /* 6034 */ { MAD_F(0x06b46f18) /* 0.419051262 */, 18 }, /* 6035 */ { MAD_F(0x06b4d031) /* 0.419143862 */, 18 }, /* 6036 */ { MAD_F(0x06b5314c) /* 0.419236467 */, 18 }, /* 6037 */ { MAD_F(0x06b59268) /* 0.419329078 */, 18 }, /* 6038 */ { MAD_F(0x06b5f385) /* 0.419421694 */, 18 }, /* 6039 */ { MAD_F(0x06b654a4) /* 0.419514314 */, 18 }, /* 6040 */ { MAD_F(0x06b6b5c4) /* 0.419606940 */, 18 }, /* 6041 */ { MAD_F(0x06b716e6) /* 0.419699571 */, 18 }, /* 6042 */ { MAD_F(0x06b77808) /* 0.419792208 */, 18 }, /* 6043 */ { MAD_F(0x06b7d92d) /* 0.419884849 */, 18 }, /* 6044 */ { MAD_F(0x06b83a52) /* 0.419977495 */, 18 }, /* 6045 */ { MAD_F(0x06b89b79) /* 0.420070147 */, 18 }, /* 6046 */ { MAD_F(0x06b8fca1) /* 0.420162803 */, 18 }, /* 6047 */ { MAD_F(0x06b95dcb) /* 0.420255465 */, 18 }, /* 6048 */ { MAD_F(0x06b9bef6) /* 0.420348132 */, 18 }, /* 6049 */ { MAD_F(0x06ba2023) /* 0.420440803 */, 18 }, /* 6050 */ { MAD_F(0x06ba8150) /* 0.420533481 */, 18 }, /* 6051 */ { MAD_F(0x06bae280) /* 0.420626163 */, 18 }, /* 6052 */ { MAD_F(0x06bb43b0) /* 0.420718850 */, 18 }, /* 6053 */ { MAD_F(0x06bba4e2) /* 0.420811542 */, 18 }, /* 6054 */ { MAD_F(0x06bc0615) /* 0.420904240 */, 18 }, /* 6055 */ { MAD_F(0x06bc674a) /* 0.420996942 */, 18 }, /* 6056 */ { MAD_F(0x06bcc880) /* 0.421089650 */, 18 }, /* 6057 */ { MAD_F(0x06bd29b7) /* 0.421182362 */, 18 }, /* 6058 */ { MAD_F(0x06bd8af0) /* 0.421275080 */, 18 }, /* 6059 */ { MAD_F(0x06bdec2a) /* 0.421367803 */, 18 }, /* 6060 */ { MAD_F(0x06be4d66) /* 0.421460531 */, 18 }, /* 6061 */ { MAD_F(0x06beaea3) /* 0.421553264 */, 18 }, /* 6062 */ { MAD_F(0x06bf0fe1) /* 0.421646003 */, 18 }, /* 6063 */ { MAD_F(0x06bf7120) /* 0.421738746 */, 18 }, /* 6064 */ { MAD_F(0x06bfd261) /* 0.421831494 */, 18 }, /* 6065 */ { MAD_F(0x06c033a4) /* 0.421924248 */, 18 }, /* 6066 */ { MAD_F(0x06c094e7) /* 0.422017007 */, 18 }, /* 6067 */ { MAD_F(0x06c0f62c) /* 0.422109770 */, 18 }, /* 6068 */ { MAD_F(0x06c15773) /* 0.422202539 */, 18 }, /* 6069 */ { MAD_F(0x06c1b8bb) /* 0.422295313 */, 18 }, /* 6070 */ { MAD_F(0x06c21a04) /* 0.422388092 */, 18 }, /* 6071 */ { MAD_F(0x06c27b4e) /* 0.422480876 */, 18 }, /* 6072 */ { MAD_F(0x06c2dc9a) /* 0.422573665 */, 18 }, /* 6073 */ { MAD_F(0x06c33de8) /* 0.422666460 */, 18 }, /* 6074 */ { MAD_F(0x06c39f36) /* 0.422759259 */, 18 }, /* 6075 */ { MAD_F(0x06c40086) /* 0.422852064 */, 18 }, /* 6076 */ { MAD_F(0x06c461d8) /* 0.422944873 */, 18 }, /* 6077 */ { MAD_F(0x06c4c32a) /* 0.423037688 */, 18 }, /* 6078 */ { MAD_F(0x06c5247f) /* 0.423130508 */, 18 }, /* 6079 */ { MAD_F(0x06c585d4) /* 0.423223333 */, 18 }, /* 6080 */ { MAD_F(0x06c5e72b) /* 0.423316162 */, 18 }, /* 6081 */ { MAD_F(0x06c64883) /* 0.423408997 */, 18 }, /* 6082 */ { MAD_F(0x06c6a9dd) /* 0.423501838 */, 18 }, /* 6083 */ { MAD_F(0x06c70b38) /* 0.423594683 */, 18 }, /* 6084 */ { MAD_F(0x06c76c94) /* 0.423687533 */, 18 }, /* 6085 */ { MAD_F(0x06c7cdf2) /* 0.423780389 */, 18 }, /* 6086 */ { MAD_F(0x06c82f51) /* 0.423873249 */, 18 }, /* 6087 */ { MAD_F(0x06c890b1) /* 0.423966115 */, 18 }, /* 6088 */ { MAD_F(0x06c8f213) /* 0.424058985 */, 18 }, /* 6089 */ { MAD_F(0x06c95376) /* 0.424151861 */, 18 }, /* 6090 */ { MAD_F(0x06c9b4da) /* 0.424244742 */, 18 }, /* 6091 */ { MAD_F(0x06ca1640) /* 0.424337628 */, 18 }, /* 6092 */ { MAD_F(0x06ca77a8) /* 0.424430519 */, 18 }, /* 6093 */ { MAD_F(0x06cad910) /* 0.424523415 */, 18 }, /* 6094 */ { MAD_F(0x06cb3a7a) /* 0.424616316 */, 18 }, /* 6095 */ { MAD_F(0x06cb9be5) /* 0.424709222 */, 18 }, /* 6096 */ { MAD_F(0x06cbfd52) /* 0.424802133 */, 18 }, /* 6097 */ { MAD_F(0x06cc5ec0) /* 0.424895050 */, 18 }, /* 6098 */ { MAD_F(0x06ccc030) /* 0.424987971 */, 18 }, /* 6099 */ { MAD_F(0x06cd21a0) /* 0.425080898 */, 18 }, /* 6100 */ { MAD_F(0x06cd8313) /* 0.425173829 */, 18 }, /* 6101 */ { MAD_F(0x06cde486) /* 0.425266766 */, 18 }, /* 6102 */ { MAD_F(0x06ce45fb) /* 0.425359708 */, 18 }, /* 6103 */ { MAD_F(0x06cea771) /* 0.425452655 */, 18 }, /* 6104 */ { MAD_F(0x06cf08e9) /* 0.425545607 */, 18 }, /* 6105 */ { MAD_F(0x06cf6a62) /* 0.425638564 */, 18 }, /* 6106 */ { MAD_F(0x06cfcbdc) /* 0.425731526 */, 18 }, /* 6107 */ { MAD_F(0x06d02d58) /* 0.425824493 */, 18 }, /* 6108 */ { MAD_F(0x06d08ed5) /* 0.425917465 */, 18 }, /* 6109 */ { MAD_F(0x06d0f053) /* 0.426010443 */, 18 }, /* 6110 */ { MAD_F(0x06d151d3) /* 0.426103425 */, 18 }, /* 6111 */ { MAD_F(0x06d1b354) /* 0.426196412 */, 18 }, /* 6112 */ { MAD_F(0x06d214d7) /* 0.426289405 */, 18 }, /* 6113 */ { MAD_F(0x06d2765a) /* 0.426382403 */, 18 }, /* 6114 */ { MAD_F(0x06d2d7e0) /* 0.426475405 */, 18 }, /* 6115 */ { MAD_F(0x06d33966) /* 0.426568413 */, 18 }, /* 6116 */ { MAD_F(0x06d39aee) /* 0.426661426 */, 18 }, /* 6117 */ { MAD_F(0x06d3fc77) /* 0.426754444 */, 18 }, /* 6118 */ { MAD_F(0x06d45e02) /* 0.426847467 */, 18 }, /* 6119 */ { MAD_F(0x06d4bf8e) /* 0.426940495 */, 18 }, /* 6120 */ { MAD_F(0x06d5211c) /* 0.427033528 */, 18 }, /* 6121 */ { MAD_F(0x06d582aa) /* 0.427126566 */, 18 }, /* 6122 */ { MAD_F(0x06d5e43a) /* 0.427219609 */, 18 }, /* 6123 */ { MAD_F(0x06d645cc) /* 0.427312657 */, 18 }, /* 6124 */ { MAD_F(0x06d6a75f) /* 0.427405711 */, 18 }, /* 6125 */ { MAD_F(0x06d708f3) /* 0.427498769 */, 18 }, /* 6126 */ { MAD_F(0x06d76a88) /* 0.427591833 */, 18 }, /* 6127 */ { MAD_F(0x06d7cc1f) /* 0.427684901 */, 18 }, /* 6128 */ { MAD_F(0x06d82db8) /* 0.427777975 */, 18 }, /* 6129 */ { MAD_F(0x06d88f51) /* 0.427871054 */, 18 }, /* 6130 */ { MAD_F(0x06d8f0ec) /* 0.427964137 */, 18 }, /* 6131 */ { MAD_F(0x06d95288) /* 0.428057226 */, 18 }, /* 6132 */ { MAD_F(0x06d9b426) /* 0.428150320 */, 18 }, /* 6133 */ { MAD_F(0x06da15c5) /* 0.428243419 */, 18 }, /* 6134 */ { MAD_F(0x06da7766) /* 0.428336523 */, 18 }, /* 6135 */ { MAD_F(0x06dad907) /* 0.428429632 */, 18 }, /* 6136 */ { MAD_F(0x06db3aaa) /* 0.428522746 */, 18 }, /* 6137 */ { MAD_F(0x06db9c4f) /* 0.428615865 */, 18 }, /* 6138 */ { MAD_F(0x06dbfdf5) /* 0.428708989 */, 18 }, /* 6139 */ { MAD_F(0x06dc5f9c) /* 0.428802119 */, 18 }, /* 6140 */ { MAD_F(0x06dcc145) /* 0.428895253 */, 18 }, /* 6141 */ { MAD_F(0x06dd22ee) /* 0.428988392 */, 18 }, /* 6142 */ { MAD_F(0x06dd849a) /* 0.429081537 */, 18 }, /* 6143 */ { MAD_F(0x06dde646) /* 0.429174686 */, 18 }, /* 6144 */ { MAD_F(0x06de47f4) /* 0.429267841 */, 18 }, /* 6145 */ { MAD_F(0x06dea9a4) /* 0.429361001 */, 18 }, /* 6146 */ { MAD_F(0x06df0b54) /* 0.429454165 */, 18 }, /* 6147 */ { MAD_F(0x06df6d06) /* 0.429547335 */, 18 }, /* 6148 */ { MAD_F(0x06dfceba) /* 0.429640510 */, 18 }, /* 6149 */ { MAD_F(0x06e0306f) /* 0.429733690 */, 18 }, /* 6150 */ { MAD_F(0x06e09225) /* 0.429826874 */, 18 }, /* 6151 */ { MAD_F(0x06e0f3dc) /* 0.429920064 */, 18 }, /* 6152 */ { MAD_F(0x06e15595) /* 0.430013259 */, 18 }, /* 6153 */ { MAD_F(0x06e1b74f) /* 0.430106459 */, 18 }, /* 6154 */ { MAD_F(0x06e2190b) /* 0.430199664 */, 18 }, /* 6155 */ { MAD_F(0x06e27ac8) /* 0.430292875 */, 18 }, /* 6156 */ { MAD_F(0x06e2dc86) /* 0.430386090 */, 18 }, /* 6157 */ { MAD_F(0x06e33e46) /* 0.430479310 */, 18 }, /* 6158 */ { MAD_F(0x06e3a007) /* 0.430572535 */, 18 }, /* 6159 */ { MAD_F(0x06e401c9) /* 0.430665765 */, 18 }, /* 6160 */ { MAD_F(0x06e4638d) /* 0.430759001 */, 18 }, /* 6161 */ { MAD_F(0x06e4c552) /* 0.430852241 */, 18 }, /* 6162 */ { MAD_F(0x06e52718) /* 0.430945487 */, 18 }, /* 6163 */ { MAD_F(0x06e588e0) /* 0.431038737 */, 18 }, /* 6164 */ { MAD_F(0x06e5eaa9) /* 0.431131993 */, 18 }, /* 6165 */ { MAD_F(0x06e64c73) /* 0.431225253 */, 18 }, /* 6166 */ { MAD_F(0x06e6ae3f) /* 0.431318519 */, 18 }, /* 6167 */ { MAD_F(0x06e7100c) /* 0.431411790 */, 18 }, /* 6168 */ { MAD_F(0x06e771db) /* 0.431505065 */, 18 }, /* 6169 */ { MAD_F(0x06e7d3ab) /* 0.431598346 */, 18 }, /* 6170 */ { MAD_F(0x06e8357c) /* 0.431691632 */, 18 }, /* 6171 */ { MAD_F(0x06e8974e) /* 0.431784923 */, 18 }, /* 6172 */ { MAD_F(0x06e8f922) /* 0.431878218 */, 18 }, /* 6173 */ { MAD_F(0x06e95af8) /* 0.431971519 */, 18 }, /* 6174 */ { MAD_F(0x06e9bcce) /* 0.432064825 */, 18 }, /* 6175 */ { MAD_F(0x06ea1ea6) /* 0.432158136 */, 18 }, /* 6176 */ { MAD_F(0x06ea807f) /* 0.432251452 */, 18 }, /* 6177 */ { MAD_F(0x06eae25a) /* 0.432344773 */, 18 }, /* 6178 */ { MAD_F(0x06eb4436) /* 0.432438099 */, 18 }, /* 6179 */ { MAD_F(0x06eba614) /* 0.432531431 */, 18 }, /* 6180 */ { MAD_F(0x06ec07f2) /* 0.432624767 */, 18 }, /* 6181 */ { MAD_F(0x06ec69d2) /* 0.432718108 */, 18 }, /* 6182 */ { MAD_F(0x06eccbb4) /* 0.432811454 */, 18 }, /* 6183 */ { MAD_F(0x06ed2d97) /* 0.432904805 */, 18 }, /* 6184 */ { MAD_F(0x06ed8f7b) /* 0.432998162 */, 18 }, /* 6185 */ { MAD_F(0x06edf160) /* 0.433091523 */, 18 }, /* 6186 */ { MAD_F(0x06ee5347) /* 0.433184889 */, 18 }, /* 6187 */ { MAD_F(0x06eeb52f) /* 0.433278261 */, 18 }, /* 6188 */ { MAD_F(0x06ef1719) /* 0.433371637 */, 18 }, /* 6189 */ { MAD_F(0x06ef7904) /* 0.433465019 */, 18 }, /* 6190 */ { MAD_F(0x06efdaf0) /* 0.433558405 */, 18 }, /* 6191 */ { MAD_F(0x06f03cde) /* 0.433651797 */, 18 }, /* 6192 */ { MAD_F(0x06f09ecc) /* 0.433745193 */, 18 }, /* 6193 */ { MAD_F(0x06f100bd) /* 0.433838595 */, 18 }, /* 6194 */ { MAD_F(0x06f162ae) /* 0.433932001 */, 18 }, /* 6195 */ { MAD_F(0x06f1c4a1) /* 0.434025413 */, 18 }, /* 6196 */ { MAD_F(0x06f22696) /* 0.434118830 */, 18 }, /* 6197 */ { MAD_F(0x06f2888b) /* 0.434212251 */, 18 }, /* 6198 */ { MAD_F(0x06f2ea82) /* 0.434305678 */, 18 }, /* 6199 */ { MAD_F(0x06f34c7b) /* 0.434399110 */, 18 }, /* 6200 */ { MAD_F(0x06f3ae75) /* 0.434492546 */, 18 }, /* 6201 */ { MAD_F(0x06f41070) /* 0.434585988 */, 18 }, /* 6202 */ { MAD_F(0x06f4726c) /* 0.434679435 */, 18 }, /* 6203 */ { MAD_F(0x06f4d46a) /* 0.434772887 */, 18 }, /* 6204 */ { MAD_F(0x06f53669) /* 0.434866344 */, 18 }, /* 6205 */ { MAD_F(0x06f59869) /* 0.434959806 */, 18 }, /* 6206 */ { MAD_F(0x06f5fa6b) /* 0.435053272 */, 18 }, /* 6207 */ { MAD_F(0x06f65c6e) /* 0.435146744 */, 18 }, /* 6208 */ { MAD_F(0x06f6be73) /* 0.435240221 */, 18 }, /* 6209 */ { MAD_F(0x06f72079) /* 0.435333703 */, 18 }, /* 6210 */ { MAD_F(0x06f78280) /* 0.435427190 */, 18 }, /* 6211 */ { MAD_F(0x06f7e489) /* 0.435520682 */, 18 }, /* 6212 */ { MAD_F(0x06f84693) /* 0.435614179 */, 18 }, /* 6213 */ { MAD_F(0x06f8a89e) /* 0.435707681 */, 18 }, /* 6214 */ { MAD_F(0x06f90aaa) /* 0.435801188 */, 18 }, /* 6215 */ { MAD_F(0x06f96cb8) /* 0.435894700 */, 18 }, /* 6216 */ { MAD_F(0x06f9cec8) /* 0.435988217 */, 18 }, /* 6217 */ { MAD_F(0x06fa30d8) /* 0.436081739 */, 18 }, /* 6218 */ { MAD_F(0x06fa92ea) /* 0.436175266 */, 18 }, /* 6219 */ { MAD_F(0x06faf4fe) /* 0.436268799 */, 18 }, /* 6220 */ { MAD_F(0x06fb5712) /* 0.436362336 */, 18 }, /* 6221 */ { MAD_F(0x06fbb928) /* 0.436455878 */, 18 }, /* 6222 */ { MAD_F(0x06fc1b40) /* 0.436549425 */, 18 }, /* 6223 */ { MAD_F(0x06fc7d58) /* 0.436642977 */, 18 }, /* 6224 */ { MAD_F(0x06fcdf72) /* 0.436736534 */, 18 }, /* 6225 */ { MAD_F(0x06fd418e) /* 0.436830096 */, 18 }, /* 6226 */ { MAD_F(0x06fda3ab) /* 0.436923664 */, 18 }, /* 6227 */ { MAD_F(0x06fe05c9) /* 0.437017236 */, 18 }, /* 6228 */ { MAD_F(0x06fe67e8) /* 0.437110813 */, 18 }, /* 6229 */ { MAD_F(0x06feca09) /* 0.437204395 */, 18 }, /* 6230 */ { MAD_F(0x06ff2c2b) /* 0.437297982 */, 18 }, /* 6231 */ { MAD_F(0x06ff8e4f) /* 0.437391575 */, 18 }, /* 6232 */ { MAD_F(0x06fff073) /* 0.437485172 */, 18 }, /* 6233 */ { MAD_F(0x0700529a) /* 0.437578774 */, 18 }, /* 6234 */ { MAD_F(0x0700b4c1) /* 0.437672381 */, 18 }, /* 6235 */ { MAD_F(0x070116ea) /* 0.437765994 */, 18 }, /* 6236 */ { MAD_F(0x07017914) /* 0.437859611 */, 18 }, /* 6237 */ { MAD_F(0x0701db40) /* 0.437953233 */, 18 }, /* 6238 */ { MAD_F(0x07023d6c) /* 0.438046860 */, 18 }, /* 6239 */ { MAD_F(0x07029f9b) /* 0.438140493 */, 18 }, /* 6240 */ { MAD_F(0x070301ca) /* 0.438234130 */, 18 }, /* 6241 */ { MAD_F(0x070363fb) /* 0.438327772 */, 18 }, /* 6242 */ { MAD_F(0x0703c62d) /* 0.438421419 */, 18 }, /* 6243 */ { MAD_F(0x07042861) /* 0.438515072 */, 18 }, /* 6244 */ { MAD_F(0x07048a96) /* 0.438608729 */, 18 }, /* 6245 */ { MAD_F(0x0704eccc) /* 0.438702391 */, 18 }, /* 6246 */ { MAD_F(0x07054f04) /* 0.438796059 */, 18 }, /* 6247 */ { MAD_F(0x0705b13d) /* 0.438889731 */, 18 }, /* 6248 */ { MAD_F(0x07061377) /* 0.438983408 */, 18 }, /* 6249 */ { MAD_F(0x070675b3) /* 0.439077090 */, 18 }, /* 6250 */ { MAD_F(0x0706d7f0) /* 0.439170778 */, 18 }, /* 6251 */ { MAD_F(0x07073a2e) /* 0.439264470 */, 18 }, /* 6252 */ { MAD_F(0x07079c6e) /* 0.439358167 */, 18 }, /* 6253 */ { MAD_F(0x0707feaf) /* 0.439451869 */, 18 }, /* 6254 */ { MAD_F(0x070860f1) /* 0.439545577 */, 18 }, /* 6255 */ { MAD_F(0x0708c335) /* 0.439639289 */, 18 }, /* 6256 */ { MAD_F(0x0709257a) /* 0.439733006 */, 18 }, /* 6257 */ { MAD_F(0x070987c0) /* 0.439826728 */, 18 }, /* 6258 */ { MAD_F(0x0709ea08) /* 0.439920456 */, 18 }, /* 6259 */ { MAD_F(0x070a4c51) /* 0.440014188 */, 18 }, /* 6260 */ { MAD_F(0x070aae9b) /* 0.440107925 */, 18 }, /* 6261 */ { MAD_F(0x070b10e7) /* 0.440201667 */, 18 }, /* 6262 */ { MAD_F(0x070b7334) /* 0.440295414 */, 18 }, /* 6263 */ { MAD_F(0x070bd583) /* 0.440389167 */, 18 }, /* 6264 */ { MAD_F(0x070c37d2) /* 0.440482924 */, 18 }, /* 6265 */ { MAD_F(0x070c9a23) /* 0.440576686 */, 18 }, /* 6266 */ { MAD_F(0x070cfc76) /* 0.440670453 */, 18 }, /* 6267 */ { MAD_F(0x070d5eca) /* 0.440764225 */, 18 }, /* 6268 */ { MAD_F(0x070dc11f) /* 0.440858002 */, 18 }, /* 6269 */ { MAD_F(0x070e2375) /* 0.440951784 */, 18 }, /* 6270 */ { MAD_F(0x070e85cd) /* 0.441045572 */, 18 }, /* 6271 */ { MAD_F(0x070ee826) /* 0.441139364 */, 18 }, /* 6272 */ { MAD_F(0x070f4a80) /* 0.441233161 */, 18 }, /* 6273 */ { MAD_F(0x070facdc) /* 0.441326963 */, 18 }, /* 6274 */ { MAD_F(0x07100f39) /* 0.441420770 */, 18 }, /* 6275 */ { MAD_F(0x07107198) /* 0.441514582 */, 18 }, /* 6276 */ { MAD_F(0x0710d3f8) /* 0.441608399 */, 18 }, /* 6277 */ { MAD_F(0x07113659) /* 0.441702221 */, 18 }, /* 6278 */ { MAD_F(0x071198bb) /* 0.441796048 */, 18 }, /* 6279 */ { MAD_F(0x0711fb1f) /* 0.441889880 */, 18 }, /* 6280 */ { MAD_F(0x07125d84) /* 0.441983717 */, 18 }, /* 6281 */ { MAD_F(0x0712bfeb) /* 0.442077559 */, 18 }, /* 6282 */ { MAD_F(0x07132253) /* 0.442171406 */, 18 }, /* 6283 */ { MAD_F(0x071384bc) /* 0.442265257 */, 18 }, /* 6284 */ { MAD_F(0x0713e726) /* 0.442359114 */, 18 }, /* 6285 */ { MAD_F(0x07144992) /* 0.442452976 */, 18 }, /* 6286 */ { MAD_F(0x0714abff) /* 0.442546843 */, 18 }, /* 6287 */ { MAD_F(0x07150e6e) /* 0.442640715 */, 18 }, /* 6288 */ { MAD_F(0x071570de) /* 0.442734592 */, 18 }, /* 6289 */ { MAD_F(0x0715d34f) /* 0.442828473 */, 18 }, /* 6290 */ { MAD_F(0x071635c1) /* 0.442922360 */, 18 }, /* 6291 */ { MAD_F(0x07169835) /* 0.443016252 */, 18 }, /* 6292 */ { MAD_F(0x0716faaa) /* 0.443110148 */, 18 }, /* 6293 */ { MAD_F(0x07175d21) /* 0.443204050 */, 18 }, /* 6294 */ { MAD_F(0x0717bf99) /* 0.443297957 */, 18 }, /* 6295 */ { MAD_F(0x07182212) /* 0.443391868 */, 18 }, /* 6296 */ { MAD_F(0x0718848d) /* 0.443485785 */, 18 }, /* 6297 */ { MAD_F(0x0718e709) /* 0.443579706 */, 18 }, /* 6298 */ { MAD_F(0x07194986) /* 0.443673633 */, 18 }, /* 6299 */ { MAD_F(0x0719ac04) /* 0.443767564 */, 18 }, /* 6300 */ { MAD_F(0x071a0e84) /* 0.443861501 */, 18 }, /* 6301 */ { MAD_F(0x071a7105) /* 0.443955442 */, 18 }, /* 6302 */ { MAD_F(0x071ad388) /* 0.444049389 */, 18 }, /* 6303 */ { MAD_F(0x071b360c) /* 0.444143340 */, 18 }, /* 6304 */ { MAD_F(0x071b9891) /* 0.444237296 */, 18 }, /* 6305 */ { MAD_F(0x071bfb18) /* 0.444331258 */, 18 }, /* 6306 */ { MAD_F(0x071c5d9f) /* 0.444425224 */, 18 }, /* 6307 */ { MAD_F(0x071cc029) /* 0.444519195 */, 18 }, /* 6308 */ { MAD_F(0x071d22b3) /* 0.444613171 */, 18 }, /* 6309 */ { MAD_F(0x071d853f) /* 0.444707153 */, 18 }, /* 6310 */ { MAD_F(0x071de7cc) /* 0.444801139 */, 18 }, /* 6311 */ { MAD_F(0x071e4a5b) /* 0.444895130 */, 18 }, /* 6312 */ { MAD_F(0x071eaceb) /* 0.444989126 */, 18 }, /* 6313 */ { MAD_F(0x071f0f7c) /* 0.445083127 */, 18 }, /* 6314 */ { MAD_F(0x071f720e) /* 0.445177133 */, 18 }, /* 6315 */ { MAD_F(0x071fd4a2) /* 0.445271144 */, 18 }, /* 6316 */ { MAD_F(0x07203737) /* 0.445365160 */, 18 }, /* 6317 */ { MAD_F(0x072099ce) /* 0.445459181 */, 18 }, /* 6318 */ { MAD_F(0x0720fc66) /* 0.445553206 */, 18 }, /* 6319 */ { MAD_F(0x07215eff) /* 0.445647237 */, 18 }, /* 6320 */ { MAD_F(0x0721c19a) /* 0.445741273 */, 18 }, /* 6321 */ { MAD_F(0x07222436) /* 0.445835314 */, 18 }, /* 6322 */ { MAD_F(0x072286d3) /* 0.445929359 */, 18 }, /* 6323 */ { MAD_F(0x0722e971) /* 0.446023410 */, 18 }, /* 6324 */ { MAD_F(0x07234c11) /* 0.446117466 */, 18 }, /* 6325 */ { MAD_F(0x0723aeb2) /* 0.446211526 */, 18 }, /* 6326 */ { MAD_F(0x07241155) /* 0.446305592 */, 18 }, /* 6327 */ { MAD_F(0x072473f9) /* 0.446399662 */, 18 }, /* 6328 */ { MAD_F(0x0724d69e) /* 0.446493738 */, 18 }, /* 6329 */ { MAD_F(0x07253944) /* 0.446587818 */, 18 }, /* 6330 */ { MAD_F(0x07259bec) /* 0.446681903 */, 18 }, /* 6331 */ { MAD_F(0x0725fe95) /* 0.446775994 */, 18 }, /* 6332 */ { MAD_F(0x07266140) /* 0.446870089 */, 18 }, /* 6333 */ { MAD_F(0x0726c3ec) /* 0.446964189 */, 18 }, /* 6334 */ { MAD_F(0x07272699) /* 0.447058294 */, 18 }, /* 6335 */ { MAD_F(0x07278947) /* 0.447152404 */, 18 }, /* 6336 */ { MAD_F(0x0727ebf7) /* 0.447246519 */, 18 }, /* 6337 */ { MAD_F(0x07284ea8) /* 0.447340639 */, 18 }, /* 6338 */ { MAD_F(0x0728b15b) /* 0.447434764 */, 18 }, /* 6339 */ { MAD_F(0x0729140f) /* 0.447528894 */, 18 }, /* 6340 */ { MAD_F(0x072976c4) /* 0.447623029 */, 18 }, /* 6341 */ { MAD_F(0x0729d97a) /* 0.447717169 */, 18 }, /* 6342 */ { MAD_F(0x072a3c32) /* 0.447811314 */, 18 }, /* 6343 */ { MAD_F(0x072a9eeb) /* 0.447905463 */, 18 }, /* 6344 */ { MAD_F(0x072b01a6) /* 0.447999618 */, 18 }, /* 6345 */ { MAD_F(0x072b6461) /* 0.448093778 */, 18 }, /* 6346 */ { MAD_F(0x072bc71e) /* 0.448187942 */, 18 }, /* 6347 */ { MAD_F(0x072c29dd) /* 0.448282112 */, 18 }, /* 6348 */ { MAD_F(0x072c8c9d) /* 0.448376286 */, 18 }, /* 6349 */ { MAD_F(0x072cef5e) /* 0.448470466 */, 18 }, /* 6350 */ { MAD_F(0x072d5220) /* 0.448564650 */, 18 }, /* 6351 */ { MAD_F(0x072db4e4) /* 0.448658839 */, 18 }, /* 6352 */ { MAD_F(0x072e17a9) /* 0.448753033 */, 18 }, /* 6353 */ { MAD_F(0x072e7a6f) /* 0.448847233 */, 18 }, /* 6354 */ { MAD_F(0x072edd37) /* 0.448941437 */, 18 }, /* 6355 */ { MAD_F(0x072f4000) /* 0.449035646 */, 18 }, /* 6356 */ { MAD_F(0x072fa2ca) /* 0.449129860 */, 18 }, /* 6357 */ { MAD_F(0x07300596) /* 0.449224079 */, 18 }, /* 6358 */ { MAD_F(0x07306863) /* 0.449318303 */, 18 }, /* 6359 */ { MAD_F(0x0730cb32) /* 0.449412531 */, 18 }, /* 6360 */ { MAD_F(0x07312e01) /* 0.449506765 */, 18 }, /* 6361 */ { MAD_F(0x073190d2) /* 0.449601004 */, 18 }, /* 6362 */ { MAD_F(0x0731f3a5) /* 0.449695247 */, 18 }, /* 6363 */ { MAD_F(0x07325678) /* 0.449789496 */, 18 }, /* 6364 */ { MAD_F(0x0732b94d) /* 0.449883749 */, 18 }, /* 6365 */ { MAD_F(0x07331c23) /* 0.449978008 */, 18 }, /* 6366 */ { MAD_F(0x07337efb) /* 0.450072271 */, 18 }, /* 6367 */ { MAD_F(0x0733e1d4) /* 0.450166540 */, 18 }, /* 6368 */ { MAD_F(0x073444ae) /* 0.450260813 */, 18 }, /* 6369 */ { MAD_F(0x0734a78a) /* 0.450355091 */, 18 }, /* 6370 */ { MAD_F(0x07350a67) /* 0.450449374 */, 18 }, /* 6371 */ { MAD_F(0x07356d45) /* 0.450543662 */, 18 }, /* 6372 */ { MAD_F(0x0735d025) /* 0.450637955 */, 18 }, /* 6373 */ { MAD_F(0x07363306) /* 0.450732253 */, 18 }, /* 6374 */ { MAD_F(0x073695e8) /* 0.450826556 */, 18 }, /* 6375 */ { MAD_F(0x0736f8cb) /* 0.450920864 */, 18 }, /* 6376 */ { MAD_F(0x07375bb0) /* 0.451015176 */, 18 }, /* 6377 */ { MAD_F(0x0737be96) /* 0.451109494 */, 18 }, /* 6378 */ { MAD_F(0x0738217e) /* 0.451203817 */, 18 }, /* 6379 */ { MAD_F(0x07388467) /* 0.451298144 */, 18 }, /* 6380 */ { MAD_F(0x0738e751) /* 0.451392477 */, 18 }, /* 6381 */ { MAD_F(0x07394a3d) /* 0.451486814 */, 18 }, /* 6382 */ { MAD_F(0x0739ad29) /* 0.451581156 */, 18 }, /* 6383 */ { MAD_F(0x073a1017) /* 0.451675503 */, 18 }, /* 6384 */ { MAD_F(0x073a7307) /* 0.451769856 */, 18 }, /* 6385 */ { MAD_F(0x073ad5f8) /* 0.451864213 */, 18 }, /* 6386 */ { MAD_F(0x073b38ea) /* 0.451958575 */, 18 }, /* 6387 */ { MAD_F(0x073b9bdd) /* 0.452052942 */, 18 }, /* 6388 */ { MAD_F(0x073bfed2) /* 0.452147313 */, 18 }, /* 6389 */ { MAD_F(0x073c61c8) /* 0.452241690 */, 18 }, /* 6390 */ { MAD_F(0x073cc4bf) /* 0.452336072 */, 18 }, /* 6391 */ { MAD_F(0x073d27b8) /* 0.452430458 */, 18 }, /* 6392 */ { MAD_F(0x073d8ab2) /* 0.452524850 */, 18 }, /* 6393 */ { MAD_F(0x073dedae) /* 0.452619246 */, 18 }, /* 6394 */ { MAD_F(0x073e50aa) /* 0.452713648 */, 18 }, /* 6395 */ { MAD_F(0x073eb3a8) /* 0.452808054 */, 18 }, /* 6396 */ { MAD_F(0x073f16a8) /* 0.452902465 */, 18 }, /* 6397 */ { MAD_F(0x073f79a8) /* 0.452996882 */, 18 }, /* 6398 */ { MAD_F(0x073fdcaa) /* 0.453091303 */, 18 }, /* 6399 */ { MAD_F(0x07403fad) /* 0.453185729 */, 18 }, /* 6400 */ { MAD_F(0x0740a2b2) /* 0.453280160 */, 18 }, /* 6401 */ { MAD_F(0x074105b8) /* 0.453374595 */, 18 }, /* 6402 */ { MAD_F(0x074168bf) /* 0.453469036 */, 18 }, /* 6403 */ { MAD_F(0x0741cbc8) /* 0.453563482 */, 18 }, /* 6404 */ { MAD_F(0x07422ed2) /* 0.453657932 */, 18 }, /* 6405 */ { MAD_F(0x074291dd) /* 0.453752388 */, 18 }, /* 6406 */ { MAD_F(0x0742f4e9) /* 0.453846848 */, 18 }, /* 6407 */ { MAD_F(0x074357f7) /* 0.453941314 */, 18 }, /* 6408 */ { MAD_F(0x0743bb06) /* 0.454035784 */, 18 }, /* 6409 */ { MAD_F(0x07441e17) /* 0.454130259 */, 18 }, /* 6410 */ { MAD_F(0x07448129) /* 0.454224739 */, 18 }, /* 6411 */ { MAD_F(0x0744e43c) /* 0.454319224 */, 18 }, /* 6412 */ { MAD_F(0x07454750) /* 0.454413714 */, 18 }, /* 6413 */ { MAD_F(0x0745aa66) /* 0.454508209 */, 18 }, /* 6414 */ { MAD_F(0x07460d7d) /* 0.454602708 */, 18 }, /* 6415 */ { MAD_F(0x07467095) /* 0.454697213 */, 18 }, /* 6416 */ { MAD_F(0x0746d3af) /* 0.454791723 */, 18 }, /* 6417 */ { MAD_F(0x074736ca) /* 0.454886237 */, 18 }, /* 6418 */ { MAD_F(0x074799e7) /* 0.454980756 */, 18 }, /* 6419 */ { MAD_F(0x0747fd04) /* 0.455075281 */, 18 }, /* 6420 */ { MAD_F(0x07486023) /* 0.455169810 */, 18 }, /* 6421 */ { MAD_F(0x0748c344) /* 0.455264344 */, 18 }, /* 6422 */ { MAD_F(0x07492665) /* 0.455358883 */, 18 }, /* 6423 */ { MAD_F(0x07498988) /* 0.455453427 */, 18 }, /* 6424 */ { MAD_F(0x0749ecac) /* 0.455547976 */, 18 }, /* 6425 */ { MAD_F(0x074a4fd2) /* 0.455642529 */, 18 }, /* 6426 */ { MAD_F(0x074ab2f9) /* 0.455737088 */, 18 }, /* 6427 */ { MAD_F(0x074b1621) /* 0.455831652 */, 18 }, /* 6428 */ { MAD_F(0x074b794b) /* 0.455926220 */, 18 }, /* 6429 */ { MAD_F(0x074bdc75) /* 0.456020793 */, 18 }, /* 6430 */ { MAD_F(0x074c3fa1) /* 0.456115372 */, 18 }, /* 6431 */ { MAD_F(0x074ca2cf) /* 0.456209955 */, 18 }, /* 6432 */ { MAD_F(0x074d05fe) /* 0.456304543 */, 18 }, /* 6433 */ { MAD_F(0x074d692e) /* 0.456399136 */, 18 }, /* 6434 */ { MAD_F(0x074dcc5f) /* 0.456493733 */, 18 }, /* 6435 */ { MAD_F(0x074e2f92) /* 0.456588336 */, 18 }, /* 6436 */ { MAD_F(0x074e92c6) /* 0.456682944 */, 18 }, /* 6437 */ { MAD_F(0x074ef5fb) /* 0.456777556 */, 18 }, /* 6438 */ { MAD_F(0x074f5932) /* 0.456872174 */, 18 }, /* 6439 */ { MAD_F(0x074fbc6a) /* 0.456966796 */, 18 }, /* 6440 */ { MAD_F(0x07501fa3) /* 0.457061423 */, 18 }, /* 6441 */ { MAD_F(0x075082de) /* 0.457156056 */, 18 }, /* 6442 */ { MAD_F(0x0750e61a) /* 0.457250693 */, 18 }, /* 6443 */ { MAD_F(0x07514957) /* 0.457345335 */, 18 }, /* 6444 */ { MAD_F(0x0751ac96) /* 0.457439981 */, 18 }, /* 6445 */ { MAD_F(0x07520fd6) /* 0.457534633 */, 18 }, /* 6446 */ { MAD_F(0x07527317) /* 0.457629290 */, 18 }, /* 6447 */ { MAD_F(0x0752d659) /* 0.457723951 */, 18 }, /* 6448 */ { MAD_F(0x0753399d) /* 0.457818618 */, 18 }, /* 6449 */ { MAD_F(0x07539ce2) /* 0.457913289 */, 18 }, /* 6450 */ { MAD_F(0x07540029) /* 0.458007965 */, 18 }, /* 6451 */ { MAD_F(0x07546371) /* 0.458102646 */, 18 }, /* 6452 */ { MAD_F(0x0754c6ba) /* 0.458197332 */, 18 }, /* 6453 */ { MAD_F(0x07552a04) /* 0.458292023 */, 18 }, /* 6454 */ { MAD_F(0x07558d50) /* 0.458386719 */, 18 }, /* 6455 */ { MAD_F(0x0755f09d) /* 0.458481420 */, 18 }, /* 6456 */ { MAD_F(0x075653eb) /* 0.458576125 */, 18 }, /* 6457 */ { MAD_F(0x0756b73b) /* 0.458670836 */, 18 }, /* 6458 */ { MAD_F(0x07571a8c) /* 0.458765551 */, 18 }, /* 6459 */ { MAD_F(0x07577dde) /* 0.458860271 */, 18 }, /* 6460 */ { MAD_F(0x0757e131) /* 0.458954996 */, 18 }, /* 6461 */ { MAD_F(0x07584486) /* 0.459049726 */, 18 }, /* 6462 */ { MAD_F(0x0758a7dd) /* 0.459144461 */, 18 }, /* 6463 */ { MAD_F(0x07590b34) /* 0.459239201 */, 18 }, /* 6464 */ { MAD_F(0x07596e8d) /* 0.459333946 */, 18 }, /* 6465 */ { MAD_F(0x0759d1e7) /* 0.459428695 */, 18 }, /* 6466 */ { MAD_F(0x075a3542) /* 0.459523450 */, 18 }, /* 6467 */ { MAD_F(0x075a989f) /* 0.459618209 */, 18 }, /* 6468 */ { MAD_F(0x075afbfd) /* 0.459712973 */, 18 }, /* 6469 */ { MAD_F(0x075b5f5d) /* 0.459807742 */, 18 }, /* 6470 */ { MAD_F(0x075bc2bd) /* 0.459902516 */, 18 }, /* 6471 */ { MAD_F(0x075c261f) /* 0.459997295 */, 18 }, /* 6472 */ { MAD_F(0x075c8983) /* 0.460092079 */, 18 }, /* 6473 */ { MAD_F(0x075cece7) /* 0.460186867 */, 18 }, /* 6474 */ { MAD_F(0x075d504d) /* 0.460281661 */, 18 }, /* 6475 */ { MAD_F(0x075db3b5) /* 0.460376459 */, 18 }, /* 6476 */ { MAD_F(0x075e171d) /* 0.460471262 */, 18 }, /* 6477 */ { MAD_F(0x075e7a87) /* 0.460566071 */, 18 }, /* 6478 */ { MAD_F(0x075eddf2) /* 0.460660884 */, 18 }, /* 6479 */ { MAD_F(0x075f415f) /* 0.460755701 */, 18 }, /* 6480 */ { MAD_F(0x075fa4cc) /* 0.460850524 */, 18 }, /* 6481 */ { MAD_F(0x0760083b) /* 0.460945352 */, 18 }, /* 6482 */ { MAD_F(0x07606bac) /* 0.461040184 */, 18 }, /* 6483 */ { MAD_F(0x0760cf1e) /* 0.461135022 */, 18 }, /* 6484 */ { MAD_F(0x07613291) /* 0.461229864 */, 18 }, /* 6485 */ { MAD_F(0x07619605) /* 0.461324711 */, 18 }, /* 6486 */ { MAD_F(0x0761f97b) /* 0.461419563 */, 18 }, /* 6487 */ { MAD_F(0x07625cf2) /* 0.461514420 */, 18 }, /* 6488 */ { MAD_F(0x0762c06a) /* 0.461609282 */, 18 }, /* 6489 */ { MAD_F(0x076323e3) /* 0.461704149 */, 18 }, /* 6490 */ { MAD_F(0x0763875e) /* 0.461799020 */, 18 }, /* 6491 */ { MAD_F(0x0763eadb) /* 0.461893897 */, 18 }, /* 6492 */ { MAD_F(0x07644e58) /* 0.461988778 */, 18 }, /* 6493 */ { MAD_F(0x0764b1d7) /* 0.462083664 */, 18 }, /* 6494 */ { MAD_F(0x07651557) /* 0.462178555 */, 18 }, /* 6495 */ { MAD_F(0x076578d8) /* 0.462273451 */, 18 }, /* 6496 */ { MAD_F(0x0765dc5b) /* 0.462368352 */, 18 }, /* 6497 */ { MAD_F(0x07663fdf) /* 0.462463257 */, 18 }, /* 6498 */ { MAD_F(0x0766a364) /* 0.462558168 */, 18 }, /* 6499 */ { MAD_F(0x076706eb) /* 0.462653083 */, 18 }, /* 6500 */ { MAD_F(0x07676a73) /* 0.462748003 */, 18 }, /* 6501 */ { MAD_F(0x0767cdfc) /* 0.462842928 */, 18 }, /* 6502 */ { MAD_F(0x07683187) /* 0.462937858 */, 18 }, /* 6503 */ { MAD_F(0x07689513) /* 0.463032793 */, 18 }, /* 6504 */ { MAD_F(0x0768f8a0) /* 0.463127733 */, 18 }, /* 6505 */ { MAD_F(0x07695c2e) /* 0.463222678 */, 18 }, /* 6506 */ { MAD_F(0x0769bfbe) /* 0.463317627 */, 18 }, /* 6507 */ { MAD_F(0x076a234f) /* 0.463412581 */, 18 }, /* 6508 */ { MAD_F(0x076a86e2) /* 0.463507540 */, 18 }, /* 6509 */ { MAD_F(0x076aea75) /* 0.463602504 */, 18 }, /* 6510 */ { MAD_F(0x076b4e0a) /* 0.463697473 */, 18 }, /* 6511 */ { MAD_F(0x076bb1a1) /* 0.463792447 */, 18 }, /* 6512 */ { MAD_F(0x076c1538) /* 0.463887426 */, 18 }, /* 6513 */ { MAD_F(0x076c78d1) /* 0.463982409 */, 18 }, /* 6514 */ { MAD_F(0x076cdc6c) /* 0.464077398 */, 18 }, /* 6515 */ { MAD_F(0x076d4007) /* 0.464172391 */, 18 }, /* 6516 */ { MAD_F(0x076da3a4) /* 0.464267389 */, 18 }, /* 6517 */ { MAD_F(0x076e0742) /* 0.464362392 */, 18 }, /* 6518 */ { MAD_F(0x076e6ae2) /* 0.464457399 */, 18 }, /* 6519 */ { MAD_F(0x076ece82) /* 0.464552412 */, 18 }, /* 6520 */ { MAD_F(0x076f3224) /* 0.464647430 */, 18 }, /* 6521 */ { MAD_F(0x076f95c8) /* 0.464742452 */, 18 }, /* 6522 */ { MAD_F(0x076ff96c) /* 0.464837479 */, 18 }, /* 6523 */ { MAD_F(0x07705d12) /* 0.464932511 */, 18 }, /* 6524 */ { MAD_F(0x0770c0ba) /* 0.465027548 */, 18 }, /* 6525 */ { MAD_F(0x07712462) /* 0.465122590 */, 18 }, /* 6526 */ { MAD_F(0x0771880c) /* 0.465217637 */, 18 }, /* 6527 */ { MAD_F(0x0771ebb7) /* 0.465312688 */, 18 }, /* 6528 */ { MAD_F(0x07724f64) /* 0.465407744 */, 18 }, /* 6529 */ { MAD_F(0x0772b312) /* 0.465502806 */, 18 }, /* 6530 */ { MAD_F(0x077316c1) /* 0.465597872 */, 18 }, /* 6531 */ { MAD_F(0x07737a71) /* 0.465692943 */, 18 }, /* 6532 */ { MAD_F(0x0773de23) /* 0.465788018 */, 18 }, /* 6533 */ { MAD_F(0x077441d6) /* 0.465883099 */, 18 }, /* 6534 */ { MAD_F(0x0774a58a) /* 0.465978184 */, 18 }, /* 6535 */ { MAD_F(0x07750940) /* 0.466073275 */, 18 }, /* 6536 */ { MAD_F(0x07756cf7) /* 0.466168370 */, 18 }, /* 6537 */ { MAD_F(0x0775d0af) /* 0.466263470 */, 18 }, /* 6538 */ { MAD_F(0x07763468) /* 0.466358575 */, 18 }, /* 6539 */ { MAD_F(0x07769823) /* 0.466453684 */, 18 }, /* 6540 */ { MAD_F(0x0776fbdf) /* 0.466548799 */, 18 }, /* 6541 */ { MAD_F(0x07775f9d) /* 0.466643918 */, 18 }, /* 6542 */ { MAD_F(0x0777c35c) /* 0.466739043 */, 18 }, /* 6543 */ { MAD_F(0x0778271c) /* 0.466834172 */, 18 }, /* 6544 */ { MAD_F(0x07788add) /* 0.466929306 */, 18 }, /* 6545 */ { MAD_F(0x0778ee9f) /* 0.467024445 */, 18 }, /* 6546 */ { MAD_F(0x07795263) /* 0.467119588 */, 18 }, /* 6547 */ { MAD_F(0x0779b629) /* 0.467214737 */, 18 }, /* 6548 */ { MAD_F(0x077a19ef) /* 0.467309890 */, 18 }, /* 6549 */ { MAD_F(0x077a7db7) /* 0.467405048 */, 18 }, /* 6550 */ { MAD_F(0x077ae180) /* 0.467500211 */, 18 }, /* 6551 */ { MAD_F(0x077b454b) /* 0.467595379 */, 18 }, /* 6552 */ { MAD_F(0x077ba916) /* 0.467690552 */, 18 }, /* 6553 */ { MAD_F(0x077c0ce3) /* 0.467785729 */, 18 }, /* 6554 */ { MAD_F(0x077c70b2) /* 0.467880912 */, 18 }, /* 6555 */ { MAD_F(0x077cd481) /* 0.467976099 */, 18 }, /* 6556 */ { MAD_F(0x077d3852) /* 0.468071291 */, 18 }, /* 6557 */ { MAD_F(0x077d9c24) /* 0.468166488 */, 18 }, /* 6558 */ { MAD_F(0x077dfff8) /* 0.468261690 */, 18 }, /* 6559 */ { MAD_F(0x077e63cd) /* 0.468356896 */, 18 }, /* 6560 */ { MAD_F(0x077ec7a3) /* 0.468452108 */, 18 }, /* 6561 */ { MAD_F(0x077f2b7a) /* 0.468547324 */, 18 }, /* 6562 */ { MAD_F(0x077f8f53) /* 0.468642545 */, 18 }, /* 6563 */ { MAD_F(0x077ff32d) /* 0.468737771 */, 18 }, /* 6564 */ { MAD_F(0x07805708) /* 0.468833002 */, 18 }, /* 6565 */ { MAD_F(0x0780bae5) /* 0.468928237 */, 18 }, /* 6566 */ { MAD_F(0x07811ec3) /* 0.469023478 */, 18 }, /* 6567 */ { MAD_F(0x078182a2) /* 0.469118723 */, 18 }, /* 6568 */ { MAD_F(0x0781e683) /* 0.469213973 */, 18 }, /* 6569 */ { MAD_F(0x07824a64) /* 0.469309228 */, 18 }, /* 6570 */ { MAD_F(0x0782ae47) /* 0.469404488 */, 18 }, /* 6571 */ { MAD_F(0x0783122c) /* 0.469499752 */, 18 }, /* 6572 */ { MAD_F(0x07837612) /* 0.469595022 */, 18 }, /* 6573 */ { MAD_F(0x0783d9f9) /* 0.469690296 */, 18 }, /* 6574 */ { MAD_F(0x07843de1) /* 0.469785575 */, 18 }, /* 6575 */ { MAD_F(0x0784a1ca) /* 0.469880859 */, 18 }, /* 6576 */ { MAD_F(0x078505b5) /* 0.469976148 */, 18 }, /* 6577 */ { MAD_F(0x078569a2) /* 0.470071442 */, 18 }, /* 6578 */ { MAD_F(0x0785cd8f) /* 0.470166740 */, 18 }, /* 6579 */ { MAD_F(0x0786317e) /* 0.470262043 */, 18 }, /* 6580 */ { MAD_F(0x0786956e) /* 0.470357351 */, 18 }, /* 6581 */ { MAD_F(0x0786f95f) /* 0.470452664 */, 18 }, /* 6582 */ { MAD_F(0x07875d52) /* 0.470547982 */, 18 }, /* 6583 */ { MAD_F(0x0787c146) /* 0.470643305 */, 18 }, /* 6584 */ { MAD_F(0x0788253b) /* 0.470738632 */, 18 }, /* 6585 */ { MAD_F(0x07888932) /* 0.470833964 */, 18 }, /* 6586 */ { MAD_F(0x0788ed2a) /* 0.470929301 */, 18 }, /* 6587 */ { MAD_F(0x07895123) /* 0.471024643 */, 18 }, /* 6588 */ { MAD_F(0x0789b51d) /* 0.471119990 */, 18 }, /* 6589 */ { MAD_F(0x078a1919) /* 0.471215341 */, 18 }, /* 6590 */ { MAD_F(0x078a7d16) /* 0.471310698 */, 18 }, /* 6591 */ { MAD_F(0x078ae114) /* 0.471406059 */, 18 }, /* 6592 */ { MAD_F(0x078b4514) /* 0.471501425 */, 18 }, /* 6593 */ { MAD_F(0x078ba915) /* 0.471596796 */, 18 }, /* 6594 */ { MAD_F(0x078c0d17) /* 0.471692171 */, 18 }, /* 6595 */ { MAD_F(0x078c711a) /* 0.471787552 */, 18 }, /* 6596 */ { MAD_F(0x078cd51f) /* 0.471882937 */, 18 }, /* 6597 */ { MAD_F(0x078d3925) /* 0.471978327 */, 18 }, /* 6598 */ { MAD_F(0x078d9d2d) /* 0.472073722 */, 18 }, /* 6599 */ { MAD_F(0x078e0135) /* 0.472169122 */, 18 }, /* 6600 */ { MAD_F(0x078e653f) /* 0.472264527 */, 18 }, /* 6601 */ { MAD_F(0x078ec94b) /* 0.472359936 */, 18 }, /* 6602 */ { MAD_F(0x078f2d57) /* 0.472455350 */, 18 }, /* 6603 */ { MAD_F(0x078f9165) /* 0.472550769 */, 18 }, /* 6604 */ { MAD_F(0x078ff574) /* 0.472646193 */, 18 }, /* 6605 */ { MAD_F(0x07905985) /* 0.472741622 */, 18 }, /* 6606 */ { MAD_F(0x0790bd96) /* 0.472837055 */, 18 }, /* 6607 */ { MAD_F(0x079121a9) /* 0.472932493 */, 18 }, /* 6608 */ { MAD_F(0x079185be) /* 0.473027937 */, 18 }, /* 6609 */ { MAD_F(0x0791e9d3) /* 0.473123384 */, 18 }, /* 6610 */ { MAD_F(0x07924dea) /* 0.473218837 */, 18 }, /* 6611 */ { MAD_F(0x0792b202) /* 0.473314295 */, 18 }, /* 6612 */ { MAD_F(0x0793161c) /* 0.473409757 */, 18 }, /* 6613 */ { MAD_F(0x07937a37) /* 0.473505224 */, 18 }, /* 6614 */ { MAD_F(0x0793de53) /* 0.473600696 */, 18 }, /* 6615 */ { MAD_F(0x07944270) /* 0.473696173 */, 18 }, /* 6616 */ { MAD_F(0x0794a68f) /* 0.473791655 */, 18 }, /* 6617 */ { MAD_F(0x07950aaf) /* 0.473887141 */, 18 }, /* 6618 */ { MAD_F(0x07956ed0) /* 0.473982632 */, 18 }, /* 6619 */ { MAD_F(0x0795d2f2) /* 0.474078128 */, 18 }, /* 6620 */ { MAD_F(0x07963716) /* 0.474173629 */, 18 }, /* 6621 */ { MAD_F(0x07969b3b) /* 0.474269135 */, 18 }, /* 6622 */ { MAD_F(0x0796ff62) /* 0.474364645 */, 18 }, /* 6623 */ { MAD_F(0x07976389) /* 0.474460161 */, 18 }, /* 6624 */ { MAD_F(0x0797c7b2) /* 0.474555681 */, 18 }, /* 6625 */ { MAD_F(0x07982bdd) /* 0.474651205 */, 18 }, /* 6626 */ { MAD_F(0x07989008) /* 0.474746735 */, 18 }, /* 6627 */ { MAD_F(0x0798f435) /* 0.474842270 */, 18 }, /* 6628 */ { MAD_F(0x07995863) /* 0.474937809 */, 18 }, /* 6629 */ { MAD_F(0x0799bc92) /* 0.475033353 */, 18 }, /* 6630 */ { MAD_F(0x079a20c3) /* 0.475128902 */, 18 }, /* 6631 */ { MAD_F(0x079a84f5) /* 0.475224456 */, 18 }, /* 6632 */ { MAD_F(0x079ae929) /* 0.475320014 */, 18 }, /* 6633 */ { MAD_F(0x079b4d5d) /* 0.475415578 */, 18 }, /* 6634 */ { MAD_F(0x079bb193) /* 0.475511146 */, 18 }, /* 6635 */ { MAD_F(0x079c15ca) /* 0.475606719 */, 18 }, /* 6636 */ { MAD_F(0x079c7a03) /* 0.475702296 */, 18 }, /* 6637 */ { MAD_F(0x079cde3c) /* 0.475797879 */, 18 }, /* 6638 */ { MAD_F(0x079d4277) /* 0.475893466 */, 18 }, /* 6639 */ { MAD_F(0x079da6b4) /* 0.475989058 */, 18 }, /* 6640 */ { MAD_F(0x079e0af1) /* 0.476084655 */, 18 }, /* 6641 */ { MAD_F(0x079e6f30) /* 0.476180257 */, 18 }, /* 6642 */ { MAD_F(0x079ed370) /* 0.476275863 */, 18 }, /* 6643 */ { MAD_F(0x079f37b2) /* 0.476371475 */, 18 }, /* 6644 */ { MAD_F(0x079f9bf5) /* 0.476467091 */, 18 }, /* 6645 */ { MAD_F(0x07a00039) /* 0.476562712 */, 18 }, /* 6646 */ { MAD_F(0x07a0647e) /* 0.476658338 */, 18 }, /* 6647 */ { MAD_F(0x07a0c8c5) /* 0.476753968 */, 18 }, /* 6648 */ { MAD_F(0x07a12d0c) /* 0.476849603 */, 18 }, /* 6649 */ { MAD_F(0x07a19156) /* 0.476945243 */, 18 }, /* 6650 */ { MAD_F(0x07a1f5a0) /* 0.477040888 */, 18 }, /* 6651 */ { MAD_F(0x07a259ec) /* 0.477136538 */, 18 }, /* 6652 */ { MAD_F(0x07a2be39) /* 0.477232193 */, 18 }, /* 6653 */ { MAD_F(0x07a32287) /* 0.477327852 */, 18 }, /* 6654 */ { MAD_F(0x07a386d7) /* 0.477423516 */, 18 }, /* 6655 */ { MAD_F(0x07a3eb28) /* 0.477519185 */, 18 }, /* 6656 */ { MAD_F(0x07a44f7a) /* 0.477614858 */, 18 }, /* 6657 */ { MAD_F(0x07a4b3ce) /* 0.477710537 */, 18 }, /* 6658 */ { MAD_F(0x07a51822) /* 0.477806220 */, 18 }, /* 6659 */ { MAD_F(0x07a57c78) /* 0.477901908 */, 18 }, /* 6660 */ { MAD_F(0x07a5e0d0) /* 0.477997601 */, 18 }, /* 6661 */ { MAD_F(0x07a64528) /* 0.478093299 */, 18 }, /* 6662 */ { MAD_F(0x07a6a982) /* 0.478189001 */, 18 }, /* 6663 */ { MAD_F(0x07a70ddd) /* 0.478284708 */, 18 }, /* 6664 */ { MAD_F(0x07a7723a) /* 0.478380420 */, 18 }, /* 6665 */ { MAD_F(0x07a7d698) /* 0.478476137 */, 18 }, /* 6666 */ { MAD_F(0x07a83af7) /* 0.478571858 */, 18 }, /* 6667 */ { MAD_F(0x07a89f57) /* 0.478667585 */, 18 }, /* 6668 */ { MAD_F(0x07a903b9) /* 0.478763316 */, 18 }, /* 6669 */ { MAD_F(0x07a9681c) /* 0.478859052 */, 18 }, /* 6670 */ { MAD_F(0x07a9cc80) /* 0.478954793 */, 18 }, /* 6671 */ { MAD_F(0x07aa30e5) /* 0.479050538 */, 18 }, /* 6672 */ { MAD_F(0x07aa954c) /* 0.479146288 */, 18 }, /* 6673 */ { MAD_F(0x07aaf9b4) /* 0.479242043 */, 18 }, /* 6674 */ { MAD_F(0x07ab5e1e) /* 0.479337803 */, 18 }, /* 6675 */ { MAD_F(0x07abc288) /* 0.479433568 */, 18 }, /* 6676 */ { MAD_F(0x07ac26f4) /* 0.479529337 */, 18 }, /* 6677 */ { MAD_F(0x07ac8b61) /* 0.479625111 */, 18 }, /* 6678 */ { MAD_F(0x07acefd0) /* 0.479720890 */, 18 }, /* 6679 */ { MAD_F(0x07ad543f) /* 0.479816674 */, 18 }, /* 6680 */ { MAD_F(0x07adb8b0) /* 0.479912463 */, 18 }, /* 6681 */ { MAD_F(0x07ae1d23) /* 0.480008256 */, 18 }, /* 6682 */ { MAD_F(0x07ae8196) /* 0.480104054 */, 18 }, /* 6683 */ { MAD_F(0x07aee60b) /* 0.480199857 */, 18 }, /* 6684 */ { MAD_F(0x07af4a81) /* 0.480295664 */, 18 }, /* 6685 */ { MAD_F(0x07afaef9) /* 0.480391477 */, 18 }, /* 6686 */ { MAD_F(0x07b01372) /* 0.480487294 */, 18 }, /* 6687 */ { MAD_F(0x07b077ec) /* 0.480583116 */, 18 }, /* 6688 */ { MAD_F(0x07b0dc67) /* 0.480678943 */, 18 }, /* 6689 */ { MAD_F(0x07b140e4) /* 0.480774774 */, 18 }, /* 6690 */ { MAD_F(0x07b1a561) /* 0.480870611 */, 18 }, /* 6691 */ { MAD_F(0x07b209e1) /* 0.480966452 */, 18 }, /* 6692 */ { MAD_F(0x07b26e61) /* 0.481062298 */, 18 }, /* 6693 */ { MAD_F(0x07b2d2e3) /* 0.481158148 */, 18 }, /* 6694 */ { MAD_F(0x07b33766) /* 0.481254004 */, 18 }, /* 6695 */ { MAD_F(0x07b39bea) /* 0.481349864 */, 18 }, /* 6696 */ { MAD_F(0x07b4006f) /* 0.481445729 */, 18 }, /* 6697 */ { MAD_F(0x07b464f6) /* 0.481541598 */, 18 }, /* 6698 */ { MAD_F(0x07b4c97e) /* 0.481637473 */, 18 }, /* 6699 */ { MAD_F(0x07b52e08) /* 0.481733352 */, 18 }, /* 6700 */ { MAD_F(0x07b59292) /* 0.481829236 */, 18 }, /* 6701 */ { MAD_F(0x07b5f71e) /* 0.481925125 */, 18 }, /* 6702 */ { MAD_F(0x07b65bac) /* 0.482021019 */, 18 }, /* 6703 */ { MAD_F(0x07b6c03a) /* 0.482116917 */, 18 }, /* 6704 */ { MAD_F(0x07b724ca) /* 0.482212820 */, 18 }, /* 6705 */ { MAD_F(0x07b7895b) /* 0.482308728 */, 18 }, /* 6706 */ { MAD_F(0x07b7eded) /* 0.482404640 */, 18 }, /* 6707 */ { MAD_F(0x07b85281) /* 0.482500558 */, 18 }, /* 6708 */ { MAD_F(0x07b8b716) /* 0.482596480 */, 18 }, /* 6709 */ { MAD_F(0x07b91bac) /* 0.482692407 */, 18 }, /* 6710 */ { MAD_F(0x07b98044) /* 0.482788339 */, 18 }, /* 6711 */ { MAD_F(0x07b9e4dc) /* 0.482884275 */, 18 }, /* 6712 */ { MAD_F(0x07ba4976) /* 0.482980216 */, 18 }, /* 6713 */ { MAD_F(0x07baae12) /* 0.483076162 */, 18 }, /* 6714 */ { MAD_F(0x07bb12ae) /* 0.483172113 */, 18 }, /* 6715 */ { MAD_F(0x07bb774c) /* 0.483268069 */, 18 }, /* 6716 */ { MAD_F(0x07bbdbeb) /* 0.483364029 */, 18 }, /* 6717 */ { MAD_F(0x07bc408c) /* 0.483459994 */, 18 }, /* 6718 */ { MAD_F(0x07bca52d) /* 0.483555964 */, 18 }, /* 6719 */ { MAD_F(0x07bd09d0) /* 0.483651939 */, 18 }, /* 6720 */ { MAD_F(0x07bd6e75) /* 0.483747918 */, 18 }, /* 6721 */ { MAD_F(0x07bdd31a) /* 0.483843902 */, 18 }, /* 6722 */ { MAD_F(0x07be37c1) /* 0.483939891 */, 18 }, /* 6723 */ { MAD_F(0x07be9c69) /* 0.484035885 */, 18 }, /* 6724 */ { MAD_F(0x07bf0113) /* 0.484131883 */, 18 }, /* 6725 */ { MAD_F(0x07bf65bd) /* 0.484227886 */, 18 }, /* 6726 */ { MAD_F(0x07bfca69) /* 0.484323894 */, 18 }, /* 6727 */ { MAD_F(0x07c02f16) /* 0.484419907 */, 18 }, /* 6728 */ { MAD_F(0x07c093c5) /* 0.484515924 */, 18 }, /* 6729 */ { MAD_F(0x07c0f875) /* 0.484611946 */, 18 }, /* 6730 */ { MAD_F(0x07c15d26) /* 0.484707973 */, 18 }, /* 6731 */ { MAD_F(0x07c1c1d8) /* 0.484804005 */, 18 }, /* 6732 */ { MAD_F(0x07c2268b) /* 0.484900041 */, 18 }, /* 6733 */ { MAD_F(0x07c28b40) /* 0.484996083 */, 18 }, /* 6734 */ { MAD_F(0x07c2eff6) /* 0.485092128 */, 18 }, /* 6735 */ { MAD_F(0x07c354ae) /* 0.485188179 */, 18 }, /* 6736 */ { MAD_F(0x07c3b967) /* 0.485284235 */, 18 }, /* 6737 */ { MAD_F(0x07c41e21) /* 0.485380295 */, 18 }, /* 6738 */ { MAD_F(0x07c482dc) /* 0.485476360 */, 18 }, /* 6739 */ { MAD_F(0x07c4e798) /* 0.485572430 */, 18 }, /* 6740 */ { MAD_F(0x07c54c56) /* 0.485668504 */, 18 }, /* 6741 */ { MAD_F(0x07c5b115) /* 0.485764583 */, 18 }, /* 6742 */ { MAD_F(0x07c615d6) /* 0.485860667 */, 18 }, /* 6743 */ { MAD_F(0x07c67a97) /* 0.485956756 */, 18 }, /* 6744 */ { MAD_F(0x07c6df5a) /* 0.486052849 */, 18 }, /* 6745 */ { MAD_F(0x07c7441e) /* 0.486148948 */, 18 }, /* 6746 */ { MAD_F(0x07c7a8e4) /* 0.486245051 */, 18 }, /* 6747 */ { MAD_F(0x07c80daa) /* 0.486341158 */, 18 }, /* 6748 */ { MAD_F(0x07c87272) /* 0.486437271 */, 18 }, /* 6749 */ { MAD_F(0x07c8d73c) /* 0.486533388 */, 18 }, /* 6750 */ { MAD_F(0x07c93c06) /* 0.486629510 */, 18 }, /* 6751 */ { MAD_F(0x07c9a0d2) /* 0.486725637 */, 18 }, /* 6752 */ { MAD_F(0x07ca059f) /* 0.486821768 */, 18 }, /* 6753 */ { MAD_F(0x07ca6a6d) /* 0.486917905 */, 18 }, /* 6754 */ { MAD_F(0x07cacf3d) /* 0.487014045 */, 18 }, /* 6755 */ { MAD_F(0x07cb340e) /* 0.487110191 */, 18 }, /* 6756 */ { MAD_F(0x07cb98e0) /* 0.487206342 */, 18 }, /* 6757 */ { MAD_F(0x07cbfdb4) /* 0.487302497 */, 18 }, /* 6758 */ { MAD_F(0x07cc6288) /* 0.487398657 */, 18 }, /* 6759 */ { MAD_F(0x07ccc75e) /* 0.487494821 */, 18 }, /* 6760 */ { MAD_F(0x07cd2c36) /* 0.487590991 */, 18 }, /* 6761 */ { MAD_F(0x07cd910e) /* 0.487687165 */, 18 }, /* 6762 */ { MAD_F(0x07cdf5e8) /* 0.487783344 */, 18 }, /* 6763 */ { MAD_F(0x07ce5ac3) /* 0.487879528 */, 18 }, /* 6764 */ { MAD_F(0x07cebfa0) /* 0.487975716 */, 18 }, /* 6765 */ { MAD_F(0x07cf247d) /* 0.488071909 */, 18 }, /* 6766 */ { MAD_F(0x07cf895c) /* 0.488168107 */, 18 }, /* 6767 */ { MAD_F(0x07cfee3c) /* 0.488264310 */, 18 }, /* 6768 */ { MAD_F(0x07d0531e) /* 0.488360517 */, 18 }, /* 6769 */ { MAD_F(0x07d0b801) /* 0.488456729 */, 18 }, /* 6770 */ { MAD_F(0x07d11ce5) /* 0.488552946 */, 18 }, /* 6771 */ { MAD_F(0x07d181ca) /* 0.488649167 */, 18 }, /* 6772 */ { MAD_F(0x07d1e6b0) /* 0.488745394 */, 18 }, /* 6773 */ { MAD_F(0x07d24b98) /* 0.488841625 */, 18 }, /* 6774 */ { MAD_F(0x07d2b081) /* 0.488937860 */, 18 }, /* 6775 */ { MAD_F(0x07d3156c) /* 0.489034101 */, 18 }, /* 6776 */ { MAD_F(0x07d37a57) /* 0.489130346 */, 18 }, /* 6777 */ { MAD_F(0x07d3df44) /* 0.489226596 */, 18 }, /* 6778 */ { MAD_F(0x07d44432) /* 0.489322851 */, 18 }, /* 6779 */ { MAD_F(0x07d4a922) /* 0.489419110 */, 18 }, /* 6780 */ { MAD_F(0x07d50e13) /* 0.489515375 */, 18 }, /* 6781 */ { MAD_F(0x07d57305) /* 0.489611643 */, 18 }, /* 6782 */ { MAD_F(0x07d5d7f8) /* 0.489707917 */, 18 }, /* 6783 */ { MAD_F(0x07d63cec) /* 0.489804195 */, 18 }, /* 6784 */ { MAD_F(0x07d6a1e2) /* 0.489900479 */, 18 }, /* 6785 */ { MAD_F(0x07d706d9) /* 0.489996766 */, 18 }, /* 6786 */ { MAD_F(0x07d76bd2) /* 0.490093059 */, 18 }, /* 6787 */ { MAD_F(0x07d7d0cb) /* 0.490189356 */, 18 }, /* 6788 */ { MAD_F(0x07d835c6) /* 0.490285658 */, 18 }, /* 6789 */ { MAD_F(0x07d89ac2) /* 0.490381965 */, 18 }, /* 6790 */ { MAD_F(0x07d8ffc0) /* 0.490478277 */, 18 }, /* 6791 */ { MAD_F(0x07d964be) /* 0.490574593 */, 18 }, /* 6792 */ { MAD_F(0x07d9c9be) /* 0.490670914 */, 18 }, /* 6793 */ { MAD_F(0x07da2ebf) /* 0.490767239 */, 18 }, /* 6794 */ { MAD_F(0x07da93c2) /* 0.490863570 */, 18 }, /* 6795 */ { MAD_F(0x07daf8c6) /* 0.490959905 */, 18 }, /* 6796 */ { MAD_F(0x07db5dcb) /* 0.491056245 */, 18 }, /* 6797 */ { MAD_F(0x07dbc2d1) /* 0.491152589 */, 18 }, /* 6798 */ { MAD_F(0x07dc27d9) /* 0.491248939 */, 18 }, /* 6799 */ { MAD_F(0x07dc8ce1) /* 0.491345293 */, 18 }, /* 6800 */ { MAD_F(0x07dcf1ec) /* 0.491441651 */, 18 }, /* 6801 */ { MAD_F(0x07dd56f7) /* 0.491538015 */, 18 }, /* 6802 */ { MAD_F(0x07ddbc04) /* 0.491634383 */, 18 }, /* 6803 */ { MAD_F(0x07de2111) /* 0.491730756 */, 18 }, /* 6804 */ { MAD_F(0x07de8621) /* 0.491827134 */, 18 }, /* 6805 */ { MAD_F(0x07deeb31) /* 0.491923516 */, 18 }, /* 6806 */ { MAD_F(0x07df5043) /* 0.492019903 */, 18 }, /* 6807 */ { MAD_F(0x07dfb556) /* 0.492116295 */, 18 }, /* 6808 */ { MAD_F(0x07e01a6a) /* 0.492212691 */, 18 }, /* 6809 */ { MAD_F(0x07e07f80) /* 0.492309093 */, 18 }, /* 6810 */ { MAD_F(0x07e0e496) /* 0.492405499 */, 18 }, /* 6811 */ { MAD_F(0x07e149ae) /* 0.492501909 */, 18 }, /* 6812 */ { MAD_F(0x07e1aec8) /* 0.492598325 */, 18 }, /* 6813 */ { MAD_F(0x07e213e2) /* 0.492694745 */, 18 }, /* 6814 */ { MAD_F(0x07e278fe) /* 0.492791170 */, 18 }, /* 6815 */ { MAD_F(0x07e2de1b) /* 0.492887599 */, 18 }, /* 6816 */ { MAD_F(0x07e3433a) /* 0.492984033 */, 18 }, /* 6817 */ { MAD_F(0x07e3a859) /* 0.493080472 */, 18 }, /* 6818 */ { MAD_F(0x07e40d7a) /* 0.493176916 */, 18 }, /* 6819 */ { MAD_F(0x07e4729c) /* 0.493273365 */, 18 }, /* 6820 */ { MAD_F(0x07e4d7c0) /* 0.493369818 */, 18 }, /* 6821 */ { MAD_F(0x07e53ce4) /* 0.493466275 */, 18 }, /* 6822 */ { MAD_F(0x07e5a20a) /* 0.493562738 */, 18 }, /* 6823 */ { MAD_F(0x07e60732) /* 0.493659205 */, 18 }, /* 6824 */ { MAD_F(0x07e66c5a) /* 0.493755677 */, 18 }, /* 6825 */ { MAD_F(0x07e6d184) /* 0.493852154 */, 18 }, /* 6826 */ { MAD_F(0x07e736af) /* 0.493948635 */, 18 }, /* 6827 */ { MAD_F(0x07e79bdb) /* 0.494045122 */, 18 }, /* 6828 */ { MAD_F(0x07e80109) /* 0.494141612 */, 18 }, /* 6829 */ { MAD_F(0x07e86638) /* 0.494238108 */, 18 }, /* 6830 */ { MAD_F(0x07e8cb68) /* 0.494334608 */, 18 }, /* 6831 */ { MAD_F(0x07e93099) /* 0.494431113 */, 18 }, /* 6832 */ { MAD_F(0x07e995cc) /* 0.494527623 */, 18 }, /* 6833 */ { MAD_F(0x07e9fb00) /* 0.494624137 */, 18 }, /* 6834 */ { MAD_F(0x07ea6035) /* 0.494720656 */, 18 }, /* 6835 */ { MAD_F(0x07eac56b) /* 0.494817180 */, 18 }, /* 6836 */ { MAD_F(0x07eb2aa3) /* 0.494913709 */, 18 }, /* 6837 */ { MAD_F(0x07eb8fdc) /* 0.495010242 */, 18 }, /* 6838 */ { MAD_F(0x07ebf516) /* 0.495106780 */, 18 }, /* 6839 */ { MAD_F(0x07ec5a51) /* 0.495203322 */, 18 }, /* 6840 */ { MAD_F(0x07ecbf8e) /* 0.495299870 */, 18 }, /* 6841 */ { MAD_F(0x07ed24cc) /* 0.495396422 */, 18 }, /* 6842 */ { MAD_F(0x07ed8a0b) /* 0.495492978 */, 18 }, /* 6843 */ { MAD_F(0x07edef4c) /* 0.495589540 */, 18 }, /* 6844 */ { MAD_F(0x07ee548e) /* 0.495686106 */, 18 }, /* 6845 */ { MAD_F(0x07eeb9d1) /* 0.495782677 */, 18 }, /* 6846 */ { MAD_F(0x07ef1f15) /* 0.495879252 */, 18 }, /* 6847 */ { MAD_F(0x07ef845b) /* 0.495975833 */, 18 }, /* 6848 */ { MAD_F(0x07efe9a1) /* 0.496072418 */, 18 }, /* 6849 */ { MAD_F(0x07f04ee9) /* 0.496169007 */, 18 }, /* 6850 */ { MAD_F(0x07f0b433) /* 0.496265602 */, 18 }, /* 6851 */ { MAD_F(0x07f1197d) /* 0.496362201 */, 18 }, /* 6852 */ { MAD_F(0x07f17ec9) /* 0.496458804 */, 18 }, /* 6853 */ { MAD_F(0x07f1e416) /* 0.496555413 */, 18 }, /* 6854 */ { MAD_F(0x07f24965) /* 0.496652026 */, 18 }, /* 6855 */ { MAD_F(0x07f2aeb5) /* 0.496748644 */, 18 }, /* 6856 */ { MAD_F(0x07f31405) /* 0.496845266 */, 18 }, /* 6857 */ { MAD_F(0x07f37958) /* 0.496941894 */, 18 }, /* 6858 */ { MAD_F(0x07f3deab) /* 0.497038526 */, 18 }, /* 6859 */ { MAD_F(0x07f44400) /* 0.497135162 */, 18 }, /* 6860 */ { MAD_F(0x07f4a956) /* 0.497231804 */, 18 }, /* 6861 */ { MAD_F(0x07f50ead) /* 0.497328450 */, 18 }, /* 6862 */ { MAD_F(0x07f57405) /* 0.497425100 */, 18 }, /* 6863 */ { MAD_F(0x07f5d95f) /* 0.497521756 */, 18 }, /* 6864 */ { MAD_F(0x07f63eba) /* 0.497618416 */, 18 }, /* 6865 */ { MAD_F(0x07f6a416) /* 0.497715081 */, 18 }, /* 6866 */ { MAD_F(0x07f70974) /* 0.497811750 */, 18 }, /* 6867 */ { MAD_F(0x07f76ed3) /* 0.497908425 */, 18 }, /* 6868 */ { MAD_F(0x07f7d433) /* 0.498005103 */, 18 }, /* 6869 */ { MAD_F(0x07f83994) /* 0.498101787 */, 18 }, /* 6870 */ { MAD_F(0x07f89ef7) /* 0.498198475 */, 18 }, /* 6871 */ { MAD_F(0x07f9045a) /* 0.498295168 */, 18 }, /* 6872 */ { MAD_F(0x07f969c0) /* 0.498391866 */, 18 }, /* 6873 */ { MAD_F(0x07f9cf26) /* 0.498488568 */, 18 }, /* 6874 */ { MAD_F(0x07fa348e) /* 0.498585275 */, 18 }, /* 6875 */ { MAD_F(0x07fa99f6) /* 0.498681987 */, 18 }, /* 6876 */ { MAD_F(0x07faff60) /* 0.498778704 */, 18 }, /* 6877 */ { MAD_F(0x07fb64cc) /* 0.498875425 */, 18 }, /* 6878 */ { MAD_F(0x07fbca38) /* 0.498972150 */, 18 }, /* 6879 */ { MAD_F(0x07fc2fa6) /* 0.499068881 */, 18 }, /* 6880 */ { MAD_F(0x07fc9516) /* 0.499165616 */, 18 }, /* 6881 */ { MAD_F(0x07fcfa86) /* 0.499262356 */, 18 }, /* 6882 */ { MAD_F(0x07fd5ff8) /* 0.499359101 */, 18 }, /* 6883 */ { MAD_F(0x07fdc56b) /* 0.499455850 */, 18 }, /* 6884 */ { MAD_F(0x07fe2adf) /* 0.499552604 */, 18 }, /* 6885 */ { MAD_F(0x07fe9054) /* 0.499649362 */, 18 }, /* 6886 */ { MAD_F(0x07fef5cb) /* 0.499746126 */, 18 }, /* 6887 */ { MAD_F(0x07ff5b43) /* 0.499842894 */, 18 }, /* 6888 */ { MAD_F(0x07ffc0bc) /* 0.499939666 */, 18 }, /* 6889 */ { MAD_F(0x0400131b) /* 0.250018222 */, 19 }, /* 6890 */ { MAD_F(0x040045d9) /* 0.250066613 */, 19 }, /* 6891 */ { MAD_F(0x04007897) /* 0.250115006 */, 19 }, /* 6892 */ { MAD_F(0x0400ab57) /* 0.250163402 */, 19 }, /* 6893 */ { MAD_F(0x0400de16) /* 0.250211800 */, 19 }, /* 6894 */ { MAD_F(0x040110d7) /* 0.250260200 */, 19 }, /* 6895 */ { MAD_F(0x04014398) /* 0.250308603 */, 19 }, /* 6896 */ { MAD_F(0x04017659) /* 0.250357008 */, 19 }, /* 6897 */ { MAD_F(0x0401a91c) /* 0.250405415 */, 19 }, /* 6898 */ { MAD_F(0x0401dbdf) /* 0.250453825 */, 19 }, /* 6899 */ { MAD_F(0x04020ea2) /* 0.250502237 */, 19 }, /* 6900 */ { MAD_F(0x04024166) /* 0.250550652 */, 19 }, /* 6901 */ { MAD_F(0x0402742b) /* 0.250599068 */, 19 }, /* 6902 */ { MAD_F(0x0402a6f0) /* 0.250647488 */, 19 }, /* 6903 */ { MAD_F(0x0402d9b6) /* 0.250695909 */, 19 }, /* 6904 */ { MAD_F(0x04030c7d) /* 0.250744333 */, 19 }, /* 6905 */ { MAD_F(0x04033f44) /* 0.250792759 */, 19 }, /* 6906 */ { MAD_F(0x0403720c) /* 0.250841187 */, 19 }, /* 6907 */ { MAD_F(0x0403a4d5) /* 0.250889618 */, 19 }, /* 6908 */ { MAD_F(0x0403d79e) /* 0.250938051 */, 19 }, /* 6909 */ { MAD_F(0x04040a68) /* 0.250986487 */, 19 }, /* 6910 */ { MAD_F(0x04043d32) /* 0.251034924 */, 19 }, /* 6911 */ { MAD_F(0x04046ffd) /* 0.251083365 */, 19 }, /* 6912 */ { MAD_F(0x0404a2c9) /* 0.251131807 */, 19 }, /* 6913 */ { MAD_F(0x0404d595) /* 0.251180252 */, 19 }, /* 6914 */ { MAD_F(0x04050862) /* 0.251228699 */, 19 }, /* 6915 */ { MAD_F(0x04053b30) /* 0.251277148 */, 19 }, /* 6916 */ { MAD_F(0x04056dfe) /* 0.251325600 */, 19 }, /* 6917 */ { MAD_F(0x0405a0cd) /* 0.251374054 */, 19 }, /* 6918 */ { MAD_F(0x0405d39c) /* 0.251422511 */, 19 }, /* 6919 */ { MAD_F(0x0406066c) /* 0.251470970 */, 19 }, /* 6920 */ { MAD_F(0x0406393d) /* 0.251519431 */, 19 }, /* 6921 */ { MAD_F(0x04066c0e) /* 0.251567894 */, 19 }, /* 6922 */ { MAD_F(0x04069ee0) /* 0.251616360 */, 19 }, /* 6923 */ { MAD_F(0x0406d1b3) /* 0.251664828 */, 19 }, /* 6924 */ { MAD_F(0x04070486) /* 0.251713299 */, 19 }, /* 6925 */ { MAD_F(0x0407375a) /* 0.251761772 */, 19 }, /* 6926 */ { MAD_F(0x04076a2e) /* 0.251810247 */, 19 }, /* 6927 */ { MAD_F(0x04079d03) /* 0.251858724 */, 19 }, /* 6928 */ { MAD_F(0x0407cfd9) /* 0.251907204 */, 19 }, /* 6929 */ { MAD_F(0x040802af) /* 0.251955686 */, 19 }, /* 6930 */ { MAD_F(0x04083586) /* 0.252004171 */, 19 }, /* 6931 */ { MAD_F(0x0408685e) /* 0.252052658 */, 19 }, /* 6932 */ { MAD_F(0x04089b36) /* 0.252101147 */, 19 }, /* 6933 */ { MAD_F(0x0408ce0f) /* 0.252149638 */, 19 }, /* 6934 */ { MAD_F(0x040900e8) /* 0.252198132 */, 19 }, /* 6935 */ { MAD_F(0x040933c2) /* 0.252246628 */, 19 }, /* 6936 */ { MAD_F(0x0409669d) /* 0.252295127 */, 19 }, /* 6937 */ { MAD_F(0x04099978) /* 0.252343627 */, 19 }, /* 6938 */ { MAD_F(0x0409cc54) /* 0.252392131 */, 19 }, /* 6939 */ { MAD_F(0x0409ff31) /* 0.252440636 */, 19 }, /* 6940 */ { MAD_F(0x040a320e) /* 0.252489144 */, 19 }, /* 6941 */ { MAD_F(0x040a64ec) /* 0.252537654 */, 19 }, /* 6942 */ { MAD_F(0x040a97cb) /* 0.252586166 */, 19 }, /* 6943 */ { MAD_F(0x040acaaa) /* 0.252634681 */, 19 }, /* 6944 */ { MAD_F(0x040afd89) /* 0.252683198 */, 19 }, /* 6945 */ { MAD_F(0x040b306a) /* 0.252731718 */, 19 }, /* 6946 */ { MAD_F(0x040b634b) /* 0.252780240 */, 19 }, /* 6947 */ { MAD_F(0x040b962c) /* 0.252828764 */, 19 }, /* 6948 */ { MAD_F(0x040bc90e) /* 0.252877290 */, 19 }, /* 6949 */ { MAD_F(0x040bfbf1) /* 0.252925819 */, 19 }, /* 6950 */ { MAD_F(0x040c2ed5) /* 0.252974350 */, 19 }, /* 6951 */ { MAD_F(0x040c61b9) /* 0.253022883 */, 19 }, /* 6952 */ { MAD_F(0x040c949e) /* 0.253071419 */, 19 }, /* 6953 */ { MAD_F(0x040cc783) /* 0.253119957 */, 19 }, /* 6954 */ { MAD_F(0x040cfa69) /* 0.253168498 */, 19 }, /* 6955 */ { MAD_F(0x040d2d4f) /* 0.253217040 */, 19 }, /* 6956 */ { MAD_F(0x040d6037) /* 0.253265585 */, 19 }, /* 6957 */ { MAD_F(0x040d931e) /* 0.253314133 */, 19 }, /* 6958 */ { MAD_F(0x040dc607) /* 0.253362682 */, 19 }, /* 6959 */ { MAD_F(0x040df8f0) /* 0.253411234 */, 19 }, /* 6960 */ { MAD_F(0x040e2bda) /* 0.253459789 */, 19 }, /* 6961 */ { MAD_F(0x040e5ec4) /* 0.253508345 */, 19 }, /* 6962 */ { MAD_F(0x040e91af) /* 0.253556904 */, 19 }, /* 6963 */ { MAD_F(0x040ec49b) /* 0.253605466 */, 19 }, /* 6964 */ { MAD_F(0x040ef787) /* 0.253654029 */, 19 }, /* 6965 */ { MAD_F(0x040f2a74) /* 0.253702595 */, 19 }, /* 6966 */ { MAD_F(0x040f5d61) /* 0.253751164 */, 19 }, /* 6967 */ { MAD_F(0x040f904f) /* 0.253799734 */, 19 }, /* 6968 */ { MAD_F(0x040fc33e) /* 0.253848307 */, 19 }, /* 6969 */ { MAD_F(0x040ff62d) /* 0.253896883 */, 19 }, /* 6970 */ { MAD_F(0x0410291d) /* 0.253945460 */, 19 }, /* 6971 */ { MAD_F(0x04105c0e) /* 0.253994040 */, 19 }, /* 6972 */ { MAD_F(0x04108eff) /* 0.254042622 */, 19 }, /* 6973 */ { MAD_F(0x0410c1f1) /* 0.254091207 */, 19 }, /* 6974 */ { MAD_F(0x0410f4e3) /* 0.254139794 */, 19 }, /* 6975 */ { MAD_F(0x041127d6) /* 0.254188383 */, 19 }, /* 6976 */ { MAD_F(0x04115aca) /* 0.254236974 */, 19 }, /* 6977 */ { MAD_F(0x04118dbe) /* 0.254285568 */, 19 }, /* 6978 */ { MAD_F(0x0411c0b3) /* 0.254334165 */, 19 }, /* 6979 */ { MAD_F(0x0411f3a9) /* 0.254382763 */, 19 }, /* 6980 */ { MAD_F(0x0412269f) /* 0.254431364 */, 19 }, /* 6981 */ { MAD_F(0x04125996) /* 0.254479967 */, 19 }, /* 6982 */ { MAD_F(0x04128c8d) /* 0.254528572 */, 19 }, /* 6983 */ { MAD_F(0x0412bf85) /* 0.254577180 */, 19 }, /* 6984 */ { MAD_F(0x0412f27e) /* 0.254625790 */, 19 }, /* 6985 */ { MAD_F(0x04132577) /* 0.254674403 */, 19 }, /* 6986 */ { MAD_F(0x04135871) /* 0.254723017 */, 19 }, /* 6987 */ { MAD_F(0x04138b6c) /* 0.254771635 */, 19 }, /* 6988 */ { MAD_F(0x0413be67) /* 0.254820254 */, 19 }, /* 6989 */ { MAD_F(0x0413f163) /* 0.254868876 */, 19 }, /* 6990 */ { MAD_F(0x0414245f) /* 0.254917500 */, 19 }, /* 6991 */ { MAD_F(0x0414575c) /* 0.254966126 */, 19 }, /* 6992 */ { MAD_F(0x04148a5a) /* 0.255014755 */, 19 }, /* 6993 */ { MAD_F(0x0414bd58) /* 0.255063386 */, 19 }, /* 6994 */ { MAD_F(0x0414f057) /* 0.255112019 */, 19 }, /* 6995 */ { MAD_F(0x04152356) /* 0.255160655 */, 19 }, /* 6996 */ { MAD_F(0x04155657) /* 0.255209292 */, 19 }, /* 6997 */ { MAD_F(0x04158957) /* 0.255257933 */, 19 }, /* 6998 */ { MAD_F(0x0415bc59) /* 0.255306575 */, 19 }, /* 6999 */ { MAD_F(0x0415ef5b) /* 0.255355220 */, 19 }, /* 7000 */ { MAD_F(0x0416225d) /* 0.255403867 */, 19 }, /* 7001 */ { MAD_F(0x04165561) /* 0.255452517 */, 19 }, /* 7002 */ { MAD_F(0x04168864) /* 0.255501169 */, 19 }, /* 7003 */ { MAD_F(0x0416bb69) /* 0.255549823 */, 19 }, /* 7004 */ { MAD_F(0x0416ee6e) /* 0.255598479 */, 19 }, /* 7005 */ { MAD_F(0x04172174) /* 0.255647138 */, 19 }, /* 7006 */ { MAD_F(0x0417547a) /* 0.255695799 */, 19 }, /* 7007 */ { MAD_F(0x04178781) /* 0.255744463 */, 19 }, /* 7008 */ { MAD_F(0x0417ba89) /* 0.255793128 */, 19 }, /* 7009 */ { MAD_F(0x0417ed91) /* 0.255841796 */, 19 }, /* 7010 */ { MAD_F(0x0418209a) /* 0.255890467 */, 19 }, /* 7011 */ { MAD_F(0x041853a3) /* 0.255939139 */, 19 }, /* 7012 */ { MAD_F(0x041886ad) /* 0.255987814 */, 19 }, /* 7013 */ { MAD_F(0x0418b9b8) /* 0.256036492 */, 19 }, /* 7014 */ { MAD_F(0x0418ecc3) /* 0.256085171 */, 19 }, /* 7015 */ { MAD_F(0x04191fcf) /* 0.256133853 */, 19 }, /* 7016 */ { MAD_F(0x041952dc) /* 0.256182537 */, 19 }, /* 7017 */ { MAD_F(0x041985e9) /* 0.256231224 */, 19 }, /* 7018 */ { MAD_F(0x0419b8f7) /* 0.256279913 */, 19 }, /* 7019 */ { MAD_F(0x0419ec05) /* 0.256328604 */, 19 }, /* 7020 */ { MAD_F(0x041a1f15) /* 0.256377297 */, 19 }, /* 7021 */ { MAD_F(0x041a5224) /* 0.256425993 */, 19 }, /* 7022 */ { MAD_F(0x041a8534) /* 0.256474691 */, 19 }, /* 7023 */ { MAD_F(0x041ab845) /* 0.256523392 */, 19 }, /* 7024 */ { MAD_F(0x041aeb57) /* 0.256572095 */, 19 }, /* 7025 */ { MAD_F(0x041b1e69) /* 0.256620800 */, 19 }, /* 7026 */ { MAD_F(0x041b517c) /* 0.256669507 */, 19 }, /* 7027 */ { MAD_F(0x041b848f) /* 0.256718217 */, 19 }, /* 7028 */ { MAD_F(0x041bb7a3) /* 0.256766929 */, 19 }, /* 7029 */ { MAD_F(0x041beab8) /* 0.256815643 */, 19 }, /* 7030 */ { MAD_F(0x041c1dcd) /* 0.256864359 */, 19 }, /* 7031 */ { MAD_F(0x041c50e3) /* 0.256913078 */, 19 }, /* 7032 */ { MAD_F(0x041c83fa) /* 0.256961800 */, 19 }, /* 7033 */ { MAD_F(0x041cb711) /* 0.257010523 */, 19 }, /* 7034 */ { MAD_F(0x041cea28) /* 0.257059249 */, 19 }, /* 7035 */ { MAD_F(0x041d1d41) /* 0.257107977 */, 19 }, /* 7036 */ { MAD_F(0x041d505a) /* 0.257156708 */, 19 }, /* 7037 */ { MAD_F(0x041d8373) /* 0.257205440 */, 19 }, /* 7038 */ { MAD_F(0x041db68e) /* 0.257254175 */, 19 }, /* 7039 */ { MAD_F(0x041de9a8) /* 0.257302913 */, 19 }, /* 7040 */ { MAD_F(0x041e1cc4) /* 0.257351652 */, 19 }, /* 7041 */ { MAD_F(0x041e4fe0) /* 0.257400394 */, 19 }, /* 7042 */ { MAD_F(0x041e82fd) /* 0.257449139 */, 19 }, /* 7043 */ { MAD_F(0x041eb61a) /* 0.257497885 */, 19 }, /* 7044 */ { MAD_F(0x041ee938) /* 0.257546634 */, 19 }, /* 7045 */ { MAD_F(0x041f1c57) /* 0.257595386 */, 19 }, /* 7046 */ { MAD_F(0x041f4f76) /* 0.257644139 */, 19 }, /* 7047 */ { MAD_F(0x041f8296) /* 0.257692895 */, 19 }, /* 7048 */ { MAD_F(0x041fb5b6) /* 0.257741653 */, 19 }, /* 7049 */ { MAD_F(0x041fe8d7) /* 0.257790414 */, 19 }, /* 7050 */ { MAD_F(0x04201bf9) /* 0.257839176 */, 19 }, /* 7051 */ { MAD_F(0x04204f1b) /* 0.257887941 */, 19 }, /* 7052 */ { MAD_F(0x0420823e) /* 0.257936709 */, 19 }, /* 7053 */ { MAD_F(0x0420b561) /* 0.257985478 */, 19 }, /* 7054 */ { MAD_F(0x0420e885) /* 0.258034250 */, 19 }, /* 7055 */ { MAD_F(0x04211baa) /* 0.258083025 */, 19 }, /* 7056 */ { MAD_F(0x04214ed0) /* 0.258131801 */, 19 }, /* 7057 */ { MAD_F(0x042181f6) /* 0.258180580 */, 19 }, /* 7058 */ { MAD_F(0x0421b51c) /* 0.258229361 */, 19 }, /* 7059 */ { MAD_F(0x0421e843) /* 0.258278145 */, 19 }, /* 7060 */ { MAD_F(0x04221b6b) /* 0.258326931 */, 19 }, /* 7061 */ { MAD_F(0x04224e94) /* 0.258375719 */, 19 }, /* 7062 */ { MAD_F(0x042281bd) /* 0.258424509 */, 19 }, /* 7063 */ { MAD_F(0x0422b4e6) /* 0.258473302 */, 19 }, /* 7064 */ { MAD_F(0x0422e811) /* 0.258522097 */, 19 }, /* 7065 */ { MAD_F(0x04231b3c) /* 0.258570894 */, 19 }, /* 7066 */ { MAD_F(0x04234e67) /* 0.258619694 */, 19 }, /* 7067 */ { MAD_F(0x04238193) /* 0.258668496 */, 19 }, /* 7068 */ { MAD_F(0x0423b4c0) /* 0.258717300 */, 19 }, /* 7069 */ { MAD_F(0x0423e7ee) /* 0.258766106 */, 19 }, /* 7070 */ { MAD_F(0x04241b1c) /* 0.258814915 */, 19 }, /* 7071 */ { MAD_F(0x04244e4a) /* 0.258863726 */, 19 }, /* 7072 */ { MAD_F(0x04248179) /* 0.258912540 */, 19 }, /* 7073 */ { MAD_F(0x0424b4a9) /* 0.258961356 */, 19 }, /* 7074 */ { MAD_F(0x0424e7da) /* 0.259010174 */, 19 }, /* 7075 */ { MAD_F(0x04251b0b) /* 0.259058994 */, 19 }, /* 7076 */ { MAD_F(0x04254e3d) /* 0.259107817 */, 19 }, /* 7077 */ { MAD_F(0x0425816f) /* 0.259156642 */, 19 }, /* 7078 */ { MAD_F(0x0425b4a2) /* 0.259205469 */, 19 }, /* 7079 */ { MAD_F(0x0425e7d6) /* 0.259254298 */, 19 }, /* 7080 */ { MAD_F(0x04261b0a) /* 0.259303130 */, 19 }, /* 7081 */ { MAD_F(0x04264e3f) /* 0.259351964 */, 19 }, /* 7082 */ { MAD_F(0x04268174) /* 0.259400801 */, 19 }, /* 7083 */ { MAD_F(0x0426b4aa) /* 0.259449639 */, 19 }, /* 7084 */ { MAD_F(0x0426e7e1) /* 0.259498480 */, 19 }, /* 7085 */ { MAD_F(0x04271b18) /* 0.259547324 */, 19 }, /* 7086 */ { MAD_F(0x04274e50) /* 0.259596169 */, 19 }, /* 7087 */ { MAD_F(0x04278188) /* 0.259645017 */, 19 }, /* 7088 */ { MAD_F(0x0427b4c2) /* 0.259693868 */, 19 }, /* 7089 */ { MAD_F(0x0427e7fb) /* 0.259742720 */, 19 }, /* 7090 */ { MAD_F(0x04281b36) /* 0.259791575 */, 19 }, /* 7091 */ { MAD_F(0x04284e71) /* 0.259840432 */, 19 }, /* 7092 */ { MAD_F(0x042881ac) /* 0.259889291 */, 19 }, /* 7093 */ { MAD_F(0x0428b4e8) /* 0.259938153 */, 19 }, /* 7094 */ { MAD_F(0x0428e825) /* 0.259987017 */, 19 }, /* 7095 */ { MAD_F(0x04291b63) /* 0.260035883 */, 19 }, /* 7096 */ { MAD_F(0x04294ea1) /* 0.260084752 */, 19 }, /* 7097 */ { MAD_F(0x042981df) /* 0.260133623 */, 19 }, /* 7098 */ { MAD_F(0x0429b51f) /* 0.260182496 */, 19 }, /* 7099 */ { MAD_F(0x0429e85f) /* 0.260231372 */, 19 }, /* 7100 */ { MAD_F(0x042a1b9f) /* 0.260280249 */, 19 }, /* 7101 */ { MAD_F(0x042a4ee0) /* 0.260329129 */, 19 }, /* 7102 */ { MAD_F(0x042a8222) /* 0.260378012 */, 19 }, /* 7103 */ { MAD_F(0x042ab564) /* 0.260426896 */, 19 }, /* 7104 */ { MAD_F(0x042ae8a7) /* 0.260475783 */, 19 }, /* 7105 */ { MAD_F(0x042b1beb) /* 0.260524673 */, 19 }, /* 7106 */ { MAD_F(0x042b4f2f) /* 0.260573564 */, 19 }, /* 7107 */ { MAD_F(0x042b8274) /* 0.260622458 */, 19 }, /* 7108 */ { MAD_F(0x042bb5ba) /* 0.260671354 */, 19 }, /* 7109 */ { MAD_F(0x042be900) /* 0.260720252 */, 19 }, /* 7110 */ { MAD_F(0x042c1c46) /* 0.260769153 */, 19 }, /* 7111 */ { MAD_F(0x042c4f8e) /* 0.260818056 */, 19 }, /* 7112 */ { MAD_F(0x042c82d6) /* 0.260866961 */, 19 }, /* 7113 */ { MAD_F(0x042cb61e) /* 0.260915869 */, 19 }, /* 7114 */ { MAD_F(0x042ce967) /* 0.260964779 */, 19 }, /* 7115 */ { MAD_F(0x042d1cb1) /* 0.261013691 */, 19 }, /* 7116 */ { MAD_F(0x042d4ffb) /* 0.261062606 */, 19 }, /* 7117 */ { MAD_F(0x042d8346) /* 0.261111522 */, 19 }, /* 7118 */ { MAD_F(0x042db692) /* 0.261160441 */, 19 }, /* 7119 */ { MAD_F(0x042de9de) /* 0.261209363 */, 19 }, /* 7120 */ { MAD_F(0x042e1d2b) /* 0.261258286 */, 19 }, /* 7121 */ { MAD_F(0x042e5078) /* 0.261307212 */, 19 }, /* 7122 */ { MAD_F(0x042e83c6) /* 0.261356140 */, 19 }, /* 7123 */ { MAD_F(0x042eb715) /* 0.261405071 */, 19 }, /* 7124 */ { MAD_F(0x042eea64) /* 0.261454004 */, 19 }, /* 7125 */ { MAD_F(0x042f1db4) /* 0.261502939 */, 19 }, /* 7126 */ { MAD_F(0x042f5105) /* 0.261551876 */, 19 }, /* 7127 */ { MAD_F(0x042f8456) /* 0.261600816 */, 19 }, /* 7128 */ { MAD_F(0x042fb7a8) /* 0.261649758 */, 19 }, /* 7129 */ { MAD_F(0x042feafa) /* 0.261698702 */, 19 }, /* 7130 */ { MAD_F(0x04301e4d) /* 0.261747649 */, 19 }, /* 7131 */ { MAD_F(0x043051a1) /* 0.261796597 */, 19 }, /* 7132 */ { MAD_F(0x043084f5) /* 0.261845548 */, 19 }, /* 7133 */ { MAD_F(0x0430b84a) /* 0.261894502 */, 19 }, /* 7134 */ { MAD_F(0x0430eb9f) /* 0.261943458 */, 19 }, /* 7135 */ { MAD_F(0x04311ef5) /* 0.261992416 */, 19 }, /* 7136 */ { MAD_F(0x0431524c) /* 0.262041376 */, 19 }, /* 7137 */ { MAD_F(0x043185a3) /* 0.262090338 */, 19 }, /* 7138 */ { MAD_F(0x0431b8fb) /* 0.262139303 */, 19 }, /* 7139 */ { MAD_F(0x0431ec54) /* 0.262188270 */, 19 }, /* 7140 */ { MAD_F(0x04321fad) /* 0.262237240 */, 19 }, /* 7141 */ { MAD_F(0x04325306) /* 0.262286211 */, 19 }, /* 7142 */ { MAD_F(0x04328661) /* 0.262335185 */, 19 }, /* 7143 */ { MAD_F(0x0432b9bc) /* 0.262384162 */, 19 }, /* 7144 */ { MAD_F(0x0432ed17) /* 0.262433140 */, 19 }, /* 7145 */ { MAD_F(0x04332074) /* 0.262482121 */, 19 }, /* 7146 */ { MAD_F(0x043353d0) /* 0.262531104 */, 19 }, /* 7147 */ { MAD_F(0x0433872e) /* 0.262580089 */, 19 }, /* 7148 */ { MAD_F(0x0433ba8c) /* 0.262629077 */, 19 }, /* 7149 */ { MAD_F(0x0433edea) /* 0.262678067 */, 19 }, /* 7150 */ { MAD_F(0x0434214a) /* 0.262727059 */, 19 }, /* 7151 */ { MAD_F(0x043454aa) /* 0.262776054 */, 19 }, /* 7152 */ { MAD_F(0x0434880a) /* 0.262825051 */, 19 }, /* 7153 */ { MAD_F(0x0434bb6b) /* 0.262874050 */, 19 }, /* 7154 */ { MAD_F(0x0434eecd) /* 0.262923051 */, 19 }, /* 7155 */ { MAD_F(0x0435222f) /* 0.262972055 */, 19 }, /* 7156 */ { MAD_F(0x04355592) /* 0.263021061 */, 19 }, /* 7157 */ { MAD_F(0x043588f6) /* 0.263070069 */, 19 }, /* 7158 */ { MAD_F(0x0435bc5a) /* 0.263119079 */, 19 }, /* 7159 */ { MAD_F(0x0435efbf) /* 0.263168092 */, 19 }, /* 7160 */ { MAD_F(0x04362324) /* 0.263217107 */, 19 }, /* 7161 */ { MAD_F(0x0436568a) /* 0.263266125 */, 19 }, /* 7162 */ { MAD_F(0x043689f1) /* 0.263315144 */, 19 }, /* 7163 */ { MAD_F(0x0436bd58) /* 0.263364166 */, 19 }, /* 7164 */ { MAD_F(0x0436f0c0) /* 0.263413191 */, 19 }, /* 7165 */ { MAD_F(0x04372428) /* 0.263462217 */, 19 }, /* 7166 */ { MAD_F(0x04375791) /* 0.263511246 */, 19 }, /* 7167 */ { MAD_F(0x04378afb) /* 0.263560277 */, 19 }, /* 7168 */ { MAD_F(0x0437be65) /* 0.263609310 */, 19 }, /* 7169 */ { MAD_F(0x0437f1d0) /* 0.263658346 */, 19 }, /* 7170 */ { MAD_F(0x0438253c) /* 0.263707384 */, 19 }, /* 7171 */ { MAD_F(0x043858a8) /* 0.263756424 */, 19 }, /* 7172 */ { MAD_F(0x04388c14) /* 0.263805466 */, 19 }, /* 7173 */ { MAD_F(0x0438bf82) /* 0.263854511 */, 19 }, /* 7174 */ { MAD_F(0x0438f2f0) /* 0.263903558 */, 19 }, /* 7175 */ { MAD_F(0x0439265e) /* 0.263952607 */, 19 }, /* 7176 */ { MAD_F(0x043959cd) /* 0.264001659 */, 19 }, /* 7177 */ { MAD_F(0x04398d3d) /* 0.264050713 */, 19 }, /* 7178 */ { MAD_F(0x0439c0ae) /* 0.264099769 */, 19 }, /* 7179 */ { MAD_F(0x0439f41f) /* 0.264148827 */, 19 }, /* 7180 */ { MAD_F(0x043a2790) /* 0.264197888 */, 19 }, /* 7181 */ { MAD_F(0x043a5b02) /* 0.264246951 */, 19 }, /* 7182 */ { MAD_F(0x043a8e75) /* 0.264296016 */, 19 }, /* 7183 */ { MAD_F(0x043ac1e9) /* 0.264345084 */, 19 }, /* 7184 */ { MAD_F(0x043af55d) /* 0.264394153 */, 19 }, /* 7185 */ { MAD_F(0x043b28d2) /* 0.264443225 */, 19 }, /* 7186 */ { MAD_F(0x043b5c47) /* 0.264492300 */, 19 }, /* 7187 */ { MAD_F(0x043b8fbd) /* 0.264541376 */, 19 }, /* 7188 */ { MAD_F(0x043bc333) /* 0.264590455 */, 19 }, /* 7189 */ { MAD_F(0x043bf6aa) /* 0.264639536 */, 19 }, /* 7190 */ { MAD_F(0x043c2a22) /* 0.264688620 */, 19 }, /* 7191 */ { MAD_F(0x043c5d9a) /* 0.264737706 */, 19 }, /* 7192 */ { MAD_F(0x043c9113) /* 0.264786794 */, 19 }, /* 7193 */ { MAD_F(0x043cc48d) /* 0.264835884 */, 19 }, /* 7194 */ { MAD_F(0x043cf807) /* 0.264884976 */, 19 }, /* 7195 */ { MAD_F(0x043d2b82) /* 0.264934071 */, 19 }, /* 7196 */ { MAD_F(0x043d5efd) /* 0.264983168 */, 19 }, /* 7197 */ { MAD_F(0x043d9279) /* 0.265032268 */, 19 }, /* 7198 */ { MAD_F(0x043dc5f6) /* 0.265081369 */, 19 }, /* 7199 */ { MAD_F(0x043df973) /* 0.265130473 */, 19 }, /* 7200 */ { MAD_F(0x043e2cf1) /* 0.265179580 */, 19 }, /* 7201 */ { MAD_F(0x043e6070) /* 0.265228688 */, 19 }, /* 7202 */ { MAD_F(0x043e93ef) /* 0.265277799 */, 19 }, /* 7203 */ { MAD_F(0x043ec76e) /* 0.265326912 */, 19 }, /* 7204 */ { MAD_F(0x043efaef) /* 0.265376027 */, 19 }, /* 7205 */ { MAD_F(0x043f2e6f) /* 0.265425145 */, 19 }, /* 7206 */ { MAD_F(0x043f61f1) /* 0.265474264 */, 19 }, /* 7207 */ { MAD_F(0x043f9573) /* 0.265523387 */, 19 }, /* 7208 */ { MAD_F(0x043fc8f6) /* 0.265572511 */, 19 }, /* 7209 */ { MAD_F(0x043ffc79) /* 0.265621638 */, 19 }, /* 7210 */ { MAD_F(0x04402ffd) /* 0.265670766 */, 19 }, /* 7211 */ { MAD_F(0x04406382) /* 0.265719898 */, 19 }, /* 7212 */ { MAD_F(0x04409707) /* 0.265769031 */, 19 }, /* 7213 */ { MAD_F(0x0440ca8d) /* 0.265818167 */, 19 }, /* 7214 */ { MAD_F(0x0440fe13) /* 0.265867305 */, 19 }, /* 7215 */ { MAD_F(0x0441319a) /* 0.265916445 */, 19 }, /* 7216 */ { MAD_F(0x04416522) /* 0.265965588 */, 19 }, /* 7217 */ { MAD_F(0x044198aa) /* 0.266014732 */, 19 }, /* 7218 */ { MAD_F(0x0441cc33) /* 0.266063880 */, 19 }, /* 7219 */ { MAD_F(0x0441ffbc) /* 0.266113029 */, 19 }, /* 7220 */ { MAD_F(0x04423346) /* 0.266162181 */, 19 }, /* 7221 */ { MAD_F(0x044266d1) /* 0.266211334 */, 19 }, /* 7222 */ { MAD_F(0x04429a5c) /* 0.266260491 */, 19 }, /* 7223 */ { MAD_F(0x0442cde8) /* 0.266309649 */, 19 }, /* 7224 */ { MAD_F(0x04430174) /* 0.266358810 */, 19 }, /* 7225 */ { MAD_F(0x04433501) /* 0.266407973 */, 19 }, /* 7226 */ { MAD_F(0x0443688f) /* 0.266457138 */, 19 }, /* 7227 */ { MAD_F(0x04439c1d) /* 0.266506305 */, 19 }, /* 7228 */ { MAD_F(0x0443cfac) /* 0.266555475 */, 19 }, /* 7229 */ { MAD_F(0x0444033c) /* 0.266604647 */, 19 }, /* 7230 */ { MAD_F(0x044436cc) /* 0.266653822 */, 19 }, /* 7231 */ { MAD_F(0x04446a5d) /* 0.266702998 */, 19 }, /* 7232 */ { MAD_F(0x04449dee) /* 0.266752177 */, 19 }, /* 7233 */ { MAD_F(0x0444d180) /* 0.266801358 */, 19 }, /* 7234 */ { MAD_F(0x04450513) /* 0.266850541 */, 19 }, /* 7235 */ { MAD_F(0x044538a6) /* 0.266899727 */, 19 }, /* 7236 */ { MAD_F(0x04456c39) /* 0.266948915 */, 19 }, /* 7237 */ { MAD_F(0x04459fce) /* 0.266998105 */, 19 }, /* 7238 */ { MAD_F(0x0445d363) /* 0.267047298 */, 19 }, /* 7239 */ { MAD_F(0x044606f8) /* 0.267096492 */, 19 }, /* 7240 */ { MAD_F(0x04463a8f) /* 0.267145689 */, 19 }, /* 7241 */ { MAD_F(0x04466e25) /* 0.267194888 */, 19 }, /* 7242 */ { MAD_F(0x0446a1bd) /* 0.267244090 */, 19 }, /* 7243 */ { MAD_F(0x0446d555) /* 0.267293294 */, 19 }, /* 7244 */ { MAD_F(0x044708ee) /* 0.267342500 */, 19 }, /* 7245 */ { MAD_F(0x04473c87) /* 0.267391708 */, 19 }, /* 7246 */ { MAD_F(0x04477021) /* 0.267440919 */, 19 }, /* 7247 */ { MAD_F(0x0447a3bb) /* 0.267490131 */, 19 }, /* 7248 */ { MAD_F(0x0447d756) /* 0.267539347 */, 19 }, /* 7249 */ { MAD_F(0x04480af2) /* 0.267588564 */, 19 }, /* 7250 */ { MAD_F(0x04483e8e) /* 0.267637783 */, 19 }, /* 7251 */ { MAD_F(0x0448722b) /* 0.267687005 */, 19 }, /* 7252 */ { MAD_F(0x0448a5c9) /* 0.267736229 */, 19 }, /* 7253 */ { MAD_F(0x0448d967) /* 0.267785456 */, 19 }, /* 7254 */ { MAD_F(0x04490d05) /* 0.267834685 */, 19 }, /* 7255 */ { MAD_F(0x044940a5) /* 0.267883915 */, 19 }, /* 7256 */ { MAD_F(0x04497445) /* 0.267933149 */, 19 }, /* 7257 */ { MAD_F(0x0449a7e5) /* 0.267982384 */, 19 }, /* 7258 */ { MAD_F(0x0449db86) /* 0.268031622 */, 19 }, /* 7259 */ { MAD_F(0x044a0f28) /* 0.268080862 */, 19 }, /* 7260 */ { MAD_F(0x044a42ca) /* 0.268130104 */, 19 }, /* 7261 */ { MAD_F(0x044a766d) /* 0.268179349 */, 19 }, /* 7262 */ { MAD_F(0x044aaa11) /* 0.268228595 */, 19 }, /* 7263 */ { MAD_F(0x044addb5) /* 0.268277844 */, 19 }, /* 7264 */ { MAD_F(0x044b115a) /* 0.268327096 */, 19 }, /* 7265 */ { MAD_F(0x044b44ff) /* 0.268376349 */, 19 }, /* 7266 */ { MAD_F(0x044b78a5) /* 0.268425605 */, 19 }, /* 7267 */ { MAD_F(0x044bac4c) /* 0.268474863 */, 19 }, /* 7268 */ { MAD_F(0x044bdff3) /* 0.268524123 */, 19 }, /* 7269 */ { MAD_F(0x044c139b) /* 0.268573386 */, 19 }, /* 7270 */ { MAD_F(0x044c4743) /* 0.268622651 */, 19 }, /* 7271 */ { MAD_F(0x044c7aec) /* 0.268671918 */, 19 }, /* 7272 */ { MAD_F(0x044cae96) /* 0.268721187 */, 19 }, /* 7273 */ { MAD_F(0x044ce240) /* 0.268770459 */, 19 }, /* 7274 */ { MAD_F(0x044d15eb) /* 0.268819733 */, 19 }, /* 7275 */ { MAD_F(0x044d4997) /* 0.268869009 */, 19 }, /* 7276 */ { MAD_F(0x044d7d43) /* 0.268918287 */, 19 }, /* 7277 */ { MAD_F(0x044db0ef) /* 0.268967568 */, 19 }, /* 7278 */ { MAD_F(0x044de49d) /* 0.269016851 */, 19 }, /* 7279 */ { MAD_F(0x044e184b) /* 0.269066136 */, 19 }, /* 7280 */ { MAD_F(0x044e4bf9) /* 0.269115423 */, 19 }, /* 7281 */ { MAD_F(0x044e7fa8) /* 0.269164713 */, 19 }, /* 7282 */ { MAD_F(0x044eb358) /* 0.269214005 */, 19 }, /* 7283 */ { MAD_F(0x044ee708) /* 0.269263299 */, 19 }, /* 7284 */ { MAD_F(0x044f1ab9) /* 0.269312595 */, 19 }, /* 7285 */ { MAD_F(0x044f4e6b) /* 0.269361894 */, 19 }, /* 7286 */ { MAD_F(0x044f821d) /* 0.269411195 */, 19 }, /* 7287 */ { MAD_F(0x044fb5cf) /* 0.269460498 */, 19 }, /* 7288 */ { MAD_F(0x044fe983) /* 0.269509804 */, 19 }, /* 7289 */ { MAD_F(0x04501d37) /* 0.269559111 */, 19 }, /* 7290 */ { MAD_F(0x045050eb) /* 0.269608421 */, 19 }, /* 7291 */ { MAD_F(0x045084a0) /* 0.269657734 */, 19 }, /* 7292 */ { MAD_F(0x0450b856) /* 0.269707048 */, 19 }, /* 7293 */ { MAD_F(0x0450ec0d) /* 0.269756365 */, 19 }, /* 7294 */ { MAD_F(0x04511fc4) /* 0.269805684 */, 19 }, /* 7295 */ { MAD_F(0x0451537b) /* 0.269855005 */, 19 }, /* 7296 */ { MAD_F(0x04518733) /* 0.269904329 */, 19 }, /* 7297 */ { MAD_F(0x0451baec) /* 0.269953654 */, 19 }, /* 7298 */ { MAD_F(0x0451eea5) /* 0.270002982 */, 19 }, /* 7299 */ { MAD_F(0x0452225f) /* 0.270052313 */, 19 }, /* 7300 */ { MAD_F(0x0452561a) /* 0.270101645 */, 19 }, /* 7301 */ { MAD_F(0x045289d5) /* 0.270150980 */, 19 }, /* 7302 */ { MAD_F(0x0452bd91) /* 0.270200317 */, 19 }, /* 7303 */ { MAD_F(0x0452f14d) /* 0.270249656 */, 19 }, /* 7304 */ { MAD_F(0x0453250a) /* 0.270298998 */, 19 }, /* 7305 */ { MAD_F(0x045358c8) /* 0.270348341 */, 19 }, /* 7306 */ { MAD_F(0x04538c86) /* 0.270397687 */, 19 }, /* 7307 */ { MAD_F(0x0453c045) /* 0.270447036 */, 19 }, /* 7308 */ { MAD_F(0x0453f405) /* 0.270496386 */, 19 }, /* 7309 */ { MAD_F(0x045427c5) /* 0.270545739 */, 19 }, /* 7310 */ { MAD_F(0x04545b85) /* 0.270595094 */, 19 }, /* 7311 */ { MAD_F(0x04548f46) /* 0.270644451 */, 19 }, /* 7312 */ { MAD_F(0x0454c308) /* 0.270693811 */, 19 }, /* 7313 */ { MAD_F(0x0454f6cb) /* 0.270743173 */, 19 }, /* 7314 */ { MAD_F(0x04552a8e) /* 0.270792537 */, 19 }, /* 7315 */ { MAD_F(0x04555e51) /* 0.270841903 */, 19 }, /* 7316 */ { MAD_F(0x04559216) /* 0.270891271 */, 19 }, /* 7317 */ { MAD_F(0x0455c5db) /* 0.270940642 */, 19 }, /* 7318 */ { MAD_F(0x0455f9a0) /* 0.270990015 */, 19 }, /* 7319 */ { MAD_F(0x04562d66) /* 0.271039390 */, 19 }, /* 7320 */ { MAD_F(0x0456612d) /* 0.271088768 */, 19 }, /* 7321 */ { MAD_F(0x045694f4) /* 0.271138148 */, 19 }, /* 7322 */ { MAD_F(0x0456c8bc) /* 0.271187530 */, 19 }, /* 7323 */ { MAD_F(0x0456fc84) /* 0.271236914 */, 19 }, /* 7324 */ { MAD_F(0x0457304e) /* 0.271286301 */, 19 }, /* 7325 */ { MAD_F(0x04576417) /* 0.271335689 */, 19 }, /* 7326 */ { MAD_F(0x045797e2) /* 0.271385080 */, 19 }, /* 7327 */ { MAD_F(0x0457cbac) /* 0.271434474 */, 19 }, /* 7328 */ { MAD_F(0x0457ff78) /* 0.271483869 */, 19 }, /* 7329 */ { MAD_F(0x04583344) /* 0.271533267 */, 19 }, /* 7330 */ { MAD_F(0x04586711) /* 0.271582667 */, 19 }, /* 7331 */ { MAD_F(0x04589ade) /* 0.271632069 */, 19 }, /* 7332 */ { MAD_F(0x0458ceac) /* 0.271681474 */, 19 }, /* 7333 */ { MAD_F(0x0459027b) /* 0.271730880 */, 19 }, /* 7334 */ { MAD_F(0x0459364a) /* 0.271780289 */, 19 }, /* 7335 */ { MAD_F(0x04596a19) /* 0.271829701 */, 19 }, /* 7336 */ { MAD_F(0x04599dea) /* 0.271879114 */, 19 }, /* 7337 */ { MAD_F(0x0459d1bb) /* 0.271928530 */, 19 }, /* 7338 */ { MAD_F(0x045a058c) /* 0.271977948 */, 19 }, /* 7339 */ { MAD_F(0x045a395e) /* 0.272027368 */, 19 }, /* 7340 */ { MAD_F(0x045a6d31) /* 0.272076790 */, 19 }, /* 7341 */ { MAD_F(0x045aa104) /* 0.272126215 */, 19 }, /* 7342 */ { MAD_F(0x045ad4d8) /* 0.272175642 */, 19 }, /* 7343 */ { MAD_F(0x045b08ad) /* 0.272225071 */, 19 }, /* 7344 */ { MAD_F(0x045b3c82) /* 0.272274503 */, 19 }, /* 7345 */ { MAD_F(0x045b7058) /* 0.272323936 */, 19 }, /* 7346 */ { MAD_F(0x045ba42e) /* 0.272373372 */, 19 }, /* 7347 */ { MAD_F(0x045bd805) /* 0.272422810 */, 19 }, /* 7348 */ { MAD_F(0x045c0bdd) /* 0.272472251 */, 19 }, /* 7349 */ { MAD_F(0x045c3fb5) /* 0.272521693 */, 19 }, /* 7350 */ { MAD_F(0x045c738e) /* 0.272571138 */, 19 }, /* 7351 */ { MAD_F(0x045ca767) /* 0.272620585 */, 19 }, /* 7352 */ { MAD_F(0x045cdb41) /* 0.272670035 */, 19 }, /* 7353 */ { MAD_F(0x045d0f1b) /* 0.272719486 */, 19 }, /* 7354 */ { MAD_F(0x045d42f7) /* 0.272768940 */, 19 }, /* 7355 */ { MAD_F(0x045d76d2) /* 0.272818396 */, 19 }, /* 7356 */ { MAD_F(0x045daaaf) /* 0.272867855 */, 19 }, /* 7357 */ { MAD_F(0x045dde8c) /* 0.272917315 */, 19 }, /* 7358 */ { MAD_F(0x045e1269) /* 0.272966778 */, 19 }, /* 7359 */ { MAD_F(0x045e4647) /* 0.273016243 */, 19 }, /* 7360 */ { MAD_F(0x045e7a26) /* 0.273065710 */, 19 }, /* 7361 */ { MAD_F(0x045eae06) /* 0.273115180 */, 19 }, /* 7362 */ { MAD_F(0x045ee1e6) /* 0.273164652 */, 19 }, /* 7363 */ { MAD_F(0x045f15c6) /* 0.273214126 */, 19 }, /* 7364 */ { MAD_F(0x045f49a7) /* 0.273263602 */, 19 }, /* 7365 */ { MAD_F(0x045f7d89) /* 0.273313081 */, 19 }, /* 7366 */ { MAD_F(0x045fb16c) /* 0.273362561 */, 19 }, /* 7367 */ { MAD_F(0x045fe54f) /* 0.273412044 */, 19 }, /* 7368 */ { MAD_F(0x04601932) /* 0.273461530 */, 19 }, /* 7369 */ { MAD_F(0x04604d16) /* 0.273511017 */, 19 }, /* 7370 */ { MAD_F(0x046080fb) /* 0.273560507 */, 19 }, /* 7371 */ { MAD_F(0x0460b4e1) /* 0.273609999 */, 19 }, /* 7372 */ { MAD_F(0x0460e8c7) /* 0.273659493 */, 19 }, /* 7373 */ { MAD_F(0x04611cad) /* 0.273708989 */, 19 }, /* 7374 */ { MAD_F(0x04615094) /* 0.273758488 */, 19 }, /* 7375 */ { MAD_F(0x0461847c) /* 0.273807989 */, 19 }, /* 7376 */ { MAD_F(0x0461b864) /* 0.273857492 */, 19 }, /* 7377 */ { MAD_F(0x0461ec4d) /* 0.273906997 */, 19 }, /* 7378 */ { MAD_F(0x04622037) /* 0.273956505 */, 19 }, /* 7379 */ { MAD_F(0x04625421) /* 0.274006015 */, 19 }, /* 7380 */ { MAD_F(0x0462880c) /* 0.274055527 */, 19 }, /* 7381 */ { MAD_F(0x0462bbf7) /* 0.274105041 */, 19 }, /* 7382 */ { MAD_F(0x0462efe3) /* 0.274154558 */, 19 }, /* 7383 */ { MAD_F(0x046323d0) /* 0.274204076 */, 19 }, /* 7384 */ { MAD_F(0x046357bd) /* 0.274253597 */, 19 }, /* 7385 */ { MAD_F(0x04638bab) /* 0.274303121 */, 19 }, /* 7386 */ { MAD_F(0x0463bf99) /* 0.274352646 */, 19 }, /* 7387 */ { MAD_F(0x0463f388) /* 0.274402174 */, 19 }, /* 7388 */ { MAD_F(0x04642778) /* 0.274451704 */, 19 }, /* 7389 */ { MAD_F(0x04645b68) /* 0.274501236 */, 19 }, /* 7390 */ { MAD_F(0x04648f59) /* 0.274550771 */, 19 }, /* 7391 */ { MAD_F(0x0464c34a) /* 0.274600307 */, 19 }, /* 7392 */ { MAD_F(0x0464f73c) /* 0.274649846 */, 19 }, /* 7393 */ { MAD_F(0x04652b2f) /* 0.274699387 */, 19 }, /* 7394 */ { MAD_F(0x04655f22) /* 0.274748931 */, 19 }, /* 7395 */ { MAD_F(0x04659316) /* 0.274798476 */, 19 }, /* 7396 */ { MAD_F(0x0465c70a) /* 0.274848024 */, 19 }, /* 7397 */ { MAD_F(0x0465faff) /* 0.274897574 */, 19 }, /* 7398 */ { MAD_F(0x04662ef5) /* 0.274947126 */, 19 }, /* 7399 */ { MAD_F(0x046662eb) /* 0.274996681 */, 19 }, /* 7400 */ { MAD_F(0x046696e2) /* 0.275046238 */, 19 }, /* 7401 */ { MAD_F(0x0466cad9) /* 0.275095797 */, 19 }, /* 7402 */ { MAD_F(0x0466fed1) /* 0.275145358 */, 19 }, /* 7403 */ { MAD_F(0x046732ca) /* 0.275194921 */, 19 }, /* 7404 */ { MAD_F(0x046766c3) /* 0.275244487 */, 19 }, /* 7405 */ { MAD_F(0x04679abd) /* 0.275294055 */, 19 }, /* 7406 */ { MAD_F(0x0467ceb7) /* 0.275343625 */, 19 }, /* 7407 */ { MAD_F(0x046802b2) /* 0.275393198 */, 19 }, /* 7408 */ { MAD_F(0x046836ae) /* 0.275442772 */, 19 }, /* 7409 */ { MAD_F(0x04686aaa) /* 0.275492349 */, 19 }, /* 7410 */ { MAD_F(0x04689ea7) /* 0.275541928 */, 19 }, /* 7411 */ { MAD_F(0x0468d2a4) /* 0.275591509 */, 19 }, /* 7412 */ { MAD_F(0x046906a2) /* 0.275641093 */, 19 }, /* 7413 */ { MAD_F(0x04693aa1) /* 0.275690679 */, 19 }, /* 7414 */ { MAD_F(0x04696ea0) /* 0.275740267 */, 19 }, /* 7415 */ { MAD_F(0x0469a2a0) /* 0.275789857 */, 19 }, /* 7416 */ { MAD_F(0x0469d6a0) /* 0.275839449 */, 19 }, /* 7417 */ { MAD_F(0x046a0aa1) /* 0.275889044 */, 19 }, /* 7418 */ { MAD_F(0x046a3ea3) /* 0.275938641 */, 19 }, /* 7419 */ { MAD_F(0x046a72a5) /* 0.275988240 */, 19 }, /* 7420 */ { MAD_F(0x046aa6a8) /* 0.276037842 */, 19 }, /* 7421 */ { MAD_F(0x046adaab) /* 0.276087445 */, 19 }, /* 7422 */ { MAD_F(0x046b0eaf) /* 0.276137051 */, 19 }, /* 7423 */ { MAD_F(0x046b42b3) /* 0.276186659 */, 19 }, /* 7424 */ { MAD_F(0x046b76b9) /* 0.276236269 */, 19 }, /* 7425 */ { MAD_F(0x046baabe) /* 0.276285882 */, 19 }, /* 7426 */ { MAD_F(0x046bdec5) /* 0.276335497 */, 19 }, /* 7427 */ { MAD_F(0x046c12cc) /* 0.276385113 */, 19 }, /* 7428 */ { MAD_F(0x046c46d3) /* 0.276434733 */, 19 }, /* 7429 */ { MAD_F(0x046c7adb) /* 0.276484354 */, 19 }, /* 7430 */ { MAD_F(0x046caee4) /* 0.276533978 */, 19 }, /* 7431 */ { MAD_F(0x046ce2ee) /* 0.276583604 */, 19 }, /* 7432 */ { MAD_F(0x046d16f7) /* 0.276633232 */, 19 }, /* 7433 */ { MAD_F(0x046d4b02) /* 0.276682862 */, 19 }, /* 7434 */ { MAD_F(0x046d7f0d) /* 0.276732495 */, 19 }, /* 7435 */ { MAD_F(0x046db319) /* 0.276782129 */, 19 }, /* 7436 */ { MAD_F(0x046de725) /* 0.276831766 */, 19 }, /* 7437 */ { MAD_F(0x046e1b32) /* 0.276881406 */, 19 }, /* 7438 */ { MAD_F(0x046e4f40) /* 0.276931047 */, 19 }, /* 7439 */ { MAD_F(0x046e834e) /* 0.276980691 */, 19 }, /* 7440 */ { MAD_F(0x046eb75c) /* 0.277030337 */, 19 }, /* 7441 */ { MAD_F(0x046eeb6c) /* 0.277079985 */, 19 }, /* 7442 */ { MAD_F(0x046f1f7c) /* 0.277129635 */, 19 }, /* 7443 */ { MAD_F(0x046f538c) /* 0.277179288 */, 19 }, /* 7444 */ { MAD_F(0x046f879d) /* 0.277228942 */, 19 }, /* 7445 */ { MAD_F(0x046fbbaf) /* 0.277278600 */, 19 }, /* 7446 */ { MAD_F(0x046fefc1) /* 0.277328259 */, 19 }, /* 7447 */ { MAD_F(0x047023d4) /* 0.277377920 */, 19 }, /* 7448 */ { MAD_F(0x047057e8) /* 0.277427584 */, 19 }, /* 7449 */ { MAD_F(0x04708bfc) /* 0.277477250 */, 19 }, /* 7450 */ { MAD_F(0x0470c011) /* 0.277526918 */, 19 }, /* 7451 */ { MAD_F(0x0470f426) /* 0.277576588 */, 19 }, /* 7452 */ { MAD_F(0x0471283c) /* 0.277626261 */, 19 }, /* 7453 */ { MAD_F(0x04715c52) /* 0.277675936 */, 19 }, /* 7454 */ { MAD_F(0x04719069) /* 0.277725613 */, 19 }, /* 7455 */ { MAD_F(0x0471c481) /* 0.277775292 */, 19 }, /* 7456 */ { MAD_F(0x0471f899) /* 0.277824973 */, 19 }, /* 7457 */ { MAD_F(0x04722cb2) /* 0.277874657 */, 19 }, /* 7458 */ { MAD_F(0x047260cc) /* 0.277924343 */, 19 }, /* 7459 */ { MAD_F(0x047294e6) /* 0.277974031 */, 19 }, /* 7460 */ { MAD_F(0x0472c900) /* 0.278023722 */, 19 }, /* 7461 */ { MAD_F(0x0472fd1b) /* 0.278073414 */, 19 }, /* 7462 */ { MAD_F(0x04733137) /* 0.278123109 */, 19 }, /* 7463 */ { MAD_F(0x04736554) /* 0.278172806 */, 19 }, /* 7464 */ { MAD_F(0x04739971) /* 0.278222505 */, 19 }, /* 7465 */ { MAD_F(0x0473cd8e) /* 0.278272207 */, 19 }, /* 7466 */ { MAD_F(0x047401ad) /* 0.278321910 */, 19 }, /* 7467 */ { MAD_F(0x047435cb) /* 0.278371616 */, 19 }, /* 7468 */ { MAD_F(0x047469eb) /* 0.278421324 */, 19 }, /* 7469 */ { MAD_F(0x04749e0b) /* 0.278471035 */, 19 }, /* 7470 */ { MAD_F(0x0474d22c) /* 0.278520747 */, 19 }, /* 7471 */ { MAD_F(0x0475064d) /* 0.278570462 */, 19 }, /* 7472 */ { MAD_F(0x04753a6f) /* 0.278620179 */, 19 }, /* 7473 */ { MAD_F(0x04756e91) /* 0.278669898 */, 19 }, /* 7474 */ { MAD_F(0x0475a2b4) /* 0.278719619 */, 19 }, /* 7475 */ { MAD_F(0x0475d6d7) /* 0.278769343 */, 19 }, /* 7476 */ { MAD_F(0x04760afc) /* 0.278819069 */, 19 }, /* 7477 */ { MAD_F(0x04763f20) /* 0.278868797 */, 19 }, /* 7478 */ { MAD_F(0x04767346) /* 0.278918527 */, 19 }, /* 7479 */ { MAD_F(0x0476a76c) /* 0.278968260 */, 19 }, /* 7480 */ { MAD_F(0x0476db92) /* 0.279017995 */, 19 }, /* 7481 */ { MAD_F(0x04770fba) /* 0.279067731 */, 19 }, /* 7482 */ { MAD_F(0x047743e1) /* 0.279117471 */, 19 }, /* 7483 */ { MAD_F(0x0477780a) /* 0.279167212 */, 19 }, /* 7484 */ { MAD_F(0x0477ac33) /* 0.279216956 */, 19 }, /* 7485 */ { MAD_F(0x0477e05c) /* 0.279266701 */, 19 }, /* 7486 */ { MAD_F(0x04781486) /* 0.279316449 */, 19 }, /* 7487 */ { MAD_F(0x047848b1) /* 0.279366200 */, 19 }, /* 7488 */ { MAD_F(0x04787cdc) /* 0.279415952 */, 19 }, /* 7489 */ { MAD_F(0x0478b108) /* 0.279465707 */, 19 }, /* 7490 */ { MAD_F(0x0478e535) /* 0.279515464 */, 19 }, /* 7491 */ { MAD_F(0x04791962) /* 0.279565223 */, 19 }, /* 7492 */ { MAD_F(0x04794d8f) /* 0.279614984 */, 19 }, /* 7493 */ { MAD_F(0x047981be) /* 0.279664748 */, 19 }, /* 7494 */ { MAD_F(0x0479b5ed) /* 0.279714513 */, 19 }, /* 7495 */ { MAD_F(0x0479ea1c) /* 0.279764281 */, 19 }, /* 7496 */ { MAD_F(0x047a1e4c) /* 0.279814051 */, 19 }, /* 7497 */ { MAD_F(0x047a527d) /* 0.279863824 */, 19 }, /* 7498 */ { MAD_F(0x047a86ae) /* 0.279913598 */, 19 }, /* 7499 */ { MAD_F(0x047abae0) /* 0.279963375 */, 19 }, /* 7500 */ { MAD_F(0x047aef12) /* 0.280013154 */, 19 }, /* 7501 */ { MAD_F(0x047b2346) /* 0.280062935 */, 19 }, /* 7502 */ { MAD_F(0x047b5779) /* 0.280112719 */, 19 }, /* 7503 */ { MAD_F(0x047b8bad) /* 0.280162504 */, 19 }, /* 7504 */ { MAD_F(0x047bbfe2) /* 0.280212292 */, 19 }, /* 7505 */ { MAD_F(0x047bf418) /* 0.280262082 */, 19 }, /* 7506 */ { MAD_F(0x047c284e) /* 0.280311875 */, 19 }, /* 7507 */ { MAD_F(0x047c5c84) /* 0.280361669 */, 19 }, /* 7508 */ { MAD_F(0x047c90bb) /* 0.280411466 */, 19 }, /* 7509 */ { MAD_F(0x047cc4f3) /* 0.280461265 */, 19 }, /* 7510 */ { MAD_F(0x047cf92c) /* 0.280511066 */, 19 }, /* 7511 */ { MAD_F(0x047d2d65) /* 0.280560869 */, 19 }, /* 7512 */ { MAD_F(0x047d619e) /* 0.280610675 */, 19 }, /* 7513 */ { MAD_F(0x047d95d8) /* 0.280660483 */, 19 }, /* 7514 */ { MAD_F(0x047dca13) /* 0.280710292 */, 19 }, /* 7515 */ { MAD_F(0x047dfe4e) /* 0.280760105 */, 19 }, /* 7516 */ { MAD_F(0x047e328a) /* 0.280809919 */, 19 }, /* 7517 */ { MAD_F(0x047e66c7) /* 0.280859736 */, 19 }, /* 7518 */ { MAD_F(0x047e9b04) /* 0.280909554 */, 19 }, /* 7519 */ { MAD_F(0x047ecf42) /* 0.280959375 */, 19 }, /* 7520 */ { MAD_F(0x047f0380) /* 0.281009199 */, 19 }, /* 7521 */ { MAD_F(0x047f37bf) /* 0.281059024 */, 19 }, /* 7522 */ { MAD_F(0x047f6bff) /* 0.281108852 */, 19 }, /* 7523 */ { MAD_F(0x047fa03f) /* 0.281158682 */, 19 }, /* 7524 */ { MAD_F(0x047fd47f) /* 0.281208514 */, 19 }, /* 7525 */ { MAD_F(0x048008c1) /* 0.281258348 */, 19 }, /* 7526 */ { MAD_F(0x04803d02) /* 0.281308184 */, 19 }, /* 7527 */ { MAD_F(0x04807145) /* 0.281358023 */, 19 }, /* 7528 */ { MAD_F(0x0480a588) /* 0.281407864 */, 19 }, /* 7529 */ { MAD_F(0x0480d9cc) /* 0.281457707 */, 19 }, /* 7530 */ { MAD_F(0x04810e10) /* 0.281507552 */, 19 }, /* 7531 */ { MAD_F(0x04814255) /* 0.281557400 */, 19 }, /* 7532 */ { MAD_F(0x0481769a) /* 0.281607250 */, 19 }, /* 7533 */ { MAD_F(0x0481aae0) /* 0.281657101 */, 19 }, /* 7534 */ { MAD_F(0x0481df27) /* 0.281706956 */, 19 }, /* 7535 */ { MAD_F(0x0482136e) /* 0.281756812 */, 19 }, /* 7536 */ { MAD_F(0x048247b6) /* 0.281806670 */, 19 }, /* 7537 */ { MAD_F(0x04827bfe) /* 0.281856531 */, 19 }, /* 7538 */ { MAD_F(0x0482b047) /* 0.281906394 */, 19 }, /* 7539 */ { MAD_F(0x0482e491) /* 0.281956259 */, 19 }, /* 7540 */ { MAD_F(0x048318db) /* 0.282006127 */, 19 }, /* 7541 */ { MAD_F(0x04834d26) /* 0.282055996 */, 19 }, /* 7542 */ { MAD_F(0x04838171) /* 0.282105868 */, 19 }, /* 7543 */ { MAD_F(0x0483b5bd) /* 0.282155742 */, 19 }, /* 7544 */ { MAD_F(0x0483ea0a) /* 0.282205618 */, 19 }, /* 7545 */ { MAD_F(0x04841e57) /* 0.282255496 */, 19 }, /* 7546 */ { MAD_F(0x048452a4) /* 0.282305377 */, 19 }, /* 7547 */ { MAD_F(0x048486f3) /* 0.282355260 */, 19 }, /* 7548 */ { MAD_F(0x0484bb42) /* 0.282405145 */, 19 }, /* 7549 */ { MAD_F(0x0484ef91) /* 0.282455032 */, 19 }, /* 7550 */ { MAD_F(0x048523e1) /* 0.282504921 */, 19 }, /* 7551 */ { MAD_F(0x04855832) /* 0.282554813 */, 19 }, /* 7552 */ { MAD_F(0x04858c83) /* 0.282604707 */, 19 }, /* 7553 */ { MAD_F(0x0485c0d5) /* 0.282654603 */, 19 }, /* 7554 */ { MAD_F(0x0485f527) /* 0.282704501 */, 19 }, /* 7555 */ { MAD_F(0x0486297a) /* 0.282754401 */, 19 }, /* 7556 */ { MAD_F(0x04865dce) /* 0.282804304 */, 19 }, /* 7557 */ { MAD_F(0x04869222) /* 0.282854209 */, 19 }, /* 7558 */ { MAD_F(0x0486c677) /* 0.282904116 */, 19 }, /* 7559 */ { MAD_F(0x0486facc) /* 0.282954025 */, 19 }, /* 7560 */ { MAD_F(0x04872f22) /* 0.283003936 */, 19 }, /* 7561 */ { MAD_F(0x04876379) /* 0.283053850 */, 19 }, /* 7562 */ { MAD_F(0x048797d0) /* 0.283103766 */, 19 }, /* 7563 */ { MAD_F(0x0487cc28) /* 0.283153684 */, 19 }, /* 7564 */ { MAD_F(0x04880080) /* 0.283203604 */, 19 }, /* 7565 */ { MAD_F(0x048834d9) /* 0.283253527 */, 19 }, /* 7566 */ { MAD_F(0x04886933) /* 0.283303451 */, 19 }, /* 7567 */ { MAD_F(0x04889d8d) /* 0.283353378 */, 19 }, /* 7568 */ { MAD_F(0x0488d1e8) /* 0.283403307 */, 19 }, /* 7569 */ { MAD_F(0x04890643) /* 0.283453238 */, 19 }, /* 7570 */ { MAD_F(0x04893a9f) /* 0.283503172 */, 19 }, /* 7571 */ { MAD_F(0x04896efb) /* 0.283553107 */, 19 }, /* 7572 */ { MAD_F(0x0489a358) /* 0.283603045 */, 19 }, /* 7573 */ { MAD_F(0x0489d7b6) /* 0.283652985 */, 19 }, /* 7574 */ { MAD_F(0x048a0c14) /* 0.283702927 */, 19 }, /* 7575 */ { MAD_F(0x048a4073) /* 0.283752872 */, 19 }, /* 7576 */ { MAD_F(0x048a74d3) /* 0.283802818 */, 19 }, /* 7577 */ { MAD_F(0x048aa933) /* 0.283852767 */, 19 }, /* 7578 */ { MAD_F(0x048add93) /* 0.283902718 */, 19 }, /* 7579 */ { MAD_F(0x048b11f5) /* 0.283952671 */, 19 }, /* 7580 */ { MAD_F(0x048b4656) /* 0.284002627 */, 19 }, /* 7581 */ { MAD_F(0x048b7ab9) /* 0.284052584 */, 19 }, /* 7582 */ { MAD_F(0x048baf1c) /* 0.284102544 */, 19 }, /* 7583 */ { MAD_F(0x048be37f) /* 0.284152506 */, 19 }, /* 7584 */ { MAD_F(0x048c17e3) /* 0.284202470 */, 19 }, /* 7585 */ { MAD_F(0x048c4c48) /* 0.284252436 */, 19 }, /* 7586 */ { MAD_F(0x048c80ad) /* 0.284302405 */, 19 }, /* 7587 */ { MAD_F(0x048cb513) /* 0.284352376 */, 19 }, /* 7588 */ { MAD_F(0x048ce97a) /* 0.284402349 */, 19 }, /* 7589 */ { MAD_F(0x048d1de1) /* 0.284452324 */, 19 }, /* 7590 */ { MAD_F(0x048d5249) /* 0.284502301 */, 19 }, /* 7591 */ { MAD_F(0x048d86b1) /* 0.284552281 */, 19 }, /* 7592 */ { MAD_F(0x048dbb1a) /* 0.284602263 */, 19 }, /* 7593 */ { MAD_F(0x048def83) /* 0.284652246 */, 19 }, /* 7594 */ { MAD_F(0x048e23ed) /* 0.284702233 */, 19 }, /* 7595 */ { MAD_F(0x048e5858) /* 0.284752221 */, 19 }, /* 7596 */ { MAD_F(0x048e8cc3) /* 0.284802211 */, 19 }, /* 7597 */ { MAD_F(0x048ec12f) /* 0.284852204 */, 19 }, /* 7598 */ { MAD_F(0x048ef59b) /* 0.284902199 */, 19 }, /* 7599 */ { MAD_F(0x048f2a08) /* 0.284952196 */, 19 }, /* 7600 */ { MAD_F(0x048f5e76) /* 0.285002195 */, 19 }, /* 7601 */ { MAD_F(0x048f92e4) /* 0.285052197 */, 19 }, /* 7602 */ { MAD_F(0x048fc753) /* 0.285102201 */, 19 }, /* 7603 */ { MAD_F(0x048ffbc2) /* 0.285152206 */, 19 }, /* 7604 */ { MAD_F(0x04903032) /* 0.285202214 */, 19 }, /* 7605 */ { MAD_F(0x049064a3) /* 0.285252225 */, 19 }, /* 7606 */ { MAD_F(0x04909914) /* 0.285302237 */, 19 }, /* 7607 */ { MAD_F(0x0490cd86) /* 0.285352252 */, 19 }, /* 7608 */ { MAD_F(0x049101f8) /* 0.285402269 */, 19 }, /* 7609 */ { MAD_F(0x0491366b) /* 0.285452288 */, 19 }, /* 7610 */ { MAD_F(0x04916ade) /* 0.285502309 */, 19 }, /* 7611 */ { MAD_F(0x04919f52) /* 0.285552332 */, 19 }, /* 7612 */ { MAD_F(0x0491d3c7) /* 0.285602358 */, 19 }, /* 7613 */ { MAD_F(0x0492083c) /* 0.285652386 */, 19 }, /* 7614 */ { MAD_F(0x04923cb2) /* 0.285702416 */, 19 }, /* 7615 */ { MAD_F(0x04927128) /* 0.285752448 */, 19 }, /* 7616 */ { MAD_F(0x0492a59f) /* 0.285802482 */, 19 }, /* 7617 */ { MAD_F(0x0492da17) /* 0.285852519 */, 19 }, /* 7618 */ { MAD_F(0x04930e8f) /* 0.285902557 */, 19 }, /* 7619 */ { MAD_F(0x04934308) /* 0.285952598 */, 19 }, /* 7620 */ { MAD_F(0x04937781) /* 0.286002641 */, 19 }, /* 7621 */ { MAD_F(0x0493abfb) /* 0.286052687 */, 19 }, /* 7622 */ { MAD_F(0x0493e076) /* 0.286102734 */, 19 }, /* 7623 */ { MAD_F(0x049414f1) /* 0.286152784 */, 19 }, /* 7624 */ { MAD_F(0x0494496c) /* 0.286202836 */, 19 }, /* 7625 */ { MAD_F(0x04947de9) /* 0.286252890 */, 19 }, /* 7626 */ { MAD_F(0x0494b266) /* 0.286302946 */, 19 }, /* 7627 */ { MAD_F(0x0494e6e3) /* 0.286353005 */, 19 }, /* 7628 */ { MAD_F(0x04951b61) /* 0.286403065 */, 19 }, /* 7629 */ { MAD_F(0x04954fe0) /* 0.286453128 */, 19 }, /* 7630 */ { MAD_F(0x0495845f) /* 0.286503193 */, 19 }, /* 7631 */ { MAD_F(0x0495b8df) /* 0.286553260 */, 19 }, /* 7632 */ { MAD_F(0x0495ed5f) /* 0.286603329 */, 19 }, /* 7633 */ { MAD_F(0x049621e0) /* 0.286653401 */, 19 }, /* 7634 */ { MAD_F(0x04965662) /* 0.286703475 */, 19 }, /* 7635 */ { MAD_F(0x04968ae4) /* 0.286753551 */, 19 }, /* 7636 */ { MAD_F(0x0496bf67) /* 0.286803629 */, 19 }, /* 7637 */ { MAD_F(0x0496f3ea) /* 0.286853709 */, 19 }, /* 7638 */ { MAD_F(0x0497286e) /* 0.286903792 */, 19 }, /* 7639 */ { MAD_F(0x04975cf2) /* 0.286953876 */, 19 }, /* 7640 */ { MAD_F(0x04979177) /* 0.287003963 */, 19 }, /* 7641 */ { MAD_F(0x0497c5fd) /* 0.287054052 */, 19 }, /* 7642 */ { MAD_F(0x0497fa83) /* 0.287104143 */, 19 }, /* 7643 */ { MAD_F(0x04982f0a) /* 0.287154237 */, 19 }, /* 7644 */ { MAD_F(0x04986392) /* 0.287204332 */, 19 }, /* 7645 */ { MAD_F(0x0498981a) /* 0.287254430 */, 19 }, /* 7646 */ { MAD_F(0x0498cca2) /* 0.287304530 */, 19 }, /* 7647 */ { MAD_F(0x0499012c) /* 0.287354632 */, 19 }, /* 7648 */ { MAD_F(0x049935b5) /* 0.287404737 */, 19 }, /* 7649 */ { MAD_F(0x04996a40) /* 0.287454843 */, 19 }, /* 7650 */ { MAD_F(0x04999ecb) /* 0.287504952 */, 19 }, /* 7651 */ { MAD_F(0x0499d356) /* 0.287555063 */, 19 }, /* 7652 */ { MAD_F(0x049a07e2) /* 0.287605176 */, 19 }, /* 7653 */ { MAD_F(0x049a3c6f) /* 0.287655291 */, 19 }, /* 7654 */ { MAD_F(0x049a70fc) /* 0.287705409 */, 19 }, /* 7655 */ { MAD_F(0x049aa58a) /* 0.287755528 */, 19 }, /* 7656 */ { MAD_F(0x049ada19) /* 0.287805650 */, 19 }, /* 7657 */ { MAD_F(0x049b0ea8) /* 0.287855774 */, 19 }, /* 7658 */ { MAD_F(0x049b4337) /* 0.287905900 */, 19 }, /* 7659 */ { MAD_F(0x049b77c8) /* 0.287956028 */, 19 }, /* 7660 */ { MAD_F(0x049bac58) /* 0.288006159 */, 19 }, /* 7661 */ { MAD_F(0x049be0ea) /* 0.288056292 */, 19 }, /* 7662 */ { MAD_F(0x049c157c) /* 0.288106427 */, 19 }, /* 7663 */ { MAD_F(0x049c4a0e) /* 0.288156564 */, 19 }, /* 7664 */ { MAD_F(0x049c7ea1) /* 0.288206703 */, 19 }, /* 7665 */ { MAD_F(0x049cb335) /* 0.288256844 */, 19 }, /* 7666 */ { MAD_F(0x049ce7ca) /* 0.288306988 */, 19 }, /* 7667 */ { MAD_F(0x049d1c5e) /* 0.288357134 */, 19 }, /* 7668 */ { MAD_F(0x049d50f4) /* 0.288407282 */, 19 }, /* 7669 */ { MAD_F(0x049d858a) /* 0.288457432 */, 19 }, /* 7670 */ { MAD_F(0x049dba21) /* 0.288507584 */, 19 }, /* 7671 */ { MAD_F(0x049deeb8) /* 0.288557739 */, 19 }, /* 7672 */ { MAD_F(0x049e2350) /* 0.288607895 */, 19 }, /* 7673 */ { MAD_F(0x049e57e8) /* 0.288658054 */, 19 }, /* 7674 */ { MAD_F(0x049e8c81) /* 0.288708215 */, 19 }, /* 7675 */ { MAD_F(0x049ec11b) /* 0.288758379 */, 19 }, /* 7676 */ { MAD_F(0x049ef5b5) /* 0.288808544 */, 19 }, /* 7677 */ { MAD_F(0x049f2a50) /* 0.288858712 */, 19 }, /* 7678 */ { MAD_F(0x049f5eeb) /* 0.288908881 */, 19 }, /* 7679 */ { MAD_F(0x049f9387) /* 0.288959053 */, 19 }, /* 7680 */ { MAD_F(0x049fc824) /* 0.289009227 */, 19 }, /* 7681 */ { MAD_F(0x049ffcc1) /* 0.289059404 */, 19 }, /* 7682 */ { MAD_F(0x04a0315e) /* 0.289109582 */, 19 }, /* 7683 */ { MAD_F(0x04a065fd) /* 0.289159763 */, 19 }, /* 7684 */ { MAD_F(0x04a09a9b) /* 0.289209946 */, 19 }, /* 7685 */ { MAD_F(0x04a0cf3b) /* 0.289260131 */, 19 }, /* 7686 */ { MAD_F(0x04a103db) /* 0.289310318 */, 19 }, /* 7687 */ { MAD_F(0x04a1387b) /* 0.289360507 */, 19 }, /* 7688 */ { MAD_F(0x04a16d1d) /* 0.289410699 */, 19 }, /* 7689 */ { MAD_F(0x04a1a1be) /* 0.289460893 */, 19 }, /* 7690 */ { MAD_F(0x04a1d661) /* 0.289511088 */, 19 }, /* 7691 */ { MAD_F(0x04a20b04) /* 0.289561287 */, 19 }, /* 7692 */ { MAD_F(0x04a23fa7) /* 0.289611487 */, 19 }, /* 7693 */ { MAD_F(0x04a2744b) /* 0.289661689 */, 19 }, /* 7694 */ { MAD_F(0x04a2a8f0) /* 0.289711894 */, 19 }, /* 7695 */ { MAD_F(0x04a2dd95) /* 0.289762101 */, 19 }, /* 7696 */ { MAD_F(0x04a3123b) /* 0.289812309 */, 19 }, /* 7697 */ { MAD_F(0x04a346e2) /* 0.289862521 */, 19 }, /* 7698 */ { MAD_F(0x04a37b89) /* 0.289912734 */, 19 }, /* 7699 */ { MAD_F(0x04a3b030) /* 0.289962949 */, 19 }, /* 7700 */ { MAD_F(0x04a3e4d8) /* 0.290013167 */, 19 }, /* 7701 */ { MAD_F(0x04a41981) /* 0.290063387 */, 19 }, /* 7702 */ { MAD_F(0x04a44e2b) /* 0.290113609 */, 19 }, /* 7703 */ { MAD_F(0x04a482d5) /* 0.290163833 */, 19 }, /* 7704 */ { MAD_F(0x04a4b77f) /* 0.290214059 */, 19 }, /* 7705 */ { MAD_F(0x04a4ec2a) /* 0.290264288 */, 19 }, /* 7706 */ { MAD_F(0x04a520d6) /* 0.290314519 */, 19 }, /* 7707 */ { MAD_F(0x04a55582) /* 0.290364751 */, 19 }, /* 7708 */ { MAD_F(0x04a58a2f) /* 0.290414986 */, 19 }, /* 7709 */ { MAD_F(0x04a5bedd) /* 0.290465224 */, 19 }, /* 7710 */ { MAD_F(0x04a5f38b) /* 0.290515463 */, 19 }, /* 7711 */ { MAD_F(0x04a62839) /* 0.290565705 */, 19 }, /* 7712 */ { MAD_F(0x04a65ce8) /* 0.290615948 */, 19 }, /* 7713 */ { MAD_F(0x04a69198) /* 0.290666194 */, 19 }, /* 7714 */ { MAD_F(0x04a6c648) /* 0.290716442 */, 19 }, /* 7715 */ { MAD_F(0x04a6faf9) /* 0.290766692 */, 19 }, /* 7716 */ { MAD_F(0x04a72fab) /* 0.290816945 */, 19 }, /* 7717 */ { MAD_F(0x04a7645d) /* 0.290867199 */, 19 }, /* 7718 */ { MAD_F(0x04a79910) /* 0.290917456 */, 19 }, /* 7719 */ { MAD_F(0x04a7cdc3) /* 0.290967715 */, 19 }, /* 7720 */ { MAD_F(0x04a80277) /* 0.291017976 */, 19 }, /* 7721 */ { MAD_F(0x04a8372b) /* 0.291068239 */, 19 }, /* 7722 */ { MAD_F(0x04a86be0) /* 0.291118505 */, 19 }, /* 7723 */ { MAD_F(0x04a8a096) /* 0.291168772 */, 19 }, /* 7724 */ { MAD_F(0x04a8d54c) /* 0.291219042 */, 19 }, /* 7725 */ { MAD_F(0x04a90a03) /* 0.291269314 */, 19 }, /* 7726 */ { MAD_F(0x04a93eba) /* 0.291319588 */, 19 }, /* 7727 */ { MAD_F(0x04a97372) /* 0.291369865 */, 19 }, /* 7728 */ { MAD_F(0x04a9a82b) /* 0.291420143 */, 19 }, /* 7729 */ { MAD_F(0x04a9dce4) /* 0.291470424 */, 19 }, /* 7730 */ { MAD_F(0x04aa119d) /* 0.291520706 */, 19 }, /* 7731 */ { MAD_F(0x04aa4658) /* 0.291570991 */, 19 }, /* 7732 */ { MAD_F(0x04aa7b13) /* 0.291621278 */, 19 }, /* 7733 */ { MAD_F(0x04aaafce) /* 0.291671568 */, 19 }, /* 7734 */ { MAD_F(0x04aae48a) /* 0.291721859 */, 19 }, /* 7735 */ { MAD_F(0x04ab1947) /* 0.291772153 */, 19 }, /* 7736 */ { MAD_F(0x04ab4e04) /* 0.291822449 */, 19 }, /* 7737 */ { MAD_F(0x04ab82c2) /* 0.291872747 */, 19 }, /* 7738 */ { MAD_F(0x04abb780) /* 0.291923047 */, 19 }, /* 7739 */ { MAD_F(0x04abec3f) /* 0.291973349 */, 19 }, /* 7740 */ { MAD_F(0x04ac20fe) /* 0.292023653 */, 19 }, /* 7741 */ { MAD_F(0x04ac55be) /* 0.292073960 */, 19 }, /* 7742 */ { MAD_F(0x04ac8a7f) /* 0.292124269 */, 19 }, /* 7743 */ { MAD_F(0x04acbf40) /* 0.292174580 */, 19 }, /* 7744 */ { MAD_F(0x04acf402) /* 0.292224893 */, 19 }, /* 7745 */ { MAD_F(0x04ad28c5) /* 0.292275208 */, 19 }, /* 7746 */ { MAD_F(0x04ad5d88) /* 0.292325526 */, 19 }, /* 7747 */ { MAD_F(0x04ad924b) /* 0.292375845 */, 19 }, /* 7748 */ { MAD_F(0x04adc70f) /* 0.292426167 */, 19 }, /* 7749 */ { MAD_F(0x04adfbd4) /* 0.292476491 */, 19 }, /* 7750 */ { MAD_F(0x04ae3099) /* 0.292526817 */, 19 }, /* 7751 */ { MAD_F(0x04ae655f) /* 0.292577145 */, 19 }, /* 7752 */ { MAD_F(0x04ae9a26) /* 0.292627476 */, 19 }, /* 7753 */ { MAD_F(0x04aeceed) /* 0.292677808 */, 19 }, /* 7754 */ { MAD_F(0x04af03b4) /* 0.292728143 */, 19 }, /* 7755 */ { MAD_F(0x04af387d) /* 0.292778480 */, 19 }, /* 7756 */ { MAD_F(0x04af6d45) /* 0.292828819 */, 19 }, /* 7757 */ { MAD_F(0x04afa20f) /* 0.292879160 */, 19 }, /* 7758 */ { MAD_F(0x04afd6d9) /* 0.292929504 */, 19 }, /* 7759 */ { MAD_F(0x04b00ba3) /* 0.292979849 */, 19 }, /* 7760 */ { MAD_F(0x04b0406e) /* 0.293030197 */, 19 }, /* 7761 */ { MAD_F(0x04b0753a) /* 0.293080547 */, 19 }, /* 7762 */ { MAD_F(0x04b0aa06) /* 0.293130899 */, 19 }, /* 7763 */ { MAD_F(0x04b0ded3) /* 0.293181253 */, 19 }, /* 7764 */ { MAD_F(0x04b113a1) /* 0.293231610 */, 19 }, /* 7765 */ { MAD_F(0x04b1486f) /* 0.293281968 */, 19 }, /* 7766 */ { MAD_F(0x04b17d3d) /* 0.293332329 */, 19 }, /* 7767 */ { MAD_F(0x04b1b20c) /* 0.293382692 */, 19 }, /* 7768 */ { MAD_F(0x04b1e6dc) /* 0.293433057 */, 19 }, /* 7769 */ { MAD_F(0x04b21bad) /* 0.293483424 */, 19 }, /* 7770 */ { MAD_F(0x04b2507d) /* 0.293533794 */, 19 }, /* 7771 */ { MAD_F(0x04b2854f) /* 0.293584165 */, 19 }, /* 7772 */ { MAD_F(0x04b2ba21) /* 0.293634539 */, 19 }, /* 7773 */ { MAD_F(0x04b2eef4) /* 0.293684915 */, 19 }, /* 7774 */ { MAD_F(0x04b323c7) /* 0.293735293 */, 19 }, /* 7775 */ { MAD_F(0x04b3589b) /* 0.293785673 */, 19 }, /* 7776 */ { MAD_F(0x04b38d6f) /* 0.293836055 */, 19 }, /* 7777 */ { MAD_F(0x04b3c244) /* 0.293886440 */, 19 }, /* 7778 */ { MAD_F(0x04b3f71a) /* 0.293936826 */, 19 }, /* 7779 */ { MAD_F(0x04b42bf0) /* 0.293987215 */, 19 }, /* 7780 */ { MAD_F(0x04b460c7) /* 0.294037606 */, 19 }, /* 7781 */ { MAD_F(0x04b4959e) /* 0.294087999 */, 19 }, /* 7782 */ { MAD_F(0x04b4ca76) /* 0.294138395 */, 19 }, /* 7783 */ { MAD_F(0x04b4ff4e) /* 0.294188792 */, 19 }, /* 7784 */ { MAD_F(0x04b53427) /* 0.294239192 */, 19 }, /* 7785 */ { MAD_F(0x04b56901) /* 0.294289593 */, 19 }, /* 7786 */ { MAD_F(0x04b59ddb) /* 0.294339997 */, 19 }, /* 7787 */ { MAD_F(0x04b5d2b6) /* 0.294390403 */, 19 }, /* 7788 */ { MAD_F(0x04b60791) /* 0.294440812 */, 19 }, /* 7789 */ { MAD_F(0x04b63c6d) /* 0.294491222 */, 19 }, /* 7790 */ { MAD_F(0x04b6714a) /* 0.294541635 */, 19 }, /* 7791 */ { MAD_F(0x04b6a627) /* 0.294592049 */, 19 }, /* 7792 */ { MAD_F(0x04b6db05) /* 0.294642466 */, 19 }, /* 7793 */ { MAD_F(0x04b70fe3) /* 0.294692885 */, 19 }, /* 7794 */ { MAD_F(0x04b744c2) /* 0.294743306 */, 19 }, /* 7795 */ { MAD_F(0x04b779a1) /* 0.294793730 */, 19 }, /* 7796 */ { MAD_F(0x04b7ae81) /* 0.294844155 */, 19 }, /* 7797 */ { MAD_F(0x04b7e362) /* 0.294894583 */, 19 }, /* 7798 */ { MAD_F(0x04b81843) /* 0.294945013 */, 19 }, /* 7799 */ { MAD_F(0x04b84d24) /* 0.294995445 */, 19 }, /* 7800 */ { MAD_F(0x04b88207) /* 0.295045879 */, 19 }, /* 7801 */ { MAD_F(0x04b8b6ea) /* 0.295096315 */, 19 }, /* 7802 */ { MAD_F(0x04b8ebcd) /* 0.295146753 */, 19 }, /* 7803 */ { MAD_F(0x04b920b1) /* 0.295197194 */, 19 }, /* 7804 */ { MAD_F(0x04b95596) /* 0.295247637 */, 19 }, /* 7805 */ { MAD_F(0x04b98a7b) /* 0.295298082 */, 19 }, /* 7806 */ { MAD_F(0x04b9bf61) /* 0.295348529 */, 19 }, /* 7807 */ { MAD_F(0x04b9f447) /* 0.295398978 */, 19 }, /* 7808 */ { MAD_F(0x04ba292e) /* 0.295449429 */, 19 }, /* 7809 */ { MAD_F(0x04ba5e16) /* 0.295499883 */, 19 }, /* 7810 */ { MAD_F(0x04ba92fe) /* 0.295550338 */, 19 }, /* 7811 */ { MAD_F(0x04bac7e6) /* 0.295600796 */, 19 }, /* 7812 */ { MAD_F(0x04bafcd0) /* 0.295651256 */, 19 }, /* 7813 */ { MAD_F(0x04bb31b9) /* 0.295701718 */, 19 }, /* 7814 */ { MAD_F(0x04bb66a4) /* 0.295752183 */, 19 }, /* 7815 */ { MAD_F(0x04bb9b8f) /* 0.295802649 */, 19 }, /* 7816 */ { MAD_F(0x04bbd07a) /* 0.295853118 */, 19 }, /* 7817 */ { MAD_F(0x04bc0566) /* 0.295903588 */, 19 }, /* 7818 */ { MAD_F(0x04bc3a53) /* 0.295954061 */, 19 }, /* 7819 */ { MAD_F(0x04bc6f40) /* 0.296004536 */, 19 }, /* 7820 */ { MAD_F(0x04bca42e) /* 0.296055013 */, 19 }, /* 7821 */ { MAD_F(0x04bcd91d) /* 0.296105493 */, 19 }, /* 7822 */ { MAD_F(0x04bd0e0c) /* 0.296155974 */, 19 }, /* 7823 */ { MAD_F(0x04bd42fb) /* 0.296206458 */, 19 }, /* 7824 */ { MAD_F(0x04bd77ec) /* 0.296256944 */, 19 }, /* 7825 */ { MAD_F(0x04bdacdc) /* 0.296307432 */, 19 }, /* 7826 */ { MAD_F(0x04bde1ce) /* 0.296357922 */, 19 }, /* 7827 */ { MAD_F(0x04be16c0) /* 0.296408414 */, 19 }, /* 7828 */ { MAD_F(0x04be4bb2) /* 0.296458908 */, 19 }, /* 7829 */ { MAD_F(0x04be80a5) /* 0.296509405 */, 19 }, /* 7830 */ { MAD_F(0x04beb599) /* 0.296559904 */, 19 }, /* 7831 */ { MAD_F(0x04beea8d) /* 0.296610404 */, 19 }, /* 7832 */ { MAD_F(0x04bf1f82) /* 0.296660907 */, 19 }, /* 7833 */ { MAD_F(0x04bf5477) /* 0.296711413 */, 19 }, /* 7834 */ { MAD_F(0x04bf896d) /* 0.296761920 */, 19 }, /* 7835 */ { MAD_F(0x04bfbe64) /* 0.296812429 */, 19 }, /* 7836 */ { MAD_F(0x04bff35b) /* 0.296862941 */, 19 }, /* 7837 */ { MAD_F(0x04c02852) /* 0.296913455 */, 19 }, /* 7838 */ { MAD_F(0x04c05d4b) /* 0.296963971 */, 19 }, /* 7839 */ { MAD_F(0x04c09243) /* 0.297014489 */, 19 }, /* 7840 */ { MAD_F(0x04c0c73d) /* 0.297065009 */, 19 }, /* 7841 */ { MAD_F(0x04c0fc37) /* 0.297115531 */, 19 }, /* 7842 */ { MAD_F(0x04c13131) /* 0.297166056 */, 19 }, /* 7843 */ { MAD_F(0x04c1662d) /* 0.297216582 */, 19 }, /* 7844 */ { MAD_F(0x04c19b28) /* 0.297267111 */, 19 }, /* 7845 */ { MAD_F(0x04c1d025) /* 0.297317642 */, 19 }, /* 7846 */ { MAD_F(0x04c20521) /* 0.297368175 */, 19 }, /* 7847 */ { MAD_F(0x04c23a1f) /* 0.297418710 */, 19 }, /* 7848 */ { MAD_F(0x04c26f1d) /* 0.297469248 */, 19 }, /* 7849 */ { MAD_F(0x04c2a41b) /* 0.297519787 */, 19 }, /* 7850 */ { MAD_F(0x04c2d91b) /* 0.297570329 */, 19 }, /* 7851 */ { MAD_F(0x04c30e1a) /* 0.297620873 */, 19 }, /* 7852 */ { MAD_F(0x04c3431b) /* 0.297671418 */, 19 }, /* 7853 */ { MAD_F(0x04c3781c) /* 0.297721967 */, 19 }, /* 7854 */ { MAD_F(0x04c3ad1d) /* 0.297772517 */, 19 }, /* 7855 */ { MAD_F(0x04c3e21f) /* 0.297823069 */, 19 }, /* 7856 */ { MAD_F(0x04c41722) /* 0.297873624 */, 19 }, /* 7857 */ { MAD_F(0x04c44c25) /* 0.297924180 */, 19 }, /* 7858 */ { MAD_F(0x04c48129) /* 0.297974739 */, 19 }, /* 7859 */ { MAD_F(0x04c4b62d) /* 0.298025300 */, 19 }, /* 7860 */ { MAD_F(0x04c4eb32) /* 0.298075863 */, 19 }, /* 7861 */ { MAD_F(0x04c52038) /* 0.298126429 */, 19 }, /* 7862 */ { MAD_F(0x04c5553e) /* 0.298176996 */, 19 }, /* 7863 */ { MAD_F(0x04c58a44) /* 0.298227565 */, 19 }, /* 7864 */ { MAD_F(0x04c5bf4c) /* 0.298278137 */, 19 }, /* 7865 */ { MAD_F(0x04c5f453) /* 0.298328711 */, 19 }, /* 7866 */ { MAD_F(0x04c6295c) /* 0.298379287 */, 19 }, /* 7867 */ { MAD_F(0x04c65e65) /* 0.298429865 */, 19 }, /* 7868 */ { MAD_F(0x04c6936e) /* 0.298480445 */, 19 }, /* 7869 */ { MAD_F(0x04c6c878) /* 0.298531028 */, 19 }, /* 7870 */ { MAD_F(0x04c6fd83) /* 0.298581612 */, 19 }, /* 7871 */ { MAD_F(0x04c7328e) /* 0.298632199 */, 19 }, /* 7872 */ { MAD_F(0x04c7679a) /* 0.298682788 */, 19 }, /* 7873 */ { MAD_F(0x04c79ca7) /* 0.298733379 */, 19 }, /* 7874 */ { MAD_F(0x04c7d1b4) /* 0.298783972 */, 19 }, /* 7875 */ { MAD_F(0x04c806c1) /* 0.298834567 */, 19 }, /* 7876 */ { MAD_F(0x04c83bcf) /* 0.298885165 */, 19 }, /* 7877 */ { MAD_F(0x04c870de) /* 0.298935764 */, 19 }, /* 7878 */ { MAD_F(0x04c8a5ed) /* 0.298986366 */, 19 }, /* 7879 */ { MAD_F(0x04c8dafd) /* 0.299036970 */, 19 }, /* 7880 */ { MAD_F(0x04c9100d) /* 0.299087576 */, 19 }, /* 7881 */ { MAD_F(0x04c9451e) /* 0.299138184 */, 19 }, /* 7882 */ { MAD_F(0x04c97a30) /* 0.299188794 */, 19 }, /* 7883 */ { MAD_F(0x04c9af42) /* 0.299239406 */, 19 }, /* 7884 */ { MAD_F(0x04c9e455) /* 0.299290021 */, 19 }, /* 7885 */ { MAD_F(0x04ca1968) /* 0.299340638 */, 19 }, /* 7886 */ { MAD_F(0x04ca4e7c) /* 0.299391256 */, 19 }, /* 7887 */ { MAD_F(0x04ca8391) /* 0.299441877 */, 19 }, /* 7888 */ { MAD_F(0x04cab8a6) /* 0.299492500 */, 19 }, /* 7889 */ { MAD_F(0x04caedbb) /* 0.299543126 */, 19 }, /* 7890 */ { MAD_F(0x04cb22d1) /* 0.299593753 */, 19 }, /* 7891 */ { MAD_F(0x04cb57e8) /* 0.299644382 */, 19 }, /* 7892 */ { MAD_F(0x04cb8d00) /* 0.299695014 */, 19 }, /* 7893 */ { MAD_F(0x04cbc217) /* 0.299745648 */, 19 }, /* 7894 */ { MAD_F(0x04cbf730) /* 0.299796284 */, 19 }, /* 7895 */ { MAD_F(0x04cc2c49) /* 0.299846922 */, 19 }, /* 7896 */ { MAD_F(0x04cc6163) /* 0.299897562 */, 19 }, /* 7897 */ { MAD_F(0x04cc967d) /* 0.299948204 */, 19 }, /* 7898 */ { MAD_F(0x04cccb98) /* 0.299998849 */, 19 }, /* 7899 */ { MAD_F(0x04cd00b3) /* 0.300049495 */, 19 }, /* 7900 */ { MAD_F(0x04cd35cf) /* 0.300100144 */, 19 }, /* 7901 */ { MAD_F(0x04cd6aeb) /* 0.300150795 */, 19 }, /* 7902 */ { MAD_F(0x04cda008) /* 0.300201448 */, 19 }, /* 7903 */ { MAD_F(0x04cdd526) /* 0.300252103 */, 19 }, /* 7904 */ { MAD_F(0x04ce0a44) /* 0.300302761 */, 19 }, /* 7905 */ { MAD_F(0x04ce3f63) /* 0.300353420 */, 19 }, /* 7906 */ { MAD_F(0x04ce7482) /* 0.300404082 */, 19 }, /* 7907 */ { MAD_F(0x04cea9a2) /* 0.300454745 */, 19 }, /* 7908 */ { MAD_F(0x04cedec3) /* 0.300505411 */, 19 }, /* 7909 */ { MAD_F(0x04cf13e4) /* 0.300556079 */, 19 }, /* 7910 */ { MAD_F(0x04cf4906) /* 0.300606749 */, 19 }, /* 7911 */ { MAD_F(0x04cf7e28) /* 0.300657421 */, 19 }, /* 7912 */ { MAD_F(0x04cfb34b) /* 0.300708096 */, 19 }, /* 7913 */ { MAD_F(0x04cfe86e) /* 0.300758772 */, 19 }, /* 7914 */ { MAD_F(0x04d01d92) /* 0.300809451 */, 19 }, /* 7915 */ { MAD_F(0x04d052b6) /* 0.300860132 */, 19 }, /* 7916 */ { MAD_F(0x04d087db) /* 0.300910815 */, 19 }, /* 7917 */ { MAD_F(0x04d0bd01) /* 0.300961500 */, 19 }, /* 7918 */ { MAD_F(0x04d0f227) /* 0.301012187 */, 19 }, /* 7919 */ { MAD_F(0x04d1274e) /* 0.301062876 */, 19 }, /* 7920 */ { MAD_F(0x04d15c76) /* 0.301113568 */, 19 }, /* 7921 */ { MAD_F(0x04d1919e) /* 0.301164261 */, 19 }, /* 7922 */ { MAD_F(0x04d1c6c6) /* 0.301214957 */, 19 }, /* 7923 */ { MAD_F(0x04d1fbef) /* 0.301265655 */, 19 }, /* 7924 */ { MAD_F(0x04d23119) /* 0.301316355 */, 19 }, /* 7925 */ { MAD_F(0x04d26643) /* 0.301367057 */, 19 }, /* 7926 */ { MAD_F(0x04d29b6e) /* 0.301417761 */, 19 }, /* 7927 */ { MAD_F(0x04d2d099) /* 0.301468468 */, 19 }, /* 7928 */ { MAD_F(0x04d305c5) /* 0.301519176 */, 19 }, /* 7929 */ { MAD_F(0x04d33af2) /* 0.301569887 */, 19 }, /* 7930 */ { MAD_F(0x04d3701f) /* 0.301620599 */, 19 }, /* 7931 */ { MAD_F(0x04d3a54d) /* 0.301671314 */, 19 }, /* 7932 */ { MAD_F(0x04d3da7b) /* 0.301722031 */, 19 }, /* 7933 */ { MAD_F(0x04d40faa) /* 0.301772751 */, 19 }, /* 7934 */ { MAD_F(0x04d444d9) /* 0.301823472 */, 19 }, /* 7935 */ { MAD_F(0x04d47a09) /* 0.301874195 */, 19 }, /* 7936 */ { MAD_F(0x04d4af3a) /* 0.301924921 */, 19 }, /* 7937 */ { MAD_F(0x04d4e46b) /* 0.301975649 */, 19 }, /* 7938 */ { MAD_F(0x04d5199c) /* 0.302026378 */, 19 }, /* 7939 */ { MAD_F(0x04d54ecf) /* 0.302077110 */, 19 }, /* 7940 */ { MAD_F(0x04d58401) /* 0.302127845 */, 19 }, /* 7941 */ { MAD_F(0x04d5b935) /* 0.302178581 */, 19 }, /* 7942 */ { MAD_F(0x04d5ee69) /* 0.302229319 */, 19 }, /* 7943 */ { MAD_F(0x04d6239d) /* 0.302280060 */, 19 }, /* 7944 */ { MAD_F(0x04d658d2) /* 0.302330802 */, 19 }, /* 7945 */ { MAD_F(0x04d68e08) /* 0.302381547 */, 19 }, /* 7946 */ { MAD_F(0x04d6c33e) /* 0.302432294 */, 19 }, /* 7947 */ { MAD_F(0x04d6f875) /* 0.302483043 */, 19 }, /* 7948 */ { MAD_F(0x04d72dad) /* 0.302533794 */, 19 }, /* 7949 */ { MAD_F(0x04d762e5) /* 0.302584547 */, 19 }, /* 7950 */ { MAD_F(0x04d7981d) /* 0.302635303 */, 19 }, /* 7951 */ { MAD_F(0x04d7cd56) /* 0.302686060 */, 19 }, /* 7952 */ { MAD_F(0x04d80290) /* 0.302736820 */, 19 }, /* 7953 */ { MAD_F(0x04d837ca) /* 0.302787581 */, 19 }, /* 7954 */ { MAD_F(0x04d86d05) /* 0.302838345 */, 19 }, /* 7955 */ { MAD_F(0x04d8a240) /* 0.302889111 */, 19 }, /* 7956 */ { MAD_F(0x04d8d77c) /* 0.302939879 */, 19 }, /* 7957 */ { MAD_F(0x04d90cb9) /* 0.302990650 */, 19 }, /* 7958 */ { MAD_F(0x04d941f6) /* 0.303041422 */, 19 }, /* 7959 */ { MAD_F(0x04d97734) /* 0.303092197 */, 19 }, /* 7960 */ { MAD_F(0x04d9ac72) /* 0.303142973 */, 19 }, /* 7961 */ { MAD_F(0x04d9e1b1) /* 0.303193752 */, 19 }, /* 7962 */ { MAD_F(0x04da16f0) /* 0.303244533 */, 19 }, /* 7963 */ { MAD_F(0x04da4c30) /* 0.303295316 */, 19 }, /* 7964 */ { MAD_F(0x04da8171) /* 0.303346101 */, 19 }, /* 7965 */ { MAD_F(0x04dab6b2) /* 0.303396889 */, 19 }, /* 7966 */ { MAD_F(0x04daebf4) /* 0.303447678 */, 19 }, /* 7967 */ { MAD_F(0x04db2136) /* 0.303498469 */, 19 }, /* 7968 */ { MAD_F(0x04db5679) /* 0.303549263 */, 19 }, /* 7969 */ { MAD_F(0x04db8bbc) /* 0.303600059 */, 19 }, /* 7970 */ { MAD_F(0x04dbc100) /* 0.303650857 */, 19 }, /* 7971 */ { MAD_F(0x04dbf644) /* 0.303701657 */, 19 }, /* 7972 */ { MAD_F(0x04dc2b8a) /* 0.303752459 */, 19 }, /* 7973 */ { MAD_F(0x04dc60cf) /* 0.303803263 */, 19 }, /* 7974 */ { MAD_F(0x04dc9616) /* 0.303854070 */, 19 }, /* 7975 */ { MAD_F(0x04dccb5c) /* 0.303904878 */, 19 }, /* 7976 */ { MAD_F(0x04dd00a4) /* 0.303955689 */, 19 }, /* 7977 */ { MAD_F(0x04dd35ec) /* 0.304006502 */, 19 }, /* 7978 */ { MAD_F(0x04dd6b34) /* 0.304057317 */, 19 }, /* 7979 */ { MAD_F(0x04dda07d) /* 0.304108134 */, 19 }, /* 7980 */ { MAD_F(0x04ddd5c7) /* 0.304158953 */, 19 }, /* 7981 */ { MAD_F(0x04de0b11) /* 0.304209774 */, 19 }, /* 7982 */ { MAD_F(0x04de405c) /* 0.304260597 */, 19 }, /* 7983 */ { MAD_F(0x04de75a7) /* 0.304311423 */, 19 }, /* 7984 */ { MAD_F(0x04deaaf3) /* 0.304362251 */, 19 }, /* 7985 */ { MAD_F(0x04dee040) /* 0.304413080 */, 19 }, /* 7986 */ { MAD_F(0x04df158d) /* 0.304463912 */, 19 }, /* 7987 */ { MAD_F(0x04df4adb) /* 0.304514746 */, 19 }, /* 7988 */ { MAD_F(0x04df8029) /* 0.304565582 */, 19 }, /* 7989 */ { MAD_F(0x04dfb578) /* 0.304616421 */, 19 }, /* 7990 */ { MAD_F(0x04dfeac7) /* 0.304667261 */, 19 }, /* 7991 */ { MAD_F(0x04e02017) /* 0.304718103 */, 19 }, /* 7992 */ { MAD_F(0x04e05567) /* 0.304768948 */, 19 }, /* 7993 */ { MAD_F(0x04e08ab8) /* 0.304819795 */, 19 }, /* 7994 */ { MAD_F(0x04e0c00a) /* 0.304870644 */, 19 }, /* 7995 */ { MAD_F(0x04e0f55c) /* 0.304921495 */, 19 }, /* 7996 */ { MAD_F(0x04e12aaf) /* 0.304972348 */, 19 }, /* 7997 */ { MAD_F(0x04e16002) /* 0.305023203 */, 19 }, /* 7998 */ { MAD_F(0x04e19556) /* 0.305074060 */, 19 }, /* 7999 */ { MAD_F(0x04e1caab) /* 0.305124920 */, 19 }, /* 8000 */ { MAD_F(0x04e20000) /* 0.305175781 */, 19 }, /* 8001 */ { MAD_F(0x04e23555) /* 0.305226645 */, 19 }, /* 8002 */ { MAD_F(0x04e26aac) /* 0.305277511 */, 19 }, /* 8003 */ { MAD_F(0x04e2a002) /* 0.305328379 */, 19 }, /* 8004 */ { MAD_F(0x04e2d55a) /* 0.305379249 */, 19 }, /* 8005 */ { MAD_F(0x04e30ab2) /* 0.305430121 */, 19 }, /* 8006 */ { MAD_F(0x04e3400a) /* 0.305480995 */, 19 }, /* 8007 */ { MAD_F(0x04e37563) /* 0.305531872 */, 19 }, /* 8008 */ { MAD_F(0x04e3aabd) /* 0.305582750 */, 19 }, /* 8009 */ { MAD_F(0x04e3e017) /* 0.305633631 */, 19 }, /* 8010 */ { MAD_F(0x04e41572) /* 0.305684513 */, 19 }, /* 8011 */ { MAD_F(0x04e44acd) /* 0.305735398 */, 19 }, /* 8012 */ { MAD_F(0x04e48029) /* 0.305786285 */, 19 }, /* 8013 */ { MAD_F(0x04e4b585) /* 0.305837174 */, 19 }, /* 8014 */ { MAD_F(0x04e4eae2) /* 0.305888066 */, 19 }, /* 8015 */ { MAD_F(0x04e52040) /* 0.305938959 */, 19 }, /* 8016 */ { MAD_F(0x04e5559e) /* 0.305989854 */, 19 }, /* 8017 */ { MAD_F(0x04e58afd) /* 0.306040752 */, 19 }, /* 8018 */ { MAD_F(0x04e5c05c) /* 0.306091652 */, 19 }, /* 8019 */ { MAD_F(0x04e5f5bc) /* 0.306142554 */, 19 }, /* 8020 */ { MAD_F(0x04e62b1c) /* 0.306193457 */, 19 }, /* 8021 */ { MAD_F(0x04e6607d) /* 0.306244364 */, 19 }, /* 8022 */ { MAD_F(0x04e695df) /* 0.306295272 */, 19 }, /* 8023 */ { MAD_F(0x04e6cb41) /* 0.306346182 */, 19 }, /* 8024 */ { MAD_F(0x04e700a3) /* 0.306397094 */, 19 }, /* 8025 */ { MAD_F(0x04e73607) /* 0.306448009 */, 19 }, /* 8026 */ { MAD_F(0x04e76b6b) /* 0.306498925 */, 19 }, /* 8027 */ { MAD_F(0x04e7a0cf) /* 0.306549844 */, 19 }, /* 8028 */ { MAD_F(0x04e7d634) /* 0.306600765 */, 19 }, /* 8029 */ { MAD_F(0x04e80b99) /* 0.306651688 */, 19 }, /* 8030 */ { MAD_F(0x04e84100) /* 0.306702613 */, 19 }, /* 8031 */ { MAD_F(0x04e87666) /* 0.306753540 */, 19 }, /* 8032 */ { MAD_F(0x04e8abcd) /* 0.306804470 */, 19 }, /* 8033 */ { MAD_F(0x04e8e135) /* 0.306855401 */, 19 }, /* 8034 */ { MAD_F(0x04e9169e) /* 0.306906334 */, 19 }, /* 8035 */ { MAD_F(0x04e94c07) /* 0.306957270 */, 19 }, /* 8036 */ { MAD_F(0x04e98170) /* 0.307008208 */, 19 }, /* 8037 */ { MAD_F(0x04e9b6da) /* 0.307059148 */, 19 }, /* 8038 */ { MAD_F(0x04e9ec45) /* 0.307110090 */, 19 }, /* 8039 */ { MAD_F(0x04ea21b0) /* 0.307161034 */, 19 }, /* 8040 */ { MAD_F(0x04ea571c) /* 0.307211980 */, 19 }, /* 8041 */ { MAD_F(0x04ea8c88) /* 0.307262928 */, 19 }, /* 8042 */ { MAD_F(0x04eac1f5) /* 0.307313879 */, 19 }, /* 8043 */ { MAD_F(0x04eaf762) /* 0.307364831 */, 19 }, /* 8044 */ { MAD_F(0x04eb2cd0) /* 0.307415786 */, 19 }, /* 8045 */ { MAD_F(0x04eb623f) /* 0.307466743 */, 19 }, /* 8046 */ { MAD_F(0x04eb97ae) /* 0.307517702 */, 19 }, /* 8047 */ { MAD_F(0x04ebcd1e) /* 0.307568663 */, 19 }, /* 8048 */ { MAD_F(0x04ec028e) /* 0.307619626 */, 19 }, /* 8049 */ { MAD_F(0x04ec37ff) /* 0.307670591 */, 19 }, /* 8050 */ { MAD_F(0x04ec6d71) /* 0.307721558 */, 19 }, /* 8051 */ { MAD_F(0x04eca2e3) /* 0.307772528 */, 19 }, /* 8052 */ { MAD_F(0x04ecd855) /* 0.307823499 */, 19 }, /* 8053 */ { MAD_F(0x04ed0dc8) /* 0.307874473 */, 19 }, /* 8054 */ { MAD_F(0x04ed433c) /* 0.307925449 */, 19 }, /* 8055 */ { MAD_F(0x04ed78b0) /* 0.307976426 */, 19 }, /* 8056 */ { MAD_F(0x04edae25) /* 0.308027406 */, 19 }, /* 8057 */ { MAD_F(0x04ede39a) /* 0.308078389 */, 19 }, /* 8058 */ { MAD_F(0x04ee1910) /* 0.308129373 */, 19 }, /* 8059 */ { MAD_F(0x04ee4e87) /* 0.308180359 */, 19 }, /* 8060 */ { MAD_F(0x04ee83fe) /* 0.308231347 */, 19 }, /* 8061 */ { MAD_F(0x04eeb976) /* 0.308282338 */, 19 }, /* 8062 */ { MAD_F(0x04eeeeee) /* 0.308333331 */, 19 }, /* 8063 */ { MAD_F(0x04ef2467) /* 0.308384325 */, 19 }, /* 8064 */ { MAD_F(0x04ef59e0) /* 0.308435322 */, 19 }, /* 8065 */ { MAD_F(0x04ef8f5a) /* 0.308486321 */, 19 }, /* 8066 */ { MAD_F(0x04efc4d5) /* 0.308537322 */, 19 }, /* 8067 */ { MAD_F(0x04effa50) /* 0.308588325 */, 19 }, /* 8068 */ { MAD_F(0x04f02fcb) /* 0.308639331 */, 19 }, /* 8069 */ { MAD_F(0x04f06547) /* 0.308690338 */, 19 }, /* 8070 */ { MAD_F(0x04f09ac4) /* 0.308741348 */, 19 }, /* 8071 */ { MAD_F(0x04f0d041) /* 0.308792359 */, 19 }, /* 8072 */ { MAD_F(0x04f105bf) /* 0.308843373 */, 19 }, /* 8073 */ { MAD_F(0x04f13b3e) /* 0.308894389 */, 19 }, /* 8074 */ { MAD_F(0x04f170bd) /* 0.308945407 */, 19 }, /* 8075 */ { MAD_F(0x04f1a63c) /* 0.308996427 */, 19 }, /* 8076 */ { MAD_F(0x04f1dbbd) /* 0.309047449 */, 19 }, /* 8077 */ { MAD_F(0x04f2113d) /* 0.309098473 */, 19 }, /* 8078 */ { MAD_F(0x04f246bf) /* 0.309149499 */, 19 }, /* 8079 */ { MAD_F(0x04f27c40) /* 0.309200528 */, 19 }, /* 8080 */ { MAD_F(0x04f2b1c3) /* 0.309251558 */, 19 }, /* 8081 */ { MAD_F(0x04f2e746) /* 0.309302591 */, 19 }, /* 8082 */ { MAD_F(0x04f31cc9) /* 0.309353626 */, 19 }, /* 8083 */ { MAD_F(0x04f3524d) /* 0.309404663 */, 19 }, /* 8084 */ { MAD_F(0x04f387d2) /* 0.309455702 */, 19 }, /* 8085 */ { MAD_F(0x04f3bd57) /* 0.309506743 */, 19 }, /* 8086 */ { MAD_F(0x04f3f2dd) /* 0.309557786 */, 19 }, /* 8087 */ { MAD_F(0x04f42864) /* 0.309608831 */, 19 }, /* 8088 */ { MAD_F(0x04f45dea) /* 0.309659879 */, 19 }, /* 8089 */ { MAD_F(0x04f49372) /* 0.309710928 */, 19 }, /* 8090 */ { MAD_F(0x04f4c8fa) /* 0.309761980 */, 19 }, /* 8091 */ { MAD_F(0x04f4fe83) /* 0.309813033 */, 19 }, /* 8092 */ { MAD_F(0x04f5340c) /* 0.309864089 */, 19 }, /* 8093 */ { MAD_F(0x04f56996) /* 0.309915147 */, 19 }, /* 8094 */ { MAD_F(0x04f59f20) /* 0.309966207 */, 19 }, /* 8095 */ { MAD_F(0x04f5d4ab) /* 0.310017269 */, 19 }, /* 8096 */ { MAD_F(0x04f60a36) /* 0.310068333 */, 19 }, /* 8097 */ { MAD_F(0x04f63fc2) /* 0.310119400 */, 19 }, /* 8098 */ { MAD_F(0x04f6754f) /* 0.310170468 */, 19 }, /* 8099 */ { MAD_F(0x04f6aadc) /* 0.310221539 */, 19 }, /* 8100 */ { MAD_F(0x04f6e06a) /* 0.310272611 */, 19 }, /* 8101 */ { MAD_F(0x04f715f8) /* 0.310323686 */, 19 }, /* 8102 */ { MAD_F(0x04f74b87) /* 0.310374763 */, 19 }, /* 8103 */ { MAD_F(0x04f78116) /* 0.310425842 */, 19 }, /* 8104 */ { MAD_F(0x04f7b6a6) /* 0.310476923 */, 19 }, /* 8105 */ { MAD_F(0x04f7ec37) /* 0.310528006 */, 19 }, /* 8106 */ { MAD_F(0x04f821c8) /* 0.310579091 */, 19 }, /* 8107 */ { MAD_F(0x04f85759) /* 0.310630179 */, 19 }, /* 8108 */ { MAD_F(0x04f88cec) /* 0.310681268 */, 19 }, /* 8109 */ { MAD_F(0x04f8c27e) /* 0.310732360 */, 19 }, /* 8110 */ { MAD_F(0x04f8f812) /* 0.310783453 */, 19 }, /* 8111 */ { MAD_F(0x04f92da6) /* 0.310834549 */, 19 }, /* 8112 */ { MAD_F(0x04f9633a) /* 0.310885647 */, 19 }, /* 8113 */ { MAD_F(0x04f998cf) /* 0.310936747 */, 19 }, /* 8114 */ { MAD_F(0x04f9ce65) /* 0.310987849 */, 19 }, /* 8115 */ { MAD_F(0x04fa03fb) /* 0.311038953 */, 19 }, /* 8116 */ { MAD_F(0x04fa3992) /* 0.311090059 */, 19 }, /* 8117 */ { MAD_F(0x04fa6f29) /* 0.311141168 */, 19 }, /* 8118 */ { MAD_F(0x04faa4c1) /* 0.311192278 */, 19 }, /* 8119 */ { MAD_F(0x04fada59) /* 0.311243390 */, 19 }, /* 8120 */ { MAD_F(0x04fb0ff2) /* 0.311294505 */, 19 }, /* 8121 */ { MAD_F(0x04fb458c) /* 0.311345622 */, 19 }, /* 8122 */ { MAD_F(0x04fb7b26) /* 0.311396741 */, 19 }, /* 8123 */ { MAD_F(0x04fbb0c1) /* 0.311447862 */, 19 }, /* 8124 */ { MAD_F(0x04fbe65c) /* 0.311498985 */, 19 }, /* 8125 */ { MAD_F(0x04fc1bf8) /* 0.311550110 */, 19 }, /* 8126 */ { MAD_F(0x04fc5194) /* 0.311601237 */, 19 }, /* 8127 */ { MAD_F(0x04fc8731) /* 0.311652366 */, 19 }, /* 8128 */ { MAD_F(0x04fcbcce) /* 0.311703498 */, 19 }, /* 8129 */ { MAD_F(0x04fcf26c) /* 0.311754631 */, 19 }, /* 8130 */ { MAD_F(0x04fd280b) /* 0.311805767 */, 19 }, /* 8131 */ { MAD_F(0x04fd5daa) /* 0.311856905 */, 19 }, /* 8132 */ { MAD_F(0x04fd934a) /* 0.311908044 */, 19 }, /* 8133 */ { MAD_F(0x04fdc8ea) /* 0.311959186 */, 19 }, /* 8134 */ { MAD_F(0x04fdfe8b) /* 0.312010330 */, 19 }, /* 8135 */ { MAD_F(0x04fe342c) /* 0.312061476 */, 19 }, /* 8136 */ { MAD_F(0x04fe69ce) /* 0.312112625 */, 19 }, /* 8137 */ { MAD_F(0x04fe9f71) /* 0.312163775 */, 19 }, /* 8138 */ { MAD_F(0x04fed514) /* 0.312214927 */, 19 }, /* 8139 */ { MAD_F(0x04ff0ab8) /* 0.312266082 */, 19 }, /* 8140 */ { MAD_F(0x04ff405c) /* 0.312317238 */, 19 }, /* 8141 */ { MAD_F(0x04ff7601) /* 0.312368397 */, 19 }, /* 8142 */ { MAD_F(0x04ffaba6) /* 0.312419558 */, 19 }, /* 8143 */ { MAD_F(0x04ffe14c) /* 0.312470720 */, 19 }, /* 8144 */ { MAD_F(0x050016f3) /* 0.312521885 */, 19 }, /* 8145 */ { MAD_F(0x05004c9a) /* 0.312573052 */, 19 }, /* 8146 */ { MAD_F(0x05008241) /* 0.312624222 */, 19 }, /* 8147 */ { MAD_F(0x0500b7e9) /* 0.312675393 */, 19 }, /* 8148 */ { MAD_F(0x0500ed92) /* 0.312726566 */, 19 }, /* 8149 */ { MAD_F(0x0501233b) /* 0.312777742 */, 19 }, /* 8150 */ { MAD_F(0x050158e5) /* 0.312828919 */, 19 }, /* 8151 */ { MAD_F(0x05018e90) /* 0.312880099 */, 19 }, /* 8152 */ { MAD_F(0x0501c43b) /* 0.312931280 */, 19 }, /* 8153 */ { MAD_F(0x0501f9e6) /* 0.312982464 */, 19 }, /* 8154 */ { MAD_F(0x05022f92) /* 0.313033650 */, 19 }, /* 8155 */ { MAD_F(0x0502653f) /* 0.313084838 */, 19 }, /* 8156 */ { MAD_F(0x05029aec) /* 0.313136028 */, 19 }, /* 8157 */ { MAD_F(0x0502d09a) /* 0.313187220 */, 19 }, /* 8158 */ { MAD_F(0x05030648) /* 0.313238414 */, 19 }, /* 8159 */ { MAD_F(0x05033bf7) /* 0.313289611 */, 19 }, /* 8160 */ { MAD_F(0x050371a7) /* 0.313340809 */, 19 }, /* 8161 */ { MAD_F(0x0503a757) /* 0.313392010 */, 19 }, /* 8162 */ { MAD_F(0x0503dd07) /* 0.313443212 */, 19 }, /* 8163 */ { MAD_F(0x050412b9) /* 0.313494417 */, 19 }, /* 8164 */ { MAD_F(0x0504486a) /* 0.313545624 */, 19 }, /* 8165 */ { MAD_F(0x05047e1d) /* 0.313596833 */, 19 }, /* 8166 */ { MAD_F(0x0504b3cf) /* 0.313648044 */, 19 }, /* 8167 */ { MAD_F(0x0504e983) /* 0.313699257 */, 19 }, /* 8168 */ { MAD_F(0x05051f37) /* 0.313750472 */, 19 }, /* 8169 */ { MAD_F(0x050554eb) /* 0.313801689 */, 19 }, /* 8170 */ { MAD_F(0x05058aa0) /* 0.313852909 */, 19 }, /* 8171 */ { MAD_F(0x0505c056) /* 0.313904130 */, 19 }, /* 8172 */ { MAD_F(0x0505f60c) /* 0.313955354 */, 19 }, /* 8173 */ { MAD_F(0x05062bc3) /* 0.314006579 */, 19 }, /* 8174 */ { MAD_F(0x0506617a) /* 0.314057807 */, 19 }, /* 8175 */ { MAD_F(0x05069732) /* 0.314109037 */, 19 }, /* 8176 */ { MAD_F(0x0506cceb) /* 0.314160269 */, 19 }, /* 8177 */ { MAD_F(0x050702a4) /* 0.314211502 */, 19 }, /* 8178 */ { MAD_F(0x0507385d) /* 0.314262739 */, 19 }, /* 8179 */ { MAD_F(0x05076e17) /* 0.314313977 */, 19 }, /* 8180 */ { MAD_F(0x0507a3d2) /* 0.314365217 */, 19 }, /* 8181 */ { MAD_F(0x0507d98d) /* 0.314416459 */, 19 }, /* 8182 */ { MAD_F(0x05080f49) /* 0.314467704 */, 19 }, /* 8183 */ { MAD_F(0x05084506) /* 0.314518950 */, 19 }, /* 8184 */ { MAD_F(0x05087ac2) /* 0.314570199 */, 19 }, /* 8185 */ { MAD_F(0x0508b080) /* 0.314621449 */, 19 }, /* 8186 */ { MAD_F(0x0508e63e) /* 0.314672702 */, 19 }, /* 8187 */ { MAD_F(0x05091bfd) /* 0.314723957 */, 19 }, /* 8188 */ { MAD_F(0x050951bc) /* 0.314775214 */, 19 }, /* 8189 */ { MAD_F(0x0509877c) /* 0.314826473 */, 19 }, /* 8190 */ { MAD_F(0x0509bd3c) /* 0.314877734 */, 19 }, /* 8191 */ { MAD_F(0x0509f2fd) /* 0.314928997 */, 19 }, /* 8192 */ { MAD_F(0x050a28be) /* 0.314980262 */, 19 }, /* 8193 */ { MAD_F(0x050a5e80) /* 0.315031530 */, 19 }, /* 8194 */ { MAD_F(0x050a9443) /* 0.315082799 */, 19 }, /* 8195 */ { MAD_F(0x050aca06) /* 0.315134071 */, 19 }, /* 8196 */ { MAD_F(0x050affc9) /* 0.315185344 */, 19 }, /* 8197 */ { MAD_F(0x050b358e) /* 0.315236620 */, 19 }, /* 8198 */ { MAD_F(0x050b6b52) /* 0.315287898 */, 19 }, /* 8199 */ { MAD_F(0x050ba118) /* 0.315339178 */, 19 }, /* 8200 */ { MAD_F(0x050bd6de) /* 0.315390460 */, 19 }, /* 8201 */ { MAD_F(0x050c0ca4) /* 0.315441744 */, 19 }, /* 8202 */ { MAD_F(0x050c426b) /* 0.315493030 */, 19 }, /* 8203 */ { MAD_F(0x050c7833) /* 0.315544318 */, 19 }, /* 8204 */ { MAD_F(0x050cadfb) /* 0.315595608 */, 19 }, /* 8205 */ { MAD_F(0x050ce3c4) /* 0.315646901 */, 19 }, /* 8206 */ { MAD_F(0x050d198d) /* 0.315698195 */, 19 } sources_5316/external/mp3/mad_bit.c0000644000176700017670000001533110627342357016023 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: bit.c,v 1.12 2004/01/23 09:41:32 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # ifdef HAVE_LIMITS_H # include # else # define CHAR_BIT 8 # endif # include "mad_bit.h" /* * This is the lookup table for computing the CRC-check word. * As described in section 2.4.3.1 and depicted in Figure A.9 * of ISO/IEC 11172-3, the generator polynomial is: * * G(X) = X^16 + X^15 + X^2 + 1 */ static unsigned short const crc_table[256] = { 0x0000, 0x8005, 0x800f, 0x000a, 0x801b, 0x001e, 0x0014, 0x8011, 0x8033, 0x0036, 0x003c, 0x8039, 0x0028, 0x802d, 0x8027, 0x0022, 0x8063, 0x0066, 0x006c, 0x8069, 0x0078, 0x807d, 0x8077, 0x0072, 0x0050, 0x8055, 0x805f, 0x005a, 0x804b, 0x004e, 0x0044, 0x8041, 0x80c3, 0x00c6, 0x00cc, 0x80c9, 0x00d8, 0x80dd, 0x80d7, 0x00d2, 0x00f0, 0x80f5, 0x80ff, 0x00fa, 0x80eb, 0x00ee, 0x00e4, 0x80e1, 0x00a0, 0x80a5, 0x80af, 0x00aa, 0x80bb, 0x00be, 0x00b4, 0x80b1, 0x8093, 0x0096, 0x009c, 0x8099, 0x0088, 0x808d, 0x8087, 0x0082, 0x8183, 0x0186, 0x018c, 0x8189, 0x0198, 0x819d, 0x8197, 0x0192, 0x01b0, 0x81b5, 0x81bf, 0x01ba, 0x81ab, 0x01ae, 0x01a4, 0x81a1, 0x01e0, 0x81e5, 0x81ef, 0x01ea, 0x81fb, 0x01fe, 0x01f4, 0x81f1, 0x81d3, 0x01d6, 0x01dc, 0x81d9, 0x01c8, 0x81cd, 0x81c7, 0x01c2, 0x0140, 0x8145, 0x814f, 0x014a, 0x815b, 0x015e, 0x0154, 0x8151, 0x8173, 0x0176, 0x017c, 0x8179, 0x0168, 0x816d, 0x8167, 0x0162, 0x8123, 0x0126, 0x012c, 0x8129, 0x0138, 0x813d, 0x8137, 0x0132, 0x0110, 0x8115, 0x811f, 0x011a, 0x810b, 0x010e, 0x0104, 0x8101, 0x8303, 0x0306, 0x030c, 0x8309, 0x0318, 0x831d, 0x8317, 0x0312, 0x0330, 0x8335, 0x833f, 0x033a, 0x832b, 0x032e, 0x0324, 0x8321, 0x0360, 0x8365, 0x836f, 0x036a, 0x837b, 0x037e, 0x0374, 0x8371, 0x8353, 0x0356, 0x035c, 0x8359, 0x0348, 0x834d, 0x8347, 0x0342, 0x03c0, 0x83c5, 0x83cf, 0x03ca, 0x83db, 0x03de, 0x03d4, 0x83d1, 0x83f3, 0x03f6, 0x03fc, 0x83f9, 0x03e8, 0x83ed, 0x83e7, 0x03e2, 0x83a3, 0x03a6, 0x03ac, 0x83a9, 0x03b8, 0x83bd, 0x83b7, 0x03b2, 0x0390, 0x8395, 0x839f, 0x039a, 0x838b, 0x038e, 0x0384, 0x8381, 0x0280, 0x8285, 0x828f, 0x028a, 0x829b, 0x029e, 0x0294, 0x8291, 0x82b3, 0x02b6, 0x02bc, 0x82b9, 0x02a8, 0x82ad, 0x82a7, 0x02a2, 0x82e3, 0x02e6, 0x02ec, 0x82e9, 0x02f8, 0x82fd, 0x82f7, 0x02f2, 0x02d0, 0x82d5, 0x82df, 0x02da, 0x82cb, 0x02ce, 0x02c4, 0x82c1, 0x8243, 0x0246, 0x024c, 0x8249, 0x0258, 0x825d, 0x8257, 0x0252, 0x0270, 0x8275, 0x827f, 0x027a, 0x826b, 0x026e, 0x0264, 0x8261, 0x0220, 0x8225, 0x822f, 0x022a, 0x823b, 0x023e, 0x0234, 0x8231, 0x8213, 0x0216, 0x021c, 0x8219, 0x0208, 0x820d, 0x8207, 0x0202 }; # define CRC_POLY 0x8005 /* * NAME: bit->init() * DESCRIPTION: initialize bit pointer struct */ void mad_bit_init(struct mad_bitptr *bitptr, unsigned char const *byte) { bitptr->byte = byte; bitptr->cache = 0; bitptr->left = CHAR_BIT; } /* * NAME: bit->length() * DESCRIPTION: return number of bits between start and end points */ unsigned int mad_bit_length(struct mad_bitptr const *begin, struct mad_bitptr const *end) { return begin->left + CHAR_BIT * (end->byte - (begin->byte + 1)) + (CHAR_BIT - end->left); } /* * NAME: bit->nextbyte() * DESCRIPTION: return pointer to next unprocessed byte */ unsigned char const *mad_bit_nextbyte(struct mad_bitptr const *bitptr) { return bitptr->left == CHAR_BIT ? bitptr->byte : bitptr->byte + 1; } /* * NAME: bit->skip() * DESCRIPTION: advance bit pointer */ void mad_bit_skip(struct mad_bitptr *bitptr, unsigned int len) { bitptr->byte += len / CHAR_BIT; bitptr->left -= len % CHAR_BIT; if (bitptr->left > CHAR_BIT) { bitptr->byte++; bitptr->left += CHAR_BIT; } if (bitptr->left < CHAR_BIT) bitptr->cache = *bitptr->byte; } /* * NAME: bit->read() * DESCRIPTION: read an arbitrary number of bits and return their UIMSBF value */ unsigned long mad_bit_read(struct mad_bitptr *bitptr, unsigned int len) { register unsigned long value; if (bitptr->left == CHAR_BIT) bitptr->cache = *bitptr->byte; if (len < bitptr->left) { value = (bitptr->cache & ((1 << bitptr->left) - 1)) >> (bitptr->left - len); bitptr->left -= len; return value; } /* remaining bits in current byte */ value = bitptr->cache & ((1 << bitptr->left) - 1); len -= bitptr->left; bitptr->byte++; bitptr->left = CHAR_BIT; /* more bytes */ while (len >= CHAR_BIT) { value = (value << CHAR_BIT) | *bitptr->byte++; len -= CHAR_BIT; } if (len > 0) { bitptr->cache = *bitptr->byte; value = (value << len) | (bitptr->cache >> (CHAR_BIT - len)); bitptr->left -= len; } return value; } # if 0 /* * NAME: bit->write() * DESCRIPTION: write an arbitrary number of bits */ void mad_bit_write(struct mad_bitptr *bitptr, unsigned int len, unsigned long value) { unsigned char *ptr; ptr = (unsigned char *) bitptr->byte; /* ... */ } # endif /* * NAME: bit->crc() * DESCRIPTION: compute CRC-check word */ unsigned short mad_bit_crc(struct mad_bitptr bitptr, unsigned int len, unsigned short init) { register unsigned int crc; for (crc = init; len >= 32; len -= 32) { register unsigned long data; data = mad_bit_read(&bitptr, 32); crc = (crc << 8) ^ crc_table[((crc >> 8) ^ (data >> 24)) & 0xff]; crc = (crc << 8) ^ crc_table[((crc >> 8) ^ (data >> 16)) & 0xff]; crc = (crc << 8) ^ crc_table[((crc >> 8) ^ (data >> 8)) & 0xff]; crc = (crc << 8) ^ crc_table[((crc >> 8) ^ (data >> 0)) & 0xff]; } switch (len / 8) { case 3: crc = (crc << 8) ^ crc_table[((crc >> 8) ^ mad_bit_read(&bitptr, 8)) & 0xff]; case 2: crc = (crc << 8) ^ crc_table[((crc >> 8) ^ mad_bit_read(&bitptr, 8)) & 0xff]; case 1: crc = (crc << 8) ^ crc_table[((crc >> 8) ^ mad_bit_read(&bitptr, 8)) & 0xff]; len %= 8; case 0: break; } while (len--) { register unsigned int msb; msb = mad_bit_read(&bitptr, 1) ^ (crc >> 15); crc <<= 1; if (msb & 1) crc ^= CRC_POLY; } return crc & 0xffff; } sources_5316/external/mp3/mad_fixed.c0000644000176700017670000000342710627342357016347 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: fixed.c,v 1.13 2004/01/23 09:41:32 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # include "mad_fixed.h" /* * NAME: fixed->abs() * DESCRIPTION: return absolute value of a fixed-point number */ mad_fixed_t mad_f_abs(mad_fixed_t x) { return x < 0 ? -x : x; } /* * NAME: fixed->div() * DESCRIPTION: perform division using fixed-point math */ mad_fixed_t mad_f_div(mad_fixed_t x, mad_fixed_t y) { mad_fixed_t q, r; unsigned int bits; q = mad_f_abs(x / y); if (x < 0) { x = -x; y = -y; } r = x % y; if (y < 0) { x = -x; y = -y; } if (q > mad_f_intpart(MAD_F_MAX) && !(q == -mad_f_intpart(MAD_F_MIN) && r == 0 && (x < 0) != (y < 0))) return 0; for (bits = MAD_F_FRACBITS; bits && r; --bits) { q <<= 1, r <<= 1; if (r >= y) r -= y, ++q; } /* round */ if (2 * r >= y) ++q; /* fix sign */ if ((x < 0) != (y < 0)) q = -q; return q << bits; } sources_5316/external/mp3/mad_global.h0000644000176700017670000000315610627342357016514 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: global.h,v 1.11 2004/01/23 09:41:32 rob Exp $ */ # ifndef LIBMAD_GLOBAL_H # define LIBMAD_GLOBAL_H /* conditional debugging */ # if defined(DEBUG) && defined(NDEBUG) # error "cannot define both DEBUG and NDEBUG" # endif # if defined(DEBUG) # include # endif /* conditional features */ # if defined(OPT_SPEED) && defined(OPT_ACCURACY) # error "cannot optimize for both speed and accuracy" # endif # if defined(OPT_SPEED) && !defined(OPT_SSO) # define OPT_SSO # endif # if defined(HAVE_UNISTD_H) && defined(HAVE_WAITPID) && \ defined(HAVE_FCNTL) && defined(HAVE_PIPE) && defined(HAVE_FORK) # define USE_ASYNC # endif # if !defined(HAVE_ASSERT_H) # if defined(NDEBUG) # define assert(x) /* nothing */ # else # define assert(x) do { if (!(x)) abort(); } while (0) # endif # endif # endif sources_5316/external/mp3/mad_huffman.c0000644000176700017670000021675210627342357016703 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: huffman.c,v 1.10 2004/01/23 09:41:32 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # include "mad_huffman.h" /* * These are the Huffman code words for Layer III. * The data for these tables are derived from Table B.7 of ISO/IEC 11172-3. * * These tables support decoding up to 4 Huffman code bits at a time. */ # if defined(__GNUC__) || \ (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901) # define PTR(offs, bits) { .ptr = { 0, bits, offs } } # define V(v, w, x, y, hlen) { .value = { 1, hlen, v, w, x, y } } # else # define PTR(offs, bits) { { 0, bits, offs } } # if defined(WORDS_BIGENDIAN) # define V(v, w, x, y, hlen) { { 1, hlen, (v << 11) | (w << 10) | \ (x << 9) | (y << 8) } } # else # define V(v, w, x, y, hlen) { { 1, hlen, (v << 0) | (w << 1) | \ (x << 2) | (y << 3) } } # endif # endif static union huffquad const hufftabA[] = { /* 0000 */ PTR(16, 2), /* 0001 */ PTR(20, 2), /* 0010 */ PTR(24, 1), /* 0011 */ PTR(26, 1), /* 0100 */ V(0, 0, 1, 0, 4), /* 0101 */ V(0, 0, 0, 1, 4), /* 0110 */ V(0, 1, 0, 0, 4), /* 0111 */ V(1, 0, 0, 0, 4), /* 1000 */ V(0, 0, 0, 0, 1), /* 1001 */ V(0, 0, 0, 0, 1), /* 1010 */ V(0, 0, 0, 0, 1), /* 1011 */ V(0, 0, 0, 0, 1), /* 1100 */ V(0, 0, 0, 0, 1), /* 1101 */ V(0, 0, 0, 0, 1), /* 1110 */ V(0, 0, 0, 0, 1), /* 1111 */ V(0, 0, 0, 0, 1), /* 0000 ... */ /* 00 */ V(1, 0, 1, 1, 2), /* 16 */ /* 01 */ V(1, 1, 1, 1, 2), /* 10 */ V(1, 1, 0, 1, 2), /* 11 */ V(1, 1, 1, 0, 2), /* 0001 ... */ /* 00 */ V(0, 1, 1, 1, 2), /* 20 */ /* 01 */ V(0, 1, 0, 1, 2), /* 10 */ V(1, 0, 0, 1, 1), /* 11 */ V(1, 0, 0, 1, 1), /* 0010 ... */ /* 0 */ V(0, 1, 1, 0, 1), /* 24 */ /* 1 */ V(0, 0, 1, 1, 1), /* 0011 ... */ /* 0 */ V(1, 0, 1, 0, 1), /* 26 */ /* 1 */ V(1, 1, 0, 0, 1) }; static union huffquad const hufftabB[] = { /* 0000 */ V(1, 1, 1, 1, 4), /* 0001 */ V(1, 1, 1, 0, 4), /* 0010 */ V(1, 1, 0, 1, 4), /* 0011 */ V(1, 1, 0, 0, 4), /* 0100 */ V(1, 0, 1, 1, 4), /* 0101 */ V(1, 0, 1, 0, 4), /* 0110 */ V(1, 0, 0, 1, 4), /* 0111 */ V(1, 0, 0, 0, 4), /* 1000 */ V(0, 1, 1, 1, 4), /* 1001 */ V(0, 1, 1, 0, 4), /* 1010 */ V(0, 1, 0, 1, 4), /* 1011 */ V(0, 1, 0, 0, 4), /* 1100 */ V(0, 0, 1, 1, 4), /* 1101 */ V(0, 0, 1, 0, 4), /* 1110 */ V(0, 0, 0, 1, 4), /* 1111 */ V(0, 0, 0, 0, 4) }; # undef V # undef PTR # if defined(__GNUC__) || \ (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901) # define PTR(offs, bits) { .ptr = { 0, bits, offs } } # define V(x, y, hlen) { .value = { 1, hlen, x, y } } # else # define PTR(offs, bits) { { 0, bits, offs } } # if defined(WORDS_BIGENDIAN) # define V(x, y, hlen) { { 1, hlen, (x << 8) | (y << 4) } } # else # define V(x, y, hlen) { { 1, hlen, (x << 0) | (y << 4) } } # endif # endif static union huffpair const hufftab0[] = { /* */ V(0, 0, 0) }; static union huffpair const hufftab1[] = { /* 000 */ V(1, 1, 3), /* 001 */ V(0, 1, 3), /* 010 */ V(1, 0, 2), /* 011 */ V(1, 0, 2), /* 100 */ V(0, 0, 1), /* 101 */ V(0, 0, 1), /* 110 */ V(0, 0, 1), /* 111 */ V(0, 0, 1) }; static union huffpair const hufftab2[] = { /* 000 */ PTR(8, 3), /* 001 */ V(1, 1, 3), /* 010 */ V(0, 1, 3), /* 011 */ V(1, 0, 3), /* 100 */ V(0, 0, 1), /* 101 */ V(0, 0, 1), /* 110 */ V(0, 0, 1), /* 111 */ V(0, 0, 1), /* 000 ... */ /* 000 */ V(2, 2, 3), /* 8 */ /* 001 */ V(0, 2, 3), /* 010 */ V(1, 2, 2), /* 011 */ V(1, 2, 2), /* 100 */ V(2, 1, 2), /* 101 */ V(2, 1, 2), /* 110 */ V(2, 0, 2), /* 111 */ V(2, 0, 2) }; static union huffpair const hufftab3[] = { /* 000 */ PTR(8, 3), /* 001 */ V(1, 0, 3), /* 010 */ V(1, 1, 2), /* 011 */ V(1, 1, 2), /* 100 */ V(0, 1, 2), /* 101 */ V(0, 1, 2), /* 110 */ V(0, 0, 2), /* 111 */ V(0, 0, 2), /* 000 ... */ /* 000 */ V(2, 2, 3), /* 8 */ /* 001 */ V(0, 2, 3), /* 010 */ V(1, 2, 2), /* 011 */ V(1, 2, 2), /* 100 */ V(2, 1, 2), /* 101 */ V(2, 1, 2), /* 110 */ V(2, 0, 2), /* 111 */ V(2, 0, 2) }; static union huffpair const hufftab5[] = { /* 000 */ PTR(8, 4), /* 001 */ V(1, 1, 3), /* 010 */ V(0, 1, 3), /* 011 */ V(1, 0, 3), /* 100 */ V(0, 0, 1), /* 101 */ V(0, 0, 1), /* 110 */ V(0, 0, 1), /* 111 */ V(0, 0, 1), /* 000 ... */ /* 0000 */ PTR(24, 1), /* 8 */ /* 0001 */ V(3, 2, 4), /* 0010 */ V(3, 1, 3), /* 0011 */ V(3, 1, 3), /* 0100 */ V(1, 3, 4), /* 0101 */ V(0, 3, 4), /* 0110 */ V(3, 0, 4), /* 0111 */ V(2, 2, 4), /* 1000 */ V(1, 2, 3), /* 1001 */ V(1, 2, 3), /* 1010 */ V(2, 1, 3), /* 1011 */ V(2, 1, 3), /* 1100 */ V(0, 2, 3), /* 1101 */ V(0, 2, 3), /* 1110 */ V(2, 0, 3), /* 1111 */ V(2, 0, 3), /* 000 0000 ... */ /* 0 */ V(3, 3, 1), /* 24 */ /* 1 */ V(2, 3, 1) }; static union huffpair const hufftab6[] = { /* 0000 */ PTR(16, 3), /* 0001 */ PTR(24, 1), /* 0010 */ PTR(26, 1), /* 0011 */ V(1, 2, 4), /* 0100 */ V(2, 1, 4), /* 0101 */ V(2, 0, 4), /* 0110 */ V(0, 1, 3), /* 0111 */ V(0, 1, 3), /* 1000 */ V(1, 1, 2), /* 1001 */ V(1, 1, 2), /* 1010 */ V(1, 1, 2), /* 1011 */ V(1, 1, 2), /* 1100 */ V(1, 0, 3), /* 1101 */ V(1, 0, 3), /* 1110 */ V(0, 0, 3), /* 1111 */ V(0, 0, 3), /* 0000 ... */ /* 000 */ V(3, 3, 3), /* 16 */ /* 001 */ V(0, 3, 3), /* 010 */ V(2, 3, 2), /* 011 */ V(2, 3, 2), /* 100 */ V(3, 2, 2), /* 101 */ V(3, 2, 2), /* 110 */ V(3, 0, 2), /* 111 */ V(3, 0, 2), /* 0001 ... */ /* 0 */ V(1, 3, 1), /* 24 */ /* 1 */ V(3, 1, 1), /* 0010 ... */ /* 0 */ V(2, 2, 1), /* 26 */ /* 1 */ V(0, 2, 1) }; static union huffpair const hufftab7[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 4), /* 0010 */ PTR(48, 2), /* 0011 */ V(1, 1, 4), /* 0100 */ V(0, 1, 3), /* 0101 */ V(0, 1, 3), /* 0110 */ V(1, 0, 3), /* 0111 */ V(1, 0, 3), /* 1000 */ V(0, 0, 1), /* 1001 */ V(0, 0, 1), /* 1010 */ V(0, 0, 1), /* 1011 */ V(0, 0, 1), /* 1100 */ V(0, 0, 1), /* 1101 */ V(0, 0, 1), /* 1110 */ V(0, 0, 1), /* 1111 */ V(0, 0, 1), /* 0000 ... */ /* 0000 */ PTR(52, 2), /* 16 */ /* 0001 */ PTR(56, 1), /* 0010 */ PTR(58, 1), /* 0011 */ V(1, 5, 4), /* 0100 */ V(5, 1, 4), /* 0101 */ PTR(60, 1), /* 0110 */ V(5, 0, 4), /* 0111 */ PTR(62, 1), /* 1000 */ V(2, 4, 4), /* 1001 */ V(4, 2, 4), /* 1010 */ V(1, 4, 3), /* 1011 */ V(1, 4, 3), /* 1100 */ V(4, 1, 3), /* 1101 */ V(4, 1, 3), /* 1110 */ V(4, 0, 3), /* 1111 */ V(4, 0, 3), /* 0001 ... */ /* 0000 */ V(0, 4, 4), /* 32 */ /* 0001 */ V(2, 3, 4), /* 0010 */ V(3, 2, 4), /* 0011 */ V(0, 3, 4), /* 0100 */ V(1, 3, 3), /* 0101 */ V(1, 3, 3), /* 0110 */ V(3, 1, 3), /* 0111 */ V(3, 1, 3), /* 1000 */ V(3, 0, 3), /* 1001 */ V(3, 0, 3), /* 1010 */ V(2, 2, 3), /* 1011 */ V(2, 2, 3), /* 1100 */ V(1, 2, 2), /* 1101 */ V(1, 2, 2), /* 1110 */ V(1, 2, 2), /* 1111 */ V(1, 2, 2), /* 0010 ... */ /* 00 */ V(2, 1, 1), /* 48 */ /* 01 */ V(2, 1, 1), /* 10 */ V(0, 2, 2), /* 11 */ V(2, 0, 2), /* 0000 0000 ... */ /* 00 */ V(5, 5, 2), /* 52 */ /* 01 */ V(4, 5, 2), /* 10 */ V(5, 4, 2), /* 11 */ V(5, 3, 2), /* 0000 0001 ... */ /* 0 */ V(3, 5, 1), /* 56 */ /* 1 */ V(4, 4, 1), /* 0000 0010 ... */ /* 0 */ V(2, 5, 1), /* 58 */ /* 1 */ V(5, 2, 1), /* 0000 0101 ... */ /* 0 */ V(0, 5, 1), /* 60 */ /* 1 */ V(3, 4, 1), /* 0000 0111 ... */ /* 0 */ V(4, 3, 1), /* 62 */ /* 1 */ V(3, 3, 1) }; # if 0 /* this version saves 8 entries (16 bytes) at the expense of an extra lookup in 4 out of 36 cases */ static union huffpair const hufftab8[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 2), /* 0010 */ V(1, 2, 4), /* 0011 */ V(2, 1, 4), /* 0100 */ V(1, 1, 2), /* 0101 */ V(1, 1, 2), /* 0110 */ V(1, 1, 2), /* 0111 */ V(1, 1, 2), /* 1000 */ V(0, 1, 3), /* 1001 */ V(0, 1, 3), /* 1010 */ V(1, 0, 3), /* 1011 */ V(1, 0, 3), /* 1100 */ V(0, 0, 2), /* 1101 */ V(0, 0, 2), /* 1110 */ V(0, 0, 2), /* 1111 */ V(0, 0, 2), /* 0000 ... */ /* 0000 */ PTR(36, 3), /* 16 */ /* 0001 */ PTR(44, 2), /* 0010 */ PTR(48, 1), /* 0011 */ V(1, 5, 4), /* 0100 */ V(5, 1, 4), /* 0101 */ PTR(50, 1), /* 0110 */ PTR(52, 1), /* 0111 */ V(2, 4, 4), /* 1000 */ V(4, 2, 4), /* 1001 */ V(1, 4, 4), /* 1010 */ V(4, 1, 3), /* 1011 */ V(4, 1, 3), /* 1100 */ V(0, 4, 4), /* 1101 */ V(4, 0, 4), /* 1110 */ V(2, 3, 4), /* 1111 */ V(3, 2, 4), /* 0001 ... */ /* 00 */ PTR(54, 2), /* 32 */ /* 01 */ V(2, 2, 2), /* 10 */ V(0, 2, 2), /* 11 */ V(2, 0, 2), /* 0000 0000 ... */ /* 000 */ V(5, 5, 3), /* 36 */ /* 001 */ V(5, 4, 3), /* 010 */ V(4, 5, 2), /* 011 */ V(4, 5, 2), /* 100 */ V(5, 3, 1), /* 101 */ V(5, 3, 1), /* 110 */ V(5, 3, 1), /* 111 */ V(5, 3, 1), /* 0000 0001 ... */ /* 00 */ V(3, 5, 2), /* 44 */ /* 01 */ V(4, 4, 2), /* 10 */ V(2, 5, 1), /* 11 */ V(2, 5, 1), /* 0000 0010 ... */ /* 0 */ V(5, 2, 1), /* 48 */ /* 1 */ V(0, 5, 1), /* 0000 0101 ... */ /* 0 */ V(3, 4, 1), /* 50 */ /* 1 */ V(4, 3, 1), /* 0000 0110 ... */ /* 0 */ V(5, 0, 1), /* 52 */ /* 1 */ V(3, 3, 1), /* 0001 00 ... */ /* 00 */ V(1, 3, 2), /* 54 */ /* 01 */ V(3, 1, 2), /* 10 */ V(0, 3, 2), /* 11 */ V(3, 0, 2), }; # else static union huffpair const hufftab8[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 4), /* 0010 */ V(1, 2, 4), /* 0011 */ V(2, 1, 4), /* 0100 */ V(1, 1, 2), /* 0101 */ V(1, 1, 2), /* 0110 */ V(1, 1, 2), /* 0111 */ V(1, 1, 2), /* 1000 */ V(0, 1, 3), /* 1001 */ V(0, 1, 3), /* 1010 */ V(1, 0, 3), /* 1011 */ V(1, 0, 3), /* 1100 */ V(0, 0, 2), /* 1101 */ V(0, 0, 2), /* 1110 */ V(0, 0, 2), /* 1111 */ V(0, 0, 2), /* 0000 ... */ /* 0000 */ PTR(48, 3), /* 16 */ /* 0001 */ PTR(56, 2), /* 0010 */ PTR(60, 1), /* 0011 */ V(1, 5, 4), /* 0100 */ V(5, 1, 4), /* 0101 */ PTR(62, 1), /* 0110 */ PTR(64, 1), /* 0111 */ V(2, 4, 4), /* 1000 */ V(4, 2, 4), /* 1001 */ V(1, 4, 4), /* 1010 */ V(4, 1, 3), /* 1011 */ V(4, 1, 3), /* 1100 */ V(0, 4, 4), /* 1101 */ V(4, 0, 4), /* 1110 */ V(2, 3, 4), /* 1111 */ V(3, 2, 4), /* 0001 ... */ /* 0000 */ V(1, 3, 4), /* 32 */ /* 0001 */ V(3, 1, 4), /* 0010 */ V(0, 3, 4), /* 0011 */ V(3, 0, 4), /* 0100 */ V(2, 2, 2), /* 0101 */ V(2, 2, 2), /* 0110 */ V(2, 2, 2), /* 0111 */ V(2, 2, 2), /* 1000 */ V(0, 2, 2), /* 1001 */ V(0, 2, 2), /* 1010 */ V(0, 2, 2), /* 1011 */ V(0, 2, 2), /* 1100 */ V(2, 0, 2), /* 1101 */ V(2, 0, 2), /* 1110 */ V(2, 0, 2), /* 1111 */ V(2, 0, 2), /* 0000 0000 ... */ /* 000 */ V(5, 5, 3), /* 48 */ /* 001 */ V(5, 4, 3), /* 010 */ V(4, 5, 2), /* 011 */ V(4, 5, 2), /* 100 */ V(5, 3, 1), /* 101 */ V(5, 3, 1), /* 110 */ V(5, 3, 1), /* 111 */ V(5, 3, 1), /* 0000 0001 ... */ /* 00 */ V(3, 5, 2), /* 56 */ /* 01 */ V(4, 4, 2), /* 10 */ V(2, 5, 1), /* 11 */ V(2, 5, 1), /* 0000 0010 ... */ /* 0 */ V(5, 2, 1), /* 60 */ /* 1 */ V(0, 5, 1), /* 0000 0101 ... */ /* 0 */ V(3, 4, 1), /* 62 */ /* 1 */ V(4, 3, 1), /* 0000 0110 ... */ /* 0 */ V(5, 0, 1), /* 64 */ /* 1 */ V(3, 3, 1) }; # endif static union huffpair const hufftab9[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 3), /* 0010 */ PTR(40, 2), /* 0011 */ PTR(44, 2), /* 0100 */ PTR(48, 1), /* 0101 */ V(1, 2, 4), /* 0110 */ V(2, 1, 4), /* 0111 */ V(2, 0, 4), /* 1000 */ V(1, 1, 3), /* 1001 */ V(1, 1, 3), /* 1010 */ V(0, 1, 3), /* 1011 */ V(0, 1, 3), /* 1100 */ V(1, 0, 3), /* 1101 */ V(1, 0, 3), /* 1110 */ V(0, 0, 3), /* 1111 */ V(0, 0, 3), /* 0000 ... */ /* 0000 */ PTR(50, 1), /* 16 */ /* 0001 */ V(3, 5, 4), /* 0010 */ V(5, 3, 4), /* 0011 */ PTR(52, 1), /* 0100 */ V(4, 4, 4), /* 0101 */ V(2, 5, 4), /* 0110 */ V(5, 2, 4), /* 0111 */ V(1, 5, 4), /* 1000 */ V(5, 1, 3), /* 1001 */ V(5, 1, 3), /* 1010 */ V(3, 4, 3), /* 1011 */ V(3, 4, 3), /* 1100 */ V(4, 3, 3), /* 1101 */ V(4, 3, 3), /* 1110 */ V(5, 0, 4), /* 1111 */ V(0, 4, 4), /* 0001 ... */ /* 000 */ V(2, 4, 3), /* 32 */ /* 001 */ V(4, 2, 3), /* 010 */ V(3, 3, 3), /* 011 */ V(4, 0, 3), /* 100 */ V(1, 4, 2), /* 101 */ V(1, 4, 2), /* 110 */ V(4, 1, 2), /* 111 */ V(4, 1, 2), /* 0010 ... */ /* 00 */ V(2, 3, 2), /* 40 */ /* 01 */ V(3, 2, 2), /* 10 */ V(1, 3, 1), /* 11 */ V(1, 3, 1), /* 0011 ... */ /* 00 */ V(3, 1, 1), /* 44 */ /* 01 */ V(3, 1, 1), /* 10 */ V(0, 3, 2), /* 11 */ V(3, 0, 2), /* 0100 ... */ /* 0 */ V(2, 2, 1), /* 48 */ /* 1 */ V(0, 2, 1), /* 0000 0000 ... */ /* 0 */ V(5, 5, 1), /* 50 */ /* 1 */ V(4, 5, 1), /* 0000 0011 ... */ /* 0 */ V(5, 4, 1), /* 52 */ /* 1 */ V(0, 5, 1) }; static union huffpair const hufftab10[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 4), /* 0010 */ PTR(48, 2), /* 0011 */ V(1, 1, 4), /* 0100 */ V(0, 1, 3), /* 0101 */ V(0, 1, 3), /* 0110 */ V(1, 0, 3), /* 0111 */ V(1, 0, 3), /* 1000 */ V(0, 0, 1), /* 1001 */ V(0, 0, 1), /* 1010 */ V(0, 0, 1), /* 1011 */ V(0, 0, 1), /* 1100 */ V(0, 0, 1), /* 1101 */ V(0, 0, 1), /* 1110 */ V(0, 0, 1), /* 1111 */ V(0, 0, 1), /* 0000 ... */ /* 0000 */ PTR(52, 3), /* 16 */ /* 0001 */ PTR(60, 2), /* 0010 */ PTR(64, 3), /* 0011 */ PTR(72, 1), /* 0100 */ PTR(74, 2), /* 0101 */ PTR(78, 2), /* 0110 */ PTR(82, 2), /* 0111 */ V(1, 7, 4), /* 1000 */ V(7, 1, 4), /* 1001 */ PTR(86, 1), /* 1010 */ PTR(88, 2), /* 1011 */ PTR(92, 2), /* 1100 */ V(1, 6, 4), /* 1101 */ V(6, 1, 4), /* 1110 */ V(6, 0, 4), /* 1111 */ PTR(96, 1), /* 0001 ... */ /* 0000 */ PTR(98, 1), /* 32 */ /* 0001 */ PTR(100, 1), /* 0010 */ V(1, 4, 4), /* 0011 */ V(4, 1, 4), /* 0100 */ V(4, 0, 4), /* 0101 */ V(2, 3, 4), /* 0110 */ V(3, 2, 4), /* 0111 */ V(0, 3, 4), /* 1000 */ V(1, 3, 3), /* 1001 */ V(1, 3, 3), /* 1010 */ V(3, 1, 3), /* 1011 */ V(3, 1, 3), /* 1100 */ V(3, 0, 3), /* 1101 */ V(3, 0, 3), /* 1110 */ V(2, 2, 3), /* 1111 */ V(2, 2, 3), /* 0010 ... */ /* 00 */ V(1, 2, 2), /* 48 */ /* 01 */ V(2, 1, 2), /* 10 */ V(0, 2, 2), /* 11 */ V(2, 0, 2), /* 0000 0000 ... */ /* 000 */ V(7, 7, 3), /* 52 */ /* 001 */ V(6, 7, 3), /* 010 */ V(7, 6, 3), /* 011 */ V(5, 7, 3), /* 100 */ V(7, 5, 3), /* 101 */ V(6, 6, 3), /* 110 */ V(4, 7, 2), /* 111 */ V(4, 7, 2), /* 0000 0001 ... */ /* 00 */ V(7, 4, 2), /* 60 */ /* 01 */ V(5, 6, 2), /* 10 */ V(6, 5, 2), /* 11 */ V(3, 7, 2), /* 0000 0010 ... */ /* 000 */ V(7, 3, 2), /* 64 */ /* 001 */ V(7, 3, 2), /* 010 */ V(4, 6, 2), /* 011 */ V(4, 6, 2), /* 100 */ V(5, 5, 3), /* 101 */ V(5, 4, 3), /* 110 */ V(6, 3, 2), /* 111 */ V(6, 3, 2), /* 0000 0011 ... */ /* 0 */ V(2, 7, 1), /* 72 */ /* 1 */ V(7, 2, 1), /* 0000 0100 ... */ /* 00 */ V(6, 4, 2), /* 74 */ /* 01 */ V(0, 7, 2), /* 10 */ V(7, 0, 1), /* 11 */ V(7, 0, 1), /* 0000 0101 ... */ /* 00 */ V(6, 2, 1), /* 78 */ /* 01 */ V(6, 2, 1), /* 10 */ V(4, 5, 2), /* 11 */ V(3, 5, 2), /* 0000 0110 ... */ /* 00 */ V(0, 6, 1), /* 82 */ /* 01 */ V(0, 6, 1), /* 10 */ V(5, 3, 2), /* 11 */ V(4, 4, 2), /* 0000 1001 ... */ /* 0 */ V(3, 6, 1), /* 86 */ /* 1 */ V(2, 6, 1), /* 0000 1010 ... */ /* 00 */ V(2, 5, 2), /* 88 */ /* 01 */ V(5, 2, 2), /* 10 */ V(1, 5, 1), /* 11 */ V(1, 5, 1), /* 0000 1011 ... */ /* 00 */ V(5, 1, 1), /* 92 */ /* 01 */ V(5, 1, 1), /* 10 */ V(3, 4, 2), /* 11 */ V(4, 3, 2), /* 0000 1111 ... */ /* 0 */ V(0, 5, 1), /* 96 */ /* 1 */ V(5, 0, 1), /* 0001 0000 ... */ /* 0 */ V(2, 4, 1), /* 98 */ /* 1 */ V(4, 2, 1), /* 0001 0001 ... */ /* 0 */ V(3, 3, 1), /* 100 */ /* 1 */ V(0, 4, 1) }; static union huffpair const hufftab11[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 4), /* 0010 */ PTR(48, 4), /* 0011 */ PTR(64, 3), /* 0100 */ V(1, 2, 4), /* 0101 */ PTR(72, 1), /* 0110 */ V(1, 1, 3), /* 0111 */ V(1, 1, 3), /* 1000 */ V(0, 1, 3), /* 1001 */ V(0, 1, 3), /* 1010 */ V(1, 0, 3), /* 1011 */ V(1, 0, 3), /* 1100 */ V(0, 0, 2), /* 1101 */ V(0, 0, 2), /* 1110 */ V(0, 0, 2), /* 1111 */ V(0, 0, 2), /* 0000 ... */ /* 0000 */ PTR(74, 2), /* 16 */ /* 0001 */ PTR(78, 3), /* 0010 */ PTR(86, 2), /* 0011 */ PTR(90, 1), /* 0100 */ PTR(92, 2), /* 0101 */ V(2, 7, 4), /* 0110 */ V(7, 2, 4), /* 0111 */ PTR(96, 1), /* 1000 */ V(7, 1, 3), /* 1001 */ V(7, 1, 3), /* 1010 */ V(1, 7, 4), /* 1011 */ V(7, 0, 4), /* 1100 */ V(3, 6, 4), /* 1101 */ V(6, 3, 4), /* 1110 */ V(6, 0, 4), /* 1111 */ PTR(98, 1), /* 0001 ... */ /* 0000 */ PTR(100, 1), /* 32 */ /* 0001 */ V(1, 5, 4), /* 0010 */ V(6, 2, 3), /* 0011 */ V(6, 2, 3), /* 0100 */ V(2, 6, 4), /* 0101 */ V(0, 6, 4), /* 0110 */ V(1, 6, 3), /* 0111 */ V(1, 6, 3), /* 1000 */ V(6, 1, 3), /* 1001 */ V(6, 1, 3), /* 1010 */ V(5, 1, 4), /* 1011 */ V(3, 4, 4), /* 1100 */ V(5, 0, 4), /* 1101 */ PTR(102, 1), /* 1110 */ V(2, 4, 4), /* 1111 */ V(4, 2, 4), /* 0010 ... */ /* 0000 */ V(1, 4, 4), /* 48 */ /* 0001 */ V(4, 1, 4), /* 0010 */ V(0, 4, 4), /* 0011 */ V(4, 0, 4), /* 0100 */ V(2, 3, 3), /* 0101 */ V(2, 3, 3), /* 0110 */ V(3, 2, 3), /* 0111 */ V(3, 2, 3), /* 1000 */ V(1, 3, 2), /* 1001 */ V(1, 3, 2), /* 1010 */ V(1, 3, 2), /* 1011 */ V(1, 3, 2), /* 1100 */ V(3, 1, 2), /* 1101 */ V(3, 1, 2), /* 1110 */ V(3, 1, 2), /* 1111 */ V(3, 1, 2), /* 0011 ... */ /* 000 */ V(0, 3, 3), /* 64 */ /* 001 */ V(3, 0, 3), /* 010 */ V(2, 2, 2), /* 011 */ V(2, 2, 2), /* 100 */ V(2, 1, 1), /* 101 */ V(2, 1, 1), /* 110 */ V(2, 1, 1), /* 111 */ V(2, 1, 1), /* 0101 ... */ /* 0 */ V(0, 2, 1), /* 72 */ /* 1 */ V(2, 0, 1), /* 0000 0000 ... */ /* 00 */ V(7, 7, 2), /* 74 */ /* 01 */ V(6, 7, 2), /* 10 */ V(7, 6, 2), /* 11 */ V(7, 5, 2), /* 0000 0001 ... */ /* 000 */ V(6, 6, 2), /* 78 */ /* 001 */ V(6, 6, 2), /* 010 */ V(4, 7, 2), /* 011 */ V(4, 7, 2), /* 100 */ V(7, 4, 2), /* 101 */ V(7, 4, 2), /* 110 */ V(5, 7, 3), /* 111 */ V(5, 5, 3), /* 0000 0010 ... */ /* 00 */ V(5, 6, 2), /* 86 */ /* 01 */ V(6, 5, 2), /* 10 */ V(3, 7, 1), /* 11 */ V(3, 7, 1), /* 0000 0011 ... */ /* 0 */ V(7, 3, 1), /* 90 */ /* 1 */ V(4, 6, 1), /* 0000 0100 ... */ /* 00 */ V(4, 5, 2), /* 92 */ /* 01 */ V(5, 4, 2), /* 10 */ V(3, 5, 2), /* 11 */ V(5, 3, 2), /* 0000 0111 ... */ /* 0 */ V(6, 4, 1), /* 96 */ /* 1 */ V(0, 7, 1), /* 0000 1111 ... */ /* 0 */ V(4, 4, 1), /* 98 */ /* 1 */ V(2, 5, 1), /* 0001 0000 ... */ /* 0 */ V(5, 2, 1), /* 100 */ /* 1 */ V(0, 5, 1), /* 0001 1101 ... */ /* 0 */ V(4, 3, 1), /* 102 */ /* 1 */ V(3, 3, 1) }; static union huffpair const hufftab12[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 4), /* 0010 */ PTR(48, 4), /* 0011 */ PTR(64, 2), /* 0100 */ PTR(68, 3), /* 0101 */ PTR(76, 1), /* 0110 */ V(1, 2, 4), /* 0111 */ V(2, 1, 4), /* 1000 */ PTR(78, 1), /* 1001 */ V(0, 0, 4), /* 1010 */ V(1, 1, 3), /* 1011 */ V(1, 1, 3), /* 1100 */ V(0, 1, 3), /* 1101 */ V(0, 1, 3), /* 1110 */ V(1, 0, 3), /* 1111 */ V(1, 0, 3), /* 0000 ... */ /* 0000 */ PTR(80, 2), /* 16 */ /* 0001 */ PTR(84, 1), /* 0010 */ PTR(86, 1), /* 0011 */ PTR(88, 1), /* 0100 */ V(5, 6, 4), /* 0101 */ V(3, 7, 4), /* 0110 */ PTR(90, 1), /* 0111 */ V(2, 7, 4), /* 1000 */ V(7, 2, 4), /* 1001 */ V(4, 6, 4), /* 1010 */ V(6, 4, 4), /* 1011 */ V(1, 7, 4), /* 1100 */ V(7, 1, 4), /* 1101 */ PTR(92, 1), /* 1110 */ V(3, 6, 4), /* 1111 */ V(6, 3, 4), /* 0001 ... */ /* 0000 */ V(4, 5, 4), /* 32 */ /* 0001 */ V(5, 4, 4), /* 0010 */ V(4, 4, 4), /* 0011 */ PTR(94, 1), /* 0100 */ V(2, 6, 3), /* 0101 */ V(2, 6, 3), /* 0110 */ V(6, 2, 3), /* 0111 */ V(6, 2, 3), /* 1000 */ V(6, 1, 3), /* 1001 */ V(6, 1, 3), /* 1010 */ V(1, 6, 4), /* 1011 */ V(6, 0, 4), /* 1100 */ V(3, 5, 4), /* 1101 */ V(5, 3, 4), /* 1110 */ V(2, 5, 4), /* 1111 */ V(5, 2, 4), /* 0010 ... */ /* 0000 */ V(1, 5, 3), /* 48 */ /* 0001 */ V(1, 5, 3), /* 0010 */ V(5, 1, 3), /* 0011 */ V(5, 1, 3), /* 0100 */ V(3, 4, 3), /* 0101 */ V(3, 4, 3), /* 0110 */ V(4, 3, 3), /* 0111 */ V(4, 3, 3), /* 1000 */ V(5, 0, 4), /* 1001 */ V(0, 4, 4), /* 1010 */ V(2, 4, 3), /* 1011 */ V(2, 4, 3), /* 1100 */ V(4, 2, 3), /* 1101 */ V(4, 2, 3), /* 1110 */ V(1, 4, 3), /* 1111 */ V(1, 4, 3), /* 0011 ... */ /* 00 */ V(3, 3, 2), /* 64 */ /* 01 */ V(4, 1, 2), /* 10 */ V(2, 3, 2), /* 11 */ V(3, 2, 2), /* 0100 ... */ /* 000 */ V(4, 0, 3), /* 68 */ /* 001 */ V(0, 3, 3), /* 010 */ V(3, 0, 2), /* 011 */ V(3, 0, 2), /* 100 */ V(1, 3, 1), /* 101 */ V(1, 3, 1), /* 110 */ V(1, 3, 1), /* 111 */ V(1, 3, 1), /* 0101 ... */ /* 0 */ V(3, 1, 1), /* 76 */ /* 1 */ V(2, 2, 1), /* 1000 ... */ /* 0 */ V(0, 2, 1), /* 78 */ /* 1 */ V(2, 0, 1), /* 0000 0000 ... */ /* 00 */ V(7, 7, 2), /* 80 */ /* 01 */ V(6, 7, 2), /* 10 */ V(7, 6, 1), /* 11 */ V(7, 6, 1), /* 0000 0001 ... */ /* 0 */ V(5, 7, 1), /* 84 */ /* 1 */ V(7, 5, 1), /* 0000 0010 ... */ /* 0 */ V(6, 6, 1), /* 86 */ /* 1 */ V(4, 7, 1), /* 0000 0011 ... */ /* 0 */ V(7, 4, 1), /* 88 */ /* 1 */ V(6, 5, 1), /* 0000 0110 ... */ /* 0 */ V(7, 3, 1), /* 90 */ /* 1 */ V(5, 5, 1), /* 0000 1101 ... */ /* 0 */ V(0, 7, 1), /* 92 */ /* 1 */ V(7, 0, 1), /* 0001 0011 ... */ /* 0 */ V(0, 6, 1), /* 94 */ /* 1 */ V(0, 5, 1) }; static union huffpair const hufftab13[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 4), /* 0010 */ PTR(48, 4), /* 0011 */ PTR(64, 2), /* 0100 */ V(1, 1, 4), /* 0101 */ V(0, 1, 4), /* 0110 */ V(1, 0, 3), /* 0111 */ V(1, 0, 3), /* 1000 */ V(0, 0, 1), /* 1001 */ V(0, 0, 1), /* 1010 */ V(0, 0, 1), /* 1011 */ V(0, 0, 1), /* 1100 */ V(0, 0, 1), /* 1101 */ V(0, 0, 1), /* 1110 */ V(0, 0, 1), /* 1111 */ V(0, 0, 1), /* 0000 ... */ /* 0000 */ PTR(68, 4), /* 16 */ /* 0001 */ PTR(84, 4), /* 0010 */ PTR(100, 4), /* 0011 */ PTR(116, 4), /* 0100 */ PTR(132, 4), /* 0101 */ PTR(148, 4), /* 0110 */ PTR(164, 3), /* 0111 */ PTR(172, 3), /* 1000 */ PTR(180, 3), /* 1001 */ PTR(188, 3), /* 1010 */ PTR(196, 3), /* 1011 */ PTR(204, 3), /* 1100 */ PTR(212, 1), /* 1101 */ PTR(214, 2), /* 1110 */ PTR(218, 3), /* 1111 */ PTR(226, 1), /* 0001 ... */ /* 0000 */ PTR(228, 2), /* 32 */ /* 0001 */ PTR(232, 2), /* 0010 */ PTR(236, 2), /* 0011 */ PTR(240, 2), /* 0100 */ V(8, 1, 4), /* 0101 */ PTR(244, 1), /* 0110 */ PTR(246, 1), /* 0111 */ PTR(248, 1), /* 1000 */ PTR(250, 2), /* 1001 */ PTR(254, 1), /* 1010 */ V(1, 5, 4), /* 1011 */ V(5, 1, 4), /* 1100 */ PTR(256, 1), /* 1101 */ PTR(258, 1), /* 1110 */ PTR(260, 1), /* 1111 */ V(1, 4, 4), /* 0010 ... */ /* 0000 */ V(4, 1, 3), /* 48 */ /* 0001 */ V(4, 1, 3), /* 0010 */ V(0, 4, 4), /* 0011 */ V(4, 0, 4), /* 0100 */ V(2, 3, 4), /* 0101 */ V(3, 2, 4), /* 0110 */ V(1, 3, 3), /* 0111 */ V(1, 3, 3), /* 1000 */ V(3, 1, 3), /* 1001 */ V(3, 1, 3), /* 1010 */ V(0, 3, 3), /* 1011 */ V(0, 3, 3), /* 1100 */ V(3, 0, 3), /* 1101 */ V(3, 0, 3), /* 1110 */ V(2, 2, 3), /* 1111 */ V(2, 2, 3), /* 0011 ... */ /* 00 */ V(1, 2, 2), /* 64 */ /* 01 */ V(2, 1, 2), /* 10 */ V(0, 2, 2), /* 11 */ V(2, 0, 2), /* 0000 0000 ... */ /* 0000 */ PTR(262, 4), /* 68 */ /* 0001 */ PTR(278, 4), /* 0010 */ PTR(294, 4), /* 0011 */ PTR(310, 3), /* 0100 */ PTR(318, 2), /* 0101 */ PTR(322, 2), /* 0110 */ PTR(326, 3), /* 0111 */ PTR(334, 2), /* 1000 */ PTR(338, 1), /* 1001 */ PTR(340, 2), /* 1010 */ PTR(344, 2), /* 1011 */ PTR(348, 2), /* 1100 */ PTR(352, 2), /* 1101 */ PTR(356, 2), /* 1110 */ V(1, 15, 4), /* 1111 */ V(15, 1, 4), /* 0000 0001 ... */ /* 0000 */ V(15, 0, 4), /* 84 */ /* 0001 */ PTR(360, 1), /* 0010 */ PTR(362, 1), /* 0011 */ PTR(364, 1), /* 0100 */ V(14, 2, 4), /* 0101 */ PTR(366, 1), /* 0110 */ V(1, 14, 4), /* 0111 */ V(14, 1, 4), /* 1000 */ PTR(368, 1), /* 1001 */ PTR(370, 1), /* 1010 */ PTR(372, 1), /* 1011 */ PTR(374, 1), /* 1100 */ PTR(376, 1), /* 1101 */ PTR(378, 1), /* 1110 */ V(12, 6, 4), /* 1111 */ V(3, 13, 4), /* 0000 0010 ... */ /* 0000 */ PTR(380, 1), /* 100 */ /* 0001 */ V(2, 13, 4), /* 0010 */ V(13, 2, 4), /* 0011 */ V(1, 13, 4), /* 0100 */ V(11, 7, 4), /* 0101 */ PTR(382, 1), /* 0110 */ PTR(384, 1), /* 0111 */ V(12, 3, 4), /* 1000 */ PTR(386, 1), /* 1001 */ V(4, 11, 4), /* 1010 */ V(13, 1, 3), /* 1011 */ V(13, 1, 3), /* 1100 */ V(0, 13, 4), /* 1101 */ V(13, 0, 4), /* 1110 */ V(8, 10, 4), /* 1111 */ V(10, 8, 4), /* 0000 0011 ... */ /* 0000 */ V(4, 12, 4), /* 116 */ /* 0001 */ V(12, 4, 4), /* 0010 */ V(6, 11, 4), /* 0011 */ V(11, 6, 4), /* 0100 */ V(3, 12, 3), /* 0101 */ V(3, 12, 3), /* 0110 */ V(2, 12, 3), /* 0111 */ V(2, 12, 3), /* 1000 */ V(12, 2, 3), /* 1001 */ V(12, 2, 3), /* 1010 */ V(5, 11, 3), /* 1011 */ V(5, 11, 3), /* 1100 */ V(11, 5, 4), /* 1101 */ V(8, 9, 4), /* 1110 */ V(1, 12, 3), /* 1111 */ V(1, 12, 3), /* 0000 0100 ... */ /* 0000 */ V(12, 1, 3), /* 132 */ /* 0001 */ V(12, 1, 3), /* 0010 */ V(9, 8, 4), /* 0011 */ V(0, 12, 4), /* 0100 */ V(12, 0, 3), /* 0101 */ V(12, 0, 3), /* 0110 */ V(11, 4, 4), /* 0111 */ V(6, 10, 4), /* 1000 */ V(10, 6, 4), /* 1001 */ V(7, 9, 4), /* 1010 */ V(3, 11, 3), /* 1011 */ V(3, 11, 3), /* 1100 */ V(11, 3, 3), /* 1101 */ V(11, 3, 3), /* 1110 */ V(8, 8, 4), /* 1111 */ V(5, 10, 4), /* 0000 0101 ... */ /* 0000 */ V(2, 11, 3), /* 148 */ /* 0001 */ V(2, 11, 3), /* 0010 */ V(10, 5, 4), /* 0011 */ V(6, 9, 4), /* 0100 */ V(10, 4, 3), /* 0101 */ V(10, 4, 3), /* 0110 */ V(7, 8, 4), /* 0111 */ V(8, 7, 4), /* 1000 */ V(9, 4, 3), /* 1001 */ V(9, 4, 3), /* 1010 */ V(7, 7, 4), /* 1011 */ V(7, 6, 4), /* 1100 */ V(11, 2, 2), /* 1101 */ V(11, 2, 2), /* 1110 */ V(11, 2, 2), /* 1111 */ V(11, 2, 2), /* 0000 0110 ... */ /* 000 */ V(1, 11, 2), /* 164 */ /* 001 */ V(1, 11, 2), /* 010 */ V(11, 1, 2), /* 011 */ V(11, 1, 2), /* 100 */ V(0, 11, 3), /* 101 */ V(11, 0, 3), /* 110 */ V(9, 6, 3), /* 111 */ V(4, 10, 3), /* 0000 0111 ... */ /* 000 */ V(3, 10, 3), /* 172 */ /* 001 */ V(10, 3, 3), /* 010 */ V(5, 9, 3), /* 011 */ V(9, 5, 3), /* 100 */ V(2, 10, 2), /* 101 */ V(2, 10, 2), /* 110 */ V(10, 2, 2), /* 111 */ V(10, 2, 2), /* 0000 1000 ... */ /* 000 */ V(1, 10, 2), /* 180 */ /* 001 */ V(1, 10, 2), /* 010 */ V(10, 1, 2), /* 011 */ V(10, 1, 2), /* 100 */ V(0, 10, 3), /* 101 */ V(6, 8, 3), /* 110 */ V(10, 0, 2), /* 111 */ V(10, 0, 2), /* 0000 1001 ... */ /* 000 */ V(8, 6, 3), /* 188 */ /* 001 */ V(4, 9, 3), /* 010 */ V(9, 3, 2), /* 011 */ V(9, 3, 2), /* 100 */ V(3, 9, 3), /* 101 */ V(5, 8, 3), /* 110 */ V(8, 5, 3), /* 111 */ V(6, 7, 3), /* 0000 1010 ... */ /* 000 */ V(2, 9, 2), /* 196 */ /* 001 */ V(2, 9, 2), /* 010 */ V(9, 2, 2), /* 011 */ V(9, 2, 2), /* 100 */ V(5, 7, 3), /* 101 */ V(7, 5, 3), /* 110 */ V(3, 8, 2), /* 111 */ V(3, 8, 2), /* 0000 1011 ... */ /* 000 */ V(8, 3, 2), /* 204 */ /* 001 */ V(8, 3, 2), /* 010 */ V(6, 6, 3), /* 011 */ V(4, 7, 3), /* 100 */ V(7, 4, 3), /* 101 */ V(5, 6, 3), /* 110 */ V(6, 5, 3), /* 111 */ V(7, 3, 3), /* 0000 1100 ... */ /* 0 */ V(1, 9, 1), /* 212 */ /* 1 */ V(9, 1, 1), /* 0000 1101 ... */ /* 00 */ V(0, 9, 2), /* 214 */ /* 01 */ V(9, 0, 2), /* 10 */ V(4, 8, 2), /* 11 */ V(8, 4, 2), /* 0000 1110 ... */ /* 000 */ V(7, 2, 2), /* 218 */ /* 001 */ V(7, 2, 2), /* 010 */ V(4, 6, 3), /* 011 */ V(6, 4, 3), /* 100 */ V(2, 8, 1), /* 101 */ V(2, 8, 1), /* 110 */ V(2, 8, 1), /* 111 */ V(2, 8, 1), /* 0000 1111 ... */ /* 0 */ V(8, 2, 1), /* 226 */ /* 1 */ V(1, 8, 1), /* 0001 0000 ... */ /* 00 */ V(3, 7, 2), /* 228 */ /* 01 */ V(2, 7, 2), /* 10 */ V(1, 7, 1), /* 11 */ V(1, 7, 1), /* 0001 0001 ... */ /* 00 */ V(7, 1, 1), /* 232 */ /* 01 */ V(7, 1, 1), /* 10 */ V(5, 5, 2), /* 11 */ V(0, 7, 2), /* 0001 0010 ... */ /* 00 */ V(7, 0, 2), /* 236 */ /* 01 */ V(3, 6, 2), /* 10 */ V(6, 3, 2), /* 11 */ V(4, 5, 2), /* 0001 0011 ... */ /* 00 */ V(5, 4, 2), /* 240 */ /* 01 */ V(2, 6, 2), /* 10 */ V(6, 2, 2), /* 11 */ V(3, 5, 2), /* 0001 0101 ... */ /* 0 */ V(0, 8, 1), /* 244 */ /* 1 */ V(8, 0, 1), /* 0001 0110 ... */ /* 0 */ V(1, 6, 1), /* 246 */ /* 1 */ V(6, 1, 1), /* 0001 0111 ... */ /* 0 */ V(0, 6, 1), /* 248 */ /* 1 */ V(6, 0, 1), /* 0001 1000 ... */ /* 00 */ V(5, 3, 2), /* 250 */ /* 01 */ V(4, 4, 2), /* 10 */ V(2, 5, 1), /* 11 */ V(2, 5, 1), /* 0001 1001 ... */ /* 0 */ V(5, 2, 1), /* 254 */ /* 1 */ V(0, 5, 1), /* 0001 1100 ... */ /* 0 */ V(3, 4, 1), /* 256 */ /* 1 */ V(4, 3, 1), /* 0001 1101 ... */ /* 0 */ V(5, 0, 1), /* 258 */ /* 1 */ V(2, 4, 1), /* 0001 1110 ... */ /* 0 */ V(4, 2, 1), /* 260 */ /* 1 */ V(3, 3, 1), /* 0000 0000 0000 ... */ /* 0000 */ PTR(388, 3), /* 262 */ /* 0001 */ V(15, 15, 4), /* 0010 */ V(14, 15, 4), /* 0011 */ V(13, 15, 4), /* 0100 */ V(14, 14, 4), /* 0101 */ V(12, 15, 4), /* 0110 */ V(13, 14, 4), /* 0111 */ V(11, 15, 4), /* 1000 */ V(15, 11, 4), /* 1001 */ V(12, 14, 4), /* 1010 */ V(13, 12, 4), /* 1011 */ PTR(396, 1), /* 1100 */ V(14, 12, 3), /* 1101 */ V(14, 12, 3), /* 1110 */ V(13, 13, 3), /* 1111 */ V(13, 13, 3), /* 0000 0000 0001 ... */ /* 0000 */ V(15, 10, 4), /* 278 */ /* 0001 */ V(12, 13, 4), /* 0010 */ V(11, 14, 3), /* 0011 */ V(11, 14, 3), /* 0100 */ V(14, 11, 3), /* 0101 */ V(14, 11, 3), /* 0110 */ V(9, 15, 3), /* 0111 */ V(9, 15, 3), /* 1000 */ V(15, 9, 3), /* 1001 */ V(15, 9, 3), /* 1010 */ V(14, 10, 3), /* 1011 */ V(14, 10, 3), /* 1100 */ V(11, 13, 3), /* 1101 */ V(11, 13, 3), /* 1110 */ V(13, 11, 3), /* 1111 */ V(13, 11, 3), /* 0000 0000 0010 ... */ /* 0000 */ V(8, 15, 3), /* 294 */ /* 0001 */ V(8, 15, 3), /* 0010 */ V(15, 8, 3), /* 0011 */ V(15, 8, 3), /* 0100 */ V(12, 12, 3), /* 0101 */ V(12, 12, 3), /* 0110 */ V(10, 14, 4), /* 0111 */ V(9, 14, 4), /* 1000 */ V(8, 14, 3), /* 1001 */ V(8, 14, 3), /* 1010 */ V(7, 15, 4), /* 1011 */ V(7, 14, 4), /* 1100 */ V(15, 7, 2), /* 1101 */ V(15, 7, 2), /* 1110 */ V(15, 7, 2), /* 1111 */ V(15, 7, 2), /* 0000 0000 0011 ... */ /* 000 */ V(13, 10, 2), /* 310 */ /* 001 */ V(13, 10, 2), /* 010 */ V(10, 13, 3), /* 011 */ V(11, 12, 3), /* 100 */ V(12, 11, 3), /* 101 */ V(15, 6, 3), /* 110 */ V(6, 15, 2), /* 111 */ V(6, 15, 2), /* 0000 0000 0100 ... */ /* 00 */ V(14, 8, 2), /* 318 */ /* 01 */ V(5, 15, 2), /* 10 */ V(9, 13, 2), /* 11 */ V(13, 9, 2), /* 0000 0000 0101 ... */ /* 00 */ V(15, 5, 2), /* 322 */ /* 01 */ V(14, 7, 2), /* 10 */ V(10, 12, 2), /* 11 */ V(11, 11, 2), /* 0000 0000 0110 ... */ /* 000 */ V(4, 15, 2), /* 326 */ /* 001 */ V(4, 15, 2), /* 010 */ V(15, 4, 2), /* 011 */ V(15, 4, 2), /* 100 */ V(12, 10, 3), /* 101 */ V(14, 6, 3), /* 110 */ V(15, 3, 2), /* 111 */ V(15, 3, 2), /* 0000 0000 0111 ... */ /* 00 */ V(3, 15, 1), /* 334 */ /* 01 */ V(3, 15, 1), /* 10 */ V(8, 13, 2), /* 11 */ V(13, 8, 2), /* 0000 0000 1000 ... */ /* 0 */ V(2, 15, 1), /* 338 */ /* 1 */ V(15, 2, 1), /* 0000 0000 1001 ... */ /* 00 */ V(6, 14, 2), /* 340 */ /* 01 */ V(9, 12, 2), /* 10 */ V(0, 15, 1), /* 11 */ V(0, 15, 1), /* 0000 0000 1010 ... */ /* 00 */ V(12, 9, 2), /* 344 */ /* 01 */ V(5, 14, 2), /* 10 */ V(10, 11, 1), /* 11 */ V(10, 11, 1), /* 0000 0000 1011 ... */ /* 00 */ V(7, 13, 2), /* 348 */ /* 01 */ V(13, 7, 2), /* 10 */ V(4, 14, 1), /* 11 */ V(4, 14, 1), /* 0000 0000 1100 ... */ /* 00 */ V(12, 8, 2), /* 352 */ /* 01 */ V(13, 6, 2), /* 10 */ V(3, 14, 1), /* 11 */ V(3, 14, 1), /* 0000 0000 1101 ... */ /* 00 */ V(11, 9, 1), /* 356 */ /* 01 */ V(11, 9, 1), /* 10 */ V(9, 11, 2), /* 11 */ V(10, 10, 2), /* 0000 0001 0001 ... */ /* 0 */ V(11, 10, 1), /* 360 */ /* 1 */ V(14, 5, 1), /* 0000 0001 0010 ... */ /* 0 */ V(14, 4, 1), /* 362 */ /* 1 */ V(8, 12, 1), /* 0000 0001 0011 ... */ /* 0 */ V(6, 13, 1), /* 364 */ /* 1 */ V(14, 3, 1), /* 0000 0001 0101 ... */ /* 0 */ V(2, 14, 1), /* 366 */ /* 1 */ V(0, 14, 1), /* 0000 0001 1000 ... */ /* 0 */ V(14, 0, 1), /* 368 */ /* 1 */ V(5, 13, 1), /* 0000 0001 1001 ... */ /* 0 */ V(13, 5, 1), /* 370 */ /* 1 */ V(7, 12, 1), /* 0000 0001 1010 ... */ /* 0 */ V(12, 7, 1), /* 372 */ /* 1 */ V(4, 13, 1), /* 0000 0001 1011 ... */ /* 0 */ V(8, 11, 1), /* 374 */ /* 1 */ V(11, 8, 1), /* 0000 0001 1100 ... */ /* 0 */ V(13, 4, 1), /* 376 */ /* 1 */ V(9, 10, 1), /* 0000 0001 1101 ... */ /* 0 */ V(10, 9, 1), /* 378 */ /* 1 */ V(6, 12, 1), /* 0000 0010 0000 ... */ /* 0 */ V(13, 3, 1), /* 380 */ /* 1 */ V(7, 11, 1), /* 0000 0010 0101 ... */ /* 0 */ V(5, 12, 1), /* 382 */ /* 1 */ V(12, 5, 1), /* 0000 0010 0110 ... */ /* 0 */ V(9, 9, 1), /* 384 */ /* 1 */ V(7, 10, 1), /* 0000 0010 1000 ... */ /* 0 */ V(10, 7, 1), /* 386 */ /* 1 */ V(9, 7, 1), /* 0000 0000 0000 0000 ... */ /* 000 */ V(15, 14, 3), /* 388 */ /* 001 */ V(15, 12, 3), /* 010 */ V(15, 13, 2), /* 011 */ V(15, 13, 2), /* 100 */ V(14, 13, 1), /* 101 */ V(14, 13, 1), /* 110 */ V(14, 13, 1), /* 111 */ V(14, 13, 1), /* 0000 0000 0000 1011 ... */ /* 0 */ V(10, 15, 1), /* 396 */ /* 1 */ V(14, 9, 1) }; static union huffpair const hufftab15[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 4), /* 0010 */ PTR(48, 4), /* 0011 */ PTR(64, 4), /* 0100 */ PTR(80, 4), /* 0101 */ PTR(96, 3), /* 0110 */ PTR(104, 3), /* 0111 */ PTR(112, 2), /* 1000 */ PTR(116, 1), /* 1001 */ PTR(118, 1), /* 1010 */ V(1, 1, 3), /* 1011 */ V(1, 1, 3), /* 1100 */ V(0, 1, 4), /* 1101 */ V(1, 0, 4), /* 1110 */ V(0, 0, 3), /* 1111 */ V(0, 0, 3), /* 0000 ... */ /* 0000 */ PTR(120, 4), /* 16 */ /* 0001 */ PTR(136, 4), /* 0010 */ PTR(152, 4), /* 0011 */ PTR(168, 4), /* 0100 */ PTR(184, 4), /* 0101 */ PTR(200, 3), /* 0110 */ PTR(208, 3), /* 0111 */ PTR(216, 4), /* 1000 */ PTR(232, 3), /* 1001 */ PTR(240, 3), /* 1010 */ PTR(248, 3), /* 1011 */ PTR(256, 3), /* 1100 */ PTR(264, 2), /* 1101 */ PTR(268, 3), /* 1110 */ PTR(276, 3), /* 1111 */ PTR(284, 2), /* 0001 ... */ /* 0000 */ PTR(288, 2), /* 32 */ /* 0001 */ PTR(292, 2), /* 0010 */ PTR(296, 2), /* 0011 */ PTR(300, 2), /* 0100 */ PTR(304, 2), /* 0101 */ PTR(308, 2), /* 0110 */ PTR(312, 2), /* 0111 */ PTR(316, 2), /* 1000 */ PTR(320, 1), /* 1001 */ PTR(322, 1), /* 1010 */ PTR(324, 1), /* 1011 */ PTR(326, 2), /* 1100 */ PTR(330, 1), /* 1101 */ PTR(332, 1), /* 1110 */ PTR(334, 2), /* 1111 */ PTR(338, 1), /* 0010 ... */ /* 0000 */ PTR(340, 1), /* 48 */ /* 0001 */ PTR(342, 1), /* 0010 */ V(9, 1, 4), /* 0011 */ PTR(344, 1), /* 0100 */ PTR(346, 1), /* 0101 */ PTR(348, 1), /* 0110 */ PTR(350, 1), /* 0111 */ PTR(352, 1), /* 1000 */ V(2, 8, 4), /* 1001 */ V(8, 2, 4), /* 1010 */ V(1, 8, 4), /* 1011 */ V(8, 1, 4), /* 1100 */ PTR(354, 1), /* 1101 */ PTR(356, 1), /* 1110 */ PTR(358, 1), /* 1111 */ PTR(360, 1), /* 0011 ... */ /* 0000 */ V(2, 7, 4), /* 64 */ /* 0001 */ V(7, 2, 4), /* 0010 */ V(6, 4, 4), /* 0011 */ V(1, 7, 4), /* 0100 */ V(5, 5, 4), /* 0101 */ V(7, 1, 4), /* 0110 */ PTR(362, 1), /* 0111 */ V(3, 6, 4), /* 1000 */ V(6, 3, 4), /* 1001 */ V(4, 5, 4), /* 1010 */ V(5, 4, 4), /* 1011 */ V(2, 6, 4), /* 1100 */ V(6, 2, 4), /* 1101 */ V(1, 6, 4), /* 1110 */ PTR(364, 1), /* 1111 */ V(3, 5, 4), /* 0100 ... */ /* 0000 */ V(6, 1, 3), /* 80 */ /* 0001 */ V(6, 1, 3), /* 0010 */ V(5, 3, 4), /* 0011 */ V(4, 4, 4), /* 0100 */ V(2, 5, 3), /* 0101 */ V(2, 5, 3), /* 0110 */ V(5, 2, 3), /* 0111 */ V(5, 2, 3), /* 1000 */ V(1, 5, 3), /* 1001 */ V(1, 5, 3), /* 1010 */ V(5, 1, 3), /* 1011 */ V(5, 1, 3), /* 1100 */ V(0, 5, 4), /* 1101 */ V(5, 0, 4), /* 1110 */ V(3, 4, 3), /* 1111 */ V(3, 4, 3), /* 0101 ... */ /* 000 */ V(4, 3, 3), /* 96 */ /* 001 */ V(2, 4, 3), /* 010 */ V(4, 2, 3), /* 011 */ V(3, 3, 3), /* 100 */ V(4, 1, 2), /* 101 */ V(4, 1, 2), /* 110 */ V(1, 4, 3), /* 111 */ V(0, 4, 3), /* 0110 ... */ /* 000 */ V(2, 3, 2), /* 104 */ /* 001 */ V(2, 3, 2), /* 010 */ V(3, 2, 2), /* 011 */ V(3, 2, 2), /* 100 */ V(4, 0, 3), /* 101 */ V(0, 3, 3), /* 110 */ V(1, 3, 2), /* 111 */ V(1, 3, 2), /* 0111 ... */ /* 00 */ V(3, 1, 2), /* 112 */ /* 01 */ V(3, 0, 2), /* 10 */ V(2, 2, 1), /* 11 */ V(2, 2, 1), /* 1000 ... */ /* 0 */ V(1, 2, 1), /* 116 */ /* 1 */ V(2, 1, 1), /* 1001 ... */ /* 0 */ V(0, 2, 1), /* 118 */ /* 1 */ V(2, 0, 1), /* 0000 0000 ... */ /* 0000 */ PTR(366, 1), /* 120 */ /* 0001 */ PTR(368, 1), /* 0010 */ V(14, 14, 4), /* 0011 */ PTR(370, 1), /* 0100 */ PTR(372, 1), /* 0101 */ PTR(374, 1), /* 0110 */ V(15, 11, 4), /* 0111 */ PTR(376, 1), /* 1000 */ V(13, 13, 4), /* 1001 */ V(10, 15, 4), /* 1010 */ V(15, 10, 4), /* 1011 */ V(11, 14, 4), /* 1100 */ V(14, 11, 4), /* 1101 */ V(12, 13, 4), /* 1110 */ V(13, 12, 4), /* 1111 */ V(9, 15, 4), /* 0000 0001 ... */ /* 0000 */ V(15, 9, 4), /* 136 */ /* 0001 */ V(14, 10, 4), /* 0010 */ V(11, 13, 4), /* 0011 */ V(13, 11, 4), /* 0100 */ V(8, 15, 4), /* 0101 */ V(15, 8, 4), /* 0110 */ V(12, 12, 4), /* 0111 */ V(9, 14, 4), /* 1000 */ V(14, 9, 4), /* 1001 */ V(7, 15, 4), /* 1010 */ V(15, 7, 4), /* 1011 */ V(10, 13, 4), /* 1100 */ V(13, 10, 4), /* 1101 */ V(11, 12, 4), /* 1110 */ V(6, 15, 4), /* 1111 */ PTR(378, 1), /* 0000 0010 ... */ /* 0000 */ V(12, 11, 3), /* 152 */ /* 0001 */ V(12, 11, 3), /* 0010 */ V(15, 6, 3), /* 0011 */ V(15, 6, 3), /* 0100 */ V(8, 14, 4), /* 0101 */ V(14, 8, 4), /* 0110 */ V(5, 15, 4), /* 0111 */ V(9, 13, 4), /* 1000 */ V(15, 5, 3), /* 1001 */ V(15, 5, 3), /* 1010 */ V(7, 14, 3), /* 1011 */ V(7, 14, 3), /* 1100 */ V(14, 7, 3), /* 1101 */ V(14, 7, 3), /* 1110 */ V(10, 12, 3), /* 1111 */ V(10, 12, 3), /* 0000 0011 ... */ /* 0000 */ V(12, 10, 3), /* 168 */ /* 0001 */ V(12, 10, 3), /* 0010 */ V(11, 11, 3), /* 0011 */ V(11, 11, 3), /* 0100 */ V(13, 9, 4), /* 0101 */ V(8, 13, 4), /* 0110 */ V(4, 15, 3), /* 0111 */ V(4, 15, 3), /* 1000 */ V(15, 4, 3), /* 1001 */ V(15, 4, 3), /* 1010 */ V(3, 15, 3), /* 1011 */ V(3, 15, 3), /* 1100 */ V(15, 3, 3), /* 1101 */ V(15, 3, 3), /* 1110 */ V(13, 8, 3), /* 1111 */ V(13, 8, 3), /* 0000 0100 ... */ /* 0000 */ V(14, 6, 3), /* 184 */ /* 0001 */ V(14, 6, 3), /* 0010 */ V(2, 15, 3), /* 0011 */ V(2, 15, 3), /* 0100 */ V(15, 2, 3), /* 0101 */ V(15, 2, 3), /* 0110 */ V(6, 14, 4), /* 0111 */ V(15, 0, 4), /* 1000 */ V(1, 15, 3), /* 1001 */ V(1, 15, 3), /* 1010 */ V(15, 1, 3), /* 1011 */ V(15, 1, 3), /* 1100 */ V(9, 12, 3), /* 1101 */ V(9, 12, 3), /* 1110 */ V(12, 9, 3), /* 1111 */ V(12, 9, 3), /* 0000 0101 ... */ /* 000 */ V(5, 14, 3), /* 200 */ /* 001 */ V(10, 11, 3), /* 010 */ V(11, 10, 3), /* 011 */ V(14, 5, 3), /* 100 */ V(7, 13, 3), /* 101 */ V(13, 7, 3), /* 110 */ V(4, 14, 3), /* 111 */ V(14, 4, 3), /* 0000 0110 ... */ /* 000 */ V(8, 12, 3), /* 208 */ /* 001 */ V(12, 8, 3), /* 010 */ V(3, 14, 3), /* 011 */ V(6, 13, 3), /* 100 */ V(13, 6, 3), /* 101 */ V(14, 3, 3), /* 110 */ V(9, 11, 3), /* 111 */ V(11, 9, 3), /* 0000 0111 ... */ /* 0000 */ V(2, 14, 3), /* 216 */ /* 0001 */ V(2, 14, 3), /* 0010 */ V(10, 10, 3), /* 0011 */ V(10, 10, 3), /* 0100 */ V(14, 2, 3), /* 0101 */ V(14, 2, 3), /* 0110 */ V(1, 14, 3), /* 0111 */ V(1, 14, 3), /* 1000 */ V(14, 1, 3), /* 1001 */ V(14, 1, 3), /* 1010 */ V(0, 14, 4), /* 1011 */ V(14, 0, 4), /* 1100 */ V(5, 13, 3), /* 1101 */ V(5, 13, 3), /* 1110 */ V(13, 5, 3), /* 1111 */ V(13, 5, 3), /* 0000 1000 ... */ /* 000 */ V(7, 12, 3), /* 232 */ /* 001 */ V(12, 7, 3), /* 010 */ V(4, 13, 3), /* 011 */ V(8, 11, 3), /* 100 */ V(13, 4, 2), /* 101 */ V(13, 4, 2), /* 110 */ V(11, 8, 3), /* 111 */ V(9, 10, 3), /* 0000 1001 ... */ /* 000 */ V(10, 9, 3), /* 240 */ /* 001 */ V(6, 12, 3), /* 010 */ V(12, 6, 3), /* 011 */ V(3, 13, 3), /* 100 */ V(13, 3, 2), /* 101 */ V(13, 3, 2), /* 110 */ V(13, 2, 2), /* 111 */ V(13, 2, 2), /* 0000 1010 ... */ /* 000 */ V(2, 13, 3), /* 248 */ /* 001 */ V(0, 13, 3), /* 010 */ V(1, 13, 2), /* 011 */ V(1, 13, 2), /* 100 */ V(7, 11, 2), /* 101 */ V(7, 11, 2), /* 110 */ V(11, 7, 2), /* 111 */ V(11, 7, 2), /* 0000 1011 ... */ /* 000 */ V(13, 1, 2), /* 256 */ /* 001 */ V(13, 1, 2), /* 010 */ V(5, 12, 3), /* 011 */ V(13, 0, 3), /* 100 */ V(12, 5, 2), /* 101 */ V(12, 5, 2), /* 110 */ V(8, 10, 2), /* 111 */ V(8, 10, 2), /* 0000 1100 ... */ /* 00 */ V(10, 8, 2), /* 264 */ /* 01 */ V(4, 12, 2), /* 10 */ V(12, 4, 2), /* 11 */ V(6, 11, 2), /* 0000 1101 ... */ /* 000 */ V(11, 6, 2), /* 268 */ /* 001 */ V(11, 6, 2), /* 010 */ V(9, 9, 3), /* 011 */ V(0, 12, 3), /* 100 */ V(3, 12, 2), /* 101 */ V(3, 12, 2), /* 110 */ V(12, 3, 2), /* 111 */ V(12, 3, 2), /* 0000 1110 ... */ /* 000 */ V(7, 10, 2), /* 276 */ /* 001 */ V(7, 10, 2), /* 010 */ V(10, 7, 2), /* 011 */ V(10, 7, 2), /* 100 */ V(10, 6, 2), /* 101 */ V(10, 6, 2), /* 110 */ V(12, 0, 3), /* 111 */ V(0, 11, 3), /* 0000 1111 ... */ /* 00 */ V(12, 2, 1), /* 284 */ /* 01 */ V(12, 2, 1), /* 10 */ V(2, 12, 2), /* 11 */ V(5, 11, 2), /* 0001 0000 ... */ /* 00 */ V(11, 5, 2), /* 288 */ /* 01 */ V(1, 12, 2), /* 10 */ V(8, 9, 2), /* 11 */ V(9, 8, 2), /* 0001 0001 ... */ /* 00 */ V(12, 1, 2), /* 292 */ /* 01 */ V(4, 11, 2), /* 10 */ V(11, 4, 2), /* 11 */ V(6, 10, 2), /* 0001 0010 ... */ /* 00 */ V(3, 11, 2), /* 296 */ /* 01 */ V(7, 9, 2), /* 10 */ V(11, 3, 1), /* 11 */ V(11, 3, 1), /* 0001 0011 ... */ /* 00 */ V(9, 7, 2), /* 300 */ /* 01 */ V(8, 8, 2), /* 10 */ V(2, 11, 2), /* 11 */ V(5, 10, 2), /* 0001 0100 ... */ /* 00 */ V(11, 2, 1), /* 304 */ /* 01 */ V(11, 2, 1), /* 10 */ V(10, 5, 2), /* 11 */ V(1, 11, 2), /* 0001 0101 ... */ /* 00 */ V(11, 1, 1), /* 308 */ /* 01 */ V(11, 1, 1), /* 10 */ V(11, 0, 2), /* 11 */ V(6, 9, 2), /* 0001 0110 ... */ /* 00 */ V(9, 6, 2), /* 312 */ /* 01 */ V(4, 10, 2), /* 10 */ V(10, 4, 2), /* 11 */ V(7, 8, 2), /* 0001 0111 ... */ /* 00 */ V(8, 7, 2), /* 316 */ /* 01 */ V(3, 10, 2), /* 10 */ V(10, 3, 1), /* 11 */ V(10, 3, 1), /* 0001 1000 ... */ /* 0 */ V(5, 9, 1), /* 320 */ /* 1 */ V(9, 5, 1), /* 0001 1001 ... */ /* 0 */ V(2, 10, 1), /* 322 */ /* 1 */ V(10, 2, 1), /* 0001 1010 ... */ /* 0 */ V(1, 10, 1), /* 324 */ /* 1 */ V(10, 1, 1), /* 0001 1011 ... */ /* 00 */ V(0, 10, 2), /* 326 */ /* 01 */ V(10, 0, 2), /* 10 */ V(6, 8, 1), /* 11 */ V(6, 8, 1), /* 0001 1100 ... */ /* 0 */ V(8, 6, 1), /* 330 */ /* 1 */ V(4, 9, 1), /* 0001 1101 ... */ /* 0 */ V(9, 4, 1), /* 332 */ /* 1 */ V(3, 9, 1), /* 0001 1110 ... */ /* 00 */ V(9, 3, 1), /* 334 */ /* 01 */ V(9, 3, 1), /* 10 */ V(7, 7, 2), /* 11 */ V(0, 9, 2), /* 0001 1111 ... */ /* 0 */ V(5, 8, 1), /* 338 */ /* 1 */ V(8, 5, 1), /* 0010 0000 ... */ /* 0 */ V(2, 9, 1), /* 340 */ /* 1 */ V(6, 7, 1), /* 0010 0001 ... */ /* 0 */ V(7, 6, 1), /* 342 */ /* 1 */ V(9, 2, 1), /* 0010 0011 ... */ /* 0 */ V(1, 9, 1), /* 344 */ /* 1 */ V(9, 0, 1), /* 0010 0100 ... */ /* 0 */ V(4, 8, 1), /* 346 */ /* 1 */ V(8, 4, 1), /* 0010 0101 ... */ /* 0 */ V(5, 7, 1), /* 348 */ /* 1 */ V(7, 5, 1), /* 0010 0110 ... */ /* 0 */ V(3, 8, 1), /* 350 */ /* 1 */ V(8, 3, 1), /* 0010 0111 ... */ /* 0 */ V(6, 6, 1), /* 352 */ /* 1 */ V(4, 7, 1), /* 0010 1100 ... */ /* 0 */ V(7, 4, 1), /* 354 */ /* 1 */ V(0, 8, 1), /* 0010 1101 ... */ /* 0 */ V(8, 0, 1), /* 356 */ /* 1 */ V(5, 6, 1), /* 0010 1110 ... */ /* 0 */ V(6, 5, 1), /* 358 */ /* 1 */ V(3, 7, 1), /* 0010 1111 ... */ /* 0 */ V(7, 3, 1), /* 360 */ /* 1 */ V(4, 6, 1), /* 0011 0110 ... */ /* 0 */ V(0, 7, 1), /* 362 */ /* 1 */ V(7, 0, 1), /* 0011 1110 ... */ /* 0 */ V(0, 6, 1), /* 364 */ /* 1 */ V(6, 0, 1), /* 0000 0000 0000 ... */ /* 0 */ V(15, 15, 1), /* 366 */ /* 1 */ V(14, 15, 1), /* 0000 0000 0001 ... */ /* 0 */ V(15, 14, 1), /* 368 */ /* 1 */ V(13, 15, 1), /* 0000 0000 0011 ... */ /* 0 */ V(15, 13, 1), /* 370 */ /* 1 */ V(12, 15, 1), /* 0000 0000 0100 ... */ /* 0 */ V(15, 12, 1), /* 372 */ /* 1 */ V(13, 14, 1), /* 0000 0000 0101 ... */ /* 0 */ V(14, 13, 1), /* 374 */ /* 1 */ V(11, 15, 1), /* 0000 0000 0111 ... */ /* 0 */ V(12, 14, 1), /* 376 */ /* 1 */ V(14, 12, 1), /* 0000 0001 1111 ... */ /* 0 */ V(10, 14, 1), /* 378 */ /* 1 */ V(0, 15, 1) }; static union huffpair const hufftab16[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 4), /* 0010 */ PTR(48, 4), /* 0011 */ PTR(64, 2), /* 0100 */ V(1, 1, 4), /* 0101 */ V(0, 1, 4), /* 0110 */ V(1, 0, 3), /* 0111 */ V(1, 0, 3), /* 1000 */ V(0, 0, 1), /* 1001 */ V(0, 0, 1), /* 1010 */ V(0, 0, 1), /* 1011 */ V(0, 0, 1), /* 1100 */ V(0, 0, 1), /* 1101 */ V(0, 0, 1), /* 1110 */ V(0, 0, 1), /* 1111 */ V(0, 0, 1), /* 0000 ... */ /* 0000 */ PTR(68, 3), /* 16 */ /* 0001 */ PTR(76, 3), /* 0010 */ PTR(84, 2), /* 0011 */ V(15, 15, 4), /* 0100 */ PTR(88, 2), /* 0101 */ PTR(92, 1), /* 0110 */ PTR(94, 4), /* 0111 */ V(15, 2, 4), /* 1000 */ PTR(110, 1), /* 1001 */ V(1, 15, 4), /* 1010 */ V(15, 1, 4), /* 1011 */ PTR(112, 4), /* 1100 */ PTR(128, 4), /* 1101 */ PTR(144, 4), /* 1110 */ PTR(160, 4), /* 1111 */ PTR(176, 4), /* 0001 ... */ /* 0000 */ PTR(192, 4), /* 32 */ /* 0001 */ PTR(208, 3), /* 0010 */ PTR(216, 3), /* 0011 */ PTR(224, 3), /* 0100 */ PTR(232, 3), /* 0101 */ PTR(240, 3), /* 0110 */ PTR(248, 3), /* 0111 */ PTR(256, 3), /* 1000 */ PTR(264, 2), /* 1001 */ PTR(268, 2), /* 1010 */ PTR(272, 1), /* 1011 */ PTR(274, 2), /* 1100 */ PTR(278, 2), /* 1101 */ PTR(282, 1), /* 1110 */ V(5, 1, 4), /* 1111 */ PTR(284, 1), /* 0010 ... */ /* 0000 */ PTR(286, 1), /* 48 */ /* 0001 */ PTR(288, 1), /* 0010 */ PTR(290, 1), /* 0011 */ V(1, 4, 4), /* 0100 */ V(4, 1, 4), /* 0101 */ PTR(292, 1), /* 0110 */ V(2, 3, 4), /* 0111 */ V(3, 2, 4), /* 1000 */ V(1, 3, 3), /* 1001 */ V(1, 3, 3), /* 1010 */ V(3, 1, 3), /* 1011 */ V(3, 1, 3), /* 1100 */ V(0, 3, 4), /* 1101 */ V(3, 0, 4), /* 1110 */ V(2, 2, 3), /* 1111 */ V(2, 2, 3), /* 0011 ... */ /* 00 */ V(1, 2, 2), /* 64 */ /* 01 */ V(2, 1, 2), /* 10 */ V(0, 2, 2), /* 11 */ V(2, 0, 2), /* 0000 0000 ... */ /* 000 */ V(14, 15, 3), /* 68 */ /* 001 */ V(15, 14, 3), /* 010 */ V(13, 15, 3), /* 011 */ V(15, 13, 3), /* 100 */ V(12, 15, 3), /* 101 */ V(15, 12, 3), /* 110 */ V(11, 15, 3), /* 111 */ V(15, 11, 3), /* 0000 0001 ... */ /* 000 */ V(10, 15, 2), /* 76 */ /* 001 */ V(10, 15, 2), /* 010 */ V(15, 10, 3), /* 011 */ V(9, 15, 3), /* 100 */ V(15, 9, 3), /* 101 */ V(15, 8, 3), /* 110 */ V(8, 15, 2), /* 111 */ V(8, 15, 2), /* 0000 0010 ... */ /* 00 */ V(7, 15, 2), /* 84 */ /* 01 */ V(15, 7, 2), /* 10 */ V(6, 15, 2), /* 11 */ V(15, 6, 2), /* 0000 0100 ... */ /* 00 */ V(5, 15, 2), /* 88 */ /* 01 */ V(15, 5, 2), /* 10 */ V(4, 15, 1), /* 11 */ V(4, 15, 1), /* 0000 0101 ... */ /* 0 */ V(15, 4, 1), /* 92 */ /* 1 */ V(15, 3, 1), /* 0000 0110 ... */ /* 0000 */ V(15, 0, 1), /* 94 */ /* 0001 */ V(15, 0, 1), /* 0010 */ V(15, 0, 1), /* 0011 */ V(15, 0, 1), /* 0100 */ V(15, 0, 1), /* 0101 */ V(15, 0, 1), /* 0110 */ V(15, 0, 1), /* 0111 */ V(15, 0, 1), /* 1000 */ V(3, 15, 2), /* 1001 */ V(3, 15, 2), /* 1010 */ V(3, 15, 2), /* 1011 */ V(3, 15, 2), /* 1100 */ PTR(294, 4), /* 1101 */ PTR(310, 3), /* 1110 */ PTR(318, 3), /* 1111 */ PTR(326, 3), /* 0000 1000 ... */ /* 0 */ V(2, 15, 1), /* 110 */ /* 1 */ V(0, 15, 1), /* 0000 1011 ... */ /* 0000 */ PTR(334, 2), /* 112 */ /* 0001 */ PTR(338, 2), /* 0010 */ PTR(342, 2), /* 0011 */ PTR(346, 1), /* 0100 */ PTR(348, 2), /* 0101 */ PTR(352, 2), /* 0110 */ PTR(356, 1), /* 0111 */ PTR(358, 2), /* 1000 */ PTR(362, 2), /* 1001 */ PTR(366, 2), /* 1010 */ PTR(370, 2), /* 1011 */ V(14, 3, 4), /* 1100 */ PTR(374, 1), /* 1101 */ PTR(376, 1), /* 1110 */ PTR(378, 1), /* 1111 */ PTR(380, 1), /* 0000 1100 ... */ /* 0000 */ PTR(382, 1), /* 128 */ /* 0001 */ PTR(384, 1), /* 0010 */ PTR(386, 1), /* 0011 */ V(0, 13, 4), /* 0100 */ PTR(388, 1), /* 0101 */ PTR(390, 1), /* 0110 */ PTR(392, 1), /* 0111 */ V(3, 12, 4), /* 1000 */ PTR(394, 1), /* 1001 */ V(1, 12, 4), /* 1010 */ V(12, 0, 4), /* 1011 */ PTR(396, 1), /* 1100 */ V(14, 2, 3), /* 1101 */ V(14, 2, 3), /* 1110 */ V(2, 14, 4), /* 1111 */ V(1, 14, 4), /* 0000 1101 ... */ /* 0000 */ V(13, 3, 4), /* 144 */ /* 0001 */ V(2, 13, 4), /* 0010 */ V(13, 2, 4), /* 0011 */ V(13, 1, 4), /* 0100 */ V(3, 11, 4), /* 0101 */ PTR(398, 1), /* 0110 */ V(1, 13, 3), /* 0111 */ V(1, 13, 3), /* 1000 */ V(12, 4, 4), /* 1001 */ V(6, 11, 4), /* 1010 */ V(12, 3, 4), /* 1011 */ V(10, 7, 4), /* 1100 */ V(2, 12, 3), /* 1101 */ V(2, 12, 3), /* 1110 */ V(12, 2, 4), /* 1111 */ V(11, 5, 4), /* 0000 1110 ... */ /* 0000 */ V(12, 1, 4), /* 160 */ /* 0001 */ V(0, 12, 4), /* 0010 */ V(4, 11, 4), /* 0011 */ V(11, 4, 4), /* 0100 */ V(6, 10, 4), /* 0101 */ V(10, 6, 4), /* 0110 */ V(11, 3, 3), /* 0111 */ V(11, 3, 3), /* 1000 */ V(5, 10, 4), /* 1001 */ V(10, 5, 4), /* 1010 */ V(2, 11, 3), /* 1011 */ V(2, 11, 3), /* 1100 */ V(11, 2, 3), /* 1101 */ V(11, 2, 3), /* 1110 */ V(1, 11, 3), /* 1111 */ V(1, 11, 3), /* 0000 1111 ... */ /* 0000 */ V(11, 1, 3), /* 176 */ /* 0001 */ V(11, 1, 3), /* 0010 */ V(0, 11, 4), /* 0011 */ V(11, 0, 4), /* 0100 */ V(6, 9, 4), /* 0101 */ V(9, 6, 4), /* 0110 */ V(4, 10, 4), /* 0111 */ V(10, 4, 4), /* 1000 */ V(7, 8, 4), /* 1001 */ V(8, 7, 4), /* 1010 */ V(10, 3, 3), /* 1011 */ V(10, 3, 3), /* 1100 */ V(3, 10, 4), /* 1101 */ V(5, 9, 4), /* 1110 */ V(2, 10, 3), /* 1111 */ V(2, 10, 3), /* 0001 0000 ... */ /* 0000 */ V(9, 5, 4), /* 192 */ /* 0001 */ V(6, 8, 4), /* 0010 */ V(10, 1, 3), /* 0011 */ V(10, 1, 3), /* 0100 */ V(8, 6, 4), /* 0101 */ V(7, 7, 4), /* 0110 */ V(9, 4, 3), /* 0111 */ V(9, 4, 3), /* 1000 */ V(4, 9, 4), /* 1001 */ V(5, 7, 4), /* 1010 */ V(6, 7, 3), /* 1011 */ V(6, 7, 3), /* 1100 */ V(10, 2, 2), /* 1101 */ V(10, 2, 2), /* 1110 */ V(10, 2, 2), /* 1111 */ V(10, 2, 2), /* 0001 0001 ... */ /* 000 */ V(1, 10, 2), /* 208 */ /* 001 */ V(1, 10, 2), /* 010 */ V(0, 10, 3), /* 011 */ V(10, 0, 3), /* 100 */ V(3, 9, 3), /* 101 */ V(9, 3, 3), /* 110 */ V(5, 8, 3), /* 111 */ V(8, 5, 3), /* 0001 0010 ... */ /* 000 */ V(2, 9, 2), /* 216 */ /* 001 */ V(2, 9, 2), /* 010 */ V(9, 2, 2), /* 011 */ V(9, 2, 2), /* 100 */ V(7, 6, 3), /* 101 */ V(0, 9, 3), /* 110 */ V(1, 9, 2), /* 111 */ V(1, 9, 2), /* 0001 0011 ... */ /* 000 */ V(9, 1, 2), /* 224 */ /* 001 */ V(9, 1, 2), /* 010 */ V(9, 0, 3), /* 011 */ V(4, 8, 3), /* 100 */ V(8, 4, 3), /* 101 */ V(7, 5, 3), /* 110 */ V(3, 8, 3), /* 111 */ V(8, 3, 3), /* 0001 0100 ... */ /* 000 */ V(6, 6, 3), /* 232 */ /* 001 */ V(2, 8, 3), /* 010 */ V(8, 2, 2), /* 011 */ V(8, 2, 2), /* 100 */ V(4, 7, 3), /* 101 */ V(7, 4, 3), /* 110 */ V(1, 8, 2), /* 111 */ V(1, 8, 2), /* 0001 0101 ... */ /* 000 */ V(8, 1, 2), /* 240 */ /* 001 */ V(8, 1, 2), /* 010 */ V(8, 0, 2), /* 011 */ V(8, 0, 2), /* 100 */ V(0, 8, 3), /* 101 */ V(5, 6, 3), /* 110 */ V(3, 7, 2), /* 111 */ V(3, 7, 2), /* 0001 0110 ... */ /* 000 */ V(7, 3, 2), /* 248 */ /* 001 */ V(7, 3, 2), /* 010 */ V(6, 5, 3), /* 011 */ V(4, 6, 3), /* 100 */ V(2, 7, 2), /* 101 */ V(2, 7, 2), /* 110 */ V(7, 2, 2), /* 111 */ V(7, 2, 2), /* 0001 0111 ... */ /* 000 */ V(6, 4, 3), /* 256 */ /* 001 */ V(5, 5, 3), /* 010 */ V(0, 7, 2), /* 011 */ V(0, 7, 2), /* 100 */ V(1, 7, 1), /* 101 */ V(1, 7, 1), /* 110 */ V(1, 7, 1), /* 111 */ V(1, 7, 1), /* 0001 1000 ... */ /* 00 */ V(7, 1, 1), /* 264 */ /* 01 */ V(7, 1, 1), /* 10 */ V(7, 0, 2), /* 11 */ V(3, 6, 2), /* 0001 1001 ... */ /* 00 */ V(6, 3, 2), /* 268 */ /* 01 */ V(4, 5, 2), /* 10 */ V(5, 4, 2), /* 11 */ V(2, 6, 2), /* 0001 1010 ... */ /* 0 */ V(6, 2, 1), /* 272 */ /* 1 */ V(1, 6, 1), /* 0001 1011 ... */ /* 00 */ V(6, 1, 1), /* 274 */ /* 01 */ V(6, 1, 1), /* 10 */ V(0, 6, 2), /* 11 */ V(6, 0, 2), /* 0001 1100 ... */ /* 00 */ V(5, 3, 1), /* 278 */ /* 01 */ V(5, 3, 1), /* 10 */ V(3, 5, 2), /* 11 */ V(4, 4, 2), /* 0001 1101 ... */ /* 0 */ V(2, 5, 1), /* 282 */ /* 1 */ V(5, 2, 1), /* 0001 1111 ... */ /* 0 */ V(1, 5, 1), /* 284 */ /* 1 */ V(0, 5, 1), /* 0010 0000 ... */ /* 0 */ V(3, 4, 1), /* 286 */ /* 1 */ V(4, 3, 1), /* 0010 0001 ... */ /* 0 */ V(5, 0, 1), /* 288 */ /* 1 */ V(2, 4, 1), /* 0010 0010 ... */ /* 0 */ V(4, 2, 1), /* 290 */ /* 1 */ V(3, 3, 1), /* 0010 0101 ... */ /* 0 */ V(0, 4, 1), /* 292 */ /* 1 */ V(4, 0, 1), /* 0000 0110 1100 ... */ /* 0000 */ V(12, 14, 4), /* 294 */ /* 0001 */ PTR(400, 1), /* 0010 */ V(13, 14, 3), /* 0011 */ V(13, 14, 3), /* 0100 */ V(14, 9, 3), /* 0101 */ V(14, 9, 3), /* 0110 */ V(14, 10, 4), /* 0111 */ V(13, 9, 4), /* 1000 */ V(14, 14, 2), /* 1001 */ V(14, 14, 2), /* 1010 */ V(14, 14, 2), /* 1011 */ V(14, 14, 2), /* 1100 */ V(14, 13, 3), /* 1101 */ V(14, 13, 3), /* 1110 */ V(14, 11, 3), /* 1111 */ V(14, 11, 3), /* 0000 0110 1101 ... */ /* 000 */ V(11, 14, 2), /* 310 */ /* 001 */ V(11, 14, 2), /* 010 */ V(12, 13, 2), /* 011 */ V(12, 13, 2), /* 100 */ V(13, 12, 3), /* 101 */ V(13, 11, 3), /* 110 */ V(10, 14, 2), /* 111 */ V(10, 14, 2), /* 0000 0110 1110 ... */ /* 000 */ V(12, 12, 2), /* 318 */ /* 001 */ V(12, 12, 2), /* 010 */ V(10, 13, 3), /* 011 */ V(13, 10, 3), /* 100 */ V(7, 14, 3), /* 101 */ V(10, 12, 3), /* 110 */ V(12, 10, 2), /* 111 */ V(12, 10, 2), /* 0000 0110 1111 ... */ /* 000 */ V(12, 9, 3), /* 326 */ /* 001 */ V(7, 13, 3), /* 010 */ V(5, 14, 2), /* 011 */ V(5, 14, 2), /* 100 */ V(11, 13, 1), /* 101 */ V(11, 13, 1), /* 110 */ V(11, 13, 1), /* 111 */ V(11, 13, 1), /* 0000 1011 0000 ... */ /* 00 */ V(9, 14, 1), /* 334 */ /* 01 */ V(9, 14, 1), /* 10 */ V(11, 12, 2), /* 11 */ V(12, 11, 2), /* 0000 1011 0001 ... */ /* 00 */ V(8, 14, 2), /* 338 */ /* 01 */ V(14, 8, 2), /* 10 */ V(9, 13, 2), /* 11 */ V(14, 7, 2), /* 0000 1011 0010 ... */ /* 00 */ V(11, 11, 2), /* 342 */ /* 01 */ V(8, 13, 2), /* 10 */ V(13, 8, 2), /* 11 */ V(6, 14, 2), /* 0000 1011 0011 ... */ /* 0 */ V(14, 6, 1), /* 346 */ /* 1 */ V(9, 12, 1), /* 0000 1011 0100 ... */ /* 00 */ V(10, 11, 2), /* 348 */ /* 01 */ V(11, 10, 2), /* 10 */ V(14, 5, 2), /* 11 */ V(13, 7, 2), /* 0000 1011 0101 ... */ /* 00 */ V(4, 14, 1), /* 352 */ /* 01 */ V(4, 14, 1), /* 10 */ V(14, 4, 2), /* 11 */ V(8, 12, 2), /* 0000 1011 0110 ... */ /* 0 */ V(12, 8, 1), /* 356 */ /* 1 */ V(3, 14, 1), /* 0000 1011 0111 ... */ /* 00 */ V(6, 13, 1), /* 358 */ /* 01 */ V(6, 13, 1), /* 10 */ V(13, 6, 2), /* 11 */ V(9, 11, 2), /* 0000 1011 1000 ... */ /* 00 */ V(11, 9, 2), /* 362 */ /* 01 */ V(10, 10, 2), /* 10 */ V(14, 1, 1), /* 11 */ V(14, 1, 1), /* 0000 1011 1001 ... */ /* 00 */ V(13, 4, 1), /* 366 */ /* 01 */ V(13, 4, 1), /* 10 */ V(11, 8, 2), /* 11 */ V(10, 9, 2), /* 0000 1011 1010 ... */ /* 00 */ V(7, 11, 1), /* 370 */ /* 01 */ V(7, 11, 1), /* 10 */ V(11, 7, 2), /* 11 */ V(13, 0, 2), /* 0000 1011 1100 ... */ /* 0 */ V(0, 14, 1), /* 374 */ /* 1 */ V(14, 0, 1), /* 0000 1011 1101 ... */ /* 0 */ V(5, 13, 1), /* 376 */ /* 1 */ V(13, 5, 1), /* 0000 1011 1110 ... */ /* 0 */ V(7, 12, 1), /* 378 */ /* 1 */ V(12, 7, 1), /* 0000 1011 1111 ... */ /* 0 */ V(4, 13, 1), /* 380 */ /* 1 */ V(8, 11, 1), /* 0000 1100 0000 ... */ /* 0 */ V(9, 10, 1), /* 382 */ /* 1 */ V(6, 12, 1), /* 0000 1100 0001 ... */ /* 0 */ V(12, 6, 1), /* 384 */ /* 1 */ V(3, 13, 1), /* 0000 1100 0010 ... */ /* 0 */ V(5, 12, 1), /* 386 */ /* 1 */ V(12, 5, 1), /* 0000 1100 0100 ... */ /* 0 */ V(8, 10, 1), /* 388 */ /* 1 */ V(10, 8, 1), /* 0000 1100 0101 ... */ /* 0 */ V(9, 9, 1), /* 390 */ /* 1 */ V(4, 12, 1), /* 0000 1100 0110 ... */ /* 0 */ V(11, 6, 1), /* 392 */ /* 1 */ V(7, 10, 1), /* 0000 1100 1000 ... */ /* 0 */ V(5, 11, 1), /* 394 */ /* 1 */ V(8, 9, 1), /* 0000 1100 1011 ... */ /* 0 */ V(9, 8, 1), /* 396 */ /* 1 */ V(7, 9, 1), /* 0000 1101 0101 ... */ /* 0 */ V(9, 7, 1), /* 398 */ /* 1 */ V(8, 8, 1), /* 0000 0110 1100 0001 ... */ /* 0 */ V(14, 12, 1), /* 400 */ /* 1 */ V(13, 13, 1) }; static union huffpair const hufftab24[] = { /* 0000 */ PTR(16, 4), /* 0001 */ PTR(32, 4), /* 0010 */ PTR(48, 4), /* 0011 */ V(15, 15, 4), /* 0100 */ PTR(64, 4), /* 0101 */ PTR(80, 4), /* 0110 */ PTR(96, 4), /* 0111 */ PTR(112, 4), /* 1000 */ PTR(128, 4), /* 1001 */ PTR(144, 4), /* 1010 */ PTR(160, 3), /* 1011 */ PTR(168, 2), /* 1100 */ V(1, 1, 4), /* 1101 */ V(0, 1, 4), /* 1110 */ V(1, 0, 4), /* 1111 */ V(0, 0, 4), /* 0000 ... */ /* 0000 */ V(14, 15, 4), /* 16 */ /* 0001 */ V(15, 14, 4), /* 0010 */ V(13, 15, 4), /* 0011 */ V(15, 13, 4), /* 0100 */ V(12, 15, 4), /* 0101 */ V(15, 12, 4), /* 0110 */ V(11, 15, 4), /* 0111 */ V(15, 11, 4), /* 1000 */ V(15, 10, 3), /* 1001 */ V(15, 10, 3), /* 1010 */ V(10, 15, 4), /* 1011 */ V(9, 15, 4), /* 1100 */ V(15, 9, 3), /* 1101 */ V(15, 9, 3), /* 1110 */ V(15, 8, 3), /* 1111 */ V(15, 8, 3), /* 0001 ... */ /* 0000 */ V(8, 15, 4), /* 32 */ /* 0001 */ V(7, 15, 4), /* 0010 */ V(15, 7, 3), /* 0011 */ V(15, 7, 3), /* 0100 */ V(6, 15, 3), /* 0101 */ V(6, 15, 3), /* 0110 */ V(15, 6, 3), /* 0111 */ V(15, 6, 3), /* 1000 */ V(5, 15, 3), /* 1001 */ V(5, 15, 3), /* 1010 */ V(15, 5, 3), /* 1011 */ V(15, 5, 3), /* 1100 */ V(4, 15, 3), /* 1101 */ V(4, 15, 3), /* 1110 */ V(15, 4, 3), /* 1111 */ V(15, 4, 3), /* 0010 ... */ /* 0000 */ V(3, 15, 3), /* 48 */ /* 0001 */ V(3, 15, 3), /* 0010 */ V(15, 3, 3), /* 0011 */ V(15, 3, 3), /* 0100 */ V(2, 15, 3), /* 0101 */ V(2, 15, 3), /* 0110 */ V(15, 2, 3), /* 0111 */ V(15, 2, 3), /* 1000 */ V(15, 1, 3), /* 1001 */ V(15, 1, 3), /* 1010 */ V(1, 15, 4), /* 1011 */ V(15, 0, 4), /* 1100 */ PTR(172, 3), /* 1101 */ PTR(180, 3), /* 1110 */ PTR(188, 3), /* 1111 */ PTR(196, 3), /* 0100 ... */ /* 0000 */ PTR(204, 4), /* 64 */ /* 0001 */ PTR(220, 3), /* 0010 */ PTR(228, 3), /* 0011 */ PTR(236, 3), /* 0100 */ PTR(244, 2), /* 0101 */ PTR(248, 2), /* 0110 */ PTR(252, 2), /* 0111 */ PTR(256, 2), /* 1000 */ PTR(260, 2), /* 1001 */ PTR(264, 2), /* 1010 */ PTR(268, 2), /* 1011 */ PTR(272, 2), /* 1100 */ PTR(276, 2), /* 1101 */ PTR(280, 3), /* 1110 */ PTR(288, 2), /* 1111 */ PTR(292, 2), /* 0101 ... */ /* 0000 */ PTR(296, 2), /* 80 */ /* 0001 */ PTR(300, 3), /* 0010 */ PTR(308, 2), /* 0011 */ PTR(312, 3), /* 0100 */ PTR(320, 1), /* 0101 */ PTR(322, 2), /* 0110 */ PTR(326, 2), /* 0111 */ PTR(330, 1), /* 1000 */ PTR(332, 2), /* 1001 */ PTR(336, 1), /* 1010 */ PTR(338, 1), /* 1011 */ PTR(340, 1), /* 1100 */ PTR(342, 1), /* 1101 */ PTR(344, 1), /* 1110 */ PTR(346, 1), /* 1111 */ PTR(348, 1), /* 0110 ... */ /* 0000 */ PTR(350, 1), /* 96 */ /* 0001 */ PTR(352, 1), /* 0010 */ PTR(354, 1), /* 0011 */ PTR(356, 1), /* 0100 */ PTR(358, 1), /* 0101 */ PTR(360, 1), /* 0110 */ PTR(362, 1), /* 0111 */ PTR(364, 1), /* 1000 */ PTR(366, 1), /* 1001 */ PTR(368, 1), /* 1010 */ PTR(370, 2), /* 1011 */ PTR(374, 1), /* 1100 */ PTR(376, 2), /* 1101 */ V(7, 3, 4), /* 1110 */ PTR(380, 1), /* 1111 */ V(7, 2, 4), /* 0111 ... */ /* 0000 */ V(4, 6, 4), /* 112 */ /* 0001 */ V(6, 4, 4), /* 0010 */ V(5, 5, 4), /* 0011 */ V(7, 1, 4), /* 0100 */ V(3, 6, 4), /* 0101 */ V(6, 3, 4), /* 0110 */ V(4, 5, 4), /* 0111 */ V(5, 4, 4), /* 1000 */ V(2, 6, 4), /* 1001 */ V(6, 2, 4), /* 1010 */ V(1, 6, 4), /* 1011 */ V(6, 1, 4), /* 1100 */ PTR(382, 1), /* 1101 */ V(3, 5, 4), /* 1110 */ V(5, 3, 4), /* 1111 */ V(4, 4, 4), /* 1000 ... */ /* 0000 */ V(2, 5, 4), /* 128 */ /* 0001 */ V(5, 2, 4), /* 0010 */ V(1, 5, 4), /* 0011 */ PTR(384, 1), /* 0100 */ V(5, 1, 3), /* 0101 */ V(5, 1, 3), /* 0110 */ V(3, 4, 4), /* 0111 */ V(4, 3, 4), /* 1000 */ V(2, 4, 3), /* 1001 */ V(2, 4, 3), /* 1010 */ V(4, 2, 3), /* 1011 */ V(4, 2, 3), /* 1100 */ V(3, 3, 3), /* 1101 */ V(3, 3, 3), /* 1110 */ V(1, 4, 3), /* 1111 */ V(1, 4, 3), /* 1001 ... */ /* 0000 */ V(4, 1, 3), /* 144 */ /* 0001 */ V(4, 1, 3), /* 0010 */ V(0, 4, 4), /* 0011 */ V(4, 0, 4), /* 0100 */ V(2, 3, 3), /* 0101 */ V(2, 3, 3), /* 0110 */ V(3, 2, 3), /* 0111 */ V(3, 2, 3), /* 1000 */ V(1, 3, 2), /* 1001 */ V(1, 3, 2), /* 1010 */ V(1, 3, 2), /* 1011 */ V(1, 3, 2), /* 1100 */ V(3, 1, 2), /* 1101 */ V(3, 1, 2), /* 1110 */ V(3, 1, 2), /* 1111 */ V(3, 1, 2), /* 1010 ... */ /* 000 */ V(0, 3, 3), /* 160 */ /* 001 */ V(3, 0, 3), /* 010 */ V(2, 2, 2), /* 011 */ V(2, 2, 2), /* 100 */ V(1, 2, 1), /* 101 */ V(1, 2, 1), /* 110 */ V(1, 2, 1), /* 111 */ V(1, 2, 1), /* 1011 ... */ /* 00 */ V(2, 1, 1), /* 168 */ /* 01 */ V(2, 1, 1), /* 10 */ V(0, 2, 2), /* 11 */ V(2, 0, 2), /* 0010 1100 ... */ /* 000 */ V(0, 15, 1), /* 172 */ /* 001 */ V(0, 15, 1), /* 010 */ V(0, 15, 1), /* 011 */ V(0, 15, 1), /* 100 */ V(14, 14, 3), /* 101 */ V(13, 14, 3), /* 110 */ V(14, 13, 3), /* 111 */ V(12, 14, 3), /* 0010 1101 ... */ /* 000 */ V(14, 12, 3), /* 180 */ /* 001 */ V(13, 13, 3), /* 010 */ V(11, 14, 3), /* 011 */ V(14, 11, 3), /* 100 */ V(12, 13, 3), /* 101 */ V(13, 12, 3), /* 110 */ V(10, 14, 3), /* 111 */ V(14, 10, 3), /* 0010 1110 ... */ /* 000 */ V(11, 13, 3), /* 188 */ /* 001 */ V(13, 11, 3), /* 010 */ V(12, 12, 3), /* 011 */ V(9, 14, 3), /* 100 */ V(14, 9, 3), /* 101 */ V(10, 13, 3), /* 110 */ V(13, 10, 3), /* 111 */ V(11, 12, 3), /* 0010 1111 ... */ /* 000 */ V(12, 11, 3), /* 196 */ /* 001 */ V(8, 14, 3), /* 010 */ V(14, 8, 3), /* 011 */ V(9, 13, 3), /* 100 */ V(13, 9, 3), /* 101 */ V(7, 14, 3), /* 110 */ V(14, 7, 3), /* 111 */ V(10, 12, 3), /* 0100 0000 ... */ /* 0000 */ V(12, 10, 3), /* 204 */ /* 0001 */ V(12, 10, 3), /* 0010 */ V(11, 11, 3), /* 0011 */ V(11, 11, 3), /* 0100 */ V(8, 13, 3), /* 0101 */ V(8, 13, 3), /* 0110 */ V(13, 8, 3), /* 0111 */ V(13, 8, 3), /* 1000 */ V(0, 14, 4), /* 1001 */ V(14, 0, 4), /* 1010 */ V(0, 13, 3), /* 1011 */ V(0, 13, 3), /* 1100 */ V(14, 6, 2), /* 1101 */ V(14, 6, 2), /* 1110 */ V(14, 6, 2), /* 1111 */ V(14, 6, 2), /* 0100 0001 ... */ /* 000 */ V(6, 14, 3), /* 220 */ /* 001 */ V(9, 12, 3), /* 010 */ V(12, 9, 2), /* 011 */ V(12, 9, 2), /* 100 */ V(5, 14, 2), /* 101 */ V(5, 14, 2), /* 110 */ V(11, 10, 2), /* 111 */ V(11, 10, 2), /* 0100 0010 ... */ /* 000 */ V(14, 5, 2), /* 228 */ /* 001 */ V(14, 5, 2), /* 010 */ V(10, 11, 3), /* 011 */ V(7, 13, 3), /* 100 */ V(13, 7, 2), /* 101 */ V(13, 7, 2), /* 110 */ V(14, 4, 2), /* 111 */ V(14, 4, 2), /* 0100 0011 ... */ /* 000 */ V(8, 12, 2), /* 236 */ /* 001 */ V(8, 12, 2), /* 010 */ V(12, 8, 2), /* 011 */ V(12, 8, 2), /* 100 */ V(4, 14, 3), /* 101 */ V(2, 14, 3), /* 110 */ V(3, 14, 2), /* 111 */ V(3, 14, 2), /* 0100 0100 ... */ /* 00 */ V(6, 13, 2), /* 244 */ /* 01 */ V(13, 6, 2), /* 10 */ V(14, 3, 2), /* 11 */ V(9, 11, 2), /* 0100 0101 ... */ /* 00 */ V(11, 9, 2), /* 248 */ /* 01 */ V(10, 10, 2), /* 10 */ V(14, 2, 2), /* 11 */ V(1, 14, 2), /* 0100 0110 ... */ /* 00 */ V(14, 1, 2), /* 252 */ /* 01 */ V(5, 13, 2), /* 10 */ V(13, 5, 2), /* 11 */ V(7, 12, 2), /* 0100 0111 ... */ /* 00 */ V(12, 7, 2), /* 256 */ /* 01 */ V(4, 13, 2), /* 10 */ V(8, 11, 2), /* 11 */ V(11, 8, 2), /* 0100 1000 ... */ /* 00 */ V(13, 4, 2), /* 260 */ /* 01 */ V(9, 10, 2), /* 10 */ V(10, 9, 2), /* 11 */ V(6, 12, 2), /* 0100 1001 ... */ /* 00 */ V(12, 6, 2), /* 264 */ /* 01 */ V(3, 13, 2), /* 10 */ V(13, 3, 2), /* 11 */ V(2, 13, 2), /* 0100 1010 ... */ /* 00 */ V(13, 2, 2), /* 268 */ /* 01 */ V(1, 13, 2), /* 10 */ V(7, 11, 2), /* 11 */ V(11, 7, 2), /* 0100 1011 ... */ /* 00 */ V(13, 1, 2), /* 272 */ /* 01 */ V(5, 12, 2), /* 10 */ V(12, 5, 2), /* 11 */ V(8, 10, 2), /* 0100 1100 ... */ /* 00 */ V(10, 8, 2), /* 276 */ /* 01 */ V(9, 9, 2), /* 10 */ V(4, 12, 2), /* 11 */ V(12, 4, 2), /* 0100 1101 ... */ /* 000 */ V(6, 11, 2), /* 280 */ /* 001 */ V(6, 11, 2), /* 010 */ V(11, 6, 2), /* 011 */ V(11, 6, 2), /* 100 */ V(13, 0, 3), /* 101 */ V(0, 12, 3), /* 110 */ V(3, 12, 2), /* 111 */ V(3, 12, 2), /* 0100 1110 ... */ /* 00 */ V(12, 3, 2), /* 288 */ /* 01 */ V(7, 10, 2), /* 10 */ V(10, 7, 2), /* 11 */ V(2, 12, 2), /* 0100 1111 ... */ /* 00 */ V(12, 2, 2), /* 292 */ /* 01 */ V(5, 11, 2), /* 10 */ V(11, 5, 2), /* 11 */ V(1, 12, 2), /* 0101 0000 ... */ /* 00 */ V(8, 9, 2), /* 296 */ /* 01 */ V(9, 8, 2), /* 10 */ V(12, 1, 2), /* 11 */ V(4, 11, 2), /* 0101 0001 ... */ /* 000 */ V(12, 0, 3), /* 300 */ /* 001 */ V(0, 11, 3), /* 010 */ V(3, 11, 2), /* 011 */ V(3, 11, 2), /* 100 */ V(11, 0, 3), /* 101 */ V(0, 10, 3), /* 110 */ V(1, 10, 2), /* 111 */ V(1, 10, 2), /* 0101 0010 ... */ /* 00 */ V(11, 4, 1), /* 308 */ /* 01 */ V(11, 4, 1), /* 10 */ V(6, 10, 2), /* 11 */ V(10, 6, 2), /* 0101 0011 ... */ /* 000 */ V(7, 9, 2), /* 312 */ /* 001 */ V(7, 9, 2), /* 010 */ V(9, 7, 2), /* 011 */ V(9, 7, 2), /* 100 */ V(10, 0, 3), /* 101 */ V(0, 9, 3), /* 110 */ V(9, 0, 2), /* 111 */ V(9, 0, 2), /* 0101 0100 ... */ /* 0 */ V(11, 3, 1), /* 320 */ /* 1 */ V(8, 8, 1), /* 0101 0101 ... */ /* 00 */ V(2, 11, 2), /* 322 */ /* 01 */ V(5, 10, 2), /* 10 */ V(11, 2, 1), /* 11 */ V(11, 2, 1), /* 0101 0110 ... */ /* 00 */ V(10, 5, 2), /* 326 */ /* 01 */ V(1, 11, 2), /* 10 */ V(11, 1, 2), /* 11 */ V(6, 9, 2), /* 0101 0111 ... */ /* 0 */ V(9, 6, 1), /* 330 */ /* 1 */ V(10, 4, 1), /* 0101 1000 ... */ /* 00 */ V(4, 10, 2), /* 332 */ /* 01 */ V(7, 8, 2), /* 10 */ V(8, 7, 1), /* 11 */ V(8, 7, 1), /* 0101 1001 ... */ /* 0 */ V(3, 10, 1), /* 336 */ /* 1 */ V(10, 3, 1), /* 0101 1010 ... */ /* 0 */ V(5, 9, 1), /* 338 */ /* 1 */ V(9, 5, 1), /* 0101 1011 ... */ /* 0 */ V(2, 10, 1), /* 340 */ /* 1 */ V(10, 2, 1), /* 0101 1100 ... */ /* 0 */ V(10, 1, 1), /* 342 */ /* 1 */ V(6, 8, 1), /* 0101 1101 ... */ /* 0 */ V(8, 6, 1), /* 344 */ /* 1 */ V(7, 7, 1), /* 0101 1110 ... */ /* 0 */ V(4, 9, 1), /* 346 */ /* 1 */ V(9, 4, 1), /* 0101 1111 ... */ /* 0 */ V(3, 9, 1), /* 348 */ /* 1 */ V(9, 3, 1), /* 0110 0000 ... */ /* 0 */ V(5, 8, 1), /* 350 */ /* 1 */ V(8, 5, 1), /* 0110 0001 ... */ /* 0 */ V(2, 9, 1), /* 352 */ /* 1 */ V(6, 7, 1), /* 0110 0010 ... */ /* 0 */ V(7, 6, 1), /* 354 */ /* 1 */ V(9, 2, 1), /* 0110 0011 ... */ /* 0 */ V(1, 9, 1), /* 356 */ /* 1 */ V(9, 1, 1), /* 0110 0100 ... */ /* 0 */ V(4, 8, 1), /* 358 */ /* 1 */ V(8, 4, 1), /* 0110 0101 ... */ /* 0 */ V(5, 7, 1), /* 360 */ /* 1 */ V(7, 5, 1), /* 0110 0110 ... */ /* 0 */ V(3, 8, 1), /* 362 */ /* 1 */ V(8, 3, 1), /* 0110 0111 ... */ /* 0 */ V(6, 6, 1), /* 364 */ /* 1 */ V(2, 8, 1), /* 0110 1000 ... */ /* 0 */ V(8, 2, 1), /* 366 */ /* 1 */ V(1, 8, 1), /* 0110 1001 ... */ /* 0 */ V(4, 7, 1), /* 368 */ /* 1 */ V(7, 4, 1), /* 0110 1010 ... */ /* 00 */ V(8, 1, 1), /* 370 */ /* 01 */ V(8, 1, 1), /* 10 */ V(0, 8, 2), /* 11 */ V(8, 0, 2), /* 0110 1011 ... */ /* 0 */ V(5, 6, 1), /* 374 */ /* 1 */ V(6, 5, 1), /* 0110 1100 ... */ /* 00 */ V(1, 7, 1), /* 376 */ /* 01 */ V(1, 7, 1), /* 10 */ V(0, 7, 2), /* 11 */ V(7, 0, 2), /* 0110 1110 ... */ /* 0 */ V(3, 7, 1), /* 380 */ /* 1 */ V(2, 7, 1), /* 0111 1100 ... */ /* 0 */ V(0, 6, 1), /* 382 */ /* 1 */ V(6, 0, 1), /* 1000 0011 ... */ /* 0 */ V(0, 5, 1), /* 384 */ /* 1 */ V(5, 0, 1) }; # undef V # undef PTR /* external tables */ union huffquad const *const mad_huff_quad_table[2] = { hufftabA, hufftabB }; struct hufftable const mad_huff_pair_table[32] = { /* 0 */ { hufftab0, 0, 0 }, /* 1 */ { hufftab1, 0, 3 }, /* 2 */ { hufftab2, 0, 3 }, /* 3 */ { hufftab3, 0, 3 }, /* 4 */ { 0 /* not used */ }, /* 5 */ { hufftab5, 0, 3 }, /* 6 */ { hufftab6, 0, 4 }, /* 7 */ { hufftab7, 0, 4 }, /* 8 */ { hufftab8, 0, 4 }, /* 9 */ { hufftab9, 0, 4 }, /* 10 */ { hufftab10, 0, 4 }, /* 11 */ { hufftab11, 0, 4 }, /* 12 */ { hufftab12, 0, 4 }, /* 13 */ { hufftab13, 0, 4 }, /* 14 */ { 0 /* not used */ }, /* 15 */ { hufftab15, 0, 4 }, /* 16 */ { hufftab16, 1, 4 }, /* 17 */ { hufftab16, 2, 4 }, /* 18 */ { hufftab16, 3, 4 }, /* 19 */ { hufftab16, 4, 4 }, /* 20 */ { hufftab16, 6, 4 }, /* 21 */ { hufftab16, 8, 4 }, /* 22 */ { hufftab16, 10, 4 }, /* 23 */ { hufftab16, 13, 4 }, /* 24 */ { hufftab24, 4, 4 }, /* 25 */ { hufftab24, 5, 4 }, /* 26 */ { hufftab24, 6, 4 }, /* 27 */ { hufftab24, 7, 4 }, /* 28 */ { hufftab24, 8, 4 }, /* 29 */ { hufftab24, 9, 4 }, /* 30 */ { hufftab24, 11, 4 }, /* 31 */ { hufftab24, 13, 4 } }; sources_5316/external/mp3/mad_sf_table.dat0000644000176700017670000001464110627342357017355 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: sf_table.dat,v 1.7 2004/01/23 09:41:33 rob Exp $ */ /* * These are the scalefactor values for Layer I and Layer II. * The values are from Table B.1 of ISO/IEC 11172-3. * * There is some error introduced by the 32-bit fixed-point representation; * the amount of error is shown. For 16-bit PCM output, this shouldn't be * too much of a problem. * * Strictly speaking, Table B.1 has only 63 entries (0-62), thus a strict * interpretation of ISO/IEC 11172-3 would suggest that a scalefactor index of * 63 is invalid. However, for better compatibility with current practices, we * add a 64th entry. */ MAD_F(0x20000000), /* 2.000000000000 => 2.000000000000, e 0.000000000000 */ MAD_F(0x1965fea5), /* 1.587401051968 => 1.587401051074, e 0.000000000894 */ MAD_F(0x1428a2fa), /* 1.259921049895 => 1.259921051562, e -0.000000001667 */ MAD_F(0x10000000), /* 1.000000000000 => 1.000000000000, e 0.000000000000 */ MAD_F(0x0cb2ff53), /* 0.793700525984 => 0.793700527400, e -0.000000001416 */ MAD_F(0x0a14517d), /* 0.629960524947 => 0.629960525781, e -0.000000000833 */ MAD_F(0x08000000), /* 0.500000000000 => 0.500000000000, e 0.000000000000 */ MAD_F(0x06597fa9), /* 0.396850262992 => 0.396850261837, e 0.000000001155 */ MAD_F(0x050a28be), /* 0.314980262474 => 0.314980261028, e 0.000000001446 */ MAD_F(0x04000000), /* 0.250000000000 => 0.250000000000, e 0.000000000000 */ MAD_F(0x032cbfd5), /* 0.198425131496 => 0.198425132781, e -0.000000001285 */ MAD_F(0x0285145f), /* 0.157490131237 => 0.157490130514, e 0.000000000723 */ MAD_F(0x02000000), /* 0.125000000000 => 0.125000000000, e 0.000000000000 */ MAD_F(0x01965fea), /* 0.099212565748 => 0.099212564528, e 0.000000001220 */ MAD_F(0x01428a30), /* 0.078745065618 => 0.078745067120, e -0.000000001501 */ MAD_F(0x01000000), /* 0.062500000000 => 0.062500000000, e 0.000000000000 */ MAD_F(0x00cb2ff5), /* 0.049606282874 => 0.049606282264, e 0.000000000610 */ MAD_F(0x00a14518), /* 0.039372532809 => 0.039372533560, e -0.000000000751 */ MAD_F(0x00800000), /* 0.031250000000 => 0.031250000000, e 0.000000000000 */ MAD_F(0x006597fb), /* 0.024803141437 => 0.024803142995, e -0.000000001558 */ MAD_F(0x0050a28c), /* 0.019686266405 => 0.019686266780, e -0.000000000375 */ MAD_F(0x00400000), /* 0.015625000000 => 0.015625000000, e 0.000000000000 */ MAD_F(0x0032cbfd), /* 0.012401570719 => 0.012401569635, e 0.000000001084 */ MAD_F(0x00285146), /* 0.009843133202 => 0.009843133390, e -0.000000000188 */ MAD_F(0x00200000), /* 0.007812500000 => 0.007812500000, e 0.000000000000 */ MAD_F(0x001965ff), /* 0.006200785359 => 0.006200786680, e -0.000000001321 */ MAD_F(0x001428a3), /* 0.004921566601 => 0.004921566695, e -0.000000000094 */ MAD_F(0x00100000), /* 0.003906250000 => 0.003906250000, e 0.000000000000 */ MAD_F(0x000cb2ff), /* 0.003100392680 => 0.003100391477, e 0.000000001202 */ MAD_F(0x000a1451), /* 0.002460783301 => 0.002460781485, e 0.000000001816 */ MAD_F(0x00080000), /* 0.001953125000 => 0.001953125000, e 0.000000000000 */ MAD_F(0x00065980), /* 0.001550196340 => 0.001550197601, e -0.000000001262 */ MAD_F(0x00050a29), /* 0.001230391650 => 0.001230392605, e -0.000000000955 */ MAD_F(0x00040000), /* 0.000976562500 => 0.000976562500, e 0.000000000000 */ MAD_F(0x00032cc0), /* 0.000775098170 => 0.000775098801, e -0.000000000631 */ MAD_F(0x00028514), /* 0.000615195825 => 0.000615194440, e 0.000000001385 */ MAD_F(0x00020000), /* 0.000488281250 => 0.000488281250, e 0.000000000000 */ MAD_F(0x00019660), /* 0.000387549085 => 0.000387549400, e -0.000000000315 */ MAD_F(0x0001428a), /* 0.000307597913 => 0.000307597220, e 0.000000000693 */ MAD_F(0x00010000), /* 0.000244140625 => 0.000244140625, e 0.000000000000 */ MAD_F(0x0000cb30), /* 0.000193774542 => 0.000193774700, e -0.000000000158 */ MAD_F(0x0000a145), /* 0.000153798956 => 0.000153798610, e 0.000000000346 */ MAD_F(0x00008000), /* 0.000122070313 => 0.000122070313, e 0.000000000000 */ MAD_F(0x00006598), /* 0.000096887271 => 0.000096887350, e -0.000000000079 */ MAD_F(0x000050a3), /* 0.000076899478 => 0.000076901168, e -0.000000001689 */ MAD_F(0x00004000), /* 0.000061035156 => 0.000061035156, e 0.000000000000 */ MAD_F(0x000032cc), /* 0.000048443636 => 0.000048443675, e -0.000000000039 */ MAD_F(0x00002851), /* 0.000038449739 => 0.000038448721, e 0.000000001018 */ MAD_F(0x00002000), /* 0.000030517578 => 0.000030517578, e 0.000000000000 */ MAD_F(0x00001966), /* 0.000024221818 => 0.000024221838, e -0.000000000020 */ MAD_F(0x00001429), /* 0.000019224870 => 0.000019226223, e -0.000000001354 */ MAD_F(0x00001000), /* 0.000015258789 => 0.000015258789, e -0.000000000000 */ MAD_F(0x00000cb3), /* 0.000012110909 => 0.000012110919, e -0.000000000010 */ MAD_F(0x00000a14), /* 0.000009612435 => 0.000009611249, e 0.000000001186 */ MAD_F(0x00000800), /* 0.000007629395 => 0.000007629395, e -0.000000000000 */ MAD_F(0x00000659), /* 0.000006055454 => 0.000006053597, e 0.000000001858 */ MAD_F(0x0000050a), /* 0.000004806217 => 0.000004805624, e 0.000000000593 */ MAD_F(0x00000400), /* 0.000003814697 => 0.000003814697, e 0.000000000000 */ MAD_F(0x0000032d), /* 0.000003027727 => 0.000003028661, e -0.000000000934 */ MAD_F(0x00000285), /* 0.000002403109 => 0.000002402812, e 0.000000000296 */ MAD_F(0x00000200), /* 0.000001907349 => 0.000001907349, e -0.000000000000 */ MAD_F(0x00000196), /* 0.000001513864 => 0.000001512468, e 0.000000001396 */ MAD_F(0x00000143), /* 0.000001201554 => 0.000001203269, e -0.000000001714 */ MAD_F(0x00000000) /* this compatibility entry is not part of Table B.1 */ sources_5316/external/mp3/mad_layer12.h0000644000176700017670000000212110627342357016522 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: layer12.h,v 1.10 2004/01/23 09:41:32 rob Exp $ */ # ifndef LIBMAD_LAYER12_H # define LIBMAD_LAYER12_H # include "mad_stream.h" # include "mad_frame.h" int mad_layer_I(struct mad_stream *, struct mad_frame *); int mad_layer_II(struct mad_stream *, struct mad_frame *); # endif sources_5316/external/mp3/mad_version.h0000644000176700017670000000311210627342357016731 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: version.h,v 1.26 2004/01/23 09:41:33 rob Exp $ */ # ifndef LIBMAD_VERSION_H # define LIBMAD_VERSION_H # define MAD_VERSION_MAJOR 0 # define MAD_VERSION_MINOR 15 # define MAD_VERSION_PATCH 1 # define MAD_VERSION_EXTRA " (beta)" # define MAD_VERSION_STRINGIZE(str) #str # define MAD_VERSION_STRING(num) MAD_VERSION_STRINGIZE(num) # define MAD_VERSION MAD_VERSION_STRING(MAD_VERSION_MAJOR) "." \ MAD_VERSION_STRING(MAD_VERSION_MINOR) "." \ MAD_VERSION_STRING(MAD_VERSION_PATCH) \ MAD_VERSION_EXTRA # define MAD_PUBLISHYEAR "2000-2004" # define MAD_AUTHOR "Underbit Technologies, Inc." # define MAD_EMAIL "info@underbit.com" extern char const mad_version[]; extern char const mad_copyright[]; extern char const mad_author[]; extern char const mad_build[]; # endif sources_5316/external/mp3/mad_huffman.h0000644000176700017670000000350610627342357016677 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: huffman.h,v 1.11 2004/01/23 09:41:32 rob Exp $ */ # ifndef LIBMAD_HUFFMAN_H # define LIBMAD_HUFFMAN_H union huffquad { struct { unsigned short final : 1; unsigned short bits : 3; unsigned short offset : 12; } ptr; struct { unsigned short final : 1; unsigned short hlen : 3; unsigned short v : 1; unsigned short w : 1; unsigned short x : 1; unsigned short y : 1; } value; unsigned short final : 1; }; union huffpair { struct { unsigned short final : 1; unsigned short bits : 3; unsigned short offset : 12; } ptr; struct { unsigned short final : 1; unsigned short hlen : 3; unsigned short x : 4; unsigned short y : 4; } value; unsigned short final : 1; }; struct hufftable { union huffpair const *table; unsigned short linbits; unsigned short startbits; }; extern union huffquad const *const mad_huff_quad_table[2]; extern struct hufftable const mad_huff_pair_table[32]; # endif sources_5316/external/mp3/mad_decoder.h0000644000176700017670000000545010627342357016660 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: decoder.h,v 1.17 2004/01/23 09:41:32 rob Exp $ */ # ifndef LIBMAD_DECODER_H # define LIBMAD_DECODER_H # include "mad_stream.h" # include "mad_frame.h" # include "mad_synth.h" enum mad_decoder_mode { MAD_DECODER_MODE_SYNC = 0, MAD_DECODER_MODE_ASYNC }; enum mad_flow { MAD_FLOW_CONTINUE = 0x0000, /* continue normally */ MAD_FLOW_STOP = 0x0010, /* stop decoding normally */ MAD_FLOW_BREAK = 0x0011, /* stop decoding and signal an error */ MAD_FLOW_IGNORE = 0x0020 /* ignore the current frame */ }; struct mad_decoder { enum mad_decoder_mode mode; int options; struct { long pid; int in; int out; } async; struct { struct mad_stream stream; struct mad_frame frame; struct mad_synth synth; } *sync; void *cb_data; enum mad_flow (*input_func)(void *, struct mad_stream *); enum mad_flow (*header_func)(void *, struct mad_header const *); enum mad_flow (*filter_func)(void *, struct mad_stream const *, struct mad_frame *); enum mad_flow (*output_func)(void *, struct mad_header const *, struct mad_pcm *); enum mad_flow (*error_func)(void *, struct mad_stream *, struct mad_frame *); enum mad_flow (*message_func)(void *, void *, unsigned int *); }; void mad_decoder_init(struct mad_decoder *, void *, enum mad_flow (*)(void *, struct mad_stream *), enum mad_flow (*)(void *, struct mad_header const *), enum mad_flow (*)(void *, struct mad_stream const *, struct mad_frame *), enum mad_flow (*)(void *, struct mad_header const *, struct mad_pcm *), enum mad_flow (*)(void *, struct mad_stream *, struct mad_frame *), enum mad_flow (*)(void *, void *, unsigned int *)); int mad_decoder_finish(struct mad_decoder *); # define mad_decoder_options(decoder, opts) \ ((void) ((decoder)->options = (opts))) int mad_decoder_run(struct mad_decoder *, enum mad_decoder_mode); int mad_decoder_message(struct mad_decoder *, void *, unsigned int *); # endif sources_5316/external/mp3/mad_timer.h0000644000176700017670000000547710627342357016404 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: timer.h,v 1.16 2004/01/23 09:41:33 rob Exp $ */ # ifndef LIBMAD_TIMER_H # define LIBMAD_TIMER_H typedef struct { signed long seconds; /* whole seconds */ unsigned long fraction; /* 1/MAD_TIMER_RESOLUTION seconds */ } mad_timer_t; extern mad_timer_t const mad_timer_zero; # define MAD_TIMER_RESOLUTION 352800000UL enum mad_units { MAD_UNITS_HOURS = -2, MAD_UNITS_MINUTES = -1, MAD_UNITS_SECONDS = 0, /* metric units */ MAD_UNITS_DECISECONDS = 10, MAD_UNITS_CENTISECONDS = 100, MAD_UNITS_MILLISECONDS = 1000, /* audio sample units */ MAD_UNITS_8000_HZ = 8000, MAD_UNITS_11025_HZ = 11025, MAD_UNITS_12000_HZ = 12000, MAD_UNITS_16000_HZ = 16000, MAD_UNITS_22050_HZ = 22050, MAD_UNITS_24000_HZ = 24000, MAD_UNITS_32000_HZ = 32000, MAD_UNITS_44100_HZ = 44100, MAD_UNITS_48000_HZ = 48000, /* video frame/field units */ MAD_UNITS_24_FPS = 24, MAD_UNITS_25_FPS = 25, MAD_UNITS_30_FPS = 30, MAD_UNITS_48_FPS = 48, MAD_UNITS_50_FPS = 50, MAD_UNITS_60_FPS = 60, /* CD audio frames */ MAD_UNITS_75_FPS = 75, /* video drop-frame units */ MAD_UNITS_23_976_FPS = -24, MAD_UNITS_24_975_FPS = -25, MAD_UNITS_29_97_FPS = -30, MAD_UNITS_47_952_FPS = -48, MAD_UNITS_49_95_FPS = -50, MAD_UNITS_59_94_FPS = -60 }; # define mad_timer_reset(timer) ((void) (*(timer) = mad_timer_zero)) int mad_timer_compare(mad_timer_t, mad_timer_t); # define mad_timer_sign(timer) mad_timer_compare((timer), mad_timer_zero) void mad_timer_negate(mad_timer_t *); mad_timer_t mad_timer_abs(mad_timer_t); void mad_timer_set(mad_timer_t *, unsigned long, unsigned long, unsigned long); void mad_timer_add(mad_timer_t *, mad_timer_t); void mad_timer_multiply(mad_timer_t *, signed long); signed long mad_timer_count(mad_timer_t, enum mad_units); unsigned long mad_timer_fraction(mad_timer_t, unsigned long); void mad_timer_string(mad_timer_t, char *, char const *, enum mad_units, enum mad_units, unsigned long); # endif sources_5316/external/mp3/mad_stream.h0000644000176700017670000001057210630501270016530 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: stream.h,v 1.20 2004/02/05 09:02:39 rob Exp $ */ # ifndef LIBMAD_STREAM_H # define LIBMAD_STREAM_H # include "mad_bit.h" # define MAD_BUFFER_GUARD 8 # define MAD_BUFFER_MDLEN (511 + 2048 + MAD_BUFFER_GUARD) enum mad_error { MAD_ERROR_NONE = 0x0000, /* no error */ MAD_ERROR_BUFLEN = 0x0001, /* input buffer too small (or EOF) */ MAD_ERROR_BUFPTR = 0x0002, /* invalid (null) buffer pointer */ MAD_ERROR_NOMEM = 0x0031, /* not enough memory */ MAD_ERROR_LOSTSYNC = 0x0101, /* lost synchronization */ MAD_ERROR_BADLAYER = 0x0102, /* reserved header layer value */ MAD_ERROR_BADBITRATE = 0x0103, /* forbidden bitrate value */ MAD_ERROR_BADSAMPLERATE = 0x0104, /* reserved sample frequency value */ MAD_ERROR_BADEMPHASIS = 0x0105, /* reserved emphasis value */ MAD_ERROR_BADCRC = 0x0201, /* CRC check failed */ MAD_ERROR_BADBITALLOC = 0x0211, /* forbidden bit allocation value */ MAD_ERROR_BADSCALEFACTOR = 0x0221, /* bad scalefactor index */ MAD_ERROR_BADMODE = 0x0222, /* bad bitrate/mode combination */ MAD_ERROR_BADFRAMELEN = 0x0231, /* bad frame length */ MAD_ERROR_BADBIGVALUES = 0x0232, /* bad big_values count */ MAD_ERROR_BADBLOCKTYPE = 0x0233, /* reserved block_type */ MAD_ERROR_BADSCFSI = 0x0234, /* bad scalefactor selection info */ MAD_ERROR_BADDATAPTR = 0x0235, /* bad main_data_begin pointer */ MAD_ERROR_BADPART3LEN = 0x0236, /* bad audio data length */ MAD_ERROR_BADHUFFTABLE = 0x0237, /* bad Huffman table select */ MAD_ERROR_BADHUFFDATA = 0x0238, /* Huffman data overrun */ MAD_ERROR_BADSTEREO = 0x0239 /* incompatible block_type for JS */ }; # define MAD_RECOVERABLE(error) ((error) & 0xff00) struct mad_stream { unsigned char const *buffer; /* input bitstream buffer */ unsigned char const *bufend; /* end of buffer */ unsigned long skiplen; /* bytes to skip before next frame */ int sync; /* stream sync found */ unsigned long freerate; /* free bitrate (fixed) */ unsigned char const *this_frame; /* start of current frame */ unsigned char const *next_frame; /* start of next frame */ struct mad_bitptr ptr; /* current processing bit pointer */ struct mad_bitptr anc_ptr; /* ancillary bits pointer */ unsigned int anc_bitlen; /* number of ancillary bits */ unsigned char (*main_data)[MAD_BUFFER_MDLEN]; /* Layer III main_data() */ unsigned int md_len; /* bytes in main_data */ int options; /* decoding options (see below) */ enum mad_error error; /* error code (see above) */ /* Erez Volk 2007-05-30: */ unsigned long this_offset; /* Offset in stream of current frame */ }; enum { MAD_OPTION_IGNORECRC = 0x0001, /* ignore CRC errors */ MAD_OPTION_HALFSAMPLERATE = 0x0002 /* generate PCM at 1/2 sample rate */ # if 0 /* not yet implemented */ MAD_OPTION_LEFTCHANNEL = 0x0010, /* decode left channel only */ MAD_OPTION_RIGHTCHANNEL = 0x0020, /* decode right channel only */ MAD_OPTION_SINGLECHANNEL = 0x0030 /* combine channels */ # endif }; void mad_stream_init(struct mad_stream *); void mad_stream_finish(struct mad_stream *); # define mad_stream_options(stream, opts) \ ((void) ((stream)->options = (opts))) void mad_stream_buffer(struct mad_stream *, unsigned char const *, unsigned long); void mad_stream_skip(struct mad_stream *, unsigned long); /* Erez Volk */ void mad_stream_buffer_offset(struct mad_stream *, unsigned char const *, unsigned long, unsigned long); int mad_stream_sync(struct mad_stream *); char const *mad_stream_errorstr(struct mad_stream const *); # endif sources_5316/external/mp3/mad_config.h0000644000176700017670000001006610630635500016504 0ustar paulpaul/* config.h. */ /* Edited by Erez Volk for Praat. */ /* Luckily we assume C99, which makes life easier. */ /* Compile with Intel implementation for Win32, otherwise 64-bit */ #if defined (_WIN32) && defined (_MSC_VER) || defined (__GNUC__) && defined (__i386__) && ! defined (macintosh) # define FPM_INTEL #else /* !_WIN32 */ # define FPM_64BIT #endif /* _WIN32 */ /* Define to enable diagnostic debugging support. */ /* #undef DEBUG */ /* Define to enable experimental code. */ /* #undef EXPERIMENTAL */ /* Define to 1 if you have the header file. */ #define HAVE_ASSERT_H 1 /* Define to 1 if you have the header file. */ /* #undef HAVE_DLFCN_H */ /* Define to 1 if you have the header file. */ /* #undef HAVE_ERRNO_H */ /* Define to 1 if you have the `fcntl' function. */ /* #undef HAVE_FCNTL */ /* Define to 1 if you have the header file. */ /* #undef HAVE_FCNTL_H */ /* Define to 1 if you have the `fork' function. */ /* #undef HAVE_FORK */ /* Define to 1 if you have the header file. */ #define HAVE_INTTYPES_H 1 /* Define to 1 if you have the header file. */ #define HAVE_LIMITS_H 1 /* Define if your MIPS CPU supports a 2-operand MADD16 instruction. */ /* #undef HAVE_MADD16_ASM */ /* Define if your MIPS CPU supports a 2-operand MADD instruction. */ /* #undef HAVE_MADD_ASM */ /* Define to 1 if you have the header file. */ #define HAVE_MEMORY_H 1 /* Define to 1 if you have the `pipe' function. */ /* #undef HAVE_PIPE */ /* Define to 1 if you have the header file. */ #define HAVE_STDINT_H 1 /* Define to 1 if you have the header file. */ #define HAVE_STDLIB_H 1 /* Define to 1 if you have the header file. */ #define HAVE_STRINGS_H 1 /* Define to 1 if you have the header file. */ #define HAVE_STRING_H 1 /* Define to 1 if you have the header file. */ #define HAVE_SYS_STAT_H 1 /* Define to 1 if you have the header file. */ #define HAVE_SYS_TYPES_H 1 /* Define to 1 if you have that is POSIX.1 compatible. */ /* #undef HAVE_SYS_WAIT_H */ /* Define to 1 if you have the header file. */ /* #undef HAVE_UNISTD_H */ /* Define to 1 if you have the `waitpid' function. */ /* #undef HAVE_WAITPID */ /* Define to disable debugging assertions. */ /* #undef NDEBUG */ /* Define to optimize for accuracy over speed. */ /* #undef OPT_ACCURACY */ /* Define to optimize for speed over accuracy. */ /* #undef OPT_SPEED */ /* Define to enable a fast subband synthesis approximation optimization. */ /* #undef OPT_SSO */ /* Define to influence a strict interpretation of the ISO/IEC standards, even if this is in opposition with best accepted practices. */ /* #undef OPT_STRICT */ /* Name of package */ #define PACKAGE "libmad" /* Define to the address where bug reports for this package should be sent. */ #define PACKAGE_BUGREPORT "support@underbit.com" /* Define to the full name of this package. */ #define PACKAGE_NAME "MPEG Audio Decoder" /* Define to the full name and version of this package. */ #define PACKAGE_STRING "MPEG Audio Decoder 0.15.1b" /* Define to the one symbol short name of this package. */ #define PACKAGE_TARNAME "libmad" /* Define to the version of this package. */ #define PACKAGE_VERSION "0.15.1b" /* Erez Volk: Let's hope these sizes are correct. */ /* I've added a runtime test for them just in case. */ /* The size of a `int', as computed by sizeof. */ #define SIZEOF_INT 4 /* The size of a `long', as computed by sizeof. */ #define SIZEOF_LONG 4 /* The size of a `long long', as computed by sizeof. */ #define SIZEOF_LONG_LONG 8 /* Define to 1 if you have the ANSI C header files. */ #define STDC_HEADERS 1 /* Version number of package */ #define VERSION "0.15.1b" /* Define to empty if `const' does not conform to ANSI C. */ /* #undef const */ /* Define as `__inline' if that's what the C compiler calls it, or to nothing if it is not supported. */ #ifdef _MSC_VER # define inline __inline #endif /* _MSC_VER */ /* Define to `int' if does not define. */ /* #undef pid_t */ sources_5316/external/mp3/test.c0000644000176700017670000001744110631103262015370 0ustar paulpaul#include #include #include #include #include "mp3.h" #include "mad_config.h" #include "mad_decoder.h" /* * This small program tests that my offset addition to libMAD actually works. * Erez Volk 2007-05-30 */ static void dump_file( const char *filename ); static void test_file( const char *filename ); static void test_mad( FILE *f ); static void test_mp3f( FILE *f ); static void get_offsets( FILE *f ); static enum mad_flow cb_input( void *context, struct mad_stream *stream ); static enum mad_flow cb_header( void *context, struct mad_header const *header ); static enum mad_flow cb_accept_header( void *context, struct mad_header const *header ); static enum mad_flow cb_dump( void *context, struct mad_header const *header, struct mad_pcm *pcm ); static void cb_samples( const int *channels[MP3F_MAX_CHANNELS], unsigned num_samples, void *context ); #define BUFFER_SIZE 2048 static unsigned char the_buffer[BUFFER_SIZE]; #define MAX_OFFSETS 4096 static unsigned long offsets[MAX_OFFSETS]; static unsigned num_offsets; int main( int argc, char *argv[] ) { int i; if ( argc <= 1 ) { printf( "Usage: %s MP3_FILE [MP3_FILE...]\n", argv[0] ); return -1; } if ( argc > 2 && !strcmp( argv[1], "-dump" ) ) dump_file( argv[2] ); else for ( i = 1; i < argc; ++ i ) test_file( argv[i] ); return 0; } typedef struct { FILE *f; unsigned done; unsigned left; FILE *f2; } DUMP_CONTEXT; static void dump_file( const char *filename ) { enum { MAX_FRAMES = 16 }; FILE *f; unsigned i; printf( "Dumping file: \"%s\"...\n", filename ); if ( (f = fopen( filename, "rb" )) == NULL ) { printf( " Cannot open file.\n" ); return; } get_offsets( f ); printf( " Header offsets: %lu, %lu, %lu, %lu, ... %lu\n", offsets[0], offsets[1], offsets[2], offsets[3], offsets[num_offsets - 1] ); for ( i = 0; i < MAX_FRAMES; ++ i ) { char dumpname[128]; struct mad_decoder d; DUMP_CONTEXT c = { f, i, MAX_FRAMES - i }; sprintf( dumpname, "%02u.dump", i ); printf( " Creating %s...\n", dumpname ); c.f2 = fopen( dumpname, "w" ); fseek( f, offsets[i], SEEK_SET ); mad_decoder_init( &d, &c, cb_input, cb_accept_header, NULL, cb_dump, NULL, NULL ); mad_decoder_run( &d, MAD_DECODER_MODE_SYNC ); mad_decoder_finish( &d ); fclose( c.f2 ); } fclose( f ); } static void test_file( const char *filename ) { FILE *f; printf( "Testing file: \"%s\"...\n", filename ); if ( (f = fopen( filename, "rb" )) == NULL ) { printf( " Cannot open file.\n" ); return; } test_mad( f ); test_mp3f( f ); fclose( f ); } static void test_mad( FILE *f ) { enum { MAX_BAD = 16 }; unsigned i, bad; get_offsets( f ); if ( num_offsets >= MAX_OFFSETS ) printf( " Reached maximum number of headers (%u)\n", MAX_OFFSETS ); else printf( " Number of headers found: %u\n", num_offsets ); printf( " Header offsets: %lu, %lu, %lu, %lu, ... %lu\n", offsets[0], offsets[1], offsets[2], offsets[3], offsets[num_offsets - 1] ); printf( " Checking header validity...\n" ); for ( i = bad = 0; i < num_offsets && bad < MAX_BAD; ++ i ) { unsigned char header[2] = { 0, 0 }; if ( i > 0 && offsets[i] <= offsets[i - 1] ) { printf( " Invalid offset table.\n" ); return; } fseek( f, offsets[i], SEEK_SET ); fread( header, 1, sizeof(header), f ); if ( (header[0] != 0xFF) || ((header[1] & 0xE0) != 0xE0) ) { ++ bad; printf( " ERROR: No header at file offset %lu\n", offsets[i] ); } else if ( bad > 0 ) printf( " Good header at file offset %lu\n", offsets[i] ); } if ( bad == 0 ) printf( " All offsets have valid MP3 headers\n" ); } static void get_offsets( FILE *f ) { struct mad_decoder d; /* Make sure there are no leftovers */ memset( &d, time(NULL), sizeof(d) ); num_offsets = 0; mad_decoder_init( &d, &f, cb_input, cb_header, NULL, NULL, NULL, NULL ); if ( mad_decoder_run( &d, MAD_DECODER_MODE_SYNC ) != 0 ) { printf( " Error scanning file.\n" ); return; } mad_decoder_finish( &d ); } static enum mad_flow cb_input( void *context, struct mad_stream *stream ) { FILE *f = *(FILE **)context; unsigned char *data = NULL; unsigned nthrown = 0, ncopied = 0, size = 0; unsigned offset; size_t nread = 0; if (feof (f)) return MAD_FLOW_STOP; if (stream -> next_frame) { nthrown = stream -> next_frame - the_buffer; ncopied = BUFFER_SIZE - nthrown; memmove (the_buffer, stream -> next_frame, ncopied); } data = the_buffer + ncopied; size = BUFFER_SIZE - ncopied; offset = ftell (f) - ncopied; if (size > 0) nread = fread (data, 1, size, f); mad_stream_buffer_offset (stream, the_buffer, nread + ncopied, offset); stream -> this_offset = offset; return MAD_FLOW_CONTINUE; } static enum mad_flow cb_header( void *context, struct mad_header const *header ) { FILE *f = *(FILE **)context; unsigned long foff = ftell( f ); if ( foff > header->offset + BUFFER_SIZE ) printf( " ??? %lu <-> %lu\n", foff, header->offset ); offsets[num_offsets] = header->offset; if ( ++ num_offsets >= MAX_OFFSETS ) return MAD_FLOW_STOP; return MAD_FLOW_CONTINUE; } static enum mad_flow cb_accept_header( void *context, struct mad_header const *header ) { (void)context; (void)header; return MAD_FLOW_CONTINUE; } static enum mad_flow cb_dump( void *context, struct mad_header const *header, struct mad_pcm *pcm ) { DUMP_CONTEXT *c = (DUMP_CONTEXT *)context; FILE *f = c->f2; unsigned i, j, length = pcm->length; const mad_fixed_t *samples = pcm->samples[0]; (void)header; fprintf( f, "FRAME %u, OFFSET %lu (expected %lu)\n", c->done, header->offset, offsets[c->done] ); for ( i = 0; i < length; i += 8 ) { for ( j = i; i < length && j < i + 8; ++ j ) fprintf( f, "%9i ", samples[j] ); fprintf( f, "\n" ); } fprintf( f, "\n" ); ++ c->done; -- c->left; return c->left == 0 ? MAD_FLOW_STOP : MAD_FLOW_CONTINUE; } static void test_mp3f( FILE *f ) { enum { FIRST = 15000, SECOND = 2000, TOTAL = FIRST + SECOND }; enum { MID_OFFSET = 16000, MID_SIZE = 800 }; static int x[TOTAL], y[TOTAL], z[MID_SIZE]; int *p; MP3_FILE mp3f = mp3f_new(); mp3f_set_file( mp3f, f ); if ( mp3f_analyze( mp3f ) ) { printf( " MP3F: Channels = %u\n", mp3f_channels( mp3f ) ); printf( " MP3F: Frequency = %u\n", mp3f_frequency( mp3f ) ); printf( " MP3F: Samples = %lu\n", (unsigned long)mp3f_samples( mp3f ) ); printf( " MP3F: Time => %.2lfs\n", (double)mp3f_samples(mp3f) / (double)mp3f_frequency(mp3f) ); } else printf( " MP3F: Cannot analyze\n" ); memset( x, 0x22, sizeof(x) ); memset( y, 0x22, sizeof(y) ); memset( z, 0x22, sizeof(z) ); mp3f_set_file( mp3f, f ); p = x; mp3f_set_callback( mp3f, cb_samples, &p ); mp3f_read( mp3f, TOTAL ); mp3f_set_file( mp3f, f ); p = y; mp3f_set_callback( mp3f, cb_samples, &p ); mp3f_read( mp3f, FIRST ); mp3f_read( mp3f, SECOND ); mp3f_set_file( mp3f, f ); p = z; mp3f_set_callback( mp3f, cb_samples, &p ); if ( mp3f_seek( mp3f, MID_OFFSET ) ) mp3f_read( mp3f, MID_SIZE ); else printf( " MP3F: Seek failed\n" ); if ( memcmp( x, y, FIRST * sizeof(int) ) != 0 ) printf( " MP3F: Difference in first samples!\n" ); else printf( " MP3F: First samples OK\n" ); if ( memcmp( x + FIRST, y + FIRST, SECOND * sizeof(int) ) != 0 ) printf( " MP3F: Difference in later samples!\n" ); else printf( " MP3F: Later samples OK\n" ); if ( memcmp( x + MID_OFFSET, z, MID_SIZE * sizeof(int) ) != 0 ) printf( " MP3F: Seek doesn't work\n" ); else printf( " MP3F: Seek works\n" ); mp3f_delete( mp3f ); } static void cb_samples( const int *channels[MP3F_MAX_CHANNELS], unsigned num_samples, void *context ) { int **pp = (int **)context; int *p = *pp; unsigned i; for ( i = 0; i < num_samples; ++ i ) p[i] = channels[0][i]; *pp += num_samples; } /* Needed for libMP3 */ void *Melder_malloc( unsigned size ) { return malloc( size ); } void _Melder_free( void **p ) { free( *p ); } sources_5316/external/mp3/mad_frame.h0000644000176700017670000001010610627367005016334 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: frame.h,v 1.20 2004/01/23 09:41:32 rob Exp $ */ # ifndef LIBMAD_FRAME_H # define LIBMAD_FRAME_H # include "mad_fixed.h" # include "mad_timer.h" # include "mad_stream.h" enum mad_layer { MAD_LAYER_I = 1, /* Layer I */ MAD_LAYER_II = 2, /* Layer II */ MAD_LAYER_III = 3 /* Layer III */ }; enum mad_mode { MAD_MODE_SINGLE_CHANNEL = 0, /* single channel */ MAD_MODE_DUAL_CHANNEL = 1, /* dual channel */ MAD_MODE_JOINT_STEREO = 2, /* joint (MS/intensity) stereo */ MAD_MODE_STEREO = 3 /* normal LR stereo */ }; enum mad_emphasis { MAD_EMPHASIS_NONE = 0, /* no emphasis */ MAD_EMPHASIS_50_15_US = 1, /* 50/15 microseconds emphasis */ MAD_EMPHASIS_CCITT_J_17 = 3, /* CCITT J.17 emphasis */ MAD_EMPHASIS_RESERVED = 2 /* unknown emphasis */ }; struct mad_header { enum mad_layer layer; /* audio layer (1, 2, or 3) */ enum mad_mode mode; /* channel mode (see above) */ int mode_extension; /* additional mode info */ enum mad_emphasis emphasis; /* de-emphasis to use (see above) */ unsigned long bitrate; /* stream bitrate (bps) */ unsigned int samplerate; /* sampling frequency (Hz) */ unsigned short crc_check; /* frame CRC accumulator */ unsigned short crc_target; /* final target CRC checksum */ int flags; /* flags (see below) */ int private_bits; /* private bits (see below) */ mad_timer_t duration; /* audio playing time of frame */ /* Erez Volk 2007-05-30: */ unsigned long offset; /* Offset of frame in stream */ }; struct mad_frame { struct mad_header header; /* MPEG audio header */ int options; /* decoding options (from stream) */ mad_fixed_t sbsample[2][36][32]; /* synthesis subband filter samples */ mad_fixed_t (*overlap)[2][32][18]; /* Layer III block overlap data */ }; # define MAD_NCHANNELS(header) ((header)->mode ? 2 : 1) # define MAD_NSBSAMPLES(header) \ ((header)->layer == MAD_LAYER_I ? 12 : \ (((header)->layer == MAD_LAYER_III && \ ((header)->flags & MAD_FLAG_LSF_EXT)) ? 18 : 36)) enum { MAD_FLAG_NPRIVATE_III = 0x0007, /* number of Layer III private bits */ MAD_FLAG_INCOMPLETE = 0x0008, /* header but not data is decoded */ MAD_FLAG_PROTECTION = 0x0010, /* frame has CRC protection */ MAD_FLAG_COPYRIGHT = 0x0020, /* frame is copyright */ MAD_FLAG_ORIGINAL = 0x0040, /* frame is original (else copy) */ MAD_FLAG_PADDING = 0x0080, /* frame has additional slot */ MAD_FLAG_I_STEREO = 0x0100, /* uses intensity joint stereo */ MAD_FLAG_MS_STEREO = 0x0200, /* uses middle/side joint stereo */ MAD_FLAG_FREEFORMAT = 0x0400, /* uses free format bitrate */ MAD_FLAG_LSF_EXT = 0x1000, /* lower sampling freq. extension */ MAD_FLAG_MC_EXT = 0x2000, /* multichannel audio extension */ MAD_FLAG_MPEG_2_5_EXT = 0x4000 /* MPEG 2.5 (unofficial) extension */ }; enum { MAD_PRIVATE_HEADER = 0x0100, /* header private bit */ MAD_PRIVATE_III = 0x001f /* Layer III private bits (up to 5) */ }; void mad_header_init(struct mad_header *); # define mad_header_finish(header) /* nothing */ int mad_header_decode(struct mad_header *, struct mad_stream *); void mad_frame_init(struct mad_frame *); void mad_frame_finish(struct mad_frame *); int mad_frame_decode(struct mad_frame *, struct mad_stream *); void mad_frame_mute(struct mad_frame *); # endif sources_5316/external/mp3/mad_layer3.h0000644000176700017670000000202510627342357016445 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: layer3.h,v 1.10 2004/01/23 09:41:32 rob Exp $ */ # ifndef LIBMAD_LAYER3_H # define LIBMAD_LAYER3_H # include "mad_stream.h" # include "mad_frame.h" int mad_layer_III(struct mad_stream *, struct mad_frame *); # endif sources_5316/external/mp3/mad_bit.h0000644000176700017670000000311510627342357016025 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: bit.h,v 1.12 2004/01/23 09:41:32 rob Exp $ */ # ifndef LIBMAD_BIT_H # define LIBMAD_BIT_H struct mad_bitptr { unsigned char const *byte; unsigned short cache; unsigned short left; }; void mad_bit_init(struct mad_bitptr *, unsigned char const *); # define mad_bit_finish(bitptr) /* nothing */ unsigned int mad_bit_length(struct mad_bitptr const *, struct mad_bitptr const *); # define mad_bit_bitsleft(bitptr) ((bitptr)->left) unsigned char const *mad_bit_nextbyte(struct mad_bitptr const *); void mad_bit_skip(struct mad_bitptr *, unsigned int); unsigned long mad_bit_read(struct mad_bitptr *, unsigned int); void mad_bit_write(struct mad_bitptr *, unsigned int, unsigned long); unsigned short mad_bit_crc(struct mad_bitptr, unsigned int, unsigned short); # endif sources_5316/external/mp3/mad_frame.c0000644000176700017670000003004610627367005016334 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: frame.c,v 1.29 2004/02/04 22:59:19 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # include # include "mad_bit.h" # include "mad_stream.h" # include "mad_frame.h" # include "mad_timer.h" # include "mad_layer12.h" # include "mad_layer3.h" static unsigned long const bitrate_table[5][15] = { /* MPEG-1 */ { 0, 32000, 64000, 96000, 128000, 160000, 192000, 224000, /* Layer I */ 256000, 288000, 320000, 352000, 384000, 416000, 448000 }, { 0, 32000, 48000, 56000, 64000, 80000, 96000, 112000, /* Layer II */ 128000, 160000, 192000, 224000, 256000, 320000, 384000 }, { 0, 32000, 40000, 48000, 56000, 64000, 80000, 96000, /* Layer III */ 112000, 128000, 160000, 192000, 224000, 256000, 320000 }, /* MPEG-2 LSF */ { 0, 32000, 48000, 56000, 64000, 80000, 96000, 112000, /* Layer I */ 128000, 144000, 160000, 176000, 192000, 224000, 256000 }, { 0, 8000, 16000, 24000, 32000, 40000, 48000, 56000, /* Layers */ 64000, 80000, 96000, 112000, 128000, 144000, 160000 } /* II & III */ }; static unsigned int const samplerate_table[3] = { 44100, 48000, 32000 }; static int (*const decoder_table[3])(struct mad_stream *, struct mad_frame *) = { mad_layer_I, mad_layer_II, mad_layer_III }; /* * NAME: header->init() * DESCRIPTION: initialize header struct */ void mad_header_init(struct mad_header *header) { header->layer = 0; header->mode = 0; header->mode_extension = 0; header->emphasis = 0; header->bitrate = 0; header->samplerate = 0; header->crc_check = 0; header->crc_target = 0; header->flags = 0; header->private_bits = 0; header->duration = mad_timer_zero; } /* * NAME: frame->init() * DESCRIPTION: initialize frame struct */ void mad_frame_init(struct mad_frame *frame) { mad_header_init(&frame->header); frame->options = 0; frame->overlap = 0; mad_frame_mute(frame); } /* * NAME: frame->finish() * DESCRIPTION: deallocate any dynamic memory associated with frame */ void mad_frame_finish(struct mad_frame *frame) { mad_header_finish(&frame->header); if (frame->overlap) { free(frame->overlap); frame->overlap = 0; } } /* * NAME: decode_header() * DESCRIPTION: read header data and following CRC word */ static int decode_header(struct mad_header *header, struct mad_stream *stream) { unsigned int index; header->offset = stream->this_offset; header->flags = 0; header->private_bits = 0; /* header() */ /* syncword */ mad_bit_skip(&stream->ptr, 11); /* MPEG 2.5 indicator (really part of syncword) */ if (mad_bit_read(&stream->ptr, 1) == 0) header->flags |= MAD_FLAG_MPEG_2_5_EXT; /* ID */ if (mad_bit_read(&stream->ptr, 1) == 0) header->flags |= MAD_FLAG_LSF_EXT; else if (header->flags & MAD_FLAG_MPEG_2_5_EXT) { stream->error = MAD_ERROR_LOSTSYNC; return -1; } /* layer */ header->layer = 4 - mad_bit_read(&stream->ptr, 2); if (header->layer == 4) { stream->error = MAD_ERROR_BADLAYER; return -1; } /* protection_bit */ if (mad_bit_read(&stream->ptr, 1) == 0) { header->flags |= MAD_FLAG_PROTECTION; header->crc_check = mad_bit_crc(stream->ptr, 16, 0xffff); } /* bitrate_index */ index = mad_bit_read(&stream->ptr, 4); if (index == 15) { stream->error = MAD_ERROR_BADBITRATE; return -1; } if (header->flags & MAD_FLAG_LSF_EXT) header->bitrate = bitrate_table[3 + (header->layer >> 1)][index]; else header->bitrate = bitrate_table[header->layer - 1][index]; /* sampling_frequency */ index = mad_bit_read(&stream->ptr, 2); if (index == 3) { stream->error = MAD_ERROR_BADSAMPLERATE; return -1; } header->samplerate = samplerate_table[index]; if (header->flags & MAD_FLAG_LSF_EXT) { header->samplerate /= 2; if (header->flags & MAD_FLAG_MPEG_2_5_EXT) header->samplerate /= 2; } /* padding_bit */ if (mad_bit_read(&stream->ptr, 1)) header->flags |= MAD_FLAG_PADDING; /* private_bit */ if (mad_bit_read(&stream->ptr, 1)) header->private_bits |= MAD_PRIVATE_HEADER; /* mode */ header->mode = 3 - mad_bit_read(&stream->ptr, 2); /* mode_extension */ header->mode_extension = mad_bit_read(&stream->ptr, 2); /* copyright */ if (mad_bit_read(&stream->ptr, 1)) header->flags |= MAD_FLAG_COPYRIGHT; /* original/copy */ if (mad_bit_read(&stream->ptr, 1)) header->flags |= MAD_FLAG_ORIGINAL; /* emphasis */ header->emphasis = mad_bit_read(&stream->ptr, 2); # if defined(OPT_STRICT) /* * ISO/IEC 11172-3 says this is a reserved emphasis value, but * streams exist which use it anyway. Since the value is not important * to the decoder proper, we allow it unless OPT_STRICT is defined. */ if (header->emphasis == MAD_EMPHASIS_RESERVED) { stream->error = MAD_ERROR_BADEMPHASIS; return -1; } # endif /* error_check() */ /* crc_check */ if (header->flags & MAD_FLAG_PROTECTION) header->crc_target = mad_bit_read(&stream->ptr, 16); return 0; } /* * NAME: free_bitrate() * DESCRIPTION: attempt to discover the bitstream's free bitrate */ static int free_bitrate(struct mad_stream *stream, struct mad_header const *header) { struct mad_bitptr keep_ptr; unsigned long rate = 0; unsigned int pad_slot, slots_per_frame; unsigned char const *ptr = 0; keep_ptr = stream->ptr; pad_slot = (header->flags & MAD_FLAG_PADDING) ? 1 : 0; slots_per_frame = (header->layer == MAD_LAYER_III && (header->flags & MAD_FLAG_LSF_EXT)) ? 72 : 144; while (mad_stream_sync(stream) == 0) { struct mad_stream peek_stream; struct mad_header peek_header; peek_stream = *stream; peek_header = *header; if (decode_header(&peek_header, &peek_stream) == 0 && peek_header.layer == header->layer && peek_header.samplerate == header->samplerate) { unsigned int N; ptr = mad_bit_nextbyte(&stream->ptr); N = ptr - stream->this_frame; if (header->layer == MAD_LAYER_I) { rate = (unsigned long) header->samplerate * (N - 4 * pad_slot + 4) / 48 / 1000; } else { rate = (unsigned long) header->samplerate * (N - pad_slot + 1) / slots_per_frame / 1000; } if (rate >= 8) break; } mad_bit_skip(&stream->ptr, 8); } stream->ptr = keep_ptr; if (rate < 8 || (header->layer == MAD_LAYER_III && rate > 640)) { stream->error = MAD_ERROR_LOSTSYNC; return -1; } stream->freerate = rate * 1000; return 0; } /* * NAME: header->decode() * DESCRIPTION: read the next frame header from the stream */ int mad_header_decode(struct mad_header *header, struct mad_stream *stream) { register unsigned char const *ptr, *end; unsigned int pad_slot, N; ptr = stream->next_frame; end = stream->bufend; if (ptr == 0) { stream->error = MAD_ERROR_BUFPTR; goto fail; } /* stream skip */ if (stream->skiplen) { if (!stream->sync) ptr = stream->this_frame; if (end - ptr < stream->skiplen) { stream->skiplen -= end - ptr; stream->next_frame = end; stream->error = MAD_ERROR_BUFLEN; goto fail; } ptr += stream->skiplen; stream->skiplen = 0; stream->sync = 1; } sync: /* synchronize */ if (stream->sync) { if (end - ptr < MAD_BUFFER_GUARD) { stream->next_frame = ptr; stream->error = MAD_ERROR_BUFLEN; goto fail; } else if (!(ptr[0] == 0xff && (ptr[1] & 0xe0) == 0xe0)) { /* mark point where frame sync word was expected */ stream->this_offset += (ptr - stream->this_frame); /* Erez Volk */ stream->this_frame = ptr; stream->next_frame = ptr + 1; stream->error = MAD_ERROR_LOSTSYNC; goto fail; } } else { mad_bit_init(&stream->ptr, ptr); if (mad_stream_sync(stream) == -1) { if (end - stream->next_frame >= MAD_BUFFER_GUARD) stream->next_frame = end - MAD_BUFFER_GUARD; stream->error = MAD_ERROR_BUFLEN; goto fail; } ptr = mad_bit_nextbyte(&stream->ptr); } /* begin processing */ stream->this_offset += (ptr - stream->this_frame); /* Erez Volk */ stream->this_frame = ptr; stream->next_frame = ptr + 1; /* possibly bogus sync word */ mad_bit_init(&stream->ptr, stream->this_frame); if (decode_header(header, stream) == -1) goto fail; /* calculate frame duration */ mad_timer_set(&header->duration, 0, 32 * MAD_NSBSAMPLES(header), header->samplerate); /* calculate free bit rate */ if (header->bitrate == 0) { if ((stream->freerate == 0 || !stream->sync || (header->layer == MAD_LAYER_III && stream->freerate > 640000)) && free_bitrate(stream, header) == -1) goto fail; header->bitrate = stream->freerate; header->flags |= MAD_FLAG_FREEFORMAT; } /* calculate beginning of next frame */ pad_slot = (header->flags & MAD_FLAG_PADDING) ? 1 : 0; if (header->layer == MAD_LAYER_I) N = ((12 * header->bitrate / header->samplerate) + pad_slot) * 4; else { unsigned int slots_per_frame; slots_per_frame = (header->layer == MAD_LAYER_III && (header->flags & MAD_FLAG_LSF_EXT)) ? 72 : 144; N = (slots_per_frame * header->bitrate / header->samplerate) + pad_slot; } /* verify there is enough data left in buffer to decode this frame */ if (N + MAD_BUFFER_GUARD > end - stream->this_frame) { stream->next_frame = stream->this_frame; stream->error = MAD_ERROR_BUFLEN; goto fail; } stream->next_frame = stream->this_frame + N; if (!stream->sync) { /* check that a valid frame header follows this frame */ ptr = stream->next_frame; if (!(ptr[0] == 0xff && (ptr[1] & 0xe0) == 0xe0)) { ptr = stream->next_frame = stream->this_frame + 1; goto sync; } stream->sync = 1; } header->flags |= MAD_FLAG_INCOMPLETE; return 0; fail: stream->sync = 0; return -1; } /* * NAME: frame->decode() * DESCRIPTION: decode a single frame from a bitstream */ int mad_frame_decode(struct mad_frame *frame, struct mad_stream *stream) { frame->options = stream->options; /* header() */ /* error_check() */ if (!(frame->header.flags & MAD_FLAG_INCOMPLETE) && mad_header_decode(&frame->header, stream) == -1) goto fail; /* audio_data() */ frame->header.flags &= ~MAD_FLAG_INCOMPLETE; if (decoder_table[frame->header.layer - 1](stream, frame) == -1) { if (!MAD_RECOVERABLE(stream->error)) stream->next_frame = stream->this_frame; goto fail; } /* ancillary_data() */ if (frame->header.layer != MAD_LAYER_III) { struct mad_bitptr next_frame; mad_bit_init(&next_frame, stream->next_frame); stream->anc_ptr = stream->ptr; stream->anc_bitlen = mad_bit_length(&stream->ptr, &next_frame); mad_bit_finish(&next_frame); } return 0; fail: stream->anc_bitlen = 0; return -1; } /* * NAME: frame->mute() * DESCRIPTION: zero all subband values so the frame becomes silent */ void mad_frame_mute(struct mad_frame *frame) { unsigned int s, sb; for (s = 0; s < 36; ++s) { for (sb = 0; sb < 32; ++sb) { frame->sbsample[0][s][sb] = frame->sbsample[1][s][sb] = 0; } } if (frame->overlap) { for (s = 0; s < 18; ++s) { for (sb = 0; sb < 32; ++sb) { (*frame->overlap)[0][sb][s] = (*frame->overlap)[1][sb][s] = 0; } } } } sources_5316/external/mp3/mad_stream.c0000644000176700017670000001143410630501270016521 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: stream.c,v 1.12 2004/02/05 09:02:39 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # include # include "mad_bit.h" # include "mad_stream.h" /* * NAME: stream->init() * DESCRIPTION: initialize stream struct */ void mad_stream_init(struct mad_stream *stream) { stream->buffer = 0; stream->bufend = 0; stream->skiplen = 0; stream->sync = 0; stream->freerate = 0; stream->this_frame = 0; stream->next_frame = 0; mad_bit_init(&stream->ptr, 0); mad_bit_init(&stream->anc_ptr, 0); stream->anc_bitlen = 0; stream->main_data = 0; stream->md_len = 0; stream->options = 0; stream->error = MAD_ERROR_NONE; stream->this_offset = 0; /* Erez Volk */ } /* * NAME: stream->finish() * DESCRIPTION: deallocate any dynamic memory associated with stream */ void mad_stream_finish(struct mad_stream *stream) { if (stream->main_data) { free(stream->main_data); stream->main_data = 0; } mad_bit_finish(&stream->anc_ptr); mad_bit_finish(&stream->ptr); } /* * NAME: stream->buffer() * DESCRIPTION: set stream buffer pointers */ void mad_stream_buffer(struct mad_stream *stream, unsigned char const *buffer, unsigned long length) { stream->buffer = buffer; stream->bufend = buffer + length; stream->this_frame = buffer; stream->next_frame = buffer; stream->sync = 1; mad_bit_init(&stream->ptr, buffer); } /* * NAME: stream->buffer_offset() * DESCRIPTION: set stream buffer pointers and offset * Erez Volk */ void mad_stream_buffer_offset(struct mad_stream *stream, unsigned char const *buffer, unsigned long length, unsigned long offset) { mad_stream_buffer(stream, buffer, length); stream->this_offset = offset; } /* * NAME: stream->skip() * DESCRIPTION: arrange to skip bytes before the next frame */ void mad_stream_skip(struct mad_stream *stream, unsigned long length) { stream->skiplen += length; } /* * NAME: stream->sync() * DESCRIPTION: locate the next stream sync word */ int mad_stream_sync(struct mad_stream *stream) { register unsigned char const *ptr, *end; ptr = mad_bit_nextbyte(&stream->ptr); end = stream->bufend; while (ptr < end - 1 && !(ptr[0] == 0xff && (ptr[1] & 0xe0) == 0xe0)) { ++ptr; } if (end - ptr < MAD_BUFFER_GUARD) return -1; mad_bit_init(&stream->ptr, ptr); return 0; } /* * NAME: stream->errorstr() * DESCRIPTION: return a string description of the current error condition */ char const *mad_stream_errorstr(struct mad_stream const *stream) { switch (stream->error) { case MAD_ERROR_NONE: return "no error"; case MAD_ERROR_BUFLEN: return "input buffer too small (or EOF)"; case MAD_ERROR_BUFPTR: return "invalid (null) buffer pointer"; case MAD_ERROR_NOMEM: return "not enough memory"; case MAD_ERROR_LOSTSYNC: return "lost synchronization"; case MAD_ERROR_BADLAYER: return "reserved header layer value"; case MAD_ERROR_BADBITRATE: return "forbidden bitrate value"; case MAD_ERROR_BADSAMPLERATE: return "reserved sample frequency value"; case MAD_ERROR_BADEMPHASIS: return "reserved emphasis value"; case MAD_ERROR_BADCRC: return "CRC check failed"; case MAD_ERROR_BADBITALLOC: return "forbidden bit allocation value"; case MAD_ERROR_BADSCALEFACTOR: return "bad scalefactor index"; case MAD_ERROR_BADMODE: return "bad bitrate/mode combination"; case MAD_ERROR_BADFRAMELEN: return "bad frame length"; case MAD_ERROR_BADBIGVALUES: return "bad big_values count"; case MAD_ERROR_BADBLOCKTYPE: return "reserved block_type"; case MAD_ERROR_BADSCFSI: return "bad scalefactor selection info"; case MAD_ERROR_BADDATAPTR: return "bad main_data_begin pointer"; case MAD_ERROR_BADPART3LEN: return "bad audio data length"; case MAD_ERROR_BADHUFFTABLE: return "bad Huffman table select"; case MAD_ERROR_BADHUFFDATA: return "Huffman data overrun"; case MAD_ERROR_BADSTEREO: return "incompatible block_type for JS"; } return 0; } sources_5316/external/mp3/mad_D.dat0000644000176700017670000006355110627342357015765 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: D.dat,v 1.9 2004/01/23 09:41:32 rob Exp $ */ /* * These are the coefficients for the subband synthesis window. This is a * reordered version of Table B.3 from ISO/IEC 11172-3. * * Every value is parameterized so that shift optimizations can be made at * compile-time. For example, every value can be right-shifted 12 bits to * minimize multiply instruction times without any loss of accuracy. */ { PRESHIFT(0x00000000) /* 0.000000000 */, /* 0 */ -PRESHIFT(0x0001d000) /* -0.000442505 */, PRESHIFT(0x000d5000) /* 0.003250122 */, -PRESHIFT(0x001cb000) /* -0.007003784 */, PRESHIFT(0x007f5000) /* 0.031082153 */, -PRESHIFT(0x01421000) /* -0.078628540 */, PRESHIFT(0x019ae000) /* 0.100311279 */, -PRESHIFT(0x09271000) /* -0.572036743 */, PRESHIFT(0x1251e000) /* 1.144989014 */, PRESHIFT(0x09271000) /* 0.572036743 */, PRESHIFT(0x019ae000) /* 0.100311279 */, PRESHIFT(0x01421000) /* 0.078628540 */, PRESHIFT(0x007f5000) /* 0.031082153 */, PRESHIFT(0x001cb000) /* 0.007003784 */, PRESHIFT(0x000d5000) /* 0.003250122 */, PRESHIFT(0x0001d000) /* 0.000442505 */, PRESHIFT(0x00000000) /* 0.000000000 */, -PRESHIFT(0x0001d000) /* -0.000442505 */, PRESHIFT(0x000d5000) /* 0.003250122 */, -PRESHIFT(0x001cb000) /* -0.007003784 */, PRESHIFT(0x007f5000) /* 0.031082153 */, -PRESHIFT(0x01421000) /* -0.078628540 */, PRESHIFT(0x019ae000) /* 0.100311279 */, -PRESHIFT(0x09271000) /* -0.572036743 */, PRESHIFT(0x1251e000) /* 1.144989014 */, PRESHIFT(0x09271000) /* 0.572036743 */, PRESHIFT(0x019ae000) /* 0.100311279 */, PRESHIFT(0x01421000) /* 0.078628540 */, PRESHIFT(0x007f5000) /* 0.031082153 */, PRESHIFT(0x001cb000) /* 0.007003784 */, PRESHIFT(0x000d5000) /* 0.003250122 */, PRESHIFT(0x0001d000) /* 0.000442505 */ }, { -PRESHIFT(0x00001000) /* -0.000015259 */, /* 1 */ -PRESHIFT(0x0001f000) /* -0.000473022 */, PRESHIFT(0x000da000) /* 0.003326416 */, -PRESHIFT(0x00207000) /* -0.007919312 */, PRESHIFT(0x007d0000) /* 0.030517578 */, -PRESHIFT(0x0158d000) /* -0.084182739 */, PRESHIFT(0x01747000) /* 0.090927124 */, -PRESHIFT(0x099a8000) /* -0.600219727 */, PRESHIFT(0x124f0000) /* 1.144287109 */, PRESHIFT(0x08b38000) /* 0.543823242 */, PRESHIFT(0x01bde000) /* 0.108856201 */, PRESHIFT(0x012b4000) /* 0.073059082 */, PRESHIFT(0x0080f000) /* 0.031478882 */, PRESHIFT(0x00191000) /* 0.006118774 */, PRESHIFT(0x000d0000) /* 0.003173828 */, PRESHIFT(0x0001a000) /* 0.000396729 */, -PRESHIFT(0x00001000) /* -0.000015259 */, -PRESHIFT(0x0001f000) /* -0.000473022 */, PRESHIFT(0x000da000) /* 0.003326416 */, -PRESHIFT(0x00207000) /* -0.007919312 */, PRESHIFT(0x007d0000) /* 0.030517578 */, -PRESHIFT(0x0158d000) /* -0.084182739 */, PRESHIFT(0x01747000) /* 0.090927124 */, -PRESHIFT(0x099a8000) /* -0.600219727 */, PRESHIFT(0x124f0000) /* 1.144287109 */, PRESHIFT(0x08b38000) /* 0.543823242 */, PRESHIFT(0x01bde000) /* 0.108856201 */, PRESHIFT(0x012b4000) /* 0.073059082 */, PRESHIFT(0x0080f000) /* 0.031478882 */, PRESHIFT(0x00191000) /* 0.006118774 */, PRESHIFT(0x000d0000) /* 0.003173828 */, PRESHIFT(0x0001a000) /* 0.000396729 */ }, { -PRESHIFT(0x00001000) /* -0.000015259 */, /* 2 */ -PRESHIFT(0x00023000) /* -0.000534058 */, PRESHIFT(0x000de000) /* 0.003387451 */, -PRESHIFT(0x00245000) /* -0.008865356 */, PRESHIFT(0x007a0000) /* 0.029785156 */, -PRESHIFT(0x016f7000) /* -0.089706421 */, PRESHIFT(0x014a8000) /* 0.080688477 */, -PRESHIFT(0x0a0d8000) /* -0.628295898 */, PRESHIFT(0x12468000) /* 1.142211914 */, PRESHIFT(0x083ff000) /* 0.515609741 */, PRESHIFT(0x01dd8000) /* 0.116577148 */, PRESHIFT(0x01149000) /* 0.067520142 */, PRESHIFT(0x00820000) /* 0.031738281 */, PRESHIFT(0x0015b000) /* 0.005294800 */, PRESHIFT(0x000ca000) /* 0.003082275 */, PRESHIFT(0x00018000) /* 0.000366211 */, -PRESHIFT(0x00001000) /* -0.000015259 */, -PRESHIFT(0x00023000) /* -0.000534058 */, PRESHIFT(0x000de000) /* 0.003387451 */, -PRESHIFT(0x00245000) /* -0.008865356 */, PRESHIFT(0x007a0000) /* 0.029785156 */, -PRESHIFT(0x016f7000) /* -0.089706421 */, PRESHIFT(0x014a8000) /* 0.080688477 */, -PRESHIFT(0x0a0d8000) /* -0.628295898 */, PRESHIFT(0x12468000) /* 1.142211914 */, PRESHIFT(0x083ff000) /* 0.515609741 */, PRESHIFT(0x01dd8000) /* 0.116577148 */, PRESHIFT(0x01149000) /* 0.067520142 */, PRESHIFT(0x00820000) /* 0.031738281 */, PRESHIFT(0x0015b000) /* 0.005294800 */, PRESHIFT(0x000ca000) /* 0.003082275 */, PRESHIFT(0x00018000) /* 0.000366211 */ }, { -PRESHIFT(0x00001000) /* -0.000015259 */, /* 3 */ -PRESHIFT(0x00026000) /* -0.000579834 */, PRESHIFT(0x000e1000) /* 0.003433228 */, -PRESHIFT(0x00285000) /* -0.009841919 */, PRESHIFT(0x00765000) /* 0.028884888 */, -PRESHIFT(0x0185d000) /* -0.095169067 */, PRESHIFT(0x011d1000) /* 0.069595337 */, -PRESHIFT(0x0a7fe000) /* -0.656219482 */, PRESHIFT(0x12386000) /* 1.138763428 */, PRESHIFT(0x07ccb000) /* 0.487472534 */, PRESHIFT(0x01f9c000) /* 0.123474121 */, PRESHIFT(0x00fdf000) /* 0.061996460 */, PRESHIFT(0x00827000) /* 0.031845093 */, PRESHIFT(0x00126000) /* 0.004486084 */, PRESHIFT(0x000c4000) /* 0.002990723 */, PRESHIFT(0x00015000) /* 0.000320435 */, -PRESHIFT(0x00001000) /* -0.000015259 */, -PRESHIFT(0x00026000) /* -0.000579834 */, PRESHIFT(0x000e1000) /* 0.003433228 */, -PRESHIFT(0x00285000) /* -0.009841919 */, PRESHIFT(0x00765000) /* 0.028884888 */, -PRESHIFT(0x0185d000) /* -0.095169067 */, PRESHIFT(0x011d1000) /* 0.069595337 */, -PRESHIFT(0x0a7fe000) /* -0.656219482 */, PRESHIFT(0x12386000) /* 1.138763428 */, PRESHIFT(0x07ccb000) /* 0.487472534 */, PRESHIFT(0x01f9c000) /* 0.123474121 */, PRESHIFT(0x00fdf000) /* 0.061996460 */, PRESHIFT(0x00827000) /* 0.031845093 */, PRESHIFT(0x00126000) /* 0.004486084 */, PRESHIFT(0x000c4000) /* 0.002990723 */, PRESHIFT(0x00015000) /* 0.000320435 */ }, { -PRESHIFT(0x00001000) /* -0.000015259 */, /* 4 */ -PRESHIFT(0x00029000) /* -0.000625610 */, PRESHIFT(0x000e3000) /* 0.003463745 */, -PRESHIFT(0x002c7000) /* -0.010848999 */, PRESHIFT(0x0071e000) /* 0.027801514 */, -PRESHIFT(0x019bd000) /* -0.100540161 */, PRESHIFT(0x00ec0000) /* 0.057617187 */, -PRESHIFT(0x0af15000) /* -0.683914185 */, PRESHIFT(0x12249000) /* 1.133926392 */, PRESHIFT(0x075a0000) /* 0.459472656 */, PRESHIFT(0x0212c000) /* 0.129577637 */, PRESHIFT(0x00e79000) /* 0.056533813 */, PRESHIFT(0x00825000) /* 0.031814575 */, PRESHIFT(0x000f4000) /* 0.003723145 */, PRESHIFT(0x000be000) /* 0.002899170 */, PRESHIFT(0x00013000) /* 0.000289917 */, -PRESHIFT(0x00001000) /* -0.000015259 */, -PRESHIFT(0x00029000) /* -0.000625610 */, PRESHIFT(0x000e3000) /* 0.003463745 */, -PRESHIFT(0x002c7000) /* -0.010848999 */, PRESHIFT(0x0071e000) /* 0.027801514 */, -PRESHIFT(0x019bd000) /* -0.100540161 */, PRESHIFT(0x00ec0000) /* 0.057617187 */, -PRESHIFT(0x0af15000) /* -0.683914185 */, PRESHIFT(0x12249000) /* 1.133926392 */, PRESHIFT(0x075a0000) /* 0.459472656 */, PRESHIFT(0x0212c000) /* 0.129577637 */, PRESHIFT(0x00e79000) /* 0.056533813 */, PRESHIFT(0x00825000) /* 0.031814575 */, PRESHIFT(0x000f4000) /* 0.003723145 */, PRESHIFT(0x000be000) /* 0.002899170 */, PRESHIFT(0x00013000) /* 0.000289917 */ }, { -PRESHIFT(0x00001000) /* -0.000015259 */, /* 5 */ -PRESHIFT(0x0002d000) /* -0.000686646 */, PRESHIFT(0x000e4000) /* 0.003479004 */, -PRESHIFT(0x0030b000) /* -0.011886597 */, PRESHIFT(0x006cb000) /* 0.026535034 */, -PRESHIFT(0x01b17000) /* -0.105819702 */, PRESHIFT(0x00b77000) /* 0.044784546 */, -PRESHIFT(0x0b619000) /* -0.711318970 */, PRESHIFT(0x120b4000) /* 1.127746582 */, PRESHIFT(0x06e81000) /* 0.431655884 */, PRESHIFT(0x02288000) /* 0.134887695 */, PRESHIFT(0x00d17000) /* 0.051132202 */, PRESHIFT(0x0081b000) /* 0.031661987 */, PRESHIFT(0x000c5000) /* 0.003005981 */, PRESHIFT(0x000b7000) /* 0.002792358 */, PRESHIFT(0x00011000) /* 0.000259399 */, -PRESHIFT(0x00001000) /* -0.000015259 */, -PRESHIFT(0x0002d000) /* -0.000686646 */, PRESHIFT(0x000e4000) /* 0.003479004 */, -PRESHIFT(0x0030b000) /* -0.011886597 */, PRESHIFT(0x006cb000) /* 0.026535034 */, -PRESHIFT(0x01b17000) /* -0.105819702 */, PRESHIFT(0x00b77000) /* 0.044784546 */, -PRESHIFT(0x0b619000) /* -0.711318970 */, PRESHIFT(0x120b4000) /* 1.127746582 */, PRESHIFT(0x06e81000) /* 0.431655884 */, PRESHIFT(0x02288000) /* 0.134887695 */, PRESHIFT(0x00d17000) /* 0.051132202 */, PRESHIFT(0x0081b000) /* 0.031661987 */, PRESHIFT(0x000c5000) /* 0.003005981 */, PRESHIFT(0x000b7000) /* 0.002792358 */, PRESHIFT(0x00011000) /* 0.000259399 */ }, { -PRESHIFT(0x00001000) /* -0.000015259 */, /* 6 */ -PRESHIFT(0x00031000) /* -0.000747681 */, PRESHIFT(0x000e4000) /* 0.003479004 */, -PRESHIFT(0x00350000) /* -0.012939453 */, PRESHIFT(0x0066c000) /* 0.025085449 */, -PRESHIFT(0x01c67000) /* -0.110946655 */, PRESHIFT(0x007f5000) /* 0.031082153 */, -PRESHIFT(0x0bd06000) /* -0.738372803 */, PRESHIFT(0x11ec7000) /* 1.120223999 */, PRESHIFT(0x06772000) /* 0.404083252 */, PRESHIFT(0x023b3000) /* 0.139450073 */, PRESHIFT(0x00bbc000) /* 0.045837402 */, PRESHIFT(0x00809000) /* 0.031387329 */, PRESHIFT(0x00099000) /* 0.002334595 */, PRESHIFT(0x000b0000) /* 0.002685547 */, PRESHIFT(0x00010000) /* 0.000244141 */, -PRESHIFT(0x00001000) /* -0.000015259 */, -PRESHIFT(0x00031000) /* -0.000747681 */, PRESHIFT(0x000e4000) /* 0.003479004 */, -PRESHIFT(0x00350000) /* -0.012939453 */, PRESHIFT(0x0066c000) /* 0.025085449 */, -PRESHIFT(0x01c67000) /* -0.110946655 */, PRESHIFT(0x007f5000) /* 0.031082153 */, -PRESHIFT(0x0bd06000) /* -0.738372803 */, PRESHIFT(0x11ec7000) /* 1.120223999 */, PRESHIFT(0x06772000) /* 0.404083252 */, PRESHIFT(0x023b3000) /* 0.139450073 */, PRESHIFT(0x00bbc000) /* 0.045837402 */, PRESHIFT(0x00809000) /* 0.031387329 */, PRESHIFT(0x00099000) /* 0.002334595 */, PRESHIFT(0x000b0000) /* 0.002685547 */, PRESHIFT(0x00010000) /* 0.000244141 */ }, { -PRESHIFT(0x00002000) /* -0.000030518 */, /* 7 */ -PRESHIFT(0x00035000) /* -0.000808716 */, PRESHIFT(0x000e3000) /* 0.003463745 */, -PRESHIFT(0x00397000) /* -0.014022827 */, PRESHIFT(0x005ff000) /* 0.023422241 */, -PRESHIFT(0x01dad000) /* -0.115921021 */, PRESHIFT(0x0043a000) /* 0.016510010 */, -PRESHIFT(0x0c3d9000) /* -0.765029907 */, PRESHIFT(0x11c83000) /* 1.111373901 */, PRESHIFT(0x06076000) /* 0.376800537 */, PRESHIFT(0x024ad000) /* 0.143264771 */, PRESHIFT(0x00a67000) /* 0.040634155 */, PRESHIFT(0x007f0000) /* 0.031005859 */, PRESHIFT(0x0006f000) /* 0.001693726 */, PRESHIFT(0x000a9000) /* 0.002578735 */, PRESHIFT(0x0000e000) /* 0.000213623 */, -PRESHIFT(0x00002000) /* -0.000030518 */, -PRESHIFT(0x00035000) /* -0.000808716 */, PRESHIFT(0x000e3000) /* 0.003463745 */, -PRESHIFT(0x00397000) /* -0.014022827 */, PRESHIFT(0x005ff000) /* 0.023422241 */, -PRESHIFT(0x01dad000) /* -0.115921021 */, PRESHIFT(0x0043a000) /* 0.016510010 */, -PRESHIFT(0x0c3d9000) /* -0.765029907 */, PRESHIFT(0x11c83000) /* 1.111373901 */, PRESHIFT(0x06076000) /* 0.376800537 */, PRESHIFT(0x024ad000) /* 0.143264771 */, PRESHIFT(0x00a67000) /* 0.040634155 */, PRESHIFT(0x007f0000) /* 0.031005859 */, PRESHIFT(0x0006f000) /* 0.001693726 */, PRESHIFT(0x000a9000) /* 0.002578735 */, PRESHIFT(0x0000e000) /* 0.000213623 */ }, { -PRESHIFT(0x00002000) /* -0.000030518 */, /* 8 */ -PRESHIFT(0x0003a000) /* -0.000885010 */, PRESHIFT(0x000e0000) /* 0.003417969 */, -PRESHIFT(0x003df000) /* -0.015121460 */, PRESHIFT(0x00586000) /* 0.021575928 */, -PRESHIFT(0x01ee6000) /* -0.120697021 */, PRESHIFT(0x00046000) /* 0.001068115 */, -PRESHIFT(0x0ca8d000) /* -0.791213989 */, PRESHIFT(0x119e9000) /* 1.101211548 */, PRESHIFT(0x05991000) /* 0.349868774 */, PRESHIFT(0x02578000) /* 0.146362305 */, PRESHIFT(0x0091a000) /* 0.035552979 */, PRESHIFT(0x007d1000) /* 0.030532837 */, PRESHIFT(0x00048000) /* 0.001098633 */, PRESHIFT(0x000a1000) /* 0.002456665 */, PRESHIFT(0x0000d000) /* 0.000198364 */, -PRESHIFT(0x00002000) /* -0.000030518 */, -PRESHIFT(0x0003a000) /* -0.000885010 */, PRESHIFT(0x000e0000) /* 0.003417969 */, -PRESHIFT(0x003df000) /* -0.015121460 */, PRESHIFT(0x00586000) /* 0.021575928 */, -PRESHIFT(0x01ee6000) /* -0.120697021 */, PRESHIFT(0x00046000) /* 0.001068115 */, -PRESHIFT(0x0ca8d000) /* -0.791213989 */, PRESHIFT(0x119e9000) /* 1.101211548 */, PRESHIFT(0x05991000) /* 0.349868774 */, PRESHIFT(0x02578000) /* 0.146362305 */, PRESHIFT(0x0091a000) /* 0.035552979 */, PRESHIFT(0x007d1000) /* 0.030532837 */, PRESHIFT(0x00048000) /* 0.001098633 */, PRESHIFT(0x000a1000) /* 0.002456665 */, PRESHIFT(0x0000d000) /* 0.000198364 */ }, { -PRESHIFT(0x00002000) /* -0.000030518 */, /* 9 */ -PRESHIFT(0x0003f000) /* -0.000961304 */, PRESHIFT(0x000dd000) /* 0.003372192 */, -PRESHIFT(0x00428000) /* -0.016235352 */, PRESHIFT(0x00500000) /* 0.019531250 */, -PRESHIFT(0x02011000) /* -0.125259399 */, -PRESHIFT(0x003e6000) /* -0.015228271 */, -PRESHIFT(0x0d11e000) /* -0.816864014 */, PRESHIFT(0x116fc000) /* 1.089782715 */, PRESHIFT(0x052c5000) /* 0.323318481 */, PRESHIFT(0x02616000) /* 0.148773193 */, PRESHIFT(0x007d6000) /* 0.030609131 */, PRESHIFT(0x007aa000) /* 0.029937744 */, PRESHIFT(0x00024000) /* 0.000549316 */, PRESHIFT(0x0009a000) /* 0.002349854 */, PRESHIFT(0x0000b000) /* 0.000167847 */, -PRESHIFT(0x00002000) /* -0.000030518 */, -PRESHIFT(0x0003f000) /* -0.000961304 */, PRESHIFT(0x000dd000) /* 0.003372192 */, -PRESHIFT(0x00428000) /* -0.016235352 */, PRESHIFT(0x00500000) /* 0.019531250 */, -PRESHIFT(0x02011000) /* -0.125259399 */, -PRESHIFT(0x003e6000) /* -0.015228271 */, -PRESHIFT(0x0d11e000) /* -0.816864014 */, PRESHIFT(0x116fc000) /* 1.089782715 */, PRESHIFT(0x052c5000) /* 0.323318481 */, PRESHIFT(0x02616000) /* 0.148773193 */, PRESHIFT(0x007d6000) /* 0.030609131 */, PRESHIFT(0x007aa000) /* 0.029937744 */, PRESHIFT(0x00024000) /* 0.000549316 */, PRESHIFT(0x0009a000) /* 0.002349854 */, PRESHIFT(0x0000b000) /* 0.000167847 */ }, { -PRESHIFT(0x00002000) /* -0.000030518 */, /* 10 */ -PRESHIFT(0x00044000) /* -0.001037598 */, PRESHIFT(0x000d7000) /* 0.003280640 */, -PRESHIFT(0x00471000) /* -0.017349243 */, PRESHIFT(0x0046b000) /* 0.017257690 */, -PRESHIFT(0x0212b000) /* -0.129562378 */, -PRESHIFT(0x0084a000) /* -0.032379150 */, -PRESHIFT(0x0d78a000) /* -0.841949463 */, PRESHIFT(0x113be000) /* 1.077117920 */, PRESHIFT(0x04c16000) /* 0.297210693 */, PRESHIFT(0x02687000) /* 0.150497437 */, PRESHIFT(0x0069c000) /* 0.025817871 */, PRESHIFT(0x0077f000) /* 0.029281616 */, PRESHIFT(0x00002000) /* 0.000030518 */, PRESHIFT(0x00093000) /* 0.002243042 */, PRESHIFT(0x0000a000) /* 0.000152588 */, -PRESHIFT(0x00002000) /* -0.000030518 */, -PRESHIFT(0x00044000) /* -0.001037598 */, PRESHIFT(0x000d7000) /* 0.003280640 */, -PRESHIFT(0x00471000) /* -0.017349243 */, PRESHIFT(0x0046b000) /* 0.017257690 */, -PRESHIFT(0x0212b000) /* -0.129562378 */, -PRESHIFT(0x0084a000) /* -0.032379150 */, -PRESHIFT(0x0d78a000) /* -0.841949463 */, PRESHIFT(0x113be000) /* 1.077117920 */, PRESHIFT(0x04c16000) /* 0.297210693 */, PRESHIFT(0x02687000) /* 0.150497437 */, PRESHIFT(0x0069c000) /* 0.025817871 */, PRESHIFT(0x0077f000) /* 0.029281616 */, PRESHIFT(0x00002000) /* 0.000030518 */, PRESHIFT(0x00093000) /* 0.002243042 */, PRESHIFT(0x0000a000) /* 0.000152588 */ }, { -PRESHIFT(0x00003000) /* -0.000045776 */, /* 11 */ -PRESHIFT(0x00049000) /* -0.001113892 */, PRESHIFT(0x000d0000) /* 0.003173828 */, -PRESHIFT(0x004ba000) /* -0.018463135 */, PRESHIFT(0x003ca000) /* 0.014801025 */, -PRESHIFT(0x02233000) /* -0.133590698 */, -PRESHIFT(0x00ce4000) /* -0.050354004 */, -PRESHIFT(0x0ddca000) /* -0.866363525 */, PRESHIFT(0x1102f000) /* 1.063217163 */, PRESHIFT(0x04587000) /* 0.271591187 */, PRESHIFT(0x026cf000) /* 0.151596069 */, PRESHIFT(0x0056c000) /* 0.021179199 */, PRESHIFT(0x0074e000) /* 0.028533936 */, -PRESHIFT(0x0001d000) /* -0.000442505 */, PRESHIFT(0x0008b000) /* 0.002120972 */, PRESHIFT(0x00009000) /* 0.000137329 */, -PRESHIFT(0x00003000) /* -0.000045776 */, -PRESHIFT(0x00049000) /* -0.001113892 */, PRESHIFT(0x000d0000) /* 0.003173828 */, -PRESHIFT(0x004ba000) /* -0.018463135 */, PRESHIFT(0x003ca000) /* 0.014801025 */, -PRESHIFT(0x02233000) /* -0.133590698 */, -PRESHIFT(0x00ce4000) /* -0.050354004 */, -PRESHIFT(0x0ddca000) /* -0.866363525 */, PRESHIFT(0x1102f000) /* 1.063217163 */, PRESHIFT(0x04587000) /* 0.271591187 */, PRESHIFT(0x026cf000) /* 0.151596069 */, PRESHIFT(0x0056c000) /* 0.021179199 */, PRESHIFT(0x0074e000) /* 0.028533936 */, -PRESHIFT(0x0001d000) /* -0.000442505 */, PRESHIFT(0x0008b000) /* 0.002120972 */, PRESHIFT(0x00009000) /* 0.000137329 */ }, { -PRESHIFT(0x00003000) /* -0.000045776 */, /* 12 */ -PRESHIFT(0x0004f000) /* -0.001205444 */, PRESHIFT(0x000c8000) /* 0.003051758 */, -PRESHIFT(0x00503000) /* -0.019577026 */, PRESHIFT(0x0031a000) /* 0.012115479 */, -PRESHIFT(0x02326000) /* -0.137298584 */, -PRESHIFT(0x011b5000) /* -0.069168091 */, -PRESHIFT(0x0e3dd000) /* -0.890090942 */, PRESHIFT(0x10c54000) /* 1.048156738 */, PRESHIFT(0x03f1b000) /* 0.246505737 */, PRESHIFT(0x026ee000) /* 0.152069092 */, PRESHIFT(0x00447000) /* 0.016708374 */, PRESHIFT(0x00719000) /* 0.027725220 */, -PRESHIFT(0x00039000) /* -0.000869751 */, PRESHIFT(0x00084000) /* 0.002014160 */, PRESHIFT(0x00008000) /* 0.000122070 */, -PRESHIFT(0x00003000) /* -0.000045776 */, -PRESHIFT(0x0004f000) /* -0.001205444 */, PRESHIFT(0x000c8000) /* 0.003051758 */, -PRESHIFT(0x00503000) /* -0.019577026 */, PRESHIFT(0x0031a000) /* 0.012115479 */, -PRESHIFT(0x02326000) /* -0.137298584 */, -PRESHIFT(0x011b5000) /* -0.069168091 */, -PRESHIFT(0x0e3dd000) /* -0.890090942 */, PRESHIFT(0x10c54000) /* 1.048156738 */, PRESHIFT(0x03f1b000) /* 0.246505737 */, PRESHIFT(0x026ee000) /* 0.152069092 */, PRESHIFT(0x00447000) /* 0.016708374 */, PRESHIFT(0x00719000) /* 0.027725220 */, -PRESHIFT(0x00039000) /* -0.000869751 */, PRESHIFT(0x00084000) /* 0.002014160 */, PRESHIFT(0x00008000) /* 0.000122070 */ }, { -PRESHIFT(0x00004000) /* -0.000061035 */, /* 13 */ -PRESHIFT(0x00055000) /* -0.001296997 */, PRESHIFT(0x000bd000) /* 0.002883911 */, -PRESHIFT(0x0054c000) /* -0.020690918 */, PRESHIFT(0x0025d000) /* 0.009231567 */, -PRESHIFT(0x02403000) /* -0.140670776 */, -PRESHIFT(0x016ba000) /* -0.088775635 */, -PRESHIFT(0x0e9be000) /* -0.913055420 */, PRESHIFT(0x1082d000) /* 1.031936646 */, PRESHIFT(0x038d4000) /* 0.221984863 */, PRESHIFT(0x026e7000) /* 0.151962280 */, PRESHIFT(0x0032e000) /* 0.012420654 */, PRESHIFT(0x006df000) /* 0.026840210 */, -PRESHIFT(0x00053000) /* -0.001266479 */, PRESHIFT(0x0007d000) /* 0.001907349 */, PRESHIFT(0x00007000) /* 0.000106812 */, -PRESHIFT(0x00004000) /* -0.000061035 */, -PRESHIFT(0x00055000) /* -0.001296997 */, PRESHIFT(0x000bd000) /* 0.002883911 */, -PRESHIFT(0x0054c000) /* -0.020690918 */, PRESHIFT(0x0025d000) /* 0.009231567 */, -PRESHIFT(0x02403000) /* -0.140670776 */, -PRESHIFT(0x016ba000) /* -0.088775635 */, -PRESHIFT(0x0e9be000) /* -0.913055420 */, PRESHIFT(0x1082d000) /* 1.031936646 */, PRESHIFT(0x038d4000) /* 0.221984863 */, PRESHIFT(0x026e7000) /* 0.151962280 */, PRESHIFT(0x0032e000) /* 0.012420654 */, PRESHIFT(0x006df000) /* 0.026840210 */, -PRESHIFT(0x00053000) /* -0.001266479 */, PRESHIFT(0x0007d000) /* 0.001907349 */, PRESHIFT(0x00007000) /* 0.000106812 */ }, { -PRESHIFT(0x00004000) /* -0.000061035 */, /* 14 */ -PRESHIFT(0x0005b000) /* -0.001388550 */, PRESHIFT(0x000b1000) /* 0.002700806 */, -PRESHIFT(0x00594000) /* -0.021789551 */, PRESHIFT(0x00192000) /* 0.006134033 */, -PRESHIFT(0x024c8000) /* -0.143676758 */, -PRESHIFT(0x01bf2000) /* -0.109161377 */, -PRESHIFT(0x0ef69000) /* -0.935195923 */, PRESHIFT(0x103be000) /* 1.014617920 */, PRESHIFT(0x032b4000) /* 0.198059082 */, PRESHIFT(0x026bc000) /* 0.151306152 */, PRESHIFT(0x00221000) /* 0.008316040 */, PRESHIFT(0x006a2000) /* 0.025909424 */, -PRESHIFT(0x0006a000) /* -0.001617432 */, PRESHIFT(0x00075000) /* 0.001785278 */, PRESHIFT(0x00007000) /* 0.000106812 */, -PRESHIFT(0x00004000) /* -0.000061035 */, -PRESHIFT(0x0005b000) /* -0.001388550 */, PRESHIFT(0x000b1000) /* 0.002700806 */, -PRESHIFT(0x00594000) /* -0.021789551 */, PRESHIFT(0x00192000) /* 0.006134033 */, -PRESHIFT(0x024c8000) /* -0.143676758 */, -PRESHIFT(0x01bf2000) /* -0.109161377 */, -PRESHIFT(0x0ef69000) /* -0.935195923 */, PRESHIFT(0x103be000) /* 1.014617920 */, PRESHIFT(0x032b4000) /* 0.198059082 */, PRESHIFT(0x026bc000) /* 0.151306152 */, PRESHIFT(0x00221000) /* 0.008316040 */, PRESHIFT(0x006a2000) /* 0.025909424 */, -PRESHIFT(0x0006a000) /* -0.001617432 */, PRESHIFT(0x00075000) /* 0.001785278 */, PRESHIFT(0x00007000) /* 0.000106812 */ }, { -PRESHIFT(0x00005000) /* -0.000076294 */, /* 15 */ -PRESHIFT(0x00061000) /* -0.001480103 */, PRESHIFT(0x000a3000) /* 0.002487183 */, -PRESHIFT(0x005da000) /* -0.022857666 */, PRESHIFT(0x000b9000) /* 0.002822876 */, -PRESHIFT(0x02571000) /* -0.146255493 */, -PRESHIFT(0x0215c000) /* -0.130310059 */, -PRESHIFT(0x0f4dc000) /* -0.956481934 */, PRESHIFT(0x0ff0a000) /* 0.996246338 */, PRESHIFT(0x02cbf000) /* 0.174789429 */, PRESHIFT(0x0266e000) /* 0.150115967 */, PRESHIFT(0x00120000) /* 0.004394531 */, PRESHIFT(0x00662000) /* 0.024932861 */, -PRESHIFT(0x0007f000) /* -0.001937866 */, PRESHIFT(0x0006f000) /* 0.001693726 */, PRESHIFT(0x00006000) /* 0.000091553 */, -PRESHIFT(0x00005000) /* -0.000076294 */, -PRESHIFT(0x00061000) /* -0.001480103 */, PRESHIFT(0x000a3000) /* 0.002487183 */, -PRESHIFT(0x005da000) /* -0.022857666 */, PRESHIFT(0x000b9000) /* 0.002822876 */, -PRESHIFT(0x02571000) /* -0.146255493 */, -PRESHIFT(0x0215c000) /* -0.130310059 */, -PRESHIFT(0x0f4dc000) /* -0.956481934 */, PRESHIFT(0x0ff0a000) /* 0.996246338 */, PRESHIFT(0x02cbf000) /* 0.174789429 */, PRESHIFT(0x0266e000) /* 0.150115967 */, PRESHIFT(0x00120000) /* 0.004394531 */, PRESHIFT(0x00662000) /* 0.024932861 */, -PRESHIFT(0x0007f000) /* -0.001937866 */, PRESHIFT(0x0006f000) /* 0.001693726 */, PRESHIFT(0x00006000) /* 0.000091553 */ }, { -PRESHIFT(0x00005000) /* -0.000076294 */, /* 16 */ -PRESHIFT(0x00068000) /* -0.001586914 */, PRESHIFT(0x00092000) /* 0.002227783 */, -PRESHIFT(0x0061f000) /* -0.023910522 */, -PRESHIFT(0x0002d000) /* -0.000686646 */, -PRESHIFT(0x025ff000) /* -0.148422241 */, -PRESHIFT(0x026f7000) /* -0.152206421 */, -PRESHIFT(0x0fa13000) /* -0.976852417 */, PRESHIFT(0x0fa13000) /* 0.976852417 */, PRESHIFT(0x026f7000) /* 0.152206421 */, PRESHIFT(0x025ff000) /* 0.148422241 */, PRESHIFT(0x0002d000) /* 0.000686646 */, PRESHIFT(0x0061f000) /* 0.023910522 */, -PRESHIFT(0x00092000) /* -0.002227783 */, PRESHIFT(0x00068000) /* 0.001586914 */, PRESHIFT(0x00005000) /* 0.000076294 */, -PRESHIFT(0x00005000) /* -0.000076294 */, -PRESHIFT(0x00068000) /* -0.001586914 */, PRESHIFT(0x00092000) /* 0.002227783 */, -PRESHIFT(0x0061f000) /* -0.023910522 */, -PRESHIFT(0x0002d000) /* -0.000686646 */, -PRESHIFT(0x025ff000) /* -0.148422241 */, -PRESHIFT(0x026f7000) /* -0.152206421 */, -PRESHIFT(0x0fa13000) /* -0.976852417 */, PRESHIFT(0x0fa13000) /* 0.976852417 */, PRESHIFT(0x026f7000) /* 0.152206421 */, PRESHIFT(0x025ff000) /* 0.148422241 */, PRESHIFT(0x0002d000) /* 0.000686646 */, PRESHIFT(0x0061f000) /* 0.023910522 */, -PRESHIFT(0x00092000) /* -0.002227783 */, PRESHIFT(0x00068000) /* 0.001586914 */, PRESHIFT(0x00005000) /* 0.000076294 */ } sources_5316/external/mp3/mad_synth.c0000644000176700017670000005751610630626517016422 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: synth.c,v 1.25 2004/01/23 09:41:33 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # include "mad_fixed.h" # include "mad_frame.h" # include "mad_synth.h" /* * NAME: synth->init() * DESCRIPTION: initialize synth struct */ void mad_synth_init(struct mad_synth *synth) { mad_synth_mute(synth); synth->phase = 0; synth->pcm.samplerate = 0; synth->pcm.channels = 0; synth->pcm.length = 0; } /* * NAME: synth->mute() * DESCRIPTION: zero all polyphase filterbank values, resetting synthesis */ void mad_synth_mute(struct mad_synth *synth) { unsigned int ch, s, v; for (ch = 0; ch < 2; ++ch) { for (s = 0; s < 16; ++s) { for (v = 0; v < 8; ++v) { synth->filter[ch][0][0][s][v] = synth->filter[ch][0][1][s][v] = synth->filter[ch][1][0][s][v] = synth->filter[ch][1][1][s][v] = 0; } } } } /* * An optional optimization called here the Subband Synthesis Optimization * (SSO) improves the performance of subband synthesis at the expense of * accuracy. * * The idea is to simplify 32x32->64-bit multiplication to 32x32->32 such * that extra scaling and rounding are not necessary. This often allows the * compiler to use faster 32-bit multiply-accumulate instructions instead of * explicit 64-bit multiply, shift, and add instructions. * * SSO works like this: a full 32x32->64-bit multiply of two mad_fixed_t * values requires the result to be right-shifted 28 bits to be properly * scaled to the same fixed-point format. Right shifts can be applied at any * time to either operand or to the result, so the optimization involves * careful placement of these shifts to minimize the loss of accuracy. * * First, a 14-bit shift is applied with rounding at compile-time to the D[] * table of coefficients for the subband synthesis window. This only loses 2 * bits of accuracy because the lower 12 bits are always zero. A second * 12-bit shift occurs after the DCT calculation. This loses 12 bits of * accuracy. Finally, a third 2-bit shift occurs just before the sample is * saved in the PCM buffer. 14 + 12 + 2 == 28 bits. */ /* FPM_DEFAULT without OPT_SSO will actually lose accuracy and performance */ # if defined(FPM_DEFAULT) && !defined(OPT_SSO) # define OPT_SSO # endif /* second SSO shift, with rounding */ # if defined(OPT_SSO) # define SHIFT(x) (((x) + (1L << 11)) >> 12) # else # define SHIFT(x) (x) # endif /* possible DCT speed optimization */ # if defined(OPT_SPEED) && defined(MAD_F_MLX) # define OPT_DCTO # define MUL(x, y) \ ({ mad_fixed64hi_t hi; \ mad_fixed64lo_t lo; \ MAD_F_MLX(hi, lo, (x), (y)); \ hi << (32 - MAD_F_SCALEBITS - 3); \ }) # else # undef OPT_DCTO # define MUL(x, y) mad_f_mul((x), (y)) # endif /* * NAME: dct32() * DESCRIPTION: perform fast in[32]->out[32] DCT */ static void dct32(mad_fixed_t const in[32], unsigned int slot, mad_fixed_t lo[16][8], mad_fixed_t hi[16][8]) { mad_fixed_t t0, t1, t2, t3, t4, t5, t6, t7; mad_fixed_t t8, t9, t10, t11, t12, t13, t14, t15; mad_fixed_t t16, t17, t18, t19, t20, t21, t22, t23; mad_fixed_t t24, t25, t26, t27, t28, t29, t30, t31; mad_fixed_t t32, t33, t34, t35, t36, t37, t38, t39; mad_fixed_t t40, t41, t42, t43, t44, t45, t46, t47; mad_fixed_t t48, t49, t50, t51, t52, t53, t54, t55; mad_fixed_t t56, t57, t58, t59, t60, t61, t62, t63; mad_fixed_t t64, t65, t66, t67, t68, t69, t70, t71; mad_fixed_t t72, t73, t74, t75, t76, t77, t78, t79; mad_fixed_t t80, t81, t82, t83, t84, t85, t86, t87; mad_fixed_t t88, t89, t90, t91, t92, t93, t94, t95; mad_fixed_t t96, t97, t98, t99, t100, t101, t102, t103; mad_fixed_t t104, t105, t106, t107, t108, t109, t110, t111; mad_fixed_t t112, t113, t114, t115, t116, t117, t118, t119; mad_fixed_t t120, t121, t122, t123, t124, t125, t126, t127; mad_fixed_t t128, t129, t130, t131, t132, t133, t134, t135; mad_fixed_t t136, t137, t138, t139, t140, t141, t142, t143; mad_fixed_t t144, t145, t146, t147, t148, t149, t150, t151; mad_fixed_t t152, t153, t154, t155, t156, t157, t158, t159; mad_fixed_t t160, t161, t162, t163, t164, t165, t166, t167; mad_fixed_t t168, t169, t170, t171, t172, t173, t174, t175; mad_fixed_t t176; /* costab[i] = cos(PI / (2 * 32) * i) */ # if defined(OPT_DCTO) # define costab1 MAD_F(0x7fd8878e) # define costab2 MAD_F(0x7f62368f) # define costab3 MAD_F(0x7e9d55fc) # define costab4 MAD_F(0x7d8a5f40) # define costab5 MAD_F(0x7c29fbee) # define costab6 MAD_F(0x7a7d055b) # define costab7 MAD_F(0x78848414) # define costab8 MAD_F(0x7641af3d) # define costab9 MAD_F(0x73b5ebd1) # define costab10 MAD_F(0x70e2cbc6) # define costab11 MAD_F(0x6dca0d14) # define costab12 MAD_F(0x6a6d98a4) # define costab13 MAD_F(0x66cf8120) # define costab14 MAD_F(0x62f201ac) # define costab15 MAD_F(0x5ed77c8a) # define costab16 MAD_F(0x5a82799a) # define costab17 MAD_F(0x55f5a4d2) # define costab18 MAD_F(0x5133cc94) # define costab19 MAD_F(0x4c3fdff4) # define costab20 MAD_F(0x471cece7) # define costab21 MAD_F(0x41ce1e65) # define costab22 MAD_F(0x3c56ba70) # define costab23 MAD_F(0x36ba2014) # define costab24 MAD_F(0x30fbc54d) # define costab25 MAD_F(0x2b1f34eb) # define costab26 MAD_F(0x25280c5e) # define costab27 MAD_F(0x1f19f97b) # define costab28 MAD_F(0x18f8b83c) # define costab29 MAD_F(0x12c8106f) # define costab30 MAD_F(0x0c8bd35e) # define costab31 MAD_F(0x0647d97c) # else # define costab1 MAD_F(0x0ffb10f2) /* 0.998795456 */ # define costab2 MAD_F(0x0fec46d2) /* 0.995184727 */ # define costab3 MAD_F(0x0fd3aac0) /* 0.989176510 */ # define costab4 MAD_F(0x0fb14be8) /* 0.980785280 */ # define costab5 MAD_F(0x0f853f7e) /* 0.970031253 */ # define costab6 MAD_F(0x0f4fa0ab) /* 0.956940336 */ # define costab7 MAD_F(0x0f109082) /* 0.941544065 */ # define costab8 MAD_F(0x0ec835e8) /* 0.923879533 */ # define costab9 MAD_F(0x0e76bd7a) /* 0.903989293 */ # define costab10 MAD_F(0x0e1c5979) /* 0.881921264 */ # define costab11 MAD_F(0x0db941a3) /* 0.857728610 */ # define costab12 MAD_F(0x0d4db315) /* 0.831469612 */ # define costab13 MAD_F(0x0cd9f024) /* 0.803207531 */ # define costab14 MAD_F(0x0c5e4036) /* 0.773010453 */ # define costab15 MAD_F(0x0bdaef91) /* 0.740951125 */ # define costab16 MAD_F(0x0b504f33) /* 0.707106781 */ # define costab17 MAD_F(0x0abeb49a) /* 0.671558955 */ # define costab18 MAD_F(0x0a267993) /* 0.634393284 */ # define costab19 MAD_F(0x0987fbfe) /* 0.595699304 */ # define costab20 MAD_F(0x08e39d9d) /* 0.555570233 */ # define costab21 MAD_F(0x0839c3cd) /* 0.514102744 */ # define costab22 MAD_F(0x078ad74e) /* 0.471396737 */ # define costab23 MAD_F(0x06d74402) /* 0.427555093 */ # define costab24 MAD_F(0x061f78aa) /* 0.382683432 */ # define costab25 MAD_F(0x0563e69d) /* 0.336889853 */ # define costab26 MAD_F(0x04a5018c) /* 0.290284677 */ # define costab27 MAD_F(0x03e33f2f) /* 0.242980180 */ # define costab28 MAD_F(0x031f1708) /* 0.195090322 */ # define costab29 MAD_F(0x0259020e) /* 0.146730474 */ # define costab30 MAD_F(0x01917a6c) /* 0.098017140 */ # define costab31 MAD_F(0x00c8fb30) /* 0.049067674 */ # endif t0 = in[0] + in[31]; t16 = MUL(in[0] - in[31], costab1); t1 = in[15] + in[16]; t17 = MUL(in[15] - in[16], costab31); t41 = t16 + t17; t59 = MUL(t16 - t17, costab2); t33 = t0 + t1; t50 = MUL(t0 - t1, costab2); t2 = in[7] + in[24]; t18 = MUL(in[7] - in[24], costab15); t3 = in[8] + in[23]; t19 = MUL(in[8] - in[23], costab17); t42 = t18 + t19; t60 = MUL(t18 - t19, costab30); t34 = t2 + t3; t51 = MUL(t2 - t3, costab30); t4 = in[3] + in[28]; t20 = MUL(in[3] - in[28], costab7); t5 = in[12] + in[19]; t21 = MUL(in[12] - in[19], costab25); t43 = t20 + t21; t61 = MUL(t20 - t21, costab14); t35 = t4 + t5; t52 = MUL(t4 - t5, costab14); t6 = in[4] + in[27]; t22 = MUL(in[4] - in[27], costab9); t7 = in[11] + in[20]; t23 = MUL(in[11] - in[20], costab23); t44 = t22 + t23; t62 = MUL(t22 - t23, costab18); t36 = t6 + t7; t53 = MUL(t6 - t7, costab18); t8 = in[1] + in[30]; t24 = MUL(in[1] - in[30], costab3); t9 = in[14] + in[17]; t25 = MUL(in[14] - in[17], costab29); t45 = t24 + t25; t63 = MUL(t24 - t25, costab6); t37 = t8 + t9; t54 = MUL(t8 - t9, costab6); t10 = in[6] + in[25]; t26 = MUL(in[6] - in[25], costab13); t11 = in[9] + in[22]; t27 = MUL(in[9] - in[22], costab19); t46 = t26 + t27; t64 = MUL(t26 - t27, costab26); t38 = t10 + t11; t55 = MUL(t10 - t11, costab26); t12 = in[2] + in[29]; t28 = MUL(in[2] - in[29], costab5); t13 = in[13] + in[18]; t29 = MUL(in[13] - in[18], costab27); t47 = t28 + t29; t65 = MUL(t28 - t29, costab10); t39 = t12 + t13; t56 = MUL(t12 - t13, costab10); t14 = in[5] + in[26]; t30 = MUL(in[5] - in[26], costab11); t15 = in[10] + in[21]; t31 = MUL(in[10] - in[21], costab21); t48 = t30 + t31; t66 = MUL(t30 - t31, costab22); t40 = t14 + t15; t57 = MUL(t14 - t15, costab22); t69 = t33 + t34; t89 = MUL(t33 - t34, costab4); t70 = t35 + t36; t90 = MUL(t35 - t36, costab28); t71 = t37 + t38; t91 = MUL(t37 - t38, costab12); t72 = t39 + t40; t92 = MUL(t39 - t40, costab20); t73 = t41 + t42; t94 = MUL(t41 - t42, costab4); t74 = t43 + t44; t95 = MUL(t43 - t44, costab28); t75 = t45 + t46; t96 = MUL(t45 - t46, costab12); t76 = t47 + t48; t97 = MUL(t47 - t48, costab20); t78 = t50 + t51; t100 = MUL(t50 - t51, costab4); t79 = t52 + t53; t101 = MUL(t52 - t53, costab28); t80 = t54 + t55; t102 = MUL(t54 - t55, costab12); t81 = t56 + t57; t103 = MUL(t56 - t57, costab20); t83 = t59 + t60; t106 = MUL(t59 - t60, costab4); t84 = t61 + t62; t107 = MUL(t61 - t62, costab28); t85 = t63 + t64; t108 = MUL(t63 - t64, costab12); t86 = t65 + t66; t109 = MUL(t65 - t66, costab20); t113 = t69 + t70; t114 = t71 + t72; /* 0 */ hi[15][slot] = SHIFT(t113 + t114); /* 16 */ lo[ 0][slot] = SHIFT(MUL(t113 - t114, costab16)); t115 = t73 + t74; t116 = t75 + t76; t32 = t115 + t116; /* 1 */ hi[14][slot] = SHIFT(t32); t118 = t78 + t79; t119 = t80 + t81; t58 = t118 + t119; /* 2 */ hi[13][slot] = SHIFT(t58); t121 = t83 + t84; t122 = t85 + t86; t67 = t121 + t122; t49 = (t67 * 2) - t32; /* 3 */ hi[12][slot] = SHIFT(t49); t125 = t89 + t90; t126 = t91 + t92; t93 = t125 + t126; /* 4 */ hi[11][slot] = SHIFT(t93); t128 = t94 + t95; t129 = t96 + t97; t98 = t128 + t129; t68 = (t98 * 2) - t49; /* 5 */ hi[10][slot] = SHIFT(t68); t132 = t100 + t101; t133 = t102 + t103; t104 = t132 + t133; t82 = (t104 * 2) - t58; /* 6 */ hi[ 9][slot] = SHIFT(t82); t136 = t106 + t107; t137 = t108 + t109; t110 = t136 + t137; t87 = (t110 * 2) - t67; t77 = (t87 * 2) - t68; /* 7 */ hi[ 8][slot] = SHIFT(t77); t141 = MUL(t69 - t70, costab8); t142 = MUL(t71 - t72, costab24); t143 = t141 + t142; /* 8 */ hi[ 7][slot] = SHIFT(t143); /* 24 */ lo[ 8][slot] = SHIFT((MUL(t141 - t142, costab16) * 2) - t143); t144 = MUL(t73 - t74, costab8); t145 = MUL(t75 - t76, costab24); t146 = t144 + t145; t88 = (t146 * 2) - t77; /* 9 */ hi[ 6][slot] = SHIFT(t88); t148 = MUL(t78 - t79, costab8); t149 = MUL(t80 - t81, costab24); t150 = t148 + t149; t105 = (t150 * 2) - t82; /* 10 */ hi[ 5][slot] = SHIFT(t105); t152 = MUL(t83 - t84, costab8); t153 = MUL(t85 - t86, costab24); t154 = t152 + t153; t111 = (t154 * 2) - t87; t99 = (t111 * 2) - t88; /* 11 */ hi[ 4][slot] = SHIFT(t99); t157 = MUL(t89 - t90, costab8); t158 = MUL(t91 - t92, costab24); t159 = t157 + t158; t127 = (t159 * 2) - t93; /* 12 */ hi[ 3][slot] = SHIFT(t127); t160 = (MUL(t125 - t126, costab16) * 2) - t127; /* 20 */ lo[ 4][slot] = SHIFT(t160); /* 28 */ lo[12][slot] = SHIFT((((MUL(t157 - t158, costab16) * 2) - t159) * 2) - t160); t161 = MUL(t94 - t95, costab8); t162 = MUL(t96 - t97, costab24); t163 = t161 + t162; t130 = (t163 * 2) - t98; t112 = (t130 * 2) - t99; /* 13 */ hi[ 2][slot] = SHIFT(t112); t164 = (MUL(t128 - t129, costab16) * 2) - t130; t166 = MUL(t100 - t101, costab8); t167 = MUL(t102 - t103, costab24); t168 = t166 + t167; t134 = (t168 * 2) - t104; t120 = (t134 * 2) - t105; /* 14 */ hi[ 1][slot] = SHIFT(t120); t135 = (MUL(t118 - t119, costab16) * 2) - t120; /* 18 */ lo[ 2][slot] = SHIFT(t135); t169 = (MUL(t132 - t133, costab16) * 2) - t134; t151 = (t169 * 2) - t135; /* 22 */ lo[ 6][slot] = SHIFT(t151); t170 = (((MUL(t148 - t149, costab16) * 2) - t150) * 2) - t151; /* 26 */ lo[10][slot] = SHIFT(t170); /* 30 */ lo[14][slot] = SHIFT((((((MUL(t166 - t167, costab16) * 2) - t168) * 2) - t169) * 2) - t170); t171 = MUL(t106 - t107, costab8); t172 = MUL(t108 - t109, costab24); t173 = t171 + t172; t138 = (t173 * 2) - t110; t123 = (t138 * 2) - t111; t139 = (MUL(t121 - t122, costab16) * 2) - t123; t117 = (t123 * 2) - t112; /* 15 */ hi[ 0][slot] = SHIFT(t117); t124 = (MUL(t115 - t116, costab16) * 2) - t117; /* 17 */ lo[ 1][slot] = SHIFT(t124); t131 = (t139 * 2) - t124; /* 19 */ lo[ 3][slot] = SHIFT(t131); t140 = (t164 * 2) - t131; /* 21 */ lo[ 5][slot] = SHIFT(t140); t174 = (MUL(t136 - t137, costab16) * 2) - t138; t155 = (t174 * 2) - t139; t147 = (t155 * 2) - t140; /* 23 */ lo[ 7][slot] = SHIFT(t147); t156 = (((MUL(t144 - t145, costab16) * 2) - t146) * 2) - t147; /* 25 */ lo[ 9][slot] = SHIFT(t156); t175 = (((MUL(t152 - t153, costab16) * 2) - t154) * 2) - t155; t165 = (t175 * 2) - t156; /* 27 */ lo[11][slot] = SHIFT(t165); t176 = (((((MUL(t161 - t162, costab16) * 2) - t163) * 2) - t164) * 2) - t165; /* 29 */ lo[13][slot] = SHIFT(t176); /* 31 */ lo[15][slot] = SHIFT((((((((MUL(t171 - t172, costab16) * 2) - t173) * 2) - t174) * 2) - t175) * 2) - t176); /* * Totals: * 80 multiplies * 80 additions * 119 subtractions * 49 shifts (not counting SSO) */ } # undef MUL # undef SHIFT /* third SSO shift and/or D[] optimization preshift */ # if defined(OPT_SSO) # if MAD_F_FRACBITS != 28 # error "MAD_F_FRACBITS must be 28 to use OPT_SSO" # endif # define ML0(hi, lo, x, y) ((lo) = (x) * (y)) # define MLA(hi, lo, x, y) ((lo) += (x) * (y)) # define MLN(hi, lo) ((lo) = -(lo)) # define MLZ(hi, lo) ((void) (hi), (mad_fixed_t) (lo)) # define SHIFT(x) ((x) >> 2) # define PRESHIFT(x) ((MAD_F(x) + (1L << 13)) >> 14) # else # define ML0(hi, lo, x, y) MAD_F_ML0((hi), (lo), (x), (y)) # define MLA(hi, lo, x, y) MAD_F_MLA((hi), (lo), (x), (y)) # define MLN(hi, lo) MAD_F_MLN((hi), (lo)) # define MLZ(hi, lo) MAD_F_MLZ((hi), (lo)) # define SHIFT(x) (x) # if defined(MAD_F_SCALEBITS) # undef MAD_F_SCALEBITS # define MAD_F_SCALEBITS (MAD_F_FRACBITS - 12) # define PRESHIFT(x) (MAD_F(x) >> 12) # else # define PRESHIFT(x) MAD_F(x) # endif # endif static mad_fixed_t const D[17][32] = { # include "mad_D.dat" }; # if defined(ASO_SYNTH) void synth_full(struct mad_synth *, struct mad_frame const *, unsigned int, unsigned int); # else /* * NAME: synth->full() * DESCRIPTION: perform full frequency PCM synthesis */ static void synth_full(struct mad_synth *synth, struct mad_frame const *frame, unsigned int nch, unsigned int ns) { unsigned int phase, ch, s, sb, pe, po; mad_fixed_t *pcm1, *pcm2, (*filter)[2][2][16][8]; mad_fixed_t const (*sbsample)[36][32]; register mad_fixed_t (*fe)[8], (*fx)[8], (*fo)[8]; register mad_fixed_t const (*Dptr)[32], *ptr; register mad_fixed64hi_t hi; register mad_fixed64lo_t lo; for (ch = 0; ch < nch; ++ch) { sbsample = &frame->sbsample[ch]; filter = &synth->filter[ch]; phase = synth->phase; pcm1 = synth->pcm.samples[ch]; for (s = 0; s < ns; ++s) { dct32((*sbsample)[s], phase >> 1, (*filter)[0][phase & 1], (*filter)[1][phase & 1]); pe = phase & ~1; po = ((phase - 1) & 0xf) | 1; /* calculate 32 samples */ fe = &(*filter)[0][ phase & 1][0]; fx = &(*filter)[0][~phase & 1][0]; fo = &(*filter)[1][~phase & 1][0]; Dptr = &D[0]; ptr = *Dptr + po; ML0(hi, lo, (*fx)[0], ptr[ 0]); MLA(hi, lo, (*fx)[1], ptr[14]); MLA(hi, lo, (*fx)[2], ptr[12]); MLA(hi, lo, (*fx)[3], ptr[10]); MLA(hi, lo, (*fx)[4], ptr[ 8]); MLA(hi, lo, (*fx)[5], ptr[ 6]); MLA(hi, lo, (*fx)[6], ptr[ 4]); MLA(hi, lo, (*fx)[7], ptr[ 2]); MLN(hi, lo); ptr = *Dptr + pe; MLA(hi, lo, (*fe)[0], ptr[ 0]); MLA(hi, lo, (*fe)[1], ptr[14]); MLA(hi, lo, (*fe)[2], ptr[12]); MLA(hi, lo, (*fe)[3], ptr[10]); MLA(hi, lo, (*fe)[4], ptr[ 8]); MLA(hi, lo, (*fe)[5], ptr[ 6]); MLA(hi, lo, (*fe)[6], ptr[ 4]); MLA(hi, lo, (*fe)[7], ptr[ 2]); *pcm1++ = SHIFT(MLZ(hi, lo)); pcm2 = pcm1 + 30; for (sb = 1; sb < 16; ++sb) { ++fe; ++Dptr; /* D[32 - sb][i] == -D[sb][31 - i] */ ptr = *Dptr + po; ML0(hi, lo, (*fo)[0], ptr[ 0]); MLA(hi, lo, (*fo)[1], ptr[14]); MLA(hi, lo, (*fo)[2], ptr[12]); MLA(hi, lo, (*fo)[3], ptr[10]); MLA(hi, lo, (*fo)[4], ptr[ 8]); MLA(hi, lo, (*fo)[5], ptr[ 6]); MLA(hi, lo, (*fo)[6], ptr[ 4]); MLA(hi, lo, (*fo)[7], ptr[ 2]); MLN(hi, lo); ptr = *Dptr + pe; MLA(hi, lo, (*fe)[7], ptr[ 2]); MLA(hi, lo, (*fe)[6], ptr[ 4]); MLA(hi, lo, (*fe)[5], ptr[ 6]); MLA(hi, lo, (*fe)[4], ptr[ 8]); MLA(hi, lo, (*fe)[3], ptr[10]); MLA(hi, lo, (*fe)[2], ptr[12]); MLA(hi, lo, (*fe)[1], ptr[14]); MLA(hi, lo, (*fe)[0], ptr[ 0]); *pcm1++ = SHIFT(MLZ(hi, lo)); ptr = *Dptr - pe; ML0(hi, lo, (*fe)[0], ptr[31 - 16]); MLA(hi, lo, (*fe)[1], ptr[31 - 14]); MLA(hi, lo, (*fe)[2], ptr[31 - 12]); MLA(hi, lo, (*fe)[3], ptr[31 - 10]); MLA(hi, lo, (*fe)[4], ptr[31 - 8]); MLA(hi, lo, (*fe)[5], ptr[31 - 6]); MLA(hi, lo, (*fe)[6], ptr[31 - 4]); MLA(hi, lo, (*fe)[7], ptr[31 - 2]); ptr = *Dptr - po; MLA(hi, lo, (*fo)[7], ptr[31 - 2]); MLA(hi, lo, (*fo)[6], ptr[31 - 4]); MLA(hi, lo, (*fo)[5], ptr[31 - 6]); MLA(hi, lo, (*fo)[4], ptr[31 - 8]); MLA(hi, lo, (*fo)[3], ptr[31 - 10]); MLA(hi, lo, (*fo)[2], ptr[31 - 12]); MLA(hi, lo, (*fo)[1], ptr[31 - 14]); MLA(hi, lo, (*fo)[0], ptr[31 - 16]); *pcm2-- = SHIFT(MLZ(hi, lo)); ++fo; } ++Dptr; ptr = *Dptr + po; ML0(hi, lo, (*fo)[0], ptr[ 0]); MLA(hi, lo, (*fo)[1], ptr[14]); MLA(hi, lo, (*fo)[2], ptr[12]); MLA(hi, lo, (*fo)[3], ptr[10]); MLA(hi, lo, (*fo)[4], ptr[ 8]); MLA(hi, lo, (*fo)[5], ptr[ 6]); MLA(hi, lo, (*fo)[6], ptr[ 4]); MLA(hi, lo, (*fo)[7], ptr[ 2]); *pcm1 = SHIFT(-MLZ(hi, lo)); pcm1 += 16; phase = (phase + 1) % 16; } } } # endif /* * NAME: synth->half() * DESCRIPTION: perform half frequency PCM synthesis */ static void synth_half(struct mad_synth *synth, struct mad_frame const *frame, unsigned int nch, unsigned int ns) { unsigned int phase, ch, s, sb, pe, po; mad_fixed_t *pcm1, *pcm2, (*filter)[2][2][16][8]; mad_fixed_t const (*sbsample)[36][32]; register mad_fixed_t (*fe)[8], (*fx)[8], (*fo)[8]; register mad_fixed_t const (*Dptr)[32], *ptr; register mad_fixed64hi_t hi; register mad_fixed64lo_t lo; for (ch = 0; ch < nch; ++ch) { sbsample = &frame->sbsample[ch]; filter = &synth->filter[ch]; phase = synth->phase; pcm1 = synth->pcm.samples[ch]; for (s = 0; s < ns; ++s) { dct32((*sbsample)[s], phase >> 1, (*filter)[0][phase & 1], (*filter)[1][phase & 1]); pe = phase & ~1; po = ((phase - 1) & 0xf) | 1; /* calculate 16 samples */ fe = &(*filter)[0][ phase & 1][0]; fx = &(*filter)[0][~phase & 1][0]; fo = &(*filter)[1][~phase & 1][0]; Dptr = &D[0]; ptr = *Dptr + po; ML0(hi, lo, (*fx)[0], ptr[ 0]); MLA(hi, lo, (*fx)[1], ptr[14]); MLA(hi, lo, (*fx)[2], ptr[12]); MLA(hi, lo, (*fx)[3], ptr[10]); MLA(hi, lo, (*fx)[4], ptr[ 8]); MLA(hi, lo, (*fx)[5], ptr[ 6]); MLA(hi, lo, (*fx)[6], ptr[ 4]); MLA(hi, lo, (*fx)[7], ptr[ 2]); MLN(hi, lo); ptr = *Dptr + pe; MLA(hi, lo, (*fe)[0], ptr[ 0]); MLA(hi, lo, (*fe)[1], ptr[14]); MLA(hi, lo, (*fe)[2], ptr[12]); MLA(hi, lo, (*fe)[3], ptr[10]); MLA(hi, lo, (*fe)[4], ptr[ 8]); MLA(hi, lo, (*fe)[5], ptr[ 6]); MLA(hi, lo, (*fe)[6], ptr[ 4]); MLA(hi, lo, (*fe)[7], ptr[ 2]); *pcm1++ = SHIFT(MLZ(hi, lo)); pcm2 = pcm1 + 14; for (sb = 1; sb < 16; ++sb) { ++fe; ++Dptr; /* D[32 - sb][i] == -D[sb][31 - i] */ if (!(sb & 1)) { ptr = *Dptr + po; ML0(hi, lo, (*fo)[0], ptr[ 0]); MLA(hi, lo, (*fo)[1], ptr[14]); MLA(hi, lo, (*fo)[2], ptr[12]); MLA(hi, lo, (*fo)[3], ptr[10]); MLA(hi, lo, (*fo)[4], ptr[ 8]); MLA(hi, lo, (*fo)[5], ptr[ 6]); MLA(hi, lo, (*fo)[6], ptr[ 4]); MLA(hi, lo, (*fo)[7], ptr[ 2]); MLN(hi, lo); ptr = *Dptr + pe; MLA(hi, lo, (*fe)[7], ptr[ 2]); MLA(hi, lo, (*fe)[6], ptr[ 4]); MLA(hi, lo, (*fe)[5], ptr[ 6]); MLA(hi, lo, (*fe)[4], ptr[ 8]); MLA(hi, lo, (*fe)[3], ptr[10]); MLA(hi, lo, (*fe)[2], ptr[12]); MLA(hi, lo, (*fe)[1], ptr[14]); MLA(hi, lo, (*fe)[0], ptr[ 0]); *pcm1++ = SHIFT(MLZ(hi, lo)); ptr = *Dptr - po; ML0(hi, lo, (*fo)[7], ptr[31 - 2]); MLA(hi, lo, (*fo)[6], ptr[31 - 4]); MLA(hi, lo, (*fo)[5], ptr[31 - 6]); MLA(hi, lo, (*fo)[4], ptr[31 - 8]); MLA(hi, lo, (*fo)[3], ptr[31 - 10]); MLA(hi, lo, (*fo)[2], ptr[31 - 12]); MLA(hi, lo, (*fo)[1], ptr[31 - 14]); MLA(hi, lo, (*fo)[0], ptr[31 - 16]); ptr = *Dptr - pe; MLA(hi, lo, (*fe)[0], ptr[31 - 16]); MLA(hi, lo, (*fe)[1], ptr[31 - 14]); MLA(hi, lo, (*fe)[2], ptr[31 - 12]); MLA(hi, lo, (*fe)[3], ptr[31 - 10]); MLA(hi, lo, (*fe)[4], ptr[31 - 8]); MLA(hi, lo, (*fe)[5], ptr[31 - 6]); MLA(hi, lo, (*fe)[6], ptr[31 - 4]); MLA(hi, lo, (*fe)[7], ptr[31 - 2]); *pcm2-- = SHIFT(MLZ(hi, lo)); } ++fo; } ++Dptr; ptr = *Dptr + po; ML0(hi, lo, (*fo)[0], ptr[ 0]); MLA(hi, lo, (*fo)[1], ptr[14]); MLA(hi, lo, (*fo)[2], ptr[12]); MLA(hi, lo, (*fo)[3], ptr[10]); MLA(hi, lo, (*fo)[4], ptr[ 8]); MLA(hi, lo, (*fo)[5], ptr[ 6]); MLA(hi, lo, (*fo)[6], ptr[ 4]); MLA(hi, lo, (*fo)[7], ptr[ 2]); *pcm1 = SHIFT(-MLZ(hi, lo)); pcm1 += 8; phase = (phase + 1) % 16; } } } /* * NAME: synth->frame() * DESCRIPTION: perform PCM synthesis of frame subband samples */ void mad_synth_frame(struct mad_synth *synth, struct mad_frame const *frame) { unsigned int nch, ns; void (*synth_frame)(struct mad_synth *, struct mad_frame const *, unsigned int, unsigned int); nch = MAD_NCHANNELS(&frame->header); ns = MAD_NSBSAMPLES(&frame->header); synth->pcm.samplerate = frame->header.samplerate; synth->pcm.channels = nch; synth->pcm.length = 32 * ns; synth_frame = synth_full; if (frame->options & MAD_OPTION_HALFSAMPLERATE) { synth->pcm.samplerate /= 2; synth->pcm.length /= 2; synth_frame = synth_half; } synth_frame(synth, frame, nch, ns); synth->phase = (synth->phase + ns) % 16; } sources_5316/external/mp3/mad_layer12.c0000644000176700017670000003254310627342357016530 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: layer12.c,v 1.17 2004/02/05 09:02:39 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # ifdef HAVE_LIMITS_H # include # else # define CHAR_BIT 8 # endif # include "mad_fixed.h" # include "mad_bit.h" # include "mad_stream.h" # include "mad_frame.h" # include "mad_layer12.h" /* * scalefactor table * used in both Layer I and Layer II decoding */ static mad_fixed_t const sf_table[64] = { # include "mad_sf_table.dat" }; /* --- Layer I ------------------------------------------------------------- */ /* linear scaling table */ static mad_fixed_t const linear_table[14] = { MAD_F(0x15555555), /* 2^2 / (2^2 - 1) == 1.33333333333333 */ MAD_F(0x12492492), /* 2^3 / (2^3 - 1) == 1.14285714285714 */ MAD_F(0x11111111), /* 2^4 / (2^4 - 1) == 1.06666666666667 */ MAD_F(0x10842108), /* 2^5 / (2^5 - 1) == 1.03225806451613 */ MAD_F(0x10410410), /* 2^6 / (2^6 - 1) == 1.01587301587302 */ MAD_F(0x10204081), /* 2^7 / (2^7 - 1) == 1.00787401574803 */ MAD_F(0x10101010), /* 2^8 / (2^8 - 1) == 1.00392156862745 */ MAD_F(0x10080402), /* 2^9 / (2^9 - 1) == 1.00195694716243 */ MAD_F(0x10040100), /* 2^10 / (2^10 - 1) == 1.00097751710655 */ MAD_F(0x10020040), /* 2^11 / (2^11 - 1) == 1.00048851978505 */ MAD_F(0x10010010), /* 2^12 / (2^12 - 1) == 1.00024420024420 */ MAD_F(0x10008004), /* 2^13 / (2^13 - 1) == 1.00012208521548 */ MAD_F(0x10004001), /* 2^14 / (2^14 - 1) == 1.00006103888177 */ MAD_F(0x10002000) /* 2^15 / (2^15 - 1) == 1.00003051850948 */ }; /* * NAME: I_sample() * DESCRIPTION: decode one requantized Layer I sample from a bitstream */ static mad_fixed_t I_sample(struct mad_bitptr *ptr, unsigned int nb) { mad_fixed_t sample; sample = mad_bit_read(ptr, nb); /* invert most significant bit, extend sign, then scale to fixed format */ sample ^= 1 << (nb - 1); sample |= -(sample & (1 << (nb - 1))); sample <<= MAD_F_FRACBITS - (nb - 1); /* requantize the sample */ /* s'' = (2^nb / (2^nb - 1)) * (s''' + 2^(-nb + 1)) */ sample += MAD_F_ONE >> (nb - 1); return mad_f_mul(sample, linear_table[nb - 2]); /* s' = factor * s'' */ /* (to be performed by caller) */ } /* * NAME: layer->I() * DESCRIPTION: decode a single Layer I frame */ int mad_layer_I(struct mad_stream *stream, struct mad_frame *frame) { struct mad_header *header = &frame->header; unsigned int nch, bound, ch, s, sb, nb; unsigned char allocation[2][32], scalefactor[2][32]; nch = MAD_NCHANNELS(header); bound = 32; if (header->mode == MAD_MODE_JOINT_STEREO) { header->flags |= MAD_FLAG_I_STEREO; bound = 4 + header->mode_extension * 4; } /* check CRC word */ if (header->flags & MAD_FLAG_PROTECTION) { header->crc_check = mad_bit_crc(stream->ptr, 4 * (bound * nch + (32 - bound)), header->crc_check); if (header->crc_check != header->crc_target && !(frame->options & MAD_OPTION_IGNORECRC)) { stream->error = MAD_ERROR_BADCRC; return -1; } } /* decode bit allocations */ for (sb = 0; sb < bound; ++sb) { for (ch = 0; ch < nch; ++ch) { nb = mad_bit_read(&stream->ptr, 4); if (nb == 15) { stream->error = MAD_ERROR_BADBITALLOC; return -1; } allocation[ch][sb] = nb ? nb + 1 : 0; } } for (sb = bound; sb < 32; ++sb) { nb = mad_bit_read(&stream->ptr, 4); if (nb == 15) { stream->error = MAD_ERROR_BADBITALLOC; return -1; } allocation[0][sb] = allocation[1][sb] = nb ? nb + 1 : 0; } /* decode scalefactors */ for (sb = 0; sb < 32; ++sb) { for (ch = 0; ch < nch; ++ch) { if (allocation[ch][sb]) { scalefactor[ch][sb] = mad_bit_read(&stream->ptr, 6); # if defined(OPT_STRICT) /* * Scalefactor index 63 does not appear in Table B.1 of * ISO/IEC 11172-3. Nonetheless, other implementations accept it, * so we only reject it if OPT_STRICT is defined. */ if (scalefactor[ch][sb] == 63) { stream->error = MAD_ERROR_BADSCALEFACTOR; return -1; } # endif } } } /* decode samples */ for (s = 0; s < 12; ++s) { for (sb = 0; sb < bound; ++sb) { for (ch = 0; ch < nch; ++ch) { nb = allocation[ch][sb]; frame->sbsample[ch][s][sb] = nb ? mad_f_mul(I_sample(&stream->ptr, nb), sf_table[scalefactor[ch][sb]]) : 0; } } for (sb = bound; sb < 32; ++sb) { if ((nb = allocation[0][sb])) { mad_fixed_t sample; sample = I_sample(&stream->ptr, nb); for (ch = 0; ch < nch; ++ch) { frame->sbsample[ch][s][sb] = mad_f_mul(sample, sf_table[scalefactor[ch][sb]]); } } else { for (ch = 0; ch < nch; ++ch) frame->sbsample[ch][s][sb] = 0; } } } return 0; } /* --- Layer II ------------------------------------------------------------ */ /* possible quantization per subband table */ static struct { unsigned int sblimit; unsigned char const offsets[30]; } const sbquant_table[5] = { /* ISO/IEC 11172-3 Table B.2a */ { 27, { 7, 7, 7, 6, 6, 6, 6, 6, 6, 6, 6, 3, 3, 3, 3, 3, /* 0 */ 3, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0 } }, /* ISO/IEC 11172-3 Table B.2b */ { 30, { 7, 7, 7, 6, 6, 6, 6, 6, 6, 6, 6, 3, 3, 3, 3, 3, /* 1 */ 3, 3, 3, 3, 3, 3, 3, 0, 0, 0, 0, 0, 0, 0 } }, /* ISO/IEC 11172-3 Table B.2c */ { 8, { 5, 5, 2, 2, 2, 2, 2, 2 } }, /* 2 */ /* ISO/IEC 11172-3 Table B.2d */ { 12, { 5, 5, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2 } }, /* 3 */ /* ISO/IEC 13818-3 Table B.1 */ { 30, { 4, 4, 4, 4, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, /* 4 */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 } } }; /* bit allocation table */ static struct { unsigned short nbal; unsigned short offset; } const bitalloc_table[8] = { { 2, 0 }, /* 0 */ { 2, 3 }, /* 1 */ { 3, 3 }, /* 2 */ { 3, 1 }, /* 3 */ { 4, 2 }, /* 4 */ { 4, 3 }, /* 5 */ { 4, 4 }, /* 6 */ { 4, 5 } /* 7 */ }; /* offsets into quantization class table */ static unsigned char const offset_table[6][15] = { { 0, 1, 16 }, /* 0 */ { 0, 1, 2, 3, 4, 5, 16 }, /* 1 */ { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14 }, /* 2 */ { 0, 1, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 }, /* 3 */ { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 16 }, /* 4 */ { 0, 2, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16 } /* 5 */ }; /* quantization class table */ static struct quantclass { unsigned short nlevels; unsigned char group; unsigned char bits; mad_fixed_t C; mad_fixed_t D; } const qc_table[17] = { # include "mad_qc_table.dat" }; /* * NAME: II_samples() * DESCRIPTION: decode three requantized Layer II samples from a bitstream */ static void II_samples(struct mad_bitptr *ptr, struct quantclass const *quantclass, mad_fixed_t output[3]) { unsigned int nb, s, sample[3]; if ((nb = quantclass->group)) { unsigned int c, nlevels; /* degrouping */ c = mad_bit_read(ptr, quantclass->bits); nlevels = quantclass->nlevels; for (s = 0; s < 3; ++s) { sample[s] = c % nlevels; c /= nlevels; } } else { nb = quantclass->bits; for (s = 0; s < 3; ++s) sample[s] = mad_bit_read(ptr, nb); } for (s = 0; s < 3; ++s) { mad_fixed_t requantized; /* invert most significant bit, extend sign, then scale to fixed format */ requantized = sample[s] ^ (1 << (nb - 1)); requantized |= -(requantized & (1 << (nb - 1))); requantized <<= MAD_F_FRACBITS - (nb - 1); /* requantize the sample */ /* s'' = C * (s''' + D) */ output[s] = mad_f_mul(requantized + quantclass->D, quantclass->C); /* s' = factor * s'' */ /* (to be performed by caller) */ } } /* * NAME: layer->II() * DESCRIPTION: decode a single Layer II frame */ int mad_layer_II(struct mad_stream *stream, struct mad_frame *frame) { struct mad_header *header = &frame->header; struct mad_bitptr start; unsigned int index, sblimit, nbal, nch, bound, gr, ch, s, sb; unsigned char const *offsets; unsigned char allocation[2][32], scfsi[2][32], scalefactor[2][32][3]; mad_fixed_t samples[3]; nch = MAD_NCHANNELS(header); if (header->flags & MAD_FLAG_LSF_EXT) index = 4; else if (header->flags & MAD_FLAG_FREEFORMAT) goto freeformat; else { unsigned long bitrate_per_channel; bitrate_per_channel = header->bitrate; if (nch == 2) { bitrate_per_channel /= 2; # if defined(OPT_STRICT) /* * ISO/IEC 11172-3 allows only single channel mode for 32, 48, 56, and * 80 kbps bitrates in Layer II, but some encoders ignore this * restriction. We enforce it if OPT_STRICT is defined. */ if (bitrate_per_channel <= 28000 || bitrate_per_channel == 40000) { stream->error = MAD_ERROR_BADMODE; return -1; } # endif } else { /* nch == 1 */ if (bitrate_per_channel > 192000) { /* * ISO/IEC 11172-3 does not allow single channel mode for 224, 256, * 320, or 384 kbps bitrates in Layer II. */ stream->error = MAD_ERROR_BADMODE; return -1; } } if (bitrate_per_channel <= 48000) index = (header->samplerate == 32000) ? 3 : 2; else if (bitrate_per_channel <= 80000) index = 0; else { freeformat: index = (header->samplerate == 48000) ? 0 : 1; } } sblimit = sbquant_table[index].sblimit; offsets = sbquant_table[index].offsets; bound = 32; if (header->mode == MAD_MODE_JOINT_STEREO) { header->flags |= MAD_FLAG_I_STEREO; bound = 4 + header->mode_extension * 4; } if (bound > sblimit) bound = sblimit; start = stream->ptr; /* decode bit allocations */ for (sb = 0; sb < bound; ++sb) { nbal = bitalloc_table[offsets[sb]].nbal; for (ch = 0; ch < nch; ++ch) allocation[ch][sb] = mad_bit_read(&stream->ptr, nbal); } for (sb = bound; sb < sblimit; ++sb) { nbal = bitalloc_table[offsets[sb]].nbal; allocation[0][sb] = allocation[1][sb] = mad_bit_read(&stream->ptr, nbal); } /* decode scalefactor selection info */ for (sb = 0; sb < sblimit; ++sb) { for (ch = 0; ch < nch; ++ch) { if (allocation[ch][sb]) scfsi[ch][sb] = mad_bit_read(&stream->ptr, 2); } } /* check CRC word */ if (header->flags & MAD_FLAG_PROTECTION) { header->crc_check = mad_bit_crc(start, mad_bit_length(&start, &stream->ptr), header->crc_check); if (header->crc_check != header->crc_target && !(frame->options & MAD_OPTION_IGNORECRC)) { stream->error = MAD_ERROR_BADCRC; return -1; } } /* decode scalefactors */ for (sb = 0; sb < sblimit; ++sb) { for (ch = 0; ch < nch; ++ch) { if (allocation[ch][sb]) { scalefactor[ch][sb][0] = mad_bit_read(&stream->ptr, 6); switch (scfsi[ch][sb]) { case 2: scalefactor[ch][sb][2] = scalefactor[ch][sb][1] = scalefactor[ch][sb][0]; break; case 0: scalefactor[ch][sb][1] = mad_bit_read(&stream->ptr, 6); /* fall through */ case 1: case 3: scalefactor[ch][sb][2] = mad_bit_read(&stream->ptr, 6); } if (scfsi[ch][sb] & 1) scalefactor[ch][sb][1] = scalefactor[ch][sb][scfsi[ch][sb] - 1]; # if defined(OPT_STRICT) /* * Scalefactor index 63 does not appear in Table B.1 of * ISO/IEC 11172-3. Nonetheless, other implementations accept it, * so we only reject it if OPT_STRICT is defined. */ if (scalefactor[ch][sb][0] == 63 || scalefactor[ch][sb][1] == 63 || scalefactor[ch][sb][2] == 63) { stream->error = MAD_ERROR_BADSCALEFACTOR; return -1; } # endif } } } /* decode samples */ for (gr = 0; gr < 12; ++gr) { for (sb = 0; sb < bound; ++sb) { for (ch = 0; ch < nch; ++ch) { if ((index = allocation[ch][sb])) { index = offset_table[bitalloc_table[offsets[sb]].offset][index - 1]; II_samples(&stream->ptr, &qc_table[index], samples); for (s = 0; s < 3; ++s) { frame->sbsample[ch][3 * gr + s][sb] = mad_f_mul(samples[s], sf_table[scalefactor[ch][sb][gr / 4]]); } } else { for (s = 0; s < 3; ++s) frame->sbsample[ch][3 * gr + s][sb] = 0; } } } for (sb = bound; sb < sblimit; ++sb) { if ((index = allocation[0][sb])) { index = offset_table[bitalloc_table[offsets[sb]].offset][index - 1]; II_samples(&stream->ptr, &qc_table[index], samples); for (ch = 0; ch < nch; ++ch) { for (s = 0; s < 3; ++s) { frame->sbsample[ch][3 * gr + s][sb] = mad_f_mul(samples[s], sf_table[scalefactor[ch][sb][gr / 4]]); } } } else { for (ch = 0; ch < nch; ++ch) { for (s = 0; s < 3; ++s) frame->sbsample[ch][3 * gr + s][sb] = 0; } } } for (ch = 0; ch < nch; ++ch) { for (s = 0; s < 3; ++s) { for (sb = sblimit; sb < 32; ++sb) frame->sbsample[ch][3 * gr + s][sb] = 0; } } } return 0; } sources_5316/external/mp3/mad_timer.c0000644000176700017670000002454510627342357016374 0ustar paulpaul/* * libmad - MPEG audio decoder library * Copyright (C) 2000-2004 Underbit Technologies, Inc. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * $Id: timer.c,v 1.18 2004/01/23 09:41:33 rob Exp $ */ /*# ifdef HAVE_CONFIG_H*/ # include "mad_config.h" /*# endif*/ # include "mad_global.h" # include # ifdef HAVE_ASSERT_H # include # endif # include "mad_timer.h" mad_timer_t const mad_timer_zero = { 0, 0 }; /* * NAME: timer->compare() * DESCRIPTION: indicate relative order of two timers */ int mad_timer_compare(mad_timer_t timer1, mad_timer_t timer2) { signed long diff; diff = timer1.seconds - timer2.seconds; if (diff < 0) return -1; else if (diff > 0) return +1; diff = timer1.fraction - timer2.fraction; if (diff < 0) return -1; else if (diff > 0) return +1; return 0; } /* * NAME: timer->negate() * DESCRIPTION: invert the sign of a timer */ void mad_timer_negate(mad_timer_t *timer) { timer->seconds = -timer->seconds; if (timer->fraction) { timer->seconds -= 1; timer->fraction = MAD_TIMER_RESOLUTION - timer->fraction; } } /* * NAME: timer->abs() * DESCRIPTION: return the absolute value of a timer */ mad_timer_t mad_timer_abs(mad_timer_t timer) { if (timer.seconds < 0) mad_timer_negate(&timer); return timer; } /* * NAME: reduce_timer() * DESCRIPTION: carry timer fraction into seconds */ static void reduce_timer(mad_timer_t *timer) { timer->seconds += timer->fraction / MAD_TIMER_RESOLUTION; timer->fraction %= MAD_TIMER_RESOLUTION; } /* * NAME: gcd() * DESCRIPTION: compute greatest common denominator */ static unsigned long gcd(unsigned long num1, unsigned long num2) { unsigned long tmp; while (num2) { tmp = num2; num2 = num1 % num2; num1 = tmp; } return num1; } /* * NAME: reduce_rational() * DESCRIPTION: convert rational expression to lowest terms */ static void reduce_rational(unsigned long *numer, unsigned long *denom) { unsigned long factor; factor = gcd(*numer, *denom); assert(factor != 0); *numer /= factor; *denom /= factor; } /* * NAME: scale_rational() * DESCRIPTION: solve numer/denom == ?/scale avoiding overflowing */ static unsigned long scale_rational(unsigned long numer, unsigned long denom, unsigned long scale) { reduce_rational(&numer, &denom); reduce_rational(&scale, &denom); assert(denom != 0); if (denom < scale) return numer * (scale / denom) + numer * (scale % denom) / denom; if (denom < numer) return scale * (numer / denom) + scale * (numer % denom) / denom; return numer * scale / denom; } /* * NAME: timer->set() * DESCRIPTION: set timer to specific (positive) value */ void mad_timer_set(mad_timer_t *timer, unsigned long seconds, unsigned long numer, unsigned long denom) { timer->seconds = seconds; if (numer >= denom && denom > 0) { timer->seconds += numer / denom; numer %= denom; } switch (denom) { case 0: case 1: timer->fraction = 0; break; case MAD_TIMER_RESOLUTION: timer->fraction = numer; break; case 1000: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 1000); break; case 8000: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 8000); break; case 11025: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 11025); break; case 12000: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 12000); break; case 16000: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 16000); break; case 22050: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 22050); break; case 24000: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 24000); break; case 32000: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 32000); break; case 44100: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 44100); break; case 48000: timer->fraction = numer * (MAD_TIMER_RESOLUTION / 48000); break; default: timer->fraction = scale_rational(numer, denom, MAD_TIMER_RESOLUTION); break; } if (timer->fraction >= MAD_TIMER_RESOLUTION) reduce_timer(timer); } /* * NAME: timer->add() * DESCRIPTION: add one timer to another */ void mad_timer_add(mad_timer_t *timer, mad_timer_t incr) { timer->seconds += incr.seconds; timer->fraction += incr.fraction; if (timer->fraction >= MAD_TIMER_RESOLUTION) reduce_timer(timer); } /* * NAME: timer->multiply() * DESCRIPTION: multiply a timer by a scalar value */ void mad_timer_multiply(mad_timer_t *timer, signed long scalar) { mad_timer_t addend; unsigned long factor; factor = scalar; if (scalar < 0) { factor = -scalar; mad_timer_negate(timer); } addend = *timer; *timer = mad_timer_zero; while (factor) { if (factor & 1) mad_timer_add(timer, addend); mad_timer_add(&addend, addend); factor >>= 1; } } /* * NAME: timer->count() * DESCRIPTION: return timer value in selected units */ signed long mad_timer_count(mad_timer_t timer, enum mad_units units) { switch (units) { case MAD_UNITS_HOURS: return timer.seconds / 60 / 60; case MAD_UNITS_MINUTES: return timer.seconds / 60; case MAD_UNITS_SECONDS: return timer.seconds; case MAD_UNITS_DECISECONDS: case MAD_UNITS_CENTISECONDS: case MAD_UNITS_MILLISECONDS: case MAD_UNITS_8000_HZ: case MAD_UNITS_11025_HZ: case MAD_UNITS_12000_HZ: case MAD_UNITS_16000_HZ: case MAD_UNITS_22050_HZ: case MAD_UNITS_24000_HZ: case MAD_UNITS_32000_HZ: case MAD_UNITS_44100_HZ: case MAD_UNITS_48000_HZ: case MAD_UNITS_24_FPS: case MAD_UNITS_25_FPS: case MAD_UNITS_30_FPS: case MAD_UNITS_48_FPS: case MAD_UNITS_50_FPS: case MAD_UNITS_60_FPS: case MAD_UNITS_75_FPS: return timer.seconds * (signed long) units + (signed long) scale_rational(timer.fraction, MAD_TIMER_RESOLUTION, units); case MAD_UNITS_23_976_FPS: case MAD_UNITS_24_975_FPS: case MAD_UNITS_29_97_FPS: case MAD_UNITS_47_952_FPS: case MAD_UNITS_49_95_FPS: case MAD_UNITS_59_94_FPS: return (mad_timer_count(timer, -units) + 1) * 1000 / 1001; } /* unsupported units */ return 0; } /* * NAME: timer->fraction() * DESCRIPTION: return fractional part of timer in arbitrary terms */ unsigned long mad_timer_fraction(mad_timer_t timer, unsigned long denom) { timer = mad_timer_abs(timer); switch (denom) { case 0: return timer.fraction ? MAD_TIMER_RESOLUTION / timer.fraction : MAD_TIMER_RESOLUTION + 1; case MAD_TIMER_RESOLUTION: return timer.fraction; default: return scale_rational(timer.fraction, MAD_TIMER_RESOLUTION, denom); } } /* * NAME: timer->string() * DESCRIPTION: write a string representation of a timer using a template */ void mad_timer_string(mad_timer_t timer, char *dest, char const *format, enum mad_units units, enum mad_units fracunits, unsigned long subparts) { unsigned long hours, minutes, seconds, sub; unsigned int frac; timer = mad_timer_abs(timer); seconds = timer.seconds; frac = sub = 0; switch (fracunits) { case MAD_UNITS_HOURS: case MAD_UNITS_MINUTES: case MAD_UNITS_SECONDS: break; case MAD_UNITS_DECISECONDS: case MAD_UNITS_CENTISECONDS: case MAD_UNITS_MILLISECONDS: case MAD_UNITS_8000_HZ: case MAD_UNITS_11025_HZ: case MAD_UNITS_12000_HZ: case MAD_UNITS_16000_HZ: case MAD_UNITS_22050_HZ: case MAD_UNITS_24000_HZ: case MAD_UNITS_32000_HZ: case MAD_UNITS_44100_HZ: case MAD_UNITS_48000_HZ: case MAD_UNITS_24_FPS: case MAD_UNITS_25_FPS: case MAD_UNITS_30_FPS: case MAD_UNITS_48_FPS: case MAD_UNITS_50_FPS: case MAD_UNITS_60_FPS: case MAD_UNITS_75_FPS: { unsigned long denom; denom = MAD_TIMER_RESOLUTION / fracunits; frac = timer.fraction / denom; sub = scale_rational(timer.fraction % denom, denom, subparts); } break; case MAD_UNITS_23_976_FPS: case MAD_UNITS_24_975_FPS: case MAD_UNITS_29_97_FPS: case MAD_UNITS_47_952_FPS: case MAD_UNITS_49_95_FPS: case MAD_UNITS_59_94_FPS: /* drop-frame encoding */ /* N.B. this is only well-defined for MAD_UNITS_29_97_FPS */ { unsigned long frame, cycle, d, m; frame = mad_timer_count(timer, fracunits); cycle = -fracunits * 60 * 10 - (10 - 1) * 2; d = frame / cycle; m = frame % cycle; frame += (10 - 1) * 2 * d; if (m > 2) frame += 2 * ((m - 2) / (cycle / 10)); frac = frame % -fracunits; seconds = frame / -fracunits; } break; } switch (units) { case MAD_UNITS_HOURS: minutes = seconds / 60; hours = minutes / 60; sprintf(dest, format, hours, (unsigned int) (minutes % 60), (unsigned int) (seconds % 60), frac, sub); break; case MAD_UNITS_MINUTES: minutes = seconds / 60; sprintf(dest, format, minutes, (unsigned int) (seconds % 60), frac, sub); break; case MAD_UNITS_SECONDS: sprintf(dest, format, seconds, frac, sub); break; case MAD_UNITS_23_976_FPS: case MAD_UNITS_24_975_FPS: case MAD_UNITS_29_97_FPS: case MAD_UNITS_47_952_FPS: case MAD_UNITS_49_95_FPS: case MAD_UNITS_59_94_FPS: if (fracunits < 0) { /* not yet implemented */ sub = 0; } /* fall through */ case MAD_UNITS_DECISECONDS: case MAD_UNITS_CENTISECONDS: case MAD_UNITS_MILLISECONDS: case MAD_UNITS_8000_HZ: case MAD_UNITS_11025_HZ: case MAD_UNITS_12000_HZ: case MAD_UNITS_16000_HZ: case MAD_UNITS_22050_HZ: case MAD_UNITS_24000_HZ: case MAD_UNITS_32000_HZ: case MAD_UNITS_44100_HZ: case MAD_UNITS_48000_HZ: case MAD_UNITS_24_FPS: case MAD_UNITS_25_FPS: case MAD_UNITS_30_FPS: case MAD_UNITS_48_FPS: case MAD_UNITS_50_FPS: case MAD_UNITS_60_FPS: case MAD_UNITS_75_FPS: sprintf(dest, format, mad_timer_count(timer, units), sub); break; } } sources_5316/external/flac/0000755000176700017670000000000011704272715014460 5ustar paulpaulsources_5316/external/flac/flac_FLAC_ordinals.h0000644000176700017670000000521210560556406020217 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__ORDINALS_H #define FLAC__ORDINALS_H #if !(defined(_MSC_VER) || defined(__BORLANDC__) || defined(__EMX__)) #include #endif typedef signed char FLAC__int8; typedef unsigned char FLAC__uint8; #if defined(_MSC_VER) || defined(__BORLANDC__) typedef __int16 FLAC__int16; typedef __int32 FLAC__int32; typedef __int64 FLAC__int64; typedef unsigned __int16 FLAC__uint16; typedef unsigned __int32 FLAC__uint32; typedef unsigned __int64 FLAC__uint64; #elif defined(__EMX__) typedef short FLAC__int16; typedef long FLAC__int32; typedef long long FLAC__int64; typedef unsigned short FLAC__uint16; typedef unsigned long FLAC__uint32; typedef unsigned long long FLAC__uint64; #else typedef int16_t FLAC__int16; typedef int32_t FLAC__int32; typedef int64_t FLAC__int64; typedef uint16_t FLAC__uint16; typedef uint32_t FLAC__uint32; typedef uint64_t FLAC__uint64; #endif typedef int FLAC__bool; typedef FLAC__uint8 FLAC__byte; #ifdef true #undef true #endif #ifdef false #undef false #endif #ifndef __cplusplus #define true 1 #define false 0 #endif #endif sources_5316/external/flac/flac_private_bitmath.h0000644000176700017670000000357210720607255021005 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__BITMATH_H #define FLAC__PRIVATE__BITMATH_H #include "flac_FLAC_ordinals.h" unsigned FLAC__bitmath_ilog2(FLAC__uint32 v); unsigned FLAC__bitmath_ilog2_wide(FLAC__uint64 v); unsigned FLAC__bitmath_silog2(int v); unsigned FLAC__bitmath_silog2_wide(FLAC__int64 v); #endif sources_5316/external/flac/flac_md5.c0000644000176700017670000003357110720650225016300 0ustar paulpaul#if HAVE_CONFIG_H # include #endif #include /* for malloc() */ #include /* for memcpy() */ #include "flac_private_autocpu.h" #include "flac_private_md5.h" #include "flac_share_alloc.h" #ifndef FLaC__INLINE #define FLaC__INLINE #endif /* * This code implements the MD5 message-digest algorithm. * The algorithm is due to Ron Rivest. This code was * written by Colin Plumb in 1993, no copyright is claimed. * This code is in the public domain; do with it what you wish. * * Equivalent code is available from RSA Data Security, Inc. * This code has been tested against that, and is equivalent, * except that you don't need to include two pages of legalese * with every copy. * * To compute the message digest of a chunk of bytes, declare an * MD5Context structure, pass it to MD5Init, call MD5Update as * needed on buffers full of bytes, and then call MD5Final, which * will fill a supplied 16-byte array with the digest. * * Changed so as no longer to depend on Colin Plumb's `usual.h' header * definitions; now uses stuff from dpkg's config.h. * - Ian Jackson . * Still in the public domain. * * Josh Coalson: made some changes to integrate with libFLAC. * Still in the public domain. */ /* The four core functions - F1 is optimized somewhat */ /* #define F1(x, y, z) (x & y | ~x & z) */ #define F1(x, y, z) (z ^ (x & (y ^ z))) #define F2(x, y, z) F1(z, x, y) #define F3(x, y, z) (x ^ y ^ z) #define F4(x, y, z) (y ^ (x | ~z)) /* This is the central step in the MD5 algorithm. */ #define MD5STEP(f,w,x,y,z,in,s) \ (w += f(x,y,z) + in, w = (w<>(32-s)) + x) /* * The core of the MD5 algorithm, this alters an existing MD5 hash to * reflect the addition of 16 longwords of new data. MD5Update blocks * the data and converts bytes into longwords for this routine. */ static void FLAC__MD5Transform(FLAC__uint32 buf[4], FLAC__uint32 const in[16]) { register FLAC__uint32 a, b, c, d; a = buf[0]; b = buf[1]; c = buf[2]; d = buf[3]; MD5STEP(F1, a, b, c, d, in[0] + 0xd76aa478, 7); MD5STEP(F1, d, a, b, c, in[1] + 0xe8c7b756, 12); MD5STEP(F1, c, d, a, b, in[2] + 0x242070db, 17); MD5STEP(F1, b, c, d, a, in[3] + 0xc1bdceee, 22); MD5STEP(F1, a, b, c, d, in[4] + 0xf57c0faf, 7); MD5STEP(F1, d, a, b, c, in[5] + 0x4787c62a, 12); MD5STEP(F1, c, d, a, b, in[6] + 0xa8304613, 17); MD5STEP(F1, b, c, d, a, in[7] + 0xfd469501, 22); MD5STEP(F1, a, b, c, d, in[8] + 0x698098d8, 7); MD5STEP(F1, d, a, b, c, in[9] + 0x8b44f7af, 12); MD5STEP(F1, c, d, a, b, in[10] + 0xffff5bb1, 17); MD5STEP(F1, b, c, d, a, in[11] + 0x895cd7be, 22); MD5STEP(F1, a, b, c, d, in[12] + 0x6b901122, 7); MD5STEP(F1, d, a, b, c, in[13] + 0xfd987193, 12); MD5STEP(F1, c, d, a, b, in[14] + 0xa679438e, 17); MD5STEP(F1, b, c, d, a, in[15] + 0x49b40821, 22); MD5STEP(F2, a, b, c, d, in[1] + 0xf61e2562, 5); MD5STEP(F2, d, a, b, c, in[6] + 0xc040b340, 9); MD5STEP(F2, c, d, a, b, in[11] + 0x265e5a51, 14); MD5STEP(F2, b, c, d, a, in[0] + 0xe9b6c7aa, 20); MD5STEP(F2, a, b, c, d, in[5] + 0xd62f105d, 5); MD5STEP(F2, d, a, b, c, in[10] + 0x02441453, 9); MD5STEP(F2, c, d, a, b, in[15] + 0xd8a1e681, 14); MD5STEP(F2, b, c, d, a, in[4] + 0xe7d3fbc8, 20); MD5STEP(F2, a, b, c, d, in[9] + 0x21e1cde6, 5); MD5STEP(F2, d, a, b, c, in[14] + 0xc33707d6, 9); MD5STEP(F2, c, d, a, b, in[3] + 0xf4d50d87, 14); MD5STEP(F2, b, c, d, a, in[8] + 0x455a14ed, 20); MD5STEP(F2, a, b, c, d, in[13] + 0xa9e3e905, 5); MD5STEP(F2, d, a, b, c, in[2] + 0xfcefa3f8, 9); MD5STEP(F2, c, d, a, b, in[7] + 0x676f02d9, 14); MD5STEP(F2, b, c, d, a, in[12] + 0x8d2a4c8a, 20); MD5STEP(F3, a, b, c, d, in[5] + 0xfffa3942, 4); MD5STEP(F3, d, a, b, c, in[8] + 0x8771f681, 11); MD5STEP(F3, c, d, a, b, in[11] + 0x6d9d6122, 16); MD5STEP(F3, b, c, d, a, in[14] + 0xfde5380c, 23); MD5STEP(F3, a, b, c, d, in[1] + 0xa4beea44, 4); MD5STEP(F3, d, a, b, c, in[4] + 0x4bdecfa9, 11); MD5STEP(F3, c, d, a, b, in[7] + 0xf6bb4b60, 16); MD5STEP(F3, b, c, d, a, in[10] + 0xbebfbc70, 23); MD5STEP(F3, a, b, c, d, in[13] + 0x289b7ec6, 4); MD5STEP(F3, d, a, b, c, in[0] + 0xeaa127fa, 11); MD5STEP(F3, c, d, a, b, in[3] + 0xd4ef3085, 16); MD5STEP(F3, b, c, d, a, in[6] + 0x04881d05, 23); MD5STEP(F3, a, b, c, d, in[9] + 0xd9d4d039, 4); MD5STEP(F3, d, a, b, c, in[12] + 0xe6db99e5, 11); MD5STEP(F3, c, d, a, b, in[15] + 0x1fa27cf8, 16); MD5STEP(F3, b, c, d, a, in[2] + 0xc4ac5665, 23); MD5STEP(F4, a, b, c, d, in[0] + 0xf4292244, 6); MD5STEP(F4, d, a, b, c, in[7] + 0x432aff97, 10); MD5STEP(F4, c, d, a, b, in[14] + 0xab9423a7, 15); MD5STEP(F4, b, c, d, a, in[5] + 0xfc93a039, 21); MD5STEP(F4, a, b, c, d, in[12] + 0x655b59c3, 6); MD5STEP(F4, d, a, b, c, in[3] + 0x8f0ccc92, 10); MD5STEP(F4, c, d, a, b, in[10] + 0xffeff47d, 15); MD5STEP(F4, b, c, d, a, in[1] + 0x85845dd1, 21); MD5STEP(F4, a, b, c, d, in[8] + 0x6fa87e4f, 6); MD5STEP(F4, d, a, b, c, in[15] + 0xfe2ce6e0, 10); MD5STEP(F4, c, d, a, b, in[6] + 0xa3014314, 15); MD5STEP(F4, b, c, d, a, in[13] + 0x4e0811a1, 21); MD5STEP(F4, a, b, c, d, in[4] + 0xf7537e82, 6); MD5STEP(F4, d, a, b, c, in[11] + 0xbd3af235, 10); MD5STEP(F4, c, d, a, b, in[2] + 0x2ad7d2bb, 15); MD5STEP(F4, b, c, d, a, in[9] + 0xeb86d391, 21); buf[0] += a; buf[1] += b; buf[2] += c; buf[3] += d; } #if WORDS_BIGENDIAN //@@@@@@ OPT: use bswap/intrinsics static void byteSwap(FLAC__uint32 *buf, unsigned words) { register FLAC__uint32 x; do { x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); } while (--words); } static void byteSwapX16(FLAC__uint32 *buf) { register FLAC__uint32 x; x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf++ = (x >> 16) | (x << 16); x = *buf; x = ((x << 8) & 0xff00ff00) | ((x >> 8) & 0x00ff00ff); *buf = (x >> 16) | (x << 16); } #else #define byteSwap(buf, words) #define byteSwapX16(buf) #endif /* * Update context to reflect the concatenation of another buffer full * of bytes. */ static void FLAC__MD5Update(FLAC__MD5Context *ctx, FLAC__byte const *buf, unsigned len) { FLAC__uint32 t; /* Update byte count */ t = ctx->bytes[0]; if ((ctx->bytes[0] = t + len) < t) ctx->bytes[1]++; /* Carry from low to high */ t = 64 - (t & 0x3f); /* Space available in ctx->in (at least 1) */ if (t > len) { memcpy((FLAC__byte *)ctx->in + 64 - t, buf, len); return; } /* First chunk is an odd size */ memcpy((FLAC__byte *)ctx->in + 64 - t, buf, t); byteSwapX16(ctx->in); FLAC__MD5Transform(ctx->buf, ctx->in); buf += t; len -= t; /* Process data in 64-byte chunks */ while (len >= 64) { memcpy(ctx->in, buf, 64); byteSwapX16(ctx->in); FLAC__MD5Transform(ctx->buf, ctx->in); buf += 64; len -= 64; } /* Handle any remaining bytes of data. */ memcpy(ctx->in, buf, len); } /* * Start MD5 accumulation. Set bit count to 0 and buffer to mysterious * initialization constants. */ void FLAC__MD5Init(FLAC__MD5Context *ctx) { ctx->buf[0] = 0x67452301; ctx->buf[1] = 0xefcdab89; ctx->buf[2] = 0x98badcfe; ctx->buf[3] = 0x10325476; ctx->bytes[0] = 0; ctx->bytes[1] = 0; ctx->internal_buf = 0; ctx->capacity = 0; } /* * Final wrapup - pad to 64-byte boundary with the bit pattern * 1 0* (64-bit count of bits processed, MSB-first) */ void FLAC__MD5Final(FLAC__byte digest[16], FLAC__MD5Context *ctx) { int count = ctx->bytes[0] & 0x3f; /* Number of bytes in ctx->in */ FLAC__byte *p = (FLAC__byte *)ctx->in + count; /* Set the first char of padding to 0x80. There is always room. */ *p++ = 0x80; /* Bytes of padding needed to make 56 bytes (-8..55) */ count = 56 - 1 - count; if (count < 0) { /* Padding forces an extra block */ memset(p, 0, count + 8); byteSwapX16(ctx->in); FLAC__MD5Transform(ctx->buf, ctx->in); p = (FLAC__byte *)ctx->in; count = 56; } memset(p, 0, count); byteSwap(ctx->in, 14); /* Append length in bits and transform */ ctx->in[14] = ctx->bytes[0] << 3; ctx->in[15] = ctx->bytes[1] << 3 | ctx->bytes[0] >> 29; FLAC__MD5Transform(ctx->buf, ctx->in); byteSwap(ctx->buf, 4); memcpy(digest, ctx->buf, 16); memset(ctx, 0, sizeof(ctx)); /* In case it's sensitive */ if(0 != ctx->internal_buf) { free(ctx->internal_buf); ctx->internal_buf = 0; ctx->capacity = 0; } } /* * Convert the incoming audio signal to a byte stream */ static void format_input_(FLAC__byte *buf, const FLAC__int32 * const signal[], unsigned channels, unsigned samples, unsigned bytes_per_sample) { unsigned channel, sample; register FLAC__int32 a_word; register FLAC__byte *buf_ = buf; #if WORDS_BIGENDIAN #else if(channels == 2 && bytes_per_sample == 2) { FLAC__int16 *buf1_ = ((FLAC__int16*)buf_) + 1; memcpy(buf_, signal[0], sizeof(FLAC__int32) * samples); for(sample = 0; sample < samples; sample++, buf1_+=2) *buf1_ = (FLAC__int16)signal[1][sample]; } else if(channels == 1 && bytes_per_sample == 2) { FLAC__int16 *buf1_ = (FLAC__int16*)buf_; for(sample = 0; sample < samples; sample++) *buf1_++ = (FLAC__int16)signal[0][sample]; } else #endif if(bytes_per_sample == 2) { if(channels == 2) { for(sample = 0; sample < samples; sample++) { a_word = signal[0][sample]; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; a_word = signal[1][sample]; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; } } else if(channels == 1) { for(sample = 0; sample < samples; sample++) { a_word = signal[0][sample]; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; } } else { for(sample = 0; sample < samples; sample++) { for(channel = 0; channel < channels; channel++) { a_word = signal[channel][sample]; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; } } } } else if(bytes_per_sample == 3) { if(channels == 2) { for(sample = 0; sample < samples; sample++) { a_word = signal[0][sample]; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; a_word = signal[1][sample]; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; } } else if(channels == 1) { for(sample = 0; sample < samples; sample++) { a_word = signal[0][sample]; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; } } else { for(sample = 0; sample < samples; sample++) { for(channel = 0; channel < channels; channel++) { a_word = signal[channel][sample]; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; } } } } else if(bytes_per_sample == 1) { if(channels == 2) { for(sample = 0; sample < samples; sample++) { a_word = signal[0][sample]; *buf_++ = (FLAC__byte)a_word; a_word = signal[1][sample]; *buf_++ = (FLAC__byte)a_word; } } else if(channels == 1) { for(sample = 0; sample < samples; sample++) { a_word = signal[0][sample]; *buf_++ = (FLAC__byte)a_word; } } else { for(sample = 0; sample < samples; sample++) { for(channel = 0; channel < channels; channel++) { a_word = signal[channel][sample]; *buf_++ = (FLAC__byte)a_word; } } } } else { /* bytes_per_sample == 4, maybe optimize more later */ for(sample = 0; sample < samples; sample++) { for(channel = 0; channel < channels; channel++) { a_word = signal[channel][sample]; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; a_word >>= 8; *buf_++ = (FLAC__byte)a_word; } } } } /* * Convert the incoming audio signal to a byte stream and FLAC__MD5Update it. */ FLAC__bool FLAC__MD5Accumulate(FLAC__MD5Context *ctx, const FLAC__int32 * const signal[], unsigned channels, unsigned samples, unsigned bytes_per_sample) { const size_t bytes_needed = (size_t)channels * (size_t)samples * (size_t)bytes_per_sample; /* overflow check */ if((size_t)channels > SIZE_MAX / (size_t)bytes_per_sample) return false; if((size_t)channels * (size_t)bytes_per_sample > SIZE_MAX / (size_t)samples) return false; if(ctx->capacity < bytes_needed) { FLAC__byte *tmp = (FLAC__byte*)realloc(ctx->internal_buf, bytes_needed); if(0 == tmp) { free(ctx->internal_buf); if(0 == (ctx->internal_buf = (FLAC__byte*)safe_malloc_(bytes_needed))) return false; } ctx->internal_buf = tmp; ctx->capacity = bytes_needed; } format_input_(ctx->internal_buf, signal, channels, samples, bytes_per_sample); FLAC__MD5Update(ctx, ctx->internal_buf, bytes_needed); return true; } sources_5316/external/flac/flac_private_window.h0000644000176700017670000000624310720607255020662 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__WINDOW_H #define FLAC__PRIVATE__WINDOW_H #ifdef HAVE_CONFIG_H #include #endif #include "flac_private_float.h" #include "flac_FLAC_format.h" #ifndef FLAC__INTEGER_ONLY_LIBRARY /* * FLAC__window_*() * -------------------------------------------------------------------- * Calculates window coefficients according to different apodization * functions. * * OUT window[0,L-1] * IN L (number of points in window) */ void FLAC__window_bartlett(FLAC__real *window, const FLAC__int32 L); void FLAC__window_bartlett_hann(FLAC__real *window, const FLAC__int32 L); void FLAC__window_blackman(FLAC__real *window, const FLAC__int32 L); void FLAC__window_blackman_harris_4term_92db_sidelobe(FLAC__real *window, const FLAC__int32 L); void FLAC__window_connes(FLAC__real *window, const FLAC__int32 L); void FLAC__window_flattop(FLAC__real *window, const FLAC__int32 L); void FLAC__window_gauss(FLAC__real *window, const FLAC__int32 L, const FLAC__real stddev); /* 0.0 < stddev <= 0.5 */ void FLAC__window_hamming(FLAC__real *window, const FLAC__int32 L); void FLAC__window_hann(FLAC__real *window, const FLAC__int32 L); void FLAC__window_kaiser_bessel(FLAC__real *window, const FLAC__int32 L); void FLAC__window_nuttall(FLAC__real *window, const FLAC__int32 L); void FLAC__window_rectangle(FLAC__real *window, const FLAC__int32 L); void FLAC__window_triangle(FLAC__real *window, const FLAC__int32 L); void FLAC__window_tukey(FLAC__real *window, const FLAC__int32 L, const FLAC__real p); void FLAC__window_welch(FLAC__real *window, const FLAC__int32 L); #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ #endif sources_5316/external/flac/flac_float.c0000644000176700017670000002210410720610370016703 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include "flac_FLAC_assert.h" #include "flac_private_float.h" #ifdef FLAC__INTEGER_ONLY_LIBRARY /* adjust for compilers that can't understand using LLU suffix for uint64_t literals */ #ifdef _MSC_VER #define FLAC__U64L(x) x #else #define FLAC__U64L(x) x##LLU #endif const FLAC__fixedpoint FLAC__FP_ZERO = 0; const FLAC__fixedpoint FLAC__FP_ONE_HALF = 0x00008000; const FLAC__fixedpoint FLAC__FP_ONE = 0x00010000; const FLAC__fixedpoint FLAC__FP_LN2 = 45426; const FLAC__fixedpoint FLAC__FP_E = 178145; /* Lookup tables for Knuth's logarithm algorithm */ #define LOG2_LOOKUP_PRECISION 16 static const FLAC__uint32 log2_lookup[][LOG2_LOOKUP_PRECISION] = { { /* * 0 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ 0x00000001, /* lg(4/3) = */ 0x00000000, /* lg(8/7) = */ 0x00000000, /* lg(16/15) = */ 0x00000000, /* lg(32/31) = */ 0x00000000, /* lg(64/63) = */ 0x00000000, /* lg(128/127) = */ 0x00000000, /* lg(256/255) = */ 0x00000000, /* lg(512/511) = */ 0x00000000, /* lg(1024/1023) = */ 0x00000000, /* lg(2048/2047) = */ 0x00000000, /* lg(4096/4095) = */ 0x00000000, /* lg(8192/8191) = */ 0x00000000, /* lg(16384/16383) = */ 0x00000000, /* lg(32768/32767) = */ 0x00000000 }, { /* * 4 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ 0x00000010, /* lg(4/3) = */ 0x00000007, /* lg(8/7) = */ 0x00000003, /* lg(16/15) = */ 0x00000001, /* lg(32/31) = */ 0x00000001, /* lg(64/63) = */ 0x00000000, /* lg(128/127) = */ 0x00000000, /* lg(256/255) = */ 0x00000000, /* lg(512/511) = */ 0x00000000, /* lg(1024/1023) = */ 0x00000000, /* lg(2048/2047) = */ 0x00000000, /* lg(4096/4095) = */ 0x00000000, /* lg(8192/8191) = */ 0x00000000, /* lg(16384/16383) = */ 0x00000000, /* lg(32768/32767) = */ 0x00000000 }, { /* * 8 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ 0x00000100, /* lg(4/3) = */ 0x0000006a, /* lg(8/7) = */ 0x00000031, /* lg(16/15) = */ 0x00000018, /* lg(32/31) = */ 0x0000000c, /* lg(64/63) = */ 0x00000006, /* lg(128/127) = */ 0x00000003, /* lg(256/255) = */ 0x00000001, /* lg(512/511) = */ 0x00000001, /* lg(1024/1023) = */ 0x00000000, /* lg(2048/2047) = */ 0x00000000, /* lg(4096/4095) = */ 0x00000000, /* lg(8192/8191) = */ 0x00000000, /* lg(16384/16383) = */ 0x00000000, /* lg(32768/32767) = */ 0x00000000 }, { /* * 12 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ 0x00001000, /* lg(4/3) = */ 0x000006a4, /* lg(8/7) = */ 0x00000315, /* lg(16/15) = */ 0x0000017d, /* lg(32/31) = */ 0x000000bc, /* lg(64/63) = */ 0x0000005d, /* lg(128/127) = */ 0x0000002e, /* lg(256/255) = */ 0x00000017, /* lg(512/511) = */ 0x0000000c, /* lg(1024/1023) = */ 0x00000006, /* lg(2048/2047) = */ 0x00000003, /* lg(4096/4095) = */ 0x00000001, /* lg(8192/8191) = */ 0x00000001, /* lg(16384/16383) = */ 0x00000000, /* lg(32768/32767) = */ 0x00000000 }, { /* * 16 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ 0x00010000, /* lg(4/3) = */ 0x00006a40, /* lg(8/7) = */ 0x00003151, /* lg(16/15) = */ 0x000017d6, /* lg(32/31) = */ 0x00000bba, /* lg(64/63) = */ 0x000005d1, /* lg(128/127) = */ 0x000002e6, /* lg(256/255) = */ 0x00000172, /* lg(512/511) = */ 0x000000b9, /* lg(1024/1023) = */ 0x0000005c, /* lg(2048/2047) = */ 0x0000002e, /* lg(4096/4095) = */ 0x00000017, /* lg(8192/8191) = */ 0x0000000c, /* lg(16384/16383) = */ 0x00000006, /* lg(32768/32767) = */ 0x00000003 }, { /* * 20 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ 0x00100000, /* lg(4/3) = */ 0x0006a3fe, /* lg(8/7) = */ 0x00031513, /* lg(16/15) = */ 0x00017d60, /* lg(32/31) = */ 0x0000bb9d, /* lg(64/63) = */ 0x00005d10, /* lg(128/127) = */ 0x00002e59, /* lg(256/255) = */ 0x00001721, /* lg(512/511) = */ 0x00000b8e, /* lg(1024/1023) = */ 0x000005c6, /* lg(2048/2047) = */ 0x000002e3, /* lg(4096/4095) = */ 0x00000171, /* lg(8192/8191) = */ 0x000000b9, /* lg(16384/16383) = */ 0x0000005c, /* lg(32768/32767) = */ 0x0000002e }, { /* * 24 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ 0x01000000, /* lg(4/3) = */ 0x006a3fe6, /* lg(8/7) = */ 0x00315130, /* lg(16/15) = */ 0x0017d605, /* lg(32/31) = */ 0x000bb9ca, /* lg(64/63) = */ 0x0005d0fc, /* lg(128/127) = */ 0x0002e58f, /* lg(256/255) = */ 0x0001720e, /* lg(512/511) = */ 0x0000b8d8, /* lg(1024/1023) = */ 0x00005c61, /* lg(2048/2047) = */ 0x00002e2d, /* lg(4096/4095) = */ 0x00001716, /* lg(8192/8191) = */ 0x00000b8b, /* lg(16384/16383) = */ 0x000005c5, /* lg(32768/32767) = */ 0x000002e3 }, { /* * 28 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ 0x10000000, /* lg(4/3) = */ 0x06a3fe5c, /* lg(8/7) = */ 0x03151301, /* lg(16/15) = */ 0x017d6049, /* lg(32/31) = */ 0x00bb9ca6, /* lg(64/63) = */ 0x005d0fba, /* lg(128/127) = */ 0x002e58f7, /* lg(256/255) = */ 0x001720da, /* lg(512/511) = */ 0x000b8d87, /* lg(1024/1023) = */ 0x0005c60b, /* lg(2048/2047) = */ 0x0002e2d7, /* lg(4096/4095) = */ 0x00017160, /* lg(8192/8191) = */ 0x0000b8ad, /* lg(16384/16383) = */ 0x00005c56, /* lg(32768/32767) = */ 0x00002e2b } }; #if 0 static const FLAC__uint64 log2_lookup_wide[] = { { /* * 32 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ FLAC__U64L(0x100000000), /* lg(4/3) = */ FLAC__U64L(0x6a3fe5c6), /* lg(8/7) = */ FLAC__U64L(0x31513015), /* lg(16/15) = */ FLAC__U64L(0x17d60497), /* lg(32/31) = */ FLAC__U64L(0x0bb9ca65), /* lg(64/63) = */ FLAC__U64L(0x05d0fba2), /* lg(128/127) = */ FLAC__U64L(0x02e58f74), /* lg(256/255) = */ FLAC__U64L(0x01720d9c), /* lg(512/511) = */ FLAC__U64L(0x00b8d875), /* lg(1024/1023) = */ FLAC__U64L(0x005c60aa), /* lg(2048/2047) = */ FLAC__U64L(0x002e2d72), /* lg(4096/4095) = */ FLAC__U64L(0x00171600), /* lg(8192/8191) = */ FLAC__U64L(0x000b8ad2), /* lg(16384/16383) = */ FLAC__U64L(0x0005c55d), /* lg(32768/32767) = */ FLAC__U64L(0x0002e2ac) }, { /* * 48 fraction bits */ /* undefined */ 0x00000000, /* lg(2/1) = */ FLAC__U64L(0x1000000000000), /* lg(4/3) = */ FLAC__U64L(0x6a3fe5c60429), /* lg(8/7) = */ FLAC__U64L(0x315130157f7a), /* lg(16/15) = */ FLAC__U64L(0x17d60496cfbb), /* lg(32/31) = */ FLAC__U64L(0xbb9ca64ecac), /* lg(64/63) = */ FLAC__U64L(0x5d0fba187cd), /* lg(128/127) = */ FLAC__U64L(0x2e58f7441ee), /* lg(256/255) = */ FLAC__U64L(0x1720d9c06a8), /* lg(512/511) = */ FLAC__U64L(0xb8d8752173), /* lg(1024/1023) = */ FLAC__U64L(0x5c60aa252e), /* lg(2048/2047) = */ FLAC__U64L(0x2e2d71b0d8), /* lg(4096/4095) = */ FLAC__U64L(0x1716001719), /* lg(8192/8191) = */ FLAC__U64L(0xb8ad1de1b), /* lg(16384/16383) = */ FLAC__U64L(0x5c55d640d), /* lg(32768/32767) = */ FLAC__U64L(0x2e2abcf52) } }; #endif FLAC__uint32 FLAC__fixedpoint_log2(FLAC__uint32 x, unsigned fracbits, unsigned precision) { const FLAC__uint32 ONE = (1u << fracbits); const FLAC__uint32 *table = log2_lookup[fracbits >> 2]; FLAC__ASSERT(fracbits < 32); FLAC__ASSERT((fracbits & 0x3) == 0); if(x < ONE) return 0; if(precision > LOG2_LOOKUP_PRECISION) precision = LOG2_LOOKUP_PRECISION; /* Knuth's algorithm for computing logarithms, optimized for base-2 with lookup tables */ { FLAC__uint32 y = 0; FLAC__uint32 z = x >> 1, k = 1; while (x > ONE && k < precision) { if (x - z >= ONE) { x -= z; z = x >> k; y += table[k]; } else { z >>= 1; k++; } } return y; } } #endif /* defined FLAC__INTEGER_ONLY_LIBRARY */ sources_5316/external/flac/flac_private_metadata.h0000644000176700017670000000404410720607255021130 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__METADATA_H #define FLAC__PRIVATE__METADATA_H #include "flac_FLAC_metadata.h" /* WATCHOUT: all malloc()ed data in the block is free()ed; this may not * be a consistent state (e.g. PICTURE) or equivalent to the initial * state after FLAC__metadata_object_new() */ void FLAC__metadata_object_delete_data(FLAC__StreamMetadata *object); void FLAC__metadata_object_cuesheet_track_delete_data(FLAC__StreamMetadata_CueSheet_Track *object); #endif sources_5316/external/flac/Makefile0000644000176700017670000000163711704272715016127 0ustar paulpaul# Makefile of the library "external/flac" # Erez Volk, March 2007 # pb 20100108: include sys/melder.h # Paul Boersma, 14 January 2012 include ../../makefile.defs CPPFLAGS = -DFLAC__NOASM -I ../../sys # EREZ ? # On non-Intel, also define -DFLAC__CPU_UNKNOWN # On Intel, define -DFLAC__CPU_IA32 # On PowerPC, define -DFLAC__CPU_PPC # How/when are these relevant? OBJECTS = \ flac_bitmath.o \ flac_bitreader.o \ flac_bitwriter.o \ flac_cpu.o \ flac_crc.o \ flac_fixed.o \ flac_float.o \ flac_format.o \ flac_lpc.o \ flac_md5.o \ flac_memory.o \ flac_metadata_iterators.o \ flac_metadata_object.o \ flac_stream_decoder.o \ flac_stream_encoder.o \ flac_stream_encoder_framing.o \ flac_window.o .PHONY: all clean all: libflac.a clean: $(RM) $(OBJECTS) $(RM) libflac.a libflac.a: $(OBJECTS) touch libflac.a rm libflac.a ar cq libflac.a $(OBJECTS) $(RANLIB) libflac.a $(OBJECTS): *.h ../../sys/melder.h sources_5316/external/flac/flac_format.c0000644000176700017670000005114310720610573017100 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include #include /* for qsort() */ #include /* for memset() */ #include "flac_FLAC_assert.h" #include "flac_FLAC_format.h" #include "flac_private_format.h" #ifndef FLaC__INLINE #define FLaC__INLINE #endif #ifdef min #undef min #endif #define min(a,b) ((a)<(b)?(a):(b)) /* adjust for compilers that can't understand using LLU suffix for uint64_t literals */ #ifdef _MSC_VER #define FLAC__U64L(x) x #else #define FLAC__U64L(x) x##LLU #endif /* VERSION should come from configure */ FLAC_API const char *FLAC__VERSION_STRING = "1.2.1"; // ppgb 20071120 FLAC_API const char *FLAC__VENDOR_STRING = "reference libFLAC 1.2.1 20070917"; // ppgb 20071120 FLAC_API const FLAC__byte FLAC__STREAM_SYNC_STRING[4] = { 'f','L','a','C' }; FLAC_API const unsigned FLAC__STREAM_SYNC = 0x664C6143; FLAC_API const unsigned FLAC__STREAM_SYNC_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN = 16; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN = 16; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN = 24; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN = 24; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_SAMPLE_RATE_LEN = 20; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN = 3; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN = 5; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_TOTAL_SAMPLES_LEN = 36; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MD5SUM_LEN = 128; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_APPLICATION_ID_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_SEEKPOINT_SAMPLE_NUMBER_LEN = 64; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_SEEKPOINT_STREAM_OFFSET_LEN = 64; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_SEEKPOINT_FRAME_SAMPLES_LEN = 16; /* bits */ FLAC_API const FLAC__uint64 FLAC__STREAM_METADATA_SEEKPOINT_PLACEHOLDER = FLAC__U64L(0xffffffffffffffff); FLAC_API const unsigned FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_VORBIS_COMMENT_NUM_COMMENTS_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_INDEX_OFFSET_LEN = 64; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_INDEX_NUMBER_LEN = 8; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN = 3*8; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_OFFSET_LEN = 64; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_NUMBER_LEN = 8; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN = 12*8; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN = 1; /* bit */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN = 1; /* bit */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN = 6+13*8; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_NUM_INDICES_LEN = 8; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN = 128*8; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_LEAD_IN_LEN = 64; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN = 1; /* bit */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN = 7+258*8; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_NUM_TRACKS_LEN = 8; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_TYPE_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_MIME_TYPE_LENGTH_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_DESCRIPTION_LENGTH_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_COLORS_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_DATA_LENGTH_LEN = 32; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_IS_LAST_LEN = 1; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_TYPE_LEN = 7; /* bits */ FLAC_API const unsigned FLAC__STREAM_METADATA_LENGTH_LEN = 24; /* bits */ FLAC_API const unsigned FLAC__FRAME_HEADER_SYNC = 0x3ffe; FLAC_API const unsigned FLAC__FRAME_HEADER_SYNC_LEN = 14; /* bits */ FLAC_API const unsigned FLAC__FRAME_HEADER_RESERVED_LEN = 1; /* bits */ FLAC_API const unsigned FLAC__FRAME_HEADER_BLOCKING_STRATEGY_LEN = 1; /* bits */ FLAC_API const unsigned FLAC__FRAME_HEADER_BLOCK_SIZE_LEN = 4; /* bits */ FLAC_API const unsigned FLAC__FRAME_HEADER_SAMPLE_RATE_LEN = 4; /* bits */ FLAC_API const unsigned FLAC__FRAME_HEADER_CHANNEL_ASSIGNMENT_LEN = 4; /* bits */ FLAC_API const unsigned FLAC__FRAME_HEADER_BITS_PER_SAMPLE_LEN = 3; /* bits */ FLAC_API const unsigned FLAC__FRAME_HEADER_ZERO_PAD_LEN = 1; /* bits */ FLAC_API const unsigned FLAC__FRAME_HEADER_CRC_LEN = 8; /* bits */ FLAC_API const unsigned FLAC__FRAME_FOOTER_CRC_LEN = 16; /* bits */ FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_TYPE_LEN = 2; /* bits */ FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ORDER_LEN = 4; /* bits */ FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_PARAMETER_LEN = 4; /* bits */ FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_PARAMETER_LEN = 5; /* bits */ FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_RAW_LEN = 5; /* bits */ FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ESCAPE_PARAMETER = 15; /* == (1< FLAC__MAX_SAMPLE_RATE) { return false; } else return true; } FLAC_API FLAC__bool FLAC__format_sample_rate_is_subset(unsigned sample_rate) { if( !FLAC__format_sample_rate_is_valid(sample_rate) || ( sample_rate >= (1u << 16) && !(sample_rate % 1000 == 0 || sample_rate % 10 == 0) ) ) { return false; } else return true; } /* @@@@ add to unit tests; it is already indirectly tested by the metadata_object tests */ FLAC_API FLAC__bool FLAC__format_seektable_is_legal(const FLAC__StreamMetadata_SeekTable *seek_table) { unsigned i; FLAC__uint64 prev_sample_number = 0; FLAC__bool got_prev = false; FLAC__ASSERT(0 != seek_table); for(i = 0; i < seek_table->num_points; i++) { if(got_prev) { if( seek_table->points[i].sample_number != FLAC__STREAM_METADATA_SEEKPOINT_PLACEHOLDER && seek_table->points[i].sample_number <= prev_sample_number ) return false; } prev_sample_number = seek_table->points[i].sample_number; got_prev = true; } return true; } /* used as the sort predicate for qsort() */ static int seekpoint_compare_(const FLAC__StreamMetadata_SeekPoint *l, const FLAC__StreamMetadata_SeekPoint *r) { /* we don't just 'return l->sample_number - r->sample_number' since the result (FLAC__int64) might overflow an 'int' */ if(l->sample_number == r->sample_number) return 0; else if(l->sample_number < r->sample_number) return -1; else return 1; } /* @@@@ add to unit tests; it is already indirectly tested by the metadata_object tests */ FLAC_API unsigned FLAC__format_seektable_sort(FLAC__StreamMetadata_SeekTable *seek_table) { unsigned i, j; FLAC__bool first; FLAC__ASSERT(0 != seek_table); /* sort the seekpoints */ qsort(seek_table->points, seek_table->num_points, sizeof(FLAC__StreamMetadata_SeekPoint), (int (*)(const void *, const void *))seekpoint_compare_); /* uniquify the seekpoints */ first = true; for(i = j = 0; i < seek_table->num_points; i++) { if(seek_table->points[i].sample_number != FLAC__STREAM_METADATA_SEEKPOINT_PLACEHOLDER) { if(!first) { if(seek_table->points[i].sample_number == seek_table->points[j-1].sample_number) continue; } } first = false; seek_table->points[j++] = seek_table->points[i]; } for(i = j; i < seek_table->num_points; i++) { seek_table->points[i].sample_number = FLAC__STREAM_METADATA_SEEKPOINT_PLACEHOLDER; seek_table->points[i].stream_offset = 0; seek_table->points[i].frame_samples = 0; } return j; } /* * also disallows non-shortest-form encodings, c.f. * http://www.unicode.org/versions/corrigendum1.html * and a more clear explanation at the end of this section: * http://www.cl.cam.ac.uk/~mgk25/unicode.html#utf-8 */ static FLaC__INLINE unsigned utf8len_(const FLAC__byte *utf8) { FLAC__ASSERT(0 != utf8); if ((utf8[0] & 0x80) == 0) { return 1; } else if ((utf8[0] & 0xE0) == 0xC0 && (utf8[1] & 0xC0) == 0x80) { if ((utf8[0] & 0xFE) == 0xC0) /* overlong sequence check */ return 0; return 2; } else if ((utf8[0] & 0xF0) == 0xE0 && (utf8[1] & 0xC0) == 0x80 && (utf8[2] & 0xC0) == 0x80) { if (utf8[0] == 0xE0 && (utf8[1] & 0xE0) == 0x80) /* overlong sequence check */ return 0; /* illegal surrogates check (U+D800...U+DFFF and U+FFFE...U+FFFF) */ if (utf8[0] == 0xED && (utf8[1] & 0xE0) == 0xA0) /* D800-DFFF */ return 0; if (utf8[0] == 0xEF && utf8[1] == 0xBF && (utf8[2] & 0xFE) == 0xBE) /* FFFE-FFFF */ return 0; return 3; } else if ((utf8[0] & 0xF8) == 0xF0 && (utf8[1] & 0xC0) == 0x80 && (utf8[2] & 0xC0) == 0x80 && (utf8[3] & 0xC0) == 0x80) { if (utf8[0] == 0xF0 && (utf8[1] & 0xF0) == 0x80) /* overlong sequence check */ return 0; return 4; } else if ((utf8[0] & 0xFC) == 0xF8 && (utf8[1] & 0xC0) == 0x80 && (utf8[2] & 0xC0) == 0x80 && (utf8[3] & 0xC0) == 0x80 && (utf8[4] & 0xC0) == 0x80) { if (utf8[0] == 0xF8 && (utf8[1] & 0xF8) == 0x80) /* overlong sequence check */ return 0; return 5; } else if ((utf8[0] & 0xFE) == 0xFC && (utf8[1] & 0xC0) == 0x80 && (utf8[2] & 0xC0) == 0x80 && (utf8[3] & 0xC0) == 0x80 && (utf8[4] & 0xC0) == 0x80 && (utf8[5] & 0xC0) == 0x80) { if (utf8[0] == 0xFC && (utf8[1] & 0xFC) == 0x80) /* overlong sequence check */ return 0; return 6; } else { return 0; } } FLAC_API FLAC__bool FLAC__format_vorbiscomment_entry_name_is_legal(const char *name) { char c; for(c = *name; c; c = *(++name)) if(c < 0x20 || c == 0x3d || c > 0x7d) return false; return true; } FLAC_API FLAC__bool FLAC__format_vorbiscomment_entry_value_is_legal(const FLAC__byte *value, unsigned length) { if(length == (unsigned)(-1)) { while(*value) { unsigned n = utf8len_(value); if(n == 0) return false; value += n; } } else { const FLAC__byte *end = value + length; while(value < end) { unsigned n = utf8len_(value); if(n == 0) return false; value += n; } if(value != end) return false; } return true; } FLAC_API FLAC__bool FLAC__format_vorbiscomment_entry_is_legal(const FLAC__byte *entry, unsigned length) { const FLAC__byte *s, *end; for(s = entry, end = s + length; s < end && *s != '='; s++) { if(*s < 0x20 || *s > 0x7D) return false; } if(s == end) return false; s++; /* skip '=' */ while(s < end) { unsigned n = utf8len_(s); if(n == 0) return false; s += n; } if(s != end) return false; return true; } /* @@@@ add to unit tests; it is already indirectly tested by the metadata_object tests */ FLAC_API FLAC__bool FLAC__format_cuesheet_is_legal(const FLAC__StreamMetadata_CueSheet *cue_sheet, FLAC__bool check_cd_da_subset, const char **violation) { unsigned i, j; if(check_cd_da_subset) { if(cue_sheet->lead_in < 2 * 44100) { if(violation) *violation = "CD-DA cue sheet must have a lead-in length of at least 2 seconds"; return false; } if(cue_sheet->lead_in % 588 != 0) { if(violation) *violation = "CD-DA cue sheet lead-in length must be evenly divisible by 588 samples"; return false; } } if(cue_sheet->num_tracks == 0) { if(violation) *violation = "cue sheet must have at least one track (the lead-out)"; return false; } if(check_cd_da_subset && cue_sheet->tracks[cue_sheet->num_tracks-1].number != 170) { if(violation) *violation = "CD-DA cue sheet must have a lead-out track number 170 (0xAA)"; return false; } for(i = 0; i < cue_sheet->num_tracks; i++) { if(cue_sheet->tracks[i].number == 0) { if(violation) *violation = "cue sheet may not have a track number 0"; return false; } if(check_cd_da_subset) { if(!((cue_sheet->tracks[i].number >= 1 && cue_sheet->tracks[i].number <= 99) || cue_sheet->tracks[i].number == 170)) { if(violation) *violation = "CD-DA cue sheet track number must be 1-99 or 170"; return false; } } if(check_cd_da_subset && cue_sheet->tracks[i].offset % 588 != 0) { if(violation) { if(i == cue_sheet->num_tracks-1) /* the lead-out track... */ *violation = "CD-DA cue sheet lead-out offset must be evenly divisible by 588 samples"; else *violation = "CD-DA cue sheet track offset must be evenly divisible by 588 samples"; } return false; } if(i < cue_sheet->num_tracks - 1) { if(cue_sheet->tracks[i].num_indices == 0) { if(violation) *violation = "cue sheet track must have at least one index point"; return false; } if(cue_sheet->tracks[i].indices[0].number > 1) { if(violation) *violation = "cue sheet track's first index number must be 0 or 1"; return false; } } for(j = 0; j < cue_sheet->tracks[i].num_indices; j++) { if(check_cd_da_subset && cue_sheet->tracks[i].indices[j].offset % 588 != 0) { if(violation) *violation = "CD-DA cue sheet track index offset must be evenly divisible by 588 samples"; return false; } if(j > 0) { if(cue_sheet->tracks[i].indices[j].number != cue_sheet->tracks[i].indices[j-1].number + 1) { if(violation) *violation = "cue sheet track index numbers must increase by 1"; return false; } } } } return true; } /* @@@@ add to unit tests; it is already indirectly tested by the metadata_object tests */ FLAC_API FLAC__bool FLAC__format_picture_is_legal(const FLAC__StreamMetadata_Picture *picture, const char **violation) { char *p; FLAC__byte *b; for(p = picture->mime_type; *p; p++) { if(*p < 0x20 || *p > 0x7e) { if(violation) *violation = "MIME type string must contain only printable ASCII characters (0x20-0x7e)"; return false; } } for(b = picture->description; *b; ) { unsigned n = utf8len_(b); if(n == 0) { if(violation) *violation = "description string must be valid UTF-8"; return false; } b += n; } return true; } /* * These routines are private to libFLAC */ unsigned FLAC__format_get_max_rice_partition_order(unsigned blocksize, unsigned predictor_order) { return FLAC__format_get_max_rice_partition_order_from_blocksize_limited_max_and_predictor_order( FLAC__format_get_max_rice_partition_order_from_blocksize(blocksize), blocksize, predictor_order ); } unsigned FLAC__format_get_max_rice_partition_order_from_blocksize(unsigned blocksize) { unsigned max_rice_partition_order = 0; while(!(blocksize & 1)) { max_rice_partition_order++; blocksize >>= 1; } return min(FLAC__MAX_RICE_PARTITION_ORDER, max_rice_partition_order); } unsigned FLAC__format_get_max_rice_partition_order_from_blocksize_limited_max_and_predictor_order(unsigned limit, unsigned blocksize, unsigned predictor_order) { unsigned max_rice_partition_order = limit; while(max_rice_partition_order > 0 && (blocksize >> max_rice_partition_order) <= predictor_order) max_rice_partition_order--; FLAC__ASSERT( (max_rice_partition_order == 0 && blocksize >= predictor_order) || (max_rice_partition_order > 0 && blocksize >> max_rice_partition_order > predictor_order) ); return max_rice_partition_order; } void FLAC__format_entropy_coding_method_partitioned_rice_contents_init(FLAC__EntropyCodingMethod_PartitionedRiceContents *object) { FLAC__ASSERT(0 != object); object->parameters = 0; object->raw_bits = 0; object->capacity_by_order = 0; } void FLAC__format_entropy_coding_method_partitioned_rice_contents_clear(FLAC__EntropyCodingMethod_PartitionedRiceContents *object) { FLAC__ASSERT(0 != object); if(0 != object->parameters) free(object->parameters); if(0 != object->raw_bits) free(object->raw_bits); FLAC__format_entropy_coding_method_partitioned_rice_contents_init(object); } FLAC__bool FLAC__format_entropy_coding_method_partitioned_rice_contents_ensure_size(FLAC__EntropyCodingMethod_PartitionedRiceContents *object, unsigned max_partition_order) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->capacity_by_order > 0 || (0 == object->parameters && 0 == object->raw_bits)); if(object->capacity_by_order < max_partition_order) { if(0 == (object->parameters = (unsigned*)realloc(object->parameters, sizeof(unsigned)*(1 << max_partition_order)))) return false; if(0 == (object->raw_bits = (unsigned*)realloc(object->raw_bits, sizeof(unsigned)*(1 << max_partition_order)))) return false; memset(object->raw_bits, 0, sizeof(unsigned)*(1 << max_partition_order)); object->capacity_by_order = max_partition_order; } return true; } sources_5316/external/flac/flac_cpu.c0000644000176700017670000003526410720650063016403 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include "flac_private_autocpu.h" #include "flac_private_cpu.h" #include #include #if defined FLAC__CPU_IA32 # include #elif defined FLAC__CPU_PPC # if !defined FLAC__NO_ASM # if defined FLAC__SYS_DARWIN # include # include # include # include # include # ifndef CPU_SUBTYPE_POWERPC_970 # define CPU_SUBTYPE_POWERPC_970 ((cpu_subtype_t) 100) # endif # else /* FLAC__SYS_DARWIN */ # include # include static sigjmp_buf jmpbuf; static volatile sig_atomic_t canjump = 0; static void sigill_handler (int sig) { if (!canjump) { signal (sig, SIG_DFL); raise (sig); } canjump = 0; siglongjmp (jmpbuf, 1); } # endif /* FLAC__SYS_DARWIN */ # endif /* FLAC__NO_ASM */ #endif /* FLAC__CPU_PPC */ #if defined (__NetBSD__) || defined(__OpenBSD__) #include #include #include #endif #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__) || defined(__DragonFly__) #include #include #endif #if defined(__APPLE__) /* how to get sysctlbyname()? */ #endif /* these are flags in EDX of CPUID AX=00000001 */ static const unsigned FLAC__CPUINFO_IA32_CPUID_CMOV = 0x00008000; static const unsigned FLAC__CPUINFO_IA32_CPUID_MMX = 0x00800000; static const unsigned FLAC__CPUINFO_IA32_CPUID_FXSR = 0x01000000; static const unsigned FLAC__CPUINFO_IA32_CPUID_SSE = 0x02000000; static const unsigned FLAC__CPUINFO_IA32_CPUID_SSE2 = 0x04000000; /* these are flags in ECX of CPUID AX=00000001 */ static const unsigned FLAC__CPUINFO_IA32_CPUID_SSE3 = 0x00000001; static const unsigned FLAC__CPUINFO_IA32_CPUID_SSSE3 = 0x00000200; /* these are flags in EDX of CPUID AX=80000001 */ static const unsigned FLAC__CPUINFO_IA32_CPUID_EXTENDED_AMD_3DNOW = 0x80000000; static const unsigned FLAC__CPUINFO_IA32_CPUID_EXTENDED_AMD_EXT3DNOW = 0x40000000; static const unsigned FLAC__CPUINFO_IA32_CPUID_EXTENDED_AMD_EXTMMX = 0x00400000; /* * Extra stuff needed for detection of OS support for SSE on IA-32 */ #if defined(FLAC__CPU_IA32) && !defined FLAC__NO_ASM && defined FLAC__HAS_NASM && !defined FLAC__NO_SSE_OS && !defined FLAC__SSE_OS # if defined(__linux__) /* * If the OS doesn't support SSE, we will get here with a SIGILL. We * modify the return address to jump over the offending SSE instruction * and also the operation following it that indicates the instruction * executed successfully. In this way we use no global variables and * stay thread-safe. * * 3 + 3 + 6: * 3 bytes for "xorps xmm0,xmm0" * 3 bytes for estimate of how long the follwing "inc var" instruction is * 6 bytes extra in case our estimate is wrong * 12 bytes puts us in the NOP "landing zone" */ # undef USE_OBSOLETE_SIGCONTEXT_FLAVOR /* #define this to use the older signal handler method */ # ifdef USE_OBSOLETE_SIGCONTEXT_FLAVOR static void sigill_handler_sse_os(int signal, struct sigcontext sc) { (void)signal; sc.eip += 3 + 3 + 6; } # else # include static void sigill_handler_sse_os(int signal, siginfo_t *si, void *uc) { (void)signal, (void)si; ((ucontext_t*)uc)->uc_mcontext.gregs[14/*REG_EIP*/] += 3 + 3 + 6; } # endif # elif defined(_MSC_VER) # include # undef USE_TRY_CATCH_FLAVOR /* #define this to use the try/catch method for catching illegal opcode exception */ # ifdef USE_TRY_CATCH_FLAVOR # else LONG CALLBACK sigill_handler_sse_os(EXCEPTION_POINTERS *ep) { if(ep->ExceptionRecord->ExceptionCode == EXCEPTION_ILLEGAL_INSTRUCTION) { ep->ContextRecord->Eip += 3 + 3 + 6; return EXCEPTION_CONTINUE_EXECUTION; } return EXCEPTION_CONTINUE_SEARCH; } # endif # endif #endif void FLAC__cpu_info(FLAC__CPUInfo *info) { /* * IA32-specific */ #ifdef FLAC__CPU_IA32 info->type = FLAC__CPUINFO_TYPE_IA32; #if !defined FLAC__NO_ASM && defined FLAC__HAS_NASM info->use_asm = true; /* we assume a minimum of 80386 with FLAC__CPU_IA32 */ info->data.ia32.cpuid = FLAC__cpu_have_cpuid_asm_ia32()? true : false; info->data.ia32.bswap = info->data.ia32.cpuid; /* CPUID => BSWAP since it came after */ info->data.ia32.cmov = false; info->data.ia32.mmx = false; info->data.ia32.fxsr = false; info->data.ia32.sse = false; info->data.ia32.sse2 = false; info->data.ia32.sse3 = false; info->data.ia32.ssse3 = false; info->data.ia32._3dnow = false; info->data.ia32.ext3dnow = false; info->data.ia32.extmmx = false; if(info->data.ia32.cpuid) { /* http://www.sandpile.org/ia32/cpuid.htm */ FLAC__uint32 flags_edx, flags_ecx; FLAC__cpu_info_asm_ia32(&flags_edx, &flags_ecx); info->data.ia32.cmov = (flags_edx & FLAC__CPUINFO_IA32_CPUID_CMOV )? true : false; info->data.ia32.mmx = (flags_edx & FLAC__CPUINFO_IA32_CPUID_MMX )? true : false; info->data.ia32.fxsr = (flags_edx & FLAC__CPUINFO_IA32_CPUID_FXSR )? true : false; info->data.ia32.sse = (flags_edx & FLAC__CPUINFO_IA32_CPUID_SSE )? true : false; info->data.ia32.sse2 = (flags_edx & FLAC__CPUINFO_IA32_CPUID_SSE2 )? true : false; info->data.ia32.sse3 = (flags_ecx & FLAC__CPUINFO_IA32_CPUID_SSE3 )? true : false; info->data.ia32.ssse3 = (flags_ecx & FLAC__CPUINFO_IA32_CPUID_SSSE3)? true : false; #ifdef FLAC__USE_3DNOW flags_edx = FLAC__cpu_info_extended_amd_asm_ia32(); info->data.ia32._3dnow = (flags_edx & FLAC__CPUINFO_IA32_CPUID_EXTENDED_AMD_3DNOW )? true : false; info->data.ia32.ext3dnow = (flags_edx & FLAC__CPUINFO_IA32_CPUID_EXTENDED_AMD_EXT3DNOW)? true : false; info->data.ia32.extmmx = (flags_edx & FLAC__CPUINFO_IA32_CPUID_EXTENDED_AMD_EXTMMX )? true : false; #else info->data.ia32._3dnow = info->data.ia32.ext3dnow = info->data.ia32.extmmx = false; #endif #ifdef DEBUG fprintf(stderr, "CPU info (IA-32):\n"); fprintf(stderr, " CPUID ...... %c\n", info->data.ia32.cpuid ? 'Y' : 'n'); fprintf(stderr, " BSWAP ...... %c\n", info->data.ia32.bswap ? 'Y' : 'n'); fprintf(stderr, " CMOV ....... %c\n", info->data.ia32.cmov ? 'Y' : 'n'); fprintf(stderr, " MMX ........ %c\n", info->data.ia32.mmx ? 'Y' : 'n'); fprintf(stderr, " FXSR ....... %c\n", info->data.ia32.fxsr ? 'Y' : 'n'); fprintf(stderr, " SSE ........ %c\n", info->data.ia32.sse ? 'Y' : 'n'); fprintf(stderr, " SSE2 ....... %c\n", info->data.ia32.sse2 ? 'Y' : 'n'); fprintf(stderr, " SSE3 ....... %c\n", info->data.ia32.sse3 ? 'Y' : 'n'); fprintf(stderr, " SSSE3 ...... %c\n", info->data.ia32.ssse3 ? 'Y' : 'n'); fprintf(stderr, " 3DNow! ..... %c\n", info->data.ia32._3dnow ? 'Y' : 'n'); fprintf(stderr, " 3DNow!-ext . %c\n", info->data.ia32.ext3dnow? 'Y' : 'n'); fprintf(stderr, " 3DNow!-MMX . %c\n", info->data.ia32.extmmx ? 'Y' : 'n'); #endif /* * now have to check for OS support of SSE/SSE2 */ if(info->data.ia32.fxsr || info->data.ia32.sse || info->data.ia32.sse2) { #if defined FLAC__NO_SSE_OS /* assume user knows better than us; turn it off */ info->data.ia32.fxsr = info->data.ia32.sse = info->data.ia32.sse2 = info->data.ia32.sse3 = info->data.ia32.ssse3 = false; #elif defined FLAC__SSE_OS /* assume user knows better than us; leave as detected above */ #elif defined(__FreeBSD__) || defined(__FreeBSD_kernel__) || defined(__DragonFly__) || defined(__APPLE__) int sse = 0; size_t len; /* at least one of these must work: */ len = sizeof(sse); sse = sse || (sysctlbyname("hw.instruction_sse", &sse, &len, NULL, 0) == 0 && sse); len = sizeof(sse); sse = sse || (sysctlbyname("hw.optional.sse" , &sse, &len, NULL, 0) == 0 && sse); /* __APPLE__ ? */ if(!sse) info->data.ia32.fxsr = info->data.ia32.sse = info->data.ia32.sse2 = info->data.ia32.sse3 = info->data.ia32.ssse3 = false; #elif defined(__NetBSD__) || defined (__OpenBSD__) # if __NetBSD_Version__ >= 105250000 || (defined __OpenBSD__) int val = 0, mib[2] = { CTL_MACHDEP, CPU_SSE }; size_t len = sizeof(val); if(sysctl(mib, 2, &val, &len, NULL, 0) < 0 || !val) info->data.ia32.fxsr = info->data.ia32.sse = info->data.ia32.sse2 = info->data.ia32.sse3 = info->data.ia32.ssse3 = false; else { /* double-check SSE2 */ mib[1] = CPU_SSE2; len = sizeof(val); if(sysctl(mib, 2, &val, &len, NULL, 0) < 0 || !val) info->data.ia32.sse2 = info->data.ia32.sse3 = info->data.ia32.ssse3 = false; } # else info->data.ia32.fxsr = info->data.ia32.sse = info->data.ia32.sse2 = info->data.ia32.sse3 = info->data.ia32.ssse3 = false; # endif #elif defined(__linux__) int sse = 0; struct sigaction sigill_save; #ifdef USE_OBSOLETE_SIGCONTEXT_FLAVOR if(0 == sigaction(SIGILL, NULL, &sigill_save) && signal(SIGILL, (void (*)(int))sigill_handler_sse_os) != SIG_ERR) #else struct sigaction sigill_sse; sigill_sse.sa_sigaction = sigill_handler_sse_os; __sigemptyset(&sigill_sse.sa_mask); sigill_sse.sa_flags = SA_SIGINFO | SA_RESETHAND; /* SA_RESETHAND just in case our SIGILL return jump breaks, so we don't get stuck in a loop */ if(0 == sigaction(SIGILL, &sigill_sse, &sigill_save)) #endif { /* http://www.ibiblio.org/gferg/ldp/GCC-Inline-Assembly-HOWTO.html */ /* see sigill_handler_sse_os() for an explanation of the following: */ asm volatile ( "xorl %0,%0\n\t" /* for some reason, still need to do this to clear 'sse' var */ "xorps %%xmm0,%%xmm0\n\t" /* will cause SIGILL if unsupported by OS */ "incl %0\n\t" /* SIGILL handler will jump over this */ /* landing zone */ "nop\n\t" /* SIGILL jump lands here if "inc" is 9 bytes */ "nop\n\t" "nop\n\t" "nop\n\t" "nop\n\t" "nop\n\t" "nop\n\t" /* SIGILL jump lands here if "inc" is 3 bytes (expected) */ "nop\n\t" "nop" /* SIGILL jump lands here if "inc" is 1 byte */ : "=r"(sse) : "r"(sse) ); sigaction(SIGILL, &sigill_save, NULL); } if(!sse) info->data.ia32.fxsr = info->data.ia32.sse = info->data.ia32.sse2 = info->data.ia32.sse3 = info->data.ia32.ssse3 = false; #elif defined(_MSC_VER) # ifdef USE_TRY_CATCH_FLAVOR _try { __asm { # if _MSC_VER <= 1200 /* VC6 assembler doesn't know SSE, have to emit bytecode instead */ _emit 0x0F _emit 0x57 _emit 0xC0 # else xorps xmm0,xmm0 # endif } } _except(EXCEPTION_EXECUTE_HANDLER) { if (_exception_code() == STATUS_ILLEGAL_INSTRUCTION) info->data.ia32.fxsr = info->data.ia32.sse = info->data.ia32.sse2 = info->data.ia32.sse3 = info->data.ia32.ssse3 = false; } # else int sse = 0; LPTOP_LEVEL_EXCEPTION_FILTER save = SetUnhandledExceptionFilter(sigill_handler_sse_os); /* see GCC version above for explanation */ /* http://msdn2.microsoft.com/en-us/library/4ks26t93.aspx */ /* http://www.codeproject.com/cpp/gccasm.asp */ /* http://www.hick.org/~mmiller/msvc_inline_asm.html */ __asm { # if _MSC_VER <= 1200 /* VC6 assembler doesn't know SSE, have to emit bytecode instead */ _emit 0x0F _emit 0x57 _emit 0xC0 # else xorps xmm0,xmm0 # endif inc sse nop nop nop nop nop nop nop nop nop } SetUnhandledExceptionFilter(save); if(!sse) info->data.ia32.fxsr = info->data.ia32.sse = info->data.ia32.sse2 = info->data.ia32.sse3 = info->data.ia32.ssse3 = false; # endif #else /* no way to test, disable to be safe */ info->data.ia32.fxsr = info->data.ia32.sse = info->data.ia32.sse2 = info->data.ia32.sse3 = info->data.ia32.ssse3 = false; #endif #ifdef DEBUG fprintf(stderr, " SSE OS sup . %c\n", info->data.ia32.sse ? 'Y' : 'n'); #endif } } #else info->use_asm = false; #endif /* * PPC-specific */ #elif defined FLAC__CPU_PPC info->type = FLAC__CPUINFO_TYPE_PPC; # if !defined FLAC__NO_ASM info->use_asm = true; # ifdef FLAC__USE_ALTIVEC # if defined FLAC__SYS_DARWIN { int val = 0, mib[2] = { CTL_HW, HW_VECTORUNIT }; size_t len = sizeof(val); info->data.ppc.altivec = !(sysctl(mib, 2, &val, &len, NULL, 0) || !val); } { host_basic_info_data_t hostInfo; mach_msg_type_number_t infoCount; infoCount = HOST_BASIC_INFO_COUNT; host_info(mach_host_self(), HOST_BASIC_INFO, (host_info_t)&hostInfo, &infoCount); info->data.ppc.ppc64 = (hostInfo.cpu_type == CPU_TYPE_POWERPC) && (hostInfo.cpu_subtype == CPU_SUBTYPE_POWERPC_970); } # else /* FLAC__USE_ALTIVEC && !FLAC__SYS_DARWIN */ { /* no Darwin, do it the brute-force way */ /* @@@@@@ this is not thread-safe; replace with SSE OS method above or remove */ info->data.ppc.altivec = 0; info->data.ppc.ppc64 = 0; signal (SIGILL, sigill_handler); canjump = 0; if (!sigsetjmp (jmpbuf, 1)) { canjump = 1; asm volatile ( "mtspr 256, %0\n\t" "vand %%v0, %%v0, %%v0" : : "r" (-1) ); info->data.ppc.altivec = 1; } canjump = 0; if (!sigsetjmp (jmpbuf, 1)) { int x = 0; canjump = 1; /* PPC64 hardware implements the cntlzd instruction */ asm volatile ("cntlzd %0, %1" : "=r" (x) : "r" (x) ); info->data.ppc.ppc64 = 1; } signal (SIGILL, SIG_DFL); /*@@@@@@ should save and restore old signal */ } # endif # else /* !FLAC__USE_ALTIVEC */ info->data.ppc.altivec = 0; info->data.ppc.ppc64 = 0; # endif # else info->use_asm = false; # endif /* * unknown CPI */ #else info->type = FLAC__CPUINFO_TYPE_UNKNOWN; info->use_asm = false; #endif } sources_5316/external/flac/flac_private_autocpu.h0000644000176700017670000000112510720762520021022 0ustar paulpaul/* FLAC/private/autocpu.h by Erez Volk * Try to set FLAC__CPU_[IA32|PPC|UNKNOWN] automatically (if not already set) */ #ifndef FLAC__PRIVATE__AUTOCPU_H #define FLAC__PRIVATE__AUTOCPU_H #if !defined(FLAC__CPU_IA32) && !defined(FLAC__CPU_PPC) # if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__NT__) || defined(__i386) || defined(_M_IX86) # define FLAC__CPU_IA32 gdfjgdfjgd # elif defined(__ppc) # define FLAC__CPU_PPC # else # define FLAC__CPU_UNKNOWN # endif #endif /* !FLAC__CPU_IA32 && !FLAC__CPU_PPC */ #endif /* FLAC__PRIVATE__AUTOCPU_H */ sources_5316/external/flac/flac_crc.c0000644000176700017670000001433410720610304016350 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include "flac_private_crc.h" /* CRC-8, poly = x^8 + x^2 + x^1 + x^0, init = 0 */ FLAC__byte const FLAC__crc8_table[256] = { 0x00, 0x07, 0x0E, 0x09, 0x1C, 0x1B, 0x12, 0x15, 0x38, 0x3F, 0x36, 0x31, 0x24, 0x23, 0x2A, 0x2D, 0x70, 0x77, 0x7E, 0x79, 0x6C, 0x6B, 0x62, 0x65, 0x48, 0x4F, 0x46, 0x41, 0x54, 0x53, 0x5A, 0x5D, 0xE0, 0xE7, 0xEE, 0xE9, 0xFC, 0xFB, 0xF2, 0xF5, 0xD8, 0xDF, 0xD6, 0xD1, 0xC4, 0xC3, 0xCA, 0xCD, 0x90, 0x97, 0x9E, 0x99, 0x8C, 0x8B, 0x82, 0x85, 0xA8, 0xAF, 0xA6, 0xA1, 0xB4, 0xB3, 0xBA, 0xBD, 0xC7, 0xC0, 0xC9, 0xCE, 0xDB, 0xDC, 0xD5, 0xD2, 0xFF, 0xF8, 0xF1, 0xF6, 0xE3, 0xE4, 0xED, 0xEA, 0xB7, 0xB0, 0xB9, 0xBE, 0xAB, 0xAC, 0xA5, 0xA2, 0x8F, 0x88, 0x81, 0x86, 0x93, 0x94, 0x9D, 0x9A, 0x27, 0x20, 0x29, 0x2E, 0x3B, 0x3C, 0x35, 0x32, 0x1F, 0x18, 0x11, 0x16, 0x03, 0x04, 0x0D, 0x0A, 0x57, 0x50, 0x59, 0x5E, 0x4B, 0x4C, 0x45, 0x42, 0x6F, 0x68, 0x61, 0x66, 0x73, 0x74, 0x7D, 0x7A, 0x89, 0x8E, 0x87, 0x80, 0x95, 0x92, 0x9B, 0x9C, 0xB1, 0xB6, 0xBF, 0xB8, 0xAD, 0xAA, 0xA3, 0xA4, 0xF9, 0xFE, 0xF7, 0xF0, 0xE5, 0xE2, 0xEB, 0xEC, 0xC1, 0xC6, 0xCF, 0xC8, 0xDD, 0xDA, 0xD3, 0xD4, 0x69, 0x6E, 0x67, 0x60, 0x75, 0x72, 0x7B, 0x7C, 0x51, 0x56, 0x5F, 0x58, 0x4D, 0x4A, 0x43, 0x44, 0x19, 0x1E, 0x17, 0x10, 0x05, 0x02, 0x0B, 0x0C, 0x21, 0x26, 0x2F, 0x28, 0x3D, 0x3A, 0x33, 0x34, 0x4E, 0x49, 0x40, 0x47, 0x52, 0x55, 0x5C, 0x5B, 0x76, 0x71, 0x78, 0x7F, 0x6A, 0x6D, 0x64, 0x63, 0x3E, 0x39, 0x30, 0x37, 0x22, 0x25, 0x2C, 0x2B, 0x06, 0x01, 0x08, 0x0F, 0x1A, 0x1D, 0x14, 0x13, 0xAE, 0xA9, 0xA0, 0xA7, 0xB2, 0xB5, 0xBC, 0xBB, 0x96, 0x91, 0x98, 0x9F, 0x8A, 0x8D, 0x84, 0x83, 0xDE, 0xD9, 0xD0, 0xD7, 0xC2, 0xC5, 0xCC, 0xCB, 0xE6, 0xE1, 0xE8, 0xEF, 0xFA, 0xFD, 0xF4, 0xF3 }; /* CRC-16, poly = x^16 + x^15 + x^2 + x^0, init = 0 */ unsigned FLAC__crc16_table[256] = { 0x0000, 0x8005, 0x800f, 0x000a, 0x801b, 0x001e, 0x0014, 0x8011, 0x8033, 0x0036, 0x003c, 0x8039, 0x0028, 0x802d, 0x8027, 0x0022, 0x8063, 0x0066, 0x006c, 0x8069, 0x0078, 0x807d, 0x8077, 0x0072, 0x0050, 0x8055, 0x805f, 0x005a, 0x804b, 0x004e, 0x0044, 0x8041, 0x80c3, 0x00c6, 0x00cc, 0x80c9, 0x00d8, 0x80dd, 0x80d7, 0x00d2, 0x00f0, 0x80f5, 0x80ff, 0x00fa, 0x80eb, 0x00ee, 0x00e4, 0x80e1, 0x00a0, 0x80a5, 0x80af, 0x00aa, 0x80bb, 0x00be, 0x00b4, 0x80b1, 0x8093, 0x0096, 0x009c, 0x8099, 0x0088, 0x808d, 0x8087, 0x0082, 0x8183, 0x0186, 0x018c, 0x8189, 0x0198, 0x819d, 0x8197, 0x0192, 0x01b0, 0x81b5, 0x81bf, 0x01ba, 0x81ab, 0x01ae, 0x01a4, 0x81a1, 0x01e0, 0x81e5, 0x81ef, 0x01ea, 0x81fb, 0x01fe, 0x01f4, 0x81f1, 0x81d3, 0x01d6, 0x01dc, 0x81d9, 0x01c8, 0x81cd, 0x81c7, 0x01c2, 0x0140, 0x8145, 0x814f, 0x014a, 0x815b, 0x015e, 0x0154, 0x8151, 0x8173, 0x0176, 0x017c, 0x8179, 0x0168, 0x816d, 0x8167, 0x0162, 0x8123, 0x0126, 0x012c, 0x8129, 0x0138, 0x813d, 0x8137, 0x0132, 0x0110, 0x8115, 0x811f, 0x011a, 0x810b, 0x010e, 0x0104, 0x8101, 0x8303, 0x0306, 0x030c, 0x8309, 0x0318, 0x831d, 0x8317, 0x0312, 0x0330, 0x8335, 0x833f, 0x033a, 0x832b, 0x032e, 0x0324, 0x8321, 0x0360, 0x8365, 0x836f, 0x036a, 0x837b, 0x037e, 0x0374, 0x8371, 0x8353, 0x0356, 0x035c, 0x8359, 0x0348, 0x834d, 0x8347, 0x0342, 0x03c0, 0x83c5, 0x83cf, 0x03ca, 0x83db, 0x03de, 0x03d4, 0x83d1, 0x83f3, 0x03f6, 0x03fc, 0x83f9, 0x03e8, 0x83ed, 0x83e7, 0x03e2, 0x83a3, 0x03a6, 0x03ac, 0x83a9, 0x03b8, 0x83bd, 0x83b7, 0x03b2, 0x0390, 0x8395, 0x839f, 0x039a, 0x838b, 0x038e, 0x0384, 0x8381, 0x0280, 0x8285, 0x828f, 0x028a, 0x829b, 0x029e, 0x0294, 0x8291, 0x82b3, 0x02b6, 0x02bc, 0x82b9, 0x02a8, 0x82ad, 0x82a7, 0x02a2, 0x82e3, 0x02e6, 0x02ec, 0x82e9, 0x02f8, 0x82fd, 0x82f7, 0x02f2, 0x02d0, 0x82d5, 0x82df, 0x02da, 0x82cb, 0x02ce, 0x02c4, 0x82c1, 0x8243, 0x0246, 0x024c, 0x8249, 0x0258, 0x825d, 0x8257, 0x0252, 0x0270, 0x8275, 0x827f, 0x027a, 0x826b, 0x026e, 0x0264, 0x8261, 0x0220, 0x8225, 0x822f, 0x022a, 0x823b, 0x023e, 0x0234, 0x8231, 0x8213, 0x0216, 0x021c, 0x8219, 0x0208, 0x820d, 0x8207, 0x0202 }; void FLAC__crc8_update(const FLAC__byte data, FLAC__uint8 *crc) { *crc = FLAC__crc8_table[*crc ^ data]; } void FLAC__crc8_update_block(const FLAC__byte *data, unsigned len, FLAC__uint8 *crc) { while(len--) *crc = FLAC__crc8_table[*crc ^ *data++]; } FLAC__uint8 FLAC__crc8(const FLAC__byte *data, unsigned len) { FLAC__uint8 crc = 0; while(len--) crc = FLAC__crc8_table[crc ^ *data++]; return crc; } unsigned FLAC__crc16(const FLAC__byte *data, unsigned len) { unsigned crc = 0; while(len--) crc = ((crc<<8) ^ FLAC__crc16_table[(crc>>8) ^ *data++]) & 0xffff; return crc; } sources_5316/external/flac/flac_FLAC_format.h0000644000176700017670000011614511611125735017677 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__FORMAT_H #define FLAC__FORMAT_H #include "flac_FLAC_export.h" #include "flac_FLAC_ordinals.h" #ifdef __cplusplus extern "C" { #endif /** \file include/FLAC/format.h * * \brief * This module contains structure definitions for the representation * of FLAC format components in memory. These are the basic * structures used by the rest of the interfaces. * * See the detailed documentation in the * \link flac_format format \endlink module. */ /** \defgroup flac_format FLAC/format.h: format components * \ingroup flac * * \brief * This module contains structure definitions for the representation * of FLAC format components in memory. These are the basic * structures used by the rest of the interfaces. * * First, you should be familiar with the * FLAC format. Many of the values here * follow directly from the specification. As a user of libFLAC, the * interesting parts really are the structures that describe the frame * header and metadata blocks. * * The format structures here are very primitive, designed to store * information in an efficient way. Reading information from the * structures is easy but creating or modifying them directly is * more complex. For the most part, as a user of a library, editing * is not necessary; however, for metadata blocks it is, so there are * convenience functions provided in the \link flac_metadata metadata * module \endlink to simplify the manipulation of metadata blocks. * * \note * It's not the best convention, but symbols ending in _LEN are in bits * and _LENGTH are in bytes. _LENGTH symbols are \#defines instead of * global variables because they are usually used when declaring byte * arrays and some compilers require compile-time knowledge of array * sizes when declared on the stack. * * \{ */ /* Most of the values described in this file are defined by the FLAC format specification. There is nothing to tune here. */ /** The largest legal metadata type code. */ #define FLAC__MAX_METADATA_TYPE_CODE (126u) /** The minimum block size, in samples, permitted by the format. */ #define FLAC__MIN_BLOCK_SIZE (16u) /** The maximum block size, in samples, permitted by the format. */ #define FLAC__MAX_BLOCK_SIZE (65535u) /** The maximum block size, in samples, permitted by the FLAC subset for * sample rates up to 48kHz. */ #define FLAC__SUBSET_MAX_BLOCK_SIZE_48000HZ (4608u) /** The maximum number of channels permitted by the format. */ #define FLAC__MAX_CHANNELS (8u) /** The minimum sample resolution permitted by the format. */ #define FLAC__MIN_BITS_PER_SAMPLE (4u) /** The maximum sample resolution permitted by the format. */ #define FLAC__MAX_BITS_PER_SAMPLE (32u) /** The maximum sample resolution permitted by libFLAC. * * \warning * FLAC__MAX_BITS_PER_SAMPLE is the limit of the FLAC format. However, * the reference encoder/decoder is currently limited to 24 bits because * of prevalent 32-bit math, so make sure and use this value when * appropriate. */ #define FLAC__REFERENCE_CODEC_MAX_BITS_PER_SAMPLE (24u) /** The maximum sample rate permitted by the format. The value is * ((2 ^ 16) - 1) * 10; see FLAC format * as to why. */ #define FLAC__MAX_SAMPLE_RATE (655350u) /** The maximum LPC order permitted by the format. */ #define FLAC__MAX_LPC_ORDER (32u) /** The maximum LPC order permitted by the FLAC subset for sample rates * up to 48kHz. */ #define FLAC__SUBSET_MAX_LPC_ORDER_48000HZ (12u) /** The minimum quantized linear predictor coefficient precision * permitted by the format. */ #define FLAC__MIN_QLP_COEFF_PRECISION (5u) /** The maximum quantized linear predictor coefficient precision * permitted by the format. */ #define FLAC__MAX_QLP_COEFF_PRECISION (15u) /** The maximum order of the fixed predictors permitted by the format. */ #define FLAC__MAX_FIXED_ORDER (4u) /** The maximum Rice partition order permitted by the format. */ #define FLAC__MAX_RICE_PARTITION_ORDER (15u) /** The maximum Rice partition order permitted by the FLAC Subset. */ #define FLAC__SUBSET_MAX_RICE_PARTITION_ORDER (8u) /** The version string of the release, stamped onto the libraries and binaries. * * \note * This does not correspond to the shared library version number, which * is used to determine binary compatibility. */ extern FLAC_API const char *FLAC__VERSION_STRING; /** The vendor string inserted by the encoder into the VORBIS_COMMENT block. * This is a NUL-terminated ASCII string; when inserted into the * VORBIS_COMMENT the trailing null is stripped. */ extern FLAC_API const char *FLAC__VENDOR_STRING; /** The byte string representation of the beginning of a FLAC stream. */ extern FLAC_API const FLAC__byte FLAC__STREAM_SYNC_STRING[4]; /* = "fLaC" */ /** The 32-bit integer big-endian representation of the beginning of * a FLAC stream. */ extern FLAC_API const unsigned FLAC__STREAM_SYNC; /* = 0x664C6143 */ /** The length of the FLAC signature in bits. */ extern FLAC_API const unsigned FLAC__STREAM_SYNC_LEN; /* = 32 bits */ /** The length of the FLAC signature in bytes. */ #define FLAC__STREAM_SYNC_LENGTH (4u) /***************************************************************************** * * Subframe structures * *****************************************************************************/ /*****************************************************************************/ /** An enumeration of the available entropy coding methods. */ typedef enum { FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE = 0, /**< Residual is coded by partitioning into contexts, each with it's own * 4-bit Rice parameter. */ FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2 = 1 /**< Residual is coded by partitioning into contexts, each with it's own * 5-bit Rice parameter. */ } FLAC__EntropyCodingMethodType; /** Maps a FLAC__EntropyCodingMethodType to a C string. * * Using a FLAC__EntropyCodingMethodType as the index to this array will * give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__EntropyCodingMethodTypeString[]; /** Contents of a Rice partitioned residual */ typedef struct { unsigned *parameters; /**< The Rice parameters for each context. */ unsigned *raw_bits; /**< Widths for escape-coded partitions. Will be non-zero for escaped * partitions and zero for unescaped partitions. */ unsigned capacity_by_order; /**< The capacity of the \a parameters and \a raw_bits arrays * specified as an order, i.e. the number of array elements * allocated is 2 ^ \a capacity_by_order. */ } FLAC__EntropyCodingMethod_PartitionedRiceContents; /** Header for a Rice partitioned residual. (c.f. format specification) */ typedef struct { unsigned order; /**< The partition order, i.e. # of contexts = 2 ^ \a order. */ const FLAC__EntropyCodingMethod_PartitionedRiceContents *contents; /**< The context's Rice parameters and/or raw bits. */ } FLAC__EntropyCodingMethod_PartitionedRice; extern FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ORDER_LEN; /**< == 4 (bits) */ extern FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_PARAMETER_LEN; /**< == 4 (bits) */ extern FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_PARAMETER_LEN; /**< == 5 (bits) */ extern FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_RAW_LEN; /**< == 5 (bits) */ extern FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ESCAPE_PARAMETER; /**< == (1<format specification) */ typedef struct { FLAC__EntropyCodingMethodType type; union { FLAC__EntropyCodingMethod_PartitionedRice partitioned_rice; } data; } FLAC__EntropyCodingMethod; extern FLAC_API const unsigned FLAC__ENTROPY_CODING_METHOD_TYPE_LEN; /**< == 2 (bits) */ /*****************************************************************************/ /** An enumeration of the available subframe types. */ typedef enum { FLAC__SUBFRAME_TYPE_CONSTANT = 0, /**< constant signal */ FLAC__SUBFRAME_TYPE_VERBATIM = 1, /**< uncompressed signal */ FLAC__SUBFRAME_TYPE_FIXED = 2, /**< fixed polynomial prediction */ FLAC__SUBFRAME_TYPE_LPC = 3 /**< linear prediction */ } FLAC__SubframeType; /** Maps a FLAC__SubframeType to a C string. * * Using a FLAC__SubframeType as the index to this array will * give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__SubframeTypeString[]; /** CONSTANT subframe. (c.f. format specification) */ typedef struct { FLAC__int32 value; /**< The constant signal value. */ } FLAC__Subframe_Constant; /** VERBATIM subframe. (c.f. format specification) */ typedef struct { const FLAC__int32 *data; /**< A pointer to verbatim signal. */ } FLAC__Subframe_Verbatim; /** FIXED subframe. (c.f. format specification) */ typedef struct { FLAC__EntropyCodingMethod entropy_coding_method; /**< The residual coding method. */ unsigned order; /**< The polynomial order. */ FLAC__int32 warmup[FLAC__MAX_FIXED_ORDER]; /**< Warmup samples to prime the predictor, length == order. */ const FLAC__int32 *residual; /**< The residual signal, length == (blocksize minus order) samples. */ } FLAC__Subframe_Fixed; /** LPC subframe. (c.f. format specification) */ typedef struct { FLAC__EntropyCodingMethod entropy_coding_method; /**< The residual coding method. */ unsigned order; /**< The FIR order. */ unsigned qlp_coeff_precision; /**< Quantized FIR filter coefficient precision in bits. */ int quantization_level; /**< The qlp coeff shift needed. */ FLAC__int32 qlp_coeff[FLAC__MAX_LPC_ORDER]; /**< FIR filter coefficients. */ FLAC__int32 warmup[FLAC__MAX_LPC_ORDER]; /**< Warmup samples to prime the predictor, length == order. */ const FLAC__int32 *residual; /**< The residual signal, length == (blocksize minus order) samples. */ } FLAC__Subframe_LPC; extern FLAC_API const unsigned FLAC__SUBFRAME_LPC_QLP_COEFF_PRECISION_LEN; /**< == 4 (bits) */ extern FLAC_API const unsigned FLAC__SUBFRAME_LPC_QLP_SHIFT_LEN; /**< == 5 (bits) */ /** FLAC subframe structure. (c.f. format specification) */ typedef struct { FLAC__SubframeType type; union { FLAC__Subframe_Constant constant; FLAC__Subframe_Fixed fixed; FLAC__Subframe_LPC lpc; FLAC__Subframe_Verbatim verbatim; } data; unsigned wasted_bits; } FLAC__Subframe; /** == 1 (bit) * * This used to be a zero-padding bit (hence the name * FLAC__SUBFRAME_ZERO_PAD_LEN) but is now a reserved bit. It still has a * mandatory value of \c 0 but in the future may take on the value \c 0 or \c 1 * to mean something else. */ extern FLAC_API const unsigned FLAC__SUBFRAME_ZERO_PAD_LEN; extern FLAC_API const unsigned FLAC__SUBFRAME_TYPE_LEN; /**< == 6 (bits) */ extern FLAC_API const unsigned FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN; /**< == 1 (bit) */ extern FLAC_API const unsigned FLAC__SUBFRAME_TYPE_CONSTANT_BYTE_ALIGNED_MASK; /**< = 0x00 */ extern FLAC_API const unsigned FLAC__SUBFRAME_TYPE_VERBATIM_BYTE_ALIGNED_MASK; /**< = 0x02 */ extern FLAC_API const unsigned FLAC__SUBFRAME_TYPE_FIXED_BYTE_ALIGNED_MASK; /**< = 0x10 */ extern FLAC_API const unsigned FLAC__SUBFRAME_TYPE_LPC_BYTE_ALIGNED_MASK; /**< = 0x40 */ /*****************************************************************************/ /***************************************************************************** * * Frame structures * *****************************************************************************/ /** An enumeration of the available channel assignments. */ typedef enum { FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT = 0, /**< independent channels */ FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE = 1, /**< left+side stereo */ FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE = 2, /**< right+side stereo */ FLAC__CHANNEL_ASSIGNMENT_MID_SIDE = 3 /**< mid+side stereo */ } FLAC__ChannelAssignment; /** Maps a FLAC__ChannelAssignment to a C string. * * Using a FLAC__ChannelAssignment as the index to this array will * give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__ChannelAssignmentString[]; /** An enumeration of the possible frame numbering methods. */ typedef enum { FLAC__FRAME_NUMBER_TYPE_FRAME_NUMBER, /**< number contains the frame number */ FLAC__FRAME_NUMBER_TYPE_SAMPLE_NUMBER /**< number contains the sample number of first sample in frame */ } FLAC__FrameNumberType; /** Maps a FLAC__FrameNumberType to a C string. * * Using a FLAC__FrameNumberType as the index to this array will * give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__FrameNumberTypeString[]; /** FLAC frame header structure. (c.f. format specification) */ typedef struct { unsigned blocksize; /**< The number of samples per subframe. */ unsigned sample_rate; /**< The sample rate in Hz. */ unsigned channels; /**< The number of channels (== number of subframes). */ FLAC__ChannelAssignment channel_assignment; /**< The channel assignment for the frame. */ unsigned bits_per_sample; /**< The sample resolution. */ FLAC__FrameNumberType number_type; /**< The numbering scheme used for the frame. As a convenience, the * decoder will always convert a frame number to a sample number because * the rules are complex. */ union { FLAC__uint32 frame_number; FLAC__uint64 sample_number; } number; /**< The frame number or sample number of first sample in frame; * use the \a number_type value to determine which to use. */ FLAC__uint8 crc; /**< CRC-8 (polynomial = x^8 + x^2 + x^1 + x^0, initialized with 0) * of the raw frame header bytes, meaning everything before the CRC byte * including the sync code. */ } FLAC__FrameHeader; extern FLAC_API const unsigned FLAC__FRAME_HEADER_SYNC; /**< == 0x3ffe; the frame header sync code */ extern FLAC_API const unsigned FLAC__FRAME_HEADER_SYNC_LEN; /**< == 14 (bits) */ extern FLAC_API const unsigned FLAC__FRAME_HEADER_RESERVED_LEN; /**< == 1 (bits) */ extern FLAC_API const unsigned FLAC__FRAME_HEADER_BLOCKING_STRATEGY_LEN; /**< == 1 (bits) */ extern FLAC_API const unsigned FLAC__FRAME_HEADER_BLOCK_SIZE_LEN; /**< == 4 (bits) */ extern FLAC_API const unsigned FLAC__FRAME_HEADER_SAMPLE_RATE_LEN; /**< == 4 (bits) */ extern FLAC_API const unsigned FLAC__FRAME_HEADER_CHANNEL_ASSIGNMENT_LEN; /**< == 4 (bits) */ extern FLAC_API const unsigned FLAC__FRAME_HEADER_BITS_PER_SAMPLE_LEN; /**< == 3 (bits) */ extern FLAC_API const unsigned FLAC__FRAME_HEADER_ZERO_PAD_LEN; /**< == 1 (bit) */ extern FLAC_API const unsigned FLAC__FRAME_HEADER_CRC_LEN; /**< == 8 (bits) */ /** FLAC frame footer structure. (c.f. format specification) */ typedef struct { FLAC__uint16 crc; /**< CRC-16 (polynomial = x^16 + x^15 + x^2 + x^0, initialized with * 0) of the bytes before the crc, back to and including the frame header * sync code. */ } FLAC__FrameFooter; extern FLAC_API const unsigned FLAC__FRAME_FOOTER_CRC_LEN; /**< == 16 (bits) */ /** FLAC frame structure. (c.f. format specification) */ typedef struct { FLAC__FrameHeader header; FLAC__Subframe subframes[FLAC__MAX_CHANNELS]; FLAC__FrameFooter footer; } FLAC__Frame; /*****************************************************************************/ /***************************************************************************** * * Meta-data structures * *****************************************************************************/ /** An enumeration of the available metadata block types. */ typedef enum { FLAC__METADATA_TYPE_STREAMINFO = 0, /**< STREAMINFO block */ FLAC__METADATA_TYPE_PADDING = 1, /**< PADDING block */ FLAC__METADATA_TYPE_APPLICATION = 2, /**< APPLICATION block */ FLAC__METADATA_TYPE_SEEKTABLE = 3, /**< SEEKTABLE block */ FLAC__METADATA_TYPE_VORBIS_COMMENT = 4, /**< VORBISCOMMENT block (a.k.a. FLAC tags) */ FLAC__METADATA_TYPE_CUESHEET = 5, /**< CUESHEET block */ FLAC__METADATA_TYPE_PICTURE = 6, /**< PICTURE block */ FLAC__METADATA_TYPE_UNDEFINED = 7 /**< marker to denote beginning of undefined type range; this number will increase as new metadata types are added */ } FLAC__MetadataType; /** Maps a FLAC__MetadataType to a C string. * * Using a FLAC__MetadataType as the index to this array will * give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__MetadataTypeString[]; /** FLAC STREAMINFO structure. (c.f. format specification) */ typedef struct { unsigned min_blocksize, max_blocksize; unsigned min_framesize, max_framesize; unsigned sample_rate; unsigned channels; unsigned bits_per_sample; FLAC__uint64 total_samples; FLAC__byte md5sum[16]; } FLAC__StreamMetadata_StreamInfo; extern FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN; /**< == 16 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN; /**< == 16 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN; /**< == 24 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN; /**< == 24 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_SAMPLE_RATE_LEN; /**< == 20 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN; /**< == 3 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN; /**< == 5 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_TOTAL_SAMPLES_LEN; /**< == 36 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_STREAMINFO_MD5SUM_LEN; /**< == 128 (bits) */ /** The total stream length of the STREAMINFO block in bytes. */ #define FLAC__STREAM_METADATA_STREAMINFO_LENGTH (34u) /** FLAC PADDING structure. (c.f. format specification) */ typedef struct { int dummy; /**< Conceptually this is an empty struct since we don't store the * padding bytes. Empty structs are not allowed by some C compilers, * hence the dummy. */ } FLAC__StreamMetadata_Padding; /** FLAC APPLICATION structure. (c.f. format specification) */ typedef struct { FLAC__byte id[4]; FLAC__byte *data; } FLAC__StreamMetadata_Application; extern FLAC_API const unsigned FLAC__STREAM_METADATA_APPLICATION_ID_LEN; /**< == 32 (bits) */ /** SeekPoint structure used in SEEKTABLE blocks. (c.f. format specification) */ typedef struct { FLAC__uint64 sample_number; /**< The sample number of the target frame. */ FLAC__uint64 stream_offset; /**< The offset, in bytes, of the target frame with respect to * beginning of the first frame. */ unsigned frame_samples; /**< The number of samples in the target frame. */ } FLAC__StreamMetadata_SeekPoint; extern FLAC_API const unsigned FLAC__STREAM_METADATA_SEEKPOINT_SAMPLE_NUMBER_LEN; /**< == 64 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_SEEKPOINT_STREAM_OFFSET_LEN; /**< == 64 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_SEEKPOINT_FRAME_SAMPLES_LEN; /**< == 16 (bits) */ /** The total stream length of a seek point in bytes. */ #define FLAC__STREAM_METADATA_SEEKPOINT_LENGTH (18u) /** The value used in the \a sample_number field of * FLAC__StreamMetadataSeekPoint used to indicate a placeholder * point (== 0xffffffffffffffff). */ extern FLAC_API const FLAC__uint64 FLAC__STREAM_METADATA_SEEKPOINT_PLACEHOLDER; /** FLAC SEEKTABLE structure. (c.f. format specification) * * \note From the format specification: * - The seek points must be sorted by ascending sample number. * - Each seek point's sample number must be the first sample of the * target frame. * - Each seek point's sample number must be unique within the table. * - Existence of a SEEKTABLE block implies a correct setting of * total_samples in the stream_info block. * - Behavior is undefined when more than one SEEKTABLE block is * present in a stream. */ typedef struct { unsigned num_points; FLAC__StreamMetadata_SeekPoint *points; } FLAC__StreamMetadata_SeekTable; /** Vorbis comment entry structure used in VORBIS_COMMENT blocks. (c.f. format specification) * * For convenience, the APIs maintain a trailing NUL character at the end of * \a entry which is not counted toward \a length, i.e. * \code strlen(entry) == length \endcode */ typedef struct { FLAC__uint32 length; FLAC__byte *entry; } FLAC__StreamMetadata_VorbisComment_Entry; extern FLAC_API const unsigned FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN; /**< == 32 (bits) */ /** FLAC VORBIS_COMMENT structure. (c.f. format specification) */ typedef struct { FLAC__StreamMetadata_VorbisComment_Entry vendor_string; FLAC__uint32 num_comments; FLAC__StreamMetadata_VorbisComment_Entry *comments; } FLAC__StreamMetadata_VorbisComment; extern FLAC_API const unsigned FLAC__STREAM_METADATA_VORBIS_COMMENT_NUM_COMMENTS_LEN; /**< == 32 (bits) */ /** FLAC CUESHEET track index structure. (See the * format specification for * the full description of each field.) */ typedef struct { FLAC__uint64 offset; /**< Offset in samples, relative to the track offset, of the index * point. */ FLAC__byte number; /**< The index point number. */ } FLAC__StreamMetadata_CueSheet_Index; extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_INDEX_OFFSET_LEN; /**< == 64 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_INDEX_NUMBER_LEN; /**< == 8 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN; /**< == 3*8 (bits) */ /** FLAC CUESHEET track structure. (See the * format specification for * the full description of each field.) */ typedef struct { FLAC__uint64 offset; /**< Track offset in samples, relative to the beginning of the FLAC audio stream. */ FLAC__byte number; /**< The track number. */ char isrc[13]; /**< Track ISRC. This is a 12-digit alphanumeric code plus a trailing \c NUL byte */ unsigned type:1; /**< The track type: 0 for audio, 1 for non-audio. */ unsigned pre_emphasis:1; /**< The pre-emphasis flag: 0 for no pre-emphasis, 1 for pre-emphasis. */ FLAC__byte num_indices; /**< The number of track index points. */ FLAC__StreamMetadata_CueSheet_Index *indices; /**< NULL if num_indices == 0, else pointer to array of index points. */ } FLAC__StreamMetadata_CueSheet_Track; extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_OFFSET_LEN; /**< == 64 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_NUMBER_LEN; /**< == 8 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN; /**< == 12*8 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN; /**< == 1 (bit) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN; /**< == 1 (bit) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN; /**< == 6+13*8 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_TRACK_NUM_INDICES_LEN; /**< == 8 (bits) */ /** FLAC CUESHEET structure. (See the * format specification * for the full description of each field.) */ typedef struct { char media_catalog_number[129]; /**< Media catalog number, in ASCII printable characters 0x20-0x7e. In * general, the media catalog number may be 0 to 128 bytes long; any * unused characters should be right-padded with NUL characters. */ FLAC__uint64 lead_in; /**< The number of lead-in samples. */ FLAC__bool is_cd; /**< \c true if CUESHEET corresponds to a Compact Disc, else \c false. */ unsigned num_tracks; /**< The number of tracks. */ FLAC__StreamMetadata_CueSheet_Track *tracks; /**< NULL if num_tracks == 0, else pointer to array of tracks. */ } FLAC__StreamMetadata_CueSheet; extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN; /**< == 128*8 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_LEAD_IN_LEN; /**< == 64 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN; /**< == 1 (bit) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN; /**< == 7+258*8 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_CUESHEET_NUM_TRACKS_LEN; /**< == 8 (bits) */ /** An enumeration of the PICTURE types (see FLAC__StreamMetadataPicture and id3 v2.4 APIC tag). */ typedef enum { FLAC__STREAM_METADATA_PICTURE_TYPE_OTHER = 0, /**< Other */ FLAC__STREAM_METADATA_PICTURE_TYPE_FILE_ICON_STANDARD = 1, /**< 32x32 pixels 'file icon' (PNG only) */ FLAC__STREAM_METADATA_PICTURE_TYPE_FILE_ICON = 2, /**< Other file icon */ FLAC__STREAM_METADATA_PICTURE_TYPE_FRONT_COVER = 3, /**< Cover (front) */ FLAC__STREAM_METADATA_PICTURE_TYPE_BACK_COVER = 4, /**< Cover (back) */ FLAC__STREAM_METADATA_PICTURE_TYPE_LEAFLET_PAGE = 5, /**< Leaflet page */ FLAC__STREAM_METADATA_PICTURE_TYPE_MEDIA = 6, /**< Media (e.g. label side of CD) */ FLAC__STREAM_METADATA_PICTURE_TYPE_LEAD_ARTIST = 7, /**< Lead artist/lead performer/soloist */ FLAC__STREAM_METADATA_PICTURE_TYPE_ARTIST = 8, /**< Artist/performer */ FLAC__STREAM_METADATA_PICTURE_TYPE_CONDUCTOR = 9, /**< Conductor */ FLAC__STREAM_METADATA_PICTURE_TYPE_BAND = 10, /**< Band/Orchestra */ FLAC__STREAM_METADATA_PICTURE_TYPE_COMPOSER = 11, /**< Composer */ FLAC__STREAM_METADATA_PICTURE_TYPE_LYRICIST = 12, /**< Lyricist/text writer */ FLAC__STREAM_METADATA_PICTURE_TYPE_RECORDING_LOCATION = 13, /**< Recording Location */ FLAC__STREAM_METADATA_PICTURE_TYPE_DURING_RECORDING = 14, /**< During recording */ FLAC__STREAM_METADATA_PICTURE_TYPE_DURING_PERFORMANCE = 15, /**< During performance */ FLAC__STREAM_METADATA_PICTURE_TYPE_VIDEO_SCREEN_CAPTURE = 16, /**< Movie/video screen capture */ FLAC__STREAM_METADATA_PICTURE_TYPE_FISH = 17, /**< A bright coloured fish */ FLAC__STREAM_METADATA_PICTURE_TYPE_ILLUSTRATION = 18, /**< Illustration */ FLAC__STREAM_METADATA_PICTURE_TYPE_BAND_LOGOTYPE = 19, /**< Band/artist logotype */ FLAC__STREAM_METADATA_PICTURE_TYPE_PUBLISHER_LOGOTYPE = 20, /**< Publisher/Studio logotype */ FLAC__STREAM_METADATA_PICTURE_TYPE_UNDEFINED } FLAC__StreamMetadata_Picture_Type; /** Maps a FLAC__StreamMetadata_Picture_Type to a C string. * * Using a FLAC__StreamMetadata_Picture_Type as the index to this array * will give the string equivalent. The contents should not be * modified. */ extern FLAC_API const char * const FLAC__StreamMetadata_Picture_TypeString[]; /** FLAC PICTURE structure. (See the * format specification * for the full description of each field.) */ typedef struct { FLAC__StreamMetadata_Picture_Type type; /**< The kind of picture stored. */ char *mime_type; /**< Picture data's MIME type, in ASCII printable characters * 0x20-0x7e, NUL terminated. For best compatibility with players, * use picture data of MIME type \c image/jpeg or \c image/png. A * MIME type of '-->' is also allowed, in which case the picture * data should be a complete URL. In file storage, the MIME type is * stored as a 32-bit length followed by the ASCII string with no NUL * terminator, but is converted to a plain C string in this structure * for convenience. */ FLAC__byte *description; /**< Picture's description in UTF-8, NUL terminated. In file storage, * the description is stored as a 32-bit length followed by the UTF-8 * string with no NUL terminator, but is converted to a plain C string * in this structure for convenience. */ FLAC__uint32 width; /**< Picture's width in pixels. */ FLAC__uint32 height; /**< Picture's height in pixels. */ FLAC__uint32 depth; /**< Picture's color depth in bits-per-pixel. */ FLAC__uint32 colors; /**< For indexed palettes (like GIF), picture's number of colors (the * number of palette entries), or \c 0 for non-indexed (i.e. 2^depth). */ FLAC__uint32 data_length; /**< Length of binary picture data in bytes. */ FLAC__byte *data; /**< Binary picture data. */ } FLAC__StreamMetadata_Picture; extern FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_TYPE_LEN; /**< == 32 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_MIME_TYPE_LENGTH_LEN; /**< == 32 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_DESCRIPTION_LENGTH_LEN; /**< == 32 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN; /**< == 32 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN; /**< == 32 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN; /**< == 32 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_COLORS_LEN; /**< == 32 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_PICTURE_DATA_LENGTH_LEN; /**< == 32 (bits) */ /** Structure that is used when a metadata block of unknown type is loaded. * The contents are opaque. The structure is used only internally to * correctly handle unknown metadata. */ typedef struct { FLAC__byte *data; } FLAC__StreamMetadata_Unknown; /** FLAC metadata block structure. (c.f. format specification) */ typedef struct { FLAC__MetadataType type; /**< The type of the metadata block; used determine which member of the * \a data union to dereference. If type >= FLAC__METADATA_TYPE_UNDEFINED * then \a data.unknown must be used. */ FLAC__bool is_last; /**< \c true if this metadata block is the last, else \a false */ unsigned length; /**< Length, in bytes, of the block data as it appears in the stream. */ union { FLAC__StreamMetadata_StreamInfo stream_info; FLAC__StreamMetadata_Padding padding; FLAC__StreamMetadata_Application application; FLAC__StreamMetadata_SeekTable seek_table; FLAC__StreamMetadata_VorbisComment vorbis_comment; FLAC__StreamMetadata_CueSheet cue_sheet; FLAC__StreamMetadata_Picture picture; FLAC__StreamMetadata_Unknown unknown; } data; /**< Polymorphic block data; use the \a type value to determine which * to use. */ } FLAC__StreamMetadata; extern FLAC_API const unsigned FLAC__STREAM_METADATA_IS_LAST_LEN; /**< == 1 (bit) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_TYPE_LEN; /**< == 7 (bits) */ extern FLAC_API const unsigned FLAC__STREAM_METADATA_LENGTH_LEN; /**< == 24 (bits) */ /** The total stream length of a metadata block header in bytes. */ #define FLAC__STREAM_METADATA_HEADER_LENGTH (4u) /*****************************************************************************/ /***************************************************************************** * * Utility functions * *****************************************************************************/ /** Tests that a sample rate is valid for FLAC. * * \param sample_rate The sample rate to test for compliance. * \retval FLAC__bool * \c true if the given sample rate conforms to the specification, else * \c false. */ FLAC_API FLAC__bool FLAC__format_sample_rate_is_valid(unsigned sample_rate); /** Tests that a sample rate is valid for the FLAC subset. The subset rules * for valid sample rates are slightly more complex since the rate has to * be expressible completely in the frame header. * * \param sample_rate The sample rate to test for compliance. * \retval FLAC__bool * \c true if the given sample rate conforms to the specification for the * subset, else \c false. */ FLAC_API FLAC__bool FLAC__format_sample_rate_is_subset(unsigned sample_rate); /** Check a Vorbis comment entry name to see if it conforms to the Vorbis * comment specification. * * Vorbis comment names must be composed only of characters from * [0x20-0x3C,0x3E-0x7D]. * * \param name A NUL-terminated string to be checked. * \assert * \code name != NULL \endcode * \retval FLAC__bool * \c false if entry name is illegal, else \c true. */ FLAC_API FLAC__bool FLAC__format_vorbiscomment_entry_name_is_legal(const char *name); /** Check a Vorbis comment entry value to see if it conforms to the Vorbis * comment specification. * * Vorbis comment values must be valid UTF-8 sequences. * * \param value A string to be checked. * \param length A the length of \a value in bytes. May be * \c (unsigned)(-1) to indicate that \a value is a plain * UTF-8 NUL-terminated string. * \assert * \code value != NULL \endcode * \retval FLAC__bool * \c false if entry name is illegal, else \c true. */ FLAC_API FLAC__bool FLAC__format_vorbiscomment_entry_value_is_legal(const FLAC__byte *value, unsigned length); /** Check a Vorbis comment entry to see if it conforms to the Vorbis * comment specification. * * Vorbis comment entries must be of the form 'name=value', and 'name' and * 'value' must be legal according to * FLAC__format_vorbiscomment_entry_name_is_legal() and * FLAC__format_vorbiscomment_entry_value_is_legal() respectively. * * \param entry An entry to be checked. * \param length The length of \a entry in bytes. * \assert * \code value != NULL \endcode * \retval FLAC__bool * \c false if entry name is illegal, else \c true. */ FLAC_API FLAC__bool FLAC__format_vorbiscomment_entry_is_legal(const FLAC__byte *entry, unsigned length); /** Check a seek table to see if it conforms to the FLAC specification. * See the format specification for limits on the contents of the * seek table. * * \param seek_table A pointer to a seek table to be checked. * \assert * \code seek_table != NULL \endcode * \retval FLAC__bool * \c false if seek table is illegal, else \c true. */ FLAC_API FLAC__bool FLAC__format_seektable_is_legal(const FLAC__StreamMetadata_SeekTable *seek_table); /** Sort a seek table's seek points according to the format specification. * This includes a "unique-ification" step to remove duplicates, i.e. * seek points with identical \a sample_number values. Duplicate seek * points are converted into placeholder points and sorted to the end of * the table. * * \param seek_table A pointer to a seek table to be sorted. * \assert * \code seek_table != NULL \endcode * \retval unsigned * The number of duplicate seek points converted into placeholders. */ FLAC_API unsigned FLAC__format_seektable_sort(FLAC__StreamMetadata_SeekTable *seek_table); /** Check a cue sheet to see if it conforms to the FLAC specification. * See the format specification for limits on the contents of the * cue sheet. * * \param cue_sheet A pointer to an existing cue sheet to be checked. * \param check_cd_da_subset If \c true, check CUESHEET against more * stringent requirements for a CD-DA (audio) disc. * \param violation Address of a pointer to a string. If there is a * violation, a pointer to a string explanation of the * violation will be returned here. \a violation may be * \c NULL if you don't need the returned string. Do not * free the returned string; it will always point to static * data. * \assert * \code cue_sheet != NULL \endcode * \retval FLAC__bool * \c false if cue sheet is illegal, else \c true. */ FLAC_API FLAC__bool FLAC__format_cuesheet_is_legal(const FLAC__StreamMetadata_CueSheet *cue_sheet, FLAC__bool check_cd_da_subset, const char **violation); /** Check picture data to see if it conforms to the FLAC specification. * See the format specification for limits on the contents of the * PICTURE block. * * \param picture A pointer to existing picture data to be checked. * \param violation Address of a pointer to a string. If there is a * violation, a pointer to a string explanation of the * violation will be returned here. \a violation may be * \c NULL if you don't need the returned string. Do not * free the returned string; it will always point to static * data. * \assert * \code picture != NULL \endcode * \retval FLAC__bool * \c false if picture data is illegal, else \c true. */ FLAC_API FLAC__bool FLAC__format_picture_is_legal(const FLAC__StreamMetadata_Picture *picture, const char **violation); /* \} */ // pb 20080502 #ifdef _WIN32 wchar_t * Melder_peekUtf8ToWcs (const char *string); const uint16_t * Melder_peekWcsToUtf16 (const wchar_t *string); #define fopen(filename,mode) _wfopen (Melder_peekWcsToUtf16 (Melder_peekUtf8ToWcs (filename)), L"" mode) #endif #ifdef __cplusplus } #endif #endif sources_5316/external/flac/flac_private_cpu.h0000644000176700017670000000526410720650277020146 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__CPU_H #define FLAC__PRIVATE__CPU_H #include "flac_FLAC_ordinals.h" #include "flac_private_autocpu.h" #ifdef HAVE_CONFIG_H #include #endif typedef enum { FLAC__CPUINFO_TYPE_IA32, FLAC__CPUINFO_TYPE_PPC, FLAC__CPUINFO_TYPE_UNKNOWN } FLAC__CPUInfo_Type; typedef struct { FLAC__bool cpuid; FLAC__bool bswap; FLAC__bool cmov; FLAC__bool mmx; FLAC__bool fxsr; FLAC__bool sse; FLAC__bool sse2; FLAC__bool sse3; FLAC__bool ssse3; FLAC__bool _3dnow; FLAC__bool ext3dnow; FLAC__bool extmmx; } FLAC__CPUInfo_IA32; typedef struct { FLAC__bool altivec; FLAC__bool ppc64; } FLAC__CPUInfo_PPC; typedef struct { FLAC__bool use_asm; FLAC__CPUInfo_Type type; union { FLAC__CPUInfo_IA32 ia32; FLAC__CPUInfo_PPC ppc; } data; } FLAC__CPUInfo; void FLAC__cpu_info(FLAC__CPUInfo *info); #ifndef FLAC__NO_ASM #ifdef FLAC__CPU_IA32 #ifdef FLAC__HAS_NASM FLAC__uint32 FLAC__cpu_have_cpuid_asm_ia32(void); void FLAC__cpu_info_asm_ia32(FLAC__uint32 *flags_edx, FLAC__uint32 *flags_ecx); FLAC__uint32 FLAC__cpu_info_extended_amd_asm_ia32(void); #endif #endif #endif #endif sources_5316/external/flac/flac_private_crc.h0000644000176700017670000000512210720607255020115 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__CRC_H #define FLAC__PRIVATE__CRC_H #include "flac_FLAC_ordinals.h" /* 8 bit CRC generator, MSB shifted first ** polynomial = x^8 + x^2 + x^1 + x^0 ** init = 0 */ extern FLAC__byte const FLAC__crc8_table[256]; #define FLAC__CRC8_UPDATE(data, crc) (crc) = FLAC__crc8_table[(crc) ^ (data)]; void FLAC__crc8_update(const FLAC__byte data, FLAC__uint8 *crc); void FLAC__crc8_update_block(const FLAC__byte *data, unsigned len, FLAC__uint8 *crc); FLAC__uint8 FLAC__crc8(const FLAC__byte *data, unsigned len); /* 16 bit CRC generator, MSB shifted first ** polynomial = x^16 + x^15 + x^2 + x^0 ** init = 0 */ extern unsigned FLAC__crc16_table[256]; #define FLAC__CRC16_UPDATE(data, crc) (((((crc)<<8) & 0xffff) ^ FLAC__crc16_table[((crc)>>8) ^ (data)])) /* this alternate may be faster on some systems/compilers */ #if 0 #define FLAC__CRC16_UPDATE(data, crc) ((((crc)<<8) ^ FLAC__crc16_table[((crc)>>8) ^ (data)]) & 0xffff) #endif unsigned FLAC__crc16(const FLAC__byte *data, unsigned len); #endif sources_5316/external/flac/flac_private_all.h0000644000176700017670000000412410720607255020117 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__ALL_H #define FLAC__PRIVATE__ALL_H #include "flac_private_bitmath.h" #include "flac_private_bitreader.h" #include "flac_private_bitwriter.h" #include "flac_private_cpu.h" #include "flac_private_crc.h" #include "flac_private_fixed.h" #include "flac_private_float.h" #include "flac_private_format.h" #include "flac_private_lpc.h" #include "flac_private_md5.h" #include "flac_private_memory.h" #include "flac_private_metadata.h" #include "flac_private_stream_encoder_framing.h" #endif sources_5316/external/flac/flac_share_alloc.h0000644000176700017670000001310411553625104020065 0ustar paulpaul/* alloc - Convenience routines for safely allocating memory * Copyright (C) 2007 Josh Coalson * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ #ifndef FLAC__SHARE__ALLOC_H #define FLAC__SHARE__ALLOC_H #if HAVE_CONFIG_H # include #endif /* WATCHOUT: for c++ you may have to #define __STDC_LIMIT_MACROS 1 real early * before #including this file, otherwise SIZE_MAX might not be defined */ #include /* for SIZE_MAX */ #if !defined _MSC_VER && !defined __EMX__ #include /* for SIZE_MAX in case limits.h didn't get it */ #endif #include /* for size_t, malloc(), etc */ #ifndef SIZE_MAX # ifndef SIZE_T_MAX # ifdef _MSC_VER # define SIZE_T_MAX UINT_MAX # else # error # endif # endif # define SIZE_MAX SIZE_T_MAX #endif #ifndef FLaC__INLINE #define FLaC__INLINE inline // ppgb 20071120 #endif /* avoid malloc()ing 0 bytes, see: * https://www.securecoding.cert.org/confluence/display/seccode/MEM04-A.+Do+not+make+assumptions+about+the+result+of+allocating+0+bytes?focusedCommentId=5407003 */ static FLaC__INLINE void *safe_malloc_(size_t size) { /* malloc(0) is undefined; FLAC src convention is to always allocate */ if(!size) size++; return malloc(size); } static FLaC__INLINE void *safe_calloc_(size_t nmemb, size_t size) { if(!nmemb || !size) return malloc(1); /* malloc(0) is undefined; FLAC src convention is to always allocate */ return calloc(nmemb, size); } /*@@@@ there's probably a better way to prevent overflows when allocating untrusted sums but this works for now */ static FLaC__INLINE void *safe_malloc_add_2op_(size_t size1, size_t size2) { size2 += size1; if(size2 < size1) return 0; return safe_malloc_(size2); } static FLaC__INLINE void *safe_malloc_add_3op_(size_t size1, size_t size2, size_t size3) { size2 += size1; if(size2 < size1) return 0; size3 += size2; if(size3 < size2) return 0; return safe_malloc_(size3); } static FLaC__INLINE void *safe_malloc_add_4op_(size_t size1, size_t size2, size_t size3, size_t size4) { size2 += size1; if(size2 < size1) return 0; size3 += size2; if(size3 < size2) return 0; size4 += size3; if(size4 < size3) return 0; return safe_malloc_(size4); } static FLaC__INLINE void *safe_malloc_mul_2op_(size_t size1, size_t size2) #if 0 needs support for cases where sizeof(size_t) != 4 { /* could be faster #ifdef'ing off SIZEOF_SIZE_T */ if(sizeof(size_t) == 4) { if ((double)size1 * (double)size2 < 4294967296.0) return malloc(size1*size2); } return 0; } #else /* better? */ { if(!size1 || !size2) return malloc(1); /* malloc(0) is undefined; FLAC src convention is to always allocate */ if(size1 > SIZE_MAX / size2) return 0; return malloc(size1*size2); } #endif static FLaC__INLINE void *safe_malloc_mul_3op_(size_t size1, size_t size2, size_t size3) { if(!size1 || !size2 || !size3) return malloc(1); /* malloc(0) is undefined; FLAC src convention is to always allocate */ if(size1 > SIZE_MAX / size2) return 0; size1 *= size2; if(size1 > SIZE_MAX / size3) return 0; return malloc(size1*size3); } /* size1*size2 + size3 */ static FLaC__INLINE void *safe_malloc_mul2add_(size_t size1, size_t size2, size_t size3) { if(!size1 || !size2) return safe_malloc_(size3); if(size1 > SIZE_MAX / size2) return 0; return safe_malloc_add_2op_(size1*size2, size3); } /* size1 * (size2 + size3) */ static FLaC__INLINE void *safe_malloc_muladd2_(size_t size1, size_t size2, size_t size3) { if(!size1 || (!size2 && !size3)) return malloc(1); /* malloc(0) is undefined; FLAC src convention is to always allocate */ size2 += size3; if(size2 < size3) return 0; return safe_malloc_mul_2op_(size1, size2); } static FLaC__INLINE void *safe_realloc_add_2op_(void *ptr, size_t size1, size_t size2) { size2 += size1; if(size2 < size1) return 0; return realloc(ptr, size2); } static FLaC__INLINE void *safe_realloc_add_3op_(void *ptr, size_t size1, size_t size2, size_t size3) { size2 += size1; if(size2 < size1) return 0; size3 += size2; if(size3 < size2) return 0; return realloc(ptr, size3); } static FLaC__INLINE void *safe_realloc_add_4op_(void *ptr, size_t size1, size_t size2, size_t size3, size_t size4) { size2 += size1; if(size2 < size1) return 0; size3 += size2; if(size3 < size2) return 0; size4 += size3; if(size4 < size3) return 0; return realloc(ptr, size4); } static FLaC__INLINE void *safe_realloc_mul_2op_(void *ptr, size_t size1, size_t size2) { if(!size1 || !size2) return realloc(ptr, 0); /* preserve POSIX realloc(ptr, 0) semantics */ if(size1 > SIZE_MAX / size2) return 0; return realloc(ptr, size1*size2); } /* size1 * (size2 + size3) */ static FLaC__INLINE void *safe_realloc_muladd2_(void *ptr, size_t size1, size_t size2, size_t size3) { if(!size1 || (!size2 && !size3)) return realloc(ptr, 0); /* preserve POSIX realloc(ptr, 0) semantics */ size2 += size3; if(size2 < size3) return 0; return safe_realloc_mul_2op_(ptr, size1, size2); } #endif sources_5316/external/flac/flac_private_bitreader.h0000644000176700017670000001141510720606571021311 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__BITREADER_H #define FLAC__PRIVATE__BITREADER_H #include /* for FILE */ #include "flac_FLAC_ordinals.h" #include "flac_private_cpu.h" /* * opaque structure definition */ struct FLAC__BitReader; typedef struct FLAC__BitReader FLAC__BitReader; typedef FLAC__bool (*FLAC__BitReaderReadCallback)(FLAC__byte buffer[], size_t *bytes, void *client_data); /* * construction, deletion, initialization, etc functions */ FLAC__BitReader *FLAC__bitreader_new(void); void FLAC__bitreader_delete(FLAC__BitReader *br); FLAC__bool FLAC__bitreader_init(FLAC__BitReader *br, FLAC__CPUInfo cpu, FLAC__BitReaderReadCallback rcb, void *cd); void FLAC__bitreader_free(FLAC__BitReader *br); /* does not 'free(br)' */ FLAC__bool FLAC__bitreader_clear(FLAC__BitReader *br); void FLAC__bitreader_dump(const FLAC__BitReader *br, FILE *out); /* * CRC functions */ void FLAC__bitreader_reset_read_crc16(FLAC__BitReader *br, FLAC__uint16 seed); FLAC__uint16 FLAC__bitreader_get_read_crc16(FLAC__BitReader *br); /* * info functions */ FLAC__bool FLAC__bitreader_is_consumed_byte_aligned(const FLAC__BitReader *br); unsigned FLAC__bitreader_bits_left_for_byte_alignment(const FLAC__BitReader *br); unsigned FLAC__bitreader_get_input_bits_unconsumed(const FLAC__BitReader *br); /* * read functions */ FLAC__bool FLAC__bitreader_read_raw_uint32(FLAC__BitReader *br, FLAC__uint32 *val, unsigned bits); FLAC__bool FLAC__bitreader_read_raw_int32(FLAC__BitReader *br, FLAC__int32 *val, unsigned bits); FLAC__bool FLAC__bitreader_read_raw_uint64(FLAC__BitReader *br, FLAC__uint64 *val, unsigned bits); FLAC__bool FLAC__bitreader_read_uint32_little_endian(FLAC__BitReader *br, FLAC__uint32 *val); /*only for bits=32*/ FLAC__bool FLAC__bitreader_skip_bits_no_crc(FLAC__BitReader *br, unsigned bits); /* WATCHOUT: does not CRC the skipped data! */ /*@@@@ add to unit tests */ FLAC__bool FLAC__bitreader_skip_byte_block_aligned_no_crc(FLAC__BitReader *br, unsigned nvals); /* WATCHOUT: does not CRC the read data! */ FLAC__bool FLAC__bitreader_read_byte_block_aligned_no_crc(FLAC__BitReader *br, FLAC__byte *val, unsigned nvals); /* WATCHOUT: does not CRC the read data! */ FLAC__bool FLAC__bitreader_read_unary_unsigned(FLAC__BitReader *br, unsigned *val); FLAC__bool FLAC__bitreader_read_rice_signed(FLAC__BitReader *br, int *val, unsigned parameter); FLAC__bool FLAC__bitreader_read_rice_signed_block(FLAC__BitReader *br, int vals[], unsigned nvals, unsigned parameter); #ifndef FLAC__NO_ASM # ifdef FLAC__CPU_IA32 # ifdef FLAC__HAS_NASM FLAC__bool FLAC__bitreader_read_rice_signed_block_asm_ia32_bswap(FLAC__BitReader *br, int vals[], unsigned nvals, unsigned parameter); # endif # endif #endif #if 0 /* UNUSED */ FLAC__bool FLAC__bitreader_read_golomb_signed(FLAC__BitReader *br, int *val, unsigned parameter); FLAC__bool FLAC__bitreader_read_golomb_unsigned(FLAC__BitReader *br, unsigned *val, unsigned parameter); #endif FLAC__bool FLAC__bitreader_read_utf8_uint32(FLAC__BitReader *br, FLAC__uint32 *val, FLAC__byte *raw, unsigned *rawlen); FLAC__bool FLAC__bitreader_read_utf8_uint64(FLAC__BitReader *br, FLAC__uint64 *val, FLAC__byte *raw, unsigned *rawlen); FLAC__bool bitreader_read_from_client_(FLAC__BitReader *br); #endif sources_5316/external/flac/flac_bitreader.c0000644000176700017670000012212210720617464017553 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include /* for malloc() */ #include /* for memcpy(), memset() */ #ifdef _WIN32 #include /* for ntohl() */ #elif defined macintosh #include /* for ntohl() */ #else #include /* for ntohl() */ #endif #include "flac_private_bitmath.h" #include "flac_private_bitreader.h" #include "flac_private_crc.h" #include "flac_FLAC_assert.h" /* Things should be fastest when this matches the machine word size */ /* WATCHOUT: if you change this you must also change the following #defines down to COUNT_ZERO_MSBS below to match */ /* WATCHOUT: there are a few places where the code will not work unless brword is >= 32 bits wide */ /* also, some sections currently only have fast versions for 4 or 8 bytes per word */ typedef FLAC__uint32 brword; #define FLAC__BYTES_PER_WORD 4 #define FLAC__BITS_PER_WORD 32 #define FLAC__WORD_ALL_ONES ((FLAC__uint32)0xffffffff) /* SWAP_BE_WORD_TO_HOST swaps bytes in a brword (which is always big-endian) if necessary to match host byte order */ #if WORDS_BIGENDIAN #define SWAP_BE_WORD_TO_HOST(x) (x) #else #ifdef _MSC_VER #define SWAP_BE_WORD_TO_HOST(x) local_swap32_(x) #else #define SWAP_BE_WORD_TO_HOST(x) ntohl(x) #endif #endif /* counts the # of zero MSBs in a word */ #define COUNT_ZERO_MSBS(word) ( \ (word) <= 0xffff ? \ ( (word) <= 0xff? byte_to_unary_table[word] + 24 : byte_to_unary_table[(word) >> 8] + 16 ) : \ ( (word) <= 0xffffff? byte_to_unary_table[word >> 16] + 8 : byte_to_unary_table[(word) >> 24] ) \ ) /* this alternate might be slightly faster on some systems/compilers: */ #define COUNT_ZERO_MSBS2(word) ( (word) <= 0xff ? byte_to_unary_table[word] + 24 : ((word) <= 0xffff ? byte_to_unary_table[(word) >> 8] + 16 : ((word) <= 0xffffff ? byte_to_unary_table[(word) >> 16] + 8 : byte_to_unary_table[(word) >> 24])) ) /* * This should be at least twice as large as the largest number of words * required to represent any 'number' (in any encoding) you are going to * read. With FLAC this is on the order of maybe a few hundred bits. * If the buffer is smaller than that, the decoder won't be able to read * in a whole number that is in a variable length encoding (e.g. Rice). * But to be practical it should be at least 1K bytes. * * Increase this number to decrease the number of read callbacks, at the * expense of using more memory. Or decrease for the reverse effect, * keeping in mind the limit from the first paragraph. The optimal size * also depends on the CPU cache size and other factors; some twiddling * may be necessary to squeeze out the best performance. */ static const unsigned FLAC__BITREADER_DEFAULT_CAPACITY = 65536u / FLAC__BITS_PER_WORD; /* in words */ static const unsigned char byte_to_unary_table[] = { 8, 7, 6, 6, 5, 5, 5, 5, 4, 4, 4, 4, 4, 4, 4, 4, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; #ifdef min #undef min #endif #define min(x,y) ((x)<(y)?(x):(y)) #ifdef max #undef max #endif #define max(x,y) ((x)>(y)?(x):(y)) /* adjust for compilers that can't understand using LLU suffix for uint64_t literals */ #ifdef _MSC_VER #define FLAC__U64L(x) x #else #define FLAC__U64L(x) x##LLU #endif #ifndef FLaC__INLINE #define FLaC__INLINE #endif /* WATCHOUT: assembly routines rely on the order in which these fields are declared */ struct FLAC__BitReader { /* any partially-consumed word at the head will stay right-justified as bits are consumed from the left */ /* any incomplete word at the tail will be left-justified, and bytes from the read callback are added on the right */ brword *buffer; unsigned capacity; /* in words */ unsigned words; /* # of completed words in buffer */ unsigned bytes; /* # of bytes in incomplete word at buffer[words] */ unsigned consumed_words; /* #words ... */ unsigned consumed_bits; /* ... + (#bits of head word) already consumed from the front of buffer */ unsigned read_crc16; /* the running frame CRC */ unsigned crc16_align; /* the number of bits in the current consumed word that should not be CRC'd */ FLAC__BitReaderReadCallback read_callback; void *client_data; FLAC__CPUInfo cpu_info; }; #ifdef _MSC_VER /* OPT: an MSVC built-in would be better */ static _inline FLAC__uint32 local_swap32_(FLAC__uint32 x) { x = ((x<<8)&0xFF00FF00) | ((x>>8)&0x00FF00FF); return (x>>16) | (x<<16); } static void local_swap32_block_(FLAC__uint32 *start, FLAC__uint32 len) { __asm { mov edx, start mov ecx, len test ecx, ecx loop1: jz done1 mov eax, [edx] bswap eax mov [edx], eax add edx, 4 dec ecx jmp short loop1 done1: } } #endif static FLaC__INLINE void crc16_update_word_(FLAC__BitReader *br, brword word) { register unsigned crc = br->read_crc16; #if FLAC__BYTES_PER_WORD == 4 switch(br->crc16_align) { case 0: crc = FLAC__CRC16_UPDATE((unsigned)(word >> 24), crc); case 8: crc = FLAC__CRC16_UPDATE((unsigned)((word >> 16) & 0xff), crc); case 16: crc = FLAC__CRC16_UPDATE((unsigned)((word >> 8) & 0xff), crc); case 24: br->read_crc16 = FLAC__CRC16_UPDATE((unsigned)(word & 0xff), crc); } #elif FLAC__BYTES_PER_WORD == 8 switch(br->crc16_align) { case 0: crc = FLAC__CRC16_UPDATE((unsigned)(word >> 56), crc); case 8: crc = FLAC__CRC16_UPDATE((unsigned)((word >> 48) & 0xff), crc); case 16: crc = FLAC__CRC16_UPDATE((unsigned)((word >> 40) & 0xff), crc); case 24: crc = FLAC__CRC16_UPDATE((unsigned)((word >> 32) & 0xff), crc); case 32: crc = FLAC__CRC16_UPDATE((unsigned)((word >> 24) & 0xff), crc); case 40: crc = FLAC__CRC16_UPDATE((unsigned)((word >> 16) & 0xff), crc); case 48: crc = FLAC__CRC16_UPDATE((unsigned)((word >> 8) & 0xff), crc); case 56: br->read_crc16 = FLAC__CRC16_UPDATE((unsigned)(word & 0xff), crc); } #else for( ; br->crc16_align < FLAC__BITS_PER_WORD; br->crc16_align += 8) crc = FLAC__CRC16_UPDATE((unsigned)((word >> (FLAC__BITS_PER_WORD-8-br->crc16_align)) & 0xff), crc); br->read_crc16 = crc; #endif br->crc16_align = 0; } /* would be static except it needs to be called by asm routines */ FLAC__bool bitreader_read_from_client_(FLAC__BitReader *br) { unsigned start, end; size_t bytes; FLAC__byte *target; /* first shift the unconsumed buffer data toward the front as much as possible */ if(br->consumed_words > 0) { start = br->consumed_words; end = br->words + (br->bytes? 1:0); memmove(br->buffer, br->buffer+start, FLAC__BYTES_PER_WORD * (end - start)); br->words -= start; br->consumed_words = 0; } /* * set the target for reading, taking into account word alignment and endianness */ bytes = (br->capacity - br->words) * FLAC__BYTES_PER_WORD - br->bytes; if(bytes == 0) return false; /* no space left, buffer is too small; see note for FLAC__BITREADER_DEFAULT_CAPACITY */ target = ((FLAC__byte*)(br->buffer+br->words)) + br->bytes; /* before reading, if the existing reader looks like this (say brword is 32 bits wide) * bitstream : 11 22 33 44 55 br->words=1 br->bytes=1 (partial tail word is left-justified) * buffer[BE]: 11 22 33 44 55 ?? ?? ?? (shown layed out as bytes sequentially in memory) * buffer[LE]: 44 33 22 11 ?? ?? ?? 55 (?? being don't-care) * ^^-------target, bytes=3 * on LE machines, have to byteswap the odd tail word so nothing is * overwritten: */ #if WORDS_BIGENDIAN #else if(br->bytes) br->buffer[br->words] = SWAP_BE_WORD_TO_HOST(br->buffer[br->words]); #endif /* now it looks like: * bitstream : 11 22 33 44 55 br->words=1 br->bytes=1 * buffer[BE]: 11 22 33 44 55 ?? ?? ?? * buffer[LE]: 44 33 22 11 55 ?? ?? ?? * ^^-------target, bytes=3 */ /* read in the data; note that the callback may return a smaller number of bytes */ if(!br->read_callback(target, &bytes, br->client_data)) return false; /* after reading bytes 66 77 88 99 AA BB CC DD EE FF from the client: * bitstream : 11 22 33 44 55 66 77 88 99 AA BB CC DD EE FF * buffer[BE]: 11 22 33 44 55 66 77 88 99 AA BB CC DD EE FF ?? * buffer[LE]: 44 33 22 11 55 66 77 88 99 AA BB CC DD EE FF ?? * now have to byteswap on LE machines: */ #if WORDS_BIGENDIAN #else end = (br->words*FLAC__BYTES_PER_WORD + br->bytes + bytes + (FLAC__BYTES_PER_WORD-1)) / FLAC__BYTES_PER_WORD; # if defined(_MSC_VER) && (FLAC__BYTES_PER_WORD == 4) if(br->cpu_info.type == FLAC__CPUINFO_TYPE_IA32 && br->cpu_info.data.ia32.bswap) { start = br->words; local_swap32_block_(br->buffer + start, end - start); } else # endif for(start = br->words; start < end; start++) br->buffer[start] = SWAP_BE_WORD_TO_HOST(br->buffer[start]); #endif /* now it looks like: * bitstream : 11 22 33 44 55 66 77 88 99 AA BB CC DD EE FF * buffer[BE]: 11 22 33 44 55 66 77 88 99 AA BB CC DD EE FF ?? * buffer[LE]: 44 33 22 11 88 77 66 55 CC BB AA 99 ?? FF EE DD * finally we'll update the reader values: */ end = br->words*FLAC__BYTES_PER_WORD + br->bytes + bytes; br->words = end / FLAC__BYTES_PER_WORD; br->bytes = end % FLAC__BYTES_PER_WORD; return true; } /*********************************************************************** * * Class constructor/destructor * ***********************************************************************/ FLAC__BitReader *FLAC__bitreader_new(void) { FLAC__BitReader *br = (FLAC__BitReader*)calloc(1, sizeof(FLAC__BitReader)); /* calloc() implies: memset(br, 0, sizeof(FLAC__BitReader)); br->buffer = 0; br->capacity = 0; br->words = br->bytes = 0; br->consumed_words = br->consumed_bits = 0; br->read_callback = 0; br->client_data = 0; */ return br; } void FLAC__bitreader_delete(FLAC__BitReader *br) { FLAC__ASSERT(0 != br); FLAC__bitreader_free(br); free(br); } /*********************************************************************** * * Public class methods * ***********************************************************************/ FLAC__bool FLAC__bitreader_init(FLAC__BitReader *br, FLAC__CPUInfo cpu, FLAC__BitReaderReadCallback rcb, void *cd) { FLAC__ASSERT(0 != br); br->words = br->bytes = 0; br->consumed_words = br->consumed_bits = 0; br->capacity = FLAC__BITREADER_DEFAULT_CAPACITY; br->buffer = (brword*)malloc(sizeof(brword) * br->capacity); if(br->buffer == 0) return false; br->read_callback = rcb; br->client_data = cd; br->cpu_info = cpu; return true; } void FLAC__bitreader_free(FLAC__BitReader *br) { FLAC__ASSERT(0 != br); if(0 != br->buffer) free(br->buffer); br->buffer = 0; br->capacity = 0; br->words = br->bytes = 0; br->consumed_words = br->consumed_bits = 0; br->read_callback = 0; br->client_data = 0; } FLAC__bool FLAC__bitreader_clear(FLAC__BitReader *br) { br->words = br->bytes = 0; br->consumed_words = br->consumed_bits = 0; return true; } void FLAC__bitreader_dump(const FLAC__BitReader *br, FILE *out) { unsigned i, j; if(br == 0) { fprintf(out, "bitreader is NULL\n"); } else { fprintf(out, "bitreader: capacity=%u words=%u bytes=%u consumed: words=%u, bits=%u\n", br->capacity, br->words, br->bytes, br->consumed_words, br->consumed_bits); for(i = 0; i < br->words; i++) { fprintf(out, "%08X: ", i); for(j = 0; j < FLAC__BITS_PER_WORD; j++) if(i < br->consumed_words || (i == br->consumed_words && j < br->consumed_bits)) fprintf(out, "."); else fprintf(out, "%01u", br->buffer[i] & (1 << (FLAC__BITS_PER_WORD-j-1)) ? 1:0); fprintf(out, "\n"); } if(br->bytes > 0) { fprintf(out, "%08X: ", i); for(j = 0; j < br->bytes*8; j++) if(i < br->consumed_words || (i == br->consumed_words && j < br->consumed_bits)) fprintf(out, "."); else fprintf(out, "%01u", br->buffer[i] & (1 << (br->bytes*8-j-1)) ? 1:0); fprintf(out, "\n"); } } } void FLAC__bitreader_reset_read_crc16(FLAC__BitReader *br, FLAC__uint16 seed) { FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); FLAC__ASSERT((br->consumed_bits & 7) == 0); br->read_crc16 = (unsigned)seed; br->crc16_align = br->consumed_bits; } FLAC__uint16 FLAC__bitreader_get_read_crc16(FLAC__BitReader *br) { FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); FLAC__ASSERT((br->consumed_bits & 7) == 0); FLAC__ASSERT(br->crc16_align <= br->consumed_bits); /* CRC any tail bytes in a partially-consumed word */ if(br->consumed_bits) { const brword tail = br->buffer[br->consumed_words]; for( ; br->crc16_align < br->consumed_bits; br->crc16_align += 8) br->read_crc16 = FLAC__CRC16_UPDATE((unsigned)((tail >> (FLAC__BITS_PER_WORD-8-br->crc16_align)) & 0xff), br->read_crc16); } return br->read_crc16; } FLaC__INLINE FLAC__bool FLAC__bitreader_is_consumed_byte_aligned(const FLAC__BitReader *br) { return ((br->consumed_bits & 7) == 0); } FLaC__INLINE unsigned FLAC__bitreader_bits_left_for_byte_alignment(const FLAC__BitReader *br) { return 8 - (br->consumed_bits & 7); } FLaC__INLINE unsigned FLAC__bitreader_get_input_bits_unconsumed(const FLAC__BitReader *br) { return (br->words-br->consumed_words)*FLAC__BITS_PER_WORD + br->bytes*8 - br->consumed_bits; } FLaC__INLINE FLAC__bool FLAC__bitreader_read_raw_uint32(FLAC__BitReader *br, FLAC__uint32 *val, unsigned bits) { FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); FLAC__ASSERT(bits <= 32); FLAC__ASSERT((br->capacity*FLAC__BITS_PER_WORD) * 2 >= bits); FLAC__ASSERT(br->consumed_words <= br->words); /* WATCHOUT: code does not work with <32bit words; we can make things much faster with this assertion */ FLAC__ASSERT(FLAC__BITS_PER_WORD >= 32); if(bits == 0) { /* OPT: investigate if this can ever happen, maybe change to assertion */ *val = 0; return true; } while((br->words-br->consumed_words)*FLAC__BITS_PER_WORD + br->bytes*8 - br->consumed_bits < bits) { if(!bitreader_read_from_client_(br)) return false; } if(br->consumed_words < br->words) { /* if we've not consumed up to a partial tail word... */ /* OPT: taking out the consumed_bits==0 "else" case below might make things faster if less code allows the compiler to inline this function */ if(br->consumed_bits) { /* this also works when consumed_bits==0, it's just a little slower than necessary for that case */ const unsigned n = FLAC__BITS_PER_WORD - br->consumed_bits; const brword word = br->buffer[br->consumed_words]; if(bits < n) { *val = (word & (FLAC__WORD_ALL_ONES >> br->consumed_bits)) >> (n-bits); br->consumed_bits += bits; return true; } *val = word & (FLAC__WORD_ALL_ONES >> br->consumed_bits); bits -= n; crc16_update_word_(br, word); br->consumed_words++; br->consumed_bits = 0; if(bits) { /* if there are still bits left to read, there have to be less than 32 so they will all be in the next word */ *val <<= bits; *val |= (br->buffer[br->consumed_words] >> (FLAC__BITS_PER_WORD-bits)); br->consumed_bits = bits; } return true; } else { const brword word = br->buffer[br->consumed_words]; if(bits < FLAC__BITS_PER_WORD) { *val = word >> (FLAC__BITS_PER_WORD-bits); br->consumed_bits = bits; return true; } /* at this point 'bits' must be == FLAC__BITS_PER_WORD; because of previous assertions, it can't be larger */ *val = word; crc16_update_word_(br, word); br->consumed_words++; return true; } } else { /* in this case we're starting our read at a partial tail word; * the reader has guaranteed that we have at least 'bits' bits * available to read, which makes this case simpler. */ /* OPT: taking out the consumed_bits==0 "else" case below might make things faster if less code allows the compiler to inline this function */ if(br->consumed_bits) { /* this also works when consumed_bits==0, it's just a little slower than necessary for that case */ FLAC__ASSERT(br->consumed_bits + bits <= br->bytes*8); *val = (br->buffer[br->consumed_words] & (FLAC__WORD_ALL_ONES >> br->consumed_bits)) >> (FLAC__BITS_PER_WORD-br->consumed_bits-bits); br->consumed_bits += bits; return true; } else { *val = br->buffer[br->consumed_words] >> (FLAC__BITS_PER_WORD-bits); br->consumed_bits += bits; return true; } } } FLAC__bool FLAC__bitreader_read_raw_int32(FLAC__BitReader *br, FLAC__int32 *val, unsigned bits) { /* OPT: inline raw uint32 code here, or make into a macro if possible in the .h file */ if(!FLAC__bitreader_read_raw_uint32(br, (FLAC__uint32*)val, bits)) return false; /* sign-extend: */ *val <<= (32-bits); *val >>= (32-bits); return true; } FLAC__bool FLAC__bitreader_read_raw_uint64(FLAC__BitReader *br, FLAC__uint64 *val, unsigned bits) { FLAC__uint32 hi, lo; if(bits > 32) { if(!FLAC__bitreader_read_raw_uint32(br, &hi, bits-32)) return false; if(!FLAC__bitreader_read_raw_uint32(br, &lo, 32)) return false; *val = hi; *val <<= 32; *val |= lo; } else { if(!FLAC__bitreader_read_raw_uint32(br, &lo, bits)) return false; *val = lo; } return true; } FLaC__INLINE FLAC__bool FLAC__bitreader_read_uint32_little_endian(FLAC__BitReader *br, FLAC__uint32 *val) { FLAC__uint32 x8, x32 = 0; /* this doesn't need to be that fast as currently it is only used for vorbis comments */ if(!FLAC__bitreader_read_raw_uint32(br, &x32, 8)) return false; if(!FLAC__bitreader_read_raw_uint32(br, &x8, 8)) return false; x32 |= (x8 << 8); if(!FLAC__bitreader_read_raw_uint32(br, &x8, 8)) return false; x32 |= (x8 << 16); if(!FLAC__bitreader_read_raw_uint32(br, &x8, 8)) return false; x32 |= (x8 << 24); *val = x32; return true; } FLAC__bool FLAC__bitreader_skip_bits_no_crc(FLAC__BitReader *br, unsigned bits) { /* * OPT: a faster implementation is possible but probably not that useful * since this is only called a couple of times in the metadata readers. */ FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); if(bits > 0) { const unsigned n = br->consumed_bits & 7; unsigned m; FLAC__uint32 x; if(n != 0) { m = min(8-n, bits); if(!FLAC__bitreader_read_raw_uint32(br, &x, m)) return false; bits -= m; } m = bits / 8; if(m > 0) { if(!FLAC__bitreader_skip_byte_block_aligned_no_crc(br, m)) return false; bits %= 8; } if(bits > 0) { if(!FLAC__bitreader_read_raw_uint32(br, &x, bits)) return false; } } return true; } FLAC__bool FLAC__bitreader_skip_byte_block_aligned_no_crc(FLAC__BitReader *br, unsigned nvals) { FLAC__uint32 x; FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(br)); /* step 1: skip over partial head word to get word aligned */ while(nvals && br->consumed_bits) { /* i.e. run until we read 'nvals' bytes or we hit the end of the head word */ if(!FLAC__bitreader_read_raw_uint32(br, &x, 8)) return false; nvals--; } if(0 == nvals) return true; /* step 2: skip whole words in chunks */ while(nvals >= FLAC__BYTES_PER_WORD) { if(br->consumed_words < br->words) { br->consumed_words++; nvals -= FLAC__BYTES_PER_WORD; } else if(!bitreader_read_from_client_(br)) return false; } /* step 3: skip any remainder from partial tail bytes */ while(nvals) { if(!FLAC__bitreader_read_raw_uint32(br, &x, 8)) return false; nvals--; } return true; } FLAC__bool FLAC__bitreader_read_byte_block_aligned_no_crc(FLAC__BitReader *br, FLAC__byte *val, unsigned nvals) { FLAC__uint32 x; FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(br)); /* step 1: read from partial head word to get word aligned */ while(nvals && br->consumed_bits) { /* i.e. run until we read 'nvals' bytes or we hit the end of the head word */ if(!FLAC__bitreader_read_raw_uint32(br, &x, 8)) return false; *val++ = (FLAC__byte)x; nvals--; } if(0 == nvals) return true; /* step 2: read whole words in chunks */ while(nvals >= FLAC__BYTES_PER_WORD) { if(br->consumed_words < br->words) { const brword word = br->buffer[br->consumed_words++]; #if FLAC__BYTES_PER_WORD == 4 val[0] = (FLAC__byte)(word >> 24); val[1] = (FLAC__byte)(word >> 16); val[2] = (FLAC__byte)(word >> 8); val[3] = (FLAC__byte)word; #elif FLAC__BYTES_PER_WORD == 8 val[0] = (FLAC__byte)(word >> 56); val[1] = (FLAC__byte)(word >> 48); val[2] = (FLAC__byte)(word >> 40); val[3] = (FLAC__byte)(word >> 32); val[4] = (FLAC__byte)(word >> 24); val[5] = (FLAC__byte)(word >> 16); val[6] = (FLAC__byte)(word >> 8); val[7] = (FLAC__byte)word; #else for(x = 0; x < FLAC__BYTES_PER_WORD; x++) val[x] = (FLAC__byte)(word >> (8*(FLAC__BYTES_PER_WORD-x-1))); #endif val += FLAC__BYTES_PER_WORD; nvals -= FLAC__BYTES_PER_WORD; } else if(!bitreader_read_from_client_(br)) return false; } /* step 3: read any remainder from partial tail bytes */ while(nvals) { if(!FLAC__bitreader_read_raw_uint32(br, &x, 8)) return false; *val++ = (FLAC__byte)x; nvals--; } return true; } FLaC__INLINE FLAC__bool FLAC__bitreader_read_unary_unsigned(FLAC__BitReader *br, unsigned *val) #if 0 /* slow but readable version */ { unsigned bit; FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); *val = 0; while(1) { if(!FLAC__bitreader_read_bit(br, &bit)) return false; if(bit) break; else *val++; } return true; } #else { unsigned i; FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); *val = 0; while(1) { while(br->consumed_words < br->words) { /* if we've not consumed up to a partial tail word... */ brword b = br->buffer[br->consumed_words] << br->consumed_bits; if(b) { i = COUNT_ZERO_MSBS(b); *val += i; i++; br->consumed_bits += i; if(br->consumed_bits >= FLAC__BITS_PER_WORD) { /* faster way of testing if(br->consumed_bits == FLAC__BITS_PER_WORD) */ crc16_update_word_(br, br->buffer[br->consumed_words]); br->consumed_words++; br->consumed_bits = 0; } return true; } else { *val += FLAC__BITS_PER_WORD - br->consumed_bits; crc16_update_word_(br, br->buffer[br->consumed_words]); br->consumed_words++; br->consumed_bits = 0; /* didn't find stop bit yet, have to keep going... */ } } /* at this point we've eaten up all the whole words; have to try * reading through any tail bytes before calling the read callback. * this is a repeat of the above logic adjusted for the fact we * don't have a whole word. note though if the client is feeding * us data a byte at a time (unlikely), br->consumed_bits may not * be zero. */ if(br->bytes) { const unsigned end = br->bytes * 8; brword b = (br->buffer[br->consumed_words] & (FLAC__WORD_ALL_ONES << (FLAC__BITS_PER_WORD-end))) << br->consumed_bits; if(b) { i = COUNT_ZERO_MSBS(b); *val += i; i++; br->consumed_bits += i; FLAC__ASSERT(br->consumed_bits < FLAC__BITS_PER_WORD); return true; } else { *val += end - br->consumed_bits; br->consumed_bits += end; FLAC__ASSERT(br->consumed_bits < FLAC__BITS_PER_WORD); /* didn't find stop bit yet, have to keep going... */ } } if(!bitreader_read_from_client_(br)) return false; } } #endif FLAC__bool FLAC__bitreader_read_rice_signed(FLAC__BitReader *br, int *val, unsigned parameter) { FLAC__uint32 lsbs = 0; unsigned msbs = 0; unsigned uval; FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); FLAC__ASSERT(parameter <= 31); /* read the unary MSBs and end bit */ if(!FLAC__bitreader_read_unary_unsigned(br, &msbs)) return false; /* read the binary LSBs */ if(!FLAC__bitreader_read_raw_uint32(br, &lsbs, parameter)) return false; /* compose the value */ uval = (msbs << parameter) | lsbs; if(uval & 1) *val = -((int)(uval >> 1)) - 1; else *val = (int)(uval >> 1); return true; } /* this is by far the most heavily used reader call. it ain't pretty but it's fast */ /* a lot of the logic is copied, then adapted, from FLAC__bitreader_read_unary_unsigned() and FLAC__bitreader_read_raw_uint32() */ FLAC__bool FLAC__bitreader_read_rice_signed_block(FLAC__BitReader *br, int vals[], unsigned nvals, unsigned parameter) /* OPT: possibly faster version for use with MSVC */ #ifdef _MSC_VER { unsigned i; unsigned uval = 0; unsigned bits; /* the # of binary LSBs left to read to finish a rice codeword */ /* try and get br->consumed_words and br->consumed_bits into register; * must remember to flush them back to *br before calling other * bitwriter functions that use them, and before returning */ register unsigned cwords; register unsigned cbits; FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); /* WATCHOUT: code does not work with <32bit words; we can make things much faster with this assertion */ FLAC__ASSERT(FLAC__BITS_PER_WORD >= 32); FLAC__ASSERT(parameter < 32); /* the above two asserts also guarantee that the binary part never straddles more that 2 words, so we don't have to loop to read it */ if(nvals == 0) return true; cbits = br->consumed_bits; cwords = br->consumed_words; while(1) { /* read unary part */ while(1) { while(cwords < br->words) { /* if we've not consumed up to a partial tail word... */ brword b = br->buffer[cwords] << cbits; if(b) { #if 0 /* slower, probably due to bad register allocation... */ && defined FLAC__CPU_IA32 && !defined FLAC__NO_ASM && FLAC__BITS_PER_WORD == 32 __asm { bsr eax, b not eax and eax, 31 mov i, eax } #else i = COUNT_ZERO_MSBS(b); #endif uval += i; bits = parameter; i++; cbits += i; if(cbits == FLAC__BITS_PER_WORD) { crc16_update_word_(br, br->buffer[cwords]); cwords++; cbits = 0; } goto break1; } else { uval += FLAC__BITS_PER_WORD - cbits; crc16_update_word_(br, br->buffer[cwords]); cwords++; cbits = 0; /* didn't find stop bit yet, have to keep going... */ } } /* at this point we've eaten up all the whole words; have to try * reading through any tail bytes before calling the read callback. * this is a repeat of the above logic adjusted for the fact we * don't have a whole word. note though if the client is feeding * us data a byte at a time (unlikely), br->consumed_bits may not * be zero. */ if(br->bytes) { const unsigned end = br->bytes * 8; brword b = (br->buffer[cwords] & (FLAC__WORD_ALL_ONES << (FLAC__BITS_PER_WORD-end))) << cbits; if(b) { i = COUNT_ZERO_MSBS(b); uval += i; bits = parameter; i++; cbits += i; FLAC__ASSERT(cbits < FLAC__BITS_PER_WORD); goto break1; } else { uval += end - cbits; cbits += end; FLAC__ASSERT(cbits < FLAC__BITS_PER_WORD); /* didn't find stop bit yet, have to keep going... */ } } /* flush registers and read; bitreader_read_from_client_() does * not touch br->consumed_bits at all but we still need to set * it in case it fails and we have to return false. */ br->consumed_bits = cbits; br->consumed_words = cwords; if(!bitreader_read_from_client_(br)) return false; cwords = br->consumed_words; } break1: /* read binary part */ FLAC__ASSERT(cwords <= br->words); if(bits) { while((br->words-cwords)*FLAC__BITS_PER_WORD + br->bytes*8 - cbits < bits) { /* flush registers and read; bitreader_read_from_client_() does * not touch br->consumed_bits at all but we still need to set * it in case it fails and we have to return false. */ br->consumed_bits = cbits; br->consumed_words = cwords; if(!bitreader_read_from_client_(br)) return false; cwords = br->consumed_words; } if(cwords < br->words) { /* if we've not consumed up to a partial tail word... */ if(cbits) { /* this also works when consumed_bits==0, it's just a little slower than necessary for that case */ const unsigned n = FLAC__BITS_PER_WORD - cbits; const brword word = br->buffer[cwords]; if(bits < n) { uval <<= bits; uval |= (word & (FLAC__WORD_ALL_ONES >> cbits)) >> (n-bits); cbits += bits; goto break2; } uval <<= n; uval |= word & (FLAC__WORD_ALL_ONES >> cbits); bits -= n; crc16_update_word_(br, word); cwords++; cbits = 0; if(bits) { /* if there are still bits left to read, there have to be less than 32 so they will all be in the next word */ uval <<= bits; uval |= (br->buffer[cwords] >> (FLAC__BITS_PER_WORD-bits)); cbits = bits; } goto break2; } else { FLAC__ASSERT(bits < FLAC__BITS_PER_WORD); uval <<= bits; uval |= br->buffer[cwords] >> (FLAC__BITS_PER_WORD-bits); cbits = bits; goto break2; } } else { /* in this case we're starting our read at a partial tail word; * the reader has guaranteed that we have at least 'bits' bits * available to read, which makes this case simpler. */ uval <<= bits; if(cbits) { /* this also works when consumed_bits==0, it's just a little slower than necessary for that case */ FLAC__ASSERT(cbits + bits <= br->bytes*8); uval |= (br->buffer[cwords] & (FLAC__WORD_ALL_ONES >> cbits)) >> (FLAC__BITS_PER_WORD-cbits-bits); cbits += bits; goto break2; } else { uval |= br->buffer[cwords] >> (FLAC__BITS_PER_WORD-bits); cbits += bits; goto break2; } } } break2: /* compose the value */ *vals = (int)(uval >> 1 ^ -(int)(uval & 1)); /* are we done? */ --nvals; if(nvals == 0) { br->consumed_bits = cbits; br->consumed_words = cwords; return true; } uval = 0; ++vals; } } #else { unsigned i; unsigned uval = 0; /* try and get br->consumed_words and br->consumed_bits into register; * must remember to flush them back to *br before calling other * bitwriter functions that use them, and before returning */ register unsigned cwords; register unsigned cbits; unsigned ucbits; /* keep track of the number of unconsumed bits in the buffer */ FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); /* WATCHOUT: code does not work with <32bit words; we can make things much faster with this assertion */ FLAC__ASSERT(FLAC__BITS_PER_WORD >= 32); FLAC__ASSERT(parameter < 32); /* the above two asserts also guarantee that the binary part never straddles more than 2 words, so we don't have to loop to read it */ if(nvals == 0) return true; cbits = br->consumed_bits; cwords = br->consumed_words; ucbits = (br->words-cwords)*FLAC__BITS_PER_WORD + br->bytes*8 - cbits; while(1) { /* read unary part */ while(1) { while(cwords < br->words) { /* if we've not consumed up to a partial tail word... */ brword b = br->buffer[cwords] << cbits; if(b) { #if 0 /* is not discernably faster... */ && defined FLAC__CPU_IA32 && !defined FLAC__NO_ASM && FLAC__BITS_PER_WORD == 32 && defined __GNUC__ asm volatile ( "bsrl %1, %0;" "notl %0;" "andl $31, %0;" : "=r"(i) : "r"(b) ); #else i = COUNT_ZERO_MSBS(b); #endif uval += i; cbits += i; cbits++; /* skip over stop bit */ if(cbits >= FLAC__BITS_PER_WORD) { /* faster way of testing if(cbits == FLAC__BITS_PER_WORD) */ crc16_update_word_(br, br->buffer[cwords]); cwords++; cbits = 0; } goto break1; } else { uval += FLAC__BITS_PER_WORD - cbits; crc16_update_word_(br, br->buffer[cwords]); cwords++; cbits = 0; /* didn't find stop bit yet, have to keep going... */ } } /* at this point we've eaten up all the whole words; have to try * reading through any tail bytes before calling the read callback. * this is a repeat of the above logic adjusted for the fact we * don't have a whole word. note though if the client is feeding * us data a byte at a time (unlikely), br->consumed_bits may not * be zero. */ if(br->bytes) { const unsigned end = br->bytes * 8; brword b = (br->buffer[cwords] & ~(FLAC__WORD_ALL_ONES >> end)) << cbits; if(b) { i = COUNT_ZERO_MSBS(b); uval += i; cbits += i; cbits++; /* skip over stop bit */ FLAC__ASSERT(cbits < FLAC__BITS_PER_WORD); goto break1; } else { uval += end - cbits; cbits += end; FLAC__ASSERT(cbits < FLAC__BITS_PER_WORD); /* didn't find stop bit yet, have to keep going... */ } } /* flush registers and read; bitreader_read_from_client_() does * not touch br->consumed_bits at all but we still need to set * it in case it fails and we have to return false. */ br->consumed_bits = cbits; br->consumed_words = cwords; if(!bitreader_read_from_client_(br)) return false; cwords = br->consumed_words; ucbits = (br->words-cwords)*FLAC__BITS_PER_WORD + br->bytes*8 - cbits + uval; /* + uval to offset our count by the # of unary bits already * consumed before the read, because we will add these back * in all at once at break1 */ } break1: ucbits -= uval; ucbits--; /* account for stop bit */ /* read binary part */ FLAC__ASSERT(cwords <= br->words); if(parameter) { while(ucbits < parameter) { /* flush registers and read; bitreader_read_from_client_() does * not touch br->consumed_bits at all but we still need to set * it in case it fails and we have to return false. */ br->consumed_bits = cbits; br->consumed_words = cwords; if(!bitreader_read_from_client_(br)) return false; cwords = br->consumed_words; ucbits = (br->words-cwords)*FLAC__BITS_PER_WORD + br->bytes*8 - cbits; } if(cwords < br->words) { /* if we've not consumed up to a partial tail word... */ if(cbits) { /* this also works when consumed_bits==0, it's just slower than necessary for that case */ const unsigned n = FLAC__BITS_PER_WORD - cbits; const brword word = br->buffer[cwords]; if(parameter < n) { uval <<= parameter; uval |= (word & (FLAC__WORD_ALL_ONES >> cbits)) >> (n-parameter); cbits += parameter; } else { uval <<= n; uval |= word & (FLAC__WORD_ALL_ONES >> cbits); crc16_update_word_(br, word); cwords++; cbits = parameter - n; if(cbits) { /* parameter > n, i.e. if there are still bits left to read, there have to be less than 32 so they will all be in the next word */ uval <<= cbits; uval |= (br->buffer[cwords] >> (FLAC__BITS_PER_WORD-cbits)); } } } else { cbits = parameter; uval <<= parameter; uval |= br->buffer[cwords] >> (FLAC__BITS_PER_WORD-cbits); } } else { /* in this case we're starting our read at a partial tail word; * the reader has guaranteed that we have at least 'parameter' * bits available to read, which makes this case simpler. */ uval <<= parameter; if(cbits) { /* this also works when consumed_bits==0, it's just a little slower than necessary for that case */ FLAC__ASSERT(cbits + parameter <= br->bytes*8); uval |= (br->buffer[cwords] & (FLAC__WORD_ALL_ONES >> cbits)) >> (FLAC__BITS_PER_WORD-cbits-parameter); cbits += parameter; } else { cbits = parameter; uval |= br->buffer[cwords] >> (FLAC__BITS_PER_WORD-cbits); } } } ucbits -= parameter; /* compose the value */ *vals = (int)(uval >> 1 ^ -(int)(uval & 1)); /* are we done? */ --nvals; if(nvals == 0) { br->consumed_bits = cbits; br->consumed_words = cwords; return true; } uval = 0; ++vals; } } #endif #if 0 /* UNUSED */ FLAC__bool FLAC__bitreader_read_golomb_signed(FLAC__BitReader *br, int *val, unsigned parameter) { FLAC__uint32 lsbs = 0, msbs = 0; unsigned bit, uval, k; FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); k = FLAC__bitmath_ilog2(parameter); /* read the unary MSBs and end bit */ if(!FLAC__bitreader_read_unary_unsigned(br, &msbs)) return false; /* read the binary LSBs */ if(!FLAC__bitreader_read_raw_uint32(br, &lsbs, k)) return false; if(parameter == 1u<= d) { if(!FLAC__bitreader_read_bit(br, &bit)) return false; lsbs <<= 1; lsbs |= bit; lsbs -= d; } /* compose the value */ uval = msbs * parameter + lsbs; } /* unfold unsigned to signed */ if(uval & 1) *val = -((int)(uval >> 1)) - 1; else *val = (int)(uval >> 1); return true; } FLAC__bool FLAC__bitreader_read_golomb_unsigned(FLAC__BitReader *br, unsigned *val, unsigned parameter) { FLAC__uint32 lsbs, msbs = 0; unsigned bit, k; FLAC__ASSERT(0 != br); FLAC__ASSERT(0 != br->buffer); k = FLAC__bitmath_ilog2(parameter); /* read the unary MSBs and end bit */ if(!FLAC__bitreader_read_unary_unsigned(br, &msbs)) return false; /* read the binary LSBs */ if(!FLAC__bitreader_read_raw_uint32(br, &lsbs, k)) return false; if(parameter == 1u<= d) { if(!FLAC__bitreader_read_bit(br, &bit)) return false; lsbs <<= 1; lsbs |= bit; lsbs -= d; } /* compose the value */ *val = msbs * parameter + lsbs; } return true; } #endif /* UNUSED */ /* on return, if *val == 0xffffffff then the utf-8 sequence was invalid, but the return value will be true */ FLAC__bool FLAC__bitreader_read_utf8_uint32(FLAC__BitReader *br, FLAC__uint32 *val, FLAC__byte *raw, unsigned *rawlen) { FLAC__uint32 v = 0; FLAC__uint32 x; unsigned i; if(!FLAC__bitreader_read_raw_uint32(br, &x, 8)) return false; if(raw) raw[(*rawlen)++] = (FLAC__byte)x; if(!(x & 0x80)) { /* 0xxxxxxx */ v = x; i = 0; } else if(x & 0xC0 && !(x & 0x20)) { /* 110xxxxx */ v = x & 0x1F; i = 1; } else if(x & 0xE0 && !(x & 0x10)) { /* 1110xxxx */ v = x & 0x0F; i = 2; } else if(x & 0xF0 && !(x & 0x08)) { /* 11110xxx */ v = x & 0x07; i = 3; } else if(x & 0xF8 && !(x & 0x04)) { /* 111110xx */ v = x & 0x03; i = 4; } else if(x & 0xFC && !(x & 0x02)) { /* 1111110x */ v = x & 0x01; i = 5; } else { *val = 0xffffffff; return true; } for( ; i; i--) { if(!FLAC__bitreader_read_raw_uint32(br, &x, 8)) return false; if(raw) raw[(*rawlen)++] = (FLAC__byte)x; if(!(x & 0x80) || (x & 0x40)) { /* 10xxxxxx */ *val = 0xffffffff; return true; } v <<= 6; v |= (x & 0x3F); } *val = v; return true; } /* on return, if *val == 0xffffffffffffffff then the utf-8 sequence was invalid, but the return value will be true */ FLAC__bool FLAC__bitreader_read_utf8_uint64(FLAC__BitReader *br, FLAC__uint64 *val, FLAC__byte *raw, unsigned *rawlen) { FLAC__uint64 v = 0; FLAC__uint32 x; unsigned i; if(!FLAC__bitreader_read_raw_uint32(br, &x, 8)) return false; if(raw) raw[(*rawlen)++] = (FLAC__byte)x; if(!(x & 0x80)) { /* 0xxxxxxx */ v = x; i = 0; } else if(x & 0xC0 && !(x & 0x20)) { /* 110xxxxx */ v = x & 0x1F; i = 1; } else if(x & 0xE0 && !(x & 0x10)) { /* 1110xxxx */ v = x & 0x0F; i = 2; } else if(x & 0xF0 && !(x & 0x08)) { /* 11110xxx */ v = x & 0x07; i = 3; } else if(x & 0xF8 && !(x & 0x04)) { /* 111110xx */ v = x & 0x03; i = 4; } else if(x & 0xFC && !(x & 0x02)) { /* 1111110x */ v = x & 0x01; i = 5; } else if(x & 0xFE && !(x & 0x01)) { /* 11111110 */ v = 0; i = 6; } else { *val = FLAC__U64L(0xffffffffffffffff); return true; } for( ; i; i--) { if(!FLAC__bitreader_read_raw_uint32(br, &x, 8)) return false; if(raw) raw[(*rawlen)++] = (FLAC__byte)x; if(!(x & 0x80) || (x & 0x40)) { /* 10xxxxxx */ *val = FLAC__U64L(0xffffffffffffffff); return true; } v <<= 6; v |= (x & 0x3F); } *val = v; return true; } sources_5316/external/flac/flac_FLAC_assert.h0000644000176700017670000000367110560556375017721 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__ASSERT_H #define FLAC__ASSERT_H /* we need this since some compilers (like MSVC) leave assert()s on release code (and we don't want to use their ASSERT) */ #ifdef DEBUG #include #define FLAC__ASSERT(x) assert(x) #define FLAC__ASSERT_DECLARATION(x) x #else #define FLAC__ASSERT(x) #define FLAC__ASSERT_DECLARATION(x) #endif #endif sources_5316/external/flac/flac_FLAC_all.h0000644000176700017670000003724210720606357017163 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__ALL_H #define FLAC__ALL_H #include "flac_FLAC_export.h" #include "flac_FLAC_assert.h" #include "flac_FLAC_callback.h" #include "flac_FLAC_format.h" #include "flac_FLAC_metadata.h" #include "flac_FLAC_ordinals.h" #include "flac_FLAC_stream_decoder.h" #include "flac_FLAC_stream_encoder.h" /** \mainpage * * \section intro Introduction * * This is the documentation for the FLAC C and C++ APIs. It is * highly interconnected; this introduction should give you a top * level idea of the structure and how to find the information you * need. As a prerequisite you should have at least a basic * knowledge of the FLAC format, documented * here. * * \section c_api FLAC C API * * The FLAC C API is the interface to libFLAC, a set of structures * describing the components of FLAC streams, and functions for * encoding and decoding streams, as well as manipulating FLAC * metadata in files. The public include files will be installed * in your include area (for example /usr/include/FLAC/...). * * By writing a little code and linking against libFLAC, it is * relatively easy to add FLAC support to another program. The * library is licensed under Xiph's BSD license. * Complete source code of libFLAC as well as the command-line * encoder and plugins is available and is a useful source of * examples. * * Aside from encoders and decoders, libFLAC provides a powerful * metadata interface for manipulating metadata in FLAC files. It * allows the user to add, delete, and modify FLAC metadata blocks * and it can automatically take advantage of PADDING blocks to avoid * rewriting the entire FLAC file when changing the size of the * metadata. * * libFLAC usually only requires the standard C library and C math * library. In particular, threading is not used so there is no * dependency on a thread library. However, libFLAC does not use * global variables and should be thread-safe. * * libFLAC also supports encoding to and decoding from Ogg FLAC. * However the metadata editing interfaces currently have limited * read-only support for Ogg FLAC files. * * \section cpp_api FLAC C++ API * * The FLAC C++ API is a set of classes that encapsulate the * structures and functions in libFLAC. They provide slightly more * functionality with respect to metadata but are otherwise * equivalent. For the most part, they share the same usage as * their counterparts in libFLAC, and the FLAC C API documentation * can be used as a supplement. The public include files * for the C++ API will be installed in your include area (for * example /usr/include/FLAC++/...). * * libFLAC++ is also licensed under * Xiph's BSD license. * * \section getting_started Getting Started * * A good starting point for learning the API is to browse through * the modules. Modules are logical * groupings of related functions or classes, which correspond roughly * to header files or sections of header files. Each module includes a * detailed description of the general usage of its functions or * classes. * * From there you can go on to look at the documentation of * individual functions. You can see different views of the individual * functions through the links in top bar across this page. * * If you prefer a more hands-on approach, you can jump right to some * example code. * * \section porting_guide Porting Guide * * Starting with FLAC 1.1.3 a \link porting Porting Guide \endlink * has been introduced which gives detailed instructions on how to * port your code to newer versions of FLAC. * * \section embedded_developers Embedded Developers * * libFLAC has grown larger over time as more functionality has been * included, but much of it may be unnecessary for a particular embedded * implementation. Unused parts may be pruned by some simple editing of * src/libFLAC/Makefile.am. In general, the decoders, encoders, and * metadata interface are all independent from each other. * * It is easiest to just describe the dependencies: * * - All modules depend on the \link flac_format Format \endlink module. * - The decoders and encoders depend on the bitbuffer. * - The decoder is independent of the encoder. The encoder uses the * decoder because of the verify feature, but this can be removed if * not needed. * - Parts of the metadata interface require the stream decoder (but not * the encoder). * - Ogg support is selectable through the compile time macro * \c FLAC__HAS_OGG. * * For example, if your application only requires the stream decoder, no * encoder, and no metadata interface, you can remove the stream encoder * and the metadata interface, which will greatly reduce the size of the * library. * * Also, there are several places in the libFLAC code with comments marked * with "OPT:" where a #define can be changed to enable code that might be * faster on a specific platform. Experimenting with these can yield faster * binaries. */ /** \defgroup porting Porting Guide for New Versions * * This module describes differences in the library interfaces from * version to version. It assists in the porting of code that uses * the libraries to newer versions of FLAC. * * One simple facility for making porting easier that has been added * in FLAC 1.1.3 is a set of \c #defines in \c export.h of each * library's includes (e.g. \c include/FLAC/export.h). The * \c #defines mirror the libraries' * libtool version numbers, * e.g. in libFLAC there are \c FLAC_API_VERSION_CURRENT, * \c FLAC_API_VERSION_REVISION, and \c FLAC_API_VERSION_AGE. * These can be used to support multiple versions of an API during the * transition phase, e.g. * * \code * #if !defined(FLAC_API_VERSION_CURRENT) || FLAC_API_VERSION_CURRENT <= 7 * legacy code * #else * new code * #endif * \endcode * * The the source will work for multiple versions and the legacy code can * easily be removed when the transition is complete. * * Another available symbol is FLAC_API_SUPPORTS_OGG_FLAC (defined in * include/FLAC/export.h), which can be used to determine whether or not * the library has been compiled with support for Ogg FLAC. This is * simpler than trying to call an Ogg init function and catching the * error. */ /** \defgroup porting_1_1_2_to_1_1_3 Porting from FLAC 1.1.2 to 1.1.3 * \ingroup porting * * \brief * This module describes porting from FLAC 1.1.2 to FLAC 1.1.3. * * The main change between the APIs in 1.1.2 and 1.1.3 is that they have * been simplified. First, libOggFLAC has been merged into libFLAC and * libOggFLAC++ has been merged into libFLAC++. Second, both the three * decoding layers and three encoding layers have been merged into a * single stream decoder and stream encoder. That is, the functionality * of FLAC__SeekableStreamDecoder and FLAC__FileDecoder has been merged * into FLAC__StreamDecoder, and FLAC__SeekableStreamEncoder and * FLAC__FileEncoder into FLAC__StreamEncoder. Only the * FLAC__StreamDecoder and FLAC__StreamEncoder remain. What this means * is there is now a single API that can be used to encode or decode * streams to/from native FLAC or Ogg FLAC and the single API can work * on both seekable and non-seekable streams. * * Instead of creating an encoder or decoder of a certain layer, now the * client will always create a FLAC__StreamEncoder or * FLAC__StreamDecoder. The old layers are now differentiated by the * initialization function. For example, for the decoder, * FLAC__stream_decoder_init() has been replaced by * FLAC__stream_decoder_init_stream(). This init function takes * callbacks for the I/O, and the seeking callbacks are optional. This * allows the client to use the same object for seekable and * non-seekable streams. For decoding a FLAC file directly, the client * can use FLAC__stream_decoder_init_file() and pass just a filename * and fewer callbacks; most of the other callbacks are supplied * internally. For situations where fopen()ing by filename is not * possible (e.g. Unicode filenames on Windows) the client can instead * open the file itself and supply the FILE* to * FLAC__stream_decoder_init_FILE(). The init functions now returns a * FLAC__StreamDecoderInitStatus instead of FLAC__StreamDecoderState. * Since the callbacks and client data are now passed to the init * function, the FLAC__stream_decoder_set_*_callback() functions and * FLAC__stream_decoder_set_client_data() are no longer needed. The * rest of the calls to the decoder are the same as before. * * There are counterpart init functions for Ogg FLAC, e.g. * FLAC__stream_decoder_init_ogg_stream(). All the rest of the calls * and callbacks are the same as for native FLAC. * * As an example, in FLAC 1.1.2 a seekable stream decoder would have * been set up like so: * * \code * FLAC__SeekableStreamDecoder *decoder = FLAC__seekable_stream_decoder_new(); * if(decoder == NULL) do_something; * FLAC__seekable_stream_decoder_set_md5_checking(decoder, true); * [... other settings ...] * FLAC__seekable_stream_decoder_set_read_callback(decoder, my_read_callback); * FLAC__seekable_stream_decoder_set_seek_callback(decoder, my_seek_callback); * FLAC__seekable_stream_decoder_set_tell_callback(decoder, my_tell_callback); * FLAC__seekable_stream_decoder_set_length_callback(decoder, my_length_callback); * FLAC__seekable_stream_decoder_set_eof_callback(decoder, my_eof_callback); * FLAC__seekable_stream_decoder_set_write_callback(decoder, my_write_callback); * FLAC__seekable_stream_decoder_set_metadata_callback(decoder, my_metadata_callback); * FLAC__seekable_stream_decoder_set_error_callback(decoder, my_error_callback); * FLAC__seekable_stream_decoder_set_client_data(decoder, my_client_data); * if(FLAC__seekable_stream_decoder_init(decoder) != FLAC__SEEKABLE_STREAM_DECODER_OK) do_something; * \endcode * * In FLAC 1.1.3 it is like this: * * \code * FLAC__StreamDecoder *decoder = FLAC__stream_decoder_new(); * if(decoder == NULL) do_something; * FLAC__stream_decoder_set_md5_checking(decoder, true); * [... other settings ...] * if(FLAC__stream_decoder_init_stream( * decoder, * my_read_callback, * my_seek_callback, // or NULL * my_tell_callback, // or NULL * my_length_callback, // or NULL * my_eof_callback, // or NULL * my_write_callback, * my_metadata_callback, // or NULL * my_error_callback, * my_client_data * ) != FLAC__STREAM_DECODER_INIT_STATUS_OK) do_something; * \endcode * * or you could do; * * \code * [...] * FILE *file = fopen("somefile.flac","rb"); * if(file == NULL) do_somthing; * if(FLAC__stream_decoder_init_FILE( * decoder, * file, * my_write_callback, * my_metadata_callback, // or NULL * my_error_callback, * my_client_data * ) != FLAC__STREAM_DECODER_INIT_STATUS_OK) do_something; * \endcode * * or just: * * \code * [...] * if(FLAC__stream_decoder_init_file( * decoder, * "somefile.flac", * my_write_callback, * my_metadata_callback, // or NULL * my_error_callback, * my_client_data * ) != FLAC__STREAM_DECODER_INIT_STATUS_OK) do_something; * \endcode * * Another small change to the decoder is in how it handles unparseable * streams. Before, when the decoder found an unparseable stream * (reserved for when the decoder encounters a stream from a future * encoder that it can't parse), it changed the state to * \c FLAC__STREAM_DECODER_UNPARSEABLE_STREAM. Now the decoder instead * drops sync and calls the error callback with a new error code * \c FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM. This is * more robust. If your error callback does not discriminate on the the * error state, your code does not need to be changed. * * The encoder now has a new setting: * FLAC__stream_encoder_set_apodization(). This is for setting the * method used to window the data before LPC analysis. You only need to * add a call to this function if the default is not suitable. There * are also two new convenience functions that may be useful: * FLAC__metadata_object_cuesheet_calculate_cddb_id() and * FLAC__metadata_get_cuesheet(). * * The \a bytes parameter to FLAC__StreamDecoderReadCallback, * FLAC__StreamEncoderReadCallback, and FLAC__StreamEncoderWriteCallback * is now \c size_t instead of \c unsigned. */ /** \defgroup porting_1_1_3_to_1_1_4 Porting from FLAC 1.1.3 to 1.1.4 * \ingroup porting * * \brief * This module describes porting from FLAC 1.1.3 to FLAC 1.1.4. * * There were no changes to any of the interfaces from 1.1.3 to 1.1.4. * There was a slight change in the implementation of * FLAC__stream_encoder_set_metadata(); the function now makes a copy * of the \a metadata array of pointers so the client no longer needs * to maintain it after the call. The objects themselves that are * pointed to by the array are still not copied though and must be * maintained until the call to FLAC__stream_encoder_finish(). */ /** \defgroup porting_1_1_4_to_1_2_0 Porting from FLAC 1.1.4 to 1.2.0 * \ingroup porting * * \brief * This module describes porting from FLAC 1.1.4 to FLAC 1.2.0. * * There were only very minor changes to the interfaces from 1.1.4 to 1.2.0. * In libFLAC, \c FLAC__format_sample_rate_is_subset() was added. * In libFLAC++, \c FLAC::Decoder::Stream::get_decode_position() was added. * * Finally, value of the constant \c FLAC__FRAME_HEADER_RESERVED_LEN * has changed to reflect the conversion of one of the reserved bits * into active use. It used to be \c 2 and now is \c 1. However the * FLAC frame header length has not changed, so to skip the proper * number of bits, use \c FLAC__FRAME_HEADER_RESERVED_LEN + * \c FLAC__FRAME_HEADER_BLOCKING_STRATEGY_LEN */ /** \defgroup flac FLAC C API * * The FLAC C API is the interface to libFLAC, a set of structures * describing the components of FLAC streams, and functions for * encoding and decoding streams, as well as manipulating FLAC * metadata in files. * * You should start with the format components as all other modules * are dependent on it. */ #endif sources_5316/external/flac/flac_private_bitwriter.h0000644000176700017670000001141210720607255021360 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__BITWRITER_H #define FLAC__PRIVATE__BITWRITER_H #include /* for FILE */ #include "flac_FLAC_ordinals.h" /* * opaque structure definition */ struct FLAC__BitWriter; typedef struct FLAC__BitWriter FLAC__BitWriter; /* * construction, deletion, initialization, etc functions */ FLAC__BitWriter *FLAC__bitwriter_new(void); void FLAC__bitwriter_delete(FLAC__BitWriter *bw); FLAC__bool FLAC__bitwriter_init(FLAC__BitWriter *bw); void FLAC__bitwriter_free(FLAC__BitWriter *bw); /* does not 'free(buffer)' */ void FLAC__bitwriter_clear(FLAC__BitWriter *bw); void FLAC__bitwriter_dump(const FLAC__BitWriter *bw, FILE *out); /* * CRC functions * * non-const *bw because they have to cal FLAC__bitwriter_get_buffer() */ FLAC__bool FLAC__bitwriter_get_write_crc16(FLAC__BitWriter *bw, FLAC__uint16 *crc); FLAC__bool FLAC__bitwriter_get_write_crc8(FLAC__BitWriter *bw, FLAC__byte *crc); /* * info functions */ FLAC__bool FLAC__bitwriter_is_byte_aligned(const FLAC__BitWriter *bw); unsigned FLAC__bitwriter_get_input_bits_unconsumed(const FLAC__BitWriter *bw); /* can be called anytime, returns total # of bits unconsumed */ /* * direct buffer access * * there may be no calls on the bitwriter between get and release. * the bitwriter continues to own the returned buffer. * before get, bitwriter MUST be byte aligned: check with FLAC__bitwriter_is_byte_aligned() */ FLAC__bool FLAC__bitwriter_get_buffer(FLAC__BitWriter *bw, const FLAC__byte **buffer, size_t *bytes); void FLAC__bitwriter_release_buffer(FLAC__BitWriter *bw); /* * write functions */ FLAC__bool FLAC__bitwriter_write_zeroes(FLAC__BitWriter *bw, unsigned bits); FLAC__bool FLAC__bitwriter_write_raw_uint32(FLAC__BitWriter *bw, FLAC__uint32 val, unsigned bits); FLAC__bool FLAC__bitwriter_write_raw_int32(FLAC__BitWriter *bw, FLAC__int32 val, unsigned bits); FLAC__bool FLAC__bitwriter_write_raw_uint64(FLAC__BitWriter *bw, FLAC__uint64 val, unsigned bits); FLAC__bool FLAC__bitwriter_write_raw_uint32_little_endian(FLAC__BitWriter *bw, FLAC__uint32 val); /*only for bits=32*/ FLAC__bool FLAC__bitwriter_write_byte_block(FLAC__BitWriter *bw, const FLAC__byte vals[], unsigned nvals); FLAC__bool FLAC__bitwriter_write_unary_unsigned(FLAC__BitWriter *bw, unsigned val); unsigned FLAC__bitwriter_rice_bits(FLAC__int32 val, unsigned parameter); #if 0 /* UNUSED */ unsigned FLAC__bitwriter_golomb_bits_signed(int val, unsigned parameter); unsigned FLAC__bitwriter_golomb_bits_unsigned(unsigned val, unsigned parameter); #endif FLAC__bool FLAC__bitwriter_write_rice_signed(FLAC__BitWriter *bw, FLAC__int32 val, unsigned parameter); FLAC__bool FLAC__bitwriter_write_rice_signed_block(FLAC__BitWriter *bw, const FLAC__int32 *vals, unsigned nvals, unsigned parameter); #if 0 /* UNUSED */ FLAC__bool FLAC__bitwriter_write_golomb_signed(FLAC__BitWriter *bw, int val, unsigned parameter); FLAC__bool FLAC__bitwriter_write_golomb_unsigned(FLAC__BitWriter *bw, unsigned val, unsigned parameter); #endif FLAC__bool FLAC__bitwriter_write_utf8_uint32(FLAC__BitWriter *bw, FLAC__uint32 val); FLAC__bool FLAC__bitwriter_write_utf8_uint64(FLAC__BitWriter *bw, FLAC__uint64 val); FLAC__bool FLAC__bitwriter_zero_pad_to_byte_boundary(FLAC__BitWriter *bw); #endif sources_5316/external/flac/flac_window.c0000644000176700017670000001466210720610123017113 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include #include "flac_FLAC_assert.h" #include "flac_FLAC_format.h" #include "flac_private_window.h" #ifndef FLAC__INTEGER_ONLY_LIBRARY #ifndef M_PI /* math.h in VC++ doesn't seem to have this (how Microsoft is that?) */ #define M_PI 3.14159265358979323846 #endif void FLAC__window_bartlett(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; FLAC__int32 n; if (L & 1) { for (n = 0; n <= N/2; n++) window[n] = 2.0f * n / (float)N; for (; n <= N; n++) window[n] = 2.0f - 2.0f * n / (float)N; } else { for (n = 0; n <= L/2-1; n++) window[n] = 2.0f * n / (float)N; for (; n <= N; n++) window[n] = 2.0f - 2.0f * (N-n) / (float)N; } } void FLAC__window_bartlett_hann(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; FLAC__int32 n; for (n = 0; n < L; n++) window[n] = (FLAC__real)(0.62f - 0.48f * fabs((float)n/(float)N+0.5f) + 0.38f * cos(2.0f * M_PI * ((float)n/(float)N+0.5f))); } void FLAC__window_blackman(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; FLAC__int32 n; for (n = 0; n < L; n++) window[n] = (FLAC__real)(0.42f - 0.5f * cos(2.0f * M_PI * n / N) + 0.08f * cos(4.0f * M_PI * n / N)); } /* 4-term -92dB side-lobe */ void FLAC__window_blackman_harris_4term_92db_sidelobe(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; FLAC__int32 n; for (n = 0; n <= N; n++) window[n] = (FLAC__real)(0.35875f - 0.48829f * cos(2.0f * M_PI * n / N) + 0.14128f * cos(4.0f * M_PI * n / N) - 0.01168f * cos(6.0f * M_PI * n / N)); } void FLAC__window_connes(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; const double N2 = (double)N / 2.; FLAC__int32 n; for (n = 0; n <= N; n++) { double k = ((double)n - N2) / N2; k = 1.0f - k * k; window[n] = (FLAC__real)(k * k); } } void FLAC__window_flattop(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; FLAC__int32 n; for (n = 0; n < L; n++) window[n] = (FLAC__real)(1.0f - 1.93f * cos(2.0f * M_PI * n / N) + 1.29f * cos(4.0f * M_PI * n / N) - 0.388f * cos(6.0f * M_PI * n / N) + 0.0322f * cos(8.0f * M_PI * n / N)); } void FLAC__window_gauss(FLAC__real *window, const FLAC__int32 L, const FLAC__real stddev) { const FLAC__int32 N = L - 1; const double N2 = (double)N / 2.; FLAC__int32 n; for (n = 0; n <= N; n++) { const double k = ((double)n - N2) / (stddev * N2); window[n] = (FLAC__real)exp(-0.5f * k * k); } } void FLAC__window_hamming(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; FLAC__int32 n; for (n = 0; n < L; n++) window[n] = (FLAC__real)(0.54f - 0.46f * cos(2.0f * M_PI * n / N)); } void FLAC__window_hann(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; FLAC__int32 n; for (n = 0; n < L; n++) window[n] = (FLAC__real)(0.5f - 0.5f * cos(2.0f * M_PI * n / N)); } void FLAC__window_kaiser_bessel(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; FLAC__int32 n; for (n = 0; n < L; n++) window[n] = (FLAC__real)(0.402f - 0.498f * cos(2.0f * M_PI * n / N) + 0.098f * cos(4.0f * M_PI * n / N) - 0.001f * cos(6.0f * M_PI * n / N)); } void FLAC__window_nuttall(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; FLAC__int32 n; for (n = 0; n < L; n++) window[n] = (FLAC__real)(0.3635819f - 0.4891775f*cos(2.0f*M_PI*n/N) + 0.1365995f*cos(4.0f*M_PI*n/N) - 0.0106411f*cos(6.0f*M_PI*n/N)); } void FLAC__window_rectangle(FLAC__real *window, const FLAC__int32 L) { FLAC__int32 n; for (n = 0; n < L; n++) window[n] = 1.0f; } void FLAC__window_triangle(FLAC__real *window, const FLAC__int32 L) { FLAC__int32 n; if (L & 1) { for (n = 1; n <= L+1/2; n++) window[n-1] = 2.0f * n / ((float)L + 1.0f); for (; n <= L; n++) window[n-1] = - (float)(2 * (L - n + 1)) / ((float)L + 1.0f); } else { for (n = 1; n <= L/2; n++) window[n-1] = 2.0f * n / (float)L; for (; n <= L; n++) window[n-1] = ((float)(2 * (L - n)) + 1.0f) / (float)L; } } void FLAC__window_tukey(FLAC__real *window, const FLAC__int32 L, const FLAC__real p) { if (p <= 0.0) FLAC__window_rectangle(window, L); else if (p >= 1.0) FLAC__window_hann(window, L); else { const FLAC__int32 Np = (FLAC__int32)(p / 2.0f * L) - 1; FLAC__int32 n; /* start with rectangle... */ FLAC__window_rectangle(window, L); /* ...replace ends with hann */ if (Np > 0) { for (n = 0; n <= Np; n++) { window[n] = (FLAC__real)(0.5f - 0.5f * cos(M_PI * n / Np)); window[L-Np-1+n] = (FLAC__real)(0.5f - 0.5f * cos(M_PI * (n+Np) / Np)); } } } } void FLAC__window_welch(FLAC__real *window, const FLAC__int32 L) { const FLAC__int32 N = L - 1; const double N2 = (double)N / 2.; FLAC__int32 n; for (n = 0; n <= N; n++) { const double k = ((double)n - N2) / N2; window[n] = (FLAC__real)(1.0f - k * k); } } #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ sources_5316/external/flac/flac_memory.c0000644000176700017670000001554010720610767017126 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include "flac_private_memory.h" #include "flac_FLAC_assert.h" #include "flac_share_alloc.h" void *FLAC__memory_alloc_aligned(size_t bytes, void **aligned_address) { void *x; FLAC__ASSERT(0 != aligned_address); #ifdef FLAC__ALIGN_MALLOC_DATA /* align on 32-byte (256-bit) boundary */ x = safe_malloc_add_2op_(bytes, /*+*/31); #ifdef SIZEOF_VOIDP #if SIZEOF_VOIDP == 4 /* could do *aligned_address = x + ((unsigned) (32 - (((unsigned)x) & 31))) & 31; */ *aligned_address = (void*)(((unsigned)x + 31) & -32); #elif SIZEOF_VOIDP == 8 *aligned_address = (void*)(((FLAC__uint64)x + 31) & (FLAC__uint64)(-((FLAC__int64)32))); #else # error Unsupported sizeof(void*) #endif #else /* there's got to be a better way to do this right for all archs */ if(sizeof(void*) == sizeof(unsigned)) *aligned_address = (void*)(((unsigned)x + 31) & -32); else if(sizeof(void*) == sizeof(FLAC__uint64)) *aligned_address = (void*)(((FLAC__uint64)x + 31) & (FLAC__uint64)(-((FLAC__int64)32))); else return 0; #endif #else x = safe_malloc_(bytes); *aligned_address = x; #endif return x; } FLAC__bool FLAC__memory_alloc_aligned_int32_array(unsigned elements, FLAC__int32 **unaligned_pointer, FLAC__int32 **aligned_pointer) { FLAC__int32 *pu; /* unaligned pointer */ union { /* union needed to comply with C99 pointer aliasing rules */ FLAC__int32 *pa; /* aligned pointer */ void *pv; /* aligned pointer alias */ } u; FLAC__ASSERT(elements > 0); FLAC__ASSERT(0 != unaligned_pointer); FLAC__ASSERT(0 != aligned_pointer); FLAC__ASSERT(unaligned_pointer != aligned_pointer); if((size_t)elements > SIZE_MAX / sizeof(*pu)) /* overflow check */ return false; pu = (FLAC__int32*)FLAC__memory_alloc_aligned(sizeof(*pu) * (size_t)elements, &u.pv); if(0 == pu) { return false; } else { if(*unaligned_pointer != 0) free(*unaligned_pointer); *unaligned_pointer = pu; *aligned_pointer = u.pa; return true; } } FLAC__bool FLAC__memory_alloc_aligned_uint32_array(unsigned elements, FLAC__uint32 **unaligned_pointer, FLAC__uint32 **aligned_pointer) { FLAC__uint32 *pu; /* unaligned pointer */ union { /* union needed to comply with C99 pointer aliasing rules */ FLAC__uint32 *pa; /* aligned pointer */ void *pv; /* aligned pointer alias */ } u; FLAC__ASSERT(elements > 0); FLAC__ASSERT(0 != unaligned_pointer); FLAC__ASSERT(0 != aligned_pointer); FLAC__ASSERT(unaligned_pointer != aligned_pointer); if((size_t)elements > SIZE_MAX / sizeof(*pu)) /* overflow check */ return false; pu = (FLAC__uint32*)FLAC__memory_alloc_aligned(sizeof(*pu) * elements, &u.pv); if(0 == pu) { return false; } else { if(*unaligned_pointer != 0) free(*unaligned_pointer); *unaligned_pointer = pu; *aligned_pointer = u.pa; return true; } } FLAC__bool FLAC__memory_alloc_aligned_uint64_array(unsigned elements, FLAC__uint64 **unaligned_pointer, FLAC__uint64 **aligned_pointer) { FLAC__uint64 *pu; /* unaligned pointer */ union { /* union needed to comply with C99 pointer aliasing rules */ FLAC__uint64 *pa; /* aligned pointer */ void *pv; /* aligned pointer alias */ } u; FLAC__ASSERT(elements > 0); FLAC__ASSERT(0 != unaligned_pointer); FLAC__ASSERT(0 != aligned_pointer); FLAC__ASSERT(unaligned_pointer != aligned_pointer); if((size_t)elements > SIZE_MAX / sizeof(*pu)) /* overflow check */ return false; pu = (FLAC__uint64*)FLAC__memory_alloc_aligned(sizeof(*pu) * elements, &u.pv); if(0 == pu) { return false; } else { if(*unaligned_pointer != 0) free(*unaligned_pointer); *unaligned_pointer = pu; *aligned_pointer = u.pa; return true; } } FLAC__bool FLAC__memory_alloc_aligned_unsigned_array(unsigned elements, unsigned **unaligned_pointer, unsigned **aligned_pointer) { unsigned *pu; /* unaligned pointer */ union { /* union needed to comply with C99 pointer aliasing rules */ unsigned *pa; /* aligned pointer */ void *pv; /* aligned pointer alias */ } u; FLAC__ASSERT(elements > 0); FLAC__ASSERT(0 != unaligned_pointer); FLAC__ASSERT(0 != aligned_pointer); FLAC__ASSERT(unaligned_pointer != aligned_pointer); if((size_t)elements > SIZE_MAX / sizeof(*pu)) /* overflow check */ return false; pu = (unsigned*)FLAC__memory_alloc_aligned(sizeof(*pu) * elements, &u.pv); if(0 == pu) { return false; } else { if(*unaligned_pointer != 0) free(*unaligned_pointer); *unaligned_pointer = pu; *aligned_pointer = u.pa; return true; } } #ifndef FLAC__INTEGER_ONLY_LIBRARY FLAC__bool FLAC__memory_alloc_aligned_real_array(unsigned elements, FLAC__real **unaligned_pointer, FLAC__real **aligned_pointer) { FLAC__real *pu; /* unaligned pointer */ union { /* union needed to comply with C99 pointer aliasing rules */ FLAC__real *pa; /* aligned pointer */ void *pv; /* aligned pointer alias */ } u; FLAC__ASSERT(elements > 0); FLAC__ASSERT(0 != unaligned_pointer); FLAC__ASSERT(0 != aligned_pointer); FLAC__ASSERT(unaligned_pointer != aligned_pointer); if((size_t)elements > SIZE_MAX / sizeof(*pu)) /* overflow check */ return false; pu = (FLAC__real*)FLAC__memory_alloc_aligned(sizeof(*pu) * elements, &u.pv); if(0 == pu) { return false; } else { if(*unaligned_pointer != 0) free(*unaligned_pointer); *unaligned_pointer = pu; *aligned_pointer = u.pa; return true; } } #endif sources_5316/external/flac/flac_private_fixed.h0000644000176700017670000001064710720650355020454 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__FIXED_H #define FLAC__PRIVATE__FIXED_H #ifdef HAVE_CONFIG_H #include #endif #include "flac_private_autocpu.h" #include "flac_private_float.h" #include "flac_FLAC_format.h" /* * FLAC__fixed_compute_best_predictor() * -------------------------------------------------------------------- * Compute the best fixed predictor and the expected bits-per-sample * of the residual signal for each order. The _wide() version uses * 64-bit integers which is statistically necessary when bits-per- * sample + log2(blocksize) > 30 * * IN data[0,data_len-1] * IN data_len * OUT residual_bits_per_sample[0,FLAC__MAX_FIXED_ORDER] */ #ifndef FLAC__INTEGER_ONLY_LIBRARY unsigned FLAC__fixed_compute_best_predictor(const FLAC__int32 data[], unsigned data_len, FLAC__float residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]); # ifndef FLAC__NO_ASM # ifdef FLAC__CPU_IA32 # ifdef FLAC__HAS_NASM unsigned FLAC__fixed_compute_best_predictor_asm_ia32_mmx_cmov(const FLAC__int32 data[], unsigned data_len, FLAC__float residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]); # endif # endif # endif unsigned FLAC__fixed_compute_best_predictor_wide(const FLAC__int32 data[], unsigned data_len, FLAC__float residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]); #else unsigned FLAC__fixed_compute_best_predictor(const FLAC__int32 data[], unsigned data_len, FLAC__fixedpoint residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]); unsigned FLAC__fixed_compute_best_predictor_wide(const FLAC__int32 data[], unsigned data_len, FLAC__fixedpoint residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]); #endif /* * FLAC__fixed_compute_residual() * -------------------------------------------------------------------- * Compute the residual signal obtained from sutracting the predicted * signal from the original. * * IN data[-order,data_len-1] original signal (NOTE THE INDICES!) * IN data_len length of original signal * IN order <= FLAC__MAX_FIXED_ORDER fixed-predictor order * OUT residual[0,data_len-1] residual signal */ void FLAC__fixed_compute_residual(const FLAC__int32 data[], unsigned data_len, unsigned order, FLAC__int32 residual[]); /* * FLAC__fixed_restore_signal() * -------------------------------------------------------------------- * Restore the original signal by summing the residual and the * predictor. * * IN residual[0,data_len-1] residual signal * IN data_len length of original signal * IN order <= FLAC__MAX_FIXED_ORDER fixed-predictor order * *** IMPORTANT: the caller must pass in the historical samples: * IN data[-order,-1] previously-reconstructed historical samples * OUT data[0,data_len-1] original signal */ void FLAC__fixed_restore_signal(const FLAC__int32 residual[], unsigned data_len, unsigned order, FLAC__int32 data[]); #endif sources_5316/external/flac/flac_protected_stream_encoder.h0000644000176700017670000000713310720607052022656 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PROTECTED__STREAM_ENCODER_H #define FLAC__PROTECTED__STREAM_ENCODER_H #include "flac_FLAC_stream_encoder.h" #if FLAC__HAS_OGG #include "private/ogg_encoder_aspect.h" #endif #ifndef FLAC__INTEGER_ONLY_LIBRARY #include "flac_private_float.h" #define FLAC__MAX_APODIZATION_FUNCTIONS 32 typedef enum { FLAC__APODIZATION_BARTLETT, FLAC__APODIZATION_BARTLETT_HANN, FLAC__APODIZATION_BLACKMAN, FLAC__APODIZATION_BLACKMAN_HARRIS_4TERM_92DB_SIDELOBE, FLAC__APODIZATION_CONNES, FLAC__APODIZATION_FLATTOP, FLAC__APODIZATION_GAUSS, FLAC__APODIZATION_HAMMING, FLAC__APODIZATION_HANN, FLAC__APODIZATION_KAISER_BESSEL, FLAC__APODIZATION_NUTTALL, FLAC__APODIZATION_RECTANGLE, FLAC__APODIZATION_TRIANGLE, FLAC__APODIZATION_TUKEY, FLAC__APODIZATION_WELCH } FLAC__ApodizationFunction; typedef struct { FLAC__ApodizationFunction type; union { struct { FLAC__real stddev; } gauss; struct { FLAC__real p; } tukey; } parameters; } FLAC__ApodizationSpecification; #endif // #ifndef FLAC__INTEGER_ONLY_LIBRARY typedef struct FLAC__StreamEncoderProtected { FLAC__StreamEncoderState state; FLAC__bool verify; FLAC__bool streamable_subset; FLAC__bool do_md5; FLAC__bool do_mid_side_stereo; FLAC__bool loose_mid_side_stereo; unsigned channels; unsigned bits_per_sample; unsigned sample_rate; unsigned blocksize; #ifndef FLAC__INTEGER_ONLY_LIBRARY unsigned num_apodizations; FLAC__ApodizationSpecification apodizations[FLAC__MAX_APODIZATION_FUNCTIONS]; #endif unsigned max_lpc_order; unsigned qlp_coeff_precision; FLAC__bool do_qlp_coeff_prec_search; FLAC__bool do_exhaustive_model_search; FLAC__bool do_escape_coding; unsigned min_residual_partition_order; unsigned max_residual_partition_order; unsigned rice_parameter_search_dist; FLAC__uint64 total_samples_estimate; FLAC__StreamMetadata **metadata; unsigned num_metadata_blocks; FLAC__uint64 streaminfo_offset, seektable_offset, audio_offset; #if FLAC__HAS_OGG FLAC__OggEncoderAspect ogg_encoder_aspect; #endif } FLAC__StreamEncoderProtected; #endif sources_5316/external/flac/flac_lpc.c0000644000176700017670000013550110720610627016367 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include #include "flac_FLAC_assert.h" #include "flac_FLAC_format.h" #include "flac_private_bitmath.h" #include "flac_private_lpc.h" #if defined DEBUG || defined FLAC__OVERFLOW_DETECT || defined FLAC__OVERFLOW_DETECT_VERBOSE #include #endif #ifndef FLAC__INTEGER_ONLY_LIBRARY #ifndef M_LN2 /* math.h in VC++ doesn't seem to have this (how Microsoft is that?) */ #define M_LN2 0.69314718055994530942 #endif /* OPT: #undef'ing this may improve the speed on some architectures */ #define FLAC__LPC_UNROLLED_FILTER_LOOPS void FLAC__lpc_window_data(const FLAC__int32 in[], const FLAC__real window[], FLAC__real out[], unsigned data_len) { unsigned i; for(i = 0; i < data_len; i++) out[i] = in[i] * window[i]; } void FLAC__lpc_compute_autocorrelation(const FLAC__real data[], unsigned data_len, unsigned lag, FLAC__real autoc[]) { /* a readable, but slower, version */ #if 0 FLAC__real d; unsigned i; FLAC__ASSERT(lag > 0); FLAC__ASSERT(lag <= data_len); /* * Technically we should subtract the mean first like so: * for(i = 0; i < data_len; i++) * data[i] -= mean; * but it appears not to make enough of a difference to matter, and * most signals are already closely centered around zero */ while(lag--) { for(i = lag, d = 0.0; i < data_len; i++) d += data[i] * data[i - lag]; autoc[lag] = d; } #endif /* * this version tends to run faster because of better data locality * ('data_len' is usually much larger than 'lag') */ FLAC__real d; unsigned sample, coeff; const unsigned limit = data_len - lag; FLAC__ASSERT(lag > 0); FLAC__ASSERT(lag <= data_len); for(coeff = 0; coeff < lag; coeff++) autoc[coeff] = 0.0; for(sample = 0; sample <= limit; sample++) { d = data[sample]; for(coeff = 0; coeff < lag; coeff++) autoc[coeff] += d * data[sample+coeff]; } for(; sample < data_len; sample++) { d = data[sample]; for(coeff = 0; coeff < data_len - sample; coeff++) autoc[coeff] += d * data[sample+coeff]; } } void FLAC__lpc_compute_lp_coefficients(const FLAC__real autoc[], unsigned *max_order, FLAC__real lp_coeff[][FLAC__MAX_LPC_ORDER], FLAC__double error[]) { unsigned i, j; FLAC__double r, err, ref[FLAC__MAX_LPC_ORDER], lpc[FLAC__MAX_LPC_ORDER]; FLAC__ASSERT(0 != max_order); FLAC__ASSERT(0 < *max_order); FLAC__ASSERT(*max_order <= FLAC__MAX_LPC_ORDER); FLAC__ASSERT(autoc[0] != 0.0); err = autoc[0]; for(i = 0; i < *max_order; i++) { /* Sum up this iteration's reflection coefficient. */ r = -autoc[i+1]; for(j = 0; j < i; j++) r -= lpc[j] * autoc[i-j]; ref[i] = (r/=err); /* Update LPC coefficients and total error. */ lpc[i]=r; for(j = 0; j < (i>>1); j++) { FLAC__double tmp = lpc[j]; lpc[j] += r * lpc[i-1-j]; lpc[i-1-j] += r * tmp; } if(i & 1) lpc[j] += lpc[j] * r; err *= (1.0 - r * r); /* save this order */ for(j = 0; j <= i; j++) lp_coeff[i][j] = (FLAC__real)(-lpc[j]); /* negate FIR filter coeff to get predictor coeff */ error[i] = err; /* see SF bug #1601812 http://sourceforge.net/tracker/index.php?func=detail&aid=1601812&group_id=13478&atid=113478 */ if(err == 0.0) { *max_order = i+1; return; } } } int FLAC__lpc_quantize_coefficients(const FLAC__real lp_coeff[], unsigned order, unsigned precision, FLAC__int32 qlp_coeff[], int *shift) { unsigned i; FLAC__double cmax; FLAC__int32 qmax, qmin; FLAC__ASSERT(precision > 0); FLAC__ASSERT(precision >= FLAC__MIN_QLP_COEFF_PRECISION); /* drop one bit for the sign; from here on out we consider only |lp_coeff[i]| */ precision--; qmax = 1 << precision; qmin = -qmax; qmax--; /* calc cmax = max( |lp_coeff[i]| ) */ cmax = 0.0; for(i = 0; i < order; i++) { const FLAC__double d = fabs(lp_coeff[i]); if(d > cmax) cmax = d; } if(cmax <= 0.0) { /* => coefficients are all 0, which means our constant-detect didn't work */ return 2; } else { const int max_shiftlimit = (1 << (FLAC__SUBFRAME_LPC_QLP_SHIFT_LEN-1)) - 1; const int min_shiftlimit = -max_shiftlimit - 1; int log2cmax; (void)frexp(cmax, &log2cmax); log2cmax--; *shift = (int)precision - log2cmax - 1; if(*shift > max_shiftlimit) *shift = max_shiftlimit; else if(*shift < min_shiftlimit) return 1; } if(*shift >= 0) { FLAC__double error = 0.0; FLAC__int32 q; for(i = 0; i < order; i++) { error += lp_coeff[i] * (1 << *shift); #if 1 /* unfortunately lround() is C99 */ if(error >= 0.0) q = (FLAC__int32)(error + 0.5); else q = (FLAC__int32)(error - 0.5); #else q = lround(error); #endif #ifdef FLAC__OVERFLOW_DETECT if(q > qmax+1) /* we expect q==qmax+1 occasionally due to rounding */ fprintf(stderr,"FLAC__lpc_quantize_coefficients: quantizer overflow: q>qmax %d>%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,qmax,*shift,cmax,precision+1,i,lp_coeff[i]); else if(q < qmin) fprintf(stderr,"FLAC__lpc_quantize_coefficients: quantizer overflow: q qmax) q = qmax; else if(q < qmin) q = qmin; error -= q; qlp_coeff[i] = q; } } /* negative shift is very rare but due to design flaw, negative shift is * a NOP in the decoder, so it must be handled specially by scaling down * coeffs */ else { const int nshift = -(*shift); FLAC__double error = 0.0; FLAC__int32 q; #ifdef DEBUG fprintf(stderr,"FLAC__lpc_quantize_coefficients: negative shift=%d order=%u cmax=%f\n", *shift, order, cmax); #endif for(i = 0; i < order; i++) { error += lp_coeff[i] / (1 << nshift); #if 1 /* unfortunately lround() is C99 */ if(error >= 0.0) q = (FLAC__int32)(error + 0.5); else q = (FLAC__int32)(error - 0.5); #else q = lround(error); #endif #ifdef FLAC__OVERFLOW_DETECT if(q > qmax+1) /* we expect q==qmax+1 occasionally due to rounding */ fprintf(stderr,"FLAC__lpc_quantize_coefficients: quantizer overflow: q>qmax %d>%d shift=%d cmax=%f precision=%u lpc[%u]=%f\n",q,qmax,*shift,cmax,precision+1,i,lp_coeff[i]); else if(q < qmin) fprintf(stderr,"FLAC__lpc_quantize_coefficients: quantizer overflow: q qmax) q = qmax; else if(q < qmin) q = qmin; error -= q; qlp_coeff[i] = q; } *shift = 0; } return 0; } void FLAC__lpc_compute_residual_from_qlp_coefficients(const FLAC__int32 *data, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 residual[]) #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) { FLAC__int64 sumo; unsigned i, j; FLAC__int32 sum; const FLAC__int32 *history; #ifdef FLAC__OVERFLOW_DETECT_VERBOSE fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients: data_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization); for(i=0;i 0); for(i = 0; i < data_len; i++) { sumo = 0; sum = 0; history = data; for(j = 0; j < order; j++) { sum += qlp_coeff[j] * (*(--history)); sumo += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*history); #if defined _MSC_VER if(sumo > 2147483647I64 || sumo < -2147483648I64) fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients: OVERFLOW, i=%u, j=%u, c=%d, d=%d, sumo=%I64d\n",i,j,qlp_coeff[j],*history,sumo); #else if(sumo > 2147483647ll || sumo < -2147483648ll) fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients: OVERFLOW, i=%u, j=%u, c=%d, d=%d, sumo=%lld\n",i,j,qlp_coeff[j],*history,(long long)sumo); #endif } *(residual++) = *(data++) - (sum >> lp_quantization); } /* Here's a slower but clearer version: for(i = 0; i < data_len; i++) { sum = 0; for(j = 0; j < order; j++) sum += qlp_coeff[j] * data[i-j-1]; residual[i] = data[i] - (sum >> lp_quantization); } */ } #else /* fully unrolled version for normal use */ { int i; FLAC__int32 sum; FLAC__ASSERT(order > 0); FLAC__ASSERT(order <= 32); /* * We do unique versions up to 12th order since that's the subset limit. * Also they are roughly ordered to match frequency of occurrence to * minimize branching. */ if(order <= 12) { if(order > 8) { if(order > 10) { if(order == 12) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[11] * data[i-12]; sum += qlp_coeff[10] * data[i-11]; sum += qlp_coeff[9] * data[i-10]; sum += qlp_coeff[8] * data[i-9]; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } else { /* order == 11 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[10] * data[i-11]; sum += qlp_coeff[9] * data[i-10]; sum += qlp_coeff[8] * data[i-9]; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } } else { if(order == 10) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[9] * data[i-10]; sum += qlp_coeff[8] * data[i-9]; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } else { /* order == 9 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[8] * data[i-9]; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } } } else if(order > 4) { if(order > 6) { if(order == 8) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } else { /* order == 7 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } } else { if(order == 6) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } else { /* order == 5 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } } } else { if(order > 2) { if(order == 4) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } else { /* order == 3 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } } else { if(order == 2) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; residual[i] = data[i] - (sum >> lp_quantization); } } else { /* order == 1 */ for(i = 0; i < (int)data_len; i++) residual[i] = data[i] - ((qlp_coeff[0] * data[i-1]) >> lp_quantization); } } } } else { /* order > 12 */ for(i = 0; i < (int)data_len; i++) { sum = 0; switch(order) { case 32: sum += qlp_coeff[31] * data[i-32]; case 31: sum += qlp_coeff[30] * data[i-31]; case 30: sum += qlp_coeff[29] * data[i-30]; case 29: sum += qlp_coeff[28] * data[i-29]; case 28: sum += qlp_coeff[27] * data[i-28]; case 27: sum += qlp_coeff[26] * data[i-27]; case 26: sum += qlp_coeff[25] * data[i-26]; case 25: sum += qlp_coeff[24] * data[i-25]; case 24: sum += qlp_coeff[23] * data[i-24]; case 23: sum += qlp_coeff[22] * data[i-23]; case 22: sum += qlp_coeff[21] * data[i-22]; case 21: sum += qlp_coeff[20] * data[i-21]; case 20: sum += qlp_coeff[19] * data[i-20]; case 19: sum += qlp_coeff[18] * data[i-19]; case 18: sum += qlp_coeff[17] * data[i-18]; case 17: sum += qlp_coeff[16] * data[i-17]; case 16: sum += qlp_coeff[15] * data[i-16]; case 15: sum += qlp_coeff[14] * data[i-15]; case 14: sum += qlp_coeff[13] * data[i-14]; case 13: sum += qlp_coeff[12] * data[i-13]; sum += qlp_coeff[11] * data[i-12]; sum += qlp_coeff[10] * data[i-11]; sum += qlp_coeff[ 9] * data[i-10]; sum += qlp_coeff[ 8] * data[i- 9]; sum += qlp_coeff[ 7] * data[i- 8]; sum += qlp_coeff[ 6] * data[i- 7]; sum += qlp_coeff[ 5] * data[i- 6]; sum += qlp_coeff[ 4] * data[i- 5]; sum += qlp_coeff[ 3] * data[i- 4]; sum += qlp_coeff[ 2] * data[i- 3]; sum += qlp_coeff[ 1] * data[i- 2]; sum += qlp_coeff[ 0] * data[i- 1]; } residual[i] = data[i] - (sum >> lp_quantization); } } } #endif void FLAC__lpc_compute_residual_from_qlp_coefficients_wide(const FLAC__int32 *data, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 residual[]) #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) { unsigned i, j; FLAC__int64 sum; const FLAC__int32 *history; #ifdef FLAC__OVERFLOW_DETECT_VERBOSE fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients_wide: data_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization); for(i=0;i 0); for(i = 0; i < data_len; i++) { sum = 0; history = data; for(j = 0; j < order; j++) sum += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*(--history)); if(FLAC__bitmath_silog2_wide(sum >> lp_quantization) > 32) { #if defined _MSC_VER fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients_wide: OVERFLOW, i=%u, sum=%I64d\n", i, sum >> lp_quantization); #else fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients_wide: OVERFLOW, i=%u, sum=%lld\n", i, (long long)(sum >> lp_quantization)); #endif break; } if(FLAC__bitmath_silog2_wide((FLAC__int64)(*data) - (sum >> lp_quantization)) > 32) { #if defined _MSC_VER fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients_wide: OVERFLOW, i=%u, data=%d, sum=%I64d, residual=%I64d\n", i, *data, sum >> lp_quantization, (FLAC__int64)(*data) - (sum >> lp_quantization)); #else fprintf(stderr,"FLAC__lpc_compute_residual_from_qlp_coefficients_wide: OVERFLOW, i=%u, data=%d, sum=%lld, residual=%lld\n", i, *data, (long long)(sum >> lp_quantization), (long long)((FLAC__int64)(*data) - (sum >> lp_quantization))); #endif break; } *(residual++) = *(data++) - (FLAC__int32)(sum >> lp_quantization); } } #else /* fully unrolled version for normal use */ { int i; FLAC__int64 sum; FLAC__ASSERT(order > 0); FLAC__ASSERT(order <= 32); /* * We do unique versions up to 12th order since that's the subset limit. * Also they are roughly ordered to match frequency of occurrence to * minimize branching. */ if(order <= 12) { if(order > 8) { if(order > 10) { if(order == 12) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[11] * (FLAC__int64)data[i-12]; sum += qlp_coeff[10] * (FLAC__int64)data[i-11]; sum += qlp_coeff[9] * (FLAC__int64)data[i-10]; sum += qlp_coeff[8] * (FLAC__int64)data[i-9]; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 11 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[10] * (FLAC__int64)data[i-11]; sum += qlp_coeff[9] * (FLAC__int64)data[i-10]; sum += qlp_coeff[8] * (FLAC__int64)data[i-9]; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } } else { if(order == 10) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[9] * (FLAC__int64)data[i-10]; sum += qlp_coeff[8] * (FLAC__int64)data[i-9]; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 9 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[8] * (FLAC__int64)data[i-9]; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } } } else if(order > 4) { if(order > 6) { if(order == 8) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 7 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } } else { if(order == 6) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 5 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } } } else { if(order > 2) { if(order == 4) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 3 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } } else { if(order == 2) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 1 */ for(i = 0; i < (int)data_len; i++) residual[i] = data[i] - (FLAC__int32)((qlp_coeff[0] * (FLAC__int64)data[i-1]) >> lp_quantization); } } } } else { /* order > 12 */ for(i = 0; i < (int)data_len; i++) { sum = 0; switch(order) { case 32: sum += qlp_coeff[31] * (FLAC__int64)data[i-32]; case 31: sum += qlp_coeff[30] * (FLAC__int64)data[i-31]; case 30: sum += qlp_coeff[29] * (FLAC__int64)data[i-30]; case 29: sum += qlp_coeff[28] * (FLAC__int64)data[i-29]; case 28: sum += qlp_coeff[27] * (FLAC__int64)data[i-28]; case 27: sum += qlp_coeff[26] * (FLAC__int64)data[i-27]; case 26: sum += qlp_coeff[25] * (FLAC__int64)data[i-26]; case 25: sum += qlp_coeff[24] * (FLAC__int64)data[i-25]; case 24: sum += qlp_coeff[23] * (FLAC__int64)data[i-24]; case 23: sum += qlp_coeff[22] * (FLAC__int64)data[i-23]; case 22: sum += qlp_coeff[21] * (FLAC__int64)data[i-22]; case 21: sum += qlp_coeff[20] * (FLAC__int64)data[i-21]; case 20: sum += qlp_coeff[19] * (FLAC__int64)data[i-20]; case 19: sum += qlp_coeff[18] * (FLAC__int64)data[i-19]; case 18: sum += qlp_coeff[17] * (FLAC__int64)data[i-18]; case 17: sum += qlp_coeff[16] * (FLAC__int64)data[i-17]; case 16: sum += qlp_coeff[15] * (FLAC__int64)data[i-16]; case 15: sum += qlp_coeff[14] * (FLAC__int64)data[i-15]; case 14: sum += qlp_coeff[13] * (FLAC__int64)data[i-14]; case 13: sum += qlp_coeff[12] * (FLAC__int64)data[i-13]; sum += qlp_coeff[11] * (FLAC__int64)data[i-12]; sum += qlp_coeff[10] * (FLAC__int64)data[i-11]; sum += qlp_coeff[ 9] * (FLAC__int64)data[i-10]; sum += qlp_coeff[ 8] * (FLAC__int64)data[i- 9]; sum += qlp_coeff[ 7] * (FLAC__int64)data[i- 8]; sum += qlp_coeff[ 6] * (FLAC__int64)data[i- 7]; sum += qlp_coeff[ 5] * (FLAC__int64)data[i- 6]; sum += qlp_coeff[ 4] * (FLAC__int64)data[i- 5]; sum += qlp_coeff[ 3] * (FLAC__int64)data[i- 4]; sum += qlp_coeff[ 2] * (FLAC__int64)data[i- 3]; sum += qlp_coeff[ 1] * (FLAC__int64)data[i- 2]; sum += qlp_coeff[ 0] * (FLAC__int64)data[i- 1]; } residual[i] = data[i] - (FLAC__int32)(sum >> lp_quantization); } } } #endif #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ void FLAC__lpc_restore_signal(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]) #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) { FLAC__int64 sumo; unsigned i, j; FLAC__int32 sum; const FLAC__int32 *r = residual, *history; #ifdef FLAC__OVERFLOW_DETECT_VERBOSE fprintf(stderr,"FLAC__lpc_restore_signal: data_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization); for(i=0;i 0); for(i = 0; i < data_len; i++) { sumo = 0; sum = 0; history = data; for(j = 0; j < order; j++) { sum += qlp_coeff[j] * (*(--history)); sumo += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*history); #if defined _MSC_VER if(sumo > 2147483647I64 || sumo < -2147483648I64) fprintf(stderr,"FLAC__lpc_restore_signal: OVERFLOW, i=%u, j=%u, c=%d, d=%d, sumo=%I64d\n",i,j,qlp_coeff[j],*history,sumo); #else if(sumo > 2147483647ll || sumo < -2147483648ll) fprintf(stderr,"FLAC__lpc_restore_signal: OVERFLOW, i=%u, j=%u, c=%d, d=%d, sumo=%lld\n",i,j,qlp_coeff[j],*history,(long long)sumo); #endif } *(data++) = *(r++) + (sum >> lp_quantization); } /* Here's a slower but clearer version: for(i = 0; i < data_len; i++) { sum = 0; for(j = 0; j < order; j++) sum += qlp_coeff[j] * data[i-j-1]; data[i] = residual[i] + (sum >> lp_quantization); } */ } #else /* fully unrolled version for normal use */ { int i; FLAC__int32 sum; FLAC__ASSERT(order > 0); FLAC__ASSERT(order <= 32); /* * We do unique versions up to 12th order since that's the subset limit. * Also they are roughly ordered to match frequency of occurrence to * minimize branching. */ if(order <= 12) { if(order > 8) { if(order > 10) { if(order == 12) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[11] * data[i-12]; sum += qlp_coeff[10] * data[i-11]; sum += qlp_coeff[9] * data[i-10]; sum += qlp_coeff[8] * data[i-9]; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } else { /* order == 11 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[10] * data[i-11]; sum += qlp_coeff[9] * data[i-10]; sum += qlp_coeff[8] * data[i-9]; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } } else { if(order == 10) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[9] * data[i-10]; sum += qlp_coeff[8] * data[i-9]; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } else { /* order == 9 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[8] * data[i-9]; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } } } else if(order > 4) { if(order > 6) { if(order == 8) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[7] * data[i-8]; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } else { /* order == 7 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[6] * data[i-7]; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } } else { if(order == 6) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[5] * data[i-6]; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } else { /* order == 5 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[4] * data[i-5]; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } } } else { if(order > 2) { if(order == 4) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[3] * data[i-4]; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } else { /* order == 3 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[2] * data[i-3]; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } } else { if(order == 2) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[1] * data[i-2]; sum += qlp_coeff[0] * data[i-1]; data[i] = residual[i] + (sum >> lp_quantization); } } else { /* order == 1 */ for(i = 0; i < (int)data_len; i++) data[i] = residual[i] + ((qlp_coeff[0] * data[i-1]) >> lp_quantization); } } } } else { /* order > 12 */ for(i = 0; i < (int)data_len; i++) { sum = 0; switch(order) { case 32: sum += qlp_coeff[31] * data[i-32]; case 31: sum += qlp_coeff[30] * data[i-31]; case 30: sum += qlp_coeff[29] * data[i-30]; case 29: sum += qlp_coeff[28] * data[i-29]; case 28: sum += qlp_coeff[27] * data[i-28]; case 27: sum += qlp_coeff[26] * data[i-27]; case 26: sum += qlp_coeff[25] * data[i-26]; case 25: sum += qlp_coeff[24] * data[i-25]; case 24: sum += qlp_coeff[23] * data[i-24]; case 23: sum += qlp_coeff[22] * data[i-23]; case 22: sum += qlp_coeff[21] * data[i-22]; case 21: sum += qlp_coeff[20] * data[i-21]; case 20: sum += qlp_coeff[19] * data[i-20]; case 19: sum += qlp_coeff[18] * data[i-19]; case 18: sum += qlp_coeff[17] * data[i-18]; case 17: sum += qlp_coeff[16] * data[i-17]; case 16: sum += qlp_coeff[15] * data[i-16]; case 15: sum += qlp_coeff[14] * data[i-15]; case 14: sum += qlp_coeff[13] * data[i-14]; case 13: sum += qlp_coeff[12] * data[i-13]; sum += qlp_coeff[11] * data[i-12]; sum += qlp_coeff[10] * data[i-11]; sum += qlp_coeff[ 9] * data[i-10]; sum += qlp_coeff[ 8] * data[i- 9]; sum += qlp_coeff[ 7] * data[i- 8]; sum += qlp_coeff[ 6] * data[i- 7]; sum += qlp_coeff[ 5] * data[i- 6]; sum += qlp_coeff[ 4] * data[i- 5]; sum += qlp_coeff[ 3] * data[i- 4]; sum += qlp_coeff[ 2] * data[i- 3]; sum += qlp_coeff[ 1] * data[i- 2]; sum += qlp_coeff[ 0] * data[i- 1]; } data[i] = residual[i] + (sum >> lp_quantization); } } } #endif void FLAC__lpc_restore_signal_wide(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]) #if defined(FLAC__OVERFLOW_DETECT) || !defined(FLAC__LPC_UNROLLED_FILTER_LOOPS) { unsigned i, j; FLAC__int64 sum; const FLAC__int32 *r = residual, *history; #ifdef FLAC__OVERFLOW_DETECT_VERBOSE fprintf(stderr,"FLAC__lpc_restore_signal_wide: data_len=%d, order=%u, lpq=%d",data_len,order,lp_quantization); for(i=0;i 0); for(i = 0; i < data_len; i++) { sum = 0; history = data; for(j = 0; j < order; j++) sum += (FLAC__int64)qlp_coeff[j] * (FLAC__int64)(*(--history)); if(FLAC__bitmath_silog2_wide(sum >> lp_quantization) > 32) { #ifdef _MSC_VER fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW, i=%u, sum=%I64d\n", i, sum >> lp_quantization); #else fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW, i=%u, sum=%lld\n", i, (long long)(sum >> lp_quantization)); #endif break; } if(FLAC__bitmath_silog2_wide((FLAC__int64)(*r) + (sum >> lp_quantization)) > 32) { #ifdef _MSC_VER fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW, i=%u, residual=%d, sum=%I64d, data=%I64d\n", i, *r, sum >> lp_quantization, (FLAC__int64)(*r) + (sum >> lp_quantization)); #else fprintf(stderr,"FLAC__lpc_restore_signal_wide: OVERFLOW, i=%u, residual=%d, sum=%lld, data=%lld\n", i, *r, (long long)(sum >> lp_quantization), (long long)((FLAC__int64)(*r) + (sum >> lp_quantization))); #endif break; } *(data++) = *(r++) + (FLAC__int32)(sum >> lp_quantization); } } #else /* fully unrolled version for normal use */ { int i; FLAC__int64 sum; FLAC__ASSERT(order > 0); FLAC__ASSERT(order <= 32); /* * We do unique versions up to 12th order since that's the subset limit. * Also they are roughly ordered to match frequency of occurrence to * minimize branching. */ if(order <= 12) { if(order > 8) { if(order > 10) { if(order == 12) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[11] * (FLAC__int64)data[i-12]; sum += qlp_coeff[10] * (FLAC__int64)data[i-11]; sum += qlp_coeff[9] * (FLAC__int64)data[i-10]; sum += qlp_coeff[8] * (FLAC__int64)data[i-9]; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 11 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[10] * (FLAC__int64)data[i-11]; sum += qlp_coeff[9] * (FLAC__int64)data[i-10]; sum += qlp_coeff[8] * (FLAC__int64)data[i-9]; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } } else { if(order == 10) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[9] * (FLAC__int64)data[i-10]; sum += qlp_coeff[8] * (FLAC__int64)data[i-9]; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 9 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[8] * (FLAC__int64)data[i-9]; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } } } else if(order > 4) { if(order > 6) { if(order == 8) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[7] * (FLAC__int64)data[i-8]; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 7 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[6] * (FLAC__int64)data[i-7]; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } } else { if(order == 6) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[5] * (FLAC__int64)data[i-6]; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 5 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[4] * (FLAC__int64)data[i-5]; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } } } else { if(order > 2) { if(order == 4) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[3] * (FLAC__int64)data[i-4]; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 3 */ for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[2] * (FLAC__int64)data[i-3]; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } } else { if(order == 2) { for(i = 0; i < (int)data_len; i++) { sum = 0; sum += qlp_coeff[1] * (FLAC__int64)data[i-2]; sum += qlp_coeff[0] * (FLAC__int64)data[i-1]; data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } else { /* order == 1 */ for(i = 0; i < (int)data_len; i++) data[i] = residual[i] + (FLAC__int32)((qlp_coeff[0] * (FLAC__int64)data[i-1]) >> lp_quantization); } } } } else { /* order > 12 */ for(i = 0; i < (int)data_len; i++) { sum = 0; switch(order) { case 32: sum += qlp_coeff[31] * (FLAC__int64)data[i-32]; case 31: sum += qlp_coeff[30] * (FLAC__int64)data[i-31]; case 30: sum += qlp_coeff[29] * (FLAC__int64)data[i-30]; case 29: sum += qlp_coeff[28] * (FLAC__int64)data[i-29]; case 28: sum += qlp_coeff[27] * (FLAC__int64)data[i-28]; case 27: sum += qlp_coeff[26] * (FLAC__int64)data[i-27]; case 26: sum += qlp_coeff[25] * (FLAC__int64)data[i-26]; case 25: sum += qlp_coeff[24] * (FLAC__int64)data[i-25]; case 24: sum += qlp_coeff[23] * (FLAC__int64)data[i-24]; case 23: sum += qlp_coeff[22] * (FLAC__int64)data[i-23]; case 22: sum += qlp_coeff[21] * (FLAC__int64)data[i-22]; case 21: sum += qlp_coeff[20] * (FLAC__int64)data[i-21]; case 20: sum += qlp_coeff[19] * (FLAC__int64)data[i-20]; case 19: sum += qlp_coeff[18] * (FLAC__int64)data[i-19]; case 18: sum += qlp_coeff[17] * (FLAC__int64)data[i-18]; case 17: sum += qlp_coeff[16] * (FLAC__int64)data[i-17]; case 16: sum += qlp_coeff[15] * (FLAC__int64)data[i-16]; case 15: sum += qlp_coeff[14] * (FLAC__int64)data[i-15]; case 14: sum += qlp_coeff[13] * (FLAC__int64)data[i-14]; case 13: sum += qlp_coeff[12] * (FLAC__int64)data[i-13]; sum += qlp_coeff[11] * (FLAC__int64)data[i-12]; sum += qlp_coeff[10] * (FLAC__int64)data[i-11]; sum += qlp_coeff[ 9] * (FLAC__int64)data[i-10]; sum += qlp_coeff[ 8] * (FLAC__int64)data[i- 9]; sum += qlp_coeff[ 7] * (FLAC__int64)data[i- 8]; sum += qlp_coeff[ 6] * (FLAC__int64)data[i- 7]; sum += qlp_coeff[ 5] * (FLAC__int64)data[i- 6]; sum += qlp_coeff[ 4] * (FLAC__int64)data[i- 5]; sum += qlp_coeff[ 3] * (FLAC__int64)data[i- 4]; sum += qlp_coeff[ 2] * (FLAC__int64)data[i- 3]; sum += qlp_coeff[ 1] * (FLAC__int64)data[i- 2]; sum += qlp_coeff[ 0] * (FLAC__int64)data[i- 1]; } data[i] = residual[i] + (FLAC__int32)(sum >> lp_quantization); } } } #endif #ifndef FLAC__INTEGER_ONLY_LIBRARY FLAC__double FLAC__lpc_compute_expected_bits_per_residual_sample(FLAC__double lpc_error, unsigned total_samples) { FLAC__double error_scale; FLAC__ASSERT(total_samples > 0); error_scale = 0.5 * M_LN2 * M_LN2 / (FLAC__double)total_samples; return FLAC__lpc_compute_expected_bits_per_residual_sample_with_error_scale(lpc_error, error_scale); } FLAC__double FLAC__lpc_compute_expected_bits_per_residual_sample_with_error_scale(FLAC__double lpc_error, FLAC__double error_scale) { if(lpc_error > 0.0) { FLAC__double bps = (FLAC__double)0.5 * log(error_scale * lpc_error) / M_LN2; if(bps >= 0.0) return bps; else return 0.0; } else if(lpc_error < 0.0) { /* error should not be negative but can happen due to inadequate floating-point resolution */ return 1e32; } else { return 0.0; } } unsigned FLAC__lpc_compute_best_order(const FLAC__double lpc_error[], unsigned max_order, unsigned total_samples, unsigned overhead_bits_per_order) { unsigned order, index, best_index; /* 'index' the index into lpc_error; index==order-1 since lpc_error[0] is for order==1, lpc_error[1] is for order==2, etc */ FLAC__double bits, best_bits, error_scale; FLAC__ASSERT(max_order > 0); FLAC__ASSERT(total_samples > 0); error_scale = 0.5 * M_LN2 * M_LN2 / (FLAC__double)total_samples; best_index = 0; best_bits = (unsigned)(-1); for(index = 0, order = 1; index < max_order; index++, order++) { bits = FLAC__lpc_compute_expected_bits_per_residual_sample_with_error_scale(lpc_error[index], error_scale) * (FLAC__double)(total_samples - order) + (FLAC__double)(order * overhead_bits_per_order); if(bits < best_bits) { best_index = index; best_bits = bits; } } return best_index+1; /* +1 since index of lpc_error[] is order-1 */ } #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ sources_5316/external/flac/flac_private_format.h0000644000176700017670000000472010720607255020641 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__FORMAT_H #define FLAC__PRIVATE__FORMAT_H #include "flac_FLAC_format.h" unsigned FLAC__format_get_max_rice_partition_order(unsigned blocksize, unsigned predictor_order); unsigned FLAC__format_get_max_rice_partition_order_from_blocksize(unsigned blocksize); unsigned FLAC__format_get_max_rice_partition_order_from_blocksize_limited_max_and_predictor_order(unsigned limit, unsigned blocksize, unsigned predictor_order); void FLAC__format_entropy_coding_method_partitioned_rice_contents_init(FLAC__EntropyCodingMethod_PartitionedRiceContents *object); void FLAC__format_entropy_coding_method_partitioned_rice_contents_clear(FLAC__EntropyCodingMethod_PartitionedRiceContents *object); FLAC__bool FLAC__format_entropy_coding_method_partitioned_rice_contents_ensure_size(FLAC__EntropyCodingMethod_PartitionedRiceContents *object, unsigned max_partition_order); #endif sources_5316/external/flac/flac_stream_decoder.c0000644000176700017670000040734710724323412020600 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #if defined _WIN32 #include /* for _setmode() */ #include /* for _O_BINARY */ #endif #include #include /* for malloc() */ #include /* for memset/memcpy() */ #include /* for stat() */ #include /* for off_t */ #if defined _WIN32 #define fseeko fseek #define ftello ftell #endif #include "flac_FLAC_assert.h" #include "flac_share_alloc.h" #include "flac_protected_stream_decoder.h" #include "flac_private_autocpu.h" #include "flac_private_bitreader.h" #include "flac_private_bitmath.h" #include "flac_private_cpu.h" #include "flac_private_crc.h" #include "flac_private_fixed.h" #include "flac_private_format.h" #include "flac_private_lpc.h" #include "flac_private_md5.h" #include "flac_private_memory.h" #ifdef max #undef max #endif #define max(a,b) ((a)>(b)?(a):(b)) /* adjust for compilers that can't understand using LLU suffix for uint64_t literals */ #ifdef _MSC_VER #define FLAC__U64L(x) x #else #define FLAC__U64L(x) x##LLU #endif /* technically this should be in an "export.c" but this is convenient enough */ FLAC_API int FLAC_API_SUPPORTS_OGG_FLAC = #if FLAC__HAS_OGG 1 #else 0 #endif ; /*********************************************************************** * * Private static data * ***********************************************************************/ static FLAC__byte ID3V2_TAG_[3] = { 'I', 'D', '3' }; /*********************************************************************** * * Private class method prototypes * ***********************************************************************/ static void set_defaults_(FLAC__StreamDecoder *decoder); static FILE *get_binary_stdin_(void); static FLAC__bool allocate_output_(FLAC__StreamDecoder *decoder, unsigned size, unsigned channels); static FLAC__bool has_id_filtered_(FLAC__StreamDecoder *decoder, FLAC__byte *id); static FLAC__bool find_metadata_(FLAC__StreamDecoder *decoder); static FLAC__bool read_metadata_(FLAC__StreamDecoder *decoder); static FLAC__bool read_metadata_streaminfo_(FLAC__StreamDecoder *decoder, FLAC__bool is_last, unsigned length); static FLAC__bool read_metadata_seektable_(FLAC__StreamDecoder *decoder, FLAC__bool is_last, unsigned length); static FLAC__bool read_metadata_vorbiscomment_(FLAC__StreamDecoder *decoder, FLAC__StreamMetadata_VorbisComment *obj); static FLAC__bool read_metadata_cuesheet_(FLAC__StreamDecoder *decoder, FLAC__StreamMetadata_CueSheet *obj); static FLAC__bool read_metadata_picture_(FLAC__StreamDecoder *decoder, FLAC__StreamMetadata_Picture *obj); static FLAC__bool skip_id3v2_tag_(FLAC__StreamDecoder *decoder); static FLAC__bool frame_sync_(FLAC__StreamDecoder *decoder); static FLAC__bool read_frame_(FLAC__StreamDecoder *decoder, FLAC__bool *got_a_frame, FLAC__bool do_full_decode); static FLAC__bool read_frame_header_(FLAC__StreamDecoder *decoder); static FLAC__bool read_subframe_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, FLAC__bool do_full_decode); static FLAC__bool read_subframe_constant_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, FLAC__bool do_full_decode); static FLAC__bool read_subframe_fixed_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, const unsigned order, FLAC__bool do_full_decode); static FLAC__bool read_subframe_lpc_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, const unsigned order, FLAC__bool do_full_decode); static FLAC__bool read_subframe_verbatim_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, FLAC__bool do_full_decode); static FLAC__bool read_residual_partitioned_rice_(FLAC__StreamDecoder *decoder, unsigned predictor_order, unsigned partition_order, FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents, FLAC__int32 *residual, FLAC__bool is_extended); static FLAC__bool read_zero_padding_(FLAC__StreamDecoder *decoder); static FLAC__bool read_callback_(FLAC__byte buffer[], size_t *bytes, void *client_data); #if FLAC__HAS_OGG static FLAC__StreamDecoderReadStatus read_callback_ogg_aspect_(const FLAC__StreamDecoder *decoder, FLAC__byte buffer[], size_t *bytes); static FLAC__OggDecoderAspectReadStatus read_callback_proxy_(const void *void_decoder, FLAC__byte buffer[], size_t *bytes, void *client_data); #endif static FLAC__StreamDecoderWriteStatus write_audio_frame_to_client_(FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer[]); static void send_error_to_client_(const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status); static FLAC__bool seek_to_absolute_sample_(FLAC__StreamDecoder *decoder, FLAC__uint64 stream_length, FLAC__uint64 target_sample); #if FLAC__HAS_OGG static FLAC__bool seek_to_absolute_sample_ogg_(FLAC__StreamDecoder *decoder, FLAC__uint64 stream_length, FLAC__uint64 target_sample); #endif static FLAC__StreamDecoderReadStatus file_read_callback_(const FLAC__StreamDecoder *decoder, FLAC__byte buffer[], size_t *bytes, void *client_data); static FLAC__StreamDecoderSeekStatus file_seek_callback_(const FLAC__StreamDecoder *decoder, FLAC__uint64 absolute_byte_offset, void *client_data); static FLAC__StreamDecoderTellStatus file_tell_callback_(const FLAC__StreamDecoder *decoder, FLAC__uint64 *absolute_byte_offset, void *client_data); static FLAC__StreamDecoderLengthStatus file_length_callback_(const FLAC__StreamDecoder *decoder, FLAC__uint64 *stream_length, void *client_data); static FLAC__bool file_eof_callback_(const FLAC__StreamDecoder *decoder, void *client_data); /*********************************************************************** * * Private class data * ***********************************************************************/ typedef struct FLAC__StreamDecoderPrivate { #if FLAC__HAS_OGG FLAC__bool is_ogg; #endif FLAC__StreamDecoderReadCallback read_callback; FLAC__StreamDecoderSeekCallback seek_callback; FLAC__StreamDecoderTellCallback tell_callback; FLAC__StreamDecoderLengthCallback length_callback; FLAC__StreamDecoderEofCallback eof_callback; FLAC__StreamDecoderWriteCallback write_callback; FLAC__StreamDecoderMetadataCallback metadata_callback; FLAC__StreamDecoderErrorCallback error_callback; /* generic 32-bit datapath: */ void (*local_lpc_restore_signal)(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); /* generic 64-bit datapath: */ void (*local_lpc_restore_signal_64bit)(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); /* for use when the signal is <= 16 bits-per-sample, or <= 15 bits-per-sample on a side channel (which requires 1 extra bit): */ void (*local_lpc_restore_signal_16bit)(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); /* for use when the signal is <= 16 bits-per-sample, or <= 15 bits-per-sample on a side channel (which requires 1 extra bit), AND order <= 8: */ void (*local_lpc_restore_signal_16bit_order8)(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); FLAC__bool (*local_bitreader_read_rice_signed_block)(FLAC__BitReader *br, int vals[], unsigned nvals, unsigned parameter); void *client_data; FILE *file; /* only used if FLAC__stream_decoder_init_file()/FLAC__stream_decoder_init_file() called, else NULL */ FLAC__BitReader *input; FLAC__int32 *output[FLAC__MAX_CHANNELS]; FLAC__int32 *residual[FLAC__MAX_CHANNELS]; /* WATCHOUT: these are the aligned pointers; the real pointers that should be free()'d are residual_unaligned[] below */ FLAC__EntropyCodingMethod_PartitionedRiceContents partitioned_rice_contents[FLAC__MAX_CHANNELS]; unsigned output_capacity, output_channels; FLAC__uint32 fixed_block_size, next_fixed_block_size; FLAC__uint64 samples_decoded; FLAC__bool has_stream_info, has_seek_table; FLAC__StreamMetadata stream_info; FLAC__StreamMetadata seek_table; FLAC__bool metadata_filter[128]; /* MAGIC number 128 == total number of metadata block types == 1 << 7 */ FLAC__byte *metadata_filter_ids; size_t metadata_filter_ids_count, metadata_filter_ids_capacity; /* units for both are IDs, not bytes */ FLAC__Frame frame; FLAC__bool cached; /* true if there is a byte in lookahead */ FLAC__CPUInfo cpuinfo; FLAC__byte header_warmup[2]; /* contains the sync code and reserved bits */ FLAC__byte lookahead; /* temp storage when we need to look ahead one byte in the stream */ /* unaligned (original) pointers to allocated data */ FLAC__int32 *residual_unaligned[FLAC__MAX_CHANNELS]; FLAC__bool do_md5_checking; /* initially gets protected_->md5_checking but is turned off after a seek or if the metadata has a zero MD5 */ FLAC__bool internal_reset_hack; /* used only during init() so we can call reset to set up the decoder without rewinding the input */ FLAC__bool is_seeking; FLAC__MD5Context md5context; FLAC__byte computed_md5sum[16]; /* this is the sum we computed from the decoded data */ /* (the rest of these are only used for seeking) */ FLAC__Frame last_frame; /* holds the info of the last frame we seeked to */ FLAC__uint64 first_frame_offset; /* hint to the seek routine of where in the stream the first audio frame starts */ FLAC__uint64 target_sample; unsigned unparseable_frame_count; /* used to tell whether we're decoding a future version of FLAC or just got a bad sync */ #if FLAC__HAS_OGG FLAC__bool got_a_frame; /* hack needed in Ogg FLAC seek routine to check when process_single() actually writes a frame */ #endif } FLAC__StreamDecoderPrivate; /*********************************************************************** * * Public static class data * ***********************************************************************/ FLAC_API const char * const FLAC__StreamDecoderStateString[] = { "FLAC__STREAM_DECODER_SEARCH_FOR_METADATA", "FLAC__STREAM_DECODER_READ_METADATA", "FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC", "FLAC__STREAM_DECODER_READ_FRAME", "FLAC__STREAM_DECODER_END_OF_STREAM", "FLAC__STREAM_DECODER_OGG_ERROR", "FLAC__STREAM_DECODER_SEEK_ERROR", "FLAC__STREAM_DECODER_ABORTED", "FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR", "FLAC__STREAM_DECODER_UNINITIALIZED" }; FLAC_API const char * const FLAC__StreamDecoderInitStatusString[] = { "FLAC__STREAM_DECODER_INIT_STATUS_OK", "FLAC__STREAM_DECODER_INIT_STATUS_UNSUPPORTED_CONTAINER", "FLAC__STREAM_DECODER_INIT_STATUS_INVALID_CALLBACKS", "FLAC__STREAM_DECODER_INIT_STATUS_MEMORY_ALLOCATION_ERROR", "FLAC__STREAM_DECODER_INIT_STATUS_ERROR_OPENING_FILE", "FLAC__STREAM_DECODER_INIT_STATUS_ALREADY_INITIALIZED" }; FLAC_API const char * const FLAC__StreamDecoderReadStatusString[] = { "FLAC__STREAM_DECODER_READ_STATUS_CONTINUE", "FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM", "FLAC__STREAM_DECODER_READ_STATUS_ABORT" }; FLAC_API const char * const FLAC__StreamDecoderSeekStatusString[] = { "FLAC__STREAM_DECODER_SEEK_STATUS_OK", "FLAC__STREAM_DECODER_SEEK_STATUS_ERROR", "FLAC__STREAM_DECODER_SEEK_STATUS_UNSUPPORTED" }; FLAC_API const char * const FLAC__StreamDecoderTellStatusString[] = { "FLAC__STREAM_DECODER_TELL_STATUS_OK", "FLAC__STREAM_DECODER_TELL_STATUS_ERROR", "FLAC__STREAM_DECODER_TELL_STATUS_UNSUPPORTED" }; FLAC_API const char * const FLAC__StreamDecoderLengthStatusString[] = { "FLAC__STREAM_DECODER_LENGTH_STATUS_OK", "FLAC__STREAM_DECODER_LENGTH_STATUS_ERROR", "FLAC__STREAM_DECODER_LENGTH_STATUS_UNSUPPORTED" }; FLAC_API const char * const FLAC__StreamDecoderWriteStatusString[] = { "FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE", "FLAC__STREAM_DECODER_WRITE_STATUS_ABORT" }; FLAC_API const char * const FLAC__StreamDecoderErrorStatusString[] = { "FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC", "FLAC__STREAM_DECODER_ERROR_STATUS_BAD_HEADER", "FLAC__STREAM_DECODER_ERROR_STATUS_FRAME_CRC_MISMATCH", "FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM" }; /*********************************************************************** * * Class constructor/destructor * ***********************************************************************/ FLAC_API FLAC__StreamDecoder *FLAC__stream_decoder_new(void) { FLAC__StreamDecoder *decoder; unsigned i; FLAC__ASSERT(sizeof(int) >= 4); /* we want to die right away if this is not true */ decoder = (FLAC__StreamDecoder*)calloc(1, sizeof(FLAC__StreamDecoder)); if(decoder == 0) { return 0; } decoder->protected_ = (FLAC__StreamDecoderProtected*)calloc(1, sizeof(FLAC__StreamDecoderProtected)); if(decoder->protected_ == 0) { free(decoder); return 0; } decoder->private_ = (FLAC__StreamDecoderPrivate*)calloc(1, sizeof(FLAC__StreamDecoderPrivate)); if(decoder->private_ == 0) { free(decoder->protected_); free(decoder); return 0; } decoder->private_->input = FLAC__bitreader_new(); if(decoder->private_->input == 0) { free(decoder->private_); free(decoder->protected_); free(decoder); return 0; } decoder->private_->metadata_filter_ids_capacity = 16; if(0 == (decoder->private_->metadata_filter_ids = (FLAC__byte*)malloc((FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8) * decoder->private_->metadata_filter_ids_capacity))) { FLAC__bitreader_delete(decoder->private_->input); free(decoder->private_); free(decoder->protected_); free(decoder); return 0; } for(i = 0; i < FLAC__MAX_CHANNELS; i++) { decoder->private_->output[i] = 0; decoder->private_->residual_unaligned[i] = decoder->private_->residual[i] = 0; } decoder->private_->output_capacity = 0; decoder->private_->output_channels = 0; decoder->private_->has_seek_table = false; for(i = 0; i < FLAC__MAX_CHANNELS; i++) FLAC__format_entropy_coding_method_partitioned_rice_contents_init(&decoder->private_->partitioned_rice_contents[i]); decoder->private_->file = 0; set_defaults_(decoder); decoder->protected_->state = FLAC__STREAM_DECODER_UNINITIALIZED; return decoder; } FLAC_API void FLAC__stream_decoder_delete(FLAC__StreamDecoder *decoder) { unsigned i; FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->private_->input); (void)FLAC__stream_decoder_finish(decoder); if(0 != decoder->private_->metadata_filter_ids) free(decoder->private_->metadata_filter_ids); FLAC__bitreader_delete(decoder->private_->input); for(i = 0; i < FLAC__MAX_CHANNELS; i++) FLAC__format_entropy_coding_method_partitioned_rice_contents_clear(&decoder->private_->partitioned_rice_contents[i]); free(decoder->private_); free(decoder->protected_); free(decoder); } /*********************************************************************** * * Public class methods * ***********************************************************************/ static FLAC__StreamDecoderInitStatus init_stream_internal_( FLAC__StreamDecoder *decoder, FLAC__StreamDecoderReadCallback read_callback, FLAC__StreamDecoderSeekCallback seek_callback, FLAC__StreamDecoderTellCallback tell_callback, FLAC__StreamDecoderLengthCallback length_callback, FLAC__StreamDecoderEofCallback eof_callback, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data, FLAC__bool is_ogg ) { FLAC__ASSERT(0 != decoder); if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return FLAC__STREAM_DECODER_INIT_STATUS_ALREADY_INITIALIZED; #if !FLAC__HAS_OGG if(is_ogg) return FLAC__STREAM_DECODER_INIT_STATUS_UNSUPPORTED_CONTAINER; #endif if( 0 == read_callback || 0 == write_callback || 0 == error_callback || (seek_callback && (0 == tell_callback || 0 == length_callback || 0 == eof_callback)) ) return FLAC__STREAM_DECODER_INIT_STATUS_INVALID_CALLBACKS; #if FLAC__HAS_OGG decoder->private_->is_ogg = is_ogg; if(is_ogg && !FLAC__ogg_decoder_aspect_init(&decoder->protected_->ogg_decoder_aspect)) return decoder->protected_->state = FLAC__STREAM_DECODER_OGG_ERROR; #endif /* * get the CPU info and set the function pointers */ FLAC__cpu_info(&decoder->private_->cpuinfo); /* first default to the non-asm routines */ decoder->private_->local_lpc_restore_signal = FLAC__lpc_restore_signal; decoder->private_->local_lpc_restore_signal_64bit = FLAC__lpc_restore_signal_wide; decoder->private_->local_lpc_restore_signal_16bit = FLAC__lpc_restore_signal; decoder->private_->local_lpc_restore_signal_16bit_order8 = FLAC__lpc_restore_signal; decoder->private_->local_bitreader_read_rice_signed_block = FLAC__bitreader_read_rice_signed_block; /* now override with asm where appropriate */ #ifndef FLAC__NO_ASM if(decoder->private_->cpuinfo.use_asm) { #ifdef FLAC__CPU_IA32 FLAC__ASSERT(decoder->private_->cpuinfo.type == FLAC__CPUINFO_TYPE_IA32); #ifdef FLAC__HAS_NASM #if 1 /*@@@@@@ OPT: not clearly faster, needs more testing */ if(decoder->private_->cpuinfo.data.ia32.bswap) decoder->private_->local_bitreader_read_rice_signed_block = FLAC__bitreader_read_rice_signed_block_asm_ia32_bswap; #endif if(decoder->private_->cpuinfo.data.ia32.mmx) { decoder->private_->local_lpc_restore_signal = FLAC__lpc_restore_signal_asm_ia32; decoder->private_->local_lpc_restore_signal_16bit = FLAC__lpc_restore_signal_asm_ia32_mmx; decoder->private_->local_lpc_restore_signal_16bit_order8 = FLAC__lpc_restore_signal_asm_ia32_mmx; } else { decoder->private_->local_lpc_restore_signal = FLAC__lpc_restore_signal_asm_ia32; decoder->private_->local_lpc_restore_signal_16bit = FLAC__lpc_restore_signal_asm_ia32; decoder->private_->local_lpc_restore_signal_16bit_order8 = FLAC__lpc_restore_signal_asm_ia32; } #endif #elif defined FLAC__CPU_PPC FLAC__ASSERT(decoder->private_->cpuinfo.type == FLAC__CPUINFO_TYPE_PPC); if(decoder->private_->cpuinfo.data.ppc.altivec) { decoder->private_->local_lpc_restore_signal_16bit = FLAC__lpc_restore_signal_asm_ppc_altivec_16; decoder->private_->local_lpc_restore_signal_16bit_order8 = FLAC__lpc_restore_signal_asm_ppc_altivec_16_order8; } #endif } #endif /* from here on, errors are fatal */ if(!FLAC__bitreader_init(decoder->private_->input, decoder->private_->cpuinfo, read_callback_, decoder)) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return FLAC__STREAM_DECODER_INIT_STATUS_MEMORY_ALLOCATION_ERROR; } decoder->private_->read_callback = read_callback; decoder->private_->seek_callback = seek_callback; decoder->private_->tell_callback = tell_callback; decoder->private_->length_callback = length_callback; decoder->private_->eof_callback = eof_callback; decoder->private_->write_callback = write_callback; decoder->private_->metadata_callback = metadata_callback; decoder->private_->error_callback = error_callback; decoder->private_->client_data = client_data; decoder->private_->fixed_block_size = decoder->private_->next_fixed_block_size = 0; decoder->private_->samples_decoded = 0; decoder->private_->has_stream_info = false; decoder->private_->cached = false; decoder->private_->do_md5_checking = decoder->protected_->md5_checking; decoder->private_->is_seeking = false; decoder->private_->internal_reset_hack = true; /* so the following reset does not try to rewind the input */ if(!FLAC__stream_decoder_reset(decoder)) { /* above call sets the state for us */ return FLAC__STREAM_DECODER_INIT_STATUS_MEMORY_ALLOCATION_ERROR; } return FLAC__STREAM_DECODER_INIT_STATUS_OK; } FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_stream( FLAC__StreamDecoder *decoder, FLAC__StreamDecoderReadCallback read_callback, FLAC__StreamDecoderSeekCallback seek_callback, FLAC__StreamDecoderTellCallback tell_callback, FLAC__StreamDecoderLengthCallback length_callback, FLAC__StreamDecoderEofCallback eof_callback, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ) { return init_stream_internal_( decoder, read_callback, seek_callback, tell_callback, length_callback, eof_callback, write_callback, metadata_callback, error_callback, client_data, /*is_ogg=*/false ); } FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_ogg_stream( FLAC__StreamDecoder *decoder, FLAC__StreamDecoderReadCallback read_callback, FLAC__StreamDecoderSeekCallback seek_callback, FLAC__StreamDecoderTellCallback tell_callback, FLAC__StreamDecoderLengthCallback length_callback, FLAC__StreamDecoderEofCallback eof_callback, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ) { return init_stream_internal_( decoder, read_callback, seek_callback, tell_callback, length_callback, eof_callback, write_callback, metadata_callback, error_callback, client_data, /*is_ogg=*/true ); } static FLAC__StreamDecoderInitStatus init_FILE_internal_( FLAC__StreamDecoder *decoder, FILE *file, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data, FLAC__bool is_ogg ) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != file); if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return decoder->protected_->state = FLAC__STREAM_DECODER_INIT_STATUS_ALREADY_INITIALIZED; if(0 == write_callback || 0 == error_callback) return decoder->protected_->state = FLAC__STREAM_DECODER_INIT_STATUS_INVALID_CALLBACKS; /* * To make sure that our file does not go unclosed after an error, we * must assign the FILE pointer before any further error can occur in * this routine. */ if(file == stdin) file = get_binary_stdin_(); /* just to be safe */ decoder->private_->file = file; return init_stream_internal_( decoder, file_read_callback_, decoder->private_->file == stdin? 0: file_seek_callback_, decoder->private_->file == stdin? 0: file_tell_callback_, decoder->private_->file == stdin? 0: file_length_callback_, file_eof_callback_, write_callback, metadata_callback, error_callback, client_data, is_ogg ); } FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_FILE( FLAC__StreamDecoder *decoder, FILE *file, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ) { return init_FILE_internal_(decoder, file, write_callback, metadata_callback, error_callback, client_data, /*is_ogg=*/false); } FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_ogg_FILE( FLAC__StreamDecoder *decoder, FILE *file, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ) { return init_FILE_internal_(decoder, file, write_callback, metadata_callback, error_callback, client_data, /*is_ogg=*/true); } static FLAC__StreamDecoderInitStatus init_file_internal_( FLAC__StreamDecoder *decoder, const char *filename, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data, FLAC__bool is_ogg ) { FILE *file; FLAC__ASSERT(0 != decoder); /* * To make sure that our file does not go unclosed after an error, we * have to do the same entrance checks here that are later performed * in FLAC__stream_decoder_init_FILE() before the FILE* is assigned. */ if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return decoder->protected_->state = FLAC__STREAM_DECODER_INIT_STATUS_ALREADY_INITIALIZED; if(0 == write_callback || 0 == error_callback) return decoder->protected_->state = FLAC__STREAM_DECODER_INIT_STATUS_INVALID_CALLBACKS; file = filename? fopen(filename, "rb") : stdin; if(0 == file) return FLAC__STREAM_DECODER_INIT_STATUS_ERROR_OPENING_FILE; return init_FILE_internal_(decoder, file, write_callback, metadata_callback, error_callback, client_data, is_ogg); } FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_file( FLAC__StreamDecoder *decoder, const char *filename, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ) { return init_file_internal_(decoder, filename, write_callback, metadata_callback, error_callback, client_data, /*is_ogg=*/false); } FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_ogg_file( FLAC__StreamDecoder *decoder, const char *filename, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ) { return init_file_internal_(decoder, filename, write_callback, metadata_callback, error_callback, client_data, /*is_ogg=*/true); } FLAC_API FLAC__bool FLAC__stream_decoder_finish(FLAC__StreamDecoder *decoder) { FLAC__bool md5_failed = false; unsigned i; FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); if(decoder->protected_->state == FLAC__STREAM_DECODER_UNINITIALIZED) return true; /* see the comment in FLAC__seekable_stream_decoder_reset() as to why we * always call FLAC__MD5Final() */ FLAC__MD5Final(decoder->private_->computed_md5sum, &decoder->private_->md5context); if(decoder->private_->has_seek_table && 0 != decoder->private_->seek_table.data.seek_table.points) { free(decoder->private_->seek_table.data.seek_table.points); decoder->private_->seek_table.data.seek_table.points = 0; decoder->private_->has_seek_table = false; } FLAC__bitreader_free(decoder->private_->input); for(i = 0; i < FLAC__MAX_CHANNELS; i++) { /* WATCHOUT: * FLAC__lpc_restore_signal_asm_ia32_mmx() requires that the * output arrays have a buffer of up to 3 zeroes in front * (at negative indices) for alignment purposes; we use 4 * to keep the data well-aligned. */ if(0 != decoder->private_->output[i]) { free(decoder->private_->output[i]-4); decoder->private_->output[i] = 0; } if(0 != decoder->private_->residual_unaligned[i]) { free(decoder->private_->residual_unaligned[i]); decoder->private_->residual_unaligned[i] = decoder->private_->residual[i] = 0; } } decoder->private_->output_capacity = 0; decoder->private_->output_channels = 0; #if FLAC__HAS_OGG if(decoder->private_->is_ogg) FLAC__ogg_decoder_aspect_finish(&decoder->protected_->ogg_decoder_aspect); #endif if(0 != decoder->private_->file) { if(decoder->private_->file != stdin) fclose(decoder->private_->file); decoder->private_->file = 0; } if(decoder->private_->do_md5_checking) { if(memcmp(decoder->private_->stream_info.data.stream_info.md5sum, decoder->private_->computed_md5sum, 16)) md5_failed = true; } decoder->private_->is_seeking = false; set_defaults_(decoder); decoder->protected_->state = FLAC__STREAM_DECODER_UNINITIALIZED; return !md5_failed; } FLAC_API FLAC__bool FLAC__stream_decoder_set_ogg_serial_number(FLAC__StreamDecoder *decoder, long value) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return false; #if FLAC__HAS_OGG /* can't check decoder->private_->is_ogg since that's not set until init time */ FLAC__ogg_decoder_aspect_set_serial_number(&decoder->protected_->ogg_decoder_aspect, value); return true; #else (void)value; return false; #endif } FLAC_API FLAC__bool FLAC__stream_decoder_set_md5_checking(FLAC__StreamDecoder *decoder, FLAC__bool value) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return false; decoder->protected_->md5_checking = value; return true; } FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_respond(FLAC__StreamDecoder *decoder, FLAC__MetadataType type) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); FLAC__ASSERT((unsigned)type <= FLAC__MAX_METADATA_TYPE_CODE); /* double protection */ if((unsigned)type > FLAC__MAX_METADATA_TYPE_CODE) return false; if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return false; decoder->private_->metadata_filter[type] = true; if(type == FLAC__METADATA_TYPE_APPLICATION) decoder->private_->metadata_filter_ids_count = 0; return true; } FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_respond_application(FLAC__StreamDecoder *decoder, const FLAC__byte id[4]) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); FLAC__ASSERT(0 != id); if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return false; if(decoder->private_->metadata_filter[FLAC__METADATA_TYPE_APPLICATION]) return true; FLAC__ASSERT(0 != decoder->private_->metadata_filter_ids); if(decoder->private_->metadata_filter_ids_count == decoder->private_->metadata_filter_ids_capacity) { if(0 == (decoder->private_->metadata_filter_ids = (FLAC__byte*)safe_realloc_mul_2op_(decoder->private_->metadata_filter_ids, decoder->private_->metadata_filter_ids_capacity, /*times*/2))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } decoder->private_->metadata_filter_ids_capacity *= 2; } memcpy(decoder->private_->metadata_filter_ids + decoder->private_->metadata_filter_ids_count * (FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8), id, (FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8)); decoder->private_->metadata_filter_ids_count++; return true; } FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_respond_all(FLAC__StreamDecoder *decoder) { unsigned i; FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return false; for(i = 0; i < sizeof(decoder->private_->metadata_filter) / sizeof(decoder->private_->metadata_filter[0]); i++) decoder->private_->metadata_filter[i] = true; decoder->private_->metadata_filter_ids_count = 0; return true; } FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_ignore(FLAC__StreamDecoder *decoder, FLAC__MetadataType type) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); FLAC__ASSERT((unsigned)type <= FLAC__MAX_METADATA_TYPE_CODE); /* double protection */ if((unsigned)type > FLAC__MAX_METADATA_TYPE_CODE) return false; if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return false; decoder->private_->metadata_filter[type] = false; if(type == FLAC__METADATA_TYPE_APPLICATION) decoder->private_->metadata_filter_ids_count = 0; return true; } FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_ignore_application(FLAC__StreamDecoder *decoder, const FLAC__byte id[4]) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); FLAC__ASSERT(0 != id); if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return false; if(!decoder->private_->metadata_filter[FLAC__METADATA_TYPE_APPLICATION]) return true; FLAC__ASSERT(0 != decoder->private_->metadata_filter_ids); if(decoder->private_->metadata_filter_ids_count == decoder->private_->metadata_filter_ids_capacity) { if(0 == (decoder->private_->metadata_filter_ids = (FLAC__byte*)safe_realloc_mul_2op_(decoder->private_->metadata_filter_ids, decoder->private_->metadata_filter_ids_capacity, /*times*/2))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } decoder->private_->metadata_filter_ids_capacity *= 2; } memcpy(decoder->private_->metadata_filter_ids + decoder->private_->metadata_filter_ids_count * (FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8), id, (FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8)); decoder->private_->metadata_filter_ids_count++; return true; } FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_ignore_all(FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); if(decoder->protected_->state != FLAC__STREAM_DECODER_UNINITIALIZED) return false; memset(decoder->private_->metadata_filter, 0, sizeof(decoder->private_->metadata_filter)); decoder->private_->metadata_filter_ids_count = 0; return true; } FLAC_API FLAC__StreamDecoderState FLAC__stream_decoder_get_state(const FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); return decoder->protected_->state; } FLAC_API const char *FLAC__stream_decoder_get_resolved_state_string(const FLAC__StreamDecoder *decoder) { return FLAC__StreamDecoderStateString[decoder->protected_->state]; } FLAC_API FLAC__bool FLAC__stream_decoder_get_md5_checking(const FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); return decoder->protected_->md5_checking; } FLAC_API FLAC__uint64 FLAC__stream_decoder_get_total_samples(const FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); return decoder->private_->has_stream_info? decoder->private_->stream_info.data.stream_info.total_samples : 0; } FLAC_API unsigned FLAC__stream_decoder_get_channels(const FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); return decoder->protected_->channels; } FLAC_API FLAC__ChannelAssignment FLAC__stream_decoder_get_channel_assignment(const FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); return decoder->protected_->channel_assignment; } FLAC_API unsigned FLAC__stream_decoder_get_bits_per_sample(const FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); return decoder->protected_->bits_per_sample; } FLAC_API unsigned FLAC__stream_decoder_get_sample_rate(const FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); return decoder->protected_->sample_rate; } FLAC_API unsigned FLAC__stream_decoder_get_blocksize(const FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); return decoder->protected_->blocksize; } FLAC_API FLAC__bool FLAC__stream_decoder_get_decode_position(const FLAC__StreamDecoder *decoder, FLAC__uint64 *position) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != position); #if FLAC__HAS_OGG if(decoder->private_->is_ogg) return false; #endif if(0 == decoder->private_->tell_callback) return false; if(decoder->private_->tell_callback(decoder, position, decoder->private_->client_data) != FLAC__STREAM_DECODER_TELL_STATUS_OK) return false; /* should never happen since all FLAC frames and metadata blocks are byte aligned, but check just in case */ if(!FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)) return false; FLAC__ASSERT(*position >= FLAC__stream_decoder_get_input_bytes_unconsumed(decoder)); *position -= FLAC__stream_decoder_get_input_bytes_unconsumed(decoder); return true; } FLAC_API FLAC__bool FLAC__stream_decoder_flush(FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); decoder->private_->samples_decoded = 0; decoder->private_->do_md5_checking = false; #if FLAC__HAS_OGG if(decoder->private_->is_ogg) FLAC__ogg_decoder_aspect_flush(&decoder->protected_->ogg_decoder_aspect); #endif if(!FLAC__bitreader_clear(decoder->private_->input)) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } FLAC_API FLAC__bool FLAC__stream_decoder_reset(FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); FLAC__ASSERT(0 != decoder->protected_); if(!FLAC__stream_decoder_flush(decoder)) { /* above call sets the state for us */ return false; } #if FLAC__HAS_OGG /*@@@ could go in !internal_reset_hack block below */ if(decoder->private_->is_ogg) FLAC__ogg_decoder_aspect_reset(&decoder->protected_->ogg_decoder_aspect); #endif /* Rewind if necessary. If FLAC__stream_decoder_init() is calling us, * (internal_reset_hack) don't try to rewind since we are already at * the beginning of the stream and don't want to fail if the input is * not seekable. */ if(!decoder->private_->internal_reset_hack) { if(decoder->private_->file == stdin) return false; /* can't rewind stdin, reset fails */ if(decoder->private_->seek_callback && decoder->private_->seek_callback(decoder, 0, decoder->private_->client_data) == FLAC__STREAM_DECODER_SEEK_STATUS_ERROR) return false; /* seekable and seek fails, reset fails */ } else decoder->private_->internal_reset_hack = false; decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_METADATA; decoder->private_->has_stream_info = false; if(decoder->private_->has_seek_table && 0 != decoder->private_->seek_table.data.seek_table.points) { free(decoder->private_->seek_table.data.seek_table.points); decoder->private_->seek_table.data.seek_table.points = 0; decoder->private_->has_seek_table = false; } decoder->private_->do_md5_checking = decoder->protected_->md5_checking; /* * This goes in reset() and not flush() because according to the spec, a * fixed-blocksize stream must stay that way through the whole stream. */ decoder->private_->fixed_block_size = decoder->private_->next_fixed_block_size = 0; /* We initialize the FLAC__MD5Context even though we may never use it. This * is because md5 checking may be turned on to start and then turned off if * a seek occurs. So we init the context here and finalize it in * FLAC__stream_decoder_finish() to make sure things are always cleaned up * properly. */ FLAC__MD5Init(&decoder->private_->md5context); decoder->private_->first_frame_offset = 0; decoder->private_->unparseable_frame_count = 0; return true; } FLAC_API FLAC__bool FLAC__stream_decoder_process_single(FLAC__StreamDecoder *decoder) { FLAC__bool got_a_frame; FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); while(1) { switch(decoder->protected_->state) { case FLAC__STREAM_DECODER_SEARCH_FOR_METADATA: if(!find_metadata_(decoder)) return false; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_READ_METADATA: if(!read_metadata_(decoder)) return false; /* above function sets the status for us */ else return true; case FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC: if(!frame_sync_(decoder)) return true; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_READ_FRAME: if(!read_frame_(decoder, &got_a_frame, /*do_full_decode=*/true)) return false; /* above function sets the status for us */ if(got_a_frame) return true; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_END_OF_STREAM: case FLAC__STREAM_DECODER_ABORTED: return true; default: FLAC__ASSERT(0); return false; } } } FLAC_API FLAC__bool FLAC__stream_decoder_process_until_end_of_metadata(FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); while(1) { switch(decoder->protected_->state) { case FLAC__STREAM_DECODER_SEARCH_FOR_METADATA: if(!find_metadata_(decoder)) return false; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_READ_METADATA: if(!read_metadata_(decoder)) return false; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC: case FLAC__STREAM_DECODER_READ_FRAME: case FLAC__STREAM_DECODER_END_OF_STREAM: case FLAC__STREAM_DECODER_ABORTED: return true; default: FLAC__ASSERT(0); return false; } } } FLAC_API FLAC__bool FLAC__stream_decoder_process_until_end_of_stream(FLAC__StreamDecoder *decoder) { FLAC__bool dummy; FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); while(1) { switch(decoder->protected_->state) { case FLAC__STREAM_DECODER_SEARCH_FOR_METADATA: if(!find_metadata_(decoder)) return false; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_READ_METADATA: if(!read_metadata_(decoder)) return false; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC: if(!frame_sync_(decoder)) return true; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_READ_FRAME: if(!read_frame_(decoder, &dummy, /*do_full_decode=*/true)) return false; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_END_OF_STREAM: case FLAC__STREAM_DECODER_ABORTED: return true; default: FLAC__ASSERT(0); return false; } } } FLAC_API FLAC__bool FLAC__stream_decoder_skip_single_frame(FLAC__StreamDecoder *decoder) { FLAC__bool got_a_frame; FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->protected_); while(1) { switch(decoder->protected_->state) { case FLAC__STREAM_DECODER_SEARCH_FOR_METADATA: case FLAC__STREAM_DECODER_READ_METADATA: return false; /* above function sets the status for us */ case FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC: if(!frame_sync_(decoder)) return true; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_READ_FRAME: if(!read_frame_(decoder, &got_a_frame, /*do_full_decode=*/false)) return false; /* above function sets the status for us */ if(got_a_frame) return true; /* above function sets the status for us */ break; case FLAC__STREAM_DECODER_END_OF_STREAM: case FLAC__STREAM_DECODER_ABORTED: return true; default: FLAC__ASSERT(0); return false; } } } FLAC_API FLAC__bool FLAC__stream_decoder_seek_absolute(FLAC__StreamDecoder *decoder, FLAC__uint64 sample) { FLAC__uint64 length; FLAC__ASSERT(0 != decoder); if( decoder->protected_->state != FLAC__STREAM_DECODER_SEARCH_FOR_METADATA && decoder->protected_->state != FLAC__STREAM_DECODER_READ_METADATA && decoder->protected_->state != FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC && decoder->protected_->state != FLAC__STREAM_DECODER_READ_FRAME && decoder->protected_->state != FLAC__STREAM_DECODER_END_OF_STREAM ) return false; if(0 == decoder->private_->seek_callback) return false; FLAC__ASSERT(decoder->private_->seek_callback); FLAC__ASSERT(decoder->private_->tell_callback); FLAC__ASSERT(decoder->private_->length_callback); FLAC__ASSERT(decoder->private_->eof_callback); if(FLAC__stream_decoder_get_total_samples(decoder) > 0 && sample >= FLAC__stream_decoder_get_total_samples(decoder)) return false; decoder->private_->is_seeking = true; /* turn off md5 checking if a seek is attempted */ decoder->private_->do_md5_checking = false; /* get the file length (currently our algorithm needs to know the length so it's also an error to get FLAC__STREAM_DECODER_LENGTH_STATUS_UNSUPPORTED) */ if(decoder->private_->length_callback(decoder, &length, decoder->private_->client_data) != FLAC__STREAM_DECODER_LENGTH_STATUS_OK) { decoder->private_->is_seeking = false; return false; } /* if we haven't finished processing the metadata yet, do that so we have the STREAMINFO, SEEK_TABLE, and first_frame_offset */ if( decoder->protected_->state == FLAC__STREAM_DECODER_SEARCH_FOR_METADATA || decoder->protected_->state == FLAC__STREAM_DECODER_READ_METADATA ) { if(!FLAC__stream_decoder_process_until_end_of_metadata(decoder)) { /* above call sets the state for us */ decoder->private_->is_seeking = false; return false; } /* check this again in case we didn't know total_samples the first time */ if(FLAC__stream_decoder_get_total_samples(decoder) > 0 && sample >= FLAC__stream_decoder_get_total_samples(decoder)) { decoder->private_->is_seeking = false; return false; } } { const FLAC__bool ok = #if FLAC__HAS_OGG decoder->private_->is_ogg? seek_to_absolute_sample_ogg_(decoder, length, sample) : #endif seek_to_absolute_sample_(decoder, length, sample) ; decoder->private_->is_seeking = false; return ok; } } /*********************************************************************** * * Protected class methods * ***********************************************************************/ unsigned FLAC__stream_decoder_get_input_bytes_unconsumed(const FLAC__StreamDecoder *decoder) { FLAC__ASSERT(0 != decoder); FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)); FLAC__ASSERT(!(FLAC__bitreader_get_input_bits_unconsumed(decoder->private_->input) & 7)); return FLAC__bitreader_get_input_bits_unconsumed(decoder->private_->input) / 8; } /*********************************************************************** * * Private class methods * ***********************************************************************/ void set_defaults_(FLAC__StreamDecoder *decoder) { #if FLAC__HAS_OGG decoder->private_->is_ogg = false; #endif decoder->private_->read_callback = 0; decoder->private_->seek_callback = 0; decoder->private_->tell_callback = 0; decoder->private_->length_callback = 0; decoder->private_->eof_callback = 0; decoder->private_->write_callback = 0; decoder->private_->metadata_callback = 0; decoder->private_->error_callback = 0; decoder->private_->client_data = 0; memset(decoder->private_->metadata_filter, 0, sizeof(decoder->private_->metadata_filter)); decoder->private_->metadata_filter[FLAC__METADATA_TYPE_STREAMINFO] = true; decoder->private_->metadata_filter_ids_count = 0; decoder->protected_->md5_checking = false; #if FLAC__HAS_OGG FLAC__ogg_decoder_aspect_set_defaults(&decoder->protected_->ogg_decoder_aspect); #endif } /* * This will forcibly set stdin to binary mode (for OSes that require it) */ FILE *get_binary_stdin_(void) { /* if something breaks here it is probably due to the presence or * absence of an underscore before the identifiers 'setmode', * 'fileno', and/or 'O_BINARY'; check your system header files. */ #if defined _MSC_VER || defined __MINGW32__ _setmode(_fileno(stdin), _O_BINARY); #elif defined __CYGWIN__ /* almost certainly not needed for any modern Cygwin, but let's be safe... */ setmode(_fileno(stdin), _O_BINARY); #elif defined __EMX__ setmode(fileno(stdin), O_BINARY); #endif return stdin; } FLAC__bool allocate_output_(FLAC__StreamDecoder *decoder, unsigned size, unsigned channels) { unsigned i; FLAC__int32 *tmp; if(size <= decoder->private_->output_capacity && channels <= decoder->private_->output_channels) return true; /* simply using realloc() is not practical because the number of channels may change mid-stream */ for(i = 0; i < FLAC__MAX_CHANNELS; i++) { if(0 != decoder->private_->output[i]) { free(decoder->private_->output[i]-4); decoder->private_->output[i] = 0; } if(0 != decoder->private_->residual_unaligned[i]) { free(decoder->private_->residual_unaligned[i]); decoder->private_->residual_unaligned[i] = decoder->private_->residual[i] = 0; } } for(i = 0; i < channels; i++) { /* WATCHOUT: * FLAC__lpc_restore_signal_asm_ia32_mmx() requires that the * output arrays have a buffer of up to 3 zeroes in front * (at negative indices) for alignment purposes; we use 4 * to keep the data well-aligned. */ tmp = (FLAC__int32*)safe_malloc_muladd2_(sizeof(FLAC__int32), /*times (*/size, /*+*/4/*)*/); if(tmp == 0) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } memset(tmp, 0, sizeof(FLAC__int32)*4); decoder->private_->output[i] = tmp + 4; /* WATCHOUT: * minimum of quadword alignment for PPC vector optimizations is REQUIRED: */ if(!FLAC__memory_alloc_aligned_int32_array(size, &decoder->private_->residual_unaligned[i], &decoder->private_->residual[i])) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } } decoder->private_->output_capacity = size; decoder->private_->output_channels = channels; return true; } FLAC__bool has_id_filtered_(FLAC__StreamDecoder *decoder, FLAC__byte *id) { size_t i; FLAC__ASSERT(0 != decoder); FLAC__ASSERT(0 != decoder->private_); for(i = 0; i < decoder->private_->metadata_filter_ids_count; i++) if(0 == memcmp(decoder->private_->metadata_filter_ids + i * (FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8), id, (FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8))) return true; return false; } FLAC__bool find_metadata_(FLAC__StreamDecoder *decoder) { FLAC__uint32 x; unsigned i, id; FLAC__bool first = true; FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)); for(i = id = 0; i < 4; ) { if(decoder->private_->cached) { x = (FLAC__uint32)decoder->private_->lookahead; decoder->private_->cached = false; } else { if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) return false; /* read_callback_ sets the state for us */ } if(x == FLAC__STREAM_SYNC_STRING[i]) { first = true; i++; id = 0; continue; } if(x == ID3V2_TAG_[id]) { id++; i = 0; if(id == 3) { if(!skip_id3v2_tag_(decoder)) return false; /* skip_id3v2_tag_ sets the state for us */ } continue; } id = 0; if(x == 0xff) { /* MAGIC NUMBER for the first 8 frame sync bits */ decoder->private_->header_warmup[0] = (FLAC__byte)x; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) return false; /* read_callback_ sets the state for us */ /* we have to check if we just read two 0xff's in a row; the second may actually be the beginning of the sync code */ /* else we have to check if the second byte is the end of a sync code */ if(x == 0xff) { /* MAGIC NUMBER for the first 8 frame sync bits */ decoder->private_->lookahead = (FLAC__byte)x; decoder->private_->cached = true; } else if(x >> 2 == 0x3e) { /* MAGIC NUMBER for the last 6 sync bits */ decoder->private_->header_warmup[1] = (FLAC__byte)x; decoder->protected_->state = FLAC__STREAM_DECODER_READ_FRAME; return true; } } i = 0; if(first) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC); first = false; } } decoder->protected_->state = FLAC__STREAM_DECODER_READ_METADATA; return true; } FLAC__bool read_metadata_(FLAC__StreamDecoder *decoder) { FLAC__bool is_last; FLAC__uint32 i, x, type, length; FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)); if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_IS_LAST_LEN)) return false; /* read_callback_ sets the state for us */ is_last = x? true : false; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &type, FLAC__STREAM_METADATA_TYPE_LEN)) return false; /* read_callback_ sets the state for us */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &length, FLAC__STREAM_METADATA_LENGTH_LEN)) return false; /* read_callback_ sets the state for us */ if(type == FLAC__METADATA_TYPE_STREAMINFO) { if(!read_metadata_streaminfo_(decoder, is_last, length)) return false; decoder->private_->has_stream_info = true; if(0 == memcmp(decoder->private_->stream_info.data.stream_info.md5sum, "\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0", 16)) decoder->private_->do_md5_checking = false; if(!decoder->private_->is_seeking && decoder->private_->metadata_filter[FLAC__METADATA_TYPE_STREAMINFO] && decoder->private_->metadata_callback) decoder->private_->metadata_callback(decoder, &decoder->private_->stream_info, decoder->private_->client_data); } else if(type == FLAC__METADATA_TYPE_SEEKTABLE) { if(!read_metadata_seektable_(decoder, is_last, length)) return false; decoder->private_->has_seek_table = true; if(!decoder->private_->is_seeking && decoder->private_->metadata_filter[FLAC__METADATA_TYPE_SEEKTABLE] && decoder->private_->metadata_callback) decoder->private_->metadata_callback(decoder, &decoder->private_->seek_table, decoder->private_->client_data); } else { FLAC__bool skip_it = !decoder->private_->metadata_filter[type]; unsigned real_length = length; FLAC__StreamMetadata block; block.is_last = is_last; block.type = (FLAC__MetadataType)type; block.length = length; if(type == FLAC__METADATA_TYPE_APPLICATION) { if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, block.data.application.id, FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8)) return false; /* read_callback_ sets the state for us */ if(real_length < FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8) { /* underflow check */ decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR;/*@@@@@@ maybe wrong error? need to resync?*/ return false; } real_length -= FLAC__STREAM_METADATA_APPLICATION_ID_LEN/8; if(decoder->private_->metadata_filter_ids_count > 0 && has_id_filtered_(decoder, block.data.application.id)) skip_it = !skip_it; } if(skip_it) { if(!FLAC__bitreader_skip_byte_block_aligned_no_crc(decoder->private_->input, real_length)) return false; /* read_callback_ sets the state for us */ } else { switch(type) { case FLAC__METADATA_TYPE_PADDING: /* skip the padding bytes */ if(!FLAC__bitreader_skip_byte_block_aligned_no_crc(decoder->private_->input, real_length)) return false; /* read_callback_ sets the state for us */ break; case FLAC__METADATA_TYPE_APPLICATION: /* remember, we read the ID already */ if(real_length > 0) { if(0 == (block.data.application.data = (FLAC__byte*)malloc(real_length))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, block.data.application.data, real_length)) return false; /* read_callback_ sets the state for us */ } else block.data.application.data = 0; break; case FLAC__METADATA_TYPE_VORBIS_COMMENT: if(!read_metadata_vorbiscomment_(decoder, &block.data.vorbis_comment)) return false; break; case FLAC__METADATA_TYPE_CUESHEET: if(!read_metadata_cuesheet_(decoder, &block.data.cue_sheet)) return false; break; case FLAC__METADATA_TYPE_PICTURE: if(!read_metadata_picture_(decoder, &block.data.picture)) return false; break; case FLAC__METADATA_TYPE_STREAMINFO: case FLAC__METADATA_TYPE_SEEKTABLE: FLAC__ASSERT(0); break; default: if(real_length > 0) { if(0 == (block.data.unknown.data = (FLAC__byte*)malloc(real_length))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, block.data.unknown.data, real_length)) return false; /* read_callback_ sets the state for us */ } else block.data.unknown.data = 0; break; } if(!decoder->private_->is_seeking && decoder->private_->metadata_callback) decoder->private_->metadata_callback(decoder, &block, decoder->private_->client_data); /* now we have to free any malloc()ed data in the block */ switch(type) { case FLAC__METADATA_TYPE_PADDING: break; case FLAC__METADATA_TYPE_APPLICATION: if(0 != block.data.application.data) free(block.data.application.data); break; case FLAC__METADATA_TYPE_VORBIS_COMMENT: if(0 != block.data.vorbis_comment.vendor_string.entry) free(block.data.vorbis_comment.vendor_string.entry); if(block.data.vorbis_comment.num_comments > 0) for(i = 0; i < block.data.vorbis_comment.num_comments; i++) if(0 != block.data.vorbis_comment.comments[i].entry) free(block.data.vorbis_comment.comments[i].entry); if(0 != block.data.vorbis_comment.comments) free(block.data.vorbis_comment.comments); break; case FLAC__METADATA_TYPE_CUESHEET: if(block.data.cue_sheet.num_tracks > 0) for(i = 0; i < block.data.cue_sheet.num_tracks; i++) if(0 != block.data.cue_sheet.tracks[i].indices) free(block.data.cue_sheet.tracks[i].indices); if(0 != block.data.cue_sheet.tracks) free(block.data.cue_sheet.tracks); break; case FLAC__METADATA_TYPE_PICTURE: if(0 != block.data.picture.mime_type) free(block.data.picture.mime_type); if(0 != block.data.picture.description) free(block.data.picture.description); if(0 != block.data.picture.data) free(block.data.picture.data); break; case FLAC__METADATA_TYPE_STREAMINFO: case FLAC__METADATA_TYPE_SEEKTABLE: FLAC__ASSERT(0); default: if(0 != block.data.unknown.data) free(block.data.unknown.data); break; } } } if(is_last) { /* if this fails, it's OK, it's just a hint for the seek routine */ if(!FLAC__stream_decoder_get_decode_position(decoder, &decoder->private_->first_frame_offset)) decoder->private_->first_frame_offset = 0; decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; } return true; } FLAC__bool read_metadata_streaminfo_(FLAC__StreamDecoder *decoder, FLAC__bool is_last, unsigned length) { FLAC__uint32 x; unsigned bits, used_bits = 0; FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)); decoder->private_->stream_info.type = FLAC__METADATA_TYPE_STREAMINFO; decoder->private_->stream_info.is_last = is_last; decoder->private_->stream_info.length = length; bits = FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, bits)) return false; /* read_callback_ sets the state for us */ decoder->private_->stream_info.data.stream_info.min_blocksize = x; used_bits += bits; bits = FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN)) return false; /* read_callback_ sets the state for us */ decoder->private_->stream_info.data.stream_info.max_blocksize = x; used_bits += bits; bits = FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN)) return false; /* read_callback_ sets the state for us */ decoder->private_->stream_info.data.stream_info.min_framesize = x; used_bits += bits; bits = FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN)) return false; /* read_callback_ sets the state for us */ decoder->private_->stream_info.data.stream_info.max_framesize = x; used_bits += bits; bits = FLAC__STREAM_METADATA_STREAMINFO_SAMPLE_RATE_LEN; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_STREAMINFO_SAMPLE_RATE_LEN)) return false; /* read_callback_ sets the state for us */ decoder->private_->stream_info.data.stream_info.sample_rate = x; used_bits += bits; bits = FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN)) return false; /* read_callback_ sets the state for us */ decoder->private_->stream_info.data.stream_info.channels = x+1; used_bits += bits; bits = FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN)) return false; /* read_callback_ sets the state for us */ decoder->private_->stream_info.data.stream_info.bits_per_sample = x+1; used_bits += bits; bits = FLAC__STREAM_METADATA_STREAMINFO_TOTAL_SAMPLES_LEN; if(!FLAC__bitreader_read_raw_uint64(decoder->private_->input, &decoder->private_->stream_info.data.stream_info.total_samples, FLAC__STREAM_METADATA_STREAMINFO_TOTAL_SAMPLES_LEN)) return false; /* read_callback_ sets the state for us */ used_bits += bits; if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, decoder->private_->stream_info.data.stream_info.md5sum, 16)) return false; /* read_callback_ sets the state for us */ used_bits += 16*8; /* skip the rest of the block */ FLAC__ASSERT(used_bits % 8 == 0); length -= (used_bits / 8); if(!FLAC__bitreader_skip_byte_block_aligned_no_crc(decoder->private_->input, length)) return false; /* read_callback_ sets the state for us */ return true; } FLAC__bool read_metadata_seektable_(FLAC__StreamDecoder *decoder, FLAC__bool is_last, unsigned length) { FLAC__uint32 i, x; FLAC__uint64 xx; FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)); decoder->private_->seek_table.type = FLAC__METADATA_TYPE_SEEKTABLE; decoder->private_->seek_table.is_last = is_last; decoder->private_->seek_table.length = length; decoder->private_->seek_table.data.seek_table.num_points = length / FLAC__STREAM_METADATA_SEEKPOINT_LENGTH; /* use realloc since we may pass through here several times (e.g. after seeking) */ if(0 == (decoder->private_->seek_table.data.seek_table.points = (FLAC__StreamMetadata_SeekPoint*)safe_realloc_mul_2op_(decoder->private_->seek_table.data.seek_table.points, decoder->private_->seek_table.data.seek_table.num_points, /*times*/sizeof(FLAC__StreamMetadata_SeekPoint)))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } for(i = 0; i < decoder->private_->seek_table.data.seek_table.num_points; i++) { if(!FLAC__bitreader_read_raw_uint64(decoder->private_->input, &xx, FLAC__STREAM_METADATA_SEEKPOINT_SAMPLE_NUMBER_LEN)) return false; /* read_callback_ sets the state for us */ decoder->private_->seek_table.data.seek_table.points[i].sample_number = xx; if(!FLAC__bitreader_read_raw_uint64(decoder->private_->input, &xx, FLAC__STREAM_METADATA_SEEKPOINT_STREAM_OFFSET_LEN)) return false; /* read_callback_ sets the state for us */ decoder->private_->seek_table.data.seek_table.points[i].stream_offset = xx; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_SEEKPOINT_FRAME_SAMPLES_LEN)) return false; /* read_callback_ sets the state for us */ decoder->private_->seek_table.data.seek_table.points[i].frame_samples = x; } length -= (decoder->private_->seek_table.data.seek_table.num_points * FLAC__STREAM_METADATA_SEEKPOINT_LENGTH); /* if there is a partial point left, skip over it */ if(length > 0) { /*@@@ do a send_error_to_client_() here? there's an argument for either way */ if(!FLAC__bitreader_skip_byte_block_aligned_no_crc(decoder->private_->input, length)) return false; /* read_callback_ sets the state for us */ } return true; } FLAC__bool read_metadata_vorbiscomment_(FLAC__StreamDecoder *decoder, FLAC__StreamMetadata_VorbisComment *obj) { FLAC__uint32 i; FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)); /* read vendor string */ FLAC__ASSERT(FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN == 32); if(!FLAC__bitreader_read_uint32_little_endian(decoder->private_->input, &obj->vendor_string.length)) return false; /* read_callback_ sets the state for us */ if(obj->vendor_string.length > 0) { if(0 == (obj->vendor_string.entry = (FLAC__byte*)safe_malloc_add_2op_(obj->vendor_string.length, /*+*/1))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, obj->vendor_string.entry, obj->vendor_string.length)) return false; /* read_callback_ sets the state for us */ obj->vendor_string.entry[obj->vendor_string.length] = '\0'; } else obj->vendor_string.entry = 0; /* read num comments */ FLAC__ASSERT(FLAC__STREAM_METADATA_VORBIS_COMMENT_NUM_COMMENTS_LEN == 32); if(!FLAC__bitreader_read_uint32_little_endian(decoder->private_->input, &obj->num_comments)) return false; /* read_callback_ sets the state for us */ /* read comments */ if(obj->num_comments > 0) { if(0 == (obj->comments = (FLAC__StreamMetadata_VorbisComment_Entry*)safe_malloc_mul_2op_(obj->num_comments, /*times*/sizeof(FLAC__StreamMetadata_VorbisComment_Entry)))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } for(i = 0; i < obj->num_comments; i++) { FLAC__ASSERT(FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN == 32); if(!FLAC__bitreader_read_uint32_little_endian(decoder->private_->input, &obj->comments[i].length)) return false; /* read_callback_ sets the state for us */ if(obj->comments[i].length > 0) { if(0 == (obj->comments[i].entry = (FLAC__byte*)safe_malloc_add_2op_(obj->comments[i].length, /*+*/1))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, obj->comments[i].entry, obj->comments[i].length)) return false; /* read_callback_ sets the state for us */ obj->comments[i].entry[obj->comments[i].length] = '\0'; } else obj->comments[i].entry = 0; } } else { obj->comments = 0; } return true; } FLAC__bool read_metadata_cuesheet_(FLAC__StreamDecoder *decoder, FLAC__StreamMetadata_CueSheet *obj) { FLAC__uint32 i, j, x; FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)); memset(obj, 0, sizeof(FLAC__StreamMetadata_CueSheet)); FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN % 8 == 0); if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, (FLAC__byte*)obj->media_catalog_number, FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN/8)) return false; /* read_callback_ sets the state for us */ if(!FLAC__bitreader_read_raw_uint64(decoder->private_->input, &obj->lead_in, FLAC__STREAM_METADATA_CUESHEET_LEAD_IN_LEN)) return false; /* read_callback_ sets the state for us */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN)) return false; /* read_callback_ sets the state for us */ obj->is_cd = x? true : false; if(!FLAC__bitreader_skip_bits_no_crc(decoder->private_->input, FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN)) return false; /* read_callback_ sets the state for us */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_CUESHEET_NUM_TRACKS_LEN)) return false; /* read_callback_ sets the state for us */ obj->num_tracks = x; if(obj->num_tracks > 0) { if(0 == (obj->tracks = (FLAC__StreamMetadata_CueSheet_Track*)safe_calloc_(obj->num_tracks, sizeof(FLAC__StreamMetadata_CueSheet_Track)))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } for(i = 0; i < obj->num_tracks; i++) { FLAC__StreamMetadata_CueSheet_Track *track = &obj->tracks[i]; if(!FLAC__bitreader_read_raw_uint64(decoder->private_->input, &track->offset, FLAC__STREAM_METADATA_CUESHEET_TRACK_OFFSET_LEN)) return false; /* read_callback_ sets the state for us */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_CUESHEET_TRACK_NUMBER_LEN)) return false; /* read_callback_ sets the state for us */ track->number = (FLAC__byte)x; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN % 8 == 0); if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, (FLAC__byte*)track->isrc, FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN/8)) return false; /* read_callback_ sets the state for us */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN)) return false; /* read_callback_ sets the state for us */ track->type = x; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN)) return false; /* read_callback_ sets the state for us */ track->pre_emphasis = x; if(!FLAC__bitreader_skip_bits_no_crc(decoder->private_->input, FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN)) return false; /* read_callback_ sets the state for us */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_CUESHEET_TRACK_NUM_INDICES_LEN)) return false; /* read_callback_ sets the state for us */ track->num_indices = (FLAC__byte)x; if(track->num_indices > 0) { if(0 == (track->indices = (FLAC__StreamMetadata_CueSheet_Index*)safe_calloc_(track->num_indices, sizeof(FLAC__StreamMetadata_CueSheet_Index)))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } for(j = 0; j < track->num_indices; j++) { FLAC__StreamMetadata_CueSheet_Index *index = &track->indices[j]; if(!FLAC__bitreader_read_raw_uint64(decoder->private_->input, &index->offset, FLAC__STREAM_METADATA_CUESHEET_INDEX_OFFSET_LEN)) return false; /* read_callback_ sets the state for us */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_CUESHEET_INDEX_NUMBER_LEN)) return false; /* read_callback_ sets the state for us */ index->number = (FLAC__byte)x; if(!FLAC__bitreader_skip_bits_no_crc(decoder->private_->input, FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN)) return false; /* read_callback_ sets the state for us */ } } } } return true; } FLAC__bool read_metadata_picture_(FLAC__StreamDecoder *decoder, FLAC__StreamMetadata_Picture *obj) { FLAC__uint32 x; FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)); /* read type */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_PICTURE_TYPE_LEN)) return false; /* read_callback_ sets the state for us */ obj->type = x; /* read MIME type */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_PICTURE_MIME_TYPE_LENGTH_LEN)) return false; /* read_callback_ sets the state for us */ if(0 == (obj->mime_type = (char*)safe_malloc_add_2op_(x, /*+*/1))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } if(x > 0) { if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, (FLAC__byte*)obj->mime_type, x)) return false; /* read_callback_ sets the state for us */ } obj->mime_type[x] = '\0'; /* read description */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__STREAM_METADATA_PICTURE_DESCRIPTION_LENGTH_LEN)) return false; /* read_callback_ sets the state for us */ if(0 == (obj->description = (FLAC__byte*)safe_malloc_add_2op_(x, /*+*/1))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } if(x > 0) { if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, obj->description, x)) return false; /* read_callback_ sets the state for us */ } obj->description[x] = '\0'; /* read width */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &obj->width, FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN)) return false; /* read_callback_ sets the state for us */ /* read height */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &obj->height, FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN)) return false; /* read_callback_ sets the state for us */ /* read depth */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &obj->depth, FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN)) return false; /* read_callback_ sets the state for us */ /* read colors */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &obj->colors, FLAC__STREAM_METADATA_PICTURE_COLORS_LEN)) return false; /* read_callback_ sets the state for us */ /* read data */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &(obj->data_length), FLAC__STREAM_METADATA_PICTURE_DATA_LENGTH_LEN)) return false; /* read_callback_ sets the state for us */ if(0 == (obj->data = (FLAC__byte*)safe_malloc_(obj->data_length))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } if(obj->data_length > 0) { if(!FLAC__bitreader_read_byte_block_aligned_no_crc(decoder->private_->input, obj->data, obj->data_length)) return false; /* read_callback_ sets the state for us */ } return true; } FLAC__bool skip_id3v2_tag_(FLAC__StreamDecoder *decoder) { FLAC__uint32 x; unsigned i, skip; /* skip the version and flags bytes */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 24)) return false; /* read_callback_ sets the state for us */ /* get the size (in bytes) to skip */ skip = 0; for(i = 0; i < 4; i++) { if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) return false; /* read_callback_ sets the state for us */ skip <<= 7; skip |= (x & 0x7f); } /* skip the rest of the tag */ if(!FLAC__bitreader_skip_byte_block_aligned_no_crc(decoder->private_->input, skip)) return false; /* read_callback_ sets the state for us */ return true; } FLAC__bool frame_sync_(FLAC__StreamDecoder *decoder) { FLAC__uint32 x; FLAC__bool first = true; /* If we know the total number of samples in the stream, stop if we've read that many. */ /* This will stop us, for example, from wasting time trying to sync on an ID3V1 tag. */ if(FLAC__stream_decoder_get_total_samples(decoder) > 0) { if(decoder->private_->samples_decoded >= FLAC__stream_decoder_get_total_samples(decoder)) { decoder->protected_->state = FLAC__STREAM_DECODER_END_OF_STREAM; return true; } } /* make sure we're byte aligned */ if(!FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)) { if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__bitreader_bits_left_for_byte_alignment(decoder->private_->input))) return false; /* read_callback_ sets the state for us */ } while(1) { if(decoder->private_->cached) { x = (FLAC__uint32)decoder->private_->lookahead; decoder->private_->cached = false; } else { if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) return false; /* read_callback_ sets the state for us */ } if(x == 0xff) { /* MAGIC NUMBER for the first 8 frame sync bits */ decoder->private_->header_warmup[0] = (FLAC__byte)x; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) return false; /* read_callback_ sets the state for us */ /* we have to check if we just read two 0xff's in a row; the second may actually be the beginning of the sync code */ /* else we have to check if the second byte is the end of a sync code */ if(x == 0xff) { /* MAGIC NUMBER for the first 8 frame sync bits */ decoder->private_->lookahead = (FLAC__byte)x; decoder->private_->cached = true; } else if(x >> 2 == 0x3e) { /* MAGIC NUMBER for the last 6 sync bits */ decoder->private_->header_warmup[1] = (FLAC__byte)x; decoder->protected_->state = FLAC__STREAM_DECODER_READ_FRAME; return true; } } if(first) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC); first = false; } } return true; } FLAC__bool read_frame_(FLAC__StreamDecoder *decoder, FLAC__bool *got_a_frame, FLAC__bool do_full_decode) { unsigned channel; unsigned i; FLAC__int32 mid, side; unsigned frame_crc; /* the one we calculate from the input stream */ FLAC__uint32 x; *got_a_frame = false; /* init the CRC */ frame_crc = 0; frame_crc = FLAC__CRC16_UPDATE(decoder->private_->header_warmup[0], frame_crc); frame_crc = FLAC__CRC16_UPDATE(decoder->private_->header_warmup[1], frame_crc); FLAC__bitreader_reset_read_crc16(decoder->private_->input, (FLAC__uint16)frame_crc); if(!read_frame_header_(decoder)) return false; if(decoder->protected_->state == FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC) /* means we didn't sync on a valid header */ return true; if(!allocate_output_(decoder, decoder->private_->frame.header.blocksize, decoder->private_->frame.header.channels)) return false; for(channel = 0; channel < decoder->private_->frame.header.channels; channel++) { /* * first figure the correct bits-per-sample of the subframe */ unsigned bps = decoder->private_->frame.header.bits_per_sample; switch(decoder->private_->frame.header.channel_assignment) { case FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT: /* no adjustment needed */ break; case FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE: FLAC__ASSERT(decoder->private_->frame.header.channels == 2); if(channel == 1) bps++; break; case FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE: FLAC__ASSERT(decoder->private_->frame.header.channels == 2); if(channel == 0) bps++; break; case FLAC__CHANNEL_ASSIGNMENT_MID_SIDE: FLAC__ASSERT(decoder->private_->frame.header.channels == 2); if(channel == 1) bps++; break; default: FLAC__ASSERT(0); } /* * now read it */ if(!read_subframe_(decoder, channel, bps, do_full_decode)) return false; if(decoder->protected_->state == FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC) /* means bad sync or got corruption */ return true; } if(!read_zero_padding_(decoder)) return false; if(decoder->protected_->state == FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC) /* means bad sync or got corruption (i.e. "zero bits" were not all zeroes) */ return true; /* * Read the frame CRC-16 from the footer and check */ frame_crc = FLAC__bitreader_get_read_crc16(decoder->private_->input); if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, FLAC__FRAME_FOOTER_CRC_LEN)) return false; /* read_callback_ sets the state for us */ if(frame_crc == x) { if(do_full_decode) { /* Undo any special channel coding */ switch(decoder->private_->frame.header.channel_assignment) { case FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT: /* do nothing */ break; case FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE: FLAC__ASSERT(decoder->private_->frame.header.channels == 2); for(i = 0; i < decoder->private_->frame.header.blocksize; i++) decoder->private_->output[1][i] = decoder->private_->output[0][i] - decoder->private_->output[1][i]; break; case FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE: FLAC__ASSERT(decoder->private_->frame.header.channels == 2); for(i = 0; i < decoder->private_->frame.header.blocksize; i++) decoder->private_->output[0][i] += decoder->private_->output[1][i]; break; case FLAC__CHANNEL_ASSIGNMENT_MID_SIDE: FLAC__ASSERT(decoder->private_->frame.header.channels == 2); for(i = 0; i < decoder->private_->frame.header.blocksize; i++) { #if 1 mid = decoder->private_->output[0][i]; side = decoder->private_->output[1][i]; mid <<= 1; mid |= (side & 1); /* i.e. if 'side' is odd... */ decoder->private_->output[0][i] = (mid + side) >> 1; decoder->private_->output[1][i] = (mid - side) >> 1; #else /* OPT: without 'side' temp variable */ mid = (decoder->private_->output[0][i] << 1) | (decoder->private_->output[1][i] & 1); /* i.e. if 'side' is odd... */ decoder->private_->output[0][i] = (mid + decoder->private_->output[1][i]) >> 1; decoder->private_->output[1][i] = (mid - decoder->private_->output[1][i]) >> 1; #endif } break; default: FLAC__ASSERT(0); break; } } } else { /* Bad frame, emit error and zero the output signal */ send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_FRAME_CRC_MISMATCH); if(do_full_decode) { for(channel = 0; channel < decoder->private_->frame.header.channels; channel++) { memset(decoder->private_->output[channel], 0, sizeof(FLAC__int32) * decoder->private_->frame.header.blocksize); } } } *got_a_frame = true; /* we wait to update fixed_block_size until here, when we're sure we've got a proper frame and hence a correct blocksize */ if(decoder->private_->next_fixed_block_size) decoder->private_->fixed_block_size = decoder->private_->next_fixed_block_size; /* put the latest values into the public section of the decoder instance */ decoder->protected_->channels = decoder->private_->frame.header.channels; decoder->protected_->channel_assignment = decoder->private_->frame.header.channel_assignment; decoder->protected_->bits_per_sample = decoder->private_->frame.header.bits_per_sample; decoder->protected_->sample_rate = decoder->private_->frame.header.sample_rate; decoder->protected_->blocksize = decoder->private_->frame.header.blocksize; FLAC__ASSERT(decoder->private_->frame.header.number_type == FLAC__FRAME_NUMBER_TYPE_SAMPLE_NUMBER); decoder->private_->samples_decoded = decoder->private_->frame.header.number.sample_number + decoder->private_->frame.header.blocksize; /* write it */ if(do_full_decode) { if(write_audio_frame_to_client_(decoder, &decoder->private_->frame, (const FLAC__int32 * const *)decoder->private_->output) != FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE) return false; } decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } FLAC__bool read_frame_header_(FLAC__StreamDecoder *decoder) { FLAC__uint32 x; FLAC__uint64 xx; unsigned i, blocksize_hint = 0, sample_rate_hint = 0; FLAC__byte crc8, raw_header[16]; /* MAGIC NUMBER based on the maximum frame header size, including CRC */ unsigned raw_header_len; FLAC__bool is_unparseable = false; FLAC__ASSERT(FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)); /* init the raw header with the saved bits from synchronization */ raw_header[0] = decoder->private_->header_warmup[0]; raw_header[1] = decoder->private_->header_warmup[1]; raw_header_len = 2; /* check to make sure that reserved bit is 0 */ if(raw_header[1] & 0x02) /* MAGIC NUMBER */ is_unparseable = true; /* * Note that along the way as we read the header, we look for a sync * code inside. If we find one it would indicate that our original * sync was bad since there cannot be a sync code in a valid header. * * Three kinds of things can go wrong when reading the frame header: * 1) We may have sync'ed incorrectly and not landed on a frame header. * If we don't find a sync code, it can end up looking like we read * a valid but unparseable header, until getting to the frame header * CRC. Even then we could get a false positive on the CRC. * 2) We may have sync'ed correctly but on an unparseable frame (from a * future encoder). * 3) We may be on a damaged frame which appears valid but unparseable. * * For all these reasons, we try and read a complete frame header as * long as it seems valid, even if unparseable, up until the frame * header CRC. */ /* * read in the raw header as bytes so we can CRC it, and parse it on the way */ for(i = 0; i < 2; i++) { if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) return false; /* read_callback_ sets the state for us */ if(x == 0xff) { /* MAGIC NUMBER for the first 8 frame sync bits */ /* if we get here it means our original sync was erroneous since the sync code cannot appear in the header */ decoder->private_->lookahead = (FLAC__byte)x; decoder->private_->cached = true; send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_BAD_HEADER); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } raw_header[raw_header_len++] = (FLAC__byte)x; } switch(x = raw_header[2] >> 4) { case 0: is_unparseable = true; break; case 1: decoder->private_->frame.header.blocksize = 192; break; case 2: case 3: case 4: case 5: decoder->private_->frame.header.blocksize = 576 << (x-2); break; case 6: case 7: blocksize_hint = x; break; case 8: case 9: case 10: case 11: case 12: case 13: case 14: case 15: decoder->private_->frame.header.blocksize = 256 << (x-8); break; default: FLAC__ASSERT(0); break; } switch(x = raw_header[2] & 0x0f) { case 0: if(decoder->private_->has_stream_info) decoder->private_->frame.header.sample_rate = decoder->private_->stream_info.data.stream_info.sample_rate; else is_unparseable = true; break; case 1: decoder->private_->frame.header.sample_rate = 88200; break; case 2: decoder->private_->frame.header.sample_rate = 176400; break; case 3: decoder->private_->frame.header.sample_rate = 192000; break; case 4: decoder->private_->frame.header.sample_rate = 8000; break; case 5: decoder->private_->frame.header.sample_rate = 16000; break; case 6: decoder->private_->frame.header.sample_rate = 22050; break; case 7: decoder->private_->frame.header.sample_rate = 24000; break; case 8: decoder->private_->frame.header.sample_rate = 32000; break; case 9: decoder->private_->frame.header.sample_rate = 44100; break; case 10: decoder->private_->frame.header.sample_rate = 48000; break; case 11: decoder->private_->frame.header.sample_rate = 96000; break; case 12: case 13: case 14: sample_rate_hint = x; break; case 15: send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_BAD_HEADER); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; default: FLAC__ASSERT(0); } x = (unsigned)(raw_header[3] >> 4); if(x & 8) { decoder->private_->frame.header.channels = 2; switch(x & 7) { case 0: decoder->private_->frame.header.channel_assignment = FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE; break; case 1: decoder->private_->frame.header.channel_assignment = FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE; break; case 2: decoder->private_->frame.header.channel_assignment = FLAC__CHANNEL_ASSIGNMENT_MID_SIDE; break; default: is_unparseable = true; break; } } else { decoder->private_->frame.header.channels = (unsigned)x + 1; decoder->private_->frame.header.channel_assignment = FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT; } switch(x = (unsigned)(raw_header[3] & 0x0e) >> 1) { case 0: if(decoder->private_->has_stream_info) decoder->private_->frame.header.bits_per_sample = decoder->private_->stream_info.data.stream_info.bits_per_sample; else is_unparseable = true; break; case 1: decoder->private_->frame.header.bits_per_sample = 8; break; case 2: decoder->private_->frame.header.bits_per_sample = 12; break; case 4: decoder->private_->frame.header.bits_per_sample = 16; break; case 5: decoder->private_->frame.header.bits_per_sample = 20; break; case 6: decoder->private_->frame.header.bits_per_sample = 24; break; case 3: case 7: is_unparseable = true; break; default: FLAC__ASSERT(0); break; } /* check to make sure that reserved bit is 0 */ if(raw_header[3] & 0x01) /* MAGIC NUMBER */ is_unparseable = true; /* read the frame's starting sample number (or frame number as the case may be) */ if( raw_header[1] & 0x01 || /*@@@ this clause is a concession to the old way of doing variable blocksize; the only known implementation is flake and can probably be removed without inconveniencing anyone */ (decoder->private_->has_stream_info && decoder->private_->stream_info.data.stream_info.min_blocksize != decoder->private_->stream_info.data.stream_info.max_blocksize) ) { /* variable blocksize */ if(!FLAC__bitreader_read_utf8_uint64(decoder->private_->input, &xx, raw_header, &raw_header_len)) return false; /* read_callback_ sets the state for us */ if(xx == FLAC__U64L(0xffffffffffffffff)) { /* i.e. non-UTF8 code... */ decoder->private_->lookahead = raw_header[raw_header_len-1]; /* back up as much as we can */ decoder->private_->cached = true; send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_BAD_HEADER); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } decoder->private_->frame.header.number_type = FLAC__FRAME_NUMBER_TYPE_SAMPLE_NUMBER; decoder->private_->frame.header.number.sample_number = xx; } else { /* fixed blocksize */ if(!FLAC__bitreader_read_utf8_uint32(decoder->private_->input, &x, raw_header, &raw_header_len)) return false; /* read_callback_ sets the state for us */ if(x == 0xffffffff) { /* i.e. non-UTF8 code... */ decoder->private_->lookahead = raw_header[raw_header_len-1]; /* back up as much as we can */ decoder->private_->cached = true; send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_BAD_HEADER); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } decoder->private_->frame.header.number_type = FLAC__FRAME_NUMBER_TYPE_FRAME_NUMBER; decoder->private_->frame.header.number.frame_number = x; } if(blocksize_hint) { if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) return false; /* read_callback_ sets the state for us */ raw_header[raw_header_len++] = (FLAC__byte)x; if(blocksize_hint == 7) { FLAC__uint32 _x; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &_x, 8)) return false; /* read_callback_ sets the state for us */ raw_header[raw_header_len++] = (FLAC__byte)_x; x = (x << 8) | _x; } decoder->private_->frame.header.blocksize = x+1; } if(sample_rate_hint) { if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) return false; /* read_callback_ sets the state for us */ raw_header[raw_header_len++] = (FLAC__byte)x; if(sample_rate_hint != 12) { FLAC__uint32 _x; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &_x, 8)) return false; /* read_callback_ sets the state for us */ raw_header[raw_header_len++] = (FLAC__byte)_x; x = (x << 8) | _x; } if(sample_rate_hint == 12) decoder->private_->frame.header.sample_rate = x*1000; else if(sample_rate_hint == 13) decoder->private_->frame.header.sample_rate = x; else decoder->private_->frame.header.sample_rate = x*10; } /* read the CRC-8 byte */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) return false; /* read_callback_ sets the state for us */ crc8 = (FLAC__byte)x; if(FLAC__crc8(raw_header, raw_header_len) != crc8) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_BAD_HEADER); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } /* calculate the sample number from the frame number if needed */ decoder->private_->next_fixed_block_size = 0; if(decoder->private_->frame.header.number_type == FLAC__FRAME_NUMBER_TYPE_FRAME_NUMBER) { x = decoder->private_->frame.header.number.frame_number; decoder->private_->frame.header.number_type = FLAC__FRAME_NUMBER_TYPE_SAMPLE_NUMBER; if(decoder->private_->fixed_block_size) decoder->private_->frame.header.number.sample_number = (FLAC__uint64)decoder->private_->fixed_block_size * (FLAC__uint64)x; else if(decoder->private_->has_stream_info) { if(decoder->private_->stream_info.data.stream_info.min_blocksize == decoder->private_->stream_info.data.stream_info.max_blocksize) { decoder->private_->frame.header.number.sample_number = (FLAC__uint64)decoder->private_->stream_info.data.stream_info.min_blocksize * (FLAC__uint64)x; decoder->private_->next_fixed_block_size = decoder->private_->stream_info.data.stream_info.max_blocksize; } else is_unparseable = true; } else if(x == 0) { decoder->private_->frame.header.number.sample_number = 0; decoder->private_->next_fixed_block_size = decoder->private_->frame.header.blocksize; } else { /* can only get here if the stream has invalid frame numbering and no STREAMINFO, so assume it's not the last (possibly short) frame */ decoder->private_->frame.header.number.sample_number = (FLAC__uint64)decoder->private_->frame.header.blocksize * (FLAC__uint64)x; } } if(is_unparseable) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } return true; } FLAC__bool read_subframe_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, FLAC__bool do_full_decode) { FLAC__uint32 x; FLAC__bool wasted_bits; unsigned i; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &x, 8)) /* MAGIC NUMBER */ return false; /* read_callback_ sets the state for us */ wasted_bits = (x & 1); x &= 0xfe; if(wasted_bits) { unsigned u; if(!FLAC__bitreader_read_unary_unsigned(decoder->private_->input, &u)) return false; /* read_callback_ sets the state for us */ decoder->private_->frame.subframes[channel].wasted_bits = u+1; bps -= decoder->private_->frame.subframes[channel].wasted_bits; } else decoder->private_->frame.subframes[channel].wasted_bits = 0; /* * Lots of magic numbers here */ if(x & 0x80) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } else if(x == 0) { if(!read_subframe_constant_(decoder, channel, bps, do_full_decode)) return false; } else if(x == 2) { if(!read_subframe_verbatim_(decoder, channel, bps, do_full_decode)) return false; } else if(x < 16) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } else if(x <= 24) { if(!read_subframe_fixed_(decoder, channel, bps, (x>>1)&7, do_full_decode)) return false; if(decoder->protected_->state == FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC) /* means bad sync or got corruption */ return true; } else if(x < 64) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } else { if(!read_subframe_lpc_(decoder, channel, bps, ((x>>1)&31)+1, do_full_decode)) return false; if(decoder->protected_->state == FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC) /* means bad sync or got corruption */ return true; } if(wasted_bits && do_full_decode) { x = decoder->private_->frame.subframes[channel].wasted_bits; for(i = 0; i < decoder->private_->frame.header.blocksize; i++) decoder->private_->output[channel][i] <<= x; } return true; } FLAC__bool read_subframe_constant_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, FLAC__bool do_full_decode) { FLAC__Subframe_Constant *subframe = &decoder->private_->frame.subframes[channel].data.constant; FLAC__int32 x; unsigned i; FLAC__int32 *output = decoder->private_->output[channel]; decoder->private_->frame.subframes[channel].type = FLAC__SUBFRAME_TYPE_CONSTANT; if(!FLAC__bitreader_read_raw_int32(decoder->private_->input, &x, bps)) return false; /* read_callback_ sets the state for us */ subframe->value = x; /* decode the subframe */ if(do_full_decode) { for(i = 0; i < decoder->private_->frame.header.blocksize; i++) output[i] = x; } return true; } FLAC__bool read_subframe_fixed_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, const unsigned order, FLAC__bool do_full_decode) { FLAC__Subframe_Fixed *subframe = &decoder->private_->frame.subframes[channel].data.fixed; FLAC__int32 i32; FLAC__uint32 u32; unsigned u; decoder->private_->frame.subframes[channel].type = FLAC__SUBFRAME_TYPE_FIXED; subframe->residual = decoder->private_->residual[channel]; subframe->order = order; /* read warm-up samples */ for(u = 0; u < order; u++) { if(!FLAC__bitreader_read_raw_int32(decoder->private_->input, &i32, bps)) return false; /* read_callback_ sets the state for us */ subframe->warmup[u] = i32; } /* read entropy coding method info */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &u32, FLAC__ENTROPY_CODING_METHOD_TYPE_LEN)) return false; /* read_callback_ sets the state for us */ subframe->entropy_coding_method.type = (FLAC__EntropyCodingMethodType)u32; switch(subframe->entropy_coding_method.type) { case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE: case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2: if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &u32, FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ORDER_LEN)) return false; /* read_callback_ sets the state for us */ subframe->entropy_coding_method.data.partitioned_rice.order = u32; subframe->entropy_coding_method.data.partitioned_rice.contents = &decoder->private_->partitioned_rice_contents[channel]; break; default: send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } /* read residual */ switch(subframe->entropy_coding_method.type) { case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE: case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2: if(!read_residual_partitioned_rice_(decoder, order, subframe->entropy_coding_method.data.partitioned_rice.order, &decoder->private_->partitioned_rice_contents[channel], decoder->private_->residual[channel], /*is_extended=*/subframe->entropy_coding_method.type == FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2)) return false; break; default: FLAC__ASSERT(0); } /* decode the subframe */ if(do_full_decode) { memcpy(decoder->private_->output[channel], subframe->warmup, sizeof(FLAC__int32) * order); FLAC__fixed_restore_signal(decoder->private_->residual[channel], decoder->private_->frame.header.blocksize-order, order, decoder->private_->output[channel]+order); } return true; } FLAC__bool read_subframe_lpc_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, const unsigned order, FLAC__bool do_full_decode) { FLAC__Subframe_LPC *subframe = &decoder->private_->frame.subframes[channel].data.lpc; FLAC__int32 i32; FLAC__uint32 u32; unsigned u; decoder->private_->frame.subframes[channel].type = FLAC__SUBFRAME_TYPE_LPC; subframe->residual = decoder->private_->residual[channel]; subframe->order = order; /* read warm-up samples */ for(u = 0; u < order; u++) { if(!FLAC__bitreader_read_raw_int32(decoder->private_->input, &i32, bps)) return false; /* read_callback_ sets the state for us */ subframe->warmup[u] = i32; } /* read qlp coeff precision */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &u32, FLAC__SUBFRAME_LPC_QLP_COEFF_PRECISION_LEN)) return false; /* read_callback_ sets the state for us */ if(u32 == (1u << FLAC__SUBFRAME_LPC_QLP_COEFF_PRECISION_LEN) - 1) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } subframe->qlp_coeff_precision = u32+1; /* read qlp shift */ if(!FLAC__bitreader_read_raw_int32(decoder->private_->input, &i32, FLAC__SUBFRAME_LPC_QLP_SHIFT_LEN)) return false; /* read_callback_ sets the state for us */ subframe->quantization_level = i32; /* read quantized lp coefficiencts */ for(u = 0; u < order; u++) { if(!FLAC__bitreader_read_raw_int32(decoder->private_->input, &i32, subframe->qlp_coeff_precision)) return false; /* read_callback_ sets the state for us */ subframe->qlp_coeff[u] = i32; } /* read entropy coding method info */ if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &u32, FLAC__ENTROPY_CODING_METHOD_TYPE_LEN)) return false; /* read_callback_ sets the state for us */ subframe->entropy_coding_method.type = (FLAC__EntropyCodingMethodType)u32; switch(subframe->entropy_coding_method.type) { case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE: case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2: if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &u32, FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ORDER_LEN)) return false; /* read_callback_ sets the state for us */ subframe->entropy_coding_method.data.partitioned_rice.order = u32; subframe->entropy_coding_method.data.partitioned_rice.contents = &decoder->private_->partitioned_rice_contents[channel]; break; default: send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } /* read residual */ switch(subframe->entropy_coding_method.type) { case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE: case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2: if(!read_residual_partitioned_rice_(decoder, order, subframe->entropy_coding_method.data.partitioned_rice.order, &decoder->private_->partitioned_rice_contents[channel], decoder->private_->residual[channel], /*is_extended=*/subframe->entropy_coding_method.type == FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2)) return false; break; default: FLAC__ASSERT(0); } /* decode the subframe */ if(do_full_decode) { memcpy(decoder->private_->output[channel], subframe->warmup, sizeof(FLAC__int32) * order); /*@@@@@@ technically not pessimistic enough, should be more like if( (FLAC__uint64)order * ((((FLAC__uint64)1)<qlp_coeff_precision)-1) < (((FLAC__uint64)-1) << 32) ) */ if(bps + subframe->qlp_coeff_precision + FLAC__bitmath_ilog2(order) <= 32) if(bps <= 16 && subframe->qlp_coeff_precision <= 16) { if(order <= 8) decoder->private_->local_lpc_restore_signal_16bit_order8(decoder->private_->residual[channel], decoder->private_->frame.header.blocksize-order, subframe->qlp_coeff, order, subframe->quantization_level, decoder->private_->output[channel]+order); else decoder->private_->local_lpc_restore_signal_16bit(decoder->private_->residual[channel], decoder->private_->frame.header.blocksize-order, subframe->qlp_coeff, order, subframe->quantization_level, decoder->private_->output[channel]+order); } else decoder->private_->local_lpc_restore_signal(decoder->private_->residual[channel], decoder->private_->frame.header.blocksize-order, subframe->qlp_coeff, order, subframe->quantization_level, decoder->private_->output[channel]+order); else decoder->private_->local_lpc_restore_signal_64bit(decoder->private_->residual[channel], decoder->private_->frame.header.blocksize-order, subframe->qlp_coeff, order, subframe->quantization_level, decoder->private_->output[channel]+order); } return true; } FLAC__bool read_subframe_verbatim_(FLAC__StreamDecoder *decoder, unsigned channel, unsigned bps, FLAC__bool do_full_decode) { FLAC__Subframe_Verbatim *subframe = &decoder->private_->frame.subframes[channel].data.verbatim; FLAC__int32 x, *residual = decoder->private_->residual[channel]; unsigned i; decoder->private_->frame.subframes[channel].type = FLAC__SUBFRAME_TYPE_VERBATIM; subframe->data = residual; for(i = 0; i < decoder->private_->frame.header.blocksize; i++) { if(!FLAC__bitreader_read_raw_int32(decoder->private_->input, &x, bps)) return false; /* read_callback_ sets the state for us */ residual[i] = x; } /* decode the subframe */ if(do_full_decode) memcpy(decoder->private_->output[channel], subframe->data, sizeof(FLAC__int32) * decoder->private_->frame.header.blocksize); return true; } FLAC__bool read_residual_partitioned_rice_(FLAC__StreamDecoder *decoder, unsigned predictor_order, unsigned partition_order, FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents, FLAC__int32 *residual, FLAC__bool is_extended) { FLAC__uint32 rice_parameter; FLAC__int32 i; unsigned partition, sample, u; const unsigned partitions = 1u << partition_order; const unsigned partition_samples = partition_order > 0? decoder->private_->frame.header.blocksize >> partition_order : decoder->private_->frame.header.blocksize - predictor_order; const unsigned plen = is_extended? FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_PARAMETER_LEN : FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_PARAMETER_LEN; const unsigned pesc = is_extended? FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_ESCAPE_PARAMETER : FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ESCAPE_PARAMETER; /* sanity checks */ if(partition_order == 0) { if(decoder->private_->frame.header.blocksize < predictor_order) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } } else { if(partition_samples < predictor_order) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; return true; } } if(!FLAC__format_entropy_coding_method_partitioned_rice_contents_ensure_size(partitioned_rice_contents, max(6, partition_order))) { decoder->protected_->state = FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR; return false; } sample = 0; for(partition = 0; partition < partitions; partition++) { if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &rice_parameter, plen)) return false; /* read_callback_ sets the state for us */ partitioned_rice_contents->parameters[partition] = rice_parameter; if(rice_parameter < pesc) { partitioned_rice_contents->raw_bits[partition] = 0; u = (partition_order == 0 || partition > 0)? partition_samples : partition_samples - predictor_order; FLAC__ASSERT (sizeof (int) == 4); // ppgb 20071120: needed for the following cast. if(!decoder->private_->local_bitreader_read_rice_signed_block(decoder->private_->input, (int *) residual + sample, u, rice_parameter)) return false; /* read_callback_ sets the state for us */ sample += u; } else { if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &rice_parameter, FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_RAW_LEN)) return false; /* read_callback_ sets the state for us */ partitioned_rice_contents->raw_bits[partition] = rice_parameter; for(u = (partition_order == 0 || partition > 0)? 0 : predictor_order; u < partition_samples; u++, sample++) { if(!FLAC__bitreader_read_raw_int32(decoder->private_->input, &i, rice_parameter)) return false; /* read_callback_ sets the state for us */ residual[sample] = i; } } } return true; } FLAC__bool read_zero_padding_(FLAC__StreamDecoder *decoder) { if(!FLAC__bitreader_is_consumed_byte_aligned(decoder->private_->input)) { FLAC__uint32 zero = 0; if(!FLAC__bitreader_read_raw_uint32(decoder->private_->input, &zero, FLAC__bitreader_bits_left_for_byte_alignment(decoder->private_->input))) return false; /* read_callback_ sets the state for us */ if(zero != 0) { send_error_to_client_(decoder, FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC); decoder->protected_->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; } } return true; } FLAC__bool read_callback_(FLAC__byte buffer[], size_t *bytes, void *client_data) { FLAC__StreamDecoder *decoder = (FLAC__StreamDecoder *)client_data; if( #if FLAC__HAS_OGG /* see [1] HACK NOTE below for why we don't call the eof_callback when decoding Ogg FLAC */ !decoder->private_->is_ogg && #endif decoder->private_->eof_callback && decoder->private_->eof_callback(decoder, decoder->private_->client_data) ) { *bytes = 0; decoder->protected_->state = FLAC__STREAM_DECODER_END_OF_STREAM; return false; } else if(*bytes > 0) { /* While seeking, it is possible for our seek to land in the * middle of audio data that looks exactly like a frame header * from a future version of an encoder. When that happens, our * error callback will get an * FLAC__STREAM_DECODER_UNPARSEABLE_STREAM and increment its * unparseable_frame_count. But there is a remote possibility * that it is properly synced at such a "future-codec frame", * so to make sure, we wait to see many "unparseable" errors in * a row before bailing out. */ if(decoder->private_->is_seeking && decoder->private_->unparseable_frame_count > 20) { decoder->protected_->state = FLAC__STREAM_DECODER_ABORTED; return false; } else { const FLAC__StreamDecoderReadStatus status = #if FLAC__HAS_OGG decoder->private_->is_ogg? read_callback_ogg_aspect_(decoder, buffer, bytes) : #endif decoder->private_->read_callback(decoder, buffer, bytes, decoder->private_->client_data) ; if(status == FLAC__STREAM_DECODER_READ_STATUS_ABORT) { decoder->protected_->state = FLAC__STREAM_DECODER_ABORTED; return false; } else if(*bytes == 0) { if( status == FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM || ( #if FLAC__HAS_OGG /* see [1] HACK NOTE below for why we don't call the eof_callback when decoding Ogg FLAC */ !decoder->private_->is_ogg && #endif decoder->private_->eof_callback && decoder->private_->eof_callback(decoder, decoder->private_->client_data) ) ) { decoder->protected_->state = FLAC__STREAM_DECODER_END_OF_STREAM; return false; } else return true; } else return true; } } else { /* abort to avoid a deadlock */ decoder->protected_->state = FLAC__STREAM_DECODER_ABORTED; return false; } /* [1] @@@ HACK NOTE: The end-of-stream checking has to be hacked around * for Ogg FLAC. This is because the ogg decoder aspect can lose sync * and at the same time hit the end of the stream (for example, seeking * to a point that is after the beginning of the last Ogg page). There * is no way to report an Ogg sync loss through the callbacks (see note * in read_callback_ogg_aspect_()) so it returns CONTINUE with *bytes==0. * So to keep the decoder from stopping at this point we gate the call * to the eof_callback and let the Ogg decoder aspect set the * end-of-stream state when it is needed. */ } #if FLAC__HAS_OGG FLAC__StreamDecoderReadStatus read_callback_ogg_aspect_(const FLAC__StreamDecoder *decoder, FLAC__byte buffer[], size_t *bytes) { switch(FLAC__ogg_decoder_aspect_read_callback_wrapper(&decoder->protected_->ogg_decoder_aspect, buffer, bytes, read_callback_proxy_, decoder, decoder->private_->client_data)) { case FLAC__OGG_DECODER_ASPECT_READ_STATUS_OK: return FLAC__STREAM_DECODER_READ_STATUS_CONTINUE; /* we don't really have a way to handle lost sync via read * callback so we'll let it pass and let the underlying * FLAC decoder catch the error */ case FLAC__OGG_DECODER_ASPECT_READ_STATUS_LOST_SYNC: return FLAC__STREAM_DECODER_READ_STATUS_CONTINUE; case FLAC__OGG_DECODER_ASPECT_READ_STATUS_END_OF_STREAM: return FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM; case FLAC__OGG_DECODER_ASPECT_READ_STATUS_NOT_FLAC: case FLAC__OGG_DECODER_ASPECT_READ_STATUS_UNSUPPORTED_MAPPING_VERSION: case FLAC__OGG_DECODER_ASPECT_READ_STATUS_ABORT: case FLAC__OGG_DECODER_ASPECT_READ_STATUS_ERROR: case FLAC__OGG_DECODER_ASPECT_READ_STATUS_MEMORY_ALLOCATION_ERROR: return FLAC__STREAM_DECODER_READ_STATUS_ABORT; default: FLAC__ASSERT(0); /* double protection */ return FLAC__STREAM_DECODER_READ_STATUS_ABORT; } } FLAC__OggDecoderAspectReadStatus read_callback_proxy_(const void *void_decoder, FLAC__byte buffer[], size_t *bytes, void *client_data) { FLAC__StreamDecoder *decoder = (FLAC__StreamDecoder*)void_decoder; switch(decoder->private_->read_callback(decoder, buffer, bytes, client_data)) { case FLAC__STREAM_DECODER_READ_STATUS_CONTINUE: return FLAC__OGG_DECODER_ASPECT_READ_STATUS_OK; case FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM: return FLAC__OGG_DECODER_ASPECT_READ_STATUS_END_OF_STREAM; case FLAC__STREAM_DECODER_READ_STATUS_ABORT: return FLAC__OGG_DECODER_ASPECT_READ_STATUS_ABORT; default: /* double protection: */ FLAC__ASSERT(0); return FLAC__OGG_DECODER_ASPECT_READ_STATUS_ABORT; } } #endif FLAC__StreamDecoderWriteStatus write_audio_frame_to_client_(FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer[]) { if(decoder->private_->is_seeking) { FLAC__uint64 this_frame_sample = frame->header.number.sample_number; FLAC__uint64 next_frame_sample = this_frame_sample + (FLAC__uint64)frame->header.blocksize; FLAC__uint64 target_sample = decoder->private_->target_sample; FLAC__ASSERT(frame->header.number_type == FLAC__FRAME_NUMBER_TYPE_SAMPLE_NUMBER); #if FLAC__HAS_OGG decoder->private_->got_a_frame = true; #endif decoder->private_->last_frame = *frame; /* save the frame */ if(this_frame_sample <= target_sample && target_sample < next_frame_sample) { /* we hit our target frame */ unsigned delta = (unsigned)(target_sample - this_frame_sample); /* kick out of seek mode */ decoder->private_->is_seeking = false; /* shift out the samples before target_sample */ if(delta > 0) { unsigned channel; const FLAC__int32 *newbuffer[FLAC__MAX_CHANNELS]; for(channel = 0; channel < frame->header.channels; channel++) newbuffer[channel] = buffer[channel] + delta; decoder->private_->last_frame.header.blocksize -= delta; decoder->private_->last_frame.header.number.sample_number += (FLAC__uint64)delta; /* write the relevant samples */ return decoder->private_->write_callback(decoder, &decoder->private_->last_frame, newbuffer, decoder->private_->client_data); } else { /* write the relevant samples */ return decoder->private_->write_callback(decoder, frame, buffer, decoder->private_->client_data); } } else { return FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE; } } else { /* * If we never got STREAMINFO, turn off MD5 checking to save * cycles since we don't have a sum to compare to anyway */ if(!decoder->private_->has_stream_info) decoder->private_->do_md5_checking = false; if(decoder->private_->do_md5_checking) { if(!FLAC__MD5Accumulate(&decoder->private_->md5context, buffer, frame->header.channels, frame->header.blocksize, (frame->header.bits_per_sample+7) / 8)) return FLAC__STREAM_DECODER_WRITE_STATUS_ABORT; } return decoder->private_->write_callback(decoder, frame, buffer, decoder->private_->client_data); } } void send_error_to_client_(const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status) { if(!decoder->private_->is_seeking) decoder->private_->error_callback(decoder, status, decoder->private_->client_data); else if(status == FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM) decoder->private_->unparseable_frame_count++; } FLAC__bool seek_to_absolute_sample_(FLAC__StreamDecoder *decoder, FLAC__uint64 stream_length, FLAC__uint64 target_sample) { FLAC__uint64 first_frame_offset = decoder->private_->first_frame_offset, lower_bound, upper_bound, lower_bound_sample, upper_bound_sample, this_frame_sample; FLAC__int64 pos = -1; int i; unsigned approx_bytes_per_frame; FLAC__bool first_seek = true; const FLAC__uint64 total_samples = FLAC__stream_decoder_get_total_samples(decoder); const unsigned min_blocksize = decoder->private_->stream_info.data.stream_info.min_blocksize; const unsigned max_blocksize = decoder->private_->stream_info.data.stream_info.max_blocksize; const unsigned max_framesize = decoder->private_->stream_info.data.stream_info.max_framesize; const unsigned min_framesize = decoder->private_->stream_info.data.stream_info.min_framesize; /* take these from the current frame in case they've changed mid-stream */ unsigned channels = FLAC__stream_decoder_get_channels(decoder); unsigned bps = FLAC__stream_decoder_get_bits_per_sample(decoder); const FLAC__StreamMetadata_SeekTable *seek_table = decoder->private_->has_seek_table? &decoder->private_->seek_table.data.seek_table : 0; /* use values from stream info if we didn't decode a frame */ if(channels == 0) channels = decoder->private_->stream_info.data.stream_info.channels; if(bps == 0) bps = decoder->private_->stream_info.data.stream_info.bits_per_sample; /* we are just guessing here */ if(max_framesize > 0) approx_bytes_per_frame = (max_framesize + min_framesize) / 2 + 1; /* * Check if it's a known fixed-blocksize stream. Note that though * the spec doesn't allow zeroes in the STREAMINFO block, we may * never get a STREAMINFO block when decoding so the value of * min_blocksize might be zero. */ else if(min_blocksize == max_blocksize && min_blocksize > 0) { /* note there are no () around 'bps/8' to keep precision up since it's an integer calulation */ approx_bytes_per_frame = min_blocksize * channels * bps/8 + 64; } else approx_bytes_per_frame = 4096 * channels * bps/8 + 64; /* * First, we set an upper and lower bound on where in the * stream we will search. For now we assume the worst case * scenario, which is our best guess at the beginning of * the first frame and end of the stream. */ lower_bound = first_frame_offset; lower_bound_sample = 0; upper_bound = stream_length; upper_bound_sample = total_samples > 0 ? total_samples : target_sample /*estimate it*/; /* * Now we refine the bounds if we have a seektable with * suitable points. Note that according to the spec they * must be ordered by ascending sample number. * * Note: to protect against invalid seek tables we will ignore points * that have frame_samples==0 or sample_number>=total_samples */ if(seek_table) { FLAC__uint64 new_lower_bound = lower_bound; FLAC__uint64 new_upper_bound = upper_bound; FLAC__uint64 new_lower_bound_sample = lower_bound_sample; FLAC__uint64 new_upper_bound_sample = upper_bound_sample; /* find the closest seek point <= target_sample, if it exists */ for(i = (int)seek_table->num_points - 1; i >= 0; i--) { if( seek_table->points[i].sample_number != FLAC__STREAM_METADATA_SEEKPOINT_PLACEHOLDER && seek_table->points[i].frame_samples > 0 && /* defense against bad seekpoints */ (total_samples <= 0 || seek_table->points[i].sample_number < total_samples) && /* defense against bad seekpoints */ seek_table->points[i].sample_number <= target_sample ) break; } if(i >= 0) { /* i.e. we found a suitable seek point... */ new_lower_bound = first_frame_offset + seek_table->points[i].stream_offset; new_lower_bound_sample = seek_table->points[i].sample_number; } /* find the closest seek point > target_sample, if it exists */ for(i = 0; i < (int)seek_table->num_points; i++) { if( seek_table->points[i].sample_number != FLAC__STREAM_METADATA_SEEKPOINT_PLACEHOLDER && seek_table->points[i].frame_samples > 0 && /* defense against bad seekpoints */ (total_samples <= 0 || seek_table->points[i].sample_number < total_samples) && /* defense against bad seekpoints */ seek_table->points[i].sample_number > target_sample ) break; } if(i < (int)seek_table->num_points) { /* i.e. we found a suitable seek point... */ new_upper_bound = first_frame_offset + seek_table->points[i].stream_offset; new_upper_bound_sample = seek_table->points[i].sample_number; } /* final protection against unsorted seek tables; keep original values if bogus */ if(new_upper_bound >= new_lower_bound) { lower_bound = new_lower_bound; upper_bound = new_upper_bound; lower_bound_sample = new_lower_bound_sample; upper_bound_sample = new_upper_bound_sample; } } FLAC__ASSERT(upper_bound_sample >= lower_bound_sample); /* there are 2 insidious ways that the following equality occurs, which * we need to fix: * 1) total_samples is 0 (unknown) and target_sample is 0 * 2) total_samples is 0 (unknown) and target_sample happens to be * exactly equal to the last seek point in the seek table; this * means there is no seek point above it, and upper_bound_samples * remains equal to the estimate (of target_samples) we made above * in either case it does not hurt to move upper_bound_sample up by 1 */ if(upper_bound_sample == lower_bound_sample) upper_bound_sample++; decoder->private_->target_sample = target_sample; while(1) { /* check if the bounds are still ok */ if (lower_bound_sample >= upper_bound_sample || lower_bound > upper_bound) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } #ifndef FLAC__INTEGER_ONLY_LIBRARY #if defined _MSC_VER || defined __MINGW32__ /* with VC++ you have to spoon feed it the casting */ pos = (FLAC__int64)lower_bound + (FLAC__int64)((FLAC__double)(FLAC__int64)(target_sample - lower_bound_sample) / (FLAC__double)(FLAC__int64)(upper_bound_sample - lower_bound_sample) * (FLAC__double)(FLAC__int64)(upper_bound - lower_bound)) - approx_bytes_per_frame; #else pos = (FLAC__int64)lower_bound + (FLAC__int64)((FLAC__double)(target_sample - lower_bound_sample) / (FLAC__double)(upper_bound_sample - lower_bound_sample) * (FLAC__double)(upper_bound - lower_bound)) - approx_bytes_per_frame; #endif #else /* a little less accurate: */ if(upper_bound - lower_bound < 0xffffffff) pos = (FLAC__int64)lower_bound + (FLAC__int64)(((target_sample - lower_bound_sample) * (upper_bound - lower_bound)) / (upper_bound_sample - lower_bound_sample)) - approx_bytes_per_frame; else /* @@@ WATCHOUT, ~2TB limit */ pos = (FLAC__int64)lower_bound + (FLAC__int64)((((target_sample - lower_bound_sample)>>8) * ((upper_bound - lower_bound)>>8)) / ((upper_bound_sample - lower_bound_sample)>>16)) - approx_bytes_per_frame; #endif if(pos >= (FLAC__int64)upper_bound) pos = (FLAC__int64)upper_bound - 1; if(pos < (FLAC__int64)lower_bound) pos = (FLAC__int64)lower_bound; if(decoder->private_->seek_callback(decoder, (FLAC__uint64)pos, decoder->private_->client_data) != FLAC__STREAM_DECODER_SEEK_STATUS_OK) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } if(!FLAC__stream_decoder_flush(decoder)) { /* above call sets the state for us */ return false; } /* Now we need to get a frame. First we need to reset our * unparseable_frame_count; if we get too many unparseable * frames in a row, the read callback will return * FLAC__STREAM_DECODER_READ_STATUS_ABORT, causing * FLAC__stream_decoder_process_single() to return false. */ decoder->private_->unparseable_frame_count = 0; if(!FLAC__stream_decoder_process_single(decoder)) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } /* our write callback will change the state when it gets to the target frame */ /* actually, we could have got_a_frame if our decoder is at FLAC__STREAM_DECODER_END_OF_STREAM so we need to check for that also */ #if 0 /*@@@@@@ used to be the following; not clear if the check for end of stream is needed anymore */ if(decoder->protected_->state != FLAC__SEEKABLE_STREAM_DECODER_SEEKING && decoder->protected_->state != FLAC__STREAM_DECODER_END_OF_STREAM) break; #endif if(!decoder->private_->is_seeking) break; FLAC__ASSERT(decoder->private_->last_frame.header.number_type == FLAC__FRAME_NUMBER_TYPE_SAMPLE_NUMBER); this_frame_sample = decoder->private_->last_frame.header.number.sample_number; if (0 == decoder->private_->samples_decoded || (this_frame_sample + decoder->private_->last_frame.header.blocksize >= upper_bound_sample && !first_seek)) { if (pos == (FLAC__int64)lower_bound) { /* can't move back any more than the first frame, something is fatally wrong */ decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } /* our last move backwards wasn't big enough, try again */ approx_bytes_per_frame = approx_bytes_per_frame? approx_bytes_per_frame * 2 : 16; continue; } /* allow one seek over upper bound, so we can get a correct upper_bound_sample for streams with unknown total_samples */ first_seek = false; /* make sure we are not seeking in corrupted stream */ if (this_frame_sample < lower_bound_sample) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } /* we need to narrow the search */ if(target_sample < this_frame_sample) { upper_bound_sample = this_frame_sample + decoder->private_->last_frame.header.blocksize; /*@@@@@@ what will decode position be if at end of stream? */ if(!FLAC__stream_decoder_get_decode_position(decoder, &upper_bound)) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } approx_bytes_per_frame = (unsigned)(2 * (upper_bound - pos) / 3 + 16); } else { /* target_sample >= this_frame_sample + this frame's blocksize */ lower_bound_sample = this_frame_sample + decoder->private_->last_frame.header.blocksize; if(!FLAC__stream_decoder_get_decode_position(decoder, &lower_bound)) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } approx_bytes_per_frame = (unsigned)(2 * (lower_bound - pos) / 3 + 16); } } return true; } #if FLAC__HAS_OGG FLAC__bool seek_to_absolute_sample_ogg_(FLAC__StreamDecoder *decoder, FLAC__uint64 stream_length, FLAC__uint64 target_sample) { FLAC__uint64 left_pos = 0, right_pos = stream_length; FLAC__uint64 left_sample = 0, right_sample = FLAC__stream_decoder_get_total_samples(decoder); FLAC__uint64 this_frame_sample = (FLAC__uint64)0 - 1; FLAC__uint64 pos = 0; /* only initialized to avoid compiler warning */ FLAC__bool did_a_seek; unsigned iteration = 0; /* In the first iterations, we will calculate the target byte position * by the distance from the target sample to left_sample and * right_sample (let's call it "proportional search"). After that, we * will switch to binary search. */ unsigned BINARY_SEARCH_AFTER_ITERATION = 2; /* We will switch to a linear search once our current sample is less * than this number of samples ahead of the target sample */ static const FLAC__uint64 LINEAR_SEARCH_WITHIN_SAMPLES = FLAC__MAX_BLOCK_SIZE * 2; /* If the total number of samples is unknown, use a large value, and * force binary search immediately. */ if(right_sample == 0) { right_sample = (FLAC__uint64)(-1); BINARY_SEARCH_AFTER_ITERATION = 0; } decoder->private_->target_sample = target_sample; for( ; ; iteration++) { if (iteration == 0 || this_frame_sample > target_sample || target_sample - this_frame_sample > LINEAR_SEARCH_WITHIN_SAMPLES) { if (iteration >= BINARY_SEARCH_AFTER_ITERATION) { pos = (right_pos + left_pos) / 2; } else { #ifndef FLAC__INTEGER_ONLY_LIBRARY #if defined _MSC_VER || defined __MINGW32__ /* with MSVC you have to spoon feed it the casting */ pos = (FLAC__uint64)((FLAC__double)(FLAC__int64)(target_sample - left_sample) / (FLAC__double)(FLAC__int64)(right_sample - left_sample) * (FLAC__double)(FLAC__int64)(right_pos - left_pos)); #else pos = (FLAC__uint64)((FLAC__double)(target_sample - left_sample) / (FLAC__double)(right_sample - left_sample) * (FLAC__double)(right_pos - left_pos)); #endif #else /* a little less accurate: */ if ((target_sample-left_sample <= 0xffffffff) && (right_pos-left_pos <= 0xffffffff)) pos = (FLAC__int64)(((target_sample-left_sample) * (right_pos-left_pos)) / (right_sample-left_sample)); else /* @@@ WATCHOUT, ~2TB limit */ pos = (FLAC__int64)((((target_sample-left_sample)>>8) * ((right_pos-left_pos)>>8)) / ((right_sample-left_sample)>>16)); #endif /* @@@ TODO: might want to limit pos to some distance * before EOF, to make sure we land before the last frame, * thereby getting a this_frame_sample and so having a better * estimate. */ } /* physical seek */ if(decoder->private_->seek_callback((FLAC__StreamDecoder*)decoder, (FLAC__uint64)pos, decoder->private_->client_data) != FLAC__STREAM_DECODER_SEEK_STATUS_OK) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } if(!FLAC__stream_decoder_flush(decoder)) { /* above call sets the state for us */ return false; } did_a_seek = true; } else did_a_seek = false; decoder->private_->got_a_frame = false; if(!FLAC__stream_decoder_process_single(decoder)) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } if(!decoder->private_->got_a_frame) { if(did_a_seek) { /* this can happen if we seek to a point after the last frame; we drop * to binary search right away in this case to avoid any wasted * iterations of proportional search. */ right_pos = pos; BINARY_SEARCH_AFTER_ITERATION = 0; } else { /* this can probably only happen if total_samples is unknown and the * target_sample is past the end of the stream */ decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } } /* our write callback will change the state when it gets to the target frame */ else if(!decoder->private_->is_seeking) { break; } else { this_frame_sample = decoder->private_->last_frame.header.number.sample_number; FLAC__ASSERT(decoder->private_->last_frame.header.number_type == FLAC__FRAME_NUMBER_TYPE_SAMPLE_NUMBER); if (did_a_seek) { if (this_frame_sample <= target_sample) { /* The 'equal' case should not happen, since * FLAC__stream_decoder_process_single() * should recognize that it has hit the * target sample and we would exit through * the 'break' above. */ FLAC__ASSERT(this_frame_sample != target_sample); left_sample = this_frame_sample; /* sanity check to avoid infinite loop */ if (left_pos == pos) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } left_pos = pos; } else if(this_frame_sample > target_sample) { right_sample = this_frame_sample; /* sanity check to avoid infinite loop */ if (right_pos == pos) { decoder->protected_->state = FLAC__STREAM_DECODER_SEEK_ERROR; return false; } right_pos = pos; } } } } return true; } #endif FLAC__StreamDecoderReadStatus file_read_callback_(const FLAC__StreamDecoder *decoder, FLAC__byte buffer[], size_t *bytes, void *client_data) { (void)client_data; if(*bytes > 0) { *bytes = fread(buffer, sizeof(FLAC__byte), *bytes, decoder->private_->file); if(ferror(decoder->private_->file)) return FLAC__STREAM_DECODER_READ_STATUS_ABORT; else if(*bytes == 0) return FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM; else return FLAC__STREAM_DECODER_READ_STATUS_CONTINUE; } else return FLAC__STREAM_DECODER_READ_STATUS_ABORT; /* abort to avoid a deadlock */ } FLAC__StreamDecoderSeekStatus file_seek_callback_(const FLAC__StreamDecoder *decoder, FLAC__uint64 absolute_byte_offset, void *client_data) { (void)client_data; if(decoder->private_->file == stdin) return FLAC__STREAM_DECODER_SEEK_STATUS_UNSUPPORTED; else if(fseeko(decoder->private_->file, (off_t)absolute_byte_offset, SEEK_SET) < 0) return FLAC__STREAM_DECODER_SEEK_STATUS_ERROR; else return FLAC__STREAM_DECODER_SEEK_STATUS_OK; } FLAC__StreamDecoderTellStatus file_tell_callback_(const FLAC__StreamDecoder *decoder, FLAC__uint64 *absolute_byte_offset, void *client_data) { off_t pos; (void)client_data; if(decoder->private_->file == stdin) return FLAC__STREAM_DECODER_TELL_STATUS_UNSUPPORTED; else if((pos = ftello(decoder->private_->file)) < 0) return FLAC__STREAM_DECODER_TELL_STATUS_ERROR; else { *absolute_byte_offset = (FLAC__uint64)pos; return FLAC__STREAM_DECODER_TELL_STATUS_OK; } } FLAC__StreamDecoderLengthStatus file_length_callback_(const FLAC__StreamDecoder *decoder, FLAC__uint64 *stream_length, void *client_data) { struct stat filestats; (void)client_data; if(decoder->private_->file == stdin) return FLAC__STREAM_DECODER_LENGTH_STATUS_UNSUPPORTED; else if(fstat(fileno(decoder->private_->file), &filestats) != 0) return FLAC__STREAM_DECODER_LENGTH_STATUS_ERROR; else { *stream_length = (FLAC__uint64)filestats.st_size; return FLAC__STREAM_DECODER_LENGTH_STATUS_OK; } } FLAC__bool file_eof_callback_(const FLAC__StreamDecoder *decoder, void *client_data) { (void)client_data; return feof(decoder->private_->file)? true : false; } sources_5316/external/flac/flac_fixed.c0000644000176700017670000004164210720610334016705 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include #include #include "flac_private_bitmath.h" #include "flac_private_fixed.h" #include "flac_FLAC_assert.h" #ifndef M_LN2 /* math.h in VC++ doesn't seem to have this (how Microsoft is that?) */ #define M_LN2 0.69314718055994530942 #endif #ifdef min #undef min #endif #define min(x,y) ((x) < (y)? (x) : (y)) #ifdef local_abs #undef local_abs #endif #define local_abs(x) ((unsigned)((x)<0? -(x) : (x))) #ifdef FLAC__INTEGER_ONLY_LIBRARY /* rbps stands for residual bits per sample * * (ln(2) * err) * rbps = log (-----------) * 2 ( n ) */ static FLAC__fixedpoint local__compute_rbps_integerized(FLAC__uint32 err, FLAC__uint32 n) { FLAC__uint32 rbps; unsigned bits; /* the number of bits required to represent a number */ int fracbits; /* the number of bits of rbps that comprise the fractional part */ FLAC__ASSERT(sizeof(rbps) == sizeof(FLAC__fixedpoint)); FLAC__ASSERT(err > 0); FLAC__ASSERT(n > 0); FLAC__ASSERT(n <= FLAC__MAX_BLOCK_SIZE); if(err <= n) return 0; /* * The above two things tell us 1) n fits in 16 bits; 2) err/n > 1. * These allow us later to know we won't lose too much precision in the * fixed-point division (err< 0); bits = FLAC__bitmath_ilog2(err)+1; if(bits > 16) { err >>= (bits-16); fracbits -= (bits-16); } rbps = (FLAC__uint32)err; /* Multiply by fixed-point version of ln(2), with 16 fractional bits */ rbps *= FLAC__FP_LN2; fracbits += 16; FLAC__ASSERT(fracbits >= 0); /* FLAC__fixedpoint_log2 requires fracbits%4 to be 0 */ { const int f = fracbits & 3; if(f) { rbps >>= f; fracbits -= f; } } rbps = FLAC__fixedpoint_log2(rbps, fracbits, (unsigned)(-1)); if(rbps == 0) return 0; /* * The return value must have 16 fractional bits. Since the whole part * of the base-2 log of a 32 bit number must fit in 5 bits, and fracbits * must be >= -3, these assertion allows us to be able to shift rbps * left if necessary to get 16 fracbits without losing any bits of the * whole part of rbps. * * There is a slight chance due to accumulated error that the whole part * will require 6 bits, so we use 6 in the assertion. Really though as * long as it fits in 13 bits (32 - (16 - (-3))) we are fine. */ FLAC__ASSERT((int)FLAC__bitmath_ilog2(rbps)+1 <= fracbits + 6); FLAC__ASSERT(fracbits >= -3); /* now shift the decimal point into place */ if(fracbits < 16) return rbps << (16-fracbits); else if(fracbits > 16) return rbps >> (fracbits-16); else return rbps; } static FLAC__fixedpoint local__compute_rbps_wide_integerized(FLAC__uint64 err, FLAC__uint32 n) { FLAC__uint32 rbps; unsigned bits; /* the number of bits required to represent a number */ int fracbits; /* the number of bits of rbps that comprise the fractional part */ FLAC__ASSERT(sizeof(rbps) == sizeof(FLAC__fixedpoint)); FLAC__ASSERT(err > 0); FLAC__ASSERT(n > 0); FLAC__ASSERT(n <= FLAC__MAX_BLOCK_SIZE); if(err <= n) return 0; /* * The above two things tell us 1) n fits in 16 bits; 2) err/n > 1. * These allow us later to know we won't lose too much precision in the * fixed-point division (err< 0); bits = FLAC__bitmath_ilog2_wide(err)+1; if(bits > 16) { err >>= (bits-16); fracbits -= (bits-16); } rbps = (FLAC__uint32)err; /* Multiply by fixed-point version of ln(2), with 16 fractional bits */ rbps *= FLAC__FP_LN2; fracbits += 16; FLAC__ASSERT(fracbits >= 0); /* FLAC__fixedpoint_log2 requires fracbits%4 to be 0 */ { const int f = fracbits & 3; if(f) { rbps >>= f; fracbits -= f; } } rbps = FLAC__fixedpoint_log2(rbps, fracbits, (unsigned)(-1)); if(rbps == 0) return 0; /* * The return value must have 16 fractional bits. Since the whole part * of the base-2 log of a 32 bit number must fit in 5 bits, and fracbits * must be >= -3, these assertion allows us to be able to shift rbps * left if necessary to get 16 fracbits without losing any bits of the * whole part of rbps. * * There is a slight chance due to accumulated error that the whole part * will require 6 bits, so we use 6 in the assertion. Really though as * long as it fits in 13 bits (32 - (16 - (-3))) we are fine. */ FLAC__ASSERT((int)FLAC__bitmath_ilog2(rbps)+1 <= fracbits + 6); FLAC__ASSERT(fracbits >= -3); /* now shift the decimal point into place */ if(fracbits < 16) return rbps << (16-fracbits); else if(fracbits > 16) return rbps >> (fracbits-16); else return rbps; } #endif #ifndef FLAC__INTEGER_ONLY_LIBRARY unsigned FLAC__fixed_compute_best_predictor(const FLAC__int32 data[], unsigned data_len, FLAC__float residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]) #else unsigned FLAC__fixed_compute_best_predictor(const FLAC__int32 data[], unsigned data_len, FLAC__fixedpoint residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]) #endif { FLAC__int32 last_error_0 = data[-1]; FLAC__int32 last_error_1 = data[-1] - data[-2]; FLAC__int32 last_error_2 = last_error_1 - (data[-2] - data[-3]); FLAC__int32 last_error_3 = last_error_2 - (data[-2] - 2*data[-3] + data[-4]); FLAC__int32 error, save; FLAC__uint32 total_error_0 = 0, total_error_1 = 0, total_error_2 = 0, total_error_3 = 0, total_error_4 = 0; unsigned i, order; for(i = 0; i < data_len; i++) { error = data[i] ; total_error_0 += local_abs(error); save = error; error -= last_error_0; total_error_1 += local_abs(error); last_error_0 = save; save = error; error -= last_error_1; total_error_2 += local_abs(error); last_error_1 = save; save = error; error -= last_error_2; total_error_3 += local_abs(error); last_error_2 = save; save = error; error -= last_error_3; total_error_4 += local_abs(error); last_error_3 = save; } if(total_error_0 < min(min(min(total_error_1, total_error_2), total_error_3), total_error_4)) order = 0; else if(total_error_1 < min(min(total_error_2, total_error_3), total_error_4)) order = 1; else if(total_error_2 < min(total_error_3, total_error_4)) order = 2; else if(total_error_3 < total_error_4) order = 3; else order = 4; /* Estimate the expected number of bits per residual signal sample. */ /* 'total_error*' is linearly related to the variance of the residual */ /* signal, so we use it directly to compute E(|x|) */ FLAC__ASSERT(data_len > 0 || total_error_0 == 0); FLAC__ASSERT(data_len > 0 || total_error_1 == 0); FLAC__ASSERT(data_len > 0 || total_error_2 == 0); FLAC__ASSERT(data_len > 0 || total_error_3 == 0); FLAC__ASSERT(data_len > 0 || total_error_4 == 0); #ifndef FLAC__INTEGER_ONLY_LIBRARY residual_bits_per_sample[0] = (FLAC__float)((total_error_0 > 0) ? log(M_LN2 * (FLAC__double)total_error_0 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[1] = (FLAC__float)((total_error_1 > 0) ? log(M_LN2 * (FLAC__double)total_error_1 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[2] = (FLAC__float)((total_error_2 > 0) ? log(M_LN2 * (FLAC__double)total_error_2 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[3] = (FLAC__float)((total_error_3 > 0) ? log(M_LN2 * (FLAC__double)total_error_3 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[4] = (FLAC__float)((total_error_4 > 0) ? log(M_LN2 * (FLAC__double)total_error_4 / (FLAC__double)data_len) / M_LN2 : 0.0); #else residual_bits_per_sample[0] = (total_error_0 > 0) ? local__compute_rbps_integerized(total_error_0, data_len) : 0; residual_bits_per_sample[1] = (total_error_1 > 0) ? local__compute_rbps_integerized(total_error_1, data_len) : 0; residual_bits_per_sample[2] = (total_error_2 > 0) ? local__compute_rbps_integerized(total_error_2, data_len) : 0; residual_bits_per_sample[3] = (total_error_3 > 0) ? local__compute_rbps_integerized(total_error_3, data_len) : 0; residual_bits_per_sample[4] = (total_error_4 > 0) ? local__compute_rbps_integerized(total_error_4, data_len) : 0; #endif return order; } #ifndef FLAC__INTEGER_ONLY_LIBRARY unsigned FLAC__fixed_compute_best_predictor_wide(const FLAC__int32 data[], unsigned data_len, FLAC__float residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]) #else unsigned FLAC__fixed_compute_best_predictor_wide(const FLAC__int32 data[], unsigned data_len, FLAC__fixedpoint residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]) #endif { FLAC__int32 last_error_0 = data[-1]; FLAC__int32 last_error_1 = data[-1] - data[-2]; FLAC__int32 last_error_2 = last_error_1 - (data[-2] - data[-3]); FLAC__int32 last_error_3 = last_error_2 - (data[-2] - 2*data[-3] + data[-4]); FLAC__int32 error, save; /* total_error_* are 64-bits to avoid overflow when encoding * erratic signals when the bits-per-sample and blocksize are * large. */ FLAC__uint64 total_error_0 = 0, total_error_1 = 0, total_error_2 = 0, total_error_3 = 0, total_error_4 = 0; unsigned i, order; for(i = 0; i < data_len; i++) { error = data[i] ; total_error_0 += local_abs(error); save = error; error -= last_error_0; total_error_1 += local_abs(error); last_error_0 = save; save = error; error -= last_error_1; total_error_2 += local_abs(error); last_error_1 = save; save = error; error -= last_error_2; total_error_3 += local_abs(error); last_error_2 = save; save = error; error -= last_error_3; total_error_4 += local_abs(error); last_error_3 = save; } if(total_error_0 < min(min(min(total_error_1, total_error_2), total_error_3), total_error_4)) order = 0; else if(total_error_1 < min(min(total_error_2, total_error_3), total_error_4)) order = 1; else if(total_error_2 < min(total_error_3, total_error_4)) order = 2; else if(total_error_3 < total_error_4) order = 3; else order = 4; /* Estimate the expected number of bits per residual signal sample. */ /* 'total_error*' is linearly related to the variance of the residual */ /* signal, so we use it directly to compute E(|x|) */ FLAC__ASSERT(data_len > 0 || total_error_0 == 0); FLAC__ASSERT(data_len > 0 || total_error_1 == 0); FLAC__ASSERT(data_len > 0 || total_error_2 == 0); FLAC__ASSERT(data_len > 0 || total_error_3 == 0); FLAC__ASSERT(data_len > 0 || total_error_4 == 0); #ifndef FLAC__INTEGER_ONLY_LIBRARY #if defined _MSC_VER || defined __MINGW32__ /* with MSVC you have to spoon feed it the casting */ residual_bits_per_sample[0] = (FLAC__float)((total_error_0 > 0) ? log(M_LN2 * (FLAC__double)(FLAC__int64)total_error_0 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[1] = (FLAC__float)((total_error_1 > 0) ? log(M_LN2 * (FLAC__double)(FLAC__int64)total_error_1 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[2] = (FLAC__float)((total_error_2 > 0) ? log(M_LN2 * (FLAC__double)(FLAC__int64)total_error_2 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[3] = (FLAC__float)((total_error_3 > 0) ? log(M_LN2 * (FLAC__double)(FLAC__int64)total_error_3 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[4] = (FLAC__float)((total_error_4 > 0) ? log(M_LN2 * (FLAC__double)(FLAC__int64)total_error_4 / (FLAC__double)data_len) / M_LN2 : 0.0); #else residual_bits_per_sample[0] = (FLAC__float)((total_error_0 > 0) ? log(M_LN2 * (FLAC__double)total_error_0 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[1] = (FLAC__float)((total_error_1 > 0) ? log(M_LN2 * (FLAC__double)total_error_1 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[2] = (FLAC__float)((total_error_2 > 0) ? log(M_LN2 * (FLAC__double)total_error_2 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[3] = (FLAC__float)((total_error_3 > 0) ? log(M_LN2 * (FLAC__double)total_error_3 / (FLAC__double)data_len) / M_LN2 : 0.0); residual_bits_per_sample[4] = (FLAC__float)((total_error_4 > 0) ? log(M_LN2 * (FLAC__double)total_error_4 / (FLAC__double)data_len) / M_LN2 : 0.0); #endif #else residual_bits_per_sample[0] = (total_error_0 > 0) ? local__compute_rbps_wide_integerized(total_error_0, data_len) : 0; residual_bits_per_sample[1] = (total_error_1 > 0) ? local__compute_rbps_wide_integerized(total_error_1, data_len) : 0; residual_bits_per_sample[2] = (total_error_2 > 0) ? local__compute_rbps_wide_integerized(total_error_2, data_len) : 0; residual_bits_per_sample[3] = (total_error_3 > 0) ? local__compute_rbps_wide_integerized(total_error_3, data_len) : 0; residual_bits_per_sample[4] = (total_error_4 > 0) ? local__compute_rbps_wide_integerized(total_error_4, data_len) : 0; #endif return order; } void FLAC__fixed_compute_residual(const FLAC__int32 data[], unsigned data_len, unsigned order, FLAC__int32 residual[]) { const int idata_len = (int)data_len; int i; switch(order) { case 0: FLAC__ASSERT(sizeof(residual[0]) == sizeof(data[0])); memcpy(residual, data, sizeof(residual[0])*data_len); break; case 1: for(i = 0; i < idata_len; i++) residual[i] = data[i] - data[i-1]; break; case 2: for(i = 0; i < idata_len; i++) #if 1 /* OPT: may be faster with some compilers on some systems */ residual[i] = data[i] - (data[i-1] << 1) + data[i-2]; #else residual[i] = data[i] - 2*data[i-1] + data[i-2]; #endif break; case 3: for(i = 0; i < idata_len; i++) #if 1 /* OPT: may be faster with some compilers on some systems */ residual[i] = data[i] - (((data[i-1]-data[i-2])<<1) + (data[i-1]-data[i-2])) - data[i-3]; #else residual[i] = data[i] - 3*data[i-1] + 3*data[i-2] - data[i-3]; #endif break; case 4: for(i = 0; i < idata_len; i++) #if 1 /* OPT: may be faster with some compilers on some systems */ residual[i] = data[i] - ((data[i-1]+data[i-3])<<2) + ((data[i-2]<<2) + (data[i-2]<<1)) + data[i-4]; #else residual[i] = data[i] - 4*data[i-1] + 6*data[i-2] - 4*data[i-3] + data[i-4]; #endif break; default: FLAC__ASSERT(0); } } void FLAC__fixed_restore_signal(const FLAC__int32 residual[], unsigned data_len, unsigned order, FLAC__int32 data[]) { int i, idata_len = (int)data_len; switch(order) { case 0: FLAC__ASSERT(sizeof(residual[0]) == sizeof(data[0])); memcpy(data, residual, sizeof(residual[0])*data_len); break; case 1: for(i = 0; i < idata_len; i++) data[i] = residual[i] + data[i-1]; break; case 2: for(i = 0; i < idata_len; i++) #if 1 /* OPT: may be faster with some compilers on some systems */ data[i] = residual[i] + (data[i-1]<<1) - data[i-2]; #else data[i] = residual[i] + 2*data[i-1] - data[i-2]; #endif break; case 3: for(i = 0; i < idata_len; i++) #if 1 /* OPT: may be faster with some compilers on some systems */ data[i] = residual[i] + (((data[i-1]-data[i-2])<<1) + (data[i-1]-data[i-2])) + data[i-3]; #else data[i] = residual[i] + 3*data[i-1] - 3*data[i-2] + data[i-3]; #endif break; case 4: for(i = 0; i < idata_len; i++) #if 1 /* OPT: may be faster with some compilers on some systems */ data[i] = residual[i] + ((data[i-1]+data[i-3])<<2) - ((data[i-2]<<2) + (data[i-2]<<1)) - data[i-4]; #else data[i] = residual[i] + 4*data[i-1] - 6*data[i-2] + 4*data[i-3] - data[i-4]; #endif break; default: FLAC__ASSERT(0); } } sources_5316/external/flac/flac_private_lpc.h0000644000176700017670000002513710720650413020126 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__LPC_H #define FLAC__PRIVATE__LPC_H #ifdef HAVE_CONFIG_H #include #endif #include "flac_private_autocpu.h" #include "flac_private_float.h" #include "flac_FLAC_format.h" #ifndef FLAC__INTEGER_ONLY_LIBRARY /* * FLAC__lpc_window_data() * -------------------------------------------------------------------- * Applies the given window to the data. * OPT: asm implementation * * IN in[0,data_len-1] * IN window[0,data_len-1] * OUT out[0,lag-1] * IN data_len */ void FLAC__lpc_window_data(const FLAC__int32 in[], const FLAC__real window[], FLAC__real out[], unsigned data_len); /* * FLAC__lpc_compute_autocorrelation() * -------------------------------------------------------------------- * Compute the autocorrelation for lags between 0 and lag-1. * Assumes data[] outside of [0,data_len-1] == 0. * Asserts that lag > 0. * * IN data[0,data_len-1] * IN data_len * IN 0 < lag <= data_len * OUT autoc[0,lag-1] */ void FLAC__lpc_compute_autocorrelation(const FLAC__real data[], unsigned data_len, unsigned lag, FLAC__real autoc[]); #ifndef FLAC__NO_ASM # ifdef FLAC__CPU_IA32 # ifdef FLAC__HAS_NASM void FLAC__lpc_compute_autocorrelation_asm_ia32(const FLAC__real data[], unsigned data_len, unsigned lag, FLAC__real autoc[]); void FLAC__lpc_compute_autocorrelation_asm_ia32_sse_lag_4(const FLAC__real data[], unsigned data_len, unsigned lag, FLAC__real autoc[]); void FLAC__lpc_compute_autocorrelation_asm_ia32_sse_lag_8(const FLAC__real data[], unsigned data_len, unsigned lag, FLAC__real autoc[]); void FLAC__lpc_compute_autocorrelation_asm_ia32_sse_lag_12(const FLAC__real data[], unsigned data_len, unsigned lag, FLAC__real autoc[]); void FLAC__lpc_compute_autocorrelation_asm_ia32_3dnow(const FLAC__real data[], unsigned data_len, unsigned lag, FLAC__real autoc[]); # endif # endif #endif /* * FLAC__lpc_compute_lp_coefficients() * -------------------------------------------------------------------- * Computes LP coefficients for orders 1..max_order. * Do not call if autoc[0] == 0.0. This means the signal is zero * and there is no point in calculating a predictor. * * IN autoc[0,max_order] autocorrelation values * IN 0 < max_order <= FLAC__MAX_LPC_ORDER max LP order to compute * OUT lp_coeff[0,max_order-1][0,max_order-1] LP coefficients for each order * *** IMPORTANT: * *** lp_coeff[0,max_order-1][max_order,FLAC__MAX_LPC_ORDER-1] are untouched * OUT error[0,max_order-1] error for each order (more * specifically, the variance of * the error signal times # of * samples in the signal) * * Example: if max_order is 9, the LP coefficients for order 9 will be * in lp_coeff[8][0,8], the LP coefficients for order 8 will be * in lp_coeff[7][0,7], etc. */ void FLAC__lpc_compute_lp_coefficients(const FLAC__real autoc[], unsigned *max_order, FLAC__real lp_coeff[][FLAC__MAX_LPC_ORDER], FLAC__double error[]); /* * FLAC__lpc_quantize_coefficients() * -------------------------------------------------------------------- * Quantizes the LP coefficients. NOTE: precision + bits_per_sample * must be less than 32 (sizeof(FLAC__int32)*8). * * IN lp_coeff[0,order-1] LP coefficients * IN order LP order * IN FLAC__MIN_QLP_COEFF_PRECISION < precision * desired precision (in bits, including sign * bit) of largest coefficient * OUT qlp_coeff[0,order-1] quantized coefficients * OUT shift # of bits to shift right to get approximated * LP coefficients. NOTE: could be negative. * RETURN 0 => quantization OK * 1 => coefficients require too much shifting for *shift to * fit in the LPC subframe header. 'shift' is unset. * 2 => coefficients are all zero, which is bad. 'shift' is * unset. */ int FLAC__lpc_quantize_coefficients(const FLAC__real lp_coeff[], unsigned order, unsigned precision, FLAC__int32 qlp_coeff[], int *shift); /* * FLAC__lpc_compute_residual_from_qlp_coefficients() * -------------------------------------------------------------------- * Compute the residual signal obtained from sutracting the predicted * signal from the original. * * IN data[-order,data_len-1] original signal (NOTE THE INDICES!) * IN data_len length of original signal * IN qlp_coeff[0,order-1] quantized LP coefficients * IN order > 0 LP order * IN lp_quantization quantization of LP coefficients in bits * OUT residual[0,data_len-1] residual signal */ void FLAC__lpc_compute_residual_from_qlp_coefficients(const FLAC__int32 *data, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 residual[]); void FLAC__lpc_compute_residual_from_qlp_coefficients_wide(const FLAC__int32 *data, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 residual[]); #ifndef FLAC__NO_ASM # ifdef FLAC__CPU_IA32 # ifdef FLAC__HAS_NASM void FLAC__lpc_compute_residual_from_qlp_coefficients_asm_ia32(const FLAC__int32 *data, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 residual[]); void FLAC__lpc_compute_residual_from_qlp_coefficients_asm_ia32_mmx(const FLAC__int32 *data, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 residual[]); # endif # endif #endif #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ /* * FLAC__lpc_restore_signal() * -------------------------------------------------------------------- * Restore the original signal by summing the residual and the * predictor. * * IN residual[0,data_len-1] residual signal * IN data_len length of original signal * IN qlp_coeff[0,order-1] quantized LP coefficients * IN order > 0 LP order * IN lp_quantization quantization of LP coefficients in bits * *** IMPORTANT: the caller must pass in the historical samples: * IN data[-order,-1] previously-reconstructed historical samples * OUT data[0,data_len-1] original signal */ void FLAC__lpc_restore_signal(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); void FLAC__lpc_restore_signal_wide(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); #ifndef FLAC__NO_ASM # ifdef FLAC__CPU_IA32 # ifdef FLAC__HAS_NASM void FLAC__lpc_restore_signal_asm_ia32(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); void FLAC__lpc_restore_signal_asm_ia32_mmx(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); # endif /* FLAC__HAS_NASM */ # elif defined FLAC__CPU_PPC void FLAC__lpc_restore_signal_asm_ppc_altivec_16(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); void FLAC__lpc_restore_signal_asm_ppc_altivec_16_order8(const FLAC__int32 residual[], unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 data[]); # endif/* FLAC__CPU_IA32 || FLAC__CPU_PPC */ #endif /* FLAC__NO_ASM */ #ifndef FLAC__INTEGER_ONLY_LIBRARY /* * FLAC__lpc_compute_expected_bits_per_residual_sample() * -------------------------------------------------------------------- * Compute the expected number of bits per residual signal sample * based on the LP error (which is related to the residual variance). * * IN lpc_error >= 0.0 error returned from calculating LP coefficients * IN total_samples > 0 # of samples in residual signal * RETURN expected bits per sample */ FLAC__double FLAC__lpc_compute_expected_bits_per_residual_sample(FLAC__double lpc_error, unsigned total_samples); FLAC__double FLAC__lpc_compute_expected_bits_per_residual_sample_with_error_scale(FLAC__double lpc_error, FLAC__double error_scale); /* * FLAC__lpc_compute_best_order() * -------------------------------------------------------------------- * Compute the best order from the array of signal errors returned * during coefficient computation. * * IN lpc_error[0,max_order-1] >= 0.0 error returned from calculating LP coefficients * IN max_order > 0 max LP order * IN total_samples > 0 # of samples in residual signal * IN overhead_bits_per_order # of bits overhead for each increased LP order * (includes warmup sample size and quantized LP coefficient) * RETURN [1,max_order] best order */ unsigned FLAC__lpc_compute_best_order(const FLAC__double lpc_error[], unsigned max_order, unsigned total_samples, unsigned overhead_bits_per_order); #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ #endif sources_5316/external/flac/flac_protected_all.h0000644000176700017670000000336110720607255020440 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PROTECTED__ALL_H #define FLAC__PROTECTED__ALL_H #include "flac_protected_stream_decoder.h" #include "flac_protected_stream_encoder.h" #endif sources_5316/external/flac/flac_bitmath.c0000644000176700017670000000645310720605602017241 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include "flac_private_bitmath.h" #include "flac_FLAC_assert.h" /* An example of what FLAC__bitmath_ilog2() computes: * * ilog2( 0) = assertion failure * ilog2( 1) = 0 * ilog2( 2) = 1 * ilog2( 3) = 1 * ilog2( 4) = 2 * ilog2( 5) = 2 * ilog2( 6) = 2 * ilog2( 7) = 2 * ilog2( 8) = 3 * ilog2( 9) = 3 * ilog2(10) = 3 * ilog2(11) = 3 * ilog2(12) = 3 * ilog2(13) = 3 * ilog2(14) = 3 * ilog2(15) = 3 * ilog2(16) = 4 * ilog2(17) = 4 * ilog2(18) = 4 */ unsigned FLAC__bitmath_ilog2(FLAC__uint32 v) { unsigned l = 0; FLAC__ASSERT(v > 0); while(v >>= 1) l++; return l; } unsigned FLAC__bitmath_ilog2_wide(FLAC__uint64 v) { unsigned l = 0; FLAC__ASSERT(v > 0); while(v >>= 1) l++; return l; } /* An example of what FLAC__bitmath_silog2() computes: * * silog2(-10) = 5 * silog2(- 9) = 5 * silog2(- 8) = 4 * silog2(- 7) = 4 * silog2(- 6) = 4 * silog2(- 5) = 4 * silog2(- 4) = 3 * silog2(- 3) = 3 * silog2(- 2) = 2 * silog2(- 1) = 2 * silog2( 0) = 0 * silog2( 1) = 2 * silog2( 2) = 3 * silog2( 3) = 3 * silog2( 4) = 4 * silog2( 5) = 4 * silog2( 6) = 4 * silog2( 7) = 4 * silog2( 8) = 5 * silog2( 9) = 5 * silog2( 10) = 5 */ unsigned FLAC__bitmath_silog2(int v) { while(1) { if(v == 0) { return 0; } else if(v > 0) { unsigned l = 0; while(v) { l++; v >>= 1; } return l+1; } else if(v == -1) { return 2; } else { v++; v = -v; } } } unsigned FLAC__bitmath_silog2_wide(FLAC__int64 v) { while(1) { if(v == 0) { return 0; } else if(v > 0) { unsigned l = 0; while(v) { l++; v >>= 1; } return l+1; } else if(v == -1) { return 2; } else { v++; v = -v; } } } sources_5316/external/flac/flac_stream_encoder.c0000644000176700017670000052135010720650533020604 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #if defined _WIN32 #include /* for _setmode() */ #include /* for _O_BINARY */ #endif #include #include #include /* for malloc() */ #include /* for memcpy() */ #include /* for off_t */ #if defined _WIN32 #define fseeko fseek #define ftello ftell #endif #include "flac_FLAC_assert.h" #include "flac_FLAC_stream_decoder.h" #include "flac_share_alloc.h" #include "flac_protected_stream_encoder.h" #include "flac_private_autocpu.h" #include "flac_private_bitwriter.h" #include "flac_private_bitmath.h" #include "flac_private_crc.h" #include "flac_private_cpu.h" #include "flac_private_fixed.h" #include "flac_private_format.h" #include "flac_private_lpc.h" #include "flac_private_md5.h" #include "flac_private_memory.h" #if FLAC__HAS_OGG #include "private/ogg_helper.h" #include "private/ogg_mapping.h" #endif #include "flac_private_stream_encoder_framing.h" #include "flac_private_window.h" #ifndef FLaC__INLINE #define FLaC__INLINE #endif #ifdef min #undef min #endif #define min(x,y) ((x)<(y)?(x):(y)) #ifdef max #undef max #endif #define max(x,y) ((x)>(y)?(x):(y)) /* Exact Rice codeword length calculation is off by default. The simple * (and fast) estimation (of how many bits a residual value will be * encoded with) in this encoder is very good, almost always yielding * compression within 0.1% of exact calculation. */ #undef EXACT_RICE_BITS_CALCULATION /* Rice parameter searching is off by default. The simple (and fast) * parameter estimation in this encoder is very good, almost always * yielding compression within 0.1% of the optimal parameters. */ #undef ENABLE_RICE_PARAMETER_SEARCH typedef struct { FLAC__int32 *data[FLAC__MAX_CHANNELS]; unsigned size; /* of each data[] in samples */ unsigned tail; } verify_input_fifo; typedef struct { const FLAC__byte *data; unsigned capacity; unsigned bytes; } verify_output; typedef enum { ENCODER_IN_MAGIC = 0, ENCODER_IN_METADATA = 1, ENCODER_IN_AUDIO = 2 } EncoderStateHint; static struct CompressionLevels { FLAC__bool do_mid_side_stereo; FLAC__bool loose_mid_side_stereo; unsigned max_lpc_order; unsigned qlp_coeff_precision; FLAC__bool do_qlp_coeff_prec_search; FLAC__bool do_escape_coding; FLAC__bool do_exhaustive_model_search; unsigned min_residual_partition_order; unsigned max_residual_partition_order; unsigned rice_parameter_search_dist; } compression_levels_[] = { { false, false, 0, 0, false, false, false, 0, 3, 0 }, { true , true , 0, 0, false, false, false, 0, 3, 0 }, { true , false, 0, 0, false, false, false, 0, 3, 0 }, { false, false, 6, 0, false, false, false, 0, 4, 0 }, { true , true , 8, 0, false, false, false, 0, 4, 0 }, { true , false, 8, 0, false, false, false, 0, 5, 0 }, { true , false, 8, 0, false, false, false, 0, 6, 0 }, { true , false, 8, 0, false, false, true , 0, 6, 0 }, { true , false, 12, 0, false, false, true , 0, 6, 0 } }; /*********************************************************************** * * Private class method prototypes * ***********************************************************************/ static void set_defaults_(FLAC__StreamEncoder *encoder); static void free_(FLAC__StreamEncoder *encoder); static FLAC__bool resize_buffers_(FLAC__StreamEncoder *encoder, unsigned new_blocksize); static FLAC__bool write_bitbuffer_(FLAC__StreamEncoder *encoder, unsigned samples, FLAC__bool is_last_block); static FLAC__StreamEncoderWriteStatus write_frame_(FLAC__StreamEncoder *encoder, const FLAC__byte buffer[], size_t bytes, unsigned samples, FLAC__bool is_last_block); static void update_metadata_(const FLAC__StreamEncoder *encoder); #if FLAC__HAS_OGG static void update_ogg_metadata_(FLAC__StreamEncoder *encoder); #endif static FLAC__bool process_frame_(FLAC__StreamEncoder *encoder, FLAC__bool is_fractional_block, FLAC__bool is_last_block); static FLAC__bool process_subframes_(FLAC__StreamEncoder *encoder, FLAC__bool is_fractional_block); static FLAC__bool process_subframe_( FLAC__StreamEncoder *encoder, unsigned min_partition_order, unsigned max_partition_order, const FLAC__FrameHeader *frame_header, unsigned subframe_bps, const FLAC__int32 integer_signal[], FLAC__Subframe *subframe[2], FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents[2], FLAC__int32 *residual[2], unsigned *best_subframe, unsigned *best_bits ); static FLAC__bool add_subframe_( FLAC__StreamEncoder *encoder, unsigned blocksize, unsigned subframe_bps, const FLAC__Subframe *subframe, FLAC__BitWriter *frame ); static unsigned evaluate_constant_subframe_( FLAC__StreamEncoder *encoder, const FLAC__int32 signal, unsigned blocksize, unsigned subframe_bps, FLAC__Subframe *subframe ); static unsigned evaluate_fixed_subframe_( FLAC__StreamEncoder *encoder, const FLAC__int32 signal[], FLAC__int32 residual[], FLAC__uint64 abs_residual_partition_sums[], unsigned raw_bits_per_partition[], unsigned blocksize, unsigned subframe_bps, unsigned order, unsigned rice_parameter, unsigned rice_parameter_limit, unsigned min_partition_order, unsigned max_partition_order, FLAC__bool do_escape_coding, unsigned rice_parameter_search_dist, FLAC__Subframe *subframe, FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents ); #ifndef FLAC__INTEGER_ONLY_LIBRARY static unsigned evaluate_lpc_subframe_( FLAC__StreamEncoder *encoder, const FLAC__int32 signal[], FLAC__int32 residual[], FLAC__uint64 abs_residual_partition_sums[], unsigned raw_bits_per_partition[], const FLAC__real lp_coeff[], unsigned blocksize, unsigned subframe_bps, unsigned order, unsigned qlp_coeff_precision, unsigned rice_parameter, unsigned rice_parameter_limit, unsigned min_partition_order, unsigned max_partition_order, FLAC__bool do_escape_coding, unsigned rice_parameter_search_dist, FLAC__Subframe *subframe, FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents ); #endif static unsigned evaluate_verbatim_subframe_( FLAC__StreamEncoder *encoder, const FLAC__int32 signal[], unsigned blocksize, unsigned subframe_bps, FLAC__Subframe *subframe ); static unsigned find_best_partition_order_( struct FLAC__StreamEncoderPrivate *private_, const FLAC__int32 residual[], FLAC__uint64 abs_residual_partition_sums[], unsigned raw_bits_per_partition[], unsigned residual_samples, unsigned predictor_order, unsigned rice_parameter, unsigned rice_parameter_limit, unsigned min_partition_order, unsigned max_partition_order, unsigned bps, FLAC__bool do_escape_coding, unsigned rice_parameter_search_dist, FLAC__EntropyCodingMethod *best_ecm ); static void precompute_partition_info_sums_( const FLAC__int32 residual[], FLAC__uint64 abs_residual_partition_sums[], unsigned residual_samples, unsigned predictor_order, unsigned min_partition_order, unsigned max_partition_order, unsigned bps ); static void precompute_partition_info_escapes_( const FLAC__int32 residual[], unsigned raw_bits_per_partition[], unsigned residual_samples, unsigned predictor_order, unsigned min_partition_order, unsigned max_partition_order ); static FLAC__bool set_partitioned_rice_( #ifdef EXACT_RICE_BITS_CALCULATION const FLAC__int32 residual[], #endif const FLAC__uint64 abs_residual_partition_sums[], const unsigned raw_bits_per_partition[], const unsigned residual_samples, const unsigned predictor_order, const unsigned suggested_rice_parameter, const unsigned rice_parameter_limit, const unsigned rice_parameter_search_dist, const unsigned partition_order, const FLAC__bool search_for_escapes, FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents, unsigned *bits ); static unsigned get_wasted_bits_(FLAC__int32 signal[], unsigned samples); /* verify-related routines: */ static void append_to_verify_fifo_( verify_input_fifo *fifo, const FLAC__int32 * const input[], unsigned input_offset, unsigned channels, unsigned wide_samples ); static void append_to_verify_fifo_interleaved_( verify_input_fifo *fifo, const FLAC__int32 input[], unsigned input_offset, unsigned channels, unsigned wide_samples ); static FLAC__StreamDecoderReadStatus verify_read_callback_(const FLAC__StreamDecoder *decoder, FLAC__byte buffer[], size_t *bytes, void *client_data); static FLAC__StreamDecoderWriteStatus verify_write_callback_(const FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer[], void *client_data); static void verify_metadata_callback_(const FLAC__StreamDecoder *decoder, const FLAC__StreamMetadata *metadata, void *client_data); static void verify_error_callback_(const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data); static FLAC__StreamEncoderReadStatus file_read_callback_(const FLAC__StreamEncoder *encoder, FLAC__byte buffer[], size_t *bytes, void *client_data); static FLAC__StreamEncoderSeekStatus file_seek_callback_(const FLAC__StreamEncoder *encoder, FLAC__uint64 absolute_byte_offset, void *client_data); static FLAC__StreamEncoderTellStatus file_tell_callback_(const FLAC__StreamEncoder *encoder, FLAC__uint64 *absolute_byte_offset, void *client_data); static FLAC__StreamEncoderWriteStatus file_write_callback_(const FLAC__StreamEncoder *encoder, const FLAC__byte buffer[], size_t bytes, unsigned samples, unsigned current_frame, void *client_data); static FILE *get_binary_stdout_(void); /*********************************************************************** * * Private class data * ***********************************************************************/ typedef struct FLAC__StreamEncoderPrivate { unsigned input_capacity; /* current size (in samples) of the signal and residual buffers */ FLAC__int32 *integer_signal[FLAC__MAX_CHANNELS]; /* the integer version of the input signal */ FLAC__int32 *integer_signal_mid_side[2]; /* the integer version of the mid-side input signal (stereo only) */ #ifndef FLAC__INTEGER_ONLY_LIBRARY FLAC__real *real_signal[FLAC__MAX_CHANNELS]; /* (@@@ currently unused) the floating-point version of the input signal */ FLAC__real *real_signal_mid_side[2]; /* (@@@ currently unused) the floating-point version of the mid-side input signal (stereo only) */ FLAC__real *window[FLAC__MAX_APODIZATION_FUNCTIONS]; /* the pre-computed floating-point window for each apodization function */ FLAC__real *windowed_signal; /* the integer_signal[] * current window[] */ #endif unsigned subframe_bps[FLAC__MAX_CHANNELS]; /* the effective bits per sample of the input signal (stream bps - wasted bits) */ unsigned subframe_bps_mid_side[2]; /* the effective bits per sample of the mid-side input signal (stream bps - wasted bits + 0/1) */ FLAC__int32 *residual_workspace[FLAC__MAX_CHANNELS][2]; /* each channel has a candidate and best workspace where the subframe residual signals will be stored */ FLAC__int32 *residual_workspace_mid_side[2][2]; FLAC__Subframe subframe_workspace[FLAC__MAX_CHANNELS][2]; FLAC__Subframe subframe_workspace_mid_side[2][2]; FLAC__Subframe *subframe_workspace_ptr[FLAC__MAX_CHANNELS][2]; FLAC__Subframe *subframe_workspace_ptr_mid_side[2][2]; FLAC__EntropyCodingMethod_PartitionedRiceContents partitioned_rice_contents_workspace[FLAC__MAX_CHANNELS][2]; FLAC__EntropyCodingMethod_PartitionedRiceContents partitioned_rice_contents_workspace_mid_side[FLAC__MAX_CHANNELS][2]; FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents_workspace_ptr[FLAC__MAX_CHANNELS][2]; FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents_workspace_ptr_mid_side[FLAC__MAX_CHANNELS][2]; unsigned best_subframe[FLAC__MAX_CHANNELS]; /* index (0 or 1) into 2nd dimension of the above workspaces */ unsigned best_subframe_mid_side[2]; unsigned best_subframe_bits[FLAC__MAX_CHANNELS]; /* size in bits of the best subframe for each channel */ unsigned best_subframe_bits_mid_side[2]; FLAC__uint64 *abs_residual_partition_sums; /* workspace where the sum of abs(candidate residual) for each partition is stored */ unsigned *raw_bits_per_partition; /* workspace where the sum of silog2(candidate residual) for each partition is stored */ FLAC__BitWriter *frame; /* the current frame being worked on */ unsigned loose_mid_side_stereo_frames; /* rounded number of frames the encoder will use before trying both independent and mid/side frames again */ unsigned loose_mid_side_stereo_frame_count; /* number of frames using the current channel assignment */ FLAC__ChannelAssignment last_channel_assignment; FLAC__StreamMetadata streaminfo; /* scratchpad for STREAMINFO as it is built */ FLAC__StreamMetadata_SeekTable *seek_table; /* pointer into encoder->protected_->metadata_ where the seek table is */ unsigned current_sample_number; unsigned current_frame_number; FLAC__MD5Context md5context; FLAC__CPUInfo cpuinfo; #ifndef FLAC__INTEGER_ONLY_LIBRARY unsigned (*local_fixed_compute_best_predictor)(const FLAC__int32 data[], unsigned data_len, FLAC__float residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]); #else unsigned (*local_fixed_compute_best_predictor)(const FLAC__int32 data[], unsigned data_len, FLAC__fixedpoint residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]); #endif #ifndef FLAC__INTEGER_ONLY_LIBRARY void (*local_lpc_compute_autocorrelation)(const FLAC__real data[], unsigned data_len, unsigned lag, FLAC__real autoc[]); void (*local_lpc_compute_residual_from_qlp_coefficients)(const FLAC__int32 *data, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 residual[]); void (*local_lpc_compute_residual_from_qlp_coefficients_64bit)(const FLAC__int32 *data, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 residual[]); void (*local_lpc_compute_residual_from_qlp_coefficients_16bit)(const FLAC__int32 *data, unsigned data_len, const FLAC__int32 qlp_coeff[], unsigned order, int lp_quantization, FLAC__int32 residual[]); #endif FLAC__bool use_wide_by_block; /* use slow 64-bit versions of some functions because of the block size */ FLAC__bool use_wide_by_partition; /* use slow 64-bit versions of some functions because of the min partition order and blocksize */ FLAC__bool use_wide_by_order; /* use slow 64-bit versions of some functions because of the lpc order */ FLAC__bool disable_constant_subframes; FLAC__bool disable_fixed_subframes; FLAC__bool disable_verbatim_subframes; #if FLAC__HAS_OGG FLAC__bool is_ogg; #endif FLAC__StreamEncoderReadCallback read_callback; /* currently only needed for Ogg FLAC */ FLAC__StreamEncoderSeekCallback seek_callback; FLAC__StreamEncoderTellCallback tell_callback; FLAC__StreamEncoderWriteCallback write_callback; FLAC__StreamEncoderMetadataCallback metadata_callback; FLAC__StreamEncoderProgressCallback progress_callback; void *client_data; unsigned first_seekpoint_to_check; FILE *file; /* only used when encoding to a file */ FLAC__uint64 bytes_written; FLAC__uint64 samples_written; unsigned frames_written; unsigned total_frames_estimate; /* unaligned (original) pointers to allocated data */ FLAC__int32 *integer_signal_unaligned[FLAC__MAX_CHANNELS]; FLAC__int32 *integer_signal_mid_side_unaligned[2]; #ifndef FLAC__INTEGER_ONLY_LIBRARY FLAC__real *real_signal_unaligned[FLAC__MAX_CHANNELS]; /* (@@@ currently unused) */ FLAC__real *real_signal_mid_side_unaligned[2]; /* (@@@ currently unused) */ FLAC__real *window_unaligned[FLAC__MAX_APODIZATION_FUNCTIONS]; FLAC__real *windowed_signal_unaligned; #endif FLAC__int32 *residual_workspace_unaligned[FLAC__MAX_CHANNELS][2]; FLAC__int32 *residual_workspace_mid_side_unaligned[2][2]; FLAC__uint64 *abs_residual_partition_sums_unaligned; unsigned *raw_bits_per_partition_unaligned; /* * These fields have been moved here from private function local * declarations merely to save stack space during encoding. */ #ifndef FLAC__INTEGER_ONLY_LIBRARY FLAC__real lp_coeff[FLAC__MAX_LPC_ORDER][FLAC__MAX_LPC_ORDER]; /* from process_subframe_() */ #endif FLAC__EntropyCodingMethod_PartitionedRiceContents partitioned_rice_contents_extra[2]; /* from find_best_partition_order_() */ /* * The data for the verify section */ struct { FLAC__StreamDecoder *decoder; EncoderStateHint state_hint; FLAC__bool needs_magic_hack; verify_input_fifo input_fifo; verify_output output; struct { FLAC__uint64 absolute_sample; unsigned frame_number; unsigned channel; unsigned sample; FLAC__int32 expected; FLAC__int32 got; } error_stats; } verify; FLAC__bool is_being_deleted; /* if true, call to ..._finish() from ..._delete() will not call the callbacks */ } FLAC__StreamEncoderPrivate; /*********************************************************************** * * Public static class data * ***********************************************************************/ FLAC_API const char * const FLAC__StreamEncoderStateString[] = { "FLAC__STREAM_ENCODER_OK", "FLAC__STREAM_ENCODER_UNINITIALIZED", "FLAC__STREAM_ENCODER_OGG_ERROR", "FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR", "FLAC__STREAM_ENCODER_VERIFY_MISMATCH_IN_AUDIO_DATA", "FLAC__STREAM_ENCODER_CLIENT_ERROR", "FLAC__STREAM_ENCODER_IO_ERROR", "FLAC__STREAM_ENCODER_FRAMING_ERROR", "FLAC__STREAM_ENCODER_MEMORY_ALLOCATION_ERROR" }; FLAC_API const char * const FLAC__StreamEncoderInitStatusString[] = { "FLAC__STREAM_ENCODER_INIT_STATUS_OK", "FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR", "FLAC__STREAM_ENCODER_INIT_STATUS_UNSUPPORTED_CONTAINER", "FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_CALLBACKS", "FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_NUMBER_OF_CHANNELS", "FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_BITS_PER_SAMPLE", "FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_SAMPLE_RATE", "FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_BLOCK_SIZE", "FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_MAX_LPC_ORDER", "FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_QLP_COEFF_PRECISION", "FLAC__STREAM_ENCODER_INIT_STATUS_BLOCK_SIZE_TOO_SMALL_FOR_LPC_ORDER", "FLAC__STREAM_ENCODER_INIT_STATUS_NOT_STREAMABLE", "FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA", "FLAC__STREAM_ENCODER_INIT_STATUS_ALREADY_INITIALIZED" }; FLAC_API const char * const FLAC__treamEncoderReadStatusString[] = { "FLAC__STREAM_ENCODER_READ_STATUS_CONTINUE", "FLAC__STREAM_ENCODER_READ_STATUS_END_OF_STREAM", "FLAC__STREAM_ENCODER_READ_STATUS_ABORT", "FLAC__STREAM_ENCODER_READ_STATUS_UNSUPPORTED" }; FLAC_API const char * const FLAC__StreamEncoderWriteStatusString[] = { "FLAC__STREAM_ENCODER_WRITE_STATUS_OK", "FLAC__STREAM_ENCODER_WRITE_STATUS_FATAL_ERROR" }; FLAC_API const char * const FLAC__StreamEncoderSeekStatusString[] = { "FLAC__STREAM_ENCODER_SEEK_STATUS_OK", "FLAC__STREAM_ENCODER_SEEK_STATUS_ERROR", "FLAC__STREAM_ENCODER_SEEK_STATUS_UNSUPPORTED" }; FLAC_API const char * const FLAC__StreamEncoderTellStatusString[] = { "FLAC__STREAM_ENCODER_TELL_STATUS_OK", "FLAC__STREAM_ENCODER_TELL_STATUS_ERROR", "FLAC__STREAM_ENCODER_TELL_STATUS_UNSUPPORTED" }; /* Number of samples that will be overread to watch for end of stream. By * 'overread', we mean that the FLAC__stream_encoder_process*() calls will * always try to read blocksize+1 samples before encoding a block, so that * even if the stream has a total sample count that is an integral multiple * of the blocksize, we will still notice when we are encoding the last * block. This is needed, for example, to correctly set the end-of-stream * marker in Ogg FLAC. * * WATCHOUT: some parts of the code assert that OVERREAD_ == 1 and there's * not really any reason to change it. */ static const unsigned OVERREAD_ = 1; /*********************************************************************** * * Class constructor/destructor * */ FLAC_API FLAC__StreamEncoder *FLAC__stream_encoder_new(void) { FLAC__StreamEncoder *encoder; unsigned i; FLAC__ASSERT(sizeof(int) >= 4); /* we want to die right away if this is not true */ encoder = (FLAC__StreamEncoder*)calloc(1, sizeof(FLAC__StreamEncoder)); if(encoder == 0) { return 0; } encoder->protected_ = (FLAC__StreamEncoderProtected*)calloc(1, sizeof(FLAC__StreamEncoderProtected)); if(encoder->protected_ == 0) { free(encoder); return 0; } encoder->private_ = (FLAC__StreamEncoderPrivate*)calloc(1, sizeof(FLAC__StreamEncoderPrivate)); if(encoder->private_ == 0) { free(encoder->protected_); free(encoder); return 0; } encoder->private_->frame = FLAC__bitwriter_new(); if(encoder->private_->frame == 0) { free(encoder->private_); free(encoder->protected_); free(encoder); return 0; } encoder->private_->file = 0; set_defaults_(encoder); encoder->private_->is_being_deleted = false; for(i = 0; i < FLAC__MAX_CHANNELS; i++) { encoder->private_->subframe_workspace_ptr[i][0] = &encoder->private_->subframe_workspace[i][0]; encoder->private_->subframe_workspace_ptr[i][1] = &encoder->private_->subframe_workspace[i][1]; } for(i = 0; i < 2; i++) { encoder->private_->subframe_workspace_ptr_mid_side[i][0] = &encoder->private_->subframe_workspace_mid_side[i][0]; encoder->private_->subframe_workspace_ptr_mid_side[i][1] = &encoder->private_->subframe_workspace_mid_side[i][1]; } for(i = 0; i < FLAC__MAX_CHANNELS; i++) { encoder->private_->partitioned_rice_contents_workspace_ptr[i][0] = &encoder->private_->partitioned_rice_contents_workspace[i][0]; encoder->private_->partitioned_rice_contents_workspace_ptr[i][1] = &encoder->private_->partitioned_rice_contents_workspace[i][1]; } for(i = 0; i < 2; i++) { encoder->private_->partitioned_rice_contents_workspace_ptr_mid_side[i][0] = &encoder->private_->partitioned_rice_contents_workspace_mid_side[i][0]; encoder->private_->partitioned_rice_contents_workspace_ptr_mid_side[i][1] = &encoder->private_->partitioned_rice_contents_workspace_mid_side[i][1]; } for(i = 0; i < FLAC__MAX_CHANNELS; i++) { FLAC__format_entropy_coding_method_partitioned_rice_contents_init(&encoder->private_->partitioned_rice_contents_workspace[i][0]); FLAC__format_entropy_coding_method_partitioned_rice_contents_init(&encoder->private_->partitioned_rice_contents_workspace[i][1]); } for(i = 0; i < 2; i++) { FLAC__format_entropy_coding_method_partitioned_rice_contents_init(&encoder->private_->partitioned_rice_contents_workspace_mid_side[i][0]); FLAC__format_entropy_coding_method_partitioned_rice_contents_init(&encoder->private_->partitioned_rice_contents_workspace_mid_side[i][1]); } for(i = 0; i < 2; i++) FLAC__format_entropy_coding_method_partitioned_rice_contents_init(&encoder->private_->partitioned_rice_contents_extra[i]); encoder->protected_->state = FLAC__STREAM_ENCODER_UNINITIALIZED; return encoder; } FLAC_API void FLAC__stream_encoder_delete(FLAC__StreamEncoder *encoder) { unsigned i; FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->protected_); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->private_->frame); encoder->private_->is_being_deleted = true; (void)FLAC__stream_encoder_finish(encoder); if(0 != encoder->private_->verify.decoder) FLAC__stream_decoder_delete(encoder->private_->verify.decoder); for(i = 0; i < FLAC__MAX_CHANNELS; i++) { FLAC__format_entropy_coding_method_partitioned_rice_contents_clear(&encoder->private_->partitioned_rice_contents_workspace[i][0]); FLAC__format_entropy_coding_method_partitioned_rice_contents_clear(&encoder->private_->partitioned_rice_contents_workspace[i][1]); } for(i = 0; i < 2; i++) { FLAC__format_entropy_coding_method_partitioned_rice_contents_clear(&encoder->private_->partitioned_rice_contents_workspace_mid_side[i][0]); FLAC__format_entropy_coding_method_partitioned_rice_contents_clear(&encoder->private_->partitioned_rice_contents_workspace_mid_side[i][1]); } for(i = 0; i < 2; i++) FLAC__format_entropy_coding_method_partitioned_rice_contents_clear(&encoder->private_->partitioned_rice_contents_extra[i]); FLAC__bitwriter_delete(encoder->private_->frame); free(encoder->private_); free(encoder->protected_); free(encoder); } /*********************************************************************** * * Public class methods * ***********************************************************************/ static FLAC__StreamEncoderInitStatus init_stream_internal_( FLAC__StreamEncoder *encoder, FLAC__StreamEncoderReadCallback read_callback, FLAC__StreamEncoderWriteCallback write_callback, FLAC__StreamEncoderSeekCallback seek_callback, FLAC__StreamEncoderTellCallback tell_callback, FLAC__StreamEncoderMetadataCallback metadata_callback, void *client_data, FLAC__bool is_ogg ) { unsigned i; FLAC__bool metadata_has_seektable, metadata_has_vorbis_comment, metadata_picture_has_type1, metadata_picture_has_type2; FLAC__ASSERT(0 != encoder); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return FLAC__STREAM_ENCODER_INIT_STATUS_ALREADY_INITIALIZED; #if !FLAC__HAS_OGG if(is_ogg) return FLAC__STREAM_ENCODER_INIT_STATUS_UNSUPPORTED_CONTAINER; #endif if(0 == write_callback || (seek_callback && 0 == tell_callback)) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_CALLBACKS; if(encoder->protected_->channels == 0 || encoder->protected_->channels > FLAC__MAX_CHANNELS) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_NUMBER_OF_CHANNELS; if(encoder->protected_->channels != 2) { encoder->protected_->do_mid_side_stereo = false; encoder->protected_->loose_mid_side_stereo = false; } else if(!encoder->protected_->do_mid_side_stereo) encoder->protected_->loose_mid_side_stereo = false; if(encoder->protected_->bits_per_sample >= 32) encoder->protected_->do_mid_side_stereo = false; /* since we currenty do 32-bit math, the side channel would have 33 bps and overflow */ if(encoder->protected_->bits_per_sample < FLAC__MIN_BITS_PER_SAMPLE || encoder->protected_->bits_per_sample > FLAC__REFERENCE_CODEC_MAX_BITS_PER_SAMPLE) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_BITS_PER_SAMPLE; if(!FLAC__format_sample_rate_is_valid(encoder->protected_->sample_rate)) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_SAMPLE_RATE; if(encoder->protected_->blocksize == 0) { if(encoder->protected_->max_lpc_order == 0) encoder->protected_->blocksize = 1152; else encoder->protected_->blocksize = 4096; } if(encoder->protected_->blocksize < FLAC__MIN_BLOCK_SIZE || encoder->protected_->blocksize > FLAC__MAX_BLOCK_SIZE) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_BLOCK_SIZE; if(encoder->protected_->max_lpc_order > FLAC__MAX_LPC_ORDER) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_MAX_LPC_ORDER; if(encoder->protected_->blocksize < encoder->protected_->max_lpc_order) return FLAC__STREAM_ENCODER_INIT_STATUS_BLOCK_SIZE_TOO_SMALL_FOR_LPC_ORDER; if(encoder->protected_->qlp_coeff_precision == 0) { if(encoder->protected_->bits_per_sample < 16) { /* @@@ need some data about how to set this here w.r.t. blocksize and sample rate */ /* @@@ until then we'll make a guess */ encoder->protected_->qlp_coeff_precision = max(FLAC__MIN_QLP_COEFF_PRECISION, 2 + encoder->protected_->bits_per_sample / 2); } else if(encoder->protected_->bits_per_sample == 16) { if(encoder->protected_->blocksize <= 192) encoder->protected_->qlp_coeff_precision = 7; else if(encoder->protected_->blocksize <= 384) encoder->protected_->qlp_coeff_precision = 8; else if(encoder->protected_->blocksize <= 576) encoder->protected_->qlp_coeff_precision = 9; else if(encoder->protected_->blocksize <= 1152) encoder->protected_->qlp_coeff_precision = 10; else if(encoder->protected_->blocksize <= 2304) encoder->protected_->qlp_coeff_precision = 11; else if(encoder->protected_->blocksize <= 4608) encoder->protected_->qlp_coeff_precision = 12; else encoder->protected_->qlp_coeff_precision = 13; } else { if(encoder->protected_->blocksize <= 384) encoder->protected_->qlp_coeff_precision = FLAC__MAX_QLP_COEFF_PRECISION-2; else if(encoder->protected_->blocksize <= 1152) encoder->protected_->qlp_coeff_precision = FLAC__MAX_QLP_COEFF_PRECISION-1; else encoder->protected_->qlp_coeff_precision = FLAC__MAX_QLP_COEFF_PRECISION; } FLAC__ASSERT(encoder->protected_->qlp_coeff_precision <= FLAC__MAX_QLP_COEFF_PRECISION); } else if(encoder->protected_->qlp_coeff_precision < FLAC__MIN_QLP_COEFF_PRECISION || encoder->protected_->qlp_coeff_precision > FLAC__MAX_QLP_COEFF_PRECISION) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_QLP_COEFF_PRECISION; if(encoder->protected_->streamable_subset) { if( encoder->protected_->blocksize != 192 && encoder->protected_->blocksize != 576 && encoder->protected_->blocksize != 1152 && encoder->protected_->blocksize != 2304 && encoder->protected_->blocksize != 4608 && encoder->protected_->blocksize != 256 && encoder->protected_->blocksize != 512 && encoder->protected_->blocksize != 1024 && encoder->protected_->blocksize != 2048 && encoder->protected_->blocksize != 4096 && encoder->protected_->blocksize != 8192 && encoder->protected_->blocksize != 16384 ) return FLAC__STREAM_ENCODER_INIT_STATUS_NOT_STREAMABLE; if(!FLAC__format_sample_rate_is_subset(encoder->protected_->sample_rate)) return FLAC__STREAM_ENCODER_INIT_STATUS_NOT_STREAMABLE; if( encoder->protected_->bits_per_sample != 8 && encoder->protected_->bits_per_sample != 12 && encoder->protected_->bits_per_sample != 16 && encoder->protected_->bits_per_sample != 20 && encoder->protected_->bits_per_sample != 24 ) return FLAC__STREAM_ENCODER_INIT_STATUS_NOT_STREAMABLE; if(encoder->protected_->max_residual_partition_order > FLAC__SUBSET_MAX_RICE_PARTITION_ORDER) return FLAC__STREAM_ENCODER_INIT_STATUS_NOT_STREAMABLE; if( encoder->protected_->sample_rate <= 48000 && ( encoder->protected_->blocksize > FLAC__SUBSET_MAX_BLOCK_SIZE_48000HZ || encoder->protected_->max_lpc_order > FLAC__SUBSET_MAX_LPC_ORDER_48000HZ ) ) { return FLAC__STREAM_ENCODER_INIT_STATUS_NOT_STREAMABLE; } } if(encoder->protected_->max_residual_partition_order >= (1u << FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ORDER_LEN)) encoder->protected_->max_residual_partition_order = (1u << FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ORDER_LEN) - 1; if(encoder->protected_->min_residual_partition_order >= encoder->protected_->max_residual_partition_order) encoder->protected_->min_residual_partition_order = encoder->protected_->max_residual_partition_order; #if FLAC__HAS_OGG /* reorder metadata if necessary to ensure that any VORBIS_COMMENT is the first, according to the mapping spec */ if(is_ogg && 0 != encoder->protected_->metadata && encoder->protected_->num_metadata_blocks > 1) { unsigned i; for(i = 1; i < encoder->protected_->num_metadata_blocks; i++) { if(0 != encoder->protected_->metadata[i] && encoder->protected_->metadata[i]->type == FLAC__METADATA_TYPE_VORBIS_COMMENT) { FLAC__StreamMetadata *vc = encoder->protected_->metadata[i]; for( ; i > 0; i--) encoder->protected_->metadata[i] = encoder->protected_->metadata[i-1]; encoder->protected_->metadata[0] = vc; break; } } } #endif /* keep track of any SEEKTABLE block */ if(0 != encoder->protected_->metadata && encoder->protected_->num_metadata_blocks > 0) { unsigned i; for(i = 0; i < encoder->protected_->num_metadata_blocks; i++) { if(0 != encoder->protected_->metadata[i] && encoder->protected_->metadata[i]->type == FLAC__METADATA_TYPE_SEEKTABLE) { encoder->private_->seek_table = &encoder->protected_->metadata[i]->data.seek_table; break; /* take only the first one */ } } } /* validate metadata */ if(0 == encoder->protected_->metadata && encoder->protected_->num_metadata_blocks > 0) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; metadata_has_seektable = false; metadata_has_vorbis_comment = false; metadata_picture_has_type1 = false; metadata_picture_has_type2 = false; for(i = 0; i < encoder->protected_->num_metadata_blocks; i++) { const FLAC__StreamMetadata *m = encoder->protected_->metadata[i]; if(m->type == FLAC__METADATA_TYPE_STREAMINFO) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; else if(m->type == FLAC__METADATA_TYPE_SEEKTABLE) { if(metadata_has_seektable) /* only one is allowed */ return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; metadata_has_seektable = true; if(!FLAC__format_seektable_is_legal(&m->data.seek_table)) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; } else if(m->type == FLAC__METADATA_TYPE_VORBIS_COMMENT) { if(metadata_has_vorbis_comment) /* only one is allowed */ return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; metadata_has_vorbis_comment = true; } else if(m->type == FLAC__METADATA_TYPE_CUESHEET) { if(!FLAC__format_cuesheet_is_legal(&m->data.cue_sheet, m->data.cue_sheet.is_cd, /*violation=*/0)) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; } else if(m->type == FLAC__METADATA_TYPE_PICTURE) { if(!FLAC__format_picture_is_legal(&m->data.picture, /*violation=*/0)) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; if(m->data.picture.type == FLAC__STREAM_METADATA_PICTURE_TYPE_FILE_ICON_STANDARD) { if(metadata_picture_has_type1) /* there should only be 1 per stream */ return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; metadata_picture_has_type1 = true; /* standard icon must be 32x32 pixel PNG */ if( m->data.picture.type == FLAC__STREAM_METADATA_PICTURE_TYPE_FILE_ICON_STANDARD && ( (strcmp(m->data.picture.mime_type, "image/png") && strcmp(m->data.picture.mime_type, "-->")) || m->data.picture.width != 32 || m->data.picture.height != 32 ) ) return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; } else if(m->data.picture.type == FLAC__STREAM_METADATA_PICTURE_TYPE_FILE_ICON) { if(metadata_picture_has_type2) /* there should only be 1 per stream */ return FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA; metadata_picture_has_type2 = true; } } } encoder->private_->input_capacity = 0; for(i = 0; i < encoder->protected_->channels; i++) { encoder->private_->integer_signal_unaligned[i] = encoder->private_->integer_signal[i] = 0; #ifndef FLAC__INTEGER_ONLY_LIBRARY encoder->private_->real_signal_unaligned[i] = encoder->private_->real_signal[i] = 0; #endif } for(i = 0; i < 2; i++) { encoder->private_->integer_signal_mid_side_unaligned[i] = encoder->private_->integer_signal_mid_side[i] = 0; #ifndef FLAC__INTEGER_ONLY_LIBRARY encoder->private_->real_signal_mid_side_unaligned[i] = encoder->private_->real_signal_mid_side[i] = 0; #endif } #ifndef FLAC__INTEGER_ONLY_LIBRARY for(i = 0; i < encoder->protected_->num_apodizations; i++) encoder->private_->window_unaligned[i] = encoder->private_->window[i] = 0; encoder->private_->windowed_signal_unaligned = encoder->private_->windowed_signal = 0; #endif for(i = 0; i < encoder->protected_->channels; i++) { encoder->private_->residual_workspace_unaligned[i][0] = encoder->private_->residual_workspace[i][0] = 0; encoder->private_->residual_workspace_unaligned[i][1] = encoder->private_->residual_workspace[i][1] = 0; encoder->private_->best_subframe[i] = 0; } for(i = 0; i < 2; i++) { encoder->private_->residual_workspace_mid_side_unaligned[i][0] = encoder->private_->residual_workspace_mid_side[i][0] = 0; encoder->private_->residual_workspace_mid_side_unaligned[i][1] = encoder->private_->residual_workspace_mid_side[i][1] = 0; encoder->private_->best_subframe_mid_side[i] = 0; } encoder->private_->abs_residual_partition_sums_unaligned = encoder->private_->abs_residual_partition_sums = 0; encoder->private_->raw_bits_per_partition_unaligned = encoder->private_->raw_bits_per_partition = 0; #ifndef FLAC__INTEGER_ONLY_LIBRARY encoder->private_->loose_mid_side_stereo_frames = (unsigned)((FLAC__double)encoder->protected_->sample_rate * 0.4 / (FLAC__double)encoder->protected_->blocksize + 0.5); #else /* 26214 is the approximate fixed-point equivalent to 0.4 (0.4 * 2^16) */ /* sample rate can be up to 655350 Hz, and thus use 20 bits, so we do the multiply÷ by hand */ FLAC__ASSERT(FLAC__MAX_SAMPLE_RATE <= 655350); FLAC__ASSERT(FLAC__MAX_BLOCK_SIZE <= 65535); FLAC__ASSERT(encoder->protected_->sample_rate <= 655350); FLAC__ASSERT(encoder->protected_->blocksize <= 65535); encoder->private_->loose_mid_side_stereo_frames = (unsigned)FLAC__fixedpoint_trunc((((FLAC__uint64)(encoder->protected_->sample_rate) * (FLAC__uint64)(26214)) << 16) / (encoder->protected_->blocksize<<16) + FLAC__FP_ONE_HALF); #endif if(encoder->private_->loose_mid_side_stereo_frames == 0) encoder->private_->loose_mid_side_stereo_frames = 1; encoder->private_->loose_mid_side_stereo_frame_count = 0; encoder->private_->current_sample_number = 0; encoder->private_->current_frame_number = 0; encoder->private_->use_wide_by_block = (encoder->protected_->bits_per_sample + FLAC__bitmath_ilog2(encoder->protected_->blocksize)+1 > 30); encoder->private_->use_wide_by_order = (encoder->protected_->bits_per_sample + FLAC__bitmath_ilog2(max(encoder->protected_->max_lpc_order, FLAC__MAX_FIXED_ORDER))+1 > 30); /*@@@ need to use this? */ encoder->private_->use_wide_by_partition = (false); /*@@@ need to set this */ /* * get the CPU info and set the function pointers */ FLAC__cpu_info(&encoder->private_->cpuinfo); /* first default to the non-asm routines */ #ifndef FLAC__INTEGER_ONLY_LIBRARY encoder->private_->local_lpc_compute_autocorrelation = FLAC__lpc_compute_autocorrelation; #endif encoder->private_->local_fixed_compute_best_predictor = FLAC__fixed_compute_best_predictor; #ifndef FLAC__INTEGER_ONLY_LIBRARY encoder->private_->local_lpc_compute_residual_from_qlp_coefficients = FLAC__lpc_compute_residual_from_qlp_coefficients; encoder->private_->local_lpc_compute_residual_from_qlp_coefficients_64bit = FLAC__lpc_compute_residual_from_qlp_coefficients_wide; encoder->private_->local_lpc_compute_residual_from_qlp_coefficients_16bit = FLAC__lpc_compute_residual_from_qlp_coefficients; #endif /* now override with asm where appropriate */ #ifndef FLAC__INTEGER_ONLY_LIBRARY # ifndef FLAC__NO_ASM if(encoder->private_->cpuinfo.use_asm) { # ifdef FLAC__CPU_IA32 FLAC__ASSERT(encoder->private_->cpuinfo.type == FLAC__CPUINFO_TYPE_IA32); # ifdef FLAC__HAS_NASM if(encoder->private_->cpuinfo.data.ia32.sse) { if(encoder->protected_->max_lpc_order < 4) encoder->private_->local_lpc_compute_autocorrelation = FLAC__lpc_compute_autocorrelation_asm_ia32_sse_lag_4; else if(encoder->protected_->max_lpc_order < 8) encoder->private_->local_lpc_compute_autocorrelation = FLAC__lpc_compute_autocorrelation_asm_ia32_sse_lag_8; else if(encoder->protected_->max_lpc_order < 12) encoder->private_->local_lpc_compute_autocorrelation = FLAC__lpc_compute_autocorrelation_asm_ia32_sse_lag_12; else encoder->private_->local_lpc_compute_autocorrelation = FLAC__lpc_compute_autocorrelation_asm_ia32; } else if(encoder->private_->cpuinfo.data.ia32._3dnow) encoder->private_->local_lpc_compute_autocorrelation = FLAC__lpc_compute_autocorrelation_asm_ia32_3dnow; else encoder->private_->local_lpc_compute_autocorrelation = FLAC__lpc_compute_autocorrelation_asm_ia32; if(encoder->private_->cpuinfo.data.ia32.mmx) { encoder->private_->local_lpc_compute_residual_from_qlp_coefficients = FLAC__lpc_compute_residual_from_qlp_coefficients_asm_ia32; encoder->private_->local_lpc_compute_residual_from_qlp_coefficients_16bit = FLAC__lpc_compute_residual_from_qlp_coefficients_asm_ia32_mmx; } else { encoder->private_->local_lpc_compute_residual_from_qlp_coefficients = FLAC__lpc_compute_residual_from_qlp_coefficients_asm_ia32; encoder->private_->local_lpc_compute_residual_from_qlp_coefficients_16bit = FLAC__lpc_compute_residual_from_qlp_coefficients_asm_ia32; } if(encoder->private_->cpuinfo.data.ia32.mmx && encoder->private_->cpuinfo.data.ia32.cmov) encoder->private_->local_fixed_compute_best_predictor = FLAC__fixed_compute_best_predictor_asm_ia32_mmx_cmov; # endif /* FLAC__HAS_NASM */ # endif /* FLAC__CPU_IA32 */ } # endif /* !FLAC__NO_ASM */ #endif /* !FLAC__INTEGER_ONLY_LIBRARY */ /* finally override based on wide-ness if necessary */ if(encoder->private_->use_wide_by_block) { encoder->private_->local_fixed_compute_best_predictor = FLAC__fixed_compute_best_predictor_wide; } /* set state to OK; from here on, errors are fatal and we'll override the state then */ encoder->protected_->state = FLAC__STREAM_ENCODER_OK; #if FLAC__HAS_OGG encoder->private_->is_ogg = is_ogg; if(is_ogg && !FLAC__ogg_encoder_aspect_init(&encoder->protected_->ogg_encoder_aspect)) { encoder->protected_->state = FLAC__STREAM_ENCODER_OGG_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } #endif encoder->private_->read_callback = read_callback; encoder->private_->write_callback = write_callback; encoder->private_->seek_callback = seek_callback; encoder->private_->tell_callback = tell_callback; encoder->private_->metadata_callback = metadata_callback; encoder->private_->client_data = client_data; if(!resize_buffers_(encoder, encoder->protected_->blocksize)) { /* the above function sets the state for us in case of an error */ return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } if(!FLAC__bitwriter_init(encoder->private_->frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_MEMORY_ALLOCATION_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } /* * Set up the verify stuff if necessary */ if(encoder->protected_->verify) { /* * First, set up the fifo which will hold the * original signal to compare against */ encoder->private_->verify.input_fifo.size = encoder->protected_->blocksize+OVERREAD_; for(i = 0; i < encoder->protected_->channels; i++) { if(0 == (encoder->private_->verify.input_fifo.data[i] = (FLAC__int32*)safe_malloc_mul_2op_(sizeof(FLAC__int32), /*times*/encoder->private_->verify.input_fifo.size))) { encoder->protected_->state = FLAC__STREAM_ENCODER_MEMORY_ALLOCATION_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } } encoder->private_->verify.input_fifo.tail = 0; /* * Now set up a stream decoder for verification */ encoder->private_->verify.decoder = FLAC__stream_decoder_new(); if(0 == encoder->private_->verify.decoder) { encoder->protected_->state = FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } if(FLAC__stream_decoder_init_stream(encoder->private_->verify.decoder, verify_read_callback_, /*seek_callback=*/0, /*tell_callback=*/0, /*length_callback=*/0, /*eof_callback=*/0, verify_write_callback_, verify_metadata_callback_, verify_error_callback_, /*client_data=*/encoder) != FLAC__STREAM_DECODER_INIT_STATUS_OK) { encoder->protected_->state = FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } } encoder->private_->verify.error_stats.absolute_sample = 0; encoder->private_->verify.error_stats.frame_number = 0; encoder->private_->verify.error_stats.channel = 0; encoder->private_->verify.error_stats.sample = 0; encoder->private_->verify.error_stats.expected = 0; encoder->private_->verify.error_stats.got = 0; /* * These must be done before we write any metadata, because that * calls the write_callback, which uses these values. */ encoder->private_->first_seekpoint_to_check = 0; encoder->private_->samples_written = 0; encoder->protected_->streaminfo_offset = 0; encoder->protected_->seektable_offset = 0; encoder->protected_->audio_offset = 0; /* * write the stream header */ if(encoder->protected_->verify) encoder->private_->verify.state_hint = ENCODER_IN_MAGIC; if(!FLAC__bitwriter_write_raw_uint32(encoder->private_->frame, FLAC__STREAM_SYNC, FLAC__STREAM_SYNC_LEN)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } if(!write_bitbuffer_(encoder, 0, /*is_last_block=*/false)) { /* the above function sets the state for us in case of an error */ return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } /* * write the STREAMINFO metadata block */ if(encoder->protected_->verify) encoder->private_->verify.state_hint = ENCODER_IN_METADATA; encoder->private_->streaminfo.type = FLAC__METADATA_TYPE_STREAMINFO; encoder->private_->streaminfo.is_last = false; /* we will have at a minimum a VORBIS_COMMENT afterwards */ encoder->private_->streaminfo.length = FLAC__STREAM_METADATA_STREAMINFO_LENGTH; encoder->private_->streaminfo.data.stream_info.min_blocksize = encoder->protected_->blocksize; /* this encoder uses the same blocksize for the whole stream */ encoder->private_->streaminfo.data.stream_info.max_blocksize = encoder->protected_->blocksize; encoder->private_->streaminfo.data.stream_info.min_framesize = 0; /* we don't know this yet; have to fill it in later */ encoder->private_->streaminfo.data.stream_info.max_framesize = 0; /* we don't know this yet; have to fill it in later */ encoder->private_->streaminfo.data.stream_info.sample_rate = encoder->protected_->sample_rate; encoder->private_->streaminfo.data.stream_info.channels = encoder->protected_->channels; encoder->private_->streaminfo.data.stream_info.bits_per_sample = encoder->protected_->bits_per_sample; encoder->private_->streaminfo.data.stream_info.total_samples = encoder->protected_->total_samples_estimate; /* we will replace this later with the real total */ memset(encoder->private_->streaminfo.data.stream_info.md5sum, 0, 16); /* we don't know this yet; have to fill it in later */ if(encoder->protected_->do_md5) FLAC__MD5Init(&encoder->private_->md5context); if(!FLAC__add_metadata_block(&encoder->private_->streaminfo, encoder->private_->frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } if(!write_bitbuffer_(encoder, 0, /*is_last_block=*/false)) { /* the above function sets the state for us in case of an error */ return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } /* * Now that the STREAMINFO block is written, we can init this to an * absurdly-high value... */ encoder->private_->streaminfo.data.stream_info.min_framesize = (1u << FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN) - 1; /* ... and clear this to 0 */ encoder->private_->streaminfo.data.stream_info.total_samples = 0; /* * Check to see if the supplied metadata contains a VORBIS_COMMENT; * if not, we will write an empty one (FLAC__add_metadata_block() * automatically supplies the vendor string). * * WATCHOUT: the Ogg FLAC mapping requires us to write this block after * the STREAMINFO. (In the case that metadata_has_vorbis_comment is * true it will have already insured that the metadata list is properly * ordered.) */ if(!metadata_has_vorbis_comment) { FLAC__StreamMetadata vorbis_comment; vorbis_comment.type = FLAC__METADATA_TYPE_VORBIS_COMMENT; vorbis_comment.is_last = (encoder->protected_->num_metadata_blocks == 0); vorbis_comment.length = 4 + 4; /* MAGIC NUMBER */ vorbis_comment.data.vorbis_comment.vendor_string.length = 0; vorbis_comment.data.vorbis_comment.vendor_string.entry = 0; vorbis_comment.data.vorbis_comment.num_comments = 0; vorbis_comment.data.vorbis_comment.comments = 0; if(!FLAC__add_metadata_block(&vorbis_comment, encoder->private_->frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } if(!write_bitbuffer_(encoder, 0, /*is_last_block=*/false)) { /* the above function sets the state for us in case of an error */ return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } } /* * write the user's metadata blocks */ for(i = 0; i < encoder->protected_->num_metadata_blocks; i++) { encoder->protected_->metadata[i]->is_last = (i == encoder->protected_->num_metadata_blocks - 1); if(!FLAC__add_metadata_block(encoder->protected_->metadata[i], encoder->private_->frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } if(!write_bitbuffer_(encoder, 0, /*is_last_block=*/false)) { /* the above function sets the state for us in case of an error */ return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } } /* now that all the metadata is written, we save the stream offset */ if(encoder->private_->tell_callback && encoder->private_->tell_callback(encoder, &encoder->protected_->audio_offset, encoder->private_->client_data) == FLAC__STREAM_ENCODER_TELL_STATUS_ERROR) { /* FLAC__STREAM_ENCODER_TELL_STATUS_UNSUPPORTED just means we didn't get the offset; no error */ encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } if(encoder->protected_->verify) encoder->private_->verify.state_hint = ENCODER_IN_AUDIO; return FLAC__STREAM_ENCODER_INIT_STATUS_OK; } FLAC_API FLAC__StreamEncoderInitStatus FLAC__stream_encoder_init_stream( FLAC__StreamEncoder *encoder, FLAC__StreamEncoderWriteCallback write_callback, FLAC__StreamEncoderSeekCallback seek_callback, FLAC__StreamEncoderTellCallback tell_callback, FLAC__StreamEncoderMetadataCallback metadata_callback, void *client_data ) { return init_stream_internal_( encoder, /*read_callback=*/0, write_callback, seek_callback, tell_callback, metadata_callback, client_data, /*is_ogg=*/false ); } FLAC_API FLAC__StreamEncoderInitStatus FLAC__stream_encoder_init_ogg_stream( FLAC__StreamEncoder *encoder, FLAC__StreamEncoderReadCallback read_callback, FLAC__StreamEncoderWriteCallback write_callback, FLAC__StreamEncoderSeekCallback seek_callback, FLAC__StreamEncoderTellCallback tell_callback, FLAC__StreamEncoderMetadataCallback metadata_callback, void *client_data ) { return init_stream_internal_( encoder, read_callback, write_callback, seek_callback, tell_callback, metadata_callback, client_data, /*is_ogg=*/true ); } static FLAC__StreamEncoderInitStatus init_FILE_internal_( FLAC__StreamEncoder *encoder, FILE *file, FLAC__StreamEncoderProgressCallback progress_callback, void *client_data, FLAC__bool is_ogg ) { FLAC__StreamEncoderInitStatus init_status; FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != file); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return FLAC__STREAM_ENCODER_INIT_STATUS_ALREADY_INITIALIZED; /* double protection */ if(file == 0) { encoder->protected_->state = FLAC__STREAM_ENCODER_IO_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } /* * To make sure that our file does not go unclosed after an error, we * must assign the FILE pointer before any further error can occur in * this routine. */ if(file == stdout) file = get_binary_stdout_(); /* just to be safe */ encoder->private_->file = file; encoder->private_->progress_callback = progress_callback; encoder->private_->bytes_written = 0; encoder->private_->samples_written = 0; encoder->private_->frames_written = 0; init_status = init_stream_internal_( encoder, encoder->private_->file == stdout? 0 : is_ogg? file_read_callback_ : 0, file_write_callback_, encoder->private_->file == stdout? 0 : file_seek_callback_, encoder->private_->file == stdout? 0 : file_tell_callback_, /*metadata_callback=*/0, client_data, is_ogg ); if(init_status != FLAC__STREAM_ENCODER_INIT_STATUS_OK) { /* the above function sets the state for us in case of an error */ return init_status; } { unsigned blocksize = FLAC__stream_encoder_get_blocksize(encoder); FLAC__ASSERT(blocksize != 0); encoder->private_->total_frames_estimate = (unsigned)((FLAC__stream_encoder_get_total_samples_estimate(encoder) + blocksize - 1) / blocksize); } return init_status; } FLAC_API FLAC__StreamEncoderInitStatus FLAC__stream_encoder_init_FILE( FLAC__StreamEncoder *encoder, FILE *file, FLAC__StreamEncoderProgressCallback progress_callback, void *client_data ) { return init_FILE_internal_(encoder, file, progress_callback, client_data, /*is_ogg=*/false); } FLAC_API FLAC__StreamEncoderInitStatus FLAC__stream_encoder_init_ogg_FILE( FLAC__StreamEncoder *encoder, FILE *file, FLAC__StreamEncoderProgressCallback progress_callback, void *client_data ) { return init_FILE_internal_(encoder, file, progress_callback, client_data, /*is_ogg=*/true); } static FLAC__StreamEncoderInitStatus init_file_internal_( FLAC__StreamEncoder *encoder, const char *filename, FLAC__StreamEncoderProgressCallback progress_callback, void *client_data, FLAC__bool is_ogg ) { FILE *file; FLAC__ASSERT(0 != encoder); /* * To make sure that our file does not go unclosed after an error, we * have to do the same entrance checks here that are later performed * in FLAC__stream_encoder_init_FILE() before the FILE* is assigned. */ if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return FLAC__STREAM_ENCODER_INIT_STATUS_ALREADY_INITIALIZED; file = filename? fopen(filename, "w+b") : stdout; if(file == 0) { encoder->protected_->state = FLAC__STREAM_ENCODER_IO_ERROR; return FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR; } return init_FILE_internal_(encoder, file, progress_callback, client_data, is_ogg); } FLAC_API FLAC__StreamEncoderInitStatus FLAC__stream_encoder_init_file( FLAC__StreamEncoder *encoder, const char *filename, FLAC__StreamEncoderProgressCallback progress_callback, void *client_data ) { return init_file_internal_(encoder, filename, progress_callback, client_data, /*is_ogg=*/false); } FLAC_API FLAC__StreamEncoderInitStatus FLAC__stream_encoder_init_ogg_file( FLAC__StreamEncoder *encoder, const char *filename, FLAC__StreamEncoderProgressCallback progress_callback, void *client_data ) { return init_file_internal_(encoder, filename, progress_callback, client_data, /*is_ogg=*/true); } FLAC_API FLAC__bool FLAC__stream_encoder_finish(FLAC__StreamEncoder *encoder) { FLAC__bool error = false; FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state == FLAC__STREAM_ENCODER_UNINITIALIZED) return true; if(encoder->protected_->state == FLAC__STREAM_ENCODER_OK && !encoder->private_->is_being_deleted) { if(encoder->private_->current_sample_number != 0) { const FLAC__bool is_fractional_block = encoder->protected_->blocksize != encoder->private_->current_sample_number; encoder->protected_->blocksize = encoder->private_->current_sample_number; if(!process_frame_(encoder, is_fractional_block, /*is_last_block=*/true)) error = true; } } if(encoder->protected_->do_md5) FLAC__MD5Final(encoder->private_->streaminfo.data.stream_info.md5sum, &encoder->private_->md5context); if(!encoder->private_->is_being_deleted) { if(encoder->protected_->state == FLAC__STREAM_ENCODER_OK) { if(encoder->private_->seek_callback) { #if FLAC__HAS_OGG if(encoder->private_->is_ogg) update_ogg_metadata_(encoder); else #endif update_metadata_(encoder); /* check if an error occurred while updating metadata */ if(encoder->protected_->state != FLAC__STREAM_ENCODER_OK) error = true; } if(encoder->private_->metadata_callback) encoder->private_->metadata_callback(encoder, &encoder->private_->streaminfo, encoder->private_->client_data); } if(encoder->protected_->verify && 0 != encoder->private_->verify.decoder && !FLAC__stream_decoder_finish(encoder->private_->verify.decoder)) { if(!error) encoder->protected_->state = FLAC__STREAM_ENCODER_VERIFY_MISMATCH_IN_AUDIO_DATA; error = true; } } if(0 != encoder->private_->file) { if(encoder->private_->file != stdout) fclose(encoder->private_->file); encoder->private_->file = 0; } #if FLAC__HAS_OGG if(encoder->private_->is_ogg) FLAC__ogg_encoder_aspect_finish(&encoder->protected_->ogg_encoder_aspect); #endif free_(encoder); set_defaults_(encoder); if(!error) encoder->protected_->state = FLAC__STREAM_ENCODER_UNINITIALIZED; return !error; } FLAC_API FLAC__bool FLAC__stream_encoder_set_ogg_serial_number(FLAC__StreamEncoder *encoder, long value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; #if FLAC__HAS_OGG /* can't check encoder->private_->is_ogg since that's not set until init time */ FLAC__ogg_encoder_aspect_set_serial_number(&encoder->protected_->ogg_encoder_aspect, value); return true; #else (void)value; return false; #endif } FLAC_API FLAC__bool FLAC__stream_encoder_set_verify(FLAC__StreamEncoder *encoder, FLAC__bool value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; #ifndef FLAC__MANDATORY_VERIFY_WHILE_ENCODING encoder->protected_->verify = value; #endif return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_streamable_subset(FLAC__StreamEncoder *encoder, FLAC__bool value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->streamable_subset = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_channels(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->channels = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_bits_per_sample(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->bits_per_sample = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_sample_rate(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->sample_rate = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_compression_level(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__bool ok = true; FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; if(value >= sizeof(compression_levels_)/sizeof(compression_levels_[0])) value = sizeof(compression_levels_)/sizeof(compression_levels_[0]) - 1; ok &= FLAC__stream_encoder_set_do_mid_side_stereo (encoder, compression_levels_[value].do_mid_side_stereo); ok &= FLAC__stream_encoder_set_loose_mid_side_stereo (encoder, compression_levels_[value].loose_mid_side_stereo); #ifndef FLAC__INTEGER_ONLY_LIBRARY #if 0 /* was: */ ok &= FLAC__stream_encoder_set_apodization (encoder, compression_levels_[value].apodization); /* but it's too hard to specify the string in a locale-specific way */ #else encoder->protected_->num_apodizations = 1; encoder->protected_->apodizations[0].type = FLAC__APODIZATION_TUKEY; encoder->protected_->apodizations[0].parameters.tukey.p = 0.5; #endif #endif ok &= FLAC__stream_encoder_set_max_lpc_order (encoder, compression_levels_[value].max_lpc_order); ok &= FLAC__stream_encoder_set_qlp_coeff_precision (encoder, compression_levels_[value].qlp_coeff_precision); ok &= FLAC__stream_encoder_set_do_qlp_coeff_prec_search (encoder, compression_levels_[value].do_qlp_coeff_prec_search); ok &= FLAC__stream_encoder_set_do_escape_coding (encoder, compression_levels_[value].do_escape_coding); ok &= FLAC__stream_encoder_set_do_exhaustive_model_search (encoder, compression_levels_[value].do_exhaustive_model_search); ok &= FLAC__stream_encoder_set_min_residual_partition_order(encoder, compression_levels_[value].min_residual_partition_order); ok &= FLAC__stream_encoder_set_max_residual_partition_order(encoder, compression_levels_[value].max_residual_partition_order); ok &= FLAC__stream_encoder_set_rice_parameter_search_dist (encoder, compression_levels_[value].rice_parameter_search_dist); return ok; } FLAC_API FLAC__bool FLAC__stream_encoder_set_blocksize(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->blocksize = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_do_mid_side_stereo(FLAC__StreamEncoder *encoder, FLAC__bool value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->do_mid_side_stereo = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_loose_mid_side_stereo(FLAC__StreamEncoder *encoder, FLAC__bool value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->loose_mid_side_stereo = value; return true; } /*@@@@add to tests*/ FLAC_API FLAC__bool FLAC__stream_encoder_set_apodization(FLAC__StreamEncoder *encoder, const char *specification) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); FLAC__ASSERT(0 != specification); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; #ifdef FLAC__INTEGER_ONLY_LIBRARY (void)specification; /* silently ignore since we haven't integerized; will always use a rectangular window */ #else encoder->protected_->num_apodizations = 0; while(1) { const char *s = strchr(specification, ';'); const size_t n = s? (size_t)(s - specification) : strlen(specification); if (n==8 && 0 == strncmp("bartlett" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_BARTLETT; else if(n==13 && 0 == strncmp("bartlett_hann", specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_BARTLETT_HANN; else if(n==8 && 0 == strncmp("blackman" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_BLACKMAN; else if(n==26 && 0 == strncmp("blackman_harris_4term_92db", specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_BLACKMAN_HARRIS_4TERM_92DB_SIDELOBE; else if(n==6 && 0 == strncmp("connes" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_CONNES; else if(n==7 && 0 == strncmp("flattop" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_FLATTOP; else if(n>7 && 0 == strncmp("gauss(" , specification, 6)) { FLAC__real stddev = (FLAC__real)strtod(specification+6, 0); if (stddev > 0.0 && stddev <= 0.5) { encoder->protected_->apodizations[encoder->protected_->num_apodizations].parameters.gauss.stddev = stddev; encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_GAUSS; } } else if(n==7 && 0 == strncmp("hamming" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_HAMMING; else if(n==4 && 0 == strncmp("hann" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_HANN; else if(n==13 && 0 == strncmp("kaiser_bessel", specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_KAISER_BESSEL; else if(n==7 && 0 == strncmp("nuttall" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_NUTTALL; else if(n==9 && 0 == strncmp("rectangle" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_RECTANGLE; else if(n==8 && 0 == strncmp("triangle" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_TRIANGLE; else if(n>7 && 0 == strncmp("tukey(" , specification, 6)) { FLAC__real p = (FLAC__real)strtod(specification+6, 0); if (p >= 0.0 && p <= 1.0) { encoder->protected_->apodizations[encoder->protected_->num_apodizations].parameters.tukey.p = p; encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_TUKEY; } } else if(n==5 && 0 == strncmp("welch" , specification, n)) encoder->protected_->apodizations[encoder->protected_->num_apodizations++].type = FLAC__APODIZATION_WELCH; if (encoder->protected_->num_apodizations == 32) break; if (s) specification = s+1; else break; } if(encoder->protected_->num_apodizations == 0) { encoder->protected_->num_apodizations = 1; encoder->protected_->apodizations[0].type = FLAC__APODIZATION_TUKEY; encoder->protected_->apodizations[0].parameters.tukey.p = 0.5; } #endif return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_max_lpc_order(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->max_lpc_order = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_qlp_coeff_precision(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->qlp_coeff_precision = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_do_qlp_coeff_prec_search(FLAC__StreamEncoder *encoder, FLAC__bool value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->do_qlp_coeff_prec_search = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_do_escape_coding(FLAC__StreamEncoder *encoder, FLAC__bool value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; #if 0 /*@@@ deprecated: */ encoder->protected_->do_escape_coding = value; #else (void)value; #endif return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_do_exhaustive_model_search(FLAC__StreamEncoder *encoder, FLAC__bool value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->do_exhaustive_model_search = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_min_residual_partition_order(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->min_residual_partition_order = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_max_residual_partition_order(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->max_residual_partition_order = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_rice_parameter_search_dist(FLAC__StreamEncoder *encoder, unsigned value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; #if 0 /*@@@ deprecated: */ encoder->protected_->rice_parameter_search_dist = value; #else (void)value; #endif return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_total_samples_estimate(FLAC__StreamEncoder *encoder, FLAC__uint64 value) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; encoder->protected_->total_samples_estimate = value; return true; } FLAC_API FLAC__bool FLAC__stream_encoder_set_metadata(FLAC__StreamEncoder *encoder, FLAC__StreamMetadata **metadata, unsigned num_blocks) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_UNINITIALIZED) return false; if(0 == metadata) num_blocks = 0; if(0 == num_blocks) metadata = 0; /* realloc() does not do exactly what we want so... */ if(encoder->protected_->metadata) { free(encoder->protected_->metadata); encoder->protected_->metadata = 0; encoder->protected_->num_metadata_blocks = 0; } if(num_blocks) { FLAC__StreamMetadata **m; if(0 == (m = (FLAC__StreamMetadata**)safe_malloc_mul_2op_(sizeof(m[0]), /*times*/num_blocks))) return false; memcpy(m, metadata, sizeof(m[0]) * num_blocks); encoder->protected_->metadata = m; encoder->protected_->num_metadata_blocks = num_blocks; } #if FLAC__HAS_OGG if(!FLAC__ogg_encoder_aspect_set_num_metadata(&encoder->protected_->ogg_encoder_aspect, num_blocks)) return false; #endif return true; } FLAC_API FLAC__StreamEncoderState FLAC__stream_encoder_get_state(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->state; } FLAC_API FLAC__StreamDecoderState FLAC__stream_encoder_get_verify_decoder_state(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->verify) return FLAC__stream_decoder_get_state(encoder->private_->verify.decoder); else return FLAC__STREAM_DECODER_UNINITIALIZED; } FLAC_API const char *FLAC__stream_encoder_get_resolved_state_string(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(encoder->protected_->state != FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR) return FLAC__StreamEncoderStateString[encoder->protected_->state]; else return FLAC__stream_decoder_get_resolved_state_string(encoder->private_->verify.decoder); } FLAC_API void FLAC__stream_encoder_get_verify_decoder_error_stats(const FLAC__StreamEncoder *encoder, FLAC__uint64 *absolute_sample, unsigned *frame_number, unsigned *channel, unsigned *sample, FLAC__int32 *expected, FLAC__int32 *got) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); if(0 != absolute_sample) *absolute_sample = encoder->private_->verify.error_stats.absolute_sample; if(0 != frame_number) *frame_number = encoder->private_->verify.error_stats.frame_number; if(0 != channel) *channel = encoder->private_->verify.error_stats.channel; if(0 != sample) *sample = encoder->private_->verify.error_stats.sample; if(0 != expected) *expected = encoder->private_->verify.error_stats.expected; if(0 != got) *got = encoder->private_->verify.error_stats.got; } FLAC_API FLAC__bool FLAC__stream_encoder_get_verify(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->verify; } FLAC_API FLAC__bool FLAC__stream_encoder_get_streamable_subset(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->streamable_subset; } FLAC_API unsigned FLAC__stream_encoder_get_channels(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->channels; } FLAC_API unsigned FLAC__stream_encoder_get_bits_per_sample(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->bits_per_sample; } FLAC_API unsigned FLAC__stream_encoder_get_sample_rate(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->sample_rate; } FLAC_API unsigned FLAC__stream_encoder_get_blocksize(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->blocksize; } FLAC_API FLAC__bool FLAC__stream_encoder_get_do_mid_side_stereo(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->do_mid_side_stereo; } FLAC_API FLAC__bool FLAC__stream_encoder_get_loose_mid_side_stereo(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->loose_mid_side_stereo; } FLAC_API unsigned FLAC__stream_encoder_get_max_lpc_order(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->max_lpc_order; } FLAC_API unsigned FLAC__stream_encoder_get_qlp_coeff_precision(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->qlp_coeff_precision; } FLAC_API FLAC__bool FLAC__stream_encoder_get_do_qlp_coeff_prec_search(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->do_qlp_coeff_prec_search; } FLAC_API FLAC__bool FLAC__stream_encoder_get_do_escape_coding(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->do_escape_coding; } FLAC_API FLAC__bool FLAC__stream_encoder_get_do_exhaustive_model_search(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->do_exhaustive_model_search; } FLAC_API unsigned FLAC__stream_encoder_get_min_residual_partition_order(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->min_residual_partition_order; } FLAC_API unsigned FLAC__stream_encoder_get_max_residual_partition_order(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->max_residual_partition_order; } FLAC_API unsigned FLAC__stream_encoder_get_rice_parameter_search_dist(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->rice_parameter_search_dist; } FLAC_API FLAC__uint64 FLAC__stream_encoder_get_total_samples_estimate(const FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); return encoder->protected_->total_samples_estimate; } FLAC_API FLAC__bool FLAC__stream_encoder_process(FLAC__StreamEncoder *encoder, const FLAC__int32 * const buffer[], unsigned samples) { unsigned i, j = 0, channel; const unsigned channels = encoder->protected_->channels, blocksize = encoder->protected_->blocksize; FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); FLAC__ASSERT(encoder->protected_->state == FLAC__STREAM_ENCODER_OK); do { const unsigned n = min(blocksize+OVERREAD_-encoder->private_->current_sample_number, samples-j); if(encoder->protected_->verify) append_to_verify_fifo_(&encoder->private_->verify.input_fifo, buffer, j, channels, n); for(channel = 0; channel < channels; channel++) memcpy(&encoder->private_->integer_signal[channel][encoder->private_->current_sample_number], &buffer[channel][j], sizeof(buffer[channel][0]) * n); if(encoder->protected_->do_mid_side_stereo) { FLAC__ASSERT(channels == 2); /* "i <= blocksize" to overread 1 sample; see comment in OVERREAD_ decl */ for(i = encoder->private_->current_sample_number; i <= blocksize && j < samples; i++, j++) { encoder->private_->integer_signal_mid_side[1][i] = buffer[0][j] - buffer[1][j]; encoder->private_->integer_signal_mid_side[0][i] = (buffer[0][j] + buffer[1][j]) >> 1; /* NOTE: not the same as 'mid = (buffer[0][j] + buffer[1][j]) / 2' ! */ } } else j += n; encoder->private_->current_sample_number += n; /* we only process if we have a full block + 1 extra sample; final block is always handled by FLAC__stream_encoder_finish() */ if(encoder->private_->current_sample_number > blocksize) { FLAC__ASSERT(encoder->private_->current_sample_number == blocksize+OVERREAD_); FLAC__ASSERT(OVERREAD_ == 1); /* assert we only overread 1 sample which simplifies the rest of the code below */ if(!process_frame_(encoder, /*is_fractional_block=*/false, /*is_last_block=*/false)) return false; /* move unprocessed overread samples to beginnings of arrays */ for(channel = 0; channel < channels; channel++) encoder->private_->integer_signal[channel][0] = encoder->private_->integer_signal[channel][blocksize]; if(encoder->protected_->do_mid_side_stereo) { encoder->private_->integer_signal_mid_side[0][0] = encoder->private_->integer_signal_mid_side[0][blocksize]; encoder->private_->integer_signal_mid_side[1][0] = encoder->private_->integer_signal_mid_side[1][blocksize]; } encoder->private_->current_sample_number = 1; } } while(j < samples); return true; } FLAC_API FLAC__bool FLAC__stream_encoder_process_interleaved(FLAC__StreamEncoder *encoder, const FLAC__int32 buffer[], unsigned samples) { unsigned i, j, k, channel; FLAC__int32 x, mid, side; const unsigned channels = encoder->protected_->channels, blocksize = encoder->protected_->blocksize; FLAC__ASSERT(0 != encoder); FLAC__ASSERT(0 != encoder->private_); FLAC__ASSERT(0 != encoder->protected_); FLAC__ASSERT(encoder->protected_->state == FLAC__STREAM_ENCODER_OK); j = k = 0; /* * we have several flavors of the same basic loop, optimized for * different conditions: */ if(encoder->protected_->do_mid_side_stereo && channels == 2) { /* * stereo coding: unroll channel loop */ do { if(encoder->protected_->verify) append_to_verify_fifo_interleaved_(&encoder->private_->verify.input_fifo, buffer, j, channels, min(blocksize+OVERREAD_-encoder->private_->current_sample_number, samples-j)); /* "i <= blocksize" to overread 1 sample; see comment in OVERREAD_ decl */ for(i = encoder->private_->current_sample_number; i <= blocksize && j < samples; i++, j++) { encoder->private_->integer_signal[0][i] = mid = side = buffer[k++]; x = buffer[k++]; encoder->private_->integer_signal[1][i] = x; mid += x; side -= x; mid >>= 1; /* NOTE: not the same as 'mid = (left + right) / 2' ! */ encoder->private_->integer_signal_mid_side[1][i] = side; encoder->private_->integer_signal_mid_side[0][i] = mid; } encoder->private_->current_sample_number = i; /* we only process if we have a full block + 1 extra sample; final block is always handled by FLAC__stream_encoder_finish() */ if(i > blocksize) { if(!process_frame_(encoder, /*is_fractional_block=*/false, /*is_last_block=*/false)) return false; /* move unprocessed overread samples to beginnings of arrays */ FLAC__ASSERT(i == blocksize+OVERREAD_); FLAC__ASSERT(OVERREAD_ == 1); /* assert we only overread 1 sample which simplifies the rest of the code below */ encoder->private_->integer_signal[0][0] = encoder->private_->integer_signal[0][blocksize]; encoder->private_->integer_signal[1][0] = encoder->private_->integer_signal[1][blocksize]; encoder->private_->integer_signal_mid_side[0][0] = encoder->private_->integer_signal_mid_side[0][blocksize]; encoder->private_->integer_signal_mid_side[1][0] = encoder->private_->integer_signal_mid_side[1][blocksize]; encoder->private_->current_sample_number = 1; } } while(j < samples); } else { /* * independent channel coding: buffer each channel in inner loop */ do { if(encoder->protected_->verify) append_to_verify_fifo_interleaved_(&encoder->private_->verify.input_fifo, buffer, j, channels, min(blocksize+OVERREAD_-encoder->private_->current_sample_number, samples-j)); /* "i <= blocksize" to overread 1 sample; see comment in OVERREAD_ decl */ for(i = encoder->private_->current_sample_number; i <= blocksize && j < samples; i++, j++) { for(channel = 0; channel < channels; channel++) encoder->private_->integer_signal[channel][i] = buffer[k++]; } encoder->private_->current_sample_number = i; /* we only process if we have a full block + 1 extra sample; final block is always handled by FLAC__stream_encoder_finish() */ if(i > blocksize) { if(!process_frame_(encoder, /*is_fractional_block=*/false, /*is_last_block=*/false)) return false; /* move unprocessed overread samples to beginnings of arrays */ FLAC__ASSERT(i == blocksize+OVERREAD_); FLAC__ASSERT(OVERREAD_ == 1); /* assert we only overread 1 sample which simplifies the rest of the code below */ for(channel = 0; channel < channels; channel++) encoder->private_->integer_signal[channel][0] = encoder->private_->integer_signal[channel][blocksize]; encoder->private_->current_sample_number = 1; } } while(j < samples); } return true; } /*********************************************************************** * * Private class methods * ***********************************************************************/ void set_defaults_(FLAC__StreamEncoder *encoder) { FLAC__ASSERT(0 != encoder); #ifdef FLAC__MANDATORY_VERIFY_WHILE_ENCODING encoder->protected_->verify = true; #else encoder->protected_->verify = false; #endif encoder->protected_->streamable_subset = true; encoder->protected_->do_md5 = true; encoder->protected_->do_mid_side_stereo = false; encoder->protected_->loose_mid_side_stereo = false; encoder->protected_->channels = 2; encoder->protected_->bits_per_sample = 16; encoder->protected_->sample_rate = 44100; encoder->protected_->blocksize = 0; #ifndef FLAC__INTEGER_ONLY_LIBRARY encoder->protected_->num_apodizations = 1; encoder->protected_->apodizations[0].type = FLAC__APODIZATION_TUKEY; encoder->protected_->apodizations[0].parameters.tukey.p = 0.5; #endif encoder->protected_->max_lpc_order = 0; encoder->protected_->qlp_coeff_precision = 0; encoder->protected_->do_qlp_coeff_prec_search = false; encoder->protected_->do_exhaustive_model_search = false; encoder->protected_->do_escape_coding = false; encoder->protected_->min_residual_partition_order = 0; encoder->protected_->max_residual_partition_order = 0; encoder->protected_->rice_parameter_search_dist = 0; encoder->protected_->total_samples_estimate = 0; encoder->protected_->metadata = 0; encoder->protected_->num_metadata_blocks = 0; encoder->private_->seek_table = 0; encoder->private_->disable_constant_subframes = false; encoder->private_->disable_fixed_subframes = false; encoder->private_->disable_verbatim_subframes = false; #if FLAC__HAS_OGG encoder->private_->is_ogg = false; #endif encoder->private_->read_callback = 0; encoder->private_->write_callback = 0; encoder->private_->seek_callback = 0; encoder->private_->tell_callback = 0; encoder->private_->metadata_callback = 0; encoder->private_->progress_callback = 0; encoder->private_->client_data = 0; #if FLAC__HAS_OGG FLAC__ogg_encoder_aspect_set_defaults(&encoder->protected_->ogg_encoder_aspect); #endif } void free_(FLAC__StreamEncoder *encoder) { unsigned i, channel; FLAC__ASSERT(0 != encoder); if(encoder->protected_->metadata) { free(encoder->protected_->metadata); encoder->protected_->metadata = 0; encoder->protected_->num_metadata_blocks = 0; } for(i = 0; i < encoder->protected_->channels; i++) { if(0 != encoder->private_->integer_signal_unaligned[i]) { free(encoder->private_->integer_signal_unaligned[i]); encoder->private_->integer_signal_unaligned[i] = 0; } #ifndef FLAC__INTEGER_ONLY_LIBRARY if(0 != encoder->private_->real_signal_unaligned[i]) { free(encoder->private_->real_signal_unaligned[i]); encoder->private_->real_signal_unaligned[i] = 0; } #endif } for(i = 0; i < 2; i++) { if(0 != encoder->private_->integer_signal_mid_side_unaligned[i]) { free(encoder->private_->integer_signal_mid_side_unaligned[i]); encoder->private_->integer_signal_mid_side_unaligned[i] = 0; } #ifndef FLAC__INTEGER_ONLY_LIBRARY if(0 != encoder->private_->real_signal_mid_side_unaligned[i]) { free(encoder->private_->real_signal_mid_side_unaligned[i]); encoder->private_->real_signal_mid_side_unaligned[i] = 0; } #endif } #ifndef FLAC__INTEGER_ONLY_LIBRARY for(i = 0; i < encoder->protected_->num_apodizations; i++) { if(0 != encoder->private_->window_unaligned[i]) { free(encoder->private_->window_unaligned[i]); encoder->private_->window_unaligned[i] = 0; } } if(0 != encoder->private_->windowed_signal_unaligned) { free(encoder->private_->windowed_signal_unaligned); encoder->private_->windowed_signal_unaligned = 0; } #endif for(channel = 0; channel < encoder->protected_->channels; channel++) { for(i = 0; i < 2; i++) { if(0 != encoder->private_->residual_workspace_unaligned[channel][i]) { free(encoder->private_->residual_workspace_unaligned[channel][i]); encoder->private_->residual_workspace_unaligned[channel][i] = 0; } } } for(channel = 0; channel < 2; channel++) { for(i = 0; i < 2; i++) { if(0 != encoder->private_->residual_workspace_mid_side_unaligned[channel][i]) { free(encoder->private_->residual_workspace_mid_side_unaligned[channel][i]); encoder->private_->residual_workspace_mid_side_unaligned[channel][i] = 0; } } } if(0 != encoder->private_->abs_residual_partition_sums_unaligned) { free(encoder->private_->abs_residual_partition_sums_unaligned); encoder->private_->abs_residual_partition_sums_unaligned = 0; } if(0 != encoder->private_->raw_bits_per_partition_unaligned) { free(encoder->private_->raw_bits_per_partition_unaligned); encoder->private_->raw_bits_per_partition_unaligned = 0; } if(encoder->protected_->verify) { for(i = 0; i < encoder->protected_->channels; i++) { if(0 != encoder->private_->verify.input_fifo.data[i]) { free(encoder->private_->verify.input_fifo.data[i]); encoder->private_->verify.input_fifo.data[i] = 0; } } } FLAC__bitwriter_free(encoder->private_->frame); } FLAC__bool resize_buffers_(FLAC__StreamEncoder *encoder, unsigned new_blocksize) { FLAC__bool ok; unsigned i, channel; FLAC__ASSERT(new_blocksize > 0); FLAC__ASSERT(encoder->protected_->state == FLAC__STREAM_ENCODER_OK); FLAC__ASSERT(encoder->private_->current_sample_number == 0); /* To avoid excessive malloc'ing, we only grow the buffer; no shrinking. */ if(new_blocksize <= encoder->private_->input_capacity) return true; ok = true; /* WATCHOUT: FLAC__lpc_compute_residual_from_qlp_coefficients_asm_ia32_mmx() * requires that the input arrays (in our case the integer signals) * have a buffer of up to 3 zeroes in front (at negative indices) for * alignment purposes; we use 4 in front to keep the data well-aligned. */ for(i = 0; ok && i < encoder->protected_->channels; i++) { ok = ok && FLAC__memory_alloc_aligned_int32_array(new_blocksize+4+OVERREAD_, &encoder->private_->integer_signal_unaligned[i], &encoder->private_->integer_signal[i]); memset(encoder->private_->integer_signal[i], 0, sizeof(FLAC__int32)*4); encoder->private_->integer_signal[i] += 4; #ifndef FLAC__INTEGER_ONLY_LIBRARY #if 0 /* @@@ currently unused */ if(encoder->protected_->max_lpc_order > 0) ok = ok && FLAC__memory_alloc_aligned_real_array(new_blocksize+OVERREAD_, &encoder->private_->real_signal_unaligned[i], &encoder->private_->real_signal[i]); #endif #endif } for(i = 0; ok && i < 2; i++) { ok = ok && FLAC__memory_alloc_aligned_int32_array(new_blocksize+4+OVERREAD_, &encoder->private_->integer_signal_mid_side_unaligned[i], &encoder->private_->integer_signal_mid_side[i]); memset(encoder->private_->integer_signal_mid_side[i], 0, sizeof(FLAC__int32)*4); encoder->private_->integer_signal_mid_side[i] += 4; #ifndef FLAC__INTEGER_ONLY_LIBRARY #if 0 /* @@@ currently unused */ if(encoder->protected_->max_lpc_order > 0) ok = ok && FLAC__memory_alloc_aligned_real_array(new_blocksize+OVERREAD_, &encoder->private_->real_signal_mid_side_unaligned[i], &encoder->private_->real_signal_mid_side[i]); #endif #endif } #ifndef FLAC__INTEGER_ONLY_LIBRARY if(ok && encoder->protected_->max_lpc_order > 0) { for(i = 0; ok && i < encoder->protected_->num_apodizations; i++) ok = ok && FLAC__memory_alloc_aligned_real_array(new_blocksize, &encoder->private_->window_unaligned[i], &encoder->private_->window[i]); ok = ok && FLAC__memory_alloc_aligned_real_array(new_blocksize, &encoder->private_->windowed_signal_unaligned, &encoder->private_->windowed_signal); } #endif for(channel = 0; ok && channel < encoder->protected_->channels; channel++) { for(i = 0; ok && i < 2; i++) { ok = ok && FLAC__memory_alloc_aligned_int32_array(new_blocksize, &encoder->private_->residual_workspace_unaligned[channel][i], &encoder->private_->residual_workspace[channel][i]); } } for(channel = 0; ok && channel < 2; channel++) { for(i = 0; ok && i < 2; i++) { ok = ok && FLAC__memory_alloc_aligned_int32_array(new_blocksize, &encoder->private_->residual_workspace_mid_side_unaligned[channel][i], &encoder->private_->residual_workspace_mid_side[channel][i]); } } /* the *2 is an approximation to the series 1 + 1/2 + 1/4 + ... that sums tree occupies in a flat array */ /*@@@ new_blocksize*2 is too pessimistic, but to fix, we need smarter logic because a smaller new_blocksize can actually increase the # of partitions; would require moving this out into a separate function, then checking its capacity against the need of the current blocksize&min/max_partition_order (and maybe predictor order) */ ok = ok && FLAC__memory_alloc_aligned_uint64_array(new_blocksize * 2, &encoder->private_->abs_residual_partition_sums_unaligned, &encoder->private_->abs_residual_partition_sums); if(encoder->protected_->do_escape_coding) ok = ok && FLAC__memory_alloc_aligned_unsigned_array(new_blocksize * 2, &encoder->private_->raw_bits_per_partition_unaligned, &encoder->private_->raw_bits_per_partition); /* now adjust the windows if the blocksize has changed */ #ifndef FLAC__INTEGER_ONLY_LIBRARY if(ok && new_blocksize != encoder->private_->input_capacity && encoder->protected_->max_lpc_order > 0) { for(i = 0; ok && i < encoder->protected_->num_apodizations; i++) { switch(encoder->protected_->apodizations[i].type) { case FLAC__APODIZATION_BARTLETT: FLAC__window_bartlett(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_BARTLETT_HANN: FLAC__window_bartlett_hann(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_BLACKMAN: FLAC__window_blackman(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_BLACKMAN_HARRIS_4TERM_92DB_SIDELOBE: FLAC__window_blackman_harris_4term_92db_sidelobe(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_CONNES: FLAC__window_connes(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_FLATTOP: FLAC__window_flattop(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_GAUSS: FLAC__window_gauss(encoder->private_->window[i], new_blocksize, encoder->protected_->apodizations[i].parameters.gauss.stddev); break; case FLAC__APODIZATION_HAMMING: FLAC__window_hamming(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_HANN: FLAC__window_hann(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_KAISER_BESSEL: FLAC__window_kaiser_bessel(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_NUTTALL: FLAC__window_nuttall(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_RECTANGLE: FLAC__window_rectangle(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_TRIANGLE: FLAC__window_triangle(encoder->private_->window[i], new_blocksize); break; case FLAC__APODIZATION_TUKEY: FLAC__window_tukey(encoder->private_->window[i], new_blocksize, encoder->protected_->apodizations[i].parameters.tukey.p); break; case FLAC__APODIZATION_WELCH: FLAC__window_welch(encoder->private_->window[i], new_blocksize); break; default: FLAC__ASSERT(0); /* double protection */ FLAC__window_hann(encoder->private_->window[i], new_blocksize); break; } } } #endif if(ok) encoder->private_->input_capacity = new_blocksize; else encoder->protected_->state = FLAC__STREAM_ENCODER_MEMORY_ALLOCATION_ERROR; return ok; } FLAC__bool write_bitbuffer_(FLAC__StreamEncoder *encoder, unsigned samples, FLAC__bool is_last_block) { const FLAC__byte *buffer; size_t bytes; FLAC__ASSERT(FLAC__bitwriter_is_byte_aligned(encoder->private_->frame)); if(!FLAC__bitwriter_get_buffer(encoder->private_->frame, &buffer, &bytes)) { encoder->protected_->state = FLAC__STREAM_ENCODER_MEMORY_ALLOCATION_ERROR; return false; } if(encoder->protected_->verify) { encoder->private_->verify.output.data = buffer; encoder->private_->verify.output.bytes = bytes; if(encoder->private_->verify.state_hint == ENCODER_IN_MAGIC) { encoder->private_->verify.needs_magic_hack = true; } else { if(!FLAC__stream_decoder_process_single(encoder->private_->verify.decoder)) { FLAC__bitwriter_release_buffer(encoder->private_->frame); FLAC__bitwriter_clear(encoder->private_->frame); if(encoder->protected_->state != FLAC__STREAM_ENCODER_VERIFY_MISMATCH_IN_AUDIO_DATA) encoder->protected_->state = FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR; return false; } } } if(write_frame_(encoder, buffer, bytes, samples, is_last_block) != FLAC__STREAM_ENCODER_WRITE_STATUS_OK) { FLAC__bitwriter_release_buffer(encoder->private_->frame); FLAC__bitwriter_clear(encoder->private_->frame); encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return false; } FLAC__bitwriter_release_buffer(encoder->private_->frame); FLAC__bitwriter_clear(encoder->private_->frame); if(samples > 0) { encoder->private_->streaminfo.data.stream_info.min_framesize = min(bytes, encoder->private_->streaminfo.data.stream_info.min_framesize); encoder->private_->streaminfo.data.stream_info.max_framesize = max(bytes, encoder->private_->streaminfo.data.stream_info.max_framesize); } return true; } FLAC__StreamEncoderWriteStatus write_frame_(FLAC__StreamEncoder *encoder, const FLAC__byte buffer[], size_t bytes, unsigned samples, FLAC__bool is_last_block) { (void) is_last_block; FLAC__StreamEncoderWriteStatus status; FLAC__uint64 output_position = 0; /* FLAC__STREAM_ENCODER_TELL_STATUS_UNSUPPORTED just means we didn't get the offset; no error */ if(encoder->private_->tell_callback && encoder->private_->tell_callback(encoder, &output_position, encoder->private_->client_data) == FLAC__STREAM_ENCODER_TELL_STATUS_ERROR) { encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return FLAC__STREAM_ENCODER_WRITE_STATUS_FATAL_ERROR; } /* * Watch for the STREAMINFO block and first SEEKTABLE block to go by and store their offsets. */ if(samples == 0) { FLAC__MetadataType type = (buffer[0] & 0x7f); if(type == FLAC__METADATA_TYPE_STREAMINFO) encoder->protected_->streaminfo_offset = output_position; else if(type == FLAC__METADATA_TYPE_SEEKTABLE && encoder->protected_->seektable_offset == 0) encoder->protected_->seektable_offset = output_position; } /* * Mark the current seek point if hit (if audio_offset == 0 that * means we're still writing metadata and haven't hit the first * frame yet) */ if(0 != encoder->private_->seek_table && encoder->protected_->audio_offset > 0 && encoder->private_->seek_table->num_points > 0) { const unsigned blocksize = FLAC__stream_encoder_get_blocksize(encoder); const FLAC__uint64 frame_first_sample = encoder->private_->samples_written; const FLAC__uint64 frame_last_sample = frame_first_sample + (FLAC__uint64)blocksize - 1; FLAC__uint64 test_sample; unsigned i; for(i = encoder->private_->first_seekpoint_to_check; i < encoder->private_->seek_table->num_points; i++) { test_sample = encoder->private_->seek_table->points[i].sample_number; if(test_sample > frame_last_sample) { break; } else if(test_sample >= frame_first_sample) { encoder->private_->seek_table->points[i].sample_number = frame_first_sample; encoder->private_->seek_table->points[i].stream_offset = output_position - encoder->protected_->audio_offset; encoder->private_->seek_table->points[i].frame_samples = blocksize; encoder->private_->first_seekpoint_to_check++; /* DO NOT: "break;" and here's why: * The seektable template may contain more than one target * sample for any given frame; we will keep looping, generating * duplicate seekpoints for them, and we'll clean it up later, * just before writing the seektable back to the metadata. */ } else { encoder->private_->first_seekpoint_to_check++; } } } #if FLAC__HAS_OGG if(encoder->private_->is_ogg) { status = FLAC__ogg_encoder_aspect_write_callback_wrapper( &encoder->protected_->ogg_encoder_aspect, buffer, bytes, samples, encoder->private_->current_frame_number, is_last_block, (FLAC__OggEncoderAspectWriteCallbackProxy)encoder->private_->write_callback, encoder, encoder->private_->client_data ); } else #endif status = encoder->private_->write_callback(encoder, buffer, bytes, samples, encoder->private_->current_frame_number, encoder->private_->client_data); if(status == FLAC__STREAM_ENCODER_WRITE_STATUS_OK) { encoder->private_->bytes_written += bytes; encoder->private_->samples_written += samples; /* we keep a high watermark on the number of frames written because * when the encoder goes back to write metadata, 'current_frame' * will drop back to 0. */ encoder->private_->frames_written = max(encoder->private_->frames_written, encoder->private_->current_frame_number+1); } else encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return status; } /* Gets called when the encoding process has finished so that we can update the STREAMINFO and SEEKTABLE blocks. */ void update_metadata_(const FLAC__StreamEncoder *encoder) { FLAC__byte b[max(6, FLAC__STREAM_METADATA_SEEKPOINT_LENGTH)]; const FLAC__StreamMetadata *metadata = &encoder->private_->streaminfo; const FLAC__uint64 samples = metadata->data.stream_info.total_samples; const unsigned min_framesize = metadata->data.stream_info.min_framesize; const unsigned max_framesize = metadata->data.stream_info.max_framesize; const unsigned bps = metadata->data.stream_info.bits_per_sample; FLAC__StreamEncoderSeekStatus seek_status; FLAC__ASSERT(metadata->type == FLAC__METADATA_TYPE_STREAMINFO); /* All this is based on intimate knowledge of the stream header * layout, but a change to the header format that would break this * would also break all streams encoded in the previous format. */ /* * Write MD5 signature */ { const unsigned md5_offset = FLAC__STREAM_METADATA_HEADER_LENGTH + ( FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_SAMPLE_RATE_LEN + FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN + FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN + FLAC__STREAM_METADATA_STREAMINFO_TOTAL_SAMPLES_LEN ) / 8; if((seek_status = encoder->private_->seek_callback(encoder, encoder->protected_->streaminfo_offset + md5_offset, encoder->private_->client_data)) != FLAC__STREAM_ENCODER_SEEK_STATUS_OK) { if(seek_status == FLAC__STREAM_ENCODER_SEEK_STATUS_ERROR) encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return; } if(encoder->private_->write_callback(encoder, metadata->data.stream_info.md5sum, 16, 0, 0, encoder->private_->client_data) != FLAC__STREAM_ENCODER_WRITE_STATUS_OK) { encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return; } } /* * Write total samples */ { const unsigned total_samples_byte_offset = FLAC__STREAM_METADATA_HEADER_LENGTH + ( FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_SAMPLE_RATE_LEN + FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN + FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN - 4 ) / 8; b[0] = ((FLAC__byte)(bps-1) << 4) | (FLAC__byte)((samples >> 32) & 0x0F); b[1] = (FLAC__byte)((samples >> 24) & 0xFF); b[2] = (FLAC__byte)((samples >> 16) & 0xFF); b[3] = (FLAC__byte)((samples >> 8) & 0xFF); b[4] = (FLAC__byte)(samples & 0xFF); if((seek_status = encoder->private_->seek_callback(encoder, encoder->protected_->streaminfo_offset + total_samples_byte_offset, encoder->private_->client_data)) != FLAC__STREAM_ENCODER_SEEK_STATUS_OK) { if(seek_status == FLAC__STREAM_ENCODER_SEEK_STATUS_ERROR) encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return; } if(encoder->private_->write_callback(encoder, b, 5, 0, 0, encoder->private_->client_data) != FLAC__STREAM_ENCODER_WRITE_STATUS_OK) { encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return; } } /* * Write min/max framesize */ { const unsigned min_framesize_offset = FLAC__STREAM_METADATA_HEADER_LENGTH + ( FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN ) / 8; b[0] = (FLAC__byte)((min_framesize >> 16) & 0xFF); b[1] = (FLAC__byte)((min_framesize >> 8) & 0xFF); b[2] = (FLAC__byte)(min_framesize & 0xFF); b[3] = (FLAC__byte)((max_framesize >> 16) & 0xFF); b[4] = (FLAC__byte)((max_framesize >> 8) & 0xFF); b[5] = (FLAC__byte)(max_framesize & 0xFF); if((seek_status = encoder->private_->seek_callback(encoder, encoder->protected_->streaminfo_offset + min_framesize_offset, encoder->private_->client_data)) != FLAC__STREAM_ENCODER_SEEK_STATUS_OK) { if(seek_status == FLAC__STREAM_ENCODER_SEEK_STATUS_ERROR) encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return; } if(encoder->private_->write_callback(encoder, b, 6, 0, 0, encoder->private_->client_data) != FLAC__STREAM_ENCODER_WRITE_STATUS_OK) { encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return; } } /* * Write seektable */ if(0 != encoder->private_->seek_table && encoder->private_->seek_table->num_points > 0 && encoder->protected_->seektable_offset > 0) { unsigned i; FLAC__format_seektable_sort(encoder->private_->seek_table); FLAC__ASSERT(FLAC__format_seektable_is_legal(encoder->private_->seek_table)); if((seek_status = encoder->private_->seek_callback(encoder, encoder->protected_->seektable_offset + FLAC__STREAM_METADATA_HEADER_LENGTH, encoder->private_->client_data)) != FLAC__STREAM_ENCODER_SEEK_STATUS_OK) { if(seek_status == FLAC__STREAM_ENCODER_SEEK_STATUS_ERROR) encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return; } for(i = 0; i < encoder->private_->seek_table->num_points; i++) { FLAC__uint64 xx; unsigned x; xx = encoder->private_->seek_table->points[i].sample_number; b[7] = (FLAC__byte)xx; xx >>= 8; b[6] = (FLAC__byte)xx; xx >>= 8; b[5] = (FLAC__byte)xx; xx >>= 8; b[4] = (FLAC__byte)xx; xx >>= 8; b[3] = (FLAC__byte)xx; xx >>= 8; b[2] = (FLAC__byte)xx; xx >>= 8; b[1] = (FLAC__byte)xx; xx >>= 8; b[0] = (FLAC__byte)xx; xx >>= 8; xx = encoder->private_->seek_table->points[i].stream_offset; b[15] = (FLAC__byte)xx; xx >>= 8; b[14] = (FLAC__byte)xx; xx >>= 8; b[13] = (FLAC__byte)xx; xx >>= 8; b[12] = (FLAC__byte)xx; xx >>= 8; b[11] = (FLAC__byte)xx; xx >>= 8; b[10] = (FLAC__byte)xx; xx >>= 8; b[9] = (FLAC__byte)xx; xx >>= 8; b[8] = (FLAC__byte)xx; xx >>= 8; x = encoder->private_->seek_table->points[i].frame_samples; b[17] = (FLAC__byte)x; x >>= 8; b[16] = (FLAC__byte)x; x >>= 8; if(encoder->private_->write_callback(encoder, b, 18, 0, 0, encoder->private_->client_data) != FLAC__STREAM_ENCODER_WRITE_STATUS_OK) { encoder->protected_->state = FLAC__STREAM_ENCODER_CLIENT_ERROR; return; } } } } #if FLAC__HAS_OGG /* Gets called when the encoding process has finished so that we can update the STREAMINFO and SEEKTABLE blocks. */ void update_ogg_metadata_(FLAC__StreamEncoder *encoder) { /* the # of bytes in the 1st packet that precede the STREAMINFO */ static const unsigned FIRST_OGG_PACKET_STREAMINFO_PREFIX_LENGTH = FLAC__OGG_MAPPING_PACKET_TYPE_LENGTH + FLAC__OGG_MAPPING_MAGIC_LENGTH + FLAC__OGG_MAPPING_VERSION_MAJOR_LENGTH + FLAC__OGG_MAPPING_VERSION_MINOR_LENGTH + FLAC__OGG_MAPPING_NUM_HEADERS_LENGTH + FLAC__STREAM_SYNC_LENGTH ; FLAC__byte b[max(6, FLAC__STREAM_METADATA_SEEKPOINT_LENGTH)]; const FLAC__StreamMetadata *metadata = &encoder->private_->streaminfo; const FLAC__uint64 samples = metadata->data.stream_info.total_samples; const unsigned min_framesize = metadata->data.stream_info.min_framesize; const unsigned max_framesize = metadata->data.stream_info.max_framesize; ogg_page page; FLAC__ASSERT(metadata->type == FLAC__METADATA_TYPE_STREAMINFO); FLAC__ASSERT(0 != encoder->private_->seek_callback); /* Pre-check that client supports seeking, since we don't want the * ogg_helper code to ever have to deal with this condition. */ if(encoder->private_->seek_callback(encoder, 0, encoder->private_->client_data) == FLAC__STREAM_ENCODER_SEEK_STATUS_UNSUPPORTED) return; /* All this is based on intimate knowledge of the stream header * layout, but a change to the header format that would break this * would also break all streams encoded in the previous format. */ /** ** Write STREAMINFO stats **/ simple_ogg_page__init(&page); if(!simple_ogg_page__get_at(encoder, encoder->protected_->streaminfo_offset, &page, encoder->private_->seek_callback, encoder->private_->read_callback, encoder->private_->client_data)) { simple_ogg_page__clear(&page); return; /* state already set */ } /* * Write MD5 signature */ { const unsigned md5_offset = FIRST_OGG_PACKET_STREAMINFO_PREFIX_LENGTH + FLAC__STREAM_METADATA_HEADER_LENGTH + ( FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_SAMPLE_RATE_LEN + FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN + FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN + FLAC__STREAM_METADATA_STREAMINFO_TOTAL_SAMPLES_LEN ) / 8; if(md5_offset + 16 > (unsigned)page.body_len) { encoder->protected_->state = FLAC__STREAM_ENCODER_OGG_ERROR; simple_ogg_page__clear(&page); return; } memcpy(page.body + md5_offset, metadata->data.stream_info.md5sum, 16); } /* * Write total samples */ { const unsigned total_samples_byte_offset = FIRST_OGG_PACKET_STREAMINFO_PREFIX_LENGTH + FLAC__STREAM_METADATA_HEADER_LENGTH + ( FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_SAMPLE_RATE_LEN + FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN + FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN - 4 ) / 8; if(total_samples_byte_offset + 5 > (unsigned)page.body_len) { encoder->protected_->state = FLAC__STREAM_ENCODER_OGG_ERROR; simple_ogg_page__clear(&page); return; } b[0] = (FLAC__byte)page.body[total_samples_byte_offset] & 0xF0; b[0] |= (FLAC__byte)((samples >> 32) & 0x0F); b[1] = (FLAC__byte)((samples >> 24) & 0xFF); b[2] = (FLAC__byte)((samples >> 16) & 0xFF); b[3] = (FLAC__byte)((samples >> 8) & 0xFF); b[4] = (FLAC__byte)(samples & 0xFF); memcpy(page.body + total_samples_byte_offset, b, 5); } /* * Write min/max framesize */ { const unsigned min_framesize_offset = FIRST_OGG_PACKET_STREAMINFO_PREFIX_LENGTH + FLAC__STREAM_METADATA_HEADER_LENGTH + ( FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN + FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN ) / 8; if(min_framesize_offset + 6 > (unsigned)page.body_len) { encoder->protected_->state = FLAC__STREAM_ENCODER_OGG_ERROR; simple_ogg_page__clear(&page); return; } b[0] = (FLAC__byte)((min_framesize >> 16) & 0xFF); b[1] = (FLAC__byte)((min_framesize >> 8) & 0xFF); b[2] = (FLAC__byte)(min_framesize & 0xFF); b[3] = (FLAC__byte)((max_framesize >> 16) & 0xFF); b[4] = (FLAC__byte)((max_framesize >> 8) & 0xFF); b[5] = (FLAC__byte)(max_framesize & 0xFF); memcpy(page.body + min_framesize_offset, b, 6); } if(!simple_ogg_page__set_at(encoder, encoder->protected_->streaminfo_offset, &page, encoder->private_->seek_callback, encoder->private_->write_callback, encoder->private_->client_data)) { simple_ogg_page__clear(&page); return; /* state already set */ } simple_ogg_page__clear(&page); /* * Write seektable */ if(0 != encoder->private_->seek_table && encoder->private_->seek_table->num_points > 0 && encoder->protected_->seektable_offset > 0) { unsigned i; FLAC__byte *p; FLAC__format_seektable_sort(encoder->private_->seek_table); FLAC__ASSERT(FLAC__format_seektable_is_legal(encoder->private_->seek_table)); simple_ogg_page__init(&page); if(!simple_ogg_page__get_at(encoder, encoder->protected_->seektable_offset, &page, encoder->private_->seek_callback, encoder->private_->read_callback, encoder->private_->client_data)) { simple_ogg_page__clear(&page); return; /* state already set */ } if((FLAC__STREAM_METADATA_HEADER_LENGTH + 18*encoder->private_->seek_table->num_points) != (unsigned)page.body_len) { encoder->protected_->state = FLAC__STREAM_ENCODER_OGG_ERROR; simple_ogg_page__clear(&page); return; } for(i = 0, p = page.body + FLAC__STREAM_METADATA_HEADER_LENGTH; i < encoder->private_->seek_table->num_points; i++, p += 18) { FLAC__uint64 xx; unsigned x; xx = encoder->private_->seek_table->points[i].sample_number; b[7] = (FLAC__byte)xx; xx >>= 8; b[6] = (FLAC__byte)xx; xx >>= 8; b[5] = (FLAC__byte)xx; xx >>= 8; b[4] = (FLAC__byte)xx; xx >>= 8; b[3] = (FLAC__byte)xx; xx >>= 8; b[2] = (FLAC__byte)xx; xx >>= 8; b[1] = (FLAC__byte)xx; xx >>= 8; b[0] = (FLAC__byte)xx; xx >>= 8; xx = encoder->private_->seek_table->points[i].stream_offset; b[15] = (FLAC__byte)xx; xx >>= 8; b[14] = (FLAC__byte)xx; xx >>= 8; b[13] = (FLAC__byte)xx; xx >>= 8; b[12] = (FLAC__byte)xx; xx >>= 8; b[11] = (FLAC__byte)xx; xx >>= 8; b[10] = (FLAC__byte)xx; xx >>= 8; b[9] = (FLAC__byte)xx; xx >>= 8; b[8] = (FLAC__byte)xx; xx >>= 8; x = encoder->private_->seek_table->points[i].frame_samples; b[17] = (FLAC__byte)x; x >>= 8; b[16] = (FLAC__byte)x; x >>= 8; memcpy(p, b, 18); } if(!simple_ogg_page__set_at(encoder, encoder->protected_->seektable_offset, &page, encoder->private_->seek_callback, encoder->private_->write_callback, encoder->private_->client_data)) { simple_ogg_page__clear(&page); return; /* state already set */ } simple_ogg_page__clear(&page); } } #endif FLAC__bool process_frame_(FLAC__StreamEncoder *encoder, FLAC__bool is_fractional_block, FLAC__bool is_last_block) { FLAC__uint16 crc; FLAC__ASSERT(encoder->protected_->state == FLAC__STREAM_ENCODER_OK); /* * Accumulate raw signal to the MD5 signature */ if(encoder->protected_->do_md5 && !FLAC__MD5Accumulate(&encoder->private_->md5context, (const FLAC__int32 * const *)encoder->private_->integer_signal, encoder->protected_->channels, encoder->protected_->blocksize, (encoder->protected_->bits_per_sample+7) / 8)) { encoder->protected_->state = FLAC__STREAM_ENCODER_MEMORY_ALLOCATION_ERROR; return false; } /* * Process the frame header and subframes into the frame bitbuffer */ if(!process_subframes_(encoder, is_fractional_block)) { /* the above function sets the state for us in case of an error */ return false; } /* * Zero-pad the frame to a byte_boundary */ if(!FLAC__bitwriter_zero_pad_to_byte_boundary(encoder->private_->frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_MEMORY_ALLOCATION_ERROR; return false; } /* * CRC-16 the whole thing */ FLAC__ASSERT(FLAC__bitwriter_is_byte_aligned(encoder->private_->frame)); if( !FLAC__bitwriter_get_write_crc16(encoder->private_->frame, &crc) || !FLAC__bitwriter_write_raw_uint32(encoder->private_->frame, crc, FLAC__FRAME_FOOTER_CRC_LEN) ) { encoder->protected_->state = FLAC__STREAM_ENCODER_MEMORY_ALLOCATION_ERROR; return false; } /* * Write it */ if(!write_bitbuffer_(encoder, encoder->protected_->blocksize, is_last_block)) { /* the above function sets the state for us in case of an error */ return false; } /* * Get ready for the next frame */ encoder->private_->current_sample_number = 0; encoder->private_->current_frame_number++; encoder->private_->streaminfo.data.stream_info.total_samples += (FLAC__uint64)encoder->protected_->blocksize; return true; } FLAC__bool process_subframes_(FLAC__StreamEncoder *encoder, FLAC__bool is_fractional_block) { FLAC__FrameHeader frame_header; unsigned channel, min_partition_order = encoder->protected_->min_residual_partition_order, max_partition_order; FLAC__bool do_independent, do_mid_side; /* * Calculate the min,max Rice partition orders */ if(is_fractional_block) { max_partition_order = 0; } else { max_partition_order = FLAC__format_get_max_rice_partition_order_from_blocksize(encoder->protected_->blocksize); max_partition_order = min(max_partition_order, encoder->protected_->max_residual_partition_order); } min_partition_order = min(min_partition_order, max_partition_order); /* * Setup the frame */ frame_header.blocksize = encoder->protected_->blocksize; frame_header.sample_rate = encoder->protected_->sample_rate; frame_header.channels = encoder->protected_->channels; frame_header.channel_assignment = FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT; /* the default unless the encoder determines otherwise */ frame_header.bits_per_sample = encoder->protected_->bits_per_sample; frame_header.number_type = FLAC__FRAME_NUMBER_TYPE_FRAME_NUMBER; frame_header.number.frame_number = encoder->private_->current_frame_number; /* * Figure out what channel assignments to try */ if(encoder->protected_->do_mid_side_stereo) { if(encoder->protected_->loose_mid_side_stereo) { if(encoder->private_->loose_mid_side_stereo_frame_count == 0) { do_independent = true; do_mid_side = true; } else { do_independent = (encoder->private_->last_channel_assignment == FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT); do_mid_side = !do_independent; } } else { do_independent = true; do_mid_side = true; } } else { do_independent = true; do_mid_side = false; } FLAC__ASSERT(do_independent || do_mid_side); /* * Check for wasted bits; set effective bps for each subframe */ if(do_independent) { for(channel = 0; channel < encoder->protected_->channels; channel++) { const unsigned w = get_wasted_bits_(encoder->private_->integer_signal[channel], encoder->protected_->blocksize); encoder->private_->subframe_workspace[channel][0].wasted_bits = encoder->private_->subframe_workspace[channel][1].wasted_bits = w; encoder->private_->subframe_bps[channel] = encoder->protected_->bits_per_sample - w; } } if(do_mid_side) { FLAC__ASSERT(encoder->protected_->channels == 2); for(channel = 0; channel < 2; channel++) { const unsigned w = get_wasted_bits_(encoder->private_->integer_signal_mid_side[channel], encoder->protected_->blocksize); encoder->private_->subframe_workspace_mid_side[channel][0].wasted_bits = encoder->private_->subframe_workspace_mid_side[channel][1].wasted_bits = w; encoder->private_->subframe_bps_mid_side[channel] = encoder->protected_->bits_per_sample - w + (channel==0? 0:1); } } /* * First do a normal encoding pass of each independent channel */ if(do_independent) { for(channel = 0; channel < encoder->protected_->channels; channel++) { if(! process_subframe_( encoder, min_partition_order, max_partition_order, &frame_header, encoder->private_->subframe_bps[channel], encoder->private_->integer_signal[channel], encoder->private_->subframe_workspace_ptr[channel], encoder->private_->partitioned_rice_contents_workspace_ptr[channel], encoder->private_->residual_workspace[channel], encoder->private_->best_subframe+channel, encoder->private_->best_subframe_bits+channel ) ) return false; } } /* * Now do mid and side channels if requested */ if(do_mid_side) { FLAC__ASSERT(encoder->protected_->channels == 2); for(channel = 0; channel < 2; channel++) { if(! process_subframe_( encoder, min_partition_order, max_partition_order, &frame_header, encoder->private_->subframe_bps_mid_side[channel], encoder->private_->integer_signal_mid_side[channel], encoder->private_->subframe_workspace_ptr_mid_side[channel], encoder->private_->partitioned_rice_contents_workspace_ptr_mid_side[channel], encoder->private_->residual_workspace_mid_side[channel], encoder->private_->best_subframe_mid_side+channel, encoder->private_->best_subframe_bits_mid_side+channel ) ) return false; } } /* * Compose the frame bitbuffer */ if(do_mid_side) { unsigned left_bps = 0, right_bps = 0; /* initialized only to prevent superfluous compiler warning */ FLAC__Subframe *left_subframe = 0, *right_subframe = 0; /* initialized only to prevent superfluous compiler warning */ FLAC__ChannelAssignment channel_assignment; FLAC__ASSERT(encoder->protected_->channels == 2); if(encoder->protected_->loose_mid_side_stereo && encoder->private_->loose_mid_side_stereo_frame_count > 0) { channel_assignment = (encoder->private_->last_channel_assignment == FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT? FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT : FLAC__CHANNEL_ASSIGNMENT_MID_SIDE); } else { unsigned bits[4]; /* WATCHOUT - indexed by FLAC__ChannelAssignment */ unsigned min_bits; int ca; FLAC__ASSERT(FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT == 0); FLAC__ASSERT(FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE == 1); FLAC__ASSERT(FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE == 2); FLAC__ASSERT(FLAC__CHANNEL_ASSIGNMENT_MID_SIDE == 3); FLAC__ASSERT(do_independent && do_mid_side); /* We have to figure out which channel assignent results in the smallest frame */ bits[FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT] = encoder->private_->best_subframe_bits [0] + encoder->private_->best_subframe_bits [1]; bits[FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE ] = encoder->private_->best_subframe_bits [0] + encoder->private_->best_subframe_bits_mid_side[1]; bits[FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE ] = encoder->private_->best_subframe_bits [1] + encoder->private_->best_subframe_bits_mid_side[1]; bits[FLAC__CHANNEL_ASSIGNMENT_MID_SIDE ] = encoder->private_->best_subframe_bits_mid_side[0] + encoder->private_->best_subframe_bits_mid_side[1]; channel_assignment = FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT; min_bits = bits[channel_assignment]; for(ca = 1; ca <= 3; ca++) { if(bits[ca] < min_bits) { min_bits = bits[ca]; channel_assignment = (FLAC__ChannelAssignment)ca; } } } frame_header.channel_assignment = channel_assignment; if(!FLAC__frame_add_header(&frame_header, encoder->private_->frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return false; } switch(channel_assignment) { case FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT: left_subframe = &encoder->private_->subframe_workspace [0][encoder->private_->best_subframe [0]]; right_subframe = &encoder->private_->subframe_workspace [1][encoder->private_->best_subframe [1]]; break; case FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE: left_subframe = &encoder->private_->subframe_workspace [0][encoder->private_->best_subframe [0]]; right_subframe = &encoder->private_->subframe_workspace_mid_side[1][encoder->private_->best_subframe_mid_side[1]]; break; case FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE: left_subframe = &encoder->private_->subframe_workspace_mid_side[1][encoder->private_->best_subframe_mid_side[1]]; right_subframe = &encoder->private_->subframe_workspace [1][encoder->private_->best_subframe [1]]; break; case FLAC__CHANNEL_ASSIGNMENT_MID_SIDE: left_subframe = &encoder->private_->subframe_workspace_mid_side[0][encoder->private_->best_subframe_mid_side[0]]; right_subframe = &encoder->private_->subframe_workspace_mid_side[1][encoder->private_->best_subframe_mid_side[1]]; break; default: FLAC__ASSERT(0); } switch(channel_assignment) { case FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT: left_bps = encoder->private_->subframe_bps [0]; right_bps = encoder->private_->subframe_bps [1]; break; case FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE: left_bps = encoder->private_->subframe_bps [0]; right_bps = encoder->private_->subframe_bps_mid_side[1]; break; case FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE: left_bps = encoder->private_->subframe_bps_mid_side[1]; right_bps = encoder->private_->subframe_bps [1]; break; case FLAC__CHANNEL_ASSIGNMENT_MID_SIDE: left_bps = encoder->private_->subframe_bps_mid_side[0]; right_bps = encoder->private_->subframe_bps_mid_side[1]; break; default: FLAC__ASSERT(0); } /* note that encoder_add_subframe_ sets the state for us in case of an error */ if(!add_subframe_(encoder, frame_header.blocksize, left_bps , left_subframe , encoder->private_->frame)) return false; if(!add_subframe_(encoder, frame_header.blocksize, right_bps, right_subframe, encoder->private_->frame)) return false; } else { if(!FLAC__frame_add_header(&frame_header, encoder->private_->frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return false; } for(channel = 0; channel < encoder->protected_->channels; channel++) { if(!add_subframe_(encoder, frame_header.blocksize, encoder->private_->subframe_bps[channel], &encoder->private_->subframe_workspace[channel][encoder->private_->best_subframe[channel]], encoder->private_->frame)) { /* the above function sets the state for us in case of an error */ return false; } } } if(encoder->protected_->loose_mid_side_stereo) { encoder->private_->loose_mid_side_stereo_frame_count++; if(encoder->private_->loose_mid_side_stereo_frame_count >= encoder->private_->loose_mid_side_stereo_frames) encoder->private_->loose_mid_side_stereo_frame_count = 0; } encoder->private_->last_channel_assignment = frame_header.channel_assignment; return true; } FLAC__bool process_subframe_( FLAC__StreamEncoder *encoder, unsigned min_partition_order, unsigned max_partition_order, const FLAC__FrameHeader *frame_header, unsigned subframe_bps, const FLAC__int32 integer_signal[], FLAC__Subframe *subframe[2], FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents[2], FLAC__int32 *residual[2], unsigned *best_subframe, unsigned *best_bits ) { #ifndef FLAC__INTEGER_ONLY_LIBRARY FLAC__float fixed_residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]; #else FLAC__fixedpoint fixed_residual_bits_per_sample[FLAC__MAX_FIXED_ORDER+1]; #endif #ifndef FLAC__INTEGER_ONLY_LIBRARY FLAC__double lpc_residual_bits_per_sample; FLAC__real autoc[FLAC__MAX_LPC_ORDER+1]; /* WATCHOUT: the size is important even though encoder->protected_->max_lpc_order might be less; some asm routines need all the space */ FLAC__double lpc_error[FLAC__MAX_LPC_ORDER]; unsigned min_lpc_order, max_lpc_order, lpc_order; unsigned min_qlp_coeff_precision, max_qlp_coeff_precision, qlp_coeff_precision; #endif unsigned min_fixed_order, max_fixed_order, guess_fixed_order, fixed_order; unsigned rice_parameter; unsigned _candidate_bits, _best_bits; unsigned _best_subframe; /* only use RICE2 partitions if stream bps > 16 */ const unsigned rice_parameter_limit = FLAC__stream_encoder_get_bits_per_sample(encoder) > 16? FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_ESCAPE_PARAMETER : FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ESCAPE_PARAMETER; FLAC__ASSERT(frame_header->blocksize > 0); /* verbatim subframe is the baseline against which we measure other compressed subframes */ _best_subframe = 0; if(encoder->private_->disable_verbatim_subframes && frame_header->blocksize >= FLAC__MAX_FIXED_ORDER) _best_bits = UINT_MAX; else _best_bits = evaluate_verbatim_subframe_(encoder, integer_signal, frame_header->blocksize, subframe_bps, subframe[_best_subframe]); if(frame_header->blocksize >= FLAC__MAX_FIXED_ORDER) { unsigned signal_is_constant = false; guess_fixed_order = encoder->private_->local_fixed_compute_best_predictor(integer_signal+FLAC__MAX_FIXED_ORDER, frame_header->blocksize-FLAC__MAX_FIXED_ORDER, fixed_residual_bits_per_sample); /* check for constant subframe */ if( !encoder->private_->disable_constant_subframes && #ifndef FLAC__INTEGER_ONLY_LIBRARY fixed_residual_bits_per_sample[1] == 0.0 #else fixed_residual_bits_per_sample[1] == FLAC__FP_ZERO #endif ) { /* the above means it's possible all samples are the same value; now double-check it: */ unsigned i; signal_is_constant = true; for(i = 1; i < frame_header->blocksize; i++) { if(integer_signal[0] != integer_signal[i]) { signal_is_constant = false; break; } } } if(signal_is_constant) { _candidate_bits = evaluate_constant_subframe_(encoder, integer_signal[0], frame_header->blocksize, subframe_bps, subframe[!_best_subframe]); if(_candidate_bits < _best_bits) { _best_subframe = !_best_subframe; _best_bits = _candidate_bits; } } else { if(!encoder->private_->disable_fixed_subframes || (encoder->protected_->max_lpc_order == 0 && _best_bits == UINT_MAX)) { /* encode fixed */ if(encoder->protected_->do_exhaustive_model_search) { min_fixed_order = 0; max_fixed_order = FLAC__MAX_FIXED_ORDER; } else { min_fixed_order = max_fixed_order = guess_fixed_order; } if(max_fixed_order >= frame_header->blocksize) max_fixed_order = frame_header->blocksize - 1; for(fixed_order = min_fixed_order; fixed_order <= max_fixed_order; fixed_order++) { #ifndef FLAC__INTEGER_ONLY_LIBRARY if(fixed_residual_bits_per_sample[fixed_order] >= (FLAC__float)subframe_bps) continue; /* don't even try */ rice_parameter = (fixed_residual_bits_per_sample[fixed_order] > 0.0)? (unsigned)(fixed_residual_bits_per_sample[fixed_order]+0.5) : 0; /* 0.5 is for rounding */ #else if(FLAC__fixedpoint_trunc(fixed_residual_bits_per_sample[fixed_order]) >= (int)subframe_bps) continue; /* don't even try */ rice_parameter = (fixed_residual_bits_per_sample[fixed_order] > FLAC__FP_ZERO)? (unsigned)FLAC__fixedpoint_trunc(fixed_residual_bits_per_sample[fixed_order]+FLAC__FP_ONE_HALF) : 0; /* 0.5 is for rounding */ #endif rice_parameter++; /* to account for the signed->unsigned conversion during rice coding */ if(rice_parameter >= rice_parameter_limit) { #ifdef DEBUG_VERBOSE fprintf(stderr, "clipping rice_parameter (%u -> %u) @0\n", rice_parameter, rice_parameter_limit - 1); #endif rice_parameter = rice_parameter_limit - 1; } _candidate_bits = evaluate_fixed_subframe_( encoder, integer_signal, residual[!_best_subframe], encoder->private_->abs_residual_partition_sums, encoder->private_->raw_bits_per_partition, frame_header->blocksize, subframe_bps, fixed_order, rice_parameter, rice_parameter_limit, min_partition_order, max_partition_order, encoder->protected_->do_escape_coding, encoder->protected_->rice_parameter_search_dist, subframe[!_best_subframe], partitioned_rice_contents[!_best_subframe] ); if(_candidate_bits < _best_bits) { _best_subframe = !_best_subframe; _best_bits = _candidate_bits; } } } #ifndef FLAC__INTEGER_ONLY_LIBRARY /* encode lpc */ if(encoder->protected_->max_lpc_order > 0) { if(encoder->protected_->max_lpc_order >= frame_header->blocksize) max_lpc_order = frame_header->blocksize-1; else max_lpc_order = encoder->protected_->max_lpc_order; if(max_lpc_order > 0) { unsigned a; for (a = 0; a < encoder->protected_->num_apodizations; a++) { FLAC__lpc_window_data(integer_signal, encoder->private_->window[a], encoder->private_->windowed_signal, frame_header->blocksize); encoder->private_->local_lpc_compute_autocorrelation(encoder->private_->windowed_signal, frame_header->blocksize, max_lpc_order+1, autoc); /* if autoc[0] == 0.0, the signal is constant and we usually won't get here, but it can happen */ if(autoc[0] != 0.0) { FLAC__lpc_compute_lp_coefficients(autoc, &max_lpc_order, encoder->private_->lp_coeff, lpc_error); if(encoder->protected_->do_exhaustive_model_search) { min_lpc_order = 1; } else { const unsigned guess_lpc_order = FLAC__lpc_compute_best_order( lpc_error, max_lpc_order, frame_header->blocksize, subframe_bps + ( encoder->protected_->do_qlp_coeff_prec_search? FLAC__MIN_QLP_COEFF_PRECISION : /* have to guess; use the min possible size to avoid accidentally favoring lower orders */ encoder->protected_->qlp_coeff_precision ) ); min_lpc_order = max_lpc_order = guess_lpc_order; } if(max_lpc_order >= frame_header->blocksize) max_lpc_order = frame_header->blocksize - 1; for(lpc_order = min_lpc_order; lpc_order <= max_lpc_order; lpc_order++) { lpc_residual_bits_per_sample = FLAC__lpc_compute_expected_bits_per_residual_sample(lpc_error[lpc_order-1], frame_header->blocksize-lpc_order); if(lpc_residual_bits_per_sample >= (FLAC__double)subframe_bps) continue; /* don't even try */ rice_parameter = (lpc_residual_bits_per_sample > 0.0)? (unsigned)(lpc_residual_bits_per_sample+0.5) : 0; /* 0.5 is for rounding */ rice_parameter++; /* to account for the signed->unsigned conversion during rice coding */ if(rice_parameter >= rice_parameter_limit) { #ifdef DEBUG_VERBOSE fprintf(stderr, "clipping rice_parameter (%u -> %u) @1\n", rice_parameter, rice_parameter_limit - 1); #endif rice_parameter = rice_parameter_limit - 1; } if(encoder->protected_->do_qlp_coeff_prec_search) { min_qlp_coeff_precision = FLAC__MIN_QLP_COEFF_PRECISION; /* try to ensure a 32-bit datapath throughout for 16bps(+1bps for side channel) or less */ if(subframe_bps <= 17) { max_qlp_coeff_precision = min(32 - subframe_bps - lpc_order, FLAC__MAX_QLP_COEFF_PRECISION); max_qlp_coeff_precision = max(max_qlp_coeff_precision, min_qlp_coeff_precision); } else max_qlp_coeff_precision = FLAC__MAX_QLP_COEFF_PRECISION; } else { min_qlp_coeff_precision = max_qlp_coeff_precision = encoder->protected_->qlp_coeff_precision; } for(qlp_coeff_precision = min_qlp_coeff_precision; qlp_coeff_precision <= max_qlp_coeff_precision; qlp_coeff_precision++) { _candidate_bits = evaluate_lpc_subframe_( encoder, integer_signal, residual[!_best_subframe], encoder->private_->abs_residual_partition_sums, encoder->private_->raw_bits_per_partition, encoder->private_->lp_coeff[lpc_order-1], frame_header->blocksize, subframe_bps, lpc_order, qlp_coeff_precision, rice_parameter, rice_parameter_limit, min_partition_order, max_partition_order, encoder->protected_->do_escape_coding, encoder->protected_->rice_parameter_search_dist, subframe[!_best_subframe], partitioned_rice_contents[!_best_subframe] ); if(_candidate_bits > 0) { /* if == 0, there was a problem quantizing the lpcoeffs */ if(_candidate_bits < _best_bits) { _best_subframe = !_best_subframe; _best_bits = _candidate_bits; } } } } } } } } #endif /* !defined FLAC__INTEGER_ONLY_LIBRARY */ } } /* under rare circumstances this can happen when all but lpc subframe types are disabled: */ if(_best_bits == UINT_MAX) { FLAC__ASSERT(_best_subframe == 0); _best_bits = evaluate_verbatim_subframe_(encoder, integer_signal, frame_header->blocksize, subframe_bps, subframe[_best_subframe]); } *best_subframe = _best_subframe; *best_bits = _best_bits; return true; } FLAC__bool add_subframe_( FLAC__StreamEncoder *encoder, unsigned blocksize, unsigned subframe_bps, const FLAC__Subframe *subframe, FLAC__BitWriter *frame ) { switch(subframe->type) { case FLAC__SUBFRAME_TYPE_CONSTANT: if(!FLAC__subframe_add_constant(&(subframe->data.constant), subframe_bps, subframe->wasted_bits, frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return false; } break; case FLAC__SUBFRAME_TYPE_FIXED: if(!FLAC__subframe_add_fixed(&(subframe->data.fixed), blocksize - subframe->data.fixed.order, subframe_bps, subframe->wasted_bits, frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return false; } break; case FLAC__SUBFRAME_TYPE_LPC: if(!FLAC__subframe_add_lpc(&(subframe->data.lpc), blocksize - subframe->data.lpc.order, subframe_bps, subframe->wasted_bits, frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return false; } break; case FLAC__SUBFRAME_TYPE_VERBATIM: if(!FLAC__subframe_add_verbatim(&(subframe->data.verbatim), blocksize, subframe_bps, subframe->wasted_bits, frame)) { encoder->protected_->state = FLAC__STREAM_ENCODER_FRAMING_ERROR; return false; } break; default: FLAC__ASSERT(0); } return true; } #define SPOTCHECK_ESTIMATE 0 #if SPOTCHECK_ESTIMATE static void spotcheck_subframe_estimate_( FLAC__StreamEncoder *encoder, unsigned blocksize, unsigned subframe_bps, const FLAC__Subframe *subframe, unsigned estimate ) { FLAC__bool ret; FLAC__BitWriter *frame = FLAC__bitwriter_new(); if(frame == 0) { fprintf(stderr, "EST: can't allocate frame\n"); return; } if(!FLAC__bitwriter_init(frame)) { fprintf(stderr, "EST: can't init frame\n"); return; } ret = add_subframe_(encoder, blocksize, subframe_bps, subframe, frame); FLAC__ASSERT(ret); { const unsigned actual = FLAC__bitwriter_get_input_bits_unconsumed(frame); if(estimate != actual) fprintf(stderr, "EST: bad, frame#%u sub#%%d type=%8s est=%u, actual=%u, delta=%d\n", encoder->private_->current_frame_number, FLAC__SubframeTypeString[subframe->type], estimate, actual, (int)actual-(int)estimate); } FLAC__bitwriter_delete(frame); } #endif unsigned evaluate_constant_subframe_( FLAC__StreamEncoder *encoder, const FLAC__int32 signal, unsigned blocksize, unsigned subframe_bps, FLAC__Subframe *subframe ) { unsigned estimate; subframe->type = FLAC__SUBFRAME_TYPE_CONSTANT; subframe->data.constant.value = signal; estimate = FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN + subframe->wasted_bits + subframe_bps; #if SPOTCHECK_ESTIMATE spotcheck_subframe_estimate_(encoder, blocksize, subframe_bps, subframe, estimate); #else (void)encoder, (void)blocksize; #endif return estimate; } unsigned evaluate_fixed_subframe_( FLAC__StreamEncoder *encoder, const FLAC__int32 signal[], FLAC__int32 residual[], FLAC__uint64 abs_residual_partition_sums[], unsigned raw_bits_per_partition[], unsigned blocksize, unsigned subframe_bps, unsigned order, unsigned rice_parameter, unsigned rice_parameter_limit, unsigned min_partition_order, unsigned max_partition_order, FLAC__bool do_escape_coding, unsigned rice_parameter_search_dist, FLAC__Subframe *subframe, FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents ) { unsigned i, residual_bits, estimate; const unsigned residual_samples = blocksize - order; FLAC__fixed_compute_residual(signal+order, residual_samples, order, residual); subframe->type = FLAC__SUBFRAME_TYPE_FIXED; subframe->data.fixed.entropy_coding_method.type = FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE; subframe->data.fixed.entropy_coding_method.data.partitioned_rice.contents = partitioned_rice_contents; subframe->data.fixed.residual = residual; residual_bits = find_best_partition_order_( encoder->private_, residual, abs_residual_partition_sums, raw_bits_per_partition, residual_samples, order, rice_parameter, rice_parameter_limit, min_partition_order, max_partition_order, subframe_bps, do_escape_coding, rice_parameter_search_dist, &subframe->data.fixed.entropy_coding_method ); subframe->data.fixed.order = order; for(i = 0; i < order; i++) subframe->data.fixed.warmup[i] = signal[i]; estimate = FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN + subframe->wasted_bits + (order * subframe_bps) + residual_bits; #if SPOTCHECK_ESTIMATE spotcheck_subframe_estimate_(encoder, blocksize, subframe_bps, subframe, estimate); #endif return estimate; } #ifndef FLAC__INTEGER_ONLY_LIBRARY unsigned evaluate_lpc_subframe_( FLAC__StreamEncoder *encoder, const FLAC__int32 signal[], FLAC__int32 residual[], FLAC__uint64 abs_residual_partition_sums[], unsigned raw_bits_per_partition[], const FLAC__real lp_coeff[], unsigned blocksize, unsigned subframe_bps, unsigned order, unsigned qlp_coeff_precision, unsigned rice_parameter, unsigned rice_parameter_limit, unsigned min_partition_order, unsigned max_partition_order, FLAC__bool do_escape_coding, unsigned rice_parameter_search_dist, FLAC__Subframe *subframe, FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents ) { FLAC__int32 qlp_coeff[FLAC__MAX_LPC_ORDER]; unsigned i, residual_bits, estimate; int quantization, ret; const unsigned residual_samples = blocksize - order; /* try to keep qlp coeff precision such that only 32-bit math is required for decode of <=16bps streams */ if(subframe_bps <= 16) { FLAC__ASSERT(order > 0); FLAC__ASSERT(order <= FLAC__MAX_LPC_ORDER); qlp_coeff_precision = min(qlp_coeff_precision, 32 - subframe_bps - FLAC__bitmath_ilog2(order)); } ret = FLAC__lpc_quantize_coefficients(lp_coeff, order, qlp_coeff_precision, qlp_coeff, &quantization); if(ret != 0) return 0; /* this is a hack to indicate to the caller that we can't do lp at this order on this subframe */ if(subframe_bps + qlp_coeff_precision + FLAC__bitmath_ilog2(order) <= 32) if(subframe_bps <= 16 && qlp_coeff_precision <= 16) encoder->private_->local_lpc_compute_residual_from_qlp_coefficients_16bit(signal+order, residual_samples, qlp_coeff, order, quantization, residual); else encoder->private_->local_lpc_compute_residual_from_qlp_coefficients(signal+order, residual_samples, qlp_coeff, order, quantization, residual); else encoder->private_->local_lpc_compute_residual_from_qlp_coefficients_64bit(signal+order, residual_samples, qlp_coeff, order, quantization, residual); subframe->type = FLAC__SUBFRAME_TYPE_LPC; subframe->data.lpc.entropy_coding_method.type = FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE; subframe->data.lpc.entropy_coding_method.data.partitioned_rice.contents = partitioned_rice_contents; subframe->data.lpc.residual = residual; residual_bits = find_best_partition_order_( encoder->private_, residual, abs_residual_partition_sums, raw_bits_per_partition, residual_samples, order, rice_parameter, rice_parameter_limit, min_partition_order, max_partition_order, subframe_bps, do_escape_coding, rice_parameter_search_dist, &subframe->data.lpc.entropy_coding_method ); subframe->data.lpc.order = order; subframe->data.lpc.qlp_coeff_precision = qlp_coeff_precision; subframe->data.lpc.quantization_level = quantization; memcpy(subframe->data.lpc.qlp_coeff, qlp_coeff, sizeof(FLAC__int32)*FLAC__MAX_LPC_ORDER); for(i = 0; i < order; i++) subframe->data.lpc.warmup[i] = signal[i]; estimate = FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN + subframe->wasted_bits + FLAC__SUBFRAME_LPC_QLP_COEFF_PRECISION_LEN + FLAC__SUBFRAME_LPC_QLP_SHIFT_LEN + (order * (qlp_coeff_precision + subframe_bps)) + residual_bits; #if SPOTCHECK_ESTIMATE spotcheck_subframe_estimate_(encoder, blocksize, subframe_bps, subframe, estimate); #endif return estimate; } #endif unsigned evaluate_verbatim_subframe_( FLAC__StreamEncoder *encoder, const FLAC__int32 signal[], unsigned blocksize, unsigned subframe_bps, FLAC__Subframe *subframe ) { unsigned estimate; subframe->type = FLAC__SUBFRAME_TYPE_VERBATIM; subframe->data.verbatim.data = signal; estimate = FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN + subframe->wasted_bits + (blocksize * subframe_bps); #if SPOTCHECK_ESTIMATE spotcheck_subframe_estimate_(encoder, blocksize, subframe_bps, subframe, estimate); #else (void)encoder; #endif return estimate; } unsigned find_best_partition_order_( FLAC__StreamEncoderPrivate *private_, const FLAC__int32 residual[], FLAC__uint64 abs_residual_partition_sums[], unsigned raw_bits_per_partition[], unsigned residual_samples, unsigned predictor_order, unsigned rice_parameter, unsigned rice_parameter_limit, unsigned min_partition_order, unsigned max_partition_order, unsigned bps, FLAC__bool do_escape_coding, unsigned rice_parameter_search_dist, FLAC__EntropyCodingMethod *best_ecm ) { unsigned residual_bits, best_residual_bits = 0; unsigned best_parameters_index = 0; unsigned best_partition_order = 0; const unsigned blocksize = residual_samples + predictor_order; max_partition_order = FLAC__format_get_max_rice_partition_order_from_blocksize_limited_max_and_predictor_order(max_partition_order, blocksize, predictor_order); min_partition_order = min(min_partition_order, max_partition_order); precompute_partition_info_sums_(residual, abs_residual_partition_sums, residual_samples, predictor_order, min_partition_order, max_partition_order, bps); if(do_escape_coding) precompute_partition_info_escapes_(residual, raw_bits_per_partition, residual_samples, predictor_order, min_partition_order, max_partition_order); { int partition_order; unsigned sum; for(partition_order = (int)max_partition_order, sum = 0; partition_order >= (int)min_partition_order; partition_order--) { if(! set_partitioned_rice_( #ifdef EXACT_RICE_BITS_CALCULATION residual, #endif abs_residual_partition_sums+sum, raw_bits_per_partition+sum, residual_samples, predictor_order, rice_parameter, rice_parameter_limit, rice_parameter_search_dist, (unsigned)partition_order, do_escape_coding, &private_->partitioned_rice_contents_extra[!best_parameters_index], &residual_bits ) ) { FLAC__ASSERT(best_residual_bits != 0); break; } sum += 1u << partition_order; if(best_residual_bits == 0 || residual_bits < best_residual_bits) { best_residual_bits = residual_bits; best_parameters_index = !best_parameters_index; best_partition_order = partition_order; } } } best_ecm->data.partitioned_rice.order = best_partition_order; { /* * We are allowed to de-const the pointer based on our special * knowledge; it is const to the outside world. */ FLAC__EntropyCodingMethod_PartitionedRiceContents* prc = (FLAC__EntropyCodingMethod_PartitionedRiceContents*)best_ecm->data.partitioned_rice.contents; unsigned partition; /* save best parameters and raw_bits */ FLAC__format_entropy_coding_method_partitioned_rice_contents_ensure_size(prc, max(6, best_partition_order)); memcpy(prc->parameters, private_->partitioned_rice_contents_extra[best_parameters_index].parameters, sizeof(unsigned)*(1<<(best_partition_order))); if(do_escape_coding) memcpy(prc->raw_bits, private_->partitioned_rice_contents_extra[best_parameters_index].raw_bits, sizeof(unsigned)*(1<<(best_partition_order))); /* * Now need to check if the type should be changed to * FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2 based on the * size of the rice parameters. */ for(partition = 0; partition < (1u<parameters[partition] >= FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ESCAPE_PARAMETER) { best_ecm->type = FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2; break; } } } return best_residual_bits; } #if defined(FLAC__CPU_IA32) && !defined FLAC__NO_ASM && defined FLAC__HAS_NASM extern void precompute_partition_info_sums_32bit_asm_ia32_( const FLAC__int32 residual[], FLAC__uint64 abs_residual_partition_sums[], unsigned blocksize, unsigned predictor_order, unsigned min_partition_order, unsigned max_partition_order ); #endif void precompute_partition_info_sums_( const FLAC__int32 residual[], FLAC__uint64 abs_residual_partition_sums[], unsigned residual_samples, unsigned predictor_order, unsigned min_partition_order, unsigned max_partition_order, unsigned bps ) { const unsigned default_partition_samples = (residual_samples + predictor_order) >> max_partition_order; unsigned partitions = 1u << max_partition_order; FLAC__ASSERT(default_partition_samples > predictor_order); #if defined(FLAC__CPU_IA32) && !defined FLAC__NO_ASM && defined FLAC__HAS_NASM /* slightly pessimistic but still catches all common cases */ /* WATCHOUT: "+ bps" is an assumption that the average residual magnitude will not be more than "bps" bits */ if(FLAC__bitmath_ilog2(default_partition_samples) + bps < 32) { precompute_partition_info_sums_32bit_asm_ia32_(residual, abs_residual_partition_sums, residual_samples + predictor_order, predictor_order, min_partition_order, max_partition_order); return; } #endif /* first do max_partition_order */ { unsigned partition, residual_sample, end = (unsigned)(-(int)predictor_order); /* slightly pessimistic but still catches all common cases */ /* WATCHOUT: "+ bps" is an assumption that the average residual magnitude will not be more than "bps" bits */ if(FLAC__bitmath_ilog2(default_partition_samples) + bps < 32) { FLAC__uint32 abs_residual_partition_sum; for(partition = residual_sample = 0; partition < partitions; partition++) { end += default_partition_samples; abs_residual_partition_sum = 0; for( ; residual_sample < end; residual_sample++) abs_residual_partition_sum += abs(residual[residual_sample]); /* abs(INT_MIN) is undefined, but if the residual is INT_MIN we have bigger problems */ abs_residual_partition_sums[partition] = abs_residual_partition_sum; } } else { /* have to pessimistically use 64 bits for accumulator */ FLAC__uint64 abs_residual_partition_sum; for(partition = residual_sample = 0; partition < partitions; partition++) { end += default_partition_samples; abs_residual_partition_sum = 0; for( ; residual_sample < end; residual_sample++) abs_residual_partition_sum += abs(residual[residual_sample]); /* abs(INT_MIN) is undefined, but if the residual is INT_MIN we have bigger problems */ abs_residual_partition_sums[partition] = abs_residual_partition_sum; } } } /* now merge partitions for lower orders */ { unsigned from_partition = 0, to_partition = partitions; int partition_order; for(partition_order = (int)max_partition_order - 1; partition_order >= (int)min_partition_order; partition_order--) { unsigned i; partitions >>= 1; for(i = 0; i < partitions; i++) { abs_residual_partition_sums[to_partition++] = abs_residual_partition_sums[from_partition ] + abs_residual_partition_sums[from_partition+1]; from_partition += 2; } } } } void precompute_partition_info_escapes_( const FLAC__int32 residual[], unsigned raw_bits_per_partition[], unsigned residual_samples, unsigned predictor_order, unsigned min_partition_order, unsigned max_partition_order ) { int partition_order; unsigned from_partition, to_partition = 0; const unsigned blocksize = residual_samples + predictor_order; /* first do max_partition_order */ for(partition_order = (int)max_partition_order; partition_order >= 0; partition_order--) { FLAC__int32 r; FLAC__uint32 rmax; unsigned partition, partition_sample, partition_samples, residual_sample; const unsigned partitions = 1u << partition_order; const unsigned default_partition_samples = blocksize >> partition_order; FLAC__ASSERT(default_partition_samples > predictor_order); for(partition = residual_sample = 0; partition < partitions; partition++) { partition_samples = default_partition_samples; if(partition == 0) partition_samples -= predictor_order; rmax = 0; for(partition_sample = 0; partition_sample < partition_samples; partition_sample++) { r = residual[residual_sample++]; /* OPT: maybe faster: rmax |= r ^ (r>>31) */ if(r < 0) rmax |= ~r; else rmax |= r; } /* now we know all residual values are in the range [-rmax-1,rmax] */ raw_bits_per_partition[partition] = rmax? FLAC__bitmath_ilog2(rmax) + 2 : 1; } to_partition = partitions; break; /*@@@ yuck, should remove the 'for' loop instead */ } /* now merge partitions for lower orders */ for(from_partition = 0, --partition_order; partition_order >= (int)min_partition_order; partition_order--) { unsigned m; unsigned i; const unsigned partitions = 1u << partition_order; for(i = 0; i < partitions; i++) { m = raw_bits_per_partition[from_partition]; from_partition++; raw_bits_per_partition[to_partition] = max(m, raw_bits_per_partition[from_partition]); from_partition++; to_partition++; } } } #ifdef EXACT_RICE_BITS_CALCULATION static FLaC__INLINE unsigned count_rice_bits_in_partition_( const unsigned rice_parameter, const unsigned partition_samples, const FLAC__int32 *residual ) { unsigned i, partition_bits = FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_PARAMETER_LEN + /* actually could end up being FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_PARAMETER_LEN but err on side of 16bps */ (1+rice_parameter) * partition_samples /* 1 for unary stop bit + rice_parameter for the binary portion */ ; for(i = 0; i < partition_samples; i++) partition_bits += ( (FLAC__uint32)((residual[i]<<1)^(residual[i]>>31)) >> rice_parameter ); return partition_bits; } #else static FLaC__INLINE unsigned count_rice_bits_in_partition_( const unsigned rice_parameter, const unsigned partition_samples, const FLAC__uint64 abs_residual_partition_sum ) { return FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_PARAMETER_LEN + /* actually could end up being FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_PARAMETER_LEN but err on side of 16bps */ (1+rice_parameter) * partition_samples + /* 1 for unary stop bit + rice_parameter for the binary portion */ ( rice_parameter? (unsigned)(abs_residual_partition_sum >> (rice_parameter-1)) /* rice_parameter-1 because the real coder sign-folds instead of using a sign bit */ : (unsigned)(abs_residual_partition_sum << 1) /* can't shift by negative number, so reverse */ ) - (partition_samples >> 1) /* -(partition_samples>>1) to subtract out extra contributions to the abs_residual_partition_sum. * The actual number of bits used is closer to the sum(for all i in the partition) of abs(residual[i])>>(rice_parameter-1) * By using the abs_residual_partition sum, we also add in bits in the LSBs that would normally be shifted out. * So the subtraction term tries to guess how many extra bits were contributed. * If the LSBs are randomly distributed, this should average to 0.5 extra bits per sample. */ ; } #endif FLAC__bool set_partitioned_rice_( #ifdef EXACT_RICE_BITS_CALCULATION const FLAC__int32 residual[], #endif const FLAC__uint64 abs_residual_partition_sums[], const unsigned raw_bits_per_partition[], const unsigned residual_samples, const unsigned predictor_order, const unsigned suggested_rice_parameter, const unsigned rice_parameter_limit, const unsigned rice_parameter_search_dist, const unsigned partition_order, const FLAC__bool search_for_escapes, FLAC__EntropyCodingMethod_PartitionedRiceContents *partitioned_rice_contents, unsigned *bits ) { unsigned rice_parameter, partition_bits; unsigned best_partition_bits, best_rice_parameter = 0; unsigned bits_ = FLAC__ENTROPY_CODING_METHOD_TYPE_LEN + FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ORDER_LEN; unsigned *parameters, *raw_bits; #ifdef ENABLE_RICE_PARAMETER_SEARCH unsigned min_rice_parameter, max_rice_parameter; #else (void)rice_parameter_search_dist; #endif FLAC__ASSERT(suggested_rice_parameter < FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_ESCAPE_PARAMETER); FLAC__ASSERT(rice_parameter_limit <= FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_ESCAPE_PARAMETER); FLAC__format_entropy_coding_method_partitioned_rice_contents_ensure_size(partitioned_rice_contents, max(6, partition_order)); parameters = partitioned_rice_contents->parameters; raw_bits = partitioned_rice_contents->raw_bits; if(partition_order == 0) { best_partition_bits = (unsigned)(-1); #ifdef ENABLE_RICE_PARAMETER_SEARCH if(rice_parameter_search_dist) { if(suggested_rice_parameter < rice_parameter_search_dist) min_rice_parameter = 0; else min_rice_parameter = suggested_rice_parameter - rice_parameter_search_dist; max_rice_parameter = suggested_rice_parameter + rice_parameter_search_dist; if(max_rice_parameter >= rice_parameter_limit) { #ifdef DEBUG_VERBOSE fprintf(stderr, "clipping rice_parameter (%u -> %u) @5\n", max_rice_parameter, rice_parameter_limit - 1); #endif max_rice_parameter = rice_parameter_limit - 1; } } else min_rice_parameter = max_rice_parameter = suggested_rice_parameter; for(rice_parameter = min_rice_parameter; rice_parameter <= max_rice_parameter; rice_parameter++) { #else rice_parameter = suggested_rice_parameter; #endif #ifdef EXACT_RICE_BITS_CALCULATION partition_bits = count_rice_bits_in_partition_(rice_parameter, residual_samples, residual); #else partition_bits = count_rice_bits_in_partition_(rice_parameter, residual_samples, abs_residual_partition_sums[0]); #endif if(partition_bits < best_partition_bits) { best_rice_parameter = rice_parameter; best_partition_bits = partition_bits; } #ifdef ENABLE_RICE_PARAMETER_SEARCH } #endif if(search_for_escapes) { partition_bits = FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_PARAMETER_LEN + FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_RAW_LEN + raw_bits_per_partition[0] * residual_samples; if(partition_bits <= best_partition_bits) { raw_bits[0] = raw_bits_per_partition[0]; best_rice_parameter = 0; /* will be converted to appropriate escape parameter later */ best_partition_bits = partition_bits; } else raw_bits[0] = 0; } parameters[0] = best_rice_parameter; bits_ += best_partition_bits; } else { unsigned partition, residual_sample; unsigned partition_samples; FLAC__uint64 mean, k; const unsigned partitions = 1u << partition_order; for(partition = residual_sample = 0; partition < partitions; partition++) { partition_samples = (residual_samples+predictor_order) >> partition_order; if(partition == 0) { if(partition_samples <= predictor_order) return false; else partition_samples -= predictor_order; } mean = abs_residual_partition_sums[partition]; /* we are basically calculating the size in bits of the * average residual magnitude in the partition: * rice_parameter = floor(log2(mean/partition_samples)) * 'mean' is not a good name for the variable, it is * actually the sum of magnitudes of all residual values * in the partition, so the actual mean is * mean/partition_samples */ for(rice_parameter = 0, k = partition_samples; k < mean; rice_parameter++, k <<= 1) ; if(rice_parameter >= rice_parameter_limit) { #ifdef DEBUG_VERBOSE fprintf(stderr, "clipping rice_parameter (%u -> %u) @6\n", rice_parameter, rice_parameter_limit - 1); #endif rice_parameter = rice_parameter_limit - 1; } best_partition_bits = (unsigned)(-1); #ifdef ENABLE_RICE_PARAMETER_SEARCH if(rice_parameter_search_dist) { if(rice_parameter < rice_parameter_search_dist) min_rice_parameter = 0; else min_rice_parameter = rice_parameter - rice_parameter_search_dist; max_rice_parameter = rice_parameter + rice_parameter_search_dist; if(max_rice_parameter >= rice_parameter_limit) { #ifdef DEBUG_VERBOSE fprintf(stderr, "clipping rice_parameter (%u -> %u) @7\n", max_rice_parameter, rice_parameter_limit - 1); #endif max_rice_parameter = rice_parameter_limit - 1; } } else min_rice_parameter = max_rice_parameter = rice_parameter; for(rice_parameter = min_rice_parameter; rice_parameter <= max_rice_parameter; rice_parameter++) { #endif #ifdef EXACT_RICE_BITS_CALCULATION partition_bits = count_rice_bits_in_partition_(rice_parameter, partition_samples, residual+residual_sample); #else partition_bits = count_rice_bits_in_partition_(rice_parameter, partition_samples, abs_residual_partition_sums[partition]); #endif if(partition_bits < best_partition_bits) { best_rice_parameter = rice_parameter; best_partition_bits = partition_bits; } #ifdef ENABLE_RICE_PARAMETER_SEARCH } #endif if(search_for_escapes) { partition_bits = FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_PARAMETER_LEN + FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_RAW_LEN + raw_bits_per_partition[partition] * partition_samples; if(partition_bits <= best_partition_bits) { raw_bits[partition] = raw_bits_per_partition[partition]; best_rice_parameter = 0; /* will be converted to appropriate escape parameter later */ best_partition_bits = partition_bits; } else raw_bits[partition] = 0; } parameters[partition] = best_rice_parameter; bits_ += best_partition_bits; residual_sample += partition_samples; } } *bits = bits_; return true; } unsigned get_wasted_bits_(FLAC__int32 signal[], unsigned samples) { unsigned i, shift; FLAC__int32 x = 0; for(i = 0; i < samples && !(x&1); i++) x |= signal[i]; if(x == 0) { shift = 0; } else { for(shift = 0; !(x&1); shift++) x >>= 1; } if(shift > 0) { for(i = 0; i < samples; i++) signal[i] >>= shift; } return shift; } void append_to_verify_fifo_(verify_input_fifo *fifo, const FLAC__int32 * const input[], unsigned input_offset, unsigned channels, unsigned wide_samples) { unsigned channel; for(channel = 0; channel < channels; channel++) memcpy(&fifo->data[channel][fifo->tail], &input[channel][input_offset], sizeof(FLAC__int32) * wide_samples); fifo->tail += wide_samples; FLAC__ASSERT(fifo->tail <= fifo->size); } void append_to_verify_fifo_interleaved_(verify_input_fifo *fifo, const FLAC__int32 input[], unsigned input_offset, unsigned channels, unsigned wide_samples) { unsigned channel; unsigned sample, wide_sample; unsigned tail = fifo->tail; sample = input_offset * channels; for(wide_sample = 0; wide_sample < wide_samples; wide_sample++) { for(channel = 0; channel < channels; channel++) fifo->data[channel][tail] = input[sample++]; tail++; } fifo->tail = tail; FLAC__ASSERT(fifo->tail <= fifo->size); } FLAC__StreamDecoderReadStatus verify_read_callback_(const FLAC__StreamDecoder *decoder, FLAC__byte buffer[], size_t *bytes, void *client_data) { FLAC__StreamEncoder *encoder = (FLAC__StreamEncoder*)client_data; const size_t encoded_bytes = encoder->private_->verify.output.bytes; (void)decoder; if(encoder->private_->verify.needs_magic_hack) { FLAC__ASSERT(*bytes >= FLAC__STREAM_SYNC_LENGTH); *bytes = FLAC__STREAM_SYNC_LENGTH; memcpy(buffer, FLAC__STREAM_SYNC_STRING, *bytes); encoder->private_->verify.needs_magic_hack = false; } else { if(encoded_bytes == 0) { /* * If we get here, a FIFO underflow has occurred, * which means there is a bug somewhere. */ FLAC__ASSERT(0); return FLAC__STREAM_DECODER_READ_STATUS_ABORT; } else if(encoded_bytes < *bytes) *bytes = encoded_bytes; memcpy(buffer, encoder->private_->verify.output.data, *bytes); encoder->private_->verify.output.data += *bytes; encoder->private_->verify.output.bytes -= *bytes; } return FLAC__STREAM_DECODER_READ_STATUS_CONTINUE; } FLAC__StreamDecoderWriteStatus verify_write_callback_(const FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer[], void *client_data) { FLAC__StreamEncoder *encoder = (FLAC__StreamEncoder *)client_data; unsigned channel; const unsigned channels = frame->header.channels; const unsigned blocksize = frame->header.blocksize; const unsigned bytes_per_block = sizeof(FLAC__int32) * blocksize; (void)decoder; for(channel = 0; channel < channels; channel++) { if(0 != memcmp(buffer[channel], encoder->private_->verify.input_fifo.data[channel], bytes_per_block)) { unsigned i, sample = 0; FLAC__int32 expect = 0, got = 0; for(i = 0; i < blocksize; i++) { if(buffer[channel][i] != encoder->private_->verify.input_fifo.data[channel][i]) { sample = i; expect = (FLAC__int32)encoder->private_->verify.input_fifo.data[channel][i]; got = (FLAC__int32)buffer[channel][i]; break; } } FLAC__ASSERT(i < blocksize); FLAC__ASSERT(frame->header.number_type == FLAC__FRAME_NUMBER_TYPE_SAMPLE_NUMBER); encoder->private_->verify.error_stats.absolute_sample = frame->header.number.sample_number + sample; encoder->private_->verify.error_stats.frame_number = (unsigned)(frame->header.number.sample_number / blocksize); encoder->private_->verify.error_stats.channel = channel; encoder->private_->verify.error_stats.sample = sample; encoder->private_->verify.error_stats.expected = expect; encoder->private_->verify.error_stats.got = got; encoder->protected_->state = FLAC__STREAM_ENCODER_VERIFY_MISMATCH_IN_AUDIO_DATA; return FLAC__STREAM_DECODER_WRITE_STATUS_ABORT; } } /* dequeue the frame from the fifo */ encoder->private_->verify.input_fifo.tail -= blocksize; FLAC__ASSERT(encoder->private_->verify.input_fifo.tail <= OVERREAD_); for(channel = 0; channel < channels; channel++) memmove(&encoder->private_->verify.input_fifo.data[channel][0], &encoder->private_->verify.input_fifo.data[channel][blocksize], encoder->private_->verify.input_fifo.tail * sizeof(encoder->private_->verify.input_fifo.data[0][0])); return FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE; } void verify_metadata_callback_(const FLAC__StreamDecoder *decoder, const FLAC__StreamMetadata *metadata, void *client_data) { (void)decoder, (void)metadata, (void)client_data; } void verify_error_callback_(const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data) { FLAC__StreamEncoder *encoder = (FLAC__StreamEncoder*)client_data; (void)decoder, (void)status; encoder->protected_->state = FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR; } FLAC__StreamEncoderReadStatus file_read_callback_(const FLAC__StreamEncoder *encoder, FLAC__byte buffer[], size_t *bytes, void *client_data) { (void)client_data; *bytes = fread(buffer, 1, *bytes, encoder->private_->file); if (*bytes == 0) { if (feof(encoder->private_->file)) return FLAC__STREAM_ENCODER_READ_STATUS_END_OF_STREAM; else if (ferror(encoder->private_->file)) return FLAC__STREAM_ENCODER_READ_STATUS_ABORT; } return FLAC__STREAM_ENCODER_READ_STATUS_CONTINUE; } FLAC__StreamEncoderSeekStatus file_seek_callback_(const FLAC__StreamEncoder *encoder, FLAC__uint64 absolute_byte_offset, void *client_data) { (void)client_data; if(fseeko(encoder->private_->file, (off_t)absolute_byte_offset, SEEK_SET) < 0) return FLAC__STREAM_ENCODER_SEEK_STATUS_ERROR; else return FLAC__STREAM_ENCODER_SEEK_STATUS_OK; } FLAC__StreamEncoderTellStatus file_tell_callback_(const FLAC__StreamEncoder *encoder, FLAC__uint64 *absolute_byte_offset, void *client_data) { off_t offset; (void)client_data; offset = ftello(encoder->private_->file); if(offset < 0) { return FLAC__STREAM_ENCODER_TELL_STATUS_ERROR; } else { *absolute_byte_offset = (FLAC__uint64)offset; return FLAC__STREAM_ENCODER_TELL_STATUS_OK; } } #ifdef FLAC__VALGRIND_TESTING static size_t local__fwrite(const void *ptr, size_t size, size_t nmemb, FILE *stream) { size_t ret = fwrite(ptr, size, nmemb, stream); if(!ferror(stream)) fflush(stream); return ret; } #else #define local__fwrite fwrite #endif FLAC__StreamEncoderWriteStatus file_write_callback_(const FLAC__StreamEncoder *encoder, const FLAC__byte buffer[], size_t bytes, unsigned samples, unsigned current_frame, void *client_data) { (void)client_data, (void)current_frame; if(local__fwrite(buffer, sizeof(FLAC__byte), bytes, encoder->private_->file) == bytes) { FLAC__bool call_it = 0 != encoder->private_->progress_callback && ( #if FLAC__HAS_OGG /* We would like to be able to use 'samples > 0' in the * clause here but currently because of the nature of our * Ogg writing implementation, 'samples' is always 0 (see * ogg_encoder_aspect.c). The downside is extra progress * callbacks. */ encoder->private_->is_ogg? true : #endif samples > 0 ); if(call_it) { /* NOTE: We have to add +bytes, +samples, and +1 to the stats * because at this point in the callback chain, the stats * have not been updated. Only after we return and control * gets back to write_frame_() are the stats updated */ encoder->private_->progress_callback(encoder, encoder->private_->bytes_written+bytes, encoder->private_->samples_written+samples, encoder->private_->frames_written+(samples?1:0), encoder->private_->total_frames_estimate, encoder->private_->client_data); } return FLAC__STREAM_ENCODER_WRITE_STATUS_OK; } else return FLAC__STREAM_ENCODER_WRITE_STATUS_FATAL_ERROR; } /* * This will forcibly set stdout to binary mode (for OSes that require it) */ FILE *get_binary_stdout_(void) { /* if something breaks here it is probably due to the presence or * absence of an underscore before the identifiers 'setmode', * 'fileno', and/or 'O_BINARY'; check your system header files. */ #if defined _MSC_VER || defined __MINGW32__ _setmode(_fileno(stdout), _O_BINARY); #elif defined __CYGWIN__ /* almost certainly not needed for any modern Cygwin, but let's be safe... */ setmode(_fileno(stdout), _O_BINARY); #elif defined __EMX__ setmode(fileno(stdout), O_BINARY); #endif return stdout; } sources_5316/external/flac/flac_FLAC_export.h0000644000176700017670000000576110672574035017740 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__EXPORT_H #define FLAC__EXPORT_H /** \file include/FLAC/export.h * * \brief * This module contains #defines and symbols for exporting function * calls, and providing version information and compiled-in features. * * See the \link flac_export export \endlink module. */ /** \defgroup flac_export FLAC/export.h: export symbols * \ingroup flac * * \brief * This module contains #defines and symbols for exporting function * calls, and providing version information and compiled-in features. * * If you are compiling with MSVC and will link to the static library * (libFLAC.lib) you should define FLAC__NO_DLL in your project to * make sure the symbols are exported properly. * * \{ */ #if defined(FLAC__NO_DLL) || !defined(_MSC_VER) #define FLAC_API #else #ifdef FLAC_API_EXPORTS #define FLAC_API _declspec(dllexport) #else #define FLAC_API _declspec(dllimport) #endif #endif /** These #defines will mirror the libtool-based library version number, see * http://www.gnu.org/software/libtool/manual.html#Libtool-versioning */ #define FLAC_API_VERSION_CURRENT 10 #define FLAC_API_VERSION_REVISION 0 /**< see above */ #define FLAC_API_VERSION_AGE 2 /**< see above */ #ifdef __cplusplus extern "C" { #endif /** \c 1 if the library has been compiled with support for Ogg FLAC, else \c 0. */ extern FLAC_API int FLAC_API_SUPPORTS_OGG_FLAC; #ifdef __cplusplus } #endif /* \} */ #endif sources_5316/external/flac/flac_private_float.h0000644000176700017670000000735010720607255020460 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__FLOAT_H #define FLAC__PRIVATE__FLOAT_H #ifdef HAVE_CONFIG_H #include #endif #include "flac_FLAC_ordinals.h" /* * These typedefs make it easier to ensure that integer versions of * the library really only contain integer operations. All the code * in libFLAC should use FLAC__float and FLAC__double in place of * float and double, and be protected by checks of the macro * FLAC__INTEGER_ONLY_LIBRARY. * * FLAC__real is the basic floating point type used in LPC analysis. */ #ifndef FLAC__INTEGER_ONLY_LIBRARY typedef double FLAC__double; typedef float FLAC__float; /* * WATCHOUT: changing FLAC__real will change the signatures of many * functions that have assembly language equivalents and break them. */ typedef float FLAC__real; #else /* * The convention for FLAC__fixedpoint is to use the upper 16 bits * for the integer part and lower 16 bits for the fractional part. */ typedef FLAC__int32 FLAC__fixedpoint; extern const FLAC__fixedpoint FLAC__FP_ZERO; extern const FLAC__fixedpoint FLAC__FP_ONE_HALF; extern const FLAC__fixedpoint FLAC__FP_ONE; extern const FLAC__fixedpoint FLAC__FP_LN2; extern const FLAC__fixedpoint FLAC__FP_E; #define FLAC__fixedpoint_trunc(x) ((x)>>16) #define FLAC__fixedpoint_mul(x, y) ( (FLAC__fixedpoint) ( ((FLAC__int64)(x)*(FLAC__int64)(y)) >> 16 ) ) #define FLAC__fixedpoint_div(x, y) ( (FLAC__fixedpoint) ( ( ((FLAC__int64)(x)<<32) / (FLAC__int64)(y) ) >> 16 ) ) /* * FLAC__fixedpoint_log2() * -------------------------------------------------------------------- * Returns the base-2 logarithm of the fixed-point number 'x' using an * algorithm by Knuth for x >= 1.0 * * 'fracbits' is the number of fractional bits of 'x'. 'fracbits' must * be < 32 and evenly divisible by 4 (0 is OK but not very precise). * * 'precision' roughly limits the number of iterations that are done; * use (unsigned)(-1) for maximum precision. * * If 'x' is less than one -- that is, x < (1< /* for off_t */ #include "flac_FLAC_export.h" #include "flac_FLAC_callback.h" #include "flac_FLAC_format.h" /* -------------------------------------------------------------------- (For an example of how all these routines are used, see the source code for the unit tests in src/test_libFLAC/metadata_*.c, or metaflac in src/metaflac/) ------------------------------------------------------------------*/ /** \file include/FLAC/metadata.h * * \brief * This module provides functions for creating and manipulating FLAC * metadata blocks in memory, and three progressively more powerful * interfaces for traversing and editing metadata in FLAC files. * * See the detailed documentation for each interface in the * \link flac_metadata metadata \endlink module. */ /** \defgroup flac_metadata FLAC/metadata.h: metadata interfaces * \ingroup flac * * \brief * This module provides functions for creating and manipulating FLAC * metadata blocks in memory, and three progressively more powerful * interfaces for traversing and editing metadata in native FLAC files. * Note that currently only the Chain interface (level 2) supports Ogg * FLAC files, and it is read-only i.e. no writing back changed * metadata to file. * * There are three metadata interfaces of increasing complexity: * * Level 0: * Read-only access to the STREAMINFO, VORBIS_COMMENT, CUESHEET, and * PICTURE blocks. * * Level 1: * Read-write access to all metadata blocks. This level is write- * efficient in most cases (more on this below), and uses less memory * than level 2. * * Level 2: * Read-write access to all metadata blocks. This level is write- * efficient in all cases, but uses more memory since all metadata for * the whole file is read into memory and manipulated before writing * out again. * * What do we mean by efficient? Since FLAC metadata appears at the * beginning of the file, when writing metadata back to a FLAC file * it is possible to grow or shrink the metadata such that the entire * file must be rewritten. However, if the size remains the same during * changes or PADDING blocks are utilized, only the metadata needs to be * overwritten, which is much faster. * * Efficient means the whole file is rewritten at most one time, and only * when necessary. Level 1 is not efficient only in the case that you * cause more than one metadata block to grow or shrink beyond what can * be accomodated by padding. In this case you should probably use level * 2, which allows you to edit all the metadata for a file in memory and * write it out all at once. * * All levels know how to skip over and not disturb an ID3v2 tag at the * front of the file. * * All levels access files via their filenames. In addition, level 2 * has additional alternative read and write functions that take an I/O * handle and callbacks, for situations where access by filename is not * possible. * * In addition to the three interfaces, this module defines functions for * creating and manipulating various metadata objects in memory. As we see * from the Format module, FLAC metadata blocks in memory are very primitive * structures for storing information in an efficient way. Reading * information from the structures is easy but creating or modifying them * directly is more complex. The metadata object routines here facilitate * this by taking care of the consistency and memory management drudgery. * * Unless you will be using the level 1 or 2 interfaces to modify existing * metadata however, you will not probably not need these. * * From a dependency standpoint, none of the encoders or decoders require * the metadata module. This is so that embedded users can strip out the * metadata module from libFLAC to reduce the size and complexity. */ #ifdef __cplusplus extern "C" { #endif /** \defgroup flac_metadata_level0 FLAC/metadata.h: metadata level 0 interface * \ingroup flac_metadata * * \brief * The level 0 interface consists of individual routines to read the * STREAMINFO, VORBIS_COMMENT, CUESHEET, and PICTURE blocks, requiring * only a filename. * * They try to skip any ID3v2 tag at the head of the file. * * \{ */ /** Read the STREAMINFO metadata block of the given FLAC file. This function * will try to skip any ID3v2 tag at the head of the file. * * \param filename The path to the FLAC file to read. * \param streaminfo A pointer to space for the STREAMINFO block. Since * FLAC__StreamMetadata is a simple structure with no * memory allocation involved, you pass the address of * an existing structure. It need not be initialized. * \assert * \code filename != NULL \endcode * \code streaminfo != NULL \endcode * \retval FLAC__bool * \c true if a valid STREAMINFO block was read from \a filename. Returns * \c false if there was a memory allocation error, a file decoder error, * or the file contained no STREAMINFO block. (A memory allocation error * is possible because this function must set up a file decoder.) */ FLAC_API FLAC__bool FLAC__metadata_get_streaminfo(const char *filename, FLAC__StreamMetadata *streaminfo); /** Read the VORBIS_COMMENT metadata block of the given FLAC file. This * function will try to skip any ID3v2 tag at the head of the file. * * \param filename The path to the FLAC file to read. * \param tags The address where the returned pointer will be * stored. The \a tags object must be deleted by * the caller using FLAC__metadata_object_delete(). * \assert * \code filename != NULL \endcode * \code tags != NULL \endcode * \retval FLAC__bool * \c true if a valid VORBIS_COMMENT block was read from \a filename, * and \a *tags will be set to the address of the metadata structure. * Returns \c false if there was a memory allocation error, a file * decoder error, or the file contained no VORBIS_COMMENT block, and * \a *tags will be set to \c NULL. */ FLAC_API FLAC__bool FLAC__metadata_get_tags(const char *filename, FLAC__StreamMetadata **tags); /** Read the CUESHEET metadata block of the given FLAC file. This * function will try to skip any ID3v2 tag at the head of the file. * * \param filename The path to the FLAC file to read. * \param cuesheet The address where the returned pointer will be * stored. The \a cuesheet object must be deleted by * the caller using FLAC__metadata_object_delete(). * \assert * \code filename != NULL \endcode * \code cuesheet != NULL \endcode * \retval FLAC__bool * \c true if a valid CUESHEET block was read from \a filename, * and \a *cuesheet will be set to the address of the metadata * structure. Returns \c false if there was a memory allocation * error, a file decoder error, or the file contained no CUESHEET * block, and \a *cuesheet will be set to \c NULL. */ FLAC_API FLAC__bool FLAC__metadata_get_cuesheet(const char *filename, FLAC__StreamMetadata **cuesheet); /** Read a PICTURE metadata block of the given FLAC file. This * function will try to skip any ID3v2 tag at the head of the file. * Since there can be more than one PICTURE block in a file, this * function takes a number of parameters that act as constraints to * the search. The PICTURE block with the largest area matching all * the constraints will be returned, or \a *picture will be set to * \c NULL if there was no such block. * * \param filename The path to the FLAC file to read. * \param picture The address where the returned pointer will be * stored. The \a picture object must be deleted by * the caller using FLAC__metadata_object_delete(). * \param type The desired picture type. Use \c -1 to mean * "any type". * \param mime_type The desired MIME type, e.g. "image/jpeg". The * string will be matched exactly. Use \c NULL to * mean "any MIME type". * \param description The desired description. The string will be * matched exactly. Use \c NULL to mean "any * description". * \param max_width The maximum width in pixels desired. Use * \c (unsigned)(-1) to mean "any width". * \param max_height The maximum height in pixels desired. Use * \c (unsigned)(-1) to mean "any height". * \param max_depth The maximum color depth in bits-per-pixel desired. * Use \c (unsigned)(-1) to mean "any depth". * \param max_colors The maximum number of colors desired. Use * \c (unsigned)(-1) to mean "any number of colors". * \assert * \code filename != NULL \endcode * \code picture != NULL \endcode * \retval FLAC__bool * \c true if a valid PICTURE block was read from \a filename, * and \a *picture will be set to the address of the metadata * structure. Returns \c false if there was a memory allocation * error, a file decoder error, or the file contained no PICTURE * block, and \a *picture will be set to \c NULL. */ FLAC_API FLAC__bool FLAC__metadata_get_picture(const char *filename, FLAC__StreamMetadata **picture, FLAC__StreamMetadata_Picture_Type type, const char *mime_type, const FLAC__byte *description, unsigned max_width, unsigned max_height, unsigned max_depth, unsigned max_colors); /* \} */ /** \defgroup flac_metadata_level1 FLAC/metadata.h: metadata level 1 interface * \ingroup flac_metadata * * \brief * The level 1 interface provides read-write access to FLAC file metadata and * operates directly on the FLAC file. * * The general usage of this interface is: * * - Create an iterator using FLAC__metadata_simple_iterator_new() * - Attach it to a file using FLAC__metadata_simple_iterator_init() and check * the exit code. Call FLAC__metadata_simple_iterator_is_writable() to * see if the file is writable, or only read access is allowed. * - Use FLAC__metadata_simple_iterator_next() and * FLAC__metadata_simple_iterator_prev() to traverse the blocks. * This is does not read the actual blocks themselves. * FLAC__metadata_simple_iterator_next() is relatively fast. * FLAC__metadata_simple_iterator_prev() is slower since it needs to search * forward from the front of the file. * - Use FLAC__metadata_simple_iterator_get_block_type() or * FLAC__metadata_simple_iterator_get_block() to access the actual data at * the current iterator position. The returned object is yours to modify * and free. * - Use FLAC__metadata_simple_iterator_set_block() to write a modified block * back. You must have write permission to the original file. Make sure to * read the whole comment to FLAC__metadata_simple_iterator_set_block() * below. * - Use FLAC__metadata_simple_iterator_insert_block_after() to add new blocks. * Use the object creation functions from * \link flac_metadata_object here \endlink to generate new objects. * - Use FLAC__metadata_simple_iterator_delete_block() to remove the block * currently referred to by the iterator, or replace it with padding. * - Destroy the iterator with FLAC__metadata_simple_iterator_delete() when * finished. * * \note * The FLAC file remains open the whole time between * FLAC__metadata_simple_iterator_init() and * FLAC__metadata_simple_iterator_delete(), so make sure you are not altering * the file during this time. * * \note * Do not modify the \a is_last, \a length, or \a type fields of returned * FLAC__StreamMetadata objects. These are managed automatically. * * \note * If any of the modification functions * (FLAC__metadata_simple_iterator_set_block(), * FLAC__metadata_simple_iterator_delete_block(), * FLAC__metadata_simple_iterator_insert_block_after(), etc.) return \c false, * you should delete the iterator as it may no longer be valid. * * \{ */ struct FLAC__Metadata_SimpleIterator; /** The opaque structure definition for the level 1 iterator type. * See the * \link flac_metadata_level1 metadata level 1 module \endlink * for a detailed description. */ typedef struct FLAC__Metadata_SimpleIterator FLAC__Metadata_SimpleIterator; /** Status type for FLAC__Metadata_SimpleIterator. * * The iterator's current status can be obtained by calling FLAC__metadata_simple_iterator_status(). */ typedef enum { FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK = 0, /**< The iterator is in the normal OK state */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ILLEGAL_INPUT, /**< The data passed into a function violated the function's usage criteria */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ERROR_OPENING_FILE, /**< The iterator could not open the target file */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_A_FLAC_FILE, /**< The iterator could not find the FLAC signature at the start of the file */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_WRITABLE, /**< The iterator tried to write to a file that was not writable */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_BAD_METADATA, /**< The iterator encountered input that does not conform to the FLAC metadata specification */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR, /**< The iterator encountered an error while reading the FLAC file */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR, /**< The iterator encountered an error while seeking in the FLAC file */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR, /**< The iterator encountered an error while writing the FLAC file */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_RENAME_ERROR, /**< The iterator encountered an error renaming the FLAC file */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_UNLINK_ERROR, /**< The iterator encountered an error removing the temporary file */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR, /**< Memory allocation failed */ FLAC__METADATA_SIMPLE_ITERATOR_STATUS_INTERNAL_ERROR /**< The caller violated an assertion or an unexpected error occurred */ } FLAC__Metadata_SimpleIteratorStatus; /** Maps a FLAC__Metadata_SimpleIteratorStatus to a C string. * * Using a FLAC__Metadata_SimpleIteratorStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__Metadata_SimpleIteratorStatusString[]; /** Create a new iterator instance. * * \retval FLAC__Metadata_SimpleIterator* * \c NULL if there was an error allocating memory, else the new instance. */ FLAC_API FLAC__Metadata_SimpleIterator *FLAC__metadata_simple_iterator_new(void); /** Free an iterator instance. Deletes the object pointed to by \a iterator. * * \param iterator A pointer to an existing iterator. * \assert * \code iterator != NULL \endcode */ FLAC_API void FLAC__metadata_simple_iterator_delete(FLAC__Metadata_SimpleIterator *iterator); /** Get the current status of the iterator. Call this after a function * returns \c false to get the reason for the error. Also resets the status * to FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK. * * \param iterator A pointer to an existing iterator. * \assert * \code iterator != NULL \endcode * \retval FLAC__Metadata_SimpleIteratorStatus * The current status of the iterator. */ FLAC_API FLAC__Metadata_SimpleIteratorStatus FLAC__metadata_simple_iterator_status(FLAC__Metadata_SimpleIterator *iterator); /** Initialize the iterator to point to the first metadata block in the * given FLAC file. * * \param iterator A pointer to an existing iterator. * \param filename The path to the FLAC file. * \param read_only If \c true, the FLAC file will be opened * in read-only mode; if \c false, the FLAC * file will be opened for edit even if no * edits are performed. * \param preserve_file_stats If \c true, the owner and modification * time will be preserved even if the FLAC * file is written to. * \assert * \code iterator != NULL \endcode * \code filename != NULL \endcode * \retval FLAC__bool * \c false if a memory allocation error occurs, the file can't be * opened, or another error occurs, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_init(FLAC__Metadata_SimpleIterator *iterator, const char *filename, FLAC__bool read_only, FLAC__bool preserve_file_stats); /** Returns \c true if the FLAC file is writable. If \c false, calls to * FLAC__metadata_simple_iterator_set_block() and * FLAC__metadata_simple_iterator_insert_block_after() will fail. * * \param iterator A pointer to an existing iterator. * \assert * \code iterator != NULL \endcode * \retval FLAC__bool * See above. */ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_is_writable(const FLAC__Metadata_SimpleIterator *iterator); /** Moves the iterator forward one metadata block, returning \c false if * already at the end. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \retval FLAC__bool * \c false if already at the last metadata block of the chain, else * \c true. */ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_next(FLAC__Metadata_SimpleIterator *iterator); /** Moves the iterator backward one metadata block, returning \c false if * already at the beginning. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \retval FLAC__bool * \c false if already at the first metadata block of the chain, else * \c true. */ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_prev(FLAC__Metadata_SimpleIterator *iterator); /** Returns a flag telling if the current metadata block is the last. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \retval FLAC__bool * \c true if the current metadata block is the last in the file, * else \c false. */ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_is_last(const FLAC__Metadata_SimpleIterator *iterator); /** Get the offset of the metadata block at the current position. This * avoids reading the actual block data which can save time for large * blocks. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \retval off_t * The offset of the metadata block at the current iterator position. * This is the byte offset relative to the beginning of the file of * the current metadata block's header. */ #if defined (_WIN32) && ! defined (off_t) #define off_t long #endif FLAC_API off_t FLAC__metadata_simple_iterator_get_block_offset(const FLAC__Metadata_SimpleIterator *iterator); /** Get the type of the metadata block at the current position. This * avoids reading the actual block data which can save time for large * blocks. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \retval FLAC__MetadataType * The type of the metadata block at the current iterator position. */ FLAC_API FLAC__MetadataType FLAC__metadata_simple_iterator_get_block_type(const FLAC__Metadata_SimpleIterator *iterator); /** Get the length of the metadata block at the current position. This * avoids reading the actual block data which can save time for large * blocks. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \retval unsigned * The length of the metadata block at the current iterator position. * The is same length as that in the * metadata block header, * i.e. the length of the metadata body that follows the header. */ FLAC_API unsigned FLAC__metadata_simple_iterator_get_block_length(const FLAC__Metadata_SimpleIterator *iterator); /** Get the application ID of the \c APPLICATION block at the current * position. This avoids reading the actual block data which can save * time for large blocks. * * \param iterator A pointer to an existing initialized iterator. * \param id A pointer to a buffer of at least \c 4 bytes where * the ID will be stored. * \assert * \code iterator != NULL \endcode * \code id != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \retval FLAC__bool * \c true if the ID was successfully read, else \c false, in which * case you should check FLAC__metadata_simple_iterator_status() to * find out why. If the status is * \c FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ILLEGAL_INPUT, then the * current metadata block is not an \c APPLICATION block. Otherwise * if the status is * \c FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR or * \c FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR, an I/O error * occurred and the iterator can no longer be used. */ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_get_application_id(FLAC__Metadata_SimpleIterator *iterator, FLAC__byte *id); /** Get the metadata block at the current position. You can modify the * block but must use FLAC__metadata_simple_iterator_set_block() to * write it back to the FLAC file. * * You must call FLAC__metadata_object_delete() on the returned object * when you are finished with it. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \retval FLAC__StreamMetadata* * The current metadata block, or \c NULL if there was a memory * allocation error. */ FLAC_API FLAC__StreamMetadata *FLAC__metadata_simple_iterator_get_block(FLAC__Metadata_SimpleIterator *iterator); /** Write a block back to the FLAC file. This function tries to be * as efficient as possible; how the block is actually written is * shown by the following: * * Existing block is a STREAMINFO block and the new block is a * STREAMINFO block: the new block is written in place. Make sure * you know what you're doing when changing the values of a * STREAMINFO block. * * Existing block is a STREAMINFO block and the new block is a * not a STREAMINFO block: this is an error since the first block * must be a STREAMINFO block. Returns \c false without altering the * file. * * Existing block is not a STREAMINFO block and the new block is a * STREAMINFO block: this is an error since there may be only one * STREAMINFO block. Returns \c false without altering the file. * * Existing block and new block are the same length: the existing * block will be replaced by the new block, written in place. * * Existing block is longer than new block: if use_padding is \c true, * the existing block will be overwritten in place with the new * block followed by a PADDING block, if possible, to make the total * size the same as the existing block. Remember that a padding * block requires at least four bytes so if the difference in size * between the new block and existing block is less than that, the * entire file will have to be rewritten, using the new block's * exact size. If use_padding is \c false, the entire file will be * rewritten, replacing the existing block by the new block. * * Existing block is shorter than new block: if use_padding is \c true, * the function will try and expand the new block into the following * PADDING block, if it exists and doing so won't shrink the PADDING * block to less than 4 bytes. If there is no following PADDING * block, or it will shrink to less than 4 bytes, or use_padding is * \c false, the entire file is rewritten, replacing the existing block * with the new block. Note that in this case any following PADDING * block is preserved as is. * * After writing the block, the iterator will remain in the same * place, i.e. pointing to the new block. * * \param iterator A pointer to an existing initialized iterator. * \param block The block to set. * \param use_padding See above. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \code block != NULL \endcode * \retval FLAC__bool * \c true if successful, else \c false. */ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_set_block(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block, FLAC__bool use_padding); /** This is similar to FLAC__metadata_simple_iterator_set_block() * except that instead of writing over an existing block, it appends * a block after the existing block. \a use_padding is again used to * tell the function to try an expand into following padding in an * attempt to avoid rewriting the entire file. * * This function will fail and return \c false if given a STREAMINFO * block. * * After writing the block, the iterator will be pointing to the * new block. * * \param iterator A pointer to an existing initialized iterator. * \param block The block to set. * \param use_padding See above. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \code block != NULL \endcode * \retval FLAC__bool * \c true if successful, else \c false. */ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_insert_block_after(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block, FLAC__bool use_padding); /** Deletes the block at the current position. This will cause the * entire FLAC file to be rewritten, unless \a use_padding is \c true, * in which case the block will be replaced by an equal-sized PADDING * block. The iterator will be left pointing to the block before the * one just deleted. * * You may not delete the STREAMINFO block. * * \param iterator A pointer to an existing initialized iterator. * \param use_padding See above. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_simple_iterator_init() * \retval FLAC__bool * \c true if successful, else \c false. */ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_delete_block(FLAC__Metadata_SimpleIterator *iterator, FLAC__bool use_padding); /* \} */ /** \defgroup flac_metadata_level2 FLAC/metadata.h: metadata level 2 interface * \ingroup flac_metadata * * \brief * The level 2 interface provides read-write access to FLAC file metadata; * all metadata is read into memory, operated on in memory, and then written * to file, which is more efficient than level 1 when editing multiple blocks. * * Currently Ogg FLAC is supported for read only, via * FLAC__metadata_chain_read_ogg() but a subsequent * FLAC__metadata_chain_write() will fail. * * The general usage of this interface is: * * - Create a new chain using FLAC__metadata_chain_new(). A chain is a * linked list of FLAC metadata blocks. * - Read all metadata into the the chain from a FLAC file using * FLAC__metadata_chain_read() or FLAC__metadata_chain_read_ogg() and * check the status. * - Optionally, consolidate the padding using * FLAC__metadata_chain_merge_padding() or * FLAC__metadata_chain_sort_padding(). * - Create a new iterator using FLAC__metadata_iterator_new() * - Initialize the iterator to point to the first element in the chain * using FLAC__metadata_iterator_init() * - Traverse the chain using FLAC__metadata_iterator_next and * FLAC__metadata_iterator_prev(). * - Get a block for reading or modification using * FLAC__metadata_iterator_get_block(). The pointer to the object * inside the chain is returned, so the block is yours to modify. * Changes will be reflected in the FLAC file when you write the * chain. You can also add and delete blocks (see functions below). * - When done, write out the chain using FLAC__metadata_chain_write(). * Make sure to read the whole comment to the function below. * - Delete the chain using FLAC__metadata_chain_delete(). * * \note * Even though the FLAC file is not open while the chain is being * manipulated, you must not alter the file externally during * this time. The chain assumes the FLAC file will not change * between the time of FLAC__metadata_chain_read()/FLAC__metadata_chain_read_ogg() * and FLAC__metadata_chain_write(). * * \note * Do not modify the is_last, length, or type fields of returned * FLAC__StreamMetadata objects. These are managed automatically. * * \note * The metadata objects returned by FLAC__metadata_iterator_get_block() * are owned by the chain; do not FLAC__metadata_object_delete() them. * In the same way, blocks passed to FLAC__metadata_iterator_set_block() * become owned by the chain and they will be deleted when the chain is * deleted. * * \{ */ struct FLAC__Metadata_Chain; /** The opaque structure definition for the level 2 chain type. */ typedef struct FLAC__Metadata_Chain FLAC__Metadata_Chain; struct FLAC__Metadata_Iterator; /** The opaque structure definition for the level 2 iterator type. */ typedef struct FLAC__Metadata_Iterator FLAC__Metadata_Iterator; typedef enum { FLAC__METADATA_CHAIN_STATUS_OK = 0, /**< The chain is in the normal OK state */ FLAC__METADATA_CHAIN_STATUS_ILLEGAL_INPUT, /**< The data passed into a function violated the function's usage criteria */ FLAC__METADATA_CHAIN_STATUS_ERROR_OPENING_FILE, /**< The chain could not open the target file */ FLAC__METADATA_CHAIN_STATUS_NOT_A_FLAC_FILE, /**< The chain could not find the FLAC signature at the start of the file */ FLAC__METADATA_CHAIN_STATUS_NOT_WRITABLE, /**< The chain tried to write to a file that was not writable */ FLAC__METADATA_CHAIN_STATUS_BAD_METADATA, /**< The chain encountered input that does not conform to the FLAC metadata specification */ FLAC__METADATA_CHAIN_STATUS_READ_ERROR, /**< The chain encountered an error while reading the FLAC file */ FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR, /**< The chain encountered an error while seeking in the FLAC file */ FLAC__METADATA_CHAIN_STATUS_WRITE_ERROR, /**< The chain encountered an error while writing the FLAC file */ FLAC__METADATA_CHAIN_STATUS_RENAME_ERROR, /**< The chain encountered an error renaming the FLAC file */ FLAC__METADATA_CHAIN_STATUS_UNLINK_ERROR, /**< The chain encountered an error removing the temporary file */ FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR, /**< Memory allocation failed */ FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR, /**< The caller violated an assertion or an unexpected error occurred */ FLAC__METADATA_CHAIN_STATUS_INVALID_CALLBACKS, /**< One or more of the required callbacks was NULL */ FLAC__METADATA_CHAIN_STATUS_READ_WRITE_MISMATCH, /**< FLAC__metadata_chain_write() was called on a chain read by * FLAC__metadata_chain_read_with_callbacks()/FLAC__metadata_chain_read_ogg_with_callbacks(), * or * FLAC__metadata_chain_write_with_callbacks()/FLAC__metadata_chain_write_with_callbacks_and_tempfile() * was called on a chain read by * FLAC__metadata_chain_read()/FLAC__metadata_chain_read_ogg(). * Matching read/write methods must always be used. */ FLAC__METADATA_CHAIN_STATUS_WRONG_WRITE_CALL /**< FLAC__metadata_chain_write_with_callbacks() was called when the * chain write requires a tempfile; use * FLAC__metadata_chain_write_with_callbacks_and_tempfile() instead. * Or, FLAC__metadata_chain_write_with_callbacks_and_tempfile() was * called when the chain write does not require a tempfile; use * FLAC__metadata_chain_write_with_callbacks() instead. * Always check FLAC__metadata_chain_check_if_tempfile_needed() * before writing via callbacks. */ } FLAC__Metadata_ChainStatus; /** Maps a FLAC__Metadata_ChainStatus to a C string. * * Using a FLAC__Metadata_ChainStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__Metadata_ChainStatusString[]; /*********** FLAC__Metadata_Chain ***********/ /** Create a new chain instance. * * \retval FLAC__Metadata_Chain* * \c NULL if there was an error allocating memory, else the new instance. */ FLAC_API FLAC__Metadata_Chain *FLAC__metadata_chain_new(void); /** Free a chain instance. Deletes the object pointed to by \a chain. * * \param chain A pointer to an existing chain. * \assert * \code chain != NULL \endcode */ FLAC_API void FLAC__metadata_chain_delete(FLAC__Metadata_Chain *chain); /** Get the current status of the chain. Call this after a function * returns \c false to get the reason for the error. Also resets the * status to FLAC__METADATA_CHAIN_STATUS_OK. * * \param chain A pointer to an existing chain. * \assert * \code chain != NULL \endcode * \retval FLAC__Metadata_ChainStatus * The current status of the chain. */ FLAC_API FLAC__Metadata_ChainStatus FLAC__metadata_chain_status(FLAC__Metadata_Chain *chain); /** Read all metadata from a FLAC file into the chain. * * \param chain A pointer to an existing chain. * \param filename The path to the FLAC file to read. * \assert * \code chain != NULL \endcode * \code filename != NULL \endcode * \retval FLAC__bool * \c true if a valid list of metadata blocks was read from * \a filename, else \c false. On failure, check the status with * FLAC__metadata_chain_status(). */ FLAC_API FLAC__bool FLAC__metadata_chain_read(FLAC__Metadata_Chain *chain, const char *filename); /** Read all metadata from an Ogg FLAC file into the chain. * * \note Ogg FLAC metadata data writing is not supported yet and * FLAC__metadata_chain_write() will fail. * * \param chain A pointer to an existing chain. * \param filename The path to the Ogg FLAC file to read. * \assert * \code chain != NULL \endcode * \code filename != NULL \endcode * \retval FLAC__bool * \c true if a valid list of metadata blocks was read from * \a filename, else \c false. On failure, check the status with * FLAC__metadata_chain_status(). */ FLAC_API FLAC__bool FLAC__metadata_chain_read_ogg(FLAC__Metadata_Chain *chain, const char *filename); /** Read all metadata from a FLAC stream into the chain via I/O callbacks. * * The \a handle need only be open for reading, but must be seekable. * The equivalent minimum stdio fopen() file mode is \c "r" (or \c "rb" * for Windows). * * \param chain A pointer to an existing chain. * \param handle The I/O handle of the FLAC stream to read. The * handle will NOT be closed after the metadata is read; * that is the duty of the caller. * \param callbacks * A set of callbacks to use for I/O. The mandatory * callbacks are \a read, \a seek, and \a tell. * \assert * \code chain != NULL \endcode * \retval FLAC__bool * \c true if a valid list of metadata blocks was read from * \a handle, else \c false. On failure, check the status with * FLAC__metadata_chain_status(). */ FLAC_API FLAC__bool FLAC__metadata_chain_read_with_callbacks(FLAC__Metadata_Chain *chain, FLAC__IOHandle handle, FLAC__IOCallbacks callbacks); /** Read all metadata from an Ogg FLAC stream into the chain via I/O callbacks. * * The \a handle need only be open for reading, but must be seekable. * The equivalent minimum stdio fopen() file mode is \c "r" (or \c "rb" * for Windows). * * \note Ogg FLAC metadata data writing is not supported yet and * FLAC__metadata_chain_write() will fail. * * \param chain A pointer to an existing chain. * \param handle The I/O handle of the Ogg FLAC stream to read. The * handle will NOT be closed after the metadata is read; * that is the duty of the caller. * \param callbacks * A set of callbacks to use for I/O. The mandatory * callbacks are \a read, \a seek, and \a tell. * \assert * \code chain != NULL \endcode * \retval FLAC__bool * \c true if a valid list of metadata blocks was read from * \a handle, else \c false. On failure, check the status with * FLAC__metadata_chain_status(). */ FLAC_API FLAC__bool FLAC__metadata_chain_read_ogg_with_callbacks(FLAC__Metadata_Chain *chain, FLAC__IOHandle handle, FLAC__IOCallbacks callbacks); /** Checks if writing the given chain would require the use of a * temporary file, or if it could be written in place. * * Under certain conditions, padding can be utilized so that writing * edited metadata back to the FLAC file does not require rewriting the * entire file. If rewriting is required, then a temporary workfile is * required. When writing metadata using callbacks, you must check * this function to know whether to call * FLAC__metadata_chain_write_with_callbacks() or * FLAC__metadata_chain_write_with_callbacks_and_tempfile(). When * writing with FLAC__metadata_chain_write(), the temporary file is * handled internally. * * \param chain A pointer to an existing chain. * \param use_padding * Whether or not padding will be allowed to be used * during the write. The value of \a use_padding given * here must match the value later passed to * FLAC__metadata_chain_write_with_callbacks() or * FLAC__metadata_chain_write_with_callbacks_with_tempfile(). * \assert * \code chain != NULL \endcode * \retval FLAC__bool * \c true if writing the current chain would require a tempfile, or * \c false if metadata can be written in place. */ FLAC_API FLAC__bool FLAC__metadata_chain_check_if_tempfile_needed(FLAC__Metadata_Chain *chain, FLAC__bool use_padding); /** Write all metadata out to the FLAC file. This function tries to be as * efficient as possible; how the metadata is actually written is shown by * the following: * * If the current chain is the same size as the existing metadata, the new * data is written in place. * * If the current chain is longer than the existing metadata, and * \a use_padding is \c true, and the last block is a PADDING block of * sufficient length, the function will truncate the final padding block * so that the overall size of the metadata is the same as the existing * metadata, and then just rewrite the metadata. Otherwise, if not all of * the above conditions are met, the entire FLAC file must be rewritten. * If you want to use padding this way it is a good idea to call * FLAC__metadata_chain_sort_padding() first so that you have the maximum * amount of padding to work with, unless you need to preserve ordering * of the PADDING blocks for some reason. * * If the current chain is shorter than the existing metadata, and * \a use_padding is \c true, and the final block is a PADDING block, the padding * is extended to make the overall size the same as the existing data. If * \a use_padding is \c true and the last block is not a PADDING block, a new * PADDING block is added to the end of the new data to make it the same * size as the existing data (if possible, see the note to * FLAC__metadata_simple_iterator_set_block() about the four byte limit) * and the new data is written in place. If none of the above apply or * \a use_padding is \c false, the entire FLAC file is rewritten. * * If \a preserve_file_stats is \c true, the owner and modification time will * be preserved even if the FLAC file is written. * * For this write function to be used, the chain must have been read with * FLAC__metadata_chain_read()/FLAC__metadata_chain_read_ogg(), not * FLAC__metadata_chain_read_with_callbacks()/FLAC__metadata_chain_read_ogg_with_callbacks(). * * \param chain A pointer to an existing chain. * \param use_padding See above. * \param preserve_file_stats See above. * \assert * \code chain != NULL \endcode * \retval FLAC__bool * \c true if the write succeeded, else \c false. On failure, * check the status with FLAC__metadata_chain_status(). */ FLAC_API FLAC__bool FLAC__metadata_chain_write(FLAC__Metadata_Chain *chain, FLAC__bool use_padding, FLAC__bool preserve_file_stats); /** Write all metadata out to a FLAC stream via callbacks. * * (See FLAC__metadata_chain_write() for the details on how padding is * used to write metadata in place if possible.) * * The \a handle must be open for updating and be seekable. The * equivalent minimum stdio fopen() file mode is \c "r+" (or \c "r+b" * for Windows). * * For this write function to be used, the chain must have been read with * FLAC__metadata_chain_read_with_callbacks()/FLAC__metadata_chain_read_ogg_with_callbacks(), * not FLAC__metadata_chain_read()/FLAC__metadata_chain_read_ogg(). * Also, FLAC__metadata_chain_check_if_tempfile_needed() must have returned * \c false. * * \param chain A pointer to an existing chain. * \param use_padding See FLAC__metadata_chain_write() * \param handle The I/O handle of the FLAC stream to write. The * handle will NOT be closed after the metadata is * written; that is the duty of the caller. * \param callbacks A set of callbacks to use for I/O. The mandatory * callbacks are \a write and \a seek. * \assert * \code chain != NULL \endcode * \retval FLAC__bool * \c true if the write succeeded, else \c false. On failure, * check the status with FLAC__metadata_chain_status(). */ FLAC_API FLAC__bool FLAC__metadata_chain_write_with_callbacks(FLAC__Metadata_Chain *chain, FLAC__bool use_padding, FLAC__IOHandle handle, FLAC__IOCallbacks callbacks); /** Write all metadata out to a FLAC stream via callbacks. * * (See FLAC__metadata_chain_write() for the details on how padding is * used to write metadata in place if possible.) * * This version of the write-with-callbacks function must be used when * FLAC__metadata_chain_check_if_tempfile_needed() returns true. In * this function, you must supply an I/O handle corresponding to the * FLAC file to edit, and a temporary handle to which the new FLAC * file will be written. It is the caller's job to move this temporary * FLAC file on top of the original FLAC file to complete the metadata * edit. * * The \a handle must be open for reading and be seekable. The * equivalent minimum stdio fopen() file mode is \c "r" (or \c "rb" * for Windows). * * The \a temp_handle must be open for writing. The * equivalent minimum stdio fopen() file mode is \c "w" (or \c "wb" * for Windows). It should be an empty stream, or at least positioned * at the start-of-file (in which case it is the caller's duty to * truncate it on return). * * For this write function to be used, the chain must have been read with * FLAC__metadata_chain_read_with_callbacks()/FLAC__metadata_chain_read_ogg_with_callbacks(), * not FLAC__metadata_chain_read()/FLAC__metadata_chain_read_ogg(). * Also, FLAC__metadata_chain_check_if_tempfile_needed() must have returned * \c true. * * \param chain A pointer to an existing chain. * \param use_padding See FLAC__metadata_chain_write() * \param handle The I/O handle of the original FLAC stream to read. * The handle will NOT be closed after the metadata is * written; that is the duty of the caller. * \param callbacks A set of callbacks to use for I/O on \a handle. * The mandatory callbacks are \a read, \a seek, and * \a eof. * \param temp_handle The I/O handle of the FLAC stream to write. The * handle will NOT be closed after the metadata is * written; that is the duty of the caller. * \param temp_callbacks * A set of callbacks to use for I/O on temp_handle. * The only mandatory callback is \a write. * \assert * \code chain != NULL \endcode * \retval FLAC__bool * \c true if the write succeeded, else \c false. On failure, * check the status with FLAC__metadata_chain_status(). */ FLAC_API FLAC__bool FLAC__metadata_chain_write_with_callbacks_and_tempfile(FLAC__Metadata_Chain *chain, FLAC__bool use_padding, FLAC__IOHandle handle, FLAC__IOCallbacks callbacks, FLAC__IOHandle temp_handle, FLAC__IOCallbacks temp_callbacks); /** Merge adjacent PADDING blocks into a single block. * * \note This function does not write to the FLAC file, it only * modifies the chain. * * \warning Any iterator on the current chain will become invalid after this * call. You should delete the iterator and get a new one. * * \param chain A pointer to an existing chain. * \assert * \code chain != NULL \endcode */ FLAC_API void FLAC__metadata_chain_merge_padding(FLAC__Metadata_Chain *chain); /** This function will move all PADDING blocks to the end on the metadata, * then merge them into a single block. * * \note This function does not write to the FLAC file, it only * modifies the chain. * * \warning Any iterator on the current chain will become invalid after this * call. You should delete the iterator and get a new one. * * \param chain A pointer to an existing chain. * \assert * \code chain != NULL \endcode */ FLAC_API void FLAC__metadata_chain_sort_padding(FLAC__Metadata_Chain *chain); /*********** FLAC__Metadata_Iterator ***********/ /** Create a new iterator instance. * * \retval FLAC__Metadata_Iterator* * \c NULL if there was an error allocating memory, else the new instance. */ FLAC_API FLAC__Metadata_Iterator *FLAC__metadata_iterator_new(void); /** Free an iterator instance. Deletes the object pointed to by \a iterator. * * \param iterator A pointer to an existing iterator. * \assert * \code iterator != NULL \endcode */ FLAC_API void FLAC__metadata_iterator_delete(FLAC__Metadata_Iterator *iterator); /** Initialize the iterator to point to the first metadata block in the * given chain. * * \param iterator A pointer to an existing iterator. * \param chain A pointer to an existing and initialized (read) chain. * \assert * \code iterator != NULL \endcode * \code chain != NULL \endcode */ FLAC_API void FLAC__metadata_iterator_init(FLAC__Metadata_Iterator *iterator, FLAC__Metadata_Chain *chain); /** Moves the iterator forward one metadata block, returning \c false if * already at the end. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_iterator_init() * \retval FLAC__bool * \c false if already at the last metadata block of the chain, else * \c true. */ FLAC_API FLAC__bool FLAC__metadata_iterator_next(FLAC__Metadata_Iterator *iterator); /** Moves the iterator backward one metadata block, returning \c false if * already at the beginning. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_iterator_init() * \retval FLAC__bool * \c false if already at the first metadata block of the chain, else * \c true. */ FLAC_API FLAC__bool FLAC__metadata_iterator_prev(FLAC__Metadata_Iterator *iterator); /** Get the type of the metadata block at the current position. * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_iterator_init() * \retval FLAC__MetadataType * The type of the metadata block at the current iterator position. */ FLAC_API FLAC__MetadataType FLAC__metadata_iterator_get_block_type(const FLAC__Metadata_Iterator *iterator); /** Get the metadata block at the current position. You can modify * the block in place but must write the chain before the changes * are reflected to the FLAC file. You do not need to call * FLAC__metadata_iterator_set_block() to reflect the changes; * the pointer returned by FLAC__metadata_iterator_get_block() * points directly into the chain. * * \warning * Do not call FLAC__metadata_object_delete() on the returned object; * to delete a block use FLAC__metadata_iterator_delete_block(). * * \param iterator A pointer to an existing initialized iterator. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_iterator_init() * \retval FLAC__StreamMetadata* * The current metadata block. */ FLAC_API FLAC__StreamMetadata *FLAC__metadata_iterator_get_block(FLAC__Metadata_Iterator *iterator); /** Set the metadata block at the current position, replacing the existing * block. The new block passed in becomes owned by the chain and it will be * deleted when the chain is deleted. * * \param iterator A pointer to an existing initialized iterator. * \param block A pointer to a metadata block. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_iterator_init() * \code block != NULL \endcode * \retval FLAC__bool * \c false if the conditions in the above description are not met, or * a memory allocation error occurs, otherwise \c true. */ FLAC_API FLAC__bool FLAC__metadata_iterator_set_block(FLAC__Metadata_Iterator *iterator, FLAC__StreamMetadata *block); /** Removes the current block from the chain. If \a replace_with_padding is * \c true, the block will instead be replaced with a padding block of equal * size. You can not delete the STREAMINFO block. The iterator will be * left pointing to the block before the one just "deleted", even if * \a replace_with_padding is \c true. * * \param iterator A pointer to an existing initialized iterator. * \param replace_with_padding See above. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_iterator_init() * \retval FLAC__bool * \c false if the conditions in the above description are not met, * otherwise \c true. */ FLAC_API FLAC__bool FLAC__metadata_iterator_delete_block(FLAC__Metadata_Iterator *iterator, FLAC__bool replace_with_padding); /** Insert a new block before the current block. You cannot insert a block * before the first STREAMINFO block. You cannot insert a STREAMINFO block * as there can be only one, the one that already exists at the head when you * read in a chain. The chain takes ownership of the new block and it will be * deleted when the chain is deleted. The iterator will be left pointing to * the new block. * * \param iterator A pointer to an existing initialized iterator. * \param block A pointer to a metadata block to insert. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_iterator_init() * \retval FLAC__bool * \c false if the conditions in the above description are not met, or * a memory allocation error occurs, otherwise \c true. */ FLAC_API FLAC__bool FLAC__metadata_iterator_insert_block_before(FLAC__Metadata_Iterator *iterator, FLAC__StreamMetadata *block); /** Insert a new block after the current block. You cannot insert a STREAMINFO * block as there can be only one, the one that already exists at the head when * you read in a chain. The chain takes ownership of the new block and it will * be deleted when the chain is deleted. The iterator will be left pointing to * the new block. * * \param iterator A pointer to an existing initialized iterator. * \param block A pointer to a metadata block to insert. * \assert * \code iterator != NULL \endcode * \a iterator has been successfully initialized with * FLAC__metadata_iterator_init() * \retval FLAC__bool * \c false if the conditions in the above description are not met, or * a memory allocation error occurs, otherwise \c true. */ FLAC_API FLAC__bool FLAC__metadata_iterator_insert_block_after(FLAC__Metadata_Iterator *iterator, FLAC__StreamMetadata *block); /* \} */ /** \defgroup flac_metadata_object FLAC/metadata.h: metadata object methods * \ingroup flac_metadata * * \brief * This module contains methods for manipulating FLAC metadata objects. * * Since many are variable length we have to be careful about the memory * management. We decree that all pointers to data in the object are * owned by the object and memory-managed by the object. * * Use the FLAC__metadata_object_new() and FLAC__metadata_object_delete() * functions to create all instances. When using the * FLAC__metadata_object_set_*() functions to set pointers to data, set * \a copy to \c true to have the function make it's own copy of the data, or * to \c false to give the object ownership of your data. In the latter case * your pointer must be freeable by free() and will be free()d when the object * is FLAC__metadata_object_delete()d. It is legal to pass a null pointer as * the data pointer to a FLAC__metadata_object_set_*() function as long as * the length argument is 0 and the \a copy argument is \c false. * * The FLAC__metadata_object_new() and FLAC__metadata_object_clone() function * will return \c NULL in the case of a memory allocation error, otherwise a new * object. The FLAC__metadata_object_set_*() functions return \c false in the * case of a memory allocation error. * * We don't have the convenience of C++ here, so note that the library relies * on you to keep the types straight. In other words, if you pass, for * example, a FLAC__StreamMetadata* that represents a STREAMINFO block to * FLAC__metadata_object_application_set_data(), you will get an assertion * failure. * * For convenience the FLAC__metadata_object_vorbiscomment_*() functions * maintain a trailing NUL on each Vorbis comment entry. This is not counted * toward the length or stored in the stream, but it can make working with plain * comments (those that don't contain embedded-NULs in the value) easier. * Entries passed into these functions have trailing NULs added if missing, and * returned entries are guaranteed to have a trailing NUL. * * The FLAC__metadata_object_vorbiscomment_*() functions that take a Vorbis * comment entry/name/value will first validate that it complies with the Vorbis * comment specification and return false if it does not. * * There is no need to recalculate the length field on metadata blocks you * have modified. They will be calculated automatically before they are * written back to a file. * * \{ */ /** Create a new metadata object instance of the given type. * * The object will be "empty"; i.e. values and data pointers will be \c 0, * with the exception of FLAC__METADATA_TYPE_VORBIS_COMMENT, which will have * the vendor string set (but zero comments). * * Do not pass in a value greater than or equal to * \a FLAC__METADATA_TYPE_UNDEFINED unless you really know what you're * doing. * * \param type Type of object to create * \retval FLAC__StreamMetadata* * \c NULL if there was an error allocating memory or the type code is * greater than FLAC__MAX_METADATA_TYPE_CODE, else the new instance. */ FLAC_API FLAC__StreamMetadata *FLAC__metadata_object_new(FLAC__MetadataType type); /** Create a copy of an existing metadata object. * * The copy is a "deep" copy, i.e. dynamically allocated data within the * object is also copied. The caller takes ownership of the new block and * is responsible for freeing it with FLAC__metadata_object_delete(). * * \param object Pointer to object to copy. * \assert * \code object != NULL \endcode * \retval FLAC__StreamMetadata* * \c NULL if there was an error allocating memory, else the new instance. */ FLAC_API FLAC__StreamMetadata *FLAC__metadata_object_clone(const FLAC__StreamMetadata *object); /** Free a metadata object. Deletes the object pointed to by \a object. * * The delete is a "deep" delete, i.e. dynamically allocated data within the * object is also deleted. * * \param object A pointer to an existing object. * \assert * \code object != NULL \endcode */ FLAC_API void FLAC__metadata_object_delete(FLAC__StreamMetadata *object); /** Compares two metadata objects. * * The compare is "deep", i.e. dynamically allocated data within the * object is also compared. * * \param block1 A pointer to an existing object. * \param block2 A pointer to an existing object. * \assert * \code block1 != NULL \endcode * \code block2 != NULL \endcode * \retval FLAC__bool * \c true if objects are identical, else \c false. */ FLAC_API FLAC__bool FLAC__metadata_object_is_equal(const FLAC__StreamMetadata *block1, const FLAC__StreamMetadata *block2); /** Sets the application data of an APPLICATION block. * * If \a copy is \c true, a copy of the data is stored; otherwise, the object * takes ownership of the pointer. The existing data will be freed if this * function is successful, otherwise the original data will remain if \a copy * is \c true and malloc() fails. * * \note It is safe to pass a const pointer to \a data if \a copy is \c true. * * \param object A pointer to an existing APPLICATION object. * \param data A pointer to the data to set. * \param length The length of \a data in bytes. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_APPLICATION \endcode * \code (data != NULL && length > 0) || * (data == NULL && length == 0 && copy == false) \endcode * \retval FLAC__bool * \c false if \a copy is \c true and malloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_application_set_data(FLAC__StreamMetadata *object, FLAC__byte *data, unsigned length, FLAC__bool copy); /** Resize the seekpoint array. * * If the size shrinks, elements will truncated; if it grows, new placeholder * points will be added to the end. * * \param object A pointer to an existing SEEKTABLE object. * \param new_num_points The desired length of the array; may be \c 0. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \code (object->data.seek_table.points == NULL && object->data.seek_table.num_points == 0) || * (object->data.seek_table.points != NULL && object->data.seek_table.num_points > 0) \endcode * \retval FLAC__bool * \c false if memory allocation error, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_resize_points(FLAC__StreamMetadata *object, unsigned new_num_points); /** Set a seekpoint in a seektable. * * \param object A pointer to an existing SEEKTABLE object. * \param point_num Index into seekpoint array to set. * \param point The point to set. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \code object->data.seek_table.num_points > point_num \endcode */ FLAC_API void FLAC__metadata_object_seektable_set_point(FLAC__StreamMetadata *object, unsigned point_num, FLAC__StreamMetadata_SeekPoint point); /** Insert a seekpoint into a seektable. * * \param object A pointer to an existing SEEKTABLE object. * \param point_num Index into seekpoint array to set. * \param point The point to set. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \code object->data.seek_table.num_points >= point_num \endcode * \retval FLAC__bool * \c false if memory allocation error, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_insert_point(FLAC__StreamMetadata *object, unsigned point_num, FLAC__StreamMetadata_SeekPoint point); /** Delete a seekpoint from a seektable. * * \param object A pointer to an existing SEEKTABLE object. * \param point_num Index into seekpoint array to set. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \code object->data.seek_table.num_points > point_num \endcode * \retval FLAC__bool * \c false if memory allocation error, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_delete_point(FLAC__StreamMetadata *object, unsigned point_num); /** Check a seektable to see if it conforms to the FLAC specification. * See the format specification for limits on the contents of the * seektable. * * \param object A pointer to an existing SEEKTABLE object. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \retval FLAC__bool * \c false if seek table is illegal, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_is_legal(const FLAC__StreamMetadata *object); /** Append a number of placeholder points to the end of a seek table. * * \note * As with the other ..._seektable_template_... functions, you should * call FLAC__metadata_object_seektable_template_sort() when finished * to make the seek table legal. * * \param object A pointer to an existing SEEKTABLE object. * \param num The number of placeholder points to append. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \retval FLAC__bool * \c false if memory allocation fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_placeholders(FLAC__StreamMetadata *object, unsigned num); /** Append a specific seek point template to the end of a seek table. * * \note * As with the other ..._seektable_template_... functions, you should * call FLAC__metadata_object_seektable_template_sort() when finished * to make the seek table legal. * * \param object A pointer to an existing SEEKTABLE object. * \param sample_number The sample number of the seek point template. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \retval FLAC__bool * \c false if memory allocation fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_point(FLAC__StreamMetadata *object, FLAC__uint64 sample_number); /** Append specific seek point templates to the end of a seek table. * * \note * As with the other ..._seektable_template_... functions, you should * call FLAC__metadata_object_seektable_template_sort() when finished * to make the seek table legal. * * \param object A pointer to an existing SEEKTABLE object. * \param sample_numbers An array of sample numbers for the seek points. * \param num The number of seek point templates to append. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \retval FLAC__bool * \c false if memory allocation fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_points(FLAC__StreamMetadata *object, FLAC__uint64 sample_numbers[], unsigned num); /** Append a set of evenly-spaced seek point templates to the end of a * seek table. * * \note * As with the other ..._seektable_template_... functions, you should * call FLAC__metadata_object_seektable_template_sort() when finished * to make the seek table legal. * * \param object A pointer to an existing SEEKTABLE object. * \param num The number of placeholder points to append. * \param total_samples The total number of samples to be encoded; * the seekpoints will be spaced approximately * \a total_samples / \a num samples apart. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \code total_samples > 0 \endcode * \retval FLAC__bool * \c false if memory allocation fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_spaced_points(FLAC__StreamMetadata *object, unsigned num, FLAC__uint64 total_samples); /** Append a set of evenly-spaced seek point templates to the end of a * seek table. * * \note * As with the other ..._seektable_template_... functions, you should * call FLAC__metadata_object_seektable_template_sort() when finished * to make the seek table legal. * * \param object A pointer to an existing SEEKTABLE object. * \param samples The number of samples apart to space the placeholder * points. The first point will be at sample \c 0, the * second at sample \a samples, then 2*\a samples, and * so on. As long as \a samples and \a total_samples * are greater than \c 0, there will always be at least * one seekpoint at sample \c 0. * \param total_samples The total number of samples to be encoded; * the seekpoints will be spaced * \a samples samples apart. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \code samples > 0 \endcode * \code total_samples > 0 \endcode * \retval FLAC__bool * \c false if memory allocation fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_spaced_points_by_samples(FLAC__StreamMetadata *object, unsigned samples, FLAC__uint64 total_samples); /** Sort a seek table's seek points according to the format specification, * removing duplicates. * * \param object A pointer to a seek table to be sorted. * \param compact If \c false, behaves like FLAC__format_seektable_sort(). * If \c true, duplicates are deleted and the seek table is * shrunk appropriately; the number of placeholder points * present in the seek table will be the same after the call * as before. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_SEEKTABLE \endcode * \retval FLAC__bool * \c false if realloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_sort(FLAC__StreamMetadata *object, FLAC__bool compact); /** Sets the vendor string in a VORBIS_COMMENT block. * * For convenience, a trailing NUL is added to the entry if it doesn't have * one already. * * If \a copy is \c true, a copy of the entry is stored; otherwise, the object * takes ownership of the \c entry.entry pointer. * * \note If this function returns \c false, the caller still owns the * pointer. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param entry The entry to set the vendor string to. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \code (entry.entry != NULL && entry.length > 0) || * (entry.entry == NULL && entry.length == 0) \endcode * \retval FLAC__bool * \c false if memory allocation fails or \a entry does not comply with the * Vorbis comment specification, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_set_vendor_string(FLAC__StreamMetadata *object, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool copy); /** Resize the comment array. * * If the size shrinks, elements will truncated; if it grows, new empty * fields will be added to the end. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param new_num_comments The desired length of the array; may be \c 0. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \code (object->data.vorbis_comment.comments == NULL && object->data.vorbis_comment.num_comments == 0) || * (object->data.vorbis_comment.comments != NULL && object->data.vorbis_comment.num_comments > 0) \endcode * \retval FLAC__bool * \c false if memory allocation fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_resize_comments(FLAC__StreamMetadata *object, unsigned new_num_comments); /** Sets a comment in a VORBIS_COMMENT block. * * For convenience, a trailing NUL is added to the entry if it doesn't have * one already. * * If \a copy is \c true, a copy of the entry is stored; otherwise, the object * takes ownership of the \c entry.entry pointer. * * \note If this function returns \c false, the caller still owns the * pointer. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param comment_num Index into comment array to set. * \param entry The entry to set the comment to. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \code comment_num < object->data.vorbis_comment.num_comments \endcode * \code (entry.entry != NULL && entry.length > 0) || * (entry.entry == NULL && entry.length == 0) \endcode * \retval FLAC__bool * \c false if memory allocation fails or \a entry does not comply with the * Vorbis comment specification, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_set_comment(FLAC__StreamMetadata *object, unsigned comment_num, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool copy); /** Insert a comment in a VORBIS_COMMENT block at the given index. * * For convenience, a trailing NUL is added to the entry if it doesn't have * one already. * * If \a copy is \c true, a copy of the entry is stored; otherwise, the object * takes ownership of the \c entry.entry pointer. * * \note If this function returns \c false, the caller still owns the * pointer. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param comment_num The index at which to insert the comment. The comments * at and after \a comment_num move right one position. * To append a comment to the end, set \a comment_num to * \c object->data.vorbis_comment.num_comments . * \param entry The comment to insert. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \code object->data.vorbis_comment.num_comments >= comment_num \endcode * \code (entry.entry != NULL && entry.length > 0) || * (entry.entry == NULL && entry.length == 0 && copy == false) \endcode * \retval FLAC__bool * \c false if memory allocation fails or \a entry does not comply with the * Vorbis comment specification, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_insert_comment(FLAC__StreamMetadata *object, unsigned comment_num, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool copy); /** Appends a comment to a VORBIS_COMMENT block. * * For convenience, a trailing NUL is added to the entry if it doesn't have * one already. * * If \a copy is \c true, a copy of the entry is stored; otherwise, the object * takes ownership of the \c entry.entry pointer. * * \note If this function returns \c false, the caller still owns the * pointer. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param entry The comment to insert. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \code (entry.entry != NULL && entry.length > 0) || * (entry.entry == NULL && entry.length == 0 && copy == false) \endcode * \retval FLAC__bool * \c false if memory allocation fails or \a entry does not comply with the * Vorbis comment specification, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_append_comment(FLAC__StreamMetadata *object, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool copy); /** Replaces comments in a VORBIS_COMMENT block with a new one. * * For convenience, a trailing NUL is added to the entry if it doesn't have * one already. * * Depending on the the value of \a all, either all or just the first comment * whose field name(s) match the given entry's name will be replaced by the * given entry. If no comments match, \a entry will simply be appended. * * If \a copy is \c true, a copy of the entry is stored; otherwise, the object * takes ownership of the \c entry.entry pointer. * * \note If this function returns \c false, the caller still owns the * pointer. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param entry The comment to insert. * \param all If \c true, all comments whose field name matches * \a entry's field name will be removed, and \a entry will * be inserted at the position of the first matching * comment. If \c false, only the first comment whose * field name matches \a entry's field name will be * replaced with \a entry. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \code (entry.entry != NULL && entry.length > 0) || * (entry.entry == NULL && entry.length == 0 && copy == false) \endcode * \retval FLAC__bool * \c false if memory allocation fails or \a entry does not comply with the * Vorbis comment specification, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_replace_comment(FLAC__StreamMetadata *object, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool all, FLAC__bool copy); /** Delete a comment in a VORBIS_COMMENT block at the given index. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param comment_num The index of the comment to delete. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \code object->data.vorbis_comment.num_comments > comment_num \endcode * \retval FLAC__bool * \c false if realloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_delete_comment(FLAC__StreamMetadata *object, unsigned comment_num); /** Creates a Vorbis comment entry from NUL-terminated name and value strings. * * On return, the filled-in \a entry->entry pointer will point to malloc()ed * memory and shall be owned by the caller. For convenience the entry will * have a terminating NUL. * * \param entry A pointer to a Vorbis comment entry. The entry's * \c entry pointer should not point to allocated * memory as it will be overwritten. * \param field_name The field name in ASCII, \c NUL terminated. * \param field_value The field value in UTF-8, \c NUL terminated. * \assert * \code entry != NULL \endcode * \code field_name != NULL \endcode * \code field_value != NULL \endcode * \retval FLAC__bool * \c false if malloc() fails, or if \a field_name or \a field_value does * not comply with the Vorbis comment specification, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_entry_from_name_value_pair(FLAC__StreamMetadata_VorbisComment_Entry *entry, const char *field_name, const char *field_value); /** Splits a Vorbis comment entry into NUL-terminated name and value strings. * * The returned pointers to name and value will be allocated by malloc() * and shall be owned by the caller. * * \param entry An existing Vorbis comment entry. * \param field_name The address of where the returned pointer to the * field name will be stored. * \param field_value The address of where the returned pointer to the * field value will be stored. * \assert * \code (entry.entry != NULL && entry.length > 0) \endcode * \code memchr(entry.entry, '=', entry.length) != NULL \endcode * \code field_name != NULL \endcode * \code field_value != NULL \endcode * \retval FLAC__bool * \c false if memory allocation fails or \a entry does not comply with the * Vorbis comment specification, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_entry_to_name_value_pair(const FLAC__StreamMetadata_VorbisComment_Entry entry, char **field_name, char **field_value); /** Check if the given Vorbis comment entry's field name matches the given * field name. * * \param entry An existing Vorbis comment entry. * \param field_name The field name to check. * \param field_name_length The length of \a field_name, not including the * terminating \c NUL. * \assert * \code (entry.entry != NULL && entry.length > 0) \endcode * \retval FLAC__bool * \c true if the field names match, else \c false */ FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_entry_matches(const FLAC__StreamMetadata_VorbisComment_Entry entry, const char *field_name, unsigned field_name_length); /** Find a Vorbis comment with the given field name. * * The search begins at entry number \a offset; use an offset of 0 to * search from the beginning of the comment array. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param offset The offset into the comment array from where to start * the search. * \param field_name The field name of the comment to find. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \code field_name != NULL \endcode * \retval int * The offset in the comment array of the first comment whose field * name matches \a field_name, or \c -1 if no match was found. */ FLAC_API int FLAC__metadata_object_vorbiscomment_find_entry_from(const FLAC__StreamMetadata *object, unsigned offset, const char *field_name); /** Remove first Vorbis comment matching the given field name. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param field_name The field name of comment to delete. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \retval int * \c -1 for memory allocation error, \c 0 for no matching entries, * \c 1 for one matching entry deleted. */ FLAC_API int FLAC__metadata_object_vorbiscomment_remove_entry_matching(FLAC__StreamMetadata *object, const char *field_name); /** Remove all Vorbis comments matching the given field name. * * \param object A pointer to an existing VORBIS_COMMENT object. * \param field_name The field name of comments to delete. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT \endcode * \retval int * \c -1 for memory allocation error, \c 0 for no matching entries, * else the number of matching entries deleted. */ FLAC_API int FLAC__metadata_object_vorbiscomment_remove_entries_matching(FLAC__StreamMetadata *object, const char *field_name); /** Create a new CUESHEET track instance. * * The object will be "empty"; i.e. values and data pointers will be \c 0. * * \retval FLAC__StreamMetadata_CueSheet_Track* * \c NULL if there was an error allocating memory, else the new instance. */ FLAC_API FLAC__StreamMetadata_CueSheet_Track *FLAC__metadata_object_cuesheet_track_new(void); /** Create a copy of an existing CUESHEET track object. * * The copy is a "deep" copy, i.e. dynamically allocated data within the * object is also copied. The caller takes ownership of the new object and * is responsible for freeing it with * FLAC__metadata_object_cuesheet_track_delete(). * * \param object Pointer to object to copy. * \assert * \code object != NULL \endcode * \retval FLAC__StreamMetadata_CueSheet_Track* * \c NULL if there was an error allocating memory, else the new instance. */ FLAC_API FLAC__StreamMetadata_CueSheet_Track *FLAC__metadata_object_cuesheet_track_clone(const FLAC__StreamMetadata_CueSheet_Track *object); /** Delete a CUESHEET track object * * \param object A pointer to an existing CUESHEET track object. * \assert * \code object != NULL \endcode */ FLAC_API void FLAC__metadata_object_cuesheet_track_delete(FLAC__StreamMetadata_CueSheet_Track *object); /** Resize a track's index point array. * * If the size shrinks, elements will truncated; if it grows, new blank * indices will be added to the end. * * \param object A pointer to an existing CUESHEET object. * \param track_num The index of the track to modify. NOTE: this is not * necessarily the same as the track's \a number field. * \param new_num_indices The desired length of the array; may be \c 0. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \code object->data.cue_sheet.num_tracks > track_num \endcode * \code (object->data.cue_sheet.tracks[track_num].indices == NULL && object->data.cue_sheet.tracks[track_num].num_indices == 0) || * (object->data.cue_sheet.tracks[track_num].indices != NULL && object->data.cue_sheet.tracks[track_num].num_indices > 0) \endcode * \retval FLAC__bool * \c false if memory allocation error, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_track_resize_indices(FLAC__StreamMetadata *object, unsigned track_num, unsigned new_num_indices); /** Insert an index point in a CUESHEET track at the given index. * * \param object A pointer to an existing CUESHEET object. * \param track_num The index of the track to modify. NOTE: this is not * necessarily the same as the track's \a number field. * \param index_num The index into the track's index array at which to * insert the index point. NOTE: this is not necessarily * the same as the index point's \a number field. The * indices at and after \a index_num move right one * position. To append an index point to the end, set * \a index_num to * \c object->data.cue_sheet.tracks[track_num].num_indices . * \param index The index point to insert. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \code object->data.cue_sheet.num_tracks > track_num \endcode * \code object->data.cue_sheet.tracks[track_num].num_indices >= index_num \endcode * \retval FLAC__bool * \c false if realloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_track_insert_index(FLAC__StreamMetadata *object, unsigned track_num, unsigned index_num, FLAC__StreamMetadata_CueSheet_Index index); /** Insert a blank index point in a CUESHEET track at the given index. * * A blank index point is one in which all field values are zero. * * \param object A pointer to an existing CUESHEET object. * \param track_num The index of the track to modify. NOTE: this is not * necessarily the same as the track's \a number field. * \param index_num The index into the track's index array at which to * insert the index point. NOTE: this is not necessarily * the same as the index point's \a number field. The * indices at and after \a index_num move right one * position. To append an index point to the end, set * \a index_num to * \c object->data.cue_sheet.tracks[track_num].num_indices . * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \code object->data.cue_sheet.num_tracks > track_num \endcode * \code object->data.cue_sheet.tracks[track_num].num_indices >= index_num \endcode * \retval FLAC__bool * \c false if realloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_track_insert_blank_index(FLAC__StreamMetadata *object, unsigned track_num, unsigned index_num); /** Delete an index point in a CUESHEET track at the given index. * * \param object A pointer to an existing CUESHEET object. * \param track_num The index into the track array of the track to * modify. NOTE: this is not necessarily the same * as the track's \a number field. * \param index_num The index into the track's index array of the index * to delete. NOTE: this is not necessarily the same * as the index's \a number field. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \code object->data.cue_sheet.num_tracks > track_num \endcode * \code object->data.cue_sheet.tracks[track_num].num_indices > index_num \endcode * \retval FLAC__bool * \c false if realloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_track_delete_index(FLAC__StreamMetadata *object, unsigned track_num, unsigned index_num); /** Resize the track array. * * If the size shrinks, elements will truncated; if it grows, new blank * tracks will be added to the end. * * \param object A pointer to an existing CUESHEET object. * \param new_num_tracks The desired length of the array; may be \c 0. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \code (object->data.cue_sheet.tracks == NULL && object->data.cue_sheet.num_tracks == 0) || * (object->data.cue_sheet.tracks != NULL && object->data.cue_sheet.num_tracks > 0) \endcode * \retval FLAC__bool * \c false if memory allocation error, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_resize_tracks(FLAC__StreamMetadata *object, unsigned new_num_tracks); /** Sets a track in a CUESHEET block. * * If \a copy is \c true, a copy of the track is stored; otherwise, the object * takes ownership of the \a track pointer. * * \param object A pointer to an existing CUESHEET object. * \param track_num Index into track array to set. NOTE: this is not * necessarily the same as the track's \a number field. * \param track The track to set the track to. You may safely pass in * a const pointer if \a copy is \c true. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \code track_num < object->data.cue_sheet.num_tracks \endcode * \code (track->indices != NULL && track->num_indices > 0) || * (track->indices == NULL && track->num_indices == 0) * \retval FLAC__bool * \c false if \a copy is \c true and malloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_set_track(FLAC__StreamMetadata *object, unsigned track_num, FLAC__StreamMetadata_CueSheet_Track *track, FLAC__bool copy); /** Insert a track in a CUESHEET block at the given index. * * If \a copy is \c true, a copy of the track is stored; otherwise, the object * takes ownership of the \a track pointer. * * \param object A pointer to an existing CUESHEET object. * \param track_num The index at which to insert the track. NOTE: this * is not necessarily the same as the track's \a number * field. The tracks at and after \a track_num move right * one position. To append a track to the end, set * \a track_num to \c object->data.cue_sheet.num_tracks . * \param track The track to insert. You may safely pass in a const * pointer if \a copy is \c true. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \code object->data.cue_sheet.num_tracks >= track_num \endcode * \retval FLAC__bool * \c false if \a copy is \c true and malloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_insert_track(FLAC__StreamMetadata *object, unsigned track_num, FLAC__StreamMetadata_CueSheet_Track *track, FLAC__bool copy); /** Insert a blank track in a CUESHEET block at the given index. * * A blank track is one in which all field values are zero. * * \param object A pointer to an existing CUESHEET object. * \param track_num The index at which to insert the track. NOTE: this * is not necessarily the same as the track's \a number * field. The tracks at and after \a track_num move right * one position. To append a track to the end, set * \a track_num to \c object->data.cue_sheet.num_tracks . * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \code object->data.cue_sheet.num_tracks >= track_num \endcode * \retval FLAC__bool * \c false if \a copy is \c true and malloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_insert_blank_track(FLAC__StreamMetadata *object, unsigned track_num); /** Delete a track in a CUESHEET block at the given index. * * \param object A pointer to an existing CUESHEET object. * \param track_num The index into the track array of the track to * delete. NOTE: this is not necessarily the same * as the track's \a number field. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \code object->data.cue_sheet.num_tracks > track_num \endcode * \retval FLAC__bool * \c false if realloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_delete_track(FLAC__StreamMetadata *object, unsigned track_num); /** Check a cue sheet to see if it conforms to the FLAC specification. * See the format specification for limits on the contents of the * cue sheet. * * \param object A pointer to an existing CUESHEET object. * \param check_cd_da_subset If \c true, check CUESHEET against more * stringent requirements for a CD-DA (audio) disc. * \param violation Address of a pointer to a string. If there is a * violation, a pointer to a string explanation of the * violation will be returned here. \a violation may be * \c NULL if you don't need the returned string. Do not * free the returned string; it will always point to static * data. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \retval FLAC__bool * \c false if cue sheet is illegal, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_is_legal(const FLAC__StreamMetadata *object, FLAC__bool check_cd_da_subset, const char **violation); /** Calculate and return the CDDB/freedb ID for a cue sheet. The function * assumes the cue sheet corresponds to a CD; the result is undefined * if the cuesheet's is_cd bit is not set. * * \param object A pointer to an existing CUESHEET object. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_CUESHEET \endcode * \retval FLAC__uint32 * The unsigned integer representation of the CDDB/freedb ID */ FLAC_API FLAC__uint32 FLAC__metadata_object_cuesheet_calculate_cddb_id(const FLAC__StreamMetadata *object); /** Sets the MIME type of a PICTURE block. * * If \a copy is \c true, a copy of the string is stored; otherwise, the object * takes ownership of the pointer. The existing string will be freed if this * function is successful, otherwise the original string will remain if \a copy * is \c true and malloc() fails. * * \note It is safe to pass a const pointer to \a mime_type if \a copy is \c true. * * \param object A pointer to an existing PICTURE object. * \param mime_type A pointer to the MIME type string. The string must be * ASCII characters 0x20-0x7e, NUL-terminated. No validation * is done. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_PICTURE \endcode * \code (mime_type != NULL) \endcode * \retval FLAC__bool * \c false if \a copy is \c true and malloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_picture_set_mime_type(FLAC__StreamMetadata *object, char *mime_type, FLAC__bool copy); /** Sets the description of a PICTURE block. * * If \a copy is \c true, a copy of the string is stored; otherwise, the object * takes ownership of the pointer. The existing string will be freed if this * function is successful, otherwise the original string will remain if \a copy * is \c true and malloc() fails. * * \note It is safe to pass a const pointer to \a description if \a copy is \c true. * * \param object A pointer to an existing PICTURE object. * \param description A pointer to the description string. The string must be * valid UTF-8, NUL-terminated. No validation is done. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_PICTURE \endcode * \code (description != NULL) \endcode * \retval FLAC__bool * \c false if \a copy is \c true and malloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_picture_set_description(FLAC__StreamMetadata *object, FLAC__byte *description, FLAC__bool copy); /** Sets the picture data of a PICTURE block. * * If \a copy is \c true, a copy of the data is stored; otherwise, the object * takes ownership of the pointer. Also sets the \a data_length field of the * metadata object to what is passed in as the \a length parameter. The * existing data will be freed if this function is successful, otherwise the * original data and data_length will remain if \a copy is \c true and * malloc() fails. * * \note It is safe to pass a const pointer to \a data if \a copy is \c true. * * \param object A pointer to an existing PICTURE object. * \param data A pointer to the data to set. * \param length The length of \a data in bytes. * \param copy See above. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_PICTURE \endcode * \code (data != NULL && length > 0) || * (data == NULL && length == 0 && copy == false) \endcode * \retval FLAC__bool * \c false if \a copy is \c true and malloc() fails, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_picture_set_data(FLAC__StreamMetadata *object, FLAC__byte *data, FLAC__uint32 length, FLAC__bool copy); /** Check a PICTURE block to see if it conforms to the FLAC specification. * See the format specification for limits on the contents of the * PICTURE block. * * \param object A pointer to existing PICTURE block to be checked. * \param violation Address of a pointer to a string. If there is a * violation, a pointer to a string explanation of the * violation will be returned here. \a violation may be * \c NULL if you don't need the returned string. Do not * free the returned string; it will always point to static * data. * \assert * \code object != NULL \endcode * \code object->type == FLAC__METADATA_TYPE_PICTURE \endcode * \retval FLAC__bool * \c false if PICTURE block is illegal, else \c true. */ FLAC_API FLAC__bool FLAC__metadata_object_picture_is_legal(const FLAC__StreamMetadata *object, const char **violation); /* \} */ #ifdef __cplusplus } #endif #endif sources_5316/external/flac/flac_metadata_iterators.c0000644000176700017670000034741410720617270021476 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include #include #include #include #if defined _WIN32 #include /* for utime() */ #include /* for chmod() */ #include /* for off_t */ #define fseeko fseek #define ftello ftell #else #include /* some flavors of BSD (like OS X) require this to get time_t */ #include /* for utime() */ #include /* for chown(), unlink() */ #endif #include /* for stat(), maybe chmod() */ #include "flac_private_metadata.h" #include "flac_FLAC_assert.h" #include "flac_FLAC_stream_decoder.h" #include "flac_share_alloc.h" #ifdef max #undef max #endif #define max(a,b) ((a)>(b)?(a):(b)) #ifdef min #undef min #endif #define min(a,b) ((a)<(b)?(a):(b)) /**************************************************************************** * * Local function declarations * ***************************************************************************/ static void pack_uint32_(FLAC__uint32 val, FLAC__byte *b, unsigned bytes); static void pack_uint32_little_endian_(FLAC__uint32 val, FLAC__byte *b, unsigned bytes); static void pack_uint64_(FLAC__uint64 val, FLAC__byte *b, unsigned bytes); static FLAC__uint32 unpack_uint32_(FLAC__byte *b, unsigned bytes); static FLAC__uint32 unpack_uint32_little_endian_(FLAC__byte *b, unsigned bytes); static FLAC__uint64 unpack_uint64_(FLAC__byte *b, unsigned bytes); static FLAC__bool read_metadata_block_header_(FLAC__Metadata_SimpleIterator *iterator); static FLAC__bool read_metadata_block_data_(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block); static FLAC__bool read_metadata_block_header_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__bool *is_last, FLAC__MetadataType *type, unsigned *length); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOCallback_Seek seek_cb, FLAC__StreamMetadata *block); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_streaminfo_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_StreamInfo *block); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_padding_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Seek seek_cb, FLAC__StreamMetadata_Padding *block, unsigned block_length); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_application_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_Application *block, unsigned block_length); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_seektable_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_SeekTable *block, unsigned block_length); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_vorbis_comment_entry_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_VorbisComment_Entry *entry); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_vorbis_comment_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_VorbisComment *block); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_cuesheet_track_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_CueSheet_Track *track); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_cuesheet_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_CueSheet *block); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_picture_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_Picture *block); static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_unknown_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_Unknown *block, unsigned block_length); static FLAC__bool write_metadata_block_header_(FILE *file, FLAC__Metadata_SimpleIteratorStatus *status, const FLAC__StreamMetadata *block); static FLAC__bool write_metadata_block_data_(FILE *file, FLAC__Metadata_SimpleIteratorStatus *status, const FLAC__StreamMetadata *block); static FLAC__bool write_metadata_block_header_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata *block); static FLAC__bool write_metadata_block_data_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata *block); static FLAC__bool write_metadata_block_data_streaminfo_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_StreamInfo *block); static FLAC__bool write_metadata_block_data_padding_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_Padding *block, unsigned block_length); static FLAC__bool write_metadata_block_data_application_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_Application *block, unsigned block_length); static FLAC__bool write_metadata_block_data_seektable_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_SeekTable *block); static FLAC__bool write_metadata_block_data_vorbis_comment_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_VorbisComment *block); static FLAC__bool write_metadata_block_data_cuesheet_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_CueSheet *block); static FLAC__bool write_metadata_block_data_picture_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_Picture *block); static FLAC__bool write_metadata_block_data_unknown_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_Unknown *block, unsigned block_length); static FLAC__bool write_metadata_block_stationary_(FLAC__Metadata_SimpleIterator *iterator, const FLAC__StreamMetadata *block); static FLAC__bool write_metadata_block_stationary_with_padding_(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block, unsigned padding_length, FLAC__bool padding_is_last); static FLAC__bool rewrite_whole_file_(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block, FLAC__bool append); static void simple_iterator_push_(FLAC__Metadata_SimpleIterator *iterator); static FLAC__bool simple_iterator_pop_(FLAC__Metadata_SimpleIterator *iterator); static unsigned seek_to_first_metadata_block_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOCallback_Seek seek_cb); static unsigned seek_to_first_metadata_block_(FILE *f); static FLAC__bool simple_iterator_copy_file_prefix_(FLAC__Metadata_SimpleIterator *iterator, FILE **tempfile, char **tempfilename, FLAC__bool append); static FLAC__bool simple_iterator_copy_file_postfix_(FLAC__Metadata_SimpleIterator *iterator, FILE **tempfile, char **tempfilename, int fixup_is_last_code, off_t fixup_is_last_flag_offset, FLAC__bool backup); static FLAC__bool copy_n_bytes_from_file_(FILE *file, FILE *tempfile, off_t bytes, FLAC__Metadata_SimpleIteratorStatus *status); static FLAC__bool copy_n_bytes_from_file_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOHandle temp_handle, FLAC__IOCallback_Write temp_write_cb, off_t bytes, FLAC__Metadata_SimpleIteratorStatus *status); static FLAC__bool copy_remaining_bytes_from_file_(FILE *file, FILE *tempfile, FLAC__Metadata_SimpleIteratorStatus *status); static FLAC__bool copy_remaining_bytes_from_file_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOCallback_Eof eof_cb, FLAC__IOHandle temp_handle, FLAC__IOCallback_Write temp_write_cb, FLAC__Metadata_SimpleIteratorStatus *status); static FLAC__bool open_tempfile_(const char *filename, const char *tempfile_path_prefix, FILE **tempfile, char **tempfilename, FLAC__Metadata_SimpleIteratorStatus *status); static FLAC__bool transport_tempfile_(const char *filename, FILE **tempfile, char **tempfilename, FLAC__Metadata_SimpleIteratorStatus *status); static void cleanup_tempfile_(FILE **tempfile, char **tempfilename); static FLAC__bool get_file_stats_(const char *filename, struct stat *stats); static void set_file_stats_(const char *filename, struct stat *stats); static int fseek_wrapper_(FLAC__IOHandle handle, FLAC__int64 offset, int whence); static FLAC__int64 ftell_wrapper_(FLAC__IOHandle handle); static FLAC__Metadata_ChainStatus get_equivalent_status_(FLAC__Metadata_SimpleIteratorStatus status); #ifdef FLAC__VALGRIND_TESTING static size_t local__fwrite(const void *ptr, size_t size, size_t nmemb, FILE *stream) { size_t ret = fwrite(ptr, size, nmemb, stream); if(!ferror(stream)) fflush(stream); return ret; } #else #define local__fwrite fwrite #endif /**************************************************************************** * * Level 0 implementation * ***************************************************************************/ static FLAC__StreamDecoderWriteStatus write_callback_(const FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer[], void *client_data); static void metadata_callback_(const FLAC__StreamDecoder *decoder, const FLAC__StreamMetadata *metadata, void *client_data); static void error_callback_(const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data); typedef struct { FLAC__bool got_error; FLAC__StreamMetadata *object; } level0_client_data; static FLAC__StreamMetadata *get_one_metadata_block_(const char *filename, FLAC__MetadataType type) { level0_client_data cd; FLAC__StreamDecoder *decoder; FLAC__ASSERT(0 != filename); cd.got_error = false; cd.object = 0; decoder = FLAC__stream_decoder_new(); if(0 == decoder) return 0; FLAC__stream_decoder_set_md5_checking(decoder, false); FLAC__stream_decoder_set_metadata_ignore_all(decoder); FLAC__stream_decoder_set_metadata_respond(decoder, type); if(FLAC__stream_decoder_init_file(decoder, filename, write_callback_, metadata_callback_, error_callback_, &cd) != FLAC__STREAM_DECODER_INIT_STATUS_OK || cd.got_error) { (void)FLAC__stream_decoder_finish(decoder); FLAC__stream_decoder_delete(decoder); return 0; } if(!FLAC__stream_decoder_process_until_end_of_metadata(decoder) || cd.got_error) { (void)FLAC__stream_decoder_finish(decoder); FLAC__stream_decoder_delete(decoder); if(0 != cd.object) FLAC__metadata_object_delete(cd.object); return 0; } (void)FLAC__stream_decoder_finish(decoder); FLAC__stream_decoder_delete(decoder); return cd.object; } FLAC_API FLAC__bool FLAC__metadata_get_streaminfo(const char *filename, FLAC__StreamMetadata *streaminfo) { FLAC__StreamMetadata *object; FLAC__ASSERT(0 != filename); FLAC__ASSERT(0 != streaminfo); object = get_one_metadata_block_(filename, FLAC__METADATA_TYPE_STREAMINFO); if (object) { /* can just copy the contents since STREAMINFO has no internal structure */ *streaminfo = *object; FLAC__metadata_object_delete(object); return true; } else { return false; } } FLAC_API FLAC__bool FLAC__metadata_get_tags(const char *filename, FLAC__StreamMetadata **tags) { FLAC__ASSERT(0 != filename); FLAC__ASSERT(0 != tags); *tags = get_one_metadata_block_(filename, FLAC__METADATA_TYPE_VORBIS_COMMENT); return 0 != *tags; } FLAC_API FLAC__bool FLAC__metadata_get_cuesheet(const char *filename, FLAC__StreamMetadata **cuesheet) { FLAC__ASSERT(0 != filename); FLAC__ASSERT(0 != cuesheet); *cuesheet = get_one_metadata_block_(filename, FLAC__METADATA_TYPE_CUESHEET); return 0 != *cuesheet; } FLAC__StreamDecoderWriteStatus write_callback_(const FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer[], void *client_data) { (void)decoder, (void)frame, (void)buffer, (void)client_data; return FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE; } void metadata_callback_(const FLAC__StreamDecoder *decoder, const FLAC__StreamMetadata *metadata, void *client_data) { level0_client_data *cd = (level0_client_data *)client_data; (void)decoder; /* * we assume we only get here when the one metadata block we were * looking for was passed to us */ if(!cd->got_error && 0 == cd->object) { if(0 == (cd->object = FLAC__metadata_object_clone(metadata))) cd->got_error = true; } } void error_callback_(const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data) { level0_client_data *cd = (level0_client_data *)client_data; (void)decoder; if(status != FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC) cd->got_error = true; } FLAC_API FLAC__bool FLAC__metadata_get_picture(const char *filename, FLAC__StreamMetadata **picture, FLAC__StreamMetadata_Picture_Type type, const char *mime_type, const FLAC__byte *description, unsigned max_width, unsigned max_height, unsigned max_depth, unsigned max_colors) { FLAC__Metadata_SimpleIterator *it; FLAC__uint64 max_area_seen = 0; FLAC__uint64 max_depth_seen = 0; FLAC__ASSERT(0 != filename); FLAC__ASSERT(0 != picture); *picture = 0; it = FLAC__metadata_simple_iterator_new(); if(0 == it) return false; if(!FLAC__metadata_simple_iterator_init(it, filename, /*read_only=*/true, /*preserve_file_stats=*/true)) { FLAC__metadata_simple_iterator_delete(it); return false; } do { if(FLAC__metadata_simple_iterator_get_block_type(it) == FLAC__METADATA_TYPE_PICTURE) { FLAC__StreamMetadata *obj = FLAC__metadata_simple_iterator_get_block(it); FLAC__uint64 area = (FLAC__uint64)obj->data.picture.width * (FLAC__uint64)obj->data.picture.height; /* check constraints */ if( (type == (FLAC__StreamMetadata_Picture_Type)(-1) || type == obj->data.picture.type) && (mime_type == 0 || !strcmp(mime_type, obj->data.picture.mime_type)) && (description == 0 || !strcmp((const char *)description, (const char *)obj->data.picture.description)) && obj->data.picture.width <= max_width && obj->data.picture.height <= max_height && obj->data.picture.depth <= max_depth && obj->data.picture.colors <= max_colors && (area > max_area_seen || (area == max_area_seen && obj->data.picture.depth > max_depth_seen)) ) { if(*picture) FLAC__metadata_object_delete(*picture); *picture = obj; max_area_seen = area; max_depth_seen = obj->data.picture.depth; } else { FLAC__metadata_object_delete(obj); } } } while(FLAC__metadata_simple_iterator_next(it)); FLAC__metadata_simple_iterator_delete(it); return (0 != *picture); } /**************************************************************************** * * Level 1 implementation * ***************************************************************************/ #define SIMPLE_ITERATOR_MAX_PUSH_DEPTH (1+4) /* 1 for initial offset, +4 for our own personal use */ struct FLAC__Metadata_SimpleIterator { FILE *file; char *filename, *tempfile_path_prefix; struct stat stats; FLAC__bool has_stats; FLAC__bool is_writable; FLAC__Metadata_SimpleIteratorStatus status; off_t offset[SIMPLE_ITERATOR_MAX_PUSH_DEPTH]; off_t first_offset; /* this is the offset to the STREAMINFO block */ unsigned depth; /* this is the metadata block header of the current block we are pointing to: */ FLAC__bool is_last; FLAC__MetadataType type; unsigned length; }; FLAC_API const char * const FLAC__Metadata_SimpleIteratorStatusString[] = { "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ILLEGAL_INPUT", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ERROR_OPENING_FILE", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_A_FLAC_FILE", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_WRITABLE", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_BAD_METADATA", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_RENAME_ERROR", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_UNLINK_ERROR", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR", "FLAC__METADATA_SIMPLE_ITERATOR_STATUS_INTERNAL_ERROR" }; FLAC_API FLAC__Metadata_SimpleIterator *FLAC__metadata_simple_iterator_new(void) { FLAC__Metadata_SimpleIterator *iterator = (FLAC__Metadata_SimpleIterator*)calloc(1, sizeof(FLAC__Metadata_SimpleIterator)); if(0 != iterator) { iterator->file = 0; iterator->filename = 0; iterator->tempfile_path_prefix = 0; iterator->has_stats = false; iterator->is_writable = false; iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; iterator->first_offset = iterator->offset[0] = -1; iterator->depth = 0; } return iterator; } static void simple_iterator_free_guts_(FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(0 != iterator); if(0 != iterator->file) { fclose(iterator->file); iterator->file = 0; if(iterator->has_stats) set_file_stats_(iterator->filename, &iterator->stats); } if(0 != iterator->filename) { free(iterator->filename); iterator->filename = 0; } if(0 != iterator->tempfile_path_prefix) { free(iterator->tempfile_path_prefix); iterator->tempfile_path_prefix = 0; } } FLAC_API void FLAC__metadata_simple_iterator_delete(FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(0 != iterator); simple_iterator_free_guts_(iterator); free(iterator); } FLAC_API FLAC__Metadata_SimpleIteratorStatus FLAC__metadata_simple_iterator_status(FLAC__Metadata_SimpleIterator *iterator) { FLAC__Metadata_SimpleIteratorStatus status; FLAC__ASSERT(0 != iterator); status = iterator->status; iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; return status; } static FLAC__bool simple_iterator_prime_input_(FLAC__Metadata_SimpleIterator *iterator, FLAC__bool read_only) { unsigned ret; FLAC__ASSERT(0 != iterator); if(read_only || 0 == (iterator->file = fopen(iterator->filename, "r+b"))) { iterator->is_writable = false; if(read_only || errno == EACCES) { if(0 == (iterator->file = fopen(iterator->filename, "rb"))) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ERROR_OPENING_FILE; return false; } } else { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ERROR_OPENING_FILE; return false; } } else { iterator->is_writable = true; } ret = seek_to_first_metadata_block_(iterator->file); switch(ret) { case 0: iterator->depth = 0; iterator->first_offset = iterator->offset[iterator->depth] = ftello(iterator->file); return read_metadata_block_header_(iterator); case 1: iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; return false; case 2: iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; case 3: iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_A_FLAC_FILE; return false; default: FLAC__ASSERT(0); return false; } } #if 0 @@@ If we decide to finish implementing this, put this comment back in metadata.h /* * The 'tempfile_path_prefix' allows you to specify a directory where * tempfiles should go. Remember that if your metadata edits cause the * FLAC file to grow, the entire file will have to be rewritten. If * 'tempfile_path_prefix' is NULL, the temp file will be written in the * same directory as the original FLAC file. This makes replacing the * original with the tempfile fast but requires extra space in the same * partition for the tempfile. If space is a problem, you can pass a * directory name belonging to a different partition in * 'tempfile_path_prefix'. Note that you should use the forward slash * '/' as the directory separator. A trailing slash is not needed; it * will be added automatically. */ FLAC__bool FLAC__metadata_simple_iterator_init(FLAC__Metadata_SimpleIterator *iterator, const char *filename, FLAC__bool preserve_file_stats, const char *tempfile_path_prefix); #endif FLAC_API FLAC__bool FLAC__metadata_simple_iterator_init(FLAC__Metadata_SimpleIterator *iterator, const char *filename, FLAC__bool read_only, FLAC__bool preserve_file_stats) { const char *tempfile_path_prefix = 0; /*@@@ search for comments near 'rename(...)' for what it will take to finish implementing this */ FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != filename); simple_iterator_free_guts_(iterator); if(!read_only && preserve_file_stats) iterator->has_stats = get_file_stats_(filename, &iterator->stats); if(0 == (iterator->filename = strdup(filename))) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; return false; } if(0 != tempfile_path_prefix && 0 == (iterator->tempfile_path_prefix = strdup(tempfile_path_prefix))) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; return false; } return simple_iterator_prime_input_(iterator, read_only); } FLAC_API FLAC__bool FLAC__metadata_simple_iterator_is_writable(const FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); return iterator->is_writable; } FLAC_API FLAC__bool FLAC__metadata_simple_iterator_next(FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); if(iterator->is_last) return false; if(0 != fseeko(iterator->file, iterator->length, SEEK_CUR)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } iterator->offset[iterator->depth] = ftello(iterator->file); return read_metadata_block_header_(iterator); } FLAC_API FLAC__bool FLAC__metadata_simple_iterator_prev(FLAC__Metadata_SimpleIterator *iterator) { off_t this_offset; FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); if(iterator->offset[iterator->depth] == iterator->first_offset) return false; if(0 != fseeko(iterator->file, iterator->first_offset, SEEK_SET)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } this_offset = iterator->first_offset; if(!read_metadata_block_header_(iterator)) return false; /* we ignore any error from ftello() and catch it in fseeko() */ while(ftello(iterator->file) + (off_t)iterator->length < iterator->offset[iterator->depth]) { if(0 != fseeko(iterator->file, iterator->length, SEEK_CUR)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } this_offset = ftello(iterator->file); if(!read_metadata_block_header_(iterator)) return false; } iterator->offset[iterator->depth] = this_offset; return true; } /*@@@@add to tests*/ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_is_last(const FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); return iterator->is_last; } /*@@@@add to tests*/ FLAC_API off_t FLAC__metadata_simple_iterator_get_block_offset(const FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); return iterator->offset[iterator->depth]; } FLAC_API FLAC__MetadataType FLAC__metadata_simple_iterator_get_block_type(const FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); return iterator->type; } /*@@@@add to tests*/ FLAC_API unsigned FLAC__metadata_simple_iterator_get_block_length(const FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); return iterator->length; } /*@@@@add to tests*/ FLAC_API FLAC__bool FLAC__metadata_simple_iterator_get_application_id(FLAC__Metadata_SimpleIterator *iterator, FLAC__byte *id) { const unsigned id_bytes = FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8; FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); FLAC__ASSERT(0 != id); if(iterator->type != FLAC__METADATA_TYPE_APPLICATION) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ILLEGAL_INPUT; return false; } if(fread(id, 1, id_bytes, iterator->file) != id_bytes) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; return false; } /* back up */ if(0 != fseeko(iterator->file, -((int)id_bytes), SEEK_CUR)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } return true; } FLAC_API FLAC__StreamMetadata *FLAC__metadata_simple_iterator_get_block(FLAC__Metadata_SimpleIterator *iterator) { FLAC__StreamMetadata *block = FLAC__metadata_object_new(iterator->type); FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); if(0 != block) { block->is_last = iterator->is_last; block->length = iterator->length; if(!read_metadata_block_data_(iterator, block)) { FLAC__metadata_object_delete(block); return 0; } /* back up to the beginning of the block data to stay consistent */ if(0 != fseeko(iterator->file, iterator->offset[iterator->depth] + FLAC__STREAM_METADATA_HEADER_LENGTH, SEEK_SET)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; FLAC__metadata_object_delete(block); return 0; } } else iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; return block; } FLAC_API FLAC__bool FLAC__metadata_simple_iterator_set_block(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block, FLAC__bool use_padding) { FLAC__ASSERT_DECLARATION(off_t debug_target_offset = iterator->offset[iterator->depth];) FLAC__bool ret; FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); FLAC__ASSERT(0 != block); if(!iterator->is_writable) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_WRITABLE; return false; } if(iterator->type == FLAC__METADATA_TYPE_STREAMINFO || block->type == FLAC__METADATA_TYPE_STREAMINFO) { if(iterator->type != block->type) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ILLEGAL_INPUT; return false; } } block->is_last = iterator->is_last; if(iterator->length == block->length) return write_metadata_block_stationary_(iterator, block); else if(iterator->length > block->length) { if(use_padding && iterator->length >= FLAC__STREAM_METADATA_HEADER_LENGTH + block->length) { ret = write_metadata_block_stationary_with_padding_(iterator, block, iterator->length - FLAC__STREAM_METADATA_HEADER_LENGTH - block->length, block->is_last); FLAC__ASSERT(!ret || iterator->offset[iterator->depth] == debug_target_offset); FLAC__ASSERT(!ret || ftello(iterator->file) == debug_target_offset + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH); return ret; } else { ret = rewrite_whole_file_(iterator, block, /*append=*/false); FLAC__ASSERT(!ret || iterator->offset[iterator->depth] == debug_target_offset); FLAC__ASSERT(!ret || ftello(iterator->file) == debug_target_offset + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH); return ret; } } else /* iterator->length < block->length */ { unsigned padding_leftover = 0; FLAC__bool padding_is_last = false; if(use_padding) { /* first see if we can even use padding */ if(iterator->is_last) { use_padding = false; } else { const unsigned extra_padding_bytes_required = block->length - iterator->length; simple_iterator_push_(iterator); if(!FLAC__metadata_simple_iterator_next(iterator)) { (void)simple_iterator_pop_(iterator); return false; } if(iterator->type != FLAC__METADATA_TYPE_PADDING) { use_padding = false; } else { if(FLAC__STREAM_METADATA_HEADER_LENGTH + iterator->length == extra_padding_bytes_required) { padding_leftover = 0; block->is_last = iterator->is_last; } else if(iterator->length < extra_padding_bytes_required) use_padding = false; else { padding_leftover = FLAC__STREAM_METADATA_HEADER_LENGTH + iterator->length - extra_padding_bytes_required; padding_is_last = iterator->is_last; block->is_last = false; } } if(!simple_iterator_pop_(iterator)) return false; } } if(use_padding) { if(padding_leftover == 0) { ret = write_metadata_block_stationary_(iterator, block); FLAC__ASSERT(!ret || iterator->offset[iterator->depth] == debug_target_offset); FLAC__ASSERT(!ret || ftello(iterator->file) == debug_target_offset + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH); return ret; } else { FLAC__ASSERT(padding_leftover >= FLAC__STREAM_METADATA_HEADER_LENGTH); ret = write_metadata_block_stationary_with_padding_(iterator, block, padding_leftover - FLAC__STREAM_METADATA_HEADER_LENGTH, padding_is_last); FLAC__ASSERT(!ret || iterator->offset[iterator->depth] == debug_target_offset); FLAC__ASSERT(!ret || ftello(iterator->file) == debug_target_offset + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH); return ret; } } else { ret = rewrite_whole_file_(iterator, block, /*append=*/false); FLAC__ASSERT(!ret || iterator->offset[iterator->depth] == debug_target_offset); FLAC__ASSERT(!ret || ftello(iterator->file) == debug_target_offset + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH); return ret; } } } FLAC_API FLAC__bool FLAC__metadata_simple_iterator_insert_block_after(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block, FLAC__bool use_padding) { unsigned padding_leftover = 0; FLAC__bool padding_is_last = false; FLAC__ASSERT_DECLARATION(off_t debug_target_offset = iterator->offset[iterator->depth] + FLAC__STREAM_METADATA_HEADER_LENGTH + iterator->length;) FLAC__bool ret; FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); FLAC__ASSERT(0 != block); if(!iterator->is_writable) return false; if(block->type == FLAC__METADATA_TYPE_STREAMINFO) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ILLEGAL_INPUT; return false; } block->is_last = iterator->is_last; if(use_padding) { /* first see if we can even use padding */ if(iterator->is_last) { use_padding = false; } else { simple_iterator_push_(iterator); if(!FLAC__metadata_simple_iterator_next(iterator)) { (void)simple_iterator_pop_(iterator); return false; } if(iterator->type != FLAC__METADATA_TYPE_PADDING) { use_padding = false; } else { if(iterator->length == block->length) { padding_leftover = 0; block->is_last = iterator->is_last; } else if(iterator->length < FLAC__STREAM_METADATA_HEADER_LENGTH + block->length) use_padding = false; else { padding_leftover = iterator->length - block->length; padding_is_last = iterator->is_last; block->is_last = false; } } if(!simple_iterator_pop_(iterator)) return false; } } if(use_padding) { /* move to the next block, which is suitable padding */ if(!FLAC__metadata_simple_iterator_next(iterator)) return false; if(padding_leftover == 0) { ret = write_metadata_block_stationary_(iterator, block); FLAC__ASSERT(iterator->offset[iterator->depth] == debug_target_offset); FLAC__ASSERT(ftello(iterator->file) == debug_target_offset + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH); return ret; } else { FLAC__ASSERT(padding_leftover >= FLAC__STREAM_METADATA_HEADER_LENGTH); ret = write_metadata_block_stationary_with_padding_(iterator, block, padding_leftover - FLAC__STREAM_METADATA_HEADER_LENGTH, padding_is_last); FLAC__ASSERT(iterator->offset[iterator->depth] == debug_target_offset); FLAC__ASSERT(ftello(iterator->file) == debug_target_offset + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH); return ret; } } else { ret = rewrite_whole_file_(iterator, block, /*append=*/true); FLAC__ASSERT(iterator->offset[iterator->depth] == debug_target_offset); FLAC__ASSERT(ftello(iterator->file) == debug_target_offset + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH); return ret; } } FLAC_API FLAC__bool FLAC__metadata_simple_iterator_delete_block(FLAC__Metadata_SimpleIterator *iterator, FLAC__bool use_padding) { FLAC__ASSERT_DECLARATION(off_t debug_target_offset = iterator->offset[iterator->depth];) FLAC__bool ret; if(iterator->type == FLAC__METADATA_TYPE_STREAMINFO) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ILLEGAL_INPUT; return false; } if(use_padding) { FLAC__StreamMetadata *padding = FLAC__metadata_object_new(FLAC__METADATA_TYPE_PADDING); if(0 == padding) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; return false; } padding->length = iterator->length; if(!FLAC__metadata_simple_iterator_set_block(iterator, padding, false)) { FLAC__metadata_object_delete(padding); return false; } FLAC__metadata_object_delete(padding); if(!FLAC__metadata_simple_iterator_prev(iterator)) return false; FLAC__ASSERT(iterator->offset[iterator->depth] + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH + (off_t)iterator->length == debug_target_offset); FLAC__ASSERT(ftello(iterator->file) + (off_t)iterator->length == debug_target_offset); return true; } else { ret = rewrite_whole_file_(iterator, 0, /*append=*/false); FLAC__ASSERT(iterator->offset[iterator->depth] + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH + (off_t)iterator->length == debug_target_offset); FLAC__ASSERT(ftello(iterator->file) + (off_t)iterator->length == debug_target_offset); return ret; } } /**************************************************************************** * * Level 2 implementation * ***************************************************************************/ typedef struct FLAC__Metadata_Node { FLAC__StreamMetadata *data; struct FLAC__Metadata_Node *prev, *next; } FLAC__Metadata_Node; struct FLAC__Metadata_Chain { char *filename; /* will be NULL if using callbacks */ FLAC__bool is_ogg; FLAC__Metadata_Node *head; FLAC__Metadata_Node *tail; unsigned nodes; FLAC__Metadata_ChainStatus status; off_t first_offset, last_offset; /* * This is the length of the chain initially read from the FLAC file. * it is used to compare against the current length to decide whether * or not the whole file has to be rewritten. */ off_t initial_length; /* @@@ hacky, these are currently only needed by ogg reader */ FLAC__IOHandle handle; FLAC__IOCallback_Read read_cb; }; struct FLAC__Metadata_Iterator { FLAC__Metadata_Chain *chain; FLAC__Metadata_Node *current; }; FLAC_API const char * const FLAC__Metadata_ChainStatusString[] = { "FLAC__METADATA_CHAIN_STATUS_OK", "FLAC__METADATA_CHAIN_STATUS_ILLEGAL_INPUT", "FLAC__METADATA_CHAIN_STATUS_ERROR_OPENING_FILE", "FLAC__METADATA_CHAIN_STATUS_NOT_A_FLAC_FILE", "FLAC__METADATA_CHAIN_STATUS_NOT_WRITABLE", "FLAC__METADATA_CHAIN_STATUS_BAD_METADATA", "FLAC__METADATA_CHAIN_STATUS_READ_ERROR", "FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR", "FLAC__METADATA_CHAIN_STATUS_WRITE_ERROR", "FLAC__METADATA_CHAIN_STATUS_RENAME_ERROR", "FLAC__METADATA_CHAIN_STATUS_UNLINK_ERROR", "FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR", "FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR", "FLAC__METADATA_CHAIN_STATUS_INVALID_CALLBACKS", "FLAC__METADATA_CHAIN_STATUS_READ_WRITE_MISMATCH", "FLAC__METADATA_CHAIN_STATUS_WRONG_WRITE_CALL" }; static FLAC__Metadata_Node *node_new_(void) { return (FLAC__Metadata_Node*)calloc(1, sizeof(FLAC__Metadata_Node)); } static void node_delete_(FLAC__Metadata_Node *node) { FLAC__ASSERT(0 != node); if(0 != node->data) FLAC__metadata_object_delete(node->data); free(node); } static void chain_init_(FLAC__Metadata_Chain *chain) { FLAC__ASSERT(0 != chain); chain->filename = 0; chain->is_ogg = false; chain->head = chain->tail = 0; chain->nodes = 0; chain->status = FLAC__METADATA_CHAIN_STATUS_OK; chain->initial_length = 0; chain->read_cb = 0; } static void chain_clear_(FLAC__Metadata_Chain *chain) { FLAC__Metadata_Node *node, *next; FLAC__ASSERT(0 != chain); for(node = chain->head; node; ) { next = node->next; node_delete_(node); node = next; } if(0 != chain->filename) free(chain->filename); chain_init_(chain); } static void chain_append_node_(FLAC__Metadata_Chain *chain, FLAC__Metadata_Node *node) { FLAC__ASSERT(0 != chain); FLAC__ASSERT(0 != node); FLAC__ASSERT(0 != node->data); node->next = node->prev = 0; node->data->is_last = true; if(0 != chain->tail) chain->tail->data->is_last = false; if(0 == chain->head) chain->head = node; else { FLAC__ASSERT(0 != chain->tail); chain->tail->next = node; node->prev = chain->tail; } chain->tail = node; chain->nodes++; } static void chain_remove_node_(FLAC__Metadata_Chain *chain, FLAC__Metadata_Node *node) { FLAC__ASSERT(0 != chain); FLAC__ASSERT(0 != node); if(node == chain->head) chain->head = node->next; else node->prev->next = node->next; if(node == chain->tail) chain->tail = node->prev; else node->next->prev = node->prev; if(0 != chain->tail) chain->tail->data->is_last = true; chain->nodes--; } static void chain_delete_node_(FLAC__Metadata_Chain *chain, FLAC__Metadata_Node *node) { chain_remove_node_(chain, node); node_delete_(node); } static off_t chain_calculate_length_(FLAC__Metadata_Chain *chain) { const FLAC__Metadata_Node *node; off_t length = 0; for(node = chain->head; node; node = node->next) length += (FLAC__STREAM_METADATA_HEADER_LENGTH + node->data->length); return length; } static void iterator_insert_node_(FLAC__Metadata_Iterator *iterator, FLAC__Metadata_Node *node) { FLAC__ASSERT(0 != node); FLAC__ASSERT(0 != node->data); FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->current); FLAC__ASSERT(0 != iterator->chain); FLAC__ASSERT(0 != iterator->chain->head); FLAC__ASSERT(0 != iterator->chain->tail); node->data->is_last = false; node->prev = iterator->current->prev; node->next = iterator->current; if(0 == node->prev) iterator->chain->head = node; else node->prev->next = node; iterator->current->prev = node; iterator->chain->nodes++; } static void iterator_insert_node_after_(FLAC__Metadata_Iterator *iterator, FLAC__Metadata_Node *node) { FLAC__ASSERT(0 != node); FLAC__ASSERT(0 != node->data); FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->current); FLAC__ASSERT(0 != iterator->chain); FLAC__ASSERT(0 != iterator->chain->head); FLAC__ASSERT(0 != iterator->chain->tail); iterator->current->data->is_last = false; node->prev = iterator->current; node->next = iterator->current->next; if(0 == node->next) iterator->chain->tail = node; else node->next->prev = node; node->prev->next = node; iterator->chain->tail->data->is_last = true; iterator->chain->nodes++; } /* return true iff node and node->next are both padding */ static FLAC__bool chain_merge_adjacent_padding_(FLAC__Metadata_Chain *chain, FLAC__Metadata_Node *node) { if(node->data->type == FLAC__METADATA_TYPE_PADDING && 0 != node->next && node->next->data->type == FLAC__METADATA_TYPE_PADDING) { const unsigned growth = FLAC__STREAM_METADATA_HEADER_LENGTH + node->next->data->length; node->data->length += growth; chain_delete_node_(chain, node->next); return true; } else return false; } /* Returns the new length of the chain, or 0 if there was an error. */ /* WATCHOUT: This can get called multiple times before a write, so * it should still work when this happens. */ /* WATCHOUT: Make sure to also update the logic in * FLAC__metadata_chain_check_if_tempfile_needed() if the logic here changes. */ static off_t chain_prepare_for_write_(FLAC__Metadata_Chain *chain, FLAC__bool use_padding) { off_t current_length = chain_calculate_length_(chain); if(use_padding) { /* if the metadata shrank and the last block is padding, we just extend the last padding block */ if(current_length < chain->initial_length && chain->tail->data->type == FLAC__METADATA_TYPE_PADDING) { const off_t delta = chain->initial_length - current_length; chain->tail->data->length += delta; current_length += delta; FLAC__ASSERT(current_length == chain->initial_length); } /* if the metadata shrank more than 4 bytes then there's room to add another padding block */ else if(current_length + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH <= chain->initial_length) { FLAC__StreamMetadata *padding; FLAC__Metadata_Node *node; if(0 == (padding = FLAC__metadata_object_new(FLAC__METADATA_TYPE_PADDING))) { chain->status = FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR; return 0; } padding->length = chain->initial_length - (FLAC__STREAM_METADATA_HEADER_LENGTH + current_length); if(0 == (node = node_new_())) { FLAC__metadata_object_delete(padding); chain->status = FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR; return 0; } node->data = padding; chain_append_node_(chain, node); current_length = chain_calculate_length_(chain); FLAC__ASSERT(current_length == chain->initial_length); } /* if the metadata grew but the last block is padding, try cutting the padding to restore the original length so we don't have to rewrite the whole file */ else if(current_length > chain->initial_length) { const off_t delta = current_length - chain->initial_length; if(chain->tail->data->type == FLAC__METADATA_TYPE_PADDING) { /* if the delta is exactly the size of the last padding block, remove the padding block */ if((off_t)chain->tail->data->length + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH == delta) { chain_delete_node_(chain, chain->tail); current_length = chain_calculate_length_(chain); FLAC__ASSERT(current_length == chain->initial_length); } /* if there is at least 'delta' bytes of padding, trim the padding down */ else if((off_t)chain->tail->data->length >= delta) { chain->tail->data->length -= delta; current_length -= delta; FLAC__ASSERT(current_length == chain->initial_length); } } } } return current_length; } static FLAC__bool chain_read_cb_(FLAC__Metadata_Chain *chain, FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOCallback_Seek seek_cb, FLAC__IOCallback_Tell tell_cb) { FLAC__Metadata_Node *node; FLAC__ASSERT(0 != chain); /* we assume we're already at the beginning of the file */ switch(seek_to_first_metadata_block_cb_(handle, read_cb, seek_cb)) { case 0: break; case 1: chain->status = FLAC__METADATA_CHAIN_STATUS_READ_ERROR; return false; case 2: chain->status = FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR; return false; case 3: chain->status = FLAC__METADATA_CHAIN_STATUS_NOT_A_FLAC_FILE; return false; default: FLAC__ASSERT(0); return false; } { FLAC__int64 pos = tell_cb(handle); if(pos < 0) { chain->status = FLAC__METADATA_CHAIN_STATUS_READ_ERROR; return false; } chain->first_offset = (off_t)pos; } { FLAC__bool is_last; FLAC__MetadataType type; unsigned length; do { node = node_new_(); if(0 == node) { chain->status = FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR; return false; } if(!read_metadata_block_header_cb_(handle, read_cb, &is_last, &type, &length)) { chain->status = FLAC__METADATA_CHAIN_STATUS_READ_ERROR; return false; } node->data = FLAC__metadata_object_new(type); if(0 == node->data) { node_delete_(node); chain->status = FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR; return false; } node->data->is_last = is_last; node->data->length = length; chain->status = get_equivalent_status_(read_metadata_block_data_cb_(handle, read_cb, seek_cb, node->data)); if(chain->status != FLAC__METADATA_CHAIN_STATUS_OK) { node_delete_(node); return false; } chain_append_node_(chain, node); } while(!is_last); } { FLAC__int64 pos = tell_cb(handle); if(pos < 0) { chain->status = FLAC__METADATA_CHAIN_STATUS_READ_ERROR; return false; } chain->last_offset = (off_t)pos; } chain->initial_length = chain_calculate_length_(chain); return true; } static FLAC__StreamDecoderReadStatus chain_read_ogg_read_cb_(const FLAC__StreamDecoder *decoder, FLAC__byte buffer[], size_t *bytes, void *client_data) { FLAC__Metadata_Chain *chain = (FLAC__Metadata_Chain*)client_data; (void)decoder; if(*bytes > 0 && chain->status == FLAC__METADATA_CHAIN_STATUS_OK) { *bytes = chain->read_cb(buffer, sizeof(FLAC__byte), *bytes, chain->handle); if(*bytes == 0) return FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM; else return FLAC__STREAM_DECODER_READ_STATUS_CONTINUE; } else return FLAC__STREAM_DECODER_READ_STATUS_ABORT; } static FLAC__StreamDecoderWriteStatus chain_read_ogg_write_cb_(const FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer[], void *client_data) { (void)decoder, (void)frame, (void)buffer, (void)client_data; return FLAC__STREAM_DECODER_WRITE_STATUS_ABORT; } static void chain_read_ogg_metadata_cb_(const FLAC__StreamDecoder *decoder, const FLAC__StreamMetadata *metadata, void *client_data) { FLAC__Metadata_Chain *chain = (FLAC__Metadata_Chain*)client_data; FLAC__Metadata_Node *node; (void)decoder; node = node_new_(); if(0 == node) { chain->status = FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR; return; } node->data = FLAC__metadata_object_clone(metadata); if(0 == node->data) { node_delete_(node); chain->status = FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR; return; } chain_append_node_(chain, node); } static void chain_read_ogg_error_cb_(const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data) { FLAC__Metadata_Chain *chain = (FLAC__Metadata_Chain*)client_data; (void)decoder, (void)status; chain->status = FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR; /*@@@ maybe needs better error code */ } static FLAC__bool chain_read_ogg_cb_(FLAC__Metadata_Chain *chain, FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb) { FLAC__StreamDecoder *decoder; FLAC__ASSERT(0 != chain); /* we assume we're already at the beginning of the file */ chain->handle = handle; chain->read_cb = read_cb; if(0 == (decoder = FLAC__stream_decoder_new())) { chain->status = FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR; return false; } FLAC__stream_decoder_set_metadata_respond_all(decoder); if(FLAC__stream_decoder_init_ogg_stream(decoder, chain_read_ogg_read_cb_, /*seek_callback=*/0, /*tell_callback=*/0, /*length_callback=*/0, /*eof_callback=*/0, chain_read_ogg_write_cb_, chain_read_ogg_metadata_cb_, chain_read_ogg_error_cb_, chain) != FLAC__STREAM_DECODER_INIT_STATUS_OK) { FLAC__stream_decoder_delete(decoder); chain->status = FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR; /*@@@ maybe needs better error code */ return false; } chain->first_offset = 0; /*@@@ wrong; will need to be set correctly to implement metadata writing for Ogg FLAC */ if(!FLAC__stream_decoder_process_until_end_of_metadata(decoder)) chain->status = FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR; /*@@@ maybe needs better error code */ if(chain->status != FLAC__METADATA_CHAIN_STATUS_OK) { FLAC__stream_decoder_delete(decoder); return false; } FLAC__stream_decoder_delete(decoder); chain->last_offset = 0; /*@@@ wrong; will need to be set correctly to implement metadata writing for Ogg FLAC */ chain->initial_length = chain_calculate_length_(chain); return true; } static FLAC__bool chain_rewrite_metadata_in_place_cb_(FLAC__Metadata_Chain *chain, FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, FLAC__IOCallback_Seek seek_cb) { FLAC__Metadata_Node *node; FLAC__ASSERT(0 != chain); FLAC__ASSERT(0 != chain->head); if(0 != seek_cb(handle, chain->first_offset, SEEK_SET)) { chain->status = FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR; return false; } for(node = chain->head; node; node = node->next) { if(!write_metadata_block_header_cb_(handle, write_cb, node->data)) { chain->status = FLAC__METADATA_CHAIN_STATUS_WRITE_ERROR; return false; } if(!write_metadata_block_data_cb_(handle, write_cb, node->data)) { chain->status = FLAC__METADATA_CHAIN_STATUS_WRITE_ERROR; return false; } } /*FLAC__ASSERT(fflush(), ftello() == chain->last_offset);*/ chain->status = FLAC__METADATA_CHAIN_STATUS_OK; return true; } static FLAC__bool chain_rewrite_metadata_in_place_(FLAC__Metadata_Chain *chain) { FILE *file; FLAC__bool ret; FLAC__ASSERT(0 != chain->filename); if(0 == (file = fopen(chain->filename, "r+b"))) { chain->status = FLAC__METADATA_CHAIN_STATUS_ERROR_OPENING_FILE; return false; } /* chain_rewrite_metadata_in_place_cb_() sets chain->status for us */ ret = chain_rewrite_metadata_in_place_cb_(chain, (FLAC__IOHandle)file, (FLAC__IOCallback_Write)fwrite, fseek_wrapper_); fclose(file); return ret; } static FLAC__bool chain_rewrite_file_(FLAC__Metadata_Chain *chain, const char *tempfile_path_prefix) { FILE *f, *tempfile; char *tempfilename; FLAC__Metadata_SimpleIteratorStatus status; const FLAC__Metadata_Node *node; FLAC__ASSERT(0 != chain); FLAC__ASSERT(0 != chain->filename); FLAC__ASSERT(0 != chain->head); /* copy the file prefix (data up to first metadata block */ if(0 == (f = fopen(chain->filename, "rb"))) { chain->status = FLAC__METADATA_CHAIN_STATUS_ERROR_OPENING_FILE; return false; } if(!open_tempfile_(chain->filename, tempfile_path_prefix, &tempfile, &tempfilename, &status)) { chain->status = get_equivalent_status_(status); cleanup_tempfile_(&tempfile, &tempfilename); return false; } if(!copy_n_bytes_from_file_(f, tempfile, chain->first_offset, &status)) { chain->status = get_equivalent_status_(status); cleanup_tempfile_(&tempfile, &tempfilename); return false; } /* write the metadata */ for(node = chain->head; node; node = node->next) { if(!write_metadata_block_header_(tempfile, &status, node->data)) { chain->status = get_equivalent_status_(status); return false; } if(!write_metadata_block_data_(tempfile, &status, node->data)) { chain->status = get_equivalent_status_(status); return false; } } /*FLAC__ASSERT(fflush(), ftello() == chain->last_offset);*/ /* copy the file postfix (everything after the metadata) */ if(0 != fseeko(f, chain->last_offset, SEEK_SET)) { cleanup_tempfile_(&tempfile, &tempfilename); chain->status = FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR; return false; } if(!copy_remaining_bytes_from_file_(f, tempfile, &status)) { cleanup_tempfile_(&tempfile, &tempfilename); chain->status = get_equivalent_status_(status); return false; } /* move the tempfile on top of the original */ (void)fclose(f); if(!transport_tempfile_(chain->filename, &tempfile, &tempfilename, &status)) return false; return true; } /* assumes 'handle' is already at beginning of file */ static FLAC__bool chain_rewrite_file_cb_(FLAC__Metadata_Chain *chain, FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOCallback_Seek seek_cb, FLAC__IOCallback_Eof eof_cb, FLAC__IOHandle temp_handle, FLAC__IOCallback_Write temp_write_cb) { FLAC__Metadata_SimpleIteratorStatus status; const FLAC__Metadata_Node *node; FLAC__ASSERT(0 != chain); FLAC__ASSERT(0 == chain->filename); FLAC__ASSERT(0 != chain->head); /* copy the file prefix (data up to first metadata block */ if(!copy_n_bytes_from_file_cb_(handle, read_cb, temp_handle, temp_write_cb, chain->first_offset, &status)) { chain->status = get_equivalent_status_(status); return false; } /* write the metadata */ for(node = chain->head; node; node = node->next) { if(!write_metadata_block_header_cb_(temp_handle, temp_write_cb, node->data)) { chain->status = FLAC__METADATA_CHAIN_STATUS_WRITE_ERROR; return false; } if(!write_metadata_block_data_cb_(temp_handle, temp_write_cb, node->data)) { chain->status = FLAC__METADATA_CHAIN_STATUS_WRITE_ERROR; return false; } } /*FLAC__ASSERT(fflush(), ftello() == chain->last_offset);*/ /* copy the file postfix (everything after the metadata) */ if(0 != seek_cb(handle, chain->last_offset, SEEK_SET)) { chain->status = FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR; return false; } if(!copy_remaining_bytes_from_file_cb_(handle, read_cb, eof_cb, temp_handle, temp_write_cb, &status)) { chain->status = get_equivalent_status_(status); return false; } return true; } FLAC_API FLAC__Metadata_Chain *FLAC__metadata_chain_new(void) { FLAC__Metadata_Chain *chain = (FLAC__Metadata_Chain*)calloc(1, sizeof(FLAC__Metadata_Chain)); if(0 != chain) chain_init_(chain); return chain; } FLAC_API void FLAC__metadata_chain_delete(FLAC__Metadata_Chain *chain) { FLAC__ASSERT(0 != chain); chain_clear_(chain); free(chain); } FLAC_API FLAC__Metadata_ChainStatus FLAC__metadata_chain_status(FLAC__Metadata_Chain *chain) { FLAC__Metadata_ChainStatus status; FLAC__ASSERT(0 != chain); status = chain->status; chain->status = FLAC__METADATA_CHAIN_STATUS_OK; return status; } static FLAC__bool chain_read_(FLAC__Metadata_Chain *chain, const char *filename, FLAC__bool is_ogg) { FILE *file; FLAC__bool ret; FLAC__ASSERT(0 != chain); FLAC__ASSERT(0 != filename); chain_clear_(chain); if(0 == (chain->filename = strdup(filename))) { chain->status = FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR; return false; } chain->is_ogg = is_ogg; if(0 == (file = fopen(filename, "rb"))) { chain->status = FLAC__METADATA_CHAIN_STATUS_ERROR_OPENING_FILE; return false; } /* the function also sets chain->status for us */ ret = is_ogg? chain_read_ogg_cb_(chain, file, (FLAC__IOCallback_Read)fread) : chain_read_cb_(chain, file, (FLAC__IOCallback_Read)fread, fseek_wrapper_, ftell_wrapper_) ; fclose(file); return ret; } FLAC_API FLAC__bool FLAC__metadata_chain_read(FLAC__Metadata_Chain *chain, const char *filename) { return chain_read_(chain, filename, /*is_ogg=*/false); } /*@@@@add to tests*/ FLAC_API FLAC__bool FLAC__metadata_chain_read_ogg(FLAC__Metadata_Chain *chain, const char *filename) { return chain_read_(chain, filename, /*is_ogg=*/true); } static FLAC__bool chain_read_with_callbacks_(FLAC__Metadata_Chain *chain, FLAC__IOHandle handle, FLAC__IOCallbacks callbacks, FLAC__bool is_ogg) { FLAC__bool ret; FLAC__ASSERT(0 != chain); chain_clear_(chain); if (0 == callbacks.read || 0 == callbacks.seek || 0 == callbacks.tell) { chain->status = FLAC__METADATA_CHAIN_STATUS_INVALID_CALLBACKS; return false; } chain->is_ogg = is_ogg; /* rewind */ if(0 != callbacks.seek(handle, 0, SEEK_SET)) { chain->status = FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR; return false; } /* the function also sets chain->status for us */ ret = is_ogg? chain_read_ogg_cb_(chain, handle, callbacks.read) : chain_read_cb_(chain, handle, callbacks.read, callbacks.seek, callbacks.tell) ; return ret; } FLAC_API FLAC__bool FLAC__metadata_chain_read_with_callbacks(FLAC__Metadata_Chain *chain, FLAC__IOHandle handle, FLAC__IOCallbacks callbacks) { return chain_read_with_callbacks_(chain, handle, callbacks, /*is_ogg=*/false); } /*@@@@add to tests*/ FLAC_API FLAC__bool FLAC__metadata_chain_read_ogg_with_callbacks(FLAC__Metadata_Chain *chain, FLAC__IOHandle handle, FLAC__IOCallbacks callbacks) { return chain_read_with_callbacks_(chain, handle, callbacks, /*is_ogg=*/true); } FLAC_API FLAC__bool FLAC__metadata_chain_check_if_tempfile_needed(FLAC__Metadata_Chain *chain, FLAC__bool use_padding) { /* This does all the same checks that are in chain_prepare_for_write_() * but doesn't actually alter the chain. Make sure to update the logic * here if chain_prepare_for_write_() changes. */ const off_t current_length = chain_calculate_length_(chain); FLAC__ASSERT(0 != chain); if(use_padding) { /* if the metadata shrank and the last block is padding, we just extend the last padding block */ if(current_length < chain->initial_length && chain->tail->data->type == FLAC__METADATA_TYPE_PADDING) return false; /* if the metadata shrank more than 4 bytes then there's room to add another padding block */ else if(current_length + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH <= chain->initial_length) return false; /* if the metadata grew but the last block is padding, try cutting the padding to restore the original length so we don't have to rewrite the whole file */ else if(current_length > chain->initial_length) { const off_t delta = current_length - chain->initial_length; if(chain->tail->data->type == FLAC__METADATA_TYPE_PADDING) { /* if the delta is exactly the size of the last padding block, remove the padding block */ if((off_t)chain->tail->data->length + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH == delta) return false; /* if there is at least 'delta' bytes of padding, trim the padding down */ else if((off_t)chain->tail->data->length >= delta) return false; } } } return (current_length != chain->initial_length); } FLAC_API FLAC__bool FLAC__metadata_chain_write(FLAC__Metadata_Chain *chain, FLAC__bool use_padding, FLAC__bool preserve_file_stats) { struct stat stats; const char *tempfile_path_prefix = 0; off_t current_length; FLAC__ASSERT(0 != chain); if (chain->is_ogg) { /* cannot write back to Ogg FLAC yet */ chain->status = FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR; return false; } if (0 == chain->filename) { chain->status = FLAC__METADATA_CHAIN_STATUS_READ_WRITE_MISMATCH; return false; } current_length = chain_prepare_for_write_(chain, use_padding); /* a return value of 0 means there was an error; chain->status is already set */ if (0 == current_length) return false; if(preserve_file_stats) get_file_stats_(chain->filename, &stats); if(current_length == chain->initial_length) { if(!chain_rewrite_metadata_in_place_(chain)) return false; } else { if(!chain_rewrite_file_(chain, tempfile_path_prefix)) return false; /* recompute lengths and offsets */ { const FLAC__Metadata_Node *node; chain->initial_length = current_length; chain->last_offset = chain->first_offset; for(node = chain->head; node; node = node->next) chain->last_offset += (FLAC__STREAM_METADATA_HEADER_LENGTH + node->data->length); } } if(preserve_file_stats) set_file_stats_(chain->filename, &stats); return true; } FLAC_API FLAC__bool FLAC__metadata_chain_write_with_callbacks(FLAC__Metadata_Chain *chain, FLAC__bool use_padding, FLAC__IOHandle handle, FLAC__IOCallbacks callbacks) { off_t current_length; FLAC__ASSERT(0 != chain); if (chain->is_ogg) { /* cannot write back to Ogg FLAC yet */ chain->status = FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR; return false; } if (0 != chain->filename) { chain->status = FLAC__METADATA_CHAIN_STATUS_READ_WRITE_MISMATCH; return false; } if (0 == callbacks.write || 0 == callbacks.seek) { chain->status = FLAC__METADATA_CHAIN_STATUS_INVALID_CALLBACKS; return false; } if (FLAC__metadata_chain_check_if_tempfile_needed(chain, use_padding)) { chain->status = FLAC__METADATA_CHAIN_STATUS_WRONG_WRITE_CALL; return false; } current_length = chain_prepare_for_write_(chain, use_padding); /* a return value of 0 means there was an error; chain->status is already set */ if (0 == current_length) return false; FLAC__ASSERT(current_length == chain->initial_length); return chain_rewrite_metadata_in_place_cb_(chain, handle, callbacks.write, callbacks.seek); } FLAC_API FLAC__bool FLAC__metadata_chain_write_with_callbacks_and_tempfile(FLAC__Metadata_Chain *chain, FLAC__bool use_padding, FLAC__IOHandle handle, FLAC__IOCallbacks callbacks, FLAC__IOHandle temp_handle, FLAC__IOCallbacks temp_callbacks) { off_t current_length; FLAC__ASSERT(0 != chain); if (chain->is_ogg) { /* cannot write back to Ogg FLAC yet */ chain->status = FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR; return false; } if (0 != chain->filename) { chain->status = FLAC__METADATA_CHAIN_STATUS_READ_WRITE_MISMATCH; return false; } if (0 == callbacks.read || 0 == callbacks.seek || 0 == callbacks.eof) { chain->status = FLAC__METADATA_CHAIN_STATUS_INVALID_CALLBACKS; return false; } if (0 == temp_callbacks.write) { chain->status = FLAC__METADATA_CHAIN_STATUS_INVALID_CALLBACKS; return false; } if (!FLAC__metadata_chain_check_if_tempfile_needed(chain, use_padding)) { chain->status = FLAC__METADATA_CHAIN_STATUS_WRONG_WRITE_CALL; return false; } current_length = chain_prepare_for_write_(chain, use_padding); /* a return value of 0 means there was an error; chain->status is already set */ if (0 == current_length) return false; FLAC__ASSERT(current_length != chain->initial_length); /* rewind */ if(0 != callbacks.seek(handle, 0, SEEK_SET)) { chain->status = FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR; return false; } if(!chain_rewrite_file_cb_(chain, handle, callbacks.read, callbacks.seek, callbacks.eof, temp_handle, temp_callbacks.write)) return false; /* recompute lengths and offsets */ { const FLAC__Metadata_Node *node; chain->initial_length = current_length; chain->last_offset = chain->first_offset; for(node = chain->head; node; node = node->next) chain->last_offset += (FLAC__STREAM_METADATA_HEADER_LENGTH + node->data->length); } return true; } FLAC_API void FLAC__metadata_chain_merge_padding(FLAC__Metadata_Chain *chain) { FLAC__Metadata_Node *node; FLAC__ASSERT(0 != chain); for(node = chain->head; node; ) { if(!chain_merge_adjacent_padding_(chain, node)) node = node->next; } } FLAC_API void FLAC__metadata_chain_sort_padding(FLAC__Metadata_Chain *chain) { FLAC__Metadata_Node *node, *save; unsigned i; FLAC__ASSERT(0 != chain); /* * Don't try and be too smart... this simple algo is good enough for * the small number of nodes that we deal with. */ for(i = 0, node = chain->head; i < chain->nodes; i++) { if(node->data->type == FLAC__METADATA_TYPE_PADDING) { save = node->next; chain_remove_node_(chain, node); chain_append_node_(chain, node); node = save; } else { node = node->next; } } FLAC__metadata_chain_merge_padding(chain); } FLAC_API FLAC__Metadata_Iterator *FLAC__metadata_iterator_new(void) { FLAC__Metadata_Iterator *iterator = (FLAC__Metadata_Iterator*)calloc(1, sizeof(FLAC__Metadata_Iterator)); /* calloc() implies: iterator->current = 0; iterator->chain = 0; */ return iterator; } FLAC_API void FLAC__metadata_iterator_delete(FLAC__Metadata_Iterator *iterator) { FLAC__ASSERT(0 != iterator); free(iterator); } FLAC_API void FLAC__metadata_iterator_init(FLAC__Metadata_Iterator *iterator, FLAC__Metadata_Chain *chain) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != chain); FLAC__ASSERT(0 != chain->head); iterator->chain = chain; iterator->current = chain->head; } FLAC_API FLAC__bool FLAC__metadata_iterator_next(FLAC__Metadata_Iterator *iterator) { FLAC__ASSERT(0 != iterator); if(0 == iterator->current || 0 == iterator->current->next) return false; iterator->current = iterator->current->next; return true; } FLAC_API FLAC__bool FLAC__metadata_iterator_prev(FLAC__Metadata_Iterator *iterator) { FLAC__ASSERT(0 != iterator); if(0 == iterator->current || 0 == iterator->current->prev) return false; iterator->current = iterator->current->prev; return true; } FLAC_API FLAC__MetadataType FLAC__metadata_iterator_get_block_type(const FLAC__Metadata_Iterator *iterator) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->current); FLAC__ASSERT(0 != iterator->current->data); return iterator->current->data->type; } FLAC_API FLAC__StreamMetadata *FLAC__metadata_iterator_get_block(FLAC__Metadata_Iterator *iterator) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->current); return iterator->current->data; } FLAC_API FLAC__bool FLAC__metadata_iterator_set_block(FLAC__Metadata_Iterator *iterator, FLAC__StreamMetadata *block) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != block); return FLAC__metadata_iterator_delete_block(iterator, false) && FLAC__metadata_iterator_insert_block_after(iterator, block); } FLAC_API FLAC__bool FLAC__metadata_iterator_delete_block(FLAC__Metadata_Iterator *iterator, FLAC__bool replace_with_padding) { FLAC__Metadata_Node *save; FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->current); if(0 == iterator->current->prev) { FLAC__ASSERT(iterator->current->data->type == FLAC__METADATA_TYPE_STREAMINFO); return false; } save = iterator->current->prev; if(replace_with_padding) { FLAC__metadata_object_delete_data(iterator->current->data); iterator->current->data->type = FLAC__METADATA_TYPE_PADDING; } else { chain_delete_node_(iterator->chain, iterator->current); } iterator->current = save; return true; } FLAC_API FLAC__bool FLAC__metadata_iterator_insert_block_before(FLAC__Metadata_Iterator *iterator, FLAC__StreamMetadata *block) { FLAC__Metadata_Node *node; FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->current); FLAC__ASSERT(0 != block); if(block->type == FLAC__METADATA_TYPE_STREAMINFO) return false; if(0 == iterator->current->prev) { FLAC__ASSERT(iterator->current->data->type == FLAC__METADATA_TYPE_STREAMINFO); return false; } if(0 == (node = node_new_())) return false; node->data = block; iterator_insert_node_(iterator, node); iterator->current = node; return true; } FLAC_API FLAC__bool FLAC__metadata_iterator_insert_block_after(FLAC__Metadata_Iterator *iterator, FLAC__StreamMetadata *block) { FLAC__Metadata_Node *node; FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->current); FLAC__ASSERT(0 != block); if(block->type == FLAC__METADATA_TYPE_STREAMINFO) return false; if(0 == (node = node_new_())) return false; node->data = block; iterator_insert_node_after_(iterator, node); iterator->current = node; return true; } /**************************************************************************** * * Local function definitions * ***************************************************************************/ void pack_uint32_(FLAC__uint32 val, FLAC__byte *b, unsigned bytes) { unsigned i; b += bytes; for(i = 0; i < bytes; i++) { *(--b) = (FLAC__byte)(val & 0xff); val >>= 8; } } void pack_uint32_little_endian_(FLAC__uint32 val, FLAC__byte *b, unsigned bytes) { unsigned i; for(i = 0; i < bytes; i++) { *(b++) = (FLAC__byte)(val & 0xff); val >>= 8; } } void pack_uint64_(FLAC__uint64 val, FLAC__byte *b, unsigned bytes) { unsigned i; b += bytes; for(i = 0; i < bytes; i++) { *(--b) = (FLAC__byte)(val & 0xff); val >>= 8; } } FLAC__uint32 unpack_uint32_(FLAC__byte *b, unsigned bytes) { FLAC__uint32 ret = 0; unsigned i; for(i = 0; i < bytes; i++) ret = (ret << 8) | (FLAC__uint32)(*b++); return ret; } FLAC__uint32 unpack_uint32_little_endian_(FLAC__byte *b, unsigned bytes) { FLAC__uint32 ret = 0; unsigned i; b += bytes; for(i = 0; i < bytes; i++) ret = (ret << 8) | (FLAC__uint32)(*--b); return ret; } FLAC__uint64 unpack_uint64_(FLAC__byte *b, unsigned bytes) { FLAC__uint64 ret = 0; unsigned i; for(i = 0; i < bytes; i++) ret = (ret << 8) | (FLAC__uint64)(*b++); return ret; } FLAC__bool read_metadata_block_header_(FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); if(!read_metadata_block_header_cb_((FLAC__IOHandle)iterator->file, (FLAC__IOCallback_Read)fread, &iterator->is_last, &iterator->type, &iterator->length)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; return false; } return true; } FLAC__bool read_metadata_block_data_(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block) { FLAC__ASSERT(0 != iterator); FLAC__ASSERT(0 != iterator->file); iterator->status = read_metadata_block_data_cb_((FLAC__IOHandle)iterator->file, (FLAC__IOCallback_Read)fread, fseek_wrapper_, block); return (iterator->status == FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK); } FLAC__bool read_metadata_block_header_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__bool *is_last, FLAC__MetadataType *type, unsigned *length) { FLAC__byte raw_header[FLAC__STREAM_METADATA_HEADER_LENGTH]; if(read_cb(raw_header, 1, FLAC__STREAM_METADATA_HEADER_LENGTH, handle) != FLAC__STREAM_METADATA_HEADER_LENGTH) return false; *is_last = raw_header[0] & 0x80? true : false; *type = (FLAC__MetadataType)(raw_header[0] & 0x7f); *length = unpack_uint32_(raw_header + 1, 3); /* Note that we don't check: * if(iterator->type >= FLAC__METADATA_TYPE_UNDEFINED) * we just will read in an opaque block */ return true; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOCallback_Seek seek_cb, FLAC__StreamMetadata *block) { switch(block->type) { case FLAC__METADATA_TYPE_STREAMINFO: return read_metadata_block_data_streaminfo_cb_(handle, read_cb, &block->data.stream_info); case FLAC__METADATA_TYPE_PADDING: return read_metadata_block_data_padding_cb_(handle, seek_cb, &block->data.padding, block->length); case FLAC__METADATA_TYPE_APPLICATION: return read_metadata_block_data_application_cb_(handle, read_cb, &block->data.application, block->length); case FLAC__METADATA_TYPE_SEEKTABLE: return read_metadata_block_data_seektable_cb_(handle, read_cb, &block->data.seek_table, block->length); case FLAC__METADATA_TYPE_VORBIS_COMMENT: return read_metadata_block_data_vorbis_comment_cb_(handle, read_cb, &block->data.vorbis_comment); case FLAC__METADATA_TYPE_CUESHEET: return read_metadata_block_data_cuesheet_cb_(handle, read_cb, &block->data.cue_sheet); case FLAC__METADATA_TYPE_PICTURE: return read_metadata_block_data_picture_cb_(handle, read_cb, &block->data.picture); default: return read_metadata_block_data_unknown_cb_(handle, read_cb, &block->data.unknown, block->length); } } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_streaminfo_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_StreamInfo *block) { FLAC__byte buffer[FLAC__STREAM_METADATA_STREAMINFO_LENGTH], *b; if(read_cb(buffer, 1, FLAC__STREAM_METADATA_STREAMINFO_LENGTH, handle) != FLAC__STREAM_METADATA_STREAMINFO_LENGTH) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; b = buffer; /* we are using hardcoded numbers for simplicity but we should * probably eventually write a bit-level unpacker and use the * _STREAMINFO_ constants. */ block->min_blocksize = unpack_uint32_(b, 2); b += 2; block->max_blocksize = unpack_uint32_(b, 2); b += 2; block->min_framesize = unpack_uint32_(b, 3); b += 3; block->max_framesize = unpack_uint32_(b, 3); b += 3; block->sample_rate = (unpack_uint32_(b, 2) << 4) | ((unsigned)(b[2] & 0xf0) >> 4); block->channels = (unsigned)((b[2] & 0x0e) >> 1) + 1; block->bits_per_sample = ((((unsigned)(b[2] & 0x01)) << 4) | (((unsigned)(b[3] & 0xf0)) >> 4)) + 1; block->total_samples = (((FLAC__uint64)(b[3] & 0x0f)) << 32) | unpack_uint64_(b+4, 4); memcpy(block->md5sum, b+8, 16); return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_padding_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Seek seek_cb, FLAC__StreamMetadata_Padding *block, unsigned block_length) { (void)block; /* nothing to do; we don't care about reading the padding bytes */ if(0 != seek_cb(handle, block_length, SEEK_CUR)) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_application_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_Application *block, unsigned block_length) { const unsigned id_bytes = FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8; if(read_cb(block->id, 1, id_bytes, handle) != id_bytes) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; if(block_length < id_bytes) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block_length -= id_bytes; if(block_length == 0) { block->data = 0; } else { if(0 == (block->data = (FLAC__byte*)malloc(block_length))) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; if(read_cb(block->data, 1, block_length, handle) != block_length) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; } return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_seektable_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_SeekTable *block, unsigned block_length) { unsigned i; FLAC__byte buffer[FLAC__STREAM_METADATA_SEEKPOINT_LENGTH]; FLAC__ASSERT(block_length % FLAC__STREAM_METADATA_SEEKPOINT_LENGTH == 0); block->num_points = block_length / FLAC__STREAM_METADATA_SEEKPOINT_LENGTH; if(block->num_points == 0) block->points = 0; else if(0 == (block->points = (FLAC__StreamMetadata_SeekPoint*)safe_malloc_mul_2op_(block->num_points, /*times*/sizeof(FLAC__StreamMetadata_SeekPoint)))) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; for(i = 0; i < block->num_points; i++) { if(read_cb(buffer, 1, FLAC__STREAM_METADATA_SEEKPOINT_LENGTH, handle) != FLAC__STREAM_METADATA_SEEKPOINT_LENGTH) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; /* some MAGIC NUMBERs here */ block->points[i].sample_number = unpack_uint64_(buffer, 8); block->points[i].stream_offset = unpack_uint64_(buffer+8, 8); block->points[i].frame_samples = unpack_uint32_(buffer+16, 2); } return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_vorbis_comment_entry_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_VorbisComment_Entry *entry) { const unsigned entry_length_len = FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN / 8; FLAC__byte buffer[4]; /* magic number is asserted below */ FLAC__ASSERT(FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN / 8 == sizeof(buffer)); if(read_cb(buffer, 1, entry_length_len, handle) != entry_length_len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; entry->length = unpack_uint32_little_endian_(buffer, entry_length_len); if(0 != entry->entry) free(entry->entry); if(entry->length == 0) { entry->entry = 0; } else { if(0 == (entry->entry = (FLAC__byte*)safe_malloc_add_2op_(entry->length, /*+*/1))) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; if(read_cb(entry->entry, 1, entry->length, handle) != entry->length) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; entry->entry[entry->length] = '\0'; } return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_vorbis_comment_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_VorbisComment *block) { unsigned i; FLAC__Metadata_SimpleIteratorStatus status; const unsigned num_comments_len = FLAC__STREAM_METADATA_VORBIS_COMMENT_NUM_COMMENTS_LEN / 8; FLAC__byte buffer[4]; /* magic number is asserted below */ FLAC__ASSERT(FLAC__STREAM_METADATA_VORBIS_COMMENT_NUM_COMMENTS_LEN / 8 == sizeof(buffer)); if(FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK != (status = read_metadata_block_data_vorbis_comment_entry_cb_(handle, read_cb, &(block->vendor_string)))) return status; if(read_cb(buffer, 1, num_comments_len, handle) != num_comments_len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block->num_comments = unpack_uint32_little_endian_(buffer, num_comments_len); if(block->num_comments == 0) { block->comments = 0; } else if(0 == (block->comments = (FLAC__StreamMetadata_VorbisComment_Entry*)calloc(block->num_comments, sizeof(FLAC__StreamMetadata_VorbisComment_Entry)))) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; for(i = 0; i < block->num_comments; i++) { if(FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK != (status = read_metadata_block_data_vorbis_comment_entry_cb_(handle, read_cb, block->comments + i))) return status; } return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_cuesheet_track_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_CueSheet_Track *track) { unsigned i, len; FLAC__byte buffer[32]; /* asserted below that this is big enough */ FLAC__ASSERT(sizeof(buffer) >= sizeof(FLAC__uint64)); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN/8); FLAC__ASSERT(sizeof(buffer) >= (FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN) / 8); FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_OFFSET_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_TRACK_OFFSET_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; track->offset = unpack_uint64_(buffer, len); FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_NUMBER_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_TRACK_NUMBER_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; track->number = (FLAC__byte)unpack_uint32_(buffer, len); FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN / 8; if(read_cb(track->isrc, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; FLAC__ASSERT((FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN) % 8 == 0); len = (FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN) / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN == 1); FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN == 1); track->type = buffer[0] >> 7; track->pre_emphasis = (buffer[0] >> 6) & 1; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_NUM_INDICES_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_TRACK_NUM_INDICES_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; track->num_indices = (FLAC__byte)unpack_uint32_(buffer, len); if(track->num_indices == 0) { track->indices = 0; } else if(0 == (track->indices = (FLAC__StreamMetadata_CueSheet_Index*)calloc(track->num_indices, sizeof(FLAC__StreamMetadata_CueSheet_Index)))) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; for(i = 0; i < track->num_indices; i++) { FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_INDEX_OFFSET_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_INDEX_OFFSET_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; track->indices[i].offset = unpack_uint64_(buffer, len); FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_INDEX_NUMBER_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_INDEX_NUMBER_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; track->indices[i].number = (FLAC__byte)unpack_uint32_(buffer, len); FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; } return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_cuesheet_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_CueSheet *block) { unsigned i, len; FLAC__Metadata_SimpleIteratorStatus status; FLAC__byte buffer[1024]; /* MSVC needs a constant expression so we put a magic number and assert */ FLAC__ASSERT((FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN + FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN)/8 <= sizeof(buffer)); FLAC__ASSERT(sizeof(FLAC__uint64) <= sizeof(buffer)); FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN / 8; if(read_cb(block->media_catalog_number, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_LEAD_IN_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_LEAD_IN_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block->lead_in = unpack_uint64_(buffer, len); FLAC__ASSERT((FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN + FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN) % 8 == 0); len = (FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN + FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN) / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block->is_cd = buffer[0]&0x80? true : false; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_NUM_TRACKS_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_NUM_TRACKS_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block->num_tracks = unpack_uint32_(buffer, len); if(block->num_tracks == 0) { block->tracks = 0; } else if(0 == (block->tracks = (FLAC__StreamMetadata_CueSheet_Track*)calloc(block->num_tracks, sizeof(FLAC__StreamMetadata_CueSheet_Track)))) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; for(i = 0; i < block->num_tracks; i++) { if(FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK != (status = read_metadata_block_data_cuesheet_track_cb_(handle, read_cb, block->tracks + i))) return status; } return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } static FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_picture_cstring_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__byte **data, FLAC__uint32 *length, FLAC__uint32 length_len) { FLAC__byte buffer[sizeof(FLAC__uint32)]; FLAC__ASSERT(0 != data); FLAC__ASSERT(length_len%8 == 0); length_len /= 8; /* convert to bytes */ FLAC__ASSERT(sizeof(buffer) >= length_len); if(read_cb(buffer, 1, length_len, handle) != length_len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; *length = unpack_uint32_(buffer, length_len); if(0 != *data) free(*data); if(0 == (*data = (FLAC__byte*)safe_malloc_add_2op_(*length, /*+*/1))) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; if(*length > 0) { if(read_cb(*data, 1, *length, handle) != *length) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; } (*data)[*length] = '\0'; return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_picture_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_Picture *block) { FLAC__Metadata_SimpleIteratorStatus status; FLAC__byte buffer[4]; /* asserted below that this is big enough */ FLAC__uint32 len; FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_TYPE_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_COLORS_LEN/8); FLAC__ASSERT(FLAC__STREAM_METADATA_PICTURE_TYPE_LEN % 8 == 0); len = FLAC__STREAM_METADATA_PICTURE_TYPE_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block->type = (FLAC__StreamMetadata_Picture_Type)unpack_uint32_(buffer, len); if((status = read_metadata_block_data_picture_cstring_cb_(handle, read_cb, (FLAC__byte**)(&(block->mime_type)), &len, FLAC__STREAM_METADATA_PICTURE_MIME_TYPE_LENGTH_LEN)) != FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK) return status; if((status = read_metadata_block_data_picture_cstring_cb_(handle, read_cb, &(block->description), &len, FLAC__STREAM_METADATA_PICTURE_DESCRIPTION_LENGTH_LEN)) != FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK) return status; FLAC__ASSERT(FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN % 8 == 0); len = FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block->width = unpack_uint32_(buffer, len); FLAC__ASSERT(FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN % 8 == 0); len = FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block->height = unpack_uint32_(buffer, len); FLAC__ASSERT(FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN % 8 == 0); len = FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block->depth = unpack_uint32_(buffer, len); FLAC__ASSERT(FLAC__STREAM_METADATA_PICTURE_COLORS_LEN % 8 == 0); len = FLAC__STREAM_METADATA_PICTURE_COLORS_LEN / 8; if(read_cb(buffer, 1, len, handle) != len) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; block->colors = unpack_uint32_(buffer, len); /* for convenience we use read_metadata_block_data_picture_cstring_cb_() even though it adds an extra terminating NUL we don't use */ if((status = read_metadata_block_data_picture_cstring_cb_(handle, read_cb, &(block->data), &(block->data_length), FLAC__STREAM_METADATA_PICTURE_DATA_LENGTH_LEN)) != FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK) return status; return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__Metadata_SimpleIteratorStatus read_metadata_block_data_unknown_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__StreamMetadata_Unknown *block, unsigned block_length) { if(block_length == 0) { block->data = 0; } else { if(0 == (block->data = (FLAC__byte*)malloc(block_length))) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; if(read_cb(block->data, 1, block_length, handle) != block_length) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; } return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; } FLAC__bool write_metadata_block_header_(FILE *file, FLAC__Metadata_SimpleIteratorStatus *status, const FLAC__StreamMetadata *block) { FLAC__ASSERT(0 != file); FLAC__ASSERT(0 != status); if(!write_metadata_block_header_cb_((FLAC__IOHandle)file, (FLAC__IOCallback_Write)fwrite, block)) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR; return false; } return true; } FLAC__bool write_metadata_block_data_(FILE *file, FLAC__Metadata_SimpleIteratorStatus *status, const FLAC__StreamMetadata *block) { FLAC__ASSERT(0 != file); FLAC__ASSERT(0 != status); if (write_metadata_block_data_cb_((FLAC__IOHandle)file, (FLAC__IOCallback_Write)fwrite, block)) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK; return true; } else { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR; return false; } } FLAC__bool write_metadata_block_header_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata *block) { FLAC__byte buffer[FLAC__STREAM_METADATA_HEADER_LENGTH]; FLAC__ASSERT(block->length < (1u << FLAC__STREAM_METADATA_LENGTH_LEN)); buffer[0] = (block->is_last? 0x80 : 0) | (FLAC__byte)block->type; pack_uint32_(block->length, buffer + 1, 3); if(write_cb(buffer, 1, FLAC__STREAM_METADATA_HEADER_LENGTH, handle) != FLAC__STREAM_METADATA_HEADER_LENGTH) return false; return true; } FLAC__bool write_metadata_block_data_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata *block) { FLAC__ASSERT(0 != block); switch(block->type) { case FLAC__METADATA_TYPE_STREAMINFO: return write_metadata_block_data_streaminfo_cb_(handle, write_cb, &block->data.stream_info); case FLAC__METADATA_TYPE_PADDING: return write_metadata_block_data_padding_cb_(handle, write_cb, &block->data.padding, block->length); case FLAC__METADATA_TYPE_APPLICATION: return write_metadata_block_data_application_cb_(handle, write_cb, &block->data.application, block->length); case FLAC__METADATA_TYPE_SEEKTABLE: return write_metadata_block_data_seektable_cb_(handle, write_cb, &block->data.seek_table); case FLAC__METADATA_TYPE_VORBIS_COMMENT: return write_metadata_block_data_vorbis_comment_cb_(handle, write_cb, &block->data.vorbis_comment); case FLAC__METADATA_TYPE_CUESHEET: return write_metadata_block_data_cuesheet_cb_(handle, write_cb, &block->data.cue_sheet); case FLAC__METADATA_TYPE_PICTURE: return write_metadata_block_data_picture_cb_(handle, write_cb, &block->data.picture); default: return write_metadata_block_data_unknown_cb_(handle, write_cb, &block->data.unknown, block->length); } } FLAC__bool write_metadata_block_data_streaminfo_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_StreamInfo *block) { FLAC__byte buffer[FLAC__STREAM_METADATA_STREAMINFO_LENGTH]; const unsigned channels1 = block->channels - 1; const unsigned bps1 = block->bits_per_sample - 1; /* we are using hardcoded numbers for simplicity but we should * probably eventually write a bit-level packer and use the * _STREAMINFO_ constants. */ pack_uint32_(block->min_blocksize, buffer, 2); pack_uint32_(block->max_blocksize, buffer+2, 2); pack_uint32_(block->min_framesize, buffer+4, 3); pack_uint32_(block->max_framesize, buffer+7, 3); buffer[10] = (block->sample_rate >> 12) & 0xff; buffer[11] = (block->sample_rate >> 4) & 0xff; buffer[12] = ((block->sample_rate & 0x0f) << 4) | (channels1 << 1) | (bps1 >> 4); buffer[13] = (FLAC__byte)(((bps1 & 0x0f) << 4) | ((block->total_samples >> 32) & 0x0f)); pack_uint32_((FLAC__uint32)block->total_samples, buffer+14, 4); memcpy(buffer+18, block->md5sum, 16); if(write_cb(buffer, 1, FLAC__STREAM_METADATA_STREAMINFO_LENGTH, handle) != FLAC__STREAM_METADATA_STREAMINFO_LENGTH) return false; return true; } FLAC__bool write_metadata_block_data_padding_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_Padding *block, unsigned block_length) { unsigned i, n = block_length; FLAC__byte buffer[1024]; (void)block; memset(buffer, 0, 1024); for(i = 0; i < n/1024; i++) if(write_cb(buffer, 1, 1024, handle) != 1024) return false; n %= 1024; if(write_cb(buffer, 1, n, handle) != n) return false; return true; } FLAC__bool write_metadata_block_data_application_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_Application *block, unsigned block_length) { const unsigned id_bytes = FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8; if(write_cb(block->id, 1, id_bytes, handle) != id_bytes) return false; block_length -= id_bytes; if(write_cb(block->data, 1, block_length, handle) != block_length) return false; return true; } FLAC__bool write_metadata_block_data_seektable_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_SeekTable *block) { unsigned i; FLAC__byte buffer[FLAC__STREAM_METADATA_SEEKPOINT_LENGTH]; for(i = 0; i < block->num_points; i++) { /* some MAGIC NUMBERs here */ pack_uint64_(block->points[i].sample_number, buffer, 8); pack_uint64_(block->points[i].stream_offset, buffer+8, 8); pack_uint32_(block->points[i].frame_samples, buffer+16, 2); if(write_cb(buffer, 1, FLAC__STREAM_METADATA_SEEKPOINT_LENGTH, handle) != FLAC__STREAM_METADATA_SEEKPOINT_LENGTH) return false; } return true; } FLAC__bool write_metadata_block_data_vorbis_comment_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_VorbisComment *block) { unsigned i; const unsigned entry_length_len = FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN / 8; const unsigned num_comments_len = FLAC__STREAM_METADATA_VORBIS_COMMENT_NUM_COMMENTS_LEN / 8; FLAC__byte buffer[4]; /* magic number is asserted below */ FLAC__ASSERT(max(FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN, FLAC__STREAM_METADATA_VORBIS_COMMENT_NUM_COMMENTS_LEN) / 8 == sizeof(buffer)); pack_uint32_little_endian_(block->vendor_string.length, buffer, entry_length_len); if(write_cb(buffer, 1, entry_length_len, handle) != entry_length_len) return false; if(write_cb(block->vendor_string.entry, 1, block->vendor_string.length, handle) != block->vendor_string.length) return false; pack_uint32_little_endian_(block->num_comments, buffer, num_comments_len); if(write_cb(buffer, 1, num_comments_len, handle) != num_comments_len) return false; for(i = 0; i < block->num_comments; i++) { pack_uint32_little_endian_(block->comments[i].length, buffer, entry_length_len); if(write_cb(buffer, 1, entry_length_len, handle) != entry_length_len) return false; if(write_cb(block->comments[i].entry, 1, block->comments[i].length, handle) != block->comments[i].length) return false; } return true; } FLAC__bool write_metadata_block_data_cuesheet_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_CueSheet *block) { unsigned i, j, len; FLAC__byte buffer[1024]; /* asserted below that this is big enough */ FLAC__ASSERT(sizeof(buffer) >= sizeof(FLAC__uint64)); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN/8); FLAC__ASSERT(sizeof(buffer) >= (FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN + FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN)/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN/8); FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN / 8; if(write_cb(block->media_catalog_number, 1, len, handle) != len) return false; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_LEAD_IN_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_LEAD_IN_LEN / 8; pack_uint64_(block->lead_in, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; FLAC__ASSERT((FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN + FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN) % 8 == 0); len = (FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN + FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN) / 8; memset(buffer, 0, len); if(block->is_cd) buffer[0] |= 0x80; if(write_cb(buffer, 1, len, handle) != len) return false; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_NUM_TRACKS_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_NUM_TRACKS_LEN / 8; pack_uint32_(block->num_tracks, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; for(i = 0; i < block->num_tracks; i++) { FLAC__StreamMetadata_CueSheet_Track *track = block->tracks + i; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_OFFSET_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_TRACK_OFFSET_LEN / 8; pack_uint64_(track->offset, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_NUMBER_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_TRACK_NUMBER_LEN / 8; pack_uint32_(track->number, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN / 8; if(write_cb(track->isrc, 1, len, handle) != len) return false; FLAC__ASSERT((FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN) % 8 == 0); len = (FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN) / 8; memset(buffer, 0, len); buffer[0] = (track->type << 7) | (track->pre_emphasis << 6); if(write_cb(buffer, 1, len, handle) != len) return false; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_NUM_INDICES_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_TRACK_NUM_INDICES_LEN / 8; pack_uint32_(track->num_indices, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; for(j = 0; j < track->num_indices; j++) { FLAC__StreamMetadata_CueSheet_Index *index = track->indices + j; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_INDEX_OFFSET_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_INDEX_OFFSET_LEN / 8; pack_uint64_(index->offset, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_INDEX_NUMBER_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_INDEX_NUMBER_LEN / 8; pack_uint32_(index->number, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN % 8 == 0); len = FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN / 8; memset(buffer, 0, len); if(write_cb(buffer, 1, len, handle) != len) return false; } } return true; } FLAC__bool write_metadata_block_data_picture_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_Picture *block) { unsigned len; size_t slen; FLAC__byte buffer[4]; /* magic number is asserted below */ FLAC__ASSERT(0 == FLAC__STREAM_METADATA_PICTURE_TYPE_LEN%8); FLAC__ASSERT(0 == FLAC__STREAM_METADATA_PICTURE_MIME_TYPE_LENGTH_LEN%8); FLAC__ASSERT(0 == FLAC__STREAM_METADATA_PICTURE_DESCRIPTION_LENGTH_LEN%8); FLAC__ASSERT(0 == FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN%8); FLAC__ASSERT(0 == FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN%8); FLAC__ASSERT(0 == FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN%8); FLAC__ASSERT(0 == FLAC__STREAM_METADATA_PICTURE_COLORS_LEN%8); FLAC__ASSERT(0 == FLAC__STREAM_METADATA_PICTURE_DATA_LENGTH_LEN%8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_TYPE_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_MIME_TYPE_LENGTH_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_DESCRIPTION_LENGTH_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_COLORS_LEN/8); FLAC__ASSERT(sizeof(buffer) >= FLAC__STREAM_METADATA_PICTURE_DATA_LENGTH_LEN/8); len = FLAC__STREAM_METADATA_PICTURE_TYPE_LEN/8; pack_uint32_(block->type, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; len = FLAC__STREAM_METADATA_PICTURE_MIME_TYPE_LENGTH_LEN/8; slen = strlen(block->mime_type); pack_uint32_(slen, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; if(write_cb(block->mime_type, 1, slen, handle) != slen) return false; len = FLAC__STREAM_METADATA_PICTURE_DESCRIPTION_LENGTH_LEN/8; slen = strlen((const char *)block->description); pack_uint32_(slen, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; if(write_cb(block->description, 1, slen, handle) != slen) return false; len = FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN/8; pack_uint32_(block->width, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; len = FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN/8; pack_uint32_(block->height, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; len = FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN/8; pack_uint32_(block->depth, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; len = FLAC__STREAM_METADATA_PICTURE_COLORS_LEN/8; pack_uint32_(block->colors, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; len = FLAC__STREAM_METADATA_PICTURE_DATA_LENGTH_LEN/8; pack_uint32_(block->data_length, buffer, len); if(write_cb(buffer, 1, len, handle) != len) return false; if(write_cb(block->data, 1, block->data_length, handle) != block->data_length) return false; return true; } FLAC__bool write_metadata_block_data_unknown_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Write write_cb, const FLAC__StreamMetadata_Unknown *block, unsigned block_length) { if(write_cb(block->data, 1, block_length, handle) != block_length) return false; return true; } FLAC__bool write_metadata_block_stationary_(FLAC__Metadata_SimpleIterator *iterator, const FLAC__StreamMetadata *block) { if(0 != fseeko(iterator->file, iterator->offset[iterator->depth], SEEK_SET)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } if(!write_metadata_block_header_(iterator->file, &iterator->status, block)) return false; if(!write_metadata_block_data_(iterator->file, &iterator->status, block)) return false; if(0 != fseeko(iterator->file, iterator->offset[iterator->depth], SEEK_SET)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } return read_metadata_block_header_(iterator); } FLAC__bool write_metadata_block_stationary_with_padding_(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block, unsigned padding_length, FLAC__bool padding_is_last) { FLAC__StreamMetadata *padding; if(0 != fseeko(iterator->file, iterator->offset[iterator->depth], SEEK_SET)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } block->is_last = false; if(!write_metadata_block_header_(iterator->file, &iterator->status, block)) return false; if(!write_metadata_block_data_(iterator->file, &iterator->status, block)) return false; if(0 == (padding = FLAC__metadata_object_new(FLAC__METADATA_TYPE_PADDING))) return FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; padding->is_last = padding_is_last; padding->length = padding_length; if(!write_metadata_block_header_(iterator->file, &iterator->status, padding)) { FLAC__metadata_object_delete(padding); return false; } if(!write_metadata_block_data_(iterator->file, &iterator->status, padding)) { FLAC__metadata_object_delete(padding); return false; } FLAC__metadata_object_delete(padding); if(0 != fseeko(iterator->file, iterator->offset[iterator->depth], SEEK_SET)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } return read_metadata_block_header_(iterator); } FLAC__bool rewrite_whole_file_(FLAC__Metadata_SimpleIterator *iterator, FLAC__StreamMetadata *block, FLAC__bool append) { FILE *tempfile; char *tempfilename; int fixup_is_last_code = 0; /* 0 => no need to change any is_last flags */ off_t fixup_is_last_flag_offset = -1; FLAC__ASSERT(0 != block || append == false); if(iterator->is_last) { if(append) { fixup_is_last_code = 1; /* 1 => clear the is_last flag at the following offset */ fixup_is_last_flag_offset = iterator->offset[iterator->depth]; } else if(0 == block) { simple_iterator_push_(iterator); if(!FLAC__metadata_simple_iterator_prev(iterator)) { (void)simple_iterator_pop_(iterator); return false; } fixup_is_last_code = -1; /* -1 => set the is_last the flag at the following offset */ fixup_is_last_flag_offset = iterator->offset[iterator->depth]; if(!simple_iterator_pop_(iterator)) return false; } } if(!simple_iterator_copy_file_prefix_(iterator, &tempfile, &tempfilename, append)) return false; if(0 != block) { if(!write_metadata_block_header_(tempfile, &iterator->status, block)) { cleanup_tempfile_(&tempfile, &tempfilename); return false; } if(!write_metadata_block_data_(tempfile, &iterator->status, block)) { cleanup_tempfile_(&tempfile, &tempfilename); return false; } } if(!simple_iterator_copy_file_postfix_(iterator, &tempfile, &tempfilename, fixup_is_last_code, fixup_is_last_flag_offset, block==0)) return false; if(append) return FLAC__metadata_simple_iterator_next(iterator); return true; } void simple_iterator_push_(FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(iterator->depth+1 < SIMPLE_ITERATOR_MAX_PUSH_DEPTH); iterator->offset[iterator->depth+1] = iterator->offset[iterator->depth]; iterator->depth++; } FLAC__bool simple_iterator_pop_(FLAC__Metadata_SimpleIterator *iterator) { FLAC__ASSERT(iterator->depth > 0); iterator->depth--; if(0 != fseeko(iterator->file, iterator->offset[iterator->depth], SEEK_SET)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } return read_metadata_block_header_(iterator); } /* return meanings: * 0: ok * 1: read error * 2: seek error * 3: not a FLAC file */ unsigned seek_to_first_metadata_block_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOCallback_Seek seek_cb) { FLAC__byte buffer[4]; size_t n; unsigned i; FLAC__ASSERT(FLAC__STREAM_SYNC_LENGTH == sizeof(buffer)); /* skip any id3v2 tag */ errno = 0; n = read_cb(buffer, 1, 4, handle); if(errno) return 1; else if(n != 4) return 3; else if(0 == memcmp(buffer, "ID3", 3)) { unsigned tag_length = 0; /* skip to the tag length */ if(seek_cb(handle, 2, SEEK_CUR) < 0) return 2; /* read the length */ for(i = 0; i < 4; i++) { if(read_cb(buffer, 1, 1, handle) < 1 || buffer[0] & 0x80) return 1; tag_length <<= 7; tag_length |= (buffer[0] & 0x7f); } /* skip the rest of the tag */ if(seek_cb(handle, tag_length, SEEK_CUR) < 0) return 2; /* read the stream sync code */ errno = 0; n = read_cb(buffer, 1, 4, handle); if(errno) return 1; else if(n != 4) return 3; } /* check for the fLaC signature */ if(0 == memcmp(FLAC__STREAM_SYNC_STRING, buffer, FLAC__STREAM_SYNC_LENGTH)) return 0; else return 3; } unsigned seek_to_first_metadata_block_(FILE *f) { return seek_to_first_metadata_block_cb_((FLAC__IOHandle)f, (FLAC__IOCallback_Read)fread, fseek_wrapper_); } FLAC__bool simple_iterator_copy_file_prefix_(FLAC__Metadata_SimpleIterator *iterator, FILE **tempfile, char **tempfilename, FLAC__bool append) { const off_t offset_end = append? iterator->offset[iterator->depth] + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH + (off_t)iterator->length : iterator->offset[iterator->depth]; if(0 != fseeko(iterator->file, 0, SEEK_SET)) { iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } if(!open_tempfile_(iterator->filename, iterator->tempfile_path_prefix, tempfile, tempfilename, &iterator->status)) { cleanup_tempfile_(tempfile, tempfilename); return false; } if(!copy_n_bytes_from_file_(iterator->file, *tempfile, offset_end, &iterator->status)) { cleanup_tempfile_(tempfile, tempfilename); return false; } return true; } FLAC__bool simple_iterator_copy_file_postfix_(FLAC__Metadata_SimpleIterator *iterator, FILE **tempfile, char **tempfilename, int fixup_is_last_code, off_t fixup_is_last_flag_offset, FLAC__bool backup) { off_t save_offset = iterator->offset[iterator->depth]; FLAC__ASSERT(0 != *tempfile); if(0 != fseeko(iterator->file, save_offset + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH + (off_t)iterator->length, SEEK_SET)) { cleanup_tempfile_(tempfile, tempfilename); iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } if(!copy_remaining_bytes_from_file_(iterator->file, *tempfile, &iterator->status)) { cleanup_tempfile_(tempfile, tempfilename); return false; } if(fixup_is_last_code != 0) { /* * if code == 1, it means a block was appended to the end so * we have to clear the is_last flag of the previous block * if code == -1, it means the last block was deleted so * we have to set the is_last flag of the previous block */ /* MAGIC NUMBERs here; we know the is_last flag is the high bit of the byte at this location */ FLAC__byte x; if(0 != fseeko(*tempfile, fixup_is_last_flag_offset, SEEK_SET)) { cleanup_tempfile_(tempfile, tempfilename); iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } if(fread(&x, 1, 1, *tempfile) != 1) { cleanup_tempfile_(tempfile, tempfilename); iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; return false; } if(fixup_is_last_code > 0) { FLAC__ASSERT(x & 0x80); x &= 0x7f; } else { FLAC__ASSERT(!(x & 0x80)); x |= 0x80; } if(0 != fseeko(*tempfile, fixup_is_last_flag_offset, SEEK_SET)) { cleanup_tempfile_(tempfile, tempfilename); iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR; return false; } if(local__fwrite(&x, 1, 1, *tempfile) != 1) { cleanup_tempfile_(tempfile, tempfilename); iterator->status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR; return false; } } (void)fclose(iterator->file); if(!transport_tempfile_(iterator->filename, tempfile, tempfilename, &iterator->status)) return false; if(iterator->has_stats) set_file_stats_(iterator->filename, &iterator->stats); if(!simple_iterator_prime_input_(iterator, !iterator->is_writable)) return false; if(backup) { while(iterator->offset[iterator->depth] + (off_t)FLAC__STREAM_METADATA_HEADER_LENGTH + (off_t)iterator->length < save_offset) if(!FLAC__metadata_simple_iterator_next(iterator)) return false; return true; } else { /* move the iterator to it's original block faster by faking a push, then doing a pop_ */ FLAC__ASSERT(iterator->depth == 0); iterator->offset[0] = save_offset; iterator->depth++; return simple_iterator_pop_(iterator); } } FLAC__bool copy_n_bytes_from_file_(FILE *file, FILE *tempfile, off_t bytes, FLAC__Metadata_SimpleIteratorStatus *status) { FLAC__byte buffer[8192]; size_t n; FLAC__ASSERT(bytes >= 0); while(bytes > 0) { n = min(sizeof(buffer), (size_t)bytes); if(fread(buffer, 1, n, file) != n) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; return false; } if(local__fwrite(buffer, 1, n, tempfile) != n) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR; return false; } bytes -= n; } return true; } FLAC__bool copy_n_bytes_from_file_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOHandle temp_handle, FLAC__IOCallback_Write temp_write_cb, off_t bytes, FLAC__Metadata_SimpleIteratorStatus *status) { FLAC__byte buffer[8192]; size_t n; FLAC__ASSERT(bytes >= 0); while(bytes > 0) { n = min(sizeof(buffer), (size_t)bytes); if(read_cb(buffer, 1, n, handle) != n) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; return false; } if(temp_write_cb(buffer, 1, n, temp_handle) != n) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR; return false; } bytes -= n; } return true; } FLAC__bool copy_remaining_bytes_from_file_(FILE *file, FILE *tempfile, FLAC__Metadata_SimpleIteratorStatus *status) { FLAC__byte buffer[8192]; size_t n; while(!feof(file)) { n = fread(buffer, 1, sizeof(buffer), file); if(n == 0 && !feof(file)) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; return false; } if(n > 0 && local__fwrite(buffer, 1, n, tempfile) != n) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR; return false; } } return true; } FLAC__bool copy_remaining_bytes_from_file_cb_(FLAC__IOHandle handle, FLAC__IOCallback_Read read_cb, FLAC__IOCallback_Eof eof_cb, FLAC__IOHandle temp_handle, FLAC__IOCallback_Write temp_write_cb, FLAC__Metadata_SimpleIteratorStatus *status) { FLAC__byte buffer[8192]; size_t n; while(!eof_cb(handle)) { n = read_cb(buffer, 1, sizeof(buffer), handle); if(n == 0 && !eof_cb(handle)) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR; return false; } if(n > 0 && temp_write_cb(buffer, 1, n, temp_handle) != n) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR; return false; } } return true; } FLAC__bool open_tempfile_(const char *filename, const char *tempfile_path_prefix, FILE **tempfile, char **tempfilename, FLAC__Metadata_SimpleIteratorStatus *status) { static const char *tempfile_suffix = ".metadata_edit"; if(0 == tempfile_path_prefix) { if(0 == (*tempfilename = (char*)safe_malloc_add_3op_(strlen(filename), /*+*/strlen(tempfile_suffix), /*+*/1))) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; return false; } strcpy(*tempfilename, filename); strcat(*tempfilename, tempfile_suffix); } else { const char *p = strrchr(filename, '/'); if(0 == p) p = filename; else p++; if(0 == (*tempfilename = (char*)safe_malloc_add_4op_(strlen(tempfile_path_prefix), /*+*/strlen(p), /*+*/strlen(tempfile_suffix), /*+*/2))) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR; return false; } strcpy(*tempfilename, tempfile_path_prefix); strcat(*tempfilename, "/"); strcat(*tempfilename, p); strcat(*tempfilename, tempfile_suffix); } if(0 == (*tempfile = fopen(*tempfilename, "w+b"))) { *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ERROR_OPENING_FILE; return false; } return true; } FLAC__bool transport_tempfile_(const char *filename, FILE **tempfile, char **tempfilename, FLAC__Metadata_SimpleIteratorStatus *status) { FLAC__ASSERT(0 != filename); FLAC__ASSERT(0 != tempfile); FLAC__ASSERT(0 != *tempfile); FLAC__ASSERT(0 != tempfilename); FLAC__ASSERT(0 != *tempfilename); FLAC__ASSERT(0 != status); (void)fclose(*tempfile); *tempfile = 0; #if defined _MSC_VER || defined __BORLANDC__ || defined __MINGW32__ || defined __EMX__ /* on some flavors of windows, rename() will fail if the destination already exists */ if(unlink(filename) < 0) { cleanup_tempfile_(tempfile, tempfilename); *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_UNLINK_ERROR; return false; } #endif /*@@@ to fully support the tempfile_path_prefix we need to update this piece to actually copy across filesystems instead of just rename(): */ if(0 != rename(*tempfilename, filename)) { cleanup_tempfile_(tempfile, tempfilename); *status = FLAC__METADATA_SIMPLE_ITERATOR_STATUS_RENAME_ERROR; return false; } cleanup_tempfile_(tempfile, tempfilename); return true; } void cleanup_tempfile_(FILE **tempfile, char **tempfilename) { if(0 != *tempfile) { (void)fclose(*tempfile); *tempfile = 0; } if(0 != *tempfilename) { (void)unlink(*tempfilename); free(*tempfilename); *tempfilename = 0; } } FLAC__bool get_file_stats_(const char *filename, struct stat *stats) { FLAC__ASSERT(0 != filename); FLAC__ASSERT(0 != stats); return (0 == stat(filename, stats)); } void set_file_stats_(const char *filename, struct stat *stats) { struct utimbuf srctime; FLAC__ASSERT(0 != filename); FLAC__ASSERT(0 != stats); srctime.actime = stats->st_atime; srctime.modtime = stats->st_mtime; (void)chmod(filename, stats->st_mode); (void)utime(filename, &srctime); #if !defined _WIN32 && !defined __BORLANDC__ && !defined __MINGW32__ && !defined __EMX__ (void)chown(filename, stats->st_uid, -1); (void)chown(filename, -1, stats->st_gid); #endif } int fseek_wrapper_(FLAC__IOHandle handle, FLAC__int64 offset, int whence) { return fseeko((FILE*)handle, (off_t)offset, whence); } FLAC__int64 ftell_wrapper_(FLAC__IOHandle handle) { return ftello((FILE*)handle); } FLAC__Metadata_ChainStatus get_equivalent_status_(FLAC__Metadata_SimpleIteratorStatus status) { switch(status) { case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_OK: return FLAC__METADATA_CHAIN_STATUS_OK; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ILLEGAL_INPUT: return FLAC__METADATA_CHAIN_STATUS_ILLEGAL_INPUT; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_ERROR_OPENING_FILE: return FLAC__METADATA_CHAIN_STATUS_ERROR_OPENING_FILE; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_A_FLAC_FILE: return FLAC__METADATA_CHAIN_STATUS_NOT_A_FLAC_FILE; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_NOT_WRITABLE: return FLAC__METADATA_CHAIN_STATUS_NOT_WRITABLE; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_BAD_METADATA: return FLAC__METADATA_CHAIN_STATUS_BAD_METADATA; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_READ_ERROR: return FLAC__METADATA_CHAIN_STATUS_READ_ERROR; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_SEEK_ERROR: return FLAC__METADATA_CHAIN_STATUS_SEEK_ERROR; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_WRITE_ERROR: return FLAC__METADATA_CHAIN_STATUS_WRITE_ERROR; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_RENAME_ERROR: return FLAC__METADATA_CHAIN_STATUS_RENAME_ERROR; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_UNLINK_ERROR: return FLAC__METADATA_CHAIN_STATUS_UNLINK_ERROR; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_MEMORY_ALLOCATION_ERROR: return FLAC__METADATA_CHAIN_STATUS_MEMORY_ALLOCATION_ERROR; case FLAC__METADATA_SIMPLE_ITERATOR_STATUS_INTERNAL_ERROR: default: return FLAC__METADATA_CHAIN_STATUS_INTERNAL_ERROR; } } sources_5316/external/flac/flac_metadata_object.c0000644000176700017670000017071110720610767020726 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include #include #include "flac_private_metadata.h" #include "flac_FLAC_assert.h" #include "flac_share_alloc.h" /**************************************************************************** * * Local routines * ***************************************************************************/ /* copy bytes: * from = NULL && bytes = 0 * to <- NULL * from != NULL && bytes > 0 * to <- copy of from * else ASSERT * malloc error leaves 'to' unchanged */ static FLAC__bool copy_bytes_(FLAC__byte **to, const FLAC__byte *from, unsigned bytes) { FLAC__ASSERT(0 != to); if(bytes > 0 && 0 != from) { FLAC__byte *x; if(0 == (x = (FLAC__byte*)safe_malloc_(bytes))) return false; memcpy(x, from, bytes); *to = x; } else { FLAC__ASSERT(0 == from); FLAC__ASSERT(bytes == 0); *to = 0; } return true; } #if 0 /* UNUSED */ /* like copy_bytes_(), but free()s the original '*to' if the copy succeeds and the original '*to' is non-NULL */ static FLAC__bool free_copy_bytes_(FLAC__byte **to, const FLAC__byte *from, unsigned bytes) { FLAC__byte *copy; FLAC__ASSERT(0 != to); if(copy_bytes_(©, from, bytes)) { if(*to) free(*to); *to = copy; return true; } else return false; } #endif /* reallocate entry to 1 byte larger and add a terminating NUL */ /* realloc() failure leaves entry unchanged */ static FLAC__bool ensure_null_terminated_(FLAC__byte **entry, unsigned length) { FLAC__byte *x = (FLAC__byte*)safe_realloc_add_2op_(*entry, length, /*+*/1); if(0 != x) { x[length] = '\0'; *entry = x; return true; } else return false; } /* copies the NUL-terminated C-string 'from' to '*to', leaving '*to' * unchanged if malloc fails, free()ing the original '*to' if it * succeeds and the original '*to' was not NULL */ static FLAC__bool copy_cstring_(char **to, const char *from) { char *copy = strdup(from); FLAC__ASSERT(to); if(copy) { if(*to) free(*to); *to = copy; return true; } else return false; } static FLAC__bool copy_vcentry_(FLAC__StreamMetadata_VorbisComment_Entry *to, const FLAC__StreamMetadata_VorbisComment_Entry *from) { to->length = from->length; if(0 == from->entry) { FLAC__ASSERT(from->length == 0); to->entry = 0; } else { FLAC__byte *x; FLAC__ASSERT(from->length > 0); if(0 == (x = (FLAC__byte*)safe_malloc_add_2op_(from->length, /*+*/1))) return false; memcpy(x, from->entry, from->length); x[from->length] = '\0'; to->entry = x; } return true; } static FLAC__bool copy_track_(FLAC__StreamMetadata_CueSheet_Track *to, const FLAC__StreamMetadata_CueSheet_Track *from) { memcpy(to, from, sizeof(FLAC__StreamMetadata_CueSheet_Track)); if(0 == from->indices) { FLAC__ASSERT(from->num_indices == 0); } else { FLAC__StreamMetadata_CueSheet_Index *x; FLAC__ASSERT(from->num_indices > 0); if(0 == (x = (FLAC__StreamMetadata_CueSheet_Index*)safe_malloc_mul_2op_(from->num_indices, /*times*/sizeof(FLAC__StreamMetadata_CueSheet_Index)))) return false; memcpy(x, from->indices, from->num_indices * sizeof(FLAC__StreamMetadata_CueSheet_Index)); to->indices = x; } return true; } static void seektable_calculate_length_(FLAC__StreamMetadata *object) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); object->length = object->data.seek_table.num_points * FLAC__STREAM_METADATA_SEEKPOINT_LENGTH; } static FLAC__StreamMetadata_SeekPoint *seekpoint_array_new_(unsigned num_points) { FLAC__StreamMetadata_SeekPoint *object_array; FLAC__ASSERT(num_points > 0); object_array = (FLAC__StreamMetadata_SeekPoint*)safe_malloc_mul_2op_(num_points, /*times*/sizeof(FLAC__StreamMetadata_SeekPoint)); if(0 != object_array) { unsigned i; for(i = 0; i < num_points; i++) { object_array[i].sample_number = FLAC__STREAM_METADATA_SEEKPOINT_PLACEHOLDER; object_array[i].stream_offset = 0; object_array[i].frame_samples = 0; } } return object_array; } static void vorbiscomment_calculate_length_(FLAC__StreamMetadata *object) { unsigned i; FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT); object->length = (FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN) / 8; object->length += object->data.vorbis_comment.vendor_string.length; object->length += (FLAC__STREAM_METADATA_VORBIS_COMMENT_NUM_COMMENTS_LEN) / 8; for(i = 0; i < object->data.vorbis_comment.num_comments; i++) { object->length += (FLAC__STREAM_METADATA_VORBIS_COMMENT_ENTRY_LENGTH_LEN / 8); object->length += object->data.vorbis_comment.comments[i].length; } } static FLAC__StreamMetadata_VorbisComment_Entry *vorbiscomment_entry_array_new_(unsigned num_comments) { FLAC__ASSERT(num_comments > 0); return (FLAC__StreamMetadata_VorbisComment_Entry*)safe_calloc_(num_comments, sizeof(FLAC__StreamMetadata_VorbisComment_Entry)); } static void vorbiscomment_entry_array_delete_(FLAC__StreamMetadata_VorbisComment_Entry *object_array, unsigned num_comments) { unsigned i; FLAC__ASSERT(0 != object_array && num_comments > 0); for(i = 0; i < num_comments; i++) if(0 != object_array[i].entry) free(object_array[i].entry); if(0 != object_array) free(object_array); } static FLAC__StreamMetadata_VorbisComment_Entry *vorbiscomment_entry_array_copy_(const FLAC__StreamMetadata_VorbisComment_Entry *object_array, unsigned num_comments) { FLAC__StreamMetadata_VorbisComment_Entry *return_array; FLAC__ASSERT(0 != object_array); FLAC__ASSERT(num_comments > 0); return_array = vorbiscomment_entry_array_new_(num_comments); if(0 != return_array) { unsigned i; for(i = 0; i < num_comments; i++) { if(!copy_vcentry_(return_array+i, object_array+i)) { vorbiscomment_entry_array_delete_(return_array, num_comments); return 0; } } } return return_array; } static FLAC__bool vorbiscomment_set_entry_(FLAC__StreamMetadata *object, FLAC__StreamMetadata_VorbisComment_Entry *dest, const FLAC__StreamMetadata_VorbisComment_Entry *src, FLAC__bool copy) { FLAC__byte *save; FLAC__ASSERT(0 != object); FLAC__ASSERT(0 != dest); FLAC__ASSERT(0 != src); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT); FLAC__ASSERT((0 != src->entry && src->length > 0) || (0 == src->entry && src->length == 0)); save = dest->entry; if(0 != src->entry && src->length > 0) { if(copy) { /* do the copy first so that if we fail we leave the dest object untouched */ if(!copy_vcentry_(dest, src)) return false; } else { /* we have to make sure that the string we're taking over is null-terminated */ /* * Stripping the const from src->entry is OK since we're taking * ownership of the pointer. This is a hack around a deficiency * in the API where the same function is used for 'copy' and * 'own', but the source entry is a const pointer. If we were * precise, the 'own' flavor would be a separate function with a * non-const source pointer. But it's not, so we hack away. */ if(!ensure_null_terminated_((FLAC__byte**)(&src->entry), src->length)) return false; *dest = *src; } } else { /* the src is null */ *dest = *src; } if(0 != save) free(save); vorbiscomment_calculate_length_(object); return true; } static int vorbiscomment_find_entry_from_(const FLAC__StreamMetadata *object, unsigned offset, const char *field_name, unsigned field_name_length) { unsigned i; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT); FLAC__ASSERT(0 != field_name); for(i = offset; i < object->data.vorbis_comment.num_comments; i++) { if(FLAC__metadata_object_vorbiscomment_entry_matches(object->data.vorbis_comment.comments[i], field_name, field_name_length)) return (int)i; } return -1; } static void cuesheet_calculate_length_(FLAC__StreamMetadata *object) { unsigned i; FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); object->length = ( FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN + FLAC__STREAM_METADATA_CUESHEET_LEAD_IN_LEN + FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN + FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN + FLAC__STREAM_METADATA_CUESHEET_NUM_TRACKS_LEN ) / 8; object->length += object->data.cue_sheet.num_tracks * ( FLAC__STREAM_METADATA_CUESHEET_TRACK_OFFSET_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_NUMBER_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN + FLAC__STREAM_METADATA_CUESHEET_TRACK_NUM_INDICES_LEN ) / 8; for(i = 0; i < object->data.cue_sheet.num_tracks; i++) { object->length += object->data.cue_sheet.tracks[i].num_indices * ( FLAC__STREAM_METADATA_CUESHEET_INDEX_OFFSET_LEN + FLAC__STREAM_METADATA_CUESHEET_INDEX_NUMBER_LEN + FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN ) / 8; } } static FLAC__StreamMetadata_CueSheet_Index *cuesheet_track_index_array_new_(unsigned num_indices) { FLAC__ASSERT(num_indices > 0); return (FLAC__StreamMetadata_CueSheet_Index*)safe_calloc_(num_indices, sizeof(FLAC__StreamMetadata_CueSheet_Index)); } static FLAC__StreamMetadata_CueSheet_Track *cuesheet_track_array_new_(unsigned num_tracks) { FLAC__ASSERT(num_tracks > 0); return (FLAC__StreamMetadata_CueSheet_Track*)safe_calloc_(num_tracks, sizeof(FLAC__StreamMetadata_CueSheet_Track)); } static void cuesheet_track_array_delete_(FLAC__StreamMetadata_CueSheet_Track *object_array, unsigned num_tracks) { unsigned i; FLAC__ASSERT(0 != object_array && num_tracks > 0); for(i = 0; i < num_tracks; i++) { if(0 != object_array[i].indices) { FLAC__ASSERT(object_array[i].num_indices > 0); free(object_array[i].indices); } } if(0 != object_array) free(object_array); } static FLAC__StreamMetadata_CueSheet_Track *cuesheet_track_array_copy_(const FLAC__StreamMetadata_CueSheet_Track *object_array, unsigned num_tracks) { FLAC__StreamMetadata_CueSheet_Track *return_array; FLAC__ASSERT(0 != object_array); FLAC__ASSERT(num_tracks > 0); return_array = cuesheet_track_array_new_(num_tracks); if(0 != return_array) { unsigned i; for(i = 0; i < num_tracks; i++) { if(!copy_track_(return_array+i, object_array+i)) { cuesheet_track_array_delete_(return_array, num_tracks); return 0; } } } return return_array; } static FLAC__bool cuesheet_set_track_(FLAC__StreamMetadata *object, FLAC__StreamMetadata_CueSheet_Track *dest, const FLAC__StreamMetadata_CueSheet_Track *src, FLAC__bool copy) { FLAC__StreamMetadata_CueSheet_Index *save; FLAC__ASSERT(0 != object); FLAC__ASSERT(0 != dest); FLAC__ASSERT(0 != src); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); FLAC__ASSERT((0 != src->indices && src->num_indices > 0) || (0 == src->indices && src->num_indices == 0)); save = dest->indices; /* do the copy first so that if we fail we leave the object untouched */ if(copy) { if(!copy_track_(dest, src)) return false; } else { *dest = *src; } if(0 != save) free(save); cuesheet_calculate_length_(object); return true; } /**************************************************************************** * * Metadata object routines * ***************************************************************************/ FLAC_API FLAC__StreamMetadata *FLAC__metadata_object_new(FLAC__MetadataType type) { FLAC__StreamMetadata *object; if(type > FLAC__MAX_METADATA_TYPE_CODE) return 0; object = (FLAC__StreamMetadata*)calloc(1, sizeof(FLAC__StreamMetadata)); if(0 != object) { object->is_last = false; object->type = type; switch(type) { case FLAC__METADATA_TYPE_STREAMINFO: object->length = FLAC__STREAM_METADATA_STREAMINFO_LENGTH; break; case FLAC__METADATA_TYPE_PADDING: /* calloc() took care of this for us: object->length = 0; */ break; case FLAC__METADATA_TYPE_APPLICATION: object->length = FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8; /* calloc() took care of this for us: object->data.application.data = 0; */ break; case FLAC__METADATA_TYPE_SEEKTABLE: /* calloc() took care of this for us: object->length = 0; object->data.seek_table.num_points = 0; object->data.seek_table.points = 0; */ break; case FLAC__METADATA_TYPE_VORBIS_COMMENT: object->data.vorbis_comment.vendor_string.length = (unsigned)strlen(FLAC__VENDOR_STRING); if(!copy_bytes_(&object->data.vorbis_comment.vendor_string.entry, (const FLAC__byte*)FLAC__VENDOR_STRING, object->data.vorbis_comment.vendor_string.length+1)) { free(object); return 0; } vorbiscomment_calculate_length_(object); break; case FLAC__METADATA_TYPE_CUESHEET: cuesheet_calculate_length_(object); break; case FLAC__METADATA_TYPE_PICTURE: object->length = ( FLAC__STREAM_METADATA_PICTURE_TYPE_LEN + FLAC__STREAM_METADATA_PICTURE_MIME_TYPE_LENGTH_LEN + /* empty mime_type string */ FLAC__STREAM_METADATA_PICTURE_DESCRIPTION_LENGTH_LEN + /* empty description string */ FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN + FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN + FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN + FLAC__STREAM_METADATA_PICTURE_COLORS_LEN + FLAC__STREAM_METADATA_PICTURE_DATA_LENGTH_LEN + 0 /* no data */ ) / 8; object->data.picture.type = FLAC__STREAM_METADATA_PICTURE_TYPE_OTHER; object->data.picture.mime_type = 0; object->data.picture.description = 0; /* calloc() took care of this for us: object->data.picture.width = 0; object->data.picture.height = 0; object->data.picture.depth = 0; object->data.picture.colors = 0; object->data.picture.data_length = 0; object->data.picture.data = 0; */ /* now initialize mime_type and description with empty strings to make things easier on the client */ if(!copy_cstring_(&object->data.picture.mime_type, "")) { free(object); return 0; } if(!copy_cstring_((char**)(&object->data.picture.description), "")) { if(object->data.picture.mime_type) free(object->data.picture.mime_type); free(object); return 0; } break; default: /* calloc() took care of this for us: object->length = 0; object->data.unknown.data = 0; */ break; } } return object; } FLAC_API FLAC__StreamMetadata *FLAC__metadata_object_clone(const FLAC__StreamMetadata *object) { FLAC__StreamMetadata *to; FLAC__ASSERT(0 != object); if(0 != (to = FLAC__metadata_object_new(object->type))) { to->is_last = object->is_last; to->type = object->type; to->length = object->length; switch(to->type) { case FLAC__METADATA_TYPE_STREAMINFO: memcpy(&to->data.stream_info, &object->data.stream_info, sizeof(FLAC__StreamMetadata_StreamInfo)); break; case FLAC__METADATA_TYPE_PADDING: break; case FLAC__METADATA_TYPE_APPLICATION: if(to->length < FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8) { /* underflow check */ FLAC__metadata_object_delete(to); return 0; } memcpy(&to->data.application.id, &object->data.application.id, FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8); if(!copy_bytes_(&to->data.application.data, object->data.application.data, object->length - FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8)) { FLAC__metadata_object_delete(to); return 0; } break; case FLAC__METADATA_TYPE_SEEKTABLE: to->data.seek_table.num_points = object->data.seek_table.num_points; if(to->data.seek_table.num_points > SIZE_MAX / sizeof(FLAC__StreamMetadata_SeekPoint)) { /* overflow check */ FLAC__metadata_object_delete(to); return 0; } if(!copy_bytes_((FLAC__byte**)&to->data.seek_table.points, (FLAC__byte*)object->data.seek_table.points, object->data.seek_table.num_points * sizeof(FLAC__StreamMetadata_SeekPoint))) { FLAC__metadata_object_delete(to); return 0; } break; case FLAC__METADATA_TYPE_VORBIS_COMMENT: if(0 != to->data.vorbis_comment.vendor_string.entry) { free(to->data.vorbis_comment.vendor_string.entry); to->data.vorbis_comment.vendor_string.entry = 0; } if(!copy_vcentry_(&to->data.vorbis_comment.vendor_string, &object->data.vorbis_comment.vendor_string)) { FLAC__metadata_object_delete(to); return 0; } if(object->data.vorbis_comment.num_comments == 0) { FLAC__ASSERT(0 == object->data.vorbis_comment.comments); to->data.vorbis_comment.comments = 0; } else { FLAC__ASSERT(0 != object->data.vorbis_comment.comments); to->data.vorbis_comment.comments = vorbiscomment_entry_array_copy_(object->data.vorbis_comment.comments, object->data.vorbis_comment.num_comments); if(0 == to->data.vorbis_comment.comments) { FLAC__metadata_object_delete(to); return 0; } } to->data.vorbis_comment.num_comments = object->data.vorbis_comment.num_comments; break; case FLAC__METADATA_TYPE_CUESHEET: memcpy(&to->data.cue_sheet, &object->data.cue_sheet, sizeof(FLAC__StreamMetadata_CueSheet)); if(object->data.cue_sheet.num_tracks == 0) { FLAC__ASSERT(0 == object->data.cue_sheet.tracks); } else { FLAC__ASSERT(0 != object->data.cue_sheet.tracks); to->data.cue_sheet.tracks = cuesheet_track_array_copy_(object->data.cue_sheet.tracks, object->data.cue_sheet.num_tracks); if(0 == to->data.cue_sheet.tracks) { FLAC__metadata_object_delete(to); return 0; } } break; case FLAC__METADATA_TYPE_PICTURE: to->data.picture.type = object->data.picture.type; if(!copy_cstring_(&to->data.picture.mime_type, object->data.picture.mime_type)) { FLAC__metadata_object_delete(to); return 0; } if(!copy_cstring_((char**)(&to->data.picture.description), (const char*)object->data.picture.description)) { FLAC__metadata_object_delete(to); return 0; } to->data.picture.width = object->data.picture.width; to->data.picture.height = object->data.picture.height; to->data.picture.depth = object->data.picture.depth; to->data.picture.colors = object->data.picture.colors; to->data.picture.data_length = object->data.picture.data_length; if(!copy_bytes_((&to->data.picture.data), object->data.picture.data, object->data.picture.data_length)) { FLAC__metadata_object_delete(to); return 0; } break; default: if(!copy_bytes_(&to->data.unknown.data, object->data.unknown.data, object->length)) { FLAC__metadata_object_delete(to); return 0; } break; } } return to; } void FLAC__metadata_object_delete_data(FLAC__StreamMetadata *object) { FLAC__ASSERT(0 != object); switch(object->type) { case FLAC__METADATA_TYPE_STREAMINFO: case FLAC__METADATA_TYPE_PADDING: break; case FLAC__METADATA_TYPE_APPLICATION: if(0 != object->data.application.data) { free(object->data.application.data); object->data.application.data = 0; } break; case FLAC__METADATA_TYPE_SEEKTABLE: if(0 != object->data.seek_table.points) { free(object->data.seek_table.points); object->data.seek_table.points = 0; } break; case FLAC__METADATA_TYPE_VORBIS_COMMENT: if(0 != object->data.vorbis_comment.vendor_string.entry) { free(object->data.vorbis_comment.vendor_string.entry); object->data.vorbis_comment.vendor_string.entry = 0; } if(0 != object->data.vorbis_comment.comments) { FLAC__ASSERT(object->data.vorbis_comment.num_comments > 0); vorbiscomment_entry_array_delete_(object->data.vorbis_comment.comments, object->data.vorbis_comment.num_comments); } break; case FLAC__METADATA_TYPE_CUESHEET: if(0 != object->data.cue_sheet.tracks) { FLAC__ASSERT(object->data.cue_sheet.num_tracks > 0); cuesheet_track_array_delete_(object->data.cue_sheet.tracks, object->data.cue_sheet.num_tracks); } break; case FLAC__METADATA_TYPE_PICTURE: if(0 != object->data.picture.mime_type) { free(object->data.picture.mime_type); object->data.picture.mime_type = 0; } if(0 != object->data.picture.description) { free(object->data.picture.description); object->data.picture.description = 0; } if(0 != object->data.picture.data) { free(object->data.picture.data); object->data.picture.data = 0; } break; default: if(0 != object->data.unknown.data) { free(object->data.unknown.data); object->data.unknown.data = 0; } break; } } FLAC_API void FLAC__metadata_object_delete(FLAC__StreamMetadata *object) { FLAC__metadata_object_delete_data(object); free(object); } static FLAC__bool compare_block_data_streaminfo_(const FLAC__StreamMetadata_StreamInfo *block1, const FLAC__StreamMetadata_StreamInfo *block2) { if(block1->min_blocksize != block2->min_blocksize) return false; if(block1->max_blocksize != block2->max_blocksize) return false; if(block1->min_framesize != block2->min_framesize) return false; if(block1->max_framesize != block2->max_framesize) return false; if(block1->sample_rate != block2->sample_rate) return false; if(block1->channels != block2->channels) return false; if(block1->bits_per_sample != block2->bits_per_sample) return false; if(block1->total_samples != block2->total_samples) return false; if(0 != memcmp(block1->md5sum, block2->md5sum, 16)) return false; return true; } static FLAC__bool compare_block_data_application_(const FLAC__StreamMetadata_Application *block1, const FLAC__StreamMetadata_Application *block2, unsigned block_length) { FLAC__ASSERT(0 != block1); FLAC__ASSERT(0 != block2); FLAC__ASSERT(block_length >= sizeof(block1->id)); if(0 != memcmp(block1->id, block2->id, sizeof(block1->id))) return false; if(0 != block1->data && 0 != block2->data) return 0 == memcmp(block1->data, block2->data, block_length - sizeof(block1->id)); else return block1->data == block2->data; } static FLAC__bool compare_block_data_seektable_(const FLAC__StreamMetadata_SeekTable *block1, const FLAC__StreamMetadata_SeekTable *block2) { unsigned i; FLAC__ASSERT(0 != block1); FLAC__ASSERT(0 != block2); if(block1->num_points != block2->num_points) return false; if(0 != block1->points && 0 != block2->points) { for(i = 0; i < block1->num_points; i++) { if(block1->points[i].sample_number != block2->points[i].sample_number) return false; if(block1->points[i].stream_offset != block2->points[i].stream_offset) return false; if(block1->points[i].frame_samples != block2->points[i].frame_samples) return false; } return true; } else return block1->points == block2->points; } static FLAC__bool compare_block_data_vorbiscomment_(const FLAC__StreamMetadata_VorbisComment *block1, const FLAC__StreamMetadata_VorbisComment *block2) { unsigned i; if(block1->vendor_string.length != block2->vendor_string.length) return false; if(0 != block1->vendor_string.entry && 0 != block2->vendor_string.entry) { if(0 != memcmp(block1->vendor_string.entry, block2->vendor_string.entry, block1->vendor_string.length)) return false; } else if(block1->vendor_string.entry != block2->vendor_string.entry) return false; if(block1->num_comments != block2->num_comments) return false; for(i = 0; i < block1->num_comments; i++) { if(0 != block1->comments[i].entry && 0 != block2->comments[i].entry) { if(0 != memcmp(block1->comments[i].entry, block2->comments[i].entry, block1->comments[i].length)) return false; } else if(block1->comments[i].entry != block2->comments[i].entry) return false; } return true; } static FLAC__bool compare_block_data_cuesheet_(const FLAC__StreamMetadata_CueSheet *block1, const FLAC__StreamMetadata_CueSheet *block2) { unsigned i, j; if(0 != strcmp(block1->media_catalog_number, block2->media_catalog_number)) return false; if(block1->lead_in != block2->lead_in) return false; if(block1->is_cd != block2->is_cd) return false; if(block1->num_tracks != block2->num_tracks) return false; if(0 != block1->tracks && 0 != block2->tracks) { FLAC__ASSERT(block1->num_tracks > 0); for(i = 0; i < block1->num_tracks; i++) { if(block1->tracks[i].offset != block2->tracks[i].offset) return false; if(block1->tracks[i].number != block2->tracks[i].number) return false; if(0 != memcmp(block1->tracks[i].isrc, block2->tracks[i].isrc, sizeof(block1->tracks[i].isrc))) return false; if(block1->tracks[i].type != block2->tracks[i].type) return false; if(block1->tracks[i].pre_emphasis != block2->tracks[i].pre_emphasis) return false; if(block1->tracks[i].num_indices != block2->tracks[i].num_indices) return false; if(0 != block1->tracks[i].indices && 0 != block2->tracks[i].indices) { FLAC__ASSERT(block1->tracks[i].num_indices > 0); for(j = 0; j < block1->tracks[i].num_indices; j++) { if(block1->tracks[i].indices[j].offset != block2->tracks[i].indices[j].offset) return false; if(block1->tracks[i].indices[j].number != block2->tracks[i].indices[j].number) return false; } } else if(block1->tracks[i].indices != block2->tracks[i].indices) return false; } } else if(block1->tracks != block2->tracks) return false; return true; } static FLAC__bool compare_block_data_picture_(const FLAC__StreamMetadata_Picture *block1, const FLAC__StreamMetadata_Picture *block2) { if(block1->type != block2->type) return false; if(block1->mime_type != block2->mime_type && (0 == block1->mime_type || 0 == block2->mime_type || strcmp(block1->mime_type, block2->mime_type))) return false; if(block1->description != block2->description && (0 == block1->description || 0 == block2->description || strcmp((const char *)block1->description, (const char *)block2->description))) return false; if(block1->width != block2->width) return false; if(block1->height != block2->height) return false; if(block1->depth != block2->depth) return false; if(block1->colors != block2->colors) return false; if(block1->data_length != block2->data_length) return false; if(block1->data != block2->data && (0 == block1->data || 0 == block2->data || memcmp(block1->data, block2->data, block1->data_length))) return false; return true; } static FLAC__bool compare_block_data_unknown_(const FLAC__StreamMetadata_Unknown *block1, const FLAC__StreamMetadata_Unknown *block2, unsigned block_length) { FLAC__ASSERT(0 != block1); FLAC__ASSERT(0 != block2); if(0 != block1->data && 0 != block2->data) return 0 == memcmp(block1->data, block2->data, block_length); else return block1->data == block2->data; } FLAC_API FLAC__bool FLAC__metadata_object_is_equal(const FLAC__StreamMetadata *block1, const FLAC__StreamMetadata *block2) { FLAC__ASSERT(0 != block1); FLAC__ASSERT(0 != block2); if(block1->type != block2->type) { return false; } if(block1->is_last != block2->is_last) { return false; } if(block1->length != block2->length) { return false; } switch(block1->type) { case FLAC__METADATA_TYPE_STREAMINFO: return compare_block_data_streaminfo_(&block1->data.stream_info, &block2->data.stream_info); case FLAC__METADATA_TYPE_PADDING: return true; /* we don't compare the padding guts */ case FLAC__METADATA_TYPE_APPLICATION: return compare_block_data_application_(&block1->data.application, &block2->data.application, block1->length); case FLAC__METADATA_TYPE_SEEKTABLE: return compare_block_data_seektable_(&block1->data.seek_table, &block2->data.seek_table); case FLAC__METADATA_TYPE_VORBIS_COMMENT: return compare_block_data_vorbiscomment_(&block1->data.vorbis_comment, &block2->data.vorbis_comment); case FLAC__METADATA_TYPE_CUESHEET: return compare_block_data_cuesheet_(&block1->data.cue_sheet, &block2->data.cue_sheet); case FLAC__METADATA_TYPE_PICTURE: return compare_block_data_picture_(&block1->data.picture, &block2->data.picture); default: return compare_block_data_unknown_(&block1->data.unknown, &block2->data.unknown, block1->length); } } FLAC_API FLAC__bool FLAC__metadata_object_application_set_data(FLAC__StreamMetadata *object, FLAC__byte *data, unsigned length, FLAC__bool copy) { FLAC__byte *save; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_APPLICATION); FLAC__ASSERT((0 != data && length > 0) || (0 == data && length == 0 && copy == false)); save = object->data.application.data; /* do the copy first so that if we fail we leave the object untouched */ if(copy) { if(!copy_bytes_(&object->data.application.data, data, length)) return false; } else { object->data.application.data = data; } if(0 != save) free(save); object->length = FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8 + length; return true; } FLAC_API FLAC__bool FLAC__metadata_object_seektable_resize_points(FLAC__StreamMetadata *object, unsigned new_num_points) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); if(0 == object->data.seek_table.points) { FLAC__ASSERT(object->data.seek_table.num_points == 0); if(0 == new_num_points) return true; else if(0 == (object->data.seek_table.points = seekpoint_array_new_(new_num_points))) return false; } else { const size_t old_size = object->data.seek_table.num_points * sizeof(FLAC__StreamMetadata_SeekPoint); const size_t new_size = new_num_points * sizeof(FLAC__StreamMetadata_SeekPoint); /* overflow check */ if((size_t)new_num_points > SIZE_MAX / sizeof(FLAC__StreamMetadata_SeekPoint)) return false; FLAC__ASSERT(object->data.seek_table.num_points > 0); if(new_size == 0) { free(object->data.seek_table.points); object->data.seek_table.points = 0; } else if(0 == (object->data.seek_table.points = (FLAC__StreamMetadata_SeekPoint*)realloc(object->data.seek_table.points, new_size))) return false; /* if growing, set new elements to placeholders */ if(new_size > old_size) { unsigned i; for(i = object->data.seek_table.num_points; i < new_num_points; i++) { object->data.seek_table.points[i].sample_number = FLAC__STREAM_METADATA_SEEKPOINT_PLACEHOLDER; object->data.seek_table.points[i].stream_offset = 0; object->data.seek_table.points[i].frame_samples = 0; } } } object->data.seek_table.num_points = new_num_points; seektable_calculate_length_(object); return true; } FLAC_API void FLAC__metadata_object_seektable_set_point(FLAC__StreamMetadata *object, unsigned point_num, FLAC__StreamMetadata_SeekPoint point) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); FLAC__ASSERT(point_num < object->data.seek_table.num_points); object->data.seek_table.points[point_num] = point; } FLAC_API FLAC__bool FLAC__metadata_object_seektable_insert_point(FLAC__StreamMetadata *object, unsigned point_num, FLAC__StreamMetadata_SeekPoint point) { int i; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); FLAC__ASSERT(point_num <= object->data.seek_table.num_points); if(!FLAC__metadata_object_seektable_resize_points(object, object->data.seek_table.num_points+1)) return false; /* move all points >= point_num forward one space */ for(i = (int)object->data.seek_table.num_points-1; i > (int)point_num; i--) object->data.seek_table.points[i] = object->data.seek_table.points[i-1]; FLAC__metadata_object_seektable_set_point(object, point_num, point); seektable_calculate_length_(object); return true; } FLAC_API FLAC__bool FLAC__metadata_object_seektable_delete_point(FLAC__StreamMetadata *object, unsigned point_num) { unsigned i; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); FLAC__ASSERT(point_num < object->data.seek_table.num_points); /* move all points > point_num backward one space */ for(i = point_num; i < object->data.seek_table.num_points-1; i++) object->data.seek_table.points[i] = object->data.seek_table.points[i+1]; return FLAC__metadata_object_seektable_resize_points(object, object->data.seek_table.num_points-1); } FLAC_API FLAC__bool FLAC__metadata_object_seektable_is_legal(const FLAC__StreamMetadata *object) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); return FLAC__format_seektable_is_legal(&object->data.seek_table); } FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_placeholders(FLAC__StreamMetadata *object, unsigned num) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); if(num > 0) /* WATCHOUT: we rely on the fact that growing the array adds PLACEHOLDERS at the end */ return FLAC__metadata_object_seektable_resize_points(object, object->data.seek_table.num_points + num); else return true; } FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_point(FLAC__StreamMetadata *object, FLAC__uint64 sample_number) { FLAC__StreamMetadata_SeekTable *seek_table; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); seek_table = &object->data.seek_table; if(!FLAC__metadata_object_seektable_resize_points(object, seek_table->num_points + 1)) return false; seek_table->points[seek_table->num_points - 1].sample_number = sample_number; seek_table->points[seek_table->num_points - 1].stream_offset = 0; seek_table->points[seek_table->num_points - 1].frame_samples = 0; return true; } FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_points(FLAC__StreamMetadata *object, FLAC__uint64 sample_numbers[], unsigned num) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); FLAC__ASSERT(0 != sample_numbers || num == 0); if(num > 0) { FLAC__StreamMetadata_SeekTable *seek_table = &object->data.seek_table; unsigned i, j; i = seek_table->num_points; if(!FLAC__metadata_object_seektable_resize_points(object, seek_table->num_points + num)) return false; for(j = 0; j < num; i++, j++) { seek_table->points[i].sample_number = sample_numbers[j]; seek_table->points[i].stream_offset = 0; seek_table->points[i].frame_samples = 0; } } return true; } FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_spaced_points(FLAC__StreamMetadata *object, unsigned num, FLAC__uint64 total_samples) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); FLAC__ASSERT(total_samples > 0); if(num > 0 && total_samples > 0) { FLAC__StreamMetadata_SeekTable *seek_table = &object->data.seek_table; unsigned i, j; i = seek_table->num_points; if(!FLAC__metadata_object_seektable_resize_points(object, seek_table->num_points + num)) return false; for(j = 0; j < num; i++, j++) { seek_table->points[i].sample_number = total_samples * (FLAC__uint64)j / (FLAC__uint64)num; seek_table->points[i].stream_offset = 0; seek_table->points[i].frame_samples = 0; } } return true; } FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_append_spaced_points_by_samples(FLAC__StreamMetadata *object, unsigned samples, FLAC__uint64 total_samples) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); FLAC__ASSERT(samples > 0); FLAC__ASSERT(total_samples > 0); if(samples > 0 && total_samples > 0) { FLAC__StreamMetadata_SeekTable *seek_table = &object->data.seek_table; unsigned i, j; FLAC__uint64 num, sample; num = 1 + total_samples / samples; /* 1+ for the first sample at 0 */ /* now account for the fact that we don't place a seekpoint at "total_samples" since samples are number from 0: */ if(total_samples % samples == 0) num--; i = seek_table->num_points; if(!FLAC__metadata_object_seektable_resize_points(object, seek_table->num_points + (unsigned)num)) return false; sample = 0; for(j = 0; j < num; i++, j++, sample += samples) { seek_table->points[i].sample_number = sample; seek_table->points[i].stream_offset = 0; seek_table->points[i].frame_samples = 0; } } return true; } FLAC_API FLAC__bool FLAC__metadata_object_seektable_template_sort(FLAC__StreamMetadata *object, FLAC__bool compact) { unsigned unique; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_SEEKTABLE); unique = FLAC__format_seektable_sort(&object->data.seek_table); return !compact || FLAC__metadata_object_seektable_resize_points(object, unique); } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_set_vendor_string(FLAC__StreamMetadata *object, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool copy) { if(!FLAC__format_vorbiscomment_entry_value_is_legal(entry.entry, entry.length)) return false; return vorbiscomment_set_entry_(object, &object->data.vorbis_comment.vendor_string, &entry, copy); } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_resize_comments(FLAC__StreamMetadata *object, unsigned new_num_comments) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT); if(0 == object->data.vorbis_comment.comments) { FLAC__ASSERT(object->data.vorbis_comment.num_comments == 0); if(0 == new_num_comments) return true; else if(0 == (object->data.vorbis_comment.comments = vorbiscomment_entry_array_new_(new_num_comments))) return false; } else { const size_t old_size = object->data.vorbis_comment.num_comments * sizeof(FLAC__StreamMetadata_VorbisComment_Entry); const size_t new_size = new_num_comments * sizeof(FLAC__StreamMetadata_VorbisComment_Entry); /* overflow check */ if((size_t)new_num_comments > SIZE_MAX / sizeof(FLAC__StreamMetadata_VorbisComment_Entry)) return false; FLAC__ASSERT(object->data.vorbis_comment.num_comments > 0); /* if shrinking, free the truncated entries */ if(new_num_comments < object->data.vorbis_comment.num_comments) { unsigned i; for(i = new_num_comments; i < object->data.vorbis_comment.num_comments; i++) if(0 != object->data.vorbis_comment.comments[i].entry) free(object->data.vorbis_comment.comments[i].entry); } if(new_size == 0) { free(object->data.vorbis_comment.comments); object->data.vorbis_comment.comments = 0; } else if(0 == (object->data.vorbis_comment.comments = (FLAC__StreamMetadata_VorbisComment_Entry*)realloc(object->data.vorbis_comment.comments, new_size))) return false; /* if growing, zero all the length/pointers of new elements */ if(new_size > old_size) memset(object->data.vorbis_comment.comments + object->data.vorbis_comment.num_comments, 0, new_size - old_size); } object->data.vorbis_comment.num_comments = new_num_comments; vorbiscomment_calculate_length_(object); return true; } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_set_comment(FLAC__StreamMetadata *object, unsigned comment_num, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool copy) { FLAC__ASSERT(0 != object); FLAC__ASSERT(comment_num < object->data.vorbis_comment.num_comments); if(!FLAC__format_vorbiscomment_entry_is_legal(entry.entry, entry.length)) return false; return vorbiscomment_set_entry_(object, &object->data.vorbis_comment.comments[comment_num], &entry, copy); } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_insert_comment(FLAC__StreamMetadata *object, unsigned comment_num, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool copy) { FLAC__StreamMetadata_VorbisComment *vc; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT); FLAC__ASSERT(comment_num <= object->data.vorbis_comment.num_comments); if(!FLAC__format_vorbiscomment_entry_is_legal(entry.entry, entry.length)) return false; vc = &object->data.vorbis_comment; if(!FLAC__metadata_object_vorbiscomment_resize_comments(object, vc->num_comments+1)) return false; /* move all comments >= comment_num forward one space */ memmove(&vc->comments[comment_num+1], &vc->comments[comment_num], sizeof(FLAC__StreamMetadata_VorbisComment_Entry)*(vc->num_comments-1-comment_num)); vc->comments[comment_num].length = 0; vc->comments[comment_num].entry = 0; return FLAC__metadata_object_vorbiscomment_set_comment(object, comment_num, entry, copy); } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_append_comment(FLAC__StreamMetadata *object, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool copy) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT); return FLAC__metadata_object_vorbiscomment_insert_comment(object, object->data.vorbis_comment.num_comments, entry, copy); } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_replace_comment(FLAC__StreamMetadata *object, FLAC__StreamMetadata_VorbisComment_Entry entry, FLAC__bool all, FLAC__bool copy) { FLAC__ASSERT(0 != entry.entry && entry.length > 0); if(!FLAC__format_vorbiscomment_entry_is_legal(entry.entry, entry.length)) return false; { int i; size_t field_name_length; const FLAC__byte *eq = (FLAC__byte*)memchr(entry.entry, '=', entry.length); FLAC__ASSERT(0 != eq); if(0 == eq) return false; /* double protection */ field_name_length = eq-entry.entry; if((i = vorbiscomment_find_entry_from_(object, 0, (const char *)entry.entry, field_name_length)) >= 0) { unsigned index = (unsigned)i; if(!FLAC__metadata_object_vorbiscomment_set_comment(object, index, entry, copy)) return false; if(all && (index+1 < object->data.vorbis_comment.num_comments)) { for(i = vorbiscomment_find_entry_from_(object, index+1, (const char *)entry.entry, field_name_length); i >= 0; ) { if(!FLAC__metadata_object_vorbiscomment_delete_comment(object, (unsigned)i)) return false; if((unsigned)i < object->data.vorbis_comment.num_comments) i = vorbiscomment_find_entry_from_(object, (unsigned)i, (const char *)entry.entry, field_name_length); else i = -1; } } return true; } else return FLAC__metadata_object_vorbiscomment_append_comment(object, entry, copy); } } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_delete_comment(FLAC__StreamMetadata *object, unsigned comment_num) { FLAC__StreamMetadata_VorbisComment *vc; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT); FLAC__ASSERT(comment_num < object->data.vorbis_comment.num_comments); vc = &object->data.vorbis_comment; /* free the comment at comment_num */ if(0 != vc->comments[comment_num].entry) free(vc->comments[comment_num].entry); /* move all comments > comment_num backward one space */ memmove(&vc->comments[comment_num], &vc->comments[comment_num+1], sizeof(FLAC__StreamMetadata_VorbisComment_Entry)*(vc->num_comments-comment_num-1)); vc->comments[vc->num_comments-1].length = 0; vc->comments[vc->num_comments-1].entry = 0; return FLAC__metadata_object_vorbiscomment_resize_comments(object, vc->num_comments-1); } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_entry_from_name_value_pair(FLAC__StreamMetadata_VorbisComment_Entry *entry, const char *field_name, const char *field_value) { FLAC__ASSERT(0 != entry); FLAC__ASSERT(0 != field_name); FLAC__ASSERT(0 != field_value); if(!FLAC__format_vorbiscomment_entry_name_is_legal(field_name)) return false; if(!FLAC__format_vorbiscomment_entry_value_is_legal((const FLAC__byte *)field_value, (unsigned)(-1))) return false; { const size_t nn = strlen(field_name); const size_t nv = strlen(field_value); entry->length = nn + 1 /*=*/ + nv; if(0 == (entry->entry = (FLAC__byte*)safe_malloc_add_4op_(nn, /*+*/1, /*+*/nv, /*+*/1))) return false; memcpy(entry->entry, field_name, nn); entry->entry[nn] = '='; memcpy(entry->entry+nn+1, field_value, nv); entry->entry[entry->length] = '\0'; } return true; } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_entry_to_name_value_pair(const FLAC__StreamMetadata_VorbisComment_Entry entry, char **field_name, char **field_value) { FLAC__ASSERT(0 != entry.entry && entry.length > 0); FLAC__ASSERT(0 != field_name); FLAC__ASSERT(0 != field_value); if(!FLAC__format_vorbiscomment_entry_is_legal(entry.entry, entry.length)) return false; { const FLAC__byte *eq = (FLAC__byte*)memchr(entry.entry, '=', entry.length); const size_t nn = eq-entry.entry; const size_t nv = entry.length-nn-1; /* -1 for the '=' */ FLAC__ASSERT(0 != eq); if(0 == eq) return false; /* double protection */ if(0 == (*field_name = (char*)safe_malloc_add_2op_(nn, /*+*/1))) return false; if(0 == (*field_value = (char*)safe_malloc_add_2op_(nv, /*+*/1))) { free(*field_name); return false; } memcpy(*field_name, entry.entry, nn); memcpy(*field_value, entry.entry+nn+1, nv); (*field_name)[nn] = '\0'; (*field_value)[nv] = '\0'; } return true; } FLAC_API FLAC__bool FLAC__metadata_object_vorbiscomment_entry_matches(const FLAC__StreamMetadata_VorbisComment_Entry entry, const char *field_name, unsigned field_name_length) { FLAC__ASSERT(0 != entry.entry && entry.length > 0); { const FLAC__byte *eq = (FLAC__byte*)memchr(entry.entry, '=', entry.length); #if defined _MSC_VER || defined __BORLANDC__ || defined __MINGW32__ || defined __EMX__ #define FLAC__STRNCASECMP strnicmp #else #define FLAC__STRNCASECMP strncasecmp #endif return (0 != eq && (unsigned)(eq-entry.entry) == field_name_length && 0 == FLAC__STRNCASECMP(field_name, (const char *)entry.entry, field_name_length)); #undef FLAC__STRNCASECMP } } FLAC_API int FLAC__metadata_object_vorbiscomment_find_entry_from(const FLAC__StreamMetadata *object, unsigned offset, const char *field_name) { FLAC__ASSERT(0 != field_name); return vorbiscomment_find_entry_from_(object, offset, field_name, strlen(field_name)); } FLAC_API int FLAC__metadata_object_vorbiscomment_remove_entry_matching(FLAC__StreamMetadata *object, const char *field_name) { const unsigned field_name_length = strlen(field_name); unsigned i; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT); for(i = 0; i < object->data.vorbis_comment.num_comments; i++) { if(FLAC__metadata_object_vorbiscomment_entry_matches(object->data.vorbis_comment.comments[i], field_name, field_name_length)) { if(!FLAC__metadata_object_vorbiscomment_delete_comment(object, i)) return -1; else return 1; } } return 0; } FLAC_API int FLAC__metadata_object_vorbiscomment_remove_entries_matching(FLAC__StreamMetadata *object, const char *field_name) { FLAC__bool ok = true; unsigned matching = 0; const unsigned field_name_length = strlen(field_name); int i; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_VORBIS_COMMENT); /* must delete from end to start otherwise it will interfere with our iteration */ for(i = (int)object->data.vorbis_comment.num_comments - 1; ok && i >= 0; i--) { if(FLAC__metadata_object_vorbiscomment_entry_matches(object->data.vorbis_comment.comments[i], field_name, field_name_length)) { matching++; ok &= FLAC__metadata_object_vorbiscomment_delete_comment(object, (unsigned)i); } } return ok? (int)matching : -1; } FLAC_API FLAC__StreamMetadata_CueSheet_Track *FLAC__metadata_object_cuesheet_track_new(void) { return (FLAC__StreamMetadata_CueSheet_Track*)calloc(1, sizeof(FLAC__StreamMetadata_CueSheet_Track)); } FLAC_API FLAC__StreamMetadata_CueSheet_Track *FLAC__metadata_object_cuesheet_track_clone(const FLAC__StreamMetadata_CueSheet_Track *object) { FLAC__StreamMetadata_CueSheet_Track *to; FLAC__ASSERT(0 != object); if(0 != (to = FLAC__metadata_object_cuesheet_track_new())) { if(!copy_track_(to, object)) { FLAC__metadata_object_cuesheet_track_delete(to); return 0; } } return to; } void FLAC__metadata_object_cuesheet_track_delete_data(FLAC__StreamMetadata_CueSheet_Track *object) { FLAC__ASSERT(0 != object); if(0 != object->indices) { FLAC__ASSERT(object->num_indices > 0); free(object->indices); } } FLAC_API void FLAC__metadata_object_cuesheet_track_delete(FLAC__StreamMetadata_CueSheet_Track *object) { FLAC__metadata_object_cuesheet_track_delete_data(object); free(object); } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_track_resize_indices(FLAC__StreamMetadata *object, unsigned track_num, unsigned new_num_indices) { FLAC__StreamMetadata_CueSheet_Track *track; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); FLAC__ASSERT(track_num < object->data.cue_sheet.num_tracks); track = &object->data.cue_sheet.tracks[track_num]; if(0 == track->indices) { FLAC__ASSERT(track->num_indices == 0); if(0 == new_num_indices) return true; else if(0 == (track->indices = cuesheet_track_index_array_new_(new_num_indices))) return false; } else { const size_t old_size = track->num_indices * sizeof(FLAC__StreamMetadata_CueSheet_Index); const size_t new_size = new_num_indices * sizeof(FLAC__StreamMetadata_CueSheet_Index); /* overflow check */ if((size_t)new_num_indices > SIZE_MAX / sizeof(FLAC__StreamMetadata_CueSheet_Index)) return false; FLAC__ASSERT(track->num_indices > 0); if(new_size == 0) { free(track->indices); track->indices = 0; } else if(0 == (track->indices = (FLAC__StreamMetadata_CueSheet_Index*)realloc(track->indices, new_size))) return false; /* if growing, zero all the lengths/pointers of new elements */ if(new_size > old_size) memset(track->indices + track->num_indices, 0, new_size - old_size); } track->num_indices = new_num_indices; cuesheet_calculate_length_(object); return true; } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_track_insert_index(FLAC__StreamMetadata *object, unsigned track_num, unsigned index_num, FLAC__StreamMetadata_CueSheet_Index index) { FLAC__StreamMetadata_CueSheet_Track *track; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); FLAC__ASSERT(track_num < object->data.cue_sheet.num_tracks); FLAC__ASSERT(index_num <= object->data.cue_sheet.tracks[track_num].num_indices); track = &object->data.cue_sheet.tracks[track_num]; if(!FLAC__metadata_object_cuesheet_track_resize_indices(object, track_num, track->num_indices+1)) return false; /* move all indices >= index_num forward one space */ memmove(&track->indices[index_num+1], &track->indices[index_num], sizeof(FLAC__StreamMetadata_CueSheet_Index)*(track->num_indices-1-index_num)); track->indices[index_num] = index; cuesheet_calculate_length_(object); return true; } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_track_insert_blank_index(FLAC__StreamMetadata *object, unsigned track_num, unsigned index_num) { FLAC__StreamMetadata_CueSheet_Index index; memset(&index, 0, sizeof(index)); return FLAC__metadata_object_cuesheet_track_insert_index(object, track_num, index_num, index); } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_track_delete_index(FLAC__StreamMetadata *object, unsigned track_num, unsigned index_num) { FLAC__StreamMetadata_CueSheet_Track *track; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); FLAC__ASSERT(track_num < object->data.cue_sheet.num_tracks); FLAC__ASSERT(index_num < object->data.cue_sheet.tracks[track_num].num_indices); track = &object->data.cue_sheet.tracks[track_num]; /* move all indices > index_num backward one space */ memmove(&track->indices[index_num], &track->indices[index_num+1], sizeof(FLAC__StreamMetadata_CueSheet_Index)*(track->num_indices-index_num-1)); FLAC__metadata_object_cuesheet_track_resize_indices(object, track_num, track->num_indices-1); cuesheet_calculate_length_(object); return true; } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_resize_tracks(FLAC__StreamMetadata *object, unsigned new_num_tracks) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); if(0 == object->data.cue_sheet.tracks) { FLAC__ASSERT(object->data.cue_sheet.num_tracks == 0); if(0 == new_num_tracks) return true; else if(0 == (object->data.cue_sheet.tracks = cuesheet_track_array_new_(new_num_tracks))) return false; } else { const size_t old_size = object->data.cue_sheet.num_tracks * sizeof(FLAC__StreamMetadata_CueSheet_Track); const size_t new_size = new_num_tracks * sizeof(FLAC__StreamMetadata_CueSheet_Track); /* overflow check */ if((size_t)new_num_tracks > SIZE_MAX / sizeof(FLAC__StreamMetadata_CueSheet_Track)) return false; FLAC__ASSERT(object->data.cue_sheet.num_tracks > 0); /* if shrinking, free the truncated entries */ if(new_num_tracks < object->data.cue_sheet.num_tracks) { unsigned i; for(i = new_num_tracks; i < object->data.cue_sheet.num_tracks; i++) if(0 != object->data.cue_sheet.tracks[i].indices) free(object->data.cue_sheet.tracks[i].indices); } if(new_size == 0) { free(object->data.cue_sheet.tracks); object->data.cue_sheet.tracks = 0; } else if(0 == (object->data.cue_sheet.tracks = (FLAC__StreamMetadata_CueSheet_Track*)realloc(object->data.cue_sheet.tracks, new_size))) return false; /* if growing, zero all the lengths/pointers of new elements */ if(new_size > old_size) memset(object->data.cue_sheet.tracks + object->data.cue_sheet.num_tracks, 0, new_size - old_size); } object->data.cue_sheet.num_tracks = new_num_tracks; cuesheet_calculate_length_(object); return true; } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_set_track(FLAC__StreamMetadata *object, unsigned track_num, FLAC__StreamMetadata_CueSheet_Track *track, FLAC__bool copy) { FLAC__ASSERT(0 != object); FLAC__ASSERT(track_num < object->data.cue_sheet.num_tracks); return cuesheet_set_track_(object, object->data.cue_sheet.tracks + track_num, track, copy); } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_insert_track(FLAC__StreamMetadata *object, unsigned track_num, FLAC__StreamMetadata_CueSheet_Track *track, FLAC__bool copy) { FLAC__StreamMetadata_CueSheet *cs; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); FLAC__ASSERT(track_num <= object->data.cue_sheet.num_tracks); cs = &object->data.cue_sheet; if(!FLAC__metadata_object_cuesheet_resize_tracks(object, cs->num_tracks+1)) return false; /* move all tracks >= track_num forward one space */ memmove(&cs->tracks[track_num+1], &cs->tracks[track_num], sizeof(FLAC__StreamMetadata_CueSheet_Track)*(cs->num_tracks-1-track_num)); cs->tracks[track_num].num_indices = 0; cs->tracks[track_num].indices = 0; return FLAC__metadata_object_cuesheet_set_track(object, track_num, track, copy); } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_insert_blank_track(FLAC__StreamMetadata *object, unsigned track_num) { FLAC__StreamMetadata_CueSheet_Track track; memset(&track, 0, sizeof(track)); return FLAC__metadata_object_cuesheet_insert_track(object, track_num, &track, /*copy=*/false); } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_delete_track(FLAC__StreamMetadata *object, unsigned track_num) { FLAC__StreamMetadata_CueSheet *cs; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); FLAC__ASSERT(track_num < object->data.cue_sheet.num_tracks); cs = &object->data.cue_sheet; /* free the track at track_num */ if(0 != cs->tracks[track_num].indices) free(cs->tracks[track_num].indices); /* move all tracks > track_num backward one space */ memmove(&cs->tracks[track_num], &cs->tracks[track_num+1], sizeof(FLAC__StreamMetadata_CueSheet_Track)*(cs->num_tracks-track_num-1)); cs->tracks[cs->num_tracks-1].num_indices = 0; cs->tracks[cs->num_tracks-1].indices = 0; return FLAC__metadata_object_cuesheet_resize_tracks(object, cs->num_tracks-1); } FLAC_API FLAC__bool FLAC__metadata_object_cuesheet_is_legal(const FLAC__StreamMetadata *object, FLAC__bool check_cd_da_subset, const char **violation) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); return FLAC__format_cuesheet_is_legal(&object->data.cue_sheet, check_cd_da_subset, violation); } static FLAC__uint64 get_index_01_offset_(const FLAC__StreamMetadata_CueSheet *cs, unsigned track) { if (track >= (cs->num_tracks-1) || cs->tracks[track].num_indices < 1) return 0; else if (cs->tracks[track].indices[0].number == 1) return cs->tracks[track].indices[0].offset + cs->tracks[track].offset + cs->lead_in; else if (cs->tracks[track].num_indices < 2) return 0; else if (cs->tracks[track].indices[1].number == 1) return cs->tracks[track].indices[1].offset + cs->tracks[track].offset + cs->lead_in; else return 0; } static FLAC__uint32 cddb_add_digits_(FLAC__uint32 x) { FLAC__uint32 n = 0; while (x) { n += (x%10); x /= 10; } return n; } /*@@@@add to tests*/ FLAC_API FLAC__uint32 FLAC__metadata_object_cuesheet_calculate_cddb_id(const FLAC__StreamMetadata *object) { const FLAC__StreamMetadata_CueSheet *cs; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_CUESHEET); cs = &object->data.cue_sheet; if (cs->num_tracks < 2) /* need at least one real track and the lead-out track */ return 0; { FLAC__uint32 i, length, sum = 0; for (i = 0; i < (cs->num_tracks-1); i++) /* -1 to avoid counting the lead-out */ sum += cddb_add_digits_((FLAC__uint32)(get_index_01_offset_(cs, i) / 44100)); length = (FLAC__uint32)((cs->tracks[cs->num_tracks-1].offset+cs->lead_in) / 44100) - (FLAC__uint32)(get_index_01_offset_(cs, 0) / 44100); return (sum % 0xFF) << 24 | length << 8 | (FLAC__uint32)(cs->num_tracks-1); } } FLAC_API FLAC__bool FLAC__metadata_object_picture_set_mime_type(FLAC__StreamMetadata *object, char *mime_type, FLAC__bool copy) { char *old; size_t old_length, new_length; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_PICTURE); FLAC__ASSERT(0 != mime_type); old = object->data.picture.mime_type; old_length = old? strlen(old) : 0; new_length = strlen(mime_type); /* do the copy first so that if we fail we leave the object untouched */ if(copy) { if(new_length >= SIZE_MAX) /* overflow check */ return false; if(!copy_bytes_((FLAC__byte**)(&object->data.picture.mime_type), (FLAC__byte*)mime_type, new_length+1)) return false; } else { object->data.picture.mime_type = mime_type; } if(0 != old) free(old); object->length -= old_length; object->length += new_length; return true; } FLAC_API FLAC__bool FLAC__metadata_object_picture_set_description(FLAC__StreamMetadata *object, FLAC__byte *description, FLAC__bool copy) { FLAC__byte *old; size_t old_length, new_length; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_PICTURE); FLAC__ASSERT(0 != description); old = object->data.picture.description; old_length = old? strlen((const char *)old) : 0; new_length = strlen((const char *)description); /* do the copy first so that if we fail we leave the object untouched */ if(copy) { if(new_length >= SIZE_MAX) /* overflow check */ return false; if(!copy_bytes_(&object->data.picture.description, description, new_length+1)) return false; } else { object->data.picture.description = description; } if(0 != old) free(old); object->length -= old_length; object->length += new_length; return true; } FLAC_API FLAC__bool FLAC__metadata_object_picture_set_data(FLAC__StreamMetadata *object, FLAC__byte *data, FLAC__uint32 length, FLAC__bool copy) { FLAC__byte *old; FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_PICTURE); FLAC__ASSERT((0 != data && length > 0) || (0 == data && length == 0 && copy == false)); old = object->data.picture.data; /* do the copy first so that if we fail we leave the object untouched */ if(copy) { if(!copy_bytes_(&object->data.picture.data, data, length)) return false; } else { object->data.picture.data = data; } if(0 != old) free(old); object->length -= object->data.picture.data_length; object->data.picture.data_length = length; object->length += length; return true; } FLAC_API FLAC__bool FLAC__metadata_object_picture_is_legal(const FLAC__StreamMetadata *object, const char **violation) { FLAC__ASSERT(0 != object); FLAC__ASSERT(object->type == FLAC__METADATA_TYPE_PICTURE); return FLAC__format_picture_is_legal(&object->data.picture, violation); } sources_5316/external/flac/flac_protected_stream_decoder.h0000644000176700017670000000464710720607255022660 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PROTECTED__STREAM_DECODER_H #define FLAC__PROTECTED__STREAM_DECODER_H #include "flac_FLAC_stream_decoder.h" #if FLAC__HAS_OGG #include "private/ogg_decoder_aspect.h" #endif typedef struct FLAC__StreamDecoderProtected { FLAC__StreamDecoderState state; unsigned channels; FLAC__ChannelAssignment channel_assignment; unsigned bits_per_sample; unsigned sample_rate; /* in Hz */ unsigned blocksize; /* in samples (per channel) */ FLAC__bool md5_checking; /* if true, generate MD5 signature of decoded data and compare against signature in the STREAMINFO metadata block */ #if FLAC__HAS_OGG FLAC__OggDecoderAspect ogg_decoder_aspect; #endif } FLAC__StreamDecoderProtected; /* * return the number of input bytes consumed */ unsigned FLAC__stream_decoder_get_input_bytes_unconsumed(const FLAC__StreamDecoder *decoder); #endif sources_5316/external/flac/flac_private_md5.h0000644000176700017670000000302010720607255020026 0ustar paulpaul#ifndef FLAC__PRIVATE__MD5_H #define FLAC__PRIVATE__MD5_H /* * This is the header file for the MD5 message-digest algorithm. * The algorithm is due to Ron Rivest. This code was * written by Colin Plumb in 1993, no copyright is claimed. * This code is in the public domain; do with it what you wish. * * Equivalent code is available from RSA Data Security, Inc. * This code has been tested against that, and is equivalent, * except that you don't need to include two pages of legalese * with every copy. * * To compute the message digest of a chunk of bytes, declare an * MD5Context structure, pass it to MD5Init, call MD5Update as * needed on buffers full of bytes, and then call MD5Final, which * will fill a supplied 16-byte array with the digest. * * Changed so as no longer to depend on Colin Plumb's `usual.h' * header definitions; now uses stuff from dpkg's config.h * - Ian Jackson . * Still in the public domain. * * Josh Coalson: made some changes to integrate with libFLAC. * Still in the public domain, with no warranty. */ #include "flac_FLAC_ordinals.h" typedef struct { FLAC__uint32 in[16]; FLAC__uint32 buf[4]; FLAC__uint32 bytes[2]; FLAC__byte *internal_buf; size_t capacity; } FLAC__MD5Context; void FLAC__MD5Init(FLAC__MD5Context *context); void FLAC__MD5Final(FLAC__byte digest[16], FLAC__MD5Context *context); FLAC__bool FLAC__MD5Accumulate(FLAC__MD5Context *ctx, const FLAC__int32 * const signal[], unsigned channels, unsigned samples, unsigned bytes_per_sample); #endif sources_5316/external/flac/flac_FLAC_callback.h0000644000176700017670000001604510720611143020132 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__CALLBACK_H #define FLAC__CALLBACK_H #include "flac_FLAC_ordinals.h" #include /* for size_t */ /** \file include/FLAC/callback.h * * \brief * This module defines the structures for describing I/O callbacks * to the other FLAC interfaces. * * See the detailed documentation for callbacks in the * \link flac_callbacks callbacks \endlink module. */ /** \defgroup flac_callbacks FLAC/callback.h: I/O callback structures * \ingroup flac * * \brief * This module defines the structures for describing I/O callbacks * to the other FLAC interfaces. * * The purpose of the I/O callback functions is to create a common way * for the metadata interfaces to handle I/O. * * Originally the metadata interfaces required filenames as the way of * specifying FLAC files to operate on. This is problematic in some * environments so there is an additional option to specify a set of * callbacks for doing I/O on the FLAC file, instead of the filename. * * In addition to the callbacks, a FLAC__IOHandle type is defined as an * opaque structure for a data source. * * The callback function prototypes are similar (but not identical) to the * stdio functions fread, fwrite, fseek, ftell, feof, and fclose. If you use * stdio streams to implement the callbacks, you can pass fread, fwrite, and * fclose anywhere a FLAC__IOCallback_Read, FLAC__IOCallback_Write, or * FLAC__IOCallback_Close is required, and a FILE* anywhere a FLAC__IOHandle * is required. \warning You generally CANNOT directly use fseek or ftell * for FLAC__IOCallback_Seek or FLAC__IOCallback_Tell since on most systems * these use 32-bit offsets and FLAC requires 64-bit offsets to deal with * large files. You will have to find an equivalent function (e.g. ftello), * or write a wrapper. The same is true for feof() since this is usually * implemented as a macro, not as a function whose address can be taken. * * \{ */ #ifdef __cplusplus extern "C" { #endif /** This is the opaque handle type used by the callbacks. Typically * this is a \c FILE* or address of a file descriptor. */ typedef void* FLAC__IOHandle; /** Signature for the read callback. * The signature and semantics match POSIX fread() implementations * and can generally be used interchangeably. * * \param ptr The address of the read buffer. * \param size The size of the records to be read. * \param nmemb The number of records to be read. * \param handle The handle to the data source. * \retval size_t * The number of records read. */ typedef size_t (*FLAC__IOCallback_Read) (void *ptr, size_t size, size_t nmemb, FLAC__IOHandle handle); /** Signature for the write callback. * The signature and semantics match POSIX fwrite() implementations * and can generally be used interchangeably. * * \param ptr The address of the write buffer. * \param size The size of the records to be written. * \param nmemb The number of records to be written. * \param handle The handle to the data source. * \retval size_t * The number of records written. */ typedef size_t (*FLAC__IOCallback_Write) (const void *ptr, size_t size, size_t nmemb, FLAC__IOHandle handle); /** Signature for the seek callback. * The signature and semantics mostly match POSIX fseek() WITH ONE IMPORTANT * EXCEPTION: the offset is a 64-bit type whereas fseek() is generally 'long' * and 32-bits wide. * * \param handle The handle to the data source. * \param offset The new position, relative to \a whence * \param whence \c SEEK_SET, \c SEEK_CUR, or \c SEEK_END * \retval int * \c 0 on success, \c -1 on error. */ typedef int (*FLAC__IOCallback_Seek) (FLAC__IOHandle handle, FLAC__int64 offset, int whence); /** Signature for the tell callback. * The signature and semantics mostly match POSIX ftell() WITH ONE IMPORTANT * EXCEPTION: the offset is a 64-bit type whereas ftell() is generally 'long' * and 32-bits wide. * * \param handle The handle to the data source. * \retval FLAC__int64 * The current position on success, \c -1 on error. */ typedef FLAC__int64 (*FLAC__IOCallback_Tell) (FLAC__IOHandle handle); /** Signature for the EOF callback. * The signature and semantics mostly match POSIX feof() but WATCHOUT: * on many systems, feof() is a macro, so in this case a wrapper function * must be provided instead. * * \param handle The handle to the data source. * \retval int * \c 0 if not at end of file, nonzero if at end of file. */ typedef int (*FLAC__IOCallback_Eof) (FLAC__IOHandle handle); /** Signature for the close callback. * The signature and semantics match POSIX fclose() implementations * and can generally be used interchangeably. * * \param handle The handle to the data source. * \retval int * \c 0 on success, \c EOF on error. */ typedef int (*FLAC__IOCallback_Close) (FLAC__IOHandle handle); /** A structure for holding a set of callbacks. * Each FLAC interface that requires a FLAC__IOCallbacks structure will * describe which of the callbacks are required. The ones that are not * required may be set to NULL. * * If the seek requirement for an interface is optional, you can signify that * a data sorce is not seekable by setting the \a seek field to \c NULL. */ typedef struct { FLAC__IOCallback_Read read; FLAC__IOCallback_Write write; FLAC__IOCallback_Seek seek; FLAC__IOCallback_Tell tell; FLAC__IOCallback_Eof eof; FLAC__IOCallback_Close close; } FLAC__IOCallbacks; /* \} */ #ifdef __cplusplus } #endif #endif sources_5316/external/flac/flac_stream_encoder_framing.c0000644000176700017670000005620310720610061022277 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #if HAVE_CONFIG_H # include #endif #include #include /* for strlen() */ #include "flac_private_stream_encoder_framing.h" #include "flac_private_crc.h" #include "flac_FLAC_assert.h" #ifdef max #undef max #endif #define max(x,y) ((x)>(y)?(x):(y)) static FLAC__bool add_entropy_coding_method_(FLAC__BitWriter *bw, const FLAC__EntropyCodingMethod *method); static FLAC__bool add_residual_partitioned_rice_(FLAC__BitWriter *bw, const FLAC__int32 residual[], const unsigned residual_samples, const unsigned predictor_order, const unsigned rice_parameters[], const unsigned raw_bits[], const unsigned partition_order, const FLAC__bool is_extended); FLAC__bool FLAC__add_metadata_block(const FLAC__StreamMetadata *metadata, FLAC__BitWriter *bw) { unsigned i, j; const unsigned vendor_string_length = (unsigned)strlen(FLAC__VENDOR_STRING); if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->is_last, FLAC__STREAM_METADATA_IS_LAST_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->type, FLAC__STREAM_METADATA_TYPE_LEN)) return false; /* * First, for VORBIS_COMMENTs, adjust the length to reflect our vendor string */ i = metadata->length; if(metadata->type == FLAC__METADATA_TYPE_VORBIS_COMMENT) { FLAC__ASSERT(metadata->data.vorbis_comment.vendor_string.length == 0 || 0 != metadata->data.vorbis_comment.vendor_string.entry); i -= metadata->data.vorbis_comment.vendor_string.length; i += vendor_string_length; } FLAC__ASSERT(i < (1u << FLAC__STREAM_METADATA_LENGTH_LEN)); if(!FLAC__bitwriter_write_raw_uint32(bw, i, FLAC__STREAM_METADATA_LENGTH_LEN)) return false; switch(metadata->type) { case FLAC__METADATA_TYPE_STREAMINFO: FLAC__ASSERT(metadata->data.stream_info.min_blocksize < (1u << FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN)); if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.stream_info.min_blocksize, FLAC__STREAM_METADATA_STREAMINFO_MIN_BLOCK_SIZE_LEN)) return false; FLAC__ASSERT(metadata->data.stream_info.max_blocksize < (1u << FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN)); if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.stream_info.max_blocksize, FLAC__STREAM_METADATA_STREAMINFO_MAX_BLOCK_SIZE_LEN)) return false; FLAC__ASSERT(metadata->data.stream_info.min_framesize < (1u << FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN)); if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.stream_info.min_framesize, FLAC__STREAM_METADATA_STREAMINFO_MIN_FRAME_SIZE_LEN)) return false; FLAC__ASSERT(metadata->data.stream_info.max_framesize < (1u << FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN)); if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.stream_info.max_framesize, FLAC__STREAM_METADATA_STREAMINFO_MAX_FRAME_SIZE_LEN)) return false; FLAC__ASSERT(FLAC__format_sample_rate_is_valid(metadata->data.stream_info.sample_rate)); if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.stream_info.sample_rate, FLAC__STREAM_METADATA_STREAMINFO_SAMPLE_RATE_LEN)) return false; FLAC__ASSERT(metadata->data.stream_info.channels > 0); FLAC__ASSERT(metadata->data.stream_info.channels <= (1u << FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN)); if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.stream_info.channels-1, FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN)) return false; FLAC__ASSERT(metadata->data.stream_info.bits_per_sample > 0); FLAC__ASSERT(metadata->data.stream_info.bits_per_sample <= (1u << FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN)); if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.stream_info.bits_per_sample-1, FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint64(bw, metadata->data.stream_info.total_samples, FLAC__STREAM_METADATA_STREAMINFO_TOTAL_SAMPLES_LEN)) return false; if(!FLAC__bitwriter_write_byte_block(bw, metadata->data.stream_info.md5sum, 16)) return false; break; case FLAC__METADATA_TYPE_PADDING: if(!FLAC__bitwriter_write_zeroes(bw, metadata->length * 8)) return false; break; case FLAC__METADATA_TYPE_APPLICATION: if(!FLAC__bitwriter_write_byte_block(bw, metadata->data.application.id, FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8)) return false; if(!FLAC__bitwriter_write_byte_block(bw, metadata->data.application.data, metadata->length - (FLAC__STREAM_METADATA_APPLICATION_ID_LEN / 8))) return false; break; case FLAC__METADATA_TYPE_SEEKTABLE: for(i = 0; i < metadata->data.seek_table.num_points; i++) { if(!FLAC__bitwriter_write_raw_uint64(bw, metadata->data.seek_table.points[i].sample_number, FLAC__STREAM_METADATA_SEEKPOINT_SAMPLE_NUMBER_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint64(bw, metadata->data.seek_table.points[i].stream_offset, FLAC__STREAM_METADATA_SEEKPOINT_STREAM_OFFSET_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.seek_table.points[i].frame_samples, FLAC__STREAM_METADATA_SEEKPOINT_FRAME_SAMPLES_LEN)) return false; } break; case FLAC__METADATA_TYPE_VORBIS_COMMENT: if(!FLAC__bitwriter_write_raw_uint32_little_endian(bw, vendor_string_length)) return false; if(!FLAC__bitwriter_write_byte_block(bw, (const FLAC__byte*)FLAC__VENDOR_STRING, vendor_string_length)) return false; if(!FLAC__bitwriter_write_raw_uint32_little_endian(bw, metadata->data.vorbis_comment.num_comments)) return false; for(i = 0; i < metadata->data.vorbis_comment.num_comments; i++) { if(!FLAC__bitwriter_write_raw_uint32_little_endian(bw, metadata->data.vorbis_comment.comments[i].length)) return false; if(!FLAC__bitwriter_write_byte_block(bw, metadata->data.vorbis_comment.comments[i].entry, metadata->data.vorbis_comment.comments[i].length)) return false; } break; case FLAC__METADATA_TYPE_CUESHEET: FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN % 8 == 0); if(!FLAC__bitwriter_write_byte_block(bw, (const FLAC__byte*)metadata->data.cue_sheet.media_catalog_number, FLAC__STREAM_METADATA_CUESHEET_MEDIA_CATALOG_NUMBER_LEN/8)) return false; if(!FLAC__bitwriter_write_raw_uint64(bw, metadata->data.cue_sheet.lead_in, FLAC__STREAM_METADATA_CUESHEET_LEAD_IN_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.cue_sheet.is_cd? 1 : 0, FLAC__STREAM_METADATA_CUESHEET_IS_CD_LEN)) return false; if(!FLAC__bitwriter_write_zeroes(bw, FLAC__STREAM_METADATA_CUESHEET_RESERVED_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.cue_sheet.num_tracks, FLAC__STREAM_METADATA_CUESHEET_NUM_TRACKS_LEN)) return false; for(i = 0; i < metadata->data.cue_sheet.num_tracks; i++) { const FLAC__StreamMetadata_CueSheet_Track *track = metadata->data.cue_sheet.tracks + i; if(!FLAC__bitwriter_write_raw_uint64(bw, track->offset, FLAC__STREAM_METADATA_CUESHEET_TRACK_OFFSET_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, track->number, FLAC__STREAM_METADATA_CUESHEET_TRACK_NUMBER_LEN)) return false; FLAC__ASSERT(FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN % 8 == 0); if(!FLAC__bitwriter_write_byte_block(bw, (const FLAC__byte*)track->isrc, FLAC__STREAM_METADATA_CUESHEET_TRACK_ISRC_LEN/8)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, track->type, FLAC__STREAM_METADATA_CUESHEET_TRACK_TYPE_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, track->pre_emphasis, FLAC__STREAM_METADATA_CUESHEET_TRACK_PRE_EMPHASIS_LEN)) return false; if(!FLAC__bitwriter_write_zeroes(bw, FLAC__STREAM_METADATA_CUESHEET_TRACK_RESERVED_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, track->num_indices, FLAC__STREAM_METADATA_CUESHEET_TRACK_NUM_INDICES_LEN)) return false; for(j = 0; j < track->num_indices; j++) { const FLAC__StreamMetadata_CueSheet_Index *index = track->indices + j; if(!FLAC__bitwriter_write_raw_uint64(bw, index->offset, FLAC__STREAM_METADATA_CUESHEET_INDEX_OFFSET_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, index->number, FLAC__STREAM_METADATA_CUESHEET_INDEX_NUMBER_LEN)) return false; if(!FLAC__bitwriter_write_zeroes(bw, FLAC__STREAM_METADATA_CUESHEET_INDEX_RESERVED_LEN)) return false; } } break; case FLAC__METADATA_TYPE_PICTURE: { size_t len; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.picture.type, FLAC__STREAM_METADATA_PICTURE_TYPE_LEN)) return false; len = strlen(metadata->data.picture.mime_type); if(!FLAC__bitwriter_write_raw_uint32(bw, len, FLAC__STREAM_METADATA_PICTURE_MIME_TYPE_LENGTH_LEN)) return false; if(!FLAC__bitwriter_write_byte_block(bw, (const FLAC__byte*)metadata->data.picture.mime_type, len)) return false; len = strlen((const char *)metadata->data.picture.description); if(!FLAC__bitwriter_write_raw_uint32(bw, len, FLAC__STREAM_METADATA_PICTURE_DESCRIPTION_LENGTH_LEN)) return false; if(!FLAC__bitwriter_write_byte_block(bw, metadata->data.picture.description, len)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.picture.width, FLAC__STREAM_METADATA_PICTURE_WIDTH_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.picture.height, FLAC__STREAM_METADATA_PICTURE_HEIGHT_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.picture.depth, FLAC__STREAM_METADATA_PICTURE_DEPTH_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.picture.colors, FLAC__STREAM_METADATA_PICTURE_COLORS_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, metadata->data.picture.data_length, FLAC__STREAM_METADATA_PICTURE_DATA_LENGTH_LEN)) return false; if(!FLAC__bitwriter_write_byte_block(bw, metadata->data.picture.data, metadata->data.picture.data_length)) return false; } break; default: if(!FLAC__bitwriter_write_byte_block(bw, metadata->data.unknown.data, metadata->length)) return false; break; } FLAC__ASSERT(FLAC__bitwriter_is_byte_aligned(bw)); return true; } FLAC__bool FLAC__frame_add_header(const FLAC__FrameHeader *header, FLAC__BitWriter *bw) { unsigned u, blocksize_hint, sample_rate_hint; FLAC__byte crc; FLAC__ASSERT(FLAC__bitwriter_is_byte_aligned(bw)); if(!FLAC__bitwriter_write_raw_uint32(bw, FLAC__FRAME_HEADER_SYNC, FLAC__FRAME_HEADER_SYNC_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, 0, FLAC__FRAME_HEADER_RESERVED_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, (header->number_type == FLAC__FRAME_NUMBER_TYPE_FRAME_NUMBER)? 0 : 1, FLAC__FRAME_HEADER_BLOCKING_STRATEGY_LEN)) return false; FLAC__ASSERT(header->blocksize > 0 && header->blocksize <= FLAC__MAX_BLOCK_SIZE); /* when this assertion holds true, any legal blocksize can be expressed in the frame header */ FLAC__ASSERT(FLAC__MAX_BLOCK_SIZE <= 65535u); blocksize_hint = 0; switch(header->blocksize) { case 192: u = 1; break; case 576: u = 2; break; case 1152: u = 3; break; case 2304: u = 4; break; case 4608: u = 5; break; case 256: u = 8; break; case 512: u = 9; break; case 1024: u = 10; break; case 2048: u = 11; break; case 4096: u = 12; break; case 8192: u = 13; break; case 16384: u = 14; break; case 32768: u = 15; break; default: if(header->blocksize <= 0x100) blocksize_hint = u = 6; else blocksize_hint = u = 7; break; } if(!FLAC__bitwriter_write_raw_uint32(bw, u, FLAC__FRAME_HEADER_BLOCK_SIZE_LEN)) return false; FLAC__ASSERT(FLAC__format_sample_rate_is_valid(header->sample_rate)); sample_rate_hint = 0; switch(header->sample_rate) { case 88200: u = 1; break; case 176400: u = 2; break; case 192000: u = 3; break; case 8000: u = 4; break; case 16000: u = 5; break; case 22050: u = 6; break; case 24000: u = 7; break; case 32000: u = 8; break; case 44100: u = 9; break; case 48000: u = 10; break; case 96000: u = 11; break; default: if(header->sample_rate <= 255000 && header->sample_rate % 1000 == 0) sample_rate_hint = u = 12; else if(header->sample_rate % 10 == 0) sample_rate_hint = u = 14; else if(header->sample_rate <= 0xffff) sample_rate_hint = u = 13; else u = 0; break; } if(!FLAC__bitwriter_write_raw_uint32(bw, u, FLAC__FRAME_HEADER_SAMPLE_RATE_LEN)) return false; FLAC__ASSERT(header->channels > 0 && header->channels <= (1u << FLAC__STREAM_METADATA_STREAMINFO_CHANNELS_LEN) && header->channels <= FLAC__MAX_CHANNELS); switch(header->channel_assignment) { case FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT: u = header->channels - 1; break; case FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE: FLAC__ASSERT(header->channels == 2); u = 8; break; case FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE: FLAC__ASSERT(header->channels == 2); u = 9; break; case FLAC__CHANNEL_ASSIGNMENT_MID_SIDE: FLAC__ASSERT(header->channels == 2); u = 10; break; default: FLAC__ASSERT(0); } if(!FLAC__bitwriter_write_raw_uint32(bw, u, FLAC__FRAME_HEADER_CHANNEL_ASSIGNMENT_LEN)) return false; FLAC__ASSERT(header->bits_per_sample > 0 && header->bits_per_sample <= (1u << FLAC__STREAM_METADATA_STREAMINFO_BITS_PER_SAMPLE_LEN)); switch(header->bits_per_sample) { case 8 : u = 1; break; case 12: u = 2; break; case 16: u = 4; break; case 20: u = 5; break; case 24: u = 6; break; default: u = 0; break; } if(!FLAC__bitwriter_write_raw_uint32(bw, u, FLAC__FRAME_HEADER_BITS_PER_SAMPLE_LEN)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, 0, FLAC__FRAME_HEADER_ZERO_PAD_LEN)) return false; if(header->number_type == FLAC__FRAME_NUMBER_TYPE_FRAME_NUMBER) { if(!FLAC__bitwriter_write_utf8_uint32(bw, header->number.frame_number)) return false; } else { if(!FLAC__bitwriter_write_utf8_uint64(bw, header->number.sample_number)) return false; } if(blocksize_hint) if(!FLAC__bitwriter_write_raw_uint32(bw, header->blocksize-1, (blocksize_hint==6)? 8:16)) return false; switch(sample_rate_hint) { case 12: if(!FLAC__bitwriter_write_raw_uint32(bw, header->sample_rate / 1000, 8)) return false; break; case 13: if(!FLAC__bitwriter_write_raw_uint32(bw, header->sample_rate, 16)) return false; break; case 14: if(!FLAC__bitwriter_write_raw_uint32(bw, header->sample_rate / 10, 16)) return false; break; } /* write the CRC */ if(!FLAC__bitwriter_get_write_crc8(bw, &crc)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, crc, FLAC__FRAME_HEADER_CRC_LEN)) return false; return true; } FLAC__bool FLAC__subframe_add_constant(const FLAC__Subframe_Constant *subframe, unsigned subframe_bps, unsigned wasted_bits, FLAC__BitWriter *bw) { FLAC__bool ok; ok = FLAC__bitwriter_write_raw_uint32(bw, FLAC__SUBFRAME_TYPE_CONSTANT_BYTE_ALIGNED_MASK | (wasted_bits? 1:0), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN) && (wasted_bits? FLAC__bitwriter_write_unary_unsigned(bw, wasted_bits-1) : true) && FLAC__bitwriter_write_raw_int32(bw, subframe->value, subframe_bps) ; return ok; } FLAC__bool FLAC__subframe_add_fixed(const FLAC__Subframe_Fixed *subframe, unsigned residual_samples, unsigned subframe_bps, unsigned wasted_bits, FLAC__BitWriter *bw) { unsigned i; if(!FLAC__bitwriter_write_raw_uint32(bw, FLAC__SUBFRAME_TYPE_FIXED_BYTE_ALIGNED_MASK | (subframe->order<<1) | (wasted_bits? 1:0), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN)) return false; if(wasted_bits) if(!FLAC__bitwriter_write_unary_unsigned(bw, wasted_bits-1)) return false; for(i = 0; i < subframe->order; i++) if(!FLAC__bitwriter_write_raw_int32(bw, subframe->warmup[i], subframe_bps)) return false; if(!add_entropy_coding_method_(bw, &subframe->entropy_coding_method)) return false; switch(subframe->entropy_coding_method.type) { case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE: case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2: if(!add_residual_partitioned_rice_( bw, subframe->residual, residual_samples, subframe->order, subframe->entropy_coding_method.data.partitioned_rice.contents->parameters, subframe->entropy_coding_method.data.partitioned_rice.contents->raw_bits, subframe->entropy_coding_method.data.partitioned_rice.order, /*is_extended=*/subframe->entropy_coding_method.type == FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2 )) return false; break; default: FLAC__ASSERT(0); } return true; } FLAC__bool FLAC__subframe_add_lpc(const FLAC__Subframe_LPC *subframe, unsigned residual_samples, unsigned subframe_bps, unsigned wasted_bits, FLAC__BitWriter *bw) { unsigned i; if(!FLAC__bitwriter_write_raw_uint32(bw, FLAC__SUBFRAME_TYPE_LPC_BYTE_ALIGNED_MASK | ((subframe->order-1)<<1) | (wasted_bits? 1:0), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN)) return false; if(wasted_bits) if(!FLAC__bitwriter_write_unary_unsigned(bw, wasted_bits-1)) return false; for(i = 0; i < subframe->order; i++) if(!FLAC__bitwriter_write_raw_int32(bw, subframe->warmup[i], subframe_bps)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, subframe->qlp_coeff_precision-1, FLAC__SUBFRAME_LPC_QLP_COEFF_PRECISION_LEN)) return false; if(!FLAC__bitwriter_write_raw_int32(bw, subframe->quantization_level, FLAC__SUBFRAME_LPC_QLP_SHIFT_LEN)) return false; for(i = 0; i < subframe->order; i++) if(!FLAC__bitwriter_write_raw_int32(bw, subframe->qlp_coeff[i], subframe->qlp_coeff_precision)) return false; if(!add_entropy_coding_method_(bw, &subframe->entropy_coding_method)) return false; switch(subframe->entropy_coding_method.type) { case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE: case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2: if(!add_residual_partitioned_rice_( bw, subframe->residual, residual_samples, subframe->order, subframe->entropy_coding_method.data.partitioned_rice.contents->parameters, subframe->entropy_coding_method.data.partitioned_rice.contents->raw_bits, subframe->entropy_coding_method.data.partitioned_rice.order, /*is_extended=*/subframe->entropy_coding_method.type == FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2 )) return false; break; default: FLAC__ASSERT(0); } return true; } FLAC__bool FLAC__subframe_add_verbatim(const FLAC__Subframe_Verbatim *subframe, unsigned samples, unsigned subframe_bps, unsigned wasted_bits, FLAC__BitWriter *bw) { unsigned i; const FLAC__int32 *signal = subframe->data; if(!FLAC__bitwriter_write_raw_uint32(bw, FLAC__SUBFRAME_TYPE_VERBATIM_BYTE_ALIGNED_MASK | (wasted_bits? 1:0), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN)) return false; if(wasted_bits) if(!FLAC__bitwriter_write_unary_unsigned(bw, wasted_bits-1)) return false; for(i = 0; i < samples; i++) if(!FLAC__bitwriter_write_raw_int32(bw, signal[i], subframe_bps)) return false; return true; } FLAC__bool add_entropy_coding_method_(FLAC__BitWriter *bw, const FLAC__EntropyCodingMethod *method) { if(!FLAC__bitwriter_write_raw_uint32(bw, method->type, FLAC__ENTROPY_CODING_METHOD_TYPE_LEN)) return false; switch(method->type) { case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE: case FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2: if(!FLAC__bitwriter_write_raw_uint32(bw, method->data.partitioned_rice.order, FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ORDER_LEN)) return false; break; default: FLAC__ASSERT(0); } return true; } FLAC__bool add_residual_partitioned_rice_(FLAC__BitWriter *bw, const FLAC__int32 residual[], const unsigned residual_samples, const unsigned predictor_order, const unsigned rice_parameters[], const unsigned raw_bits[], const unsigned partition_order, const FLAC__bool is_extended) { const unsigned plen = is_extended? FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_PARAMETER_LEN : FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_PARAMETER_LEN; const unsigned pesc = is_extended? FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE2_ESCAPE_PARAMETER : FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_ESCAPE_PARAMETER; if(partition_order == 0) { unsigned i; if(raw_bits[0] == 0) { if(!FLAC__bitwriter_write_raw_uint32(bw, rice_parameters[0], plen)) return false; if(!FLAC__bitwriter_write_rice_signed_block(bw, residual, residual_samples, rice_parameters[0])) return false; } else { FLAC__ASSERT(rice_parameters[0] == 0); if(!FLAC__bitwriter_write_raw_uint32(bw, pesc, plen)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, raw_bits[0], FLAC__ENTROPY_CODING_METHOD_PARTITIONED_RICE_RAW_LEN)) return false; for(i = 0; i < residual_samples; i++) { if(!FLAC__bitwriter_write_raw_int32(bw, residual[i], raw_bits[0])) return false; } } return true; } else { unsigned i, j, k = 0, k_last = 0; unsigned partition_samples; const unsigned default_partition_samples = (residual_samples+predictor_order) >> partition_order; for(i = 0; i < (1u< #endif #include /* for malloc() */ #include /* for memcpy(), memset() */ #ifdef _WIN32 #include /* for ntohl() */ #elif defined FLAC__SYS_DARWIN #include /* for ntohl() */ #elif defined __MINGW32__ #include /* for ntohl() */ #else #include /* for ntohl() */ #endif #if 0 /* UNUSED */ #include "flac_private_bitmath.h" #endif #include "flac_private_bitwriter.h" #include "flac_private_crc.h" #include "flac_FLAC_assert.h" #include "flac_share_alloc.h" /* Things should be fastest when this matches the machine word size */ /* WATCHOUT: if you change this you must also change the following #defines down to SWAP_BE_WORD_TO_HOST below to match */ /* WATCHOUT: there are a few places where the code will not work unless bwword is >= 32 bits wide */ typedef FLAC__uint32 bwword; #define FLAC__BYTES_PER_WORD 4 #define FLAC__BITS_PER_WORD 32 #define FLAC__WORD_ALL_ONES ((FLAC__uint32)0xffffffff) /* SWAP_BE_WORD_TO_HOST swaps bytes in a bwword (which is always big-endian) if necessary to match host byte order */ #if WORDS_BIGENDIAN #define SWAP_BE_WORD_TO_HOST(x) (x) #else #ifdef _MSC_VER #define SWAP_BE_WORD_TO_HOST(x) local_swap32_(x) #else #define SWAP_BE_WORD_TO_HOST(x) ntohl(x) #endif #endif /* * The default capacity here doesn't matter too much. The buffer always grows * to hold whatever is written to it. Usually the encoder will stop adding at * a frame or metadata block, then write that out and clear the buffer for the * next one. */ static const unsigned FLAC__BITWRITER_DEFAULT_CAPACITY = 32768u / sizeof(bwword); /* size in words */ /* When growing, increment 4K at a time */ static const unsigned FLAC__BITWRITER_DEFAULT_INCREMENT = 4096u / sizeof(bwword); /* size in words */ #define FLAC__WORDS_TO_BITS(words) ((words) * FLAC__BITS_PER_WORD) #define FLAC__TOTAL_BITS(bw) (FLAC__WORDS_TO_BITS((bw)->words) + (bw)->bits) #ifdef min #undef min #endif #define min(x,y) ((x)<(y)?(x):(y)) /* adjust for compilers that can't understand using LLU suffix for uint64_t literals */ #ifdef _MSC_VER #define FLAC__U64L(x) x #else #define FLAC__U64L(x) x##LLU #endif #ifndef FLaC__INLINE #define FLaC__INLINE #endif struct FLAC__BitWriter { bwword *buffer; bwword accum; /* accumulator; bits are right-justified; when full, accum is appended to buffer */ unsigned capacity; /* capacity of buffer in words */ unsigned words; /* # of complete words in buffer */ unsigned bits; /* # of used bits in accum */ }; #ifdef _MSC_VER /* OPT: an MSVC built-in would be better */ static _inline FLAC__uint32 local_swap32_(FLAC__uint32 x) { x = ((x<<8)&0xFF00FF00) | ((x>>8)&0x00FF00FF); return (x>>16) | (x<<16); } #endif /* * WATCHOUT: The current implementation only grows the buffer. */ static FLAC__bool bitwriter_grow_(FLAC__BitWriter *bw, unsigned bits_to_add) { unsigned new_capacity; bwword *new_buffer; FLAC__ASSERT(0 != bw); FLAC__ASSERT(0 != bw->buffer); /* calculate total words needed to store 'bits_to_add' additional bits */ new_capacity = bw->words + ((bw->bits + bits_to_add + FLAC__BITS_PER_WORD - 1) / FLAC__BITS_PER_WORD); /* it's possible (due to pessimism in the growth estimation that * leads to this call) that we don't actually need to grow */ if(bw->capacity >= new_capacity) return true; /* round up capacity increase to the nearest FLAC__BITWRITER_DEFAULT_INCREMENT */ if((new_capacity - bw->capacity) % FLAC__BITWRITER_DEFAULT_INCREMENT) new_capacity += FLAC__BITWRITER_DEFAULT_INCREMENT - ((new_capacity - bw->capacity) % FLAC__BITWRITER_DEFAULT_INCREMENT); /* make sure we got everything right */ FLAC__ASSERT(0 == (new_capacity - bw->capacity) % FLAC__BITWRITER_DEFAULT_INCREMENT); FLAC__ASSERT(new_capacity > bw->capacity); FLAC__ASSERT(new_capacity >= bw->words + ((bw->bits + bits_to_add + FLAC__BITS_PER_WORD - 1) / FLAC__BITS_PER_WORD)); new_buffer = (bwword*)safe_realloc_mul_2op_(bw->buffer, sizeof(bwword), /*times*/new_capacity); if(new_buffer == 0) return false; bw->buffer = new_buffer; bw->capacity = new_capacity; return true; } /*********************************************************************** * * Class constructor/destructor * ***********************************************************************/ FLAC__BitWriter *FLAC__bitwriter_new(void) { FLAC__BitWriter *bw = (FLAC__BitWriter*)calloc(1, sizeof(FLAC__BitWriter)); /* note that calloc() sets all members to 0 for us */ return bw; } void FLAC__bitwriter_delete(FLAC__BitWriter *bw) { FLAC__ASSERT(0 != bw); FLAC__bitwriter_free(bw); free(bw); } /*********************************************************************** * * Public class methods * ***********************************************************************/ FLAC__bool FLAC__bitwriter_init(FLAC__BitWriter *bw) { FLAC__ASSERT(0 != bw); bw->words = bw->bits = 0; bw->capacity = FLAC__BITWRITER_DEFAULT_CAPACITY; bw->buffer = (bwword*)malloc(sizeof(bwword) * bw->capacity); if(bw->buffer == 0) return false; return true; } void FLAC__bitwriter_free(FLAC__BitWriter *bw) { FLAC__ASSERT(0 != bw); if(0 != bw->buffer) free(bw->buffer); bw->buffer = 0; bw->capacity = 0; bw->words = bw->bits = 0; } void FLAC__bitwriter_clear(FLAC__BitWriter *bw) { bw->words = bw->bits = 0; } void FLAC__bitwriter_dump(const FLAC__BitWriter *bw, FILE *out) { unsigned i, j; if(bw == 0) { fprintf(out, "bitwriter is NULL\n"); } else { fprintf(out, "bitwriter: capacity=%u words=%u bits=%u total_bits=%u\n", bw->capacity, bw->words, bw->bits, FLAC__TOTAL_BITS(bw)); for(i = 0; i < bw->words; i++) { fprintf(out, "%08X: ", i); for(j = 0; j < FLAC__BITS_PER_WORD; j++) fprintf(out, "%01u", bw->buffer[i] & (1 << (FLAC__BITS_PER_WORD-j-1)) ? 1:0); fprintf(out, "\n"); } if(bw->bits > 0) { fprintf(out, "%08X: ", i); for(j = 0; j < bw->bits; j++) fprintf(out, "%01u", bw->accum & (1 << (bw->bits-j-1)) ? 1:0); fprintf(out, "\n"); } } } FLAC__bool FLAC__bitwriter_get_write_crc16(FLAC__BitWriter *bw, FLAC__uint16 *crc) { const FLAC__byte *buffer; size_t bytes; FLAC__ASSERT((bw->bits & 7) == 0); /* assert that we're byte-aligned */ if(!FLAC__bitwriter_get_buffer(bw, &buffer, &bytes)) return false; *crc = (FLAC__uint16)FLAC__crc16(buffer, bytes); FLAC__bitwriter_release_buffer(bw); return true; } FLAC__bool FLAC__bitwriter_get_write_crc8(FLAC__BitWriter *bw, FLAC__byte *crc) { const FLAC__byte *buffer; size_t bytes; FLAC__ASSERT((bw->bits & 7) == 0); /* assert that we're byte-aligned */ if(!FLAC__bitwriter_get_buffer(bw, &buffer, &bytes)) return false; *crc = FLAC__crc8(buffer, bytes); FLAC__bitwriter_release_buffer(bw); return true; } FLAC__bool FLAC__bitwriter_is_byte_aligned(const FLAC__BitWriter *bw) { return ((bw->bits & 7) == 0); } unsigned FLAC__bitwriter_get_input_bits_unconsumed(const FLAC__BitWriter *bw) { return FLAC__TOTAL_BITS(bw); } FLAC__bool FLAC__bitwriter_get_buffer(FLAC__BitWriter *bw, const FLAC__byte **buffer, size_t *bytes) { FLAC__ASSERT((bw->bits & 7) == 0); /* double protection */ if(bw->bits & 7) return false; /* if we have bits in the accumulator we have to flush those to the buffer first */ if(bw->bits) { FLAC__ASSERT(bw->words <= bw->capacity); if(bw->words == bw->capacity && !bitwriter_grow_(bw, FLAC__BITS_PER_WORD)) return false; /* append bits as complete word to buffer, but don't change bw->accum or bw->bits */ bw->buffer[bw->words] = SWAP_BE_WORD_TO_HOST(bw->accum << (FLAC__BITS_PER_WORD-bw->bits)); } /* now we can just return what we have */ *buffer = (FLAC__byte*)bw->buffer; *bytes = (FLAC__BYTES_PER_WORD * bw->words) + (bw->bits >> 3); return true; } void FLAC__bitwriter_release_buffer(FLAC__BitWriter *bw) { /* nothing to do. in the future, strict checking of a 'writer-is-in- * get-mode' flag could be added everywhere and then cleared here */ (void)bw; } FLAC__bool FLAC__bitwriter_write_zeroes(FLAC__BitWriter *bw, unsigned bits) { unsigned n; FLAC__ASSERT(0 != bw); FLAC__ASSERT(0 != bw->buffer); if(bits == 0) return true; /* slightly pessimistic size check but faster than "<= bw->words + (bw->bits+bits+FLAC__BITS_PER_WORD-1)/FLAC__BITS_PER_WORD" */ if(bw->capacity <= bw->words + bits && !bitwriter_grow_(bw, bits)) return false; /* first part gets to word alignment */ if(bw->bits) { n = min(FLAC__BITS_PER_WORD - bw->bits, bits); bw->accum <<= n; bits -= n; bw->bits += n; if(bw->bits == FLAC__BITS_PER_WORD) { bw->buffer[bw->words++] = SWAP_BE_WORD_TO_HOST(bw->accum); bw->bits = 0; } else return true; } /* do whole words */ while(bits >= FLAC__BITS_PER_WORD) { bw->buffer[bw->words++] = 0; bits -= FLAC__BITS_PER_WORD; } /* do any leftovers */ if(bits > 0) { bw->accum = 0; bw->bits = bits; } return true; } FLAC__bool FLAC__bitwriter_write_raw_uint32(FLAC__BitWriter *bw, FLAC__uint32 val, unsigned bits) { register unsigned left; /* WATCHOUT: code does not work with <32bit words; we can make things much faster with this assertion */ FLAC__ASSERT(FLAC__BITS_PER_WORD >= 32); FLAC__ASSERT(0 != bw); FLAC__ASSERT(0 != bw->buffer); FLAC__ASSERT(bits <= 32); if(bits == 0) return true; /* slightly pessimistic size check but faster than "<= bw->words + (bw->bits+bits+FLAC__BITS_PER_WORD-1)/FLAC__BITS_PER_WORD" */ if(bw->capacity <= bw->words + bits && !bitwriter_grow_(bw, bits)) return false; left = FLAC__BITS_PER_WORD - bw->bits; if(bits < left) { bw->accum <<= bits; bw->accum |= val; bw->bits += bits; } else if(bw->bits) { /* WATCHOUT: if bw->bits == 0, left==FLAC__BITS_PER_WORD and bw->accum<<=left is a NOP instead of setting to 0 */ bw->accum <<= left; bw->accum |= val >> (bw->bits = bits - left); bw->buffer[bw->words++] = SWAP_BE_WORD_TO_HOST(bw->accum); bw->accum = val; } else { bw->accum = val; bw->bits = 0; bw->buffer[bw->words++] = SWAP_BE_WORD_TO_HOST(val); } return true; } FLAC__bool FLAC__bitwriter_write_raw_int32(FLAC__BitWriter *bw, FLAC__int32 val, unsigned bits) { /* zero-out unused bits */ if(bits < 32) val &= (~(0xffffffff << bits)); return FLAC__bitwriter_write_raw_uint32(bw, (FLAC__uint32)val, bits); } FLAC__bool FLAC__bitwriter_write_raw_uint64(FLAC__BitWriter *bw, FLAC__uint64 val, unsigned bits) { /* this could be a little faster but it's not used for much */ if(bits > 32) { return FLAC__bitwriter_write_raw_uint32(bw, (FLAC__uint32)(val>>32), bits-32) && FLAC__bitwriter_write_raw_uint32(bw, (FLAC__uint32)val, 32); } else return FLAC__bitwriter_write_raw_uint32(bw, (FLAC__uint32)val, bits); } FLAC__bool FLAC__bitwriter_write_raw_uint32_little_endian(FLAC__BitWriter *bw, FLAC__uint32 val) { /* this doesn't need to be that fast as currently it is only used for vorbis comments */ if(!FLAC__bitwriter_write_raw_uint32(bw, val & 0xff, 8)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, (val>>8) & 0xff, 8)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, (val>>16) & 0xff, 8)) return false; if(!FLAC__bitwriter_write_raw_uint32(bw, val>>24, 8)) return false; return true; } FLAC__bool FLAC__bitwriter_write_byte_block(FLAC__BitWriter *bw, const FLAC__byte vals[], unsigned nvals) { unsigned i; /* this could be faster but currently we don't need it to be since it's only used for writing metadata */ for(i = 0; i < nvals; i++) { if(!FLAC__bitwriter_write_raw_uint32(bw, (FLAC__uint32)(vals[i]), 8)) return false; } return true; } FLAC__bool FLAC__bitwriter_write_unary_unsigned(FLAC__BitWriter *bw, unsigned val) { if(val < 32) return FLAC__bitwriter_write_raw_uint32(bw, 1, ++val); else return FLAC__bitwriter_write_zeroes(bw, val) && FLAC__bitwriter_write_raw_uint32(bw, 1, 1); } unsigned FLAC__bitwriter_rice_bits(FLAC__int32 val, unsigned parameter) { FLAC__uint32 uval; FLAC__ASSERT(parameter < sizeof(unsigned)*8); /* fold signed to unsigned; actual formula is: negative(v)? -2v-1 : 2v */ uval = (val<<1) ^ (val>>31); return 1 + parameter + (uval >> parameter); } #if 0 /* UNUSED */ unsigned FLAC__bitwriter_golomb_bits_signed(int val, unsigned parameter) { unsigned bits, msbs, uval; unsigned k; FLAC__ASSERT(parameter > 0); /* fold signed to unsigned */ if(val < 0) uval = (unsigned)(((-(++val)) << 1) + 1); else uval = (unsigned)(val << 1); k = FLAC__bitmath_ilog2(parameter); if(parameter == 1u<> k; bits = 1 + k + msbs; } else { unsigned q, r, d; d = (1 << (k+1)) - parameter; q = uval / parameter; r = uval - (q * parameter); bits = 1 + q + k; if(r >= d) bits++; } return bits; } unsigned FLAC__bitwriter_golomb_bits_unsigned(unsigned uval, unsigned parameter) { unsigned bits, msbs; unsigned k; FLAC__ASSERT(parameter > 0); k = FLAC__bitmath_ilog2(parameter); if(parameter == 1u<> k; bits = 1 + k + msbs; } else { unsigned q, r, d; d = (1 << (k+1)) - parameter; q = uval / parameter; r = uval - (q * parameter); bits = 1 + q + k; if(r >= d) bits++; } return bits; } #endif /* UNUSED */ FLAC__bool FLAC__bitwriter_write_rice_signed(FLAC__BitWriter *bw, FLAC__int32 val, unsigned parameter) { unsigned total_bits, interesting_bits, msbs; FLAC__uint32 uval, pattern; FLAC__ASSERT(0 != bw); FLAC__ASSERT(0 != bw->buffer); FLAC__ASSERT(parameter < 8*sizeof(uval)); /* fold signed to unsigned; actual formula is: negative(v)? -2v-1 : 2v */ uval = (val<<1) ^ (val>>31); msbs = uval >> parameter; interesting_bits = 1 + parameter; total_bits = interesting_bits + msbs; pattern = 1 << parameter; /* the unary end bit */ pattern |= (uval & ((1<> (31-parameter); /* ...then mask off the bits above the stop bit with val&=mask2*/ FLAC__uint32 uval; unsigned left; const unsigned lsbits = 1 + parameter; unsigned msbits; FLAC__ASSERT(0 != bw); FLAC__ASSERT(0 != bw->buffer); FLAC__ASSERT(parameter < 8*sizeof(bwword)-1); /* WATCHOUT: code does not work with <32bit words; we can make things much faster with this assertion */ FLAC__ASSERT(FLAC__BITS_PER_WORD >= 32); while(nvals) { /* fold signed to unsigned; actual formula is: negative(v)? -2v-1 : 2v */ uval = (*vals<<1) ^ (*vals>>31); msbits = uval >> parameter; #if 0 /* OPT: can remove this special case if it doesn't make up for the extra compare (doesn't make a statistically significant difference with msvc or gcc/x86) */ if(bw->bits && bw->bits + msbits + lsbits <= FLAC__BITS_PER_WORD) { /* i.e. if the whole thing fits in the current bwword */ /* ^^^ if bw->bits is 0 then we may have filled the buffer and have no free bwword to work in */ bw->bits = bw->bits + msbits + lsbits; uval |= mask1; /* set stop bit */ uval &= mask2; /* mask off unused top bits */ /* NOT: bw->accum <<= msbits + lsbits because msbits+lsbits could be 32, then the shift would be a NOP */ bw->accum <<= msbits; bw->accum <<= lsbits; bw->accum |= uval; if(bw->bits == FLAC__BITS_PER_WORD) { bw->buffer[bw->words++] = SWAP_BE_WORD_TO_HOST(bw->accum); bw->bits = 0; /* burying the capacity check down here means we have to grow the buffer a little if there are more vals to do */ if(bw->capacity <= bw->words && nvals > 1 && !bitwriter_grow_(bw, 1)) { FLAC__ASSERT(bw->capacity == bw->words); return false; } } } else { #elif 1 /*@@@@@@ OPT: try this version with MSVC6 to see if better, not much difference for gcc-4 */ if(bw->bits && bw->bits + msbits + lsbits < FLAC__BITS_PER_WORD) { /* i.e. if the whole thing fits in the current bwword */ /* ^^^ if bw->bits is 0 then we may have filled the buffer and have no free bwword to work in */ bw->bits = bw->bits + msbits + lsbits; uval |= mask1; /* set stop bit */ uval &= mask2; /* mask off unused top bits */ bw->accum <<= msbits + lsbits; bw->accum |= uval; } else { #endif /* slightly pessimistic size check but faster than "<= bw->words + (bw->bits+msbits+lsbits+FLAC__BITS_PER_WORD-1)/FLAC__BITS_PER_WORD" */ /* OPT: pessimism may cause flurry of false calls to grow_ which eat up all savings before it */ if(bw->capacity <= bw->words + bw->bits + msbits + 1/*lsbits always fit in 1 bwword*/ && !bitwriter_grow_(bw, msbits+lsbits)) return false; if(msbits) { /* first part gets to word alignment */ if(bw->bits) { left = FLAC__BITS_PER_WORD - bw->bits; if(msbits < left) { bw->accum <<= msbits; bw->bits += msbits; goto break1; } else { bw->accum <<= left; msbits -= left; bw->buffer[bw->words++] = SWAP_BE_WORD_TO_HOST(bw->accum); bw->bits = 0; } } /* do whole words */ while(msbits >= FLAC__BITS_PER_WORD) { bw->buffer[bw->words++] = 0; msbits -= FLAC__BITS_PER_WORD; } /* do any leftovers */ if(msbits > 0) { bw->accum = 0; bw->bits = msbits; } } break1: uval |= mask1; /* set stop bit */ uval &= mask2; /* mask off unused top bits */ left = FLAC__BITS_PER_WORD - bw->bits; if(lsbits < left) { bw->accum <<= lsbits; bw->accum |= uval; bw->bits += lsbits; } else { /* if bw->bits == 0, left==FLAC__BITS_PER_WORD which will always * be > lsbits (because of previous assertions) so it would have * triggered the (lsbitsbits); FLAC__ASSERT(left < FLAC__BITS_PER_WORD); bw->accum <<= left; bw->accum |= uval >> (bw->bits = lsbits - left); bw->buffer[bw->words++] = SWAP_BE_WORD_TO_HOST(bw->accum); bw->accum = uval; } #if 1 } #endif vals++; nvals--; } return true; } #if 0 /* UNUSED */ FLAC__bool FLAC__bitwriter_write_golomb_signed(FLAC__BitWriter *bw, int val, unsigned parameter) { unsigned total_bits, msbs, uval; unsigned k; FLAC__ASSERT(0 != bw); FLAC__ASSERT(0 != bw->buffer); FLAC__ASSERT(parameter > 0); /* fold signed to unsigned */ if(val < 0) uval = (unsigned)(((-(++val)) << 1) + 1); else uval = (unsigned)(val << 1); k = FLAC__bitmath_ilog2(parameter); if(parameter == 1u<> k; total_bits = 1 + k + msbs; pattern = 1 << k; /* the unary end bit */ pattern |= (uval & ((1u<= d) { if(!FLAC__bitwriter_write_raw_uint32(bw, r+d, k+1)) return false; } else { if(!FLAC__bitwriter_write_raw_uint32(bw, r, k)) return false; } } return true; } FLAC__bool FLAC__bitwriter_write_golomb_unsigned(FLAC__BitWriter *bw, unsigned uval, unsigned parameter) { unsigned total_bits, msbs; unsigned k; FLAC__ASSERT(0 != bw); FLAC__ASSERT(0 != bw->buffer); FLAC__ASSERT(parameter > 0); k = FLAC__bitmath_ilog2(parameter); if(parameter == 1u<> k; total_bits = 1 + k + msbs; pattern = 1 << k; /* the unary end bit */ pattern |= (uval & ((1u<= d) { if(!FLAC__bitwriter_write_raw_uint32(bw, r+d, k+1)) return false; } else { if(!FLAC__bitwriter_write_raw_uint32(bw, r, k)) return false; } } return true; } #endif /* UNUSED */ FLAC__bool FLAC__bitwriter_write_utf8_uint32(FLAC__BitWriter *bw, FLAC__uint32 val) { FLAC__bool ok = 1; FLAC__ASSERT(0 != bw); FLAC__ASSERT(0 != bw->buffer); FLAC__ASSERT(!(val & 0x80000000)); /* this version only handles 31 bits */ if(val < 0x80) { return FLAC__bitwriter_write_raw_uint32(bw, val, 8); } else if(val < 0x800) { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xC0 | (val>>6), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (val&0x3F), 8); } else if(val < 0x10000) { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xE0 | (val>>12), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>6)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (val&0x3F), 8); } else if(val < 0x200000) { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xF0 | (val>>18), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>12)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>6)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (val&0x3F), 8); } else if(val < 0x4000000) { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xF8 | (val>>24), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>18)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>12)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>6)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (val&0x3F), 8); } else { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xFC | (val>>30), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>24)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>18)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>12)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | ((val>>6)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (val&0x3F), 8); } return ok; } FLAC__bool FLAC__bitwriter_write_utf8_uint64(FLAC__BitWriter *bw, FLAC__uint64 val) { FLAC__bool ok = 1; FLAC__ASSERT(0 != bw); FLAC__ASSERT(0 != bw->buffer); FLAC__ASSERT(!(val & FLAC__U64L(0xFFFFFFF000000000))); /* this version only handles 36 bits */ if(val < 0x80) { return FLAC__bitwriter_write_raw_uint32(bw, (FLAC__uint32)val, 8); } else if(val < 0x800) { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xC0 | (FLAC__uint32)(val>>6), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)(val&0x3F), 8); } else if(val < 0x10000) { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xE0 | (FLAC__uint32)(val>>12), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>6)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)(val&0x3F), 8); } else if(val < 0x200000) { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xF0 | (FLAC__uint32)(val>>18), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>12)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>6)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)(val&0x3F), 8); } else if(val < 0x4000000) { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xF8 | (FLAC__uint32)(val>>24), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>18)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>12)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>6)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)(val&0x3F), 8); } else if(val < 0x80000000) { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xFC | (FLAC__uint32)(val>>30), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>24)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>18)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>12)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>6)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)(val&0x3F), 8); } else { ok &= FLAC__bitwriter_write_raw_uint32(bw, 0xFE, 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>30)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>24)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>18)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>12)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)((val>>6)&0x3F), 8); ok &= FLAC__bitwriter_write_raw_uint32(bw, 0x80 | (FLAC__uint32)(val&0x3F), 8); } return ok; } FLAC__bool FLAC__bitwriter_zero_pad_to_byte_boundary(FLAC__BitWriter *bw) { /* 0-pad to byte boundary */ if(bw->bits & 7u) return FLAC__bitwriter_write_zeroes(bw, 8 - (bw->bits & 7u)); else return true; } sources_5316/external/flac/READ_ME.TXT0000644000176700017670000000306311704065641016155 0ustar paulpaulPraats/external/flac/READ_ME.TXT Paul Boersma, May 13, 2008 This file describes the adaptations to the FLAC 1.2.1 sources that are needed to make them compatible with Praat. The .c and .h files are put into the single FLAC directory. The #include statements are flattened, e.g. #include private/float.h becomes #include flac_private_float.h. The FLaC__INLINE statement is turned into an inline statement in flac_share_alloc.h, and removed elsewhere (i.e. wherever there is a compiler message). For MinGW we need to change in flac_share_alloc.h: #if !defined _MSC_VER && !defined __EMX__ #include /* for SIZE_MAX in case limits.h didn't get it */ #endif For win32 on Metrowerks CodeWarrior we do a #if defined (_WIN32) && ! defined (off_t) #define off_t long #endif just above the declaration of FLAC__metadata_simple_iterator_get_block_offset; we also do #define fseeko fseek #define ftello ftell on win32 on Metrowerks CodeWarrior. This measure may be expendable once we compile on mingw or so. The sources contain a confusion of FLAC__int32 and int, especially in calls to local_bitreader_read_rice_signed_block or FLAC__bitreader_read_rice_signed_block; Some changes from int to FLAC__int32 may be necessary. We also have to insert Melder_assert (sizeof (int) == 4) in read_residual_partitioned_rice_. To ensure compatibility with international file names on Windows, the following is added to flac_FLAC_formant.h: #ifdef _WIN32 #include "melder.h" #define fopen(filename,mode) _wfopen (Melder_peekWcsToUtf16 (Melder_peekUtf8ToWcs (filename)), L"" mode) #endif sources_5316/external/flac/flac_private_stream_encoder_framing.h0000644000176700017670000000510210720607255024041 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__STREAM_ENCODER_FRAMING_H #define FLAC__PRIVATE__STREAM_ENCODER_FRAMING_H #include "flac_FLAC_format.h" #include "flac_private_bitwriter.h" FLAC__bool FLAC__add_metadata_block(const FLAC__StreamMetadata *metadata, FLAC__BitWriter *bw); FLAC__bool FLAC__frame_add_header(const FLAC__FrameHeader *header, FLAC__BitWriter *bw); FLAC__bool FLAC__subframe_add_constant(const FLAC__Subframe_Constant *subframe, unsigned subframe_bps, unsigned wasted_bits, FLAC__BitWriter *bw); FLAC__bool FLAC__subframe_add_fixed(const FLAC__Subframe_Fixed *subframe, unsigned residual_samples, unsigned subframe_bps, unsigned wasted_bits, FLAC__BitWriter *bw); FLAC__bool FLAC__subframe_add_lpc(const FLAC__Subframe_LPC *subframe, unsigned residual_samples, unsigned subframe_bps, unsigned wasted_bits, FLAC__BitWriter *bw); FLAC__bool FLAC__subframe_add_verbatim(const FLAC__Subframe_Verbatim *subframe, unsigned samples, unsigned subframe_bps, unsigned wasted_bits, FLAC__BitWriter *bw); #endif sources_5316/external/flac/flac_FLAC_stream_decoder.h0000644000176700017670000021156210720613046021363 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__STREAM_DECODER_H #define FLAC__STREAM_DECODER_H #include /* for FILE */ #include "flac_FLAC_export.h" #include "flac_FLAC_format.h" #ifdef __cplusplus extern "C" { #endif /** \file include/FLAC/stream_decoder.h * * \brief * This module contains the functions which implement the stream * decoder. * * See the detailed documentation in the * \link flac_stream_decoder stream decoder \endlink module. */ /** \defgroup flac_decoder FLAC/ \*_decoder.h: decoder interfaces * \ingroup flac * * \brief * This module describes the decoder layers provided by libFLAC. * * The stream decoder can be used to decode complete streams either from * the client via callbacks, or directly from a file, depending on how * it is initialized. When decoding via callbacks, the client provides * callbacks for reading FLAC data and writing decoded samples, and * handling metadata and errors. If the client also supplies seek-related * callback, the decoder function for sample-accurate seeking within the * FLAC input is also available. When decoding from a file, the client * needs only supply a filename or open \c FILE* and write/metadata/error * callbacks; the rest of the callbacks are supplied internally. For more * info see the \link flac_stream_decoder stream decoder \endlink module. */ /** \defgroup flac_stream_decoder FLAC/stream_decoder.h: stream decoder interface * \ingroup flac_decoder * * \brief * This module contains the functions which implement the stream * decoder. * * The stream decoder can decode native FLAC, and optionally Ogg FLAC * (check FLAC_API_SUPPORTS_OGG_FLAC) streams and files. * * The basic usage of this decoder is as follows: * - The program creates an instance of a decoder using * FLAC__stream_decoder_new(). * - The program overrides the default settings using * FLAC__stream_decoder_set_*() functions. * - The program initializes the instance to validate the settings and * prepare for decoding using * - FLAC__stream_decoder_init_stream() or FLAC__stream_decoder_init_FILE() * or FLAC__stream_decoder_init_file() for native FLAC, * - FLAC__stream_decoder_init_ogg_stream() or FLAC__stream_decoder_init_ogg_FILE() * or FLAC__stream_decoder_init_ogg_file() for Ogg FLAC * - The program calls the FLAC__stream_decoder_process_*() functions * to decode data, which subsequently calls the callbacks. * - The program finishes the decoding with FLAC__stream_decoder_finish(), * which flushes the input and output and resets the decoder to the * uninitialized state. * - The instance may be used again or deleted with * FLAC__stream_decoder_delete(). * * In more detail, the program will create a new instance by calling * FLAC__stream_decoder_new(), then call FLAC__stream_decoder_set_*() * functions to override the default decoder options, and call * one of the FLAC__stream_decoder_init_*() functions. * * There are three initialization functions for native FLAC, one for * setting up the decoder to decode FLAC data from the client via * callbacks, and two for decoding directly from a FLAC file. * * For decoding via callbacks, use FLAC__stream_decoder_init_stream(). * You must also supply several callbacks for handling I/O. Some (like * seeking) are optional, depending on the capabilities of the input. * * For decoding directly from a file, use FLAC__stream_decoder_init_FILE() * or FLAC__stream_decoder_init_file(). Then you must only supply an open * \c FILE* or filename and fewer callbacks; the decoder will handle * the other callbacks internally. * * There are three similarly-named init functions for decoding from Ogg * FLAC streams. Check \c FLAC_API_SUPPORTS_OGG_FLAC to find out if the * library has been built with Ogg support. * * Once the decoder is initialized, your program will call one of several * functions to start the decoding process: * * - FLAC__stream_decoder_process_single() - Tells the decoder to process at * most one metadata block or audio frame and return, calling either the * metadata callback or write callback, respectively, once. If the decoder * loses sync it will return with only the error callback being called. * - FLAC__stream_decoder_process_until_end_of_metadata() - Tells the decoder * to process the stream from the current location and stop upon reaching * the first audio frame. The client will get one metadata, write, or error * callback per metadata block, audio frame, or sync error, respectively. * - FLAC__stream_decoder_process_until_end_of_stream() - Tells the decoder * to process the stream from the current location until the read callback * returns FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM or * FLAC__STREAM_DECODER_READ_STATUS_ABORT. The client will get one metadata, * write, or error callback per metadata block, audio frame, or sync error, * respectively. * * When the decoder has finished decoding (normally or through an abort), * the instance is finished by calling FLAC__stream_decoder_finish(), which * ensures the decoder is in the correct state and frees memory. Then the * instance may be deleted with FLAC__stream_decoder_delete() or initialized * again to decode another stream. * * Seeking is exposed through the FLAC__stream_decoder_seek_absolute() method. * At any point after the stream decoder has been initialized, the client can * call this function to seek to an exact sample within the stream. * Subsequently, the first time the write callback is called it will be * passed a (possibly partial) block starting at that sample. * * If the client cannot seek via the callback interface provided, but still * has another way of seeking, it can flush the decoder using * FLAC__stream_decoder_flush() and start feeding data from the new position * through the read callback. * * The stream decoder also provides MD5 signature checking. If this is * turned on before initialization, FLAC__stream_decoder_finish() will * report when the decoded MD5 signature does not match the one stored * in the STREAMINFO block. MD5 checking is automatically turned off * (until the next FLAC__stream_decoder_reset()) if there is no signature * in the STREAMINFO block or when a seek is attempted. * * The FLAC__stream_decoder_set_metadata_*() functions deserve special * attention. By default, the decoder only calls the metadata_callback for * the STREAMINFO block. These functions allow you to tell the decoder * explicitly which blocks to parse and return via the metadata_callback * and/or which to skip. Use a FLAC__stream_decoder_set_metadata_respond_all(), * FLAC__stream_decoder_set_metadata_ignore() ... or FLAC__stream_decoder_set_metadata_ignore_all(), * FLAC__stream_decoder_set_metadata_respond() ... sequence to exactly specify * which blocks to return. Remember that metadata blocks can potentially * be big (for example, cover art) so filtering out the ones you don't * use can reduce the memory requirements of the decoder. Also note the * special forms FLAC__stream_decoder_set_metadata_respond_application(id) * and FLAC__stream_decoder_set_metadata_ignore_application(id) for * filtering APPLICATION blocks based on the application ID. * * STREAMINFO and SEEKTABLE blocks are always parsed and used internally, but * they still can legally be filtered from the metadata_callback. * * \note * The "set" functions may only be called when the decoder is in the * state FLAC__STREAM_DECODER_UNINITIALIZED, i.e. after * FLAC__stream_decoder_new() or FLAC__stream_decoder_finish(), but * before FLAC__stream_decoder_init_*(). If this is the case they will * return \c true, otherwise \c false. * * \note * FLAC__stream_decoder_finish() resets all settings to the constructor * defaults, including the callbacks. * * \{ */ /** State values for a FLAC__StreamDecoder * * The decoder's state can be obtained by calling FLAC__stream_decoder_get_state(). */ typedef enum { FLAC__STREAM_DECODER_SEARCH_FOR_METADATA = 0, /**< The decoder is ready to search for metadata. */ FLAC__STREAM_DECODER_READ_METADATA, /**< The decoder is ready to or is in the process of reading metadata. */ FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC, /**< The decoder is ready to or is in the process of searching for the * frame sync code. */ FLAC__STREAM_DECODER_READ_FRAME, /**< The decoder is ready to or is in the process of reading a frame. */ FLAC__STREAM_DECODER_END_OF_STREAM, /**< The decoder has reached the end of the stream. */ FLAC__STREAM_DECODER_OGG_ERROR, /**< An error occurred in the underlying Ogg layer. */ FLAC__STREAM_DECODER_SEEK_ERROR, /**< An error occurred while seeking. The decoder must be flushed * with FLAC__stream_decoder_flush() or reset with * FLAC__stream_decoder_reset() before decoding can continue. */ FLAC__STREAM_DECODER_ABORTED, /**< The decoder was aborted by the read callback. */ FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR, /**< An error occurred allocating memory. The decoder is in an invalid * state and can no longer be used. */ FLAC__STREAM_DECODER_UNINITIALIZED /**< The decoder is in the uninitialized state; one of the * FLAC__stream_decoder_init_*() functions must be called before samples * can be processed. */ } FLAC__StreamDecoderState; /** Maps a FLAC__StreamDecoderState to a C string. * * Using a FLAC__StreamDecoderState as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamDecoderStateString[]; /** Possible return values for the FLAC__stream_decoder_init_*() functions. */ typedef enum { FLAC__STREAM_DECODER_INIT_STATUS_OK = 0, /**< Initialization was successful. */ FLAC__STREAM_DECODER_INIT_STATUS_UNSUPPORTED_CONTAINER, /**< The library was not compiled with support for the given container * format. */ FLAC__STREAM_DECODER_INIT_STATUS_INVALID_CALLBACKS, /**< A required callback was not supplied. */ FLAC__STREAM_DECODER_INIT_STATUS_MEMORY_ALLOCATION_ERROR, /**< An error occurred allocating memory. */ FLAC__STREAM_DECODER_INIT_STATUS_ERROR_OPENING_FILE, /**< fopen() failed in FLAC__stream_decoder_init_file() or * FLAC__stream_decoder_init_ogg_file(). */ FLAC__STREAM_DECODER_INIT_STATUS_ALREADY_INITIALIZED /**< FLAC__stream_decoder_init_*() was called when the decoder was * already initialized, usually because * FLAC__stream_decoder_finish() was not called. */ } FLAC__StreamDecoderInitStatus; /** Maps a FLAC__StreamDecoderInitStatus to a C string. * * Using a FLAC__StreamDecoderInitStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamDecoderInitStatusString[]; /** Return values for the FLAC__StreamDecoder read callback. */ typedef enum { FLAC__STREAM_DECODER_READ_STATUS_CONTINUE, /**< The read was OK and decoding can continue. */ FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM, /**< The read was attempted while at the end of the stream. Note that * the client must only return this value when the read callback was * called when already at the end of the stream. Otherwise, if the read * itself moves to the end of the stream, the client should still return * the data and \c FLAC__STREAM_DECODER_READ_STATUS_CONTINUE, and then on * the next read callback it should return * \c FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM with a byte count * of \c 0. */ FLAC__STREAM_DECODER_READ_STATUS_ABORT /**< An unrecoverable error occurred. The decoder will return from the process call. */ } FLAC__StreamDecoderReadStatus; /** Maps a FLAC__StreamDecoderReadStatus to a C string. * * Using a FLAC__StreamDecoderReadStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamDecoderReadStatusString[]; /** Return values for the FLAC__StreamDecoder seek callback. */ typedef enum { FLAC__STREAM_DECODER_SEEK_STATUS_OK, /**< The seek was OK and decoding can continue. */ FLAC__STREAM_DECODER_SEEK_STATUS_ERROR, /**< An unrecoverable error occurred. The decoder will return from the process call. */ FLAC__STREAM_DECODER_SEEK_STATUS_UNSUPPORTED /**< Client does not support seeking. */ } FLAC__StreamDecoderSeekStatus; /** Maps a FLAC__StreamDecoderSeekStatus to a C string. * * Using a FLAC__StreamDecoderSeekStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamDecoderSeekStatusString[]; /** Return values for the FLAC__StreamDecoder tell callback. */ typedef enum { FLAC__STREAM_DECODER_TELL_STATUS_OK, /**< The tell was OK and decoding can continue. */ FLAC__STREAM_DECODER_TELL_STATUS_ERROR, /**< An unrecoverable error occurred. The decoder will return from the process call. */ FLAC__STREAM_DECODER_TELL_STATUS_UNSUPPORTED /**< Client does not support telling the position. */ } FLAC__StreamDecoderTellStatus; /** Maps a FLAC__StreamDecoderTellStatus to a C string. * * Using a FLAC__StreamDecoderTellStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamDecoderTellStatusString[]; /** Return values for the FLAC__StreamDecoder length callback. */ typedef enum { FLAC__STREAM_DECODER_LENGTH_STATUS_OK, /**< The length call was OK and decoding can continue. */ FLAC__STREAM_DECODER_LENGTH_STATUS_ERROR, /**< An unrecoverable error occurred. The decoder will return from the process call. */ FLAC__STREAM_DECODER_LENGTH_STATUS_UNSUPPORTED /**< Client does not support reporting the length. */ } FLAC__StreamDecoderLengthStatus; /** Maps a FLAC__StreamDecoderLengthStatus to a C string. * * Using a FLAC__StreamDecoderLengthStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamDecoderLengthStatusString[]; /** Return values for the FLAC__StreamDecoder write callback. */ typedef enum { FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE, /**< The write was OK and decoding can continue. */ FLAC__STREAM_DECODER_WRITE_STATUS_ABORT /**< An unrecoverable error occurred. The decoder will return from the process call. */ } FLAC__StreamDecoderWriteStatus; /** Maps a FLAC__StreamDecoderWriteStatus to a C string. * * Using a FLAC__StreamDecoderWriteStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamDecoderWriteStatusString[]; /** Possible values passed back to the FLAC__StreamDecoder error callback. * \c FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC is the generic catch- * all. The rest could be caused by bad sync (false synchronization on * data that is not the start of a frame) or corrupted data. The error * itself is the decoder's best guess at what happened assuming a correct * sync. For example \c FLAC__STREAM_DECODER_ERROR_STATUS_BAD_HEADER * could be caused by a correct sync on the start of a frame, but some * data in the frame header was corrupted. Or it could be the result of * syncing on a point the stream that looked like the starting of a frame * but was not. \c FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM * could be because the decoder encountered a valid frame made by a future * version of the encoder which it cannot parse, or because of a false * sync making it appear as though an encountered frame was generated by * a future encoder. */ typedef enum { FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC, /**< An error in the stream caused the decoder to lose synchronization. */ FLAC__STREAM_DECODER_ERROR_STATUS_BAD_HEADER, /**< The decoder encountered a corrupted frame header. */ FLAC__STREAM_DECODER_ERROR_STATUS_FRAME_CRC_MISMATCH, /**< The frame's data did not match the CRC in the footer. */ FLAC__STREAM_DECODER_ERROR_STATUS_UNPARSEABLE_STREAM /**< The decoder encountered reserved fields in use in the stream. */ } FLAC__StreamDecoderErrorStatus; /** Maps a FLAC__StreamDecoderErrorStatus to a C string. * * Using a FLAC__StreamDecoderErrorStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamDecoderErrorStatusString[]; /*********************************************************************** * * class FLAC__StreamDecoder * ***********************************************************************/ struct FLAC__StreamDecoderProtected; struct FLAC__StreamDecoderPrivate; /** The opaque structure definition for the stream decoder type. * See the \link flac_stream_decoder stream decoder module \endlink * for a detailed description. */ typedef struct FLAC__StreamDecoder { // ppgb 20071120 struct FLAC__StreamDecoderProtected *protected_; /* avoid the C++ keyword 'protected' */ struct FLAC__StreamDecoderPrivate *private_; /* avoid the C++ keyword 'private' */ } FLAC__StreamDecoder; /** Signature for the read callback. * * A function pointer matching this signature must be passed to * FLAC__stream_decoder_init*_stream(). The supplied function will be * called when the decoder needs more input data. The address of the * buffer to be filled is supplied, along with the number of bytes the * buffer can hold. The callback may choose to supply less data and * modify the byte count but must be careful not to overflow the buffer. * The callback then returns a status code chosen from * FLAC__StreamDecoderReadStatus. * * Here is an example of a read callback for stdio streams: * \code * FLAC__StreamDecoderReadStatus read_cb(const FLAC__StreamDecoder *decoder, FLAC__byte buffer[], size_t *bytes, void *client_data) * { * FILE *file = ((MyClientData*)client_data)->file; * if(*bytes > 0) { * *bytes = fread(buffer, sizeof(FLAC__byte), *bytes, file); * if(ferror(file)) * return FLAC__STREAM_DECODER_READ_STATUS_ABORT; * else if(*bytes == 0) * return FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM; * else * return FLAC__STREAM_DECODER_READ_STATUS_CONTINUE; * } * else * return FLAC__STREAM_DECODER_READ_STATUS_ABORT; * } * \endcode * * \note In general, FLAC__StreamDecoder functions which change the * state should not be called on the \a decoder while in the callback. * * \param decoder The decoder instance calling the callback. * \param buffer A pointer to a location for the callee to store * data to be decoded. * \param bytes A pointer to the size of the buffer. On entry * to the callback, it contains the maximum number * of bytes that may be stored in \a buffer. The * callee must set it to the actual number of bytes * stored (0 in case of error or end-of-stream) before * returning. * \param client_data The callee's client data set through * FLAC__stream_decoder_init_*(). * \retval FLAC__StreamDecoderReadStatus * The callee's return status. Note that the callback should return * \c FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM if and only if * zero bytes were read and there is no more data to be read. */ typedef FLAC__StreamDecoderReadStatus (*FLAC__StreamDecoderReadCallback)(const FLAC__StreamDecoder *decoder, FLAC__byte buffer[], size_t *bytes, void *client_data); /** Signature for the seek callback. * * A function pointer matching this signature may be passed to * FLAC__stream_decoder_init*_stream(). The supplied function will be * called when the decoder needs to seek the input stream. The decoder * will pass the absolute byte offset to seek to, 0 meaning the * beginning of the stream. * * Here is an example of a seek callback for stdio streams: * \code * FLAC__StreamDecoderSeekStatus seek_cb(const FLAC__StreamDecoder *decoder, FLAC__uint64 absolute_byte_offset, void *client_data) * { * FILE *file = ((MyClientData*)client_data)->file; * if(file == stdin) * return FLAC__STREAM_DECODER_SEEK_STATUS_UNSUPPORTED; * else if(fseeko(file, (off_t)absolute_byte_offset, SEEK_SET) < 0) * return FLAC__STREAM_DECODER_SEEK_STATUS_ERROR; * else * return FLAC__STREAM_DECODER_SEEK_STATUS_OK; * } * \endcode * * \note In general, FLAC__StreamDecoder functions which change the * state should not be called on the \a decoder while in the callback. * * \param decoder The decoder instance calling the callback. * \param absolute_byte_offset The offset from the beginning of the stream * to seek to. * \param client_data The callee's client data set through * FLAC__stream_decoder_init_*(). * \retval FLAC__StreamDecoderSeekStatus * The callee's return status. */ typedef FLAC__StreamDecoderSeekStatus (*FLAC__StreamDecoderSeekCallback)(const FLAC__StreamDecoder *decoder, FLAC__uint64 absolute_byte_offset, void *client_data); /** Signature for the tell callback. * * A function pointer matching this signature may be passed to * FLAC__stream_decoder_init*_stream(). The supplied function will be * called when the decoder wants to know the current position of the * stream. The callback should return the byte offset from the * beginning of the stream. * * Here is an example of a tell callback for stdio streams: * \code * FLAC__StreamDecoderTellStatus tell_cb(const FLAC__StreamDecoder *decoder, FLAC__uint64 *absolute_byte_offset, void *client_data) * { * FILE *file = ((MyClientData*)client_data)->file; * off_t pos; * if(file == stdin) * return FLAC__STREAM_DECODER_TELL_STATUS_UNSUPPORTED; * else if((pos = ftello(file)) < 0) * return FLAC__STREAM_DECODER_TELL_STATUS_ERROR; * else { * *absolute_byte_offset = (FLAC__uint64)pos; * return FLAC__STREAM_DECODER_TELL_STATUS_OK; * } * } * \endcode * * \note In general, FLAC__StreamDecoder functions which change the * state should not be called on the \a decoder while in the callback. * * \param decoder The decoder instance calling the callback. * \param absolute_byte_offset A pointer to storage for the current offset * from the beginning of the stream. * \param client_data The callee's client data set through * FLAC__stream_decoder_init_*(). * \retval FLAC__StreamDecoderTellStatus * The callee's return status. */ typedef FLAC__StreamDecoderTellStatus (*FLAC__StreamDecoderTellCallback)(const FLAC__StreamDecoder *decoder, FLAC__uint64 *absolute_byte_offset, void *client_data); /** Signature for the length callback. * * A function pointer matching this signature may be passed to * FLAC__stream_decoder_init*_stream(). The supplied function will be * called when the decoder wants to know the total length of the stream * in bytes. * * Here is an example of a length callback for stdio streams: * \code * FLAC__StreamDecoderLengthStatus length_cb(const FLAC__StreamDecoder *decoder, FLAC__uint64 *stream_length, void *client_data) * { * FILE *file = ((MyClientData*)client_data)->file; * struct stat filestats; * * if(file == stdin) * return FLAC__STREAM_DECODER_LENGTH_STATUS_UNSUPPORTED; * else if(fstat(fileno(file), &filestats) != 0) * return FLAC__STREAM_DECODER_LENGTH_STATUS_ERROR; * else { * *stream_length = (FLAC__uint64)filestats.st_size; * return FLAC__STREAM_DECODER_LENGTH_STATUS_OK; * } * } * \endcode * * \note In general, FLAC__StreamDecoder functions which change the * state should not be called on the \a decoder while in the callback. * * \param decoder The decoder instance calling the callback. * \param stream_length A pointer to storage for the length of the stream * in bytes. * \param client_data The callee's client data set through * FLAC__stream_decoder_init_*(). * \retval FLAC__StreamDecoderLengthStatus * The callee's return status. */ typedef FLAC__StreamDecoderLengthStatus (*FLAC__StreamDecoderLengthCallback)(const FLAC__StreamDecoder *decoder, FLAC__uint64 *stream_length, void *client_data); /** Signature for the EOF callback. * * A function pointer matching this signature may be passed to * FLAC__stream_decoder_init*_stream(). The supplied function will be * called when the decoder needs to know if the end of the stream has * been reached. * * Here is an example of a EOF callback for stdio streams: * FLAC__bool eof_cb(const FLAC__StreamDecoder *decoder, void *client_data) * \code * { * FILE *file = ((MyClientData*)client_data)->file; * return feof(file)? true : false; * } * \endcode * * \note In general, FLAC__StreamDecoder functions which change the * state should not be called on the \a decoder while in the callback. * * \param decoder The decoder instance calling the callback. * \param client_data The callee's client data set through * FLAC__stream_decoder_init_*(). * \retval FLAC__bool * \c true if the currently at the end of the stream, else \c false. */ typedef FLAC__bool (*FLAC__StreamDecoderEofCallback)(const FLAC__StreamDecoder *decoder, void *client_data); /** Signature for the write callback. * * A function pointer matching this signature must be passed to one of * the FLAC__stream_decoder_init_*() functions. * The supplied function will be called when the decoder has decoded a * single audio frame. The decoder will pass the frame metadata as well * as an array of pointers (one for each channel) pointing to the * decoded audio. * * \note In general, FLAC__StreamDecoder functions which change the * state should not be called on the \a decoder while in the callback. * * \param decoder The decoder instance calling the callback. * \param frame The description of the decoded frame. See * FLAC__Frame. * \param buffer An array of pointers to decoded channels of data. * Each pointer will point to an array of signed * samples of length \a frame->header.blocksize. * Channels will be ordered according to the FLAC * specification; see the documentation for the * frame header. * \param client_data The callee's client data set through * FLAC__stream_decoder_init_*(). * \retval FLAC__StreamDecoderWriteStatus * The callee's return status. */ typedef FLAC__StreamDecoderWriteStatus (*FLAC__StreamDecoderWriteCallback)(const FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer[], void *client_data); /** Signature for the metadata callback. * * A function pointer matching this signature must be passed to one of * the FLAC__stream_decoder_init_*() functions. * The supplied function will be called when the decoder has decoded a * metadata block. In a valid FLAC file there will always be one * \c STREAMINFO block, followed by zero or more other metadata blocks. * These will be supplied by the decoder in the same order as they * appear in the stream and always before the first audio frame (i.e. * write callback). The metadata block that is passed in must not be * modified, and it doesn't live beyond the callback, so you should make * a copy of it with FLAC__metadata_object_clone() if you will need it * elsewhere. Since metadata blocks can potentially be large, by * default the decoder only calls the metadata callback for the * \c STREAMINFO block; you can instruct the decoder to pass or filter * other blocks with FLAC__stream_decoder_set_metadata_*() calls. * * \note In general, FLAC__StreamDecoder functions which change the * state should not be called on the \a decoder while in the callback. * * \param decoder The decoder instance calling the callback. * \param metadata The decoded metadata block. * \param client_data The callee's client data set through * FLAC__stream_decoder_init_*(). */ typedef void (*FLAC__StreamDecoderMetadataCallback)(const FLAC__StreamDecoder *decoder, const FLAC__StreamMetadata *metadata, void *client_data); /** Signature for the error callback. * * A function pointer matching this signature must be passed to one of * the FLAC__stream_decoder_init_*() functions. * The supplied function will be called whenever an error occurs during * decoding. * * \note In general, FLAC__StreamDecoder functions which change the * state should not be called on the \a decoder while in the callback. * * \param decoder The decoder instance calling the callback. * \param status The error encountered by the decoder. * \param client_data The callee's client data set through * FLAC__stream_decoder_init_*(). */ typedef void (*FLAC__StreamDecoderErrorCallback)(const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data); /*********************************************************************** * * Class constructor/destructor * ***********************************************************************/ /** Create a new stream decoder instance. The instance is created with * default settings; see the individual FLAC__stream_decoder_set_*() * functions for each setting's default. * * \retval FLAC__StreamDecoder* * \c NULL if there was an error allocating memory, else the new instance. */ FLAC_API FLAC__StreamDecoder *FLAC__stream_decoder_new(void); /** Free a decoder instance. Deletes the object pointed to by \a decoder. * * \param decoder A pointer to an existing decoder. * \assert * \code decoder != NULL \endcode */ FLAC_API void FLAC__stream_decoder_delete(FLAC__StreamDecoder *decoder); /*********************************************************************** * * Public class method prototypes * ***********************************************************************/ /** Set the serial number for the FLAC stream within the Ogg container. * The default behavior is to use the serial number of the first Ogg * page. Setting a serial number here will explicitly specify which * stream is to be decoded. * * \note * This does not need to be set for native FLAC decoding. * * \default \c use serial number of first page * \param decoder A decoder instance to set. * \param serial_number See above. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c false if the decoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_decoder_set_ogg_serial_number(FLAC__StreamDecoder *decoder, long serial_number); /** Set the "MD5 signature checking" flag. If \c true, the decoder will * compute the MD5 signature of the unencoded audio data while decoding * and compare it to the signature from the STREAMINFO block, if it * exists, during FLAC__stream_decoder_finish(). * * MD5 signature checking will be turned off (until the next * FLAC__stream_decoder_reset()) if there is no signature in the * STREAMINFO block or when a seek is attempted. * * Clients that do not use the MD5 check should leave this off to speed * up decoding. * * \default \c false * \param decoder A decoder instance to set. * \param value Flag value (see above). * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c false if the decoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_decoder_set_md5_checking(FLAC__StreamDecoder *decoder, FLAC__bool value); /** Direct the decoder to pass on all metadata blocks of type \a type. * * \default By default, only the \c STREAMINFO block is returned via the * metadata callback. * \param decoder A decoder instance to set. * \param type See above. * \assert * \code decoder != NULL \endcode * \a type is valid * \retval FLAC__bool * \c false if the decoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_respond(FLAC__StreamDecoder *decoder, FLAC__MetadataType type); /** Direct the decoder to pass on all APPLICATION metadata blocks of the * given \a id. * * \default By default, only the \c STREAMINFO block is returned via the * metadata callback. * \param decoder A decoder instance to set. * \param id See above. * \assert * \code decoder != NULL \endcode * \code id != NULL \endcode * \retval FLAC__bool * \c false if the decoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_respond_application(FLAC__StreamDecoder *decoder, const FLAC__byte id[4]); /** Direct the decoder to pass on all metadata blocks of any type. * * \default By default, only the \c STREAMINFO block is returned via the * metadata callback. * \param decoder A decoder instance to set. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c false if the decoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_respond_all(FLAC__StreamDecoder *decoder); /** Direct the decoder to filter out all metadata blocks of type \a type. * * \default By default, only the \c STREAMINFO block is returned via the * metadata callback. * \param decoder A decoder instance to set. * \param type See above. * \assert * \code decoder != NULL \endcode * \a type is valid * \retval FLAC__bool * \c false if the decoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_ignore(FLAC__StreamDecoder *decoder, FLAC__MetadataType type); /** Direct the decoder to filter out all APPLICATION metadata blocks of * the given \a id. * * \default By default, only the \c STREAMINFO block is returned via the * metadata callback. * \param decoder A decoder instance to set. * \param id See above. * \assert * \code decoder != NULL \endcode * \code id != NULL \endcode * \retval FLAC__bool * \c false if the decoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_ignore_application(FLAC__StreamDecoder *decoder, const FLAC__byte id[4]); /** Direct the decoder to filter out all metadata blocks of any type. * * \default By default, only the \c STREAMINFO block is returned via the * metadata callback. * \param decoder A decoder instance to set. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c false if the decoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_decoder_set_metadata_ignore_all(FLAC__StreamDecoder *decoder); /** Get the current decoder state. * * \param decoder A decoder instance to query. * \assert * \code decoder != NULL \endcode * \retval FLAC__StreamDecoderState * The current decoder state. */ FLAC_API FLAC__StreamDecoderState FLAC__stream_decoder_get_state(const FLAC__StreamDecoder *decoder); /** Get the current decoder state as a C string. * * \param decoder A decoder instance to query. * \assert * \code decoder != NULL \endcode * \retval const char * * The decoder state as a C string. Do not modify the contents. */ FLAC_API const char *FLAC__stream_decoder_get_resolved_state_string(const FLAC__StreamDecoder *decoder); /** Get the "MD5 signature checking" flag. * This is the value of the setting, not whether or not the decoder is * currently checking the MD5 (remember, it can be turned off automatically * by a seek). When the decoder is reset the flag will be restored to the * value returned by this function. * * \param decoder A decoder instance to query. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * See above. */ FLAC_API FLAC__bool FLAC__stream_decoder_get_md5_checking(const FLAC__StreamDecoder *decoder); /** Get the total number of samples in the stream being decoded. * Will only be valid after decoding has started and will contain the * value from the \c STREAMINFO block. A value of \c 0 means "unknown". * * \param decoder A decoder instance to query. * \assert * \code decoder != NULL \endcode * \retval unsigned * See above. */ FLAC_API FLAC__uint64 FLAC__stream_decoder_get_total_samples(const FLAC__StreamDecoder *decoder); /** Get the current number of channels in the stream being decoded. * Will only be valid after decoding has started and will contain the * value from the most recently decoded frame header. * * \param decoder A decoder instance to query. * \assert * \code decoder != NULL \endcode * \retval unsigned * See above. */ FLAC_API unsigned FLAC__stream_decoder_get_channels(const FLAC__StreamDecoder *decoder); /** Get the current channel assignment in the stream being decoded. * Will only be valid after decoding has started and will contain the * value from the most recently decoded frame header. * * \param decoder A decoder instance to query. * \assert * \code decoder != NULL \endcode * \retval FLAC__ChannelAssignment * See above. */ FLAC_API FLAC__ChannelAssignment FLAC__stream_decoder_get_channel_assignment(const FLAC__StreamDecoder *decoder); /** Get the current sample resolution in the stream being decoded. * Will only be valid after decoding has started and will contain the * value from the most recently decoded frame header. * * \param decoder A decoder instance to query. * \assert * \code decoder != NULL \endcode * \retval unsigned * See above. */ FLAC_API unsigned FLAC__stream_decoder_get_bits_per_sample(const FLAC__StreamDecoder *decoder); /** Get the current sample rate in Hz of the stream being decoded. * Will only be valid after decoding has started and will contain the * value from the most recently decoded frame header. * * \param decoder A decoder instance to query. * \assert * \code decoder != NULL \endcode * \retval unsigned * See above. */ FLAC_API unsigned FLAC__stream_decoder_get_sample_rate(const FLAC__StreamDecoder *decoder); /** Get the current blocksize of the stream being decoded. * Will only be valid after decoding has started and will contain the * value from the most recently decoded frame header. * * \param decoder A decoder instance to query. * \assert * \code decoder != NULL \endcode * \retval unsigned * See above. */ FLAC_API unsigned FLAC__stream_decoder_get_blocksize(const FLAC__StreamDecoder *decoder); /** Returns the decoder's current read position within the stream. * The position is the byte offset from the start of the stream. * Bytes before this position have been fully decoded. Note that * there may still be undecoded bytes in the decoder's read FIFO. * The returned position is correct even after a seek. * * \warning This function currently only works for native FLAC, * not Ogg FLAC streams. * * \param decoder A decoder instance to query. * \param position Address at which to return the desired position. * \assert * \code decoder != NULL \endcode * \code position != NULL \endcode * \retval FLAC__bool * \c true if successful, \c false if the stream is not native FLAC, * or there was an error from the 'tell' callback or it returned * \c FLAC__STREAM_DECODER_TELL_STATUS_UNSUPPORTED. */ FLAC_API FLAC__bool FLAC__stream_decoder_get_decode_position(const FLAC__StreamDecoder *decoder, FLAC__uint64 *position); /** Initialize the decoder instance to decode native FLAC streams. * * This flavor of initialization sets up the decoder to decode from a * native FLAC stream. I/O is performed via callbacks to the client. * For decoding from a plain file via filename or open FILE*, * FLAC__stream_decoder_init_file() and FLAC__stream_decoder_init_FILE() * provide a simpler interface. * * This function should be called after FLAC__stream_decoder_new() and * FLAC__stream_decoder_set_*() but before any of the * FLAC__stream_decoder_process_*() functions. Will set and return the * decoder state, which will be FLAC__STREAM_DECODER_SEARCH_FOR_METADATA * if initialization succeeded. * * \param decoder An uninitialized decoder instance. * \param read_callback See FLAC__StreamDecoderReadCallback. This * pointer must not be \c NULL. * \param seek_callback See FLAC__StreamDecoderSeekCallback. This * pointer may be \c NULL if seeking is not * supported. If \a seek_callback is not \c NULL then a * \a tell_callback, \a length_callback, and \a eof_callback must also be supplied. * Alternatively, a dummy seek callback that just * returns \c FLAC__STREAM_DECODER_SEEK_STATUS_UNSUPPORTED * may also be supplied, all though this is slightly * less efficient for the decoder. * \param tell_callback See FLAC__StreamDecoderTellCallback. This * pointer may be \c NULL if not supported by the client. If * \a seek_callback is not \c NULL then a * \a tell_callback must also be supplied. * Alternatively, a dummy tell callback that just * returns \c FLAC__STREAM_DECODER_TELL_STATUS_UNSUPPORTED * may also be supplied, all though this is slightly * less efficient for the decoder. * \param length_callback See FLAC__StreamDecoderLengthCallback. This * pointer may be \c NULL if not supported by the client. If * \a seek_callback is not \c NULL then a * \a length_callback must also be supplied. * Alternatively, a dummy length callback that just * returns \c FLAC__STREAM_DECODER_LENGTH_STATUS_UNSUPPORTED * may also be supplied, all though this is slightly * less efficient for the decoder. * \param eof_callback See FLAC__StreamDecoderEofCallback. This * pointer may be \c NULL if not supported by the client. If * \a seek_callback is not \c NULL then a * \a eof_callback must also be supplied. * Alternatively, a dummy length callback that just * returns \c false * may also be supplied, all though this is slightly * less efficient for the decoder. * \param write_callback See FLAC__StreamDecoderWriteCallback. This * pointer must not be \c NULL. * \param metadata_callback See FLAC__StreamDecoderMetadataCallback. This * pointer may be \c NULL if the callback is not * desired. * \param error_callback See FLAC__StreamDecoderErrorCallback. This * pointer must not be \c NULL. * \param client_data This value will be supplied to callbacks in their * \a client_data argument. * \assert * \code decoder != NULL \endcode * \retval FLAC__StreamDecoderInitStatus * \c FLAC__STREAM_DECODER_INIT_STATUS_OK if initialization was successful; * see FLAC__StreamDecoderInitStatus for the meanings of other return values. */ FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_stream( FLAC__StreamDecoder *decoder, FLAC__StreamDecoderReadCallback read_callback, FLAC__StreamDecoderSeekCallback seek_callback, FLAC__StreamDecoderTellCallback tell_callback, FLAC__StreamDecoderLengthCallback length_callback, FLAC__StreamDecoderEofCallback eof_callback, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ); /** Initialize the decoder instance to decode Ogg FLAC streams. * * This flavor of initialization sets up the decoder to decode from a * FLAC stream in an Ogg container. I/O is performed via callbacks to the * client. For decoding from a plain file via filename or open FILE*, * FLAC__stream_decoder_init_ogg_file() and FLAC__stream_decoder_init_ogg_FILE() * provide a simpler interface. * * This function should be called after FLAC__stream_decoder_new() and * FLAC__stream_decoder_set_*() but before any of the * FLAC__stream_decoder_process_*() functions. Will set and return the * decoder state, which will be FLAC__STREAM_DECODER_SEARCH_FOR_METADATA * if initialization succeeded. * * \note Support for Ogg FLAC in the library is optional. If this * library has been built without support for Ogg FLAC, this function * will return \c FLAC__STREAM_DECODER_INIT_STATUS_UNSUPPORTED_CONTAINER. * * \param decoder An uninitialized decoder instance. * \param read_callback See FLAC__StreamDecoderReadCallback. This * pointer must not be \c NULL. * \param seek_callback See FLAC__StreamDecoderSeekCallback. This * pointer may be \c NULL if seeking is not * supported. If \a seek_callback is not \c NULL then a * \a tell_callback, \a length_callback, and \a eof_callback must also be supplied. * Alternatively, a dummy seek callback that just * returns \c FLAC__STREAM_DECODER_SEEK_STATUS_UNSUPPORTED * may also be supplied, all though this is slightly * less efficient for the decoder. * \param tell_callback See FLAC__StreamDecoderTellCallback. This * pointer may be \c NULL if not supported by the client. If * \a seek_callback is not \c NULL then a * \a tell_callback must also be supplied. * Alternatively, a dummy tell callback that just * returns \c FLAC__STREAM_DECODER_TELL_STATUS_UNSUPPORTED * may also be supplied, all though this is slightly * less efficient for the decoder. * \param length_callback See FLAC__StreamDecoderLengthCallback. This * pointer may be \c NULL if not supported by the client. If * \a seek_callback is not \c NULL then a * \a length_callback must also be supplied. * Alternatively, a dummy length callback that just * returns \c FLAC__STREAM_DECODER_LENGTH_STATUS_UNSUPPORTED * may also be supplied, all though this is slightly * less efficient for the decoder. * \param eof_callback See FLAC__StreamDecoderEofCallback. This * pointer may be \c NULL if not supported by the client. If * \a seek_callback is not \c NULL then a * \a eof_callback must also be supplied. * Alternatively, a dummy length callback that just * returns \c false * may also be supplied, all though this is slightly * less efficient for the decoder. * \param write_callback See FLAC__StreamDecoderWriteCallback. This * pointer must not be \c NULL. * \param metadata_callback See FLAC__StreamDecoderMetadataCallback. This * pointer may be \c NULL if the callback is not * desired. * \param error_callback See FLAC__StreamDecoderErrorCallback. This * pointer must not be \c NULL. * \param client_data This value will be supplied to callbacks in their * \a client_data argument. * \assert * \code decoder != NULL \endcode * \retval FLAC__StreamDecoderInitStatus * \c FLAC__STREAM_DECODER_INIT_STATUS_OK if initialization was successful; * see FLAC__StreamDecoderInitStatus for the meanings of other return values. */ FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_ogg_stream( FLAC__StreamDecoder *decoder, FLAC__StreamDecoderReadCallback read_callback, FLAC__StreamDecoderSeekCallback seek_callback, FLAC__StreamDecoderTellCallback tell_callback, FLAC__StreamDecoderLengthCallback length_callback, FLAC__StreamDecoderEofCallback eof_callback, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ); /** Initialize the decoder instance to decode native FLAC files. * * This flavor of initialization sets up the decoder to decode from a * plain native FLAC file. For non-stdio streams, you must use * FLAC__stream_decoder_init_stream() and provide callbacks for the I/O. * * This function should be called after FLAC__stream_decoder_new() and * FLAC__stream_decoder_set_*() but before any of the * FLAC__stream_decoder_process_*() functions. Will set and return the * decoder state, which will be FLAC__STREAM_DECODER_SEARCH_FOR_METADATA * if initialization succeeded. * * \param decoder An uninitialized decoder instance. * \param file An open FLAC file. The file should have been * opened with mode \c "rb" and rewound. The file * becomes owned by the decoder and should not be * manipulated by the client while decoding. * Unless \a file is \c stdin, it will be closed * when FLAC__stream_decoder_finish() is called. * Note however that seeking will not work when * decoding from \c stdout since it is not seekable. * \param write_callback See FLAC__StreamDecoderWriteCallback. This * pointer must not be \c NULL. * \param metadata_callback See FLAC__StreamDecoderMetadataCallback. This * pointer may be \c NULL if the callback is not * desired. * \param error_callback See FLAC__StreamDecoderErrorCallback. This * pointer must not be \c NULL. * \param client_data This value will be supplied to callbacks in their * \a client_data argument. * \assert * \code decoder != NULL \endcode * \code file != NULL \endcode * \retval FLAC__StreamDecoderInitStatus * \c FLAC__STREAM_DECODER_INIT_STATUS_OK if initialization was successful; * see FLAC__StreamDecoderInitStatus for the meanings of other return values. */ FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_FILE( FLAC__StreamDecoder *decoder, FILE *file, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ); /** Initialize the decoder instance to decode Ogg FLAC files. * * This flavor of initialization sets up the decoder to decode from a * plain Ogg FLAC file. For non-stdio streams, you must use * FLAC__stream_decoder_init_ogg_stream() and provide callbacks for the I/O. * * This function should be called after FLAC__stream_decoder_new() and * FLAC__stream_decoder_set_*() but before any of the * FLAC__stream_decoder_process_*() functions. Will set and return the * decoder state, which will be FLAC__STREAM_DECODER_SEARCH_FOR_METADATA * if initialization succeeded. * * \note Support for Ogg FLAC in the library is optional. If this * library has been built without support for Ogg FLAC, this function * will return \c FLAC__STREAM_DECODER_INIT_STATUS_UNSUPPORTED_CONTAINER. * * \param decoder An uninitialized decoder instance. * \param file An open FLAC file. The file should have been * opened with mode \c "rb" and rewound. The file * becomes owned by the decoder and should not be * manipulated by the client while decoding. * Unless \a file is \c stdin, it will be closed * when FLAC__stream_decoder_finish() is called. * Note however that seeking will not work when * decoding from \c stdout since it is not seekable. * \param write_callback See FLAC__StreamDecoderWriteCallback. This * pointer must not be \c NULL. * \param metadata_callback See FLAC__StreamDecoderMetadataCallback. This * pointer may be \c NULL if the callback is not * desired. * \param error_callback See FLAC__StreamDecoderErrorCallback. This * pointer must not be \c NULL. * \param client_data This value will be supplied to callbacks in their * \a client_data argument. * \assert * \code decoder != NULL \endcode * \code file != NULL \endcode * \retval FLAC__StreamDecoderInitStatus * \c FLAC__STREAM_DECODER_INIT_STATUS_OK if initialization was successful; * see FLAC__StreamDecoderInitStatus for the meanings of other return values. */ FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_ogg_FILE( FLAC__StreamDecoder *decoder, FILE *file, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ); /** Initialize the decoder instance to decode native FLAC files. * * This flavor of initialization sets up the decoder to decode from a plain * native FLAC file. If POSIX fopen() semantics are not sufficient, (for * example, with Unicode filenames on Windows), you must use * FLAC__stream_decoder_init_FILE(), or FLAC__stream_decoder_init_stream() * and provide callbacks for the I/O. * * This function should be called after FLAC__stream_decoder_new() and * FLAC__stream_decoder_set_*() but before any of the * FLAC__stream_decoder_process_*() functions. Will set and return the * decoder state, which will be FLAC__STREAM_DECODER_SEARCH_FOR_METADATA * if initialization succeeded. * * \param decoder An uninitialized decoder instance. * \param filename The name of the file to decode from. The file will * be opened with fopen(). Use \c NULL to decode from * \c stdin. Note that \c stdin is not seekable. * \param write_callback See FLAC__StreamDecoderWriteCallback. This * pointer must not be \c NULL. * \param metadata_callback See FLAC__StreamDecoderMetadataCallback. This * pointer may be \c NULL if the callback is not * desired. * \param error_callback See FLAC__StreamDecoderErrorCallback. This * pointer must not be \c NULL. * \param client_data This value will be supplied to callbacks in their * \a client_data argument. * \assert * \code decoder != NULL \endcode * \retval FLAC__StreamDecoderInitStatus * \c FLAC__STREAM_DECODER_INIT_STATUS_OK if initialization was successful; * see FLAC__StreamDecoderInitStatus for the meanings of other return values. */ FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_file( FLAC__StreamDecoder *decoder, const char *filename, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ); /** Initialize the decoder instance to decode Ogg FLAC files. * * This flavor of initialization sets up the decoder to decode from a plain * Ogg FLAC file. If POSIX fopen() semantics are not sufficient, (for * example, with Unicode filenames on Windows), you must use * FLAC__stream_decoder_init_ogg_FILE(), or FLAC__stream_decoder_init_ogg_stream() * and provide callbacks for the I/O. * * This function should be called after FLAC__stream_decoder_new() and * FLAC__stream_decoder_set_*() but before any of the * FLAC__stream_decoder_process_*() functions. Will set and return the * decoder state, which will be FLAC__STREAM_DECODER_SEARCH_FOR_METADATA * if initialization succeeded. * * \note Support for Ogg FLAC in the library is optional. If this * library has been built without support for Ogg FLAC, this function * will return \c FLAC__STREAM_DECODER_INIT_STATUS_UNSUPPORTED_CONTAINER. * * \param decoder An uninitialized decoder instance. * \param filename The name of the file to decode from. The file will * be opened with fopen(). Use \c NULL to decode from * \c stdin. Note that \c stdin is not seekable. * \param write_callback See FLAC__StreamDecoderWriteCallback. This * pointer must not be \c NULL. * \param metadata_callback See FLAC__StreamDecoderMetadataCallback. This * pointer may be \c NULL if the callback is not * desired. * \param error_callback See FLAC__StreamDecoderErrorCallback. This * pointer must not be \c NULL. * \param client_data This value will be supplied to callbacks in their * \a client_data argument. * \assert * \code decoder != NULL \endcode * \retval FLAC__StreamDecoderInitStatus * \c FLAC__STREAM_DECODER_INIT_STATUS_OK if initialization was successful; * see FLAC__StreamDecoderInitStatus for the meanings of other return values. */ FLAC_API FLAC__StreamDecoderInitStatus FLAC__stream_decoder_init_ogg_file( FLAC__StreamDecoder *decoder, const char *filename, FLAC__StreamDecoderWriteCallback write_callback, FLAC__StreamDecoderMetadataCallback metadata_callback, FLAC__StreamDecoderErrorCallback error_callback, void *client_data ); /** Finish the decoding process. * Flushes the decoding buffer, releases resources, resets the decoder * settings to their defaults, and returns the decoder state to * FLAC__STREAM_DECODER_UNINITIALIZED. * * In the event of a prematurely-terminated decode, it is not strictly * necessary to call this immediately before FLAC__stream_decoder_delete() * but it is good practice to match every FLAC__stream_decoder_init_*() * with a FLAC__stream_decoder_finish(). * * \param decoder An uninitialized decoder instance. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c false if MD5 checking is on AND a STREAMINFO block was available * AND the MD5 signature in the STREAMINFO block was non-zero AND the * signature does not match the one computed by the decoder; else * \c true. */ FLAC_API FLAC__bool FLAC__stream_decoder_finish(FLAC__StreamDecoder *decoder); /** Flush the stream input. * The decoder's input buffer will be cleared and the state set to * \c FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC. This will also turn * off MD5 checking. * * \param decoder A decoder instance. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c true if successful, else \c false if a memory allocation * error occurs (in which case the state will be set to * \c FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR). */ FLAC_API FLAC__bool FLAC__stream_decoder_flush(FLAC__StreamDecoder *decoder); /** Reset the decoding process. * The decoder's input buffer will be cleared and the state set to * \c FLAC__STREAM_DECODER_SEARCH_FOR_METADATA. This is similar to * FLAC__stream_decoder_finish() except that the settings are * preserved; there is no need to call FLAC__stream_decoder_init_*() * before decoding again. MD5 checking will be restored to its original * setting. * * If the decoder is seekable, or was initialized with * FLAC__stream_decoder_init*_FILE() or FLAC__stream_decoder_init*_file(), * the decoder will also attempt to seek to the beginning of the file. * If this rewind fails, this function will return \c false. It follows * that FLAC__stream_decoder_reset() cannot be used when decoding from * \c stdin. * * If the decoder was initialized with FLAC__stream_encoder_init*_stream() * and is not seekable (i.e. no seek callback was provided or the seek * callback returns \c FLAC__STREAM_DECODER_SEEK_STATUS_UNSUPPORTED), it * is the duty of the client to start feeding data from the beginning of * the stream on the next FLAC__stream_decoder_process() or * FLAC__stream_decoder_process_interleaved() call. * * \param decoder A decoder instance. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c true if successful, else \c false if a memory allocation occurs * (in which case the state will be set to * \c FLAC__STREAM_DECODER_MEMORY_ALLOCATION_ERROR) or a seek error * occurs (the state will be unchanged). */ FLAC_API FLAC__bool FLAC__stream_decoder_reset(FLAC__StreamDecoder *decoder); /** Decode one metadata block or audio frame. * This version instructs the decoder to decode a either a single metadata * block or a single frame and stop, unless the callbacks return a fatal * error or the read callback returns * \c FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM. * * As the decoder needs more input it will call the read callback. * Depending on what was decoded, the metadata or write callback will be * called with the decoded metadata block or audio frame. * * Unless there is a fatal read error or end of stream, this function * will return once one whole frame is decoded. In other words, if the * stream is not synchronized or points to a corrupt frame header, the * decoder will continue to try and resync until it gets to a valid * frame, then decode one frame, then return. If the decoder points to * a frame whose frame CRC in the frame footer does not match the * computed frame CRC, this function will issue a * FLAC__STREAM_DECODER_ERROR_STATUS_FRAME_CRC_MISMATCH error to the * error callback, and return, having decoded one complete, although * corrupt, frame. (Such corrupted frames are sent as silence of the * correct length to the write callback.) * * \param decoder An initialized decoder instance. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c false if any fatal read, write, or memory allocation error * occurred (meaning decoding must stop), else \c true; for more * information about the decoder, check the decoder state with * FLAC__stream_decoder_get_state(). */ FLAC_API FLAC__bool FLAC__stream_decoder_process_single(FLAC__StreamDecoder *decoder); /** Decode until the end of the metadata. * This version instructs the decoder to decode from the current position * and continue until all the metadata has been read, or until the * callbacks return a fatal error or the read callback returns * \c FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM. * * As the decoder needs more input it will call the read callback. * As each metadata block is decoded, the metadata callback will be called * with the decoded metadata. * * \param decoder An initialized decoder instance. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c false if any fatal read, write, or memory allocation error * occurred (meaning decoding must stop), else \c true; for more * information about the decoder, check the decoder state with * FLAC__stream_decoder_get_state(). */ FLAC_API FLAC__bool FLAC__stream_decoder_process_until_end_of_metadata(FLAC__StreamDecoder *decoder); /** Decode until the end of the stream. * This version instructs the decoder to decode from the current position * and continue until the end of stream (the read callback returns * \c FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM), or until the * callbacks return a fatal error. * * As the decoder needs more input it will call the read callback. * As each metadata block and frame is decoded, the metadata or write * callback will be called with the decoded metadata or frame. * * \param decoder An initialized decoder instance. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c false if any fatal read, write, or memory allocation error * occurred (meaning decoding must stop), else \c true; for more * information about the decoder, check the decoder state with * FLAC__stream_decoder_get_state(). */ FLAC_API FLAC__bool FLAC__stream_decoder_process_until_end_of_stream(FLAC__StreamDecoder *decoder); /** Skip one audio frame. * This version instructs the decoder to 'skip' a single frame and stop, * unless the callbacks return a fatal error or the read callback returns * \c FLAC__STREAM_DECODER_READ_STATUS_END_OF_STREAM. * * The decoding flow is the same as what occurs when * FLAC__stream_decoder_process_single() is called to process an audio * frame, except that this function does not decode the parsed data into * PCM or call the write callback. The integrity of the frame is still * checked the same way as in the other process functions. * * This function will return once one whole frame is skipped, in the * same way that FLAC__stream_decoder_process_single() will return once * one whole frame is decoded. * * This function can be used in more quickly determining FLAC frame * boundaries when decoding of the actual data is not needed, for * example when an application is separating a FLAC stream into frames * for editing or storing in a container. To do this, the application * can use FLAC__stream_decoder_skip_single_frame() to quickly advance * to the next frame, then use * FLAC__stream_decoder_get_decode_position() to find the new frame * boundary. * * This function should only be called when the stream has advanced * past all the metadata, otherwise it will return \c false. * * \param decoder An initialized decoder instance not in a metadata * state. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c false if any fatal read, write, or memory allocation error * occurred (meaning decoding must stop), or if the decoder * is in the FLAC__STREAM_DECODER_SEARCH_FOR_METADATA or * FLAC__STREAM_DECODER_READ_METADATA state, else \c true; for more * information about the decoder, check the decoder state with * FLAC__stream_decoder_get_state(). */ FLAC_API FLAC__bool FLAC__stream_decoder_skip_single_frame(FLAC__StreamDecoder *decoder); /** Flush the input and seek to an absolute sample. * Decoding will resume at the given sample. Note that because of * this, the next write callback may contain a partial block. The * client must support seeking the input or this function will fail * and return \c false. Furthermore, if the decoder state is * \c FLAC__STREAM_DECODER_SEEK_ERROR, then the decoder must be flushed * with FLAC__stream_decoder_flush() or reset with * FLAC__stream_decoder_reset() before decoding can continue. * * \param decoder A decoder instance. * \param sample The target sample number to seek to. * \assert * \code decoder != NULL \endcode * \retval FLAC__bool * \c true if successful, else \c false. */ FLAC_API FLAC__bool FLAC__stream_decoder_seek_absolute(FLAC__StreamDecoder *decoder, FLAC__uint64 sample); /* \} */ #ifdef __cplusplus } #endif #endif sources_5316/external/flac/flac_FLAC_stream_encoder.h0000644000176700017670000023560210720612770021401 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2000,2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__STREAM_ENCODER_H #define FLAC__STREAM_ENCODER_H #include /* for FILE */ #include "flac_FLAC_export.h" #include "flac_FLAC_format.h" #include "flac_FLAC_stream_decoder.h" #ifdef __cplusplus extern "C" { #endif /** \file include/FLAC/stream_encoder.h * * \brief * This module contains the functions which implement the stream * encoder. * * See the detailed documentation in the * \link flac_stream_encoder stream encoder \endlink module. */ /** \defgroup flac_encoder FLAC/ \*_encoder.h: encoder interfaces * \ingroup flac * * \brief * This module describes the encoder layers provided by libFLAC. * * The stream encoder can be used to encode complete streams either to the * client via callbacks, or directly to a file, depending on how it is * initialized. When encoding via callbacks, the client provides a write * callback which will be called whenever FLAC data is ready to be written. * If the client also supplies a seek callback, the encoder will also * automatically handle the writing back of metadata discovered while * encoding, like stream info, seek points offsets, etc. When encoding to * a file, the client needs only supply a filename or open \c FILE* and an * optional progress callback for periodic notification of progress; the * write and seek callbacks are supplied internally. For more info see the * \link flac_stream_encoder stream encoder \endlink module. */ /** \defgroup flac_stream_encoder FLAC/stream_encoder.h: stream encoder interface * \ingroup flac_encoder * * \brief * This module contains the functions which implement the stream * encoder. * * The stream encoder can encode to native FLAC, and optionally Ogg FLAC * (check FLAC_API_SUPPORTS_OGG_FLAC) streams and files. * * The basic usage of this encoder is as follows: * - The program creates an instance of an encoder using * FLAC__stream_encoder_new(). * - The program overrides the default settings using * FLAC__stream_encoder_set_*() functions. At a minimum, the following * functions should be called: * - FLAC__stream_encoder_set_channels() * - FLAC__stream_encoder_set_bits_per_sample() * - FLAC__stream_encoder_set_sample_rate() * - FLAC__stream_encoder_set_ogg_serial_number() (if encoding to Ogg FLAC) * - FLAC__stream_encoder_set_total_samples_estimate() (if known) * - If the application wants to control the compression level or set its own * metadata, then the following should also be called: * - FLAC__stream_encoder_set_compression_level() * - FLAC__stream_encoder_set_verify() * - FLAC__stream_encoder_set_metadata() * - The rest of the set functions should only be called if the client needs * exact control over how the audio is compressed; thorough understanding * of the FLAC format is necessary to achieve good results. * - The program initializes the instance to validate the settings and * prepare for encoding using * - FLAC__stream_encoder_init_stream() or FLAC__stream_encoder_init_FILE() * or FLAC__stream_encoder_init_file() for native FLAC * - FLAC__stream_encoder_init_ogg_stream() or FLAC__stream_encoder_init_ogg_FILE() * or FLAC__stream_encoder_init_ogg_file() for Ogg FLAC * - The program calls FLAC__stream_encoder_process() or * FLAC__stream_encoder_process_interleaved() to encode data, which * subsequently calls the callbacks when there is encoder data ready * to be written. * - The program finishes the encoding with FLAC__stream_encoder_finish(), * which causes the encoder to encode any data still in its input pipe, * update the metadata with the final encoding statistics if output * seeking is possible, and finally reset the encoder to the * uninitialized state. * - The instance may be used again or deleted with * FLAC__stream_encoder_delete(). * * In more detail, the stream encoder functions similarly to the * \link flac_stream_decoder stream decoder \endlink, but has fewer * callbacks and more options. Typically the client will create a new * instance by calling FLAC__stream_encoder_new(), then set the necessary * parameters with FLAC__stream_encoder_set_*(), and initialize it by * calling one of the FLAC__stream_encoder_init_*() functions. * * Unlike the decoders, the stream encoder has many options that can * affect the speed and compression ratio. When setting these parameters * you should have some basic knowledge of the format (see the * user-level documentation * or the formal description). The * FLAC__stream_encoder_set_*() functions themselves do not validate the * values as many are interdependent. The FLAC__stream_encoder_init_*() * functions will do this, so make sure to pay attention to the state * returned by FLAC__stream_encoder_init_*() to make sure that it is * FLAC__STREAM_ENCODER_INIT_STATUS_OK. Any parameters that are not set * before FLAC__stream_encoder_init_*() will take on the defaults from * the constructor. * * There are three initialization functions for native FLAC, one for * setting up the encoder to encode FLAC data to the client via * callbacks, and two for encoding directly to a file. * * For encoding via callbacks, use FLAC__stream_encoder_init_stream(). * You must also supply a write callback which will be called anytime * there is raw encoded data to write. If the client can seek the output * it is best to also supply seek and tell callbacks, as this allows the * encoder to go back after encoding is finished to write back * information that was collected while encoding, like seek point offsets, * frame sizes, etc. * * For encoding directly to a file, use FLAC__stream_encoder_init_FILE() * or FLAC__stream_encoder_init_file(). Then you must only supply a * filename or open \c FILE*; the encoder will handle all the callbacks * internally. You may also supply a progress callback for periodic * notification of the encoding progress. * * There are three similarly-named init functions for encoding to Ogg * FLAC streams. Check \c FLAC_API_SUPPORTS_OGG_FLAC to find out if the * library has been built with Ogg support. * * The call to FLAC__stream_encoder_init_*() currently will also immediately * call the write callback several times, once with the \c fLaC signature, * and once for each encoded metadata block. Note that for Ogg FLAC * encoding you will usually get at least twice the number of callbacks than * with native FLAC, one for the Ogg page header and one for the page body. * * After initializing the instance, the client may feed audio data to the * encoder in one of two ways: * * - Channel separate, through FLAC__stream_encoder_process() - The client * will pass an array of pointers to buffers, one for each channel, to * the encoder, each of the same length. The samples need not be * block-aligned, but each channel should have the same number of samples. * - Channel interleaved, through * FLAC__stream_encoder_process_interleaved() - The client will pass a single * pointer to data that is channel-interleaved (i.e. channel0_sample0, * channel1_sample0, ... , channelN_sample0, channel0_sample1, ...). * Again, the samples need not be block-aligned but they must be * sample-aligned, i.e. the first value should be channel0_sample0 and * the last value channelN_sampleM. * * Note that for either process call, each sample in the buffers should be a * signed integer, right-justified to the resolution set by * FLAC__stream_encoder_set_bits_per_sample(). For example, if the resolution * is 16 bits per sample, the samples should all be in the range [-32768,32767]. * * When the client is finished encoding data, it calls * FLAC__stream_encoder_finish(), which causes the encoder to encode any * data still in its input pipe, and call the metadata callback with the * final encoding statistics. Then the instance may be deleted with * FLAC__stream_encoder_delete() or initialized again to encode another * stream. * * For programs that write their own metadata, but that do not know the * actual metadata until after encoding, it is advantageous to instruct * the encoder to write a PADDING block of the correct size, so that * instead of rewriting the whole stream after encoding, the program can * just overwrite the PADDING block. If only the maximum size of the * metadata is known, the program can write a slightly larger padding * block, then split it after encoding. * * Make sure you understand how lengths are calculated. All FLAC metadata * blocks have a 4 byte header which contains the type and length. This * length does not include the 4 bytes of the header. See the format page * for the specification of metadata blocks and their lengths. * * \note * If you are writing the FLAC data to a file via callbacks, make sure it * is open for update (e.g. mode "w+" for stdio streams). This is because * after the first encoding pass, the encoder will try to seek back to the * beginning of the stream, to the STREAMINFO block, to write some data * there. (If using FLAC__stream_encoder_init*_file() or * FLAC__stream_encoder_init*_FILE(), the file is managed internally.) * * \note * The "set" functions may only be called when the encoder is in the * state FLAC__STREAM_ENCODER_UNINITIALIZED, i.e. after * FLAC__stream_encoder_new() or FLAC__stream_encoder_finish(), but * before FLAC__stream_encoder_init_*(). If this is the case they will * return \c true, otherwise \c false. * * \note * FLAC__stream_encoder_finish() resets all settings to the constructor * defaults. * * \{ */ /** State values for a FLAC__StreamEncoder. * * The encoder's state can be obtained by calling FLAC__stream_encoder_get_state(). * * If the encoder gets into any other state besides \c FLAC__STREAM_ENCODER_OK * or \c FLAC__STREAM_ENCODER_UNINITIALIZED, it becomes invalid for encoding and * must be deleted with FLAC__stream_encoder_delete(). */ typedef enum { FLAC__STREAM_ENCODER_OK = 0, /**< The encoder is in the normal OK state and samples can be processed. */ FLAC__STREAM_ENCODER_UNINITIALIZED, /**< The encoder is in the uninitialized state; one of the * FLAC__stream_encoder_init_*() functions must be called before samples * can be processed. */ FLAC__STREAM_ENCODER_OGG_ERROR, /**< An error occurred in the underlying Ogg layer. */ FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR, /**< An error occurred in the underlying verify stream decoder; * check FLAC__stream_encoder_get_verify_decoder_state(). */ FLAC__STREAM_ENCODER_VERIFY_MISMATCH_IN_AUDIO_DATA, /**< The verify decoder detected a mismatch between the original * audio signal and the decoded audio signal. */ FLAC__STREAM_ENCODER_CLIENT_ERROR, /**< One of the callbacks returned a fatal error. */ FLAC__STREAM_ENCODER_IO_ERROR, /**< An I/O error occurred while opening/reading/writing a file. * Check \c errno. */ FLAC__STREAM_ENCODER_FRAMING_ERROR, /**< An error occurred while writing the stream; usually, the * write_callback returned an error. */ FLAC__STREAM_ENCODER_MEMORY_ALLOCATION_ERROR /**< Memory allocation failed. */ } FLAC__StreamEncoderState; /** Maps a FLAC__StreamEncoderState to a C string. * * Using a FLAC__StreamEncoderState as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamEncoderStateString[]; /** Possible return values for the FLAC__stream_encoder_init_*() functions. */ typedef enum { FLAC__STREAM_ENCODER_INIT_STATUS_OK = 0, /**< Initialization was successful. */ FLAC__STREAM_ENCODER_INIT_STATUS_ENCODER_ERROR, /**< General failure to set up encoder; call FLAC__stream_encoder_get_state() for cause. */ FLAC__STREAM_ENCODER_INIT_STATUS_UNSUPPORTED_CONTAINER, /**< The library was not compiled with support for the given container * format. */ FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_CALLBACKS, /**< A required callback was not supplied. */ FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_NUMBER_OF_CHANNELS, /**< The encoder has an invalid setting for number of channels. */ FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_BITS_PER_SAMPLE, /**< The encoder has an invalid setting for bits-per-sample. * FLAC supports 4-32 bps but the reference encoder currently supports * only up to 24 bps. */ FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_SAMPLE_RATE, /**< The encoder has an invalid setting for the input sample rate. */ FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_BLOCK_SIZE, /**< The encoder has an invalid setting for the block size. */ FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_MAX_LPC_ORDER, /**< The encoder has an invalid setting for the maximum LPC order. */ FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_QLP_COEFF_PRECISION, /**< The encoder has an invalid setting for the precision of the quantized linear predictor coefficients. */ FLAC__STREAM_ENCODER_INIT_STATUS_BLOCK_SIZE_TOO_SMALL_FOR_LPC_ORDER, /**< The specified block size is less than the maximum LPC order. */ FLAC__STREAM_ENCODER_INIT_STATUS_NOT_STREAMABLE, /**< The encoder is bound to the Subset but other settings violate it. */ FLAC__STREAM_ENCODER_INIT_STATUS_INVALID_METADATA, /**< The metadata input to the encoder is invalid, in one of the following ways: * - FLAC__stream_encoder_set_metadata() was called with a null pointer but a block count > 0 * - One of the metadata blocks contains an undefined type * - It contains an illegal CUESHEET as checked by FLAC__format_cuesheet_is_legal() * - It contains an illegal SEEKTABLE as checked by FLAC__format_seektable_is_legal() * - It contains more than one SEEKTABLE block or more than one VORBIS_COMMENT block */ FLAC__STREAM_ENCODER_INIT_STATUS_ALREADY_INITIALIZED /**< FLAC__stream_encoder_init_*() was called when the encoder was * already initialized, usually because * FLAC__stream_encoder_finish() was not called. */ } FLAC__StreamEncoderInitStatus; /** Maps a FLAC__StreamEncoderInitStatus to a C string. * * Using a FLAC__StreamEncoderInitStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamEncoderInitStatusString[]; /** Return values for the FLAC__StreamEncoder read callback. */ typedef enum { FLAC__STREAM_ENCODER_READ_STATUS_CONTINUE, /**< The read was OK and decoding can continue. */ FLAC__STREAM_ENCODER_READ_STATUS_END_OF_STREAM, /**< The read was attempted at the end of the stream. */ FLAC__STREAM_ENCODER_READ_STATUS_ABORT, /**< An unrecoverable error occurred. */ FLAC__STREAM_ENCODER_READ_STATUS_UNSUPPORTED /**< Client does not support reading back from the output. */ } FLAC__StreamEncoderReadStatus; /** Maps a FLAC__StreamEncoderReadStatus to a C string. * * Using a FLAC__StreamEncoderReadStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamEncoderReadStatusString[]; /** Return values for the FLAC__StreamEncoder write callback. */ typedef enum { FLAC__STREAM_ENCODER_WRITE_STATUS_OK = 0, /**< The write was OK and encoding can continue. */ FLAC__STREAM_ENCODER_WRITE_STATUS_FATAL_ERROR /**< An unrecoverable error occurred. The encoder will return from the process call. */ } FLAC__StreamEncoderWriteStatus; /** Maps a FLAC__StreamEncoderWriteStatus to a C string. * * Using a FLAC__StreamEncoderWriteStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamEncoderWriteStatusString[]; /** Return values for the FLAC__StreamEncoder seek callback. */ typedef enum { FLAC__STREAM_ENCODER_SEEK_STATUS_OK, /**< The seek was OK and encoding can continue. */ FLAC__STREAM_ENCODER_SEEK_STATUS_ERROR, /**< An unrecoverable error occurred. */ FLAC__STREAM_ENCODER_SEEK_STATUS_UNSUPPORTED /**< Client does not support seeking. */ } FLAC__StreamEncoderSeekStatus; /** Maps a FLAC__StreamEncoderSeekStatus to a C string. * * Using a FLAC__StreamEncoderSeekStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamEncoderSeekStatusString[]; /** Return values for the FLAC__StreamEncoder tell callback. */ typedef enum { FLAC__STREAM_ENCODER_TELL_STATUS_OK, /**< The tell was OK and encoding can continue. */ FLAC__STREAM_ENCODER_TELL_STATUS_ERROR, /**< An unrecoverable error occurred. */ FLAC__STREAM_ENCODER_TELL_STATUS_UNSUPPORTED /**< Client does not support seeking. */ } FLAC__StreamEncoderTellStatus; /** Maps a FLAC__StreamEncoderTellStatus to a C string. * * Using a FLAC__StreamEncoderTellStatus as the index to this array * will give the string equivalent. The contents should not be modified. */ extern FLAC_API const char * const FLAC__StreamEncoderTellStatusString[]; /*********************************************************************** * * class FLAC__StreamEncoder * ***********************************************************************/ struct FLAC__StreamEncoderProtected; struct FLAC__StreamEncoderPrivate; /** The opaque structure definition for the stream encoder type. * See the \link flac_stream_encoder stream encoder module \endlink * for a detailed description. */ typedef struct FLAC__StreamEncoder { // ppgb 20071120 struct FLAC__StreamEncoderProtected *protected_; /* avoid the C++ keyword 'protected' */ struct FLAC__StreamEncoderPrivate *private_; /* avoid the C++ keyword 'private' */ } FLAC__StreamEncoder; /** Signature for the read callback. * * A function pointer matching this signature must be passed to * FLAC__stream_encoder_init_ogg_stream() if seeking is supported. * The supplied function will be called when the encoder needs to read back * encoded data. This happens during the metadata callback, when the encoder * has to read, modify, and rewrite the metadata (e.g. seekpoints) gathered * while encoding. The address of the buffer to be filled is supplied, along * with the number of bytes the buffer can hold. The callback may choose to * supply less data and modify the byte count but must be careful not to * overflow the buffer. The callback then returns a status code chosen from * FLAC__StreamEncoderReadStatus. * * Here is an example of a read callback for stdio streams: * \code * FLAC__StreamEncoderReadStatus read_cb(const FLAC__StreamEncoder *encoder, FLAC__byte buffer[], size_t *bytes, void *client_data) * { * FILE *file = ((MyClientData*)client_data)->file; * if(*bytes > 0) { * *bytes = fread(buffer, sizeof(FLAC__byte), *bytes, file); * if(ferror(file)) * return FLAC__STREAM_ENCODER_READ_STATUS_ABORT; * else if(*bytes == 0) * return FLAC__STREAM_ENCODER_READ_STATUS_END_OF_STREAM; * else * return FLAC__STREAM_ENCODER_READ_STATUS_CONTINUE; * } * else * return FLAC__STREAM_ENCODER_READ_STATUS_ABORT; * } * \endcode * * \note In general, FLAC__StreamEncoder functions which change the * state should not be called on the \a encoder while in the callback. * * \param encoder The encoder instance calling the callback. * \param buffer A pointer to a location for the callee to store * data to be encoded. * \param bytes A pointer to the size of the buffer. On entry * to the callback, it contains the maximum number * of bytes that may be stored in \a buffer. The * callee must set it to the actual number of bytes * stored (0 in case of error or end-of-stream) before * returning. * \param client_data The callee's client data set through * FLAC__stream_encoder_set_client_data(). * \retval FLAC__StreamEncoderReadStatus * The callee's return status. */ typedef FLAC__StreamEncoderReadStatus (*FLAC__StreamEncoderReadCallback)(const FLAC__StreamEncoder *encoder, FLAC__byte buffer[], size_t *bytes, void *client_data); /** Signature for the write callback. * * A function pointer matching this signature must be passed to * FLAC__stream_encoder_init*_stream(). The supplied function will be called * by the encoder anytime there is raw encoded data ready to write. It may * include metadata mixed with encoded audio frames and the data is not * guaranteed to be aligned on frame or metadata block boundaries. * * The only duty of the callback is to write out the \a bytes worth of data * in \a buffer to the current position in the output stream. The arguments * \a samples and \a current_frame are purely informational. If \a samples * is greater than \c 0, then \a current_frame will hold the current frame * number that is being written; otherwise it indicates that the write * callback is being called to write metadata. * * \note * Unlike when writing to native FLAC, when writing to Ogg FLAC the * write callback will be called twice when writing each audio * frame; once for the page header, and once for the page body. * When writing the page header, the \a samples argument to the * write callback will be \c 0. * * \note In general, FLAC__StreamEncoder functions which change the * state should not be called on the \a encoder while in the callback. * * \param encoder The encoder instance calling the callback. * \param buffer An array of encoded data of length \a bytes. * \param bytes The byte length of \a buffer. * \param samples The number of samples encoded by \a buffer. * \c 0 has a special meaning; see above. * \param current_frame The number of the current frame being encoded. * \param client_data The callee's client data set through * FLAC__stream_encoder_init_*(). * \retval FLAC__StreamEncoderWriteStatus * The callee's return status. */ typedef FLAC__StreamEncoderWriteStatus (*FLAC__StreamEncoderWriteCallback)(const FLAC__StreamEncoder *encoder, const FLAC__byte buffer[], size_t bytes, unsigned samples, unsigned current_frame, void *client_data); /** Signature for the seek callback. * * A function pointer matching this signature may be passed to * FLAC__stream_encoder_init*_stream(). The supplied function will be called * when the encoder needs to seek the output stream. The encoder will pass * the absolute byte offset to seek to, 0 meaning the beginning of the stream. * * Here is an example of a seek callback for stdio streams: * \code * FLAC__StreamEncoderSeekStatus seek_cb(const FLAC__StreamEncoder *encoder, FLAC__uint64 absolute_byte_offset, void *client_data) * { * FILE *file = ((MyClientData*)client_data)->file; * if(file == stdin) * return FLAC__STREAM_ENCODER_SEEK_STATUS_UNSUPPORTED; * else if(fseeko(file, (off_t)absolute_byte_offset, SEEK_SET) < 0) * return FLAC__STREAM_ENCODER_SEEK_STATUS_ERROR; * else * return FLAC__STREAM_ENCODER_SEEK_STATUS_OK; * } * \endcode * * \note In general, FLAC__StreamEncoder functions which change the * state should not be called on the \a encoder while in the callback. * * \param encoder The encoder instance calling the callback. * \param absolute_byte_offset The offset from the beginning of the stream * to seek to. * \param client_data The callee's client data set through * FLAC__stream_encoder_init_*(). * \retval FLAC__StreamEncoderSeekStatus * The callee's return status. */ typedef FLAC__StreamEncoderSeekStatus (*FLAC__StreamEncoderSeekCallback)(const FLAC__StreamEncoder *encoder, FLAC__uint64 absolute_byte_offset, void *client_data); /** Signature for the tell callback. * * A function pointer matching this signature may be passed to * FLAC__stream_encoder_init*_stream(). The supplied function will be called * when the encoder needs to know the current position of the output stream. * * \warning * The callback must return the true current byte offset of the output to * which the encoder is writing. If you are buffering the output, make * sure and take this into account. If you are writing directly to a * FILE* from your write callback, ftell() is sufficient. If you are * writing directly to a file descriptor from your write callback, you * can use lseek(fd, SEEK_CUR, 0). The encoder may later seek back to * these points to rewrite metadata after encoding. * * Here is an example of a tell callback for stdio streams: * \code * FLAC__StreamEncoderTellStatus tell_cb(const FLAC__StreamEncoder *encoder, FLAC__uint64 *absolute_byte_offset, void *client_data) * { * FILE *file = ((MyClientData*)client_data)->file; * off_t pos; * if(file == stdin) * return FLAC__STREAM_ENCODER_TELL_STATUS_UNSUPPORTED; * else if((pos = ftello(file)) < 0) * return FLAC__STREAM_ENCODER_TELL_STATUS_ERROR; * else { * *absolute_byte_offset = (FLAC__uint64)pos; * return FLAC__STREAM_ENCODER_TELL_STATUS_OK; * } * } * \endcode * * \note In general, FLAC__StreamEncoder functions which change the * state should not be called on the \a encoder while in the callback. * * \param encoder The encoder instance calling the callback. * \param absolute_byte_offset The address at which to store the current * position of the output. * \param client_data The callee's client data set through * FLAC__stream_encoder_init_*(). * \retval FLAC__StreamEncoderTellStatus * The callee's return status. */ typedef FLAC__StreamEncoderTellStatus (*FLAC__StreamEncoderTellCallback)(const FLAC__StreamEncoder *encoder, FLAC__uint64 *absolute_byte_offset, void *client_data); /** Signature for the metadata callback. * * A function pointer matching this signature may be passed to * FLAC__stream_encoder_init*_stream(). The supplied function will be called * once at the end of encoding with the populated STREAMINFO structure. This * is so the client can seek back to the beginning of the file and write the * STREAMINFO block with the correct statistics after encoding (like * minimum/maximum frame size and total samples). * * \note In general, FLAC__StreamEncoder functions which change the * state should not be called on the \a encoder while in the callback. * * \param encoder The encoder instance calling the callback. * \param metadata The final populated STREAMINFO block. * \param client_data The callee's client data set through * FLAC__stream_encoder_init_*(). */ typedef void (*FLAC__StreamEncoderMetadataCallback)(const FLAC__StreamEncoder *encoder, const FLAC__StreamMetadata *metadata, void *client_data); /** Signature for the progress callback. * * A function pointer matching this signature may be passed to * FLAC__stream_encoder_init*_file() or FLAC__stream_encoder_init*_FILE(). * The supplied function will be called when the encoder has finished * writing a frame. The \c total_frames_estimate argument to the * callback will be based on the value from * FLAC__stream_encoder_set_total_samples_estimate(). * * \note In general, FLAC__StreamEncoder functions which change the * state should not be called on the \a encoder while in the callback. * * \param encoder The encoder instance calling the callback. * \param bytes_written Bytes written so far. * \param samples_written Samples written so far. * \param frames_written Frames written so far. * \param total_frames_estimate The estimate of the total number of * frames to be written. * \param client_data The callee's client data set through * FLAC__stream_encoder_init_*(). */ typedef void (*FLAC__StreamEncoderProgressCallback)(const FLAC__StreamEncoder *encoder, FLAC__uint64 bytes_written, FLAC__uint64 samples_written, unsigned frames_written, unsigned total_frames_estimate, void *client_data); /*********************************************************************** * * Class constructor/destructor * ***********************************************************************/ /** Create a new stream encoder instance. The instance is created with * default settings; see the individual FLAC__stream_encoder_set_*() * functions for each setting's default. * * \retval FLAC__StreamEncoder* * \c NULL if there was an error allocating memory, else the new instance. */ FLAC_API FLAC__StreamEncoder *FLAC__stream_encoder_new(void); /** Free an encoder instance. Deletes the object pointed to by \a encoder. * * \param encoder A pointer to an existing encoder. * \assert * \code encoder != NULL \endcode */ FLAC_API void FLAC__stream_encoder_delete(FLAC__StreamEncoder *encoder); /*********************************************************************** * * Public class method prototypes * ***********************************************************************/ /** Set the serial number for the FLAC stream to use in the Ogg container. * * \note * This does not need to be set for native FLAC encoding. * * \note * It is recommended to set a serial number explicitly as the default of '0' * may collide with other streams. * * \default \c 0 * \param encoder An encoder instance to set. * \param serial_number See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_ogg_serial_number(FLAC__StreamEncoder *encoder, long serial_number); /** Set the "verify" flag. If \c true, the encoder will verify it's own * encoded output by feeding it through an internal decoder and comparing * the original signal against the decoded signal. If a mismatch occurs, * the process call will return \c false. Note that this will slow the * encoding process by the extra time required for decoding and comparison. * * \default \c false * \param encoder An encoder instance to set. * \param value Flag value (see above). * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_verify(FLAC__StreamEncoder *encoder, FLAC__bool value); /** Set the Subset flag. If \c true, * the encoder will comply with the Subset and will check the * settings during FLAC__stream_encoder_init_*() to see if all settings * comply. If \c false, the settings may take advantage of the full * range that the format allows. * * Make sure you know what it entails before setting this to \c false. * * \default \c true * \param encoder An encoder instance to set. * \param value Flag value (see above). * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_streamable_subset(FLAC__StreamEncoder *encoder, FLAC__bool value); /** Set the number of channels to be encoded. * * \default \c 2 * \param encoder An encoder instance to set. * \param value See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_channels(FLAC__StreamEncoder *encoder, unsigned value); /** Set the sample resolution of the input to be encoded. * * \warning * Do not feed the encoder data that is wider than the value you * set here or you will generate an invalid stream. * * \default \c 16 * \param encoder An encoder instance to set. * \param value See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_bits_per_sample(FLAC__StreamEncoder *encoder, unsigned value); /** Set the sample rate (in Hz) of the input to be encoded. * * \default \c 44100 * \param encoder An encoder instance to set. * \param value See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_sample_rate(FLAC__StreamEncoder *encoder, unsigned value); /** Set the compression level * * The compression level is roughly proportional to the amount of effort * the encoder expends to compress the file. A higher level usually * means more computation but higher compression. The default level is * suitable for most applications. * * Currently the levels range from \c 0 (fastest, least compression) to * \c 8 (slowest, most compression). A value larger than \c 8 will be * treated as \c 8. * * This function automatically calls the following other \c _set_ * functions with appropriate values, so the client does not need to * unless it specifically wants to override them: * - FLAC__stream_encoder_set_do_mid_side_stereo() * - FLAC__stream_encoder_set_loose_mid_side_stereo() * - FLAC__stream_encoder_set_apodization() * - FLAC__stream_encoder_set_max_lpc_order() * - FLAC__stream_encoder_set_qlp_coeff_precision() * - FLAC__stream_encoder_set_do_qlp_coeff_prec_search() * - FLAC__stream_encoder_set_do_escape_coding() * - FLAC__stream_encoder_set_do_exhaustive_model_search() * - FLAC__stream_encoder_set_min_residual_partition_order() * - FLAC__stream_encoder_set_max_residual_partition_order() * - FLAC__stream_encoder_set_rice_parameter_search_dist() * * The actual values set for each level are: *

* * * * * * * * * * * *
level * do mid-side stereo * loose mid-side stereo * apodization * max lpc order * qlp coeff precision * qlp coeff prec search * escape coding * exhaustive model search * min residual partition order * max residual partition order * rice parameter search dist *
0 false false tukey(0.5) 0 0 false false false 0 3 0
1 true true tukey(0.5) 0 0 false false false 0 3 0
2 true false tukey(0.5) 0 0 false false false 0 3 0
3 false false tukey(0.5) 6 0 false false false 0 4 0
4 true true tukey(0.5) 8 0 false false false 0 4 0
5 true false tukey(0.5) 8 0 false false false 0 5 0
6 true false tukey(0.5) 8 0 false false false 0 6 0
7 true false tukey(0.5) 8 0 false false true 0 6 0
8 true false tukey(0.5) 12 0 false false true 0 6 0
* * \default \c 5 * \param encoder An encoder instance to set. * \param value See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_compression_level(FLAC__StreamEncoder *encoder, unsigned value); /** Set the blocksize to use while encoding. * * The number of samples to use per frame. Use \c 0 to let the encoder * estimate a blocksize; this is usually best. * * \default \c 0 * \param encoder An encoder instance to set. * \param value See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_blocksize(FLAC__StreamEncoder *encoder, unsigned value); /** Set to \c true to enable mid-side encoding on stereo input. The * number of channels must be 2 for this to have any effect. Set to * \c false to use only independent channel coding. * * \default \c false * \param encoder An encoder instance to set. * \param value Flag value (see above). * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_do_mid_side_stereo(FLAC__StreamEncoder *encoder, FLAC__bool value); /** Set to \c true to enable adaptive switching between mid-side and * left-right encoding on stereo input. Set to \c false to use * exhaustive searching. Setting this to \c true requires * FLAC__stream_encoder_set_do_mid_side_stereo() to also be set to * \c true in order to have any effect. * * \default \c false * \param encoder An encoder instance to set. * \param value Flag value (see above). * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_loose_mid_side_stereo(FLAC__StreamEncoder *encoder, FLAC__bool value); /** Sets the apodization function(s) the encoder will use when windowing * audio data for LPC analysis. * * The \a specification is a plain ASCII string which specifies exactly * which functions to use. There may be more than one (up to 32), * separated by \c ';' characters. Some functions take one or more * comma-separated arguments in parentheses. * * The available functions are \c bartlett, \c bartlett_hann, * \c blackman, \c blackman_harris_4term_92db, \c connes, \c flattop, * \c gauss(STDDEV), \c hamming, \c hann, \c kaiser_bessel, \c nuttall, * \c rectangle, \c triangle, \c tukey(P), \c welch. * * For \c gauss(STDDEV), STDDEV specifies the standard deviation * (0blocksize / (2 ^ order). * * Set both min and max values to \c 0 to force a single context, * whose Rice parameter is based on the residual signal variance. * Otherwise, set a min and max order, and the encoder will search * all orders, using the mean of each context for its Rice parameter, * and use the best. * * \default \c 0 * \param encoder An encoder instance to set. * \param value See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_min_residual_partition_order(FLAC__StreamEncoder *encoder, unsigned value); /** Set the maximum partition order to search when coding the residual. * This is used in tandem with * FLAC__stream_encoder_set_min_residual_partition_order(). * * The partition order determines the context size in the residual. * The context size will be approximately blocksize / (2 ^ order). * * Set both min and max values to \c 0 to force a single context, * whose Rice parameter is based on the residual signal variance. * Otherwise, set a min and max order, and the encoder will search * all orders, using the mean of each context for its Rice parameter, * and use the best. * * \default \c 0 * \param encoder An encoder instance to set. * \param value See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_max_residual_partition_order(FLAC__StreamEncoder *encoder, unsigned value); /** Deprecated. Setting this value has no effect. * * \default \c 0 * \param encoder An encoder instance to set. * \param value See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_rice_parameter_search_dist(FLAC__StreamEncoder *encoder, unsigned value); /** Set an estimate of the total samples that will be encoded. * This is merely an estimate and may be set to \c 0 if unknown. * This value will be written to the STREAMINFO block before encoding, * and can remove the need for the caller to rewrite the value later * if the value is known before encoding. * * \default \c 0 * \param encoder An encoder instance to set. * \param value See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_total_samples_estimate(FLAC__StreamEncoder *encoder, FLAC__uint64 value); /** Set the metadata blocks to be emitted to the stream before encoding. * A value of \c NULL, \c 0 implies no metadata; otherwise, supply an * array of pointers to metadata blocks. The array is non-const since * the encoder may need to change the \a is_last flag inside them, and * in some cases update seek point offsets. Otherwise, the encoder will * not modify or free the blocks. It is up to the caller to free the * metadata blocks after encoding finishes. * * \note * The encoder stores only copies of the pointers in the \a metadata array; * the metadata blocks themselves must survive at least until after * FLAC__stream_encoder_finish() returns. Do not free the blocks until then. * * \note * The STREAMINFO block is always written and no STREAMINFO block may * occur in the supplied array. * * \note * By default the encoder does not create a SEEKTABLE. If one is supplied * in the \a metadata array, but the client has specified that it does not * support seeking, then the SEEKTABLE will be written verbatim. However * by itself this is not very useful as the client will not know the stream * offsets for the seekpoints ahead of time. In order to get a proper * seektable the client must support seeking. See next note. * * \note * SEEKTABLE blocks are handled specially. Since you will not know * the values for the seek point stream offsets, you should pass in * a SEEKTABLE 'template', that is, a SEEKTABLE object with the * required sample numbers (or placeholder points), with \c 0 for the * \a frame_samples and \a stream_offset fields for each point. If the * client has specified that it supports seeking by providing a seek * callback to FLAC__stream_encoder_init_stream() or both seek AND read * callback to FLAC__stream_encoder_init_ogg_stream() (or by using * FLAC__stream_encoder_init*_file() or FLAC__stream_encoder_init*_FILE()), * then while it is encoding the encoder will fill the stream offsets in * for you and when encoding is finished, it will seek back and write the * real values into the SEEKTABLE block in the stream. There are helper * routines for manipulating seektable template blocks; see metadata.h: * FLAC__metadata_object_seektable_template_*(). If the client does * not support seeking, the SEEKTABLE will have inaccurate offsets which * will slow down or remove the ability to seek in the FLAC stream. * * \note * The encoder instance \b will modify the first \c SEEKTABLE block * as it transforms the template to a valid seektable while encoding, * but it is still up to the caller to free all metadata blocks after * encoding. * * \note * A VORBIS_COMMENT block may be supplied. The vendor string in it * will be ignored. libFLAC will use it's own vendor string. libFLAC * will not modify the passed-in VORBIS_COMMENT's vendor string, it * will simply write it's own into the stream. If no VORBIS_COMMENT * block is present in the \a metadata array, libFLAC will write an * empty one, containing only the vendor string. * * \note The Ogg FLAC mapping requires that the VORBIS_COMMENT block be * the second metadata block of the stream. The encoder already supplies * the STREAMINFO block automatically. If \a metadata does not contain a * VORBIS_COMMENT block, the encoder will supply that too. Otherwise, if * \a metadata does contain a VORBIS_COMMENT block and it is not the * first, the init function will reorder \a metadata by moving the * VORBIS_COMMENT block to the front; the relative ordering of the other * blocks will remain as they were. * * \note The Ogg FLAC mapping limits the number of metadata blocks per * stream to \c 65535. If \a num_blocks exceeds this the function will * return \c false. * * \default \c NULL, 0 * \param encoder An encoder instance to set. * \param metadata See above. * \param num_blocks See above. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * \c false if the encoder is already initialized, else \c true. * \c false if the encoder is already initialized, or if * \a num_blocks > 65535 if encoding to Ogg FLAC, else \c true. */ FLAC_API FLAC__bool FLAC__stream_encoder_set_metadata(FLAC__StreamEncoder *encoder, FLAC__StreamMetadata **metadata, unsigned num_blocks); /** Get the current encoder state. * * \param encoder An encoder instance to query. * \assert * \code encoder != NULL \endcode * \retval FLAC__StreamEncoderState * The current encoder state. */ FLAC_API FLAC__StreamEncoderState FLAC__stream_encoder_get_state(const FLAC__StreamEncoder *encoder); /** Get the state of the verify stream decoder. * Useful when the stream encoder state is * \c FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR. * * \param encoder An encoder instance to query. * \assert * \code encoder != NULL \endcode * \retval FLAC__StreamDecoderState * The verify stream decoder state. */ FLAC_API FLAC__StreamDecoderState FLAC__stream_encoder_get_verify_decoder_state(const FLAC__StreamEncoder *encoder); /** Get the current encoder state as a C string. * This version automatically resolves * \c FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR by getting the * verify decoder's state. * * \param encoder A encoder instance to query. * \assert * \code encoder != NULL \endcode * \retval const char * * The encoder state as a C string. Do not modify the contents. */ FLAC_API const char *FLAC__stream_encoder_get_resolved_state_string(const FLAC__StreamEncoder *encoder); /** Get relevant values about the nature of a verify decoder error. * Useful when the stream encoder state is * \c FLAC__STREAM_ENCODER_VERIFY_DECODER_ERROR. The arguments should * be addresses in which the stats will be returned, or NULL if value * is not desired. * * \param encoder An encoder instance to query. * \param absolute_sample The absolute sample number of the mismatch. * \param frame_number The number of the frame in which the mismatch occurred. * \param channel The channel in which the mismatch occurred. * \param sample The number of the sample (relative to the frame) in * which the mismatch occurred. * \param expected The expected value for the sample in question. * \param got The actual value returned by the decoder. * \assert * \code encoder != NULL \endcode */ FLAC_API void FLAC__stream_encoder_get_verify_decoder_error_stats(const FLAC__StreamEncoder *encoder, FLAC__uint64 *absolute_sample, unsigned *frame_number, unsigned *channel, unsigned *sample, FLAC__int32 *expected, FLAC__int32 *got); /** Get the "verify" flag. * * \param encoder An encoder instance to query. * \assert * \code encoder != NULL \endcode * \retval FLAC__bool * See FLAC__stream_encoder_set_verify(). */ FLAC_API FLAC__bool FLAC__stream_encoder_get_verify(const FLAC__StreamEncoder *encoder); /** Get the frame header. * * \param encoder An initialized encoder instance in the OK state. * \param buffer An array of pointers to each channel's signal. * \param samples The number of samples in one channel. * \assert * \code encoder != NULL \endcode * \code FLAC__stream_encoder_get_state(encoder) == FLAC__STREAM_ENCODER_OK \endcode * \retval FLAC__bool * \c true if successful, else \c false; in this case, check the * encoder state with FLAC__stream_encoder_get_state() to see what * went wrong. */ FLAC_API FLAC__bool FLAC__stream_encoder_process(FLAC__StreamEncoder *encoder, const FLAC__int32 * const buffer[], unsigned samples); /** Submit data for encoding. * This version allows you to supply the input data where the channels * are interleaved into a single array (i.e. channel0_sample0, * channel1_sample0, ... , channelN_sample0, channel0_sample1, ...). * The samples need not be block-aligned but they must be * sample-aligned, i.e. the first value should be channel0_sample0 * and the last value channelN_sampleM. Each sample should be a signed * integer, right-justified to the resolution set by * FLAC__stream_encoder_set_bits_per_sample(). For example, if the * resolution is 16 bits per sample, the samples should all be in the * range [-32768,32767]. * * For applications where channel order is important, channels must * follow the order as described in the * frame header. * * \param encoder An initialized encoder instance in the OK state. * \param buffer An array of channel-interleaved data (see above). * \param samples The number of samples in one channel, the same as for * FLAC__stream_encoder_process(). For example, if * encoding two channels, \c 1000 \a samples corresponds * to a \a buffer of 2000 values. * \assert * \code encoder != NULL \endcode * \code FLAC__stream_encoder_get_state(encoder) == FLAC__STREAM_ENCODER_OK \endcode * \retval FLAC__bool * \c true if successful, else \c false; in this case, check the * encoder state with FLAC__stream_encoder_get_state() to see what * went wrong. */ FLAC_API FLAC__bool FLAC__stream_encoder_process_interleaved(FLAC__StreamEncoder *encoder, const FLAC__int32 buffer[], unsigned samples); /* \} */ #ifdef __cplusplus } #endif #endif sources_5316/external/flac/flac_private_memory.h0000644000176700017670000000530010720607255020654 0ustar paulpaul/* libFLAC - Free Lossless Audio Codec library * Copyright (C) 2001,2002,2003,2004,2005,2006,2007 Josh Coalson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * - Neither the name of the Xiph.org Foundation nor the names of its * contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #ifndef FLAC__PRIVATE__MEMORY_H #define FLAC__PRIVATE__MEMORY_H #ifdef HAVE_CONFIG_H #include #endif #include /* for size_t */ #include "flac_private_float.h" #include "flac_FLAC_ordinals.h" /* for FLAC__bool */ /* Returns the unaligned address returned by malloc. * Use free() on this address to deallocate. */ void *FLAC__memory_alloc_aligned(size_t bytes, void **aligned_address); FLAC__bool FLAC__memory_alloc_aligned_int32_array(unsigned elements, FLAC__int32 **unaligned_pointer, FLAC__int32 **aligned_pointer); FLAC__bool FLAC__memory_alloc_aligned_uint32_array(unsigned elements, FLAC__uint32 **unaligned_pointer, FLAC__uint32 **aligned_pointer); FLAC__bool FLAC__memory_alloc_aligned_uint64_array(unsigned elements, FLAC__uint64 **unaligned_pointer, FLAC__uint64 **aligned_pointer); FLAC__bool FLAC__memory_alloc_aligned_unsigned_array(unsigned elements, unsigned **unaligned_pointer, unsigned **aligned_pointer); #ifndef FLAC__INTEGER_ONLY_LIBRARY FLAC__bool FLAC__memory_alloc_aligned_real_array(unsigned elements, FLAC__real **unaligned_pointer, FLAC__real **aligned_pointer); #endif #endif sources_5316/external/gsl/0000755000176700017670000000000011755136555014347 5ustar paulpaulsources_5316/external/gsl/gsl_cblas__chpr2.c0000664000176700017670000000054111723710247017672 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_chpr2 (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *Ap) { #define BASE float #include "gsl_cblas__source_hpr2.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__gamma.c0000664000176700017670000016660411723710247020475 0ustar paulpaul/* specfunc/gamma.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_log.h" #include "gsl_sf_psi.h" #include "gsl_sf_trig.h" #include "gsl_sf_gamma.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__check.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" #define LogRootTwoPi_ 0.9189385332046727418 /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ static struct {int n; double f; long i; } fact_table[GSL_SF_FACT_NMAX + 1] = { { 0, 1.0, 1L }, { 1, 1.0, 1L }, { 2, 2.0, 2L }, { 3, 6.0, 6L }, { 4, 24.0, 24L }, { 5, 120.0, 120L }, { 6, 720.0, 720L }, { 7, 5040.0, 5040L }, { 8, 40320.0, 40320L }, { 9, 362880.0, 362880L }, { 10, 3628800.0, 3628800L }, { 11, 39916800.0, 39916800L }, { 12, 479001600.0, 479001600L }, { 13, 6227020800.0, 0 }, { 14, 87178291200.0, 0 }, { 15, 1307674368000.0, 0 }, { 16, 20922789888000.0, 0 }, { 17, 355687428096000.0, 0 }, { 18, 6402373705728000.0, 0 }, { 19, 121645100408832000.0, 0 }, { 20, 2432902008176640000.0, 0 }, { 21, 51090942171709440000.0, 0 }, { 22, 1124000727777607680000.0, 0 }, { 23, 25852016738884976640000.0, 0 }, { 24, 620448401733239439360000.0, 0 }, { 25, 15511210043330985984000000.0, 0 }, { 26, 403291461126605635584000000.0, 0 }, { 27, 10888869450418352160768000000.0, 0 }, { 28, 304888344611713860501504000000.0, 0 }, { 29, 8841761993739701954543616000000.0, 0 }, { 30, 265252859812191058636308480000000.0, 0 }, { 31, 8222838654177922817725562880000000.0, 0 }, { 32, 263130836933693530167218012160000000.0, 0 }, { 33, 8683317618811886495518194401280000000.0, 0 }, { 34, 2.95232799039604140847618609644e38, 0 }, { 35, 1.03331479663861449296666513375e40, 0 }, { 36, 3.71993326789901217467999448151e41, 0 }, { 37, 1.37637530912263450463159795816e43, 0 }, { 38, 5.23022617466601111760007224100e44, 0 }, { 39, 2.03978820811974433586402817399e46, 0 }, { 40, 8.15915283247897734345611269600e47, 0 }, { 41, 3.34525266131638071081700620534e49, 0 }, { 42, 1.40500611775287989854314260624e51, 0 }, { 43, 6.04152630633738356373551320685e52, 0 }, { 44, 2.65827157478844876804362581101e54, 0 }, { 45, 1.19622220865480194561963161496e56, 0 }, { 46, 5.50262215981208894985030542880e57, 0 }, { 47, 2.58623241511168180642964355154e59, 0 }, { 48, 1.24139155925360726708622890474e61, 0 }, { 49, 6.08281864034267560872252163321e62, 0 }, { 50, 3.04140932017133780436126081661e64, 0 }, { 51, 1.55111875328738228022424301647e66, 0 }, { 52, 8.06581751709438785716606368564e67, 0 }, { 53, 4.27488328406002556429801375339e69, 0 }, { 54, 2.30843697339241380472092742683e71, 0 }, { 55, 1.26964033536582759259651008476e73, 0 }, { 56, 7.10998587804863451854045647464e74, 0 }, { 57, 4.05269195048772167556806019054e76, 0 }, { 58, 2.35056133128287857182947491052e78, 0 }, { 59, 1.38683118545689835737939019720e80, 0 }, { 60, 8.32098711274139014427634118320e81, 0 }, { 61, 5.07580213877224798800856812177e83, 0 }, { 62, 3.14699732603879375256531223550e85, 0 }, { 63, 1.982608315404440064116146708360e87, 0 }, { 64, 1.268869321858841641034333893350e89, 0 }, { 65, 8.247650592082470666723170306800e90, 0 }, { 66, 5.443449390774430640037292402480e92, 0 }, { 67, 3.647111091818868528824985909660e94, 0 }, { 68, 2.480035542436830599600990418570e96, 0 }, { 69, 1.711224524281413113724683388810e98, 0 }, { 70, 1.197857166996989179607278372170e100, 0 }, { 71, 8.504785885678623175211676442400e101, 0 }, { 72, 6.123445837688608686152407038530e103, 0 }, { 73, 4.470115461512684340891257138130e105, 0 }, { 74, 3.307885441519386412259530282210e107, 0 }, { 75, 2.480914081139539809194647711660e109, 0 }, { 76, 1.885494701666050254987932260860e111, 0 }, { 77, 1.451830920282858696340707840860e113, 0 }, { 78, 1.132428117820629783145752115870e115, 0 }, { 79, 8.946182130782975286851441715400e116, 0 }, { 80, 7.156945704626380229481153372320e118, 0 }, { 81, 5.797126020747367985879734231580e120, 0 }, { 82, 4.753643337012841748421382069890e122, 0 }, { 83, 3.945523969720658651189747118010e124, 0 }, { 84, 3.314240134565353266999387579130e126, 0 }, { 85, 2.817104114380550276949479442260e128, 0 }, { 86, 2.422709538367273238176552320340e130, 0 }, { 87, 2.107757298379527717213600518700e132, 0 }, { 88, 1.854826422573984391147968456460e134, 0 }, { 89, 1.650795516090846108121691926250e136, 0 }, { 90, 1.485715964481761497309522733620e138, 0 }, { 91, 1.352001527678402962551665687590e140, 0 }, { 92, 1.243841405464130725547532432590e142, 0 }, { 93, 1.156772507081641574759205162310e144, 0 }, { 94, 1.087366156656743080273652852570e146, 0 }, { 95, 1.032997848823905926259970209940e148, 0 }, { 96, 9.916779348709496892095714015400e149, 0 }, { 97, 9.619275968248211985332842594960e151, 0 }, { 98, 9.426890448883247745626185743100e153, 0 }, { 99, 9.332621544394415268169923885600e155, 0 }, { 100, 9.33262154439441526816992388563e157, 0 }, { 101, 9.42594775983835942085162312450e159, 0 }, { 102, 9.61446671503512660926865558700e161, 0 }, { 103, 9.90290071648618040754671525458e163, 0 }, { 104, 1.02990167451456276238485838648e166, 0 }, { 105, 1.08139675824029090050410130580e168, 0 }, { 106, 1.146280563734708354534347384148e170, 0 }, { 107, 1.226520203196137939351751701040e172, 0 }, { 108, 1.324641819451828974499891837120e174, 0 }, { 109, 1.443859583202493582204882102460e176, 0 }, { 110, 1.588245541522742940425370312710e178, 0 }, { 111, 1.762952551090244663872161047110e180, 0 }, { 112, 1.974506857221074023536820372760e182, 0 }, { 113, 2.231192748659813646596607021220e184, 0 }, { 114, 2.543559733472187557120132004190e186, 0 }, { 115, 2.925093693493015690688151804820e188, 0 }, { 116, 3.393108684451898201198256093590e190, 0 }, { 117, 3.96993716080872089540195962950e192, 0 }, { 118, 4.68452584975429065657431236281e194, 0 }, { 119, 5.57458576120760588132343171174e196, 0 }, { 120, 6.68950291344912705758811805409e198, 0 }, { 121, 8.09429852527344373968162284545e200, 0 }, { 122, 9.87504420083360136241157987140e202, 0 }, { 123, 1.21463043670253296757662432419e205, 0 }, { 124, 1.50614174151114087979501416199e207, 0 }, { 125, 1.88267717688892609974376770249e209, 0 }, { 126, 2.37217324288004688567714730514e211, 0 }, { 127, 3.01266001845765954480997707753e213, 0 }, { 128, 3.85620482362580421735677065923e215, 0 }, { 129, 4.97450422247728744039023415041e217, 0 }, { 130, 6.46685548922047367250730439554e219, 0 }, { 131, 8.47158069087882051098456875820e221, 0 }, { 132, 1.11824865119600430744996307608e224, 0 }, { 133, 1.48727070609068572890845089118e226, 0 }, { 134, 1.99294274616151887673732419418e228, 0 }, { 135, 2.69047270731805048359538766215e230, 0 }, { 136, 3.65904288195254865768972722052e232, 0 }, { 137, 5.01288874827499166103492629211e234, 0 }, { 138, 6.91778647261948849222819828311e236, 0 }, { 139, 9.61572319694108900419719561353e238, 0 }, { 140, 1.34620124757175246058760738589e241, 0 }, { 141, 1.89814375907617096942852641411e243, 0 }, { 142, 2.69536413788816277658850750804e245, 0 }, { 143, 3.85437071718007277052156573649e247, 0 }, { 144, 5.55029383273930478955105466055e249, 0 }, { 145, 8.04792605747199194484902925780e251, 0 }, { 146, 1.17499720439091082394795827164e254, 0 }, { 147, 1.72724589045463891120349865931e256, 0 }, { 148, 2.55632391787286558858117801578e258, 0 }, { 149, 3.80892263763056972698595524351e260, 0 }, { 150, 5.71338395644585459047893286526e262, 0 }, { 151, 8.62720977423324043162318862650e264, 0 }, { 152, 1.31133588568345254560672467123e267, 0 }, { 153, 2.00634390509568239477828874699e269, 0 }, { 154, 3.08976961384735088795856467036e271, 0 }, { 155, 4.78914290146339387633577523906e273, 0 }, { 156, 7.47106292628289444708380937294e275, 0 }, { 157, 1.17295687942641442819215807155e278, 0 }, { 158, 1.85327186949373479654360975305e280, 0 }, { 159, 2.94670227249503832650433950735e282, 0 }, { 160, 4.71472363599206132240694321176e284, 0 }, { 161, 7.59070505394721872907517857094e286, 0 }, { 162, 1.22969421873944943411017892849e289, 0 }, { 163, 2.00440157654530257759959165344e291, 0 }, { 164, 3.28721858553429622726333031164e293, 0 }, { 165, 5.42391066613158877498449501421e295, 0 }, { 166, 9.00369170577843736647426172359e297, 0 }, { 167, 1.50361651486499904020120170784e300, 0 }, { 168, 2.52607574497319838753801886917e302, 0 }, { 169, 4.26906800900470527493925188890e304, 0 }, { 170, 7.25741561530799896739672821113e306, 0 }, /* { 171, 1.24101807021766782342484052410e309, 0 }, { 172, 2.13455108077438865629072570146e311, 0 }, { 173, 3.69277336973969237538295546352e313, 0 }, { 174, 6.42542566334706473316634250653e315, 0 }, { 175, 1.12444949108573632830410993864e318, 0 }, { 176, 1.97903110431089593781523349201e320, 0 }, { 177, 3.50288505463028580993296328086e322, 0 }, { 178, 6.23513539724190874168067463993e324, 0 }, { 179, 1.11608923610630166476084076055e327, 0 }, { 180, 2.00896062499134299656951336898e329, 0 }, { 181, 3.63621873123433082379081919786e331, 0 }, { 182, 6.61791809084648209929929094011e333, 0 }, { 183, 1.21107901062490622417177024204e336, 0 }, { 184, 2.22838537954982745247605724535e338, 0 }, { 185, 4.12251295216718078708070590390e340, 0 }, { 186, 7.66787409103095626397011298130e342, 0 }, { 187, 1.43389245502278882136241112750e345, 0 }, { 188, 2.69571781544284298416133291969e347, 0 }, { 189, 5.09490667118697324006491921822e349, 0 }, { 190, 9.68032267525524915612334651460e351, 0 }, { 191, 1.84894163097375258881955918429e354, 0 }, { 192, 3.54996793146960497053355363384e356, 0 }, { 193, 6.85143810773633759312975851330e358, 0 }, { 194, 1.32917899290084949306717315158e361, 0 }, { 195, 2.59189903615665651148098764559e363, 0 }, { 196, 5.08012211086704676250273578535e365, 0 }, { 197, 1.00078405584080821221303894971e368, 0 }, { 198, 1.98155243056480026018181712043e370, 0 }, { 199, 3.94328933682395251776181606966e372, 0 }, { 200, 7.88657867364790503552363213932e374, 0 } */ }; static struct {int n; double f; long i; } doub_fact_table[GSL_SF_DOUBLEFACT_NMAX + 1] = { { 0, 1.000000000000000000000000000, 1L }, { 1, 1.000000000000000000000000000, 1L }, { 2, 2.000000000000000000000000000, 2L }, { 3, 3.000000000000000000000000000, 3L }, { 4, 8.000000000000000000000000000, 8L }, { 5, 15.00000000000000000000000000, 15L }, { 6, 48.00000000000000000000000000, 48L }, { 7, 105.0000000000000000000000000, 105L }, { 8, 384.0000000000000000000000000, 384L }, { 9, 945.0000000000000000000000000, 945L }, { 10, 3840.000000000000000000000000, 3840L }, { 11, 10395.00000000000000000000000, 10395L }, { 12, 46080.00000000000000000000000, 46080L }, { 13, 135135.0000000000000000000000, 135135L }, { 14, 645120.00000000000000000000000, 645120L }, { 15, 2.02702500000000000000000000000e6, 2027025L }, { 16, 1.03219200000000000000000000000e7, 10321920L }, { 17, 3.4459425000000000000000000000e7, 34459425L }, { 18, 1.85794560000000000000000000000e8, 185794560L }, { 19, 6.5472907500000000000000000000e8, 0 }, { 20, 3.7158912000000000000000000000e9, 0 }, { 21, 1.37493105750000000000000000000e10, 0 }, { 22, 8.1749606400000000000000000000e10, 0 }, { 23, 3.1623414322500000000000000000e11, 0 }, { 24, 1.96199055360000000000000000000e12, 0 }, { 25, 7.9058535806250000000000000000e12, 0 }, { 26, 5.1011754393600000000000000000e13, 0 }, { 27, 2.13458046676875000000000000000e14, 0 }, { 28, 1.42832912302080000000000000000e15, 0 }, { 29, 6.1902833536293750000000000000e15, 0 }, { 30, 4.2849873690624000000000000000e16, 0 }, { 31, 1.91898783962510625000000000000e17, 0 }, { 32, 1.37119595809996800000000000000e18, 0 }, { 33, 6.3326598707628506250000000000e18, 0 }, { 34, 4.6620662575398912000000000000e19, 0 }, { 35, 2.21643095476699771875000000000e20, 0 }, { 36, 1.67834385271436083200000000000e21, 0 }, { 37, 8.2007945326378915593750000000e21, 0 }, { 38, 6.3777066403145711616000000000e22, 0 }, { 39, 3.1983098677287777081562500000e23, 0 }, { 40, 2.55108265612582846464000000000e24, 0 }, { 41, 1.31130704576879886034406250000e25, 0 }, { 42, 1.07145471557284795514880000000e26, 0 }, { 43, 5.6386202968058350994794687500e26, 0 }, { 44, 4.7144007485205310026547200000e27, 0 }, { 45, 2.53737913356262579476576093750e28, 0 }, { 46, 2.16862434431944426122117120000e29, 0 }, { 47, 1.19256819277443412353990764062e30, 0 }, { 48, 1.04093968527333324538616217600e31, 0 }, { 49, 5.8435841445947272053455474391e31, 0 }, { 50, 5.2046984263666662269308108800e32, 0 }, { 51, 2.98022791374331087472622919392e33, 0 }, { 52, 2.70644318171066643800402165760e34, 0 }, { 53, 1.57952079428395476360490147278e35, 0 }, { 54, 1.46147931812375987652217169510e36, 0 }, { 55, 8.6873643685617511998269581003e36, 0 }, { 56, 8.1842841814930553085241614926e37, 0 }, { 57, 4.9517976900801981839013661172e38, 0 }, { 58, 4.7468848252659720789440136657e39, 0 }, { 59, 2.92156063714731692850180600912e40, 0 }, { 60, 2.84813089515958324736640819942e41, 0 }, { 61, 1.78215198865986332638610166557e42, 0 }, { 62, 1.76584115499894161336717308364e43, 0 }, { 63, 1.12275575285571389562324404931e44, 0 }, { 64, 1.13013833919932263255499077353e45, 0 }, { 65, 7.2979123935621403215510863205e45, 0 }, { 66, 7.4589130387155293748629391053e46, 0 }, { 67, 4.8896013036866340154392278347e47, 0 }, { 68, 5.0720608663265599749067985916e48, 0 }, { 69, 3.3738248995437774706530672060e49, 0 }, { 70, 3.5504426064285919824347590141e50, 0 }, { 71, 2.39541567867608200416367771623e51, 0 }, { 72, 2.55631867662858622735302649017e52, 0 }, { 73, 1.74865344543353986303948473285e53, 0 }, { 74, 1.89167582070515380824123960272e54, 0 }, { 75, 1.31149008407515489727961354964e55, 0 }, { 76, 1.43767362373591689426334209807e56, 0 }, { 77, 1.00984736473786927090530243322e57, 0 }, { 78, 1.12138542651401517752540683649e58, 0 }, { 79, 7.9777941814291672401518892225e58, 0 }, { 80, 8.9710834121121214202032546920e59, 0 }, { 81, 6.4620132869576254645230302702e60, 0 }, { 82, 7.3562883979319395645666688474e61, 0 }, { 83, 5.3634710281748291355541151243e62, 0 }, { 84, 6.1792822542628292342360018318e63, 0 }, { 85, 4.5589503739486047652209978556e64, 0 }, { 86, 5.3141827386660331414429615754e65, 0 }, { 87, 3.9662868253352861457422681344e66, 0 }, { 88, 4.6764808100261091644698061863e67, 0 }, { 89, 3.5299952745484046697106186396e68, 0 }, { 90, 4.2088327290234982480228255677e69, 0 }, { 91, 3.2122956998390482494366629620e70, 0 }, { 92, 3.8721261107016183881809995223e71, 0 }, { 93, 2.98743500085031487197609655470e72, 0 }, { 94, 3.6397985440595212848901395509e73, 0 }, { 95, 2.83806325080779912837729172696e74, 0 }, { 96, 3.4942066022971404334945339689e75, 0 }, { 97, 2.75292135328356515452597297515e76, 0 }, { 98, 3.4243224702511976248246432895e77, 0 }, { 99, 2.72539213975072950298071324540e78, 0 }, { 100, 3.4243224702511976248246432895e79, 0 }, { 101, 2.75264606114823679801052037785e80, 0 }, { 102, 3.4928089196562215773211361553e81, 0 }, { 103, 2.83522544298268390195083598919e82, 0 }, { 104, 3.6325212764424704404139816015e83, 0 }, { 105, 2.97698671513181809704837778865e84, 0 }, { 106, 3.8504725530290186668388204976e85, 0 }, { 107, 3.1853757851910453638417642339e86, 0 }, { 108, 4.1585103572713401601859261374e87, 0 }, { 109, 3.4720596058582394465875230149e88, 0 }, { 110, 4.5743613929984741762045187512e89, 0 }, { 111, 3.8539861625026457857121505465e90, 0 }, { 112, 5.1232847601582910773490610013e91, 0 }, { 113, 4.3550043636279897378547301176e92, 0 }, { 114, 5.8405446265804518281779295415e93, 0 }, { 115, 5.0082550181721881985329396352e94, 0 }, { 116, 6.7750317668333241206863982681e95, 0 }, { 117, 5.8596583712614601922835393732e96, 0 }, { 118, 7.9945374848633224624099499564e97, 0 }, { 119, 6.9729934618011376288174118541e98, 0 }, { 120, 9.5934449818359869548919399477e99, 0 }, { 121, 8.4373220887793765308690683435e100, 0 }, { 122, 1.17040028778399040849681667362e102, 0 }, { 123, 1.03779061691986331329689540625e103, 0 }, { 124, 1.45129635685214810653605267528e104, 0 }, { 125, 1.29723827114982914162111925781e105, 0 }, { 126, 1.82863340963370661423542637086e106, 0 }, { 127, 1.64749260436028300985882145742e107, 0 }, { 128, 2.34065076433114446622134575470e108, 0 }, { 129, 2.12526545962476508271787968008e109, 0 }, { 130, 3.04284599363048780608774948111e110, 0 }, { 131, 2.78409775210844225836042238090e111, 0 }, { 132, 4.0165567115922439040358293151e112, 0 }, { 133, 3.7028500103042282036193617666e113, 0 }, { 134, 5.3821859935336068314080112822e114, 0 }, { 135, 4.9988475139107080748861383849e115, 0 }, { 136, 7.3197729512057052907148953438e116, 0 }, { 137, 6.8484210940576700625940095873e117, 0 }, { 138, 1.01012866726638733011865555744e119, 0 }, { 139, 9.5193053207401613870056733264e119, 0 }, { 140, 1.41418013417294226216611778042e121, 0 }, { 141, 1.34222205022436275556779993902e122, 0 }, { 142, 2.00813579052557801227588724819e123, 0 }, { 143, 1.91937753182083874046195391280e124, 0 }, { 144, 2.89171553835683233767727763739e125, 0 }, { 145, 2.78309742114021617366983317355e126, 0 }, { 146, 4.2219046860009752130088253506e127, 0 }, { 147, 4.0911532090761177752946547651e128, 0 }, { 148, 6.2484189352814433152530615189e129, 0 }, { 149, 6.0958182815234154851890356000e130, 0 }, { 150, 9.3726284029221649728795922783e131, 0 }, { 151, 9.2046856051003573826354437561e132, 0 }, { 152, 1.42463951724416907587769802630e134, 0 }, { 153, 1.40831689758035467954322289468e135, 0 }, { 154, 2.19394485655602037685165496051e136, 0 }, { 155, 2.18289119124954975329199548675e137, 0 }, { 156, 3.4225539762273917878885817384e138, 0 }, { 157, 3.4271391702617931126684329142e139, 0 }, { 158, 5.4076352824392790248639591467e140, 0 }, { 159, 5.4491512807162510491428083336e141, 0 }, { 160, 8.6522164519028464397823346347e142, 0 }, { 161, 8.7731335619531641891199214170e143, 0 }, { 162, 1.40165906520826112324473821082e145, 0 }, { 163, 1.43002077059836576282654719098e146, 0 }, { 164, 2.29872086694154824212137066574e147, 0 }, { 165, 2.35953427148730350866380286512e148, 0 }, { 166, 3.8158766391229700819214753051e149, 0 }, { 167, 3.9404222333837968594685507847e150, 0 }, { 168, 6.4106727537265897376280785126e151, 0 }, { 169, 6.6593135744186166925018508262e152, 0 }, { 170, 1.08981436813352025539677334714e154, 0 }, { 171, 1.13874262122558345441781649128e155, 0 }, { 172, 1.87448071318965483928245015709e156, 0 }, { 173, 1.97002473472025937614282252992e157, 0 }, { 174, 3.2615964409499994203514632733e158, 0 }, { 175, 3.4475432857604539082499394274e159, 0 }, { 176, 5.7404097360719989798185753611e160, 0 }, { 177, 6.1021516157960034176023927864e161, 0 }, { 178, 1.02179293302081581840770641427e163, 0 }, { 179, 1.09228513922748461175082830877e164, 0 }, { 180, 1.83922727943746847313387154568e165, 0 }, { 181, 1.97703610200174714726899923887e166, 0 }, { 182, 3.3473936485761926211036462131e167, 0 }, { 183, 3.6179760666631972795022686071e168, 0 }, { 184, 6.1592043133801944228307090322e169, 0 }, { 185, 6.6932557233269149670791969232e170, 0 }, { 186, 1.14561200228871616264651187999e172, 0 }, { 187, 1.25163882026213309884380982464e173, 0 }, { 188, 2.15375056430278638577544233437e174, 0 }, { 189, 2.36559737029543155681480056857e175, 0 }, { 190, 4.0921260721752941329733404353e176, 0 }, { 191, 4.5182909772642742735162690860e177, 0 }, { 192, 7.8568820585765647353088136358e178, 0 }, { 193, 8.7203015861200493478863993359e179, 0 }, { 194, 1.52423511936385355864990984535e181, 0 }, { 195, 1.70045880929340962283784787050e182, 0 }, { 196, 2.98750083395315297495382329688e183, 0 }, { 197, 3.3499038543080169569905603049e184, 0 }, { 198, 5.9152516512272428904085701278e185, 0 }, { 199, 6.6663086700729537444112150067e186, 0 }, { 200, 1.18305033024544857808171402556e188, 0 }, { 201, 1.33992804268466370262665421635e189, 0 }, { 202, 2.38976166709580612772506233164e190, 0 }, { 203, 2.72005392664986731633210805920e191, 0 }, { 204, 4.8751138008754445005591271565e192, 0 }, { 205, 5.5761105496322279984808215214e193, 0 }, { 206, 1.00427344298034156711518019425e195, 0 }, { 207, 1.15425488377387119568553005492e196, 0 }, { 208, 2.08888876139911045959957480403e197, 0 }, { 209, 2.41239270708739079898275781478e198, 0 }, { 210, 4.3866663989381319651591070885e199, 0 }, { 211, 5.0901486119543945858536189892e200, 0 }, { 212, 9.2997327657488397661373070276e201, 0 }, { 213, 1.08420165434628604678682084470e203, 0 }, { 214, 1.99014281187025170995338370390e204, 0 }, { 215, 2.33103355684451500059166481610e205, 0 }, { 216, 4.2987084736397436934993088004e206, 0 }, { 217, 5.0583428183525975512839126509e207, 0 }, { 218, 9.3711844725346412518284931849e208, 0 }, { 219, 1.10777707721921886373117687056e210, 0 }, { 220, 2.06166058395762107540226850068e211, 0 }, { 221, 2.44818734065447368884590088393e212, 0 }, { 222, 4.5768864963859187873930360715e213, 0 }, { 223, 5.4594577696594763261263589712e214, 0 }, { 224, 1.02522257519044580837604008002e216, 0 }, { 225, 1.22837799817338217337843076851e217, 0 }, { 226, 2.31700301993040752692985058084e218, 0 }, { 227, 2.78841805585357753356903784452e219, 0 }, { 228, 5.2827668854413291614000593243e220, 0 }, { 229, 6.3854773479046925518730966640e221, 0 }, { 230, 1.21503638365150570712201364459e223, 0 }, { 231, 1.47504526736598397948268532937e224, 0 }, { 232, 2.81888441007149324052307165546e225, 0 }, { 233, 3.4368554729627426721946568174e226, 0 }, { 234, 6.5961895195672941828239876738e227, 0 }, { 235, 8.0766103614624452796574435210e228, 0 }, { 236, 1.55670072661788142714646109101e230, 0 }, { 237, 1.91415665566659953127881411447e231, 0 }, { 238, 3.7049477293505577966085773966e232, 0 }, { 239, 4.5748344070431728797563657336e233, 0 }, { 240, 8.8918745504413387118605857518e234, 0 }, { 241, 1.10253509209740466402128414180e236, 0 }, { 242, 2.15183364120680396827026175195e237, 0 }, { 243, 2.67916027379669333357172046456e238, 0 }, { 244, 5.2504740845446016825794386748e239, 0 }, { 245, 6.5639426708018986672507151382e240, 0 }, { 246, 1.29161662479797201391454191399e242, 0 }, { 247, 1.62129383968806897081092663913e243, 0 }, { 248, 3.2032092294989705945080639467e244, 0 }, { 249, 4.0370216608232917373192073314e245, 0 }, { 250, 8.0080230737474264862701598667e246, 0 }, { 251, 1.01329243686664622606712104019e248, 0 }, { 252, 2.01802181458435147454008028642e249, 0 }, { 253, 2.56362986527261495194981623168e250, 0 }, { 254, 5.1257754090442527453318039275e251, 0 }, { 255, 6.5372561564451681274720313908e252, 0 }, { 256, 1.31219850471532870280494180544e254, 0 }, { 257, 1.68007483220640820876031206743e255, 0 }, { 258, 3.3854721421655480532367498580e256, 0 }, { 259, 4.3513938154145972606892082546e257, 0 }, { 260, 8.8022275696304249384155496309e258, 0 }, { 261, 1.13571378582320988503988335446e260, 0 }, { 262, 2.30618362324317133386487400329e261, 0 }, { 263, 2.98692725671504199765489322224e262, 0 }, { 264, 6.0883247653619723214032673687e263, 0 }, { 265, 7.9153572302948612937854670389e264, 0 }, { 266, 1.61949438758628463749326912007e266, 0 }, { 267, 2.11340038048872796544071969939e267, 0 }, { 268, 4.3402449587312428284819612418e268, 0 }, { 269, 5.6850470235146782270355359914e269, 0 }, { 270, 1.17186613885743556369012953528e271, 0 }, { 271, 1.54064774337247779952663025366e272, 0 }, { 272, 3.1874758976922247332371523360e273, 0 }, { 273, 4.2059683394068643927077005925e274, 0 }, { 274, 8.7336839596766957690697974006e275, 0 }, { 275, 1.15664129333688770799461766294e277, 0 }, { 276, 2.41049677287076803226326408256e278, 0 }, { 277, 3.2038963825431789511450909263e279, 0 }, { 278, 6.7011810285807351296918741495e280, 0 }, { 279, 8.9388709072954692736948036845e281, 0 }, { 280, 1.87633068800260583631372476186e283, 0 }, { 281, 2.51182272495002686590823983534e284, 0 }, { 282, 5.2912525401673484584047038284e285, 0 }, { 283, 7.1084583116085760305203187340e286, 0 }, { 284, 1.50271572140752696218693588728e288, 0 }, { 285, 2.02591061880844416869829083919e289, 0 }, { 286, 4.2977669632255271118546366376e290, 0 }, { 287, 5.8143634759802347641640947085e291, 0 }, { 288, 1.23775688540895180821413535163e293, 0 }, { 289, 1.68035104455828784684342337075e294, 0 }, { 290, 3.5894949676859602438209925197e295, 0 }, { 291, 4.8898215396646176343143620089e296, 0 }, { 292, 1.04813253056430039119572981576e298, 0 }, { 293, 1.43271771112173296685410806860e299, 0 }, { 294, 3.08150963985904315011544565835e300, 0 }, { 295, 4.2265172478091122522196188024e301, 0 }, { 296, 9.1212685339827677243417191487e302, 0 }, { 297, 1.25527562259930633890922678431e304, 0 }, /* { 298, 2.71813802312686478185383230631e305, 0 }, { 299, 3.7532741115719259533385880851e306, 0 }, { 300, 8.1544140693805943455614969189e307, } */ }; /* Chebyshev coefficients for Gamma*(3/4(t+1)+1/2), -1val = (zr+0.5)*log1_r.val - zi*log1_i.val - (zr+7.5) + LogRootTwoPi_ + logAg_r.val; yi->val = zi*log1_r.val + (zr+0.5)*log1_i.val - zi + logAg_i.val; yr->err = 4.0 * GSL_DBL_EPSILON * fabs(yr->val); yi->err = 4.0 * GSL_DBL_EPSILON * fabs(yi->val); yi_tmp_val = yi->val; yi_tmp_err = yi->err; gsl_sf_angle_restrict_symm_err_e(yi_tmp_val, yi); yi->err += yi_tmp_err; return GSL_SUCCESS; } /* Lanczos method for real x > 0; * gamma=7, truncated at 1/(z+8) * [J. SIAM Numer. Anal, Ser. B, 1 (1964) 86] */ static int lngamma_lanczos(double x, gsl_sf_result * result) { int k; double Ag; double term1, term2; x -= 1.0; /* Lanczos writes z! instead of Gamma(z) */ Ag = lanczos_7_c[0]; for(k=1; k<=8; k++) { Ag += lanczos_7_c[k]/(x+k); } /* (x+0.5)*log(x+7.5) - (x+7.5) + LogRootTwoPi_ + log(Ag(x)) */ term1 = (x+0.5)*log((x+7.5)/M_E); term2 = LogRootTwoPi_ + log(Ag); result->val = term1 + (term2 - 7.0); result->err = 2.0 * GSL_DBL_EPSILON * (fabs(term1) + fabs(term2) + 7.0); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* x = eps near zero * gives double-precision for |eps| < 0.02 */ static int lngamma_sgn_0(double eps, gsl_sf_result * lng, double * sgn) { /* calculate series for g(eps) = Gamma(eps) eps - 1/(1+eps) - eps/2 */ const double c1 = -0.07721566490153286061; const double c2 = -0.01094400467202744461; const double c3 = 0.09252092391911371098; const double c4 = -0.01827191316559981266; const double c5 = 0.01800493109685479790; const double c6 = -0.00685088537872380685; const double c7 = 0.00399823955756846603; const double c8 = -0.00189430621687107802; const double c9 = 0.00097473237804513221; const double c10 = -0.00048434392722255893; const double g6 = c6+eps*(c7+eps*(c8 + eps*(c9 + eps*c10))); const double g = eps*(c1+eps*(c2+eps*(c3+eps*(c4+eps*(c5+eps*g6))))); /* calculate Gamma(eps) eps, a positive quantity */ const double gee = g + 1.0/(1.0+eps) + 0.5*eps; lng->val = log(gee/fabs(eps)); lng->err = 4.0 * GSL_DBL_EPSILON * fabs(lng->val); *sgn = GSL_SIGN(eps); return GSL_SUCCESS; } /* x near a negative integer * Calculates sign as well as log(|gamma(x)|). * x = -N + eps * assumes N >= 1 */ static int lngamma_sgn_sing(int N, double eps, gsl_sf_result * lng, double * sgn) { if(eps == 0.0) { lng->val = 0.0; lng->err = 0.0; *sgn = 0.0; GSL_ERROR ("error", GSL_EDOM); } else if(N == 1) { /* calculate series for * g = eps gamma(-1+eps) + 1 + eps/2 (1+3eps)/(1-eps^2) * double-precision for |eps| < 0.02 */ const double c0 = 0.07721566490153286061; const double c1 = 0.08815966957356030521; const double c2 = -0.00436125434555340577; const double c3 = 0.01391065882004640689; const double c4 = -0.00409427227680839100; const double c5 = 0.00275661310191541584; const double c6 = -0.00124162645565305019; const double c7 = 0.00065267976121802783; const double c8 = -0.00032205261682710437; const double c9 = 0.00016229131039545456; const double g5 = c5 + eps*(c6 + eps*(c7 + eps*(c8 + eps*c9))); const double g = eps*(c0 + eps*(c1 + eps*(c2 + eps*(c3 + eps*(c4 + eps*g5))))); /* calculate eps gamma(-1+eps), a negative quantity */ const double gam_e = g - 1.0 - 0.5*eps*(1.0+3.0*eps)/(1.0 - eps*eps); lng->val = log(fabs(gam_e)/fabs(eps)); lng->err = 2.0 * GSL_DBL_EPSILON * fabs(lng->val); *sgn = ( eps > 0.0 ? -1.0 : 1.0 ); return GSL_SUCCESS; } else { double g; /* series for sin(Pi(N+1-eps))/(Pi eps) modulo the sign * double-precision for |eps| < 0.02 */ const double cs1 = -1.6449340668482264365; const double cs2 = 0.8117424252833536436; const double cs3 = -0.1907518241220842137; const double cs4 = 0.0261478478176548005; const double cs5 = -0.0023460810354558236; const double e2 = eps*eps; const double sin_ser = 1.0 + e2*(cs1+e2*(cs2+e2*(cs3+e2*(cs4+e2*cs5)))); /* calculate series for ln(gamma(1+N-eps)) * double-precision for |eps| < 0.02 */ double aeps = fabs(eps); double c1, c2, c3, c4, c5, c6, c7; double lng_ser; gsl_sf_result c0; gsl_sf_result psi_0; gsl_sf_result psi_1; gsl_sf_result psi_2; gsl_sf_result psi_3; gsl_sf_result psi_4; gsl_sf_result psi_5; gsl_sf_result psi_6; psi_2.val = 0.0; psi_3.val = 0.0; psi_4.val = 0.0; psi_5.val = 0.0; psi_6.val = 0.0; gsl_sf_lnfact_e(N, &c0); gsl_sf_psi_int_e(N+1, &psi_0); gsl_sf_psi_1_int_e(N+1, &psi_1); if(aeps > 0.00001) gsl_sf_psi_n_e(2, N+1.0, &psi_2); if(aeps > 0.0002) gsl_sf_psi_n_e(3, N+1.0, &psi_3); if(aeps > 0.001) gsl_sf_psi_n_e(4, N+1.0, &psi_4); if(aeps > 0.005) gsl_sf_psi_n_e(5, N+1.0, &psi_5); if(aeps > 0.01) gsl_sf_psi_n_e(6, N+1.0, &psi_6); c1 = psi_0.val; c2 = psi_1.val/2.0; c3 = psi_2.val/6.0; c4 = psi_3.val/24.0; c5 = psi_4.val/120.0; c6 = psi_5.val/720.0; c7 = psi_6.val/5040.0; lng_ser = c0.val-eps*(c1-eps*(c2-eps*(c3-eps*(c4-eps*(c5-eps*(c6-eps*c7)))))); /* calculate * g = ln(|eps gamma(-N+eps)|) * = -ln(gamma(1+N-eps)) + ln(|eps Pi/sin(Pi(N+1+eps))|) */ g = -lng_ser - log(sin_ser); lng->val = g - log(fabs(eps)); lng->err = c0.err + 2.0 * GSL_DBL_EPSILON * (fabs(g) + fabs(lng->val)); *sgn = ( GSL_IS_ODD(N) ? -1.0 : 1.0 ) * ( eps > 0.0 ? 1.0 : -1.0 ); return GSL_SUCCESS; } } /* This gets bad near the negative half axis. However, this * region can be avoided by use of the reflection formula, as usual. * Only the first two terms of the series are kept. */ #if 0 static int lngamma_complex_stirling(const double zr, const double zi, double * lg_r, double * arg) { double re_zinv, im_zinv; double re_zinv2, im_zinv2; double re_zinv3, im_zinv3; double re_zhlnz, im_zhlnz; double r, lnr, theta; gsl_sf_complex_log_e(zr, zi, &lnr, &theta); /* z = r e^{i theta} */ r = exp(lnr); re_zinv = (zr/r)/r; im_zinv = -(zi/r)/r; re_zinv2 = re_zinv*re_zinv - im_zinv*im_zinv; re_zinv2 = 2.0*re_zinv*im_zinv; re_zinv3 = re_zinv2*re_zinv - im_zinv2*im_zinv; re_zinv3 = re_zinv2*im_zinv + im_zinv2*re_zinv; re_zhlnz = (zr - 0.5)*lnr - zi*theta; im_zhlnz = zi*lnr + zr*theta; *lg_r = re_zhlnz - zr + 0.5*(M_LN2+M_LNPI) + re_zinv/12.0 - re_zinv3/360.0; *arg = im_zhlnz - zi + 1.0/12.0*im_zinv - im_zinv3/360.0; return GSL_SUCCESS; } #endif /* 0 */ inline static int lngamma_1_pade(const double eps, gsl_sf_result * result) { /* Use (2,2) Pade for Log[Gamma[1+eps]]/eps * plus a correction series. */ const double n1 = -1.0017419282349508699871138440; const double n2 = 1.7364839209922879823280541733; const double d1 = 1.2433006018858751556055436011; const double d2 = 5.0456274100274010152489597514; const double num = (eps + n1) * (eps + n2); const double den = (eps + d1) * (eps + d2); const double pade = 2.0816265188662692474880210318 * num / den; const double c0 = 0.004785324257581753; const double c1 = -0.01192457083645441; const double c2 = 0.01931961413960498; const double c3 = -0.02594027398725020; const double c4 = 0.03141928755021455; const double eps5 = eps*eps*eps*eps*eps; const double corr = eps5 * (c0 + eps*(c1 + eps*(c2 + eps*(c3 + c4*eps)))); result->val = eps * (pade + corr); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } inline static int lngamma_2_pade(const double eps, gsl_sf_result * result) { /* Use (2,2) Pade for Log[Gamma[2+eps]]/eps * plus a correction series. */ const double n1 = 1.000895834786669227164446568; const double n2 = 4.209376735287755081642901277; const double d1 = 2.618851904903217274682578255; const double d2 = 10.85766559900983515322922936; const double num = (eps + n1) * (eps + n2); const double den = (eps + d1) * (eps + d2); const double pade = 2.85337998765781918463568869 * num/den; const double c0 = 0.0001139406357036744; const double c1 = -0.0001365435269792533; const double c2 = 0.0001067287169183665; const double c3 = -0.0000693271800931282; const double c4 = 0.0000407220927867950; const double eps5 = eps*eps*eps*eps*eps; const double corr = eps5 * (c0 + eps*(c1 + eps*(c2 + eps*(c3 + c4*eps)))); result->val = eps * (pade + corr); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* series for gammastar(x) * double-precision for x > 10.0 */ static int gammastar_ser(const double x, gsl_sf_result * result) { /* Use the Stirling series for the correction to Log(Gamma(x)), * which is better behaved and easier to compute than the * regular Stirling series for Gamma(x). */ const double y = 1.0/(x*x); const double c0 = 1.0/12.0; const double c1 = -1.0/360.0; const double c2 = 1.0/1260.0; const double c3 = -1.0/1680.0; const double c4 = 1.0/1188.0; const double c5 = -691.0/360360.0; const double c6 = 1.0/156.0; const double c7 = -3617.0/122400.0; const double ser = c0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*(c6 + y*c7)))))); result->val = exp(ser/x); result->err = 2.0 * GSL_DBL_EPSILON * result->val * GSL_MAX_DBL(1.0, ser/x); return GSL_SUCCESS; } /* Chebyshev expansion for log(gamma(x)/gamma(8)) * 5 < x < 10 * -1 < t < 1 */ static double gamma_5_10_data[24] = { -1.5285594096661578881275075214, 4.8259152300595906319768555035, 0.2277712320977614992970601978, -0.0138867665685617873604917300, 0.0012704876495201082588139723, -0.0001393841240254993658962470, 0.0000169709242992322702260663, -2.2108528820210580075775889168e-06, 3.0196602854202309805163918716e-07, -4.2705675000079118380587357358e-08, 6.2026423818051402794663551945e-09, -9.1993973208880910416311405656e-10, 1.3875551258028145778301211638e-10, -2.1218861491906788718519522978e-11, 3.2821736040381439555133562600e-12, -5.1260001009953791220611135264e-13, 8.0713532554874636696982146610e-14, -1.2798522376569209083811628061e-14, 2.0417711600852502310258808643e-15, -3.2745239502992355776882614137e-16, 5.2759418422036579482120897453e-17, -8.5354147151695233960425725513e-18, 1.3858639703888078291599886143e-18, -2.2574398807738626571560124396e-19 }; static const cheb_series gamma_5_10_cs = { gamma_5_10_data, 23, -1, 1, 11 }; /* gamma(x) for x >= 1/2 * assumes x >= 1/2 */ static int gamma_xgthalf(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.5) { result->val = 1.77245385090551602729817; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if (x <= (GSL_SF_FACT_NMAX + 1.0) && x == floor(x)) { int n = (int) floor (x); result->val = fact_table[n - 1].f; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(fabs(x - 1.0) < 0.01) { /* Use series for Gamma[1+eps] - 1/(1+eps). */ const double eps = x - 1.0; const double c1 = 0.4227843350984671394; const double c2 = -0.01094400467202744461; const double c3 = 0.09252092391911371098; const double c4 = -0.018271913165599812664; const double c5 = 0.018004931096854797895; const double c6 = -0.006850885378723806846; const double c7 = 0.003998239557568466030; result->val = 1.0/x + eps*(c1+eps*(c2+eps*(c3+eps*(c4+eps*(c5+eps*(c6+eps*c7)))))); result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(fabs(x - 2.0) < 0.01) { /* Use series for Gamma[1 + eps]. */ const double eps = x - 2.0; const double c1 = 0.4227843350984671394; const double c2 = 0.4118403304264396948; const double c3 = 0.08157691924708626638; const double c4 = 0.07424901075351389832; const double c5 = -0.00026698206874501476832; const double c6 = 0.011154045718130991049; const double c7 = -0.002852645821155340816; const double c8 = 0.0021039333406973880085; result->val = 1.0 + eps*(c1+eps*(c2+eps*(c3+eps*(c4+eps*(c5+eps*(c6+eps*(c7+eps*c8))))))); result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < 5.0) { /* Exponentiating the logarithm is fine, as * long as the exponential is not so large * that it greatly amplifies the error. */ gsl_sf_result lg; lngamma_lanczos(x, &lg); result->val = exp(lg.val); result->err = result->val * (lg.err + 2.0 * GSL_DBL_EPSILON); return GSL_SUCCESS; } else if(x < 10.0) { /* This is a sticky area. The logarithm * is too large and the gammastar series * is not good. */ const double gamma_8 = 5040.0; const double t = (2.0*x - 15.0)/5.0; gsl_sf_result c; cheb_eval_e(&gamma_5_10_cs, t, &c); result->val = exp(c.val) * gamma_8; result->err = result->val * c.err; result->err += 2.0 * GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x < GSL_SF_GAMMA_XMAX) { /* We do not want to exponentiate the logarithm * if x is large because of the inevitable * inflation of the error. So we carefully * use pow() and exp() with exact quantities. */ double p = pow(x, 0.5*x); double e = exp(-x); double q = (p * e) * p; double pre = M_SQRT2 * M_SQRTPI * q/sqrt(x); gsl_sf_result gstar; int stat_gs = gammastar_ser(x, &gstar); result->val = pre * gstar.val; result->err = (x + 2.5) * GSL_DBL_EPSILON * result->val; return stat_gs; } else { OVERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_lngamma_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(fabs(x - 1.0) < 0.01) { /* Note that we must amplify the errors * from the Pade evaluations because of * the way we must pass the argument, i.e. * writing (1-x) is a loss of precision * when x is near 1. */ int stat = lngamma_1_pade(x - 1.0, result); result->err *= 1.0/(GSL_DBL_EPSILON + fabs(x - 1.0)); return stat; } else if(fabs(x - 2.0) < 0.01) { int stat = lngamma_2_pade(x - 2.0, result); result->err *= 1.0/(GSL_DBL_EPSILON + fabs(x - 2.0)); return stat; } else if(x >= 0.5) { return lngamma_lanczos(x, result); } else if(x == 0.0) { DOMAIN_ERROR(result); } else if(fabs(x) < 0.02) { double sgn; return lngamma_sgn_0(x, result, &sgn); } else if(x > -0.5/(GSL_DBL_EPSILON*M_PI)) { /* Try to extract a fractional * part from x. */ double z = 1.0 - x; double s = sin(M_PI*z); double as = fabs(s); if(s == 0.0) { DOMAIN_ERROR(result); } else if(as < M_PI*0.015) { /* x is near a negative integer, -N */ if(x < INT_MIN + 2.0) { result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EROUND); } else { int N = -(int)(x - 0.5); double eps = x + N; double sgn; return lngamma_sgn_sing(N, eps, result, &sgn); } } else { gsl_sf_result lg_z; lngamma_lanczos(z, &lg_z); result->val = M_LNPI - (log(as) + lg_z.val); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + lg_z.err; return GSL_SUCCESS; } } else { /* |x| was too large to extract any fractional part */ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EROUND); } } int gsl_sf_lngamma_sgn_e(double x, gsl_sf_result * result_lg, double * sgn) { if(fabs(x - 1.0) < 0.01) { int stat = lngamma_1_pade(x - 1.0, result_lg); result_lg->err *= 1.0/(GSL_DBL_EPSILON + fabs(x - 1.0)); *sgn = 1.0; return stat; } else if(fabs(x - 2.0) < 0.01) { int stat = lngamma_2_pade(x - 2.0, result_lg); result_lg->err *= 1.0/(GSL_DBL_EPSILON + fabs(x - 2.0)); *sgn = 1.0; return stat; } else if(x >= 0.5) { *sgn = 1.0; return lngamma_lanczos(x, result_lg); } else if(x == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result_lg); } else if(fabs(x) < 0.02) { return lngamma_sgn_0(x, result_lg, sgn); } else if(x > -0.5/(GSL_DBL_EPSILON*M_PI)) { /* Try to extract a fractional * part from x. */ double z = 1.0 - x; double s = sin(M_PI*x); double as = fabs(s); if(s == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result_lg); } else if(as < M_PI*0.015) { /* x is near a negative integer, -N */ if(x < INT_MIN + 2.0) { result_lg->val = 0.0; result_lg->err = 0.0; *sgn = 0.0; GSL_ERROR ("error", GSL_EROUND); } else { int N = -(int)(x - 0.5); double eps = x + N; return lngamma_sgn_sing(N, eps, result_lg, sgn); } } else { gsl_sf_result lg_z; lngamma_lanczos(z, &lg_z); *sgn = (s > 0.0 ? 1.0 : -1.0); result_lg->val = M_LNPI - (log(as) + lg_z.val); result_lg->err = 2.0 * GSL_DBL_EPSILON * fabs(result_lg->val) + lg_z.err; return GSL_SUCCESS; } } else { /* |x| was too large to extract any fractional part */ result_lg->val = 0.0; result_lg->err = 0.0; *sgn = 0.0; GSL_ERROR ("x too large to extract fraction part", GSL_EROUND); } } int gsl_sf_gamma_e(const double x, gsl_sf_result * result) { if(x < 0.5) { int rint_x = (int)floor(x+0.5); double f_x = x - rint_x; double sgn_gamma = ( GSL_IS_EVEN(rint_x) ? 1.0 : -1.0 ); double sin_term = sgn_gamma * sin(M_PI * f_x) / M_PI; if(sin_term == 0.0) { DOMAIN_ERROR(result); } else if(x > -169.0) { gsl_sf_result g; gamma_xgthalf(1.0-x, &g); if(fabs(sin_term) * g.val * GSL_DBL_MIN < 1.0) { result->val = 1.0/(sin_term * g.val); result->err = fabs(g.err/g.val) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } else { /* It is hard to control it here. * We can only exponentiate the * logarithm and eat the loss of * precision. */ gsl_sf_result lng; double sgn; int stat_lng = gsl_sf_lngamma_sgn_e(x, &lng, &sgn); int stat_e = gsl_sf_exp_mult_err_e(lng.val, lng.err, sgn, 0.0, result); return GSL_ERROR_SELECT_2(stat_e, stat_lng); } } else { return gamma_xgthalf(x, result); } } int gsl_sf_gammastar_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 0.5) { gsl_sf_result lg; const int stat_lg = gsl_sf_lngamma_e(x, &lg); const double lx = log(x); const double c = 0.5*(M_LN2+M_LNPI); const double lnr_val = lg.val - (x-0.5)*lx + x - c; const double lnr_err = lg.err + 2.0 * GSL_DBL_EPSILON *((x+0.5)*fabs(lx) + c); const int stat_e = gsl_sf_exp_err_e(lnr_val, lnr_err, result); return GSL_ERROR_SELECT_2(stat_lg, stat_e); } else if(x < 2.0) { const double t = 4.0/3.0*(x-0.5) - 1.0; return cheb_eval_e(&gstar_a_cs, t, result); } else if(x < 10.0) { const double t = 0.25*(x-2.0) - 1.0; gsl_sf_result c; cheb_eval_e(&gstar_b_cs, t, &c); result->val = c.val/(x*x) + 1.0 + 1.0/(12.0*x); result->err = c.err/(x*x); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 1.0/GSL_ROOT4_DBL_EPSILON) { return gammastar_ser(x, result); } else if(x < 1.0/GSL_DBL_EPSILON) { /* Use Stirling formula for Gamma(x). */ const double xi = 1.0/x; result->val = 1.0 + xi/12.0*(1.0 + xi/24.0*(1.0 - xi*(139.0/180.0 + 571.0/8640.0*xi))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = 1.0; result->err = 1.0/x; return GSL_SUCCESS; } } int gsl_sf_gammainv_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if (x <= 0.0 && x == floor(x)) { /* negative integer */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 0.5) { gsl_sf_result lng; double sgn; int stat_lng = gsl_sf_lngamma_sgn_e(x, &lng, &sgn); if(stat_lng == GSL_EDOM) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(stat_lng != GSL_SUCCESS) { result->val = 0.0; result->err = 0.0; return stat_lng; } else { return gsl_sf_exp_mult_err_e(-lng.val, lng.err, sgn, 0.0, result); } } else { gsl_sf_result g; int stat_g = gamma_xgthalf(x, &g); if(stat_g == GSL_EOVRFLW) { UNDERFLOW_ERROR(result); } else { result->val = 1.0/g.val; result->err = fabs(g.err/g.val) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } } int gsl_sf_lngamma_complex_e(double zr, double zi, gsl_sf_result * lnr, gsl_sf_result * arg) { if(zr <= 0.5) { /* Transform to right half plane using reflection; * in fact we do a little better by stopping at 1/2. */ double x = 1.0-zr; double y = -zi; gsl_sf_result a, b; gsl_sf_result lnsin_r, lnsin_i; int stat_l = lngamma_lanczos_complex(x, y, &a, &b); int stat_s = gsl_sf_complex_logsin_e(M_PI*zr, M_PI*zi, &lnsin_r, &lnsin_i); if(stat_s == GSL_SUCCESS) { int stat_r; lnr->val = M_LNPI - lnsin_r.val - a.val; lnr->err = lnsin_r.err + a.err + 2.0 * GSL_DBL_EPSILON * fabs(lnr->val); arg->val = -lnsin_i.val - b.val; arg->err = lnsin_i.err + b.err + 2.0 * GSL_DBL_EPSILON * fabs(arg->val); stat_r = gsl_sf_angle_restrict_symm_e(&(arg->val)); return GSL_ERROR_SELECT_2(stat_r, stat_l); } else { DOMAIN_ERROR_2(lnr,arg); } } else { /* otherwise plain vanilla Lanczos */ return lngamma_lanczos_complex(zr, zi, lnr, arg); } } int gsl_sf_taylorcoeff_e(const int n, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < 0.0 || n < 0) { DOMAIN_ERROR(result); } else if(n == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(n == 1) { result->val = x; result->err = 0.0; return GSL_SUCCESS; } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { const double log2pi = M_LNPI + M_LN2; const double ln_test = n*(log(x)+1.0) + 1.0 - (n+0.5)*log(n+1.0) + 0.5*log2pi; if(ln_test < GSL_LOG_DBL_MIN+1.0) { UNDERFLOW_ERROR(result); } else if(ln_test > GSL_LOG_DBL_MAX-1.0) { OVERFLOW_ERROR(result); } else { double product = 1.0; int k; for(k=1; k<=n; k++) { product *= (x/k); } result->val = product; result->err = n * GSL_DBL_EPSILON * product; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } } int gsl_sf_fact_e(const unsigned int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n < 18) { result->val = fact_table[n].f; result->err = 0.0; return GSL_SUCCESS; } else if(n <= GSL_SF_FACT_NMAX){ result->val = fact_table[n].f; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_doublefact_e(const unsigned int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n < 26) { result->val = doub_fact_table[n].f; result->err = 0.0; return GSL_SUCCESS; } else if(n <= GSL_SF_DOUBLEFACT_NMAX){ result->val = doub_fact_table[n].f; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_lnfact_e(const unsigned int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n <= GSL_SF_FACT_NMAX){ result->val = log(fact_table[n].f); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_lngamma_e(n+1.0, result); return GSL_SUCCESS; } } int gsl_sf_lndoublefact_e(const unsigned int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n <= GSL_SF_DOUBLEFACT_NMAX){ result->val = log(doub_fact_table[n].f); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(GSL_IS_ODD(n)) { gsl_sf_result lg; gsl_sf_lngamma_e(0.5*(n+2.0), &lg); result->val = 0.5*(n+1.0) * M_LN2 - 0.5*M_LNPI + lg.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + lg.err; return GSL_SUCCESS; } else { gsl_sf_result lg; gsl_sf_lngamma_e(0.5*n+1.0, &lg); result->val = 0.5*n*M_LN2 + lg.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + lg.err; return GSL_SUCCESS; } } int gsl_sf_lnchoose_e(unsigned int n, unsigned int m, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(m > n) { DOMAIN_ERROR(result); } else if(m == n || m == 0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result nf; gsl_sf_result mf; gsl_sf_result nmmf; if(m*2 > n) m = n-m; gsl_sf_lnfact_e(n, &nf); gsl_sf_lnfact_e(m, &mf); gsl_sf_lnfact_e(n-m, &nmmf); result->val = nf.val - mf.val - nmmf.val; result->err = nf.err + mf.err + nmmf.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_choose_e(unsigned int n, unsigned int m, gsl_sf_result * result) { if(m > n) { DOMAIN_ERROR(result); } else if(m == n || m == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if (n <= GSL_SF_FACT_NMAX) { result->val = (fact_table[n].f / fact_table[m].f) / fact_table[n-m].f; result->err = 6.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { if(m*2 < n) m = n-m; if (n - m < 64) /* compute product for a manageable number of terms */ { double prod = 1.0; unsigned int k; for(k=n; k>=m+1; k--) { double tk = (double)k / (double)(k-m); if(tk > GSL_DBL_MAX/prod) { OVERFLOW_ERROR(result); } prod *= tk; } result->val = prod; result->err = 2.0 * GSL_DBL_EPSILON * prod * fabs(n-m); return GSL_SUCCESS; } else { gsl_sf_result lc; const int stat_lc = gsl_sf_lnchoose_e (n, m, &lc); const int stat_e = gsl_sf_exp_err_e(lc.val, lc.err, result); return GSL_ERROR_SELECT_2(stat_lc, stat_e); } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_fact(const unsigned int n) { EVAL_RESULT(gsl_sf_fact_e(n, &result)); } double gsl_sf_lnfact(const unsigned int n) { EVAL_RESULT(gsl_sf_lnfact_e(n, &result)); } double gsl_sf_doublefact(const unsigned int n) { EVAL_RESULT(gsl_sf_doublefact_e(n, &result)); } double gsl_sf_lndoublefact(const unsigned int n) { EVAL_RESULT(gsl_sf_lndoublefact_e(n, &result)); } double gsl_sf_lngamma(const double x) { EVAL_RESULT(gsl_sf_lngamma_e(x, &result)); } double gsl_sf_gamma(const double x) { EVAL_RESULT(gsl_sf_gamma_e(x, &result)); } double gsl_sf_gammastar(const double x) { EVAL_RESULT(gsl_sf_gammastar_e(x, &result)); } double gsl_sf_gammainv(const double x) { EVAL_RESULT(gsl_sf_gammainv_e(x, &result)); } double gsl_sf_taylorcoeff(const int n, const double x) { EVAL_RESULT(gsl_sf_taylorcoeff_e(n, x, &result)); } double gsl_sf_choose(unsigned int n, unsigned int m) { EVAL_RESULT(gsl_sf_choose_e(n, m, &result)); } double gsl_sf_lnchoose(unsigned int n, unsigned int m) { EVAL_RESULT(gsl_sf_lnchoose_e(n, m, &result)); } sources_5316/external/gsl/gsl_cblas__zswap.c0000664000176700017670000000034711723710247020024 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zswap (const int N, void *X, const int incX, void *Y, const int incY) { #define BASE double #include "gsl_cblas__source_swap_c.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__result.c0000664000176700017670000000452611723710247020723 0ustar paulpaul/* specfunc/result.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_result.h" int gsl_sf_result_smash_e(const gsl_sf_result_e10 * re, gsl_sf_result * r) { if(re->e10 == 0) { /* nothing to smash */ r->val = re->val; r->err = re->err; return GSL_SUCCESS; } else { const double av = fabs(re->val); const double ae = fabs(re->err); if( GSL_SQRT_DBL_MIN < av && av < GSL_SQRT_DBL_MAX && GSL_SQRT_DBL_MIN < ae && ae < GSL_SQRT_DBL_MAX && 0.49*GSL_LOG_DBL_MIN < re->e10 && re->e10 < 0.49*GSL_LOG_DBL_MAX ) { const double scale = exp(re->e10 * M_LN10); r->val = re->val * scale; r->err = re->err * scale; return GSL_SUCCESS; } else { return gsl_sf_exp_mult_err_e(re->e10*M_LN10, 0.0, re->val, re->err, r); } } /* int stat_v; int stat_e; if(re->val == 0.0) { r->val = 0.0; stat_v = GSL_SUCCESS; } else { gsl_sf_result r_val; const double s = GSL_SIGN(re->val); const double x_v = re->e10*M_LN10 + log(fabs(re->val)); stat_v = gsl_sf_exp_e(x_v, &r_val); r->val = s * r_val.val; } if(re->err == 0.0) { r->err = 0.0; stat_e = GSL_SUCCESS; } else if(re->val != 0.0) { r->err = fabs(r->val * re->err/re->val); stat_e = GSL_SUCCESS; } else { gsl_sf_result r_err; const double x_e = re->e10*M_LN10 + log(fabs(re->err)); stat_e = gsl_sf_exp_e(x_e, &r_err); r->err = r_err.val; } return GSL_ERROR_SELECT_2(stat_v, stat_e); */ } sources_5316/external/gsl/gsl__config.h0000664000176700017670000002136411754441550016772 0ustar paulpaul/* config.h. Generated from config.h.in by configure. */ /* config.h.in. Generated from configure.ac by autoheader. */ /* Define to 1 if you have the declaration of `acosh', and to 0 if you don't. */ #define HAVE_DECL_ACOSH 1 /* Define to 1 if you have the declaration of `asinh', and to 0 if you don't. */ #define HAVE_DECL_ASINH 1 /* Define to 1 if you have the declaration of `atanh', and to 0 if you don't. */ #define HAVE_DECL_ATANH 1 /* Define to 1 if you have the declaration of `expm1', and to 0 if you don't. */ #if defined(linux) || defined (_WIN32) #define HAVE_DECL_EXPM1 1 #else #define HAVE_DECL_EXPM1 0 #endif /* Define to 1 if you have the declaration of `feenableexcept', and to 0 if you don't. */ #if defined(linux) #define HAVE_DECL_FEENABLEEXCEPT 1 #else #define HAVE_DECL_FEENABLEEXCEPT 0 #endif /* Define to 1 if you have the declaration of `fesettrapenable', and to 0 if you don't. */ #define HAVE_DECL_FESETTRAPENABLE 0 /* Define to 1 if you have the declaration of `finite', and to 0 if you don't. */ #if defined(linux) || defined (_WIN32) #define HAVE_DECL_FINITE 1 #else #define HAVE_DECL_FINITE 0 #endif /* Define to 1 if you have the declaration of `frexp', and to 0 if you don't. */ #define HAVE_DECL_FREXP 1 /* Define to 1 if you have the declaration of `hypot', and to 0 if you don't. */ #define HAVE_DECL_HYPOT 1 /* Define to 1 if you have the declaration of `isfinite', and to 0 if you don't. */ #if defined(linux) #define HAVE_DECL_ISFINITE 0 #else #define HAVE_DECL_ISFINITE 0 #endif /* Define to 1 if you have the declaration of `isinf', and to 0 if you don't. */ #if defined(linux) || defined (macintosh) || defined (_WIN32) #define HAVE_DECL_ISINF 1 #else #define HAVE_DECL_ISINF 0 #endif /* Define to 1 if you have the declaration of `isnan', and to 0 if you don't. */ #if defined(linux) || defined (macintosh) || defined (_WIN32) #define HAVE_DECL_ISNAN 1 #else #define HAVE_DECL_ISNAN 0 #endif /* Define to 1 if you have the declaration of `ldexp', and to 0 if you don't. */ #define HAVE_DECL_LDEXP 1 /* Define to 1 if you have the declaration of `log1p', and to 0 if you don't. */ #define HAVE_DECL_LOG1P 1 /* Define to 1 if you have the header file. */ #if defined(linux) #define HAVE_DLFCN_H 1 #else #define HAVE_DLFCN_H 0 #endif /* Define to 1 if you don't have `vprintf' but do have `_doprnt.' */ /* #undef HAVE_DOPRNT */ /* Defined if you have ansi EXIT_SUCCESS and EXIT_FAILURE in stdlib.h */ #define HAVE_EXIT_SUCCESS_AND_FAILURE 1 /* Defined on architectures with excess floating-point precision */ #define HAVE_EXTENDED_PRECISION_REGISTERS 1 /* Define if x86 processor has sse extensions. */ #define HAVE_FPU_X86_SSE 1 /* Define to 1 if you have the header file. */ /* #undef HAVE_IEEEFP_H */ #define HAVE_IEEEFP_H 0 /* Define this if IEEE comparisons work correctly (e.g. NaN != NaN) */ #define HAVE_IEEE_COMPARISONS 1 /* Define this if IEEE denormalized numbers are available */ #define HAVE_IEEE_DENORMALS 1 /* Define if you have inline */ #undef HAVE_INLINE #ifdef sgi #define inline #endif /* Define to 1 if you have the header file. */ #define HAVE_INTTYPES_H 1 /* Define to 1 if you have the `m' library (-lm). */ #define HAVE_LIBM 1 /* Define to 1 if you have the `memcpy' function. */ #define HAVE_MEMCPY 1 /* Define to 1 if you have the `memmove' function. */ #define HAVE_MEMMOVE 1 /* Define to 1 if you have the header file. */ #define HAVE_MEMORY_H 1 /* Define this if printf can handle %Lf for long double */ #define HAVE_PRINTF_LONGDOUBLE 1 /* Define to 1 if you have the header file. */ #define HAVE_STDINT_H 1 /* Define to 1 if you have the header file. */ #define HAVE_STDLIB_H 1 /* Define to 1 if you have the `strdup' function. */ #if defined(linux) #define HAVE_STRDUP 1 #else #define HAVE_STRDUP 0 #endif /* Define to 1 if you have the header file. */ #define HAVE_STRINGS_H 1 /* Define to 1 if you have the header file. */ #define HAVE_STRING_H 1 /* Define to 1 if you have the `strtol' function. */ #if defined(linux) #define HAVE_STRTOL 1 #else #define HAVE_STRTOL 0 #endif /* Define to 1 if you have the `strtoul' function. */ #if defined(linux) #define HAVE_STRTOUL 1 #else #define HAVE_STRTOUL 0 #endif /* Define to 1 if you have the header file. */ #define HAVE_SYS_STAT_H 1 /* Define to 1 if you have the header file. */ #define HAVE_SYS_TYPES_H 1 /* Define to 1 if you have the header file. */ #define HAVE_UNISTD_H 1 /* Define to 1 if you have the `vprintf' function. */ #define HAVE_VPRINTF 1 /* Name of package */ #define PACKAGE "gsl" /* Define to the address where bug reports for this package should be sent. */ #define PACKAGE_BUGREPORT "" /* Define to the full name of this package. */ #define PACKAGE_NAME "gsl" /* Define to the full name and version of this package. */ #define PACKAGE_STRING "gsl 1.10" /* Define to the one symbol short name of this package. */ #define PACKAGE_TARNAME "gsl" /* Define to the version of this package. */ #define PACKAGE_VERSION "1.10" /* Defined if this is an official release */ #define RELEASED /* Define to 1 if you have the ANSI C header files. */ #define STDC_HEADERS 1 /* Version number of package */ #define VERSION "1.10" /* Define to 1 if type `char' is unsigned and you are not using gcc. */ #ifndef __CHAR_UNSIGNED__ /* # undef __CHAR_UNSIGNED__ */ #endif /* Define to `__inline__' or `__inline' if that's what the C compiler calls it, or to nothing if 'inline' is not supported under any name. */ #ifndef __cplusplus /* #undef inline */ #endif /* Define to `unsigned int' if does not define. */ /* #undef size_t */ /* Define to empty if the keyword `volatile' does not work. Warning: valid code using `volatile' can become incorrect without. Disable with care. */ /* #undef volatile */ /* Define if you need to hide the static definitions of inline functions */ /* #undef HIDE_INLINE_STATIC */ /* Use 0 and 1 for EXIT_SUCCESS and EXIT_FAILURE if we don't have them */ #if !HAVE_EXIT_SUCCESS_AND_FAILURE #define EXIT_SUCCESS 0 #define EXIT_FAILURE 1 #endif /* Define one of these if you have a known IEEE arithmetic interface */ /* #undef HAVE_GNUSPARC_IEEE_INTERFACE */ /* #undef HAVE_GNUM68K_IEEE_INTERFACE */ /* #undef HAVE_GNUPPC_IEEE_INTERFACE */ /* #undef HAVE_GNUX86_IEEE_INTERFACE */ /* #undef HAVE_SUNOS4_IEEE_INTERFACE */ /* #undef HAVE_SOLARIS_IEEE_INTERFACE */ /* #undef HAVE_HPUX11_IEEE_INTERFACE */ /* #undef HAVE_HPUX_IEEE_INTERFACE */ /* #undef HAVE_TRU64_IEEE_INTERFACE */ /* #undef HAVE_IRIX_IEEE_INTERFACE */ /* #undef HAVE_AIX_IEEE_INTERFACE */ /* #undef HAVE_FREEBSD_IEEE_INTERFACE */ /* #undef HAVE_OS2EMX_IEEE_INTERFACE */ /* #undef HAVE_NETBSD_IEEE_INTERFACE */ /* #undef HAVE_OPENBSD_IEEE_INTERFACE */ /* #undef HAVE_DARWIN_IEEE_INTERFACE */ /* #undef HAVE_DARWIN86_IEEE_INTERFACE */ /* Define a rounding function which moves extended precision values out of registers and rounds them to double-precision. This should be used *sparingly*, in places where it is necessary to keep double-precision rounding for critical expressions while running in extended precision. For example, the following code should ensure exact equality, even when extended precision registers are in use, double q = GSL_COERCE_DBL(3.0/7.0) ; if (q == GSL_COERCE_DBL(3.0/7.0)) { ... } ; It carries a penalty even when the program is running in double precision mode unless you compile a separate version of the library with HAVE_EXTENDED_PRECISION_REGISTERS turned off. */ #if HAVE_EXTENDED_PRECISION_REGISTERS #define GSL_COERCE_DBL(x) (gsl_coerce_double(x)) #else #define GSL_COERCE_DBL(x) (x) #endif /* Substitute gsl functions for missing system functions */ #if !HAVE_DECL_HYPOT #define hypot gsl_hypot #endif #if !HAVE_DECL_LOG1P #define log1p gsl_log1p #endif #if !HAVE_DECL_EXPM1 #define expm1 gsl_expm1 #endif #if !HAVE_DECL_ACOSH #define acosh gsl_acosh #endif #if !HAVE_DECL_ASINH #define asinh gsl_asinh #endif #if !HAVE_DECL_ATANH #define atanh gsl_atanh #endif #if !HAVE_DECL_LDEXP #define ldexp gsl_ldexp #endif #if !HAVE_DECL_FREXP #define frexp gsl_frexp #endif #if !HAVE_DECL_ISINF #define isinf gsl_isinf #endif #if !HAVE_DECL_FINITE #define finite gsl_finite #endif #if !HAVE_DECL_ISNAN #define isnan gsl_isnan #endif #ifdef __GNUC__ #define DISCARD_POINTER(p) do { ; } while(p ? 0 : 0); #else #define DISCARD_POINTER(p) /* ignoring discarded pointer */ #endif #if defined(GSL_RANGE_CHECK_OFF) || !defined(GSL_RANGE_CHECK) #define GSL_RANGE_CHECK 0 /* turn off range checking by default internally */ #endif /* Disable deprecated functions and enums while building */ #define GSL_DISABLE_DEPRECATED 1 // 20110502 #define USE_BLAS 0 sources_5316/external/gsl/gsl_sys__expm1.c0000664000176700017670000000254011723710247017441 0ustar paulpaul/* sys/expm1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" double gsl_expm1 (const double x) { /* FIXME: this should be improved */ if (fabs(x) < M_LN2) { /* Compute the taylor series S = x + (1/2!) x^2 + (1/3!) x^3 + ... */ double i = 1.0; double sum = x; double term = x / 1.0; do { i++ ; term *= x/i; sum += term; } while (fabs(term) > fabs(sum) * GSL_DBL_EPSILON) ; return sum ; } else { return exp(x) - 1; } } sources_5316/external/gsl/gsl_specfunc__bessel_j.c0000664000176700017670000002552111723710247021171 0ustar paulpaul/* specfunc/bessel_j.c * * Copyright (C) 1996,1997,1998,1999,2000,2001,2002,2003 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_olver.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_j0_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(ax < 0.5) { const double y = x*x; const double c1 = -1.0/6.0; const double c2 = 1.0/120.0; const double c3 = -1.0/5040.0; const double c4 = 1.0/362880.0; const double c5 = -1.0/39916800.0; const double c6 = 1.0/6227020800.0; result->val = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*c6))))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result sin_result; const int stat = gsl_sf_sin_e(x, &sin_result); result->val = sin_result.val/x; result->err = fabs(sin_result.err/x); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } } int gsl_sf_bessel_j1_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 3.1*GSL_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(ax < 0.25) { const double y = x*x; const double c1 = -1.0/10.0; const double c2 = 1.0/280.0; const double c3 = -1.0/15120.0; const double c4 = 1.0/1330560.0; const double c5 = -1.0/172972800.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*c5)))); result->val = x/3.0 * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result cos_result; gsl_sf_result sin_result; const int stat_cos = gsl_sf_cos_e(x, &cos_result); const int stat_sin = gsl_sf_sin_e(x, &sin_result); const double cos_x = cos_result.val; const double sin_x = sin_result.val; result->val = (sin_x/x - cos_x)/x; result->err = (fabs(sin_result.err/x) + fabs(cos_result.err))/fabs(x); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(sin_x/(x*x)) + fabs(cos_x/x)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_cos, stat_sin); } } int gsl_sf_bessel_j2_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 4.0*GSL_SQRT_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(ax < 1.3) { const double y = x*x; const double c1 = -1.0/14.0; const double c2 = 1.0/504.0; const double c3 = -1.0/33264.0; const double c4 = 1.0/3459456.0; const double c5 = -1.0/518918400; const double c6 = 1.0/105859353600.0; const double c7 = -1.0/28158588057600.0; const double c8 = 1.0/9461285587353600.0; const double c9 = -1.0/3916972233164390400.0; const double sum = 1.0+y*(c1+y*(c2+y*(c3+y*(c4+y*(c5+y*(c6+y*(c7+y*(c8+y*c9)))))))); result->val = y/15.0 * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result cos_result; gsl_sf_result sin_result; const int stat_cos = gsl_sf_cos_e(x, &cos_result); const int stat_sin = gsl_sf_sin_e(x, &sin_result); const double cos_x = cos_result.val; const double sin_x = sin_result.val; const double f = (3.0/(x*x) - 1.0); result->val = (f * sin_x - 3.0*cos_x/x)/x; result->err = fabs(f * sin_result.err/x) + fabs((3.0*cos_result.err/x)/x); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(f*sin_x/x) + 3.0*fabs(cos_x/(x*x))); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_cos, stat_sin); } } int gsl_sf_bessel_jl_e(const int l, const double x, gsl_sf_result * result) { if(l < 0 || x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = ( l > 0 ? 0.0 : 1.0 ); result->err = 0.0; return GSL_SUCCESS; } else if(l == 0) { return gsl_sf_bessel_j0_e(x, result); } else if(l == 1) { return gsl_sf_bessel_j1_e(x, result); } else if(l == 2) { return gsl_sf_bessel_j2_e(x, result); } else if(x*x < 10.0*(l+0.5)/M_E) { gsl_sf_result b; int status = gsl_sf_bessel_IJ_taylor_e(l+0.5, x, -1, 50, GSL_DBL_EPSILON, &b); double pre = sqrt((0.5*M_PI)/x); result->val = pre * b.val; result->err = pre * b.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return status; } else if(GSL_ROOT4_DBL_EPSILON * x > (l*l + l + 1.0)) { gsl_sf_result b; int status = gsl_sf_bessel_Jnu_asympx_e(l + 0.5, x, &b); double pre = sqrt((0.5*M_PI)/x); result->val = pre * b.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * b.err; return status; } else if(l > 1.0/GSL_ROOT6_DBL_EPSILON) { gsl_sf_result b; int status = gsl_sf_bessel_Jnu_asymp_Olver_e(l + 0.5, x, &b); double pre = sqrt((0.5*M_PI)/x); result->val = pre * b.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * b.err; return status; } else if(x > 1000.0 && x > 100.0*l*l) { /* We need this to avoid feeding large x to CF1; note that * due to the above check, we know that n <= 50. */ gsl_sf_result b; int status = gsl_sf_bessel_Jnu_asympx_e(l + 0.5, x, &b); double pre = sqrt((0.5*M_PI)/x); result->val = pre * b.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * b.err; return status; } else { double sgn; double ratio; int stat_CF1 = gsl_sf_bessel_J_CF1(l+0.5, x, &ratio, &sgn); double jellp1 = GSL_SQRT_DBL_EPSILON * ratio; double jell = GSL_SQRT_DBL_EPSILON; double jellm1; int ell; for(ell = l; ell > 0; ell--) { jellm1 = -jellp1 + (2*ell + 1)/x * jell; jellp1 = jell; jell = jellm1; } if(fabs(jell) > fabs(jellp1)) { gsl_sf_result j0_result; int stat_j0 = gsl_sf_bessel_j0_e(x, &j0_result); double pre = GSL_SQRT_DBL_EPSILON / jell; result->val = j0_result.val * pre; result->err = j0_result.err * fabs(pre); result->err += 2.0 * GSL_DBL_EPSILON * (0.5*l + 1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_j0, stat_CF1); } else { gsl_sf_result j1_result; int stat_j1 = gsl_sf_bessel_j1_e(x, &j1_result); double pre = GSL_SQRT_DBL_EPSILON / jellp1; result->val = j1_result.val * pre; result->err = j1_result.err * fabs(pre); result->err += 2.0 * GSL_DBL_EPSILON * (0.5*l + 1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_j1, stat_CF1); } } } int gsl_sf_bessel_jl_array(const int lmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(lmax < 0 || x < 0.0) { int j; for(j=0; j<=lmax; j++) result_array[j] = 0.0; GSL_ERROR ("error", GSL_EDOM); } else if(x == 0.0) { int j; for(j=1; j<=lmax; j++) result_array[j] = 0.0; result_array[0] = 1.0; return GSL_SUCCESS; } else { gsl_sf_result r_jellp1; gsl_sf_result r_jell; int stat_0 = gsl_sf_bessel_jl_e(lmax+1, x, &r_jellp1); int stat_1 = gsl_sf_bessel_jl_e(lmax, x, &r_jell); double jellp1 = r_jellp1.val; double jell = r_jell.val; double jellm1; int ell; result_array[lmax] = jell; for(ell = lmax; ell >= 1; ell--) { jellm1 = -jellp1 + (2*ell + 1)/x * jell; jellp1 = jell; jell = jellm1; result_array[ell-1] = jellm1; } return GSL_ERROR_SELECT_2(stat_0, stat_1); } } int gsl_sf_bessel_jl_steed_array(const int lmax, const double x, double * jl_x) { /* CHECK_POINTER(jl_x) */ if(lmax < 0 || x < 0.0) { int j; for(j=0; j<=lmax; j++) jl_x[j] = 0.0; GSL_ERROR ("error", GSL_EDOM); } else if(x == 0.0) { int j; for(j=1; j<=lmax; j++) jl_x[j] = 0.0; jl_x[0] = 1.0; return GSL_SUCCESS; } else if(x < 2.0*GSL_ROOT4_DBL_EPSILON) { /* first two terms of Taylor series */ double inv_fact = 1.0; /* 1/(1 3 5 ... (2l+1)) */ double x_l = 1.0; /* x^l */ int l; for(l=0; l<=lmax; l++) { jl_x[l] = x_l * inv_fact; jl_x[l] *= 1.0 - 0.5*x*x/(2.0*l+3.0); inv_fact /= 2.0*l+3.0; x_l *= x; } return GSL_SUCCESS; } else { /* Steed/Barnett algorithm [Comp. Phys. Comm. 21, 297 (1981)] */ double x_inv = 1.0/x; double W = 2.0*x_inv; double F = 1.0; double FP = (lmax+1.0) * x_inv; double B = 2.0*FP + x_inv; double end = B + 20000.0*W; double D = 1.0/B; double del = -D; FP += del; /* continued fraction */ do { B += W; D = 1.0/(B-D); del *= (B*D - 1.); FP += del; if(D < 0.0) F = -F; if(B > end) { GSL_ERROR ("error", GSL_EMAXITER); } } while(fabs(del) >= fabs(FP) * GSL_DBL_EPSILON); FP *= F; if(lmax > 0) { /* downward recursion */ double XP2 = FP; double PL = lmax * x_inv; int L = lmax; int LP; jl_x[lmax] = F; for(LP = 1; LP<=lmax; LP++) { jl_x[L-1] = PL * jl_x[L] + XP2; FP = PL*jl_x[L-1] - jl_x[L]; XP2 = FP; PL -= x_inv; --L; } F = jl_x[0]; } /* normalization */ W = x_inv / hypot(FP, F); jl_x[0] = W*F; if(lmax > 0) { int L; for(L=1; L<=lmax; L++) { jl_x[L] *= W; } } return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_j0(const double x) { EVAL_RESULT(gsl_sf_bessel_j0_e(x, &result)); } double gsl_sf_bessel_j1(const double x) { EVAL_RESULT(gsl_sf_bessel_j1_e(x, &result)); } double gsl_sf_bessel_j2(const double x) { EVAL_RESULT(gsl_sf_bessel_j2_e(x, &result)); } double gsl_sf_bessel_jl(const int l, const double x) { EVAL_RESULT(gsl_sf_bessel_jl_e(l, x, &result)); } sources_5316/external/gsl/gsl_cblas__source_hemv.h0000664000176700017670000001164411705263724021211 0ustar paulpaul/* blas/source_hemv.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (order == CblasColMajor) ? -1 : 1; INDEX i, j; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; /* form y := beta*y */ if (beta_real == 0.0 && beta_imag == 0.0) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { REAL(Y, iy) = 0.0; IMAG(Y, iy) = 0.0; iy += incY; } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE y_real = REAL(Y, iy); const BASE y_imag = IMAG(Y, iy); const BASE tmpR = y_real * beta_real - y_imag * beta_imag; const BASE tmpI = y_real * beta_imag + y_imag * beta_real; REAL(Y, iy) = tmpR; IMAG(Y, iy) = tmpI; iy += incY; } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; /* form y := alpha*A*x + y */ if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { BASE x_real = CONST_REAL(X, ix); BASE x_imag = CONST_IMAG(X, ix); BASE temp1_real = alpha_real * x_real - alpha_imag * x_imag; BASE temp1_imag = alpha_real * x_imag + alpha_imag * x_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; const INDEX j_min = i + 1; const INDEX j_max = N; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; BASE Aii_real = CONST_REAL(A, lda * i + i); /* Aii_imag is zero */ REAL(Y, iy) += temp1_real * Aii_real; IMAG(Y, iy) += temp1_imag * Aii_real; for (j = j_min; j < j_max; j++) { BASE Aij_real = CONST_REAL(A, lda * i + j); BASE Aij_imag = conj * CONST_IMAG(A, lda * i + j); REAL(Y, jy) += temp1_real * Aij_real - temp1_imag * (-Aij_imag); IMAG(Y, jy) += temp1_real * (-Aij_imag) + temp1_imag * Aij_real; x_real = CONST_REAL(X, jx); x_imag = CONST_IMAG(X, jx); temp2_real += x_real * Aij_real - x_imag * Aij_imag; temp2_imag += x_real * Aij_imag + x_imag * Aij_real; jx += incX; jy += incY; } REAL(Y, iy) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(Y, iy) += alpha_real * temp2_imag + alpha_imag * temp2_real; ix += incX; iy += incY; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX) + (N - 1) * incX; INDEX iy = OFFSET(N, incY) + (N - 1) * incY; for (i = N; i > 0 && i--;) { BASE x_real = CONST_REAL(X, ix); BASE x_imag = CONST_IMAG(X, ix); BASE temp1_real = alpha_real * x_real - alpha_imag * x_imag; BASE temp1_imag = alpha_real * x_imag + alpha_imag * x_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; const INDEX j_min = 0; const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; BASE Aii_real = CONST_REAL(A, lda * i + i); /* Aii_imag is zero */ REAL(Y, iy) += temp1_real * Aii_real; IMAG(Y, iy) += temp1_imag * Aii_real; for (j = j_min; j < j_max; j++) { BASE Aij_real = CONST_REAL(A, lda * i + j); BASE Aij_imag = conj * CONST_IMAG(A, lda * i + j); REAL(Y, jy) += temp1_real * Aij_real - temp1_imag * (-Aij_imag); IMAG(Y, jy) += temp1_real * (-Aij_imag) + temp1_imag * Aij_real; x_real = CONST_REAL(X, jx); x_imag = CONST_IMAG(X, jx); temp2_real += x_real * Aij_real - x_imag * Aij_imag; temp2_imag += x_real * Aij_imag + x_imag * Aij_real; jx += incX; jy += incY; } REAL(Y, iy) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(Y, iy) += alpha_real * temp2_imag + alpha_imag * temp2_real; ix -= incX; iy -= incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_sf_pow_int.h0000664000176700017670000000255211705263724017534 0ustar paulpaul/* specfunc/gsl_sf_pow_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_POW_INT_H__ #define __GSL_SF_POW_INT_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Calculate x^n. * Does not check for overflow/underflow. */ int gsl_sf_pow_int_e(double x, int n, gsl_sf_result * result); double gsl_sf_pow_int(const double x, const int n); __END_DECLS #endif /* __GSL_SF_POW_INT_H__ */ sources_5316/external/gsl/gsl_cblas__zgemm.c0000664000176700017670000000074011723710247017774 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zgemm (const enum CBLAS_ORDER Order, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_TRANSPOSE TransB, const int M, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc) { #define BASE double #include "gsl_cblas__source_gemm_c.h" #undef BASE } sources_5316/external/gsl/gsl_fft__real_pass_2.c0000664000176700017670000000720611723710247020546 0ustar paulpaul/* fft/real_pass_2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_real,pass_2) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]) { size_t k, k1; const size_t factor = 2; const size_t m = n / factor; const size_t q = n / product; const size_t product_1 = product / factor; for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1; const size_t from1 = from0 + m; const ATOMIC r0 = VECTOR(in,istride,from0); const ATOMIC r1 = VECTOR(in,istride,from1); const ATOMIC s0 = r0 + r1; const ATOMIC s1 = r0 - r1; const size_t to0 = product * k1; const size_t to1 = to0 + product - 1; VECTOR(out,ostride,to0) = s0; VECTOR(out,ostride,to1) = s1; } if (product_1 == 1) return; for (k = 1; k < (product_1 + 1) / 2; k++) { /* forward real transform: w -> conjugate(w) */ const ATOMIC w_real = GSL_REAL(twiddle[k - 1]); const ATOMIC w_imag = -GSL_IMAG(twiddle[k - 1]); for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1 + 2 * k - 1; const size_t from1 = from0 + m; const ATOMIC f0_real = VECTOR(in,istride,from0); const ATOMIC f0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC f1_real = VECTOR(in,istride,from1); const ATOMIC f1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC z0_real = f0_real; const ATOMIC z0_imag = f0_imag; const ATOMIC z1_real = w_real * f1_real - w_imag * f1_imag; const ATOMIC z1_imag = w_real * f1_imag + w_imag * f1_real; /* compute x = W(2) z */ /* x0 = z0 + z1 */ const ATOMIC x0_real = z0_real + z1_real; const ATOMIC x0_imag = z0_imag + z1_imag; /* x1 = z0 - z1 */ const ATOMIC x1_real = z0_real - z1_real; const ATOMIC x1_imag = z0_imag - z1_imag; const size_t to0 = k1 * product + 2 * k - 1; const size_t to1 = k1 * product + product - 2 * k - 1; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to0 + 1) = x0_imag; /* stored in conjugate location */ VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to1 + 1) = -x1_imag; } } if (product_1 % 2 == 1) return; for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1 + product_1 - 1; const size_t from1 = from0 + m; const size_t to0 = k1 * product + product_1 - 1; VECTOR(out,ostride,to0) = VECTOR(in,istride,from0); VECTOR(out,ostride,to0 + 1) = -VECTOR(in,istride,from1); } return; } sources_5316/external/gsl/gsl_sf_exp.h0000664000176700017670000000725411705263724016655 0ustar paulpaul/* specfunc/gsl_sf_exp.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_EXP_H__ #define __GSL_SF_EXP_H__ #include "gsl_sf_result.h" #include "gsl_precision.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Provide an exp() function with GSL semantics, * i.e. with proper error checking, etc. * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_exp_e(const double x, gsl_sf_result * result); double gsl_sf_exp(const double x); /* Exp(x) * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_exp_e10_e(const double x, gsl_sf_result_e10 * result); /* Exponentiate and multiply by a given factor: y * Exp(x) * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_exp_mult_e(const double x, const double y, gsl_sf_result * result); double gsl_sf_exp_mult(const double x, const double y); /* Exponentiate and multiply by a given factor: y * Exp(x) * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_exp_mult_e10_e(const double x, const double y, gsl_sf_result_e10 * result); /* exp(x)-1 * * exceptions: GSL_EOVRFLW */ int gsl_sf_expm1_e(const double x, gsl_sf_result * result); double gsl_sf_expm1(const double x); /* (exp(x)-1)/x = 1 + x/2 + x^2/(2*3) + x^3/(2*3*4) + ... * * exceptions: GSL_EOVRFLW */ int gsl_sf_exprel_e(const double x, gsl_sf_result * result); double gsl_sf_exprel(const double x); /* 2(exp(x)-1-x)/x^2 = 1 + x/3 + x^2/(3*4) + x^3/(3*4*5) + ... * * exceptions: GSL_EOVRFLW */ int gsl_sf_exprel_2_e(double x, gsl_sf_result * result); double gsl_sf_exprel_2(const double x); /* Similarly for the N-th generalization of * the above. The so-called N-relative exponential * * exprel_N(x) = N!/x^N (exp(x) - Sum[x^k/k!, {k,0,N-1}]) * = 1 + x/(N+1) + x^2/((N+1)(N+2)) + ... * = 1F1(1,1+N,x) */ int gsl_sf_exprel_n_e(const int n, const double x, gsl_sf_result * result); double gsl_sf_exprel_n(const int n, const double x); /* Exponentiate a quantity with an associated error. */ int gsl_sf_exp_err_e(const double x, const double dx, gsl_sf_result * result); /* Exponentiate a quantity with an associated error. */ int gsl_sf_exp_err_e10_e(const double x, const double dx, gsl_sf_result_e10 * result); /* Exponentiate and multiply by a given factor: y * Exp(x), * for quantities with associated errors. * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_exp_mult_err_e(const double x, const double dx, const double y, const double dy, gsl_sf_result * result); /* Exponentiate and multiply by a given factor: y * Exp(x), * for quantities with associated errors. * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_exp_mult_err_e10_e(const double x, const double dx, const double y, const double dy, gsl_sf_result_e10 * result); __END_DECLS #endif /* __GSL_SF_EXP_H__ */ sources_5316/external/gsl/gsl_multiroots__dnewton.c0000664000176700017670000001046311723710247021473 0ustar paulpaul/* multiroots/dnewton.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multiroots.h" #include "gsl_linalg.h" /* Newton method using a finite difference approximation to the jacobian. The derivatives are estimated using a step size of h_i = sqrt(DBL_EPSILON) * x_i */ typedef struct { gsl_matrix * J; gsl_matrix * lu; gsl_permutation * permutation; } dnewton_state_t; static int dnewton_alloc (void * vstate, size_t n); static int dnewton_set (void * vstate, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx); static int dnewton_iterate (void * vstate, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx); static void dnewton_free (void * vstate); static int dnewton_alloc (void * vstate, size_t n) { dnewton_state_t * state = (dnewton_state_t *) vstate; gsl_permutation * p; gsl_matrix * m, * J; m = gsl_matrix_calloc (n,n); if (m == 0) { GSL_ERROR ("failed to allocate space for lu", GSL_ENOMEM); } state->lu = m ; p = gsl_permutation_calloc (n); if (p == 0) { gsl_matrix_free(m); GSL_ERROR ("failed to allocate space for permutation", GSL_ENOMEM); } state->permutation = p ; J = gsl_matrix_calloc (n,n); if (J == 0) { gsl_permutation_free(p); gsl_matrix_free(m); GSL_ERROR ("failed to allocate space for d", GSL_ENOMEM); } state->J = J; return GSL_SUCCESS; } static int dnewton_set (void * vstate, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx) { dnewton_state_t * state = (dnewton_state_t *) vstate; size_t i, n = function->n ; int status; status = GSL_MULTIROOT_FN_EVAL (function, x, f); if (status) return status; status = gsl_multiroot_fdjacobian (function, x, f, GSL_SQRT_DBL_EPSILON, state->J); if (status) return status; for (i = 0; i < n; i++) { gsl_vector_set (dx, i, 0.0); } return GSL_SUCCESS; } static int dnewton_iterate (void * vstate, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx) { dnewton_state_t * state = (dnewton_state_t *) vstate; int signum ; size_t i; size_t n = function->n ; gsl_matrix_memcpy (state->lu, state->J); { int status = gsl_linalg_LU_decomp (state->lu, state->permutation, &signum); if (status) return status; } { int status = gsl_linalg_LU_solve (state->lu, state->permutation, f, dx); if (status) return status; } for (i = 0; i < n; i++) { double e = gsl_vector_get (dx, i); double y = gsl_vector_get (x, i); gsl_vector_set (dx, i, -e); gsl_vector_set (x, i, y - e); } { int status = GSL_MULTIROOT_FN_EVAL (function, x, f); if (status != GSL_SUCCESS) { return GSL_EBADFUNC; } } gsl_multiroot_fdjacobian (function, x, f, GSL_SQRT_DBL_EPSILON, state->J); return GSL_SUCCESS; } static void dnewton_free (void * vstate) { dnewton_state_t * state = (dnewton_state_t *) vstate; gsl_matrix_free(state->J); gsl_matrix_free(state->lu); gsl_permutation_free(state->permutation); } static const gsl_multiroot_fsolver_type dnewton_type = {"dnewton", /* name */ sizeof (dnewton_state_t), &dnewton_alloc, &dnewton_set, &dnewton_iterate, &dnewton_free}; const gsl_multiroot_fsolver_type * gsl_multiroot_fsolver_dnewton = &dnewton_type; sources_5316/external/gsl/gsl_linalg__ptlq.c0000664000176700017670000003211411723710247020017 0ustar paulpaul/* linalg/ptlq.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * Copyright (C) 2004 Joerg Wensch, modifications for LQ. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_blas.h" #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_permute_vector.h" #include "gsl_linalg.h" #include "gsl_linalg__givens.c" #include "gsl_linalg__apply_givens.c" /* The purpose of this package is to speed up QR-decomposition for large matrices. Because QR-decomposition is column oriented, but GSL uses a row-oriented matrix format, there can considerable speedup obtained by computing the LQ-decomposition of the transposed matrix instead. This package provides LQ-decomposition and related algorithms. */ /* Factorise a general N x M matrix A into * * P A = L Q * * where Q is orthogonal (M x M) and L is lower triangular (N x M). * When A is rank deficient, r = rank(A) < n, then the permutation is * used to ensure that the lower n - r columns of L are zero and the first * l rows of Q form an orthonormal basis for the rows of A. * * Q is stored as a packed set of Householder transformations in the * strict upper triangular part of the input matrix. * * L is stored in the diagonal and lower triangle of the input matrix. * * P: column j of P is column k of the identity matrix, where k = * permutation->data[j] * * The full matrix for Q can be obtained as the product * * Q = Q_k .. Q_2 Q_1 * * where k = MIN(M,N) and * * Q_i = (I - tau_i * v_i * v_i') * * and where v_i is a Householder vector * * v_i = [1, m(i,i+1), m(i,i+2), ... , m(i,M)] * * This storage scheme is the same as in LAPACK. See LAPACK's * dgeqpf.f for details. * */ int gsl_linalg_PTLQ_decomp (gsl_matrix * A, gsl_vector * tau, gsl_permutation * p, int *signum, gsl_vector * norm) { const size_t N = A->size1; const size_t M = A->size2; if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (p->size != N) { GSL_ERROR ("permutation size must be N", GSL_EBADLEN); } else if (norm->size != N) { GSL_ERROR ("norm size must be N", GSL_EBADLEN); } else { size_t i; *signum = 1; gsl_permutation_init (p); /* set to identity */ /* Compute column norms and store in workspace */ for (i = 0; i < N; i++) { gsl_vector_view c = gsl_matrix_row (A, i); double x = gsl_blas_dnrm2 (&c.vector); gsl_vector_set (norm, i, x); } for (i = 0; i < GSL_MIN (M, N); i++) { /* Bring the column of largest norm into the pivot position */ double max_norm = gsl_vector_get(norm, i); size_t j, kmax = i; for (j = i + 1; j < N; j++) { double x = gsl_vector_get (norm, j); if (x > max_norm) { max_norm = x; kmax = j; } } if (kmax != i) { gsl_matrix_swap_rows (A, i, kmax); gsl_permutation_swap (p, i, kmax); gsl_vector_swap_elements(norm,i,kmax); (*signum) = -(*signum); } /* Compute the Householder transformation to reduce the j-th column of the matrix to a multiple of the j-th unit vector */ { gsl_vector_view c_full = gsl_matrix_row (A, i); gsl_vector_view c = gsl_vector_subvector (&c_full.vector, i, M - i); double tau_i = gsl_linalg_householder_transform (&c.vector); gsl_vector_set (tau, i, tau_i); /* Apply the transformation to the remaining columns */ if (i + 1 < N) { gsl_matrix_view m = gsl_matrix_submatrix (A, i +1, i, N - (i+1), M - i); gsl_linalg_householder_mh (tau_i, &c.vector, &m.matrix); } } /* Update the norms of the remaining columns too */ if (i + 1 < M) { for (j = i + 1; j < N; j++) { double x = gsl_vector_get (norm, j); if (x > 0.0) { double y = 0; double temp= gsl_matrix_get (A, j, i) / x; if (fabs (temp) >= 1) y = 0.0; else y = x * sqrt (1 - temp * temp); /* recompute norm to prevent loss of accuracy */ if (fabs (y / x) < sqrt (20.0) * GSL_SQRT_DBL_EPSILON) { gsl_vector_view c_full = gsl_matrix_row (A, j); gsl_vector_view c = gsl_vector_subvector(&c_full.vector, i+1, M - (i+1)); y = gsl_blas_dnrm2 (&c.vector); } gsl_vector_set (norm, j, y); } } } } return GSL_SUCCESS; } } int gsl_linalg_PTLQ_decomp2 (const gsl_matrix * A, gsl_matrix * q, gsl_matrix * r, gsl_vector * tau, gsl_permutation * p, int *signum, gsl_vector * norm) { const size_t N = A->size1; const size_t M = A->size2; if (q->size1 != M || q->size2 !=M) { GSL_ERROR ("q must be M x M", GSL_EBADLEN); } else if (r->size1 != N || r->size2 !=M) { GSL_ERROR ("r must be N x M", GSL_EBADLEN); } else if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (p->size != N) { GSL_ERROR ("permutation size must be N", GSL_EBADLEN); } else if (norm->size != N) { GSL_ERROR ("norm size must be N", GSL_EBADLEN); } gsl_matrix_memcpy (r, A); gsl_linalg_PTLQ_decomp (r, tau, p, signum, norm); /* FIXME: aliased arguments depends on behavior of unpack routine! */ gsl_linalg_LQ_unpack (r, tau, q, r); return GSL_SUCCESS; } /* Solves the system x^T A = b^T using the P^T L Q factorisation, z^T L = b^T Q^T x = P z; to obtain x. Based on SLATEC code. */ int gsl_linalg_PTLQ_solve_T (const gsl_matrix * QR, const gsl_vector * tau, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x) { if (QR->size1 != QR->size2) { GSL_ERROR ("QR matrix must be square", GSL_ENOTSQR); } else if (QR->size2 != p->size) { GSL_ERROR ("matrix size must match permutation size", GSL_EBADLEN); } else if (QR->size2 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (QR->size1 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { gsl_vector_memcpy (x, b); gsl_linalg_PTLQ_svx_T (QR, tau, p, x); return GSL_SUCCESS; } } int gsl_linalg_PTLQ_svx_T (const gsl_matrix * LQ, const gsl_vector * tau, const gsl_permutation * p, gsl_vector * x) { if (LQ->size1 != LQ->size2) { GSL_ERROR ("LQ matrix must be square", GSL_ENOTSQR); } else if (LQ->size2 != p->size) { GSL_ERROR ("matrix size must match permutation size", GSL_EBADLEN); } else if (LQ->size1 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* compute sol = b^T Q^T */ gsl_linalg_LQ_vecQT (LQ, tau, x); /* Solve L^T x = sol, storing x inplace in sol */ gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, LQ, x); gsl_permute_vector_inverse (p, x); return GSL_SUCCESS; } } int gsl_linalg_PTLQ_LQsolve_T (const gsl_matrix * Q, const gsl_matrix * L, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x) { if (Q->size1 != Q->size2 || L->size1 != L->size2) { return GSL_ENOTSQR; } else if (Q->size1 != p->size || Q->size1 != L->size1 || Q->size1 != b->size) { return GSL_EBADLEN; } else { /* compute b' = Q b */ gsl_blas_dgemv (CblasNoTrans, 1.0, Q, b, 0.0, x); /* Solve L^T x = b', storing x inplace */ gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, L, x); /* Apply permutation to solution in place */ gsl_permute_vector_inverse (p, x); return GSL_SUCCESS; } } int gsl_linalg_PTLQ_Lsolve_T (const gsl_matrix * LQ, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x) { if (LQ->size1 != LQ->size2) { GSL_ERROR ("LQ matrix must be square", GSL_ENOTSQR); } else if (LQ->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (LQ->size2 != x->size) { GSL_ERROR ("matrix size must match x size", GSL_EBADLEN); } else if (p->size != x->size) { GSL_ERROR ("permutation size must match x size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve L^T x = b, storing x inplace */ gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, LQ, x); gsl_permute_vector_inverse (p, x); return GSL_SUCCESS; } } int gsl_linalg_PTLQ_Lsvx_T (const gsl_matrix * LQ, const gsl_permutation * p, gsl_vector * x) { if (LQ->size1 != LQ->size2) { GSL_ERROR ("LQ matrix must be square", GSL_ENOTSQR); } else if (LQ->size2 != x->size) { GSL_ERROR ("matrix size must match x size", GSL_EBADLEN); } else if (p->size != x->size) { GSL_ERROR ("permutation size must match x size", GSL_EBADLEN); } else { /* Solve L^T x = b, storing x inplace */ gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, LQ, x); gsl_permute_vector_inverse (p, x); return GSL_SUCCESS; } } /* Update a P^T L Q factorisation for P A= L Q , A' = A + v u^T, PA' = PA + Pv u^T * P^T L' Q' = P^T LQ + v u^T * = P^T (L + (P v) u^T Q^T) Q * = P^T (L + (P v) w^T) Q * * where w = Q^T u. * * Algorithm from Golub and Van Loan, "Matrix Computations", Section * 12.5 (Updating Matrix Factorizations, Rank-One Changes) */ int gsl_linalg_PTLQ_update (gsl_matrix * Q, gsl_matrix * L, const gsl_permutation * p, const gsl_vector * v, gsl_vector * w) { if (Q->size1 != Q->size2 || L->size1 != L->size2) { return GSL_ENOTSQR; } else if (L->size1 != Q->size2 || v->size != Q->size2 || w->size != Q->size2) { return GSL_EBADLEN; } else { size_t j, k; const size_t N = Q->size1; const size_t M = Q->size2; double w0; /* Apply Given's rotations to reduce w to (|w|, 0, 0, ... , 0) J_1^T .... J_(n-1)^T w = +/- |w| e_1 simultaneously applied to L, H = J_1^T ... J^T_(n-1) L so that H is upper Hessenberg. (12.5.2) */ for (k = M - 1; k > 0; k--) { double c, s; double wk = gsl_vector_get (w, k); double wkm1 = gsl_vector_get (w, k - 1); create_givens (wkm1, wk, &c, &s); apply_givens_vec (w, k - 1, k, c, s); apply_givens_lq (M, N, Q, L, k - 1, k, c, s); } w0 = gsl_vector_get (w, 0); /* Add in v w^T (Equation 12.5.3) */ for (j = 0; j < N; j++) { double lj0 = gsl_matrix_get (L, j, 0); size_t p_j = gsl_permutation_get (p, j); double vj = gsl_vector_get (v, p_j); gsl_matrix_set (L, j, 0, lj0 + w0 * vj); } /* Apply Givens transformations L' = G_(n-1)^T ... G_1^T H Equation 12.5.4 */ for (k = 1; k < N; k++) { double c, s; double diag = gsl_matrix_get (L, k - 1, k - 1); double offdiag = gsl_matrix_get (L, k - 1, k ); create_givens (diag, offdiag, &c, &s); apply_givens_lq (M, N, Q, L, k - 1, k, c, s); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_cblas__dtrmm.c0000664000176700017670000000073111723710247020000 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dtrmm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const double alpha, const double *A, const int lda, double *B, const int ldb) { #define BASE double #include "gsl_cblas__source_trmm_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__chemm.c0000664000176700017670000000066511723710247017754 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_chemm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc) { #define BASE float #include "gsl_cblas__source_hemm.h" #undef BASE } sources_5316/external/gsl/gsl_fft__c_pass.h0000664000176700017670000001137111705263724017632 0ustar paulpaul/* fft/c_pass.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int FUNCTION(fft_complex,pass_2) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]); static int FUNCTION(fft_complex,pass_3) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[]); static int FUNCTION(fft_complex,pass_4) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[]); static int FUNCTION(fft_complex,pass_5) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[]); static int FUNCTION(fft_complex,pass_6) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[], const TYPE(gsl_complex) twiddle5[]); static int FUNCTION(fft_complex,pass_7) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[], const TYPE(gsl_complex) twiddle5[], const TYPE(gsl_complex) twiddle6[]); static int FUNCTION(fft_complex,pass_n) (BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t factor, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]); sources_5316/external/gsl/gsl_cblas__zhpr.c0000664000176700017670000000050011723710247017632 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zhpr (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const void *X, const int incX, void *Ap) { #define BASE double #include "gsl_cblas__source_hpr.h" #undef BASE } sources_5316/external/gsl/gsl_sf__bessel_k.c0000644000176700017670000001447410707442037017777 0ustar paulpaul/* specfunc/bessel_k.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_gamma.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__check.h" #include "gsl_sf__bessel.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* [Abramowitz+Stegun, 10.2.4 + 10.2.6] * with lmax=15, precision ~ 15D for x < 3 * * assumes l >= 1 */ static int bessel_kl_scaled_small_x(int l, const double x, gsl_sf_result * result) { gsl_sf_result num_fact; double den = gsl_sf_pow_int(x, l+1); int stat_df = gsl_sf_doublefact_e((unsigned int) (2*l-1), &num_fact); if(stat_df != GSL_SUCCESS || den == 0.0) { OVERFLOW_ERROR(result); } else { const int lmax = 50; gsl_sf_result ipos_term; double ineg_term; double sgn = (GSL_IS_ODD(l) ? -1.0 : 1.0); double ex = exp(x); double t = 0.5*x*x; double sum = 1.0; double t_coeff = 1.0; double t_power = 1.0; double delta; int stat_il; int i; for(i=1; ival = -sgn * 0.5*M_PI * (ex*ipos_term.val - ineg_term); result->val *= ex; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_il; } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_k0_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else { result->val = M_PI/(2.0*x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_bessel_k1_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < (M_SQRTPI+1.0)/(M_SQRT2*GSL_SQRT_DBL_MAX)) { OVERFLOW_ERROR(result); } else { result->val = M_PI/(2.0*x) * (1.0 + 1.0/x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_bessel_k2_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0/GSL_ROOT3_DBL_MAX) { OVERFLOW_ERROR(result); } else { result->val = M_PI/(2.0*x) * (1.0 + 3.0/x * (1.0 + 1.0/x)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_bessel_kl_scaled_e(int l, const double x, gsl_sf_result * result) { if(l < 0 || x <= 0.0) { DOMAIN_ERROR(result); } else if(l == 0) { return gsl_sf_bessel_k0_scaled_e(x, result); } else if(l == 1) { return gsl_sf_bessel_k1_scaled_e(x, result); } else if(l == 2) { return gsl_sf_bessel_k2_scaled_e(x, result); } else if(x < 3.0) { return bessel_kl_scaled_small_x(l, x, result); } else if(GSL_ROOT3_DBL_EPSILON * x > (l*l + l + 1)) { int status = gsl_sf_bessel_Knu_scaled_asympx_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= pre; result->err *= pre; return status; } else if(GSL_MIN(0.29/(l*l+1.0), 0.5/(l*l+1.0+x*x)) < GSL_ROOT3_DBL_EPSILON) { int status = gsl_sf_bessel_Knu_scaled_asymp_unif_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= pre; result->err *= pre; return status; } else { /* recurse upward */ gsl_sf_result r_bk; gsl_sf_result r_bkm; int stat_1 = gsl_sf_bessel_k1_scaled_e(x, &r_bk); int stat_0 = gsl_sf_bessel_k0_scaled_e(x, &r_bkm); double bkp; double bk = r_bk.val; double bkm = r_bkm.val; int j; for(j=1; jval = bk; result->err = fabs(bk) * (fabs(r_bk.err/r_bk.val) + fabs(r_bkm.err/r_bkm.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_1, stat_0); } } int gsl_sf_bessel_kl_scaled_array(const int lmax, const double x, double * result_array) { if(lmax < 0 || x <= 0.0) { GSL_ERROR("domain error", GSL_EDOM); } else if (lmax == 0) { gsl_sf_result result; int stat = gsl_sf_bessel_k0_scaled_e(x, &result); result_array[0] = result.val; return stat; } else { int ell; double kellp1, kell, kellm1; gsl_sf_result r_kell; gsl_sf_result r_kellm1; gsl_sf_bessel_k1_scaled_e(x, &r_kell); gsl_sf_bessel_k0_scaled_e(x, &r_kellm1); kell = r_kell.val; kellm1 = r_kellm1.val; result_array[0] = kellm1; result_array[1] = kell; for(ell = 1; ell < lmax; ell++) { kellp1 = (2*ell+1)/x * kell + kellm1; result_array[ell+1] = kellp1; kellm1 = kell; kell = kellp1; } return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_k0_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_k0_scaled_e(x, &result)); } double gsl_sf_bessel_k1_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_k1_scaled_e(x, &result)); } double gsl_sf_bessel_k2_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_k2_scaled_e(x, &result)); } double gsl_sf_bessel_kl_scaled(const int l, const double x) { EVAL_RESULT(gsl_sf_bessel_kl_scaled_e(l, x, &result)); } sources_5316/external/gsl/gsl_multiroots__gnewton.c0000664000176700017670000001177211723710247021502 0ustar paulpaul/* multiroots/gnewton.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multiroots.h" #include "gsl_linalg.h" #include "gsl_multiroots__enorm.c" /* Simple globally convergent Newton method (rejects uphill steps) */ typedef struct { double phi; gsl_vector * x_trial; gsl_vector * d; gsl_matrix * lu; gsl_permutation * permutation; } gnewton_state_t; static int gnewton_alloc (void * vstate, size_t n); static int gnewton_set (void * vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static int gnewton_iterate (void * vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static void gnewton_free (void * vstate); static int gnewton_alloc (void * vstate, size_t n) { gnewton_state_t * state = (gnewton_state_t *) vstate; gsl_vector * d, * x_trial ; gsl_permutation * p; gsl_matrix * m; m = gsl_matrix_calloc (n,n); if (m == 0) { GSL_ERROR ("failed to allocate space for lu", GSL_ENOMEM); } state->lu = m ; p = gsl_permutation_calloc (n); if (p == 0) { gsl_matrix_free(m); GSL_ERROR ("failed to allocate space for permutation", GSL_ENOMEM); } state->permutation = p ; d = gsl_vector_calloc (n); if (d == 0) { gsl_permutation_free(p); gsl_matrix_free(m); GSL_ERROR ("failed to allocate space for d", GSL_ENOMEM); } state->d = d; x_trial = gsl_vector_calloc (n); if (x_trial == 0) { gsl_vector_free(d); gsl_permutation_free(p); gsl_matrix_free(m); GSL_ERROR ("failed to allocate space for x_trial", GSL_ENOMEM); } state->x_trial = x_trial; return GSL_SUCCESS; } static int gnewton_set (void * vstate, gsl_multiroot_function_fdf * FDF, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { gnewton_state_t * state = (gnewton_state_t *) vstate; size_t i, n = FDF->n ; GSL_MULTIROOT_FN_EVAL_F_DF (FDF, x, f, J); for (i = 0; i < n; i++) { gsl_vector_set (dx, i, 0.0); } state->phi = enorm(f); return GSL_SUCCESS; } static int gnewton_iterate (void * vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { gnewton_state_t * state = (gnewton_state_t *) vstate; int signum ; double t, phi0, phi1; size_t i; size_t n = fdf->n ; gsl_matrix_memcpy (state->lu, J); gsl_linalg_LU_decomp (state->lu, state->permutation, &signum); gsl_linalg_LU_solve (state->lu, state->permutation, f, state->d); t = 1; phi0 = state->phi; new_step: for (i = 0; i < n; i++) { double di = gsl_vector_get (state->d, i); double xi = gsl_vector_get (x, i); gsl_vector_set (state->x_trial, i, xi - t*di); } { int status = GSL_MULTIROOT_FN_EVAL_F (fdf, state->x_trial, f); if (status != GSL_SUCCESS) { return GSL_EBADFUNC; } } phi1 = enorm (f); if (phi1 > phi0 && t > GSL_DBL_EPSILON) { /* full step goes uphill, take a reduced step instead */ double theta = phi1 / phi0; double u = (sqrt(1.0 + 6.0 * theta) - 1.0) / (3.0 * theta); t *= u ; goto new_step; } /* copy x_trial into x */ gsl_vector_memcpy (x, state->x_trial); for (i = 0; i < n; i++) { double di = gsl_vector_get (state->d, i); gsl_vector_set (dx, i, -t*di); } { int status = GSL_MULTIROOT_FN_EVAL_DF (fdf, x, J); if (status != GSL_SUCCESS) { return GSL_EBADFUNC; } } state->phi = phi1; return GSL_SUCCESS; } static void gnewton_free (void * vstate) { gnewton_state_t * state = (gnewton_state_t *) vstate; gsl_vector_free(state->d); gsl_vector_free(state->x_trial); gsl_matrix_free(state->lu); gsl_permutation_free(state->permutation); } static const gsl_multiroot_fdfsolver_type gnewton_type = {"gnewton", /* name */ sizeof (gnewton_state_t), &gnewton_alloc, &gnewton_set, &gnewton_iterate, &gnewton_free}; const gsl_multiroot_fdfsolver_type * gsl_multiroot_fdfsolver_gnewton = &gnewton_type; sources_5316/external/gsl/gsl_block_complex_long_double.h0000664000176700017670000000531311705263724022555 0ustar paulpaul/* block/gsl_block_complex_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_COMPLEX_LONG_DOUBLE_H__ #define __GSL_BLOCK_COMPLEX_LONG_DOUBLE_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_complex_long_double_struct { size_t size; long double *data; }; typedef struct gsl_block_complex_long_double_struct gsl_block_complex_long_double; gsl_block_complex_long_double *gsl_block_complex_long_double_alloc (const size_t n); gsl_block_complex_long_double *gsl_block_complex_long_double_calloc (const size_t n); void gsl_block_complex_long_double_free (gsl_block_complex_long_double * b); int gsl_block_complex_long_double_fread (FILE * stream, gsl_block_complex_long_double * b); int gsl_block_complex_long_double_fwrite (FILE * stream, const gsl_block_complex_long_double * b); int gsl_block_complex_long_double_fscanf (FILE * stream, gsl_block_complex_long_double * b); int gsl_block_complex_long_double_fprintf (FILE * stream, const gsl_block_complex_long_double * b, const char *format); int gsl_block_complex_long_double_raw_fread (FILE * stream, long double * b, const size_t n, const size_t stride); int gsl_block_complex_long_double_raw_fwrite (FILE * stream, const long double * b, const size_t n, const size_t stride); int gsl_block_complex_long_double_raw_fscanf (FILE * stream, long double * b, const size_t n, const size_t stride); int gsl_block_complex_long_double_raw_fprintf (FILE * stream, const long double * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_complex_long_double_size (const gsl_block_complex_long_double * b); long double * gsl_block_complex_long_double_data (const gsl_block_complex_long_double * b); __END_DECLS #endif /* __GSL_BLOCK_COMPLEX_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_specfunc__bessel_Inu.c0000664000176700017670000000660111723710247021471 0ustar paulpaul/* specfunc/bessel_Inu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_temme.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Inu_scaled_e(double nu, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else if(x*x < 10.0*(nu+1.0)) { gsl_sf_result b; double ex = exp(-x); int stat = gsl_sf_bessel_IJ_taylor_e(nu, x, 1, 100, GSL_DBL_EPSILON, &b); result->val = b.val * ex; result->err = b.err * ex; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } else if(0.5/(nu*nu + x*x) < GSL_ROOT3_DBL_EPSILON) { return gsl_sf_bessel_Inu_scaled_asymp_unif_e(nu, x, result); } else { int N = (int)(nu + 0.5); double mu = nu - N; /* -1/2 <= mu <= 1/2 */ double K_mu, K_mup1, Kp_mu; double K_nu, K_nup1, K_num1; double I_nu_ratio; int stat_Irat; int stat_Kmu; int n; /* obtain K_mu, K_mup1 */ if(x < 2.0) { stat_Kmu = gsl_sf_bessel_K_scaled_temme(mu, x, &K_mu, &K_mup1, &Kp_mu); } else { stat_Kmu = gsl_sf_bessel_K_scaled_steed_temme_CF2(mu, x, &K_mu, &K_mup1, &Kp_mu); } /* recurse forward to obtain K_num1, K_nu */ K_nu = K_mu; K_nup1 = K_mup1; for(n=0; nval = 1.0/(x * (K_nup1 + I_nu_ratio * K_nu)); result->err = GSL_DBL_EPSILON * (0.5*N + 2.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Kmu, stat_Irat); } } int gsl_sf_bessel_Inu_e(double nu, double x, gsl_sf_result * result) { gsl_sf_result b; int stat_I = gsl_sf_bessel_Inu_scaled_e(nu, x, &b); int stat_e = gsl_sf_exp_mult_err_e(x, fabs(x*GSL_DBL_EPSILON), b.val, b.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_I); } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_Inu_scaled(double nu, double x) { EVAL_RESULT(gsl_sf_bessel_Inu_scaled_e(nu, x, &result)); } double gsl_sf_bessel_Inu(double nu, double x) { EVAL_RESULT(gsl_sf_bessel_Inu_e(nu, x, &result)); } sources_5316/external/gsl/gsl_randist__gausszig.c0000664000176700017670000002163511723710247021077 0ustar paulpaul/* gauss.c - gaussian random numbers, using the Ziggurat method * * Copyright (C) 2005 Jochen Voss. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ /* * This routine is based on the following article, with a couple of * modifications which simplify the implementation. * * George Marsaglia, Wai Wan Tsang * The Ziggurat Method for Generating Random Variables * Journal of Statistical Software, vol. 5 (2000), no. 8 * http://www.jstatsoft.org/v05/i08/ * * The modifications are: * * 1) use 128 steps instead of 256 to decrease the amount of static * data necessary. * * 2) use an acceptance sampling from an exponential wedge * exp(-R*(x-R/2)) for the tail of the base strip to simplify the * implementation. The area of exponential wedge is used in * calculating 'v' and the coefficients in ziggurat table, so the * coefficients differ slightly from those in the Marsaglia and Tsang * paper. * * See also Leong et al, "A Comment on the Implementation of the * Ziggurat Method", Journal of Statistical Software, vol 5 (2005), no 7. * */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_randist.h" /* position of right-most step */ #define PARAM_R 3.44428647676 /* tabulated values for the heigt of the Ziggurat levels */ static const double ytab[128] = { 1, 0.963598623011, 0.936280813353, 0.913041104253, 0.892278506696, 0.873239356919, 0.855496407634, 0.838778928349, 0.822902083699, 0.807732738234, 0.793171045519, 0.779139726505, 0.765577436082, 0.752434456248, 0.739669787677, 0.727249120285, 0.715143377413, 0.703327646455, 0.691780377035, 0.68048276891, 0.669418297233, 0.65857233912, 0.647931876189, 0.637485254896, 0.62722199145, 0.617132611532, 0.607208517467, 0.597441877296, 0.587825531465, 0.578352913803, 0.569017984198, 0.559815170911, 0.550739320877, 0.541785656682, 0.532949739145, 0.524227434628, 0.515614886373, 0.507108489253, 0.498704867478, 0.490400854812, 0.482193476986, 0.47407993601, 0.466057596125, 0.458123971214, 0.450276713467, 0.442513603171, 0.434832539473, 0.427231532022, 0.419708693379, 0.41226223212, 0.404890446548, 0.397591718955, 0.390364510382, 0.383207355816, 0.376118859788, 0.369097692334, 0.362142585282, 0.355252328834, 0.348425768415, 0.341661801776, 0.334959376311, 0.328317486588, 0.321735172063, 0.31521151497, 0.308745638367, 0.302336704338, 0.29598391232, 0.289686497571, 0.283443729739, 0.27725491156, 0.271119377649, 0.265036493387, 0.259005653912, 0.253026283183, 0.247097833139, 0.241219782932, 0.235391638239, 0.229612930649, 0.223883217122, 0.218202079518, 0.212569124201, 0.206983981709, 0.201446306496, 0.195955776745, 0.190512094256, 0.185114984406, 0.179764196185, 0.174459502324, 0.169200699492, 0.1639876086, 0.158820075195, 0.153697969964, 0.148621189348, 0.143589656295, 0.138603321143, 0.133662162669, 0.128766189309, 0.123915440582, 0.119109988745, 0.114349940703, 0.10963544023, 0.104966670533, 0.100343857232, 0.0957672718266, 0.0912372357329, 0.0867541250127, 0.082318375932, 0.0779304915295, 0.0735910494266, 0.0693007111742, 0.065060233529, 0.0608704821745, 0.056732448584, 0.05264727098, 0.0486162607163, 0.0446409359769, 0.0407230655415, 0.0368647267386, 0.0330683839378, 0.0293369977411, 0.0256741818288, 0.0220844372634, 0.0185735200577, 0.0151490552854, 0.0118216532614, 0.00860719483079, 0.00553245272614, 0.00265435214565 }; /* tabulated values for 2^24 times x[i]/x[i+1], * used to accept for U*x[i+1]<=x[i] without any floating point operations */ static const unsigned long ktab[128] = { 0, 12590644, 14272653, 14988939, 15384584, 15635009, 15807561, 15933577, 16029594, 16105155, 16166147, 16216399, 16258508, 16294295, 16325078, 16351831, 16375291, 16396026, 16414479, 16431002, 16445880, 16459343, 16471578, 16482744, 16492970, 16502368, 16511031, 16519039, 16526459, 16533352, 16539769, 16545755, 16551348, 16556584, 16561493, 16566101, 16570433, 16574511, 16578353, 16581977, 16585398, 16588629, 16591685, 16594575, 16597311, 16599901, 16602354, 16604679, 16606881, 16608968, 16610945, 16612818, 16614592, 16616272, 16617861, 16619363, 16620782, 16622121, 16623383, 16624570, 16625685, 16626730, 16627708, 16628619, 16629465, 16630248, 16630969, 16631628, 16632228, 16632768, 16633248, 16633671, 16634034, 16634340, 16634586, 16634774, 16634903, 16634972, 16634980, 16634926, 16634810, 16634628, 16634381, 16634066, 16633680, 16633222, 16632688, 16632075, 16631380, 16630598, 16629726, 16628757, 16627686, 16626507, 16625212, 16623794, 16622243, 16620548, 16618698, 16616679, 16614476, 16612071, 16609444, 16606571, 16603425, 16599973, 16596178, 16591995, 16587369, 16582237, 16576520, 16570120, 16562917, 16554758, 16545450, 16534739, 16522287, 16507638, 16490152, 16468907, 16442518, 16408804, 16364095, 16301683, 16207738, 16047994, 15704248, 15472926 }; /* tabulated values of 2^{-24}*x[i] */ static const double wtab[128] = { 1.62318314817e-08, 2.16291505214e-08, 2.54246305087e-08, 2.84579525938e-08, 3.10340022482e-08, 3.33011726243e-08, 3.53439060345e-08, 3.72152672658e-08, 3.8950989572e-08, 4.05763964764e-08, 4.21101548915e-08, 4.35664624904e-08, 4.49563968336e-08, 4.62887864029e-08, 4.75707945735e-08, 4.88083237257e-08, 5.00063025384e-08, 5.11688950428e-08, 5.22996558616e-08, 5.34016475624e-08, 5.44775307871e-08, 5.55296344581e-08, 5.65600111659e-08, 5.75704813695e-08, 5.85626690412e-08, 5.95380306862e-08, 6.04978791776e-08, 6.14434034901e-08, 6.23756851626e-08, 6.32957121259e-08, 6.42043903937e-08, 6.51025540077e-08, 6.59909735447e-08, 6.68703634341e-08, 6.77413882848e-08, 6.8604668381e-08, 6.94607844804e-08, 7.03102820203e-08, 7.11536748229e-08, 7.1991448372e-08, 7.2824062723e-08, 7.36519550992e-08, 7.44755422158e-08, 7.52952223703e-08, 7.61113773308e-08, 7.69243740467e-08, 7.77345662086e-08, 7.85422956743e-08, 7.93478937793e-08, 8.01516825471e-08, 8.09539758128e-08, 8.17550802699e-08, 8.25552964535e-08, 8.33549196661e-08, 8.41542408569e-08, 8.49535474601e-08, 8.57531242006e-08, 8.65532538723e-08, 8.73542180955e-08, 8.8156298059e-08, 8.89597752521e-08, 8.97649321908e-08, 9.05720531451e-08, 9.138142487e-08, 9.21933373471e-08, 9.30080845407e-08, 9.38259651738e-08, 9.46472835298e-08, 9.54723502847e-08, 9.63014833769e-08, 9.71350089201e-08, 9.79732621669e-08, 9.88165885297e-08, 9.96653446693e-08, 1.00519899658e-07, 1.0138063623e-07, 1.02247952126e-07, 1.03122261554e-07, 1.04003996769e-07, 1.04893609795e-07, 1.05791574313e-07, 1.06698387725e-07, 1.07614573423e-07, 1.08540683296e-07, 1.09477300508e-07, 1.1042504257e-07, 1.11384564771e-07, 1.12356564007e-07, 1.13341783071e-07, 1.14341015475e-07, 1.15355110887e-07, 1.16384981291e-07, 1.17431607977e-07, 1.18496049514e-07, 1.19579450872e-07, 1.20683053909e-07, 1.21808209468e-07, 1.2295639141e-07, 1.24129212952e-07, 1.25328445797e-07, 1.26556042658e-07, 1.27814163916e-07, 1.29105209375e-07, 1.30431856341e-07, 1.31797105598e-07, 1.3320433736e-07, 1.34657379914e-07, 1.36160594606e-07, 1.37718982103e-07, 1.39338316679e-07, 1.41025317971e-07, 1.42787873535e-07, 1.44635331499e-07, 1.4657889173e-07, 1.48632138436e-07, 1.50811780719e-07, 1.53138707402e-07, 1.55639532047e-07, 1.58348931426e-07, 1.61313325908e-07, 1.64596952856e-07, 1.68292495203e-07, 1.72541128694e-07, 1.77574279496e-07, 1.83813550477e-07, 1.92166040885e-07, 2.05295471952e-07, 2.22600839893e-07 }; double gsl_ran_gaussian_ziggurat (const gsl_rng * r, const double sigma) { unsigned long int i, j; int sign; double x, y; while (1) { i = gsl_rng_uniform_int (r, 256); /* choose the step */ j = gsl_rng_uniform_int (r, 16777216); /* sample from 2^24 */ sign = (i & 0x80) ? +1 : -1; i &= 0x7f; x = j * wtab[i]; if (j < ktab[i]) break; if (i < 127) { double y0, y1, U1; y0 = ytab[i]; y1 = ytab[i + 1]; U1 = gsl_rng_uniform (r); y = y1 + (y0 - y1) * U1; } else { double U1, U2; U1 = 1.0 - gsl_rng_uniform (r); U2 = gsl_rng_uniform (r); x = PARAM_R - log (U1) / PARAM_R; y = exp (-PARAM_R * (x - 0.5 * PARAM_R)) * U2; } if (y < exp (-0.5 * x * x)) break; } return sign * sigma * x; } sources_5316/external/gsl/gsl_sys__ldfrexp.c0000664000176700017670000000260211723710247020052 0ustar paulpaul/* sys/ldfrexp.c * * Copyright (C) 2002, Gert Van den Eynde * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" double gsl_ldexp (const double x, const int e) { double p2 = pow (2.0, (double)e); return x * p2; } double gsl_frexp (const double x, int *e) { if (x == 0.0) { *e = 0; return 0.0; } else { double ex = ceil (log (fabs (x)) / M_LN2); int ei = (int) ex; double f = gsl_ldexp (x, -ei); while (fabs (f) >= 1.0) { ei++; f /= 2.0; } while (fabs (f) < 0.5) { ei--; f *= 2.0; } *e = ei; return f; } } sources_5316/external/gsl/gsl_spline.h0000664000176700017670000000533111705263724016655 0ustar paulpaul/* interpolation/gsl_spline.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SPLINE_H__ #define __GSL_SPLINE_H__ #include #include "gsl_interp.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* general interpolation object */ typedef struct { gsl_interp * interp; double * x; double * y; size_t size; } gsl_spline; gsl_spline * gsl_spline_alloc(const gsl_interp_type * T, size_t size); int gsl_spline_init(gsl_spline * spline, const double xa[], const double ya[], size_t size); const char * gsl_spline_name(const gsl_spline * spline); unsigned int gsl_spline_min_size(const gsl_spline * spline); int gsl_spline_eval_e(const gsl_spline * spline, double x, gsl_interp_accel * a, double * y); double gsl_spline_eval(const gsl_spline * spline, double x, gsl_interp_accel * a); int gsl_spline_eval_deriv_e(const gsl_spline * spline, double x, gsl_interp_accel * a, double * y); double gsl_spline_eval_deriv(const gsl_spline * spline, double x, gsl_interp_accel * a); int gsl_spline_eval_deriv2_e(const gsl_spline * spline, double x, gsl_interp_accel * a, double * y); double gsl_spline_eval_deriv2(const gsl_spline * spline, double x, gsl_interp_accel * a); int gsl_spline_eval_integ_e(const gsl_spline * spline, double a, double b, gsl_interp_accel * acc, double * y); double gsl_spline_eval_integ(const gsl_spline * spline, double a, double b, gsl_interp_accel * acc); void gsl_spline_free(gsl_spline * spline); __END_DECLS #endif /* __GSL_INTERP_H__ */ sources_5316/external/gsl/gsl_cblas__dsdot.c0000664000176700017670000000052111723710247017767 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" double cblas_dsdot (const int N, const float *X, const int incX, const float *Y, const int incY) { #define INIT_VAL 0.0 #define ACC_TYPE double #define BASE float #include "gsl_cblas__source_dot_r.h" #undef ACC_TYPE #undef BASE #undef INIT_VAL } sources_5316/external/gsl/gsl_cblas__source_syrk_r.h0000664000176700017670000000606311705263724021562 0ustar paulpaul/* blas/source_syrk_r.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; int uplo, trans; if (alpha == 0.0 && beta == 1.0) return; if (Order == CblasRowMajor) { uplo = Uplo; trans = (Trans == CblasConjTrans) ? CblasTrans : Trans; } else { uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; if (Trans == CblasTrans || Trans == CblasConjTrans) { trans = CblasNoTrans; } else { trans = CblasTrans; } } /* form y := beta*y */ if (beta == 0.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { C[ldc * i + j] = 0.0; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { C[ldc * i + j] = 0.0; } } } } else if (beta != 1.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { C[ldc * i + j] *= beta; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { C[ldc * i + j] *= beta; } } } } if (alpha == 0.0) return; if (uplo == CblasUpper && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { BASE temp = 0.0; for (k = 0; k < K; k++) { temp += A[i * lda + k] * A[j * lda + k]; } C[i * ldc + j] += alpha * temp; } } } else if (uplo == CblasUpper && trans == CblasTrans) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { BASE temp = 0.0; for (k = 0; k < K; k++) { temp += A[k * lda + i] * A[k * lda + j]; } C[i * ldc + j] += alpha * temp; } } } else if (uplo == CblasLower && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { BASE temp = 0.0; for (k = 0; k < K; k++) { temp += A[i * lda + k] * A[j * lda + k]; } C[i * ldc + j] += alpha * temp; } } } else if (uplo == CblasLower && trans == CblasTrans) { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { BASE temp = 0.0; for (k = 0; k < K; k++) { temp += A[k * lda + i] * A[k * lda + j]; } C[i * ldc + j] += alpha * temp; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_poly__eval.c0000664000176700017670000000225611723710247017507 0ustar paulpaul/* poly/eval.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_poly.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*-*/ /* checked OK [GJ] Tue May 5 12:19:56 MDT 1998 */ #ifndef HIDE_INLINE_STATIC double gsl_poly_eval(const double c[], const int len, const double x) { int i; double ans = c[len-1]; for(i=len-1; i>0; i--) ans = c[i-1] + x * ans; return ans; } #endif sources_5316/external/gsl/gsl_vector_uchar.h0000664000176700017670000001634211705263724020053 0ustar paulpaul/* vector/gsl_vector_uchar.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_UCHAR_H__ #define __GSL_VECTOR_UCHAR_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_uchar.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; unsigned char *data; gsl_block_uchar *block; int owner; } gsl_vector_uchar; typedef struct { gsl_vector_uchar vector; } _gsl_vector_uchar_view; typedef _gsl_vector_uchar_view gsl_vector_uchar_view; typedef struct { gsl_vector_uchar vector; } _gsl_vector_uchar_const_view; typedef const _gsl_vector_uchar_const_view gsl_vector_uchar_const_view; /* Allocation */ gsl_vector_uchar *gsl_vector_uchar_alloc (const size_t n); gsl_vector_uchar *gsl_vector_uchar_calloc (const size_t n); gsl_vector_uchar *gsl_vector_uchar_alloc_from_block (gsl_block_uchar * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_uchar *gsl_vector_uchar_alloc_from_vector (gsl_vector_uchar * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_uchar_free (gsl_vector_uchar * v); /* Views */ _gsl_vector_uchar_view gsl_vector_uchar_view_array (unsigned char *v, size_t n); _gsl_vector_uchar_view gsl_vector_uchar_view_array_with_stride (unsigned char *base, size_t stride, size_t n); _gsl_vector_uchar_const_view gsl_vector_uchar_const_view_array (const unsigned char *v, size_t n); _gsl_vector_uchar_const_view gsl_vector_uchar_const_view_array_with_stride (const unsigned char *base, size_t stride, size_t n); _gsl_vector_uchar_view gsl_vector_uchar_subvector (gsl_vector_uchar *v, size_t i, size_t n); _gsl_vector_uchar_view gsl_vector_uchar_subvector_with_stride (gsl_vector_uchar *v, size_t i, size_t stride, size_t n); _gsl_vector_uchar_const_view gsl_vector_uchar_const_subvector (const gsl_vector_uchar *v, size_t i, size_t n); _gsl_vector_uchar_const_view gsl_vector_uchar_const_subvector_with_stride (const gsl_vector_uchar *v, size_t i, size_t stride, size_t n); /* Operations */ unsigned char gsl_vector_uchar_get (const gsl_vector_uchar * v, const size_t i); void gsl_vector_uchar_set (gsl_vector_uchar * v, const size_t i, unsigned char x); unsigned char *gsl_vector_uchar_ptr (gsl_vector_uchar * v, const size_t i); const unsigned char *gsl_vector_uchar_const_ptr (const gsl_vector_uchar * v, const size_t i); void gsl_vector_uchar_set_zero (gsl_vector_uchar * v); void gsl_vector_uchar_set_all (gsl_vector_uchar * v, unsigned char x); int gsl_vector_uchar_set_basis (gsl_vector_uchar * v, size_t i); int gsl_vector_uchar_fread (FILE * stream, gsl_vector_uchar * v); int gsl_vector_uchar_fwrite (FILE * stream, const gsl_vector_uchar * v); int gsl_vector_uchar_fscanf (FILE * stream, gsl_vector_uchar * v); int gsl_vector_uchar_fprintf (FILE * stream, const gsl_vector_uchar * v, const char *format); int gsl_vector_uchar_memcpy (gsl_vector_uchar * dest, const gsl_vector_uchar * src); int gsl_vector_uchar_reverse (gsl_vector_uchar * v); int gsl_vector_uchar_swap (gsl_vector_uchar * v, gsl_vector_uchar * w); int gsl_vector_uchar_swap_elements (gsl_vector_uchar * v, const size_t i, const size_t j); unsigned char gsl_vector_uchar_max (const gsl_vector_uchar * v); unsigned char gsl_vector_uchar_min (const gsl_vector_uchar * v); void gsl_vector_uchar_minmax (const gsl_vector_uchar * v, unsigned char * min_out, unsigned char * max_out); size_t gsl_vector_uchar_max_index (const gsl_vector_uchar * v); size_t gsl_vector_uchar_min_index (const gsl_vector_uchar * v); void gsl_vector_uchar_minmax_index (const gsl_vector_uchar * v, size_t * imin, size_t * imax); int gsl_vector_uchar_add (gsl_vector_uchar * a, const gsl_vector_uchar * b); int gsl_vector_uchar_sub (gsl_vector_uchar * a, const gsl_vector_uchar * b); int gsl_vector_uchar_mul (gsl_vector_uchar * a, const gsl_vector_uchar * b); int gsl_vector_uchar_div (gsl_vector_uchar * a, const gsl_vector_uchar * b); int gsl_vector_uchar_scale (gsl_vector_uchar * a, const double x); int gsl_vector_uchar_add_constant (gsl_vector_uchar * a, const double x); int gsl_vector_uchar_isnull (const gsl_vector_uchar * v); int gsl_vector_uchar_ispos (const gsl_vector_uchar * v); int gsl_vector_uchar_isneg (const gsl_vector_uchar * v); int gsl_vector_uchar_isnonneg (const gsl_vector_uchar * v); #ifdef HAVE_INLINE extern inline unsigned char gsl_vector_uchar_get (const gsl_vector_uchar * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_uchar_set (gsl_vector_uchar * v, const size_t i, unsigned char x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline unsigned char * gsl_vector_uchar_ptr (gsl_vector_uchar * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (unsigned char *) (v->data + i * v->stride); } extern inline const unsigned char * gsl_vector_uchar_const_ptr (const gsl_vector_uchar * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const unsigned char *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_UCHAR_H__ */ sources_5316/external/gsl/gsl_sf__bessel_j.c0000644000176700017670000002547110707442037017775 0ustar paulpaul/* specfunc/bessel_j.c * * Copyright (C) 1996,1997,1998,1999,2000,2001,2002,2003 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_olver.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_j0_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(ax < 0.5) { const double y = x*x; const double c1 = -1.0/6.0; const double c2 = 1.0/120.0; const double c3 = -1.0/5040.0; const double c4 = 1.0/362880.0; const double c5 = -1.0/39916800.0; const double c6 = 1.0/6227020800.0; result->val = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*c6))))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result sin_result; const int stat = gsl_sf_sin_e(x, &sin_result); result->val = sin_result.val/x; result->err = fabs(sin_result.err/x); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } } int gsl_sf_bessel_j1_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 3.1*GSL_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(ax < 0.25) { const double y = x*x; const double c1 = -1.0/10.0; const double c2 = 1.0/280.0; const double c3 = -1.0/15120.0; const double c4 = 1.0/1330560.0; const double c5 = -1.0/172972800.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*c5)))); result->val = x/3.0 * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result cos_result; gsl_sf_result sin_result; const int stat_cos = gsl_sf_cos_e(x, &cos_result); const int stat_sin = gsl_sf_sin_e(x, &sin_result); const double cos_x = cos_result.val; const double sin_x = sin_result.val; result->val = (sin_x/x - cos_x)/x; result->err = (fabs(sin_result.err/x) + fabs(cos_result.err))/fabs(x); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(sin_x/(x*x)) + fabs(cos_x/x)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_cos, stat_sin); } } int gsl_sf_bessel_j2_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 4.0*GSL_SQRT_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(ax < 1.3) { const double y = x*x; const double c1 = -1.0/14.0; const double c2 = 1.0/504.0; const double c3 = -1.0/33264.0; const double c4 = 1.0/3459456.0; const double c5 = -1.0/518918400; const double c6 = 1.0/105859353600.0; const double c7 = -1.0/28158588057600.0; const double c8 = 1.0/9461285587353600.0; const double c9 = -1.0/3916972233164390400.0; const double sum = 1.0+y*(c1+y*(c2+y*(c3+y*(c4+y*(c5+y*(c6+y*(c7+y*(c8+y*c9)))))))); result->val = y/15.0 * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result cos_result; gsl_sf_result sin_result; const int stat_cos = gsl_sf_cos_e(x, &cos_result); const int stat_sin = gsl_sf_sin_e(x, &sin_result); const double cos_x = cos_result.val; const double sin_x = sin_result.val; const double f = (3.0/(x*x) - 1.0); result->val = (f * sin_x - 3.0*cos_x/x)/x; result->err = fabs(f * sin_result.err/x) + fabs((3.0*cos_result.err/x)/x); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(f*sin_x/x) + 3.0*fabs(cos_x/(x*x))); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_cos, stat_sin); } } int gsl_sf_bessel_jl_e(const int l, const double x, gsl_sf_result * result) { if(l < 0 || x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = ( l > 0 ? 0.0 : 1.0 ); result->err = 0.0; return GSL_SUCCESS; } else if(l == 0) { return gsl_sf_bessel_j0_e(x, result); } else if(l == 1) { return gsl_sf_bessel_j1_e(x, result); } else if(l == 2) { return gsl_sf_bessel_j2_e(x, result); } else if(x*x < 10.0*(l+0.5)/M_E) { gsl_sf_result b; int status = gsl_sf_bessel_IJ_taylor_e(l+0.5, x, -1, 50, GSL_DBL_EPSILON, &b); double pre = sqrt((0.5*M_PI)/x); result->val = pre * b.val; result->err = pre * b.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return status; } else if(GSL_ROOT4_DBL_EPSILON * x > (l*l + l + 1.0)) { gsl_sf_result b; int status = gsl_sf_bessel_Jnu_asympx_e(l + 0.5, x, &b); double pre = sqrt((0.5*M_PI)/x); result->val = pre * b.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * b.err; return status; } else if(l > 1.0/GSL_ROOT6_DBL_EPSILON) { gsl_sf_result b; int status = gsl_sf_bessel_Jnu_asymp_Olver_e(l + 0.5, x, &b); double pre = sqrt((0.5*M_PI)/x); result->val = pre * b.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * b.err; return status; } else if(x > 1000.0 && x > 100.0*l*l) { /* We need this to avoid feeding large x to CF1; note that * due to the above check, we know that n <= 50. */ gsl_sf_result b; int status = gsl_sf_bessel_Jnu_asympx_e(l + 0.5, x, &b); double pre = sqrt((0.5*M_PI)/x); result->val = pre * b.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * b.err; return status; } else { double sgn; double ratio; int stat_CF1 = gsl_sf_bessel_J_CF1(l+0.5, x, &ratio, &sgn); double jellp1 = GSL_SQRT_DBL_EPSILON * ratio; double jell = GSL_SQRT_DBL_EPSILON; double jellm1; int ell; for(ell = l; ell > 0; ell--) { jellm1 = -jellp1 + (2*ell + 1)/x * jell; jellp1 = jell; jell = jellm1; } if(fabs(jell) > fabs(jellp1)) { gsl_sf_result j0_result; int stat_j0 = gsl_sf_bessel_j0_e(x, &j0_result); double pre = GSL_SQRT_DBL_EPSILON / jell; result->val = j0_result.val * pre; result->err = j0_result.err * fabs(pre); result->err += 2.0 * GSL_DBL_EPSILON * (0.5*l + 1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_j0, stat_CF1); } else { gsl_sf_result j1_result; int stat_j1 = gsl_sf_bessel_j1_e(x, &j1_result); double pre = GSL_SQRT_DBL_EPSILON / jellp1; result->val = j1_result.val * pre; result->err = j1_result.err * fabs(pre); result->err += 2.0 * GSL_DBL_EPSILON * (0.5*l + 1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_j1, stat_CF1); } } } int gsl_sf_bessel_jl_array(const int lmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(lmax < 0 || x < 0.0) { int j; for(j=0; j<=lmax; j++) result_array[j] = 0.0; GSL_ERROR ("error", GSL_EDOM); } else if(x == 0.0) { int j; for(j=1; j<=lmax; j++) result_array[j] = 0.0; result_array[0] = 1.0; return GSL_SUCCESS; } else { gsl_sf_result r_jellp1; gsl_sf_result r_jell; int stat_0 = gsl_sf_bessel_jl_e(lmax+1, x, &r_jellp1); int stat_1 = gsl_sf_bessel_jl_e(lmax, x, &r_jell); double jellp1 = r_jellp1.val; double jell = r_jell.val; double jellm1; int ell; result_array[lmax] = jell; for(ell = lmax; ell >= 1; ell--) { jellm1 = -jellp1 + (2*ell + 1)/x * jell; jellp1 = jell; jell = jellm1; result_array[ell-1] = jellm1; } return GSL_ERROR_SELECT_2(stat_0, stat_1); } } int gsl_sf_bessel_jl_steed_array(const int lmax, const double x, double * jl_x) { /* CHECK_POINTER(jl_x) */ if(lmax < 0 || x < 0.0) { int j; for(j=0; j<=lmax; j++) jl_x[j] = 0.0; GSL_ERROR ("error", GSL_EDOM); } else if(x == 0.0) { int j; for(j=1; j<=lmax; j++) jl_x[j] = 0.0; jl_x[0] = 1.0; return GSL_SUCCESS; } else if(x < 2.0*GSL_ROOT4_DBL_EPSILON) { /* first two terms of Taylor series */ double inv_fact = 1.0; /* 1/(1 3 5 ... (2l+1)) */ double x_l = 1.0; /* x^l */ int l; for(l=0; l<=lmax; l++) { jl_x[l] = x_l * inv_fact; jl_x[l] *= 1.0 - 0.5*x*x/(2.0*l+3.0); inv_fact /= 2.0*l+3.0; x_l *= x; } return GSL_SUCCESS; } else { /* Steed/Barnett algorithm [Comp. Phys. Comm. 21, 297 (1981)] */ double x_inv = 1.0/x; double W = 2.0*x_inv; double F = 1.0; double FP = (lmax+1.0) * x_inv; double B = 2.0*FP + x_inv; double end = B + 20000.0*W; double D = 1.0/B; double del = -D; FP += del; /* continued fraction */ do { B += W; D = 1.0/(B-D); del *= (B*D - 1.); FP += del; if(D < 0.0) F = -F; if(B > end) { GSL_ERROR ("error", GSL_EMAXITER); } } while(fabs(del) >= fabs(FP) * GSL_DBL_EPSILON); FP *= F; if(lmax > 0) { /* downward recursion */ double XP2 = FP; double PL = lmax * x_inv; int L = lmax; int LP; jl_x[lmax] = F; for(LP = 1; LP<=lmax; LP++) { jl_x[L-1] = PL * jl_x[L] + XP2; FP = PL*jl_x[L-1] - jl_x[L]; XP2 = FP; PL -= x_inv; --L; } F = jl_x[0]; } /* normalization */ W = x_inv / hypot(FP, F); jl_x[0] = W*F; if(lmax > 0) { int L; for(L=1; L<=lmax; L++) { jl_x[L] *= W; } } return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_j0(const double x) { EVAL_RESULT(gsl_sf_bessel_j0_e(x, &result)); } double gsl_sf_bessel_j1(const double x) { EVAL_RESULT(gsl_sf_bessel_j1_e(x, &result)); } double gsl_sf_bessel_j2(const double x) { EVAL_RESULT(gsl_sf_bessel_j2_e(x, &result)); } double gsl_sf_bessel_jl(const int l, const double x) { EVAL_RESULT(gsl_sf_bessel_jl_e(l, x, &result)); } sources_5316/external/gsl/gsl_integration__qags.c0000664000176700017670000003274511723710247021061 0ustar paulpaul/* integration/qags.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_integration.h" #include "gsl_integration__initialise.c" #include "gsl_integration__set_initial.c" #include "gsl_integration__qpsrt.c" #include "gsl_integration__util.c" #include "gsl_integration__reset.c" #include "gsl_integration__qpsrt2.c" #include "gsl_integration__qelg.c" #include "gsl_integration__positivity.c" static int qags (const gsl_function * f, const double a, const double b, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr, gsl_integration_rule * q); int gsl_integration_qags (const gsl_function *f, double a, double b, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double * result, double * abserr) { int status = qags (f, a, b, epsabs, epsrel, limit, workspace, result, abserr, &gsl_integration_qk21) ; return status ; } /* QAGI: evaluate an integral over an infinite range using the transformation integrate(f(x),-Inf,Inf) = integrate((f((1-t)/t) + f(-(1-t)/t))/t^2,0,1) */ static double i_transform (double t, void *params); int gsl_integration_qagi (gsl_function * f, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr) { int status; gsl_function f_transform; f_transform.function = &i_transform; f_transform.params = f; status = qags (&f_transform, 0.0, 1.0, epsabs, epsrel, limit, workspace, result, abserr, &gsl_integration_qk15); return status; } static double i_transform (double t, void *params) { gsl_function *f = (gsl_function *) params; double x = (1 - t) / t; double y = GSL_FN_EVAL (f, x) + GSL_FN_EVAL (f, -x); return (y / t) / t; } /* QAGIL: Evaluate an integral over an infinite range using the transformation, integrate(f(x),-Inf,b) = integrate(f(b-(1-t)/t)/t^2,0,1) */ struct il_params { double b ; gsl_function * f ; } ; static double il_transform (double t, void *params); int gsl_integration_qagil (gsl_function * f, double b, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr) { int status; gsl_function f_transform; struct il_params transform_params ; transform_params.b = b ; transform_params.f = f ; f_transform.function = &il_transform; f_transform.params = &transform_params; status = qags (&f_transform, 0.0, 1.0, epsabs, epsrel, limit, workspace, result, abserr, &gsl_integration_qk15); return status; } static double il_transform (double t, void *params) { struct il_params *p = (struct il_params *) params; double b = p->b; gsl_function * f = p->f; double x = b - (1 - t) / t; double y = GSL_FN_EVAL (f, x); return (y / t) / t; } /* QAGIU: Evaluate an integral over an infinite range using the transformation integrate(f(x),a,Inf) = integrate(f(a+(1-t)/t)/t^2,0,1) */ struct iu_params { double a ; gsl_function * f ; } ; static double iu_transform (double t, void *params); int gsl_integration_qagiu (gsl_function * f, double a, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr) { int status; gsl_function f_transform; struct iu_params transform_params ; transform_params.a = a ; transform_params.f = f ; f_transform.function = &iu_transform; f_transform.params = &transform_params; status = qags (&f_transform, 0.0, 1.0, epsabs, epsrel, limit, workspace, result, abserr, &gsl_integration_qk15); return status; } static double iu_transform (double t, void *params) { struct iu_params *p = (struct iu_params *) params; double a = p->a; gsl_function * f = p->f; double x = a + (1 - t) / t; double y = GSL_FN_EVAL (f, x); return (y / t) / t; } /* Main integration function */ static int qags (const gsl_function * f, const double a, const double b, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr, gsl_integration_rule * q) { double area, errsum; double res_ext, err_ext; double result0, abserr0, resabs0, resasc0; double tolerance; double ertest = 0; double error_over_large_intervals = 0; double reseps = 0, abseps = 0, correc = 0; size_t ktmin = 0; int roundoff_type1 = 0, roundoff_type2 = 0, roundoff_type3 = 0; int error_type = 0, error_type2 = 0; size_t iteration = 0; int positive_integrand = 0; int extrapolate = 0; int disallow_extrapolation = 0; struct extrapolation_table table; /* Initialize results */ initialise (workspace, a, b); *result = 0; *abserr = 0; if (limit > workspace->limit) { GSL_ERROR ("iteration limit exceeds available workspace", GSL_EINVAL) ; } /* Test on accuracy */ if (epsabs <= 0 && (epsrel < 50 * GSL_DBL_EPSILON || epsrel < 0.5e-28)) { GSL_ERROR ("tolerance cannot be acheived with given epsabs and epsrel", GSL_EBADTOL); } /* Perform the first integration */ q (f, a, b, &result0, &abserr0, &resabs0, &resasc0); set_initial_result (workspace, result0, abserr0); tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (result0)); if (abserr0 <= 100 * GSL_DBL_EPSILON * resabs0 && abserr0 > tolerance) { *result = result0; *abserr = abserr0; GSL_ERROR ("cannot reach tolerance because of roundoff error" "on first attempt", GSL_EROUND); } else if ((abserr0 <= tolerance && abserr0 != resasc0) || abserr0 == 0.0) { *result = result0; *abserr = abserr0; return GSL_SUCCESS; } else if (limit == 1) { *result = result0; *abserr = abserr0; GSL_ERROR ("a maximum of one iteration was insufficient", GSL_EMAXITER); } /* Initialization */ initialise_table (&table); append_table (&table, result0); area = result0; errsum = abserr0; res_ext = result0; err_ext = GSL_DBL_MAX; positive_integrand = test_positivity (result0, resabs0); iteration = 1; do { size_t current_level; double a1, b1, a2, b2; double a_i, b_i, r_i, e_i; double area1 = 0, area2 = 0, area12 = 0; double error1 = 0, error2 = 0, error12 = 0; double resasc1, resasc2; double resabs1, resabs2; double last_e_i; /* Bisect the subinterval with the largest error estimate */ retrieve (workspace, &a_i, &b_i, &r_i, &e_i); current_level = workspace->level[workspace->i] + 1; a1 = a_i; b1 = 0.5 * (a_i + b_i); a2 = b1; b2 = b_i; iteration++; q (f, a1, b1, &area1, &error1, &resabs1, &resasc1); q (f, a2, b2, &area2, &error2, &resabs2, &resasc2); area12 = area1 + area2; error12 = error1 + error2; last_e_i = e_i; /* Improve previous approximations to the integral and test for accuracy. We write these expressions in the same way as the original QUADPACK code so that the rounding errors are the same, which makes testing easier. */ errsum = errsum + error12 - e_i; area = area + area12 - r_i; tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (area)); if (resasc1 != error1 && resasc2 != error2) { double delta = r_i - area12; if (fabs (delta) <= 1.0e-5 * fabs (area12) && error12 >= 0.99 * e_i) { if (!extrapolate) { roundoff_type1++; } else { roundoff_type2++; } } if (iteration > 10 && error12 > e_i) { roundoff_type3++; } } /* Test for roundoff and eventually set error flag */ if (roundoff_type1 + roundoff_type2 >= 10 || roundoff_type3 >= 20) { error_type = 2; /* round off error */ } if (roundoff_type2 >= 5) { error_type2 = 1; } /* set error flag in the case of bad integrand behaviour at a point of the integration range */ if (subinterval_too_small (a1, a2, b2)) { error_type = 4; } /* append the newly-created intervals to the list */ update (workspace, a1, b1, area1, error1, a2, b2, area2, error2); if (errsum <= tolerance) { goto compute_result; } if (error_type) { break; } if (iteration >= limit - 1) { error_type = 1; break; } if (iteration == 2) /* set up variables on first iteration */ { error_over_large_intervals = errsum; ertest = tolerance; append_table (&table, area); continue; } if (disallow_extrapolation) { continue; } error_over_large_intervals += -last_e_i; if (current_level < workspace->maximum_level) { error_over_large_intervals += error12; } if (!extrapolate) { /* test whether the interval to be bisected next is the smallest interval. */ if (large_interval (workspace)) continue; extrapolate = 1; workspace->nrmax = 1; } if (!error_type2 && error_over_large_intervals > ertest) { if (increase_nrmax (workspace)) continue; } /* Perform extrapolation */ append_table (&table, area); qelg (&table, &reseps, &abseps); ktmin++; if (ktmin > 5 && err_ext < 0.001 * errsum) { error_type = 5; } if (abseps < err_ext) { ktmin = 0; err_ext = abseps; res_ext = reseps; correc = error_over_large_intervals; ertest = GSL_MAX_DBL (epsabs, epsrel * fabs (reseps)); if (err_ext <= ertest) break; } /* Prepare bisection of the smallest interval. */ if (table.n == 1) { disallow_extrapolation = 1; } if (error_type == 5) { break; } /* work on interval with largest error */ reset_nrmax (workspace); extrapolate = 0; error_over_large_intervals = errsum; } while (iteration < limit); *result = res_ext; *abserr = err_ext; if (err_ext == GSL_DBL_MAX) goto compute_result; if (error_type || error_type2) { if (error_type2) { err_ext += correc; } if (error_type == 0) error_type = 3; if (res_ext != 0.0 && area != 0.0) { if (err_ext / fabs (res_ext) > errsum / fabs (area)) goto compute_result; } else if (err_ext > errsum) { goto compute_result; } else if (area == 0.0) { goto return_error; } } /* Test on divergence. */ { double max_area = GSL_MAX_DBL (fabs (res_ext), fabs (area)); if (!positive_integrand && max_area < 0.01 * resabs0) goto return_error; } { double ratio = res_ext / area; if (ratio < 0.01 || ratio > 100.0 || errsum > fabs (area)) error_type = 6; } goto return_error; compute_result: *result = sum_results (workspace); *abserr = errsum; return_error: if (error_type > 2) error_type--; if (error_type == 0) { return GSL_SUCCESS; } else if (error_type == 1) { GSL_ERROR ("number of iterations was insufficient", GSL_EMAXITER); } else if (error_type == 2) { GSL_ERROR ("cannot reach tolerance because of roundoff error", GSL_EROUND); } else if (error_type == 3) { GSL_ERROR ("bad integrand behavior found in the integration interval", GSL_ESING); } else if (error_type == 4) { GSL_ERROR ("roundoff error detected in the extrapolation table", GSL_EROUND); } else if (error_type == 5) { GSL_ERROR ("integral is divergent, or slowly convergent", GSL_EDIVERGE); } else { GSL_ERROR ("could not integrate function", GSL_EFAILED); } } sources_5316/external/gsl/gsl_cblas__source_swap_c.h0000664000176700017670000000220211705263724021514 0ustar paulpaul/* blas/source_swap_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE tmp_real = REAL(X, ix); const BASE tmp_imag = IMAG(X, ix); REAL(X, ix) = REAL(Y, iy); IMAG(X, ix) = IMAG(Y, iy); REAL(Y, iy) = tmp_real; IMAG(Y, iy) = tmp_imag; ix += incX; iy += incY; } } sources_5316/external/gsl/gsl_multiroots__fdfsolver.c0000664000176700017670000001024111723710247022001 0ustar paulpaul/* multiroots/fdfsolver.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_multiroots.h" gsl_multiroot_fdfsolver * gsl_multiroot_fdfsolver_alloc (const gsl_multiroot_fdfsolver_type * T, size_t n) { int status; gsl_multiroot_fdfsolver * s; s = (gsl_multiroot_fdfsolver *) malloc (sizeof (gsl_multiroot_fdfsolver)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for multiroot solver struct", GSL_ENOMEM, 0); } s->x = gsl_vector_calloc (n); if (s->x == 0) { free (s); GSL_ERROR_VAL ("failed to allocate space for x", GSL_ENOMEM, 0); } s->f = gsl_vector_calloc (n); if (s->f == 0) { gsl_vector_free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for f", GSL_ENOMEM, 0); } s->J = gsl_matrix_calloc (n,n); if (s->J == 0) { gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); GSL_ERROR_VAL ("failed to allocate space for g", GSL_ENOMEM, 0); } s->dx = gsl_vector_calloc (n); if (s->dx == 0) { gsl_matrix_free (s->J); gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); GSL_ERROR_VAL ("failed to allocate space for dx", GSL_ENOMEM, 0); } s->state = malloc (T->size); if (s->state == 0) { gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); gsl_matrix_free (s->J); free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for multiroot solver state", GSL_ENOMEM, 0); } s->type = T ; status = (s->type->alloc)(s->state, n); if (status != GSL_SUCCESS) { free (s->state); gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); gsl_matrix_free (s->J); free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to set solver", status, 0); } s->fdf = NULL; return s; } int gsl_multiroot_fdfsolver_set (gsl_multiroot_fdfsolver * s, gsl_multiroot_function_fdf * f, const gsl_vector * x) { if (s->x->size != f->n) { GSL_ERROR ("function incompatible with solver size", GSL_EBADLEN); } if (x->size != f->n) { GSL_ERROR ("vector length not compatible with function", GSL_EBADLEN); } s->fdf = f; gsl_vector_memcpy(s->x,x); return (s->type->set) (s->state, s->fdf, s->x, s->f, s->J, s->dx); } int gsl_multiroot_fdfsolver_iterate (gsl_multiroot_fdfsolver * s) { return (s->type->iterate) (s->state, s->fdf, s->x, s->f, s->J, s->dx); } void gsl_multiroot_fdfsolver_free (gsl_multiroot_fdfsolver * s) { (s->type->free) (s->state); free (s->state); gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); gsl_matrix_free (s->J); free (s); } const char * gsl_multiroot_fdfsolver_name (const gsl_multiroot_fdfsolver * s) { return s->type->name; } gsl_vector * gsl_multiroot_fdfsolver_root (const gsl_multiroot_fdfsolver * s) { return s->x; } gsl_vector * gsl_multiroot_fdfsolver_dx (const gsl_multiroot_fdfsolver * s) { return s->dx; } gsl_vector * gsl_multiroot_fdfsolver_f (const gsl_multiroot_fdfsolver * s) { return s->f; } sources_5316/external/gsl/gsl_cblas__source_syrk_c.h0000664000176700017670000001345211705263724021543 0ustar paulpaul/* blas/source_syrk_r.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; int uplo, trans; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; if (Order == CblasRowMajor) { uplo = Uplo; /* FIXME: original blas does not make distinction between Trans and ConjTrans?? */ trans = (Trans == CblasNoTrans) ? CblasNoTrans : CblasTrans; } else { uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; trans = (Trans == CblasNoTrans) ? CblasTrans : CblasNoTrans; } /* form y := beta*y */ if (beta_real == 0.0 && beta_imag == 0.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { const BASE Cij_real = REAL(C, ldc * i + j); const BASE Cij_imag = IMAG(C, ldc * i + j); REAL(C, ldc * i + j) = beta_real * Cij_real - beta_imag * Cij_imag; IMAG(C, ldc * i + j) = beta_real * Cij_imag + beta_imag * Cij_real; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { const BASE Cij_real = REAL(C, ldc * i + j); const BASE Cij_imag = IMAG(C, ldc * i + j); REAL(C, ldc * i + j) = beta_real * Cij_real - beta_imag * Cij_imag; IMAG(C, ldc * i + j) = beta_real * Cij_imag + beta_imag * Cij_real; } } } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; if (uplo == CblasUpper && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); temp_real += Aik_real * Ajk_real - Aik_imag * Ajk_imag; temp_imag += Aik_real * Ajk_imag + Aik_imag * Ajk_real; } REAL(C, i * ldc + j) += alpha_real * temp_real - alpha_imag * temp_imag; IMAG(C, i * ldc + j) += alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (uplo == CblasUpper && trans == CblasTrans) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aki_real = CONST_REAL(A, k * lda + i); const BASE Aki_imag = CONST_IMAG(A, k * lda + i); const BASE Akj_real = CONST_REAL(A, k * lda + j); const BASE Akj_imag = CONST_IMAG(A, k * lda + j); temp_real += Aki_real * Akj_real - Aki_imag * Akj_imag; temp_imag += Aki_real * Akj_imag + Aki_imag * Akj_real; } REAL(C, i * ldc + j) += alpha_real * temp_real - alpha_imag * temp_imag; IMAG(C, i * ldc + j) += alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (uplo == CblasLower && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); temp_real += Aik_real * Ajk_real - Aik_imag * Ajk_imag; temp_imag += Aik_real * Ajk_imag + Aik_imag * Ajk_real; } REAL(C, i * ldc + j) += alpha_real * temp_real - alpha_imag * temp_imag; IMAG(C, i * ldc + j) += alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (uplo == CblasLower && trans == CblasTrans) { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aki_real = CONST_REAL(A, k * lda + i); const BASE Aki_imag = CONST_IMAG(A, k * lda + i); const BASE Akj_real = CONST_REAL(A, k * lda + j); const BASE Akj_imag = CONST_IMAG(A, k * lda + j); temp_real += Aki_real * Akj_real - Aki_imag * Akj_imag; temp_imag += Aki_real * Akj_imag + Aki_imag * Akj_real; } REAL(C, i * ldc + j) += alpha_real * temp_real - alpha_imag * temp_imag; IMAG(C, i * ldc + j) += alpha_real * temp_imag + alpha_imag * temp_real; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_ieee-utils__fp-tru64.c0000664000176700017670000001316511723710247021232 0ustar paulpaul/* ieee-utils/fp-tru64.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Tim Mooney * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * Under Compaq's Unix with the silly name, read the man pages for read_rnd, * write_rnd, and ieee(3) for more information on the functions used here. * * Note that enabling control of dynamic rounding mode (via write_rnd) requires * that you pass a special flag to your C compiler. For Compaq's C compiler * the flag is `-fprm d', for gcc it's `-mfp-rounding-mode=d'. * * Enabling the trap control (via ieee_set_fp_control) also requires a * flag be passed to the C compiler. The flag for Compaq's C compiler * is `-ieee' and for gcc it's `-mieee'. * We have not implemented the `inexact' case, since it is rarely used * and requires the library being built with an additional compiler * flag that can degrade performance for everything else. If you need * to add support for `inexact' the relevant flag for Compaq's * compiler is `-ieee_with_inexact', and the flag for gcc is * `-mieee-with-inexact'. * * Problem have been reported with the "fixed" float.h installed with * gcc-2.95 lacking some of the definitions in the system float.h (the * symptoms are errors like: `FP_RND_RN' undeclared). To work around * this we can include the system float.h before the gcc version, e.g. * * #include "/usr/include/float.h" * #include */ #include #ifndef FP_RND_RN # undef _FLOAT_H_ # include /usr/include/float.h # undef _FLOAT_H_ # include #endif #include #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { unsigned long int mode = 0 ; unsigned int rnd = 0 ; /* I'm actually not completely sure that the alpha only supports default * precisions rounding, but I couldn't find any information regarding this, so * it seems safe to assume this for now until it's proven otherwise. */ switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("Tru64 Unix on the alpha only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("Tru64 Unix on the alpha only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("Tru64 Unix on the alpha only supports default precision rounding", GSL_EUNSUP) ; break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: rnd = FP_RND_RN ; write_rnd (rnd) ; break ; case GSL_IEEE_ROUND_DOWN: rnd = FP_RND_RM ; write_rnd (rnd) ; break ; case GSL_IEEE_ROUND_UP: rnd = FP_RND_RP ; write_rnd (rnd) ; break ; case GSL_IEEE_ROUND_TO_ZERO: rnd = FP_RND_RZ ; write_rnd (rnd) ; break ; default: rnd = FP_RND_RN ; write_rnd (rnd) ; } /* Turn on all the exceptions apart from 'inexact' */ /* from the ieee(3) man page: * IEEE_TRAP_ENABLE_INV -> Invalid operation * IEEE_TRAP_ENABLE_DZE -> Divide by 0 * IEEE_TRAP_ENABLE_OVF -> Overflow * IEEE_TRAP_ENABLE_UNF -> Underflow * IEEE_TRAP_ENABLE_INE -> Inexact (requires special option to C compiler) * IEEE_TRAP_ENABLE_DNO -> denormal operand * Note: IEEE_TRAP_ENABLE_DNO is not supported on OSF 3.x or Digital Unix * 4.0 - 4.0d(?). * IEEE_TRAP_ENABLE_MASK -> mask of all the trap enables * IEEE_MAP_DMZ -> map denormal inputs to zero * IEEE_MAP_UMZ -> map underflow results to zero */ mode = IEEE_TRAP_ENABLE_INV | IEEE_TRAP_ENABLE_DZE | IEEE_TRAP_ENABLE_OVF | IEEE_TRAP_ENABLE_UNF ; if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ IEEE_TRAP_ENABLE_INV ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { #ifdef IEEE_TRAP_ENABLE_DNO mode &= ~ IEEE_TRAP_ENABLE_DNO ; #else GSL_ERROR ("Sorry, this version of Digital Unix does not support denormalized operands", GSL_EUNSUP) ; #endif } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ IEEE_TRAP_ENABLE_DZE ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ IEEE_TRAP_ENABLE_OVF ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ IEEE_TRAP_ENABLE_UNF ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { /* To implement this would require a special flag to the C compiler which can cause degraded performance */ GSL_ERROR ("Sorry, GSL does not implement trap-inexact for Tru64 Unix on the alpha - see fp-tru64.c for details", GSL_EUNSUP) ; /* In case you need to add it, the appropriate line would be * * mode |= IEEE_TRAP_ENABLE_INE ; * */ } else { mode &= ~ IEEE_TRAP_ENABLE_INE ; } ieee_set_fp_control (mode) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_cblas__ztrmm.c0000664000176700017670000000072411723710247020030 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ztrmm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const void *alpha, const void *A, const int lda, void *B, const int ldb) { #define BASE double #include "gsl_cblas__source_trmm_c.h" #undef BASE } sources_5316/external/gsl/gsl_histogram__find2d.c0000664000176700017670000000257411723710247020743 0ustar paulpaul/* histogram/find2d.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl_histogram__find.c" static int find2d (const size_t nx, const double xrange[], const size_t ny, const double yrange[], const double x, const double y, size_t * i, size_t * j); static int find2d (const size_t nx, const double xrange[], const size_t ny, const double yrange[], const double x, const double y, size_t * i, size_t * j) { int status = find (nx, xrange, x, i); if (status) { return status; } status = find (ny, yrange, y, j); if (status) { return status; } return 0; } sources_5316/external/gsl/gsl_blas__blas.c0000664000176700017670000015775111723710247017452 0ustar paulpaul/* blas/blas.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001 Gerard Jungman & Brian * Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* GSL implementation of BLAS operations for vectors and dense * matrices. Note that GSL native storage is row-major. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_cblas.h" #include "gsl_cblas.h" #include "gsl_blas_types.h" #include "gsl_blas.h" /* ======================================================================== * Level 1 * ======================================================================== */ /* CBLAS defines vector sizes in terms of int. GSL defines sizes in terms of size_t, so we need to convert these into integers. There is the possibility of overflow here. FIXME: Maybe this could be caught */ #define INT(X) ((int)(X)) int gsl_blas_sdsdot (float alpha, const gsl_vector_float * X, const gsl_vector_float * Y, float *result) { if (X->size == Y->size) { *result = cblas_sdsdot (INT (X->size), alpha, X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_dsdot (const gsl_vector_float * X, const gsl_vector_float * Y, double *result) { if (X->size == Y->size) { *result = cblas_dsdot (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_sdot (const gsl_vector_float * X, const gsl_vector_float * Y, float *result) { if (X->size == Y->size) { *result = cblas_sdot (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_ddot (const gsl_vector * X, const gsl_vector * Y, double *result) { if (X->size == Y->size) { *result = cblas_ddot (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_cdotu (const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_complex_float * dotu) { if (X->size == Y->size) { cblas_cdotu_sub (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride), GSL_COMPLEX_P (dotu)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_cdotc (const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_complex_float * dotc) { if (X->size == Y->size) { cblas_cdotc_sub (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride), GSL_COMPLEX_P (dotc)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zdotu (const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_complex * dotu) { if (X->size == Y->size) { cblas_zdotu_sub (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride), GSL_COMPLEX_P (dotu)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zdotc (const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_complex * dotc) { if (X->size == Y->size) { cblas_zdotc_sub (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride), GSL_COMPLEX_P (dotc)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* Norms of vectors */ float gsl_blas_snrm2 (const gsl_vector_float * X) { return cblas_snrm2 (INT (X->size), X->data, INT (X->stride)); } double gsl_blas_dnrm2 (const gsl_vector * X) { return cblas_dnrm2 (INT (X->size), X->data, INT (X->stride)); } float gsl_blas_scnrm2 (const gsl_vector_complex_float * X) { return cblas_scnrm2 (INT (X->size), X->data, INT (X->stride)); } double gsl_blas_dznrm2 (const gsl_vector_complex * X) { return cblas_dznrm2 (INT (X->size), X->data, INT (X->stride)); } /* Absolute sums of vectors */ float gsl_blas_sasum (const gsl_vector_float * X) { return cblas_sasum (INT (X->size), X->data, INT (X->stride)); } double gsl_blas_dasum (const gsl_vector * X) { return cblas_dasum (INT (X->size), X->data, INT (X->stride)); } float gsl_blas_scasum (const gsl_vector_complex_float * X) { return cblas_scasum (INT (X->size), X->data, INT (X->stride)); } double gsl_blas_dzasum (const gsl_vector_complex * X) { return cblas_dzasum (INT (X->size), X->data, INT (X->stride)); } /* Maximum elements of vectors */ CBLAS_INDEX_t gsl_blas_isamax (const gsl_vector_float * X) { return cblas_isamax (INT (X->size), X->data, INT (X->stride)); } CBLAS_INDEX_t gsl_blas_idamax (const gsl_vector * X) { return cblas_idamax (INT (X->size), X->data, INT (X->stride)); } CBLAS_INDEX_t gsl_blas_icamax (const gsl_vector_complex_float * X) { return cblas_icamax (INT (X->size), X->data, INT (X->stride)); } CBLAS_INDEX_t gsl_blas_izamax (const gsl_vector_complex * X) { return cblas_izamax (INT (X->size), X->data, INT (X->stride)); } /* Swap vectors */ int gsl_blas_sswap (gsl_vector_float * X, gsl_vector_float * Y) { if (X->size == Y->size) { cblas_sswap (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_dswap (gsl_vector * X, gsl_vector * Y) { if (X->size == Y->size) { cblas_dswap (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); }; } int gsl_blas_cswap (gsl_vector_complex_float * X, gsl_vector_complex_float * Y) { if (X->size == Y->size) { cblas_cswap (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zswap (gsl_vector_complex * X, gsl_vector_complex * Y) { if (X->size == Y->size) { cblas_zswap (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* Copy vectors */ int gsl_blas_scopy (const gsl_vector_float * X, gsl_vector_float * Y) { if (X->size == Y->size) { cblas_scopy (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_dcopy (const gsl_vector * X, gsl_vector * Y) { if (X->size == Y->size) { cblas_dcopy (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_ccopy (const gsl_vector_complex_float * X, gsl_vector_complex_float * Y) { if (X->size == Y->size) { cblas_ccopy (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zcopy (const gsl_vector_complex * X, gsl_vector_complex * Y) { if (X->size == Y->size) { cblas_zcopy (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* Compute Y = alpha X + Y */ int gsl_blas_saxpy (float alpha, const gsl_vector_float * X, gsl_vector_float * Y) { if (X->size == Y->size) { cblas_saxpy (INT (X->size), alpha, X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_daxpy (double alpha, const gsl_vector * X, gsl_vector * Y) { if (X->size == Y->size) { cblas_daxpy (INT (X->size), alpha, X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_caxpy (const gsl_complex_float alpha, const gsl_vector_complex_float * X, gsl_vector_complex_float * Y) { if (X->size == Y->size) { cblas_caxpy (INT (X->size), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zaxpy (const gsl_complex alpha, const gsl_vector_complex * X, gsl_vector_complex * Y) { if (X->size == Y->size) { cblas_zaxpy (INT (X->size), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* Generate rotation */ int gsl_blas_srotg (float a[], float b[], float c[], float s[]) { cblas_srotg (a, b, c, s); return GSL_SUCCESS; } int gsl_blas_drotg (double a[], double b[], double c[], double s[]) { cblas_drotg (a, b, c, s); return GSL_SUCCESS; } /* Apply rotation to vectors */ int gsl_blas_srot (gsl_vector_float * X, gsl_vector_float * Y, float c, float s) { if (X->size == Y->size) { cblas_srot (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride), c, s); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_drot (gsl_vector * X, gsl_vector * Y, const double c, const double s) { if (X->size == Y->size) { cblas_drot (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride), c, s); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* Generate modified rotation */ int gsl_blas_srotmg (float d1[], float d2[], float b1[], float b2, float P[]) { cblas_srotmg (d1, d2, b1, b2, P); return GSL_SUCCESS; } int gsl_blas_drotmg (double d1[], double d2[], double b1[], double b2, double P[]) { cblas_drotmg (d1, d2, b1, b2, P); return GSL_SUCCESS; } /* Apply modified rotation */ int gsl_blas_srotm (gsl_vector_float * X, gsl_vector_float * Y, const float P[]) { if (X->size == Y->size) { cblas_srotm (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride), P); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_drotm (gsl_vector * X, gsl_vector * Y, const double P[]) { if (X->size != Y->size) { cblas_drotm (INT (X->size), X->data, INT (X->stride), Y->data, INT (Y->stride), P); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* Scale vector */ void gsl_blas_sscal (float alpha, gsl_vector_float * X) { cblas_sscal (INT (X->size), alpha, X->data, INT (X->stride)); } void gsl_blas_dscal (double alpha, gsl_vector * X) { cblas_dscal (INT (X->size), alpha, X->data, INT (X->stride)); } void gsl_blas_cscal (const gsl_complex_float alpha, gsl_vector_complex_float * X) { cblas_cscal (INT (X->size), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride)); } void gsl_blas_zscal (const gsl_complex alpha, gsl_vector_complex * X) { cblas_zscal (INT (X->size), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride)); } void gsl_blas_csscal (float alpha, gsl_vector_complex_float * X) { cblas_csscal (INT (X->size), alpha, X->data, INT (X->stride)); } void gsl_blas_zdscal (double alpha, gsl_vector_complex * X) { cblas_zdscal (INT (X->size), alpha, X->data, INT (X->stride)); } /* =========================================================================== * Level 2 * =========================================================================== */ /* GEMV */ int gsl_blas_sgemv (CBLAS_TRANSPOSE_t TransA, float alpha, const gsl_matrix_float * A, const gsl_vector_float * X, float beta, gsl_vector_float * Y) { const size_t M = A->size1; const size_t N = A->size2; if ((TransA == CblasNoTrans && N == X->size && M == Y->size) || (TransA == CblasTrans && M == X->size && N == Y->size)) { cblas_sgemv (CblasRowMajor, TransA, INT (M), INT (N), alpha, A->data, INT (A->tda), X->data, INT (X->stride), beta, Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_dgemv (CBLAS_TRANSPOSE_t TransA, double alpha, const gsl_matrix * A, const gsl_vector * X, double beta, gsl_vector * Y) { const size_t M = A->size1; const size_t N = A->size2; if ((TransA == CblasNoTrans && N == X->size && M == Y->size) || (TransA == CblasTrans && M == X->size && N == Y->size)) { cblas_dgemv (CblasRowMajor, TransA, INT (M), INT (N), alpha, A->data, INT (A->tda), X->data, INT (X->stride), beta, Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_cgemv (CBLAS_TRANSPOSE_t TransA, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_vector_complex_float * X, const gsl_complex_float beta, gsl_vector_complex_float * Y) { const size_t M = A->size1; const size_t N = A->size2; if ((TransA == CblasNoTrans && N == X->size && M == Y->size) || (TransA == CblasTrans && M == X->size && N == Y->size) || (TransA == CblasConjTrans && M == X->size && N == Y->size)) { cblas_cgemv (CblasRowMajor, TransA, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), X->data, INT (X->stride), GSL_COMPLEX_P (&beta), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zgemv (CBLAS_TRANSPOSE_t TransA, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_vector_complex * X, const gsl_complex beta, gsl_vector_complex * Y) { const size_t M = A->size1; const size_t N = A->size2; if ((TransA == CblasNoTrans && N == X->size && M == Y->size) || (TransA == CblasTrans && M == X->size && N == Y->size) || (TransA == CblasConjTrans && M == X->size && N == Y->size)) { cblas_zgemv (CblasRowMajor, TransA, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), X->data, INT (X->stride), GSL_COMPLEX_P (&beta), Y->data, INT (Y->stride)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* HEMV */ int gsl_blas_chemv (CBLAS_UPLO_t Uplo, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_vector_complex_float * X, const gsl_complex_float beta, gsl_vector_complex_float * Y) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size || N != Y->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_chemv (CblasRowMajor, Uplo, INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), X->data, INT (X->stride), GSL_COMPLEX_P (&beta), Y->data, INT (Y->stride)); return GSL_SUCCESS; } int gsl_blas_zhemv (CBLAS_UPLO_t Uplo, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_vector_complex * X, const gsl_complex beta, gsl_vector_complex * Y) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size || N != Y->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_zhemv (CblasRowMajor, Uplo, INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), X->data, INT (X->stride), GSL_COMPLEX_P (&beta), Y->data, INT (Y->stride)); return GSL_SUCCESS; } /* SYMV */ int gsl_blas_ssymv (CBLAS_UPLO_t Uplo, float alpha, const gsl_matrix_float * A, const gsl_vector_float * X, float beta, gsl_vector_float * Y) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size || N != Y->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_ssymv (CblasRowMajor, Uplo, INT (N), alpha, A->data, INT (A->tda), X->data, INT (X->stride), beta, Y->data, INT (Y->stride)); return GSL_SUCCESS; } int gsl_blas_dsymv (CBLAS_UPLO_t Uplo, double alpha, const gsl_matrix * A, const gsl_vector * X, double beta, gsl_vector * Y) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size || N != Y->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_dsymv (CblasRowMajor, Uplo, INT (N), alpha, A->data, INT (A->tda), X->data, INT (X->stride), beta, Y->data, INT (Y->stride)); return GSL_SUCCESS; } /* TRMV */ int gsl_blas_strmv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_float * A, gsl_vector_float * X) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_strmv (CblasRowMajor, Uplo, TransA, Diag, INT (N), A->data, INT (A->tda), X->data, INT (X->stride)); return GSL_SUCCESS; } int gsl_blas_dtrmv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix * A, gsl_vector * X) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_dtrmv (CblasRowMajor, Uplo, TransA, Diag, INT (N), A->data, INT (A->tda), X->data, INT (X->stride)); return GSL_SUCCESS; } int gsl_blas_ctrmv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_complex_float * A, gsl_vector_complex_float * X) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_ctrmv (CblasRowMajor, Uplo, TransA, Diag, INT (N), A->data, INT (A->tda), X->data, INT (X->stride)); return GSL_SUCCESS; } int gsl_blas_ztrmv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_complex * A, gsl_vector_complex * X) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_ztrmv (CblasRowMajor, Uplo, TransA, Diag, INT (N), A->data, INT (A->tda), X->data, INT (X->stride)); return GSL_SUCCESS; } /* TRSV */ int gsl_blas_strsv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_float * A, gsl_vector_float * X) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_strsv (CblasRowMajor, Uplo, TransA, Diag, INT (N), A->data, INT (A->tda), X->data, INT (X->stride)); return GSL_SUCCESS; } int gsl_blas_dtrsv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix * A, gsl_vector * X) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_dtrsv (CblasRowMajor, Uplo, TransA, Diag, INT (N), A->data, INT (A->tda), X->data, INT (X->stride)); return GSL_SUCCESS; } int gsl_blas_ctrsv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_complex_float * A, gsl_vector_complex_float * X) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_ctrsv (CblasRowMajor, Uplo, TransA, Diag, INT (N), A->data, INT (A->tda), X->data, INT (X->stride)); return GSL_SUCCESS; } int gsl_blas_ztrsv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_complex * A, gsl_vector_complex * X) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (N != X->size) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_ztrsv (CblasRowMajor, Uplo, TransA, Diag, INT (N), A->data, INT (A->tda), X->data, INT (X->stride)); return GSL_SUCCESS; } /* GER */ int gsl_blas_sger (float alpha, const gsl_vector_float * X, const gsl_vector_float * Y, gsl_matrix_float * A) { const size_t M = A->size1; const size_t N = A->size2; if (X->size == M && Y->size == N) { cblas_sger (CblasRowMajor, INT (M), INT (N), alpha, X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_dger (double alpha, const gsl_vector * X, const gsl_vector * Y, gsl_matrix * A) { const size_t M = A->size1; const size_t N = A->size2; if (X->size == M && Y->size == N) { cblas_dger (CblasRowMajor, INT (M), INT (N), alpha, X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* GERU */ int gsl_blas_cgeru (const gsl_complex_float alpha, const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_matrix_complex_float * A) { const size_t M = A->size1; const size_t N = A->size2; if (X->size == M && Y->size == N) { cblas_cgeru (CblasRowMajor, INT (M), INT (N), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zgeru (const gsl_complex alpha, const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_matrix_complex * A) { const size_t M = A->size1; const size_t N = A->size2; if (X->size == M && Y->size == N) { cblas_zgeru (CblasRowMajor, INT (M), INT (N), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* GERC */ int gsl_blas_cgerc (const gsl_complex_float alpha, const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_matrix_complex_float * A) { const size_t M = A->size1; const size_t N = A->size2; if (X->size == M && Y->size == N) { cblas_cgerc (CblasRowMajor, INT (M), INT (N), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zgerc (const gsl_complex alpha, const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_matrix_complex * A) { const size_t M = A->size1; const size_t N = A->size2; if (X->size == M && Y->size == N) { cblas_zgerc (CblasRowMajor, INT (M), INT (N), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* HER */ int gsl_blas_cher (CBLAS_UPLO_t Uplo, float alpha, const gsl_vector_complex_float * X, gsl_matrix_complex_float * A) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (X->size != N) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_cher (CblasRowMajor, Uplo, INT (M), alpha, X->data, INT (X->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } int gsl_blas_zher (CBLAS_UPLO_t Uplo, double alpha, const gsl_vector_complex * X, gsl_matrix_complex * A) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (X->size != N) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_zher (CblasRowMajor, Uplo, INT (N), alpha, X->data, INT (X->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } /* HER2 */ int gsl_blas_cher2 (CBLAS_UPLO_t Uplo, const gsl_complex_float alpha, const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_matrix_complex_float * A) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (X->size != N || Y->size != N) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_cher2 (CblasRowMajor, Uplo, INT (N), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } int gsl_blas_zher2 (CBLAS_UPLO_t Uplo, const gsl_complex alpha, const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_matrix_complex * A) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (X->size != N || Y->size != N) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_zher2 (CblasRowMajor, Uplo, INT (N), GSL_COMPLEX_P (&alpha), X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } /* SYR */ int gsl_blas_ssyr (CBLAS_UPLO_t Uplo, float alpha, const gsl_vector_float * X, gsl_matrix_float * A) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (X->size != N) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_ssyr (CblasRowMajor, Uplo, INT (N), alpha, X->data, INT (X->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } int gsl_blas_dsyr (CBLAS_UPLO_t Uplo, double alpha, const gsl_vector * X, gsl_matrix * A) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (X->size != N) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_dsyr (CblasRowMajor, Uplo, INT (N), alpha, X->data, INT (X->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } /* SYR2 */ int gsl_blas_ssyr2 (CBLAS_UPLO_t Uplo, float alpha, const gsl_vector_float * X, const gsl_vector_float * Y, gsl_matrix_float * A) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (X->size != N || Y->size != N) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_ssyr2 (CblasRowMajor, Uplo, INT (N), alpha, X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } int gsl_blas_dsyr2 (CBLAS_UPLO_t Uplo, double alpha, const gsl_vector * X, const gsl_vector * Y, gsl_matrix * A) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR ("matrix must be square", GSL_ENOTSQR); } else if (X->size != N || Y->size != N) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_dsyr2 (CblasRowMajor, Uplo, INT (N), alpha, X->data, INT (X->stride), Y->data, INT (Y->stride), A->data, INT (A->tda)); return GSL_SUCCESS; } /* * =========================================================================== * Prototypes for level 3 BLAS * =========================================================================== */ /* GEMM */ int gsl_blas_sgemm (CBLAS_TRANSPOSE_t TransA, CBLAS_TRANSPOSE_t TransB, float alpha, const gsl_matrix_float * A, const gsl_matrix_float * B, float beta, gsl_matrix_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (TransA == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (TransA == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (TransB == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (TransB == CblasNoTrans) ? B->size2 : B->size1; if (M == MA && N == NB && NA == MB) /* [MxN] = [MAxNA][MBxNB] */ { cblas_sgemm (CblasRowMajor, TransA, TransB, INT (M), INT (N), INT (NA), alpha, A->data, INT (A->tda), B->data, INT (B->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_dgemm (CBLAS_TRANSPOSE_t TransA, CBLAS_TRANSPOSE_t TransB, double alpha, const gsl_matrix * A, const gsl_matrix * B, double beta, gsl_matrix * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (TransA == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (TransA == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (TransB == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (TransB == CblasNoTrans) ? B->size2 : B->size1; if (M == MA && N == NB && NA == MB) /* [MxN] = [MAxNA][MBxNB] */ { cblas_dgemm (CblasRowMajor, TransA, TransB, INT (M), INT (N), INT (NA), alpha, A->data, INT (A->tda), B->data, INT (B->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_cgemm (CBLAS_TRANSPOSE_t TransA, CBLAS_TRANSPOSE_t TransB, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, const gsl_complex_float beta, gsl_matrix_complex_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (TransA == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (TransA == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (TransB == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (TransB == CblasNoTrans) ? B->size2 : B->size1; if (M == MA && N == NB && NA == MB) /* [MxN] = [MAxNA][MBxNB] */ { cblas_cgemm (CblasRowMajor, TransA, TransB, INT (M), INT (N), INT (NA), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zgemm (CBLAS_TRANSPOSE_t TransA, CBLAS_TRANSPOSE_t TransB, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, const gsl_complex beta, gsl_matrix_complex * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (TransA == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (TransA == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (TransB == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (TransB == CblasNoTrans) ? B->size2 : B->size1; if (M == MA && N == NB && NA == MB) /* [MxN] = [MAxNA][MBxNB] */ { cblas_zgemm (CblasRowMajor, TransA, TransB, INT (M), INT (N), INT (NA), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* SYMM */ int gsl_blas_ssymm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, float alpha, const gsl_matrix_float * A, const gsl_matrix_float * B, float beta, gsl_matrix_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = A->size1; const size_t NA = A->size2; const size_t MB = B->size1; const size_t NB = B->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && (M == MA && N == NB && NA == MB)) || (Side == CblasRight && (M == MB && N == NA && NB == MA))) { cblas_ssymm (CblasRowMajor, Side, Uplo, INT (M), INT (N), alpha, A->data, INT (A->tda), B->data, INT (B->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_dsymm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, double alpha, const gsl_matrix * A, const gsl_matrix * B, double beta, gsl_matrix * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = A->size1; const size_t NA = A->size2; const size_t MB = B->size1; const size_t NB = B->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && (M == MA && N == NB && NA == MB)) || (Side == CblasRight && (M == MB && N == NA && NB == MA))) { cblas_dsymm (CblasRowMajor, Side, Uplo, INT (M), INT (N), alpha, A->data, INT (A->tda), B->data, INT (B->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_csymm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, const gsl_complex_float beta, gsl_matrix_complex_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = A->size1; const size_t NA = A->size2; const size_t MB = B->size1; const size_t NB = B->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && (M == MA && N == NB && NA == MB)) || (Side == CblasRight && (M == MB && N == NA && NB == MA))) { cblas_csymm (CblasRowMajor, Side, Uplo, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zsymm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, const gsl_complex beta, gsl_matrix_complex * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = A->size1; const size_t NA = A->size2; const size_t MB = B->size1; const size_t NB = B->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && (M == MA && N == NB && NA == MB)) || (Side == CblasRight && (M == MB && N == NA && NB == MA))) { cblas_zsymm (CblasRowMajor, Side, Uplo, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* HEMM */ int gsl_blas_chemm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, const gsl_complex_float beta, gsl_matrix_complex_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = A->size1; const size_t NA = A->size2; const size_t MB = B->size1; const size_t NB = B->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && (M == MA && N == NB && NA == MB)) || (Side == CblasRight && (M == MB && N == NA && NB == MA))) { cblas_chemm (CblasRowMajor, Side, Uplo, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_zhemm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, const gsl_complex beta, gsl_matrix_complex * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = A->size1; const size_t NA = A->size2; const size_t MB = B->size1; const size_t NB = B->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && (M == MA && N == NB && NA == MB)) || (Side == CblasRight && (M == MB && N == NA && NB == MA))) { cblas_zhemm (CblasRowMajor, Side, Uplo, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* SYRK */ int gsl_blas_ssyrk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, float alpha, const gsl_matrix_float * A, float beta, gsl_matrix_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t J = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t K = (Trans == CblasNoTrans) ? A->size2 : A->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != J) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_ssyrk (CblasRowMajor, Uplo, Trans, INT (N), INT (K), alpha, A->data, INT (A->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } int gsl_blas_dsyrk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, double alpha, const gsl_matrix * A, double beta, gsl_matrix * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t J = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t K = (Trans == CblasNoTrans) ? A->size2 : A->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != J) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_dsyrk (CblasRowMajor, Uplo, Trans, INT (N), INT (K), alpha, A->data, INT (A->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } int gsl_blas_csyrk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_complex_float beta, gsl_matrix_complex_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t J = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t K = (Trans == CblasNoTrans) ? A->size2 : A->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != J) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_csyrk (CblasRowMajor, Uplo, Trans, INT (N), INT (K), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } int gsl_blas_zsyrk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_complex beta, gsl_matrix_complex * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t J = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t K = (Trans == CblasNoTrans) ? A->size2 : A->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != J) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_zsyrk (CblasRowMajor, Uplo, Trans, INT (N), INT (K), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } /* HERK */ int gsl_blas_cherk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, float alpha, const gsl_matrix_complex_float * A, float beta, gsl_matrix_complex_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t J = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t K = (Trans == CblasNoTrans) ? A->size2 : A->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != J) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_cherk (CblasRowMajor, Uplo, Trans, INT (N), INT (K), alpha, A->data, INT (A->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } int gsl_blas_zherk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, double alpha, const gsl_matrix_complex * A, double beta, gsl_matrix_complex * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t J = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t K = (Trans == CblasNoTrans) ? A->size2 : A->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != J) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_zherk (CblasRowMajor, Uplo, Trans, INT (N), INT (K), alpha, A->data, INT (A->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } /* SYR2K */ int gsl_blas_ssyr2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, float alpha, const gsl_matrix_float * A, const gsl_matrix_float * B, float beta, gsl_matrix_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (Trans == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (Trans == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (Trans == CblasNoTrans) ? B->size2 : B->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != MA || N != MB || NA != NB) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_ssyr2k (CblasRowMajor, Uplo, Trans, INT (N), INT (NA), alpha, A->data, INT (A->tda), B->data, INT (B->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } int gsl_blas_dsyr2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, double alpha, const gsl_matrix * A, const gsl_matrix * B, double beta, gsl_matrix * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (Trans == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (Trans == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (Trans == CblasNoTrans) ? B->size2 : B->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != MA || N != MB || NA != NB) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_dsyr2k (CblasRowMajor, Uplo, Trans, INT (N), INT (NA), alpha, A->data, INT (A->tda), B->data, INT (B->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } int gsl_blas_csyr2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, const gsl_complex_float beta, gsl_matrix_complex_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (Trans == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (Trans == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (Trans == CblasNoTrans) ? B->size2 : B->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != MA || N != MB || NA != NB) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_csyr2k (CblasRowMajor, Uplo, Trans, INT (N), INT (NA), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } int gsl_blas_zsyr2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, const gsl_complex beta, gsl_matrix_complex * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (Trans == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (Trans == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (Trans == CblasNoTrans) ? B->size2 : B->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != MA || N != MB || NA != NB) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_zsyr2k (CblasRowMajor, Uplo, Trans, INT (N), INT (NA), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), GSL_COMPLEX_P (&beta), C->data, INT (C->tda)); return GSL_SUCCESS; } /* HER2K */ int gsl_blas_cher2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, float beta, gsl_matrix_complex_float * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (Trans == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (Trans == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (Trans == CblasNoTrans) ? B->size2 : B->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != MA || N != MB || NA != NB) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_cher2k (CblasRowMajor, Uplo, Trans, INT (N), INT (NA), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } int gsl_blas_zher2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, double beta, gsl_matrix_complex * C) { const size_t M = C->size1; const size_t N = C->size2; const size_t MA = (Trans == CblasNoTrans) ? A->size1 : A->size2; const size_t NA = (Trans == CblasNoTrans) ? A->size2 : A->size1; const size_t MB = (Trans == CblasNoTrans) ? B->size1 : B->size2; const size_t NB = (Trans == CblasNoTrans) ? B->size2 : B->size1; if (M != N) { GSL_ERROR ("matrix C must be square", GSL_ENOTSQR); } else if (N != MA || N != MB || NA != NB) { GSL_ERROR ("invalid length", GSL_EBADLEN); } cblas_zher2k (CblasRowMajor, Uplo, Trans, INT (N), INT (NA), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda), beta, C->data, INT (C->tda)); return GSL_SUCCESS; } /* TRMM */ int gsl_blas_strmm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, float alpha, const gsl_matrix_float * A, gsl_matrix_float * B) { const size_t M = B->size1; const size_t N = B->size2; const size_t MA = A->size1; const size_t NA = A->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && M == MA) || (Side == CblasRight && N == MA)) { cblas_strmm (CblasRowMajor, Side, Uplo, TransA, Diag, INT (M), INT (N), alpha, A->data, INT (A->tda), B->data, INT (B->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_dtrmm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, double alpha, const gsl_matrix * A, gsl_matrix * B) { const size_t M = B->size1; const size_t N = B->size2; const size_t MA = A->size1; const size_t NA = A->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && M == MA) || (Side == CblasRight && N == MA)) { cblas_dtrmm (CblasRowMajor, Side, Uplo, TransA, Diag, INT (M), INT (N), alpha, A->data, INT (A->tda), B->data, INT (B->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_ctrmm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, gsl_matrix_complex_float * B) { const size_t M = B->size1; const size_t N = B->size2; const size_t MA = A->size1; const size_t NA = A->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && M == MA) || (Side == CblasRight && N == MA)) { cblas_ctrmm (CblasRowMajor, Side, Uplo, TransA, Diag, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_ztrmm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_complex alpha, const gsl_matrix_complex * A, gsl_matrix_complex * B) { const size_t M = B->size1; const size_t N = B->size2; const size_t MA = A->size1; const size_t NA = A->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && M == MA) || (Side == CblasRight && N == MA)) { cblas_ztrmm (CblasRowMajor, Side, Uplo, TransA, Diag, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } /* TRSM */ int gsl_blas_strsm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, float alpha, const gsl_matrix_float * A, gsl_matrix_float * B) { const size_t M = B->size1; const size_t N = B->size2; const size_t MA = A->size1; const size_t NA = A->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && M == MA) || (Side == CblasRight && N == MA)) { cblas_strsm (CblasRowMajor, Side, Uplo, TransA, Diag, INT (M), INT (N), alpha, A->data, INT (A->tda), B->data, INT (B->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_dtrsm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, double alpha, const gsl_matrix * A, gsl_matrix * B) { const size_t M = B->size1; const size_t N = B->size2; const size_t MA = A->size1; const size_t NA = A->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && M == MA) || (Side == CblasRight && N == MA)) { cblas_dtrsm (CblasRowMajor, Side, Uplo, TransA, Diag, INT (M), INT (N), alpha, A->data, INT (A->tda), B->data, INT (B->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_ctrsm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, gsl_matrix_complex_float * B) { const size_t M = B->size1; const size_t N = B->size2; const size_t MA = A->size1; const size_t NA = A->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && M == MA) || (Side == CblasRight && N == MA)) { cblas_ctrsm (CblasRowMajor, Side, Uplo, TransA, Diag, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } int gsl_blas_ztrsm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_complex alpha, const gsl_matrix_complex * A, gsl_matrix_complex * B) { const size_t M = B->size1; const size_t N = B->size2; const size_t MA = A->size1; const size_t NA = A->size2; if (MA != NA) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } if ((Side == CblasLeft && M == MA) || (Side == CblasRight && N == MA)) { cblas_ztrsm (CblasRowMajor, Side, Uplo, TransA, Diag, INT (M), INT (N), GSL_COMPLEX_P (&alpha), A->data, INT (A->tda), B->data, INT (B->tda)); return GSL_SUCCESS; } else { GSL_ERROR ("invalid length", GSL_EBADLEN); } } sources_5316/external/gsl/gsl_fft__real_pass_5.c0000664000176700017670000002437211723710247020554 0ustar paulpaul/* fft/real_pass_5.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_real,pass_5) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[]) { size_t k, k1; const size_t factor = 5; const size_t m = n / factor; const size_t q = n / product; const size_t product_1 = product / factor; const ATOMIC sina = sin (2.0 * M_PI / 5.0); const ATOMIC sinb = sin (2.0 * M_PI / 10.0); for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1; const size_t from1 = from0 + m; const size_t from2 = from1 + m; const size_t from3 = from2 + m; const size_t from4 = from3 + m; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC z3_real = VECTOR(in,istride,from3); const ATOMIC z4_real = VECTOR(in,istride,from4); /* t1 = z1 + z4 */ const ATOMIC t1_real = z1_real + z4_real; /* t2 = z2 + z3 */ const ATOMIC t2_real = z2_real + z3_real; /* t3 = z1 - z4 */ const ATOMIC t3_real = z1_real - z4_real; /* t4 = z2 - z3 */ const ATOMIC t4_real = z2_real - z3_real; /* t5 = t1 + t2 */ const ATOMIC t5_real = t1_real + t2_real; /* t6 = (sqrt(5)/4)(t1 - t2) */ const ATOMIC t6_real = (sqrt (5.0) / 4.0) * (t1_real - t2_real); /* t7 = z0 - ((t5)/4) */ const ATOMIC t7_real = z0_real - t5_real / 4.0; /* t8 = t7 + t6 */ const ATOMIC t8_real = t7_real + t6_real; /* t9 = t7 - t6 */ const ATOMIC t9_real = t7_real - t6_real; /* t10 = -(sin(2 pi/5) t3 + sin(2 pi/10) t4 ) */ const ATOMIC t10_real = -sina * t3_real - sinb * t4_real; /* t11 = -(sin(2 pi/10) t3 - sin(2 pi/5) t4) */ const ATOMIC t11_real = -sinb * t3_real + sina * t4_real; /* x0 = z0 + t5 */ const ATOMIC x0_real = z0_real + t5_real; /* x1 = t8 + i t10 */ const ATOMIC x1_real = t8_real; const ATOMIC x1_imag = t10_real; /* x2 = t9 + i t11 */ const ATOMIC x2_real = t9_real; const ATOMIC x2_imag = t11_real; const size_t to0 = product * k1; const size_t to1 = to0 + 2 * product_1 - 1; const size_t to2 = to1 + 2 * product_1; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to1 + 1) = x1_imag; VECTOR(out,ostride,to2) = x2_real; VECTOR(out,ostride,to2 + 1) = x2_imag; } if (product_1 == 1) return; for (k = 1; k < (product_1 + 1) / 2; k++) { const ATOMIC w1_real = GSL_REAL(twiddle1[k - 1]); const ATOMIC w1_imag = -GSL_IMAG(twiddle1[k - 1]); const ATOMIC w2_real = GSL_REAL(twiddle2[k - 1]); const ATOMIC w2_imag = -GSL_IMAG(twiddle2[k - 1]); const ATOMIC w3_real = GSL_REAL(twiddle3[k - 1]); const ATOMIC w3_imag = -GSL_IMAG(twiddle3[k - 1]); const ATOMIC w4_real = GSL_REAL(twiddle4[k - 1]); const ATOMIC w4_imag = -GSL_IMAG(twiddle4[k - 1]); for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1 + 2 * k - 1; const size_t from1 = from0 + m; const size_t from2 = from1 + m; const size_t from3 = from2 + m; const size_t from4 = from3 + m; const ATOMIC f0_real = VECTOR(in,istride,from0); const ATOMIC f0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC f1_real = VECTOR(in,istride,from1); const ATOMIC f1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC f2_real = VECTOR(in,istride,from2); const ATOMIC f2_imag = VECTOR(in,istride,from2 + 1); const ATOMIC f3_real = VECTOR(in,istride,from3); const ATOMIC f3_imag = VECTOR(in,istride,from3 + 1); const ATOMIC f4_real = VECTOR(in,istride,from4); const ATOMIC f4_imag = VECTOR(in,istride,from4 + 1); const ATOMIC z0_real = f0_real; const ATOMIC z0_imag = f0_imag; const ATOMIC z1_real = w1_real * f1_real - w1_imag * f1_imag; const ATOMIC z1_imag = w1_real * f1_imag + w1_imag * f1_real; const ATOMIC z2_real = w2_real * f2_real - w2_imag * f2_imag; const ATOMIC z2_imag = w2_real * f2_imag + w2_imag * f2_real; const ATOMIC z3_real = w3_real * f3_real - w3_imag * f3_imag; const ATOMIC z3_imag = w3_real * f3_imag + w3_imag * f3_real; const ATOMIC z4_real = w4_real * f4_real - w4_imag * f4_imag; const ATOMIC z4_imag = w4_real * f4_imag + w4_imag * f4_real; /* compute x = W(5) z */ /* t1 = z1 + z4 */ const ATOMIC t1_real = z1_real + z4_real; const ATOMIC t1_imag = z1_imag + z4_imag; /* t2 = z2 + z3 */ const ATOMIC t2_real = z2_real + z3_real; const ATOMIC t2_imag = z2_imag + z3_imag; /* t3 = z1 - z4 */ const ATOMIC t3_real = z1_real - z4_real; const ATOMIC t3_imag = z1_imag - z4_imag; /* t4 = z2 - z3 */ const ATOMIC t4_real = z2_real - z3_real; const ATOMIC t4_imag = z2_imag - z3_imag; /* t5 = t1 + t2 */ const ATOMIC t5_real = t1_real + t2_real; const ATOMIC t5_imag = t1_imag + t2_imag; /* t6 = (sqrt(5)/4)(t1 - t2) */ const ATOMIC t6_real = (sqrt (5.0) / 4.0) * (t1_real - t2_real); const ATOMIC t6_imag = (sqrt (5.0) / 4.0) * (t1_imag - t2_imag); /* t7 = z0 - ((t5)/4) */ const ATOMIC t7_real = z0_real - t5_real / 4.0; const ATOMIC t7_imag = z0_imag - t5_imag / 4.0; /* t8 = t7 + t6 */ const ATOMIC t8_real = t7_real + t6_real; const ATOMIC t8_imag = t7_imag + t6_imag; /* t9 = t7 - t6 */ const ATOMIC t9_real = t7_real - t6_real; const ATOMIC t9_imag = t7_imag - t6_imag; /* t10 = - (sin(2 pi/5) t3 + sin(2 pi/10) t4) */ const ATOMIC t10_real = -sina * t3_real - sinb * t4_real; const ATOMIC t10_imag = -sina * t3_imag - sinb * t4_imag; /* t11 = -(sin(2 pi/10) t3 - sin(2 pi/5) t4) */ const ATOMIC t11_real = -sinb * t3_real + sina * t4_real; const ATOMIC t11_imag = -sinb * t3_imag + sina * t4_imag; /* x0 = z0 + t5 */ const ATOMIC x0_real = z0_real + t5_real; const ATOMIC x0_imag = z0_imag + t5_imag; /* x1 = t8 + i t10 */ const ATOMIC x1_real = t8_real - t10_imag; const ATOMIC x1_imag = t8_imag + t10_real; /* x2 = t9 + i t11 */ const ATOMIC x2_real = t9_real - t11_imag; const ATOMIC x2_imag = t9_imag + t11_real; /* x3 = t9 - i t11 */ const ATOMIC x3_real = t9_real + t11_imag; const ATOMIC x3_imag = t9_imag - t11_real; /* x4 = t8 - i t10 */ const ATOMIC x4_real = t8_real + t10_imag; const ATOMIC x4_imag = t8_imag - t10_real; const size_t to0 = k1 * product + 2 * k - 1; const size_t to1 = to0 + 2 * product_1; const size_t to2 = to1 + 2 * product_1; const size_t to3 = 2 * product_1 - 2 * k + k1 * product - 1; const size_t to4 = to3 + 2 * product_1; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to0 + 1) = x0_imag; VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to1 + 1) = x1_imag; VECTOR(out,ostride,to2) = x2_real; VECTOR(out,ostride,to2 + 1) = x2_imag; VECTOR(out,ostride,to3) = x4_real; VECTOR(out,ostride,to3 + 1) = -x4_imag; VECTOR(out,ostride,to4) = x3_real; VECTOR(out,ostride,to4 + 1) = -x3_imag; } } if (product_1 % 2 == 1) return; for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1 + product_1 - 1; const size_t from1 = from0 + m; const size_t from2 = from1 + m; const size_t from3 = from2 + m; const size_t from4 = from3 + m; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC z3_real = VECTOR(in,istride,from3); const ATOMIC z4_real = VECTOR(in,istride,from4); const ATOMIC t1 = z1_real - z4_real; const ATOMIC t2 = z1_real + z4_real; const ATOMIC t3 = z2_real - z3_real; const ATOMIC t4 = z2_real + z3_real; const ATOMIC t5 = t1 - t3; const ATOMIC t6 = z0_real + t5 / 4.0; const ATOMIC t7 = (sqrt (5.0) / 4.0) * (t1 + t3); const size_t to0 = k1 * product + product_1 - 1; const size_t to1 = to0 + 2 * product_1; const size_t to2 = to1 + 2 * product_1; VECTOR(out,ostride,to0) = t6 + t7; VECTOR(out,ostride,to0 + 1) = -sinb * t2 - sina * t4; VECTOR(out,ostride,to1) = t6 - t7; VECTOR(out,ostride,to1 + 1) = -sina * t2 + sinb * t4; VECTOR(out,ostride,to2) = z0_real - t5; } return; } sources_5316/external/gsl/gsl_cdf__hypergeometric.c0000664000176700017670000001014411723710247021352 0ustar paulpaul/* cdf/hypergeometric.c * * Copyright (C) 2004 Jason H. Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * Computes the cumulative distribution function for a hypergeometric * random variable. A hypergeometric random variable X is the number * of elements of type 1 in a sample of size t, drawn from a population * of size n1 + n2, in which n1 are of type 1 and n2 are of type 2. * * This algorithm computes Pr( X <= k ) by summing the terms from * the mass function, Pr( X = k ). * * References: * * T. Wu. An accurate computation of the hypergeometric distribution * function. ACM Transactions on Mathematical Software. Volume 19, number 1, * March 1993. * This algorithm is not used, since it requires factoring the * numerator and denominator, then cancelling. It is more accurate * than the algorithm used here, but the cancellation requires more * time than the algorithm used here. * * W. Feller. An Introduction to Probability Theory and Its Applications, * third edition. 1968. Chapter 2, section 6. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_cdf.h" #include "gsl_randist.h" #include "gsl_cdf__error.h" static double lower_tail (const unsigned int k, const unsigned int n1, const unsigned int n2, const unsigned int t) { double relerr; int i = k; double s, P; s = gsl_ran_hypergeometric_pdf (i, n1, n2, t); P = s; while (i > 0) { double factor = (i / (n1 - i + 1.0)) * ((n2 + i - t) / (t - i + 1.0)); s *= factor; P += s; relerr = s / P; if (relerr < GSL_DBL_EPSILON) break; i--; } return P; } static double upper_tail (const unsigned int k, const unsigned int n1, const unsigned int n2, const unsigned int t) { double relerr; unsigned int i = k + 1; double s, Q; s = gsl_ran_hypergeometric_pdf (i, n1, n2, t); Q = s; while (i < t) { double factor = ((n1 - i) / (i + 1.0)) * ((t - i) / (n2 + i + 1.0 - t)); s *= factor; Q += s; relerr = s / Q; if (relerr < GSL_DBL_EPSILON) break; i++; } return Q; } /* * Pr (X <= k) */ double gsl_cdf_hypergeometric_P (const unsigned int k, const unsigned int n1, const unsigned int n2, const unsigned int t) { double P; if (t > (n1 + n2)) { CDF_ERROR ("t larger than population size", GSL_EDOM); } else if (k >= n1 || k >= t) { P = 1.0; } else if (k < 0.0) { P = 0.0; } else { double midpoint = (int) (t * n1 / (n1 + n2)); if (k >= midpoint) { P = 1 - upper_tail (k, n1, n2, t); } else { P = lower_tail (k, n1, n2, t); } } return P; } /* * Pr (X > k) */ double gsl_cdf_hypergeometric_Q (const unsigned int k, const unsigned int n1, const unsigned int n2, const unsigned int t) { double Q; if (t > (n1 + n2)) { CDF_ERROR ("t larger than population size", GSL_EDOM); } else if (k >= n1 || k >= t) { Q = 0.0; } else if (k < 0.0) { Q = 1.0; } else { double midpoint = (int) (t * n1 / (n1 + n2)); if (k < midpoint) { Q = 1 - lower_tail (k, n1, n2, t); } else { Q = upper_tail (k, n1, n2, t); } } return Q; } sources_5316/external/gsl/gsl_statistics__skew_source.c0000664000176700017670000000335511723710247022321 0ustar paulpaul/* statistics/skew_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,skew) (const BASE data[], const size_t stride, const size_t n) { const double mean = FUNCTION(gsl_stats,mean)(data, stride, n); const double sd = FUNCTION(gsl_stats,sd_m)(data, stride, n, mean); return FUNCTION(gsl_stats,skew_m_sd)(data, stride, n, mean, sd); } double FUNCTION(gsl_stats,skew_m_sd) (const BASE data[], const size_t stride, const size_t n, const double mean, const double sd) { /* takes a dataset and finds the skewness */ long double skew = 0; size_t i; /* find the sum of the cubed deviations, normalized by the sd. */ /* we use a recurrence relation to stably update a running value so there aren't any large sums that can overflow */ for (i = 0; i < n; i++) { const long double x = (data[i * stride] - mean) / sd; skew += (x * x * x - skew) / (i + 1); } return skew; } sources_5316/external/gsl/gsl_sf_elljac.h0000664000176700017670000000252411705263724017306 0ustar paulpaul/* specfunc/gsl_sf_elljac.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_ELLJAC_H__ #define __GSL_SF_ELLJAC_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Jacobian elliptic functions sn, dn, cn, * by descending Landen transformations * * exceptions: GSL_EDOM */ int gsl_sf_elljac_e(double u, double m, double * sn, double * cn, double * dn); __END_DECLS #endif /* __GSL_SF_ELLJAC_H__ */ sources_5316/external/gsl/gsl_cblas__source_her.h0000664000176700017670000000533311705263724021026 0ustar paulpaul/* blas/source_her.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (order == CblasColMajor) ? -1 : 1; INDEX i, j; if (alpha == 0.0) return; if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { const BASE tmp_real = alpha * CONST_REAL(X, ix); const BASE tmp_imag = alpha * conj * CONST_IMAG(X, ix); INDEX jx = ix; { const BASE X_real = CONST_REAL(X, jx); const BASE X_imag = -conj * CONST_IMAG(X, jx); REAL(A, lda * i + i) += X_real * tmp_real - X_imag * tmp_imag; IMAG(A, lda * i + i) = 0; jx += incX; } for (j = i + 1; j < N; j++) { const BASE X_real = CONST_REAL(X, jx); const BASE X_imag = -conj * CONST_IMAG(X, jx); REAL(A, lda * i + j) += X_real * tmp_real - X_imag * tmp_imag; IMAG(A, lda * i + j) += X_imag * tmp_real + X_real * tmp_imag; jx += incX; } ix += incX; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { const BASE tmp_real = alpha * CONST_REAL(X, ix); const BASE tmp_imag = alpha * conj * CONST_IMAG(X, ix); INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE X_real = CONST_REAL(X, jx); const BASE X_imag = -conj * CONST_IMAG(X, jx); REAL(A, lda * i + j) += X_real * tmp_real - X_imag * tmp_imag; IMAG(A, lda * i + j) += X_imag * tmp_real + X_real * tmp_imag; jx += incX; } { const BASE X_real = CONST_REAL(X, jx); const BASE X_imag = -conj * CONST_IMAG(X, jx); REAL(A, lda * i + i) += X_real * tmp_real - X_imag * tmp_imag; IMAG(A, lda * i + i) = 0; jx += incX; } ix += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_specfunc__bessel_I0.c0000664000176700017670000001424511723710247021211 0ustar paulpaul/* specfunc/bessel_I0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besi0 */ /* chebyshev expansions series for bi0 on the interval 0. to 9.00000d+00 with weighted error 2.46e-18 log weighted error 17.61 significant figures required 17.90 decimal places required 18.15 series for ai0 on the interval 1.25000d-01 to 3.33333d-01 with weighted error 7.87e-17 log weighted error 16.10 significant figures required 14.69 decimal places required 16.76 series for ai02 on the interval 0. to 1.25000d-01 with weighted error 3.79e-17 log weighted error 16.42 significant figures required 14.86 decimal places required 17.09 */ static double bi0_data[12] = { -.07660547252839144951, 1.92733795399380827000, .22826445869203013390, .01304891466707290428, .00043442709008164874, .00000942265768600193, .00000014340062895106, .00000000161384906966, .00000000001396650044, .00000000000009579451, .00000000000000053339, .00000000000000000245 }; static cheb_series bi0_cs = { bi0_data, 11, -1, 1, 11 }; static double ai0_data[21] = { .07575994494023796, .00759138081082334, .00041531313389237, .00001070076463439, -.00000790117997921, -.00000078261435014, .00000027838499429, .00000000825247260, -.00000001204463945, .00000000155964859, .00000000022925563, -.00000000011916228, .00000000001757854, .00000000000112822, -.00000000000114684, .00000000000027155, -.00000000000002415, -.00000000000000608, .00000000000000314, -.00000000000000071, .00000000000000007 }; static cheb_series ai0_cs = { ai0_data, 20, -1, 1, 13 }; static double ai02_data[22] = { .05449041101410882, .00336911647825569, .00006889758346918, .00000289137052082, .00000020489185893, .00000002266668991, .00000000339623203, .00000000049406022, .00000000001188914, -.00000000003149915, -.00000000001321580, -.00000000000179419, .00000000000071801, .00000000000038529, .00000000000001539, -.00000000000004151, -.00000000000000954, .00000000000000382, .00000000000000176, -.00000000000000034, -.00000000000000027, .00000000000000003 }; static cheb_series ai02_cs = { ai02_data, 21, -1, 1, 11 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_I0_scaled_e(const double x, gsl_sf_result * result) { double y = fabs(x); /* CHECK_POINTER(result) */ if(y < 2.0 * GSL_SQRT_DBL_EPSILON) { result->val = 1.0 - y; result->err = 0.5*y*y; return GSL_SUCCESS; } else if(y <= 3.0) { const double ey = exp(-y); gsl_sf_result c; cheb_eval_e(&bi0_cs, y*y/4.5-1.0, &c); result->val = ey * (2.75 + c.val); result->err = GSL_DBL_EPSILON * fabs(result->val) + ey * c.err; return GSL_SUCCESS; } else if(y <= 8.0) { const double sy = sqrt(y); gsl_sf_result c; cheb_eval_e(&ai0_cs, (48.0/y-11.0)/5.0, &c); result->val = (0.375 + c.val) / sy; result->err = 2.0 * GSL_DBL_EPSILON * (0.375 + fabs(c.val)) / sy; result->err += c.err / sy; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sy = sqrt(y); gsl_sf_result c; cheb_eval_e(&ai02_cs, 16.0/y-1.0, &c); result->val = (0.375 + c.val) / sy; result->err = 2.0 * GSL_DBL_EPSILON * (0.375 + fabs(c.val)) / sy; result->err += c.err / sy; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_I0_e(const double x, gsl_sf_result * result) { double y = fabs(x); /* CHECK_POINTER(result) */ if(y < 2.0 * GSL_SQRT_DBL_EPSILON) { result->val = 1.0; result->err = 0.5*y*y; return GSL_SUCCESS; } else if(y <= 3.0) { gsl_sf_result c; cheb_eval_e(&bi0_cs, y*y/4.5-1.0, &c); result->val = 2.75 + c.val; result->err = GSL_DBL_EPSILON * (2.75 + fabs(c.val)); result->err += c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(y < GSL_LOG_DBL_MAX - 1.0) { const double ey = exp(y); gsl_sf_result b_scaled; gsl_sf_bessel_I0_scaled_e(x, &b_scaled); result->val = ey * b_scaled.val; result->err = ey * b_scaled.err + y*GSL_DBL_EPSILON*fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_I0_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_I0_scaled_e(x, &result); ) } double gsl_sf_bessel_I0(const double x) { EVAL_RESULT(gsl_sf_bessel_I0_e(x, &result); ) } sources_5316/external/gsl/gsl_rng__ran1.c0000664000176700017670000000570311723710247017224 0ustar paulpaul/* rng/ran1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is an implementation of the algorithm used in Numerical Recipe's ran1 generator. It is MINSTD with a 32-element shuffle-box. */ static inline unsigned long int ran1_get (void *vstate); static double ran1_get_double (void *vstate); static void ran1_set (void *state, unsigned long int s); static const long int m = 2147483647, a = 16807, q = 127773, r = 2836; #define N_SHUFFLE 32 #define N_DIV (1 + 2147483646/N_SHUFFLE) typedef struct { unsigned long int x; unsigned long int n; unsigned long int shuffle[N_SHUFFLE]; } ran1_state_t; static inline unsigned long int ran1_get (void *vstate) { ran1_state_t *state = (ran1_state_t *) vstate; const unsigned long int x = state->x; const long int h = x / q; const long int t = a * (x - h * q) - h * r; if (t < 0) { state->x = t + m; } else { state->x = t; } { unsigned long int j = state->n / N_DIV; state->n = state->shuffle[j]; state->shuffle[j] = state->x; } return state->n; } static double ran1_get_double (void *vstate) { float x_max = 1 - 1.2e-7f ; /* Numerical Recipes version of 1-FLT_EPS */ float x = ran1_get (vstate) / 2147483647.0f ; if (x > x_max) return x_max ; return x ; } static void ran1_set (void *vstate, unsigned long int s) { ran1_state_t *state = (ran1_state_t *) vstate; int i; if (s == 0) s = 1; /* default seed is 1 */ for (i = 0; i < 8; i++) { long int h = s / q; long int t = a * (s - h * q) - h * r; if (t < 0) t += m; s = t; } for (i = N_SHUFFLE - 1; i >= 0; i--) { long int h = s / q; long int t = a * (s - h * q) - h * r; if (t < 0) t += m; s = t; state->shuffle[i] = s; } state->x = s; state->n = s; return; } static const gsl_rng_type ran1_type = {"ran1", /* name */ 2147483646, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (ran1_state_t), &ran1_set, &ran1_get, &ran1_get_double}; const gsl_rng_type *gsl_rng_ran1 = &ran1_type; sources_5316/external/gsl/gsl_poly__zsolve_quadratic.c0000664000176700017670000000505411723710247022136 0ustar paulpaul/* poly/zsolve_quadratic.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* complex_solve_quadratic.c - finds complex roots of a x^2 + b x + c = 0 */ #include "gsl__config.h" #include #include "gsl_complex.h" #include "gsl_poly.h" int gsl_poly_complex_solve_quadratic (double a, double b, double c, gsl_complex *z0, gsl_complex *z1) { double disc = b * b - 4 * a * c; if (a == 0) /* Handle linear case */ { if (b == 0) { return 0; } else { GSL_REAL(*z0) = -c / b; GSL_IMAG(*z0) = 0; return 1; }; } if (disc > 0) { if (b == 0) { double s = fabs (0.5 * sqrt (disc) / a); GSL_REAL (*z0) = -s; GSL_IMAG (*z0) = 0; GSL_REAL (*z1) = s; GSL_IMAG (*z1) = 0; } else { double sgnb = (b > 0 ? 1 : -1); double temp = -0.5 * (b + sgnb * sqrt (disc)); double r1 = temp / a; double r2 = c / temp; if (r1 < r2) { GSL_REAL (*z0) = r1; GSL_IMAG (*z0) = 0; GSL_REAL (*z1) = r2; GSL_IMAG (*z1) = 0; } else { GSL_REAL (*z0) = r2; GSL_IMAG (*z0) = 0; GSL_REAL (*z1) = r1; GSL_IMAG (*z1) = 0; } } return 2; } else if (disc == 0) { GSL_REAL (*z0) = -0.5 * b / a; GSL_IMAG (*z0) = 0; GSL_REAL (*z1) = -0.5 * b / a; GSL_IMAG (*z1) = 0; return 2; } else { double s = fabs (0.5 * sqrt (-disc) / a); GSL_REAL (*z0) = -0.5 * b / a; GSL_IMAG (*z0) = -s; GSL_REAL (*z1) = -0.5 * b / a; GSL_IMAG (*z1) = s; return 2; } } sources_5316/external/gsl/gsl_specfunc__hyperg_2F0.c0000664000176700017670000000357611723710247021316 0ustar paulpaul/* specfunc/hyperg_2F0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_hyperg.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__hyperg.h" int gsl_sf_hyperg_2F0_e(const double a, const double b, const double x, gsl_sf_result * result) { if(x < 0.0) { /* Use "definition" 2F0(a,b,x) = (-1/x)^a U(a,1+a-b,-1/x). */ gsl_sf_result U; double pre = pow(-1.0/x, a); int stat_U = gsl_sf_hyperg_U_e(a, 1.0+a-b, -1.0/x, &U); result->val = pre * U.val; result->err = GSL_DBL_EPSILON * fabs(result->val) + pre * U.err; return stat_U; } else if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else { /* Use asymptotic series. ?? */ /* return hyperg_2F0_series(a, b, x, -1, result, &prec); */ DOMAIN_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_hyperg_2F0(const double a, const double b, const double x) { EVAL_RESULT(gsl_sf_hyperg_2F0_e(a, b, x, &result)); } sources_5316/external/gsl/gsl_sf__bessel_Yn.c0000644000176700017670000001262510707442037020127 0ustar paulpaul/* specfunc/bessel_Yn.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_gamma.h" #include "gsl_sf_psi.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_amp_phase.h" #include "gsl_sf__bessel_olver.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* assumes n >= 1 */ static int bessel_Yn_small_x(const int n, const double x, gsl_sf_result * result) { int k; double y = 0.25 * x * x; double ln_x_2 = log(0.5*x); gsl_sf_result ln_nm1_fact; double k_term; double term1, sum1, ln_pre1; double term2, sum2, pre2; gsl_sf_lnfact_e((unsigned int)(n-1), &ln_nm1_fact); ln_pre1 = -n*ln_x_2 + ln_nm1_fact.val; if(ln_pre1 > GSL_LOG_DBL_MAX - 3.0) GSL_ERROR ("error", GSL_EOVRFLW); sum1 = 1.0; k_term = 1.0; for(k=1; k<=n-1; k++) { k_term *= y/(k * (n-k)); sum1 += k_term; } term1 = -exp(ln_pre1) * sum1 / M_PI; pre2 = -exp(n*ln_x_2) / M_PI; if(fabs(pre2) > 0.0) { const int KMAX = 20; gsl_sf_result psi_n; gsl_sf_result npk_fact; double yk = 1.0; double k_fact = 1.0; double psi_kp1 = -M_EULER; double psi_npkp1; gsl_sf_psi_int_e(n, &psi_n); gsl_sf_fact_e((unsigned int)n, &npk_fact); psi_npkp1 = psi_n.val + 1.0/n; sum2 = (psi_kp1 + psi_npkp1 - 2.0*ln_x_2)/npk_fact.val; for(k=1; kval = term1 + term2; result->err = GSL_DBL_EPSILON * (fabs(ln_pre1)*fabs(term1) + fabs(term2)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Yn_e(int n, const double x, gsl_sf_result * result) { int sign = 1; if(n < 0) { /* reduce to case n >= 0 */ n = -n; if(GSL_IS_ODD(n)) sign = -1; } /* CHECK_POINTER(result) */ if(n == 0) { int status = gsl_sf_bessel_Y0_e(x, result); result->val *= sign; return status; } else if(n == 1) { int status = gsl_sf_bessel_Y1_e(x, result); result->val *= sign; return status; } else { if(x <= 0.0) { DOMAIN_ERROR(result); } if(x < 5.0) { int status = bessel_Yn_small_x(n, x, result); result->val *= sign; return status; } else if(GSL_ROOT3_DBL_EPSILON * x > (n*n + 1.0)) { int status = gsl_sf_bessel_Ynu_asympx_e((double)n, x, result); result->val *= sign; return status; } else if(n > 50) { int status = gsl_sf_bessel_Ynu_asymp_Olver_e((double)n, x, result); result->val *= sign; return status; } else { double two_over_x = 2.0/x; gsl_sf_result r_by; gsl_sf_result r_bym; int stat_1 = gsl_sf_bessel_Y1_e(x, &r_by); int stat_0 = gsl_sf_bessel_Y0_e(x, &r_bym); double bym = r_bym.val; double by = r_by.val; double byp; int j; for(j=1; jval = sign * by; result->err = fabs(result->val) * (fabs(r_by.err/r_by.val) + fabs(r_bym.err/r_bym.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_1, stat_0); } } } int gsl_sf_bessel_Yn_array(const int nmin, const int nmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(nmin < 0 || nmax < nmin || x <= 0.0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; GSL_ERROR ("error", GSL_EDOM); } else { gsl_sf_result r_Ynm1; gsl_sf_result r_Yn; int stat_nm1 = gsl_sf_bessel_Yn_e(nmin, x, &r_Ynm1); int stat_n = gsl_sf_bessel_Yn_e(nmin+1, x, &r_Yn); double Ynp1; double Yn = r_Yn.val; double Ynm1 = r_Ynm1.val; int n; int stat = GSL_ERROR_SELECT_2(stat_nm1, stat_n); if(stat == GSL_SUCCESS) { for(n=nmin+1; n<=nmax+1; n++) { result_array[n-nmin-1] = Ynm1; Ynp1 = -Ynm1 + 2.0*n/x * Yn; Ynm1 = Yn; Yn = Ynp1; } } else { for(n=nmin; n<=nmax; n++) { result_array[n-nmin] = 0.0; } } return stat; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_Yn(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_Yn_e(n, x, &result)); } sources_5316/external/gsl/gsl_sf.h0000664000176700017670000000163011705263724015771 0ustar paulpaul/* Author: G. Jungman */ #ifndef __GSL_SF_H__ #define __GSL_SF_H__ #include "gsl_sf_result.h" #include "gsl_sf_airy.h" #include "gsl_sf_bessel.h" #include "gsl_sf_clausen.h" #include "gsl_sf_coupling.h" #include "gsl_sf_coulomb.h" #include "gsl_sf_dawson.h" #include "gsl_sf_debye.h" #include "gsl_sf_dilog.h" #include "gsl_sf_elementary.h" #include "gsl_sf_ellint.h" #include "gsl_sf_elljac.h" #include "gsl_sf_erf.h" #include "gsl_sf_exp.h" #include "gsl_sf_expint.h" #include "gsl_sf_fermi_dirac.h" #include "gsl_sf_gamma.h" #include "gsl_sf_gegenbauer.h" #include "gsl_sf_hyperg.h" #include "gsl_sf_laguerre.h" #include "gsl_sf_lambert.h" #include "gsl_sf_legendre.h" #include "gsl_sf_log.h" #include "gsl_sf_mathieu.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_psi.h" #include "gsl_sf_synchrotron.h" #include "gsl_sf_transport.h" #include "gsl_sf_trig.h" #include "gsl_sf_zeta.h" #endif /* __GSL_SF_H__ */ sources_5316/external/gsl/gsl_matrix__init_source.c0000664000176700017670000001364011723710247021423 0ustar paulpaul/* matrix/init_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ TYPE (gsl_matrix) * FUNCTION (gsl_matrix, alloc) (const size_t n1, const size_t n2) { TYPE (gsl_block) * block; TYPE (gsl_matrix) * m; if (n1 == 0) { GSL_ERROR_VAL ("matrix dimension n1 must be positive integer", GSL_EINVAL, 0); } else if (n2 == 0) { GSL_ERROR_VAL ("matrix dimension n2 must be positive integer", GSL_EINVAL, 0); } m = (TYPE (gsl_matrix) *) malloc (sizeof (TYPE (gsl_matrix))); if (m == 0) { GSL_ERROR_VAL ("failed to allocate space for matrix struct", GSL_ENOMEM, 0); } /* FIXME: n1*n2 could overflow for large dimensions */ block = FUNCTION(gsl_block, alloc) (n1 * n2) ; if (block == 0) { GSL_ERROR_VAL ("failed to allocate space for block", GSL_ENOMEM, 0); } m->data = block->data; m->size1 = n1; m->size2 = n2; m->tda = n2; m->block = block; m->owner = 1; return m; } TYPE (gsl_matrix) * FUNCTION (gsl_matrix, calloc) (const size_t n1, const size_t n2) { size_t i; TYPE (gsl_matrix) * m = FUNCTION (gsl_matrix, alloc) (n1, n2); if (m == 0) return 0; /* initialize matrix to zero */ for (i = 0; i < MULTIPLICITY * n1 * n2; i++) { m->data[i] = 0; } return m; } TYPE (gsl_matrix) * FUNCTION (gsl_matrix, alloc_from_block) (TYPE(gsl_block) * block, const size_t offset, const size_t n1, const size_t n2, const size_t d2) { TYPE (gsl_matrix) * m; if (n1 == 0) { GSL_ERROR_VAL ("matrix dimension n1 must be positive integer", GSL_EINVAL, 0); } else if (n2 == 0) { GSL_ERROR_VAL ("matrix dimension n2 must be positive integer", GSL_EINVAL, 0); } else if (d2 < n2) { GSL_ERROR_VAL ("matrix dimension d2 must be greater than n2", GSL_EINVAL, 0); } else if (block->size < offset + n1 * d2) { GSL_ERROR_VAL ("matrix size exceeds available block size", GSL_EINVAL, 0); } m = (TYPE (gsl_matrix) *) malloc (sizeof (TYPE (gsl_matrix))); if (m == 0) { GSL_ERROR_VAL ("failed to allocate space for matrix struct", GSL_ENOMEM, 0); } m->data = block->data + MULTIPLICITY * offset; m->size1 = n1; m->size2 = n2; m->tda = d2; m->block = block; m->owner = 0; return m; } TYPE (gsl_matrix) * FUNCTION (gsl_matrix, alloc_from_matrix) (TYPE(gsl_matrix) * mm, const size_t k1, const size_t k2, const size_t n1, const size_t n2) { TYPE (gsl_matrix) * m; if (n1 == 0) { GSL_ERROR_VAL ("matrix dimension n1 must be positive integer", GSL_EINVAL, 0); } else if (n2 == 0) { GSL_ERROR_VAL ("matrix dimension n2 must be positive integer", GSL_EINVAL, 0); } else if (k1 + n1 > mm->size1) { GSL_ERROR_VAL ("submatrix dimension 1 exceeds size of original", GSL_EINVAL, 0); } else if (k2 + n2 > mm->size2) { GSL_ERROR_VAL ("submatrix dimension 2 exceeds size of original", GSL_EINVAL, 0); } m = (TYPE (gsl_matrix) *) malloc (sizeof (TYPE (gsl_matrix))); if (m == 0) { GSL_ERROR_VAL ("failed to allocate space for matrix struct", GSL_ENOMEM, 0); } m->data = mm->data + k1 * mm->tda + k2 ; m->size1 = n1; m->size2 = n2; m->tda = mm->tda; m->block = mm->block; m->owner = 0; return m; } void FUNCTION (gsl_matrix, free) (TYPE (gsl_matrix) * m) { if (m->owner) { FUNCTION(gsl_block, free) (m->block); } free (m); } void FUNCTION (gsl_matrix, set_identity) (TYPE (gsl_matrix) * m) { size_t i, j; ATOMIC * const data = m->data; const size_t p = m->size1 ; const size_t q = m->size2 ; const size_t tda = m->tda ; const BASE zero = ZERO; const BASE one = ONE; for (i = 0; i < p; i++) { for (j = 0; j < q; j++) { *(BASE *) (data + MULTIPLICITY * (i * tda + j)) = ((i == j) ? one : zero); } } } void FUNCTION (gsl_matrix, set_zero) (TYPE (gsl_matrix) * m) { size_t i, j; ATOMIC * const data = m->data; const size_t p = m->size1 ; const size_t q = m->size2 ; const size_t tda = m->tda ; const BASE zero = ZERO; for (i = 0; i < p; i++) { for (j = 0; j < q; j++) { *(BASE *) (data + MULTIPLICITY * (i * tda + j)) = zero; } } } void FUNCTION (gsl_matrix, set_all) (TYPE (gsl_matrix) * m, BASE x) { size_t i, j; ATOMIC * const data = m->data; const size_t p = m->size1 ; const size_t q = m->size2 ; const size_t tda = m->tda ; for (i = 0; i < p; i++) { for (j = 0; j < q; j++) { *(BASE *) (data + MULTIPLICITY * (i * tda + j)) = x; } } } sources_5316/external/gsl/gsl_histogram__calloc_range.c0000664000176700017670000000532711723710247022205 0ustar paulpaul/* gsl_histogram_calloc_range.c * Copyright (C) 2000 Simone Piccardi * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File gsl_histogram_calloc_range.c: * Routine to create a variable binning histogram providing * an input range vector. Need GSL library and header. * Do range check and allocate the histogram data. * * Author: S. Piccardi * Jan. 2000 * ***************************************************************/ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram.h" gsl_histogram * gsl_histogram_calloc_range (size_t n, double *range) { size_t i; gsl_histogram *h; /* check arguments */ if (n == 0) { GSL_ERROR_VAL ("histogram length n must be positive integer", GSL_EDOM, 0); } /* check ranges */ for (i = 0; i < n; i++) { if (range[i] >= range[i + 1]) { GSL_ERROR_VAL ("histogram bin extremes must be " "in increasing order", GSL_EDOM, 0); } } /* Allocate histogram */ h = (gsl_histogram *) malloc (sizeof (gsl_histogram)); if (h == 0) { GSL_ERROR_VAL ("failed to allocate space for histogram struct", GSL_ENOMEM, 0); } h->range = (double *) malloc ((n + 1) * sizeof (double)); if (h->range == 0) { /* exception in constructor, avoid memory leak */ free (h); GSL_ERROR_VAL ("failed to allocate space for histogram ranges", GSL_ENOMEM, 0); } h->bin = (double *) malloc (n * sizeof (double)); if (h->bin == 0) { /* exception in constructor, avoid memory leak */ free (h->range); free (h); GSL_ERROR_VAL ("failed to allocate space for histogram bins", GSL_ENOMEM, 0); } /* initialize ranges */ for (i = 0; i <= n; i++) { h->range[i] = range[i]; } /* clear contents */ for (i = 0; i < n; i++) { h->bin[i] = 0; } h->n = n; return h; } sources_5316/external/gsl/gsl_matrix__minmax_source.c0000664000176700017670000001256511723710247021756 0ustar paulpaul/* matrix/minmax_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ BASE FUNCTION (gsl_matrix, max) (const TYPE (gsl_matrix) * m) { /* finds the largest element of a matrix */ const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; BASE max = m->data[0 * tda + 0]; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { BASE x = m->data[i * tda + j]; if (x > max) max = x; #ifdef FP if (isnan (x)) return x; #endif } } return max; } BASE FUNCTION (gsl_matrix, min) (const TYPE (gsl_matrix) * m) { /* finds the smallest element of a matrix */ const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; BASE min = m->data[0 * tda + 0]; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { BASE x = m->data[i * tda + j]; if (x < min) min = x; #ifdef FP if (isnan (x)) return x; #endif } } return min; } void FUNCTION (gsl_matrix, minmax) (const TYPE (gsl_matrix) * m, BASE * min_out, BASE * max_out) { /* finds the smallest and largest elements of a matrix */ const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; BASE max = m->data[0 * tda + 0]; BASE min = m->data[0 * tda + 0]; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { BASE x = m->data[i * tda + j]; if (x < min) { min = x; } if (x > max) { max = x; } #ifdef FP if (isnan (x)) { *min_out = x; *max_out = x; return; } #endif } } *min_out = min; *max_out = max; } void FUNCTION (gsl_matrix, max_index) (const TYPE (gsl_matrix) * m, size_t * imax_out, size_t *jmax_out) { /* finds the largest element of a matrix */ const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; BASE max = m->data[0 * tda + 0]; size_t imax = 0, jmax = 0; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { BASE x = m->data[i * tda + j]; if (x > max) { max = x; imax = i; jmax = j; } #ifdef FP if (isnan (x)) { *imax_out = i; *jmax_out = j; return; } #endif } } *imax_out = imax; *jmax_out = jmax; } void FUNCTION (gsl_matrix, min_index) (const TYPE (gsl_matrix) * m, size_t * imin_out, size_t *jmin_out) { /* finds the largest element of a matrix */ const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; BASE min = m->data[0 * tda + 0]; size_t imin = 0, jmin = 0; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { BASE x = m->data[i * tda + j]; if (x < min) { min = x; imin = i; jmin = j; } #ifdef FP if (isnan (x)) { *imin_out = i; *jmin_out = j; return; } #endif } } *imin_out = imin; *jmin_out = jmin; } void FUNCTION (gsl_matrix, minmax_index) (const TYPE (gsl_matrix) * m, size_t * imin_out, size_t * jmin_out, size_t * imax_out, size_t * jmax_out) { /* finds the smallest and largest elements of a matrix */ const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; size_t imin = 0, jmin = 0, imax = 0, jmax = 0; BASE max = m->data[0 * tda + 0]; BASE min = m->data[0 * tda + 0]; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { BASE x = m->data[i * tda + j]; if (x < min) { min = x; imin = i; jmin = j; } if (x > max) { max = x; imax = i; jmax = j; } #ifdef FP if (isnan (x)) { *imin_out = i; *jmin_out = j; *imax_out = i; *jmax_out = j; return; } #endif } } *imin_out = imin; *jmin_out = jmin; *imax_out = imax; *jmax_out = jmax; } sources_5316/external/gsl/gsl_block_ushort.h0000664000176700017670000000454411705263724020066 0ustar paulpaul/* block/gsl_block_ushort.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_USHORT_H__ #define __GSL_BLOCK_USHORT_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_ushort_struct { size_t size; unsigned short *data; }; typedef struct gsl_block_ushort_struct gsl_block_ushort; gsl_block_ushort *gsl_block_ushort_alloc (const size_t n); gsl_block_ushort *gsl_block_ushort_calloc (const size_t n); void gsl_block_ushort_free (gsl_block_ushort * b); int gsl_block_ushort_fread (FILE * stream, gsl_block_ushort * b); int gsl_block_ushort_fwrite (FILE * stream, const gsl_block_ushort * b); int gsl_block_ushort_fscanf (FILE * stream, gsl_block_ushort * b); int gsl_block_ushort_fprintf (FILE * stream, const gsl_block_ushort * b, const char *format); int gsl_block_ushort_raw_fread (FILE * stream, unsigned short * b, const size_t n, const size_t stride); int gsl_block_ushort_raw_fwrite (FILE * stream, const unsigned short * b, const size_t n, const size_t stride); int gsl_block_ushort_raw_fscanf (FILE * stream, unsigned short * b, const size_t n, const size_t stride); int gsl_block_ushort_raw_fprintf (FILE * stream, const unsigned short * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_ushort_size (const gsl_block_ushort * b); unsigned short * gsl_block_ushort_data (const gsl_block_ushort * b); __END_DECLS #endif /* __GSL_BLOCK_USHORT_H__ */ sources_5316/external/gsl/gsl_cdf__chisqinv.c0000664000176700017670000000207111723710247020150 0ustar paulpaul/* cdf/chisqinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include "gsl__config.h" #include "gsl_cdf.h" #include "gsl_sf_gamma.h" double gsl_cdf_chisq_Pinv (const double P, const double nu) { return gsl_cdf_gamma_Pinv (P, nu / 2, 2.0); } double gsl_cdf_chisq_Qinv (const double Q, const double nu) { return gsl_cdf_gamma_Qinv (Q, nu / 2, 2.0); } sources_5316/external/gsl/gsl_cblas__source_gemv_r.h0000664000176700017670000000457111705263724021532 0ustar paulpaul/* blas/source_gemv_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; INDEX lenX, lenY; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; if (M == 0 || N == 0) return; if (alpha == 0.0 && beta == 1.0) return; if (Trans == CblasNoTrans) { lenX = N; lenY = M; } else { lenX = M; lenY = N; } /* form y := beta*y */ if (beta == 0.0) { INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { Y[iy] = 0.0; iy += incY; } } else if (beta != 1.0) { INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { Y[iy] *= beta; iy += incY; } } if (alpha == 0.0) return; if ((order == CblasRowMajor && Trans == CblasNoTrans) || (order == CblasColMajor && Trans == CblasTrans)) { /* form y := alpha*A*x + y */ INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { BASE temp = 0.0; INDEX ix = OFFSET(lenX, incX); for (j = 0; j < lenX; j++) { temp += X[ix] * A[lda * i + j]; ix += incX; } Y[iy] += alpha * temp; iy += incY; } } else if ((order == CblasRowMajor && Trans == CblasTrans) || (order == CblasColMajor && Trans == CblasNoTrans)) { /* form y := alpha*A'*x + y */ INDEX ix = OFFSET(lenX, incX); for (j = 0; j < lenX; j++) { const BASE temp = alpha * X[ix]; if (temp != 0.0) { INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { Y[iy] += temp * A[lda * j + i]; iy += incY; } } ix += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_histogram__get.c0000664000176700017670000000333011723710247020343 0ustar paulpaul/* histogram/get.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_histogram.h" #include "gsl_histogram__find.c" double gsl_histogram_get (const gsl_histogram * h, size_t i) { const size_t n = h->n; if (i >= n) { GSL_ERROR_VAL ("index lies outside valid range of 0 .. n - 1", GSL_EDOM, 0); } return h->bin[i]; } int gsl_histogram_get_range (const gsl_histogram * h, size_t i, double *lower, double *upper) { const size_t n = h->n; if (i >= n) { GSL_ERROR ("index lies outside valid range of 0 .. n - 1", GSL_EDOM); } *lower = h->range[i]; *upper = h->range[i + 1]; return GSL_SUCCESS; } int gsl_histogram_find (const gsl_histogram * h, const double x, size_t * i) { int status = find (h->n, h->range, x, i); if (status) { GSL_ERROR ("x not found in range of h", GSL_EDOM); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_roots__newton.c0000664000176700017670000000506011723710247020251 0ustar paulpaul/* roots/newton.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* newton.c -- newton root finding algorithm This is the classical Newton-Raphson iteration. x[i+1] = x[i] - f(x[i])/f'(x[i]) */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_roots.h" #include "gsl_roots__roots.h" typedef struct { double f, df; } newton_state_t; static int newton_init (void * vstate, gsl_function_fdf * fdf, double * root); static int newton_iterate (void * vstate, gsl_function_fdf * fdf, double * root); static int newton_init (void * vstate, gsl_function_fdf * fdf, double * root) { newton_state_t * state = (newton_state_t *) vstate; const double x = *root ; state->f = GSL_FN_FDF_EVAL_F (fdf, x); state->df = GSL_FN_FDF_EVAL_DF (fdf, x) ; return GSL_SUCCESS; } static int newton_iterate (void * vstate, gsl_function_fdf * fdf, double * root) { newton_state_t * state = (newton_state_t *) vstate; double root_new, f_new, df_new; if (state->df == 0.0) { GSL_ERROR("derivative is zero", GSL_EZERODIV); } root_new = *root - (state->f / state->df); *root = root_new ; GSL_FN_FDF_EVAL_F_DF(fdf, root_new, &f_new, &df_new); state->f = f_new ; state->df = df_new ; if (!gsl_finite(f_new)) { GSL_ERROR ("function value is not finite", GSL_EBADFUNC); } if (!gsl_finite (df_new)) { GSL_ERROR ("derivative value is not finite", GSL_EBADFUNC); } return GSL_SUCCESS; } static const gsl_root_fdfsolver_type newton_type = {"newton", /* name */ sizeof (newton_state_t), &newton_init, &newton_iterate}; const gsl_root_fdfsolver_type * gsl_root_fdfsolver_newton = &newton_type; sources_5316/external/gsl/gsl_specfunc__bessel_Knu.c0000664000176700017670000001116411723710247021473 0ustar paulpaul/* specfunc/bessel_Knu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_temme.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Knu_scaled_e(const double nu, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else { int N = (int)(nu + 0.5); double mu = nu - N; /* -1/2 <= mu <= 1/2 */ double K_mu, K_mup1, Kp_mu; double K_nu, K_nup1, K_num1; int n; if(x < 2.0) { gsl_sf_bessel_K_scaled_temme(mu, x, &K_mu, &K_mup1, &Kp_mu); } else { gsl_sf_bessel_K_scaled_steed_temme_CF2(mu, x, &K_mu, &K_mup1, &Kp_mu); } /* recurse forward to obtain K_num1, K_nu */ K_nu = K_mu; K_nup1 = K_mup1; for(n=0; nval = K_nu; result->err = 2.0 * GSL_DBL_EPSILON * (N + 4.0) * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_Knu_e(const double nu, const double x, gsl_sf_result * result) { gsl_sf_result b; int stat_K = gsl_sf_bessel_Knu_scaled_e(nu, x, &b); int stat_e = gsl_sf_exp_mult_err_e(-x, 0.0, b.val, b.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } int gsl_sf_bessel_lnKnu_e(const double nu, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else if(nu == 0.0) { gsl_sf_result K_scaled; /* This cannot underflow, and * it will not throw GSL_EDOM * since that is already checked. */ gsl_sf_bessel_K0_scaled_e(x, &K_scaled); result->val = -x + log(fabs(K_scaled.val)); result->err = GSL_DBL_EPSILON * fabs(x) + fabs(K_scaled.err/K_scaled.val); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 2.0 && nu > 1.0) { /* Make use of the inequality * Knu(x) <= 1/2 (2/x)^nu Gamma(nu), * which follows from the integral representation * [Abramowitz+Stegun, 9.6.23 (2)]. With this * we decide whether or not there is an overflow * problem because x is small. */ double ln_bound; gsl_sf_result lg_nu; gsl_sf_lngamma_e(nu, &lg_nu); ln_bound = -M_LN2 - nu*log(0.5*x) + lg_nu.val; if(ln_bound > GSL_LOG_DBL_MAX - 20.0) { /* x must be very small or nu very large (or both). */ double xi = 0.25*x*x; double sum = 1.0 - xi/(nu-1.0); if(nu > 2.0) sum += (xi/(nu-1.0)) * (xi/(nu-2.0)); result->val = ln_bound + log(sum); result->err = lg_nu.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* can drop-through here */ } { /* We passed the above tests, so no problem. * Evaluate as usual. Note the possible drop-through * in the above code! */ gsl_sf_result K_scaled; gsl_sf_bessel_Knu_scaled_e(nu, x, &K_scaled); result->val = -x + log(fabs(K_scaled.val)); result->err = GSL_DBL_EPSILON * fabs(x) + fabs(K_scaled.err/K_scaled.val); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_Knu_scaled(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_Knu_scaled_e(nu, x, &result)); } double gsl_sf_bessel_Knu(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_Knu_e(nu, x, &result)); } double gsl_sf_bessel_lnKnu(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_lnKnu_e(nu, x, &result)); } sources_5316/external/gsl/gsl_permute_vector_long_double.h0000664000176700017670000000275411705263724023005 0ustar paulpaul/* permutation/gsl_permute_vector_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_LONG_DOUBLE_H__ #define __GSL_PERMUTE_VECTOR_LONG_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_long_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_long_double (const gsl_permutation * p, gsl_vector_long_double * v); int gsl_permute_vector_long_double_inverse (const gsl_permutation * p, gsl_vector_long_double * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_rng__rand48.c0000664000176700017670000000742411723710247017465 0ustar paulpaul/* rng/rand48.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_sys.h" #include "gsl_rng.h" /* This is the Unix rand48() generator. The generator returns the upper 32 bits from each term of the sequence, x_{n+1} = (a x_n + c) mod m using 48-bit unsigned arithmetic, with a = 0x5DEECE66D , c = 0xB and m = 2^48. The seed specifies the upper 32 bits of the initial value, x_1, with the lower 16 bits set to 0x330E. The theoretical value of x_{10001} is 244131582646046. The period of this generator is ? FIXME (probably around 2^48). */ static inline void rand48_advance (void *vstate); static unsigned long int rand48_get (void *vstate); static double rand48_get_double (void *vstate); static void rand48_set (void *state, unsigned long int s); static const unsigned short int a0 = 0xE66D ; static const unsigned short int a1 = 0xDEEC ; static const unsigned short int a2 = 0x0005 ; static const unsigned short int c0 = 0x000B ; typedef struct { unsigned short int x0, x1, x2; } rand48_state_t; static inline void rand48_advance (void *vstate) { rand48_state_t *state = (rand48_state_t *) vstate; /* work with unsigned long ints throughout to get correct integer promotions of any unsigned short ints */ const unsigned long int x0 = (unsigned long int) state->x0 ; const unsigned long int x1 = (unsigned long int) state->x1 ; const unsigned long int x2 = (unsigned long int) state->x2 ; unsigned long int a ; a = a0 * x0 + c0 ; state->x0 = (a & 0xFFFF) ; a >>= 16 ; /* although the next line may overflow we only need the top 16 bits in the following stage, so it does not matter */ a += a0 * x1 + a1 * x0 ; state->x1 = (a & 0xFFFF) ; a >>= 16 ; a += a0 * x2 + a1 * x1 + a2 * x0 ; state->x2 = (a & 0xFFFF) ; } static unsigned long int rand48_get (void *vstate) { unsigned long int x1, x2; rand48_state_t *state = (rand48_state_t *) vstate; rand48_advance (state) ; x2 = (unsigned long int) state->x2; x1 = (unsigned long int) state->x1; return (x2 << 16) + x1; } static double rand48_get_double (void * vstate) { rand48_state_t *state = (rand48_state_t *) vstate; rand48_advance (state) ; return (ldexp((double) state->x2, -16) + ldexp((double) state->x1, -32) + ldexp((double) state->x0, -48)) ; } static void rand48_set (void *vstate, unsigned long int s) { rand48_state_t *state = (rand48_state_t *) vstate; if (s == 0) /* default seed */ { state->x0 = 0x330E ; state->x1 = 0xABCD ; state->x2 = 0x1234 ; } else { state->x0 = 0x330E ; state->x1 = s & 0xFFFF ; state->x2 = (s >> 16) & 0xFFFF ; } return; } static const gsl_rng_type rand48_type = {"rand48", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (rand48_state_t), &rand48_set, &rand48_get, &rand48_get_double }; const gsl_rng_type *gsl_rng_rand48 = &rand48_type; sources_5316/external/gsl/gsl_randist__gumbel.c0000664000176700017670000000345511723710247020516 0ustar paulpaul/* randist/gumbel.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* The Type I Gumbel distribution has the form, p(x) dx = a b exp(-(b exp(-ax) + ax)) dx and the Type II Gumbel distribution has the form, p(x) dx = b a x^-(a+1) exp(-b x^-a)) dx */ double gsl_ran_gumbel1 (const gsl_rng * r, const double a, const double b) { double x = gsl_rng_uniform_pos (r); double z = (log(b) - log(-log(x))) / a; return z; } double gsl_ran_gumbel1_pdf (const double x, const double a, const double b) { double p = a * b * exp (-(b * exp(-a * x) + a * x)); return p; } double gsl_ran_gumbel2 (const gsl_rng * r, const double a, const double b) { double x = gsl_rng_uniform_pos (r); double z = pow(-b / log(x), 1/a); return z; } double gsl_ran_gumbel2_pdf (const double x, const double a, const double b) { if (x <= 0) { return 0 ; } else { double p = b * a * pow(x,-(a+1)) * exp (-b * pow(x, -a)); return p; } } sources_5316/external/gsl/gsl_cblas__source_rotm.h0000664000176700017670000000270511705263724021231 0ustar paulpaul/* blas/source_rotmg.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX n; INDEX i = OFFSET(N, incX); INDEX j = OFFSET(N, incY); BASE h11, h21, h12, h22; if (P[0] == -1.0) { h11 = P[1]; h21 = P[2]; h12 = P[3]; h22 = P[4]; } else if (P[0] == 0.0) { h11 = 1.0; h21 = P[2]; h12 = P[3]; h22 = 1.0; } else if (P[0] == 1.0) { h11 = P[1]; h21 = -1.0; h12 = 1.0; h22 = P[4]; } else if (P[0] == -2.0) { return; } else { BLAS_ERROR("unrecognized value of P[0]"); return; } for (n = 0; n < N; n++) { const BASE w = X[i]; const BASE z = Y[j]; X[i] = h11 * w + h12 * z; Y[j] = h21 * w + h22 * z; i += incX; j += incY; } } sources_5316/external/gsl/gsl_specfunc__bessel_zero.c0000664000176700017670000007024111723710247021716 0ustar paulpaul/* specfunc/bessel_zero.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_airy.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel_olver.h" /* For Chebyshev expansions of the roots as functions of nu, * see [G. Nemeth, Mathematical Approximation of Special Functions]. * This gives the fits for all nu and s <= 10. * I made the fits for other values of s myself [GJ]. */ /* Chebyshev expansion: j_{nu,1} = c_k T_k*(nu/2), nu <= 2 */ static const double coef_jnu1_a[] = { 3.801775243633476, 1.360704737511120, -0.030707710261106, 0.004526823746202, -0.000808682832134, 0.000159218792489, -0.000033225189761, 0.000007205599763, -0.000001606110397, 0.000000365439424, -0.000000084498039, 0.000000019793815, -0.000000004687054, 0.000000001120052, -0.000000000269767, 0.000000000065420, -0.000000000015961, 0.000000000003914, -0.000000000000965, 0.000000000000239, -0.000000000000059, 0.000000000000015, -0.000000000000004, 0.000000000000001 }; /* Chebyshev expansion: j_{nu,1} = nu c_k T_k*((2/nu)^(2/3)), nu >= 2 */ static const double coef_jnu1_b[] = { 1.735063412537096, 0.784478100951978, 0.048881473180370, -0.000578279783021, -0.000038984957864, 0.000005758297879, -0.000000327583229, -0.000000003853878, 0.000000002284653, -0.000000000153079, -0.000000000000895, 0.000000000000283, 0.000000000000043, 0.000000000000010, -0.000000000000003 }; /* Chebyshev expansion: j_{nu,2} = c_k T_k*(nu/2), nu <= 2 */ static const double coef_jnu2_a[] = { 6.992370244046161, 1.446379282056534, -0.023458616207293, 0.002172149448700, -0.000246262775620, 0.000030990180959, -0.000004154183047, 0.000000580766328, -0.000000083648175, 0.000000012317355, -0.000000001844887, 0.000000000280076, -0.000000000042986, 0.000000000006658, -0.000000000001039, 0.000000000000163, -0.000000000000026, 0.000000000000004, -0.000000000000001 }; /* Chebyshev expansion: j_{nu,2} = nu c_k T_k*((2/nu)^(2/3)), nu >= 2 */ static const double coef_jnu2_b[] = { 2.465611864263400, 1.607952988471069, 0.138758034431497, -0.003687791182054, -0.000051276007868, 0.000045113570749, -0.000007579172152, 0.000000736469208, -0.000000011118527, -0.000000011919884, 0.000000002696788, -0.000000000314488, 0.000000000008124, 0.000000000005211, -0.000000000001292, 0.000000000000158, -0.000000000000004, -0.000000000000003, 0.000000000000001 }; /* Chebyshev expansion: j_{nu,3} = c_k T_k*(nu/3), nu <= 3 */ static const double coef_jnu3_a[] = { 10.869647065239236, 2.177524286141710, -0.034822817125293, 0.003167249102413, -0.000353960349344, 0.000044039086085, -0.000005851380981, 0.000000812575483, -0.000000116463617, 0.000000017091246, -0.000000002554376, 0.000000000387335, -0.000000000059428, 0.000000000009207, -0.000000000001438, 0.000000000000226, -0.000000000000036, 0.000000000000006, -0.000000000000001 }; /* Chebyshev expansion: j_{nu,3} = nu c_k T_k*((3/nu)^(2/3)), nu >= 3 */ static const double coef_jnu3_b[] = { 2.522816775173244, 1.673199424973720, 0.146431617506314, -0.004049001763912, -0.000039517767244, 0.000048781729288, -0.000008729705695, 0.000000928737310, -0.000000028388244, -0.000000012927432, 0.000000003441008, -0.000000000471695, 0.000000000025590, 0.000000000005502, -0.000000000001881, 0.000000000000295, -0.000000000000020, -0.000000000000003, 0.000000000000001 }; /* Chebyshev expansion: j_{nu,4} = c_k T_k*(nu/4), nu <= 4 */ static const double coef_jnu4_a[] = { 14.750310252773009, 2.908010932941708, -0.046093293420315, 0.004147172321412, -0.000459092310473, 0.000056646951906, -0.000007472351546, 0.000001031210065, -0.000000147008137, 0.000000021475218, -0.000000003197208, 0.000000000483249, -0.000000000073946, 0.000000000011431, -0.000000000001782, 0.000000000000280, -0.000000000000044, 0.000000000000007, -0.000000000000001 }; /* Chebyshev expansion: j_{nu,4} = nu c_k T_k*((4/nu)^(2/3)), nu >= 4 */ static const double coef_jnu4_b[] = { 2.551681323117914, 1.706177978336572, 0.150357658406131, -0.004234001378590, -0.000033854229898, 0.000050763551485, -0.000009337464057, 0.000001029717834, -0.000000037474196, -0.000000013450153, 0.000000003836180, -0.000000000557404, 0.000000000035748, 0.000000000005487, -0.000000000002187, 0.000000000000374, -0.000000000000031, -0.000000000000003, 0.000000000000001 }; /* Chebyshev expansion: j_{nu,5} = c_k T_k*(nu/5), nu <= 5 */ static const double coef_jnu5_a[] = { 18.632261081028211, 3.638249012596966, -0.057329705998828, 0.005121709126820, -0.000563325259487, 0.000069100826174, -0.000009066603030, 0.000001245181383, -0.000000176737282, 0.000000025716695, -0.000000003815184, 0.000000000574839, -0.000000000087715, 0.000000000013526, -0.000000000002104, 0.000000000000330, -0.000000000000052, 0.000000000000008, -0.000000000000001 }; /* Chebyshev expansion: j_{nu,5} = nu c_k T_k*((5/nu)^(2/3)), nu >= 5 */ /* FIXME: There is something wrong with this fit, in about the * 9th or 10th decimal place. */ static const double coef_jnu5_b[] = { 2.569079487591442, 1.726073360882134, 0.152740776809531, -0.004346449660148, -0.000030512461856, 0.000052000821080, -0.000009713343981, 0.000001091997863, -0.000000043061707, -0.000000013779413, 0.000000004082870, -0.000000000611259, 0.000000000042242, 0.000000000005448, -0.000000000002377, 0.000000000000424, -0.000000000000038, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,6} = c_k T_k*(nu/6), nu <= 6 */ static const double coef_jnu6_a[] = { 22.514836143374042, 4.368367257557198, -0.068550155285562, 0.006093776505822, -0.000667152784957, 0.000081486022398, -0.000010649011647, 0.000001457089679, -0.000000206105082, 0.000000029894724, -0.000000004422012, 0.000000000664471, -0.000000000101140, 0.000000000015561, -0.000000000002416, 0.000000000000378, -0.000000000000060, 0.000000000000009, -0.000000000000002 }; /* Chebyshev expansion: j_{nu,6} = nu c_k T_k*((6/nu)^(2/3)), nu >= 6 */ static const double coef_jnu6_b[] = { 2.580710285494837, 1.739380728566154, 0.154340696401691, -0.004422028860168, -0.000028305272624, 0.000052845975269, -0.000009968794373, 0.000001134252926, -0.000000046841241, -0.000000014007555, 0.000000004251816, -0.000000000648213, 0.000000000046728, 0.000000000005414, -0.000000000002508, 0.000000000000459, -0.000000000000043, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,7} = c_k T_k*(nu/7), nu <= 7 */ static const double coef_jnu7_a[] = { 26.397760539730869, 5.098418721711790, -0.079761896398948, 0.007064521280487, -0.000770766522482, 0.000093835449636, -0.000012225308542, 0.000001667939800, -0.000000235288157, 0.000000034040347, -0.000000005023142, 0.000000000753101, -0.000000000114389, 0.000000000017564, -0.000000000002722, 0.000000000000425, -0.000000000000067, 0.000000000000011, -0.000000000000002 }; /* Chebyshev expansion: j_{nu,7} = nu c_k T_k*((7/nu)^(2/3)), nu >= 7 */ static const double coef_jnu7_b[] = { 2.589033335856773, 1.748907007612678, 0.155488900387653, -0.004476317805688, -0.000026737952924, 0.000053459680946, -0.000010153699240, 0.000001164804272, -0.000000049566917, -0.000000014175403, 0.000000004374840, -0.000000000675135, 0.000000000050004, 0.000000000005387, -0.000000000002603, 0.000000000000485, -0.000000000000047, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,8} = c_k T_k*(nu/8), nu <= 8 */ static const double coef_jnu8_a[] = { 30.280900001606662, 5.828429205461221, -0.090968381181069, 0.008034479731033, -0.000874254899080, 0.000106164151611, -0.000013798098749, 0.000001878187386, -0.000000264366627, 0.000000038167685, -0.000000005621060, 0.000000000841165, -0.000000000127538, 0.000000000019550, -0.000000000003025, 0.000000000000472, -0.000000000000074, 0.000000000000012, -0.000000000000002 }; /* Chebyshev expansion: j_{nu,8} = nu c_k T_k*((8/nu)^(2/3)), nu >= 8 */ static const double coef_jnu8_b[] = { 2.595283877150078, 1.756063044986928, 0.156352972371030, -0.004517201896761, -0.000025567187878, 0.000053925472558, -0.000010293734486, 0.000001187923085, -0.000000051625122, -0.000000014304212, 0.000000004468450, -0.000000000695620, 0.000000000052500, 0.000000000005367, -0.000000000002676, 0.000000000000505, -0.000000000000050, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,9} = c_k T_k*(nu/9), nu <= 9 */ static const double coef_jnu9_a[] = { 34.164181213238386, 6.558412747925228, -0.102171455365016, 0.009003934361201, -0.000977663914535, 0.000118479876579, -0.000015368714220, 0.000002088064285, -0.000000293381154, 0.000000042283900, -0.000000006217033, 0.000000000928887, -0.000000000140627, 0.000000000021526, -0.000000000003326, 0.000000000000518, -0.000000000000081, 0.000000000000013, -0.000000000000002 }; /* Chebyshev expansion: j_{nu,9} = nu c_k T_k*((9/nu)^(2/3)), nu >= 9 */ static const double coef_jnu9_b[] = { 2.600150240905079, 1.761635491694032, 0.157026743724010, -0.004549100368716, -0.000024659248617, 0.000054291035068, -0.000010403464334, 0.000001206027524, -0.000000053234089, -0.000000014406241, 0.000000004542078, -0.000000000711728, 0.000000000054464, 0.000000000005350, -0.000000000002733, 0.000000000000521, -0.000000000000052, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,10} = c_k T_k*(nu/10), nu <= 10 */ static const double coef_jnu10_a[] = { 38.047560766184647, 7.288377637926008, -0.113372193277897, 0.009973047509098, -0.001081019701335, 0.000130786983847, -0.000016937898538, 0.000002297699179, -0.000000322354218, 0.000000046392941, -0.000000006811759, 0.000000001016395, -0.000000000153677, 0.000000000023486, -0.000000000003616, 0.000000000000561, -0.000000000000095, 0.000000000000027, -0.000000000000013, 0.000000000000005 }; /* Chebyshev expansion: j_{nu,10} = nu c_k T_k*((10/nu)^(2/3)), nu >= 10 */ static const double coef_jnu10_b[] = { 2.604046346867949, 1.766097596481182, 0.157566834446511, -0.004574682244089, -0.000023934500688, 0.000054585558231, -0.000010491765415, 0.000001220589364, -0.000000054526331, -0.000000014489078, 0.000000004601510, -0.000000000724727, 0.000000000056049, 0.000000000005337, -0.000000000002779, 0.000000000000533, -0.000000000000054, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,11} = c_k T_k*(nu/22), nu <= 22 */ static const double coef_jnu11_a[] = { 49.5054081076848637, 15.33692279367165101, -0.33677234163517130, 0.04623235772920729, -0.00781084960665093, 0.00147217395434708, -0.00029695043846867, 0.00006273356860235, -0.00001370575125628, 3.07171282012e-6, -7.0235041249e-7, 1.6320559339e-7, -3.843117306e-8, 9.15083800e-9, -2.19957642e-9, 5.3301703e-10, -1.3007541e-10, 3.193827e-11, -7.88605e-12, 1.95918e-12, -4.9020e-13, 1.2207e-13, -2.820e-14, 5.25e-15, -1.88e-15, 2.80e-15, -2.45e-15 }; /* Chebyshev expansion: j_{nu,12} = c_k T_k*(nu/24), nu <= 24 */ static const double coef_jnu12_a[] = { 54.0787833216641519, 16.7336367772863598, -0.36718411124537953, 0.05035523375053820, -0.00849884978867533, 0.00160027692813434, -0.00032248114889921, 0.00006806354127199, -0.00001485665901339, 3.32668783672e-6, -7.5998952729e-7, 1.7644939709e-7, -4.151538210e-8, 9.87722772e-9, -2.37230133e-9, 5.7442875e-10, -1.4007767e-10, 3.437166e-11, -8.48215e-12, 2.10554e-12, -5.2623e-13, 1.3189e-13, -3.175e-14, 5.73e-15, 5.6e-16, -8.7e-16, -6.5e-16 }; /* Chebyshev expansion: j_{nu,13} = c_k T_k*(nu/26), nu <= 26 */ static const double coef_jnu13_a[] = { 58.6521941921708890, 18.1303398137970284, -0.39759381380126650, 0.05447765240465494, -0.00918674227679980, 0.00172835361420579, -0.00034800528297612, 0.00007339183835188, -0.00001600713368099, 3.58154960392e-6, -8.1759873497e-7, 1.8968523220e-7, -4.459745253e-8, 1.060304419e-8, -2.54487624e-9, 6.1580214e-10, -1.5006751e-10, 3.679707e-11, -9.07159e-12, 2.24713e-12, -5.5943e-13, 1.4069e-13, -3.679e-14, 1.119e-14, -4.99e-15, 3.43e-15, -2.85e-15, 2.3e-15, -1.7e-15, 8.7e-16 }; /* Chebyshev expansion: j_{nu,14} = c_k T_k*(nu/28), nu <= 28 */ static const double coef_jnu14_a[] = { 63.2256329577315566, 19.5270342832914901, -0.42800190567884337, 0.05859971627729398, -0.00987455163523582, 0.00185641011402081, -0.00037352439419968, 0.00007871886257265, -0.00001715728110045, 3.83632624437e-6, -8.7518558668e-7, 2.0291515353e-7, -4.767795233e-8, 1.132844415e-8, -2.71734219e-9, 6.5714886e-10, -1.6005342e-10, 3.922557e-11, -9.66637e-12, 2.39379e-12, -5.9541e-13, 1.4868e-13, -3.726e-14, 9.37e-15, -2.36e-15, 6.0e-16 }; /* Chebyshev expansion: j_{nu,15} = c_k T_k*(nu/30), nu <= 30 */ static const double coef_jnu15_a[] = { 67.7990939565631635, 20.9237219226859859, -0.45840871823085836, 0.06272149946755639, -0.01056229551143042, 0.00198445078693100, -0.00039903958650729, 0.00008404489865469, -0.00001830717574922, 4.09103745566e-6, -9.3275533309e-7, 2.1614056403e-7, -5.075725222e-8, 1.205352081e-8, -2.88971837e-9, 6.9846848e-10, -1.7002946e-10, 4.164941e-11, -1.025859e-11, 2.53921e-12, -6.3128e-13, 1.5757e-13, -3.947e-14, 9.92e-15, -2.50e-15, 6.3e-16 }; /* Chebyshev expansion: j_{nu,16} = c_k T_k*(nu/32), nu <= 32 */ static const double coef_jnu16_a[] = { 72.3725729616724770, 22.32040402918608585, -0.48881449782358690, 0.06684305681828766, -0.01124998690363398, 0.00211247882775445, -0.00042455166484632, 0.00008937015316346, -0.00001945687139551, 4.34569739281e-6, -9.9031173548e-7, 2.2936247195e-7, -5.383562595e-8, 1.277835103e-8, -3.06202860e-9, 7.3977037e-10, -1.8000071e-10, 4.407196e-11, -1.085046e-11, 2.68453e-12, -6.6712e-13, 1.6644e-13, -4.168e-14, 1.047e-14, -2.64e-15, 6.7e-16 }; /* Chebyshev expansion: j_{nu,17} = c_k T_k*(nu/34), nu <= 34 */ static const double coef_jnu17_a[] = { 76.9460667535209549, 23.71708159112252670, -0.51921943142405352, 0.07096442978067622, -0.01193763559341369, 0.00224049662974902, -0.00045006122941781, 0.00009469477941684, -0.00002060640777107, 4.60031647195e-6, -1.04785755046e-6, 2.4258161247e-7, -5.691327087e-8, 1.350298805e-8, -3.23428733e-9, 7.8105847e-10, -1.8996825e-10, 4.649350e-11, -1.144205e-11, 2.82979e-12, -7.0294e-13, 1.7531e-13, -4.388e-14, 1.102e-14, -2.78e-15, 7.0e-16 }; /* Chebyshev expansion: j_{nu,18} = c_k T_k*(nu/36), nu <= 36 */ static const double coef_jnu18_a[] = { 81.5195728368096659, 25.11375537470259305, -0.54962366347317668, 0.07508565026117689, -0.01262524908033818, 0.00236850602019778, -0.00047556873651929, 0.00010001889347161, -0.00002175581482429, 4.85490251239e-6, -1.10539483940e-6, 2.5579853343e-7, -5.999033352e-8, 1.422747129e-8, -3.40650521e-9, 8.2233565e-10, -1.9993286e-10, 4.891426e-11, -1.203343e-11, 2.97498e-12, -7.3875e-13, 1.8418e-13, -4.608e-14, 1.157e-14, -2.91e-15, 7.4e-16 }; /* Chebyshev expansion: j_{nu,19} = c_k T_k*(nu/38), nu <= 38 */ static const double coef_jnu19_a[] = { 86.0930892477047512, 26.51042598308271729, -0.58002730731948358, 0.07920674321589394, -0.01331283320930301, 0.00249650841778073, -0.00050107453900793, 0.00010534258471335, -0.00002290511552874, 5.10946148897e-6, -1.16292517157e-6, 2.6901365037e-7, -6.306692473e-8, 1.495183048e-8, -3.57869025e-9, 8.6360410e-10, -2.0989514e-10, 5.133439e-11, -1.262465e-11, 3.12013e-12, -7.7455e-13, 1.9304e-13, -4.829e-14, 1.212e-14, -3.05e-15, 7.7e-16 }; /* Chebyshev expansion: j_{nu,20} = c_k T_k*(nu/40), nu <= 40 */ static const double coef_jnu20_a[] = { 90.6666144195163770, 27.9070938975436823, -0.61043045315390591, 0.08332772844325554, -0.01400039260208282, 0.00262450494035660, -0.00052657891389470, 0.00011066592304919, -0.00002405432778364, 5.36399803946e-6, -1.22044976064e-6, 2.8222728362e-7, -6.614312964e-8, 1.567608839e-8, -3.75084856e-9, 9.0486546e-10, -2.1985553e-10, 5.375401e-11, -1.321572e-11, 3.26524e-12, -8.1033e-13, 2.0190e-13, -5.049e-14, 1.267e-14, -3.19e-15, 8.0e-16, -2.0e-16 }; static const double * coef_jnu_a[] = { 0, coef_jnu1_a, coef_jnu2_a, coef_jnu3_a, coef_jnu4_a, coef_jnu5_a, coef_jnu6_a, coef_jnu7_a, coef_jnu8_a, coef_jnu9_a, coef_jnu10_a, coef_jnu11_a, coef_jnu12_a, coef_jnu13_a, coef_jnu14_a, coef_jnu15_a, coef_jnu16_a, coef_jnu17_a, coef_jnu18_a, coef_jnu19_a, coef_jnu20_a }; static const size_t size_jnu_a[] = { 0, sizeof(coef_jnu1_a)/sizeof(double), sizeof(coef_jnu2_a)/sizeof(double), sizeof(coef_jnu3_a)/sizeof(double), sizeof(coef_jnu4_a)/sizeof(double), sizeof(coef_jnu5_a)/sizeof(double), sizeof(coef_jnu6_a)/sizeof(double), sizeof(coef_jnu7_a)/sizeof(double), sizeof(coef_jnu8_a)/sizeof(double), sizeof(coef_jnu9_a)/sizeof(double), sizeof(coef_jnu10_a)/sizeof(double), sizeof(coef_jnu11_a)/sizeof(double), sizeof(coef_jnu12_a)/sizeof(double), sizeof(coef_jnu13_a)/sizeof(double), sizeof(coef_jnu14_a)/sizeof(double), sizeof(coef_jnu15_a)/sizeof(double), sizeof(coef_jnu16_a)/sizeof(double), sizeof(coef_jnu17_a)/sizeof(double), sizeof(coef_jnu18_a)/sizeof(double), sizeof(coef_jnu19_a)/sizeof(double), sizeof(coef_jnu20_a)/sizeof(double) }; static const double * coef_jnu_b[] = { 0, coef_jnu1_b, coef_jnu2_b, coef_jnu3_b, coef_jnu4_b, coef_jnu5_b, coef_jnu6_b, coef_jnu7_b, coef_jnu8_b, coef_jnu9_b, coef_jnu10_b }; static const size_t size_jnu_b[] = { 0, sizeof(coef_jnu1_b)/sizeof(double), sizeof(coef_jnu2_b)/sizeof(double), sizeof(coef_jnu3_b)/sizeof(double), sizeof(coef_jnu4_b)/sizeof(double), sizeof(coef_jnu5_b)/sizeof(double), sizeof(coef_jnu6_b)/sizeof(double), sizeof(coef_jnu7_b)/sizeof(double), sizeof(coef_jnu8_b)/sizeof(double), sizeof(coef_jnu9_b)/sizeof(double), sizeof(coef_jnu10_b)/sizeof(double) }; /* Evaluate Clenshaw recurrence for * a T* Chebyshev series. * sizeof(c) = N+1 */ static double clenshaw(const double * c, int N, double u) { double B_np1 = 0.0; double B_n = c[N]; double B_nm1; int n; for(n=N; n>0; n--) { B_nm1 = 2.0*(2.0*u-1.0) * B_n - B_np1 + c[n-1]; B_np1 = B_n; B_n = B_nm1; } return B_n - (2.0*u-1.0)*B_np1; } /* correction terms to leading McMahon expansion * [Abramowitz+Stegun 9.5.12] * [Olver, Royal Society Math. Tables, v. 7] * We factor out a beta, so that this is a multiplicative * correction: * j_{nu,s} = beta(s,nu) * mcmahon_correction(nu, beta(s,nu)) * macmahon_correction --> 1 as s --> Inf */ static double mcmahon_correction(const double mu, const double beta) { const double eb = 8.0*beta; const double ebsq = eb*eb; if(mu < GSL_DBL_EPSILON) { /* Prevent division by zero below. */ const double term1 = 1.0/ebsq; const double term2 = -4.0*31.0/(3*ebsq*ebsq); const double term3 = 32.0*3779.0/(15.0*ebsq*ebsq*ebsq); const double term4 = -64.0*6277237.0/(105.0*ebsq*ebsq*ebsq*ebsq); const double term5 = 512.0*2092163573.0/(315.0*ebsq*ebsq*ebsq*ebsq*ebsq); return 1.0 + 8.0*(term1 + term2 + term3 + term4 + term5); } else { /* Here we do things in terms of 1/mu, which * is purely to prevent overflow in the very * unlikely case that mu is really big. */ const double mi = 1.0/mu; const double r = mu/ebsq; const double n2 = 4.0/3.0 * (7.0 - 31.0*mi); const double n3 = 32.0/15.0 * (83.0 + (-982.0 + 3779.0*mi)*mi); const double n4 = 64.0/105.0 * (6949.0 + (-153855.0 + (1585743.0 - 6277237.0*mi)*mi)*mi); const double n5 = 512.0/315.0 * (70197.0 + (-2479316.0 + (48010494.0 + (-512062548.0 + 2092163573.0*mi)*mi)*mi)*mi); const double n6 = 2048.0/3465.0 * (5592657.0 + (-287149133.0 + (8903961290.0 + (-179289628602.0 + (1982611456181.0 - 8249725736393.0*mi)*mi)*mi)*mi)*mi); const double term1 = (1.0 - mi) * r; const double term2 = term1 * n2 * r; const double term3 = term1 * n3 * r*r; const double term4 = term1 * n4 * r*r*r; const double term5 = term1 * n5 * r*r*r*r; const double term6 = term1 * n6 * r*r*r*r*r; return 1.0 - 8.0*(term1 + term2 + term3 + term4 + term5 + term6); } } /* Assumes z >= 1.0 */ static double olver_b0(double z, double minus_zeta) { if(z < 1.02) { const double a = 1.0-z; const double c0 = 0.0179988721413553309252458658183; const double c1 = 0.0111992982212877614645974276203; const double c2 = 0.0059404069786014304317781160605; const double c3 = 0.0028676724516390040844556450173; const double c4 = 0.0012339189052567271708525111185; const double c5 = 0.0004169250674535178764734660248; const double c6 = 0.0000330173385085949806952777365; const double c7 = -0.0001318076238578203009990106425; const double c8 = -0.0001906870370050847239813945647; return c0 + a*(c1 + a*(c2 + a*(c3 + a*(c4 + a*(c5 + a*(c6 + a*(c7 + a*c8))))))); } else { const double abs_zeta = minus_zeta; const double t = 1.0/(z*sqrt(1.0 - 1.0/(z*z))); return -5.0/(48.0*abs_zeta*abs_zeta) + t*(3.0 + 5.0*t*t)/(24.0*sqrt(abs_zeta)); } } inline static double olver_f1(double z, double minus_zeta) { const double b0 = olver_b0(z, minus_zeta); const double h2 = sqrt(4.0*minus_zeta/(z*z-1.0)); /* FIXME */ return 0.5 * z * h2 * b0; } int gsl_sf_bessel_zero_J0_e(unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s == 0){ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EINVAL); } else { /* See [F. Lether, J. Comp. Appl .Math. 67, 167 (1996)]. */ static const double P[] = { 1567450796.0/12539606369.0, 8903660.0/2365861.0, 10747040.0/536751.0, 17590991.0/1696654.0 }; static const double Q[] = { 1.0, 29354255.0/954518.0, 76900001.0/431847.0, 67237052.0/442411.0 }; const double beta = (s - 0.25) * M_PI; const double bi2 = 1.0/(beta*beta); const double R33num = P[0] + bi2 * (P[1] + bi2 * (P[2] + P[3] * bi2)); const double R33den = Q[0] + bi2 * (Q[1] + bi2 * (Q[2] + Q[3] * bi2)); const double R33 = R33num/R33den; result->val = beta + R33/beta; result->err = fabs(3.0e-15 * result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_zero_J1_e(unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s == 0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* See [M. Branders et al., J. Comp. Phys. 42, 403 (1981)]. */ static const double a[] = { -0.362804405737084, 0.120341279038597, 0.439454547101171e-01, 0.159340088474713e-02 }; static const double b[] = { 1.0, -0.325641790801361, -0.117453445968927, -0.424906902601794e-02 }; const double beta = (s + 0.25) * M_PI; const double bi2 = 1.0/(beta*beta); const double Rnum = a[3] + bi2 * (a[2] + bi2 * (a[1] + bi2 * a[0])); const double Rden = b[3] + bi2 * (b[2] + bi2 * (b[1] + bi2 * b[0])); const double R = Rnum/Rden; result->val = beta * (1.0 + R*bi2); result->err = fabs(2.0e-14 * result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_zero_Jnu_e(double nu, unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(nu <= -1.0) { DOMAIN_ERROR(result); } else if(s == 0) { result->val = 0.0; result->err = 0.0; if (nu == 0.0) { GSL_ERROR ("no zero-th root for nu = 0.0", GSL_EINVAL); } return GSL_SUCCESS; } else if(nu < 0.0) { /* This can be done, I'm just lazy now. */ result->val = 0.0; result->err = 0.0; GSL_ERROR("unimplemented", GSL_EUNIMPL); } else if(s == 1) { /* Chebyshev fits for the first positive zero. * For some reason Nemeth made this different from the others. */ if(nu < 2.0) { const double * c = coef_jnu_a[s]; const size_t L = size_jnu_a[s]; const double arg = nu/2.0; const double chb = clenshaw(c, L-1, arg); result->val = chb; result->err = 2.0e-15 * result->val; } else { const double * c = coef_jnu_b[s]; const size_t L = size_jnu_b[s]; const double arg = pow(2.0/nu, 2.0/3.0); const double chb = clenshaw(c, L-1, arg); result->val = nu * chb; result->err = 2.0e-15 * result->val; } return GSL_SUCCESS; } else if(s <= 10) { /* Chebyshev fits for the first 10 positive zeros. */ if(nu < s) { const double * c = coef_jnu_a[s]; const size_t L = size_jnu_a[s]; const double arg = nu/s; const double chb = clenshaw(c, L-1, arg); result->val = chb; result->err = 2.0e-15 * result->val; } else { const double * c = coef_jnu_b[s]; const size_t L = size_jnu_b[s]; const double arg = pow(s/nu, 2.0/3.0); const double chb = clenshaw(c, L-1, arg); result->val = nu * chb; result->err = 2.0e-15 * result->val; /* FIXME: truth in advertising for the screwed up * s = 5 fit. Need to fix that. */ if(s == 5) { result->err *= 5.0e+06; } } return GSL_SUCCESS; } else if(s > 0.5*nu && s <= 20) { /* Chebyshev fits for 10 < s <= 20. */ const double * c = coef_jnu_a[s]; const size_t L = size_jnu_a[s]; const double arg = nu/(2.0*s); const double chb = clenshaw(c, L-1, arg); result->val = chb; result->err = 4.0e-15 * chb; return GSL_SUCCESS; } else if(s > 2.0 * nu) { /* McMahon expansion if s is large compared to nu. */ const double beta = (s + 0.5*nu - 0.25) * M_PI; const double mc = mcmahon_correction(4.0*nu*nu, beta); gsl_sf_result rat12; gsl_sf_pow_int_e(nu/beta, 14, &rat12); result->val = beta * mc; result->err = 4.0 * fabs(beta) * rat12.val; result->err += 4.0 * fabs(GSL_DBL_EPSILON * result->val); return GSL_SUCCESS; } else { /* Olver uniform asymptotic. */ gsl_sf_result as; const int stat_as = gsl_sf_airy_zero_Ai_e(s, &as); const double minus_zeta = -pow(nu,-2.0/3.0) * as.val; const double z = gsl_sf_bessel_Olver_zofmzeta(minus_zeta); const double f1 = olver_f1(z, minus_zeta); result->val = nu * (z + f1/(nu*nu)); result->err = 0.001/(nu*nu*nu); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_as; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_zero_J0(unsigned int s) { EVAL_RESULT(gsl_sf_bessel_zero_J0_e(s, &result)); } double gsl_sf_bessel_zero_J1(unsigned int s) { EVAL_RESULT(gsl_sf_bessel_zero_J1_e(s, &result)); } double gsl_sf_bessel_zero_Jnu(double nu, unsigned int s) { EVAL_RESULT(gsl_sf_bessel_zero_Jnu_e(nu, s, &result)); } sources_5316/external/gsl/gsl_histogram__init2d.c0000664000176700017670000001517711723710247020771 0ustar paulpaul/* histogram/init2d.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_histogram2d.h" gsl_histogram2d * gsl_histogram2d_alloc (const size_t nx, const size_t ny) { gsl_histogram2d *h; if (nx == 0) { GSL_ERROR_VAL ("histogram2d length nx must be positive integer", GSL_EDOM, 0); } if (ny == 0) { GSL_ERROR_VAL ("histogram2d length ny must be positive integer", GSL_EDOM, 0); } h = (gsl_histogram2d *) malloc (sizeof (gsl_histogram2d)); if (h == 0) { GSL_ERROR_VAL ("failed to allocate space for histogram2d struct", GSL_ENOMEM, 0); } h->xrange = (double *) malloc ((nx + 1) * sizeof (double)); if (h->xrange == 0) { free (h); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram2d x ranges", GSL_ENOMEM, 0); } h->yrange = (double *) malloc ((ny + 1) * sizeof (double)); if (h->yrange == 0) { free (h->xrange); free (h); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram2d y ranges", GSL_ENOMEM, 0); } h->bin = (double *) malloc (nx * ny * sizeof (double)); if (h->bin == 0) { free (h->xrange); free (h->yrange); free (h); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram bins", GSL_ENOMEM, 0); } h->nx = nx; h->ny = ny; return h; } static void make_uniform (double range[], size_t n, double xmin, double xmax) { size_t i; for (i = 0; i <= n; i++) { double f1 = ((double) (n-i) / (double) n); double f2 = ((double) i / (double) n); range[i] = f1 * xmin + f2 * xmax; } } gsl_histogram2d * gsl_histogram2d_calloc_uniform (const size_t nx, const size_t ny, const double xmin, const double xmax, const double ymin, const double ymax) { gsl_histogram2d *h; if (xmin >= xmax) { GSL_ERROR_VAL ("xmin must be less than xmax", GSL_EINVAL, 0); } if (ymin >= ymax) { GSL_ERROR_VAL ("ymin must be less than ymax", GSL_EINVAL, 0); } h = gsl_histogram2d_calloc (nx, ny); if (h == 0) { return h; } make_uniform (h->xrange, nx, xmin, xmax); make_uniform (h->yrange, ny, ymin, ymax); return h; } gsl_histogram2d * gsl_histogram2d_calloc (const size_t nx, const size_t ny) { gsl_histogram2d *h; if (nx == 0) { GSL_ERROR_VAL ("histogram2d length nx must be positive integer", GSL_EDOM, 0); } if (ny == 0) { GSL_ERROR_VAL ("histogram2d length ny must be positive integer", GSL_EDOM, 0); } h = (gsl_histogram2d *) malloc (sizeof (gsl_histogram2d)); if (h == 0) { GSL_ERROR_VAL ("failed to allocate space for histogram2d struct", GSL_ENOMEM, 0); } h->xrange = (double *) malloc ((nx + 1) * sizeof (double)); if (h->xrange == 0) { free (h); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram2d x ranges", GSL_ENOMEM, 0); } h->yrange = (double *) malloc ((ny + 1) * sizeof (double)); if (h->yrange == 0) { free (h->xrange); free (h); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram2d y ranges", GSL_ENOMEM, 0); } h->bin = (double *) malloc (nx * ny * sizeof (double)); if (h->bin == 0) { free (h->xrange); free (h->yrange); free (h); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram bins", GSL_ENOMEM, 0); } { size_t i; for (i = 0; i < nx + 1; i++) { h->xrange[i] = i; } for (i = 0; i < ny + 1; i++) { h->yrange[i] = i; } for (i = 0; i < nx * ny; i++) { h->bin[i] = 0; } } h->nx = nx; h->ny = ny; return h; } void gsl_histogram2d_free (gsl_histogram2d * h) { free (h->xrange); free (h->yrange); free (h->bin); free (h); } int gsl_histogram2d_set_ranges_uniform (gsl_histogram2d * h, double xmin, double xmax, double ymin, double ymax) { size_t i; const size_t nx = h->nx, ny = h->ny; if (xmin >= xmax) { GSL_ERROR_VAL ("xmin must be less than xmax", GSL_EINVAL, 0); } if (ymin >= ymax) { GSL_ERROR_VAL ("ymin must be less than ymax", GSL_EINVAL, 0); } /* initialize ranges */ make_uniform (h->xrange, nx, xmin, xmax); make_uniform (h->yrange, ny, ymin, ymax); /* clear contents */ for (i = 0; i < nx * ny; i++) { h->bin[i] = 0; } return GSL_SUCCESS; } int gsl_histogram2d_set_ranges (gsl_histogram2d * h, const double xrange[], size_t xsize, const double yrange[], size_t ysize) { size_t i; const size_t nx = h->nx, ny = h->ny; if (xsize != (nx + 1)) { GSL_ERROR_VAL ("size of xrange must match size of histogram", GSL_EINVAL, 0); } if (ysize != (ny + 1)) { GSL_ERROR_VAL ("size of yrange must match size of histogram", GSL_EINVAL, 0); } /* initialize ranges */ for (i = 0; i <= nx; i++) { h->xrange[i] = xrange[i]; } for (i = 0; i <= ny; i++) { h->yrange[i] = yrange[i]; } /* clear contents */ for (i = 0; i < nx * ny; i++) { h->bin[i] = 0; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_rng__knuthran2.c0000664000176700017670000000500411723710247020271 0ustar paulpaul/* rng/knuthran2.c * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth * The Art of Computer Programming * Volume 2 * Third Edition * Addison-Wesley * Page 108 * * This implementation copyright (C) 2001 Carlo Perassi * and (C) 2003 Heiko Bauke. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_rng__schrage.c" #define AA1 271828183UL #define AA2 1833324378UL /* = -314159269 mod (2 ^ 31 -1) */ #define MM 0x7fffffffUL /* 2 ^ 31 - 1 */ #define CEIL_SQRT_MM 46341UL /* sqrt(2 ^ 31 - 1) */ static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); typedef struct { unsigned long int x0; unsigned long int x1; } ran_state_t; static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; const unsigned long int xtmp = state->x1; state->x1 = schrage_mult (AA1, state->x1, MM, CEIL_SQRT_MM) + schrage_mult (AA2, state->x0, MM, CEIL_SQRT_MM); if (state->x1 >= MM) state->x1 -= MM; state->x0 = xtmp; return state->x1; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 2147483647.0; } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; if ((s % MM) == 0) s = 1; /* default seed is 1 */ state->x0 = s % MM; state->x1 = s % MM; return; } static const gsl_rng_type ran_type = { "knuthran2", /* name */ MM - 1L, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_knuthran2 = &ran_type; sources_5316/external/gsl/gsl_rng__minstd.c0000664000176700017670000000547011723710247017662 0ustar paulpaul/* rng/minstd.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* MINSTD is Park and Miller's minimal standard generator (i.e. it's not particularly good). The sequence is x_{n+1} = (a x_n) mod m with a = 16807 and m = 2^31 - 1 = 2147483647. The seed specifies the initial value, x_1. The theoretical value of x_{10001} is 1043618065, starting with a seed of x_1 = 1. The period of this generator is 2^31. It is used as the RNUN subroutine in the IMSL Library and the RAND function in MATLAB. The generator is sometimes known by the acronym "GGL" (I'm not sure what that stands for). From: Park and Miller, "Random Number Generators: Good ones are hard to find" Communications of the ACM, October 1988, Volume 31, No 10, pages 1192-1201. */ static inline unsigned long int minstd_get (void *vstate); static double minstd_get_double (void *vstate); static void minstd_set (void *state, unsigned long int s); static const long int m = 2147483647, a = 16807, q = 127773, r = 2836; typedef struct { unsigned long int x; } minstd_state_t; static inline unsigned long int minstd_get (void *vstate) { minstd_state_t *state = (minstd_state_t *) vstate; const unsigned long int x = state->x; const long int h = x / q; const long int t = a * (x - h * q) - h * r; if (t < 0) { state->x = t + m; } else { state->x = t; } return state->x; } static double minstd_get_double (void *vstate) { return minstd_get (vstate) / 2147483647.0; } static void minstd_set (void *vstate, unsigned long int s) { minstd_state_t *state = (minstd_state_t *) vstate; if (s == 0) s = 1; /* default seed is 1 */ state->x = s; return; } static const gsl_rng_type minstd_type = {"minstd", /* name */ 2147483646, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (minstd_state_t), &minstd_set, &minstd_get, &minstd_get_double}; const gsl_rng_type *gsl_rng_minstd = &minstd_type; sources_5316/external/gsl/gsl_fft__c_pass_6.c0000664000176700017670000002023111723710247020042 0ustar paulpaul/* fft/c_pass_6.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int FUNCTION(fft_complex,pass_6) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[], const TYPE(gsl_complex) twiddle5[]) { size_t i = 0, j = 0; size_t k, k1; const size_t factor = 6; const size_t m = n / factor; const size_t q = n / product; const size_t p_1 = product / factor; const size_t jump = (factor - 1) * p_1; const ATOMIC tau = sqrt (3.0) / 2.0; for (k = 0; k < q; k++) { ATOMIC w1_real, w1_imag, w2_real, w2_imag, w3_real, w3_imag, w4_real, w4_imag, w5_real, w5_imag; if (k == 0) { w1_real = 1.0; w1_imag = 0.0; w2_real = 1.0; w2_imag = 0.0; w3_real = 1.0; w3_imag = 0.0; w4_real = 1.0; w4_imag = 0.0; w5_real = 1.0; w5_imag = 0.0; } else { if (sign == gsl_fft_forward) { /* forward tranform */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = GSL_IMAG(twiddle2[k - 1]); w3_real = GSL_REAL(twiddle3[k - 1]); w3_imag = GSL_IMAG(twiddle3[k - 1]); w4_real = GSL_REAL(twiddle4[k - 1]); w4_imag = GSL_IMAG(twiddle4[k - 1]); w5_real = GSL_REAL(twiddle5[k - 1]); w5_imag = GSL_IMAG(twiddle5[k - 1]); } else { /* backward tranform: w -> conjugate(w) */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = -GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = -GSL_IMAG(twiddle2[k - 1]); w3_real = GSL_REAL(twiddle3[k - 1]); w3_imag = -GSL_IMAG(twiddle3[k - 1]); w4_real = GSL_REAL(twiddle4[k - 1]); w4_imag = -GSL_IMAG(twiddle4[k - 1]); w5_real = GSL_REAL(twiddle5[k - 1]); w5_imag = -GSL_IMAG(twiddle5[k - 1]); } } for (k1 = 0; k1 < p_1; k1++) { const ATOMIC z0_real = REAL(in,istride,i); const ATOMIC z0_imag = IMAG(in,istride,i); const ATOMIC z1_real = REAL(in,istride,i+m); const ATOMIC z1_imag = IMAG(in,istride,i+m); const ATOMIC z2_real = REAL(in,istride,i+2*m); const ATOMIC z2_imag = IMAG(in,istride,i+2*m); const ATOMIC z3_real = REAL(in,istride,i+3*m); const ATOMIC z3_imag = IMAG(in,istride,i+3*m); const ATOMIC z4_real = REAL(in,istride,i+4*m); const ATOMIC z4_imag = IMAG(in,istride,i+4*m); const ATOMIC z5_real = REAL(in,istride,i+5*m); const ATOMIC z5_imag = IMAG(in,istride,i+5*m); /* compute x = W(6) z */ /* W(6) is a combination of sums and differences of W(3) acting on the even and odd elements of z */ /* ta1 = z2 + z4 */ const ATOMIC ta1_real = z2_real + z4_real; const ATOMIC ta1_imag = z2_imag + z4_imag; /* ta2 = z0 - ta1/2 */ const ATOMIC ta2_real = z0_real - ta1_real / 2; const ATOMIC ta2_imag = z0_imag - ta1_imag / 2; /* ta3 = (+/-) sin(pi/3)*(z2 - z4) */ const ATOMIC ta3_real = ((int) sign) * tau * (z2_real - z4_real); const ATOMIC ta3_imag = ((int) sign) * tau * (z2_imag - z4_imag); /* a0 = z0 + ta1 */ const ATOMIC a0_real = z0_real + ta1_real; const ATOMIC a0_imag = z0_imag + ta1_imag; /* a1 = ta2 + i ta3 */ const ATOMIC a1_real = ta2_real - ta3_imag; const ATOMIC a1_imag = ta2_imag + ta3_real; /* a2 = ta2 - i ta3 */ const ATOMIC a2_real = ta2_real + ta3_imag; const ATOMIC a2_imag = ta2_imag - ta3_real; /* tb1 = z5 + z1 */ const ATOMIC tb1_real = z5_real + z1_real; const ATOMIC tb1_imag = z5_imag + z1_imag; /* tb2 = z3 - tb1/2 */ const ATOMIC tb2_real = z3_real - tb1_real / 2; const ATOMIC tb2_imag = z3_imag - tb1_imag / 2; /* tb3 = (+/-) sin(pi/3)*(z5 - z1) */ const ATOMIC tb3_real = ((int) sign) * tau * (z5_real - z1_real); const ATOMIC tb3_imag = ((int) sign) * tau * (z5_imag - z1_imag); /* b0 = z3 + tb1 */ const ATOMIC b0_real = z3_real + tb1_real; const ATOMIC b0_imag = z3_imag + tb1_imag; /* b1 = tb2 + i tb3 */ const ATOMIC b1_real = tb2_real - tb3_imag; const ATOMIC b1_imag = tb2_imag + tb3_real; /* b2 = tb2 - i tb3 */ const ATOMIC b2_real = tb2_real + tb3_imag; const ATOMIC b2_imag = tb2_imag - tb3_real; /* x0 = a0 + b0 */ const ATOMIC x0_real = a0_real + b0_real; const ATOMIC x0_imag = a0_imag + b0_imag; /* x4 = a1 + b1 */ const ATOMIC x4_real = a1_real + b1_real; const ATOMIC x4_imag = a1_imag + b1_imag; /* x2 = a2 + b2 */ const ATOMIC x2_real = a2_real + b2_real; const ATOMIC x2_imag = a2_imag + b2_imag; /* x3 = a0 - b0 */ const ATOMIC x3_real = a0_real - b0_real; const ATOMIC x3_imag = a0_imag - b0_imag; /* x1 = a1 - b1 */ const ATOMIC x1_real = a1_real - b1_real; const ATOMIC x1_imag = a1_imag - b1_imag; /* x5 = a2 - b2 */ const ATOMIC x5_real = a2_real - b2_real; const ATOMIC x5_imag = a2_imag - b2_imag; /* apply twiddle factors */ /* to0 = 1 * x0 */ REAL(out,ostride,j) = x0_real; IMAG(out,ostride,j) = x0_imag; /* to1 = w1 * x1 */ REAL(out,ostride,j+p_1) = w1_real * x1_real - w1_imag * x1_imag; IMAG(out,ostride,j+p_1) = w1_real * x1_imag + w1_imag * x1_real; /* to2 = w2 * x2 */ REAL(out,ostride,j+2*p_1) = w2_real * x2_real - w2_imag * x2_imag; IMAG(out,ostride,j+2*p_1) = w2_real * x2_imag + w2_imag * x2_real; /* to3 = w3 * x3 */ REAL(out,ostride,j+3*p_1) = w3_real * x3_real - w3_imag * x3_imag; IMAG(out,ostride,j+3*p_1) = w3_real * x3_imag + w3_imag * x3_real; /* to4 = w4 * x4 */ REAL(out,ostride,j+4*p_1) = w4_real * x4_real - w4_imag * x4_imag; IMAG(out,ostride,j+4*p_1) = w4_real * x4_imag + w4_imag * x4_real; /* to5 = w5 * x5 */ REAL(out,ostride,j+5*p_1) = w5_real * x5_real - w5_imag * x5_imag; IMAG(out,ostride,j+5*p_1) = w5_real * x5_imag + w5_imag * x5_real; i++; j++; } j += jump; } return 0; } sources_5316/external/gsl/gsl_vector_ulong.h0000664000176700017670000001634211705263724020075 0ustar paulpaul/* vector/gsl_vector_ulong.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_ULONG_H__ #define __GSL_VECTOR_ULONG_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_ulong.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; unsigned long *data; gsl_block_ulong *block; int owner; } gsl_vector_ulong; typedef struct { gsl_vector_ulong vector; } _gsl_vector_ulong_view; typedef _gsl_vector_ulong_view gsl_vector_ulong_view; typedef struct { gsl_vector_ulong vector; } _gsl_vector_ulong_const_view; typedef const _gsl_vector_ulong_const_view gsl_vector_ulong_const_view; /* Allocation */ gsl_vector_ulong *gsl_vector_ulong_alloc (const size_t n); gsl_vector_ulong *gsl_vector_ulong_calloc (const size_t n); gsl_vector_ulong *gsl_vector_ulong_alloc_from_block (gsl_block_ulong * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_ulong *gsl_vector_ulong_alloc_from_vector (gsl_vector_ulong * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_ulong_free (gsl_vector_ulong * v); /* Views */ _gsl_vector_ulong_view gsl_vector_ulong_view_array (unsigned long *v, size_t n); _gsl_vector_ulong_view gsl_vector_ulong_view_array_with_stride (unsigned long *base, size_t stride, size_t n); _gsl_vector_ulong_const_view gsl_vector_ulong_const_view_array (const unsigned long *v, size_t n); _gsl_vector_ulong_const_view gsl_vector_ulong_const_view_array_with_stride (const unsigned long *base, size_t stride, size_t n); _gsl_vector_ulong_view gsl_vector_ulong_subvector (gsl_vector_ulong *v, size_t i, size_t n); _gsl_vector_ulong_view gsl_vector_ulong_subvector_with_stride (gsl_vector_ulong *v, size_t i, size_t stride, size_t n); _gsl_vector_ulong_const_view gsl_vector_ulong_const_subvector (const gsl_vector_ulong *v, size_t i, size_t n); _gsl_vector_ulong_const_view gsl_vector_ulong_const_subvector_with_stride (const gsl_vector_ulong *v, size_t i, size_t stride, size_t n); /* Operations */ unsigned long gsl_vector_ulong_get (const gsl_vector_ulong * v, const size_t i); void gsl_vector_ulong_set (gsl_vector_ulong * v, const size_t i, unsigned long x); unsigned long *gsl_vector_ulong_ptr (gsl_vector_ulong * v, const size_t i); const unsigned long *gsl_vector_ulong_const_ptr (const gsl_vector_ulong * v, const size_t i); void gsl_vector_ulong_set_zero (gsl_vector_ulong * v); void gsl_vector_ulong_set_all (gsl_vector_ulong * v, unsigned long x); int gsl_vector_ulong_set_basis (gsl_vector_ulong * v, size_t i); int gsl_vector_ulong_fread (FILE * stream, gsl_vector_ulong * v); int gsl_vector_ulong_fwrite (FILE * stream, const gsl_vector_ulong * v); int gsl_vector_ulong_fscanf (FILE * stream, gsl_vector_ulong * v); int gsl_vector_ulong_fprintf (FILE * stream, const gsl_vector_ulong * v, const char *format); int gsl_vector_ulong_memcpy (gsl_vector_ulong * dest, const gsl_vector_ulong * src); int gsl_vector_ulong_reverse (gsl_vector_ulong * v); int gsl_vector_ulong_swap (gsl_vector_ulong * v, gsl_vector_ulong * w); int gsl_vector_ulong_swap_elements (gsl_vector_ulong * v, const size_t i, const size_t j); unsigned long gsl_vector_ulong_max (const gsl_vector_ulong * v); unsigned long gsl_vector_ulong_min (const gsl_vector_ulong * v); void gsl_vector_ulong_minmax (const gsl_vector_ulong * v, unsigned long * min_out, unsigned long * max_out); size_t gsl_vector_ulong_max_index (const gsl_vector_ulong * v); size_t gsl_vector_ulong_min_index (const gsl_vector_ulong * v); void gsl_vector_ulong_minmax_index (const gsl_vector_ulong * v, size_t * imin, size_t * imax); int gsl_vector_ulong_add (gsl_vector_ulong * a, const gsl_vector_ulong * b); int gsl_vector_ulong_sub (gsl_vector_ulong * a, const gsl_vector_ulong * b); int gsl_vector_ulong_mul (gsl_vector_ulong * a, const gsl_vector_ulong * b); int gsl_vector_ulong_div (gsl_vector_ulong * a, const gsl_vector_ulong * b); int gsl_vector_ulong_scale (gsl_vector_ulong * a, const double x); int gsl_vector_ulong_add_constant (gsl_vector_ulong * a, const double x); int gsl_vector_ulong_isnull (const gsl_vector_ulong * v); int gsl_vector_ulong_ispos (const gsl_vector_ulong * v); int gsl_vector_ulong_isneg (const gsl_vector_ulong * v); int gsl_vector_ulong_isnonneg (const gsl_vector_ulong * v); #ifdef HAVE_INLINE extern inline unsigned long gsl_vector_ulong_get (const gsl_vector_ulong * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_ulong_set (gsl_vector_ulong * v, const size_t i, unsigned long x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline unsigned long * gsl_vector_ulong_ptr (gsl_vector_ulong * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (unsigned long *) (v->data + i * v->stride); } extern inline const unsigned long * gsl_vector_ulong_const_ptr (const gsl_vector_ulong * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const unsigned long *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_ULONG_H__ */ sources_5316/external/gsl/gsl_vector_int.h0000664000176700017670000001544411705263724017545 0ustar paulpaul/* vector/gsl_vector_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_INT_H__ #define __GSL_VECTOR_INT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_int.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; int *data; gsl_block_int *block; int owner; } gsl_vector_int; typedef struct { gsl_vector_int vector; } _gsl_vector_int_view; typedef _gsl_vector_int_view gsl_vector_int_view; typedef struct { gsl_vector_int vector; } _gsl_vector_int_const_view; typedef const _gsl_vector_int_const_view gsl_vector_int_const_view; /* Allocation */ gsl_vector_int *gsl_vector_int_alloc (const size_t n); gsl_vector_int *gsl_vector_int_calloc (const size_t n); gsl_vector_int *gsl_vector_int_alloc_from_block (gsl_block_int * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_int *gsl_vector_int_alloc_from_vector (gsl_vector_int * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_int_free (gsl_vector_int * v); /* Views */ _gsl_vector_int_view gsl_vector_int_view_array (int *v, size_t n); _gsl_vector_int_view gsl_vector_int_view_array_with_stride (int *base, size_t stride, size_t n); _gsl_vector_int_const_view gsl_vector_int_const_view_array (const int *v, size_t n); _gsl_vector_int_const_view gsl_vector_int_const_view_array_with_stride (const int *base, size_t stride, size_t n); _gsl_vector_int_view gsl_vector_int_subvector (gsl_vector_int *v, size_t i, size_t n); _gsl_vector_int_view gsl_vector_int_subvector_with_stride (gsl_vector_int *v, size_t i, size_t stride, size_t n); _gsl_vector_int_const_view gsl_vector_int_const_subvector (const gsl_vector_int *v, size_t i, size_t n); _gsl_vector_int_const_view gsl_vector_int_const_subvector_with_stride (const gsl_vector_int *v, size_t i, size_t stride, size_t n); /* Operations */ int gsl_vector_int_get (const gsl_vector_int * v, const size_t i); void gsl_vector_int_set (gsl_vector_int * v, const size_t i, int x); int *gsl_vector_int_ptr (gsl_vector_int * v, const size_t i); const int *gsl_vector_int_const_ptr (const gsl_vector_int * v, const size_t i); void gsl_vector_int_set_zero (gsl_vector_int * v); void gsl_vector_int_set_all (gsl_vector_int * v, int x); int gsl_vector_int_set_basis (gsl_vector_int * v, size_t i); int gsl_vector_int_fread (FILE * stream, gsl_vector_int * v); int gsl_vector_int_fwrite (FILE * stream, const gsl_vector_int * v); int gsl_vector_int_fscanf (FILE * stream, gsl_vector_int * v); int gsl_vector_int_fprintf (FILE * stream, const gsl_vector_int * v, const char *format); int gsl_vector_int_memcpy (gsl_vector_int * dest, const gsl_vector_int * src); int gsl_vector_int_reverse (gsl_vector_int * v); int gsl_vector_int_swap (gsl_vector_int * v, gsl_vector_int * w); int gsl_vector_int_swap_elements (gsl_vector_int * v, const size_t i, const size_t j); int gsl_vector_int_max (const gsl_vector_int * v); int gsl_vector_int_min (const gsl_vector_int * v); void gsl_vector_int_minmax (const gsl_vector_int * v, int * min_out, int * max_out); size_t gsl_vector_int_max_index (const gsl_vector_int * v); size_t gsl_vector_int_min_index (const gsl_vector_int * v); void gsl_vector_int_minmax_index (const gsl_vector_int * v, size_t * imin, size_t * imax); int gsl_vector_int_add (gsl_vector_int * a, const gsl_vector_int * b); int gsl_vector_int_sub (gsl_vector_int * a, const gsl_vector_int * b); int gsl_vector_int_mul (gsl_vector_int * a, const gsl_vector_int * b); int gsl_vector_int_div (gsl_vector_int * a, const gsl_vector_int * b); int gsl_vector_int_scale (gsl_vector_int * a, const double x); int gsl_vector_int_add_constant (gsl_vector_int * a, const double x); int gsl_vector_int_isnull (const gsl_vector_int * v); int gsl_vector_int_ispos (const gsl_vector_int * v); int gsl_vector_int_isneg (const gsl_vector_int * v); int gsl_vector_int_isnonneg (const gsl_vector_int * v); #ifdef HAVE_INLINE extern inline int gsl_vector_int_get (const gsl_vector_int * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_int_set (gsl_vector_int * v, const size_t i, int x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline int * gsl_vector_int_ptr (gsl_vector_int * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (int *) (v->data + i * v->stride); } extern inline const int * gsl_vector_int_const_ptr (const gsl_vector_int * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const int *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_INT_H__ */ sources_5316/external/gsl/gsl_linalg__qr.c0000664000176700017670000003467711723710247017501 0ustar paulpaul/* linalg/qr.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_linalg.h" #define REAL double #include "gsl_linalg__givens.c" #include "gsl_linalg__apply_givens.c" /* Factorise a general M x N matrix A into * * A = Q R * * where Q is orthogonal (M x M) and R is upper triangular (M x N). * * Q is stored as a packed set of Householder transformations in the * strict lower triangular part of the input matrix. * * R is stored in the diagonal and upper triangle of the input matrix. * * The full matrix for Q can be obtained as the product * * Q = Q_k .. Q_2 Q_1 * * where k = MIN(M,N) and * * Q_i = (I - tau_i * v_i * v_i') * * and where v_i is a Householder vector * * v_i = [1, m(i+1,i), m(i+2,i), ... , m(M,i)] * * This storage scheme is the same as in LAPACK. */ int gsl_linalg_QR_decomp (gsl_matrix * A, gsl_vector * tau) { const size_t M = A->size1; const size_t N = A->size2; if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else { size_t i; for (i = 0; i < GSL_MIN (M, N); i++) { /* Compute the Householder transformation to reduce the j-th column of the matrix to a multiple of the j-th unit vector */ gsl_vector_view c_full = gsl_matrix_column (A, i); gsl_vector_view c = gsl_vector_subvector (&(c_full.vector), i, M-i); double tau_i = gsl_linalg_householder_transform (&(c.vector)); gsl_vector_set (tau, i, tau_i); /* Apply the transformation to the remaining columns and update the norms */ if (i + 1 < N) { gsl_matrix_view m = gsl_matrix_submatrix (A, i, i + 1, M - i, N - (i + 1)); gsl_linalg_householder_hm (tau_i, &(c.vector), &(m.matrix)); } } return GSL_SUCCESS; } } /* Solves the system A x = b using the QR factorisation, * R x = Q^T b * * to obtain x. Based on SLATEC code. */ int gsl_linalg_QR_solve (const gsl_matrix * QR, const gsl_vector * tau, const gsl_vector * b, gsl_vector * x) { if (QR->size1 != QR->size2) { GSL_ERROR ("QR matrix must be square", GSL_ENOTSQR); } else if (QR->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (QR->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve for x */ gsl_linalg_QR_svx (QR, tau, x); return GSL_SUCCESS; } } /* Solves the system A x = b in place using the QR factorisation, * R x = Q^T b * * to obtain x. Based on SLATEC code. */ int gsl_linalg_QR_svx (const gsl_matrix * QR, const gsl_vector * tau, gsl_vector * x) { if (QR->size1 != QR->size2) { GSL_ERROR ("QR matrix must be square", GSL_ENOTSQR); } else if (QR->size1 != x->size) { GSL_ERROR ("matrix size must match x/rhs size", GSL_EBADLEN); } else { /* compute rhs = Q^T b */ gsl_linalg_QR_QTvec (QR, tau, x); /* Solve R x = rhs, storing x in-place */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, QR, x); return GSL_SUCCESS; } } /* Find the least squares solution to the overdetermined system * * A x = b * * for M >= N using the QR factorization A = Q R. */ int gsl_linalg_QR_lssolve (const gsl_matrix * QR, const gsl_vector * tau, const gsl_vector * b, gsl_vector * x, gsl_vector * residual) { const size_t M = QR->size1; const size_t N = QR->size2; if (M < N) { GSL_ERROR ("QR matrix must have M>=N", GSL_EBADLEN); } else if (M != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (N != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else if (M != residual->size) { GSL_ERROR ("matrix size must match residual size", GSL_EBADLEN); } else { gsl_matrix_const_view R = gsl_matrix_const_submatrix (QR, 0, 0, N, N); gsl_vector_view c = gsl_vector_subvector(residual, 0, N); gsl_vector_memcpy(residual, b); /* compute rhs = Q^T b */ gsl_linalg_QR_QTvec (QR, tau, residual); /* Solve R x = rhs */ gsl_vector_memcpy(x, &(c.vector)); gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, &(R.matrix), x); /* Compute residual = b - A x = Q (Q^T b - R x) */ gsl_vector_set_zero(&(c.vector)); gsl_linalg_QR_Qvec(QR, tau, residual); return GSL_SUCCESS; } } int gsl_linalg_QR_Rsolve (const gsl_matrix * QR, const gsl_vector * b, gsl_vector * x) { if (QR->size1 != QR->size2) { GSL_ERROR ("QR matrix must be square", GSL_ENOTSQR); } else if (QR->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (QR->size2 != x->size) { GSL_ERROR ("matrix size must match x size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve R x = b, storing x in-place */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, QR, x); return GSL_SUCCESS; } } int gsl_linalg_QR_Rsvx (const gsl_matrix * QR, gsl_vector * x) { if (QR->size1 != QR->size2) { GSL_ERROR ("QR matrix must be square", GSL_ENOTSQR); } else if (QR->size1 != x->size) { GSL_ERROR ("matrix size must match rhs size", GSL_EBADLEN); } else { /* Solve R x = b, storing x in-place */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, QR, x); return GSL_SUCCESS; } } int gsl_linalg_R_solve (const gsl_matrix * R, const gsl_vector * b, gsl_vector * x) { if (R->size1 != R->size2) { GSL_ERROR ("R matrix must be square", GSL_ENOTSQR); } else if (R->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (R->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve R x = b, storing x inplace in b */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, R, x); return GSL_SUCCESS; } } int gsl_linalg_R_svx (const gsl_matrix * R, gsl_vector * x) { if (R->size1 != R->size2) { GSL_ERROR ("R matrix must be square", GSL_ENOTSQR); } else if (R->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Solve R x = b, storing x inplace in b */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, R, x); return GSL_SUCCESS; } } /* Form the product Q^T v from a QR factorized matrix */ int gsl_linalg_QR_QTvec (const gsl_matrix * QR, const gsl_vector * tau, gsl_vector * v) { const size_t M = QR->size1; const size_t N = QR->size2; if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (v->size != M) { GSL_ERROR ("vector size must be N", GSL_EBADLEN); } else { size_t i; /* compute Q^T v */ for (i = 0; i < GSL_MIN (M, N); i++) { gsl_vector_const_view c = gsl_matrix_const_column (QR, i); gsl_vector_const_view h = gsl_vector_const_subvector (&(c.vector), i, M - i); gsl_vector_view w = gsl_vector_subvector (v, i, M - i); double ti = gsl_vector_get (tau, i); gsl_linalg_householder_hv (ti, &(h.vector), &(w.vector)); } return GSL_SUCCESS; } } int gsl_linalg_QR_Qvec (const gsl_matrix * QR, const gsl_vector * tau, gsl_vector * v) { const size_t M = QR->size1; const size_t N = QR->size2; if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (v->size != M) { GSL_ERROR ("vector size must be N", GSL_EBADLEN); } else { size_t i; /* compute Q^T v */ for (i = GSL_MIN (M, N); i > 0 && i--;) { gsl_vector_const_view c = gsl_matrix_const_column (QR, i); gsl_vector_const_view h = gsl_vector_const_subvector (&(c.vector), i, M - i); gsl_vector_view w = gsl_vector_subvector (v, i, M - i); double ti = gsl_vector_get (tau, i); gsl_linalg_householder_hv (ti, &h.vector, &w.vector); } return GSL_SUCCESS; } } /* Form the product Q^T A from a QR factorized matrix */ int gsl_linalg_QR_QTmat (const gsl_matrix * QR, const gsl_vector * tau, gsl_matrix * A) { const size_t M = QR->size1; const size_t N = QR->size2; if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (A->size1 != M) { GSL_ERROR ("matrix must have M rows", GSL_EBADLEN); } else { size_t i; /* compute Q^T A */ for (i = 0; i < GSL_MIN (M, N); i++) { gsl_vector_const_view c = gsl_matrix_const_column (QR, i); gsl_vector_const_view h = gsl_vector_const_subvector (&(c.vector), i, M - i); gsl_matrix_view m = gsl_matrix_submatrix(A, i, 0, M - i, A->size2); double ti = gsl_vector_get (tau, i); gsl_linalg_householder_hm (ti, &(h.vector), &(m.matrix)); } return GSL_SUCCESS; } } /* Form the orthogonal matrix Q from the packed QR matrix */ int gsl_linalg_QR_unpack (const gsl_matrix * QR, const gsl_vector * tau, gsl_matrix * Q, gsl_matrix * R) { const size_t M = QR->size1; const size_t N = QR->size2; if (Q->size1 != M || Q->size2 != M) { GSL_ERROR ("Q matrix must be M x M", GSL_ENOTSQR); } else if (R->size1 != M || R->size2 != N) { GSL_ERROR ("R matrix must be M x N", GSL_ENOTSQR); } else if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else { size_t i, j; /* Initialize Q to the identity */ gsl_matrix_set_identity (Q); for (i = GSL_MIN (M, N); i > 0 && i--;) { gsl_vector_const_view c = gsl_matrix_const_column (QR, i); gsl_vector_const_view h = gsl_vector_const_subvector (&c.vector, i, M - i); gsl_matrix_view m = gsl_matrix_submatrix (Q, i, i, M - i, M - i); double ti = gsl_vector_get (tau, i); gsl_linalg_householder_hm (ti, &h.vector, &m.matrix); } /* Form the right triangular matrix R from a packed QR matrix */ for (i = 0; i < M; i++) { for (j = 0; j < i && j < N; j++) gsl_matrix_set (R, i, j, 0.0); for (j = i; j < N; j++) gsl_matrix_set (R, i, j, gsl_matrix_get (QR, i, j)); } return GSL_SUCCESS; } } /* Update a QR factorisation for A= Q R , A' = A + u v^T, * Q' R' = QR + u v^T * = Q (R + Q^T u v^T) * = Q (R + w v^T) * * where w = Q^T u. * * Algorithm from Golub and Van Loan, "Matrix Computations", Section * 12.5 (Updating Matrix Factorizations, Rank-One Changes) */ int gsl_linalg_QR_update (gsl_matrix * Q, gsl_matrix * R, gsl_vector * w, const gsl_vector * v) { const size_t M = R->size1; const size_t N = R->size2; if (Q->size1 != M || Q->size2 != M) { GSL_ERROR ("Q matrix must be M x M if R is M x N", GSL_ENOTSQR); } else if (w->size != M) { GSL_ERROR ("w must be length M if R is M x N", GSL_EBADLEN); } else if (v->size != N) { GSL_ERROR ("v must be length N if R is M x N", GSL_EBADLEN); } else { size_t j, k; double w0; /* Apply Given's rotations to reduce w to (|w|, 0, 0, ... , 0) J_1^T .... J_(n-1)^T w = +/- |w| e_1 simultaneously applied to R, H = J_1^T ... J^T_(n-1) R so that H is upper Hessenberg. (12.5.2) */ for (k = M - 1; k > 0; k--) { double c, s; double wk = gsl_vector_get (w, k); double wkm1 = gsl_vector_get (w, k - 1); create_givens (wkm1, wk, &c, &s); apply_givens_vec (w, k - 1, k, c, s); apply_givens_qr (M, N, Q, R, k - 1, k, c, s); } w0 = gsl_vector_get (w, 0); /* Add in w v^T (Equation 12.5.3) */ for (j = 0; j < N; j++) { double r0j = gsl_matrix_get (R, 0, j); double vj = gsl_vector_get (v, j); gsl_matrix_set (R, 0, j, r0j + w0 * vj); } /* Apply Givens transformations R' = G_(n-1)^T ... G_1^T H Equation 12.5.4 */ for (k = 1; k < GSL_MIN(M,N+1); k++) { double c, s; double diag = gsl_matrix_get (R, k - 1, k - 1); double offdiag = gsl_matrix_get (R, k, k - 1); create_givens (diag, offdiag, &c, &s); apply_givens_qr (M, N, Q, R, k - 1, k, c, s); gsl_matrix_set (R, k, k - 1, 0.0); /* exact zero of G^T */ } return GSL_SUCCESS; } } int gsl_linalg_QR_QRsolve (gsl_matrix * Q, gsl_matrix * R, const gsl_vector * b, gsl_vector * x) { const size_t M = R->size1; const size_t N = R->size2; if (M != N) { return GSL_ENOTSQR; } else if (Q->size1 != M || b->size != M || x->size != M) { return GSL_EBADLEN; } else { /* compute sol = Q^T b */ gsl_blas_dgemv (CblasTrans, 1.0, Q, b, 0.0, x); /* Solve R x = sol, storing x in-place */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, R, x); return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_cblas__source_trsm_r.h0000664000176700017670000001437011705263724021557 0ustar paulpaul/* blas/source_trsm_r.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; INDEX n1, n2; const int nonunit = (Diag == CblasNonUnit); int side, uplo, trans; if (Order == CblasRowMajor) { n1 = M; n2 = N; side = Side; uplo = Uplo; trans = (TransA == CblasConjTrans) ? CblasTrans : TransA; } else { n1 = N; n2 = M; side = (Side == CblasLeft) ? CblasRight : CblasLeft; uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; trans = (TransA == CblasConjTrans) ? CblasTrans : TransA; } if (side == CblasLeft && uplo == CblasUpper && trans == CblasNoTrans) { /* form B := alpha * inv(TriU(A)) *B */ if (alpha != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { B[ldb * i + j] *= alpha; } } } for (i = n1; i > 0 && i--;) { if (nonunit) { BASE Aii = A[lda * i + i]; for (j = 0; j < n2; j++) { B[ldb * i + j] /= Aii; } } for (k = 0; k < i; k++) { const BASE Aki = A[k * lda + i]; for (j = 0; j < n2; j++) { B[ldb * k + j] -= Aki * B[ldb * i + j]; } } } } else if (side == CblasLeft && uplo == CblasUpper && trans == CblasTrans) { /* form B := alpha * inv(TriU(A))' *B */ if (alpha != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { B[ldb * i + j] *= alpha; } } } for (i = 0; i < n1; i++) { if (nonunit) { BASE Aii = A[lda * i + i]; for (j = 0; j < n2; j++) { B[ldb * i + j] /= Aii; } } for (k = i + 1; k < n1; k++) { const BASE Aik = A[i * lda + k]; for (j = 0; j < n2; j++) { B[ldb * k + j] -= Aik * B[ldb * i + j]; } } } } else if (side == CblasLeft && uplo == CblasLower && trans == CblasNoTrans) { /* form B := alpha * inv(TriL(A))*B */ if (alpha != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { B[ldb * i + j] *= alpha; } } } for (i = 0; i < n1; i++) { if (nonunit) { BASE Aii = A[lda * i + i]; for (j = 0; j < n2; j++) { B[ldb * i + j] /= Aii; } } for (k = i + 1; k < n1; k++) { const BASE Aki = A[k * lda + i]; for (j = 0; j < n2; j++) { B[ldb * k + j] -= Aki * B[ldb * i + j]; } } } } else if (side == CblasLeft && uplo == CblasLower && trans == CblasTrans) { /* form B := alpha * TriL(A)' *B */ if (alpha != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { B[ldb * i + j] *= alpha; } } } for (i = n1; i > 0 && i--;) { if (nonunit) { BASE Aii = A[lda * i + i]; for (j = 0; j < n2; j++) { B[ldb * i + j] /= Aii; } } for (k = 0; k < i; k++) { const BASE Aik = A[i * lda + k]; for (j = 0; j < n2; j++) { B[ldb * k + j] -= Aik * B[ldb * i + j]; } } } } else if (side == CblasRight && uplo == CblasUpper && trans == CblasNoTrans) { /* form B := alpha * B * inv(TriU(A)) */ if (alpha != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { B[ldb * i + j] *= alpha; } } } for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { if (nonunit) { BASE Ajj = A[lda * j + j]; B[ldb * i + j] /= Ajj; } { BASE Bij = B[ldb * i + j]; for (k = j + 1; k < n2; k++) { B[ldb * i + k] -= A[j * lda + k] * Bij; } } } } } else if (side == CblasRight && uplo == CblasUpper && trans == CblasTrans) { /* form B := alpha * B * inv(TriU(A))' */ if (alpha != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { B[ldb * i + j] *= alpha; } } } for (i = 0; i < n1; i++) { for (j = n2; j > 0 && j--;) { if (nonunit) { BASE Ajj = A[lda * j + j]; B[ldb * i + j] /= Ajj; } { BASE Bij = B[ldb * i + j]; for (k = 0; k < j; k++) { B[ldb * i + k] -= A[k * lda + j] * Bij; } } } } } else if (side == CblasRight && uplo == CblasLower && trans == CblasNoTrans) { /* form B := alpha * B * inv(TriL(A)) */ if (alpha != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { B[ldb * i + j] *= alpha; } } } for (i = 0; i < n1; i++) { for (j = n2; j > 0 && j--;) { if (nonunit) { BASE Ajj = A[lda * j + j]; B[ldb * i + j] /= Ajj; } { BASE Bij = B[ldb * i + j]; for (k = 0; k < j; k++) { B[ldb * i + k] -= A[j * lda + k] * Bij; } } } } } else if (side == CblasRight && uplo == CblasLower && trans == CblasTrans) { /* form B := alpha * B * inv(TriL(A))' */ if (alpha != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { B[ldb * i + j] *= alpha; } } } for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { if (nonunit) { BASE Ajj = A[lda * j + j]; B[ldb * i + j] /= Ajj; } { BASE Bij = B[ldb * i + j]; for (k = j + 1; k < n2; k++) { B[ldb * i + k] -= A[k * lda + j] * Bij; } } } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_vector__minmax_source.c0000664000176700017670000001007111723710247021742 0ustar paulpaul/* vector/minmax_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ BASE FUNCTION(gsl_vector,max) (const TYPE(gsl_vector) * v) { /* finds the largest element of a vector */ const size_t N = v->size ; const size_t stride = v->stride ; BASE max = v->data[0 * stride]; size_t i; for (i = 0; i < N; i++) { BASE x = v->data[i*stride]; if (x > max) max = x; #ifdef FP if (isnan (x)) return x; #endif } return max; } BASE FUNCTION(gsl_vector,min) (const TYPE(gsl_vector) * v) { /* finds the smallest element of a vector */ const size_t N = v->size ; const size_t stride = v->stride ; BASE min = v->data[0 * stride]; size_t i; for (i = 0; i < N; i++) { BASE x = v->data[i*stride]; if (x < min) min = x; #ifdef FP if (isnan (x)) return x; #endif } return min; } void FUNCTION(gsl_vector,minmax) (const TYPE(gsl_vector) * v, BASE * min_out, BASE * max_out) { /* finds the smallest and largest elements of a vector */ const size_t N = v->size ; const size_t stride = v->stride ; BASE max = v->data[0 * stride]; BASE min = v->data[0 * stride]; size_t i; for (i = 0; i < N; i++) { BASE x = v->data[i*stride]; if (x < min) { min = x; } if (x > max) { max = x; } #ifdef FP if (isnan (x)) { min = x; max = x; break; } #endif } *min_out = min; *max_out = max; } size_t FUNCTION(gsl_vector,max_index) (const TYPE(gsl_vector) * v) { /* finds the largest element of a vector */ const size_t N = v->size ; const size_t stride = v->stride ; BASE max = v->data[0 * stride]; size_t imax = 0; size_t i; for (i = 0; i < N; i++) { BASE x = v->data[i*stride]; if (x > max) { max = x; imax = i; } #ifdef FP if (isnan (x)) { return i; } #endif } return imax; } size_t FUNCTION(gsl_vector,min_index) (const TYPE(gsl_vector) * v) { /* finds the smallest element of a vector */ const size_t N = v->size ; const size_t stride = v->stride ; BASE min = v->data[0 * stride]; size_t imin = 0; size_t i; for (i = 0; i < N; i++) { BASE x = v->data[i*stride]; if (x < min) { min = x; imin = i; } #ifdef FP if (isnan (x)) { return i; } #endif } return imin; } void FUNCTION(gsl_vector,minmax_index) (const TYPE(gsl_vector) * v, size_t * imin_out, size_t * imax_out) { /* finds the smallest and largest elements of a vector */ const size_t N = v->size ; const size_t stride = v->stride ; size_t imin = 0, imax = 0; BASE max = v->data[0 * stride]; BASE min = v->data[0 * stride]; size_t i; for (i = 0; i < N; i++) { BASE x = v->data[i*stride]; if (x < min) { min = x; imin = i; } if (x > max) { max = x; imax = i; } #ifdef FP if (isnan (x)) { imin = i; imax = i; break; } #endif } *imin_out = imin; *imax_out = imax; } sources_5316/external/gsl/gsl_cdf__fdistinv.c0000664000176700017670000000431511723710247020155 0ustar paulpaul/* cdf/fdistinv.c * * Copyright (C) 2002 Przemyslaw Sliwa and Jason H. Stover. * Copyright (C) 2006, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include "gsl__config.h" #include "gsl_cdf.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_cdf__error.h" double gsl_cdf_fdist_Pinv (const double P, const double nu1, const double nu2) { double result; double y; if (P < 0.0) { CDF_ERROR ("P < 0.0", GSL_EDOM); } if (P > 1.0) { CDF_ERROR ("P > 1.0", GSL_EDOM); } if (nu1 < 1.0) { CDF_ERROR ("nu1 < 1", GSL_EDOM); } if (nu2 < 1.0) { CDF_ERROR ("nu2 < 1", GSL_EDOM); } if (P < 0.5) { y = gsl_cdf_beta_Pinv (P, nu1 / 2.0, nu2 / 2.0); result = nu2 * y / (nu1 * (1.0 - y)); } else { y = gsl_cdf_beta_Qinv (P, nu2 / 2.0, nu1 / 2.0); result = nu2 * (1 - y) / (nu1 * y); } return result; } double gsl_cdf_fdist_Qinv (const double Q, const double nu1, const double nu2) { double result; double y; if (Q < 0.0) { CDF_ERROR ("Q < 0.0", GSL_EDOM); } if (Q > 1.0) { CDF_ERROR ("Q > 1.0", GSL_EDOM); } if (nu1 < 1.0) { CDF_ERROR ("nu1 < 1", GSL_EDOM); } if (nu2 < 1.0) { CDF_ERROR ("nu2 < 1", GSL_EDOM); } if (Q > 0.5) { y = gsl_cdf_beta_Qinv (Q, nu1 / 2.0, nu2 / 2.0); result = nu2 * y / (nu1 * (1.0 - y)); } else { y = gsl_cdf_beta_Pinv (Q, nu2 / 2.0, nu1 / 2.0); result = nu2 * (1 - y) / (nu1 * y); } return result; } sources_5316/external/gsl/gsl_specfunc__pow_int.c0000664000176700017670000000360111723710247021055 0ustar paulpaul/* specfunc/pow_int.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions w/ Error handling *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_pow_int_e(double x, int n, gsl_sf_result * result) { double value = 1.0; int count = 0; /* CHECK_POINTER(result) */ if(n < 0) { n = -n; if(x == 0.0) { double u = 1.0 / x; result->val = (n % 2) ? u : (u * u) ; /* correct sign of infinity */ result->err = GSL_POSINF; GSL_ERROR ("overflow", GSL_EOVRFLW); } x = 1.0/x; } /* repeated squaring method * returns 0.0^0 = 1.0, so continuous in x */ do { if(GSL_IS_ODD(n)) value *= x; n >>= 1; x *= x; ++count; } while (n); result->val = value; result->err = 2.0 * GSL_DBL_EPSILON * (count + 1.0) * fabs(value); return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_pow_int(const double x, const int n) { EVAL_RESULT(gsl_sf_pow_int_e(x, n, &result)); } sources_5316/external/gsl/gsl_fft_complex.h0000664000176700017670000001132211705263724017666 0ustar paulpaul/* fft/gsl_fft_complex.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_FFT_COMPLEX_H__ #define __GSL_FFT_COMPLEX_H__ #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_fft.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Power of 2 routines */ int gsl_fft_complex_radix2_forward (gsl_complex_packed_array data, const size_t stride, const size_t n); int gsl_fft_complex_radix2_backward (gsl_complex_packed_array data, const size_t stride, const size_t n); int gsl_fft_complex_radix2_inverse (gsl_complex_packed_array data, const size_t stride, const size_t n); int gsl_fft_complex_radix2_transform (gsl_complex_packed_array data, const size_t stride, const size_t n, const gsl_fft_direction sign); int gsl_fft_complex_radix2_dif_forward (gsl_complex_packed_array data, const size_t stride, const size_t n); int gsl_fft_complex_radix2_dif_backward (gsl_complex_packed_array data, const size_t stride, const size_t n); int gsl_fft_complex_radix2_dif_inverse (gsl_complex_packed_array data, const size_t stride, const size_t n); int gsl_fft_complex_radix2_dif_transform (gsl_complex_packed_array data, const size_t stride, const size_t n, const gsl_fft_direction sign); /* Mixed Radix general-N routines */ typedef struct { size_t n; size_t nf; size_t factor[64]; gsl_complex *twiddle[64]; gsl_complex *trig; } gsl_fft_complex_wavetable; typedef struct { size_t n; double *scratch; } gsl_fft_complex_workspace; gsl_fft_complex_wavetable *gsl_fft_complex_wavetable_alloc (size_t n); void gsl_fft_complex_wavetable_free (gsl_fft_complex_wavetable * wavetable); gsl_fft_complex_workspace *gsl_fft_complex_workspace_alloc (size_t n); void gsl_fft_complex_workspace_free (gsl_fft_complex_workspace * workspace); int gsl_fft_complex_memcpy (gsl_fft_complex_wavetable * dest, gsl_fft_complex_wavetable * src); int gsl_fft_complex_forward (gsl_complex_packed_array data, const size_t stride, const size_t n, const gsl_fft_complex_wavetable * wavetable, gsl_fft_complex_workspace * work); int gsl_fft_complex_backward (gsl_complex_packed_array data, const size_t stride, const size_t n, const gsl_fft_complex_wavetable * wavetable, gsl_fft_complex_workspace * work); int gsl_fft_complex_inverse (gsl_complex_packed_array data, const size_t stride, const size_t n, const gsl_fft_complex_wavetable * wavetable, gsl_fft_complex_workspace * work); int gsl_fft_complex_transform (gsl_complex_packed_array data, const size_t stride, const size_t n, const gsl_fft_complex_wavetable * wavetable, gsl_fft_complex_workspace * work, const gsl_fft_direction sign); __END_DECLS #endif /* __GSL_FFT_COMPLEX_H__ */ sources_5316/external/gsl/gsl_sort.h0000664000176700017670000000060711705263724016353 0ustar paulpaul#ifndef __GSL_SORT_H__ #define __GSL_SORT_H__ #include "gsl_sort_long_double.h" #include "gsl_sort_double.h" #include "gsl_sort_float.h" #include "gsl_sort_ulong.h" #include "gsl_sort_long.h" #include "gsl_sort_uint.h" #include "gsl_sort_int.h" #include "gsl_sort_ushort.h" #include "gsl_sort_short.h" #include "gsl_sort_uchar.h" #include "gsl_sort_char.h" #endif /* __GSL_SORT_H__ */ sources_5316/external/gsl/gsl_permute_complex_long_double.h0000664000176700017670000000301711705263724023143 0ustar paulpaul/* permutation/gsl_permute_complex_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_COMPLEX_LONG_DOUBLE_H__ #define __GSL_PERMUTE_COMPLEX_LONG_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_complex_long_double (const size_t * p, long double * data, const size_t stride, const size_t n); int gsl_permute_complex_long_double_inverse (const size_t * p, long double * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_COMPLEX_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_cblas__cgbmv.c0000664000176700017670000000070011723710247017747 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cgbmv (const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const int KL, const int KU, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE float #include "gsl_cblas__source_gbmv_c.h" #undef BASE } sources_5316/external/gsl/gsl_sort__sortvecind.c0000664000176700017670000000435611723710247020747 0ustar paulpaul/* * Implement Heap sort -- direct and indirect sorting * Based on descriptions in Sedgewick "Algorithms in C" * * Copyright (C) 1999 Thomas Walter * * 18 February 2000: Modified for GSL by Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_vector.h" #include "gsl_sort.h" #include "gsl_sort_vector.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_sort__sortvecind_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_cdf__gumbel1.c0000664000176700017670000000236011723710247017661 0ustar paulpaul/* cdf/gumbel1.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_gumbel1_P (const double x, const double a, const double b) { double P = pow(exp (-b), exp (-a * x)); return P; } double gsl_cdf_gumbel1_Q (const double x, const double a, const double b) { double u = exp (-a * x); double Q; double P = pow(exp (-b), u); if (P < 0.5) { Q = 1 - P; } else { Q = -expm1 (-b * u); } return Q; } sources_5316/external/gsl/gsl_sf__bessel_Knu.c0000644000176700017670000001113410707442037020270 0ustar paulpaul/* specfunc/bessel_Knu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_temme.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Knu_scaled_e(const double nu, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else { int N = (int)(nu + 0.5); double mu = nu - N; /* -1/2 <= mu <= 1/2 */ double K_mu, K_mup1, Kp_mu; double K_nu, K_nup1, K_num1; int n; if(x < 2.0) { gsl_sf_bessel_K_scaled_temme(mu, x, &K_mu, &K_mup1, &Kp_mu); } else { gsl_sf_bessel_K_scaled_steed_temme_CF2(mu, x, &K_mu, &K_mup1, &Kp_mu); } /* recurse forward to obtain K_num1, K_nu */ K_nu = K_mu; K_nup1 = K_mup1; for(n=0; nval = K_nu; result->err = 2.0 * GSL_DBL_EPSILON * (N + 4.0) * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_Knu_e(const double nu, const double x, gsl_sf_result * result) { gsl_sf_result b; int stat_K = gsl_sf_bessel_Knu_scaled_e(nu, x, &b); int stat_e = gsl_sf_exp_mult_err_e(-x, 0.0, b.val, b.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } int gsl_sf_bessel_lnKnu_e(const double nu, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else if(nu == 0.0) { gsl_sf_result K_scaled; /* This cannot underflow, and * it will not throw GSL_EDOM * since that is already checked. */ gsl_sf_bessel_K0_scaled_e(x, &K_scaled); result->val = -x + log(fabs(K_scaled.val)); result->err = GSL_DBL_EPSILON * fabs(x) + fabs(K_scaled.err/K_scaled.val); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 2.0 && nu > 1.0) { /* Make use of the inequality * Knu(x) <= 1/2 (2/x)^nu Gamma(nu), * which follows from the integral representation * [Abramowitz+Stegun, 9.6.23 (2)]. With this * we decide whether or not there is an overflow * problem because x is small. */ double ln_bound; gsl_sf_result lg_nu; gsl_sf_lngamma_e(nu, &lg_nu); ln_bound = -M_LN2 - nu*log(0.5*x) + lg_nu.val; if(ln_bound > GSL_LOG_DBL_MAX - 20.0) { /* x must be very small or nu very large (or both). */ double xi = 0.25*x*x; double sum = 1.0 - xi/(nu-1.0); if(nu > 2.0) sum += (xi/(nu-1.0)) * (xi/(nu-2.0)); result->val = ln_bound + log(sum); result->err = lg_nu.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* can drop-through here */ } { /* We passed the above tests, so no problem. * Evaluate as usual. Note the possible drop-through * in the above code! */ gsl_sf_result K_scaled; gsl_sf_bessel_Knu_scaled_e(nu, x, &K_scaled); result->val = -x + log(fabs(K_scaled.val)); result->err = GSL_DBL_EPSILON * fabs(x) + fabs(K_scaled.err/K_scaled.val); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_Knu_scaled(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_Knu_scaled_e(nu, x, &result)); } double gsl_sf_bessel_Knu(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_Knu_e(nu, x, &result)); } double gsl_sf_bessel_lnKnu(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_lnKnu_e(nu, x, &result)); } sources_5316/external/gsl/gsl_cblas__source_hbmv.h0000664000176700017670000001202111705263724021174 0ustar paulpaul/* blas/source_hbmv.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; const int conj = (order == CblasColMajor) ? -1 : 1; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if (N == 0) return; if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; /* form y := beta*y */ if (beta_real == 0.0 && beta_imag == 0.0) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { REAL(Y, iy) = 0.0; IMAG(Y, iy) = 0.0; iy += incY; } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE y_real = REAL(Y, iy); const BASE y_imag = IMAG(Y, iy); const BASE tmpR = y_real * beta_real - y_imag * beta_imag; const BASE tmpI = y_real * beta_imag + y_imag * beta_real; REAL(Y, iy) = tmpR; IMAG(Y, iy) = tmpI; iy += incY; } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; /* form y := alpha*A*x + y */ if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { BASE x_real = CONST_REAL(X, ix); BASE x_imag = CONST_IMAG(X, ix); BASE temp1_real = alpha_real * x_real - alpha_imag * x_imag; BASE temp1_imag = alpha_real * x_imag + alpha_imag * x_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; const INDEX j_min = i + 1; const INDEX j_max = GSL_MIN(N, i + K + 1); INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; BASE Aii_real = CONST_REAL(A, lda * i + 0); /* Aii_imag is zero */ REAL(Y, iy) += temp1_real * Aii_real; IMAG(Y, iy) += temp1_imag * Aii_real; for (j = j_min; j < j_max; j++) { BASE Aij_real = CONST_REAL(A, lda * i + (j - i)); BASE Aij_imag = conj * CONST_IMAG(A, lda * i + (j - i)); REAL(Y, jy) += temp1_real * Aij_real - temp1_imag * (-Aij_imag); IMAG(Y, jy) += temp1_real * (-Aij_imag) + temp1_imag * Aij_real; x_real = CONST_REAL(X, jx); x_imag = CONST_IMAG(X, jx); temp2_real += x_real * Aij_real - x_imag * Aij_imag; temp2_imag += x_real * Aij_imag + x_imag * Aij_real; jx += incX; jy += incY; } REAL(Y, iy) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(Y, iy) += alpha_real * temp2_imag + alpha_imag * temp2_real; ix += incX; iy += incY; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { BASE x_real = CONST_REAL(X, ix); BASE x_imag = CONST_IMAG(X, ix); BASE temp1_real = alpha_real * x_real - alpha_imag * x_imag; BASE temp1_imag = alpha_real * x_imag + alpha_imag * x_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; const INDEX j_min = (K > i ? 0 : i - K); const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; for (j = j_min; j < j_max; j++) { BASE Aij_real = CONST_REAL(A, i * lda + (K - i + j)); BASE Aij_imag = conj * CONST_IMAG(A, i * lda + (K - i + j)); REAL(Y, jy) += temp1_real * Aij_real - temp1_imag * (-Aij_imag); IMAG(Y, jy) += temp1_real * (-Aij_imag) + temp1_imag * Aij_real; x_real = CONST_REAL(X, jx); x_imag = CONST_IMAG(X, jx); temp2_real += x_real * Aij_real - x_imag * Aij_imag; temp2_imag += x_real * Aij_imag + x_imag * Aij_real; jx += incX; jy += incY; } { BASE Aii_real = CONST_REAL(A, lda * i + K); /* Aii_imag is zero */ REAL(Y, iy) += temp1_real * Aii_real; IMAG(Y, iy) += temp1_imag * Aii_real; } REAL(Y, iy) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(Y, iy) += alpha_real * temp2_imag + alpha_imag * temp2_real; ix += incX; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_permutation.h0000664000176700017670000000631211705263724017732 0ustar paulpaul/* permutation/gsl_permutation.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTATION_H__ #define __GSL_PERMUTATION_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_permutation_struct { size_t size; size_t *data; }; typedef struct gsl_permutation_struct gsl_permutation; gsl_permutation *gsl_permutation_alloc (const size_t n); gsl_permutation *gsl_permutation_calloc (const size_t n); void gsl_permutation_init (gsl_permutation * p); void gsl_permutation_free (gsl_permutation * p); int gsl_permutation_memcpy (gsl_permutation * dest, const gsl_permutation * src); int gsl_permutation_fread (FILE * stream, gsl_permutation * p); int gsl_permutation_fwrite (FILE * stream, const gsl_permutation * p); int gsl_permutation_fscanf (FILE * stream, gsl_permutation * p); int gsl_permutation_fprintf (FILE * stream, const gsl_permutation * p, const char *format); size_t gsl_permutation_size (const gsl_permutation * p); size_t * gsl_permutation_data (const gsl_permutation * p); size_t gsl_permutation_get (const gsl_permutation * p, const size_t i); int gsl_permutation_swap (gsl_permutation * p, const size_t i, const size_t j); int gsl_permutation_valid (gsl_permutation * p); void gsl_permutation_reverse (gsl_permutation * p); int gsl_permutation_inverse (gsl_permutation * inv, const gsl_permutation * p); int gsl_permutation_next (gsl_permutation * p); int gsl_permutation_prev (gsl_permutation * p); int gsl_permutation_mul (gsl_permutation * p, const gsl_permutation * pa, const gsl_permutation * pb); int gsl_permutation_linear_to_canonical (gsl_permutation * q, const gsl_permutation * p); int gsl_permutation_canonical_to_linear (gsl_permutation * p, const gsl_permutation * q); size_t gsl_permutation_inversions (const gsl_permutation * p); size_t gsl_permutation_linear_cycles (const gsl_permutation * p); size_t gsl_permutation_canonical_cycles (const gsl_permutation * q); #ifdef HAVE_INLINE extern inline size_t gsl_permutation_get (const gsl_permutation * p, const size_t i) { #if GSL_RANGE_CHECK if (i >= p->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return p->data[i]; } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_PERMUTATION_H__ */ sources_5316/external/gsl/gsl_sf_synchrotron.h0000664000176700017670000000326711705263724020451 0ustar paulpaul/* specfunc/gsl_sf_synchrotron.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_SYNCHROTRON_H__ #define __GSL_SF_SYNCHROTRON_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* First synchrotron function: * synchrotron_1(x) = x Integral[ K_{5/3}(t), {t, x, Infinity}] * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_synchrotron_1_e(const double x, gsl_sf_result * result); double gsl_sf_synchrotron_1(const double x); /* Second synchroton function: * synchrotron_2(x) = x * K_{2/3}(x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_synchrotron_2_e(const double x, gsl_sf_result * result); double gsl_sf_synchrotron_2(const double x); __END_DECLS #endif /* __GSL_SF_SYNCHROTRON_H__ */ sources_5316/external/gsl/gsl_monte_plain.h0000664000176700017670000000352411705263724017672 0ustar paulpaul/* monte/gsl_monte_plain.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Michael Booth * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Plain Monte-Carlo. */ /* Author: MJB */ #ifndef __GSL_MONTE_PLAIN_H__ #define __GSL_MONTE_PLAIN_H__ #include #include "gsl_monte.h" #include "gsl_rng.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t dim; double *x; } gsl_monte_plain_state; int gsl_monte_plain_integrate (const gsl_monte_function * f, const double xl[], const double xu[], const size_t dim, const size_t calls, gsl_rng * r, gsl_monte_plain_state * state, double *result, double *abserr); gsl_monte_plain_state* gsl_monte_plain_alloc(size_t dim); int gsl_monte_plain_init(gsl_monte_plain_state* state); void gsl_monte_plain_free (gsl_monte_plain_state* state); __END_DECLS #endif /* __GSL_MONTE_PLAIN_H__ */ sources_5316/external/gsl/gsl_ieee-utils__env.c0000664000176700017670000000572211723710247020433 0ustar paulpaul/* ieee-utils/env.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" void gsl_ieee_env_setup (void) { const char * p = getenv("GSL_IEEE_MODE") ; int precision = 0, rounding = 0, exception_mask = 0 ; int comma = 0 ; if (p == 0) /* GSL_IEEE_MODE environment variable is not set */ return ; if (*p == '\0') /* GSL_IEEE_MODE environment variable is empty */ return ; gsl_ieee_read_mode_string (p, &precision, &rounding, &exception_mask) ; gsl_ieee_set_mode (precision, rounding, exception_mask) ; fprintf(stderr, "GSL_IEEE_MODE=\"") ; /* Print string with a preceeding comma if the list has already begun */ #define PRINTC(x) do {if(comma) fprintf(stderr,","); fprintf(stderr,x); comma++ ;} while(0) switch (precision) { case GSL_IEEE_SINGLE_PRECISION: PRINTC("single-precision") ; break ; case GSL_IEEE_DOUBLE_PRECISION: PRINTC("double-precision") ; break ; case GSL_IEEE_EXTENDED_PRECISION: PRINTC("extended-precision") ; break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: PRINTC("round-to-nearest") ; break ; case GSL_IEEE_ROUND_DOWN: PRINTC("round-down") ; break ; case GSL_IEEE_ROUND_UP: PRINTC("round-up") ; break ; case GSL_IEEE_ROUND_TO_ZERO: PRINTC("round-to-zero") ; break ; } if ((exception_mask & GSL_IEEE_MASK_ALL) == GSL_IEEE_MASK_ALL) { PRINTC("mask-all") ; } else if ((exception_mask & GSL_IEEE_MASK_ALL) == 0) { PRINTC("trap-common") ; } else { if (exception_mask & GSL_IEEE_MASK_INVALID) PRINTC("mask-invalid") ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) PRINTC("mask-denormalized") ; if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) PRINTC("mask-division-by-zero") ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) PRINTC("mask-overflow") ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) PRINTC("mask-underflow") ; } if (exception_mask & GSL_IEEE_TRAP_INEXACT) PRINTC("trap-inexact") ; fprintf(stderr,"\"\n") ; } sources_5316/external/gsl/gsl_eigen__genherm.c0000664000176700017670000001333411723710247020310 0ustar paulpaul/* eigen/genherm.c * * Copyright (C) 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include "gsl__config.h" #include "gsl_eigen.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_blas.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_complex.h" #include "gsl_complex_math.h" /* * This module computes the eigenvalues of a complex generalized * hermitian-definite eigensystem A x = \lambda B x, where A and * B are hermitian, and B is positive-definite. */ /* gsl_eigen_genherm_alloc() Allocate a workspace for solving the generalized hermitian-definite eigenvalue problem. The size of this workspace is O(3n). Inputs: n - size of matrices Return: pointer to workspace */ gsl_eigen_genherm_workspace * gsl_eigen_genherm_alloc(const size_t n) { gsl_eigen_genherm_workspace *w; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = calloc (1, sizeof (gsl_eigen_genherm_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->size = n; w->herm_workspace_p = gsl_eigen_herm_alloc(n); if (!w->herm_workspace_p) { gsl_eigen_genherm_free(w); GSL_ERROR_NULL("failed to allocate space for herm workspace", GSL_ENOMEM); } return (w); } /* gsl_eigen_genherm_alloc() */ /* gsl_eigen_genherm_free() Free workspace w */ void gsl_eigen_genherm_free (gsl_eigen_genherm_workspace * w) { if (w->herm_workspace_p) gsl_eigen_herm_free(w->herm_workspace_p); free(w); } /* gsl_eigen_genherm_free() */ /* gsl_eigen_genherm() Solve the generalized hermitian-definite eigenvalue problem A x = \lambda B x for the eigenvalues \lambda. Inputs: A - complex hermitian matrix B - complex hermitian and positive definite matrix eval - where to store eigenvalues w - workspace Return: success or error */ int gsl_eigen_genherm (gsl_matrix_complex * A, gsl_matrix_complex * B, gsl_vector * eval, gsl_eigen_genherm_workspace * w) { const size_t N = A->size1; /* check matrix and vector sizes */ if (N != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if ((N != B->size1) || (N != B->size2)) { GSL_ERROR ("B matrix dimensions must match A", GSL_EBADLEN); } else if (eval->size != N) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (w->size != N) { GSL_ERROR ("matrix size does not match workspace", GSL_EBADLEN); } else { int s; /* compute Cholesky factorization of B */ s = gsl_linalg_complex_cholesky_decomp(B); if (s != GSL_SUCCESS) return s; /* B is not positive definite */ /* transform to standard hermitian eigenvalue problem */ gsl_eigen_genherm_standardize(A, B); s = gsl_eigen_herm(A, eval, w->herm_workspace_p); return s; } } /* gsl_eigen_genherm() */ /* gsl_eigen_genherm_standardize() Reduce the generalized hermitian-definite eigenproblem to the standard hermitian eigenproblem by computing C = L^{-1} A L^{-H} where L L^H is the Cholesky decomposition of B Inputs: A - (input/output) complex hermitian matrix B - complex hermitian, positive definite matrix in Cholesky form Return: success Notes: A is overwritten by L^{-1} A L^{-H} */ int gsl_eigen_genherm_standardize(gsl_matrix_complex *A, const gsl_matrix_complex *B) { const size_t N = A->size1; size_t i; double a, b; gsl_complex y, z; GSL_SET_IMAG(&z, 0.0); for (i = 0; i < N; ++i) { /* update lower triangle of A(i:n, i:n) */ y = gsl_matrix_complex_get(A, i, i); a = GSL_REAL(y); y = gsl_matrix_complex_get(B, i, i); b = GSL_REAL(y); a /= b * b; GSL_SET_REAL(&z, a); gsl_matrix_complex_set(A, i, i, z); if (i < N - 1) { gsl_vector_complex_view ai = gsl_matrix_complex_subcolumn(A, i, i + 1, N - i - 1); gsl_matrix_complex_view ma = gsl_matrix_complex_submatrix(A, i + 1, i + 1, N - i - 1, N - i - 1); gsl_vector_complex_const_view bi = gsl_matrix_complex_const_subcolumn(B, i, i + 1, N - i - 1); gsl_matrix_complex_const_view mb = gsl_matrix_complex_const_submatrix(B, i + 1, i + 1, N - i - 1, N - i - 1); gsl_blas_zdscal(1.0 / b, &ai.vector); GSL_SET_REAL(&z, -0.5 * a); gsl_blas_zaxpy(z, &bi.vector, &ai.vector); gsl_blas_zher2(CblasLower, GSL_COMPLEX_NEGONE, &ai.vector, &bi.vector, &ma.matrix); gsl_blas_zaxpy(z, &bi.vector, &ai.vector); gsl_blas_ztrsv(CblasLower, CblasNoTrans, CblasNonUnit, &mb.matrix, &ai.vector); } } return GSL_SUCCESS; } /* gsl_eigen_genherm_standardize() */ sources_5316/external/gsl/gsl_matrix__file.c0000664000176700017670000000365611723710247020025 0ustar paulpaul#include "gsl__config.h" #include "gsl_errno.h" #include "gsl_matrix.h" #include "gsl_vector.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__file_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_multifit__covar.c0000664000176700017670000001070711723710247020544 0ustar paulpaul/* multifit/covar.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_linalg.h" #include "gsl_multifit_nlin.h" /* Compute the covariance matrix cov = inv (J^T J) by QRP^T decomposition of J */ int gsl_multifit_covar (const gsl_matrix * J, double epsrel, gsl_matrix * covar) { double tolr; size_t i, j, k; size_t kmax = 0; gsl_matrix * r; gsl_vector * tau; gsl_vector * norm; gsl_permutation * perm; size_t m = J->size1, n = J->size2 ; if (m < n) { GSL_ERROR ("Jacobian be rectangular M x N with M >= N", GSL_EBADLEN); } if (covar->size1 != covar->size2 || covar->size1 != n) { GSL_ERROR ("covariance matrix must be square and match second dimension of jacobian", GSL_EBADLEN); } r = gsl_matrix_alloc (m, n); tau = gsl_vector_alloc (n); perm = gsl_permutation_alloc (n) ; norm = gsl_vector_alloc (n) ; { int signum = 0; gsl_matrix_memcpy (r, J); gsl_linalg_QRPT_decomp (r, tau, perm, &signum, norm); } /* Form the inverse of R in the full upper triangle of R */ tolr = epsrel * fabs(gsl_matrix_get(r, 0, 0)); for (k = 0 ; k < n ; k++) { double rkk = gsl_matrix_get(r, k, k); if (fabs(rkk) <= tolr) { break; } gsl_matrix_set(r, k, k, 1.0/rkk); for (j = 0; j < k ; j++) { double t = gsl_matrix_get(r, j, k) / rkk; gsl_matrix_set (r, j, k, 0.0); for (i = 0; i <= j; i++) { double rik = gsl_matrix_get (r, i, k); double rij = gsl_matrix_get (r, i, j); gsl_matrix_set (r, i, k, rik - t * rij); } } kmax = k; } /* Form the full upper triangle of the inverse of R^T R in the full upper triangle of R */ for (k = 0; k <= kmax ; k++) { for (j = 0; j < k; j++) { double rjk = gsl_matrix_get (r, j, k); for (i = 0; i <= j ; i++) { double rij = gsl_matrix_get (r, i, j); double rik = gsl_matrix_get (r, i, k); gsl_matrix_set (r, i, j, rij + rjk * rik); } } { double t = gsl_matrix_get (r, k, k); for (i = 0; i <= k; i++) { double rik = gsl_matrix_get (r, i, k); gsl_matrix_set (r, i, k, t * rik); }; } } /* Form the full lower triangle of the covariance matrix in the strict lower triangle of R and in w */ for (j = 0 ; j < n ; j++) { size_t pj = gsl_permutation_get (perm, j); for (i = 0; i <= j; i++) { size_t pi = gsl_permutation_get (perm, i); double rij; if (j > kmax) { gsl_matrix_set (r, i, j, 0.0); rij = 0.0 ; } else { rij = gsl_matrix_get (r, i, j); } if (pi > pj) { gsl_matrix_set (r, pi, pj, rij); } else if (pi < pj) { gsl_matrix_set (r, pj, pi, rij); } } { double rjj = gsl_matrix_get (r, j, j); gsl_matrix_set (covar, pj, pj, rjj); } } /* symmetrize the covariance matrix */ for (j = 0 ; j < n ; j++) { for (i = 0; i < j ; i++) { double rji = gsl_matrix_get (r, j, i); gsl_matrix_set (covar, j, i, rji); gsl_matrix_set (covar, i, j, rji); } } gsl_matrix_free (r); gsl_permutation_free (perm); gsl_vector_free (tau); gsl_vector_free (norm); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_statistics__kurtosis.c0000664000176700017670000000306211723710247021646 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__kurtosis_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_cblas__dznrm2.c0000664000176700017670000000032711723710247020072 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" double cblas_dznrm2 (const int N, const void *X, const int incX) { #define BASE double #include "gsl_cblas__source_nrm2_c.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__hyperg_1F1.c0000664000176700017670000017037211723710247021315 0ustar paulpaul/* specfunc/hyperg_1F1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_elementary.h" #include "gsl_sf_exp.h" #include "gsl_sf_bessel.h" #include "gsl_sf_gamma.h" #include "gsl_sf_laguerre.h" #include "gsl_sf_hyperg.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__hyperg.h" #define _1F1_INT_THRESHOLD (100.0*GSL_DBL_EPSILON) /* Asymptotic result for 1F1(a, b, x) x -> -Infinity. * Assumes b-a != neg integer and b != neg integer. */ static int hyperg_1F1_asymp_negx(const double a, const double b, const double x, gsl_sf_result * result) { gsl_sf_result lg_b; gsl_sf_result lg_bma; double sgn_b; double sgn_bma; int stat_b = gsl_sf_lngamma_sgn_e(b, &lg_b, &sgn_b); int stat_bma = gsl_sf_lngamma_sgn_e(b-a, &lg_bma, &sgn_bma); if(stat_b == GSL_SUCCESS && stat_bma == GSL_SUCCESS) { gsl_sf_result F; int stat_F = gsl_sf_hyperg_2F0_series_e(a, 1.0+a-b, -1.0/x, -1, &F); if(F.val != 0) { double ln_term_val = a*log(-x); double ln_term_err = 2.0 * GSL_DBL_EPSILON * (fabs(a) + fabs(ln_term_val)); double ln_pre_val = lg_b.val - lg_bma.val - ln_term_val; double ln_pre_err = lg_b.err + lg_bma.err + ln_term_err; int stat_e = gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, sgn_bma*sgn_b*F.val, F.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_F); } else { result->val = 0.0; result->err = 0.0; return stat_F; } } else { DOMAIN_ERROR(result); } } /* Asymptotic result for 1F1(a, b, x) x -> +Infinity * Assumes b != neg integer and a != neg integer */ static int hyperg_1F1_asymp_posx(const double a, const double b, const double x, gsl_sf_result * result) { gsl_sf_result lg_b; gsl_sf_result lg_a; double sgn_b; double sgn_a; int stat_b = gsl_sf_lngamma_sgn_e(b, &lg_b, &sgn_b); int stat_a = gsl_sf_lngamma_sgn_e(a, &lg_a, &sgn_a); if(stat_a == GSL_SUCCESS && stat_b == GSL_SUCCESS) { gsl_sf_result F; int stat_F = gsl_sf_hyperg_2F0_series_e(b-a, 1.0-a, 1.0/x, -1, &F); if(stat_F == GSL_SUCCESS && F.val != 0) { double lnx = log(x); double ln_term_val = (a-b)*lnx; double ln_term_err = 2.0 * GSL_DBL_EPSILON * (fabs(a) + fabs(b)) * fabs(lnx) + 2.0 * GSL_DBL_EPSILON * fabs(a-b); double ln_pre_val = lg_b.val - lg_a.val + ln_term_val + x; double ln_pre_err = lg_b.err + lg_a.err + ln_term_err + 2.0 * GSL_DBL_EPSILON * fabs(x); int stat_e = gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, sgn_a*sgn_b*F.val, F.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_F); } else { result->val = 0.0; result->err = 0.0; return stat_F; } } else { DOMAIN_ERROR(result); } } /* Asymptotic result from Slater 4.3.7 * * To get the general series, write M(a,b,x) as * * M(a,b,x)=sum ((a)_n/(b)_n) (x^n / n!) * * and expand (b)_n in inverse powers of b as follows * * -log(1/(b)_n) = sum_(k=0)^(n-1) log(b+k) * = n log(b) + sum_(k=0)^(n-1) log(1+k/b) * * Do a taylor expansion of the log in 1/b and sum the resulting terms * using the standard algebraic formulas for finite sums of powers of * k. This should then give * * M(a,b,x) = sum_(n=0)^(inf) (a_n/n!) (x/b)^n * (1 - n(n-1)/(2b) * + (n-1)n(n+1)(3n-2)/(24b^2) + ... * * which can be summed explicitly. The trick for summing it is to take * derivatives of sum_(i=0)^(inf) a_n*y^n/n! = (1-y)^(-a); * * [BJG 16/01/2007] */ static int hyperg_1F1_largebx(const double a, const double b, const double x, gsl_sf_result * result) { double y = x/b; double f = exp(-a*log1p(-y)); double t1 = -((a*(a+1.0))/(2*b))*pow((y/(1.0-y)),2.0); double t2 = (1/(24*b*b))*((a*(a+1)*y*y)/pow(1-y,4))*(12+8*(2*a+1)*y+(3*a*a-a-2)*y*y); double t3 = (-1/(48*b*b*b*pow(1-y,6)))*a*((a + 1)*((y*((a + 1)*(a*(y*(y*((y*(a - 2) + 16)*(a - 1)) + 72)) + 96)) + 24)*pow(y, 2))); result->val = f * (1 + t1 + t2 + t3); result->err = 2*fabs(f*t3) + 2*GSL_DBL_EPSILON*fabs(result->val); return GSL_SUCCESS; } /* Asymptotic result for x < 2b-4a, 2b-4a large. * [Abramowitz+Stegun, 13.5.21] * * assumes 0 <= x/(2b-4a) <= 1 */ static int hyperg_1F1_large2bm4a(const double a, const double b, const double x, gsl_sf_result * result) { double eta = 2.0*b - 4.0*a; double cos2th = x/eta; double sin2th = 1.0 - cos2th; double th = acos(sqrt(cos2th)); double pre_h = 0.25*M_PI*M_PI*eta*eta*cos2th*sin2th; gsl_sf_result lg_b; int stat_lg = gsl_sf_lngamma_e(b, &lg_b); double t1 = 0.5*(1.0-b)*log(0.25*x*eta); double t2 = 0.25*log(pre_h); double lnpre_val = lg_b.val + 0.5*x + t1 - t2; double lnpre_err = lg_b.err + 2.0 * GSL_DBL_EPSILON * (fabs(0.5*x) + fabs(t1) + fabs(t2)); #if SMALL_ANGLE const double eps = asin(sqrt(cos2th)); /* theta = pi/2 - eps */ double s1 = (fmod(a, 1.0) == 0.0) ? 0.0 : sin(a*M_PI); double eta_reduc = (fmod(eta + 1, 4.0) == 0.0) ? 0.0 : fmod(eta + 1, 8.0); double phi1 = 0.25*eta_reduc*M_PI; double phi2 = 0.25*eta*(2*eps + sin(2.0*eps)); double s2 = sin(phi1 - phi2); #else double s1 = sin(a*M_PI); double s2 = sin(0.25*eta*(2.0*th - sin(2.0*th)) + 0.25*M_PI); #endif double ser_val = s1 + s2; double ser_err = 2.0 * GSL_DBL_EPSILON * (fabs(s1) + fabs(s2)); int stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, ser_val, ser_err, result); return GSL_ERROR_SELECT_2(stat_e, stat_lg); } /* Luke's rational approximation. * See [Luke, Algorithms for the Computation of Mathematical Functions, p.182] * * Like the case of the 2F1 rational approximations, these are * probably guaranteed to converge for x < 0, barring gross * numerical instability in the pre-asymptotic regime. */ static int hyperg_1F1_luke(const double a, const double c, const double xin, gsl_sf_result * result) { const double RECUR_BIG = 1.0e+50; const int nmax = 5000; int n = 3; const double x = -xin; const double x3 = x*x*x; const double t0 = a/c; const double t1 = (a+1.0)/(2.0*c); const double t2 = (a+2.0)/(2.0*(c+1.0)); double F = 1.0; double prec; double Bnm3 = 1.0; /* B0 */ double Bnm2 = 1.0 + t1 * x; /* B1 */ double Bnm1 = 1.0 + t2 * x * (1.0 + t1/3.0 * x); /* B2 */ double Anm3 = 1.0; /* A0 */ double Anm2 = Bnm2 - t0 * x; /* A1 */ double Anm1 = Bnm1 - t0*(1.0 + t2*x)*x + t0 * t1 * (c/(c+1.0)) * x*x; /* A2 */ while(1) { double npam1 = n + a - 1; double npcm1 = n + c - 1; double npam2 = n + a - 2; double npcm2 = n + c - 2; double tnm1 = 2*n - 1; double tnm3 = 2*n - 3; double tnm5 = 2*n - 5; double F1 = (n-a-2) / (2*tnm3*npcm1); double F2 = (n+a)*npam1 / (4*tnm1*tnm3*npcm2*npcm1); double F3 = -npam2*npam1*(n-a-2) / (8*tnm3*tnm3*tnm5*(n+c-3)*npcm2*npcm1); double E = -npam1*(n-c-1) / (2*tnm3*npcm2*npcm1); double An = (1.0+F1*x)*Anm1 + (E + F2*x)*x*Anm2 + F3*x3*Anm3; double Bn = (1.0+F1*x)*Bnm1 + (E + F2*x)*x*Bnm2 + F3*x3*Bnm3; double r = An/Bn; prec = fabs((F - r)/F); F = r; if(prec < GSL_DBL_EPSILON || n > nmax) break; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; Anm3 /= RECUR_BIG; Bnm3 /= RECUR_BIG; } else if(fabs(An) < 1.0/RECUR_BIG || fabs(Bn) < 1.0/RECUR_BIG) { An *= RECUR_BIG; Bn *= RECUR_BIG; Anm1 *= RECUR_BIG; Bnm1 *= RECUR_BIG; Anm2 *= RECUR_BIG; Bnm2 *= RECUR_BIG; Anm3 *= RECUR_BIG; Bnm3 *= RECUR_BIG; } n++; Bnm3 = Bnm2; Bnm2 = Bnm1; Bnm1 = Bn; Anm3 = Anm2; Anm2 = Anm1; Anm1 = An; } result->val = F; result->err = 2.0 * fabs(F * prec); result->err += 2.0 * GSL_DBL_EPSILON * (n-1.0) * fabs(F); return GSL_SUCCESS; } /* Series for 1F1(1,b,x) * b > 0 */ static int hyperg_1F1_1_series(const double b, const double x, gsl_sf_result * result) { double sum_val = 1.0; double sum_err = 0.0; double term = 1.0; double n = 1.0; while(fabs(term/sum_val) > 0.25*GSL_DBL_EPSILON) { term *= x/(b+n-1); sum_val += term; sum_err += 8.0*GSL_DBL_EPSILON*fabs(term) + GSL_DBL_EPSILON*fabs(sum_val); n += 1.0; } result->val = sum_val; result->err = sum_err; result->err += 2.0 * fabs(term); return GSL_SUCCESS; } /* 1F1(1,b,x) * b >= 1, b integer */ static int hyperg_1F1_1_int(const int b, const double x, gsl_sf_result * result) { if(b < 1) { DOMAIN_ERROR(result); } else if(b == 1) { return gsl_sf_exp_e(x, result); } else if(b == 2) { return gsl_sf_exprel_e(x, result); } else if(b == 3) { return gsl_sf_exprel_2_e(x, result); } else { return gsl_sf_exprel_n_e(b-1, x, result); } } /* 1F1(1,b,x) * b >=1, b real * * checked OK: [GJ] Thu Oct 1 16:46:35 MDT 1998 */ static int hyperg_1F1_1(const double b, const double x, gsl_sf_result * result) { double ax = fabs(x); double ib = floor(b + 0.1); if(b < 1.0) { DOMAIN_ERROR(result); } else if(b == 1.0) { return gsl_sf_exp_e(x, result); } else if(b >= 1.4*ax) { return hyperg_1F1_1_series(b, x, result); } else if(fabs(b - ib) < _1F1_INT_THRESHOLD && ib < INT_MAX) { return hyperg_1F1_1_int((int)ib, x, result); } else if(x > 0.0) { if(x > 100.0 && b < 0.75*x) { return hyperg_1F1_asymp_posx(1.0, b, x, result); } else if(b < 1.0e+05) { /* Recurse backward on b, from a * chosen offset point. For x > 0, * which holds here, this should * be a stable direction. */ const double off = ceil(1.4*x-b) + 1.0; double bp = b + off; gsl_sf_result M; int stat_s = hyperg_1F1_1_series(bp, x, &M); const double err_rat = M.err / fabs(M.val); while(bp > b+0.1) { /* M(1,b-1) = x/(b-1) M(1,b) + 1 */ bp -= 1.0; M.val = 1.0 + x/bp * M.val; } result->val = M.val; result->err = err_rat * fabs(M.val); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(off)+1.0) * fabs(M.val); return stat_s; } else if (fabs(x) < fabs(b) && fabs(x) < sqrt(fabs(b)) * fabs(b-x)) { return hyperg_1F1_largebx(1.0, b, x, result); } else if (fabs(x) > fabs(b)) { return hyperg_1F1_1_series(b, x, result); } else { return hyperg_1F1_large2bm4a(1.0, b, x, result); } } else { /* x <= 0 and b not large compared to |x| */ if(ax < 10.0 && b < 10.0) { return hyperg_1F1_1_series(b, x, result); } else if(ax >= 100.0 && GSL_MAX_DBL(fabs(2.0-b),1.0) < 0.99*ax) { return hyperg_1F1_asymp_negx(1.0, b, x, result); } else { return hyperg_1F1_luke(1.0, b, x, result); } } } /* 1F1(a,b,x)/Gamma(b) for b->0 * [limit of Abramowitz+Stegun 13.3.7] */ static int hyperg_1F1_renorm_b0(const double a, const double x, gsl_sf_result * result) { double eta = a*x; if(eta > 0.0) { double root_eta = sqrt(eta); gsl_sf_result I1_scaled; int stat_I = gsl_sf_bessel_I1_scaled_e(2.0*root_eta, &I1_scaled); if(I1_scaled.val <= 0.0) { result->val = 0.0; result->err = 0.0; return GSL_ERROR_SELECT_2(stat_I, GSL_EDOM); } else { /* Note that 13.3.7 contains higher terms which are zeroth order in b. These make a non-negligible contribution to the sum. With the first correction term, the I1 above is replaced by I1 + (2/3)*a*(x/(4a))**(3/2)*I2(2*root_eta). We will add this as part of the result and error estimate. */ const double corr1 =(2.0/3.0)*a*pow(x/(4.0*a),1.5)*gsl_sf_bessel_In_scaled(2, 2.0*root_eta) ; const double lnr_val = 0.5*x + 0.5*log(eta) + fabs(2.0*root_eta) + log(I1_scaled.val+corr1); const double lnr_err = GSL_DBL_EPSILON * (1.5*fabs(x) + 1.0) + fabs((I1_scaled.err+corr1)/I1_scaled.val); return gsl_sf_exp_err_e(lnr_val, lnr_err, result); } } else if(eta == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* eta < 0 */ double root_eta = sqrt(-eta); gsl_sf_result J1; int stat_J = gsl_sf_bessel_J1_e(2.0*root_eta, &J1); if(J1.val <= 0.0) { result->val = 0.0; result->err = 0.0; return GSL_ERROR_SELECT_2(stat_J, GSL_EDOM); } else { const double t1 = 0.5*x; const double t2 = 0.5*log(-eta); const double t3 = fabs(x); const double t4 = log(J1.val); const double lnr_val = t1 + t2 + t3 + t4; const double lnr_err = GSL_DBL_EPSILON * (1.5*fabs(x) + 1.0) + fabs(J1.err/J1.val); gsl_sf_result ex; int stat_e = gsl_sf_exp_err_e(lnr_val, lnr_err, &ex); result->val = -ex.val; result->err = ex.err; return stat_e; } } } /* 1F1'(a,b,x)/1F1(a,b,x) * Uses Gautschi's version of the CF. * [Gautschi, Math. Comp. 31, 994 (1977)] * * Supposedly this suffers from the "anomalous convergence" * problem when b < x. I have seen anomalous convergence * in several of the continued fractions associated with * 1F1(a,b,x). This particular CF formulation seems stable * for b > x. However, it does display a painful artifact * of the anomalous convergence; the convergence plateaus * unless b >>> x. For example, even for b=1000, x=1, this * method locks onto a ratio which is only good to about * 4 digits. Apparently the rest of the digits are hiding * way out on the plateau, but finite-precision lossage * means you will never get them. */ #if 0 static int hyperg_1F1_CF1_p(const double a, const double b, const double x, double * result) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 5000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = 1.0; double b1 = 1.0; double An = b1*Anm1 + a1*Anm2; double Bn = b1*Bnm1 + a1*Bnm2; double an, bn; double fn = An/Bn; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = (a+n)*x/((b-x+n-1)*(b-x+n)); bn = 1.0; An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 10.0*GSL_DBL_EPSILON) break; } *result = a/(b-x) * fn; if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } #endif /* 0 */ /* 1F1'(a,b,x)/1F1(a,b,x) * Uses Gautschi's series transformation of the * continued fraction. This is apparently the best * method for getting this ratio in the stable region. * The convergence is monotone and supergeometric * when b > x. * Assumes a >= -1. */ static int hyperg_1F1_CF1_p_ser(const double a, const double b, const double x, double * result) { if(a == 0.0) { *result = 0.0; return GSL_SUCCESS; } else { const int maxiter = 5000; double sum = 1.0; double pk = 1.0; double rhok = 0.0; int k; for(k=1; k RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 10.0*GSL_DBL_EPSILON) break; } *result = fn; if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } #endif /* 0 */ /* 1F1(a,b+1,x)/1F1(a,b,x) * * This seemed to suffer from "anomalous convergence". * However, I have no theory for this recurrence. */ #if 0 static int hyperg_1F1_CF1_b(const double a, const double b, const double x, double * result) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 5000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = b + 1.0; double b1 = (b + 1.0) * (b - x); double An = b1*Anm1 + a1*Anm2; double Bn = b1*Bnm1 + a1*Bnm2; double an, bn; double fn = An/Bn; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = (b + n) * (b + n - 1.0 - a) * x; bn = (b + n) * (b + n - 1.0 - x); An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 10.0*GSL_DBL_EPSILON) break; } *result = fn; if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } #endif /* 0 */ /* 1F1(a,b,x) * |a| <= 1, b > 0 */ static int hyperg_1F1_small_a_bgt0(const double a, const double b, const double x, gsl_sf_result * result) { const double bma = b-a; const double oma = 1.0-a; const double ap1mb = 1.0+a-b; const double abs_bma = fabs(bma); const double abs_oma = fabs(oma); const double abs_ap1mb = fabs(ap1mb); const double ax = fabs(x); if(a == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(a == 1.0 && b >= 1.0) { return hyperg_1F1_1(b, x, result); } else if(a == -1.0) { result->val = 1.0 + a/b * x; result->err = GSL_DBL_EPSILON * (1.0 + fabs(a/b * x)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(b >= 1.4*ax) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if(x > 0.0) { if(x > 100.0 && abs_bma*abs_oma < 0.5*x) { return hyperg_1F1_asymp_posx(a, b, x, result); } else if(b < 5.0e+06) { /* Recurse backward on b from * a suitably high point. */ const double b_del = ceil(1.4*x-b) + 1.0; double bp = b + b_del; gsl_sf_result r_Mbp1; gsl_sf_result r_Mb; double Mbp1; double Mb; double Mbm1; int stat_0 = gsl_sf_hyperg_1F1_series_e(a, bp+1.0, x, &r_Mbp1); int stat_1 = gsl_sf_hyperg_1F1_series_e(a, bp, x, &r_Mb); const double err_rat = fabs(r_Mbp1.err/r_Mbp1.val) + fabs(r_Mb.err/r_Mb.val); Mbp1 = r_Mbp1.val; Mb = r_Mb.val; while(bp > b+0.1) { /* Do backward recursion. */ Mbm1 = ((x+bp-1.0)*Mb - x*(bp-a)/bp*Mbp1)/(bp-1.0); bp -= 1.0; Mbp1 = Mb; Mb = Mbm1; } result->val = Mb; result->err = err_rat * (fabs(b_del)+1.0) * fabs(Mb); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Mb); return GSL_ERROR_SELECT_2(stat_0, stat_1); } else if (fabs(x) < fabs(b) && fabs(a*x) < sqrt(fabs(b)) * fabs(b-x)) { return hyperg_1F1_largebx(a, b, x, result); } else { return hyperg_1F1_large2bm4a(a, b, x, result); } } else { /* x < 0 and b not large compared to |x| */ if(ax < 10.0 && b < 10.0) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if(ax >= 100.0 && GSL_MAX(abs_ap1mb,1.0) < 0.99*ax) { return hyperg_1F1_asymp_negx(a, b, x, result); } else { return hyperg_1F1_luke(a, b, x, result); } } } /* 1F1(b+eps,b,x) * |eps|<=1, b > 0 */ static int hyperg_1F1_beps_bgt0(const double eps, const double b, const double x, gsl_sf_result * result) { if(b > fabs(x) && fabs(eps) < GSL_SQRT_DBL_EPSILON) { /* If b-a is very small and x/b is not too large we can * use this explicit approximation. * * 1F1(b+eps,b,x) = exp(ax/b) (1 - eps x^2 (v2 + v3 x + ...) + ...) * * v2 = a/(2b^2(b+1)) * v3 = a(b-2a)/(3b^3(b+1)(b+2)) * ... * * See [Luke, Mathematical Functions and Their Approximations, p.292] * * This cannot be used for b near a negative integer or zero. * Also, if x/b is large the deviation from exp(x) behaviour grows. */ double a = b + eps; gsl_sf_result exab; int stat_e = gsl_sf_exp_e(a*x/b, &exab); double v2 = a/(2.0*b*b*(b+1.0)); double v3 = a*(b-2.0*a)/(3.0*b*b*b*(b+1.0)*(b+2.0)); double v = v2 + v3 * x; double f = (1.0 - eps*x*x*v); result->val = exab.val * f; result->err = exab.err * fabs(f); result->err += fabs(exab.val) * GSL_DBL_EPSILON * (1.0 + fabs(eps*x*x*v)); result->err += 4.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_e; } else { /* Otherwise use a Kummer transformation to reduce * it to the small a case. */ gsl_sf_result Kummer_1F1; int stat_K = hyperg_1F1_small_a_bgt0(-eps, b, -x, &Kummer_1F1); if(Kummer_1F1.val != 0.0) { int stat_e = gsl_sf_exp_mult_err_e(x, 2.0*GSL_DBL_EPSILON*fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else { result->val = 0.0; result->err = 0.0; return stat_K; } } } /* 1F1(a,2a,x) = Gamma(a + 1/2) E(x) (|x|/4)^(-a+1/2) scaled_I(a-1/2,|x|/2) * * E(x) = exp(x) x > 0 * = 1 x < 0 * * a >= 1/2 */ static int hyperg_1F1_beq2a_pos(const double a, const double x, gsl_sf_result * result) { if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result I; int stat_I = gsl_sf_bessel_Inu_scaled_e(a-0.5, 0.5*fabs(x), &I); gsl_sf_result lg; int stat_g = gsl_sf_lngamma_e(a + 0.5, &lg); double ln_term = (0.5-a)*log(0.25*fabs(x)); double lnpre_val = lg.val + GSL_MAX_DBL(x,0.0) + ln_term; double lnpre_err = lg.err + GSL_DBL_EPSILON * (fabs(ln_term) + fabs(x)); int stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, I.val, I.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_g, stat_I); } } /* Determine middle parts of diagonal recursion along b=2a * from two endpoints, i.e. * * given: M(a,b) and M(a+1,b+2) * get: M(a+1,b+1) and M(a,b+1) */ #if 0 inline static int hyperg_1F1_diag_step(const double a, const double b, const double x, const double Mab, const double Map1bp2, double * Map1bp1, double * Mabp1) { if(a == b) { *Map1bp1 = Mab; *Mabp1 = Mab - x/(b+1.0) * Map1bp2; } else { *Map1bp1 = Mab - x * (a-b)/(b*(b+1.0)) * Map1bp2; *Mabp1 = (a * *Map1bp1 - b * Mab)/(a-b); } return GSL_SUCCESS; } #endif /* 0 */ /* Determine endpoint of diagonal recursion. * * given: M(a,b) and M(a+1,b+2) * get: M(a+1,b) and M(a+1,b+1) */ #if 0 inline static int hyperg_1F1_diag_end_step(const double a, const double b, const double x, const double Mab, const double Map1bp2, double * Map1b, double * Map1bp1) { *Map1bp1 = Mab - x * (a-b)/(b*(b+1.0)) * Map1bp2; *Map1b = Mab + x/b * *Map1bp1; return GSL_SUCCESS; } #endif /* 0 */ /* Handle the case of a and b both positive integers. * Assumes a > 0 and b > 0. */ static int hyperg_1F1_ab_posint(const int a, const int b, const double x, gsl_sf_result * result) { double ax = fabs(x); if(a == b) { return gsl_sf_exp_e(x, result); /* 1F1(a,a,x) */ } else if(a == 1) { return gsl_sf_exprel_n_e(b-1, x, result); /* 1F1(1,b,x) */ } else if(b == a + 1) { gsl_sf_result K; int stat_K = gsl_sf_exprel_n_e(a, -x, &K); /* 1F1(1,1+a,-x) */ int stat_e = gsl_sf_exp_mult_err_e(x, 2.0 * GSL_DBL_EPSILON * fabs(x), K.val, K.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if(a == b + 1) { gsl_sf_result ex; int stat_e = gsl_sf_exp_e(x, &ex); result->val = ex.val * (1.0 + x/b); result->err = ex.err * (1.0 + x/b); result->err += ex.val * GSL_DBL_EPSILON * (1.0 + fabs(x/b)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_e; } else if(a == b + 2) { gsl_sf_result ex; int stat_e = gsl_sf_exp_e(x, &ex); double poly = (1.0 + x/b*(2.0 + x/(b+1.0))); result->val = ex.val * poly; result->err = ex.err * fabs(poly); result->err += ex.val * GSL_DBL_EPSILON * (1.0 + fabs(x/b) * (2.0 + fabs(x/(b+1.0)))); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_e; } else if(b == 2*a) { return hyperg_1F1_beq2a_pos(a, x, result); /* 1F1(a,2a,x) */ } else if( ( b < 10 && a < 10 && ax < 5.0 ) || ( b > a*ax ) || ( b > a && ax < 5.0 ) ) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if(b > a && b >= 2*a + x) { /* Use the Gautschi CF series, then * recurse backward to a=0 for normalization. * This will work for either sign of x. */ double rap; int stat_CF1 = hyperg_1F1_CF1_p_ser(a, b, x, &rap); double ra = 1.0 + x/a * rap; double Ma = GSL_SQRT_DBL_MIN; double Map1 = ra * Ma; double Mnp1 = Map1; double Mn = Ma; double Mnm1; int n; for(n=a; n>0; n--) { Mnm1 = (n * Mnp1 - (2*n-b+x) * Mn) / (b-n); Mnp1 = Mn; Mn = Mnm1; } result->val = Ma/Mn; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(a) + 1.0) * fabs(Ma/Mn); return stat_CF1; } else if(b > a && b < 2*a + x && b > x) { /* Use the Gautschi series representation of * the continued fraction. Then recurse forward * to the a=b line for normalization. This will * work for either sign of x, although we do need * to check for b > x, for when x is positive. */ double rap; int stat_CF1 = hyperg_1F1_CF1_p_ser(a, b, x, &rap); double ra = 1.0 + x/a * rap; gsl_sf_result ex; int stat_ex; double Ma = GSL_SQRT_DBL_MIN; double Map1 = ra * Ma; double Mnm1 = Ma; double Mn = Map1; double Mnp1; int n; for(n=a+1; nval = ex.val * Ma/Mn; result->err = ex.err * fabs(Ma/Mn); result->err += 4.0 * GSL_DBL_EPSILON * (fabs(b-a)+1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_ex, stat_CF1); } else if(x >= 0.0) { if(b < a) { /* The point b,b is below the b=2a+x line. * Forward recursion on a from b,b+1 is possible. * Note that a > b + 1 as well, since we already tried a = b + 1. */ if(x + log(fabs(x/b)) < GSL_LOG_DBL_MAX-2.0) { double ex = exp(x); int n; double Mnm1 = ex; /* 1F1(b,b,x) */ double Mn = ex * (1.0 + x/b); /* 1F1(b+1,b,x) */ double Mnp1; for(n=b+1; nval = Mn; result->err = (x + 1.0) * GSL_DBL_EPSILON * fabs(Mn); result->err *= fabs(a-b)+1.0; return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } else { /* b > a * b < 2a + x * b <= x (otherwise we would have finished above) * * Gautschi anomalous convergence region. However, we can * recurse forward all the way from a=0,1 because we are * always underneath the b=2a+x line. */ gsl_sf_result r_Mn; double Mnm1 = 1.0; /* 1F1(0,b,x) */ double Mn; /* 1F1(1,b,x) */ double Mnp1; int n; gsl_sf_exprel_n_e(b-1, x, &r_Mn); Mn = r_Mn.val; for(n=1; nval = Mn; result->err = fabs(Mn) * (1.0 + fabs(a)) * fabs(r_Mn.err / r_Mn.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Mn); return GSL_SUCCESS; } } else { /* x < 0 * b < a (otherwise we would have tripped one of the above) */ if(a <= 0.5*(b-x) || a >= -x) { /* Gautschi continued fraction is in the anomalous region, * so we must find another way. We recurse down in b, * from the a=b line. */ double ex = exp(x); double Manp1 = ex; double Man = ex * (1.0 + x/(a-1.0)); double Manm1; int n; for(n=a-1; n>b; n--) { Manm1 = (-n*(1-n-x)*Man - x*(n-a)*Manp1)/(n*(n-1.0)); Manp1 = Man; Man = Manm1; } result->val = Man; result->err = (fabs(x) + 1.0) * GSL_DBL_EPSILON * fabs(Man); result->err *= fabs(b-a)+1.0; return GSL_SUCCESS; } else { /* Pick a0 such that b ~= 2a0 + x, then * recurse down in b from a0,a0 to determine * the values near the line b=2a+x. Then recurse * forward on a from a0. */ int a0 = ceil(0.5*(b-x)); double Ma0b; /* M(a0,b) */ double Ma0bp1; /* M(a0,b+1) */ double Ma0p1b; /* M(a0+1,b) */ double Mnm1; double Mn; double Mnp1; int n; { double ex = exp(x); double Ma0np1 = ex; double Ma0n = ex * (1.0 + x/(a0-1.0)); double Ma0nm1; for(n=a0-1; n>b; n--) { Ma0nm1 = (-n*(1-n-x)*Ma0n - x*(n-a0)*Ma0np1)/(n*(n-1.0)); Ma0np1 = Ma0n; Ma0n = Ma0nm1; } Ma0bp1 = Ma0np1; Ma0b = Ma0n; Ma0p1b = (b*(a0+x)*Ma0b + x*(a0-b)*Ma0bp1)/(a0*b); } /* Initialise the recurrence correctly BJG */ if (a0 >= a) { Mn = Ma0b; } else if (a0 + 1>= a) { Mn = Ma0p1b; } else { Mnm1 = Ma0b; Mn = Ma0p1b; for(n=a0+1; nval = Mn; result->err = (fabs(x) + 1.0) * GSL_DBL_EPSILON * fabs(Mn); result->err *= fabs(b-a)+1.0; return GSL_SUCCESS; } } } /* Evaluate a <= 0, a integer, cases directly. (Polynomial; Horner) * When the terms are all positive, this * must work. We will assume this here. */ static int hyperg_1F1_a_negint_poly(const int a, const double b, const double x, gsl_sf_result * result) { if(a == 0) { result->val = 1.0; result->err = 1.0; return GSL_SUCCESS; } else { int N = -a; double poly = 1.0; int k; for(k=N-1; k>=0; k--) { double t = (a+k)/(b+k) * (x/(k+1)); double r = t + 1.0/poly; if(r > 0.9*GSL_DBL_MAX/poly) { OVERFLOW_ERROR(result); } else { poly *= r; /* P_n = 1 + t_n P_{n-1} */ } } result->val = poly; result->err = 2.0 * (sqrt(N) + 1.0) * GSL_DBL_EPSILON * fabs(poly); return GSL_SUCCESS; } } /* Evaluate negative integer a case by relation * to Laguerre polynomials. This is more general than * the direct polynomial evaluation, but is safe * for all values of x. * * 1F1(-n,b,x) = n!/(b)_n Laguerre[n,b-1,x] * = n B(b,n) Laguerre[n,b-1,x] * * assumes b is not a negative integer */ static int hyperg_1F1_a_negint_lag(const int a, const double b, const double x, gsl_sf_result * result) { const int n = -a; gsl_sf_result lag; const int stat_l = gsl_sf_laguerre_n_e(n, b-1.0, x, &lag); if(b < 0.0) { gsl_sf_result lnfact; gsl_sf_result lng1; gsl_sf_result lng2; double s1, s2; const int stat_f = gsl_sf_lnfact_e(n, &lnfact); const int stat_g1 = gsl_sf_lngamma_sgn_e(b + n, &lng1, &s1); const int stat_g2 = gsl_sf_lngamma_sgn_e(b, &lng2, &s2); const double lnpre_val = lnfact.val - (lng1.val - lng2.val); const double lnpre_err = lnfact.err + lng1.err + lng2.err + 2.0 * GSL_DBL_EPSILON * fabs(lnpre_val); const int stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, s1*s2*lag.val, lag.err, result); return GSL_ERROR_SELECT_5(stat_e, stat_l, stat_g1, stat_g2, stat_f); } else { gsl_sf_result lnbeta; gsl_sf_lnbeta_e(b, n, &lnbeta); if(fabs(lnbeta.val) < 0.1) { /* As we have noted, when B(x,y) is near 1, * evaluating log(B(x,y)) is not accurate. * Instead we evaluate B(x,y) directly. */ const double ln_term_val = log(1.25*n); const double ln_term_err = 2.0 * GSL_DBL_EPSILON * ln_term_val; gsl_sf_result beta; int stat_b = gsl_sf_beta_e(b, n, &beta); int stat_e = gsl_sf_exp_mult_err_e(ln_term_val, ln_term_err, lag.val, lag.err, result); result->val *= beta.val/1.25; result->err *= beta.val/1.25; return GSL_ERROR_SELECT_3(stat_e, stat_l, stat_b); } else { /* B(x,y) was not near 1, so it is safe to use * the logarithmic values. */ const double ln_n = log(n); const double ln_term_val = lnbeta.val + ln_n; const double ln_term_err = lnbeta.err + 2.0 * GSL_DBL_EPSILON * fabs(ln_n); int stat_e = gsl_sf_exp_mult_err_e(ln_term_val, ln_term_err, lag.val, lag.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_l); } } } /* Handle negative integer a case for x > 0 and * generic b. * * Combine [Abramowitz+Stegun, 13.6.9 + 13.6.27] * M(-n,b,x) = (-1)^n / (b)_n U(-n,b,x) = n! / (b)_n Laguerre^(b-1)_n(x) */ #if 0 static int hyperg_1F1_a_negint_U(const int a, const double b, const double x, gsl_sf_result * result) { const int n = -a; const double sgn = ( GSL_IS_ODD(n) ? -1.0 : 1.0 ); double sgpoch; gsl_sf_result lnpoch; gsl_sf_result U; const int stat_p = gsl_sf_lnpoch_sgn_e(b, n, &lnpoch, &sgpoch); const int stat_U = gsl_sf_hyperg_U_e(-n, b, x, &U); const int stat_e = gsl_sf_exp_mult_err_e(-lnpoch.val, lnpoch.err, sgn * sgpoch * U.val, U.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_U, stat_p); } #endif /* Assumes a <= -1, b <= -1, and b <= a. */ static int hyperg_1F1_ab_negint(const int a, const int b, const double x, gsl_sf_result * result) { if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(x > 0.0) { return hyperg_1F1_a_negint_poly(a, b, x, result); } else { /* Apply a Kummer transformation to make x > 0 so * we can evaluate the polynomial safely. Of course, * this assumes b <= a, which must be true for * a<0 and b<0, since otherwise the thing is undefined. */ gsl_sf_result K; int stat_K = hyperg_1F1_a_negint_poly(b-a, b, -x, &K); int stat_e = gsl_sf_exp_mult_err_e(x, 2.0 * GSL_DBL_EPSILON * fabs(x), K.val, K.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } } /* [Abramowitz+Stegun, 13.1.3] * * M(a,b,x) = Gamma(1+a-b)/Gamma(2-b) x^(1-b) * * { Gamma(b)/Gamma(a) M(1+a-b,2-b,x) - (b-1) U(1+a-b,2-b,x) } * * b not an integer >= 2 * a-b not a negative integer */ static int hyperg_1F1_U(const double a, const double b, const double x, gsl_sf_result * result) { const double bp = 2.0 - b; const double ap = a - b + 1.0; gsl_sf_result lg_ap, lg_bp; double sg_ap; int stat_lg0 = gsl_sf_lngamma_sgn_e(ap, &lg_ap, &sg_ap); int stat_lg1 = gsl_sf_lngamma_e(bp, &lg_bp); int stat_lg2 = GSL_ERROR_SELECT_2(stat_lg0, stat_lg1); double t1 = (bp-1.0) * log(x); double lnpre_val = lg_ap.val - lg_bp.val + t1; double lnpre_err = lg_ap.err + lg_bp.err + 2.0 * GSL_DBL_EPSILON * fabs(t1); gsl_sf_result lg_2mbp, lg_1papmbp; double sg_2mbp, sg_1papmbp; int stat_lg3 = gsl_sf_lngamma_sgn_e(2.0-bp, &lg_2mbp, &sg_2mbp); int stat_lg4 = gsl_sf_lngamma_sgn_e(1.0+ap-bp, &lg_1papmbp, &sg_1papmbp); int stat_lg5 = GSL_ERROR_SELECT_2(stat_lg3, stat_lg4); double lnc1_val = lg_2mbp.val - lg_1papmbp.val; double lnc1_err = lg_2mbp.err + lg_1papmbp.err + GSL_DBL_EPSILON * (fabs(lg_2mbp.val) + fabs(lg_1papmbp.val)); gsl_sf_result M; gsl_sf_result_e10 U; int stat_F = gsl_sf_hyperg_1F1_e(ap, bp, x, &M); int stat_U = gsl_sf_hyperg_U_e10_e(ap, bp, x, &U); int stat_FU = GSL_ERROR_SELECT_2(stat_F, stat_U); gsl_sf_result_e10 term_M; int stat_e0 = gsl_sf_exp_mult_err_e10_e(lnc1_val, lnc1_err, sg_2mbp*sg_1papmbp*M.val, M.err, &term_M); const double ombp = 1.0 - bp; const double Uee_val = U.e10*M_LN10; const double Uee_err = 2.0 * GSL_DBL_EPSILON * fabs(Uee_val); const double Mee_val = term_M.e10*M_LN10; const double Mee_err = 2.0 * GSL_DBL_EPSILON * fabs(Mee_val); int stat_e1; /* Do a little dance with the exponential prefactors * to avoid overflows in intermediate results. */ if(Uee_val > Mee_val) { const double factorM_val = exp(Mee_val-Uee_val); const double factorM_err = 2.0 * GSL_DBL_EPSILON * (fabs(Mee_val-Uee_val)+1.0) * factorM_val; const double inner_val = term_M.val*factorM_val - ombp*U.val; const double inner_err = term_M.err*factorM_val + fabs(ombp) * U.err + fabs(term_M.val) * factorM_err + GSL_DBL_EPSILON * (fabs(term_M.val*factorM_val) + fabs(ombp*U.val)); stat_e1 = gsl_sf_exp_mult_err_e(lnpre_val+Uee_val, lnpre_err+Uee_err, sg_ap*inner_val, inner_err, result); } else { const double factorU_val = exp(Uee_val - Mee_val); const double factorU_err = 2.0 * GSL_DBL_EPSILON * (fabs(Mee_val-Uee_val)+1.0) * factorU_val; const double inner_val = term_M.val - ombp*factorU_val*U.val; const double inner_err = term_M.err + fabs(ombp*factorU_val*U.err) + fabs(ombp*factorU_err*U.val) + GSL_DBL_EPSILON * (fabs(term_M.val) + fabs(ombp*factorU_val*U.val)); stat_e1 = gsl_sf_exp_mult_err_e(lnpre_val+Mee_val, lnpre_err+Mee_err, sg_ap*inner_val, inner_err, result); } return GSL_ERROR_SELECT_5(stat_e1, stat_e0, stat_FU, stat_lg5, stat_lg2); } /* Handle case of generic positive a, b. * Assumes b-a is not a negative integer. */ static int hyperg_1F1_ab_pos(const double a, const double b, const double x, gsl_sf_result * result) { const double ax = fabs(x); if( ( b < 10.0 && a < 10.0 && ax < 5.0 ) || ( b > a*ax ) || ( b > a && ax < 5.0 ) ) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if( x < -100.0 && GSL_MAX_DBL(fabs(a),1.0)*GSL_MAX_DBL(fabs(1.0+a-b),1.0) < 0.7*fabs(x) ) { /* Large negative x asymptotic. */ return hyperg_1F1_asymp_negx(a, b, x, result); } else if( x > 100.0 && GSL_MAX_DBL(fabs(b-a),1.0)*GSL_MAX_DBL(fabs(1.0-a),1.0) < 0.7*fabs(x) ) { /* Large positive x asymptotic. */ return hyperg_1F1_asymp_posx(a, b, x, result); } else if(fabs(b-a) <= 1.0) { /* Directly handle b near a. */ return hyperg_1F1_beps_bgt0(a-b, b, x, result); /* a = b + eps */ } else if(b > a && b >= 2*a + x) { /* Use the Gautschi CF series, then * recurse backward to a near 0 for normalization. * This will work for either sign of x. */ double rap; int stat_CF1 = hyperg_1F1_CF1_p_ser(a, b, x, &rap); double ra = 1.0 + x/a * rap; double Ma = GSL_SQRT_DBL_MIN; double Map1 = ra * Ma; double Mnp1 = Map1; double Mn = Ma; double Mnm1; gsl_sf_result Mn_true; int stat_Mt; double n; for(n=a; n>0.5; n -= 1.0) { Mnm1 = (n * Mnp1 - (2.0*n-b+x) * Mn) / (b-n); Mnp1 = Mn; Mn = Mnm1; } stat_Mt = hyperg_1F1_small_a_bgt0(n, b, x, &Mn_true); result->val = (Ma/Mn) * Mn_true.val; result->err = fabs(Ma/Mn) * Mn_true.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(a)+1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Mt, stat_CF1); } else if(b > a && b < 2*a + x && b > x) { /* Use the Gautschi series representation of * the continued fraction. Then recurse forward * to near the a=b line for normalization. This will * work for either sign of x, although we do need * to check for b > x, which is relevant when x is positive. */ gsl_sf_result Mn_true; int stat_Mt; double rap; int stat_CF1 = hyperg_1F1_CF1_p_ser(a, b, x, &rap); double ra = 1.0 + x/a * rap; double Ma = GSL_SQRT_DBL_MIN; double Mnm1 = Ma; double Mn = ra * Mnm1; double Mnp1; double n; for(n=a+1.0; nval = Ma/Mn * Mn_true.val; result->err = fabs(Ma/Mn) * Mn_true.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(b-a)+1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Mt, stat_CF1); } else if(x >= 0.0) { if(b < a) { /* Forward recursion on a from a=b+eps-1,b+eps. */ double N = floor(a-b); double eps = a - b - N; gsl_sf_result r_M0; gsl_sf_result r_M1; int stat_0 = hyperg_1F1_beps_bgt0(eps-1.0, b, x, &r_M0); int stat_1 = hyperg_1F1_beps_bgt0(eps, b, x, &r_M1); double M0 = r_M0.val; double M1 = r_M1.val; double Mam1 = M0; double Ma = M1; double Map1; double ap; double start_pair = fabs(M0) + fabs(M1); double minim_pair = GSL_DBL_MAX; double pair_ratio; double rat_0 = fabs(r_M0.err/r_M0.val); double rat_1 = fabs(r_M1.err/r_M1.val); for(ap=b+eps; apval = Ma; result->err = 2.0 * (rat_0 + rat_1 + GSL_DBL_EPSILON) * (fabs(b-a)+1.0) * fabs(Ma); result->err += 2.0 * (rat_0 + rat_1) * pair_ratio*pair_ratio * fabs(Ma); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Ma); return GSL_ERROR_SELECT_2(stat_0, stat_1); } else { /* b > a * b < 2a + x * b <= x * * Recurse forward on a from a=eps,eps+1. */ double eps = a - floor(a); gsl_sf_result r_Mnm1; gsl_sf_result r_Mn; int stat_0 = hyperg_1F1_small_a_bgt0(eps, b, x, &r_Mnm1); int stat_1 = hyperg_1F1_small_a_bgt0(eps+1.0, b, x, &r_Mn); double Mnm1 = r_Mnm1.val; double Mn = r_Mn.val; double Mnp1; double n; double start_pair = fabs(Mn) + fabs(Mnm1); double minim_pair = GSL_DBL_MAX; double pair_ratio; double rat_0 = fabs(r_Mnm1.err/r_Mnm1.val); double rat_1 = fabs(r_Mn.err/r_Mn.val); for(n=eps+1.0; nval = Mn; result->err = 2.0 * (rat_0 + rat_1 + GSL_DBL_EPSILON) * (fabs(a)+1.0) * fabs(Mn); result->err += 2.0 * (rat_0 + rat_1) * pair_ratio*pair_ratio * fabs(Mn); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Mn); return GSL_ERROR_SELECT_2(stat_0, stat_1); } } else { /* x < 0 * b < a */ if(a <= 0.5*(b-x) || a >= -x) { /* Recurse down in b, from near the a=b line, b=a+eps,a+eps-1. */ double N = floor(a - b); double eps = 1.0 + N - a + b; gsl_sf_result r_Manp1; gsl_sf_result r_Man; int stat_0 = hyperg_1F1_beps_bgt0(-eps, a+eps, x, &r_Manp1); int stat_1 = hyperg_1F1_beps_bgt0(1.0-eps, a+eps-1.0, x, &r_Man); double Manp1 = r_Manp1.val; double Man = r_Man.val; double Manm1; double n; double start_pair = fabs(Manp1) + fabs(Man); double minim_pair = GSL_DBL_MAX; double pair_ratio; double rat_0 = fabs(r_Manp1.err/r_Manp1.val); double rat_1 = fabs(r_Man.err/r_Man.val); for(n=a+eps-1.0; n>b+0.1; n -= 1.0) { Manm1 = (-n*(1-n-x)*Man - x*(n-a)*Manp1)/(n*(n-1.0)); Manp1 = Man; Man = Manm1; minim_pair = GSL_MIN_DBL(fabs(Manp1) + fabs(Man), minim_pair); } /* FIXME: this is a nasty little hack; there is some (transient?) instability in this recurrence for some values. I can tell when it happens, which is when this pair_ratio is large. But I do not know how to measure the error in terms of it. I guessed quadratic below, but it is probably worse than that. */ pair_ratio = start_pair/minim_pair; result->val = Man; result->err = 2.0 * (rat_0 + rat_1 + GSL_DBL_EPSILON) * (fabs(b-a)+1.0) * fabs(Man); result->err *= pair_ratio*pair_ratio + 1.0; return GSL_ERROR_SELECT_2(stat_0, stat_1); } else { /* Pick a0 such that b ~= 2a0 + x, then * recurse down in b from a0,a0 to determine * the values near the line b=2a+x. Then recurse * forward on a from a0. */ double epsa = a - floor(a); double a0 = floor(0.5*(b-x)) + epsa; double N = floor(a0 - b); double epsb = 1.0 + N - a0 + b; double Ma0b; double Ma0bp1; double Ma0p1b; int stat_a0; double Mnm1; double Mn; double Mnp1; double n; double err_rat; { gsl_sf_result r_Ma0np1; gsl_sf_result r_Ma0n; int stat_0 = hyperg_1F1_beps_bgt0(-epsb, a0+epsb, x, &r_Ma0np1); int stat_1 = hyperg_1F1_beps_bgt0(1.0-epsb, a0+epsb-1.0, x, &r_Ma0n); double Ma0np1 = r_Ma0np1.val; double Ma0n = r_Ma0n.val; double Ma0nm1; err_rat = fabs(r_Ma0np1.err/r_Ma0np1.val) + fabs(r_Ma0n.err/r_Ma0n.val); for(n=a0+epsb-1.0; n>b+0.1; n -= 1.0) { Ma0nm1 = (-n*(1-n-x)*Ma0n - x*(n-a0)*Ma0np1)/(n*(n-1.0)); Ma0np1 = Ma0n; Ma0n = Ma0nm1; } Ma0bp1 = Ma0np1; Ma0b = Ma0n; Ma0p1b = (b*(a0+x)*Ma0b+x*(a0-b)*Ma0bp1)/(a0*b); /* right-down hook */ stat_a0 = GSL_ERROR_SELECT_2(stat_0, stat_1); } /* Initialise the recurrence correctly BJG */ if (a0 >= a - 0.1) { Mn = Ma0b; } else if (a0 + 1>= a - 0.1) { Mn = Ma0p1b; } else { Mnm1 = Ma0b; Mn = Ma0p1b; for(n=a0+1.0; nval = Mn; result->err = (err_rat + GSL_DBL_EPSILON) * (fabs(b-a)+1.0) * fabs(Mn); return stat_a0; } } } /* Assumes b != integer * Assumes a != integer when x > 0 * Assumes b-a != neg integer when x < 0 */ static int hyperg_1F1_ab_neg(const double a, const double b, const double x, gsl_sf_result * result) { const double bma = b - a; const double abs_x = fabs(x); const double abs_a = fabs(a); const double abs_b = fabs(b); const double size_a = GSL_MAX(abs_a, 1.0); const double size_b = GSL_MAX(abs_b, 1.0); const int bma_integer = ( bma - floor(bma+0.5) < _1F1_INT_THRESHOLD ); if( (abs_a < 10.0 && abs_b < 10.0 && abs_x < 5.0) || (b > 0.8*GSL_MAX(fabs(a),1.0)*fabs(x)) ) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if( x > 0.0 && size_b > size_a && size_a*log(M_E*x/size_b) < GSL_LOG_DBL_EPSILON+7.0 ) { /* Series terms are positive definite up until * there is a sign change. But by then the * terms are small due to the last condition. */ return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if( (abs_x < 5.0 && fabs(bma) < 10.0 && abs_b < 10.0) || (b > 0.8*GSL_MAX_DBL(fabs(bma),1.0)*abs_x) ) { /* Use Kummer transformation to render series safe. */ gsl_sf_result Kummer_1F1; int stat_K = gsl_sf_hyperg_1F1_series_e(bma, b, -x, &Kummer_1F1); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if( x < -30.0 && GSL_MAX_DBL(fabs(a),1.0)*GSL_MAX_DBL(fabs(1.0+a-b),1.0) < 0.99*fabs(x) ) { /* Large negative x asymptotic. * Note that we do not check if b-a is a negative integer. */ return hyperg_1F1_asymp_negx(a, b, x, result); } else if( x > 100.0 && GSL_MAX_DBL(fabs(bma),1.0)*GSL_MAX_DBL(fabs(1.0-a),1.0) < 0.99*fabs(x) ) { /* Large positive x asymptotic. * Note that we do not check if a is a negative integer. */ return hyperg_1F1_asymp_posx(a, b, x, result); } else if(x > 0.0 && !(bma_integer && bma > 0.0)) { return hyperg_1F1_U(a, b, x, result); } else { /* FIXME: if all else fails, try the series... BJG */ if (x < 0.0) { /* Apply Kummer Transformation */ int status = gsl_sf_hyperg_1F1_series_e(b-a, b, -x, result); double K_factor = exp(x); result->val *= K_factor; result->err *= K_factor; return status; } else { int status = gsl_sf_hyperg_1F1_series_e(a, b, x, result); return status; } /* Sadness... */ /* result->val = 0.0; */ /* result->err = 0.0; */ /* GSL_ERROR ("error", GSL_EUNIMPL); */ } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_hyperg_1F1_int_e(const int a, const int b, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(a == b) { return gsl_sf_exp_e(x, result); } else if(b == 0) { DOMAIN_ERROR(result); } else if(a == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(b < 0 && (a < b || a > 0)) { /* Standard domain error due to singularity. */ DOMAIN_ERROR(result); } else if(x > 100.0 && GSL_MAX_DBL(1.0,fabs(b-a))*GSL_MAX_DBL(1.0,fabs(1-a)) < 0.5 * x) { /* x -> +Inf asymptotic */ return hyperg_1F1_asymp_posx(a, b, x, result); } else if(x < -100.0 && GSL_MAX_DBL(1.0,fabs(a))*GSL_MAX_DBL(1.0,fabs(1+a-b)) < 0.5 * fabs(x)) { /* x -> -Inf asymptotic */ return hyperg_1F1_asymp_negx(a, b, x, result); } else if(a < 0 && b < 0) { return hyperg_1F1_ab_negint(a, b, x, result); } else if(a < 0 && b > 0) { /* Use Kummer to reduce it to the positive integer case. * Note that b > a, strictly, since we already trapped b = a. */ gsl_sf_result Kummer_1F1; int stat_K = hyperg_1F1_ab_posint(b-a, b, -x, &Kummer_1F1); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else { /* a > 0 and b > 0 */ return hyperg_1F1_ab_posint(a, b, x, result); } } int gsl_sf_hyperg_1F1_e(const double a, const double b, const double x, gsl_sf_result * result ) { const double bma = b - a; const double rinta = floor(a + 0.5); const double rintb = floor(b + 0.5); const double rintbma = floor(bma + 0.5); const int a_integer = ( fabs(a-rinta) < _1F1_INT_THRESHOLD && rinta > INT_MIN && rinta < INT_MAX ); const int b_integer = ( fabs(b-rintb) < _1F1_INT_THRESHOLD && rintb > INT_MIN && rintb < INT_MAX ); const int bma_integer = ( fabs(bma-rintbma) < _1F1_INT_THRESHOLD && rintbma > INT_MIN && rintbma < INT_MAX ); const int b_neg_integer = ( b < -0.1 && b_integer ); const int a_neg_integer = ( a < -0.1 && a_integer ); const int bma_neg_integer = ( bma < -0.1 && bma_integer ); /* CHECK_POINTER(result) */ if(x == 0.0) { /* Testing for this before testing a and b * is somewhat arbitrary. The result is that * we have 1F1(a,0,0) = 1. */ result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(b == 0.0) { DOMAIN_ERROR(result); } else if(a == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(a == b) { /* case: a==b; exp(x) * It's good to test exact equality now. * We also test approximate equality later. */ return gsl_sf_exp_e(x, result); } else if(fabs(b) < _1F1_INT_THRESHOLD && fabs(a) < _1F1_INT_THRESHOLD) { /* a and b near zero: 1 + a/b (exp(x)-1) */ /* Note that neither a nor b is zero, since * we eliminated that with the above tests. */ gsl_sf_result exm1; int stat_e = gsl_sf_expm1_e(x, &exm1); double sa = ( a > 0.0 ? 1.0 : -1.0 ); double sb = ( b > 0.0 ? 1.0 : -1.0 ); double lnab = log(fabs(a/b)); /* safe */ gsl_sf_result hx; int stat_hx = gsl_sf_exp_mult_err_e(lnab, GSL_DBL_EPSILON * fabs(lnab), sa * sb * exm1.val, exm1.err, &hx); result->val = (hx.val == GSL_DBL_MAX ? hx.val : 1.0 + hx.val); /* FIXME: excessive paranoia ? what is DBL_MAX+1 ?*/ result->err = hx.err; return GSL_ERROR_SELECT_2(stat_hx, stat_e); } else if (fabs(b) < _1F1_INT_THRESHOLD && fabs(x*a) < 1) { /* b near zero and a not near zero */ const double m_arg = 1.0/(0.5*b); gsl_sf_result F_renorm; int stat_F = hyperg_1F1_renorm_b0(a, x, &F_renorm); int stat_m = gsl_sf_multiply_err_e(m_arg, 2.0 * GSL_DBL_EPSILON * m_arg, 0.5*F_renorm.val, 0.5*F_renorm.err, result); return GSL_ERROR_SELECT_2(stat_m, stat_F); } else if(a_integer && b_integer) { /* Check for reduction to the integer case. * Relies on the arbitrary "near an integer" test. */ return gsl_sf_hyperg_1F1_int_e((int)rinta, (int)rintb, x, result); } else if(b_neg_integer && !(a_neg_integer && a > b)) { /* Standard domain error due to * uncancelled singularity. */ DOMAIN_ERROR(result); } else if(a_neg_integer) { return hyperg_1F1_a_negint_lag((int)rinta, b, x, result); } else if(b > 0.0) { if(-1.0 <= a && a <= 1.0) { /* Handle small a explicitly. */ return hyperg_1F1_small_a_bgt0(a, b, x, result); } else if(bma_neg_integer) { /* Catch this now, to avoid problems in the * generic evaluation code. */ gsl_sf_result Kummer_1F1; int stat_K = hyperg_1F1_a_negint_lag((int)rintbma, b, -x, &Kummer_1F1); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if(a < 0.0 && fabs(x) < 100.0) { /* Use Kummer to reduce it to the generic positive case. * Note that b > a, strictly, since we already trapped b = a. * Also b-(b-a)=a, and a is not a negative integer here, * so the generic evaluation is safe. */ gsl_sf_result Kummer_1F1; int stat_K = hyperg_1F1_ab_pos(b-a, b, -x, &Kummer_1F1); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if (a > 0) { /* a > 0.0 */ return hyperg_1F1_ab_pos(a, b, x, result); } else { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } } else { /* b < 0.0 */ if(bma_neg_integer && x < 0.0) { /* Handle this now to prevent problems * in the generic evaluation. */ gsl_sf_result K; int stat_K; int stat_e; if(a < 0.0) { /* Kummer transformed version of safe polynomial. * The condition a < 0 is equivalent to b < b-a, * which is the condition required for the series * to be positive definite here. */ stat_K = hyperg_1F1_a_negint_poly((int)rintbma, b, -x, &K); } else { /* Generic eval for negative integer a. */ stat_K = hyperg_1F1_a_negint_lag((int)rintbma, b, -x, &K); } stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), K.val, K.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if(a > 0.0) { /* Use Kummer to reduce it to the generic negative case. */ gsl_sf_result K; int stat_K = hyperg_1F1_ab_neg(b-a, b, -x, &K); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), K.val, K.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else { return hyperg_1F1_ab_neg(a, b, x, result); } } } #if 0 /* Luke in the canonical case. */ if(x < 0.0 && !a_neg_integer && !bma_neg_integer) { double prec; return hyperg_1F1_luke(a, b, x, result, &prec); } /* Luke with Kummer transformation. */ if(x > 0.0 && !a_neg_integer && !bma_neg_integer) { double prec; double Kummer_1F1; double ex; int stat_F = hyperg_1F1_luke(b-a, b, -x, &Kummer_1F1, &prec); int stat_e = gsl_sf_exp_e(x, &ex); if(stat_F == GSL_SUCCESS && stat_e == GSL_SUCCESS) { double lnr = log(fabs(Kummer_1F1)) + x; if(lnr < GSL_LOG_DBL_MAX) { *result = ex * Kummer_1F1; return GSL_SUCCESS; } else { *result = GSL_POSINF; GSL_ERROR ("overflow", GSL_EOVRFLW); } } else if(stat_F != GSL_SUCCESS) { *result = 0.0; return stat_F; } else { *result = 0.0; return stat_e; } } #endif /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_hyperg_1F1_int(const int m, const int n, double x) { EVAL_RESULT(gsl_sf_hyperg_1F1_int_e(m, n, x, &result)); } double gsl_sf_hyperg_1F1(double a, double b, double x) { EVAL_RESULT(gsl_sf_hyperg_1F1_e(a, b, x, &result)); } sources_5316/external/gsl/gsl_sf__bessel_temme.c0000644000176700017670000001427210707442037020650 0ustar paulpaul/* specfunc/bessel_temme.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Calculate series for Y_nu and K_nu for small x and nu. * This is applicable for x < 2 and |nu|<=1/2. * These functions assume x > 0. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_mode.h" #include "gsl_sf__bessel_temme.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" /* nu = (x+1)/4, -1val = -sum0; Ynu->err = (2.0 + 0.5*k) * GSL_DBL_EPSILON * fabs(Ynu->val); Ynup1->val = -sum1 * 2.0/x; Ynup1->err = (2.0 + 0.5*k) * GSL_DBL_EPSILON * fabs(Ynup1->val); stat_iter = ( k >= max_iter ? GSL_EMAXITER : GSL_SUCCESS ); return GSL_ERROR_SELECT_2(stat_iter, stat_g); } int gsl_sf_bessel_K_scaled_temme(const double nu, const double x, double * K_nu, double * K_nup1, double * Kp_nu) { const int max_iter = 15000; const double half_x = 0.5 * x; const double ln_half_x = log(half_x); const double half_x_nu = exp(nu*ln_half_x); const double pi_nu = M_PI * nu; const double sigma = -nu * ln_half_x; const double sinrat = (fabs(pi_nu) < GSL_DBL_EPSILON ? 1.0 : pi_nu/sin(pi_nu)); const double sinhrat = (fabs(sigma) < GSL_DBL_EPSILON ? 1.0 : sinh(sigma)/sigma); const double ex = exp(x); double sum0, sum1; double fk, pk, qk, hk, ck; int k = 0; int stat_iter; double g_1pnu, g_1mnu, g1, g2; int stat_g = gsl_sf_temme_gamma(nu, &g_1pnu, &g_1mnu, &g1, &g2); fk = sinrat * (cosh(sigma)*g1 - sinhrat*ln_half_x*g2); pk = 0.5/half_x_nu * g_1pnu; qk = 0.5*half_x_nu * g_1mnu; hk = pk; ck = 1.0; sum0 = fk; sum1 = hk; while(k < max_iter) { double del0; double del1; k++; fk = (k*fk + pk + qk)/(k*k-nu*nu); ck *= half_x*half_x/k; pk /= (k - nu); qk /= (k + nu); hk = -k*fk + pk; del0 = ck * fk; del1 = ck * hk; sum0 += del0; sum1 += del1; if(fabs(del0) < 0.5*fabs(sum0)*GSL_DBL_EPSILON) break; } *K_nu = sum0 * ex; *K_nup1 = sum1 * 2.0/x * ex; *Kp_nu = - *K_nup1 + nu/x * *K_nu; stat_iter = ( k == max_iter ? GSL_EMAXITER : GSL_SUCCESS ); return GSL_ERROR_SELECT_2(stat_iter, stat_g); } sources_5316/external/gsl/gsl_rng__waterman14.c0000664000176700017670000000422211723710247020341 0ustar paulpaul/* rng/waterman14.c * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth * The Art of Computer Programming * Volume 2 * Third Edition * Addison-Wesley * Page 106-108 * * It is called "Waterman". * * This implementation copyright (C) 2001 Carlo Perassi * and (C) 2003 Heiko Bauke. */ #include "gsl__config.h" #include #include "gsl_rng.h" #define AA 1566083941UL #define MM 0xffffffffUL /* 2 ^ 32 - 1 */ static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); typedef struct { unsigned long int x; } ran_state_t; static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; state->x = (AA * state->x) & MM; return state->x; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 4294967296.0; } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; if (s == 0) s = 1; /* default seed is 1 */ state->x = s & MM; return; } static const gsl_rng_type ran_type = { "waterman14", /* name */ MM, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_waterman14 = &ran_type; sources_5316/external/gsl/gsl_specfunc__legendre.h0000664000176700017670000000447311705263724021203 0ustar paulpaul/* specfunc/legendre.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Declare private but non-local support functions * used in various Legendre function evaluations. */ #include "gsl_sf_result.h" /* Large negative mu asymptotic * P^{-mu}_{-1/2 + I tau}, mu -> Inf * |x| < 1 */ int gsl_sf_conicalP_xlt1_large_neg_mu_e(double mu, double tau, double x, gsl_sf_result * result, double * ln_multiplier); /* Large tau uniform asymptotics * P^{-mu}_{-1/2 + I tau}, tau -> Inf * 1 < x */ int gsl_sf_conicalP_xgt1_neg_mu_largetau_e(const double mu, const double tau, const double x, double acosh_x, gsl_sf_result * result, double * ln_multiplier); /* Large tau uniform asymptotics * P^{-mu}_{-1/2 + I tau}, tau -> Inf * -1 < x < 1 */ int gsl_sf_conicalP_xlt1_neg_mu_largetau_e(const double mu, const double tau, const double x, const double acos_x, gsl_sf_result * result, double * ln_multiplier); /* P^{mu}_{-1/2 + I tau} * x->Inf * * * This is effective to precision EPS for * * (mu^2 + tau^2)/((1 + tau^2)^(1/2) x^2) < EPS^{1/3} * * since it goes only to a fixed order, based on the * representation in terms of hypegeometric functions * of argument 1/x^2. * [Zhurina+Karmazina, (3.8)] */ int gsl_sf_conicalP_large_x_e(const double mu, const double tau, const double x, gsl_sf_result * result, double * ln_multiplier); sources_5316/external/gsl/gsl_roots__convergence.c0000664000176700017670000000446111723710247021241 0ustar paulpaul/* roots/convergence.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_roots.h" int gsl_root_test_interval (double x_lower, double x_upper, double epsabs, double epsrel) { const double abs_lower = fabs(x_lower) ; const double abs_upper = fabs(x_upper) ; double min_abs, tolerance; if (epsrel < 0.0) GSL_ERROR ("relative tolerance is negative", GSL_EBADTOL); if (epsabs < 0.0) GSL_ERROR ("absolute tolerance is negative", GSL_EBADTOL); if (x_lower > x_upper) GSL_ERROR ("lower bound larger than upper bound", GSL_EINVAL); if ((x_lower > 0.0 && x_upper > 0.0) || (x_lower < 0.0 && x_upper < 0.0)) { min_abs = GSL_MIN_DBL(abs_lower, abs_upper) ; } else { min_abs = 0; } tolerance = epsabs + epsrel * min_abs ; if (fabs(x_upper - x_lower) < tolerance) return GSL_SUCCESS; return GSL_CONTINUE ; } int gsl_root_test_delta (double x1, double x0, double epsabs, double epsrel) { const double tolerance = epsabs + epsrel * fabs(x1) ; if (epsrel < 0.0) GSL_ERROR ("relative tolerance is negative", GSL_EBADTOL); if (epsabs < 0.0) GSL_ERROR ("absolute tolerance is negative", GSL_EBADTOL); if (fabs(x1 - x0) < tolerance || x1 == x0) return GSL_SUCCESS; return GSL_CONTINUE ; } int gsl_root_test_residual (double f, double epsabs) { if (epsabs < 0.0) GSL_ERROR ("absolute tolerance is negative", GSL_EBADTOL); if (fabs(f) < epsabs) return GSL_SUCCESS; return GSL_CONTINUE ; } sources_5316/external/gsl/gsl_randist__multinomial.c0000664000176700017670000000564611723710247021601 0ustar paulpaul/* randist/multinomial.c * * Copyright (C) 2002 Gavin E. Crooks * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" #include "gsl_sf_gamma.h" /* The multinomial distribution has the form N! n_1 n_2 n_K prob(n_1, n_2, ... n_K) = -------------------- p_1 p_2 ... p_K (n_1! n_2! ... n_K!) where n_1, n_2, ... n_K are nonnegative integers, sum_{k=1,K} n_k = N, and p = (p_1, p_2, ..., p_K) is a probability distribution. Random variates are generated using the conditional binomial method. This scales well with N and does not require a setup step. Ref: C.S. David, The computer generation of multinomial random variates, Comp. Stat. Data Anal. 16 (1993) 205-217 */ void gsl_ran_multinomial (const gsl_rng * r, const size_t K, const unsigned int N, const double p[], unsigned int n[]) { size_t k; double norm = 0.0; double sum_p = 0.0; unsigned int sum_n = 0; /* p[k] may contain non-negative weights that do not sum to 1.0. * Even a probability distribution will not exactly sum to 1.0 * due to rounding errors. */ for (k = 0; k < K; k++) { norm += p[k]; } for (k = 0; k < K; k++) { if (p[k] > 0.0) { n[k] = gsl_ran_binomial (r, p[k] / (norm - sum_p), N - sum_n); } else { n[k] = 0; } sum_p += p[k]; sum_n += n[k]; } } double gsl_ran_multinomial_pdf (const size_t K, const double p[], const unsigned int n[]) { return exp (gsl_ran_multinomial_lnpdf (K, p, n)); } double gsl_ran_multinomial_lnpdf (const size_t K, const double p[], const unsigned int n[]) { size_t k; unsigned int N = 0; double log_pdf = 0.0; double norm = 0.0; for (k = 0; k < K; k++) { N += n[k]; } for (k = 0; k < K; k++) { norm += p[k]; } log_pdf = gsl_sf_lnfact (N); for (k = 0; k < K; k++) { log_pdf -= gsl_sf_lnfact (n[k]); } for (k = 0; k < K; k++) { log_pdf += log (p[k] / norm) * n[k]; } return log_pdf; } sources_5316/external/gsl/gsl_sf__poch.c0000644000176700017670000003156610707442037017142 0ustar paulpaul/* specfunc/poch.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_log.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_psi.h" #include "gsl_sf_gamma.h" #include "gsl_sf__error.h" static const double bern[21] = { 0.0 /* no element 0 */, +0.833333333333333333333333333333333e-01, -0.138888888888888888888888888888888e-02, +0.330687830687830687830687830687830e-04, -0.826719576719576719576719576719576e-06, +0.208767569878680989792100903212014e-07, -0.528419013868749318484768220217955e-09, +0.133825365306846788328269809751291e-10, -0.338968029632258286683019539124944e-12, +0.858606205627784456413590545042562e-14, -0.217486869855806187304151642386591e-15, +0.550900282836022951520265260890225e-17, -0.139544646858125233407076862640635e-18, +0.353470703962946747169322997780379e-20, -0.895351742703754685040261131811274e-22, +0.226795245233768306031095073886816e-23, -0.574472439520264523834847971943400e-24, +0.145517247561486490186626486727132e-26, -0.368599494066531017818178247990866e-28, +0.933673425709504467203255515278562e-30, -0.236502241570062993455963519636983e-31 }; /* ((a)_x - 1)/x in the "small x" region where * cancellation must be controlled. * * Based on SLATEC DPOCH1(). */ /* C When ABS(X) is so small that substantial cancellation will occur if C the straightforward formula is used, we use an expansion due C to Fields and discussed by Y. L. Luke, The Special Functions and Their C Approximations, Vol. 1, Academic Press, 1969, page 34. C C The ratio POCH(A,X) = GAMMA(A+X)/GAMMA(A) is written by Luke as C (A+(X-1)/2)**X * polynomial in (A+(X-1)/2)**(-2) . C In order to maintain significance in POCH1, we write for positive a C (A+(X-1)/2)**X = EXP(X*LOG(A+(X-1)/2)) = EXP(Q) C = 1.0 + Q*EXPREL(Q) . C Likewise the polynomial is written C POLY = 1.0 + X*POLY1(A,X) . C Thus, C POCH1(A,X) = (POCH(A,X) - 1) / X C = EXPREL(Q)*(Q/X + Q*POLY1(A,X)) + POLY1(A,X) C */ static int pochrel_smallx(const double a, const double x, gsl_sf_result * result) { /* SQTBIG = 1.0D0/SQRT(24.0D0*D1MACH(1)) ALNEPS = LOG(D1MACH(3)) */ const double SQTBIG = 1.0/(2.0*M_SQRT2*M_SQRT3*GSL_SQRT_DBL_MIN); const double ALNEPS = GSL_LOG_DBL_EPSILON - M_LN2; if(x == 0.0) { return gsl_sf_psi_e(a, result); } else { const double bp = ( (a < -0.5) ? 1.0-a-x : a ); const int incr = ( (bp < 10.0) ? 11.0-bp : 0 ); const double b = bp + incr; double dpoch1; gsl_sf_result dexprl; int stat_dexprl; int i; double var = b + 0.5*(x-1.0); double alnvar = log(var); double q = x*alnvar; double poly1 = 0.0; if(var < SQTBIG) { const int nterms = (int)(-0.5*ALNEPS/alnvar + 1.0); const double var2 = (1.0/var)/var; const double rho = 0.5 * (x + 1.0); double term = var2; double gbern[24]; int k, j; gbern[1] = 1.0; gbern[2] = -rho/12.0; poly1 = gbern[2] * term; if(nterms > 20) { /* NTERMS IS TOO BIG, MAYBE D1MACH(3) IS BAD */ /* nterms = 20; */ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_ESANITY); } for(k=2; k<=nterms; k++) { double gbk = 0.0; for(j=1; j<=k; j++) { gbk += bern[k-j+1]*gbern[j]; } gbern[k+1] = -rho*gbk/k; term *= (2*k-2-x)*(2*k-1-x)*var2; poly1 += gbern[k+1]*term; } } stat_dexprl = gsl_sf_expm1_e(q, &dexprl); if(stat_dexprl != GSL_SUCCESS) { result->val = 0.0; result->err = 0.0; return stat_dexprl; } dexprl.val = dexprl.val/q; poly1 *= (x - 1.0); dpoch1 = dexprl.val * (alnvar + q * poly1) + poly1; for(i=incr-1; i >= 0; i--) { /* C WE HAVE DPOCH1(B,X), BUT BP IS SMALL, SO WE USE BACKWARDS RECURSION C TO OBTAIN DPOCH1(BP,X). */ double binv = 1.0/(bp+i); dpoch1 = (dpoch1 - binv) / (1.0 + x*binv); } if(bp == a) { result->val = dpoch1; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(incr) + 1.0) * fabs(result->val); return GSL_SUCCESS; } else { /* C WE HAVE DPOCH1(BP,X), BUT A IS LT -0.5. WE THEREFORE USE A C REFLECTION FORMULA TO OBTAIN DPOCH1(A,X). */ double sinpxx = sin(M_PI*x)/x; double sinpx2 = sin(0.5*M_PI*x); double t1 = sinpxx/tan(M_PI*b); double t2 = 2.0*sinpx2*(sinpx2/x); double trig = t1 - t2; result->val = dpoch1 * (1.0 + x*trig) + trig; result->err = (fabs(dpoch1*x) + 1.0) * GSL_DBL_EPSILON * (fabs(t1) + fabs(t2)); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(incr) + 1.0) * fabs(result->val); return GSL_SUCCESS; } } } /* Assumes a>0 and a+x>0. */ static int lnpoch_pos(const double a, const double x, gsl_sf_result * result) { double absx = fabs(x); if(absx > 0.1*a || absx*log(GSL_MAX_DBL(a,2.0)) > 0.1) { if(a < GSL_SF_GAMMA_XMAX && a+x < GSL_SF_GAMMA_XMAX) { /* If we can do it by calculating the gamma functions * directly, then that will be more accurate than * doing the subtraction of the logs. */ gsl_sf_result g1; gsl_sf_result g2; gsl_sf_gammainv_e(a, &g1); gsl_sf_gammainv_e(a+x, &g2); result->val = -log(g2.val/g1.val); result->err = g1.err/fabs(g1.val) + g2.err/fabs(g2.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* Otherwise we must do the subtraction. */ gsl_sf_result lg1; gsl_sf_result lg2; int stat_1 = gsl_sf_lngamma_e(a, &lg1); int stat_2 = gsl_sf_lngamma_e(a+x, &lg2); result->val = lg2.val - lg1.val; result->err = lg2.err + lg1.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_1, stat_2); } } else if(absx < 0.1*a && a > 15.0) { /* Be careful about the implied subtraction. * Note that both a+x and and a must be * large here since a is not small * and x is not relatively large. * So we calculate using Stirling for Log[Gamma(z)]. * * Log[Gamma(a+x)/Gamma(a)] = x(Log[a]-1) + (x+a-1/2)Log[1+x/a] * + (1/(1+eps) - 1) / (12 a) * - (1/(1+eps)^3 - 1) / (360 a^3) * + (1/(1+eps)^5 - 1) / (1260 a^5) * - (1/(1+eps)^7 - 1) / (1680 a^7) * + ... */ const double eps = x/a; const double den = 1.0 + eps; const double d3 = den*den*den; const double d5 = d3*den*den; const double d7 = d5*den*den; const double c1 = -eps/den; const double c3 = -eps*(3.0+eps*(3.0+eps))/d3; const double c5 = -eps*(5.0+eps*(10.0+eps*(10.0+eps*(5.0+eps))))/d5; const double c7 = -eps*(7.0+eps*(21.0+eps*(35.0+eps*(35.0+eps*(21.0+eps*(7.0+eps))))))/d7; const double p8 = gsl_sf_pow_int(1.0+eps,8); const double c8 = 1.0/p8 - 1.0; /* these need not */ const double c9 = 1.0/(p8*(1.0+eps)) - 1.0; /* be very accurate */ const double a4 = a*a*a*a; const double a6 = a4*a*a; const double ser_1 = c1 + c3/(30.0*a*a) + c5/(105.0*a4) + c7/(140.0*a6); const double ser_2 = c8/(99.0*a6*a*a) - 691.0/360360.0 * c9/(a6*a4); const double ser = (ser_1 + ser_2)/ (12.0*a); double term1 = x * log(a/M_E); double term2; gsl_sf_result ln_1peps; gsl_sf_log_1plusx_e(eps, &ln_1peps); /* log(1 + x/a) */ term2 = (x + a - 0.5) * ln_1peps.val; result->val = term1 + term2 + ser; result->err = GSL_DBL_EPSILON*fabs(term1); result->err += fabs((x + a - 0.5)*ln_1peps.err); result->err += fabs(ln_1peps.val) * GSL_DBL_EPSILON * (fabs(x) + fabs(a) + 0.5); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result poch_rel; int stat_p = pochrel_smallx(a, x, &poch_rel); double eps = x*poch_rel.val; int stat_e = gsl_sf_log_1plusx_e(eps, result); result->err = 2.0 * fabs(x * poch_rel.err / (1.0 + eps)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_e, stat_p); } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_lnpoch_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(a <= 0.0 || a+x <= 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { return lnpoch_pos(a, x, result); } } int gsl_sf_lnpoch_sgn_e(const double a, const double x, gsl_sf_result * result, double * sgn) { if(a == 0.0 || a+x == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result); } else if(x == 0.0) { *sgn = 1.0; result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(a > 0.0 && a+x > 0.0) { *sgn = 1.0; return lnpoch_pos(a, x, result); } else if(a < 0.0 && a+x < 0.0) { /* Reduce to positive case using reflection. */ double sin_1 = sin(M_PI * (1.0 - a)); double sin_2 = sin(M_PI * (1.0 - a - x)); if(sin_1 == 0.0 || sin_2 == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result); } else { gsl_sf_result lnp_pos; int stat_pp = lnpoch_pos(1.0-a, -x, &lnp_pos); double lnterm = log(fabs(sin_1/sin_2)); result->val = lnterm - lnp_pos.val; result->err = lnp_pos.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(1.0-a) + fabs(1.0-a-x)) * fabs(lnterm); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *sgn = GSL_SIGN(sin_1*sin_2); return stat_pp; } } else { /* Evaluate gamma ratio directly. */ gsl_sf_result lg_apn; gsl_sf_result lg_a; double s_apn, s_a; int stat_apn = gsl_sf_lngamma_sgn_e(a+x, &lg_apn, &s_apn); int stat_a = gsl_sf_lngamma_sgn_e(a, &lg_a, &s_a); if(stat_apn == GSL_SUCCESS && stat_a == GSL_SUCCESS) { result->val = lg_apn.val - lg_a.val; result->err = lg_apn.err + lg_a.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *sgn = s_a * s_apn; return GSL_SUCCESS; } else if(stat_apn == GSL_EDOM || stat_a == GSL_EDOM){ *sgn = 0.0; DOMAIN_ERROR(result); } else { result->val = 0.0; result->err = 0.0; *sgn = 0.0; return GSL_FAILURE; } } } int gsl_sf_poch_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result lnpoch; double sgn; int stat_lnpoch = gsl_sf_lnpoch_sgn_e(a, x, &lnpoch, &sgn); int stat_exp = gsl_sf_exp_err_e(lnpoch.val, lnpoch.err, result); result->val *= sgn; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_exp, stat_lnpoch); } } int gsl_sf_pochrel_e(const double a, const double x, gsl_sf_result * result) { const double absx = fabs(x); const double absa = fabs(a); /* CHECK_POINTER(result) */ if(absx > 0.1*absa || absx*log(GSL_MAX(absa,2.0)) > 0.1) { gsl_sf_result lnpoch; double sgn; int stat_poch = gsl_sf_lnpoch_sgn_e(a, x, &lnpoch, &sgn); if(lnpoch.val > GSL_LOG_DBL_MAX) { OVERFLOW_ERROR(result); } else { const double el = exp(lnpoch.val); result->val = (sgn*el - 1.0)/x; result->err = fabs(result->val) * (lnpoch.err + 2.0 * GSL_DBL_EPSILON); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(sgn*el) + 1.0) / fabs(x); return stat_poch; } } else { return pochrel_smallx(a, x, result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_lnpoch(const double a, const double x) { EVAL_RESULT(gsl_sf_lnpoch_e(a, x, &result)); } double gsl_sf_poch(const double a, const double x) { EVAL_RESULT(gsl_sf_poch_e(a, x, &result)); } double gsl_sf_pochrel(const double a, const double x) { EVAL_RESULT(gsl_sf_pochrel_e(a, x, &result)); } sources_5316/external/gsl/gsl_block_uchar.h0000664000176700017670000000450111705263724017635 0ustar paulpaul/* block/gsl_block_uchar.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_UCHAR_H__ #define __GSL_BLOCK_UCHAR_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_uchar_struct { size_t size; unsigned char *data; }; typedef struct gsl_block_uchar_struct gsl_block_uchar; gsl_block_uchar *gsl_block_uchar_alloc (const size_t n); gsl_block_uchar *gsl_block_uchar_calloc (const size_t n); void gsl_block_uchar_free (gsl_block_uchar * b); int gsl_block_uchar_fread (FILE * stream, gsl_block_uchar * b); int gsl_block_uchar_fwrite (FILE * stream, const gsl_block_uchar * b); int gsl_block_uchar_fscanf (FILE * stream, gsl_block_uchar * b); int gsl_block_uchar_fprintf (FILE * stream, const gsl_block_uchar * b, const char *format); int gsl_block_uchar_raw_fread (FILE * stream, unsigned char * b, const size_t n, const size_t stride); int gsl_block_uchar_raw_fwrite (FILE * stream, const unsigned char * b, const size_t n, const size_t stride); int gsl_block_uchar_raw_fscanf (FILE * stream, unsigned char * b, const size_t n, const size_t stride); int gsl_block_uchar_raw_fprintf (FILE * stream, const unsigned char * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_uchar_size (const gsl_block_uchar * b); unsigned char * gsl_block_uchar_data (const gsl_block_uchar * b); __END_DECLS #endif /* __GSL_BLOCK_UCHAR_H__ */ sources_5316/external/gsl/gsl_cblas__cscal.c0000664000176700017670000000034011723710247017736 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cscal (const int N, const void *alpha, void *X, const int incX) { #define BASE float #include "gsl_cblas__source_scal_c.h" #undef BASE } sources_5316/external/gsl/gsl_integration__positivity.c0000664000176700017670000000054211723710247022337 0ustar paulpaul/* Compare the integral of f(x) with the integral of |f(x)| to determine if f(x) covers both positive and negative values */ static inline int test_positivity (double result, double resabs); static inline int test_positivity (double result, double resabs) { int status = (fabs (result) >= (1 - 50 * GSL_DBL_EPSILON) * resabs); return status; } sources_5316/external/gsl/gsl_statistics__minmax.c0000664000176700017670000000306411723710247021256 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__minmax_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_cblas__source_gbmv_r.h0000664000176700017670000000526311705263724021526 0ustar paulpaul/* blas/source_gbmv_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; INDEX lenX, lenY, L, U; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; if (M == 0 || N == 0) return; if (alpha == 0.0 && beta == 1.0) return; if (Trans == CblasNoTrans) { lenX = N; lenY = M; L = KL; U = KU; } else { lenX = M; lenY = N; L = KU; U = KL; } /* form y := beta*y */ if (beta == 0.0) { INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { Y[iy] = 0; iy += incY; } } else if (beta != 1.0) { INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { Y[iy] *= beta; iy += incY; } } if (alpha == 0.0) return; if ((order == CblasRowMajor && Trans == CblasNoTrans) || (order == CblasColMajor && Trans == CblasTrans)) { /* form y := alpha*A*x + y */ INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { BASE temp = 0.0; const INDEX j_min = (i > L ? i - L : 0); const INDEX j_max = GSL_MIN(lenX, i + U + 1); INDEX jx = OFFSET(lenX, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { temp += X[jx] * A[(L - i + j) + i * lda]; jx += incX; } Y[iy] += alpha * temp; iy += incY; } } else if ((order == CblasRowMajor && Trans == CblasTrans) || (order == CblasColMajor && Trans == CblasNoTrans)) { /* form y := alpha*A'*x + y */ INDEX jx = OFFSET(lenX, incX); for (j = 0; j < lenX; j++) { const BASE temp = alpha * X[jx]; if (temp != 0.0) { const INDEX i_min = (j > U ? j - U : 0); const INDEX i_max = GSL_MIN(lenY, j + L + 1); INDEX iy = OFFSET(lenY, incY) + i_min * incY; for (i = i_min; i < i_max; i++) { Y[iy] += temp * A[lda * j + (U + i - j)]; iy += incY; } } jx += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_specfunc__fermi_dirac.c0000664000176700017670000010321511723710247021644 0ustar paulpaul/* specfunc/fermi_dirac.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_hyperg.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_zeta.h" #include "gsl_sf_fermi_dirac.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" #define locEPS (1000.0*GSL_DBL_EPSILON) /* Chebyshev fit for F_{1}(t); -1 < t < 1, -1 < x < 1 */ static double fd_1_a_data[22] = { 1.8949340668482264365, 0.7237719066890052793, 0.1250000000000000000, 0.0101065196435973942, 0.0, -0.0000600615242174119, 0.0, 6.816528764623e-7, 0.0, -9.5895779195e-9, 0.0, 1.515104135e-10, 0.0, -2.5785616e-12, 0.0, 4.62270e-14, 0.0, -8.612e-16, 0.0, 1.65e-17, 0.0, -3.e-19 }; static cheb_series fd_1_a_cs = { fd_1_a_data, 21, -1, 1, 12 }; /* Chebyshev fit for F_{1}(3/2(t+1) + 1); -1 < t < 1, 1 < x < 4 */ static double fd_1_b_data[22] = { 10.409136795234611872, 3.899445098225161947, 0.513510935510521222, 0.010618736770218426, -0.001584468020659694, 0.000146139297161640, -1.408095734499e-6, -2.177993899484e-6, 3.91423660640e-7, -2.3860262660e-8, -4.138309573e-9, 1.283965236e-9, -1.39695990e-10, -4.907743e-12, 4.399878e-12, -7.17291e-13, 2.4320e-14, 1.4230e-14, -3.446e-15, 2.93e-16, 3.7e-17, -1.6e-17 }; static cheb_series fd_1_b_cs = { fd_1_b_data, 21, -1, 1, 11 }; /* Chebyshev fit for F_{1}(3(t+1) + 4); -1 < t < 1, 4 < x < 10 */ static double fd_1_c_data[23] = { 56.78099449124299762, 21.00718468237668011, 2.24592457063193457, 0.00173793640425994, -0.00058716468739423, 0.00016306958492437, -0.00003817425583020, 7.64527252009e-6, -1.31348500162e-6, 1.9000646056e-7, -2.141328223e-8, 1.23906372e-9, 2.1848049e-10, -1.0134282e-10, 2.484728e-11, -4.73067e-12, 7.3555e-13, -8.740e-14, 4.85e-15, 1.23e-15, -5.6e-16, 1.4e-16, -3.e-17 }; static cheb_series fd_1_c_cs = { fd_1_c_data, 22, -1, 1, 13 }; /* Chebyshev fit for F_{1}(x) / x^2 * 10 < x < 30 * -1 < t < 1 * t = 1/10 (x-10) - 1 = x/10 - 2 * x = 10(t+2) */ static double fd_1_d_data[30] = { 1.0126626021151374442, -0.0063312525536433793, 0.0024837319237084326, -0.0008764333697726109, 0.0002913344438921266, -0.0000931877907705692, 0.0000290151342040275, -8.8548707259955e-6, 2.6603474114517e-6, -7.891415690452e-7, 2.315730237195e-7, -6.73179452963e-8, 1.94048035606e-8, -5.5507129189e-9, 1.5766090896e-9, -4.449310875e-10, 1.248292745e-10, -3.48392894e-11, 9.6791550e-12, -2.6786240e-12, 7.388852e-13, -2.032828e-13, 5.58115e-14, -1.52987e-14, 4.1886e-15, -1.1458e-15, 3.132e-16, -8.56e-17, 2.33e-17, -5.9e-18 }; static cheb_series fd_1_d_cs = { fd_1_d_data, 29, -1, 1, 14 }; /* Chebyshev fit for F_{1}(x) / x^2 * 30 < x < Inf * -1 < t < 1 * t = 60/x - 1 * x = 60/(t+1) */ static double fd_1_e_data[10] = { 1.0013707783890401683, 0.0009138522593601060, 0.0002284630648400133, -1.57e-17, -1.27e-17, -9.7e-18, -6.9e-18, -4.6e-18, -2.9e-18, -1.7e-18 }; static cheb_series fd_1_e_cs = { fd_1_e_data, 9, -1, 1, 4 }; /* Chebyshev fit for F_{2}(t); -1 < t < 1, -1 < x < 1 */ static double fd_2_a_data[21] = { 2.1573661917148458336, 0.8849670334241132182, 0.1784163467613519713, 0.0208333333333333333, 0.0012708226459768508, 0.0, -5.0619314244895e-6, 0.0, 4.32026533989e-8, 0.0, -4.870544166e-10, 0.0, 6.4203740e-12, 0.0, -9.37424e-14, 0.0, 1.4715e-15, 0.0, -2.44e-17, 0.0, 4.e-19 }; static cheb_series fd_2_a_cs = { fd_2_a_data, 20, -1, 1, 12 }; /* Chebyshev fit for F_{2}(3/2(t+1) + 1); -1 < t < 1, 1 < x < 4 */ static double fd_2_b_data[22] = { 16.508258811798623599, 7.421719394793067988, 1.458309885545603821, 0.128773850882795229, 0.001963612026198147, -0.000237458988738779, 0.000018539661382641, -1.92805649479e-7, -2.01950028452e-7, 3.2963497518e-8, -1.885817092e-9, -2.72632744e-10, 8.0554561e-11, -8.313223e-12, -2.24489e-13, 2.18778e-13, -3.4290e-14, 1.225e-15, 5.81e-16, -1.37e-16, 1.2e-17, 1.e-18 }; static cheb_series fd_2_b_cs = { fd_2_b_data, 21, -1, 1, 12 }; /* Chebyshev fit for F_{1}(3(t+1) + 4); -1 < t < 1, 4 < x < 10 */ static double fd_2_c_data[20] = { 168.87129776686440711, 81.80260488091659458, 15.75408505947931513, 1.12325586765966440, 0.00059057505725084, -0.00016469712946921, 0.00003885607810107, -7.89873660613e-6, 1.39786238616e-6, -2.1534528656e-7, 2.831510953e-8, -2.94978583e-9, 1.6755082e-10, 2.234229e-11, -1.035130e-11, 2.41117e-12, -4.3531e-13, 6.447e-14, -7.39e-15, 4.3e-16 }; static cheb_series fd_2_c_cs = { fd_2_c_data, 19, -1, 1, 12 }; /* Chebyshev fit for F_{1}(x) / x^3 * 10 < x < 30 * -1 < t < 1 * t = 1/10 (x-10) - 1 = x/10 - 2 * x = 10(t+2) */ static double fd_2_d_data[30] = { 0.3459960518965277589, -0.00633136397691958024, 0.00248382959047594408, -0.00087651191884005114, 0.00029139255351719932, -0.00009322746111846199, 0.00002904021914564786, -8.86962264810663e-6, 2.66844972574613e-6, -7.9331564996004e-7, 2.3359868615516e-7, -6.824790880436e-8, 1.981036528154e-8, -5.71940426300e-9, 1.64379426579e-9, -4.7064937566e-10, 1.3432614122e-10, -3.823400534e-11, 1.085771994e-11, -3.07727465e-12, 8.7064848e-13, -2.4595431e-13, 6.938531e-14, -1.954939e-14, 5.50162e-15, -1.54657e-15, 4.3429e-16, -1.2178e-16, 3.394e-17, -8.81e-18 }; static cheb_series fd_2_d_cs = { fd_2_d_data, 29, -1, 1, 14 }; /* Chebyshev fit for F_{2}(x) / x^3 * 30 < x < Inf * -1 < t < 1 * t = 60/x - 1 * x = 60/(t+1) */ static double fd_2_e_data[4] = { 0.3347041117223735227, 0.00091385225936012645, 0.00022846306484003205, 5.2e-19 }; static cheb_series fd_2_e_cs = { fd_2_e_data, 3, -1, 1, 3 }; /* Chebyshev fit for F_{-1/2}(t); -1 < t < 1, -1 < x < 1 */ static double fd_mhalf_a_data[20] = { 1.2663290042859741974, 0.3697876251911153071, 0.0278131011214405055, -0.0033332848565672007, -0.0004438108265412038, 0.0000616495177243839, 8.7589611449897e-6, -1.2622936986172e-6, -1.837464037221e-7, 2.69495091400e-8, 3.9760866257e-9, -5.894468795e-10, -8.77321638e-11, 1.31016571e-11, 1.9621619e-12, -2.945887e-13, -4.43234e-14, 6.6816e-15, 1.0084e-15, -1.561e-16 }; static cheb_series fd_mhalf_a_cs = { fd_mhalf_a_data, 19, -1, 1, 12 }; /* Chebyshev fit for F_{-1/2}(3/2(t+1) + 1); -1 < t < 1, 1 < x < 4 */ static double fd_mhalf_b_data[20] = { 3.270796131942071484, 0.5809004935853417887, -0.0299313438794694987, -0.0013287935412612198, 0.0009910221228704198, -0.0001690954939688554, 6.5955849946915e-6, 3.5953966033618e-6, -9.430672023181e-7, 8.75773958291e-8, 1.06247652607e-8, -4.9587006215e-9, 7.160432795e-10, 4.5072219e-12, -2.3695425e-11, 4.9122208e-12, -2.905277e-13, -9.59291e-14, 3.00028e-14, -3.4970e-15 }; static cheb_series fd_mhalf_b_cs = { fd_mhalf_b_data, 19, -1, 1, 12 }; /* Chebyshev fit for F_{-1/2}(3(t+1) + 4); -1 < t < 1, 4 < x < 10 */ static double fd_mhalf_c_data[25] = { 5.828283273430595507, 0.677521118293264655, -0.043946248736481554, 0.005825595781828244, -0.000864858907380668, 0.000110017890076539, -6.973305225404e-6, -1.716267414672e-6, 8.59811582041e-7, -2.33066786976e-7, 4.8503191159e-8, -8.130620247e-9, 1.021068250e-9, -5.3188423e-11, -1.9430559e-11, 8.750506e-12, -2.324897e-12, 4.83102e-13, -8.1207e-14, 1.0132e-14, -4.64e-16, -2.24e-16, 9.7e-17, -2.6e-17, 5.e-18 }; static cheb_series fd_mhalf_c_cs = { fd_mhalf_c_data, 24, -1, 1, 13 }; /* Chebyshev fit for F_{-1/2}(x) / x^(1/2) * 10 < x < 30 * -1 < t < 1 * t = 1/10 (x-10) - 1 = x/10 - 2 */ static double fd_mhalf_d_data[30] = { 2.2530744202862438709, 0.0018745152720114692, -0.0007550198497498903, 0.0002759818676644382, -0.0000959406283465913, 0.0000324056855537065, -0.0000107462396145761, 3.5126865219224e-6, -1.1313072730092e-6, 3.577454162766e-7, -1.104926666238e-7, 3.31304165692e-8, -9.5837381008e-9, 2.6575790141e-9, -7.015201447e-10, 1.747111336e-10, -4.04909605e-11, 8.5104999e-12, -1.5261885e-12, 1.876851e-13, 1.00574e-14, -1.82002e-14, 8.6634e-15, -3.2058e-15, 1.0572e-15, -3.259e-16, 9.60e-17, -2.74e-17, 7.6e-18, -1.9e-18 }; static cheb_series fd_mhalf_d_cs = { fd_mhalf_d_data, 29, -1, 1, 15 }; /* Chebyshev fit for F_{1/2}(t); -1 < t < 1, -1 < x < 1 */ static double fd_half_a_data[23] = { 1.7177138871306189157, 0.6192579515822668460, 0.0932802275119206269, 0.0047094853246636182, -0.0004243667967864481, -0.0000452569787686193, 5.2426509519168e-6, 6.387648249080e-7, -8.05777004848e-8, -1.04290272415e-8, 1.3769478010e-9, 1.847190359e-10, -2.51061890e-11, -3.4497818e-12, 4.784373e-13, 6.68828e-14, -9.4147e-15, -1.3333e-15, 1.898e-16, 2.72e-17, -3.9e-18, -6.e-19, 1.e-19 }; static cheb_series fd_half_a_cs = { fd_half_a_data, 22, -1, 1, 11 }; /* Chebyshev fit for F_{1/2}(3/2(t+1) + 1); -1 < t < 1, 1 < x < 4 */ static double fd_half_b_data[20] = { 7.651013792074984027, 2.475545606866155737, 0.218335982672476128, -0.007730591500584980, -0.000217443383867318, 0.000147663980681359, -0.000021586361321527, 8.07712735394e-7, 3.28858050706e-7, -7.9474330632e-8, 6.940207234e-9, 6.75594681e-10, -3.10200490e-10, 4.2677233e-11, -2.1696e-14, -1.170245e-12, 2.34757e-13, -1.4139e-14, -3.864e-15, 1.202e-15 }; static cheb_series fd_half_b_cs = { fd_half_b_data, 19, -1, 1, 12 }; /* Chebyshev fit for F_{1/2}(3(t+1) + 4); -1 < t < 1, 4 < x < 10 */ static double fd_half_c_data[23] = { 29.584339348839816528, 8.808344283250615592, 0.503771641883577308, -0.021540694914550443, 0.002143341709406890, -0.000257365680646579, 0.000027933539372803, -1.678525030167e-6, -2.78100117693e-7, 1.35218065147e-7, -3.3740425009e-8, 6.474834942e-9, -1.009678978e-9, 1.20057555e-10, -6.636314e-12, -1.710566e-12, 7.75069e-13, -1.97973e-13, 3.9414e-14, -6.374e-15, 7.77e-16, -4.0e-17, -1.4e-17 }; static cheb_series fd_half_c_cs = { fd_half_c_data, 22, -1, 1, 13 }; /* Chebyshev fit for F_{1/2}(x) / x^(3/2) * 10 < x < 30 * -1 < t < 1 * t = 1/10 (x-10) - 1 = x/10 - 2 */ static double fd_half_d_data[30] = { 1.5116909434145508537, -0.0036043405371630468, 0.0014207743256393359, -0.0005045399052400260, 0.0001690758006957347, -0.0000546305872688307, 0.0000172223228484571, -5.3352603788706e-6, 1.6315287543662e-6, -4.939021084898e-7, 1.482515450316e-7, -4.41552276226e-8, 1.30503160961e-8, -3.8262599802e-9, 1.1123226976e-9, -3.204765534e-10, 9.14870489e-11, -2.58778946e-11, 7.2550731e-12, -2.0172226e-12, 5.566891e-13, -1.526247e-13, 4.16121e-14, -1.12933e-14, 3.0537e-15, -8.234e-16, 2.215e-16, -5.95e-17, 1.59e-17, -4.0e-18 }; static cheb_series fd_half_d_cs = { fd_half_d_data, 29, -1, 1, 15 }; /* Chebyshev fit for F_{3/2}(t); -1 < t < 1, -1 < x < 1 */ static double fd_3half_a_data[20] = { 2.0404775940601704976, 0.8122168298093491444, 0.1536371165644008069, 0.0156174323847845125, 0.0005943427879290297, -0.0000429609447738365, -3.8246452994606e-6, 3.802306180287e-7, 4.05746157593e-8, -4.5530360159e-9, -5.306873139e-10, 6.37297268e-11, 7.8403674e-12, -9.840241e-13, -1.255952e-13, 1.62617e-14, 2.1318e-15, -2.825e-16, -3.78e-17, 5.1e-18 }; static cheb_series fd_3half_a_cs = { fd_3half_a_data, 19, -1, 1, 11 }; /* Chebyshev fit for F_{3/2}(3/2(t+1) + 1); -1 < t < 1, 1 < x < 4 */ static double fd_3half_b_data[22] = { 13.403206654624176674, 5.574508357051880924, 0.931228574387527769, 0.054638356514085862, -0.001477172902737439, -0.000029378553381869, 0.000018357033493246, -2.348059218454e-6, 8.3173787440e-8, 2.6826486956e-8, -6.011244398e-9, 4.94345981e-10, 3.9557340e-11, -1.7894930e-11, 2.348972e-12, -1.2823e-14, -5.4192e-14, 1.0527e-14, -6.39e-16, -1.47e-16, 4.5e-17, -5.e-18 }; static cheb_series fd_3half_b_cs = { fd_3half_b_data, 21, -1, 1, 12 }; /* Chebyshev fit for F_{3/2}(3(t+1) + 4); -1 < t < 1, 4 < x < 10 */ static double fd_3half_c_data[21] = { 101.03685253378877642, 43.62085156043435883, 6.62241373362387453, 0.25081415008708521, -0.00798124846271395, 0.00063462245101023, -0.00006392178890410, 6.04535131939e-6, -3.4007683037e-7, -4.072661545e-8, 1.931148453e-8, -4.46328355e-9, 7.9434717e-10, -1.1573569e-10, 1.304658e-11, -7.4114e-13, -1.4181e-13, 6.491e-14, -1.597e-14, 3.05e-15, -4.8e-16 }; static cheb_series fd_3half_c_cs = { fd_3half_c_data, 20, -1, 1, 12 }; /* Chebyshev fit for F_{3/2}(x) / x^(5/2) * 10 < x < 30 * -1 < t < 1 * t = 1/10 (x-10) - 1 = x/10 - 2 */ static double fd_3half_d_data[25] = { 0.6160645215171852381, -0.0071239478492671463, 0.0027906866139659846, -0.0009829521424317718, 0.0003260229808519545, -0.0001040160912910890, 0.0000322931223232439, -9.8243506588102e-6, 2.9420132351277e-6, -8.699154670418e-7, 2.545460071999e-7, -7.38305056331e-8, 2.12545670310e-8, -6.0796532462e-9, 1.7294556741e-9, -4.896540687e-10, 1.380786037e-10, -3.88057305e-11, 1.08753212e-11, -3.0407308e-12, 8.485626e-13, -2.364275e-13, 6.57636e-14, -1.81807e-14, 4.6884e-15 }; static cheb_series fd_3half_d_cs = { fd_3half_d_data, 24, -1, 1, 16 }; /* Goano's modification of the Levin-u implementation. * This is a simplification of the original WHIZ algorithm. * See [Fessler et al., ACM Toms 9, 346 (1983)]. */ static int fd_whiz(const double term, const int iterm, double * qnum, double * qden, double * result, double * s) { if(iterm == 0) *s = 0.0; *s += term; qden[iterm] = 1.0/(term*(iterm+1.0)*(iterm+1.0)); qnum[iterm] = *s * qden[iterm]; if(iterm > 0) { double factor = 1.0; double ratio = iterm/(iterm+1.0); int j; for(j=iterm-1; j>=0; j--) { double c = factor * (j+1.0) / (iterm+1.0); factor *= ratio; qden[j] = qden[j+1] - c * qden[j]; qnum[j] = qnum[j+1] - c * qnum[j]; } } *result = qnum[0] / qden[0]; return GSL_SUCCESS; } /* Handle case of integer j <= -2. */ static int fd_nint(const int j, const double x, gsl_sf_result * result) { /* const int nsize = 100 + 1; */ enum { nsize = 100+1 }; double qcoeff[nsize]; if(j >= -1) { result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_ESANITY); } else if(j < -(nsize)) { result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EUNIMPL); } else { double a, p, f; int i, k; int n = -(j+1); qcoeff[1] = 1.0; for(k=2; k<=n; k++) { qcoeff[k] = -qcoeff[k-1]; for(i=k-1; i>=2; i--) { qcoeff[i] = i*qcoeff[i] - (k-(i-1))*qcoeff[i-1]; } } if(x >= 0.0) { a = exp(-x); f = qcoeff[1]; for(i=2; i<=n; i++) { f = f*a + qcoeff[i]; } } else { a = exp(x); f = qcoeff[n]; for(i=n-1; i>=1; i--) { f = f*a + qcoeff[i]; } } p = gsl_sf_pow_int(1.0+a, j); result->val = f*a*p; result->err = 3.0 * GSL_DBL_EPSILON * fabs(f*a*p); return GSL_SUCCESS; } } /* x < 0 */ static int fd_neg(const double j, const double x, gsl_sf_result * result) { enum { itmax = 100, qsize = 100+1 }; /* const int itmax = 100; */ /* const int qsize = 100 + 1; */ double qnum[qsize], qden[qsize]; if(x < GSL_LOG_DBL_MIN) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < -1.0 && x < -fabs(j+1.0)) { /* Simple series implementation. Avoid the * complexity and extra work of the series * acceleration method below. */ double ex = exp(x); double term = ex; double sum = term; int n; for(n=2; n<100; n++) { double rat = (n-1.0)/n; double p = pow(rat, j+1.0); term *= -ex * p; sum += term; if(fabs(term/sum) < GSL_DBL_EPSILON) break; } result->val = sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(sum); return GSL_SUCCESS; } else { double s = 0.0; double xn = x; double ex = -exp(x); double enx = -ex; double f = 0.0; double f_previous; int jterm; for(jterm=0; jterm<=itmax; jterm++) { double p = pow(jterm+1.0, j+1.0); double term = enx/p; f_previous = f; fd_whiz(term, jterm, qnum, qden, &f, &s); xn += x; if(fabs(f-f_previous) < fabs(f)*2.0*GSL_DBL_EPSILON || xn < GSL_LOG_DBL_MIN) break; enx *= ex; } result->val = f; result->err = fabs(f-f_previous); result->err += 2.0 * GSL_DBL_EPSILON * fabs(f); if(jterm == itmax) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } } /* asymptotic expansion * j + 2.0 > 0.0 */ static int fd_asymp(const double j, const double x, gsl_sf_result * result) { const int j_integer = ( fabs(j - floor(j+0.5)) < 100.0*GSL_DBL_EPSILON ); const int itmax = 200; gsl_sf_result lg; int stat_lg = gsl_sf_lngamma_e(j + 2.0, &lg); double seqn_val = 0.5; double seqn_err = 0.0; double xm2 = (1.0/x)/x; double xgam = 1.0; double add = GSL_DBL_MAX; double cos_term; double ln_x; double ex_term_1; double ex_term_2; gsl_sf_result fneg; gsl_sf_result ex_arg; gsl_sf_result ex; int stat_fneg; int stat_e; int n; for(n=1; n<=itmax; n++) { double add_previous = add; gsl_sf_result eta; gsl_sf_eta_int_e(2*n, &eta); xgam = xgam * xm2 * (j + 1.0 - (2*n-2)) * (j + 1.0 - (2*n-1)); add = eta.val * xgam; if(!j_integer && fabs(add) > fabs(add_previous)) break; if(fabs(add/seqn_val) < GSL_DBL_EPSILON) break; seqn_val += add; seqn_err += 2.0 * GSL_DBL_EPSILON * fabs(add); } seqn_err += fabs(add); stat_fneg = fd_neg(j, -x, &fneg); ln_x = log(x); ex_term_1 = (j+1.0)*ln_x; ex_term_2 = lg.val; ex_arg.val = ex_term_1 - ex_term_2; /*(j+1.0)*ln_x - lg.val; */ ex_arg.err = GSL_DBL_EPSILON*(fabs(ex_term_1) + fabs(ex_term_2)) + lg.err; stat_e = gsl_sf_exp_err_e(ex_arg.val, ex_arg.err, &ex); cos_term = cos(j*M_PI); result->val = cos_term * fneg.val + 2.0 * seqn_val * ex.val; result->err = fabs(2.0 * ex.err * seqn_val); result->err += fabs(2.0 * ex.val * seqn_err); result->err += fabs(cos_term) * fneg.err; result->err += 4.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_e, stat_fneg, stat_lg); } /* Series evaluation for small x, generic j. * [Goano (8)] */ #if 0 static int fd_series(const double j, const double x, double * result) { const int nmax = 1000; int n; double sum = 0.0; double prev; double pow_factor = 1.0; double eta_factor; gsl_sf_eta_e(j + 1.0, &eta_factor); prev = pow_factor * eta_factor; sum += prev; for(n=1; n 0, integer j > 0; x < Pi. * [Goano (8)] */ static int fd_series_int(const int j, const double x, gsl_sf_result * result) { int n; double sum = 0.0; double del; double pow_factor = 1.0; gsl_sf_result eta_factor; gsl_sf_eta_int_e(j + 1, &eta_factor); del = pow_factor * eta_factor.val; sum += del; /* Sum terms where the argument * of eta() is positive. */ for(n=1; n<=j+2; n++) { gsl_sf_eta_int_e(j+1-n, &eta_factor); pow_factor *= x/n; del = pow_factor * eta_factor.val; sum += del; if(fabs(del/sum) < GSL_DBL_EPSILON) break; } /* Now sum the terms where eta() is negative. * The argument of eta() must be odd as well, * so it is convenient to transform the series * as follows: * * Sum[ eta(j+1-n) x^n / n!, {n,j+4,Infinity}] * = x^j / j! Sum[ eta(1-2m) x^(2m) j! / (2m+j)! , {m,2,Infinity}] * * We do not need to do this sum if j is large enough. */ if(j < 32) { int m; gsl_sf_result jfact; double sum2; double pre2; gsl_sf_fact_e((unsigned int)j, &jfact); pre2 = gsl_sf_pow_int(x, j) / jfact.val; gsl_sf_eta_int_e(-3, &eta_factor); pow_factor = x*x*x*x / ((j+4)*(j+3)*(j+2)*(j+1)); sum2 = eta_factor.val * pow_factor; for(m=3; m<24; m++) { gsl_sf_eta_int_e(1-2*m, &eta_factor); pow_factor *= x*x / ((j+2*m)*(j+2*m-1)); sum2 += eta_factor.val * pow_factor; } sum += pre2 * sum2; } result->val = sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(sum); return GSL_SUCCESS; } /* series of hypergeometric functions for integer j > 0, x > 0 * [Goano (7)] */ static int fd_UMseries_int(const int j, const double x, gsl_sf_result * result) { const int nmax = 2000; double pre; double lnpre_val; double lnpre_err; double sum_even_val = 1.0; double sum_even_err = 0.0; double sum_odd_val = 0.0; double sum_odd_err = 0.0; int stat_sum; int stat_e; int stat_h = GSL_SUCCESS; int n; if(x < 500.0 && j < 80) { double p = gsl_sf_pow_int(x, j+1); gsl_sf_result g; gsl_sf_fact_e(j+1, &g); /* Gamma(j+2) */ lnpre_val = 0.0; lnpre_err = 0.0; pre = p/g.val; } else { double lnx = log(x); gsl_sf_result lg; gsl_sf_lngamma_e(j + 2.0, &lg); lnpre_val = (j+1.0)*lnx - lg.val; lnpre_err = 2.0 * GSL_DBL_EPSILON * fabs((j+1.0)*lnx) + lg.err; pre = 1.0; } /* Add up the odd terms of the sum. */ for(n=1; n= nmax ? GSL_EMAXITER : GSL_SUCCESS ); stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, pre*(sum_even_val + sum_odd_val), pre*(sum_even_err + sum_odd_err), result); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_e, stat_h, stat_sum); } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ /* [Goano (4)] */ int gsl_sf_fermi_dirac_m1_e(const double x, gsl_sf_result * result) { if(x < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(x < 0.0) { const double ex = exp(x); result->val = ex/(1.0+ex); result->err = 2.0 * (fabs(x) + 1.0) * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double ex = exp(-x); result->val = 1.0/(1.0 + ex); result->err = 2.0 * GSL_DBL_EPSILON * (x + 1.0) * ex; return GSL_SUCCESS; } } /* [Goano (3)] */ int gsl_sf_fermi_dirac_0_e(const double x, gsl_sf_result * result) { if(x < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(x < -5.0) { double ex = exp(x); double ser = 1.0 - ex*(0.5 - ex*(1.0/3.0 - ex*(1.0/4.0 - ex*(1.0/5.0 - ex/6.0)))); result->val = ex * ser; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 10.0) { result->val = log(1.0 + exp(x)); result->err = fabs(x * GSL_DBL_EPSILON); return GSL_SUCCESS; } else { double ex = exp(-x); result->val = x + ex * (1.0 - 0.5*ex + ex*ex/3.0 - ex*ex*ex/4.0); result->err = (x + ex) * GSL_DBL_EPSILON; return GSL_SUCCESS; } } int gsl_sf_fermi_dirac_1_e(const double x, gsl_sf_result * result) { if(x < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(x < -1.0) { /* series [Goano (6)] */ double ex = exp(x); double term = ex; double sum = term; int n; for(n=2; n<100 ; n++) { double rat = (n-1.0)/n; term *= -ex * rat * rat; sum += term; if(fabs(term/sum) < GSL_DBL_EPSILON) break; } result->val = sum; result->err = 2.0 * fabs(sum) * GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < 1.0) { return cheb_eval_e(&fd_1_a_cs, x, result); } else if(x < 4.0) { double t = 2.0/3.0*(x-1.0) - 1.0; return cheb_eval_e(&fd_1_b_cs, t, result); } else if(x < 10.0) { double t = 1.0/3.0*(x-4.0) - 1.0; return cheb_eval_e(&fd_1_c_cs, t, result); } else if(x < 30.0) { double t = 0.1*x - 2.0; gsl_sf_result c; cheb_eval_e(&fd_1_d_cs, t, &c); result->val = c.val * x*x; result->err = c.err * x*x + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 1.0/GSL_SQRT_DBL_EPSILON) { double t = 60.0/x - 1.0; gsl_sf_result c; cheb_eval_e(&fd_1_e_cs, t, &c); result->val = c.val * x*x; result->err = c.err * x*x + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < GSL_SQRT_DBL_MAX) { result->val = 0.5 * x*x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_fermi_dirac_2_e(const double x, gsl_sf_result * result) { if(x < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(x < -1.0) { /* series [Goano (6)] */ double ex = exp(x); double term = ex; double sum = term; int n; for(n=2; n<100 ; n++) { double rat = (n-1.0)/n; term *= -ex * rat * rat * rat; sum += term; if(fabs(term/sum) < GSL_DBL_EPSILON) break; } result->val = sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(sum); return GSL_SUCCESS; } else if(x < 1.0) { return cheb_eval_e(&fd_2_a_cs, x, result); } else if(x < 4.0) { double t = 2.0/3.0*(x-1.0) - 1.0; return cheb_eval_e(&fd_2_b_cs, t, result); } else if(x < 10.0) { double t = 1.0/3.0*(x-4.0) - 1.0; return cheb_eval_e(&fd_2_c_cs, t, result); } else if(x < 30.0) { double t = 0.1*x - 2.0; gsl_sf_result c; cheb_eval_e(&fd_2_d_cs, t, &c); result->val = c.val * x*x*x; result->err = c.err * x*x*x + 3.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 1.0/GSL_ROOT3_DBL_EPSILON) { double t = 60.0/x - 1.0; gsl_sf_result c; cheb_eval_e(&fd_2_e_cs, t, &c); result->val = c.val * x*x*x; result->err = c.err * x*x*x + 3.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < GSL_ROOT3_DBL_MAX) { result->val = 1.0/6.0 * x*x*x; result->err = 3.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_fermi_dirac_int_e(const int j, const double x, gsl_sf_result * result) { if(j < -1) { return fd_nint(j, x, result); } else if (j == -1) { return gsl_sf_fermi_dirac_m1_e(x, result); } else if(j == 0) { return gsl_sf_fermi_dirac_0_e(x, result); } else if(j == 1) { return gsl_sf_fermi_dirac_1_e(x, result); } else if(j == 2) { return gsl_sf_fermi_dirac_2_e(x, result); } else if(x < 0.0) { return fd_neg(j, x, result); } else if(x == 0.0) { return gsl_sf_eta_int_e(j+1, result); } else if(x < 1.5) { return fd_series_int(j, x, result); } else { gsl_sf_result fasymp; int stat_asymp = fd_asymp(j, x, &fasymp); if(stat_asymp == GSL_SUCCESS) { result->val = fasymp.val; result->err = fasymp.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_asymp; } else { return fd_UMseries_int(j, x, result); } } } int gsl_sf_fermi_dirac_mhalf_e(const double x, gsl_sf_result * result) { if(x < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(x < -1.0) { /* series [Goano (6)] */ double ex = exp(x); double term = ex; double sum = term; int n; for(n=2; n<200 ; n++) { double rat = (n-1.0)/n; term *= -ex * sqrt(rat); sum += term; if(fabs(term/sum) < GSL_DBL_EPSILON) break; } result->val = sum; result->err = 2.0 * fabs(sum) * GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < 1.0) { return cheb_eval_e(&fd_mhalf_a_cs, x, result); } else if(x < 4.0) { double t = 2.0/3.0*(x-1.0) - 1.0; return cheb_eval_e(&fd_mhalf_b_cs, t, result); } else if(x < 10.0) { double t = 1.0/3.0*(x-4.0) - 1.0; return cheb_eval_e(&fd_mhalf_c_cs, t, result); } else if(x < 30.0) { double rtx = sqrt(x); double t = 0.1*x - 2.0; gsl_sf_result c; cheb_eval_e(&fd_mhalf_d_cs, t, &c); result->val = c.val * rtx; result->err = c.err * rtx + 0.5 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { return fd_asymp(-0.5, x, result); } } int gsl_sf_fermi_dirac_half_e(const double x, gsl_sf_result * result) { if(x < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(x < -1.0) { /* series [Goano (6)] */ double ex = exp(x); double term = ex; double sum = term; int n; for(n=2; n<100 ; n++) { double rat = (n-1.0)/n; term *= -ex * rat * sqrt(rat); sum += term; if(fabs(term/sum) < GSL_DBL_EPSILON) break; } result->val = sum; result->err = 2.0 * fabs(sum) * GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < 1.0) { return cheb_eval_e(&fd_half_a_cs, x, result); } else if(x < 4.0) { double t = 2.0/3.0*(x-1.0) - 1.0; return cheb_eval_e(&fd_half_b_cs, t, result); } else if(x < 10.0) { double t = 1.0/3.0*(x-4.0) - 1.0; return cheb_eval_e(&fd_half_c_cs, t, result); } else if(x < 30.0) { double x32 = x*sqrt(x); double t = 0.1*x - 2.0; gsl_sf_result c; cheb_eval_e(&fd_half_d_cs, t, &c); result->val = c.val * x32; result->err = c.err * x32 + 1.5 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { return fd_asymp(0.5, x, result); } } int gsl_sf_fermi_dirac_3half_e(const double x, gsl_sf_result * result) { if(x < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(x < -1.0) { /* series [Goano (6)] */ double ex = exp(x); double term = ex; double sum = term; int n; for(n=2; n<100 ; n++) { double rat = (n-1.0)/n; term *= -ex * rat * rat * sqrt(rat); sum += term; if(fabs(term/sum) < GSL_DBL_EPSILON) break; } result->val = sum; result->err = 2.0 * fabs(sum) * GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < 1.0) { return cheb_eval_e(&fd_3half_a_cs, x, result); } else if(x < 4.0) { double t = 2.0/3.0*(x-1.0) - 1.0; return cheb_eval_e(&fd_3half_b_cs, t, result); } else if(x < 10.0) { double t = 1.0/3.0*(x-4.0) - 1.0; return cheb_eval_e(&fd_3half_c_cs, t, result); } else if(x < 30.0) { double x52 = x*x*sqrt(x); double t = 0.1*x - 2.0; gsl_sf_result c; cheb_eval_e(&fd_3half_d_cs, t, &c); result->val = c.val * x52; result->err = c.err * x52 + 2.5 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { return fd_asymp(1.5, x, result); } } /* [Goano p. 222] */ int gsl_sf_fermi_dirac_inc_0_e(const double x, const double b, gsl_sf_result * result) { if(b < 0.0) { DOMAIN_ERROR(result); } else { double arg = b - x; gsl_sf_result f0; int status = gsl_sf_fermi_dirac_0_e(arg, &f0); result->val = f0.val - arg; result->err = f0.err + GSL_DBL_EPSILON * (fabs(x) + fabs(b)); return status; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_fermi_dirac_m1(const double x) { EVAL_RESULT(gsl_sf_fermi_dirac_m1_e(x, &result)); } double gsl_sf_fermi_dirac_0(const double x) { EVAL_RESULT(gsl_sf_fermi_dirac_0_e(x, &result)); } double gsl_sf_fermi_dirac_1(const double x) { EVAL_RESULT(gsl_sf_fermi_dirac_1_e(x, &result)); } double gsl_sf_fermi_dirac_2(const double x) { EVAL_RESULT(gsl_sf_fermi_dirac_2_e(x, &result)); } double gsl_sf_fermi_dirac_int(const int j, const double x) { EVAL_RESULT(gsl_sf_fermi_dirac_int_e(j, x, &result)); } double gsl_sf_fermi_dirac_mhalf(const double x) { EVAL_RESULT(gsl_sf_fermi_dirac_mhalf_e(x, &result)); } double gsl_sf_fermi_dirac_half(const double x) { EVAL_RESULT(gsl_sf_fermi_dirac_half_e(x, &result)); } double gsl_sf_fermi_dirac_3half(const double x) { EVAL_RESULT(gsl_sf_fermi_dirac_3half_e(x, &result)); } double gsl_sf_fermi_dirac_inc_0(const double x, const double b) { EVAL_RESULT(gsl_sf_fermi_dirac_inc_0_e(x, b, &result)); } sources_5316/external/gsl/gsl_wavelet__bspline.c0000664000176700017670000003673711723710247020713 0ustar paulpaul/* wavelet/bspline.c * * Copyright (C) 2004 Ivo Alxneit * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Coefficients are from A. Cohen, I. Daubechies, and J.-C. Feauveau; * "Biorthogonal Bases of Compactly Supported Wavelets", Communications * on Pure and Applied Mathematics, 45 (1992) 485--560 (table 6.1). * * Note the following errors in table 1: * * N = 2, N~ = 4, m0~ * the second term in z^-1 (45/64 z^-1) should be left out. * * N = 3, N~ = 7, m0~ * the term 336z^-3 should read 363z^-3. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_math.h" #include "gsl_wavelet.h" static const double h1_103[6] = { -0.0883883476483184405501055452631, 0.0883883476483184405501055452631, M_SQRT1_2, M_SQRT1_2, 0.0883883476483184405501055452631, -0.0883883476483184405501055452631 }; static const double g2_103[6] = { -0.0883883476483184405501055452631, -0.0883883476483184405501055452631, M_SQRT1_2, -(M_SQRT1_2), 0.0883883476483184405501055452631, 0.0883883476483184405501055452631 }; static const double h1_105[10] = { 0.0165728151840597076031447897368, -0.0165728151840597076031447897368, -0.1215339780164378557563951247368, 0.1215339780164378557563951247368, M_SQRT1_2, M_SQRT1_2, 0.1215339780164378557563951247368, -0.1215339780164378557563951247368, -0.0165728151840597076031447897368, 0.0165728151840597076031447897368 }; static const double g2_105[10] = { 0.0165728151840597076031447897368, 0.0165728151840597076031447897368, -0.1215339780164378557563951247368, -0.1215339780164378557563951247368, M_SQRT1_2, -(M_SQRT1_2), 0.1215339780164378557563951247368, 0.1215339780164378557563951247368, -0.0165728151840597076031447897368, -0.0165728151840597076031447897368 }; static const double g1_1[10] = { 0.0, 0.0, 0.0, 0.0, M_SQRT1_2, -(M_SQRT1_2), 0.0, 0.0, 0.0, 0.0 }; static const double h2_1[10] = { 0.0, 0.0, 0.0, 0.0, M_SQRT1_2, M_SQRT1_2, 0.0, 0.0, 0.0, 0.0 }; static const double h1_202[6] = { -0.1767766952966368811002110905262, 0.3535533905932737622004221810524, 1.0606601717798212866012665431573, 0.3535533905932737622004221810524, -0.1767766952966368811002110905262, 0.0 }; static const double g2_202[6] = { 0.0, -0.1767766952966368811002110905262, -0.3535533905932737622004221810524, 1.0606601717798212866012665431573, -0.3535533905932737622004221810524, -0.1767766952966368811002110905262 }; static const double h1_204[10] = { 0.0331456303681194152062895794737, -0.0662912607362388304125791589473, -0.1767766952966368811002110905262, 0.4198446513295125926130013399998, 0.9943689110435824561886873842099, 0.4198446513295125926130013399998, -0.1767766952966368811002110905262, -0.0662912607362388304125791589473, 0.0331456303681194152062895794737, 0.0 }; static const double g2_204[10] = { 0.0, 0.0331456303681194152062895794737, 0.0662912607362388304125791589473, -0.1767766952966368811002110905262, -0.4198446513295125926130013399998, 0.9943689110435824561886873842099, -0.4198446513295125926130013399998, -0.1767766952966368811002110905262, 0.0662912607362388304125791589473, 0.0331456303681194152062895794737 }; static const double h1_206[14] = { -0.0069053396600248781679769957237, 0.0138106793200497563359539914474, 0.0469563096881691715422435709210, -0.1077232986963880994204411332894, -0.1698713556366120029322340948025, 0.4474660099696121052849093228945, 0.9667475524034829435167794013152, 0.4474660099696121052849093228945, -0.1698713556366120029322340948025, -0.1077232986963880994204411332894, 0.0469563096881691715422435709210, 0.0138106793200497563359539914474, -0.0069053396600248781679769957237, 0.0 }; static const double g2_206[14] = { 0.0, -0.0069053396600248781679769957237, -0.0138106793200497563359539914474, 0.0469563096881691715422435709210, 0.1077232986963880994204411332894, -0.1698713556366120029322340948025, -0.4474660099696121052849093228945, 0.9667475524034829435167794013152, -0.4474660099696121052849093228945, -0.1698713556366120029322340948025, 0.1077232986963880994204411332894, 0.0469563096881691715422435709210, -0.0138106793200497563359539914474, -0.0069053396600248781679769957237, }; static const double h1_208[18] = { 0.0015105430506304420992449678146, -0.0030210861012608841984899356291, -0.0129475118625466465649568669819, 0.0289161098263541773284036695929, 0.0529984818906909399392234421792, -0.1349130736077360572068505539514, -0.1638291834340902345352542235443, 0.4625714404759165262773590010400, 0.9516421218971785225243297231697, 0.4625714404759165262773590010400, -0.1638291834340902345352542235443, -0.1349130736077360572068505539514, 0.0529984818906909399392234421792, 0.0289161098263541773284036695929, -0.0129475118625466465649568669819, -0.0030210861012608841984899356291, 0.0015105430506304420992449678146, 0.0 }; static const double g2_208[18] = { 0.0, 0.0015105430506304420992449678146, 0.0030210861012608841984899356291, -0.0129475118625466465649568669819, -0.0289161098263541773284036695929, 0.0529984818906909399392234421792, 0.1349130736077360572068505539514, -0.1638291834340902345352542235443, -0.4625714404759165262773590010400, 0.9516421218971785225243297231697, -0.4625714404759165262773590010400, -0.1638291834340902345352542235443, 0.1349130736077360572068505539514, 0.0529984818906909399392234421792, -0.0289161098263541773284036695929, -0.0129475118625466465649568669819, 0.0030210861012608841984899356291, 0.0015105430506304420992449678146, }; static const double h2_2[18] = { 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.3535533905932737622004221810524, 0.7071067811865475244008443621048, 0.3535533905932737622004221810524, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; static const double g1_2[18] = { 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -0.3535533905932737622004221810524, 0.7071067811865475244008443621048, -0.3535533905932737622004221810524, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; static const double h1_301[4] = { -0.3535533905932737622004221810524, 1.0606601717798212866012665431573, 1.0606601717798212866012665431573, -0.3535533905932737622004221810524 }; static const double g2_301[4] = { 0.3535533905932737622004221810524, 1.0606601717798212866012665431573, -1.0606601717798212866012665431573, -0.3535533905932737622004221810524 }; static const double h1_303[8] = { 0.0662912607362388304125791589473, -0.1988737822087164912377374768420, -0.1546796083845572709626847042104, 0.9943689110435824561886873842099, 0.9943689110435824561886873842099, -0.1546796083845572709626847042104, -0.1988737822087164912377374768420, 0.0662912607362388304125791589473 }; static const double g2_303[8] = { -0.0662912607362388304125791589473, -0.1988737822087164912377374768420, 0.1546796083845572709626847042104, 0.9943689110435824561886873842099, -0.9943689110435824561886873842099, -0.1546796083845572709626847042104, 0.1988737822087164912377374768420, 0.0662912607362388304125791589473 }; static const double h1_305[12] = { -0.0138106793200497563359539914474, 0.0414320379601492690078619743421, 0.0524805814161890740766251675000, -0.2679271788089652729175074340788, -0.0718155324642587329469607555263, 0.9667475524034829435167794013152, 0.9667475524034829435167794013152, -0.0718155324642587329469607555263, -0.2679271788089652729175074340788, 0.0524805814161890740766251675000, 0.0414320379601492690078619743421, -0.0138106793200497563359539914474 }; static const double g2_305[12] = { 0.0138106793200497563359539914474, 0.0414320379601492690078619743421, -0.0524805814161890740766251675000, -0.2679271788089652729175074340788, 0.0718155324642587329469607555263, 0.9667475524034829435167794013152, -0.9667475524034829435167794013152, -0.0718155324642587329469607555263, 0.2679271788089652729175074340788, 0.0524805814161890740766251675000, -0.0414320379601492690078619743421, -0.0138106793200497563359539914474 }; static const double h1_307[16] = { 0.0030210861012608841984899356291, -0.0090632583037826525954698068873, -0.0168317654213106405344439270765, 0.0746639850740189951912512662623, 0.0313329787073628846871956180962, -0.3011591259228349991008967259990, -0.0264992409453454699696117210896, 0.9516421218971785225243297231697, 0.9516421218971785225243297231697, -0.0264992409453454699696117210896, -0.3011591259228349991008967259990, 0.0313329787073628846871956180962, 0.0746639850740189951912512662623, -0.0168317654213106405344439270765, -0.0090632583037826525954698068873, 0.0030210861012608841984899356291 }; static const double g2_307[16] = { -0.0030210861012608841984899356291, -0.0090632583037826525954698068873, 0.0168317654213106405344439270765, 0.0746639850740189951912512662623, -0.0313329787073628846871956180962, -0.3011591259228349991008967259990, 0.0264992409453454699696117210896, 0.9516421218971785225243297231697, -0.9516421218971785225243297231697, -0.0264992409453454699696117210896, 0.3011591259228349991008967259990, 0.0313329787073628846871956180962, -0.0746639850740189951912512662623, -0.0168317654213106405344439270765, 0.0090632583037826525954698068873, 0.0030210861012608841984899356291 }; static const double h1_309[20] = { -0.0006797443727836989446602355165, 0.0020392331183510968339807065496, 0.0050603192196119810324706421788, -0.0206189126411055346546938106687, -0.0141127879301758447558029850103, 0.0991347824942321571990197448581, 0.0123001362694193142367090236328, -0.3201919683607785695513833204624, 0.0020500227115698857061181706055, 0.9421257006782067372990864259380, 0.9421257006782067372990864259380, 0.0020500227115698857061181706055, -0.3201919683607785695513833204624, 0.0123001362694193142367090236328, 0.0991347824942321571990197448581, -0.0141127879301758447558029850103, -0.0206189126411055346546938106687, 0.0050603192196119810324706421788, 0.0020392331183510968339807065496, -0.0006797443727836989446602355165 }; static const double g2_309[20] = { 0.0006797443727836989446602355165, 0.0020392331183510968339807065496, -0.0050603192196119810324706421788, -0.0206189126411055346546938106687, 0.0141127879301758447558029850103, 0.0991347824942321571990197448581, -0.0123001362694193142367090236328, -0.3201919683607785695513833204624, -0.0020500227115698857061181706055, 0.9421257006782067372990864259380, -0.9421257006782067372990864259380, 0.0020500227115698857061181706055, 0.3201919683607785695513833204624, 0.0123001362694193142367090236328, -0.0991347824942321571990197448581, -0.0141127879301758447558029850103, 0.0206189126411055346546938106687, 0.0050603192196119810324706421788, -0.0020392331183510968339807065496, -0.0006797443727836989446602355165 }; static const double h2_3[20] = { 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.1767766952966368811002110905262, 0.5303300858899106433006332715786, 0.5303300858899106433006332715786, 0.1767766952966368811002110905262, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; static const double g1_3[20] = { 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -0.1767766952966368811002110905262, 0.5303300858899106433006332715786, -0.5303300858899106433006332715786, 0.1767766952966368811002110905262, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; static int bspline_init (const double **h1, const double **g1, const double **h2, const double **g2, size_t * nc, size_t * offset, size_t member) { switch (member) { case 103: *nc = 6; *h1 = h1_103; *g1 = &g1_1[2]; *h2 = &h2_1[2]; *g2 = g2_103; break; case 105: *nc = 10; *h1 = h1_105; *g1 = g1_1; *h2 = h2_1; *g2 = g2_105; break; case 202: *nc = 6; *h1 = h1_202; *g1 = &g1_2[6]; *h2 = &h2_2[6]; *g2 = g2_202; break; case 204: *nc = 10; *h1 = h1_204; *g1 = &g1_2[4]; *h2 = &h2_2[4]; *g2 = g2_204; break; case 206: *nc = 14; *h1 = h1_206; *g1 = &g1_2[2]; *h2 = &h2_2[2]; *g2 = g2_206; break; case 208: *nc = 18; *h1 = h1_208; *g1 = g1_2; *h2 = h2_2; *g2 = g2_208; break; case 301: *nc = 4; *h1 = h1_301; *g1 = &g1_3[8]; *h2 = &h2_3[8]; *g2 = g2_301; break; case 303: *nc = 8; *h1 = h1_303; *g1 = &g1_3[6]; *h2 = &h2_3[6]; *g2 = g2_303; break; case 305: *nc = 12; *h1 = h1_305; *g1 = &g1_3[4]; *h2 = &h2_3[4]; *g2 = g2_305; break; case 307: *nc = 16; *h1 = h1_307; *g1 = &g1_3[2]; *h2 = &h2_3[2]; *g2 = g2_307; break; case 309: *nc = 20; *h1 = h1_309; *g1 = g1_3; *h2 = h2_3; *g2 = g2_309; break; default: return GSL_FAILURE; } *offset = 0; return GSL_SUCCESS; } static int bspline_centered_init (const double **h1, const double **g1, const double **h2, const double **g2, size_t * nc, size_t * offset, size_t member) { switch (member) { case 103: *nc = 6; *h1 = h1_103; *g1 = &g1_1[2]; *h2 = &h2_1[2]; *g2 = g2_103; break; case 105: *nc = 10; *h1 = h1_105; *g1 = g1_1; *h2 = h2_1; *g2 = g2_105; break; case 202: *nc = 6; *h1 = h1_202; *g1 = &g1_2[6]; *h2 = &h2_2[6]; *g2 = g2_202; break; case 204: *nc = 10; *h1 = h1_204; *g1 = &g1_2[4]; *h2 = &h2_2[4]; *g2 = g2_204; break; case 206: *nc = 14; *h1 = h1_206; *g1 = &g1_2[2]; *h2 = &h2_2[2]; *g2 = g2_206; break; case 208: *nc = 18; *h1 = h1_208; *g1 = g1_2; *h2 = h2_2; *g2 = g2_208; break; case 301: *nc = 4; *h1 = h1_301; *g1 = &g1_3[8]; *h2 = &h2_3[8]; *g2 = g2_301; break; case 303: *nc = 8; *h1 = h1_303; *g1 = &g1_3[6]; *h2 = &h2_3[6]; *g2 = g2_303; break; case 305: *nc = 12; *h1 = h1_305; *g1 = &g1_3[4]; *h2 = &h2_3[4]; *g2 = g2_305; break; case 307: *nc = 16; *h1 = h1_307; *g1 = &g1_3[2]; *h2 = &h2_3[2]; *g2 = g2_307; break; case 309: *nc = 20; *h1 = h1_309; *g1 = g1_3; *h2 = h2_3; *g2 = g2_309; break; default: return GSL_FAILURE; } *offset = ((*nc) >> 1); return GSL_SUCCESS; } static const gsl_wavelet_type bspline_type = { "bspline", &bspline_init }; static const gsl_wavelet_type bspline_centered_type = { "bspline-centered", &bspline_centered_init }; const gsl_wavelet_type *gsl_wavelet_bspline = &bspline_type; const gsl_wavelet_type *gsl_wavelet_bspline_centered = &bspline_centered_type; sources_5316/external/gsl/gsl_wavelet2d.h0000664000176700017670000001010711705263724017255 0ustar paulpaul/* wavelet/gsl_wavelet.h * * Copyright (C) 2004 Ivo Alxneit * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_WAVELET2D_H__ #define __GSL_WAVELET2D_H__ #include #include "gsl_errno.h" #include "gsl_vector_double.h" #include "gsl_matrix_double.h" #include "gsl_wavelet.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_wavelet2d_transform (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_direction dir, gsl_wavelet_workspace * work); int gsl_wavelet2d_transform_forward (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_workspace * work); int gsl_wavelet2d_transform_inverse (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_workspace * work); int gsl_wavelet2d_nstransform (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_direction dir, gsl_wavelet_workspace * work); int gsl_wavelet2d_nstransform_forward (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_workspace * work); int gsl_wavelet2d_nstransform_inverse (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_workspace * work); int gsl_wavelet2d_transform_matrix (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_direction dir, gsl_wavelet_workspace * work); int gsl_wavelet2d_transform_matrix_forward (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_workspace * work); int gsl_wavelet2d_transform_matrix_inverse (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_workspace * work); int gsl_wavelet2d_nstransform_matrix (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_direction dir, gsl_wavelet_workspace * work); int gsl_wavelet2d_nstransform_matrix_forward (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_workspace * work); int gsl_wavelet2d_nstransform_matrix_inverse (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_workspace * work); __END_DECLS #endif /* __GSL_WAVELET2D_H__ */ sources_5316/external/gsl/gsl_vector__prop.c0000664000176700017670000000362611723710247020061 0ustar paulpaul#include "gsl__config.h" #include "gsl_vector.h" #include "gsl_errno.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__prop_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_vector__minmax.c0000664000176700017670000000300411723710247020360 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__minmax_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_linalg__balance.c0000664000176700017670000000370711723710247020432 0ustar paulpaul/* linalg/balance.c * * Copyright (C) 2001, 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Balance a general matrix by scaling the columns * * B = A D * * where D is a diagonal matrix */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_linalg.h" int gsl_linalg_balance_columns (gsl_matrix * A, gsl_vector * D) { const size_t N = A->size2; size_t j; if (D->size != A->size2) { GSL_ERROR("length of D must match second dimension of A", GSL_EINVAL); } gsl_vector_set_all (D, 1.0); for (j = 0; j < N; j++) { gsl_vector_view A_j = gsl_matrix_column (A, j); double s = gsl_blas_dasum(&A_j.vector); double f = 1.0; if (s == 0.0 || !gsl_finite(s)) { gsl_vector_set (D, j, f); continue; } /* FIXME: we could use frexp() here */ while (s > 1.0) { s /= 2.0; f *= 2.0; } while (s < 0.5) { s *= 2.0; f /= 2.0; } gsl_vector_set (D, j, f); if (f != 1.0) { gsl_blas_dscal(1.0/f, &A_j.vector); } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_vector_float.h0000664000176700017670000001610211705263724020050 0ustar paulpaul/* vector/gsl_vector_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_FLOAT_H__ #define __GSL_VECTOR_FLOAT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_float.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; float *data; gsl_block_float *block; int owner; } gsl_vector_float; typedef struct { gsl_vector_float vector; } _gsl_vector_float_view; typedef _gsl_vector_float_view gsl_vector_float_view; typedef struct { gsl_vector_float vector; } _gsl_vector_float_const_view; typedef const _gsl_vector_float_const_view gsl_vector_float_const_view; /* Allocation */ gsl_vector_float *gsl_vector_float_alloc (const size_t n); gsl_vector_float *gsl_vector_float_calloc (const size_t n); gsl_vector_float *gsl_vector_float_alloc_from_block (gsl_block_float * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_float *gsl_vector_float_alloc_from_vector (gsl_vector_float * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_float_free (gsl_vector_float * v); /* Views */ _gsl_vector_float_view gsl_vector_float_view_array (float *v, size_t n); _gsl_vector_float_view gsl_vector_float_view_array_with_stride (float *base, size_t stride, size_t n); _gsl_vector_float_const_view gsl_vector_float_const_view_array (const float *v, size_t n); _gsl_vector_float_const_view gsl_vector_float_const_view_array_with_stride (const float *base, size_t stride, size_t n); _gsl_vector_float_view gsl_vector_float_subvector (gsl_vector_float *v, size_t i, size_t n); _gsl_vector_float_view gsl_vector_float_subvector_with_stride (gsl_vector_float *v, size_t i, size_t stride, size_t n); _gsl_vector_float_const_view gsl_vector_float_const_subvector (const gsl_vector_float *v, size_t i, size_t n); _gsl_vector_float_const_view gsl_vector_float_const_subvector_with_stride (const gsl_vector_float *v, size_t i, size_t stride, size_t n); /* Operations */ float gsl_vector_float_get (const gsl_vector_float * v, const size_t i); void gsl_vector_float_set (gsl_vector_float * v, const size_t i, float x); float *gsl_vector_float_ptr (gsl_vector_float * v, const size_t i); const float *gsl_vector_float_const_ptr (const gsl_vector_float * v, const size_t i); void gsl_vector_float_set_zero (gsl_vector_float * v); void gsl_vector_float_set_all (gsl_vector_float * v, float x); int gsl_vector_float_set_basis (gsl_vector_float * v, size_t i); int gsl_vector_float_fread (FILE * stream, gsl_vector_float * v); int gsl_vector_float_fwrite (FILE * stream, const gsl_vector_float * v); int gsl_vector_float_fscanf (FILE * stream, gsl_vector_float * v); int gsl_vector_float_fprintf (FILE * stream, const gsl_vector_float * v, const char *format); int gsl_vector_float_memcpy (gsl_vector_float * dest, const gsl_vector_float * src); int gsl_vector_float_reverse (gsl_vector_float * v); int gsl_vector_float_swap (gsl_vector_float * v, gsl_vector_float * w); int gsl_vector_float_swap_elements (gsl_vector_float * v, const size_t i, const size_t j); float gsl_vector_float_max (const gsl_vector_float * v); float gsl_vector_float_min (const gsl_vector_float * v); void gsl_vector_float_minmax (const gsl_vector_float * v, float * min_out, float * max_out); size_t gsl_vector_float_max_index (const gsl_vector_float * v); size_t gsl_vector_float_min_index (const gsl_vector_float * v); void gsl_vector_float_minmax_index (const gsl_vector_float * v, size_t * imin, size_t * imax); int gsl_vector_float_add (gsl_vector_float * a, const gsl_vector_float * b); int gsl_vector_float_sub (gsl_vector_float * a, const gsl_vector_float * b); int gsl_vector_float_mul (gsl_vector_float * a, const gsl_vector_float * b); int gsl_vector_float_div (gsl_vector_float * a, const gsl_vector_float * b); int gsl_vector_float_scale (gsl_vector_float * a, const double x); int gsl_vector_float_add_constant (gsl_vector_float * a, const double x); int gsl_vector_float_isnull (const gsl_vector_float * v); int gsl_vector_float_ispos (const gsl_vector_float * v); int gsl_vector_float_isneg (const gsl_vector_float * v); int gsl_vector_float_isnonneg (const gsl_vector_float * v); #ifdef HAVE_INLINE extern inline float gsl_vector_float_get (const gsl_vector_float * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_float_set (gsl_vector_float * v, const size_t i, float x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline float * gsl_vector_float_ptr (gsl_vector_float * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (float *) (v->data + i * v->stride); } extern inline const float * gsl_vector_float_const_ptr (const gsl_vector_float * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const float *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_FLOAT_H__ */ sources_5316/external/gsl/gsl_ieee-utils__endian.c0000664000176700017670000000216711723710247021101 0ustar paulpaul/* ieee-utils/endian.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_ieee_utils.h" static int little_endian_p (void) ; static int little_endian_p (void) { /* Are we little or big endian? From Harbison & Steele. */ union { long l; char c[sizeof (long)]; } u; u.l = 1; return (u.c[sizeof (long) - 1] == 1); } sources_5316/external/gsl/gsl_linalg__cholesky.c0000664000176700017670000001516211723710247020664 0ustar paulpaul/* Cholesky Decomposition * * Copyright (C) 2000 Thomas Walter * * 03 May 2000: Modified for GSL by Brian Gough * 29 Jul 2005: Additions by Gerard Jungman * Copyright (C) 2000,2001, 2002, 2003, 2005, 2007 Brian Gough, Gerard Jungman * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ /* * Cholesky decomposition of a symmetrix positive definite matrix. * This is useful to solve the matrix arising in * periodic cubic splines * approximating splines * * This algorithm does: * A = L * L' * with * L := lower left triangle matrix * L' := the transposed form of L. * */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_linalg.h" static inline double quiet_sqrt (double x) /* avoids runtime error, for checking matrix for positive definiteness */ { return (x >= 0) ? sqrt(x) : GSL_NAN; } int gsl_linalg_cholesky_decomp (gsl_matrix * A) { const size_t M = A->size1; const size_t N = A->size2; if (M != N) { GSL_ERROR("cholesky decomposition requires square matrix", GSL_ENOTSQR); } else { size_t i,j,k; int status = 0; /* Do the first 2 rows explicitly. It is simple, and faster. And * one can return if the matrix has only 1 or 2 rows. */ double A_00 = gsl_matrix_get (A, 0, 0); double L_00 = quiet_sqrt(A_00); if (A_00 <= 0) { status = GSL_EDOM ; } gsl_matrix_set (A, 0, 0, L_00); if (M > 1) { double A_10 = gsl_matrix_get (A, 1, 0); double A_11 = gsl_matrix_get (A, 1, 1); double L_10 = A_10 / L_00; double diag = A_11 - L_10 * L_10; double L_11 = quiet_sqrt(diag); if (diag <= 0) { status = GSL_EDOM; } gsl_matrix_set (A, 1, 0, L_10); gsl_matrix_set (A, 1, 1, L_11); } for (k = 2; k < M; k++) { double A_kk = gsl_matrix_get (A, k, k); for (i = 0; i < k; i++) { double sum = 0; double A_ki = gsl_matrix_get (A, k, i); double A_ii = gsl_matrix_get (A, i, i); gsl_vector_view ci = gsl_matrix_row (A, i); gsl_vector_view ck = gsl_matrix_row (A, k); if (i > 0) { gsl_vector_view di = gsl_vector_subvector(&ci.vector, 0, i); gsl_vector_view dk = gsl_vector_subvector(&ck.vector, 0, i); gsl_blas_ddot (&di.vector, &dk.vector, &sum); } A_ki = (A_ki - sum) / A_ii; gsl_matrix_set (A, k, i, A_ki); } { gsl_vector_view ck = gsl_matrix_row (A, k); gsl_vector_view dk = gsl_vector_subvector (&ck.vector, 0, k); double sum = gsl_blas_dnrm2 (&dk.vector); double diag = A_kk - sum * sum; double L_kk = quiet_sqrt(diag); if (diag <= 0) { status = GSL_EDOM; } gsl_matrix_set (A, k, k, L_kk); } } /* Now copy the transposed lower triangle to the upper triangle, * the diagonal is common. */ for (i = 1; i < M; i++) { for (j = 0; j < i; j++) { double A_ij = gsl_matrix_get (A, i, j); gsl_matrix_set (A, j, i, A_ij); } } if (status == GSL_EDOM) { GSL_ERROR ("matrix must be positive definite", GSL_EDOM); } return GSL_SUCCESS; } } int gsl_linalg_cholesky_solve (const gsl_matrix * LLT, const gsl_vector * b, gsl_vector * x) { if (LLT->size1 != LLT->size2) { GSL_ERROR ("cholesky matrix must be square", GSL_ENOTSQR); } else if (LLT->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (LLT->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve for c using forward-substitution, L c = b */ gsl_blas_dtrsv (CblasLower, CblasNoTrans, CblasNonUnit, LLT, x); /* Perform back-substitution, U x = c */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, LLT, x); return GSL_SUCCESS; } } int gsl_linalg_cholesky_svx (const gsl_matrix * LLT, gsl_vector * x) { if (LLT->size1 != LLT->size2) { GSL_ERROR ("cholesky matrix must be square", GSL_ENOTSQR); } else if (LLT->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Solve for c using forward-substitution, L c = b */ gsl_blas_dtrsv (CblasLower, CblasNoTrans, CblasNonUnit, LLT, x); /* Perform back-substitution, U x = c */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, LLT, x); return GSL_SUCCESS; } } int gsl_linalg_cholesky_decomp_unit(gsl_matrix * A, gsl_vector * D) { const size_t N = A->size1; size_t i, j; /* initial Cholesky */ int stat_chol = gsl_linalg_cholesky_decomp(A); if(stat_chol == GSL_SUCCESS) { /* calculate D from diagonal part of initial Cholesky */ for(i = 0; i < N; ++i) { const double C_ii = gsl_matrix_get(A, i, i); gsl_vector_set(D, i, C_ii*C_ii); } /* multiply initial Cholesky by 1/sqrt(D) on the right */ for(i = 0; i < N; ++i) { for(j = 0; j < N; ++j) { gsl_matrix_set(A, i, j, gsl_matrix_get(A, i, j) / sqrt(gsl_vector_get(D, j))); } } /* Because the initial Cholesky contained both L and transpose(L), the result of the multiplication is not symmetric anymore; but the lower triangle _is_ correct. Therefore we reflect it to the upper triangle and declare victory. */ for(i = 0; i < N; ++i) for(j = i + 1; j < N; ++j) gsl_matrix_set(A, i, j, gsl_matrix_get(A, j, i)); } return stat_chol; } sources_5316/external/gsl/gsl_roots__steffenson.c0000664000176700017670000000673411723710247021122 0ustar paulpaul/* roots/steffenson.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* steffenson.c -- steffenson root finding algorithm This is Newton's method with an Aitken "delta-squared" acceleration of the iterates. This can improve the convergence on multiple roots where the ordinary Newton algorithm is slow. x[i+1] = x[i] - f(x[i]) / f'(x[i]) x_accelerated[i] = x[i] - (x[i+1] - x[i])**2 / (x[i+2] - 2*x[i+1] + x[i]) We can only use the accelerated estimate after three iterations, and use the unaccelerated value until then. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_roots.h" #include "gsl_roots__roots.h" typedef struct { double f, df; double x; double x_1; double x_2; int count; } steffenson_state_t; static int steffenson_init (void * vstate, gsl_function_fdf * fdf, double * root); static int steffenson_iterate (void * vstate, gsl_function_fdf * fdf, double * root); static int steffenson_init (void * vstate, gsl_function_fdf * fdf, double * root) { steffenson_state_t * state = (steffenson_state_t *) vstate; const double x = *root ; state->f = GSL_FN_FDF_EVAL_F (fdf, x); state->df = GSL_FN_FDF_EVAL_DF (fdf, x) ; state->x = x; state->x_1 = 0.0; state->x_2 = 0.0; state->count = 1; return GSL_SUCCESS; } static int steffenson_iterate (void * vstate, gsl_function_fdf * fdf, double * root) { steffenson_state_t * state = (steffenson_state_t *) vstate; double x_new, f_new, df_new; double x_1 = state->x_1 ; double x = state->x ; if (state->df == 0.0) { GSL_ERROR("derivative is zero", GSL_EZERODIV); } x_new = x - (state->f / state->df); GSL_FN_FDF_EVAL_F_DF(fdf, x_new, &f_new, &df_new); state->x_2 = x_1 ; state->x_1 = x ; state->x = x_new; state->f = f_new ; state->df = df_new ; if (!gsl_finite (f_new)) { GSL_ERROR ("function value is not finite", GSL_EBADFUNC); } if (state->count < 3) { *root = x_new ; state->count++ ; } else { double u = (x - x_1) ; double v = (x_new - 2 * x + x_1); if (v == 0) *root = x_new; /* avoid division by zero */ else *root = x_1 - u * u / v ; /* accelerated value */ } if (!gsl_finite (df_new)) { GSL_ERROR ("derivative value is not finite", GSL_EBADFUNC); } return GSL_SUCCESS; } static const gsl_root_fdfsolver_type steffenson_type = {"steffenson", /* name */ sizeof (steffenson_state_t), &steffenson_init, &steffenson_iterate}; const gsl_root_fdfsolver_type * gsl_root_fdfsolver_steffenson = &steffenson_type; sources_5316/external/gsl/gsl_ieee-utils__fp-freebsd.c0000664000176700017670000000465011723710247021657 0ustar paulpaul/* ieee-utils/fp-freebsd.c * * Copyright (C) 2000 Vladimir Kushnir * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { fp_prec_t prec = 0 ; fp_except_t mode = 0 ; fp_rnd_t rnd = 0 ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: prec = FP_PS; fpsetprec(prec); break ; case GSL_IEEE_DOUBLE_PRECISION: prec = FP_PD; fpsetprec(prec); break ; case GSL_IEEE_EXTENDED_PRECISION: prec = FP_PE; fpsetprec(prec); break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: rnd = FP_RN ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_DOWN: rnd = FP_RM ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_UP: rnd = FP_RP ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_TO_ZERO: rnd = FP_RZ ; fpsetround (rnd) ; break ; default: rnd = FP_RN ; fpsetround (rnd) ; } /* Turn on all the exceptions apart from 'inexact' */ mode = FP_X_INV | FP_X_DNML | FP_X_DZ | FP_X_OFL | FP_X_UFL ; if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ FP_X_INV ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) mode &= ~ FP_X_DNML ; if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ FP_X_DZ ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ FP_X_OFL ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ FP_X_UFL ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode |= FP_X_IMP ; } else { mode &= ~ FP_X_IMP ; } fpsetmask (mode) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_cblas__source_tbmv_r.h0000664000176700017670000000667611705263724021554 0ustar paulpaul/* blas/source_tbmv_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; const int nonunit = (Diag == CblasNonUnit); const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; if (N == 0) return; if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { /* form x := A*x */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE temp = (nonunit ? A[lda * i + 0] : 1.0) * X[ix]; const INDEX j_min = i + 1; const INDEX j_max = GSL_MIN(N, i + K + 1); INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { temp += X[jx] * A[lda * i + (j - i)]; jx += incX; } X[ix] = temp; ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { BASE temp = (nonunit ? A[lda * i + K] : 1.0) * X[ix]; const INDEX j_min = (i > K ? i - K : 0); const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { temp += X[jx] * A[lda * i + (K - i + j)]; jx += incX; } X[ix] = temp; ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := A'*x */ INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { BASE temp = 0.0; const INDEX j_min = (K > i ? 0 : i - K); const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { temp += X[jx] * A[lda * j + (i - j)]; jx += incX; } if (nonunit) { X[ix] = temp + X[ix] * A[lda * i + 0]; } else { X[ix] += temp; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE temp = 0.0; const INDEX j_min = i + 1; const INDEX j_max = GSL_MIN(N, i + K + 1); INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { temp += X[jx] * A[lda * j + (K - j + i)]; jx += incX; } if (nonunit) { X[ix] = temp + X[ix] * A[lda * i + K]; } else { X[ix] += temp; } ix += incX; } } } sources_5316/external/gsl/gsl_rng__taus113.c0000664000176700017670000001257011723710247017564 0ustar paulpaul/* rng/taus113.c * Copyright (C) 2002 Atakan Gurkan * Based on the file taus.c which has the notice * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* This is a maximally equidistributed combined, collision free Tausworthe generator, with a period ~2^{113}. The sequence is, x_n = (z1_n ^ z2_n ^ z3_n ^ z4_n) b = (((z1_n << 6) ^ z1_n) >> 13) z1_{n+1} = (((z1_n & 4294967294) << 18) ^ b) b = (((z2_n << 2) ^ z2_n) >> 27) z2_{n+1} = (((z2_n & 4294967288) << 2) ^ b) b = (((z3_n << 13) ^ z3_n) >> 21) z3_{n+1} = (((z3_n & 4294967280) << 7) ^ b) b = (((z4_n << 3) ^ z4_n) >> 12) z4_{n+1} = (((z4_n & 4294967168) << 13) ^ b) computed modulo 2^32. In the formulas above '^' means exclusive-or (C-notation), not exponentiation. The algorithm is for 32-bit integers, hence a bitmask is used to clear all but least significant 32 bits, after left shifts, to make the code work on architectures where integers are 64-bit. The generator is initialized with zi = (69069 * z{i+1}) MOD 2^32 where z0 is the seed provided During initialization a check is done to make sure that the initial seeds have a required number of their most significant bits set. After this, the state is passed through the RNG 10 times to ensure the state satisfies a recurrence relation. References: P. L'Ecuyer, "Tables of Maximally-Equidistributed Combined LFSR Generators", Mathematics of Computation, 68, 225 (1999), 261--269. http://www.iro.umontreal.ca/~lecuyer/myftp/papers/tausme2.ps P. L'Ecuyer, "Maximally Equidistributed Combined Tausworthe Generators", Mathematics of Computation, 65, 213 (1996), 203--213. http://www.iro.umontreal.ca/~lecuyer/myftp/papers/tausme.ps the online version of the latter contains corrections to the print version. */ #include "gsl__config.h" #include #include "gsl_rng.h" #define LCG(n) ((69069UL * n) & 0xffffffffUL) #define MASK 0xffffffffUL static inline unsigned long int taus113_get (void *vstate); static double taus113_get_double (void *vstate); static void taus113_set (void *state, unsigned long int s); typedef struct { unsigned long int z1, z2, z3, z4; } taus113_state_t; static inline unsigned long taus113_get (void *vstate) { taus113_state_t *state = (taus113_state_t *) vstate; unsigned long b1, b2, b3, b4; b1 = ((((state->z1 << 6UL) & MASK) ^ state->z1) >> 13UL); state->z1 = ((((state->z1 & 4294967294UL) << 18UL) & MASK) ^ b1); b2 = ((((state->z2 << 2UL) & MASK) ^ state->z2) >> 27UL); state->z2 = ((((state->z2 & 4294967288UL) << 2UL) & MASK) ^ b2); b3 = ((((state->z3 << 13UL) & MASK) ^ state->z3) >> 21UL); state->z3 = ((((state->z3 & 4294967280UL) << 7UL) & MASK) ^ b3); b4 = ((((state->z4 << 3UL) & MASK) ^ state->z4) >> 12UL); state->z4 = ((((state->z4 & 4294967168UL) << 13UL) & MASK) ^ b4); return (state->z1 ^ state->z2 ^ state->z3 ^ state->z4); } static double taus113_get_double (void *vstate) { return taus113_get (vstate) / 4294967296.0; } static void taus113_set (void *vstate, unsigned long int s) { taus113_state_t *state = (taus113_state_t *) vstate; if (!s) s = 1UL; /* default seed is 1 */ state->z1 = LCG (s); if (state->z1 < 2UL) state->z1 += 2UL; state->z2 = LCG (state->z1); if (state->z2 < 8UL) state->z2 += 8UL; state->z3 = LCG (state->z2); if (state->z3 < 16UL) state->z3 += 16UL; state->z4 = LCG (state->z3); if (state->z4 < 128UL) state->z4 += 128UL; /* Calling RNG ten times to satify recurrence condition */ taus113_get (state); taus113_get (state); taus113_get (state); taus113_get (state); taus113_get (state); taus113_get (state); taus113_get (state); taus113_get (state); taus113_get (state); taus113_get (state); return; } static const gsl_rng_type taus113_type = { "taus113", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (taus113_state_t), &taus113_set, &taus113_get, &taus113_get_double }; const gsl_rng_type *gsl_rng_taus113 = &taus113_type; /* Rules for analytic calculations using GNU Emacs Calc: (used to find the values for the test program) [ LCG(n) := n * 69069 mod (2^32) ] [ b1(x) := rsh(xor(lsh(x, 6), x), 13), q1(x) := xor(lsh(and(x, 4294967294), 18), b1(x)), b2(x) := rsh(xor(lsh(x, 2), x), 27), q2(x) := xor(lsh(and(x, 4294967288), 2), b2(x)), b3(x) := rsh(xor(lsh(x, 13), x), 21), q3(x) := xor(lsh(and(x, 4294967280), 7), b3(x)), b4(x) := rsh(xor(lsh(x, 3), x), 12), q4(x) := xor(lsh(and(x, 4294967168), 13), b4(x)) ] [ S([z1,z2,z3,z4]) := [q1(z1), q2(z2), q3(z3), q4(z4)] ] */ sources_5316/external/gsl/gsl_rng__fishman18.c0000664000176700017670000000444711723710247020165 0ustar paulpaul/* rng/fishman18.c * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth * The Art of Computer Programming * Volume 2 * Third Edition * Addison-Wesley * Page 106-108 * * It is called "Fishman - Moore III". * * This implementation copyright (C) 2001 Carlo Perassi * and (C) 2003 Heiko Bauke. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_rng__schrage.c" #define AA 62089911UL #define MM 0x7fffffffUL /* 2 ^ 31 - 1 */ #define CEIL_SQRT_MM 46341UL /* ceil(sqrt(2 ^ 31 - 1)) */ static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); typedef struct { unsigned long int x; } ran_state_t; static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; state->x = schrage_mult (AA, state->x, MM, CEIL_SQRT_MM); return state->x; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 2147483647.0; } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; if ((s % MM) == 0) s = 1; /* default seed is 1 */ state->x = s % MM; return; } static const gsl_rng_type ran_type = { "fishman18", /* name */ MM - 1, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_fishman18 = &ran_type; sources_5316/external/gsl/gsl_cdf.h0000664000176700017670000001631111705263724016117 0ustar paulpaul/* cdf/gsl_cdf.h * * Copyright (C) 2002 Jason H. Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* Author: J. Stover */ #ifndef __GSL_CDF_H__ #define __GSL_CDF_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_cdf_ugaussian_P (const double x); double gsl_cdf_ugaussian_Q (const double x); double gsl_cdf_ugaussian_Pinv (const double P); double gsl_cdf_ugaussian_Qinv (const double Q); double gsl_cdf_gaussian_P (const double x, const double sigma); double gsl_cdf_gaussian_Q (const double x, const double sigma); double gsl_cdf_gaussian_Pinv (const double P, const double sigma); double gsl_cdf_gaussian_Qinv (const double Q, const double sigma); double gsl_cdf_gamma_P (const double x, const double a, const double b); double gsl_cdf_gamma_Q (const double x, const double a, const double b); double gsl_cdf_gamma_Pinv (const double P, const double a, const double b); double gsl_cdf_gamma_Qinv (const double Q, const double a, const double b); double gsl_cdf_cauchy_P (const double x, const double a); double gsl_cdf_cauchy_Q (const double x, const double a); double gsl_cdf_cauchy_Pinv (const double P, const double a); double gsl_cdf_cauchy_Qinv (const double Q, const double a); double gsl_cdf_laplace_P (const double x, const double a); double gsl_cdf_laplace_Q (const double x, const double a); double gsl_cdf_laplace_Pinv (const double P, const double a); double gsl_cdf_laplace_Qinv (const double Q, const double a); double gsl_cdf_rayleigh_P (const double x, const double sigma); double gsl_cdf_rayleigh_Q (const double x, const double sigma); double gsl_cdf_rayleigh_Pinv (const double P, const double sigma); double gsl_cdf_rayleigh_Qinv (const double Q, const double sigma); double gsl_cdf_chisq_P (const double x, const double nu); double gsl_cdf_chisq_Q (const double x, const double nu); double gsl_cdf_chisq_Pinv (const double P, const double nu); double gsl_cdf_chisq_Qinv (const double Q, const double nu); double gsl_cdf_exponential_P (const double x, const double mu); double gsl_cdf_exponential_Q (const double x, const double mu); double gsl_cdf_exponential_Pinv (const double P, const double mu); double gsl_cdf_exponential_Qinv (const double Q, const double mu); double gsl_cdf_exppow_P (const double x, const double a, const double b); double gsl_cdf_exppow_Q (const double x, const double a, const double b); double gsl_cdf_tdist_P (const double x, const double nu); double gsl_cdf_tdist_Q (const double x, const double nu); double gsl_cdf_tdist_Pinv (const double P, const double nu); double gsl_cdf_tdist_Qinv (const double Q, const double nu); double gsl_cdf_fdist_P (const double x, const double nu1, const double nu2); double gsl_cdf_fdist_Q (const double x, const double nu1, const double nu2); double gsl_cdf_fdist_Pinv (const double P, const double nu1, const double nu2); double gsl_cdf_fdist_Qinv (const double Q, const double nu1, const double nu2); double gsl_cdf_beta_P (const double x, const double a, const double b); double gsl_cdf_beta_Q (const double x, const double a, const double b); double gsl_cdf_beta_Pinv (const double P, const double a, const double b); double gsl_cdf_beta_Qinv (const double Q, const double a, const double b); double gsl_cdf_flat_P (const double x, const double a, const double b); double gsl_cdf_flat_Q (const double x, const double a, const double b); double gsl_cdf_flat_Pinv (const double P, const double a, const double b); double gsl_cdf_flat_Qinv (const double Q, const double a, const double b); double gsl_cdf_lognormal_P (const double x, const double zeta, const double sigma); double gsl_cdf_lognormal_Q (const double x, const double zeta, const double sigma); double gsl_cdf_lognormal_Pinv (const double P, const double zeta, const double sigma); double gsl_cdf_lognormal_Qinv (const double Q, const double zeta, const double sigma); double gsl_cdf_gumbel1_P (const double x, const double a, const double b); double gsl_cdf_gumbel1_Q (const double x, const double a, const double b); double gsl_cdf_gumbel1_Pinv (const double P, const double a, const double b); double gsl_cdf_gumbel1_Qinv (const double Q, const double a, const double b); double gsl_cdf_gumbel2_P (const double x, const double a, const double b); double gsl_cdf_gumbel2_Q (const double x, const double a, const double b); double gsl_cdf_gumbel2_Pinv (const double P, const double a, const double b); double gsl_cdf_gumbel2_Qinv (const double Q, const double a, const double b); double gsl_cdf_weibull_P (const double x, const double a, const double b); double gsl_cdf_weibull_Q (const double x, const double a, const double b); double gsl_cdf_weibull_Pinv (const double P, const double a, const double b); double gsl_cdf_weibull_Qinv (const double Q, const double a, const double b); double gsl_cdf_pareto_P (const double x, const double a, const double b); double gsl_cdf_pareto_Q (const double x, const double a, const double b); double gsl_cdf_pareto_Pinv (const double P, const double a, const double b); double gsl_cdf_pareto_Qinv (const double Q, const double a, const double b); double gsl_cdf_logistic_P (const double x, const double a); double gsl_cdf_logistic_Q (const double x, const double a); double gsl_cdf_logistic_Pinv (const double P, const double a); double gsl_cdf_logistic_Qinv (const double Q, const double a); double gsl_cdf_binomial_P (const unsigned int k, const double p, const unsigned int n); double gsl_cdf_binomial_Q (const unsigned int k, const double p, const unsigned int n); double gsl_cdf_poisson_P (const unsigned int k, const double mu); double gsl_cdf_poisson_Q (const unsigned int k, const double mu); double gsl_cdf_geometric_P (const unsigned int k, const double p); double gsl_cdf_geometric_Q (const unsigned int k, const double p); double gsl_cdf_negative_binomial_P (const unsigned int k, const double p, const double n); double gsl_cdf_negative_binomial_Q (const unsigned int k, const double p, const double n); double gsl_cdf_pascal_P (const unsigned int k, const double p, const unsigned int n); double gsl_cdf_pascal_Q (const unsigned int k, const double p, const unsigned int n); double gsl_cdf_hypergeometric_P (const unsigned int k, const unsigned int n1, const unsigned int n2, const unsigned int t); double gsl_cdf_hypergeometric_Q (const unsigned int k, const unsigned int n1, const unsigned int n2, const unsigned int t); __END_DECLS #endif /* __GSL_CDF_H__ */ sources_5316/external/gsl/gsl_sf__bessel_Y0.c0000644000176700017670000000707710707442037020036 0ustar paulpaul/* specfunc/bessel_Y0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_amp_phase.h" #include "gsl_sf__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besy0, 1980 version, w. fullerton */ /* chebyshev expansions series for by0 on the interval 0. to 1.60000d+01 with weighted error 1.20e-17 log weighted error 16.92 significant figures required 16.15 decimal places required 17.48 */ static double by0_data[13] = { -0.011277839392865573, -0.128345237560420350, -0.104378847997942490, 0.023662749183969695, -0.002090391647700486, 0.000103975453939057, -0.000003369747162423, 0.000000077293842676, -0.000000001324976772, 0.000000000017648232, -0.000000000000188105, 0.000000000000001641, -0.000000000000000011 }; static cheb_series by0_cs = { by0_data, 12, -1, 1, 8 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Y0_e(const double x, gsl_sf_result * result) { const double two_over_pi = 2.0/M_PI; const double xmax = 1.0/GSL_DBL_EPSILON; /* CHECK_POINTER(result) */ if (x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 4.0) { gsl_sf_result J0; gsl_sf_result c; int stat_J0 = gsl_sf_bessel_J0_e(x, &J0); cheb_eval_e(&by0_cs, 0.125*x*x-1.0, &c); result->val = two_over_pi*(-M_LN2 + log(x))*J0.val + 0.375 + c.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + c.err; return stat_J0; } else if(x < xmax) { /* Leading behaviour of phase is x, which is exact, * so the error is bounded. */ const double z = 32.0/(x*x) - 1.0; gsl_sf_result c1; gsl_sf_result c2; gsl_sf_result sp; const int stat_c1 = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bm0_cs, z, &c1); const int stat_c2 = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bth0_cs, z, &c2); const int stat_sp = gsl_sf_bessel_sin_pi4_e(x, c2.val/x, &sp); const double sqrtx = sqrt(x); const double ampl = (0.75 + c1.val) / sqrtx; result->val = ampl * sp.val; result->err = fabs(sp.val) * c1.err/sqrtx + fabs(ampl) * sp.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_sp, stat_c1, stat_c2); } else { UNDERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_Y0(const double x) { EVAL_RESULT(gsl_sf_bessel_Y0_e(x, &result)); } sources_5316/external/gsl/gsl_sys__minmax.c0000664000176700017670000000363111723710247017702 0ustar paulpaul/* sys/minmax.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #define GSL_MAX(a,b) ((a) > (b) ? (a) : (b)) #define GSL_MIN(a,b) ((a) < (b) ? (a) : (b)) #ifndef HIDE_INLINE_STATIC int GSL_MAX_INT (int a, int b); int GSL_MIN_INT (int a, int b); double GSL_MAX_DBL (double a, double b); double GSL_MIN_DBL (double a, double b); long double GSL_MAX_LDBL (long double a, long double b); long double GSL_MIN_LDBL (long double a, long double b); int GSL_MAX_INT (int a, int b) { return GSL_MAX (a, b); } int GSL_MIN_INT (int a, int b) { return GSL_MIN (a, b); } double GSL_MAX_DBL (double a, double b) { return GSL_MAX (a, b); } double GSL_MIN_DBL (double a, double b) { return GSL_MIN (a, b); } long double GSL_MAX_LDBL (long double a, long double b) { return GSL_MAX (a, b); } long double GSL_MIN_LDBL (long double a, long double b) { return GSL_MIN (a, b); } #endif /* Define some static functions which are always available */ double gsl_max (double a, double b); double gsl_min (double a, double b); double gsl_max (double a, double b) { return GSL_MAX (a, b); } double gsl_min (double a, double b) { return GSL_MIN (a, b); } sources_5316/external/gsl/gsl_cblas__ssbmv.c0000664000176700017670000000063611723710247020013 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ssbmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const int K, const float alpha, const float *A, const int lda, const float *X, const int incX, const float beta, float *Y, const int incY) { #define BASE float #include "gsl_cblas__source_sbmv.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_tbmv_c.h0000664000176700017670000001422711705263724021524 0ustar paulpaul/* blas/source_tbmv_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (TransA == CblasConjTrans) ? -1 : 1; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; const int nonunit = (Diag == CblasNonUnit); INDEX i, j; if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { /* form x := A*x */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE temp_r = 0.0; BASE temp_i = 0.0; const INDEX j_min = i + 1; const INDEX j_max = GSL_MIN(N, i + K + 1); INDEX jx = OFFSET(N, incX) + incX * j_min; for (j = j_min; j < j_max; j++) { const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); const BASE A_real = CONST_REAL(A, lda * i + (j - i)); const BASE A_imag = conj * CONST_IMAG(A, lda * i + (j - i)); temp_r += A_real * x_real - A_imag * x_imag; temp_i += A_real * x_imag + A_imag * x_real; jx += incX; } if (nonunit) { const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + 0); const BASE A_imag = conj * CONST_IMAG(A, lda * i + 0); REAL(X, ix) = temp_r + (A_real * x_real - A_imag * x_imag); IMAG(X, ix) = temp_i + (A_real * x_imag + A_imag * x_real); } else { REAL(X, ix) += temp_r; IMAG(X, ix) += temp_i; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { /* N-1 ... 0 */ BASE temp_r = 0.0; BASE temp_i = 0.0; const INDEX j_min = (K > i ? 0 : i - K); const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); const BASE A_real = CONST_REAL(A, lda * i + (K - i + j)); const BASE A_imag = conj * CONST_IMAG(A, lda * i + (K - i + j)); temp_r += A_real * x_real - A_imag * x_imag; temp_i += A_real * x_imag + A_imag * x_real; jx += incX; } if (nonunit) { const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + K); const BASE A_imag = conj * CONST_IMAG(A, lda * i + K); REAL(X, ix) = temp_r + (A_real * x_real - A_imag * x_imag); IMAG(X, ix) = temp_i + (A_real * x_imag + A_imag * x_real); } else { REAL(X, ix) += temp_r; IMAG(X, ix) += temp_i; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := A'*x */ INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { /* N-1 ... 0 */ BASE temp_r = 0.0; BASE temp_i = 0.0; const INDEX j_min = (K > i ? 0 : i - K); const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); const BASE A_real = CONST_REAL(A, lda * j + (i - j)); const BASE A_imag = conj * CONST_IMAG(A, lda * j + (i - j)); temp_r += A_real * x_real - A_imag * x_imag; temp_i += A_real * x_imag + A_imag * x_real; jx += incX; } if (nonunit) { const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + 0); const BASE A_imag = conj * CONST_IMAG(A, lda * i + 0); REAL(X, ix) = temp_r + (A_real * x_real - A_imag * x_imag); IMAG(X, ix) = temp_i + (A_real * x_imag + A_imag * x_real); } else { REAL(X, ix) += temp_r; IMAG(X, ix) += temp_i; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE temp_r = 0.0; BASE temp_i = 0.0; const INDEX j_min = i + 1; const INDEX j_max = GSL_MIN(N, i + K + 1); INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); const BASE A_real = CONST_REAL(A, lda * j + (K - j + i)); const BASE A_imag = conj * CONST_IMAG(A, lda * j + (K - j + i)); temp_r += A_real * x_real - A_imag * x_imag; temp_i += A_real * x_imag + A_imag * x_real; jx += incX; } if (nonunit) { const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + K); const BASE A_imag = conj * CONST_IMAG(A, lda * i + K); REAL(X, ix) = temp_r + (A_real * x_real - A_imag * x_imag); IMAG(X, ix) = temp_i + (A_real * x_imag + A_imag * x_real); } else { REAL(X, ix) += temp_r; IMAG(X, ix) += temp_i; } ix += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_permute_vector_double.h0000664000176700017670000000264311705263724021763 0ustar paulpaul/* permutation/gsl_permute_vector_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_DOUBLE_H__ #define __GSL_PERMUTE_VECTOR_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector (const gsl_permutation * p, gsl_vector * v); int gsl_permute_vector_inverse (const gsl_permutation * p, gsl_vector * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_DOUBLE_H__ */ sources_5316/external/gsl/gsl_sort_char.h0000664000176700017670000000350011705263724017343 0ustar paulpaul/* sort/gsl_sort_char.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_CHAR_H__ #define __GSL_SORT_CHAR_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_char (char * data, const size_t stride, const size_t n); void gsl_sort_char_index (size_t * p, const char * data, const size_t stride, const size_t n); int gsl_sort_char_smallest (char * dest, const size_t k, const char * src, const size_t stride, const size_t n); int gsl_sort_char_smallest_index (size_t * p, const size_t k, const char * src, const size_t stride, const size_t n); int gsl_sort_char_largest (char * dest, const size_t k, const char * src, const size_t stride, const size_t n); int gsl_sort_char_largest_index (size_t * p, const size_t k, const char * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_CHAR_H__ */ sources_5316/external/gsl/gsl_fft__fft.c0000664000176700017670000000564011723710247017133 0ustar paulpaul#include "gsl__config.h" #include #include #include #include #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_fft_complex.h" #include "gsl_fft_complex_float.h" #define BASE_DOUBLE #include "templates_on.h" #include "gsl_fft__bitreverse.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_fft__bitreverse.c" #include "templates_off.h" #undef BASE_FLOAT #include "gsl_fft__factorize.c" #define BASE_DOUBLE #include "templates_on.h" #include "gsl_fft__c_init.c" #include "gsl_fft__c_main.c" #include "gsl_fft__c_pass_2.c" #include "gsl_fft__c_pass_3.c" #include "gsl_fft__c_pass_4.c" #include "gsl_fft__c_pass_5.c" #include "gsl_fft__c_pass_6.c" #include "gsl_fft__c_pass_7.c" #include "gsl_fft__c_pass_n.c" #include "gsl_fft__c_radix2.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_fft__c_init.c" #include "gsl_fft__c_main.c" #include "gsl_fft__c_pass_2.c" #include "gsl_fft__c_pass_3.c" #include "gsl_fft__c_pass_4.c" #include "gsl_fft__c_pass_5.c" #include "gsl_fft__c_pass_6.c" #include "gsl_fft__c_pass_7.c" #include "gsl_fft__c_pass_n.c" #include "gsl_fft__c_radix2.c" #include "templates_off.h" #undef BASE_FLOAT #include "gsl_fft_halfcomplex.h" #include "gsl_fft_halfcomplex_float.h" #define BASE_DOUBLE #include "templates_on.h" #include "gsl_fft__hc_init.c" #include "gsl_fft__hc_main.c" #include "gsl_fft__hc_pass_2.c" #include "gsl_fft__hc_pass_3.c" #include "gsl_fft__hc_pass_4.c" #include "gsl_fft__hc_pass_5.c" #include "gsl_fft__hc_pass_n.c" #include "gsl_fft__hc_radix2.c" #include "gsl_fft__hc_unpack.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_fft__hc_init.c" #include "gsl_fft__hc_main.c" #include "gsl_fft__hc_pass_2.c" #include "gsl_fft__hc_pass_3.c" #include "gsl_fft__hc_pass_4.c" #include "gsl_fft__hc_pass_5.c" #include "gsl_fft__hc_pass_n.c" #include "gsl_fft__hc_radix2.c" #include "gsl_fft__hc_unpack.c" #include "templates_off.h" #undef BASE_FLOAT #include "gsl_fft_real.h" #include "gsl_fft_real_float.h" #define BASE_DOUBLE #include "templates_on.h" #include "gsl_fft__real_init.c" #include "gsl_fft__real_main.c" #include "gsl_fft__real_pass_2.c" #include "gsl_fft__real_pass_3.c" #include "gsl_fft__real_pass_4.c" #include "gsl_fft__real_pass_5.c" #include "gsl_fft__real_pass_n.c" #include "gsl_fft__real_radix2.c" #include "gsl_fft__real_unpack.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_fft__real_init.c" #include "gsl_fft__real_main.c" #include "gsl_fft__real_pass_2.c" #include "gsl_fft__real_pass_3.c" #include "gsl_fft__real_pass_4.c" #include "gsl_fft__real_pass_5.c" #include "gsl_fft__real_pass_n.c" #include "gsl_fft__real_radix2.c" #include "gsl_fft__real_unpack.c" #include "templates_off.h" #undef BASE_FLOAT sources_5316/external/gsl/gsl_sf__bessel_Jn.c0000644000176700017670000001173710707442037020113 0ustar paulpaul/* specfunc/bessel_Jn.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_amp_phase.h" #include "gsl_sf__bessel_olver.h" #include "gsl_sf_bessel.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Jn_e(int n, double x, gsl_sf_result * result) { int sign = 1; if(n < 0) { /* reduce to case n >= 0 */ n = -n; if(GSL_IS_ODD(n)) sign = -sign; } if(x < 0.0) { /* reduce to case x >= 0. */ x = -x; if(GSL_IS_ODD(n)) sign = -sign; } /* CHECK_POINTER(result) */ if(n == 0) { gsl_sf_result b0; int stat_J0 = gsl_sf_bessel_J0_e(x, &b0); result->val = sign * b0.val; result->err = b0.err; return stat_J0; } else if(n == 1) { gsl_sf_result b1; int stat_J1 = gsl_sf_bessel_J1_e(x, &b1); result->val = sign * b1.val; result->err = b1.err; return stat_J1; } else { if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x*x < 10.0*(n+1.0)*GSL_ROOT5_DBL_EPSILON) { gsl_sf_result b; int status = gsl_sf_bessel_IJ_taylor_e((double)n, x, -1, 50, GSL_DBL_EPSILON, &b); result->val = sign * b.val; result->err = b.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return status; } else if(GSL_ROOT4_DBL_EPSILON * x > (n*n+1.0)) { int status = gsl_sf_bessel_Jnu_asympx_e((double)n, x, result); result->val *= sign; return status; } else if(n > 50) { int status = gsl_sf_bessel_Jnu_asymp_Olver_e((double)n, x, result); result->val *= sign; return status; } else if(x > 1000.0) { /* We need this to avoid feeding large x to CF1; note that * due to the above check, we know that n <= 50. */ int status = gsl_sf_bessel_Jnu_asympx_e((double)n, x, result); result->val *= sign; return status; } else { double ans; double err; double ratio; double sgn; int stat_b; int stat_CF1 = gsl_sf_bessel_J_CF1((double)n, x, &ratio, &sgn); /* backward recurrence */ double Jkp1 = GSL_SQRT_DBL_MIN * ratio; double Jk = GSL_SQRT_DBL_MIN; double Jkm1; int k; for(k=n; k>0; k--) { Jkm1 = 2.0*k/x * Jk - Jkp1; Jkp1 = Jk; Jk = Jkm1; } if(fabs(Jkp1) > fabs(Jk)) { gsl_sf_result b1; stat_b = gsl_sf_bessel_J1_e(x, &b1); ans = b1.val/Jkp1 * GSL_SQRT_DBL_MIN; err = b1.err/Jkp1 * GSL_SQRT_DBL_MIN; } else { gsl_sf_result b0; stat_b = gsl_sf_bessel_J0_e(x, &b0); ans = b0.val/Jk * GSL_SQRT_DBL_MIN; err = b0.err/Jk * GSL_SQRT_DBL_MIN; } result->val = sign * ans; result->err = fabs(err); return GSL_ERROR_SELECT_2(stat_CF1, stat_b); } } } int gsl_sf_bessel_Jn_array(int nmin, int nmax, double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(nmin < 0 || nmax < nmin) { int n; for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = 0.0; } GSL_ERROR ("domain error", GSL_EDOM); } else if(x == 0.0) { int n; for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = 0.0; } if(nmin == 0) result_array[0] = 1.0; return GSL_SUCCESS; } else { gsl_sf_result r_Jnp1; gsl_sf_result r_Jn; int stat_np1 = gsl_sf_bessel_Jn_e(nmax+1, x, &r_Jnp1); int stat_n = gsl_sf_bessel_Jn_e(nmax, x, &r_Jn); int stat = GSL_ERROR_SELECT_2(stat_np1, stat_n); double Jnp1 = r_Jnp1.val; double Jn = r_Jn.val; double Jnm1; int n; if(stat == GSL_SUCCESS) { for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = Jn; Jnm1 = -Jnp1 + 2.0*n/x * Jn; Jnp1 = Jn; Jn = Jnm1; } } else { for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = 0.0; } } return stat; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_Jn(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_Jn_e(n, x, &result)); } sources_5316/external/gsl/gsl_fft__c_pass_7.c0000664000176700017670000003075311723710247020055 0ustar paulpaul/* fft/c_pass_7.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int FUNCTION(fft_complex,pass_7) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[], const TYPE(gsl_complex) twiddle5[], const TYPE(gsl_complex) twiddle6[]) { size_t i = 0, j = 0; size_t k, k1; const size_t factor = 7; const size_t m = n / factor; const size_t q = n / product; const size_t p_1 = product / factor; const size_t jump = (factor - 1) * p_1; const ATOMIC c1 = cos(1.0 * 2.0 * M_PI / 7.0) ; const ATOMIC c2 = cos(2.0 * 2.0 * M_PI / 7.0) ; const ATOMIC c3 = cos(3.0 * 2.0 * M_PI / 7.0) ; const ATOMIC s1 = sin(1.0 * 2.0 * M_PI / 7.0) ; const ATOMIC s2 = sin(2.0 * 2.0 * M_PI / 7.0) ; const ATOMIC s3 = sin(3.0 * 2.0 * M_PI / 7.0) ; for (k = 0; k < q; k++) { ATOMIC w1_real, w1_imag, w2_real, w2_imag, w3_real, w3_imag, w4_real, w4_imag, w5_real, w5_imag, w6_real, w6_imag; if (k == 0) { w1_real = 1.0; w1_imag = 0.0; w2_real = 1.0; w2_imag = 0.0; w3_real = 1.0; w3_imag = 0.0; w4_real = 1.0; w4_imag = 0.0; w5_real = 1.0; w5_imag = 0.0; w6_real = 1.0; w6_imag = 0.0; } else { if (sign == gsl_fft_forward) { /* forward tranform */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = GSL_IMAG(twiddle2[k - 1]); w3_real = GSL_REAL(twiddle3[k - 1]); w3_imag = GSL_IMAG(twiddle3[k - 1]); w4_real = GSL_REAL(twiddle4[k - 1]); w4_imag = GSL_IMAG(twiddle4[k - 1]); w5_real = GSL_REAL(twiddle5[k - 1]); w5_imag = GSL_IMAG(twiddle5[k - 1]); w6_real = GSL_REAL(twiddle6[k - 1]); w6_imag = GSL_IMAG(twiddle6[k - 1]); } else { /* backward tranform: w -> conjugate(w) */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = -GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = -GSL_IMAG(twiddle2[k - 1]); w3_real = GSL_REAL(twiddle3[k - 1]); w3_imag = -GSL_IMAG(twiddle3[k - 1]); w4_real = GSL_REAL(twiddle4[k - 1]); w4_imag = -GSL_IMAG(twiddle4[k - 1]); w5_real = GSL_REAL(twiddle5[k - 1]); w5_imag = -GSL_IMAG(twiddle5[k - 1]); w6_real = GSL_REAL(twiddle6[k - 1]); w6_imag = -GSL_IMAG(twiddle6[k - 1]); } } for (k1 = 0; k1 < p_1; k1++) { const ATOMIC z0_real = REAL(in,istride,i); const ATOMIC z0_imag = IMAG(in,istride,i); const ATOMIC z1_real = REAL(in,istride,i+m); const ATOMIC z1_imag = IMAG(in,istride,i+m); const ATOMIC z2_real = REAL(in,istride,i+2*m); const ATOMIC z2_imag = IMAG(in,istride,i+2*m); const ATOMIC z3_real = REAL(in,istride,i+3*m); const ATOMIC z3_imag = IMAG(in,istride,i+3*m); const ATOMIC z4_real = REAL(in,istride,i+4*m); const ATOMIC z4_imag = IMAG(in,istride,i+4*m); const ATOMIC z5_real = REAL(in,istride,i+5*m); const ATOMIC z5_imag = IMAG(in,istride,i+5*m); const ATOMIC z6_real = REAL(in,istride,i+6*m); const ATOMIC z6_imag = IMAG(in,istride,i+6*m); /* compute x = W(7) z */ /* t0 = z1 + z6 */ const ATOMIC t0_real = z1_real + z6_real ; const ATOMIC t0_imag = z1_imag + z6_imag ; /* t1 = z1 - z6 */ const ATOMIC t1_real = z1_real - z6_real ; const ATOMIC t1_imag = z1_imag - z6_imag ; /* t2 = z2 + z5 */ const ATOMIC t2_real = z2_real + z5_real ; const ATOMIC t2_imag = z2_imag + z5_imag ; /* t3 = z2 - z5 */ const ATOMIC t3_real = z2_real - z5_real ; const ATOMIC t3_imag = z2_imag - z5_imag ; /* t4 = z4 + z3 */ const ATOMIC t4_real = z4_real + z3_real ; const ATOMIC t4_imag = z4_imag + z3_imag ; /* t5 = z4 - z3 */ const ATOMIC t5_real = z4_real - z3_real ; const ATOMIC t5_imag = z4_imag - z3_imag ; /* t6 = t2 + t0 */ const ATOMIC t6_real = t2_real + t0_real ; const ATOMIC t6_imag = t2_imag + t0_imag ; /* t7 = t5 + t3 */ const ATOMIC t7_real = t5_real + t3_real ; const ATOMIC t7_imag = t5_imag + t3_imag ; /* b0 = z0 + t6 + t4 */ const ATOMIC b0_real = z0_real + t6_real + t4_real ; const ATOMIC b0_imag = z0_imag + t6_imag + t4_imag ; /* b1 = ((cos(2pi/7) + cos(4pi/7) + cos(6pi/7))/3-1) (t6 + t4) */ const ATOMIC b1_real = (((c1 + c2 + c3)/3.0 - 1.0) * (t6_real + t4_real)); const ATOMIC b1_imag = (((c1 + c2 + c3)/3.0 - 1.0) * (t6_imag + t4_imag)); /* b2 = ((2*cos(2pi/7) - cos(4pi/7) - cos(6pi/7))/3) (t0 - t4) */ const ATOMIC b2_real = (((2.0 * c1 - c2 - c3)/3.0) * (t0_real - t4_real)); const ATOMIC b2_imag = (((2.0 * c1 - c2 - c3)/3.0) * (t0_imag - t4_imag)); /* b3 = ((cos(2pi/7) - 2*cos(4pi/7) + cos(6pi/7))/3) (t4 - t2) */ const ATOMIC b3_real = (((c1 - 2.0*c2 + c3)/3.0) * (t4_real - t2_real)); const ATOMIC b3_imag = (((c1 - 2.0*c2 + c3)/3.0) * (t4_imag - t2_imag)); /* b4 = ((cos(2pi/7) + cos(4pi/7) - 2*cos(6pi/7))/3) (t2 - t0) */ const ATOMIC b4_real = (((c1 + c2 - 2.0 * c3)/3.0) * (t2_real - t0_real)); const ATOMIC b4_imag = (((c1 + c2 - 2.0 * c3)/3.0) * (t2_imag - t0_imag)); /* b5 = sign * ((sin(2pi/7) + sin(4pi/7) - sin(6pi/7))/3) (t7 + t1) */ const ATOMIC b5_real = (-(int)sign) * ((s1 + s2 - s3)/3.0) * (t7_real + t1_real) ; const ATOMIC b5_imag = (-(int)sign) * ((s1 + s2 - s3)/3.0) * (t7_imag + t1_imag) ; /* b6 = sign * ((2sin(2pi/7) - sin(4pi/7) + sin(6pi/7))/3) (t1 - t5) */ const ATOMIC b6_real = (-(int)sign) * ((2.0 * s1 - s2 + s3)/3.0) * (t1_real - t5_real) ; const ATOMIC b6_imag = (-(int)sign) * ((2.0 * s1 - s2 + s3)/3.0) * (t1_imag - t5_imag) ; /* b7 = sign * ((sin(2pi/7) - 2sin(4pi/7) - sin(6pi/7))/3) (t5 - t3) */ const ATOMIC b7_real = (-(int)sign) * ((s1 - 2.0 * s2 - s3)/3.0) * (t5_real - t3_real) ; const ATOMIC b7_imag = (-(int)sign) * ((s1 - 2.0 * s2 - s3)/3.0) * (t5_imag - t3_imag) ; /* b8 = sign * ((sin(2pi/7) + sin(4pi/7) + 2sin(6pi/7))/3) (t3 - t1) */ const ATOMIC b8_real = (-(int)sign) * ((s1 + s2 + 2.0 * s3)/3.0) * (t3_real - t1_real) ; const ATOMIC b8_imag = (-(int)sign) * ((s1 + s2 + 2.0 * s3)/3.0) * (t3_imag - t1_imag) ; /* T0 = b0 + b1 */ const ATOMIC T0_real = b0_real + b1_real ; const ATOMIC T0_imag = b0_imag + b1_imag ; /* T1 = b2 + b3 */ const ATOMIC T1_real = b2_real + b3_real ; const ATOMIC T1_imag = b2_imag + b3_imag ; /* T2 = b4 - b3 */ const ATOMIC T2_real = b4_real - b3_real ; const ATOMIC T2_imag = b4_imag - b3_imag ; /* T3 = -b2 - b4 */ const ATOMIC T3_real = -b2_real - b4_real ; const ATOMIC T3_imag = -b2_imag - b4_imag ; /* T4 = b6 + b7 */ const ATOMIC T4_real = b6_real + b7_real ; const ATOMIC T4_imag = b6_imag + b7_imag ; /* T5 = b8 - b7 */ const ATOMIC T5_real = b8_real - b7_real ; const ATOMIC T5_imag = b8_imag - b7_imag ; /* T6 = -b8 - b6 */ const ATOMIC T6_real = -b8_real - b6_real ; const ATOMIC T6_imag = -b8_imag - b6_imag ; /* T7 = T0 + T1 */ const ATOMIC T7_real = T0_real + T1_real ; const ATOMIC T7_imag = T0_imag + T1_imag ; /* T8 = T0 + T2 */ const ATOMIC T8_real = T0_real + T2_real ; const ATOMIC T8_imag = T0_imag + T2_imag ; /* T9 = T0 + T3 */ const ATOMIC T9_real = T0_real + T3_real ; const ATOMIC T9_imag = T0_imag + T3_imag ; /* T10 = T4 + b5 */ const ATOMIC T10_real = T4_real + b5_real ; const ATOMIC T10_imag = T4_imag + b5_imag ; /* T11 = T5 + b5 */ const ATOMIC T11_real = T5_real + b5_real ; const ATOMIC T11_imag = T5_imag + b5_imag ; /* T12 = T6 + b5 */ const ATOMIC T12_real = T6_real + b5_real ; const ATOMIC T12_imag = T6_imag + b5_imag ; /* x0 = b0 */ const ATOMIC x0_real = b0_real ; const ATOMIC x0_imag = b0_imag ; /* x1 = T7 - i T10 */ const ATOMIC x1_real = T7_real + T10_imag ; const ATOMIC x1_imag = T7_imag - T10_real ; /* x2 = T9 - i T12 */ const ATOMIC x2_real = T9_real + T12_imag ; const ATOMIC x2_imag = T9_imag - T12_real ; /* x3 = T8 + i T11 */ const ATOMIC x3_real = T8_real - T11_imag ; const ATOMIC x3_imag = T8_imag + T11_real ; /* x4 = T8 - i T11 */ const ATOMIC x4_real = T8_real + T11_imag ; const ATOMIC x4_imag = T8_imag - T11_real ; /* x5 = T9 + i T12 */ const ATOMIC x5_real = T9_real - T12_imag ; const ATOMIC x5_imag = T9_imag + T12_real ; /* x6 = T7 + i T10 */ const ATOMIC x6_real = T7_real - T10_imag ; const ATOMIC x6_imag = T7_imag + T10_real ; /* apply twiddle factors */ /* to0 = 1 * x0 */ REAL(out,ostride,j) = x0_real; IMAG(out,ostride,j) = x0_imag; /* to1 = w1 * x1 */ REAL(out,ostride,j+p_1) = w1_real * x1_real - w1_imag * x1_imag; IMAG(out,ostride,j+p_1) = w1_real * x1_imag + w1_imag * x1_real; /* to2 = w2 * x2 */ REAL(out,ostride,j+2*p_1) = w2_real * x2_real - w2_imag * x2_imag; IMAG(out,ostride,j+2*p_1) = w2_real * x2_imag + w2_imag * x2_real; /* to3 = w3 * x3 */ REAL(out,ostride,j+3*p_1) = w3_real * x3_real - w3_imag * x3_imag; IMAG(out,ostride,j+3*p_1) = w3_real * x3_imag + w3_imag * x3_real; /* to4 = w4 * x4 */ REAL(out,ostride,j+4*p_1) = w4_real * x4_real - w4_imag * x4_imag; IMAG(out,ostride,j+4*p_1) = w4_real * x4_imag + w4_imag * x4_real; /* to5 = w5 * x5 */ REAL(out,ostride,j+5*p_1) = w5_real * x5_real - w5_imag * x5_imag; IMAG(out,ostride,j+5*p_1) = w5_real * x5_imag + w5_imag * x5_real; /* to6 = w6 * x6 */ REAL(out,ostride,j+6*p_1) = w6_real * x6_real - w6_imag * x6_imag; IMAG(out,ostride,j+6*p_1) = w6_real * x6_imag + w6_imag * x6_real; i++; j++; } j += jump; } return 0; } sources_5316/external/gsl/gsl_sort_ulong.h0000664000176700017670000000362211705263724017557 0ustar paulpaul/* sort/gsl_sort_ulong.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_ULONG_H__ #define __GSL_SORT_ULONG_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_ulong (unsigned long * data, const size_t stride, const size_t n); void gsl_sort_ulong_index (size_t * p, const unsigned long * data, const size_t stride, const size_t n); int gsl_sort_ulong_smallest (unsigned long * dest, const size_t k, const unsigned long * src, const size_t stride, const size_t n); int gsl_sort_ulong_smallest_index (size_t * p, const size_t k, const unsigned long * src, const size_t stride, const size_t n); int gsl_sort_ulong_largest (unsigned long * dest, const size_t k, const unsigned long * src, const size_t stride, const size_t n); int gsl_sort_ulong_largest_index (size_t * p, const size_t k, const unsigned long * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_ULONG_H__ */ sources_5316/external/gsl/gsl_vector.h0000664000176700017670000000103611705263724016663 0ustar paulpaul#ifndef __GSL_VECTOR_H__ #define __GSL_VECTOR_H__ #include "gsl_vector_complex_long_double.h" #include "gsl_vector_complex_double.h" #include "gsl_vector_complex_float.h" #include "gsl_vector_long_double.h" #include "gsl_vector_double.h" #include "gsl_vector_float.h" #include "gsl_vector_ulong.h" #include "gsl_vector_long.h" #include "gsl_vector_uint.h" #include "gsl_vector_int.h" #include "gsl_vector_ushort.h" #include "gsl_vector_short.h" #include "gsl_vector_uchar.h" #include "gsl_vector_char.h" #endif /* __GSL_VECTOR_H__ */ sources_5316/external/gsl/gsl_sf_dawson.h0000664000176700017670000000256611705263724017355 0ustar paulpaul/* specfunc/gsl_sf_dawson.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_DAWSON_H__ #define __GSL_SF_DAWSON_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Dawson's integral: * * Exp[-x^2] Integral[ Exp[t^2], {t,0,x}] * * exceptions: GSL_EUNDRFLW; */ int gsl_sf_dawson_e(double x, gsl_sf_result * result); double gsl_sf_dawson(double x); __END_DECLS #endif /* __GSL_SF_DAWSON_H__ */ sources_5316/external/gsl/gsl_combination__combination.c0000664000176700017670000000756511723710247022411 0ustar paulpaul/* combination/combination.c * based on permutation/permutation.c by Brian Gough * * Copyright (C) 2001 Szymon Jaroszewicz * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_combination.h" size_t gsl_combination_n (const gsl_combination * c) { return c->n ; } size_t gsl_combination_k (const gsl_combination * c) { return c->k ; } size_t * gsl_combination_data (const gsl_combination * c) { return c->data ; } #ifndef HIDE_INLINE_STATIC size_t gsl_combination_get (const gsl_combination * c, const size_t i) { if (gsl_check_range) { if (i >= c->k) /* size_t is unsigned, can't be negative */ { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } } return c->data[i]; } #endif int gsl_combination_valid (gsl_combination * c) { const size_t n = c->n ; const size_t k = c->k ; size_t i, j ; if( k > n ) { GSL_ERROR("combination has k greater than n", GSL_FAILURE) ; } for (i = 0; i < k; i++) { const size_t ci = c->data[i]; if (ci >= n) { GSL_ERROR("combination index outside range", GSL_FAILURE) ; } for (j = 0; j < i; j++) { if (c->data[j] == ci) { GSL_ERROR("duplicate combination index", GSL_FAILURE) ; } if (c->data[j] > ci) { GSL_ERROR("combination indices not in increasing order", GSL_FAILURE) ; } } } return GSL_SUCCESS; } int gsl_combination_next (gsl_combination * c) { /* Replaces c with the next combination (in the standard lexicographical * ordering). Returns GSL_FAILURE if there is no next combination. */ const size_t n = c->n; const size_t k = c->k; size_t *data = c->data; size_t i; if(k == 0) { return GSL_FAILURE; } i = k - 1; while(i > 0 && data[i] == n - k + i) { i--; } if(i == 0 && data[i] == n - k) { return GSL_FAILURE; } data[i]++; for(; i < k - 1; i++) { data[i + 1] = data[i] + 1; } return GSL_SUCCESS; } int gsl_combination_prev (gsl_combination * c) { /* Replaces c with the previous combination (in the standard * lexicographical ordering). Returns GSL_FAILURE if there is no * previous combination. */ const size_t n = c->n; const size_t k = c->k; size_t *data = c->data; size_t i; if(k == 0) { return GSL_FAILURE; } i = k - 1; while(i > 0 && data[i] == data[i-1] + 1) { i--; } if(i == 0 && data[i] == 0) { return GSL_FAILURE; } data[i++]--; for(; i < k; i++) { data[i] = n - k + i; } return GSL_SUCCESS; } int gsl_combination_memcpy (gsl_combination * dest, const gsl_combination * src) { const size_t src_n = src->n; const size_t src_k = src->k; const size_t dest_n = dest->n; const size_t dest_k = dest->k; if (src_n != dest_n || src_k != dest_k) { GSL_ERROR ("combination lengths are not equal", GSL_EBADLEN); } { size_t j; for (j = 0; j < src_k; j++) { dest->data[j] = src->data[j]; } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__sgemv.c0000664000176700017670000000064711723710247020004 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_sgemv (const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const float alpha, const float *A, const int lda, const float *X, const int incX, const float beta, float *Y, const int incY) { #define BASE float #include "gsl_cblas__source_gemv_r.h" #undef BASE } sources_5316/external/gsl/gsl_complex_math.h0000664000176700017670000001356611705263724020054 0ustar paulpaul/* complex/gsl_complex_math.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 Jorma Olavi Tähtinen, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_COMPLEX_MATH_H__ #define __GSL_COMPLEX_MATH_H__ #include "gsl_complex.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus #define __BEGIN_DECLS extern "C" { #define __END_DECLS } #else #define __BEGIN_DECLS /* empty */ #define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Complex numbers */ gsl_complex gsl_complex_rect (double x, double y); /* r= real+i*imag */ gsl_complex gsl_complex_polar (double r, double theta); /* r= r e^(i theta) */ #ifdef HAVE_INLINE extern inline gsl_complex gsl_complex_rect (double x, double y) { /* return z = x + i y */ gsl_complex z; GSL_SET_COMPLEX (&z, x, y); return z; } #endif #define GSL_COMPLEX_ONE (gsl_complex_rect(1.0,0.0)) #define GSL_COMPLEX_ZERO (gsl_complex_rect(0.0,0.0)) #define GSL_COMPLEX_NEGONE (gsl_complex_rect(-1.0,0.0)) /* Properties of complex numbers */ double gsl_complex_arg (gsl_complex z); /* return arg(z), -pi< arg(z) <=+pi */ double gsl_complex_abs (gsl_complex z); /* return |z| */ double gsl_complex_abs2 (gsl_complex z); /* return |z|^2 */ double gsl_complex_logabs (gsl_complex z); /* return log|z| */ /* Complex arithmetic operators */ gsl_complex gsl_complex_add (gsl_complex a, gsl_complex b); /* r=a+b */ gsl_complex gsl_complex_sub (gsl_complex a, gsl_complex b); /* r=a-b */ gsl_complex gsl_complex_mul (gsl_complex a, gsl_complex b); /* r=a*b */ gsl_complex gsl_complex_div (gsl_complex a, gsl_complex b); /* r=a/b */ gsl_complex gsl_complex_add_real (gsl_complex a, double x); /* r=a+x */ gsl_complex gsl_complex_sub_real (gsl_complex a, double x); /* r=a-x */ gsl_complex gsl_complex_mul_real (gsl_complex a, double x); /* r=a*x */ gsl_complex gsl_complex_div_real (gsl_complex a, double x); /* r=a/x */ gsl_complex gsl_complex_add_imag (gsl_complex a, double y); /* r=a+iy */ gsl_complex gsl_complex_sub_imag (gsl_complex a, double y); /* r=a-iy */ gsl_complex gsl_complex_mul_imag (gsl_complex a, double y); /* r=a*iy */ gsl_complex gsl_complex_div_imag (gsl_complex a, double y); /* r=a/iy */ gsl_complex gsl_complex_conjugate (gsl_complex z); /* r=conj(z) */ gsl_complex gsl_complex_inverse (gsl_complex a); /* r=1/a */ gsl_complex gsl_complex_negative (gsl_complex a); /* r=-a */ /* Elementary Complex Functions */ gsl_complex gsl_complex_sqrt (gsl_complex z); /* r=sqrt(z) */ gsl_complex gsl_complex_sqrt_real (double x); /* r=sqrt(x) (x<0 ok) */ gsl_complex gsl_complex_pow (gsl_complex a, gsl_complex b); /* r=a^b */ gsl_complex gsl_complex_pow_real (gsl_complex a, double b); /* r=a^b */ gsl_complex gsl_complex_exp (gsl_complex a); /* r=exp(a) */ gsl_complex gsl_complex_log (gsl_complex a); /* r=log(a) (base e) */ gsl_complex gsl_complex_log10 (gsl_complex a); /* r=log10(a) (base 10) */ gsl_complex gsl_complex_log_b (gsl_complex a, gsl_complex b); /* r=log_b(a) (base=b) */ /* Complex Trigonometric Functions */ gsl_complex gsl_complex_sin (gsl_complex a); /* r=sin(a) */ gsl_complex gsl_complex_cos (gsl_complex a); /* r=cos(a) */ gsl_complex gsl_complex_sec (gsl_complex a); /* r=sec(a) */ gsl_complex gsl_complex_csc (gsl_complex a); /* r=csc(a) */ gsl_complex gsl_complex_tan (gsl_complex a); /* r=tan(a) */ gsl_complex gsl_complex_cot (gsl_complex a); /* r=cot(a) */ /* Inverse Complex Trigonometric Functions */ gsl_complex gsl_complex_arcsin (gsl_complex a); /* r=arcsin(a) */ gsl_complex gsl_complex_arcsin_real (double a); /* r=arcsin(a) */ gsl_complex gsl_complex_arccos (gsl_complex a); /* r=arccos(a) */ gsl_complex gsl_complex_arccos_real (double a); /* r=arccos(a) */ gsl_complex gsl_complex_arcsec (gsl_complex a); /* r=arcsec(a) */ gsl_complex gsl_complex_arcsec_real (double a); /* r=arcsec(a) */ gsl_complex gsl_complex_arccsc (gsl_complex a); /* r=arccsc(a) */ gsl_complex gsl_complex_arccsc_real (double a); /* r=arccsc(a) */ gsl_complex gsl_complex_arctan (gsl_complex a); /* r=arctan(a) */ gsl_complex gsl_complex_arccot (gsl_complex a); /* r=arccot(a) */ /* Complex Hyperbolic Functions */ gsl_complex gsl_complex_sinh (gsl_complex a); /* r=sinh(a) */ gsl_complex gsl_complex_cosh (gsl_complex a); /* r=coshh(a) */ gsl_complex gsl_complex_sech (gsl_complex a); /* r=sech(a) */ gsl_complex gsl_complex_csch (gsl_complex a); /* r=csch(a) */ gsl_complex gsl_complex_tanh (gsl_complex a); /* r=tanh(a) */ gsl_complex gsl_complex_coth (gsl_complex a); /* r=coth(a) */ /* Inverse Complex Hyperbolic Functions */ gsl_complex gsl_complex_arcsinh (gsl_complex a); /* r=arcsinh(a) */ gsl_complex gsl_complex_arccosh (gsl_complex a); /* r=arccosh(a) */ gsl_complex gsl_complex_arccosh_real (double a); /* r=arccosh(a) */ gsl_complex gsl_complex_arcsech (gsl_complex a); /* r=arcsech(a) */ gsl_complex gsl_complex_arccsch (gsl_complex a); /* r=arccsch(a) */ gsl_complex gsl_complex_arctanh (gsl_complex a); /* r=arctanh(a) */ gsl_complex gsl_complex_arctanh_real (double a); /* r=arctanh(a) */ gsl_complex gsl_complex_arccoth (gsl_complex a); /* r=arccoth(a) */ __END_DECLS #endif /* __GSL_COMPLEX_MATH_H__ */ sources_5316/external/gsl/gsl_sf_result.h0000664000176700017670000000305111705263724017366 0ustar paulpaul/* specfunc/gsl_sf_result.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_RESULT_H__ #define __GSL_SF_RESULT_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_sf_result_struct { double val; double err; }; typedef struct gsl_sf_result_struct gsl_sf_result; #define GSL_SF_RESULT_SET(r,v,e) do { (r)->val=(v); (r)->err=(e); } while(0) struct gsl_sf_result_e10_struct { double val; double err; int e10; }; typedef struct gsl_sf_result_e10_struct gsl_sf_result_e10; int gsl_sf_result_smash_e(const gsl_sf_result_e10 * re, gsl_sf_result * r); __END_DECLS #endif /* __GSL_SF_RESULT_H__ */ sources_5316/external/gsl/gsl_sf__bessel_I1.c0000644000176700017670000001526510707442037020015 0ustar paulpaul/* specfunc/bessel_I1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" #define ROOT_EIGHT (2.0*M_SQRT2) /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besi1(), besi1e() */ /* chebyshev expansions series for bi1 on the interval 0. to 9.00000d+00 with weighted error 2.40e-17 log weighted error 16.62 significant figures required 16.23 decimal places required 17.14 series for ai1 on the interval 1.25000d-01 to 3.33333d-01 with weighted error 6.98e-17 log weighted error 16.16 significant figures required 14.53 decimal places required 16.82 series for ai12 on the interval 0. to 1.25000d-01 with weighted error 3.55e-17 log weighted error 16.45 significant figures required 14.69 decimal places required 17.12 */ static double bi1_data[11] = { -0.001971713261099859, 0.407348876675464810, 0.034838994299959456, 0.001545394556300123, 0.000041888521098377, 0.000000764902676483, 0.000000010042493924, 0.000000000099322077, 0.000000000000766380, 0.000000000000004741, 0.000000000000000024 }; static cheb_series bi1_cs = { bi1_data, 10, -1, 1, 10 }; static double ai1_data[21] = { -0.02846744181881479, -0.01922953231443221, -0.00061151858579437, -0.00002069971253350, 0.00000858561914581, 0.00000104949824671, -0.00000029183389184, -0.00000001559378146, 0.00000001318012367, -0.00000000144842341, -0.00000000029085122, 0.00000000012663889, -0.00000000001664947, -0.00000000000166665, 0.00000000000124260, -0.00000000000027315, 0.00000000000002023, 0.00000000000000730, -0.00000000000000333, 0.00000000000000071, -0.00000000000000006 }; static cheb_series ai1_cs = { ai1_data, 20, -1, 1, 11 }; static double ai12_data[22] = { 0.02857623501828014, -0.00976109749136147, -0.00011058893876263, -0.00000388256480887, -0.00000025122362377, -0.00000002631468847, -0.00000000383538039, -0.00000000055897433, -0.00000000001897495, 0.00000000003252602, 0.00000000001412580, 0.00000000000203564, -0.00000000000071985, -0.00000000000040836, -0.00000000000002101, 0.00000000000004273, 0.00000000000001041, -0.00000000000000382, -0.00000000000000186, 0.00000000000000033, 0.00000000000000028, -0.00000000000000003 }; static cheb_series ai12_cs = { ai12_data, 21, -1, 1, 9 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_I1_scaled_e(const double x, gsl_sf_result * result) { const double xmin = 2.0 * GSL_DBL_MIN; const double x_small = ROOT_EIGHT * GSL_SQRT_DBL_EPSILON; const double y = fabs(x); /* CHECK_POINTER(result) */ if(y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(y < xmin) { UNDERFLOW_ERROR(result); } else if(y < x_small) { result->val = 0.5*x; result->err = 0.0; return GSL_SUCCESS; } else if(y <= 3.0) { const double ey = exp(-y); gsl_sf_result c; cheb_eval_e(&bi1_cs, y*y/4.5-1.0, &c); result->val = x * ey * (0.875 + c.val); result->err = ey * c.err + y * GSL_DBL_EPSILON * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(y <= 8.0) { const double sy = sqrt(y); gsl_sf_result c; double b; double s; cheb_eval_e(&ai1_cs, (48.0/y-11.0)/5.0, &c); b = (0.375 + c.val) / sy; s = (x > 0.0 ? 1.0 : -1.0); result->val = s * b; result->err = c.err / sy; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sy = sqrt(y); gsl_sf_result c; double b; double s; cheb_eval_e(&ai12_cs, 16.0/y-1.0, &c); b = (0.375 + c.val) / sy; s = (x > 0.0 ? 1.0 : -1.0); result->val = s * b; result->err = c.err / sy; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_I1_e(const double x, gsl_sf_result * result) { const double xmin = 2.0 * GSL_DBL_MIN; const double x_small = ROOT_EIGHT * GSL_SQRT_DBL_EPSILON; const double y = fabs(x); /* CHECK_POINTER(result) */ if(y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(y < xmin) { UNDERFLOW_ERROR(result); } else if(y < x_small) { result->val = 0.5*x; result->err = 0.0; return GSL_SUCCESS; } else if(y <= 3.0) { gsl_sf_result c; cheb_eval_e(&bi1_cs, y*y/4.5-1.0, &c); result->val = x * (0.875 + c.val); result->err = y * c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(y < GSL_LOG_DBL_MAX) { const double ey = exp(y); gsl_sf_result I1_scaled; gsl_sf_bessel_I1_scaled_e(x, &I1_scaled); result->val = ey * I1_scaled.val; result->err = ey * I1_scaled.err + y * GSL_DBL_EPSILON * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_I1_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_I1_scaled_e(x, &result)); } double gsl_sf_bessel_I1(const double x) { EVAL_RESULT(gsl_sf_bessel_I1_e(x, &result)); } sources_5316/external/gsl/gsl_fft_halfcomplex_float.h0000664000176700017670000000622211705263724021711 0ustar paulpaul/* fft/gsl_fft_halfcomplex_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_FFT_HALFCOMPLEX_FLOAT_H__ #define __GSL_FFT_HALFCOMPLEX_FLOAT_H__ #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_fft.h" #include "gsl_fft_real_float.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_fft_halfcomplex_float_radix2_backward (float data[], const size_t stride, const size_t n); int gsl_fft_halfcomplex_float_radix2_inverse (float data[], const size_t stride, const size_t n); int gsl_fft_halfcomplex_float_radix2_transform (float data[], const size_t stride, const size_t n); typedef struct { size_t n; size_t nf; size_t factor[64]; gsl_complex_float *twiddle[64]; gsl_complex_float *trig; } gsl_fft_halfcomplex_wavetable_float; gsl_fft_halfcomplex_wavetable_float * gsl_fft_halfcomplex_wavetable_float_alloc (size_t n); void gsl_fft_halfcomplex_wavetable_float_free (gsl_fft_halfcomplex_wavetable_float * wavetable); int gsl_fft_halfcomplex_float_backward (float data[], const size_t stride, const size_t n, const gsl_fft_halfcomplex_wavetable_float * wavetable, gsl_fft_real_workspace_float * work); int gsl_fft_halfcomplex_float_inverse (float data[], const size_t stride, const size_t n, const gsl_fft_halfcomplex_wavetable_float * wavetable, gsl_fft_real_workspace_float * work); int gsl_fft_halfcomplex_float_transform (float data[], const size_t stride, const size_t n, const gsl_fft_halfcomplex_wavetable_float * wavetable, gsl_fft_real_workspace_float * work); int gsl_fft_halfcomplex_float_unpack (const float halfcomplex_coefficient[], float complex_coefficient[], const size_t stride, const size_t n); int gsl_fft_halfcomplex_float_radix2_unpack (const float halfcomplex_coefficient[], float complex_coefficient[], const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_FFT_HALFCOMPLEX_FLOAT_H__ */ sources_5316/external/gsl/gsl_multiroots__broyden.c0000664000176700017670000002332211723710247021455 0ustar paulpaul/* multiroots/broyden.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multiroots.h" #include "gsl_linalg.h" #include "gsl_multiroots__enorm.c" /* Broyden's method. It is not an efficient or modern algorithm but gives an example of a rank-1 update. C.G. Broyden, "A Class of Methods for Solving Nonlinear Simultaneous Equations", Mathematics of Computation, vol 19 (1965), p 577-593 */ typedef struct { gsl_matrix *H; gsl_matrix *lu; gsl_permutation *permutation; gsl_vector *v; gsl_vector *w; gsl_vector *y; gsl_vector *p; gsl_vector *fnew; gsl_vector *x_trial; double phi; } broyden_state_t; static int broyden_alloc (void *vstate, size_t n); static int broyden_set (void *vstate, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx); static int broyden_iterate (void *vstate, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx); static void broyden_free (void *vstate); static int broyden_alloc (void *vstate, size_t n) { broyden_state_t *state = (broyden_state_t *) vstate; gsl_vector *v, *w, *y, *fnew, *x_trial, *p; gsl_permutation *perm; gsl_matrix *m, *H; m = gsl_matrix_calloc (n, n); if (m == 0) { GSL_ERROR ("failed to allocate space for lu", GSL_ENOMEM); } state->lu = m; perm = gsl_permutation_calloc (n); if (perm == 0) { gsl_matrix_free (m); GSL_ERROR ("failed to allocate space for permutation", GSL_ENOMEM); } state->permutation = perm; H = gsl_matrix_calloc (n, n); if (H == 0) { gsl_permutation_free (perm); gsl_matrix_free (m); GSL_ERROR ("failed to allocate space for d", GSL_ENOMEM); } state->H = H; v = gsl_vector_calloc (n); if (v == 0) { gsl_matrix_free (H); gsl_permutation_free (perm); gsl_matrix_free (m); GSL_ERROR ("failed to allocate space for v", GSL_ENOMEM); } state->v = v; w = gsl_vector_calloc (n); if (w == 0) { gsl_vector_free (v); gsl_matrix_free (H); gsl_permutation_free (perm); gsl_matrix_free (m); GSL_ERROR ("failed to allocate space for w", GSL_ENOMEM); } state->w = w; y = gsl_vector_calloc (n); if (y == 0) { gsl_vector_free (w); gsl_vector_free (v); gsl_matrix_free (H); gsl_permutation_free (perm); gsl_matrix_free (m); GSL_ERROR ("failed to allocate space for y", GSL_ENOMEM); } state->y = y; fnew = gsl_vector_calloc (n); if (fnew == 0) { gsl_vector_free (y); gsl_vector_free (w); gsl_vector_free (v); gsl_matrix_free (H); gsl_permutation_free (perm); gsl_matrix_free (m); GSL_ERROR ("failed to allocate space for fnew", GSL_ENOMEM); } state->fnew = fnew; x_trial = gsl_vector_calloc (n); if (x_trial == 0) { gsl_vector_free (fnew); gsl_vector_free (y); gsl_vector_free (w); gsl_vector_free (v); gsl_matrix_free (H); gsl_permutation_free (perm); gsl_matrix_free (m); GSL_ERROR ("failed to allocate space for x_trial", GSL_ENOMEM); } state->x_trial = x_trial; p = gsl_vector_calloc (n); if (p == 0) { gsl_vector_free (x_trial); gsl_vector_free (fnew); gsl_vector_free (y); gsl_vector_free (w); gsl_vector_free (v); gsl_matrix_free (H); gsl_permutation_free (perm); gsl_matrix_free (m); GSL_ERROR ("failed to allocate space for p", GSL_ENOMEM); } state->p = p; return GSL_SUCCESS; } static int broyden_set (void *vstate, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx) { broyden_state_t *state = (broyden_state_t *) vstate; size_t i, j, n = function->n; int signum = 0; GSL_MULTIROOT_FN_EVAL (function, x, f); gsl_multiroot_fdjacobian (function, x, f, GSL_SQRT_DBL_EPSILON, state->lu); gsl_linalg_LU_decomp (state->lu, state->permutation, &signum); gsl_linalg_LU_invert (state->lu, state->permutation, state->H); for (i = 0; i < n; i++) for (j = 0; j < n; j++) gsl_matrix_set(state->H,i,j,-gsl_matrix_get(state->H,i,j)); for (i = 0; i < n; i++) { gsl_vector_set (dx, i, 0.0); } state->phi = enorm (f); return GSL_SUCCESS; } static int broyden_iterate (void *vstate, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx) { broyden_state_t *state = (broyden_state_t *) vstate; double phi0, phi1, t, lambda; gsl_matrix *H = state->H; gsl_vector *p = state->p; gsl_vector *y = state->y; gsl_vector *v = state->v; gsl_vector *w = state->w; gsl_vector *fnew = state->fnew; gsl_vector *x_trial = state->x_trial; gsl_matrix *lu = state->lu; gsl_permutation *perm = state->permutation; size_t i, j, iter; size_t n = function->n; /* p = H f */ for (i = 0; i < n; i++) { double sum = 0; for (j = 0; j < n; j++) { sum += gsl_matrix_get (H, i, j) * gsl_vector_get (f, j); } gsl_vector_set (p, i, sum); } t = 1; iter = 0; phi0 = state->phi; new_step: for (i = 0; i < n; i++) { double pi = gsl_vector_get (p, i); double xi = gsl_vector_get (x, i); gsl_vector_set (x_trial, i, xi + t * pi); } { int status = GSL_MULTIROOT_FN_EVAL (function, x_trial, fnew); if (status != GSL_SUCCESS) { return GSL_EBADFUNC; } } phi1 = enorm (fnew); iter++ ; if (phi1 > phi0 && iter < 10 && t > 0.1) { /* full step goes uphill, take a reduced step instead */ double theta = phi1 / phi0; t *= (sqrt (1.0 + 6.0 * theta) - 1.0) / (3.0 * theta); goto new_step; } if (phi1 > phi0) { /* need to recompute Jacobian */ int signum = 0; gsl_multiroot_fdjacobian (function, x, f, GSL_SQRT_DBL_EPSILON, lu); for (i = 0; i < n; i++) for (j = 0; j < n; j++) gsl_matrix_set(lu,i,j,-gsl_matrix_get(lu,i,j)); gsl_linalg_LU_decomp (lu, perm, &signum); gsl_linalg_LU_invert (lu, perm, H); gsl_linalg_LU_solve (lu, perm, f, p); t = 1; for (i = 0; i < n; i++) { double pi = gsl_vector_get (p, i); double xi = gsl_vector_get (x, i); gsl_vector_set (x_trial, i, xi + t * pi); } { int status = GSL_MULTIROOT_FN_EVAL (function, x_trial, fnew); if (status != GSL_SUCCESS) { return GSL_EBADFUNC; } } phi1 = enorm (fnew); } /* y = f' - f */ for (i = 0; i < n; i++) { double yi = gsl_vector_get (fnew, i) - gsl_vector_get (f, i); gsl_vector_set (y, i, yi); } /* v = H y */ for (i = 0; i < n; i++) { double sum = 0; for (j = 0; j < n; j++) { sum += gsl_matrix_get (H, i, j) * gsl_vector_get (y, j); } gsl_vector_set (v, i, sum); } /* lambda = p . v */ lambda = 0; for (i = 0; i < n; i++) { lambda += gsl_vector_get (p, i) * gsl_vector_get (v, i); } if (lambda == 0) { GSL_ERROR ("approximation to Jacobian has collapsed", GSL_EZERODIV) ; } /* v' = v + t * p */ for (i = 0; i < n; i++) { double vi = gsl_vector_get (v, i) + t * gsl_vector_get (p, i); gsl_vector_set (v, i, vi); } /* w^T = p^T H */ for (i = 0; i < n; i++) { double sum = 0; for (j = 0; j < n; j++) { sum += gsl_matrix_get (H, j, i) * gsl_vector_get (p, j); } gsl_vector_set (w, i, sum); } /* Hij -> Hij - (vi wj / lambda) */ for (i = 0; i < n; i++) { double vi = gsl_vector_get (v, i); for (j = 0; j < n; j++) { double wj = gsl_vector_get (w, j); double Hij = gsl_matrix_get (H, i, j) - vi * wj / lambda; gsl_matrix_set (H, i, j, Hij); } } /* copy fnew into f */ gsl_vector_memcpy (f, fnew); /* copy x_trial into x */ gsl_vector_memcpy (x, x_trial); for (i = 0; i < n; i++) { double pi = gsl_vector_get (p, i); gsl_vector_set (dx, i, t * pi); } state->phi = phi1; return GSL_SUCCESS; } static void broyden_free (void *vstate) { broyden_state_t *state = (broyden_state_t *) vstate; gsl_matrix_free (state->H); gsl_matrix_free (state->lu); gsl_permutation_free (state->permutation); gsl_vector_free (state->v); gsl_vector_free (state->w); gsl_vector_free (state->y); gsl_vector_free (state->p); gsl_vector_free (state->fnew); gsl_vector_free (state->x_trial); } static const gsl_multiroot_fsolver_type broyden_type = {"broyden", /* name */ sizeof (broyden_state_t), &broyden_alloc, &broyden_set, &broyden_iterate, &broyden_free}; const gsl_multiroot_fsolver_type *gsl_multiroot_fsolver_broyden = &broyden_type; sources_5316/external/gsl/gsl_const_cgsm.h0000664000176700017670000001523611705263724017527 0ustar paulpaul/* const/gsl_const_cgsm.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, * 2006 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_CONST_CGSM__ #define __GSL_CONST_CGSM__ #define GSL_CONST_CGSM_SPEED_OF_LIGHT (2.99792458e10) /* cm / s */ #define GSL_CONST_CGSM_GRAVITATIONAL_CONSTANT (6.673e-8) /* cm^3 / g s^2 */ #define GSL_CONST_CGSM_PLANCKS_CONSTANT_H (6.62606876e-27) /* g cm^2 / s */ #define GSL_CONST_CGSM_PLANCKS_CONSTANT_HBAR (1.05457159642e-27) /* g cm^2 / s */ #define GSL_CONST_CGSM_ASTRONOMICAL_UNIT (1.49597870691e13) /* cm */ #define GSL_CONST_CGSM_LIGHT_YEAR (9.46053620707e17) /* cm */ #define GSL_CONST_CGSM_PARSEC (3.08567758135e18) /* cm */ #define GSL_CONST_CGSM_GRAV_ACCEL (9.80665e2) /* cm / s^2 */ #define GSL_CONST_CGSM_ELECTRON_VOLT (1.602176462e-12) /* g cm^2 / s^2 */ #define GSL_CONST_CGSM_MASS_ELECTRON (9.10938188e-28) /* g */ #define GSL_CONST_CGSM_MASS_MUON (1.88353109e-25) /* g */ #define GSL_CONST_CGSM_MASS_PROTON (1.67262158e-24) /* g */ #define GSL_CONST_CGSM_MASS_NEUTRON (1.67492716e-24) /* g */ #define GSL_CONST_CGSM_RYDBERG (2.17987190389e-11) /* g cm^2 / s^2 */ #define GSL_CONST_CGSM_BOLTZMANN (1.3806503e-16) /* g cm^2 / K s^2 */ #define GSL_CONST_CGSM_BOHR_MAGNETON (9.27400899e-21) /* abamp cm^2 */ #define GSL_CONST_CGSM_NUCLEAR_MAGNETON (5.05078317e-24) /* abamp cm^2 */ #define GSL_CONST_CGSM_ELECTRON_MAGNETIC_MOMENT (9.28476362e-21) /* abamp cm^2 */ #define GSL_CONST_CGSM_PROTON_MAGNETIC_MOMENT (1.410606633e-23) /* abamp cm^2 */ #define GSL_CONST_CGSM_MOLAR_GAS (8.314472e7) /* g cm^2 / K mol s^2 */ #define GSL_CONST_CGSM_STANDARD_GAS_VOLUME (2.2710981e4) /* cm^3 / mol */ #define GSL_CONST_CGSM_MINUTE (6e1) /* s */ #define GSL_CONST_CGSM_HOUR (3.6e3) /* s */ #define GSL_CONST_CGSM_DAY (8.64e4) /* s */ #define GSL_CONST_CGSM_WEEK (6.048e5) /* s */ #define GSL_CONST_CGSM_INCH (2.54e0) /* cm */ #define GSL_CONST_CGSM_FOOT (3.048e1) /* cm */ #define GSL_CONST_CGSM_YARD (9.144e1) /* cm */ #define GSL_CONST_CGSM_MILE (1.609344e5) /* cm */ #define GSL_CONST_CGSM_NAUTICAL_MILE (1.852e5) /* cm */ #define GSL_CONST_CGSM_FATHOM (1.8288e2) /* cm */ #define GSL_CONST_CGSM_MIL (2.54e-3) /* cm */ #define GSL_CONST_CGSM_POINT (3.52777777778e-2) /* cm */ #define GSL_CONST_CGSM_TEXPOINT (3.51459803515e-2) /* cm */ #define GSL_CONST_CGSM_MICRON (1e-4) /* cm */ #define GSL_CONST_CGSM_ANGSTROM (1e-8) /* cm */ #define GSL_CONST_CGSM_HECTARE (1e8) /* cm^2 */ #define GSL_CONST_CGSM_ACRE (4.04685642241e7) /* cm^2 */ #define GSL_CONST_CGSM_BARN (1e-24) /* cm^2 */ #define GSL_CONST_CGSM_LITER (1e3) /* cm^3 */ #define GSL_CONST_CGSM_US_GALLON (3.78541178402e3) /* cm^3 */ #define GSL_CONST_CGSM_QUART (9.46352946004e2) /* cm^3 */ #define GSL_CONST_CGSM_PINT (4.73176473002e2) /* cm^3 */ #define GSL_CONST_CGSM_CUP (2.36588236501e2) /* cm^3 */ #define GSL_CONST_CGSM_FLUID_OUNCE (2.95735295626e1) /* cm^3 */ #define GSL_CONST_CGSM_TABLESPOON (1.47867647813e1) /* cm^3 */ #define GSL_CONST_CGSM_TEASPOON (4.92892159375e0) /* cm^3 */ #define GSL_CONST_CGSM_CANADIAN_GALLON (4.54609e3) /* cm^3 */ #define GSL_CONST_CGSM_UK_GALLON (4.546092e3) /* cm^3 */ #define GSL_CONST_CGSM_MILES_PER_HOUR (4.4704e1) /* cm / s */ #define GSL_CONST_CGSM_KILOMETERS_PER_HOUR (2.77777777778e1) /* cm / s */ #define GSL_CONST_CGSM_KNOT (5.14444444444e1) /* cm / s */ #define GSL_CONST_CGSM_POUND_MASS (4.5359237e2) /* g */ #define GSL_CONST_CGSM_OUNCE_MASS (2.8349523125e1) /* g */ #define GSL_CONST_CGSM_TON (9.0718474e5) /* g */ #define GSL_CONST_CGSM_METRIC_TON (1e6) /* g */ #define GSL_CONST_CGSM_UK_TON (1.0160469088e6) /* g */ #define GSL_CONST_CGSM_TROY_OUNCE (3.1103475e1) /* g */ #define GSL_CONST_CGSM_CARAT (2e-1) /* g */ #define GSL_CONST_CGSM_UNIFIED_ATOMIC_MASS (1.66053873e-24) /* g */ #define GSL_CONST_CGSM_GRAM_FORCE (9.80665e2) /* cm g / s^2 */ #define GSL_CONST_CGSM_POUND_FORCE (4.44822161526e5) /* cm g / s^2 */ #define GSL_CONST_CGSM_KILOPOUND_FORCE (4.44822161526e8) /* cm g / s^2 */ #define GSL_CONST_CGSM_POUNDAL (1.38255e4) /* cm g / s^2 */ #define GSL_CONST_CGSM_CALORIE (4.1868e7) /* g cm^2 / s^2 */ #define GSL_CONST_CGSM_BTU (1.05505585262e10) /* g cm^2 / s^2 */ #define GSL_CONST_CGSM_THERM (1.05506e15) /* g cm^2 / s^2 */ #define GSL_CONST_CGSM_HORSEPOWER (7.457e9) /* g cm^2 / s^3 */ #define GSL_CONST_CGSM_BAR (1e6) /* g / cm s^2 */ #define GSL_CONST_CGSM_STD_ATMOSPHERE (1.01325e6) /* g / cm s^2 */ #define GSL_CONST_CGSM_TORR (1.33322368421e3) /* g / cm s^2 */ #define GSL_CONST_CGSM_METER_OF_MERCURY (1.33322368421e6) /* g / cm s^2 */ #define GSL_CONST_CGSM_INCH_OF_MERCURY (3.38638815789e4) /* g / cm s^2 */ #define GSL_CONST_CGSM_INCH_OF_WATER (2.490889e3) /* g / cm s^2 */ #define GSL_CONST_CGSM_PSI (6.89475729317e4) /* g / cm s^2 */ #define GSL_CONST_CGSM_POISE (1e0) /* g / cm s */ #define GSL_CONST_CGSM_STOKES (1e0) /* cm^2 / s */ #define GSL_CONST_CGSM_FARADAY (9.6485341472e3) /* abamp s / mol */ #define GSL_CONST_CGSM_ELECTRON_CHARGE (1.602176462e-20) /* abamp s */ #define GSL_CONST_CGSM_GAUSS (1e0) /* g / abamp s^2 */ #define GSL_CONST_CGSM_STILB (1e0) /* cd / cm^2 */ #define GSL_CONST_CGSM_LUMEN (1e0) /* cd sr */ #define GSL_CONST_CGSM_LUX (1e-4) /* cd sr / cm^2 */ #define GSL_CONST_CGSM_PHOT (1e0) /* cd sr / cm^2 */ #define GSL_CONST_CGSM_FOOTCANDLE (1.076e-3) /* cd sr / cm^2 */ #define GSL_CONST_CGSM_LAMBERT (1e0) /* cd sr / cm^2 */ #define GSL_CONST_CGSM_FOOTLAMBERT (1.07639104e-3) /* cd sr / cm^2 */ #define GSL_CONST_CGSM_CURIE (3.7e10) /* 1 / s */ #define GSL_CONST_CGSM_ROENTGEN (2.58e-8) /* abamp s / g */ #define GSL_CONST_CGSM_RAD (1e2) /* cm^2 / s^2 */ #define GSL_CONST_CGSM_SOLAR_MASS (1.98892e33) /* g */ #define GSL_CONST_CGSM_BOHR_RADIUS (5.291772083e-9) /* cm */ #define GSL_CONST_CGSM_NEWTON (1e5) /* cm g / s^2 */ #define GSL_CONST_CGSM_DYNE (1e0) /* cm g / s^2 */ #define GSL_CONST_CGSM_JOULE (1e7) /* g cm^2 / s^2 */ #define GSL_CONST_CGSM_ERG (1e0) /* g cm^2 / s^2 */ #define GSL_CONST_CGSM_STEFAN_BOLTZMANN_CONSTANT (5.67039934436e-5) /* g / K^4 s^3 */ #define GSL_CONST_CGSM_THOMSON_CROSS_SECTION (6.65245853542e-25) /* cm^2 */ #endif /* __GSL_CONST_CGSM__ */ sources_5316/external/gsl/gsl_rng__schrage.c0000664000176700017670000000352211723710247017774 0ustar paulpaul/* rng/schrage.c * Copyright (C) 2003 Carlo Perassi and Heiko Bauke. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static inline unsigned long int schrage (unsigned long int a, unsigned long int b, unsigned long int m) { /* This is a modified version of Schrage's method. It ensures that no * overflow or underflow occurs even if a=ceil(sqrt(m)). Usual * Schrage's method works only until a=floor(sqrt(m)). */ unsigned long int q, t; if (a == 0UL) return 0UL; q = m / a; t = 2 * m - (m % a) * (b / q); if (t >= m) t -= m; t += a * (b % q); return (t >= m) ? (t - m) : t; } static inline unsigned long int schrage_mult (unsigned long int a, unsigned long int b, unsigned long int m, unsigned long int sqrtm) { /* To multiply a and b use Schrage's method 3 times. * represent a in base ceil(sqrt(m)) a = a1*ceil(sqrt(m)) + a0 * a*b = (a1*ceil(sqrt(m)) + a0)*b = a1*ceil(sqrt(m))*b + a0*b */ unsigned long int t0 = schrage (sqrtm, b, m); unsigned long int t1 = schrage (a / sqrtm, t0, m); unsigned long int t2 = schrage (a % sqrtm, b, m); unsigned long int t = t1 + t2; return (t >= m) ? (t - m) : t; } sources_5316/external/gsl/gsl_randist__chisq.c0000664000176700017670000000271511723710247020350 0ustar paulpaul/* randist/chisq.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_sf_gamma.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The chisq distribution has the form p(x) dx = (1/(2*Gamma(nu/2))) (x/2)^(nu/2 - 1) exp(-x/2) dx for x = 0 ... +infty */ double gsl_ran_chisq (const gsl_rng * r, const double nu) { double chisq = 2 * gsl_ran_gamma (r, nu / 2, 1.0); return chisq; } double gsl_ran_chisq_pdf (const double x, const double nu) { if (x <= 0) { return 0 ; } else { double p; double lngamma = gsl_sf_lngamma (nu / 2); p = exp ((nu / 2 - 1) * log (x/2) - x/2 - lngamma) / 2; return p; } } sources_5316/external/gsl/gsl_multifit__work.c0000664000176700017670000000643011723710247020412 0ustar paulpaul/* multifit/work.c * * Copyright (C) 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_multifit.h" gsl_multifit_linear_workspace * gsl_multifit_linear_alloc (size_t n, size_t p) { gsl_multifit_linear_workspace *w; w = (gsl_multifit_linear_workspace *) malloc (sizeof (gsl_multifit_linear_workspace)); if (w == 0) { GSL_ERROR_VAL ("failed to allocate space for multifit_linear struct", GSL_ENOMEM, 0); } w->n = n; /* number of observations */ w->p = p; /* number of parameters */ w->A = gsl_matrix_alloc (n, p); if (w->A == 0) { free (w); GSL_ERROR_VAL ("failed to allocate space for A", GSL_ENOMEM, 0); } w->Q = gsl_matrix_alloc (p, p); if (w->Q == 0) { gsl_matrix_free (w->A); free (w); GSL_ERROR_VAL ("failed to allocate space for Q", GSL_ENOMEM, 0); } w->QSI = gsl_matrix_alloc (p, p); if (w->QSI == 0) { gsl_matrix_free (w->Q); gsl_matrix_free (w->A); free (w); GSL_ERROR_VAL ("failed to allocate space for QSI", GSL_ENOMEM, 0); } w->S = gsl_vector_alloc (p); if (w->S == 0) { gsl_matrix_free (w->QSI); gsl_matrix_free (w->Q); gsl_matrix_free (w->A); free (w); GSL_ERROR_VAL ("failed to allocate space for S", GSL_ENOMEM, 0); } w->t = gsl_vector_alloc (n); if (w->t == 0) { gsl_vector_free (w->S); gsl_matrix_free (w->QSI); gsl_matrix_free (w->Q); gsl_matrix_free (w->A); free (w); GSL_ERROR_VAL ("failed to allocate space for t", GSL_ENOMEM, 0); } w->xt = gsl_vector_calloc (p); if (w->xt == 0) { gsl_vector_free (w->t); gsl_vector_free (w->S); gsl_matrix_free (w->QSI); gsl_matrix_free (w->Q); gsl_matrix_free (w->A); free (w); GSL_ERROR_VAL ("failed to allocate space for xt", GSL_ENOMEM, 0); } w->D = gsl_vector_calloc (p); if (w->D == 0) { gsl_vector_free (w->D); gsl_vector_free (w->t); gsl_vector_free (w->S); gsl_matrix_free (w->QSI); gsl_matrix_free (w->Q); gsl_matrix_free (w->A); free (w); GSL_ERROR_VAL ("failed to allocate space for xt", GSL_ENOMEM, 0); } return w; } void gsl_multifit_linear_free (gsl_multifit_linear_workspace * work) { gsl_matrix_free (work->A); gsl_matrix_free (work->Q); gsl_matrix_free (work->QSI); gsl_vector_free (work->S); gsl_vector_free (work->t); gsl_vector_free (work->xt); gsl_vector_free (work->D); free (work); } sources_5316/external/gsl/gsl_cblas__source_dot_r.h0000664000176700017670000000177311705263724021363 0ustar paulpaul/* blas/source_dot_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { ACC_TYPE r = INIT_VAL; INDEX i; INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { r += X[ix] * Y[iy]; ix += incX; iy += incY; } return r; } sources_5316/external/gsl/gsl_block.h0000664000176700017670000000101411705263724016447 0ustar paulpaul#ifndef __GSL_BLOCK_H__ #define __GSL_BLOCK_H__ #include "gsl_block_complex_long_double.h" #include "gsl_block_complex_double.h" #include "gsl_block_complex_float.h" #include "gsl_block_long_double.h" #include "gsl_block_double.h" #include "gsl_block_float.h" #include "gsl_block_ulong.h" #include "gsl_block_long.h" #include "gsl_block_uint.h" #include "gsl_block_int.h" #include "gsl_block_ushort.h" #include "gsl_block_short.h" #include "gsl_block_uchar.h" #include "gsl_block_char.h" #endif /* __GSL_BLOCK_H__ */ sources_5316/external/gsl/gsl_statistics_float.h0000664000176700017670000001436011705263724020744 0ustar paulpaul/* statistics/gsl_statistics_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_FLOAT_H__ #define __GSL_STATISTICS_FLOAT_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_float_mean (const float data[], const size_t stride, const size_t n); double gsl_stats_float_variance (const float data[], const size_t stride, const size_t n); double gsl_stats_float_sd (const float data[], const size_t stride, const size_t n); double gsl_stats_float_variance_with_fixed_mean (const float data[], const size_t stride, const size_t n, const double mean); double gsl_stats_float_sd_with_fixed_mean (const float data[], const size_t stride, const size_t n, const double mean); double gsl_stats_float_absdev (const float data[], const size_t stride, const size_t n); double gsl_stats_float_skew (const float data[], const size_t stride, const size_t n); double gsl_stats_float_kurtosis (const float data[], const size_t stride, const size_t n); double gsl_stats_float_lag1_autocorrelation (const float data[], const size_t stride, const size_t n); double gsl_stats_float_covariance (const float data1[], const size_t stride1,const float data2[], const size_t stride2, const size_t n); double gsl_stats_float_correlation (const float data1[], const size_t stride1,const float data2[], const size_t stride2, const size_t n); double gsl_stats_float_variance_m (const float data[], const size_t stride, const size_t n, const double mean); double gsl_stats_float_sd_m (const float data[], const size_t stride, const size_t n, const double mean); double gsl_stats_float_absdev_m (const float data[], const size_t stride, const size_t n, const double mean); double gsl_stats_float_skew_m_sd (const float data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_float_kurtosis_m_sd (const float data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_float_lag1_autocorrelation_m (const float data[], const size_t stride, const size_t n, const double mean); double gsl_stats_float_covariance_m (const float data1[], const size_t stride1,const float data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); /* DEFINED FOR FLOATING POINT TYPES ONLY */ double gsl_stats_float_wmean (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n); double gsl_stats_float_wvariance (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n); double gsl_stats_float_wsd (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n); double gsl_stats_float_wvariance_with_fixed_mean (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n, const double mean); double gsl_stats_float_wsd_with_fixed_mean (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n, const double mean); double gsl_stats_float_wabsdev (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n); double gsl_stats_float_wskew (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n); double gsl_stats_float_wkurtosis (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n); double gsl_stats_float_wvariance_m (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n, const double wmean); double gsl_stats_float_wsd_m (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n, const double wmean); double gsl_stats_float_wabsdev_m (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n, const double wmean); double gsl_stats_float_wskew_m_sd (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n, const double wmean, const double wsd); double gsl_stats_float_wkurtosis_m_sd (const float w[], const size_t wstride, const float data[], const size_t stride, const size_t n, const double wmean, const double wsd); /* END OF FLOATING POINT TYPES */ double gsl_stats_float_pvariance (const float data1[], const size_t stride1, const size_t n1, const float data2[], const size_t stride2, const size_t n2); double gsl_stats_float_ttest (const float data1[], const size_t stride1, const size_t n1, const float data2[], const size_t stride2, const size_t n2); float gsl_stats_float_max (const float data[], const size_t stride, const size_t n); float gsl_stats_float_min (const float data[], const size_t stride, const size_t n); void gsl_stats_float_minmax (float * min, float * max, const float data[], const size_t stride, const size_t n); size_t gsl_stats_float_max_index (const float data[], const size_t stride, const size_t n); size_t gsl_stats_float_min_index (const float data[], const size_t stride, const size_t n); void gsl_stats_float_minmax_index (size_t * min_index, size_t * max_index, const float data[], const size_t stride, const size_t n); double gsl_stats_float_median_from_sorted_data (const float sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_float_quantile_from_sorted_data (const float sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_FLOAT_H__ */ sources_5316/external/gsl/gsl_block_double.h0000664000176700017670000000420511705263724020006 0ustar paulpaul/* block/gsl_block_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_DOUBLE_H__ #define __GSL_BLOCK_DOUBLE_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_struct { size_t size; double *data; }; typedef struct gsl_block_struct gsl_block; gsl_block *gsl_block_alloc (const size_t n); gsl_block *gsl_block_calloc (const size_t n); void gsl_block_free (gsl_block * b); int gsl_block_fread (FILE * stream, gsl_block * b); int gsl_block_fwrite (FILE * stream, const gsl_block * b); int gsl_block_fscanf (FILE * stream, gsl_block * b); int gsl_block_fprintf (FILE * stream, const gsl_block * b, const char *format); int gsl_block_raw_fread (FILE * stream, double * b, const size_t n, const size_t stride); int gsl_block_raw_fwrite (FILE * stream, const double * b, const size_t n, const size_t stride); int gsl_block_raw_fscanf (FILE * stream, double * b, const size_t n, const size_t stride); int gsl_block_raw_fprintf (FILE * stream, const double * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_size (const gsl_block * b); double * gsl_block_data (const gsl_block * b); __END_DECLS #endif /* __GSL_BLOCK_DOUBLE_H__ */ sources_5316/external/gsl/gsl_specfunc__cheb_eval_mode.c0000664000176700017670000000125011723710247022310 0ustar paulpaulstatic inline int cheb_eval_mode_e(const cheb_series * cs, const double x, gsl_mode_t mode, gsl_sf_result * result) { int j; double d = 0.0; double dd = 0.0; double y = (2.*x - cs->a - cs->b) / (cs->b - cs->a); double y2 = 2.0 * y; int eval_order; if(GSL_MODE_PREC(mode) == GSL_PREC_DOUBLE) eval_order = cs->order; else eval_order = cs->order_sp; for(j = eval_order; j>=1; j--) { double temp = d; d = y2*d - dd + cs->c[j]; dd = temp; } result->val = y*d - dd + 0.5 * cs->c[0]; result->err = GSL_DBL_EPSILON * fabs(result->val) + fabs(cs->c[eval_order]); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_multimin__fminimizer.c0000664000176700017670000000622111723710247021600 0ustar paulpaul/* multimin/fminimizer.c * * Copyright (C) 2002 Tuomo Keskitalo, Ivo Alxneit * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_multimin.h" gsl_multimin_fminimizer * gsl_multimin_fminimizer_alloc (const gsl_multimin_fminimizer_type * T, size_t n) { int status; gsl_multimin_fminimizer *s = (gsl_multimin_fminimizer *) malloc (sizeof (gsl_multimin_fminimizer)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for minimizer struct", GSL_ENOMEM, 0); } s->type = T; s->x = gsl_vector_calloc (n); if (s->x == 0) { free (s); GSL_ERROR_VAL ("failed to allocate space for x", GSL_ENOMEM, 0); } s->state = malloc (T->size); if (s->state == 0) { gsl_vector_free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for minimizer state", GSL_ENOMEM, 0); } status = (T->alloc) (s->state, n); if (status != GSL_SUCCESS) { free (s->state); gsl_vector_free (s->x); free (s); GSL_ERROR_VAL ("failed to initialize minimizer state", GSL_ENOMEM, 0); } return s; } int gsl_multimin_fminimizer_set (gsl_multimin_fminimizer * s, gsl_multimin_function * f, const gsl_vector * x, const gsl_vector * step_size) { if (s->x->size != f->n) { GSL_ERROR ("function incompatible with solver size", GSL_EBADLEN); } if (x->size != f->n || step_size->size != f->n) { GSL_ERROR ("vector length not compatible with function", GSL_EBADLEN); } s->f = f; gsl_vector_memcpy (s->x,x); return (s->type->set) (s->state, s->f, s->x, &(s->size), step_size); } void gsl_multimin_fminimizer_free (gsl_multimin_fminimizer * s) { (s->type->free) (s->state); free (s->state); gsl_vector_free (s->x); free (s); } int gsl_multimin_fminimizer_iterate (gsl_multimin_fminimizer * s) { return (s->type->iterate) (s->state, s->f, s->x, &(s->size), &(s->fval)); } const char * gsl_multimin_fminimizer_name (const gsl_multimin_fminimizer * s) { return s->type->name; } gsl_vector * gsl_multimin_fminimizer_x (const gsl_multimin_fminimizer * s) { return s->x; } double gsl_multimin_fminimizer_minimum (const gsl_multimin_fminimizer * s) { return s->fval; } double gsl_multimin_fminimizer_size (const gsl_multimin_fminimizer * s) { return s->size; } sources_5316/external/gsl/gsl_err__error.c0000664000176700017670000000400311723710247017506 0ustar paulpaul/* err/error.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include "gsl_errno.h" #include "gsl_message.h" gsl_error_handler_t * gsl_error_handler = NULL; static void no_error_handler (const char *reason, const char *file, int line, int gsl_errno); void gsl_error (const char * reason, const char * file, int line, int gsl_errno) { if (gsl_error_handler) { (*gsl_error_handler) (reason, file, line, gsl_errno); return ; } gsl_stream_printf ("ERROR", file, line, reason); fflush (stdout); fprintf (stderr, "Default GSL error handler invoked.\n"); fflush (stderr); abort (); } gsl_error_handler_t * gsl_set_error_handler (gsl_error_handler_t * new_handler) { gsl_error_handler_t * previous_handler = gsl_error_handler; gsl_error_handler = new_handler; return previous_handler; } gsl_error_handler_t * gsl_set_error_handler_off (void) { gsl_error_handler_t * previous_handler = gsl_error_handler; gsl_error_handler = no_error_handler; return previous_handler; } static void no_error_handler (const char *reason, const char *file, int line, int gsl_errno) { /* do nothing */ reason = 0; file = 0; line = 0; gsl_errno = 0; return; } sources_5316/external/gsl/gsl_cblas__zdotu_sub.c0000664000176700017670000000047011723710247020673 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zdotu_sub (const int N, const void *X, const int incX, const void *Y, const int incY, void *result) { #define BASE double #define CONJ_SIGN 1.0 #include "gsl_cblas__source_dot_c.h" #undef CONJ_SIGN #undef BASE } sources_5316/external/gsl/gsl_cblas__sgemm.c0000664000176700017670000000074211723710247017767 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_sgemm (const enum CBLAS_ORDER Order, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_TRANSPOSE TransB, const int M, const int N, const int K, const float alpha, const float *A, const int lda, const float *B, const int ldb, const float beta, float *C, const int ldc) { #define BASE float #include "gsl_cblas__source_gemm_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_symm_r.h0000664000176700017670000000670611705263724021563 0ustar paulpaul/* blas/source_symm_r.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; INDEX n1, n2; int uplo, side; if (alpha == 0.0 && beta == 1.0) return; if (Order == CblasRowMajor) { n1 = M; n2 = N; uplo = Uplo; side = Side; } else { n1 = N; n2 = M; uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; side = (Side == CblasLeft) ? CblasRight : CblasLeft; } /* form y := beta*y */ if (beta == 0.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { C[ldc * i + j] = 0.0; } } } else if (beta != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { C[ldc * i + j] *= beta; } } } if (alpha == 0.0) return; if (side == CblasLeft && uplo == CblasUpper) { /* form C := alpha*A*B + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE temp1 = alpha * B[ldb * i + j]; BASE temp2 = 0.0; C[i * ldc + j] += temp1 * A[i * lda + i]; for (k = i + 1; k < n1; k++) { const BASE Aik = A[i * lda + k]; C[k * ldc + j] += Aik * temp1; temp2 += Aik * B[ldb * k + j]; } C[i * ldc + j] += alpha * temp2; } } } else if (side == CblasLeft && uplo == CblasLower) { /* form C := alpha*A*B + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE temp1 = alpha * B[ldb * i + j]; BASE temp2 = 0.0; for (k = 0; k < i; k++) { const BASE Aik = A[i * lda + k]; C[k * ldc + j] += Aik * temp1; temp2 += Aik * B[ldb * k + j]; } C[i * ldc + j] += temp1 * A[i * lda + i] + alpha * temp2; } } } else if (side == CblasRight && uplo == CblasUpper) { /* form C := alpha*B*A + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE temp1 = alpha * B[ldb * i + j]; BASE temp2 = 0.0; C[i * ldc + j] += temp1 * A[j * lda + j]; for (k = j + 1; k < n2; k++) { const BASE Ajk = A[j * lda + k]; C[i * ldc + k] += temp1 * Ajk; temp2 += B[ldb * i + k] * Ajk; } C[i * ldc + j] += alpha * temp2; } } } else if (side == CblasRight && uplo == CblasLower) { /* form C := alpha*B*A + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE temp1 = alpha * B[ldb * i + j]; BASE temp2 = 0.0; for (k = 0; k < j; k++) { const BASE Ajk = A[j * lda + k]; C[i * ldc + k] += temp1 * Ajk; temp2 += B[ldb * i + k] * Ajk; } C[i * ldc + j] += temp1 * A[j * lda + j] + alpha * temp2; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_sf__zeta.c0000644000176700017670000010077110707442037017147 0ustar paulpaul/* specfunc/zeta.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_elementary.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_zeta.h" #include "gsl_sf__error.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" #define LogTwoPi_ 1.8378770664093454835606594728111235279723 /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* chebyshev fit for (s(t)-1)Zeta[s(t)] * s(t)= (t+1)/2 * -1 <= t <= 1 */ static double zeta_xlt1_data[14] = { 1.48018677156931561235192914649, 0.25012062539889426471999938167, 0.00991137502135360774243761467, -0.00012084759656676410329833091, -4.7585866367662556504652535281e-06, 2.2229946694466391855561441361e-07, -2.2237496498030257121309056582e-09, -1.0173226513229028319420799028e-10, 4.3756643450424558284466248449e-12, -6.2229632593100551465504090814e-14, -6.6116201003272207115277520305e-16, 4.9477279533373912324518463830e-17, -1.0429819093456189719660003522e-18, 6.9925216166580021051464412040e-21, }; static cheb_series zeta_xlt1_cs = { zeta_xlt1_data, 13, -1, 1, 8 }; /* chebyshev fit for (s(t)-1)Zeta[s(t)] * s(t)= (19t+21)/2 * -1 <= t <= 1 */ static double zeta_xgt1_data[30] = { 19.3918515726724119415911269006, 9.1525329692510756181581271500, 0.2427897658867379985365270155, -0.1339000688262027338316641329, 0.0577827064065028595578410202, -0.0187625983754002298566409700, 0.0039403014258320354840823803, -0.0000581508273158127963598882, -0.0003756148907214820704594549, 0.0001892530548109214349092999, -0.0000549032199695513496115090, 8.7086484008939038610413331863e-6, 6.4609477924811889068410083425e-7, -9.6749773915059089205835337136e-7, 3.6585400766767257736982342461e-7, -8.4592516427275164351876072573e-8, 9.9956786144497936572288988883e-9, 1.4260036420951118112457144842e-9, -1.1761968823382879195380320948e-9, 3.7114575899785204664648987295e-10, -7.4756855194210961661210215325e-11, 7.8536934209183700456512982968e-12, 9.9827182259685539619810406271e-13, -7.5276687030192221587850302453e-13, 2.1955026393964279988917878654e-13, -4.1934859852834647427576319246e-14, 4.6341149635933550715779074274e-15, 2.3742488509048340106830309402e-16, -2.7276516388124786119323824391e-16, 7.8473570134636044722154797225e-17 }; static cheb_series zeta_xgt1_cs = { zeta_xgt1_data, 29, -1, 1, 17 }; /* chebyshev fit for Ln[Zeta[s(t)] - 1 - 2^(-s(t))] * s(t)= 10 + 5t * -1 <= t <= 1; 5 <= s <= 15 */ static double zetam1_inter_data[24] = { -21.7509435653088483422022339374, -5.63036877698121782876372020472, 0.0528041358684229425504861579635, -0.0156381809179670789342700883562, 0.00408218474372355881195080781927, -0.0010264867349474874045036628282, 0.000260469880409886900143834962387, -0.0000676175847209968878098566819447, 0.0000179284472587833525426660171124, -4.83238651318556188834107605116e-6, 1.31913788964999288471371329447e-6, -3.63760500656329972578222188542e-7, 1.01146847513194744989748396574e-7, -2.83215225141806501619105289509e-8, 7.97733710252021423361012829496e-9, -2.25850168553956886676250696891e-9, 6.42269392950164306086395744145e-10, -1.83363861846127284505060843614e-10, 5.25309763895283179960368072104e-11, -1.50958687042589821074710575446e-11, 4.34997545516049244697776942981e-12, -1.25597782748190416118082322061e-12, 3.61280740072222650030134104162e-13, -9.66437239205745207188920348801e-14 }; static cheb_series zetam1_inter_cs = { zetam1_inter_data, 22, -1, 1, 12 }; /* assumes s >= 0 and s != 1.0 */ inline static int riemann_zeta_sgt0(double s, gsl_sf_result * result) { if(s < 1.0) { gsl_sf_result c; cheb_eval_e(&zeta_xlt1_cs, 2.0*s - 1.0, &c); result->val = c.val / (s - 1.0); result->err = c.err / fabs(s-1.0) + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(s <= 20.0) { double x = (2.0*s - 21.0)/19.0; gsl_sf_result c; cheb_eval_e(&zeta_xgt1_cs, x, &c); result->val = c.val / (s - 1.0); result->err = c.err / (s - 1.0) + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double f2 = 1.0 - pow(2.0,-s); double f3 = 1.0 - pow(3.0,-s); double f5 = 1.0 - pow(5.0,-s); double f7 = 1.0 - pow(7.0,-s); result->val = 1.0/(f2*f3*f5*f7); result->err = 3.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } inline static int riemann_zeta1ms_slt0(double s, gsl_sf_result * result) { if(s > -19.0) { double x = (-19 - 2.0*s)/19.0; gsl_sf_result c; cheb_eval_e(&zeta_xgt1_cs, x, &c); result->val = c.val / (-s); result->err = c.err / (-s) + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double f2 = 1.0 - pow(2.0,-(1.0-s)); double f3 = 1.0 - pow(3.0,-(1.0-s)); double f5 = 1.0 - pow(5.0,-(1.0-s)); double f7 = 1.0 - pow(7.0,-(1.0-s)); result->val = 1.0/(f2*f3*f5*f7); result->err = 3.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /* works for 5 < s < 15*/ static int riemann_zeta_minus_1_intermediate_s(double s, gsl_sf_result * result) { double t = (s - 10.0)/5.0; gsl_sf_result c; cheb_eval_e(&zetam1_inter_cs, t, &c); result->val = exp(c.val) + pow(2.0, -s); result->err = (c.err + 2.0*GSL_DBL_EPSILON)*result->val; return GSL_SUCCESS; } /* assumes s is large and positive * write: zeta(s) - 1 = zeta(s) * (1 - 1/zeta(s)) * and expand a few terms of the product formula to evaluate 1 - 1/zeta(s) * * works well for s > 15 */ static int riemann_zeta_minus1_large_s(double s, gsl_sf_result * result) { double a = pow( 2.0,-s); double b = pow( 3.0,-s); double c = pow( 5.0,-s); double d = pow( 7.0,-s); double e = pow(11.0,-s); double f = pow(13.0,-s); double t1 = a + b + c + d + e + f; double t2 = a*(b+c+d+e+f) + b*(c+d+e+f) + c*(d+e+f) + d*(e+f) + e*f; /* double t3 = a*(b*(c+d+e+f) + c*(d+e+f) + d*(e+f) + e*f) + b*(c*(d+e+f) + d*(e+f) + e*f) + c*(d*(e+f) + e*f) + d*e*f; double t4 = a*(b*(c*(d + e + f) + d*(e + f) + e*f) + c*(d*(e+f) + e*f) + d*e*f) + b*(c*(d*(e+f) + e*f) + d*e*f) + c*d*e*f; double t5 = b*c*d*e*f + a*c*d*e*f+ a*b*d*e*f+ a*b*c*e*f+ a*b*c*d*f+ a*b*c*d*e; double t6 = a*b*c*d*e*f; */ double numt = t1 - t2 /* + t3 - t4 + t5 - t6 */; double zeta = 1.0/((1.0-a)*(1.0-b)*(1.0-c)*(1.0-d)*(1.0-e)*(1.0-f)); result->val = numt*zeta; result->err = (15.0/s + 1.0) * 6.0*GSL_DBL_EPSILON*result->val; return GSL_SUCCESS; } #if 0 /* zeta(n) */ #define ZETA_POS_TABLE_NMAX 100 static double zeta_pos_int_table_OLD[ZETA_POS_TABLE_NMAX+1] = { -0.50000000000000000000000000000, /* zeta(0) */ 0.0 /* FIXME: DirectedInfinity() */, /* zeta(1) */ 1.64493406684822643647241516665, /* ... */ 1.20205690315959428539973816151, 1.08232323371113819151600369654, 1.03692775514336992633136548646, 1.01734306198444913971451792979, 1.00834927738192282683979754985, 1.00407735619794433937868523851, 1.00200839282608221441785276923, 1.00099457512781808533714595890, 1.00049418860411946455870228253, 1.00024608655330804829863799805, 1.00012271334757848914675183653, 1.00006124813505870482925854511, 1.00003058823630702049355172851, 1.00001528225940865187173257149, 1.00000763719763789976227360029, 1.00000381729326499983985646164, 1.00000190821271655393892565696, 1.00000095396203387279611315204, 1.00000047693298678780646311672, 1.00000023845050272773299000365, 1.00000011921992596531107306779, 1.00000005960818905125947961244, 1.00000002980350351465228018606, 1.00000001490155482836504123466, 1.00000000745071178983542949198, 1.00000000372533402478845705482, 1.00000000186265972351304900640, 1.00000000093132743241966818287, 1.00000000046566290650337840730, 1.00000000023283118336765054920, 1.00000000011641550172700519776, 1.00000000005820772087902700889, 1.00000000002910385044497099687, 1.00000000001455192189104198424, 1.00000000000727595983505748101, 1.00000000000363797954737865119, 1.00000000000181898965030706595, 1.00000000000090949478402638893, 1.00000000000045474737830421540, 1.00000000000022737368458246525, 1.00000000000011368684076802278, 1.00000000000005684341987627586, 1.00000000000002842170976889302, 1.00000000000001421085482803161, 1.00000000000000710542739521085, 1.00000000000000355271369133711, 1.00000000000000177635684357912, 1.00000000000000088817842109308, 1.00000000000000044408921031438, 1.00000000000000022204460507980, 1.00000000000000011102230251411, 1.00000000000000005551115124845, 1.00000000000000002775557562136, 1.00000000000000001387778780973, 1.00000000000000000693889390454, 1.00000000000000000346944695217, 1.00000000000000000173472347605, 1.00000000000000000086736173801, 1.00000000000000000043368086900, 1.00000000000000000021684043450, 1.00000000000000000010842021725, 1.00000000000000000005421010862, 1.00000000000000000002710505431, 1.00000000000000000001355252716, 1.00000000000000000000677626358, 1.00000000000000000000338813179, 1.00000000000000000000169406589, 1.00000000000000000000084703295, 1.00000000000000000000042351647, 1.00000000000000000000021175824, 1.00000000000000000000010587912, 1.00000000000000000000005293956, 1.00000000000000000000002646978, 1.00000000000000000000001323489, 1.00000000000000000000000661744, 1.00000000000000000000000330872, 1.00000000000000000000000165436, 1.00000000000000000000000082718, 1.00000000000000000000000041359, 1.00000000000000000000000020680, 1.00000000000000000000000010340, 1.00000000000000000000000005170, 1.00000000000000000000000002585, 1.00000000000000000000000001292, 1.00000000000000000000000000646, 1.00000000000000000000000000323, 1.00000000000000000000000000162, 1.00000000000000000000000000081, 1.00000000000000000000000000040, 1.00000000000000000000000000020, 1.00000000000000000000000000010, 1.00000000000000000000000000005, 1.00000000000000000000000000003, 1.00000000000000000000000000001, 1.00000000000000000000000000001, 1.00000000000000000000000000000, 1.00000000000000000000000000000, 1.00000000000000000000000000000 }; #endif /* 0 */ /* zeta(n) - 1 */ #define ZETA_POS_TABLE_NMAX 100 static double zetam1_pos_int_table[ZETA_POS_TABLE_NMAX+1] = { -1.5, /* zeta(0) */ 0.0, /* FIXME: Infinity */ /* zeta(1) - 1 */ 0.644934066848226436472415166646, /* zeta(2) - 1 */ 0.202056903159594285399738161511, 0.082323233711138191516003696541, 0.036927755143369926331365486457, 0.017343061984449139714517929790, 0.008349277381922826839797549849, 0.004077356197944339378685238508, 0.002008392826082214417852769232, 0.000994575127818085337145958900, 0.000494188604119464558702282526, 0.000246086553308048298637998047, 0.000122713347578489146751836526, 0.000061248135058704829258545105, 0.000030588236307020493551728510, 0.000015282259408651871732571487, 7.6371976378997622736002935630e-6, 3.8172932649998398564616446219e-6, 1.9082127165539389256569577951e-6, 9.5396203387279611315203868344e-7, 4.7693298678780646311671960437e-7, 2.3845050272773299000364818675e-7, 1.1921992596531107306778871888e-7, 5.9608189051259479612440207935e-8, 2.9803503514652280186063705069e-8, 1.4901554828365041234658506630e-8, 7.4507117898354294919810041706e-9, 3.7253340247884570548192040184e-9, 1.8626597235130490064039099454e-9, 9.3132743241966818287176473502e-10, 4.6566290650337840729892332512e-10, 2.3283118336765054920014559759e-10, 1.1641550172700519775929738354e-10, 5.8207720879027008892436859891e-11, 2.9103850444970996869294252278e-11, 1.4551921891041984235929632245e-11, 7.2759598350574810145208690123e-12, 3.6379795473786511902372363558e-12, 1.8189896503070659475848321007e-12, 9.0949478402638892825331183869e-13, 4.5474737830421540267991120294e-13, 2.2737368458246525152268215779e-13, 1.1368684076802278493491048380e-13, 5.6843419876275856092771829675e-14, 2.8421709768893018554550737049e-14, 1.4210854828031606769834307141e-14, 7.1054273952108527128773544799e-15, 3.5527136913371136732984695340e-15, 1.7763568435791203274733490144e-15, 8.8817842109308159030960913863e-16, 4.4408921031438133641977709402e-16, 2.2204460507980419839993200942e-16, 1.1102230251410661337205445699e-16, 5.5511151248454812437237365905e-17, 2.7755575621361241725816324538e-17, 1.3877787809725232762839094906e-17, 6.9388939045441536974460853262e-18, 3.4694469521659226247442714961e-18, 1.7347234760475765720489729699e-18, 8.6736173801199337283420550673e-19, 4.3368086900206504874970235659e-19, 2.1684043449972197850139101683e-19, 1.0842021724942414063012711165e-19, 5.4210108624566454109187004043e-20, 2.7105054312234688319546213119e-20, 1.3552527156101164581485233996e-20, 6.7762635780451890979952987415e-21, 3.3881317890207968180857031004e-21, 1.6940658945097991654064927471e-21, 8.4703294725469983482469926091e-22, 4.2351647362728333478622704833e-22, 2.1175823681361947318442094398e-22, 1.0587911840680233852265001539e-22, 5.2939559203398703238139123029e-23, 2.6469779601698529611341166842e-23, 1.3234889800848990803094510250e-23, 6.6174449004244040673552453323e-24, 3.3087224502121715889469563843e-24, 1.6543612251060756462299236771e-24, 8.2718061255303444036711056167e-25, 4.1359030627651609260093824555e-25, 2.0679515313825767043959679193e-25, 1.0339757656912870993284095591e-25, 5.1698788284564313204101332166e-26, 2.5849394142282142681277617708e-26, 1.2924697071141066700381126118e-26, 6.4623485355705318034380021611e-27, 3.2311742677852653861348141180e-27, 1.6155871338926325212060114057e-27, 8.0779356694631620331587381863e-28, 4.0389678347315808256222628129e-28, 2.0194839173657903491587626465e-28, 1.0097419586828951533619250700e-28, 5.0487097934144756960847711725e-29, 2.5243548967072378244674341938e-29, 1.2621774483536189043753999660e-29, 6.3108872417680944956826093943e-30, 3.1554436208840472391098412184e-30, 1.5777218104420236166444327830e-30, 7.8886090522101180735205378276e-31 }; #define ZETA_NEG_TABLE_NMAX 99 #define ZETA_NEG_TABLE_SIZE 50 static double zeta_neg_int_table[ZETA_NEG_TABLE_SIZE] = { -0.083333333333333333333333333333, /* zeta(-1) */ 0.008333333333333333333333333333, /* zeta(-3) */ -0.003968253968253968253968253968, /* ... */ 0.004166666666666666666666666667, -0.007575757575757575757575757576, 0.021092796092796092796092796093, -0.083333333333333333333333333333, 0.44325980392156862745098039216, -3.05395433027011974380395433027, 26.4562121212121212121212121212, -281.460144927536231884057971014, 3607.5105463980463980463980464, -54827.583333333333333333333333, 974936.82385057471264367816092, -2.0052695796688078946143462272e+07, 4.7238486772162990196078431373e+08, -1.2635724795916666666666666667e+10, 3.8087931125245368811553022079e+11, -1.2850850499305083333333333333e+13, 4.8241448354850170371581670362e+14, -2.0040310656516252738108421663e+16, 9.1677436031953307756992753623e+17, -4.5979888343656503490437943262e+19, 2.5180471921451095697089023320e+21, -1.5001733492153928733711440151e+23, 9.6899578874635940656497942895e+24, -6.7645882379292820990945242302e+26, 5.0890659468662289689766332916e+28, -4.1147288792557978697665486068e+30, 3.5666582095375556109684574609e+32, -3.3066089876577576725680214670e+34, 3.2715634236478716264211227016e+36, -3.4473782558278053878256455080e+38, 3.8614279832705258893092720200e+40, -4.5892974432454332168863989006e+42, 5.7775386342770431824884825688e+44, -7.6919858759507135167410075972e+46, 1.0813635449971654696354033351e+49, -1.6029364522008965406067102346e+51, 2.5019479041560462843656661499e+53, -4.1067052335810212479752045004e+55, 7.0798774408494580617452972433e+57, -1.2804546887939508790190849756e+60, 2.4267340392333524078020892067e+62, -4.8143218874045769355129570066e+64, 9.9875574175727530680652777408e+66, -2.1645634868435185631335136160e+69, 4.8962327039620553206849224516e+71, /* ... */ -1.1549023923963519663954271692e+74, /* zeta(-97) */ 2.8382249570693706959264156336e+76 /* zeta(-99) */ }; /* coefficients for Maclaurin summation in hzeta() * B_{2j}/(2j)! */ static double hzeta_c[15] = { 1.00000000000000000000000000000, 0.083333333333333333333333333333, -0.00138888888888888888888888888889, 0.000033068783068783068783068783069, -8.2671957671957671957671957672e-07, 2.0876756987868098979210090321e-08, -5.2841901386874931848476822022e-10, 1.3382536530684678832826980975e-11, -3.3896802963225828668301953912e-13, 8.5860620562778445641359054504e-15, -2.1748686985580618730415164239e-16, 5.5090028283602295152026526089e-18, -1.3954464685812523340707686264e-19, 3.5347070396294674716932299778e-21, -8.9535174270375468504026113181e-23 }; #define ETA_POS_TABLE_NMAX 100 static double eta_pos_int_table[ETA_POS_TABLE_NMAX+1] = { 0.50000000000000000000000000000, /* eta(0) */ M_LN2, /* eta(1) */ 0.82246703342411321823620758332, /* ... */ 0.90154267736969571404980362113, 0.94703282949724591757650323447, 0.97211977044690930593565514355, 0.98555109129743510409843924448, 0.99259381992283028267042571313, 0.99623300185264789922728926008, 0.99809429754160533076778303185, 0.99903950759827156563922184570, 0.99951714349806075414409417483, 0.99975768514385819085317967871, 0.99987854276326511549217499282, 0.99993917034597971817095419226, 0.99996955121309923808263293263, 0.99998476421490610644168277496, 0.99999237829204101197693787224, 0.99999618786961011347968922641, 0.99999809350817167510685649297, 0.99999904661158152211505084256, 0.99999952325821554281631666433, 0.99999976161323082254789720494, 0.99999988080131843950322382485, 0.99999994039889239462836140314, 0.99999997019885696283441513311, 0.99999998509923199656878766181, 0.99999999254955048496351585274, 0.99999999627475340010872752767, 0.99999999813736941811218674656, 0.99999999906868228145397862728, 0.99999999953434033145421751469, 0.99999999976716989595149082282, 0.99999999988358485804603047265, 0.99999999994179239904531592388, 0.99999999997089618952980952258, 0.99999999998544809143388476396, 0.99999999999272404460658475006, 0.99999999999636202193316875550, 0.99999999999818101084320873555, 0.99999999999909050538047887809, 0.99999999999954525267653087357, 0.99999999999977262633369589773, 0.99999999999988631316532476488, 0.99999999999994315658215465336, 0.99999999999997157829090808339, 0.99999999999998578914539762720, 0.99999999999999289457268000875, 0.99999999999999644728633373609, 0.99999999999999822364316477861, 0.99999999999999911182158169283, 0.99999999999999955591079061426, 0.99999999999999977795539522974, 0.99999999999999988897769758908, 0.99999999999999994448884878594, 0.99999999999999997224442439010, 0.99999999999999998612221219410, 0.99999999999999999306110609673, 0.99999999999999999653055304826, 0.99999999999999999826527652409, 0.99999999999999999913263826204, 0.99999999999999999956631913101, 0.99999999999999999978315956551, 0.99999999999999999989157978275, 0.99999999999999999994578989138, 0.99999999999999999997289494569, 0.99999999999999999998644747284, 0.99999999999999999999322373642, 0.99999999999999999999661186821, 0.99999999999999999999830593411, 0.99999999999999999999915296705, 0.99999999999999999999957648353, 0.99999999999999999999978824176, 0.99999999999999999999989412088, 0.99999999999999999999994706044, 0.99999999999999999999997353022, 0.99999999999999999999998676511, 0.99999999999999999999999338256, 0.99999999999999999999999669128, 0.99999999999999999999999834564, 0.99999999999999999999999917282, 0.99999999999999999999999958641, 0.99999999999999999999999979320, 0.99999999999999999999999989660, 0.99999999999999999999999994830, 0.99999999999999999999999997415, 0.99999999999999999999999998708, 0.99999999999999999999999999354, 0.99999999999999999999999999677, 0.99999999999999999999999999838, 0.99999999999999999999999999919, 0.99999999999999999999999999960, 0.99999999999999999999999999980, 0.99999999999999999999999999990, 0.99999999999999999999999999995, 0.99999999999999999999999999997, 0.99999999999999999999999999999, 0.99999999999999999999999999999, 1.00000000000000000000000000000, 1.00000000000000000000000000000, 1.00000000000000000000000000000, }; #define ETA_NEG_TABLE_NMAX 99 #define ETA_NEG_TABLE_SIZE 50 static double eta_neg_int_table[ETA_NEG_TABLE_SIZE] = { 0.25000000000000000000000000000, /* eta(-1) */ -0.12500000000000000000000000000, /* eta(-3) */ 0.25000000000000000000000000000, /* ... */ -1.06250000000000000000000000000, 7.75000000000000000000000000000, -86.3750000000000000000000000000, 1365.25000000000000000000000000, -29049.0312500000000000000000000, 800572.750000000000000000000000, -2.7741322625000000000000000000e+7, 1.1805291302500000000000000000e+9, -6.0523980051687500000000000000e+10, 3.6794167785377500000000000000e+12, -2.6170760990658387500000000000e+14, 2.1531418140800295250000000000e+16, -2.0288775575173015930156250000e+18, 2.1708009902623770590275000000e+20, -2.6173826968455814932120125000e+22, 3.5324148876863877826668602500e+24, -5.3042033406864906641493838981e+26, 8.8138218364311576767253114668e+28, -1.6128065107490778547354654864e+31, 3.2355470001722734208527794569e+33, -7.0876727476537493198506645215e+35, 1.6890450341293965779175629389e+38, -4.3639690731216831157655651358e+40, 1.2185998827061261322605065672e+43, -3.6670584803153006180101262324e+45, 1.1859898526302099104271449748e+48, -4.1120769493584015047981746438e+50, 1.5249042436787620309090168687e+53, -6.0349693196941307074572991901e+55, 2.5437161764210695823197691519e+58, -1.1396923802632287851130360170e+61, 5.4180861064753979196802726455e+63, -2.7283654799994373847287197104e+66, 1.4529750514918543238511171663e+69, -8.1705519371067450079777183386e+71, 4.8445781606678367790247757259e+74, -3.0246694206649519336179448018e+77, 1.9858807961690493054169047970e+80, -1.3694474620720086994386818232e+83, 9.9070382984295807826303785989e+85, -7.5103780796592645925968460677e+88, 5.9598418264260880840077992227e+91, -4.9455988887500020399263196307e+94, 4.2873596927020241277675775935e+97, -3.8791952037716162900707994047e+100, 3.6600317773156342245401829308e+103, -3.5978775704117283875784869570e+106 /* eta(-99) */ }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_hzeta_e(const double s, const double q, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s <= 1.0 || q <= 0.0) { DOMAIN_ERROR(result); } else { const double max_bits = 54.0; const double ln_term0 = -s * log(q); if(ln_term0 < GSL_LOG_DBL_MIN + 1.0) { UNDERFLOW_ERROR(result); } else if(ln_term0 > GSL_LOG_DBL_MAX - 1.0) { OVERFLOW_ERROR (result); } else if((s > max_bits && q < 1.0) || (s > 0.5*max_bits && q < 0.25)) { result->val = pow(q, -s); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(s > 0.5*max_bits && q < 1.0) { const double p1 = pow(q, -s); const double p2 = pow(q/(1.0+q), s); const double p3 = pow(q/(2.0+q), s); result->val = p1 * (1.0 + p2 + p3); result->err = GSL_DBL_EPSILON * (0.5*s + 2.0) * fabs(result->val); return GSL_SUCCESS; } else { /* Euler-Maclaurin summation formula * [Moshier, p. 400, with several typo corrections] */ const int jmax = 12; const int kmax = 10; int j, k; const double pmax = pow(kmax + q, -s); double scp = s; double pcp = pmax / (kmax + q); double ans = pmax*((kmax+q)/(s-1.0) + 0.5); for(k=0; kval = ans; result->err = 2.0 * (jmax + 1.0) * GSL_DBL_EPSILON * fabs(ans); return GSL_SUCCESS; } } } int gsl_sf_zeta_e(const double s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s == 1.0) { DOMAIN_ERROR(result); } else if(s >= 0.0) { return riemann_zeta_sgt0(s, result); } else { /* reflection formula, [Abramowitz+Stegun, 23.2.5] */ gsl_sf_result zeta_one_minus_s; const int stat_zoms = riemann_zeta1ms_slt0(s, &zeta_one_minus_s); const double sin_term = (fmod(s,2.0) == 0.0) ? 0.0 : sin(0.5*M_PI*fmod(s,4.0))/M_PI; if(sin_term == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(s > -170) { /* We have to be careful about losing digits * in calculating pow(2 Pi, s). The gamma * function is fine because we were careful * with that implementation. * We keep an array of (2 Pi)^(10 n). */ const double twopi_pow[18] = { 1.0, 9.589560061550901348e+007, 9.195966217409212684e+015, 8.818527036583869903e+023, 8.456579467173150313e+031, 8.109487671573504384e+039, 7.776641909496069036e+047, 7.457457466828644277e+055, 7.151373628461452286e+063, 6.857852693272229709e+071, 6.576379029540265771e+079, 6.306458169130020789e+087, 6.047615938853066678e+095, 5.799397627482402614e+103, 5.561367186955830005e+111, 5.333106466365131227e+119, 5.114214477385391780e+127, 4.904306689854036836e+135 }; const int n = floor((-s)/10.0); const double fs = s + 10.0*n; const double p = pow(2.0*M_PI, fs) / twopi_pow[n]; gsl_sf_result g; const int stat_g = gsl_sf_gamma_e(1.0-s, &g); result->val = p * g.val * sin_term * zeta_one_minus_s.val; result->err = fabs(p * g.val * sin_term) * zeta_one_minus_s.err; result->err += fabs(p * sin_term * zeta_one_minus_s.val) * g.err; result->err += GSL_DBL_EPSILON * (fabs(s)+2.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_g, stat_zoms); } else { /* The actual zeta function may or may not * overflow here. But we have no easy way * to calculate it when the prefactor(s) * overflow. Trying to use log's and exp * is no good because we loose a couple * digits to the exp error amplification. * When we gather a little more patience, * we can implement something here. Until * then just give up. */ OVERFLOW_ERROR(result); } } } int gsl_sf_zeta_int_e(const int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n < 0) { if(!GSL_IS_ODD(n)) { result->val = 0.0; /* exactly zero at even negative integers */ result->err = 0.0; return GSL_SUCCESS; } else if(n > -ZETA_NEG_TABLE_NMAX) { result->val = zeta_neg_int_table[-(n+1)/2]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { return gsl_sf_zeta_e((double)n, result); } } else if(n == 1){ DOMAIN_ERROR(result); } else if(n <= ZETA_POS_TABLE_NMAX){ result->val = 1.0 + zetam1_pos_int_table[n]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = 1.0; result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } } int gsl_sf_zetam1_e(const double s, gsl_sf_result * result) { if(s <= 5.0) { int stat = gsl_sf_zeta_e(s, result); result->val = result->val - 1.0; return stat; } else if(s < 15.0) { return riemann_zeta_minus_1_intermediate_s(s, result); } else { return riemann_zeta_minus1_large_s(s, result); } } int gsl_sf_zetam1_int_e(const int n, gsl_sf_result * result) { if(n < 0) { if(!GSL_IS_ODD(n)) { result->val = -1.0; /* at even negative integers zetam1 == -1 since zeta is exactly zero */ result->err = 0.0; return GSL_SUCCESS; } else if(n > -ZETA_NEG_TABLE_NMAX) { result->val = zeta_neg_int_table[-(n+1)/2] - 1.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* could use gsl_sf_zetam1_e here but subtracting 1 makes no difference for such large values, so go straight to the result */ return gsl_sf_zeta_e((double)n, result); } } else if(n == 1){ DOMAIN_ERROR(result); } else if(n <= ZETA_POS_TABLE_NMAX){ result->val = zetam1_pos_int_table[n]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { return gsl_sf_zetam1_e(n, result); } } int gsl_sf_eta_int_e(int n, gsl_sf_result * result) { if(n > ETA_POS_TABLE_NMAX) { result->val = 1.0; result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(n >= 0) { result->val = eta_pos_int_table[n]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* n < 0 */ if(!GSL_IS_ODD(n)) { /* exactly zero at even negative integers */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(n > -ETA_NEG_TABLE_NMAX) { result->val = eta_neg_int_table[-(n+1)/2]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result z; gsl_sf_result p; int stat_z = gsl_sf_zeta_int_e(n, &z); int stat_p = gsl_sf_exp_e((1.0-n)*M_LN2, &p); int stat_m = gsl_sf_multiply_e(-p.val, z.val, result); result->err = fabs(p.err * (M_LN2*(1.0-n)) * z.val) + z.err * fabs(p.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_m, stat_p, stat_z); } } } int gsl_sf_eta_e(const double s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s > 100.0) { result->val = 1.0; result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(fabs(s-1.0) < 10.0*GSL_ROOT5_DBL_EPSILON) { double del = s-1.0; double c0 = M_LN2; double c1 = M_LN2 * (M_EULER - 0.5*M_LN2); double c2 = -0.0326862962794492996; double c3 = 0.0015689917054155150; double c4 = 0.00074987242112047532; result->val = c0 + del * (c1 + del * (c2 + del * (c3 + del * c4))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result z; gsl_sf_result p; int stat_z = gsl_sf_zeta_e(s, &z); int stat_p = gsl_sf_exp_e((1.0-s)*M_LN2, &p); int stat_m = gsl_sf_multiply_e(1.0-p.val, z.val, result); result->err = fabs(p.err * (M_LN2*(1.0-s)) * z.val) + z.err * fabs(p.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_m, stat_p, stat_z); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_zeta(const double s) { EVAL_RESULT(gsl_sf_zeta_e(s, &result)); } double gsl_sf_hzeta(const double s, const double a) { EVAL_RESULT(gsl_sf_hzeta_e(s, a, &result)); } double gsl_sf_zeta_int(const int s) { EVAL_RESULT(gsl_sf_zeta_int_e(s, &result)); } double gsl_sf_zetam1(const double s) { EVAL_RESULT(gsl_sf_zetam1_e(s, &result)); } double gsl_sf_zetam1_int(const int s) { EVAL_RESULT(gsl_sf_zetam1_int_e(s, &result)); } double gsl_sf_eta_int(const int s) { EVAL_RESULT(gsl_sf_eta_int_e(s, &result)); } double gsl_sf_eta(const double s) { EVAL_RESULT(gsl_sf_eta_e(s, &result)); } sources_5316/external/gsl/gsl_randist__bernoulli.c0000664000176700017670000000255111723710247021232 0ustar paulpaul/* randist/bernoulli.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* The bernoulli distribution has the form, prob(0) = 1-p, prob(1) = p */ unsigned int gsl_ran_bernoulli (const gsl_rng * r, double p) { double u = gsl_rng_uniform (r) ; if (u < p) { return 1 ; } else { return 0 ; } } double gsl_ran_bernoulli_pdf (const unsigned int k, double p) { if (k == 0) { return 1 - p ; } else if (k == 1) { return p ; } else { return 0 ; } } sources_5316/external/gsl/gsl_block_int.h0000664000176700017670000000431311705263724017326 0ustar paulpaul/* block/gsl_block_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_INT_H__ #define __GSL_BLOCK_INT_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_int_struct { size_t size; int *data; }; typedef struct gsl_block_int_struct gsl_block_int; gsl_block_int *gsl_block_int_alloc (const size_t n); gsl_block_int *gsl_block_int_calloc (const size_t n); void gsl_block_int_free (gsl_block_int * b); int gsl_block_int_fread (FILE * stream, gsl_block_int * b); int gsl_block_int_fwrite (FILE * stream, const gsl_block_int * b); int gsl_block_int_fscanf (FILE * stream, gsl_block_int * b); int gsl_block_int_fprintf (FILE * stream, const gsl_block_int * b, const char *format); int gsl_block_int_raw_fread (FILE * stream, int * b, const size_t n, const size_t stride); int gsl_block_int_raw_fwrite (FILE * stream, const int * b, const size_t n, const size_t stride); int gsl_block_int_raw_fscanf (FILE * stream, int * b, const size_t n, const size_t stride); int gsl_block_int_raw_fprintf (FILE * stream, const int * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_int_size (const gsl_block_int * b); int * gsl_block_int_data (const gsl_block_int * b); __END_DECLS #endif /* __GSL_BLOCK_INT_H__ */ sources_5316/external/gsl/gsl_siman.h0000664000176700017670000000570611705263724016500 0ustar paulpaul/* siman/gsl_siman.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Mark Galassi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SIMAN_H__ #define __GSL_SIMAN_H__ #include #include "gsl_rng.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* types for the function pointers passed to gsl_siman_solve */ typedef double (*gsl_siman_Efunc_t) (void *xp); typedef void (*gsl_siman_step_t) (const gsl_rng *r, void *xp, double step_size); typedef double (*gsl_siman_metric_t) (void *xp, void *yp); typedef void (*gsl_siman_print_t) (void *xp); typedef void (*gsl_siman_copy_t) (void *source, void *dest); typedef void * (*gsl_siman_copy_construct_t) (void *xp); typedef void (*gsl_siman_destroy_t) (void *xp); /* this structure contains all the information needed to structure the search, beyond the energy function, the step function and the initial guess. */ typedef struct { int n_tries; /* how many points to try for each step */ int iters_fixed_T; /* how many iterations at each temperature? */ double step_size; /* max step size in the random walk */ /* the following parameters are for the Boltzmann distribution */ double k, t_initial, mu_t, t_min; } gsl_siman_params_t; /* prototype for the workhorse function */ void gsl_siman_solve(const gsl_rng * r, void *x0_p, gsl_siman_Efunc_t Ef, gsl_siman_step_t take_step, gsl_siman_metric_t distance, gsl_siman_print_t print_position, gsl_siman_copy_t copyfunc, gsl_siman_copy_construct_t copy_constructor, gsl_siman_destroy_t destructor, size_t element_size, gsl_siman_params_t params); void gsl_siman_solve_many (const gsl_rng * r, void *x0_p, gsl_siman_Efunc_t Ef, gsl_siman_step_t take_step, gsl_siman_metric_t distance, gsl_siman_print_t print_position, size_t element_size, gsl_siman_params_t params); __END_DECLS #endif /* __GSL_SIMAN_H__ */ sources_5316/external/gsl/gsl_vector__file.c0000664000176700017670000000370011723710247020011 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_block.h" #include "gsl_vector.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__file_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_specfunc__eval.h0000664000176700017670000000064011705263724020335 0ustar paulpaul/* evaluate a function discarding the status value in a modifiable way */ #define EVAL_RESULT(fn) \ gsl_sf_result result; \ int status = fn; \ if (status != GSL_SUCCESS) { \ GSL_ERROR_VAL(#fn, status, result.val); \ } ; \ return result.val; #define EVAL_DOUBLE(fn) \ int status = fn; \ if (status != GSL_SUCCESS) { \ GSL_ERROR_VAL(#fn, status, result); \ } ; \ return result; sources_5316/external/gsl/gsl_cblas__source_geru.h0000664000176700017670000000445711705263724021220 0ustar paulpaul/* blas/source_geru.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); if (order == CblasRowMajor) { INDEX ix = OFFSET(M, incX); for (i = 0; i < M; i++) { const BASE X_real = CONST_REAL(X, ix); const BASE X_imag = CONST_IMAG(X, ix); const BASE tmp_real = alpha_real * X_real - alpha_imag * X_imag; const BASE tmp_imag = alpha_imag * X_real + alpha_real * X_imag; INDEX jy = OFFSET(N, incY); for (j = 0; j < N; j++) { const BASE Y_real = CONST_REAL(Y, jy); const BASE Y_imag = CONST_IMAG(Y, jy); REAL(A, lda * i + j) += Y_real * tmp_real - Y_imag * tmp_imag; IMAG(A, lda * i + j) += Y_imag * tmp_real + Y_real * tmp_imag; jy += incY; } ix += incX; } } else if (order == CblasColMajor) { INDEX jy = OFFSET(N, incY); for (j = 0; j < N; j++) { const BASE Y_real = CONST_REAL(Y, jy); const BASE Y_imag = CONST_IMAG(Y, jy); const BASE tmp_real = alpha_real * Y_real - alpha_imag * Y_imag; const BASE tmp_imag = alpha_imag * Y_real + alpha_real * Y_imag; INDEX ix = OFFSET(M, incX); for (i = 0; i < M; i++) { const BASE X_real = CONST_REAL(X, ix); const BASE X_imag = CONST_IMAG(X, ix); REAL(A, i + lda * j) += X_real * tmp_real - X_imag * tmp_imag; IMAG(A, i + lda * j) += X_imag * tmp_real + X_real * tmp_imag; ix += incX; } jy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_eigen__genhermv.c0000664000176700017670000001240311723710247020472 0ustar paulpaul/* eigen/genhermv.c * * Copyright (C) 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include "gsl__config.h" #include "gsl_eigen.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_blas.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_complex.h" #include "gsl_complex_math.h" /* * This module computes the eigenvalues and eigenvectors of a complex * generalized hermitian-definite eigensystem A x = \lambda B x, where * A and B are hermitian, and B is positive-definite. */ static void genhermv_normalize_eigenvectors(gsl_matrix_complex *evec); /* gsl_eigen_genhermv_alloc() Allocate a workspace for solving the generalized hermitian-definite eigenvalue problem. The size of this workspace is O(5n). Inputs: n - size of matrices Return: pointer to workspace */ gsl_eigen_genhermv_workspace * gsl_eigen_genhermv_alloc(const size_t n) { gsl_eigen_genhermv_workspace *w; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = calloc (1, sizeof (gsl_eigen_genhermv_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->size = n; w->hermv_workspace_p = gsl_eigen_hermv_alloc(n); if (!w->hermv_workspace_p) { gsl_eigen_genhermv_free(w); GSL_ERROR_NULL("failed to allocate space for hermv workspace", GSL_ENOMEM); } return (w); } /* gsl_eigen_genhermv_alloc() */ /* gsl_eigen_genhermv_free() Free workspace w */ void gsl_eigen_genhermv_free (gsl_eigen_genhermv_workspace * w) { if (w->hermv_workspace_p) gsl_eigen_hermv_free(w->hermv_workspace_p); free(w); } /* gsl_eigen_genhermv_free() */ /* gsl_eigen_genhermv() Solve the generalized hermitian-definite eigenvalue problem A x = \lambda B x for the eigenvalues \lambda and eigenvectors x. Inputs: A - complex hermitian matrix B - complex hermitian and positive definite matrix eval - where to store eigenvalues evec - where to store eigenvectors w - workspace Return: success or error */ int gsl_eigen_genhermv (gsl_matrix_complex * A, gsl_matrix_complex * B, gsl_vector * eval, gsl_matrix_complex * evec, gsl_eigen_genhermv_workspace * w) { const size_t N = A->size1; /* check matrix and vector sizes */ if (N != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if ((N != B->size1) || (N != B->size2)) { GSL_ERROR ("B matrix dimensions must match A", GSL_EBADLEN); } else if (eval->size != N) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (evec->size1 != evec->size2) { GSL_ERROR ("eigenvector matrix must be square", GSL_ENOTSQR); } else if (evec->size1 != N) { GSL_ERROR ("eigenvector matrix has wrong size", GSL_EBADLEN); } else if (w->size != N) { GSL_ERROR ("matrix size does not match workspace", GSL_EBADLEN); } else { int s; /* compute Cholesky factorization of B */ s = gsl_linalg_complex_cholesky_decomp(B); if (s != GSL_SUCCESS) return s; /* B is not positive definite */ /* transform to standard hermitian eigenvalue problem */ gsl_eigen_genherm_standardize(A, B); /* compute eigenvalues and eigenvectors */ s = gsl_eigen_hermv(A, eval, evec, w->hermv_workspace_p); if (s != GSL_SUCCESS) return s; /* backtransform eigenvectors: evec -> L^{-H} evec */ gsl_blas_ztrsm(CblasLeft, CblasLower, CblasConjTrans, CblasNonUnit, GSL_COMPLEX_ONE, B, evec); /* the blas call destroyed the normalization - renormalize */ genhermv_normalize_eigenvectors(evec); return GSL_SUCCESS; } } /* gsl_eigen_genhermv() */ /******************************************** * INTERNAL ROUTINES * ********************************************/ /* genhermv_normalize_eigenvectors() Normalize eigenvectors so that their Euclidean norm is 1 Inputs: evec - eigenvectors */ static void genhermv_normalize_eigenvectors(gsl_matrix_complex *evec) { const size_t N = evec->size1; size_t i; /* looping */ for (i = 0; i < N; ++i) { gsl_vector_complex_view vi = gsl_matrix_complex_column(evec, i); double scale = 1.0 / gsl_blas_dznrm2(&vi.vector); gsl_blas_zdscal(scale, &vi.vector); } } /* genhermv_normalize_eigenvectors() */ sources_5316/external/gsl/gsl_sf__eval.h0000644000176700017670000000064010707442037017132 0ustar paulpaul/* evaluate a function discarding the status value in a modifiable way */ #define EVAL_RESULT(fn) \ gsl_sf_result result; \ int status = fn; \ if (status != GSL_SUCCESS) { \ GSL_ERROR_VAL(#fn, status, result.val); \ } ; \ return result.val; #define EVAL_DOUBLE(fn) \ int status = fn; \ if (status != GSL_SUCCESS) { \ GSL_ERROR_VAL(#fn, status, result); \ } ; \ return result; sources_5316/external/gsl/gsl_monte_vegas.h0000664000176700017670000000512611705263724017674 0ustar paulpaul/* monte/gsl_monte_vegas.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Michael Booth * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* header for the gsl "vegas" routines. Mike Booth, May 1998 */ #ifndef __GSL_MONTE_VEGAS_H__ #define __GSL_MONTE_VEGAS_H__ #include "gsl_rng.h" #include "gsl_monte.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS enum {GSL_VEGAS_MODE_IMPORTANCE = 1, GSL_VEGAS_MODE_IMPORTANCE_ONLY = 0, GSL_VEGAS_MODE_STRATIFIED = -1}; typedef struct { /* grid */ size_t dim; size_t bins_max; unsigned int bins; unsigned int boxes; /* these are both counted along the axes */ double * xi; double * xin; double * delx; double * weight; double vol; double * x; int * bin; int * box; /* distribution */ double * d; /* control variables */ double alpha; int mode; int verbose; unsigned int iterations; int stage; /* scratch variables preserved between calls to vegas1/2/3 */ double jac; double wtd_int_sum; double sum_wgts; double chi_sum; double chisq; double result; double sigma; unsigned int it_start; unsigned int it_num; unsigned int samples; unsigned int calls_per_box; FILE * ostream; } gsl_monte_vegas_state; int gsl_monte_vegas_integrate(gsl_monte_function * f, double xl[], double xu[], size_t dim, size_t calls, gsl_rng * r, gsl_monte_vegas_state *state, double* result, double* abserr); gsl_monte_vegas_state* gsl_monte_vegas_alloc(size_t dim); int gsl_monte_vegas_init(gsl_monte_vegas_state* state); void gsl_monte_vegas_free (gsl_monte_vegas_state* state); __END_DECLS #endif /* __GSL_MONTE_VEGAS_H__ */ sources_5316/external/gsl/gsl_sf__bessel_Ynu.c0000644000176700017670000000654610707442037020321 0ustar paulpaul/* specfunc/bessel_Ynu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_olver.h" #include "gsl_sf__bessel_temme.h" /* Perform forward recurrence for Y_nu(x) and Y'_nu(x) * * Y_{nu+1} = nu/x Y_nu - Y'_nu * Y'_{nu+1} = -(nu+1)/x Y_{nu+1} + Y_nu */ #if 0 static int bessel_Y_recur(const double nu_min, const double x, const int kmax, const double Y_start, const double Yp_start, double * Y_end, double * Yp_end) { double x_inv = 1.0/x; double nu = nu_min; double Y_nu = Y_start; double Yp_nu = Yp_start; int k; for(k=1; k<=kmax; k++) { double nuox = nu*x_inv; double Y_nu_save = Y_nu; Y_nu = -Yp_nu + nuox * Y_nu; Yp_nu = Y_nu_save - (nuox+x_inv) * Y_nu; nu += 1.0; } *Y_end = Y_nu; *Yp_end = Yp_nu; return GSL_SUCCESS; } #endif /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Ynu_e(double nu, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else if(nu > 50.0) { return gsl_sf_bessel_Ynu_asymp_Olver_e(nu, x, result); } else { /* -1/2 <= mu <= 1/2 */ int N = (int)(nu + 0.5); double mu = nu - N; gsl_sf_result Y_mu, Y_mup1; int stat_mu; double Ynm1; double Yn; double Ynp1; int n; if(x < 2.0) { /* Determine Ymu, Ymup1 directly. This is really * an optimization since this case could as well * be handled by a call to gsl_sf_bessel_JY_mu_restricted(), * as below. */ stat_mu = gsl_sf_bessel_Y_temme(mu, x, &Y_mu, &Y_mup1); } else { /* Determine Ymu, Ymup1 and Jmu, Jmup1. */ gsl_sf_result J_mu, J_mup1; stat_mu = gsl_sf_bessel_JY_mu_restricted(mu, x, &J_mu, &J_mup1, &Y_mu, &Y_mup1); } /* Forward recursion to get Ynu, Ynup1. */ Ynm1 = Y_mu.val; Yn = Y_mup1.val; for(n=1; n<=N; n++) { Ynp1 = 2.0*(mu+n)/x * Yn - Ynm1; Ynm1 = Yn; Yn = Ynp1; } result->val = Ynm1; /* Y_nu */ result->err = (N + 1.0) * fabs(Ynm1) * (fabs(Y_mu.err/Y_mu.val) + fabs(Y_mup1.err/Y_mup1.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Ynm1); return stat_mu; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_Ynu(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_Ynu_e(nu, x, &result)); } sources_5316/external/gsl/gsl_specfunc__bessel_In.c0000664000176700017670000001447311723710247021312 0ustar paulpaul/* specfunc/bessel_In.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_In_scaled_e(int n, const double x, gsl_sf_result * result) { const double ax = fabs(x); n = abs(n); /* I(-n, z) = I(n, z) */ /* CHECK_POINTER(result) */ if(n == 0) { return gsl_sf_bessel_I0_scaled_e(x, result); } else if(n == 1) { return gsl_sf_bessel_I1_scaled_e(x, result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x*x < 10.0*(n+1.0)/M_E) { gsl_sf_result t; double ex = exp(-ax); int stat_In = gsl_sf_bessel_IJ_taylor_e((double)n, ax, 1, 50, GSL_DBL_EPSILON, &t); result->val = t.val * ex; result->err = t.err * ex; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return stat_In; } else if(n < 150 && ax < 1e7) { gsl_sf_result I0_scaled; int stat_I0 = gsl_sf_bessel_I0_scaled_e(ax, &I0_scaled); double rat; int stat_CF1 = gsl_sf_bessel_I_CF1_ser((double)n, ax, &rat); double Ikp1 = rat * GSL_SQRT_DBL_MIN; double Ik = GSL_SQRT_DBL_MIN; double Ikm1; int k; for(k=n; k >= 1; k--) { Ikm1 = Ikp1 + 2.0*k/ax * Ik; Ikp1 = Ik; Ik = Ikm1; } result->val = I0_scaled.val * (GSL_SQRT_DBL_MIN / Ik); result->err = I0_scaled.err * (GSL_SQRT_DBL_MIN / Ik); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return GSL_ERROR_SELECT_2(stat_I0, stat_CF1); } else if( GSL_MIN( 0.29/(n*n), 0.5/(n*n + x*x) ) < 0.5*GSL_ROOT3_DBL_EPSILON) { int stat_as = gsl_sf_bessel_Inu_scaled_asymp_unif_e((double)n, ax, result); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return stat_as; } else { const int nhi = 2 + (int) (1.2 / GSL_ROOT6_DBL_EPSILON); gsl_sf_result r_Ikp1; gsl_sf_result r_Ik; int stat_a1 = gsl_sf_bessel_Inu_scaled_asymp_unif_e(nhi+1.0, ax, &r_Ikp1); int stat_a2 = gsl_sf_bessel_Inu_scaled_asymp_unif_e((double)nhi, ax, &r_Ik); double Ikp1 = r_Ikp1.val; double Ik = r_Ik.val; double Ikm1; int k; for(k=nhi; k > n; k--) { Ikm1 = Ikp1 + 2.0*k/ax * Ik; Ikp1 = Ik; Ik = Ikm1; } result->val = Ik; result->err = Ik * (r_Ikp1.err/r_Ikp1.val + r_Ik.err/r_Ik.val); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return GSL_ERROR_SELECT_2(stat_a1, stat_a2); } } int gsl_sf_bessel_In_scaled_array(const int nmin, const int nmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(nmax < nmin || nmin < 0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; GSL_ERROR ("domain error", GSL_EDOM); } else if(x == 0.0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; if(nmin == 0) result_array[0] = 1.0; return GSL_SUCCESS; } else if(nmax == 0) { gsl_sf_result I0_scaled; int stat = gsl_sf_bessel_I0_scaled_e(x, &I0_scaled); result_array[0] = I0_scaled.val; return stat; } else { const double ax = fabs(x); const double two_over_x = 2.0/ax; /* starting values */ gsl_sf_result r_Inp1; gsl_sf_result r_In; int stat_0 = gsl_sf_bessel_In_scaled_e(nmax+1, ax, &r_Inp1); int stat_1 = gsl_sf_bessel_In_scaled_e(nmax, ax, &r_In); double Inp1 = r_Inp1.val; double In = r_In.val; double Inm1; int n; for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = In; Inm1 = Inp1 + n * two_over_x * In; Inp1 = In; In = Inm1; } /* deal with signs */ if(x < 0.0) { for(n=nmin; n<=nmax; n++) { if(GSL_IS_ODD(n)) result_array[n-nmin] = -result_array[n-nmin]; } } return GSL_ERROR_SELECT_2(stat_0, stat_1); } } int gsl_sf_bessel_In_e(const int n_in, const double x, gsl_sf_result * result) { const double ax = fabs(x); const int n = abs(n_in); /* I(-n, z) = I(n, z) */ gsl_sf_result In_scaled; const int stat_In_scaled = gsl_sf_bessel_In_scaled_e(n, ax, &In_scaled); /* In_scaled is always less than 1, * so this overflow check is conservative. */ if(ax > GSL_LOG_DBL_MAX - 1.0) { OVERFLOW_ERROR(result); } else { const double ex = exp(ax); result->val = ex * In_scaled.val; result->err = ex * In_scaled.err; result->err += ax * GSL_DBL_EPSILON * fabs(result->val); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return stat_In_scaled; } } int gsl_sf_bessel_In_array(const int nmin, const int nmax, const double x, double * result_array) { double ax = fabs(x); /* CHECK_POINTER(result_array) */ if(ax > GSL_LOG_DBL_MAX - 1.0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; /* FIXME: should be Inf */ GSL_ERROR ("overflow", GSL_EOVRFLW); } else { int j; double eax = exp(ax); int status = gsl_sf_bessel_In_scaled_array(nmin, nmax, x, result_array); for(j=0; j<=nmax-nmin; j++) result_array[j] *= eax; return status; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_In_scaled(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_In_scaled_e(n, x, &result)); } double gsl_sf_bessel_In(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_In_e(n, x, &result)); } sources_5316/external/gsl/gsl_block_float.h0000664000176700017670000000442111705263724017641 0ustar paulpaul/* block/gsl_block_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_FLOAT_H__ #define __GSL_BLOCK_FLOAT_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_float_struct { size_t size; float *data; }; typedef struct gsl_block_float_struct gsl_block_float; gsl_block_float *gsl_block_float_alloc (const size_t n); gsl_block_float *gsl_block_float_calloc (const size_t n); void gsl_block_float_free (gsl_block_float * b); int gsl_block_float_fread (FILE * stream, gsl_block_float * b); int gsl_block_float_fwrite (FILE * stream, const gsl_block_float * b); int gsl_block_float_fscanf (FILE * stream, gsl_block_float * b); int gsl_block_float_fprintf (FILE * stream, const gsl_block_float * b, const char *format); int gsl_block_float_raw_fread (FILE * stream, float * b, const size_t n, const size_t stride); int gsl_block_float_raw_fwrite (FILE * stream, const float * b, const size_t n, const size_t stride); int gsl_block_float_raw_fscanf (FILE * stream, float * b, const size_t n, const size_t stride); int gsl_block_float_raw_fprintf (FILE * stream, const float * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_float_size (const gsl_block_float * b); float * gsl_block_float_data (const gsl_block_float * b); __END_DECLS #endif /* __GSL_BLOCK_FLOAT_H__ */ sources_5316/external/gsl/gsl_cblas__zher.c0000664000176700017670000000051611723710247017626 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zher (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const void *X, const int incX, void *A, const int lda) { #define BASE double #include "gsl_cblas__source_her.h" #undef BASE } sources_5316/external/gsl/gsl_linalg__bidiag.c0000664000176700017670000002361711723710247020266 0ustar paulpaul/* linalg/bidiag.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Factorise a matrix A into * * A = U B V^T * * where U and V are orthogonal and B is upper bidiagonal. * * On exit, B is stored in the diagonal and first superdiagonal of A. * * U is stored as a packed set of Householder transformations in the * lower triangular part of the input matrix below the diagonal. * * V is stored as a packed set of Householder transformations in the * upper triangular part of the input matrix above the first * superdiagonal. * * The full matrix for U can be obtained as the product * * U = U_1 U_2 .. U_N * * where * * U_i = (I - tau_i * u_i * u_i') * * and where u_i is a Householder vector * * u_i = [0, .. , 0, 1, A(i+1,i), A(i+3,i), .. , A(M,i)] * * The full matrix for V can be obtained as the product * * V = V_1 V_2 .. V_(N-2) * * where * * V_i = (I - tau_i * v_i * v_i') * * and where v_i is a Householder vector * * v_i = [0, .. , 0, 1, A(i,i+2), A(i,i+3), .. , A(i,N)] * * See Golub & Van Loan, "Matrix Computations" (3rd ed), Algorithm 5.4.2 * * Note: this description uses 1-based indices. The code below uses * 0-based indices */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_linalg.h" int gsl_linalg_bidiag_decomp (gsl_matrix * A, gsl_vector * tau_U, gsl_vector * tau_V) { if (A->size1 < A->size2) { GSL_ERROR ("bidiagonal decomposition requires M>=N", GSL_EBADLEN); } else if (tau_U->size != A->size2) { GSL_ERROR ("size of tau_U must be N", GSL_EBADLEN); } else if (tau_V->size + 1 != A->size2) { GSL_ERROR ("size of tau_V must be (N - 1)", GSL_EBADLEN); } else { const size_t M = A->size1; const size_t N = A->size2; size_t i; for (i = 0 ; i < N; i++) { /* Apply Householder transformation to current column */ { gsl_vector_view c = gsl_matrix_column (A, i); gsl_vector_view v = gsl_vector_subvector (&c.vector, i, M - i); double tau_i = gsl_linalg_householder_transform (&v.vector); /* Apply the transformation to the remaining columns */ if (i + 1 < N) { gsl_matrix_view m = gsl_matrix_submatrix (A, i, i + 1, M - i, N - (i + 1)); gsl_linalg_householder_hm (tau_i, &v.vector, &m.matrix); } gsl_vector_set (tau_U, i, tau_i); } /* Apply Householder transformation to current row */ if (i + 1 < N) { gsl_vector_view r = gsl_matrix_row (A, i); gsl_vector_view v = gsl_vector_subvector (&r.vector, i + 1, N - (i + 1)); double tau_i = gsl_linalg_householder_transform (&v.vector); /* Apply the transformation to the remaining rows */ if (i + 1 < M) { gsl_matrix_view m = gsl_matrix_submatrix (A, i+1, i+1, M - (i+1), N - (i+1)); gsl_linalg_householder_mh (tau_i, &v.vector, &m.matrix); } gsl_vector_set (tau_V, i, tau_i); } } } return GSL_SUCCESS; } /* Form the orthogonal matrices U, V, diagonal d and superdiagonal sd from the packed bidiagonal matrix A */ int gsl_linalg_bidiag_unpack (const gsl_matrix * A, const gsl_vector * tau_U, gsl_matrix * U, const gsl_vector * tau_V, gsl_matrix * V, gsl_vector * diag, gsl_vector * superdiag) { const size_t M = A->size1; const size_t N = A->size2; const size_t K = GSL_MIN(M, N); if (M < N) { GSL_ERROR ("matrix A must have M >= N", GSL_EBADLEN); } else if (tau_U->size != K) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (tau_V->size + 1 != K) { GSL_ERROR ("size of tau must be MIN(M,N) - 1", GSL_EBADLEN); } else if (U->size1 != M || U->size2 != N) { GSL_ERROR ("size of U must be M x N", GSL_EBADLEN); } else if (V->size1 != N || V->size2 != N) { GSL_ERROR ("size of V must be N x N", GSL_EBADLEN); } else if (diag->size != K) { GSL_ERROR ("size of diagonal must match size of A", GSL_EBADLEN); } else if (superdiag->size + 1 != K) { GSL_ERROR ("size of subdiagonal must be (diagonal size - 1)", GSL_EBADLEN); } else { size_t i, j; /* Copy diagonal into diag */ for (i = 0; i < N; i++) { double Aii = gsl_matrix_get (A, i, i); gsl_vector_set (diag, i, Aii); } /* Copy superdiagonal into superdiag */ for (i = 0; i < N - 1; i++) { double Aij = gsl_matrix_get (A, i, i+1); gsl_vector_set (superdiag, i, Aij); } /* Initialize V to the identity */ gsl_matrix_set_identity (V); for (i = N - 1; i > 0 && i--;) { /* Householder row transformation to accumulate V */ gsl_vector_const_view r = gsl_matrix_const_row (A, i); gsl_vector_const_view h = gsl_vector_const_subvector (&r.vector, i + 1, N - (i+1)); double ti = gsl_vector_get (tau_V, i); gsl_matrix_view m = gsl_matrix_submatrix (V, i + 1, i + 1, N-(i+1), N-(i+1)); gsl_linalg_householder_hm (ti, &h.vector, &m.matrix); } /* Initialize U to the identity */ gsl_matrix_set_identity (U); for (j = N; j > 0 && j--;) { /* Householder column transformation to accumulate U */ gsl_vector_const_view c = gsl_matrix_const_column (A, j); gsl_vector_const_view h = gsl_vector_const_subvector (&c.vector, j, M - j); double tj = gsl_vector_get (tau_U, j); gsl_matrix_view m = gsl_matrix_submatrix (U, j, j, M-j, N-j); gsl_linalg_householder_hm (tj, &h.vector, &m.matrix); } return GSL_SUCCESS; } } int gsl_linalg_bidiag_unpack2 (gsl_matrix * A, gsl_vector * tau_U, gsl_vector * tau_V, gsl_matrix * V) { const size_t M = A->size1; const size_t N = A->size2; const size_t K = GSL_MIN(M, N); if (M < N) { GSL_ERROR ("matrix A must have M >= N", GSL_EBADLEN); } else if (tau_U->size != K) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (tau_V->size + 1 != K) { GSL_ERROR ("size of tau must be MIN(M,N) - 1", GSL_EBADLEN); } else if (V->size1 != N || V->size2 != N) { GSL_ERROR ("size of V must be N x N", GSL_EBADLEN); } else { size_t i, j; /* Initialize V to the identity */ gsl_matrix_set_identity (V); for (i = N - 1; i > 0 && i--;) { /* Householder row transformation to accumulate V */ gsl_vector_const_view r = gsl_matrix_const_row (A, i); gsl_vector_const_view h = gsl_vector_const_subvector (&r.vector, i + 1, N - (i+1)); double ti = gsl_vector_get (tau_V, i); gsl_matrix_view m = gsl_matrix_submatrix (V, i + 1, i + 1, N-(i+1), N-(i+1)); gsl_linalg_householder_hm (ti, &h.vector, &m.matrix); } /* Copy superdiagonal into tau_v */ for (i = 0; i < N - 1; i++) { double Aij = gsl_matrix_get (A, i, i+1); gsl_vector_set (tau_V, i, Aij); } /* Allow U to be unpacked into the same memory as A, copy diagonal into tau_U */ for (j = N; j > 0 && j--;) { /* Householder column transformation to accumulate U */ double tj = gsl_vector_get (tau_U, j); double Ajj = gsl_matrix_get (A, j, j); gsl_matrix_view m = gsl_matrix_submatrix (A, j, j, M-j, N-j); gsl_vector_set (tau_U, j, Ajj); gsl_linalg_householder_hm1 (tj, &m.matrix); } return GSL_SUCCESS; } } int gsl_linalg_bidiag_unpack_B (const gsl_matrix * A, gsl_vector * diag, gsl_vector * superdiag) { const size_t M = A->size1; const size_t N = A->size2; const size_t K = GSL_MIN(M, N); if (diag->size != K) { GSL_ERROR ("size of diagonal must match size of A", GSL_EBADLEN); } else if (superdiag->size + 1 != K) { GSL_ERROR ("size of subdiagonal must be (matrix size - 1)", GSL_EBADLEN); } else { size_t i; /* Copy diagonal into diag */ for (i = 0; i < K; i++) { double Aii = gsl_matrix_get (A, i, i); gsl_vector_set (diag, i, Aii); } /* Copy superdiagonal into superdiag */ for (i = 0; i < K - 1; i++) { double Aij = gsl_matrix_get (A, i, i+1); gsl_vector_set (superdiag, i, Aij); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_vector__subvector.c0000664000176700017670000000767311723710247021123 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_vector.h" #include "gsl_vector__view.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_CHAR #define USE_QUALIFIER #define QUALIFIER const #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__subvector_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_cblas__source_syr2k_r.h0000664000176700017670000000641211705263724021642 0ustar paulpaul/* blas/source_syr2k_r.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; int uplo, trans; if (alpha == 0.0 && beta == 1.0) return; if (Order == CblasRowMajor) { uplo = Uplo; trans = (Trans == CblasConjTrans) ? CblasTrans : Trans; } else { uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; if (Trans == CblasTrans || Trans == CblasConjTrans) { trans = CblasNoTrans; } else { trans = CblasTrans; } } /* form C := beta*C */ if (beta == 0.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { C[ldc * i + j] = 0.0; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { C[ldc * i + j] = 0.0; } } } } else if (beta != 1.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { C[ldc * i + j] *= beta; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { C[ldc * i + j] *= beta; } } } } if (alpha == 0.0) return; if (uplo == CblasUpper && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { BASE temp = 0.0; for (k = 0; k < K; k++) { temp += (A[i * lda + k] * B[j * ldb + k] + B[i * ldb + k] * A[j * lda + k]); } C[i * ldc + j] += alpha * temp; } } } else if (uplo == CblasUpper && trans == CblasTrans) { for (k = 0; k < K; k++) { for (i = 0; i < N; i++) { BASE temp1 = alpha * A[k * lda + i]; BASE temp2 = alpha * B[k * ldb + i]; for (j = i; j < N; j++) { C[i * lda + j] += temp1 * B[k * ldb + j] + temp2 * A[k * lda + j]; } } } } else if (uplo == CblasLower && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { BASE temp = 0.0; for (k = 0; k < K; k++) { temp += (A[i * lda + k] * B[j * ldb + k] + B[i * ldb + k] * A[j * lda + k]); } C[i * ldc + j] += alpha * temp; } } } else if (uplo == CblasLower && trans == CblasTrans) { for (k = 0; k < K; k++) { for (i = 0; i < N; i++) { BASE temp1 = alpha * A[k * lda + i]; BASE temp2 = alpha * B[k * ldb + i]; for (j = 0; j <= i; j++) { C[i * lda + j] += temp1 * B[k * ldb + j] + temp2 * A[k * lda + j]; } } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_multiroots__hybridj.c0000664000176700017670000003350211723710247021447 0ustar paulpaul/* multiroots/hybridj.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multiroots.h" #include "gsl_linalg.h" #include "gsl_multiroots__dogleg.c" typedef struct { size_t iter; size_t ncfail; size_t ncsuc; size_t nslow1; size_t nslow2; double fnorm; double delta; gsl_matrix *q; gsl_matrix *r; gsl_vector *tau; gsl_vector *diag; gsl_vector *qtf; gsl_vector *newton; gsl_vector *gradient; gsl_vector *x_trial; gsl_vector *f_trial; gsl_vector *df; gsl_vector *qtdf; gsl_vector *rdx; gsl_vector *w; gsl_vector *v; } hybridj_state_t; static int hybridj_alloc (void *vstate, size_t n); static int hybridj_set (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static int hybridsj_set (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static int set (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx, int scale); static int hybridj_iterate (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static void hybridj_free (void *vstate); static int iterate (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx, int scale); static int hybridj_alloc (void *vstate, size_t n) { hybridj_state_t *state = (hybridj_state_t *) vstate; gsl_matrix *q, *r; gsl_vector *tau, *diag, *qtf, *newton, *gradient, *x_trial, *f_trial, *df, *qtdf, *rdx, *w, *v; q = gsl_matrix_calloc (n, n); if (q == 0) { GSL_ERROR ("failed to allocate space for q", GSL_ENOMEM); } state->q = q; r = gsl_matrix_calloc (n, n); if (r == 0) { gsl_matrix_free (q); GSL_ERROR ("failed to allocate space for r", GSL_ENOMEM); } state->r = r; tau = gsl_vector_calloc (n); if (tau == 0) { gsl_matrix_free (q); gsl_matrix_free (r); GSL_ERROR ("failed to allocate space for tau", GSL_ENOMEM); } state->tau = tau; diag = gsl_vector_calloc (n); if (diag == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); GSL_ERROR ("failed to allocate space for diag", GSL_ENOMEM); } state->diag = diag; qtf = gsl_vector_calloc (n); if (qtf == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); GSL_ERROR ("failed to allocate space for qtf", GSL_ENOMEM); } state->qtf = qtf; newton = gsl_vector_calloc (n); if (newton == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); GSL_ERROR ("failed to allocate space for newton", GSL_ENOMEM); } state->newton = newton; gradient = gsl_vector_calloc (n); if (gradient == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); GSL_ERROR ("failed to allocate space for gradient", GSL_ENOMEM); } state->gradient = gradient; x_trial = gsl_vector_calloc (n); if (x_trial == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); GSL_ERROR ("failed to allocate space for x_trial", GSL_ENOMEM); } state->x_trial = x_trial; f_trial = gsl_vector_calloc (n); if (f_trial == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); GSL_ERROR ("failed to allocate space for f_trial", GSL_ENOMEM); } state->f_trial = f_trial; df = gsl_vector_calloc (n); if (df == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); GSL_ERROR ("failed to allocate space for df", GSL_ENOMEM); } state->df = df; qtdf = gsl_vector_calloc (n); if (qtdf == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); GSL_ERROR ("failed to allocate space for qtdf", GSL_ENOMEM); } state->qtdf = qtdf; rdx = gsl_vector_calloc (n); if (rdx == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (qtdf); GSL_ERROR ("failed to allocate space for rdx", GSL_ENOMEM); } state->rdx = rdx; w = gsl_vector_calloc (n); if (w == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (qtdf); gsl_vector_free (rdx); GSL_ERROR ("failed to allocate space for w", GSL_ENOMEM); } state->w = w; v = gsl_vector_calloc (n); if (v == 0) { gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (qtdf); gsl_vector_free (rdx); gsl_vector_free (w); GSL_ERROR ("failed to allocate space for v", GSL_ENOMEM); } state->v = v; return GSL_SUCCESS; } static int hybridj_set (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { int status = set (vstate, fdf, x, f, J, dx, 0); return status ; } static int hybridsj_set (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { int status = set (vstate, fdf, x, f, J, dx, 1); return status ; } static int set (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx, int scale) { hybridj_state_t *state = (hybridj_state_t *) vstate; gsl_matrix *q = state->q; gsl_matrix *r = state->r; gsl_vector *tau = state->tau; gsl_vector *diag = state->diag; GSL_MULTIROOT_FN_EVAL_F_DF (fdf, x, f, J); state->iter = 1; state->fnorm = enorm (f); state->ncfail = 0; state->ncsuc = 0; state->nslow1 = 0; state->nslow2 = 0; gsl_vector_set_all (dx, 0.0); /* Store column norms in diag */ if (scale) compute_diag (J, diag); else gsl_vector_set_all (diag, 1.0); /* Set delta to factor |D x| or to factor if |D x| is zero */ state->delta = compute_delta (diag, x); /* Factorize J into QR decomposition */ gsl_linalg_QR_decomp (J, tau); gsl_linalg_QR_unpack (J, tau, q, r); return GSL_SUCCESS; } static int hybridj_iterate (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { int status = iterate (vstate, fdf, x, f, J, dx, 0); return status; } static int hybridsj_iterate (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { int status = iterate (vstate, fdf, x, f, J, dx, 1); return status; } static int iterate (void *vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx, int scale) { hybridj_state_t *state = (hybridj_state_t *) vstate; const double fnorm = state->fnorm; gsl_matrix *q = state->q; gsl_matrix *r = state->r; gsl_vector *tau = state->tau; gsl_vector *diag = state->diag; gsl_vector *qtf = state->qtf; gsl_vector *x_trial = state->x_trial; gsl_vector *f_trial = state->f_trial; gsl_vector *df = state->df; gsl_vector *qtdf = state->qtdf; gsl_vector *rdx = state->rdx; gsl_vector *w = state->w; gsl_vector *v = state->v; double prered, actred; double pnorm, fnorm1, fnorm1p; double ratio; double p1 = 0.1, p5 = 0.5, p001 = 0.001, p0001 = 0.0001; /* Compute qtf = Q^T f */ compute_qtf (q, f, qtf); /* Compute dogleg step */ dogleg (r, qtf, diag, state->delta, state->newton, state->gradient, dx); /* Take a trial step */ compute_trial_step (x, dx, state->x_trial); pnorm = scaled_enorm (diag, dx); if (state->iter == 1) { if (pnorm < state->delta) { state->delta = pnorm; } } /* Evaluate function at x + p */ { int status = GSL_MULTIROOT_FN_EVAL_F (fdf, x_trial, f_trial); if (status != GSL_SUCCESS) { return GSL_EBADFUNC; } } /* Set df = f_trial - f */ compute_df (f_trial, f, df); /* Compute the scaled actual reduction */ fnorm1 = enorm (f_trial); actred = compute_actual_reduction (fnorm, fnorm1); /* Compute rdx = R dx */ compute_rdx (r, dx, rdx); /* Compute the scaled predicted reduction phi1p = |Q^T f + R dx| */ fnorm1p = enorm_sum (qtf, rdx); prered = compute_predicted_reduction (fnorm, fnorm1p); /* Compute the ratio of the actual to predicted reduction */ if (prered > 0) { ratio = actred / prered; } else { ratio = 0; } /* Update the step bound */ if (ratio < p1) { state->ncsuc = 0; state->ncfail++; state->delta *= p5; } else { state->ncfail = 0; state->ncsuc++; if (ratio >= p5 || state->ncsuc > 1) state->delta = GSL_MAX (state->delta, pnorm / p5); if (fabs (ratio - 1) <= p1) state->delta = pnorm / p5; } /* Test for successful iteration */ if (ratio >= p0001) { gsl_vector_memcpy (x, x_trial); gsl_vector_memcpy (f, f_trial); state->fnorm = fnorm1; state->iter++; } /* Determine the progress of the iteration */ state->nslow1++; if (actred >= p001) state->nslow1 = 0; if (actred >= p1) state->nslow2 = 0; if (state->ncfail == 2) { { int status = GSL_MULTIROOT_FN_EVAL_DF (fdf, x, J); if (status != GSL_SUCCESS) { return GSL_EBADFUNC; } } state->nslow2++; if (state->iter == 1) { if (scale) compute_diag (J, diag); state->delta = compute_delta (diag, x); } else { if (scale) update_diag (J, diag); } /* Factorize J into QR decomposition */ gsl_linalg_QR_decomp (J, tau); gsl_linalg_QR_unpack (J, tau, q, r); return GSL_SUCCESS; } /* Compute qtdf = Q^T df, w = (Q^T df - R dx)/|dx|, v = D^2 dx/|dx| */ compute_qtf (q, df, qtdf); compute_wv (qtdf, rdx, dx, diag, pnorm, w, v); /* Rank-1 update of the jacobian Q'R' = Q(R + w v^T) */ gsl_linalg_QR_update (q, r, w, v); /* No progress as measured by jacobian evaluations */ if (state->nslow2 == 5) { return GSL_ENOPROGJ; } /* No progress as measured by function evaluations */ if (state->nslow1 == 10) { return GSL_ENOPROG; } return GSL_SUCCESS; } static void hybridj_free (void *vstate) { hybridj_state_t *state = (hybridj_state_t *) vstate; gsl_vector_free (state->v); gsl_vector_free (state->w); gsl_vector_free (state->rdx); gsl_vector_free (state->qtdf); gsl_vector_free (state->df); gsl_vector_free (state->f_trial); gsl_vector_free (state->x_trial); gsl_vector_free (state->gradient); gsl_vector_free (state->newton); gsl_vector_free (state->qtf); gsl_vector_free (state->diag); gsl_vector_free (state->tau); gsl_matrix_free (state->r); gsl_matrix_free (state->q); } static const gsl_multiroot_fdfsolver_type hybridj_type = { "hybridj", /* name */ sizeof (hybridj_state_t), &hybridj_alloc, &hybridj_set, &hybridj_iterate, &hybridj_free }; static const gsl_multiroot_fdfsolver_type hybridsj_type = { "hybridsj", /* name */ sizeof (hybridj_state_t), &hybridj_alloc, &hybridsj_set, &hybridsj_iterate, &hybridj_free }; const gsl_multiroot_fdfsolver_type *gsl_multiroot_fdfsolver_hybridj = &hybridj_type; const gsl_multiroot_fdfsolver_type *gsl_multiroot_fdfsolver_hybridsj = &hybridsj_type; sources_5316/external/gsl/gsl_fft.h0000664000176700017670000000304111705263724016136 0ustar paulpaul/* fft/gsl_fft.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_FFT_H__ #define __GSL_FFT_H__ #include "gsl_complex.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS #ifndef GSL_DISABLE_DEPRECATED typedef enum { forward = -1, backward = +1, gsl_fft_forward = -1, gsl_fft_backward = +1 } gsl_fft_direction; #else typedef enum { gsl_fft_forward = -1, gsl_fft_backward = +1 } gsl_fft_direction; #endif /* this gives the sign in the formula h(f) = \sum x(t) exp(+/- 2 pi i f t) where - is the forward transform direction and + the inverse direction */ __END_DECLS #endif /* __GSL_FFT_H__ */ sources_5316/external/gsl/gsl_cdf__cauchy.c0000664000176700017670000000243311723710247017602 0ustar paulpaul/* cdf/cauchy.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_cauchy_P (const double x, const double a) { double P; double u = x / a; if (u > -1) { P = 0.5 + atan (u) / M_PI; } else { P = atan(-1/u) / M_PI; } return P; } double gsl_cdf_cauchy_Q (const double x, const double a) { double Q; double u = x / a; if (u < 1) { Q = 0.5 - atan (u) / M_PI; } else { Q = atan(1/u) / M_PI; } return Q; } sources_5316/external/gsl/gsl_specfunc__elementary.c0000664000176700017670000000470011723710247021544 0ustar paulpaul/* specfunc/elementary.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_elementary.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__check.h" int gsl_sf_multiply_e(const double x, const double y, gsl_sf_result * result) { const double ax = fabs(x); const double ay = fabs(y); if(x == 0.0 || y == 0.0) { /* It is necessary to eliminate this immediately. */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if((ax <= 1.0 && ay >= 1.0) || (ay <= 1.0 && ax >= 1.0)) { /* Straddling 1.0 is always safe. */ result->val = x*y; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double f = 1.0 - 2.0 * GSL_DBL_EPSILON; const double min = GSL_MIN_DBL(fabs(x), fabs(y)); const double max = GSL_MAX_DBL(fabs(x), fabs(y)); if(max < 0.9 * GSL_SQRT_DBL_MAX || min < (f * DBL_MAX)/max) { result->val = GSL_COERCE_DBL(x*y); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } } int gsl_sf_multiply_err_e(const double x, const double dx, const double y, const double dy, gsl_sf_result * result) { int status = gsl_sf_multiply_e(x, y, result); result->err += fabs(dx*y) + fabs(dy*x); return status; } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_multiply(const double x, const double y) { EVAL_RESULT(gsl_sf_multiply_e(x, y, &result)); } sources_5316/external/gsl/gsl_multimin__linear_wrapper.c0000664000176700017670000000773411723710247022453 0ustar paulpaultypedef struct { gsl_function_fdf fdf_linear; gsl_multimin_function_fdf *fdf; /* fixed values */ const gsl_vector *x; const gsl_vector *g; const gsl_vector *p; /* cached values, for x(alpha) = x + alpha * p */ double f_alpha; double df_alpha; gsl_vector *x_alpha; gsl_vector *g_alpha; /* cache "keys" */ double f_cache_key; double df_cache_key; double x_cache_key; double g_cache_key; } wrapper_t; static void moveto (double alpha, wrapper_t * w) { if (alpha == w->x_cache_key) /* using previously cached position */ { return; } /* set x_alpha = x + alpha * p */ gsl_vector_memcpy (w->x_alpha, w->x); gsl_blas_daxpy (alpha, w->p, w->x_alpha); w->x_cache_key = alpha; } static double slope (wrapper_t * w) /* compute gradient . direction */ { double df; gsl_blas_ddot (w->g_alpha, w->p, &df); return df; } static double wrap_f (double alpha, void *params) { wrapper_t *w = (wrapper_t *) params; if (alpha == w->f_cache_key) /* using previously cached f(alpha) */ { return w->f_alpha; } moveto (alpha, w); w->f_alpha = GSL_MULTIMIN_FN_EVAL_F (w->fdf, w->x_alpha); w->f_cache_key = alpha; return w->f_alpha; } static double wrap_df (double alpha, void *params) { wrapper_t *w = (wrapper_t *) params; if (alpha == w->df_cache_key) /* using previously cached df(alpha) */ { return w->df_alpha; } moveto (alpha, w); if (alpha != w->g_cache_key) { GSL_MULTIMIN_FN_EVAL_DF (w->fdf, w->x_alpha, w->g_alpha); w->g_cache_key = alpha; } w->df_alpha = slope (w); w->df_cache_key = alpha; return w->df_alpha; } static void wrap_fdf (double alpha, void *params, double *f, double *df) { wrapper_t *w = (wrapper_t *) params; /* Check for previously cached values */ if (alpha == w->f_cache_key && alpha == w->df_cache_key) { *f = w->f_alpha; *df = w->df_alpha; return; } if (alpha == w->f_cache_key || alpha == w->df_cache_key) { *f = wrap_f (alpha, params); *df = wrap_df (alpha, params); return; } moveto (alpha, w); GSL_MULTIMIN_FN_EVAL_F_DF (w->fdf, w->x_alpha, &w->f_alpha, w->g_alpha); w->f_cache_key = alpha; w->g_cache_key = alpha; w->df_alpha = slope (w); w->df_cache_key = alpha; *f = w->f_alpha; *df = w->df_alpha; } static void prepare_wrapper (wrapper_t * w, gsl_multimin_function_fdf * fdf, const gsl_vector * x, double f, const gsl_vector *g, const gsl_vector * p, gsl_vector * x_alpha, gsl_vector *g_alpha) { w->fdf_linear.f = &wrap_f; w->fdf_linear.df = &wrap_df; w->fdf_linear.fdf = &wrap_fdf; w->fdf_linear.params = (void *)w; /* pointer to "self" */ w->fdf = fdf; w->x = x; w->g = g; w->p = p; w->x_alpha = x_alpha; w->g_alpha = g_alpha; gsl_vector_memcpy(w->x_alpha, w->x); w->x_cache_key = 0.0; w->f_alpha = f; w->f_cache_key = 0.0; gsl_vector_memcpy(w->g_alpha, w->g); w->g_cache_key = 0.0; w->df_alpha = slope(w); w->df_cache_key = 0.0; } static void update_position (wrapper_t * w, double alpha, gsl_vector *x, double *f, gsl_vector *g) { /* ensure that everything is fully cached */ { double f_alpha, df_alpha; wrap_fdf (alpha, w, &f_alpha, &df_alpha); } ; *f = w->f_alpha; gsl_vector_memcpy(x, w->x_alpha); gsl_vector_memcpy(g, w->g_alpha); } static void change_direction (wrapper_t * w) { /* Convert the cache values from the end of the current minimisation to those needed for the start of the next minimisation, alpha=0 */ /* The new x_alpha for alpha=0 is the current position */ gsl_vector_memcpy (w->x_alpha, w->x); w->x_cache_key = 0.0; /* The function value does not change */ w->f_cache_key = 0.0; /* The new g_alpha for alpha=0 is the current gradient at the endpoint */ gsl_vector_memcpy (w->g_alpha, w->g); w->g_cache_key = 0.0; /* Calculate the slope along the new direction vector, p */ w->df_alpha = slope (w); w->df_cache_key = 0.0; } sources_5316/external/gsl/gsl_vector__vector_source.c0000664000176700017670000000464611723710247021766 0ustar paulpaul/* vector/vector_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef HIDE_INLINE_STATIC BASE FUNCTION (gsl_vector, get) (const TYPE (gsl_vector) * v, const size_t i) { if (gsl_check_range) { if (i >= v->size) /* size_t is unsigned, can't be negative */ { BASE zero = ZERO; GSL_ERROR_VAL ("index out of range", GSL_EINVAL, zero); } } /* The following line is a generalization of return v->data[i] */ return *(BASE *) (v->data + MULTIPLICITY * i * v->stride); } void FUNCTION (gsl_vector, set) (TYPE (gsl_vector) * v, const size_t i, BASE x) { if (gsl_check_range) { if (i >= v->size) /* size_t is unsigned, can't be negative */ { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } } /* The following line is a generalization of v->data[i] = x */ *(BASE *) (v->data + MULTIPLICITY * i * v->stride) = x; } BASE * FUNCTION (gsl_vector, ptr) (TYPE (gsl_vector) * v, const size_t i) { if (gsl_check_range) { if (i >= v->size) /* size_t is unsigned, can't be negative */ { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } } return (BASE *) (v->data + MULTIPLICITY * i * v->stride); } const BASE * FUNCTION (gsl_vector, const_ptr) (const TYPE (gsl_vector) * v, const size_t i) { if (gsl_check_range) { if (i >= v->size) /* size_t is unsigned, can't be negative */ { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } } /* The following line is a generalization of return v->data[i] */ return (const BASE *) (v->data + MULTIPLICITY * i * v->stride); } #endif sources_5316/external/gsl/gsl_min__bracketing.c0000664000176700017670000000774711723710247020503 0ustar paulpaul/* min/bracketing.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Fabrice Rossi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* bracketing.c -- find an initial bracketing interval for a function to minimize */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_min.h" #include "gsl_machine.h" #include "gsl_min__min.h" int gsl_min_find_bracket(gsl_function *f,double *x_minimum,double * f_minimum, double * x_lower, double * f_lower, double * x_upper, double * f_upper, size_t eval_max) { /* The three following variables must be declared volatile to avoid storage in extended precision registers available on some architecture. The code relies on the ability to compare double values. As the values will be store in regular memory, the extended precision will then be lost and values that are different in extended precision might have equal representation in double precision. This behavior might break the algorithm. */ volatile double f_left = *f_lower; volatile double f_right = *f_upper; volatile double f_center; double x_left = *x_lower; double x_right= *x_upper; double x_center; const double golden = 0.3819660; /* golden = (3 - sqrt(5))/2 */ size_t nb_eval = 0; if (f_right >= f_left) { x_center = (x_right - x_left) * golden + x_left; nb_eval++; SAFE_FUNC_CALL (f, x_center, &f_center); } else { x_center = x_right ; f_center = f_right ; x_right = (x_center - x_left) / golden + x_left; nb_eval++; SAFE_FUNC_CALL (f, x_right, &f_right); } do { if (f_center < f_left ) { if (f_center < f_right) { *x_lower = x_left; *x_upper = x_right; *x_minimum = x_center; *f_lower = f_left; *f_upper = f_right; *f_minimum = f_center; /* gsl_ieee_printf_double (&f_left); printf(" "); gsl_ieee_printf_double (&f_center); printf("\n");*/ return GSL_SUCCESS; } else if (f_center > f_right) { x_left = x_center; f_left = f_center; x_center = x_right; f_center = f_right; x_right = (x_center - x_left) / golden + x_left; nb_eval++; SAFE_FUNC_CALL (f, x_right, &f_right); } else /* f_center == f_right */ { x_right = x_center; f_right = f_center; x_center = (x_right - x_left) * golden + x_left; nb_eval++; SAFE_FUNC_CALL (f, x_center, &f_center); } } else /* f_center >= f_left */ { x_right = x_center; f_right = f_center; x_center = (x_right - x_left) * golden + x_left; nb_eval++; SAFE_FUNC_CALL (f, x_center, &f_center); } } while (nb_eval < eval_max && (x_right - x_left) > GSL_SQRT_DBL_EPSILON * ( (x_right + x_left) * 0.5 ) + GSL_SQRT_DBL_EPSILON); *x_lower = x_left; *x_upper = x_right; *x_minimum = x_center; *f_lower = f_left; *f_upper = f_right; *f_minimum = f_center; return GSL_FAILURE; } sources_5316/external/gsl/gsl_wavelet__dwt.c0000664000176700017670000002476211723710247020050 0ustar paulpaul/* wavelet/dwt.c * * Copyright (C) 2004 Ivo Alxneit * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* function dwt_step is based on the public domain function pwt.c * available from http://www.numerical-recipes.com */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_wavelet.h" #include "gsl_wavelet2d.h" #define ELEMENT(a,stride,i) ((a)[(stride)*(i)]) static int binary_logn (const size_t n); static void dwt_step (const gsl_wavelet * w, double *a, size_t stride, size_t n, gsl_wavelet_direction dir, gsl_wavelet_workspace * work); static int binary_logn (const size_t n) { size_t ntest; size_t logn = 0; size_t k = 1; while (k < n) { k *= 2; logn++; } ntest = (1 << logn); if (n != ntest) { return -1; /* n is not a power of 2 */ } return logn; } static void dwt_step (const gsl_wavelet * w, double *a, size_t stride, size_t n, gsl_wavelet_direction dir, gsl_wavelet_workspace * work) { double ai, ai1; size_t i, ii; size_t jf; size_t k; size_t n1, ni, nh, nmod; for (i = 0; i < work->n; i++) { work->scratch[i] = 0.0; } nmod = w->nc * n; nmod -= w->offset; /* center support */ n1 = n - 1; nh = n >> 1; if (dir == gsl_wavelet_forward) { for (ii = 0, i = 0; i < n; i += 2, ii++) { ni = i + nmod; for (k = 0; k < w->nc; k++) { jf = n1 & (ni + k); work->scratch[ii] += w->h1[k] * ELEMENT (a, stride, jf); work->scratch[ii + nh] += w->g1[k] * ELEMENT (a, stride, jf); } } } else { for (ii = 0, i = 0; i < n; i += 2, ii++) { ai = ELEMENT (a, stride, ii); ai1 = ELEMENT (a, stride, ii + nh); ni = i + nmod; for (k = 0; k < w->nc; k++) { jf = (n1 & (ni + k)); work->scratch[jf] += (w->h2[k] * ai + w->g2[k] * ai1); } } } for (i = 0; i < n; i++) { ELEMENT (a, stride, i) = work->scratch[i]; } } int gsl_wavelet_transform (const gsl_wavelet * w, double *data, size_t stride, size_t n, gsl_wavelet_direction dir, gsl_wavelet_workspace * work) { size_t i; if (work->n < n) { GSL_ERROR ("not enough workspace provided", GSL_EINVAL); } if (binary_logn (n) == -1) { GSL_ERROR ("n is not a power of 2", GSL_EINVAL); } if (n < 2) { return GSL_SUCCESS; } if (dir == gsl_wavelet_forward) { for (i = n; i >= 2; i >>= 1) { dwt_step (w, data, stride, i, dir, work); } } else { for (i = 2; i <= n; i <<= 1) { dwt_step (w, data, stride, i, dir, work); } } return GSL_SUCCESS; } int gsl_wavelet_transform_forward (const gsl_wavelet * w, double *data, size_t stride, size_t n, gsl_wavelet_workspace * work) { return gsl_wavelet_transform (w, data, stride, n, gsl_wavelet_forward, work); } int gsl_wavelet_transform_inverse (const gsl_wavelet * w, double *data, size_t stride, size_t n, gsl_wavelet_workspace * work) { return gsl_wavelet_transform (w, data, stride, n, gsl_wavelet_backward, work); } /* Leaving this out for now BJG */ #if 0 int gsl_dwt_vector (const gsl_wavelet * w, gsl_vector *v, gsl_wavelet_direction dir, gsl_wavelet_workspace * work) { return gsl_dwt (w, v->data, v->stride, v->size, dir, work); } #endif int gsl_wavelet2d_transform (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_direction dir, gsl_wavelet_workspace * work) { size_t i; if (size1 != size2) { GSL_ERROR ("2d dwt works only with square matrix", GSL_EINVAL); } if (work->n < size1) { GSL_ERROR ("not enough workspace provided", GSL_EINVAL); } if (binary_logn (size1) == -1) { GSL_ERROR ("n is not a power of 2", GSL_EINVAL); } if (size1 < 2) { return GSL_SUCCESS; } if (dir == gsl_wavelet_forward) { for (i = 0; i < size1; i++) /* for every row j */ { gsl_wavelet_transform (w, &ELEMENT(data, tda, i), 1, size1, dir, work); } for (i = 0; i < size2; i++) /* for every column j */ { gsl_wavelet_transform (w, &ELEMENT(data, 1, i), tda, size2, dir, work); } } else { for (i = 0; i < size2; i++) /* for every column j */ { gsl_wavelet_transform (w, &ELEMENT(data, 1, i), tda, size2, dir, work); } for (i = 0; i < size1; i++) /* for every row j */ { gsl_wavelet_transform (w, &ELEMENT(data, tda, i), 1, size1, dir, work); } } return GSL_SUCCESS; } int gsl_wavelet2d_nstransform (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_direction dir, gsl_wavelet_workspace * work) { size_t i, j; if (size1 != size2) { GSL_ERROR ("2d dwt works only with square matrix", GSL_EINVAL); } if (work->n < size1) { GSL_ERROR ("not enough workspace provided", GSL_EINVAL); } if (binary_logn (size1) == -1) { GSL_ERROR ("n is not a power of 2", GSL_EINVAL); } if (size1 < 2) { return GSL_SUCCESS; } if (dir == gsl_wavelet_forward) { for (i = size1; i >= 2; i >>= 1) { for (j = 0; j < i; j++) /* for every row j */ { dwt_step (w, &ELEMENT(data, tda, j), 1, i, dir, work); } for (j = 0; j < i; j++) /* for every column j */ { dwt_step (w, &ELEMENT(data, 1, j), tda, i, dir, work); } } } else { for (i = 2; i <= size1; i <<= 1) { for (j = 0; j < i; j++) /* for every column j */ { dwt_step (w, &ELEMENT(data, 1, j), tda, i, dir, work); } for (j = 0; j < i; j++) /* for every row j */ { dwt_step (w, &ELEMENT(data, tda, j), 1, i, dir, work); } } } return GSL_SUCCESS; } int gsl_wavelet2d_transform_forward (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_workspace * work) { return gsl_wavelet2d_transform (w, data, tda, size1, size2, gsl_wavelet_forward, work); } int gsl_wavelet2d_transform_inverse (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_workspace * work) { return gsl_wavelet2d_transform (w, data, tda, size1, size2, gsl_wavelet_backward, work); } int gsl_wavelet2d_nstransform_forward (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_workspace * work) { return gsl_wavelet2d_nstransform (w, data, tda, size1, size2, gsl_wavelet_forward, work); } int gsl_wavelet2d_nstransform_inverse (const gsl_wavelet * w, double *data, size_t tda, size_t size1, size_t size2, gsl_wavelet_workspace * work) { return gsl_wavelet2d_nstransform (w, data, tda, size1, size2, gsl_wavelet_backward, work); } int gsl_wavelet2d_transform_matrix (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_direction dir, gsl_wavelet_workspace * work) { return gsl_wavelet2d_transform (w, a->data, a->tda, a->size1, a->size2, dir, work); } int gsl_wavelet2d_transform_matrix_forward (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_workspace * work) { return gsl_wavelet2d_transform (w, a->data, a->tda, a->size1, a->size2, gsl_wavelet_forward, work); } int gsl_wavelet2d_transform_matrix_inverse (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_workspace * work) { return gsl_wavelet2d_transform (w, a->data, a->tda, a->size1, a->size2, gsl_wavelet_backward, work); } int gsl_wavelet2d_nstransform_matrix (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_direction dir, gsl_wavelet_workspace * work) { return gsl_wavelet2d_nstransform (w, a->data, a->tda, a->size1, a->size2, dir, work); } int gsl_wavelet2d_nstransform_matrix_forward (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_workspace * work) { return gsl_wavelet2d_nstransform (w, a->data, a->tda, a->size1, a->size2, gsl_wavelet_forward, work); } int gsl_wavelet2d_nstransform_matrix_inverse (const gsl_wavelet * w, gsl_matrix * a, gsl_wavelet_workspace * work) { return gsl_wavelet2d_nstransform (w, a->data, a->tda, a->size1, a->size2, gsl_wavelet_backward, work); } sources_5316/external/gsl/gsl_cblas__ctpmv.c0000664000176700017670000000056011723710247020006 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ctpmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *Ap, void *X, const int incX) { #define BASE float #include "gsl_cblas__source_tpmv_c.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__bessel_J0.c0000664000176700017670000000634711723710247021216 0ustar paulpaul/* specfunc/bessel_J0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_mode.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_amp_phase.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besj0, 1977 version, w. fullerton */ /* chebyshev expansions for Bessel functions series for bj0 on the interval 0. to 1.60000d+01 with weighted error 7.47e-18 log weighted error 17.13 significant figures required 16.98 decimal places required 17.68 */ static double bj0_data[13] = { 0.100254161968939137, -0.665223007764405132, 0.248983703498281314, -0.0332527231700357697, 0.0023114179304694015, -0.0000991127741995080, 0.0000028916708643998, -0.0000000612108586630, 0.0000000009838650793, -0.0000000000124235515, 0.0000000000001265433, -0.0000000000000010619, 0.0000000000000000074, }; static cheb_series bj0_cs = { bj0_data, 12, -1, 1, 9 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_J0_e(const double x, gsl_sf_result * result) { double y = fabs(x); /* CHECK_POINTER(result) */ if(y < 2.0*GSL_SQRT_DBL_EPSILON) { result->val = 1.0; result->err = y*y; return GSL_SUCCESS; } else if(y <= 4.0) { return cheb_eval_e(&bj0_cs, 0.125*y*y - 1.0, result); } else { const double z = 32.0/(y*y) - 1.0; gsl_sf_result ca; gsl_sf_result ct; gsl_sf_result cp; const int stat_ca = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bm0_cs, z, &ca); const int stat_ct = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bth0_cs, z, &ct); const int stat_cp = gsl_sf_bessel_cos_pi4_e(y, ct.val/y, &cp); const double sqrty = sqrt(y); const double ampl = (0.75 + ca.val) / sqrty; result->val = ampl * cp.val; result->err = fabs(cp.val) * ca.err/sqrty + fabs(ampl) * cp.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_ca, stat_ct, stat_cp); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_J0(const double x) { EVAL_RESULT(gsl_sf_bessel_J0_e(x, &result)); } sources_5316/external/gsl/gsl_sf_debye.h0000664000176700017670000000437311705263724017150 0ustar paulpaul/* specfunc/gsl_sf_debye.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* augmented by D_5(x) and D_6(x) by Richard J. Mathar, 2005-11-08 */ #ifndef __GSL_SF_DEBYE_H__ #define __GSL_SF_DEBYE_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* D_n(x) := n/x^n Integrate[t^n/(e^t - 1), {t,0,x}] */ /* D_1(x) * * exceptions: GSL_EDOM */ int gsl_sf_debye_1_e(const double x, gsl_sf_result * result); double gsl_sf_debye_1(const double x); /* D_2(x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_debye_2_e(const double x, gsl_sf_result * result); double gsl_sf_debye_2(const double x); /* D_3(x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_debye_3_e(const double x, gsl_sf_result * result); double gsl_sf_debye_3(const double x); /* D_4(x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_debye_4_e(const double x, gsl_sf_result * result); double gsl_sf_debye_4(const double x); /* D_5(x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_debye_5_e(const double x, gsl_sf_result * result); double gsl_sf_debye_5(const double x); /* D_6(x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_debye_6_e(const double x, gsl_sf_result * result); double gsl_sf_debye_6(const double x); __END_DECLS #endif /* __GSL_SF_DEBYE_H__ */ sources_5316/external/gsl/gsl_sf__bessel_i.c0000644000176700017670000002151410707442037017766 0ustar paulpaul/* specfunc/bessel_i.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" /* i_{l+1}/i_l */ static int bessel_il_CF1(const int l, const double x, const double threshold, double * ratio) { const int kmax = 2000; double tk = 1.0; double sum = 1.0; double rhok = 0.0; int k; for(k=1; k<=kmax; k++) { double ak = (x/(2.0*l+1.0+2.0*k)) * (x/(2.0*l+3.0+2.0*k)); rhok = -ak*(1.0 + rhok)/(1.0 + ak*(1.0 + rhok)); tk *= rhok; sum += tk; if(fabs(tk/sum) < threshold) break; } *ratio = x/(2.0*l+3.0) * sum; if(k == kmax) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_i0_scaled_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 0.2) { const double eax = exp(-ax); const double y = ax*ax; const double c1 = 1.0/6.0; const double c2 = 1.0/120.0; const double c3 = 1.0/5040.0; const double c4 = 1.0/362880.0; const double c5 = 1.0/39916800.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*c5)))); result->val = eax * sum; result->err = 2.0 * GSL_DBL_EPSILON * result->val; } else if(ax < -0.5*GSL_LOG_DBL_EPSILON) { result->val = (1.0 - exp(-2.0*ax))/(2.0*ax); result->err = 2.0 * GSL_DBL_EPSILON * result->val; } else { result->val = 1.0/(2.0*ax); result->err = 2.0 * GSL_DBL_EPSILON * result->val; } return GSL_SUCCESS; } int gsl_sf_bessel_i1_scaled_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 3.0*GSL_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(ax < 0.25) { const double eax = exp(-ax); const double y = x*x; const double c1 = 1.0/10.0; const double c2 = 1.0/280.0; const double c3 = 1.0/15120.0; const double c4 = 1.0/1330560.0; const double c5 = 1.0/172972800.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*c5)))); result->val = eax * x/3.0 * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double ex = exp(-2.0*ax); result->val = 0.5 * (ax*(1.0+ex) - (1.0-ex)) / (ax*ax); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(x < 0.0) result->val = -result->val; return GSL_SUCCESS; } } int gsl_sf_bessel_i2_scaled_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 4.0*GSL_SQRT_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(ax < 0.25) { const double y = x*x; const double c1 = 1.0/14.0; const double c2 = 1.0/504.0; const double c3 = 1.0/33264.0; const double c4 = 1.0/3459456.0; const double c5 = 1.0/518918400.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*c5)))); const double pre = exp(-ax) * x*x/15.0; result->val = pre * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double ex = exp(-2.0*ax); double x2 = x*x; result->val = 0.5 * ((3.0+x2)*(1.0-ex) - 3.0*ax*(1.0+ex))/(ax*ax*ax); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_il_scaled_e(const int l, double x, gsl_sf_result * result) { double sgn = 1.0; double ax = fabs(x); if(x < 0.0) { /* i_l(-x) = (-1)^l i_l(x) */ sgn = ( GSL_IS_ODD(l) ? -1.0 : 1.0 ); x = -x; } if(l < 0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = ( l == 0 ? 1.0 : 0.0 ); result->err = 0.0; return GSL_SUCCESS; } else if(l == 0) { gsl_sf_result il; int stat_il = gsl_sf_bessel_i0_scaled_e(x, &il); result->val = sgn * il.val; result->err = il.err; return stat_il; } else if(l == 1) { gsl_sf_result il; int stat_il = gsl_sf_bessel_i1_scaled_e(x, &il); result->val = sgn * il.val; result->err = il.err; return stat_il; } else if(l == 2) { gsl_sf_result il; int stat_il = gsl_sf_bessel_i2_scaled_e(x, &il); result->val = sgn * il.val; result->err = il.err; return stat_il; } else if(x*x < 10.0*(l+1.5)/M_E) { gsl_sf_result b; int stat = gsl_sf_bessel_IJ_taylor_e(l+0.5, x, 1, 50, GSL_DBL_EPSILON, &b); double pre = exp(-ax) * sqrt((0.5*M_PI)/x); result->val = sgn * pre * b.val; result->err = pre * b.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } else if(l < 150) { gsl_sf_result i0_scaled; int stat_i0 = gsl_sf_bessel_i0_scaled_e(ax, &i0_scaled); double rat; int stat_CF1 = bessel_il_CF1(l, ax, GSL_DBL_EPSILON, &rat); double iellp1 = rat * GSL_SQRT_DBL_MIN; double iell = GSL_SQRT_DBL_MIN; double iellm1; int ell; for(ell = l; ell >= 1; ell--) { iellm1 = iellp1 + (2*ell + 1)/x * iell; iellp1 = iell; iell = iellm1; } result->val = sgn * i0_scaled.val * (GSL_SQRT_DBL_MIN / iell); result->err = i0_scaled.err * (GSL_SQRT_DBL_MIN / iell); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_i0, stat_CF1); } else if(GSL_MIN(0.29/(l*l+1.0), 0.5/(l*l+1.0+x*x)) < 0.5*GSL_ROOT3_DBL_EPSILON) { int status = gsl_sf_bessel_Inu_scaled_asymp_unif_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= sgn * pre; result->err *= pre; return status; } else { /* recurse down from safe values */ double rt_term = sqrt((0.5*M_PI)/x); const int LMAX = 2 + (int) (1.2 / GSL_ROOT6_DBL_EPSILON); gsl_sf_result r_iellp1; gsl_sf_result r_iell; int stat_a1 = gsl_sf_bessel_Inu_scaled_asymp_unif_e(LMAX + 1 + 0.5, x, &r_iellp1); int stat_a2 = gsl_sf_bessel_Inu_scaled_asymp_unif_e(LMAX + 0.5, x, &r_iell); double iellp1 = r_iellp1.val; double iell = r_iell.val; double iellm1 = 0.0; int ell; iellp1 *= rt_term; iell *= rt_term; for(ell = LMAX; ell >= l+1; ell--) { iellm1 = iellp1 + (2*ell + 1)/x * iell; iellp1 = iell; iell = iellm1; } result->val = sgn * iellm1; result->err = fabs(result->val)*(GSL_DBL_EPSILON + fabs(r_iellp1.err/r_iellp1.val) + fabs(r_iell.err/r_iell.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_a1, stat_a2); } } int gsl_sf_bessel_il_scaled_array(const int lmax, const double x, double * result_array) { if(x == 0.0) { int ell; result_array[0] = 1.0; for (ell = lmax; ell >= 1; ell--) { result_array[ell] = 0.0; }; return GSL_SUCCESS; } else { int ell; gsl_sf_result r_iellp1; gsl_sf_result r_iell; int stat_0 = gsl_sf_bessel_il_scaled_e(lmax+1, x, &r_iellp1); int stat_1 = gsl_sf_bessel_il_scaled_e(lmax, x, &r_iell); double iellp1 = r_iellp1.val; double iell = r_iell.val; double iellm1; result_array[lmax] = iell; for(ell = lmax; ell >= 1; ell--) { iellm1 = iellp1 + (2*ell + 1)/x * iell; iellp1 = iell; iell = iellm1; result_array[ell-1] = iellm1; } return GSL_ERROR_SELECT_2(stat_0, stat_1); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_i0_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_i0_scaled_e(x, &result)); } double gsl_sf_bessel_i1_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_i1_scaled_e(x, &result)); } double gsl_sf_bessel_i2_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_i2_scaled_e(x, &result)); } double gsl_sf_bessel_il_scaled(const int l, const double x) { EVAL_RESULT(gsl_sf_bessel_il_scaled_e(l, x, &result)); } sources_5316/external/gsl/gsl_statistics_ushort.h0000664000176700017670000001125111705263724021157 0ustar paulpaul/* statistics/gsl_statistics_ushort.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_USHORT_H__ #define __GSL_STATISTICS_USHORT_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_ushort_mean (const unsigned short data[], const size_t stride, const size_t n); double gsl_stats_ushort_variance (const unsigned short data[], const size_t stride, const size_t n); double gsl_stats_ushort_sd (const unsigned short data[], const size_t stride, const size_t n); double gsl_stats_ushort_variance_with_fixed_mean (const unsigned short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ushort_sd_with_fixed_mean (const unsigned short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ushort_absdev (const unsigned short data[], const size_t stride, const size_t n); double gsl_stats_ushort_skew (const unsigned short data[], const size_t stride, const size_t n); double gsl_stats_ushort_kurtosis (const unsigned short data[], const size_t stride, const size_t n); double gsl_stats_ushort_lag1_autocorrelation (const unsigned short data[], const size_t stride, const size_t n); double gsl_stats_ushort_covariance (const unsigned short data1[], const size_t stride1,const unsigned short data2[], const size_t stride2, const size_t n); double gsl_stats_ushort_correlation (const unsigned short data1[], const size_t stride1,const unsigned short data2[], const size_t stride2, const size_t n); double gsl_stats_ushort_variance_m (const unsigned short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ushort_sd_m (const unsigned short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ushort_absdev_m (const unsigned short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ushort_skew_m_sd (const unsigned short data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_ushort_kurtosis_m_sd (const unsigned short data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_ushort_lag1_autocorrelation_m (const unsigned short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ushort_covariance_m (const unsigned short data1[], const size_t stride1,const unsigned short data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); double gsl_stats_ushort_pvariance (const unsigned short data1[], const size_t stride1, const size_t n1, const unsigned short data2[], const size_t stride2, const size_t n2); double gsl_stats_ushort_ttest (const unsigned short data1[], const size_t stride1, const size_t n1, const unsigned short data2[], const size_t stride2, const size_t n2); unsigned short gsl_stats_ushort_max (const unsigned short data[], const size_t stride, const size_t n); unsigned short gsl_stats_ushort_min (const unsigned short data[], const size_t stride, const size_t n); void gsl_stats_ushort_minmax (unsigned short * min, unsigned short * max, const unsigned short data[], const size_t stride, const size_t n); size_t gsl_stats_ushort_max_index (const unsigned short data[], const size_t stride, const size_t n); size_t gsl_stats_ushort_min_index (const unsigned short data[], const size_t stride, const size_t n); void gsl_stats_ushort_minmax_index (size_t * min_index, size_t * max_index, const unsigned short data[], const size_t stride, const size_t n); double gsl_stats_ushort_median_from_sorted_data (const unsigned short sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_ushort_quantile_from_sorted_data (const unsigned short sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_USHORT_H__ */ sources_5316/external/gsl/gsl_cblas__source_nrm2_c.h0000664000176700017670000000300311705263724021420 0ustar paulpaul/* blas/source_nrm2_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { BASE scale = 0.0; BASE ssq = 1.0; INDEX i; INDEX ix = 0; if (N == 0 || incX < 1) { return 0; } for (i = 0; i < N; i++) { const BASE x = CONST_REAL(X, ix); const BASE y = CONST_IMAG(X, ix); if (x != 0.0) { const BASE ax = fabs(x); if (scale < ax) { ssq = 1.0 + ssq * (scale / ax) * (scale / ax); scale = ax; } else { ssq += (ax / scale) * (ax / scale); } } if (y != 0.0) { const BASE ay = fabs(y); if (scale < ay) { ssq = 1.0 + ssq * (scale / ay) * (scale / ay); scale = ay; } else { ssq += (ay / scale) * (ay / scale); } } ix += incX; } return scale * sqrt(ssq); } sources_5316/external/gsl/gsl_block_long_double.h0000664000176700017670000000474311705263724021034 0ustar paulpaul/* block/gsl_block_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_LONG_DOUBLE_H__ #define __GSL_BLOCK_LONG_DOUBLE_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_long_double_struct { size_t size; long double *data; }; typedef struct gsl_block_long_double_struct gsl_block_long_double; gsl_block_long_double *gsl_block_long_double_alloc (const size_t n); gsl_block_long_double *gsl_block_long_double_calloc (const size_t n); void gsl_block_long_double_free (gsl_block_long_double * b); int gsl_block_long_double_fread (FILE * stream, gsl_block_long_double * b); int gsl_block_long_double_fwrite (FILE * stream, const gsl_block_long_double * b); int gsl_block_long_double_fscanf (FILE * stream, gsl_block_long_double * b); int gsl_block_long_double_fprintf (FILE * stream, const gsl_block_long_double * b, const char *format); int gsl_block_long_double_raw_fread (FILE * stream, long double * b, const size_t n, const size_t stride); int gsl_block_long_double_raw_fwrite (FILE * stream, const long double * b, const size_t n, const size_t stride); int gsl_block_long_double_raw_fscanf (FILE * stream, long double * b, const size_t n, const size_t stride); int gsl_block_long_double_raw_fprintf (FILE * stream, const long double * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_long_double_size (const gsl_block_long_double * b); long double * gsl_block_long_double_data (const gsl_block_long_double * b); __END_DECLS #endif /* __GSL_BLOCK_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_specfunc__mathieu_radfunc.c0000664000176700017670000002673311723710247022547 0ustar paulpaul/* specfunc/mathieu_radfunc.c * * Copyright (C) 2002 Lowell Johnson * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Author: L. Johnson */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_sf.h" #include "gsl_sf_mathieu.h" int gsl_sf_mathieu_Mc(int kind, int order, double qq, double zz, gsl_sf_result *result) { int even_odd, kk, mm, status; double maxerr = 1e-14, amax, pi = M_PI, fn, factor; double coeff[GSL_SF_MATHIEU_COEFF], fc; double j1c, z2c, j1pc, z2pc; double u1, u2; gsl_sf_result aa; /* Check for out of bounds parameters. */ if (qq <= 0.0) { GSL_ERROR("q must be greater than zero", GSL_EINVAL); } if (kind < 1 || kind > 2) { GSL_ERROR("kind must be 1 or 2", GSL_EINVAL); } mm = 0; amax = 0.0; fn = 0.0; u1 = sqrt(qq)*exp(-1.0*zz); u2 = sqrt(qq)*exp(zz); even_odd = 0; if (order % 2 != 0) even_odd = 1; /* Compute the characteristic value. */ status = gsl_sf_mathieu_a(order, qq, &aa); if (status != GSL_SUCCESS) { return status; } /* Compute the series coefficients. */ status = gsl_sf_mathieu_a_coeff(order, qq, aa.val, coeff); if (status != GSL_SUCCESS) { return status; } if (even_odd == 0) { for (kk=0; kkval = fn; result->err = 2.0*GSL_DBL_EPSILON; factor = fabs(fn); if (factor > 1.0) result->err *= factor; return GSL_SUCCESS; } int gsl_sf_mathieu_Ms(int kind, int order, double qq, double zz, gsl_sf_result *result) { int even_odd, kk, mm, status; double maxerr = 1e-14, amax, pi = M_PI, fn, factor; double coeff[GSL_SF_MATHIEU_COEFF], fc; double j1c, z2c, j1mc, z2mc, j1pc, z2pc; double u1, u2; gsl_sf_result aa; /* Check for out of bounds parameters. */ if (qq <= 0.0) { GSL_ERROR("q must be greater than zero", GSL_EINVAL); } if (kind < 1 || kind > 2) { GSL_ERROR("kind must be 1 or 2", GSL_EINVAL); } mm = 0; amax = 0.0; fn = 0.0; u1 = sqrt(qq)*exp(-1.0*zz); u2 = sqrt(qq)*exp(zz); even_odd = 0; if (order % 2 != 0) even_odd = 1; /* Compute the characteristic value. */ status = gsl_sf_mathieu_b(order, qq, &aa); if (status != GSL_SUCCESS) { return status; } /* Compute the series coefficients. */ status = gsl_sf_mathieu_b_coeff(order, qq, aa.val, coeff); if (status != GSL_SUCCESS) { return status; } if (even_odd == 0) { for (kk=0; kkval = fn; result->err = 2.0*GSL_DBL_EPSILON; factor = fabs(fn); if (factor > 1.0) result->err *= factor; return GSL_SUCCESS; } int gsl_sf_mathieu_Mc_array(int kind, int nmin, int nmax, double qq, double zz, gsl_sf_mathieu_workspace *work, double result_array[]) { int even_odd, order, ii, kk, mm, status; double maxerr = 1e-14, amax, pi = M_PI, fn; double coeff[GSL_SF_MATHIEU_COEFF], fc; double j1c, z2c, j1pc, z2pc; double u1, u2; double *aa = work->aa; /* Initialize the result array to zeroes. */ for (ii=0; ii 2) { GSL_ERROR("kind must be 1 or 2", GSL_EINVAL); } mm = 0; amax = 0.0; fn = 0.0; u1 = sqrt(qq)*exp(-1.0*zz); u2 = sqrt(qq)*exp(zz); /* Compute all eigenvalues up to nmax. */ gsl_sf_mathieu_a_array(0, nmax, qq, work, aa); for (ii=0, order=nmin; order<=nmax; ii++, order++) { even_odd = 0; if (order % 2 != 0) even_odd = 1; /* Compute the series coefficients. */ status = gsl_sf_mathieu_a_coeff(order, qq, aa[order], coeff); if (status != GSL_SUCCESS) { return status; } if (even_odd == 0) { for (kk=0; kkbb; /* Initialize the result array to zeroes. */ for (ii=0; ii 2) { GSL_ERROR("kind must be 1 or 2", GSL_EINVAL); } mm = 0; amax = 0.0; fn = 0.0; u1 = sqrt(qq)*exp(-1.0*zz); u2 = sqrt(qq)*exp(zz); /* Compute all eigenvalues up to nmax. */ gsl_sf_mathieu_b_array(0, nmax, qq, work, bb); for (ii=0, order=nmin; order<=nmax; ii++, order++) { even_odd = 0; if (order % 2 != 0) even_odd = 1; /* Compute the series coefficients. */ status = gsl_sf_mathieu_b_coeff(order, qq, bb[order], coeff); if (status != GSL_SUCCESS) { return status; } if (even_odd == 0) { for (kk=0; kk #include "gsl_math.h" #include "gsl_cdf.h" #include "gsl_sf_gamma.h" #include "gsl_cdf__error.h" /* Computes the cumulative distribution function for a binomial random variable. For a binomial random variable X with n trials and success probability p, Pr( X <= k ) = Pr( Y >= p ) where Y is a beta random variable with parameters k+1 and n-k. The binomial distribution has the form, prob(k) = n!/(k!(n-k)!) * p^k (1-p)^(n-k) for k = 0, 1, ..., n The cumulated distributions can be expressed in terms of normalized incomplete beta functions (see Abramowitz & Stegun eq. 26.5.26 and eq. 6.6.3). Reference: W. Feller, "An Introduction to Probability and Its Applications," volume 1. Wiley, 1968. Exercise 45, page 173, chapter 6. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_cdf.h" double gsl_cdf_binomial_P (const unsigned int k, const double p, const unsigned int n) { double P; double a; double b; if (p > 1.0 || p < 0.0) { CDF_ERROR ("p < 0 or p > 1", GSL_EDOM); } if (k >= n) { P = 1.0; } else { a = (double) k + 1.0; b = (double) n - k; P = gsl_cdf_beta_Q (p, a, b); } return P; } double gsl_cdf_binomial_Q (const unsigned int k, const double p, const unsigned int n) { double Q; double a; double b; if (p > 1.0 || p < 0.0) { CDF_ERROR ("p < 0 or p > 1", GSL_EDOM); } if (k >= n) { Q = 0.0; } else { a = (double) k + 1.0; b = (double) n - k; Q = gsl_cdf_beta_P (p, a, b); } return Q; } sources_5316/external/gsl/gsl_cblas__source_swap_r.h0000664000176700017670000000177511705263724021551 0ustar paulpaul/* blas/source_swap_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE tmp = X[ix]; X[ix] = Y[iy]; Y[iy] = tmp; ix += incX; iy += incY; } } sources_5316/external/gsl/gsl_odeiv.h0000664000176700017670000001710211705263724016470 0ustar paulpaul/* ode-initval/gsl_odeiv.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_ODEIV_H__ #define __GSL_ODEIV_H__ #include #include #include "gsl_types.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Description of a system of ODEs. * * y' = f(t,y) = dydt(t, y) * * The system is specified by giving the right-hand-side * of the equation and possibly a jacobian function. * * Some methods require the jacobian function, which calculates * the matrix dfdy and the vector dfdt. The matrix dfdy conforms * to the GSL standard, being a continuous range of floating point * values, in row-order. * * As with GSL function objects, user-supplied parameter * data is also present. */ typedef struct { int (* function) (double t, const double y[], double dydt[], void * params); int (* jacobian) (double t, const double y[], double * dfdy, double dfdt[], void * params); size_t dimension; void * params; } gsl_odeiv_system; #define GSL_ODEIV_FN_EVAL(S,t,y,f) (*((S)->function))(t,y,f,(S)->params) #define GSL_ODEIV_JA_EVAL(S,t,y,dfdy,dfdt) (*((S)->jacobian))(t,y,dfdy,dfdt,(S)->params) /* General stepper object. * * Opaque object for stepping an ODE system from t to t+h. * In general the object has some state which facilitates * iterating the stepping operation. */ typedef struct { const char * name; int can_use_dydt_in; int gives_exact_dydt_out; void * (*alloc) (size_t dim); int (*apply) (void * state, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * dydt); int (*reset) (void * state, size_t dim); unsigned int (*order) (void * state); void (*free) (void * state); } gsl_odeiv_step_type; typedef struct { const gsl_odeiv_step_type * type; size_t dimension; void * state; } gsl_odeiv_step; /* Available stepper types. * * rk2 : embedded 2nd(3rd) Runge-Kutta * rk4 : 4th order (classical) Runge-Kutta * rkck : embedded 4th(5th) Runge-Kutta, Cash-Karp * rk8pd : embedded 8th(9th) Runge-Kutta, Prince-Dormand * rk2imp : implicit 2nd order Runge-Kutta at Gaussian points * rk4imp : implicit 4th order Runge-Kutta at Gaussian points * gear1 : M=1 implicit Gear method * gear2 : M=2 implicit Gear method */ GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_rk2; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_rk4; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_rkf45; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_rkck; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_rk8pd; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_rk2imp; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_rk2simp; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_rk4imp; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_bsimp; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_gear1; GSL_VAR const gsl_odeiv_step_type *gsl_odeiv_step_gear2; /* Constructor for specialized stepper objects. */ gsl_odeiv_step * gsl_odeiv_step_alloc(const gsl_odeiv_step_type * T, size_t dim); int gsl_odeiv_step_reset(gsl_odeiv_step * s); void gsl_odeiv_step_free(gsl_odeiv_step * s); /* General stepper object methods. */ const char * gsl_odeiv_step_name(const gsl_odeiv_step *); unsigned int gsl_odeiv_step_order(const gsl_odeiv_step * s); int gsl_odeiv_step_apply(gsl_odeiv_step *, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * dydt); /* General step size control object. * * The hadjust() method controls the adjustment of * step size given the result of a step and the error. * Valid hadjust() methods must return one of the codes below. * * The general data can be used by specializations * to store state and control their heuristics. */ typedef struct { const char * name; void * (*alloc) (void); int (*init) (void * state, double eps_abs, double eps_rel, double a_y, double a_dydt); int (*hadjust) (void * state, size_t dim, unsigned int ord, const double y[], const double yerr[], const double yp[], double * h); void (*free) (void * state); } gsl_odeiv_control_type; typedef struct { const gsl_odeiv_control_type * type; void * state; } gsl_odeiv_control; /* Possible return values for an hadjust() evolution method. */ #define GSL_ODEIV_HADJ_INC 1 /* step was increased */ #define GSL_ODEIV_HADJ_NIL 0 /* step unchanged */ #define GSL_ODEIV_HADJ_DEC (-1) /* step decreased */ gsl_odeiv_control * gsl_odeiv_control_alloc(const gsl_odeiv_control_type * T); int gsl_odeiv_control_init(gsl_odeiv_control * c, double eps_abs, double eps_rel, double a_y, double a_dydt); void gsl_odeiv_control_free(gsl_odeiv_control * c); int gsl_odeiv_control_hadjust (gsl_odeiv_control * c, gsl_odeiv_step * s, const double y[], const double yerr[], const double dydt[], double * h); const char * gsl_odeiv_control_name(const gsl_odeiv_control * c); /* Available control object constructors. * * The standard control object is a four parameter heuristic * defined as follows: * D0 = eps_abs + eps_rel * (a_y |y| + a_dydt h |y'|) * D1 = |yerr| * q = consistency order of method (q=4 for 4(5) embedded RK) * S = safety factor (0.9 say) * * / (D0/D1)^(1/(q+1)) D0 >= D1 * h_NEW = S h_OLD * | * \ (D0/D1)^(1/q) D0 < D1 * * This encompasses all the standard error scaling methods. * * The y method is the standard method with a_y=1, a_dydt=0. * The yp method is the standard method with a_y=0, a_dydt=1. */ gsl_odeiv_control * gsl_odeiv_control_standard_new(double eps_abs, double eps_rel, double a_y, double a_dydt); gsl_odeiv_control * gsl_odeiv_control_y_new(double eps_abs, double eps_rel); gsl_odeiv_control * gsl_odeiv_control_yp_new(double eps_abs, double eps_rel); /* This controller computes errors using different absolute errors for * each component * * D0 = eps_abs * scale_abs[i] + eps_rel * (a_y |y| + a_dydt h |y'|) */ gsl_odeiv_control * gsl_odeiv_control_scaled_new(double eps_abs, double eps_rel, double a_y, double a_dydt, const double scale_abs[], size_t dim); /* General evolution object. */ typedef struct { size_t dimension; double * y0; double * yerr; double * dydt_in; double * dydt_out; double last_step; unsigned long int count; unsigned long int failed_steps; } gsl_odeiv_evolve; /* Evolution object methods. */ gsl_odeiv_evolve * gsl_odeiv_evolve_alloc(size_t dim); int gsl_odeiv_evolve_apply(gsl_odeiv_evolve *, gsl_odeiv_control * con, gsl_odeiv_step * step, const gsl_odeiv_system * dydt, double * t, double t1, double * h, double y[]); int gsl_odeiv_evolve_reset(gsl_odeiv_evolve *); void gsl_odeiv_evolve_free(gsl_odeiv_evolve *); __END_DECLS #endif /* __GSL_ODEIV_H__ */ sources_5316/external/gsl/gsl_sum.h0000664000176700017670000001253411705263724016172 0ustar paulpaul/* sum/gsl_sum.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SUM_H__ #define __GSL_SUM_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Workspace for Levin U Transform with error estimation, * * size = number of terms the workspace can handle * sum_plain = simple sum of series * q_num = backward diagonal of numerator; length = size * q_den = backward diagonal of denominator; length = size * dq_num = table of numerator derivatives; length = size**2 * dq_den = table of denominator derivatives; length = size**2 * dsum = derivative of sum wrt term i; length = size */ typedef struct { size_t size; size_t i; /* position in array */ size_t terms_used; /* number of calls */ double sum_plain; double *q_num; double *q_den; double *dq_num; double *dq_den; double *dsum; } gsl_sum_levin_u_workspace; gsl_sum_levin_u_workspace *gsl_sum_levin_u_alloc (size_t n); void gsl_sum_levin_u_free (gsl_sum_levin_u_workspace * w); /* Basic Levin-u acceleration method. * * array = array of series elements * n = size of array * sum_accel = result of summation acceleration * err = estimated error * * See [Fessler et al., ACM TOMS 9, 346 (1983) and TOMS-602] */ int gsl_sum_levin_u_accel (const double *array, const size_t n, gsl_sum_levin_u_workspace * w, double *sum_accel, double *abserr); /* Basic Levin-u acceleration method with constraints on the terms * used, * * array = array of series elements * n = size of array * min_terms = minimum number of terms to sum * max_terms = maximum number of terms to sum * sum_accel = result of summation acceleration * err = estimated error * * See [Fessler et al., ACM TOMS 9, 346 (1983) and TOMS-602] */ int gsl_sum_levin_u_minmax (const double *array, const size_t n, const size_t min_terms, const size_t max_terms, gsl_sum_levin_u_workspace * w, double *sum_accel, double *abserr); /* Basic Levin-u step w/o reference to the array of terms. * We only need to specify the value of the current term * to execute the step. See TOMS-745. * * sum = t0 + ... + t_{n-1} + term; term = t_{n} * * term = value of the series term to be added * n = position of term in series (starting from 0) * sum_accel = result of summation acceleration * sum_plain = simple sum of series */ int gsl_sum_levin_u_step (const double term, const size_t n, const size_t nmax, gsl_sum_levin_u_workspace * w, double *sum_accel); /* The following functions perform the same calculation without estimating the errors. They require O(N) storage instead of O(N^2). This may be useful for summing many similar series where the size of the error has already been estimated reliably and is not expected to change. */ typedef struct { size_t size; size_t i; /* position in array */ size_t terms_used; /* number of calls */ double sum_plain; double *q_num; double *q_den; double *dsum; } gsl_sum_levin_utrunc_workspace; gsl_sum_levin_utrunc_workspace *gsl_sum_levin_utrunc_alloc (size_t n); void gsl_sum_levin_utrunc_free (gsl_sum_levin_utrunc_workspace * w); int gsl_sum_levin_utrunc_accel (const double *array, const size_t n, gsl_sum_levin_utrunc_workspace * w, double *sum_accel, double *abserr_trunc); int gsl_sum_levin_utrunc_minmax (const double *array, const size_t n, const size_t min_terms, const size_t max_terms, gsl_sum_levin_utrunc_workspace * w, double *sum_accel, double *abserr_trunc); int gsl_sum_levin_utrunc_step (const double term, const size_t n, gsl_sum_levin_utrunc_workspace * w, double *sum_accel); __END_DECLS #endif /* __GSL_SUM_H__ */ sources_5316/external/gsl/gsl_specfunc__bessel_amp_phase.h0000664000176700017670000000300511705263724022676 0ustar paulpaul/* specfunc/bessel_amp_phase.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef _BESSEL_AMP_PHASE_H_ #define _BESSEL_AMP_PHASE_H_ #include "gsl_specfunc__chebyshev.h" extern const cheb_series _gsl_sf_bessel_amp_phase_bm0_cs; extern const cheb_series _gsl_sf_bessel_amp_phase_bth0_cs; extern const cheb_series _gsl_sf_bessel_amp_phase_bm1_cs; extern const cheb_series _gsl_sf_bessel_amp_phase_bth1_cs; /* large argument expansions [Abramowitz+Stegun, 9.2.28-29] * * thetanu_corr = thetanu - x + 1/2 nu Pi * * assumes x > 0 */ int gsl_sf_bessel_asymp_Mnu_e(const double nu, const double x, double * result); int gsl_sf_bessel_asymp_thetanu_corr_e(const double nu, const double x, double * result); /* w/o x term */ #endif /* !_BESSEL_AMP_PHASE_H_ */ sources_5316/external/gsl/gsl_cblas__source_gemm_r.h0000664000176700017670000000605611705263724021521 0ustar paulpaul/* blas/source_gemm_r.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; INDEX n1, n2; INDEX ldf, ldg; int TransF, TransG; const BASE *F, *G; if (alpha == 0.0 && beta == 1.0) return; if (Order == CblasRowMajor) { n1 = M; n2 = N; F = A; ldf = lda; TransF = (TransA == CblasConjTrans) ? CblasTrans : TransA; G = B; ldg = ldb; TransG = (TransB == CblasConjTrans) ? CblasTrans : TransB; } else { n1 = N; n2 = M; F = B; ldf = ldb; TransF = (TransB == CblasConjTrans) ? CblasTrans : TransB; G = A; ldg = lda; TransG = (TransA == CblasConjTrans) ? CblasTrans : TransA; } /* form y := beta*y */ if (beta == 0.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { C[ldc * i + j] = 0.0; } } } else if (beta != 1.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { C[ldc * i + j] *= beta; } } } if (alpha == 0.0) return; if (TransF == CblasNoTrans && TransG == CblasNoTrans) { /* form C := alpha*A*B + C */ for (k = 0; k < K; k++) { for (i = 0; i < n1; i++) { const BASE temp = alpha * F[ldf * i + k]; if (temp != 0.0) { for (j = 0; j < n2; j++) { C[ldc * i + j] += temp * G[ldg * k + j]; } } } } } else if (TransF == CblasNoTrans && TransG == CblasTrans) { /* form C := alpha*A*B' + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp = 0.0; for (k = 0; k < K; k++) { temp += F[ldf * i + k] * G[ldg * j + k]; } C[ldc * i + j] += alpha * temp; } } } else if (TransF == CblasTrans && TransG == CblasNoTrans) { for (k = 0; k < K; k++) { for (i = 0; i < n1; i++) { const BASE temp = alpha * F[ldf * k + i]; if (temp != 0.0) { for (j = 0; j < n2; j++) { C[ldc * i + j] += temp * G[ldg * k + j]; } } } } } else if (TransF == CblasTrans && TransG == CblasTrans) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp = 0.0; for (k = 0; k < K; k++) { temp += F[ldf * k + i] * G[ldg * j + k]; } C[ldc * i + j] += alpha * temp; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_randist__gauss.c0000664000176700017670000001063011723710247020356 0ustar paulpaul/* randist/gauss.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2006, 2007 James Theiler, Brian Gough * Copyright (C) 2006 Charles Karney * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_randist.h" /* Of the two methods provided below, I think the Polar method is more * efficient, but only when you are actually producing two random * deviates. We don't produce two, because then we'd have to save one * in a static variable for the next call, and that would screws up * re-entrant or threaded code, so we only produce one. This makes * the Ratio method suddenly more appealing. * * [Added by Charles Karney] We use Leva's implementation of the Ratio * method which avoids calling log() nearly all the time and makes the * Ratio method faster than the Polar method (when it produces just one * result per call). Timing per call (gcc -O2 on 866MHz Pentium, * average over 10^8 calls) * * Polar method: 660 ns * Ratio method: 368 ns * */ /* Polar (Box-Mueller) method; See Knuth v2, 3rd ed, p122 */ double gsl_ran_gaussian (const gsl_rng * r, const double sigma) { double x, y, r2; do { /* choose x,y in uniform square (-1,-1) to (+1,+1) */ x = -1 + 2 * gsl_rng_uniform_pos (r); y = -1 + 2 * gsl_rng_uniform_pos (r); /* see if it is in the unit circle */ r2 = x * x + y * y; } while (r2 > 1.0 || r2 == 0); /* Box-Muller transform */ return sigma * y * sqrt (-2.0 * log (r2) / r2); } /* Ratio method (Kinderman-Monahan); see Knuth v2, 3rd ed, p130. * K+M, ACM Trans Math Software 3 (1977) 257-260. * * [Added by Charles Karney] This is an implementation of Leva's * modifications to the original K+M method; see: * J. L. Leva, ACM Trans Math Software 18 (1992) 449-453 and 454-455. */ double gsl_ran_gaussian_ratio_method (const gsl_rng * r, const double sigma) { double u, v, x, y, Q; const double s = 0.449871; /* Constants from Leva */ const double t = -0.386595; const double a = 0.19600; const double b = 0.25472; const double r1 = 0.27597; const double r2 = 0.27846; do /* This loop is executed 1.369 times on average */ { /* Generate a point P = (u, v) uniform in a rectangle enclosing the K+M region v^2 <= - 4 u^2 log(u). */ /* u in (0, 1] to avoid singularity at u = 0 */ u = 1 - gsl_rng_uniform (r); /* v is in the asymmetric interval [-0.5, 0.5). However v = -0.5 is rejected in the last part of the while clause. The resulting normal deviate is strictly symmetric about 0 (provided that v is symmetric once v = -0.5 is excluded). */ v = gsl_rng_uniform (r) - 0.5; /* Constant 1.7156 > sqrt(8/e) (for accuracy); but not by too much (for efficiency). */ v *= 1.7156; /* Compute Leva's quadratic form Q */ x = u - s; y = fabs (v) - t; Q = x * x + y * (a * y - b * x); /* Accept P if Q < r1 (Leva) */ /* Reject P if Q > r2 (Leva) */ /* Accept if v^2 <= -4 u^2 log(u) (K+M) */ /* This final test is executed 0.012 times on average. */ } while (Q >= r1 && (Q > r2 || v * v > -4 * u * u * log (u))); return sigma * (v / u); /* Return slope */ } double gsl_ran_gaussian_pdf (const double x, const double sigma) { double u = x / fabs (sigma); double p = (1 / (sqrt (2 * M_PI) * fabs (sigma))) * exp (-u * u / 2); return p; } double gsl_ran_ugaussian (const gsl_rng * r) { return gsl_ran_gaussian (r, 1.0); } double gsl_ran_ugaussian_ratio_method (const gsl_rng * r) { return gsl_ran_gaussian_ratio_method (r, 1.0); } double gsl_ran_ugaussian_pdf (const double x) { return gsl_ran_gaussian_pdf (x, 1.0); } sources_5316/external/gsl/gsl_histogram__add.c0000664000176700017670000000266411723710247020325 0ustar paulpaul/* histogram/add.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_histogram.h" #include "gsl_histogram__find.c" int gsl_histogram_increment (gsl_histogram * h, double x) { int status = gsl_histogram_accumulate (h, x, 1.0); return status; } int gsl_histogram_accumulate (gsl_histogram * h, double x, double weight) { const size_t n = h->n; size_t index = 0; int status = find (h->n, h->range, x, &index); if (status) { return GSL_EDOM; } if (index >= n) { GSL_ERROR ("index lies outside valid range of 0 .. n - 1", GSL_ESANITY); } h->bin[index] += weight; return GSL_SUCCESS; } sources_5316/external/gsl/gsl_linalg__lq.c0000664000176700017670000003443111723710247017457 0ustar paulpaul/* linalg/lq.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * Copyright (C) 2004 Joerg Wensch, modifications for LQ. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_linalg.h" #define REAL double #include "gsl_linalg__givens.c" #include "gsl_linalg__apply_givens.c" /* Note: The standard in numerical linear algebra is to solve A x = b * resp. ||A x - b||_2 -> min by QR-decompositions where x, b are * column vectors. * * When the matrix A has a large number of rows it is much more * efficient to work with the transposed matrix A^T and to solve the * system x^T A = b^T resp. ||x^T A - b^T||_2 -> min. This is caused * by the row-oriented format in which GSL stores matrices. Therefore * the QR-decomposition of A has to be replaced by a LQ decomposition * of A^T * * The purpose of this package is to provide the algorithms to compute * the LQ-decomposition and to solve the linear equations resp. least * squares problems. The dimensions N, M of the matrix are switched * because here A will probably be a transposed matrix. We write x^T, * b^T,... for vectors the comments to emphasize that they are row * vectors. * * It may even be useful to transpose your matrix explicitly (assumed * that there are no memory restrictions) because this takes O(M x N) * computing time where the decompostion takes O(M x N^2) computing * time. */ /* Factorise a general N x M matrix A into * * A = L Q * * where Q is orthogonal (M x M) and L is lower triangular (N x M). * * Q is stored as a packed set of Householder transformations in the * strict upper triangular part of the input matrix. * * R is stored in the diagonal and lower triangle of the input matrix. * * The full matrix for Q can be obtained as the product * * Q = Q_k .. Q_2 Q_1 * * where k = MIN(M,N) and * * Q_i = (I - tau_i * v_i * v_i') * * and where v_i is a Householder vector * * v_i = [1, m(i+1,i), m(i+2,i), ... , m(M,i)] * * This storage scheme is the same as in LAPACK. */ int gsl_linalg_LQ_decomp (gsl_matrix * A, gsl_vector * tau) { const size_t N = A->size1; const size_t M = A->size2; if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else { size_t i; for (i = 0; i < GSL_MIN (M, N); i++) { /* Compute the Householder transformation to reduce the j-th column of the matrix to a multiple of the j-th unit vector */ gsl_vector_view c_full = gsl_matrix_row (A, i); gsl_vector_view c = gsl_vector_subvector (&(c_full.vector), i, M-i); double tau_i = gsl_linalg_householder_transform (&(c.vector)); gsl_vector_set (tau, i, tau_i); /* Apply the transformation to the remaining columns and update the norms */ if (i + 1 < N) { gsl_matrix_view m = gsl_matrix_submatrix (A, i + 1, i, N - (i + 1), M - i ); gsl_linalg_householder_mh (tau_i, &(c.vector), &(m.matrix)); } } return GSL_SUCCESS; } } /* Solves the system x^T A = b^T using the LQ factorisation, * x^T L = b^T Q^T * * to obtain x. Based on SLATEC code. */ int gsl_linalg_LQ_solve_T (const gsl_matrix * LQ, const gsl_vector * tau, const gsl_vector * b, gsl_vector * x) { if (LQ->size1 != LQ->size2) { GSL_ERROR ("LQ matrix must be square", GSL_ENOTSQR); } else if (LQ->size2 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (LQ->size1 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve for x */ gsl_linalg_LQ_svx_T (LQ, tau, x); return GSL_SUCCESS; } } /* Solves the system x^T A = b^T in place using the LQ factorisation, * * x^T L = b^T Q^T * * to obtain x. Based on SLATEC code. */ int gsl_linalg_LQ_svx_T (const gsl_matrix * LQ, const gsl_vector * tau, gsl_vector * x) { if (LQ->size1 != LQ->size2) { GSL_ERROR ("LQ matrix must be square", GSL_ENOTSQR); } else if (LQ->size1 != x->size) { GSL_ERROR ("matrix size must match x/rhs size", GSL_EBADLEN); } else { /* compute rhs = Q^T b */ gsl_linalg_LQ_vecQT (LQ, tau, x); /* Solve R x = rhs, storing x in-place */ gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, LQ, x); return GSL_SUCCESS; } } /* Find the least squares solution to the overdetermined system * * x^T A = b^T * * for M >= N using the LQ factorization A = L Q. */ int gsl_linalg_LQ_lssolve_T (const gsl_matrix * LQ, const gsl_vector * tau, const gsl_vector * b, gsl_vector * x, gsl_vector * residual) { const size_t N = LQ->size1; const size_t M = LQ->size2; if (M < N) { GSL_ERROR ("LQ matrix must have M>=N", GSL_EBADLEN); } else if (M != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (N != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else if (M != residual->size) { GSL_ERROR ("matrix size must match residual size", GSL_EBADLEN); } else { gsl_matrix_const_view L = gsl_matrix_const_submatrix (LQ, 0, 0, N, N); gsl_vector_view c = gsl_vector_subvector(residual, 0, N); gsl_vector_memcpy(residual, b); /* compute rhs = b^T Q^T */ gsl_linalg_LQ_vecQT (LQ, tau, residual); /* Solve x^T L = rhs */ gsl_vector_memcpy(x, &(c.vector)); gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, &(L.matrix), x); /* Compute residual = b^T - x^T A = (b^T Q^T - x^T L) Q */ gsl_vector_set_zero(&(c.vector)); gsl_linalg_LQ_vecQ(LQ, tau, residual); return GSL_SUCCESS; } } int gsl_linalg_LQ_Lsolve_T (const gsl_matrix * LQ, const gsl_vector * b, gsl_vector * x) { if (LQ->size1 != LQ->size2) { GSL_ERROR ("LQ matrix must be square", GSL_ENOTSQR); } else if (LQ->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (LQ->size1 != x->size) { GSL_ERROR ("matrix size must match x size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve R x = b, storing x in-place */ gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, LQ, x); return GSL_SUCCESS; } } int gsl_linalg_LQ_Lsvx_T (const gsl_matrix * LQ, gsl_vector * x) { if (LQ->size1 != LQ->size2) { GSL_ERROR ("LQ matrix must be square", GSL_ENOTSQR); } else if (LQ->size2 != x->size) { GSL_ERROR ("matrix size must match rhs size", GSL_EBADLEN); } else { /* Solve x^T L = b^T, storing x in-place */ gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, LQ, x); return GSL_SUCCESS; } } int gsl_linalg_L_solve_T (const gsl_matrix * L, const gsl_vector * b, gsl_vector * x) { if (L->size1 != L->size2) { GSL_ERROR ("R matrix must be square", GSL_ENOTSQR); } else if (L->size2 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (L->size1 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve R x = b, storing x inplace in b */ gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, L, x); return GSL_SUCCESS; } } int gsl_linalg_LQ_vecQT (const gsl_matrix * LQ, const gsl_vector * tau, gsl_vector * v) { const size_t N = LQ->size1; const size_t M = LQ->size2; if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (v->size != M) { GSL_ERROR ("vector size must be M", GSL_EBADLEN); } else { size_t i; /* compute v Q^T */ for (i = 0; i < GSL_MIN (M, N); i++) { gsl_vector_const_view c = gsl_matrix_const_row (LQ, i); gsl_vector_const_view h = gsl_vector_const_subvector (&(c.vector), i, M - i); gsl_vector_view w = gsl_vector_subvector (v, i, M - i); double ti = gsl_vector_get (tau, i); gsl_linalg_householder_hv (ti, &(h.vector), &(w.vector)); } return GSL_SUCCESS; } } int gsl_linalg_LQ_vecQ (const gsl_matrix * LQ, const gsl_vector * tau, gsl_vector * v) { const size_t N = LQ->size1; const size_t M = LQ->size2; if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (v->size != M) { GSL_ERROR ("vector size must be M", GSL_EBADLEN); } else { size_t i; /* compute v Q^T */ for (i = GSL_MIN (M, N); i > 0 && i--;) { gsl_vector_const_view c = gsl_matrix_const_row (LQ, i); gsl_vector_const_view h = gsl_vector_const_subvector (&(c.vector), i, M - i); gsl_vector_view w = gsl_vector_subvector (v, i, M - i); double ti = gsl_vector_get (tau, i); gsl_linalg_householder_hv (ti, &(h.vector), &(w.vector)); } return GSL_SUCCESS; } } /* Form the orthogonal matrix Q from the packed LQ matrix */ int gsl_linalg_LQ_unpack (const gsl_matrix * LQ, const gsl_vector * tau, gsl_matrix * Q, gsl_matrix * L) { const size_t N = LQ->size1; const size_t M = LQ->size2; if (Q->size1 != M || Q->size2 != M) { GSL_ERROR ("Q matrix must be M x M", GSL_ENOTSQR); } else if (L->size1 != N || L->size2 != M) { GSL_ERROR ("R matrix must be N x M", GSL_ENOTSQR); } else if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else { size_t i, j, l_border; /* Initialize Q to the identity */ gsl_matrix_set_identity (Q); for (i = GSL_MIN (M, N); i > 0 && i--;) { gsl_vector_const_view c = gsl_matrix_const_row (LQ, i); gsl_vector_const_view h = gsl_vector_const_subvector (&c.vector, i, M - i); gsl_matrix_view m = gsl_matrix_submatrix (Q, i, i, M - i, M - i); double ti = gsl_vector_get (tau, i); gsl_linalg_householder_mh (ti, &h.vector, &m.matrix); } /* Form the lower triangular matrix L from a packed LQ matrix */ for (i = 0; i < N; i++) { l_border=GSL_MIN(i,M-1); for (j = 0; j <= l_border ; j++) gsl_matrix_set (L, i, j, gsl_matrix_get (LQ, i, j)); for (j = l_border+1; j < M; j++) gsl_matrix_set (L, i, j, 0.0); } return GSL_SUCCESS; } } /* Update a LQ factorisation for A= L Q , A' = A + v u^T, * L' Q' = LQ + v u^T * = (L + v u^T Q^T) Q * = (L + v w^T) Q * * where w = Q u. * * Algorithm from Golub and Van Loan, "Matrix Computations", Section * 12.5 (Updating Matrix Factorizations, Rank-One Changes) */ int gsl_linalg_LQ_update (gsl_matrix * Q, gsl_matrix * L, const gsl_vector * v, gsl_vector * w) { const size_t N = L->size1; const size_t M = L->size2; if (Q->size1 != M || Q->size2 != M) { GSL_ERROR ("Q matrix must be N x N if L is M x N", GSL_ENOTSQR); } else if (w->size != M) { GSL_ERROR ("w must be length N if L is M x N", GSL_EBADLEN); } else if (v->size != N) { GSL_ERROR ("v must be length M if L is M x N", GSL_EBADLEN); } else { size_t j, k; double w0; /* Apply Given's rotations to reduce w to (|w|, 0, 0, ... , 0) J_1^T .... J_(n-1)^T w = +/- |w| e_1 simultaneously applied to L, H = J_1^T ... J^T_(n-1) L so that H is upper Hessenberg. (12.5.2) */ for (k = M - 1; k > 0; k--) { double c, s; double wk = gsl_vector_get (w, k); double wkm1 = gsl_vector_get (w, k - 1); create_givens (wkm1, wk, &c, &s); apply_givens_vec (w, k - 1, k, c, s); apply_givens_lq (M, N, Q, L, k - 1, k, c, s); } w0 = gsl_vector_get (w, 0); /* Add in v w^T (Equation 12.5.3) */ for (j = 0; j < N; j++) { double lj0 = gsl_matrix_get (L, j, 0); double vj = gsl_vector_get (v, j); gsl_matrix_set (L, j, 0, lj0 + w0 * vj); } /* Apply Givens transformations L' = G_(n-1)^T ... G_1^T H Equation 12.5.4 */ for (k = 1; k < GSL_MIN(M,N+1); k++) { double c, s; double diag = gsl_matrix_get (L, k - 1, k - 1); double offdiag = gsl_matrix_get (L, k - 1 , k); create_givens (diag, offdiag, &c, &s); apply_givens_lq (M, N, Q, L, k - 1, k, c, s); gsl_matrix_set (L, k - 1, k, 0.0); /* exact zero of G^T */ } return GSL_SUCCESS; } } int gsl_linalg_LQ_LQsolve (gsl_matrix * Q, gsl_matrix * L, const gsl_vector * b, gsl_vector * x) { const size_t N = L->size1; const size_t M = L->size2; if (M != N) { return GSL_ENOTSQR; } else if (Q->size1 != M || b->size != M || x->size != M) { return GSL_EBADLEN; } else { /* compute sol = b^T Q^T */ gsl_blas_dgemv (CblasNoTrans, 1.0, Q, b, 0.0, x); /* Solve x^T L = sol, storing x in-place */ gsl_blas_dtrsv (CblasLower, CblasTrans, CblasNonUnit, L, x); return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_ieee-utils__fp-gnuppc.c0000664000176700017670000000532611723710247021542 0ustar paulpaul/* ieee-utils/fp-gnuppc.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough, John Fisher * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl_errno.h" #include "gsl_ieee_utils.h" /* * Identical to fp-gnux86.c, except with references to * _FPU_SINGLE, _FPU_DOUBLE, _FPU_EXTENDED, _FPU_MASK_DM * and _FPU_MASK_PM converted to errors. */ int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { unsigned short mode = 0 ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("powerpc only supports default precision rounding", GSL_EUNSUP); break ; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("powerpc only supports default precision rounding", GSL_EUNSUP); break ; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("powerpc only supports default precision rounding", GSL_EUNSUP); break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: mode |= _FPU_RC_NEAREST ; break ; case GSL_IEEE_ROUND_DOWN: mode |= _FPU_RC_DOWN ; break ; case GSL_IEEE_ROUND_UP: mode |= _FPU_RC_UP ; break ; case GSL_IEEE_ROUND_TO_ZERO: mode |= _FPU_RC_ZERO ; break ; default: mode |= _FPU_RC_NEAREST ; } if (exception_mask & GSL_IEEE_MASK_INVALID) mode |= _FPU_MASK_IM ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("powerpc does not support the denormalized operand exception. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode |= _FPU_MASK_ZM ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode |= _FPU_MASK_OM ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode |= _FPU_MASK_UM ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { GSL_ERROR ("powerpc does not support traps for inexact operations", GSL_EUNSUP) ; } _FPU_SETCW(mode) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_rng__random.c0000664000176700017670000004003411723710247017637 0ustar paulpaul/* rng/random.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This file provides support for random() generators. There are three versions in widespread use today, - The original BSD version, e.g. on SunOS 4.1 and FreeBSD. - The Linux libc5 version, which is differs from the BSD version in its seeding procedure, possibly due to the introduction of a typo in the multiplier. - The GNU glibc2 version, which has a new (and better) seeding procedure. They all produce different numbers, due to the different seeding algorithms, but the algorithm for the generator is the same in each case. */ static inline long int random_get (int * i, int * j, int n, long int * x); static inline unsigned long int random8_get (void *vstate); static inline unsigned long int random32_get (void *vstate); static inline unsigned long int random64_get (void *vstate); static inline unsigned long int random128_get (void *vstate); static inline unsigned long int random256_get (void *vstate); static double random8_get_double (void *vstate); static double random32_get_double (void *vstate); static double random64_get_double (void *vstate); static double random128_get_double (void *vstate); static double random256_get_double (void *vstate); static void random8_glibc2_set (void *state, unsigned long int s); static void random32_glibc2_set (void *state, unsigned long int s); static void random64_glibc2_set (void *state, unsigned long int s); static void random128_glibc2_set (void *state, unsigned long int s); static void random256_glibc2_set (void *state, unsigned long int s); static void random8_libc5_set (void *state, unsigned long int s); static void random32_libc5_set (void *state, unsigned long int s); static void random64_libc5_set (void *state, unsigned long int s); static void random128_libc5_set (void *state, unsigned long int s); static void random256_libc5_set (void *state, unsigned long int s); static void random8_bsd_set (void *state, unsigned long int s); static void random32_bsd_set (void *state, unsigned long int s); static void random64_bsd_set (void *state, unsigned long int s); static void random128_bsd_set (void *state, unsigned long int s); static void random256_bsd_set (void *state, unsigned long int s); static void bsd_initialize (long int * x, int n, unsigned long int s); static void libc5_initialize (long int * x, int n, unsigned long int s); static void glibc2_initialize (long int * x, int n, unsigned long int s); typedef struct { long int x; } random8_state_t; typedef struct { int i, j; long int x[7]; } random32_state_t; typedef struct { int i, j; long int x[15]; } random64_state_t; typedef struct { int i, j; long int x[31]; } random128_state_t; typedef struct { int i, j; long int x[63]; } random256_state_t; static inline unsigned long int random8_get (void *vstate) { random8_state_t *state = (random8_state_t *) vstate; state->x = (1103515245 * state->x + 12345) & 0x7fffffffUL; return state->x; } static inline long int random_get (int * i, int * j, int n, long int * x) { long int k ; x[*i] += x[*j] ; k = (x[*i] >> 1) & 0x7FFFFFFF ; (*i)++ ; if (*i == n) *i = 0 ; (*j)++ ; if (*j == n) *j = 0 ; return k ; } static inline unsigned long int random32_get (void *vstate) { random32_state_t *state = (random32_state_t *) vstate; unsigned long int k = random_get (&state->i, &state->j, 7, state->x) ; return k ; } static inline unsigned long int random64_get (void *vstate) { random64_state_t *state = (random64_state_t *) vstate; long int k = random_get (&state->i, &state->j, 15, state->x) ; return k ; } static inline unsigned long int random128_get (void *vstate) { random128_state_t *state = (random128_state_t *) vstate; unsigned long int k = random_get (&state->i, &state->j, 31, state->x) ; return k ; } static inline unsigned long int random256_get (void *vstate) { random256_state_t *state = (random256_state_t *) vstate; long int k = random_get (&state->i, &state->j, 63, state->x) ; return k ; } static double random8_get_double (void *vstate) { return random8_get (vstate) / 2147483648.0 ; } static double random32_get_double (void *vstate) { return random32_get (vstate) / 2147483648.0 ; } static double random64_get_double (void *vstate) { return random64_get (vstate) / 2147483648.0 ; } static double random128_get_double (void *vstate) { return random128_get (vstate) / 2147483648.0 ; } static double random256_get_double (void *vstate) { return random256_get (vstate) / 2147483648.0 ; } static void random8_bsd_set (void *vstate, unsigned long int s) { random8_state_t *state = (random8_state_t *) vstate; if (s == 0) s = 1; state->x = s; } static void random32_bsd_set (void *vstate, unsigned long int s) { random32_state_t *state = (random32_state_t *) vstate; int i; bsd_initialize (state->x, 7, s) ; state->i = 3; state->j = 0; for (i = 0 ; i < 10 * 7 ; i++) random32_get (state) ; } static void random64_bsd_set (void *vstate, unsigned long int s) { random64_state_t *state = (random64_state_t *) vstate; int i; bsd_initialize (state->x, 15, s) ; state->i = 1; state->j = 0; for (i = 0 ; i < 10 * 15 ; i++) random64_get (state) ; } static void random128_bsd_set (void *vstate, unsigned long int s) { random128_state_t *state = (random128_state_t *) vstate; int i; bsd_initialize (state->x, 31, s) ; state->i = 3; state->j = 0; for (i = 0 ; i < 10 * 31 ; i++) random128_get (state) ; } static void random256_bsd_set (void *vstate, unsigned long int s) { random256_state_t *state = (random256_state_t *) vstate; int i; bsd_initialize (state->x, 63, s) ; state->i = 1; state->j = 0; for (i = 0 ; i < 10 * 63 ; i++) random256_get (state) ; } static void bsd_initialize (long int * x, int n, unsigned long int s) { int i; if (s == 0) s = 1 ; x[0] = s; for (i = 1 ; i < n ; i++) x[i] = 1103515245 * x[i-1] + 12345 ; } static void libc5_initialize (long int * x, int n, unsigned long int s) { int i; if (s == 0) s = 1 ; x[0] = s; for (i = 1 ; i < n ; i++) x[i] = 1103515145 * x[i-1] + 12345 ; } static void glibc2_initialize (long int * x, int n, unsigned long int s) { int i; if (s == 0) s = 1 ; x[0] = s; for (i = 1 ; i < n ; i++) { const long int h = s / 127773; const long int t = 16807 * (s - h * 127773) - h * 2836; if (t < 0) { s = t + 2147483647 ; } else { s = t ; } x[i] = s ; } } static void random8_glibc2_set (void *vstate, unsigned long int s) { random8_state_t *state = (random8_state_t *) vstate; if (s == 0) s = 1; state->x = s; } static void random32_glibc2_set (void *vstate, unsigned long int s) { random32_state_t *state = (random32_state_t *) vstate; int i; glibc2_initialize (state->x, 7, s) ; state->i = 3; state->j = 0; for (i = 0 ; i < 10 * 7 ; i++) random32_get (state) ; } static void random64_glibc2_set (void *vstate, unsigned long int s) { random64_state_t *state = (random64_state_t *) vstate; int i; glibc2_initialize (state->x, 15, s) ; state->i = 1; state->j = 0; for (i = 0 ; i < 10 * 15 ; i++) random64_get (state) ; } static void random128_glibc2_set (void *vstate, unsigned long int s) { random128_state_t *state = (random128_state_t *) vstate; int i; glibc2_initialize (state->x, 31, s) ; state->i = 3; state->j = 0; for (i = 0 ; i < 10 * 31 ; i++) random128_get (state) ; } static void random256_glibc2_set (void *vstate, unsigned long int s) { random256_state_t *state = (random256_state_t *) vstate; int i; glibc2_initialize (state->x, 63, s) ; state->i = 1; state->j = 0; for (i = 0 ; i < 10 * 63 ; i++) random256_get (state) ; } static void random8_libc5_set (void *vstate, unsigned long int s) { random8_state_t *state = (random8_state_t *) vstate; if (s == 0) s = 1; state->x = s; } static void random32_libc5_set (void *vstate, unsigned long int s) { random32_state_t *state = (random32_state_t *) vstate; int i; libc5_initialize (state->x, 7, s) ; state->i = 3; state->j = 0; for (i = 0 ; i < 10 * 7 ; i++) random32_get (state) ; } static void random64_libc5_set (void *vstate, unsigned long int s) { random64_state_t *state = (random64_state_t *) vstate; int i; libc5_initialize (state->x, 15, s) ; state->i = 1; state->j = 0; for (i = 0 ; i < 10 * 15 ; i++) random64_get (state) ; } static void random128_libc5_set (void *vstate, unsigned long int s) { random128_state_t *state = (random128_state_t *) vstate; int i; libc5_initialize (state->x, 31, s) ; state->i = 3; state->j = 0; for (i = 0 ; i < 10 * 31 ; i++) random128_get (state) ; } static void random256_libc5_set (void *vstate, unsigned long int s) { random256_state_t *state = (random256_state_t *) vstate; int i; libc5_initialize (state->x, 63, s) ; state->i = 1; state->j = 0; for (i = 0 ; i < 10 * 63 ; i++) random256_get (state) ; } static const gsl_rng_type random_glibc2_type = {"random-glibc2", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random128_state_t), &random128_glibc2_set, &random128_get, &random128_get_double}; static const gsl_rng_type random8_glibc2_type = {"random8-glibc2", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random8_state_t), &random8_glibc2_set, &random8_get, &random8_get_double}; static const gsl_rng_type random32_glibc2_type = {"random32-glibc2", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random32_state_t), &random32_glibc2_set, &random32_get, &random32_get_double}; static const gsl_rng_type random64_glibc2_type = {"random64-glibc2", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random64_state_t), &random64_glibc2_set, &random64_get, &random64_get_double}; static const gsl_rng_type random128_glibc2_type = {"random128-glibc2", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random128_state_t), &random128_glibc2_set, &random128_get, &random128_get_double}; static const gsl_rng_type random256_glibc2_type = {"random256-glibc2", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random256_state_t), &random256_glibc2_set, &random256_get, &random256_get_double}; static const gsl_rng_type random_libc5_type = {"random-libc5", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random128_state_t), &random128_libc5_set, &random128_get, &random128_get_double}; static const gsl_rng_type random8_libc5_type = {"random8-libc5", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random8_state_t), &random8_libc5_set, &random8_get, &random8_get_double}; static const gsl_rng_type random32_libc5_type = {"random32-libc5", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random32_state_t), &random32_libc5_set, &random32_get, &random32_get_double}; static const gsl_rng_type random64_libc5_type = {"random64-libc5", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random64_state_t), &random64_libc5_set, &random64_get, &random64_get_double}; static const gsl_rng_type random128_libc5_type = {"random128-libc5", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random128_state_t), &random128_libc5_set, &random128_get, &random128_get_double}; static const gsl_rng_type random256_libc5_type = {"random256-libc5", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random256_state_t), &random256_libc5_set, &random256_get, &random256_get_double}; static const gsl_rng_type random_bsd_type = {"random-bsd", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random128_state_t), &random128_bsd_set, &random128_get, &random128_get_double}; static const gsl_rng_type random8_bsd_type = {"random8-bsd", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random8_state_t), &random8_bsd_set, &random8_get, &random8_get_double}; static const gsl_rng_type random32_bsd_type = {"random32-bsd", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random32_state_t), &random32_bsd_set, &random32_get, &random32_get_double}; static const gsl_rng_type random64_bsd_type = {"random64-bsd", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random64_state_t), &random64_bsd_set, &random64_get, &random64_get_double}; static const gsl_rng_type random128_bsd_type = {"random128-bsd", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random128_state_t), &random128_bsd_set, &random128_get, &random128_get_double}; static const gsl_rng_type random256_bsd_type = {"random256-bsd", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (random256_state_t), &random256_bsd_set, &random256_get, &random256_get_double}; const gsl_rng_type *gsl_rng_random_libc5 = &random_libc5_type; const gsl_rng_type *gsl_rng_random8_libc5 = &random8_libc5_type; const gsl_rng_type *gsl_rng_random32_libc5 = &random32_libc5_type; const gsl_rng_type *gsl_rng_random64_libc5 = &random64_libc5_type; const gsl_rng_type *gsl_rng_random128_libc5 = &random128_libc5_type; const gsl_rng_type *gsl_rng_random256_libc5 = &random256_libc5_type; const gsl_rng_type *gsl_rng_random_glibc2 = &random_glibc2_type; const gsl_rng_type *gsl_rng_random8_glibc2 = &random8_glibc2_type; const gsl_rng_type *gsl_rng_random32_glibc2 = &random32_glibc2_type; const gsl_rng_type *gsl_rng_random64_glibc2 = &random64_glibc2_type; const gsl_rng_type *gsl_rng_random128_glibc2 = &random128_glibc2_type; const gsl_rng_type *gsl_rng_random256_glibc2 = &random256_glibc2_type; const gsl_rng_type *gsl_rng_random_bsd = &random_bsd_type; const gsl_rng_type *gsl_rng_random8_bsd = &random8_bsd_type; const gsl_rng_type *gsl_rng_random32_bsd = &random32_bsd_type; const gsl_rng_type *gsl_rng_random64_bsd = &random64_bsd_type; const gsl_rng_type *gsl_rng_random128_bsd = &random128_bsd_type; const gsl_rng_type *gsl_rng_random256_bsd = &random256_bsd_type; sources_5316/external/gsl/gsl_rng__ran2.c0000664000176700017670000000676511723710247017236 0ustar paulpaul/* rng/ran2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is an implementation of the algorithm used in Numerical Recipe's ran2 generator. It is a L'Ecuyer combined recursive generator with a 32-element shuffle-box. As far as I can tell, in general the effects of adding a shuffle box cannot be proven theoretically, so the period of this generator is unknown. The period of the underlying combined generator is O(2^60). */ static inline unsigned long int ran2_get (void *vstate); static double ran2_get_double (void *vstate); static void ran2_set (void *state, unsigned long int s); static const long int m1 = 2147483563, a1 = 40014, q1 = 53668, r1 = 12211; static const long int m2 = 2147483399, a2 = 40692, q2 = 52774, r2 = 3791; #define N_SHUFFLE 32 #define N_DIV (1 + 2147483562/N_SHUFFLE) typedef struct { unsigned long int x; unsigned long int y; unsigned long int n; unsigned long int shuffle[N_SHUFFLE]; } ran2_state_t; static inline unsigned long int ran2_get (void *vstate) { ran2_state_t *state = (ran2_state_t *) vstate; const unsigned long int x = state->x; const unsigned long int y = state->y; long int h1 = x / q1; long int t1 = a1 * (x - h1 * q1) - h1 * r1; long int h2 = y / q2; long int t2 = a2 * (y - h2 * q2) - h2 * r2; if (t1 < 0) t1 += m1; if (t2 < 0) t2 += m2; state->x = t1; state->y = t2; { unsigned long int j = state->n / N_DIV; long int delta = state->shuffle[j] - t2; if (delta < 1) delta += m1 - 1; state->n = delta; state->shuffle[j] = t1; } return state->n; } static double ran2_get_double (void *vstate) { float x_max = 1 - 1.2e-7f ; /* Numerical Recipes version of 1-FLT_EPS */ float x = ran2_get (vstate) / 2147483563.0f ; if (x > x_max) return x_max ; return x ; } static void ran2_set (void *vstate, unsigned long int s) { ran2_state_t *state = (ran2_state_t *) vstate; int i; if (s == 0) s = 1; /* default seed is 1 */ state->y = s; for (i = 0; i < 8; i++) { long int h = s / q1; long int t = a1 * (s - h * q1) - h * r1; if (t < 0) t += m1; s = t; } for (i = N_SHUFFLE - 1; i >= 0; i--) { long int h = s / q1; long int t = a1 * (s - h * q1) - h * r1; if (t < 0) t += m1; s = t; state->shuffle[i] = s; } state->x = s; state->n = s; return; } static const gsl_rng_type ran2_type = {"ran2", /* name */ 2147483562, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (ran2_state_t), &ran2_set, &ran2_get, &ran2_get_double}; const gsl_rng_type *gsl_rng_ran2 = &ran2_type; sources_5316/external/gsl/gsl_randist__binomial_tpe.c0000664000176700017670000003116611723710247021705 0ustar paulpaul/* randist/binomial_tpe.c * * Copyright (C) 1996, 2003, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" #include "gsl_pow_int.h" #include "gsl_sf_gamma.h" /* The binomial distribution has the form, f(x) = n!/(x!(n-x)!) * p^x (1-p)^(n-x) for integer 0 <= x <= n = 0 otherwise This implementation follows the public domain ranlib function "ignbin", the bulk of which is the BTPE (Binomial Triangle Parallelogram Exponential) algorithm introduced in Kachitvichyanukul and Schmeiser[1]. It has been translated to use modern C coding standards. If n is small and/or p is near 0 or near 1 (specifically, if n*min(p,1-p) < SMALL_MEAN), then a different algorithm, called BINV, is used which has an average runtime that scales linearly with n*min(p,1-p). But for larger problems, the BTPE algorithm takes the form of two functions b(x) and t(x) -- "bottom" and "top" -- for which b(x) < f(x)/f(M) < t(x), with M = floor(n*p+p). b(x) defines a triangular region, and t(x) includes a parallelogram and two tails. Details (including a nice drawing) are in the paper. [1] Kachitvichyanukul, V. and Schmeiser, B. W. Binomial Random Variate Generation. Communications of the ACM, 31, 2 (February, 1988) 216. Note, Bruce Schmeiser (personal communication) points out that if you want very fast binomial deviates, and you are happy with approximate results, and/or n and n*p are both large, then you can just use gaussian estimates: mean=n*p, variance=n*p*(1-p). This implementation by James Theiler, April 2003, after obtaining permission -- and some good advice -- from Drs. Kachitvichyanukul and Schmeiser to use their code as a starting point, and then doing a little bit of tweaking. Additional polishing for GSL coding standards by Brian Gough. */ #define SMALL_MEAN 14 /* If n*p < SMALL_MEAN then use BINV algorithm. The ranlib implementation used cutoff=30; but on my computer 14 works better */ #define BINV_CUTOFF 110 /* In BINV, do not permit ix too large */ #define FAR_FROM_MEAN 20 /* If ix-n*p is larger than this, then use the "squeeze" algorithm. Ranlib used 20, and this seems to be the best choice on my machine as well */ #define LNFACT(x) gsl_sf_lnfact(x) inline static double Stirling (double y1) { double y2 = y1 * y1; double s = (13860.0 - (462.0 - (132.0 - (99.0 - 140.0 / y2) / y2) / y2) / y2) / y1 / 166320.0; return s; } unsigned int gsl_ran_binomial_tpe (const gsl_rng * rng, double p, unsigned int n) { return gsl_ran_binomial (rng, p, n); } unsigned int gsl_ran_binomial (const gsl_rng * rng, double p, unsigned int n) { int ix; /* return value */ int flipped = 0; double q, s, np; if (n == 0) return 0; if (p > 0.5) { p = 1.0 - p; /* work with small p */ flipped = 1; } q = 1 - p; s = p / q; np = n * p; /* Inverse cdf logic for small mean (BINV in K+S) */ if (np < SMALL_MEAN) { double f0 = gsl_pow_int (q, n); /* f(x), starting with x=0 */ while (1) { /* This while(1) loop will almost certainly only loop once; but * if u=1 to within a few epsilons of machine precision, then it * is possible for roundoff to prevent the main loop over ix to * achieve its proper value. following the ranlib implementation, * we introduce a check for that situation, and when it occurs, * we just try again. */ double f = f0; double u = gsl_rng_uniform (rng); for (ix = 0; ix <= BINV_CUTOFF; ++ix) { if (u < f) goto Finish; u -= f; /* Use recursion f(x+1) = f(x)*[(n-x)/(x+1)]*[p/(1-p)] */ f *= s * (n - ix) / (ix + 1); } /* It should be the case that the 'goto Finish' was encountered * before this point was ever reached. But if we have reached * this point, then roundoff has prevented u from decreasing * all the way to zero. This can happen only if the initial u * was very nearly equal to 1, which is a rare situation. In * that rare situation, we just try again. * * Note, following the ranlib implementation, we loop ix only to * a hardcoded value of SMALL_MEAN_LARGE_N=110; we could have * looped to n, and 99.99...% of the time it won't matter. This * choice, I think is a little more robust against the rare * roundoff error. If n>LARGE_N, then it is technically * possible for ix>LARGE_N, but it is astronomically rare, and * if ix is that large, it is more likely due to roundoff than * probability, so better to nip it at LARGE_N than to take a * chance that roundoff will somehow conspire to produce an even * larger (and more improbable) ix. If n= SMALL_MEAN, we invoke the BTPE algorithm */ int k; double ffm = np + p; /* ffm = n*p+p */ int m = (int) ffm; /* m = int floor[n*p+p] */ double fm = m; /* fm = double m; */ double xm = fm + 0.5; /* xm = half integer mean (tip of triangle) */ double npq = np * q; /* npq = n*p*q */ /* Compute cumulative area of tri, para, exp tails */ /* p1: radius of triangle region; since height=1, also: area of region */ /* p2: p1 + area of parallelogram region */ /* p3: p2 + area of left tail */ /* p4: p3 + area of right tail */ /* pi/p4: probability of i'th area (i=1,2,3,4) */ /* Note: magic numbers 2.195, 4.6, 0.134, 20.5, 15.3 */ /* These magic numbers are not adjustable...at least not easily! */ double p1 = floor (2.195 * sqrt (npq) - 4.6 * q) + 0.5; /* xl, xr: left and right edges of triangle */ double xl = xm - p1; double xr = xm + p1; /* Parameter of exponential tails */ /* Left tail: t(x) = c*exp(-lambda_l*[xl - (x+0.5)]) */ /* Right tail: t(x) = c*exp(-lambda_r*[(x+0.5) - xr]) */ double c = 0.134 + 20.5 / (15.3 + fm); double p2 = p1 * (1.0 + c + c); double al = (ffm - xl) / (ffm - xl * p); double lambda_l = al * (1.0 + 0.5 * al); double ar = (xr - ffm) / (xr * q); double lambda_r = ar * (1.0 + 0.5 * ar); double p3 = p2 + c / lambda_l; double p4 = p3 + c / lambda_r; double var, accept; double u, v; /* random variates */ TryAgain: /* generate random variates, u specifies which region: Tri, Par, Tail */ u = gsl_rng_uniform (rng) * p4; v = gsl_rng_uniform (rng); if (u <= p1) { /* Triangular region */ ix = (int) (xm - p1 * v + u); goto Finish; } else if (u <= p2) { /* Parallelogram region */ double x = xl + (u - p1) / c; v = v * c + 1.0 - fabs (x - xm) / p1; if (v > 1.0 || v <= 0.0) goto TryAgain; ix = (int) x; } else if (u <= p3) { /* Left tail */ ix = (int) (xl + log (v) / lambda_l); if (ix < 0) goto TryAgain; v *= ((u - p2) * lambda_l); } else { /* Right tail */ ix = (int) (xr - log (v) / lambda_r); if (ix > (double) n) goto TryAgain; v *= ((u - p3) * lambda_r); } /* At this point, the goal is to test whether v <= f(x)/f(m) * * v <= f(x)/f(m) = (m!(n-m)! / (x!(n-x)!)) * (p/q)^{x-m} * */ /* Here is a direct test using logarithms. It is a little * slower than the various "squeezing" computations below, but * if things are working, it should give exactly the same answer * (given the same random number seed). */ #ifdef DIRECT var = log (v); accept = LNFACT (m) + LNFACT (n - m) - LNFACT (ix) - LNFACT (n - ix) + (ix - m) * log (p / q); #else /* SQUEEZE METHOD */ /* More efficient determination of whether v < f(x)/f(M) */ k = abs (ix - m); if (k <= FAR_FROM_MEAN) { /* * If ix near m (ie, |ix-m| ix) { int i; for (i = ix + 1; i <= m; i++) { f /= (g / i - s); } } accept = f; } else { /* If ix is far from the mean m: k=ABS(ix-m) large */ var = log (v); if (k < npq / 2 - 1) { /* "Squeeze" using upper and lower bounds on * log(f(x)) The squeeze condition was derived * under the condition k < npq/2-1 */ double amaxp = k / npq * ((k * (k / 3.0 + 0.625) + (1.0 / 6.0)) / npq + 0.5); double ynorm = -(k * k / (2.0 * npq)); if (var < ynorm - amaxp) goto Finish; if (var > ynorm + amaxp) goto TryAgain; } /* Now, again: do the test log(v) vs. log f(x)/f(M) */ #if USE_EXACT /* This is equivalent to the above, but is a little (~20%) slower */ /* There are five log's vs three above, maybe that's it? */ accept = LNFACT (m) + LNFACT (n - m) - LNFACT (ix) - LNFACT (n - ix) + (ix - m) * log (p / q); #else /* USE STIRLING */ /* The "#define Stirling" above corresponds to the first five * terms in asymptoic formula for * log Gamma (y) - (y-0.5)log(y) + y - 0.5 log(2*pi); * See Abramowitz and Stegun, eq 6.1.40 */ /* Note below: two Stirling's are added, and two are * subtracted. In both K+S, and in the ranlib * implementation, all four are added. I (jt) believe that * is a mistake -- this has been confirmed by personal * correspondence w/ Dr. Kachitvichyanukul. Note, however, * the corrections are so small, that I couldn't find an * example where it made a difference that could be * observed, let alone tested. In fact, define'ing Stirling * to be zero gave identical results!! In practice, alv is * O(1), ranging 0 to -10 or so, while the Stirling * correction is typically O(10^{-5}) ...setting the * correction to zero gives about a 2% performance boost; * might as well keep it just to be pendantic. */ { double x1 = ix + 1.0; double w1 = n - ix + 1.0; double f1 = fm + 1.0; double z1 = n + 1.0 - fm; accept = xm * log (f1 / x1) + (n - m + 0.5) * log (z1 / w1) + (ix - m) * log (w1 * p / (x1 * q)) + Stirling (f1) + Stirling (z1) - Stirling (x1) - Stirling (w1); } #endif #endif } if (var <= accept) { goto Finish; } else { goto TryAgain; } } Finish: return (flipped) ? (n - ix) : (unsigned int)ix; } sources_5316/external/gsl/gsl_matrix_double.h0000664000176700017670000002461311705263724020225 0ustar paulpaul/* matrix/gsl_matrix_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_DOUBLE_H__ #define __GSL_MATRIX_DOUBLE_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; double * data; gsl_block * block; int owner; } gsl_matrix; typedef struct { gsl_matrix matrix; } _gsl_matrix_view; typedef _gsl_matrix_view gsl_matrix_view; typedef struct { gsl_matrix matrix; } _gsl_matrix_const_view; typedef const _gsl_matrix_const_view gsl_matrix_const_view; /* Allocation */ gsl_matrix * gsl_matrix_alloc (const size_t n1, const size_t n2); gsl_matrix * gsl_matrix_calloc (const size_t n1, const size_t n2); gsl_matrix * gsl_matrix_alloc_from_block (gsl_block * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix * gsl_matrix_alloc_from_matrix (gsl_matrix * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector * gsl_vector_alloc_row_from_matrix (gsl_matrix * m, const size_t i); gsl_vector * gsl_vector_alloc_col_from_matrix (gsl_matrix * m, const size_t j); void gsl_matrix_free (gsl_matrix * m); /* Views */ _gsl_matrix_view gsl_matrix_submatrix (gsl_matrix * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_view gsl_matrix_row (gsl_matrix * m, const size_t i); _gsl_vector_view gsl_matrix_column (gsl_matrix * m, const size_t j); _gsl_vector_view gsl_matrix_diagonal (gsl_matrix * m); _gsl_vector_view gsl_matrix_subdiagonal (gsl_matrix * m, const size_t k); _gsl_vector_view gsl_matrix_superdiagonal (gsl_matrix * m, const size_t k); _gsl_vector_view gsl_matrix_subrow (gsl_matrix * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_view gsl_matrix_subcolumn (gsl_matrix * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_view gsl_matrix_view_array (double * base, const size_t n1, const size_t n2); _gsl_matrix_view gsl_matrix_view_array_with_tda (double * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_view gsl_matrix_view_vector (gsl_vector * v, const size_t n1, const size_t n2); _gsl_matrix_view gsl_matrix_view_vector_with_tda (gsl_vector * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_const_view gsl_matrix_const_submatrix (const gsl_matrix * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_const_view gsl_matrix_const_row (const gsl_matrix * m, const size_t i); _gsl_vector_const_view gsl_matrix_const_column (const gsl_matrix * m, const size_t j); _gsl_vector_const_view gsl_matrix_const_diagonal (const gsl_matrix * m); _gsl_vector_const_view gsl_matrix_const_subdiagonal (const gsl_matrix * m, const size_t k); _gsl_vector_const_view gsl_matrix_const_superdiagonal (const gsl_matrix * m, const size_t k); _gsl_vector_const_view gsl_matrix_const_subrow (const gsl_matrix * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_const_view gsl_matrix_const_subcolumn (const gsl_matrix * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_const_view gsl_matrix_const_view_array (const double * base, const size_t n1, const size_t n2); _gsl_matrix_const_view gsl_matrix_const_view_array_with_tda (const double * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_const_view gsl_matrix_const_view_vector (const gsl_vector * v, const size_t n1, const size_t n2); _gsl_matrix_const_view gsl_matrix_const_view_vector_with_tda (const gsl_vector * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ double gsl_matrix_get(const gsl_matrix * m, const size_t i, const size_t j); void gsl_matrix_set(gsl_matrix * m, const size_t i, const size_t j, const double x); double * gsl_matrix_ptr(gsl_matrix * m, const size_t i, const size_t j); const double * gsl_matrix_const_ptr(const gsl_matrix * m, const size_t i, const size_t j); void gsl_matrix_set_zero (gsl_matrix * m); void gsl_matrix_set_identity (gsl_matrix * m); void gsl_matrix_set_all (gsl_matrix * m, double x); int gsl_matrix_fread (FILE * stream, gsl_matrix * m) ; int gsl_matrix_fwrite (FILE * stream, const gsl_matrix * m) ; int gsl_matrix_fscanf (FILE * stream, gsl_matrix * m); int gsl_matrix_fprintf (FILE * stream, const gsl_matrix * m, const char * format); int gsl_matrix_memcpy(gsl_matrix * dest, const gsl_matrix * src); int gsl_matrix_swap(gsl_matrix * m1, gsl_matrix * m2); int gsl_matrix_swap_rows(gsl_matrix * m, const size_t i, const size_t j); int gsl_matrix_swap_columns(gsl_matrix * m, const size_t i, const size_t j); int gsl_matrix_swap_rowcol(gsl_matrix * m, const size_t i, const size_t j); int gsl_matrix_transpose (gsl_matrix * m); int gsl_matrix_transpose_memcpy (gsl_matrix * dest, const gsl_matrix * src); double gsl_matrix_max (const gsl_matrix * m); double gsl_matrix_min (const gsl_matrix * m); void gsl_matrix_minmax (const gsl_matrix * m, double * min_out, double * max_out); void gsl_matrix_max_index (const gsl_matrix * m, size_t * imax, size_t *jmax); void gsl_matrix_min_index (const gsl_matrix * m, size_t * imin, size_t *jmin); void gsl_matrix_minmax_index (const gsl_matrix * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_isnull (const gsl_matrix * m); int gsl_matrix_ispos (const gsl_matrix * m); int gsl_matrix_isneg (const gsl_matrix * m); int gsl_matrix_isnonneg (const gsl_matrix * m); int gsl_matrix_add (gsl_matrix * a, const gsl_matrix * b); int gsl_matrix_sub (gsl_matrix * a, const gsl_matrix * b); int gsl_matrix_mul_elements (gsl_matrix * a, const gsl_matrix * b); int gsl_matrix_div_elements (gsl_matrix * a, const gsl_matrix * b); int gsl_matrix_scale (gsl_matrix * a, const double x); int gsl_matrix_add_constant (gsl_matrix * a, const double x); int gsl_matrix_add_diagonal (gsl_matrix * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_get_row(gsl_vector * v, const gsl_matrix * m, const size_t i); int gsl_matrix_get_col(gsl_vector * v, const gsl_matrix * m, const size_t j); int gsl_matrix_set_row(gsl_matrix * m, const size_t i, const gsl_vector * v); int gsl_matrix_set_col(gsl_matrix * m, const size_t j, const gsl_vector * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline double gsl_matrix_get(const gsl_matrix * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_set(gsl_matrix * m, const size_t i, const size_t j, const double x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline double * gsl_matrix_ptr(gsl_matrix * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (double *) (m->data + (i * m->tda + j)) ; } extern inline const double * gsl_matrix_const_ptr(const gsl_matrix * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const double *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_DOUBLE_H__ */ sources_5316/external/gsl/gsl_randist__tdist.c0000664000176700017670000000416511723710247020371 0ustar paulpaul/* randist/tdist.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_sf_gamma.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The t-distribution has the form p(x) dx = (Gamma((nu + 1)/2)/(sqrt(pi nu) Gamma(nu/2)) * (1 + (x^2)/nu)^-((nu + 1)/2) dx The method used here is the one described in Knuth */ double gsl_ran_tdist (const gsl_rng * r, const double nu) { if (nu <= 2) { double Y1 = gsl_ran_ugaussian (r); double Y2 = gsl_ran_chisq (r, nu); double t = Y1 / sqrt (Y2 / nu); return t; } else { double Y1, Y2, Z, t; do { Y1 = gsl_ran_ugaussian (r); Y2 = gsl_ran_exponential (r, 1 / (nu/2 - 1)); Z = Y1 * Y1 / (nu - 2); } while (1 - Z < 0 || exp (-Y2 - Z) > (1 - Z)); /* Note that there is a typo in Knuth's formula, the line below is taken from the original paper of Marsaglia, Mathematics of Computation, 34 (1980), p 234-256 */ t = Y1 / sqrt ((1 - 2 / nu) * (1 - Z)); return t; } } double gsl_ran_tdist_pdf (const double x, const double nu) { double p; double lg1 = gsl_sf_lngamma (nu / 2); double lg2 = gsl_sf_lngamma ((nu + 1) / 2); p = ((exp (lg2 - lg1) / sqrt (M_PI * nu)) * pow ((1 + x * x / nu), -(nu + 1) / 2)); return p; } sources_5316/external/gsl/gsl_poly__zsolve_init.c0000664000176700017670000000342611723710247021125 0ustar paulpaul/* poly/zsolve_init.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_poly.h" #include "gsl_errno.h" gsl_poly_complex_workspace * gsl_poly_complex_workspace_alloc (size_t n) { size_t nc ; gsl_poly_complex_workspace * w ; if (n == 0) { GSL_ERROR_VAL ("matrix size n must be positive integer", GSL_EDOM, 0); } w = (gsl_poly_complex_workspace *) malloc (sizeof(gsl_poly_complex_workspace)); if (w == 0) { GSL_ERROR_VAL ("failed to allocate space for struct", GSL_ENOMEM, 0); } nc = n - 1; w->nc = nc; w->matrix = (double *) malloc (nc * nc * sizeof(double)); if (w->matrix == 0) { free (w) ; /* error in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for workspace matrix", GSL_ENOMEM, 0); } return w ; } void gsl_poly_complex_workspace_free (gsl_poly_complex_workspace * w) { free(w->matrix) ; free(w); } sources_5316/external/gsl/gsl_cblas__sdot.c0000664000176700017670000000051511723710247017626 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" float cblas_sdot (const int N, const float *X, const int incX, const float *Y, const int incY) { #define INIT_VAL 0.0 #define ACC_TYPE float #define BASE float #include "gsl_cblas__source_dot_r.h" #undef ACC_TYPE #undef BASE #undef INIT_VAL } sources_5316/external/gsl/gsl_linalg__householder.c0000664000176700017670000001736611723710247021374 0ustar paulpaul/* linalg/householder.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_linalg.h" double gsl_linalg_householder_transform (gsl_vector * v) { /* replace v[0:n-1] with a householder vector (v[0:n-1]) and coefficient tau that annihilate v[1:n-1] */ const size_t n = v->size ; if (n == 1) { return 0.0; /* tau = 0 */ } else { double alpha, beta, tau ; gsl_vector_view x = gsl_vector_subvector (v, 1, n - 1) ; double xnorm = gsl_blas_dnrm2 (&x.vector); if (xnorm == 0) { return 0.0; /* tau = 0 */ } alpha = gsl_vector_get (v, 0) ; beta = - (alpha >= 0.0 ? +1.0 : -1.0) * hypot(alpha, xnorm) ; tau = (beta - alpha) / beta ; gsl_blas_dscal (1.0 / (alpha - beta), &x.vector); gsl_vector_set (v, 0, beta) ; return tau; } } int gsl_linalg_householder_hm (double tau, const gsl_vector * v, gsl_matrix * A) { /* applies a householder transformation v,tau to matrix m */ if (tau == 0.0) { return GSL_SUCCESS; } #ifdef USE_BLAS { gsl_vector_const_view v1 = gsl_vector_const_subvector (v, 1, v->size - 1); gsl_matrix_view A1 = gsl_matrix_submatrix (A, 1, 0, A->size1 - 1, A->size2); size_t j; for (j = 0; j < A->size2; j++) { double wj = 0.0; gsl_vector_view A1j = gsl_matrix_column(&A1.matrix, j); gsl_blas_ddot (&A1j.vector, &v1.vector, &wj); wj += gsl_matrix_get(A,0,j); { double A0j = gsl_matrix_get (A, 0, j); gsl_matrix_set (A, 0, j, A0j - tau * wj); } gsl_blas_daxpy (-tau * wj, &v1.vector, &A1j.vector); } } #else { size_t i, j; for (j = 0; j < A->size2; j++) { /* Compute wj = Akj vk */ double wj = gsl_matrix_get(A,0,j); for (i = 1; i < A->size1; i++) /* note, computed for v(0) = 1 above */ { wj += gsl_matrix_get(A,i,j) * gsl_vector_get(v,i); } /* Aij = Aij - tau vi wj */ /* i = 0 */ { double A0j = gsl_matrix_get (A, 0, j); gsl_matrix_set (A, 0, j, A0j - tau * wj); } /* i = 1 .. M-1 */ for (i = 1; i < A->size1; i++) { double Aij = gsl_matrix_get (A, i, j); double vi = gsl_vector_get (v, i); gsl_matrix_set (A, i, j, Aij - tau * vi * wj); } } } #endif return GSL_SUCCESS; } int gsl_linalg_householder_mh (double tau, const gsl_vector * v, gsl_matrix * A) { /* applies a householder transformation v,tau to matrix m from the right hand side in order to zero out rows */ if (tau == 0) return GSL_SUCCESS; /* A = A - tau w v' */ #ifdef USE_BLAS { gsl_vector_const_view v1 = gsl_vector_const_subvector (v, 1, v->size - 1); gsl_matrix_view A1 = gsl_matrix_submatrix (A, 0, 1, A->size1, A->size2-1); size_t i; for (i = 0; i < A->size1; i++) { double wi = 0.0; gsl_vector_view A1i = gsl_matrix_row(&A1.matrix, i); gsl_blas_ddot (&A1i.vector, &v1.vector, &wi); wi += gsl_matrix_get(A,i,0); { double Ai0 = gsl_matrix_get (A, i, 0); gsl_matrix_set (A, i, 0, Ai0 - tau * wi); } gsl_blas_daxpy(-tau * wi, &v1.vector, &A1i.vector); } } #else { size_t i, j; for (i = 0; i < A->size1; i++) { double wi = gsl_matrix_get(A,i,0); for (j = 1; j < A->size2; j++) /* note, computed for v(0) = 1 above */ { wi += gsl_matrix_get(A,i,j) * gsl_vector_get(v,j); } /* j = 0 */ { double Ai0 = gsl_matrix_get (A, i, 0); gsl_matrix_set (A, i, 0, Ai0 - tau * wi); } /* j = 1 .. N-1 */ for (j = 1; j < A->size2; j++) { double vj = gsl_vector_get (v, j); double Aij = gsl_matrix_get (A, i, j); gsl_matrix_set (A, i, j, Aij - tau * wi * vj); } } } #endif return GSL_SUCCESS; } int gsl_linalg_householder_hv (double tau, const gsl_vector * v, gsl_vector * w) { /* applies a householder transformation v to vector w */ const size_t N = v->size; if (tau == 0) return GSL_SUCCESS ; { /* compute d = v'w */ double d0 = gsl_vector_get(w,0); double d1, d; gsl_vector_const_view v1 = gsl_vector_const_subvector(v, 1, N-1); gsl_vector_view w1 = gsl_vector_subvector(w, 1, N-1); gsl_blas_ddot (&v1.vector, &w1.vector, &d1); d = d0 + d1; /* compute w = w - tau (v) (v'w) */ { double w0 = gsl_vector_get (w,0); gsl_vector_set (w, 0, w0 - tau * d); } gsl_blas_daxpy (-tau * d, &v1.vector, &w1.vector); } return GSL_SUCCESS; } int gsl_linalg_householder_hm1 (double tau, gsl_matrix * A) { /* applies a householder transformation v,tau to a matrix being build up from the identity matrix, using the first column of A as a householder vector */ if (tau == 0) { size_t i,j; gsl_matrix_set (A, 0, 0, 1.0); for (j = 1; j < A->size2; j++) { gsl_matrix_set (A, 0, j, 0.0); } for (i = 1; i < A->size1; i++) { gsl_matrix_set (A, i, 0, 0.0); } return GSL_SUCCESS; } /* w = A' v */ #ifdef USE_BLAS { gsl_matrix_view A1 = gsl_matrix_submatrix (A, 1, 0, A->size1 - 1, A->size2); gsl_vector_view v1 = gsl_matrix_column (&A1.matrix, 0); size_t j; for (j = 1; j < A->size2; j++) { double wj = 0.0; /* A0j * v0 */ gsl_vector_view A1j = gsl_matrix_column(&A1.matrix, j); gsl_blas_ddot (&A1j.vector, &v1.vector, &wj); /* A = A - tau v w' */ gsl_matrix_set (A, 0, j, - tau * wj); gsl_blas_daxpy(-tau*wj, &v1.vector, &A1j.vector); } gsl_blas_dscal(-tau, &v1.vector); gsl_matrix_set (A, 0, 0, 1.0 - tau); } #else { size_t i, j; for (j = 1; j < A->size2; j++) { double wj = 0.0; /* A0j * v0 */ for (i = 1; i < A->size1; i++) { double vi = gsl_matrix_get(A, i, 0); wj += gsl_matrix_get(A,i,j) * vi; } /* A = A - tau v w' */ gsl_matrix_set (A, 0, j, - tau * wj); for (i = 1; i < A->size1; i++) { double vi = gsl_matrix_get (A, i, 0); double Aij = gsl_matrix_get (A, i, j); gsl_matrix_set (A, i, j, Aij - tau * vi * wj); } } for (i = 1; i < A->size1; i++) { double vi = gsl_matrix_get(A, i, 0); gsl_matrix_set(A, i, 0, -tau * vi); } gsl_matrix_set (A, 0, 0, 1.0 - tau); } #endif return GSL_SUCCESS; } sources_5316/external/gsl/gsl_fft__compare_source.c0000664000176700017670000000627411723710247021366 0ustar paulpaul/* fft/compare_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl_fft__compare.h" int FUNCTION(compare_complex,results) (const char *name_a, const BASE a[], const char *name_b, const BASE b[], size_t stride, size_t n, const double allowed_ticks) { size_t i; double ticks, max_ticks = 0; double dr, di; const char *flag; for (i = 0; i < n; i++) { dr = b[2*stride*i] - a[2*stride*i]; di = b[2*stride*i+1] - a[2*stride*i+1]; ticks = (fabs (dr) + fabs (di)) / BASE_EPSILON; if (ticks > max_ticks) { max_ticks = ticks; } } if (max_ticks < allowed_ticks) { return 0; } printf ("\n%s vs %s : max_ticks = %f\n", name_a, name_b, max_ticks); for (i = 0; i < n; i++) { dr = b[2*stride*i] - a[2*stride*i]; di = b[2*stride*i+1] - a[2*stride*i+1]; ticks = (fabs (dr) + fabs (di)) / BASE_EPSILON; if (ticks > 1000) { flag = "***"; } else { flag = ""; } printf ("%15s: %d %.16f %.16f %s\n", name_a, (int)i, a[2*stride*i], a[2*stride*i+1], flag); printf ("%15s: %d %.16f %.16f %e %s\n", name_b, (int)i, b[2*stride*i], b[2*stride*i+1], ticks, flag); } return -1; } int FUNCTION(compare_real,results) (const char *name_a, const BASE a[], const char *name_b, const BASE b[], size_t stride, size_t n, const double allowed_ticks) { size_t i; double ticks, max_ticks = 0; double dr; const char *flag; for (i = 0; i < n; i++) { dr = b[stride*i] - a[stride*i]; ticks = fabs (dr) / BASE_EPSILON; if (ticks > max_ticks) { max_ticks = ticks; } } if (max_ticks < allowed_ticks) { return 0; } printf ("\n%s vs %s : max_ticks = %f\n", name_a, name_b, max_ticks); for (i = 0; i < n; i++) { dr = b[stride*i] - a[stride*i]; ticks = fabs (dr) / BASE_EPSILON; if (ticks > 1000) { flag = "***"; } else { flag = ""; } printf ("%15s: %d %.16f %s\n", name_a, (int)i, a[stride*i], flag); printf ("%15s: %d %.16f %e %s\n", name_b, (int)i, b[stride*i], ticks, flag); } return -1; } sources_5316/external/gsl/gsl_sf_fermi_dirac.h0000664000176700017670000000652111705263724020321 0ustar paulpaul/* specfunc/gsl_sf_fermi_dirac.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_FERMI_DIRAC_H__ #define __GSL_SF_FERMI_DIRAC_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Complete Fermi-Dirac Integrals: * * F_j(x) := 1/Gamma[j+1] Integral[ t^j /(Exp[t-x] + 1), {t,0,Infinity}] * * * Incomplete Fermi-Dirac Integrals: * * F_j(x,b) := 1/Gamma[j+1] Integral[ t^j /(Exp[t-x] + 1), {t,b,Infinity}] */ /* Complete integral F_{-1}(x) = e^x / (1 + e^x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_fermi_dirac_m1_e(const double x, gsl_sf_result * result); double gsl_sf_fermi_dirac_m1(const double x); /* Complete integral F_0(x) = ln(1 + e^x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_fermi_dirac_0_e(const double x, gsl_sf_result * result); double gsl_sf_fermi_dirac_0(const double x); /* Complete integral F_1(x) * * exceptions: GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_fermi_dirac_1_e(const double x, gsl_sf_result * result); double gsl_sf_fermi_dirac_1(const double x); /* Complete integral F_2(x) * * exceptions: GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_fermi_dirac_2_e(const double x, gsl_sf_result * result); double gsl_sf_fermi_dirac_2(const double x); /* Complete integral F_j(x) * for integer j * * exceptions: GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_fermi_dirac_int_e(const int j, const double x, gsl_sf_result * result); double gsl_sf_fermi_dirac_int(const int j, const double x); /* Complete integral F_{-1/2}(x) * * exceptions: GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_fermi_dirac_mhalf_e(const double x, gsl_sf_result * result); double gsl_sf_fermi_dirac_mhalf(const double x); /* Complete integral F_{1/2}(x) * * exceptions: GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_fermi_dirac_half_e(const double x, gsl_sf_result * result); double gsl_sf_fermi_dirac_half(const double x); /* Complete integral F_{3/2}(x) * * exceptions: GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_fermi_dirac_3half_e(const double x, gsl_sf_result * result); double gsl_sf_fermi_dirac_3half(const double x); /* Incomplete integral F_0(x,b) = ln(1 + e^(b-x)) - (b-x) * * exceptions: GSL_EUNDRFLW, GSL_EDOM */ int gsl_sf_fermi_dirac_inc_0_e(const double x, const double b, gsl_sf_result * result); double gsl_sf_fermi_dirac_inc_0(const double x, const double b); __END_DECLS #endif /* __GSL_SF_FERMI_DIRAC_H__ */ sources_5316/external/gsl/gsl_statistics__covariance.c0000664000176700017670000000311111723710247022070 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__covariance_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_cblas__cherk.c0000664000176700017670000000063511723710247017754 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cherk (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const float alpha, const void *A, const int lda, const float beta, void *C, const int ldc) { #define BASE float #include "gsl_cblas__source_herk.h" #undef BASE } sources_5316/external/gsl/gsl_eigen__gensymm.c0000664000176700017670000001236711723710247020347 0ustar paulpaul/* eigen/gensymm.c * * Copyright (C) 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include "gsl__config.h" #include "gsl_eigen.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_blas.h" #include "gsl_vector.h" #include "gsl_matrix.h" /* * This module computes the eigenvalues of a real generalized * symmetric-definite eigensystem A x = \lambda B x, where A and * B are symmetric, and B is positive-definite. */ /* gsl_eigen_gensymm_alloc() Allocate a workspace for solving the generalized symmetric-definite eigenvalue problem. The size of this workspace is O(2n). Inputs: n - size of matrices Return: pointer to workspace */ gsl_eigen_gensymm_workspace * gsl_eigen_gensymm_alloc(const size_t n) { gsl_eigen_gensymm_workspace *w; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = calloc (1, sizeof (gsl_eigen_gensymm_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->size = n; w->symm_workspace_p = gsl_eigen_symm_alloc(n); if (!w->symm_workspace_p) { gsl_eigen_gensymm_free(w); GSL_ERROR_NULL("failed to allocate space for symm workspace", GSL_ENOMEM); } return (w); } /* gsl_eigen_gensymm_alloc() */ /* gsl_eigen_gensymm_free() Free workspace w */ void gsl_eigen_gensymm_free (gsl_eigen_gensymm_workspace * w) { if (w->symm_workspace_p) gsl_eigen_symm_free(w->symm_workspace_p); free(w); } /* gsl_eigen_gensymm_free() */ /* gsl_eigen_gensymm() Solve the generalized symmetric-definite eigenvalue problem A x = \lambda B x for the eigenvalues \lambda. Inputs: A - real symmetric matrix B - real symmetric and positive definite matrix eval - where to store eigenvalues w - workspace Return: success or error */ int gsl_eigen_gensymm (gsl_matrix * A, gsl_matrix * B, gsl_vector * eval, gsl_eigen_gensymm_workspace * w) { const size_t N = A->size1; /* check matrix and vector sizes */ if (N != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if ((N != B->size1) || (N != B->size2)) { GSL_ERROR ("B matrix dimensions must match A", GSL_EBADLEN); } else if (eval->size != N) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (w->size != N) { GSL_ERROR ("matrix size does not match workspace", GSL_EBADLEN); } else { int s; /* compute Cholesky factorization of B */ s = gsl_linalg_cholesky_decomp(B); if (s != GSL_SUCCESS) return s; /* B is not positive definite */ /* transform to standard symmetric eigenvalue problem */ gsl_eigen_gensymm_standardize(A, B); s = gsl_eigen_symm(A, eval, w->symm_workspace_p); return s; } } /* gsl_eigen_gensymm() */ /* gsl_eigen_gensymm_standardize() Reduce the generalized symmetric-definite eigenproblem to the standard symmetric eigenproblem by computing C = L^{-1} A L^{-t} where L L^t is the Cholesky decomposition of B Inputs: A - (input/output) real symmetric matrix B - real symmetric, positive definite matrix in Cholesky form Return: success Notes: A is overwritten by L^{-1} A L^{-t} */ int gsl_eigen_gensymm_standardize(gsl_matrix *A, const gsl_matrix *B) { const size_t N = A->size1; size_t i; double a, b, c; for (i = 0; i < N; ++i) { /* update lower triangle of A(i:n, i:n) */ a = gsl_matrix_get(A, i, i); b = gsl_matrix_get(B, i, i); a /= b * b; gsl_matrix_set(A, i, i, a); if (i < N - 1) { gsl_vector_view ai = gsl_matrix_subcolumn(A, i, i + 1, N - i - 1); gsl_matrix_view ma = gsl_matrix_submatrix(A, i + 1, i + 1, N - i - 1, N - i - 1); gsl_vector_const_view bi = gsl_matrix_const_subcolumn(B, i, i + 1, N - i - 1); gsl_matrix_const_view mb = gsl_matrix_const_submatrix(B, i + 1, i + 1, N - i - 1, N - i - 1); gsl_blas_dscal(1.0 / b, &ai.vector); c = -0.5 * a; gsl_blas_daxpy(c, &bi.vector, &ai.vector); gsl_blas_dsyr2(CblasLower, -1.0, &ai.vector, &bi.vector, &ma.matrix); gsl_blas_daxpy(c, &bi.vector, &ai.vector); gsl_blas_dtrsv(CblasLower, CblasNoTrans, CblasNonUnit, &mb.matrix, &ai.vector); } } return GSL_SUCCESS; } /* gsl_eigen_gensymm_standardize() */ sources_5316/external/gsl/gsl_cblas__source_her2k.h0000664000176700017670000002443411705263724021266 0ustar paulpaul/* blas/source_her2k_c.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; int uplo, trans; const BASE alpha_real = CONST_REAL0(alpha); BASE alpha_imag = CONST_IMAG0(alpha); if (beta == 1.0 && ((alpha_real == 0.0 && alpha_imag == 0.0) || K == 0)) return; if (Order == CblasRowMajor) { uplo = Uplo; trans = Trans; } else { uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; trans = (Trans == CblasNoTrans) ? CblasConjTrans : CblasNoTrans; alpha_imag *= -1; /* conjugate alpha */ } /* form C := beta*C */ if (beta == 0.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } } else if (beta != 1.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { REAL(C, ldc * i + i) *= beta; IMAG(C, ldc * i + i) = 0.0; for (j = i + 1; j < N; j++) { REAL(C, ldc * i + j) *= beta; IMAG(C, ldc * i + j) *= beta; } } } else { for (i = 0; i < N; i++) { for (j = 0; j < i; j++) { REAL(C, ldc * i + j) *= beta; IMAG(C, ldc * i + j) *= beta; } REAL(C, ldc * i + i) *= beta; IMAG(C, ldc * i + i) = 0.0; } } } else { for (i = 0; i < N; i++) { IMAG(C, ldc * i + i) = 0.0; } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; if (uplo == CblasUpper && trans == CblasNoTrans) { for (i = 0; i < N; i++) { /* Cii += alpha Aik conj(Bik) + conj(alpha) Bik conj(Aik) */ { BASE temp_real = 0.0; /* BASE temp_imag = 0.0; */ for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); /* temp1 = alpha * Aik */ const BASE temp1_real = alpha_real * Aik_real - alpha_imag * Aik_imag; const BASE temp1_imag = alpha_real * Aik_imag + alpha_imag * Aik_real; const BASE Bik_real = CONST_REAL(B, i * ldb + k); const BASE Bik_imag = CONST_IMAG(B, i * ldb + k); temp_real += temp1_real * Bik_real + temp1_imag * Bik_imag; } REAL(C, i * ldc + i) += 2 * temp_real; IMAG(C, i * ldc + i) = 0.0; } /* Cij += alpha Aik conj(Bjk) + conj(alpha) Bik conj(Ajk) */ for (j = i + 1; j < N; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); /* temp1 = alpha * Aik */ const BASE temp1_real = alpha_real * Aik_real - alpha_imag * Aik_imag; const BASE temp1_imag = alpha_real * Aik_imag + alpha_imag * Aik_real; const BASE Bik_real = CONST_REAL(B, i * ldb + k); const BASE Bik_imag = CONST_IMAG(B, i * ldb + k); const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); /* temp2 = alpha * Ajk */ const BASE temp2_real = alpha_real * Ajk_real - alpha_imag * Ajk_imag; const BASE temp2_imag = alpha_real * Ajk_imag + alpha_imag * Ajk_real; const BASE Bjk_real = CONST_REAL(B, j * ldb + k); const BASE Bjk_imag = CONST_IMAG(B, j * ldb + k); /* Cij += alpha * Aik * conj(Bjk) + conj(alpha) * Bik * conj(Ajk) */ temp_real += ((temp1_real * Bjk_real + temp1_imag * Bjk_imag) + (Bik_real * temp2_real + Bik_imag * temp2_imag)); temp_imag += ((temp1_real * (-Bjk_imag) + temp1_imag * Bjk_real) + (Bik_real * (-temp2_imag) + Bik_imag * temp2_real)); } REAL(C, i * ldc + j) += temp_real; IMAG(C, i * ldc + j) += temp_imag; } } } else if (uplo == CblasUpper && trans == CblasConjTrans) { for (k = 0; k < K; k++) { for (i = 0; i < N; i++) { BASE Aki_real = CONST_REAL(A, k * lda + i); BASE Aki_imag = CONST_IMAG(A, k * lda + i); BASE Bki_real = CONST_REAL(B, k * ldb + i); BASE Bki_imag = CONST_IMAG(B, k * ldb + i); /* temp1 = alpha * conj(Aki) */ BASE temp1_real = alpha_real * Aki_real - alpha_imag * (-Aki_imag); BASE temp1_imag = alpha_real * (-Aki_imag) + alpha_imag * Aki_real; /* temp2 = conj(alpha) * conj(Bki) */ BASE temp2_real = alpha_real * Bki_real - alpha_imag * Bki_imag; BASE temp2_imag = -(alpha_real * Bki_imag + alpha_imag * Bki_real); /* Cii += alpha * conj(Aki) * Bki + conj(alpha) * conj(Bki) * Aki */ { REAL(C, i * lda + i) += 2 * (temp1_real * Bki_real - temp1_imag * Bki_imag); IMAG(C, i * lda + i) = 0.0; } for (j = i + 1; j < N; j++) { BASE Akj_real = CONST_REAL(A, k * lda + j); BASE Akj_imag = CONST_IMAG(A, k * lda + j); BASE Bkj_real = CONST_REAL(B, k * ldb + j); BASE Bkj_imag = CONST_IMAG(B, k * ldb + j); /* Cij += alpha * conj(Aki) * Bkj + conj(alpha) * conj(Bki) * Akj */ REAL(C, i * lda + j) += (temp1_real * Bkj_real - temp1_imag * Bkj_imag) + (temp2_real * Akj_real - temp2_imag * Akj_imag); IMAG(C, i * lda + j) += (temp1_real * Bkj_imag + temp1_imag * Bkj_real) + (temp2_real * Akj_imag + temp2_imag * Akj_real); } } } } else if (uplo == CblasLower && trans == CblasNoTrans) { for (i = 0; i < N; i++) { /* Cij += alpha Aik conj(Bjk) + conj(alpha) Bik conj(Ajk) */ for (j = 0; j < i; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); /* temp1 = alpha * Aik */ const BASE temp1_real = alpha_real * Aik_real - alpha_imag * Aik_imag; const BASE temp1_imag = alpha_real * Aik_imag + alpha_imag * Aik_real; const BASE Bik_real = CONST_REAL(B, i * ldb + k); const BASE Bik_imag = CONST_IMAG(B, i * ldb + k); const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); /* temp2 = alpha * Ajk */ const BASE temp2_real = alpha_real * Ajk_real - alpha_imag * Ajk_imag; const BASE temp2_imag = alpha_real * Ajk_imag + alpha_imag * Ajk_real; const BASE Bjk_real = CONST_REAL(B, j * ldb + k); const BASE Bjk_imag = CONST_IMAG(B, j * ldb + k); /* Cij += alpha * Aik * conj(Bjk) + conj(alpha) * Bik * conj(Ajk) */ temp_real += ((temp1_real * Bjk_real + temp1_imag * Bjk_imag) + (Bik_real * temp2_real + Bik_imag * temp2_imag)); temp_imag += ((temp1_real * (-Bjk_imag) + temp1_imag * Bjk_real) + (Bik_real * (-temp2_imag) + Bik_imag * temp2_real)); } REAL(C, i * ldc + j) += temp_real; IMAG(C, i * ldc + j) += temp_imag; } /* Cii += alpha Aik conj(Bik) + conj(alpha) Bik conj(Aik) */ { BASE temp_real = 0.0; /* BASE temp_imag = 0.0; */ for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); /* temp1 = alpha * Aik */ const BASE temp1_real = alpha_real * Aik_real - alpha_imag * Aik_imag; const BASE temp1_imag = alpha_real * Aik_imag + alpha_imag * Aik_real; const BASE Bik_real = CONST_REAL(B, i * ldb + k); const BASE Bik_imag = CONST_IMAG(B, i * ldb + k); temp_real += temp1_real * Bik_real + temp1_imag * Bik_imag; } REAL(C, i * ldc + i) += 2 * temp_real; IMAG(C, i * ldc + i) = 0.0; } } } else if (uplo == CblasLower && trans == CblasConjTrans) { for (k = 0; k < K; k++) { for (i = 0; i < N; i++) { BASE Aki_real = CONST_REAL(A, k * lda + i); BASE Aki_imag = CONST_IMAG(A, k * lda + i); BASE Bki_real = CONST_REAL(B, k * ldb + i); BASE Bki_imag = CONST_IMAG(B, k * ldb + i); /* temp1 = alpha * conj(Aki) */ BASE temp1_real = alpha_real * Aki_real - alpha_imag * (-Aki_imag); BASE temp1_imag = alpha_real * (-Aki_imag) + alpha_imag * Aki_real; /* temp2 = conj(alpha) * conj(Bki) */ BASE temp2_real = alpha_real * Bki_real - alpha_imag * Bki_imag; BASE temp2_imag = -(alpha_real * Bki_imag + alpha_imag * Bki_real); for (j = 0; j < i; j++) { BASE Akj_real = CONST_REAL(A, k * lda + j); BASE Akj_imag = CONST_IMAG(A, k * lda + j); BASE Bkj_real = CONST_REAL(B, k * ldb + j); BASE Bkj_imag = CONST_IMAG(B, k * ldb + j); /* Cij += alpha * conj(Aki) * Bkj + conj(alpha) * conj(Bki) * Akj */ REAL(C, i * lda + j) += (temp1_real * Bkj_real - temp1_imag * Bkj_imag) + (temp2_real * Akj_real - temp2_imag * Akj_imag); IMAG(C, i * lda + j) += (temp1_real * Bkj_imag + temp1_imag * Bkj_real) + (temp2_real * Akj_imag + temp2_imag * Akj_real); } /* Cii += alpha * conj(Aki) * Bki + conj(alpha) * conj(Bki) * Aki */ { REAL(C, i * lda + i) += 2 * (temp1_real * Bki_real - temp1_imag * Bki_imag); IMAG(C, i * lda + i) = 0.0; } } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_cblas__source_gemv_c.h0000664000176700017670000001202111705263724021500 0ustar paulpaul/* blas/source_gemv_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; INDEX lenX, lenY; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if (M == 0 || N == 0) return; if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; if (TransA == CblasNoTrans) { lenX = N; lenY = M; } else { lenX = M; lenY = N; } /* form y := beta*y */ if (beta_real == 0.0 && beta_imag == 0.0) { INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { REAL(Y, iy) = 0.0; IMAG(Y, iy) = 0.0; iy += incY; } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { const BASE y_real = REAL(Y, iy); const BASE y_imag = IMAG(Y, iy); const BASE tmpR = y_real * beta_real - y_imag * beta_imag; const BASE tmpI = y_real * beta_imag + y_imag * beta_real; REAL(Y, iy) = tmpR; IMAG(Y, iy) = tmpI; iy += incY; } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; if ((order == CblasRowMajor && TransA == CblasNoTrans) || (order == CblasColMajor && TransA == CblasTrans)) { /* form y := alpha*A*x + y */ INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { BASE dotR = 0.0; BASE dotI = 0.0; INDEX ix = OFFSET(lenX, incX); for (j = 0; j < lenX; j++) { const BASE x_real = CONST_REAL(X, ix); const BASE x_imag = CONST_IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + j); const BASE A_imag = CONST_IMAG(A, lda * i + j); dotR += A_real * x_real - A_imag * x_imag; dotI += A_real * x_imag + A_imag * x_real; ix += incX; } REAL(Y, iy) += alpha_real * dotR - alpha_imag * dotI; IMAG(Y, iy) += alpha_real * dotI + alpha_imag * dotR; iy += incY; } } else if ((order == CblasRowMajor && TransA == CblasTrans) || (order == CblasColMajor && TransA == CblasNoTrans)) { /* form y := alpha*A'*x + y */ INDEX ix = OFFSET(lenX, incX); for (j = 0; j < lenX; j++) { BASE x_real = CONST_REAL(X, ix); BASE x_imag = CONST_IMAG(X, ix); BASE tmpR = alpha_real * x_real - alpha_imag * x_imag; BASE tmpI = alpha_real * x_imag + alpha_imag * x_real; INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { const BASE A_real = CONST_REAL(A, lda * j + i); const BASE A_imag = CONST_IMAG(A, lda * j + i); REAL(Y, iy) += A_real * tmpR - A_imag * tmpI; IMAG(Y, iy) += A_real * tmpI + A_imag * tmpR; iy += incY; } ix += incX; } } else if (order == CblasRowMajor && TransA == CblasConjTrans) { /* form y := alpha*A^H*x + y */ INDEX ix = OFFSET(lenX, incX); for (j = 0; j < lenX; j++) { BASE x_real = CONST_REAL(X, ix); BASE x_imag = CONST_IMAG(X, ix); BASE tmpR = alpha_real * x_real - alpha_imag * x_imag; BASE tmpI = alpha_real * x_imag + alpha_imag * x_real; INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { const BASE A_real = CONST_REAL(A, lda * j + i); const BASE A_imag = CONST_IMAG(A, lda * j + i); REAL(Y, iy) += A_real * tmpR - (-A_imag) * tmpI; IMAG(Y, iy) += A_real * tmpI + (-A_imag) * tmpR; iy += incY; } ix += incX; } } else if (order == CblasColMajor && TransA == CblasConjTrans) { /* form y := alpha*A^H*x + y */ INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { BASE dotR = 0.0; BASE dotI = 0.0; INDEX ix = OFFSET(lenX, incX); for (j = 0; j < lenX; j++) { const BASE x_real = CONST_REAL(X, ix); const BASE x_imag = CONST_IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + j); const BASE A_imag = CONST_IMAG(A, lda * i + j); dotR += A_real * x_real - (-A_imag) * x_imag; dotI += A_real * x_imag + (-A_imag) * x_real; ix += incX; } REAL(Y, iy) += alpha_real * dotR - alpha_imag * dotI; IMAG(Y, iy) += alpha_real * dotI + alpha_imag * dotR; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_deriv.h0000664000176700017670000000303011705263724016466 0ustar paulpaul/* deriv/gsl_deriv.h * * Copyright (C) 2000 David Morrison * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_DERIV_H__ #define __GSL_DERIV_H__ #include "gsl_math.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_deriv_central (const gsl_function *f, double x, double h, double *result, double *abserr); int gsl_deriv_backward (const gsl_function *f, double x, double h, double *result, double *abserr); int gsl_deriv_forward (const gsl_function *f, double x, double h, double *result, double *abserr); __END_DECLS #endif /* __GSL_DERIV_H__ */ sources_5316/external/gsl/gsl_cdf__gumbel1inv.c0000664000176700017670000000254211723710247020400 0ustar paulpaul/* cdf/gumbel1inv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_gumbel1_Pinv (const double P, const double a, const double b) { double x; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return GSL_NEGINF; } x = log(-b / log(P)) / a; return x; } double gsl_cdf_gumbel1_Qinv (const double Q, const double a, const double b) { double x; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return GSL_NEGINF; } x = log(-b / log1p(-Q)) / a; return x; } sources_5316/external/gsl/gsl_linalg__choleskyc.c0000664000176700017670000001315311723710247021025 0ustar paulpaul/* linalg/choleskyc.c * * Copyright (C) 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_matrix.h" #include "gsl_vector.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_complex_math.h" #include "gsl_blas.h" #include "gsl_errno.h" /* * This module contains routines related to the Cholesky decomposition * of a complex Hermitian positive definite matrix. */ static void cholesky_complex_conj_vector(gsl_vector_complex *v); /* gsl_linalg_complex_cholesky_decomp() Perform the Cholesky decomposition on a Hermitian positive definite matrix. See Golub & Van Loan, "Matrix Computations" (3rd ed), algorithm 4.2.2. Inputs: A - (input/output) complex postive definite matrix Return: success or error The lower triangle of A is overwritten with the Cholesky decomposition */ int gsl_linalg_complex_cholesky_decomp(gsl_matrix_complex *A) { const size_t N = A->size1; if (N != A->size2) { GSL_ERROR("cholesky decomposition requires square matrix", GSL_ENOTSQR); } else { size_t j; gsl_complex z; double ajj; for (j = 0; j < N; ++j) { z = gsl_matrix_complex_get(A, j, j); ajj = GSL_REAL(z); if (j > 0) { gsl_vector_complex_const_view aj = gsl_matrix_complex_const_subrow(A, j, 0, j); gsl_blas_zdotc(&aj.vector, &aj.vector, &z); ajj -= GSL_REAL(z); } if (ajj <= 0.0) { GSL_ERROR("matrix is not positive definite", GSL_EDOM); } ajj = sqrt(ajj); GSL_SET_COMPLEX(&z, ajj, 0.0); gsl_matrix_complex_set(A, j, j, z); if (j < N - 1) { gsl_vector_complex_view av = gsl_matrix_complex_subcolumn(A, j, j + 1, N - j - 1); if (j > 0) { gsl_vector_complex_view aj = gsl_matrix_complex_subrow(A, j, 0, j); gsl_matrix_complex_view am = gsl_matrix_complex_submatrix(A, j + 1, 0, N - j - 1, j); cholesky_complex_conj_vector(&aj.vector); gsl_blas_zgemv(CblasNoTrans, GSL_COMPLEX_NEGONE, &am.matrix, &aj.vector, GSL_COMPLEX_ONE, &av.vector); cholesky_complex_conj_vector(&aj.vector); } gsl_blas_zdscal(1.0 / ajj, &av.vector); } } return GSL_SUCCESS; } } /* gsl_linalg_complex_cholesky_decomp() */ /* gsl_linalg_complex_cholesky_solve() Solve A x = b where A is in cholesky form */ int gsl_linalg_complex_cholesky_solve (const gsl_matrix_complex * cholesky, const gsl_vector_complex * b, gsl_vector_complex * x) { if (cholesky->size1 != cholesky->size2) { GSL_ERROR ("cholesky matrix must be square", GSL_ENOTSQR); } else if (cholesky->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (cholesky->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { gsl_vector_complex_memcpy (x, b); /* solve for y using forward-substitution, L y = b */ gsl_blas_ztrsv (CblasLower, CblasNoTrans, CblasNonUnit, cholesky, x); /* perform back-substitution, L^H x = y */ gsl_blas_ztrsv (CblasLower, CblasConjTrans, CblasNonUnit, cholesky, x); return GSL_SUCCESS; } } /* gsl_linalg_complex_cholesky_solve() */ /* gsl_linalg_complex_cholesky_svx() Solve A x = b in place where A is in cholesky form */ int gsl_linalg_complex_cholesky_svx (const gsl_matrix_complex * cholesky, gsl_vector_complex * x) { if (cholesky->size1 != cholesky->size2) { GSL_ERROR ("cholesky matrix must be square", GSL_ENOTSQR); } else if (cholesky->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* solve for y using forward-substitution, L y = b */ gsl_blas_ztrsv (CblasLower, CblasNoTrans, CblasNonUnit, cholesky, x); /* perform back-substitution, L^H x = y */ gsl_blas_ztrsv (CblasLower, CblasConjTrans, CblasNonUnit, cholesky, x); return GSL_SUCCESS; } } /* gsl_linalg_complex_cholesky_svx() */ /******************************************** * INTERNAL ROUTINES * ********************************************/ static void cholesky_complex_conj_vector(gsl_vector_complex *v) { size_t i; for (i = 0; i < v->size; ++i) { gsl_complex z = gsl_vector_complex_get(v, i); gsl_vector_complex_set(v, i, gsl_complex_conjugate(z)); } } /* cholesky_complex_conj_vector() */ sources_5316/external/gsl/gsl_multiroots__fsolver.c0000664000176700017670000000751011723710247021474 0ustar paulpaul/* multiroots/fsolver.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_multiroots.h" gsl_multiroot_fsolver * gsl_multiroot_fsolver_alloc (const gsl_multiroot_fsolver_type * T, size_t n) { int status; gsl_multiroot_fsolver * s; s = (gsl_multiroot_fsolver *) malloc (sizeof (gsl_multiroot_fsolver)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for multiroot solver struct", GSL_ENOMEM, 0); } s->x = gsl_vector_calloc (n); if (s->x == 0) { free (s); GSL_ERROR_VAL ("failed to allocate space for x", GSL_ENOMEM, 0); } s->f = gsl_vector_calloc (n); if (s->f == 0) { gsl_vector_free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for f", GSL_ENOMEM, 0); } s->dx = gsl_vector_calloc (n); if (s->dx == 0) { gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); GSL_ERROR_VAL ("failed to allocate space for dx", GSL_ENOMEM, 0); } s->state = malloc (T->size); if (s->state == 0) { gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for multiroot solver state", GSL_ENOMEM, 0); } s->type = T ; status = (s->type->alloc)(s->state, n); if (status != GSL_SUCCESS) { (s->type->free)(s->state); free (s->state); gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to set solver", status, 0); } s->function = NULL; return s; } int gsl_multiroot_fsolver_set (gsl_multiroot_fsolver * s, gsl_multiroot_function * f, const gsl_vector * x) { if (s->x->size != f->n) { GSL_ERROR ("function incompatible with solver size", GSL_EBADLEN); } if (x->size != f->n) { GSL_ERROR ("vector length not compatible with function", GSL_EBADLEN); } s->function = f; gsl_vector_memcpy(s->x,x); return (s->type->set) (s->state, s->function, s->x, s->f, s->dx); } int gsl_multiroot_fsolver_iterate (gsl_multiroot_fsolver * s) { return (s->type->iterate) (s->state, s->function, s->x, s->f, s->dx); } void gsl_multiroot_fsolver_free (gsl_multiroot_fsolver * s) { (s->type->free) (s->state); free (s->state); gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); } const char * gsl_multiroot_fsolver_name (const gsl_multiroot_fsolver * s) { return s->type->name; } gsl_vector * gsl_multiroot_fsolver_root (const gsl_multiroot_fsolver * s) { return s->x; } gsl_vector * gsl_multiroot_fsolver_dx (const gsl_multiroot_fsolver * s) { return s->dx; } gsl_vector * gsl_multiroot_fsolver_f (const gsl_multiroot_fsolver * s) { return s->f; } sources_5316/external/gsl/gsl_cdf__laplace.c0000664000176700017670000000242211723710247017725 0ustar paulpaul/* cdf/laplace.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_laplace_P (const double x, const double a) { double P; double u = x / a; if (u > 0) { P = 0.5 + 0.5*(1 - exp(-u)) ; } else { P = 0.5 * exp(u); } return P; } double gsl_cdf_laplace_Q (const double x, const double a) { double Q; double u = x / a; if (u > 0) { Q = 0.5 * exp(-u); } else { Q = 1 - 0.5 *exp(u); } return Q; } sources_5316/external/gsl/gsl_matrix__submatrix_source.c0000664000176700017670000000402411723710247022472 0ustar paulpaul/* matrix/submatrix_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ QUALIFIED_VIEW(_gsl_matrix,view) FUNCTION (gsl_matrix, submatrix) (QUALIFIED_TYPE(gsl_matrix) * m, const size_t i, const size_t j, const size_t n1, const size_t n2) { QUALIFIED_VIEW(_gsl_matrix,view) view = NULL_MATRIX_VIEW; if (i >= m->size1) { GSL_ERROR_VAL ("row index is out of range", GSL_EINVAL, view); } else if (j >= m->size2) { GSL_ERROR_VAL ("column index is out of range", GSL_EINVAL, view); } else if (n1 == 0) { GSL_ERROR_VAL ("first dimension must be non-zero", GSL_EINVAL, view); } else if (n2 == 0) { GSL_ERROR_VAL ("second dimension must be non-zero", GSL_EINVAL, view); } else if (i + n1 > m->size1) { GSL_ERROR_VAL ("first dimension overflows matrix", GSL_EINVAL, view); } else if (j + n2 > m->size2) { GSL_ERROR_VAL ("second dimension overflows matrix", GSL_EINVAL, view); } { TYPE(gsl_matrix) s = NULL_MATRIX; s.data = m->data + MULTIPLICITY * (i * m->tda + j); s.size1 = n1; s.size2 = n2; s.tda = m->tda; s.block = m->block; s.owner = 0; view.matrix = s; return view; } } sources_5316/external/gsl/gsl_wavelet__daubechies.c0000664000176700017670000003000111723710247021325 0ustar paulpaul/* wavelet/daubechies.c * * Copyright (C) 2004 Ivo Alxneit * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * Coefficients for Daubechies wavelets of extremal phase are from * I. Daubechies, "Orthonormal Bases of Compactly Supported Wavelets", * Communications on Pure and Applied Mathematics, 41 (1988) 909--996 * (table 1). * Additional digits have been obtained using the Mathematica package * Daubechies.m by Tong Chen & Meng Xu available at * http://www.cwp.mines.edu/wavelets/. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_wavelet.h" static const double h_4[4] = { 0.48296291314453414337487159986, 0.83651630373780790557529378092, 0.22414386804201338102597276224, -0.12940952255126038117444941881 }; static const double g_4[4] = { -0.12940952255126038117444941881, -0.22414386804201338102597276224, 0.83651630373780790557529378092, -0.48296291314453414337487159986 }; static const double h_6[6] = { 0.33267055295008261599851158914, 0.80689150931109257649449360409, 0.45987750211849157009515194215, -0.13501102001025458869638990670, -0.08544127388202666169281916918, 0.03522629188570953660274066472 }; static const double g_6[6] = { 0.03522629188570953660274066472, 0.08544127388202666169281916918, -0.13501102001025458869638990670, -0.45987750211849157009515194215, 0.80689150931109257649449360409, -0.33267055295008261599851158914 }; static const double h_8[8] = { 0.23037781330889650086329118304, 0.71484657055291564708992195527, 0.63088076792985890788171633830, -0.02798376941685985421141374718, -0.18703481171909308407957067279, 0.03084138183556076362721936253, 0.03288301166688519973540751355, -0.01059740178506903210488320852 }; static const double g_8[8] = { -0.01059740178506903210488320852, -0.03288301166688519973540751355, 0.03084138183556076362721936253, 0.18703481171909308407957067279, -0.02798376941685985421141374718, -0.63088076792985890788171633830, 0.71484657055291564708992195527, -0.23037781330889650086329118304 }; static const double h_10[10] = { 0.16010239797419291448072374802, 0.60382926979718967054011930653, 0.72430852843777292772807124410, 0.13842814590132073150539714634, -0.24229488706638203186257137947, -0.03224486958463837464847975506, 0.07757149384004571352313048939, -0.00624149021279827427419051911, -0.01258075199908199946850973993, 0.00333572528547377127799818342 }; static const double g_10[10] = { 0.00333572528547377127799818342, 0.01258075199908199946850973993, -0.00624149021279827427419051911, -0.07757149384004571352313048939, -0.03224486958463837464847975506, 0.24229488706638203186257137947, 0.13842814590132073150539714634, -0.72430852843777292772807124410, 0.60382926979718967054011930653, -0.16010239797419291448072374802 }; static const double h_12[12] = { 0.11154074335010946362132391724, 0.49462389039845308567720417688, 0.75113390802109535067893449844, 0.31525035170919762908598965481, -0.22626469396543982007631450066, -0.12976686756726193556228960588, 0.09750160558732304910234355254, 0.02752286553030572862554083950, -0.03158203931748602956507908070, 0.00055384220116149613925191840, 0.00477725751094551063963597525, -0.00107730108530847956485262161 }; static const double g_12[12] = { -0.00107730108530847956485262161, -0.00477725751094551063963597525, 0.00055384220116149613925191840, 0.03158203931748602956507908070, 0.02752286553030572862554083950, -0.09750160558732304910234355254, -0.12976686756726193556228960588, 0.22626469396543982007631450066, 0.31525035170919762908598965481, -0.75113390802109535067893449844, 0.49462389039845308567720417688, -0.11154074335010946362132391724 }; static const double h_14[14] = { 0.07785205408500917901996352196, 0.39653931948191730653900039094, 0.72913209084623511991694307034, 0.46978228740519312247159116097, -0.14390600392856497540506836221, -0.22403618499387498263814042023, 0.07130921926683026475087657050, 0.08061260915108307191292248036, -0.03802993693501441357959206160, -0.01657454163066688065410767489, 0.01255099855609984061298988603, 0.00042957797292136652113212912, -0.00180164070404749091526826291, 0.00035371379997452024844629584 }; static const double g_14[14] = { 0.00035371379997452024844629584, 0.00180164070404749091526826291, 0.00042957797292136652113212912, -0.01255099855609984061298988603, -0.01657454163066688065410767489, 0.03802993693501441357959206160, 0.08061260915108307191292248036, -0.07130921926683026475087657050, -0.22403618499387498263814042023, 0.14390600392856497540506836221, 0.46978228740519312247159116097, -0.72913209084623511991694307034, 0.39653931948191730653900039094, -0.07785205408500917901996352196 }; static const double h_16[16] = { 0.05441584224310400995500940520, 0.31287159091429997065916237551, 0.67563073629728980680780076705, 0.58535468365420671277126552005, -0.01582910525634930566738054788, -0.28401554296154692651620313237, 0.00047248457391328277036059001, 0.12874742662047845885702928751, -0.01736930100180754616961614887, -0.04408825393079475150676372324, 0.01398102791739828164872293057, 0.00874609404740577671638274325, -0.00487035299345157431042218156, -0.00039174037337694704629808036, 0.00067544940645056936636954757, -0.00011747678412476953373062823 }; static const double g_16[16] = { -0.00011747678412476953373062823, -0.00067544940645056936636954757, -0.00039174037337694704629808036, 0.00487035299345157431042218156, 0.00874609404740577671638274325, -0.01398102791739828164872293057, -0.04408825393079475150676372324, 0.01736930100180754616961614887, 0.12874742662047845885702928751, -0.00047248457391328277036059001, -0.28401554296154692651620313237, 0.01582910525634930566738054788, 0.58535468365420671277126552005, -0.67563073629728980680780076705, 0.31287159091429997065916237551, -0.05441584224310400995500940520 }; static const double h_18[18] = { 0.03807794736387834658869765888, 0.24383467461259035373204158165, 0.60482312369011111190307686743, 0.65728807805130053807821263905, 0.13319738582500757619095494590, -0.29327378327917490880640319524, -0.09684078322297646051350813354, 0.14854074933810638013507271751, 0.03072568147933337921231740072, -0.06763282906132997367564227483, 0.00025094711483145195758718975, 0.02236166212367909720537378270, -0.00472320475775139727792570785, -0.00428150368246342983449679500, 0.00184764688305622647661912949, 0.00023038576352319596720521639, -0.00025196318894271013697498868, 0.00003934732031627159948068988 }; static const double g_18[18] = { 0.00003934732031627159948068988, 0.00025196318894271013697498868, 0.00023038576352319596720521639, -0.00184764688305622647661912949, -0.00428150368246342983449679500, 0.00472320475775139727792570785, 0.02236166212367909720537378270, -0.00025094711483145195758718975, -0.06763282906132997367564227483, -0.03072568147933337921231740072, 0.14854074933810638013507271751, 0.09684078322297646051350813354, -0.29327378327917490880640319524, -0.13319738582500757619095494590, 0.65728807805130053807821263905, -0.60482312369011111190307686743, 0.24383467461259035373204158165, -0.03807794736387834658869765888 }; static const double h_20[20] = { 0.02667005790055555358661744877, 0.18817680007769148902089297368, 0.52720118893172558648174482796, 0.68845903945360356574187178255, 0.28117234366057746074872699845, -0.24984642432731537941610189792, -0.19594627437737704350429925432, 0.12736934033579326008267723320, 0.09305736460357235116035228984, -0.07139414716639708714533609308, -0.02945753682187581285828323760, 0.03321267405934100173976365318, 0.00360655356695616965542329142, -0.01073317548333057504431811411, 0.00139535174705290116578931845, 0.00199240529518505611715874224, -0.00068585669495971162656137098, -0.00011646685512928545095148097, 0.00009358867032006959133405013, -0.00001326420289452124481243668 }; static const double g_20[20] = { -0.00001326420289452124481243668, -0.00009358867032006959133405013, -0.00011646685512928545095148097, 0.00068585669495971162656137098, 0.00199240529518505611715874224, -0.00139535174705290116578931845, -0.01073317548333057504431811411, -0.00360655356695616965542329142, 0.03321267405934100173976365318, 0.02945753682187581285828323760, -0.07139414716639708714533609308, -0.09305736460357235116035228984, 0.12736934033579326008267723320, 0.19594627437737704350429925432, -0.24984642432731537941610189792, -0.28117234366057746074872699845, 0.68845903945360356574187178255, -0.52720118893172558648174482796, 0.18817680007769148902089297368, -0.02667005790055555358661744877 }; static int daubechies_init (const double **h1, const double **g1, const double **h2, const double **g2, size_t * nc, size_t * offset, size_t member) { switch (member) { case 4: *h1 = h_4; *g1 = g_4; *h2 = h_4; *g2 = g_4; break; case 6: *h1 = h_6; *g1 = g_6; *h2 = h_6; *g2 = g_6; break; case 8: *h1 = h_8; *g1 = g_8; *h2 = h_8; *g2 = g_8; break; case 10: *h1 = h_10; *g1 = g_10; *h2 = h_10; *g2 = g_10; break; case 12: *h1 = h_12; *g1 = g_12; *h2 = h_12; *g2 = g_12; break; case 14: *h1 = h_14; *g1 = g_14; *h2 = h_14; *g2 = g_14; break; case 16: *h1 = h_16; *g1 = g_16; *h2 = h_16; *g2 = g_16; break; case 18: *h1 = h_18; *g1 = g_18; *h2 = h_18; *g2 = g_18; break; case 20: *h1 = h_20; *g1 = g_20; *h2 = h_20; *g2 = g_20; break; default: return GSL_FAILURE; } *nc = member; *offset = 0; return GSL_SUCCESS; } static int daubechies_centered_init (const double **h1, const double **g1, const double **h2, const double **g2, size_t * nc, size_t * offset, size_t member) { switch (member) { case 4: *h1 = h_4; *g1 = g_4; *h2 = h_4; *g2 = g_4; break; case 6: *h1 = h_6; *g1 = g_6; *h2 = h_6; *g2 = g_6; break; case 8: *h1 = h_8; *g1 = g_8; *h2 = h_8; *g2 = g_8; break; case 10: *h1 = h_10; *g1 = g_10; *h2 = h_10; *g2 = g_10; break; case 12: *h1 = h_12; *g1 = g_12; *h2 = h_12; *g2 = g_12; break; case 14: *h1 = h_14; *g1 = g_14; *h2 = h_14; *g2 = g_14; break; case 16: *h1 = h_16; *g1 = g_16; *h2 = h_16; *g2 = g_16; break; case 18: *h1 = h_18; *g1 = g_18; *h2 = h_18; *g2 = g_18; break; case 20: *h1 = h_20; *g1 = g_20; *h2 = h_20; *g2 = g_20; break; default: return GSL_FAILURE; } *nc = member; *offset = (member >> 1); return GSL_SUCCESS; } static const gsl_wavelet_type daubechies_type = { "daubechies", &daubechies_init }; static const gsl_wavelet_type daubechies_centered_type = { "daubechies-centered", &daubechies_centered_init }; const gsl_wavelet_type *gsl_wavelet_daubechies = &daubechies_type; const gsl_wavelet_type *gsl_wavelet_daubechies_centered = &daubechies_centered_type; sources_5316/external/gsl/gsl_histogram__reset2d.c0000664000176700017670000000207311723710247021137 0ustar paulpaul/* histogram/reset2d.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_histogram2d.h" void gsl_histogram2d_reset (gsl_histogram2d * h) { size_t i; const size_t nx = h->nx; const size_t ny = h->ny; for (i = 0; i < nx * ny; i++) { h->bin[i] = 0; } } sources_5316/external/gsl/gsl_cblas__dtpmv.c0000664000176700017670000000056511723710247020014 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dtpmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const double *Ap, double *X, const int incX) { #define BASE double #include "gsl_cblas__source_tpmv_r.h" #undef BASE } sources_5316/external/gsl/gsl_rng.h0000664000176700017670000001530411705263724016152 0ustar paulpaul/* rng/gsl_rng.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_RNG_H__ #define __GSL_RNG_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { const char *name; unsigned long int max; unsigned long int min; size_t size; void (*set) (void *state, unsigned long int seed); unsigned long int (*get) (void *state); double (*get_double) (void *state); } gsl_rng_type; typedef struct { const gsl_rng_type * type; void *state; } gsl_rng; /* These structs also need to appear in default.c so you can select them via the environment variable GSL_RNG_TYPE */ GSL_VAR const gsl_rng_type *gsl_rng_borosh13; GSL_VAR const gsl_rng_type *gsl_rng_coveyou; GSL_VAR const gsl_rng_type *gsl_rng_cmrg; GSL_VAR const gsl_rng_type *gsl_rng_fishman18; GSL_VAR const gsl_rng_type *gsl_rng_fishman20; GSL_VAR const gsl_rng_type *gsl_rng_fishman2x; GSL_VAR const gsl_rng_type *gsl_rng_gfsr4; GSL_VAR const gsl_rng_type *gsl_rng_knuthran; GSL_VAR const gsl_rng_type *gsl_rng_knuthran2; GSL_VAR const gsl_rng_type *gsl_rng_knuthran2002; GSL_VAR const gsl_rng_type *gsl_rng_lecuyer21; GSL_VAR const gsl_rng_type *gsl_rng_minstd; GSL_VAR const gsl_rng_type *gsl_rng_mrg; GSL_VAR const gsl_rng_type *gsl_rng_mt19937; GSL_VAR const gsl_rng_type *gsl_rng_mt19937_1999; GSL_VAR const gsl_rng_type *gsl_rng_mt19937_1998; GSL_VAR const gsl_rng_type *gsl_rng_r250; GSL_VAR const gsl_rng_type *gsl_rng_ran0; GSL_VAR const gsl_rng_type *gsl_rng_ran1; GSL_VAR const gsl_rng_type *gsl_rng_ran2; GSL_VAR const gsl_rng_type *gsl_rng_ran3; GSL_VAR const gsl_rng_type *gsl_rng_rand; GSL_VAR const gsl_rng_type *gsl_rng_rand48; GSL_VAR const gsl_rng_type *gsl_rng_random128_bsd; GSL_VAR const gsl_rng_type *gsl_rng_random128_glibc2; GSL_VAR const gsl_rng_type *gsl_rng_random128_libc5; GSL_VAR const gsl_rng_type *gsl_rng_random256_bsd; GSL_VAR const gsl_rng_type *gsl_rng_random256_glibc2; GSL_VAR const gsl_rng_type *gsl_rng_random256_libc5; GSL_VAR const gsl_rng_type *gsl_rng_random32_bsd; GSL_VAR const gsl_rng_type *gsl_rng_random32_glibc2; GSL_VAR const gsl_rng_type *gsl_rng_random32_libc5; GSL_VAR const gsl_rng_type *gsl_rng_random64_bsd; GSL_VAR const gsl_rng_type *gsl_rng_random64_glibc2; GSL_VAR const gsl_rng_type *gsl_rng_random64_libc5; GSL_VAR const gsl_rng_type *gsl_rng_random8_bsd; GSL_VAR const gsl_rng_type *gsl_rng_random8_glibc2; GSL_VAR const gsl_rng_type *gsl_rng_random8_libc5; GSL_VAR const gsl_rng_type *gsl_rng_random_bsd; GSL_VAR const gsl_rng_type *gsl_rng_random_glibc2; GSL_VAR const gsl_rng_type *gsl_rng_random_libc5; GSL_VAR const gsl_rng_type *gsl_rng_randu; GSL_VAR const gsl_rng_type *gsl_rng_ranf; GSL_VAR const gsl_rng_type *gsl_rng_ranlux; GSL_VAR const gsl_rng_type *gsl_rng_ranlux389; GSL_VAR const gsl_rng_type *gsl_rng_ranlxd1; GSL_VAR const gsl_rng_type *gsl_rng_ranlxd2; GSL_VAR const gsl_rng_type *gsl_rng_ranlxs0; GSL_VAR const gsl_rng_type *gsl_rng_ranlxs1; GSL_VAR const gsl_rng_type *gsl_rng_ranlxs2; GSL_VAR const gsl_rng_type *gsl_rng_ranmar; GSL_VAR const gsl_rng_type *gsl_rng_slatec; GSL_VAR const gsl_rng_type *gsl_rng_taus; GSL_VAR const gsl_rng_type *gsl_rng_taus2; GSL_VAR const gsl_rng_type *gsl_rng_taus113; GSL_VAR const gsl_rng_type *gsl_rng_transputer; GSL_VAR const gsl_rng_type *gsl_rng_tt800; GSL_VAR const gsl_rng_type *gsl_rng_uni; GSL_VAR const gsl_rng_type *gsl_rng_uni32; GSL_VAR const gsl_rng_type *gsl_rng_vax; GSL_VAR const gsl_rng_type *gsl_rng_waterman14; GSL_VAR const gsl_rng_type *gsl_rng_zuf; const gsl_rng_type ** gsl_rng_types_setup(void); GSL_VAR const gsl_rng_type *gsl_rng_default; GSL_VAR unsigned long int gsl_rng_default_seed; gsl_rng *gsl_rng_alloc (const gsl_rng_type * T); int gsl_rng_memcpy (gsl_rng * dest, const gsl_rng * src); gsl_rng *gsl_rng_clone (const gsl_rng * r); void gsl_rng_free (gsl_rng * r); void gsl_rng_set (const gsl_rng * r, unsigned long int seed); unsigned long int gsl_rng_max (const gsl_rng * r); unsigned long int gsl_rng_min (const gsl_rng * r); const char *gsl_rng_name (const gsl_rng * r); int gsl_rng_fread (FILE * stream, gsl_rng * r); int gsl_rng_fwrite (FILE * stream, const gsl_rng * r); size_t gsl_rng_size (const gsl_rng * r); void * gsl_rng_state (const gsl_rng * r); void gsl_rng_print_state (const gsl_rng * r); const gsl_rng_type * gsl_rng_env_setup (void); unsigned long int gsl_rng_get (const gsl_rng * r); double gsl_rng_uniform (const gsl_rng * r); double gsl_rng_uniform_pos (const gsl_rng * r); unsigned long int gsl_rng_uniform_int (const gsl_rng * r, unsigned long int n); #ifdef HAVE_INLINE extern inline unsigned long int gsl_rng_get (const gsl_rng * r); extern inline unsigned long int gsl_rng_get (const gsl_rng * r) { return (r->type->get) (r->state); } extern inline double gsl_rng_uniform (const gsl_rng * r); extern inline double gsl_rng_uniform (const gsl_rng * r) { return (r->type->get_double) (r->state); } extern inline double gsl_rng_uniform_pos (const gsl_rng * r); extern inline double gsl_rng_uniform_pos (const gsl_rng * r) { double x ; do { x = (r->type->get_double) (r->state) ; } while (x == 0) ; return x ; } extern inline unsigned long int gsl_rng_uniform_int (const gsl_rng * r, unsigned long int n); extern inline unsigned long int gsl_rng_uniform_int (const gsl_rng * r, unsigned long int n) { unsigned long int offset = r->type->min; unsigned long int range = r->type->max - offset; unsigned long int scale; unsigned long int k; if (n > range || n == 0) { GSL_ERROR_VAL ("invalid n, either 0 or exceeds maximum value of generator", GSL_EINVAL, 0) ; } scale = range / n; do { k = (((r->type->get) (r->state)) - offset) / scale; } while (k >= n); return k; } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_RNG_H__ */ sources_5316/external/gsl/gsl_linalg__hesstri.c0000664000176700017670000001263311723710247020524 0ustar paulpaul/* linalg/hesstri.c * * Copyright (C) 2006, 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl__config.h" #include "gsl_linalg.h" #include "gsl_matrix.h" #include "gsl_vector.h" #include "gsl_blas.h" #include "gsl_linalg__givens.c" /* * This module contains routines related to the Hessenberg-Triangular * reduction of two general real matrices * * See Golub & Van Loan, "Matrix Computations", 3rd ed, sec 7.7.4 */ /* gsl_linalg_hesstri_decomp() Perform a reduction to generalized upper Hessenberg form. Given A and B, this function overwrites A with an upper Hessenberg matrix H = U^T A V and B with an upper triangular matrix R = U^T B V with U and V orthogonal. See Golub & Van Loan, "Matrix Computations" (3rd ed) algorithm 7.7.1 Inputs: A - real square matrix B - real square matrix U - (output) if non-null, U is stored here on output V - (output) if non-null, V is stored here on output work - workspace (length n) Return: success or error */ int gsl_linalg_hesstri_decomp(gsl_matrix * A, gsl_matrix * B, gsl_matrix * U, gsl_matrix * V, gsl_vector * work) { const size_t N = A->size1; if ((N != A->size2) || (N != B->size1) || (N != B->size2)) { GSL_ERROR ("Hessenberg-triangular reduction requires square matrices", GSL_ENOTSQR); } else if (N != work->size) { GSL_ERROR ("length of workspace must match matrix dimension", GSL_EBADLEN); } else { double cs, sn; /* rotation parameters */ size_t i, j; /* looping */ gsl_vector_view xv, yv; /* temporary views */ /* B -> Q^T B = R (upper triangular) */ gsl_linalg_QR_decomp(B, work); /* A -> Q^T A */ gsl_linalg_QR_QTmat(B, work, A); /* initialize U and V if desired */ if (U) { gsl_linalg_QR_unpack(B, work, U, B); } else { /* zero out lower triangle of B */ for (j = 0; j < N - 1; ++j) { for (i = j + 1; i < N; ++i) gsl_matrix_set(B, i, j, 0.0); } } if (V) gsl_matrix_set_identity(V); if (N < 3) return GSL_SUCCESS; /* nothing more to do */ /* reduce A and B */ for (j = 0; j < N - 2; ++j) { for (i = N - 1; i >= (j + 2); --i) { /* step 1: rotate rows i - 1, i to kill A(i,j) */ /* * compute G = [ CS SN ] so that G^t [ A(i-1,j) ] = [ * ] * [-SN CS ] [ A(i, j) ] [ 0 ] */ create_givens(gsl_matrix_get(A, i - 1, j), gsl_matrix_get(A, i, j), &cs, &sn); /* invert so drot() works correctly (G -> G^t) */ sn = -sn; /* compute G^t A(i-1:i, j:n) */ xv = gsl_matrix_subrow(A, i - 1, j, N - j); yv = gsl_matrix_subrow(A, i, j, N - j); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); /* compute G^t B(i-1:i, i-1:n) */ xv = gsl_matrix_subrow(B, i - 1, i - 1, N - i + 1); yv = gsl_matrix_subrow(B, i, i - 1, N - i + 1); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); if (U) { /* accumulate U: U -> U G */ xv = gsl_matrix_column(U, i - 1); yv = gsl_matrix_column(U, i); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } /* step 2: rotate columns i, i - 1 to kill B(i, i - 1) */ create_givens(-gsl_matrix_get(B, i, i), gsl_matrix_get(B, i, i - 1), &cs, &sn); /* invert so drot() works correctly (G -> G^t) */ sn = -sn; /* compute B(1:i, i-1:i) G */ xv = gsl_matrix_subcolumn(B, i - 1, 0, i + 1); yv = gsl_matrix_subcolumn(B, i, 0, i + 1); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); /* apply to A(1:n, i-1:i) */ xv = gsl_matrix_column(A, i - 1); yv = gsl_matrix_column(A, i); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); if (V) { /* accumulate V: V -> V G */ xv = gsl_matrix_column(V, i - 1); yv = gsl_matrix_column(V, i); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } } } return GSL_SUCCESS; } } /* gsl_linalg_hesstri_decomp() */ sources_5316/external/gsl/gsl_sort_vector.h0000664000176700017670000000075111705263724017735 0ustar paulpaul#ifndef __GSL_SORT_VECTOR_H__ #define __GSL_SORT_VECTOR_H__ #include "gsl_sort_vector_long_double.h" #include "gsl_sort_vector_double.h" #include "gsl_sort_vector_float.h" #include "gsl_sort_vector_ulong.h" #include "gsl_sort_vector_long.h" #include "gsl_sort_vector_uint.h" #include "gsl_sort_vector_int.h" #include "gsl_sort_vector_ushort.h" #include "gsl_sort_vector_short.h" #include "gsl_sort_vector_uchar.h" #include "gsl_sort_vector_char.h" #endif /* __GSL_SORT_VECTOR_H__ */ sources_5316/external/gsl/gsl_specfunc__bessel_Y1.c0000664000176700017670000001021411723710247021222 0ustar paulpaul/* specfunc/bessel_Y1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_amp_phase.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besy1, 1977 version, w. fullerton */ /* chebyshev expansions series for by1 on the interval 0. to 1.60000d+01 with weighted error 1.87e-18 log weighted error 17.73 significant figures required 17.83 decimal places required 18.30 */ static double by1_data[14] = { 0.03208047100611908629, 1.262707897433500450, 0.00649996189992317500, -0.08936164528860504117, 0.01325088122175709545, -0.00089790591196483523, 0.00003647361487958306, -0.00000100137438166600, 0.00000001994539657390, -0.00000000030230656018, 0.00000000000360987815, -0.00000000000003487488, 0.00000000000000027838, -0.00000000000000000186 }; static cheb_series by1_cs = { by1_data, 13, -1, 1, 10 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Y1_e(const double x, gsl_sf_result * result) { const double two_over_pi = 2.0/M_PI; const double xmin = 1.571*GSL_DBL_MIN; /*exp ( amax1(alog(r1mach(1)), -alog(r1mach(2)))+.01) */ const double x_small = 2.0 * GSL_SQRT_DBL_EPSILON; const double xmax = 1.0/GSL_DBL_EPSILON; /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < xmin) { OVERFLOW_ERROR(result); } else if(x < x_small) { const double lnterm = log(0.5*x); gsl_sf_result J1; gsl_sf_result c; int status = gsl_sf_bessel_J1_e(x, &J1); cheb_eval_e(&by1_cs, -1.0, &c); result->val = two_over_pi * lnterm * J1.val + (0.5 + c.val)/x; result->err = fabs(lnterm) * (fabs(GSL_DBL_EPSILON * J1.val) + J1.err) + c.err/x; return status; } else if(x < 4.0) { const double lnterm = log(0.5*x); int status; gsl_sf_result J1; gsl_sf_result c; cheb_eval_e(&by1_cs, 0.125*x*x-1.0, &c); status = gsl_sf_bessel_J1_e(x, &J1); result->val = two_over_pi * lnterm * J1.val + (0.5 + c.val)/x; result->err = fabs(lnterm) * (fabs(GSL_DBL_EPSILON * J1.val) + J1.err) + c.err/x; return status; } else if(x < xmax) { const double z = 32.0/(x*x) - 1.0; gsl_sf_result ca; gsl_sf_result ct; gsl_sf_result cp; const int stat_ca = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bm1_cs, z, &ca); const int stat_ct = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bth1_cs, z, &ct); const int stat_cp = gsl_sf_bessel_cos_pi4_e(x, ct.val/x, &cp); const double sqrtx = sqrt(x); const double ampl = (0.75 + ca.val) / sqrtx; result->val = -ampl * cp.val; result->err = fabs(cp.val) * ca.err/sqrtx + fabs(ampl) * cp.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_ca, stat_ct, stat_cp); } else { UNDERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_Y1(const double x) { EVAL_RESULT(gsl_sf_bessel_Y1_e(x, &result)); } sources_5316/external/gsl/gsl_cdf__poisson.c0000664000176700017670000000357411723710247020027 0ustar paulpaul/* cdf/poisson.c * * Copyright (C) 2004 Jason H. Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * Computes the cumulative distribution function for a Poisson * random variable. For a Poisson random variable X with parameter * mu, * * Pr( X <= k ) = Pr( Y >= p ) * * where Y is a gamma random variable with parameters k+1 and 1. * * Reference: * * W. Feller, "An Introduction to Probability and Its * Applications," volume 1. Wiley, 1968. Exercise 46, page 173, * chapter 6. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_cdf.h" #include "gsl_cdf__error.h" /* * Pr (X <= k) for a Poisson random variable X. */ double gsl_cdf_poisson_P (const unsigned int k, const double mu) { double P; double a; if (mu <= 0.0) { CDF_ERROR ("mu <= 0", GSL_EDOM); } a = (double) k + 1.0; P = gsl_cdf_gamma_Q (mu, a, 1.0); return P; } /* * Pr ( X > k ) for a Possion random variable X. */ double gsl_cdf_poisson_Q (const unsigned int k, const double mu) { double Q; double a; if (mu <= 0.0) { CDF_ERROR ("mu <= 0", GSL_EDOM); } a = (double) k + 1.0; Q = gsl_cdf_gamma_P (mu, a, 1.0); return Q; } sources_5316/external/gsl/gsl_multiroots__convergence.c0000664000176700017670000000375611723710247022322 0ustar paulpaul/* multiroots/convergence.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multiroots.h" int gsl_multiroot_test_delta (const gsl_vector * dx, const gsl_vector * x, double epsabs, double epsrel) { size_t i; int ok = 1; const size_t n = x->size ; if (epsrel < 0.0) { GSL_ERROR ("relative tolerance is negative", GSL_EBADTOL); } for (i = 0 ; i < n ; i++) { double xi = gsl_vector_get(x,i); double dxi = gsl_vector_get(dx,i); double tolerance = epsabs + epsrel * fabs(xi) ; if (fabs(dxi) < tolerance) { ok = 1; } else { ok = 0; break; } } if (ok) return GSL_SUCCESS ; return GSL_CONTINUE; } int gsl_multiroot_test_residual (const gsl_vector * f, double epsabs) { size_t i; double residual = 0; const size_t n = f->size; if (epsabs < 0.0) { GSL_ERROR ("absolute tolerance is negative", GSL_EBADTOL); } for (i = 0 ; i < n ; i++) { double fi = gsl_vector_get(f, i); residual += fabs(fi); } if (residual < epsabs) { return GSL_SUCCESS; } return GSL_CONTINUE ; } sources_5316/external/gsl/gsl_multimin__vector_bfgs.c0000664000176700017670000002075411723710247021741 0ustar paulpaul/* multimin/vector_bfgs.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Fabrice Rossi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* vector_bfgs.c -- Limited memory Broyden-Fletcher-Goldfarb-Shanno method */ /* Modified by Brian Gough to use single iteration structure */ #include "gsl__config.h" #include "gsl_multimin.h" #include "gsl_blas.h" #include "gsl_multimin__directional_minimize.c" typedef struct { int iter; double step; double max_step; double tol; gsl_vector *x1; gsl_vector *dx1; gsl_vector *x2; double g0norm; double pnorm; gsl_vector *p; gsl_vector *x0; gsl_vector *g0; gsl_vector *dx0; gsl_vector *dg0; } vector_bfgs_state_t; static int vector_bfgs_alloc (void *vstate, size_t n) { vector_bfgs_state_t *state = (vector_bfgs_state_t *) vstate; state->x1 = gsl_vector_calloc (n); if (state->x1 == 0) { GSL_ERROR ("failed to allocate space for x1", GSL_ENOMEM); } state->dx1 = gsl_vector_calloc (n); if (state->dx1 == 0) { gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for dx1", GSL_ENOMEM); } state->x2 = gsl_vector_calloc (n); if (state->x2 == 0) { gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for x2", GSL_ENOMEM); } state->p = gsl_vector_calloc (n); if (state->p == 0) { gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for p", GSL_ENOMEM); } state->x0 = gsl_vector_calloc (n); if (state->x0 == 0) { gsl_vector_free (state->p); gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } state->g0 = gsl_vector_calloc (n); if (state->g0 == 0) { gsl_vector_free (state->x0); gsl_vector_free (state->p); gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } state->dx0 = gsl_vector_calloc (n); if (state->dx0 == 0) { gsl_vector_free (state->g0); gsl_vector_free (state->x0); gsl_vector_free (state->p); gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } state->dg0 = gsl_vector_calloc (n); if (state->dg0 == 0) { gsl_vector_free (state->dx0); gsl_vector_free (state->g0); gsl_vector_free (state->x0); gsl_vector_free (state->p); gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } return GSL_SUCCESS; } static int vector_bfgs_set (void *vstate, gsl_multimin_function_fdf * fdf, const gsl_vector * x, double *f, gsl_vector * gradient, double step_size, double tol) { vector_bfgs_state_t *state = (vector_bfgs_state_t *) vstate; state->iter = 0; state->step = step_size; state->max_step = step_size; state->tol = tol; GSL_MULTIMIN_FN_EVAL_F_DF (fdf, x, f, gradient); /* Use the gradient as the initial direction */ gsl_vector_memcpy (state->x0, x); gsl_vector_memcpy (state->p, gradient); gsl_vector_memcpy (state->g0, gradient); { double gnorm = gsl_blas_dnrm2 (gradient); state->pnorm = gnorm; state->g0norm = gnorm; } return GSL_SUCCESS; } static void vector_bfgs_free (void *vstate) { vector_bfgs_state_t *state = (vector_bfgs_state_t *) vstate; gsl_vector_free (state->dg0); gsl_vector_free (state->dx0); gsl_vector_free (state->g0); gsl_vector_free (state->x0); gsl_vector_free (state->p); gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); } static int vector_bfgs_restart (void *vstate) { vector_bfgs_state_t *state = (vector_bfgs_state_t *) vstate; state->iter = 0; return GSL_SUCCESS; } static int vector_bfgs_iterate (void *vstate, gsl_multimin_function_fdf * fdf, gsl_vector * x, double *f, gsl_vector * gradient, gsl_vector * dx) { vector_bfgs_state_t *state = (vector_bfgs_state_t *) vstate; gsl_vector *x1 = state->x1; gsl_vector *dx1 = state->dx1; gsl_vector *x2 = state->x2; gsl_vector *p = state->p; gsl_vector *g0 = state->g0; gsl_vector *x0 = state->x0; double pnorm = state->pnorm; double g0norm = state->g0norm; double fa = *f, fb, fc; double dir; double stepa = 0.0, stepb, stepc = state->step, tol = state->tol; double g1norm; double pg; if (pnorm == 0.0 || g0norm == 0.0) { gsl_vector_set_zero (dx); return GSL_ENOPROG; } /* Determine which direction is downhill, +p or -p */ gsl_blas_ddot (p, gradient, &pg); dir = (pg >= 0.0) ? +1.0 : -1.0; /* Compute new trial point at x_c= x - step * p, where p is the current direction */ take_step (x, p, stepc, dir / pnorm, x1, dx); /* Evaluate function and gradient at new point xc */ fc = GSL_MULTIMIN_FN_EVAL_F (fdf, x1); if (fc < fa) { /* Success, reduced the function value */ state->step = stepc * 2.0; *f = fc; gsl_vector_memcpy (x, x1); GSL_MULTIMIN_FN_EVAL_DF (fdf, x1, gradient); return GSL_SUCCESS; } #ifdef DEBUG printf ("got stepc = %g fc = %g\n", stepc, fc); #endif /* Do a line minimisation in the region (xa,fa) (xc,fc) to find an intermediate (xb,fb) satisifying fa > fb < fc. Choose an initial xb based on parabolic interpolation */ intermediate_point (fdf, x, p, dir / pnorm, pg, stepa, stepc, fa, fc, x1, dx1, gradient, &stepb, &fb); if (stepb == 0.0) { return GSL_ENOPROG; } minimize (fdf, x, p, dir / pnorm, stepa, stepb, stepc, fa, fb, fc, tol, x1, dx1, x2, dx, gradient, &(state->step), f, &g1norm); gsl_vector_memcpy (x, x2); /* Choose a new direction for the next step */ state->iter = (state->iter + 1) % x->size; if (state->iter == 0) { gsl_vector_memcpy (p, gradient); state->pnorm = g1norm; } else { /* This is the BFGS update: */ /* p' = g1 - A dx - B dg */ /* A = - (1+ dg.dg/dx.dg) B + dg.g/dx.dg */ /* B = dx.g/dx.dg */ gsl_vector *dx0 = state->dx0; gsl_vector *dg0 = state->dg0; double dxg, dgg, dxdg, dgnorm, A, B; /* dx0 = x - x0 */ gsl_vector_memcpy (dx0, x); gsl_blas_daxpy (-1.0, x0, dx0); /* dg0 = g - g0 */ gsl_vector_memcpy (dg0, gradient); gsl_blas_daxpy (-1.0, g0, dg0); gsl_blas_ddot (dx0, gradient, &dxg); gsl_blas_ddot (dg0, gradient, &dgg); gsl_blas_ddot (dx0, dg0, &dxdg); dgnorm = gsl_blas_dnrm2 (dg0); if (dxdg != 0) { B = dxg / dxdg; A = -(1.0 + dgnorm * dgnorm / dxdg) * B + dgg / dxdg; } else { B = 0; A = 0; } gsl_vector_memcpy (p, gradient); gsl_blas_daxpy (-A, dx0, p); gsl_blas_daxpy (-B, dg0, p); state->pnorm = gsl_blas_dnrm2 (p); } gsl_vector_memcpy (g0, gradient); gsl_vector_memcpy (x0, x); state->g0norm = gsl_blas_dnrm2 (g0); #ifdef DEBUG printf ("updated directions\n"); printf ("p: "); gsl_vector_fprintf (stdout, p, "%g"); printf ("g: "); gsl_vector_fprintf (stdout, gradient, "%g"); #endif return GSL_SUCCESS; } static const gsl_multimin_fdfminimizer_type vector_bfgs_type = { "vector_bfgs", /* name */ sizeof (vector_bfgs_state_t), &vector_bfgs_alloc, &vector_bfgs_set, &vector_bfgs_iterate, &vector_bfgs_restart, &vector_bfgs_free }; const gsl_multimin_fdfminimizer_type * gsl_multimin_fdfminimizer_vector_bfgs = &vector_bfgs_type; sources_5316/external/gsl/gsl_monte.h0000664000176700017670000000310111705263724016476 0ustar paulpaul/* monte/gsl_monte.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Michael Booth * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Some things common to all the Monte-Carlo implementations */ /* Author: MJB */ #ifndef __GSL_MONTE_H__ #define __GSL_MONTE_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Hide the function type in a typedef so that we can use it in all our integration functions, and make it easy to change things. */ struct gsl_monte_function_struct { double (*f)(double * x_array, size_t dim, void * params); size_t dim; void * params; }; typedef struct gsl_monte_function_struct gsl_monte_function; #define GSL_MONTE_FN_EVAL(F,x) (*((F)->f))(x,(F)->dim,(F)->params) __END_DECLS #endif /* __GSL_MONTE_H__ */ sources_5316/external/gsl/gsl_linalg__givens.c0000664000176700017670000000255111723710247020334 0ustar paulpaul/* linalg/givens.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Generate a Givens rotation (cos,sin) which takes v=(x,y) to (|v|,0) From Golub and Van Loan, "Matrix Computations", Section 5.1.8 */ inline static void create_givens (const double a, const double b, double *c, double *s) { if (b == 0) { *c = 1; *s = 0; } else if (fabs (b) > fabs (a)) { double t = -a / b; double s1 = 1.0 / sqrt (1 + t * t); *s = s1; *c = s1 * t; } else { double t = -b / a; double c1 = 1.0 / sqrt (1 + t * t); *c = c1; *s = c1 * t; } } sources_5316/external/gsl/gsl_cdf__pareto.c0000664000176700017670000000234011723710247017615 0ustar paulpaul/* cdf/pareto.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_pareto_P (const double x, const double a, const double b) { double P; if (x < b) { P = 0; } else { P = 1 - pow(b/x, a); } return P; } double gsl_cdf_pareto_Q (const double x, const double a, const double b) { double Q; if (x < b) { Q = 1; } else { Q = pow(b/x, a); } return Q; } sources_5316/external/gsl/gsl_cdf__cauchyinv.c0000664000176700017670000000275111723710247020322 0ustar paulpaul/* cdf/cauchyinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_cauchy_Pinv (const double P, const double a) { double x; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return GSL_NEGINF; } if (P > 0.5) { x = a * tan (M_PI * (P - 0.5)); } else { x = -a / tan (M_PI * P); } return x; } double gsl_cdf_cauchy_Qinv (const double Q, const double a) { double x; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return GSL_NEGINF; } if (Q > 0.5) { x = a * tan (M_PI * (0.5 - Q)); } else { x = a / tan (M_PI * Q); } return x; } sources_5316/external/gsl/gsl_cblas__zcopy.c0000664000176700017670000000037211723710247020022 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zcopy (const int N, const void *X, const int incX, void *Y, const int incY) { #define BASE double #include "gsl_cblas__source_copy_c.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__expint3.c0000664000176700017670000000667611723710247021007 0ustar paulpaul/* specfunc/expint3.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_expint.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" static double expint3_data[24] = { 1.269198414221126014, -0.248846446384140982, 0.80526220717231041e-01, -0.25772733251968330e-01, 0.7599878873073774e-02, -0.2030695581940405e-02, 0.490834586699330e-03, -0.107682239142021e-03, 0.21551726264290e-04, -0.3956705137384e-05, 0.6699240933896e-06, -0.105132180807e-06, 0.15362580199e-07, -0.20990960364e-08, 0.2692109538e-09, -0.325195242e-10, 0.37114816e-11, -0.4013652e-12, 0.412334e-13, -0.40338e-14, 0.3766e-15, -0.336e-16, 0.29e-17, -0.2e-18 }; static cheb_series expint3_cs = { expint3_data, 23, -1.0, 1.0, 15 }; static double expint3a_data[23] = { 1.9270464955068273729, -0.349293565204813805e-01, 0.14503383718983009e-02, -0.8925336718327903e-04, 0.70542392191184e-05, -0.6671727454761e-06, 0.724267589982e-07, -0.87825825606e-08, 0.11672234428e-08, -0.1676631281e-09, 0.257550158e-10, -0.41957888e-11, 0.7201041e-12, -0.1294906e-12, 0.24287e-13, -0.47331e-14, 0.95531e-15, -0.1991e-15, 0.428e-16, -0.94e-17, 0.21e-17, -0.5e-18, 0.1e-18 }; static cheb_series expint3a_cs = { expint3a_data, 22, -1.0, 1.0, 10 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_expint_3_e(const double x, gsl_sf_result * result) { const double val_infinity = 0.892979511569249211; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 1.6*GSL_ROOT3_DBL_EPSILON) { result->val = x; result->err = 0.0; return GSL_SUCCESS; } else if(x <= 2.0) { const double t = x*x*x/4.0 - 1.0; gsl_sf_result result_c; cheb_eval_e(&expint3_cs, t, &result_c); result->val = x * result_c.val; result->err = x * result_c.err; return GSL_SUCCESS; } else if(x < pow(-GSL_LOG_DBL_EPSILON, 1.0/3.0)) { const double t = 16.0/(x*x*x) - 1.0; const double s = exp(-x*x*x)/(3.0*x*x); gsl_sf_result result_c; cheb_eval_e(&expint3a_cs, t, &result_c); result->val = val_infinity - result_c.val * s; result->err = val_infinity * GSL_DBL_EPSILON + s * result_c.err; return GSL_SUCCESS; } else { result->val = val_infinity; result->err = val_infinity * GSL_DBL_EPSILON; return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_expint_3(double x) { EVAL_RESULT(gsl_sf_expint_3_e(x, &result)); } sources_5316/external/gsl/gsl_integration__qc25s.c0000664000176700017670000001332711723710247021056 0ustar paulpaul/* integration/qc25s.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ struct fn_qaws_params { gsl_function *function; double a; double b; gsl_integration_qaws_table *table; }; static double fn_qaws (double t, void *params); static double fn_qaws_L (double x, void *params); static double fn_qaws_R (double x, void *params); static void compute_result (const double * r, const double * cheb12, const double * cheb24, double * result12, double * result24); static void qc25s (gsl_function * f, double a, double b, double a1, double b1, gsl_integration_qaws_table * t, double *result, double *abserr, int *err_reliable); static void qc25s (gsl_function * f, double a, double b, double a1, double b1, gsl_integration_qaws_table * t, double *result, double *abserr, int *err_reliable) { gsl_function weighted_function; struct fn_qaws_params fn_params; fn_params.function = f; fn_params.a = a; fn_params.b = b; fn_params.table = t; weighted_function.params = &fn_params; if (a1 == a && (t->alpha != 0.0 || t->mu != 0)) { double cheb12[13], cheb24[25]; double factor = pow(0.5 * (b1 - a1), t->alpha + 1.0); weighted_function.function = &fn_qaws_R; gsl_integration_qcheb (&weighted_function, a1, b1, cheb12, cheb24); if (t->mu == 0) { double res12 = 0, res24 = 0; double u = factor; compute_result (t->ri, cheb12, cheb24, &res12, &res24); *result = u * res24; *abserr = fabs(u * (res24 - res12)); } else { double res12a = 0, res24a = 0; double res12b = 0, res24b = 0; double u = factor * log(b1 - a1); double v = factor; compute_result (t->ri, cheb12, cheb24, &res12a, &res24a); compute_result (t->rg, cheb12, cheb24, &res12b, &res24b); *result = u * res24a + v * res24b; *abserr = fabs(u * (res24a - res12a)) + fabs(v * (res24b - res12b)); } *err_reliable = 0; return; } else if (b1 == b && (t->beta != 0.0 || t->nu != 0)) { double cheb12[13], cheb24[25]; double factor = pow(0.5 * (b1 - a1), t->beta + 1.0); weighted_function.function = &fn_qaws_L; gsl_integration_qcheb (&weighted_function, a1, b1, cheb12, cheb24); if (t->nu == 0) { double res12 = 0, res24 = 0; double u = factor; compute_result (t->rj, cheb12, cheb24, &res12, &res24); *result = u * res24; *abserr = fabs(u * (res24 - res12)); } else { double res12a = 0, res24a = 0; double res12b = 0, res24b = 0; double u = factor * log(b1 - a1); double v = factor; compute_result (t->rj, cheb12, cheb24, &res12a, &res24a); compute_result (t->rh, cheb12, cheb24, &res12b, &res24b); *result = u * res24a + v * res24b; *abserr = fabs(u * (res24a - res12a)) + fabs(v * (res24b - res12b)); } *err_reliable = 0; return; } else { double resabs, resasc; weighted_function.function = &fn_qaws; gsl_integration_qk15 (&weighted_function, a1, b1, result, abserr, &resabs, &resasc); if (*abserr == resasc) { *err_reliable = 0; } else { *err_reliable = 1; } return; } } static double fn_qaws (double x, void *params) { struct fn_qaws_params *p = (struct fn_qaws_params *) params; gsl_function *f = p->function; gsl_integration_qaws_table *t = p->table; double factor = 1.0; if (t->alpha != 0.0) factor *= pow(x - p->a, t->alpha); if (t->beta != 0.0) factor *= pow(p->b - x, t->beta); if (t->mu == 1) factor *= log(x - p->a); if (t->nu == 1) factor *= log(p->b - x); return factor * GSL_FN_EVAL (f, x); } static double fn_qaws_L (double x, void *params) { struct fn_qaws_params *p = (struct fn_qaws_params *) params; gsl_function *f = p->function; gsl_integration_qaws_table *t = p->table; double factor = 1.0; if (t->alpha != 0.0) factor *= pow(x - p->a, t->alpha); if (t->mu == 1) factor *= log(x - p->a); return factor * GSL_FN_EVAL (f, x); } static double fn_qaws_R (double x, void *params) { struct fn_qaws_params *p = (struct fn_qaws_params *) params; gsl_function *f = p->function; gsl_integration_qaws_table *t = p->table; double factor = 1.0; if (t->beta != 0.0) factor *= pow(p->b - x, t->beta); if (t->nu == 1) factor *= log(p->b - x); return factor * GSL_FN_EVAL (f, x); } static void compute_result (const double * r, const double * cheb12, const double * cheb24, double * result12, double * result24) { size_t i; double res12 = 0; double res24 = 0; for (i = 0; i < 13; i++) { res12 += r[i] * cheb12[i]; } for (i = 0; i < 25; i++) { res24 += r[i] * cheb24[i]; } *result12 = res12; *result24 = res24; } sources_5316/external/gsl/gsl_specfunc__bessel_temme.h0000664000176700017670000000234511705263724022056 0ustar paulpaul/* specfunc/bessel_temme.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef BESSEL_TEMME_H_ #define BESSEL_TEMME_H_ #include "gsl_sf_result.h" int gsl_sf_bessel_Y_temme(const double nu, const double x, gsl_sf_result * Y_nu, gsl_sf_result * Y_nup1); int gsl_sf_bessel_K_scaled_temme(const double nu, const double x, double * K_nu, double * K_nup1, double * Kp_nu); #endif /* !BESSEL_TEMME_H_ */ sources_5316/external/gsl/gsl_ode-initval__odeiv_util.h0000664000176700017670000000021311705263724022152 0ustar paulpaul#define DBL_MEMCPY(dest,src,n) memcpy((dest),(src),(n)*sizeof(double)) #define DBL_ZERO_MEMSET(dest,n) memset((dest),0,(n)*sizeof(double)) sources_5316/external/gsl/gsl_sf_erf.h0000664000176700017670000000436311705263724016633 0ustar paulpaul/* specfunc/gsl_sf_erf.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_ERF_H__ #define __GSL_SF_ERF_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Complementary Error Function * erfc(x) := 2/Sqrt[Pi] Integrate[Exp[-t^2], {t,x,Infinity}] * * exceptions: none */ int gsl_sf_erfc_e(double x, gsl_sf_result * result); double gsl_sf_erfc(double x); /* Log Complementary Error Function * * exceptions: none */ int gsl_sf_log_erfc_e(double x, gsl_sf_result * result); double gsl_sf_log_erfc(double x); /* Error Function * erf(x) := 2/Sqrt[Pi] Integrate[Exp[-t^2], {t,0,x}] * * exceptions: none */ int gsl_sf_erf_e(double x, gsl_sf_result * result); double gsl_sf_erf(double x); /* Probability functions: * Z(x) : Abramowitz+Stegun 26.2.1 * Q(x) : Abramowitz+Stegun 26.2.3 * * exceptions: none */ int gsl_sf_erf_Z_e(double x, gsl_sf_result * result); int gsl_sf_erf_Q_e(double x, gsl_sf_result * result); double gsl_sf_erf_Z(double x); double gsl_sf_erf_Q(double x); /* Hazard function, also known as the inverse Mill's ratio. * * H(x) := Z(x)/Q(x) * = Sqrt[2/Pi] Exp[-x^2 / 2] / Erfc[x/Sqrt[2]] * * exceptions: GSL_EUNDRFLW */ int gsl_sf_hazard_e(double x, gsl_sf_result * result); double gsl_sf_hazard(double x); __END_DECLS #endif /* __GSL_SF_ERF_H__ */ sources_5316/external/gsl/gsl_cdf__lognormal.c0000664000176700017670000000232011723710247020313 0ustar paulpaul/* cdf/lognormal.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_lognormal_P (const double x, const double zeta, const double sigma) { double u = (log (x) - zeta) / sigma; double P = gsl_cdf_ugaussian_P (u); return P; } double gsl_cdf_lognormal_Q (const double x, const double zeta, const double sigma) { double u = (log (x) - zeta) / sigma; double Q = gsl_cdf_ugaussian_Q (u); return Q; } sources_5316/external/gsl/gsl_randist__laplace.c0000664000176700017670000000270411723710247020640 0ustar paulpaul/* randist/laplace.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* The two-sided exponential probability distribution is p(x) dx = (1/(2 a)) * exp(-|x/a|) dx for -infty < x < infty. It is also known as the Laplace distribution. */ double gsl_ran_laplace (const gsl_rng * r, const double a) { double u; do { u = 2 * gsl_rng_uniform (r) - 1.0; } while (u == 0.0); if (u < 0) { return a * log (-u); } else { return -a * log (u); } } double gsl_ran_laplace_pdf (const double x, const double a) { double p = (1/(2*a)) * exp (-fabs (x)/a); return p; } sources_5316/external/gsl/gsl_errno.h0000664000176700017670000001351111705263724016507 0ustar paulpaul/* err/gsl_errno.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_ERRNO_H__ #define __GSL_ERRNO_H__ #include #include #include "gsl_types.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS enum { GSL_SUCCESS = 0, GSL_FAILURE = -1, GSL_CONTINUE = -2, /* iteration has not converged */ GSL_EDOM = 1, /* input domain error, e.g sqrt(-1) */ GSL_ERANGE = 2, /* output range error, e.g. exp(1e100) */ GSL_EFAULT = 3, /* invalid pointer */ GSL_EINVAL = 4, /* invalid argument supplied by user */ GSL_EFAILED = 5, /* generic failure */ GSL_EFACTOR = 6, /* factorization failed */ GSL_ESANITY = 7, /* sanity check failed - shouldn't happen */ GSL_ENOMEM = 8, /* malloc failed */ GSL_EBADFUNC = 9, /* problem with user-supplied function */ GSL_ERUNAWAY = 10, /* iterative process is out of control */ GSL_EMAXITER = 11, /* exceeded max number of iterations */ GSL_EZERODIV = 12, /* tried to divide by zero */ GSL_EBADTOL = 13, /* user specified an invalid tolerance */ GSL_ETOL = 14, /* failed to reach the specified tolerance */ GSL_EUNDRFLW = 15, /* underflow */ GSL_EOVRFLW = 16, /* overflow */ GSL_ELOSS = 17, /* loss of accuracy */ GSL_EROUND = 18, /* failed because of roundoff error */ GSL_EBADLEN = 19, /* matrix, vector lengths are not conformant */ GSL_ENOTSQR = 20, /* matrix not square */ GSL_ESING = 21, /* apparent singularity detected */ GSL_EDIVERGE = 22, /* integral or series is divergent */ GSL_EUNSUP = 23, /* requested feature is not supported by the hardware */ GSL_EUNIMPL = 24, /* requested feature not (yet) implemented */ GSL_ECACHE = 25, /* cache limit exceeded */ GSL_ETABLE = 26, /* table limit exceeded */ GSL_ENOPROG = 27, /* iteration is not making progress towards solution */ GSL_ENOPROGJ = 28, /* jacobian evaluations are not improving the solution */ GSL_ETOLF = 29, /* cannot reach the specified tolerance in F */ GSL_ETOLX = 30, /* cannot reach the specified tolerance in X */ GSL_ETOLG = 31, /* cannot reach the specified tolerance in gradient */ GSL_EOF = 32 /* end of file */ } ; void gsl_error (const char * reason, const char * file, int line, int gsl_errno); void gsl_stream_printf (const char *label, const char *file, int line, const char *reason); const char * gsl_strerror (const int gsl_errno); typedef void gsl_error_handler_t (const char * reason, const char * file, int line, int gsl_errno); typedef void gsl_stream_handler_t (const char * label, const char * file, int line, const char * reason); gsl_error_handler_t * gsl_set_error_handler (gsl_error_handler_t * new_handler); gsl_error_handler_t * gsl_set_error_handler_off (void); gsl_stream_handler_t * gsl_set_stream_handler (gsl_stream_handler_t * new_handler); FILE * gsl_set_stream (FILE * new_stream); /* GSL_ERROR: call the error handler, and return the error code */ #define GSL_ERROR(reason, gsl_errno) \ do { \ gsl_error (reason, __FILE__, __LINE__, gsl_errno) ; \ return gsl_errno ; \ } while (0) /* GSL_ERROR_VAL: call the error handler, and return the given value */ #define GSL_ERROR_VAL(reason, gsl_errno, value) \ do { \ gsl_error (reason, __FILE__, __LINE__, gsl_errno) ; \ return value ; \ } while (0) /* GSL_ERROR_VOID: call the error handler, and then return (for void functions which still need to generate an error) */ #define GSL_ERROR_VOID(reason, gsl_errno) \ do { \ gsl_error (reason, __FILE__, __LINE__, gsl_errno) ; \ return ; \ } while (0) /* GSL_ERROR_NULL suitable for out-of-memory conditions */ #define GSL_ERROR_NULL(reason, gsl_errno) GSL_ERROR_VAL(reason, gsl_errno, 0) /* Sometimes you have several status results returned from * function calls and you want to combine them in some sensible * way. You cannot produce a "total" status condition, but you can * pick one from a set of conditions based on an implied hierarchy. * * In other words: * you have: status_a, status_b, ... * you want: status = (status_a if it is bad, or status_b if it is bad,...) * * In this example you consider status_a to be more important and * it is checked first, followed by the others in the order specified. * * Here are some dumb macros to do this. */ #define GSL_ERROR_SELECT_2(a,b) ((a) != GSL_SUCCESS ? (a) : ((b) != GSL_SUCCESS ? (b) : GSL_SUCCESS)) #define GSL_ERROR_SELECT_3(a,b,c) ((a) != GSL_SUCCESS ? (a) : GSL_ERROR_SELECT_2(b,c)) #define GSL_ERROR_SELECT_4(a,b,c,d) ((a) != GSL_SUCCESS ? (a) : GSL_ERROR_SELECT_3(b,c,d)) #define GSL_ERROR_SELECT_5(a,b,c,d,e) ((a) != GSL_SUCCESS ? (a) : GSL_ERROR_SELECT_4(b,c,d,e)) #define GSL_STATUS_UPDATE(sp, s) do { if ((s) != GSL_SUCCESS) *(sp) = (s);} while(0) __END_DECLS #endif /* __GSL_ERRNO_H__ */ sources_5316/external/gsl/gsl_cblas__sswap.c0000664000176700017670000000035011723710247020007 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_sswap (const int N, float *X, const int incX, float *Y, const int incY) { #define BASE float #include "gsl_cblas__source_swap_r.h" #undef BASE } sources_5316/external/gsl/gsl_sf__bessel_J1.c0000644000176700017670000000717410707442037020016 0ustar paulpaul/* specfunc/bessel_J1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_amp_phase.h" #include "gsl_sf__cheb_eval.c" #define ROOT_EIGHT (2.0*M_SQRT2) /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besj1, 1983 version, w. fullerton */ /* chebyshev expansions series for bj1 on the interval 0. to 1.60000d+01 with weighted error 4.48e-17 log weighted error 16.35 significant figures required 15.77 decimal places required 16.89 */ static double bj1_data[12] = { -0.11726141513332787, -0.25361521830790640, 0.050127080984469569, -0.004631514809625081, 0.000247996229415914, -0.000008678948686278, 0.000000214293917143, -0.000000003936093079, 0.000000000055911823, -0.000000000000632761, 0.000000000000005840, -0.000000000000000044, }; static cheb_series bj1_cs = { bj1_data, 11, -1, 1, 8 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_J1_e(const double x, gsl_sf_result * result) { double y = fabs(x); /* CHECK_POINTER(result) */ if(y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(y < 2.0*GSL_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(y < ROOT_EIGHT * GSL_SQRT_DBL_EPSILON) { result->val = 0.5*x; result->err = 0.0; return GSL_SUCCESS; } else if(y < 4.0) { gsl_sf_result c; cheb_eval_e(&bj1_cs, 0.125*y*y-1.0, &c); result->val = x * (0.25 + c.val); result->err = fabs(x * c.err); return GSL_SUCCESS; } else { /* Because the leading term in the phase is y, * which we assume is exactly known, the error * in the cos() evaluation is bounded. */ const double z = 32.0/(y*y) - 1.0; gsl_sf_result ca; gsl_sf_result ct; gsl_sf_result sp; const int stat_ca = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bm1_cs, z, &ca); const int stat_ct = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bth1_cs, z, &ct); const int stat_sp = gsl_sf_bessel_sin_pi4_e(y, ct.val/y, &sp); const double sqrty = sqrt(y); const double ampl = (0.75 + ca.val) / sqrty; result->val = (x < 0.0 ? -ampl : ampl) * sp.val; result->err = fabs(sp.val) * ca.err/sqrty + fabs(ampl) * sp.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_ca, stat_ct, stat_sp); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_J1(const double x) { EVAL_RESULT(gsl_sf_bessel_J1_e(x, &result)); } sources_5316/external/gsl/gsl_integration__err.c0000664000176700017670000000314511723710247020706 0ustar paulpaul/* integration/err.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_integration.h" static double rescale_error (double err, const double result_abs, const double result_asc) ; static double rescale_error (double err, const double result_abs, const double result_asc) { err = fabs(err) ; if (result_asc != 0 && err != 0) { double scale = pow((200 * err / result_asc), 1.5) ; if (scale < 1) { err = result_asc * scale ; } else { err = result_asc ; } } if (result_abs > GSL_DBL_MIN / (50 * GSL_DBL_EPSILON)) { double min_err = 50 * GSL_DBL_EPSILON * result_abs ; if (min_err > err) { err = min_err ; } } return err ; } sources_5316/external/gsl/gsl_rng__transputer.c0000664000176700017670000000435511723710247020574 0ustar paulpaul/* rng/transputer.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is the INMOS Transputer Development System generator. The sequence is, x_{n+1} = (a x_n) mod m with a = 1664525 and m = 2^32. The seed specifies the initial value, x_1. The theoretical value of x_{10001} is 1244127297. The period of this generator is 2^30. */ static inline unsigned long int transputer_get (void *vstate); static double transputer_get_double (void *vstate); static void transputer_set (void *state, unsigned long int s); typedef struct { unsigned long int x; } transputer_state_t; static unsigned long int transputer_get (void *vstate) { transputer_state_t *state = (transputer_state_t *) vstate; state->x = (1664525 * state->x) & 0xffffffffUL; return state->x; } static double transputer_get_double (void *vstate) { return transputer_get (vstate) / 4294967296.0 ; } static void transputer_set (void *vstate, unsigned long int s) { transputer_state_t *state = (transputer_state_t *) vstate; if (s == 0) s = 1 ; /* default seed is 1. */ state->x = s; return; } static const gsl_rng_type transputer_type = {"transputer", /* name */ 0xffffffffUL, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (transputer_state_t), &transputer_set, &transputer_get, &transputer_get_double}; const gsl_rng_type *gsl_rng_transputer = &transputer_type; sources_5316/external/gsl/gsl_multimin__fdfminimizer.c0000664000176700017670000001006111723710247022107 0ustar paulpaul/* multimin/fdfminimizer.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Fabrice Rossi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_multimin.h" gsl_multimin_fdfminimizer * gsl_multimin_fdfminimizer_alloc (const gsl_multimin_fdfminimizer_type * T, size_t n) { int status; gsl_multimin_fdfminimizer *s = (gsl_multimin_fdfminimizer *) malloc (sizeof (gsl_multimin_fdfminimizer)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for minimizer struct", GSL_ENOMEM, 0); } s->type = T; s->x = gsl_vector_calloc (n); if (s->x == 0) { free (s); GSL_ERROR_VAL ("failed to allocate space for x", GSL_ENOMEM, 0); } s->gradient = gsl_vector_calloc (n); if (s->gradient == 0) { gsl_vector_free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for gradient", GSL_ENOMEM, 0); } s->dx = gsl_vector_calloc (n); if (s->dx == 0) { gsl_vector_free (s->x); gsl_vector_free (s->gradient); free (s); GSL_ERROR_VAL ("failed to allocate space for dx", GSL_ENOMEM, 0); } s->state = malloc (T->size); if (s->state == 0) { gsl_vector_free (s->x); gsl_vector_free (s->gradient); gsl_vector_free (s->dx); free (s); GSL_ERROR_VAL ("failed to allocate space for minimizer state", GSL_ENOMEM, 0); } status = (T->alloc) (s->state, n); if (status != GSL_SUCCESS) { free (s->state); gsl_vector_free (s->x); gsl_vector_free (s->gradient); gsl_vector_free (s->dx); free (s); GSL_ERROR_VAL ("failed to initialize minimizer state", GSL_ENOMEM, 0); } return s; } int gsl_multimin_fdfminimizer_set (gsl_multimin_fdfminimizer * s, gsl_multimin_function_fdf * fdf, const gsl_vector * x, double step_size, double tol) { if (s->x->size != fdf->n) { GSL_ERROR ("function incompatible with solver size", GSL_EBADLEN); } if (x->size != fdf->n) { GSL_ERROR ("vector length not compatible with function", GSL_EBADLEN); } s->fdf = fdf; gsl_vector_memcpy (s->x,x); gsl_vector_set_zero (s->dx); return (s->type->set) (s->state, s->fdf, s->x, &(s->f), s->gradient, step_size, tol); } void gsl_multimin_fdfminimizer_free (gsl_multimin_fdfminimizer * s) { (s->type->free) (s->state); free (s->state); gsl_vector_free (s->dx); gsl_vector_free (s->gradient); gsl_vector_free (s->x); free (s); } int gsl_multimin_fdfminimizer_iterate (gsl_multimin_fdfminimizer * s) { return (s->type->iterate) (s->state, s->fdf, s->x, &(s->f), s->gradient, s->dx); } int gsl_multimin_fdfminimizer_restart (gsl_multimin_fdfminimizer * s) { return (s->type->restart) (s->state); } const char * gsl_multimin_fdfminimizer_name (const gsl_multimin_fdfminimizer * s) { return s->type->name; } gsl_vector * gsl_multimin_fdfminimizer_x (gsl_multimin_fdfminimizer * s) { return s->x; } gsl_vector * gsl_multimin_fdfminimizer_dx (gsl_multimin_fdfminimizer * s) { return s->dx; } gsl_vector * gsl_multimin_fdfminimizer_gradient (gsl_multimin_fdfminimizer * s) { return s->gradient; } double gsl_multimin_fdfminimizer_minimum (gsl_multimin_fdfminimizer * s) { return s->f; } sources_5316/external/gsl/gsl_specfunc__hyperg_2F1.c0000664000176700017670000006602011723710247021310 0ustar paulpaul/* specfunc/hyperg_2F1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_gamma.h" #include "gsl_sf_psi.h" #include "gsl_sf_hyperg.h" #include "gsl_specfunc__error.h" #define locEPS (1000.0*GSL_DBL_EPSILON) /* Assumes c != negative integer. */ static int hyperg_2F1_series(const double a, const double b, const double c, const double x, gsl_sf_result * result ) { double sum_pos = 1.0; double sum_neg = 0.0; double del_pos = 1.0; double del_neg = 0.0; double del = 1.0; double k = 0.0; int i = 0; if(fabs(c) < GSL_DBL_EPSILON) { result->val = 0.0; /* FIXME: ?? */ result->err = 1.0; GSL_ERROR ("error", GSL_EDOM); } do { if(++i > 30000) { result->val = sum_pos - sum_neg; result->err = del_pos + del_neg; result->err += 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += 2.0 * GSL_DBL_EPSILON * (2.0*sqrt(k)+1.0) * fabs(result->val); GSL_ERROR ("error", GSL_EMAXITER); } del *= (a+k)*(b+k) * x / ((c+k) * (k+1.0)); /* Gauss series */ if(del > 0.0) { del_pos = del; sum_pos += del; } else if(del == 0.0) { /* Exact termination (a or b was a negative integer). */ del_pos = 0.0; del_neg = 0.0; break; } else { del_neg = -del; sum_neg -= del; } k += 1.0; } while(fabs((del_pos + del_neg)/(sum_pos-sum_neg)) > GSL_DBL_EPSILON); result->val = sum_pos - sum_neg; result->err = del_pos + del_neg; result->err += 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += 2.0 * GSL_DBL_EPSILON * (2.0*sqrt(k) + 1.0) * fabs(result->val); return GSL_SUCCESS; } /* a = aR + i aI, b = aR - i aI */ static int hyperg_2F1_conj_series(const double aR, const double aI, const double c, double x, gsl_sf_result * result) { if(c == 0.0) { result->val = 0.0; /* FIXME: should be Inf */ result->err = 0.0; GSL_ERROR ("error", GSL_EDOM); } else { double sum_pos = 1.0; double sum_neg = 0.0; double del_pos = 1.0; double del_neg = 0.0; double del = 1.0; double k = 0.0; do { del *= ((aR+k)*(aR+k) + aI*aI)/((k+1.0)*(c+k)) * x; if(del >= 0.0) { del_pos = del; sum_pos += del; } else { del_neg = -del; sum_neg -= del; } if(k > 30000) { result->val = sum_pos - sum_neg; result->err = del_pos + del_neg; result->err += 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += 2.0 * GSL_DBL_EPSILON * (2.0*sqrt(k)+1.0) * fabs(result->val); GSL_ERROR ("error", GSL_EMAXITER); } k += 1.0; } while(fabs((del_pos + del_neg)/(sum_pos - sum_neg)) > GSL_DBL_EPSILON); result->val = sum_pos - sum_neg; result->err = del_pos + del_neg; result->err += 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += 2.0 * GSL_DBL_EPSILON * (2.0*sqrt(k) + 1.0) * fabs(result->val); return GSL_SUCCESS; } } /* Luke's rational approximation. The most accesible * discussion is in [Kolbig, CPC 23, 51 (1981)]. * The convergence is supposedly guaranteed for x < 0. * You have to read Luke's books to see this and other * results. Unfortunately, the stability is not so * clear to me, although it seems very efficient when * it works. */ static int hyperg_2F1_luke(const double a, const double b, const double c, const double xin, gsl_sf_result * result) { int stat_iter; const double RECUR_BIG = 1.0e+50; const int nmax = 20000; int n = 3; const double x = -xin; const double x3 = x*x*x; const double t0 = a*b/c; const double t1 = (a+1.0)*(b+1.0)/(2.0*c); const double t2 = (a+2.0)*(b+2.0)/(2.0*(c+1.0)); double F = 1.0; double prec; double Bnm3 = 1.0; /* B0 */ double Bnm2 = 1.0 + t1 * x; /* B1 */ double Bnm1 = 1.0 + t2 * x * (1.0 + t1/3.0 * x); /* B2 */ double Anm3 = 1.0; /* A0 */ double Anm2 = Bnm2 - t0 * x; /* A1 */ double Anm1 = Bnm1 - t0*(1.0 + t2*x)*x + t0 * t1 * (c/(c+1.0)) * x*x; /* A2 */ while(1) { double npam1 = n + a - 1; double npbm1 = n + b - 1; double npcm1 = n + c - 1; double npam2 = n + a - 2; double npbm2 = n + b - 2; double npcm2 = n + c - 2; double tnm1 = 2*n - 1; double tnm3 = 2*n - 3; double tnm5 = 2*n - 5; double n2 = n*n; double F1 = (3.0*n2 + (a+b-6)*n + 2 - a*b - 2*(a+b)) / (2*tnm3*npcm1); double F2 = -(3.0*n2 - (a+b+6)*n + 2 - a*b)*npam1*npbm1/(4*tnm1*tnm3*npcm2*npcm1); double F3 = (npam2*npam1*npbm2*npbm1*(n-a-2)*(n-b-2)) / (8*tnm3*tnm3*tnm5*(n+c-3)*npcm2*npcm1); double E = -npam1*npbm1*(n-c-1) / (2*tnm3*npcm2*npcm1); double An = (1.0+F1*x)*Anm1 + (E + F2*x)*x*Anm2 + F3*x3*Anm3; double Bn = (1.0+F1*x)*Bnm1 + (E + F2*x)*x*Bnm2 + F3*x3*Bnm3; double r = An/Bn; prec = fabs((F - r)/F); F = r; if(prec < GSL_DBL_EPSILON || n > nmax) break; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; Anm3 /= RECUR_BIG; Bnm3 /= RECUR_BIG; } else if(fabs(An) < 1.0/RECUR_BIG || fabs(Bn) < 1.0/RECUR_BIG) { An *= RECUR_BIG; Bn *= RECUR_BIG; Anm1 *= RECUR_BIG; Bnm1 *= RECUR_BIG; Anm2 *= RECUR_BIG; Bnm2 *= RECUR_BIG; Anm3 *= RECUR_BIG; Bnm3 *= RECUR_BIG; } n++; Bnm3 = Bnm2; Bnm2 = Bnm1; Bnm1 = Bn; Anm3 = Anm2; Anm2 = Anm1; Anm1 = An; } result->val = F; result->err = 2.0 * fabs(prec * F); result->err += 2.0 * GSL_DBL_EPSILON * (n+1.0) * fabs(F); /* FIXME: just a hack: there's a lot of shit going on here */ result->err *= 8.0 * (fabs(a) + fabs(b) + 1.0); stat_iter = (n >= nmax ? GSL_EMAXITER : GSL_SUCCESS ); return stat_iter; } /* Luke's rational approximation for the * case a = aR + i aI, b = aR - i aI. */ static int hyperg_2F1_conj_luke(const double aR, const double aI, const double c, const double xin, gsl_sf_result * result) { int stat_iter; const double RECUR_BIG = 1.0e+50; const int nmax = 10000; int n = 3; const double x = -xin; const double x3 = x*x*x; const double atimesb = aR*aR + aI*aI; const double apb = 2.0*aR; const double t0 = atimesb/c; const double t1 = (atimesb + apb + 1.0)/(2.0*c); const double t2 = (atimesb + 2.0*apb + 4.0)/(2.0*(c+1.0)); double F = 1.0; double prec; double Bnm3 = 1.0; /* B0 */ double Bnm2 = 1.0 + t1 * x; /* B1 */ double Bnm1 = 1.0 + t2 * x * (1.0 + t1/3.0 * x); /* B2 */ double Anm3 = 1.0; /* A0 */ double Anm2 = Bnm2 - t0 * x; /* A1 */ double Anm1 = Bnm1 - t0*(1.0 + t2*x)*x + t0 * t1 * (c/(c+1.0)) * x*x; /* A2 */ while(1) { double nm1 = n - 1; double nm2 = n - 2; double npam1_npbm1 = atimesb + nm1*apb + nm1*nm1; double npam2_npbm2 = atimesb + nm2*apb + nm2*nm2; double npcm1 = nm1 + c; double npcm2 = nm2 + c; double tnm1 = 2*n - 1; double tnm3 = 2*n - 3; double tnm5 = 2*n - 5; double n2 = n*n; double F1 = (3.0*n2 + (apb-6)*n + 2 - atimesb - 2*apb) / (2*tnm3*npcm1); double F2 = -(3.0*n2 - (apb+6)*n + 2 - atimesb)*npam1_npbm1/(4*tnm1*tnm3*npcm2*npcm1); double F3 = (npam2_npbm2*npam1_npbm1*(nm2*nm2 - nm2*apb + atimesb)) / (8*tnm3*tnm3*tnm5*(n+c-3)*npcm2*npcm1); double E = -npam1_npbm1*(n-c-1) / (2*tnm3*npcm2*npcm1); double An = (1.0+F1*x)*Anm1 + (E + F2*x)*x*Anm2 + F3*x3*Anm3; double Bn = (1.0+F1*x)*Bnm1 + (E + F2*x)*x*Bnm2 + F3*x3*Bnm3; double r = An/Bn; prec = fabs(F - r)/fabs(F); F = r; if(prec < GSL_DBL_EPSILON || n > nmax) break; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; Anm3 /= RECUR_BIG; Bnm3 /= RECUR_BIG; } else if(fabs(An) < 1.0/RECUR_BIG || fabs(Bn) < 1.0/RECUR_BIG) { An *= RECUR_BIG; Bn *= RECUR_BIG; Anm1 *= RECUR_BIG; Bnm1 *= RECUR_BIG; Anm2 *= RECUR_BIG; Bnm2 *= RECUR_BIG; Anm3 *= RECUR_BIG; Bnm3 *= RECUR_BIG; } n++; Bnm3 = Bnm2; Bnm2 = Bnm1; Bnm1 = Bn; Anm3 = Anm2; Anm2 = Anm1; Anm1 = An; } result->val = F; result->err = 2.0 * fabs(prec * F); result->err += 2.0 * GSL_DBL_EPSILON * (n+1.0) * fabs(F); /* FIXME: see above */ result->err *= 8.0 * (fabs(aR) + fabs(aI) + 1.0); stat_iter = (n >= nmax ? GSL_EMAXITER : GSL_SUCCESS ); return stat_iter; } /* Do the reflection described in [Moshier, p. 334]. * Assumes a,b,c != neg integer. */ static int hyperg_2F1_reflect(const double a, const double b, const double c, const double x, gsl_sf_result * result) { const double d = c - a - b; const int intd = floor(d+0.5); const int d_integer = ( fabs(d - intd) < locEPS ); if(d_integer) { const double ln_omx = log(1.0 - x); const double ad = fabs(d); int stat_F2 = GSL_SUCCESS; double sgn_2; gsl_sf_result F1; gsl_sf_result F2; double d1, d2; gsl_sf_result lng_c; gsl_sf_result lng_ad2; gsl_sf_result lng_bd2; int stat_c; int stat_ad2; int stat_bd2; if(d >= 0.0) { d1 = d; d2 = 0.0; } else { d1 = 0.0; d2 = d; } stat_ad2 = gsl_sf_lngamma_e(a+d2, &lng_ad2); stat_bd2 = gsl_sf_lngamma_e(b+d2, &lng_bd2); stat_c = gsl_sf_lngamma_e(c, &lng_c); /* Evaluate F1. */ if(ad < GSL_DBL_EPSILON) { /* d = 0 */ F1.val = 0.0; F1.err = 0.0; } else { gsl_sf_result lng_ad; gsl_sf_result lng_ad1; gsl_sf_result lng_bd1; int stat_ad = gsl_sf_lngamma_e(ad, &lng_ad); int stat_ad1 = gsl_sf_lngamma_e(a+d1, &lng_ad1); int stat_bd1 = gsl_sf_lngamma_e(b+d1, &lng_bd1); if(stat_ad1 == GSL_SUCCESS && stat_bd1 == GSL_SUCCESS && stat_ad == GSL_SUCCESS) { /* Gamma functions in the denominator are ok. * Proceed with evaluation. */ int i; double sum1 = 1.0; double term = 1.0; double ln_pre1_val = lng_ad.val + lng_c.val + d2*ln_omx - lng_ad1.val - lng_bd1.val; double ln_pre1_err = lng_ad.err + lng_c.err + lng_ad1.err + lng_bd1.err + GSL_DBL_EPSILON * fabs(ln_pre1_val); int stat_e; /* Do F1 sum. */ for(i=1; ival = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EOVRFLW); } } stat_F2 = GSL_ERROR_SELECT_2(stat_F2, stat_dall); } else { /* Gamma functions in the denominator not ok. * So the F2 term is zero. */ F2.val = 0.0; F2.err = 0.0; } /* end F2 evaluation */ sgn_2 = ( GSL_IS_ODD(intd) ? -1.0 : 1.0 ); result->val = F1.val + sgn_2 * F2.val; result->err = F1.err + F2. err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(F1.val) + fabs(F2.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_F2; } else { /* d not an integer */ gsl_sf_result pre1, pre2; double sgn1, sgn2; gsl_sf_result F1, F2; int status_F1, status_F2; /* These gamma functions appear in the denominator, so we * catch their harmless domain errors and set the terms to zero. */ gsl_sf_result ln_g1ca, ln_g1cb, ln_g2a, ln_g2b; double sgn_g1ca, sgn_g1cb, sgn_g2a, sgn_g2b; int stat_1ca = gsl_sf_lngamma_sgn_e(c-a, &ln_g1ca, &sgn_g1ca); int stat_1cb = gsl_sf_lngamma_sgn_e(c-b, &ln_g1cb, &sgn_g1cb); int stat_2a = gsl_sf_lngamma_sgn_e(a, &ln_g2a, &sgn_g2a); int stat_2b = gsl_sf_lngamma_sgn_e(b, &ln_g2b, &sgn_g2b); int ok1 = (stat_1ca == GSL_SUCCESS && stat_1cb == GSL_SUCCESS); int ok2 = (stat_2a == GSL_SUCCESS && stat_2b == GSL_SUCCESS); gsl_sf_result ln_gc, ln_gd, ln_gmd; double sgn_gc, sgn_gd, sgn_gmd; gsl_sf_lngamma_sgn_e( c, &ln_gc, &sgn_gc); gsl_sf_lngamma_sgn_e( d, &ln_gd, &sgn_gd); gsl_sf_lngamma_sgn_e(-d, &ln_gmd, &sgn_gmd); sgn1 = sgn_gc * sgn_gd * sgn_g1ca * sgn_g1cb; sgn2 = sgn_gc * sgn_gmd * sgn_g2a * sgn_g2b; if(ok1 && ok2) { double ln_pre1_val = ln_gc.val + ln_gd.val - ln_g1ca.val - ln_g1cb.val; double ln_pre2_val = ln_gc.val + ln_gmd.val - ln_g2a.val - ln_g2b.val + d*log(1.0-x); double ln_pre1_err = ln_gc.err + ln_gd.err + ln_g1ca.err + ln_g1cb.err; double ln_pre2_err = ln_gc.err + ln_gmd.err + ln_g2a.err + ln_g2b.err; if(ln_pre1_val < GSL_LOG_DBL_MAX && ln_pre2_val < GSL_LOG_DBL_MAX) { gsl_sf_exp_err_e(ln_pre1_val, ln_pre1_err, &pre1); gsl_sf_exp_err_e(ln_pre2_val, ln_pre2_err, &pre2); pre1.val *= sgn1; pre2.val *= sgn2; } else { OVERFLOW_ERROR(result); } } else if(ok1 && !ok2) { double ln_pre1_val = ln_gc.val + ln_gd.val - ln_g1ca.val - ln_g1cb.val; double ln_pre1_err = ln_gc.err + ln_gd.err + ln_g1ca.err + ln_g1cb.err; if(ln_pre1_val < GSL_LOG_DBL_MAX) { gsl_sf_exp_err_e(ln_pre1_val, ln_pre1_err, &pre1); pre1.val *= sgn1; pre2.val = 0.0; pre2.err = 0.0; } else { OVERFLOW_ERROR(result); } } else if(!ok1 && ok2) { double ln_pre2_val = ln_gc.val + ln_gmd.val - ln_g2a.val - ln_g2b.val + d*log(1.0-x); double ln_pre2_err = ln_gc.err + ln_gmd.err + ln_g2a.err + ln_g2b.err; if(ln_pre2_val < GSL_LOG_DBL_MAX) { pre1.val = 0.0; pre1.err = 0.0; gsl_sf_exp_err_e(ln_pre2_val, ln_pre2_err, &pre2); pre2.val *= sgn2; } else { OVERFLOW_ERROR(result); } } else { pre1.val = 0.0; pre2.val = 0.0; UNDERFLOW_ERROR(result); } status_F1 = hyperg_2F1_series( a, b, 1.0-d, 1.0-x, &F1); status_F2 = hyperg_2F1_series(c-a, c-b, 1.0+d, 1.0-x, &F2); result->val = pre1.val*F1.val + pre2.val*F2.val; result->err = fabs(pre1.val*F1.err) + fabs(pre2.val*F2.err); result->err += fabs(pre1.err*F1.val) + fabs(pre2.err*F2.val); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(pre1.val*F1.val) + fabs(pre2.val*F2.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } static int pow_omx(const double x, const double p, gsl_sf_result * result) { double ln_omx; double ln_result; if(fabs(x) < GSL_ROOT5_DBL_EPSILON) { ln_omx = -x*(1.0 + x*(1.0/2.0 + x*(1.0/3.0 + x/4.0 + x*x/5.0))); } else { ln_omx = log(1.0-x); } ln_result = p * ln_omx; return gsl_sf_exp_err_e(ln_result, GSL_DBL_EPSILON * fabs(ln_result), result); } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_hyperg_2F1_e(double a, double b, const double c, const double x, gsl_sf_result * result) { const double d = c - a - b; const double rinta = floor(a + 0.5); const double rintb = floor(b + 0.5); const double rintc = floor(c + 0.5); const int a_neg_integer = ( a < 0.0 && fabs(a - rinta) < locEPS ); const int b_neg_integer = ( b < 0.0 && fabs(b - rintb) < locEPS ); const int c_neg_integer = ( c < 0.0 && fabs(c - rintc) < locEPS ); result->val = 0.0; result->err = 0.0; if(x < -1.0 || 1.0 <= x) { DOMAIN_ERROR(result); } if(c_neg_integer) { if(! (a_neg_integer && a > c + 0.1)) DOMAIN_ERROR(result); if(! (b_neg_integer && b > c + 0.1)) DOMAIN_ERROR(result); } if(fabs(c-b) < locEPS || fabs(c-a) < locEPS) { return pow_omx(x, d, result); /* (1-x)^(c-a-b) */ } if(a >= 0.0 && b >= 0.0 && c >=0.0 && x >= 0.0 && x < 0.995) { /* Series has all positive definite * terms and x is not close to 1. */ return hyperg_2F1_series(a, b, c, x, result); } if(fabs(a) < 10.0 && fabs(b) < 10.0) { /* a and b are not too large, so we attempt * variations on the series summation. */ if(a_neg_integer) { return hyperg_2F1_series(rinta, b, c, x, result); } if(b_neg_integer) { return hyperg_2F1_series(a, rintb, c, x, result); } if(x < -0.25) { return hyperg_2F1_luke(a, b, c, x, result); } else if(x < 0.5) { return hyperg_2F1_series(a, b, c, x, result); } else { if(fabs(c) > 10.0) { return hyperg_2F1_series(a, b, c, x, result); } else { return hyperg_2F1_reflect(a, b, c, x, result); } } } else { /* Either a or b or both large. * Introduce some new variables ap,bp so that bp is * the larger in magnitude. */ double ap, bp; if(fabs(a) > fabs(b)) { bp = a; ap = b; } else { bp = b; ap = a; } if(x < 0.0) { /* What the hell, maybe Luke will converge. */ return hyperg_2F1_luke(a, b, c, x, result); } if(GSL_MAX_DBL(fabs(a),1.0)*fabs(bp)*fabs(x) < 2.0*fabs(c)) { /* If c is large enough or x is small enough, * we can attempt the series anyway. */ return hyperg_2F1_series(a, b, c, x, result); } if(fabs(bp*bp*x*x) < 0.001*fabs(bp) && fabs(a) < 10.0) { /* The famous but nearly worthless "large b" asymptotic. */ int stat = gsl_sf_hyperg_1F1_e(a, c, bp*x, result); result->err = 0.001 * fabs(result->val); return stat; } /* We give up. */ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EUNIMPL); } } int gsl_sf_hyperg_2F1_conj_e(const double aR, const double aI, const double c, const double x, gsl_sf_result * result) { const double ax = fabs(x); const double rintc = floor(c + 0.5); const int c_neg_integer = ( c < 0.0 && fabs(c - rintc) < locEPS ); result->val = 0.0; result->err = 0.0; if(ax >= 1.0 || c_neg_integer || c == 0.0) { DOMAIN_ERROR(result); } if( (ax < 0.25 && fabs(aR) < 20.0 && fabs(aI) < 20.0) || (c > 0.0 && x > 0.0) ) { return hyperg_2F1_conj_series(aR, aI, c, x, result); } else if(fabs(aR) < 10.0 && fabs(aI) < 10.0) { if(x < -0.25) { return hyperg_2F1_conj_luke(aR, aI, c, x, result); } else { return hyperg_2F1_conj_series(aR, aI, c, x, result); } } else { if(x < 0.0) { /* What the hell, maybe Luke will converge. */ return hyperg_2F1_conj_luke(aR, aI, c, x, result); } /* Give up. */ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EUNIMPL); } } int gsl_sf_hyperg_2F1_renorm_e(const double a, const double b, const double c, const double x, gsl_sf_result * result ) { const double rinta = floor(a + 0.5); const double rintb = floor(b + 0.5); const double rintc = floor(c + 0.5); const int a_neg_integer = ( a < 0.0 && fabs(a - rinta) < locEPS ); const int b_neg_integer = ( b < 0.0 && fabs(b - rintb) < locEPS ); const int c_neg_integer = ( c < 0.0 && fabs(c - rintc) < locEPS ); if(c_neg_integer) { if((a_neg_integer && a > c+0.1) || (b_neg_integer && b > c+0.1)) { /* 2F1 terminates early */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* 2F1 does not terminate early enough, so something survives */ /* [Abramowitz+Stegun, 15.1.2] */ gsl_sf_result g1, g2, g3, g4, g5; double s1, s2, s3, s4, s5; int stat = 0; stat += gsl_sf_lngamma_sgn_e(a-c+1, &g1, &s1); stat += gsl_sf_lngamma_sgn_e(b-c+1, &g2, &s2); stat += gsl_sf_lngamma_sgn_e(a, &g3, &s3); stat += gsl_sf_lngamma_sgn_e(b, &g4, &s4); stat += gsl_sf_lngamma_sgn_e(-c+2, &g5, &s5); if(stat != 0) { DOMAIN_ERROR(result); } else { gsl_sf_result F; int stat_F = gsl_sf_hyperg_2F1_e(a-c+1, b-c+1, -c+2, x, &F); double ln_pre_val = g1.val + g2.val - g3.val - g4.val - g5.val; double ln_pre_err = g1.err + g2.err + g3.err + g4.err + g5.err; double sg = s1 * s2 * s3 * s4 * s5; int stat_e = gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, sg * F.val, F.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_F); } } } else { /* generic c */ gsl_sf_result F; gsl_sf_result lng; double sgn; int stat_g = gsl_sf_lngamma_sgn_e(c, &lng, &sgn); int stat_F = gsl_sf_hyperg_2F1_e(a, b, c, x, &F); int stat_e = gsl_sf_exp_mult_err_e(-lng.val, lng.err, sgn*F.val, F.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_F, stat_g); } } int gsl_sf_hyperg_2F1_conj_renorm_e(const double aR, const double aI, const double c, const double x, gsl_sf_result * result ) { const double rintc = floor(c + 0.5); const double rinta = floor(aR + 0.5); const int a_neg_integer = ( aR < 0.0 && fabs(aR-rinta) < locEPS && aI == 0.0); const int c_neg_integer = ( c < 0.0 && fabs(c - rintc) < locEPS ); if(c_neg_integer) { if(a_neg_integer && aR > c+0.1) { /* 2F1 terminates early */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* 2F1 does not terminate early enough, so something survives */ /* [Abramowitz+Stegun, 15.1.2] */ gsl_sf_result g1, g2; gsl_sf_result g3; gsl_sf_result a1, a2; int stat = 0; stat += gsl_sf_lngamma_complex_e(aR-c+1, aI, &g1, &a1); stat += gsl_sf_lngamma_complex_e(aR, aI, &g2, &a2); stat += gsl_sf_lngamma_e(-c+2.0, &g3); if(stat != 0) { DOMAIN_ERROR(result); } else { gsl_sf_result F; int stat_F = gsl_sf_hyperg_2F1_conj_e(aR-c+1, aI, -c+2, x, &F); double ln_pre_val = 2.0*(g1.val - g2.val) - g3.val; double ln_pre_err = 2.0 * (g1.err + g2.err) + g3.err; int stat_e = gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, F.val, F.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_F); } } } else { /* generic c */ gsl_sf_result F; gsl_sf_result lng; double sgn; int stat_g = gsl_sf_lngamma_sgn_e(c, &lng, &sgn); int stat_F = gsl_sf_hyperg_2F1_conj_e(aR, aI, c, x, &F); int stat_e = gsl_sf_exp_mult_err_e(-lng.val, lng.err, sgn*F.val, F.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_F, stat_g); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_hyperg_2F1(double a, double b, double c, double x) { EVAL_RESULT(gsl_sf_hyperg_2F1_e(a, b, c, x, &result)); } double gsl_sf_hyperg_2F1_conj(double aR, double aI, double c, double x) { EVAL_RESULT(gsl_sf_hyperg_2F1_conj_e(aR, aI, c, x, &result)); } double gsl_sf_hyperg_2F1_renorm(double a, double b, double c, double x) { EVAL_RESULT(gsl_sf_hyperg_2F1_renorm_e(a, b, c, x, &result)); } double gsl_sf_hyperg_2F1_conj_renorm(double aR, double aI, double c, double x) { EVAL_RESULT(gsl_sf_hyperg_2F1_conj_renorm_e(aR, aI, c, x, &result)); } sources_5316/external/gsl/gsl_randist__landau.c0000664000176700017670000005111511723710247020503 0ustar paulpaul/* randist/landau.c * * Copyright (C) 2001, 2004 David Morrison * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Adapted from the CERN library routines DENLAN, RANLAN, and DISLAN * as described in http://consult.cern.ch/shortwrups/g110/top.html. * Original author: K.S. K\"olbig. * * The distribution is given by the complex path integral, * * p(x) = (1/(2 pi i)) \int_{c-i\inf}^{c+i\inf} ds exp(s log(s) + x s) * * which can be converted into a real integral over [0,+\inf] * * p(x) = (1/pi) \int_0^\inf dt \exp(-t log(t) - x t) sin(pi t) * */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" double gsl_ran_landau_pdf(const double x) { static double P1[5] = { 0.4259894875E0, -0.1249762550E0, 0.3984243700E-1, -0.6298287635E-2, 0.1511162253E-2 }; static double P2[5] = { 0.1788541609E0, 0.1173957403E0, 0.1488850518E-1, -0.1394989411E-2, 0.1283617211E-3 }; static double P3[5] = { 0.1788544503E0, 0.9359161662E-1, 0.6325387654E-2, 0.6611667319E-4, -0.2031049101E-5 }; static double P4[5] = { 0.9874054407E0, 0.1186723273E3, 0.8492794360E3, -0.7437792444E3, 0.4270262186E3 }; static double P5[5] = { 0.1003675074E1, 0.1675702434E3, 0.4789711289E4, 0.2121786767E5, -0.2232494910E5 }; static double P6[5] = { 0.1000827619E1, 0.6649143136E3, 0.6297292665E5, 0.4755546998E6, -0.5743609109E7 }; static double Q1[5] = { 1.0, -0.3388260629E0, 0.9594393323E-1, -0.1608042283E-1, 0.3778942063E-2 }; static double Q2[5] = { 1.0, 0.7428795082E0, 0.3153932961E0, 0.6694219548E-1, 0.8790609714E-2 }; static double Q3[5] = { 1.0, 0.6097809921E0, 0.2560616665E0, 0.4746722384E-1, 0.6957301675E-2 }; static double Q4[5] = { 1.0, 0.1068615961E3, 0.3376496214E3, 0.2016712389E4, 0.1597063511E4 }; static double Q5[5] = { 1.0, 0.1569424537E3, 0.3745310488E4, 0.9834698876E4, 0.6692428357E5 }; static double Q6[5] = { 1.0, 0.6514101098E3, 0.5697473333E5, 0.1659174725E6, -0.2815759939E7 }; static double A1[3] = { 0.4166666667E-1, -0.1996527778E-1, 0.2709538966E-1 }; static double A2[2] = { -0.1845568670E1, -0.4284640743E1 }; double U, V, DENLAN; V = x; if (V < -5.5) { U = exp(V + 1.0); DENLAN = 0.3989422803 * (exp( -1 / U) / sqrt(U)) * (1 + (A1[0] + (A1[1] + A1[2] * U) * U) * U); } else if (V < -1) { U = exp( -V - 1); DENLAN = exp( -U) * sqrt(U) * (P1[0] + (P1[1] + (P1[2] + (P1[3] + P1[4] * V) * V) * V) * V) / (Q1[0] + (Q1[1] + (Q1[2] + (Q1[3] + Q1[4] * V) * V) * V) * V); } else if (V < 1) { DENLAN = (P2[0] + (P2[1] + (P2[2] + (P2[3] + P2[4] * V) * V) * V) * V) / (Q2[0] + (Q2[1] + (Q2[2] + (Q2[3] + Q2[4] * V) * V) * V) * V); } else if (V < 5) { DENLAN = (P3[0] + (P3[1] + (P3[2] + (P3[3] + P3[4] * V) * V) * V) * V) / (Q3[0] + (Q3[1] + (Q3[2] + (Q3[3] + Q3[4] * V) * V) * V) * V); } else if (V < 12) { U = 1 / V; DENLAN = U * U * (P4[0] + (P4[1] + (P4[2] + (P4[3] + P4[4] * U) * U) * U) * U) / (Q4[0] + (Q4[1] + (Q4[2] + (Q4[3] + Q4[4] * U) * U) * U) * U); } else if (V < 50) { U = 1 / V; DENLAN = U * U * (P5[0] + (P5[1] + (P5[2] + (P5[3] + P5[4] * U) * U) * U) * U) / (Q5[0] + (Q5[1] + (Q5[2] + (Q5[3] + Q5[4] * U) * U) * U) * U); } else if (V < 300) { U = 1 / V; DENLAN = U * U * (P6[0] + (P6[1] + (P6[2] + (P6[3] + P6[4] * U) * U) * U) * U) / (Q6[0] + (Q6[1] + (Q6[2] + (Q6[3] + Q6[4] * U) * U) * U) * U); } else { U = 1 / (V - V * log(V) / (V + 1)); DENLAN = U * U * (1 + (A2[0] + A2[1] * U) * U); } return DENLAN; } #if 0 /* Not needed yet */ /* This function is a translation from the original Fortran of the * CERN library routine DISLAN, the integral from -inf to x of the * Landau p.d.f. */ static double gsl_ran_landau_dislan(const double x) { static double P1[5] = { 0.2514091491E0, -0.6250580444E-1, 0.1458381230E-1, -0.2108817737E-2, 0.7411247290E-3 }; static double P2[4] = { 0.2868328584E0, 0.3564363231E0, 0.1523518695E0, 0.2251304883E-1 }; static double P3[4] = { 0.2868329066E0, 0.3003828436E0, 0.9950951941E-1, 0.8733827185E-2 }; static double P4[4] = { 0.1000351630E1, 0.4503592498E1, 0.1085883880E2, 0.7536052269E1 }; static double P5[4] = { 0.1000006517E1, 0.4909414111E2, 0.8505544753E2, 0.1532153455E3 }; static double P6[4] = { 0.1000000983E1, 0.1329868456E3, 0.9162149244E3, -0.9605054274E3 }; static double Q1[5] = { 1.0, -0.5571175625E-2, 0.6225310236E-1, -0.3137378427E-2, 0.1931496439E-2 }; static double Q2[4] = { 1.0, 0.6191136137E0, 0.1720721448E0, 0.2278594771E-1 }; static double Q3[4] = { 1.0, 0.4237190502E0, 0.1095631512E0, 0.8693851567E-2 }; static double Q4[4] = { 1.0, 0.5539969678E1, 0.1933581111E2, 0.2721321508E2 }; static double Q5[4] = { 1.0, 0.5009928881E2, 0.1399819104E3, 0.4200002909E3 }; static double Q6[4] = { 1.0, 0.1339887843E3, 0.1055990413E4, 0.5532224619E3 }; static double A1[3] = { -0.4583333333E0, 0.6675347222E0, -0.1641741416E1 }; static double A2[3] = { 1.0, -0.4227843351E0, -0.2043403138E1 }; double U, V, DISLAN; V = x; if (V < -5.5) { U = exp(V + 1); DISLAN = 0.3989422803 * exp( -1 / U) * sqrt(U) * (1 + (A1[0] + (A1[1] + A1[2] * U) * U) * U); } else if (V < -1) { U = exp( -V - 1); DISLAN = (exp( -U) / sqrt(U)) * (P1[0] + (P1[1] + (P1[2] + (P1[3] + P1[4] * V) * V) * V) * V) / (Q1[0] + (Q1[1] + (Q1[2] + (Q1[3] + Q1[4] * V) * V) * V) * V); } else if (V < 1) { DISLAN = (P2[0] + (P2[1] + (P2[2] + P2[3] * V) * V) * V) / (Q2[0] + (Q2[1] + (Q2[2] + Q2[3] * V) * V) * V); } else if (V < 4) { DISLAN = (P3[0] + (P3[1] + (P3[2] + P3[3] * V) * V) * V) / (Q3[0] + (Q3[1] + (Q3[2] + Q3[3] * V) * V) * V); } else if (V < 12) { U = 1 / V; DISLAN = (P4[0] + (P4[1] + (P4[2] + P4[3] * U) * U) * U) / (Q4[0] + (Q4[1] + (Q4[2] + Q4[3] * U) * U) * U); } else if (V < 50) { U = 1 / V; DISLAN = (P5[0] + (P5[1] + (P5[2] + P5[3] * U) * U) * U) / (Q5[0] + (Q5[1] + (Q5[2] + Q5[3] * U) * U) * U); } else if (V < 300) { U = 1 / V; DISLAN = (P6[0] + (P6[1] + (P6[2] + P6[3] * U) * U) * U) / (Q6[0] + (Q6[1] + (Q6[2] + Q6[3] * U) * U) * U); } else { U = 1 / (V - V * log(V) / (V + 1)); DISLAN = 1 - (A2[0] + (A2[1] + A2[2] * U) * U) * U; } return DISLAN; } #endif double gsl_ran_landau(const gsl_rng * r) { static double F[983] = { 0.0000000, /* Add empty element [0] to account for difference between C and Fortran convention for lower bound. */ 00.000000, 00.000000, 00.000000, 00.000000, 00.000000, -2.244733, -2.204365, -2.168163, -2.135219, -2.104898, -2.076740, -2.050397, -2.025605, -2.002150, -1.979866, -1.958612, -1.938275, -1.918760, -1.899984, -1.881879, -1.864385, -1.847451, -1.831030, -1.815083, -1.799574, -1.784473, -1.769751, -1.755383, -1.741346, -1.727620, -1.714187, -1.701029, -1.688130, -1.675477, -1.663057, -1.650858, -1.638868, -1.627078, -1.615477, -1.604058, -1.592811, -1.581729, -1.570806, -1.560034, -1.549407, -1.538919, -1.528565, -1.518339, -1.508237, -1.498254, -1.488386, -1.478628, -1.468976, -1.459428, -1.449979, -1.440626, -1.431365, -1.422195, -1.413111, -1.404112, -1.395194, -1.386356, -1.377594, -1.368906, -1.360291, -1.351746, -1.343269, -1.334859, -1.326512, -1.318229, -1.310006, -1.301843, -1.293737, -1.285688, -1.277693, -1.269752, -1.261863, -1.254024, -1.246235, -1.238494, -1.230800, -1.223153, -1.215550, -1.207990, -1.200474, -1.192999, -1.185566, -1.178172, -1.170817, -1.163500, -1.156220, -1.148977, -1.141770, -1.134598, -1.127459, -1.120354, -1.113282, -1.106242, -1.099233, -1.092255, -1.085306, -1.078388, -1.071498, -1.064636, -1.057802, -1.050996, -1.044215, -1.037461, -1.030733, -1.024029, -1.017350, -1.010695, -1.004064, -0.997456, -0.990871, -0.984308, -0.977767, -0.971247, -0.964749, -0.958271, -0.951813, -0.945375, -0.938957, -0.932558, -0.926178, -0.919816, -0.913472, -0.907146, -0.900838, -0.894547, -0.888272, -0.882014, -0.875773, -0.869547, -0.863337, -0.857142, -0.850963, -0.844798, -0.838648, -0.832512, -0.826390, -0.820282, -0.814187, -0.808106, -0.802038, -0.795982, -0.789940, -0.783909, -0.777891, -0.771884, -0.765889, -0.759906, -0.753934, -0.747973, -0.742023, -0.736084, -0.730155, -0.724237, -0.718328, -0.712429, -0.706541, -0.700661, -0.694791, -0.688931, -0.683079, -0.677236, -0.671402, -0.665576, -0.659759, -0.653950, -0.648149, -0.642356, -0.636570, -0.630793, -0.625022, -0.619259, -0.613503, -0.607754, -0.602012, -0.596276, -0.590548, -0.584825, -0.579109, -0.573399, -0.567695, -0.561997, -0.556305, -0.550618, -0.544937, -0.539262, -0.533592, -0.527926, -0.522266, -0.516611, -0.510961, -0.505315, -0.499674, -0.494037, -0.488405, -0.482777, -0.477153, -0.471533, -0.465917, -0.460305, -0.454697, -0.449092, -0.443491, -0.437893, -0.432299, -0.426707, -0.421119, -0.415534, -0.409951, -0.404372, -0.398795, -0.393221, -0.387649, -0.382080, -0.376513, -0.370949, -0.365387, -0.359826, -0.354268, -0.348712, -0.343157, -0.337604, -0.332053, -0.326503, -0.320955, -0.315408, -0.309863, -0.304318, -0.298775, -0.293233, -0.287692, -0.282152, -0.276613, -0.271074, -0.265536, -0.259999, -0.254462, -0.248926, -0.243389, -0.237854, -0.232318, -0.226783, -0.221247, -0.215712, -0.210176, -0.204641, -0.199105, -0.193568, -0.188032, -0.182495, -0.176957, -0.171419, -0.165880, -0.160341, -0.154800, -0.149259, -0.143717, -0.138173, -0.132629, -0.127083, -0.121537, -0.115989, -0.110439, -0.104889, -0.099336, -0.093782, -0.088227, -0.082670, -0.077111, -0.071550, -0.065987, -0.060423, -0.054856, -0.049288, -0.043717, -0.038144, -0.032569, -0.026991, -0.021411, -0.015828, -0.010243, -0.004656, 00.000934, 00.006527, 00.012123, 00.017722, 00.023323, 00.028928, 00.034535, 00.040146, 00.045759, 00.051376, 00.056997, 00.062620, 00.068247, 00.073877, 00.079511, 00.085149, 00.090790, 00.096435, 00.102083, 00.107736, 00.113392, 00.119052, 00.124716, 00.130385, 00.136057, 00.141734, 00.147414, 00.153100, 00.158789, 00.164483, 00.170181, 00.175884, 00.181592, 00.187304, 00.193021, 00.198743, 00.204469, 00.210201, 00.215937, 00.221678, 00.227425, 00.233177, 00.238933, 00.244696, 00.250463, 00.256236, 00.262014, 00.267798, 00.273587, 00.279382, 00.285183, 00.290989, 00.296801, 00.302619, 00.308443, 00.314273, 00.320109, 00.325951, 00.331799, 00.337654, 00.343515, 00.349382, 00.355255, 00.361135, 00.367022, 00.372915, 00.378815, 00.384721, 00.390634, 00.396554, 00.402481, 00.408415, 00.414356, 00.420304, 00.426260, 00.432222, 00.438192, 00.444169, 00.450153, 00.456145, 00.462144, 00.468151, 00.474166, 00.480188, 00.486218, 00.492256, 00.498302, 00.504356, 00.510418, 00.516488, 00.522566, 00.528653, 00.534747, 00.540850, 00.546962, 00.553082, 00.559210, 00.565347, 00.571493, 00.577648, 00.583811, 00.589983, 00.596164, 00.602355, 00.608554, 00.614762, 00.620980, 00.627207, 00.633444, 00.639689, 00.645945, 00.652210, 00.658484, 00.664768, 00.671062, 00.677366, 00.683680, 00.690004, 00.696338, 00.702682, 00.709036, 00.715400, 00.721775, 00.728160, 00.734556, 00.740963, 00.747379, 00.753807, 00.760246, 00.766695, 00.773155, 00.779627, 00.786109, 00.792603, 00.799107, 00.805624, 00.812151, 00.818690, 00.825241, 00.831803, 00.838377, 00.844962, 00.851560, 00.858170, 00.864791, 00.871425, 00.878071, 00.884729, 00.891399, 00.898082, 00.904778, 00.911486, 00.918206, 00.924940, 00.931686, 00.938446, 00.945218, 00.952003, 00.958802, 00.965614, 00.972439, 00.979278, 00.986130, 00.992996, 00.999875, 01.006769, 01.013676, 01.020597, 01.027533, 01.034482, 01.041446, 01.048424, 01.055417, 01.062424, 01.069446, 01.076482, 01.083534, 01.090600, 01.097681, 01.104778, 01.111889, 01.119016, 01.126159, 01.133316, 01.140490, 01.147679, 01.154884, 01.162105, 01.169342, 01.176595, 01.183864, 01.191149, 01.198451, 01.205770, 01.213105, 01.220457, 01.227826, 01.235211, 01.242614, 01.250034, 01.257471, 01.264926, 01.272398, 01.279888, 01.287395, 01.294921, 01.302464, 01.310026, 01.317605, 01.325203, 01.332819, 01.340454, 01.348108, 01.355780, 01.363472, 01.371182, 01.378912, 01.386660, 01.394429, 01.402216, 01.410024, 01.417851, 01.425698, 01.433565, 01.441453, 01.449360, 01.457288, 01.465237, 01.473206, 01.481196, 01.489208, 01.497240, 01.505293, 01.513368, 01.521465, 01.529583, 01.537723, 01.545885, 01.554068, 01.562275, 01.570503, 01.578754, 01.587028, 01.595325, 01.603644, 01.611987, 01.620353, 01.628743, 01.637156, 01.645593, 01.654053, 01.662538, 01.671047, 01.679581, 01.688139, 01.696721, 01.705329, 01.713961, 01.722619, 01.731303, 01.740011, 01.748746, 01.757506, 01.766293, 01.775106, 01.783945, 01.792810, 01.801703, 01.810623, 01.819569, 01.828543, 01.837545, 01.846574, 01.855631, 01.864717, 01.873830, 01.882972, 01.892143, 01.901343, 01.910572, 01.919830, 01.929117, 01.938434, 01.947781, 01.957158, 01.966566, 01.976004, 01.985473, 01.994972, 02.004503, 02.014065, 02.023659, 02.033285, 02.042943, 02.052633, 02.062355, 02.072110, 02.081899, 02.091720, 02.101575, 02.111464, 02.121386, 02.131343, 02.141334, 02.151360, 02.161421, 02.171517, 02.181648, 02.191815, 02.202018, 02.212257, 02.222533, 02.232845, 02.243195, 02.253582, 02.264006, 02.274468, 02.284968, 02.295507, 02.306084, 02.316701, 02.327356, 02.338051, 02.348786, 02.359562, 02.370377, 02.381234, 02.392131, 02.403070, 02.414051, 02.425073, 02.436138, 02.447246, 02.458397, 02.469591, 02.480828, 02.492110, 02.503436, 02.514807, 02.526222, 02.537684, 02.549190, 02.560743, 02.572343, 02.583989, 02.595682, 02.607423, 02.619212, 02.631050, 02.642936, 02.654871, 02.666855, 02.678890, 02.690975, 02.703110, 02.715297, 02.727535, 02.739825, 02.752168, 02.764563, 02.777012, 02.789514, 02.802070, 02.814681, 02.827347, 02.840069, 02.852846, 02.865680, 02.878570, 02.891518, 02.904524, 02.917588, 02.930712, 02.943894, 02.957136, 02.970439, 02.983802, 02.997227, 03.010714, 03.024263, 03.037875, 03.051551, 03.065290, 03.079095, 03.092965, 03.106900, 03.120902, 03.134971, 03.149107, 03.163312, 03.177585, 03.191928, 03.206340, 03.220824, 03.235378, 03.250005, 03.264704, 03.279477, 03.294323, 03.309244, 03.324240, 03.339312, 03.354461, 03.369687, 03.384992, 03.400375, 03.415838, 03.431381, 03.447005, 03.462711, 03.478500, 03.494372, 03.510328, 03.526370, 03.542497, 03.558711, 03.575012, 03.591402, 03.607881, 03.624450, 03.641111, 03.657863, 03.674708, 03.691646, 03.708680, 03.725809, 03.743034, 03.760357, 03.777779, 03.795300, 03.812921, 03.830645, 03.848470, 03.866400, 03.884434, 03.902574, 03.920821, 03.939176, 03.957640, 03.976215, 03.994901, 04.013699, 04.032612, 04.051639, 04.070783, 04.090045, 04.109425, 04.128925, 04.148547, 04.168292, 04.188160, 04.208154, 04.228275, 04.248524, 04.268903, 04.289413, 04.310056, 04.330832, 04.351745, 04.372794, 04.393982, 04.415310, 04.436781, 04.458395, 04.480154, 04.502060, 04.524114, 04.546319, 04.568676, 04.591187, 04.613854, 04.636678, 04.659662, 04.682807, 04.706116, 04.729590, 04.753231, 04.777041, 04.801024, 04.825179, 04.849511, 04.874020, 04.898710, 04.923582, 04.948639, 04.973883, 04.999316, 05.024942, 05.050761, 05.076778, 05.102993, 05.129411, 05.156034, 05.182864, 05.209903, 05.237156, 05.264625, 05.292312, 05.320220, 05.348354, 05.376714, 05.405306, 05.434131, 05.463193, 05.492496, 05.522042, 05.551836, 05.581880, 05.612178, 05.642734, 05.673552, 05.704634, 05.735986, 05.767610, 05.799512, 05.831694, 05.864161, 05.896918, 05.929968, 05.963316, 05.996967, 06.030925, 06.065194, 06.099780, 06.134687, 06.169921, 06.205486, 06.241387, 06.277630, 06.314220, 06.351163, 06.388465, 06.426130, 06.464166, 06.502578, 06.541371, 06.580553, 06.620130, 06.660109, 06.700495, 06.741297, 06.782520, 06.824173, 06.866262, 06.908795, 06.951780, 06.995225, 07.039137, 07.083525, 07.128398, 07.173764, 07.219632, 07.266011, 07.312910, 07.360339, 07.408308, 07.456827, 07.505905, 07.555554, 07.605785, 07.656608, 07.708035, 07.760077, 07.812747, 07.866057, 07.920019, 07.974647, 08.029953, 08.085952, 08.142657, 08.200083, 08.258245, 08.317158, 08.376837, 08.437300, 08.498562, 08.560641, 08.623554, 08.687319, 08.751955, 08.817481, 08.883916, 08.951282, 09.019600, 09.088889, 09.159174, 09.230477, 09.302822, 09.376233, 09.450735, 09.526355, 09.603118, 09.681054, 09.760191, 09.840558, 09.922186, 10.005107, 10.089353, 10.174959, 10.261958, 10.350389, 10.440287, 10.531693, 10.624646, 10.719188, 10.815362, 10.913214, 11.012789, 11.114137, 11.217307, 11.322352, 11.429325, 11.538283, 11.649285, 11.762390, 11.877664, 11.995170, 12.114979, 12.237161, 12.361791, 12.488946, 12.618708, 12.751161, 12.886394, 13.024498, 13.165570, 13.309711, 13.457026, 13.607625, 13.761625, 13.919145, 14.080314, 14.245263, 14.414134, 14.587072, 14.764233, 14.945778, 15.131877, 15.322712, 15.518470, 15.719353, 15.925570, 16.137345, 16.354912, 16.578520, 16.808433, 17.044929, 17.288305, 17.538873, 17.796967, 18.062943, 18.337176, 18.620068, 18.912049, 19.213574, 19.525133, 19.847249, 20.180480, 20.525429, 20.882738, 21.253102, 21.637266, 22.036036, 22.450278, 22.880933, 23.329017, 23.795634, 24.281981, 24.789364, 25.319207, 25.873062, 26.452634, 27.059789, 27.696581, 28.365274, 29.068370, 29.808638, 30.589157, 31.413354, 32.285060, 33.208568, 34.188705, 35.230920, 36.341388, 37.527131, 38.796172, 40.157721, 41.622399, 43.202525, 44.912465, 46.769077, 48.792279, 51.005773, 53.437996, 56.123356, 59.103894 }; double X, U, V, RANLAN; int I; X = gsl_rng_uniform_pos(r); U = 1000.0 * X; I = U; U = U - I; if (I >= 70 && I <= 800) { RANLAN = F[I] + U * (F[I + 1] - F[I]); } else if (I >= 7 && I <= 980) { RANLAN = F[I] + U * (F[I + 1] - F[I] - 0.25 * (1 - U) * (F[I + 2] - F[I + 1] - F[I] + F[I - 1])); } else if (I < 7) { V = log(X); U = 1 / V; RANLAN = ((0.99858950 + (3.45213058E1 + 1.70854528E1 * U) * U) / (1 + (3.41760202E1 + 4.01244582 * U) * U)) * ( -log( -0.91893853 - V) - 1); } else { U = 1 - X; V = U * U; if (X <= 0.999) { RANLAN = (1.00060006 + 2.63991156E2 * U + 4.37320068E3 * V) / ((1 + 2.57368075E2 * U + 3.41448018E3 * V) * U); } else { RANLAN = (1.00001538 + 6.07514119E3 * U + 7.34266409E5 * V) / ((1 + 6.06511919E3 * U + 6.94021044E5 * V) * U); } } return RANLAN; } sources_5316/external/gsl/gsl_cblas__chpr.c0000664000176700017670000000047611723710247017617 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_chpr (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const void *X, const int incX, void *Ap) { #define BASE float #include "gsl_cblas__source_hpr.h" #undef BASE } sources_5316/external/gsl/gsl_qrng__niederreiter-2.c0000664000176700017670000002161511723710247021364 0ustar paulpaul/* Author: G. Jungman */ /* Implement Niederreiter base 2 generator. * See: * Bratley, Fox, Niederreiter, ACM Trans. Model. Comp. Sim. 2, 195 (1992) */ #include "gsl__config.h" #include "gsl_qrng.h" #define NIED2_CHARACTERISTIC 2 #define NIED2_BASE 2 #define NIED2_MAX_DIMENSION 12 #define NIED2_MAX_PRIM_DEGREE 5 #define NIED2_MAX_DEGREE 50 #define NIED2_BIT_COUNT 30 #define NIED2_NBITS (NIED2_BIT_COUNT+1) #define MAXV (NIED2_NBITS + NIED2_MAX_DEGREE) /* Z_2 field operations */ #define NIED2_ADD(x,y) (((x)+(y))%2) #define NIED2_MUL(x,y) (((x)*(y))%2) #define NIED2_SUB(x,y) NIED2_ADD((x),(y)) static size_t nied2_state_size(unsigned int dimension); static int nied2_init(void * state, unsigned int dimension); static int nied2_get(void * state, unsigned int dimension, double * v); static const gsl_qrng_type nied2_type = { "niederreiter-base-2", NIED2_MAX_DIMENSION, nied2_state_size, nied2_init, nied2_get }; const gsl_qrng_type * gsl_qrng_niederreiter_2 = &nied2_type; /* primitive polynomials in binary encoding */ static const int primitive_poly[NIED2_MAX_DIMENSION+1][NIED2_MAX_PRIM_DEGREE+1] = { { 1, 0, 0, 0, 0, 0 }, /* 1 */ { 0, 1, 0, 0, 0, 0 }, /* x */ { 1, 1, 0, 0, 0, 0 }, /* 1 + x */ { 1, 1, 1, 0, 0, 0 }, /* 1 + x + x^2 */ { 1, 1, 0, 1, 0, 0 }, /* 1 + x + x^3 */ { 1, 0, 1, 1, 0, 0 }, /* 1 + x^2 + x^3 */ { 1, 1, 0, 0, 1, 0 }, /* 1 + x + x^4 */ { 1, 0, 0, 1, 1, 0 }, /* 1 + x^3 + x^4 */ { 1, 1, 1, 1, 1, 0 }, /* 1 + x + x^2 + x^3 + x^4 */ { 1, 0, 1, 0, 0, 1 }, /* 1 + x^2 + x^5 */ { 1, 0, 0, 1, 0, 1 }, /* 1 + x^3 + x^5 */ { 1, 1, 1, 1, 0, 1 }, /* 1 + x + x^2 + x^3 + x^5 */ { 1, 1, 1, 0, 1, 1 } /* 1 + x + x^2 + x^4 + x^5 */ }; /* degrees of primitive polynomials */ static const int poly_degree[NIED2_MAX_DIMENSION+1] = { 0, 1, 1, 2, 3, 3, 4, 4, 4, 5, 5, 5, 5 }; typedef struct { unsigned int sequence_count; int cj[NIED2_NBITS][NIED2_MAX_DIMENSION]; int nextq[NIED2_MAX_DIMENSION]; } nied2_state_t; static size_t nied2_state_size(unsigned int dimension) { return sizeof(nied2_state_t); } /* Multiply polynomials over Z_2. * Notice use of a temporary vector, * side-stepping aliasing issues when * one of inputs is the same as the output * [especially important in the original fortran version, I guess]. */ static void poly_multiply( const int pa[], int pa_degree, const int pb[], int pb_degree, int pc[], int * pc_degree ) { int j, k; int pt[NIED2_MAX_DEGREE+1]; int pt_degree = pa_degree + pb_degree; for(k=0; k<=pt_degree; k++) { int term = 0; for(j=0; j<=k; j++) { const int conv_term = NIED2_MUL(pa[k-j], pb[j]); term = NIED2_ADD(term, conv_term); } pt[k] = term; } for(k=0; k<=pt_degree; k++) { pc[k] = pt[k]; } for(k=pt_degree+1; k<=NIED2_MAX_DEGREE; k++) { pc[k] = 0; } *pc_degree = pt_degree; } /* Calculate the values of the constants V(J,R) as * described in BFN section 3.3. * * px = appropriate irreducible polynomial for current dimension * pb = polynomial defined in section 2.3 of BFN. * pb is modified */ static void calculate_v( const int px[], int px_degree, int pb[], int * pb_degree, int v[], int maxv ) { const int nonzero_element = 1; /* nonzero element of Z_2 */ const int arbitrary_element = 1; /* arbitray element of Z_2 */ /* The polynomial ph is px**(J-1), which is the value of B on arrival. * In section 3.3, the values of Hi are defined with a minus sign: * don't forget this if you use them later ! */ int ph[NIED2_MAX_DEGREE+1]; /* int ph_degree = *pb_degree; */ int bigm = *pb_degree; /* m from section 3.3 */ int m; /* m from section 2.3 */ int r, k, kj; for(k=0; k<=NIED2_MAX_DEGREE; k++) { ph[k] = pb[k]; } /* Now multiply B by PX so B becomes PX**J. * In section 2.3, the values of Bi are defined with a minus sign : * don't forget this if you use them later ! */ poly_multiply(px, px_degree, pb, *pb_degree, pb, pb_degree); m = *pb_degree; /* Now choose a value of Kj as defined in section 3.3. * We must have 0 <= Kj < E*J = M. * The limit condition on Kj does not seem very relevant * in this program. */ /* Quoting from BFN: "Our program currently sets each K_q * equal to eq. This has the effect of setting all unrestricted * values of v to 1." * Actually, it sets them to the arbitrary chosen value. * Whatever. */ kj = bigm; /* Now choose values of V in accordance with * the conditions in section 3.3. */ for(r=0; r= bigm) { for(r=kj+1; rcj[r][i_dim] = term; } } } static int nied2_init(void * state, unsigned int dimension) { nied2_state_t * n_state = (nied2_state_t *) state; unsigned int i_dim; if(dimension < 1 || dimension > NIED2_MAX_DIMENSION) return GSL_EINVAL; calculate_cj(n_state, dimension); for(i_dim=0; i_dimnextq[i_dim] = 0; n_state->sequence_count = 0; return GSL_SUCCESS; } static int nied2_get(void * state, unsigned int dimension, double * v) { static const double recip = 1.0/(double)(1U << NIED2_NBITS); /* 2^(-nbits) */ nied2_state_t * n_state = (nied2_state_t *) state; int r; int c; unsigned int i_dim; /* Load the result from the saved state. */ for(i_dim=0; i_dimnextq[i_dim] * recip; } /* Find the position of the least-significant zero in sequence_count. * This is the bit that changes in the Gray-code representation as * the count is advanced. */ r = 0; c = n_state->sequence_count; while(1) { if((c % 2) == 1) { ++r; c /= 2; } else break; } if(r >= NIED2_NBITS) return GSL_EFAILED; /* FIXME: better error code here */ /* Calculate the next state. */ for(i_dim=0; i_dimnextq[i_dim] ^= n_state->cj[r][i_dim]; } n_state->sequence_count++; return GSL_SUCCESS; } sources_5316/external/gsl/gsl_specfunc__error.h0000664000176700017670000000343511705263724020544 0ustar paulpaul#define OVERFLOW_ERROR(result) do { (result)->val = GSL_POSINF; (result)->err = GSL_POSINF; GSL_ERROR ("overflow", GSL_EOVRFLW); } while(0) #define UNDERFLOW_ERROR(result) do { (result)->val = 0.0; (result)->err = GSL_DBL_MIN; GSL_ERROR ("underflow", GSL_EUNDRFLW); } while(0) #define INTERNAL_OVERFLOW_ERROR(result) do { (result)->val = GSL_POSINF; (result)->err = GSL_POSINF; return GSL_EOVRFLW; } while(0) #define INTERNAL_UNDERFLOW_ERROR(result) do { (result)->val = 0.0; (result)->err = GSL_DBL_MIN; return GSL_EUNDRFLW; } while(0) #define DOMAIN_ERROR(result) do { (result)->val = GSL_NAN; (result)->err = GSL_NAN; GSL_ERROR ("domain error", GSL_EDOM); } while(0) #define DOMAIN_ERROR_MSG(msg, result) do { (result)->val = GSL_NAN; (result)->err = GSL_NAN; GSL_ERROR ((msg), GSL_EDOM); } while(0) #define DOMAIN_ERROR_E10(result) do { (result)->val = GSL_NAN; (result)->err = GSL_NAN; (result)->e10 = 0 ; GSL_ERROR ("domain error", GSL_EDOM); } while(0) #define OVERFLOW_ERROR_E10(result) do { (result)->val = GSL_POSINF; (result)->err = GSL_POSINF; (result)->e10 = 0; GSL_ERROR ("overflow", GSL_EOVRFLW); } while(0) #define UNDERFLOW_ERROR_E10(result) do { (result)->val = 0.0; (result)->err = GSL_DBL_MIN; (result)->e10 = 0; GSL_ERROR ("underflow", GSL_EUNDRFLW); } while(0) #define OVERFLOW_ERROR_2(r1,r2) do { (r1)->val = GSL_POSINF; (r1)->err = GSL_POSINF; (r2)->val = GSL_POSINF ; (r2)->err=GSL_POSINF; GSL_ERROR ("overflow", GSL_EOVRFLW); } while(0) #define UNDERFLOW_ERROR_2(r1,r2) do { (r1)->val = 0.0; (r1)->err = GSL_DBL_MIN; (r2)->val = 0.0 ; (r2)->err = GSL_DBL_MIN; GSL_ERROR ("underflow", GSL_EUNDRFLW); } while(0) #define DOMAIN_ERROR_2(r1,r2) do { (r1)->val = GSL_NAN; (r1)->err = GSL_NAN; (r2)->val = GSL_NAN; (r2)->err = GSL_NAN; GSL_ERROR ("domain error", GSL_EDOM); } while(0) sources_5316/external/gsl/gsl_sf__bessel_y.c0000644000176700017670000001722210707442037020007 0ustar paulpaul/* specfunc/bessel_y.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_gamma.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_olver.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* [Abramowitz+Stegun, 10.1.3] * with lmax=15, precision ~ 15D for x < 3 * * checked OK [GJ] Wed May 13 15:41:25 MDT 1998 */ static int bessel_yl_small_x(int l, const double x, gsl_sf_result * result) { gsl_sf_result num_fact; double den = gsl_sf_pow_int(x, l+1); int stat_df = gsl_sf_doublefact_e(2*l-1, &num_fact); if(stat_df != GSL_SUCCESS || den == 0.0) { OVERFLOW_ERROR(result); } else { const int lmax = 200; double t = -0.5*x*x; double sum = 1.0; double t_coeff = 1.0; double t_power = 1.0; double delta; int i; for(i=1; i<=lmax; i++) { t_coeff /= i*(2*(i-l) - 1); t_power *= t; delta = t_power*t_coeff; sum += delta; if(fabs(delta/sum) < 0.5*GSL_DBL_EPSILON) break; } result->val = -num_fact.val/den * sum; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_y0_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(1.0/GSL_DBL_MAX > 0.0 && x < 1.0/GSL_DBL_MAX) { OVERFLOW_ERROR(result); } else { gsl_sf_result cos_result; const int stat = gsl_sf_cos_e(x, &cos_result); result->val = -cos_result.val/x; result->err = fabs(cos_result.err/x); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } } int gsl_sf_bessel_y1_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 1.0/GSL_SQRT_DBL_MAX) { OVERFLOW_ERROR(result); } else if(x < 0.25) { const double y = x*x; const double c1 = 1.0/2.0; const double c2 = -1.0/8.0; const double c3 = 1.0/144.0; const double c4 = -1.0/5760.0; const double c5 = 1.0/403200.0; const double c6 = -1.0/43545600.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*c6))))); result->val = -sum/y; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result cos_result; gsl_sf_result sin_result; const int stat_cos = gsl_sf_cos_e(x, &cos_result); const int stat_sin = gsl_sf_sin_e(x, &sin_result); const double cx = cos_result.val; const double sx = sin_result.val; result->val = -(cx/x + sx)/x; result->err = (fabs(cos_result.err/x) + sin_result.err)/fabs(x); result->err += GSL_DBL_EPSILON * (fabs(sx/x) + fabs(cx/(x*x))); return GSL_ERROR_SELECT_2(stat_cos, stat_sin); } } int gsl_sf_bessel_y2_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 1.0/GSL_ROOT3_DBL_MAX) { OVERFLOW_ERROR(result); } else if(x < 0.5) { const double y = x*x; const double c1 = 1.0/6.0; const double c2 = 1.0/24.0; const double c3 = -1.0/144.0; const double c4 = 1.0/3456.0; const double c5 = -1.0/172800.0; const double c6 = 1.0/14515200.0; const double c7 = -1.0/1828915200.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*(c6 + y*c7)))))); result->val = -3.0/(x*x*x) * sum; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result cos_result; gsl_sf_result sin_result; const int stat_cos = gsl_sf_cos_e(x, &cos_result); const int stat_sin = gsl_sf_sin_e(x, &sin_result); const double sx = sin_result.val; const double cx = cos_result.val; const double a = 3.0/(x*x); result->val = (1.0 - a)/x * cx - a * sx; result->err = cos_result.err * fabs((1.0 - a)/x) + sin_result.err * fabs(a); result->err += GSL_DBL_EPSILON * (fabs(cx/x) + fabs(sx/(x*x))); return GSL_ERROR_SELECT_2(stat_cos, stat_sin); } } int gsl_sf_bessel_yl_e(int l, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(l < 0 || x <= 0.0) { DOMAIN_ERROR(result); } else if(l == 0) { return gsl_sf_bessel_y0_e(x, result); } else if(l == 1) { return gsl_sf_bessel_y1_e(x, result); } else if(l == 2) { return gsl_sf_bessel_y2_e(x, result); } else if(x < 3.0) { return bessel_yl_small_x(l, x, result); } else if(GSL_ROOT3_DBL_EPSILON * x > (l*l + l + 1.0)) { int status = gsl_sf_bessel_Ynu_asympx_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= pre; result->err *= pre; return status; } else if(l > 40) { int status = gsl_sf_bessel_Ynu_asymp_Olver_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= pre; result->err *= pre; return status; } else { /* recurse upward */ gsl_sf_result r_by; gsl_sf_result r_bym; int stat_1 = gsl_sf_bessel_y1_e(x, &r_by); int stat_0 = gsl_sf_bessel_y0_e(x, &r_bym); double bym = r_bym.val; double by = r_by.val; double byp; int j; for(j=1; jval = by; result->err = fabs(result->val) * (GSL_DBL_EPSILON + fabs(r_by.err/r_by.val) + fabs(r_bym.err/r_bym.val)); return GSL_ERROR_SELECT_2(stat_1, stat_0); } } int gsl_sf_bessel_yl_array(const int lmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(lmax < 0 || x <= 0.0) { GSL_ERROR ("error", GSL_EDOM); } else if (lmax == 0) { gsl_sf_result result; int stat = gsl_sf_bessel_y0_e(x, &result); result_array[0] = result.val; return stat; } else { gsl_sf_result r_yell; gsl_sf_result r_yellm1; int stat_1 = gsl_sf_bessel_y1_e(x, &r_yell); int stat_0 = gsl_sf_bessel_y0_e(x, &r_yellm1); double yellp1; double yell = r_yell.val; double yellm1 = r_yellm1.val; int ell; result_array[0] = yellm1; result_array[1] = yell; for(ell = 1; ell < lmax; ell++) { yellp1 = (2*ell+1)/x * yell - yellm1; result_array[ell+1] = yellp1; yellm1 = yell; yell = yellp1; } return GSL_ERROR_SELECT_2(stat_0, stat_1); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_y0(const double x) { EVAL_RESULT(gsl_sf_bessel_y0_e(x, &result)); } double gsl_sf_bessel_y1(const double x) { EVAL_RESULT(gsl_sf_bessel_y1_e(x, &result)); } double gsl_sf_bessel_y2(const double x) { EVAL_RESULT(gsl_sf_bessel_y2_e(x, &result)); } double gsl_sf_bessel_yl(const int l, const double x) { EVAL_RESULT(gsl_sf_bessel_yl_e(l, x, &result)); } sources_5316/external/gsl/gsl_fft__hc_pass_4.c0000664000176700017670000001466211723710247020223 0ustar paulpaul/* fft/hc_pass_4.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_halfcomplex,pass_4) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[]) { size_t i, j, k, k1, jump; size_t factor, q, m, product_1; i = 0; j = 0; factor = 4; m = n / factor; q = n / product; product_1 = product / factor; jump = (factor - 1) * q; for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 4 * k1 * q; const size_t from1 = from0 + 2 * q - 1; const size_t from2 = from1 + 2 * q; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC t1_real = z0_real + z2_real; const ATOMIC t2_real = 2 * z1_real; const ATOMIC t3_real = z0_real - z2_real; const ATOMIC t4_imag = 2 * z1_imag; const size_t to0 = q * k1; const size_t to1 = to0 + m; const size_t to2 = to1 + m; const size_t to3 = to2 + m; VECTOR(out,ostride,to0) = t1_real + t2_real; VECTOR(out,ostride,to1) = t3_real - t4_imag; VECTOR(out,ostride,to2) = t1_real - t2_real; VECTOR(out,ostride,to3) = t3_real + t4_imag; } if (q == 1) return; for (k = 1; k < (q + 1) / 2; k++) { const ATOMIC w1_real = GSL_REAL(twiddle1[k - 1]); const ATOMIC w1_imag = GSL_IMAG(twiddle1[k - 1]); const ATOMIC w2_real = GSL_REAL(twiddle2[k - 1]); const ATOMIC w2_imag = GSL_IMAG(twiddle2[k - 1]); const ATOMIC w3_real = GSL_REAL(twiddle3[k - 1]); const ATOMIC w3_imag = GSL_IMAG(twiddle3[k - 1]); for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 4 * k1 * q + 2 * k - 1; const size_t from1 = from0 + 2 * q; const size_t from2 = 4 * k1 * q - 2 * k + 2 * q - 1; const size_t from3 = from2 + 2 * q; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC z2_real = VECTOR(in,istride,from3); const ATOMIC z2_imag = -VECTOR(in,istride,from3 + 1); const ATOMIC z3_real = VECTOR(in,istride,from2); const ATOMIC z3_imag = -VECTOR(in,istride,from2 + 1); /* compute x = W(4) z */ /* t1 = z0 + z2 */ const ATOMIC t1_real = z0_real + z2_real; const ATOMIC t1_imag = z0_imag + z2_imag; /* t2 = z1 + z3 */ const ATOMIC t2_real = z1_real + z3_real; const ATOMIC t2_imag = z1_imag + z3_imag; /* t3 = z0 - z2 */ const ATOMIC t3_real = z0_real - z2_real; const ATOMIC t3_imag = z0_imag - z2_imag; /* t4 = (z1 - z3) */ const ATOMIC t4_real = (z1_real - z3_real); const ATOMIC t4_imag = (z1_imag - z3_imag); /* x0 = t1 + t2 */ const ATOMIC x0_real = t1_real + t2_real; const ATOMIC x0_imag = t1_imag + t2_imag; /* x1 = t3 + i t4 */ const ATOMIC x1_real = t3_real - t4_imag; const ATOMIC x1_imag = t3_imag + t4_real; /* x2 = t1 - t2 */ const ATOMIC x2_real = t1_real - t2_real; const ATOMIC x2_imag = t1_imag - t2_imag; /* x3 = t3 - i t4 */ const ATOMIC x3_real = t3_real + t4_imag; const ATOMIC x3_imag = t3_imag - t4_real; const size_t to0 = k1 * q + 2 * k - 1; const size_t to1 = to0 + m; const size_t to2 = to1 + m; const size_t to3 = to2 + m; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to0 + 1) = x0_imag; VECTOR(out,ostride,to1) = w1_real * x1_real - w1_imag * x1_imag; VECTOR(out,ostride,to1 + 1) = w1_imag * x1_real + w1_real * x1_imag; VECTOR(out,ostride,to2) = w2_real * x2_real - w2_imag * x2_imag; VECTOR(out,ostride,to2 + 1) = w2_imag * x2_real + w2_real * x2_imag; /* to3 = w3 * x3 */ VECTOR(out,ostride,to3) = w3_real * x3_real - w3_imag * x3_imag; VECTOR(out,ostride,to3 + 1) = w3_real * x3_imag + w3_imag * x3_real; } } if (q % 2 == 1) return; for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 4 * k1 * q + q - 1; const size_t from1 = from0 + 2 * q; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC t1_real = sqrt (2.0) * (z0_imag + z1_imag); const ATOMIC t2_real = sqrt (2.0) * (z0_real - z1_real); const ATOMIC x0_real = 2 * (z0_real + z1_real); const ATOMIC x1_real = t2_real - t1_real; const ATOMIC x2_real = 2 * (z1_imag - z0_imag); const ATOMIC x3_real = -(t2_real + t1_real); const size_t to0 = k1 * q + q - 1; const size_t to1 = to0 + m; const size_t to2 = to1 + m; const size_t to3 = to2 + m; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to2) = x2_real; VECTOR(out,ostride,to3) = x3_real; } return; } sources_5316/external/gsl/gsl_specfunc__bessel_Yn.c0000664000176700017670000001266311723710247021331 0ustar paulpaul/* specfunc/bessel_Yn.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_gamma.h" #include "gsl_sf_psi.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_amp_phase.h" #include "gsl_specfunc__bessel_olver.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* assumes n >= 1 */ static int bessel_Yn_small_x(const int n, const double x, gsl_sf_result * result) { int k; double y = 0.25 * x * x; double ln_x_2 = log(0.5*x); gsl_sf_result ln_nm1_fact; double k_term; double term1, sum1, ln_pre1; double term2, sum2, pre2; gsl_sf_lnfact_e((unsigned int)(n-1), &ln_nm1_fact); ln_pre1 = -n*ln_x_2 + ln_nm1_fact.val; if(ln_pre1 > GSL_LOG_DBL_MAX - 3.0) GSL_ERROR ("error", GSL_EOVRFLW); sum1 = 1.0; k_term = 1.0; for(k=1; k<=n-1; k++) { k_term *= y/(k * (n-k)); sum1 += k_term; } term1 = -exp(ln_pre1) * sum1 / M_PI; pre2 = -exp(n*ln_x_2) / M_PI; if(fabs(pre2) > 0.0) { const int KMAX = 20; gsl_sf_result psi_n; gsl_sf_result npk_fact; double yk = 1.0; double k_fact = 1.0; double psi_kp1 = -M_EULER; double psi_npkp1; gsl_sf_psi_int_e(n, &psi_n); gsl_sf_fact_e((unsigned int)n, &npk_fact); psi_npkp1 = psi_n.val + 1.0/n; sum2 = (psi_kp1 + psi_npkp1 - 2.0*ln_x_2)/npk_fact.val; for(k=1; kval = term1 + term2; result->err = GSL_DBL_EPSILON * (fabs(ln_pre1)*fabs(term1) + fabs(term2)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Yn_e(int n, const double x, gsl_sf_result * result) { int sign = 1; if(n < 0) { /* reduce to case n >= 0 */ n = -n; if(GSL_IS_ODD(n)) sign = -1; } /* CHECK_POINTER(result) */ if(n == 0) { int status = gsl_sf_bessel_Y0_e(x, result); result->val *= sign; return status; } else if(n == 1) { int status = gsl_sf_bessel_Y1_e(x, result); result->val *= sign; return status; } else { if(x <= 0.0) { DOMAIN_ERROR(result); } if(x < 5.0) { int status = bessel_Yn_small_x(n, x, result); result->val *= sign; return status; } else if(GSL_ROOT3_DBL_EPSILON * x > (n*n + 1.0)) { int status = gsl_sf_bessel_Ynu_asympx_e((double)n, x, result); result->val *= sign; return status; } else if(n > 50) { int status = gsl_sf_bessel_Ynu_asymp_Olver_e((double)n, x, result); result->val *= sign; return status; } else { double two_over_x = 2.0/x; gsl_sf_result r_by; gsl_sf_result r_bym; int stat_1 = gsl_sf_bessel_Y1_e(x, &r_by); int stat_0 = gsl_sf_bessel_Y0_e(x, &r_bym); double bym = r_bym.val; double by = r_by.val; double byp; int j; for(j=1; jval = sign * by; result->err = fabs(result->val) * (fabs(r_by.err/r_by.val) + fabs(r_bym.err/r_bym.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_1, stat_0); } } } int gsl_sf_bessel_Yn_array(const int nmin, const int nmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(nmin < 0 || nmax < nmin || x <= 0.0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; GSL_ERROR ("error", GSL_EDOM); } else { gsl_sf_result r_Ynm1; gsl_sf_result r_Yn; int stat_nm1 = gsl_sf_bessel_Yn_e(nmin, x, &r_Ynm1); int stat_n = gsl_sf_bessel_Yn_e(nmin+1, x, &r_Yn); double Ynp1; double Yn = r_Yn.val; double Ynm1 = r_Ynm1.val; int n; int stat = GSL_ERROR_SELECT_2(stat_nm1, stat_n); if(stat == GSL_SUCCESS) { for(n=nmin+1; n<=nmax+1; n++) { result_array[n-nmin-1] = Ynm1; Ynp1 = -Ynm1 + 2.0*n/x * Yn; Ynm1 = Yn; Yn = Ynp1; } } else { for(n=nmin; n<=nmax; n++) { result_array[n-nmin] = 0.0; } } return stat; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_Yn(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_Yn_e(n, x, &result)); } sources_5316/external/gsl/gsl_interp.h0000664000176700017670000001341311705263724016664 0ustar paulpaul/* interpolation/gsl_interp.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_INTERP_H__ #define __GSL_INTERP_H__ #include #include "gsl_types.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* evaluation accelerator */ typedef struct { size_t cache; /* cache of index */ size_t miss_count; /* keep statistics */ size_t hit_count; } gsl_interp_accel; /* interpolation object type */ typedef struct { const char * name; unsigned int min_size; void * (*alloc) (size_t size); int (*init) (void *, const double xa[], const double ya[], size_t size); int (*eval) (const void *, const double xa[], const double ya[], size_t size, double x, gsl_interp_accel *, double * y); int (*eval_deriv) (const void *, const double xa[], const double ya[], size_t size, double x, gsl_interp_accel *, double * y_p); int (*eval_deriv2) (const void *, const double xa[], const double ya[], size_t size, double x, gsl_interp_accel *, double * y_pp); int (*eval_integ) (const void *, const double xa[], const double ya[], size_t size, gsl_interp_accel *, double a, double b, double * result); void (*free) (void *); } gsl_interp_type; /* general interpolation object */ typedef struct { const gsl_interp_type * type; double xmin; double xmax; size_t size; void * state; } gsl_interp; /* available types */ GSL_VAR const gsl_interp_type * gsl_interp_linear; GSL_VAR const gsl_interp_type * gsl_interp_polynomial; GSL_VAR const gsl_interp_type * gsl_interp_cspline; GSL_VAR const gsl_interp_type * gsl_interp_cspline_periodic; GSL_VAR const gsl_interp_type * gsl_interp_akima; GSL_VAR const gsl_interp_type * gsl_interp_akima_periodic; gsl_interp_accel * gsl_interp_accel_alloc(void); size_t gsl_interp_accel_find(gsl_interp_accel * a, const double x_array[], size_t size, double x); int gsl_interp_accel_reset (gsl_interp_accel * a); void gsl_interp_accel_free(gsl_interp_accel * a); gsl_interp * gsl_interp_alloc(const gsl_interp_type * T, size_t n); int gsl_interp_init(gsl_interp * obj, const double xa[], const double ya[], size_t size); const char * gsl_interp_name(const gsl_interp * interp); unsigned int gsl_interp_min_size(const gsl_interp * interp); int gsl_interp_eval_e(const gsl_interp * obj, const double xa[], const double ya[], double x, gsl_interp_accel * a, double * y); double gsl_interp_eval(const gsl_interp * obj, const double xa[], const double ya[], double x, gsl_interp_accel * a); int gsl_interp_eval_deriv_e(const gsl_interp * obj, const double xa[], const double ya[], double x, gsl_interp_accel * a, double * d); double gsl_interp_eval_deriv(const gsl_interp * obj, const double xa[], const double ya[], double x, gsl_interp_accel * a); int gsl_interp_eval_deriv2_e(const gsl_interp * obj, const double xa[], const double ya[], double x, gsl_interp_accel * a, double * d2); double gsl_interp_eval_deriv2(const gsl_interp * obj, const double xa[], const double ya[], double x, gsl_interp_accel * a); int gsl_interp_eval_integ_e(const gsl_interp * obj, const double xa[], const double ya[], double a, double b, gsl_interp_accel * acc, double * result); double gsl_interp_eval_integ(const gsl_interp * obj, const double xa[], const double ya[], double a, double b, gsl_interp_accel * acc); void gsl_interp_free(gsl_interp * interp); size_t gsl_interp_bsearch(const double x_array[], double x, size_t index_lo, size_t index_hi); #ifdef HAVE_INLINE extern inline size_t gsl_interp_bsearch(const double x_array[], double x, size_t index_lo, size_t index_hi); extern inline size_t gsl_interp_bsearch(const double x_array[], double x, size_t index_lo, size_t index_hi) { size_t ilo = index_lo; size_t ihi = index_hi; while(ihi > ilo + 1) { size_t i = (ihi + ilo)/2; if(x_array[i] > x) ihi = i; else ilo = i; } return ilo; } #endif #ifdef HAVE_INLINE extern inline size_t gsl_interp_accel_find(gsl_interp_accel * a, const double xa[], size_t len, double x) { size_t x_index = a->cache; if(x < xa[x_index]) { a->miss_count++; a->cache = gsl_interp_bsearch(xa, x, 0, x_index); } else if(x > xa[x_index + 1]) { a->miss_count++; a->cache = gsl_interp_bsearch(xa, x, x_index, len-1); } else { a->hit_count++; } return a->cache; } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_INTERP_H__ */ sources_5316/external/gsl/gsl_poly__dd.c0000664000176700017670000000440411723710247017144 0ustar paulpaul/* interpolation/interp_poly.c * * Copyright (C) 2001 DAN, HO-JIN * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Modified for standalone use in polynomial directory, B.Gough 2001 */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_poly.h" int gsl_poly_dd_init (double dd[], const double xa[], const double ya[], size_t size) { size_t i, j; /* Newton's divided differences */ dd[0] = ya[0]; for (j = size - 1; j >= 1; j--) { dd[j] = (ya[j] - ya[j - 1]) / (xa[j] - xa[j - 1]); } for (i = 2; i < size; i++) { for (j = size - 1; j >= i; j--) { dd[j] = (dd[j] - dd[j - 1]) / (xa[j] - xa[j - i]); } } return GSL_SUCCESS; } #ifndef HIDE_INLINE_STATIC double gsl_poly_dd_eval (const double dd[], const double xa[], const size_t size, const double x) { size_t i; double y = dd[size - 1]; for (i = size - 1; i--;) { y = dd[i] + (x - xa[i]) * y; } return y; } #endif int gsl_poly_dd_taylor (double c[], double xp, const double dd[], const double xa[], size_t size, double w[]) { size_t i, j; for (i = 0; i < size; i++) { c[i] = 0.0; w[i] = 0.0; } w[size - 1] = 1.0; c[0] = dd[0]; for (i = size - 1; i > 0 && i--;) { w[i] = -w[i + 1] * (xa[size - 2 - i] - xp); for (j = i + 1; j < size - 1; j++) { w[j] = w[j] - w[j + 1] * (xa[size - 2 - i] - xp); } for (j = i; j < size; j++) { c[j - i] += w[j] * dd[size - i - 1]; } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__source_trmv_c.h0000664000176700017670000001347311705263724021546 0ustar paulpaul/* blas/source_tbmv_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (TransA == CblasConjTrans) ? -1 : 1; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; const int nonunit = (Diag == CblasNonUnit); INDEX i, j; if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { /* form x := A*x */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE temp_r = 0.0; BASE temp_i = 0.0; const INDEX j_min = i + 1; INDEX jx = OFFSET(N, incX) + incX * j_min; for (j = j_min; j < N; j++) { const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); const BASE A_real = CONST_REAL(A, lda * i + j); const BASE A_imag = conj * CONST_IMAG(A, lda * i + j); temp_r += A_real * x_real - A_imag * x_imag; temp_i += A_real * x_imag + A_imag * x_real; jx += incX; } if (nonunit) { const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + i); const BASE A_imag = conj * CONST_IMAG(A, lda * i + i); REAL(X, ix) = temp_r + (A_real * x_real - A_imag * x_imag); IMAG(X, ix) = temp_i + (A_real * x_imag + A_imag * x_real); } else { REAL(X, ix) += temp_r; IMAG(X, ix) += temp_i; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { BASE temp_r = 0.0; BASE temp_i = 0.0; const INDEX j_max = i; INDEX jx = OFFSET(N, incX); for (j = 0; j < j_max; j++) { const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); const BASE A_real = CONST_REAL(A, lda * i + j); const BASE A_imag = conj * CONST_IMAG(A, lda * i + j); temp_r += A_real * x_real - A_imag * x_imag; temp_i += A_real * x_imag + A_imag * x_real; jx += incX; } if (nonunit) { const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + i); const BASE A_imag = conj * CONST_IMAG(A, lda * i + i); REAL(X, ix) = temp_r + (A_real * x_real - A_imag * x_imag); IMAG(X, ix) = temp_i + (A_real * x_imag + A_imag * x_real); } else { REAL(X, ix) += temp_r; IMAG(X, ix) += temp_i; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := A'*x */ INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { BASE temp_r = 0.0; BASE temp_i = 0.0; const INDEX j_max = i; INDEX jx = OFFSET(N, incX); for (j = 0; j < j_max; j++) { const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); const BASE A_real = CONST_REAL(A, lda * j + i); const BASE A_imag = conj * CONST_IMAG(A, lda * j + i); temp_r += A_real * x_real - A_imag * x_imag; temp_i += A_real * x_imag + A_imag * x_real; jx += incX; } if (nonunit) { const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + i); const BASE A_imag = conj * CONST_IMAG(A, lda * i + i); REAL(X, ix) = temp_r + (A_real * x_real - A_imag * x_imag); IMAG(X, ix) = temp_i + (A_real * x_imag + A_imag * x_real); } else { REAL(X, ix) += temp_r; IMAG(X, ix) += temp_i; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE temp_r = 0.0; BASE temp_i = 0.0; const INDEX j_min = i + 1; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < N; j++) { const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); const BASE A_real = CONST_REAL(A, lda * j + i); const BASE A_imag = conj * CONST_IMAG(A, lda * j + i); temp_r += A_real * x_real - A_imag * x_imag; temp_i += A_real * x_imag + A_imag * x_real; jx += incX; } if (nonunit) { const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + i); const BASE A_imag = conj * CONST_IMAG(A, lda * i + i); REAL(X, ix) = temp_r + (A_real * x_real - A_imag * x_imag); IMAG(X, ix) = temp_i + (A_real * x_imag + A_imag * x_real); } else { REAL(X, ix) += temp_r; IMAG(X, ix) += temp_i; } ix += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_block_long.h0000664000176700017670000000435611705263724017502 0ustar paulpaul/* block/gsl_block_long.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_LONG_H__ #define __GSL_BLOCK_LONG_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_long_struct { size_t size; long *data; }; typedef struct gsl_block_long_struct gsl_block_long; gsl_block_long *gsl_block_long_alloc (const size_t n); gsl_block_long *gsl_block_long_calloc (const size_t n); void gsl_block_long_free (gsl_block_long * b); int gsl_block_long_fread (FILE * stream, gsl_block_long * b); int gsl_block_long_fwrite (FILE * stream, const gsl_block_long * b); int gsl_block_long_fscanf (FILE * stream, gsl_block_long * b); int gsl_block_long_fprintf (FILE * stream, const gsl_block_long * b, const char *format); int gsl_block_long_raw_fread (FILE * stream, long * b, const size_t n, const size_t stride); int gsl_block_long_raw_fwrite (FILE * stream, const long * b, const size_t n, const size_t stride); int gsl_block_long_raw_fscanf (FILE * stream, long * b, const size_t n, const size_t stride); int gsl_block_long_raw_fprintf (FILE * stream, const long * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_long_size (const gsl_block_long * b); long * gsl_block_long_data (const gsl_block_long * b); __END_DECLS #endif /* __GSL_BLOCK_LONG_H__ */ sources_5316/external/gsl/gsl_vector_short.h0000664000176700017670000001610211705263724020102 0ustar paulpaul/* vector/gsl_vector_short.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_SHORT_H__ #define __GSL_VECTOR_SHORT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_short.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; short *data; gsl_block_short *block; int owner; } gsl_vector_short; typedef struct { gsl_vector_short vector; } _gsl_vector_short_view; typedef _gsl_vector_short_view gsl_vector_short_view; typedef struct { gsl_vector_short vector; } _gsl_vector_short_const_view; typedef const _gsl_vector_short_const_view gsl_vector_short_const_view; /* Allocation */ gsl_vector_short *gsl_vector_short_alloc (const size_t n); gsl_vector_short *gsl_vector_short_calloc (const size_t n); gsl_vector_short *gsl_vector_short_alloc_from_block (gsl_block_short * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_short *gsl_vector_short_alloc_from_vector (gsl_vector_short * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_short_free (gsl_vector_short * v); /* Views */ _gsl_vector_short_view gsl_vector_short_view_array (short *v, size_t n); _gsl_vector_short_view gsl_vector_short_view_array_with_stride (short *base, size_t stride, size_t n); _gsl_vector_short_const_view gsl_vector_short_const_view_array (const short *v, size_t n); _gsl_vector_short_const_view gsl_vector_short_const_view_array_with_stride (const short *base, size_t stride, size_t n); _gsl_vector_short_view gsl_vector_short_subvector (gsl_vector_short *v, size_t i, size_t n); _gsl_vector_short_view gsl_vector_short_subvector_with_stride (gsl_vector_short *v, size_t i, size_t stride, size_t n); _gsl_vector_short_const_view gsl_vector_short_const_subvector (const gsl_vector_short *v, size_t i, size_t n); _gsl_vector_short_const_view gsl_vector_short_const_subvector_with_stride (const gsl_vector_short *v, size_t i, size_t stride, size_t n); /* Operations */ short gsl_vector_short_get (const gsl_vector_short * v, const size_t i); void gsl_vector_short_set (gsl_vector_short * v, const size_t i, short x); short *gsl_vector_short_ptr (gsl_vector_short * v, const size_t i); const short *gsl_vector_short_const_ptr (const gsl_vector_short * v, const size_t i); void gsl_vector_short_set_zero (gsl_vector_short * v); void gsl_vector_short_set_all (gsl_vector_short * v, short x); int gsl_vector_short_set_basis (gsl_vector_short * v, size_t i); int gsl_vector_short_fread (FILE * stream, gsl_vector_short * v); int gsl_vector_short_fwrite (FILE * stream, const gsl_vector_short * v); int gsl_vector_short_fscanf (FILE * stream, gsl_vector_short * v); int gsl_vector_short_fprintf (FILE * stream, const gsl_vector_short * v, const char *format); int gsl_vector_short_memcpy (gsl_vector_short * dest, const gsl_vector_short * src); int gsl_vector_short_reverse (gsl_vector_short * v); int gsl_vector_short_swap (gsl_vector_short * v, gsl_vector_short * w); int gsl_vector_short_swap_elements (gsl_vector_short * v, const size_t i, const size_t j); short gsl_vector_short_max (const gsl_vector_short * v); short gsl_vector_short_min (const gsl_vector_short * v); void gsl_vector_short_minmax (const gsl_vector_short * v, short * min_out, short * max_out); size_t gsl_vector_short_max_index (const gsl_vector_short * v); size_t gsl_vector_short_min_index (const gsl_vector_short * v); void gsl_vector_short_minmax_index (const gsl_vector_short * v, size_t * imin, size_t * imax); int gsl_vector_short_add (gsl_vector_short * a, const gsl_vector_short * b); int gsl_vector_short_sub (gsl_vector_short * a, const gsl_vector_short * b); int gsl_vector_short_mul (gsl_vector_short * a, const gsl_vector_short * b); int gsl_vector_short_div (gsl_vector_short * a, const gsl_vector_short * b); int gsl_vector_short_scale (gsl_vector_short * a, const double x); int gsl_vector_short_add_constant (gsl_vector_short * a, const double x); int gsl_vector_short_isnull (const gsl_vector_short * v); int gsl_vector_short_ispos (const gsl_vector_short * v); int gsl_vector_short_isneg (const gsl_vector_short * v); int gsl_vector_short_isnonneg (const gsl_vector_short * v); #ifdef HAVE_INLINE extern inline short gsl_vector_short_get (const gsl_vector_short * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_short_set (gsl_vector_short * v, const size_t i, short x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline short * gsl_vector_short_ptr (gsl_vector_short * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (short *) (v->data + i * v->stride); } extern inline const short * gsl_vector_short_const_ptr (const gsl_vector_short * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const short *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_SHORT_H__ */ sources_5316/external/gsl/gsl_ieee-utils__read.c0000664000176700017670000001163611723710247020557 0ustar paulpaul/* ieee-utils/read.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_ieee_utils.h" static int lookup_string (const char * p, int * precision, int * rounding, int * exception_mask) ; int gsl_ieee_read_mode_string (const char * description, int * precision, int * rounding, int * exception_mask) { char * start ; char * end; char * p; int precision_count = 0 ; int rounding_count = 0 ; int exception_count = 0 ; start = (char *) malloc(strlen(description) + 1) ; if (start == 0) { GSL_ERROR ("no memory to parse mode string", GSL_ENOMEM) ; } strcpy (start, description) ; p = start ; *precision = 0 ; *rounding = 0 ; *exception_mask = 0 ; do { int status ; int new_precision, new_rounding, new_exception ; end = strchr (p,',') ; if (end) { *end = '\0' ; do { end++ ; /* skip over trailing whitespace */ } while (*end == ' ' || *end == ',') ; } new_precision = 0 ; new_rounding = 0 ; new_exception = 0 ; status = lookup_string (p, &new_precision, &new_rounding, &new_exception) ; if (status) GSL_ERROR ("unrecognized GSL_IEEE_MODE string.\nValid settings are:\n\n" " single-precision double-precision extended-precision\n" " round-to-nearest round-down round-up round-to-zero\n" " mask-invalid mask-denormalized mask-division-by-zero\n" " mask-overflow mask-underflow mask-all\n" " trap-common trap-inexact\n" "\n" "separated by commas. " "(e.g. GSL_IEEE_MODE=\"round-down,mask-underflow\")", GSL_EINVAL) ; if (new_precision) { *precision = new_precision ; precision_count ++ ; if (precision_count > 1) GSL_ERROR ("attempted to set IEEE precision twice", GSL_EINVAL) ; } if (new_rounding) { *rounding = new_rounding ; rounding_count ++ ; if (rounding_count > 1) GSL_ERROR ("attempted to set IEEE rounding mode twice", GSL_EINVAL) ; } if (new_exception) { *exception_mask |= new_exception ; exception_count ++ ; } p = end ; } while (end && *p != '\0') ; free(start) ; return GSL_SUCCESS ; } static int lookup_string (const char * p, int * precision, int * rounding, int * exception_mask) { if (strcmp(p,"single-precision") == 0) { *precision = GSL_IEEE_SINGLE_PRECISION ; } else if (strcmp(p,"double-precision") == 0) { *precision = GSL_IEEE_DOUBLE_PRECISION ; } else if (strcmp(p,"extended-precision") == 0) { *precision = GSL_IEEE_EXTENDED_PRECISION ; } else if (strcmp(p,"round-to-nearest") == 0) { *rounding = GSL_IEEE_ROUND_TO_NEAREST ; } else if (strcmp(p,"round-down") == 0) { *rounding = GSL_IEEE_ROUND_DOWN ; } else if (strcmp(p,"round-up") == 0) { *rounding = GSL_IEEE_ROUND_UP ; } else if (strcmp(p,"round-to-zero") == 0) { *rounding = GSL_IEEE_ROUND_TO_ZERO ; } else if (strcmp(p,"mask-all") == 0) { *exception_mask = GSL_IEEE_MASK_ALL ; } else if (strcmp(p,"mask-invalid") == 0) { *exception_mask = GSL_IEEE_MASK_INVALID ; } else if (strcmp(p,"mask-denormalized") == 0) { *exception_mask = GSL_IEEE_MASK_DENORMALIZED ; } else if (strcmp(p,"mask-division-by-zero") == 0) { *exception_mask = GSL_IEEE_MASK_DIVISION_BY_ZERO ; } else if (strcmp(p,"mask-overflow") == 0) { *exception_mask = GSL_IEEE_MASK_OVERFLOW ; } else if (strcmp(p,"mask-underflow") == 0) { *exception_mask = GSL_IEEE_MASK_UNDERFLOW ; } else if (strcmp(p,"trap-inexact") == 0) { *exception_mask = GSL_IEEE_TRAP_INEXACT ; } else if (strcmp(p,"trap-common") == 0) { return 0 ; } else { return 1 ; } return 0 ; } sources_5316/external/gsl/gsl_specfunc__synchrotron.c0000664000176700017670000001633511723710247021776 0ustar paulpaul/* specfunc/synchrotron.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_synchrotron.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" static double synchrotron1_data[13] = { 30.364682982501076273, 17.079395277408394574, 4.560132133545072889, 0.549281246730419979, 0.372976075069301172e-01, 0.161362430201041242e-02, 0.481916772120371e-04, 0.10512425288938e-05, 0.174638504670e-07, 0.22815486544e-09, 0.240443082e-11, 0.2086588e-13, 0.15167e-15 }; static cheb_series synchrotron1_cs = { synchrotron1_data, 12, -1.0, 1.0, 9 }; static double synchrotron2_data[12] = { 0.4490721623532660844, 0.898353677994187218e-01, 0.81044573772151290e-02, 0.4261716991089162e-03, 0.147609631270746e-04, 0.3628633615300e-06, 0.66634807498e-08, 0.949077166e-10, 0.1079125e-11, 0.10022e-13, 0.77e-16, 0.5e-18 }; static cheb_series synchrotron2_cs = { synchrotron2_data, 11, -1.0, 1.0, 7 }; static double synchrotron1a_data[23] = { 2.1329305161355000985, 0.741352864954200240e-01, 0.86968099909964198e-02, 0.11703826248775692e-02, 0.1645105798619192e-03, 0.240201021420640e-04, 0.35827756389389e-05, 0.5447747626984e-06, 0.838802856196e-07, 0.13069882684e-07, 0.2053099071e-08, 0.325187537e-09, 0.517914041e-10, 0.83002988e-11, 0.13352728e-11, 0.2159150e-12, 0.349967e-13, 0.56994e-14, 0.9291e-15, 0.152e-15, 0.249e-16, 0.41e-17, 0.7e-18 }; static cheb_series synchrotron1a_cs = { synchrotron1a_data, 22, -1.0, 1.0, 11 }; static double synchrotron21_data[13] = { 38.617839923843085480, 23.037715594963734597, 5.3802499868335705968, 0.6156793806995710776, 0.406688004668895584e-01, 0.17296274552648414e-02, 0.51061258836577e-04, 0.110459595022e-05, 0.18235530206e-07, 0.2370769803e-09, 0.24887296e-11, 0.21529e-13, 0.156e-15 }; static cheb_series synchrotron21_cs = { synchrotron21_data, 12, -1.0, 1.0, 9 }; static double synchrotron22_data[13] = { 7.9063148270660804288, 3.1353463612853425684, 0.4854879477453714538, 0.394816675827237234e-01, 0.19661622334808802e-02, 0.659078932293042e-04, 0.15857561349856e-05, 0.286865301123e-07, 0.4041202360e-09, 0.45568444e-11, 0.420459e-13, 0.3232e-15, 0.21e-17 }; static cheb_series synchrotron22_cs = { synchrotron22_data, 12, -1.0, 1.0, 8 }; static double synchrotron2a_data[17] = { 2.020337094170713600, 0.10956237121807404e-01, 0.8542384730114676e-03, 0.723430242132822e-04, 0.63124427962699e-05, 0.5648193141174e-06, 0.512832480138e-07, 0.47196532914e-08, 0.4380744214e-09, 0.410268149e-10, 0.38623072e-11, 0.3661323e-12, 0.348023e-13, 0.33301e-14, 0.319e-15, 0.307e-16, 0.3e-17 }; static cheb_series synchrotron2a_cs = { synchrotron2a_data, 16, -1.0, 1.0, 8 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_synchrotron_1_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*M_SQRT2 * GSL_SQRT_DBL_EPSILON) { /* BJG: added first order correction term. The taylor series is S1(x) = ((4pi)/(sqrt(3)gamma(1/3))) * (x/2)^(1/3) * (1 - (gamma(1/3)/2)*(x/2)^2/3 + (3/4) * (x/2)^2 ....) */ double z = pow(x, 1.0/3.0); double cf = 1 - 8.43812762813205e-01 * z * z; result->val = 2.14952824153447863671 * z * cf; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x <= 4.0) { const double c0 = M_PI/M_SQRT3; const double px = pow(x,1.0/3.0); const double px11 = gsl_sf_pow_int(px,11); const double t = x*x/8.0 - 1.0; gsl_sf_result result_c1; gsl_sf_result result_c2; cheb_eval_e(&synchrotron1_cs, t, &result_c1); cheb_eval_e(&synchrotron2_cs, t, &result_c2); result->val = px * result_c1.val - px11 * result_c2.val - c0 * x; result->err = px * result_c1.err + px11 * result_c2.err + c0 * x * GSL_DBL_EPSILON; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -8.0*GSL_LOG_DBL_MIN/7.0) { const double c0 = 0.2257913526447274323630976; /* log(sqrt(pi/2)) */ const double t = (12.0 - x) / (x + 4.0); gsl_sf_result result_c1; cheb_eval_e(&synchrotron1a_cs, t, &result_c1); result->val = sqrt(x) * result_c1.val * exp(c0 - x); result->err = 2.0 * GSL_DBL_EPSILON * result->val * (fabs(c0-x)+1.0); return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } int gsl_sf_synchrotron_2_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*M_SQRT2*GSL_SQRT_DBL_EPSILON) { /* BJG: added first order correction term. The taylor series is S2(x) = ((2pi)/(sqrt(3)*gamma(1/3))) * (x/2)^(1/3) * (1 - (gamma(1/3)/gamma(4/3))*(x/2)^(4/3) + (gamma(1/3)/gamma(4/3))*(x/2)^2...) */ double z = pow(x, 1.0/3.0); double cf = 1 - 1.17767156510235e+00 * z * x; result->val = 1.07476412076723931836 * z * cf ; result->err = 2.0 * GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x <= 4.0) { const double px = pow(x, 1.0/3.0); const double px5 = gsl_sf_pow_int(px,5); const double t = x*x/8.0 - 1.0; gsl_sf_result cheb1; gsl_sf_result cheb2; cheb_eval_e(&synchrotron21_cs, t, &cheb1); cheb_eval_e(&synchrotron22_cs, t, &cheb2); result->val = px * cheb1.val - px5 * cheb2.val; result->err = px * cheb1.err + px5 * cheb2.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -8.0*GSL_LOG_DBL_MIN/7.0) { const double c0 = 0.22579135264472743236; /* log(sqrt(pi/2)) */ const double t = (10.0 - x) / (x + 2.0); gsl_sf_result cheb1; cheb_eval_e(&synchrotron2a_cs, t, &cheb1); result->val = sqrt(x) * exp(c0-x) * cheb1.val; result->err = GSL_DBL_EPSILON * result->val * (fabs(c0-x)+1.0); return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_synchrotron_1(const double x) { EVAL_RESULT(gsl_sf_synchrotron_1_e(x, &result)); } double gsl_sf_synchrotron_2(const double x) { EVAL_RESULT(gsl_sf_synchrotron_2_e(x, &result)); } sources_5316/external/gsl/gsl_integration__qawf.c0000664000176700017670000001430511723710247021054 0ustar paulpaul/* integration/qawf.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_integration.h" #include "gsl_integration__initialise.c" #include "gsl_integration__append.c" #include "gsl_integration__qelg.c" int gsl_integration_qawf (gsl_function * f, const double a, const double epsabs, const size_t limit, gsl_integration_workspace * workspace, gsl_integration_workspace * cycle_workspace, gsl_integration_qawo_table * wf, double *result, double *abserr) { double area, errsum; double res_ext, err_ext; double correc, total_error = 0.0, truncation_error; size_t ktmin = 0; size_t iteration = 0; struct extrapolation_table table; double cycle; double omega = wf->omega; const double p = 0.9; double factor = 1; double initial_eps, eps; int error_type = 0; /* Initialize results */ initialise (workspace, a, a); *result = 0; *abserr = 0; if (limit > workspace->limit) { GSL_ERROR ("iteration limit exceeds available workspace", GSL_EINVAL) ; } /* Test on accuracy */ if (epsabs <= 0) { GSL_ERROR ("absolute tolerance epsabs must be positive", GSL_EBADTOL) ; } if (omega == 0.0) { if (wf->sine == GSL_INTEG_SINE) { /* The function sin(w x) f(x) is always zero for w = 0 */ *result = 0; *abserr = 0; return GSL_SUCCESS; } else { /* The function cos(w x) f(x) is always f(x) for w = 0 */ int status = gsl_integration_qagiu (f, a, epsabs, 0.0, cycle_workspace->limit, cycle_workspace, result, abserr); return status; } } if (epsabs > GSL_DBL_MIN / (1 - p)) { eps = epsabs * (1 - p); } else { eps = epsabs; } initial_eps = eps; area = 0; errsum = 0; res_ext = 0; err_ext = GSL_DBL_MAX; correc = 0; cycle = (2 * floor (fabs (omega)) + 1) * M_PI / fabs (omega); gsl_integration_qawo_table_set_length (wf, cycle); initialise_table (&table); for (iteration = 0; iteration < limit; iteration++) { double area1, error1, reseps, erreps; double a1 = a + iteration * cycle; double b1 = a1 + cycle; double epsabs1 = eps * factor; int status = gsl_integration_qawo (f, a1, epsabs1, 0.0, limit, cycle_workspace, wf, &area1, &error1); append_interval (workspace, a1, b1, area1, error1); factor *= p; area = area + area1; errsum = errsum + error1; /* estimate the truncation error as 50 times the final term */ truncation_error = 50 * fabs (area1); total_error = errsum + truncation_error; if (total_error < epsabs && iteration > 4) { goto compute_result; } if (error1 > correc) { correc = error1; } if (status) { eps = GSL_MAX_DBL (initial_eps, correc * (1.0 - p)); } if (status && total_error < 10 * correc && iteration > 3) { goto compute_result; } append_table (&table, area); if (table.n < 2) { continue; } qelg (&table, &reseps, &erreps); ktmin++; if (ktmin >= 15 && err_ext < 0.001 * total_error) { error_type = 4; } if (erreps < err_ext) { ktmin = 0; err_ext = erreps; res_ext = reseps; if (err_ext + 10 * correc <= epsabs) break; if (err_ext <= epsabs && 10 * correc >= epsabs) break; } } if (iteration == limit) error_type = 1; if (err_ext == GSL_DBL_MAX) goto compute_result; err_ext = err_ext + 10 * correc; *result = res_ext; *abserr = err_ext; if (error_type == 0) { return GSL_SUCCESS ; } if (res_ext != 0.0 && area != 0.0) { if (err_ext / fabs (res_ext) > errsum / fabs (area)) goto compute_result; } else if (err_ext > errsum) { goto compute_result; } else if (area == 0.0) { goto return_error; } if (error_type == 4) { err_ext = err_ext + truncation_error; } goto return_error; compute_result: *result = area; *abserr = total_error; return_error: if (error_type > 2) error_type--; if (error_type == 0) { return GSL_SUCCESS; } else if (error_type == 1) { GSL_ERROR ("number of iterations was insufficient", GSL_EMAXITER); } else if (error_type == 2) { GSL_ERROR ("cannot reach tolerance because of roundoff error", GSL_EROUND); } else if (error_type == 3) { GSL_ERROR ("bad integrand behavior found in the integration interval", GSL_ESING); } else if (error_type == 4) { GSL_ERROR ("roundoff error detected in the extrapolation table", GSL_EROUND); } else if (error_type == 5) { GSL_ERROR ("integral is divergent, or slowly convergent", GSL_EDIVERGE); } else { GSL_ERROR ("could not integrate function", GSL_EFAILED); } } sources_5316/external/gsl/gsl_sf__gamma_inc.c0000644000176700017670000004514710707442037020124 0ustar paulpaul/* specfunc/gamma_inc.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_erf.h" #include "gsl_sf_exp.h" #include "gsl_sf_log.h" #include "gsl_sf_gamma.h" #include "gsl_sf_expint.h" #include "gsl_sf__error.h" /* The dominant part, * D(a,x) := x^a e^(-x) / Gamma(a+1) */ static int gamma_inc_D(const double a, const double x, gsl_sf_result * result) { if(a < 10.0) { double lnr; gsl_sf_result lg; gsl_sf_lngamma_e(a+1.0, &lg); lnr = a * log(x) - x - lg.val; result->val = exp(lnr); result->err = 2.0 * GSL_DBL_EPSILON * (fabs(lnr) + 1.0) * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result gstar; gsl_sf_result ln_term; double term1; if (x < 0.5*a) { double u = x/a; double ln_u = log(u); ln_term.val = ln_u - u + 1.0; ln_term.err = (fabs(ln_u) + fabs(u) + 1.0) * GSL_DBL_EPSILON; } else { double mu = (x-a)/a; gsl_sf_log_1plusx_mx_e(mu, &ln_term); /* log(1+mu) - mu */ }; gsl_sf_gammastar_e(a, &gstar); term1 = exp(a*ln_term.val)/sqrt(2.0*M_PI*a); result->val = term1/gstar.val; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(a*ln_term.val) + 1.0) * fabs(result->val); result->err += gstar.err/fabs(gstar.val) * fabs(result->val); return GSL_SUCCESS; } } /* P series representation. */ static int gamma_inc_P_series(const double a, const double x, gsl_sf_result * result) { const int nmax = 5000; gsl_sf_result D; int stat_D = gamma_inc_D(a, x, &D); double sum = 1.0; double term = 1.0; int n; for(n=1; nval = D.val * sum; result->err = D.err * fabs(sum); result->err += (1.0 + n) * GSL_DBL_EPSILON * fabs(result->val); if(n == nmax) GSL_ERROR ("error", GSL_EMAXITER); else return stat_D; } /* Q large x asymptotic */ static int gamma_inc_Q_large_x(const double a, const double x, gsl_sf_result * result) { const int nmax = 5000; gsl_sf_result D; const int stat_D = gamma_inc_D(a, x, &D); double sum = 1.0; double term = 1.0; double last = 1.0; int n; for(n=1; n 1.0) break; if(fabs(term/sum) < GSL_DBL_EPSILON) break; sum += term; last = term; } result->val = D.val * (a/x) * sum; result->err = D.err * fabs((a/x) * sum); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(n == nmax) GSL_ERROR ("error in large x asymptotic", GSL_EMAXITER); else return stat_D; } /* Uniform asymptotic for x near a, a and x large. * See [Temme, p. 285] */ static int gamma_inc_Q_asymp_unif(const double a, const double x, gsl_sf_result * result) { const double rta = sqrt(a); const double eps = (x-a)/a; gsl_sf_result ln_term; const int stat_ln = gsl_sf_log_1plusx_mx_e(eps, &ln_term); /* log(1+eps) - eps */ const double eta = GSL_SIGN(eps) * sqrt(-2.0*ln_term.val); gsl_sf_result erfc; double R; double c0, c1; /* This used to say erfc(eta*M_SQRT2*rta), which is wrong. * The sqrt(2) is in the denominator. Oops. * Fixed: [GJ] Mon Nov 15 13:25:32 MST 2004 */ gsl_sf_erfc_e(eta*rta/M_SQRT2, &erfc); if(fabs(eps) < GSL_ROOT5_DBL_EPSILON) { c0 = -1.0/3.0 + eps*(1.0/12.0 - eps*(23.0/540.0 - eps*(353.0/12960.0 - eps*589.0/30240.0))); c1 = -1.0/540.0 - eps/288.0; } else { const double rt_term = sqrt(-2.0 * ln_term.val/(eps*eps)); const double lam = x/a; c0 = (1.0 - 1.0/rt_term)/eps; c1 = -(eta*eta*eta * (lam*lam + 10.0*lam + 1.0) - 12.0 * eps*eps*eps) / (12.0 * eta*eta*eta*eps*eps*eps); } R = exp(-0.5*a*eta*eta)/(M_SQRT2*M_SQRTPI*rta) * (c0 + c1/a); result->val = 0.5 * erfc.val + R; result->err = GSL_DBL_EPSILON * fabs(R * 0.5 * a*eta*eta) + 0.5 * erfc.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_ln; } /* Continued fraction which occurs in evaluation * of Q(a,x) or Gamma(a,x). * * 1 (1-a)/x 1/x (2-a)/x 2/x (3-a)/x * F(a,x) = ---- ------- ----- -------- ----- -------- ... * 1 + 1 + 1 + 1 + 1 + 1 + * * Hans E. Plesser, 2002-01-22 (hans dot plesser at itf dot nlh dot no). * * Split out from gamma_inc_Q_CF() by GJ [Tue Apr 1 13:16:41 MST 2003]. * See gamma_inc_Q_CF() below. * */ static int gamma_inc_F_CF(const double a, const double x, gsl_sf_result * result) { const int nmax = 5000; const double small = gsl_pow_3 (GSL_DBL_EPSILON); double hn = 1.0; /* convergent */ double Cn = 1.0 / small; double Dn = 1.0; int n; /* n == 1 has a_1, b_1, b_0 independent of a,x, so that has been done by hand */ for ( n = 2 ; n < nmax ; n++ ) { double an; double delta; if(GSL_IS_ODD(n)) an = 0.5*(n-1)/x; else an = (0.5*n-a)/x; Dn = 1.0 + an * Dn; if ( fabs(Dn) < small ) Dn = small; Cn = 1.0 + an/Cn; if ( fabs(Cn) < small ) Cn = small; Dn = 1.0 / Dn; delta = Cn * Dn; hn *= delta; if(fabs(delta-1.0) < GSL_DBL_EPSILON) break; } result->val = hn; result->err = 2.0*GSL_DBL_EPSILON * fabs(hn); result->err += GSL_DBL_EPSILON * (2.0 + 0.5*n) * fabs(result->val); if(n == nmax) GSL_ERROR ("error in CF for F(a,x)", GSL_EMAXITER); else return GSL_SUCCESS; } /* Continued fraction for Q. * * Q(a,x) = D(a,x) a/x F(a,x) * * Hans E. Plesser, 2002-01-22 (hans dot plesser at itf dot nlh dot no): * * Since the Gautschi equivalent series method for CF evaluation may lead * to singularities, I have replaced it with the modified Lentz algorithm * given in * * I J Thompson and A R Barnett * Coulomb and Bessel Functions of Complex Arguments and Order * J Computational Physics 64:490-509 (1986) * * In consequence, gamma_inc_Q_CF_protected() is now obsolete and has been * removed. * * Identification of terms between the above equation for F(a, x) and * the first equation in the appendix of Thompson&Barnett is as follows: * * b_0 = 0, b_n = 1 for all n > 0 * * a_1 = 1 * a_n = (n/2-a)/x for n even * a_n = (n-1)/(2x) for n odd * */ static int gamma_inc_Q_CF(const double a, const double x, gsl_sf_result * result) { gsl_sf_result D; gsl_sf_result F; const int stat_D = gamma_inc_D(a, x, &D); const int stat_F = gamma_inc_F_CF(a, x, &F); result->val = D.val * (a/x) * F.val; result->err = D.err * fabs((a/x) * F.val) + fabs(D.val * a/x * F.err); return GSL_ERROR_SELECT_2(stat_F, stat_D); } /* Useful for small a and x. Handles the subtraction analytically. */ static int gamma_inc_Q_series(const double a, const double x, gsl_sf_result * result) { double term1; /* 1 - x^a/Gamma(a+1) */ double sum; /* 1 + (a+1)/(a+2)(-x)/2! + (a+1)/(a+3)(-x)^2/3! + ... */ int stat_sum; double term2; /* a temporary variable used at the end */ { /* Evaluate series for 1 - x^a/Gamma(a+1), small a */ const double pg21 = -2.404113806319188570799476; /* PolyGamma[2,1] */ const double lnx = log(x); const double el = M_EULER+lnx; const double c1 = -el; const double c2 = M_PI*M_PI/12.0 - 0.5*el*el; const double c3 = el*(M_PI*M_PI/12.0 - el*el/6.0) + pg21/6.0; const double c4 = -0.04166666666666666667 * (-1.758243446661483480 + lnx) * (-0.764428657272716373 + lnx) * ( 0.723980571623507657 + lnx) * ( 4.107554191916823640 + lnx); const double c5 = -0.0083333333333333333 * (-2.06563396085715900 + lnx) * (-1.28459889470864700 + lnx) * (-0.27583535756454143 + lnx) * ( 1.33677371336239618 + lnx) * ( 5.17537282427561550 + lnx); const double c6 = -0.0013888888888888889 * (-2.30814336454783200 + lnx) * (-1.65846557706987300 + lnx) * (-0.88768082560020400 + lnx) * ( 0.17043847751371778 + lnx) * ( 1.92135970115863890 + lnx) * ( 6.22578557795474900 + lnx); const double c7 = -0.00019841269841269841 * (-2.5078657901291800 + lnx) * (-1.9478900888958200 + lnx) * (-1.3194837322612730 + lnx) * (-0.5281322700249279 + lnx) * ( 0.5913834939078759 + lnx) * ( 2.4876819633378140 + lnx) * ( 7.2648160783762400 + lnx); const double c8 = -0.00002480158730158730 * (-2.677341544966400 + lnx) * (-2.182810448271700 + lnx) * (-1.649350342277400 + lnx) * (-1.014099048290790 + lnx) * (-0.191366955370652 + lnx) * ( 0.995403817918724 + lnx) * ( 3.041323283529310 + lnx) * ( 8.295966556941250 + lnx); const double c9 = -2.75573192239859e-6 * (-2.8243487670469080 + lnx) * (-2.3798494322701120 + lnx) * (-1.9143674728689960 + lnx) * (-1.3814529102920370 + lnx) * (-0.7294312810261694 + lnx) * ( 0.1299079285269565 + lnx) * ( 1.3873333251885240 + lnx) * ( 3.5857258865210760 + lnx) * ( 9.3214237073814600 + lnx); const double c10 = -2.75573192239859e-7 * (-2.9540329644556910 + lnx) * (-2.5491366926991850 + lnx) * (-2.1348279229279880 + lnx) * (-1.6741881076349450 + lnx) * (-1.1325949616098420 + lnx) * (-0.4590034650618494 + lnx) * ( 0.4399352987435699 + lnx) * ( 1.7702236517651670 + lnx) * ( 4.1231539047474080 + lnx) * ( 10.342627908148680 + lnx); term1 = a*(c1+a*(c2+a*(c3+a*(c4+a*(c5+a*(c6+a*(c7+a*(c8+a*(c9+a*c10))))))))); } { /* Evaluate the sum. */ const int nmax = 5000; double t = 1.0; int n; sum = 1.0; for(n=1; nval = term1 + term2; result->err = GSL_DBL_EPSILON * (fabs(term1) + 2.0*fabs(term2)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_sum; } /* series for small a and x, but not defined for a == 0 */ static int gamma_inc_series(double a, double x, gsl_sf_result * result) { gsl_sf_result Q; gsl_sf_result G; const int stat_Q = gamma_inc_Q_series(a, x, &Q); const int stat_G = gsl_sf_gamma_e(a, &G); result->val = Q.val * G.val; result->err = fabs(Q.val * G.err) + fabs(Q.err * G.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Q, stat_G); } static int gamma_inc_a_gt_0(double a, double x, gsl_sf_result * result) { /* x > 0 and a > 0; use result for Q */ gsl_sf_result Q; gsl_sf_result G; const int stat_Q = gsl_sf_gamma_inc_Q_e(a, x, &Q); const int stat_G = gsl_sf_gamma_e(a, &G); result->val = G.val * Q.val; result->err = fabs(G.val * Q.err) + fabs(G.err * Q.val); result->err += 2.0*GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_G, stat_Q); } static int gamma_inc_CF(double a, double x, gsl_sf_result * result) { gsl_sf_result F; gsl_sf_result pre; const double am1lgx = (a-1.0)*log(x); const int stat_F = gamma_inc_F_CF(a, x, &F); const int stat_E = gsl_sf_exp_err_e(am1lgx - x, GSL_DBL_EPSILON*fabs(am1lgx), &pre); result->val = F.val * pre.val; result->err = fabs(F.err * pre.val) + fabs(F.val * pre.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_F, stat_E); } /* evaluate Gamma(0,x), x > 0 */ #define GAMMA_INC_A_0(x, result) gsl_sf_expint_E1_e(x, result) /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_gamma_inc_Q_e(const double a, const double x, gsl_sf_result * result) { if(a < 0.0 || x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(a == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x <= 0.5*a) { /* If the series is quick, do that. It is * robust and simple. */ gsl_sf_result P; int stat_P = gamma_inc_P_series(a, x, &P); result->val = 1.0 - P.val; result->err = P.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_P; } else if(a >= 1.0e+06 && (x-a)*(x-a) < a) { /* Then try the difficult asymptotic regime. * This is the only way to do this region. */ return gamma_inc_Q_asymp_unif(a, x, result); } else if(a < 0.2 && x < 5.0) { /* Cancellations at small a must be handled * analytically; x should not be too big * either since the series terms grow * with x and log(x). */ return gamma_inc_Q_series(a, x, result); } else if(a <= x) { if(x <= 1.0e+06) { /* Continued fraction is excellent for x >~ a. * We do not let x be too large when x > a since * it is somewhat pointless to try this there; * the function is rapidly decreasing for * x large and x > a, and it will just * underflow in that region anyway. We * catch that case in the standard * large-x method. */ return gamma_inc_Q_CF(a, x, result); } else { return gamma_inc_Q_large_x(a, x, result); } } else { if(x > a - sqrt(a)) { /* Continued fraction again. The convergence * is a little slower here, but that is fine. * We have to trade that off against the slow * convergence of the series, which is the * only other option. */ return gamma_inc_Q_CF(a, x, result); } else { gsl_sf_result P; int stat_P = gamma_inc_P_series(a, x, &P); result->val = 1.0 - P.val; result->err = P.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_P; } } } int gsl_sf_gamma_inc_P_e(const double a, const double x, gsl_sf_result * result) { if(a <= 0.0 || x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 20.0 || x < 0.5*a) { /* Do the easy series cases. Robust and quick. */ return gamma_inc_P_series(a, x, result); } else if(a > 1.0e+06 && (x-a)*(x-a) < a) { /* Crossover region. Note that Q and P are * roughly the same order of magnitude here, * so the subtraction is stable. */ gsl_sf_result Q; int stat_Q = gamma_inc_Q_asymp_unif(a, x, &Q); result->val = 1.0 - Q.val; result->err = Q.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_Q; } else if(a <= x) { /* Q <~ P in this area, so the * subtractions are stable. */ gsl_sf_result Q; int stat_Q; if(a > 0.2*x) { stat_Q = gamma_inc_Q_CF(a, x, &Q); } else { stat_Q = gamma_inc_Q_large_x(a, x, &Q); } result->val = 1.0 - Q.val; result->err = Q.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_Q; } else { if((x-a)*(x-a) < a) { /* This condition is meant to insure * that Q is not very close to 1, * so the subtraction is stable. */ gsl_sf_result Q; int stat_Q = gamma_inc_Q_CF(a, x, &Q); result->val = 1.0 - Q.val; result->err = Q.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_Q; } else { return gamma_inc_P_series(a, x, result); } } } int gsl_sf_gamma_inc_e(const double a, const double x, gsl_sf_result * result) { if(x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { return gsl_sf_gamma_e(a, result); } else if(a == 0.0) { return GAMMA_INC_A_0(x, result); } else if(a > 0.0) { return gamma_inc_a_gt_0(a, x, result); } else if(x > 0.25) { /* continued fraction seems to fail for x too small; otherwise it is ok, independent of the value of |x/a|, because of the non-oscillation in the expansion, i.e. the CF is un-conditionally convergent for a < 0 and x > 0 */ return gamma_inc_CF(a, x, result); } else if(fabs(a) < 0.5) { return gamma_inc_series(a, x, result); } else { /* a = fa + da; da >= 0 */ const double fa = floor(a); const double da = a - fa; gsl_sf_result g_da; const int stat_g_da = ( da > 0.0 ? gamma_inc_a_gt_0(da, x, &g_da) : GAMMA_INC_A_0(x, &g_da)); double alpha = da; double gax = g_da.val; /* Gamma(alpha-1,x) = 1/(alpha-1) (Gamma(a,x) - x^(alpha-1) e^-x) */ do { const double shift = exp(-x + (alpha-1.0)*log(x)); gax = (gax - shift) / (alpha - 1.0); alpha -= 1.0; } while(alpha > a); result->val = gax; result->err = 2.0*(1.0 + fabs(a))*GSL_DBL_EPSILON*fabs(gax); return stat_g_da; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_gamma_inc_P(const double a, const double x) { EVAL_RESULT(gsl_sf_gamma_inc_P_e(a, x, &result)); } double gsl_sf_gamma_inc_Q(const double a, const double x) { EVAL_RESULT(gsl_sf_gamma_inc_Q_e(a, x, &result)); } double gsl_sf_gamma_inc(const double a, const double x) { EVAL_RESULT(gsl_sf_gamma_inc_e(a, x, &result)); } sources_5316/external/gsl/gsl_randist__cauchy.c0000664000176700017670000000260711723710247020515 0ustar paulpaul/* randist/cauchy.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The Cauchy probability distribution is p(x) dx = (1/(pi a)) (1 + (x/a)^2)^(-1) dx It is also known as the Lorentzian probability distribution */ double gsl_ran_cauchy (const gsl_rng * r, const double a) { double u; do { u = gsl_rng_uniform (r); } while (u == 0.5); return a * tan (M_PI * u); } double gsl_ran_cauchy_pdf (const double x, const double a) { double u = x / a; double p = (1 / (M_PI * a)) / (1 + u * u); return p; } sources_5316/external/gsl/gsl_matrix_long_double.h0000664000176700017670000003142411705263724021242 0ustar paulpaul/* matrix/gsl_matrix_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_LONG_DOUBLE_H__ #define __GSL_MATRIX_LONG_DOUBLE_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_long_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; long double * data; gsl_block_long_double * block; int owner; } gsl_matrix_long_double; typedef struct { gsl_matrix_long_double matrix; } _gsl_matrix_long_double_view; typedef _gsl_matrix_long_double_view gsl_matrix_long_double_view; typedef struct { gsl_matrix_long_double matrix; } _gsl_matrix_long_double_const_view; typedef const _gsl_matrix_long_double_const_view gsl_matrix_long_double_const_view; /* Allocation */ gsl_matrix_long_double * gsl_matrix_long_double_alloc (const size_t n1, const size_t n2); gsl_matrix_long_double * gsl_matrix_long_double_calloc (const size_t n1, const size_t n2); gsl_matrix_long_double * gsl_matrix_long_double_alloc_from_block (gsl_block_long_double * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_long_double * gsl_matrix_long_double_alloc_from_matrix (gsl_matrix_long_double * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_long_double * gsl_vector_long_double_alloc_row_from_matrix (gsl_matrix_long_double * m, const size_t i); gsl_vector_long_double * gsl_vector_long_double_alloc_col_from_matrix (gsl_matrix_long_double * m, const size_t j); void gsl_matrix_long_double_free (gsl_matrix_long_double * m); /* Views */ _gsl_matrix_long_double_view gsl_matrix_long_double_submatrix (gsl_matrix_long_double * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_long_double_view gsl_matrix_long_double_row (gsl_matrix_long_double * m, const size_t i); _gsl_vector_long_double_view gsl_matrix_long_double_column (gsl_matrix_long_double * m, const size_t j); _gsl_vector_long_double_view gsl_matrix_long_double_diagonal (gsl_matrix_long_double * m); _gsl_vector_long_double_view gsl_matrix_long_double_subdiagonal (gsl_matrix_long_double * m, const size_t k); _gsl_vector_long_double_view gsl_matrix_long_double_superdiagonal (gsl_matrix_long_double * m, const size_t k); _gsl_vector_long_double_view gsl_matrix_long_double_subrow (gsl_matrix_long_double * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_long_double_view gsl_matrix_long_double_subcolumn (gsl_matrix_long_double * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_long_double_view gsl_matrix_long_double_view_array (long double * base, const size_t n1, const size_t n2); _gsl_matrix_long_double_view gsl_matrix_long_double_view_array_with_tda (long double * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_long_double_view gsl_matrix_long_double_view_vector (gsl_vector_long_double * v, const size_t n1, const size_t n2); _gsl_matrix_long_double_view gsl_matrix_long_double_view_vector_with_tda (gsl_vector_long_double * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_long_double_const_view gsl_matrix_long_double_const_submatrix (const gsl_matrix_long_double * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_long_double_const_view gsl_matrix_long_double_const_row (const gsl_matrix_long_double * m, const size_t i); _gsl_vector_long_double_const_view gsl_matrix_long_double_const_column (const gsl_matrix_long_double * m, const size_t j); _gsl_vector_long_double_const_view gsl_matrix_long_double_const_diagonal (const gsl_matrix_long_double * m); _gsl_vector_long_double_const_view gsl_matrix_long_double_const_subdiagonal (const gsl_matrix_long_double * m, const size_t k); _gsl_vector_long_double_const_view gsl_matrix_long_double_const_superdiagonal (const gsl_matrix_long_double * m, const size_t k); _gsl_vector_long_double_const_view gsl_matrix_long_double_const_subrow (const gsl_matrix_long_double * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_long_double_const_view gsl_matrix_long_double_const_subcolumn (const gsl_matrix_long_double * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_long_double_const_view gsl_matrix_long_double_const_view_array (const long double * base, const size_t n1, const size_t n2); _gsl_matrix_long_double_const_view gsl_matrix_long_double_const_view_array_with_tda (const long double * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_long_double_const_view gsl_matrix_long_double_const_view_vector (const gsl_vector_long_double * v, const size_t n1, const size_t n2); _gsl_matrix_long_double_const_view gsl_matrix_long_double_const_view_vector_with_tda (const gsl_vector_long_double * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ long double gsl_matrix_long_double_get(const gsl_matrix_long_double * m, const size_t i, const size_t j); void gsl_matrix_long_double_set(gsl_matrix_long_double * m, const size_t i, const size_t j, const long double x); long double * gsl_matrix_long_double_ptr(gsl_matrix_long_double * m, const size_t i, const size_t j); const long double * gsl_matrix_long_double_const_ptr(const gsl_matrix_long_double * m, const size_t i, const size_t j); void gsl_matrix_long_double_set_zero (gsl_matrix_long_double * m); void gsl_matrix_long_double_set_identity (gsl_matrix_long_double * m); void gsl_matrix_long_double_set_all (gsl_matrix_long_double * m, long double x); int gsl_matrix_long_double_fread (FILE * stream, gsl_matrix_long_double * m) ; int gsl_matrix_long_double_fwrite (FILE * stream, const gsl_matrix_long_double * m) ; int gsl_matrix_long_double_fscanf (FILE * stream, gsl_matrix_long_double * m); int gsl_matrix_long_double_fprintf (FILE * stream, const gsl_matrix_long_double * m, const char * format); int gsl_matrix_long_double_memcpy(gsl_matrix_long_double * dest, const gsl_matrix_long_double * src); int gsl_matrix_long_double_swap(gsl_matrix_long_double * m1, gsl_matrix_long_double * m2); int gsl_matrix_long_double_swap_rows(gsl_matrix_long_double * m, const size_t i, const size_t j); int gsl_matrix_long_double_swap_columns(gsl_matrix_long_double * m, const size_t i, const size_t j); int gsl_matrix_long_double_swap_rowcol(gsl_matrix_long_double * m, const size_t i, const size_t j); int gsl_matrix_long_double_transpose (gsl_matrix_long_double * m); int gsl_matrix_long_double_transpose_memcpy (gsl_matrix_long_double * dest, const gsl_matrix_long_double * src); long double gsl_matrix_long_double_max (const gsl_matrix_long_double * m); long double gsl_matrix_long_double_min (const gsl_matrix_long_double * m); void gsl_matrix_long_double_minmax (const gsl_matrix_long_double * m, long double * min_out, long double * max_out); void gsl_matrix_long_double_max_index (const gsl_matrix_long_double * m, size_t * imax, size_t *jmax); void gsl_matrix_long_double_min_index (const gsl_matrix_long_double * m, size_t * imin, size_t *jmin); void gsl_matrix_long_double_minmax_index (const gsl_matrix_long_double * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_long_double_isnull (const gsl_matrix_long_double * m); int gsl_matrix_long_double_ispos (const gsl_matrix_long_double * m); int gsl_matrix_long_double_isneg (const gsl_matrix_long_double * m); int gsl_matrix_long_double_isnonneg (const gsl_matrix_long_double * m); int gsl_matrix_long_double_add (gsl_matrix_long_double * a, const gsl_matrix_long_double * b); int gsl_matrix_long_double_sub (gsl_matrix_long_double * a, const gsl_matrix_long_double * b); int gsl_matrix_long_double_mul_elements (gsl_matrix_long_double * a, const gsl_matrix_long_double * b); int gsl_matrix_long_double_div_elements (gsl_matrix_long_double * a, const gsl_matrix_long_double * b); int gsl_matrix_long_double_scale (gsl_matrix_long_double * a, const double x); int gsl_matrix_long_double_add_constant (gsl_matrix_long_double * a, const double x); int gsl_matrix_long_double_add_diagonal (gsl_matrix_long_double * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_long_double_get_row(gsl_vector_long_double * v, const gsl_matrix_long_double * m, const size_t i); int gsl_matrix_long_double_get_col(gsl_vector_long_double * v, const gsl_matrix_long_double * m, const size_t j); int gsl_matrix_long_double_set_row(gsl_matrix_long_double * m, const size_t i, const gsl_vector_long_double * v); int gsl_matrix_long_double_set_col(gsl_matrix_long_double * m, const size_t j, const gsl_vector_long_double * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline long double gsl_matrix_long_double_get(const gsl_matrix_long_double * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_long_double_set(gsl_matrix_long_double * m, const size_t i, const size_t j, const long double x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline long double * gsl_matrix_long_double_ptr(gsl_matrix_long_double * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (long double *) (m->data + (i * m->tda + j)) ; } extern inline const long double * gsl_matrix_long_double_const_ptr(const gsl_matrix_long_double * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const long double *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_ieee-utils__print.c0000664000176700017670000000523511723710247020776 0ustar paulpaul/* ieee-utils/print.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_ieee_utils.h" /* A table of sign characters, 0=positive, 1=negative. We print a space instead of a unary + sign for compatibility with bc */ static char signs[2]={' ','-'} ; void gsl_ieee_fprintf_float (FILE * stream, const float * x) { gsl_ieee_float_rep r ; gsl_ieee_float_to_rep(x, &r) ; switch (r.type) { case GSL_IEEE_TYPE_NAN: fprintf(stream, "NaN") ; break ; case GSL_IEEE_TYPE_INF: fprintf(stream, "%cInf", signs[r.sign]) ; break ; case GSL_IEEE_TYPE_NORMAL: fprintf(stream, "%c1.%s*2^%d", signs[r.sign], r.mantissa, r.exponent) ; break ; case GSL_IEEE_TYPE_DENORMAL: fprintf(stream, "%c0.%s*2^%d", signs[r.sign], r.mantissa, r.exponent + 1) ; break ; case GSL_IEEE_TYPE_ZERO: fprintf(stream, "%c0", signs[r.sign]) ; break ; default: fprintf(stream, "[non-standard IEEE float]") ; } } void gsl_ieee_printf_float (const float * x) { gsl_ieee_fprintf_float (stdout,x); } void gsl_ieee_fprintf_double (FILE * stream, const double * x) { gsl_ieee_double_rep r ; gsl_ieee_double_to_rep (x, &r) ; switch (r.type) { case GSL_IEEE_TYPE_NAN: fprintf(stream, "NaN") ; break ; case GSL_IEEE_TYPE_INF: fprintf(stream, "%cInf", signs[r.sign]) ; break ; case GSL_IEEE_TYPE_NORMAL: fprintf(stream, "%c1.%s*2^%d", signs[r.sign], r.mantissa, r.exponent) ; break ; case GSL_IEEE_TYPE_DENORMAL: fprintf(stream, "%c0.%s*2^%d", signs[r.sign], r.mantissa, r.exponent + 1) ; break ; case GSL_IEEE_TYPE_ZERO: fprintf(stream, "%c0", signs[r.sign]) ; break ; default: fprintf(stream, "[non-standard IEEE double]") ; } } void gsl_ieee_printf_double (const double * x) { gsl_ieee_fprintf_double (stdout,x); } sources_5316/external/gsl/gsl_cblas__csyrk.c0000664000176700017670000000063711723710247020015 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_csyrk (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *beta, void *C, const int ldc) { #define BASE float #include "gsl_cblas__source_syrk_c.h" #undef BASE } sources_5316/external/gsl/gsl_linalg__luc.c0000664000176700017670000002076611723710247017634 0ustar paulpaul/* linalg/luc.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_complex.h" #include "gsl_complex_math.h" #include "gsl_permute_vector.h" #include "gsl_blas.h" #include "gsl_complex_math.h" #include "gsl_linalg.h" /* Factorise a general N x N complex matrix A into, * * P A = L U * * where P is a permutation matrix, L is unit lower triangular and U * is upper triangular. * * L is stored in the strict lower triangular part of the input * matrix. The diagonal elements of L are unity and are not stored. * * U is stored in the diagonal and upper triangular part of the * input matrix. * * P is stored in the permutation p. Column j of P is column k of the * identity matrix, where k = permutation->data[j] * * signum gives the sign of the permutation, (-1)^n, where n is the * number of interchanges in the permutation. * * See Golub & Van Loan, Matrix Computations, Algorithm 3.4.1 (Gauss * Elimination with Partial Pivoting). */ int gsl_linalg_complex_LU_decomp (gsl_matrix_complex * A, gsl_permutation * p, int *signum) { if (A->size1 != A->size2) { GSL_ERROR ("LU decomposition requires square matrix", GSL_ENOTSQR); } else if (p->size != A->size1) { GSL_ERROR ("permutation length must match matrix size", GSL_EBADLEN); } else { const size_t N = A->size1; size_t i, j, k; *signum = 1; gsl_permutation_init (p); for (j = 0; j < N - 1; j++) { /* Find maximum in the j-th column */ gsl_complex ajj = gsl_matrix_complex_get (A, j, j); double max = gsl_complex_abs (ajj); size_t i_pivot = j; for (i = j + 1; i < N; i++) { gsl_complex aij = gsl_matrix_complex_get (A, i, j); double ai = gsl_complex_abs (aij); if (ai > max) { max = ai; i_pivot = i; } } if (i_pivot != j) { gsl_matrix_complex_swap_rows (A, j, i_pivot); gsl_permutation_swap (p, j, i_pivot); *signum = -(*signum); } ajj = gsl_matrix_complex_get (A, j, j); if (!(GSL_REAL(ajj) == 0.0 && GSL_IMAG(ajj) == 0.0)) { for (i = j + 1; i < N; i++) { gsl_complex aij_orig = gsl_matrix_complex_get (A, i, j); gsl_complex aij = gsl_complex_div (aij_orig, ajj); gsl_matrix_complex_set (A, i, j, aij); for (k = j + 1; k < N; k++) { gsl_complex aik = gsl_matrix_complex_get (A, i, k); gsl_complex ajk = gsl_matrix_complex_get (A, j, k); /* aik = aik - aij * ajk */ gsl_complex aijajk = gsl_complex_mul (aij, ajk); gsl_complex aik_new = gsl_complex_sub (aik, aijajk); gsl_matrix_complex_set (A, i, k, aik_new); } } } } return GSL_SUCCESS; } } int gsl_linalg_complex_LU_solve (const gsl_matrix_complex * LU, const gsl_permutation * p, const gsl_vector_complex * b, gsl_vector_complex * x) { if (LU->size1 != LU->size2) { GSL_ERROR ("LU matrix must be square", GSL_ENOTSQR); } else if (LU->size1 != p->size) { GSL_ERROR ("permutation length must match matrix size", GSL_EBADLEN); } else if (LU->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (LU->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_complex_memcpy (x, b); /* Solve for x */ gsl_linalg_complex_LU_svx (LU, p, x); return GSL_SUCCESS; } } int gsl_linalg_complex_LU_svx (const gsl_matrix_complex * LU, const gsl_permutation * p, gsl_vector_complex * x) { if (LU->size1 != LU->size2) { GSL_ERROR ("LU matrix must be square", GSL_ENOTSQR); } else if (LU->size1 != p->size) { GSL_ERROR ("permutation length must match matrix size", GSL_EBADLEN); } else if (LU->size1 != x->size) { GSL_ERROR ("matrix size must match solution/rhs size", GSL_EBADLEN); } else { /* Apply permutation to RHS */ gsl_permute_vector_complex (p, x); /* Solve for c using forward-substitution, L c = P b */ gsl_blas_ztrsv (CblasLower, CblasNoTrans, CblasUnit, LU, x); /* Perform back-substitution, U x = c */ gsl_blas_ztrsv (CblasUpper, CblasNoTrans, CblasNonUnit, LU, x); return GSL_SUCCESS; } } int gsl_linalg_complex_LU_refine (const gsl_matrix_complex * A, const gsl_matrix_complex * LU, const gsl_permutation * p, const gsl_vector_complex * b, gsl_vector_complex * x, gsl_vector_complex * residual) { if (A->size1 != A->size2) { GSL_ERROR ("matrix a must be square", GSL_ENOTSQR); } if (LU->size1 != LU->size2) { GSL_ERROR ("LU matrix must be square", GSL_ENOTSQR); } else if (A->size1 != LU->size2) { GSL_ERROR ("LU matrix must be decomposition of a", GSL_ENOTSQR); } else if (LU->size1 != p->size) { GSL_ERROR ("permutation length must match matrix size", GSL_EBADLEN); } else if (LU->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (LU->size1 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Compute residual, residual = (A * x - b) */ gsl_vector_complex_memcpy (residual, b); { gsl_complex one = GSL_COMPLEX_ONE; gsl_complex negone = GSL_COMPLEX_NEGONE; gsl_blas_zgemv (CblasNoTrans, one, A, x, negone, residual); } /* Find correction, delta = - (A^-1) * residual, and apply it */ gsl_linalg_complex_LU_svx (LU, p, residual); { gsl_complex negone= GSL_COMPLEX_NEGONE; gsl_blas_zaxpy (negone, residual, x); } return GSL_SUCCESS; } } int gsl_linalg_complex_LU_invert (const gsl_matrix_complex * LU, const gsl_permutation * p, gsl_matrix_complex * inverse) { size_t i, n = LU->size1; int status = GSL_SUCCESS; gsl_matrix_complex_set_identity (inverse); for (i = 0; i < n; i++) { gsl_vector_complex_view c = gsl_matrix_complex_column (inverse, i); int status_i = gsl_linalg_complex_LU_svx (LU, p, &(c.vector)); if (status_i) status = status_i; } return status; } gsl_complex gsl_linalg_complex_LU_det (gsl_matrix_complex * LU, int signum) { size_t i, n = LU->size1; gsl_complex det = gsl_complex_rect((double) signum, 0.0); for (i = 0; i < n; i++) { gsl_complex zi = gsl_matrix_complex_get (LU, i, i); det = gsl_complex_mul (det, zi); } return det; } double gsl_linalg_complex_LU_lndet (gsl_matrix_complex * LU) { size_t i, n = LU->size1; double lndet = 0.0; for (i = 0; i < n; i++) { gsl_complex z = gsl_matrix_complex_get (LU, i, i); lndet += log (gsl_complex_abs (z)); } return lndet; } gsl_complex gsl_linalg_complex_LU_sgndet (gsl_matrix_complex * LU, int signum) { size_t i, n = LU->size1; gsl_complex phase = gsl_complex_rect((double) signum, 0.0); for (i = 0; i < n; i++) { gsl_complex z = gsl_matrix_complex_get (LU, i, i); double r = gsl_complex_abs(z); if (r == 0) { phase = gsl_complex_rect(0.0, 0.0); break; } else { z = gsl_complex_div_real(z, r); phase = gsl_complex_mul(phase, z); } } return phase; } sources_5316/external/gsl/gsl_matrix__copy_source.c0000664000176700017670000000473611723710247021440 0ustar paulpaul/* matrix/copy_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_matrix, memcpy) (TYPE (gsl_matrix) * dest, const TYPE (gsl_matrix) * src) { const size_t src_size1 = src->size1; const size_t src_size2 = src->size2; const size_t dest_size1 = dest->size1; const size_t dest_size2 = dest->size2; if (src_size1 != dest_size1 || src_size2 != dest_size2) { GSL_ERROR ("matrix sizes are different", GSL_EBADLEN); } { const size_t src_tda = src->tda ; const size_t dest_tda = dest->tda ; size_t i, j; for (i = 0; i < src_size1 ; i++) { for (j = 0; j < MULTIPLICITY * src_size2; j++) { dest->data[MULTIPLICITY * dest_tda * i + j] = src->data[MULTIPLICITY * src_tda * i + j]; } } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, swap) (TYPE (gsl_matrix) * dest, TYPE (gsl_matrix) * src) { const size_t src_size1 = src->size1; const size_t src_size2 = src->size2; const size_t dest_size1 = dest->size1; const size_t dest_size2 = dest->size2; if (src_size1 != dest_size1 || src_size2 != dest_size2) { GSL_ERROR ("matrix sizes are different", GSL_EBADLEN); } { const size_t src_tda = src->tda ; const size_t dest_tda = dest->tda ; size_t i, j; for (i = 0; i < src_size1 ; i++) { for (j = 0; j < MULTIPLICITY * src_size2; j++) { ATOMIC tmp = src->data[MULTIPLICITY * src_tda * i + j]; src->data[MULTIPLICITY * src_tda * i + j] = dest->data[MULTIPLICITY * dest_tda * i + j]; dest->data[MULTIPLICITY * dest_tda * i + j] = tmp ; } } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_ode-initval__step.c0000664000176700017670000000412411723710247020757 0ustar paulpaul/* ode-initval/odeiv.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_odeiv.h" gsl_odeiv_step * gsl_odeiv_step_alloc(const gsl_odeiv_step_type * T, size_t dim) { gsl_odeiv_step *s = (gsl_odeiv_step *) malloc (sizeof (gsl_odeiv_step)); if (s == 0) { GSL_ERROR_NULL ("failed to allocate space for ode struct", GSL_ENOMEM); }; s->type = T; s->dimension = dim; s->state = s->type->alloc(dim); if (s->state == 0) { free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_NULL ("failed to allocate space for ode state", GSL_ENOMEM); }; return s; } const char * gsl_odeiv_step_name(const gsl_odeiv_step * s) { return s->type->name; } unsigned int gsl_odeiv_step_order(const gsl_odeiv_step * s) { return s->type->order(s->state); } int gsl_odeiv_step_apply( gsl_odeiv_step * s, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * dydt) { return s->type->apply(s->state, s->dimension, t, h, y, yerr, dydt_in, dydt_out, dydt); } int gsl_odeiv_step_reset(gsl_odeiv_step * s) { return s->type->reset(s->state, s->dimension); } void gsl_odeiv_step_free(gsl_odeiv_step * s) { s->type->free(s->state); free(s); } sources_5316/external/gsl/gsl_cblas__source_tbsv_c.h0000664000176700017670000001505111705263724021526 0ustar paulpaul/* blas/source_tbsv_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (TransA == CblasConjTrans) ? -1 : 1; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; const int nonunit = (Diag == CblasNonUnit); INDEX i, j; if (N == 0) return; /* form x := inv( A )*x */ if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX) + incX * (N - 1); for (i = N; i > 0 && i--;) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); const INDEX j_min = i + 1; const INDEX j_max = GSL_MIN(N, i + K + 1); INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE Aij_real = CONST_REAL(A, lda * i + (j - i)); const BASE Aij_imag = conj * CONST_IMAG(A, lda * i + (j - i)); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(A, lda * i + 0); const BASE a_imag = conj * CONST_IMAG(A, lda * i + 0); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { /* forward substitution */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); const INDEX j_min = (K > i ? 0 : i - K); const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE Aij_real = CONST_REAL(A, lda * i + (K + j - i)); const BASE Aij_imag = conj * CONST_IMAG(A, lda * i + (K + j - i)); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(A, lda * i + K); const BASE a_imag = conj * CONST_IMAG(A, lda * i + K); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := inv( A' )*x */ /* forward substitution */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); const INDEX j_min = (K > i ? 0 : i - K); const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE Aij_real = CONST_REAL(A, (i - j) + lda * j); const BASE Aij_imag = conj * CONST_IMAG(A, (i - j) + lda * j); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(A, 0 + lda * i); const BASE a_imag = conj * CONST_IMAG(A, 0 + lda * i); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { /* backsubstitution */ INDEX ix = OFFSET(N, incX) + incX * (N - 1); for (i = N; i > 0 && i--;) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); const INDEX j_min = i + 1; const INDEX j_max = GSL_MIN(N, i + K + 1); INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE Aij_real = CONST_REAL(A, (K + i - j) + lda * j); const BASE Aij_imag = conj * CONST_IMAG(A, (K + i - j) + lda * j); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(A, K + lda * i); const BASE a_imag = conj * CONST_IMAG(A, K + lda * i); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix -= incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_cblas__source_trmm_r.h0000664000176700017670000001234711705263724021553 0ustar paulpaul/* blas/source_trmm_r.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; INDEX n1, n2; const int nonunit = (Diag == CblasNonUnit); int side, uplo, trans; if (Order == CblasRowMajor) { n1 = M; n2 = N; side = Side; uplo = Uplo; trans = (TransA == CblasConjTrans) ? CblasTrans : TransA; } else { n1 = N; n2 = M; side = (Side == CblasLeft) ? CblasRight : CblasLeft; uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; trans = (TransA == CblasConjTrans) ? CblasTrans : TransA; } if (side == CblasLeft && uplo == CblasUpper && trans == CblasNoTrans) { /* form B := alpha * TriU(A)*B */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp = 0.0; if (nonunit) { temp = A[i * lda + i] * B[i * ldb + j]; } else { temp = B[i * ldb + j]; } for (k = i + 1; k < n1; k++) { temp += A[lda * i + k] * B[k * ldb + j]; } B[ldb * i + j] = alpha * temp; } } } else if (side == CblasLeft && uplo == CblasUpper && trans == CblasTrans) { /* form B := alpha * (TriU(A))' *B */ for (i = n1; i > 0 && i--;) { for (j = 0; j < n2; j++) { BASE temp = 0.0; for (k = 0; k < i; k++) { temp += A[lda * k + i] * B[k * ldb + j]; } if (nonunit) { temp += A[i * lda + i] * B[i * ldb + j]; } else { temp += B[i * ldb + j]; } B[ldb * i + j] = alpha * temp; } } } else if (side == CblasLeft && uplo == CblasLower && trans == CblasNoTrans) { /* form B := alpha * TriL(A)*B */ for (i = n1; i > 0 && i--;) { for (j = 0; j < n2; j++) { BASE temp = 0.0; for (k = 0; k < i; k++) { temp += A[lda * i + k] * B[k * ldb + j]; } if (nonunit) { temp += A[i * lda + i] * B[i * ldb + j]; } else { temp += B[i * ldb + j]; } B[ldb * i + j] = alpha * temp; } } } else if (side == CblasLeft && uplo == CblasLower && trans == CblasTrans) { /* form B := alpha * TriL(A)' *B */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp = 0.0; if (nonunit) { temp = A[i * lda + i] * B[i * ldb + j]; } else { temp = B[i * ldb + j]; } for (k = i + 1; k < n1; k++) { temp += A[lda * k + i] * B[k * ldb + j]; } B[ldb * i + j] = alpha * temp; } } } else if (side == CblasRight && uplo == CblasUpper && trans == CblasNoTrans) { /* form B := alpha * B * TriU(A) */ for (i = 0; i < n1; i++) { for (j = n2; j > 0 && j--;) { BASE temp = 0.0; for (k = 0; k < j; k++) { temp += A[lda * k + j] * B[i * ldb + k]; } if (nonunit) { temp += A[j * lda + j] * B[i * ldb + j]; } else { temp += B[i * ldb + j]; } B[ldb * i + j] = alpha * temp; } } } else if (side == CblasRight && uplo == CblasUpper && trans == CblasTrans) { /* form B := alpha * B * (TriU(A))' */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp = 0.0; if (nonunit) { temp = A[j * lda + j] * B[i * ldb + j]; } else { temp = B[i * ldb + j]; } for (k = j + 1; k < n2; k++) { temp += A[lda * j + k] * B[i * ldb + k]; } B[ldb * i + j] = alpha * temp; } } } else if (side == CblasRight && uplo == CblasLower && trans == CblasNoTrans) { /* form B := alpha *B * TriL(A) */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp = 0.0; if (nonunit) { temp = A[j * lda + j] * B[i * ldb + j]; } else { temp = B[i * ldb + j]; } for (k = j + 1; k < n2; k++) { temp += A[lda * k + j] * B[i * ldb + k]; } B[ldb * i + j] = alpha * temp; } } } else if (side == CblasRight && uplo == CblasLower && trans == CblasTrans) { /* form B := alpha * B * TriL(A)' */ for (i = 0; i < n1; i++) { for (j = n2; j > 0 && j--;) { BASE temp = 0.0; for (k = 0; k < j; k++) { temp += A[lda * j + k] * B[i * ldb + k]; } if (nonunit) { temp += A[j * lda + j] * B[i * ldb + j]; } else { temp += B[i * ldb + j]; } B[ldb * i + j] = alpha * temp; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_multifit__lmutil.c0000664000176700017670000000530311723710247020734 0ustar paulpaulstatic void compute_diag (const gsl_matrix * J, gsl_vector * diag); static void update_diag (const gsl_matrix * J, gsl_vector * diag); static double compute_delta (gsl_vector * diag, gsl_vector * x); static double scaled_enorm (const gsl_vector * d, const gsl_vector * f); static double enorm (const gsl_vector * f); static double enorm (const gsl_vector * f) { return gsl_blas_dnrm2 (f); } static double scaled_enorm (const gsl_vector * d, const gsl_vector * f) { double e2 = 0; size_t i, n = f->size; for (i = 0; i < n; i++) { double fi = gsl_vector_get (f, i); double di = gsl_vector_get (d, i); double u = di * fi; e2 += u * u; } return sqrt (e2); } static double compute_delta (gsl_vector * diag, gsl_vector * x) { double Dx = scaled_enorm (diag, x); double factor = 100; /* generally recommended value from MINPACK */ return (Dx > 0) ? factor * Dx : factor; } static double compute_actual_reduction (double fnorm, double fnorm1) { double actred; if (0.1 * fnorm1 < fnorm) { double u = fnorm1 / fnorm; actred = 1 - u * u; } else { actred = -1; } return actred; } static void compute_diag (const gsl_matrix * J, gsl_vector * diag) { size_t i, j, n = J->size1, p = J->size2; for (j = 0; j < p; j++) { double sum = 0; for (i = 0; i < n; i++) { double Jij = gsl_matrix_get (J, i, j); sum += Jij * Jij; } if (sum == 0) sum = 1.0; gsl_vector_set (diag, j, sqrt (sum)); } } static void update_diag (const gsl_matrix * J, gsl_vector * diag) { size_t i, j, n = diag->size; for (j = 0; j < n; j++) { double cnorm, diagj, sum = 0; for (i = 0; i < n; i++) { double Jij = gsl_matrix_get (J, i, j); sum += Jij * Jij; } if (sum == 0) sum = 1.0; cnorm = sqrt (sum); diagj = gsl_vector_get (diag, j); if (cnorm > diagj) gsl_vector_set (diag, j, cnorm); } } static void compute_rptdx (const gsl_matrix * r, const gsl_permutation * p, const gsl_vector * dx, gsl_vector * rptdx) { size_t i, j, N = dx->size; for (i = 0; i < N; i++) { double sum = 0; for (j = i; j < N; j++) { size_t pj = gsl_permutation_get (p, j); sum += gsl_matrix_get (r, i, j) * gsl_vector_get (dx, pj); } gsl_vector_set (rptdx, i, sum); } } static void compute_trial_step (gsl_vector * x, gsl_vector * dx, gsl_vector * x_trial) { size_t i, N = x->size; for (i = 0; i < N; i++) { double pi = gsl_vector_get (dx, i); double xi = gsl_vector_get (x, i); gsl_vector_set (x_trial, i, xi + pi); } } sources_5316/external/gsl/gsl_specfunc__hyperg_0F1.c0000664000176700017670000001201211723710247021276 0ustar paulpaul/* specfunc/hyperg_0F1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_bessel.h" #include "gsl_sf_hyperg.h" #include "gsl_specfunc__error.h" #define locEPS (1000.0*GSL_DBL_EPSILON) /* Evaluate bessel_I(nu, x), allowing nu < 0. * This is fine here because we do not not allow * nu to be a negative integer. * x > 0. */ static int hyperg_0F1_bessel_I(const double nu, const double x, gsl_sf_result * result) { if(x > GSL_LOG_DBL_MAX) { OVERFLOW_ERROR(result); } if(nu < 0.0) { const double anu = -nu; const double s = 2.0/M_PI * sin(anu*M_PI); const double ex = exp(x); gsl_sf_result I; gsl_sf_result K; int stat_I = gsl_sf_bessel_Inu_scaled_e(anu, x, &I); int stat_K = gsl_sf_bessel_Knu_scaled_e(anu, x, &K); result->val = ex * I.val + s * (K.val / ex); result->err = ex * I.err + fabs(s * K.err/ex); result->err += fabs(s * (K.val/ex)) * GSL_DBL_EPSILON * anu * M_PI; return GSL_ERROR_SELECT_2(stat_K, stat_I); } else { const double ex = exp(x); gsl_sf_result I; int stat_I = gsl_sf_bessel_Inu_scaled_e(nu, x, &I); result->val = ex * I.val; result->err = ex * I.err + GSL_DBL_EPSILON * fabs(result->val); return stat_I; } } /* Evaluate bessel_J(nu, x), allowing nu < 0. * This is fine here because we do not not allow * nu to be a negative integer. * x > 0. */ static int hyperg_0F1_bessel_J(const double nu, const double x, gsl_sf_result * result) { if(nu < 0.0) { const double anu = -nu; const double s = sin(anu*M_PI); const double c = cos(anu*M_PI); gsl_sf_result J; gsl_sf_result Y; int stat_J = gsl_sf_bessel_Jnu_e(anu, x, &J); int stat_Y = gsl_sf_bessel_Ynu_e(anu, x, &Y); result->val = c * J.val - s * Y.val; result->err = fabs(c * J.err) + fabs(s * Y.err); result->err += fabs(anu * M_PI) * GSL_DBL_EPSILON * fabs(J.val + Y.val); return GSL_ERROR_SELECT_2(stat_Y, stat_J); } else { return gsl_sf_bessel_Jnu_e(nu, x, result); } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_hyperg_0F1_e(double c, double x, gsl_sf_result * result) { const double rintc = floor(c + 0.5); const int c_neg_integer = (c < 0.0 && fabs(c - rintc) < locEPS); /* CHECK_POINTER(result) */ if(c == 0.0 || c_neg_integer) { DOMAIN_ERROR(result); } else if(x < 0.0) { gsl_sf_result Jcm1; gsl_sf_result lg_c; double sgn; int stat_g = gsl_sf_lngamma_sgn_e(c, &lg_c, &sgn); int stat_J = hyperg_0F1_bessel_J(c-1.0, 2.0*sqrt(-x), &Jcm1); if(stat_g != GSL_SUCCESS) { result->val = 0.0; result->err = 0.0; return stat_g; } else if(Jcm1.val == 0.0) { result->val = 0.0; result->err = 0.0; return stat_J; } else { const double tl = log(-x)*0.5*(1.0-c); double ln_pre_val = lg_c.val + tl; double ln_pre_err = lg_c.err + 2.0 * GSL_DBL_EPSILON * fabs(tl); return gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, sgn*Jcm1.val, Jcm1.err, result); } } else if(x == 0.0) { result->val = 1.0; result->err = 1.0; return GSL_SUCCESS; } else { gsl_sf_result Icm1; gsl_sf_result lg_c; double sgn; int stat_g = gsl_sf_lngamma_sgn_e(c, &lg_c, &sgn); int stat_I = hyperg_0F1_bessel_I(c-1.0, 2.0*sqrt(x), &Icm1); if(stat_g != GSL_SUCCESS) { result->val = 0.0; result->err = 0.0; return stat_g; } else if(Icm1.val == 0.0) { result->val = 0.0; result->err = 0.0; return stat_I; } else { const double tl = log(x)*0.5*(1.0-c); const double ln_pre_val = lg_c.val + tl; const double ln_pre_err = lg_c.err + 2.0 * GSL_DBL_EPSILON * fabs(tl); return gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, sgn*Icm1.val, Icm1.err, result); } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_hyperg_0F1(const double c, const double x) { EVAL_RESULT(gsl_sf_hyperg_0F1_e(c, x, &result)); } sources_5316/external/gsl/gsl_cblas__source_nrm2_r.h0000664000176700017670000000243711705263724021451 0ustar paulpaul/* blas/source_nrm2_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { BASE scale = 0.0; BASE ssq = 1.0; INDEX i; INDEX ix = 0; if (N <= 0 || incX <= 0) { return 0; } else if (N == 1) { return fabs(X[0]); } for (i = 0; i < N; i++) { const BASE x = X[ix]; if (x != 0.0) { const BASE ax = fabs(x); if (scale < ax) { ssq = 1.0 + ssq * (scale / ax) * (scale / ax); scale = ax; } else { ssq += (ax / scale) * (ax / scale); } } ix += incX; } return scale * sqrt(ssq); } sources_5316/external/gsl/gsl_vector_complex.h0000664000176700017670000000137311705263724020416 0ustar paulpaul#ifndef __GSL_VECTOR_COMPLEX_H__ #define __GSL_VECTOR_COMPLEX_H__ #define GSL_VECTOR_REAL(z, i) ((z)->data[2*(i)*(z)->stride]) #define GSL_VECTOR_IMAG(z, i) ((z)->data[2*(i)*(z)->stride + 1]) #if GSL_RANGE_CHECK #define GSL_VECTOR_COMPLEX(zv, i) (((i) >= (zv)->size ? (gsl_error ("index out of range", __FILE__, __LINE__, GSL_EINVAL), 0):0 , *GSL_COMPLEX_AT((zv),(i)))) #else #define GSL_VECTOR_COMPLEX(zv, i) (GSL_COMPLEX_AT((zv),(i))) #endif #define GSL_COMPLEX_AT(zv,i) ((gsl_complex*)&((zv)->data[2*(i)*(zv)->stride])) #define GSL_COMPLEX_FLOAT_AT(zv,i) ((gsl_complex_float*)&((zv)->data[2*(i)*(zv)->stride])) #define GSL_COMPLEX_LONG_DOUBLE_AT(zv,i) ((gsl_complex_long_double*)&((zv)->data[2*(i)*(zv)->stride])) #endif /* __GSL_VECTOR_COMPLEX_H__ */ sources_5316/external/gsl/gsl_statistics__mean.c0000664000176700017670000000276411723710247020713 0ustar paulpaul#include "gsl__config.h" #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__mean_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_cblas__idamax.c0000664000176700017670000000033711723710247020122 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" CBLAS_INDEX cblas_idamax (const int N, const double *X, const int incX) { #define BASE double #include "gsl_cblas__source_iamax_r.h" #undef BASE } sources_5316/external/gsl/gsl_matrix__minmax.c0000664000176700017670000000300411723710247020362 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_matrix.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__minmax_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_cblas__ztrsm.c0000664000176700017670000000076311723710247020041 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" #include "gsl_cblas__hypot.c" void cblas_ztrsm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const void *alpha, const void *A, const int lda, void *B, const int ldb) { #define BASE double #include "gsl_cblas__source_trsm_c.h" #undef BASE } sources_5316/external/gsl/gsl_matrix__swap_source.c0000664000176700017670000001176611723710247021441 0ustar paulpaul/* matrix/swap_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_matrix, swap_rows) (TYPE (gsl_matrix) * m, const size_t i, const size_t j) { const size_t size1 = m->size1; const size_t size2 = m->size2; if (i >= size1) { GSL_ERROR ("first row index is out of range", GSL_EINVAL); } if (j >= size1) { GSL_ERROR ("second row index is out of range", GSL_EINVAL); } if (i != j) { ATOMIC *row1 = m->data + MULTIPLICITY * i * m->tda; ATOMIC *row2 = m->data + MULTIPLICITY * j * m->tda; size_t k; for (k = 0; k < MULTIPLICITY * size2; k++) { ATOMIC tmp = row1[k] ; row1[k] = row2[k] ; row2[k] = tmp ; } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, swap_columns) (TYPE (gsl_matrix) * m, const size_t i, const size_t j) { const size_t size1 = m->size1; const size_t size2 = m->size2; if (i >= size2) { GSL_ERROR ("first column index is out of range", GSL_EINVAL); } if (j >= size2) { GSL_ERROR ("second column index is out of range", GSL_EINVAL); } if (i != j) { ATOMIC *col1 = m->data + MULTIPLICITY * i; ATOMIC *col2 = m->data + MULTIPLICITY * j; size_t p; for (p = 0; p < size1; p++) { size_t k; size_t n = p * MULTIPLICITY * m->tda; for (k = 0; k < MULTIPLICITY; k++) { ATOMIC tmp = col1[n+k] ; col1[n+k] = col2[n+k] ; col2[n+k] = tmp ; } } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, swap_rowcol) (TYPE (gsl_matrix) * m, const size_t i, const size_t j) { const size_t size1 = m->size1; const size_t size2 = m->size2; if (size1 != size2) { GSL_ERROR ("matrix must be square to swap row and column", GSL_ENOTSQR); } if (i >= size1) { GSL_ERROR ("row index is out of range", GSL_EINVAL); } if (j >= size2) { GSL_ERROR ("column index is out of range", GSL_EINVAL); } { ATOMIC *row = m->data + MULTIPLICITY * i * m->tda; ATOMIC *col = m->data + MULTIPLICITY * j; size_t p; for (p = 0; p < size1; p++) { size_t k; size_t r = p * MULTIPLICITY; size_t c = p * MULTIPLICITY * m->tda; for (k = 0; k < MULTIPLICITY; k++) { ATOMIC tmp = col[c+k] ; col[c+k] = row[r+k] ; row[r+k] = tmp ; } } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, transpose) (TYPE (gsl_matrix) * m) { const size_t size1 = m->size1; const size_t size2 = m->size2; size_t i, j, k; if (size1 != size2) { GSL_ERROR ("matrix must be square to take transpose", GSL_ENOTSQR); } for (i = 0; i < size1; i++) { for (j = i + 1 ; j < size2 ; j++) { for (k = 0; k < MULTIPLICITY; k++) { size_t e1 = (i * m->tda + j) * MULTIPLICITY + k ; size_t e2 = (j * m->tda + i) * MULTIPLICITY + k ; { ATOMIC tmp = m->data[e1] ; m->data[e1] = m->data[e2] ; m->data[e2] = tmp ; } } } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, transpose_memcpy) (TYPE (gsl_matrix) * dest, const TYPE (gsl_matrix) * src) { const size_t src_size1 = src->size1; const size_t src_size2 = src->size2; const size_t dest_size1 = dest->size1; const size_t dest_size2 = dest->size2; size_t i, j, k; if (dest_size2 != src_size1 || dest_size1 != src_size2) { GSL_ERROR ("dimensions of dest matrix must be transpose of src matrix", GSL_EBADLEN); } for (i = 0; i < dest_size1; i++) { for (j = 0 ; j < dest_size2; j++) { for (k = 0; k < MULTIPLICITY; k++) { size_t e1 = (i * dest->tda + j) * MULTIPLICITY + k ; size_t e2 = (j * src->tda + i) * MULTIPLICITY + k ; dest->data[e1] = src->data[e2] ; } } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__source_rot.h0000664000176700017670000000204511705263724021051 0ustar paulpaul/* blas/source_rot.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE x = X[ix]; const BASE y = Y[iy]; X[ix] = c * x + s * y; Y[iy] = -s * x + c * y; ix += incX; iy += incY; } } sources_5316/external/gsl/gsl_cblas__ztrmv.c0000664000176700017670000000061411723710247020037 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ztrmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *A, const int lda, void *X, const int incX) { #define BASE double #include "gsl_cblas__source_trmv_c.h" #undef BASE } sources_5316/external/gsl/gsl_ieee-utils__fp-gnux86.c0000664000176700017670000000544611723710247021410 0ustar paulpaul/* ieee-utils/fp-gnux86.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl_errno.h" #include "gsl_ieee_utils.h" /* Handle libc5, where _FPU_SETCW is not available, suggested by OKUJI Yoshinori and Evgeny Stambulchik */ #ifndef _FPU_SETCW #include #define _FPU_SETCW(cw) __setfpucw(cw) #endif int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { unsigned short mode = 0 ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: mode |= _FPU_SINGLE ; break ; case GSL_IEEE_DOUBLE_PRECISION: mode |= _FPU_DOUBLE ; break ; case GSL_IEEE_EXTENDED_PRECISION: mode |= _FPU_EXTENDED ; break ; default: mode |= _FPU_EXTENDED ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: mode |= _FPU_RC_NEAREST ; break ; case GSL_IEEE_ROUND_DOWN: mode |= _FPU_RC_DOWN ; break ; case GSL_IEEE_ROUND_UP: mode |= _FPU_RC_UP ; break ; case GSL_IEEE_ROUND_TO_ZERO: mode |= _FPU_RC_ZERO ; break ; default: mode |= _FPU_RC_NEAREST ; } if (exception_mask & GSL_IEEE_MASK_INVALID) mode |= _FPU_MASK_IM ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) mode |= _FPU_MASK_DM ; if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode |= _FPU_MASK_ZM ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode |= _FPU_MASK_OM ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode |= _FPU_MASK_UM ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode &= ~ _FPU_MASK_PM ; } else { mode |= _FPU_MASK_PM ; } _FPU_SETCW(mode) ; #if HAVE_FPU_X86_SSE #define _FPU_SETMXCSR(cw_sse) asm volatile ("ldmxcsr %0" : : "m" (*&cw_sse)) { unsigned int mode_sse = 0; mode_sse |= (mode & 0x3f)<<7; /* exception masks */ mode_sse |= (mode & 0xc00)<<3; /* rounding control */ _FPU_SETMXCSR(mode_sse); } #endif return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_cdf__chisq.c0000664000176700017670000000205611723710247017436 0ustar paulpaul/* cdf/cdf_chisq.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include "gsl__config.h" #include "gsl_cdf.h" #include "gsl_sf_gamma.h" double gsl_cdf_chisq_P (const double x, const double nu) { return gsl_cdf_gamma_P (x, nu / 2, 2.0); } double gsl_cdf_chisq_Q (const double x, const double nu) { return gsl_cdf_gamma_Q (x, nu / 2, 2.0); } sources_5316/external/gsl/gsl_histogram__maxval.c0000664000176700017670000000457211723710247021065 0ustar paulpaul/* gsl_histogram_maxval.c * Copyright (C) 2000 Simone Piccardi * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File gsl_histogram_maxval.c: * Routine to find maximum and minumum content of a hisogram. * Need GSL library and header. * Contains the routines: * gsl_histogram_max_val find max content values * gsl_histogram_min_val find min content values * gsl_histogram_bin_max find coordinates of max contents bin * gsl_histogram_bin_min find coordinates of min contents bin * * Author: S. Piccardi * Jan. 2000 * ***************************************************************/ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_histogram.h" double gsl_histogram_max_val (const gsl_histogram * h) { const size_t n = h->n; size_t i; double max = h->bin[0]; for (i = 0; i < n; i++) { if (h->bin[i] > max) { max = h->bin[i]; } } return max; } size_t gsl_histogram_max_bin (const gsl_histogram * h) { size_t i; size_t imax = 0; double max = h->bin[0]; for (i = 0; i < h->n; i++) { if (h->bin[i] > max) { max = h->bin[i]; imax = i; } } return imax; } double gsl_histogram_min_val (const gsl_histogram * h) { size_t i; double min = h->bin[0]; for (i = 0; i < h->n; i++) { if (h->bin[i] < min) { min = h->bin[i]; } } return min; } size_t gsl_histogram_min_bin (const gsl_histogram * h) { size_t i; size_t imin = 0; double min = h->bin[0]; for (i = 0; i < h->n; i++) { if (h->bin[i] < min) { min = h->bin[i]; imin = i; } } return imin; } sources_5316/external/gsl/gsl_wavelet__haar.c0000664000176700017670000000372111723710247020155 0ustar paulpaul/* wavelet/haar.c * * Copyright (C) 2004 Ivo Alxneit * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_math.h" #include "gsl_wavelet.h" static const double ch_2[2] = { M_SQRT1_2, M_SQRT1_2 }; static const double cg_2[2] = { M_SQRT1_2, -(M_SQRT1_2) }; static int haar_init (const double **h1, const double **g1, const double **h2, const double **g2, size_t * nc, size_t * offset, const size_t member) { if (member != 2) { return GSL_FAILURE; } *h1 = ch_2; *g1 = cg_2; *h2 = ch_2; *g2 = cg_2; *nc = 2; *offset = 0; return GSL_SUCCESS; } static int haar_centered_init (const double **h1, const double **g1, const double **h2, const double **g2, size_t * nc, size_t * offset, const size_t member) { if (member != 2) { return GSL_FAILURE; } *h1 = ch_2; *g1 = cg_2; *h2 = ch_2; *g2 = cg_2; *nc = 2; *offset = 1; return GSL_SUCCESS; } static const gsl_wavelet_type haar_type = { "haar", &haar_init }; static const gsl_wavelet_type haar_centered_type = { "haar-centered", &haar_centered_init }; const gsl_wavelet_type *gsl_wavelet_haar = &haar_type; const gsl_wavelet_type *gsl_wavelet_haar_centered = &haar_centered_type; sources_5316/external/gsl/gsl_randist__bigauss.c0000664000176700017670000000417011723710247020673 0ustar paulpaul/* randist/bigauss.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The Bivariate Gaussian probability distribution is p(x,y) dxdy = (1/(2 pi sigma_x sigma_y sqrt(c))) exp(-((x/sigma_x)^2 + (y/sigma_y)^2 - 2 r (x/sigma_x)(y/sigma_y))/2c) dxdy where c = 1-r^2 */ void gsl_ran_bivariate_gaussian (const gsl_rng * r, double sigma_x, double sigma_y, double rho, double *x, double *y) { double u, v, r2, scale; do { /* choose x,y in uniform square (-1,-1) to (+1,+1) */ u = -1 + 2 * gsl_rng_uniform (r); v = -1 + 2 * gsl_rng_uniform (r); /* see if it is in the unit circle */ r2 = u * u + v * v; } while (r2 > 1.0 || r2 == 0); scale = sqrt (-2.0 * log (r2) / r2); *x = sigma_x * u * scale; *y = sigma_y * (rho * u + sqrt(1 - rho*rho) * v) * scale; } double gsl_ran_bivariate_gaussian_pdf (const double x, const double y, const double sigma_x, const double sigma_y, const double rho) { double u = x / sigma_x ; double v = y / sigma_y ; double c = 1 - rho*rho ; double p = (1 / (2 * M_PI * sigma_x * sigma_y * sqrt(c))) * exp (-(u * u - 2 * rho * u * v + v * v) / (2 * c)); return p; } sources_5316/external/gsl/gsl_permute_ushort.h0000664000176700017670000000265611705263724020457 0ustar paulpaul/* permutation/gsl_permute_ushort.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_USHORT_H__ #define __GSL_PERMUTE_USHORT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_ushort (const size_t * p, unsigned short * data, const size_t stride, const size_t n); int gsl_permute_ushort_inverse (const size_t * p, unsigned short * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_USHORT_H__ */ sources_5316/external/gsl/gsl_sort_vector_uint.h0000664000176700017670000000342111705263724020771 0ustar paulpaul/* sort/gsl_sort_vector_uint.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_UINT_H__ #define __GSL_SORT_VECTOR_UINT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_uint.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_uint (gsl_vector_uint * v); int gsl_sort_vector_uint_index (gsl_permutation * p, const gsl_vector_uint * v); int gsl_sort_vector_uint_smallest (unsigned int * dest, const size_t k, const gsl_vector_uint * v); int gsl_sort_vector_uint_largest (unsigned int * dest, const size_t k, const gsl_vector_uint * v); int gsl_sort_vector_uint_smallest_index (size_t * p, const size_t k, const gsl_vector_uint * v); int gsl_sort_vector_uint_largest_index (size_t * p, const size_t k, const gsl_vector_uint * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_UINT_H__ */ sources_5316/external/gsl/gsl_matrix__matrix.c0000664000176700017670000000366211723710247020407 0ustar paulpaul#include "gsl__config.h" #include "gsl_errno.h" #include "gsl_matrix.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__matrix_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_sf_hyperg.h0000664000176700017670000001064111705263724017351 0ustar paulpaul/* specfunc/gsl_sf_hyperg.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_HYPERG_H__ #define __GSL_SF_HYPERG_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Hypergeometric function related to Bessel functions * 0F1[c,x] = * Gamma[c] x^(1/2(1-c)) I_{c-1}(2 Sqrt[x]) * Gamma[c] (-x)^(1/2(1-c)) J_{c-1}(2 Sqrt[-x]) * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_hyperg_0F1_e(double c, double x, gsl_sf_result * result); double gsl_sf_hyperg_0F1(const double c, const double x); /* Confluent hypergeometric function for integer parameters. * 1F1[m,n,x] = M(m,n,x) * * exceptions: */ int gsl_sf_hyperg_1F1_int_e(const int m, const int n, const double x, gsl_sf_result * result); double gsl_sf_hyperg_1F1_int(const int m, const int n, double x); /* Confluent hypergeometric function. * 1F1[a,b,x] = M(a,b,x) * * exceptions: */ int gsl_sf_hyperg_1F1_e(const double a, const double b, const double x, gsl_sf_result * result); double gsl_sf_hyperg_1F1(double a, double b, double x); /* Confluent hypergeometric function for integer parameters. * U(m,n,x) * * exceptions: */ int gsl_sf_hyperg_U_int_e(const int m, const int n, const double x, gsl_sf_result * result); double gsl_sf_hyperg_U_int(const int m, const int n, const double x); /* Confluent hypergeometric function for integer parameters. * U(m,n,x) * * exceptions: */ int gsl_sf_hyperg_U_int_e10_e(const int m, const int n, const double x, gsl_sf_result_e10 * result); /* Confluent hypergeometric function. * U(a,b,x) * * exceptions: */ int gsl_sf_hyperg_U_e(const double a, const double b, const double x, gsl_sf_result * result); double gsl_sf_hyperg_U(const double a, const double b, const double x); /* Confluent hypergeometric function. * U(a,b,x) * * exceptions: */ int gsl_sf_hyperg_U_e10_e(const double a, const double b, const double x, gsl_sf_result_e10 * result); /* Gauss hypergeometric function 2F1[a,b,c,x] * |x| < 1 * * exceptions: */ int gsl_sf_hyperg_2F1_e(double a, double b, const double c, const double x, gsl_sf_result * result); double gsl_sf_hyperg_2F1(double a, double b, double c, double x); /* Gauss hypergeometric function * 2F1[aR + I aI, aR - I aI, c, x] * |x| < 1 * * exceptions: */ int gsl_sf_hyperg_2F1_conj_e(const double aR, const double aI, const double c, const double x, gsl_sf_result * result); double gsl_sf_hyperg_2F1_conj(double aR, double aI, double c, double x); /* Renormalized Gauss hypergeometric function * 2F1[a,b,c,x] / Gamma[c] * |x| < 1 * * exceptions: */ int gsl_sf_hyperg_2F1_renorm_e(const double a, const double b, const double c, const double x, gsl_sf_result * result); double gsl_sf_hyperg_2F1_renorm(double a, double b, double c, double x); /* Renormalized Gauss hypergeometric function * 2F1[aR + I aI, aR - I aI, c, x] / Gamma[c] * |x| < 1 * * exceptions: */ int gsl_sf_hyperg_2F1_conj_renorm_e(const double aR, const double aI, const double c, const double x, gsl_sf_result * result); double gsl_sf_hyperg_2F1_conj_renorm(double aR, double aI, double c, double x); /* Mysterious hypergeometric function. The series representation * is a divergent hypergeometric series. However, for x < 0 we * have 2F0(a,b,x) = (-1/x)^a U(a,1+a-b,-1/x) * * exceptions: GSL_EDOM */ int gsl_sf_hyperg_2F0_e(const double a, const double b, const double x, gsl_sf_result * result); double gsl_sf_hyperg_2F0(const double a, const double b, const double x); __END_DECLS #endif /* __GSL_SF_HYPERG_H__ */ sources_5316/external/gsl/gsl_ieee-utils__fp-hpux.c0000664000176700017670000000544711723710247021236 0ustar paulpaul/* ieee-utils/fp-hpux.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { fp_except mode = 0 ; fp_rnd rnd = 0 ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("HPUX PA-RISC only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("HPUX PA-RISC only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("HPUX PA-RISC only supports default precision rounding", GSL_EUNSUP) ; break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: rnd = FP_RN ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_DOWN: rnd = FP_RM ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_UP: rnd = FP_RP ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_TO_ZERO: rnd = FP_RZ ; fpsetround (rnd) ; break ; default: rnd = FP_RN ; fpsetround (rnd) ; } /* Turn on all the exceptions apart from 'inexact' */ mode = FP_X_INV | FP_X_DZ | FP_X_OFL | FP_X_UFL ; if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ FP_X_INV ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("HP-UX does not support the denormalized operand exception. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ FP_X_DZ ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ FP_X_OFL ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ FP_X_UFL ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode |= FP_X_IMP ; } else { mode &= ~ FP_X_IMP ; } fpsetmask (mode) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_cdf__exponential.c0000664000176700017670000000247611723710247020663 0ustar paulpaul/* cdf/exponential.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" /* The exponential distribution has the form p(x) dx = exp(-x/mu) dx/mu for x = 0 ... +infty */ double gsl_cdf_exponential_P (const double x, const double mu) { if (x < 0) { return 0; } else { double P = -expm1 (-x / mu); return P; } } double gsl_cdf_exponential_Q (const double x, const double mu) { if (x < 0) { return 1; } else { double Q = exp (-x / mu); return Q; } } sources_5316/external/gsl/gsl_integration__set_initial.c0000664000176700017670000000054611723710247022424 0ustar paulpaulstatic inline void set_initial_result (gsl_integration_workspace * workspace, double result, double error); static inline void set_initial_result (gsl_integration_workspace * workspace, double result, double error) { workspace->size = 1; workspace->rlist[0] = result; workspace->elist[0] = error; } sources_5316/external/gsl/gsl_cdf__nbinomial.c0000664000176700017670000000342211723710247020275 0ustar paulpaul/* cdf/negbinom.c * * Copyright (C) 2004 Jason H. Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_cdf.h" #include "gsl_cdf__error.h" /* * Pr(X <= k) for a negative binomial random variable X, i.e., * the probability of k or fewer failuers before success n. */ double gsl_cdf_negative_binomial_P (const unsigned int k, const double p, const double n) { double P; double a; double b; if (p > 1.0 || p < 0.0) { CDF_ERROR ("p < 0 or p > 1", GSL_EDOM); } if (n < 0) { CDF_ERROR ("n < 0", GSL_EDOM); } a = (double) n; b = (double) k + 1.0; P = gsl_cdf_beta_P (p, a, b); return P; } /* * Pr ( X > k ). */ double gsl_cdf_negative_binomial_Q (const unsigned int k, const double p, const double n) { double Q; double a; double b; if (p > 1.0 || p < 0.0) { CDF_ERROR ("p < 0 or p > 1", GSL_EDOM); } if (n < 0) { CDF_ERROR ("n < 0", GSL_EDOM); } a = (double) n; b = (double) k + 1.0; Q = gsl_cdf_beta_Q (p, a, b); return Q; } sources_5316/external/gsl/gsl_histogram__pdf.c0000664000176700017670000000667311723710247020352 0ustar paulpaul/* histogram/pdf.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram.h" #include "gsl_histogram__find.c" double gsl_histogram_pdf_sample (const gsl_histogram_pdf * p, double r) { size_t i; int status; /* Wrap the exclusive top of the bin down to the inclusive bottom of the bin. Since this is a single point it should not affect the distribution. */ if (r == 1.0) { r = 0.0; } status = find (p->n, p->sum, r, &i); if (status) { GSL_ERROR_VAL ("cannot find r in cumulative pdf", GSL_EDOM, 0); } else { double delta = (r - p->sum[i]) / (p->sum[i + 1] - p->sum[i]); double x = p->range[i] + delta * (p->range[i + 1] - p->range[i]); return x; } } gsl_histogram_pdf * gsl_histogram_pdf_alloc (const size_t n) { gsl_histogram_pdf *p; if (n == 0) { GSL_ERROR_VAL ("histogram pdf length n must be positive integer", GSL_EDOM, 0); } p = (gsl_histogram_pdf *) malloc (sizeof (gsl_histogram_pdf)); if (p == 0) { GSL_ERROR_VAL ("failed to allocate space for histogram pdf struct", GSL_ENOMEM, 0); } p->range = (double *) malloc ((n + 1) * sizeof (double)); if (p->range == 0) { free (p); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram pdf ranges", GSL_ENOMEM, 0); } p->sum = (double *) malloc ((n + 1) * sizeof (double)); if (p->sum == 0) { free (p->range); free (p); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram pdf sums", GSL_ENOMEM, 0); } p->n = n; return p; } int gsl_histogram_pdf_init (gsl_histogram_pdf * p, const gsl_histogram * h) { size_t i; size_t n = p->n; if (n != h->n) { GSL_ERROR ("histogram length must match pdf length", GSL_EINVAL); } for (i = 0; i < n; i++) { if (h->bin[i] < 0) { GSL_ERROR ("histogram bins must be non-negative to compute" "a probability distribution", GSL_EDOM); } } for (i = 0; i < n + 1; i++) { p->range[i] = h->range[i]; } { double mean = 0, sum = 0; for (i = 0; i < n; i++) { mean += (h->bin[i] - mean) / ((double) (i + 1)); } p->sum[0] = 0; for (i = 0; i < n; i++) { sum += (h->bin[i] / mean) / n; p->sum[i + 1] = sum; } } return GSL_SUCCESS; } void gsl_histogram_pdf_free (gsl_histogram_pdf * p) { free (p->range); free (p->sum); free (p); } sources_5316/external/gsl/gsl_eigen__hermv.c0000664000176700017670000001565411723710247020013 0ustar paulpaul/* eigen/hermv.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_complex_math.h" #include "gsl_linalg.h" #include "gsl_eigen.h" /* Compute eigenvalues/eigenvectors of complex hermitian matrix using reduction to real symmetric tridiagonal form, followed by QR iteration with implicit shifts. See Golub & Van Loan, "Matrix Computations" (3rd ed), Section 8.3 */ #include "gsl_eigen__qrstep.c" gsl_eigen_hermv_workspace * gsl_eigen_hermv_alloc (const size_t n) { gsl_eigen_hermv_workspace * w ; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = (gsl_eigen_hermv_workspace *) malloc (sizeof(gsl_eigen_hermv_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->d = (double *) malloc (n * sizeof (double)); if (w->d == 0) { free (w); GSL_ERROR_NULL ("failed to allocate space for diagonal", GSL_ENOMEM); } w->sd = (double *) malloc (n * sizeof (double)); if (w->sd == 0) { free (w->d); free (w); GSL_ERROR_NULL ("failed to allocate space for subdiagonal", GSL_ENOMEM); } w->tau = (double *) malloc (2 * n * sizeof (double)); if (w->tau == 0) { free (w->sd); free (w->d); free (w); GSL_ERROR_NULL ("failed to allocate space for tau", GSL_ENOMEM); } w->gc = (double *) malloc (n * sizeof (double)); if (w->gc == 0) { free (w->tau); free (w->sd); free (w->d); free (w); GSL_ERROR_NULL ("failed to allocate space for cosines", GSL_ENOMEM); } w->gs = (double *) malloc (n * sizeof (double)); if (w->gs == 0) { free (w->gc); free (w->tau); free (w->sd); free (w->d); free (w); GSL_ERROR_NULL ("failed to allocate space for sines", GSL_ENOMEM); } w->size = n; return w; } void gsl_eigen_hermv_free (gsl_eigen_hermv_workspace * w) { free (w->gs); free (w->gc); free (w->tau); free (w->sd); free (w->d); free (w); } int gsl_eigen_hermv (gsl_matrix_complex * A, gsl_vector * eval, gsl_matrix_complex * evec, gsl_eigen_hermv_workspace * w) { if (A->size1 != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if (eval->size != A->size1) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (evec->size1 != A->size1 || evec->size2 != A->size1) { GSL_ERROR ("eigenvector matrix must match matrix size", GSL_EBADLEN); } else { const size_t N = A->size1; double *const d = w->d; double *const sd = w->sd; size_t a, b; /* handle special case */ if (N == 1) { gsl_complex A00 = gsl_matrix_complex_get (A, 0, 0); gsl_vector_set (eval, 0, GSL_REAL(A00)); gsl_matrix_complex_set (evec, 0, 0, GSL_COMPLEX_ONE); return GSL_SUCCESS; } /* Transform the matrix into a symmetric tridiagonal form */ { gsl_vector_view d_vec = gsl_vector_view_array (d, N); gsl_vector_view sd_vec = gsl_vector_view_array (sd, N - 1); gsl_vector_complex_view tau_vec = gsl_vector_complex_view_array (w->tau, N-1); gsl_linalg_hermtd_decomp (A, &tau_vec.vector); gsl_linalg_hermtd_unpack (A, &tau_vec.vector, evec, &d_vec.vector, &sd_vec.vector); } /* Make an initial pass through the tridiagonal decomposition to remove off-diagonal elements which are effectively zero */ chop_small_elements (N, d, sd); /* Progressively reduce the matrix until it is diagonal */ b = N - 1; while (b > 0) { if (sd[b - 1] == 0.0 || isnan(sd[b - 1])) { b--; continue; } /* Find the largest unreduced block (a,b) starting from b and working backwards */ a = b - 1; while (a > 0) { if (sd[a - 1] == 0.0) { break; } a--; } { size_t i; const size_t n_block = b - a + 1; double *d_block = d + a; double *sd_block = sd + a; double * const gc = w->gc; double * const gs = w->gs; /* apply QR reduction with implicit deflation to the unreduced block */ qrstep (n_block, d_block, sd_block, gc, gs); /* Apply Givens rotation Gij(c,s) to matrix Q, Q <- Q G */ for (i = 0; i < n_block - 1; i++) { const double c = gc[i], s = gs[i]; size_t k; for (k = 0; k < N; k++) { gsl_complex qki = gsl_matrix_complex_get (evec, k, a + i); gsl_complex qkj = gsl_matrix_complex_get (evec, k, a + i + 1); /* qki <= qki * c - qkj * s */ /* qkj <= qki * s + qkj * c */ gsl_complex x1 = gsl_complex_mul_real(qki, c); gsl_complex y1 = gsl_complex_mul_real(qkj, -s); gsl_complex x2 = gsl_complex_mul_real(qki, s); gsl_complex y2 = gsl_complex_mul_real(qkj, c); gsl_complex qqki = gsl_complex_add(x1, y1); gsl_complex qqkj = gsl_complex_add(x2, y2); gsl_matrix_complex_set (evec, k, a + i, qqki); gsl_matrix_complex_set (evec, k, a + i + 1, qqkj); } } /* remove any small off-diagonal elements */ chop_small_elements (n_block, d_block, sd_block); } } { gsl_vector_view d_vec = gsl_vector_view_array (d, N); gsl_vector_memcpy (eval, &d_vec.vector); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_sf_legendre.h0000664000176700017670000002101511705263724017635 0ustar paulpaul/* specfunc/gsl_sf_legendre.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_LEGENDRE_H__ #define __GSL_SF_LEGENDRE_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* P_l(x) l >= 0; |x| <= 1 * * exceptions: GSL_EDOM */ int gsl_sf_legendre_Pl_e(const int l, const double x, gsl_sf_result * result); double gsl_sf_legendre_Pl(const int l, const double x); /* P_l(x) for l=0,...,lmax; |x| <= 1 * * exceptions: GSL_EDOM */ int gsl_sf_legendre_Pl_array( const int lmax, const double x, double * result_array ); /* P_l(x) and P_l'(x) for l=0,...,lmax; |x| <= 1 * * exceptions: GSL_EDOM */ int gsl_sf_legendre_Pl_deriv_array( const int lmax, const double x, double * result_array, double * result_deriv_array ); /* P_l(x), l=1,2,3 * * exceptions: none */ int gsl_sf_legendre_P1_e(double x, gsl_sf_result * result); int gsl_sf_legendre_P2_e(double x, gsl_sf_result * result); int gsl_sf_legendre_P3_e(double x, gsl_sf_result * result); double gsl_sf_legendre_P1(const double x); double gsl_sf_legendre_P2(const double x); double gsl_sf_legendre_P3(const double x); /* Q_0(x), x > -1, x != 1 * * exceptions: GSL_EDOM */ int gsl_sf_legendre_Q0_e(const double x, gsl_sf_result * result); double gsl_sf_legendre_Q0(const double x); /* Q_1(x), x > -1, x != 1 * * exceptions: GSL_EDOM */ int gsl_sf_legendre_Q1_e(const double x, gsl_sf_result * result); double gsl_sf_legendre_Q1(const double x); /* Q_l(x), x > -1, x != 1, l >= 0 * * exceptions: GSL_EDOM */ int gsl_sf_legendre_Ql_e(const int l, const double x, gsl_sf_result * result); double gsl_sf_legendre_Ql(const int l, const double x); /* P_l^m(x) m >= 0; l >= m; |x| <= 1.0 * * Note that this function grows combinatorially with l. * Therefore we can easily generate an overflow for l larger * than about 150. * * There is no trouble for small m, but when m and l are both large, * then there will be trouble. Rather than allow overflows, these * functions refuse to calculate when they can sense that l and m are * too big. * * If you really want to calculate a spherical harmonic, then DO NOT * use this. Instead use legendre_sphPlm() below, which uses a similar * recursion, but with the normalized functions. * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_legendre_Plm_e(const int l, const int m, const double x, gsl_sf_result * result); double gsl_sf_legendre_Plm(const int l, const int m, const double x); /* P_l^m(x) m >= 0; l >= m; |x| <= 1.0 * l=|m|,...,lmax * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_legendre_Plm_array( const int lmax, const int m, const double x, double * result_array ); /* P_l^m(x) and d(P_l^m(x))/dx; m >= 0; lmax >= m; |x| <= 1.0 * l=|m|,...,lmax * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_legendre_Plm_deriv_array( const int lmax, const int m, const double x, double * result_array, double * result_deriv_array ); /* P_l^m(x), normalized properly for use in spherical harmonics * m >= 0; l >= m; |x| <= 1.0 * * There is no overflow problem, as there is for the * standard normalization of P_l^m(x). * * Specifically, it returns: * * sqrt((2l+1)/(4pi)) sqrt((l-m)!/(l+m)!) P_l^m(x) * * exceptions: GSL_EDOM */ int gsl_sf_legendre_sphPlm_e(const int l, int m, const double x, gsl_sf_result * result); double gsl_sf_legendre_sphPlm(const int l, const int m, const double x); /* sphPlm(l,m,x) values * m >= 0; l >= m; |x| <= 1.0 * l=|m|,...,lmax * * exceptions: GSL_EDOM */ int gsl_sf_legendre_sphPlm_array( const int lmax, int m, const double x, double * result_array ); /* sphPlm(l,m,x) and d(sphPlm(l,m,x))/dx values * m >= 0; l >= m; |x| <= 1.0 * l=|m|,...,lmax * * exceptions: GSL_EDOM */ int gsl_sf_legendre_sphPlm_deriv_array( const int lmax, const int m, const double x, double * result_array, double * result_deriv_array ); /* size of result_array[] needed for the array versions of Plm * (lmax - m + 1) */ int gsl_sf_legendre_array_size(const int lmax, const int m); /* Irregular Spherical Conical Function * P^{1/2}_{-1/2 + I lambda}(x) * * x > -1.0 * exceptions: GSL_EDOM */ int gsl_sf_conicalP_half_e(const double lambda, const double x, gsl_sf_result * result); double gsl_sf_conicalP_half(const double lambda, const double x); /* Regular Spherical Conical Function * P^{-1/2}_{-1/2 + I lambda}(x) * * x > -1.0 * exceptions: GSL_EDOM */ int gsl_sf_conicalP_mhalf_e(const double lambda, const double x, gsl_sf_result * result); double gsl_sf_conicalP_mhalf(const double lambda, const double x); /* Conical Function * P^{0}_{-1/2 + I lambda}(x) * * x > -1.0 * exceptions: GSL_EDOM */ int gsl_sf_conicalP_0_e(const double lambda, const double x, gsl_sf_result * result); double gsl_sf_conicalP_0(const double lambda, const double x); /* Conical Function * P^{1}_{-1/2 + I lambda}(x) * * x > -1.0 * exceptions: GSL_EDOM */ int gsl_sf_conicalP_1_e(const double lambda, const double x, gsl_sf_result * result); double gsl_sf_conicalP_1(const double lambda, const double x); /* Regular Spherical Conical Function * P^{-1/2-l}_{-1/2 + I lambda}(x) * * x > -1.0, l >= -1 * exceptions: GSL_EDOM */ int gsl_sf_conicalP_sph_reg_e(const int l, const double lambda, const double x, gsl_sf_result * result); double gsl_sf_conicalP_sph_reg(const int l, const double lambda, const double x); /* Regular Cylindrical Conical Function * P^{-m}_{-1/2 + I lambda}(x) * * x > -1.0, m >= -1 * exceptions: GSL_EDOM */ int gsl_sf_conicalP_cyl_reg_e(const int m, const double lambda, const double x, gsl_sf_result * result); double gsl_sf_conicalP_cyl_reg(const int m, const double lambda, const double x); /* The following spherical functions are specializations * of Legendre functions which give the regular eigenfunctions * of the Laplacian on a 3-dimensional hyperbolic space. * Of particular interest is the flat limit, which is * Flat-Lim := {lambda->Inf, eta->0, lambda*eta fixed}. */ /* Zeroth radial eigenfunction of the Laplacian on the * 3-dimensional hyperbolic space. * * legendre_H3d_0(lambda,eta) := sin(lambda*eta)/(lambda*sinh(eta)) * * Normalization: * Flat-Lim legendre_H3d_0(lambda,eta) = j_0(lambda*eta) * * eta >= 0.0 * exceptions: GSL_EDOM */ int gsl_sf_legendre_H3d_0_e(const double lambda, const double eta, gsl_sf_result * result); double gsl_sf_legendre_H3d_0(const double lambda, const double eta); /* First radial eigenfunction of the Laplacian on the * 3-dimensional hyperbolic space. * * legendre_H3d_1(lambda,eta) := * 1/sqrt(lambda^2 + 1) sin(lam eta)/(lam sinh(eta)) * (coth(eta) - lambda cot(lambda*eta)) * * Normalization: * Flat-Lim legendre_H3d_1(lambda,eta) = j_1(lambda*eta) * * eta >= 0.0 * exceptions: GSL_EDOM */ int gsl_sf_legendre_H3d_1_e(const double lambda, const double eta, gsl_sf_result * result); double gsl_sf_legendre_H3d_1(const double lambda, const double eta); /* l'th radial eigenfunction of the Laplacian on the * 3-dimensional hyperbolic space. * * Normalization: * Flat-Lim legendre_H3d_l(l,lambda,eta) = j_l(lambda*eta) * * eta >= 0.0, l >= 0 * exceptions: GSL_EDOM */ int gsl_sf_legendre_H3d_e(const int l, const double lambda, const double eta, gsl_sf_result * result); double gsl_sf_legendre_H3d(const int l, const double lambda, const double eta); /* Array of H3d(ell), 0 <= ell <= lmax */ int gsl_sf_legendre_H3d_array(const int lmax, const double lambda, const double eta, double * result_array); #ifdef HAVE_INLINE extern inline int gsl_sf_legendre_array_size(const int lmax, const int m) { return lmax-m+1; } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_SF_LEGENDRE_H__ */ sources_5316/external/gsl/gsl_specfunc__debye.c0000664000176700017670000003347711723710247020504 0ustar paulpaul/* specfunc/debye.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* augmented to n=5 and 6 2005-11-08 by R. J. Mathar, http://www.strw.leidenuniv.nl/~mathar */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_debye.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__check.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" static double adeb1_data[17] = { 2.4006597190381410194, 0.1937213042189360089, -0.62329124554895770e-02, 0.3511174770206480e-03, -0.228222466701231e-04, 0.15805467875030e-05, -0.1135378197072e-06, 0.83583361188e-08, -0.6264424787e-09, 0.476033489e-10, -0.36574154e-11, 0.2835431e-12, -0.221473e-13, 0.17409e-14, -0.1376e-15, 0.109e-16, -0.9e-18 }; static cheb_series adeb1_cs = { adeb1_data, 16, -1.0, 1.0, 9 }; static double adeb2_data[18] = { 2.5943810232570770282, 0.2863357204530719834, -0.102062656158046713e-01, 0.6049109775346844e-03, -0.405257658950210e-04, 0.28633826328811e-05, -0.2086394303065e-06, 0.155237875826e-07, -0.11731280087e-08, 0.897358589e-10, -0.69317614e-11, 0.5398057e-12, -0.423241e-13, 0.33378e-14, -0.2645e-15, 0.211e-16, -0.17e-17, 0.1e-18 }; static cheb_series adeb2_cs = { adeb2_data, 17, -1.0, 1.0, 10 }; static double adeb3_data[17] = { 2.707737068327440945, 0.340068135211091751, -0.12945150184440869e-01, 0.7963755380173816e-03, -0.546360009590824e-04, 0.39243019598805e-05, -0.2894032823539e-06, 0.217317613962e-07, -0.16542099950e-08, 0.1272796189e-09, -0.987963460e-11, 0.7725074e-12, -0.607797e-13, 0.48076e-14, -0.3820e-15, 0.305e-16, -0.24e-17 }; static cheb_series adeb3_cs = { adeb3_data, 16, -1.0, 1.0, 10 }; static double adeb4_data[17] = { 2.781869415020523460, 0.374976783526892863, -0.14940907399031583e-01, 0.945679811437042e-03, -0.66132916138933e-04, 0.4815632982144e-05, -0.3588083958759e-06, 0.271601187416e-07, -0.20807099122e-08, 0.1609383869e-09, -0.125470979e-10, 0.9847265e-12, -0.777237e-13, 0.61648e-14, -0.4911e-15, 0.393e-16, -0.32e-17 }; static cheb_series adeb4_cs = { adeb4_data, 16, -1.0, 1.0, 10 }; static double adeb5_data[17] = { 2.8340269546834530149, 0.3994098857106266445, -0.164566764773099646e-1, 0.10652138340664541e-2, -0.756730374875418e-4, 0.55745985240273e-5, -0.4190692330918e-6, 0.319456143678e-7, -0.24613318171e-8, 0.1912801633e-9, -0.149720049e-10, 0.11790312e-11, -0.933329e-13, 0.74218e-14, -0.5925e-15, 0.475e-16, -0.39e-17 }; static cheb_series adeb5_cs = { adeb5_data, 16, -1.0, 1.0, 10 }; static double adeb6_data[17] = { 2.8726727134130122113, 0.4174375352339027746, -0.176453849354067873e-1, 0.11629852733494556e-2, -0.837118027357117e-4, 0.62283611596189e-5, -0.4718644465636e-6, 0.361950397806e-7, -0.28030368010e-8, 0.2187681983e-9, -0.171857387e-10, 0.13575809e-11, -0.1077580e-12, 0.85893e-14, -0.6872e-15, 0.552e-16, -0.44e-17 }; static cheb_series adeb6_cs = { adeb6_data, 16, -1.0, 1.0, 10 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_debye_1_e(const double x, gsl_sf_result * result) { const double val_infinity = 1.64493406684822644; const double xcut = -GSL_LOG_DBL_MIN; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*GSL_SQRT_DBL_EPSILON) { result->val = 1.0 - 0.25*x + x*x/36.0; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x <= 4.0) { const double t = x*x/8.0 - 1.0; gsl_sf_result c; cheb_eval_e(&adeb1_cs, t, &c); result->val = c.val - 0.25 * x; result->err = c.err + 0.25 * x * GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < -(M_LN2 + GSL_LOG_DBL_EPSILON)) { const int nexp = floor(xcut/x); const double ex = exp(-x); double sum = 0.0; double xk = nexp * x; double rk = nexp; int i; for(i=nexp; i>=1; i--) { sum *= ex; sum += (1.0 + 1.0/xk)/rk; rk -= 1.0; xk -= x; } result->val = val_infinity/x - sum*ex; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < xcut) { result->val = (val_infinity - exp(-x)*(x+1.0)) / x; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = val_infinity/x; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_debye_2_e(const double x, gsl_sf_result * result) { const double val_infinity = 4.80822761263837714; const double xcut = -GSL_LOG_DBL_MIN; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*M_SQRT2*GSL_SQRT_DBL_EPSILON) { result->val = 1.0 - x/3.0 + x*x/24.0; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x <= 4.0) { const double t = x*x/8.0 - 1.0; gsl_sf_result c; cheb_eval_e(&adeb2_cs, t, &c); result->val = c.val - x/3.0; result->err = c.err + GSL_DBL_EPSILON * x/3.0; return GSL_SUCCESS; } else if(x < -(M_LN2 + GSL_LOG_DBL_EPSILON)) { const int nexp = floor(xcut/x); const double ex = exp(-x); double xk = nexp * x; double rk = nexp; double sum = 0.0; int i; for(i=nexp; i>=1; i--) { sum *= ex; sum += (1.0 + 2.0/xk + 2.0/(xk*xk)) / rk; rk -= 1.0; xk -= x; } result->val = val_infinity/(x*x) - 2.0 * sum * ex; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < xcut) { const double x2 = x*x; const double sum = 2.0 + 2.0*x + x2; result->val = (val_infinity - 2.0 * sum * exp(-x)) / x2; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = (val_infinity/x)/x; result->err = GSL_DBL_EPSILON * result->val; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_debye_3_e(const double x, gsl_sf_result * result) { const double val_infinity = 19.4818182068004875; const double xcut = -GSL_LOG_DBL_MIN; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*M_SQRT2*GSL_SQRT_DBL_EPSILON) { result->val = 1.0 - 3.0*x/8.0 + x*x/20.0; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x <= 4.0) { const double t = x*x/8.0 - 1.0; gsl_sf_result c; cheb_eval_e(&adeb3_cs, t, &c); result->val = c.val - 0.375*x; result->err = c.err + GSL_DBL_EPSILON * 0.375*x; return GSL_SUCCESS; } else if(x < -(M_LN2 + GSL_LOG_DBL_EPSILON)) { const int nexp = floor(xcut/x); const double ex = exp(-x); double xk = nexp * x; double rk = nexp; double sum = 0.0; int i; for(i=nexp; i>=1; i--) { double xk_inv = 1.0/xk; sum *= ex; sum += (((6.0*xk_inv + 6.0)*xk_inv + 3.0)*xk_inv + 1.0) / rk; rk -= 1.0; xk -= x; } result->val = val_infinity/(x*x*x) - 3.0 * sum * ex; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x < xcut) { const double x3 = x*x*x; const double sum = 6.0 + 6.0*x + 3.0*x*x + x3; result->val = (val_infinity - 3.0 * sum * exp(-x)) / x3; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { result->val = ((val_infinity/x)/x)/x; result->err = GSL_DBL_EPSILON * result->val; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_debye_4_e(const double x, gsl_sf_result * result) { const double val_infinity = 99.5450644937635129; const double xcut = -GSL_LOG_DBL_MIN; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*M_SQRT2*GSL_SQRT_DBL_EPSILON) { result->val = 1.0 - 2.0*x/5.0 + x*x/18.0; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x <= 4.0) { const double t = x*x/8.0 - 1.0; gsl_sf_result c; cheb_eval_e(&adeb4_cs, t, &c); result->val = c.val - 2.0*x/5.0; result->err = c.err + GSL_DBL_EPSILON * 2.0*x/5.0; return GSL_SUCCESS; } else if(x < -(M_LN2 + GSL_LOG_DBL_EPSILON)) { const int nexp = floor(xcut/x); const double ex = exp(-x); double xk = nexp * x; double rk = nexp; double sum = 0.0; int i; for(i=nexp; i>=1; i--) { double xk_inv = 1.0/xk; sum *= ex; sum += ((((24.0*xk_inv + 24.0)*xk_inv + 12.0)*xk_inv + 4.0)*xk_inv + 1.0) / rk; rk -= 1.0; xk -= x; } result->val = val_infinity/(x*x*x*x) - 4.0 * sum * ex; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x < xcut) { const double x2 = x*x; const double x4 = x2*x2; const double sum = 24.0 + 24.0*x + 12.0*x2 + 4.0*x2*x + x4; result->val = (val_infinity - 4.0 * sum * exp(-x)) / x4; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { result->val = (((val_infinity/x)/x)/x)/x; result->err = GSL_DBL_EPSILON * result->val; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_debye_5_e(const double x, gsl_sf_result * result) { const double val_infinity = 610.405837190669483828710757875 ; const double xcut = -GSL_LOG_DBL_MIN; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*M_SQRT2*GSL_SQRT_DBL_EPSILON) { result->val = 1.0 - 5.0*x/12.0 + 5.0*x*x/84.0; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x <= 4.0) { const double t = x*x/8.0 - 1.0; gsl_sf_result c; cheb_eval_e(&adeb5_cs, t, &c); result->val = c.val - 5.0*x/12.0; result->err = c.err + GSL_DBL_EPSILON * 5.0*x/12.0; return GSL_SUCCESS; } else if(x < -(M_LN2 + GSL_LOG_DBL_EPSILON)) { const int nexp = floor(xcut/x); const double ex = exp(-x); double xk = nexp * x; double rk = nexp; double sum = 0.0; int i; for(i=nexp; i>=1; i--) { double xk_inv = 1.0/xk; sum *= ex; sum += (((((120.0*xk_inv + 120.0)*xk_inv + 60.0)*xk_inv + 20.0)*xk_inv + 5.0)*xk_inv+ 1.0) / rk; rk -= 1.0; xk -= x; } result->val = val_infinity/(x*x*x*x*x) - 5.0 * sum * ex; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x < xcut) { const double x2 = x*x; const double x4 = x2*x2; const double x5 = x4*x; const double sum = 120.0 + 120.0*x + 60.0*x2 + 20.0*x2*x + 5.0*x4 + x5; result->val = (val_infinity - 5.0 * sum * exp(-x)) / x5; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { result->val = ((((val_infinity/x)/x)/x)/x)/x; result->err = GSL_DBL_EPSILON * result->val; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_debye_6_e(const double x, gsl_sf_result * result) { const double val_infinity = 4356.06887828990661194792541535 ; const double xcut = -GSL_LOG_DBL_MIN; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*M_SQRT2*GSL_SQRT_DBL_EPSILON) { result->val = 1.0 - 3.0*x/7.0 + x*x/16.0; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x <= 4.0) { const double t = x*x/8.0 - 1.0; gsl_sf_result c; cheb_eval_e(&adeb6_cs, t, &c); result->val = c.val - 3.0*x/7.0; result->err = c.err + GSL_DBL_EPSILON * 3.0*x/7.0; return GSL_SUCCESS; } else if(x < -(M_LN2 + GSL_LOG_DBL_EPSILON)) { const int nexp = floor(xcut/x); const double ex = exp(-x); double xk = nexp * x; double rk = nexp; double sum = 0.0; int i; for(i=nexp; i>=1; i--) { double xk_inv = 1.0/xk; sum *= ex; sum += ((((((720.0*xk_inv + 720.0)*xk_inv + 360.0)*xk_inv + 120.0)*xk_inv + 30.0)*xk_inv+ 6.0)*xk_inv+ 1.0) / rk; rk -= 1.0; xk -= x; } result->val = val_infinity/(x*x*x*x*x*x) - 6.0 * sum * ex; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x < xcut) { const double x2 = x*x; const double x4 = x2*x2; const double x6 = x4*x2; const double sum = 720.0 + 720.0*x + 360.0*x2 + 120.0*x2*x + 30.0*x4 + 6.0*x4*x +x6 ; result->val = (val_infinity - 6.0 * sum * exp(-x)) / x6; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { result->val = (((((val_infinity/x)/x)/x)/x)/x)/x ; result->err = GSL_DBL_EPSILON * result->val; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_debye_1(const double x) { EVAL_RESULT(gsl_sf_debye_1_e(x, &result)); } double gsl_sf_debye_2(const double x) { EVAL_RESULT(gsl_sf_debye_2_e(x, &result)); } double gsl_sf_debye_3(const double x) { EVAL_RESULT(gsl_sf_debye_3_e(x, &result)); } double gsl_sf_debye_4(const double x) { EVAL_RESULT(gsl_sf_debye_4_e(x, &result)); } double gsl_sf_debye_5(const double x) { EVAL_RESULT(gsl_sf_debye_5_e(x, &result)); } double gsl_sf_debye_6(const double x) { EVAL_RESULT(gsl_sf_debye_6_e(x, &result)); } sources_5316/external/gsl/gsl_integration__qk.c0000664000176700017670000000623011723710247020527 0ustar paulpaul/* integration/qk.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_integration.h" #include "gsl_integration__err.c" void gsl_integration_qk (const int n, const double xgk[], const double wg[], const double wgk[], double fv1[], double fv2[], const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc) { const double center = 0.5 * (a + b); const double half_length = 0.5 * (b - a); const double abs_half_length = fabs (half_length); const double f_center = GSL_FN_EVAL (f, center); double result_gauss = 0; double result_kronrod = f_center * wgk[n - 1]; double result_abs = fabs (result_kronrod); double result_asc = 0; double mean = 0, err = 0; int j; if (n % 2 == 0) { result_gauss = f_center * wg[n / 2 - 1]; } for (j = 0; j < (n - 1) / 2; j++) { const int jtw = j * 2 + 1; /* j=1,2,3 jtw=2,4,6 */ const double abscissa = half_length * xgk[jtw]; const double fval1 = GSL_FN_EVAL (f, center - abscissa); const double fval2 = GSL_FN_EVAL (f, center + abscissa); const double fsum = fval1 + fval2; fv1[jtw] = fval1; fv2[jtw] = fval2; result_gauss += wg[j] * fsum; result_kronrod += wgk[jtw] * fsum; result_abs += wgk[jtw] * (fabs (fval1) + fabs (fval2)); } for (j = 0; j < n / 2; j++) { int jtwm1 = j * 2; const double abscissa = half_length * xgk[jtwm1]; const double fval1 = GSL_FN_EVAL (f, center - abscissa); const double fval2 = GSL_FN_EVAL (f, center + abscissa); fv1[jtwm1] = fval1; fv2[jtwm1] = fval2; result_kronrod += wgk[jtwm1] * (fval1 + fval2); result_abs += wgk[jtwm1] * (fabs (fval1) + fabs (fval2)); }; mean = result_kronrod * 0.5; result_asc = wgk[n - 1] * fabs (f_center - mean); for (j = 0; j < n - 1; j++) { result_asc += wgk[j] * (fabs (fv1[j] - mean) + fabs (fv2[j] - mean)); } /* scale by the width of the integration region */ err = (result_kronrod - result_gauss) * half_length; result_kronrod *= half_length; result_abs *= abs_half_length; result_asc *= abs_half_length; *result = result_kronrod; *resabs = result_abs; *resasc = result_asc; *abserr = rescale_error (err, result_abs, result_asc); } sources_5316/external/gsl/gsl_statistics_uint.h0000664000176700017670000001103711705263724020614 0ustar paulpaul/* statistics/gsl_statistics_uint.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_UINT_H__ #define __GSL_STATISTICS_UINT_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_uint_mean (const unsigned int data[], const size_t stride, const size_t n); double gsl_stats_uint_variance (const unsigned int data[], const size_t stride, const size_t n); double gsl_stats_uint_sd (const unsigned int data[], const size_t stride, const size_t n); double gsl_stats_uint_variance_with_fixed_mean (const unsigned int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uint_sd_with_fixed_mean (const unsigned int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uint_absdev (const unsigned int data[], const size_t stride, const size_t n); double gsl_stats_uint_skew (const unsigned int data[], const size_t stride, const size_t n); double gsl_stats_uint_kurtosis (const unsigned int data[], const size_t stride, const size_t n); double gsl_stats_uint_lag1_autocorrelation (const unsigned int data[], const size_t stride, const size_t n); double gsl_stats_uint_covariance (const unsigned int data1[], const size_t stride1,const unsigned int data2[], const size_t stride2, const size_t n); double gsl_stats_uint_correlation (const unsigned int data1[], const size_t stride1,const unsigned int data2[], const size_t stride2, const size_t n); double gsl_stats_uint_variance_m (const unsigned int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uint_sd_m (const unsigned int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uint_absdev_m (const unsigned int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uint_skew_m_sd (const unsigned int data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_uint_kurtosis_m_sd (const unsigned int data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_uint_lag1_autocorrelation_m (const unsigned int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uint_covariance_m (const unsigned int data1[], const size_t stride1,const unsigned int data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); double gsl_stats_uint_pvariance (const unsigned int data1[], const size_t stride1, const size_t n1, const unsigned int data2[], const size_t stride2, const size_t n2); double gsl_stats_uint_ttest (const unsigned int data1[], const size_t stride1, const size_t n1, const unsigned int data2[], const size_t stride2, const size_t n2); unsigned int gsl_stats_uint_max (const unsigned int data[], const size_t stride, const size_t n); unsigned int gsl_stats_uint_min (const unsigned int data[], const size_t stride, const size_t n); void gsl_stats_uint_minmax (unsigned int * min, unsigned int * max, const unsigned int data[], const size_t stride, const size_t n); size_t gsl_stats_uint_max_index (const unsigned int data[], const size_t stride, const size_t n); size_t gsl_stats_uint_min_index (const unsigned int data[], const size_t stride, const size_t n); void gsl_stats_uint_minmax_index (size_t * min_index, size_t * max_index, const unsigned int data[], const size_t stride, const size_t n); double gsl_stats_uint_median_from_sorted_data (const unsigned int sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_uint_quantile_from_sorted_data (const unsigned int sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_UINT_H__ */ sources_5316/external/gsl/gsl_specfunc__dawson.c0000664000176700017670000002351511723710247020677 0ustar paulpaul/* specfunc/dawson.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_dawson.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /* Based on ddaws.f, Fullerton, W., (LANL) */ /* Chebyshev expansions Series for DAW on the interval 0. to 1.00000E+00 with weighted error 8.95E-32 log weighted error 31.05 significant figures required 30.41 decimal places required 31.71 Series for DAW2 on the interval 0. to 1.60000E+01 with weighted error 1.61E-32 log weighted error 31.79 significant figures required 31.40 decimal places required 32.62 Series for DAWA on the interval 0. to 6.25000E-02 with weighted error 1.97E-32 log weighted error 31.71 significant figures required 29.79 decimal places required 32.64 */ static double daw_data[21] = { -0.6351734375145949201065127736293e-02, -0.2294071479677386939899824125866e+00, 0.2213050093908476441683979161786e-01, -0.1549265453892985046743057753375e-02, 0.8497327715684917456777542948066e-04, -0.3828266270972014924994099521309e-05, 0.1462854806250163197757148949539e-06, -0.4851982381825991798846715425114e-08, 0.1421463577759139790347568183304e-09, -0.3728836087920596525335493054088e-11, 0.8854942961778203370194565231369e-13, -0.1920757131350206355421648417493e-14, 0.3834325867246327588241074439253e-16, -0.7089154168175881633584099327999e-18, 0.1220552135889457674416901120000e-19, -0.1966204826605348760299451733333e-21, 0.2975845541376597189113173333333e-23, -0.4247069514800596951039999999999e-25, 0.5734270767391742798506666666666e-27, -0.7345836823178450261333333333333e-29, 0.8951937667516552533333333333333e-31 }; static cheb_series daw_cs = { daw_data, 15, /* 20, */ -1, 1, 9 }; static double daw2_data[45] = { -0.56886544105215527114160533733674e-01, -0.31811346996168131279322878048822e+00, 0.20873845413642236789741580198858e+00, -0.12475409913779131214073498314784e+00, 0.67869305186676777092847516423676e-01, -0.33659144895270939503068230966587e-01, 0.15260781271987971743682460381640e-01, -0.63483709625962148230586094788535e-02, 0.24326740920748520596865966109343e-02, -0.86219541491065032038526983549637e-03, 0.28376573336321625302857636538295e-03, -0.87057549874170423699396581464335e-04, 0.24986849985481658331800044137276e-04, -0.67319286764160294344603050339520e-05, 0.17078578785573543710504524047844e-05, -0.40917551226475381271896592490038e-06, 0.92828292216755773260751785312273e-07, -0.19991403610147617829845096332198e-07, 0.40963490644082195241210487868917e-08, -0.80032409540993168075706781753561e-09, 0.14938503128761465059143225550110e-09, -0.26687999885622329284924651063339e-10, 0.45712216985159458151405617724103e-11, -0.75187305222043565872243727326771e-12, 0.11893100052629681879029828987302e-12, -0.18116907933852346973490318263084e-13, 0.26611733684358969193001612199626e-14, -0.37738863052129419795444109905930e-15, 0.51727953789087172679680082229329e-16, -0.68603684084077500979419564670102e-17, 0.88123751354161071806469337321745e-18, -0.10974248249996606292106299624652e-18, 0.13261199326367178513595545891635e-19, -0.15562732768137380785488776571562e-20, 0.17751425583655720607833415570773e-21, -0.19695006967006578384953608765439e-22, 0.21270074896998699661924010120533e-23, -0.22375398124627973794182113962666e-24, 0.22942768578582348946971383125333e-25, -0.22943788846552928693329592319999e-26, 0.22391702100592453618342297600000e-27, -0.21338230616608897703678225066666e-28, 0.19866196585123531518028458666666e-29, -0.18079295866694391771955199999999e-30, 0.16090686015283030305450666666666e-31 }; static cheb_series daw2_cs = { daw2_data, 32, /* 44, */ -1, 1, 21 }; static double dawa_data[75] = { 0.1690485637765703755422637438849e-01, 0.8683252278406957990536107850768e-02, 0.2424864042417715453277703459889e-03, 0.1261182399572690001651949240377e-04, 0.1066453314636176955705691125906e-05, 0.1358159794790727611348424505728e-06, 0.2171042356577298398904312744743e-07, 0.2867010501805295270343676804813e-08, -0.1901336393035820112282492378024e-09, -0.3097780484395201125532065774268e-09, -0.1029414876057509247398132286413e-09, -0.6260356459459576150417587283121e-11, 0.8563132497446451216262303166276e-11, 0.3033045148075659292976266276257e-11, -0.2523618306809291372630886938826e-12, -0.4210604795440664513175461934510e-12, -0.4431140826646238312143429452036e-13, 0.4911210272841205205940037065117e-13, 0.1235856242283903407076477954739e-13, -0.5788733199016569246955765071069e-14, -0.2282723294807358620978183957030e-14, 0.7637149411014126476312362917590e-15, 0.3851546883566811728777594002095e-15, -0.1199932056928290592803237283045e-15, -0.6313439150094572347334270285250e-16, 0.2239559965972975375254912790237e-16, 0.9987925830076495995132891200749e-17, -0.4681068274322495334536246507252e-17, -0.1436303644349721337241628751534e-17, 0.1020822731410541112977908032130e-17, 0.1538908873136092072837389822372e-18, -0.2189157877645793888894790926056e-18, 0.2156879197938651750392359152517e-20, 0.4370219827442449851134792557395e-19, -0.8234581460977207241098927905177e-20, -0.7498648721256466222903202835420e-20, 0.3282536720735671610957612930039e-20, 0.8858064309503921116076561515151e-21, -0.9185087111727002988094460531485e-21, 0.2978962223788748988314166045791e-22, 0.1972132136618471883159505468041e-21, -0.5974775596362906638089584995117e-22, -0.2834410031503850965443825182441e-22, 0.2209560791131554514777150489012e-22, -0.5439955741897144300079480307711e-25, -0.5213549243294848668017136696470e-23, 0.1702350556813114199065671499076e-23, 0.6917400860836148343022185660197e-24, -0.6540941793002752512239445125802e-24, 0.6093576580439328960371824654636e-25, 0.1408070432905187461501945080272e-24, -0.6785886121054846331167674943755e-25, -0.9799732036214295711741583102225e-26, 0.2121244903099041332598960939160e-25, -0.5954455022548790938238802154487e-26, -0.3093088861875470177838847232049e-26, 0.2854389216344524682400691986104e-26, -0.3951289447379305566023477271811e-27, -0.5906000648607628478116840894453e-27, 0.3670236964668687003647889980609e-27, -0.4839958238042276256598303038941e-29, -0.9799265984210443869597404017022e-28, 0.4684773732612130606158908804300e-28, 0.5030877696993461051647667603155e-29, -0.1547395051706028239247552068295e-28, 0.6112180185086419243976005662714e-29, 0.1357913399124811650343602736158e-29, -0.2417687752768673088385304299044e-29, 0.8369074582074298945292887587291e-30, 0.2665413042788979165838319401566e-30, -0.3811653692354890336935691003712e-30, 0.1230054721884951464371706872585e-30, 0.4622506399041493508805536929983e-31, -0.6120087296881677722911435593001e-31, 0.1966024640193164686956230217896e-31 }; static cheb_series dawa_cs = { dawa_data, 34, /* 74, */ -1, 1, 12 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_dawson_e(double x, gsl_sf_result * result) { const double xsml = 1.225 * GSL_SQRT_DBL_EPSILON; const double xbig = 1.0/(M_SQRT2*GSL_SQRT_DBL_EPSILON); const double xmax = 0.1 * GSL_DBL_MAX; const double y = fabs(x); if(y < xsml) { result->val = x; result->err = 0.0; return GSL_SUCCESS; } else if(y < 1.0) { gsl_sf_result result_c; cheb_eval_e(&daw_cs, 2.0*y*y - 1.0, &result_c); result->val = x * (0.75 + result_c.val); result->err = y * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(y < 4.0) { gsl_sf_result result_c; cheb_eval_e(&daw2_cs, 0.125*y*y - 1.0, &result_c); result->val = x * (0.25 + result_c.val); result->err = y * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(y < xbig) { gsl_sf_result result_c; cheb_eval_e(&dawa_cs, 32.0/(y*y) - 1.0, &result_c); result->val = (0.5 + result_c.val) / x; result->err = result_c.err / y; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(y < xmax) { result->val = 0.5/x; result->err = 2.0 * GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_dawson(double x) { EVAL_RESULT(gsl_sf_dawson_e(x, &result)); } sources_5316/external/gsl/gsl_specfunc__clausen.c0000664000176700017670000000532111723710247021031 0ustar paulpaul/* specfunc/clausen.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_clausen.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" static double aclaus_data[15] = { 2.142694363766688447e+00, 0.723324281221257925e-01, 0.101642475021151164e-02, 0.3245250328531645e-04, 0.133315187571472e-05, 0.6213240591653e-07, 0.313004135337e-08, 0.16635723056e-09, 0.919659293e-11, 0.52400462e-12, 0.3058040e-13, 0.18197e-14, 0.1100e-15, 0.68e-17, 0.4e-18 }; static cheb_series aclaus_cs = { aclaus_data, 14, -1, 1, 8 /* FIXME: this is a guess, correct value needed here BJG */ }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_clausen_e(double x, gsl_sf_result *result) { const double x_cut = M_PI * GSL_SQRT_DBL_EPSILON; double sgn = 1.0; int status_red; if(x < 0.0) { x = -x; sgn = -1.0; } /* Argument reduction to [0, 2pi) */ status_red = gsl_sf_angle_restrict_pos_e(&x); /* Further reduction to [0,pi) */ if(x > M_PI) { /* simulated extra precision: 2PI = p0 + p1 */ const double p0 = 6.28125; const double p1 = 0.19353071795864769253e-02; x = (p0 - x) + p1; sgn = -sgn; } if(x == 0.0) { result->val = 0.0; result->err = 0.0; } else if(x < x_cut) { result->val = x * (1.0 - log(x)); result->err = x * GSL_DBL_EPSILON; } else { const double t = 2.0*(x*x / (M_PI*M_PI) - 0.5); gsl_sf_result result_c; cheb_eval_e(&aclaus_cs, t, &result_c); result->val = x * (result_c.val - log(x)); result->err = x * (result_c.err + GSL_DBL_EPSILON); } result->val *= sgn; return status_red; } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_clausen(const double x) { EVAL_RESULT(gsl_sf_clausen_e(x, &result)); } sources_5316/external/gsl/gsl_precision.h0000664000176700017670000000336011705263724017356 0ustar paulpaul/* gsl_precision.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: B. Gough and G. Jungman */ #ifndef __GSL_PRECISION_H__ #define __GSL_PRECISION_H__ #include "gsl_types.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* A type for the precision indicator. * This is mainly for pedagogy. */ typedef unsigned int gsl_prec_t; /* The number of precision types. * Remember that precision-mode * can index an array. */ #define _GSL_PREC_T_NUM 3 /* Arrays containing derived * precision constants for the * different precision levels. */ GSL_VAR const double gsl_prec_eps[]; GSL_VAR const double gsl_prec_sqrt_eps[]; GSL_VAR const double gsl_prec_root3_eps[]; GSL_VAR const double gsl_prec_root4_eps[]; GSL_VAR const double gsl_prec_root5_eps[]; GSL_VAR const double gsl_prec_root6_eps[]; __END_DECLS #endif /* __GSL_PRECISION_H__ */ sources_5316/external/gsl/gsl_specfunc__legendre_H3d.c0000664000176700017670000004210411723710247021662 0ustar paulpaul/* specfunc/legendre_H3d.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_trig.h" #include "gsl_sf_legendre.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__legendre.h" /* See [Abbott+Schaefer, Ap.J. 308, 546 (1986)] for * enough details to follow what is happening here. */ /* Logarithm of normalization factor, Log[N(ell,lambda)]. * N(ell,lambda) = Product[ lambda^2 + n^2, {n,0,ell} ] * = |Gamma(ell + 1 + I lambda)|^2 lambda sinh(Pi lambda) / Pi * Assumes ell >= 0. */ static int legendre_H3d_lnnorm(const int ell, const double lambda, double * result) { double abs_lam = fabs(lambda); if(abs_lam == 0.0) { *result = 0.0; GSL_ERROR ("error", GSL_EDOM); } else if(lambda > (ell + 1.0)/GSL_ROOT3_DBL_EPSILON) { /* There is a cancellation between the sinh(Pi lambda) * term and the log(gamma(ell + 1 + i lambda) in the * result below, so we show some care and save some digits. * Note that the above guarantees that lambda is large, * since ell >= 0. We use Stirling and a simple expansion * of sinh. */ double rat = (ell+1.0)/lambda; double ln_lam2ell2 = 2.0*log(lambda) + log(1.0 + rat*rat); double lg_corrected = -2.0*(ell+1.0) + M_LNPI + (ell+0.5)*ln_lam2ell2 + 1.0/(288.0*lambda*lambda); double angle_terms = lambda * 2.0 * rat * (1.0 - rat*rat/3.0); *result = log(abs_lam) + lg_corrected + angle_terms - M_LNPI; return GSL_SUCCESS; } else { gsl_sf_result lg_r; gsl_sf_result lg_theta; gsl_sf_result ln_sinh; gsl_sf_lngamma_complex_e(ell+1.0, lambda, &lg_r, &lg_theta); gsl_sf_lnsinh_e(M_PI * abs_lam, &ln_sinh); *result = log(abs_lam) + ln_sinh.val + 2.0*lg_r.val - M_LNPI; return GSL_SUCCESS; } } /* Calculate series for small eta*lambda. * Assumes eta > 0, lambda != 0. * * This is just the defining hypergeometric for the Legendre function. * * P^{mu}_{-1/2 + I lam}(z) = 1/Gamma(l+3/2) ((z+1)/(z-1)^(mu/2) * 2F1(1/2 - I lam, 1/2 + I lam; l+3/2; (1-z)/2) * We use * z = cosh(eta) * (z-1)/2 = sinh^2(eta/2) * * And recall * H3d = sqrt(Pi Norm /(2 lam^2 sinh(eta))) P^{-l-1/2}_{-1/2 + I lam}(cosh(eta)) */ static int legendre_H3d_series(const int ell, const double lambda, const double eta, gsl_sf_result * result) { const int nmax = 5000; const double shheta = sinh(0.5*eta); const double ln_zp1 = M_LN2 + log(1.0 + shheta*shheta); const double ln_zm1 = M_LN2 + 2.0*log(shheta); const double zeta = -shheta*shheta; gsl_sf_result lg_lp32; double term = 1.0; double sum = 1.0; double sum_err = 0.0; gsl_sf_result lnsheta; double lnN; double lnpre_val, lnpre_err, lnprepow; int stat_e; int n; gsl_sf_lngamma_e(ell + 3.0/2.0, &lg_lp32); gsl_sf_lnsinh_e(eta, &lnsheta); legendre_H3d_lnnorm(ell, lambda, &lnN); lnprepow = 0.5*(ell + 0.5) * (ln_zm1 - ln_zp1); lnpre_val = lnprepow + 0.5*(lnN + M_LNPI - M_LN2 - lnsheta.val) - lg_lp32.val - log(fabs(lambda)); lnpre_err = lnsheta.err + lg_lp32.err + GSL_DBL_EPSILON * fabs(lnpre_val); lnpre_err += 2.0*GSL_DBL_EPSILON * (fabs(lnN) + M_LNPI + M_LN2); lnpre_err += 2.0*GSL_DBL_EPSILON * (0.5*(ell + 0.5) * (fabs(ln_zm1) + fabs(ln_zp1))); for(n=1; n RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 4.0*GSL_DBL_EPSILON) break; } result->val = fn; result->err = 2.0 * GSL_DBL_EPSILON * (sqrt(n)+1.0) * fabs(fn); if(n >= maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } #endif /* 0 */ /* Evaluate legendre_H3d(ell+1)/legendre_H3d(ell) * by continued fraction. Use the Gautschi (Euler) * equivalent series. */ /* FIXME: Maybe we have to worry about this. The a_k are * not positive and there can be a blow-up. It happened * for J_nu once or twice. Then we should probably use * the method above. */ static int legendre_H3d_CF1_ser(const int ell, const double lambda, const double coth_eta, gsl_sf_result * result) { const double pre = hypot(lambda, ell+1.0)/((2.0*ell+3)*coth_eta); const int maxk = 20000; double tk = 1.0; double sum = 1.0; double rhok = 0.0; double sum_err = 0.0; int k; for(k=1; kval = pre * sum; result->err = fabs(pre * tk); result->err += fabs(pre * sum_err); result->err += 4.0 * GSL_DBL_EPSILON * fabs(result->val); if(k >= maxk) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_legendre_H3d_0_e(const double lambda, const double eta, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(eta < 0.0) { DOMAIN_ERROR(result); } else if(eta == 0.0 || lambda == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else { const double lam_eta = lambda * eta; gsl_sf_result s; gsl_sf_sin_err_e(lam_eta, 2.0*GSL_DBL_EPSILON * fabs(lam_eta), &s); if(eta > -0.5*GSL_LOG_DBL_EPSILON) { double f = 2.0 / lambda * exp(-eta); result->val = f * s.val; result->err = fabs(f * s.val) * (fabs(eta) + 1.0) * GSL_DBL_EPSILON; result->err += fabs(f) * s.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } else { double f = 1.0/(lambda*sinh(eta)); result->val = f * s.val; result->err = fabs(f * s.val) * (fabs(eta) + 1.0) * GSL_DBL_EPSILON; result->err += fabs(f) * s.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return GSL_SUCCESS; } } int gsl_sf_legendre_H3d_1_e(const double lambda, const double eta, gsl_sf_result * result) { const double xi = fabs(eta*lambda); const double lsq = lambda*lambda; const double lsqp1 = lsq + 1.0; /* CHECK_POINTER(result) */ if(eta < 0.0) { DOMAIN_ERROR(result); } else if(eta == 0.0 || lambda == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(xi < GSL_ROOT5_DBL_EPSILON && eta < GSL_ROOT5_DBL_EPSILON) { double etasq = eta*eta; double xisq = xi*xi; double term1 = (etasq + xisq)/3.0; double term2 = -(2.0*etasq*etasq + 5.0*etasq*xisq + 3.0*xisq*xisq)/90.0; double sinh_term = 1.0 - eta*eta/6.0 * (1.0 - 7.0/60.0*eta*eta); double pre = sinh_term/sqrt(lsqp1) / eta; result->val = pre * (term1 + term2); result->err = pre * GSL_DBL_EPSILON * (fabs(term1) + fabs(term2)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double sin_term; /* Sin(xi)/xi */ double cos_term; /* Cos(xi) */ double coth_term; /* eta/Tanh(eta) */ double sinh_term; /* eta/Sinh(eta) */ double sin_term_err; double cos_term_err; double t1; double pre_val; double pre_err; double term1; double term2; if(xi < GSL_ROOT5_DBL_EPSILON) { sin_term = 1.0 - xi*xi/6.0 * (1.0 - xi*xi/20.0); cos_term = 1.0 - 0.5*xi*xi * (1.0 - xi*xi/12.0); sin_term_err = GSL_DBL_EPSILON; cos_term_err = GSL_DBL_EPSILON; } else { gsl_sf_result sin_xi_result; gsl_sf_result cos_xi_result; gsl_sf_sin_e(xi, &sin_xi_result); gsl_sf_cos_e(xi, &cos_xi_result); sin_term = sin_xi_result.val/xi; cos_term = cos_xi_result.val; sin_term_err = sin_xi_result.err/fabs(xi); cos_term_err = cos_xi_result.err; } if(eta < GSL_ROOT5_DBL_EPSILON) { coth_term = 1.0 + eta*eta/3.0 * (1.0 - eta*eta/15.0); sinh_term = 1.0 - eta*eta/6.0 * (1.0 - 7.0/60.0*eta*eta); } else { coth_term = eta/tanh(eta); sinh_term = eta/sinh(eta); } t1 = sqrt(lsqp1) * eta; pre_val = sinh_term/t1; pre_err = 2.0 * GSL_DBL_EPSILON * fabs(pre_val); term1 = sin_term*coth_term; term2 = cos_term; result->val = pre_val * (term1 - term2); result->err = pre_err * fabs(term1 - term2); result->err += pre_val * (sin_term_err * coth_term + cos_term_err); result->err += pre_val * fabs(term1-term2) * (fabs(eta) + 1.0) * GSL_DBL_EPSILON; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_legendre_H3d_e(const int ell, const double lambda, const double eta, gsl_sf_result * result) { const double abs_lam = fabs(lambda); const double lsq = abs_lam*abs_lam; const double xi = abs_lam * eta; const double cosh_eta = cosh(eta); /* CHECK_POINTER(result) */ if(eta < 0.0) { DOMAIN_ERROR(result); } else if(eta > GSL_LOG_DBL_MAX) { /* cosh(eta) is too big. */ OVERFLOW_ERROR(result); } else if(ell == 0) { return gsl_sf_legendre_H3d_0_e(lambda, eta, result); } else if(ell == 1) { return gsl_sf_legendre_H3d_1_e(lambda, eta, result); } else if(eta == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(xi < 1.0) { return legendre_H3d_series(ell, lambda, eta, result); } else if((ell*ell+lsq)/sqrt(1.0+lsq)/(cosh_eta*cosh_eta) < 5.0*GSL_ROOT3_DBL_EPSILON) { /* Large argument. */ gsl_sf_result P; double lm; int stat_P = gsl_sf_conicalP_large_x_e(-ell-0.5, lambda, cosh_eta, &P, &lm); if(P.val == 0.0) { result->val = 0.0; result->err = 0.0; return stat_P; } else { double lnN; gsl_sf_result lnsh; double ln_abslam; double lnpre_val, lnpre_err; int stat_e; gsl_sf_lnsinh_e(eta, &lnsh); legendre_H3d_lnnorm(ell, lambda, &lnN); ln_abslam = log(abs_lam); lnpre_val = 0.5*(M_LNPI + lnN - M_LN2 - lnsh.val) - ln_abslam; lnpre_err = lnsh.err; lnpre_err += 2.0 * GSL_DBL_EPSILON * (0.5*(M_LNPI + M_LN2 + fabs(lnN)) + fabs(ln_abslam)); lnpre_err += 2.0 * GSL_DBL_EPSILON * fabs(lnpre_val); stat_e = gsl_sf_exp_mult_err_e(lnpre_val + lm, lnpre_err, P.val, P.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_P); } } else if(abs_lam > 1000.0*ell*ell) { /* Large degree. */ gsl_sf_result P; double lm; int stat_P = gsl_sf_conicalP_xgt1_neg_mu_largetau_e(ell+0.5, lambda, cosh_eta, eta, &P, &lm); if(P.val == 0.0) { result->val = 0.0; result->err = 0.0; return stat_P; } else { double lnN; gsl_sf_result lnsh; double ln_abslam; double lnpre_val, lnpre_err; int stat_e; gsl_sf_lnsinh_e(eta, &lnsh); legendre_H3d_lnnorm(ell, lambda, &lnN); ln_abslam = log(abs_lam); lnpre_val = 0.5*(M_LNPI + lnN - M_LN2 - lnsh.val) - ln_abslam; lnpre_err = lnsh.err; lnpre_err += GSL_DBL_EPSILON * (0.5*(M_LNPI + M_LN2 + fabs(lnN)) + fabs(ln_abslam)); lnpre_err += 2.0 * GSL_DBL_EPSILON * fabs(lnpre_val); stat_e = gsl_sf_exp_mult_err_e(lnpre_val + lm, lnpre_err, P.val, P.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_P); } } else { /* Backward recurrence. */ const double coth_eta = 1.0/tanh(eta); const double coth_err_mult = fabs(eta) + 1.0; gsl_sf_result rH; int stat_CF1 = legendre_H3d_CF1_ser(ell, lambda, coth_eta, &rH); double Hlm1; double Hl = GSL_SQRT_DBL_MIN; double Hlp1 = rH.val * Hl; int lp; for(lp=ell; lp>0; lp--) { double root_term_0 = hypot(lambda,lp); double root_term_1 = hypot(lambda,lp+1.0); Hlm1 = ((2.0*lp + 1.0)*coth_eta*Hl - root_term_1 * Hlp1)/root_term_0; Hlp1 = Hl; Hl = Hlm1; } if(fabs(Hl) > fabs(Hlp1)) { gsl_sf_result H0; int stat_H0 = gsl_sf_legendre_H3d_0_e(lambda, eta, &H0); result->val = GSL_SQRT_DBL_MIN/Hl * H0.val; result->err = GSL_SQRT_DBL_MIN/fabs(Hl) * H0.err; result->err += fabs(rH.err/rH.val) * (ell+1.0) * coth_err_mult * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_H0, stat_CF1); } else { gsl_sf_result H1; int stat_H1 = gsl_sf_legendre_H3d_1_e(lambda, eta, &H1); result->val = GSL_SQRT_DBL_MIN/Hlp1 * H1.val; result->err = GSL_SQRT_DBL_MIN/fabs(Hlp1) * H1.err; result->err += fabs(rH.err/rH.val) * (ell+1.0) * coth_err_mult * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_H1, stat_CF1); } } } int gsl_sf_legendre_H3d_array(const int lmax, const double lambda, const double eta, double * result_array) { /* CHECK_POINTER(result_array) */ if(eta < 0.0 || lmax < 0) { int ell; for(ell=0; ell<=lmax; ell++) result_array[ell] = 0.0; GSL_ERROR ("domain error", GSL_EDOM); } else if(eta > GSL_LOG_DBL_MAX) { /* cosh(eta) is too big. */ int ell; for(ell=0; ell<=lmax; ell++) result_array[ell] = 0.0; GSL_ERROR ("overflow", GSL_EOVRFLW); } else if(lmax == 0) { gsl_sf_result H0; int stat = gsl_sf_legendre_H3d_e(0, lambda, eta, &H0); result_array[0] = H0.val; return stat; } else { /* Not the most efficient method. But what the hell... it's simple. */ gsl_sf_result r_Hlp1; gsl_sf_result r_Hl; int stat_lmax = gsl_sf_legendre_H3d_e(lmax, lambda, eta, &r_Hlp1); int stat_lmaxm1 = gsl_sf_legendre_H3d_e(lmax-1, lambda, eta, &r_Hl); int stat_max = GSL_ERROR_SELECT_2(stat_lmax, stat_lmaxm1); const double coth_eta = 1.0/tanh(eta); int stat_recursion = GSL_SUCCESS; double Hlp1 = r_Hlp1.val; double Hl = r_Hl.val; double Hlm1; int ell; result_array[lmax] = Hlp1; result_array[lmax-1] = Hl; for(ell=lmax-1; ell>0; ell--) { double root_term_0 = hypot(lambda,ell); double root_term_1 = hypot(lambda,ell+1.0); Hlm1 = ((2.0*ell + 1.0)*coth_eta*Hl - root_term_1 * Hlp1)/root_term_0; result_array[ell-1] = Hlm1; if(!(Hlm1 < GSL_DBL_MAX)) stat_recursion = GSL_EOVRFLW; Hlp1 = Hl; Hl = Hlm1; } return GSL_ERROR_SELECT_2(stat_recursion, stat_max); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_legendre_H3d_0(const double lambda, const double eta) { EVAL_RESULT(gsl_sf_legendre_H3d_0_e(lambda, eta, &result)); } double gsl_sf_legendre_H3d_1(const double lambda, const double eta) { EVAL_RESULT(gsl_sf_legendre_H3d_1_e(lambda, eta, &result)); } double gsl_sf_legendre_H3d(const int l, const double lambda, const double eta) { EVAL_RESULT(gsl_sf_legendre_H3d_e(l, lambda, eta, &result)); } sources_5316/external/gsl/gsl_histogram__oper.c0000664000176700017670000000750111723710247020535 0ustar paulpaul/* gsl_histogram_oper.c * Copyright (C) 2000 Simone Piccardi * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File gsl_histogram_oper.c: * Routine to make operation on histograms. * Need GSL library and header. * Contains the routines: * gsl_histogram_same_binning check if two histograms have the same binning * gsl_histogram_add add two histograms * gsl_histogram_sub subctract two histograms * gsl_histogram_mult multiply two histograms * gsl_histogram_div divide two histograms * gsl_histogram_scale scale histogram contents * * Author: S. Piccardi * Jan. 2000 * ***************************************************************/ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram.h" /* * gsl_histogram_same_binning: * control if two histograms have the * same binning */ int gsl_histogram_equal_bins_p (const gsl_histogram * h1, const gsl_histogram * h2) { if (h1->n != h2->n) { return 0; } { size_t i; /* init ranges */ for (i = 0; i <= h1->n; i++) { if (h1->range[i] != h2->range[i]) { return 0; } } } return 1; } /* * gsl_histogram_add: * add two histograms */ int gsl_histogram_add (gsl_histogram * h1, const gsl_histogram * h2) { size_t i; if (!gsl_histogram_equal_bins_p (h1, h2)) { GSL_ERROR ("histograms have different binning", GSL_EINVAL); } for (i = 0; i < h1->n; i++) { h1->bin[i] += h2->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram_sub: * subtract two histograms */ int gsl_histogram_sub (gsl_histogram * h1, const gsl_histogram * h2) { size_t i; if (!gsl_histogram_equal_bins_p (h1, h2)) { GSL_ERROR ("histograms have different binning", GSL_EINVAL); } for (i = 0; i < h1->n; i++) { h1->bin[i] -= h2->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram_mult: * multiply two histograms */ int gsl_histogram_mul (gsl_histogram * h1, const gsl_histogram * h2) { size_t i; if (!gsl_histogram_equal_bins_p (h1, h2)) { GSL_ERROR ("histograms have different binning", GSL_EINVAL); } for (i = 0; i < h1->n; i++) { h1->bin[i] *= h2->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram_div: * divide two histograms */ int gsl_histogram_div (gsl_histogram * h1, const gsl_histogram * h2) { size_t i; if (!gsl_histogram_equal_bins_p (h1, h2)) { GSL_ERROR ("histograms have different binning", GSL_EINVAL); } for (i = 0; i < h1->n; i++) { h1->bin[i] /= h2->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram_scale: * scale a histogram by a numeric factor */ int gsl_histogram_scale (gsl_histogram * h, double scale) { size_t i; for (i = 0; i < h->n; i++) { h->bin[i] *= scale; } return GSL_SUCCESS; } /* * gsl_histogram_shift: * shift a histogram by a numeric offset */ int gsl_histogram_shift (gsl_histogram * h, double shift) { size_t i; for (i = 0; i < h->n; i++) { h->bin[i] += shift; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_rng__rand.c0000664000176700017670000000436711723710247017314 0ustar paulpaul/* rng/rand.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is the old BSD rand() generator. The sequence is x_{n+1} = (a x_n + c) mod m with a = 1103515245, c = 12345 and m = 2^31 = 2147483648. The seed specifies the initial value, x_1. The theoretical value of x_{10001} is 1910041713. The period of this generator is 2^31. The rand() generator is not very good -- the low bits of successive numbers are correlated. */ static inline unsigned long int rand_get (void *vstate); static double rand_get_double (void *vstate); static void rand_set (void *state, unsigned long int s); typedef struct { unsigned long int x; } rand_state_t; static inline unsigned long int rand_get (void *vstate) { rand_state_t *state = (rand_state_t *) vstate; /* The following line relies on unsigned 32-bit arithmetic */ state->x = (1103515245 * state->x + 12345) & 0x7fffffffUL; return state->x; } static double rand_get_double (void *vstate) { return rand_get (vstate) / 2147483648.0 ; } static void rand_set (void *vstate, unsigned long int s) { rand_state_t *state = (rand_state_t *) vstate; state->x = s; return; } static const gsl_rng_type rand_type = {"rand", /* name */ 0x7fffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (rand_state_t), &rand_set, &rand_get, &rand_get_double}; const gsl_rng_type *gsl_rng_rand = &rand_type; sources_5316/external/gsl/gsl_multifit__multilinear.c0000664000176700017670000002577711723710247021774 0ustar paulpaul/* multifit/multilinear.c * * Copyright (C) 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_multifit.h" #include "gsl_blas.h" #include "gsl_linalg.h" /* Fit * * y = X c * * where X is an M x N matrix of M observations for N variables. * */ int gsl_multifit_linear (const gsl_matrix * X, const gsl_vector * y, gsl_vector * c, gsl_matrix * cov, double *chisq, gsl_multifit_linear_workspace * work) { size_t rank; int status = gsl_multifit_linear_svd (X, y, GSL_DBL_EPSILON, &rank, c, cov, chisq, work); return status; } /* Handle the general case of the SVD with tolerance and rank */ int gsl_multifit_linear_svd (const gsl_matrix * X, const gsl_vector * y, double tol, size_t * rank, gsl_vector * c, gsl_matrix * cov, double *chisq, gsl_multifit_linear_workspace * work) { if (X->size1 != y->size) { GSL_ERROR ("number of observations in y does not match rows of matrix X", GSL_EBADLEN); } else if (X->size2 != c->size) { GSL_ERROR ("number of parameters c does not match columns of matrix X", GSL_EBADLEN); } else if (cov->size1 != cov->size2) { GSL_ERROR ("covariance matrix is not square", GSL_ENOTSQR); } else if (c->size != cov->size1) { GSL_ERROR ("number of parameters does not match size of covariance matrix", GSL_EBADLEN); } else if (X->size1 != work->n || X->size2 != work->p) { GSL_ERROR ("size of workspace does not match size of observation matrix", GSL_EBADLEN); } else if (tol <= 0) { GSL_ERROR ("tolerance must be positive", GSL_EINVAL); } else { const size_t n = X->size1; const size_t p = X->size2; size_t i, j, p_eff; gsl_matrix *A = work->A; gsl_matrix *Q = work->Q; gsl_matrix *QSI = work->QSI; gsl_vector *S = work->S; gsl_vector *xt = work->xt; gsl_vector *D = work->D; /* Copy X to workspace, A <= X */ gsl_matrix_memcpy (A, X); /* Balance the columns of the matrix A */ gsl_linalg_balance_columns (A, D); /* Decompose A into U S Q^T */ gsl_linalg_SV_decomp_mod (A, QSI, Q, S, xt); /* Solve y = A c for c */ gsl_blas_dgemv (CblasTrans, 1.0, A, y, 0.0, xt); /* Scale the matrix Q, Q' = Q S^-1 */ gsl_matrix_memcpy (QSI, Q); { double alpha0 = gsl_vector_get (S, 0); p_eff = 0; for (j = 0; j < p; j++) { gsl_vector_view column = gsl_matrix_column (QSI, j); double alpha = gsl_vector_get (S, j); if (alpha <= tol * alpha0) { alpha = 0.0; } else { alpha = 1.0 / alpha; p_eff++; } gsl_vector_scale (&column.vector, alpha); } *rank = p_eff; } gsl_vector_set_zero (c); gsl_blas_dgemv (CblasNoTrans, 1.0, QSI, xt, 0.0, c); /* Unscale the balancing factors */ gsl_vector_div (c, D); /* Compute chisq, from residual r = y - X c */ { double s2 = 0, r2 = 0; for (i = 0; i < n; i++) { double yi = gsl_vector_get (y, i); gsl_vector_const_view row = gsl_matrix_const_row (X, i); double y_est, ri; gsl_blas_ddot (&row.vector, c, &y_est); ri = yi - y_est; r2 += ri * ri; } s2 = r2 / (n - p_eff); /* p_eff == rank */ *chisq = r2; /* Form variance-covariance matrix cov = s2 * (Q S^-1) (Q S^-1)^T */ for (i = 0; i < p; i++) { gsl_vector_view row_i = gsl_matrix_row (QSI, i); double d_i = gsl_vector_get (D, i); for (j = i; j < p; j++) { gsl_vector_view row_j = gsl_matrix_row (QSI, j); double d_j = gsl_vector_get (D, j); double s; gsl_blas_ddot (&row_i.vector, &row_j.vector, &s); gsl_matrix_set (cov, i, j, s * s2 / (d_i * d_j)); gsl_matrix_set (cov, j, i, s * s2 / (d_i * d_j)); } } } return GSL_SUCCESS; } } int gsl_multifit_wlinear (const gsl_matrix * X, const gsl_vector * w, const gsl_vector * y, gsl_vector * c, gsl_matrix * cov, double *chisq, gsl_multifit_linear_workspace * work) { size_t rank; int status = gsl_multifit_wlinear_svd (X, w, y, GSL_DBL_EPSILON, &rank, c, cov, chisq, work); return status; } int gsl_multifit_wlinear_svd (const gsl_matrix * X, const gsl_vector * w, const gsl_vector * y, double tol, size_t * rank, gsl_vector * c, gsl_matrix * cov, double *chisq, gsl_multifit_linear_workspace * work) { if (X->size1 != y->size) { GSL_ERROR ("number of observations in y does not match rows of matrix X", GSL_EBADLEN); } else if (X->size2 != c->size) { GSL_ERROR ("number of parameters c does not match columns of matrix X", GSL_EBADLEN); } else if (w->size != y->size) { GSL_ERROR ("number of weights does not match number of observations", GSL_EBADLEN); } else if (cov->size1 != cov->size2) { GSL_ERROR ("covariance matrix is not square", GSL_ENOTSQR); } else if (c->size != cov->size1) { GSL_ERROR ("number of parameters does not match size of covariance matrix", GSL_EBADLEN); } else if (X->size1 != work->n || X->size2 != work->p) { GSL_ERROR ("size of workspace does not match size of observation matrix", GSL_EBADLEN); } else { const size_t n = X->size1; const size_t p = X->size2; size_t i, j, p_eff; gsl_matrix *A = work->A; gsl_matrix *Q = work->Q; gsl_matrix *QSI = work->QSI; gsl_vector *S = work->S; gsl_vector *t = work->t; gsl_vector *xt = work->xt; gsl_vector *D = work->D; /* Scale X, A = sqrt(w) X */ gsl_matrix_memcpy (A, X); for (i = 0; i < n; i++) { double wi = gsl_vector_get (w, i); if (wi < 0) wi = 0; { gsl_vector_view row = gsl_matrix_row (A, i); gsl_vector_scale (&row.vector, sqrt (wi)); } } /* Balance the columns of the matrix A */ gsl_linalg_balance_columns (A, D); /* Decompose A into U S Q^T */ gsl_linalg_SV_decomp_mod (A, QSI, Q, S, xt); /* Solve sqrt(w) y = A c for c, by first computing t = sqrt(w) y */ for (i = 0; i < n; i++) { double wi = gsl_vector_get (w, i); double yi = gsl_vector_get (y, i); if (wi < 0) wi = 0; gsl_vector_set (t, i, sqrt (wi) * yi); } gsl_blas_dgemv (CblasTrans, 1.0, A, t, 0.0, xt); /* Scale the matrix Q, Q' = Q S^-1 */ gsl_matrix_memcpy (QSI, Q); { double alpha0 = gsl_vector_get (S, 0); p_eff = 0; for (j = 0; j < p; j++) { gsl_vector_view column = gsl_matrix_column (QSI, j); double alpha = gsl_vector_get (S, j); if (alpha <= tol * alpha0) { alpha = 0.0; } else { alpha = 1.0 / alpha; p_eff++; } gsl_vector_scale (&column.vector, alpha); } *rank = p_eff; } gsl_vector_set_zero (c); /* Solution */ gsl_blas_dgemv (CblasNoTrans, 1.0, QSI, xt, 0.0, c); /* Unscale the balancing factors */ gsl_vector_div (c, D); /* Form covariance matrix cov = (Q S^-1) (Q S^-1)^T */ for (i = 0; i < p; i++) { gsl_vector_view row_i = gsl_matrix_row (QSI, i); double d_i = gsl_vector_get (D, i); for (j = i; j < p; j++) { gsl_vector_view row_j = gsl_matrix_row (QSI, j); double d_j = gsl_vector_get (D, j); double s; gsl_blas_ddot (&row_i.vector, &row_j.vector, &s); gsl_matrix_set (cov, i, j, s / (d_i * d_j)); gsl_matrix_set (cov, j, i, s / (d_i * d_j)); } } /* Compute chisq, from residual r = y - X c */ { double r2 = 0; for (i = 0; i < n; i++) { double yi = gsl_vector_get (y, i); double wi = gsl_vector_get (w, i); gsl_vector_const_view row = gsl_matrix_const_row (X, i); double y_est, ri; gsl_blas_ddot (&row.vector, c, &y_est); ri = yi - y_est; r2 += wi * ri * ri; } *chisq = r2; } return GSL_SUCCESS; } } int gsl_multifit_linear_est (const gsl_vector * x, const gsl_vector * c, const gsl_matrix * cov, double *y, double *y_err) { if (x->size != c->size) { GSL_ERROR ("number of parameters c does not match number of observations x", GSL_EBADLEN); } else if (cov->size1 != cov->size2) { GSL_ERROR ("covariance matrix is not square", GSL_ENOTSQR); } else if (c->size != cov->size1) { GSL_ERROR ("number of parameters c does not match size of covariance matrix cov", GSL_EBADLEN); } else { size_t i, j; double var = 0; gsl_blas_ddot(x, c, y); /* y = x.c */ /* var = x' cov x */ for (i = 0; i < x->size; i++) { const double xi = gsl_vector_get (x, i); var += xi * xi * gsl_matrix_get (cov, i, i); for (j = 0; j < i; j++) { const double xj = gsl_vector_get (x, j); var += 2 * xi * xj * gsl_matrix_get (cov, i, j); } } *y_err = sqrt (var); return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_sf_transport.h0000664000176700017670000000366611705263724020120 0ustar paulpaul/* specfunc/gsl_sf_transport.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_TRANSPORT_H__ #define __GSL_SF_TRANSPORT_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Transport function: * J(n,x) := Integral[ t^n e^t /(e^t - 1)^2, {t,0,x}] */ /* J(2,x) * * exceptions: GSL_EDOM */ int gsl_sf_transport_2_e(const double x, gsl_sf_result * result); double gsl_sf_transport_2(const double x); /* J(3,x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_transport_3_e(const double x, gsl_sf_result * result); double gsl_sf_transport_3(const double x); /* J(4,x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_transport_4_e(const double x, gsl_sf_result * result); double gsl_sf_transport_4(const double x); /* J(5,x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_transport_5_e(const double x, gsl_sf_result * result); double gsl_sf_transport_5(const double x); __END_DECLS #endif /* __GSL_SF_TRANSPORT_H__ */ sources_5316/external/gsl/gsl_specfunc__bessel_amp_phase.c0000664000176700017670000001106211723710247022670 0ustar paulpaul/* specfunc/bessel_amp_phase.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__bessel_amp_phase.h" /* chebyshev expansions for amplitude and phase functions used in bessel evaluations These are the same for J0,Y0 and for J1,Y1, so they sit outside those functions. */ static double bm0_data[21] = { 0.09284961637381644, -0.00142987707403484, 0.00002830579271257, -0.00000143300611424, 0.00000012028628046, -0.00000001397113013, 0.00000000204076188, -0.00000000035399669, 0.00000000007024759, -0.00000000001554107, 0.00000000000376226, -0.00000000000098282, 0.00000000000027408, -0.00000000000008091, 0.00000000000002511, -0.00000000000000814, 0.00000000000000275, -0.00000000000000096, 0.00000000000000034, -0.00000000000000012, 0.00000000000000004 }; const cheb_series _gsl_sf_bessel_amp_phase_bm0_cs = { bm0_data, 20, -1, 1, 10 }; static double bth0_data[24] = { -0.24639163774300119, 0.001737098307508963, -0.000062183633402968, 0.000004368050165742, -0.000000456093019869, 0.000000062197400101, -0.000000010300442889, 0.000000001979526776, -0.000000000428198396, 0.000000000102035840, -0.000000000026363898, 0.000000000007297935, -0.000000000002144188, 0.000000000000663693, -0.000000000000215126, 0.000000000000072659, -0.000000000000025465, 0.000000000000009229, -0.000000000000003448, 0.000000000000001325, -0.000000000000000522, 0.000000000000000210, -0.000000000000000087, 0.000000000000000036 }; const cheb_series _gsl_sf_bessel_amp_phase_bth0_cs = { bth0_data, 23, -1, 1, 12 }; static double bm1_data[21] = { 0.1047362510931285, 0.00442443893702345, -0.00005661639504035, 0.00000231349417339, -0.00000017377182007, 0.00000001893209930, -0.00000000265416023, 0.00000000044740209, -0.00000000008691795, 0.00000000001891492, -0.00000000000451884, 0.00000000000116765, -0.00000000000032265, 0.00000000000009450, -0.00000000000002913, 0.00000000000000939, -0.00000000000000315, 0.00000000000000109, -0.00000000000000039, 0.00000000000000014, -0.00000000000000005, }; const cheb_series _gsl_sf_bessel_amp_phase_bm1_cs = { bm1_data, 20, -1, 1, 10 }; static double bth1_data[24] = { 0.74060141026313850, -0.004571755659637690, 0.000119818510964326, -0.000006964561891648, 0.000000655495621447, -0.000000084066228945, 0.000000013376886564, -0.000000002499565654, 0.000000000529495100, -0.000000000124135944, 0.000000000031656485, -0.000000000008668640, 0.000000000002523758, -0.000000000000775085, 0.000000000000249527, -0.000000000000083773, 0.000000000000029205, -0.000000000000010534, 0.000000000000003919, -0.000000000000001500, 0.000000000000000589, -0.000000000000000237, 0.000000000000000097, -0.000000000000000040, }; const cheb_series _gsl_sf_bessel_amp_phase_bth1_cs = { bth1_data, 23, -1, 1, 12 }; int gsl_sf_bessel_asymp_Mnu_e(const double nu, const double x, double * result) { const double r = 2.0*nu/x; const double r2 = r*r; const double x2 = x*x; const double term1 = (r2-1.0/x2)/8.0; const double term2 = (r2-1.0/x2)*(r2-9.0/x2)*3.0/128.0; const double Mnu2_c = 2.0/(M_PI) * (1.0 + term1 + term2); *result = sqrt(Mnu2_c)/sqrt(x); /* will never underflow this way */ return GSL_SUCCESS; } int gsl_sf_bessel_asymp_thetanu_corr_e(const double nu, const double x, double * result) { const double r = 2.0*nu/x; const double r2 = r*r; const double x2 = x*x; const double term1 = x*(r2 - 1.0/x2)/8.0; const double term2 = x*(r2 - 1.0/x2)*(r2 - 25.0/x2)/384.0; *result = (-0.25*M_PI + term1 + term2); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_specfunc__bessel_K1.c0000664000176700017670000001402611723710247021211 0ustar paulpaul/* specfunc/bessel_K1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besk1(), besk1e() */ /* chebyshev expansions series for bk1 on the interval 0. to 4.00000d+00 with weighted error 7.02e-18 log weighted error 17.15 significant figures required 16.73 decimal places required 17.67 series for ak1 on the interval 1.25000d-01 to 5.00000d-01 with weighted error 6.06e-17 log weighted error 16.22 significant figures required 15.41 decimal places required 16.83 series for ak12 on the interval 0. to 1.25000d-01 with weighted error 2.58e-17 log weighted error 16.59 significant figures required 15.22 decimal places required 17.16 */ static double bk1_data[11] = { 0.0253002273389477705, -0.3531559607765448760, -0.1226111808226571480, -0.0069757238596398643, -0.0001730288957513052, -0.0000024334061415659, -0.0000000221338763073, -0.0000000001411488392, -0.0000000000006666901, -0.0000000000000024274, -0.0000000000000000070 }; static cheb_series bk1_cs = { bk1_data, 10, -1, 1, 8 }; static double ak1_data[17] = { 0.27443134069738830, 0.07571989953199368, -0.00144105155647540, 0.00006650116955125, -0.00000436998470952, 0.00000035402774997, -0.00000003311163779, 0.00000000344597758, -0.00000000038989323, 0.00000000004720819, -0.00000000000604783, 0.00000000000081284, -0.00000000000011386, 0.00000000000001654, -0.00000000000000248, 0.00000000000000038, -0.00000000000000006 }; static cheb_series ak1_cs = { ak1_data, 16, -1, 1, 9 }; static double ak12_data[14] = { 0.06379308343739001, 0.02832887813049721, -0.00024753706739052, 0.00000577197245160, -0.00000020689392195, 0.00000000973998344, -0.00000000055853361, 0.00000000003732996, -0.00000000000282505, 0.00000000000023720, -0.00000000000002176, 0.00000000000000215, -0.00000000000000022, 0.00000000000000002 }; static cheb_series ak12_cs = { ak12_data, 13, -1, 1, 7 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_K1_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*GSL_DBL_MIN) { OVERFLOW_ERROR(result); } else if(x <= 2.0) { const double lx = log(x); const double ex = exp(x); int stat_I1; gsl_sf_result I1; gsl_sf_result c; cheb_eval_e(&bk1_cs, 0.5*x*x-1.0, &c); stat_I1 = gsl_sf_bessel_I1_e(x, &I1); result->val = ex * ((lx-M_LN2)*I1.val + (0.75 + c.val)/x); result->err = ex * (c.err/x + fabs(lx)*I1.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_I1; } else if(x <= 8.0) { const double sx = sqrt(x); gsl_sf_result c; cheb_eval_e(&ak1_cs, (16.0/x-5.0)/3.0, &c); result->val = (1.25 + c.val) / sx; result->err = c.err / sx; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sx = sqrt(x); gsl_sf_result c; cheb_eval_e(&ak12_cs, 16.0/x-1.0, &c); result->val = (1.25 + c.val) / sx; result->err = c.err / sx; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_K1_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*GSL_DBL_MIN) { OVERFLOW_ERROR(result); } else if(x <= 2.0) { const double lx = log(x); int stat_I1; gsl_sf_result I1; gsl_sf_result c; cheb_eval_e(&bk1_cs, 0.5*x*x-1.0, &c); stat_I1 = gsl_sf_bessel_I1_e(x, &I1); result->val = (lx-M_LN2)*I1.val + (0.75 + c.val)/x; result->err = c.err/x + fabs(lx)*I1.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_I1; } else { gsl_sf_result K1_scaled; int stat_K1 = gsl_sf_bessel_K1_scaled_e(x, &K1_scaled); int stat_e = gsl_sf_exp_mult_err_e(-x, 0.0, K1_scaled.val, K1_scaled.err, result); result->err = fabs(result->val) * (GSL_DBL_EPSILON*fabs(x) + K1_scaled.err/K1_scaled.val); return GSL_ERROR_SELECT_2(stat_e, stat_K1); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_K1_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_K1_scaled_e(x, &result)); } double gsl_sf_bessel_K1(const double x) { EVAL_RESULT(gsl_sf_bessel_K1_e(x, &result)); } sources_5316/external/gsl/gsl_vector_complex_long_double.h0000664000176700017670000002145711705263724022774 0ustar paulpaul/* vector/gsl_vector_complex_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_COMPLEX_LONG_DOUBLE_H__ #define __GSL_VECTOR_COMPLEX_LONG_DOUBLE_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_check_range.h" #include "gsl_vector_long_double.h" #include "gsl_vector_complex.h" #include "gsl_block_complex_long_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; long double *data; gsl_block_complex_long_double *block; int owner; } gsl_vector_complex_long_double; typedef struct { gsl_vector_complex_long_double vector; } _gsl_vector_complex_long_double_view; typedef _gsl_vector_complex_long_double_view gsl_vector_complex_long_double_view; typedef struct { gsl_vector_complex_long_double vector; } _gsl_vector_complex_long_double_const_view; typedef const _gsl_vector_complex_long_double_const_view gsl_vector_complex_long_double_const_view; /* Allocation */ gsl_vector_complex_long_double *gsl_vector_complex_long_double_alloc (const size_t n); gsl_vector_complex_long_double *gsl_vector_complex_long_double_calloc (const size_t n); gsl_vector_complex_long_double * gsl_vector_complex_long_double_alloc_from_block (gsl_block_complex_long_double * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_complex_long_double * gsl_vector_complex_long_double_alloc_from_vector (gsl_vector_complex_long_double * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_complex_long_double_free (gsl_vector_complex_long_double * v); /* Views */ _gsl_vector_complex_long_double_view gsl_vector_complex_long_double_view_array (long double *base, size_t n); _gsl_vector_complex_long_double_view gsl_vector_complex_long_double_view_array_with_stride (long double *base, size_t stride, size_t n); _gsl_vector_complex_long_double_const_view gsl_vector_complex_long_double_const_view_array (const long double *base, size_t n); _gsl_vector_complex_long_double_const_view gsl_vector_complex_long_double_const_view_array_with_stride (const long double *base, size_t stride, size_t n); _gsl_vector_complex_long_double_view gsl_vector_complex_long_double_subvector (gsl_vector_complex_long_double *base, size_t i, size_t n); _gsl_vector_complex_long_double_view gsl_vector_complex_long_double_subvector_with_stride (gsl_vector_complex_long_double *v, size_t i, size_t stride, size_t n); _gsl_vector_complex_long_double_const_view gsl_vector_complex_long_double_const_subvector (const gsl_vector_complex_long_double *base, size_t i, size_t n); _gsl_vector_complex_long_double_const_view gsl_vector_complex_long_double_const_subvector_with_stride (const gsl_vector_complex_long_double *v, size_t i, size_t stride, size_t n); _gsl_vector_long_double_view gsl_vector_complex_long_double_real (gsl_vector_complex_long_double *v); _gsl_vector_long_double_view gsl_vector_complex_long_double_imag (gsl_vector_complex_long_double *v); _gsl_vector_long_double_const_view gsl_vector_complex_long_double_const_real (const gsl_vector_complex_long_double *v); _gsl_vector_long_double_const_view gsl_vector_complex_long_double_const_imag (const gsl_vector_complex_long_double *v); /* Operations */ gsl_complex_long_double gsl_vector_complex_long_double_get (const gsl_vector_complex_long_double * v, const size_t i); void gsl_vector_complex_long_double_set (gsl_vector_complex_long_double * v, const size_t i, gsl_complex_long_double z); gsl_complex_long_double *gsl_vector_complex_long_double_ptr (gsl_vector_complex_long_double * v, const size_t i); const gsl_complex_long_double *gsl_vector_complex_long_double_const_ptr (const gsl_vector_complex_long_double * v, const size_t i); void gsl_vector_complex_long_double_set_zero (gsl_vector_complex_long_double * v); void gsl_vector_complex_long_double_set_all (gsl_vector_complex_long_double * v, gsl_complex_long_double z); int gsl_vector_complex_long_double_set_basis (gsl_vector_complex_long_double * v, size_t i); int gsl_vector_complex_long_double_fread (FILE * stream, gsl_vector_complex_long_double * v); int gsl_vector_complex_long_double_fwrite (FILE * stream, const gsl_vector_complex_long_double * v); int gsl_vector_complex_long_double_fscanf (FILE * stream, gsl_vector_complex_long_double * v); int gsl_vector_complex_long_double_fprintf (FILE * stream, const gsl_vector_complex_long_double * v, const char *format); int gsl_vector_complex_long_double_memcpy (gsl_vector_complex_long_double * dest, const gsl_vector_complex_long_double * src); int gsl_vector_complex_long_double_reverse (gsl_vector_complex_long_double * v); int gsl_vector_complex_long_double_swap (gsl_vector_complex_long_double * v, gsl_vector_complex_long_double * w); int gsl_vector_complex_long_double_swap_elements (gsl_vector_complex_long_double * v, const size_t i, const size_t j); int gsl_vector_complex_long_double_isnull (const gsl_vector_complex_long_double * v); int gsl_vector_complex_long_double_ispos (const gsl_vector_complex_long_double * v); int gsl_vector_complex_long_double_isneg (const gsl_vector_complex_long_double * v); int gsl_vector_complex_long_double_isnonneg (const gsl_vector_complex_long_double * v); #ifdef HAVE_INLINE extern inline gsl_complex_long_double gsl_vector_complex_long_double_get (const gsl_vector_complex_long_double * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { gsl_complex_long_double zero = {{0, 0}}; GSL_ERROR_VAL ("index out of range", GSL_EINVAL, zero); } #endif return *GSL_COMPLEX_LONG_DOUBLE_AT (v, i); } extern inline void gsl_vector_complex_long_double_set (gsl_vector_complex_long_double * v, const size_t i, gsl_complex_long_double z) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif *GSL_COMPLEX_LONG_DOUBLE_AT (v, i) = z; } extern inline gsl_complex_long_double * gsl_vector_complex_long_double_ptr (gsl_vector_complex_long_double * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return GSL_COMPLEX_LONG_DOUBLE_AT (v, i); } extern inline const gsl_complex_long_double * gsl_vector_complex_long_double_const_ptr (const gsl_vector_complex_long_double * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return GSL_COMPLEX_LONG_DOUBLE_AT (v, i); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_COMPLEX_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_rng__mt.c0000664000176700017670000001463711723710247017011 0ustar paulpaul/* This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA Original implementation was copyright (C) 1997 Makoto Matsumoto and Takuji Nishimura. Coded by Takuji Nishimura, considering the suggestions by Topher Cooper and Marc Rieffel in July-Aug. 1997, "A C-program for MT19937: Integer version (1998/4/6)" This implementation copyright (C) 1998 Brian Gough. I reorganized the code to use the module framework of GSL. The license on this implementation was changed from LGPL to GPL, following paragraph 3 of the LGPL, version 2. Update: The seeding procedure has been updated to match the 10/99 release of MT19937. Update: The seeding procedure has been updated again to match the 2002 release of MT19937 The original code included the comment: "When you use this, send an email to: matumoto@math.keio.ac.jp with an appropriate reference to your work". Makoto Matsumoto has a web page with more information about the generator, http://www.math.keio.ac.jp/~matumoto/emt.html. The paper below has details of the algorithm. From: Makoto Matsumoto and Takuji Nishimura, "Mersenne Twister: A 623-dimensionally equidistributerd uniform pseudorandom number generator". ACM Transactions on Modeling and Computer Simulation, Vol. 8, No. 1 (Jan. 1998), Pages 3-30 You can obtain the paper directly from Makoto Matsumoto's web page. The period of this generator is 2^{19937} - 1. */ #include "gsl__config.h" #include #include "gsl_rng.h" static inline unsigned long int mt_get (void *vstate); static double mt_get_double (void *vstate); static void mt_set (void *state, unsigned long int s); #define N 624 /* Period parameters */ #define M 397 /* most significant w-r bits */ static const unsigned long UPPER_MASK = 0x80000000UL; /* least significant r bits */ static const unsigned long LOWER_MASK = 0x7fffffffUL; typedef struct { unsigned long mt[N]; int mti; } mt_state_t; static inline unsigned long mt_get (void *vstate) { mt_state_t *state = (mt_state_t *) vstate; unsigned long k ; unsigned long int *const mt = state->mt; #define MAGIC(y) (((y)&0x1) ? 0x9908b0dfUL : 0) if (state->mti >= N) { /* generate N words at one time */ int kk; for (kk = 0; kk < N - M; kk++) { unsigned long y = (mt[kk] & UPPER_MASK) | (mt[kk + 1] & LOWER_MASK); mt[kk] = mt[kk + M] ^ (y >> 1) ^ MAGIC(y); } for (; kk < N - 1; kk++) { unsigned long y = (mt[kk] & UPPER_MASK) | (mt[kk + 1] & LOWER_MASK); mt[kk] = mt[kk + (M - N)] ^ (y >> 1) ^ MAGIC(y); } { unsigned long y = (mt[N - 1] & UPPER_MASK) | (mt[0] & LOWER_MASK); mt[N - 1] = mt[M - 1] ^ (y >> 1) ^ MAGIC(y); } state->mti = 0; } /* Tempering */ k = mt[state->mti]; k ^= (k >> 11); k ^= (k << 7) & 0x9d2c5680UL; k ^= (k << 15) & 0xefc60000UL; k ^= (k >> 18); state->mti++; return k; } static double mt_get_double (void * vstate) { return mt_get (vstate) / 4294967296.0 ; } static void mt_set (void *vstate, unsigned long int s) { mt_state_t *state = (mt_state_t *) vstate; int i; if (s == 0) s = 4357; /* the default seed is 4357 */ state->mt[0]= s & 0xffffffffUL; for (i = 1; i < N; i++) { /* See Knuth's "Art of Computer Programming" Vol. 2, 3rd Ed. p.106 for multiplier. */ state->mt[i] = (1812433253UL * (state->mt[i-1] ^ (state->mt[i-1] >> 30)) + i); state->mt[i] &= 0xffffffffUL; } state->mti = i; } static void mt_1999_set (void *vstate, unsigned long int s) { mt_state_t *state = (mt_state_t *) vstate; int i; if (s == 0) s = 4357; /* the default seed is 4357 */ /* This is the October 1999 version of the seeding procedure. It was updated by the original developers to avoid the periodicity in the simple congruence originally used. Note that an ANSI-C unsigned long integer arithmetic is automatically modulo 2^32 (or a higher power of two), so we can safely ignore overflow. */ #define LCG(x) ((69069 * x) + 1) &0xffffffffUL for (i = 0; i < N; i++) { state->mt[i] = s & 0xffff0000UL; s = LCG(s); state->mt[i] |= (s &0xffff0000UL) >> 16; s = LCG(s); } state->mti = i; } /* This is the original version of the seeding procedure, no longer used but available for compatibility with the original MT19937. */ static void mt_1998_set (void *vstate, unsigned long int s) { mt_state_t *state = (mt_state_t *) vstate; int i; if (s == 0) s = 4357; /* the default seed is 4357 */ state->mt[0] = s & 0xffffffffUL; #define LCG1998(n) ((69069 * n) & 0xffffffffUL) for (i = 1; i < N; i++) state->mt[i] = LCG1998 (state->mt[i - 1]); state->mti = i; } static const gsl_rng_type mt_type = {"mt19937", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (mt_state_t), &mt_set, &mt_get, &mt_get_double}; static const gsl_rng_type mt_1999_type = {"mt19937_1999", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (mt_state_t), &mt_1999_set, &mt_get, &mt_get_double}; static const gsl_rng_type mt_1998_type = {"mt19937_1998", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (mt_state_t), &mt_1998_set, &mt_get, &mt_get_double}; const gsl_rng_type *gsl_rng_mt19937 = &mt_type; const gsl_rng_type *gsl_rng_mt19937_1999 = &mt_1999_type; const gsl_rng_type *gsl_rng_mt19937_1998 = &mt_1998_type; /* MT19937 is the default generator, so define that here too */ const gsl_rng_type *gsl_rng_default = &mt_type; unsigned long int gsl_rng_default_seed = 0; sources_5316/external/gsl/gsl_nan.h0000664000176700017670000000246311705263724016142 0ustar paulpaul/* gsl_nan.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_NAN_H__ #define __GSL_NAN_H__ #ifdef INFINITY # define GSL_POSINF INFINITY # define GSL_NEGINF (-INFINITY) #elif defined(HUGE_VAL) # define GSL_POSINF HUGE_VAL # define GSL_NEGINF (-HUGE_VAL) #else # define GSL_POSINF (gsl_posinf()) # define GSL_NEGINF (gsl_neginf()) #endif #ifdef NAN # define GSL_NAN NAN #elif defined(INFINITY) # define GSL_NAN (INFINITY/INFINITY) #else # define GSL_NAN (gsl_nan()) #endif #define GSL_POSZERO (+0) #define GSL_NEGZERO (-0) #endif /* __GSL_NAN_H__ */ sources_5316/external/gsl/gsl_statistics__variance.c0000664000176700017670000000306311723710247021554 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__variance_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_randist__levy.c0000664000176700017670000000723011723710247020215 0ustar paulpaul/* randist/levy.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The stable Levy probability distributions have the form p(x) dx = (1/(2 pi)) \int dt exp(- it x - |c t|^alpha) with 0 < alpha <= 2. For alpha = 1, we get the Cauchy distribution For alpha = 2, we get the Gaussian distribution with sigma = sqrt(2) c. Fromn Chapter 5 of Bratley, Fox and Schrage "A Guide to Simulation". The original reference given there is, J.M. Chambers, C.L. Mallows and B. W. Stuck. "A method for simulating stable random variates". Journal of the American Statistical Association, JASA 71 340-344 (1976). */ double gsl_ran_levy (const gsl_rng * r, const double c, const double alpha) { double u, v, t, s; u = M_PI * (gsl_rng_uniform_pos (r) - 0.5); if (alpha == 1) /* cauchy case */ { t = tan (u); return c * t; } do { v = gsl_ran_exponential (r, 1.0); } while (v == 0); if (alpha == 2) /* gaussian case */ { t = 2 * sin (u) * sqrt(v); return c * t; } /* general case */ t = sin (alpha * u) / pow (cos (u), 1 / alpha); s = pow (cos ((1 - alpha) * u) / v, (1 - alpha) / alpha); return c * t * s; } /* The following routine for the skew-symmetric case was provided by Keith Briggs. The stable Levy probability distributions have the form 2*pi* p(x) dx = \int dt exp(mu*i*t-|sigma*t|^alpha*(1-i*beta*sign(t)*tan(pi*alpha/2))) for alpha!=1 = \int dt exp(mu*i*t-|sigma*t|^alpha*(1+i*beta*sign(t)*2/pi*log(|t|))) for alpha==1 with 00. For beta=0, sigma=c, mu=0, we get gsl_ran_levy above. For alpha = 1, beta=0, we get the Lorentz distribution For alpha = 2, beta=0, we get the Gaussian distribution See A. Weron and R. Weron: Computer simulation of Lévy alpha-stable variables and processes, preprint Technical University of Wroclaw. http://www.im.pwr.wroc.pl/~hugo/Publications.html */ double gsl_ran_levy_skew (const gsl_rng * r, const double c, const double alpha, const double beta) { double V, W, X; if (beta == 0) /* symmetric case */ { return gsl_ran_levy (r, c, alpha); } V = M_PI * (gsl_rng_uniform_pos (r) - 0.5); do { W = gsl_ran_exponential (r, 1.0); } while (W == 0); if (alpha == 1) { X = ((M_PI_2 + beta * V) * tan (V) - beta * log (M_PI_2 * W * cos (V) / (M_PI_2 + beta * V))) / M_PI_2; return c * (X + beta * log (c) / M_PI_2); } else { double t = beta * tan (M_PI_2 * alpha); double B = atan (t) / alpha; double S = pow (1 + t * t, 1/(2 * alpha)); X = S * sin (alpha * (V + B)) / pow (cos (V), 1 / alpha) * pow (cos (V - alpha * (V + B)) / W, (1 - alpha) / alpha); return c * X; } } sources_5316/external/gsl/gsl_cblas__csscal.c0000664000176700017670000000034311723710247020124 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_csscal (const int N, const float alpha, void *X, const int incX) { #define BASE float #include "gsl_cblas__source_scal_c_s.h" #undef BASE } sources_5316/external/gsl/gsl_matrix_complex_double.h0000664000176700017670000002736311705263724021761 0ustar paulpaul/* matrix/gsl_matrix_complex_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_COMPLEX_DOUBLE_H__ #define __GSL_MATRIX_COMPLEX_DOUBLE_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_check_range.h" #include "gsl_vector_complex_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; double * data; gsl_block_complex * block; int owner; } gsl_matrix_complex ; typedef struct { gsl_matrix_complex matrix; } _gsl_matrix_complex_view; typedef _gsl_matrix_complex_view gsl_matrix_complex_view; typedef struct { gsl_matrix_complex matrix; } _gsl_matrix_complex_const_view; typedef const _gsl_matrix_complex_const_view gsl_matrix_complex_const_view; /* Allocation */ gsl_matrix_complex * gsl_matrix_complex_alloc (const size_t n1, const size_t n2); gsl_matrix_complex * gsl_matrix_complex_calloc (const size_t n1, const size_t n2); gsl_matrix_complex * gsl_matrix_complex_alloc_from_block (gsl_block_complex * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_complex * gsl_matrix_complex_alloc_from_matrix (gsl_matrix_complex * b, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_complex * gsl_vector_complex_alloc_row_from_matrix (gsl_matrix_complex * m, const size_t i); gsl_vector_complex * gsl_vector_complex_alloc_col_from_matrix (gsl_matrix_complex * m, const size_t j); void gsl_matrix_complex_free (gsl_matrix_complex * m); /* Views */ _gsl_matrix_complex_view gsl_matrix_complex_submatrix (gsl_matrix_complex * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_complex_view gsl_matrix_complex_row (gsl_matrix_complex * m, const size_t i); _gsl_vector_complex_view gsl_matrix_complex_column (gsl_matrix_complex * m, const size_t j); _gsl_vector_complex_view gsl_matrix_complex_diagonal (gsl_matrix_complex * m); _gsl_vector_complex_view gsl_matrix_complex_subdiagonal (gsl_matrix_complex * m, const size_t k); _gsl_vector_complex_view gsl_matrix_complex_superdiagonal (gsl_matrix_complex * m, const size_t k); _gsl_vector_complex_view gsl_matrix_complex_subrow (gsl_matrix_complex * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_complex_view gsl_matrix_complex_subcolumn (gsl_matrix_complex * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_complex_view gsl_matrix_complex_view_array (double * base, const size_t n1, const size_t n2); _gsl_matrix_complex_view gsl_matrix_complex_view_array_with_tda (double * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_complex_view gsl_matrix_complex_view_vector (gsl_vector_complex * v, const size_t n1, const size_t n2); _gsl_matrix_complex_view gsl_matrix_complex_view_vector_with_tda (gsl_vector_complex * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_complex_const_view gsl_matrix_complex_const_submatrix (const gsl_matrix_complex * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_complex_const_view gsl_matrix_complex_const_row (const gsl_matrix_complex * m, const size_t i); _gsl_vector_complex_const_view gsl_matrix_complex_const_column (const gsl_matrix_complex * m, const size_t j); _gsl_vector_complex_const_view gsl_matrix_complex_const_diagonal (const gsl_matrix_complex * m); _gsl_vector_complex_const_view gsl_matrix_complex_const_subdiagonal (const gsl_matrix_complex * m, const size_t k); _gsl_vector_complex_const_view gsl_matrix_complex_const_superdiagonal (const gsl_matrix_complex * m, const size_t k); _gsl_vector_complex_const_view gsl_matrix_complex_const_subrow (const gsl_matrix_complex * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_complex_const_view gsl_matrix_complex_const_subcolumn (const gsl_matrix_complex * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_complex_const_view gsl_matrix_complex_const_view_array (const double * base, const size_t n1, const size_t n2); _gsl_matrix_complex_const_view gsl_matrix_complex_const_view_array_with_tda (const double * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_complex_const_view gsl_matrix_complex_const_view_vector (const gsl_vector_complex * v, const size_t n1, const size_t n2); _gsl_matrix_complex_const_view gsl_matrix_complex_const_view_vector_with_tda (const gsl_vector_complex * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ gsl_complex gsl_matrix_complex_get(const gsl_matrix_complex * m, const size_t i, const size_t j); void gsl_matrix_complex_set(gsl_matrix_complex * m, const size_t i, const size_t j, const gsl_complex x); gsl_complex * gsl_matrix_complex_ptr(gsl_matrix_complex * m, const size_t i, const size_t j); const gsl_complex * gsl_matrix_complex_const_ptr(const gsl_matrix_complex * m, const size_t i, const size_t j); void gsl_matrix_complex_set_zero (gsl_matrix_complex * m); void gsl_matrix_complex_set_identity (gsl_matrix_complex * m); void gsl_matrix_complex_set_all (gsl_matrix_complex * m, gsl_complex x); int gsl_matrix_complex_fread (FILE * stream, gsl_matrix_complex * m) ; int gsl_matrix_complex_fwrite (FILE * stream, const gsl_matrix_complex * m) ; int gsl_matrix_complex_fscanf (FILE * stream, gsl_matrix_complex * m); int gsl_matrix_complex_fprintf (FILE * stream, const gsl_matrix_complex * m, const char * format); int gsl_matrix_complex_memcpy(gsl_matrix_complex * dest, const gsl_matrix_complex * src); int gsl_matrix_complex_swap(gsl_matrix_complex * m1, gsl_matrix_complex * m2); int gsl_matrix_complex_swap_rows(gsl_matrix_complex * m, const size_t i, const size_t j); int gsl_matrix_complex_swap_columns(gsl_matrix_complex * m, const size_t i, const size_t j); int gsl_matrix_complex_swap_rowcol(gsl_matrix_complex * m, const size_t i, const size_t j); int gsl_matrix_complex_transpose (gsl_matrix_complex * m); int gsl_matrix_complex_transpose_memcpy (gsl_matrix_complex * dest, const gsl_matrix_complex * src); int gsl_matrix_complex_isnull (const gsl_matrix_complex * m); int gsl_matrix_complex_ispos (const gsl_matrix_complex * m); int gsl_matrix_complex_isneg (const gsl_matrix_complex * m); int gsl_matrix_complex_isnonneg (const gsl_matrix_complex * m); int gsl_matrix_complex_add (gsl_matrix_complex * a, const gsl_matrix_complex * b); int gsl_matrix_complex_sub (gsl_matrix_complex * a, const gsl_matrix_complex * b); int gsl_matrix_complex_mul_elements (gsl_matrix_complex * a, const gsl_matrix_complex * b); int gsl_matrix_complex_div_elements (gsl_matrix_complex * a, const gsl_matrix_complex * b); int gsl_matrix_complex_scale (gsl_matrix_complex * a, const gsl_complex x); int gsl_matrix_complex_add_constant (gsl_matrix_complex * a, const gsl_complex x); int gsl_matrix_complex_add_diagonal (gsl_matrix_complex * a, const gsl_complex x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_complex_get_row(gsl_vector_complex * v, const gsl_matrix_complex * m, const size_t i); int gsl_matrix_complex_get_col(gsl_vector_complex * v, const gsl_matrix_complex * m, const size_t j); int gsl_matrix_complex_set_row(gsl_matrix_complex * m, const size_t i, const gsl_vector_complex * v); int gsl_matrix_complex_set_col(gsl_matrix_complex * m, const size_t j, const gsl_vector_complex * v); #ifdef HAVE_INLINE extern inline gsl_complex gsl_matrix_complex_get(const gsl_matrix_complex * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK gsl_complex zero = {{0,0}}; if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, zero) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, zero) ; } #endif return *(gsl_complex *)(m->data + 2*(i * m->tda + j)) ; } extern inline void gsl_matrix_complex_set(gsl_matrix_complex * m, const size_t i, const size_t j, const gsl_complex x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif *(gsl_complex *)(m->data + 2*(i * m->tda + j)) = x ; } extern inline gsl_complex * gsl_matrix_complex_ptr(gsl_matrix_complex * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (gsl_complex *)(m->data + 2*(i * m->tda + j)) ; } extern inline const gsl_complex * gsl_matrix_complex_const_ptr(const gsl_matrix_complex * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const gsl_complex *)(m->data + 2*(i * m->tda + j)) ; } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_MATRIX_COMPLEX_DOUBLE_H__ */ sources_5316/external/gsl/gsl_rng__uni32.c0000664000176700017670000001406411723710247017323 0ustar paulpaul/* rng/uni32.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /** This is a lagged Fibonacci generator which supposedly excellent statistical properties (I do not concur) I got it from the net and translated into C. * ====================================================================== * NIST Guide to Available Math Software. * Fullsource for module UNI from package CMLIB. * Retrieved from CAMSUN on Tue Oct 8 14:04:10 1996. * ====================================================================== C***BEGIN PROLOGUE UNI C***DATE WRITTEN 810915 C***REVISION DATE 830805 C***CATEGORY NO. L6A21 C***KEYWORDS RANDOM NUMBERS, UNIFORM RANDOM NUMBERS C***AUTHOR BLUE, JAMES, SCIENTIFIC COMPUTING DIVISION, NBS C KAHANER, DAVID, SCIENTIFIC COMPUTING DIVISION, NBS C MARSAGLIA, GEORGE, COMPUTER SCIENCE DEPT., WASH STATE UNIV C C***PURPOSE THIS ROUTINE GENERATES QUASI UNIFORM RANDOM NUMBERS ON [0,1 C AND CAN BE USED ON ANY COMPUTER WITH WHICH ALLOWS INTEGERS C AT LEAST AS LARGE AS 32767. C***DESCRIPTION C C THIS ROUTINE GENERATES QUASI UNIFORM RANDOM NUMBERS ON THE INTER C [0,1). IT CAN BE USED WITH ANY COMPUTER WHICH ALLOWS C INTEGERS AT LEAST AS LARGE AS 32767. C C C USE C FIRST TIME.... C Z = UNI(JD) C HERE JD IS ANY N O N - Z E R O INTEGER. C THIS CAUSES INITIALIZATION OF THE PROGRAM C AND THE FIRST RANDOM NUMBER TO BE RETURNED AS Z. C SUBSEQUENT TIMES... C Z = UNI(0) C CAUSES THE NEXT RANDOM NUMBER TO BE RETURNED AS Z. C C C.................................................................. C NOTE: USERS WHO WISH TO TRANSPORT THIS PROGRAM FROM ONE COMPUTER C TO ANOTHER SHOULD READ THE FOLLOWING INFORMATION..... C C MACHINE DEPENDENCIES... C MDIG = A LOWER BOUND ON THE NUMBER OF BINARY DIGITS AVAILABLE C FOR REPRESENTING INTEGERS, INCLUDING THE SIGN BIT. C THIS VALUE MUST BE AT LEAST 16, BUT MAY BE INCREASED C IN LINE WITH REMARK A BELOW. C C REMARKS... C A. THIS PROGRAM CAN BE USED IN TWO WAYS: C (1) TO OBTAIN REPEATABLE RESULTS ON DIFFERENT COMPUTERS, C SET 'MDIG' TO THE SMALLEST OF ITS VALUES ON EACH, OR, C (2) TO ALLOW THE LONGEST SEQUENCE OF RANDOM NUMBERS TO BE C GENERATED WITHOUT CYCLING (REPEATING) SET 'MDIG' TO THE C LARGEST POSSIBLE VALUE. C B. THE SEQUENCE OF NUMBERS GENERATED DEPENDS ON THE INITIAL C INPUT 'JD' AS WELL AS THE VALUE OF 'MDIG'. C IF MDIG=16 ONE SHOULD FIND THAT Editors Note: set the seed using 152 in order to get uni(305) -jt C THE FIRST EVALUATION C Z=UNI(305) GIVES Z=.027832881... C THE SECOND EVALUATION C Z=UNI(0) GIVES Z=.56102176... C THE THIRD EVALUATION C Z=UNI(0) GIVES Z=.41456343... C THE THOUSANDTH EVALUATION C Z=UNI(0) GIVES Z=.19797357... C C***REFERENCES MARSAGLIA G., "COMMENTS ON THE PERFECT UNIFORM RANDOM C NUMBER GENERATOR", UNPUBLISHED NOTES, WASH S. U. C***ROUTINES CALLED I1MACH,XERROR C***END PROLOGUE UNI **/ #include "gsl__config.h" #include #include "gsl_rng.h" static inline unsigned long int uni32_get (void *vstate); static double uni32_get_double (void *vstate); static void uni32_set (void *state, unsigned long int s); static const unsigned long int MDIG = 32; /* Machine digits in int */ static const unsigned long int m1 = 2147483647; /* 2^(MDIG-1) - 1 */ static const unsigned long int m2 = 65536; /* 2^(MDIG/2) */ typedef struct { int i, j; unsigned long m[17]; } uni32_state_t; static inline unsigned long uni32_get (void *vstate) { uni32_state_t *state = (uni32_state_t *) vstate; const long int i = state->i; const long int j = state->j; /* important k not be unsigned */ long int k = state->m[i] - state->m[j]; if (k < 0) k += m1; state->m[j] = k; if (i == 0) { state->i = 16; } else { (state->i)--; } if (j == 0) { state->j = 16; } else { (state->j)--; } return k; } static double uni32_get_double (void *vstate) { return uni32_get (vstate) / 2147483647.0 ; } static void uni32_set (void *vstate, unsigned long int s) { long int seed, k0, k1, j0, j1; int i; uni32_state_t *state = (uni32_state_t *) vstate; /* For this routine, the seeding is very elaborate! */ /* A flaw in this approach is that seeds 1,2 give exactly the same random number sequence! */ /*s = 2*s+1; *//* enforce seed be odd */ seed = (s < m1 ? s : m1); /* seed should be less than m1 */ seed -= (seed % 2 == 0 ? 1 : 0); k0 = 9069 % m2; k1 = 9069 / m2; j0 = seed % m2; j1 = seed / m2; for (i = 0; i < 17; i++) { seed = j0 * k0; j1 = (seed / m2 + j0 * k1 + j1 * k0) % (m2 / 2); j0 = seed % m2; state->m[i] = j0 + m2 * j1; } state->i = 4; state->j = 16; return; } static const gsl_rng_type uni32_type = {"uni32", /* name */ 2147483646, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (uni32_state_t), &uni32_set, &uni32_get, &uni32_get_double}; const gsl_rng_type *gsl_rng_uni32 = &uni32_type; sources_5316/external/gsl/gsl_cblas__cgemm.c0000664000176700017670000000073711723710247017753 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cgemm (const enum CBLAS_ORDER Order, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_TRANSPOSE TransB, const int M, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc) { #define BASE float #include "gsl_cblas__source_gemm_c.h" #undef BASE } sources_5316/external/gsl/gsl_multimin__linear_minimize.c0000664000176700017670000001413411723710247022604 0ustar paulpaul#include "gsl_math.h" #include "gsl_errno.h" #include "gsl_poly.h" /* Find a minimum in x=[0,1] of the interpolating quadratic through * (0,f0) (1,f1) with derivative fp0 at x=0. The interpolating * polynomial is q(x) = f0 + fp0 * z + (f1-f0-fp0) * z^2 */ static double interp_quad (double f0, double fp0, double f1, double zl, double zh) { double fl = f0 + zl*(fp0 + zl*(f1 - f0 -fp0)); double fh = f0 + zh*(fp0 + zh*(f1 - f0 -fp0)); double c = 2 * (f1 - f0 - fp0); /* curvature */ double zmin = zl, fmin = fl; if (fh < fmin) { zmin = zh; fmin = fh; } if (c > 0) /* positive curvature required for a minimum */ { double z = -fp0 / c; /* location of minimum */ if (z > zl && z < zh) { double f = f0 + z*(fp0 + z*(f1 - f0 -fp0)); if (f < fmin) { zmin = z; fmin = f; }; } } return zmin; } /* Find a minimum in x=[0,1] of the interpolating cubic through * (0,f0) (1,f1) with derivatives fp0 at x=0 and fp1 at x=1. * * The interpolating polynomial is: * * c(x) = f0 + fp0 * z + eta * z^2 + xi * z^3 * * where eta=3*(f1-f0)-2*fp0-fp1, xi=fp0+fp1-2*(f1-f0). */ static double cubic (double c0, double c1, double c2, double c3, double z) { return c0 + z * (c1 + z * (c2 + z * c3)); } static void check_extremum (double c0, double c1, double c2, double c3, double z, double *zmin, double *fmin) { /* could make an early return by testing curvature >0 for minimum */ double y = cubic (c0, c1, c2, c3, z); if (y < *fmin) { *zmin = z; /* accepted new point*/ *fmin = y; } } static double interp_cubic (double f0, double fp0, double f1, double fp1, double zl, double zh) { double eta = 3 * (f1 - f0) - 2 * fp0 - fp1; double xi = fp0 + fp1 - 2 * (f1 - f0); double c0 = f0, c1 = fp0, c2 = eta, c3 = xi; double zmin, fmin; double z0, z1; zmin = zl; fmin = cubic(c0, c1, c2, c3, zl); check_extremum (c0, c1, c2, c3, zh, &zmin, &fmin); { int n = gsl_poly_solve_quadratic (3 * c3, 2 * c2, c1, &z0, &z1); if (n == 2) /* found 2 roots */ { if (z0 > zl && z0 < zh) check_extremum (c0, c1, c2, c3, z0, &zmin, &fmin); if (z1 > zl && z1 < zh) check_extremum (c0, c1, c2, c3, z1, &zmin, &fmin); } else if (n == 1) /* found 1 root */ { if (z0 > zl && z0 < zh) check_extremum (c0, c1, c2, c3, z0, &zmin, &fmin); } } return zmin; } static double interpolate (double a, double fa, double fpa, double b, double fb, double fpb, double xmin, double xmax, int order) { /* Map [a,b] to [0,1] */ double z, alpha, zmin, zmax; zmin = (xmin - a) / (b - a); zmax = (xmax - a) / (b - a); if (zmin > zmax) { double tmp = zmin; zmin = zmax; zmax = tmp; }; if (order > 2 && GSL_IS_REAL(fpb)) { z = interp_cubic (fa, fpa * (b - a), fb, fpb * (b - a), zmin, zmax); } else { z = interp_quad (fa, fpa * (b - a), fb, zmin, zmax); } alpha = a + z * (b - a); return alpha; } /* recommended values from Fletcher are rho = 0.01, sigma = 0.1, tau1 = 9, tau2 = 0.05, tau3 = 0.5 */ static int minimize (gsl_function_fdf * fn, double rho, double sigma, double tau1, double tau2, double tau3, int order, double alpha1, double *alpha_new) { double f0, fp0, falpha, falpha_prev, fpalpha, fpalpha_prev, delta, alpha_next; double alpha = alpha1, alpha_prev = 0.0; double a, b, fa, fb, fpa, fpb; const size_t bracket_iters = 100, section_iters = 100; size_t i = 0; GSL_FN_FDF_EVAL_F_DF (fn, 0.0, &f0, &fp0); falpha_prev = f0; fpalpha_prev = fp0; /* Avoid uninitialized variables morning */ a = 0.0; b = alpha; fa = f0; fb = 0.0; fpa = fp0; fpb = 0.0; /* Begin bracketing */ while (i++ < bracket_iters) { falpha = GSL_FN_FDF_EVAL_F (fn, alpha); /* Fletcher's rho test */ if (falpha > f0 + alpha * rho * fp0 || falpha >= falpha_prev) { a = alpha_prev; fa = falpha_prev; fpa = fpalpha_prev; b = alpha; fb = falpha; fpb = GSL_NAN; break; /* goto sectioning */ } fpalpha = GSL_FN_FDF_EVAL_DF (fn, alpha); /* Fletcher's sigma test */ if (fabs (fpalpha) <= -sigma * fp0) { *alpha_new = alpha; return GSL_SUCCESS; } if (fpalpha >= 0) { a = alpha; fa = falpha; fpa = fpalpha; b = alpha_prev; fb = falpha_prev; fpb = fpalpha_prev; break; /* goto sectioning */ } delta = alpha - alpha_prev; { double lower = alpha + delta; double upper = alpha + tau1 * delta; alpha_next = interpolate (alpha_prev, falpha_prev, fpalpha_prev, alpha, falpha, fpalpha, lower, upper, order); } alpha_prev = alpha; falpha_prev = falpha; fpalpha_prev = fpalpha; alpha = alpha_next; } /* Sectioning of bracket [a,b] */ while (i++ < section_iters) { delta = b - a; { double lower = a + tau2 * delta; double upper = b - tau3 * delta; alpha = interpolate (a, fa, fpa, b, fb, fpb, lower, upper, order); } falpha = GSL_FN_FDF_EVAL_F (fn, alpha); if ((a-alpha)*fpa <= GSL_DBL_EPSILON) { /* roundoff prevents progress */ return GSL_ENOPROG; }; if (falpha > f0 + rho * alpha * fp0 || falpha >= fa) { /* a_next = a; */ b = alpha; fb = falpha; fpb = GSL_NAN; } else { fpalpha = GSL_FN_FDF_EVAL_DF (fn, alpha); if (fabs(fpalpha) <= -sigma * fp0) { *alpha_new = alpha; return GSL_SUCCESS; /* terminate */ } if ( ((b-a) >= 0 && fpalpha >= 0) || ((b-a) <=0 && fpalpha <= 0)) { b = a; fb = fa; fpb = fpa; a = alpha; fa = falpha; fpa = fpalpha; } else { a = alpha; fa = falpha; fpa = fpalpha; } } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_permute_double.h0000664000176700017670000000262011705263724020374 0ustar paulpaul/* permutation/gsl_permute_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_DOUBLE_H__ #define __GSL_PERMUTE_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute (const size_t * p, double * data, const size_t stride, const size_t n); int gsl_permute_inverse (const size_t * p, double * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_DOUBLE_H__ */ sources_5316/external/gsl/gsl_cblas__daxpy.c0000664000176700017670000000042211723710247017777 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_daxpy (const int N, const double alpha, const double *X, const int incX, double *Y, const int incY) { #define BASE double #include "gsl_cblas__source_axpy_r.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__bessel_Kn.c0000664000176700017670000001473111723710247021311 0ustar paulpaul/* specfunc/bessel_Kn.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_gamma.h" #include "gsl_sf_psi.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* [Abramowitz+Stegun, 9.6.11] * assumes n >= 1 */ static int bessel_Kn_scaled_small_x(const int n, const double x, gsl_sf_result * result) { int k; double y = 0.25 * x * x; double ln_x_2 = log(0.5*x); double ex = exp(x); gsl_sf_result ln_nm1_fact; double k_term; double term1, sum1, ln_pre1; double term2, sum2, pre2; gsl_sf_lnfact_e((unsigned int)(n-1), &ln_nm1_fact); ln_pre1 = -n*ln_x_2 + ln_nm1_fact.val; if(ln_pre1 > GSL_LOG_DBL_MAX - 3.0) GSL_ERROR ("error", GSL_EOVRFLW); sum1 = 1.0; k_term = 1.0; for(k=1; k<=n-1; k++) { k_term *= -y/(k * (n-k)); sum1 += k_term; } term1 = 0.5 * exp(ln_pre1) * sum1; pre2 = 0.5 * exp(n*ln_x_2); if(pre2 > 0.0) { const int KMAX = 20; gsl_sf_result psi_n; gsl_sf_result npk_fact; double yk = 1.0; double k_fact = 1.0; double psi_kp1 = -M_EULER; double psi_npkp1; gsl_sf_psi_int_e(n, &psi_n); gsl_sf_fact_e((unsigned int)n, &npk_fact); psi_npkp1 = psi_n.val + 1.0/n; sum2 = (psi_kp1 + psi_npkp1 - 2.0*ln_x_2)/npk_fact.val; for(k=1; kval = ex * (term1 + term2); result->err = ex * GSL_DBL_EPSILON * (fabs(ln_pre1)*fabs(term1) + fabs(term2)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Kn_scaled_e(int n, const double x, gsl_sf_result * result) { n = abs(n); /* K(-n, z) = K(n, z) */ /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(n == 0) { return gsl_sf_bessel_K0_scaled_e(x, result); } else if(n == 1) { return gsl_sf_bessel_K1_scaled_e(x, result); } else if(x <= 5.0) { return bessel_Kn_scaled_small_x(n, x, result); } else if(GSL_ROOT3_DBL_EPSILON * x > 0.25 * (n*n + 1)) { return gsl_sf_bessel_Knu_scaled_asympx_e((double)n, x, result); } else if(GSL_MIN(0.29/(n*n), 0.5/(n*n + x*x)) < GSL_ROOT3_DBL_EPSILON) { return gsl_sf_bessel_Knu_scaled_asymp_unif_e((double)n, x, result); } else { /* Upward recurrence. [Gradshteyn + Ryzhik, 8.471.1] */ double two_over_x = 2.0/x; gsl_sf_result r_b_jm1; gsl_sf_result r_b_j; int stat_0 = gsl_sf_bessel_K0_scaled_e(x, &r_b_jm1); int stat_1 = gsl_sf_bessel_K1_scaled_e(x, &r_b_j); double b_jm1 = r_b_jm1.val; double b_j = r_b_j.val; double b_jp1; int j; for(j=1; jval = b_j; result->err = n * (fabs(b_j) * (fabs(r_b_jm1.err/r_b_jm1.val) + fabs(r_b_j.err/r_b_j.val))); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_0, stat_1); } } int gsl_sf_bessel_Kn_e(const int n, const double x, gsl_sf_result * result) { const int status = gsl_sf_bessel_Kn_scaled_e(n, x, result); const double ex = exp(-x); result->val *= ex; result->err *= ex; result->err += x * GSL_DBL_EPSILON * fabs(result->val); return status; } int gsl_sf_bessel_Kn_scaled_array(const int nmin, const int nmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(nmin < 0 || nmax < nmin || x <= 0.0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; GSL_ERROR ("domain error", GSL_EDOM); } else if(nmax == 0) { gsl_sf_result b; int stat = gsl_sf_bessel_K0_scaled_e(x, &b); result_array[0] = b.val; return stat; } else { double two_over_x = 2.0/x; gsl_sf_result r_Knm1; gsl_sf_result r_Kn; int stat_0 = gsl_sf_bessel_Kn_scaled_e(nmin, x, &r_Knm1); int stat_1 = gsl_sf_bessel_Kn_scaled_e(nmin+1, x, &r_Kn); int stat = GSL_ERROR_SELECT_2(stat_0, stat_1); double Knp1; double Kn = r_Kn.val; double Knm1 = r_Knm1.val; int n; for(n=nmin+1; n<=nmax+1; n++) { if(Knm1 < GSL_DBL_MAX) { result_array[n-1-nmin] = Knm1; Knp1 = Knm1 + n * two_over_x * Kn; Knm1 = Kn; Kn = Knp1; } else { /* Overflow. Set the rest of the elements to * zero and bug out. * FIXME: Note: this relies on the convention * that the test x < DBL_MIN fails for x not * a number. This may be only an IEEE convention, * so the portability is unclear. */ int j; for(j=n; j<=nmax+1; j++) result_array[j-1-nmin] = 0.0; GSL_ERROR ("overflow", GSL_EOVRFLW); } } return stat; } } int gsl_sf_bessel_Kn_array(const int nmin, const int nmax, const double x, double * result_array) { int status = gsl_sf_bessel_Kn_scaled_array(nmin, nmax, x, result_array); double ex = exp(-x); int i; for(i=0; i<=nmax-nmin; i++) result_array[i] *= ex; return status; } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_Kn_scaled(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_Kn_scaled_e(n, x, &result)); } double gsl_sf_bessel_Kn(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_Kn_e(n, x, &result)); } sources_5316/external/gsl/gsl_fft__dft_source.c0000664000176700017670000000616411723710247020513 0ustar paulpaul/* fft/dft_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION(gsl_dft_complex,forward) (const BASE data[], const size_t stride, const size_t n, BASE result[]) { gsl_fft_direction sign = gsl_fft_forward; int status = FUNCTION(gsl_dft_complex,transform) (data, stride, n, result, sign); return status; } int FUNCTION(gsl_dft_complex,backward) (const BASE data[], const size_t stride, const size_t n, BASE result[]) { gsl_fft_direction sign = gsl_fft_backward; int status = FUNCTION(gsl_dft_complex,transform) (data, stride, n, result, sign); return status; } int FUNCTION(gsl_dft_complex,inverse) (const BASE data[], const size_t stride, const size_t n, BASE result[]) { gsl_fft_direction sign = gsl_fft_backward; int status = FUNCTION(gsl_dft_complex,transform) (data, stride, n, result, sign); /* normalize inverse fft with 1/n */ { const ATOMIC norm = ONE / (ATOMIC)n; size_t i; for (i = 0; i < n; i++) { REAL(result,stride,i) *= norm; IMAG(result,stride,i) *= norm; } } return status; } int FUNCTION(gsl_dft_complex,transform) (const BASE data[], const size_t stride, const size_t n, BASE result[], const gsl_fft_direction sign) { size_t i, j, exponent; const double d_theta = 2.0 * ((int) sign) * M_PI / (double) n; /* FIXME: check that input length == output length and give error */ for (i = 0; i < n; i++) { ATOMIC sum_real = 0; ATOMIC sum_imag = 0; exponent = 0; for (j = 0; j < n; j++) { double theta = d_theta * (double) exponent; /* sum = exp(i theta) * data[j] */ ATOMIC w_real = (ATOMIC) cos (theta); ATOMIC w_imag = (ATOMIC) sin (theta); ATOMIC data_real = REAL(data,stride,j); ATOMIC data_imag = IMAG(data,stride,j); sum_real += w_real * data_real - w_imag * data_imag; sum_imag += w_real * data_imag + w_imag * data_real; exponent = (exponent + i) % n; } REAL(result,stride,i) = sum_real; IMAG(result,stride,i) = sum_imag; } return 0; } sources_5316/external/gsl/gsl_permute_float.h0000664000176700017670000000262611705263724020235 0ustar paulpaul/* permutation/gsl_permute_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_FLOAT_H__ #define __GSL_PERMUTE_FLOAT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_float (const size_t * p, float * data, const size_t stride, const size_t n); int gsl_permute_float_inverse (const size_t * p, float * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_FLOAT_H__ */ sources_5316/external/gsl/gsl_sort_ushort.h0000664000176700017670000000364411705263724017763 0ustar paulpaul/* sort/gsl_sort_ushort.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_USHORT_H__ #define __GSL_SORT_USHORT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_ushort (unsigned short * data, const size_t stride, const size_t n); void gsl_sort_ushort_index (size_t * p, const unsigned short * data, const size_t stride, const size_t n); int gsl_sort_ushort_smallest (unsigned short * dest, const size_t k, const unsigned short * src, const size_t stride, const size_t n); int gsl_sort_ushort_smallest_index (size_t * p, const size_t k, const unsigned short * src, const size_t stride, const size_t n); int gsl_sort_ushort_largest (unsigned short * dest, const size_t k, const unsigned short * src, const size_t stride, const size_t n); int gsl_sort_ushort_largest_index (size_t * p, const size_t k, const unsigned short * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_USHORT_H__ */ sources_5316/external/gsl/gsl_multimin.h0000664000176700017670000001467311705263724017232 0ustar paulpaul/* multimin/gsl_multimin.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Fabrice Rossi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Modified by Tuomo Keskitalo to include fminimizer and Nelder Mead related lines */ #ifndef __GSL_MULTIMIN_H__ #define __GSL_MULTIMIN_H__ #include #include "gsl_types.h" #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_min.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Definition of an arbitrary real-valued function with gsl_vector input and */ /* parameters */ struct gsl_multimin_function_struct { double (* f) (const gsl_vector * x, void * params); size_t n; void * params; }; typedef struct gsl_multimin_function_struct gsl_multimin_function; #define GSL_MULTIMIN_FN_EVAL(F,x) (*((F)->f))(x,(F)->params) /* Definition of an arbitrary differentiable real-valued function */ /* with gsl_vector input and parameters */ struct gsl_multimin_function_fdf_struct { double (* f) (const gsl_vector * x, void * params); void (* df) (const gsl_vector * x, void * params,gsl_vector * df); void (* fdf) (const gsl_vector * x, void * params,double *f,gsl_vector * df); size_t n; void * params; }; typedef struct gsl_multimin_function_fdf_struct gsl_multimin_function_fdf; #define GSL_MULTIMIN_FN_EVAL_F(F,x) (*((F)->f))(x,(F)->params) #define GSL_MULTIMIN_FN_EVAL_DF(F,x,g) (*((F)->df))(x,(F)->params,(g)) #define GSL_MULTIMIN_FN_EVAL_F_DF(F,x,y,g) (*((F)->fdf))(x,(F)->params,(y),(g)) int gsl_multimin_diff (const gsl_multimin_function * f, const gsl_vector * x, gsl_vector * g); /* minimization of non-differentiable functions */ typedef struct { const char *name; size_t size; int (*alloc) (void *state, size_t n); int (*set) (void *state, gsl_multimin_function * f, const gsl_vector * x, double * size, const gsl_vector * step_size); int (*iterate) (void *state, gsl_multimin_function * f, gsl_vector * x, double * size, double * fval); void (*free) (void *state); } gsl_multimin_fminimizer_type; typedef struct { /* multi dimensional part */ const gsl_multimin_fminimizer_type *type; gsl_multimin_function *f; double fval; gsl_vector * x; double size; void *state; } gsl_multimin_fminimizer; gsl_multimin_fminimizer * gsl_multimin_fminimizer_alloc(const gsl_multimin_fminimizer_type *T, size_t n); int gsl_multimin_fminimizer_set (gsl_multimin_fminimizer * s, gsl_multimin_function * f, const gsl_vector * x, const gsl_vector * step_size); void gsl_multimin_fminimizer_free(gsl_multimin_fminimizer *s); const char * gsl_multimin_fminimizer_name (const gsl_multimin_fminimizer * s); int gsl_multimin_fminimizer_iterate(gsl_multimin_fminimizer *s); gsl_vector * gsl_multimin_fminimizer_x (const gsl_multimin_fminimizer * s); double gsl_multimin_fminimizer_minimum (const gsl_multimin_fminimizer * s); double gsl_multimin_fminimizer_size (const gsl_multimin_fminimizer * s); /* Convergence test functions */ int gsl_multimin_test_gradient(const gsl_vector * g,double epsabs); int gsl_multimin_test_size(const double size ,double epsabs); /* minimisation of differentiable functions */ typedef struct { const char *name; size_t size; int (*alloc) (void *state, size_t n); int (*set) (void *state, gsl_multimin_function_fdf * fdf, const gsl_vector * x, double * f, gsl_vector * gradient, double step_size, double tol); int (*iterate) (void *state,gsl_multimin_function_fdf * fdf, gsl_vector * x, double * f, gsl_vector * gradient, gsl_vector * dx); int (*restart) (void *state); void (*free) (void *state); } gsl_multimin_fdfminimizer_type; typedef struct { /* multi dimensional part */ const gsl_multimin_fdfminimizer_type *type; gsl_multimin_function_fdf *fdf; double f; gsl_vector * x; gsl_vector * gradient; gsl_vector * dx; void *state; } gsl_multimin_fdfminimizer; gsl_multimin_fdfminimizer * gsl_multimin_fdfminimizer_alloc(const gsl_multimin_fdfminimizer_type *T, size_t n); int gsl_multimin_fdfminimizer_set (gsl_multimin_fdfminimizer * s, gsl_multimin_function_fdf *fdf, const gsl_vector * x, double step_size, double tol); void gsl_multimin_fdfminimizer_free(gsl_multimin_fdfminimizer *s); const char * gsl_multimin_fdfminimizer_name (const gsl_multimin_fdfminimizer * s); int gsl_multimin_fdfminimizer_iterate(gsl_multimin_fdfminimizer *s); int gsl_multimin_fdfminimizer_restart(gsl_multimin_fdfminimizer *s); gsl_vector * gsl_multimin_fdfminimizer_x (gsl_multimin_fdfminimizer * s); gsl_vector * gsl_multimin_fdfminimizer_dx (gsl_multimin_fdfminimizer * s); gsl_vector * gsl_multimin_fdfminimizer_gradient (gsl_multimin_fdfminimizer * s); double gsl_multimin_fdfminimizer_minimum (gsl_multimin_fdfminimizer * s); GSL_VAR const gsl_multimin_fdfminimizer_type *gsl_multimin_fdfminimizer_steepest_descent; GSL_VAR const gsl_multimin_fdfminimizer_type *gsl_multimin_fdfminimizer_conjugate_pr; GSL_VAR const gsl_multimin_fdfminimizer_type *gsl_multimin_fdfminimizer_conjugate_fr; GSL_VAR const gsl_multimin_fdfminimizer_type *gsl_multimin_fdfminimizer_vector_bfgs; GSL_VAR const gsl_multimin_fdfminimizer_type *gsl_multimin_fdfminimizer_vector_bfgs2; GSL_VAR const gsl_multimin_fminimizer_type *gsl_multimin_fminimizer_nmsimplex; __END_DECLS #endif /* __GSL_MULTIMIN_H__ */ sources_5316/external/gsl/gsl_permute_vector_int.h0000664000176700017670000000264411705263724021304 0ustar paulpaul/* permutation/gsl_permute_vector_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_INT_H__ #define __GSL_PERMUTE_VECTOR_INT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_int.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_int (const gsl_permutation * p, gsl_vector_int * v); int gsl_permute_vector_int_inverse (const gsl_permutation * p, gsl_vector_int * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_INT_H__ */ sources_5316/external/gsl/gsl_cdf__exppow.c0000664000176700017670000000344611723710247017655 0ustar paulpaul/* cdf/exppow.c * * Copyright (C) 2004 Giulio Bottazzi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_cdf.h" #include "gsl_sf_gamma.h" /* The exponential power density is parametrized according to p(x) dx = (1/(2 a Gamma(1 + 1/b))) * exp(-|x/a|^b) dx so that the distribution reads / x<0 0.5 - Gamma_inc_P(1/b,|x/a|^b) P(x) = | x=0 0.5 \ x>0 0.5 + Gamma_inc_P(1/b,|x/a|^b) for x in (-infty,+infty) */ double gsl_cdf_exppow_P (const double x, const double a, const double b) { const double u = x / a; if (u < 0) { double P = 0.5 * gsl_sf_gamma_inc_Q (1.0 / b, pow (-u, b)); return P; } else { double P = 0.5 * (1.0 + gsl_sf_gamma_inc_P (1.0 / b, pow (u, b))); return P; } } double gsl_cdf_exppow_Q (const double x, const double a, const double b) { const double u = x / a; if (u < 0) { double Q = 0.5 * (1.0 + gsl_sf_gamma_inc_P (1.0 / b, pow (-u, b))); return Q; } else { double Q = 0.5 * gsl_sf_gamma_inc_Q (1.0 / b, pow (u, b)); return Q; } } sources_5316/external/gsl/gsl_statistics__median_source.c0000664000176700017670000000251411723710247022601 0ustar paulpaul/* statistics/median_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,median_from_sorted_data) (const BASE sorted_data[], const size_t stride, const size_t n) { double median ; const size_t lhs = (n - 1) / 2 ; const size_t rhs = n / 2 ; if (n == 0) return 0.0 ; if (lhs == rhs) { median = sorted_data[lhs * stride] ; } else { median = (sorted_data[lhs * stride] + sorted_data[rhs * stride])/2.0 ; } return median ; } sources_5316/external/gsl/gsl_sort_vector_uchar.h0000664000176700017670000000344411705263724021121 0ustar paulpaul/* sort/gsl_sort_vector_uchar.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_UCHAR_H__ #define __GSL_SORT_VECTOR_UCHAR_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_uchar.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_uchar (gsl_vector_uchar * v); int gsl_sort_vector_uchar_index (gsl_permutation * p, const gsl_vector_uchar * v); int gsl_sort_vector_uchar_smallest (unsigned char * dest, const size_t k, const gsl_vector_uchar * v); int gsl_sort_vector_uchar_largest (unsigned char * dest, const size_t k, const gsl_vector_uchar * v); int gsl_sort_vector_uchar_smallest_index (size_t * p, const size_t k, const gsl_vector_uchar * v); int gsl_sort_vector_uchar_largest_index (size_t * p, const size_t k, const gsl_vector_uchar * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_UCHAR_H__ */ sources_5316/external/gsl/gsl_integration__util.c0000664000176700017670000000714011723710247021072 0ustar paulpaul/* integration/util.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static inline void update (gsl_integration_workspace * workspace, double a1, double b1, double area1, double error1, double a2, double b2, double area2, double error2); static inline void retrieve (const gsl_integration_workspace * workspace, double * a, double * b, double * r, double * e); static inline void update (gsl_integration_workspace * workspace, double a1, double b1, double area1, double error1, double a2, double b2, double area2, double error2) { double * alist = workspace->alist ; double * blist = workspace->blist ; double * rlist = workspace->rlist ; double * elist = workspace->elist ; size_t * level = workspace->level ; const size_t i_max = workspace->i ; const size_t i_new = workspace->size ; const size_t new_level = workspace->level[i_max] + 1; /* append the newly-created intervals to the list */ if (error2 > error1) { alist[i_max] = a2; /* blist[maxerr] is already == b2 */ rlist[i_max] = area2; elist[i_max] = error2; level[i_max] = new_level; alist[i_new] = a1; blist[i_new] = b1; rlist[i_new] = area1; elist[i_new] = error1; level[i_new] = new_level; } else { blist[i_max] = b1; /* alist[maxerr] is already == a1 */ rlist[i_max] = area1; elist[i_max] = error1; level[i_max] = new_level; alist[i_new] = a2; blist[i_new] = b2; rlist[i_new] = area2; elist[i_new] = error2; level[i_new] = new_level; } workspace->size++; if (new_level > workspace->maximum_level) { workspace->maximum_level = new_level; } qpsrt (workspace) ; } static inline void retrieve (const gsl_integration_workspace * workspace, double * a, double * b, double * r, double * e) { const size_t i = workspace->i; double * alist = workspace->alist; double * blist = workspace->blist; double * rlist = workspace->rlist; double * elist = workspace->elist; *a = alist[i] ; *b = blist[i] ; *r = rlist[i] ; *e = elist[i] ; } static inline double sum_results (const gsl_integration_workspace * workspace); static inline double sum_results (const gsl_integration_workspace * workspace) { const double * const rlist = workspace->rlist ; const size_t n = workspace->size; size_t k; double result_sum = 0; for (k = 0; k < n; k++) { result_sum += rlist[k]; } return result_sum; } static inline int subinterval_too_small (double a1, double a2, double b2); static inline int subinterval_too_small (double a1, double a2, double b2) { const double e = GSL_DBL_EPSILON; const double u = GSL_DBL_MIN; double tmp = (1 + 100 * e) * (fabs (a2) + 1000 * u); int status = fabs (a1) <= tmp && fabs (b2) <= tmp; return status; } sources_5316/external/gsl/gsl_sort_uint.h0000664000176700017670000000360011705263724017406 0ustar paulpaul/* sort/gsl_sort_uint.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_UINT_H__ #define __GSL_SORT_UINT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_uint (unsigned int * data, const size_t stride, const size_t n); void gsl_sort_uint_index (size_t * p, const unsigned int * data, const size_t stride, const size_t n); int gsl_sort_uint_smallest (unsigned int * dest, const size_t k, const unsigned int * src, const size_t stride, const size_t n); int gsl_sort_uint_smallest_index (size_t * p, const size_t k, const unsigned int * src, const size_t stride, const size_t n); int gsl_sort_uint_largest (unsigned int * dest, const size_t k, const unsigned int * src, const size_t stride, const size_t n); int gsl_sort_uint_largest_index (size_t * p, const size_t k, const unsigned int * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_UINT_H__ */ sources_5316/external/gsl/gsl_fft__hc_main.c0000664000176700017670000001222211723710247017744 0ustar paulpaul/* fft/hc_main.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_fft_halfcomplex.h" #include "gsl_fft__hc_pass.h" int FUNCTION(gsl_fft_halfcomplex,backward) (BASE data[], const size_t stride, const size_t n, const TYPE(gsl_fft_halfcomplex_wavetable) * wavetable, TYPE(gsl_fft_real_workspace) * work) { int status = FUNCTION(gsl_fft_halfcomplex,transform) (data, stride, n, wavetable, work) ; return status ; } int FUNCTION(gsl_fft_halfcomplex,inverse) (BASE data[], const size_t stride, const size_t n, const TYPE(gsl_fft_halfcomplex_wavetable) * wavetable, TYPE(gsl_fft_real_workspace) * work) { int status = FUNCTION(gsl_fft_halfcomplex,transform) (data, stride, n, wavetable, work); if (status) { return status; } /* normalize inverse fft with 1/n */ { const double norm = 1.0 / n; size_t i; for (i = 0; i < n; i++) { data[stride*i] *= norm; } } return status; } int FUNCTION(gsl_fft_halfcomplex,transform) (BASE data[], const size_t stride, const size_t n, const TYPE(gsl_fft_halfcomplex_wavetable) * wavetable, TYPE(gsl_fft_real_workspace) * work) { BASE * const scratch = work->scratch; BASE * in; BASE * out; size_t istride, ostride ; size_t factor, product, q; size_t i; size_t nf; int state; int product_1; int tskip; TYPE(gsl_complex) *twiddle1, *twiddle2, *twiddle3, *twiddle4; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } if (n == 1) { /* FFT of one data point is the identity */ return 0; } if (n != wavetable->n) { GSL_ERROR ("wavetable does not match length of data", GSL_EINVAL); } if (n != work->n) { GSL_ERROR ("workspace does not match length of data", GSL_EINVAL); } nf = wavetable->nf; product = 1; state = 0; for (i = 0; i < nf; i++) { factor = wavetable->factor[i]; product_1 = product; product *= factor; q = n / product; tskip = (q + 1) / 2 - 1; if (state == 0) { in = data; istride = stride; out = scratch; ostride = 1; state = 1; } else { in = scratch; istride = 1; out = data; ostride = stride; state = 0; } if (factor == 2) { twiddle1 = wavetable->twiddle[i]; FUNCTION(fft_halfcomplex,pass_2) (in, istride, out, ostride, product, n, twiddle1); } else if (factor == 3) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + tskip; FUNCTION(fft_halfcomplex,pass_3) (in, istride, out, ostride, product, n, twiddle1, twiddle2); } else if (factor == 4) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + tskip; twiddle3 = twiddle2 + tskip; FUNCTION(fft_halfcomplex,pass_4) (in, istride, out, ostride, product, n, twiddle1, twiddle2, twiddle3); } else if (factor == 5) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + tskip; twiddle3 = twiddle2 + tskip; twiddle4 = twiddle3 + tskip; FUNCTION(fft_halfcomplex,pass_5) (in, istride, out, ostride, product, n, twiddle1, twiddle2, twiddle3, twiddle4); } else { twiddle1 = wavetable->twiddle[i]; FUNCTION(fft_halfcomplex,pass_n) (in, istride, out, ostride, factor, product, n, twiddle1); } } if (state == 1) /* copy results back from scratch to data */ { for (i = 0; i < n; i++) { data[stride*i] = scratch[i] ; } } return 0; } sources_5316/external/gsl/gsl_eigen__sort.c0000664000176700017670000002263111723710247017652 0ustar paulpaul/* eigen/sort.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2006, 2007 Gerard Jungman, Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman, Modified: B. Gough. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_eigen.h" #include "gsl_complex.h" #include "gsl_complex_math.h" /* The eigen_sort below is not very good, but it is simple and * self-contained. We can always implement an improved sort later. */ int gsl_eigen_symmv_sort (gsl_vector * eval, gsl_matrix * evec, gsl_eigen_sort_t sort_type) { if (evec->size1 != evec->size2) { GSL_ERROR ("eigenvector matrix must be square", GSL_ENOTSQR); } else if (eval->size != evec->size1) { GSL_ERROR ("eigenvalues must match eigenvector matrix", GSL_EBADLEN); } else { const size_t N = eval->size; size_t i; for (i = 0; i < N - 1; i++) { size_t j; size_t k = i; double ek = gsl_vector_get (eval, i); /* search for something to swap */ for (j = i + 1; j < N; j++) { int test; const double ej = gsl_vector_get (eval, j); switch (sort_type) { case GSL_EIGEN_SORT_VAL_ASC: test = (ej < ek); break; case GSL_EIGEN_SORT_VAL_DESC: test = (ej > ek); break; case GSL_EIGEN_SORT_ABS_ASC: test = (fabs (ej) < fabs (ek)); break; case GSL_EIGEN_SORT_ABS_DESC: test = (fabs (ej) > fabs (ek)); break; default: GSL_ERROR ("unrecognized sort type", GSL_EINVAL); } if (test) { k = j; ek = ej; } } if (k != i) { /* swap eigenvalues */ gsl_vector_swap_elements (eval, i, k); /* swap eigenvectors */ gsl_matrix_swap_columns (evec, i, k); } } return GSL_SUCCESS; } } int gsl_eigen_hermv_sort (gsl_vector * eval, gsl_matrix_complex * evec, gsl_eigen_sort_t sort_type) { if (evec->size1 != evec->size2) { GSL_ERROR ("eigenvector matrix must be square", GSL_ENOTSQR); } else if (eval->size != evec->size1) { GSL_ERROR ("eigenvalues must match eigenvector matrix", GSL_EBADLEN); } else { const size_t N = eval->size; size_t i; for (i = 0; i < N - 1; i++) { size_t j; size_t k = i; double ek = gsl_vector_get (eval, i); /* search for something to swap */ for (j = i + 1; j < N; j++) { int test; const double ej = gsl_vector_get (eval, j); switch (sort_type) { case GSL_EIGEN_SORT_VAL_ASC: test = (ej < ek); break; case GSL_EIGEN_SORT_VAL_DESC: test = (ej > ek); break; case GSL_EIGEN_SORT_ABS_ASC: test = (fabs (ej) < fabs (ek)); break; case GSL_EIGEN_SORT_ABS_DESC: test = (fabs (ej) > fabs (ek)); break; default: GSL_ERROR ("unrecognized sort type", GSL_EINVAL); } if (test) { k = j; ek = ej; } } if (k != i) { /* swap eigenvalues */ gsl_vector_swap_elements (eval, i, k); /* swap eigenvectors */ gsl_matrix_complex_swap_columns (evec, i, k); } } return GSL_SUCCESS; } } int gsl_eigen_nonsymmv_sort (gsl_vector_complex * eval, gsl_matrix_complex * evec, gsl_eigen_sort_t sort_type) { if (evec && (evec->size1 != evec->size2)) { GSL_ERROR ("eigenvector matrix must be square", GSL_ENOTSQR); } else if (evec && (eval->size != evec->size1)) { GSL_ERROR ("eigenvalues must match eigenvector matrix", GSL_EBADLEN); } else { const size_t N = eval->size; size_t i; for (i = 0; i < N - 1; i++) { size_t j; size_t k = i; gsl_complex ek = gsl_vector_complex_get (eval, i); /* search for something to swap */ for (j = i + 1; j < N; j++) { int test; const gsl_complex ej = gsl_vector_complex_get (eval, j); switch (sort_type) { case GSL_EIGEN_SORT_ABS_ASC: test = (gsl_complex_abs (ej) < gsl_complex_abs (ek)); break; case GSL_EIGEN_SORT_ABS_DESC: test = (gsl_complex_abs (ej) > gsl_complex_abs (ek)); break; case GSL_EIGEN_SORT_VAL_ASC: case GSL_EIGEN_SORT_VAL_DESC: default: GSL_ERROR ("invalid sort type", GSL_EINVAL); } if (test) { k = j; ek = ej; } } if (k != i) { /* swap eigenvalues */ gsl_vector_complex_swap_elements (eval, i, k); /* swap eigenvectors */ if (evec) gsl_matrix_complex_swap_columns (evec, i, k); } } return GSL_SUCCESS; } } int gsl_eigen_gensymmv_sort (gsl_vector * eval, gsl_matrix * evec, gsl_eigen_sort_t sort_type) { int s; s = gsl_eigen_symmv_sort(eval, evec, sort_type); return s; } int gsl_eigen_genhermv_sort (gsl_vector * eval, gsl_matrix_complex * evec, gsl_eigen_sort_t sort_type) { int s; s = gsl_eigen_hermv_sort(eval, evec, sort_type); return s; } int gsl_eigen_genv_sort (gsl_vector_complex * alpha, gsl_vector * beta, gsl_matrix_complex * evec, gsl_eigen_sort_t sort_type) { if (evec->size1 != evec->size2) { GSL_ERROR ("eigenvector matrix must be square", GSL_ENOTSQR); } else if (alpha->size != evec->size1 || beta->size != evec->size1) { GSL_ERROR ("eigenvalues must match eigenvector matrix", GSL_EBADLEN); } else { const size_t N = alpha->size; size_t i; for (i = 0; i < N - 1; i++) { size_t j; size_t k = i; gsl_complex ak = gsl_vector_complex_get (alpha, i); double bk = gsl_vector_get(beta, i); gsl_complex ek; if (bk < GSL_DBL_EPSILON) { GSL_SET_COMPLEX(&ek, GSL_SIGN(GSL_REAL(ak)) ? GSL_POSINF : GSL_NEGINF, GSL_SIGN(GSL_IMAG(ak)) ? GSL_POSINF : GSL_NEGINF); } else ek = gsl_complex_div_real(ak, bk); /* search for something to swap */ for (j = i + 1; j < N; j++) { int test; const gsl_complex aj = gsl_vector_complex_get (alpha, j); double bj = gsl_vector_get(beta, j); gsl_complex ej; if (bj < GSL_DBL_EPSILON) { GSL_SET_COMPLEX(&ej, GSL_SIGN(GSL_REAL(aj)) ? GSL_POSINF : GSL_NEGINF, GSL_SIGN(GSL_IMAG(aj)) ? GSL_POSINF : GSL_NEGINF); } else ej = gsl_complex_div_real(aj, bj); switch (sort_type) { case GSL_EIGEN_SORT_ABS_ASC: test = (gsl_complex_abs (ej) < gsl_complex_abs (ek)); break; case GSL_EIGEN_SORT_ABS_DESC: test = (gsl_complex_abs (ej) > gsl_complex_abs (ek)); break; case GSL_EIGEN_SORT_VAL_ASC: case GSL_EIGEN_SORT_VAL_DESC: default: GSL_ERROR ("invalid sort type", GSL_EINVAL); } if (test) { k = j; ek = ej; } } if (k != i) { /* swap eigenvalues */ gsl_vector_complex_swap_elements (alpha, i, k); gsl_vector_swap_elements (beta, i, k); /* swap eigenvectors */ gsl_matrix_complex_swap_columns (evec, i, k); } } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_cblas__chemv.c0000664000176700017670000000061611723710247017761 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_chemv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE float #include "gsl_cblas__source_hemv.h" #undef BASE } sources_5316/external/gsl/gsl_permute_vector_long.h0000664000176700017670000000265511705263724021453 0ustar paulpaul/* permutation/gsl_permute_vector_long.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_LONG_H__ #define __GSL_PERMUTE_VECTOR_LONG_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_long.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_long (const gsl_permutation * p, gsl_vector_long * v); int gsl_permute_vector_long_inverse (const gsl_permutation * p, gsl_vector_long * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_LONG_H__ */ sources_5316/external/gsl/gsl_histogram__stat2d.c0000664000176700017670000001326611723710247020776 0ustar paulpaul/* histogram/stat2d.c * Copyright (C) 2002 Achim Gaedke * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File histogram/stat2d.c: * Routine to return statistical values of the content of a 2D hisogram. * * Contains the routines: * gsl_histogram2d_sum sum up all bin values * gsl_histogram2d_xmean determine mean of x values * gsl_histogram2d_ymean determine mean of y values * * Author: Achim Gaedke Achim.Gaedke@zpr.uni-koeln.de * Jan. 2002 * ***************************************************************/ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram2d.h" /* sum up all bins of histogram2d */ double gsl_histogram2d_sum (const gsl_histogram2d * h) { const size_t n = h->nx * h->ny; double sum = 0; size_t i = 0; while (i < n) sum += h->bin[i++]; return sum; } double gsl_histogram2d_xmean (const gsl_histogram2d * h) { const size_t nx = h->nx; const size_t ny = h->ny; size_t i; size_t j; /* Compute the bin-weighted arithmetic mean M of a histogram using the recurrence relation M(n) = M(n-1) + (x[n] - M(n-1)) (w(n)/(W(n-1) + w(n))) W(n) = W(n-1) + w(n) */ long double wmean = 0; long double W = 0; for (i = 0; i < nx; i++) { double xi = (h->xrange[i + 1] + h->xrange[i]) / 2.0; double wi = 0; for (j = 0; j < ny; j++) { double wij = h->bin[i * ny + j]; if (wij > 0) wi += wij; } if (wi > 0) { W += wi; wmean += (xi - wmean) * (wi / W); } } return wmean; } double gsl_histogram2d_ymean (const gsl_histogram2d * h) { const size_t nx = h->nx; const size_t ny = h->ny; size_t i; size_t j; /* Compute the bin-weighted arithmetic mean M of a histogram using the recurrence relation M(n) = M(n-1) + (x[n] - M(n-1)) (w(n)/(W(n-1) + w(n))) W(n) = W(n-1) + w(n) */ long double wmean = 0; long double W = 0; for (j = 0; j < ny; j++) { double yj = (h->yrange[j + 1] + h->yrange[j]) / 2.0; double wj = 0; for (i = 0; i < nx; i++) { double wij = h->bin[i * ny + j]; if (wij > 0) wj += wij; } if (wj > 0) { W += wj; wmean += (yj - wmean) * (wj / W); } } return wmean; } double gsl_histogram2d_xsigma (const gsl_histogram2d * h) { const double xmean = gsl_histogram2d_xmean (h); const size_t nx = h->nx; const size_t ny = h->ny; size_t i; size_t j; /* Compute the bin-weighted arithmetic mean M of a histogram using the recurrence relation M(n) = M(n-1) + (x[n] - M(n-1)) (w(n)/(W(n-1) + w(n))) W(n) = W(n-1) + w(n) */ long double wvariance = 0; long double W = 0; for (i = 0; i < nx; i++) { double xi = (h->xrange[i + 1] + h->xrange[i]) / 2 - xmean; double wi = 0; for (j = 0; j < ny; j++) { double wij = h->bin[i * ny + j]; if (wij > 0) wi += wij; } if (wi > 0) { W += wi; wvariance += ((xi * xi) - wvariance) * (wi / W); } } { double xsigma = sqrt (wvariance); return xsigma; } } double gsl_histogram2d_ysigma (const gsl_histogram2d * h) { const double ymean = gsl_histogram2d_ymean (h); const size_t nx = h->nx; const size_t ny = h->ny; size_t i; size_t j; /* Compute the bin-weighted arithmetic mean M of a histogram using the recurrence relation M(n) = M(n-1) + (x[n] - M(n-1)) (w(n)/(W(n-1) + w(n))) W(n) = W(n-1) + w(n) */ long double wvariance = 0; long double W = 0; for (j = 0; j < ny; j++) { double yj = (h->yrange[j + 1] + h->yrange[j]) / 2.0 - ymean; double wj = 0; for (i = 0; i < nx; i++) { double wij = h->bin[i * ny + j]; if (wij > 0) wj += wij; } if (wj > 0) { W += wj; wvariance += ((yj * yj) - wvariance) * (wj / W); } } { double ysigma = sqrt (wvariance); return ysigma; } } double gsl_histogram2d_cov (const gsl_histogram2d * h) { const double xmean = gsl_histogram2d_xmean (h); const double ymean = gsl_histogram2d_ymean (h); const size_t nx = h->nx; const size_t ny = h->ny; size_t i; size_t j; /* Compute the bin-weighted arithmetic mean M of a histogram using the recurrence relation M(n) = M(n-1) + (x[n] - M(n-1)) (w(n)/(W(n-1) + w(n))) W(n) = W(n-1) + w(n) */ long double wcovariance = 0; long double W = 0; for (j = 0; j < ny; j++) { for (i = 0; i < nx; i++) { double xi = (h->xrange[i + 1] + h->xrange[i]) / 2.0 - xmean; double yj = (h->yrange[j + 1] + h->yrange[j]) / 2.0 - ymean; double wij = h->bin[i * ny + j]; if (wij > 0) { W += wij; wcovariance += ((xi * yj) - wcovariance) * (wij / W); } } } return wcovariance; } sources_5316/external/gsl/gsl_randist__nbinomial.c0000664000176700017670000000322411723710247021205 0ustar paulpaul/* randist/nbinomial.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" #include "gsl_sf_gamma.h" /* The negative binomial distribution has the form, prob(k) = Gamma(n + k)/(Gamma(n) Gamma(k + 1)) p^n (1-p)^k for k = 0, 1, ... . Note that n does not have to be an integer. This is the Leger's algorithm (given in the answers in Knuth) */ unsigned int gsl_ran_negative_binomial (const gsl_rng * r, double p, double n) { double X = gsl_ran_gamma (r, n, 1.0) ; unsigned int k = gsl_ran_poisson (r, X*(1-p)/p) ; return k ; } double gsl_ran_negative_binomial_pdf (const unsigned int k, const double p, double n) { double P; double f = gsl_sf_lngamma (k + n) ; double a = gsl_sf_lngamma (n) ; double b = gsl_sf_lngamma (k + 1.0) ; P = exp(f-a-b) * pow (p, n) * pow (1 - p, (double)k); return P; } sources_5316/external/gsl/gsl_histogram__add2d.c0000664000176700017670000000334011723710247020543 0ustar paulpaul/* histogram/add2d.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram.h" #include "gsl_histogram2d.h" #include "gsl_histogram__find2d.c" int gsl_histogram2d_increment (gsl_histogram2d * h, double x, double y) { int status = gsl_histogram2d_accumulate (h, x, y, 1.0); return status; } int gsl_histogram2d_accumulate (gsl_histogram2d * h, double x, double y, double weight) { const size_t nx = h->nx; const size_t ny = h->ny; size_t i = 0, j = 0; int status = find2d (h->nx, h->xrange, h->ny, h->yrange, x, y, &i, &j); if (status) { return GSL_EDOM; } if (i >= nx) { GSL_ERROR ("index lies outside valid range of 0 .. nx - 1", GSL_ESANITY); } if (j >= ny) { GSL_ERROR ("index lies outside valid range of 0 .. ny - 1", GSL_ESANITY); } h->bin[i * ny + j] += weight; return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__ctbmv.c0000664000176700017670000000063011723710247017766 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ctbmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const void *A, const int lda, void *X, const int incX) { #define BASE float #include "gsl_cblas__source_tbmv_c.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__recurse.h0000664000176700017670000001724611705263724021070 0ustar paulpaul/* specfunc/recurse.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef _RECURSE_H_ #define _RECURSE_H_ #define CONCAT(a,b) a ## _ ## b /* n_max >= n_min + 2 * f[n+1] + a[n] f[n] + b[n] f[n-1] = 0 * * Trivial forward recurrence. */ #define GEN_RECURSE_FORWARD_SIMPLE(func) \ int CONCAT(recurse_forward_simple, func) ( \ const int n_max, const int n_min, \ const double parameters[], \ const double f_n_min, \ const double f_n_min_p1, \ double * f, \ double * f_n_max \ ) \ { \ int n; \ \ if(f == 0) { \ double f2 = f_n_min; \ double f1 = f_n_min_p1; \ double f0; \ for(n=n_min+2; n<=n_max; n++) { \ f0 = -REC_COEFF_A(n-1,parameters) * f1 - REC_COEFF_B(n-1, parameters) * f2; \ f2 = f1; \ f1 = f0; \ } \ *f_n_max = f0; \ } \ else { \ f[n_min] = f_n_min; \ f[n_min + 1] = f_n_min_p1; \ for(n=n_min+2; n<=n_max; n++) { \ f[n] = -REC_COEFF_A(n-1,parameters) * f[n-1] - REC_COEFF_B(n-1, parameters) * f[n-2]; \ } \ *f_n_max = f[n_max]; \ } \ \ return GSL_SUCCESS; \ } \ /* n_start >= n_max >= n_min * f[n+1] + a[n] f[n] + b[n] f[n-1] = 0 * * Generate the minimal solution of the above recursion relation, * with the simplest form of the normalization condition, f[n_min] given. * [Gautschi, SIAM Rev. 9, 24 (1967); (3.9) with s[n]=0] */ #define GEN_RECURSE_BACKWARD_MINIMAL_SIMPLE(func) \ int CONCAT(recurse_backward_minimal_simple, func) ( \ const int n_start, \ const int n_max, const int n_min, \ const double parameters[], \ const double f_n_min, \ double * f, \ double * f_n_max \ ) \ { \ int n; \ double r_n = 0.; \ double r_nm1; \ double ratio; \ \ for(n=n_start; n > n_max; n--) { \ r_nm1 = -REC_COEFF_B(n, parameters) / (REC_COEFF_A(n, parameters) + r_n); \ r_n = r_nm1; \ } \ \ if(f != 0) { \ f[n_max] = 10.*DBL_MIN; \ for(n=n_max; n > n_min; n--) { \ r_nm1 = -REC_COEFF_B(n, parameters) / (REC_COEFF_A(n, parameters) + r_n); \ f[n-1] = f[n] / r_nm1; \ r_n = r_nm1; \ } \ ratio = f_n_min / f[n_min]; \ for(n=n_min; n<=n_max; n++) { \ f[n] *= ratio; \ } \ } \ else { \ double f_nm1; \ double f_n = 10.*DBL_MIN; \ *f_n_max = f_n; \ for(n=n_max; n > n_min; n--) { \ r_nm1 = -REC_COEFF_B(n, parameters) / (REC_COEFF_A(n, parameters) + r_n); \ f_nm1 = f_n / r_nm1; \ r_n = r_nm1; \ } \ ratio = f_n_min / f_nm1; \ *f_n_max *= ratio; \ } \ \ return GSL_SUCCESS; \ } \ #endif /* !_RECURSE_H_ */ sources_5316/external/gsl/gsl_block__init_source.c0000664000176700017670000000363511723710247021214 0ustar paulpaul/* block/init_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ TYPE (gsl_block) * FUNCTION (gsl_block, alloc) (const size_t n) { TYPE (gsl_block) * b; if (n == 0) { GSL_ERROR_VAL ("block length n must be positive integer", GSL_EINVAL, 0); } b = (TYPE (gsl_block) *) malloc (sizeof (TYPE (gsl_block))); if (b == 0) { GSL_ERROR_VAL ("failed to allocate space for block struct", GSL_ENOMEM, 0); } b->data = (ATOMIC *) malloc (MULTIPLICITY * n * sizeof (ATOMIC)); if (b->data == 0) { free (b); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for block data", GSL_ENOMEM, 0); } b->size = n; return b; } TYPE (gsl_block) * FUNCTION (gsl_block, calloc) (const size_t n) { size_t i; TYPE (gsl_block) * b = FUNCTION (gsl_block, alloc) (n); if (b == 0) return 0; /* initialize block to zero */ for (i = 0; i < MULTIPLICITY * n; i++) { b->data[i] = 0; } return b; } void FUNCTION (gsl_block, free) (TYPE (gsl_block) * b) { free (b->data); free (b); } sources_5316/external/gsl/gsl_sort_float.h0000664000176700017670000000352211705263724017537 0ustar paulpaul/* sort/gsl_sort_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_FLOAT_H__ #define __GSL_SORT_FLOAT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_float (float * data, const size_t stride, const size_t n); void gsl_sort_float_index (size_t * p, const float * data, const size_t stride, const size_t n); int gsl_sort_float_smallest (float * dest, const size_t k, const float * src, const size_t stride, const size_t n); int gsl_sort_float_smallest_index (size_t * p, const size_t k, const float * src, const size_t stride, const size_t n); int gsl_sort_float_largest (float * dest, const size_t k, const float * src, const size_t stride, const size_t n); int gsl_sort_float_largest_index (size_t * p, const size_t k, const float * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_FLOAT_H__ */ sources_5316/external/gsl/gsl_sort_uchar.h0000664000176700017670000000362211705263724017535 0ustar paulpaul/* sort/gsl_sort_uchar.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_UCHAR_H__ #define __GSL_SORT_UCHAR_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_uchar (unsigned char * data, const size_t stride, const size_t n); void gsl_sort_uchar_index (size_t * p, const unsigned char * data, const size_t stride, const size_t n); int gsl_sort_uchar_smallest (unsigned char * dest, const size_t k, const unsigned char * src, const size_t stride, const size_t n); int gsl_sort_uchar_smallest_index (size_t * p, const size_t k, const unsigned char * src, const size_t stride, const size_t n); int gsl_sort_uchar_largest (unsigned char * dest, const size_t k, const unsigned char * src, const size_t stride, const size_t n); int gsl_sort_uchar_largest_index (size_t * p, const size_t k, const unsigned char * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_UCHAR_H__ */ sources_5316/external/gsl/gsl_matrix_uint.h0000664000176700017670000002667611705263724017745 0ustar paulpaul/* matrix/gsl_matrix_uint.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_UINT_H__ #define __GSL_MATRIX_UINT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_uint.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; unsigned int * data; gsl_block_uint * block; int owner; } gsl_matrix_uint; typedef struct { gsl_matrix_uint matrix; } _gsl_matrix_uint_view; typedef _gsl_matrix_uint_view gsl_matrix_uint_view; typedef struct { gsl_matrix_uint matrix; } _gsl_matrix_uint_const_view; typedef const _gsl_matrix_uint_const_view gsl_matrix_uint_const_view; /* Allocation */ gsl_matrix_uint * gsl_matrix_uint_alloc (const size_t n1, const size_t n2); gsl_matrix_uint * gsl_matrix_uint_calloc (const size_t n1, const size_t n2); gsl_matrix_uint * gsl_matrix_uint_alloc_from_block (gsl_block_uint * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_uint * gsl_matrix_uint_alloc_from_matrix (gsl_matrix_uint * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_uint * gsl_vector_uint_alloc_row_from_matrix (gsl_matrix_uint * m, const size_t i); gsl_vector_uint * gsl_vector_uint_alloc_col_from_matrix (gsl_matrix_uint * m, const size_t j); void gsl_matrix_uint_free (gsl_matrix_uint * m); /* Views */ _gsl_matrix_uint_view gsl_matrix_uint_submatrix (gsl_matrix_uint * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_uint_view gsl_matrix_uint_row (gsl_matrix_uint * m, const size_t i); _gsl_vector_uint_view gsl_matrix_uint_column (gsl_matrix_uint * m, const size_t j); _gsl_vector_uint_view gsl_matrix_uint_diagonal (gsl_matrix_uint * m); _gsl_vector_uint_view gsl_matrix_uint_subdiagonal (gsl_matrix_uint * m, const size_t k); _gsl_vector_uint_view gsl_matrix_uint_superdiagonal (gsl_matrix_uint * m, const size_t k); _gsl_vector_uint_view gsl_matrix_uint_subrow (gsl_matrix_uint * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_uint_view gsl_matrix_uint_subcolumn (gsl_matrix_uint * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_uint_view gsl_matrix_uint_view_array (unsigned int * base, const size_t n1, const size_t n2); _gsl_matrix_uint_view gsl_matrix_uint_view_array_with_tda (unsigned int * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_uint_view gsl_matrix_uint_view_vector (gsl_vector_uint * v, const size_t n1, const size_t n2); _gsl_matrix_uint_view gsl_matrix_uint_view_vector_with_tda (gsl_vector_uint * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_uint_const_view gsl_matrix_uint_const_submatrix (const gsl_matrix_uint * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_uint_const_view gsl_matrix_uint_const_row (const gsl_matrix_uint * m, const size_t i); _gsl_vector_uint_const_view gsl_matrix_uint_const_column (const gsl_matrix_uint * m, const size_t j); _gsl_vector_uint_const_view gsl_matrix_uint_const_diagonal (const gsl_matrix_uint * m); _gsl_vector_uint_const_view gsl_matrix_uint_const_subdiagonal (const gsl_matrix_uint * m, const size_t k); _gsl_vector_uint_const_view gsl_matrix_uint_const_superdiagonal (const gsl_matrix_uint * m, const size_t k); _gsl_vector_uint_const_view gsl_matrix_uint_const_subrow (const gsl_matrix_uint * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_uint_const_view gsl_matrix_uint_const_subcolumn (const gsl_matrix_uint * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_uint_const_view gsl_matrix_uint_const_view_array (const unsigned int * base, const size_t n1, const size_t n2); _gsl_matrix_uint_const_view gsl_matrix_uint_const_view_array_with_tda (const unsigned int * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_uint_const_view gsl_matrix_uint_const_view_vector (const gsl_vector_uint * v, const size_t n1, const size_t n2); _gsl_matrix_uint_const_view gsl_matrix_uint_const_view_vector_with_tda (const gsl_vector_uint * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ unsigned int gsl_matrix_uint_get(const gsl_matrix_uint * m, const size_t i, const size_t j); void gsl_matrix_uint_set(gsl_matrix_uint * m, const size_t i, const size_t j, const unsigned int x); unsigned int * gsl_matrix_uint_ptr(gsl_matrix_uint * m, const size_t i, const size_t j); const unsigned int * gsl_matrix_uint_const_ptr(const gsl_matrix_uint * m, const size_t i, const size_t j); void gsl_matrix_uint_set_zero (gsl_matrix_uint * m); void gsl_matrix_uint_set_identity (gsl_matrix_uint * m); void gsl_matrix_uint_set_all (gsl_matrix_uint * m, unsigned int x); int gsl_matrix_uint_fread (FILE * stream, gsl_matrix_uint * m) ; int gsl_matrix_uint_fwrite (FILE * stream, const gsl_matrix_uint * m) ; int gsl_matrix_uint_fscanf (FILE * stream, gsl_matrix_uint * m); int gsl_matrix_uint_fprintf (FILE * stream, const gsl_matrix_uint * m, const char * format); int gsl_matrix_uint_memcpy(gsl_matrix_uint * dest, const gsl_matrix_uint * src); int gsl_matrix_uint_swap(gsl_matrix_uint * m1, gsl_matrix_uint * m2); int gsl_matrix_uint_swap_rows(gsl_matrix_uint * m, const size_t i, const size_t j); int gsl_matrix_uint_swap_columns(gsl_matrix_uint * m, const size_t i, const size_t j); int gsl_matrix_uint_swap_rowcol(gsl_matrix_uint * m, const size_t i, const size_t j); int gsl_matrix_uint_transpose (gsl_matrix_uint * m); int gsl_matrix_uint_transpose_memcpy (gsl_matrix_uint * dest, const gsl_matrix_uint * src); unsigned int gsl_matrix_uint_max (const gsl_matrix_uint * m); unsigned int gsl_matrix_uint_min (const gsl_matrix_uint * m); void gsl_matrix_uint_minmax (const gsl_matrix_uint * m, unsigned int * min_out, unsigned int * max_out); void gsl_matrix_uint_max_index (const gsl_matrix_uint * m, size_t * imax, size_t *jmax); void gsl_matrix_uint_min_index (const gsl_matrix_uint * m, size_t * imin, size_t *jmin); void gsl_matrix_uint_minmax_index (const gsl_matrix_uint * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_uint_isnull (const gsl_matrix_uint * m); int gsl_matrix_uint_ispos (const gsl_matrix_uint * m); int gsl_matrix_uint_isneg (const gsl_matrix_uint * m); int gsl_matrix_uint_isnonneg (const gsl_matrix_uint * m); int gsl_matrix_uint_add (gsl_matrix_uint * a, const gsl_matrix_uint * b); int gsl_matrix_uint_sub (gsl_matrix_uint * a, const gsl_matrix_uint * b); int gsl_matrix_uint_mul_elements (gsl_matrix_uint * a, const gsl_matrix_uint * b); int gsl_matrix_uint_div_elements (gsl_matrix_uint * a, const gsl_matrix_uint * b); int gsl_matrix_uint_scale (gsl_matrix_uint * a, const double x); int gsl_matrix_uint_add_constant (gsl_matrix_uint * a, const double x); int gsl_matrix_uint_add_diagonal (gsl_matrix_uint * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_uint_get_row(gsl_vector_uint * v, const gsl_matrix_uint * m, const size_t i); int gsl_matrix_uint_get_col(gsl_vector_uint * v, const gsl_matrix_uint * m, const size_t j); int gsl_matrix_uint_set_row(gsl_matrix_uint * m, const size_t i, const gsl_vector_uint * v); int gsl_matrix_uint_set_col(gsl_matrix_uint * m, const size_t j, const gsl_vector_uint * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline unsigned int gsl_matrix_uint_get(const gsl_matrix_uint * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_uint_set(gsl_matrix_uint * m, const size_t i, const size_t j, const unsigned int x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline unsigned int * gsl_matrix_uint_ptr(gsl_matrix_uint * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (unsigned int *) (m->data + (i * m->tda + j)) ; } extern inline const unsigned int * gsl_matrix_uint_const_ptr(const gsl_matrix_uint * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const unsigned int *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_UINT_H__ */ sources_5316/external/gsl/gsl_qrng.h0000664000176700017670000000430311705263724016330 0ustar paulpaul/* Author: G. Jungman */ #ifndef __GSL_QRNG_H__ #define __GSL_QRNG_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Once again, more inane C-style OOP... kill me now. */ /* Structure describing a type of generator. */ typedef struct { const char * name; unsigned int max_dimension; size_t (*state_size) (unsigned int dimension); int (*init_state) (void * state, unsigned int dimension); int (*get) (void * state, unsigned int dimension, double x[]); } gsl_qrng_type; /* Structure describing a generator instance of a * specified type, with generator-specific state info * and dimension-specific info. */ typedef struct { const gsl_qrng_type * type; unsigned int dimension; size_t state_size; void * state; } gsl_qrng; /* Supported generator types. */ GSL_VAR const gsl_qrng_type * gsl_qrng_niederreiter_2; GSL_VAR const gsl_qrng_type * gsl_qrng_sobol; /* Allocate and initialize a generator * of the specified type, in the given * space dimension. */ gsl_qrng * gsl_qrng_alloc (const gsl_qrng_type * T, unsigned int dimension); /* Copy a generator. */ int gsl_qrng_memcpy (gsl_qrng * dest, const gsl_qrng * src); /* Clone a generator. */ gsl_qrng * gsl_qrng_clone (const gsl_qrng * q); /* Free a generator. */ void gsl_qrng_free (gsl_qrng * q); /* Intialize a generator. */ void gsl_qrng_init (gsl_qrng * q); /* Get the standardized name of the generator. */ const char * gsl_qrng_name (const gsl_qrng * q); /* ISN'T THIS CONFUSING FOR PEOPLE? WHAT IF SOMEBODY TRIES TO COPY WITH THIS ??? */ size_t gsl_qrng_size (const gsl_qrng * q); void * gsl_qrng_state (const gsl_qrng * q); /* Retrieve next vector in sequence. */ int gsl_qrng_get (const gsl_qrng * q, double x[]); #ifdef HAVE_INLINE extern inline int gsl_qrng_get (const gsl_qrng * q, double x[]); extern inline int gsl_qrng_get (const gsl_qrng * q, double x[]) { return (q->type->get) (q->state, q->dimension, x); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* !__GSL_QRNG_H__ */ sources_5316/external/gsl/gsl_matrix__oper_complex_source.c0000664000176700017670000001315211723710247023152 0ustar paulpaul/* matrix/oper_complex_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_matrix, add) (TYPE (gsl_matrix) * a, const TYPE (gsl_matrix) * b) { const size_t M = a->size1; const size_t N = a->size2; if (b->size1 != M || b->size2 != N) { GSL_ERROR ("matrices must have same dimensions", GSL_EBADLEN); } else { const size_t tda_a = a->tda; const size_t tda_b = b->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { const size_t aij = 2 * (i * tda_a + j); const size_t bij = 2 * (i * tda_b + j); a->data[aij] += b->data[bij]; a->data[aij + 1] += b->data[bij + 1]; } } return GSL_SUCCESS; } } int FUNCTION (gsl_matrix, sub) (TYPE (gsl_matrix) * a, const TYPE (gsl_matrix) * b) { const size_t M = a->size1; const size_t N = a->size2; if (b->size1 != M || b->size2 != N) { GSL_ERROR ("matrices must have same dimensions", GSL_EBADLEN); } else { const size_t tda_a = a->tda; const size_t tda_b = b->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { const size_t aij = 2 * (i * tda_a + j); const size_t bij = 2 * (i * tda_b + j); a->data[aij] -= b->data[bij]; a->data[aij + 1] -= b->data[bij + 1]; } } return GSL_SUCCESS; } } int FUNCTION (gsl_matrix, mul_elements) (TYPE (gsl_matrix) * a, const TYPE (gsl_matrix) * b) { const size_t M = a->size1; const size_t N = a->size2; if (b->size1 != M || b->size2 != N) { GSL_ERROR ("matrices must have same dimensions", GSL_EBADLEN); } else { const size_t tda_a = a->tda; const size_t tda_b = b->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { const size_t aij = 2 * (i * tda_a + j); const size_t bij = 2 * (i * tda_b + j); ATOMIC ar = a->data[aij]; ATOMIC ai = a->data[aij + 1]; ATOMIC br = b->data[bij]; ATOMIC bi = b->data[bij + 1]; a->data[aij] = ar * br - ai * bi; a->data[aij + 1] = ar * bi + ai * br; } } return GSL_SUCCESS; } } int FUNCTION (gsl_matrix, div_elements) (TYPE (gsl_matrix) * a, const TYPE (gsl_matrix) * b) { const size_t M = a->size1; const size_t N = a->size2; if (b->size1 != M || b->size2 != N) { GSL_ERROR ("matrices must have same dimensions", GSL_EBADLEN); } else { const size_t tda_a = a->tda; const size_t tda_b = b->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { const size_t aij = 2 * (i * tda_a + j); const size_t bij = 2 * (i * tda_b + j); ATOMIC ar = a->data[aij]; ATOMIC ai = a->data[aij + 1]; ATOMIC br = b->data[bij]; ATOMIC bi = b->data[bij + 1]; ATOMIC s = 1.0 / hypot(br, bi); ATOMIC sbr = s * br; ATOMIC sbi = s * bi; a->data[aij] = (ar * sbr + ai * sbi) * s; a->data[aij + 1] = (ai * sbr - ar * sbi) * s; } } return GSL_SUCCESS; } } int FUNCTION (gsl_matrix, scale) (TYPE (gsl_matrix) * a, const BASE x) { const size_t M = a->size1; const size_t N = a->size2; const size_t tda = a->tda; size_t i, j; ATOMIC xr = GSL_REAL(x); ATOMIC xi = GSL_IMAG(x); for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { const size_t aij = 2 * (i * tda + j); ATOMIC ar = a->data[aij]; ATOMIC ai = a->data[aij + 1]; a->data[aij] = ar * xr - ai * xi; a->data[aij + 1] = ar * xi + ai * xr; } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, add_constant) (TYPE (gsl_matrix) * a, const BASE x) { const size_t M = a->size1; const size_t N = a->size2; const size_t tda = a->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { a->data[2 * (i * tda + j)] += GSL_REAL (x); a->data[2 * (i * tda + j) + 1] += GSL_IMAG (x); } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, add_diagonal) (TYPE (gsl_matrix) * a, const BASE x) { const size_t M = a->size1; const size_t N = a->size2; const size_t tda = a->tda; const size_t loop_lim = (M < N ? M : N); size_t i; for (i = 0; i < loop_lim; i++) { a->data[2 * (i * tda + i)] += GSL_REAL (x); a->data[2 * (i * tda + i) + 1] += GSL_IMAG (x); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_fft__real_pass_4.c0000664000176700017670000001604511723710247020551 0ustar paulpaul/* fft/real_pass_4.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_real,pass_4) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[]) { size_t k, k1; const size_t factor = 4; const size_t m = n / factor; const size_t q = n / product; const size_t product_1 = product / factor; for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1; const size_t from1 = from0 + m; const size_t from2 = from1 + m; const size_t from3 = from2 + m; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC z3_real = VECTOR(in,istride,from3); /* compute x = W(4) z */ /* t1 = z0 + z2 */ const ATOMIC t1_real = z0_real + z2_real; /* t2 = z1 + z3 */ const ATOMIC t2_real = z1_real + z3_real; /* t3 = z0 - z2 */ const ATOMIC t3_real = z0_real - z2_real; /* t4 = - (z1 - z3) */ const ATOMIC t4_real = -(z1_real - z3_real); /* x0 = t1 + t2 */ const ATOMIC x0_real = t1_real + t2_real; /* x1 = t3 + i t4 */ const ATOMIC x1_real = t3_real; const ATOMIC x1_imag = t4_real; /* x2 = t1 - t2 */ const ATOMIC x2_real = t1_real - t2_real; const size_t to0 = product * k1; const size_t to1 = to0 + 2 * product_1 - 1; const size_t to2 = to1 + 2 * product_1; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to1 + 1) = x1_imag; VECTOR(out,ostride,to2) = x2_real; } if (product_1 == 1) return; for (k = 1; k < (product_1 + 1) / 2; k++) { ATOMIC w1_real, w1_imag, w2_real, w2_imag, w3_real, w3_imag; w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = -GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = -GSL_IMAG(twiddle2[k - 1]); w3_real = GSL_REAL(twiddle3[k - 1]); w3_imag = -GSL_IMAG(twiddle3[k - 1]); for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1 + 2 * k - 1; const size_t from1 = from0 + m; const size_t from2 = from1 + m; const size_t from3 = from2 + m; const ATOMIC f0_real = VECTOR(in,istride,from0); const ATOMIC f0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC f1_real = VECTOR(in,istride,from1); const ATOMIC f1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC f2_real = VECTOR(in,istride,from2); const ATOMIC f2_imag = VECTOR(in,istride,from2 + 1); const ATOMIC f3_real = VECTOR(in,istride,from3); const ATOMIC f3_imag = VECTOR(in,istride,from3 + 1); const ATOMIC z0_real = f0_real; const ATOMIC z0_imag = f0_imag; const ATOMIC z1_real = w1_real * f1_real - w1_imag * f1_imag; const ATOMIC z1_imag = w1_real * f1_imag + w1_imag * f1_real; const ATOMIC z2_real = w2_real * f2_real - w2_imag * f2_imag; const ATOMIC z2_imag = w2_real * f2_imag + w2_imag * f2_real; const ATOMIC z3_real = w3_real * f3_real - w3_imag * f3_imag; const ATOMIC z3_imag = w3_real * f3_imag + w3_imag * f3_real; /* compute x = W(4) z */ /* t1 = z0 + z2 */ const ATOMIC t1_real = z0_real + z2_real; const ATOMIC t1_imag = z0_imag + z2_imag; /* t2 = z1 + z3 */ const ATOMIC t2_real = z1_real + z3_real; const ATOMIC t2_imag = z1_imag + z3_imag; /* t3 = z0 - z2 */ const ATOMIC t3_real = z0_real - z2_real; const ATOMIC t3_imag = z0_imag - z2_imag; /* t4 = - (z1 - z3) */ const ATOMIC t4_real = -(z1_real - z3_real); const ATOMIC t4_imag = -(z1_imag - z3_imag); /* x0 = t1 + t2 */ const ATOMIC x0_real = t1_real + t2_real; const ATOMIC x0_imag = t1_imag + t2_imag; /* x1 = t3 + i t4 */ const ATOMIC x1_real = t3_real - t4_imag; const ATOMIC x1_imag = t3_imag + t4_real; /* x2 = t1 - t2 */ const ATOMIC x2_real = t1_real - t2_real; const ATOMIC x2_imag = t1_imag - t2_imag; /* x3 = t3 - i t4 */ const ATOMIC x3_real = t3_real + t4_imag; const ATOMIC x3_imag = t3_imag - t4_real; const size_t to0 = k1 * product + 2 * k - 1; const size_t to1 = to0 + 2 * product_1; const size_t to2 = 2 * product_1 - 2 * k + k1 * product - 1; const size_t to3 = to2 + 2 * product_1; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to0 + 1) = x0_imag; VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to1 + 1) = x1_imag; VECTOR(out,ostride,to3) = x2_real; VECTOR(out,ostride,to3 + 1) = -x2_imag; VECTOR(out,ostride,to2) = x3_real; VECTOR(out,ostride,to2 + 1) = -x3_imag; } } if (product_1 % 2 == 1) return; for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1 + product_1 - 1; const size_t from1 = from0 + m; const size_t from2 = from1 + m; const size_t from3 = from2 + m; const ATOMIC x0 = VECTOR(in,istride,from0); const ATOMIC x1 = VECTOR(in,istride,from1); const ATOMIC x2 = VECTOR(in,istride,from2); const ATOMIC x3 = VECTOR(in,istride,from3); const ATOMIC t1 = (1.0 / sqrt (2.0)) * (x1 - x3); const ATOMIC t2 = (1.0 / sqrt (2.0)) * (x1 + x3); const size_t to0 = k1 * product + 2 * k - 1; const size_t to1 = to0 + 2 * product_1; VECTOR(out,ostride,to0) = x0 + t1; VECTOR(out,ostride,to0 + 1) = -x2 - t2; VECTOR(out,ostride,to1) = x0 - t1; VECTOR(out,ostride,to1 + 1) = x2 - t2; } return; } sources_5316/external/gsl/gsl_sys__log1p.c0000664000176700017670000000205311723710247017430 0ustar paulpaul/* sys/log1p.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include double gsl_log1p (const double x); double gsl_log1p (const double x) { volatile double y, z; y = 1 + x; z = y - 1; return log(y) - (z-x)/y ; /* cancels errors with IEEE arithmetic */ } sources_5316/external/gsl/gsl_cblas__ztbmv.c0000664000176700017670000000063111723710247020016 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ztbmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const void *A, const int lda, void *X, const int incX) { #define BASE double #include "gsl_cblas__source_tbmv_c.h" #undef BASE } sources_5316/external/gsl/gsl_cdf__gumbel2.c0000664000176700017670000000243711723710247017667 0ustar paulpaul/* cdf/gumbel2.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_gumbel2_P (const double x, const double a, const double b) { double P; if (x == 0) { P = 0; } else { double u = pow (x, a); P = exp (-b / u); } return P; } double gsl_cdf_gumbel2_Q (const double x, const double a, const double b) { double Q; if (x == 0) { Q = 1; } else { double u = pow (x, a); Q = -expm1 (-b / u); } return Q; } sources_5316/external/gsl/gsl_histogram__params.c0000664000176700017670000000217111723710247021051 0ustar paulpaul/* histogram/params.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_histogram.h" double gsl_histogram_max (const gsl_histogram * h) { const int n = h->n; return h->range[n]; } double gsl_histogram_min (const gsl_histogram * h) { return h->range[0]; } size_t gsl_histogram_bins (const gsl_histogram * h) { return h->n; } sources_5316/external/gsl/gsl_statistics__covariance_source.c0000664000176700017670000001105311723710247023454 0ustar paulpaul/* statistics/covar_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static double FUNCTION(compute,covariance) (const BASE data1[], const size_t stride1, const BASE data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); static double FUNCTION(compute,covariance) (const BASE data1[], const size_t stride1, const BASE data2[], const size_t stride2, const size_t n, const double mean1, const double mean2) { /* takes a dataset and finds the covariance */ long double covariance = 0 ; size_t i; /* find the sum of the squares */ for (i = 0; i < n; i++) { const long double delta1 = (data1[i * stride1] - mean1); const long double delta2 = (data2[i * stride2] - mean2); covariance += (delta1 * delta2 - covariance) / (i + 1); } return covariance ; } double FUNCTION(gsl_stats,covariance_m) (const BASE data1[], const size_t stride1, const BASE data2[], const size_t stride2, const size_t n, const double mean1, const double mean2) { const double covariance = FUNCTION(compute,covariance) (data1, stride1, data2, stride2, n, mean1, mean2); return covariance * ((double)n / (double)(n - 1)); } double FUNCTION(gsl_stats,covariance) (const BASE data1[], const size_t stride1, const BASE data2[], const size_t stride2, const size_t n) { const double mean1 = FUNCTION(gsl_stats,mean) (data1, stride1, n); const double mean2 = FUNCTION(gsl_stats,mean) (data2, stride2, n); return FUNCTION(gsl_stats,covariance_m)(data1, stride1, data2, stride2, n, mean1, mean2); } /* gsl_stats_correlation() Calculate Pearson correlation = cov(X, Y) / (sigma_X * sigma_Y) This routine efficiently computes the correlation in one pass of the data and makes use of the algorithm described in: B. P. Welford, "Note on a Method for Calculating Corrected Sums of Squares and Products", Technometrics, Vol 4, No 3, 1962. This paper derives a numerically stable recurrence to compute a sum of products S = sum_{i=1..N} [ (x_i - mu_x) * (y_i - mu_y) ] with the relation S_n = S_{n-1} + ((n-1)/n) * (x_n - mu_x_{n-1}) * (y_n - mu_y_{n-1}) */ double FUNCTION(gsl_stats,correlation) (const BASE data1[], const size_t stride1, const BASE data2[], const size_t stride2, const size_t n) { size_t i; long double sum_xsq = 0.0; long double sum_ysq = 0.0; long double sum_cross = 0.0; long double ratio; long double delta_x, delta_y; long double mean_x, mean_y; long double r; /* * Compute: * sum_xsq = Sum [ (x_i - mu_x)^2 ], * sum_ysq = Sum [ (y_i - mu_y)^2 ] and * sum_cross = Sum [ (x_i - mu_x) * (y_i - mu_y) ] * using the above relation from Welford's paper */ mean_x = data1[0 * stride1]; mean_y = data2[0 * stride2]; for (i = 1; i < n; ++i) { ratio = i / (i + 1.0); delta_x = data1[i * stride1] - mean_x; delta_y = data2[i * stride2] - mean_y; sum_xsq += delta_x * delta_x * ratio; sum_ysq += delta_y * delta_y * ratio; sum_cross += delta_x * delta_y * ratio; mean_x += delta_x / (i + 1.0); mean_y += delta_y / (i + 1.0); } r = sum_cross / (sqrt(sum_xsq) * sqrt(sum_ysq)); return r; } sources_5316/external/gsl/gsl_sort_vector_long_double.h0000664000176700017670000000360611705263724022310 0ustar paulpaul/* sort/gsl_sort_vector_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_LONG_DOUBLE_H__ #define __GSL_SORT_VECTOR_LONG_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_long_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_long_double (gsl_vector_long_double * v); int gsl_sort_vector_long_double_index (gsl_permutation * p, const gsl_vector_long_double * v); int gsl_sort_vector_long_double_smallest (long double * dest, const size_t k, const gsl_vector_long_double * v); int gsl_sort_vector_long_double_largest (long double * dest, const size_t k, const gsl_vector_long_double * v); int gsl_sort_vector_long_double_smallest_index (size_t * p, const size_t k, const gsl_vector_long_double * v); int gsl_sort_vector_long_double_largest_index (size_t * p, const size_t k, const gsl_vector_long_double * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_cblas__dger.c0000664000176700017670000000054411723710247017600 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dger (const enum CBLAS_ORDER order, const int M, const int N, const double alpha, const double *X, const int incX, const double *Y, const int incY, double *A, const int lda) { #define BASE double #include "gsl_cblas__source_ger.h" #undef BASE } sources_5316/external/gsl/gsl_randist__gamma.c0000664000176700017670000001177111723710247020325 0ustar paulpaul/* randist/gamma.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_sf_gamma.h" #include "gsl_rng.h" #include "gsl_randist.h" static double gamma_large (const gsl_rng * r, const double a); static double gamma_frac (const gsl_rng * r, const double a); /* The Gamma distribution of order a>0 is defined by: p(x) dx = {1 / \Gamma(a) b^a } x^{a-1} e^{-x/b} dx for x>0. If X and Y are independent gamma-distributed random variables of order a1 and a2 with the same scale parameter b, then X+Y has gamma distribution of order a1+a2. The algorithms below are from Knuth, vol 2, 2nd ed, p. 129. */ double gsl_ran_gamma_knuth (const gsl_rng * r, const double a, const double b) { /* assume a > 0 */ unsigned int na = floor (a); if (a == na) { return b * gsl_ran_gamma_int (r, na); } else if (na == 0) { return b * gamma_frac (r, a); } else { return b * (gsl_ran_gamma_int (r, na) + gamma_frac (r, a - na)) ; } } double gsl_ran_gamma_int (const gsl_rng * r, const unsigned int a) { if (a < 12) { unsigned int i; double prod = 1; for (i = 0; i < a; i++) { prod *= gsl_rng_uniform_pos (r); } /* Note: for 12 iterations we are safe against underflow, since the smallest positive random number is O(2^-32). This means the smallest possible product is 2^(-12*32) = 10^-116 which is within the range of double precision. */ return -log (prod); } else { return gamma_large (r, (double) a); } } static double gamma_large (const gsl_rng * r, const double a) { /* Works only if a > 1, and is most efficient if a is large This algorithm, reported in Knuth, is attributed to Ahrens. A faster one, we are told, can be found in: J. H. Ahrens and U. Dieter, Computing 12 (1974) 223-246. */ double sqa, x, y, v; sqa = sqrt (2 * a - 1); do { do { y = tan (M_PI * gsl_rng_uniform (r)); x = sqa * y + a - 1; } while (x <= 0); v = gsl_rng_uniform (r); } while (v > (1 + y * y) * exp ((a - 1) * log (x / (a - 1)) - sqa * y)); return x; } static double gamma_frac (const gsl_rng * r, const double a) { /* This is exercise 16 from Knuth; see page 135, and the solution is on page 551. */ double p, q, x, u, v; p = M_E / (a + M_E); do { u = gsl_rng_uniform (r); v = gsl_rng_uniform_pos (r); if (u < p) { x = exp ((1 / a) * log (v)); q = exp (-x); } else { x = 1 - log (v); q = exp ((a - 1) * log (x)); } } while (gsl_rng_uniform (r) >= q); return x; } double gsl_ran_gamma_pdf (const double x, const double a, const double b) { if (x < 0) { return 0 ; } else if (x == 0) { if (a == 1) return 1/b ; else return 0 ; } else if (a == 1) { return exp(-x/b)/b ; } else { double p; double lngamma = gsl_sf_lngamma (a); p = exp ((a - 1) * log (x/b) - x/b - lngamma)/b; return p; } } /* New version based on Marsaglia and Tsang, "A Simple Method for * generating gamma variables", ACM Transactions on Mathematical * Software, Vol 26, No 3 (2000), p363-372. * * Implemented by J.D.Lamb@btinternet.com, minor modifications for GSL * by Brian Gough */ double gsl_ran_gamma_mt (const gsl_rng * r, const double a, const double b) { return gsl_ran_gamma (r, a, b); } double gsl_ran_gamma (const gsl_rng * r, const double a, const double b) { /* assume a > 0 */ if (a < 1) { double u = gsl_rng_uniform_pos (r); return gsl_ran_gamma (r, 1.0 + a, b) * pow (u, 1.0 / a); } { double x, v, u; double d = a - 1.0 / 3.0; double c = (1.0 / 3.0) / sqrt (d); while (1) { do { x = gsl_ran_gaussian_ziggurat (r, 1.0); v = 1.0 + c * x; } while (v <= 0); v = v * v * v; u = gsl_rng_uniform_pos (r); if (u < 1 - 0.0331 * x * x * x * x) break; if (log (u) < 0.5 * x * x + d * (1 - v + log (v))) break; } return b * d * v; } } sources_5316/external/gsl/gsl_sys__fdiv.c0000664000176700017670000000167011723710247017342 0ustar paulpaul/* sys/fdiv.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include double gsl_fdiv (const double x, const double y); double gsl_fdiv (const double x, const double y) { return x / y; } sources_5316/external/gsl/gsl_sf__beta_inc.c0000644000176700017670000001334610707442037017751 0ustar paulpaul/* specfunc/beta_inc.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_log.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_hyperg.h" #include "gsl_sf__error.h" #include "gsl_sf__check.h" static double isnegint (const double x) { return (x < 0) && (x == floor(x)); } static int beta_cont_frac( const double a, const double b, const double x, gsl_sf_result * result ) { const unsigned int max_iter = 512; /* control iterations */ const double cutoff = 2.0 * GSL_DBL_MIN; /* control the zero cutoff */ unsigned int iter_count = 0; double cf; /* standard initialization for continued fraction */ double num_term = 1.0; double den_term = 1.0 - (a+b)*x/(a+1.0); if (fabs(den_term) < cutoff) den_term = cutoff; den_term = 1.0/den_term; cf = den_term; while(iter_count < max_iter) { const int k = iter_count + 1; double coeff = k*(b-k)*x/(((a-1.0)+2*k)*(a+2*k)); double delta_frac; /* first step */ den_term = 1.0 + coeff*den_term; num_term = 1.0 + coeff/num_term; if(fabs(den_term) < cutoff) den_term = cutoff; if(fabs(num_term) < cutoff) num_term = cutoff; den_term = 1.0/den_term; delta_frac = den_term * num_term; cf *= delta_frac; coeff = -(a+k)*(a+b+k)*x/((a+2*k)*(a+2*k+1.0)); /* second step */ den_term = 1.0 + coeff*den_term; num_term = 1.0 + coeff/num_term; if(fabs(den_term) < cutoff) den_term = cutoff; if(fabs(num_term) < cutoff) num_term = cutoff; den_term = 1.0/den_term; delta_frac = den_term*num_term; cf *= delta_frac; if(fabs(delta_frac-1.0) < 2.0*GSL_DBL_EPSILON) break; ++iter_count; } result->val = cf; result->err = iter_count * 4.0 * GSL_DBL_EPSILON * fabs(cf); if(iter_count >= max_iter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_beta_inc_e( const double a, const double b, const double x, gsl_sf_result * result ) { if(x < 0.0 || x > 1.0) { DOMAIN_ERROR(result); } else if (isnegint(a) || isnegint(b)) { DOMAIN_ERROR(result); } else if (isnegint(a+b)) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x == 1.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if (a <= 0 || b <= 0) { gsl_sf_result f, beta; int stat; const int stat_f = gsl_sf_hyperg_2F1_e(a, 1-b, a+1, x, &f); const int stat_beta = gsl_sf_beta_e(a, b, &beta); double prefactor = (pow(x, a) / a); result->val = prefactor * f.val / beta.val; result->err = fabs(prefactor) * f.err/ fabs(beta.val) + fabs(result->val/beta.val) * beta.err; stat = GSL_ERROR_SELECT_2(stat_f, stat_beta); if(stat == GSL_SUCCESS) { CHECK_UNDERFLOW(result); } return stat; } else { gsl_sf_result ln_beta; gsl_sf_result ln_x; gsl_sf_result ln_1mx; gsl_sf_result prefactor; const int stat_ln_beta = gsl_sf_lnbeta_e(a, b, &ln_beta); const int stat_ln_1mx = gsl_sf_log_1plusx_e(-x, &ln_1mx); const int stat_ln_x = gsl_sf_log_e(x, &ln_x); const int stat_ln = GSL_ERROR_SELECT_3(stat_ln_beta, stat_ln_1mx, stat_ln_x); const double ln_pre_val = -ln_beta.val + a * ln_x.val + b * ln_1mx.val; const double ln_pre_err = ln_beta.err + fabs(a*ln_x.err) + fabs(b*ln_1mx.err); const int stat_exp = gsl_sf_exp_err_e(ln_pre_val, ln_pre_err, &prefactor); if(stat_ln != GSL_SUCCESS) { result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_ESANITY); } if(x < (a + 1.0)/(a+b+2.0)) { /* Apply continued fraction directly. */ gsl_sf_result cf; const int stat_cf = beta_cont_frac(a, b, x, &cf); int stat; result->val = prefactor.val * cf.val / a; result->err = (fabs(prefactor.err * cf.val) + fabs(prefactor.val * cf.err))/a; stat = GSL_ERROR_SELECT_2(stat_exp, stat_cf); if(stat == GSL_SUCCESS) { CHECK_UNDERFLOW(result); } return stat; } else { /* Apply continued fraction after hypergeometric transformation. */ gsl_sf_result cf; const int stat_cf = beta_cont_frac(b, a, 1.0-x, &cf); int stat; const double term = prefactor.val * cf.val / b; result->val = 1.0 - term; result->err = fabs(prefactor.err * cf.val)/b; result->err += fabs(prefactor.val * cf.err)/b; result->err += 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(term)); stat = GSL_ERROR_SELECT_2(stat_exp, stat_cf); if(stat == GSL_SUCCESS) { CHECK_UNDERFLOW(result); } return stat; } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_beta_inc(const double a, const double b, const double x) { EVAL_RESULT(gsl_sf_beta_inc_e(a, b, x, &result)); } sources_5316/external/gsl/gsl_specfunc__bessel_k.c0000664000176700017670000001452411723710247021173 0ustar paulpaul/* specfunc/bessel_k.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_gamma.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__check.h" #include "gsl_specfunc__bessel.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* [Abramowitz+Stegun, 10.2.4 + 10.2.6] * with lmax=15, precision ~ 15D for x < 3 * * assumes l >= 1 */ static int bessel_kl_scaled_small_x(int l, const double x, gsl_sf_result * result) { gsl_sf_result num_fact; double den = gsl_sf_pow_int(x, l+1); int stat_df = gsl_sf_doublefact_e((unsigned int) (2*l-1), &num_fact); if(stat_df != GSL_SUCCESS || den == 0.0) { OVERFLOW_ERROR(result); } else { const int lmax = 50; gsl_sf_result ipos_term; double ineg_term; double sgn = (GSL_IS_ODD(l) ? -1.0 : 1.0); double ex = exp(x); double t = 0.5*x*x; double sum = 1.0; double t_coeff = 1.0; double t_power = 1.0; double delta; int stat_il; int i; for(i=1; ival = -sgn * 0.5*M_PI * (ex*ipos_term.val - ineg_term); result->val *= ex; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_il; } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_k0_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else { result->val = M_PI/(2.0*x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_bessel_k1_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < (M_SQRTPI+1.0)/(M_SQRT2*GSL_SQRT_DBL_MAX)) { OVERFLOW_ERROR(result); } else { result->val = M_PI/(2.0*x) * (1.0 + 1.0/x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_bessel_k2_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0/GSL_ROOT3_DBL_MAX) { OVERFLOW_ERROR(result); } else { result->val = M_PI/(2.0*x) * (1.0 + 3.0/x * (1.0 + 1.0/x)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_bessel_kl_scaled_e(int l, const double x, gsl_sf_result * result) { if(l < 0 || x <= 0.0) { DOMAIN_ERROR(result); } else if(l == 0) { return gsl_sf_bessel_k0_scaled_e(x, result); } else if(l == 1) { return gsl_sf_bessel_k1_scaled_e(x, result); } else if(l == 2) { return gsl_sf_bessel_k2_scaled_e(x, result); } else if(x < 3.0) { return bessel_kl_scaled_small_x(l, x, result); } else if(GSL_ROOT3_DBL_EPSILON * x > (l*l + l + 1)) { int status = gsl_sf_bessel_Knu_scaled_asympx_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= pre; result->err *= pre; return status; } else if(GSL_MIN(0.29/(l*l+1.0), 0.5/(l*l+1.0+x*x)) < GSL_ROOT3_DBL_EPSILON) { int status = gsl_sf_bessel_Knu_scaled_asymp_unif_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= pre; result->err *= pre; return status; } else { /* recurse upward */ gsl_sf_result r_bk; gsl_sf_result r_bkm; int stat_1 = gsl_sf_bessel_k1_scaled_e(x, &r_bk); int stat_0 = gsl_sf_bessel_k0_scaled_e(x, &r_bkm); double bkp; double bk = r_bk.val; double bkm = r_bkm.val; int j; for(j=1; jval = bk; result->err = fabs(bk) * (fabs(r_bk.err/r_bk.val) + fabs(r_bkm.err/r_bkm.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_1, stat_0); } } int gsl_sf_bessel_kl_scaled_array(const int lmax, const double x, double * result_array) { if(lmax < 0 || x <= 0.0) { GSL_ERROR("domain error", GSL_EDOM); } else if (lmax == 0) { gsl_sf_result result; int stat = gsl_sf_bessel_k0_scaled_e(x, &result); result_array[0] = result.val; return stat; } else { int ell; double kellp1, kell, kellm1; gsl_sf_result r_kell; gsl_sf_result r_kellm1; gsl_sf_bessel_k1_scaled_e(x, &r_kell); gsl_sf_bessel_k0_scaled_e(x, &r_kellm1); kell = r_kell.val; kellm1 = r_kellm1.val; result_array[0] = kellm1; result_array[1] = kell; for(ell = 1; ell < lmax; ell++) { kellp1 = (2*ell+1)/x * kell + kellm1; result_array[ell+1] = kellp1; kellm1 = kell; kell = kellp1; } return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_k0_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_k0_scaled_e(x, &result)); } double gsl_sf_bessel_k1_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_k1_scaled_e(x, &result)); } double gsl_sf_bessel_k2_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_k2_scaled_e(x, &result)); } double gsl_sf_bessel_kl_scaled(const int l, const double x) { EVAL_RESULT(gsl_sf_bessel_kl_scaled_e(l, x, &result)); } sources_5316/external/gsl/gsl_histogram__reset.c0000664000176700017670000000202011723710247020701 0ustar paulpaul/* histogram/reset.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_histogram.h" void gsl_histogram_reset (gsl_histogram * h) { size_t i; const size_t n = h->n; for (i = 0; i < n; i++) { h->bin[i] = 0; } } sources_5316/external/gsl/gsl_fft_real_float.h0000664000176700017670000000450211705263724020331 0ustar paulpaul/* fft/gsl_fft_real_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_FFT_REAL_FLOAT_H__ #define __GSL_FFT_REAL_FLOAT_H__ #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_fft.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_fft_real_float_radix2_transform (float data[], const size_t stride, const size_t n) ; typedef struct { size_t n; size_t nf; size_t factor[64]; gsl_complex_float *twiddle[64]; gsl_complex_float *trig; } gsl_fft_real_wavetable_float; typedef struct { size_t n; float *scratch; } gsl_fft_real_workspace_float; gsl_fft_real_wavetable_float * gsl_fft_real_wavetable_float_alloc (size_t n); void gsl_fft_real_wavetable_float_free (gsl_fft_real_wavetable_float * wavetable); gsl_fft_real_workspace_float * gsl_fft_real_workspace_float_alloc (size_t n); void gsl_fft_real_workspace_float_free (gsl_fft_real_workspace_float * workspace); int gsl_fft_real_float_transform (float data[], const size_t stride, const size_t n, const gsl_fft_real_wavetable_float * wavetable, gsl_fft_real_workspace_float * work); int gsl_fft_real_float_unpack (const float real_float_coefficient[], float complex_coefficient[], const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_FFT_REAL_FLOAT_H__ */ sources_5316/external/gsl/gsl_randist__rayleigh.c0000664000176700017670000000377311723710247021052 0ustar paulpaul/* randist/rayleigh.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* The Rayleigh distribution has the form p(x) dx = (x / sigma^2) exp(-x^2/(2 sigma^2)) dx for x = 0 ... +infty */ double gsl_ran_rayleigh (const gsl_rng * r, const double sigma) { double u = gsl_rng_uniform_pos (r); return sigma * sqrt(-2.0 * log (u)); } double gsl_ran_rayleigh_pdf (const double x, const double sigma) { if (x < 0) { return 0 ; } else { double u = x / sigma ; double p = (u / sigma) * exp(-u * u / 2.0) ; return p; } } /* The Rayleigh tail distribution has the form p(x) dx = (x / sigma^2) exp((a^2 - x^2)/(2 sigma^2)) dx for x = a ... +infty */ double gsl_ran_rayleigh_tail (const gsl_rng * r, const double a, const double sigma) { double u = gsl_rng_uniform_pos (r); return sqrt(a * a - 2.0 * sigma * sigma * log (u)); } double gsl_ran_rayleigh_tail_pdf (const double x, const double a, const double sigma) { if (x < a) { return 0 ; } else { double u = x / sigma ; double v = a / sigma ; double p = (u / sigma) * exp((v + u) * (v - u) / 2.0) ; return p; } } sources_5316/external/gsl/gsl_cblas__hypot.c0000664000176700017670000000065611723710247020026 0ustar paulpaul#include static double xhypot (const double x, const double y); static double xhypot (const double x, const double y) { double xabs = fabs(x) ; double yabs = fabs(y) ; double min, max; if (xabs < yabs) { min = xabs ; max = yabs ; } else { min = yabs ; max = xabs ; } if (min == 0) { return max ; } { double u = min / max ; return max * sqrt (1 + u * u) ; } } sources_5316/external/gsl/gsl_cblas__source_rotmg.h0000664000176700017670000000552011705263724021376 0ustar paulpaul/* blas/source_rotmg.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const BASE G = 4096.0, G2 = G * G; BASE D1 = *d1, D2 = *d2, x = *b1, y = b2; BASE h11, h12, h21, h22, u; BASE c, s; /* case of d1 < 0, appendix A, second to last paragraph */ if (D1 < 0.0) { P[0] = -1; P[1] = 0; P[2] = 0; P[3] = 0; P[4] = 0; *d1 = 0; *d2 = 0; *b1 = 0; return; } if (D2 * y == 0.0) { P[0] = -2; /* case of H = I, page 315 */ return; } c = fabs(D1 * x * x); s = fabs(D2 * y * y); if (c > s) { /* case of equation A6 */ P[0] = 0.0; h11 = 1; h12 = (D2 * y) / (D1 * x); h21 = -y / x; h22 = 1; u = 1 - h21 * h12; if (u <= 0.0) { /* the case u <= 0 is rejected */ P[0] = -1; P[1] = 0; P[2] = 0; P[3] = 0; P[4] = 0; *d1 = 0; *d2 = 0; *b1 = 0; return; } D1 /= u; D2 /= u; x *= u; } else { /* case of equation A7 */ if (D2 * y * y < 0.0) { P[0] = -1; P[1] = 0; P[2] = 0; P[3] = 0; P[4] = 0; *d1 = 0; *d2 = 0; *b1 = 0; return; } P[0] = 1; h11 = (D1 * x) / (D2 * y); h12 = 1; h21 = -1; h22 = x / y; u = 1 + h11 * h22; D1 /= u; D2 /= u; { BASE tmp = D2; D2 = D1; D1 = tmp; } x = y * u; } /* rescale D1 to range [1/G2,G2] */ while (D1 <= 1.0 / G2 && D1 != 0.0) { P[0] = -1; D1 *= G2; x /= G; h11 /= G; h12 /= G; } while (D1 >= G2) { P[0] = -1; D1 /= G2; x *= G; h11 *= G; h12 *= G; } /* rescale D2 to range [1/G2,G2] */ while (fabs(D2) <= 1.0 / G2 && D2 != 0.0) { P[0] = -1; D2 *= G2; h21 /= G; h22 /= G; } while (fabs(D2) >= G2) { P[0] = -1; D2 /= G2; h21 *= G; h22 *= G; } *d1 = D1; *d2 = D2; *b1 = x; if (P[0] == -1.0) { P[1] = h11; P[2] = h21; P[3] = h12; P[4] = h22; } else if (P[0] == 0.0) { P[2] = h21; P[3] = h12; } else if (P[0] == 1.0) { P[1] = h11; P[4] = h22; } } sources_5316/external/gsl/gsl_histogram__calloc_range2d.c0000664000176700017670000000733411723710247022433 0ustar paulpaul/* gsl_histogram2d_calloc_range.c * Copyright (C) 2000 Simone Piccardi * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File gsl_histogram2d_calloc_range.c: * Routine to create a variable binning 2D histogram providing * the input range vectors. Need GSL library and header. * Do range check and allocate the histogram data. * * Author: S. Piccardi * Jan. 2000 * ***************************************************************/ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram2d.h" /* * Routine that create a 2D histogram using the given * values for X and Y ranges */ gsl_histogram2d * gsl_histogram2d_calloc_range (size_t nx, size_t ny, double *xrange, double *yrange) { size_t i, j; gsl_histogram2d *h; /* check arguments */ if (nx == 0) { GSL_ERROR_VAL ("histogram length nx must be positive integer", GSL_EDOM, 0); } if (ny == 0) { GSL_ERROR_VAL ("histogram length ny must be positive integer", GSL_EDOM, 0); } /* init ranges */ for (i = 0; i < nx; i++) { if (xrange[i] >= xrange[i + 1]) { GSL_ERROR_VAL ("histogram xrange not in increasing order", GSL_EDOM, 0); } } for (j = 0; j < ny; j++) { if (yrange[j] >= yrange[j + 1]) { GSL_ERROR_VAL ("histogram yrange not in increasing order" ,GSL_EDOM, 0); } } /* Allocate histogram */ h = (gsl_histogram2d *) malloc (sizeof (gsl_histogram2d)); if (h == 0) { GSL_ERROR_VAL ("failed to allocate space for histogram struct", GSL_ENOMEM, 0); } h->xrange = (double *) malloc ((nx + 1) * sizeof (double)); if (h->xrange == 0) { /* exception in constructor, avoid memory leak */ free (h); GSL_ERROR_VAL ("failed to allocate space for histogram xrange", GSL_ENOMEM, 0); } h->yrange = (double *) malloc ((ny + 1) * sizeof (double)); if (h->yrange == 0) { /* exception in constructor, avoid memory leak */ free (h); GSL_ERROR_VAL ("failed to allocate space for histogram yrange", GSL_ENOMEM, 0); } h->bin = (double *) malloc (nx * ny * sizeof (double)); if (h->bin == 0) { /* exception in constructor, avoid memory leak */ free (h->xrange); free (h->yrange); free (h); GSL_ERROR_VAL ("failed to allocate space for histogram bins", GSL_ENOMEM, 0); } /* init histogram */ /* init ranges */ for (i = 0; i <= nx; i++) { h->xrange[i] = xrange[i]; } for (j = 0; j <= ny; j++) { h->yrange[j] = yrange[j]; } /* clear contents */ for (i = 0; i < nx; i++) { for (j = 0; j < ny; j++) { h->bin[i * ny + j] = 0; } } h->nx = nx; h->ny = ny; return h; } sources_5316/external/gsl/gsl_vector_uint.h0000664000176700017670000001612311705263724017725 0ustar paulpaul/* vector/gsl_vector_uint.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_UINT_H__ #define __GSL_VECTOR_UINT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_uint.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; unsigned int *data; gsl_block_uint *block; int owner; } gsl_vector_uint; typedef struct { gsl_vector_uint vector; } _gsl_vector_uint_view; typedef _gsl_vector_uint_view gsl_vector_uint_view; typedef struct { gsl_vector_uint vector; } _gsl_vector_uint_const_view; typedef const _gsl_vector_uint_const_view gsl_vector_uint_const_view; /* Allocation */ gsl_vector_uint *gsl_vector_uint_alloc (const size_t n); gsl_vector_uint *gsl_vector_uint_calloc (const size_t n); gsl_vector_uint *gsl_vector_uint_alloc_from_block (gsl_block_uint * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_uint *gsl_vector_uint_alloc_from_vector (gsl_vector_uint * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_uint_free (gsl_vector_uint * v); /* Views */ _gsl_vector_uint_view gsl_vector_uint_view_array (unsigned int *v, size_t n); _gsl_vector_uint_view gsl_vector_uint_view_array_with_stride (unsigned int *base, size_t stride, size_t n); _gsl_vector_uint_const_view gsl_vector_uint_const_view_array (const unsigned int *v, size_t n); _gsl_vector_uint_const_view gsl_vector_uint_const_view_array_with_stride (const unsigned int *base, size_t stride, size_t n); _gsl_vector_uint_view gsl_vector_uint_subvector (gsl_vector_uint *v, size_t i, size_t n); _gsl_vector_uint_view gsl_vector_uint_subvector_with_stride (gsl_vector_uint *v, size_t i, size_t stride, size_t n); _gsl_vector_uint_const_view gsl_vector_uint_const_subvector (const gsl_vector_uint *v, size_t i, size_t n); _gsl_vector_uint_const_view gsl_vector_uint_const_subvector_with_stride (const gsl_vector_uint *v, size_t i, size_t stride, size_t n); /* Operations */ unsigned int gsl_vector_uint_get (const gsl_vector_uint * v, const size_t i); void gsl_vector_uint_set (gsl_vector_uint * v, const size_t i, unsigned int x); unsigned int *gsl_vector_uint_ptr (gsl_vector_uint * v, const size_t i); const unsigned int *gsl_vector_uint_const_ptr (const gsl_vector_uint * v, const size_t i); void gsl_vector_uint_set_zero (gsl_vector_uint * v); void gsl_vector_uint_set_all (gsl_vector_uint * v, unsigned int x); int gsl_vector_uint_set_basis (gsl_vector_uint * v, size_t i); int gsl_vector_uint_fread (FILE * stream, gsl_vector_uint * v); int gsl_vector_uint_fwrite (FILE * stream, const gsl_vector_uint * v); int gsl_vector_uint_fscanf (FILE * stream, gsl_vector_uint * v); int gsl_vector_uint_fprintf (FILE * stream, const gsl_vector_uint * v, const char *format); int gsl_vector_uint_memcpy (gsl_vector_uint * dest, const gsl_vector_uint * src); int gsl_vector_uint_reverse (gsl_vector_uint * v); int gsl_vector_uint_swap (gsl_vector_uint * v, gsl_vector_uint * w); int gsl_vector_uint_swap_elements (gsl_vector_uint * v, const size_t i, const size_t j); unsigned int gsl_vector_uint_max (const gsl_vector_uint * v); unsigned int gsl_vector_uint_min (const gsl_vector_uint * v); void gsl_vector_uint_minmax (const gsl_vector_uint * v, unsigned int * min_out, unsigned int * max_out); size_t gsl_vector_uint_max_index (const gsl_vector_uint * v); size_t gsl_vector_uint_min_index (const gsl_vector_uint * v); void gsl_vector_uint_minmax_index (const gsl_vector_uint * v, size_t * imin, size_t * imax); int gsl_vector_uint_add (gsl_vector_uint * a, const gsl_vector_uint * b); int gsl_vector_uint_sub (gsl_vector_uint * a, const gsl_vector_uint * b); int gsl_vector_uint_mul (gsl_vector_uint * a, const gsl_vector_uint * b); int gsl_vector_uint_div (gsl_vector_uint * a, const gsl_vector_uint * b); int gsl_vector_uint_scale (gsl_vector_uint * a, const double x); int gsl_vector_uint_add_constant (gsl_vector_uint * a, const double x); int gsl_vector_uint_isnull (const gsl_vector_uint * v); int gsl_vector_uint_ispos (const gsl_vector_uint * v); int gsl_vector_uint_isneg (const gsl_vector_uint * v); int gsl_vector_uint_isnonneg (const gsl_vector_uint * v); #ifdef HAVE_INLINE extern inline unsigned int gsl_vector_uint_get (const gsl_vector_uint * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_uint_set (gsl_vector_uint * v, const size_t i, unsigned int x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline unsigned int * gsl_vector_uint_ptr (gsl_vector_uint * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (unsigned int *) (v->data + i * v->stride); } extern inline const unsigned int * gsl_vector_uint_const_ptr (const gsl_vector_uint * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const unsigned int *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_UINT_H__ */ sources_5316/external/gsl/gsl_sf__bessel.c0000644000176700017670000006450110707442037017461 0ustar paulpaul/* specfunc/bessel.c * * Copyright (C) 1996,1997,1998,1999,2000,2001,2002,2003 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Miscellaneous support functions for Bessel function evaluations. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_airy.h" #include "gsl_sf_elementary.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_trig.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel_amp_phase.h" #include "gsl_sf__bessel_temme.h" #include "gsl_sf__bessel.h" #define CubeRoot2_ 1.25992104989487316476721060728 /* Debye functions [Abramowitz+Stegun, 9.3.9-10] */ inline static double debye_u1(const double * tpow) { return (3.0*tpow[1] - 5.0*tpow[3])/24.0; } inline static double debye_u2(const double * tpow) { return (81.0*tpow[2] - 462.0*tpow[4] + 385.0*tpow[6])/1152.0; } inline static double debye_u3(const double * tpow) { return (30375.0*tpow[3] - 369603.0*tpow[5] + 765765.0*tpow[7] - 425425.0*tpow[9])/414720.0; } inline static double debye_u4(const double * tpow) { return (4465125.0*tpow[4] - 94121676.0*tpow[6] + 349922430.0*tpow[8] - 446185740.0*tpow[10] + 185910725.0*tpow[12])/39813120.0; } inline static double debye_u5(const double * tpow) { return (1519035525.0*tpow[5] - 49286948607.0*tpow[7] + 284499769554.0*tpow[9] - 614135872350.0*tpow[11] + 566098157625.0*tpow[13] - 188699385875.0*tpow[15])/6688604160.0; } #if 0 inline static double debye_u6(const double * tpow) { return (2757049477875.0*tpow[6] - 127577298354750.0*tpow[8] + 1050760774457901.0*tpow[10] - 3369032068261860.0*tpow[12] + 5104696716244125.0*tpow[14] - 3685299006138750.0*tpow[16] + 1023694168371875.0*tpow[18])/4815794995200.0; } #endif /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_IJ_taylor_e(const double nu, const double x, const int sign, const int kmax, const double threshold, gsl_sf_result * result ) { /* CHECK_POINTER(result) */ if(nu < 0.0 || x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { if(nu == 0.0) { result->val = 1.0; result->err = 0.0; } else { result->val = 0.0; result->err = 0.0; } return GSL_SUCCESS; } else { gsl_sf_result prefactor; /* (x/2)^nu / Gamma(nu+1) */ gsl_sf_result sum; int stat_pre; int stat_sum; int stat_mul; if(nu == 0.0) { prefactor.val = 1.0; prefactor.err = 0.0; stat_pre = GSL_SUCCESS; } else if(nu < INT_MAX-1) { /* Separate the integer part and use * y^nu / Gamma(nu+1) = y^N /N! y^f / (N+1)_f, * to control the error. */ const int N = (int)floor(nu + 0.5); const double f = nu - N; gsl_sf_result poch_factor; gsl_sf_result tc_factor; const int stat_poch = gsl_sf_poch_e(N+1.0, f, &poch_factor); const int stat_tc = gsl_sf_taylorcoeff_e(N, 0.5*x, &tc_factor); const double p = pow(0.5*x,f); prefactor.val = tc_factor.val * p / poch_factor.val; prefactor.err = tc_factor.err * p / poch_factor.val; prefactor.err += fabs(prefactor.val) / poch_factor.val * poch_factor.err; prefactor.err += 2.0 * GSL_DBL_EPSILON * fabs(prefactor.val); stat_pre = GSL_ERROR_SELECT_2(stat_tc, stat_poch); } else { gsl_sf_result lg; const int stat_lg = gsl_sf_lngamma_e(nu+1.0, &lg); const double term1 = nu*log(0.5*x); const double term2 = lg.val; const double ln_pre = term1 - term2; const double ln_pre_err = GSL_DBL_EPSILON * (fabs(term1)+fabs(term2)) + lg.err; const int stat_ex = gsl_sf_exp_err_e(ln_pre, ln_pre_err, &prefactor); stat_pre = GSL_ERROR_SELECT_2(stat_ex, stat_lg); } /* Evaluate the sum. * [Abramowitz+Stegun, 9.1.10] * [Abramowitz+Stegun, 9.6.7] */ { const double y = sign * 0.25 * x*x; double sumk = 1.0; double term = 1.0; int k; for(k=1; k<=kmax; k++) { term *= y/((nu+k)*k); sumk += term; if(fabs(term/sumk) < threshold) break; } sum.val = sumk; sum.err = threshold * fabs(sumk); stat_sum = ( k >= kmax ? GSL_EMAXITER : GSL_SUCCESS ); } stat_mul = gsl_sf_multiply_err_e(prefactor.val, prefactor.err, sum.val, sum.err, result); return GSL_ERROR_SELECT_3(stat_mul, stat_pre, stat_sum); } } /* x >> nu*nu+1 * error ~ O( ((nu*nu+1)/x)^4 ) * * empirical error analysis: * choose GSL_ROOT4_MACH_EPS * x > (nu*nu + 1) * * This is not especially useful. When the argument gets * large enough for this to apply, the cos() and sin() * start loosing digits. However, this seems inevitable * for this particular method. * * Wed Jun 25 14:39:38 MDT 2003 [GJ] * This function was inconsistent since the Q term did not * go to relative order eps^2. That's why the error estimate * originally given was screwy (it didn't make sense that the * "empirical" error was coming out O(eps^3)). * With Q to proper order, the error is O(eps^4). */ int gsl_sf_bessel_Jnu_asympx_e(const double nu, const double x, gsl_sf_result * result) { double mu = 4.0*nu*nu; double mum1 = mu-1.0; double mum9 = mu-9.0; double mum25 = mu-25.0; double chi = x - (0.5*nu + 0.25)*M_PI; double P = 1.0 - mum1*mum9/(128.0*x*x); double Q = mum1/(8.0*x) * (1.0 - mum9*mum25/(384.0*x*x)); double pre = sqrt(2.0/(M_PI*x)); double c = cos(chi); double s = sin(chi); double r = mu/x; result->val = pre * (c*P - s*Q); result->err = pre * GSL_DBL_EPSILON * (1.0 + fabs(x)) * (fabs(c*P) + fabs(s*Q)); result->err += pre * fabs(0.1*r*r*r*r); return GSL_SUCCESS; } /* x >> nu*nu+1 */ int gsl_sf_bessel_Ynu_asympx_e(const double nu, const double x, gsl_sf_result * result) { double ampl; double theta; double alpha = x; double beta = -0.5*nu*M_PI; int stat_a = gsl_sf_bessel_asymp_Mnu_e(nu, x, &l); int stat_t = gsl_sf_bessel_asymp_thetanu_corr_e(nu, x, &theta); double sin_alpha = sin(alpha); double cos_alpha = cos(alpha); double sin_chi = sin(beta + theta); double cos_chi = cos(beta + theta); double sin_term = sin_alpha * cos_chi + sin_chi * cos_alpha; double sin_term_mag = fabs(sin_alpha * cos_chi) + fabs(sin_chi * cos_alpha); result->val = ampl * sin_term; result->err = fabs(ampl) * GSL_DBL_EPSILON * sin_term_mag; result->err += fabs(result->val) * 2.0 * GSL_DBL_EPSILON; if(fabs(alpha) > 1.0/GSL_DBL_EPSILON) { result->err *= 0.5 * fabs(alpha); } else if(fabs(alpha) > 1.0/GSL_SQRT_DBL_EPSILON) { result->err *= 256.0 * fabs(alpha) * GSL_SQRT_DBL_EPSILON; } return GSL_ERROR_SELECT_2(stat_t, stat_a); } /* x >> nu*nu+1 */ int gsl_sf_bessel_Inu_scaled_asympx_e(const double nu, const double x, gsl_sf_result * result) { double mu = 4.0*nu*nu; double mum1 = mu-1.0; double mum9 = mu-9.0; double pre = 1.0/sqrt(2.0*M_PI*x); double r = mu/x; result->val = pre * (1.0 - mum1/(8.0*x) + mum1*mum9/(128.0*x*x)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * fabs(0.1*r*r*r); return GSL_SUCCESS; } /* x >> nu*nu+1 */ int gsl_sf_bessel_Knu_scaled_asympx_e(const double nu, const double x, gsl_sf_result * result) { double mu = 4.0*nu*nu; double mum1 = mu-1.0; double mum9 = mu-9.0; double pre = sqrt(M_PI/(2.0*x)); double r = nu/x; result->val = pre * (1.0 + mum1/(8.0*x) + mum1*mum9/(128.0*x*x)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * fabs(0.1*r*r*r); return GSL_SUCCESS; } /* nu -> Inf; uniform in x > 0 [Abramowitz+Stegun, 9.7.7] * * error: * The error has the form u_N(t)/nu^N where 0 <= t <= 1. * It is not hard to show that |u_N(t)| is small for such t. * We have N=6 here, and |u_6(t)| < 0.025, so the error is clearly * bounded by 0.025/nu^6. This gives the asymptotic bound on nu * seen below as nu ~ 100. For general MACH_EPS it will be * nu > 0.5 / MACH_EPS^(1/6) * When t is small, the bound is even better because |u_N(t)| vanishes * as t->0. In fact u_N(t) ~ C t^N as t->0, with C ~= 0.1. * We write * err_N <= min(0.025, C(1/(1+(x/nu)^2))^3) / nu^6 * therefore * min(0.29/nu^2, 0.5/(nu^2+x^2)) < MACH_EPS^{1/3} * and this is the general form. * * empirical error analysis, assuming 14 digit requirement: * choose x > 50.000 nu ==> nu > 3 * choose x > 10.000 nu ==> nu > 15 * choose x > 2.000 nu ==> nu > 50 * choose x > 1.000 nu ==> nu > 75 * choose x > 0.500 nu ==> nu > 80 * choose x > 0.100 nu ==> nu > 83 * * This makes sense. For x << nu, the error will be of the form u_N(1)/nu^N, * since the polynomial term will be evaluated near t=1, so the bound * on nu will become constant for small x. Furthermore, increasing x with * nu fixed will decrease the error. */ int gsl_sf_bessel_Inu_scaled_asymp_unif_e(const double nu, const double x, gsl_sf_result * result) { int i; double z = x/nu; double root_term = hypot(1.0,z); double pre = 1.0/sqrt(2.0*M_PI*nu * root_term); double eta = root_term + log(z/(1.0+root_term)); double ex_arg = ( z < 1.0/GSL_ROOT3_DBL_EPSILON ? nu*(-z + eta) : -0.5*nu/z*(1.0 - 1.0/(12.0*z*z)) ); gsl_sf_result ex_result; int stat_ex = gsl_sf_exp_e(ex_arg, &ex_result); if(stat_ex == GSL_SUCCESS) { double t = 1.0/root_term; double sum; double tpow[16]; tpow[0] = 1.0; for(i=1; i<16; i++) tpow[i] = t * tpow[i-1]; sum = 1.0 + debye_u1(tpow)/nu + debye_u2(tpow)/(nu*nu) + debye_u3(tpow)/(nu*nu*nu) + debye_u4(tpow)/(nu*nu*nu*nu) + debye_u5(tpow)/(nu*nu*nu*nu*nu); result->val = pre * ex_result.val * sum; result->err = pre * ex_result.val / (nu*nu*nu*nu*nu*nu); result->err += pre * ex_result.err * fabs(sum); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = 0.0; result->err = 0.0; return stat_ex; } } /* nu -> Inf; uniform in x > 0 [Abramowitz+Stegun, 9.7.8] * * error: * identical to that above for Inu_scaled */ int gsl_sf_bessel_Knu_scaled_asymp_unif_e(const double nu, const double x, gsl_sf_result * result) { int i; double z = x/nu; double root_term = hypot(1.0,z); double pre = sqrt(M_PI/(2.0*nu*root_term)); double eta = root_term + log(z/(1.0+root_term)); double ex_arg = ( z < 1.0/GSL_ROOT3_DBL_EPSILON ? nu*(z - eta) : 0.5*nu/z*(1.0 + 1.0/(12.0*z*z)) ); gsl_sf_result ex_result; int stat_ex = gsl_sf_exp_e(ex_arg, &ex_result); if(stat_ex == GSL_SUCCESS) { double t = 1.0/root_term; double sum; double tpow[16]; tpow[0] = 1.0; for(i=1; i<16; i++) tpow[i] = t * tpow[i-1]; sum = 1.0 - debye_u1(tpow)/nu + debye_u2(tpow)/(nu*nu) - debye_u3(tpow)/(nu*nu*nu) + debye_u4(tpow)/(nu*nu*nu*nu) - debye_u5(tpow)/(nu*nu*nu*nu*nu); result->val = pre * ex_result.val * sum; result->err = pre * ex_result.err * fabs(sum); result->err += pre * ex_result.val / (nu*nu*nu*nu*nu*nu); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = 0.0; result->err = 0.0; return stat_ex; } } /* Evaluate J_mu(x),J_{mu+1}(x) and Y_mu(x),Y_{mu+1}(x) for |mu| < 1/2 */ int gsl_sf_bessel_JY_mu_restricted(const double mu, const double x, gsl_sf_result * Jmu, gsl_sf_result * Jmup1, gsl_sf_result * Ymu, gsl_sf_result * Ymup1) { /* CHECK_POINTER(Jmu) */ /* CHECK_POINTER(Jmup1) */ /* CHECK_POINTER(Ymu) */ /* CHECK_POINTER(Ymup1) */ if(x < 0.0 || fabs(mu) > 0.5) { Jmu->val = 0.0; Jmu->err = 0.0; Jmup1->val = 0.0; Jmup1->err = 0.0; Ymu->val = 0.0; Ymu->err = 0.0; Ymup1->val = 0.0; Ymup1->err = 0.0; GSL_ERROR ("error", GSL_EDOM); } else if(x == 0.0) { if(mu == 0.0) { Jmu->val = 1.0; Jmu->err = 0.0; } else { Jmu->val = 0.0; Jmu->err = 0.0; } Jmup1->val = 0.0; Jmup1->err = 0.0; Ymu->val = 0.0; Ymu->err = 0.0; Ymup1->val = 0.0; Ymup1->err = 0.0; GSL_ERROR ("error", GSL_EDOM); } else { int stat_Y; int stat_J; if(x < 2.0) { /* Use Taylor series for J and the Temme series for Y. * The Taylor series for J requires nu > 0, so we shift * up one and use the recursion relation to get Jmu, in * case mu < 0. */ gsl_sf_result Jmup2; int stat_J1 = gsl_sf_bessel_IJ_taylor_e(mu+1.0, x, -1, 100, GSL_DBL_EPSILON, Jmup1); int stat_J2 = gsl_sf_bessel_IJ_taylor_e(mu+2.0, x, -1, 100, GSL_DBL_EPSILON, &Jmup2); double c = 2.0*(mu+1.0)/x; Jmu->val = c * Jmup1->val - Jmup2.val; Jmu->err = c * Jmup1->err + Jmup2.err; Jmu->err += 2.0 * GSL_DBL_EPSILON * fabs(Jmu->val); stat_J = GSL_ERROR_SELECT_2(stat_J1, stat_J2); stat_Y = gsl_sf_bessel_Y_temme(mu, x, Ymu, Ymup1); return GSL_ERROR_SELECT_2(stat_J, stat_Y); } else if(x < 1000.0) { double P, Q; double J_ratio; double J_sgn; const int stat_CF1 = gsl_sf_bessel_J_CF1(mu, x, &J_ratio, &J_sgn); const int stat_CF2 = gsl_sf_bessel_JY_steed_CF2(mu, x, &P, &Q); double Jprime_J_ratio = mu/x - J_ratio; double gamma = (P - Jprime_J_ratio)/Q; Jmu->val = J_sgn * sqrt(2.0/(M_PI*x) / (Q + gamma*(P-Jprime_J_ratio))); Jmu->err = 4.0 * GSL_DBL_EPSILON * fabs(Jmu->val); Jmup1->val = J_ratio * Jmu->val; Jmup1->err = fabs(J_ratio) * Jmu->err; Ymu->val = gamma * Jmu->val; Ymu->err = fabs(gamma) * Jmu->err; Ymup1->val = Ymu->val * (mu/x - P - Q/gamma); Ymup1->err = Ymu->err * fabs(mu/x - P - Q/gamma) + 4.0*GSL_DBL_EPSILON*fabs(Ymup1->val); return GSL_ERROR_SELECT_2(stat_CF1, stat_CF2); } else { /* Use asymptotics for large argument. */ const int stat_J0 = gsl_sf_bessel_Jnu_asympx_e(mu, x, Jmu); const int stat_J1 = gsl_sf_bessel_Jnu_asympx_e(mu+1.0, x, Jmup1); const int stat_Y0 = gsl_sf_bessel_Ynu_asympx_e(mu, x, Ymu); const int stat_Y1 = gsl_sf_bessel_Ynu_asympx_e(mu+1.0, x, Ymup1); stat_J = GSL_ERROR_SELECT_2(stat_J0, stat_J1); stat_Y = GSL_ERROR_SELECT_2(stat_Y0, stat_Y1); return GSL_ERROR_SELECT_2(stat_J, stat_Y); } } } int gsl_sf_bessel_J_CF1(const double nu, const double x, double * ratio, double * sgn) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 10000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = x/(2.0*(nu+1.0)); double An = Anm1 + a1*Anm2; double Bn = Bnm1 + a1*Bnm2; double an; double fn = An/Bn; double dn = a1; double s = 1.0; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = -x*x/(4.0*(nu+n-1.0)*(nu+n)); An = Anm1 + an*Anm2; Bn = Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; dn = 1.0 / (2.0*(nu+n)/x - dn); if(dn < 0.0) s = -s; if(fabs(del - 1.0) < 2.0*GSL_DBL_EPSILON) break; } *ratio = fn; *sgn = s; if(n >= maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /* Evaluate the continued fraction CF1 for J_{nu+1}/J_nu * using Gautschi (Euler) equivalent series. * This exhibits an annoying problem because the * a_k are not positive definite (in fact they are all negative). * There are cases when rho_k blows up. Example: nu=1,x=4. */ #if 0 int gsl_sf_bessel_J_CF1_ser(const double nu, const double x, double * ratio, double * sgn) { const int maxk = 20000; double tk = 1.0; double sum = 1.0; double rhok = 0.0; double dk = 0.0; double s = 1.0; int k; for(k=1; k 2 is a good cutoff. * Also requires |nu| < 1/2. */ int gsl_sf_bessel_K_scaled_steed_temme_CF2(const double nu, const double x, double * K_nu, double * K_nup1, double * Kp_nu) { const int maxiter = 10000; int i = 1; double bi = 2.0*(1.0 + x); double di = 1.0/bi; double delhi = di; double hi = di; double qi = 0.0; double qip1 = 1.0; double ai = -(0.25 - nu*nu); double a1 = ai; double ci = -ai; double Qi = -ai; double s = 1.0 + Qi*delhi; for(i=2; i<=maxiter; i++) { double dels; double tmp; ai -= 2.0*(i-1); ci = -ai*ci/i; tmp = (qi - bi*qip1)/ai; qi = qip1; qip1 = tmp; Qi += ci*qip1; bi += 2.0; di = 1.0/(bi + ai*di); delhi = (bi*di - 1.0) * delhi; hi += delhi; dels = Qi*delhi; s += dels; if(fabs(dels/s) < GSL_DBL_EPSILON) break; } hi *= -a1; *K_nu = sqrt(M_PI/(2.0*x)) / s; *K_nup1 = *K_nu * (nu + x + 0.5 - hi)/x; *Kp_nu = - *K_nup1 + nu/x * *K_nu; if(i == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } int gsl_sf_bessel_cos_pi4_e(double y, double eps, gsl_sf_result * result) { const double sy = sin(y); const double cy = cos(y); const double s = sy + cy; const double d = sy - cy; const double abs_sum = fabs(cy) + fabs(sy); double seps; double ceps; if(fabs(eps) < GSL_ROOT5_DBL_EPSILON) { const double e2 = eps*eps; seps = eps * (1.0 - e2/6.0 * (1.0 - e2/20.0)); ceps = 1.0 - e2/2.0 * (1.0 - e2/12.0); } else { seps = sin(eps); ceps = cos(eps); } result->val = (ceps * s - seps * d)/ M_SQRT2; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(ceps) + fabs(seps)) * abs_sum / M_SQRT2; /* Try to account for error in evaluation of sin(y), cos(y). * This is a little sticky because we don't really know * how the library routines are doing their argument reduction. * However, we will make a reasonable guess. * FIXME ? */ if(y > 1.0/GSL_DBL_EPSILON) { result->err *= 0.5 * y; } else if(y > 1.0/GSL_SQRT_DBL_EPSILON) { result->err *= 256.0 * y * GSL_SQRT_DBL_EPSILON; } return GSL_SUCCESS; } int gsl_sf_bessel_sin_pi4_e(double y, double eps, gsl_sf_result * result) { const double sy = sin(y); const double cy = cos(y); const double s = sy + cy; const double d = sy - cy; const double abs_sum = fabs(cy) + fabs(sy); double seps; double ceps; if(fabs(eps) < GSL_ROOT5_DBL_EPSILON) { const double e2 = eps*eps; seps = eps * (1.0 - e2/6.0 * (1.0 - e2/20.0)); ceps = 1.0 - e2/2.0 * (1.0 - e2/12.0); } else { seps = sin(eps); ceps = cos(eps); } result->val = (ceps * d + seps * s)/ M_SQRT2; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(ceps) + fabs(seps)) * abs_sum / M_SQRT2; /* Try to account for error in evaluation of sin(y), cos(y). * See above. * FIXME ? */ if(y > 1.0/GSL_DBL_EPSILON) { result->err *= 0.5 * y; } else if(y > 1.0/GSL_SQRT_DBL_EPSILON) { result->err *= 256.0 * y * GSL_SQRT_DBL_EPSILON; } return GSL_SUCCESS; } /************************************************************************ * * Asymptotic approximations 8.11.5, 8.12.5, and 8.42.7 from G.N.Watson, A Treatise on the Theory of Bessel Functions, 2nd Edition (Cambridge University Press, 1944). Higher terms in expansion for x near l given by Airey in Phil. Mag. 31, 520 (1916). This approximation is accurate to near 0.1% at the boundaries between the asymptotic regions; well away from the boundaries the accuracy is better than 10^{-5}. * * ************************************************************************/ #if 0 double besselJ_meissel(double nu, double x) { double beta = pow(nu, 0.325); double result; /* Fitted matching points. */ double llimit = 1.1 * beta; double ulimit = 1.3 * beta; double nu2 = nu * nu; if (nu < 5. && x < 1.) { /* Small argument and order. Use a Taylor expansion. */ int k; double xo2 = 0.5 * x; double gamfactor = pow(nu,nu) * exp(-nu) * sqrt(nu * 2. * M_PI) * (1. + 1./(12.*nu) + 1./(288.*nu*nu)); double prefactor = pow(xo2, nu) / gamfactor; double C[5]; C[0] = 1.; C[1] = -C[0] / (nu+1.); C[2] = -C[1] / (2.*(nu+2.)); C[3] = -C[2] / (3.*(nu+3.)); C[4] = -C[3] / (4.*(nu+4.)); result = 0.; for(k=0; k<5; k++) result += C[k] * pow(xo2, 2.*k); result *= prefactor; } else if(x < nu - llimit) { /* Small x region: x << l. */ double z = x / nu; double z2 = z*z; double rtomz2 = sqrt(1.-z2); double omz2_2 = (1.-z2)*(1.-z2); /* Calculate Meissel exponent. */ double term1 = 1./(24.*nu) * ((2.+3.*z2)/((1.-z2)*rtomz2) -2.); double term2 = - z2*(4. + z2)/(16.*nu2*(1.-z2)*omz2_2); double V_nu = term1 + term2; /* Calculate the harmless prefactor. */ double sterlingsum = 1. + 1./(12.*nu) + 1./(288*nu2); double harmless = 1. / (sqrt(rtomz2*2.*M_PI*nu) * sterlingsum); /* Calculate the logarithm of the nu dependent prefactor. */ double ln_nupre = rtomz2 + log(z) - log(1. + rtomz2); result = harmless * exp(nu*ln_nupre - V_nu); } else if(x < nu + ulimit) { /* Intermediate region 1: x near nu. */ double eps = 1.-nu/x; double eps_x = eps * x; double eps_x_2 = eps_x * eps_x; double xo6 = x/6.; double B[6]; static double gam[6] = {2.67894, 1.35412, 1., 0.89298, 0.902745, 1.}; static double sf[6] = {0.866025, 0.866025, 0., -0.866025, -0.866025, 0.}; /* Some terms are identically zero, because sf[] can be zero. * Some terms do not appear in the result. */ B[0] = 1.; B[1] = eps_x; /* B[2] = 0.5 * eps_x_2 - 1./20.; */ B[3] = eps_x * (eps_x_2/6. - 1./15.); B[4] = eps_x_2 * (eps_x_2 - 1.)/24. + 1./280.; /* B[5] = eps_x * (eps_x_2*(0.5*eps_x_2 - 1.)/60. + 43./8400.); */ result = B[0] * gam[0] * sf[0] / pow(xo6, 1./3.); result += B[1] * gam[1] * sf[1] / pow(xo6, 2./3.); result += B[3] * gam[3] * sf[3] / pow(xo6, 4./3.); result += B[4] * gam[4] * sf[4] / pow(xo6, 5./3.); result /= (3.*M_PI); } else { /* Region of very large argument. Use expansion * for x>>l, and we need not be very exacting. */ double secb = x/nu; double sec2b= secb*secb; double cotb = 1./sqrt(sec2b-1.); /* cotb=cot(beta) */ double beta = acos(nu/x); double trigarg = nu/cotb - nu*beta - 0.25 * M_PI; double cot3b = cotb * cotb * cotb; double cot6b = cot3b * cot3b; double sum1, sum2, expterm, prefactor, trigcos; sum1 = 2.0 + 3.0 * sec2b; trigarg -= sum1 * cot3b / (24.0 * nu); trigcos = cos(trigarg); sum2 = 4.0 + sec2b; expterm = sum2 * sec2b * cot6b / (16.0 * nu2); expterm = exp(-expterm); prefactor = sqrt(2. * cotb / (nu * M_PI)); result = prefactor * expterm * trigcos; } return result; } #endif sources_5316/external/gsl/gsl_specfunc__bessel_J1.c0000664000176700017670000000723211723710247021211 0ustar paulpaul/* specfunc/bessel_J1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_amp_phase.h" #include "gsl_specfunc__cheb_eval.c" #define ROOT_EIGHT (2.0*M_SQRT2) /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besj1, 1983 version, w. fullerton */ /* chebyshev expansions series for bj1 on the interval 0. to 1.60000d+01 with weighted error 4.48e-17 log weighted error 16.35 significant figures required 15.77 decimal places required 16.89 */ static double bj1_data[12] = { -0.11726141513332787, -0.25361521830790640, 0.050127080984469569, -0.004631514809625081, 0.000247996229415914, -0.000008678948686278, 0.000000214293917143, -0.000000003936093079, 0.000000000055911823, -0.000000000000632761, 0.000000000000005840, -0.000000000000000044, }; static cheb_series bj1_cs = { bj1_data, 11, -1, 1, 8 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_J1_e(const double x, gsl_sf_result * result) { double y = fabs(x); /* CHECK_POINTER(result) */ if(y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(y < 2.0*GSL_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(y < ROOT_EIGHT * GSL_SQRT_DBL_EPSILON) { result->val = 0.5*x; result->err = 0.0; return GSL_SUCCESS; } else if(y < 4.0) { gsl_sf_result c; cheb_eval_e(&bj1_cs, 0.125*y*y-1.0, &c); result->val = x * (0.25 + c.val); result->err = fabs(x * c.err); return GSL_SUCCESS; } else { /* Because the leading term in the phase is y, * which we assume is exactly known, the error * in the cos() evaluation is bounded. */ const double z = 32.0/(y*y) - 1.0; gsl_sf_result ca; gsl_sf_result ct; gsl_sf_result sp; const int stat_ca = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bm1_cs, z, &ca); const int stat_ct = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bth1_cs, z, &ct); const int stat_sp = gsl_sf_bessel_sin_pi4_e(y, ct.val/y, &sp); const double sqrty = sqrt(y); const double ampl = (0.75 + ca.val) / sqrty; result->val = (x < 0.0 ? -ampl : ampl) * sp.val; result->err = fabs(sp.val) * ca.err/sqrty + fabs(ampl) * sp.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_ca, stat_ct, stat_sp); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_J1(const double x) { EVAL_RESULT(gsl_sf_bessel_J1_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__source_asum_c.h0000664000176700017670000000200011705263724021503 0ustar paulpaul/* blas/source_asum_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { BASE r = 0.0; INDEX i; INDEX ix = 0; if (incX <= 0) { return 0; } for (i = 0; i < N; i++) { r += fabs(CONST_REAL(X, ix)) + fabs(CONST_IMAG(X, ix)); ix += incX; } return r; } sources_5316/external/gsl/gsl_cdf__gammainv.c0000664000176700017670000001011511723710247020121 0ustar paulpaul/* cdf/gammainv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include "gsl__config.h" #include #include "gsl_cdf.h" #include "gsl_math.h" #include "gsl_randist.h" #include "gsl_sf_gamma.h" #include double gsl_cdf_gamma_Pinv (const double P, const double a, const double b) { double x; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return 0.0; } /* Consider, small, large and intermediate cases separately. The boundaries at 0.05 and 0.95 have not been optimised, but seem ok for an initial approximation. */ if (P < 0.05) { double x0 = exp ((gsl_sf_lngamma (a) + log (P)) / a); x = x0; } else if (P > 0.95) { double x0 = -log1p (-P) + gsl_sf_lngamma (a); x = x0; } else { double xg = gsl_cdf_ugaussian_Pinv (P); double x0 = (xg < -sqrt (a)) ? a : sqrt (a) * xg + a; x = x0; } /* Use Lagrange's interpolation for E(x)/phi(x0) to work backwards to an improved value of x (Abramowitz & Stegun, 3.6.6) where E(x)=P-integ(phi(u),u,x0,x) and phi(u) is the pdf. */ { double lambda, dP, phi; unsigned int n = 0; start: dP = P - gsl_cdf_gamma_P (x, a, 1.0); phi = gsl_ran_gamma_pdf (x, a, 1.0); if (dP == 0.0 || n++ > 32) goto end; lambda = dP / GSL_MAX (2 * fabs (dP / x), phi); { double step0 = lambda; double step1 = -((a - 1) / x - 1) * lambda * lambda / 4.0; double step = step0; if (fabs (step1) < fabs (step0)) step += step1; if (x + step > 0) x += step; else { x /= 2.0; } if (fabs (step0) > 1e-10 * x) goto start; } end: if (fabs(dP) > GSL_SQRT_DBL_EPSILON * P) { GSL_ERROR_VAL("inverse failed to converge", GSL_EFAILED, GSL_NAN); } return b * x; } } double gsl_cdf_gamma_Qinv (const double Q, const double a, const double b) { double x; if (Q == 1.0) { return 0.0; } else if (Q == 0.0) { return GSL_POSINF; } /* Consider, small, large and intermediate cases separately. The boundaries at 0.05 and 0.95 have not been optimised, but seem ok for an initial approximation. */ if (Q < 0.05) { double x0 = -log (Q) + gsl_sf_lngamma (a); x = x0; } else if (Q > 0.95) { double x0 = exp ((gsl_sf_lngamma (a) + log1p (-Q)) / a); x = x0; } else { double xg = gsl_cdf_ugaussian_Qinv (Q); double x0 = (xg < -sqrt (a)) ? a : sqrt (a) * xg + a; x = x0; } /* Use Lagrange's interpolation for E(x)/phi(x0) to work backwards to an improved value of x (Abramowitz & Stegun, 3.6.6) where E(x)=P-integ(phi(u),u,x0,x) and phi(u) is the pdf. */ { double lambda, dQ, phi; unsigned int n = 0; start: dQ = Q - gsl_cdf_gamma_Q (x, a, 1.0); phi = gsl_ran_gamma_pdf (x, a, 1.0); if (dQ == 0.0 || n++ > 32) goto end; lambda = -dQ / GSL_MAX (2 * fabs (dQ / x), phi); { double step0 = lambda; double step1 = -((a - 1) / x - 1) * lambda * lambda / 4.0; double step = step0; if (fabs (step1) < fabs (step0)) step += step1; if (x + step > 0) x += step; else { x /= 2.0; } if (fabs (step0) > 1e-10 * x) goto start; } } end: return b * x; } sources_5316/external/gsl/gsl_integration__ptsort.c0000664000176700017670000000306211723710247021447 0ustar paulpaul/* integration/ptsort.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void sort_results (gsl_integration_workspace * workspace); static void sort_results (gsl_integration_workspace * workspace) { size_t i; double * elist = workspace->elist ; size_t * order = workspace->order ; size_t nint = workspace->size; for (i = 0; i < nint; i++) { size_t i1 = order[i]; double e1 = elist[i1]; size_t i_max = i1; size_t j; for (j = i + 1; j < nint; j++) { size_t i2 = order[j]; double e2 = elist[i2]; if (e2 >= e1) { i_max = i2; e1 = e2; } } if (i_max != i1) { order[i] = order[i_max]; order[i_max] = i1; } } workspace->i = order[0] ; } sources_5316/external/gsl/gsl_block_complex_double.h0000664000176700017670000000455511705263724021545 0ustar paulpaul/* block/gsl_block_complex_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_COMPLEX_DOUBLE_H__ #define __GSL_BLOCK_COMPLEX_DOUBLE_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_complex_struct { size_t size; double *data; }; typedef struct gsl_block_complex_struct gsl_block_complex; gsl_block_complex *gsl_block_complex_alloc (const size_t n); gsl_block_complex *gsl_block_complex_calloc (const size_t n); void gsl_block_complex_free (gsl_block_complex * b); int gsl_block_complex_fread (FILE * stream, gsl_block_complex * b); int gsl_block_complex_fwrite (FILE * stream, const gsl_block_complex * b); int gsl_block_complex_fscanf (FILE * stream, gsl_block_complex * b); int gsl_block_complex_fprintf (FILE * stream, const gsl_block_complex * b, const char *format); int gsl_block_complex_raw_fread (FILE * stream, double * b, const size_t n, const size_t stride); int gsl_block_complex_raw_fwrite (FILE * stream, const double * b, const size_t n, const size_t stride); int gsl_block_complex_raw_fscanf (FILE * stream, double * b, const size_t n, const size_t stride); int gsl_block_complex_raw_fprintf (FILE * stream, const double * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_complex_size (const gsl_block_complex * b); double * gsl_block_complex_data (const gsl_block_complex * b); __END_DECLS #endif /* __GSL_BLOCK_COMPLEX_DOUBLE_H__ */ sources_5316/external/gsl/gsl_fft__factorize.c0000664000176700017670000000722511723710247020343 0ustar paulpaul/* fft/factorize.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_fft_complex.h" #include "gsl_fft__factorize.h" static int fft_complex_factorize (const size_t n, size_t *nf, size_t factors[]) { const size_t complex_subtransforms[] = {7, 6, 5, 4, 3, 2, 0}; /* other factors can be added here if their transform modules are implemented. The end of the list is marked by 0. */ int status = fft_factorize (n, complex_subtransforms, nf, factors); return status; } static int fft_halfcomplex_factorize (const size_t n, size_t *nf, size_t factors[]) { const size_t halfcomplex_subtransforms[] = {5, 4, 3, 2, 0}; int status = fft_factorize (n, halfcomplex_subtransforms, nf, factors); return status; } static int fft_real_factorize (const size_t n, size_t *nf, size_t factors[]) { const size_t real_subtransforms[] = {5, 4, 3, 2, 0}; int status = fft_factorize (n, real_subtransforms, nf, factors); return status; } static int fft_factorize (const size_t n, const size_t implemented_subtransforms[], size_t *n_factors, size_t factors[]) { size_t nf = 0; size_t ntest = n; size_t factor; size_t i = 0; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } if (n == 1) { factors[0] = 1; *n_factors = 1; return 0; } /* deal with the implemented factors first */ while (implemented_subtransforms[i] && ntest != 1) { factor = implemented_subtransforms[i]; while ((ntest % factor) == 0) { ntest = ntest / factor; factors[nf] = factor; nf++; } i++; } /* deal with any other even prime factors (there is only one) */ factor = 2; while ((ntest % factor) == 0 && (ntest != 1)) { ntest = ntest / factor; factors[nf] = factor; nf++; } /* deal with any other odd prime factors */ factor = 3; while (ntest != 1) { while ((ntest % factor) != 0) { factor += 2; } ntest = ntest / factor; factors[nf] = factor; nf++; } /* check that the factorization is correct */ { size_t product = 1; for (i = 0; i < nf; i++) { product *= factors[i]; } if (product != n) { GSL_ERROR ("factorization failed", GSL_ESANITY); } } *n_factors = nf; return 0; } static int fft_binary_logn (const size_t n) { size_t ntest ; size_t binary_logn = 0 ; size_t k = 1; while (k < n) { k *= 2; binary_logn++; } ntest = (1 << binary_logn) ; if (n != ntest ) { return -1 ; /* n is not a power of 2 */ } return binary_logn; } sources_5316/external/gsl/gsl_multifit.h0000664000176700017670000000613011705263724017216 0ustar paulpaul/* multifit/gsl_multifit.h * * Copyright (C) 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MULTIFIT_H__ #define __GSL_MULTIFIT_H__ #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t n; /* number of observations */ size_t p; /* number of parameters */ gsl_matrix * A; gsl_matrix * Q; gsl_matrix * QSI; gsl_vector * S; gsl_vector * t; gsl_vector * xt; gsl_vector * D; } gsl_multifit_linear_workspace; gsl_multifit_linear_workspace * gsl_multifit_linear_alloc (size_t n, size_t p); void gsl_multifit_linear_free (gsl_multifit_linear_workspace * work); int gsl_multifit_linear (const gsl_matrix * X, const gsl_vector * y, gsl_vector * c, gsl_matrix * cov, double * chisq, gsl_multifit_linear_workspace * work); int gsl_multifit_linear_svd (const gsl_matrix * X, const gsl_vector * y, double tol, size_t * rank, gsl_vector * c, gsl_matrix * cov, double *chisq, gsl_multifit_linear_workspace * work); int gsl_multifit_wlinear (const gsl_matrix * X, const gsl_vector * w, const gsl_vector * y, gsl_vector * c, gsl_matrix * cov, double * chisq, gsl_multifit_linear_workspace * work); int gsl_multifit_wlinear_svd (const gsl_matrix * X, const gsl_vector * w, const gsl_vector * y, double tol, size_t * rank, gsl_vector * c, gsl_matrix * cov, double *chisq, gsl_multifit_linear_workspace * work); int gsl_multifit_linear_est (const gsl_vector * x, const gsl_vector * c, const gsl_matrix * cov, double *y, double *y_err); __END_DECLS #endif /* __GSL_MULTIFIT_H__ */ sources_5316/external/gsl/gsl_matrix__getset.c0000664000176700017670000000371211723710247020372 0ustar paulpaul#include "gsl__config.h" #include "gsl_errno.h" #include "gsl_matrix.h" #include "gsl_vector.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__getset_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_cblas__source_scal_r.h0000664000176700017670000000171711705263724021515 0ustar paulpaul/* blas/source_scal_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; INDEX ix; if (incX <= 0) { return; } ix = OFFSET(N, incX); for (i = 0; i < N; i++) { X[ix] *= alpha; ix += incX; } } sources_5316/external/gsl/gsl_ieee-utils__fp-hpux11.c0000664000176700017670000000535511723710247021376 0ustar paulpaul/* ieee-utils/fp-hpux11.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { int mode; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("HPUX PA-RISC only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("HPUX PA-RISC only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("HPUX PA-RISC only supports default precision rounding", GSL_EUNSUP) ; break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: fesetround (FE_TONEAREST) ; break ; case GSL_IEEE_ROUND_DOWN: fesetround (FE_DOWNWARD) ; break ; case GSL_IEEE_ROUND_UP: fesetround (FE_UPWARD) ; break ; case GSL_IEEE_ROUND_TO_ZERO: fesetround (FE_TOWARDZERO) ; break ; default: fesetround (FE_TONEAREST) ; } /* Turn on all the exceptions apart from 'inexact' */ mode = FE_INVALID | FE_DIVBYZERO | FE_OVERFLOW | FE_UNDERFLOW ; if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ FE_INVALID ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("HP-UX does not support the denormalized operand exception. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ FE_DIVBYZERO ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ FE_OVERFLOW ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ FE_UNDERFLOW ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode |= FE_INEXACT ; } else { mode &= ~ FE_INEXACT ; } fesettrapenable (mode) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_matrix_int.h0000664000176700017670000002610411705263724017542 0ustar paulpaul/* matrix/gsl_matrix_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_INT_H__ #define __GSL_MATRIX_INT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_int.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; int * data; gsl_block_int * block; int owner; } gsl_matrix_int; typedef struct { gsl_matrix_int matrix; } _gsl_matrix_int_view; typedef _gsl_matrix_int_view gsl_matrix_int_view; typedef struct { gsl_matrix_int matrix; } _gsl_matrix_int_const_view; typedef const _gsl_matrix_int_const_view gsl_matrix_int_const_view; /* Allocation */ gsl_matrix_int * gsl_matrix_int_alloc (const size_t n1, const size_t n2); gsl_matrix_int * gsl_matrix_int_calloc (const size_t n1, const size_t n2); gsl_matrix_int * gsl_matrix_int_alloc_from_block (gsl_block_int * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_int * gsl_matrix_int_alloc_from_matrix (gsl_matrix_int * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_int * gsl_vector_int_alloc_row_from_matrix (gsl_matrix_int * m, const size_t i); gsl_vector_int * gsl_vector_int_alloc_col_from_matrix (gsl_matrix_int * m, const size_t j); void gsl_matrix_int_free (gsl_matrix_int * m); /* Views */ _gsl_matrix_int_view gsl_matrix_int_submatrix (gsl_matrix_int * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_int_view gsl_matrix_int_row (gsl_matrix_int * m, const size_t i); _gsl_vector_int_view gsl_matrix_int_column (gsl_matrix_int * m, const size_t j); _gsl_vector_int_view gsl_matrix_int_diagonal (gsl_matrix_int * m); _gsl_vector_int_view gsl_matrix_int_subdiagonal (gsl_matrix_int * m, const size_t k); _gsl_vector_int_view gsl_matrix_int_superdiagonal (gsl_matrix_int * m, const size_t k); _gsl_vector_int_view gsl_matrix_int_subrow (gsl_matrix_int * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_int_view gsl_matrix_int_subcolumn (gsl_matrix_int * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_int_view gsl_matrix_int_view_array (int * base, const size_t n1, const size_t n2); _gsl_matrix_int_view gsl_matrix_int_view_array_with_tda (int * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_int_view gsl_matrix_int_view_vector (gsl_vector_int * v, const size_t n1, const size_t n2); _gsl_matrix_int_view gsl_matrix_int_view_vector_with_tda (gsl_vector_int * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_int_const_view gsl_matrix_int_const_submatrix (const gsl_matrix_int * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_int_const_view gsl_matrix_int_const_row (const gsl_matrix_int * m, const size_t i); _gsl_vector_int_const_view gsl_matrix_int_const_column (const gsl_matrix_int * m, const size_t j); _gsl_vector_int_const_view gsl_matrix_int_const_diagonal (const gsl_matrix_int * m); _gsl_vector_int_const_view gsl_matrix_int_const_subdiagonal (const gsl_matrix_int * m, const size_t k); _gsl_vector_int_const_view gsl_matrix_int_const_superdiagonal (const gsl_matrix_int * m, const size_t k); _gsl_vector_int_const_view gsl_matrix_int_const_subrow (const gsl_matrix_int * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_int_const_view gsl_matrix_int_const_subcolumn (const gsl_matrix_int * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_int_const_view gsl_matrix_int_const_view_array (const int * base, const size_t n1, const size_t n2); _gsl_matrix_int_const_view gsl_matrix_int_const_view_array_with_tda (const int * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_int_const_view gsl_matrix_int_const_view_vector (const gsl_vector_int * v, const size_t n1, const size_t n2); _gsl_matrix_int_const_view gsl_matrix_int_const_view_vector_with_tda (const gsl_vector_int * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ int gsl_matrix_int_get(const gsl_matrix_int * m, const size_t i, const size_t j); void gsl_matrix_int_set(gsl_matrix_int * m, const size_t i, const size_t j, const int x); int * gsl_matrix_int_ptr(gsl_matrix_int * m, const size_t i, const size_t j); const int * gsl_matrix_int_const_ptr(const gsl_matrix_int * m, const size_t i, const size_t j); void gsl_matrix_int_set_zero (gsl_matrix_int * m); void gsl_matrix_int_set_identity (gsl_matrix_int * m); void gsl_matrix_int_set_all (gsl_matrix_int * m, int x); int gsl_matrix_int_fread (FILE * stream, gsl_matrix_int * m) ; int gsl_matrix_int_fwrite (FILE * stream, const gsl_matrix_int * m) ; int gsl_matrix_int_fscanf (FILE * stream, gsl_matrix_int * m); int gsl_matrix_int_fprintf (FILE * stream, const gsl_matrix_int * m, const char * format); int gsl_matrix_int_memcpy(gsl_matrix_int * dest, const gsl_matrix_int * src); int gsl_matrix_int_swap(gsl_matrix_int * m1, gsl_matrix_int * m2); int gsl_matrix_int_swap_rows(gsl_matrix_int * m, const size_t i, const size_t j); int gsl_matrix_int_swap_columns(gsl_matrix_int * m, const size_t i, const size_t j); int gsl_matrix_int_swap_rowcol(gsl_matrix_int * m, const size_t i, const size_t j); int gsl_matrix_int_transpose (gsl_matrix_int * m); int gsl_matrix_int_transpose_memcpy (gsl_matrix_int * dest, const gsl_matrix_int * src); int gsl_matrix_int_max (const gsl_matrix_int * m); int gsl_matrix_int_min (const gsl_matrix_int * m); void gsl_matrix_int_minmax (const gsl_matrix_int * m, int * min_out, int * max_out); void gsl_matrix_int_max_index (const gsl_matrix_int * m, size_t * imax, size_t *jmax); void gsl_matrix_int_min_index (const gsl_matrix_int * m, size_t * imin, size_t *jmin); void gsl_matrix_int_minmax_index (const gsl_matrix_int * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_int_isnull (const gsl_matrix_int * m); int gsl_matrix_int_ispos (const gsl_matrix_int * m); int gsl_matrix_int_isneg (const gsl_matrix_int * m); int gsl_matrix_int_isnonneg (const gsl_matrix_int * m); int gsl_matrix_int_add (gsl_matrix_int * a, const gsl_matrix_int * b); int gsl_matrix_int_sub (gsl_matrix_int * a, const gsl_matrix_int * b); int gsl_matrix_int_mul_elements (gsl_matrix_int * a, const gsl_matrix_int * b); int gsl_matrix_int_div_elements (gsl_matrix_int * a, const gsl_matrix_int * b); int gsl_matrix_int_scale (gsl_matrix_int * a, const double x); int gsl_matrix_int_add_constant (gsl_matrix_int * a, const double x); int gsl_matrix_int_add_diagonal (gsl_matrix_int * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_int_get_row(gsl_vector_int * v, const gsl_matrix_int * m, const size_t i); int gsl_matrix_int_get_col(gsl_vector_int * v, const gsl_matrix_int * m, const size_t j); int gsl_matrix_int_set_row(gsl_matrix_int * m, const size_t i, const gsl_vector_int * v); int gsl_matrix_int_set_col(gsl_matrix_int * m, const size_t j, const gsl_vector_int * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline int gsl_matrix_int_get(const gsl_matrix_int * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_int_set(gsl_matrix_int * m, const size_t i, const size_t j, const int x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline int * gsl_matrix_int_ptr(gsl_matrix_int * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (int *) (m->data + (i * m->tda + j)) ; } extern inline const int * gsl_matrix_int_const_ptr(const gsl_matrix_int * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const int *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_INT_H__ */ sources_5316/external/gsl/gsl_math.h0000664000176700017670000001325011705263724016313 0ustar paulpaul/* gsl_math.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATH_H__ #define __GSL_MATH_H__ #include #include "gsl_sys.h" #include "gsl_machine.h" #include "gsl_precision.h" #include "gsl_nan.h" #include "gsl_pow_int.h" #ifndef M_E #define M_E 2.71828182845904523536028747135 /* e */ #endif #ifndef M_LOG2E #define M_LOG2E 1.44269504088896340735992468100 /* log_2 (e) */ #endif #ifndef M_LOG10E #define M_LOG10E 0.43429448190325182765112891892 /* log_10 (e) */ #endif #ifndef M_SQRT2 #define M_SQRT2 1.41421356237309504880168872421 /* sqrt(2) */ #endif #ifndef M_SQRT1_2 #define M_SQRT1_2 0.70710678118654752440084436210 /* sqrt(1/2) */ #endif #ifndef M_SQRT3 #define M_SQRT3 1.73205080756887729352744634151 /* sqrt(3) */ #endif #ifndef M_PI #define M_PI 3.14159265358979323846264338328 /* pi */ #endif #ifndef M_PI_2 #define M_PI_2 1.57079632679489661923132169164 /* pi/2 */ #endif #ifndef M_PI_4 #define M_PI_4 0.78539816339744830961566084582 /* pi/4 */ #endif #ifndef M_SQRTPI #define M_SQRTPI 1.77245385090551602729816748334 /* sqrt(pi) */ #endif #ifndef M_2_SQRTPI #define M_2_SQRTPI 1.12837916709551257389615890312 /* 2/sqrt(pi) */ #endif #ifndef M_1_PI #define M_1_PI 0.31830988618379067153776752675 /* 1/pi */ #endif #ifndef M_2_PI #define M_2_PI 0.63661977236758134307553505349 /* 2/pi */ #endif #ifndef M_LN10 #define M_LN10 2.30258509299404568401799145468 /* ln(10) */ #endif #ifndef M_LN2 #define M_LN2 0.69314718055994530941723212146 /* ln(2) */ #endif #ifndef M_LNPI #define M_LNPI 1.14472988584940017414342735135 /* ln(pi) */ #endif #ifndef M_EULER #define M_EULER 0.57721566490153286060651209008 /* Euler constant */ #endif #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* other needlessly compulsive abstractions */ #define GSL_IS_ODD(n) ((n) & 1) #define GSL_IS_EVEN(n) (!(GSL_IS_ODD(n))) #define GSL_SIGN(x) ((x) >= 0.0 ? 1 : -1) /* Return nonzero if x is a real number, i.e. non NaN or infinite. */ #define GSL_IS_REAL(x) (gsl_finite(x)) /* Define MAX and MIN macros/functions if they don't exist. */ /* plain old macros for general use */ #define GSL_MAX(a,b) ((a) > (b) ? (a) : (b)) #define GSL_MIN(a,b) ((a) < (b) ? (a) : (b)) /* function versions of the above, in case they are needed */ double gsl_max (double a, double b); double gsl_min (double a, double b); /* inline-friendly strongly typed versions */ #ifdef HAVE_INLINE extern inline int GSL_MAX_INT (int a, int b); extern inline int GSL_MIN_INT (int a, int b); extern inline double GSL_MAX_DBL (double a, double b); extern inline double GSL_MIN_DBL (double a, double b); extern inline long double GSL_MAX_LDBL (long double a, long double b); extern inline long double GSL_MIN_LDBL (long double a, long double b); extern inline int GSL_MAX_INT (int a, int b) { return GSL_MAX (a, b); } extern inline int GSL_MIN_INT (int a, int b) { return GSL_MIN (a, b); } extern inline double GSL_MAX_DBL (double a, double b) { return GSL_MAX (a, b); } extern inline double GSL_MIN_DBL (double a, double b) { return GSL_MIN (a, b); } extern inline long double GSL_MAX_LDBL (long double a, long double b) { return GSL_MAX (a, b); } extern inline long double GSL_MIN_LDBL (long double a, long double b) { return GSL_MIN (a, b); } #else #define GSL_MAX_INT(a,b) GSL_MAX(a,b) #define GSL_MIN_INT(a,b) GSL_MIN(a,b) #define GSL_MAX_DBL(a,b) GSL_MAX(a,b) #define GSL_MIN_DBL(a,b) GSL_MIN(a,b) #define GSL_MAX_LDBL(a,b) GSL_MAX(a,b) #define GSL_MIN_LDBL(a,b) GSL_MIN(a,b) #endif /* HAVE_INLINE */ /* Definition of an arbitrary function with parameters */ struct gsl_function_struct { double (* function) (double x, void * params); void * params; }; typedef struct gsl_function_struct gsl_function ; #define GSL_FN_EVAL(F,x) (*((F)->function))(x,(F)->params) /* Definition of an arbitrary function returning two values, r1, r2 */ struct gsl_function_fdf_struct { double (* f) (double x, void * params); double (* df) (double x, void * params); void (* fdf) (double x, void * params, double * f, double * df); void * params; }; typedef struct gsl_function_fdf_struct gsl_function_fdf ; #define GSL_FN_FDF_EVAL_F(FDF,x) (*((FDF)->f))(x,(FDF)->params) #define GSL_FN_FDF_EVAL_DF(FDF,x) (*((FDF)->df))(x,(FDF)->params) #define GSL_FN_FDF_EVAL_F_DF(FDF,x,y,dy) (*((FDF)->fdf))(x,(FDF)->params,(y),(dy)) /* Definition of an arbitrary vector-valued function with parameters */ struct gsl_function_vec_struct { int (* function) (double x, double y[], void * params); void * params; }; typedef struct gsl_function_vec_struct gsl_function_vec ; #define GSL_FN_VEC_EVAL(F,x,y) (*((F)->function))(x,y,(F)->params) __END_DECLS #endif /* __GSL_MATH_H__ */ sources_5316/external/gsl/gsl_statistics__kurtosis_source.c0000664000176700017670000000364411723710247023234 0ustar paulpaul/* statistics/kurtosis_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,kurtosis) (const BASE data[], const size_t stride, const size_t n) { const double mean = FUNCTION(gsl_stats,mean)(data, stride, n); const double est_sd = FUNCTION(gsl_stats,sd_m)(data, stride, n, mean); return FUNCTION(gsl_stats,kurtosis_m_sd)(data, stride, n, mean, est_sd); } double FUNCTION(gsl_stats,kurtosis_m_sd) (const BASE data[], const size_t stride, const size_t n, const double mean, const double sd) { /* takes a dataset and finds the kurtosis */ long double avg = 0, kurtosis; size_t i; /* find the fourth moment the deviations, normalized by the sd */ /* we use a recurrence relation to stably update a running value so there aren't any large sums that can overflow */ for (i = 0; i < n; i++) { const long double x = (data[i * stride] - mean) / sd; avg += (x * x * x * x - avg)/(i + 1); } kurtosis = avg - 3.0; /* makes kurtosis zero for a Gaussian */ return kurtosis; } sources_5316/external/gsl/gsl_sf_ellint.h0000664000176700017670000001011311705263724017334 0ustar paulpaul/* specfunc/gsl_sf_ellint.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_ELLINT_H__ #define __GSL_SF_ELLINT_H__ #include "gsl_mode.h" #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Legendre form of complete elliptic integrals * * K(k) = Integral[1/Sqrt[1 - k^2 Sin[t]^2], {t, 0, Pi/2}] * E(k) = Integral[ Sqrt[1 - k^2 Sin[t]^2], {t, 0, Pi/2}] * * exceptions: GSL_EDOM */ int gsl_sf_ellint_Kcomp_e(double k, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_Kcomp(double k, gsl_mode_t mode); int gsl_sf_ellint_Ecomp_e(double k, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_Ecomp(double k, gsl_mode_t mode); int gsl_sf_ellint_Pcomp_e(double k, double n, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_Pcomp(double k, double n, gsl_mode_t mode); int gsl_sf_ellint_Dcomp_e(double k, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_Dcomp(double k, gsl_mode_t mode); /* Legendre form of incomplete elliptic integrals * * F(phi,k) = Integral[1/Sqrt[1 - k^2 Sin[t]^2], {t, 0, phi}] * E(phi,k) = Integral[ Sqrt[1 - k^2 Sin[t]^2], {t, 0, phi}] * P(phi,k,n) = Integral[(1 + n Sin[t]^2)^(-1)/Sqrt[1 - k^2 Sin[t]^2], {t, 0, phi}] * D(phi,k,n) = R_D(1-Sin[phi]^2, 1-k^2 Sin[phi]^2, 1.0) * * F: [Carlson, Numerische Mathematik 33 (1979) 1, (4.1)] * E: [Carlson, ", (4.2)] * P: [Carlson, ", (4.3)] * D: [Carlson, ", (4.4)] * * exceptions: GSL_EDOM */ int gsl_sf_ellint_F_e(double phi, double k, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_F(double phi, double k, gsl_mode_t mode); int gsl_sf_ellint_E_e(double phi, double k, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_E(double phi, double k, gsl_mode_t mode); int gsl_sf_ellint_P_e(double phi, double k, double n, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_P(double phi, double k, double n, gsl_mode_t mode); int gsl_sf_ellint_D_e(double phi, double k, double n, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_D(double phi, double k, double n, gsl_mode_t mode); /* Carlson's symmetric basis of functions * * RC(x,y) = 1/2 Integral[(t+x)^(-1/2) (t+y)^(-1)], {t,0,Inf}] * RD(x,y,z) = 3/2 Integral[(t+x)^(-1/2) (t+y)^(-1/2) (t+z)^(-3/2), {t,0,Inf}] * RF(x,y,z) = 1/2 Integral[(t+x)^(-1/2) (t+y)^(-1/2) (t+z)^(-1/2), {t,0,Inf}] * RJ(x,y,z,p) = 3/2 Integral[(t+x)^(-1/2) (t+y)^(-1/2) (t+z)^(-1/2) (t+p)^(-1), {t,0,Inf}] * * exceptions: GSL_EDOM */ int gsl_sf_ellint_RC_e(double x, double y, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_RC(double x, double y, gsl_mode_t mode); int gsl_sf_ellint_RD_e(double x, double y, double z, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_RD(double x, double y, double z, gsl_mode_t mode); int gsl_sf_ellint_RF_e(double x, double y, double z, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_RF(double x, double y, double z, gsl_mode_t mode); int gsl_sf_ellint_RJ_e(double x, double y, double z, double p, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_ellint_RJ(double x, double y, double z, double p, gsl_mode_t mode); __END_DECLS #endif /* __GSL_SF_ELLINT_H__ */ sources_5316/external/gsl/gsl_cdf__paretoinv.c0000664000176700017670000000251311723710247020334 0ustar paulpaul/* cdf/paretoinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_pareto_Pinv (const double P, const double a, const double b) { double x; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return b; } x = b * exp(-log1p(-P)/a); return x; } double gsl_cdf_pareto_Qinv (const double Q, const double a, const double b) { double x; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return b; } x = b * exp(-log(Q) / a); return x; } sources_5316/external/gsl/gsl_sort__subset_source.c0000664000176700017670000000563011723710247021450 0ustar paulpaul/* sort/subset_source.c * * Copyright (C) 1999,2000,2001 Thomas Walter, Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ /* find the k-th smallest elements of the vector data, in ascending order */ int FUNCTION (gsl_sort, smallest) (BASE * dest, const size_t k, const BASE * src, const size_t stride, const size_t n) { size_t i, j; BASE xbound; if (k > n) { GSL_ERROR ("subset length k exceeds vector length n", GSL_EINVAL); } if (k == 0 || n == 0) { return GSL_SUCCESS; } /* take the first element */ j = 1; xbound = src[0 * stride]; dest[0] = xbound; /* examine the remaining elements */ for (i = 1; i < n; i++) { size_t i1; BASE xi = src[i * stride]; if (j < k) { j++; } else if (xi >= xbound) { continue; } for (i1 = j - 1; i1 > 0 ; i1--) { if (xi > dest[i1 - 1]) break; dest[i1] = dest[i1 - 1]; } dest[i1] = xi; xbound = dest[j-1]; } return GSL_SUCCESS; } int FUNCTION (gsl_sort_vector,smallest) (BASE * dest, const size_t k, const TYPE (gsl_vector) * v) { return FUNCTION (gsl_sort, smallest) (dest, k, v->data, v->stride, v->size); } int FUNCTION (gsl_sort, largest) (BASE * dest, const size_t k, const BASE * src, const size_t stride, const size_t n) { size_t i, j; BASE xbound; if (k > n) { GSL_ERROR ("subset length k exceeds vector length n", GSL_EINVAL); } if (k == 0 || n == 0) { return GSL_SUCCESS; } /* take the first element */ j = 1; xbound = src[0 * stride]; dest[0] = xbound; /* examine the remaining elements */ for (i = 1; i < n; i++) { size_t i1; BASE xi = src[i * stride]; if (j < k) { j++; } else if (xi <= xbound) { continue; } for (i1 = j - 1; i1 > 0 ; i1--) { if (xi < dest[i1 - 1]) break; dest[i1] = dest[i1 - 1]; } dest[i1] = xi; xbound = dest[j-1]; } return GSL_SUCCESS; } int FUNCTION (gsl_sort_vector,largest) (BASE * dest, const size_t k, const TYPE (gsl_vector) * v) { return FUNCTION (gsl_sort, largest) (dest, k, v->data, v->stride, v->size); } sources_5316/external/gsl/gsl_permute_vector_ushort.h0000664000176700017670000000267711705263724022044 0ustar paulpaul/* permutation/gsl_permute_vector_ushort.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_USHORT_H__ #define __GSL_PERMUTE_VECTOR_USHORT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_ushort.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_ushort (const gsl_permutation * p, gsl_vector_ushort * v); int gsl_permute_vector_ushort_inverse (const gsl_permutation * p, gsl_vector_ushort * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_USHORT_H__ */ sources_5316/external/gsl/gsl_sf_elementary.h0000664000176700017670000000316511705263724020223 0ustar paulpaul/* specfunc/gsl_sf_elementary.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Miscellaneous elementary functions and operations. */ #ifndef __GSL_SF_ELEMENTARY_H__ #define __GSL_SF_ELEMENTARY_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Multiplication. * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_multiply_e(const double x, const double y, gsl_sf_result * result); double gsl_sf_multiply(const double x, const double y); /* Multiplication of quantities with associated errors. */ int gsl_sf_multiply_err_e(const double x, const double dx, const double y, const double dy, gsl_sf_result * result); __END_DECLS #endif /* __GSL_SF_ELEMENTARY_H__ */ sources_5316/external/gsl/gsl_randist__binomial.c0000664000176700017670000000437611723710247021040 0ustar paulpaul/* randist/binomial.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_sys.h" #include "gsl_rng.h" #include "gsl_randist.h" #include "gsl_sf_gamma.h" /* The binomial distribution has the form, prob(k) = n!/(k!(n-k)!) * p^k (1-p)^(n-k) for k = 0, 1, ..., n This is the algorithm from Knuth */ /* Default binomial generator is now in binomial_tpe.c */ unsigned int gsl_ran_binomial_knuth (const gsl_rng * r, double p, unsigned int n) { unsigned int i, a, b, k = 0; while (n > 10) /* This parameter is tunable */ { double X; a = 1 + (n / 2); b = 1 + n - a; X = gsl_ran_beta (r, (double) a, (double) b); if (X >= p) { n = a - 1; p /= X; } else { k += a; n = b - 1; p = (p - X) / (1 - X); } } for (i = 0; i < n; i++) { double u = gsl_rng_uniform (r); if (u < p) k++; } return k; } double gsl_ran_binomial_pdf (const unsigned int k, const double p, const unsigned int n) { if (k > n) { return 0; } else { double P; if (p == 0) { P = (k == 0) ? 1 : 0; } else if (p == 1) { P = (k == n) ? 1 : 0; } else { double ln_Cnk = gsl_sf_lnchoose (n, k); P = ln_Cnk + k * log (p) + (n - k) * log1p (-p); P = exp (P); } return P; } } sources_5316/external/gsl/gsl_fft__factorize.h0000664000176700017670000000232111705263724020343 0ustar paulpaul/* fft/factorize.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int fft_complex_factorize (const size_t n, size_t *nf, size_t factors[]); static int fft_halfcomplex_factorize (const size_t n, size_t *nf, size_t factors[]); static int fft_real_factorize (const size_t n, size_t *nf, size_t factors[]); static int fft_factorize (const size_t n, const size_t implemented_subtransforms[], size_t *n_factors, size_t factors[]); static int fft_binary_logn (const size_t n) ; sources_5316/external/gsl/gsl_fft__real_radix2.c0000664000176700017670000000753711723710247020557 0ustar paulpaul/* fft/real_radix2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION(gsl_fft_real,radix2_transform) (BASE data[], const size_t stride, const size_t n) { int result ; size_t p, p_1, q; size_t i; size_t logn = 0; int status; if (n == 1) /* identity operation */ { return 0 ; } /* make sure that n is a power of 2 */ result = fft_binary_logn(n) ; if (result == -1) { GSL_ERROR ("n is not a power of 2", GSL_EINVAL); } else { logn = result ; } /* bit reverse the ordering of input data for decimation in time algorithm */ status = FUNCTION(fft_real,bitreverse_order)(data, stride, n, logn) ; /* apply fft recursion */ p = 1; q = n ; for (i = 1; i <= logn; i++) { size_t a, b; p_1 = p ; p = 2 * p ; q = q / 2 ; /* a = 0 */ for (b = 0; b < q; b++) { ATOMIC t0_real = VECTOR(data,stride,b*p) + VECTOR(data,stride,b*p + p_1) ; ATOMIC t1_real = VECTOR(data,stride,b*p) - VECTOR(data,stride,b*p + p_1) ; VECTOR(data,stride,b*p) = t0_real ; VECTOR(data,stride,b*p + p_1) = t1_real ; } /* a = 1 ... p_{i-1}/2 - 1 */ { ATOMIC w_real = 1.0; ATOMIC w_imag = 0.0; const double theta = - 2.0 * M_PI / p; const ATOMIC s = sin (theta); const ATOMIC t = sin (theta / 2.0); const ATOMIC s2 = 2.0 * t * t; for (a = 1; a < (p_1)/2; a++) { /* trignometric recurrence for w-> exp(i theta) w */ { const ATOMIC tmp_real = w_real - s * w_imag - s2 * w_real; const ATOMIC tmp_imag = w_imag + s * w_real - s2 * w_imag; w_real = tmp_real; w_imag = tmp_imag; } for (b = 0; b < q; b++) { ATOMIC z0_real = VECTOR(data,stride,b*p + a) ; ATOMIC z0_imag = VECTOR(data,stride,b*p + p_1 - a) ; ATOMIC z1_real = VECTOR(data,stride,b*p + p_1 + a) ; ATOMIC z1_imag = VECTOR(data,stride,b*p + p - a) ; /* t0 = z0 + w * z1 */ ATOMIC t0_real = z0_real + w_real * z1_real - w_imag * z1_imag; ATOMIC t0_imag = z0_imag + w_real * z1_imag + w_imag * z1_real; /* t1 = z0 - w * z1 */ ATOMIC t1_real = z0_real - w_real * z1_real + w_imag * z1_imag; ATOMIC t1_imag = z0_imag - w_real * z1_imag - w_imag * z1_real; VECTOR(data,stride,b*p + a) = t0_real ; VECTOR(data,stride,b*p + p - a) = t0_imag ; VECTOR(data,stride,b*p + p_1 - a) = t1_real ; VECTOR(data,stride,b*p + p_1 + a) = -t1_imag ; } } } if (p_1 > 1) { for (b = 0; b < q; b++) { /* a = p_{i-1}/2 */ VECTOR(data,stride,b*p + p - p_1/2) *= -1 ; } } } return 0; } sources_5316/external/gsl/gsl_ode-initval__rkf45.c0000664000176700017670000002057611723710247020750 0ustar paulpaul/* ode-initval/rkf45.c * * Copyright (C) 2001, 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Runge-Kutta-Fehlberg 4(5)*/ /* Reference eg. Hairer, E., Norsett S.P., Wanner, G. Solving ordinary differential equations I, Nonstiff Problems, 2nd revised edition, Springer, 2000. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" /* Runge-Kutta-Fehlberg coefficients. Zero elements left out */ static const double ah[] = { 1.0/4.0, 3.0/8.0, 12.0/13.0, 1.0, 1.0/2.0 }; static const double b3[] = { 3.0/32.0, 9.0/32.0 }; static const double b4[] = { 1932.0/2197.0, -7200.0/2197.0, 7296.0/2197.0}; static const double b5[] = { 8341.0/4104.0, -32832.0/4104.0, 29440.0/4104.0, -845.0/4104.0}; static const double b6[] = { -6080.0/20520.0, 41040.0/20520.0, -28352.0/20520.0, 9295.0/20520.0, -5643.0/20520.0}; static const double c1 = 902880.0/7618050.0; static const double c3 = 3953664.0/7618050.0; static const double c4 = 3855735.0/7618050.0; static const double c5 = -1371249.0/7618050.0; static const double c6 = 277020.0/7618050.0; /* These are the differences of fifth and fourth order coefficients for error estimation */ static const double ec[] = { 0.0, 1.0 / 360.0, 0.0, -128.0 / 4275.0, -2197.0 / 75240.0, 1.0 / 50.0, 2.0 / 55.0 }; typedef struct { double *k1; double *k2; double *k3; double *k4; double *k5; double *k6; double *y0; double *ytmp; } rkf45_state_t; static void * rkf45_alloc (size_t dim) { rkf45_state_t *state = (rkf45_state_t *) malloc (sizeof (rkf45_state_t)); if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for rkf45_state", GSL_ENOMEM); } state->k1 = (double *) malloc (dim * sizeof (double)); if (state->k1 == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for k1", GSL_ENOMEM); } state->k2 = (double *) malloc (dim * sizeof (double)); if (state->k2 == 0) { free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k2", GSL_ENOMEM); } state->k3 = (double *) malloc (dim * sizeof (double)); if (state->k3 == 0) { free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k3", GSL_ENOMEM); } state->k4 = (double *) malloc (dim * sizeof (double)); if (state->k4 == 0) { free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k4", GSL_ENOMEM); } state->k5 = (double *) malloc (dim * sizeof (double)); if (state->k5 == 0) { free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k5", GSL_ENOMEM); } state->k6 = (double *) malloc (dim * sizeof (double)); if (state->k6 == 0) { free (state->k5); free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k6", GSL_ENOMEM); } state->y0 = (double *) malloc (dim * sizeof (double)); if (state->y0 == 0) { free (state->k6); free (state->k5); free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } state->ytmp = (double *) malloc (dim * sizeof (double)); if (state->ytmp == 0) { free (state->y0); free (state->k6); free (state->k5); free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for ytmp", GSL_ENOMEM); } return state; } static int rkf45_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { rkf45_state_t *state = (rkf45_state_t *) vstate; size_t i; double *const k1 = state->k1; double *const k2 = state->k2; double *const k3 = state->k3; double *const k4 = state->k4; double *const k5 = state->k5; double *const k6 = state->k6; double *const ytmp = state->ytmp; double *const y0 = state->y0; DBL_MEMCPY (y0, y, dim); /* k1 step */ if (dydt_in != NULL) { DBL_MEMCPY (k1, dydt_in, dim); } else { int s = GSL_ODEIV_FN_EVAL (sys, t, y, k1); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + ah[0] * h * k1[i]; /* k2 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[0] * h, ytmp, k2); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b3[0] * k1[i] + b3[1] * k2[i]); /* k3 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[1] * h, ytmp, k3); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b4[0] * k1[i] + b4[1] * k2[i] + b4[2] * k3[i]); /* k4 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[2] * h, ytmp, k4); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b5[0] * k1[i] + b5[1] * k2[i] + b5[2] * k3[i] + b5[3] * k4[i]); /* k5 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[3] * h, ytmp, k5); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b6[0] * k1[i] + b6[1] * k2[i] + b6[2] * k3[i] + b6[3] * k4[i] + b6[4] * k5[i]); /* k6 step and final sum */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[4] * h, ytmp, k6); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) { const double d_i = c1 * k1[i] + c3 * k3[i] + c4 * k4[i] + c5 * k5[i] + c6 * k6[i]; y[i] += h * d_i; } /* Derivatives at output */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore initial values */ DBL_MEMCPY (y, y0, dim); return s; } } /* difference between 4th and 5th order */ for (i = 0; i < dim; i++) { yerr[i] = h * (ec[1] * k1[i] + ec[3] * k3[i] + ec[4] * k4[i] + ec[5] * k5[i] + ec[6] * k6[i]); } return GSL_SUCCESS; } static int rkf45_reset (void *vstate, size_t dim) { rkf45_state_t *state = (rkf45_state_t *) vstate; DBL_ZERO_MEMSET (state->k1, dim); DBL_ZERO_MEMSET (state->k2, dim); DBL_ZERO_MEMSET (state->k3, dim); DBL_ZERO_MEMSET (state->k4, dim); DBL_ZERO_MEMSET (state->k5, dim); DBL_ZERO_MEMSET (state->k6, dim); DBL_ZERO_MEMSET (state->ytmp, dim); DBL_ZERO_MEMSET (state->y0, dim); return GSL_SUCCESS; } static unsigned int rkf45_order (void *vstate) { rkf45_state_t *state = (rkf45_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 5; } static void rkf45_free (void *vstate) { rkf45_state_t *state = (rkf45_state_t *) vstate; free (state->ytmp); free (state->y0); free (state->k6); free (state->k5); free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); } static const gsl_odeiv_step_type rkf45_type = { "rkf45", /* name */ 1, /* can use dydt_in */ 0, /* gives exact dydt_out */ &rkf45_alloc, &rkf45_apply, &rkf45_reset, &rkf45_order, &rkf45_free }; const gsl_odeiv_step_type *gsl_odeiv_step_rkf45 = &rkf45_type; sources_5316/external/gsl/gsl_cblas__source_scal_c_s.h0000664000176700017670000000176111705263724022017 0ustar paulpaul/* blas/source_scal_c_s.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; INDEX ix; if (incX <= 0) { return; } ix = OFFSET(N, incX); for (i = 0; i < N; i++) { REAL(X, ix) *= alpha; IMAG(X, ix) *= alpha; ix += incX; } } sources_5316/external/gsl/gsl_permutation__init.c0000664000176700017670000000422311723710247021103 0ustar paulpaul/* permutation/init.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_permutation.h" gsl_permutation * gsl_permutation_alloc (const size_t n) { gsl_permutation * p; if (n == 0) { GSL_ERROR_VAL ("permutation length n must be positive integer", GSL_EDOM, 0); } p = (gsl_permutation *) malloc (sizeof (gsl_permutation)); if (p == 0) { GSL_ERROR_VAL ("failed to allocate space for permutation struct", GSL_ENOMEM, 0); } p->data = (size_t *) malloc (n * sizeof (size_t)); if (p->data == 0) { free (p); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for permutation data", GSL_ENOMEM, 0); } p->size = n; return p; } gsl_permutation * gsl_permutation_calloc (const size_t n) { size_t i; gsl_permutation * p = gsl_permutation_alloc (n); if (p == 0) return 0; /* initialize permutation to identity */ for (i = 0; i < n; i++) { p->data[i] = i; } return p; } void gsl_permutation_init (gsl_permutation * p) { const size_t n = p->size ; size_t i; /* initialize permutation to identity */ for (i = 0; i < n; i++) { p->data[i] = i; } } void gsl_permutation_free (gsl_permutation * p) { free (p->data); free (p); } sources_5316/external/gsl/gsl_complex__results2.h0000664000176700017670000001044111705263724021032 0ustar paulpaul {FN (pow), ARG(1.0e+00,0.0e+00), ARG(0.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(1.0e+00,0.0e+00), ARG(1.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(1.0e+00,0.0e+00), ARG(0.0e+00,1.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(1.0e+00,0.0e+00), ARG(-1.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(1.0e+00,0.0e+00), ARG(0.0e+00,-1.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(1.0e+00,0.0e+00), ARG(5.0e-01,1.00000000000000005551e-01), RES(1e0, 0.0)}, {FN (pow), ARG(1.0e+00,0.0e+00), ARG(5.0e-01,-1.00000000000000005551e-01), RES(1e0, 0.0)}, {FN (pow), ARG(0.0e+00,1.0e+00), ARG(0.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(0.0e+00,1.0e+00), ARG(1.0e+00,0.0e+00), RES(0, 1)}, {FN (pow), ARG(0.0e+00,1.0e+00), ARG(0.0e+00,1.0e+00), RES(2.0787957635076190855e-1, 0.0)}, {FN (pow), ARG(0.0e+00,1.0e+00), ARG(-1.0e+00,0.0e+00), RES(0, -1)}, {FN (pow), ARG(0.0e+00,1.0e+00), ARG(0.0e+00,-1.0e+00), RES(4.8104773809653516555e0, 0.0)}, {FN (pow), ARG(0.0e+00,1.0e+00), ARG(5.0e-01,1.00000000000000005551e-01), RES(6.0431891044739184057e-1, 6.0431891044739184057e-1)}, {FN (pow), ARG(0.0e+00,1.0e+00), ARG(5.0e-01,-1.00000000000000005551e-01), RES(8.2737771622906514822e-1, 8.2737771622906514822e-1)}, {FN (pow), ARG(-1.0e+00,0.0e+00), ARG(0.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(-1.0e+00,0.0e+00), ARG(1.0e+00,0.0e+00), RES(-1e0, 0.0)}, {FN (pow), ARG(-1.0e+00,0.0e+00), ARG(0.0e+00,1.0e+00), RES(4.3213918263772249774e-2, 0.0)}, {FN (pow), ARG(-1.0e+00,0.0e+00), ARG(-1.0e+00,0.0e+00), RES(-1e0, 0.0)}, {FN (pow), ARG(-1.0e+00,0.0e+00), ARG(0.0e+00,-1.0e+00), RES(2.3140692632779269006e1, 0.0)}, {FN (pow), ARG(-1.0e+00,0.0e+00), ARG(5.0e-01,1.00000000000000005551e-01), RES(0, 7.3040269104864559813e-1)}, {FN (pow), ARG(-1.0e+00,0.0e+00), ARG(5.0e-01,-1.00000000000000005551e-01), RES(0, 1.3691077706248469087e0)}, {FN (pow), ARG(0.0e+00,-1.0e+00), ARG(0.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(0.0e+00,-1.0e+00), ARG(1.0e+00,0.0e+00), RES(0, -1)}, {FN (pow), ARG(0.0e+00,-1.0e+00), ARG(0.0e+00,1.0e+00), RES(4.8104773809653516555e0, 0.0)}, {FN (pow), ARG(0.0e+00,-1.0e+00), ARG(-1.0e+00,0.0e+00), RES(0, 1)}, {FN (pow), ARG(0.0e+00,-1.0e+00), ARG(0.0e+00,-1.0e+00), RES(2.0787957635076190855e-1, 0.0)}, {FN (pow), ARG(0.0e+00,-1.0e+00), ARG(5.0e-01,1.00000000000000005551e-01), RES(8.2737771622906514822e-1, -8.2737771622906514822e-1)}, {FN (pow), ARG(0.0e+00,-1.0e+00), ARG(5.0e-01,-1.00000000000000005551e-01), RES(6.0431891044739184057e-1, -6.0431891044739184057e-1)}, {FN (pow), ARG(5.0e-01,1.00000000000000005551e-01), ARG(0.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(5.0e-01,1.00000000000000005551e-01), ARG(1.0e+00,0.0e+00), RES(5e-1, 1.0000000000000000555e-1)}, {FN (pow), ARG(5.0e-01,1.00000000000000005551e-01), ARG(0.0e+00,1.0e+00), RES(6.4160554864378080418e-1, -5.1201864456768275590e-1)}, {FN (pow), ARG(5.0e-01,1.00000000000000005551e-01), ARG(-1.0e+00,0.0e+00), RES(1.9230769230769230687e0, -3.8461538461538463509e-1)}, {FN (pow), ARG(5.0e-01,1.00000000000000005551e-01), ARG(0.0e+00,-1.0e+00), RES(9.5219021866126714108e-1, 7.5987364224031834571e-1)}, {FN (pow), ARG(5.0e-01,1.00000000000000005551e-01), ARG(5.0e-01,1.00000000000000005551e-01), RES(6.9977300530987816719e-1, 2.1940939105372143160e-2)}, {FN (pow), ARG(5.0e-01,1.00000000000000005551e-01), ARG(5.0e-01,-1.00000000000000005551e-01), RES(7.1829191470060938876e-1, 1.2038189555821612762e-1)}, {FN (pow), ARG(5.0e-01,-1.00000000000000005551e-01), ARG(0.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (pow), ARG(5.0e-01,-1.00000000000000005551e-01), ARG(1.0e+00,0.0e+00), RES(5e-1, -1.0000000000000000555e-1)}, {FN (pow), ARG(5.0e-01,-1.00000000000000005551e-01), ARG(0.0e+00,1.0e+00), RES(9.5219021866126714108e-1, -7.5987364224031834571e-1)}, {FN (pow), ARG(5.0e-01,-1.00000000000000005551e-01), ARG(-1.0e+00,0.0e+00), RES(1.9230769230769230687e0, 3.8461538461538463509e-1)}, {FN (pow), ARG(5.0e-01,-1.00000000000000005551e-01), ARG(0.0e+00,-1.0e+00), RES(6.4160554864378080418e-1, 5.1201864456768275590e-1)}, {FN (pow), ARG(5.0e-01,-1.00000000000000005551e-01), ARG(5.0e-01,1.00000000000000005551e-01), RES(7.1829191470060938876e-1, -1.2038189555821612762e-1)}, {FN (pow), ARG(5.0e-01,-1.00000000000000005551e-01), ARG(5.0e-01,-1.00000000000000005551e-01), RES(6.9977300530987816719e-1, -2.1940939105372143160e-2)}, sources_5316/external/gsl/gsl_specfunc__dilog.c0000664000176700017670000004317711723710247020510 0ustar paulpaul/* specfunc/dilog.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_clausen.h" #include "gsl_sf_trig.h" #include "gsl_sf_log.h" #include "gsl_sf_dilog.h" /* Evaluate series for real dilog(x) * Sum[ x^k / k^2, {k,1,Infinity}] * * Converges rapidly for |x| < 1/2. */ static int dilog_series_1(const double x, gsl_sf_result * result) { const int kmax = 1000; double sum = x; double term = x; int k; for(k=2; kval = sum; result->err = 2.0 * fabs(term); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(k == kmax) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /* Compute the associated series * * sum_{k=1}{infty} r^k / (k^2 (k+1)) * * This is a series which appears in the one-step accelerated * method, which splits out one elementary function from the * full definition of Li_2(x). See below. */ static int series_2(double r, gsl_sf_result * result) { static const int kmax = 100; double rk = r; double sum = 0.5 * r; int k; for(k=2; k<10; k++) { double ds; rk *= r; ds = rk/(k*k*(k+1.0)); sum += ds; } for(; kval = sum; result->err = 2.0 * kmax * GSL_DBL_EPSILON * fabs(sum); return GSL_SUCCESS; } /* Compute Li_2(x) using the accelerated series representation. * * Li_2(x) = 1 + (1-x)ln(1-x)/x + series_2(x) * * assumes: -1 < x < 1 */ static int dilog_series_2(double x, gsl_sf_result * result) { const int stat_s3 = series_2(x, result); double t; if(x > 0.01) t = (1.0 - x) * log(1.0-x) / x; else { static const double c3 = 1.0/3.0; static const double c4 = 1.0/4.0; static const double c5 = 1.0/5.0; static const double c6 = 1.0/6.0; static const double c7 = 1.0/7.0; static const double c8 = 1.0/8.0; const double t68 = c6 + x*(c7 + x*c8); const double t38 = c3 + x *(c4 + x *(c5 + x * t68)); t = (x - 1.0) * (1.0 + x*(0.5 + x*t38)); } result->val += 1.0 + t; result->err += 2.0 * GSL_DBL_EPSILON * fabs(t); return stat_s3; } /* Calculates Li_2(x) for real x. Assumes x >= 0.0. */ static int dilog_xge0(const double x, gsl_sf_result * result) { if(x > 2.0) { gsl_sf_result ser; const int stat_ser = dilog_series_2(1.0/x, &ser); const double log_x = log(x); const double t1 = M_PI*M_PI/3.0; const double t2 = ser.val; const double t3 = 0.5*log_x*log_x; result->val = t1 - t2 - t3; result->err = GSL_DBL_EPSILON * fabs(log_x) + ser.err; result->err += GSL_DBL_EPSILON * (fabs(t1) + fabs(t2) + fabs(t3)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_ser; } else if(x > 1.01) { gsl_sf_result ser; const int stat_ser = dilog_series_2(1.0 - 1.0/x, &ser); const double log_x = log(x); const double log_term = log_x * (log(1.0-1.0/x) + 0.5*log_x); const double t1 = M_PI*M_PI/6.0; const double t2 = ser.val; const double t3 = log_term; result->val = t1 + t2 - t3; result->err = GSL_DBL_EPSILON * fabs(log_x) + ser.err; result->err += GSL_DBL_EPSILON * (fabs(t1) + fabs(t2) + fabs(t3)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_ser; } else if(x > 1.0) { /* series around x = 1.0 */ const double eps = x - 1.0; const double lne = log(eps); const double c0 = M_PI*M_PI/6.0; const double c1 = 1.0 - lne; const double c2 = -(1.0 - 2.0*lne)/4.0; const double c3 = (1.0 - 3.0*lne)/9.0; const double c4 = -(1.0 - 4.0*lne)/16.0; const double c5 = (1.0 - 5.0*lne)/25.0; const double c6 = -(1.0 - 6.0*lne)/36.0; const double c7 = (1.0 - 7.0*lne)/49.0; const double c8 = -(1.0 - 8.0*lne)/64.0; result->val = c0+eps*(c1+eps*(c2+eps*(c3+eps*(c4+eps*(c5+eps*(c6+eps*(c7+eps*c8))))))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x == 1.0) { result->val = M_PI*M_PI/6.0; result->err = 2.0 * GSL_DBL_EPSILON * M_PI*M_PI/6.0; return GSL_SUCCESS; } else if(x > 0.5) { gsl_sf_result ser; const int stat_ser = dilog_series_2(1.0-x, &ser); const double log_x = log(x); const double t1 = M_PI*M_PI/6.0; const double t2 = ser.val; const double t3 = log_x*log(1.0-x); result->val = t1 - t2 - t3; result->err = GSL_DBL_EPSILON * fabs(log_x) + ser.err; result->err += GSL_DBL_EPSILON * (fabs(t1) + fabs(t2) + fabs(t3)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_ser; } else if(x > 0.25) { return dilog_series_2(x, result); } else if(x > 0.0) { return dilog_series_1(x, result); } else { /* x == 0.0 */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } } /* Evaluate the series representation for Li2(z): * * Li2(z) = Sum[ |z|^k / k^2 Exp[i k arg(z)], {k,1,Infinity}] * |z| = r * arg(z) = theta * * Assumes 0 < r < 1. * It is used only for small r. */ static int dilogc_series_1( const double r, const double x, const double y, gsl_sf_result * real_result, gsl_sf_result * imag_result ) { const double cos_theta = x/r; const double sin_theta = y/r; const double alpha = 1.0 - cos_theta; const double beta = sin_theta; double ck = cos_theta; double sk = sin_theta; double rk = r; double real_sum = r*ck; double imag_sum = r*sk; const int kmax = 50 + (int)(22.0/(-log(r))); /* tuned for double-precision */ int k; for(k=2; kval = real_sum; real_result->err = 2.0 * kmax * GSL_DBL_EPSILON * fabs(real_sum); imag_result->val = imag_sum; imag_result->err = 2.0 * kmax * GSL_DBL_EPSILON * fabs(imag_sum); return GSL_SUCCESS; } /* Compute * * sum_{k=1}{infty} z^k / (k^2 (k+1)) * * This is a series which appears in the one-step accelerated * method, which splits out one elementary function from the * full definition of Li_2. */ static int series_2_c( double r, double x, double y, gsl_sf_result * sum_re, gsl_sf_result * sum_im ) { const double cos_theta = x/r; const double sin_theta = y/r; const double alpha = 1.0 - cos_theta; const double beta = sin_theta; double ck = cos_theta; double sk = sin_theta; double rk = r; double real_sum = 0.5 * r*ck; double imag_sum = 0.5 * r*sk; const int kmax = 30 + (int)(18.0/(-log(r))); /* tuned for double-precision */ int k; for(k=2; kval = real_sum; sum_re->err = 2.0 * kmax * GSL_DBL_EPSILON * fabs(real_sum); sum_im->val = imag_sum; sum_im->err = 2.0 * kmax * GSL_DBL_EPSILON * fabs(imag_sum); return GSL_SUCCESS; } /* Compute Li_2(z) using the one-step accelerated series. * * Li_2(z) = 1 + (1-z)ln(1-z)/z + series_2_c(z) * * z = r exp(i theta) * assumes: r < 1 * assumes: r > epsilon, so that we take no special care with log(1-z) */ static int dilogc_series_2( const double r, const double x, const double y, gsl_sf_result * real_dl, gsl_sf_result * imag_dl ) { if(r == 0.0) { real_dl->val = 0.0; imag_dl->val = 0.0; real_dl->err = 0.0; imag_dl->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result sum_re; gsl_sf_result sum_im; const int stat_s3 = series_2_c(r, x, y, &sum_re, &sum_im); /* t = ln(1-z)/z */ gsl_sf_result ln_omz_r; gsl_sf_result ln_omz_theta; const int stat_log = gsl_sf_complex_log_e(1.0-x, -y, &ln_omz_r, &ln_omz_theta); const double t_x = ( ln_omz_r.val * x + ln_omz_theta.val * y)/(r*r); const double t_y = (-ln_omz_r.val * y + ln_omz_theta.val * x)/(r*r); /* r = (1-z) ln(1-z)/z */ const double r_x = (1.0 - x) * t_x + y * t_y; const double r_y = (1.0 - x) * t_y - y * t_x; real_dl->val = sum_re.val + r_x + 1.0; imag_dl->val = sum_im.val + r_y; real_dl->err = sum_re.err + 2.0*GSL_DBL_EPSILON*(fabs(real_dl->val) + fabs(r_x)); imag_dl->err = sum_im.err + 2.0*GSL_DBL_EPSILON*(fabs(imag_dl->val) + fabs(r_y)); return GSL_ERROR_SELECT_2(stat_s3, stat_log); } } /* Evaluate a series for Li_2(z) when |z| is near 1. * This is uniformly good away from z=1. * * Li_2(z) = Sum[ a^n/n! H_n(theta), {n, 0, Infinity}] * * where * H_n(theta) = Sum[ e^(i m theta) m^n / m^2, {m, 1, Infinity}] * a = ln(r) * * H_0(t) = Gl_2(t) + i Cl_2(t) * H_1(t) = 1/2 ln(2(1-c)) + I atan2(-s, 1-c) * H_2(t) = -1/2 + I/2 s/(1-c) * H_3(t) = -1/2 /(1-c) * H_4(t) = -I/2 s/(1-c)^2 * H_5(t) = 1/2 (2 + c)/(1-c)^2 * H_6(t) = I/2 s/(1-c)^5 (8(1-c) - s^2 (3 + c)) */ static int dilogc_series_3( const double r, const double x, const double y, gsl_sf_result * real_result, gsl_sf_result * imag_result ) { const double theta = atan2(y, x); const double cos_theta = x/r; const double sin_theta = y/r; const double a = log(r); const double omc = 1.0 - cos_theta; const double omc2 = omc*omc; double H_re[7]; double H_im[7]; double an, nfact; double sum_re, sum_im; gsl_sf_result Him0; int n; H_re[0] = M_PI*M_PI/6.0 + 0.25*(theta*theta - 2.0*M_PI*fabs(theta)); gsl_sf_clausen_e(theta, &Him0); H_im[0] = Him0.val; H_re[1] = -0.5*log(2.0*omc); H_im[1] = -atan2(-sin_theta, omc); H_re[2] = -0.5; H_im[2] = 0.5 * sin_theta/omc; H_re[3] = -0.5/omc; H_im[3] = 0.0; H_re[4] = 0.0; H_im[4] = -0.5*sin_theta/omc2; H_re[5] = 0.5 * (2.0 + cos_theta)/omc2; H_im[5] = 0.0; H_re[6] = 0.0; H_im[6] = 0.5 * sin_theta/(omc2*omc2*omc) * (8.0*omc - sin_theta*sin_theta*(3.0 + cos_theta)); sum_re = H_re[0]; sum_im = H_im[0]; an = 1.0; nfact = 1.0; for(n=1; n<=6; n++) { double t; an *= a; nfact *= n; t = an/nfact; sum_re += t * H_re[n]; sum_im += t * H_im[n]; } real_result->val = sum_re; real_result->err = 2.0 * 6.0 * GSL_DBL_EPSILON * fabs(sum_re) + fabs(an/nfact); imag_result->val = sum_im; imag_result->err = 2.0 * 6.0 * GSL_DBL_EPSILON * fabs(sum_im) + Him0.err + fabs(an/nfact); return GSL_SUCCESS; } /* Calculate complex dilogarithm Li_2(z) in the fundamental region, * which we take to be the intersection of the unit disk with the * half-space x < MAGIC_SPLIT_VALUE. It turns out that 0.732 is a * nice choice for MAGIC_SPLIT_VALUE since then points mapped out * of the x > MAGIC_SPLIT_VALUE region and into another part of the * unit disk are bounded in radius by MAGIC_SPLIT_VALUE itself. * * If |z| < 0.98 we use a direct series summation. Otherwise z is very * near the unit circle, and the series_2 expansion is used; see above. * Because the fundamental region is bounded away from z = 1, this * works well. */ static int dilogc_fundamental(double r, double x, double y, gsl_sf_result * real_dl, gsl_sf_result * imag_dl) { if(r > 0.98) return dilogc_series_3(r, x, y, real_dl, imag_dl); else if(r > 0.25) return dilogc_series_2(r, x, y, real_dl, imag_dl); else return dilogc_series_1(r, x, y, real_dl, imag_dl); } /* Compute Li_2(z) for z in the unit disk, |z| < 1. If z is outside * the fundamental region, which means that it is too close to z = 1, * then it is reflected into the fundamental region using the identity * * Li2(z) = -Li2(1-z) + zeta(2) - ln(z) ln(1-z). */ static int dilogc_unitdisk(double x, double y, gsl_sf_result * real_dl, gsl_sf_result * imag_dl) { static const double MAGIC_SPLIT_VALUE = 0.732; static const double zeta2 = M_PI*M_PI/6.0; const double r = hypot(x, y); if(x > MAGIC_SPLIT_VALUE) { /* Reflect away from z = 1 if we are too close. The magic value * insures that the reflected value of the radius satisfies the * related inequality r_tmp < MAGIC_SPLIT_VALUE. */ const double x_tmp = 1.0 - x; const double y_tmp = - y; const double r_tmp = hypot(x_tmp, y_tmp); /* const double cos_theta_tmp = x_tmp/r_tmp; */ /* const double sin_theta_tmp = y_tmp/r_tmp; */ gsl_sf_result result_re_tmp; gsl_sf_result result_im_tmp; const int stat_dilog = dilogc_fundamental(r_tmp, x_tmp, y_tmp, &result_re_tmp, &result_im_tmp); const double lnz = log(r); /* log(|z|) */ const double lnomz = log(r_tmp); /* log(|1-z|) */ const double argz = atan2(y, x); /* arg(z) assuming principal branch */ const double argomz = atan2(y_tmp, x_tmp); /* arg(1-z) */ real_dl->val = -result_re_tmp.val + zeta2 - lnz*lnomz + argz*argomz; real_dl->err = result_re_tmp.err; real_dl->err += 2.0 * GSL_DBL_EPSILON * (zeta2 + fabs(lnz*lnomz) + fabs(argz*argomz)); imag_dl->val = -result_im_tmp.val - argz*lnomz - argomz*lnz; imag_dl->err = result_im_tmp.err; imag_dl->err += 2.0 * GSL_DBL_EPSILON * (fabs(argz*lnomz) + fabs(argomz*lnz)); return stat_dilog; } else { return dilogc_fundamental(r, x, y, real_dl, imag_dl); } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_dilog_e(const double x, gsl_sf_result * result) { if(x >= 0.0) { return dilog_xge0(x, result); } else { gsl_sf_result d1, d2; int stat_d1 = dilog_xge0( -x, &d1); int stat_d2 = dilog_xge0(x*x, &d2); result->val = -d1.val + 0.5 * d2.val; result->err = d1.err + 0.5 * d2.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_d1, stat_d2); } } int gsl_sf_complex_dilog_xy_e( const double x, const double y, gsl_sf_result * real_dl, gsl_sf_result * imag_dl ) { const double zeta2 = M_PI*M_PI/6.0; const double r2 = x*x + y*y; if(y == 0.0) { if(x >= 1.0) { imag_dl->val = -M_PI * log(x); imag_dl->err = 2.0 * GSL_DBL_EPSILON * fabs(imag_dl->val); } else { imag_dl->val = 0.0; imag_dl->err = 0.0; } return gsl_sf_dilog_e(x, real_dl); } else if(fabs(r2 - 1.0) < GSL_DBL_EPSILON) { /* Lewin A.2.4.1 and A.2.4.2 */ const double theta = atan2(y, x); const double term1 = theta*theta/4.0; const double term2 = M_PI*fabs(theta)/2.0; real_dl->val = zeta2 + term1 - term2; real_dl->err = 2.0 * GSL_DBL_EPSILON * (zeta2 + term1 + term2); return gsl_sf_clausen_e(theta, imag_dl); } else if(r2 < 1.0) { return dilogc_unitdisk(x, y, real_dl, imag_dl); } else { /* Reduce argument to unit disk. */ const double r = sqrt(r2); const double x_tmp = x/r2; const double y_tmp = -y/r2; /* const double r_tmp = 1.0/r; */ gsl_sf_result result_re_tmp, result_im_tmp; const int stat_dilog = dilogc_unitdisk(x_tmp, y_tmp, &result_re_tmp, &result_im_tmp); /* Unwind the inversion. * * Li_2(z) + Li_2(1/z) = -zeta(2) - 1/2 ln(-z)^2 */ const double theta = atan2(y, x); const double theta_abs = fabs(theta); const double theta_sgn = ( theta < 0.0 ? -1.0 : 1.0 ); const double ln_minusz_re = log(r); const double ln_minusz_im = theta_sgn * (theta_abs - M_PI); const double lmz2_re = ln_minusz_re*ln_minusz_re - ln_minusz_im*ln_minusz_im; const double lmz2_im = 2.0*ln_minusz_re*ln_minusz_im; real_dl->val = -result_re_tmp.val - 0.5 * lmz2_re - zeta2; real_dl->err = result_re_tmp.err + 2.0*GSL_DBL_EPSILON*(0.5 * fabs(lmz2_re) + zeta2); imag_dl->val = -result_im_tmp.val - 0.5 * lmz2_im; imag_dl->err = result_im_tmp.err + 2.0*GSL_DBL_EPSILON*fabs(lmz2_im); return stat_dilog; } } int gsl_sf_complex_dilog_e( const double r, const double theta, gsl_sf_result * real_dl, gsl_sf_result * imag_dl ) { const double cos_theta = cos(theta); const double sin_theta = sin(theta); const double x = r * cos_theta; const double y = r * sin_theta; return gsl_sf_complex_dilog_xy_e(x, y, real_dl, imag_dl); } int gsl_sf_complex_spence_xy_e( const double x, const double y, gsl_sf_result * real_sp, gsl_sf_result * imag_sp ) { const double oms_x = 1.0 - x; const double oms_y = - y; return gsl_sf_complex_dilog_xy_e(oms_x, oms_y, real_sp, imag_sp); } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_dilog(const double x) { EVAL_RESULT(gsl_sf_dilog_e(x, &result)); } sources_5316/external/gsl/gsl_permute_vector_char.h0000664000176700017670000000265511705263724021431 0ustar paulpaul/* permutation/gsl_permute_vector_char.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_CHAR_H__ #define __GSL_PERMUTE_VECTOR_CHAR_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_char.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_char (const gsl_permutation * p, gsl_vector_char * v); int gsl_permute_vector_char_inverse (const gsl_permutation * p, gsl_vector_char * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_CHAR_H__ */ sources_5316/external/gsl/gsl_randist__exponential.c0000664000176700017670000000250611723710247021565 0ustar paulpaul/* randist/exponential.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* The exponential distribution has the form p(x) dx = exp(-x/mu) dx/mu for x = 0 ... +infty */ double gsl_ran_exponential (const gsl_rng * r, const double mu) { double u = gsl_rng_uniform_pos (r); return -mu * log (u); } double gsl_ran_exponential_pdf (const double x, const double mu) { if (x < 0) { return 0 ; } else { double p = exp (-x/mu)/mu; return p; } } sources_5316/external/gsl/gsl_cblas__srotmg.c0000664000176700017670000000034211723710247020166 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_srotmg (float *d1, float *d2, float *b1, const float b2, float *P) { #define BASE float #include "gsl_cblas__source_rotmg.h" #undef BASE } sources_5316/external/gsl/gsl_sf_clausen.h0000664000176700017670000000266711705263724017516 0ustar paulpaul/* specfunc/gsl_sf_clausen.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_CLAUSEN_H__ #define __GSL_SF_CLAUSEN_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Calculate the Clausen integral: * Cl_2(x) := Integrate[-Log[2 Sin[t/2]], {t,0,x}] * * Relation to dilogarithm: * Cl_2(theta) = Im[ Li_2(e^(i theta)) ] */ int gsl_sf_clausen_e(double x, gsl_sf_result * result); double gsl_sf_clausen(const double x); __END_DECLS #endif /* __GSL_SF_CLAUSEN_H__ */ sources_5316/external/gsl/gsl_specfunc__mathieu_angfunc.c0000664000176700017670000001747211723710247022546 0ustar paulpaul/* specfunc/mathieu_angfunc.c * * Copyright (C) 2002 Lowell Johnson * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Author: L. Johnson */ #include "gsl__config.h" #include #include #include #include "gsl_math.h" #include "gsl_sf_mathieu.h" int gsl_sf_mathieu_ce(int order, double qq, double zz, gsl_sf_result *result) { int even_odd, ii, status; double coeff[GSL_SF_MATHIEU_COEFF], norm, fn, factor; gsl_sf_result aa; norm = 0.0; even_odd = 0; if (order % 2 != 0) even_odd = 1; /* Handle the trivial case where q = 0. */ if (qq == 0.0) { norm = 1.0; if (order == 0) norm = sqrt(2.0); fn = cos(order*zz)/norm; result->val = fn; result->err = 2.0*GSL_DBL_EPSILON; factor = fabs(fn); if (factor > 1.0) result->err *= factor; return GSL_SUCCESS; } /* Use symmetry characteristics of the functions to handle cases with negative order. */ if (order < 0) order *= -1; /* Compute the characteristic value. */ status = gsl_sf_mathieu_a(order, qq, &aa); if (status != GSL_SUCCESS) { return status; } /* Compute the series coefficients. */ status = gsl_sf_mathieu_a_coeff(order, qq, aa.val, coeff); if (status != GSL_SUCCESS) { return status; } if (even_odd == 0) { fn = 0.0; norm = coeff[0]*coeff[0]; for (ii=0; iival = fn; result->err = 2.0*GSL_DBL_EPSILON; factor = fabs(fn); if (factor > 1.0) result->err *= factor; return GSL_SUCCESS; } int gsl_sf_mathieu_se(int order, double qq, double zz, gsl_sf_result *result) { int even_odd, ii, status; double coeff[GSL_SF_MATHIEU_COEFF], norm, fn, factor; gsl_sf_result aa; norm = 0.0; even_odd = 0; if (order % 2 != 0) even_odd = 1; /* Handle the trivial cases where order = 0 and/or q = 0. */ if (order == 0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } if (qq == 0.0) { norm = 1.0; fn = sin(order*zz); result->val = fn; result->err = 2.0*GSL_DBL_EPSILON; factor = fabs(fn); if (factor > 1.0) result->err *= factor; return GSL_SUCCESS; } /* Use symmetry characteristics of the functions to handle cases with negative order. */ if (order < 0) order *= -1; /* Compute the characteristic value. */ status = gsl_sf_mathieu_b(order, qq, &aa); if (status != GSL_SUCCESS) { return status; } /* Compute the series coefficients. */ status = gsl_sf_mathieu_b_coeff(order, qq, aa.val, coeff); if (status != GSL_SUCCESS) { return status; } if (even_odd == 0) { fn = 0.0; for (ii=0; iival = fn; result->err = 2.0*GSL_DBL_EPSILON; factor = fabs(fn); if (factor > 1.0) result->err *= factor; return GSL_SUCCESS; } int gsl_sf_mathieu_ce_array(int nmin, int nmax, double qq, double zz, gsl_sf_mathieu_workspace *work, double result_array[]) { int even_odd, order, ii, jj, status; double coeff[GSL_SF_MATHIEU_COEFF], *aa = work->aa, norm; /* Initialize the result array to zeroes. */ for (ii=0; iisize < (unsigned int)nmax) { GSL_ERROR("Work space not large enough", GSL_EINVAL); } if (nmin < 0 || nmax < nmin) { GSL_ERROR("domain error", GSL_EDOM); } /* Compute all of the eigenvalues up to nmax. */ gsl_sf_mathieu_a_array(0, nmax, qq, work, aa); for (ii=0, order=nmin; order<=nmax; ii++, order++) { norm = 0.0; even_odd = 0; if (order % 2 != 0) even_odd = 1; /* Handle the trivial case where q = 0. */ if (qq == 0.0) { norm = 1.0; if (order == 0) norm = sqrt(2.0); result_array[ii] = cos(order*zz)/norm; continue; } /* Compute the series coefficients. */ status = gsl_sf_mathieu_a_coeff(order, qq, aa[order], coeff); if (status != GSL_SUCCESS) return status; if (even_odd == 0) { norm = coeff[0]*coeff[0]; for (jj=0; jjbb, norm; /* Initialize the result array to zeroes. */ for (ii=0; iisize < (unsigned int)nmax) { GSL_ERROR("Work space not large enough", GSL_EINVAL); } if (nmin < 0 || nmax < nmin) { GSL_ERROR("domain error", GSL_EDOM); } /* Compute all of the eigenvalues up to nmax. */ gsl_sf_mathieu_b_array(0, nmax, qq, work, bb); for (ii=0, order=nmin; order<=nmax; ii++, order++) { norm = 0.0; even_odd = 0; if (order % 2 != 0) even_odd = 1; /* Handle the trivial case where q = 0. */ if (qq == 0.0) { norm = 1.0; result_array[ii] = sin(order*zz); continue; } /* Compute the series coefficients. */ status = gsl_sf_mathieu_b_coeff(order, qq, bb[order], coeff); if (status != GSL_SUCCESS) { return status; } if (even_odd == 0) { for (jj=0; jjval = exp(lnr); result->err = 2.0 * GSL_DBL_EPSILON * (fabs(lnr) + 1.0) * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result gstar; gsl_sf_result ln_term; double term1; if (x < 0.5*a) { double u = x/a; double ln_u = log(u); ln_term.val = ln_u - u + 1.0; ln_term.err = (fabs(ln_u) + fabs(u) + 1.0) * GSL_DBL_EPSILON; } else { double mu = (x-a)/a; gsl_sf_log_1plusx_mx_e(mu, &ln_term); /* log(1+mu) - mu */ }; gsl_sf_gammastar_e(a, &gstar); term1 = exp(a*ln_term.val)/sqrt(2.0*M_PI*a); result->val = term1/gstar.val; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(a*ln_term.val) + 1.0) * fabs(result->val); result->err += gstar.err/fabs(gstar.val) * fabs(result->val); return GSL_SUCCESS; } } /* P series representation. */ static int gamma_inc_P_series(const double a, const double x, gsl_sf_result * result) { const int nmax = 5000; gsl_sf_result D; int stat_D = gamma_inc_D(a, x, &D); double sum = 1.0; double term = 1.0; int n; for(n=1; nval = D.val * sum; result->err = D.err * fabs(sum); result->err += (1.0 + n) * GSL_DBL_EPSILON * fabs(result->val); if(n == nmax) GSL_ERROR ("error", GSL_EMAXITER); else return stat_D; } /* Q large x asymptotic */ static int gamma_inc_Q_large_x(const double a, const double x, gsl_sf_result * result) { const int nmax = 5000; gsl_sf_result D; const int stat_D = gamma_inc_D(a, x, &D); double sum = 1.0; double term = 1.0; double last = 1.0; int n; for(n=1; n 1.0) break; if(fabs(term/sum) < GSL_DBL_EPSILON) break; sum += term; last = term; } result->val = D.val * (a/x) * sum; result->err = D.err * fabs((a/x) * sum); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(n == nmax) GSL_ERROR ("error in large x asymptotic", GSL_EMAXITER); else return stat_D; } /* Uniform asymptotic for x near a, a and x large. * See [Temme, p. 285] */ static int gamma_inc_Q_asymp_unif(const double a, const double x, gsl_sf_result * result) { const double rta = sqrt(a); const double eps = (x-a)/a; gsl_sf_result ln_term; const int stat_ln = gsl_sf_log_1plusx_mx_e(eps, &ln_term); /* log(1+eps) - eps */ const double eta = GSL_SIGN(eps) * sqrt(-2.0*ln_term.val); gsl_sf_result erfc; double R; double c0, c1; /* This used to say erfc(eta*M_SQRT2*rta), which is wrong. * The sqrt(2) is in the denominator. Oops. * Fixed: [GJ] Mon Nov 15 13:25:32 MST 2004 */ gsl_sf_erfc_e(eta*rta/M_SQRT2, &erfc); if(fabs(eps) < GSL_ROOT5_DBL_EPSILON) { c0 = -1.0/3.0 + eps*(1.0/12.0 - eps*(23.0/540.0 - eps*(353.0/12960.0 - eps*589.0/30240.0))); c1 = -1.0/540.0 - eps/288.0; } else { const double rt_term = sqrt(-2.0 * ln_term.val/(eps*eps)); const double lam = x/a; c0 = (1.0 - 1.0/rt_term)/eps; c1 = -(eta*eta*eta * (lam*lam + 10.0*lam + 1.0) - 12.0 * eps*eps*eps) / (12.0 * eta*eta*eta*eps*eps*eps); } R = exp(-0.5*a*eta*eta)/(M_SQRT2*M_SQRTPI*rta) * (c0 + c1/a); result->val = 0.5 * erfc.val + R; result->err = GSL_DBL_EPSILON * fabs(R * 0.5 * a*eta*eta) + 0.5 * erfc.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_ln; } /* Continued fraction which occurs in evaluation * of Q(a,x) or Gamma(a,x). * * 1 (1-a)/x 1/x (2-a)/x 2/x (3-a)/x * F(a,x) = ---- ------- ----- -------- ----- -------- ... * 1 + 1 + 1 + 1 + 1 + 1 + * * Hans E. Plesser, 2002-01-22 (hans dot plesser at itf dot nlh dot no). * * Split out from gamma_inc_Q_CF() by GJ [Tue Apr 1 13:16:41 MST 2003]. * See gamma_inc_Q_CF() below. * */ static int gamma_inc_F_CF(const double a, const double x, gsl_sf_result * result) { const int nmax = 5000; const double small = gsl_pow_3 (GSL_DBL_EPSILON); double hn = 1.0; /* convergent */ double Cn = 1.0 / small; double Dn = 1.0; int n; /* n == 1 has a_1, b_1, b_0 independent of a,x, so that has been done by hand */ for ( n = 2 ; n < nmax ; n++ ) { double an; double delta; if(GSL_IS_ODD(n)) an = 0.5*(n-1)/x; else an = (0.5*n-a)/x; Dn = 1.0 + an * Dn; if ( fabs(Dn) < small ) Dn = small; Cn = 1.0 + an/Cn; if ( fabs(Cn) < small ) Cn = small; Dn = 1.0 / Dn; delta = Cn * Dn; hn *= delta; if(fabs(delta-1.0) < GSL_DBL_EPSILON) break; } result->val = hn; result->err = 2.0*GSL_DBL_EPSILON * fabs(hn); result->err += GSL_DBL_EPSILON * (2.0 + 0.5*n) * fabs(result->val); if(n == nmax) GSL_ERROR ("error in CF for F(a,x)", GSL_EMAXITER); else return GSL_SUCCESS; } /* Continued fraction for Q. * * Q(a,x) = D(a,x) a/x F(a,x) * * Hans E. Plesser, 2002-01-22 (hans dot plesser at itf dot nlh dot no): * * Since the Gautschi equivalent series method for CF evaluation may lead * to singularities, I have replaced it with the modified Lentz algorithm * given in * * I J Thompson and A R Barnett * Coulomb and Bessel Functions of Complex Arguments and Order * J Computational Physics 64:490-509 (1986) * * In consequence, gamma_inc_Q_CF_protected() is now obsolete and has been * removed. * * Identification of terms between the above equation for F(a, x) and * the first equation in the appendix of Thompson&Barnett is as follows: * * b_0 = 0, b_n = 1 for all n > 0 * * a_1 = 1 * a_n = (n/2-a)/x for n even * a_n = (n-1)/(2x) for n odd * */ static int gamma_inc_Q_CF(const double a, const double x, gsl_sf_result * result) { gsl_sf_result D; gsl_sf_result F; const int stat_D = gamma_inc_D(a, x, &D); const int stat_F = gamma_inc_F_CF(a, x, &F); result->val = D.val * (a/x) * F.val; result->err = D.err * fabs((a/x) * F.val) + fabs(D.val * a/x * F.err); return GSL_ERROR_SELECT_2(stat_F, stat_D); } /* Useful for small a and x. Handles the subtraction analytically. */ static int gamma_inc_Q_series(const double a, const double x, gsl_sf_result * result) { double term1; /* 1 - x^a/Gamma(a+1) */ double sum; /* 1 + (a+1)/(a+2)(-x)/2! + (a+1)/(a+3)(-x)^2/3! + ... */ int stat_sum; double term2; /* a temporary variable used at the end */ { /* Evaluate series for 1 - x^a/Gamma(a+1), small a */ const double pg21 = -2.404113806319188570799476; /* PolyGamma[2,1] */ const double lnx = log(x); const double el = M_EULER+lnx; const double c1 = -el; const double c2 = M_PI*M_PI/12.0 - 0.5*el*el; const double c3 = el*(M_PI*M_PI/12.0 - el*el/6.0) + pg21/6.0; const double c4 = -0.04166666666666666667 * (-1.758243446661483480 + lnx) * (-0.764428657272716373 + lnx) * ( 0.723980571623507657 + lnx) * ( 4.107554191916823640 + lnx); const double c5 = -0.0083333333333333333 * (-2.06563396085715900 + lnx) * (-1.28459889470864700 + lnx) * (-0.27583535756454143 + lnx) * ( 1.33677371336239618 + lnx) * ( 5.17537282427561550 + lnx); const double c6 = -0.0013888888888888889 * (-2.30814336454783200 + lnx) * (-1.65846557706987300 + lnx) * (-0.88768082560020400 + lnx) * ( 0.17043847751371778 + lnx) * ( 1.92135970115863890 + lnx) * ( 6.22578557795474900 + lnx); const double c7 = -0.00019841269841269841 * (-2.5078657901291800 + lnx) * (-1.9478900888958200 + lnx) * (-1.3194837322612730 + lnx) * (-0.5281322700249279 + lnx) * ( 0.5913834939078759 + lnx) * ( 2.4876819633378140 + lnx) * ( 7.2648160783762400 + lnx); const double c8 = -0.00002480158730158730 * (-2.677341544966400 + lnx) * (-2.182810448271700 + lnx) * (-1.649350342277400 + lnx) * (-1.014099048290790 + lnx) * (-0.191366955370652 + lnx) * ( 0.995403817918724 + lnx) * ( 3.041323283529310 + lnx) * ( 8.295966556941250 + lnx); const double c9 = -2.75573192239859e-6 * (-2.8243487670469080 + lnx) * (-2.3798494322701120 + lnx) * (-1.9143674728689960 + lnx) * (-1.3814529102920370 + lnx) * (-0.7294312810261694 + lnx) * ( 0.1299079285269565 + lnx) * ( 1.3873333251885240 + lnx) * ( 3.5857258865210760 + lnx) * ( 9.3214237073814600 + lnx); const double c10 = -2.75573192239859e-7 * (-2.9540329644556910 + lnx) * (-2.5491366926991850 + lnx) * (-2.1348279229279880 + lnx) * (-1.6741881076349450 + lnx) * (-1.1325949616098420 + lnx) * (-0.4590034650618494 + lnx) * ( 0.4399352987435699 + lnx) * ( 1.7702236517651670 + lnx) * ( 4.1231539047474080 + lnx) * ( 10.342627908148680 + lnx); term1 = a*(c1+a*(c2+a*(c3+a*(c4+a*(c5+a*(c6+a*(c7+a*(c8+a*(c9+a*c10))))))))); } { /* Evaluate the sum. */ const int nmax = 5000; double t = 1.0; int n; sum = 1.0; for(n=1; nval = term1 + term2; result->err = GSL_DBL_EPSILON * (fabs(term1) + 2.0*fabs(term2)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_sum; } /* series for small a and x, but not defined for a == 0 */ static int gamma_inc_series(double a, double x, gsl_sf_result * result) { gsl_sf_result Q; gsl_sf_result G; const int stat_Q = gamma_inc_Q_series(a, x, &Q); const int stat_G = gsl_sf_gamma_e(a, &G); result->val = Q.val * G.val; result->err = fabs(Q.val * G.err) + fabs(Q.err * G.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Q, stat_G); } static int gamma_inc_a_gt_0(double a, double x, gsl_sf_result * result) { /* x > 0 and a > 0; use result for Q */ gsl_sf_result Q; gsl_sf_result G; const int stat_Q = gsl_sf_gamma_inc_Q_e(a, x, &Q); const int stat_G = gsl_sf_gamma_e(a, &G); result->val = G.val * Q.val; result->err = fabs(G.val * Q.err) + fabs(G.err * Q.val); result->err += 2.0*GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_G, stat_Q); } static int gamma_inc_CF(double a, double x, gsl_sf_result * result) { gsl_sf_result F; gsl_sf_result pre; const double am1lgx = (a-1.0)*log(x); const int stat_F = gamma_inc_F_CF(a, x, &F); const int stat_E = gsl_sf_exp_err_e(am1lgx - x, GSL_DBL_EPSILON*fabs(am1lgx), &pre); result->val = F.val * pre.val; result->err = fabs(F.err * pre.val) + fabs(F.val * pre.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_F, stat_E); } /* evaluate Gamma(0,x), x > 0 */ #define GAMMA_INC_A_0(x, result) gsl_sf_expint_E1_e(x, result) /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_gamma_inc_Q_e(const double a, const double x, gsl_sf_result * result) { if(a < 0.0 || x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(a == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x <= 0.5*a) { /* If the series is quick, do that. It is * robust and simple. */ gsl_sf_result P; int stat_P = gamma_inc_P_series(a, x, &P); result->val = 1.0 - P.val; result->err = P.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_P; } else if(a >= 1.0e+06 && (x-a)*(x-a) < a) { /* Then try the difficult asymptotic regime. * This is the only way to do this region. */ return gamma_inc_Q_asymp_unif(a, x, result); } else if(a < 0.2 && x < 5.0) { /* Cancellations at small a must be handled * analytically; x should not be too big * either since the series terms grow * with x and log(x). */ return gamma_inc_Q_series(a, x, result); } else if(a <= x) { if(x <= 1.0e+06) { /* Continued fraction is excellent for x >~ a. * We do not let x be too large when x > a since * it is somewhat pointless to try this there; * the function is rapidly decreasing for * x large and x > a, and it will just * underflow in that region anyway. We * catch that case in the standard * large-x method. */ return gamma_inc_Q_CF(a, x, result); } else { return gamma_inc_Q_large_x(a, x, result); } } else { if(x > a - sqrt(a)) { /* Continued fraction again. The convergence * is a little slower here, but that is fine. * We have to trade that off against the slow * convergence of the series, which is the * only other option. */ return gamma_inc_Q_CF(a, x, result); } else { gsl_sf_result P; int stat_P = gamma_inc_P_series(a, x, &P); result->val = 1.0 - P.val; result->err = P.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_P; } } } int gsl_sf_gamma_inc_P_e(const double a, const double x, gsl_sf_result * result) { if(a <= 0.0 || x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 20.0 || x < 0.5*a) { /* Do the easy series cases. Robust and quick. */ return gamma_inc_P_series(a, x, result); } else if(a > 1.0e+06 && (x-a)*(x-a) < a) { /* Crossover region. Note that Q and P are * roughly the same order of magnitude here, * so the subtraction is stable. */ gsl_sf_result Q; int stat_Q = gamma_inc_Q_asymp_unif(a, x, &Q); result->val = 1.0 - Q.val; result->err = Q.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_Q; } else if(a <= x) { /* Q <~ P in this area, so the * subtractions are stable. */ gsl_sf_result Q; int stat_Q; if(a > 0.2*x) { stat_Q = gamma_inc_Q_CF(a, x, &Q); } else { stat_Q = gamma_inc_Q_large_x(a, x, &Q); } result->val = 1.0 - Q.val; result->err = Q.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_Q; } else { if((x-a)*(x-a) < a) { /* This condition is meant to insure * that Q is not very close to 1, * so the subtraction is stable. */ gsl_sf_result Q; int stat_Q = gamma_inc_Q_CF(a, x, &Q); result->val = 1.0 - Q.val; result->err = Q.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_Q; } else { return gamma_inc_P_series(a, x, result); } } } int gsl_sf_gamma_inc_e(const double a, const double x, gsl_sf_result * result) { if(x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { return gsl_sf_gamma_e(a, result); } else if(a == 0.0) { return GAMMA_INC_A_0(x, result); } else if(a > 0.0) { return gamma_inc_a_gt_0(a, x, result); } else if(x > 0.25) { /* continued fraction seems to fail for x too small; otherwise it is ok, independent of the value of |x/a|, because of the non-oscillation in the expansion, i.e. the CF is un-conditionally convergent for a < 0 and x > 0 */ return gamma_inc_CF(a, x, result); } else if(fabs(a) < 0.5) { return gamma_inc_series(a, x, result); } else { /* a = fa + da; da >= 0 */ const double fa = floor(a); const double da = a - fa; gsl_sf_result g_da; const int stat_g_da = ( da > 0.0 ? gamma_inc_a_gt_0(da, x, &g_da) : GAMMA_INC_A_0(x, &g_da)); double alpha = da; double gax = g_da.val; /* Gamma(alpha-1,x) = 1/(alpha-1) (Gamma(a,x) - x^(alpha-1) e^-x) */ do { const double shift = exp(-x + (alpha-1.0)*log(x)); gax = (gax - shift) / (alpha - 1.0); alpha -= 1.0; } while(alpha > a); result->val = gax; result->err = 2.0*(1.0 + fabs(a))*GSL_DBL_EPSILON*fabs(gax); return stat_g_da; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_gamma_inc_P(const double a, const double x) { EVAL_RESULT(gsl_sf_gamma_inc_P_e(a, x, &result)); } double gsl_sf_gamma_inc_Q(const double a, const double x) { EVAL_RESULT(gsl_sf_gamma_inc_Q_e(a, x, &result)); } double gsl_sf_gamma_inc(const double a, const double x) { EVAL_RESULT(gsl_sf_gamma_inc_e(a, x, &result)); } sources_5316/external/gsl/gsl_rng__fishman20.c0000664000176700017670000000446311723710247020154 0ustar paulpaul/* rng/fishman20.c * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth * The Art of Computer Programming * Volume 2 * Third Edition * Addison-Wesley * Page 108 * * It is called "Fishman" * * This implementation copyright (C) 2001 Carlo Perassi * and (C) 2003 Heiko Bauke. */ #include "gsl__config.h" #include #include "gsl_rng.h" static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); static const long int m = 2147483647, a = 48271, q = 44488, r = 3399; typedef struct { unsigned long int x; } ran_state_t; static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; const unsigned long int x = state->x; const long int h = x / q; const long int t = a * (x - h * q) - h * r; if (t < 0) { state->x = t + m; } else { state->x = t; } return state->x; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 2147483647.0; } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; if ((s%m) == 0) s = 1; /* default seed is 1 */ state->x = s & m; return; } static const gsl_rng_type ran_type = { "fishman20", /* name */ 2147483646, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_fishman20 = &ran_type; sources_5316/external/gsl/gsl_cblas__zdotc_sub.c0000664000176700017670000000047311723710247020654 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zdotc_sub (const int N, const void *X, const int incX, const void *Y, const int incY, void *result) { #define BASE double #define CONJ_SIGN (-1.0) #include "gsl_cblas__source_dot_c.h" #undef CONJ_SIGN #undef BASE } sources_5316/external/gsl/gsl_cblas__cswap.c0000664000176700017670000000034611723710247017774 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cswap (const int N, void *X, const int incX, void *Y, const int incY) { #define BASE float #include "gsl_cblas__source_swap_c.h" #undef BASE } sources_5316/external/gsl/gsl_cdf__gauss.c0000664000176700017670000001576111723710247017460 0ustar paulpaul/* cdf/gauss.c * * Copyright (C) 2002, 2004 Jason H. Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * Computes the cumulative distribution function for the Gaussian * distribution using a rational function approximation. The * computation is for the standard Normal distribution, i.e., mean 0 * and standard deviation 1. If you want to compute Pr(X < t) for a * Gaussian random variable X with non-zero mean m and standard * deviation sd not equal to 1, find gsl_cdf_ugaussian ((t-m)/sd). * This approximation is accurate to at least double precision. The * accuracy was verified with a pari-gp script. The largest error * found was about 1.4E-20. The coefficients were derived by Cody. * * References: * * W.J. Cody. "Rational Chebyshev Approximations for the Error * Function," Mathematics of Computation, v23 n107 1969, 631-637. * * W. Fraser, J.F Hart. "On the Computation of Rational Approximations * to Continuous Functions," Communications of the ACM, v5 1962. * * W.J. Kennedy Jr., J.E. Gentle. "Statistical Computing." Marcel Dekker. 1980. * * */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" #ifndef M_1_SQRT2PI #define M_1_SQRT2PI (M_2_SQRTPI * M_SQRT1_2 / 2.0) #endif #define SQRT32 (4.0 * M_SQRT2) /* * IEEE double precision dependent constants. * * GAUSS_EPSILON: Smallest positive value such that * gsl_cdf_gaussian(x) > 0.5. * GAUSS_XUPPER: Largest value x such that gsl_cdf_gaussian(x) < 1.0. * GAUSS_XLOWER: Smallest value x such that gsl_cdf_gaussian(x) > 0.0. */ #define GAUSS_EPSILON (GSL_DBL_EPSILON / 2) #define GAUSS_XUPPER (8.572) #define GAUSS_XLOWER (-37.519) #define GAUSS_SCALE (16.0) static double get_del (double x, double rational) { double xsq = 0.0; double del = 0.0; double result = 0.0; xsq = floor (x * GAUSS_SCALE) / GAUSS_SCALE; del = (x - xsq) * (x + xsq); del *= 0.5; result = exp (-0.5 * xsq * xsq) * exp (-1.0 * del) * rational; return result; } /* * Normal cdf for fabs(x) < 0.66291 */ static double gauss_small (const double x) { unsigned int i; double result = 0.0; double xsq; double xnum; double xden; const double a[5] = { 2.2352520354606839287, 161.02823106855587881, 1067.6894854603709582, 18154.981253343561249, 0.065682337918207449113 }; const double b[4] = { 47.20258190468824187, 976.09855173777669322, 10260.932208618978205, 45507.789335026729956 }; xsq = x * x; xnum = a[4] * xsq; xden = xsq; for (i = 0; i < 3; i++) { xnum = (xnum + a[i]) * xsq; xden = (xden + b[i]) * xsq; } result = x * (xnum + a[3]) / (xden + b[3]); return result; } /* * Normal cdf for 0.66291 < fabs(x) < sqrt(32). */ static double gauss_medium (const double x) { unsigned int i; double temp = 0.0; double result = 0.0; double xnum; double xden; double absx; const double c[9] = { 0.39894151208813466764, 8.8831497943883759412, 93.506656132177855979, 597.27027639480026226, 2494.5375852903726711, 6848.1904505362823326, 11602.651437647350124, 9842.7148383839780218, 1.0765576773720192317e-8 }; const double d[8] = { 22.266688044328115691, 235.38790178262499861, 1519.377599407554805, 6485.558298266760755, 18615.571640885098091, 34900.952721145977266, 38912.003286093271411, 19685.429676859990727 }; absx = fabs (x); xnum = c[8] * absx; xden = absx; for (i = 0; i < 7; i++) { xnum = (xnum + c[i]) * absx; xden = (xden + d[i]) * absx; } temp = (xnum + c[7]) / (xden + d[7]); result = get_del (x, temp); return result; } /* * Normal cdf for * {sqrt(32) < x < GAUSS_XUPPER} union { GAUSS_XLOWER < x < -sqrt(32) }. */ static double gauss_large (const double x) { int i; double result; double xsq; double temp; double xnum; double xden; double absx; const double p[6] = { 0.21589853405795699, 0.1274011611602473639, 0.022235277870649807, 0.001421619193227893466, 2.9112874951168792e-5, 0.02307344176494017303 }; const double q[5] = { 1.28426009614491121, 0.468238212480865118, 0.0659881378689285515, 0.00378239633202758244, 7.29751555083966205e-5 }; absx = fabs (x); xsq = 1.0 / (x * x); xnum = p[5] * xsq; xden = xsq; for (i = 0; i < 4; i++) { xnum = (xnum + p[i]) * xsq; xden = (xden + q[i]) * xsq; } temp = xsq * (xnum + p[4]) / (xden + q[4]); temp = (M_1_SQRT2PI - temp) / absx; result = get_del (x, temp); return result; } double gsl_cdf_ugaussian_P (const double x) { double result; double absx = fabs (x); if (absx < GAUSS_EPSILON) { result = 0.5; return result; } else if (absx < 0.66291) { result = 0.5 + gauss_small (x); return result; } else if (absx < SQRT32) { result = gauss_medium (x); if (x > 0.0) { result = 1.0 - result; } return result; } else if (x > GAUSS_XUPPER) { result = 1.0; return result; } else if (x < GAUSS_XLOWER) { result = 0.0; return result; } else { result = gauss_large (x); if (x > 0.0) { result = 1.0 - result; } } return result; } double gsl_cdf_ugaussian_Q (const double x) { double result; double absx = fabs (x); if (absx < GAUSS_EPSILON) { result = 0.5; return result; } else if (absx < 0.66291) { result = gauss_small (x); if (x < 0.0) { result = fabs (result) + 0.5; } else { result = 0.5 - result; } return result; } else if (absx < SQRT32) { result = gauss_medium (x); if (x < 0.0) { result = 1.0 - result; } return result; } else if (x > -(GAUSS_XLOWER)) { result = 0.0; return result; } else if (x < -(GAUSS_XUPPER)) { result = 1.0; return result; } else { result = gauss_large (x); if (x < 0.0) { result = 1.0 - result; } } return result; } double gsl_cdf_gaussian_P (const double x, const double sigma) { return gsl_cdf_ugaussian_P (x / sigma); } double gsl_cdf_gaussian_Q (const double x, const double sigma) { return gsl_cdf_ugaussian_Q (x / sigma); } sources_5316/external/gsl/gsl_sort_vector_int.h0000664000176700017670000000335611705263724020613 0ustar paulpaul/* sort/gsl_sort_vector_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_INT_H__ #define __GSL_SORT_VECTOR_INT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_int.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_int (gsl_vector_int * v); int gsl_sort_vector_int_index (gsl_permutation * p, const gsl_vector_int * v); int gsl_sort_vector_int_smallest (int * dest, const size_t k, const gsl_vector_int * v); int gsl_sort_vector_int_largest (int * dest, const size_t k, const gsl_vector_int * v); int gsl_sort_vector_int_smallest_index (size_t * p, const size_t k, const gsl_vector_int * v); int gsl_sort_vector_int_largest_index (size_t * p, const size_t k, const gsl_vector_int * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_INT_H__ */ sources_5316/external/gsl/gsl_cblas__strmv.c0000664000176700017670000000061511723710247020031 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_strmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const float *A, const int lda, float *X, const int incX) { #define BASE float #include "gsl_cblas__source_trmv_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__ssyrk.c0000664000176700017670000000064211723710247020031 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ssyrk (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const float alpha, const float *A, const int lda, const float beta, float *C, const int ldc) { #define BASE float #include "gsl_cblas__source_syrk_r.h" #undef BASE } sources_5316/external/gsl/gsl_sf_log.h0000664000176700017670000000401211705263724016627 0ustar paulpaul/* specfunc/gsl_sf_log.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_LOG_H__ #define __GSL_SF_LOG_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Provide a logarithm function with GSL semantics. * * exceptions: GSL_EDOM */ int gsl_sf_log_e(const double x, gsl_sf_result * result); double gsl_sf_log(const double x); /* Log(|x|) * * exceptions: GSL_EDOM */ int gsl_sf_log_abs_e(const double x, gsl_sf_result * result); double gsl_sf_log_abs(const double x); /* Complex Logarithm * exp(lnr + I theta) = zr + I zi * Returns argument in [-pi,pi]. * * exceptions: GSL_EDOM */ int gsl_sf_complex_log_e(const double zr, const double zi, gsl_sf_result * lnr, gsl_sf_result * theta); /* Log(1 + x) * * exceptions: GSL_EDOM */ int gsl_sf_log_1plusx_e(const double x, gsl_sf_result * result); double gsl_sf_log_1plusx(const double x); /* Log(1 + x) - x * * exceptions: GSL_EDOM */ int gsl_sf_log_1plusx_mx_e(const double x, gsl_sf_result * result); double gsl_sf_log_1plusx_mx(const double x); __END_DECLS #endif /* __GSL_SF_LOG_H__ */ sources_5316/external/gsl/gsl_poly__qr.c0000664000176700017670000001253411723710247017202 0ustar paulpaul/* poly/qr.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int qr_companion (double *h, size_t nc, gsl_complex_packed_ptr z); static int qr_companion (double *h, size_t nc, gsl_complex_packed_ptr zroot) { double t = 0.0; size_t iterations, e, i, j, k, m; double w, x, y, s, z; double p = 0, q = 0, r = 0; /* FIXME: if p,q,r, are not set to zero then the compiler complains that they ``might be used uninitialized in this function''. Looking at the code this does seem possible, so this should be checked. */ int notlast; size_t n = nc; next_root: if (n == 0) return GSL_SUCCESS ; iterations = 0; next_iteration: for (e = n; e >= 2; e--) { double a1 = fabs (FMAT (h, e, e - 1, nc)); double a2 = fabs (FMAT (h, e - 1, e - 1, nc)); double a3 = fabs (FMAT (h, e, e, nc)); if (a1 <= GSL_DBL_EPSILON * (a2 + a3)) break; } x = FMAT (h, n, n, nc); if (e == n) { GSL_SET_COMPLEX_PACKED (zroot, n-1, x + t, 0); /* one real root */ n--; goto next_root; /*continue;*/ } y = FMAT (h, n - 1, n - 1, nc); w = FMAT (h, n - 1, n, nc) * FMAT (h, n, n - 1, nc); if (e == n - 1) { p = (y - x) / 2; q = p * p + w; y = sqrt (fabs (q)); x += t; if (q > 0) /* two real roots */ { if (p < 0) y = -y; y += p; GSL_SET_COMPLEX_PACKED (zroot, n-1, x - w / y, 0); GSL_SET_COMPLEX_PACKED (zroot, n-2, x + y, 0); } else { GSL_SET_COMPLEX_PACKED (zroot, n-1, x + p, -y); GSL_SET_COMPLEX_PACKED (zroot, n-2, x + p, y); } n -= 2; goto next_root; /*continue;*/ } /* No more roots found yet, do another iteration */ if (iterations == 60) /* increased from 30 to 60 */ { /* too many iterations - give up! */ return GSL_FAILURE ; } if (iterations % 10 == 0 && iterations > 0) { /* use an exceptional shift */ t += x; for (i = 1; i <= n; i++) { FMAT (h, i, i, nc) -= x; } s = fabs (FMAT (h, n, n - 1, nc)) + fabs (FMAT (h, n - 1, n - 2, nc)); y = 0.75 * s; x = y; w = -0.4375 * s * s; } iterations++; for (m = n - 2; m >= e; m--) { double a1, a2, a3; z = FMAT (h, m, m, nc); r = x - z; s = y - z; p = FMAT (h, m, m + 1, nc) + (r * s - w) / FMAT (h, m + 1, m, nc); q = FMAT (h, m + 1, m + 1, nc) - z - r - s; r = FMAT (h, m + 2, m + 1, nc); s = fabs (p) + fabs (q) + fabs (r); p /= s; q /= s; r /= s; if (m == e) break; a1 = fabs (FMAT (h, m, m - 1, nc)); a2 = fabs (FMAT (h, m - 1, m - 1, nc)); a3 = fabs (FMAT (h, m + 1, m + 1, nc)); if (a1 * (fabs (q) + fabs (r)) <= GSL_DBL_EPSILON * fabs (p) * (a2 + a3)) break; } for (i = m + 2; i <= n; i++) { FMAT (h, i, i - 2, nc) = 0; } for (i = m + 3; i <= n; i++) { FMAT (h, i, i - 3, nc) = 0; } /* double QR step */ for (k = m; k <= n - 1; k++) { notlast = (k != n - 1); if (k != m) { p = FMAT (h, k, k - 1, nc); q = FMAT (h, k + 1, k - 1, nc); r = notlast ? FMAT (h, k + 2, k - 1, nc) : 0.0; x = fabs (p) + fabs (q) + fabs (r); if (x == 0) continue; /* FIXME????? */ p /= x; q /= x; r /= x; } s = sqrt (p * p + q * q + r * r); if (p < 0) s = -s; if (k != m) { FMAT (h, k, k - 1, nc) = -s * x; } else if (e != m) { FMAT (h, k, k - 1, nc) *= -1; } p += s; x = p / s; y = q / s; z = r / s; q /= p; r /= p; /* do row modifications */ for (j = k; j <= n; j++) { p = FMAT (h, k, j, nc) + q * FMAT (h, k + 1, j, nc); if (notlast) { p += r * FMAT (h, k + 2, j, nc); FMAT (h, k + 2, j, nc) -= p * z; } FMAT (h, k + 1, j, nc) -= p * y; FMAT (h, k, j, nc) -= p * x; } j = (k + 3 < n) ? (k + 3) : n; /* do column modifications */ for (i = e; i <= j; i++) { p = x * FMAT (h, i, k, nc) + y * FMAT (h, i, k + 1, nc); if (notlast) { p += z * FMAT (h, i, k + 2, nc); FMAT (h, i, k + 2, nc) -= p * r; } FMAT (h, i, k + 1, nc) -= p * q; FMAT (h, i, k, nc) -= p; } } goto next_iteration; } sources_5316/external/gsl/gsl_cblas__dscal.c0000664000176700017670000000034411723710247017743 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dscal (const int N, const double alpha, double *X, const int incX) { #define BASE double #include "gsl_cblas__source_scal_r.h" #undef BASE } sources_5316/external/gsl/gsl_linalg__exponential.c0000664000176700017670000001162511723710247021371 0ustar paulpaul/* linalg/exponential.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Calculate the matrix exponential, following * Moler + Van Loan, SIAM Rev. 20, 801 (1978). */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_mode.h" #include "gsl_errno.h" #include "gsl_blas.h" #include "gsl_linalg.h" /* store one of the suggested choices for the * Taylor series / square method from Moler + VanLoan */ struct moler_vanloan_optimal_suggestion { int k; int j; }; typedef struct moler_vanloan_optimal_suggestion mvl_suggestion_t; /* table from Moler and Van Loan * mvl_tab[gsl_mode_t][matrix_norm_group] */ static mvl_suggestion_t mvl_tab[3][6] = { /* double precision */ { { 5, 1 }, { 5, 4 }, { 7, 5 }, { 9, 7 }, { 10, 10 }, { 8, 14 } }, /* single precision */ { { 2, 1 }, { 4, 0 }, { 7, 1 }, { 6, 5 }, { 5, 9 }, { 7, 11 } }, /* approx precision */ { { 1, 0 }, { 3, 0 }, { 5, 1 }, { 4, 5 }, { 4, 8 }, { 2, 11 } } }; inline static double sup_norm(const gsl_matrix * A) { double min, max; gsl_matrix_minmax(A, &min, &max); return GSL_MAX_DBL(fabs(min), fabs(max)); } static mvl_suggestion_t obtain_suggestion(const gsl_matrix * A, gsl_mode_t mode) { const unsigned int mode_prec = GSL_MODE_PREC(mode); const double norm_A = sup_norm(A); if(norm_A < 0.01) return mvl_tab[mode_prec][0]; else if(norm_A < 0.1) return mvl_tab[mode_prec][1]; else if(norm_A < 1.0) return mvl_tab[mode_prec][2]; else if(norm_A < 10.0) return mvl_tab[mode_prec][3]; else if(norm_A < 100.0) return mvl_tab[mode_prec][4]; else if(norm_A < 1000.0) return mvl_tab[mode_prec][5]; else { /* outside the table we simply increase the number * of squarings, bringing the reduced matrix into * the range of the table; this is obviously suboptimal, * but that is the price paid for not having those extra * table entries */ const double extra = log(1.01*norm_A/1000.0) / M_LN2; const int extra_i = (unsigned int) ceil(extra); mvl_suggestion_t s = mvl_tab[mode][5]; s.j += extra_i; return s; } } /* use series representation to calculate matrix exponential; * this is used for small matrices; we use the sup_norm * to measure the size of the terms in the expansion */ static void matrix_exp_series( const gsl_matrix * B, gsl_matrix * eB, int number_of_terms ) { int count; gsl_matrix * temp = gsl_matrix_calloc(B->size1, B->size2); /* init the Horner polynomial evaluation, * eB = 1 + B/number_of_terms; we use * eB to collect the partial results */ gsl_matrix_memcpy(eB, B); gsl_matrix_scale(eB, 1.0/number_of_terms); gsl_matrix_add_diagonal(eB, 1.0); for(count = number_of_terms-1; count >= 1; --count) { /* mult_temp = 1 + B eB / count */ gsl_blas_dgemm(CblasNoTrans, CblasNoTrans, 1.0, B, eB, 0.0, temp); gsl_matrix_scale(temp, 1.0/count); gsl_matrix_add_diagonal(temp, 1.0); /* transfer partial result out of temp */ gsl_matrix_memcpy(eB, temp); } /* now eB holds the full result; we're done */ gsl_matrix_free(temp); } int gsl_linalg_exponential_ss( const gsl_matrix * A, gsl_matrix * eA, gsl_mode_t mode ) { if(A->size1 != A->size2) { GSL_ERROR("cannot exponentiate a non-square matrix", GSL_ENOTSQR); } else if(A->size1 != eA->size1 || A->size2 != eA->size2) { GSL_ERROR("exponential of matrix must have same dimension as matrix", GSL_EBADLEN); } else { int i; const mvl_suggestion_t sugg = obtain_suggestion(A, mode); const double divisor = exp(M_LN2 * sugg.j); gsl_matrix * reduced_A = gsl_matrix_alloc(A->size1, A->size2); /* decrease A by the calculated divisor */ gsl_matrix_memcpy(reduced_A, A); gsl_matrix_scale(reduced_A, 1.0/divisor); /* calculate exp of reduced matrix; store in eA as temp */ matrix_exp_series(reduced_A, eA, sugg.k); /* square repeatedly; use reduced_A for scratch */ for(i = 0; i < sugg.j; ++i) { gsl_blas_dgemm(CblasNoTrans, CblasNoTrans, 1.0, eA, eA, 0.0, reduced_A); gsl_matrix_memcpy(eA, reduced_A); } gsl_matrix_free(reduced_A); return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_ieee-utils__fp-solaris.c0000664000176700017670000000543611723710247021724 0ustar paulpaul/* ieee-utils/fp-solaris.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { fp_except mode = 0 ; fp_rnd rnd = 0 ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("solaris only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("solaris only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("solaris only supports default precision rounding", GSL_EUNSUP) ; break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: rnd = FP_RN ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_DOWN: rnd = FP_RM ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_UP: rnd = FP_RP ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_TO_ZERO: rnd = FP_RZ ; fpsetround (rnd) ; break ; default: rnd = FP_RN ; fpsetround (rnd) ; } /* Turn on all the exceptions apart from 'inexact' */ mode = FP_X_INV | FP_X_DZ | FP_X_OFL | FP_X_UFL ; if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ FP_X_INV ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("solaris does not support the denormalized operand exception. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ FP_X_DZ ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ FP_X_OFL ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ FP_X_UFL ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode |= FP_X_IMP ; } else { mode &= ~ FP_X_IMP ; } fpsetmask (mode) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_rng__lecuyer21.c0000664000176700017670000000434411723710247020176 0ustar paulpaul/* rng/lecuyer21.c * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth * The Art of Computer Programming * Volume 2 * Third Edition * Addison-Wesley * Page 108 * * This implementation copyright (C) 2001 Brian Gough, Carlo Perassi * and (C) 2003 Heiko Bauke. */ #include "gsl__config.h" #include #include "gsl_rng.h" #define AAA 40692 #define MMM 2147483399UL #define QQQ 52774 #define RRR 3791 static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); typedef struct { unsigned long int x; } ran_state_t; static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; long int y = state->x; long int r = RRR * (y / QQQ); y = AAA * (y % QQQ) - r; if (y < 0) y += MMM; state->x = y; return state->x; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 2147483399.0; } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; if ((s%MMM) == 0) s = 1; /* default seed is 1 */ state->x = s % MMM; return; } static const gsl_rng_type ran_type = { "lecuyer21", /* name */ MMM-1, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_lecuyer21 = &ran_type; sources_5316/external/gsl/gsl_sort__subset.c0000664000176700017670000000405711723710247020072 0ustar paulpaul/* sort/subset.c * * Copyright (C) 2001, 2007 Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_vector.h" #include "gsl_sort.h" #include "gsl_sort_vector.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_sort__subset_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_multifit__convergence.c0000664000176700017670000000376011723710247021731 0ustar paulpaul/* multifit/convergence.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multifit_nlin.h" int gsl_multifit_test_delta (const gsl_vector * dx, const gsl_vector * x, double epsabs, double epsrel) { size_t i; int ok = 1; const size_t n = x->size ; if (epsrel < 0.0) { GSL_ERROR ("relative tolerance is negative", GSL_EBADTOL); } for (i = 0 ; i < n ; i++) { double xi = gsl_vector_get(x,i); double dxi = gsl_vector_get(dx,i); double tolerance = epsabs + epsrel * fabs(xi) ; if (fabs(dxi) < tolerance) { ok = 1; } else { ok = 0; break; } } if (ok) return GSL_SUCCESS ; return GSL_CONTINUE; } int gsl_multifit_test_gradient (const gsl_vector * g, double epsabs) { size_t i; double residual = 0; const size_t n = g->size; if (epsabs < 0.0) { GSL_ERROR ("absolute tolerance is negative", GSL_EBADTOL); } for (i = 0 ; i < n ; i++) { double gi = gsl_vector_get(g, i); residual += fabs(gi); } if (residual < epsabs) { return GSL_SUCCESS; } return GSL_CONTINUE ; } sources_5316/external/gsl/gsl_block_char.h0000664000176700017670000000435611705263724017460 0ustar paulpaul/* block/gsl_block_char.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_CHAR_H__ #define __GSL_BLOCK_CHAR_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_char_struct { size_t size; char *data; }; typedef struct gsl_block_char_struct gsl_block_char; gsl_block_char *gsl_block_char_alloc (const size_t n); gsl_block_char *gsl_block_char_calloc (const size_t n); void gsl_block_char_free (gsl_block_char * b); int gsl_block_char_fread (FILE * stream, gsl_block_char * b); int gsl_block_char_fwrite (FILE * stream, const gsl_block_char * b); int gsl_block_char_fscanf (FILE * stream, gsl_block_char * b); int gsl_block_char_fprintf (FILE * stream, const gsl_block_char * b, const char *format); int gsl_block_char_raw_fread (FILE * stream, char * b, const size_t n, const size_t stride); int gsl_block_char_raw_fwrite (FILE * stream, const char * b, const size_t n, const size_t stride); int gsl_block_char_raw_fscanf (FILE * stream, char * b, const size_t n, const size_t stride); int gsl_block_char_raw_fprintf (FILE * stream, const char * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_char_size (const gsl_block_char * b); char * gsl_block_char_data (const gsl_block_char * b); __END_DECLS #endif /* __GSL_BLOCK_CHAR_H__ */ sources_5316/external/gsl/gsl_cblas__cgeru.c0000664000176700017670000000054011723710247017760 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cgeru (const enum CBLAS_ORDER order, const int M, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda) { #define BASE float #include "gsl_cblas__source_geru.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__dgbmv.c0000664000176700017670000000072611723710247017760 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dgbmv (const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const int KL, const int KU, const double alpha, const double *A, const int lda, const double *X, const int incX, const double beta, double *Y, const int incY) { #define BASE double #include "gsl_cblas__source_gbmv_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__cgemv.c0000664000176700017670000000064411723710247017761 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cgemv (const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE float #include "gsl_cblas__source_gemv_c.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_gerc.h0000664000176700017670000000446211705263724021172 0ustar paulpaul/* blas/source_gerc.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); if (order == CblasRowMajor) { INDEX ix = OFFSET(M, incX); for (i = 0; i < M; i++) { const BASE X_real = CONST_REAL(X, ix); const BASE X_imag = CONST_IMAG(X, ix); const BASE tmp_real = alpha_real * X_real - alpha_imag * X_imag; const BASE tmp_imag = alpha_imag * X_real + alpha_real * X_imag; INDEX jy = OFFSET(N, incY); for (j = 0; j < N; j++) { const BASE Y_real = CONST_REAL(Y, jy); const BASE Y_imag = -CONST_IMAG(Y, jy); REAL(A, lda * i + j) += Y_real * tmp_real - Y_imag * tmp_imag; IMAG(A, lda * i + j) += Y_imag * tmp_real + Y_real * tmp_imag; jy += incY; } ix += incX; } } else if (order == CblasColMajor) { INDEX jy = OFFSET(N, incY); for (j = 0; j < N; j++) { const BASE Y_real = CONST_REAL(Y, jy); const BASE Y_imag = -CONST_IMAG(Y, jy); const BASE tmp_real = alpha_real * Y_real - alpha_imag * Y_imag; const BASE tmp_imag = alpha_imag * Y_real + alpha_real * Y_imag; INDEX ix = OFFSET(M, incX); for (i = 0; i < M; i++) { const BASE X_real = CONST_REAL(X, ix); const BASE X_imag = CONST_IMAG(X, ix); REAL(A, i + lda * j) += X_real * tmp_real - X_imag * tmp_imag; IMAG(A, i + lda * j) += X_imag * tmp_real + X_real * tmp_imag; ix += incX; } jy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_matrix.h0000664000176700017670000000103611705263724016665 0ustar paulpaul#ifndef __GSL_MATRIX_H__ #define __GSL_MATRIX_H__ #include "gsl_matrix_complex_long_double.h" #include "gsl_matrix_complex_double.h" #include "gsl_matrix_complex_float.h" #include "gsl_matrix_long_double.h" #include "gsl_matrix_double.h" #include "gsl_matrix_float.h" #include "gsl_matrix_ulong.h" #include "gsl_matrix_long.h" #include "gsl_matrix_uint.h" #include "gsl_matrix_int.h" #include "gsl_matrix_ushort.h" #include "gsl_matrix_short.h" #include "gsl_matrix_uchar.h" #include "gsl_matrix_char.h" #endif /* __GSL_MATRIX_H__ */ sources_5316/external/gsl/gsl_cblas__ctpsv.c0000664000176700017670000000061711723710247020017 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" #include "gsl_cblas__hypot.c" void cblas_ctpsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *Ap, void *X, const int incX) { #define BASE float #include "gsl_cblas__source_tpsv_c.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_tpsv_c.h0000664000176700017670000002011111705263724021535 0ustar paulpaul/* blas/source_tpsv_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (TransA == CblasConjTrans) ? -1 : 1; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; const int nonunit = (Diag == CblasNonUnit); INDEX i, j; if (N == 0) return; /* form x := inv( A )*x */ if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX) + incX * (N - 1); if (nonunit) { const BASE a_real = CONST_REAL(Ap, TPUP(N, (N - 1), (N - 1))); const BASE a_imag = conj * CONST_IMAG(Ap, TPUP(N, (N - 1), (N - 1))); const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (x_real * b_real + x_imag * b_imag) / s; IMAG(X, ix) = (x_imag * b_real - b_imag * x_real) / s; } ix -= incX; for (i = N - 1; i > 0 && i--;) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); INDEX jx = ix + incX; for (j = i + 1; j < N; j++) { const BASE Aij_real = CONST_REAL(Ap, TPUP(N, i, j)); const BASE Aij_imag = conj * CONST_IMAG(Ap, TPUP(N, i, j)); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(Ap, TPUP(N, i, i)); const BASE a_imag = conj * CONST_IMAG(Ap, TPUP(N, i, i)); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { /* forward substitution */ INDEX ix = OFFSET(N, incX); if (nonunit) { const BASE a_real = CONST_REAL(Ap, TPLO(N, 0, 0)); const BASE a_imag = conj * CONST_IMAG(Ap, TPLO(N, 0, 0)); const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (x_real * b_real + x_imag * b_imag) / s; IMAG(X, ix) = (x_imag * b_real - b_imag * x_real) / s; } ix += incX; for (i = 1; i < N; i++) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE Aij_real = CONST_REAL(Ap, TPLO(N, i, j)); const BASE Aij_imag = conj * CONST_IMAG(Ap, TPLO(N, i, j)); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(Ap, TPLO(N, i, i)); const BASE a_imag = conj * CONST_IMAG(Ap, TPLO(N, i, i)); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := inv( A' )*x */ /* forward substitution */ INDEX ix = OFFSET(N, incX); if (nonunit) { const BASE a_real = CONST_REAL(Ap, TPUP(N, 0, 0)); const BASE a_imag = conj * CONST_IMAG(Ap, TPUP(N, 0, 0)); const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (x_real * b_real + x_imag * b_imag) / s; IMAG(X, ix) = (x_imag * b_real - b_imag * x_real) / s; } ix += incX; for (i = 1; i < N; i++) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE Aij_real = CONST_REAL(Ap, TPUP(N, j, i)); const BASE Aij_imag = conj * CONST_IMAG(Ap, TPUP(N, j, i)); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(Ap, TPUP(N, i, i)); const BASE a_imag = conj * CONST_IMAG(Ap, TPUP(N, i, i)); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { /* backsubstitution */ INDEX ix = OFFSET(N, incX) + incX * (N - 1); if (nonunit) { const BASE a_real = CONST_REAL(Ap, TPLO(N, (N - 1), (N - 1))); const BASE a_imag = conj * CONST_IMAG(Ap, TPLO(N, (N - 1), (N - 1))); const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (x_real * b_real + x_imag * b_imag) / s; IMAG(X, ix) = (x_imag * b_real - b_imag * x_real) / s; } ix -= incX; for (i = N - 1; i > 0 && i--;) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); INDEX jx = ix + incX; for (j = i + 1; j < N; j++) { const BASE Aij_real = CONST_REAL(Ap, TPLO(N, j, i)); const BASE Aij_imag = conj * CONST_IMAG(Ap, TPLO(N, j, i)); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(Ap, TPLO(N, i, i)); const BASE a_imag = conj * CONST_IMAG(Ap, TPLO(N, i, i)); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix -= incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_cdf__lognormalinv.c0000664000176700017670000000266511723710247021044 0ustar paulpaul/* cdf/lognormalinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_lognormal_Pinv (const double P, const double zeta, const double sigma) { double x, u; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return 0.0; } u = gsl_cdf_ugaussian_Pinv (P); x = exp (zeta + sigma * u); return x; } double gsl_cdf_lognormal_Qinv (const double Q, const double zeta, const double sigma) { double x, u; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return 0.0; } u = gsl_cdf_ugaussian_Qinv (Q); x = exp (zeta + sigma * u); return x; } sources_5316/external/gsl/gsl_matrix__view_source.c0000664000176700017670000001570311723710247021434 0ustar paulpaul/* matrix/view_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ QUALIFIED_VIEW (_gsl_matrix,view) FUNCTION (gsl_matrix, view_array) (QUALIFIER ATOMIC * array, const size_t n1, const size_t n2) { QUALIFIED_VIEW (_gsl_matrix,view) view = NULL_MATRIX_VIEW; if (n1 == 0) { GSL_ERROR_VAL ("matrix dimension n1 must be positive integer", GSL_EINVAL, view); } else if (n2 == 0) { GSL_ERROR_VAL ("matrix dimension n2 must be positive integer", GSL_EINVAL, view); } { TYPE(gsl_matrix) m = NULL_MATRIX; m.data = (ATOMIC *)array; m.size1 = n1; m.size2 = n2; m.tda = n2; m.block = 0; m.owner = 0; view.matrix = m; return view; } } QUALIFIED_VIEW (_gsl_matrix,view) FUNCTION(gsl_matrix, view_array_with_tda) (QUALIFIER ATOMIC * base, const size_t n1, const size_t n2, const size_t tda) { QUALIFIED_VIEW (_gsl_matrix,view) view = NULL_MATRIX_VIEW; if (n1 == 0) { GSL_ERROR_VAL ("matrix dimension n1 must be positive integer", GSL_EINVAL, view); } else if (n2 == 0) { GSL_ERROR_VAL ("matrix dimension n2 must be positive integer", GSL_EINVAL, view); } else if (n2 > tda) { GSL_ERROR_VAL ("matrix dimension n2 must not exceed tda", GSL_EINVAL, view); } { TYPE(gsl_matrix) m = NULL_MATRIX; m.data = (ATOMIC *)base; m.size1 = n1; m.size2 = n2; m.tda = tda; m.block = 0; m.owner = 0; view.matrix = m; return view; } } QUALIFIED_VIEW (_gsl_matrix,view) FUNCTION(gsl_matrix, view_vector) (QUALIFIED_TYPE(gsl_vector) * v, const size_t n1, const size_t n2) { QUALIFIED_VIEW (_gsl_matrix,view) view = NULL_MATRIX_VIEW; if (n1 == 0) { GSL_ERROR_VAL ("matrix dimension n1 must be positive integer", GSL_EINVAL, view); } else if (n2 == 0) { GSL_ERROR_VAL ("matrix dimension n2 must be positive integer", GSL_EINVAL, view); } else if (v->stride != 1) { GSL_ERROR_VAL ("vector must have unit stride", GSL_EINVAL, view); } else if (n1 * n2 > v->size) { GSL_ERROR_VAL ("matrix size exceeds size of original", GSL_EINVAL, view); } { TYPE(gsl_matrix) m = NULL_MATRIX; m.data = v->data; m.size1 = n1; m.size2 = n2; m.tda = n2; m.block = v->block; m.owner = 0; view.matrix = m; return view; } } QUALIFIED_VIEW (_gsl_matrix,view) FUNCTION(gsl_matrix, view_vector_with_tda) (QUALIFIED_TYPE(gsl_vector) * v, const size_t n1, const size_t n2, const size_t tda) { QUALIFIED_VIEW (_gsl_matrix,view) view = NULL_MATRIX_VIEW; if (n1 == 0) { GSL_ERROR_VAL ("matrix dimension n1 must be positive integer", GSL_EINVAL, view); } else if (n2 == 0) { GSL_ERROR_VAL ("matrix dimension n2 must be positive integer", GSL_EINVAL, view); } else if (v->stride != 1) { GSL_ERROR_VAL ("vector must have unit stride", GSL_EINVAL, view); } else if (n2 > tda) { GSL_ERROR_VAL ("matrix dimension n2 must not exceed tda", GSL_EINVAL, view); } else if (n1 * tda > v->size) { GSL_ERROR_VAL ("matrix size exceeds size of original", GSL_EINVAL, view); } { TYPE(gsl_matrix) m = NULL_MATRIX; m.data = v->data; m.size1 = n1; m.size2 = n2; m.tda = tda; m.block = v->block; m.owner = 0; view.matrix = m; return view; } } #ifdef JUNK int FUNCTION (gsl_matrix, view_from_matrix) (TYPE(gsl_matrix) * m, TYPE(gsl_matrix) * mm, const size_t k1, const size_t k2, const size_t n1, const size_t n2) { if (n1 == 0) { GSL_ERROR_VAL ("matrix dimension n1 must be positive integer", GSL_EINVAL, 0); } else if (n2 == 0) { GSL_ERROR_VAL ("matrix dimension n2 must be positive integer", GSL_EINVAL, 0); } else if (k1 + n1 > mm->size1) { GSL_ERROR_VAL ("submatrix dimension 1 exceeds size of original", GSL_EINVAL, 0); } else if (k2 + n2 > mm->size2) { GSL_ERROR_VAL ("submatrix dimension 2 exceeds size of original", GSL_EINVAL, 0); } m->data = mm->data + k1 * mm->tda + k2 ; m->size1 = n1; m->size2 = n2; m->tda = mm->tda; m->block = mm->block; m->owner = 0; return GSL_SUCCESS; } int FUNCTION (gsl_vector, view_row_from_matrix) (TYPE(gsl_vector) * v, TYPE(gsl_matrix) * m, const size_t i) { const size_t column_length = m->size1; if (i >= column_length) { GSL_ERROR ("row index is out of range", GSL_EINVAL); } if (v->block != 0) { GSL_ERROR ("vector already has memory allocated to it", GSL_ENOMEM); } v->data = m->data + MULTIPLICITY * i * m->tda ; v->size = m->size2; v->stride = 1; return GSL_SUCCESS; } int FUNCTION (gsl_vector, view_col_from_matrix) (TYPE(gsl_vector) * v, TYPE(gsl_matrix) * m, const size_t j) { const size_t row_length = m->size2; if (j >= row_length) { GSL_ERROR_VAL ("column index is out of range", GSL_EINVAL, 0); } if (v->block != 0) { GSL_ERROR ("vector already has memory allocated to it", GSL_ENOMEM); } v->data = m->data + MULTIPLICITY * j ; v->size = m->size1; v->stride = m->tda; return GSL_SUCCESS; } #endif /* JUNK */ sources_5316/external/gsl/gsl_cdf__rayleighinv.c0000664000176700017670000000253111723710247020646 0ustar paulpaul/* cdf/rayleighinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_rayleigh_Pinv (const double P, const double sigma) { double x; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return 0.0; } x = sigma * M_SQRT2 * sqrt (-log1p (-P)); return x; } double gsl_cdf_rayleigh_Qinv (const double Q, const double sigma) { double x; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return 0.0; } x = sigma * M_SQRT2 * sqrt (-log (Q)); return x; } sources_5316/external/gsl/gsl_types.h0000664000176700017670000000217511705263724016532 0ustar paulpaul/* gsl_types.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_TYPES_H__ #define __GSL_TYPES_H__ #ifndef GSL_VAR #ifdef WIN32 # ifdef GSL_DLL # ifdef DLL_EXPORT # define GSL_VAR extern __declspec(dllexport) # else # define GSL_VAR extern __declspec(dllimport) # endif # else # define GSL_VAR extern # endif #else # define GSL_VAR extern #endif #endif #endif /* __GSL_TYPES_H__ */ sources_5316/external/gsl/gsl_fft__hc_pass_2.c0000664000176700017670000000637111723710247020217 0ustar paulpaul/* fft/hc_pass_2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_halfcomplex,pass_2) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]) { size_t i, j, k, k1, jump; size_t factor, q, m, product_1; i = 0; j = 0; factor = 2; m = n / factor; q = n / product; product_1 = product / factor; jump = (factor - 1) * q; for (k1 = 0; k1 < product_1; k1++) { const ATOMIC r0 = VECTOR(in,istride,2 * k1 * q); const ATOMIC r1 = VECTOR(in,istride,2 * k1 * q + 2 * q - 1); const ATOMIC s0 = r0 + r1; const ATOMIC s1 = r0 - r1; VECTOR(out,ostride,q * k1) = s0; VECTOR(out,ostride,q * k1 + m) = s1; } if (q == 1) return; for (k = 1; k < (q + 1) / 2; k++) { const ATOMIC w_real = GSL_REAL(twiddle[k - 1]); const ATOMIC w_imag = GSL_IMAG(twiddle[k - 1]); for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 2 * k1 * q + 2 * k - 1; const size_t from1 = 2 * k1 * q - 2 * k + 2 * q - 1; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z1_imag = VECTOR(in,istride,from1 + 1); /* compute x = W(2) z */ /* x0 = z0 + z1 */ const ATOMIC x0_real = z0_real + z1_real; const ATOMIC x0_imag = z0_imag - z1_imag; /* x1 = z0 - z1 */ const ATOMIC x1_real = z0_real - z1_real; const ATOMIC x1_imag = z0_imag + z1_imag; const size_t to0 = k1 * q + 2 * k - 1; const size_t to1 = to0 + m; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to0 + 1) = x0_imag; VECTOR(out,ostride,to1) = w_real * x1_real - w_imag * x1_imag; VECTOR(out,ostride,to1 + 1) = w_imag * x1_real + w_real * x1_imag; } } if (q % 2 == 1) return; for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 2 * k1 * q + q - 1; const size_t to0 = k1 * q + q - 1; const size_t to1 = to0 + m; VECTOR(out,ostride,to0) = 2 * VECTOR(in,istride,from0); VECTOR(out,ostride,to1) = -2 * VECTOR(in,istride,from0 + 1); } return; } sources_5316/external/gsl/gsl_cblas__source_copy_c.h0000664000176700017670000000201011705263724021511 0ustar paulpaul/* blas/source_copy_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { REAL(Y, iy) = CONST_REAL(X, ix); IMAG(Y, iy) = CONST_IMAG(X, ix); ix += incX; iy += incY; } } sources_5316/external/gsl/gsl_vector__view.c0000664000176700017670000000745711723710247020061 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_vector.h" #include "gsl_vector__view.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_CHAR #define USE_QUALIFIER #define QUALIFIER const #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__view_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_multimin__steepest_descent.c0000664000176700017670000001003611723710247022767 0ustar paulpaul/* multimin/steepest_descent.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Fabrice Rossi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* steepest_descent.c -- the steepest descent algorithm */ /* Modified by Brian Gough to use single iteration structure */ #include "gsl__config.h" #include "gsl_multimin.h" #include "gsl_blas_types.h" #include "gsl_blas.h" typedef struct { double step; double max_step; double tol; gsl_vector *x1; gsl_vector *g1; } steepest_descent_state_t; static int steepest_descent_alloc (void *vstate, size_t n) { steepest_descent_state_t *state = (steepest_descent_state_t *) vstate; state->x1 = gsl_vector_alloc (n); if (state->x1 == NULL) { GSL_ERROR ("failed to allocate space for x1", GSL_ENOMEM); } state->g1 = gsl_vector_alloc (n); if (state->g1 == NULL) { gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for g1", GSL_ENOMEM); } return GSL_SUCCESS; } static int steepest_descent_set (void *vstate, gsl_multimin_function_fdf * fdf, const gsl_vector * x, double *f, gsl_vector * gradient, double step_size, double tol) { steepest_descent_state_t *state = (steepest_descent_state_t *) vstate; GSL_MULTIMIN_FN_EVAL_F_DF (fdf, x, f, gradient); state->step = step_size; state->max_step = step_size; state->tol = tol; return GSL_SUCCESS; } static void steepest_descent_free (void *vstate) { steepest_descent_state_t *state = (steepest_descent_state_t *) vstate; gsl_vector_free (state->x1); gsl_vector_free (state->g1); } static int steepest_descent_restart (void *vstate) { steepest_descent_state_t *state = (steepest_descent_state_t *) vstate; state->step = state->max_step; return GSL_SUCCESS; } static int steepest_descent_iterate (void *vstate, gsl_multimin_function_fdf * fdf, gsl_vector * x, double *f, gsl_vector * gradient, gsl_vector * dx) { steepest_descent_state_t *state = (steepest_descent_state_t *) vstate; gsl_vector *x1 = state->x1; gsl_vector *g1 = state->g1; double f0 = *f; double f1; double step = state->step, tol = state->tol; int failed = 0; /* compute new trial point at x1= x - step * dir, where dir is the normalized gradient */ double gnorm = gsl_blas_dnrm2 (gradient); if (gnorm == 0.0) { gsl_vector_set_zero (dx); return GSL_ENOPROG; } trial: gsl_vector_set_zero (dx); gsl_blas_daxpy (-step / gnorm, gradient, dx); gsl_vector_memcpy (x1, x); gsl_blas_daxpy (1.0, dx, x1); /* evaluate function and gradient at new point x1 */ GSL_MULTIMIN_FN_EVAL_F_DF (fdf, x1, &f1, g1); if (f1 > f0) { /* downhill step failed, reduce step-size and try again */ failed = 1; step *= tol; goto trial; } if (failed) step *= tol; else step *= 2.0; state->step = step; gsl_vector_memcpy (x, x1); gsl_vector_memcpy (gradient, g1); *f = f1; return GSL_SUCCESS; } static const gsl_multimin_fdfminimizer_type steepest_descent_type = { "steepest_descent", /* name */ sizeof (steepest_descent_state_t), &steepest_descent_alloc, &steepest_descent_set, &steepest_descent_iterate, &steepest_descent_restart, &steepest_descent_free }; const gsl_multimin_fdfminimizer_type * gsl_multimin_fdfminimizer_steepest_descent = &steepest_descent_type; sources_5316/external/gsl/gsl_specfunc__bessel.h0000664000176700017670000000604011705263724020663 0ustar paulpaul/* specfunc/bessel.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef _BESSEL_H_ #define _BESSEL_H_ #include "gsl_sf_result.h" /* Taylor expansion for J_nu(x) or I_nu(x) * sign = -1 ==> Jnu * sign = +1 ==> Inu */ int gsl_sf_bessel_IJ_taylor_e(const double nu, const double x, const int sign, const int kmax, const double threshold, gsl_sf_result * result ); int gsl_sf_bessel_Jnu_asympx_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Ynu_asympx_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Inu_scaled_asympx_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Knu_scaled_asympx_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Inu_scaled_asymp_unif_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Knu_scaled_asymp_unif_e(const double nu, const double x, gsl_sf_result * result); /* ratio = J_{nu+1}(x) / J_nu(x) * sgn = sgn(J_nu(x)) */ int gsl_sf_bessel_J_CF1(const double nu, const double x, double * ratio, double * sgn); /* ratio = I_{nu+1}(x) / I_nu(x) */ int gsl_sf_bessel_I_CF1_ser(const double nu, const double x, double * ratio); /* Evaluate the Steed method continued fraction CF2 for * * (J' + i Y')/(J + i Y) := P + i Q */ int gsl_sf_bessel_JY_steed_CF2(const double nu, const double x, double * P, double * Q); int gsl_sf_bessel_JY_mu_restricted(const double mu, const double x, gsl_sf_result * Jmu, gsl_sf_result * Jmup1, gsl_sf_result * Ymu, gsl_sf_result * Ymup1); int gsl_sf_bessel_K_scaled_steed_temme_CF2(const double nu, const double x, double * K_nu, double * K_nup1, double * Kp_nu); /* These are of use in calculating the oscillating * Bessel functions. * cos(y - pi/4 + eps) * sin(y - pi/4 + eps) */ int gsl_sf_bessel_cos_pi4_e(double y, double eps, gsl_sf_result * result); int gsl_sf_bessel_sin_pi4_e(double y, double eps, gsl_sf_result * result); #endif /* !_BESSEL_H_ */ sources_5316/external/gsl/gsl_cblas__ssyr.c0000664000176700017670000000051611723710247017656 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ssyr (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *X, const int incX, float *A, const int lda) { #define BASE float #include "gsl_cblas__source_syr.h" #undef BASE } sources_5316/external/gsl/gsl_sf_trig.h0000664000176700017670000000756111705263724017027 0ustar paulpaul/* specfunc/gsl_sf_trig.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_TRIG_H__ #define __GSL_SF_TRIG_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Sin(x) with GSL semantics. This is actually important * because we want to control the error estimate, and trying * to guess the error for the standard library implementation * every time it is used would be a little goofy. */ int gsl_sf_sin_e(double x, gsl_sf_result * result); double gsl_sf_sin(const double x); /* Cos(x) with GSL semantics. */ int gsl_sf_cos_e(double x, gsl_sf_result * result); double gsl_sf_cos(const double x); /* Hypot(x,y) with GSL semantics. */ int gsl_sf_hypot_e(const double x, const double y, gsl_sf_result * result); double gsl_sf_hypot(const double x, const double y); /* Sin(z) for complex z * * exceptions: GSL_EOVRFLW */ int gsl_sf_complex_sin_e(const double zr, const double zi, gsl_sf_result * szr, gsl_sf_result * szi); /* Cos(z) for complex z * * exceptions: GSL_EOVRFLW */ int gsl_sf_complex_cos_e(const double zr, const double zi, gsl_sf_result * czr, gsl_sf_result * czi); /* Log(Sin(z)) for complex z * * exceptions: GSL_EDOM, GSL_ELOSS */ int gsl_sf_complex_logsin_e(const double zr, const double zi, gsl_sf_result * lszr, gsl_sf_result * lszi); /* Sinc(x) = sin(pi x) / (pi x) * * exceptions: none */ int gsl_sf_sinc_e(double x, gsl_sf_result * result); double gsl_sf_sinc(const double x); /* Log(Sinh(x)), x > 0 * * exceptions: GSL_EDOM */ int gsl_sf_lnsinh_e(const double x, gsl_sf_result * result); double gsl_sf_lnsinh(const double x); /* Log(Cosh(x)) * * exceptions: none */ int gsl_sf_lncosh_e(const double x, gsl_sf_result * result); double gsl_sf_lncosh(const double x); /* Convert polar to rectlinear coordinates. * * exceptions: GSL_ELOSS */ int gsl_sf_polar_to_rect(const double r, const double theta, gsl_sf_result * x, gsl_sf_result * y); /* Convert rectilinear to polar coordinates. * return argument in range [-pi, pi] * * exceptions: GSL_EDOM */ int gsl_sf_rect_to_polar(const double x, const double y, gsl_sf_result * r, gsl_sf_result * theta); /* Sin(x) for quantity with an associated error. */ int gsl_sf_sin_err_e(const double x, const double dx, gsl_sf_result * result); /* Cos(x) for quantity with an associated error. */ int gsl_sf_cos_err_e(const double x, const double dx, gsl_sf_result * result); /* Force an angle to lie in the range (-pi,pi]. * * exceptions: GSL_ELOSS */ int gsl_sf_angle_restrict_symm_e(double * theta); double gsl_sf_angle_restrict_symm(const double theta); /* Force an angle to lie in the range [0, 2pi) * * exceptions: GSL_ELOSS */ int gsl_sf_angle_restrict_pos_e(double * theta); double gsl_sf_angle_restrict_pos(const double theta); int gsl_sf_angle_restrict_symm_err_e(const double theta, gsl_sf_result * result); int gsl_sf_angle_restrict_pos_err_e(const double theta, gsl_sf_result * result); __END_DECLS #endif /* __GSL_SF_TRIG_H__ */ sources_5316/external/gsl/gsl_block_uint.h0000664000176700017670000000443611705263724017521 0ustar paulpaul/* block/gsl_block_uint.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_UINT_H__ #define __GSL_BLOCK_UINT_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_uint_struct { size_t size; unsigned int *data; }; typedef struct gsl_block_uint_struct gsl_block_uint; gsl_block_uint *gsl_block_uint_alloc (const size_t n); gsl_block_uint *gsl_block_uint_calloc (const size_t n); void gsl_block_uint_free (gsl_block_uint * b); int gsl_block_uint_fread (FILE * stream, gsl_block_uint * b); int gsl_block_uint_fwrite (FILE * stream, const gsl_block_uint * b); int gsl_block_uint_fscanf (FILE * stream, gsl_block_uint * b); int gsl_block_uint_fprintf (FILE * stream, const gsl_block_uint * b, const char *format); int gsl_block_uint_raw_fread (FILE * stream, unsigned int * b, const size_t n, const size_t stride); int gsl_block_uint_raw_fwrite (FILE * stream, const unsigned int * b, const size_t n, const size_t stride); int gsl_block_uint_raw_fscanf (FILE * stream, unsigned int * b, const size_t n, const size_t stride); int gsl_block_uint_raw_fprintf (FILE * stream, const unsigned int * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_uint_size (const gsl_block_uint * b); unsigned int * gsl_block_uint_data (const gsl_block_uint * b); __END_DECLS #endif /* __GSL_BLOCK_UINT_H__ */ sources_5316/external/gsl/gsl_fft__c_pass_2.c0000664000176700017670000000577611723710247020057 0ustar paulpaul/* fft/c_pass_2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int FUNCTION(fft_complex,pass_2) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]) { size_t i = 0, j = 0; size_t k, k1; const size_t factor = 2; const size_t m = n / factor; const size_t q = n / product; const size_t product_1 = product / factor; const size_t jump = (factor - 1) * product_1; for (k = 0; k < q; k++) { ATOMIC w_real, w_imag; if (k == 0) { w_real = 1.0; w_imag = 0.0; } else { if (sign == gsl_fft_forward) { /* forward tranform */ w_real = GSL_REAL(twiddle[k - 1]); w_imag = GSL_IMAG(twiddle[k - 1]); } else { /* backward tranform: w -> conjugate(w) */ w_real = GSL_REAL(twiddle[k - 1]); w_imag = -GSL_IMAG(twiddle[k - 1]); } } for (k1 = 0; k1 < product_1; k1++) { const ATOMIC z0_real = REAL(in,istride,i); const ATOMIC z0_imag = IMAG(in,istride,i); const ATOMIC z1_real = REAL(in,istride,i+m); const ATOMIC z1_imag = IMAG(in,istride,i+m); /* compute x = W(2) z */ /* x0 = z0 + z1 */ const ATOMIC x0_real = z0_real + z1_real; const ATOMIC x0_imag = z0_imag + z1_imag; /* x1 = z0 - z1 */ const ATOMIC x1_real = z0_real - z1_real; const ATOMIC x1_imag = z0_imag - z1_imag; /* apply twiddle factors */ /* out0 = 1 * x0 */ REAL(out,ostride,j) = x0_real; IMAG(out,ostride,j) = x0_imag; /* out1 = w * x1 */ REAL(out,ostride,j+product_1) = w_real * x1_real - w_imag * x1_imag; IMAG(out,ostride,j+product_1) = w_real * x1_imag + w_imag * x1_real; i++; j++; } j += jump; } return 0; } sources_5316/external/gsl/gsl_sort__sortvec.c0000664000176700017670000000431511723710247020247 0ustar paulpaul/* * Implement Heap sort -- direct and indirect sorting * Based on descriptions in Sedgewick "Algorithms in C" * * Copyright (C) 1999 Thomas Walter * * 18 February 2000: Modified for GSL by Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_vector.h" #include "gsl_sort.h" #include "gsl_sort_vector.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_sort__sortvec_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_specfunc__legendre_poly.c0000664000176700017670000005117511723710247022237 0ustar paulpaul/* specfunc/legendre_poly.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_log.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_legendre.h" #include "gsl_specfunc__error.h" /* Calculate P_m^m(x) from the analytic result: * P_m^m(x) = (-1)^m (2m-1)!! (1-x^2)^(m/2) , m > 0 * = 1 , m = 0 */ static double legendre_Pmm(int m, double x) { if(m == 0) { return 1.0; } else { double p_mm = 1.0; double root_factor = sqrt(1.0-x)*sqrt(1.0+x); double fact_coeff = 1.0; int i; for(i=1; i<=m; i++) { p_mm *= -fact_coeff * root_factor; fact_coeff += 2.0; } return p_mm; } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_legendre_P1_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { result->val = x; result->err = 0.0; return GSL_SUCCESS; } } int gsl_sf_legendre_P2_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { result->val = 0.5*(3.0*x*x - 1.0); result->err = GSL_DBL_EPSILON * (fabs(3.0*x*x) + 1.0); return GSL_SUCCESS; } } int gsl_sf_legendre_P3_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { result->val = 0.5*x*(5.0*x*x - 3.0); result->err = GSL_DBL_EPSILON * (fabs(result->val) + 0.5 * fabs(x) * (fabs(5.0*x*x) + 3.0)); return GSL_SUCCESS; } } int gsl_sf_legendre_Pl_e(const int l, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(l < 0 || x < -1.0 || x > 1.0) { DOMAIN_ERROR(result); } else if(l == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(l == 1) { result->val = x; result->err = 0.0; return GSL_SUCCESS; } else if(l == 2) { result->val = 0.5 * (3.0*x*x - 1.0); result->err = GSL_DBL_EPSILON * (fabs(3.0*x*x) + 1.0); /*result->err = 3.0 * GSL_DBL_EPSILON * fabs(result->val); removed this old bogus estimate [GJ] */ return GSL_SUCCESS; } else if(x == 1.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(x == -1.0) { result->val = ( GSL_IS_ODD(l) ? -1.0 : 1.0 ); result->err = 0.0; return GSL_SUCCESS; } else if(l < 100000) { /* upward recurrence: l P_l = (2l-1) z P_{l-1} - (l-1) P_{l-2} */ double p_ellm2 = 1.0; /* P_0(x) */ double p_ellm1 = x; /* P_1(x) */ double p_ell = p_ellm1; double e_ellm2 = GSL_DBL_EPSILON; double e_ellm1 = fabs(x)*GSL_DBL_EPSILON; double e_ell = e_ellm1; int ell; for(ell=2; ell <= l; ell++){ p_ell = (x*(2*ell-1)*p_ellm1 - (ell-1)*p_ellm2) / ell; p_ellm2 = p_ellm1; p_ellm1 = p_ell; e_ell = 0.5*(fabs(x)*(2*ell-1.0) * e_ellm1 + (ell-1.0)*e_ellm2)/ell; e_ellm2 = e_ellm1; e_ellm1 = e_ell; } result->val = p_ell; result->err = e_ell + l*fabs(p_ell)*GSL_DBL_EPSILON; return GSL_SUCCESS; } else { /* Asymptotic expansion. * [Olver, p. 473] */ double u = l + 0.5; double th = acos(x); gsl_sf_result J0; gsl_sf_result Jm1; int stat_J0 = gsl_sf_bessel_J0_e(u*th, &J0); int stat_Jm1 = gsl_sf_bessel_Jn_e(-1, u*th, &Jm1); double pre; double B00; double c1; /* B00 = 1/8 (1 - th cot(th) / th^2 * pre = sqrt(th/sin(th)) */ if(th < GSL_ROOT4_DBL_EPSILON) { B00 = (1.0 + th*th/15.0)/24.0; pre = 1.0 + th*th/12.0; } else { double sin_th = sqrt(1.0 - x*x); double cot_th = x / sin_th; B00 = 1.0/8.0 * (1.0 - th * cot_th) / (th*th); pre = sqrt(th/sin_th); } c1 = th/u * B00; result->val = pre * (J0.val + c1 * Jm1.val); result->err = pre * (J0.err + fabs(c1) * Jm1.err); result->err += GSL_SQRT_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_J0, stat_Jm1); } } int gsl_sf_legendre_Pl_array(const int lmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(lmax < 0 || x < -1.0 || x > 1.0) { GSL_ERROR ("domain error", GSL_EDOM); } else if(lmax == 0) { result_array[0] = 1.0; return GSL_SUCCESS; } else if(lmax == 1) { result_array[0] = 1.0; result_array[1] = x; return GSL_SUCCESS; } else { /* upward recurrence: l P_l = (2l-1) z P_{l-1} - (l-1) P_{l-2} */ double p_ellm2 = 1.0; /* P_0(x) */ double p_ellm1 = x; /* P_1(x) */ double p_ell = p_ellm1; int ell; result_array[0] = 1.0; result_array[1] = x; for(ell=2; ell <= lmax; ell++){ p_ell = (x*(2*ell-1)*p_ellm1 - (ell-1)*p_ellm2) / ell; p_ellm2 = p_ellm1; p_ellm1 = p_ell; result_array[ell] = p_ell; } return GSL_SUCCESS; } } int gsl_sf_legendre_Pl_deriv_array(const int lmax, const double x, double * result_array, double * result_deriv_array) { int stat_array = gsl_sf_legendre_Pl_array(lmax, x, result_array); if(lmax >= 0) result_deriv_array[0] = 0.0; if(lmax >= 1) result_deriv_array[1] = 1.0; if(stat_array == GSL_SUCCESS) { int ell; if(fabs(x - 1.0)*(lmax+1.0)*(lmax+1.0) < GSL_SQRT_DBL_EPSILON) { /* x is near 1 */ for(ell = 2; ell <= lmax; ell++) { const double pre = 0.5 * ell * (ell+1.0); result_deriv_array[ell] = pre * (1.0 - 0.25 * (1.0-x) * (ell+2.0)*(ell-1.0)); } } else if(fabs(x + 1.0)*(lmax+1.0)*(lmax+1.0) < GSL_SQRT_DBL_EPSILON) { /* x is near -1 */ for(ell = 2; ell <= lmax; ell++) { const double sgn = ( GSL_IS_ODD(ell) ? 1.0 : -1.0 ); /* derivative is odd in x for even ell */ const double pre = sgn * 0.5 * ell * (ell+1.0); result_deriv_array[ell] = pre * (1.0 - 0.25 * (1.0+x) * (ell+2.0)*(ell-1.0)); } } else { const double diff_a = 1.0 + x; const double diff_b = 1.0 - x; for(ell = 2; ell <= lmax; ell++) { result_deriv_array[ell] = - ell * (x * result_array[ell] - result_array[ell-1]) / (diff_a * diff_b); } } return GSL_SUCCESS; } else { return stat_array; } } int gsl_sf_legendre_Plm_e(const int l, const int m, const double x, gsl_sf_result * result) { /* If l is large and m is large, then we have to worry * about overflow. Calculate an approximate exponent which * measures the normalization of this thing. */ const double dif = l-m; const double sum = l+m; const double t_d = ( dif == 0.0 ? 0.0 : 0.5 * dif * (log(dif)-1.0) ); const double t_s = ( dif == 0.0 ? 0.0 : 0.5 * sum * (log(sum)-1.0) ); const double exp_check = 0.5 * log(2.0*l+1.0) + t_d - t_s; /* CHECK_POINTER(result) */ if(m < 0 || l < m || x < -1.0 || x > 1.0) { DOMAIN_ERROR(result); } else if(exp_check < GSL_LOG_DBL_MIN + 10.0){ /* Bail out. */ OVERFLOW_ERROR(result); } else { /* Account for the error due to the * representation of 1-x. */ const double err_amp = 1.0 / (GSL_DBL_EPSILON + fabs(1.0-fabs(x))); /* P_m^m(x) and P_{m+1}^m(x) */ double p_mm = legendre_Pmm(m, x); double p_mmp1 = x * (2*m + 1) * p_mm; if(l == m){ result->val = p_mm; result->err = err_amp * 2.0 * GSL_DBL_EPSILON * fabs(p_mm); return GSL_SUCCESS; } else if(l == m + 1) { result->val = p_mmp1; result->err = err_amp * 2.0 * GSL_DBL_EPSILON * fabs(p_mmp1); return GSL_SUCCESS; } else{ /* upward recurrence: (l-m) P(l,m) = (2l-1) z P(l-1,m) - (l+m-1) P(l-2,m) * start at P(m,m), P(m+1,m) */ double p_ellm2 = p_mm; double p_ellm1 = p_mmp1; double p_ell = 0.0; int ell; for(ell=m+2; ell <= l; ell++){ p_ell = (x*(2*ell-1)*p_ellm1 - (ell+m-1)*p_ellm2) / (ell-m); p_ellm2 = p_ellm1; p_ellm1 = p_ell; } result->val = p_ell; result->err = err_amp * (0.5*(l-m) + 1.0) * GSL_DBL_EPSILON * fabs(p_ell); return GSL_SUCCESS; } } } int gsl_sf_legendre_Plm_array(const int lmax, const int m, const double x, double * result_array) { /* If l is large and m is large, then we have to worry * about overflow. Calculate an approximate exponent which * measures the normalization of this thing. */ const double dif = lmax-m; const double sum = lmax+m; const double t_d = ( dif == 0.0 ? 0.0 : 0.5 * dif * (log(dif)-1.0) ); const double t_s = ( dif == 0.0 ? 0.0 : 0.5 * sum * (log(sum)-1.0) ); const double exp_check = 0.5 * log(2.0*lmax+1.0) + t_d - t_s; /* CHECK_POINTER(result_array) */ if(m < 0 || lmax < m || x < -1.0 || x > 1.0) { GSL_ERROR ("domain error", GSL_EDOM); } else if(m > 0 && (x == 1.0 || x == -1.0)) { int ell; for(ell=m; ell<=lmax; ell++) result_array[ell-m] = 0.0; return GSL_SUCCESS; } else if(exp_check < GSL_LOG_DBL_MIN + 10.0){ /* Bail out. */ GSL_ERROR ("overflow", GSL_EOVRFLW); } else { double p_mm = legendre_Pmm(m, x); double p_mmp1 = x * (2.0*m + 1.0) * p_mm; if(lmax == m){ result_array[0] = p_mm; return GSL_SUCCESS; } else if(lmax == m + 1) { result_array[0] = p_mm; result_array[1] = p_mmp1; return GSL_SUCCESS; } else { double p_ellm2 = p_mm; double p_ellm1 = p_mmp1; double p_ell = 0.0; int ell; result_array[0] = p_mm; result_array[1] = p_mmp1; for(ell=m+2; ell <= lmax; ell++){ p_ell = (x*(2.0*ell-1.0)*p_ellm1 - (ell+m-1)*p_ellm2) / (ell-m); p_ellm2 = p_ellm1; p_ellm1 = p_ell; result_array[ell-m] = p_ell; } return GSL_SUCCESS; } } } int gsl_sf_legendre_Plm_deriv_array( const int lmax, const int m, const double x, double * result_array, double * result_deriv_array) { if(m < 0 || m > lmax) { GSL_ERROR("m < 0 or m > lmax", GSL_EDOM); } else if(m == 0) { /* It is better to do m=0 this way, so we can more easily * trap the divergent case which can occur when m == 1. */ return gsl_sf_legendre_Pl_deriv_array(lmax, x, result_array, result_deriv_array); } else { int stat_array = gsl_sf_legendre_Plm_array(lmax, m, x, result_array); if(stat_array == GSL_SUCCESS) { int ell; if(m == 1 && (1.0 - fabs(x) < GSL_DBL_EPSILON)) { /* This divergence is real and comes from the cusp-like * behaviour for m = 1. For example, P[1,1] = - Sqrt[1-x^2]. */ GSL_ERROR("divergence near |x| = 1.0 since m = 1", GSL_EOVRFLW); } else if(m == 2 && (1.0 - fabs(x) < GSL_DBL_EPSILON)) { /* m = 2 gives a finite nonzero result for |x| near 1 */ if(fabs(x - 1.0) < GSL_DBL_EPSILON) { for(ell = m; ell <= lmax; ell++) result_deriv_array[ell-m] = -0.25 * x * (ell - 1.0)*ell*(ell+1.0)*(ell+2.0); } else if(fabs(x + 1.0) < GSL_DBL_EPSILON) { for(ell = m; ell <= lmax; ell++) { const double sgn = ( GSL_IS_ODD(ell) ? 1.0 : -1.0 ); result_deriv_array[ell-m] = -0.25 * sgn * x * (ell - 1.0)*ell*(ell+1.0)*(ell+2.0); } } return GSL_SUCCESS; } else { /* m > 2 is easier to deal with since the endpoints always vanish */ if(1.0 - fabs(x) < GSL_DBL_EPSILON) { for(ell = m; ell <= lmax; ell++) result_deriv_array[ell-m] = 0.0; return GSL_SUCCESS; } else { const double diff_a = 1.0 + x; const double diff_b = 1.0 - x; result_deriv_array[0] = - m * x / (diff_a * diff_b) * result_array[0]; if(lmax-m >= 1) result_deriv_array[1] = (2.0 * m + 1.0) * (x * result_deriv_array[0] + result_array[0]); for(ell = m+2; ell <= lmax; ell++) { result_deriv_array[ell-m] = - (ell * x * result_array[ell-m] - (ell+m) * result_array[ell-1-m]) / (diff_a * diff_b); } return GSL_SUCCESS; } } } else { return stat_array; } } } int gsl_sf_legendre_sphPlm_e(const int l, int m, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(m < 0 || l < m || x < -1.0 || x > 1.0) { DOMAIN_ERROR(result); } else if(m == 0) { gsl_sf_result P; int stat_P = gsl_sf_legendre_Pl_e(l, x, &P); double pre = sqrt((2.0*l + 1.0)/(4.0*M_PI)); result->val = pre * P.val; result->err = pre * P.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_P; } else if(x == 1.0 || x == -1.0) { /* m > 0 here */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* m > 0 and |x| < 1 here */ /* Starting value for recursion. * Y_m^m(x) = sqrt( (2m+1)/(4pi m) gamma(m+1/2)/gamma(m) ) (-1)^m (1-x^2)^(m/2) / pi^(1/4) */ gsl_sf_result lncirc; gsl_sf_result lnpoch; double lnpre_val; double lnpre_err; gsl_sf_result ex_pre; double sr; const double sgn = ( GSL_IS_ODD(m) ? -1.0 : 1.0); const double y_mmp1_factor = x * sqrt(2.0*m + 3.0); double y_mm, y_mm_err; double y_mmp1, y_mmp1_err; gsl_sf_log_1plusx_e(-x*x, &lncirc); gsl_sf_lnpoch_e(m, 0.5, &lnpoch); /* Gamma(m+1/2)/Gamma(m) */ lnpre_val = -0.25*M_LNPI + 0.5 * (lnpoch.val + m*lncirc.val); lnpre_err = 0.25*M_LNPI*GSL_DBL_EPSILON + 0.5 * (lnpoch.err + fabs(m)*lncirc.err); /* Compute exp(ln_pre) with error term, avoiding call to gsl_sf_exp_err BJG */ ex_pre.val = exp(lnpre_val); ex_pre.err = 2.0*(sinh(lnpre_err) + GSL_DBL_EPSILON)*ex_pre.val; sr = sqrt((2.0+1.0/m)/(4.0*M_PI)); y_mm = sgn * sr * ex_pre.val; y_mm_err = 2.0 * GSL_DBL_EPSILON * fabs(y_mm) + sr * ex_pre.err; y_mm_err *= 1.0 + 1.0/(GSL_DBL_EPSILON + fabs(1.0-x)); y_mmp1 = y_mmp1_factor * y_mm; y_mmp1_err=fabs(y_mmp1_factor) * y_mm_err; if(l == m){ result->val = y_mm; result->err = y_mm_err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(y_mm); return GSL_SUCCESS; } else if(l == m + 1) { result->val = y_mmp1; result->err = y_mmp1_err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(y_mmp1); return GSL_SUCCESS; } else{ double y_ell = 0.0; double y_ell_err; int ell; /* Compute Y_l^m, l > m+1, upward recursion on l. */ for(ell=m+2; ell <= l; ell++){ const double rat1 = (double)(ell-m)/(double)(ell+m); const double rat2 = (ell-m-1.0)/(ell+m-1.0); const double factor1 = sqrt(rat1*(2.0*ell+1.0)*(2.0*ell-1.0)); const double factor2 = sqrt(rat1*rat2*(2.0*ell+1.0)/(2.0*ell-3.0)); y_ell = (x*y_mmp1*factor1 - (ell+m-1.0)*y_mm*factor2) / (ell-m); y_mm = y_mmp1; y_mmp1 = y_ell; y_ell_err = 0.5*(fabs(x*factor1)*y_mmp1_err + fabs((ell+m-1.0)*factor2)*y_mm_err) / fabs(ell-m); y_mm_err = y_mmp1_err; y_mmp1_err = y_ell_err; } result->val = y_ell; result->err = y_ell_err + (0.5*(l-m) + 1.0) * GSL_DBL_EPSILON * fabs(y_ell); return GSL_SUCCESS; } } } int gsl_sf_legendre_sphPlm_array(const int lmax, int m, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(m < 0 || lmax < m || x < -1.0 || x > 1.0) { GSL_ERROR ("error", GSL_EDOM); } else if(m > 0 && (x == 1.0 || x == -1.0)) { int ell; for(ell=m; ell<=lmax; ell++) result_array[ell-m] = 0.0; return GSL_SUCCESS; } else { double y_mm; double y_mmp1; if(m == 0) { y_mm = 0.5/M_SQRTPI; /* Y00 = 1/sqrt(4pi) */ y_mmp1 = x * M_SQRT3 * y_mm; } else { /* |x| < 1 here */ gsl_sf_result lncirc; gsl_sf_result lnpoch; double lnpre; const double sgn = ( GSL_IS_ODD(m) ? -1.0 : 1.0); gsl_sf_log_1plusx_e(-x*x, &lncirc); gsl_sf_lnpoch_e(m, 0.5, &lnpoch); /* Gamma(m+1/2)/Gamma(m) */ lnpre = -0.25*M_LNPI + 0.5 * (lnpoch.val + m*lncirc.val); y_mm = sqrt((2.0+1.0/m)/(4.0*M_PI)) * sgn * exp(lnpre); y_mmp1 = x * sqrt(2.0*m + 3.0) * y_mm; } if(lmax == m){ result_array[0] = y_mm; return GSL_SUCCESS; } else if(lmax == m + 1) { result_array[0] = y_mm; result_array[1] = y_mmp1; return GSL_SUCCESS; } else{ double y_ell; int ell; result_array[0] = y_mm; result_array[1] = y_mmp1; /* Compute Y_l^m, l > m+1, upward recursion on l. */ for(ell=m+2; ell <= lmax; ell++){ const double rat1 = (double)(ell-m)/(double)(ell+m); const double rat2 = (ell-m-1.0)/(ell+m-1.0); const double factor1 = sqrt(rat1*(2*ell+1)*(2*ell-1)); const double factor2 = sqrt(rat1*rat2*(2*ell+1)/(2*ell-3)); y_ell = (x*y_mmp1*factor1 - (ell+m-1)*y_mm*factor2) / (ell-m); y_mm = y_mmp1; y_mmp1 = y_ell; result_array[ell-m] = y_ell; } } return GSL_SUCCESS; } } int gsl_sf_legendre_sphPlm_deriv_array( const int lmax, const int m, const double x, double * result_array, double * result_deriv_array) { if(m < 0 || lmax < m || x < -1.0 || x > 1.0) { GSL_ERROR ("domain", GSL_EDOM); } else if(m == 0) { /* m = 0 is easy to trap */ const int stat_array = gsl_sf_legendre_Pl_deriv_array(lmax, x, result_array, result_deriv_array); int ell; for(ell = 0; ell <= lmax; ell++) { const double prefactor = sqrt((2.0 * ell + 1.0)/(4.0*M_PI)); result_array[ell] *= prefactor; result_deriv_array[ell] *= prefactor; } return stat_array; } else if(m == 1) { /* Trapping m = 1 is necessary because of the possible divergence. * Recall that this divergence is handled properly in ..._Plm_deriv_array(), * and the scaling factor is not large for small m, so we just scale. */ const int stat_array = gsl_sf_legendre_Plm_deriv_array(lmax, m, x, result_array, result_deriv_array); int ell; for(ell = 1; ell <= lmax; ell++) { const double prefactor = sqrt((2.0 * ell + 1.0)/(ell + 1.0) / (4.0*M_PI*ell)); result_array[ell-1] *= prefactor; result_deriv_array[ell-1] *= prefactor; } return stat_array; } else { /* as for the derivative of P_lm, everything is regular for m >= 2 */ int stat_array = gsl_sf_legendre_sphPlm_array(lmax, m, x, result_array); if(stat_array == GSL_SUCCESS) { int ell; if(1.0 - fabs(x) < GSL_DBL_EPSILON) { for(ell = m; ell <= lmax; ell++) result_deriv_array[ell-m] = 0.0; return GSL_SUCCESS; } else { const double diff_a = 1.0 + x; const double diff_b = 1.0 - x; result_deriv_array[0] = - m * x / (diff_a * diff_b) * result_array[0]; if(lmax-m >= 1) result_deriv_array[1] = sqrt(2.0 * m + 3.0) * (x * result_deriv_array[0] + result_array[0]); for(ell = m+2; ell <= lmax; ell++) { const double c1 = sqrt(((2.0*ell+1.0)/(2.0*ell-1.0)) * ((double)(ell-m)/(double)(ell+m))); result_deriv_array[ell-m] = - (ell * x * result_array[ell-m] - c1 * (ell+m) * result_array[ell-1-m]) / (diff_a * diff_b); } return GSL_SUCCESS; } } else { return stat_array; } } } #ifndef HIDE_INLINE_STATIC int gsl_sf_legendre_array_size(const int lmax, const int m) { return lmax-m+1; } #endif /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_legendre_P1(const double x) { EVAL_RESULT(gsl_sf_legendre_P1_e(x, &result)); } double gsl_sf_legendre_P2(const double x) { EVAL_RESULT(gsl_sf_legendre_P2_e(x, &result)); } double gsl_sf_legendre_P3(const double x) { EVAL_RESULT(gsl_sf_legendre_P3_e(x, &result)); } double gsl_sf_legendre_Pl(const int l, const double x) { EVAL_RESULT(gsl_sf_legendre_Pl_e(l, x, &result)); } double gsl_sf_legendre_Plm(const int l, const int m, const double x) { EVAL_RESULT(gsl_sf_legendre_Plm_e(l, m, x, &result)); } double gsl_sf_legendre_sphPlm(const int l, const int m, const double x) { EVAL_RESULT(gsl_sf_legendre_sphPlm_e(l, m, x, &result)); } sources_5316/external/gsl/gsl_linalg.h0000664000176700017670000005040711705263724016635 0ustar paulpaul/* linalg/gsl_linalg.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2006, 2007 Gerard Jungman, Brian Gough, Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_LINALG_H__ #define __GSL_LINALG_H__ #include "gsl_mode.h" #include "gsl_permutation.h" #include "gsl_vector.h" #include "gsl_matrix.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus #define __BEGIN_DECLS extern "C" { #define __END_DECLS } #else #define __BEGIN_DECLS /* empty */ #define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef enum { GSL_LINALG_MOD_NONE = 0, GSL_LINALG_MOD_TRANSPOSE = 1, GSL_LINALG_MOD_CONJUGATE = 2 } gsl_linalg_matrix_mod_t; /* Note: You can now use the gsl_blas_dgemm function instead of matmult */ /* Simple implementation of matrix multiply. * Calculates C = A.B * * exceptions: GSL_EBADLEN */ int gsl_linalg_matmult (const gsl_matrix * A, const gsl_matrix * B, gsl_matrix * C); /* Simple implementation of matrix multiply. * Allows transposition of either matrix, so it * can compute A.B or Trans(A).B or A.Trans(B) or Trans(A).Trans(B) * * exceptions: GSL_EBADLEN */ int gsl_linalg_matmult_mod (const gsl_matrix * A, gsl_linalg_matrix_mod_t modA, const gsl_matrix * B, gsl_linalg_matrix_mod_t modB, gsl_matrix * C); /* Calculate the matrix exponential by the scaling and * squaring method described in Moler + Van Loan, * SIAM Rev 20, 801 (1978). The mode argument allows * choosing an optimal strategy, from the table * given in the paper, for a given precision. * * exceptions: GSL_ENOTSQR, GSL_EBADLEN */ int gsl_linalg_exponential_ss( const gsl_matrix * A, gsl_matrix * eA, gsl_mode_t mode ); /* Householder Transformations */ double gsl_linalg_householder_transform (gsl_vector * v); gsl_complex gsl_linalg_complex_householder_transform (gsl_vector_complex * v); int gsl_linalg_householder_hm (double tau, const gsl_vector * v, gsl_matrix * A); int gsl_linalg_householder_mh (double tau, const gsl_vector * v, gsl_matrix * A); int gsl_linalg_householder_hv (double tau, const gsl_vector * v, gsl_vector * w); int gsl_linalg_householder_hm1 (double tau, gsl_matrix * A); int gsl_linalg_complex_householder_hm (gsl_complex tau, const gsl_vector_complex * v, gsl_matrix_complex * A); int gsl_linalg_complex_householder_mh (gsl_complex tau, const gsl_vector_complex * v, gsl_matrix_complex * A); int gsl_linalg_complex_householder_hv (gsl_complex tau, const gsl_vector_complex * v, gsl_vector_complex * w); /* Hessenberg reduction */ int gsl_linalg_hessenberg_decomp(gsl_matrix *A, gsl_vector *tau); int gsl_linalg_hessenberg_unpack(gsl_matrix * H, gsl_vector * tau, gsl_matrix * U); int gsl_linalg_hessenberg_unpack_accum(gsl_matrix * H, gsl_vector * tau, gsl_matrix * U); int gsl_linalg_hessenberg_set_zero(gsl_matrix * H); int gsl_linalg_hessenberg_submatrix(gsl_matrix *M, gsl_matrix *A, size_t top, gsl_vector *tau); /* Hessenberg-Triangular reduction */ int gsl_linalg_hesstri_decomp(gsl_matrix * A, gsl_matrix * B, gsl_matrix * U, gsl_matrix * V, gsl_vector * work); /* Singular Value Decomposition * exceptions: */ int gsl_linalg_SV_decomp (gsl_matrix * A, gsl_matrix * V, gsl_vector * S, gsl_vector * work); int gsl_linalg_SV_decomp_mod (gsl_matrix * A, gsl_matrix * X, gsl_matrix * V, gsl_vector * S, gsl_vector * work); int gsl_linalg_SV_decomp_jacobi (gsl_matrix * A, gsl_matrix * Q, gsl_vector * S); int gsl_linalg_SV_solve (const gsl_matrix * U, const gsl_matrix * Q, const gsl_vector * S, const gsl_vector * b, gsl_vector * x); /* LU Decomposition, Gaussian elimination with partial pivoting */ int gsl_linalg_LU_decomp (gsl_matrix * A, gsl_permutation * p, int *signum); int gsl_linalg_LU_solve (const gsl_matrix * LU, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x); int gsl_linalg_LU_svx (const gsl_matrix * LU, const gsl_permutation * p, gsl_vector * x); int gsl_linalg_LU_refine (const gsl_matrix * A, const gsl_matrix * LU, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x, gsl_vector * residual); int gsl_linalg_LU_invert (const gsl_matrix * LU, const gsl_permutation * p, gsl_matrix * inverse); double gsl_linalg_LU_det (gsl_matrix * LU, int signum); double gsl_linalg_LU_lndet (gsl_matrix * LU); int gsl_linalg_LU_sgndet (gsl_matrix * lu, int signum); /* Complex LU Decomposition */ int gsl_linalg_complex_LU_decomp (gsl_matrix_complex * A, gsl_permutation * p, int *signum); int gsl_linalg_complex_LU_solve (const gsl_matrix_complex * LU, const gsl_permutation * p, const gsl_vector_complex * b, gsl_vector_complex * x); int gsl_linalg_complex_LU_svx (const gsl_matrix_complex * LU, const gsl_permutation * p, gsl_vector_complex * x); int gsl_linalg_complex_LU_refine (const gsl_matrix_complex * A, const gsl_matrix_complex * LU, const gsl_permutation * p, const gsl_vector_complex * b, gsl_vector_complex * x, gsl_vector_complex * residual); int gsl_linalg_complex_LU_invert (const gsl_matrix_complex * LU, const gsl_permutation * p, gsl_matrix_complex * inverse); gsl_complex gsl_linalg_complex_LU_det (gsl_matrix_complex * LU, int signum); double gsl_linalg_complex_LU_lndet (gsl_matrix_complex * LU); gsl_complex gsl_linalg_complex_LU_sgndet (gsl_matrix_complex * LU, int signum); /* QR decomposition */ int gsl_linalg_QR_decomp (gsl_matrix * A, gsl_vector * tau); int gsl_linalg_QR_solve (const gsl_matrix * QR, const gsl_vector * tau, const gsl_vector * b, gsl_vector * x); int gsl_linalg_QR_svx (const gsl_matrix * QR, const gsl_vector * tau, gsl_vector * x); int gsl_linalg_QR_lssolve (const gsl_matrix * QR, const gsl_vector * tau, const gsl_vector * b, gsl_vector * x, gsl_vector * residual); int gsl_linalg_QR_QRsolve (gsl_matrix * Q, gsl_matrix * R, const gsl_vector * b, gsl_vector * x); int gsl_linalg_QR_Rsolve (const gsl_matrix * QR, const gsl_vector * b, gsl_vector * x); int gsl_linalg_QR_Rsvx (const gsl_matrix * QR, gsl_vector * x); int gsl_linalg_QR_update (gsl_matrix * Q, gsl_matrix * R, gsl_vector * w, const gsl_vector * v); int gsl_linalg_QR_QTvec (const gsl_matrix * QR, const gsl_vector * tau, gsl_vector * v); int gsl_linalg_QR_Qvec (const gsl_matrix * QR, const gsl_vector * tau, gsl_vector * v); int gsl_linalg_QR_QTmat (const gsl_matrix * QR, const gsl_vector * tau, gsl_matrix * A); int gsl_linalg_QR_unpack (const gsl_matrix * QR, const gsl_vector * tau, gsl_matrix * Q, gsl_matrix * R); int gsl_linalg_R_solve (const gsl_matrix * R, const gsl_vector * b, gsl_vector * x); int gsl_linalg_R_svx (const gsl_matrix * R, gsl_vector * x); /* Q R P^T decomposition */ int gsl_linalg_QRPT_decomp (gsl_matrix * A, gsl_vector * tau, gsl_permutation * p, int *signum, gsl_vector * norm); int gsl_linalg_QRPT_decomp2 (const gsl_matrix * A, gsl_matrix * q, gsl_matrix * r, gsl_vector * tau, gsl_permutation * p, int *signum, gsl_vector * norm); int gsl_linalg_QRPT_solve (const gsl_matrix * QR, const gsl_vector * tau, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x); int gsl_linalg_QRPT_svx (const gsl_matrix * QR, const gsl_vector * tau, const gsl_permutation * p, gsl_vector * x); int gsl_linalg_QRPT_QRsolve (const gsl_matrix * Q, const gsl_matrix * R, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x); int gsl_linalg_QRPT_Rsolve (const gsl_matrix * QR, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x); int gsl_linalg_QRPT_Rsvx (const gsl_matrix * QR, const gsl_permutation * p, gsl_vector * x); int gsl_linalg_QRPT_update (gsl_matrix * Q, gsl_matrix * R, const gsl_permutation * p, gsl_vector * u, const gsl_vector * v); /* LQ decomposition */ int gsl_linalg_LQ_decomp (gsl_matrix * A, gsl_vector * tau); int gsl_linalg_LQ_solve_T (const gsl_matrix * LQ, const gsl_vector * tau, const gsl_vector * b, gsl_vector * x); int gsl_linalg_LQ_svx_T (const gsl_matrix * LQ, const gsl_vector * tau, gsl_vector * x); int gsl_linalg_LQ_lssolve_T (const gsl_matrix * LQ, const gsl_vector * tau, const gsl_vector * b, gsl_vector * x, gsl_vector * residual); int gsl_linalg_LQ_Lsolve_T (const gsl_matrix * LQ, const gsl_vector * b, gsl_vector * x); int gsl_linalg_LQ_Lsvx_T (const gsl_matrix * LQ, gsl_vector * x); int gsl_linalg_L_solve_T (const gsl_matrix * L, const gsl_vector * b, gsl_vector * x); int gsl_linalg_LQ_vecQ (const gsl_matrix * LQ, const gsl_vector * tau, gsl_vector * v); int gsl_linalg_LQ_vecQT (const gsl_matrix * LQ, const gsl_vector * tau, gsl_vector * v); int gsl_linalg_LQ_unpack (const gsl_matrix * LQ, const gsl_vector * tau, gsl_matrix * Q, gsl_matrix * L); int gsl_linalg_LQ_update (gsl_matrix * Q, gsl_matrix * R, const gsl_vector * v, gsl_vector * w); int gsl_linalg_LQ_LQsolve (gsl_matrix * Q, gsl_matrix * L, const gsl_vector * b, gsl_vector * x); /* P^T L Q decomposition */ int gsl_linalg_PTLQ_decomp (gsl_matrix * A, gsl_vector * tau, gsl_permutation * p, int *signum, gsl_vector * norm); int gsl_linalg_PTLQ_decomp2 (const gsl_matrix * A, gsl_matrix * q, gsl_matrix * r, gsl_vector * tau, gsl_permutation * p, int *signum, gsl_vector * norm); int gsl_linalg_PTLQ_solve_T (const gsl_matrix * QR, const gsl_vector * tau, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x); int gsl_linalg_PTLQ_svx_T (const gsl_matrix * LQ, const gsl_vector * tau, const gsl_permutation * p, gsl_vector * x); int gsl_linalg_PTLQ_LQsolve_T (const gsl_matrix * Q, const gsl_matrix * L, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x); int gsl_linalg_PTLQ_Lsolve_T (const gsl_matrix * LQ, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x); int gsl_linalg_PTLQ_Lsvx_T (const gsl_matrix * LQ, const gsl_permutation * p, gsl_vector * x); int gsl_linalg_PTLQ_update (gsl_matrix * Q, gsl_matrix * L, const gsl_permutation * p, const gsl_vector * v, gsl_vector * w); /* Cholesky Decomposition */ int gsl_linalg_cholesky_decomp (gsl_matrix * A); int gsl_linalg_cholesky_solve (const gsl_matrix * cholesky, const gsl_vector * b, gsl_vector * x); int gsl_linalg_cholesky_svx (const gsl_matrix * cholesky, gsl_vector * x); /* Cholesky decomposition with unit-diagonal triangular parts. * A = L D L^T, where diag(L) = (1,1,...,1). * Upon exit, A contains L and L^T as for Cholesky, and * the diagonal of A is (1,1,...,1). The vector Dis set * to the diagonal elements of the diagonal matrix D. */ int gsl_linalg_cholesky_decomp_unit(gsl_matrix * A, gsl_vector * D); /* Complex Cholesky Decomposition */ int gsl_linalg_complex_cholesky_decomp (gsl_matrix_complex * A); int gsl_linalg_complex_cholesky_solve (const gsl_matrix_complex * cholesky, const gsl_vector_complex * b, gsl_vector_complex * x); int gsl_linalg_complex_cholesky_svx (const gsl_matrix_complex * cholesky, gsl_vector_complex * x); /* Symmetric to symmetric tridiagonal decomposition */ int gsl_linalg_symmtd_decomp (gsl_matrix * A, gsl_vector * tau); int gsl_linalg_symmtd_unpack (const gsl_matrix * A, const gsl_vector * tau, gsl_matrix * Q, gsl_vector * diag, gsl_vector * subdiag); int gsl_linalg_symmtd_unpack_T (const gsl_matrix * A, gsl_vector * diag, gsl_vector * subdiag); /* Hermitian to symmetric tridiagonal decomposition */ int gsl_linalg_hermtd_decomp (gsl_matrix_complex * A, gsl_vector_complex * tau); int gsl_linalg_hermtd_unpack (const gsl_matrix_complex * A, const gsl_vector_complex * tau, gsl_matrix_complex * Q, gsl_vector * diag, gsl_vector * sudiag); int gsl_linalg_hermtd_unpack_T (const gsl_matrix_complex * A, gsl_vector * diag, gsl_vector * subdiag); /* Linear Solve Using Householder Transformations * exceptions: */ int gsl_linalg_HH_solve (gsl_matrix * A, const gsl_vector * b, gsl_vector * x); int gsl_linalg_HH_svx (gsl_matrix * A, gsl_vector * x); /* Linear solve for a symmetric tridiagonal system. * The input vectors represent the NxN matrix as follows: * * diag[0] offdiag[0] 0 ... * offdiag[0] diag[1] offdiag[1] ... * 0 offdiag[1] diag[2] ... * 0 0 offdiag[2] ... * ... ... ... ... */ int gsl_linalg_solve_symm_tridiag (const gsl_vector * diag, const gsl_vector * offdiag, const gsl_vector * b, gsl_vector * x); /* Linear solve for a nonsymmetric tridiagonal system. * The input vectors represent the NxN matrix as follows: * * diag[0] abovediag[0] 0 ... * belowdiag[0] diag[1] abovediag[1] ... * 0 belowdiag[1] diag[2] ... * 0 0 belowdiag[2] ... * ... ... ... ... */ int gsl_linalg_solve_tridiag (const gsl_vector * diag, const gsl_vector * abovediag, const gsl_vector * belowdiag, const gsl_vector * b, gsl_vector * x); /* Linear solve for a symmetric cyclic tridiagonal system. * The input vectors represent the NxN matrix as follows: * * diag[0] offdiag[0] 0 ..... offdiag[N-1] * offdiag[0] diag[1] offdiag[1] ..... * 0 offdiag[1] diag[2] ..... * 0 0 offdiag[2] ..... * ... ... * offdiag[N-1] ... */ int gsl_linalg_solve_symm_cyc_tridiag (const gsl_vector * diag, const gsl_vector * offdiag, const gsl_vector * b, gsl_vector * x); /* Linear solve for a nonsymmetric cyclic tridiagonal system. * The input vectors represent the NxN matrix as follows: * * diag[0] abovediag[0] 0 ..... belowdiag[N-1] * belowdiag[0] diag[1] abovediag[1] ..... * 0 belowdiag[1] diag[2] * 0 0 belowdiag[2] ..... * ... ... * abovediag[N-1] ... */ int gsl_linalg_solve_cyc_tridiag (const gsl_vector * diag, const gsl_vector * abovediag, const gsl_vector * belowdiag, const gsl_vector * b, gsl_vector * x); /* Bidiagonal decomposition */ int gsl_linalg_bidiag_decomp (gsl_matrix * A, gsl_vector * tau_U, gsl_vector * tau_V); int gsl_linalg_bidiag_unpack (const gsl_matrix * A, const gsl_vector * tau_U, gsl_matrix * U, const gsl_vector * tau_V, gsl_matrix * V, gsl_vector * diag, gsl_vector * superdiag); int gsl_linalg_bidiag_unpack2 (gsl_matrix * A, gsl_vector * tau_U, gsl_vector * tau_V, gsl_matrix * V); int gsl_linalg_bidiag_unpack_B (const gsl_matrix * A, gsl_vector * diag, gsl_vector * superdiag); /* Balancing */ int gsl_linalg_balance_matrix (gsl_matrix * A, gsl_vector * D); int gsl_linalg_balance_accum (gsl_matrix * A, gsl_vector * D); int gsl_linalg_balance_columns (gsl_matrix * A, gsl_vector * D); __END_DECLS #endif /* __GSL_LINALG_H__ */ sources_5316/external/gsl/gsl_integration__qawc.c0000664000176700017670000001304711723710247021053 0ustar paulpaul/* integration/qawc.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_integration.h" #include "gsl_integration__initialise.c" #include "gsl_integration__set_initial.c" #include "gsl_integration__qpsrt.c" #include "gsl_integration__util.c" #include "gsl_integration__qc25c.c" int gsl_integration_qawc (gsl_function * f, const double a, const double b, const double c, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr) { double area, errsum; double result0, abserr0; double tolerance; size_t iteration = 0; int roundoff_type1 = 0, roundoff_type2 = 0, error_type = 0; int err_reliable; int sign = 1; double lower, higher; /* Initialize results */ *result = 0; *abserr = 0; if (limit > workspace->limit) { GSL_ERROR ("iteration limit exceeds available workspace", GSL_EINVAL) ; } if (b < a) { lower = b ; higher = a ; sign = -1 ; } else { lower = a; higher = b; } initialise (workspace, lower, higher); if (epsabs <= 0 && (epsrel < 50 * GSL_DBL_EPSILON || epsrel < 0.5e-28)) { GSL_ERROR ("tolerance cannot be acheived with given epsabs and epsrel", GSL_EBADTOL); } if (c == a || c == b) { GSL_ERROR ("cannot integrate with singularity on endpoint", GSL_EINVAL); } /* perform the first integration */ qc25c (f, lower, higher, c, &result0, &abserr0, &err_reliable); set_initial_result (workspace, result0, abserr0); /* Test on accuracy, use 0.01 relative error as an extra safety margin on the first iteration (ignored for subsequent iterations) */ tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (result0)); if (abserr0 < tolerance && abserr0 < 0.01 * fabs(result0)) { *result = sign * result0; *abserr = abserr0; return GSL_SUCCESS; } else if (limit == 1) { *result = sign * result0; *abserr = abserr0; GSL_ERROR ("a maximum of one iteration was insufficient", GSL_EMAXITER); } area = result0; errsum = abserr0; iteration = 1; do { double a1, b1, a2, b2; double a_i, b_i, r_i, e_i; double area1 = 0, area2 = 0, area12 = 0; double error1 = 0, error2 = 0, error12 = 0; int err_reliable1, err_reliable2; /* Bisect the subinterval with the largest error estimate */ retrieve (workspace, &a_i, &b_i, &r_i, &e_i); a1 = a_i; b1 = 0.5 * (a_i + b_i); a2 = b1; b2 = b_i; if (c > a1 && c <= b1) { b1 = 0.5 * (c + b2) ; a2 = b1; } else if (c > b1 && c < b2) { b1 = 0.5 * (a1 + c) ; a2 = b1; } qc25c (f, a1, b1, c, &area1, &error1, &err_reliable1); qc25c (f, a2, b2, c, &area2, &error2, &err_reliable2); area12 = area1 + area2; error12 = error1 + error2; errsum += (error12 - e_i); area += area12 - r_i; if (err_reliable1 && err_reliable2) { double delta = r_i - area12; if (fabs (delta) <= 1.0e-5 * fabs (area12) && error12 >= 0.99 * e_i) { roundoff_type1++; } if (iteration >= 10 && error12 > e_i) { roundoff_type2++; } } tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (area)); if (errsum > tolerance) { if (roundoff_type1 >= 6 || roundoff_type2 >= 20) { error_type = 2; /* round off error */ } /* set error flag in the case of bad integrand behaviour at a point of the integration range */ if (subinterval_too_small (a1, a2, b2)) { error_type = 3; } } update (workspace, a1, b1, area1, error1, a2, b2, area2, error2); retrieve (workspace, &a_i, &b_i, &r_i, &e_i); iteration++; } while (iteration < limit && !error_type && errsum > tolerance); *result = sign * sum_results (workspace); *abserr = errsum; if (errsum <= tolerance) { return GSL_SUCCESS; } else if (error_type == 2) { GSL_ERROR ("roundoff error prevents tolerance from being achieved", GSL_EROUND); } else if (error_type == 3) { GSL_ERROR ("bad integrand behavior found in the integration interval", GSL_ESING); } else if (iteration == limit) { GSL_ERROR ("maximum number of subdivisions reached", GSL_EMAXITER); } else { GSL_ERROR ("could not integrate function", GSL_EFAILED); } } sources_5316/external/gsl/gsl_ieee-utils__fp-darwin86.c0000664000176700017670000001237211723710247021707 0ustar paulpaul/* ieee-utils/fp-darwin86.c * * Copyright (C) 2006 Erik Schnetter * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_ieee_utils.h" #include "gsl_errno.h" /* Here is the dirty part. Set up your 387 through the control word * (cw) register. * * 15-13 12 11-10 9-8 7-6 5 4 3 2 1 0 * | reserved | IC | RC | PC | reserved | PM | UM | OM | ZM | DM | IM * * IM: Invalid operation mask * DM: Denormalized operand mask * ZM: Zero-divide mask * OM: Overflow mask * UM: Underflow mask * PM: Precision (inexact result) mask * * Mask bit is 1 means no interrupt. * * PC: Precision control * 11 - round to extended precision * 10 - round to double precision * 00 - round to single precision * * RC: Rounding control * 00 - rounding to nearest * 01 - rounding down (toward - infinity) * 10 - rounding up (toward + infinity) * 11 - rounding toward zero * * IC: Infinity control * That is for 8087 and 80287 only. * * The hardware default is 0x037f which we use. */ /* masking of interrupts */ #define _FPU_MASK_IM 0x01 #define _FPU_MASK_DM 0x02 #define _FPU_MASK_ZM 0x04 #define _FPU_MASK_OM 0x08 #define _FPU_MASK_UM 0x10 #define _FPU_MASK_PM 0x20 /* precision control */ #define _FPU_EXTENDED 0x300 /* libm requires double extended precision. */ #define _FPU_DOUBLE 0x200 #define _FPU_SINGLE 0x0 /* rounding control */ #define _FPU_RC_NEAREST 0x0 /* RECOMMENDED */ #define _FPU_RC_DOWN 0x400 #define _FPU_RC_UP 0x800 #define _FPU_RC_ZERO 0xC00 #define _FPU_RESERVED 0xF0C0 /* Reserved bits in cw */ /* The fdlibm code requires strict IEEE double precision arithmetic, and no interrupts for exceptions, rounding to nearest. */ #define _FPU_DEFAULT 0x037f /* IEEE: same as above. */ #define _FPU_IEEE 0x037f /* Type of the control word. */ typedef unsigned int fpu_control_t __attribute__ ((__mode__ (__HI__))); /* Macros for accessing the hardware control word. Note that the use of these macros is no sufficient anymore with recent hardware. Some floating point operations are executed in the SSE/SSE2 engines which have their own control and status register. */ #define _FPU_GETCW(cw) __asm__ __volatile__ ("fnstcw %0" : "=m" (*&cw)) #define _FPU_SETCW(cw) __asm__ __volatile__ ("fldcw %0" : : "m" (*&cw)) /* Default control word set at startup. */ extern fpu_control_t __fpu_control; #define _FPU_GETMXCSR(cw_sse) asm volatile ("stmxcsr %0" : "=m" (cw_sse)) #define _FPU_SETMXCSR(cw_sse) asm volatile ("ldmxcsr %0" : : "m" (cw_sse)) int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { fpu_control_t mode, mode_sse; _FPU_GETCW (mode) ; mode &= _FPU_RESERVED ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: mode |= _FPU_SINGLE ; break ; case GSL_IEEE_DOUBLE_PRECISION: mode |= _FPU_DOUBLE ; break ; case GSL_IEEE_EXTENDED_PRECISION: mode |= _FPU_EXTENDED ; break ; default: mode |= _FPU_EXTENDED ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: mode |= _FPU_RC_NEAREST ; break ; case GSL_IEEE_ROUND_DOWN: mode |= _FPU_RC_DOWN ; break ; case GSL_IEEE_ROUND_UP: mode |= _FPU_RC_UP ; break ; case GSL_IEEE_ROUND_TO_ZERO: mode |= _FPU_RC_ZERO ; break ; default: mode |= _FPU_RC_NEAREST ; } if (exception_mask & GSL_IEEE_MASK_INVALID) mode |= _FPU_MASK_IM ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) mode |= _FPU_MASK_DM ; if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode |= _FPU_MASK_ZM ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode |= _FPU_MASK_OM ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode |= _FPU_MASK_UM ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode &= ~ _FPU_MASK_PM ; } else { mode |= _FPU_MASK_PM ; } _FPU_SETCW (mode) ; _FPU_GETMXCSR (mode_sse) ; mode_sse &= 0xFFFF0000 ; if (exception_mask & GSL_IEEE_MASK_INVALID) mode_sse |= _FPU_MASK_IM << 7 ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) mode_sse |= _FPU_MASK_DM << 7 ; if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode_sse |= _FPU_MASK_ZM << 7 ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode_sse |= _FPU_MASK_OM << 7 ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode_sse |= _FPU_MASK_UM << 7 ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode_sse &= ~ _FPU_MASK_PM << 7 ; } else { mode_sse |= _FPU_MASK_PM << 7 ; } _FPU_SETMXCSR (mode_sse) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_ode-initval__evolve.c0000664000176700017670000001161611723710247021310 0ustar paulpaul/* ode-initval/evolve.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" gsl_odeiv_evolve * gsl_odeiv_evolve_alloc (size_t dim) { gsl_odeiv_evolve *e = (gsl_odeiv_evolve *) malloc (sizeof (gsl_odeiv_evolve)); if (e == 0) { GSL_ERROR_NULL ("failed to allocate space for evolve struct", GSL_ENOMEM); } e->y0 = (double *) malloc (dim * sizeof (double)); if (e->y0 == 0) { free (e); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } e->yerr = (double *) malloc (dim * sizeof (double)); if (e->yerr == 0) { free (e->y0); free (e); GSL_ERROR_NULL ("failed to allocate space for yerr", GSL_ENOMEM); } e->dydt_in = (double *) malloc (dim * sizeof (double)); if (e->dydt_in == 0) { free (e->yerr); free (e->y0); free (e); GSL_ERROR_NULL ("failed to allocate space for dydt_in", GSL_ENOMEM); } e->dydt_out = (double *) malloc (dim * sizeof (double)); if (e->dydt_out == 0) { free (e->dydt_in); free (e->yerr); free (e->y0); free (e); GSL_ERROR_NULL ("failed to allocate space for dydt_out", GSL_ENOMEM); } e->dimension = dim; e->count = 0; e->failed_steps = 0; e->last_step = 0.0; return e; } int gsl_odeiv_evolve_reset (gsl_odeiv_evolve * e) { e->count = 0; e->failed_steps = 0; e->last_step = 0.0; return GSL_SUCCESS; } void gsl_odeiv_evolve_free (gsl_odeiv_evolve * e) { free (e->dydt_out); free (e->dydt_in); free (e->yerr); free (e->y0); free (e); } /* Evolution framework method. * * Uses an adaptive step control object */ int gsl_odeiv_evolve_apply (gsl_odeiv_evolve * e, gsl_odeiv_control * con, gsl_odeiv_step * step, const gsl_odeiv_system * dydt, double *t, double t1, double *h, double y[]) { const double t0 = *t; double h0 = *h; int step_status; int final_step = 0; double dt = t1 - t0; /* remaining time, possibly less than h */ if (e->dimension != step->dimension) { GSL_ERROR ("step dimension must match evolution size", GSL_EINVAL); } if ((dt < 0.0 && h0 > 0.0) || (dt > 0.0 && h0 < 0.0)) { GSL_ERROR ("step direction must match interval direction", GSL_EINVAL); } /* No need to copy if we cannot control the step size. */ if (con != NULL) { DBL_MEMCPY (e->y0, y, e->dimension); } /* Calculate initial dydt once if the method can benefit. */ if (step->type->can_use_dydt_in) { int status = GSL_ODEIV_FN_EVAL (dydt, t0, y, e->dydt_in); if (status) { return status; } } try_step: if ((dt >= 0.0 && h0 > dt) || (dt < 0.0 && h0 < dt)) { h0 = dt; final_step = 1; } else { final_step = 0; } if (step->type->can_use_dydt_in) { step_status = gsl_odeiv_step_apply (step, t0, h0, y, e->yerr, e->dydt_in, e->dydt_out, dydt); } else { step_status = gsl_odeiv_step_apply (step, t0, h0, y, e->yerr, NULL, e->dydt_out, dydt); } /* Check for stepper internal failure */ if (step_status != GSL_SUCCESS) { *h = h0; /* notify user of step-size which caused the failure */ return step_status; } e->count++; e->last_step = h0; if (final_step) { *t = t1; } else { *t = t0 + h0; } if (con != NULL) { /* Check error and attempt to adjust the step. */ const int hadjust_status = gsl_odeiv_control_hadjust (con, step, y, e->yerr, e->dydt_out, &h0); if (hadjust_status == GSL_ODEIV_HADJ_DEC) { /* Step was decreased. Undo and go back to try again. */ DBL_MEMCPY (y, e->y0, dydt->dimension); e->failed_steps++; goto try_step; } } *h = h0; /* suggest step size for next time-step */ return step_status; } sources_5316/external/gsl/gsl_cblas__cblas.h0000664000176700017670000000170411705263724017752 0ustar paulpaul#define INDEX int #define OFFSET(N, incX) ((incX) > 0 ? 0 : ((N) - 1) * (-(incX))) #define BLAS_ERROR(x) cblas_xerbla(0, __FILE__, x); #define CONJUGATE(x) ((x) == CblasConjTrans) #define TRANSPOSE(x) ((x) == CblasTrans || (x) == CblasConjTrans) #define UPPER(x) ((x) == CblasUpper) #define LOWER(x) ((x) == CblasLower) /* Handling of packed complex types... */ #define REAL(a,i) (((BASE *) a)[2*(i)]) #define IMAG(a,i) (((BASE *) a)[2*(i)+1]) #define REAL0(a) (((BASE *)a)[0]) #define IMAG0(a) (((BASE *)a)[1]) #define CONST_REAL(a,i) (((const BASE *) a)[2*(i)]) #define CONST_IMAG(a,i) (((const BASE *) a)[2*(i)+1]) #define CONST_REAL0(a) (((const BASE *)a)[0]) #define CONST_IMAG0(a) (((const BASE *)a)[1]) #define GB(KU,KL,lda,i,j) ((KU+1+(i-j))*lda + j) #define TRCOUNT(N,i) ((((i)+1)*(2*(N)-(i)))/2) /* #define TBUP(N,i,j) */ /* #define TBLO(N,i,j) */ #define TPUP(N,i,j) (TRCOUNT(N,(i)-1)+(j)-(i)) #define TPLO(N,i,j) (((i)*((i)+1))/2 + (j)) sources_5316/external/gsl/gsl_linalg__hermtd.c0000664000176700017670000001621211723710247020323 0ustar paulpaul/* linalg/hermtd.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Factorise a hermitian matrix A into * * A = U T U' * * where U is unitary and T is real symmetric tridiagonal. Only the * diagonal and lower triangular part of A is referenced and modified. * * On exit, T is stored in the diagonal and first subdiagonal of * A. Since T is symmetric the upper diagonal is not stored. * * U is stored as a packed set of Householder transformations in the * lower triangular part of the input matrix below the first subdiagonal. * * The full matrix for Q can be obtained as the product * * Q = Q_N ... Q_2 Q_1 * * where * * Q_i = (I - tau_i * v_i * v_i') * * and where v_i is a Householder vector * * v_i = [0, ..., 0, 1, A(i+2,i), A(i+3,i), ... , A(N,i)] * * This storage scheme is the same as in LAPACK. See LAPACK's * chetd2.f for details. * * See Golub & Van Loan, "Matrix Computations" (3rd ed), Section 8.3 */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_complex_math.h" #include "gsl_linalg.h" int gsl_linalg_hermtd_decomp (gsl_matrix_complex * A, gsl_vector_complex * tau) { if (A->size1 != A->size2) { GSL_ERROR ("hermitian tridiagonal decomposition requires square matrix", GSL_ENOTSQR); } else if (tau->size + 1 != A->size1) { GSL_ERROR ("size of tau must be (matrix size - 1)", GSL_EBADLEN); } else { const size_t N = A->size1; size_t i; const gsl_complex zero = gsl_complex_rect (0.0, 0.0); const gsl_complex one = gsl_complex_rect (1.0, 0.0); const gsl_complex neg_one = gsl_complex_rect (-1.0, 0.0); for (i = 0 ; i < N - 1; i++) { gsl_vector_complex_view c = gsl_matrix_complex_column (A, i); gsl_vector_complex_view v = gsl_vector_complex_subvector (&c.vector, i + 1, N - (i + 1)); gsl_complex tau_i = gsl_linalg_complex_householder_transform (&v.vector); /* Apply the transformation H^T A H to the remaining columns */ if ((i + 1) < (N - 1) && !(GSL_REAL(tau_i) == 0.0 && GSL_IMAG(tau_i) == 0.0)) { gsl_matrix_complex_view m = gsl_matrix_complex_submatrix (A, i + 1, i + 1, N - (i+1), N - (i+1)); gsl_complex ei = gsl_vector_complex_get(&v.vector, 0); gsl_vector_complex_view x = gsl_vector_complex_subvector (tau, i, N-(i+1)); gsl_vector_complex_set (&v.vector, 0, one); /* x = tau * A * v */ gsl_blas_zhemv (CblasLower, tau_i, &m.matrix, &v.vector, zero, &x.vector); /* w = x - (1/2) tau * (x' * v) * v */ { gsl_complex xv, txv, alpha; gsl_blas_zdotc(&x.vector, &v.vector, &xv); txv = gsl_complex_mul(tau_i, xv); alpha = gsl_complex_mul_real(txv, -0.5); gsl_blas_zaxpy(alpha, &v.vector, &x.vector); } /* apply the transformation A = A - v w' - w v' */ gsl_blas_zher2(CblasLower, neg_one, &v.vector, &x.vector, &m.matrix); gsl_vector_complex_set (&v.vector, 0, ei); } gsl_vector_complex_set (tau, i, tau_i); } return GSL_SUCCESS; } } /* Form the orthogonal matrix Q from the packed QR matrix */ int gsl_linalg_hermtd_unpack (const gsl_matrix_complex * A, const gsl_vector_complex * tau, gsl_matrix_complex * Q, gsl_vector * diag, gsl_vector * sdiag) { if (A->size1 != A->size2) { GSL_ERROR ("matrix A must be sqaure", GSL_ENOTSQR); } else if (tau->size + 1 != A->size1) { GSL_ERROR ("size of tau must be (matrix size - 1)", GSL_EBADLEN); } else if (Q->size1 != A->size1 || Q->size2 != A->size1) { GSL_ERROR ("size of Q must match size of A", GSL_EBADLEN); } else if (diag->size != A->size1) { GSL_ERROR ("size of diagonal must match size of A", GSL_EBADLEN); } else if (sdiag->size + 1 != A->size1) { GSL_ERROR ("size of subdiagonal must be (matrix size - 1)", GSL_EBADLEN); } else { const size_t N = A->size1; size_t i; /* Initialize Q to the identity */ gsl_matrix_complex_set_identity (Q); for (i = N - 1; i > 0 && i--;) { gsl_complex ti = gsl_vector_complex_get (tau, i); gsl_vector_complex_const_view c = gsl_matrix_complex_const_column (A, i); gsl_vector_complex_const_view h = gsl_vector_complex_const_subvector (&c.vector, i + 1, N - (i+1)); gsl_matrix_complex_view m = gsl_matrix_complex_submatrix (Q, i + 1, i + 1, N-(i+1), N-(i+1)); gsl_linalg_complex_householder_hm (ti, &h.vector, &m.matrix); } /* Copy diagonal into diag */ for (i = 0; i < N; i++) { gsl_complex Aii = gsl_matrix_complex_get (A, i, i); gsl_vector_set (diag, i, GSL_REAL(Aii)); } /* Copy subdiagonal into sdiag */ for (i = 0; i < N - 1; i++) { gsl_complex Aji = gsl_matrix_complex_get (A, i+1, i); gsl_vector_set (sdiag, i, GSL_REAL(Aji)); } return GSL_SUCCESS; } } int gsl_linalg_hermtd_unpack_T (const gsl_matrix_complex * A, gsl_vector * diag, gsl_vector * sdiag) { if (A->size1 != A->size2) { GSL_ERROR ("matrix A must be sqaure", GSL_ENOTSQR); } else if (diag->size != A->size1) { GSL_ERROR ("size of diagonal must match size of A", GSL_EBADLEN); } else if (sdiag->size + 1 != A->size1) { GSL_ERROR ("size of subdiagonal must be (matrix size - 1)", GSL_EBADLEN); } else { const size_t N = A->size1; size_t i; /* Copy diagonal into diag */ for (i = 0; i < N; i++) { gsl_complex Aii = gsl_matrix_complex_get (A, i, i); gsl_vector_set (diag, i, GSL_REAL(Aii)); } /* Copy subdiagonal into sd */ for (i = 0; i < N - 1; i++) { gsl_complex Aji = gsl_matrix_complex_get (A, i+1, i); gsl_vector_set (sdiag, i, GSL_REAL(Aji)); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_sort_double.h0000664000176700017670000000347211705263724017710 0ustar paulpaul/* sort/gsl_sort_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_DOUBLE_H__ #define __GSL_SORT_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort (double * data, const size_t stride, const size_t n); void gsl_sort_index (size_t * p, const double * data, const size_t stride, const size_t n); int gsl_sort_smallest (double * dest, const size_t k, const double * src, const size_t stride, const size_t n); int gsl_sort_smallest_index (size_t * p, const size_t k, const double * src, const size_t stride, const size_t n); int gsl_sort_largest (double * dest, const size_t k, const double * src, const size_t stride, const size_t n); int gsl_sort_largest_index (size_t * p, const size_t k, const double * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_DOUBLE_H__ */ sources_5316/external/gsl/gsl_specfunc__bessel_Jnu.c0000664000176700017670000001223111723710247021466 0ustar paulpaul/* specfunc/bessel_Jnu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_olver.h" #include "gsl_specfunc__bessel_temme.h" /* Evaluate at large enough nu to apply asymptotic * results and apply backward recurrence. */ #if 0 static int bessel_J_recur_asymp(const double nu, const double x, gsl_sf_result * Jnu, gsl_sf_result * Jnup1) { const double nu_cut = 25.0; int n; int steps = ceil(nu_cut - nu) + 1; gsl_sf_result r_Jnp1; gsl_sf_result r_Jn; int stat_O1 = gsl_sf_bessel_Jnu_asymp_Olver_e(nu + steps + 1.0, x, &r_Jnp1); int stat_O2 = gsl_sf_bessel_Jnu_asymp_Olver_e(nu + steps, x, &r_Jn); double r_fe = fabs(r_Jnp1.err/r_Jnp1.val) + fabs(r_Jn.err/r_Jn.val); double Jnp1 = r_Jnp1.val; double Jn = r_Jn.val; double Jnm1; double Jnp1_save; for(n=steps; n>0; n--) { Jnm1 = 2.0*(nu+n)/x * Jn - Jnp1; Jnp1 = Jn; Jnp1_save = Jn; Jn = Jnm1; } Jnu->val = Jn; Jnu->err = (r_fe + GSL_DBL_EPSILON * (steps + 1.0)) * fabs(Jn); Jnup1->val = Jnp1_save; Jnup1->err = (r_fe + GSL_DBL_EPSILON * (steps + 1.0)) * fabs(Jnp1_save); return GSL_ERROR_SELECT_2(stat_O1, stat_O2); } #endif /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Jnu_e(const double nu, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { if(nu == 0.0) { result->val = 1.0; result->err = 0.0; } else { result->val = 0.0; result->err = 0.0; } return GSL_SUCCESS; } else if(x*x < 10.0*(nu+1.0)) { return gsl_sf_bessel_IJ_taylor_e(nu, x, -1, 100, GSL_DBL_EPSILON, result); } else if(nu > 50.0) { return gsl_sf_bessel_Jnu_asymp_Olver_e(nu, x, result); } else if(x > 1000.0) { /* We need this to avoid feeding large x to CF1; note that * due to the above check, we know that n <= 50. See similar * block in bessel_Jn.c. */ return gsl_sf_bessel_Jnu_asympx_e(nu, x, result); } else { /* -1/2 <= mu <= 1/2 */ int N = (int)(nu + 0.5); double mu = nu - N; /* Determine the J ratio at nu. */ double Jnup1_Jnu; double sgn_Jnu; const int stat_CF1 = gsl_sf_bessel_J_CF1(nu, x, &Jnup1_Jnu, &sgn_Jnu); if(x < 2.0) { /* Determine Y_mu, Y_mup1 directly and recurse forward to nu. * Then use the CF1 information to solve for J_nu and J_nup1. */ gsl_sf_result Y_mu, Y_mup1; const int stat_mu = gsl_sf_bessel_Y_temme(mu, x, &Y_mu, &Y_mup1); double Ynm1 = Y_mu.val; double Yn = Y_mup1.val; double Ynp1 = 0.0; int n; for(n=1; nval = 2.0/(M_PI*x) / (Jnup1_Jnu*Yn - Ynp1); result->err = GSL_DBL_EPSILON * (N + 2.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mu, stat_CF1); } else { /* Recurse backward from nu to mu, determining the J ratio * at mu. Use this together with a Steed method CF2 to * determine the actual J_mu, and thus obtain the normalization. */ double Jmu; double Jmup1_Jmu; double sgn_Jmu; double Jmuprime_Jmu; double P, Q; const int stat_CF2 = gsl_sf_bessel_JY_steed_CF2(mu, x, &P, &Q); double gamma; double Jnp1 = sgn_Jnu * GSL_SQRT_DBL_MIN * Jnup1_Jnu; double Jn = sgn_Jnu * GSL_SQRT_DBL_MIN; double Jnm1; int n; for(n=N; n>0; n--) { Jnm1 = 2.0*(mu+n)/x * Jn - Jnp1; Jnp1 = Jn; Jn = Jnm1; } Jmup1_Jmu = Jnp1/Jn; sgn_Jmu = GSL_SIGN(Jn); Jmuprime_Jmu = mu/x - Jmup1_Jmu; gamma = (P - Jmuprime_Jmu)/Q; Jmu = sgn_Jmu * sqrt(2.0/(M_PI*x) / (Q + gamma*(P-Jmuprime_Jmu))); result->val = Jmu * (sgn_Jnu * GSL_SQRT_DBL_MIN) / Jn; result->err = 2.0 * GSL_DBL_EPSILON * (N + 2.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_CF2, stat_CF1); } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_Jnu(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_Jnu_e(nu, x, &result)); } sources_5316/external/gsl/gsl_cblas__cher2k.c0000664000176700017670000000070011723710247020027 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cher2k (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const float beta, void *C, const int ldc) { #define BASE float #include "gsl_cblas__source_her2k.h" #undef BASE } sources_5316/external/gsl/gsl_combination.h0000664000176700017670000000530511705263724017666 0ustar paulpaul/* combination/gsl_combination.h * based on permutation/gsl_permutation.h by Brian Gough * * Copyright (C) 2001 Szymon Jaroszewicz * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_COMBINATION_H__ #define __GSL_COMBINATION_H__ #include #include "gsl_errno.h" #include "gsl_types.h" #include "gsl_check_range.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_combination_struct { size_t n; size_t k; size_t *data; }; typedef struct gsl_combination_struct gsl_combination; gsl_combination *gsl_combination_alloc (const size_t n, const size_t k); gsl_combination *gsl_combination_calloc (const size_t n, const size_t k); void gsl_combination_init_first (gsl_combination * c); void gsl_combination_init_last (gsl_combination * c); void gsl_combination_free (gsl_combination * c); int gsl_combination_memcpy (gsl_combination * dest, const gsl_combination * src); int gsl_combination_fread (FILE * stream, gsl_combination * c); int gsl_combination_fwrite (FILE * stream, const gsl_combination * c); int gsl_combination_fscanf (FILE * stream, gsl_combination * c); int gsl_combination_fprintf (FILE * stream, const gsl_combination * c, const char *format); size_t gsl_combination_n (const gsl_combination * c); size_t gsl_combination_k (const gsl_combination * c); size_t * gsl_combination_data (const gsl_combination * c); size_t gsl_combination_get (const gsl_combination * c, const size_t i); int gsl_combination_valid (gsl_combination * c); int gsl_combination_next (gsl_combination * c); int gsl_combination_prev (gsl_combination * c); #ifdef HAVE_INLINE extern inline size_t gsl_combination_get (const gsl_combination * c, const size_t i) { #if GSL_RANGE_CHECK if (i >= c->k) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return c->data[i]; } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_COMBINATION_H__ */ sources_5316/external/gsl/gsl_cblas__chpmv.c0000664000176700017670000000056311723710247017775 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_chpmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *Ap, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE float #include "gsl_cblas__source_hpmv.h" #undef BASE } sources_5316/external/gsl/gsl_poly__zsolve_cubic.c0000664000176700017670000001021111723710247021235 0ustar paulpaul/* poly/zsolve_cubic.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* zsolve_cubic.c - finds the complex roots of x^3 + a x^2 + b x + c = 0 */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_poly.h" #define SWAP(a,b) do { double tmp = b ; b = a ; a = tmp ; } while(0) int gsl_poly_complex_solve_cubic (double a, double b, double c, gsl_complex *z0, gsl_complex *z1, gsl_complex *z2) { double q = (a * a - 3 * b); double r = (2 * a * a * a - 9 * a * b + 27 * c); double Q = q / 9; double R = r / 54; double Q3 = Q * Q * Q; double R2 = R * R; double CR2 = 729 * r * r; double CQ3 = 2916 * q * q * q; if (R == 0 && Q == 0) { GSL_REAL (*z0) = -a / 3; GSL_IMAG (*z0) = 0; GSL_REAL (*z1) = -a / 3; GSL_IMAG (*z1) = 0; GSL_REAL (*z2) = -a / 3; GSL_IMAG (*z2) = 0; return 3; } else if (CR2 == CQ3) { /* this test is actually R2 == Q3, written in a form suitable for exact computation with integers */ /* Due to finite precision some double roots may be missed, and will be considered to be a pair of complex roots z = x +/- epsilon i close to the real axis. */ double sqrtQ = sqrt (Q); if (R > 0) { GSL_REAL (*z0) = -2 * sqrtQ - a / 3; GSL_IMAG (*z0) = 0; GSL_REAL (*z1) = sqrtQ - a / 3; GSL_IMAG (*z1) = 0; GSL_REAL (*z2) = sqrtQ - a / 3; GSL_IMAG (*z2) = 0; } else { GSL_REAL (*z0) = -sqrtQ - a / 3; GSL_IMAG (*z0) = 0; GSL_REAL (*z1) = -sqrtQ - a / 3; GSL_IMAG (*z1) = 0; GSL_REAL (*z2) = 2 * sqrtQ - a / 3; GSL_IMAG (*z2) = 0; } return 3; } else if (CR2 < CQ3) /* equivalent to R2 < Q3 */ { double sqrtQ = sqrt (Q); double sqrtQ3 = sqrtQ * sqrtQ * sqrtQ; double theta = acos (R / sqrtQ3); double norm = -2 * sqrtQ; double r0 = norm * cos (theta / 3) - a / 3; double r1 = norm * cos ((theta + 2.0 * M_PI) / 3) - a / 3; double r2 = norm * cos ((theta - 2.0 * M_PI) / 3) - a / 3; /* Sort r0, r1, r2 into increasing order */ if (r0 > r1) SWAP (r0, r1); if (r1 > r2) { SWAP (r1, r2); if (r0 > r1) SWAP (r0, r1); } GSL_REAL (*z0) = r0; GSL_IMAG (*z0) = 0; GSL_REAL (*z1) = r1; GSL_IMAG (*z1) = 0; GSL_REAL (*z2) = r2; GSL_IMAG (*z2) = 0; return 3; } else { double sgnR = (R >= 0 ? 1 : -1); double A = -sgnR * pow (fabs (R) + sqrt (R2 - Q3), 1.0 / 3.0); double B = Q / A; if (A + B < 0) { GSL_REAL (*z0) = A + B - a / 3; GSL_IMAG (*z0) = 0; GSL_REAL (*z1) = -0.5 * (A + B) - a / 3; GSL_IMAG (*z1) = -(sqrt (3.0) / 2.0) * fabs(A - B); GSL_REAL (*z2) = -0.5 * (A + B) - a / 3; GSL_IMAG (*z2) = (sqrt (3.0) / 2.0) * fabs(A - B); } else { GSL_REAL (*z0) = -0.5 * (A + B) - a / 3; GSL_IMAG (*z0) = -(sqrt (3.0) / 2.0) * fabs(A - B); GSL_REAL (*z1) = -0.5 * (A + B) - a / 3; GSL_IMAG (*z1) = (sqrt (3.0) / 2.0) * fabs(A - B); GSL_REAL (*z2) = A + B - a / 3; GSL_IMAG (*z2) = 0; } return 3; } } sources_5316/external/gsl/gsl_qrng__sobol.c0000664000176700017670000001442311723710247017661 0ustar paulpaul/* Author: G. Jungman */ /* Implementation for Sobol generator. * See * [Bratley+Fox, TOMS 14, 88 (1988)] * [Antonov+Saleev, USSR Comput. Maths. Math. Phys. 19, 252 (1980)] */ #include "gsl__config.h" #include "gsl_qrng.h" /* maximum allowed space dimension */ #define SOBOL_MAX_DIMENSION 40 /* bit count; assumes sizeof(int) >= 32-bit */ #define SOBOL_BIT_COUNT 30 /* prototypes for generator type functions */ static size_t sobol_state_size(unsigned int dimension); static int sobol_init(void * state, unsigned int dimension); static int sobol_get(void * state, unsigned int dimension, double * v); /* global Sobol generator type object */ static const gsl_qrng_type sobol_type = { "sobol", SOBOL_MAX_DIMENSION, sobol_state_size, sobol_init, sobol_get }; const gsl_qrng_type * gsl_qrng_sobol = &sobol_type; /* primitive polynomials in binary encoding */ static const int primitive_polynomials[SOBOL_MAX_DIMENSION] = { 1, 3, 7, 11, 13, 19, 25, 37, 59, 47, 61, 55, 41, 67, 97, 91, 109, 103, 115, 131, 193, 137, 145, 143, 241, 157, 185, 167, 229, 171, 213, 191, 253, 203, 211, 239, 247, 285, 369, 299 }; /* degrees of the primitive polynomials */ static const int degree_table[SOBOL_MAX_DIMENSION] = { 0, 1, 2, 3, 3, 4, 4, 5, 5, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 8, 8, 8 }; /* initial values for direction tables, following * Bratley+Fox, taken from [Sobol+Levitan, preprint 1976] */ static const int v_init[8][SOBOL_MAX_DIMENSION] = { { 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }, { 0, 0, 1, 3, 1, 3, 1, 3, 3, 1, 3, 1, 3, 1, 3, 1, 1, 3, 1, 3, 1, 3, 1, 3, 3, 1, 3, 1, 3, 1, 3, 1, 1, 3, 1, 3, 1, 3, 1, 3 }, { 0, 0, 0, 7, 5, 1, 3, 3, 7, 5, 5, 7, 7, 1, 3, 3, 7, 5, 1, 1, 5, 3, 3, 1, 7, 5, 1, 3, 3, 7, 5, 1, 1, 5, 7, 7, 5, 1, 3, 3 }, { 0, 0, 0, 0, 0, 1, 7, 9, 13, 11, 1, 3, 7, 9, 5, 13, 13, 11, 3, 15, 5, 3, 15, 7, 9, 13, 9, 1, 11, 7, 5, 15, 1, 15, 11, 5, 3, 1, 7, 9 }, { 0, 0, 0, 0, 0, 0, 0, 9, 3, 27, 15, 29, 21, 23, 19, 11, 25, 7, 13, 17, 1, 25, 29, 3, 31, 11, 5, 23, 27, 19, 21, 5, 1, 17, 13, 7, 15, 9, 31, 9 }, { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 37, 33, 7, 5, 11, 39, 63, 27, 17, 15, 23, 29, 3, 21, 13, 31, 25, 9, 49, 33, 19, 29, 11, 19, 27, 15, 25 }, { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 13, 33, 115, 41, 79, 17, 29, 119, 75, 73, 105, 7, 59, 65, 21, 3, 113, 61, 89, 45, 107 }, { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 23, 39 } }; /* Sobol generator state. * sequence_count = number of calls with this generator * last_numerator_vec = last generated numerator vector * last_denominator_inv = 1/denominator for last numerator vector * v_direction = direction number table */ typedef struct { unsigned int sequence_count; double last_denominator_inv; int last_numerator_vec[SOBOL_MAX_DIMENSION]; int v_direction[SOBOL_BIT_COUNT][SOBOL_MAX_DIMENSION]; } sobol_state_t; /* NOTE: I fixed the size for the preliminary implementation. This could/should be relaxed, as an optimization. */ static size_t sobol_state_size(unsigned int dimension) { return sizeof(sobol_state_t); } static int sobol_init(void * state, unsigned int dimension) { sobol_state_t * s_state = (sobol_state_t *) state; unsigned int i_dim; int j, k; int ell; if(dimension < 1 || dimension > SOBOL_MAX_DIMENSION) { return GSL_EINVAL; } /* Initialize direction table in dimension 0. */ for(k=0; kv_direction[k][0] = 1; /* Initialize in remaining dimensions. */ for(i_dim=1; i_dim= 0; k--) { includ[k] = ((p_i % 2) == 1); p_i /= 2; } /* Leading elements for dimension i come from v_init[][]. */ for(j=0; jv_direction[j][i_dim] = v_init[j][i_dim]; /* Calculate remaining elements for this dimension, * as explained in Bratley+Fox, section 2. */ for(j=degree_i; jv_direction[j-degree_i][i_dim]; ell = 1; for(k=0; kv_direction[j-k-1][i_dim]); } s_state->v_direction[j][i_dim] = newv; } } /* Multiply columns of v by appropriate power of 2. */ ell = 1; for(j=SOBOL_BIT_COUNT-1-1; j>=0; j--) { ell *= 2; for(i_dim=0; i_dimv_direction[j][i_dim] *= ell; } } /* 1/(common denominator of the elements in v_direction) */ s_state->last_denominator_inv = 1.0 /(2.0 * ell); /* final setup */ s_state->sequence_count = 0; for(i_dim=0; i_dimlast_numerator_vec[i_dim] = 0; return GSL_SUCCESS; } static int sobol_get(void * state, unsigned int dimension, double * v) { sobol_state_t * s_state = (sobol_state_t *) state; unsigned int i_dimension; /* Find the position of the least-significant zero in count. */ int ell = 0; int c = s_state->sequence_count; while(1) { ++ell; if((c % 2) == 1) c /= 2; else break; } /* Check for exhaustion. */ if(ell > SOBOL_BIT_COUNT) return GSL_EFAILED; /* FIXME: good return code here */ for(i_dimension=0; i_dimensionv_direction[ell-1][i_dimension]; const int old_numerator_i = s_state->last_numerator_vec[i_dimension]; const int new_numerator_i = old_numerator_i ^ direction_i; s_state->last_numerator_vec[i_dimension] = new_numerator_i; v[i_dimension] = new_numerator_i * s_state->last_denominator_inv; } s_state->sequence_count++; return GSL_SUCCESS; } sources_5316/external/gsl/gsl_specfunc__airy_der.c0000664000176700017670000006211211723710247021176 0ustar paulpaul/* specfunc/airy_der.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_airy.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval_mode.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC aide.f, bide.f, aid.f, bid.f, r9admp.f */ /* series for aif on the interval -1.00000e+00 to 1.00000e+00 with weighted error 5.22e-18 log weighted error 17.28 significant figures required 16.01 decimal places required 17.73 */ static double aif_data[8] = { 0.10527461226531408809, 0.01183613628152997844, 0.00012328104173225664, 0.00000062261225638140, 0.00000000185298887844, 0.00000000000363328873, 0.00000000000000504622, 0.00000000000000000522 }; static cheb_series aif_cs = { aif_data, 7, -1, 1, 7 }; /* series for aig on the interval -1.00000e+00 to 1.00000e+00 with weighted error 3.14e-19 log weighted error 18.50 significant figures required 17.44 decimal places required 18.98 */ static double aig_data[9] = { 0.021233878150918666852, 0.086315930335214406752, 0.001797594720383231358, 0.000014265499875550693, 0.000000059437995283683, 0.000000000152403366479, 0.000000000000264587660, 0.000000000000000331562, 0.000000000000000000314 }; static cheb_series aig_cs = { aig_data, 8, -1, 1, 8 }; /* series for aip2 on the interval 0.00000e+00 to 1.25000e-01 with weighted error 2.15e-17 log weighted error 16.67 significant figures required 14.27 decimal places required 17.26 */ static double aip2_data[15] = { 0.0065457691989713757, 0.0023833724120774592, -0.0000430700770220586, 0.0000015629125858629, -0.0000000815417186163, 0.0000000054103738057, -0.0000000004284130883, 0.0000000000389497963, -0.0000000000039623161, 0.0000000000004428184, -0.0000000000000536297, 0.0000000000000069650, -0.0000000000000009620, 0.0000000000000001403, -0.0000000000000000215 }; static cheb_series aip2_cs = { aip2_data, 14, -1, 1, 9 }; /* series for aip1 on the interval 1.25000e-01 to 1.00000e+00 with weighted error 2.60e-17 log weighted error 16.58 significant figures required 14.91 decimal places required 17.28 */ static double aip1_data[25] = { 0.0358865097808301538, 0.0114668575627764899, -0.0007592073583861400, 0.0000869517610893841, -0.0000128237294298592, 0.0000022062695681038, -0.0000004222295185921, 0.0000000874686415726, -0.0000000192773588418, 0.0000000044668460054, -0.0000000010790108052, 0.0000000002700029447, -0.0000000000696480108, 0.0000000000184489907, -0.0000000000050027817, 0.0000000000013852243, -0.0000000000003908218, 0.0000000000001121536, -0.0000000000000326862, 0.0000000000000096619, -0.0000000000000028935, 0.0000000000000008770, -0.0000000000000002688, 0.0000000000000000832, -0.0000000000000000260 }; static cheb_series aip1_cs = { aip1_data, 24, -1, 1, 14 }; /* series for bif on the interval -1.00000e+00 to 1.00000e+00 with weighted error 9.05e-18 log weighted error 17.04 significant figures required 15.83 decimal places required 17.49 */ static double bif_data[8] = { 0.1153536790828570243, 0.0205007894049192875, 0.0002135290278902876, 0.0000010783960614677, 0.0000000032094708833, 0.0000000000062930407, 0.0000000000000087403, 0.0000000000000000090 }; static cheb_series bif_cs = { bif_data, 7, -1, 1, 7 }; /* series for big on the interval -1.00000e+00 to 1.00000e+00 with weighted error 5.44e-19 log weighted error 18.26 significant figures required 17.46 decimal places required 18.74 */ static double big_data[9] = { -0.097196440416443537390, 0.149503576843167066571, 0.003113525387121326042, 0.000024708570579821297, 0.000000102949627731379, 0.000000000263970373987, 0.000000000000458279271, 0.000000000000000574283, 0.000000000000000000544 }; static cheb_series big_cs = { big_data, 8, -1, 1, 8 }; /* series for bif2 on the interval 1.00000e+00 to 8.00000e+00 with weighted error 3.82e-19 log weighted error 18.42 significant figures required 17.68 decimal places required 18.92 */ static double bif2_data[10] = { 0.323493987603522033521, 0.086297871535563559139, 0.002994025552655397426, 0.000051430528364661637, 0.000000525840250036811, 0.000000003561751373958, 0.000000000017146864007, 0.000000000000061663520, 0.000000000000000171911, 0.000000000000000000382 }; static cheb_series bif2_cs = { bif2_data, 9, -1, 1, 9 }; /* series for big2 on the interval 1.00000e+00 to 8.00000e+00 with weighted error 3.35e-17 log weighted error 16.48 significant figures required 16.52 decimal places required 16.98 */ static double big2_data[10] = { 1.6062999463621294578, 0.7449088819876088652, 0.0470138738610277380, 0.0012284422062548239, 0.0000173222412256624, 0.0000001521901652368, 0.0000000009113560249, 0.0000000000039547918, 0.0000000000000130017, 0.0000000000000000335 }; static cheb_series big2_cs = { big2_data, 9, -1, 1, 9 }; /* series for bip2 on the interval 0.00000e+00 to 1.25000e-01 with weighted error 2.07e-18 log weighted error 17.69 significant figures required 16.51 decimal places required 18.42 */ static double bip2_data[29] = { -0.13269705443526630495, -0.00568443626045977481, -0.00015643601119611610, -0.00001136737203679562, -0.00000143464350991284, -0.00000018098531185164, 0.00000000926177343611, 0.00000001710005490721, 0.00000000476698163504, -0.00000000035195022023, -0.00000000058890614316, -0.00000000006678499608, 0.00000000006395565102, 0.00000000001554529427, -0.00000000000792397000, -0.00000000000258326243, 0.00000000000121655048, 0.00000000000038707207, -0.00000000000022487045, -0.00000000000004953477, 0.00000000000004563782, 0.00000000000000332998, -0.00000000000000921750, 0.00000000000000094157, 0.00000000000000167154, -0.00000000000000055134, -0.00000000000000022369, 0.00000000000000017487, 0.00000000000000000207 }; static cheb_series bip2_cs = { bip2_data, 28, -1, 1, 14 }; /* series for bip1 on the interval 1.25000e-01 to 3.53553e-01 with weighted error 1.86e-17 log weighted error 16.73 significant figures required 15.67 decimal places required 17.42 */ static double bip1_data[24] = { -0.1729187351079553719, -0.0149358492984694364, -0.0005471104951678566, 0.0001537966292958408, 0.0000154353476192179, -0.0000065434113851906, 0.0000003728082407879, 0.0000002072078388189, -0.0000000658173336470, 0.0000000074926746354, 0.0000000011101336884, -0.0000000007265140553, 0.0000000001782723560, -0.0000000000217346352, -0.0000000000020302035, 0.0000000000019311827, -0.0000000000006044953, 0.0000000000001209450, -0.0000000000000125109, -0.0000000000000019917, 0.0000000000000015154, -0.0000000000000004977, 0.0000000000000001155, -0.0000000000000000186 }; static cheb_series bip1_cs = { bip1_data, 23, -1, 1, 13 }; /* series for an22 on the interval -1.00000e+00 to -1.25000e-01 with weighted error 3.30e-17 log weighted error 16.48 significant figures required 14.95 decimal places required 17.24 */ static double an22_data[33] = { 0.0537418629629794329, -0.0126661435859883193, -0.0011924334106593007, -0.0002032327627275655, -0.0000446468963075164, -0.0000113359036053123, -0.0000031641352378546, -0.0000009446708886149, -0.0000002966562236472, -0.0000000969118892024, -0.0000000326822538653, -0.0000000113144618964, -0.0000000040042691002, -0.0000000014440333684, -0.0000000005292853746, -0.0000000001967763374, -0.0000000000740800096, -0.0000000000282016314, -0.0000000000108440066, -0.0000000000042074801, -0.0000000000016459150, -0.0000000000006486827, -0.0000000000002574095, -0.0000000000001027889, -0.0000000000000412846, -0.0000000000000166711, -0.0000000000000067657, -0.0000000000000027585, -0.0000000000000011296, -0.0000000000000004645, -0.0000000000000001917, -0.0000000000000000794, -0.0000000000000000330 }; static cheb_series an22_cs = { an22_data, 32, -1, 1, 18 }; /* series for an21 on the interval -1.25000e-01 to -1.56250e-02 with weighted error 3.43e-17 log weighted error 16.47 significant figures required 14.48 decimal places required 17.16 */ static double an21_data[24] = { 0.0198313155263169394, -0.0029376249067087533, -0.0001136260695958196, -0.0000100554451087156, -0.0000013048787116563, -0.0000002123881993151, -0.0000000402270833384, -0.0000000084996745953, -0.0000000019514839426, -0.0000000004783865344, -0.0000000001236733992, -0.0000000000334137486, -0.0000000000093702824, -0.0000000000027130128, -0.0000000000008075954, -0.0000000000002463214, -0.0000000000000767656, -0.0000000000000243883, -0.0000000000000078831, -0.0000000000000025882, -0.0000000000000008619, -0.0000000000000002908, -0.0000000000000000993, -0.0000000000000000343 }; static cheb_series an21_cs = { an21_data, 23, -1, 1, 12 }; /* series for an20 on the interval -1.56250e-02 to 0.00000e+00 with weighted error 4.41e-17 log weighted error 16.36 significant figures required 14.16 decimal places required 16.96 */ static double an20_data[16] = { 0.0126732217145738027, -0.0005212847072615621, -0.0000052672111140370, -0.0000001628202185026, -0.0000000090991442687, -0.0000000007438647126, -0.0000000000795494752, -0.0000000000104050944, -0.0000000000015932426, -0.0000000000002770648, -0.0000000000000535343, -0.0000000000000113062, -0.0000000000000025772, -0.0000000000000006278, -0.0000000000000001621, -0.0000000000000000441 }; static cheb_series an20_cs = { an20_data, 15, -1, 1, 8 }; /* series for aph2 on the interval -1.00000e+00 to -1.25000e-01 with weighted error 2.94e-17 log weighted error 16.53 significant figures required 15.58 decimal places required 17.28 */ static double aph2_data[32] = { -0.2057088719781465107, 0.0422196961357771922, 0.0020482560511207275, 0.0002607800735165006, 0.0000474824268004729, 0.0000105102756431612, 0.0000026353534014668, 0.0000007208824863499, 0.0000002103236664473, 0.0000000644975634555, 0.0000000205802377264, 0.0000000067836273921, 0.0000000022974015284, 0.0000000007961306765, 0.0000000002813860610, 0.0000000001011749057, 0.0000000000369306738, 0.0000000000136615066, 0.0000000000051142751, 0.0000000000019351689, 0.0000000000007393607, 0.0000000000002849792, 0.0000000000001107281, 0.0000000000000433412, 0.0000000000000170801, 0.0000000000000067733, 0.0000000000000027017, 0.0000000000000010835, 0.0000000000000004367, 0.0000000000000001769, 0.0000000000000000719, 0.0000000000000000294 }; static cheb_series aph2_cs = { aph2_data, 31, -1, 1, 16 }; /* series for aph1 on the interval -1.25000e-01 to -1.56250e-02 with weighted error 6.38e-17 log weighted error 16.20 significant figures required 14.91 decimal places required 16.87 */ static double aph1_data[22] = { -0.1024172908077571694, 0.0071697275146591248, 0.0001209959363122329, 0.0000073361512841220, 0.0000007535382954272, 0.0000001041478171741, 0.0000000174358728519, 0.0000000033399795033, 0.0000000007073075174, 0.0000000001619187515, 0.0000000000394539982, 0.0000000000101192282, 0.0000000000027092778, 0.0000000000007523806, 0.0000000000002156369, 0.0000000000000635283, 0.0000000000000191757, 0.0000000000000059143, 0.0000000000000018597, 0.0000000000000005950, 0.0000000000000001934, 0.0000000000000000638 }; static cheb_series aph1_cs = { aph1_data, 21, -1, 1, 10 }; /* series for aph0 on the interval -1.56250e-02 to 0.00000e+00 with weighted error 2.29e-17 log weighted error 16.64 significant figures required 15.27 decimal places required 17.23 */ static double aph0_data[15] = { -0.0855849241130933257, 0.0011214378867065261, 0.0000042721029353664, 0.0000000817607381483, 0.0000000033907645000, 0.0000000002253264423, 0.0000000000206284209, 0.0000000000023858763, 0.0000000000003301618, 0.0000000000000527010, 0.0000000000000094555, 0.0000000000000018709, 0.0000000000000004024, 0.0000000000000000930, 0.0000000000000000229 }; static cheb_series aph0_cs = { aph0_data, 14, -1, 1, 7 }; static int airy_deriv_mod_phase(const double x, gsl_mode_t mode, gsl_sf_result * ampl, gsl_sf_result * phi) { const double pi34 = 2.356194490192344928847; gsl_sf_result result_a; gsl_sf_result result_p; double a, p; double sqx; double x32; if(x <= -4.0) { double z = 128.0/(x*x*x) + 1.0; cheb_eval_mode_e(&an20_cs, z, mode, &result_a); cheb_eval_mode_e(&aph0_cs, z, mode, &result_p); } else if(x <= -2.0) { double z = (128.0/(x*x*x) + 9.0) / 7.0; cheb_eval_mode_e(&an21_cs, z, mode, &result_a); cheb_eval_mode_e(&aph1_cs, z, mode, &result_p); } else if(x <= -1.0) { double z = (16.0/(x*x*x) + 9.0) / 7.0; cheb_eval_mode_e(&an22_cs, z, mode, &result_a); cheb_eval_mode_e(&aph2_cs, z, mode, &result_p); } else { ampl->val = 0.0; ampl->err = 0.0; phi->val = 0.0; phi->err = 0.0; GSL_ERROR ("x is greater than 1.0", GSL_EDOM); } a = 0.3125 + result_a.val; p = -0.625 + result_p.val; sqx = sqrt(-x); x32 = x*sqx; ampl->val = sqrt(a * sqx); ampl->err = fabs(ampl->val) * (GSL_DBL_EPSILON + fabs(result_a.err/result_a.val)); phi->val = pi34 - x * sqx * p; phi->err = fabs(phi->val) * (GSL_DBL_EPSILON + fabs(result_p.err/result_p.val)); return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_airy_Ai_deriv_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result a; gsl_sf_result p; int status_ap = airy_deriv_mod_phase(x, mode, &a, &p); double c = cos(p.val); result->val = a.val * c; result->err = fabs(result->val * p.err) + fabs(c * a.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return status_ap; } else if(x <= 1.0) { const double x3 = x*x*x; const double x2 = x*x; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&aif_cs, x3, mode, &result_c0); cheb_eval_mode_e(&aig_cs, x3, mode, &result_c1); result->val = (x2*(0.125 + result_c0.val) - result_c1.val) - 0.25; result->err = fabs(x2*result_c0.val) + result_c1.err; result->err += GSL_DBL_EPSILON * fabs(result->val); if(x > GSL_ROOT3_DBL_EPSILON*GSL_ROOT3_DBL_EPSILON) { /* scale only if x is positive */ double s = exp(2.0*x*sqrt(x)/3.0); result->val *= s; result->err *= s; } return GSL_SUCCESS; } else if(x <= 4.0) { const double sqrtx = sqrt(x); const double z = (16.0/(x*sqrtx) - 9.0)/7.0; const double s = sqrt(sqrtx); gsl_sf_result result_c0; cheb_eval_mode_e(&aip1_cs, z, mode, &result_c0); result->val = -(0.28125 + result_c0.val) * s; result->err = result_c0.err * s; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sqrtx = sqrt(x); const double z = 16.0/(x*sqrtx) - 1.0; const double s = sqrt(sqrtx); gsl_sf_result result_c0; cheb_eval_mode_e(&aip2_cs, z, mode, &result_c0); result->val = -(0.28125 + result_c0.val) * s; result->err = result_c0.err * s; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_airy_Ai_deriv_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result a; gsl_sf_result p; int status_ap = airy_deriv_mod_phase(x, mode, &a, &p); double c = cos(p.val); result->val = a.val * c; result->err = fabs(result->val * p.err) + fabs(c * a.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return status_ap; } else if(x < 1.0) { const double x3 = x*x*x; gsl_sf_result result_c1; gsl_sf_result result_c2; cheb_eval_mode_e(&aif_cs, x3, mode, &result_c1); cheb_eval_mode_e(&aig_cs, x3, mode, &result_c2); result->val = (x*x*(0.125 + result_c1.val) - result_c2.val) - 0.25; result->err = fabs(x*x*result_c1.err) + result_c2.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x*x*x < 9.0/4.0 * GSL_LOG_DBL_MIN*GSL_LOG_DBL_MIN) { gsl_sf_result result_aps; const double arg = -2.0*x*sqrt(x)/3.0; const int stat_a = gsl_sf_airy_Ai_deriv_scaled_e(x, mode, &result_aps); const int stat_e = gsl_sf_exp_mult_err_e(arg, 1.5*fabs(arg*GSL_DBL_EPSILON), result_aps.val, result_aps.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_a); } else { UNDERFLOW_ERROR(result); } } int gsl_sf_airy_Bi_deriv_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { const double atr = 8.7506905708484345; /* 16./(sqrt(8)-1) */ const double btr = -2.0938363213560543; /* -(sqrt(8)+1)/(sqrt(8)-1) */ /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result a; gsl_sf_result p; int status_ap = airy_deriv_mod_phase(x, mode, &a, &p); double s = sin(p.val); result->val = a.val * s; result->err = fabs(result->val * p.err) + fabs(s * a.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return status_ap; } else if(x < 1.0) { const double x3 = x*x*x; const double x2 = x*x; gsl_sf_result result_c1; gsl_sf_result result_c2; cheb_eval_mode_e(&bif_cs, x3, mode, &result_c1); cheb_eval_mode_e(&big_cs, x3, mode, &result_c2); result->val = x2 * (result_c1.val + 0.25) + result_c2.val + 0.5; result->err = x2 * result_c1.err + result_c2.err; result->err += GSL_DBL_EPSILON * fabs(result->val); if(x > GSL_ROOT3_DBL_EPSILON*GSL_ROOT3_DBL_EPSILON) { /* scale only if x is positive */ const double s = exp(-2.0*x*sqrt(x)/3.0); result->val *= s; result->err *= s; } return GSL_SUCCESS; } else if(x < 2.0) { const double z = (2.0*x*x*x - 9.0) / 7.0; const double s = exp(-2.0*x*sqrt(x)/3.0); gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&bif2_cs, z, mode, &result_c0); cheb_eval_mode_e(&big2_cs, z, mode, &result_c1); result->val = s * (x*x * (0.25 + result_c0.val) + 0.5 + result_c1.val); result->err = s * (x*x * result_c0.err + result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 4.0) { const double sqrtx = sqrt(x); const double z = atr/(x*sqrtx) + btr; const double s = sqrt(sqrtx); gsl_sf_result result_c0; cheb_eval_mode_e(&bip1_cs, z, mode, &result_c0); result->val = s * (0.625 + result_c0.val); result->err = s * result_c0.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sqrtx = sqrt(x); const double z = 16.0/(x*sqrtx) - 1.0; const double s = sqrt(sqrtx); gsl_sf_result result_c0; cheb_eval_mode_e(&bip2_cs, z, mode, &result_c0); result->val = s * (0.625 + result_c0.val); result->err = s * result_c0.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_airy_Bi_deriv_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result a; gsl_sf_result p; int status_ap = airy_deriv_mod_phase(x, mode, &a, &p); double s = sin(p.val); result->val = a.val * s; result->err = fabs(result->val * p.err) + fabs(s * a.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return status_ap; } else if(x < 1.0) { const double x3 = x*x*x; const double x2 = x*x; gsl_sf_result result_c1; gsl_sf_result result_c2; cheb_eval_mode_e(&bif_cs, x3, mode, &result_c1); cheb_eval_mode_e(&big_cs, x3, mode, &result_c2); result->val = x2 * (result_c1.val + 0.25) + result_c2.val + 0.5; result->err = x2 * result_c1.err + result_c2.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 2.0) { const double z = (2.0*x*x*x - 9.0) / 7.0; gsl_sf_result result_c1; gsl_sf_result result_c2; cheb_eval_mode_e(&bif2_cs, z, mode, &result_c1); cheb_eval_mode_e(&big2_cs, z, mode, &result_c2); result->val = x*x * (result_c1.val + 0.25) + result_c2.val + 0.5; result->err = x*x * result_c1.err + result_c2.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < GSL_ROOT3_DBL_MAX*GSL_ROOT3_DBL_MAX) { gsl_sf_result result_bps; const double arg = 2.0*(x*sqrt(x)/3.0); int stat_b = gsl_sf_airy_Bi_deriv_scaled_e(x, mode, &result_bps); int stat_e = gsl_sf_exp_mult_err_e(arg, 1.5*fabs(arg*GSL_DBL_EPSILON), result_bps.val, result_bps.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_b); } else { OVERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_airy_Ai_deriv_scaled(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Ai_deriv_scaled_e(x, mode, &result)); } double gsl_sf_airy_Ai_deriv(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Ai_deriv_e(x, mode, &result)); } double gsl_sf_airy_Bi_deriv_scaled(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Bi_deriv_scaled_e(x, mode, &result)); } double gsl_sf_airy_Bi_deriv(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Bi_deriv_e(x, mode, &result)); } sources_5316/external/gsl/gsl_vector__prop_source.c0000664000176700017670000000457411723710247021444 0ustar paulpaul/* vector/prop_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_vector, isnull) (const TYPE (gsl_vector) * v) { const size_t n = v->size; const size_t stride = v->stride ; size_t j; for (j = 0; j < n; j++) { size_t k; for (k = 0; k < MULTIPLICITY; k++) { if (v->data[MULTIPLICITY * stride * j + k] != 0.0) { return 0; } } } return 1; } int FUNCTION (gsl_vector, ispos) (const TYPE (gsl_vector) * v) { const size_t n = v->size; const size_t stride = v->stride ; size_t j; for (j = 0; j < n; j++) { size_t k; for (k = 0; k < MULTIPLICITY; k++) { if (v->data[MULTIPLICITY * stride * j + k] <= 0.0) { return 0; } } } return 1; } int FUNCTION (gsl_vector, isneg) (const TYPE (gsl_vector) * v) { const size_t n = v->size; const size_t stride = v->stride ; size_t j; for (j = 0; j < n; j++) { size_t k; for (k = 0; k < MULTIPLICITY; k++) { if (v->data[MULTIPLICITY * stride * j + k] >= 0.0) { return 0; } } } return 1; } int FUNCTION (gsl_vector, isnonneg) (const TYPE (gsl_vector) * v) { const size_t n = v->size; const size_t stride = v->stride ; size_t j; for (j = 0; j < n; j++) { size_t k; for (k = 0; k < MULTIPLICITY; k++) { if (v->data[MULTIPLICITY * stride * j + k] < 0.0) { return 0; } } } return 1; } sources_5316/external/gsl/gsl_fft__c_pass_n.c0000664000176700017670000001374011723710247020141 0ustar paulpaul/* fft/c_pass_n.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int FUNCTION(fft_complex,pass_n) (BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t factor, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]) { size_t i = 0, j = 0; size_t k, k1; const size_t m = n / factor; const size_t q = n / product; const size_t p_1 = product / factor; const size_t jump = (factor - 1) * p_1; size_t e, e1; for (i = 0; i < m; i++) { REAL(out,ostride,i) = REAL(in,istride,i); IMAG(out,ostride,i) = IMAG(in,istride,i); } for (e = 1; e < (factor - 1) / 2 + 1; e++) { for (i = 0; i < m; i++) { const size_t idx = i + e * m; const size_t idxc = i + (factor - e) * m; REAL(out,ostride,idx) = REAL(in,istride,idx) + REAL(in,istride,idxc); IMAG(out,ostride,idx) = IMAG(in,istride,idx) + IMAG(in,istride,idxc); REAL(out,ostride,idxc) = REAL(in,istride,idx) - REAL(in,istride,idxc); IMAG(out,ostride,idxc) = IMAG(in,istride,idx) - IMAG(in,istride,idxc); } } /* e = 0 */ for (i=0 ; i #include "gsl_sf_gamma.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The poisson distribution has the form p(n) = (mu^n / n!) exp(-mu) for n = 0, 1, 2, ... . The method used here is the one from Knuth. */ unsigned int gsl_ran_poisson (const gsl_rng * r, double mu) { double emu; double prod = 1.0; unsigned int k = 0; while (mu > 10) { unsigned int m = mu * (7.0 / 8.0); double X = gsl_ran_gamma_int (r, m); if (X >= mu) { return k + gsl_ran_binomial (r, mu / X, m - 1); } else { k += m; mu -= X; } } /* This following method works well when mu is small */ emu = exp (-mu); do { prod *= gsl_rng_uniform (r); k++; } while (prod > emu); return k - 1; } void gsl_ran_poisson_array (const gsl_rng * r, size_t n, unsigned int array[], double mu) { size_t i; for (i = 0; i < n; i++) { array[i] = gsl_ran_poisson (r, mu); } return; } double gsl_ran_poisson_pdf (const unsigned int k, const double mu) { double p; double lf = gsl_sf_lnfact (k); p = exp (log (mu) * k - lf - mu); return p; } sources_5316/external/gsl/gsl_specfunc__laguerre.c0000664000176700017670000002336511723710247021215 0ustar paulpaul/* specfunc/laguerre.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_laguerre.h" #include "gsl_specfunc__error.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on the large 2b-4a asymptotic for 1F1 * [Abramowitz+Stegun, 13.5.21] * L^a_n(x) = (a+1)_n / n! 1F1(-n,a+1,x) * * The second term (ser_term2) is from Slater,"The Confluent * Hypergeometric Function" p.73. I think there may be an error in * the first term of the expression given there, comparing with AS * 13.5.21 (cf sin(a\pi+\Theta) vs sin(a\pi) + sin(\Theta)) - but the * second term appears correct. * */ static int laguerre_large_n(const int n, const double alpha, const double x, gsl_sf_result * result) { const double a = -n; const double b = alpha + 1.0; const double eta = 2.0*b - 4.0*a; const double cos2th = x/eta; const double sin2th = 1.0 - cos2th; const double eps = asin(sqrt(cos2th)); /* theta = pi/2 - eps */ const double pre_h = 0.25*M_PI*M_PI*eta*eta*cos2th*sin2th; gsl_sf_result lg_b; gsl_sf_result lnfact; int stat_lg = gsl_sf_lngamma_e(b+n, &lg_b); int stat_lf = gsl_sf_lnfact_e(n, &lnfact); double pre_term1 = 0.5*(1.0-b)*log(0.25*x*eta); double pre_term2 = 0.25*log(pre_h); double lnpre_val = lg_b.val - lnfact.val + 0.5*x + pre_term1 - pre_term2; double lnpre_err = lg_b.err + lnfact.err + GSL_DBL_EPSILON * (fabs(pre_term1)+fabs(pre_term2)); double phi1 = 0.25*eta*(2*eps + sin(2.0*eps)); double ser_term1 = -sin(phi1); double A1 = (1.0/12.0)*(5.0/(4.0*sin2th)+(3.0*b*b-6.0*b+2.0)*sin2th - 1.0); double ser_term2 = -A1 * cos(phi1)/(0.25*eta*sin(2.0*eps)); double ser_val = ser_term1 + ser_term2; double ser_err = ser_term2*ser_term2 + GSL_DBL_EPSILON * (fabs(ser_term1) + fabs(ser_term2)); int stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, ser_val, ser_err, result); result->err += 2.0 * GSL_SQRT_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_e, stat_lf, stat_lg); } /* Evaluate polynomial based on confluent hypergeometric representation. * * L^a_n(x) = (a+1)_n / n! 1F1(-n,a+1,x) * * assumes n > 0 and a != negative integer greater than -n */ static int laguerre_n_cp(const int n, const double a, const double x, gsl_sf_result * result) { gsl_sf_result lnfact; gsl_sf_result lg1; gsl_sf_result lg2; double s1, s2; int stat_f = gsl_sf_lnfact_e(n, &lnfact); int stat_g1 = gsl_sf_lngamma_sgn_e(a+1.0+n, &lg1, &s1); int stat_g2 = gsl_sf_lngamma_sgn_e(a+1.0, &lg2, &s2); double poly_1F1_val = 1.0; double poly_1F1_err = 0.0; int stat_e; int k; double lnpre_val = (lg1.val - lg2.val) - lnfact.val; double lnpre_err = lg1.err + lg2.err + lnfact.err + 2.0 * GSL_DBL_EPSILON * fabs(lnpre_val); for(k=n-1; k>=0; k--) { double t = (-n+k)/(a+1.0+k) * (x/(k+1)); double r = t + 1.0/poly_1F1_val; if(r > 0.9*GSL_DBL_MAX/poly_1F1_val) { /* internal error only, don't call the error handler */ INTERNAL_OVERFLOW_ERROR(result); } else { /* Collect the Horner terms. */ poly_1F1_val = 1.0 + t * poly_1F1_val; poly_1F1_err += GSL_DBL_EPSILON + fabs(t) * poly_1F1_err; } } stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, poly_1F1_val, poly_1F1_err, result); return GSL_ERROR_SELECT_4(stat_e, stat_f, stat_g1, stat_g2); } /* Evaluate the polynomial based on the confluent hypergeometric * function in a safe way, with no restriction on the arguments. * * assumes x != 0 */ static int laguerre_n_poly_safe(const int n, const double a, const double x, gsl_sf_result * result) { const double b = a + 1.0; const double mx = -x; const double tc_sgn = (x < 0.0 ? 1.0 : (GSL_IS_ODD(n) ? -1.0 : 1.0)); gsl_sf_result tc; int stat_tc = gsl_sf_taylorcoeff_e(n, fabs(x), &tc); if(stat_tc == GSL_SUCCESS) { double term = tc.val * tc_sgn; double sum_val = term; double sum_err = tc.err; int k; for(k=n-1; k>=0; k--) { term *= ((b+k)/(n-k))*(k+1.0)/mx; sum_val += term; sum_err += 4.0 * GSL_DBL_EPSILON * fabs(term); } result->val = sum_val; result->err = sum_err + 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(stat_tc == GSL_EOVRFLW) { result->val = 0.0; /* FIXME: should be Inf */ result->err = 0.0; return stat_tc; } else { result->val = 0.0; result->err = 0.0; return stat_tc; } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_laguerre_1_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { result->val = 1.0 + a - x; result->err = 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(a) + fabs(x)); return GSL_SUCCESS; } } int gsl_sf_laguerre_2_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(a == -2.0) { result->val = 0.5*x*x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double c0 = 0.5 * (2.0+a)*(1.0+a); double c1 = -(2.0+a); double c2 = -0.5/(2.0+a); result->val = c0 + c1*x*(1.0 + c2*x); result->err = 2.0 * GSL_DBL_EPSILON * (fabs(c0) + 2.0 * fabs(c1*x) * (1.0 + 2.0 * fabs(c2*x))); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_laguerre_3_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(a == -2.0) { double x2_6 = x*x/6.0; result->val = x2_6 * (3.0 - x); result->err = x2_6 * (3.0 + fabs(x)) * 2.0 * GSL_DBL_EPSILON; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(a == -3.0) { result->val = -x*x/6.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double c0 = (3.0+a)*(2.0+a)*(1.0+a) / 6.0; double c1 = -c0 * 3.0 / (1.0+a); double c2 = -1.0/(2.0+a); double c3 = -1.0/(3.0*(3.0+a)); result->val = c0 + c1*x*(1.0 + c2*x*(1.0 + c3*x)); result->err = 1.0 + 2.0 * fabs(c3*x); result->err = 1.0 + 2.0 * fabs(c2*x) * result->err; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(c0) + 2.0 * fabs(c1*x) * result->err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_laguerre_n_e(const int n, const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n < 0) { DOMAIN_ERROR(result); } else if(n == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(n == 1) { result->val = 1.0 + a - x; result->err = 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(a) + fabs(x)); return GSL_SUCCESS; } else if(x == 0.0) { double product = a + 1.0; int k; for(k=2; k<=n; k++) { product *= (a + k)/k; } result->val = product; result->err = 2.0 * (n + 1.0) * GSL_DBL_EPSILON * fabs(product) + GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < 0.0 && a > -1.0) { /* In this case all the terms in the polynomial * are of the same sign. Note that this also * catches overflows correctly. */ return laguerre_n_cp(n, a, x, result); } else if(n < 5 || (x > 0.0 && a < -n-1)) { /* Either the polynomial will not lose too much accuracy * or all the terms are negative. In any case, * the error estimate here is good. We try both * explicit summation methods, as they have different * characteristics. One may underflow/overflow while the * other does not. */ if(laguerre_n_cp(n, a, x, result) == GSL_SUCCESS) return GSL_SUCCESS; else return laguerre_n_poly_safe(n, a, x, result); } else if(n > 1.0e+07 && x > 0.0 && a > -1.0 && x < 2.0*(a+1.0)+4.0*n) { return laguerre_large_n(n, a, x, result); } else if(a >= 0.0 || (x > 0.0 && a < -n-1)) { gsl_sf_result lg2; int stat_lg2 = gsl_sf_laguerre_2_e(a, x, &lg2); double Lkm1 = 1.0 + a - x; double Lk = lg2.val; double Lkp1; int k; for(k=2; kval = Lk; result->err = (fabs(lg2.err/lg2.val) + GSL_DBL_EPSILON) * n * fabs(Lk); return stat_lg2; } else { /* Despair... or magic? */ return laguerre_n_poly_safe(n, a, x, result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_laguerre_1(double a, double x) { EVAL_RESULT(gsl_sf_laguerre_1_e(a, x, &result)); } double gsl_sf_laguerre_2(double a, double x) { EVAL_RESULT(gsl_sf_laguerre_2_e(a, x, &result)); } double gsl_sf_laguerre_3(double a, double x) { EVAL_RESULT(gsl_sf_laguerre_3_e(a, x, &result)); } double gsl_sf_laguerre_n(int n, double a, double x) { EVAL_RESULT(gsl_sf_laguerre_n_e(n, a, x, &result)); } sources_5316/external/gsl/gsl_integration__qmomof.c0000664000176700017670000002141011723710247021407 0ustar paulpaul/* integration/qmomof.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_integration.h" #include "gsl_errno.h" static void compute_moments (double par, double * cheb); static int dgtsl (size_t n, double *c, double *d, double *e, double *b); gsl_integration_qawo_table * gsl_integration_qawo_table_alloc (double omega, double L, enum gsl_integration_qawo_enum sine, size_t n) { gsl_integration_qawo_table *t; double * chebmo; if (n == 0) { GSL_ERROR_VAL ("table length n must be positive integer", GSL_EDOM, 0); } t = (gsl_integration_qawo_table *) malloc (sizeof (gsl_integration_qawo_table)); if (t == 0) { GSL_ERROR_VAL ("failed to allocate space for qawo_table struct", GSL_ENOMEM, 0); } chebmo = (double *) malloc (25 * n * sizeof (double)); if (chebmo == 0) { free (t); GSL_ERROR_VAL ("failed to allocate space for chebmo block", GSL_ENOMEM, 0); } t->n = n; t->sine = sine; t->omega = omega; t->L = L; t->par = 0.5 * omega * L; t->chebmo = chebmo; /* precompute the moments */ { size_t i; double scale = 1.0; for (i = 0 ; i < t->n; i++) { compute_moments (t->par * scale, t->chebmo + 25*i); scale *= 0.5; } } return t; } int gsl_integration_qawo_table_set (gsl_integration_qawo_table * t, double omega, double L, enum gsl_integration_qawo_enum sine) { t->omega = omega; t->sine = sine; t->L = L; t->par = 0.5 * omega * L; /* recompute the moments */ { size_t i; double scale = 1.0; for (i = 0 ; i < t->n; i++) { compute_moments (t->par * scale, t->chebmo + 25*i); scale *= 0.5; } } return GSL_SUCCESS; } int gsl_integration_qawo_table_set_length (gsl_integration_qawo_table * t, double L) { /* return immediately if the length is the same as the old length */ if (L == t->L) return GSL_SUCCESS; /* otherwise reset the table and compute the new parameters */ t->L = L; t->par = 0.5 * t->omega * L; /* recompute the moments */ { size_t i; double scale = 1.0; for (i = 0 ; i < t->n; i++) { compute_moments (t->par * scale, t->chebmo + 25*i); scale *= 0.5; } } return GSL_SUCCESS; } void gsl_integration_qawo_table_free (gsl_integration_qawo_table * t) { free (t->chebmo); free (t); } static void compute_moments (double par, double *chebmo) { double v[28], d[25], d1[25], d2[25]; const size_t noeq = 25; const double par2 = par * par; const double par4 = par2 * par2; const double par22 = par2 + 2.0; const double sinpar = sin (par); const double cospar = cos (par); size_t i; /* compute the chebyschev moments with respect to cosine */ double ac = 8 * cospar; double as = 24 * par * sinpar; v[0] = 2 * sinpar / par; v[1] = (8 * cospar + (2 * par2 - 8) * sinpar / par) / par2; v[2] = (32 * (par2 - 12) * cospar + (2 * ((par2 - 80) * par2 + 192) * sinpar) / par) / par4; if (fabs (par) <= 24) { /* compute the moments as the solution of a boundary value problem using the asyptotic expansion as an endpoint */ double an2, ass, asap; double an = 6; size_t k; for (k = 0; k < noeq - 1; k++) { an2 = an * an; d[k] = -2 * (an2 - 4) * (par22 - 2 * an2); d2[k] = (an - 1) * (an - 2) * par2; d1[k + 1] = (an + 3) * (an + 4) * par2; v[k + 3] = as - (an2 - 4) * ac; an = an + 2.0; } an2 = an * an; d[noeq - 1] = -2 * (an2 - 4) * (par22 - 2 * an2); v[noeq + 2] = as - (an2 - 4) * ac; v[3] = v[3] - 56 * par2 * v[2]; ass = par * sinpar; asap = (((((210 * par2 - 1) * cospar - (105 * par2 - 63) * ass) / an2 - (1 - 15 * par2) * cospar + 15 * ass) / an2 - cospar + 3 * ass) / an2 - cospar) / an2; v[noeq + 2] = v[noeq + 2] - 2 * asap * par2 * (an - 1) * (an - 2); dgtsl (noeq, d1, d, d2, v + 3); } else { /* compute the moments by forward recursion */ size_t k; double an = 4; for (k = 3; k < 13; k++) { double an2 = an * an; v[k] = ((an2 - 4) * (2 * (par22 - 2 * an2) * v[k - 1] - ac) + as - par2 * (an + 1) * (an + 2) * v[k - 2]) / (par2 * (an - 1) * (an - 2)); an = an + 2.0; } } for (i = 0; i < 13; i++) { chebmo[2 * i] = v[i]; } /* compute the chebyschev moments with respect to sine */ v[0] = 2 * (sinpar - par * cospar) / par2; v[1] = (18 - 48 / par2) * sinpar / par2 + (-2 + 48 / par2) * cospar / par; ac = -24 * par * cospar; as = -8 * sinpar; if (fabs (par) <= 24) { /* compute the moments as the solution of a boundary value problem using the asyptotic expansion as an endpoint */ size_t k; double an2, ass, asap; double an = 5; for (k = 0; k < noeq - 1; k++) { an2 = an * an; d[k] = -2 * (an2 - 4) * (par22 - 2 * an2); d2[k] = (an - 1) * (an - 2) * par2; d1[k + 1] = (an + 3) * (an + 4) * par2; v[k + 2] = ac + (an2 - 4) * as; an = an + 2.0; } an2 = an * an; d[noeq - 1] = -2 * (an2 - 4) * (par22 - 2 * an2); v[noeq + 1] = ac + (an2 - 4) * as; v[2] = v[2] - 42 * par2 * v[1]; ass = par * cospar; asap = (((((105 * par2 - 63) * ass - (210 * par2 - 1) * sinpar) / an2 + (15 * par2 - 1) * sinpar - 15 * ass) / an2 - sinpar - 3 * ass) / an2 - sinpar) / an2; v[noeq + 1] = v[noeq + 1] - 2 * asap * par2 * (an - 1) * (an - 2); dgtsl (noeq, d1, d, d2, v + 2); } else { /* compute the moments by forward recursion */ size_t k; double an = 3; for (k = 2; k < 12; k++) { double an2 = an * an; v[k] = ((an2 - 4) * (2 * (par22 - 2 * an2) * v[k - 1] + as) + ac - par2 * (an + 1) * (an + 2) * v[k - 2]) / (par2 * (an - 1) * (an - 2)); an = an + 2.0; } } for (i = 0; i < 12; i++) { chebmo[2 * i + 1] = v[i]; } } static int dgtsl (size_t n, double *c, double *d, double *e, double *b) { /* solves a tridiagonal matrix A x = b c[1 .. n - 1] subdiagonal of the matrix A d[0 .. n - 1] diagonal of the matrix A e[0 .. n - 2] superdiagonal of the matrix A b[0 .. n - 1] right hand side, replaced by the solution vector x */ size_t k; c[0] = d[0]; if (n == 0) { return GSL_SUCCESS; } if (n == 1) { b[0] = b[0] / d[0] ; return GSL_SUCCESS; } d[0] = e[0]; e[0] = 0; e[n - 1] = 0; for (k = 0; k < n - 1; k++) { size_t k1 = k + 1; if (fabs (c[k1]) >= fabs (c[k])) { { double t = c[k1]; c[k1] = c[k]; c[k] = t; }; { double t = d[k1]; d[k1] = d[k]; d[k] = t; }; { double t = e[k1]; e[k1] = e[k]; e[k] = t; }; { double t = b[k1]; b[k1] = b[k]; b[k] = t; }; } if (c[k] == 0) { return GSL_FAILURE ; } { double t = -c[k1] / c[k]; c[k1] = d[k1] + t * d[k]; d[k1] = e[k1] + t * e[k]; e[k1] = 0; b[k1] = b[k1] + t * b[k]; } } if (c[n - 1] == 0) { return GSL_FAILURE; } b[n - 1] = b[n - 1] / c[n - 1]; b[n - 2] = (b[n - 2] - d[n - 2] * b[n - 1]) / c[n - 2]; for (k = n ; k > 2; k--) { size_t kb = k - 3; b[kb] = (b[kb] - d[kb] * b[kb + 1] - e[kb] * b[kb + 2]) / c[kb]; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_const.h0000664000176700017670000000201411705263724016504 0ustar paulpaul/* const/gsl_const.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_CONST__ #define __GSL_CONST__ #include "gsl_const_num.h" #include "gsl_const_cgs.h" #include "gsl_const_mks.h" #include "gsl_const_cgsm.h" #include "gsl_const_mksa.h" #endif /* __GSL_CONST__ */ sources_5316/external/gsl/gsl_fft__hc_pass.h0000664000176700017670000000637611705263724020013 0ustar paulpaul/* fft/hc_pass.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl_fft__complex_internal.h" static void FUNCTION(fft_halfcomplex,pass_2) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]); static void FUNCTION(fft_halfcomplex,pass_3) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[]); static void FUNCTION(fft_halfcomplex,pass_4) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[]); static void FUNCTION(fft_halfcomplex,pass_5) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[]); static void FUNCTION(fft_halfcomplex,pass_n) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t factor, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]); sources_5316/external/gsl/gsl_cblas__cher2.c0000664000176700017670000000055711723710247017666 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cher2 (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda) { #define BASE float #include "gsl_cblas__source_her2.h" #undef BASE } sources_5316/external/gsl/gsl_vector__reim.c0000664000176700017670000000201511723710247020024 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_vector.h" #include "gsl_vector__view.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__reim_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__reim_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__reim_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define USE_QUALIFIER #define QUALIFIER const #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__reim_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__reim_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__reim_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT sources_5316/external/gsl/gsl_sort_vector_float.h0000664000176700017670000000342411705263724021122 0ustar paulpaul/* sort/gsl_sort_vector_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_FLOAT_H__ #define __GSL_SORT_VECTOR_FLOAT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_float.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_float (gsl_vector_float * v); int gsl_sort_vector_float_index (gsl_permutation * p, const gsl_vector_float * v); int gsl_sort_vector_float_smallest (float * dest, const size_t k, const gsl_vector_float * v); int gsl_sort_vector_float_largest (float * dest, const size_t k, const gsl_vector_float * v); int gsl_sort_vector_float_smallest_index (size_t * p, const size_t k, const gsl_vector_float * v); int gsl_sort_vector_float_largest_index (size_t * p, const size_t k, const gsl_vector_float * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_FLOAT_H__ */ sources_5316/external/gsl/gsl_cblas__izamax.c0000664000176700017670000000033511723710247020146 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" CBLAS_INDEX cblas_izamax (const int N, const void *X, const int incX) { #define BASE double #include "gsl_cblas__source_iamax_c.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__bessel_temme.c0000664000176700017670000001431411723710247022045 0ustar paulpaul/* specfunc/bessel_temme.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Calculate series for Y_nu and K_nu for small x and nu. * This is applicable for x < 2 and |nu|<=1/2. * These functions assume x > 0. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_mode.h" #include "gsl_specfunc__bessel_temme.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /* nu = (x+1)/4, -1val = -sum0; Ynu->err = (2.0 + 0.5*k) * GSL_DBL_EPSILON * fabs(Ynu->val); Ynup1->val = -sum1 * 2.0/x; Ynup1->err = (2.0 + 0.5*k) * GSL_DBL_EPSILON * fabs(Ynup1->val); stat_iter = ( k >= max_iter ? GSL_EMAXITER : GSL_SUCCESS ); return GSL_ERROR_SELECT_2(stat_iter, stat_g); } int gsl_sf_bessel_K_scaled_temme(const double nu, const double x, double * K_nu, double * K_nup1, double * Kp_nu) { const int max_iter = 15000; const double half_x = 0.5 * x; const double ln_half_x = log(half_x); const double half_x_nu = exp(nu*ln_half_x); const double pi_nu = M_PI * nu; const double sigma = -nu * ln_half_x; const double sinrat = (fabs(pi_nu) < GSL_DBL_EPSILON ? 1.0 : pi_nu/sin(pi_nu)); const double sinhrat = (fabs(sigma) < GSL_DBL_EPSILON ? 1.0 : sinh(sigma)/sigma); const double ex = exp(x); double sum0, sum1; double fk, pk, qk, hk, ck; int k = 0; int stat_iter; double g_1pnu, g_1mnu, g1, g2; int stat_g = gsl_sf_temme_gamma(nu, &g_1pnu, &g_1mnu, &g1, &g2); fk = sinrat * (cosh(sigma)*g1 - sinhrat*ln_half_x*g2); pk = 0.5/half_x_nu * g_1pnu; qk = 0.5*half_x_nu * g_1mnu; hk = pk; ck = 1.0; sum0 = fk; sum1 = hk; while(k < max_iter) { double del0; double del1; k++; fk = (k*fk + pk + qk)/(k*k-nu*nu); ck *= half_x*half_x/k; pk /= (k - nu); qk /= (k + nu); hk = -k*fk + pk; del0 = ck * fk; del1 = ck * hk; sum0 += del0; sum1 += del1; if(fabs(del0) < 0.5*fabs(sum0)*GSL_DBL_EPSILON) break; } *K_nu = sum0 * ex; *K_nup1 = sum1 * 2.0/x * ex; *Kp_nu = - *K_nup1 + nu/x * *K_nu; stat_iter = ( k == max_iter ? GSL_EMAXITER : GSL_SUCCESS ); return GSL_ERROR_SELECT_2(stat_iter, stat_g); } sources_5316/external/gsl/gsl_histogram__init.c0000664000176700017670000000747611723710247020546 0ustar paulpaul/* histogram/init.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram.h" gsl_histogram * gsl_histogram_alloc (size_t n) { gsl_histogram *h; if (n == 0) { GSL_ERROR_VAL ("histogram length n must be positive integer", GSL_EDOM, 0); } h = (gsl_histogram *) malloc (sizeof (gsl_histogram)); if (h == 0) { GSL_ERROR_VAL ("failed to allocate space for histogram struct", GSL_ENOMEM, 0); } h->range = (double *) malloc ((n + 1) * sizeof (double)); if (h->range == 0) { free (h); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram ranges", GSL_ENOMEM, 0); } h->bin = (double *) malloc (n * sizeof (double)); if (h->bin == 0) { free (h->range); free (h); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram bins", GSL_ENOMEM, 0); } h->n = n; return h; } static void make_uniform (double range[], size_t n, double xmin, double xmax) { size_t i; for (i = 0; i <= n; i++) { double f1 = ((double) (n-i) / (double) n); double f2 = ((double) i / (double) n); range[i] = f1 * xmin + f2 * xmax; } } gsl_histogram * gsl_histogram_calloc_uniform (const size_t n, const double xmin, const double xmax) { gsl_histogram *h; if (xmin >= xmax) { GSL_ERROR_VAL ("xmin must be less than xmax", GSL_EINVAL, 0); } h = gsl_histogram_calloc (n); if (h == 0) { return h; } make_uniform (h->range, n, xmin, xmax); return h; } gsl_histogram * gsl_histogram_calloc (size_t n) { gsl_histogram * h = gsl_histogram_alloc (n); if (h == 0) { return h; } { size_t i; for (i = 0; i < n + 1; i++) { h->range[i] = i; } for (i = 0; i < n; i++) { h->bin[i] = 0; } } h->n = n; return h; } void gsl_histogram_free (gsl_histogram * h) { free (h->range); free (h->bin); free (h); } /* These initialization functions suggested by Achim Gaedke */ int gsl_histogram_set_ranges_uniform (gsl_histogram * h, double xmin, double xmax) { size_t i; const size_t n = h->n; if (xmin >= xmax) { GSL_ERROR ("xmin must be less than xmax", GSL_EINVAL); } /* initialize ranges */ make_uniform (h->range, n, xmin, xmax); /* clear contents */ for (i = 0; i < n; i++) { h->bin[i] = 0; } return GSL_SUCCESS; } int gsl_histogram_set_ranges (gsl_histogram * h, const double range[], size_t size) { size_t i; const size_t n = h->n; if (size != (n+1)) { GSL_ERROR ("size of range must match size of histogram", GSL_EINVAL); } /* initialize ranges */ for (i = 0; i <= n; i++) { h->range[i] = range[i]; } /* clear contents */ for (i = 0; i < n; i++) { h->bin[i] = 0; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_dht.h0000664000176700017670000000510511705263724016141 0ustar paulpaul/* dht/gsl_dht.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_DHT_H__ #define __GSL_DHT_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_dht_struct { size_t size; /* size of the sample arrays to be transformed */ double nu; /* Bessel function order */ double xmax; /* the upper limit to the x-sampling domain */ double kmax; /* the upper limit to the k-sampling domain */ double * j; /* array of computed J_nu zeros, j_{nu,s} = j[s] */ double * Jjj; /* transform numerator, J_nu(j_i j_m / j_N) */ double * J2; /* transform denominator, J_{nu+1}^2(j_m) */ }; typedef struct gsl_dht_struct gsl_dht; /* Create a new transform object for a given size * sampling array on the domain [0, xmax]. */ gsl_dht * gsl_dht_alloc(size_t size); gsl_dht * gsl_dht_new(size_t size, double nu, double xmax); /* Recalculate a transform object for given values of nu, xmax. * You cannot change the size of the object since the internal * allocation is reused. */ int gsl_dht_init(gsl_dht * t, double nu, double xmax); /* The n'th computed x sample point for a given transform. * 0 <= n <= size-1 */ double gsl_dht_x_sample(const gsl_dht * t, int n); /* The n'th computed k sample point for a given transform. * 0 <= n <= size-1 */ double gsl_dht_k_sample(const gsl_dht * t, int n); /* Free a transform object. */ void gsl_dht_free(gsl_dht * t); /* Perform a transform on a sampled array. * f_in[0] ... f_in[size-1] and similarly for f_out[] */ int gsl_dht_apply(const gsl_dht * t, double * f_in, double * f_out); __END_DECLS #endif /* __GSL_DHT_H__ */ sources_5316/external/gsl/gsl_matrix__file_source.c0000664000176700017670000001043211723710247021373 0ustar paulpaul/* matrix/file_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_matrix, fread) (FILE * stream, TYPE (gsl_matrix) * m) { int status = 0; const size_t size1 = m->size1; const size_t size2 = m->size2; const size_t tda = m->tda; if (tda == size2) /* the rows are contiguous */ { status = FUNCTION (gsl_block, raw_fread) (stream, m->data, size1 * size2, 1); } else { size_t i; for (i = 0 ; i < size1 ; i++) /* read each row separately */ { status = FUNCTION (gsl_block, raw_fread) (stream, m->data + i * tda, size2, 1); if (status) break; } } return status; } int FUNCTION (gsl_matrix, fwrite) (FILE * stream, const TYPE (gsl_matrix) * m) { int status = 0; const size_t size1 = m->size1; const size_t size2 = m->size2; const size_t tda = m->tda; if (tda == size2) /* the rows are contiguous */ { status = FUNCTION (gsl_block, raw_fwrite) (stream, m->data, size1 * size2, 1); } else { size_t i; for (i = 0 ; i < size1 ; i++) /* write each row separately */ { status = FUNCTION (gsl_block, raw_fwrite) (stream, m->data + i * tda, size2, 1); if (status) break; } } return status; } #if !(USES_LONGDOUBLE && !HAVE_PRINTF_LONGDOUBLE) int FUNCTION (gsl_matrix, fprintf) (FILE * stream, const TYPE (gsl_matrix) * m, const char *format) { int status = 0; const size_t size1 = m->size1; const size_t size2 = m->size2; const size_t tda = m->tda; if (tda == size2) /* the rows are contiguous */ { status = FUNCTION (gsl_block, raw_fprintf) (stream, m->data, size1 * size2, 1, format); } else { size_t i; for (i = 0 ; i < size1 ; i++) /* print each row separately */ { status = FUNCTION (gsl_block, raw_fprintf) (stream, m->data + i * tda, size2, 1, format); if (status) break; } } return status; } int FUNCTION (gsl_matrix, fscanf) (FILE * stream, TYPE (gsl_matrix) * m) { int status = 0; const size_t size1 = m->size1; const size_t size2 = m->size2; const size_t tda = m->tda; if (tda == size2) /* the rows are contiguous */ { status = FUNCTION (gsl_block, raw_fscanf) (stream, m->data, size1 * size2, 1); } else { size_t i; for (i = 0 ; i < size1 ; i++) /* scan each row separately */ { status = FUNCTION (gsl_block, raw_fscanf) (stream, m->data + i * tda, size2, 1); if (status) break; } } return status; } #endif sources_5316/external/gsl/gsl_cblas__source_spr2.h0000664000176700017670000000372511705263724021141 0ustar paulpaul/* blas/source_spr2.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; if (N == 0) return; if (alpha == 0.0) return; if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE tmp1 = alpha * X[ix]; const BASE tmp2 = alpha * Y[iy]; INDEX jx = ix; INDEX jy = iy; for (j = i; j < N; j++) { Ap[TPUP(N, i, j)] += tmp1 * Y[jy] + tmp2 * X[jx]; jx += incX; jy += incY; } ix += incX; iy += incY; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE tmp1 = alpha * X[ix]; const BASE tmp2 = alpha * Y[iy]; INDEX jx = OFFSET(N, incX); INDEX jy = OFFSET(N, incY); for (j = 0; j <= i; j++) { Ap[TPLO(N, i, j)] += tmp1 * Y[jy] + tmp2 * X[jx]; jx += incX; jy += incY; } ix += incX; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_randist.h0000664000176700017670000002063311705263724017031 0ustar paulpaul/* randist/gsl_randist.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_RANDIST_H__ #define __GSL_RANDIST_H__ #include "gsl_rng.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS unsigned int gsl_ran_bernoulli (const gsl_rng * r, double p); double gsl_ran_bernoulli_pdf (const unsigned int k, double p); double gsl_ran_beta (const gsl_rng * r, const double a, const double b); double gsl_ran_beta_pdf (const double x, const double a, const double b); unsigned int gsl_ran_binomial (const gsl_rng * r, double p, unsigned int n); unsigned int gsl_ran_binomial_knuth (const gsl_rng * r, double p, unsigned int n); unsigned int gsl_ran_binomial_tpe (const gsl_rng * r, double p, unsigned int n); double gsl_ran_binomial_pdf (const unsigned int k, const double p, const unsigned int n); double gsl_ran_exponential (const gsl_rng * r, const double mu); double gsl_ran_exponential_pdf (const double x, const double mu); double gsl_ran_exppow (const gsl_rng * r, const double a, const double b); double gsl_ran_exppow_pdf (const double x, const double a, const double b); double gsl_ran_cauchy (const gsl_rng * r, const double a); double gsl_ran_cauchy_pdf (const double x, const double a); double gsl_ran_chisq (const gsl_rng * r, const double nu); double gsl_ran_chisq_pdf (const double x, const double nu); void gsl_ran_dirichlet (const gsl_rng * r, const size_t K, const double alpha[], double theta[]); double gsl_ran_dirichlet_pdf (const size_t K, const double alpha[], const double theta[]); double gsl_ran_dirichlet_lnpdf (const size_t K, const double alpha[], const double theta[]); double gsl_ran_erlang (const gsl_rng * r, const double a, const double n); double gsl_ran_erlang_pdf (const double x, const double a, const double n); double gsl_ran_fdist (const gsl_rng * r, const double nu1, const double nu2); double gsl_ran_fdist_pdf (const double x, const double nu1, const double nu2); double gsl_ran_flat (const gsl_rng * r, const double a, const double b); double gsl_ran_flat_pdf (double x, const double a, const double b); double gsl_ran_gamma (const gsl_rng * r, const double a, const double b); double gsl_ran_gamma_int (const gsl_rng * r, const unsigned int a); double gsl_ran_gamma_pdf (const double x, const double a, const double b); double gsl_ran_gamma_mt (const gsl_rng * r, const double a, const double b); double gsl_ran_gamma_knuth (const gsl_rng * r, const double a, const double b); double gsl_ran_gaussian (const gsl_rng * r, const double sigma); double gsl_ran_gaussian_ratio_method (const gsl_rng * r, const double sigma); double gsl_ran_gaussian_ziggurat (const gsl_rng * r, const double sigma); double gsl_ran_gaussian_pdf (const double x, const double sigma); double gsl_ran_ugaussian (const gsl_rng * r); double gsl_ran_ugaussian_ratio_method (const gsl_rng * r); double gsl_ran_ugaussian_pdf (const double x); double gsl_ran_gaussian_tail (const gsl_rng * r, const double a, const double sigma); double gsl_ran_gaussian_tail_pdf (const double x, const double a, const double sigma); double gsl_ran_ugaussian_tail (const gsl_rng * r, const double a); double gsl_ran_ugaussian_tail_pdf (const double x, const double a); void gsl_ran_bivariate_gaussian (const gsl_rng * r, double sigma_x, double sigma_y, double rho, double *x, double *y); double gsl_ran_bivariate_gaussian_pdf (const double x, const double y, const double sigma_x, const double sigma_y, const double rho); double gsl_ran_landau (const gsl_rng * r); double gsl_ran_landau_pdf (const double x); unsigned int gsl_ran_geometric (const gsl_rng * r, const double p); double gsl_ran_geometric_pdf (const unsigned int k, const double p); unsigned int gsl_ran_hypergeometric (const gsl_rng * r, unsigned int n1, unsigned int n2, unsigned int t); double gsl_ran_hypergeometric_pdf (const unsigned int k, const unsigned int n1, const unsigned int n2, unsigned int t); double gsl_ran_gumbel1 (const gsl_rng * r, const double a, const double b); double gsl_ran_gumbel1_pdf (const double x, const double a, const double b); double gsl_ran_gumbel2 (const gsl_rng * r, const double a, const double b); double gsl_ran_gumbel2_pdf (const double x, const double a, const double b); double gsl_ran_logistic (const gsl_rng * r, const double a); double gsl_ran_logistic_pdf (const double x, const double a); double gsl_ran_lognormal (const gsl_rng * r, const double zeta, const double sigma); double gsl_ran_lognormal_pdf (const double x, const double zeta, const double sigma); unsigned int gsl_ran_logarithmic (const gsl_rng * r, const double p); double gsl_ran_logarithmic_pdf (const unsigned int k, const double p); void gsl_ran_multinomial (const gsl_rng * r, const size_t K, const unsigned int N, const double p[], unsigned int n[] ); double gsl_ran_multinomial_pdf (const size_t K, const double p[], const unsigned int n[] ); double gsl_ran_multinomial_lnpdf (const size_t K, const double p[], const unsigned int n[] ); unsigned int gsl_ran_negative_binomial (const gsl_rng * r, double p, double n); double gsl_ran_negative_binomial_pdf (const unsigned int k, const double p, double n); unsigned int gsl_ran_pascal (const gsl_rng * r, double p, unsigned int n); double gsl_ran_pascal_pdf (const unsigned int k, const double p, unsigned int n); double gsl_ran_pareto (const gsl_rng * r, double a, const double b); double gsl_ran_pareto_pdf (const double x, const double a, const double b); unsigned int gsl_ran_poisson (const gsl_rng * r, double mu); void gsl_ran_poisson_array (const gsl_rng * r, size_t n, unsigned int array[], double mu); double gsl_ran_poisson_pdf (const unsigned int k, const double mu); double gsl_ran_rayleigh (const gsl_rng * r, const double sigma); double gsl_ran_rayleigh_pdf (const double x, const double sigma); double gsl_ran_rayleigh_tail (const gsl_rng * r, const double a, const double sigma); double gsl_ran_rayleigh_tail_pdf (const double x, const double a, const double sigma); double gsl_ran_tdist (const gsl_rng * r, const double nu); double gsl_ran_tdist_pdf (const double x, const double nu); double gsl_ran_laplace (const gsl_rng * r, const double a); double gsl_ran_laplace_pdf (const double x, const double a); double gsl_ran_levy (const gsl_rng * r, const double c, const double alpha); double gsl_ran_levy_skew (const gsl_rng * r, const double c, const double alpha, const double beta); double gsl_ran_weibull (const gsl_rng * r, const double a, const double b); double gsl_ran_weibull_pdf (const double x, const double a, const double b); void gsl_ran_dir_2d (const gsl_rng * r, double * x, double * y); void gsl_ran_dir_2d_trig_method (const gsl_rng * r, double * x, double * y); void gsl_ran_dir_3d (const gsl_rng * r, double * x, double * y, double * z); void gsl_ran_dir_nd (const gsl_rng * r, size_t n, double * x); void gsl_ran_shuffle (const gsl_rng * r, void * base, size_t nmembm, size_t size); int gsl_ran_choose (const gsl_rng * r, void * dest, size_t k, void * src, size_t n, size_t size) ; void gsl_ran_sample (const gsl_rng * r, void * dest, size_t k, void * src, size_t n, size_t size) ; typedef struct { /* struct for Walker algorithm */ size_t K; size_t *A; double *F; } gsl_ran_discrete_t; gsl_ran_discrete_t * gsl_ran_discrete_preproc (size_t K, const double *P); void gsl_ran_discrete_free(gsl_ran_discrete_t *g); size_t gsl_ran_discrete (const gsl_rng *r, const gsl_ran_discrete_t *g); double gsl_ran_discrete_pdf (size_t k, const gsl_ran_discrete_t *g); __END_DECLS #endif /* __GSL_RANDIST_H__ */ sources_5316/external/gsl/gsl_cdf__tdist.c0000664000176700017670000001312411723710247017454 0ustar paulpaul/* cdf/tdist.c * * Copyright (C) 2002 Jason H. Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * Computes the Student's t cumulative distribution function using * the method detailed in * * W.J. Kennedy and J.E. Gentle, "Statistical Computing." 1980. * Marcel Dekker. ISBN 0-8247-6898-1. * * G.W. Hill and A.W. Davis. "Generalized asymptotic expansions * of Cornish-Fisher type." Annals of Mathematical Statistics, * vol. 39, 1264-1273. 1968. * * G.W. Hill. "Algorithm 395: Student's t-distribution," Communications * of the ACM, volume 13, number 10, page 617. October 1970. * * G.W. Hill, "Remark on algorithm 395: Student's t-distribution," * Transactions on Mathematical Software, volume 7, number 2, page * 247. June 1982. */ #include "gsl__config.h" #include "gsl_cdf.h" #include "gsl_sf_gamma.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_cdf__beta_inc.c" static double poly_eval (const double c[], unsigned int n, double x) { unsigned int i; double y = c[0] * x; for (i = 1; i < n; i++) { y = x * (y + c[i]); } y += c[n]; return y; } /* * Use the Cornish-Fisher asymptotic expansion to find a point u such * that gsl_cdf_gauss(y) = tcdf(t). * */ static double cornish_fisher (double t, double n) { const double coeffs6[10] = { 0.265974025974025974026, 5.449696969696969696970, 122.20294372294372294372, 2354.7298701298701298701, 37625.00902597402597403, 486996.1392857142857143, 4960870.65, 37978595.55, 201505390.875, 622437908.625 }; const double coeffs5[8] = { 0.2742857142857142857142, 4.499047619047619047619, 78.45142857142857142857, 1118.710714285714285714, 12387.6, 101024.55, 559494.0, 1764959.625 }; const double coeffs4[6] = { 0.3047619047619047619048, 3.752380952380952380952, 46.67142857142857142857, 427.5, 2587.5, 8518.5 }; const double coeffs3[4] = { 0.4, 3.3, 24.0, 85.5 }; double a = n - 0.5; double b = 48.0 * a * a; double z2 = a * log1p (t * t / n); double z = sqrt (z2); double p5 = z * poly_eval (coeffs6, 9, z2); double p4 = -z * poly_eval (coeffs5, 7, z2); double p3 = z * poly_eval (coeffs4, 5, z2); double p2 = -z * poly_eval (coeffs3, 3, z2); double p1 = z * (z2 + 3.0); double p0 = z; double y = p5; y = (y / b) + p4; y = (y / b) + p3; y = (y / b) + p2; y = (y / b) + p1; y = (y / b) + p0; if (t < 0) y *= -1; return y; } #if 0 /* * Series approximation for t > 4.0. This needs to be fixed; * it shouldn't subtract the result from 1.0. A better way is * to use two different series expansions. Figuring this out * means rummaging through Fisher's paper in Metron, v5, 1926, * "Expansion of Student's integral in powers of n^{-1}." */ #define MAXI 40 static double normal_approx (const double x, const double nu) { double y; double num; double diff; double q; int i; double lg1, lg2; y = 1 / sqrt (1 + x * x / nu); num = 1.0; q = 0.0; diff = 2 * GSL_DBL_EPSILON; for (i = 2; (i < MAXI) && (diff > GSL_DBL_EPSILON); i += 2) { diff = q; num *= y * y * (i - 1) / i; q += num / (nu + i); diff = q - diff; } q += 1 / nu; lg1 = gsl_sf_lngamma (nu / 2.0); lg2 = gsl_sf_lngamma ((nu + 1.0) / 2.0); diff = lg2 - lg1; q *= pow (y, nu) * exp (diff) / sqrt (M_PI); return q; } #endif double gsl_cdf_tdist_P (const double x, const double nu) { double P; double x2 = x * x; if (nu > 30 && x2 < 10 * nu) { double u = cornish_fisher (x, nu); P = gsl_cdf_ugaussian_P (u); return P; } if (x2 < nu) { double u = x2 / nu; double eps = u / (1 + u); if (x >= 0) { P = beta_inc_AXPY (0.5, 0.5, 0.5, nu / 2.0, eps); } else { P = beta_inc_AXPY (-0.5, 0.5, 0.5, nu / 2.0, eps); } } else { double v = nu / (x * x); double eps = v / (1 + v); if (x >= 0) { P = beta_inc_AXPY (-0.5, 1.0, nu / 2.0, 0.5, eps); } else { P = beta_inc_AXPY (0.5, 0.0, nu / 2.0, 0.5, eps); } } return P; } double gsl_cdf_tdist_Q (const double x, const double nu) { double Q; double x2 = x * x; if (nu > 30 && x2 < 10 * nu) { double u = cornish_fisher (x, nu); Q = gsl_cdf_ugaussian_Q (u); return Q; } if (x2 < nu) { double u = x2 / nu; double eps = u / (1 + u); if (x >= 0) { Q = beta_inc_AXPY (-0.5, 0.5, 0.5, nu / 2.0, eps); } else { Q = beta_inc_AXPY (0.5, 0.5, 0.5, nu / 2.0, eps); } } else { double v = nu / (x * x); double eps = v / (1 + v); if (x >= 0) { Q = beta_inc_AXPY (0.5, 0.0, nu / 2.0, 0.5, eps); } else { Q = beta_inc_AXPY (-0.5, 1.0, nu / 2.0, 0.5, eps); } } return Q; } sources_5316/external/gsl/gsl_fft__real_init.c0000664000176700017670000001037411723710247020322 0ustar paulpaul/* fft/real_init.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ TYPE(gsl_fft_real_wavetable) * FUNCTION(gsl_fft_real_wavetable,alloc) (size_t n) { int status; size_t i; size_t n_factors; size_t t, product, product_1, q; double d_theta; TYPE(gsl_fft_real_wavetable) * wavetable; if (n == 0) { GSL_ERROR_VAL ("length n must be positive integer", GSL_EDOM, 0); } wavetable = (TYPE(gsl_fft_real_wavetable) *) malloc(sizeof(TYPE(gsl_fft_real_wavetable))); if (wavetable == NULL) { GSL_ERROR_VAL ("failed to allocate struct", GSL_ENOMEM, 0); } if (n == 1) { wavetable->trig = 0; } else { wavetable->trig = (TYPE(gsl_complex) *) malloc ((n / 2) * sizeof (TYPE(gsl_complex))); if (wavetable->trig == NULL) { /* error in constructor, prevent memory leak */ free(wavetable) ; GSL_ERROR_VAL ("failed to allocate trigonometric lookup table", GSL_ENOMEM, 0); } } wavetable->n = n; status = fft_real_factorize (n, &n_factors, wavetable->factor); if (status) { /* error in constructor, prevent memory leak */ free(wavetable->trig); free(wavetable) ; GSL_ERROR_VAL ("factorization failed", GSL_EFACTOR, 0); } wavetable->nf = n_factors; d_theta = 2.0 * M_PI / ((double) n); t = 0; product = 1; for (i = 0; i < wavetable->nf; i++) { size_t j; const size_t factor = wavetable->factor[i]; wavetable->twiddle[i] = wavetable->trig + t; product_1 = product; /* product_1 = p_(i-1) */ product *= factor; q = n / product; for (j = 1; j < factor; j++) { size_t k; size_t m = 0; for (k = 1; k < (product_1 + 1) / 2; k++) { double theta; m = m + j * q; m = m % n; theta = d_theta * m; /* d_theta*j*k*q */ GSL_REAL(wavetable->trig[t]) = cos (theta); GSL_IMAG(wavetable->trig[t]) = sin (theta); t++; } } } if (t > (n / 2)) { /* error in constructor, prevent memory leak */ free(wavetable->trig); free(wavetable) ; GSL_ERROR_VAL ("overflowed trigonometric lookup table", GSL_ESANITY, 0); } return wavetable; } TYPE(gsl_fft_real_workspace) * FUNCTION(gsl_fft_real_workspace,alloc) (size_t n) { TYPE(gsl_fft_real_workspace) * workspace; if (n == 0) { GSL_ERROR_VAL ("length n must be positive integer", GSL_EDOM, 0); } workspace = (TYPE(gsl_fft_real_workspace) *) malloc(sizeof(TYPE(gsl_fft_real_workspace))); if (workspace == NULL) { GSL_ERROR_VAL ("failed to allocate struct", GSL_ENOMEM, 0); } workspace->n = n; workspace->scratch = (BASE *) malloc (n * sizeof (BASE)); if (workspace->scratch == NULL) { /* error in constructor, prevent memory leak */ free(workspace) ; GSL_ERROR_VAL ("failed to allocate scratch space", GSL_ENOMEM, 0); } return workspace; } void FUNCTION(gsl_fft_real_wavetable,free) (TYPE(gsl_fft_real_wavetable) * wavetable) { /* release trigonometric lookup tables */ free (wavetable->trig); wavetable->trig = NULL; free (wavetable) ; } void FUNCTION(gsl_fft_real_workspace,free) (TYPE(gsl_fft_real_workspace) * workspace) { /* release scratch space */ free (workspace->scratch); workspace->scratch = NULL; free (workspace) ; } sources_5316/external/gsl/flatten_gsl.py0000775000176700017670000002677611754441733017246 0ustar paulpaul#!/usr/bin/python # # djmw 20080323, 20120511, 20120515 # # Makes the directory structure of gsl flat by renaming all files and references by #include # E.g. the file 'd/a.c' will be renamed as: gsl_d__a.c # djmw 20100223 New makefile layout # import os, sys, glob, re, time, shutil version = '1.10' date = time.strftime('%Y%m%d') gslconfigh = 'gsl__config.h' fromdir = '/home/david/praat/gsl/gsl-' + version + '/' todir = '/home/david/praat/gsl/GSL-' + version + '/' log = open (todir + 'flatten_gsl' + version + '.log', 'w') gslconfigh = 'gsl__config.h' print >> log, date dirs = ['blas', 'block', 'bspline', 'cblas', 'cdf', 'combination', 'complex', 'const', 'deriv', 'dht', 'diff', 'doc', 'eigen', 'err', 'fft', 'fit', 'gsl', 'histogram', 'ieee-utils', 'integration', 'linalg', 'matrix', 'min', 'monte', 'multifit', 'multimin', 'multiroots', 'ntuple', 'ode-initval', 'permutation', 'poly', 'qrng', 'randist', 'rng', 'roots', 'siman', 'sort', 'specfunc', 'statistics', 'sum', 'sys', 'vector', 'wavelet'] # left out: utils test itype = 0 imake = 1 idist = 2 iname = 3 icount = 4 ihrep = 5 # per file: [type inmakefile indist renamed_as ntimesincluded headerreplacement] # type = c h def write_to_file (todir, basename, multilinetext): f = open (todir + basename, 'w') f.write (multilinetext) f.close() def dict_from_list (dict, dir, list, type = 'c', inmake = 'y', indist = 'y'): for item in list: newname = 'gsl_' + dir + '__' + item if dir == 'gsl': newname = item dict[dir + '/' + item] = [type, inmake, indist, newname, 0 , ''] def get_all_files (dirs): files = {'./config.h': ['h', 'n', 'y', gslconfigh, 0, ''], \ './templates_on.h':['h', 'n', 'y', 'templates_on.h', 0, ''], \ './templates_off.h':['h', 'n', 'y', 'templates_off.h', 0, '']} for dir in dirs: os.chdir (fromdir + dir) dict_from_list (files, dir, glob.glob('*.c'), 'c', 'y') dict_from_list (files, dir, glob.glob('*.h'), 'h', 'n') return files def quoted_include_get_newname (dict, key): if dict.has_key(key): dict[key][imake] = 'n' if dict[key][ihrep]: newname = dict[key][ihrep] dict['gsl/' + newname][icount] += 1 print >> log, 'Corrected an include header error ' + key + ' ' + newname else: newname = dict[key][iname] dict[key][icount] += 1 return '"' + newname + '"' return None # #include ..... # rewrite to "file.h" # -> # "file.(c|h)" -> "gsl_dir__file.(c|h)" def process_files (dict): include = re.compile (r'^(\s*\#\s*include\s+)([^\s]+)') # 2 groups delim = re.compile (r'(<|")\s*([^\s]+)\s*(>|")') for key, val in dict.items(): (dir, base) = os.path.split (key) if dir == '.': # config.h will be/was done by hand, don't overwrite continue file_in_name = fromdir + key file_in = open (file_in_name, 'r') file_out_name = val[iname] output_lines = '' for line in file_in: minclude = include.search (line) if minclude: headerfile = minclude.group(2) mheader = delim.search (headerfile) header = mheader.group(2) if mheader.group(1) == '<': if header[0:4] == 'gsl/': newname = '"' + header[4:] +'"' dict[header][icount] += 1 elif header == 'config.h': newname = '"' + gslconfigh + '"' dict['./'+header][icount] += 1 else: newname = '<' + header + '>' else: newkey = dir + '/' + header newname = quoted_include_get_newname (dict, newkey) if not newname: newkey = './' + header newname = quoted_include_get_newname (dict, newkey) if not newname: newname = header print >> log, 'File does not exist: '+ header + ' From: ' + key output_lines += minclude.group(1) + newname + '\n' else: output_lines += line if val[idist] == 'y': write_to_file (todir, file_out_name, output_lines) else: dict[key][imake] = 'n' return dict def gen_make_objects (dict, suffix, endofline): make_objects = '' (i , imax) = (0, 3) keysd = dict.keys() keysd.sort() for key in keysd: val = dict[key] if val[imake] == 'n': continue i += 1 post = ' ' if i%imax == 0: post = endofline (root, ext) = os.path.splitext (val[iname]) make_objects += root + suffix + post return make_objects def gen_sconscript(dict): make_objects = gen_make_objects (dict, '.c', ' \n ') sconscript = '''# SConscript for library gsl. This file was generated by the program flatten_gsl.py # djmw ''' + date + ''' sources = Split(""" ''' + make_objects + '''""") Import ('env') env.Library ('GSL', sources) # End of SConscript ''' write_to_file (todir, 'SConscript', sconscript) def gen_makefile (dict): make_objects = gen_make_objects (dict, '.o', ' \\\n ') makefile = """# Makefile for library gsl. This file was generated by the program flatten_gsl.py # djmw """ + date + """ include ../makefile.defs CFLAGS = -I ../sys -I ../dwsys OBJECTS = """ + make_objects + """ .PHONY: all clean all: libgsl.a clean: $(RM) $(OBJECTS) $(RM) libgsl.a $(OBJECTS): *.h ../sys/*.h ../dwsys/*.h libgsl.a: $(OBJECTS) touch libgsl.a rm libgsl.a ar cq libgsl.a $(OBJECTS) $(RANLIB) libgsl.a # end of Makefile """ write_to_file (todir, 'Makefile', makefile) def copy_file (fromdir, todir, file): text = open(fromdir + file).read() write_to_file (todir, file, text) def preprocessing (current_gsl_version): if not os.path.exists (todir + gslconfigh): if not os.path.exists (fromdir + 'config.h'): sys.exit(todir + gslconfigh + ' and ' + fromdir + "config.h don't exist. Please run configure first!!") else: text = open(fromdir + 'config.h').read() write_to_file (todir, gslconfigh, text) print >> log, '----------- gsl__config.h created ------------------' copy_file (fromdir,todir, 'templates_on.h') copy_file (fromdir,todir, 'templates_off.h') print >> log, """ Post/Preprocesing The layout of config.h/gsl__config.h varies from one version of gsl to the other Do it by hand in """ + todir + """gsl__config.h: Replace the #define "haves" with #define HAVE_IEEEFP_H 0 #if defined(linux) #define HAVE_DECL_EXPM1 1 #else #define HAVE_DECL_EXPM1 0 #endif #if defined(linux) || defined (_WIN32) #define HAVE_DECL_FINITE 1 #else #define HAVE_DECL_FINITE 0 #endif #if defined(linux) #define HAVE_DECL_HYPOT 1 #else #define HAVE_DECL_HYPOT 0 #endif #if defined(linux) #define HAVE_DECL_ISFINITE 0 #else #define HAVE_DECL_ISFINITE 0 #endif #if defined(linux) #define HAVE_DECL_LOG1P 1 #else #define HAVE_DECL_LOG1P 0 #endif #if defined(linux) #define HAVE_STRDUP 1 #else #define HAVE_STRDUP 0 #endif #if defined(linux) #define HAVE_STRTOL 1 #else #define HAVE_STRTOL 0 #endif #if defined(linux) #define HAVE_STRTOUL 1 #else #define HAVE_STRTOUL 0 #endif #if defined(linux) #define HAVE_DLFCN_H 1 #else #define HAVE_DLFCN_H 0 #endif #if defined(linux) #define HAVE_DECL_FEENABLEEXCEPT 1 #else #define HAVE_DECL_FEENABLEEXCEPT 0 #endif # 3.Inlines: #undef HAVE_INLINE #ifdef sgi #define inline #endif #if defined(linux) || defined (macintosh) || defined (_WIN32) #define HAVE_DECL_ISINF 1 #else #define HAVE_DECL_ISINF 0 #endif #if defined(linux) || defined (macintosh) || defined (_WIN32) #define HAVE_DECL_ISNAN 1 #else #define HAVE_DECL_ISNAN 0 #endif # 4. #if defined(linux) #define HAVE_GNUX86_IEEE_INTERFACE 1 #endif #undef HAVE_GNUSPARC_IEEE_INTERFACE #undef HAVE_GNUM68K_IEEE_INTERFACE #undef HAVE_GNUPPC_IEEE_INTERFACE #undef HAVE_SUNOS4_IEEE_INTERFACE #undef HAVE_SOLARIS_IEEE_INTERFACE #undef HAVE_HPUX11_IEEE_INTERFACE #undef HAVE_HPUX_IEEE_INTERFACE #undef HAVE_TRU64_IEEE_INTERFACE #undef HAVE_IRIX_IEEE_INTERFACE #undef HAVE_AIX_IEEE_INTERFACE #undef HAVE_FREEBSD_IEEE_INTERFACE #undef HAVE_OS2EMX_IEEE_INTERFACE #undef HAVE_NETBSD_IEEE_INTERFACE #undef HAVE_OPENBSD_IEEE_INTERFACE #undef HAVE_DARWIN_IEEE_INTERFACE #undef HAVE_DARWIN86_IEEE_INTERFACE #define GSL_DISABLE_DEPRECATED 1 #define USE_BLAS 0 By hand: Corrected in the fromdir/specfun/coupling.c: #if ! defined (GSL_DISABLE_DEPRECATED) gsl_sf_coupling_6j_INCORRECT_e .... #endif #if ! defined (GSL_DISABLE_DEPRECATED) gsl_sf_coupling_6j_INCORRECT .... #endif """ def post_processing (current_gsl_version): def correct_missing_prototypes (file, linenumber, prototype): f = open (file, 'r') lines = f.readlines () lines.insert (linenumber, prototype + '\n') f.close () f = open (file, 'w') f.writelines (lines) f.close () print >> log, 'Inserted prototype in file '+ file print >> log, ' ' + prototype if current_gsl_version == '1.10': here = todir + '/' correct_missing_prototypes (here + 'gsl_matrix_complex_double.h', 235, \ 'int gsl_matrix_complex_isnonneg (const gsl_matrix_complex * m);') correct_missing_prototypes (here + 'gsl_matrix_complex_float.h', 235, \ 'int gsl_matrix_complex_float_isnonneg (const gsl_matrix_complex_float * m);') correct_missing_prototypes (here + 'gsl_matrix_complex_long_double.h', 235, \ 'int gsl_matrix_complex_long_double_isnonneg (const gsl_matrix_complex_long_double * m);') correct_missing_prototypes (here + 'gsl_vector_complex_double.h', 181, \ 'int gsl_vector_complex_isnonneg (const gsl_vector_complex * v);') correct_missing_prototypes (here + 'gsl_vector_complex_float.h', 181, \ 'int gsl_vector_complex_float_isnonneg (const gsl_vector_complex_float * v);') correct_missing_prototypes (here + 'gsl_vector_complex_long_double.h', 181, \ 'int gsl_vector_complex_long_double_isnonneg (const gsl_vector_complex_long_double * v);') def remove_double_header_files (dict): num = 0 for key,val in dict.items(): (dir, base) = os.path.split (key) if dir == 'gsl': continue newkey = 'gsl/' + base if dict.has_key (newkey): f = open (fromdir + key, 'r') lines1 = f.read() f.close () f = open (fromdir + newkey, 'r') lines2 = f.read() f.close () if lines1 == lines2: num += 1 dict[key][idist] = 'n' dict[key][ihrep] = base print >> log, 'Also in gsl/: ' + key return num def exclude_test_files (dict): starts_with_test = re.compile (r'^test') for key in dict.keys (): (dir, base) = os.path.split (key) if starts_with_test.search (base): dict[key][idist] = 'n' dict['siman/siman_tsp.c'][idist] = 'n' def print_file_selection (dict, type = 'c', inmake = 'n', indist = 'y'): selection = {} for key, val in dict.items(): if val[itype] == type and val[imake] == inmake and val[idist] == indist: selection[key] = val[icount] keyss = selection.keys() keyss.sort() for key in keyss: print >> log, '%3d %s' % (selection[key], key) return len (keyss) preprocessing (version) files = get_all_files (dirs) exclude_test_files (files) print >> log, 'The following header files already exist in the gsl/ directory:' ll = remove_double_header_files (files) print >> log, 'Number of files = %d' % ll print >> log, '\n\n process files' process_files (files) print >> log, '\n\n corect some header files:' post_processing (version) gen_sconscript (files) gen_makefile (files) print >> log, '\n\n header-files' ll = print_file_selection (files, type = 'h') print >> log, 'Number of files = %d' % ll print >> log, '\n\n c-files' ll = print_file_selection (files, type = 'c', inmake = 'y', indist = 'y') print >> log, 'Number of files = %d' % ll print >> log, '\n\n c-files included in other files' ll = print_file_selection (files, type = 'c', inmake = 'n', indist = 'y') print >> log, 'Number of files = %d' % ll print >> log, '\n\n unused header-files' ll = print_file_selection (files, type = 'h', indist = 'n') print >> log, 'Number of files = %d' % ll print >> log, '\n\n unused c-files' ll = print_file_selection (files, type = 'c', indist = 'n') print >> log, 'Number of files = %d' % ll #print str(files) sources_5316/external/gsl/gsl_specfunc__hyperg.c0000664000176700017670000002111611723710247020675 0ustar paulpaul/* specfunc/hyperg.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Miscellaneous implementations of use * for evaluation of hypergeometric functions. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__hyperg.h" #define SUM_LARGE (1.0e-5*GSL_DBL_MAX) int gsl_sf_hyperg_1F1_series_e(const double a, const double b, const double x, gsl_sf_result * result ) { double an = a; double bn = b; double n = 1.0; double del = 1.0; double abs_del = 1.0; double max_abs_del = 1.0; double sum_val = 1.0; double sum_err = 0.0; while(abs_del/fabs(sum_val) > 0.25*GSL_DBL_EPSILON) { double u, abs_u; if(bn == 0.0) { DOMAIN_ERROR(result); } if(an == 0.0) { result->val = sum_val; result->err = sum_err; result->err += 2.0 * GSL_DBL_EPSILON * n * fabs(sum_val); return GSL_SUCCESS; } if (n > 10000.0) { result->val = sum_val; result->err = sum_err; GSL_ERROR ("hypergeometric series failed to converge", GSL_EFAILED); } u = x * (an/(bn*n)); abs_u = fabs(u); if(abs_u > 1.0 && max_abs_del > GSL_DBL_MAX/abs_u) { result->val = sum_val; result->err = fabs(sum_val); GSL_ERROR ("overflow", GSL_EOVRFLW); } del *= u; sum_val += del; if(fabs(sum_val) > SUM_LARGE) { result->val = sum_val; result->err = fabs(sum_val); GSL_ERROR ("overflow", GSL_EOVRFLW); } abs_del = fabs(del); max_abs_del = GSL_MAX_DBL(abs_del, max_abs_del); sum_err += 2.0*GSL_DBL_EPSILON*abs_del; an += 1.0; bn += 1.0; n += 1.0; } result->val = sum_val; result->err = sum_err; result->err += abs_del; result->err += 2.0 * GSL_DBL_EPSILON * n * fabs(sum_val); return GSL_SUCCESS; } int gsl_sf_hyperg_1F1_large_b_e(const double a, const double b, const double x, gsl_sf_result * result) { if(fabs(x/b) < 1.0) { const double u = x/b; const double v = 1.0/(1.0-u); const double pre = pow(v,a); const double uv = u*v; const double uv2 = uv*uv; const double t1 = a*(a+1.0)/(2.0*b)*uv2; const double t2a = a*(a+1.0)/(24.0*b*b)*uv2; const double t2b = 12.0 + 16.0*(a+2.0)*uv + 3.0*(a+2.0)*(a+3.0)*uv2; const double t2 = t2a*t2b; result->val = pre * (1.0 - t1 + t2); result->err = pre * GSL_DBL_EPSILON * (1.0 + fabs(t1) + fabs(t2)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { DOMAIN_ERROR(result); } } int gsl_sf_hyperg_U_large_b_e(const double a, const double b, const double x, gsl_sf_result * result, double * ln_multiplier ) { double N = floor(b); /* b = N + eps */ double eps = b - N; if(fabs(eps) < GSL_SQRT_DBL_EPSILON) { double lnpre_val; double lnpre_err; gsl_sf_result M; if(b > 1.0) { double tmp = (1.0-b)*log(x); gsl_sf_result lg_bm1; gsl_sf_result lg_a; gsl_sf_lngamma_e(b-1.0, &lg_bm1); gsl_sf_lngamma_e(a, &lg_a); lnpre_val = tmp + x + lg_bm1.val - lg_a.val; lnpre_err = lg_bm1.err + lg_a.err + GSL_DBL_EPSILON * (fabs(x) + fabs(tmp)); gsl_sf_hyperg_1F1_large_b_e(1.0-a, 2.0-b, -x, &M); } else { gsl_sf_result lg_1mb; gsl_sf_result lg_1pamb; gsl_sf_lngamma_e(1.0-b, &lg_1mb); gsl_sf_lngamma_e(1.0+a-b, &lg_1pamb); lnpre_val = lg_1mb.val - lg_1pamb.val; lnpre_err = lg_1mb.err + lg_1pamb.err; gsl_sf_hyperg_1F1_large_b_e(a, b, x, &M); } if(lnpre_val > GSL_LOG_DBL_MAX-10.0) { result->val = M.val; result->err = M.err; *ln_multiplier = lnpre_val; GSL_ERROR ("overflow", GSL_EOVRFLW); } else { gsl_sf_result epre; int stat_e = gsl_sf_exp_err_e(lnpre_val, lnpre_err, &epre); result->val = epre.val * M.val; result->err = epre.val * M.err + epre.err * fabs(M.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *ln_multiplier = 0.0; return stat_e; } } else { double omb_lnx = (1.0-b)*log(x); gsl_sf_result lg_1mb; double sgn_1mb; gsl_sf_result lg_1pamb; double sgn_1pamb; gsl_sf_result lg_bm1; double sgn_bm1; gsl_sf_result lg_a; double sgn_a; gsl_sf_result M1, M2; double lnpre1_val, lnpre2_val; double lnpre1_err, lnpre2_err; double sgpre1, sgpre2; gsl_sf_hyperg_1F1_large_b_e( a, b, x, &M1); gsl_sf_hyperg_1F1_large_b_e(1.0-a, 2.0-b, x, &M2); gsl_sf_lngamma_sgn_e(1.0-b, &lg_1mb, &sgn_1mb); gsl_sf_lngamma_sgn_e(1.0+a-b, &lg_1pamb, &sgn_1pamb); gsl_sf_lngamma_sgn_e(b-1.0, &lg_bm1, &sgn_bm1); gsl_sf_lngamma_sgn_e(a, &lg_a, &sgn_a); lnpre1_val = lg_1mb.val - lg_1pamb.val; lnpre1_err = lg_1mb.err + lg_1pamb.err; lnpre2_val = lg_bm1.val - lg_a.val - omb_lnx - x; lnpre2_err = lg_bm1.err + lg_a.err + GSL_DBL_EPSILON * (fabs(omb_lnx)+fabs(x)); sgpre1 = sgn_1mb * sgn_1pamb; sgpre2 = sgn_bm1 * sgn_a; if(lnpre1_val > GSL_LOG_DBL_MAX-10.0 || lnpre2_val > GSL_LOG_DBL_MAX-10.0) { double max_lnpre_val = GSL_MAX(lnpre1_val,lnpre2_val); double max_lnpre_err = GSL_MAX(lnpre1_err,lnpre2_err); double lp1 = lnpre1_val - max_lnpre_val; double lp2 = lnpre2_val - max_lnpre_val; double t1 = sgpre1*exp(lp1); double t2 = sgpre2*exp(lp2); result->val = t1*M1.val + t2*M2.val; result->err = fabs(t1)*M1.err + fabs(t2)*M2.err; result->err += GSL_DBL_EPSILON * exp(max_lnpre_err) * (fabs(t1*M1.val) + fabs(t2*M2.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *ln_multiplier = max_lnpre_val; GSL_ERROR ("overflow", GSL_EOVRFLW); } else { double t1 = sgpre1*exp(lnpre1_val); double t2 = sgpre2*exp(lnpre2_val); result->val = t1*M1.val + t2*M2.val; result->err = fabs(t1) * M1.err + fabs(t2)*M2.err; result->err += GSL_DBL_EPSILON * (exp(lnpre1_err)*fabs(t1*M1.val) + exp(lnpre2_err)*fabs(t2*M2.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *ln_multiplier = 0.0; return GSL_SUCCESS; } } } /* [Carlson, p.109] says the error in truncating this asymptotic series * is less than the absolute value of the first neglected term. * * A termination argument is provided, so that the series will * be summed at most up to n=n_trunc. If n_trunc is set negative, * then the series is summed until it appears to start diverging. */ int gsl_sf_hyperg_2F0_series_e(const double a, const double b, const double x, int n_trunc, gsl_sf_result * result ) { const int maxiter = 2000; double an = a; double bn = b; double n = 1.0; double sum = 1.0; double del = 1.0; double abs_del = 1.0; double max_abs_del = 1.0; double last_abs_del = 1.0; while(abs_del/fabs(sum) > GSL_DBL_EPSILON && n < maxiter) { double u = an * (bn/n * x); double abs_u = fabs(u); if(abs_u > 1.0 && (max_abs_del > GSL_DBL_MAX/abs_u)) { result->val = sum; result->err = fabs(sum); GSL_ERROR ("overflow", GSL_EOVRFLW); } del *= u; sum += del; abs_del = fabs(del); if(abs_del > last_abs_del) break; /* series is probably starting to grow */ last_abs_del = abs_del; max_abs_del = GSL_MAX(abs_del, max_abs_del); an += 1.0; bn += 1.0; n += 1.0; if(an == 0.0 || bn == 0.0) break; /* series terminated */ if(n_trunc >= 0 && n >= n_trunc) break; /* reached requested timeout */ } result->val = sum; result->err = GSL_DBL_EPSILON * n + abs_del; if(n >= maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } sources_5316/external/gsl/gsl_fft__signals.h0000664000176700017670000000565011705263724020025 0ustar paulpaul/* fft/signals.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION(fft_signal,complex_pulse) (const size_t k, const size_t n, const size_t stride, const BASE z_real, const BASE z_imag, BASE data[], BASE fft[]); int FUNCTION(fft_signal,complex_constant) (const size_t n, const size_t stride, const BASE z_real, const BASE z_imag, BASE data[], BASE fft[]); int FUNCTION(fft_signal,complex_exp) (const int k, const size_t n, const size_t stride, const BASE z_real, const BASE z_imag, BASE data[], BASE fft[]); int FUNCTION(fft_signal,complex_exppair) (const int k1, const int k2, const size_t n, const size_t stride, const BASE z1_real, const BASE z1_imag, const BASE z2_real, const BASE z2_imag, BASE data[], BASE fft[]); int FUNCTION(fft_signal,complex_noise) (const size_t n, const size_t stride, BASE data[], BASE fft[]); int FUNCTION(fft_signal,real_noise) (const size_t n, const size_t stride, BASE data[], BASE fft[]); sources_5316/external/gsl/gsl_permute_vector_uchar.h0000664000176700017670000000266611705263724021620 0ustar paulpaul/* permutation/gsl_permute_vector_uchar.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_UCHAR_H__ #define __GSL_PERMUTE_VECTOR_UCHAR_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_uchar.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_uchar (const gsl_permutation * p, gsl_vector_uchar * v); int gsl_permute_vector_uchar_inverse (const gsl_permutation * p, gsl_vector_uchar * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_UCHAR_H__ */ sources_5316/external/gsl/gsl_statistics_uchar.h0000664000176700017670000001114411705263724020736 0ustar paulpaul/* statistics/gsl_statistics_uchar.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_UCHAR_H__ #define __GSL_STATISTICS_UCHAR_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_uchar_mean (const unsigned char data[], const size_t stride, const size_t n); double gsl_stats_uchar_variance (const unsigned char data[], const size_t stride, const size_t n); double gsl_stats_uchar_sd (const unsigned char data[], const size_t stride, const size_t n); double gsl_stats_uchar_variance_with_fixed_mean (const unsigned char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uchar_sd_with_fixed_mean (const unsigned char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uchar_absdev (const unsigned char data[], const size_t stride, const size_t n); double gsl_stats_uchar_skew (const unsigned char data[], const size_t stride, const size_t n); double gsl_stats_uchar_kurtosis (const unsigned char data[], const size_t stride, const size_t n); double gsl_stats_uchar_lag1_autocorrelation (const unsigned char data[], const size_t stride, const size_t n); double gsl_stats_uchar_covariance (const unsigned char data1[], const size_t stride1,const unsigned char data2[], const size_t stride2, const size_t n); double gsl_stats_uchar_correlation (const unsigned char data1[], const size_t stride1,const unsigned char data2[], const size_t stride2, const size_t n); double gsl_stats_uchar_variance_m (const unsigned char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uchar_sd_m (const unsigned char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uchar_absdev_m (const unsigned char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uchar_skew_m_sd (const unsigned char data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_uchar_kurtosis_m_sd (const unsigned char data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_uchar_lag1_autocorrelation_m (const unsigned char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_uchar_covariance_m (const unsigned char data1[], const size_t stride1,const unsigned char data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); double gsl_stats_uchar_pvariance (const unsigned char data1[], const size_t stride1, const size_t n1, const unsigned char data2[], const size_t stride2, const size_t n2); double gsl_stats_uchar_ttest (const unsigned char data1[], const size_t stride1, const size_t n1, const unsigned char data2[], const size_t stride2, const size_t n2); unsigned char gsl_stats_uchar_max (const unsigned char data[], const size_t stride, const size_t n); unsigned char gsl_stats_uchar_min (const unsigned char data[], const size_t stride, const size_t n); void gsl_stats_uchar_minmax (unsigned char * min, unsigned char * max, const unsigned char data[], const size_t stride, const size_t n); size_t gsl_stats_uchar_max_index (const unsigned char data[], const size_t stride, const size_t n); size_t gsl_stats_uchar_min_index (const unsigned char data[], const size_t stride, const size_t n); void gsl_stats_uchar_minmax_index (size_t * min_index, size_t * max_index, const unsigned char data[], const size_t stride, const size_t n); double gsl_stats_uchar_median_from_sorted_data (const unsigned char sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_uchar_quantile_from_sorted_data (const unsigned char sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_UCHAR_H__ */ sources_5316/external/gsl/gsl_sum__work_utrunc.c0000664000176700017670000000267211723710247020765 0ustar paulpaul#include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sum.h" gsl_sum_levin_utrunc_workspace * gsl_sum_levin_utrunc_alloc (size_t n) { gsl_sum_levin_utrunc_workspace * w; if (n == 0) { GSL_ERROR_VAL ("length n must be positive integer", GSL_EDOM, 0); } w = (gsl_sum_levin_utrunc_workspace *) malloc(sizeof(gsl_sum_levin_utrunc_workspace)); if (w == NULL) { GSL_ERROR_VAL ("failed to allocate struct", GSL_ENOMEM, 0); } w->q_num = (double *) malloc (n * sizeof (double)); if (w->q_num == NULL) { free(w) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate space for q_num", GSL_ENOMEM, 0); } w->q_den = (double *) malloc (n * sizeof (double)); if (w->q_den == NULL) { free (w->q_num); free (w) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate space for q_den", GSL_ENOMEM, 0); } w->dsum = (double *) malloc (n * sizeof (double)); if (w->dsum == NULL) { free (w->q_den); free (w->q_num); free (w) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate space for dsum", GSL_ENOMEM, 0); } w->size = n; w->terms_used = 0; w->sum_plain = 0; return w; } void gsl_sum_levin_utrunc_free (gsl_sum_levin_utrunc_workspace * w) { free (w->dsum); free (w->q_den); free (w->q_num); free (w); } sources_5316/external/gsl/gsl_cblas__strsv.c0000664000176700017670000000061511723710247020037 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_strsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const float *A, const int lda, float *X, const int incX) { #define BASE float #include "gsl_cblas__source_trsv_r.h" #undef BASE } sources_5316/external/gsl/gsl_sf_psi.h0000664000176700017670000000516711705263724016655 0ustar paulpaul/* specfunc/gsl_sf_psi.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_PSI_H__ #define __GSL_SF_PSI_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Poly-Gamma Functions * * psi(m,x) := (d/dx)^m psi(0,x) = (d/dx)^{m+1} log(gamma(x)) */ /* Di-Gamma Function psi(n) = psi(0,n) * * n > 0 * exceptions: GSL_EDOM */ int gsl_sf_psi_int_e(const int n, gsl_sf_result * result); double gsl_sf_psi_int(const int n); /* Di-Gamma Function psi(x) = psi(0, x) * * x != 0.0, -1.0, -2.0, ... * exceptions: GSL_EDOM, GSL_ELOSS */ int gsl_sf_psi_e(const double x, gsl_sf_result * result); double gsl_sf_psi(const double x); /* Di-Gamma Function Re[psi(1 + I y)] * * exceptions: none */ int gsl_sf_psi_1piy_e(const double y, gsl_sf_result * result); double gsl_sf_psi_1piy(const double y); /* Di-Gamma Function psi(z) for general complex argument z = x + iy * * exceptions: GSL_EDOM */ int gsl_sf_complex_psi_e( const double x, const double y, gsl_sf_result * result_re, gsl_sf_result * result_im ); /* Tri-Gamma Function psi^(1)(n) * * n > 0 * exceptions: GSL_EDOM */ int gsl_sf_psi_1_int_e(const int n, gsl_sf_result * result); double gsl_sf_psi_1_int(const int n); /* Tri-Gamma Function psi^(1)(x) * * x != 0.0, -1.0, -2.0, ... * exceptions: GSL_EDOM, GSL_ELOSS */ int gsl_sf_psi_1_e(const double x, gsl_sf_result * result); double gsl_sf_psi_1(const double x); /* Poly-Gamma Function psi^(n)(x) * * n >= 0, x > 0.0 * exceptions: GSL_EDOM */ int gsl_sf_psi_n_e(const int n, const double x, gsl_sf_result * result); double gsl_sf_psi_n(const int n, const double x); __END_DECLS #endif /* __GSL_SF_PSI_H__ */ sources_5316/external/gsl/gsl_multifit__lmpar.c0000664000176700017670000002517611723710247020553 0ustar paulpaul/* multifit/lmpar.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl_permute_vector_double.h" #include "gsl_multifit__qrsolv.c" static size_t count_nsing (const gsl_matrix * r) { /* Count the number of nonsingular entries. Returns the index of the first entry which is singular. */ size_t n = r->size2; size_t i; for (i = 0; i < n; i++) { double rii = gsl_matrix_get (r, i, i); if (rii == 0) { break; } } return i; } static void compute_newton_direction (const gsl_matrix * r, const gsl_permutation * perm, const gsl_vector * qtf, gsl_vector * x) { /* Compute and store in x the Gauss-Newton direction. If the Jacobian is rank-deficient then obtain a least squares solution. */ const size_t n = r->size2; size_t i, j, nsing; for (i = 0 ; i < n ; i++) { double qtfi = gsl_vector_get (qtf, i); gsl_vector_set (x, i, qtfi); } nsing = count_nsing (r); #ifdef DEBUG printf("nsing = %d\n", nsing); printf("r = "); gsl_matrix_fprintf(stdout, r, "%g"); printf("\n"); printf("qtf = "); gsl_vector_fprintf(stdout, x, "%g"); printf("\n"); #endif for (i = nsing; i < n; i++) { gsl_vector_set (x, i, 0.0); } if (nsing > 0) { for (j = nsing; j > 0 && j--;) { double rjj = gsl_matrix_get (r, j, j); double temp = gsl_vector_get (x, j) / rjj; gsl_vector_set (x, j, temp); for (i = 0; i < j; i++) { double rij = gsl_matrix_get (r, i, j); double xi = gsl_vector_get (x, i); gsl_vector_set (x, i, xi - rij * temp); } } } gsl_permute_vector_inverse (perm, x); } static void compute_newton_correction (const gsl_matrix * r, const gsl_vector * sdiag, const gsl_permutation * p, gsl_vector * x, double dxnorm, const gsl_vector * diag, gsl_vector * w) { size_t n = r->size2; size_t i, j; for (i = 0; i < n; i++) { size_t pi = gsl_permutation_get (p, i); double dpi = gsl_vector_get (diag, pi); double xpi = gsl_vector_get (x, pi); gsl_vector_set (w, i, dpi * (dpi * xpi) / dxnorm); } for (j = 0; j < n; j++) { double sj = gsl_vector_get (sdiag, j); double wj = gsl_vector_get (w, j); double tj = wj / sj; gsl_vector_set (w, j, tj); for (i = j + 1; i < n; i++) { double rij = gsl_matrix_get (r, i, j); double wi = gsl_vector_get (w, i); gsl_vector_set (w, i, wi - rij * tj); } } } static void compute_newton_bound (const gsl_matrix * r, const gsl_vector * x, double dxnorm, const gsl_permutation * perm, const gsl_vector * diag, gsl_vector * w) { /* If the jacobian is not rank-deficient then the Newton step provides a lower bound for the zero of the function. Otherwise set this bound to zero. */ size_t n = r->size2; size_t i, j; size_t nsing = count_nsing (r); if (nsing < n) { gsl_vector_set_zero (w); return; } for (i = 0; i < n; i++) { size_t pi = gsl_permutation_get (perm, i); double dpi = gsl_vector_get (diag, pi); double xpi = gsl_vector_get (x, pi); gsl_vector_set (w, i, dpi * (dpi * xpi / dxnorm)); } for (j = 0; j < n; j++) { double sum = 0; for (i = 0; i < j; i++) { sum += gsl_matrix_get (r, i, j) * gsl_vector_get (w, i); } { double rjj = gsl_matrix_get (r, j, j); double wj = gsl_vector_get (w, j); gsl_vector_set (w, j, (wj - sum) / rjj); } } } static void compute_gradient_direction (const gsl_matrix * r, const gsl_permutation * p, const gsl_vector * qtf, const gsl_vector * diag, gsl_vector * g) { const size_t n = r->size2; size_t i, j; for (j = 0; j < n; j++) { double sum = 0; for (i = 0; i <= j; i++) { sum += gsl_matrix_get (r, i, j) * gsl_vector_get (qtf, i); } { size_t pj = gsl_permutation_get (p, j); double dpj = gsl_vector_get (diag, pj); gsl_vector_set (g, j, sum / dpj); } } } static int lmpar (gsl_matrix * r, const gsl_permutation * perm, const gsl_vector * qtf, const gsl_vector * diag, double delta, double * par_inout, gsl_vector * newton, gsl_vector * gradient, gsl_vector * sdiag, gsl_vector * x, gsl_vector * w) { double dxnorm, gnorm, fp, fp_old, par_lower, par_upper, par_c; double par = *par_inout; size_t iter = 0; #ifdef DEBUG printf("ENTERING lmpar\n"); #endif compute_newton_direction (r, perm, qtf, newton); #ifdef DEBUG printf ("newton = "); gsl_vector_fprintf (stdout, newton, "%g"); printf ("\n"); printf ("diag = "); gsl_vector_fprintf (stdout, diag, "%g"); printf ("\n"); #endif /* Evaluate the function at the origin and test for acceptance of the Gauss-Newton direction. */ dxnorm = scaled_enorm (diag, newton); fp = dxnorm - delta; #ifdef DEBUG printf ("dxnorm = %g, delta = %g, fp = %g\n", dxnorm, delta, fp); #endif if (fp <= 0.1 * delta) { gsl_vector_memcpy (x, newton); #ifdef DEBUG printf ("took newton (fp = %g, delta = %g)\n", fp, delta); #endif *par_inout = 0; return GSL_SUCCESS; } #ifdef DEBUG printf ("r = "); gsl_matrix_fprintf (stdout, r, "%g"); printf ("\n"); printf ("newton = "); gsl_vector_fprintf (stdout, newton, "%g"); printf ("\n"); printf ("dxnorm = %g\n", dxnorm); #endif compute_newton_bound (r, newton, dxnorm, perm, diag, w); #ifdef DEBUG printf("perm = "); gsl_permutation_fprintf(stdout, perm, "%d"); printf ("diag = "); gsl_vector_fprintf (stdout, diag, "%g"); printf ("\n"); printf ("w = "); gsl_vector_fprintf (stdout, w, "%g"); printf ("\n"); #endif { double wnorm = enorm (w); double phider = wnorm * wnorm; /* w == zero if r rank-deficient, then set lower bound to zero form MINPACK, lmder.f Hans E. Plesser 2002-02-25 (hans.plesser@itf.nlh.no) */ if ( wnorm > 0 ) par_lower = fp / (delta * phider); else par_lower = 0.0; } #ifdef DEBUG printf("par = %g\n", par ); printf("par_lower = %g\n", par_lower); #endif compute_gradient_direction (r, perm, qtf, diag, gradient); gnorm = enorm (gradient); #ifdef DEBUG printf("gradient = "); gsl_vector_fprintf(stdout, gradient, "%g"); printf("\n"); printf("gnorm = %g\n", gnorm); #endif par_upper = gnorm / delta; if (par_upper == 0) { par_upper = GSL_DBL_MIN / GSL_MIN_DBL(delta, 0.1); } #ifdef DEBUG printf("par_upper = %g\n", par_upper); #endif if (par > par_upper) { #ifdef DEBUG printf("set par to par_upper\n"); #endif par = par_upper; } else if (par < par_lower) { #ifdef DEBUG printf("set par to par_lower\n"); #endif par = par_lower; } if (par == 0) { par = gnorm / dxnorm; #ifdef DEBUG printf("set par to gnorm/dxnorm = %g\n", par); #endif } /* Beginning of iteration */ iteration: iter++; #ifdef DEBUG printf("lmpar iteration = %d\n", iter); #endif #ifdef BRIANSFIX /* Seems like this is described in the paper but not in the MINPACK code */ if (par < par_lower || par > par_upper) { par = GSL_MAX_DBL (0.001 * par_upper, sqrt(par_lower * par_upper)); } #endif /* Evaluate the function at the current value of par */ if (par == 0) { par = GSL_MAX_DBL (0.001 * par_upper, GSL_DBL_MIN); #ifdef DEBUG printf("par = 0, set par to = %g\n", par); #endif } /* Compute the least squares solution of [ R P x - Q^T f, sqrt(par) D x] for A = Q R P^T */ #ifdef DEBUG printf ("calling qrsolv with par = %g\n", par); #endif { double sqrt_par = sqrt(par); qrsolv (r, perm, sqrt_par, diag, qtf, x, sdiag, w); } dxnorm = scaled_enorm (diag, x); fp_old = fp; fp = dxnorm - delta; #ifdef DEBUG printf ("After qrsolv dxnorm = %g, delta = %g, fp = %g\n", dxnorm, delta, fp); printf ("sdiag = ") ; gsl_vector_fprintf(stdout, sdiag, "%g"); printf("\n"); printf ("x = ") ; gsl_vector_fprintf(stdout, x, "%g"); printf("\n"); printf ("r = ") ; gsl_matrix_fprintf(stdout, r, "%g"); printf("\nXXX\n"); #endif /* If the function is small enough, accept the current value of par */ if (fabs (fp) <= 0.1 * delta) goto line220; if (par_lower == 0 && fp <= fp_old && fp_old < 0) goto line220; /* Check for maximum number of iterations */ if (iter == 10) goto line220; /* Compute the Newton correction */ compute_newton_correction (r, sdiag, perm, x, dxnorm, diag, w); #ifdef DEBUG printf ("newton_correction = "); gsl_vector_fprintf(stdout, w, "%g"); printf("\n"); #endif { double wnorm = enorm (w); par_c = fp / (delta * wnorm * wnorm); } #ifdef DEBUG printf("fp = %g\n", fp); printf("par_lower = %g\n", par_lower); printf("par_upper = %g\n", par_upper); printf("par_c = %g\n", par_c); #endif /* Depending on the sign of the function, update par_lower or par_upper */ if (fp > 0) { if (par > par_lower) { par_lower = par; #ifdef DEBUG printf("fp > 0: set par_lower = par = %g\n", par); #endif } } else if (fp < 0) { if (par < par_upper) { #ifdef DEBUG printf("fp < 0: set par_upper = par = %g\n", par); #endif par_upper = par; } } /* Compute an improved estimate for par */ #ifdef DEBUG printf("improved estimate par = MAX(%g, %g) \n", par_lower, par+par_c); #endif par = GSL_MAX_DBL (par_lower, par + par_c); #ifdef DEBUG printf("improved estimate par = %g \n", par); #endif goto iteration; line220: #ifdef DEBUG printf("LEAVING lmpar, par = %g\n", par); #endif *par_inout = par; return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__dsbmv.c0000664000176700017670000000064411723710247017773 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dsbmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const int K, const double alpha, const double *A, const int lda, const double *X, const int incX, const double beta, double *Y, const int incY) { #define BASE double #include "gsl_cblas__source_sbmv.h" #undef BASE } sources_5316/external/gsl/gsl_sort_vector_long.h0000664000176700017670000000340111705263724020747 0ustar paulpaul/* sort/gsl_sort_vector_long.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_LONG_H__ #define __GSL_SORT_VECTOR_LONG_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_long.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_long (gsl_vector_long * v); int gsl_sort_vector_long_index (gsl_permutation * p, const gsl_vector_long * v); int gsl_sort_vector_long_smallest (long * dest, const size_t k, const gsl_vector_long * v); int gsl_sort_vector_long_largest (long * dest, const size_t k, const gsl_vector_long * v); int gsl_sort_vector_long_smallest_index (size_t * p, const size_t k, const gsl_vector_long * v); int gsl_sort_vector_long_largest_index (size_t * p, const size_t k, const gsl_vector_long * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_LONG_H__ */ sources_5316/external/gsl/gsl_cblas__source_iamax_r.h0000664000176700017670000000206511705263724021667 0ustar paulpaul/* blas/source_iamax_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { BASE max = 0.0; INDEX ix = 0; INDEX i; CBLAS_INDEX result = 0; if (incX <= 0) { return 0; } for (i = 0; i < N; i++) { if (fabs(X[ix]) > max) { max = fabs(X[ix]); result = i; } ix += incX; } return result; } sources_5316/external/gsl/gsl_sf_coupling.h0000664000176700017670000001010111705263724017662 0ustar paulpaul/* specfunc/gsl_sf_coupling.h * * Copyright (C) 1996,1997,1998,1999,2000,2001,2002 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_COUPLING_H__ #define __GSL_SF_COUPLING_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* 3j Symbols: / ja jb jc \ * \ ma mb mc / * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_coupling_3j_e(int two_ja, int two_jb, int two_jc, int two_ma, int two_mb, int two_mc, gsl_sf_result * result ); double gsl_sf_coupling_3j(int two_ja, int two_jb, int two_jc, int two_ma, int two_mb, int two_mc ); /* 6j Symbols: / ja jb jc \ * \ jd je jf / * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_coupling_6j_e(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, gsl_sf_result * result ); double gsl_sf_coupling_6j(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf ); /* Racah W coefficients: * * W(a b c d; e f) = (-1)^{a+b+c+d} / a b e \ * \ d c f / * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_coupling_RacahW_e(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, gsl_sf_result * result ); double gsl_sf_coupling_RacahW(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf ); /* 9j Symbols: / ja jb jc \ * | jd je jf | * \ jg jh ji / * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_coupling_9j_e(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, int two_jg, int two_jh, int two_ji, gsl_sf_result * result ); double gsl_sf_coupling_9j(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, int two_jg, int two_jh, int two_ji ); /* INCORRECT version of 6j Symbols: * This function actually calculates * / ja jb je \ * \ jd jc jf / * It represents the original implementation, * which had the above permutation of the * arguments. This was wrong and confusing, * and I had to fix it. Sorry for the trouble. * [GJ] Tue Nov 26 12:53:39 MST 2002 * * exceptions: GSL_EDOM, GSL_EOVRFLW */ #ifndef GSL_DISABLE_DEPRECATED int gsl_sf_coupling_6j_INCORRECT_e(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, gsl_sf_result * result ); double gsl_sf_coupling_6j_INCORRECT(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf ); #endif /* !GSL_DISABLE_DEPRECATED */ __END_DECLS #endif /* __GSL_SF_COUPLING_H__ */ sources_5316/external/gsl/gsl_cdf__betainv.c0000664000176700017670000001125211723710247017755 0ustar paulpaul/* cdf/betainv.c * * Copyright (C) 2004 Free Software Foundation, Inc. * Copyright (C) 2006, 2007 Brian Gough * Written by Jason H. Stover. * Modified for GSL by Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * Invert the Beta distribution. * * References: * * Roger W. Abernathy and Robert P. Smith. "Applying Series Expansion * to the Inverse Beta Distribution to Find Percentiles of the * F-Distribution," ACM Transactions on Mathematical Software, volume * 19, number 4, December 1993, pages 474-480. * * G.W. Hill and A.W. Davis. "Generalized asymptotic expansions of a * Cornish-Fisher type," Annals of Mathematical Statistics, volume 39, * number 8, August 1968, pages 1264-1273. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_gamma.h" #include "gsl_cdf.h" #include "gsl_randist.h" #include "gsl_cdf__error.h" static double bisect (double x, double P, double a, double b, double xtol, double Ptol) { double x0 = 0, x1 = 1, Px; while (fabs(x1 - x0) > xtol) { Px = gsl_cdf_beta_P (x, a, b); if (fabs(Px - P) < Ptol) { /* return as soon as approximation is good enough, including on the first iteration */ return x; } else if (Px < P) { x0 = x; } else if (Px > P) { x1 = x; } x = 0.5 * (x0 + x1); } return x; } double gsl_cdf_beta_Pinv (const double P, const double a, const double b) { double x, mean; if (P < 0.0 || P > 1.0) { CDF_ERROR ("P must be in range 0 < P < 1", GSL_EDOM); } if (a < 0.0) { CDF_ERROR ("a < 0", GSL_EDOM); } if (b < 0.0) { CDF_ERROR ("b < 0", GSL_EDOM); } if (P == 0.0) { return 0.0; } if (P == 1.0) { return 1.0; } if (P > 0.5) { return gsl_cdf_beta_Qinv (1 - P, a, b); } mean = a / (a + b); if (P < 0.1) { /* small x */ double lg_ab = gsl_sf_lngamma (a + b); double lg_a = gsl_sf_lngamma (a); double lg_b = gsl_sf_lngamma (b); double lx = (log (a) + lg_a + lg_b - lg_ab + log (P)) / a; if (lx <= 0) { x = exp (lx); /* first approximation */ x *= pow (1 - x, -(b - 1) / a); /* second approximation */ } else { x = mean; } if (x > mean) x = mean; } else { /* Use expected value as first guess */ x = mean; } /* Do bisection to get closer */ x = bisect (x, P, a, b, 0.01, 0.01); { double lambda, dP, phi; unsigned int n = 0; start: dP = P - gsl_cdf_beta_P (x, a, b); phi = gsl_ran_beta_pdf (x, a, b); if (dP == 0.0 || n++ > 64) goto end; lambda = dP / GSL_MAX (2 * fabs (dP / x), phi); { double step0 = lambda; double step1 = -((a - 1) / x - (b - 1) / (1 - x)) * lambda * lambda / 2; double step = step0; if (fabs (step1) < fabs (step0)) { step += step1; } else { /* scale back step to a reasonable size when too large */ step *= 2 * fabs (step0 / step1); }; if (x + step > 0 && x + step < 1) { x += step; } else { x = sqrt (x) * sqrt (mean); /* try a new starting point */ } if (fabs (step0) > 1e-10 * x) goto start; } end: if (fabs(dP) > GSL_SQRT_DBL_EPSILON * P) { GSL_ERROR_VAL("inverse failed to converge", GSL_EFAILED, GSL_NAN); } return x; } } double gsl_cdf_beta_Qinv (const double Q, const double a, const double b) { if (Q < 0.0 || Q > 1.0) { CDF_ERROR ("Q must be inside range 0 < Q < 1", GSL_EDOM); } if (a < 0.0) { CDF_ERROR ("a < 0", GSL_EDOM); } if (b < 0.0) { CDF_ERROR ("b < 0", GSL_EDOM); } if (Q == 0.0) { return 1.0; } if (Q == 1.0) { return 0.0; } if (Q > 0.5) { return gsl_cdf_beta_Pinv (1 - Q, a, b); } else { return 1 - gsl_cdf_beta_Pinv (Q, b, a); }; } sources_5316/external/gsl/gsl_multimin__diff.c0000664000176700017670000000305711723710247020343 0ustar paulpaul/* multimin/diff.c * * Copyright (C) 2000 David Morrison * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_multimin.h" int gsl_multimin_diff (const gsl_multimin_function * f, const gsl_vector * x, gsl_vector * g) { size_t i, n = f->n; double h = GSL_SQRT_DBL_EPSILON; gsl_vector * x1 = gsl_vector_alloc (n); /* FIXME: pass as argument */ gsl_vector_memcpy (x1, x); for (i = 0; i < n; i++) { double fl, fh; double xi = gsl_vector_get (x, i); double dx = fabs(xi) * h; if (dx == 0.0) dx = h; gsl_vector_set (x1, i, xi + dx); fh = GSL_MULTIMIN_FN_EVAL(f, x1); gsl_vector_set (x1, i, xi - dx); fl = GSL_MULTIMIN_FN_EVAL(f, x1); gsl_vector_set (x1, i, xi); gsl_vector_set (g, i, (fh - fl) / (2.0 * dx)); } gsl_vector_free (x1); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_matrix__submatrix.c0000664000176700017670000000775411723710247021127 0ustar paulpaul#include "gsl__config.h" #include "gsl_math.h" #include "gsl_matrix.h" #include "gsl_vector.h" #include "gsl_errno.h" #include "gsl_matrix__view.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_CHAR #define USE_QUALIFIER #define QUALIFIER const #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__submatrix_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_randist__fdist.c0000664000176700017670000000361611723710247020353 0ustar paulpaul/* randist/fdist.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_sf_gamma.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The F distribution has the form p(x) dx = (nu1^(nu1/2) nu2^(nu2/2) Gamma((nu1 + nu2)/2) / Gamma(nu1/2) Gamma(nu2/2)) * x^(nu1/2 - 1) (nu2 + nu1 * x)^(-nu1/2 -nu2/2) dx The method used here is the one described in Knuth */ double gsl_ran_fdist (const gsl_rng * r, const double nu1, const double nu2) { double Y1 = gsl_ran_gamma (r, nu1 / 2, 2.0); double Y2 = gsl_ran_gamma (r, nu2 / 2, 2.0); double f = (Y1 * nu2) / (Y2 * nu1); return f; } double gsl_ran_fdist_pdf (const double x, const double nu1, const double nu2) { if (x < 0) { return 0 ; } else { double p; double lglg = (nu1 / 2) * log (nu1) + (nu2 / 2) * log (nu2) ; double lg12 = gsl_sf_lngamma ((nu1 + nu2) / 2); double lg1 = gsl_sf_lngamma (nu1 / 2); double lg2 = gsl_sf_lngamma (nu2 / 2); p = exp (lglg + lg12 - lg1 - lg2) * pow (x, nu1 / 2 - 1) * pow (nu2 + nu1 * x, -nu1 / 2 - nu2 / 2); return p; } } sources_5316/external/gsl/gsl_matrix_uchar.h0000664000176700017670000002723011705263724020053 0ustar paulpaul/* matrix/gsl_matrix_uchar.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_UCHAR_H__ #define __GSL_MATRIX_UCHAR_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_uchar.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; unsigned char * data; gsl_block_uchar * block; int owner; } gsl_matrix_uchar; typedef struct { gsl_matrix_uchar matrix; } _gsl_matrix_uchar_view; typedef _gsl_matrix_uchar_view gsl_matrix_uchar_view; typedef struct { gsl_matrix_uchar matrix; } _gsl_matrix_uchar_const_view; typedef const _gsl_matrix_uchar_const_view gsl_matrix_uchar_const_view; /* Allocation */ gsl_matrix_uchar * gsl_matrix_uchar_alloc (const size_t n1, const size_t n2); gsl_matrix_uchar * gsl_matrix_uchar_calloc (const size_t n1, const size_t n2); gsl_matrix_uchar * gsl_matrix_uchar_alloc_from_block (gsl_block_uchar * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_uchar * gsl_matrix_uchar_alloc_from_matrix (gsl_matrix_uchar * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_uchar * gsl_vector_uchar_alloc_row_from_matrix (gsl_matrix_uchar * m, const size_t i); gsl_vector_uchar * gsl_vector_uchar_alloc_col_from_matrix (gsl_matrix_uchar * m, const size_t j); void gsl_matrix_uchar_free (gsl_matrix_uchar * m); /* Views */ _gsl_matrix_uchar_view gsl_matrix_uchar_submatrix (gsl_matrix_uchar * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_uchar_view gsl_matrix_uchar_row (gsl_matrix_uchar * m, const size_t i); _gsl_vector_uchar_view gsl_matrix_uchar_column (gsl_matrix_uchar * m, const size_t j); _gsl_vector_uchar_view gsl_matrix_uchar_diagonal (gsl_matrix_uchar * m); _gsl_vector_uchar_view gsl_matrix_uchar_subdiagonal (gsl_matrix_uchar * m, const size_t k); _gsl_vector_uchar_view gsl_matrix_uchar_superdiagonal (gsl_matrix_uchar * m, const size_t k); _gsl_vector_uchar_view gsl_matrix_uchar_subrow (gsl_matrix_uchar * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_uchar_view gsl_matrix_uchar_subcolumn (gsl_matrix_uchar * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_uchar_view gsl_matrix_uchar_view_array (unsigned char * base, const size_t n1, const size_t n2); _gsl_matrix_uchar_view gsl_matrix_uchar_view_array_with_tda (unsigned char * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_uchar_view gsl_matrix_uchar_view_vector (gsl_vector_uchar * v, const size_t n1, const size_t n2); _gsl_matrix_uchar_view gsl_matrix_uchar_view_vector_with_tda (gsl_vector_uchar * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_uchar_const_view gsl_matrix_uchar_const_submatrix (const gsl_matrix_uchar * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_uchar_const_view gsl_matrix_uchar_const_row (const gsl_matrix_uchar * m, const size_t i); _gsl_vector_uchar_const_view gsl_matrix_uchar_const_column (const gsl_matrix_uchar * m, const size_t j); _gsl_vector_uchar_const_view gsl_matrix_uchar_const_diagonal (const gsl_matrix_uchar * m); _gsl_vector_uchar_const_view gsl_matrix_uchar_const_subdiagonal (const gsl_matrix_uchar * m, const size_t k); _gsl_vector_uchar_const_view gsl_matrix_uchar_const_superdiagonal (const gsl_matrix_uchar * m, const size_t k); _gsl_vector_uchar_const_view gsl_matrix_uchar_const_subrow (const gsl_matrix_uchar * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_uchar_const_view gsl_matrix_uchar_const_subcolumn (const gsl_matrix_uchar * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_uchar_const_view gsl_matrix_uchar_const_view_array (const unsigned char * base, const size_t n1, const size_t n2); _gsl_matrix_uchar_const_view gsl_matrix_uchar_const_view_array_with_tda (const unsigned char * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_uchar_const_view gsl_matrix_uchar_const_view_vector (const gsl_vector_uchar * v, const size_t n1, const size_t n2); _gsl_matrix_uchar_const_view gsl_matrix_uchar_const_view_vector_with_tda (const gsl_vector_uchar * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ unsigned char gsl_matrix_uchar_get(const gsl_matrix_uchar * m, const size_t i, const size_t j); void gsl_matrix_uchar_set(gsl_matrix_uchar * m, const size_t i, const size_t j, const unsigned char x); unsigned char * gsl_matrix_uchar_ptr(gsl_matrix_uchar * m, const size_t i, const size_t j); const unsigned char * gsl_matrix_uchar_const_ptr(const gsl_matrix_uchar * m, const size_t i, const size_t j); void gsl_matrix_uchar_set_zero (gsl_matrix_uchar * m); void gsl_matrix_uchar_set_identity (gsl_matrix_uchar * m); void gsl_matrix_uchar_set_all (gsl_matrix_uchar * m, unsigned char x); int gsl_matrix_uchar_fread (FILE * stream, gsl_matrix_uchar * m) ; int gsl_matrix_uchar_fwrite (FILE * stream, const gsl_matrix_uchar * m) ; int gsl_matrix_uchar_fscanf (FILE * stream, gsl_matrix_uchar * m); int gsl_matrix_uchar_fprintf (FILE * stream, const gsl_matrix_uchar * m, const char * format); int gsl_matrix_uchar_memcpy(gsl_matrix_uchar * dest, const gsl_matrix_uchar * src); int gsl_matrix_uchar_swap(gsl_matrix_uchar * m1, gsl_matrix_uchar * m2); int gsl_matrix_uchar_swap_rows(gsl_matrix_uchar * m, const size_t i, const size_t j); int gsl_matrix_uchar_swap_columns(gsl_matrix_uchar * m, const size_t i, const size_t j); int gsl_matrix_uchar_swap_rowcol(gsl_matrix_uchar * m, const size_t i, const size_t j); int gsl_matrix_uchar_transpose (gsl_matrix_uchar * m); int gsl_matrix_uchar_transpose_memcpy (gsl_matrix_uchar * dest, const gsl_matrix_uchar * src); unsigned char gsl_matrix_uchar_max (const gsl_matrix_uchar * m); unsigned char gsl_matrix_uchar_min (const gsl_matrix_uchar * m); void gsl_matrix_uchar_minmax (const gsl_matrix_uchar * m, unsigned char * min_out, unsigned char * max_out); void gsl_matrix_uchar_max_index (const gsl_matrix_uchar * m, size_t * imax, size_t *jmax); void gsl_matrix_uchar_min_index (const gsl_matrix_uchar * m, size_t * imin, size_t *jmin); void gsl_matrix_uchar_minmax_index (const gsl_matrix_uchar * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_uchar_isnull (const gsl_matrix_uchar * m); int gsl_matrix_uchar_ispos (const gsl_matrix_uchar * m); int gsl_matrix_uchar_isneg (const gsl_matrix_uchar * m); int gsl_matrix_uchar_isnonneg (const gsl_matrix_uchar * m); int gsl_matrix_uchar_add (gsl_matrix_uchar * a, const gsl_matrix_uchar * b); int gsl_matrix_uchar_sub (gsl_matrix_uchar * a, const gsl_matrix_uchar * b); int gsl_matrix_uchar_mul_elements (gsl_matrix_uchar * a, const gsl_matrix_uchar * b); int gsl_matrix_uchar_div_elements (gsl_matrix_uchar * a, const gsl_matrix_uchar * b); int gsl_matrix_uchar_scale (gsl_matrix_uchar * a, const double x); int gsl_matrix_uchar_add_constant (gsl_matrix_uchar * a, const double x); int gsl_matrix_uchar_add_diagonal (gsl_matrix_uchar * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_uchar_get_row(gsl_vector_uchar * v, const gsl_matrix_uchar * m, const size_t i); int gsl_matrix_uchar_get_col(gsl_vector_uchar * v, const gsl_matrix_uchar * m, const size_t j); int gsl_matrix_uchar_set_row(gsl_matrix_uchar * m, const size_t i, const gsl_vector_uchar * v); int gsl_matrix_uchar_set_col(gsl_matrix_uchar * m, const size_t j, const gsl_vector_uchar * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline unsigned char gsl_matrix_uchar_get(const gsl_matrix_uchar * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_uchar_set(gsl_matrix_uchar * m, const size_t i, const size_t j, const unsigned char x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline unsigned char * gsl_matrix_uchar_ptr(gsl_matrix_uchar * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (unsigned char *) (m->data + (i * m->tda + j)) ; } extern inline const unsigned char * gsl_matrix_uchar_const_ptr(const gsl_matrix_uchar * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const unsigned char *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_UCHAR_H__ */ sources_5316/external/gsl/gsl_eigen__nonsymm.c0000664000176700017670000001566311723710247020372 0ustar paulpaul/* eigen/nonsymm.c * * Copyright (C) 2006 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_eigen.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_blas.h" #include "gsl_vector.h" #include "gsl_vector_complex.h" #include "gsl_matrix.h" /* * This module computes the eigenvalues of a real nonsymmetric * matrix, using the double shift Francis method. * * See the references in francis.c. * * This module gets the matrix ready by balancing it and * reducing it to Hessenberg form before passing it to the * francis module. */ /* gsl_eigen_nonsymm_alloc() Allocate a workspace for solving the nonsymmetric eigenvalue problem. The size of this workspace is O(2n) Inputs: n - size of matrix Return: pointer to workspace */ gsl_eigen_nonsymm_workspace * gsl_eigen_nonsymm_alloc(const size_t n) { gsl_eigen_nonsymm_workspace *w; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = (gsl_eigen_nonsymm_workspace *) calloc (1, sizeof (gsl_eigen_nonsymm_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->size = n; w->Z = NULL; w->do_balance = 0; w->diag = gsl_vector_alloc(n); if (w->diag == 0) { gsl_eigen_nonsymm_free(w); GSL_ERROR_NULL ("failed to allocate space for balancing vector", GSL_ENOMEM); } w->tau = gsl_vector_alloc(n); if (w->tau == 0) { gsl_eigen_nonsymm_free(w); GSL_ERROR_NULL ("failed to allocate space for hessenberg coefficients", GSL_ENOMEM); } w->francis_workspace_p = gsl_eigen_francis_alloc(); if (w->francis_workspace_p == 0) { gsl_eigen_nonsymm_free(w); GSL_ERROR_NULL ("failed to allocate space for francis workspace", GSL_ENOMEM); } return (w); } /* gsl_eigen_nonsymm_alloc() */ /* gsl_eigen_nonsymm_free() Free workspace w */ void gsl_eigen_nonsymm_free (gsl_eigen_nonsymm_workspace * w) { if (w->tau) gsl_vector_free(w->tau); if (w->diag) gsl_vector_free(w->diag); if (w->francis_workspace_p) gsl_eigen_francis_free(w->francis_workspace_p); free(w); } /* gsl_eigen_nonsymm_free() */ /* gsl_eigen_nonsymm_params() Set some parameters which define how we solve the eigenvalue problem. Inputs: compute_t - 1 if we want to compute T, 0 if not balance - 1 if we want to balance the matrix, 0 if not w - nonsymm workspace */ void gsl_eigen_nonsymm_params (const int compute_t, const int balance, gsl_eigen_nonsymm_workspace *w) { gsl_eigen_francis_T(compute_t, w->francis_workspace_p); w->do_balance = balance; } /* gsl_eigen_nonsymm_params() */ /* gsl_eigen_nonsymm() Solve the nonsymmetric eigenvalue problem A x = \lambda x for the eigenvalues \lambda using the Francis method. Here we compute the real Schur form T = Z^t A Z with the diagonal blocks of T giving us the eigenvalues. Z is a matrix of Schur vectors which is not computed by this algorithm. See gsl_eigen_nonsymm_Z(). Inputs: A - general real matrix eval - where to store eigenvalues w - workspace Return: success or error Notes: If T is computed, it is stored in A on output. Otherwise the diagonal of A contains the 1-by-1 and 2-by-2 eigenvalue blocks. */ int gsl_eigen_nonsymm (gsl_matrix * A, gsl_vector_complex * eval, gsl_eigen_nonsymm_workspace * w) { const size_t N = A->size1; /* check matrix and vector sizes */ if (N != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if (eval->size != N) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else { int s; if (w->do_balance) { /* balance the matrix */ gsl_linalg_balance_matrix(A, w->diag); } /* compute the Hessenberg reduction of A */ gsl_linalg_hessenberg_decomp(A, w->tau); if (w->Z) { /* * initialize the matrix Z to U, which is the matrix used * to construct the Hessenberg reduction. */ /* compute U and store it in Z */ gsl_linalg_hessenberg_unpack(A, w->tau, w->Z); /* find the eigenvalues and Schur vectors */ s = gsl_eigen_francis_Z(A, eval, w->Z, w->francis_workspace_p); if (w->do_balance) { /* * The Schur vectors in Z are the vectors for the balanced * matrix. We now must undo the balancing to get the * vectors for the original matrix A. */ gsl_linalg_balance_accum(w->Z, w->diag); } } else { /* find the eigenvalues only */ s = gsl_eigen_francis(A, eval, w->francis_workspace_p); } w->n_evals = w->francis_workspace_p->n_evals; return s; } } /* gsl_eigen_nonsymm() */ /* gsl_eigen_nonsymm_Z() Solve the nonsymmetric eigenvalue problem A x = \lambda x for the eigenvalues \lambda. Here we compute the real Schur form T = Z^t A Z with the diagonal blocks of T giving us the eigenvalues. Z is the matrix of Schur vectors. Inputs: A - general real matrix eval - where to store eigenvalues Z - where to store Schur vectors w - workspace Return: success or error Notes: If T is computed, it is stored in A on output. Otherwise the diagonal of A contains the 1-by-1 and 2-by-2 eigenvalue blocks. */ int gsl_eigen_nonsymm_Z (gsl_matrix * A, gsl_vector_complex * eval, gsl_matrix * Z, gsl_eigen_nonsymm_workspace * w) { /* check matrix and vector sizes */ if (A->size1 != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if (eval->size != A->size1) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if ((Z->size1 != Z->size2) || (Z->size1 != A->size1)) { GSL_ERROR ("Z matrix has wrong dimensions", GSL_EBADLEN); } else { int s; w->Z = Z; s = gsl_eigen_nonsymm(A, eval, w); w->Z = NULL; return s; } } /* gsl_eigen_nonsymm_Z() */ sources_5316/external/gsl/gsl_matrix__copy.c0000664000176700017670000000362611723710247020055 0ustar paulpaul#include "gsl__config.h" #include "gsl_matrix.h" #include "gsl_errno.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__copy_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_fft__c_main.c0000664000176700017670000001574211723710247017606 0ustar paulpaul/* fft/c_main.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl_fft__c_pass.h" int FUNCTION(gsl_fft_complex,forward) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n, const TYPE(gsl_fft_complex_wavetable) * wavetable, TYPE(gsl_fft_complex_workspace) * work) { gsl_fft_direction sign = gsl_fft_forward; int status = FUNCTION(gsl_fft_complex,transform) (data, stride, n, wavetable, work, sign); return status; } int FUNCTION(gsl_fft_complex,backward) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n, const TYPE(gsl_fft_complex_wavetable) * wavetable, TYPE(gsl_fft_complex_workspace) * work) { gsl_fft_direction sign = gsl_fft_backward; int status = FUNCTION(gsl_fft_complex,transform) (data, stride, n, wavetable, work, sign); return status; } int FUNCTION(gsl_fft_complex,inverse) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n, const TYPE(gsl_fft_complex_wavetable) * wavetable, TYPE(gsl_fft_complex_workspace) * work) { gsl_fft_direction sign = gsl_fft_backward; int status = FUNCTION(gsl_fft_complex,transform) (data, stride, n, wavetable, work, sign); if (status) { return status; } /* normalize inverse fft with 1/n */ { const ATOMIC norm = ONE / (ATOMIC)n; size_t i; for (i = 0; i < n; i++) { REAL(data,stride,i) *= norm; IMAG(data,stride,i) *= norm; } } return status; } int FUNCTION(gsl_fft_complex,transform) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n, const TYPE(gsl_fft_complex_wavetable) * wavetable, TYPE(gsl_fft_complex_workspace) * work, const gsl_fft_direction sign) { const size_t nf = wavetable->nf; size_t i; size_t q, product = 1; TYPE(gsl_complex) *twiddle1, *twiddle2, *twiddle3, *twiddle4, *twiddle5, *twiddle6; size_t state = 0; BASE * const scratch = work->scratch; BASE * in = data; size_t istride = stride; BASE * out = scratch; size_t ostride = 1; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } if (n == 1) { /* FFT of 1 data point is the identity */ return 0; } if (n != wavetable->n) { GSL_ERROR ("wavetable does not match length of data", GSL_EINVAL); } if (n != work->n) { GSL_ERROR ("workspace does not match length of data", GSL_EINVAL); } for (i = 0; i < nf; i++) { const size_t factor = wavetable->factor[i]; product *= factor; q = n / product; if (state == 0) { in = data; istride = stride; out = scratch; ostride = 1; state = 1; } else { in = scratch; istride = 1; out = data; ostride = stride; state = 0; } if (factor == 2) { twiddle1 = wavetable->twiddle[i]; FUNCTION(fft_complex,pass_2) (in, istride, out, ostride, sign, product, n, twiddle1); } else if (factor == 3) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + q; FUNCTION(fft_complex,pass_3) (in, istride, out, ostride, sign, product, n, twiddle1, twiddle2); } else if (factor == 4) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + q; twiddle3 = twiddle2 + q; FUNCTION(fft_complex,pass_4) (in, istride, out, ostride, sign, product, n, twiddle1, twiddle2, twiddle3); } else if (factor == 5) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + q; twiddle3 = twiddle2 + q; twiddle4 = twiddle3 + q; FUNCTION(fft_complex,pass_5) (in, istride, out, ostride, sign, product, n, twiddle1, twiddle2, twiddle3, twiddle4); } else if (factor == 6) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + q; twiddle3 = twiddle2 + q; twiddle4 = twiddle3 + q; twiddle5 = twiddle4 + q; FUNCTION(fft_complex,pass_6) (in, istride, out, ostride, sign, product, n, twiddle1, twiddle2, twiddle3, twiddle4, twiddle5); } else if (factor == 7) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + q; twiddle3 = twiddle2 + q; twiddle4 = twiddle3 + q; twiddle5 = twiddle4 + q; twiddle6 = twiddle5 + q; FUNCTION(fft_complex,pass_7) (in, istride, out, ostride, sign, product, n, twiddle1, twiddle2, twiddle3, twiddle4, twiddle5, twiddle6); } else { twiddle1 = wavetable->twiddle[i]; FUNCTION(fft_complex,pass_n) (in, istride, out, ostride, sign, factor, product, n, twiddle1); } } if (state == 1) /* copy results back from scratch to data */ { for (i = 0; i < n; i++) { REAL(data,stride,i) = REAL(scratch,1,i) ; IMAG(data,stride,i) = IMAG(scratch,1,i) ; } } return 0; } sources_5316/external/gsl/gsl_cblas__source_scal_c.h0000664000176700017670000000233311705263724021471 0ustar paulpaul/* blas/source_scal_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; INDEX ix; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); if (incX <= 0) { return; } ix = OFFSET(N, incX); for (i = 0; i < N; i++) { const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); REAL(X, ix) = x_real * alpha_real - x_imag * alpha_imag; IMAG(X, ix) = x_real * alpha_imag + x_imag * alpha_real; ix += incX; } } sources_5316/external/gsl/gsl_statistics__wabsdev.c0000664000176700017670000000075511723710247021424 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__wabsdev_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__wabsdev_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__wabsdev_source.c" #include "templates_off.h" #undef BASE_FLOAT sources_5316/external/gsl/gsl_specfunc__lambert.c0000664000176700017670000001404711723710247021032 0ustar paulpaul/* specfunc/lambert.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_lambert.h" /* Started with code donated by K. Briggs; added * error estimates, GSL foo, and minor tweaks. * Some Lambert-ology from * [Corless, Gonnet, Hare, and Jeffrey, "On Lambert's W Function".] */ /* Halley iteration (eqn. 5.12, Corless et al) */ static int halley_iteration( double x, double w_initial, unsigned int max_iters, gsl_sf_result * result ) { double w = w_initial; unsigned int i; for(i=0; i 0) { t = (t/p)/e; /* Newton iteration */ } else { t /= e*p - 0.5*(p + 1.0)*t/p; /* Halley iteration */ }; w -= t; tol = 10 * GSL_DBL_EPSILON * GSL_MAX_DBL(fabs(w), 1.0/(fabs(p)*e)); if(fabs(t) < tol) { result->val = w; result->err = 2.0*tol; return GSL_SUCCESS; } } /* should never get here */ result->val = w; result->err = fabs(w); return GSL_EMAXITER; } /* series which appears for q near zero; * only the argument is different for the different branches */ static double series_eval(double r) { static const double c[12] = { -1.0, 2.331643981597124203363536062168, -1.812187885639363490240191647568, 1.936631114492359755363277457668, -2.353551201881614516821543561516, 3.066858901050631912893148922704, -4.175335600258177138854984177460, 5.858023729874774148815053846119, -8.401032217523977370984161688514, 12.250753501314460424, -18.100697012472442755, 27.029044799010561650 }; const double t_8 = c[8] + r*(c[9] + r*(c[10] + r*c[11])); const double t_5 = c[5] + r*(c[6] + r*(c[7] + r*t_8)); const double t_1 = c[1] + r*(c[2] + r*(c[3] + r*(c[4] + r*t_5))); return c[0] + r*t_1; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_lambert_W0_e(double x, gsl_sf_result * result) { const double one_over_E = 1.0/M_E; const double q = x + one_over_E; if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(q < 0.0) { /* Strictly speaking this is an error. But because of the * arithmetic operation connecting x and q, I am a little * lenient in case of some epsilon overshoot. The following * answer is quite accurate in that case. Anyway, we have * to return GSL_EDOM. */ result->val = -1.0; result->err = sqrt(-q); return GSL_EDOM; } else if(q == 0.0) { result->val = -1.0; result->err = GSL_DBL_EPSILON; /* cannot error is zero, maybe q == 0 by "accident" */ return GSL_SUCCESS; } else if(q < 1.0e-03) { /* series near -1/E in sqrt(q) */ const double r = sqrt(q); result->val = series_eval(r); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { static const unsigned int MAX_ITERS = 10; double w; if (x < 1.0) { /* obtain initial approximation from series near x=0; * no need for extra care, since the Halley iteration * converges nicely on this branch */ const double p = sqrt(2.0 * M_E * q); w = -1.0 + p*(1.0 + p*(-1.0/3.0 + p*11.0/72.0)); } else { /* obtain initial approximation from rough asymptotic */ w = log(x); if(x > 3.0) w -= log(w); } return halley_iteration(x, w, MAX_ITERS, result); } } int gsl_sf_lambert_Wm1_e(double x, gsl_sf_result * result) { if(x > 0.0) { return gsl_sf_lambert_W0_e(x, result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { static const unsigned int MAX_ITERS = 32; const double one_over_E = 1.0/M_E; const double q = x + one_over_E; double w; if (q < 0.0) { /* As in the W0 branch above, return some reasonable answer anyway. */ result->val = -1.0; result->err = sqrt(-q); return GSL_EDOM; } if(x < -1.0e-6) { /* Obtain initial approximation from series about q = 0, * as long as we're not very close to x = 0. * Use full series and try to bail out if q is too small, * since the Halley iteration has bad convergence properties * in finite arithmetic for q very small, because the * increment alternates and p is near zero. */ const double r = -sqrt(q); w = series_eval(r); if(q < 3.0e-3) { /* this approximation is good enough */ result->val = w; result->err = 5.0 * GSL_DBL_EPSILON * fabs(w); return GSL_SUCCESS; } } else { /* Obtain initial approximation from asymptotic near zero. */ const double L_1 = log(-x); const double L_2 = log(-L_1); w = L_1 - L_2 + L_2/L_1; } return halley_iteration(x, w, MAX_ITERS, result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_lambert_W0(double x) { EVAL_RESULT(gsl_sf_lambert_W0_e(x, &result)); } double gsl_sf_lambert_Wm1(double x) { EVAL_RESULT(gsl_sf_lambert_Wm1_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__zgerc.c0000664000176700017670000000054111723710247017766 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zgerc (const enum CBLAS_ORDER order, const int M, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda) { #define BASE double #include "gsl_cblas__source_gerc.h" #undef BASE } sources_5316/external/gsl/gsl_permute_complex_double.h0000664000176700017670000000273111705263724022126 0ustar paulpaul/* permutation/gsl_permute_complex_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_COMPLEX_DOUBLE_H__ #define __GSL_PERMUTE_COMPLEX_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_complex (const size_t * p, double * data, const size_t stride, const size_t n); int gsl_permute_complex_inverse (const size_t * p, double * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_COMPLEX_DOUBLE_H__ */ sources_5316/external/gsl/gsl_cblas__dtpsv.c0000664000176700017670000000056511723710247020022 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dtpsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const double *Ap, double *X, const int incX) { #define BASE double #include "gsl_cblas__source_tpsv_r.h" #undef BASE } sources_5316/external/gsl/gsl_multifit__fdfsolver.c0000664000176700017670000001005011723710247021413 0ustar paulpaul/* multifit/fdfsolver.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_multifit_nlin.h" gsl_multifit_fdfsolver * gsl_multifit_fdfsolver_alloc (const gsl_multifit_fdfsolver_type * T, size_t n, size_t p) { int status; gsl_multifit_fdfsolver * s; if (n < p) { GSL_ERROR_VAL ("insufficient data points, n < p", GSL_EINVAL, 0); } s = (gsl_multifit_fdfsolver *) malloc (sizeof (gsl_multifit_fdfsolver)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for multifit solver struct", GSL_ENOMEM, 0); } s->x = gsl_vector_calloc (p); if (s->x == 0) { free (s); GSL_ERROR_VAL ("failed to allocate space for x", GSL_ENOMEM, 0); } s->f = gsl_vector_calloc (n); if (s->f == 0) { gsl_vector_free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for f", GSL_ENOMEM, 0); } s->J = gsl_matrix_calloc (n,p); if (s->J == 0) { gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); GSL_ERROR_VAL ("failed to allocate space for g", GSL_ENOMEM, 0); } s->dx = gsl_vector_calloc (p); if (s->dx == 0) { gsl_matrix_free (s->J); gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); GSL_ERROR_VAL ("failed to allocate space for dx", GSL_ENOMEM, 0); } s->state = malloc (T->size); if (s->state == 0) { gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); gsl_matrix_free (s->J); free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for multifit solver state", GSL_ENOMEM, 0); } s->type = T ; status = (s->type->alloc)(s->state, n, p); if (status != GSL_SUCCESS) { free (s->state); gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); gsl_matrix_free (s->J); free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to set solver", status, 0); } s->fdf = NULL; return s; } int gsl_multifit_fdfsolver_set (gsl_multifit_fdfsolver * s, gsl_multifit_function_fdf * f, const gsl_vector * x) { if (s->f->size != f->n) { GSL_ERROR ("function size does not match solver", GSL_EBADLEN); } if (s->x->size != x->size) { GSL_ERROR ("vector length does not match solver", GSL_EBADLEN); } s->fdf = f; gsl_vector_memcpy(s->x,x); return (s->type->set) (s->state, s->fdf, s->x, s->f, s->J, s->dx); } int gsl_multifit_fdfsolver_iterate (gsl_multifit_fdfsolver * s) { return (s->type->iterate) (s->state, s->fdf, s->x, s->f, s->J, s->dx); } void gsl_multifit_fdfsolver_free (gsl_multifit_fdfsolver * s) { (s->type->free) (s->state); free (s->state); gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); gsl_matrix_free (s->J); free (s); } const char * gsl_multifit_fdfsolver_name (const gsl_multifit_fdfsolver * s) { return s->type->name; } gsl_vector * gsl_multifit_fdfsolver_position (const gsl_multifit_fdfsolver * s) { return s->x; } sources_5316/external/gsl/gsl_matrix__swap.c0000664000176700017670000000365611723710247020060 0ustar paulpaul#include "gsl__config.h" #include "gsl_matrix.h" #include "gsl_vector.h" #include "gsl_errno.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__swap_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_complex__results.h0000664000176700017670000172367211705263724020772 0ustar paulpaul {FN (sqrt), ARG(0.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (sqrt), ARG(0.0e+00,1.19209289550781250e-07), RES(2.44140625e-4, 2.44140625e-4)}, {FN (sqrt), ARG(0.0e+00,-1.19209289550781250e-07), RES(2.44140625e-4, -2.44140625e-4)}, {FN (sqrt), ARG(0.0e+00,5.0e-01), RES(5e-1, 5e-1)}, {FN (sqrt), ARG(0.0e+00,-5.0e-01), RES(5e-1, -5e-1)}, {FN (sqrt), ARG(0.0e+00,1.0e+00), RES(7.0710678118654752440e-1, 7.0710678118654752440e-1)}, {FN (sqrt), ARG(0.0e+00,-1.0e+00), RES(7.0710678118654752440e-1, -7.0710678118654752440e-1)}, {FN (sqrt), ARG(0.0e+00,2.0e+00), RES(1, 1)}, {FN (sqrt), ARG(0.0e+00,-2.0e+00), RES(1, -1)}, {FN (sqrt), ARG(0.0e+00,8.3886080e+06), RES(2048, 2048)}, {FN (sqrt), ARG(0.0e+00,-8.3886080e+06), RES(2048, -2048)}, {FN (sqrt), ARG(1.19209289550781250e-07,0.0e+00), RES(3.4526698300124390840e-4, 0.0)}, {FN (sqrt), ARG(-1.19209289550781250e-07,0.0e+00), RES(0, 3.4526698300124390840e-4)}, {FN (sqrt), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(3.7933934912842707699e-4, 1.5712750315077700799e-4)}, {FN (sqrt), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(3.7933934912842707699e-4, -1.5712750315077700799e-4)}, {FN (sqrt), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(1.5712750315077700799e-4, 3.7933934912842707699e-4)}, {FN (sqrt), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.5712750315077700799e-4, -3.7933934912842707699e-4)}, {FN (sqrt), ARG(1.19209289550781250e-07,5.0e-01), RES(5.0000005960464832810e-1, 4.9999994039535877732e-1)}, {FN (sqrt), ARG(1.19209289550781250e-07,-5.0e-01), RES(5.0000005960464832810e-1, -4.9999994039535877732e-1)}, {FN (sqrt), ARG(-1.19209289550781250e-07,5.0e-01), RES(4.9999994039535877732e-1, 5.0000005960464832810e-1)}, {FN (sqrt), ARG(-1.19209289550781250e-07,-5.0e-01), RES(4.9999994039535877732e-1, -5.0000005960464832810e-1)}, {FN (sqrt), ARG(1.19209289550781250e-07,1.0e+00), RES(7.0710682333339729137e-1, 7.0710673903970026958e-1)}, {FN (sqrt), ARG(1.19209289550781250e-07,-1.0e+00), RES(7.0710682333339729137e-1, -7.0710673903970026958e-1)}, {FN (sqrt), ARG(-1.19209289550781250e-07,1.0e+00), RES(7.0710673903970026958e-1, 7.0710682333339729137e-1)}, {FN (sqrt), ARG(-1.19209289550781250e-07,-1.0e+00), RES(7.0710673903970026958e-1, -7.0710682333339729137e-1)}, {FN (sqrt), ARG(1.19209289550781250e-07,2.0e+00), RES(1.0000000298023228318e0, 9.9999997019767805639e-1)}, {FN (sqrt), ARG(1.19209289550781250e-07,-2.0e+00), RES(1.0000000298023228318e0, -9.9999997019767805639e-1)}, {FN (sqrt), ARG(-1.19209289550781250e-07,2.0e+00), RES(9.9999997019767805639e-1, 1.0000000298023228318e0)}, {FN (sqrt), ARG(-1.19209289550781250e-07,-2.0e+00), RES(9.9999997019767805639e-1, -1.0000000298023228318e0)}, {FN (sqrt), ARG(1.19209289550781250e-07,8.3886080e+06), RES(2.0480000000000145519e3, 2.0479999999999854481e3)}, {FN (sqrt), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(2.0480000000000145519e3, -2.0479999999999854481e3)}, {FN (sqrt), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(2.0479999999999854481e3, 2.0480000000000145519e3)}, {FN (sqrt), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(2.0479999999999854481e3, -2.0480000000000145519e3)}, {FN (sqrt), ARG(5.0e-01,0.0e+00), RES(7.0710678118654752440e-1, 0.0)}, {FN (sqrt), ARG(-5.0e-01,0.0e+00), RES(0, 7.0710678118654752440e-1)}, {FN (sqrt), ARG(5.0e-01,1.19209289550781250e-07), RES(7.0710678118655254870e-1, 8.4293697021787464631e-8)}, {FN (sqrt), ARG(5.0e-01,-1.19209289550781250e-07), RES(7.0710678118655254870e-1, -8.4293697021787464631e-8)}, {FN (sqrt), ARG(-5.0e-01,1.19209289550781250e-07), RES(8.4293697021787464631e-8, 7.0710678118655254870e-1)}, {FN (sqrt), ARG(-5.0e-01,-1.19209289550781250e-07), RES(8.4293697021787464631e-8, -7.0710678118655254870e-1)}, {FN (sqrt), ARG(5.0e-01,5.0e-01), RES(7.7688698701501865367e-1, 3.2179712645279131237e-1)}, {FN (sqrt), ARG(5.0e-01,-5.0e-01), RES(7.7688698701501865367e-1, -3.2179712645279131237e-1)}, {FN (sqrt), ARG(-5.0e-01,5.0e-01), RES(3.2179712645279131237e-1, 7.7688698701501865367e-1)}, {FN (sqrt), ARG(-5.0e-01,-5.0e-01), RES(3.2179712645279131237e-1, -7.7688698701501865367e-1)}, {FN (sqrt), ARG(5.0e-01,1.0e+00), RES(8.9945371997393363613e-1, 5.5589297025142117199e-1)}, {FN (sqrt), ARG(5.0e-01,-1.0e+00), RES(8.9945371997393363613e-1, -5.5589297025142117199e-1)}, {FN (sqrt), ARG(-5.0e-01,1.0e+00), RES(5.5589297025142117199e-1, 8.9945371997393363613e-1)}, {FN (sqrt), ARG(-5.0e-01,-1.0e+00), RES(5.5589297025142117199e-1, -8.9945371997393363613e-1)}, {FN (sqrt), ARG(5.0e-01,2.0e+00), RES(1.1317139242778694103e0, 8.8361553087551326576e-1)}, {FN (sqrt), ARG(5.0e-01,-2.0e+00), RES(1.1317139242778694103e0, -8.8361553087551326576e-1)}, {FN (sqrt), ARG(-5.0e-01,2.0e+00), RES(8.8361553087551326576e-1, 1.1317139242778694103e0)}, {FN (sqrt), ARG(-5.0e-01,-2.0e+00), RES(8.8361553087551326576e-1, -1.1317139242778694103e0)}, {FN (sqrt), ARG(5.0e-01,8.3886080e+06), RES(2.0480000610351571595e3, 2.0479999389648446595e3)}, {FN (sqrt), ARG(5.0e-01,-8.3886080e+06), RES(2.0480000610351571595e3, -2.0479999389648446595e3)}, {FN (sqrt), ARG(-5.0e-01,8.3886080e+06), RES(2.0479999389648446595e3, 2.0480000610351571595e3)}, {FN (sqrt), ARG(-5.0e-01,-8.3886080e+06), RES(2.0479999389648446595e3, -2.0480000610351571595e3)}, {FN (sqrt), ARG(1.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (sqrt), ARG(-1.0e+00,0.0e+00), RES(0, 1)}, {FN (sqrt), ARG(1.0e+00,1.19209289550781250e-07), RES(1.0000000000000017764e0, 5.9604644775390519121e-8)}, {FN (sqrt), ARG(1.0e+00,-1.19209289550781250e-07), RES(1.0000000000000017764e0, -5.9604644775390519121e-8)}, {FN (sqrt), ARG(-1.0e+00,1.19209289550781250e-07), RES(5.9604644775390519121e-8, 1.0000000000000017764e0)}, {FN (sqrt), ARG(-1.0e+00,-1.19209289550781250e-07), RES(5.9604644775390519121e-8, -1.0000000000000017764e0)}, {FN (sqrt), ARG(1.0e+00,5.0e-01), RES(1.0290855136357461252e0, 2.4293413587832283909e-1)}, {FN (sqrt), ARG(1.0e+00,-5.0e-01), RES(1.0290855136357461252e0, -2.4293413587832283909e-1)}, {FN (sqrt), ARG(-1.0e+00,5.0e-01), RES(2.4293413587832283909e-1, 1.0290855136357461252e0)}, {FN (sqrt), ARG(-1.0e+00,-5.0e-01), RES(2.4293413587832283909e-1, -1.0290855136357461252e0)}, {FN (sqrt), ARG(1.0e+00,1.0e+00), RES(1.0986841134678099660e0, 4.5508986056222734130e-1)}, {FN (sqrt), ARG(1.0e+00,-1.0e+00), RES(1.0986841134678099660e0, -4.5508986056222734130e-1)}, {FN (sqrt), ARG(-1.0e+00,1.0e+00), RES(4.5508986056222734130e-1, 1.0986841134678099660e0)}, {FN (sqrt), ARG(-1.0e+00,-1.0e+00), RES(4.5508986056222734130e-1, -1.0986841134678099660e0)}, {FN (sqrt), ARG(1.0e+00,2.0e+00), RES(1.2720196495140689643e0, 7.8615137775742328607e-1)}, {FN (sqrt), ARG(1.0e+00,-2.0e+00), RES(1.2720196495140689643e0, -7.8615137775742328607e-1)}, {FN (sqrt), ARG(-1.0e+00,2.0e+00), RES(7.8615137775742328607e-1, 1.2720196495140689643e0)}, {FN (sqrt), ARG(-1.0e+00,-2.0e+00), RES(7.8615137775742328607e-1, -1.2720196495140689643e0)}, {FN (sqrt), ARG(1.0e+00,8.3886080e+06), RES(2.0480001220703161380e3, 2.0479998779296911380e3)}, {FN (sqrt), ARG(1.0e+00,-8.3886080e+06), RES(2.0480001220703161380e3, -2.0479998779296911380e3)}, {FN (sqrt), ARG(-1.0e+00,8.3886080e+06), RES(2.0479998779296911380e3, 2.0480001220703161380e3)}, {FN (sqrt), ARG(-1.0e+00,-8.3886080e+06), RES(2.0479998779296911380e3, -2.0480001220703161380e3)}, {FN (sqrt), ARG(2.0e+00,0.0e+00), RES(1.4142135623730950488e0, 0.0)}, {FN (sqrt), ARG(-2.0e+00,0.0e+00), RES(0, 1.4142135623730950488e0)}, {FN (sqrt), ARG(2.0e+00,1.19209289550781250e-07), RES(1.4142135623730956768e0, 4.2146848510894013070e-8)}, {FN (sqrt), ARG(2.0e+00,-1.19209289550781250e-07), RES(1.4142135623730956768e0, -4.2146848510894013070e-8)}, {FN (sqrt), ARG(-2.0e+00,1.19209289550781250e-07), RES(4.2146848510894013070e-8, 1.4142135623730956768e0)}, {FN (sqrt), ARG(-2.0e+00,-1.19209289550781250e-07), RES(4.2146848510894013070e-8, -1.4142135623730956768e0)}, {FN (sqrt), ARG(2.0e+00,5.0e-01), RES(1.4250531240639470060e0, 1.7543205637629383228e-1)}, {FN (sqrt), ARG(2.0e+00,-5.0e-01), RES(1.4250531240639470060e0, -1.7543205637629383228e-1)}, {FN (sqrt), ARG(-2.0e+00,5.0e-01), RES(1.7543205637629383228e-1, 1.4250531240639470060e0)}, {FN (sqrt), ARG(-2.0e+00,-5.0e-01), RES(1.7543205637629383228e-1, -1.4250531240639470060e0)}, {FN (sqrt), ARG(2.0e+00,1.0e+00), RES(1.4553466902253548081e0, 3.4356074972251246414e-1)}, {FN (sqrt), ARG(2.0e+00,-1.0e+00), RES(1.4553466902253548081e0, -3.4356074972251246414e-1)}, {FN (sqrt), ARG(-2.0e+00,1.0e+00), RES(3.4356074972251246414e-1, 1.4553466902253548081e0)}, {FN (sqrt), ARG(-2.0e+00,-1.0e+00), RES(3.4356074972251246414e-1, -1.4553466902253548081e0)}, {FN (sqrt), ARG(2.0e+00,2.0e+00), RES(1.5537739740300373073e0, 6.4359425290558262474e-1)}, {FN (sqrt), ARG(2.0e+00,-2.0e+00), RES(1.5537739740300373073e0, -6.4359425290558262474e-1)}, {FN (sqrt), ARG(-2.0e+00,2.0e+00), RES(6.4359425290558262474e-1, 1.5537739740300373073e0)}, {FN (sqrt), ARG(-2.0e+00,-2.0e+00), RES(6.4359425290558262474e-1, -1.5537739740300373073e0)}, {FN (sqrt), ARG(2.0e+00,8.3886080e+06), RES(2.0480002441406395519e3, 2.0479997558593895519e3)}, {FN (sqrt), ARG(2.0e+00,-8.3886080e+06), RES(2.0480002441406395519e3, -2.0479997558593895519e3)}, {FN (sqrt), ARG(-2.0e+00,8.3886080e+06), RES(2.0479997558593895519e3, 2.0480002441406395519e3)}, {FN (sqrt), ARG(-2.0e+00,-8.3886080e+06), RES(2.0479997558593895519e3, -2.0480002441406395519e3)}, {FN (sqrt), ARG(8.3886080e+06,0.0e+00), RES(2.8963093757400986599e3, 0.0)}, {FN (sqrt), ARG(-8.3886080e+06,0.0e+00), RES(0, 2.8963093757400986599e3)}, {FN (sqrt), ARG(8.3886080e+06,1.19209289550781250e-07), RES(2.8963093757400986599e3, 2.0579515874459976458e-11)}, {FN (sqrt), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(2.8963093757400986599e3, -2.0579515874459976458e-11)}, {FN (sqrt), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(2.0579515874459976458e-11, 2.8963093757400986599e3)}, {FN (sqrt), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(2.0579515874459976458e-11, -2.8963093757400986599e3)}, {FN (sqrt), ARG(8.3886080e+06,5.0e-01), RES(2.8963093757400999462e3, 8.6316745750310938767e-5)}, {FN (sqrt), ARG(8.3886080e+06,-5.0e-01), RES(2.8963093757400999462e3, -8.6316745750310938767e-5)}, {FN (sqrt), ARG(-8.3886080e+06,5.0e-01), RES(8.6316745750310938767e-5, 2.8963093757400999462e3)}, {FN (sqrt), ARG(-8.3886080e+06,-5.0e-01), RES(8.6316745750310938767e-5, -2.8963093757400999462e3)}, {FN (sqrt), ARG(8.3886080e+06,1.0e+00), RES(2.8963093757401038048e3, 1.7263349150062164754e-4)}, {FN (sqrt), ARG(8.3886080e+06,-1.0e+00), RES(2.8963093757401038048e3, -1.7263349150062164754e-4)}, {FN (sqrt), ARG(-8.3886080e+06,1.0e+00), RES(1.7263349150062164754e-4, 2.8963093757401038048e3)}, {FN (sqrt), ARG(-8.3886080e+06,-1.0e+00), RES(1.7263349150062164754e-4, -2.8963093757401038048e3)}, {FN (sqrt), ARG(8.3886080e+06,2.0e+00), RES(2.8963093757401192395e3, 3.4526698300124145513e-4)}, {FN (sqrt), ARG(8.3886080e+06,-2.0e+00), RES(2.8963093757401192395e3, -3.4526698300124145513e-4)}, {FN (sqrt), ARG(-8.3886080e+06,2.0e+00), RES(3.4526698300124145513e-4, 2.8963093757401192395e3)}, {FN (sqrt), ARG(-8.3886080e+06,-2.0e+00), RES(3.4526698300124145513e-4, -2.8963093757401192395e3)}, {FN (sqrt), ARG(8.3886080e+06,8.3886080e+06), RES(3.1821290988135164054e3, 1.3180810299506332155e3)}, {FN (sqrt), ARG(8.3886080e+06,-8.3886080e+06), RES(3.1821290988135164054e3, -1.3180810299506332155e3)}, {FN (sqrt), ARG(-8.3886080e+06,8.3886080e+06), RES(1.3180810299506332155e3, 3.1821290988135164054e3)}, {FN (sqrt), ARG(-8.3886080e+06,-8.3886080e+06), RES(1.3180810299506332155e3, -3.1821290988135164054e3)}, {FN (log), ARG(1.19209289550781250e-07,0.0e+00), RES(-1.5942385152878742117e1, 0.0)}, {FN (log), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.5942385152878742117e1, 3.1415926535897932385e0)}, {FN (log), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.5595811562598769462e1, 7.8539816339744830962e-1)}, {FN (log), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.5595811562598769462e1, -7.8539816339744830962e-1)}, {FN (log), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.5595811562598769462e1, 2.3561944901923449288e0)}, {FN (log), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.5595811562598769462e1, -2.3561944901923449288e0)}, {FN (log), ARG(1.19209289550781250e-07,5.0e-01), RES(-6.9314718055991688771e-1, 1.5707960883763175177e0)}, {FN (log), ARG(1.19209289550781250e-07,-5.0e-01), RES(-6.9314718055991688771e-1, -1.5707960883763175177e0)}, {FN (log), ARG(-1.19209289550781250e-07,5.0e-01), RES(-6.9314718055991688771e-1, 1.5707965652134757208e0)}, {FN (log), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-6.9314718055991688771e-1, -1.5707965652134757208e0)}, {FN (log), ARG(1.19209289550781250e-07,1.0e+00), RES(7.1054273576009513716e-15, 1.5707962075856070685e0)}, {FN (log), ARG(1.19209289550781250e-07,-1.0e+00), RES(7.1054273576009513716e-15, -1.5707962075856070685e0)}, {FN (log), ARG(-1.19209289550781250e-07,1.0e+00), RES(7.1054273576009513716e-15, 1.570796446004186170e0)}, {FN (log), ARG(-1.19209289550781250e-07,-1.0e+00), RES(7.1054273576009513716e-15, -1.570796446004186170e0)}, {FN (log), ARG(1.19209289550781250e-07,2.0e+00), RES(6.9314718055994708577e-1, 1.5707962671902518438e0)}, {FN (log), ARG(1.19209289550781250e-07,-2.0e+00), RES(6.9314718055994708577e-1, -1.5707962671902518438e0)}, {FN (log), ARG(-1.19209289550781250e-07,2.0e+00), RES(6.9314718055994708577e-1, 1.5707963863995413946e0)}, {FN (log), ARG(-1.19209289550781250e-07,-2.0e+00), RES(6.9314718055994708577e-1, -1.5707963863995413946e0)}, {FN (log), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.5942385152878742117e1, 1.5707963267948824084e0)}, {FN (log), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.5942385152878742117e1, -1.5707963267948824084e0)}, {FN (log), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(1.5942385152878742117e1, 1.5707963267949108301e0)}, {FN (log), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(1.5942385152878742117e1, -1.5707963267949108301e0)}, {FN (log), ARG(5.0e-01,0.0e+00), RES(-6.9314718055994530942e-1, 0.0)}, {FN (log), ARG(-5.0e-01,0.0e+00), RES(-6.9314718055994530942e-1, 3.1415926535897932385e0)}, {FN (log), ARG(5.0e-01,1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 2.3841857910155798249e-7)}, {FN (log), ARG(5.0e-01,-1.19209289550781250e-07), RES(-6.9314718055991688771e-1, -2.3841857910155798249e-7)}, {FN (log), ARG(-5.0e-01,1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 3.1415924151712141369e0)}, {FN (log), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-6.9314718055991688771e-1, -3.1415924151712141369e0)}, {FN (log), ARG(5.0e-01,5.0e-01), RES(-3.4657359027997265471e-1, 7.8539816339744830962e-1)}, {FN (log), ARG(5.0e-01,-5.0e-01), RES(-3.4657359027997265471e-1, -7.8539816339744830962e-1)}, {FN (log), ARG(-5.0e-01,5.0e-01), RES(-3.4657359027997265471e-1, 2.3561944901923449288e0)}, {FN (log), ARG(-5.0e-01,-5.0e-01), RES(-3.4657359027997265471e-1, -2.3561944901923449288e0)}, {FN (log), ARG(5.0e-01,1.0e+00), RES(1.1157177565710487788e-1, 1.1071487177940905030e0)}, {FN (log), ARG(5.0e-01,-1.0e+00), RES(1.1157177565710487788e-1, -1.1071487177940905030e0)}, {FN (log), ARG(-5.0e-01,1.0e+00), RES(1.1157177565710487788e-1, 2.0344439357957027354e0)}, {FN (log), ARG(-5.0e-01,-1.0e+00), RES(1.1157177565710487788e-1, -2.0344439357957027354e0)}, {FN (log), ARG(5.0e-01,2.0e+00), RES(7.2345949146816273071e-1, 1.3258176636680324651e0)}, {FN (log), ARG(5.0e-01,-2.0e+00), RES(7.2345949146816273071e-1, -1.3258176636680324651e0)}, {FN (log), ARG(-5.0e-01,2.0e+00), RES(7.2345949146816273071e-1, 1.8157749899217607734e0)}, {FN (log), ARG(-5.0e-01,-2.0e+00), RES(7.2345949146816273071e-1, -1.8157749899217607734e0)}, {FN (log), ARG(5.0e-01,8.3886080e+06), RES(1.5942385152878743893e1, 1.5707962671902518438e0)}, {FN (log), ARG(5.0e-01,-8.3886080e+06), RES(1.5942385152878743893e1, -1.5707962671902518438e0)}, {FN (log), ARG(-5.0e-01,8.3886080e+06), RES(1.5942385152878743893e1, 1.5707963863995413946e0)}, {FN (log), ARG(-5.0e-01,-8.3886080e+06), RES(1.5942385152878743893e1, -1.5707963863995413946e0)}, {FN (log), ARG(1.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (log), ARG(-1.0e+00,0.0e+00), RES(0, 3.1415926535897932385e0)}, {FN (log), ARG(1.0e+00,1.19209289550781250e-07), RES(7.1054273576009513716e-15, 1.1920928955078068531e-7)}, {FN (log), ARG(1.0e+00,-1.19209289550781250e-07), RES(7.1054273576009513716e-15, -1.1920928955078068531e-7)}, {FN (log), ARG(-1.0e+00,1.19209289550781250e-07), RES(7.1054273576009513716e-15, 3.1415925343805036877e0)}, {FN (log), ARG(-1.0e+00,-1.19209289550781250e-07), RES(7.1054273576009513716e-15, -3.1415925343805036877e0)}, {FN (log), ARG(1.0e+00,5.0e-01), RES(1.1157177565710487788e-1, 4.6364760900080611621e-1)}, {FN (log), ARG(1.0e+00,-5.0e-01), RES(1.1157177565710487788e-1, -4.6364760900080611621e-1)}, {FN (log), ARG(-1.0e+00,5.0e-01), RES(1.1157177565710487788e-1, 2.6779450445889871222e0)}, {FN (log), ARG(-1.0e+00,-5.0e-01), RES(1.1157177565710487788e-1, -2.6779450445889871222e0)}, {FN (log), ARG(1.0e+00,1.0e+00), RES(3.4657359027997265471e-1, 7.8539816339744830962e-1)}, {FN (log), ARG(1.0e+00,-1.0e+00), RES(3.4657359027997265471e-1, -7.8539816339744830962e-1)}, {FN (log), ARG(-1.0e+00,1.0e+00), RES(3.4657359027997265471e-1, 2.3561944901923449288e0)}, {FN (log), ARG(-1.0e+00,-1.0e+00), RES(3.4657359027997265471e-1, -2.3561944901923449288e0)}, {FN (log), ARG(1.0e+00,2.0e+00), RES(8.0471895621705018730e-1, 1.1071487177940905030e0)}, {FN (log), ARG(1.0e+00,-2.0e+00), RES(8.0471895621705018730e-1, -1.1071487177940905030e0)}, {FN (log), ARG(-1.0e+00,2.0e+00), RES(8.0471895621705018730e-1, 2.0344439357957027354e0)}, {FN (log), ARG(-1.0e+00,-2.0e+00), RES(8.0471895621705018730e-1, -2.0344439357957027354e0)}, {FN (log), ARG(1.0e+00,8.3886080e+06), RES(1.5942385152878749222e1, 1.5707962075856070685e0)}, {FN (log), ARG(1.0e+00,-8.3886080e+06), RES(1.5942385152878749222e1, -1.5707962075856070685e0)}, {FN (log), ARG(-1.0e+00,8.3886080e+06), RES(1.5942385152878749222e1, 1.570796446004186170e0)}, {FN (log), ARG(-1.0e+00,-8.3886080e+06), RES(1.5942385152878749222e1, -1.570796446004186170e0)}, {FN (log), ARG(2.0e+00,0.0e+00), RES(6.9314718055994530942e-1, 0.0)}, {FN (log), ARG(-2.0e+00,0.0e+00), RES(6.9314718055994530942e-1, 3.1415926535897932385e0)}, {FN (log), ARG(2.0e+00,1.19209289550781250e-07), RES(6.9314718055994708577e-1, 5.9604644775390554414e-8)}, {FN (log), ARG(2.0e+00,-1.19209289550781250e-07), RES(6.9314718055994708577e-1, -5.9604644775390554414e-8)}, {FN (log), ARG(-2.0e+00,1.19209289550781250e-07), RES(6.9314718055994708577e-1, 3.1415925939851484631e0)}, {FN (log), ARG(-2.0e+00,-1.19209289550781250e-07), RES(6.9314718055994708577e-1, -3.1415925939851484631e0)}, {FN (log), ARG(2.0e+00,5.0e-01), RES(7.2345949146816273071e-1, 2.4497866312686415417e-1)}, {FN (log), ARG(2.0e+00,-5.0e-01), RES(7.2345949146816273071e-1, -2.4497866312686415417e-1)}, {FN (log), ARG(-2.0e+00,5.0e-01), RES(7.2345949146816273071e-1, 2.8966139904629290843e0)}, {FN (log), ARG(-2.0e+00,-5.0e-01), RES(7.2345949146816273071e-1, -2.8966139904629290843e0)}, {FN (log), ARG(2.0e+00,1.0e+00), RES(8.0471895621705018730e-1, 4.6364760900080611621e-1)}, {FN (log), ARG(2.0e+00,-1.0e+00), RES(8.0471895621705018730e-1, -4.6364760900080611621e-1)}, {FN (log), ARG(-2.0e+00,1.0e+00), RES(8.0471895621705018730e-1, 2.6779450445889871222e0)}, {FN (log), ARG(-2.0e+00,-1.0e+00), RES(8.0471895621705018730e-1, -2.6779450445889871222e0)}, {FN (log), ARG(2.0e+00,2.0e+00), RES(1.0397207708399179641e0, 7.8539816339744830962e-1)}, {FN (log), ARG(2.0e+00,-2.0e+00), RES(1.0397207708399179641e0, -7.8539816339744830962e-1)}, {FN (log), ARG(-2.0e+00,2.0e+00), RES(1.0397207708399179641e0, 2.3561944901923449288e0)}, {FN (log), ARG(-2.0e+00,-2.0e+00), RES(1.0397207708399179641e0, -2.3561944901923449288e0)}, {FN (log), ARG(2.0e+00,8.3886080e+06), RES(1.5942385152878770538e1, 1.5707960883763175177e0)}, {FN (log), ARG(2.0e+00,-8.3886080e+06), RES(1.5942385152878770538e1, -1.5707960883763175177e0)}, {FN (log), ARG(-2.0e+00,8.3886080e+06), RES(1.5942385152878770538e1, 1.5707965652134757208e0)}, {FN (log), ARG(-2.0e+00,-8.3886080e+06), RES(1.5942385152878770538e1, -1.5707965652134757208e0)}, {FN (log), ARG(8.3886080e+06,0.0e+00), RES(1.5942385152878742117e1, 0.0)}, {FN (log), ARG(-8.3886080e+06,0.0e+00), RES(1.5942385152878742117e1, 3.1415926535897932385e0)}, {FN (log), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.5942385152878742117e1, 1.4210854715202003717e-14)}, {FN (log), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.5942385152878742117e1, -1.4210854715202003717e-14)}, {FN (log), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(1.5942385152878742117e1, 3.1415926535897790276e0)}, {FN (log), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(1.5942385152878742117e1, -3.1415926535897790276e0)}, {FN (log), ARG(8.3886080e+06,5.0e-01), RES(1.5942385152878743893e1, 5.9604644775390554414e-8)}, {FN (log), ARG(8.3886080e+06,-5.0e-01), RES(1.5942385152878743893e1, -5.9604644775390554414e-8)}, {FN (log), ARG(-8.3886080e+06,5.0e-01), RES(1.5942385152878743893e1, 3.1415925939851484631e0)}, {FN (log), ARG(-8.3886080e+06,-5.0e-01), RES(1.5942385152878743893e1, -3.1415925939851484631e0)}, {FN (log), ARG(8.3886080e+06,1.0e+00), RES(1.5942385152878749222e1, 1.1920928955078068531e-7)}, {FN (log), ARG(8.3886080e+06,-1.0e+00), RES(1.5942385152878749222e1, -1.1920928955078068531e-7)}, {FN (log), ARG(-8.3886080e+06,1.0e+00), RES(1.5942385152878749222e1, 3.1415925343805036877e0)}, {FN (log), ARG(-8.3886080e+06,-1.0e+00), RES(1.5942385152878749222e1, -3.1415925343805036877e0)}, {FN (log), ARG(8.3886080e+06,2.0e+00), RES(1.5942385152878770538e1, 2.3841857910155798249e-7)}, {FN (log), ARG(8.3886080e+06,-2.0e+00), RES(1.5942385152878770538e1, -2.3841857910155798249e-7)}, {FN (log), ARG(-8.3886080e+06,2.0e+00), RES(1.5942385152878770538e1, 3.1415924151712141369e0)}, {FN (log), ARG(-8.3886080e+06,-2.0e+00), RES(1.5942385152878770538e1, -3.1415924151712141369e0)}, {FN (log), ARG(8.3886080e+06,8.3886080e+06), RES(1.6288958743158714771e1, 7.8539816339744830962e-1)}, {FN (log), ARG(8.3886080e+06,-8.3886080e+06), RES(1.6288958743158714771e1, -7.8539816339744830962e-1)}, {FN (log), ARG(-8.3886080e+06,8.3886080e+06), RES(1.6288958743158714771e1, 2.3561944901923449288e0)}, {FN (log), ARG(-8.3886080e+06,-8.3886080e+06), RES(1.6288958743158714771e1, -2.3561944901923449288e0)}, {FN (log), ARG(0.0e+00,1.19209289550781250e-07), RES(-1.5942385152878742117e1, 1.5707963267948966192e0)}, {FN (log), ARG(0.0e+00,-1.19209289550781250e-07), RES(-1.5942385152878742117e1, -1.5707963267948966192e0)}, {FN (log), ARG(0.0e+00,5.0e-01), RES(-6.9314718055994530942e-1, 1.5707963267948966192e0)}, {FN (log), ARG(0.0e+00,-5.0e-01), RES(-6.9314718055994530942e-1, -1.5707963267948966192e0)}, {FN (log), ARG(0.0e+00,1.0e+00), RES(0, 1.5707963267948966192e0)}, {FN (log), ARG(0.0e+00,-1.0e+00), RES(0, -1.5707963267948966192e0)}, {FN (log), ARG(0.0e+00,2.0e+00), RES(6.9314718055994530942e-1, 1.5707963267948966192e0)}, {FN (log), ARG(0.0e+00,-2.0e+00), RES(6.9314718055994530942e-1, -1.5707963267948966192e0)}, {FN (log), ARG(0.0e+00,8.3886080e+06), RES(1.5942385152878742117e1, 1.5707963267948966192e0)}, {FN (log), ARG(0.0e+00,-8.3886080e+06), RES(1.5942385152878742117e1, -1.5707963267948966192e0)}, {FN (log), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.5595811562598769462e1, 7.8539816339744830962e-1)}, {FN (log), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.5595811562598769462e1, -7.8539816339744830962e-1)}, {FN (log), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.5595811562598769462e1, 2.3561944901923449288e0)}, {FN (log), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.5595811562598769462e1, -2.3561944901923449288e0)}, {FN (log), ARG(1.19209289550781250e-07,5.0e-01), RES(-6.9314718055991688771e-1, 1.5707960883763175177e0)}, {FN (log), ARG(1.19209289550781250e-07,-5.0e-01), RES(-6.9314718055991688771e-1, -1.5707960883763175177e0)}, {FN (log), ARG(-1.19209289550781250e-07,5.0e-01), RES(-6.9314718055991688771e-1, 1.5707965652134757208e0)}, {FN (log), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-6.9314718055991688771e-1, -1.5707965652134757208e0)}, {FN (log), ARG(1.19209289550781250e-07,1.0e+00), RES(7.1054273576009513716e-15, 1.5707962075856070685e0)}, {FN (log), ARG(1.19209289550781250e-07,-1.0e+00), RES(7.1054273576009513716e-15, -1.5707962075856070685e0)}, {FN (log), ARG(-1.19209289550781250e-07,1.0e+00), RES(7.1054273576009513716e-15, 1.570796446004186170e0)}, {FN (log), ARG(-1.19209289550781250e-07,-1.0e+00), RES(7.1054273576009513716e-15, -1.570796446004186170e0)}, {FN (log), ARG(1.19209289550781250e-07,2.0e+00), RES(6.9314718055994708577e-1, 1.5707962671902518438e0)}, {FN (log), ARG(1.19209289550781250e-07,-2.0e+00), RES(6.9314718055994708577e-1, -1.5707962671902518438e0)}, {FN (log), ARG(-1.19209289550781250e-07,2.0e+00), RES(6.9314718055994708577e-1, 1.5707963863995413946e0)}, {FN (log), ARG(-1.19209289550781250e-07,-2.0e+00), RES(6.9314718055994708577e-1, -1.5707963863995413946e0)}, {FN (log), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.5942385152878742117e1, 1.5707963267948824084e0)}, {FN (log), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.5942385152878742117e1, -1.5707963267948824084e0)}, {FN (log), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(1.5942385152878742117e1, 1.5707963267949108301e0)}, {FN (log), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(1.5942385152878742117e1, -1.5707963267949108301e0)}, {FN (log), ARG(5.0e-01,1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 2.3841857910155798249e-7)}, {FN (log), ARG(5.0e-01,-1.19209289550781250e-07), RES(-6.9314718055991688771e-1, -2.3841857910155798249e-7)}, {FN (log), ARG(-5.0e-01,1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 3.1415924151712141369e0)}, {FN (log), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-6.9314718055991688771e-1, -3.1415924151712141369e0)}, {FN (log), ARG(5.0e-01,5.0e-01), RES(-3.4657359027997265471e-1, 7.8539816339744830962e-1)}, {FN (log), ARG(5.0e-01,-5.0e-01), RES(-3.4657359027997265471e-1, -7.8539816339744830962e-1)}, {FN (log), ARG(-5.0e-01,5.0e-01), RES(-3.4657359027997265471e-1, 2.3561944901923449288e0)}, {FN (log), ARG(-5.0e-01,-5.0e-01), RES(-3.4657359027997265471e-1, -2.3561944901923449288e0)}, {FN (log), ARG(5.0e-01,1.0e+00), RES(1.1157177565710487788e-1, 1.1071487177940905030e0)}, {FN (log), ARG(5.0e-01,-1.0e+00), RES(1.1157177565710487788e-1, -1.1071487177940905030e0)}, {FN (log), ARG(-5.0e-01,1.0e+00), RES(1.1157177565710487788e-1, 2.0344439357957027354e0)}, {FN (log), ARG(-5.0e-01,-1.0e+00), RES(1.1157177565710487788e-1, -2.0344439357957027354e0)}, {FN (log), ARG(5.0e-01,2.0e+00), RES(7.2345949146816273071e-1, 1.3258176636680324651e0)}, {FN (log), ARG(5.0e-01,-2.0e+00), RES(7.2345949146816273071e-1, -1.3258176636680324651e0)}, {FN (log), ARG(-5.0e-01,2.0e+00), RES(7.2345949146816273071e-1, 1.8157749899217607734e0)}, {FN (log), ARG(-5.0e-01,-2.0e+00), RES(7.2345949146816273071e-1, -1.8157749899217607734e0)}, {FN (log), ARG(5.0e-01,8.3886080e+06), RES(1.5942385152878743893e1, 1.5707962671902518438e0)}, {FN (log), ARG(5.0e-01,-8.3886080e+06), RES(1.5942385152878743893e1, -1.5707962671902518438e0)}, {FN (log), ARG(-5.0e-01,8.3886080e+06), RES(1.5942385152878743893e1, 1.5707963863995413946e0)}, {FN (log), ARG(-5.0e-01,-8.3886080e+06), RES(1.5942385152878743893e1, -1.5707963863995413946e0)}, {FN (log), ARG(1.0e+00,1.19209289550781250e-07), RES(7.1054273576009513716e-15, 1.1920928955078068531e-7)}, {FN (log), ARG(1.0e+00,-1.19209289550781250e-07), RES(7.1054273576009513716e-15, -1.1920928955078068531e-7)}, {FN (log), ARG(-1.0e+00,1.19209289550781250e-07), RES(7.1054273576009513716e-15, 3.1415925343805036877e0)}, {FN (log), ARG(-1.0e+00,-1.19209289550781250e-07), RES(7.1054273576009513716e-15, -3.1415925343805036877e0)}, {FN (log), ARG(1.0e+00,5.0e-01), RES(1.1157177565710487788e-1, 4.6364760900080611621e-1)}, {FN (log), ARG(1.0e+00,-5.0e-01), RES(1.1157177565710487788e-1, -4.6364760900080611621e-1)}, {FN (log), ARG(-1.0e+00,5.0e-01), RES(1.1157177565710487788e-1, 2.6779450445889871222e0)}, {FN (log), ARG(-1.0e+00,-5.0e-01), RES(1.1157177565710487788e-1, -2.6779450445889871222e0)}, {FN (log), ARG(1.0e+00,1.0e+00), RES(3.4657359027997265471e-1, 7.8539816339744830962e-1)}, {FN (log), ARG(1.0e+00,-1.0e+00), RES(3.4657359027997265471e-1, -7.8539816339744830962e-1)}, {FN (log), ARG(-1.0e+00,1.0e+00), RES(3.4657359027997265471e-1, 2.3561944901923449288e0)}, {FN (log), ARG(-1.0e+00,-1.0e+00), RES(3.4657359027997265471e-1, -2.3561944901923449288e0)}, {FN (log), ARG(1.0e+00,2.0e+00), RES(8.0471895621705018730e-1, 1.1071487177940905030e0)}, {FN (log), ARG(1.0e+00,-2.0e+00), RES(8.0471895621705018730e-1, -1.1071487177940905030e0)}, {FN (log), ARG(-1.0e+00,2.0e+00), RES(8.0471895621705018730e-1, 2.0344439357957027354e0)}, {FN (log), ARG(-1.0e+00,-2.0e+00), RES(8.0471895621705018730e-1, -2.0344439357957027354e0)}, {FN (log), ARG(1.0e+00,8.3886080e+06), RES(1.5942385152878749222e1, 1.5707962075856070685e0)}, {FN (log), ARG(1.0e+00,-8.3886080e+06), RES(1.5942385152878749222e1, -1.5707962075856070685e0)}, {FN (log), ARG(-1.0e+00,8.3886080e+06), RES(1.5942385152878749222e1, 1.570796446004186170e0)}, {FN (log), ARG(-1.0e+00,-8.3886080e+06), RES(1.5942385152878749222e1, -1.570796446004186170e0)}, {FN (log), ARG(2.0e+00,1.19209289550781250e-07), RES(6.9314718055994708577e-1, 5.9604644775390554414e-8)}, {FN (log), ARG(2.0e+00,-1.19209289550781250e-07), RES(6.9314718055994708577e-1, -5.9604644775390554414e-8)}, {FN (log), ARG(-2.0e+00,1.19209289550781250e-07), RES(6.9314718055994708577e-1, 3.1415925939851484631e0)}, {FN (log), ARG(-2.0e+00,-1.19209289550781250e-07), RES(6.9314718055994708577e-1, -3.1415925939851484631e0)}, {FN (log), ARG(2.0e+00,5.0e-01), RES(7.2345949146816273071e-1, 2.4497866312686415417e-1)}, {FN (log), ARG(2.0e+00,-5.0e-01), RES(7.2345949146816273071e-1, -2.4497866312686415417e-1)}, {FN (log), ARG(-2.0e+00,5.0e-01), RES(7.2345949146816273071e-1, 2.8966139904629290843e0)}, {FN (log), ARG(-2.0e+00,-5.0e-01), RES(7.2345949146816273071e-1, -2.8966139904629290843e0)}, {FN (log), ARG(2.0e+00,1.0e+00), RES(8.0471895621705018730e-1, 4.6364760900080611621e-1)}, {FN (log), ARG(2.0e+00,-1.0e+00), RES(8.0471895621705018730e-1, -4.6364760900080611621e-1)}, {FN (log), ARG(-2.0e+00,1.0e+00), RES(8.0471895621705018730e-1, 2.6779450445889871222e0)}, {FN (log), ARG(-2.0e+00,-1.0e+00), RES(8.0471895621705018730e-1, -2.6779450445889871222e0)}, {FN (log), ARG(2.0e+00,2.0e+00), RES(1.0397207708399179641e0, 7.8539816339744830962e-1)}, {FN (log), ARG(2.0e+00,-2.0e+00), RES(1.0397207708399179641e0, -7.8539816339744830962e-1)}, {FN (log), ARG(-2.0e+00,2.0e+00), RES(1.0397207708399179641e0, 2.3561944901923449288e0)}, {FN (log), ARG(-2.0e+00,-2.0e+00), RES(1.0397207708399179641e0, -2.3561944901923449288e0)}, {FN (log), ARG(2.0e+00,8.3886080e+06), RES(1.5942385152878770538e1, 1.5707960883763175177e0)}, {FN (log), ARG(2.0e+00,-8.3886080e+06), RES(1.5942385152878770538e1, -1.5707960883763175177e0)}, {FN (log), ARG(-2.0e+00,8.3886080e+06), RES(1.5942385152878770538e1, 1.5707965652134757208e0)}, {FN (log), ARG(-2.0e+00,-8.3886080e+06), RES(1.5942385152878770538e1, -1.5707965652134757208e0)}, {FN (log), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.5942385152878742117e1, 1.4210854715202003717e-14)}, {FN (log), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.5942385152878742117e1, -1.4210854715202003717e-14)}, {FN (log), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(1.5942385152878742117e1, 3.1415926535897790276e0)}, {FN (log), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(1.5942385152878742117e1, -3.1415926535897790276e0)}, {FN (log), ARG(8.3886080e+06,5.0e-01), RES(1.5942385152878743893e1, 5.9604644775390554414e-8)}, {FN (log), ARG(8.3886080e+06,-5.0e-01), RES(1.5942385152878743893e1, -5.9604644775390554414e-8)}, {FN (log), ARG(-8.3886080e+06,5.0e-01), RES(1.5942385152878743893e1, 3.1415925939851484631e0)}, {FN (log), ARG(-8.3886080e+06,-5.0e-01), RES(1.5942385152878743893e1, -3.1415925939851484631e0)}, {FN (log), ARG(8.3886080e+06,1.0e+00), RES(1.5942385152878749222e1, 1.1920928955078068531e-7)}, {FN (log), ARG(8.3886080e+06,-1.0e+00), RES(1.5942385152878749222e1, -1.1920928955078068531e-7)}, {FN (log), ARG(-8.3886080e+06,1.0e+00), RES(1.5942385152878749222e1, 3.1415925343805036877e0)}, {FN (log), ARG(-8.3886080e+06,-1.0e+00), RES(1.5942385152878749222e1, -3.1415925343805036877e0)}, {FN (log), ARG(8.3886080e+06,2.0e+00), RES(1.5942385152878770538e1, 2.3841857910155798249e-7)}, {FN (log), ARG(8.3886080e+06,-2.0e+00), RES(1.5942385152878770538e1, -2.3841857910155798249e-7)}, {FN (log), ARG(-8.3886080e+06,2.0e+00), RES(1.5942385152878770538e1, 3.1415924151712141369e0)}, {FN (log), ARG(-8.3886080e+06,-2.0e+00), RES(1.5942385152878770538e1, -3.1415924151712141369e0)}, {FN (log), ARG(8.3886080e+06,8.3886080e+06), RES(1.6288958743158714771e1, 7.8539816339744830962e-1)}, {FN (log), ARG(8.3886080e+06,-8.3886080e+06), RES(1.6288958743158714771e1, -7.8539816339744830962e-1)}, {FN (log), ARG(-8.3886080e+06,8.3886080e+06), RES(1.6288958743158714771e1, 2.3561944901923449288e0)}, {FN (log), ARG(-8.3886080e+06,-8.3886080e+06), RES(1.6288958743158714771e1, -2.3561944901923449288e0)}, {FN (log10), ARG(1.19209289550781250e-07,0.0e+00), RES(-6.9236899002715674899e0, 0.0)}, {FN (log10), ARG(-1.19209289550781250e-07,0.0e+00), RES(-6.9236899002715674899e0, 1.3643763538418413475e0)}, {FN (log10), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(-6.7731749024395768923e0, 3.4109408846046033687e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(-6.7731749024395768923e0, -3.4109408846046033687e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-6.7731749024395768923e0, 1.0232822653813810106e0)}, {FN (log10), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-6.7731749024395768923e0, -1.0232822653813810106e0)}, {FN (log10), ARG(1.19209289550781250e-07,5.0e-01), RES(-3.0102999566396885182e-1, 6.8218807337704738672e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-5.0e-01), RES(-3.0102999566396885182e-1, -6.8218807337704738672e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,5.0e-01), RES(-3.0102999566396885182e-1, 6.8218828046479396076e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-3.0102999566396885182e-1, -6.8218828046479396076e-1)}, {FN (log10), ARG(1.19209289550781250e-07,1.0e+00), RES(3.0858478929704968280e-15, 6.8218812514898403023e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-1.0e+00), RES(3.0858478929704968280e-15, -6.8218812514898403023e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,1.0e+00), RES(3.0858478929704968280e-15, 6.8218822869285731725e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,-1.0e+00), RES(3.0858478929704968280e-15, -6.8218822869285731725e-1)}, {FN (log10), ARG(1.19209289550781250e-07,2.0e+00), RES(3.0102999566398196668e-1, 6.8218815103495235199e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-2.0e+00), RES(3.0102999566398196668e-1, -6.8218815103495235199e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,2.0e+00), RES(3.0102999566398196668e-1, 6.8218820280688899550e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,-2.0e+00), RES(3.0102999566398196668e-1, -6.8218820280688899550e-1)}, {FN (log10), ARG(1.19209289550781250e-07,8.3886080e+06), RES(6.9236899002715674899e0, 6.8218817692091450205e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(6.9236899002715674899e0, -6.8218817692091450205e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(6.9236899002715674899e0, 6.8218817692092684544e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(6.9236899002715674899e0, -6.8218817692092684544e-1)}, {FN (log10), ARG(5.0e-01,0.0e+00), RES(-3.0102999566398119521e-1, 0.0)}, {FN (log10), ARG(-5.0e-01,0.0e+00), RES(-3.0102999566398119521e-1, 1.3643763538418413475e0)}, {FN (log10), ARG(5.0e-01,1.19209289550781250e-07), RES(-3.0102999566396885182e-1, 1.0354387328702058762e-7)}, {FN (log10), ARG(5.0e-01,-1.19209289550781250e-07), RES(-3.0102999566396885182e-1, -1.0354387328702058762e-7)}, {FN (log10), ARG(-5.0e-01,1.19209289550781250e-07), RES(-3.0102999566396885182e-1, 1.3643762502979680605e0)}, {FN (log10), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-3.0102999566396885182e-1, -1.3643762502979680605e0)}, {FN (log10), ARG(5.0e-01,5.0e-01), RES(-1.5051499783199059761e-1, 3.4109408846046033687e-1)}, {FN (log10), ARG(5.0e-01,-5.0e-01), RES(-1.5051499783199059761e-1, -3.4109408846046033687e-1)}, {FN (log10), ARG(-5.0e-01,5.0e-01), RES(-1.5051499783199059761e-1, 1.0232822653813810106e0)}, {FN (log10), ARG(-5.0e-01,-5.0e-01), RES(-1.5051499783199059761e-1, -1.0232822653813810106e0)}, {FN (log10), ARG(5.0e-01,1.0e+00), RES(4.8455006504028207179e-2, 4.8082857878423410270e-1)}, {FN (log10), ARG(5.0e-01,-1.0e+00), RES(4.8455006504028207179e-2, -4.8082857878423410270e-1)}, {FN (log10), ARG(-5.0e-01,1.0e+00), RES(4.8455006504028207179e-2, 8.8354777505760724478e-1)}, {FN (log10), ARG(-5.0e-01,-1.0e+00), RES(4.8455006504028207179e-2, -8.8354777505760724478e-1)}, {FN (log10), ARG(5.0e-01,2.0e+00), RES(3.1419446502515576906e-1, 5.7579529534088794354e-1)}, {FN (log10), ARG(5.0e-01,-2.0e+00), RES(3.1419446502515576906e-1, -5.7579529534088794354e-1)}, {FN (log10), ARG(-5.0e-01,2.0e+00), RES(3.1419446502515576906e-1, 7.8858105850095340394e-1)}, {FN (log10), ARG(-5.0e-01,-2.0e+00), RES(3.1419446502515576906e-1, -7.8858105850095340394e-1)}, {FN (log10), ARG(5.0e-01,8.3886080e+06), RES(6.9236899002715682614e0, 6.8218815103495235199e-1)}, {FN (log10), ARG(5.0e-01,-8.3886080e+06), RES(6.9236899002715682614e0, -6.8218815103495235199e-1)}, {FN (log10), ARG(-5.0e-01,8.3886080e+06), RES(6.9236899002715682614e0, 6.8218820280688899550e-1)}, {FN (log10), ARG(-5.0e-01,-8.3886080e+06), RES(6.9236899002715682614e0, -6.8218820280688899550e-1)}, {FN (log10), ARG(1.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (log10), ARG(-1.0e+00,0.0e+00), RES(0, 1.3643763538418413475e0)}, {FN (log10), ARG(1.0e+00,1.19209289550781250e-07), RES(3.0858478929704968280e-15, 5.1771936643511029532e-8)}, {FN (log10), ARG(1.0e+00,-1.19209289550781250e-07), RES(3.0858478929704968280e-15, -5.1771936643511029532e-8)}, {FN (log10), ARG(-1.0e+00,1.19209289550781250e-07), RES(3.0858478929704968280e-15, 1.3643763020699047040e0)}, {FN (log10), ARG(-1.0e+00,-1.19209289550781250e-07), RES(3.0858478929704968280e-15, -1.3643763020699047040e0)}, {FN (log10), ARG(1.0e+00,5.0e-01), RES(4.8455006504028207179e-2, 2.0135959813668657104e-1)}, {FN (log10), ARG(1.0e+00,-5.0e-01), RES(4.8455006504028207179e-2, -2.0135959813668657104e-1)}, {FN (log10), ARG(-1.0e+00,5.0e-01), RES(4.8455006504028207179e-2, 1.1630167557051547764e0)}, {FN (log10), ARG(-1.0e+00,-5.0e-01), RES(4.8455006504028207179e-2, -1.1630167557051547764e0)}, {FN (log10), ARG(1.0e+00,1.0e+00), RES(1.5051499783199059761e-1, 3.4109408846046033687e-1)}, {FN (log10), ARG(1.0e+00,-1.0e+00), RES(1.5051499783199059761e-1, -3.4109408846046033687e-1)}, {FN (log10), ARG(-1.0e+00,1.0e+00), RES(1.5051499783199059761e-1, 1.0232822653813810106e0)}, {FN (log10), ARG(-1.0e+00,-1.0e+00), RES(1.5051499783199059761e-1, -1.0232822653813810106e0)}, {FN (log10), ARG(1.0e+00,2.0e+00), RES(3.4948500216800940239e-1, 4.8082857878423410270e-1)}, {FN (log10), ARG(1.0e+00,-2.0e+00), RES(3.4948500216800940239e-1, -4.8082857878423410270e-1)}, {FN (log10), ARG(-1.0e+00,2.0e+00), RES(3.4948500216800940239e-1, 8.8354777505760724478e-1)}, {FN (log10), ARG(-1.0e+00,-2.0e+00), RES(3.4948500216800940239e-1, -8.8354777505760724478e-1)}, {FN (log10), ARG(1.0e+00,8.3886080e+06), RES(6.9236899002715705758e0, 6.8218812514898403023e-1)}, {FN (log10), ARG(1.0e+00,-8.3886080e+06), RES(6.9236899002715705758e0, -6.8218812514898403023e-1)}, {FN (log10), ARG(-1.0e+00,8.3886080e+06), RES(6.9236899002715705758e0, 6.8218822869285731725e-1)}, {FN (log10), ARG(-1.0e+00,-8.3886080e+06), RES(6.9236899002715705758e0, -6.8218822869285731725e-1)}, {FN (log10), ARG(2.0e+00,0.0e+00), RES(3.0102999566398119521e-1, 0.0)}, {FN (log10), ARG(-2.0e+00,0.0e+00), RES(3.0102999566398119521e-1, 1.3643763538418413475e0)}, {FN (log10), ARG(2.0e+00,1.19209289550781250e-07), RES(3.0102999566398196668e-1, 2.5885968321755606731e-8)}, {FN (log10), ARG(2.0e+00,-1.19209289550781250e-07), RES(3.0102999566398196668e-1, -2.5885968321755606731e-8)}, {FN (log10), ARG(-2.0e+00,1.19209289550781250e-07), RES(3.0102999566398196668e-1, 1.3643763279558730257e0)}, {FN (log10), ARG(-2.0e+00,-1.19209289550781250e-07), RES(3.0102999566398196668e-1, -1.3643763279558730257e0)}, {FN (log10), ARG(2.0e+00,5.0e-01), RES(3.1419446502515576906e-1, 1.0639288158003273020e-1)}, {FN (log10), ARG(2.0e+00,-5.0e-01), RES(3.1419446502515576906e-1, -1.0639288158003273020e-1)}, {FN (log10), ARG(-2.0e+00,5.0e-01), RES(3.1419446502515576906e-1, 1.2579834722618086173e0)}, {FN (log10), ARG(-2.0e+00,-5.0e-01), RES(3.1419446502515576906e-1, -1.2579834722618086173e0)}, {FN (log10), ARG(2.0e+00,1.0e+00), RES(3.4948500216800940239e-1, 2.0135959813668657104e-1)}, {FN (log10), ARG(2.0e+00,-1.0e+00), RES(3.4948500216800940239e-1, -2.0135959813668657104e-1)}, {FN (log10), ARG(-2.0e+00,1.0e+00), RES(3.4948500216800940239e-1, 1.1630167557051547764e0)}, {FN (log10), ARG(-2.0e+00,-1.0e+00), RES(3.4948500216800940239e-1, -1.1630167557051547764e0)}, {FN (log10), ARG(2.0e+00,2.0e+00), RES(4.5154499349597179282e-1, 3.4109408846046033687e-1)}, {FN (log10), ARG(2.0e+00,-2.0e+00), RES(4.5154499349597179282e-1, -3.4109408846046033687e-1)}, {FN (log10), ARG(-2.0e+00,2.0e+00), RES(4.5154499349597179282e-1, 1.0232822653813810106e0)}, {FN (log10), ARG(-2.0e+00,-2.0e+00), RES(4.5154499349597179282e-1, -1.0232822653813810106e0)}, {FN (log10), ARG(2.0e+00,8.3886080e+06), RES(6.9236899002715798333e0, 6.8218807337704738672e-1)}, {FN (log10), ARG(2.0e+00,-8.3886080e+06), RES(6.9236899002715798333e0, -6.8218807337704738672e-1)}, {FN (log10), ARG(-2.0e+00,8.3886080e+06), RES(6.9236899002715798333e0, 6.8218828046479396076e-1)}, {FN (log10), ARG(-2.0e+00,-8.3886080e+06), RES(6.9236899002715798333e0, -6.8218828046479396076e-1)}, {FN (log10), ARG(8.3886080e+06,0.0e+00), RES(6.9236899002715674899e0, 0.0)}, {FN (log10), ARG(-8.3886080e+06,0.0e+00), RES(6.9236899002715674899e0, 1.3643763538418413475e0)}, {FN (log10), ARG(8.3886080e+06,1.19209289550781250e-07), RES(6.9236899002715674899e0, 6.1716957859410375086e-15)}, {FN (log10), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(6.9236899002715674899e0, -6.1716957859410375086e-15)}, {FN (log10), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(6.9236899002715674899e0, 1.3643763538418351758e0)}, {FN (log10), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(6.9236899002715674899e0, -1.3643763538418351758e0)}, {FN (log10), ARG(8.3886080e+06,5.0e-01), RES(6.9236899002715682614e0, 2.5885968321755606731e-8)}, {FN (log10), ARG(8.3886080e+06,-5.0e-01), RES(6.9236899002715682614e0, -2.5885968321755606731e-8)}, {FN (log10), ARG(-8.3886080e+06,5.0e-01), RES(6.9236899002715682614e0, 1.3643763279558730257e0)}, {FN (log10), ARG(-8.3886080e+06,-5.0e-01), RES(6.9236899002715682614e0, -1.3643763279558730257e0)}, {FN (log10), ARG(8.3886080e+06,1.0e+00), RES(6.9236899002715705758e0, 5.1771936643511029532e-8)}, {FN (log10), ARG(8.3886080e+06,-1.0e+00), RES(6.9236899002715705758e0, -5.1771936643511029532e-8)}, {FN (log10), ARG(-8.3886080e+06,1.0e+00), RES(6.9236899002715705758e0, 1.3643763020699047040e0)}, {FN (log10), ARG(-8.3886080e+06,-1.0e+00), RES(6.9236899002715705758e0, -1.3643763020699047040e0)}, {FN (log10), ARG(8.3886080e+06,2.0e+00), RES(6.9236899002715798333e0, 1.0354387328702058762e-7)}, {FN (log10), ARG(8.3886080e+06,-2.0e+00), RES(6.9236899002715798333e0, -1.0354387328702058762e-7)}, {FN (log10), ARG(-8.3886080e+06,2.0e+00), RES(6.9236899002715798333e0, 1.3643762502979680605e0)}, {FN (log10), ARG(-8.3886080e+06,-2.0e+00), RES(6.9236899002715798333e0, -1.3643762502979680605e0)}, {FN (log10), ARG(8.3886080e+06,8.3886080e+06), RES(7.0742048981035580875e0, 3.4109408846046033687e-1)}, {FN (log10), ARG(8.3886080e+06,-8.3886080e+06), RES(7.0742048981035580875e0, -3.4109408846046033687e-1)}, {FN (log10), ARG(-8.3886080e+06,8.3886080e+06), RES(7.0742048981035580875e0, 1.0232822653813810106e0)}, {FN (log10), ARG(-8.3886080e+06,-8.3886080e+06), RES(7.0742048981035580875e0, -1.0232822653813810106e0)}, {FN (log10), ARG(0.0e+00,1.19209289550781250e-07), RES(-6.9236899002715674899e0, 6.8218817692092067374e-1)}, {FN (log10), ARG(0.0e+00,-1.19209289550781250e-07), RES(-6.9236899002715674899e0, -6.8218817692092067374e-1)}, {FN (log10), ARG(0.0e+00,5.0e-01), RES(-3.0102999566398119521e-1, 6.8218817692092067374e-1)}, {FN (log10), ARG(0.0e+00,-5.0e-01), RES(-3.0102999566398119521e-1, -6.8218817692092067374e-1)}, {FN (log10), ARG(0.0e+00,1.0e+00), RES(0, 6.8218817692092067374e-1)}, {FN (log10), ARG(0.0e+00,-1.0e+00), RES(0, -6.8218817692092067374e-1)}, {FN (log10), ARG(0.0e+00,2.0e+00), RES(3.0102999566398119521e-1, 6.8218817692092067374e-1)}, {FN (log10), ARG(0.0e+00,-2.0e+00), RES(3.0102999566398119521e-1, -6.8218817692092067374e-1)}, {FN (log10), ARG(0.0e+00,8.3886080e+06), RES(6.9236899002715674899e0, 6.8218817692092067374e-1)}, {FN (log10), ARG(0.0e+00,-8.3886080e+06), RES(6.9236899002715674899e0, -6.8218817692092067374e-1)}, {FN (log10), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(-6.7731749024395768923e0, 3.4109408846046033687e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(-6.7731749024395768923e0, -3.4109408846046033687e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-6.7731749024395768923e0, 1.0232822653813810106e0)}, {FN (log10), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-6.7731749024395768923e0, -1.0232822653813810106e0)}, {FN (log10), ARG(1.19209289550781250e-07,5.0e-01), RES(-3.0102999566396885182e-1, 6.8218807337704738672e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-5.0e-01), RES(-3.0102999566396885182e-1, -6.8218807337704738672e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,5.0e-01), RES(-3.0102999566396885182e-1, 6.8218828046479396076e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-3.0102999566396885182e-1, -6.8218828046479396076e-1)}, {FN (log10), ARG(1.19209289550781250e-07,1.0e+00), RES(3.0858478929704968280e-15, 6.8218812514898403023e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-1.0e+00), RES(3.0858478929704968280e-15, -6.8218812514898403023e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,1.0e+00), RES(3.0858478929704968280e-15, 6.8218822869285731725e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,-1.0e+00), RES(3.0858478929704968280e-15, -6.8218822869285731725e-1)}, {FN (log10), ARG(1.19209289550781250e-07,2.0e+00), RES(3.0102999566398196668e-1, 6.8218815103495235199e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-2.0e+00), RES(3.0102999566398196668e-1, -6.8218815103495235199e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,2.0e+00), RES(3.0102999566398196668e-1, 6.8218820280688899550e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,-2.0e+00), RES(3.0102999566398196668e-1, -6.8218820280688899550e-1)}, {FN (log10), ARG(1.19209289550781250e-07,8.3886080e+06), RES(6.9236899002715674899e0, 6.8218817692091450205e-1)}, {FN (log10), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(6.9236899002715674899e0, -6.8218817692091450205e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(6.9236899002715674899e0, 6.8218817692092684544e-1)}, {FN (log10), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(6.9236899002715674899e0, -6.8218817692092684544e-1)}, {FN (log10), ARG(5.0e-01,1.19209289550781250e-07), RES(-3.0102999566396885182e-1, 1.0354387328702058762e-7)}, {FN (log10), ARG(5.0e-01,-1.19209289550781250e-07), RES(-3.0102999566396885182e-1, -1.0354387328702058762e-7)}, {FN (log10), ARG(-5.0e-01,1.19209289550781250e-07), RES(-3.0102999566396885182e-1, 1.3643762502979680605e0)}, {FN (log10), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-3.0102999566396885182e-1, -1.3643762502979680605e0)}, {FN (log10), ARG(5.0e-01,5.0e-01), RES(-1.5051499783199059761e-1, 3.4109408846046033687e-1)}, {FN (log10), ARG(5.0e-01,-5.0e-01), RES(-1.5051499783199059761e-1, -3.4109408846046033687e-1)}, {FN (log10), ARG(-5.0e-01,5.0e-01), RES(-1.5051499783199059761e-1, 1.0232822653813810106e0)}, {FN (log10), ARG(-5.0e-01,-5.0e-01), RES(-1.5051499783199059761e-1, -1.0232822653813810106e0)}, {FN (log10), ARG(5.0e-01,1.0e+00), RES(4.8455006504028207179e-2, 4.8082857878423410270e-1)}, {FN (log10), ARG(5.0e-01,-1.0e+00), RES(4.8455006504028207179e-2, -4.8082857878423410270e-1)}, {FN (log10), ARG(-5.0e-01,1.0e+00), RES(4.8455006504028207179e-2, 8.8354777505760724478e-1)}, {FN (log10), ARG(-5.0e-01,-1.0e+00), RES(4.8455006504028207179e-2, -8.8354777505760724478e-1)}, {FN (log10), ARG(5.0e-01,2.0e+00), RES(3.1419446502515576906e-1, 5.7579529534088794354e-1)}, {FN (log10), ARG(5.0e-01,-2.0e+00), RES(3.1419446502515576906e-1, -5.7579529534088794354e-1)}, {FN (log10), ARG(-5.0e-01,2.0e+00), RES(3.1419446502515576906e-1, 7.8858105850095340394e-1)}, {FN (log10), ARG(-5.0e-01,-2.0e+00), RES(3.1419446502515576906e-1, -7.8858105850095340394e-1)}, {FN (log10), ARG(5.0e-01,8.3886080e+06), RES(6.9236899002715682614e0, 6.8218815103495235199e-1)}, {FN (log10), ARG(5.0e-01,-8.3886080e+06), RES(6.9236899002715682614e0, -6.8218815103495235199e-1)}, {FN (log10), ARG(-5.0e-01,8.3886080e+06), RES(6.9236899002715682614e0, 6.8218820280688899550e-1)}, {FN (log10), ARG(-5.0e-01,-8.3886080e+06), RES(6.9236899002715682614e0, -6.8218820280688899550e-1)}, {FN (log10), ARG(1.0e+00,1.19209289550781250e-07), RES(3.0858478929704968280e-15, 5.1771936643511029532e-8)}, {FN (log10), ARG(1.0e+00,-1.19209289550781250e-07), RES(3.0858478929704968280e-15, -5.1771936643511029532e-8)}, {FN (log10), ARG(-1.0e+00,1.19209289550781250e-07), RES(3.0858478929704968280e-15, 1.3643763020699047040e0)}, {FN (log10), ARG(-1.0e+00,-1.19209289550781250e-07), RES(3.0858478929704968280e-15, -1.3643763020699047040e0)}, {FN (log10), ARG(1.0e+00,5.0e-01), RES(4.8455006504028207179e-2, 2.0135959813668657104e-1)}, {FN (log10), ARG(1.0e+00,-5.0e-01), RES(4.8455006504028207179e-2, -2.0135959813668657104e-1)}, {FN (log10), ARG(-1.0e+00,5.0e-01), RES(4.8455006504028207179e-2, 1.1630167557051547764e0)}, {FN (log10), ARG(-1.0e+00,-5.0e-01), RES(4.8455006504028207179e-2, -1.1630167557051547764e0)}, {FN (log10), ARG(1.0e+00,1.0e+00), RES(1.5051499783199059761e-1, 3.4109408846046033687e-1)}, {FN (log10), ARG(1.0e+00,-1.0e+00), RES(1.5051499783199059761e-1, -3.4109408846046033687e-1)}, {FN (log10), ARG(-1.0e+00,1.0e+00), RES(1.5051499783199059761e-1, 1.0232822653813810106e0)}, {FN (log10), ARG(-1.0e+00,-1.0e+00), RES(1.5051499783199059761e-1, -1.0232822653813810106e0)}, {FN (log10), ARG(1.0e+00,2.0e+00), RES(3.4948500216800940239e-1, 4.8082857878423410270e-1)}, {FN (log10), ARG(1.0e+00,-2.0e+00), RES(3.4948500216800940239e-1, -4.8082857878423410270e-1)}, {FN (log10), ARG(-1.0e+00,2.0e+00), RES(3.4948500216800940239e-1, 8.8354777505760724478e-1)}, {FN (log10), ARG(-1.0e+00,-2.0e+00), RES(3.4948500216800940239e-1, -8.8354777505760724478e-1)}, {FN (log10), ARG(1.0e+00,8.3886080e+06), RES(6.9236899002715705758e0, 6.8218812514898403023e-1)}, {FN (log10), ARG(1.0e+00,-8.3886080e+06), RES(6.9236899002715705758e0, -6.8218812514898403023e-1)}, {FN (log10), ARG(-1.0e+00,8.3886080e+06), RES(6.9236899002715705758e0, 6.8218822869285731725e-1)}, {FN (log10), ARG(-1.0e+00,-8.3886080e+06), RES(6.9236899002715705758e0, -6.8218822869285731725e-1)}, {FN (log10), ARG(2.0e+00,1.19209289550781250e-07), RES(3.0102999566398196668e-1, 2.5885968321755606731e-8)}, {FN (log10), ARG(2.0e+00,-1.19209289550781250e-07), RES(3.0102999566398196668e-1, -2.5885968321755606731e-8)}, {FN (log10), ARG(-2.0e+00,1.19209289550781250e-07), RES(3.0102999566398196668e-1, 1.3643763279558730257e0)}, {FN (log10), ARG(-2.0e+00,-1.19209289550781250e-07), RES(3.0102999566398196668e-1, -1.3643763279558730257e0)}, {FN (log10), ARG(2.0e+00,5.0e-01), RES(3.1419446502515576906e-1, 1.0639288158003273020e-1)}, {FN (log10), ARG(2.0e+00,-5.0e-01), RES(3.1419446502515576906e-1, -1.0639288158003273020e-1)}, {FN (log10), ARG(-2.0e+00,5.0e-01), RES(3.1419446502515576906e-1, 1.2579834722618086173e0)}, {FN (log10), ARG(-2.0e+00,-5.0e-01), RES(3.1419446502515576906e-1, -1.2579834722618086173e0)}, {FN (log10), ARG(2.0e+00,1.0e+00), RES(3.4948500216800940239e-1, 2.0135959813668657104e-1)}, {FN (log10), ARG(2.0e+00,-1.0e+00), RES(3.4948500216800940239e-1, -2.0135959813668657104e-1)}, {FN (log10), ARG(-2.0e+00,1.0e+00), RES(3.4948500216800940239e-1, 1.1630167557051547764e0)}, {FN (log10), ARG(-2.0e+00,-1.0e+00), RES(3.4948500216800940239e-1, -1.1630167557051547764e0)}, {FN (log10), ARG(2.0e+00,2.0e+00), RES(4.5154499349597179282e-1, 3.4109408846046033687e-1)}, {FN (log10), ARG(2.0e+00,-2.0e+00), RES(4.5154499349597179282e-1, -3.4109408846046033687e-1)}, {FN (log10), ARG(-2.0e+00,2.0e+00), RES(4.5154499349597179282e-1, 1.0232822653813810106e0)}, {FN (log10), ARG(-2.0e+00,-2.0e+00), RES(4.5154499349597179282e-1, -1.0232822653813810106e0)}, {FN (log10), ARG(2.0e+00,8.3886080e+06), RES(6.9236899002715798333e0, 6.8218807337704738672e-1)}, {FN (log10), ARG(2.0e+00,-8.3886080e+06), RES(6.9236899002715798333e0, -6.8218807337704738672e-1)}, {FN (log10), ARG(-2.0e+00,8.3886080e+06), RES(6.9236899002715798333e0, 6.8218828046479396076e-1)}, {FN (log10), ARG(-2.0e+00,-8.3886080e+06), RES(6.9236899002715798333e0, -6.8218828046479396076e-1)}, {FN (log10), ARG(8.3886080e+06,1.19209289550781250e-07), RES(6.9236899002715674899e0, 6.1716957859410375086e-15)}, {FN (log10), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(6.9236899002715674899e0, -6.1716957859410375086e-15)}, {FN (log10), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(6.9236899002715674899e0, 1.3643763538418351758e0)}, {FN (log10), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(6.9236899002715674899e0, -1.3643763538418351758e0)}, {FN (log10), ARG(8.3886080e+06,5.0e-01), RES(6.9236899002715682614e0, 2.5885968321755606731e-8)}, {FN (log10), ARG(8.3886080e+06,-5.0e-01), RES(6.9236899002715682614e0, -2.5885968321755606731e-8)}, {FN (log10), ARG(-8.3886080e+06,5.0e-01), RES(6.9236899002715682614e0, 1.3643763279558730257e0)}, {FN (log10), ARG(-8.3886080e+06,-5.0e-01), RES(6.9236899002715682614e0, -1.3643763279558730257e0)}, {FN (log10), ARG(8.3886080e+06,1.0e+00), RES(6.9236899002715705758e0, 5.1771936643511029532e-8)}, {FN (log10), ARG(8.3886080e+06,-1.0e+00), RES(6.9236899002715705758e0, -5.1771936643511029532e-8)}, {FN (log10), ARG(-8.3886080e+06,1.0e+00), RES(6.9236899002715705758e0, 1.3643763020699047040e0)}, {FN (log10), ARG(-8.3886080e+06,-1.0e+00), RES(6.9236899002715705758e0, -1.3643763020699047040e0)}, {FN (log10), ARG(8.3886080e+06,2.0e+00), RES(6.9236899002715798333e0, 1.0354387328702058762e-7)}, {FN (log10), ARG(8.3886080e+06,-2.0e+00), RES(6.9236899002715798333e0, -1.0354387328702058762e-7)}, {FN (log10), ARG(-8.3886080e+06,2.0e+00), RES(6.9236899002715798333e0, 1.3643762502979680605e0)}, {FN (log10), ARG(-8.3886080e+06,-2.0e+00), RES(6.9236899002715798333e0, -1.3643762502979680605e0)}, {FN (log10), ARG(8.3886080e+06,8.3886080e+06), RES(7.0742048981035580875e0, 3.4109408846046033687e-1)}, {FN (log10), ARG(8.3886080e+06,-8.3886080e+06), RES(7.0742048981035580875e0, -3.4109408846046033687e-1)}, {FN (log10), ARG(-8.3886080e+06,8.3886080e+06), RES(7.0742048981035580875e0, 1.0232822653813810106e0)}, {FN (log10), ARG(-8.3886080e+06,-8.3886080e+06), RES(7.0742048981035580875e0, -1.0232822653813810106e0)}, {FN (exp), ARG(0.0e+00,-3.45266983001243932001e-04), RES(9.9999994039535581673e-1, -3.4526697614140534807e-4)}, {FN (exp), ARG(0.0e+00,3.45266983001243932001e-04), RES(9.9999994039535581673e-1, 3.4526697614140534807e-4)}, {FN (exp), ARG(0.0e+00,1.57045105981189525579e+00), RES(3.4526697614152485627e-4, 9.9999994039535581669e-1)}, {FN (exp), ARG(0.0e+00,-1.57045105981189525579e+00), RES(3.4526697614152485627e-4, -9.9999994039535581669e-1)}, {FN (exp), ARG(0.0e+00,1.57114159377789786021e+00), RES(-3.4526697614140239160e-4, 9.9999994039535581673e-1)}, {FN (exp), ARG(0.0e+00,-1.57114159377789786021e+00), RES(-3.4526697614140239160e-4, -9.9999994039535581673e-1)}, {FN (exp), ARG(0.0e+00,3.14124738660679181379e+00), RES(-9.9999994039535581667e-1, 3.4526697614158608860e-4)}, {FN (exp), ARG(0.0e+00,-3.14124738660679181379e+00), RES(-9.9999994039535581667e-1, -3.4526697614158608860e-4)}, {FN (exp), ARG(0.0e+00,3.14193792057279441821e+00), RES(-9.9999994039535581675e-1, -3.4526697614134115926e-4)}, {FN (exp), ARG(0.0e+00,-3.14193792057279441821e+00), RES(-9.9999994039535581675e-1, 3.4526697614134115926e-4)}, {FN (exp), ARG(0.0e+00,4.71204371340168837179e+00), RES(-3.4526697614164732094e-4, -9.9999994039535581664e-1)}, {FN (exp), ARG(0.0e+00,-4.71204371340168837179e+00), RES(-3.4526697614164732094e-4, 9.9999994039535581664e-1)}, {FN (exp), ARG(0.0e+00,4.71273424736769097620e+00), RES(3.4526697614127992692e-4, -9.9999994039535581677e-1)}, {FN (exp), ARG(0.0e+00,-4.71273424736769097620e+00), RES(3.4526697614127992692e-4, 9.9999994039535581677e-1)}, {FN (exp), ARG(0.0e+00,6.28284004019658492979e+00), RES(9.9999994039535581662e-1, -3.4526697614170855328e-4)}, {FN (exp), ARG(0.0e+00,-6.28284004019658492979e+00), RES(9.9999994039535581662e-1, 3.4526697614170855328e-4)}, {FN (exp), ARG(0.0e+00,6.28353057416258753420e+00), RES(9.9999994039535581679e-1, 3.4526697614121869459e-4)}, {FN (exp), ARG(0.0e+00,-6.28353057416258753420e+00), RES(9.9999994039535581679e-1, -3.4526697614121869459e-4)}, {FN (exp), ARG(0.0e+00,9.42443269378637893396e+00), RES(-9.9999994039535581689e-1, 3.4526697614094283958e-4)}, {FN (exp), ARG(0.0e+00,-9.42443269378637893396e+00), RES(-9.9999994039535581689e-1, -3.4526697614094283958e-4)}, {FN (exp), ARG(0.0e+00,9.42512322775237976202e+00), RES(-9.9999994039535581714e-1, -3.4526697614020805155e-4)}, {FN (exp), ARG(0.0e+00,-9.42512322775237976202e+00), RES(-9.9999994039535581714e-1, 3.4526697614020805155e-4)}, {FN (exp), ARG(1.19209289550781250e-07,-3.45266983001243932001e-04), RES(1.0000000596046453675e0, -3.4526701730043873250e-4)}, {FN (exp), ARG(1.19209289550781250e-07,3.45266983001243932001e-04), RES(1.0000000596046453675e0, 3.4526701730043873250e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,-3.45266983001243932001e-04), RES(9.9999982118608047680e-1, -3.4526693498237687017e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,3.45266983001243932001e-04), RES(9.9999982118608047680e-1, 3.4526693498237687017e-4)}, {FN (exp), ARG(1.19209289550781250e-07,1.57045105981189525579e+00), RES(3.4526701730055824072e-4, 1.0000000596046453675e0)}, {FN (exp), ARG(1.19209289550781250e-07,-1.57045105981189525579e+00), RES(3.4526701730055824072e-4, -1.0000000596046453675e0)}, {FN (exp), ARG(-1.19209289550781250e-07,1.57045105981189525579e+00), RES(3.4526693498249637836e-4, 9.9999982118608047676e-1)}, {FN (exp), ARG(-1.19209289550781250e-07,-1.57045105981189525579e+00), RES(3.4526693498249637836e-4, -9.9999982118608047676e-1)}, {FN (exp), ARG(1.19209289550781250e-07,1.57114159377789786021e+00), RES(-3.4526701730043577603e-4, 1.0000000596046453675e0)}, {FN (exp), ARG(1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-3.4526701730043577603e-4, -1.0000000596046453675e0)}, {FN (exp), ARG(-1.19209289550781250e-07,1.57114159377789786021e+00), RES(-3.4526693498237391370e-4, 9.9999982118608047680e-1)}, {FN (exp), ARG(-1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-3.4526693498237391370e-4, -9.9999982118608047680e-1)}, {FN (exp), ARG(1.19209289550781250e-07,3.14124738660679181379e+00), RES(-1.0000000596046453674e0, 3.4526701730061947306e-4)}, {FN (exp), ARG(1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-1.0000000596046453674e0, -3.4526701730061947306e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,3.14124738660679181379e+00), RES(-9.9999982118608047674e-1, 3.4526693498255761069e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-9.9999982118608047674e-1, -3.4526693498255761069e-4)}, {FN (exp), ARG(1.19209289550781250e-07,3.14193792057279441821e+00), RES(-1.0000000596046453675e0, -3.4526701730037454368e-4)}, {FN (exp), ARG(1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-1.0000000596046453675e0, 3.4526701730037454368e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,3.14193792057279441821e+00), RES(-9.9999982118608047682e-1, -3.4526693498231268137e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-9.9999982118608047682e-1, 3.4526693498231268137e-4)}, {FN (exp), ARG(1.19209289550781250e-07,4.71204371340168837179e+00), RES(-3.4526701730068070540e-4, -1.0000000596046453674e0)}, {FN (exp), ARG(1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-3.4526701730068070540e-4, 1.0000000596046453674e0)}, {FN (exp), ARG(-1.19209289550781250e-07,4.71204371340168837179e+00), RES(-3.4526693498261884302e-4, -9.9999982118608047672e-1)}, {FN (exp), ARG(-1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-3.4526693498261884302e-4, 9.9999982118608047672e-1)}, {FN (exp), ARG(1.19209289550781250e-07,4.71273424736769097620e+00), RES(3.4526701730031331134e-4, -1.0000000596046453676e0)}, {FN (exp), ARG(1.19209289550781250e-07,-4.71273424736769097620e+00), RES(3.4526701730031331134e-4, 1.0000000596046453676e0)}, {FN (exp), ARG(-1.19209289550781250e-07,4.71273424736769097620e+00), RES(3.4526693498225144904e-4, -9.9999982118608047684e-1)}, {FN (exp), ARG(-1.19209289550781250e-07,-4.71273424736769097620e+00), RES(3.4526693498225144904e-4, 9.9999982118608047684e-1)}, {FN (exp), ARG(1.19209289550781250e-07,6.28284004019658492979e+00), RES(1.0000000596046453674e0, -3.4526701730074193775e-4)}, {FN (exp), ARG(1.19209289550781250e-07,-6.28284004019658492979e+00), RES(1.0000000596046453674e0, 3.4526701730074193775e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,6.28284004019658492979e+00), RES(9.9999982118608047670e-1, -3.4526693498268007535e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,-6.28284004019658492979e+00), RES(9.9999982118608047670e-1, 3.4526693498268007535e-4)}, {FN (exp), ARG(1.19209289550781250e-07,6.28353057416258753420e+00), RES(1.0000000596046453676e0, 3.452670173002520790e-4)}, {FN (exp), ARG(1.19209289550781250e-07,-6.28353057416258753420e+00), RES(1.0000000596046453676e0, -3.452670173002520790e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,6.28353057416258753420e+00), RES(9.9999982118608047687e-1, 3.4526693498219021671e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,-6.28353057416258753420e+00), RES(9.9999982118608047687e-1, -3.4526693498219021671e-4)}, {FN (exp), ARG(1.19209289550781250e-07,9.42443269378637893396e+00), RES(-1.0000000596046453677e0, 3.4526701729997622396e-4)}, {FN (exp), ARG(1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-1.0000000596046453677e0, -3.4526701729997622396e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,9.42443269378637893396e+00), RES(-9.9999982118608047696e-1, 3.4526693498191436174e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-9.9999982118608047696e-1, -3.4526693498191436174e-4)}, {FN (exp), ARG(1.19209289550781250e-07,9.42512322775237976202e+00), RES(-1.0000000596046453679e0, -3.4526701729924143584e-4)}, {FN (exp), ARG(1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-1.0000000596046453679e0, 3.4526701729924143584e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,9.42512322775237976202e+00), RES(-9.9999982118608047721e-1, -3.4526693498117957380e-4)}, {FN (exp), ARG(-1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-9.9999982118608047721e-1, 3.4526693498117957380e-4)}, {FN (exp), ARG(5.0e-01,-3.45266983001243932001e-04), RES(1.6487211724286834494e0, -5.6924900763464865323e-4)}, {FN (exp), ARG(5.0e-01,3.45266983001243932001e-04), RES(1.6487211724286834494e0, 5.6924900763464865323e-4)}, {FN (exp), ARG(-5.0e-01,-3.45266983001243932001e-04), RES(6.0653062356058926519e-1, -2.0941500681603265022e-4)}, {FN (exp), ARG(-5.0e-01,3.45266983001243932001e-04), RES(6.0653062356058926519e-1, 2.0941500681603265022e-4)}, {FN (exp), ARG(5.0e-01,1.57045105981189525579e+00), RES(5.6924900763484568894e-4, 1.6487211724286834493e0)}, {FN (exp), ARG(5.0e-01,-1.57045105981189525579e+00), RES(5.6924900763484568894e-4, -1.6487211724286834493e0)}, {FN (exp), ARG(-5.0e-01,1.57045105981189525579e+00), RES(2.0941500681610513560e-4, 6.0653062356058926516e-1)}, {FN (exp), ARG(-5.0e-01,-1.57045105981189525579e+00), RES(2.0941500681610513560e-4, -6.0653062356058926516e-1)}, {FN (exp), ARG(5.0e-01,1.57114159377789786021e+00), RES(-5.6924900763464377883e-4, 1.6487211724286834494e0)}, {FN (exp), ARG(5.0e-01,-1.57114159377789786021e+00), RES(-5.6924900763464377883e-4, -1.6487211724286834494e0)}, {FN (exp), ARG(-5.0e-01,1.57114159377789786021e+00), RES(-2.0941500681603085702e-4, 6.0653062356058926519e-1)}, {FN (exp), ARG(-5.0e-01,-1.57114159377789786021e+00), RES(-2.0941500681603085702e-4, -6.0653062356058926519e-1)}, {FN (exp), ARG(5.0e-01,3.14124738660679181379e+00), RES(-1.6487211724286834493e0, 5.6924900763494664399e-4)}, {FN (exp), ARG(5.0e-01,-3.14124738660679181379e+00), RES(-1.6487211724286834493e0, -5.6924900763494664399e-4)}, {FN (exp), ARG(-5.0e-01,3.14124738660679181379e+00), RES(-6.0653062356058926515e-1, 2.0941500681614227489e-4)}, {FN (exp), ARG(-5.0e-01,-3.14124738660679181379e+00), RES(-6.0653062356058926515e-1, -2.0941500681614227489e-4)}, {FN (exp), ARG(5.0e-01,3.14193792057279441821e+00), RES(-1.6487211724286834494e0, -5.6924900763454282377e-4)}, {FN (exp), ARG(5.0e-01,-3.14193792057279441821e+00), RES(-1.6487211724286834494e0, 5.6924900763454282377e-4)}, {FN (exp), ARG(-5.0e-01,3.14193792057279441821e+00), RES(-6.0653062356058926520e-1, -2.0941500681599371773e-4)}, {FN (exp), ARG(-5.0e-01,-3.14193792057279441821e+00), RES(-6.0653062356058926520e-1, 2.0941500681599371773e-4)}, {FN (exp), ARG(5.0e-01,4.71204371340168837179e+00), RES(-5.6924900763504759905e-4, -1.6487211724286834492e0)}, {FN (exp), ARG(5.0e-01,-4.71204371340168837179e+00), RES(-5.6924900763504759905e-4, 1.6487211724286834492e0)}, {FN (exp), ARG(-5.0e-01,4.71204371340168837179e+00), RES(-2.0941500681617941418e-4, -6.0653062356058926514e-1)}, {FN (exp), ARG(-5.0e-01,-4.71204371340168837179e+00), RES(-2.0941500681617941418e-4, 6.0653062356058926514e-1)}, {FN (exp), ARG(5.0e-01,4.71273424736769097620e+00), RES(5.6924900763444186872e-4, -1.6487211724286834494e0)}, {FN (exp), ARG(5.0e-01,-4.71273424736769097620e+00), RES(5.6924900763444186872e-4, 1.6487211724286834494e0)}, {FN (exp), ARG(-5.0e-01,4.71273424736769097620e+00), RES(2.0941500681595657844e-4, -6.0653062356058926521e-1)}, {FN (exp), ARG(-5.0e-01,-4.71273424736769097620e+00), RES(2.0941500681595657844e-4, 6.0653062356058926521e-1)}, {FN (exp), ARG(5.0e-01,6.28284004019658492979e+00), RES(1.6487211724286834492e0, -5.6924900763514855410e-4)}, {FN (exp), ARG(5.0e-01,-6.28284004019658492979e+00), RES(1.6487211724286834492e0, 5.6924900763514855410e-4)}, {FN (exp), ARG(-5.0e-01,6.28284004019658492979e+00), RES(6.0653062356058926512e-1, -2.0941500681621655347e-4)}, {FN (exp), ARG(-5.0e-01,-6.28284004019658492979e+00), RES(6.0653062356058926512e-1, 2.0941500681621655347e-4)}, {FN (exp), ARG(5.0e-01,6.28353057416258753420e+00), RES(1.6487211724286834495e0, 5.6924900763434091366e-4)}, {FN (exp), ARG(5.0e-01,-6.28353057416258753420e+00), RES(1.6487211724286834495e0, -5.6924900763434091366e-4)}, {FN (exp), ARG(-5.0e-01,6.28353057416258753420e+00), RES(6.0653062356058926523e-1, 2.0941500681591943916e-4)}, {FN (exp), ARG(-5.0e-01,-6.28353057416258753420e+00), RES(6.0653062356058926523e-1, -2.0941500681591943916e-4)}, {FN (exp), ARG(5.0e-01,9.42443269378637893396e+00), RES(-1.6487211724286834496e0, 5.6924900763388610565e-4)}, {FN (exp), ARG(5.0e-01,-9.42443269378637893396e+00), RES(-1.6487211724286834496e0, -5.6924900763388610565e-4)}, {FN (exp), ARG(-5.0e-01,9.42443269378637893396e+00), RES(-6.0653062356058926528e-1, 2.0941500681575212464e-4)}, {FN (exp), ARG(-5.0e-01,-9.42443269378637893396e+00), RES(-6.0653062356058926528e-1, -2.0941500681575212464e-4)}, {FN (exp), ARG(5.0e-01,9.42512322775237976202e+00), RES(-1.6487211724286834501e0, -5.6924900763267464498e-4)}, {FN (exp), ARG(5.0e-01,-9.42512322775237976202e+00), RES(-1.6487211724286834501e0, 5.6924900763267464498e-4)}, {FN (exp), ARG(-5.0e-01,9.42512322775237976202e+00), RES(-6.0653062356058926544e-1, -2.0941500681530645317e-4)}, {FN (exp), ARG(-5.0e-01,-9.42512322775237976202e+00), RES(-6.0653062356058926544e-1, 2.0941500681530645317e-4)}, {FN (exp), ARG(1.0e+00,-3.45266983001243932001e-04), RES(2.7182816664368240602e0, -9.3853294721218487636e-4)}, {FN (exp), ARG(1.0e+00,3.45266983001243932001e-04), RES(2.7182816664368240602e0, 9.3853294721218487636e-4)}, {FN (exp), ARG(-1.0e+00,-3.45266983001243932001e-04), RES(3.6787941924411912823e-1, -1.2701662223785390836e-4)}, {FN (exp), ARG(-1.0e+00,3.45266983001243932001e-04), RES(3.6787941924411912823e-1, 1.2701662223785390836e-4)}, {FN (exp), ARG(1.0e+00,1.57045105981189525579e+00), RES(9.3853294721250973333e-4, 2.7182816664368240601e0)}, {FN (exp), ARG(1.0e+00,-1.57045105981189525579e+00), RES(9.3853294721250973333e-4, -2.7182816664368240601e0)}, {FN (exp), ARG(-1.0e+00,1.57045105981189525579e+00), RES(1.2701662223789787297e-4, 3.6787941924411912822e-1)}, {FN (exp), ARG(-1.0e+00,-1.57045105981189525579e+00), RES(1.2701662223789787297e-4, -3.6787941924411912822e-1)}, {FN (exp), ARG(1.0e+00,1.57114159377789786021e+00), RES(-9.3853294721217683983e-4, 2.7182816664368240602e0)}, {FN (exp), ARG(1.0e+00,-1.57114159377789786021e+00), RES(-9.3853294721217683983e-4, -2.7182816664368240602e0)}, {FN (exp), ARG(-1.0e+00,1.57114159377789786021e+00), RES(-1.2701662223785282074e-4, 3.6787941924411912823e-1)}, {FN (exp), ARG(-1.0e+00,-1.57114159377789786021e+00), RES(-1.2701662223785282074e-4, -3.6787941924411912823e-1)}, {FN (exp), ARG(1.0e+00,3.14124738660679181379e+00), RES(-2.718281666436824060e0, 9.3853294721267618008e-4)}, {FN (exp), ARG(1.0e+00,-3.14124738660679181379e+00), RES(-2.718281666436824060e0, -9.3853294721267618008e-4)}, {FN (exp), ARG(-1.0e+00,3.14124738660679181379e+00), RES(-3.6787941924411912821e-1, 1.2701662223792039909e-4)}, {FN (exp), ARG(-1.0e+00,-3.14124738660679181379e+00), RES(-3.6787941924411912821e-1, -1.2701662223792039909e-4)}, {FN (exp), ARG(1.0e+00,3.14193792057279441821e+00), RES(-2.7182816664368240603e0, -9.3853294721201039309e-4)}, {FN (exp), ARG(1.0e+00,-3.14193792057279441821e+00), RES(-2.7182816664368240603e0, 9.3853294721201039309e-4)}, {FN (exp), ARG(-1.0e+00,3.14193792057279441821e+00), RES(-3.6787941924411912824e-1, -1.2701662223783029462e-4)}, {FN (exp), ARG(-1.0e+00,-3.14193792057279441821e+00), RES(-3.6787941924411912824e-1, 1.2701662223783029462e-4)}, {FN (exp), ARG(1.0e+00,4.71204371340168837179e+00), RES(-9.3853294721284262682e-4, -2.718281666436824060e0)}, {FN (exp), ARG(1.0e+00,-4.71204371340168837179e+00), RES(-9.3853294721284262682e-4, 2.718281666436824060e0)}, {FN (exp), ARG(-1.0e+00,4.71204371340168837179e+00), RES(-1.2701662223794292521e-4, -3.6787941924411912820e-1)}, {FN (exp), ARG(-1.0e+00,-4.71204371340168837179e+00), RES(-1.2701662223794292521e-4, 3.6787941924411912820e-1)}, {FN (exp), ARG(1.0e+00,4.71273424736769097620e+00), RES(9.3853294721184394634e-4, -2.7182816664368240603e0)}, {FN (exp), ARG(1.0e+00,-4.71273424736769097620e+00), RES(9.3853294721184394634e-4, 2.7182816664368240603e0)}, {FN (exp), ARG(-1.0e+00,4.71273424736769097620e+00), RES(1.2701662223780776850e-4, -3.6787941924411912825e-1)}, {FN (exp), ARG(-1.0e+00,-4.71273424736769097620e+00), RES(1.2701662223780776850e-4, 3.6787941924411912825e-1)}, {FN (exp), ARG(1.0e+00,6.28284004019658492979e+00), RES(2.7182816664368240599e0, -9.3853294721300907357e-4)}, {FN (exp), ARG(1.0e+00,-6.28284004019658492979e+00), RES(2.7182816664368240599e0, 9.3853294721300907357e-4)}, {FN (exp), ARG(-1.0e+00,6.28284004019658492979e+00), RES(3.6787941924411912819e-1, -1.2701662223796545132e-4)}, {FN (exp), ARG(-1.0e+00,-6.28284004019658492979e+00), RES(3.6787941924411912819e-1, 1.2701662223796545132e-4)}, {FN (exp), ARG(1.0e+00,6.28353057416258753420e+00), RES(2.7182816664368240604e0, 9.3853294721167749959e-4)}, {FN (exp), ARG(1.0e+00,-6.28353057416258753420e+00), RES(2.7182816664368240604e0, -9.3853294721167749959e-4)}, {FN (exp), ARG(-1.0e+00,6.28353057416258753420e+00), RES(3.6787941924411912825e-1, 1.2701662223778524238e-4)}, {FN (exp), ARG(-1.0e+00,-6.28353057416258753420e+00), RES(3.6787941924411912825e-1, -1.2701662223778524238e-4)}, {FN (exp), ARG(1.0e+00,9.42443269378637893396e+00), RES(-2.7182816664368240606e0, 9.3853294721092764795e-4)}, {FN (exp), ARG(1.0e+00,-9.42443269378637893396e+00), RES(-2.7182816664368240606e0, -9.3853294721092764795e-4)}, {FN (exp), ARG(-1.0e+00,9.42443269378637893396e+00), RES(-3.6787941924411912829e-1, 1.270166222376837610e-4)}, {FN (exp), ARG(-1.0e+00,-9.42443269378637893396e+00), RES(-3.6787941924411912829e-1, -1.270166222376837610e-4)}, {FN (exp), ARG(1.0e+00,9.42512322775237976202e+00), RES(-2.7182816664368240613e0, -9.3853294720893028698e-4)}, {FN (exp), ARG(1.0e+00,-9.42512322775237976202e+00), RES(-2.7182816664368240613e0, 9.3853294720893028698e-4)}, {FN (exp), ARG(-1.0e+00,9.42512322775237976202e+00), RES(-3.6787941924411912838e-1, -1.2701662223741344759e-4)}, {FN (exp), ARG(-1.0e+00,-9.42512322775237976202e+00), RES(-3.6787941924411912838e-1, 1.2701662223741344759e-4)}, {FN (exp), ARG(2.0e+00,-3.45266983001243932001e-04), RES(7.3890556585085906002e0, -2.5511970558169944872e-3)}, {FN (exp), ARG(2.0e+00,3.45266983001243932001e-04), RES(7.3890556585085906002e0, 2.5511970558169944872e-3)}, {FN (exp), ARG(-2.0e+00,-3.45266983001243932001e-04), RES(1.3533527517000128913e-1, -4.6726804008345889445e-5)}, {FN (exp), ARG(-2.0e+00,3.45266983001243932001e-04), RES(1.3533527517000128913e-1, 4.6726804008345889445e-5)}, {FN (exp), ARG(2.0e+00,1.57045105981189525579e+00), RES(2.551197055817877540e-3, 7.3890556585085905999e0)}, {FN (exp), ARG(2.0e+00,-1.57045105981189525579e+00), RES(2.551197055817877540e-3, -7.3890556585085905999e0)}, {FN (exp), ARG(-2.0e+00,1.57045105981189525579e+00), RES(4.6726804008362063122e-5, 1.3533527517000128913e-1)}, {FN (exp), ARG(-2.0e+00,-1.57045105981189525579e+00), RES(4.6726804008362063122e-5, -1.3533527517000128913e-1)}, {FN (exp), ARG(2.0e+00,1.57114159377789786021e+00), RES(-2.5511970558169726417e-3, 7.3890556585085906002e0)}, {FN (exp), ARG(2.0e+00,-1.57114159377789786021e+00), RES(-2.5511970558169726417e-3, -7.3890556585085906002e0)}, {FN (exp), ARG(-2.0e+00,1.57114159377789786021e+00), RES(-4.6726804008345489330e-5, 1.3533527517000128913e-1)}, {FN (exp), ARG(-2.0e+00,-1.57114159377789786021e+00), RES(-4.6726804008345489330e-5, -1.3533527517000128913e-1)}, {FN (exp), ARG(2.0e+00,3.14124738660679181379e+00), RES(-7.3890556585085905998e0, 2.5511970558183299892e-3)}, {FN (exp), ARG(2.0e+00,-3.14124738660679181379e+00), RES(-7.3890556585085905998e0, -2.5511970558183299892e-3)}, {FN (exp), ARG(-2.0e+00,3.14124738660679181379e+00), RES(-1.3533527517000128912e-1, 4.6726804008370350017e-5)}, {FN (exp), ARG(-2.0e+00,-3.14124738660679181379e+00), RES(-1.3533527517000128912e-1, -4.6726804008370350017e-5)}, {FN (exp), ARG(2.0e+00,3.14193792057279441821e+00), RES(-7.3890556585085906004e0, -2.5511970558165201925e-3)}, {FN (exp), ARG(2.0e+00,-3.14193792057279441821e+00), RES(-7.3890556585085906004e0, 2.5511970558165201925e-3)}, {FN (exp), ARG(-2.0e+00,3.14193792057279441821e+00), RES(-1.3533527517000128914e-1, -4.6726804008337202435e-5)}, {FN (exp), ARG(-2.0e+00,-3.14193792057279441821e+00), RES(-1.3533527517000128914e-1, 4.6726804008337202435e-5)}, {FN (exp), ARG(2.0e+00,4.71204371340168837179e+00), RES(-2.5511970558187824384e-3, -7.3890556585085905996e0)}, {FN (exp), ARG(2.0e+00,-4.71204371340168837179e+00), RES(-2.5511970558187824384e-3, 7.3890556585085905996e0)}, {FN (exp), ARG(-2.0e+00,4.71204371340168837179e+00), RES(-4.6726804008378636913e-5, -1.3533527517000128912e-1)}, {FN (exp), ARG(-2.0e+00,-4.71204371340168837179e+00), RES(-4.6726804008378636913e-5, 1.3533527517000128912e-1)}, {FN (exp), ARG(2.0e+00,4.71273424736769097620e+00), RES(2.5511970558160677434e-3, -7.3890556585085906006e0)}, {FN (exp), ARG(2.0e+00,-4.71273424736769097620e+00), RES(2.5511970558160677434e-3, 7.3890556585085906006e0)}, {FN (exp), ARG(-2.0e+00,4.71273424736769097620e+00), RES(4.6726804008328915539e-5, -1.3533527517000128914e-1)}, {FN (exp), ARG(-2.0e+00,-4.71273424736769097620e+00), RES(4.6726804008328915539e-5, 1.3533527517000128914e-1)}, {FN (exp), ARG(2.0e+00,6.28284004019658492979e+00), RES(7.3890556585085905995e0, -2.5511970558192348875e-3)}, {FN (exp), ARG(2.0e+00,-6.28284004019658492979e+00), RES(7.3890556585085905995e0, 2.5511970558192348875e-3)}, {FN (exp), ARG(-2.0e+00,6.28284004019658492979e+00), RES(1.3533527517000128912e-1, -4.6726804008386923808e-5)}, {FN (exp), ARG(-2.0e+00,-6.28284004019658492979e+00), RES(1.3533527517000128912e-1, 4.6726804008386923808e-5)}, {FN (exp), ARG(2.0e+00,6.28353057416258753420e+00), RES(7.3890556585085906007e0, 2.5511970558156152942e-3)}, {FN (exp), ARG(2.0e+00,-6.28353057416258753420e+00), RES(7.3890556585085906007e0, -2.5511970558156152942e-3)}, {FN (exp), ARG(-2.0e+00,6.28353057416258753420e+00), RES(1.3533527517000128914e-1, 4.6726804008320628644e-5)}, {FN (exp), ARG(-2.0e+00,-6.28353057416258753420e+00), RES(1.3533527517000128914e-1, -4.6726804008320628644e-5)}, {FN (exp), ARG(2.0e+00,9.42443269378637893396e+00), RES(-7.3890556585085906014e0, 2.5511970558135769861e-3)}, {FN (exp), ARG(2.0e+00,-9.42443269378637893396e+00), RES(-7.3890556585085906014e0, -2.5511970558135769861e-3)}, {FN (exp), ARG(-2.0e+00,9.42443269378637893396e+00), RES(-1.3533527517000128916e-1, 4.6726804008283295729e-5)}, {FN (exp), ARG(-2.0e+00,-9.42443269378637893396e+00), RES(-1.3533527517000128916e-1, -4.6726804008283295729e-5)}, {FN (exp), ARG(2.0e+00,9.42512322775237976202e+00), RES(-7.3890556585085906033e0, -2.5511970558081475961e-3)}, {FN (exp), ARG(2.0e+00,-9.42512322775237976202e+00), RES(-7.3890556585085906033e0, 2.5511970558081475961e-3)}, {FN (exp), ARG(-2.0e+00,9.42512322775237976202e+00), RES(-1.3533527517000128919e-1, -4.6726804008183852982e-5)}, {FN (exp), ARG(-2.0e+00,-9.42512322775237976202e+00), RES(-1.3533527517000128919e-1, 4.6726804008183852982e-5)}, {FN (sin), ARG(-3.45266983001243932001e-04,0.0e+00), RES(-3.4526697614140534807e-4, 0.0)}, {FN (sin), ARG(3.45266983001243932001e-04,0.0e+00), RES(3.4526697614140534807e-4, 0.0)}, {FN (sin), ARG(-3.45266983001243932001e-04,1.19209289550781250e-07), RES(-3.4526697614140780134e-4, 1.1920928244535424533e-7)}, {FN (sin), ARG(-3.45266983001243932001e-04,-1.19209289550781250e-07), RES(-3.4526697614140780134e-4, -1.1920928244535424533e-7)}, {FN (sin), ARG(3.45266983001243932001e-04,1.19209289550781250e-07), RES(3.4526697614140780134e-4, 1.1920928244535424533e-7)}, {FN (sin), ARG(3.45266983001243932001e-04,-1.19209289550781250e-07), RES(3.4526697614140780134e-4, -1.1920928244535424533e-7)}, {FN (sin), ARG(-3.45266983001243932001e-04,5.0e-01), RES(-3.8933200722534065172e-4, 5.2109527443404709209e-1)}, {FN (sin), ARG(-3.45266983001243932001e-04,-5.0e-01), RES(-3.8933200722534065172e-4, -5.2109527443404709209e-1)}, {FN (sin), ARG(3.45266983001243932001e-04,5.0e-01), RES(3.8933200722534065172e-4, 5.2109527443404709209e-1)}, {FN (sin), ARG(3.45266983001243932001e-04,-5.0e-01), RES(3.8933200722534065172e-4, -5.2109527443404709209e-1)}, {FN (sin), ARG(-3.45266983001243932001e-04,1.0e+00), RES(-5.3277478472501939236e-4, 1.1752011235963524660e0)}, {FN (sin), ARG(-3.45266983001243932001e-04,-1.0e+00), RES(-5.3277478472501939236e-4, -1.1752011235963524660e0)}, {FN (sin), ARG(3.45266983001243932001e-04,1.0e+00), RES(5.3277478472501939236e-4, 1.1752011235963524660e0)}, {FN (sin), ARG(3.45266983001243932001e-04,-1.0e+00), RES(5.3277478472501939236e-4, -1.1752011235963524660e0)}, {FN (sin), ARG(-3.45266983001243932001e-04,2.0e+00), RES(-1.2989619299126701883e-3, 3.6268601916692946556e0)}, {FN (sin), ARG(-3.45266983001243932001e-04,-2.0e+00), RES(-1.2989619299126701883e-3, -3.6268601916692946556e0)}, {FN (sin), ARG(3.45266983001243932001e-04,2.0e+00), RES(1.2989619299126701883e-3, 3.6268601916692946556e0)}, {FN (sin), ARG(3.45266983001243932001e-04,-2.0e+00), RES(1.2989619299126701883e-3, -3.6268601916692946556e0)}, {FN (sin), ARG(1.57045105981189525579e+00,0.0e+00), RES(9.9999994039535581669e-1, 0.0)}, {FN (sin), ARG(-1.57045105981189525579e+00,0.0e+00), RES(-9.9999994039535581669e-1, 0.0)}, {FN (sin), ARG(1.57045105981189525579e+00,1.19209289550781250e-07), RES(9.9999994039536292211e-1, 4.1159030931177815679e-11)}, {FN (sin), ARG(1.57045105981189525579e+00,-1.19209289550781250e-07), RES(9.9999994039536292211e-1, -4.1159030931177815679e-11)}, {FN (sin), ARG(-1.57045105981189525579e+00,1.19209289550781250e-07), RES(-9.9999994039536292211e-1, 4.1159030931177815679e-11)}, {FN (sin), ARG(-1.57045105981189525579e+00,-1.19209289550781250e-07), RES(-9.9999994039536292211e-1, -4.1159030931177815679e-11)}, {FN (sin), ARG(1.57045105981189525579e+00,5.0e-01), RES(1.1276258979946363572e0, 1.7991700040937027667e-4)}, {FN (sin), ARG(1.57045105981189525579e+00,-5.0e-01), RES(1.1276258979946363572e0, -1.7991700040937027667e-4)}, {FN (sin), ARG(-1.57045105981189525579e+00,5.0e-01), RES(-1.1276258979946363572e0, 1.7991700040937027667e-4)}, {FN (sin), ARG(-1.57045105981189525579e+00,-5.0e-01), RES(-1.1276258979946363572e0, -1.7991700040937027667e-4)}, {FN (sin), ARG(1.57045105981189525579e+00,1.0e+00), RES(1.5430805428404715942e0, 4.0575816248730593018e-4)}, {FN (sin), ARG(1.57045105981189525579e+00,-1.0e+00), RES(1.5430805428404715942e0, -4.0575816248730593018e-4)}, {FN (sin), ARG(-1.57045105981189525579e+00,1.0e+00), RES(-1.5430805428404715942e0, 4.0575816248730593018e-4)}, {FN (sin), ARG(-1.57045105981189525579e+00,-1.0e+00), RES(-1.5430805428404715942e0, -4.0575816248730593018e-4)}, {FN (sin), ARG(1.57045105981189525579e+00,2.0e+00), RES(3.7621954668392959445e0, 1.2522351259047577385e-3)}, {FN (sin), ARG(1.57045105981189525579e+00,-2.0e+00), RES(3.7621954668392959445e0, -1.2522351259047577385e-3)}, {FN (sin), ARG(-1.57045105981189525579e+00,2.0e+00), RES(-3.7621954668392959445e0, 1.2522351259047577385e-3)}, {FN (sin), ARG(-1.57045105981189525579e+00,-2.0e+00), RES(-3.7621954668392959445e0, -1.2522351259047577385e-3)}, {FN (sin), ARG(1.57114159377789786021e+00,0.0e+00), RES(9.9999994039535581673e-1, 0.0)}, {FN (sin), ARG(-1.57114159377789786021e+00,0.0e+00), RES(-9.9999994039535581673e-1, 0.0)}, {FN (sin), ARG(1.57114159377789786021e+00,1.19209289550781250e-07), RES(9.9999994039536292216e-1, -4.1159030931163216752e-11)}, {FN (sin), ARG(1.57114159377789786021e+00,-1.19209289550781250e-07), RES(9.9999994039536292216e-1, 4.1159030931163216752e-11)}, {FN (sin), ARG(-1.57114159377789786021e+00,1.19209289550781250e-07), RES(-9.9999994039536292216e-1, -4.1159030931163216752e-11)}, {FN (sin), ARG(-1.57114159377789786021e+00,-1.19209289550781250e-07), RES(-9.9999994039536292216e-1, 4.1159030931163216752e-11)}, {FN (sin), ARG(1.57114159377789786021e+00,5.0e-01), RES(1.1276258979946363573e0, -1.7991700040930646090e-4)}, {FN (sin), ARG(1.57114159377789786021e+00,-5.0e-01), RES(1.1276258979946363573e0, 1.7991700040930646090e-4)}, {FN (sin), ARG(-1.57114159377789786021e+00,5.0e-01), RES(-1.1276258979946363573e0, -1.7991700040930646090e-4)}, {FN (sin), ARG(-1.57114159377789786021e+00,-5.0e-01), RES(-1.1276258979946363573e0, 1.7991700040930646090e-4)}, {FN (sin), ARG(1.57114159377789786021e+00,1.0e+00), RES(1.5430805428404715942e0, -4.0575816248716200955e-4)}, {FN (sin), ARG(1.57114159377789786021e+00,-1.0e+00), RES(1.5430805428404715942e0, 4.0575816248716200955e-4)}, {FN (sin), ARG(-1.57114159377789786021e+00,1.0e+00), RES(-1.5430805428404715942e0, -4.0575816248716200955e-4)}, {FN (sin), ARG(-1.57114159377789786021e+00,-1.0e+00), RES(-1.5430805428404715942e0, 4.0575816248716200955e-4)}, {FN (sin), ARG(1.57114159377789786021e+00,2.0e+00), RES(3.7621954668392959447e0, -1.2522351259043135762e-3)}, {FN (sin), ARG(1.57114159377789786021e+00,-2.0e+00), RES(3.7621954668392959447e0, 1.2522351259043135762e-3)}, {FN (sin), ARG(-1.57114159377789786021e+00,2.0e+00), RES(-3.7621954668392959447e0, -1.2522351259043135762e-3)}, {FN (sin), ARG(-1.57114159377789786021e+00,-2.0e+00), RES(-3.7621954668392959447e0, 1.2522351259043135762e-3)}, {FN (sin), ARG(3.14124738660679181379e+00,0.0e+00), RES(3.4526697614158608860e-4, 0.0)}, {FN (sin), ARG(-3.14124738660679181379e+00,0.0e+00), RES(-3.4526697614158608860e-4, 0.0)}, {FN (sin), ARG(3.14124738660679181379e+00,1.19209289550781250e-07), RES(3.4526697614158854187e-4, -1.1920928244535424532e-7)}, {FN (sin), ARG(3.14124738660679181379e+00,-1.19209289550781250e-07), RES(3.4526697614158854187e-4, 1.1920928244535424532e-7)}, {FN (sin), ARG(-3.14124738660679181379e+00,1.19209289550781250e-07), RES(-3.4526697614158854187e-4, -1.1920928244535424532e-7)}, {FN (sin), ARG(-3.14124738660679181379e+00,-1.19209289550781250e-07), RES(-3.4526697614158854187e-4, 1.1920928244535424532e-7)}, {FN (sin), ARG(3.14124738660679181379e+00,5.0e-01), RES(3.8933200722554445944e-4, -5.2109527443404709206e-1)}, {FN (sin), ARG(3.14124738660679181379e+00,-5.0e-01), RES(3.8933200722554445944e-4, 5.2109527443404709206e-1)}, {FN (sin), ARG(-3.14124738660679181379e+00,5.0e-01), RES(-3.8933200722554445944e-4, -5.2109527443404709206e-1)}, {FN (sin), ARG(-3.14124738660679181379e+00,-5.0e-01), RES(-3.8933200722554445944e-4, 5.2109527443404709206e-1)}, {FN (sin), ARG(3.14124738660679181379e+00,1.0e+00), RES(5.3277478472529828958e-4, -1.1752011235963524659e0)}, {FN (sin), ARG(3.14124738660679181379e+00,-1.0e+00), RES(5.3277478472529828958e-4, 1.1752011235963524659e0)}, {FN (sin), ARG(-3.14124738660679181379e+00,1.0e+00), RES(-5.3277478472529828958e-4, -1.1752011235963524659e0)}, {FN (sin), ARG(-3.14124738660679181379e+00,-1.0e+00), RES(-5.3277478472529828958e-4, 1.1752011235963524659e0)}, {FN (sin), ARG(3.14124738660679181379e+00,2.0e+00), RES(1.2989619299133501696e-3, -3.6268601916692946553e0)}, {FN (sin), ARG(3.14124738660679181379e+00,-2.0e+00), RES(1.2989619299133501696e-3, 3.6268601916692946553e0)}, {FN (sin), ARG(-3.14124738660679181379e+00,2.0e+00), RES(-1.2989619299133501696e-3, -3.6268601916692946553e0)}, {FN (sin), ARG(-3.14124738660679181379e+00,-2.0e+00), RES(-1.2989619299133501696e-3, 3.6268601916692946553e0)}, {FN (sin), ARG(3.14193792057279441821e+00,0.0e+00), RES(-3.4526697614134115926e-4, 0.0)}, {FN (sin), ARG(-3.14193792057279441821e+00,0.0e+00), RES(3.4526697614134115926e-4, 0.0)}, {FN (sin), ARG(3.14193792057279441821e+00,1.19209289550781250e-07), RES(-3.4526697614134361253e-4, -1.1920928244535424533e-7)}, {FN (sin), ARG(3.14193792057279441821e+00,-1.19209289550781250e-07), RES(-3.4526697614134361253e-4, 1.1920928244535424533e-7)}, {FN (sin), ARG(-3.14193792057279441821e+00,1.19209289550781250e-07), RES(3.4526697614134361253e-4, -1.1920928244535424533e-7)}, {FN (sin), ARG(-3.14193792057279441821e+00,-1.19209289550781250e-07), RES(3.4526697614134361253e-4, 1.1920928244535424533e-7)}, {FN (sin), ARG(3.14193792057279441821e+00,5.0e-01), RES(-3.8933200722526827075e-4, -5.2109527443404709211e-1)}, {FN (sin), ARG(3.14193792057279441821e+00,-5.0e-01), RES(-3.8933200722526827075e-4, 5.2109527443404709211e-1)}, {FN (sin), ARG(-3.14193792057279441821e+00,5.0e-01), RES(3.8933200722526827075e-4, -5.2109527443404709211e-1)}, {FN (sin), ARG(-3.14193792057279441821e+00,-5.0e-01), RES(3.8933200722526827075e-4, 5.2109527443404709211e-1)}, {FN (sin), ARG(3.14193792057279441821e+00,1.0e+00), RES(-5.3277478472492034385e-4, -1.1752011235963524660e0)}, {FN (sin), ARG(3.14193792057279441821e+00,-1.0e+00), RES(-5.3277478472492034385e-4, 1.1752011235963524660e0)}, {FN (sin), ARG(-3.14193792057279441821e+00,1.0e+00), RES(5.3277478472492034385e-4, -1.1752011235963524660e0)}, {FN (sin), ARG(-3.14193792057279441821e+00,-1.0e+00), RES(5.3277478472492034385e-4, 1.1752011235963524660e0)}, {FN (sin), ARG(3.14193792057279441821e+00,2.0e+00), RES(-1.2989619299124286975e-3, -3.6268601916692946556e0)}, {FN (sin), ARG(3.14193792057279441821e+00,-2.0e+00), RES(-1.2989619299124286975e-3, 3.6268601916692946556e0)}, {FN (sin), ARG(-3.14193792057279441821e+00,2.0e+00), RES(1.2989619299124286975e-3, -3.6268601916692946556e0)}, {FN (sin), ARG(-3.14193792057279441821e+00,-2.0e+00), RES(1.2989619299124286975e-3, 3.6268601916692946556e0)}, {FN (sin), ARG(4.71204371340168837179e+00,0.0e+00), RES(-9.9999994039535581664e-1, 0.0)}, {FN (sin), ARG(-4.71204371340168837179e+00,0.0e+00), RES(9.9999994039535581664e-1, 0.0)}, {FN (sin), ARG(4.71204371340168837179e+00,1.19209289550781250e-07), RES(-9.9999994039536292207e-1, -4.1159030931192414605e-11)}, {FN (sin), ARG(4.71204371340168837179e+00,-1.19209289550781250e-07), RES(-9.9999994039536292207e-1, 4.1159030931192414605e-11)}, {FN (sin), ARG(-4.71204371340168837179e+00,1.19209289550781250e-07), RES(9.9999994039536292207e-1, -4.1159030931192414605e-11)}, {FN (sin), ARG(-4.71204371340168837179e+00,-1.19209289550781250e-07), RES(9.9999994039536292207e-1, 4.1159030931192414605e-11)}, {FN (sin), ARG(4.71204371340168837179e+00,5.0e-01), RES(-1.1276258979946363572e0, -1.7991700040943409243e-4)}, {FN (sin), ARG(4.71204371340168837179e+00,-5.0e-01), RES(-1.1276258979946363572e0, 1.7991700040943409243e-4)}, {FN (sin), ARG(-4.71204371340168837179e+00,5.0e-01), RES(1.1276258979946363572e0, -1.7991700040943409243e-4)}, {FN (sin), ARG(-4.71204371340168837179e+00,-5.0e-01), RES(1.1276258979946363572e0, 1.7991700040943409243e-4)}, {FN (sin), ARG(4.71204371340168837179e+00,1.0e+00), RES(-1.5430805428404715941e0, -4.0575816248744985081e-4)}, {FN (sin), ARG(4.71204371340168837179e+00,-1.0e+00), RES(-1.5430805428404715941e0, 4.0575816248744985081e-4)}, {FN (sin), ARG(-4.71204371340168837179e+00,1.0e+00), RES(1.5430805428404715941e0, -4.0575816248744985081e-4)}, {FN (sin), ARG(-4.71204371340168837179e+00,-1.0e+00), RES(1.5430805428404715941e0, 4.0575816248744985081e-4)}, {FN (sin), ARG(4.71204371340168837179e+00,2.0e+00), RES(-3.7621954668392959444e0, -1.2522351259052019007e-3)}, {FN (sin), ARG(4.71204371340168837179e+00,-2.0e+00), RES(-3.7621954668392959444e0, 1.2522351259052019007e-3)}, {FN (sin), ARG(-4.71204371340168837179e+00,2.0e+00), RES(3.7621954668392959444e0, -1.2522351259052019007e-3)}, {FN (sin), ARG(-4.71204371340168837179e+00,-2.0e+00), RES(3.7621954668392959444e0, 1.2522351259052019007e-3)}, {FN (sin), ARG(4.71273424736769097620e+00,0.0e+00), RES(-9.9999994039535581677e-1, 0.0)}, {FN (sin), ARG(-4.71273424736769097620e+00,0.0e+00), RES(9.9999994039535581677e-1, 0.0)}, {FN (sin), ARG(4.71273424736769097620e+00,1.19209289550781250e-07), RES(-9.9999994039536292220e-1, 4.1159030931148617825e-11)}, {FN (sin), ARG(4.71273424736769097620e+00,-1.19209289550781250e-07), RES(-9.9999994039536292220e-1, -4.1159030931148617825e-11)}, {FN (sin), ARG(-4.71273424736769097620e+00,1.19209289550781250e-07), RES(9.9999994039536292220e-1, 4.1159030931148617825e-11)}, {FN (sin), ARG(-4.71273424736769097620e+00,-1.19209289550781250e-07), RES(9.9999994039536292220e-1, -4.1159030931148617825e-11)}, {FN (sin), ARG(4.71273424736769097620e+00,5.0e-01), RES(-1.1276258979946363573e0, 1.7991700040924264514e-4)}, {FN (sin), ARG(4.71273424736769097620e+00,-5.0e-01), RES(-1.1276258979946363573e0, -1.7991700040924264514e-4)}, {FN (sin), ARG(-4.71273424736769097620e+00,5.0e-01), RES(1.1276258979946363573e0, 1.7991700040924264514e-4)}, {FN (sin), ARG(-4.71273424736769097620e+00,-5.0e-01), RES(1.1276258979946363573e0, -1.7991700040924264514e-4)}, {FN (sin), ARG(4.71273424736769097620e+00,1.0e+00), RES(-1.5430805428404715943e0, 4.0575816248701808892e-4)}, {FN (sin), ARG(4.71273424736769097620e+00,-1.0e+00), RES(-1.5430805428404715943e0, -4.0575816248701808892e-4)}, {FN (sin), ARG(-4.71273424736769097620e+00,1.0e+00), RES(1.5430805428404715943e0, 4.0575816248701808892e-4)}, {FN (sin), ARG(-4.71273424736769097620e+00,-1.0e+00), RES(1.5430805428404715943e0, -4.0575816248701808892e-4)}, {FN (sin), ARG(4.71273424736769097620e+00,2.0e+00), RES(-3.7621954668392959448e0, 1.2522351259038694139e-3)}, {FN (sin), ARG(4.71273424736769097620e+00,-2.0e+00), RES(-3.7621954668392959448e0, -1.2522351259038694139e-3)}, {FN (sin), ARG(-4.71273424736769097620e+00,2.0e+00), RES(3.7621954668392959448e0, 1.2522351259038694139e-3)}, {FN (sin), ARG(-4.71273424736769097620e+00,-2.0e+00), RES(3.7621954668392959448e0, -1.2522351259038694139e-3)}, {FN (sin), ARG(6.28284004019658492979e+00,0.0e+00), RES(-3.4526697614170855328e-4, 0.0)}, {FN (sin), ARG(-6.28284004019658492979e+00,0.0e+00), RES(3.4526697614170855328e-4, 0.0)}, {FN (sin), ARG(6.28284004019658492979e+00,1.19209289550781250e-07), RES(-3.4526697614171100655e-4, 1.1920928244535424532e-7)}, {FN (sin), ARG(6.28284004019658492979e+00,-1.19209289550781250e-07), RES(-3.4526697614171100655e-4, -1.1920928244535424532e-7)}, {FN (sin), ARG(-6.28284004019658492979e+00,1.19209289550781250e-07), RES(3.4526697614171100655e-4, 1.1920928244535424532e-7)}, {FN (sin), ARG(-6.28284004019658492979e+00,-1.19209289550781250e-07), RES(3.4526697614171100655e-4, -1.1920928244535424532e-7)}, {FN (sin), ARG(6.28284004019658492979e+00,5.0e-01), RES(-3.8933200722568255379e-4, 5.2109527443404709204e-1)}, {FN (sin), ARG(6.28284004019658492979e+00,-5.0e-01), RES(-3.8933200722568255379e-4, -5.2109527443404709204e-1)}, {FN (sin), ARG(-6.28284004019658492979e+00,5.0e-01), RES(3.8933200722568255379e-4, 5.2109527443404709204e-1)}, {FN (sin), ARG(-6.28284004019658492979e+00,-5.0e-01), RES(3.8933200722568255379e-4, -5.2109527443404709204e-1)}, {FN (sin), ARG(6.28284004019658492979e+00,1.0e+00), RES(-5.3277478472548726245e-4, 1.1752011235963524659e0)}, {FN (sin), ARG(6.28284004019658492979e+00,-1.0e+00), RES(-5.3277478472548726245e-4, -1.1752011235963524659e0)}, {FN (sin), ARG(-6.28284004019658492979e+00,1.0e+00), RES(5.3277478472548726245e-4, 1.1752011235963524659e0)}, {FN (sin), ARG(-6.28284004019658492979e+00,-1.0e+00), RES(5.3277478472548726245e-4, -1.1752011235963524659e0)}, {FN (sin), ARG(6.28284004019658492979e+00,2.0e+00), RES(-1.2989619299138109057e-3, 3.6268601916692946552e0)}, {FN (sin), ARG(6.28284004019658492979e+00,-2.0e+00), RES(-1.2989619299138109057e-3, -3.6268601916692946552e0)}, {FN (sin), ARG(-6.28284004019658492979e+00,2.0e+00), RES(1.2989619299138109057e-3, 3.6268601916692946552e0)}, {FN (sin), ARG(-6.28284004019658492979e+00,-2.0e+00), RES(1.2989619299138109057e-3, -3.6268601916692946552e0)}, {FN (sin), ARG(6.28353057416258753420e+00,0.0e+00), RES(3.4526697614121869459e-4, 0.0)}, {FN (sin), ARG(-6.28353057416258753420e+00,0.0e+00), RES(-3.4526697614121869459e-4, 0.0)}, {FN (sin), ARG(6.28353057416258753420e+00,1.19209289550781250e-07), RES(3.4526697614122114786e-4, 1.1920928244535424534e-7)}, {FN (sin), ARG(6.28353057416258753420e+00,-1.19209289550781250e-07), RES(3.4526697614122114786e-4, -1.1920928244535424534e-7)}, {FN (sin), ARG(-6.28353057416258753420e+00,1.19209289550781250e-07), RES(-3.4526697614122114786e-4, 1.1920928244535424534e-7)}, {FN (sin), ARG(-6.28353057416258753420e+00,-1.19209289550781250e-07), RES(-3.4526697614122114786e-4, -1.1920928244535424534e-7)}, {FN (sin), ARG(6.28353057416258753420e+00,5.0e-01), RES(3.8933200722513017641e-4, 5.2109527443404709213e-1)}, {FN (sin), ARG(6.28353057416258753420e+00,-5.0e-01), RES(3.8933200722513017641e-4, -5.2109527443404709213e-1)}, {FN (sin), ARG(-6.28353057416258753420e+00,5.0e-01), RES(-3.8933200722513017641e-4, 5.2109527443404709213e-1)}, {FN (sin), ARG(-6.28353057416258753420e+00,-5.0e-01), RES(-3.8933200722513017641e-4, -5.2109527443404709213e-1)}, {FN (sin), ARG(6.28353057416258753420e+00,1.0e+00), RES(5.3277478472473137099e-4, 1.1752011235963524661e0)}, {FN (sin), ARG(6.28353057416258753420e+00,-1.0e+00), RES(5.3277478472473137099e-4, -1.1752011235963524661e0)}, {FN (sin), ARG(-6.28353057416258753420e+00,1.0e+00), RES(-5.3277478472473137099e-4, 1.1752011235963524661e0)}, {FN (sin), ARG(-6.28353057416258753420e+00,-1.0e+00), RES(-5.3277478472473137099e-4, -1.1752011235963524661e0)}, {FN (sin), ARG(6.28353057416258753420e+00,2.0e+00), RES(1.2989619299119679614e-3, 3.6268601916692946558e0)}, {FN (sin), ARG(6.28353057416258753420e+00,-2.0e+00), RES(1.2989619299119679614e-3, -3.6268601916692946558e0)}, {FN (sin), ARG(-6.28353057416258753420e+00,2.0e+00), RES(-1.2989619299119679614e-3, 3.6268601916692946558e0)}, {FN (sin), ARG(-6.28353057416258753420e+00,-2.0e+00), RES(-1.2989619299119679614e-3, -3.6268601916692946558e0)}, {FN (sin), ARG(9.42443269378637893396e+00,0.0e+00), RES(3.4526697614094283958e-4, 0.0)}, {FN (sin), ARG(-9.42443269378637893396e+00,0.0e+00), RES(-3.4526697614094283958e-4, 0.0)}, {FN (sin), ARG(9.42443269378637893396e+00,1.19209289550781250e-07), RES(3.4526697614094529285e-4, -1.1920928244535424535e-7)}, {FN (sin), ARG(9.42443269378637893396e+00,-1.19209289550781250e-07), RES(3.4526697614094529285e-4, 1.1920928244535424535e-7)}, {FN (sin), ARG(-9.42443269378637893396e+00,1.19209289550781250e-07), RES(-3.4526697614094529285e-4, -1.1920928244535424535e-7)}, {FN (sin), ARG(-9.42443269378637893396e+00,-1.19209289550781250e-07), RES(-3.4526697614094529285e-4, 1.1920928244535424535e-7)}, {FN (sin), ARG(9.42443269378637893396e+00,5.0e-01), RES(3.8933200722481911514e-4, -5.2109527443404709218e-1)}, {FN (sin), ARG(9.42443269378637893396e+00,-5.0e-01), RES(3.8933200722481911514e-4, 5.2109527443404709218e-1)}, {FN (sin), ARG(-9.42443269378637893396e+00,5.0e-01), RES(-3.8933200722481911514e-4, -5.2109527443404709218e-1)}, {FN (sin), ARG(-9.42443269378637893396e+00,-5.0e-01), RES(-3.8933200722481911514e-4, 5.2109527443404709218e-1)}, {FN (sin), ARG(9.42443269378637893396e+00,1.0e+00), RES(5.3277478472430570447e-4, -1.1752011235963524662e0)}, {FN (sin), ARG(9.42443269378637893396e+00,-1.0e+00), RES(5.3277478472430570447e-4, 1.1752011235963524662e0)}, {FN (sin), ARG(-9.42443269378637893396e+00,1.0e+00), RES(-5.3277478472430570447e-4, -1.1752011235963524662e0)}, {FN (sin), ARG(-9.42443269378637893396e+00,-1.0e+00), RES(-5.3277478472430570447e-4, 1.1752011235963524662e0)}, {FN (sin), ARG(9.42443269378637893396e+00,2.0e+00), RES(1.2989619299109301409e-3, -3.6268601916692946561e0)}, {FN (sin), ARG(9.42443269378637893396e+00,-2.0e+00), RES(1.2989619299109301409e-3, 3.6268601916692946561e0)}, {FN (sin), ARG(-9.42443269378637893396e+00,2.0e+00), RES(-1.2989619299109301409e-3, -3.6268601916692946561e0)}, {FN (sin), ARG(-9.42443269378637893396e+00,-2.0e+00), RES(-1.2989619299109301409e-3, 3.6268601916692946561e0)}, {FN (sin), ARG(9.42512322775237976202e+00,0.0e+00), RES(-3.4526697614020805155e-4, 0.0)}, {FN (sin), ARG(-9.42512322775237976202e+00,0.0e+00), RES(3.4526697614020805155e-4, 0.0)}, {FN (sin), ARG(9.42512322775237976202e+00,1.19209289550781250e-07), RES(-3.4526697614021050482e-4, -1.1920928244535424538e-7)}, {FN (sin), ARG(9.42512322775237976202e+00,-1.19209289550781250e-07), RES(-3.4526697614021050482e-4, 1.1920928244535424538e-7)}, {FN (sin), ARG(-9.42512322775237976202e+00,1.19209289550781250e-07), RES(3.4526697614021050482e-4, -1.1920928244535424538e-7)}, {FN (sin), ARG(-9.42512322775237976202e+00,-1.19209289550781250e-07), RES(3.4526697614021050482e-4, 1.1920928244535424538e-7)}, {FN (sin), ARG(9.42512322775237976202e+00,5.0e-01), RES(-3.8933200722399054908e-4, -5.2109527443404709231e-1)}, {FN (sin), ARG(9.42512322775237976202e+00,-5.0e-01), RES(-3.8933200722399054908e-4, 5.2109527443404709231e-1)}, {FN (sin), ARG(-9.42512322775237976202e+00,5.0e-01), RES(3.8933200722399054908e-4, -5.2109527443404709231e-1)}, {FN (sin), ARG(-9.42512322775237976202e+00,-5.0e-01), RES(3.8933200722399054908e-4, 5.2109527443404709231e-1)}, {FN (sin), ARG(9.42512322775237976202e+00,1.0e+00), RES(-5.3277478472317186729e-4, -1.1752011235963524665e0)}, {FN (sin), ARG(9.42512322775237976202e+00,-1.0e+00), RES(-5.3277478472317186729e-4, 1.1752011235963524665e0)}, {FN (sin), ARG(-9.42512322775237976202e+00,1.0e+00), RES(5.3277478472317186729e-4, -1.1752011235963524665e0)}, {FN (sin), ARG(-9.42512322775237976202e+00,-1.0e+00), RES(5.3277478472317186729e-4, 1.1752011235963524665e0)}, {FN (sin), ARG(9.42512322775237976202e+00,2.0e+00), RES(-1.2989619299081657245e-3, -3.6268601916692946571e0)}, {FN (sin), ARG(9.42512322775237976202e+00,-2.0e+00), RES(-1.2989619299081657245e-3, 3.6268601916692946571e0)}, {FN (sin), ARG(-9.42512322775237976202e+00,2.0e+00), RES(1.2989619299081657245e-3, -3.6268601916692946571e0)}, {FN (sin), ARG(-9.42512322775237976202e+00,-2.0e+00), RES(1.2989619299081657245e-3, 3.6268601916692946571e0)}, {FN (cos), ARG(-3.45266983001243932001e-04,0.0e+00), RES(9.9999994039535581673e-1, 0.0)}, {FN (cos), ARG(3.45266983001243932001e-04,0.0e+00), RES(9.9999994039535581673e-1, 0.0)}, {FN (cos), ARG(-3.45266983001243932001e-04,1.19209289550781250e-07), RES(9.9999994039536292216e-1, 4.1159030931163569191e-11)}, {FN (cos), ARG(-3.45266983001243932001e-04,-1.19209289550781250e-07), RES(9.9999994039536292216e-1, -4.1159030931163569191e-11)}, {FN (cos), ARG(3.45266983001243932001e-04,1.19209289550781250e-07), RES(9.9999994039536292216e-1, -4.1159030931163569191e-11)}, {FN (cos), ARG(3.45266983001243932001e-04,-1.19209289550781250e-07), RES(9.9999994039536292216e-1, 4.1159030931163569191e-11)}, {FN (cos), ARG(-3.45266983001243932001e-04,5.0e-01), RES(1.1276258979946363573e0, 1.7991700040930800151e-4)}, {FN (cos), ARG(-3.45266983001243932001e-04,-5.0e-01), RES(1.1276258979946363573e0, -1.7991700040930800151e-4)}, {FN (cos), ARG(3.45266983001243932001e-04,5.0e-01), RES(1.1276258979946363573e0, -1.7991700040930800151e-4)}, {FN (cos), ARG(3.45266983001243932001e-04,-5.0e-01), RES(1.1276258979946363573e0, 1.7991700040930800151e-4)}, {FN (cos), ARG(-3.45266983001243932001e-04,1.0e+00), RES(1.5430805428404715942e0, 4.057581624871654840e-4)}, {FN (cos), ARG(-3.45266983001243932001e-04,-1.0e+00), RES(1.5430805428404715942e0, -4.057581624871654840e-4)}, {FN (cos), ARG(3.45266983001243932001e-04,1.0e+00), RES(1.5430805428404715942e0, -4.057581624871654840e-4)}, {FN (cos), ARG(3.45266983001243932001e-04,-1.0e+00), RES(1.5430805428404715942e0, 4.057581624871654840e-4)}, {FN (cos), ARG(-3.45266983001243932001e-04,2.0e+00), RES(3.7621954668392959447e0, 1.2522351259043242989e-3)}, {FN (cos), ARG(-3.45266983001243932001e-04,-2.0e+00), RES(3.7621954668392959447e0, -1.2522351259043242989e-3)}, {FN (cos), ARG(3.45266983001243932001e-04,2.0e+00), RES(3.7621954668392959447e0, -1.2522351259043242989e-3)}, {FN (cos), ARG(3.45266983001243932001e-04,-2.0e+00), RES(3.7621954668392959447e0, 1.2522351259043242989e-3)}, {FN (cos), ARG(1.57045105981189525579e+00,0.0e+00), RES(3.4526697614152485627e-4, 0.0)}, {FN (cos), ARG(-1.57045105981189525579e+00,0.0e+00), RES(3.4526697614152485627e-4, 0.0)}, {FN (cos), ARG(1.57045105981189525579e+00,1.19209289550781250e-07), RES(3.4526697614152730954e-4, -1.1920928244535424532e-7)}, {FN (cos), ARG(1.57045105981189525579e+00,-1.19209289550781250e-07), RES(3.4526697614152730954e-4, 1.1920928244535424532e-7)}, {FN (cos), ARG(-1.57045105981189525579e+00,1.19209289550781250e-07), RES(3.4526697614152730954e-4, 1.1920928244535424532e-7)}, {FN (cos), ARG(-1.57045105981189525579e+00,-1.19209289550781250e-07), RES(3.4526697614152730954e-4, -1.1920928244535424532e-7)}, {FN (cos), ARG(1.57045105981189525579e+00,5.0e-01), RES(3.8933200722547541227e-4, -5.2109527443404709207e-1)}, {FN (cos), ARG(1.57045105981189525579e+00,-5.0e-01), RES(3.8933200722547541227e-4, 5.2109527443404709207e-1)}, {FN (cos), ARG(-1.57045105981189525579e+00,5.0e-01), RES(3.8933200722547541227e-4, 5.2109527443404709207e-1)}, {FN (cos), ARG(-1.57045105981189525579e+00,-5.0e-01), RES(3.8933200722547541227e-4, -5.2109527443404709207e-1)}, {FN (cos), ARG(1.57045105981189525579e+00,1.0e+00), RES(5.3277478472520380315e-4, -1.1752011235963524659e0)}, {FN (cos), ARG(1.57045105981189525579e+00,-1.0e+00), RES(5.3277478472520380315e-4, 1.1752011235963524659e0)}, {FN (cos), ARG(-1.57045105981189525579e+00,1.0e+00), RES(5.3277478472520380315e-4, 1.1752011235963524659e0)}, {FN (cos), ARG(-1.57045105981189525579e+00,-1.0e+00), RES(5.3277478472520380315e-4, -1.1752011235963524659e0)}, {FN (cos), ARG(1.57045105981189525579e+00,2.0e+00), RES(1.2989619299131198016e-3, -3.6268601916692946554e0)}, {FN (cos), ARG(1.57045105981189525579e+00,-2.0e+00), RES(1.2989619299131198016e-3, 3.6268601916692946554e0)}, {FN (cos), ARG(-1.57045105981189525579e+00,2.0e+00), RES(1.2989619299131198016e-3, 3.6268601916692946554e0)}, {FN (cos), ARG(-1.57045105981189525579e+00,-2.0e+00), RES(1.2989619299131198016e-3, -3.6268601916692946554e0)}, {FN (cos), ARG(1.57114159377789786021e+00,0.0e+00), RES(-3.4526697614140239160e-4, 0.0)}, {FN (cos), ARG(-1.57114159377789786021e+00,0.0e+00), RES(-3.4526697614140239160e-4, 0.0)}, {FN (cos), ARG(1.57114159377789786021e+00,1.19209289550781250e-07), RES(-3.4526697614140484486e-4, -1.1920928244535424533e-7)}, {FN (cos), ARG(1.57114159377789786021e+00,-1.19209289550781250e-07), RES(-3.4526697614140484486e-4, 1.1920928244535424533e-7)}, {FN (cos), ARG(-1.57114159377789786021e+00,1.19209289550781250e-07), RES(-3.4526697614140484486e-4, 1.1920928244535424533e-7)}, {FN (cos), ARG(-1.57114159377789786021e+00,-1.19209289550781250e-07), RES(-3.4526697614140484486e-4, -1.1920928244535424533e-7)}, {FN (cos), ARG(1.57114159377789786021e+00,5.0e-01), RES(-3.8933200722533731792e-4, -5.2109527443404709209e-1)}, {FN (cos), ARG(1.57114159377789786021e+00,-5.0e-01), RES(-3.8933200722533731792e-4, 5.2109527443404709209e-1)}, {FN (cos), ARG(-1.57114159377789786021e+00,5.0e-01), RES(-3.8933200722533731792e-4, 5.2109527443404709209e-1)}, {FN (cos), ARG(-1.57114159377789786021e+00,-5.0e-01), RES(-3.8933200722533731792e-4, -5.2109527443404709209e-1)}, {FN (cos), ARG(1.57114159377789786021e+00,1.0e+00), RES(-5.3277478472501483029e-4, -1.1752011235963524660e0)}, {FN (cos), ARG(1.57114159377789786021e+00,-1.0e+00), RES(-5.3277478472501483029e-4, 1.1752011235963524660e0)}, {FN (cos), ARG(-1.57114159377789786021e+00,1.0e+00), RES(-5.3277478472501483029e-4, 1.1752011235963524660e0)}, {FN (cos), ARG(-1.57114159377789786021e+00,-1.0e+00), RES(-5.3277478472501483029e-4, -1.1752011235963524660e0)}, {FN (cos), ARG(1.57114159377789786021e+00,2.0e+00), RES(-1.2989619299126590655e-3, -3.6268601916692946556e0)}, {FN (cos), ARG(1.57114159377789786021e+00,-2.0e+00), RES(-1.2989619299126590655e-3, 3.6268601916692946556e0)}, {FN (cos), ARG(-1.57114159377789786021e+00,2.0e+00), RES(-1.2989619299126590655e-3, 3.6268601916692946556e0)}, {FN (cos), ARG(-1.57114159377789786021e+00,-2.0e+00), RES(-1.2989619299126590655e-3, -3.6268601916692946556e0)}, {FN (cos), ARG(3.14124738660679181379e+00,0.0e+00), RES(-9.9999994039535581667e-1, 0.0)}, {FN (cos), ARG(-3.14124738660679181379e+00,0.0e+00), RES(-9.9999994039535581667e-1, 0.0)}, {FN (cos), ARG(3.14124738660679181379e+00,1.19209289550781250e-07), RES(-9.9999994039536292209e-1, -4.1159030931185115142e-11)}, {FN (cos), ARG(3.14124738660679181379e+00,-1.19209289550781250e-07), RES(-9.9999994039536292209e-1, 4.1159030931185115142e-11)}, {FN (cos), ARG(-3.14124738660679181379e+00,1.19209289550781250e-07), RES(-9.9999994039536292209e-1, 4.1159030931185115142e-11)}, {FN (cos), ARG(-3.14124738660679181379e+00,-1.19209289550781250e-07), RES(-9.9999994039536292209e-1, -4.1159030931185115142e-11)}, {FN (cos), ARG(3.14124738660679181379e+00,5.0e-01), RES(-1.1276258979946363572e0, -1.7991700040940218455e-4)}, {FN (cos), ARG(3.14124738660679181379e+00,-5.0e-01), RES(-1.1276258979946363572e0, 1.7991700040940218455e-4)}, {FN (cos), ARG(-3.14124738660679181379e+00,5.0e-01), RES(-1.1276258979946363572e0, 1.7991700040940218455e-4)}, {FN (cos), ARG(-3.14124738660679181379e+00,-5.0e-01), RES(-1.1276258979946363572e0, -1.7991700040940218455e-4)}, {FN (cos), ARG(3.14124738660679181379e+00,1.0e+00), RES(-1.5430805428404715941e0, -4.0575816248737789049e-4)}, {FN (cos), ARG(3.14124738660679181379e+00,-1.0e+00), RES(-1.5430805428404715941e0, 4.0575816248737789049e-4)}, {FN (cos), ARG(-3.14124738660679181379e+00,1.0e+00), RES(-1.5430805428404715941e0, 4.0575816248737789049e-4)}, {FN (cos), ARG(-3.14124738660679181379e+00,-1.0e+00), RES(-1.5430805428404715941e0, -4.0575816248737789049e-4)}, {FN (cos), ARG(3.14124738660679181379e+00,2.0e+00), RES(-3.7621954668392959444e0, -1.2522351259049798196e-3)}, {FN (cos), ARG(3.14124738660679181379e+00,-2.0e+00), RES(-3.7621954668392959444e0, 1.2522351259049798196e-3)}, {FN (cos), ARG(-3.14124738660679181379e+00,2.0e+00), RES(-3.7621954668392959444e0, 1.2522351259049798196e-3)}, {FN (cos), ARG(-3.14124738660679181379e+00,-2.0e+00), RES(-3.7621954668392959444e0, -1.2522351259049798196e-3)}, {FN (cos), ARG(3.14193792057279441821e+00,0.0e+00), RES(-9.9999994039535581675e-1, 0.0)}, {FN (cos), ARG(-3.14193792057279441821e+00,0.0e+00), RES(-9.9999994039535581675e-1, 0.0)}, {FN (cos), ARG(3.14193792057279441821e+00,1.19209289550781250e-07), RES(-9.9999994039536292218e-1, 4.1159030931155917289e-11)}, {FN (cos), ARG(3.14193792057279441821e+00,-1.19209289550781250e-07), RES(-9.9999994039536292218e-1, -4.1159030931155917289e-11)}, {FN (cos), ARG(-3.14193792057279441821e+00,1.19209289550781250e-07), RES(-9.9999994039536292218e-1, -4.1159030931155917289e-11)}, {FN (cos), ARG(-3.14193792057279441821e+00,-1.19209289550781250e-07), RES(-9.9999994039536292218e-1, 4.1159030931155917289e-11)}, {FN (cos), ARG(3.14193792057279441821e+00,5.0e-01), RES(-1.1276258979946363573e0, 1.7991700040927455302e-4)}, {FN (cos), ARG(3.14193792057279441821e+00,-5.0e-01), RES(-1.1276258979946363573e0, -1.7991700040927455302e-4)}, {FN (cos), ARG(-3.14193792057279441821e+00,5.0e-01), RES(-1.1276258979946363573e0, -1.7991700040927455302e-4)}, {FN (cos), ARG(-3.14193792057279441821e+00,-5.0e-01), RES(-1.1276258979946363573e0, 1.7991700040927455302e-4)}, {FN (cos), ARG(3.14193792057279441821e+00,1.0e+00), RES(-1.5430805428404715943e0, 4.0575816248709004923e-4)}, {FN (cos), ARG(3.14193792057279441821e+00,-1.0e+00), RES(-1.5430805428404715943e0, -4.0575816248709004923e-4)}, {FN (cos), ARG(-3.14193792057279441821e+00,1.0e+00), RES(-1.5430805428404715943e0, -4.0575816248709004923e-4)}, {FN (cos), ARG(-3.14193792057279441821e+00,-1.0e+00), RES(-1.5430805428404715943e0, 4.0575816248709004923e-4)}, {FN (cos), ARG(3.14193792057279441821e+00,2.0e+00), RES(-3.7621954668392959448e0, 1.2522351259040914950e-3)}, {FN (cos), ARG(3.14193792057279441821e+00,-2.0e+00), RES(-3.7621954668392959448e0, -1.2522351259040914950e-3)}, {FN (cos), ARG(-3.14193792057279441821e+00,2.0e+00), RES(-3.7621954668392959448e0, -1.2522351259040914950e-3)}, {FN (cos), ARG(-3.14193792057279441821e+00,-2.0e+00), RES(-3.7621954668392959448e0, 1.2522351259040914950e-3)}, {FN (cos), ARG(4.71204371340168837179e+00,0.0e+00), RES(-3.4526697614164732094e-4, 0.0)}, {FN (cos), ARG(-4.71204371340168837179e+00,0.0e+00), RES(-3.4526697614164732094e-4, 0.0)}, {FN (cos), ARG(4.71204371340168837179e+00,1.19209289550781250e-07), RES(-3.4526697614164977421e-4, 1.1920928244535424532e-7)}, {FN (cos), ARG(4.71204371340168837179e+00,-1.19209289550781250e-07), RES(-3.4526697614164977421e-4, -1.1920928244535424532e-7)}, {FN (cos), ARG(-4.71204371340168837179e+00,1.19209289550781250e-07), RES(-3.4526697614164977421e-4, -1.1920928244535424532e-7)}, {FN (cos), ARG(-4.71204371340168837179e+00,-1.19209289550781250e-07), RES(-3.4526697614164977421e-4, 1.1920928244535424532e-7)}, {FN (cos), ARG(4.71204371340168837179e+00,5.0e-01), RES(-3.8933200722561350661e-4, 5.2109527443404709205e-1)}, {FN (cos), ARG(4.71204371340168837179e+00,-5.0e-01), RES(-3.8933200722561350661e-4, -5.2109527443404709205e-1)}, {FN (cos), ARG(-4.71204371340168837179e+00,5.0e-01), RES(-3.8933200722561350661e-4, -5.2109527443404709205e-1)}, {FN (cos), ARG(-4.71204371340168837179e+00,-5.0e-01), RES(-3.8933200722561350661e-4, 5.2109527443404709205e-1)}, {FN (cos), ARG(4.71204371340168837179e+00,1.0e+00), RES(-5.3277478472539277601e-4, 1.1752011235963524659e0)}, {FN (cos), ARG(4.71204371340168837179e+00,-1.0e+00), RES(-5.3277478472539277601e-4, -1.1752011235963524659e0)}, {FN (cos), ARG(-4.71204371340168837179e+00,1.0e+00), RES(-5.3277478472539277601e-4, -1.1752011235963524659e0)}, {FN (cos), ARG(-4.71204371340168837179e+00,-1.0e+00), RES(-5.3277478472539277601e-4, 1.1752011235963524659e0)}, {FN (cos), ARG(4.71204371340168837179e+00,2.0e+00), RES(-1.2989619299135805376e-3, 3.6268601916692946552e0)}, {FN (cos), ARG(4.71204371340168837179e+00,-2.0e+00), RES(-1.2989619299135805376e-3, -3.6268601916692946552e0)}, {FN (cos), ARG(-4.71204371340168837179e+00,2.0e+00), RES(-1.2989619299135805376e-3, -3.6268601916692946552e0)}, {FN (cos), ARG(-4.71204371340168837179e+00,-2.0e+00), RES(-1.2989619299135805376e-3, 3.6268601916692946552e0)}, {FN (cos), ARG(4.71273424736769097620e+00,0.0e+00), RES(3.4526697614127992692e-4, 0.0)}, {FN (cos), ARG(-4.71273424736769097620e+00,0.0e+00), RES(3.4526697614127992692e-4, 0.0)}, {FN (cos), ARG(4.71273424736769097620e+00,1.19209289550781250e-07), RES(3.4526697614128238019e-4, 1.1920928244535424533e-7)}, {FN (cos), ARG(4.71273424736769097620e+00,-1.19209289550781250e-07), RES(3.4526697614128238019e-4, -1.1920928244535424533e-7)}, {FN (cos), ARG(-4.71273424736769097620e+00,1.19209289550781250e-07), RES(3.4526697614128238019e-4, -1.1920928244535424533e-7)}, {FN (cos), ARG(-4.71273424736769097620e+00,-1.19209289550781250e-07), RES(3.4526697614128238019e-4, 1.1920928244535424533e-7)}, {FN (cos), ARG(4.71273424736769097620e+00,5.0e-01), RES(3.8933200722519922358e-4, 5.2109527443404709212e-1)}, {FN (cos), ARG(4.71273424736769097620e+00,-5.0e-01), RES(3.8933200722519922358e-4, -5.2109527443404709212e-1)}, {FN (cos), ARG(-4.71273424736769097620e+00,5.0e-01), RES(3.8933200722519922358e-4, -5.2109527443404709212e-1)}, {FN (cos), ARG(-4.71273424736769097620e+00,-5.0e-01), RES(3.8933200722519922358e-4, 5.2109527443404709212e-1)}, {FN (cos), ARG(4.71273424736769097620e+00,1.0e+00), RES(5.3277478472482585742e-4, 1.1752011235963524660e0)}, {FN (cos), ARG(4.71273424736769097620e+00,-1.0e+00), RES(5.3277478472482585742e-4, -1.1752011235963524660e0)}, {FN (cos), ARG(-4.71273424736769097620e+00,1.0e+00), RES(5.3277478472482585742e-4, -1.1752011235963524660e0)}, {FN (cos), ARG(-4.71273424736769097620e+00,-1.0e+00), RES(5.3277478472482585742e-4, 1.1752011235963524660e0)}, {FN (cos), ARG(4.71273424736769097620e+00,2.0e+00), RES(1.2989619299121983294e-3, 3.6268601916692946557e0)}, {FN (cos), ARG(4.71273424736769097620e+00,-2.0e+00), RES(1.2989619299121983294e-3, -3.6268601916692946557e0)}, {FN (cos), ARG(-4.71273424736769097620e+00,2.0e+00), RES(1.2989619299121983294e-3, -3.6268601916692946557e0)}, {FN (cos), ARG(-4.71273424736769097620e+00,-2.0e+00), RES(1.2989619299121983294e-3, 3.6268601916692946557e0)}, {FN (cos), ARG(6.28284004019658492979e+00,0.0e+00), RES(9.9999994039535581662e-1, 0.0)}, {FN (cos), ARG(-6.28284004019658492979e+00,0.0e+00), RES(9.9999994039535581662e-1, 0.0)}, {FN (cos), ARG(6.28284004019658492979e+00,1.19209289550781250e-07), RES(9.9999994039536292205e-1, 4.1159030931199714069e-11)}, {FN (cos), ARG(6.28284004019658492979e+00,-1.19209289550781250e-07), RES(9.9999994039536292205e-1, -4.1159030931199714069e-11)}, {FN (cos), ARG(-6.28284004019658492979e+00,1.19209289550781250e-07), RES(9.9999994039536292205e-1, -4.1159030931199714069e-11)}, {FN (cos), ARG(-6.28284004019658492979e+00,-1.19209289550781250e-07), RES(9.9999994039536292205e-1, 4.1159030931199714069e-11)}, {FN (cos), ARG(6.28284004019658492979e+00,5.0e-01), RES(1.1276258979946363572e0, 1.7991700040946600032e-4)}, {FN (cos), ARG(6.28284004019658492979e+00,-5.0e-01), RES(1.1276258979946363572e0, -1.7991700040946600032e-4)}, {FN (cos), ARG(-6.28284004019658492979e+00,5.0e-01), RES(1.1276258979946363572e0, -1.7991700040946600032e-4)}, {FN (cos), ARG(-6.28284004019658492979e+00,-5.0e-01), RES(1.1276258979946363572e0, 1.7991700040946600032e-4)}, {FN (cos), ARG(6.28284004019658492979e+00,1.0e+00), RES(1.5430805428404715941e0, 4.0575816248752181112e-4)}, {FN (cos), ARG(6.28284004019658492979e+00,-1.0e+00), RES(1.5430805428404715941e0, -4.0575816248752181112e-4)}, {FN (cos), ARG(-6.28284004019658492979e+00,1.0e+00), RES(1.5430805428404715941e0, -4.0575816248752181112e-4)}, {FN (cos), ARG(-6.28284004019658492979e+00,-1.0e+00), RES(1.5430805428404715941e0, 4.0575816248752181112e-4)}, {FN (cos), ARG(6.28284004019658492979e+00,2.0e+00), RES(3.7621954668392959443e0, 1.2522351259054239819e-3)}, {FN (cos), ARG(6.28284004019658492979e+00,-2.0e+00), RES(3.7621954668392959443e0, -1.2522351259054239819e-3)}, {FN (cos), ARG(-6.28284004019658492979e+00,2.0e+00), RES(3.7621954668392959443e0, -1.2522351259054239819e-3)}, {FN (cos), ARG(-6.28284004019658492979e+00,-2.0e+00), RES(3.7621954668392959443e0, 1.2522351259054239819e-3)}, {FN (cos), ARG(6.28353057416258753420e+00,0.0e+00), RES(9.9999994039535581679e-1, 0.0)}, {FN (cos), ARG(-6.28353057416258753420e+00,0.0e+00), RES(9.9999994039535581679e-1, 0.0)}, {FN (cos), ARG(6.28353057416258753420e+00,1.19209289550781250e-07), RES(9.9999994039536292222e-1, -4.1159030931141318362e-11)}, {FN (cos), ARG(6.28353057416258753420e+00,-1.19209289550781250e-07), RES(9.9999994039536292222e-1, 4.1159030931141318362e-11)}, {FN (cos), ARG(-6.28353057416258753420e+00,1.19209289550781250e-07), RES(9.9999994039536292222e-1, 4.1159030931141318362e-11)}, {FN (cos), ARG(-6.28353057416258753420e+00,-1.19209289550781250e-07), RES(9.9999994039536292222e-1, -4.1159030931141318362e-11)}, {FN (cos), ARG(6.28353057416258753420e+00,5.0e-01), RES(1.1276258979946363574e0, -1.7991700040921073725e-4)}, {FN (cos), ARG(6.28353057416258753420e+00,-5.0e-01), RES(1.1276258979946363574e0, 1.7991700040921073725e-4)}, {FN (cos), ARG(-6.28353057416258753420e+00,5.0e-01), RES(1.1276258979946363574e0, 1.7991700040921073725e-4)}, {FN (cos), ARG(-6.28353057416258753420e+00,-5.0e-01), RES(1.1276258979946363574e0, -1.7991700040921073725e-4)}, {FN (cos), ARG(6.28353057416258753420e+00,1.0e+00), RES(1.5430805428404715943e0, -4.0575816248694612861e-4)}, {FN (cos), ARG(6.28353057416258753420e+00,-1.0e+00), RES(1.5430805428404715943e0, 4.0575816248694612861e-4)}, {FN (cos), ARG(-6.28353057416258753420e+00,1.0e+00), RES(1.5430805428404715943e0, 4.0575816248694612861e-4)}, {FN (cos), ARG(-6.28353057416258753420e+00,-1.0e+00), RES(1.5430805428404715943e0, -4.0575816248694612861e-4)}, {FN (cos), ARG(6.28353057416258753420e+00,2.0e+00), RES(3.7621954668392959449e0, -1.2522351259036473328e-3)}, {FN (cos), ARG(6.28353057416258753420e+00,-2.0e+00), RES(3.7621954668392959449e0, 1.2522351259036473328e-3)}, {FN (cos), ARG(-6.28353057416258753420e+00,2.0e+00), RES(3.7621954668392959449e0, 1.2522351259036473328e-3)}, {FN (cos), ARG(-6.28353057416258753420e+00,-2.0e+00), RES(3.7621954668392959449e0, -1.2522351259036473328e-3)}, {FN (cos), ARG(9.42443269378637893396e+00,0.0e+00), RES(-9.9999994039535581689e-1, 0.0)}, {FN (cos), ARG(-9.42443269378637893396e+00,0.0e+00), RES(-9.9999994039535581689e-1, 0.0)}, {FN (cos), ARG(9.42443269378637893396e+00,1.19209289550781250e-07), RES(-9.9999994039536292231e-1, -4.1159030931108433883e-11)}, {FN (cos), ARG(9.42443269378637893396e+00,-1.19209289550781250e-07), RES(-9.9999994039536292231e-1, 4.1159030931108433883e-11)}, {FN (cos), ARG(-9.42443269378637893396e+00,1.19209289550781250e-07), RES(-9.9999994039536292231e-1, 4.1159030931108433883e-11)}, {FN (cos), ARG(-9.42443269378637893396e+00,-1.19209289550781250e-07), RES(-9.9999994039536292231e-1, -4.1159030931108433883e-11)}, {FN (cos), ARG(9.42443269378637893396e+00,5.0e-01), RES(-1.1276258979946363575e0, -1.7991700040906699050e-4)}, {FN (cos), ARG(9.42443269378637893396e+00,-5.0e-01), RES(-1.1276258979946363575e0, 1.7991700040906699050e-4)}, {FN (cos), ARG(-9.42443269378637893396e+00,5.0e-01), RES(-1.1276258979946363575e0, 1.7991700040906699050e-4)}, {FN (cos), ARG(-9.42443269378637893396e+00,-5.0e-01), RES(-1.1276258979946363575e0, -1.7991700040906699050e-4)}, {FN (cos), ARG(9.42443269378637893396e+00,1.0e+00), RES(-1.5430805428404715945e0, -4.0575816248662194348e-4)}, {FN (cos), ARG(9.42443269378637893396e+00,-1.0e+00), RES(-1.5430805428404715945e0, 4.0575816248662194348e-4)}, {FN (cos), ARG(-9.42443269378637893396e+00,1.0e+00), RES(-1.5430805428404715945e0, 4.0575816248662194348e-4)}, {FN (cos), ARG(-9.42443269378637893396e+00,-1.0e+00), RES(-1.5430805428404715945e0, -4.0575816248662194348e-4)}, {FN (cos), ARG(9.42443269378637893396e+00,2.0e+00), RES(-3.7621954668392959453e0, -1.2522351259026468452e-3)}, {FN (cos), ARG(9.42443269378637893396e+00,-2.0e+00), RES(-3.7621954668392959453e0, 1.2522351259026468452e-3)}, {FN (cos), ARG(-9.42443269378637893396e+00,2.0e+00), RES(-3.7621954668392959453e0, 1.2522351259026468452e-3)}, {FN (cos), ARG(-9.42443269378637893396e+00,-2.0e+00), RES(-3.7621954668392959453e0, -1.2522351259026468452e-3)}, {FN (cos), ARG(9.42512322775237976202e+00,0.0e+00), RES(-9.9999994039535581714e-1, 0.0)}, {FN (cos), ARG(-9.42512322775237976202e+00,0.0e+00), RES(-9.9999994039535581714e-1, 0.0)}, {FN (cos), ARG(9.42512322775237976202e+00,1.19209289550781250e-07), RES(-9.9999994039536292257e-1, 4.1159030931020840323e-11)}, {FN (cos), ARG(9.42512322775237976202e+00,-1.19209289550781250e-07), RES(-9.9999994039536292257e-1, -4.1159030931020840323e-11)}, {FN (cos), ARG(-9.42512322775237976202e+00,1.19209289550781250e-07), RES(-9.9999994039536292257e-1, -4.1159030931020840323e-11)}, {FN (cos), ARG(-9.42512322775237976202e+00,-1.19209289550781250e-07), RES(-9.9999994039536292257e-1, 4.1159030931020840323e-11)}, {FN (cos), ARG(9.42512322775237976202e+00,5.0e-01), RES(-1.1276258979946363577e0, 1.7991700040868409591e-4)}, {FN (cos), ARG(9.42512322775237976202e+00,-5.0e-01), RES(-1.1276258979946363577e0, -1.7991700040868409591e-4)}, {FN (cos), ARG(-9.42512322775237976202e+00,5.0e-01), RES(-1.1276258979946363577e0, -1.7991700040868409591e-4)}, {FN (cos), ARG(-9.42512322775237976202e+00,-5.0e-01), RES(-1.1276258979946363577e0, 1.7991700040868409591e-4)}, {FN (cos), ARG(9.42512322775237976202e+00,1.0e+00), RES(-1.5430805428404715949e0, 4.0575816248575841970e-4)}, {FN (cos), ARG(9.42512322775237976202e+00,-1.0e+00), RES(-1.5430805428404715949e0, -4.0575816248575841970e-4)}, {FN (cos), ARG(-9.42512322775237976202e+00,1.0e+00), RES(-1.5430805428404715949e0, -4.0575816248575841970e-4)}, {FN (cos), ARG(-9.42512322775237976202e+00,-1.0e+00), RES(-1.5430805428404715949e0, 4.0575816248575841970e-4)}, {FN (cos), ARG(9.42512322775237976202e+00,2.0e+00), RES(-3.7621954668392959462e0, 1.2522351258999818715e-3)}, {FN (cos), ARG(9.42512322775237976202e+00,-2.0e+00), RES(-3.7621954668392959462e0, -1.2522351258999818715e-3)}, {FN (cos), ARG(-9.42512322775237976202e+00,2.0e+00), RES(-3.7621954668392959462e0, -1.2522351258999818715e-3)}, {FN (cos), ARG(-9.42512322775237976202e+00,-2.0e+00), RES(-3.7621954668392959462e0, 1.2522351258999818715e-3)}, {FN (tan), ARG(-3.45266983001243932001e-04,0.0e+00), RES(-3.4526699672092183585e-4, 0.0)}, {FN (tan), ARG(3.45266983001243932001e-04,0.0e+00), RES(3.4526699672092183585e-4, 0.0)}, {FN (tan), ARG(-3.45266983001243932001e-04,1.19209289550781250e-07), RES(-3.4526699672091692931e-4, 1.1920930376163652989e-7)}, {FN (tan), ARG(-3.45266983001243932001e-04,-1.19209289550781250e-07), RES(-3.4526699672091692931e-4, -1.1920930376163652989e-7)}, {FN (tan), ARG(3.45266983001243932001e-04,1.19209289550781250e-07), RES(3.4526699672091692931e-4, 1.1920930376163652989e-7)}, {FN (tan), ARG(3.45266983001243932001e-04,-1.19209289550781250e-07), RES(3.4526699672091692931e-4, -1.1920930376163652989e-7)}, {FN (tan), ARG(-3.45266983001243932001e-04,5.0e-01), RES(-2.7153443992655805934e-4, 4.6211720058436229979e-1)}, {FN (tan), ARG(-3.45266983001243932001e-04,-5.0e-01), RES(-2.7153443992655805934e-4, -4.6211720058436229979e-1)}, {FN (tan), ARG(3.45266983001243932001e-04,5.0e-01), RES(2.7153443992655805934e-4, 4.6211720058436229979e-1)}, {FN (tan), ARG(3.45266983001243932001e-04,-5.0e-01), RES(2.7153443992655805934e-4, -4.6211720058436229979e-1)}, {FN (tan), ARG(-3.45266983001243932001e-04,1.0e+00), RES(-1.4500326960274960880e-4, 7.6159419408485704836e-1)}, {FN (tan), ARG(-3.45266983001243932001e-04,-1.0e+00), RES(-1.4500326960274960880e-4, -7.6159419408485704836e-1)}, {FN (tan), ARG(3.45266983001243932001e-04,1.0e+00), RES(1.4500326960274960880e-4, 7.6159419408485704836e-1)}, {FN (tan), ARG(3.45266983001243932001e-04,-1.0e+00), RES(1.4500326960274960880e-4, -7.6159419408485704836e-1)}, {FN (tan), ARG(-3.45266983001243932001e-04,2.0e+00), RES(-2.4393395410435306874e-5, 9.6402758819508310556e-1)}, {FN (tan), ARG(-3.45266983001243932001e-04,-2.0e+00), RES(-2.4393395410435306874e-5, -9.6402758819508310556e-1)}, {FN (tan), ARG(3.45266983001243932001e-04,2.0e+00), RES(2.4393395410435306874e-5, 9.6402758819508310556e-1)}, {FN (tan), ARG(3.45266983001243932001e-04,-2.0e+00), RES(2.4393395410435306874e-5, -9.6402758819508310556e-1)}, {FN (tan), ARG(1.57045105981189525579e+00,0.0e+00), RES(2.8963092606501007060e3, 0.0)}, {FN (tan), ARG(-1.57045105981189525579e+00,0.0e+00), RES(-2.8963092606501007060e3, 0.0)}, {FN (tan), ARG(1.57045105981189525579e+00,1.19209289550781250e-07), RES(2.8963089153831588642e3, 9.9999992052646305569e-1)}, {FN (tan), ARG(1.57045105981189525579e+00,-1.19209289550781250e-07), RES(2.8963089153831588642e3, -9.9999992052646305569e-1)}, {FN (tan), ARG(-1.57045105981189525579e+00,1.19209289550781250e-07), RES(-2.8963089153831588642e3, 9.9999992052646305569e-1)}, {FN (tan), ARG(-1.57045105981189525579e+00,-1.19209289550781250e-07), RES(-2.8963089153831588642e3, -9.9999992052646305569e-1)}, {FN (tan), ARG(1.57045105981189525579e+00,5.0e-01), RES(1.2715121175455623363e-3, 2.1639524637389325996e0)}, {FN (tan), ARG(1.57045105981189525579e+00,-5.0e-01), RES(1.2715121175455623363e-3, -2.1639524637389325996e0)}, {FN (tan), ARG(-1.57045105981189525579e+00,5.0e-01), RES(-1.2715121175455623363e-3, 2.1639524637389325996e0)}, {FN (tan), ARG(-1.57045105981189525579e+00,-5.0e-01), RES(-1.2715121175455623363e-3, -2.1639524637389325996e0)}, {FN (tan), ARG(1.57045105981189525579e+00,1.0e+00), RES(2.4999454374276273814e-4, 1.3130351721648674823e0)}, {FN (tan), ARG(1.57045105981189525579e+00,-1.0e+00), RES(2.4999454374276273814e-4, -1.3130351721648674823e0)}, {FN (tan), ARG(-1.57045105981189525579e+00,1.0e+00), RES(-2.4999454374276273814e-4, 1.3130351721648674823e0)}, {FN (tan), ARG(-1.57045105981189525579e+00,-1.0e+00), RES(-2.4999454374276273814e-4, -1.3130351721648674823e0)}, {FN (tan), ARG(1.57045105981189525579e+00,2.0e+00), RES(2.6247825506572821595e-5, 1.0373147113268752620e0)}, {FN (tan), ARG(1.57045105981189525579e+00,-2.0e+00), RES(2.6247825506572821595e-5, -1.0373147113268752620e0)}, {FN (tan), ARG(-1.57045105981189525579e+00,2.0e+00), RES(-2.6247825506572821595e-5, 1.0373147113268752620e0)}, {FN (tan), ARG(-1.57045105981189525579e+00,-2.0e+00), RES(-2.6247825506572821595e-5, -1.0373147113268752620e0)}, {FN (tan), ARG(1.57114159377789786021e+00,0.0e+00), RES(-2.8963092606511280143e3, 0.0)}, {FN (tan), ARG(-1.57114159377789786021e+00,0.0e+00), RES(2.8963092606511280143e3, 0.0)}, {FN (tan), ARG(1.57114159377789786021e+00,1.19209289550781250e-07), RES(-2.8963089153841861720e3, 9.9999992052717244672e-1)}, {FN (tan), ARG(1.57114159377789786021e+00,-1.19209289550781250e-07), RES(-2.8963089153841861720e3, -9.9999992052717244672e-1)}, {FN (tan), ARG(-1.57114159377789786021e+00,1.19209289550781250e-07), RES(2.8963089153841861720e3, 9.9999992052717244672e-1)}, {FN (tan), ARG(-1.57114159377789786021e+00,-1.19209289550781250e-07), RES(2.8963089153841861720e3, -9.9999992052717244672e-1)}, {FN (tan), ARG(1.57114159377789786021e+00,5.0e-01), RES(-1.2715121175451113370e-3, 2.1639524637389326002e0)}, {FN (tan), ARG(1.57114159377789786021e+00,-5.0e-01), RES(-1.2715121175451113370e-3, -2.1639524637389326002e0)}, {FN (tan), ARG(-1.57114159377789786021e+00,5.0e-01), RES(1.2715121175451113370e-3, 2.1639524637389326002e0)}, {FN (tan), ARG(-1.57114159377789786021e+00,-5.0e-01), RES(1.2715121175451113370e-3, -2.1639524637389326002e0)}, {FN (tan), ARG(1.57114159377789786021e+00,1.0e+00), RES(-2.4999454374267406620e-4, 1.3130351721648674824e0)}, {FN (tan), ARG(1.57114159377789786021e+00,-1.0e+00), RES(-2.4999454374267406620e-4, -1.3130351721648674824e0)}, {FN (tan), ARG(-1.57114159377789786021e+00,1.0e+00), RES(2.4999454374267406620e-4, 1.3130351721648674824e0)}, {FN (tan), ARG(-1.57114159377789786021e+00,-1.0e+00), RES(2.4999454374267406620e-4, -1.3130351721648674824e0)}, {FN (tan), ARG(1.57114159377789786021e+00,2.0e+00), RES(-2.6247825506563511609e-5, 1.0373147113268752620e0)}, {FN (tan), ARG(1.57114159377789786021e+00,-2.0e+00), RES(-2.6247825506563511609e-5, -1.0373147113268752620e0)}, {FN (tan), ARG(-1.57114159377789786021e+00,2.0e+00), RES(2.6247825506563511609e-5, 1.0373147113268752620e0)}, {FN (tan), ARG(-1.57114159377789786021e+00,-2.0e+00), RES(2.6247825506563511609e-5, -1.0373147113268752620e0)}, {FN (tan), ARG(3.14124738660679181379e+00,0.0e+00), RES(-3.4526699672110257641e-4, 0.0)}, {FN (tan), ARG(-3.14124738660679181379e+00,0.0e+00), RES(3.4526699672110257641e-4, 0.0)}, {FN (tan), ARG(3.14124738660679181379e+00,1.19209289550781250e-07), RES(-3.4526699672109766987e-4, 1.1920930376163652991e-7)}, {FN (tan), ARG(3.14124738660679181379e+00,-1.19209289550781250e-07), RES(-3.4526699672109766987e-4, -1.1920930376163652991e-7)}, {FN (tan), ARG(-3.14124738660679181379e+00,1.19209289550781250e-07), RES(3.4526699672109766987e-4, 1.1920930376163652991e-7)}, {FN (tan), ARG(-3.14124738660679181379e+00,-1.19209289550781250e-07), RES(3.4526699672109766987e-4, -1.1920930376163652991e-7)}, {FN (tan), ARG(3.14124738660679181379e+00,5.0e-01), RES(-2.7153443992670020234e-4, 4.6211720058436229984e-1)}, {FN (tan), ARG(3.14124738660679181379e+00,-5.0e-01), RES(-2.7153443992670020234e-4, -4.6211720058436229984e-1)}, {FN (tan), ARG(-3.14124738660679181379e+00,5.0e-01), RES(2.7153443992670020234e-4, 4.6211720058436229984e-1)}, {FN (tan), ARG(-3.14124738660679181379e+00,-5.0e-01), RES(2.7153443992670020234e-4, -4.6211720058436229984e-1)}, {FN (tan), ARG(3.14124738660679181379e+00,1.0e+00), RES(-1.4500326960282551519e-4, 7.6159419408485704840e-1)}, {FN (tan), ARG(3.14124738660679181379e+00,-1.0e+00), RES(-1.4500326960282551519e-4, -7.6159419408485704840e-1)}, {FN (tan), ARG(-3.14124738660679181379e+00,1.0e+00), RES(1.4500326960282551519e-4, 7.6159419408485704840e-1)}, {FN (tan), ARG(-3.14124738660679181379e+00,-1.0e+00), RES(1.4500326960282551519e-4, -7.6159419408485704840e-1)}, {FN (tan), ARG(3.14124738660679181379e+00,2.0e+00), RES(-2.4393395410448076340e-5, 9.6402758819508310557e-1)}, {FN (tan), ARG(3.14124738660679181379e+00,-2.0e+00), RES(-2.4393395410448076340e-5, -9.6402758819508310557e-1)}, {FN (tan), ARG(-3.14124738660679181379e+00,2.0e+00), RES(2.4393395410448076340e-5, 9.6402758819508310557e-1)}, {FN (tan), ARG(-3.14124738660679181379e+00,-2.0e+00), RES(2.4393395410448076340e-5, -9.6402758819508310557e-1)}, {FN (tan), ARG(3.14193792057279441821e+00,0.0e+00), RES(3.4526699672085764703e-4, 0.0)}, {FN (tan), ARG(-3.14193792057279441821e+00,0.0e+00), RES(-3.4526699672085764703e-4, 0.0)}, {FN (tan), ARG(3.14193792057279441821e+00,1.19209289550781250e-07), RES(3.4526699672085274049e-4, 1.1920930376163652989e-7)}, {FN (tan), ARG(3.14193792057279441821e+00,-1.19209289550781250e-07), RES(3.4526699672085274049e-4, -1.1920930376163652989e-7)}, {FN (tan), ARG(-3.14193792057279441821e+00,1.19209289550781250e-07), RES(-3.4526699672085274049e-4, 1.1920930376163652989e-7)}, {FN (tan), ARG(-3.14193792057279441821e+00,-1.19209289550781250e-07), RES(-3.4526699672085274049e-4, -1.1920930376163652989e-7)}, {FN (tan), ARG(3.14193792057279441821e+00,5.0e-01), RES(2.7153443992650757820e-4, 4.6211720058436229978e-1)}, {FN (tan), ARG(3.14193792057279441821e+00,-5.0e-01), RES(2.7153443992650757820e-4, -4.6211720058436229978e-1)}, {FN (tan), ARG(-3.14193792057279441821e+00,5.0e-01), RES(-2.7153443992650757820e-4, 4.6211720058436229978e-1)}, {FN (tan), ARG(-3.14193792057279441821e+00,-5.0e-01), RES(-2.7153443992650757820e-4, -4.6211720058436229978e-1)}, {FN (tan), ARG(3.14193792057279441821e+00,1.0e+00), RES(1.4500326960272265115e-4, 7.6159419408485704835e-1)}, {FN (tan), ARG(3.14193792057279441821e+00,-1.0e+00), RES(1.4500326960272265115e-4, -7.6159419408485704835e-1)}, {FN (tan), ARG(-3.14193792057279441821e+00,1.0e+00), RES(-1.4500326960272265115e-4, 7.6159419408485704835e-1)}, {FN (tan), ARG(-3.14193792057279441821e+00,-1.0e+00), RES(-1.4500326960272265115e-4, -7.6159419408485704835e-1)}, {FN (tan), ARG(3.14193792057279441821e+00,2.0e+00), RES(2.4393395410430771882e-5, 9.6402758819508310556e-1)}, {FN (tan), ARG(3.14193792057279441821e+00,-2.0e+00), RES(2.4393395410430771882e-5, -9.6402758819508310556e-1)}, {FN (tan), ARG(-3.14193792057279441821e+00,2.0e+00), RES(-2.4393395410430771882e-5, 9.6402758819508310556e-1)}, {FN (tan), ARG(-3.14193792057279441821e+00,-2.0e+00), RES(-2.4393395410430771882e-5, -9.6402758819508310556e-1)}, {FN (tan), ARG(4.71204371340168837179e+00,0.0e+00), RES(2.8963092606490733978e3, 0.0)}, {FN (tan), ARG(-4.71204371340168837179e+00,0.0e+00), RES(-2.8963092606490733978e3, 0.0)}, {FN (tan), ARG(4.71204371340168837179e+00,1.19209289550781250e-07), RES(2.8963089153821315563e3, 9.9999992052575366466e-1)}, {FN (tan), ARG(4.71204371340168837179e+00,-1.19209289550781250e-07), RES(2.8963089153821315563e3, -9.9999992052575366466e-1)}, {FN (tan), ARG(-4.71204371340168837179e+00,1.19209289550781250e-07), RES(-2.8963089153821315563e3, 9.9999992052575366466e-1)}, {FN (tan), ARG(-4.71204371340168837179e+00,-1.19209289550781250e-07), RES(-2.8963089153821315563e3, -9.9999992052575366466e-1)}, {FN (tan), ARG(4.71204371340168837179e+00,5.0e-01), RES(1.2715121175460133355e-3, 2.1639524637389325989e0)}, {FN (tan), ARG(4.71204371340168837179e+00,-5.0e-01), RES(1.2715121175460133355e-3, -2.1639524637389325989e0)}, {FN (tan), ARG(-4.71204371340168837179e+00,5.0e-01), RES(-1.2715121175460133355e-3, 2.1639524637389325989e0)}, {FN (tan), ARG(-4.71204371340168837179e+00,-5.0e-01), RES(-1.2715121175460133355e-3, -2.1639524637389325989e0)}, {FN (tan), ARG(4.71204371340168837179e+00,1.0e+00), RES(2.4999454374285141007e-4, 1.3130351721648674822e0)}, {FN (tan), ARG(4.71204371340168837179e+00,-1.0e+00), RES(2.4999454374285141007e-4, -1.3130351721648674822e0)}, {FN (tan), ARG(-4.71204371340168837179e+00,1.0e+00), RES(-2.4999454374285141007e-4, 1.3130351721648674822e0)}, {FN (tan), ARG(-4.71204371340168837179e+00,-1.0e+00), RES(-2.4999454374285141007e-4, -1.3130351721648674822e0)}, {FN (tan), ARG(4.71204371340168837179e+00,2.0e+00), RES(2.6247825506582131582e-5, 1.0373147113268752620e0)}, {FN (tan), ARG(4.71204371340168837179e+00,-2.0e+00), RES(2.6247825506582131582e-5, -1.0373147113268752620e0)}, {FN (tan), ARG(-4.71204371340168837179e+00,2.0e+00), RES(-2.6247825506582131582e-5, 1.0373147113268752620e0)}, {FN (tan), ARG(-4.71204371340168837179e+00,-2.0e+00), RES(-2.6247825506582131582e-5, -1.0373147113268752620e0)}, {FN (tan), ARG(4.71273424736769097620e+00,0.0e+00), RES(-2.8963092606521553225e3, 0.0)}, {FN (tan), ARG(-4.71273424736769097620e+00,0.0e+00), RES(2.8963092606521553225e3, 0.0)}, {FN (tan), ARG(4.71273424736769097620e+00,1.19209289550781250e-07), RES(-2.8963089153852134799e3, 9.9999992052788183776e-1)}, {FN (tan), ARG(4.71273424736769097620e+00,-1.19209289550781250e-07), RES(-2.8963089153852134799e3, -9.9999992052788183776e-1)}, {FN (tan), ARG(-4.71273424736769097620e+00,1.19209289550781250e-07), RES(2.8963089153852134799e3, 9.9999992052788183776e-1)}, {FN (tan), ARG(-4.71273424736769097620e+00,-1.19209289550781250e-07), RES(2.8963089153852134799e3, -9.9999992052788183776e-1)}, {FN (tan), ARG(4.71273424736769097620e+00,5.0e-01), RES(-1.2715121175446603377e-3, 2.1639524637389326009e0)}, {FN (tan), ARG(4.71273424736769097620e+00,-5.0e-01), RES(-1.2715121175446603377e-3, -2.1639524637389326009e0)}, {FN (tan), ARG(-4.71273424736769097620e+00,5.0e-01), RES(1.2715121175446603377e-3, 2.1639524637389326009e0)}, {FN (tan), ARG(-4.71273424736769097620e+00,-5.0e-01), RES(1.2715121175446603377e-3, -2.1639524637389326009e0)}, {FN (tan), ARG(4.71273424736769097620e+00,1.0e+00), RES(-2.4999454374258539427e-4, 1.3130351721648674825e0)}, {FN (tan), ARG(4.71273424736769097620e+00,-1.0e+00), RES(-2.4999454374258539427e-4, -1.3130351721648674825e0)}, {FN (tan), ARG(-4.71273424736769097620e+00,1.0e+00), RES(2.4999454374258539427e-4, 1.3130351721648674825e0)}, {FN (tan), ARG(-4.71273424736769097620e+00,-1.0e+00), RES(2.4999454374258539427e-4, -1.3130351721648674825e0)}, {FN (tan), ARG(4.71273424736769097620e+00,2.0e+00), RES(-2.6247825506554201622e-5, 1.0373147113268752620e0)}, {FN (tan), ARG(4.71273424736769097620e+00,-2.0e+00), RES(-2.6247825506554201622e-5, -1.0373147113268752620e0)}, {FN (tan), ARG(-4.71273424736769097620e+00,2.0e+00), RES(2.6247825506554201622e-5, 1.0373147113268752620e0)}, {FN (tan), ARG(-4.71273424736769097620e+00,-2.0e+00), RES(2.6247825506554201622e-5, -1.0373147113268752620e0)}, {FN (tan), ARG(6.28284004019658492979e+00,0.0e+00), RES(-3.4526699672122504111e-4, 0.0)}, {FN (tan), ARG(-6.28284004019658492979e+00,0.0e+00), RES(3.4526699672122504111e-4, 0.0)}, {FN (tan), ARG(6.28284004019658492979e+00,1.19209289550781250e-07), RES(-3.4526699672122013457e-4, 1.1920930376163652992e-7)}, {FN (tan), ARG(6.28284004019658492979e+00,-1.19209289550781250e-07), RES(-3.4526699672122013457e-4, -1.1920930376163652992e-7)}, {FN (tan), ARG(-6.28284004019658492979e+00,1.19209289550781250e-07), RES(3.4526699672122013457e-4, 1.1920930376163652992e-7)}, {FN (tan), ARG(-6.28284004019658492979e+00,-1.19209289550781250e-07), RES(3.4526699672122013457e-4, -1.1920930376163652992e-7)}, {FN (tan), ARG(6.28284004019658492979e+00,5.0e-01), RES(-2.7153443992679651442e-4, 4.6211720058436229987e-1)}, {FN (tan), ARG(6.28284004019658492979e+00,-5.0e-01), RES(-2.7153443992679651442e-4, -4.6211720058436229987e-1)}, {FN (tan), ARG(-6.28284004019658492979e+00,5.0e-01), RES(2.7153443992679651442e-4, 4.6211720058436229987e-1)}, {FN (tan), ARG(-6.28284004019658492979e+00,-5.0e-01), RES(2.7153443992679651442e-4, -4.6211720058436229987e-1)}, {FN (tan), ARG(6.28284004019658492979e+00,1.0e+00), RES(-1.4500326960287694721e-4, 7.6159419408485704843e-1)}, {FN (tan), ARG(6.28284004019658492979e+00,-1.0e+00), RES(-1.4500326960287694721e-4, -7.6159419408485704843e-1)}, {FN (tan), ARG(-6.28284004019658492979e+00,1.0e+00), RES(1.4500326960287694721e-4, 7.6159419408485704843e-1)}, {FN (tan), ARG(-6.28284004019658492979e+00,-1.0e+00), RES(1.4500326960287694721e-4, -7.6159419408485704843e-1)}, {FN (tan), ARG(6.28284004019658492979e+00,2.0e+00), RES(-2.4393395410456728569e-5, 9.6402758819508310558e-1)}, {FN (tan), ARG(6.28284004019658492979e+00,-2.0e+00), RES(-2.4393395410456728569e-5, -9.6402758819508310558e-1)}, {FN (tan), ARG(-6.28284004019658492979e+00,2.0e+00), RES(2.4393395410456728569e-5, 9.6402758819508310558e-1)}, {FN (tan), ARG(-6.28284004019658492979e+00,-2.0e+00), RES(2.4393395410456728569e-5, -9.6402758819508310558e-1)}, {FN (tan), ARG(6.28353057416258753420e+00,0.0e+00), RES(3.4526699672073518233e-4, 0.0)}, {FN (tan), ARG(-6.28353057416258753420e+00,0.0e+00), RES(-3.4526699672073518233e-4, 0.0)}, {FN (tan), ARG(6.28353057416258753420e+00,1.19209289550781250e-07), RES(3.4526699672073027579e-4, 1.1920930376163652988e-7)}, {FN (tan), ARG(6.28353057416258753420e+00,-1.19209289550781250e-07), RES(3.4526699672073027579e-4, -1.1920930376163652988e-7)}, {FN (tan), ARG(-6.28353057416258753420e+00,1.19209289550781250e-07), RES(-3.4526699672073027579e-4, 1.1920930376163652988e-7)}, {FN (tan), ARG(-6.28353057416258753420e+00,-1.19209289550781250e-07), RES(-3.4526699672073027579e-4, -1.1920930376163652988e-7)}, {FN (tan), ARG(6.28353057416258753420e+00,5.0e-01), RES(2.7153443992641126612e-4, 4.6211720058436229974e-1)}, {FN (tan), ARG(6.28353057416258753420e+00,-5.0e-01), RES(2.7153443992641126612e-4, -4.6211720058436229974e-1)}, {FN (tan), ARG(-6.28353057416258753420e+00,5.0e-01), RES(-2.7153443992641126612e-4, 4.6211720058436229974e-1)}, {FN (tan), ARG(-6.28353057416258753420e+00,-5.0e-01), RES(-2.7153443992641126612e-4, -4.6211720058436229974e-1)}, {FN (tan), ARG(6.28353057416258753420e+00,1.0e+00), RES(1.4500326960267121913e-4, 7.6159419408485704832e-1)}, {FN (tan), ARG(6.28353057416258753420e+00,-1.0e+00), RES(1.4500326960267121913e-4, -7.6159419408485704832e-1)}, {FN (tan), ARG(-6.28353057416258753420e+00,1.0e+00), RES(-1.4500326960267121913e-4, 7.6159419408485704832e-1)}, {FN (tan), ARG(-6.28353057416258753420e+00,-1.0e+00), RES(-1.4500326960267121913e-4, -7.6159419408485704832e-1)}, {FN (tan), ARG(6.28353057416258753420e+00,2.0e+00), RES(2.4393395410422119654e-5, 9.6402758819508310555e-1)}, {FN (tan), ARG(6.28353057416258753420e+00,-2.0e+00), RES(2.4393395410422119654e-5, -9.6402758819508310555e-1)}, {FN (tan), ARG(-6.28353057416258753420e+00,2.0e+00), RES(-2.4393395410422119654e-5, 9.6402758819508310555e-1)}, {FN (tan), ARG(-6.28353057416258753420e+00,-2.0e+00), RES(-2.4393395410422119654e-5, -9.6402758819508310555e-1)}, {FN (tan), ARG(9.42443269378637893396e+00,0.0e+00), RES(-3.4526699672045932728e-4, 0.0)}, {FN (tan), ARG(-9.42443269378637893396e+00,0.0e+00), RES(3.4526699672045932728e-4, 0.0)}, {FN (tan), ARG(9.42443269378637893396e+00,1.19209289550781250e-07), RES(-3.4526699672045442074e-4, 1.1920930376163652985e-7)}, {FN (tan), ARG(9.42443269378637893396e+00,-1.19209289550781250e-07), RES(-3.4526699672045442074e-4, -1.1920930376163652985e-7)}, {FN (tan), ARG(-9.42443269378637893396e+00,1.19209289550781250e-07), RES(3.4526699672045442074e-4, 1.1920930376163652985e-7)}, {FN (tan), ARG(-9.42443269378637893396e+00,-1.19209289550781250e-07), RES(3.4526699672045442074e-4, -1.1920930376163652985e-7)}, {FN (tan), ARG(9.42443269378637893396e+00,5.0e-01), RES(-2.7153443992619432056e-4, 4.6211720058436229968e-1)}, {FN (tan), ARG(9.42443269378637893396e+00,-5.0e-01), RES(-2.7153443992619432056e-4, -4.6211720058436229968e-1)}, {FN (tan), ARG(-9.42443269378637893396e+00,5.0e-01), RES(2.7153443992619432056e-4, 4.6211720058436229968e-1)}, {FN (tan), ARG(-9.42443269378637893396e+00,-5.0e-01), RES(2.7153443992619432056e-4, -4.6211720058436229968e-1)}, {FN (tan), ARG(9.42443269378637893396e+00,1.0e+00), RES(-1.4500326960255536711e-4, 7.6159419408485704826e-1)}, {FN (tan), ARG(9.42443269378637893396e+00,-1.0e+00), RES(-1.4500326960255536711e-4, -7.6159419408485704826e-1)}, {FN (tan), ARG(-9.42443269378637893396e+00,1.0e+00), RES(1.4500326960255536711e-4, 7.6159419408485704826e-1)}, {FN (tan), ARG(-9.42443269378637893396e+00,-1.0e+00), RES(1.4500326960255536711e-4, -7.6159419408485704826e-1)}, {FN (tan), ARG(9.42443269378637893396e+00,2.0e+00), RES(-2.4393395410402630273e-5, 9.6402758819508310554e-1)}, {FN (tan), ARG(9.42443269378637893396e+00,-2.0e+00), RES(-2.4393395410402630273e-5, -9.6402758819508310554e-1)}, {FN (tan), ARG(-9.42443269378637893396e+00,2.0e+00), RES(2.4393395410402630273e-5, 9.6402758819508310554e-1)}, {FN (tan), ARG(-9.42443269378637893396e+00,-2.0e+00), RES(2.4393395410402630273e-5, -9.6402758819508310554e-1)}, {FN (tan), ARG(9.42512322775237976202e+00,0.0e+00), RES(3.4526699671972453911e-4, 0.0)}, {FN (tan), ARG(-9.42512322775237976202e+00,0.0e+00), RES(-3.4526699671972453911e-4, 0.0)}, {FN (tan), ARG(9.42512322775237976202e+00,1.19209289550781250e-07), RES(3.4526699671971963257e-4, 1.1920930376163652979e-7)}, {FN (tan), ARG(9.42512322775237976202e+00,-1.19209289550781250e-07), RES(3.4526699671971963257e-4, -1.1920930376163652979e-7)}, {FN (tan), ARG(-9.42512322775237976202e+00,1.19209289550781250e-07), RES(-3.4526699671971963257e-4, 1.1920930376163652979e-7)}, {FN (tan), ARG(-9.42512322775237976202e+00,-1.19209289550781250e-07), RES(-3.4526699671971963257e-4, -1.1920930376163652979e-7)}, {FN (tan), ARG(9.42512322775237976202e+00,5.0e-01), RES(2.7153443992561644811e-4, 4.6211720058436229949e-1)}, {FN (tan), ARG(9.42512322775237976202e+00,-5.0e-01), RES(2.7153443992561644811e-4, -4.6211720058436229949e-1)}, {FN (tan), ARG(-9.42512322775237976202e+00,5.0e-01), RES(-2.7153443992561644811e-4, 4.6211720058436229949e-1)}, {FN (tan), ARG(-9.42512322775237976202e+00,-5.0e-01), RES(-2.7153443992561644811e-4, -4.6211720058436229949e-1)}, {FN (tan), ARG(9.42512322775237976202e+00,1.0e+00), RES(1.450032696022467750e-4, 7.6159419408485704810e-1)}, {FN (tan), ARG(9.42512322775237976202e+00,-1.0e+00), RES(1.450032696022467750e-4, -7.6159419408485704810e-1)}, {FN (tan), ARG(-9.42512322775237976202e+00,1.0e+00), RES(-1.450032696022467750e-4, 7.6159419408485704810e-1)}, {FN (tan), ARG(-9.42512322775237976202e+00,-1.0e+00), RES(-1.450032696022467750e-4, -7.6159419408485704810e-1)}, {FN (tan), ARG(9.42512322775237976202e+00,2.0e+00), RES(2.439339541035071690e-5, 9.6402758819508310550e-1)}, {FN (tan), ARG(9.42512322775237976202e+00,-2.0e+00), RES(2.439339541035071690e-5, -9.6402758819508310550e-1)}, {FN (tan), ARG(-9.42512322775237976202e+00,2.0e+00), RES(-2.439339541035071690e-5, 9.6402758819508310550e-1)}, {FN (tan), ARG(-9.42512322775237976202e+00,-2.0e+00), RES(-2.439339541035071690e-5, -9.6402758819508310550e-1)}, {FN (arcsin), ARG(0.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arcsin), ARG(0.0e+00,1.19209289550781250e-07), RES(0, 1.1920928955078096766e-7)}, {FN (arcsin), ARG(0.0e+00,-1.19209289550781250e-07), RES(0, -1.1920928955078096766e-7)}, {FN (arcsin), ARG(0.0e+00,5.0e-01), RES(0, 4.8121182505960344750e-1)}, {FN (arcsin), ARG(0.0e+00,-5.0e-01), RES(0, -4.8121182505960344750e-1)}, {FN (arcsin), ARG(0.0e+00,1.0e+00), RES(0, 8.8137358701954302523e-1)}, {FN (arcsin), ARG(0.0e+00,-1.0e+00), RES(0, -8.8137358701954302523e-1)}, {FN (arcsin), ARG(0.0e+00,2.0e+00), RES(0, 1.4436354751788103425e0)}, {FN (arcsin), ARG(0.0e+00,-2.0e+00), RES(0, -1.4436354751788103425e0)}, {FN (arcsin), ARG(0.0e+00,8.3886080e+06), RES(0, 1.6635532333438690979e1)}, {FN (arcsin), ARG(0.0e+00,-8.3886080e+06), RES(0, -1.6635532333438690979e1)}, {FN (arcsin), ARG(1.19209289550781250e-07,0.0e+00), RES(1.1920928955078153234e-7, 0.0)}, {FN (arcsin), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.1920928955078153234e-7, 0.0)}, {FN (arcsin), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.1920928955078068531e-7, 1.1920928955078181469e-7)}, {FN (arcsin), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.1920928955078068531e-7, -1.1920928955078181469e-7)}, {FN (arcsin), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.1920928955078068531e-7, 1.1920928955078181469e-7)}, {FN (arcsin), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.1920928955078068531e-7, -1.1920928955078181469e-7)}, {FN (arcsin), ARG(1.19209289550781250e-07,5.0e-01), RES(1.0662402999400097805e-7, 4.8121182505960598961e-1)}, {FN (arcsin), ARG(1.19209289550781250e-07,-5.0e-01), RES(1.0662402999400097805e-7, -4.8121182505960598961e-1)}, {FN (arcsin), ARG(-1.19209289550781250e-07,5.0e-01), RES(-1.0662402999400097805e-7, 4.8121182505960598961e-1)}, {FN (arcsin), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-1.0662402999400097805e-7, -4.8121182505960598961e-1)}, {FN (arcsin), ARG(1.19209289550781250e-07,1.0e+00), RES(8.4293697021788013662e-8, 8.8137358701954553738e-1)}, {FN (arcsin), ARG(1.19209289550781250e-07,-1.0e+00), RES(8.4293697021788013662e-8, -8.8137358701954553738e-1)}, {FN (arcsin), ARG(-1.19209289550781250e-07,1.0e+00), RES(-8.4293697021788013662e-8, 8.8137358701954553738e-1)}, {FN (arcsin), ARG(-1.19209289550781250e-07,-1.0e+00), RES(-8.4293697021788013662e-8, -8.8137358701954553738e-1)}, {FN (arcsin), ARG(1.19209289550781250e-07,2.0e+00), RES(5.3312014997000413263e-8, 1.4436354751788116136e0)}, {FN (arcsin), ARG(1.19209289550781250e-07,-2.0e+00), RES(5.3312014997000413263e-8, -1.4436354751788116136e0)}, {FN (arcsin), ARG(-1.19209289550781250e-07,2.0e+00), RES(-5.3312014997000413263e-8, 1.4436354751788116136e0)}, {FN (arcsin), ARG(-1.19209289550781250e-07,-2.0e+00), RES(-5.3312014997000413263e-8, -1.4436354751788116136e0)}, {FN (arcsin), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.4210854715201902743e-14, 1.6635532333438690979e1)}, {FN (arcsin), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.4210854715201902743e-14, -1.6635532333438690979e1)}, {FN (arcsin), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(-1.4210854715201902743e-14, 1.6635532333438690979e1)}, {FN (arcsin), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(-1.4210854715201902743e-14, -1.6635532333438690979e1)}, {FN (arcsin), ARG(5.0e-01,0.0e+00), RES(5.2359877559829887308e-1, 0.0)}, {FN (arcsin), ARG(-5.0e-01,0.0e+00), RES(-5.2359877559829887308e-1, 0.0)}, {FN (arcsin), ARG(5.0e-01,1.19209289550781250e-07), RES(5.2359877559829340332e-1, 1.3765103082409432364e-7)}, {FN (arcsin), ARG(5.0e-01,-1.19209289550781250e-07), RES(5.2359877559829340332e-1, -1.3765103082409432364e-7)}, {FN (arcsin), ARG(-5.0e-01,1.19209289550781250e-07), RES(-5.2359877559829340332e-1, 1.3765103082409432364e-7)}, {FN (arcsin), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-5.2359877559829340332e-1, -1.3765103082409432364e-7)}, {FN (arcsin), ARG(5.0e-01,5.0e-01), RES(4.5227844715119068206e-1, 5.3063753095251782602e-1)}, {FN (arcsin), ARG(5.0e-01,-5.0e-01), RES(4.5227844715119068206e-1, -5.3063753095251782602e-1)}, {FN (arcsin), ARG(-5.0e-01,5.0e-01), RES(-4.5227844715119068206e-1, 5.3063753095251782602e-1)}, {FN (arcsin), ARG(-5.0e-01,-5.0e-01), RES(-4.5227844715119068206e-1, -5.3063753095251782602e-1)}, {FN (arcsin), ARG(5.0e-01,1.0e+00), RES(3.4943906285721329363e-1, 9.2613303135018242455e-1)}, {FN (arcsin), ARG(5.0e-01,-1.0e+00), RES(3.4943906285721329363e-1, -9.2613303135018242455e-1)}, {FN (arcsin), ARG(-5.0e-01,1.0e+00), RES(-3.4943906285721329363e-1, 9.2613303135018242455e-1)}, {FN (arcsin), ARG(-5.0e-01,-1.0e+00), RES(-3.4943906285721329363e-1, -9.2613303135018242455e-1)}, {FN (arcsin), ARG(5.0e-01,2.0e+00), RES(2.2101863562288385890e-1, 1.4657153519472905218e0)}, {FN (arcsin), ARG(5.0e-01,-2.0e+00), RES(2.2101863562288385890e-1, -1.4657153519472905218e0)}, {FN (arcsin), ARG(-5.0e-01,2.0e+00), RES(-2.2101863562288385890e-1, 1.4657153519472905218e0)}, {FN (arcsin), ARG(-5.0e-01,-2.0e+00), RES(-2.2101863562288385890e-1, -1.4657153519472905218e0)}, {FN (arcsin), ARG(5.0e-01,8.3886080e+06), RES(5.9604644775390130897e-8, 1.6635532333438692755e1)}, {FN (arcsin), ARG(5.0e-01,-8.3886080e+06), RES(5.9604644775390130897e-8, -1.6635532333438692755e1)}, {FN (arcsin), ARG(-5.0e-01,8.3886080e+06), RES(-5.9604644775390130897e-8, 1.6635532333438692755e1)}, {FN (arcsin), ARG(-5.0e-01,-8.3886080e+06), RES(-5.9604644775390130897e-8, -1.6635532333438692755e1)}, {FN (arcsin), ARG(1.0e+00,0.0e+00), RES(1.5707963267948966192e0, 0.0)}, {FN (arcsin), ARG(-1.0e+00,0.0e+00), RES(-1.5707963267948966192e0, 0.0)}, {FN (arcsin), ARG(1.0e+00,1.19209289550781250e-07), RES(1.5704510598153252947e0, 3.4526698643116312881e-4)}, {FN (arcsin), ARG(1.0e+00,-1.19209289550781250e-07), RES(1.5704510598153252947e0, -3.4526698643116312881e-4)}, {FN (arcsin), ARG(-1.0e+00,1.19209289550781250e-07), RES(-1.5704510598153252947e0, 3.4526698643116312881e-4)}, {FN (arcsin), ARG(-1.0e+00,-1.19209289550781250e-07), RES(-1.5704510598153252947e0, -3.4526698643116312881e-4)}, {FN (arcsin), ARG(1.0e+00,5.0e-01), RES(8.9590748120889023907e-1, 7.3285767597364526089e-1)}, {FN (arcsin), ARG(1.0e+00,-5.0e-01), RES(8.9590748120889023907e-1, -7.3285767597364526089e-1)}, {FN (arcsin), ARG(-1.0e+00,5.0e-01), RES(-8.9590748120889023907e-1, 7.3285767597364526089e-1)}, {FN (arcsin), ARG(-1.0e+00,-5.0e-01), RES(-8.9590748120889023907e-1, -7.3285767597364526089e-1)}, {FN (arcsin), ARG(1.0e+00,1.0e+00), RES(6.6623943249251525510e-1, 1.0612750619050356520e0)}, {FN (arcsin), ARG(1.0e+00,-1.0e+00), RES(6.6623943249251525510e-1, -1.0612750619050356520e0)}, {FN (arcsin), ARG(-1.0e+00,1.0e+00), RES(-6.6623943249251525510e-1, 1.0612750619050356520e0)}, {FN (arcsin), ARG(-1.0e+00,-1.0e+00), RES(-6.6623943249251525510e-1, -1.0612750619050356520e0)}, {FN (arcsin), ARG(1.0e+00,2.0e+00), RES(4.2707858639247612548e-1, 1.5285709194809981613e0)}, {FN (arcsin), ARG(1.0e+00,-2.0e+00), RES(4.2707858639247612548e-1, -1.5285709194809981613e0)}, {FN (arcsin), ARG(-1.0e+00,2.0e+00), RES(-4.2707858639247612548e-1, 1.5285709194809981613e0)}, {FN (arcsin), ARG(-1.0e+00,-2.0e+00), RES(-4.2707858639247612548e-1, -1.5285709194809981613e0)}, {FN (arcsin), ARG(1.0e+00,8.3886080e+06), RES(1.1920928955077983828e-7, 1.6635532333438698084e1)}, {FN (arcsin), ARG(1.0e+00,-8.3886080e+06), RES(1.1920928955077983828e-7, -1.6635532333438698084e1)}, {FN (arcsin), ARG(-1.0e+00,8.3886080e+06), RES(-1.1920928955077983828e-7, 1.6635532333438698084e1)}, {FN (arcsin), ARG(-1.0e+00,-8.3886080e+06), RES(-1.1920928955077983828e-7, -1.6635532333438698084e1)}, {FN (arcsin), ARG(2.0e+00,0.0e+00), RES(1.5707963267948966192e0, -1.3169578969248167086e0)}, {FN (arcsin), ARG(-2.0e+00,0.0e+00), RES(-1.5707963267948966192e0, 1.3169578969248167086e0)}, {FN (arcsin), ARG(2.0e+00,1.19209289550781250e-07), RES(1.5707962579693812072e0, 1.3169578969248194435e0)}, {FN (arcsin), ARG(2.0e+00,-1.19209289550781250e-07), RES(1.5707962579693812072e0, -1.3169578969248194435e0)}, {FN (arcsin), ARG(-2.0e+00,1.19209289550781250e-07), RES(-1.5707962579693812072e0, 1.3169578969248194435e0)}, {FN (arcsin), ARG(-2.0e+00,-1.19209289550781250e-07), RES(-1.5707962579693812072e0, -1.3169578969248194435e0)}, {FN (arcsin), ARG(2.0e+00,5.0e-01), RES(1.2930420702371826591e0, 1.3618009008578457882e0)}, {FN (arcsin), ARG(2.0e+00,-5.0e-01), RES(1.2930420702371826591e0, -1.3618009008578457882e0)}, {FN (arcsin), ARG(-2.0e+00,5.0e-01), RES(-1.2930420702371826591e0, 1.3618009008578457882e0)}, {FN (arcsin), ARG(-2.0e+00,-5.0e-01), RES(-1.2930420702371826591e0, -1.3618009008578457882e0)}, {FN (arcsin), ARG(2.0e+00,1.0e+00), RES(1.0634400235777520562e0, 1.4693517443681852733e0)}, {FN (arcsin), ARG(2.0e+00,-1.0e+00), RES(1.0634400235777520562e0, -1.4693517443681852733e0)}, {FN (arcsin), ARG(-2.0e+00,1.0e+00), RES(-1.0634400235777520562e0, 1.4693517443681852733e0)}, {FN (arcsin), ARG(-2.0e+00,-1.0e+00), RES(-1.0634400235777520562e0, -1.4693517443681852733e0)}, {FN (arcsin), ARG(2.0e+00,2.0e+00), RES(7.5424914469804604071e-1, 1.7343245214879664480e0)}, {FN (arcsin), ARG(2.0e+00,-2.0e+00), RES(7.5424914469804604071e-1, -1.7343245214879664480e0)}, {FN (arcsin), ARG(-2.0e+00,2.0e+00), RES(-7.5424914469804604071e-1, 1.7343245214879664480e0)}, {FN (arcsin), ARG(-2.0e+00,-2.0e+00), RES(-7.5424914469804604071e-1, -1.7343245214879664480e0)}, {FN (arcsin), ARG(2.0e+00,8.3886080e+06), RES(2.3841857910155628843e-7, 1.663553233343871940e1)}, {FN (arcsin), ARG(2.0e+00,-8.3886080e+06), RES(2.3841857910155628843e-7, -1.663553233343871940e1)}, {FN (arcsin), ARG(-2.0e+00,8.3886080e+06), RES(-2.3841857910155628843e-7, 1.663553233343871940e1)}, {FN (arcsin), ARG(-2.0e+00,-8.3886080e+06), RES(-2.3841857910155628843e-7, -1.663553233343871940e1)}, {FN (arcsin), ARG(8.3886080e+06,0.0e+00), RES(1.5707963267948966192e0, -1.6635532333438683873e1)}, {FN (arcsin), ARG(-8.3886080e+06,0.0e+00), RES(-1.5707963267948966192e0, 1.6635532333438683873e1)}, {FN (arcsin), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.5707963267948824084e0, 1.6635532333438683873e1)}, {FN (arcsin), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.5707963267948824084e0, -1.6635532333438683873e1)}, {FN (arcsin), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(-1.5707963267948824084e0, 1.6635532333438683873e1)}, {FN (arcsin), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(-1.5707963267948824084e0, -1.6635532333438683873e1)}, {FN (arcsin), ARG(8.3886080e+06,5.0e-01), RES(1.5707962671902518438e0, 1.6635532333438685650e1)}, {FN (arcsin), ARG(8.3886080e+06,-5.0e-01), RES(1.5707962671902518438e0, -1.6635532333438685650e1)}, {FN (arcsin), ARG(-8.3886080e+06,5.0e-01), RES(-1.5707962671902518438e0, 1.6635532333438685650e1)}, {FN (arcsin), ARG(-8.3886080e+06,-5.0e-01), RES(-1.5707962671902518438e0, -1.6635532333438685650e1)}, {FN (arcsin), ARG(8.3886080e+06,1.0e+00), RES(1.5707962075856070684e0, 1.6635532333438690979e1)}, {FN (arcsin), ARG(8.3886080e+06,-1.0e+00), RES(1.5707962075856070684e0, -1.6635532333438690979e1)}, {FN (arcsin), ARG(-8.3886080e+06,1.0e+00), RES(-1.5707962075856070684e0, 1.6635532333438690979e1)}, {FN (arcsin), ARG(-8.3886080e+06,-1.0e+00), RES(-1.5707962075856070684e0, -1.6635532333438690979e1)}, {FN (arcsin), ARG(8.3886080e+06,2.0e+00), RES(1.5707960883763175177e0, 1.6635532333438712295e1)}, {FN (arcsin), ARG(8.3886080e+06,-2.0e+00), RES(1.5707960883763175177e0, -1.6635532333438712295e1)}, {FN (arcsin), ARG(-8.3886080e+06,2.0e+00), RES(-1.5707960883763175177e0, 1.6635532333438712295e1)}, {FN (arcsin), ARG(-8.3886080e+06,-2.0e+00), RES(-1.5707960883763175177e0, -1.6635532333438712295e1)}, {FN (arcsin), ARG(8.3886080e+06,8.3886080e+06), RES(7.8539816339744653326e-1, 1.6982105923718660081e1)}, {FN (arcsin), ARG(8.3886080e+06,-8.3886080e+06), RES(7.8539816339744653326e-1, -1.6982105923718660081e1)}, {FN (arcsin), ARG(-8.3886080e+06,8.3886080e+06), RES(-7.8539816339744653326e-1, 1.6982105923718660081e1)}, {FN (arcsin), ARG(-8.3886080e+06,-8.3886080e+06), RES(-7.8539816339744653326e-1, -1.6982105923718660081e1)}, {FN (arccos), ARG(0.0e+00,0.0e+00), RES(1.5707963267948966192e0, 0.0)}, {FN (arccos), ARG(0.0e+00,1.19209289550781250e-07), RES(1.5707963267948966192e0, -1.1920928955078096766e-7)}, {FN (arccos), ARG(0.0e+00,-1.19209289550781250e-07), RES(1.5707963267948966192e0, 1.1920928955078096766e-7)}, {FN (arccos), ARG(0.0e+00,5.0e-01), RES(1.5707963267948966192e0, -4.8121182505960344750e-1)}, {FN (arccos), ARG(0.0e+00,-5.0e-01), RES(1.5707963267948966192e0, 4.8121182505960344750e-1)}, {FN (arccos), ARG(0.0e+00,1.0e+00), RES(1.5707963267948966192e0, -8.8137358701954302523e-1)}, {FN (arccos), ARG(0.0e+00,-1.0e+00), RES(1.5707963267948966192e0, 8.8137358701954302523e-1)}, {FN (arccos), ARG(0.0e+00,2.0e+00), RES(1.5707963267948966192e0, -1.4436354751788103425e0)}, {FN (arccos), ARG(0.0e+00,-2.0e+00), RES(1.5707963267948966192e0, 1.4436354751788103425e0)}, {FN (arccos), ARG(0.0e+00,8.3886080e+06), RES(1.5707963267948966192e0, -1.6635532333438690979e1)}, {FN (arccos), ARG(0.0e+00,-8.3886080e+06), RES(1.5707963267948966192e0, 1.6635532333438690979e1)}, {FN (arccos), ARG(1.19209289550781250e-07,0.0e+00), RES(1.5707962075856070684e0, 0.0)}, {FN (arccos), ARG(-1.19209289550781250e-07,0.0e+00), RES(1.570796446004186170e0, 0.0)}, {FN (arccos), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.5707962075856070685e0, -1.1920928955078181469e-7)}, {FN (arccos), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.5707962075856070685e0, 1.1920928955078181469e-7)}, {FN (arccos), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(1.570796446004186170e0, -1.1920928955078181469e-7)}, {FN (arccos), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.570796446004186170e0, 1.1920928955078181469e-7)}, {FN (arccos), ARG(1.19209289550781250e-07,5.0e-01), RES(1.5707962201708666252e0, -4.8121182505960598961e-1)}, {FN (arccos), ARG(1.19209289550781250e-07,-5.0e-01), RES(1.5707962201708666252e0, 4.8121182505960598961e-1)}, {FN (arccos), ARG(-1.19209289550781250e-07,5.0e-01), RES(1.5707964334189266132e0, -4.8121182505960598961e-1)}, {FN (arccos), ARG(-1.19209289550781250e-07,-5.0e-01), RES(1.5707964334189266132e0, 4.8121182505960598961e-1)}, {FN (arccos), ARG(1.19209289550781250e-07,1.0e+00), RES(1.5707962425011995974e0, -8.8137358701954553738e-1)}, {FN (arccos), ARG(1.19209289550781250e-07,-1.0e+00), RES(1.5707962425011995974e0, 8.8137358701954553738e-1)}, {FN (arccos), ARG(-1.19209289550781250e-07,1.0e+00), RES(1.5707964110885936410e0, -8.8137358701954553738e-1)}, {FN (arccos), ARG(-1.19209289550781250e-07,-1.0e+00), RES(1.5707964110885936410e0, 8.8137358701954553738e-1)}, {FN (arccos), ARG(1.19209289550781250e-07,2.0e+00), RES(1.5707962734828816222e0, -1.4436354751788116136e0)}, {FN (arccos), ARG(1.19209289550781250e-07,-2.0e+00), RES(1.5707962734828816222e0, 1.4436354751788116136e0)}, {FN (arccos), ARG(-1.19209289550781250e-07,2.0e+00), RES(1.5707963801069116162e0, -1.4436354751788116136e0)}, {FN (arccos), ARG(-1.19209289550781250e-07,-2.0e+00), RES(1.5707963801069116162e0, 1.4436354751788116136e0)}, {FN (arccos), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.5707963267948824084e0, -1.6635532333438690979e1)}, {FN (arccos), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.5707963267948824084e0, 1.6635532333438690979e1)}, {FN (arccos), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(1.5707963267949108301e0, -1.6635532333438690979e1)}, {FN (arccos), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(1.5707963267949108301e0, 1.6635532333438690979e1)}, {FN (arccos), ARG(5.0e-01,0.0e+00), RES(1.0471975511965977462e0, 0.0)}, {FN (arccos), ARG(-5.0e-01,0.0e+00), RES(2.0943951023931954923e0, 0.0)}, {FN (arccos), ARG(5.0e-01,1.19209289550781250e-07), RES(1.0471975511966032159e0, -1.3765103082409432364e-7)}, {FN (arccos), ARG(5.0e-01,-1.19209289550781250e-07), RES(1.0471975511966032159e0, 1.3765103082409432364e-7)}, {FN (arccos), ARG(-5.0e-01,1.19209289550781250e-07), RES(2.0943951023931900225e0, -1.3765103082409432364e-7)}, {FN (arccos), ARG(-5.0e-01,-1.19209289550781250e-07), RES(2.0943951023931900225e0, 1.3765103082409432364e-7)}, {FN (arccos), ARG(5.0e-01,5.0e-01), RES(1.1185178796437059372e0, -5.3063753095251782602e-1)}, {FN (arccos), ARG(5.0e-01,-5.0e-01), RES(1.1185178796437059372e0, 5.3063753095251782602e-1)}, {FN (arccos), ARG(-5.0e-01,5.0e-01), RES(2.0230747739460873013e0, -5.3063753095251782602e-1)}, {FN (arccos), ARG(-5.0e-01,-5.0e-01), RES(2.0230747739460873013e0, 5.3063753095251782602e-1)}, {FN (arccos), ARG(5.0e-01,1.0e+00), RES(1.2213572639376833256e0, -9.2613303135018242455e-1)}, {FN (arccos), ARG(5.0e-01,-1.0e+00), RES(1.2213572639376833256e0, 9.2613303135018242455e-1)}, {FN (arccos), ARG(-5.0e-01,1.0e+00), RES(1.9202353896521099129e0, -9.2613303135018242455e-1)}, {FN (arccos), ARG(-5.0e-01,-1.0e+00), RES(1.9202353896521099129e0, 9.2613303135018242455e-1)}, {FN (arccos), ARG(5.0e-01,2.0e+00), RES(1.3497776911720127603e0, -1.4657153519472905218e0)}, {FN (arccos), ARG(5.0e-01,-2.0e+00), RES(1.3497776911720127603e0, 1.4657153519472905218e0)}, {FN (arccos), ARG(-5.0e-01,2.0e+00), RES(1.7918149624177804781e0, -1.4657153519472905218e0)}, {FN (arccos), ARG(-5.0e-01,-2.0e+00), RES(1.7918149624177804781e0, 1.4657153519472905218e0)}, {FN (arccos), ARG(5.0e-01,8.3886080e+06), RES(1.5707962671902518438e0, -1.6635532333438692755e1)}, {FN (arccos), ARG(5.0e-01,-8.3886080e+06), RES(1.5707962671902518438e0, 1.6635532333438692755e1)}, {FN (arccos), ARG(-5.0e-01,8.3886080e+06), RES(1.5707963863995413946e0, -1.6635532333438692755e1)}, {FN (arccos), ARG(-5.0e-01,-8.3886080e+06), RES(1.5707963863995413946e0, 1.6635532333438692755e1)}, {FN (arccos), ARG(1.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arccos), ARG(-1.0e+00,0.0e+00), RES(3.1415926535897932385e0, 0.0)}, {FN (arccos), ARG(1.0e+00,1.19209289550781250e-07), RES(3.4526697957132450399e-4, -3.4526698643116312881e-4)}, {FN (arccos), ARG(1.0e+00,-1.19209289550781250e-07), RES(3.4526697957132450399e-4, 3.4526698643116312881e-4)}, {FN (arccos), ARG(-1.0e+00,1.19209289550781250e-07), RES(3.1412473866102219140e0, -3.4526698643116312881e-4)}, {FN (arccos), ARG(-1.0e+00,-1.19209289550781250e-07), RES(3.1412473866102219140e0, 3.4526698643116312881e-4)}, {FN (arccos), ARG(1.0e+00,5.0e-01), RES(6.7488884558600638016e-1, -7.3285767597364526089e-1)}, {FN (arccos), ARG(1.0e+00,-5.0e-01), RES(6.7488884558600638016e-1, 7.3285767597364526089e-1)}, {FN (arccos), ARG(-1.0e+00,5.0e-01), RES(2.4667038080037868583e0, -7.3285767597364526089e-1)}, {FN (arccos), ARG(-1.0e+00,-5.0e-01), RES(2.4667038080037868583e0, 7.3285767597364526089e-1)}, {FN (arccos), ARG(1.0e+00,1.0e+00), RES(9.0455689430238136413e-1, -1.0612750619050356520e0)}, {FN (arccos), ARG(1.0e+00,-1.0e+00), RES(9.0455689430238136413e-1, 1.0612750619050356520e0)}, {FN (arccos), ARG(-1.0e+00,1.0e+00), RES(2.2370357592874118743e0, -1.0612750619050356520e0)}, {FN (arccos), ARG(-1.0e+00,-1.0e+00), RES(2.2370357592874118743e0, 1.0612750619050356520e0)}, {FN (arccos), ARG(1.0e+00,2.0e+00), RES(1.1437177404024204938e0, -1.5285709194809981613e0)}, {FN (arccos), ARG(1.0e+00,-2.0e+00), RES(1.1437177404024204938e0, 1.5285709194809981613e0)}, {FN (arccos), ARG(-1.0e+00,2.0e+00), RES(1.9978749131873727447e0, -1.5285709194809981613e0)}, {FN (arccos), ARG(-1.0e+00,-2.0e+00), RES(1.9978749131873727447e0, 1.5285709194809981613e0)}, {FN (arccos), ARG(1.0e+00,8.3886080e+06), RES(1.5707962075856070685e0, -1.6635532333438698084e1)}, {FN (arccos), ARG(1.0e+00,-8.3886080e+06), RES(1.5707962075856070685e0, 1.6635532333438698084e1)}, {FN (arccos), ARG(-1.0e+00,8.3886080e+06), RES(1.570796446004186170e0, -1.6635532333438698084e1)}, {FN (arccos), ARG(-1.0e+00,-8.3886080e+06), RES(1.570796446004186170e0, 1.6635532333438698084e1)}, {FN (arccos), ARG(2.0e+00,0.0e+00), RES(0, 1.3169578969248167086e0)}, {FN (arccos), ARG(-2.0e+00,0.0e+00), RES(3.1415926535897932385e0, -1.3169578969248167086e0)}, {FN (arccos), ARG(2.0e+00,1.19209289550781250e-07), RES(6.8825515412047433504e-8, -1.3169578969248194435e0)}, {FN (arccos), ARG(2.0e+00,-1.19209289550781250e-07), RES(6.8825515412047433504e-8, 1.3169578969248194435e0)}, {FN (arccos), ARG(-2.0e+00,1.19209289550781250e-07), RES(3.1415925847642778264e0, -1.3169578969248194435e0)}, {FN (arccos), ARG(-2.0e+00,-1.19209289550781250e-07), RES(3.1415925847642778264e0, 1.3169578969248194435e0)}, {FN (arccos), ARG(2.0e+00,5.0e-01), RES(2.7775425655771396018e-1, -1.3618009008578457882e0)}, {FN (arccos), ARG(2.0e+00,-5.0e-01), RES(2.7775425655771396018e-1, 1.3618009008578457882e0)}, {FN (arccos), ARG(-2.0e+00,5.0e-01), RES(2.8638383970320792783e0, -1.3618009008578457882e0)}, {FN (arccos), ARG(-2.0e+00,-5.0e-01), RES(2.8638383970320792783e0, 1.3618009008578457882e0)}, {FN (arccos), ARG(2.0e+00,1.0e+00), RES(5.0735630321714456304e-1, -1.4693517443681852733e0)}, {FN (arccos), ARG(2.0e+00,-1.0e+00), RES(5.0735630321714456304e-1, 1.4693517443681852733e0)}, {FN (arccos), ARG(-2.0e+00,1.0e+00), RES(2.6342363503726486754e0, -1.4693517443681852733e0)}, {FN (arccos), ARG(-2.0e+00,-1.0e+00), RES(2.6342363503726486754e0, 1.4693517443681852733e0)}, {FN (arccos), ARG(2.0e+00,2.0e+00), RES(8.1654718209685057852e-1, -1.7343245214879664480e0)}, {FN (arccos), ARG(2.0e+00,-2.0e+00), RES(8.1654718209685057852e-1, 1.7343245214879664480e0)}, {FN (arccos), ARG(-2.0e+00,2.0e+00), RES(2.3250454714929426599e0, -1.7343245214879664480e0)}, {FN (arccos), ARG(-2.0e+00,-2.0e+00), RES(2.3250454714929426599e0, 1.7343245214879664480e0)}, {FN (arccos), ARG(2.0e+00,8.3886080e+06), RES(1.5707960883763175177e0, -1.663553233343871940e1)}, {FN (arccos), ARG(2.0e+00,-8.3886080e+06), RES(1.5707960883763175177e0, 1.663553233343871940e1)}, {FN (arccos), ARG(-2.0e+00,8.3886080e+06), RES(1.5707965652134757208e0, -1.663553233343871940e1)}, {FN (arccos), ARG(-2.0e+00,-8.3886080e+06), RES(1.5707965652134757208e0, 1.663553233343871940e1)}, {FN (arccos), ARG(8.3886080e+06,0.0e+00), RES(0, 1.6635532333438683873e1)}, {FN (arccos), ARG(-8.3886080e+06,0.0e+00), RES(3.1415926535897932385e0, -1.6635532333438683873e1)}, {FN (arccos), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.4210854715202104692e-14, -1.6635532333438683873e1)}, {FN (arccos), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.4210854715202104692e-14, 1.6635532333438683873e1)}, {FN (arccos), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(3.1415926535897790276e0, -1.6635532333438683873e1)}, {FN (arccos), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(3.1415926535897790276e0, 1.6635532333438683873e1)}, {FN (arccos), ARG(8.3886080e+06,5.0e-01), RES(5.9604644775390977930e-8, -1.6635532333438685650e1)}, {FN (arccos), ARG(8.3886080e+06,-5.0e-01), RES(5.9604644775390977930e-8, 1.6635532333438685650e1)}, {FN (arccos), ARG(-8.3886080e+06,5.0e-01), RES(3.1415925939851484631e0, -1.6635532333438685650e1)}, {FN (arccos), ARG(-8.3886080e+06,-5.0e-01), RES(3.1415925939851484631e0, 1.6635532333438685650e1)}, {FN (arccos), ARG(8.3886080e+06,1.0e+00), RES(1.1920928955078153234e-7, -1.6635532333438690979e1)}, {FN (arccos), ARG(8.3886080e+06,-1.0e+00), RES(1.1920928955078153234e-7, 1.6635532333438690979e1)}, {FN (arccos), ARG(-8.3886080e+06,1.0e+00), RES(3.1415925343805036877e0, -1.6635532333438690979e1)}, {FN (arccos), ARG(-8.3886080e+06,-1.0e+00), RES(3.1415925343805036877e0, 1.6635532333438690979e1)}, {FN (arccos), ARG(8.3886080e+06,2.0e+00), RES(2.3841857910155967656e-7, -1.6635532333438712295e1)}, {FN (arccos), ARG(8.3886080e+06,-2.0e+00), RES(2.3841857910155967656e-7, 1.6635532333438712295e1)}, {FN (arccos), ARG(-8.3886080e+06,2.0e+00), RES(3.1415924151712141369e0, -1.6635532333438712295e1)}, {FN (arccos), ARG(-8.3886080e+06,-2.0e+00), RES(3.1415924151712141369e0, 1.6635532333438712295e1)}, {FN (arccos), ARG(8.3886080e+06,8.3886080e+06), RES(7.8539816339745008597e-1, -1.6982105923718660081e1)}, {FN (arccos), ARG(8.3886080e+06,-8.3886080e+06), RES(7.8539816339745008597e-1, 1.6982105923718660081e1)}, {FN (arccos), ARG(-8.3886080e+06,8.3886080e+06), RES(2.3561944901923431525e0, -1.6982105923718660081e1)}, {FN (arccos), ARG(-8.3886080e+06,-8.3886080e+06), RES(2.3561944901923431525e0, 1.6982105923718660081e1)}, {FN (arctan), ARG(0.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arctan), ARG(0.0e+00,1.19209289550781250e-07), RES(0, 1.1920928955078181469e-7)}, {FN (arctan), ARG(0.0e+00,-1.19209289550781250e-07), RES(0, -1.1920928955078181469e-7)}, {FN (arctan), ARG(0.0e+00,5.0e-01), RES(0, 5.4930614433405484570e-1)}, {FN (arctan), ARG(0.0e+00,-5.0e-01), RES(0, -5.4930614433405484570e-1)}, {FN (arctan), ARG(0.0e+00,2.0e+00), RES(1.5707963267948966192e0, 5.4930614433405484570e-1)}, {FN (arctan), ARG(0.0e+00,-2.0e+00), RES(-1.5707963267948966192e0, -5.4930614433405484570e-1)}, {FN (arctan), ARG(0.0e+00,8.3886080e+06), RES(1.5707963267948966192e0, 1.1920928955078181469e-7)}, {FN (arctan), ARG(0.0e+00,-8.3886080e+06), RES(-1.5707963267948966192e0, -1.1920928955078181469e-7)}, {FN (arctan), ARG(1.19209289550781250e-07,0.0e+00), RES(1.1920928955078068531e-7, 0.0)}, {FN (arctan), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.1920928955078068531e-7, 0.0)}, {FN (arctan), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.1920928955078237938e-7, 1.1920928955078012062e-7)}, {FN (arctan), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.1920928955078237938e-7, -1.1920928955078012062e-7)}, {FN (arctan), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.1920928955078237938e-7, 1.1920928955078012062e-7)}, {FN (arctan), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.1920928955078237938e-7, -1.1920928955078012062e-7)}, {FN (arctan), ARG(1.19209289550781250e-07,5.0e-01), RES(1.5894571940103932425e-7, 5.4930614433404221383e-1)}, {FN (arctan), ARG(1.19209289550781250e-07,-5.0e-01), RES(1.5894571940103932425e-7, -5.4930614433404221383e-1)}, {FN (arctan), ARG(-1.19209289550781250e-07,5.0e-01), RES(-1.5894571940103932425e-7, 5.4930614433404221383e-1)}, {FN (arctan), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-1.5894571940103932425e-7, -5.4930614433404221383e-1)}, {FN (arctan), ARG(1.19209289550781250e-07,1.0e+00), RES(7.8539819319977069731e-1, 8.3177661667193446012e0)}, {FN (arctan), ARG(1.19209289550781250e-07,-1.0e+00), RES(7.8539819319977069731e-1, -8.3177661667193446012e0)}, {FN (arctan), ARG(-1.19209289550781250e-07,1.0e+00), RES(-7.8539819319977069731e-1, 8.3177661667193446012e0)}, {FN (arctan), ARG(-1.19209289550781250e-07,-1.0e+00), RES(-7.8539819319977069731e-1, -8.3177661667193446012e0)}, {FN (arctan), ARG(1.19209289550781250e-07,2.0e+00), RES(1.5707962870584667690e0, 5.4930614433405168773e-1)}, {FN (arctan), ARG(1.19209289550781250e-07,-2.0e+00), RES(1.5707962870584667690e0, -5.4930614433405168773e-1)}, {FN (arctan), ARG(-1.19209289550781250e-07,2.0e+00), RES(-1.5707962870584667690e0, 5.4930614433405168773e-1)}, {FN (arctan), ARG(-1.19209289550781250e-07,-2.0e+00), RES(-1.5707962870584667690e0, -5.4930614433405168773e-1)}, {FN (arctan), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.5707963267948966192e0, 1.1920928955078181469e-7)}, {FN (arctan), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.5707963267948966192e0, -1.1920928955078181469e-7)}, {FN (arctan), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(-1.5707963267948966192e0, 1.1920928955078181469e-7)}, {FN (arctan), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(-1.5707963267948966192e0, -1.1920928955078181469e-7)}, {FN (arctan), ARG(5.0e-01,0.0e+00), RES(4.6364760900080611621e-1, 0.0)}, {FN (arctan), ARG(-5.0e-01,0.0e+00), RES(-4.6364760900080611621e-1, 0.0)}, {FN (arctan), ARG(5.0e-01,1.19209289550781250e-07), RES(4.6364760900081066369e-1, 9.5367431640625072280e-8)}, {FN (arctan), ARG(5.0e-01,-1.19209289550781250e-07), RES(4.6364760900081066369e-1, -9.5367431640625072280e-8)}, {FN (arctan), ARG(-5.0e-01,1.19209289550781250e-07), RES(-4.6364760900081066369e-1, 9.5367431640625072280e-8)}, {FN (arctan), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-4.6364760900081066369e-1, -9.5367431640625072280e-8)}, {FN (arctan), ARG(5.0e-01,5.0e-01), RES(5.5357435889704525151e-1, 4.0235947810852509365e-1)}, {FN (arctan), ARG(5.0e-01,-5.0e-01), RES(5.5357435889704525151e-1, -4.0235947810852509365e-1)}, {FN (arctan), ARG(-5.0e-01,5.0e-01), RES(-5.5357435889704525151e-1, 4.0235947810852509365e-1)}, {FN (arctan), ARG(-5.0e-01,-5.0e-01), RES(-5.5357435889704525151e-1, -4.0235947810852509365e-1)}, {FN (arctan), ARG(5.0e-01,1.0e+00), RES(9.0788749496088038670e-1, 7.0830333601405402006e-1)}, {FN (arctan), ARG(5.0e-01,-1.0e+00), RES(9.0788749496088038670e-1, -7.0830333601405402006e-1)}, {FN (arctan), ARG(-5.0e-01,1.0e+00), RES(-9.0788749496088038670e-1, 7.0830333601405402006e-1)}, {FN (arctan), ARG(-5.0e-01,-1.0e+00), RES(-9.0788749496088038670e-1, -7.0830333601405402006e-1)}, {FN (arctan), ARG(5.0e-01,2.0e+00), RES(1.4215468610018069803e0, 5.0037000005253101744e-1)}, {FN (arctan), ARG(5.0e-01,-2.0e+00), RES(1.4215468610018069803e0, -5.0037000005253101744e-1)}, {FN (arctan), ARG(-5.0e-01,2.0e+00), RES(-1.4215468610018069803e0, 5.0037000005253101744e-1)}, {FN (arctan), ARG(-5.0e-01,-2.0e+00), RES(-1.4215468610018069803e0, -5.0037000005253101744e-1)}, {FN (arctan), ARG(5.0e-01,8.3886080e+06), RES(1.5707963267948895138e0, 1.1920928955078139117e-7)}, {FN (arctan), ARG(5.0e-01,-8.3886080e+06), RES(1.5707963267948895138e0, -1.1920928955078139117e-7)}, {FN (arctan), ARG(-5.0e-01,8.3886080e+06), RES(-1.5707963267948895138e0, 1.1920928955078139117e-7)}, {FN (arctan), ARG(-5.0e-01,-8.3886080e+06), RES(-1.5707963267948895138e0, -1.1920928955078139117e-7)}, {FN (arctan), ARG(1.0e+00,0.0e+00), RES(7.8539816339744830962e-1, 0.0)}, {FN (arctan), ARG(-1.0e+00,0.0e+00), RES(-7.8539816339744830962e-1, 0.0)}, {FN (arctan), ARG(1.0e+00,1.19209289550781250e-07), RES(7.8539816339745186233e-1, 5.9604644775390483828e-8)}, {FN (arctan), ARG(1.0e+00,-1.19209289550781250e-07), RES(7.8539816339745186233e-1, -5.9604644775390483828e-8)}, {FN (arctan), ARG(-1.0e+00,1.19209289550781250e-07), RES(-7.8539816339745186233e-1, 5.9604644775390483828e-8)}, {FN (arctan), ARG(-1.0e+00,-1.19209289550781250e-07), RES(-7.8539816339745186233e-1, -5.9604644775390483828e-8)}, {FN (arctan), ARG(1.0e+00,5.0e-01), RES(8.4757566067082902713e-1, 2.3887786125685909036e-1)}, {FN (arctan), ARG(1.0e+00,-5.0e-01), RES(8.4757566067082902713e-1, -2.3887786125685909036e-1)}, {FN (arctan), ARG(-1.0e+00,5.0e-01), RES(-8.4757566067082902713e-1, 2.3887786125685909036e-1)}, {FN (arctan), ARG(-1.0e+00,-5.0e-01), RES(-8.4757566067082902713e-1, -2.3887786125685909036e-1)}, {FN (arctan), ARG(1.0e+00,1.0e+00), RES(1.0172219678978513677e0, 4.0235947810852509365e-1)}, {FN (arctan), ARG(1.0e+00,-1.0e+00), RES(1.0172219678978513677e0, -4.0235947810852509365e-1)}, {FN (arctan), ARG(-1.0e+00,1.0e+00), RES(-1.0172219678978513677e0, 4.0235947810852509365e-1)}, {FN (arctan), ARG(-1.0e+00,-1.0e+00), RES(-1.0172219678978513677e0, -4.0235947810852509365e-1)}, {FN (arctan), ARG(1.0e+00,2.0e+00), RES(1.3389725222944935611e0, 4.0235947810852509365e-1)}, {FN (arctan), ARG(1.0e+00,-2.0e+00), RES(1.3389725222944935611e0, -4.0235947810852509365e-1)}, {FN (arctan), ARG(-1.0e+00,2.0e+00), RES(-1.3389725222944935611e0, 4.0235947810852509365e-1)}, {FN (arctan), ARG(-1.0e+00,-2.0e+00), RES(-1.3389725222944935611e0, -4.0235947810852509365e-1)}, {FN (arctan), ARG(1.0e+00,8.3886080e+06), RES(1.5707963267948824084e0, 1.1920928955078012062e-7)}, {FN (arctan), ARG(1.0e+00,-8.3886080e+06), RES(1.5707963267948824084e0, -1.1920928955078012062e-7)}, {FN (arctan), ARG(-1.0e+00,8.3886080e+06), RES(-1.5707963267948824084e0, 1.1920928955078012062e-7)}, {FN (arctan), ARG(-1.0e+00,-8.3886080e+06), RES(-1.5707963267948824084e0, -1.1920928955078012062e-7)}, {FN (arctan), ARG(2.0e+00,0.0e+00), RES(1.1071487177940905030e0, 0.0)}, {FN (arctan), ARG(-2.0e+00,0.0e+00), RES(-1.1071487177940905030e0, 0.0)}, {FN (arctan), ARG(2.0e+00,1.19209289550781250e-07), RES(1.1071487177940916399e0, 2.3841857910156200307e-8)}, {FN (arctan), ARG(2.0e+00,-1.19209289550781250e-07), RES(1.1071487177940916399e0, -2.3841857910156200307e-8)}, {FN (arctan), ARG(-2.0e+00,1.19209289550781250e-07), RES(-1.1071487177940916399e0, 2.3841857910156200307e-8)}, {FN (arctan), ARG(-2.0e+00,-1.19209289550781250e-07), RES(-1.1071487177940916399e0, -2.3841857910156200307e-8)}, {FN (arctan), ARG(2.0e+00,5.0e-01), RES(1.1265564408348223487e0, 9.6415620202996167238e-2)}, {FN (arctan), ARG(2.0e+00,-5.0e-01), RES(1.1265564408348223487e0, -9.6415620202996167238e-2)}, {FN (arctan), ARG(-2.0e+00,5.0e-01), RES(-1.1265564408348223487e0, 9.6415620202996167238e-2)}, {FN (arctan), ARG(-2.0e+00,-5.0e-01), RES(-1.1265564408348223487e0, -9.6415620202996167238e-2)}, {FN (arctan), ARG(2.0e+00,1.0e+00), RES(1.1780972450961724644e0, 1.7328679513998632735e-1)}, {FN (arctan), ARG(2.0e+00,-1.0e+00), RES(1.1780972450961724644e0, -1.7328679513998632735e-1)}, {FN (arctan), ARG(-2.0e+00,1.0e+00), RES(-1.1780972450961724644e0, 1.7328679513998632735e-1)}, {FN (arctan), ARG(-2.0e+00,-1.0e+00), RES(-1.1780972450961724644e0, -1.7328679513998632735e-1)}, {FN (arctan), ARG(2.0e+00,2.0e+00), RES(1.3112232696716351433e0, 2.3887786125685909036e-1)}, {FN (arctan), ARG(2.0e+00,-2.0e+00), RES(1.3112232696716351433e0, -2.3887786125685909036e-1)}, {FN (arctan), ARG(-2.0e+00,2.0e+00), RES(-1.3112232696716351433e0, 2.3887786125685909036e-1)}, {FN (arctan), ARG(-2.0e+00,-2.0e+00), RES(-1.3112232696716351433e0, -2.3887786125685909036e-1)}, {FN (arctan), ARG(2.0e+00,8.3886080e+06), RES(1.5707963267948681975e0, 1.1920928955077503843e-7)}, {FN (arctan), ARG(2.0e+00,-8.3886080e+06), RES(1.5707963267948681975e0, -1.1920928955077503843e-7)}, {FN (arctan), ARG(-2.0e+00,8.3886080e+06), RES(-1.5707963267948681975e0, 1.1920928955077503843e-7)}, {FN (arctan), ARG(-2.0e+00,-8.3886080e+06), RES(-1.5707963267948681975e0, -1.1920928955077503843e-7)}, {FN (arctan), ARG(8.3886080e+06,0.0e+00), RES(1.5707962075856070685e0, 0.0)}, {FN (arctan), ARG(-8.3886080e+06,0.0e+00), RES(-1.5707962075856070685e0, 0.0)}, {FN (arctan), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.5707962075856070685e0, 1.6940658945085766040e-21)}, {FN (arctan), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.5707962075856070685e0, -1.6940658945085766040e-21)}, {FN (arctan), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(-1.5707962075856070685e0, 1.6940658945085766040e-21)}, {FN (arctan), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(-1.5707962075856070685e0, -1.6940658945085766040e-21)}, {FN (arctan), ARG(8.3886080e+06,5.0e-01), RES(1.5707962075856070685e0, 7.1054273576008756410e-15)}, {FN (arctan), ARG(8.3886080e+06,-5.0e-01), RES(1.5707962075856070685e0, -7.1054273576008756410e-15)}, {FN (arctan), ARG(-8.3886080e+06,5.0e-01), RES(-1.5707962075856070685e0, 7.1054273576008756410e-15)}, {FN (arctan), ARG(-8.3886080e+06,-5.0e-01), RES(-1.5707962075856070685e0, -7.1054273576008756410e-15)}, {FN (arctan), ARG(8.3886080e+06,1.0e+00), RES(1.5707962075856070685e0, 1.4210854715201599821e-14)}, {FN (arctan), ARG(8.3886080e+06,-1.0e+00), RES(1.5707962075856070685e0, -1.4210854715201599821e-14)}, {FN (arctan), ARG(-8.3886080e+06,1.0e+00), RES(-1.5707962075856070685e0, 1.4210854715201599821e-14)}, {FN (arctan), ARG(-8.3886080e+06,-1.0e+00), RES(-1.5707962075856070685e0, -1.4210854715201599821e-14)}, {FN (arctan), ARG(8.3886080e+06,2.0e+00), RES(1.5707962075856070685e0, 2.8421709430401987951e-14)}, {FN (arctan), ARG(8.3886080e+06,-2.0e+00), RES(1.5707962075856070685e0, -2.8421709430401987951e-14)}, {FN (arctan), ARG(-8.3886080e+06,2.0e+00), RES(-1.5707962075856070685e0, 2.8421709430401987951e-14)}, {FN (arctan), ARG(-8.3886080e+06,-2.0e+00), RES(-1.5707962075856070685e0, -2.8421709430401987951e-14)}, {FN (arctan), ARG(8.3886080e+06,8.3886080e+06), RES(1.5707962671902518438e0, 5.9604644775390483828e-8)}, {FN (arctan), ARG(8.3886080e+06,-8.3886080e+06), RES(1.5707962671902518438e0, -5.9604644775390483828e-8)}, {FN (arctan), ARG(-8.3886080e+06,8.3886080e+06), RES(-1.5707962671902518438e0, 5.9604644775390483828e-8)}, {FN (arctan), ARG(-8.3886080e+06,-8.3886080e+06), RES(-1.5707962671902518438e0, -5.9604644775390483828e-8)}, {FN (sinh), ARG(0.0e+00,-3.45266983001243932001e-04), RES(0, -3.4526697614140534807e-4)}, {FN (sinh), ARG(0.0e+00,3.45266983001243932001e-04), RES(0, 3.4526697614140534807e-4)}, {FN (sinh), ARG(0.0e+00,1.57045105981189525579e+00), RES(0, 9.9999994039535581669e-1)}, {FN (sinh), ARG(0.0e+00,-1.57045105981189525579e+00), RES(0, -9.9999994039535581669e-1)}, {FN (sinh), ARG(0.0e+00,1.57114159377789786021e+00), RES(0, 9.9999994039535581673e-1)}, {FN (sinh), ARG(0.0e+00,-1.57114159377789786021e+00), RES(0, -9.9999994039535581673e-1)}, {FN (sinh), ARG(0.0e+00,3.14124738660679181379e+00), RES(0, 3.4526697614158608860e-4)}, {FN (sinh), ARG(0.0e+00,-3.14124738660679181379e+00), RES(0, -3.4526697614158608860e-4)}, {FN (sinh), ARG(0.0e+00,3.14193792057279441821e+00), RES(0, -3.4526697614134115926e-4)}, {FN (sinh), ARG(0.0e+00,-3.14193792057279441821e+00), RES(0, 3.4526697614134115926e-4)}, {FN (sinh), ARG(0.0e+00,4.71204371340168837179e+00), RES(0, -9.9999994039535581664e-1)}, {FN (sinh), ARG(0.0e+00,-4.71204371340168837179e+00), RES(0, 9.9999994039535581664e-1)}, {FN (sinh), ARG(0.0e+00,4.71273424736769097620e+00), RES(0, -9.9999994039535581677e-1)}, {FN (sinh), ARG(0.0e+00,-4.71273424736769097620e+00), RES(0, 9.9999994039535581677e-1)}, {FN (sinh), ARG(0.0e+00,6.28284004019658492979e+00), RES(0, -3.4526697614170855328e-4)}, {FN (sinh), ARG(0.0e+00,-6.28284004019658492979e+00), RES(0, 3.4526697614170855328e-4)}, {FN (sinh), ARG(0.0e+00,6.28353057416258753420e+00), RES(0, 3.4526697614121869459e-4)}, {FN (sinh), ARG(0.0e+00,-6.28353057416258753420e+00), RES(0, -3.4526697614121869459e-4)}, {FN (sinh), ARG(0.0e+00,9.42443269378637893396e+00), RES(0, 3.4526697614094283958e-4)}, {FN (sinh), ARG(0.0e+00,-9.42443269378637893396e+00), RES(0, -3.4526697614094283958e-4)}, {FN (sinh), ARG(0.0e+00,9.42512322775237976202e+00), RES(0, -3.4526697614020805155e-4)}, {FN (sinh), ARG(0.0e+00,-9.42512322775237976202e+00), RES(0, 3.4526697614020805155e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,-3.45266983001243932001e-04), RES(1.1920928244535424533e-7, -3.4526697614140780134e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,3.45266983001243932001e-04), RES(1.1920928244535424533e-7, 3.4526697614140780134e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,-3.45266983001243932001e-04), RES(-1.1920928244535424533e-7, -3.4526697614140780134e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,3.45266983001243932001e-04), RES(-1.1920928244535424533e-7, 3.4526697614140780134e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,1.57045105981189525579e+00), RES(4.1159030931177815679e-11, 9.9999994039536292211e-1)}, {FN (sinh), ARG(1.19209289550781250e-07,-1.57045105981189525579e+00), RES(4.1159030931177815679e-11, -9.9999994039536292211e-1)}, {FN (sinh), ARG(-1.19209289550781250e-07,1.57045105981189525579e+00), RES(-4.1159030931177815679e-11, 9.9999994039536292211e-1)}, {FN (sinh), ARG(-1.19209289550781250e-07,-1.57045105981189525579e+00), RES(-4.1159030931177815679e-11, -9.9999994039536292211e-1)}, {FN (sinh), ARG(1.19209289550781250e-07,1.57114159377789786021e+00), RES(-4.1159030931163216752e-11, 9.9999994039536292216e-1)}, {FN (sinh), ARG(1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-4.1159030931163216752e-11, -9.9999994039536292216e-1)}, {FN (sinh), ARG(-1.19209289550781250e-07,1.57114159377789786021e+00), RES(4.1159030931163216752e-11, 9.9999994039536292216e-1)}, {FN (sinh), ARG(-1.19209289550781250e-07,-1.57114159377789786021e+00), RES(4.1159030931163216752e-11, -9.9999994039536292216e-1)}, {FN (sinh), ARG(1.19209289550781250e-07,3.14124738660679181379e+00), RES(-1.1920928244535424532e-7, 3.4526697614158854187e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-1.1920928244535424532e-7, -3.4526697614158854187e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,3.14124738660679181379e+00), RES(1.1920928244535424532e-7, 3.4526697614158854187e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,-3.14124738660679181379e+00), RES(1.1920928244535424532e-7, -3.4526697614158854187e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,3.14193792057279441821e+00), RES(-1.1920928244535424533e-7, -3.4526697614134361253e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-1.1920928244535424533e-7, 3.4526697614134361253e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,3.14193792057279441821e+00), RES(1.1920928244535424533e-7, -3.4526697614134361253e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,-3.14193792057279441821e+00), RES(1.1920928244535424533e-7, 3.4526697614134361253e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,4.71204371340168837179e+00), RES(-4.1159030931192414605e-11, -9.9999994039536292207e-1)}, {FN (sinh), ARG(1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-4.1159030931192414605e-11, 9.9999994039536292207e-1)}, {FN (sinh), ARG(-1.19209289550781250e-07,4.71204371340168837179e+00), RES(4.1159030931192414605e-11, -9.9999994039536292207e-1)}, {FN (sinh), ARG(-1.19209289550781250e-07,-4.71204371340168837179e+00), RES(4.1159030931192414605e-11, 9.9999994039536292207e-1)}, {FN (sinh), ARG(1.19209289550781250e-07,4.71273424736769097620e+00), RES(4.1159030931148617825e-11, -9.9999994039536292220e-1)}, {FN (sinh), ARG(1.19209289550781250e-07,-4.71273424736769097620e+00), RES(4.1159030931148617825e-11, 9.9999994039536292220e-1)}, {FN (sinh), ARG(-1.19209289550781250e-07,4.71273424736769097620e+00), RES(-4.1159030931148617825e-11, -9.9999994039536292220e-1)}, {FN (sinh), ARG(-1.19209289550781250e-07,-4.71273424736769097620e+00), RES(-4.1159030931148617825e-11, 9.9999994039536292220e-1)}, {FN (sinh), ARG(1.19209289550781250e-07,6.28284004019658492979e+00), RES(1.1920928244535424532e-7, -3.4526697614171100655e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,-6.28284004019658492979e+00), RES(1.1920928244535424532e-7, 3.4526697614171100655e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,6.28284004019658492979e+00), RES(-1.1920928244535424532e-7, -3.4526697614171100655e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,-6.28284004019658492979e+00), RES(-1.1920928244535424532e-7, 3.4526697614171100655e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,6.28353057416258753420e+00), RES(1.1920928244535424534e-7, 3.4526697614122114786e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,-6.28353057416258753420e+00), RES(1.1920928244535424534e-7, -3.4526697614122114786e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,6.28353057416258753420e+00), RES(-1.1920928244535424534e-7, 3.4526697614122114786e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,-6.28353057416258753420e+00), RES(-1.1920928244535424534e-7, -3.4526697614122114786e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,9.42443269378637893396e+00), RES(-1.1920928244535424535e-7, 3.4526697614094529285e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-1.1920928244535424535e-7, -3.4526697614094529285e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,9.42443269378637893396e+00), RES(1.1920928244535424535e-7, 3.4526697614094529285e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,-9.42443269378637893396e+00), RES(1.1920928244535424535e-7, -3.4526697614094529285e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,9.42512322775237976202e+00), RES(-1.1920928244535424538e-7, -3.4526697614021050482e-4)}, {FN (sinh), ARG(1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-1.1920928244535424538e-7, 3.4526697614021050482e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,9.42512322775237976202e+00), RES(1.1920928244535424538e-7, -3.4526697614021050482e-4)}, {FN (sinh), ARG(-1.19209289550781250e-07,-9.42512322775237976202e+00), RES(1.1920928244535424538e-7, 3.4526697614021050482e-4)}, {FN (sinh), ARG(5.0e-01,-3.45266983001243932001e-04), RES(5.2109527443404709209e-1, -3.8933200722534065172e-4)}, {FN (sinh), ARG(5.0e-01,3.45266983001243932001e-04), RES(5.2109527443404709209e-1, 3.8933200722534065172e-4)}, {FN (sinh), ARG(-5.0e-01,-3.45266983001243932001e-04), RES(-5.2109527443404709209e-1, -3.8933200722534065172e-4)}, {FN (sinh), ARG(-5.0e-01,3.45266983001243932001e-04), RES(-5.2109527443404709209e-1, 3.8933200722534065172e-4)}, {FN (sinh), ARG(5.0e-01,1.57045105981189525579e+00), RES(1.7991700040937027667e-4, 1.1276258979946363572e0)}, {FN (sinh), ARG(5.0e-01,-1.57045105981189525579e+00), RES(1.7991700040937027667e-4, -1.1276258979946363572e0)}, {FN (sinh), ARG(-5.0e-01,1.57045105981189525579e+00), RES(-1.7991700040937027667e-4, 1.1276258979946363572e0)}, {FN (sinh), ARG(-5.0e-01,-1.57045105981189525579e+00), RES(-1.7991700040937027667e-4, -1.1276258979946363572e0)}, {FN (sinh), ARG(5.0e-01,1.57114159377789786021e+00), RES(-1.7991700040930646090e-4, 1.1276258979946363573e0)}, {FN (sinh), ARG(5.0e-01,-1.57114159377789786021e+00), RES(-1.7991700040930646090e-4, -1.1276258979946363573e0)}, {FN (sinh), ARG(-5.0e-01,1.57114159377789786021e+00), RES(1.7991700040930646090e-4, 1.1276258979946363573e0)}, {FN (sinh), ARG(-5.0e-01,-1.57114159377789786021e+00), RES(1.7991700040930646090e-4, -1.1276258979946363573e0)}, {FN (sinh), ARG(5.0e-01,3.14124738660679181379e+00), RES(-5.2109527443404709206e-1, 3.8933200722554445944e-4)}, {FN (sinh), ARG(5.0e-01,-3.14124738660679181379e+00), RES(-5.2109527443404709206e-1, -3.8933200722554445944e-4)}, {FN (sinh), ARG(-5.0e-01,3.14124738660679181379e+00), RES(5.2109527443404709206e-1, 3.8933200722554445944e-4)}, {FN (sinh), ARG(-5.0e-01,-3.14124738660679181379e+00), RES(5.2109527443404709206e-1, -3.8933200722554445944e-4)}, {FN (sinh), ARG(5.0e-01,3.14193792057279441821e+00), RES(-5.2109527443404709211e-1, -3.8933200722526827075e-4)}, {FN (sinh), ARG(5.0e-01,-3.14193792057279441821e+00), RES(-5.2109527443404709211e-1, 3.8933200722526827075e-4)}, {FN (sinh), ARG(-5.0e-01,3.14193792057279441821e+00), RES(5.2109527443404709211e-1, -3.8933200722526827075e-4)}, {FN (sinh), ARG(-5.0e-01,-3.14193792057279441821e+00), RES(5.2109527443404709211e-1, 3.8933200722526827075e-4)}, {FN (sinh), ARG(5.0e-01,4.71204371340168837179e+00), RES(-1.7991700040943409243e-4, -1.1276258979946363572e0)}, {FN (sinh), ARG(5.0e-01,-4.71204371340168837179e+00), RES(-1.7991700040943409243e-4, 1.1276258979946363572e0)}, {FN (sinh), ARG(-5.0e-01,4.71204371340168837179e+00), RES(1.7991700040943409243e-4, -1.1276258979946363572e0)}, {FN (sinh), ARG(-5.0e-01,-4.71204371340168837179e+00), RES(1.7991700040943409243e-4, 1.1276258979946363572e0)}, {FN (sinh), ARG(5.0e-01,4.71273424736769097620e+00), RES(1.7991700040924264514e-4, -1.1276258979946363573e0)}, {FN (sinh), ARG(5.0e-01,-4.71273424736769097620e+00), RES(1.7991700040924264514e-4, 1.1276258979946363573e0)}, {FN (sinh), ARG(-5.0e-01,4.71273424736769097620e+00), RES(-1.7991700040924264514e-4, -1.1276258979946363573e0)}, {FN (sinh), ARG(-5.0e-01,-4.71273424736769097620e+00), RES(-1.7991700040924264514e-4, 1.1276258979946363573e0)}, {FN (sinh), ARG(5.0e-01,6.28284004019658492979e+00), RES(5.2109527443404709204e-1, -3.8933200722568255379e-4)}, {FN (sinh), ARG(5.0e-01,-6.28284004019658492979e+00), RES(5.2109527443404709204e-1, 3.8933200722568255379e-4)}, {FN (sinh), ARG(-5.0e-01,6.28284004019658492979e+00), RES(-5.2109527443404709204e-1, -3.8933200722568255379e-4)}, {FN (sinh), ARG(-5.0e-01,-6.28284004019658492979e+00), RES(-5.2109527443404709204e-1, 3.8933200722568255379e-4)}, {FN (sinh), ARG(5.0e-01,6.28353057416258753420e+00), RES(5.2109527443404709213e-1, 3.8933200722513017641e-4)}, {FN (sinh), ARG(5.0e-01,-6.28353057416258753420e+00), RES(5.2109527443404709213e-1, -3.8933200722513017641e-4)}, {FN (sinh), ARG(-5.0e-01,6.28353057416258753420e+00), RES(-5.2109527443404709213e-1, 3.8933200722513017641e-4)}, {FN (sinh), ARG(-5.0e-01,-6.28353057416258753420e+00), RES(-5.2109527443404709213e-1, -3.8933200722513017641e-4)}, {FN (sinh), ARG(5.0e-01,9.42443269378637893396e+00), RES(-5.2109527443404709218e-1, 3.8933200722481911514e-4)}, {FN (sinh), ARG(5.0e-01,-9.42443269378637893396e+00), RES(-5.2109527443404709218e-1, -3.8933200722481911514e-4)}, {FN (sinh), ARG(-5.0e-01,9.42443269378637893396e+00), RES(5.2109527443404709218e-1, 3.8933200722481911514e-4)}, {FN (sinh), ARG(-5.0e-01,-9.42443269378637893396e+00), RES(5.2109527443404709218e-1, -3.8933200722481911514e-4)}, {FN (sinh), ARG(5.0e-01,9.42512322775237976202e+00), RES(-5.2109527443404709231e-1, -3.8933200722399054908e-4)}, {FN (sinh), ARG(5.0e-01,-9.42512322775237976202e+00), RES(-5.2109527443404709231e-1, 3.8933200722399054908e-4)}, {FN (sinh), ARG(-5.0e-01,9.42512322775237976202e+00), RES(5.2109527443404709231e-1, -3.8933200722399054908e-4)}, {FN (sinh), ARG(-5.0e-01,-9.42512322775237976202e+00), RES(5.2109527443404709231e-1, 3.8933200722399054908e-4)}, {FN (sinh), ARG(1.0e+00,-3.45266983001243932001e-04), RES(1.1752011235963524660e0, -5.3277478472501939236e-4)}, {FN (sinh), ARG(1.0e+00,3.45266983001243932001e-04), RES(1.1752011235963524660e0, 5.3277478472501939236e-4)}, {FN (sinh), ARG(-1.0e+00,-3.45266983001243932001e-04), RES(-1.1752011235963524660e0, -5.3277478472501939236e-4)}, {FN (sinh), ARG(-1.0e+00,3.45266983001243932001e-04), RES(-1.1752011235963524660e0, 5.3277478472501939236e-4)}, {FN (sinh), ARG(1.0e+00,1.57045105981189525579e+00), RES(4.0575816248730593018e-4, 1.5430805428404715942e0)}, {FN (sinh), ARG(1.0e+00,-1.57045105981189525579e+00), RES(4.0575816248730593018e-4, -1.5430805428404715942e0)}, {FN (sinh), ARG(-1.0e+00,1.57045105981189525579e+00), RES(-4.0575816248730593018e-4, 1.5430805428404715942e0)}, {FN (sinh), ARG(-1.0e+00,-1.57045105981189525579e+00), RES(-4.0575816248730593018e-4, -1.5430805428404715942e0)}, {FN (sinh), ARG(1.0e+00,1.57114159377789786021e+00), RES(-4.0575816248716200955e-4, 1.5430805428404715942e0)}, {FN (sinh), ARG(1.0e+00,-1.57114159377789786021e+00), RES(-4.0575816248716200955e-4, -1.5430805428404715942e0)}, {FN (sinh), ARG(-1.0e+00,1.57114159377789786021e+00), RES(4.0575816248716200955e-4, 1.5430805428404715942e0)}, {FN (sinh), ARG(-1.0e+00,-1.57114159377789786021e+00), RES(4.0575816248716200955e-4, -1.5430805428404715942e0)}, {FN (sinh), ARG(1.0e+00,3.14124738660679181379e+00), RES(-1.1752011235963524659e0, 5.3277478472529828958e-4)}, {FN (sinh), ARG(1.0e+00,-3.14124738660679181379e+00), RES(-1.1752011235963524659e0, -5.3277478472529828958e-4)}, {FN (sinh), ARG(-1.0e+00,3.14124738660679181379e+00), RES(1.1752011235963524659e0, 5.3277478472529828958e-4)}, {FN (sinh), ARG(-1.0e+00,-3.14124738660679181379e+00), RES(1.1752011235963524659e0, -5.3277478472529828958e-4)}, {FN (sinh), ARG(1.0e+00,3.14193792057279441821e+00), RES(-1.1752011235963524660e0, -5.3277478472492034385e-4)}, {FN (sinh), ARG(1.0e+00,-3.14193792057279441821e+00), RES(-1.1752011235963524660e0, 5.3277478472492034385e-4)}, {FN (sinh), ARG(-1.0e+00,3.14193792057279441821e+00), RES(1.1752011235963524660e0, -5.3277478472492034385e-4)}, {FN (sinh), ARG(-1.0e+00,-3.14193792057279441821e+00), RES(1.1752011235963524660e0, 5.3277478472492034385e-4)}, {FN (sinh), ARG(1.0e+00,4.71204371340168837179e+00), RES(-4.0575816248744985081e-4, -1.5430805428404715941e0)}, {FN (sinh), ARG(1.0e+00,-4.71204371340168837179e+00), RES(-4.0575816248744985081e-4, 1.5430805428404715941e0)}, {FN (sinh), ARG(-1.0e+00,4.71204371340168837179e+00), RES(4.0575816248744985081e-4, -1.5430805428404715941e0)}, {FN (sinh), ARG(-1.0e+00,-4.71204371340168837179e+00), RES(4.0575816248744985081e-4, 1.5430805428404715941e0)}, {FN (sinh), ARG(1.0e+00,4.71273424736769097620e+00), RES(4.0575816248701808892e-4, -1.5430805428404715943e0)}, {FN (sinh), ARG(1.0e+00,-4.71273424736769097620e+00), RES(4.0575816248701808892e-4, 1.5430805428404715943e0)}, {FN (sinh), ARG(-1.0e+00,4.71273424736769097620e+00), RES(-4.0575816248701808892e-4, -1.5430805428404715943e0)}, {FN (sinh), ARG(-1.0e+00,-4.71273424736769097620e+00), RES(-4.0575816248701808892e-4, 1.5430805428404715943e0)}, {FN (sinh), ARG(1.0e+00,6.28284004019658492979e+00), RES(1.1752011235963524659e0, -5.3277478472548726245e-4)}, {FN (sinh), ARG(1.0e+00,-6.28284004019658492979e+00), RES(1.1752011235963524659e0, 5.3277478472548726245e-4)}, {FN (sinh), ARG(-1.0e+00,6.28284004019658492979e+00), RES(-1.1752011235963524659e0, -5.3277478472548726245e-4)}, {FN (sinh), ARG(-1.0e+00,-6.28284004019658492979e+00), RES(-1.1752011235963524659e0, 5.3277478472548726245e-4)}, {FN (sinh), ARG(1.0e+00,6.28353057416258753420e+00), RES(1.1752011235963524661e0, 5.3277478472473137099e-4)}, {FN (sinh), ARG(1.0e+00,-6.28353057416258753420e+00), RES(1.1752011235963524661e0, -5.3277478472473137099e-4)}, {FN (sinh), ARG(-1.0e+00,6.28353057416258753420e+00), RES(-1.1752011235963524661e0, 5.3277478472473137099e-4)}, {FN (sinh), ARG(-1.0e+00,-6.28353057416258753420e+00), RES(-1.1752011235963524661e0, -5.3277478472473137099e-4)}, {FN (sinh), ARG(1.0e+00,9.42443269378637893396e+00), RES(-1.1752011235963524662e0, 5.3277478472430570447e-4)}, {FN (sinh), ARG(1.0e+00,-9.42443269378637893396e+00), RES(-1.1752011235963524662e0, -5.3277478472430570447e-4)}, {FN (sinh), ARG(-1.0e+00,9.42443269378637893396e+00), RES(1.1752011235963524662e0, 5.3277478472430570447e-4)}, {FN (sinh), ARG(-1.0e+00,-9.42443269378637893396e+00), RES(1.1752011235963524662e0, -5.3277478472430570447e-4)}, {FN (sinh), ARG(1.0e+00,9.42512322775237976202e+00), RES(-1.1752011235963524665e0, -5.3277478472317186729e-4)}, {FN (sinh), ARG(1.0e+00,-9.42512322775237976202e+00), RES(-1.1752011235963524665e0, 5.3277478472317186729e-4)}, {FN (sinh), ARG(-1.0e+00,9.42512322775237976202e+00), RES(1.1752011235963524665e0, -5.3277478472317186729e-4)}, {FN (sinh), ARG(-1.0e+00,-9.42512322775237976202e+00), RES(1.1752011235963524665e0, 5.3277478472317186729e-4)}, {FN (sinh), ARG(2.0e+00,-3.45266983001243932001e-04), RES(3.6268601916692946556e0, -1.2989619299126701883e-3)}, {FN (sinh), ARG(2.0e+00,3.45266983001243932001e-04), RES(3.6268601916692946556e0, 1.2989619299126701883e-3)}, {FN (sinh), ARG(-2.0e+00,-3.45266983001243932001e-04), RES(-3.6268601916692946556e0, -1.2989619299126701883e-3)}, {FN (sinh), ARG(-2.0e+00,3.45266983001243932001e-04), RES(-3.6268601916692946556e0, 1.2989619299126701883e-3)}, {FN (sinh), ARG(2.0e+00,1.57045105981189525579e+00), RES(1.2522351259047577385e-3, 3.7621954668392959445e0)}, {FN (sinh), ARG(2.0e+00,-1.57045105981189525579e+00), RES(1.2522351259047577385e-3, -3.7621954668392959445e0)}, {FN (sinh), ARG(-2.0e+00,1.57045105981189525579e+00), RES(-1.2522351259047577385e-3, 3.7621954668392959445e0)}, {FN (sinh), ARG(-2.0e+00,-1.57045105981189525579e+00), RES(-1.2522351259047577385e-3, -3.7621954668392959445e0)}, {FN (sinh), ARG(2.0e+00,1.57114159377789786021e+00), RES(-1.2522351259043135762e-3, 3.7621954668392959447e0)}, {FN (sinh), ARG(2.0e+00,-1.57114159377789786021e+00), RES(-1.2522351259043135762e-3, -3.7621954668392959447e0)}, {FN (sinh), ARG(-2.0e+00,1.57114159377789786021e+00), RES(1.2522351259043135762e-3, 3.7621954668392959447e0)}, {FN (sinh), ARG(-2.0e+00,-1.57114159377789786021e+00), RES(1.2522351259043135762e-3, -3.7621954668392959447e0)}, {FN (sinh), ARG(2.0e+00,3.14124738660679181379e+00), RES(-3.6268601916692946553e0, 1.2989619299133501696e-3)}, {FN (sinh), ARG(2.0e+00,-3.14124738660679181379e+00), RES(-3.6268601916692946553e0, -1.2989619299133501696e-3)}, {FN (sinh), ARG(-2.0e+00,3.14124738660679181379e+00), RES(3.6268601916692946553e0, 1.2989619299133501696e-3)}, {FN (sinh), ARG(-2.0e+00,-3.14124738660679181379e+00), RES(3.6268601916692946553e0, -1.2989619299133501696e-3)}, {FN (sinh), ARG(2.0e+00,3.14193792057279441821e+00), RES(-3.6268601916692946556e0, -1.2989619299124286975e-3)}, {FN (sinh), ARG(2.0e+00,-3.14193792057279441821e+00), RES(-3.6268601916692946556e0, 1.2989619299124286975e-3)}, {FN (sinh), ARG(-2.0e+00,3.14193792057279441821e+00), RES(3.6268601916692946556e0, -1.2989619299124286975e-3)}, {FN (sinh), ARG(-2.0e+00,-3.14193792057279441821e+00), RES(3.6268601916692946556e0, 1.2989619299124286975e-3)}, {FN (sinh), ARG(2.0e+00,4.71204371340168837179e+00), RES(-1.2522351259052019007e-3, -3.7621954668392959444e0)}, {FN (sinh), ARG(2.0e+00,-4.71204371340168837179e+00), RES(-1.2522351259052019007e-3, 3.7621954668392959444e0)}, {FN (sinh), ARG(-2.0e+00,4.71204371340168837179e+00), RES(1.2522351259052019007e-3, -3.7621954668392959444e0)}, {FN (sinh), ARG(-2.0e+00,-4.71204371340168837179e+00), RES(1.2522351259052019007e-3, 3.7621954668392959444e0)}, {FN (sinh), ARG(2.0e+00,4.71273424736769097620e+00), RES(1.2522351259038694139e-3, -3.7621954668392959448e0)}, {FN (sinh), ARG(2.0e+00,-4.71273424736769097620e+00), RES(1.2522351259038694139e-3, 3.7621954668392959448e0)}, {FN (sinh), ARG(-2.0e+00,4.71273424736769097620e+00), RES(-1.2522351259038694139e-3, -3.7621954668392959448e0)}, {FN (sinh), ARG(-2.0e+00,-4.71273424736769097620e+00), RES(-1.2522351259038694139e-3, 3.7621954668392959448e0)}, {FN (sinh), ARG(2.0e+00,6.28284004019658492979e+00), RES(3.6268601916692946552e0, -1.2989619299138109057e-3)}, {FN (sinh), ARG(2.0e+00,-6.28284004019658492979e+00), RES(3.6268601916692946552e0, 1.2989619299138109057e-3)}, {FN (sinh), ARG(-2.0e+00,6.28284004019658492979e+00), RES(-3.6268601916692946552e0, -1.2989619299138109057e-3)}, {FN (sinh), ARG(-2.0e+00,-6.28284004019658492979e+00), RES(-3.6268601916692946552e0, 1.2989619299138109057e-3)}, {FN (sinh), ARG(2.0e+00,6.28353057416258753420e+00), RES(3.6268601916692946558e0, 1.2989619299119679614e-3)}, {FN (sinh), ARG(2.0e+00,-6.28353057416258753420e+00), RES(3.6268601916692946558e0, -1.2989619299119679614e-3)}, {FN (sinh), ARG(-2.0e+00,6.28353057416258753420e+00), RES(-3.6268601916692946558e0, 1.2989619299119679614e-3)}, {FN (sinh), ARG(-2.0e+00,-6.28353057416258753420e+00), RES(-3.6268601916692946558e0, -1.2989619299119679614e-3)}, {FN (sinh), ARG(2.0e+00,9.42443269378637893396e+00), RES(-3.6268601916692946561e0, 1.2989619299109301409e-3)}, {FN (sinh), ARG(2.0e+00,-9.42443269378637893396e+00), RES(-3.6268601916692946561e0, -1.2989619299109301409e-3)}, {FN (sinh), ARG(-2.0e+00,9.42443269378637893396e+00), RES(3.6268601916692946561e0, 1.2989619299109301409e-3)}, {FN (sinh), ARG(-2.0e+00,-9.42443269378637893396e+00), RES(3.6268601916692946561e0, -1.2989619299109301409e-3)}, {FN (sinh), ARG(2.0e+00,9.42512322775237976202e+00), RES(-3.6268601916692946571e0, -1.2989619299081657245e-3)}, {FN (sinh), ARG(2.0e+00,-9.42512322775237976202e+00), RES(-3.6268601916692946571e0, 1.2989619299081657245e-3)}, {FN (sinh), ARG(-2.0e+00,9.42512322775237976202e+00), RES(3.6268601916692946571e0, -1.2989619299081657245e-3)}, {FN (sinh), ARG(-2.0e+00,-9.42512322775237976202e+00), RES(3.6268601916692946571e0, 1.2989619299081657245e-3)}, {FN (cosh), ARG(0.0e+00,-3.45266983001243932001e-04), RES(9.9999994039535581673e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,3.45266983001243932001e-04), RES(9.9999994039535581673e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,1.57045105981189525579e+00), RES(3.4526697614152485627e-4, 0.0)}, {FN (cosh), ARG(0.0e+00,-1.57045105981189525579e+00), RES(3.4526697614152485627e-4, 0.0)}, {FN (cosh), ARG(0.0e+00,1.57114159377789786021e+00), RES(-3.4526697614140239160e-4, 0.0)}, {FN (cosh), ARG(0.0e+00,-1.57114159377789786021e+00), RES(-3.4526697614140239160e-4, 0.0)}, {FN (cosh), ARG(0.0e+00,3.14124738660679181379e+00), RES(-9.9999994039535581667e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,-3.14124738660679181379e+00), RES(-9.9999994039535581667e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,3.14193792057279441821e+00), RES(-9.9999994039535581675e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,-3.14193792057279441821e+00), RES(-9.9999994039535581675e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,4.71204371340168837179e+00), RES(-3.4526697614164732094e-4, 0.0)}, {FN (cosh), ARG(0.0e+00,-4.71204371340168837179e+00), RES(-3.4526697614164732094e-4, 0.0)}, {FN (cosh), ARG(0.0e+00,4.71273424736769097620e+00), RES(3.4526697614127992692e-4, 0.0)}, {FN (cosh), ARG(0.0e+00,-4.71273424736769097620e+00), RES(3.4526697614127992692e-4, 0.0)}, {FN (cosh), ARG(0.0e+00,6.28284004019658492979e+00), RES(9.9999994039535581662e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,-6.28284004019658492979e+00), RES(9.9999994039535581662e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,6.28353057416258753420e+00), RES(9.9999994039535581679e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,-6.28353057416258753420e+00), RES(9.9999994039535581679e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,9.42443269378637893396e+00), RES(-9.9999994039535581689e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,-9.42443269378637893396e+00), RES(-9.9999994039535581689e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,9.42512322775237976202e+00), RES(-9.9999994039535581714e-1, 0.0)}, {FN (cosh), ARG(0.0e+00,-9.42512322775237976202e+00), RES(-9.9999994039535581714e-1, 0.0)}, {FN (cosh), ARG(1.19209289550781250e-07,-3.45266983001243932001e-04), RES(9.9999994039536292216e-1, -4.1159030931163569191e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,3.45266983001243932001e-04), RES(9.9999994039536292216e-1, 4.1159030931163569191e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,-3.45266983001243932001e-04), RES(9.9999994039536292216e-1, 4.1159030931163569191e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,3.45266983001243932001e-04), RES(9.9999994039536292216e-1, -4.1159030931163569191e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,1.57045105981189525579e+00), RES(3.4526697614152730954e-4, 1.1920928244535424532e-7)}, {FN (cosh), ARG(1.19209289550781250e-07,-1.57045105981189525579e+00), RES(3.4526697614152730954e-4, -1.1920928244535424532e-7)}, {FN (cosh), ARG(-1.19209289550781250e-07,1.57045105981189525579e+00), RES(3.4526697614152730954e-4, -1.1920928244535424532e-7)}, {FN (cosh), ARG(-1.19209289550781250e-07,-1.57045105981189525579e+00), RES(3.4526697614152730954e-4, 1.1920928244535424532e-7)}, {FN (cosh), ARG(1.19209289550781250e-07,1.57114159377789786021e+00), RES(-3.4526697614140484486e-4, 1.1920928244535424533e-7)}, {FN (cosh), ARG(1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-3.4526697614140484486e-4, -1.1920928244535424533e-7)}, {FN (cosh), ARG(-1.19209289550781250e-07,1.57114159377789786021e+00), RES(-3.4526697614140484486e-4, -1.1920928244535424533e-7)}, {FN (cosh), ARG(-1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-3.4526697614140484486e-4, 1.1920928244535424533e-7)}, {FN (cosh), ARG(1.19209289550781250e-07,3.14124738660679181379e+00), RES(-9.9999994039536292209e-1, 4.1159030931185115142e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-9.9999994039536292209e-1, -4.1159030931185115142e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,3.14124738660679181379e+00), RES(-9.9999994039536292209e-1, -4.1159030931185115142e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-9.9999994039536292209e-1, 4.1159030931185115142e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,3.14193792057279441821e+00), RES(-9.9999994039536292218e-1, -4.1159030931155917289e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-9.9999994039536292218e-1, 4.1159030931155917289e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,3.14193792057279441821e+00), RES(-9.9999994039536292218e-1, 4.1159030931155917289e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-9.9999994039536292218e-1, -4.1159030931155917289e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,4.71204371340168837179e+00), RES(-3.4526697614164977421e-4, -1.1920928244535424532e-7)}, {FN (cosh), ARG(1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-3.4526697614164977421e-4, 1.1920928244535424532e-7)}, {FN (cosh), ARG(-1.19209289550781250e-07,4.71204371340168837179e+00), RES(-3.4526697614164977421e-4, 1.1920928244535424532e-7)}, {FN (cosh), ARG(-1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-3.4526697614164977421e-4, -1.1920928244535424532e-7)}, {FN (cosh), ARG(1.19209289550781250e-07,4.71273424736769097620e+00), RES(3.4526697614128238019e-4, -1.1920928244535424533e-7)}, {FN (cosh), ARG(1.19209289550781250e-07,-4.71273424736769097620e+00), RES(3.4526697614128238019e-4, 1.1920928244535424533e-7)}, {FN (cosh), ARG(-1.19209289550781250e-07,4.71273424736769097620e+00), RES(3.4526697614128238019e-4, 1.1920928244535424533e-7)}, {FN (cosh), ARG(-1.19209289550781250e-07,-4.71273424736769097620e+00), RES(3.4526697614128238019e-4, -1.1920928244535424533e-7)}, {FN (cosh), ARG(1.19209289550781250e-07,6.28284004019658492979e+00), RES(9.9999994039536292205e-1, -4.1159030931199714069e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,-6.28284004019658492979e+00), RES(9.9999994039536292205e-1, 4.1159030931199714069e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,6.28284004019658492979e+00), RES(9.9999994039536292205e-1, 4.1159030931199714069e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,-6.28284004019658492979e+00), RES(9.9999994039536292205e-1, -4.1159030931199714069e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,6.28353057416258753420e+00), RES(9.9999994039536292222e-1, 4.1159030931141318362e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,-6.28353057416258753420e+00), RES(9.9999994039536292222e-1, -4.1159030931141318362e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,6.28353057416258753420e+00), RES(9.9999994039536292222e-1, -4.1159030931141318362e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,-6.28353057416258753420e+00), RES(9.9999994039536292222e-1, 4.1159030931141318362e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,9.42443269378637893396e+00), RES(-9.9999994039536292231e-1, 4.1159030931108433883e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-9.9999994039536292231e-1, -4.1159030931108433883e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,9.42443269378637893396e+00), RES(-9.9999994039536292231e-1, -4.1159030931108433883e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-9.9999994039536292231e-1, 4.1159030931108433883e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,9.42512322775237976202e+00), RES(-9.9999994039536292257e-1, -4.1159030931020840323e-11)}, {FN (cosh), ARG(1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-9.9999994039536292257e-1, 4.1159030931020840323e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,9.42512322775237976202e+00), RES(-9.9999994039536292257e-1, 4.1159030931020840323e-11)}, {FN (cosh), ARG(-1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-9.9999994039536292257e-1, -4.1159030931020840323e-11)}, {FN (cosh), ARG(5.0e-01,-3.45266983001243932001e-04), RES(1.1276258979946363573e0, -1.7991700040930800151e-4)}, {FN (cosh), ARG(5.0e-01,3.45266983001243932001e-04), RES(1.1276258979946363573e0, 1.7991700040930800151e-4)}, {FN (cosh), ARG(-5.0e-01,-3.45266983001243932001e-04), RES(1.1276258979946363573e0, 1.7991700040930800151e-4)}, {FN (cosh), ARG(-5.0e-01,3.45266983001243932001e-04), RES(1.1276258979946363573e0, -1.7991700040930800151e-4)}, {FN (cosh), ARG(5.0e-01,1.57045105981189525579e+00), RES(3.8933200722547541227e-4, 5.2109527443404709207e-1)}, {FN (cosh), ARG(5.0e-01,-1.57045105981189525579e+00), RES(3.8933200722547541227e-4, -5.2109527443404709207e-1)}, {FN (cosh), ARG(-5.0e-01,1.57045105981189525579e+00), RES(3.8933200722547541227e-4, -5.2109527443404709207e-1)}, {FN (cosh), ARG(-5.0e-01,-1.57045105981189525579e+00), RES(3.8933200722547541227e-4, 5.2109527443404709207e-1)}, {FN (cosh), ARG(5.0e-01,1.57114159377789786021e+00), RES(-3.8933200722533731792e-4, 5.2109527443404709209e-1)}, {FN (cosh), ARG(5.0e-01,-1.57114159377789786021e+00), RES(-3.8933200722533731792e-4, -5.2109527443404709209e-1)}, {FN (cosh), ARG(-5.0e-01,1.57114159377789786021e+00), RES(-3.8933200722533731792e-4, -5.2109527443404709209e-1)}, {FN (cosh), ARG(-5.0e-01,-1.57114159377789786021e+00), RES(-3.8933200722533731792e-4, 5.2109527443404709209e-1)}, {FN (cosh), ARG(5.0e-01,3.14124738660679181379e+00), RES(-1.1276258979946363572e0, 1.7991700040940218455e-4)}, {FN (cosh), ARG(5.0e-01,-3.14124738660679181379e+00), RES(-1.1276258979946363572e0, -1.7991700040940218455e-4)}, {FN (cosh), ARG(-5.0e-01,3.14124738660679181379e+00), RES(-1.1276258979946363572e0, -1.7991700040940218455e-4)}, {FN (cosh), ARG(-5.0e-01,-3.14124738660679181379e+00), RES(-1.1276258979946363572e0, 1.7991700040940218455e-4)}, {FN (cosh), ARG(5.0e-01,3.14193792057279441821e+00), RES(-1.1276258979946363573e0, -1.7991700040927455302e-4)}, {FN (cosh), ARG(5.0e-01,-3.14193792057279441821e+00), RES(-1.1276258979946363573e0, 1.7991700040927455302e-4)}, {FN (cosh), ARG(-5.0e-01,3.14193792057279441821e+00), RES(-1.1276258979946363573e0, 1.7991700040927455302e-4)}, {FN (cosh), ARG(-5.0e-01,-3.14193792057279441821e+00), RES(-1.1276258979946363573e0, -1.7991700040927455302e-4)}, {FN (cosh), ARG(5.0e-01,4.71204371340168837179e+00), RES(-3.8933200722561350661e-4, -5.2109527443404709205e-1)}, {FN (cosh), ARG(5.0e-01,-4.71204371340168837179e+00), RES(-3.8933200722561350661e-4, 5.2109527443404709205e-1)}, {FN (cosh), ARG(-5.0e-01,4.71204371340168837179e+00), RES(-3.8933200722561350661e-4, 5.2109527443404709205e-1)}, {FN (cosh), ARG(-5.0e-01,-4.71204371340168837179e+00), RES(-3.8933200722561350661e-4, -5.2109527443404709205e-1)}, {FN (cosh), ARG(5.0e-01,4.71273424736769097620e+00), RES(3.8933200722519922358e-4, -5.2109527443404709212e-1)}, {FN (cosh), ARG(5.0e-01,-4.71273424736769097620e+00), RES(3.8933200722519922358e-4, 5.2109527443404709212e-1)}, {FN (cosh), ARG(-5.0e-01,4.71273424736769097620e+00), RES(3.8933200722519922358e-4, 5.2109527443404709212e-1)}, {FN (cosh), ARG(-5.0e-01,-4.71273424736769097620e+00), RES(3.8933200722519922358e-4, -5.2109527443404709212e-1)}, {FN (cosh), ARG(5.0e-01,6.28284004019658492979e+00), RES(1.1276258979946363572e0, -1.7991700040946600032e-4)}, {FN (cosh), ARG(5.0e-01,-6.28284004019658492979e+00), RES(1.1276258979946363572e0, 1.7991700040946600032e-4)}, {FN (cosh), ARG(-5.0e-01,6.28284004019658492979e+00), RES(1.1276258979946363572e0, 1.7991700040946600032e-4)}, {FN (cosh), ARG(-5.0e-01,-6.28284004019658492979e+00), RES(1.1276258979946363572e0, -1.7991700040946600032e-4)}, {FN (cosh), ARG(5.0e-01,6.28353057416258753420e+00), RES(1.1276258979946363574e0, 1.7991700040921073725e-4)}, {FN (cosh), ARG(5.0e-01,-6.28353057416258753420e+00), RES(1.1276258979946363574e0, -1.7991700040921073725e-4)}, {FN (cosh), ARG(-5.0e-01,6.28353057416258753420e+00), RES(1.1276258979946363574e0, -1.7991700040921073725e-4)}, {FN (cosh), ARG(-5.0e-01,-6.28353057416258753420e+00), RES(1.1276258979946363574e0, 1.7991700040921073725e-4)}, {FN (cosh), ARG(5.0e-01,9.42443269378637893396e+00), RES(-1.1276258979946363575e0, 1.7991700040906699050e-4)}, {FN (cosh), ARG(5.0e-01,-9.42443269378637893396e+00), RES(-1.1276258979946363575e0, -1.7991700040906699050e-4)}, {FN (cosh), ARG(-5.0e-01,9.42443269378637893396e+00), RES(-1.1276258979946363575e0, -1.7991700040906699050e-4)}, {FN (cosh), ARG(-5.0e-01,-9.42443269378637893396e+00), RES(-1.1276258979946363575e0, 1.7991700040906699050e-4)}, {FN (cosh), ARG(5.0e-01,9.42512322775237976202e+00), RES(-1.1276258979946363577e0, -1.7991700040868409591e-4)}, {FN (cosh), ARG(5.0e-01,-9.42512322775237976202e+00), RES(-1.1276258979946363577e0, 1.7991700040868409591e-4)}, {FN (cosh), ARG(-5.0e-01,9.42512322775237976202e+00), RES(-1.1276258979946363577e0, 1.7991700040868409591e-4)}, {FN (cosh), ARG(-5.0e-01,-9.42512322775237976202e+00), RES(-1.1276258979946363577e0, -1.7991700040868409591e-4)}, {FN (cosh), ARG(1.0e+00,-3.45266983001243932001e-04), RES(1.5430805428404715942e0, -4.057581624871654840e-4)}, {FN (cosh), ARG(1.0e+00,3.45266983001243932001e-04), RES(1.5430805428404715942e0, 4.057581624871654840e-4)}, {FN (cosh), ARG(-1.0e+00,-3.45266983001243932001e-04), RES(1.5430805428404715942e0, 4.057581624871654840e-4)}, {FN (cosh), ARG(-1.0e+00,3.45266983001243932001e-04), RES(1.5430805428404715942e0, -4.057581624871654840e-4)}, {FN (cosh), ARG(1.0e+00,1.57045105981189525579e+00), RES(5.3277478472520380315e-4, 1.1752011235963524659e0)}, {FN (cosh), ARG(1.0e+00,-1.57045105981189525579e+00), RES(5.3277478472520380315e-4, -1.1752011235963524659e0)}, {FN (cosh), ARG(-1.0e+00,1.57045105981189525579e+00), RES(5.3277478472520380315e-4, -1.1752011235963524659e0)}, {FN (cosh), ARG(-1.0e+00,-1.57045105981189525579e+00), RES(5.3277478472520380315e-4, 1.1752011235963524659e0)}, {FN (cosh), ARG(1.0e+00,1.57114159377789786021e+00), RES(-5.3277478472501483029e-4, 1.1752011235963524660e0)}, {FN (cosh), ARG(1.0e+00,-1.57114159377789786021e+00), RES(-5.3277478472501483029e-4, -1.1752011235963524660e0)}, {FN (cosh), ARG(-1.0e+00,1.57114159377789786021e+00), RES(-5.3277478472501483029e-4, -1.1752011235963524660e0)}, {FN (cosh), ARG(-1.0e+00,-1.57114159377789786021e+00), RES(-5.3277478472501483029e-4, 1.1752011235963524660e0)}, {FN (cosh), ARG(1.0e+00,3.14124738660679181379e+00), RES(-1.5430805428404715941e0, 4.0575816248737789049e-4)}, {FN (cosh), ARG(1.0e+00,-3.14124738660679181379e+00), RES(-1.5430805428404715941e0, -4.0575816248737789049e-4)}, {FN (cosh), ARG(-1.0e+00,3.14124738660679181379e+00), RES(-1.5430805428404715941e0, -4.0575816248737789049e-4)}, {FN (cosh), ARG(-1.0e+00,-3.14124738660679181379e+00), RES(-1.5430805428404715941e0, 4.0575816248737789049e-4)}, {FN (cosh), ARG(1.0e+00,3.14193792057279441821e+00), RES(-1.5430805428404715943e0, -4.0575816248709004923e-4)}, {FN (cosh), ARG(1.0e+00,-3.14193792057279441821e+00), RES(-1.5430805428404715943e0, 4.0575816248709004923e-4)}, {FN (cosh), ARG(-1.0e+00,3.14193792057279441821e+00), RES(-1.5430805428404715943e0, 4.0575816248709004923e-4)}, {FN (cosh), ARG(-1.0e+00,-3.14193792057279441821e+00), RES(-1.5430805428404715943e0, -4.0575816248709004923e-4)}, {FN (cosh), ARG(1.0e+00,4.71204371340168837179e+00), RES(-5.3277478472539277601e-4, -1.1752011235963524659e0)}, {FN (cosh), ARG(1.0e+00,-4.71204371340168837179e+00), RES(-5.3277478472539277601e-4, 1.1752011235963524659e0)}, {FN (cosh), ARG(-1.0e+00,4.71204371340168837179e+00), RES(-5.3277478472539277601e-4, 1.1752011235963524659e0)}, {FN (cosh), ARG(-1.0e+00,-4.71204371340168837179e+00), RES(-5.3277478472539277601e-4, -1.1752011235963524659e0)}, {FN (cosh), ARG(1.0e+00,4.71273424736769097620e+00), RES(5.3277478472482585742e-4, -1.1752011235963524660e0)}, {FN (cosh), ARG(1.0e+00,-4.71273424736769097620e+00), RES(5.3277478472482585742e-4, 1.1752011235963524660e0)}, {FN (cosh), ARG(-1.0e+00,4.71273424736769097620e+00), RES(5.3277478472482585742e-4, 1.1752011235963524660e0)}, {FN (cosh), ARG(-1.0e+00,-4.71273424736769097620e+00), RES(5.3277478472482585742e-4, -1.1752011235963524660e0)}, {FN (cosh), ARG(1.0e+00,6.28284004019658492979e+00), RES(1.5430805428404715941e0, -4.0575816248752181112e-4)}, {FN (cosh), ARG(1.0e+00,-6.28284004019658492979e+00), RES(1.5430805428404715941e0, 4.0575816248752181112e-4)}, {FN (cosh), ARG(-1.0e+00,6.28284004019658492979e+00), RES(1.5430805428404715941e0, 4.0575816248752181112e-4)}, {FN (cosh), ARG(-1.0e+00,-6.28284004019658492979e+00), RES(1.5430805428404715941e0, -4.0575816248752181112e-4)}, {FN (cosh), ARG(1.0e+00,6.28353057416258753420e+00), RES(1.5430805428404715943e0, 4.0575816248694612861e-4)}, {FN (cosh), ARG(1.0e+00,-6.28353057416258753420e+00), RES(1.5430805428404715943e0, -4.0575816248694612861e-4)}, {FN (cosh), ARG(-1.0e+00,6.28353057416258753420e+00), RES(1.5430805428404715943e0, -4.0575816248694612861e-4)}, {FN (cosh), ARG(-1.0e+00,-6.28353057416258753420e+00), RES(1.5430805428404715943e0, 4.0575816248694612861e-4)}, {FN (cosh), ARG(1.0e+00,9.42443269378637893396e+00), RES(-1.5430805428404715945e0, 4.0575816248662194348e-4)}, {FN (cosh), ARG(1.0e+00,-9.42443269378637893396e+00), RES(-1.5430805428404715945e0, -4.0575816248662194348e-4)}, {FN (cosh), ARG(-1.0e+00,9.42443269378637893396e+00), RES(-1.5430805428404715945e0, -4.0575816248662194348e-4)}, {FN (cosh), ARG(-1.0e+00,-9.42443269378637893396e+00), RES(-1.5430805428404715945e0, 4.0575816248662194348e-4)}, {FN (cosh), ARG(1.0e+00,9.42512322775237976202e+00), RES(-1.5430805428404715949e0, -4.0575816248575841970e-4)}, {FN (cosh), ARG(1.0e+00,-9.42512322775237976202e+00), RES(-1.5430805428404715949e0, 4.0575816248575841970e-4)}, {FN (cosh), ARG(-1.0e+00,9.42512322775237976202e+00), RES(-1.5430805428404715949e0, 4.0575816248575841970e-4)}, {FN (cosh), ARG(-1.0e+00,-9.42512322775237976202e+00), RES(-1.5430805428404715949e0, -4.0575816248575841970e-4)}, {FN (cosh), ARG(2.0e+00,-3.45266983001243932001e-04), RES(3.7621954668392959447e0, -1.2522351259043242989e-3)}, {FN (cosh), ARG(2.0e+00,3.45266983001243932001e-04), RES(3.7621954668392959447e0, 1.2522351259043242989e-3)}, {FN (cosh), ARG(-2.0e+00,-3.45266983001243932001e-04), RES(3.7621954668392959447e0, 1.2522351259043242989e-3)}, {FN (cosh), ARG(-2.0e+00,3.45266983001243932001e-04), RES(3.7621954668392959447e0, -1.2522351259043242989e-3)}, {FN (cosh), ARG(2.0e+00,1.57045105981189525579e+00), RES(1.2989619299131198016e-3, 3.6268601916692946554e0)}, {FN (cosh), ARG(2.0e+00,-1.57045105981189525579e+00), RES(1.2989619299131198016e-3, -3.6268601916692946554e0)}, {FN (cosh), ARG(-2.0e+00,1.57045105981189525579e+00), RES(1.2989619299131198016e-3, -3.6268601916692946554e0)}, {FN (cosh), ARG(-2.0e+00,-1.57045105981189525579e+00), RES(1.2989619299131198016e-3, 3.6268601916692946554e0)}, {FN (cosh), ARG(2.0e+00,1.57114159377789786021e+00), RES(-1.2989619299126590655e-3, 3.6268601916692946556e0)}, {FN (cosh), ARG(2.0e+00,-1.57114159377789786021e+00), RES(-1.2989619299126590655e-3, -3.6268601916692946556e0)}, {FN (cosh), ARG(-2.0e+00,1.57114159377789786021e+00), RES(-1.2989619299126590655e-3, -3.6268601916692946556e0)}, {FN (cosh), ARG(-2.0e+00,-1.57114159377789786021e+00), RES(-1.2989619299126590655e-3, 3.6268601916692946556e0)}, {FN (cosh), ARG(2.0e+00,3.14124738660679181379e+00), RES(-3.7621954668392959444e0, 1.2522351259049798196e-3)}, {FN (cosh), ARG(2.0e+00,-3.14124738660679181379e+00), RES(-3.7621954668392959444e0, -1.2522351259049798196e-3)}, {FN (cosh), ARG(-2.0e+00,3.14124738660679181379e+00), RES(-3.7621954668392959444e0, -1.2522351259049798196e-3)}, {FN (cosh), ARG(-2.0e+00,-3.14124738660679181379e+00), RES(-3.7621954668392959444e0, 1.2522351259049798196e-3)}, {FN (cosh), ARG(2.0e+00,3.14193792057279441821e+00), RES(-3.7621954668392959448e0, -1.2522351259040914950e-3)}, {FN (cosh), ARG(2.0e+00,-3.14193792057279441821e+00), RES(-3.7621954668392959448e0, 1.2522351259040914950e-3)}, {FN (cosh), ARG(-2.0e+00,3.14193792057279441821e+00), RES(-3.7621954668392959448e0, 1.2522351259040914950e-3)}, {FN (cosh), ARG(-2.0e+00,-3.14193792057279441821e+00), RES(-3.7621954668392959448e0, -1.2522351259040914950e-3)}, {FN (cosh), ARG(2.0e+00,4.71204371340168837179e+00), RES(-1.2989619299135805376e-3, -3.6268601916692946552e0)}, {FN (cosh), ARG(2.0e+00,-4.71204371340168837179e+00), RES(-1.2989619299135805376e-3, 3.6268601916692946552e0)}, {FN (cosh), ARG(-2.0e+00,4.71204371340168837179e+00), RES(-1.2989619299135805376e-3, 3.6268601916692946552e0)}, {FN (cosh), ARG(-2.0e+00,-4.71204371340168837179e+00), RES(-1.2989619299135805376e-3, -3.6268601916692946552e0)}, {FN (cosh), ARG(2.0e+00,4.71273424736769097620e+00), RES(1.2989619299121983294e-3, -3.6268601916692946557e0)}, {FN (cosh), ARG(2.0e+00,-4.71273424736769097620e+00), RES(1.2989619299121983294e-3, 3.6268601916692946557e0)}, {FN (cosh), ARG(-2.0e+00,4.71273424736769097620e+00), RES(1.2989619299121983294e-3, 3.6268601916692946557e0)}, {FN (cosh), ARG(-2.0e+00,-4.71273424736769097620e+00), RES(1.2989619299121983294e-3, -3.6268601916692946557e0)}, {FN (cosh), ARG(2.0e+00,6.28284004019658492979e+00), RES(3.7621954668392959443e0, -1.2522351259054239819e-3)}, {FN (cosh), ARG(2.0e+00,-6.28284004019658492979e+00), RES(3.7621954668392959443e0, 1.2522351259054239819e-3)}, {FN (cosh), ARG(-2.0e+00,6.28284004019658492979e+00), RES(3.7621954668392959443e0, 1.2522351259054239819e-3)}, {FN (cosh), ARG(-2.0e+00,-6.28284004019658492979e+00), RES(3.7621954668392959443e0, -1.2522351259054239819e-3)}, {FN (cosh), ARG(2.0e+00,6.28353057416258753420e+00), RES(3.7621954668392959449e0, 1.2522351259036473328e-3)}, {FN (cosh), ARG(2.0e+00,-6.28353057416258753420e+00), RES(3.7621954668392959449e0, -1.2522351259036473328e-3)}, {FN (cosh), ARG(-2.0e+00,6.28353057416258753420e+00), RES(3.7621954668392959449e0, -1.2522351259036473328e-3)}, {FN (cosh), ARG(-2.0e+00,-6.28353057416258753420e+00), RES(3.7621954668392959449e0, 1.2522351259036473328e-3)}, {FN (cosh), ARG(2.0e+00,9.42443269378637893396e+00), RES(-3.7621954668392959453e0, 1.2522351259026468452e-3)}, {FN (cosh), ARG(2.0e+00,-9.42443269378637893396e+00), RES(-3.7621954668392959453e0, -1.2522351259026468452e-3)}, {FN (cosh), ARG(-2.0e+00,9.42443269378637893396e+00), RES(-3.7621954668392959453e0, -1.2522351259026468452e-3)}, {FN (cosh), ARG(-2.0e+00,-9.42443269378637893396e+00), RES(-3.7621954668392959453e0, 1.2522351259026468452e-3)}, {FN (cosh), ARG(2.0e+00,9.42512322775237976202e+00), RES(-3.7621954668392959462e0, -1.2522351258999818715e-3)}, {FN (cosh), ARG(2.0e+00,-9.42512322775237976202e+00), RES(-3.7621954668392959462e0, 1.2522351258999818715e-3)}, {FN (cosh), ARG(-2.0e+00,9.42512322775237976202e+00), RES(-3.7621954668392959462e0, 1.2522351258999818715e-3)}, {FN (cosh), ARG(-2.0e+00,-9.42512322775237976202e+00), RES(-3.7621954668392959462e0, -1.2522351258999818715e-3)}, {FN (tanh), ARG(0.0e+00,-3.45266983001243932001e-04), RES(0, -3.4526699672092183585e-4)}, {FN (tanh), ARG(0.0e+00,3.45266983001243932001e-04), RES(0, 3.4526699672092183585e-4)}, {FN (tanh), ARG(0.0e+00,1.57045105981189525579e+00), RES(0, 2.8963092606501007060e3)}, {FN (tanh), ARG(0.0e+00,-1.57045105981189525579e+00), RES(0, -2.8963092606501007060e3)}, {FN (tanh), ARG(0.0e+00,1.57114159377789786021e+00), RES(0, -2.8963092606511280143e3)}, {FN (tanh), ARG(0.0e+00,-1.57114159377789786021e+00), RES(0, 2.8963092606511280143e3)}, {FN (tanh), ARG(0.0e+00,3.14124738660679181379e+00), RES(0, -3.4526699672110257641e-4)}, {FN (tanh), ARG(0.0e+00,-3.14124738660679181379e+00), RES(0, 3.4526699672110257641e-4)}, {FN (tanh), ARG(0.0e+00,3.14193792057279441821e+00), RES(0, 3.4526699672085764703e-4)}, {FN (tanh), ARG(0.0e+00,-3.14193792057279441821e+00), RES(0, -3.4526699672085764703e-4)}, {FN (tanh), ARG(0.0e+00,4.71204371340168837179e+00), RES(0, 2.8963092606490733978e3)}, {FN (tanh), ARG(0.0e+00,-4.71204371340168837179e+00), RES(0, -2.8963092606490733978e3)}, {FN (tanh), ARG(0.0e+00,4.71273424736769097620e+00), RES(0, -2.8963092606521553225e3)}, {FN (tanh), ARG(0.0e+00,-4.71273424736769097620e+00), RES(0, 2.8963092606521553225e3)}, {FN (tanh), ARG(0.0e+00,6.28284004019658492979e+00), RES(0, -3.4526699672122504111e-4)}, {FN (tanh), ARG(0.0e+00,-6.28284004019658492979e+00), RES(0, 3.4526699672122504111e-4)}, {FN (tanh), ARG(0.0e+00,6.28353057416258753420e+00), RES(0, 3.4526699672073518233e-4)}, {FN (tanh), ARG(0.0e+00,-6.28353057416258753420e+00), RES(0, -3.4526699672073518233e-4)}, {FN (tanh), ARG(0.0e+00,9.42443269378637893396e+00), RES(0, -3.4526699672045932728e-4)}, {FN (tanh), ARG(0.0e+00,-9.42443269378637893396e+00), RES(0, 3.4526699672045932728e-4)}, {FN (tanh), ARG(0.0e+00,9.42512322775237976202e+00), RES(0, 3.4526699671972453911e-4)}, {FN (tanh), ARG(0.0e+00,-9.42512322775237976202e+00), RES(0, -3.4526699671972453911e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,-3.45266983001243932001e-04), RES(1.1920930376163652989e-7, -3.4526699672091692931e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,3.45266983001243932001e-04), RES(1.1920930376163652989e-7, 3.4526699672091692931e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,-3.45266983001243932001e-04), RES(-1.1920930376163652989e-7, -3.4526699672091692931e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,3.45266983001243932001e-04), RES(-1.1920930376163652989e-7, 3.4526699672091692931e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,1.57045105981189525579e+00), RES(9.9999992052646305569e-1, 2.8963089153831588642e3)}, {FN (tanh), ARG(1.19209289550781250e-07,-1.57045105981189525579e+00), RES(9.9999992052646305569e-1, -2.8963089153831588642e3)}, {FN (tanh), ARG(-1.19209289550781250e-07,1.57045105981189525579e+00), RES(-9.9999992052646305569e-1, 2.8963089153831588642e3)}, {FN (tanh), ARG(-1.19209289550781250e-07,-1.57045105981189525579e+00), RES(-9.9999992052646305569e-1, -2.8963089153831588642e3)}, {FN (tanh), ARG(1.19209289550781250e-07,1.57114159377789786021e+00), RES(9.9999992052717244672e-1, -2.8963089153841861720e3)}, {FN (tanh), ARG(1.19209289550781250e-07,-1.57114159377789786021e+00), RES(9.9999992052717244672e-1, 2.8963089153841861720e3)}, {FN (tanh), ARG(-1.19209289550781250e-07,1.57114159377789786021e+00), RES(-9.9999992052717244672e-1, -2.8963089153841861720e3)}, {FN (tanh), ARG(-1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-9.9999992052717244672e-1, 2.8963089153841861720e3)}, {FN (tanh), ARG(1.19209289550781250e-07,3.14124738660679181379e+00), RES(1.1920930376163652991e-7, -3.4526699672109766987e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,-3.14124738660679181379e+00), RES(1.1920930376163652991e-7, 3.4526699672109766987e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,3.14124738660679181379e+00), RES(-1.1920930376163652991e-7, -3.4526699672109766987e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-1.1920930376163652991e-7, 3.4526699672109766987e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,3.14193792057279441821e+00), RES(1.1920930376163652989e-7, 3.4526699672085274049e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,-3.14193792057279441821e+00), RES(1.1920930376163652989e-7, -3.4526699672085274049e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,3.14193792057279441821e+00), RES(-1.1920930376163652989e-7, 3.4526699672085274049e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-1.1920930376163652989e-7, -3.4526699672085274049e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,4.71204371340168837179e+00), RES(9.9999992052575366466e-1, 2.8963089153821315563e3)}, {FN (tanh), ARG(1.19209289550781250e-07,-4.71204371340168837179e+00), RES(9.9999992052575366466e-1, -2.8963089153821315563e3)}, {FN (tanh), ARG(-1.19209289550781250e-07,4.71204371340168837179e+00), RES(-9.9999992052575366466e-1, 2.8963089153821315563e3)}, {FN (tanh), ARG(-1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-9.9999992052575366466e-1, -2.8963089153821315563e3)}, {FN (tanh), ARG(1.19209289550781250e-07,4.71273424736769097620e+00), RES(9.9999992052788183776e-1, -2.8963089153852134799e3)}, {FN (tanh), ARG(1.19209289550781250e-07,-4.71273424736769097620e+00), RES(9.9999992052788183776e-1, 2.8963089153852134799e3)}, {FN (tanh), ARG(-1.19209289550781250e-07,4.71273424736769097620e+00), RES(-9.9999992052788183776e-1, -2.8963089153852134799e3)}, {FN (tanh), ARG(-1.19209289550781250e-07,-4.71273424736769097620e+00), RES(-9.9999992052788183776e-1, 2.8963089153852134799e3)}, {FN (tanh), ARG(1.19209289550781250e-07,6.28284004019658492979e+00), RES(1.1920930376163652992e-7, -3.4526699672122013457e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,-6.28284004019658492979e+00), RES(1.1920930376163652992e-7, 3.4526699672122013457e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,6.28284004019658492979e+00), RES(-1.1920930376163652992e-7, -3.4526699672122013457e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,-6.28284004019658492979e+00), RES(-1.1920930376163652992e-7, 3.4526699672122013457e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,6.28353057416258753420e+00), RES(1.1920930376163652988e-7, 3.4526699672073027579e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,-6.28353057416258753420e+00), RES(1.1920930376163652988e-7, -3.4526699672073027579e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,6.28353057416258753420e+00), RES(-1.1920930376163652988e-7, 3.4526699672073027579e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,-6.28353057416258753420e+00), RES(-1.1920930376163652988e-7, -3.4526699672073027579e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,9.42443269378637893396e+00), RES(1.1920930376163652985e-7, -3.4526699672045442074e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,-9.42443269378637893396e+00), RES(1.1920930376163652985e-7, 3.4526699672045442074e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,9.42443269378637893396e+00), RES(-1.1920930376163652985e-7, -3.4526699672045442074e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-1.1920930376163652985e-7, 3.4526699672045442074e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,9.42512322775237976202e+00), RES(1.1920930376163652979e-7, 3.4526699671971963257e-4)}, {FN (tanh), ARG(1.19209289550781250e-07,-9.42512322775237976202e+00), RES(1.1920930376163652979e-7, -3.4526699671971963257e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,9.42512322775237976202e+00), RES(-1.1920930376163652979e-7, 3.4526699671971963257e-4)}, {FN (tanh), ARG(-1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-1.1920930376163652979e-7, -3.4526699671971963257e-4)}, {FN (tanh), ARG(5.0e-01,-3.45266983001243932001e-04), RES(4.6211720058436229979e-1, -2.7153443992655805934e-4)}, {FN (tanh), ARG(5.0e-01,3.45266983001243932001e-04), RES(4.6211720058436229979e-1, 2.7153443992655805934e-4)}, {FN (tanh), ARG(-5.0e-01,-3.45266983001243932001e-04), RES(-4.6211720058436229979e-1, -2.7153443992655805934e-4)}, {FN (tanh), ARG(-5.0e-01,3.45266983001243932001e-04), RES(-4.6211720058436229979e-1, 2.7153443992655805934e-4)}, {FN (tanh), ARG(5.0e-01,1.57045105981189525579e+00), RES(2.1639524637389325996e0, 1.2715121175455623363e-3)}, {FN (tanh), ARG(5.0e-01,-1.57045105981189525579e+00), RES(2.1639524637389325996e0, -1.2715121175455623363e-3)}, {FN (tanh), ARG(-5.0e-01,1.57045105981189525579e+00), RES(-2.1639524637389325996e0, 1.2715121175455623363e-3)}, {FN (tanh), ARG(-5.0e-01,-1.57045105981189525579e+00), RES(-2.1639524637389325996e0, -1.2715121175455623363e-3)}, {FN (tanh), ARG(5.0e-01,1.57114159377789786021e+00), RES(2.1639524637389326002e0, -1.2715121175451113370e-3)}, {FN (tanh), ARG(5.0e-01,-1.57114159377789786021e+00), RES(2.1639524637389326002e0, 1.2715121175451113370e-3)}, {FN (tanh), ARG(-5.0e-01,1.57114159377789786021e+00), RES(-2.1639524637389326002e0, -1.2715121175451113370e-3)}, {FN (tanh), ARG(-5.0e-01,-1.57114159377789786021e+00), RES(-2.1639524637389326002e0, 1.2715121175451113370e-3)}, {FN (tanh), ARG(5.0e-01,3.14124738660679181379e+00), RES(4.6211720058436229984e-1, -2.7153443992670020234e-4)}, {FN (tanh), ARG(5.0e-01,-3.14124738660679181379e+00), RES(4.6211720058436229984e-1, 2.7153443992670020234e-4)}, {FN (tanh), ARG(-5.0e-01,3.14124738660679181379e+00), RES(-4.6211720058436229984e-1, -2.7153443992670020234e-4)}, {FN (tanh), ARG(-5.0e-01,-3.14124738660679181379e+00), RES(-4.6211720058436229984e-1, 2.7153443992670020234e-4)}, {FN (tanh), ARG(5.0e-01,3.14193792057279441821e+00), RES(4.6211720058436229978e-1, 2.7153443992650757820e-4)}, {FN (tanh), ARG(5.0e-01,-3.14193792057279441821e+00), RES(4.6211720058436229978e-1, -2.7153443992650757820e-4)}, {FN (tanh), ARG(-5.0e-01,3.14193792057279441821e+00), RES(-4.6211720058436229978e-1, 2.7153443992650757820e-4)}, {FN (tanh), ARG(-5.0e-01,-3.14193792057279441821e+00), RES(-4.6211720058436229978e-1, -2.7153443992650757820e-4)}, {FN (tanh), ARG(5.0e-01,4.71204371340168837179e+00), RES(2.1639524637389325989e0, 1.2715121175460133355e-3)}, {FN (tanh), ARG(5.0e-01,-4.71204371340168837179e+00), RES(2.1639524637389325989e0, -1.2715121175460133355e-3)}, {FN (tanh), ARG(-5.0e-01,4.71204371340168837179e+00), RES(-2.1639524637389325989e0, 1.2715121175460133355e-3)}, {FN (tanh), ARG(-5.0e-01,-4.71204371340168837179e+00), RES(-2.1639524637389325989e0, -1.2715121175460133355e-3)}, {FN (tanh), ARG(5.0e-01,4.71273424736769097620e+00), RES(2.1639524637389326009e0, -1.2715121175446603377e-3)}, {FN (tanh), ARG(5.0e-01,-4.71273424736769097620e+00), RES(2.1639524637389326009e0, 1.2715121175446603377e-3)}, {FN (tanh), ARG(-5.0e-01,4.71273424736769097620e+00), RES(-2.1639524637389326009e0, -1.2715121175446603377e-3)}, {FN (tanh), ARG(-5.0e-01,-4.71273424736769097620e+00), RES(-2.1639524637389326009e0, 1.2715121175446603377e-3)}, {FN (tanh), ARG(5.0e-01,6.28284004019658492979e+00), RES(4.6211720058436229987e-1, -2.7153443992679651442e-4)}, {FN (tanh), ARG(5.0e-01,-6.28284004019658492979e+00), RES(4.6211720058436229987e-1, 2.7153443992679651442e-4)}, {FN (tanh), ARG(-5.0e-01,6.28284004019658492979e+00), RES(-4.6211720058436229987e-1, -2.7153443992679651442e-4)}, {FN (tanh), ARG(-5.0e-01,-6.28284004019658492979e+00), RES(-4.6211720058436229987e-1, 2.7153443992679651442e-4)}, {FN (tanh), ARG(5.0e-01,6.28353057416258753420e+00), RES(4.6211720058436229974e-1, 2.7153443992641126612e-4)}, {FN (tanh), ARG(5.0e-01,-6.28353057416258753420e+00), RES(4.6211720058436229974e-1, -2.7153443992641126612e-4)}, {FN (tanh), ARG(-5.0e-01,6.28353057416258753420e+00), RES(-4.6211720058436229974e-1, 2.7153443992641126612e-4)}, {FN (tanh), ARG(-5.0e-01,-6.28353057416258753420e+00), RES(-4.6211720058436229974e-1, -2.7153443992641126612e-4)}, {FN (tanh), ARG(5.0e-01,9.42443269378637893396e+00), RES(4.6211720058436229968e-1, -2.7153443992619432056e-4)}, {FN (tanh), ARG(5.0e-01,-9.42443269378637893396e+00), RES(4.6211720058436229968e-1, 2.7153443992619432056e-4)}, {FN (tanh), ARG(-5.0e-01,9.42443269378637893396e+00), RES(-4.6211720058436229968e-1, -2.7153443992619432056e-4)}, {FN (tanh), ARG(-5.0e-01,-9.42443269378637893396e+00), RES(-4.6211720058436229968e-1, 2.7153443992619432056e-4)}, {FN (tanh), ARG(5.0e-01,9.42512322775237976202e+00), RES(4.6211720058436229949e-1, 2.7153443992561644811e-4)}, {FN (tanh), ARG(5.0e-01,-9.42512322775237976202e+00), RES(4.6211720058436229949e-1, -2.7153443992561644811e-4)}, {FN (tanh), ARG(-5.0e-01,9.42512322775237976202e+00), RES(-4.6211720058436229949e-1, 2.7153443992561644811e-4)}, {FN (tanh), ARG(-5.0e-01,-9.42512322775237976202e+00), RES(-4.6211720058436229949e-1, -2.7153443992561644811e-4)}, {FN (tanh), ARG(1.0e+00,-3.45266983001243932001e-04), RES(7.6159419408485704836e-1, -1.4500326960274960880e-4)}, {FN (tanh), ARG(1.0e+00,3.45266983001243932001e-04), RES(7.6159419408485704836e-1, 1.4500326960274960880e-4)}, {FN (tanh), ARG(-1.0e+00,-3.45266983001243932001e-04), RES(-7.6159419408485704836e-1, -1.4500326960274960880e-4)}, {FN (tanh), ARG(-1.0e+00,3.45266983001243932001e-04), RES(-7.6159419408485704836e-1, 1.4500326960274960880e-4)}, {FN (tanh), ARG(1.0e+00,1.57045105981189525579e+00), RES(1.3130351721648674823e0, 2.4999454374276273814e-4)}, {FN (tanh), ARG(1.0e+00,-1.57045105981189525579e+00), RES(1.3130351721648674823e0, -2.4999454374276273814e-4)}, {FN (tanh), ARG(-1.0e+00,1.57045105981189525579e+00), RES(-1.3130351721648674823e0, 2.4999454374276273814e-4)}, {FN (tanh), ARG(-1.0e+00,-1.57045105981189525579e+00), RES(-1.3130351721648674823e0, -2.4999454374276273814e-4)}, {FN (tanh), ARG(1.0e+00,1.57114159377789786021e+00), RES(1.3130351721648674824e0, -2.4999454374267406620e-4)}, {FN (tanh), ARG(1.0e+00,-1.57114159377789786021e+00), RES(1.3130351721648674824e0, 2.4999454374267406620e-4)}, {FN (tanh), ARG(-1.0e+00,1.57114159377789786021e+00), RES(-1.3130351721648674824e0, -2.4999454374267406620e-4)}, {FN (tanh), ARG(-1.0e+00,-1.57114159377789786021e+00), RES(-1.3130351721648674824e0, 2.4999454374267406620e-4)}, {FN (tanh), ARG(1.0e+00,3.14124738660679181379e+00), RES(7.6159419408485704840e-1, -1.4500326960282551519e-4)}, {FN (tanh), ARG(1.0e+00,-3.14124738660679181379e+00), RES(7.6159419408485704840e-1, 1.4500326960282551519e-4)}, {FN (tanh), ARG(-1.0e+00,3.14124738660679181379e+00), RES(-7.6159419408485704840e-1, -1.4500326960282551519e-4)}, {FN (tanh), ARG(-1.0e+00,-3.14124738660679181379e+00), RES(-7.6159419408485704840e-1, 1.4500326960282551519e-4)}, {FN (tanh), ARG(1.0e+00,3.14193792057279441821e+00), RES(7.6159419408485704835e-1, 1.4500326960272265115e-4)}, {FN (tanh), ARG(1.0e+00,-3.14193792057279441821e+00), RES(7.6159419408485704835e-1, -1.4500326960272265115e-4)}, {FN (tanh), ARG(-1.0e+00,3.14193792057279441821e+00), RES(-7.6159419408485704835e-1, 1.4500326960272265115e-4)}, {FN (tanh), ARG(-1.0e+00,-3.14193792057279441821e+00), RES(-7.6159419408485704835e-1, -1.4500326960272265115e-4)}, {FN (tanh), ARG(1.0e+00,4.71204371340168837179e+00), RES(1.3130351721648674822e0, 2.4999454374285141007e-4)}, {FN (tanh), ARG(1.0e+00,-4.71204371340168837179e+00), RES(1.3130351721648674822e0, -2.4999454374285141007e-4)}, {FN (tanh), ARG(-1.0e+00,4.71204371340168837179e+00), RES(-1.3130351721648674822e0, 2.4999454374285141007e-4)}, {FN (tanh), ARG(-1.0e+00,-4.71204371340168837179e+00), RES(-1.3130351721648674822e0, -2.4999454374285141007e-4)}, {FN (tanh), ARG(1.0e+00,4.71273424736769097620e+00), RES(1.3130351721648674825e0, -2.4999454374258539427e-4)}, {FN (tanh), ARG(1.0e+00,-4.71273424736769097620e+00), RES(1.3130351721648674825e0, 2.4999454374258539427e-4)}, {FN (tanh), ARG(-1.0e+00,4.71273424736769097620e+00), RES(-1.3130351721648674825e0, -2.4999454374258539427e-4)}, {FN (tanh), ARG(-1.0e+00,-4.71273424736769097620e+00), RES(-1.3130351721648674825e0, 2.4999454374258539427e-4)}, {FN (tanh), ARG(1.0e+00,6.28284004019658492979e+00), RES(7.6159419408485704843e-1, -1.4500326960287694721e-4)}, {FN (tanh), ARG(1.0e+00,-6.28284004019658492979e+00), RES(7.6159419408485704843e-1, 1.4500326960287694721e-4)}, {FN (tanh), ARG(-1.0e+00,6.28284004019658492979e+00), RES(-7.6159419408485704843e-1, -1.4500326960287694721e-4)}, {FN (tanh), ARG(-1.0e+00,-6.28284004019658492979e+00), RES(-7.6159419408485704843e-1, 1.4500326960287694721e-4)}, {FN (tanh), ARG(1.0e+00,6.28353057416258753420e+00), RES(7.6159419408485704832e-1, 1.4500326960267121913e-4)}, {FN (tanh), ARG(1.0e+00,-6.28353057416258753420e+00), RES(7.6159419408485704832e-1, -1.4500326960267121913e-4)}, {FN (tanh), ARG(-1.0e+00,6.28353057416258753420e+00), RES(-7.6159419408485704832e-1, 1.4500326960267121913e-4)}, {FN (tanh), ARG(-1.0e+00,-6.28353057416258753420e+00), RES(-7.6159419408485704832e-1, -1.4500326960267121913e-4)}, {FN (tanh), ARG(1.0e+00,9.42443269378637893396e+00), RES(7.6159419408485704826e-1, -1.4500326960255536711e-4)}, {FN (tanh), ARG(1.0e+00,-9.42443269378637893396e+00), RES(7.6159419408485704826e-1, 1.4500326960255536711e-4)}, {FN (tanh), ARG(-1.0e+00,9.42443269378637893396e+00), RES(-7.6159419408485704826e-1, -1.4500326960255536711e-4)}, {FN (tanh), ARG(-1.0e+00,-9.42443269378637893396e+00), RES(-7.6159419408485704826e-1, 1.4500326960255536711e-4)}, {FN (tanh), ARG(1.0e+00,9.42512322775237976202e+00), RES(7.6159419408485704810e-1, 1.450032696022467750e-4)}, {FN (tanh), ARG(1.0e+00,-9.42512322775237976202e+00), RES(7.6159419408485704810e-1, -1.450032696022467750e-4)}, {FN (tanh), ARG(-1.0e+00,9.42512322775237976202e+00), RES(-7.6159419408485704810e-1, 1.450032696022467750e-4)}, {FN (tanh), ARG(-1.0e+00,-9.42512322775237976202e+00), RES(-7.6159419408485704810e-1, -1.450032696022467750e-4)}, {FN (tanh), ARG(2.0e+00,-3.45266983001243932001e-04), RES(9.6402758819508310556e-1, -2.4393395410435306874e-5)}, {FN (tanh), ARG(2.0e+00,3.45266983001243932001e-04), RES(9.6402758819508310556e-1, 2.4393395410435306874e-5)}, {FN (tanh), ARG(-2.0e+00,-3.45266983001243932001e-04), RES(-9.6402758819508310556e-1, -2.4393395410435306874e-5)}, {FN (tanh), ARG(-2.0e+00,3.45266983001243932001e-04), RES(-9.6402758819508310556e-1, 2.4393395410435306874e-5)}, {FN (tanh), ARG(2.0e+00,1.57045105981189525579e+00), RES(1.0373147113268752620e0, 2.6247825506572821595e-5)}, {FN (tanh), ARG(2.0e+00,-1.57045105981189525579e+00), RES(1.0373147113268752620e0, -2.6247825506572821595e-5)}, {FN (tanh), ARG(-2.0e+00,1.57045105981189525579e+00), RES(-1.0373147113268752620e0, 2.6247825506572821595e-5)}, {FN (tanh), ARG(-2.0e+00,-1.57045105981189525579e+00), RES(-1.0373147113268752620e0, -2.6247825506572821595e-5)}, {FN (tanh), ARG(2.0e+00,1.57114159377789786021e+00), RES(1.0373147113268752620e0, -2.6247825506563511609e-5)}, {FN (tanh), ARG(2.0e+00,-1.57114159377789786021e+00), RES(1.0373147113268752620e0, 2.6247825506563511609e-5)}, {FN (tanh), ARG(-2.0e+00,1.57114159377789786021e+00), RES(-1.0373147113268752620e0, -2.6247825506563511609e-5)}, {FN (tanh), ARG(-2.0e+00,-1.57114159377789786021e+00), RES(-1.0373147113268752620e0, 2.6247825506563511609e-5)}, {FN (tanh), ARG(2.0e+00,3.14124738660679181379e+00), RES(9.6402758819508310557e-1, -2.4393395410448076340e-5)}, {FN (tanh), ARG(2.0e+00,-3.14124738660679181379e+00), RES(9.6402758819508310557e-1, 2.4393395410448076340e-5)}, {FN (tanh), ARG(-2.0e+00,3.14124738660679181379e+00), RES(-9.6402758819508310557e-1, -2.4393395410448076340e-5)}, {FN (tanh), ARG(-2.0e+00,-3.14124738660679181379e+00), RES(-9.6402758819508310557e-1, 2.4393395410448076340e-5)}, {FN (tanh), ARG(2.0e+00,3.14193792057279441821e+00), RES(9.6402758819508310556e-1, 2.4393395410430771882e-5)}, {FN (tanh), ARG(2.0e+00,-3.14193792057279441821e+00), RES(9.6402758819508310556e-1, -2.4393395410430771882e-5)}, {FN (tanh), ARG(-2.0e+00,3.14193792057279441821e+00), RES(-9.6402758819508310556e-1, 2.4393395410430771882e-5)}, {FN (tanh), ARG(-2.0e+00,-3.14193792057279441821e+00), RES(-9.6402758819508310556e-1, -2.4393395410430771882e-5)}, {FN (tanh), ARG(2.0e+00,4.71204371340168837179e+00), RES(1.0373147113268752620e0, 2.6247825506582131582e-5)}, {FN (tanh), ARG(2.0e+00,-4.71204371340168837179e+00), RES(1.0373147113268752620e0, -2.6247825506582131582e-5)}, {FN (tanh), ARG(-2.0e+00,4.71204371340168837179e+00), RES(-1.0373147113268752620e0, 2.6247825506582131582e-5)}, {FN (tanh), ARG(-2.0e+00,-4.71204371340168837179e+00), RES(-1.0373147113268752620e0, -2.6247825506582131582e-5)}, {FN (tanh), ARG(2.0e+00,4.71273424736769097620e+00), RES(1.0373147113268752620e0, -2.6247825506554201622e-5)}, {FN (tanh), ARG(2.0e+00,-4.71273424736769097620e+00), RES(1.0373147113268752620e0, 2.6247825506554201622e-5)}, {FN (tanh), ARG(-2.0e+00,4.71273424736769097620e+00), RES(-1.0373147113268752620e0, -2.6247825506554201622e-5)}, {FN (tanh), ARG(-2.0e+00,-4.71273424736769097620e+00), RES(-1.0373147113268752620e0, 2.6247825506554201622e-5)}, {FN (tanh), ARG(2.0e+00,6.28284004019658492979e+00), RES(9.6402758819508310558e-1, -2.4393395410456728569e-5)}, {FN (tanh), ARG(2.0e+00,-6.28284004019658492979e+00), RES(9.6402758819508310558e-1, 2.4393395410456728569e-5)}, {FN (tanh), ARG(-2.0e+00,6.28284004019658492979e+00), RES(-9.6402758819508310558e-1, -2.4393395410456728569e-5)}, {FN (tanh), ARG(-2.0e+00,-6.28284004019658492979e+00), RES(-9.6402758819508310558e-1, 2.4393395410456728569e-5)}, {FN (tanh), ARG(2.0e+00,6.28353057416258753420e+00), RES(9.6402758819508310555e-1, 2.4393395410422119654e-5)}, {FN (tanh), ARG(2.0e+00,-6.28353057416258753420e+00), RES(9.6402758819508310555e-1, -2.4393395410422119654e-5)}, {FN (tanh), ARG(-2.0e+00,6.28353057416258753420e+00), RES(-9.6402758819508310555e-1, 2.4393395410422119654e-5)}, {FN (tanh), ARG(-2.0e+00,-6.28353057416258753420e+00), RES(-9.6402758819508310555e-1, -2.4393395410422119654e-5)}, {FN (tanh), ARG(2.0e+00,9.42443269378637893396e+00), RES(9.6402758819508310554e-1, -2.4393395410402630273e-5)}, {FN (tanh), ARG(2.0e+00,-9.42443269378637893396e+00), RES(9.6402758819508310554e-1, 2.4393395410402630273e-5)}, {FN (tanh), ARG(-2.0e+00,9.42443269378637893396e+00), RES(-9.6402758819508310554e-1, -2.4393395410402630273e-5)}, {FN (tanh), ARG(-2.0e+00,-9.42443269378637893396e+00), RES(-9.6402758819508310554e-1, 2.4393395410402630273e-5)}, {FN (tanh), ARG(2.0e+00,9.42512322775237976202e+00), RES(9.6402758819508310550e-1, 2.439339541035071690e-5)}, {FN (tanh), ARG(2.0e+00,-9.42512322775237976202e+00), RES(9.6402758819508310550e-1, -2.439339541035071690e-5)}, {FN (tanh), ARG(-2.0e+00,9.42512322775237976202e+00), RES(-9.6402758819508310550e-1, 2.439339541035071690e-5)}, {FN (tanh), ARG(-2.0e+00,-9.42512322775237976202e+00), RES(-9.6402758819508310550e-1, -2.439339541035071690e-5)}, {FN (arcsinh), ARG(0.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arcsinh), ARG(0.0e+00,1.19209289550781250e-07), RES(0, 1.1920928955078153234e-7)}, {FN (arcsinh), ARG(0.0e+00,-1.19209289550781250e-07), RES(0, -1.1920928955078153234e-7)}, {FN (arcsinh), ARG(0.0e+00,5.0e-01), RES(0, 5.2359877559829887308e-1)}, {FN (arcsinh), ARG(0.0e+00,-5.0e-01), RES(0, -5.2359877559829887308e-1)}, {FN (arcsinh), ARG(0.0e+00,1.0e+00), RES(0, 1.5707963267948966192e0)}, {FN (arcsinh), ARG(0.0e+00,-1.0e+00), RES(0, -1.5707963267948966192e0)}, {FN (arcsinh), ARG(0.0e+00,2.0e+00), RES(1.3169578969248167086e0, 1.5707963267948966192e0)}, {FN (arcsinh), ARG(0.0e+00,-2.0e+00), RES(-1.3169578969248167086e0, -1.5707963267948966192e0)}, {FN (arcsinh), ARG(0.0e+00,8.3886080e+06), RES(1.6635532333438683873e1, 1.5707963267948966192e0)}, {FN (arcsinh), ARG(0.0e+00,-8.3886080e+06), RES(-1.6635532333438683873e1, -1.5707963267948966192e0)}, {FN (arcsinh), ARG(1.19209289550781250e-07,0.0e+00), RES(1.1920928955078096766e-7, 0.0)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.1920928955078096766e-7, 0.0)}, {FN (arcsinh), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.1920928955078181469e-7, 1.1920928955078068531e-7)}, {FN (arcsinh), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.1920928955078181469e-7, -1.1920928955078068531e-7)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.1920928955078181469e-7, 1.1920928955078068531e-7)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.1920928955078181469e-7, -1.1920928955078068531e-7)}, {FN (arcsinh), ARG(1.19209289550781250e-07,5.0e-01), RES(1.3765103082409432364e-7, 5.2359877559829340332e-1)}, {FN (arcsinh), ARG(1.19209289550781250e-07,-5.0e-01), RES(1.3765103082409432364e-7, -5.2359877559829340332e-1)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,5.0e-01), RES(-1.3765103082409432364e-7, 5.2359877559829340332e-1)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-1.3765103082409432364e-7, -5.2359877559829340332e-1)}, {FN (arcsinh), ARG(1.19209289550781250e-07,1.0e+00), RES(3.4526698643116312881e-4, 1.5704510598153252947e0)}, {FN (arcsinh), ARG(1.19209289550781250e-07,-1.0e+00), RES(3.4526698643116312881e-4, -1.5704510598153252947e0)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,1.0e+00), RES(-3.4526698643116312881e-4, 1.5704510598153252947e0)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,-1.0e+00), RES(-3.4526698643116312881e-4, -1.5704510598153252947e0)}, {FN (arcsinh), ARG(1.19209289550781250e-07,2.0e+00), RES(1.3169578969248194435e0, 1.5707962579693812072e0)}, {FN (arcsinh), ARG(1.19209289550781250e-07,-2.0e+00), RES(1.3169578969248194435e0, -1.5707962579693812072e0)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,2.0e+00), RES(-1.3169578969248194435e0, 1.5707962579693812072e0)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,-2.0e+00), RES(-1.3169578969248194435e0, -1.5707962579693812072e0)}, {FN (arcsinh), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.6635532333438683873e1, 1.5707963267948824084e0)}, {FN (arcsinh), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.6635532333438683873e1, -1.5707963267948824084e0)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(-1.6635532333438683873e1, 1.5707963267948824084e0)}, {FN (arcsinh), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(-1.6635532333438683873e1, -1.5707963267948824084e0)}, {FN (arcsinh), ARG(5.0e-01,0.0e+00), RES(4.8121182505960344750e-1, 0.0)}, {FN (arcsinh), ARG(-5.0e-01,0.0e+00), RES(-4.8121182505960344750e-1, 0.0)}, {FN (arcsinh), ARG(5.0e-01,1.19209289550781250e-07), RES(4.8121182505960598961e-1, 1.0662402999400097805e-7)}, {FN (arcsinh), ARG(5.0e-01,-1.19209289550781250e-07), RES(4.8121182505960598961e-1, -1.0662402999400097805e-7)}, {FN (arcsinh), ARG(-5.0e-01,1.19209289550781250e-07), RES(-4.8121182505960598961e-1, 1.0662402999400097805e-7)}, {FN (arcsinh), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-4.8121182505960598961e-1, -1.0662402999400097805e-7)}, {FN (arcsinh), ARG(5.0e-01,5.0e-01), RES(5.3063753095251782602e-1, 4.5227844715119068206e-1)}, {FN (arcsinh), ARG(5.0e-01,-5.0e-01), RES(5.3063753095251782602e-1, -4.5227844715119068206e-1)}, {FN (arcsinh), ARG(-5.0e-01,5.0e-01), RES(-5.3063753095251782602e-1, 4.5227844715119068206e-1)}, {FN (arcsinh), ARG(-5.0e-01,-5.0e-01), RES(-5.3063753095251782602e-1, -4.5227844715119068206e-1)}, {FN (arcsinh), ARG(5.0e-01,1.0e+00), RES(7.3285767597364526089e-1, 8.9590748120889023907e-1)}, {FN (arcsinh), ARG(5.0e-01,-1.0e+00), RES(7.3285767597364526089e-1, -8.9590748120889023907e-1)}, {FN (arcsinh), ARG(-5.0e-01,1.0e+00), RES(-7.3285767597364526089e-1, 8.9590748120889023907e-1)}, {FN (arcsinh), ARG(-5.0e-01,-1.0e+00), RES(-7.3285767597364526089e-1, -8.9590748120889023907e-1)}, {FN (arcsinh), ARG(5.0e-01,2.0e+00), RES(1.3618009008578457882e0, 1.2930420702371826591e0)}, {FN (arcsinh), ARG(5.0e-01,-2.0e+00), RES(1.3618009008578457882e0, -1.2930420702371826591e0)}, {FN (arcsinh), ARG(-5.0e-01,2.0e+00), RES(-1.3618009008578457882e0, 1.2930420702371826591e0)}, {FN (arcsinh), ARG(-5.0e-01,-2.0e+00), RES(-1.3618009008578457882e0, -1.2930420702371826591e0)}, {FN (arcsinh), ARG(5.0e-01,8.3886080e+06), RES(1.6635532333438685650e1, 1.5707962671902518438e0)}, {FN (arcsinh), ARG(5.0e-01,-8.3886080e+06), RES(1.6635532333438685650e1, -1.5707962671902518438e0)}, {FN (arcsinh), ARG(-5.0e-01,8.3886080e+06), RES(-1.6635532333438685650e1, 1.5707962671902518438e0)}, {FN (arcsinh), ARG(-5.0e-01,-8.3886080e+06), RES(-1.6635532333438685650e1, -1.5707962671902518438e0)}, {FN (arcsinh), ARG(1.0e+00,0.0e+00), RES(8.8137358701954302523e-1, 0.0)}, {FN (arcsinh), ARG(-1.0e+00,0.0e+00), RES(-8.8137358701954302523e-1, 0.0)}, {FN (arcsinh), ARG(1.0e+00,1.19209289550781250e-07), RES(8.8137358701954553738e-1, 8.4293697021788013662e-8)}, {FN (arcsinh), ARG(1.0e+00,-1.19209289550781250e-07), RES(8.8137358701954553738e-1, -8.4293697021788013662e-8)}, {FN (arcsinh), ARG(-1.0e+00,1.19209289550781250e-07), RES(-8.8137358701954553738e-1, 8.4293697021788013662e-8)}, {FN (arcsinh), ARG(-1.0e+00,-1.19209289550781250e-07), RES(-8.8137358701954553738e-1, -8.4293697021788013662e-8)}, {FN (arcsinh), ARG(1.0e+00,5.0e-01), RES(9.2613303135018242455e-1, 3.4943906285721329363e-1)}, {FN (arcsinh), ARG(1.0e+00,-5.0e-01), RES(9.2613303135018242455e-1, -3.4943906285721329363e-1)}, {FN (arcsinh), ARG(-1.0e+00,5.0e-01), RES(-9.2613303135018242455e-1, 3.4943906285721329363e-1)}, {FN (arcsinh), ARG(-1.0e+00,-5.0e-01), RES(-9.2613303135018242455e-1, -3.4943906285721329363e-1)}, {FN (arcsinh), ARG(1.0e+00,1.0e+00), RES(1.0612750619050356520e0, 6.6623943249251525510e-1)}, {FN (arcsinh), ARG(1.0e+00,-1.0e+00), RES(1.0612750619050356520e0, -6.6623943249251525510e-1)}, {FN (arcsinh), ARG(-1.0e+00,1.0e+00), RES(-1.0612750619050356520e0, 6.6623943249251525510e-1)}, {FN (arcsinh), ARG(-1.0e+00,-1.0e+00), RES(-1.0612750619050356520e0, -6.6623943249251525510e-1)}, {FN (arcsinh), ARG(1.0e+00,2.0e+00), RES(1.4693517443681852733e0, 1.0634400235777520562e0)}, {FN (arcsinh), ARG(1.0e+00,-2.0e+00), RES(1.4693517443681852733e0, -1.0634400235777520562e0)}, {FN (arcsinh), ARG(-1.0e+00,2.0e+00), RES(-1.4693517443681852733e0, 1.0634400235777520562e0)}, {FN (arcsinh), ARG(-1.0e+00,-2.0e+00), RES(-1.4693517443681852733e0, -1.0634400235777520562e0)}, {FN (arcsinh), ARG(1.0e+00,8.3886080e+06), RES(1.6635532333438690979e1, 1.5707962075856070684e0)}, {FN (arcsinh), ARG(1.0e+00,-8.3886080e+06), RES(1.6635532333438690979e1, -1.5707962075856070684e0)}, {FN (arcsinh), ARG(-1.0e+00,8.3886080e+06), RES(-1.6635532333438690979e1, 1.5707962075856070684e0)}, {FN (arcsinh), ARG(-1.0e+00,-8.3886080e+06), RES(-1.6635532333438690979e1, -1.5707962075856070684e0)}, {FN (arcsinh), ARG(2.0e+00,0.0e+00), RES(1.4436354751788103425e0, 0.0)}, {FN (arcsinh), ARG(-2.0e+00,0.0e+00), RES(-1.4436354751788103425e0, 0.0)}, {FN (arcsinh), ARG(2.0e+00,1.19209289550781250e-07), RES(1.4436354751788116136e0, 5.3312014997000413263e-8)}, {FN (arcsinh), ARG(2.0e+00,-1.19209289550781250e-07), RES(1.4436354751788116136e0, -5.3312014997000413263e-8)}, {FN (arcsinh), ARG(-2.0e+00,1.19209289550781250e-07), RES(-1.4436354751788116136e0, 5.3312014997000413263e-8)}, {FN (arcsinh), ARG(-2.0e+00,-1.19209289550781250e-07), RES(-1.4436354751788116136e0, -5.3312014997000413263e-8)}, {FN (arcsinh), ARG(2.0e+00,5.0e-01), RES(1.4657153519472905218e0, 2.2101863562288385890e-1)}, {FN (arcsinh), ARG(2.0e+00,-5.0e-01), RES(1.4657153519472905218e0, -2.2101863562288385890e-1)}, {FN (arcsinh), ARG(-2.0e+00,5.0e-01), RES(-1.4657153519472905218e0, 2.2101863562288385890e-1)}, {FN (arcsinh), ARG(-2.0e+00,-5.0e-01), RES(-1.4657153519472905218e0, -2.2101863562288385890e-1)}, {FN (arcsinh), ARG(2.0e+00,1.0e+00), RES(1.5285709194809981613e0, 4.2707858639247612548e-1)}, {FN (arcsinh), ARG(2.0e+00,-1.0e+00), RES(1.5285709194809981613e0, -4.2707858639247612548e-1)}, {FN (arcsinh), ARG(-2.0e+00,1.0e+00), RES(-1.5285709194809981613e0, 4.2707858639247612548e-1)}, {FN (arcsinh), ARG(-2.0e+00,-1.0e+00), RES(-1.5285709194809981613e0, -4.2707858639247612548e-1)}, {FN (arcsinh), ARG(2.0e+00,2.0e+00), RES(1.7343245214879664480e0, 7.5424914469804604071e-1)}, {FN (arcsinh), ARG(2.0e+00,-2.0e+00), RES(1.7343245214879664480e0, -7.5424914469804604071e-1)}, {FN (arcsinh), ARG(-2.0e+00,2.0e+00), RES(-1.7343245214879664480e0, 7.5424914469804604071e-1)}, {FN (arcsinh), ARG(-2.0e+00,-2.0e+00), RES(-1.7343245214879664480e0, -7.5424914469804604071e-1)}, {FN (arcsinh), ARG(2.0e+00,8.3886080e+06), RES(1.6635532333438712295e1, 1.5707960883763175177e0)}, {FN (arcsinh), ARG(2.0e+00,-8.3886080e+06), RES(1.6635532333438712295e1, -1.5707960883763175177e0)}, {FN (arcsinh), ARG(-2.0e+00,8.3886080e+06), RES(-1.6635532333438712295e1, 1.5707960883763175177e0)}, {FN (arcsinh), ARG(-2.0e+00,-8.3886080e+06), RES(-1.6635532333438712295e1, -1.5707960883763175177e0)}, {FN (arcsinh), ARG(8.3886080e+06,0.0e+00), RES(1.6635532333438690979e1, 0.0)}, {FN (arcsinh), ARG(-8.3886080e+06,0.0e+00), RES(-1.6635532333438690979e1, 0.0)}, {FN (arcsinh), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.6635532333438690979e1, 1.4210854715201902743e-14)}, {FN (arcsinh), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.6635532333438690979e1, -1.4210854715201902743e-14)}, {FN (arcsinh), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(-1.6635532333438690979e1, 1.4210854715201902743e-14)}, {FN (arcsinh), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(-1.6635532333438690979e1, -1.4210854715201902743e-14)}, {FN (arcsinh), ARG(8.3886080e+06,5.0e-01), RES(1.6635532333438692755e1, 5.9604644775390130897e-8)}, {FN (arcsinh), ARG(8.3886080e+06,-5.0e-01), RES(1.6635532333438692755e1, -5.9604644775390130897e-8)}, {FN (arcsinh), ARG(-8.3886080e+06,5.0e-01), RES(-1.6635532333438692755e1, 5.9604644775390130897e-8)}, {FN (arcsinh), ARG(-8.3886080e+06,-5.0e-01), RES(-1.6635532333438692755e1, -5.9604644775390130897e-8)}, {FN (arcsinh), ARG(8.3886080e+06,1.0e+00), RES(1.6635532333438698084e1, 1.1920928955077983828e-7)}, {FN (arcsinh), ARG(8.3886080e+06,-1.0e+00), RES(1.6635532333438698084e1, -1.1920928955077983828e-7)}, {FN (arcsinh), ARG(-8.3886080e+06,1.0e+00), RES(-1.6635532333438698084e1, 1.1920928955077983828e-7)}, {FN (arcsinh), ARG(-8.3886080e+06,-1.0e+00), RES(-1.6635532333438698084e1, -1.1920928955077983828e-7)}, {FN (arcsinh), ARG(8.3886080e+06,2.0e+00), RES(1.663553233343871940e1, 2.3841857910155628843e-7)}, {FN (arcsinh), ARG(8.3886080e+06,-2.0e+00), RES(1.663553233343871940e1, -2.3841857910155628843e-7)}, {FN (arcsinh), ARG(-8.3886080e+06,2.0e+00), RES(-1.663553233343871940e1, 2.3841857910155628843e-7)}, {FN (arcsinh), ARG(-8.3886080e+06,-2.0e+00), RES(-1.663553233343871940e1, -2.3841857910155628843e-7)}, {FN (arcsinh), ARG(8.3886080e+06,8.3886080e+06), RES(1.6982105923718660081e1, 7.8539816339744653326e-1)}, {FN (arcsinh), ARG(8.3886080e+06,-8.3886080e+06), RES(1.6982105923718660081e1, -7.8539816339744653326e-1)}, {FN (arcsinh), ARG(-8.3886080e+06,8.3886080e+06), RES(-1.6982105923718660081e1, 7.8539816339744653326e-1)}, {FN (arcsinh), ARG(-8.3886080e+06,-8.3886080e+06), RES(-1.6982105923718660081e1, -7.8539816339744653326e-1)}, {FN (arccosh), ARG(0.0e+00,0.0e+00), RES(0, 1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,1.19209289550781250e-07), RES(1.1920928955078096766e-7, 1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,-1.19209289550781250e-07), RES(1.1920928955078096766e-7, -1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,5.0e-01), RES(4.8121182505960344750e-1, 1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,-5.0e-01), RES(4.8121182505960344750e-1, -1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,1.0e+00), RES(8.8137358701954302523e-1, 1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,-1.0e+00), RES(8.8137358701954302523e-1, -1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,2.0e+00), RES(1.4436354751788103425e0, 1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,-2.0e+00), RES(1.4436354751788103425e0, -1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,8.3886080e+06), RES(1.6635532333438690979e1, 1.5707963267948966192e0)}, {FN (arccosh), ARG(0.0e+00,-8.3886080e+06), RES(1.6635532333438690979e1, -1.5707963267948966192e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,0.0e+00), RES(0, 1.5707962075856070684e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,0.0e+00), RES(0, 1.570796446004186170e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.1920928955078181469e-7, 1.5707962075856070685e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.1920928955078181469e-7, -1.5707962075856070685e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(1.1920928955078181469e-7, 1.570796446004186170e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.1920928955078181469e-7, -1.570796446004186170e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,5.0e-01), RES(4.8121182505960598961e-1, 1.5707962201708666252e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,-5.0e-01), RES(4.8121182505960598961e-1, -1.5707962201708666252e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,5.0e-01), RES(4.8121182505960598961e-1, 1.5707964334189266132e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,-5.0e-01), RES(4.8121182505960598961e-1, -1.5707964334189266132e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,1.0e+00), RES(8.8137358701954553738e-1, 1.5707962425011995974e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,-1.0e+00), RES(8.8137358701954553738e-1, -1.5707962425011995974e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,1.0e+00), RES(8.8137358701954553738e-1, 1.5707964110885936410e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,-1.0e+00), RES(8.8137358701954553738e-1, -1.5707964110885936410e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,2.0e+00), RES(1.4436354751788116136e0, 1.5707962734828816222e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,-2.0e+00), RES(1.4436354751788116136e0, -1.5707962734828816222e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,2.0e+00), RES(1.4436354751788116136e0, 1.5707963801069116162e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,-2.0e+00), RES(1.4436354751788116136e0, -1.5707963801069116162e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.6635532333438690979e1, 1.5707963267948824084e0)}, {FN (arccosh), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.6635532333438690979e1, -1.5707963267948824084e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(1.6635532333438690979e1, 1.5707963267949108301e0)}, {FN (arccosh), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(1.6635532333438690979e1, -1.5707963267949108301e0)}, {FN (arccosh), ARG(5.0e-01,0.0e+00), RES(0, 1.0471975511965977462e0)}, {FN (arccosh), ARG(-5.0e-01,0.0e+00), RES(0, 2.0943951023931954923e0)}, {FN (arccosh), ARG(5.0e-01,1.19209289550781250e-07), RES(1.3765103082409432364e-7, 1.0471975511966032159e0)}, {FN (arccosh), ARG(5.0e-01,-1.19209289550781250e-07), RES(1.3765103082409432364e-7, -1.0471975511966032159e0)}, {FN (arccosh), ARG(-5.0e-01,1.19209289550781250e-07), RES(1.3765103082409432364e-7, 2.0943951023931900225e0)}, {FN (arccosh), ARG(-5.0e-01,-1.19209289550781250e-07), RES(1.3765103082409432364e-7, -2.0943951023931900225e0)}, {FN (arccosh), ARG(5.0e-01,5.0e-01), RES(5.3063753095251782602e-1, 1.1185178796437059372e0)}, {FN (arccosh), ARG(5.0e-01,-5.0e-01), RES(5.3063753095251782602e-1, -1.1185178796437059372e0)}, {FN (arccosh), ARG(-5.0e-01,5.0e-01), RES(5.3063753095251782602e-1, 2.0230747739460873013e0)}, {FN (arccosh), ARG(-5.0e-01,-5.0e-01), RES(5.3063753095251782602e-1, -2.0230747739460873013e0)}, {FN (arccosh), ARG(5.0e-01,1.0e+00), RES(9.2613303135018242455e-1, 1.2213572639376833256e0)}, {FN (arccosh), ARG(5.0e-01,-1.0e+00), RES(9.2613303135018242455e-1, -1.2213572639376833256e0)}, {FN (arccosh), ARG(-5.0e-01,1.0e+00), RES(9.2613303135018242455e-1, 1.9202353896521099129e0)}, {FN (arccosh), ARG(-5.0e-01,-1.0e+00), RES(9.2613303135018242455e-1, -1.9202353896521099129e0)}, {FN (arccosh), ARG(5.0e-01,2.0e+00), RES(1.4657153519472905218e0, 1.3497776911720127603e0)}, {FN (arccosh), ARG(5.0e-01,-2.0e+00), RES(1.4657153519472905218e0, -1.3497776911720127603e0)}, {FN (arccosh), ARG(-5.0e-01,2.0e+00), RES(1.4657153519472905218e0, 1.7918149624177804781e0)}, {FN (arccosh), ARG(-5.0e-01,-2.0e+00), RES(1.4657153519472905218e0, -1.7918149624177804781e0)}, {FN (arccosh), ARG(5.0e-01,8.3886080e+06), RES(1.6635532333438692755e1, 1.5707962671902518438e0)}, {FN (arccosh), ARG(5.0e-01,-8.3886080e+06), RES(1.6635532333438692755e1, -1.5707962671902518438e0)}, {FN (arccosh), ARG(-5.0e-01,8.3886080e+06), RES(1.6635532333438692755e1, 1.5707963863995413946e0)}, {FN (arccosh), ARG(-5.0e-01,-8.3886080e+06), RES(1.6635532333438692755e1, -1.5707963863995413946e0)}, {FN (arccosh), ARG(1.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arccosh), ARG(-1.0e+00,0.0e+00), RES(0, 3.1415926535897932385e0)}, {FN (arccosh), ARG(1.0e+00,1.19209289550781250e-07), RES(3.4526698643116312881e-4, 3.4526697957132450399e-4)}, {FN (arccosh), ARG(1.0e+00,-1.19209289550781250e-07), RES(3.4526698643116312881e-4, -3.4526697957132450399e-4)}, {FN (arccosh), ARG(-1.0e+00,1.19209289550781250e-07), RES(3.4526698643116312881e-4, 3.1412473866102219140e0)}, {FN (arccosh), ARG(-1.0e+00,-1.19209289550781250e-07), RES(3.4526698643116312881e-4, -3.1412473866102219140e0)}, {FN (arccosh), ARG(1.0e+00,5.0e-01), RES(7.3285767597364526089e-1, 6.7488884558600638016e-1)}, {FN (arccosh), ARG(1.0e+00,-5.0e-01), RES(7.3285767597364526089e-1, -6.7488884558600638016e-1)}, {FN (arccosh), ARG(-1.0e+00,5.0e-01), RES(7.3285767597364526089e-1, 2.4667038080037868583e0)}, {FN (arccosh), ARG(-1.0e+00,-5.0e-01), RES(7.3285767597364526089e-1, -2.4667038080037868583e0)}, {FN (arccosh), ARG(1.0e+00,1.0e+00), RES(1.0612750619050356520e0, 9.0455689430238136413e-1)}, {FN (arccosh), ARG(1.0e+00,-1.0e+00), RES(1.0612750619050356520e0, -9.0455689430238136413e-1)}, {FN (arccosh), ARG(-1.0e+00,1.0e+00), RES(1.0612750619050356520e0, 2.2370357592874118743e0)}, {FN (arccosh), ARG(-1.0e+00,-1.0e+00), RES(1.0612750619050356520e0, -2.2370357592874118743e0)}, {FN (arccosh), ARG(1.0e+00,2.0e+00), RES(1.5285709194809981613e0, 1.1437177404024204938e0)}, {FN (arccosh), ARG(1.0e+00,-2.0e+00), RES(1.5285709194809981613e0, -1.1437177404024204938e0)}, {FN (arccosh), ARG(-1.0e+00,2.0e+00), RES(1.5285709194809981613e0, 1.9978749131873727447e0)}, {FN (arccosh), ARG(-1.0e+00,-2.0e+00), RES(1.5285709194809981613e0, -1.9978749131873727447e0)}, {FN (arccosh), ARG(1.0e+00,8.3886080e+06), RES(1.6635532333438698084e1, 1.5707962075856070685e0)}, {FN (arccosh), ARG(1.0e+00,-8.3886080e+06), RES(1.6635532333438698084e1, -1.5707962075856070685e0)}, {FN (arccosh), ARG(-1.0e+00,8.3886080e+06), RES(1.6635532333438698084e1, 1.570796446004186170e0)}, {FN (arccosh), ARG(-1.0e+00,-8.3886080e+06), RES(1.6635532333438698084e1, -1.570796446004186170e0)}, {FN (arccosh), ARG(2.0e+00,0.0e+00), RES(1.3169578969248167086e0, 0.0)}, {FN (arccosh), ARG(-2.0e+00,0.0e+00), RES(1.3169578969248167086e0, 3.1415926535897932385e0)}, {FN (arccosh), ARG(2.0e+00,1.19209289550781250e-07), RES(1.3169578969248194435e0, 6.8825515412047433504e-8)}, {FN (arccosh), ARG(2.0e+00,-1.19209289550781250e-07), RES(1.3169578969248194435e0, -6.8825515412047433504e-8)}, {FN (arccosh), ARG(-2.0e+00,1.19209289550781250e-07), RES(1.3169578969248194435e0, 3.1415925847642778264e0)}, {FN (arccosh), ARG(-2.0e+00,-1.19209289550781250e-07), RES(1.3169578969248194435e0, -3.1415925847642778264e0)}, {FN (arccosh), ARG(2.0e+00,5.0e-01), RES(1.3618009008578457882e0, 2.7775425655771396018e-1)}, {FN (arccosh), ARG(2.0e+00,-5.0e-01), RES(1.3618009008578457882e0, -2.7775425655771396018e-1)}, {FN (arccosh), ARG(-2.0e+00,5.0e-01), RES(1.3618009008578457882e0, 2.8638383970320792783e0)}, {FN (arccosh), ARG(-2.0e+00,-5.0e-01), RES(1.3618009008578457882e0, -2.8638383970320792783e0)}, {FN (arccosh), ARG(2.0e+00,1.0e+00), RES(1.4693517443681852733e0, 5.0735630321714456304e-1)}, {FN (arccosh), ARG(2.0e+00,-1.0e+00), RES(1.4693517443681852733e0, -5.0735630321714456304e-1)}, {FN (arccosh), ARG(-2.0e+00,1.0e+00), RES(1.4693517443681852733e0, 2.6342363503726486754e0)}, {FN (arccosh), ARG(-2.0e+00,-1.0e+00), RES(1.4693517443681852733e0, -2.6342363503726486754e0)}, {FN (arccosh), ARG(2.0e+00,2.0e+00), RES(1.7343245214879664480e0, 8.1654718209685057852e-1)}, {FN (arccosh), ARG(2.0e+00,-2.0e+00), RES(1.7343245214879664480e0, -8.1654718209685057852e-1)}, {FN (arccosh), ARG(-2.0e+00,2.0e+00), RES(1.7343245214879664480e0, 2.3250454714929426599e0)}, {FN (arccosh), ARG(-2.0e+00,-2.0e+00), RES(1.7343245214879664480e0, -2.3250454714929426599e0)}, {FN (arccosh), ARG(2.0e+00,8.3886080e+06), RES(1.663553233343871940e1, 1.5707960883763175177e0)}, {FN (arccosh), ARG(2.0e+00,-8.3886080e+06), RES(1.663553233343871940e1, -1.5707960883763175177e0)}, {FN (arccosh), ARG(-2.0e+00,8.3886080e+06), RES(1.663553233343871940e1, 1.5707965652134757208e0)}, {FN (arccosh), ARG(-2.0e+00,-8.3886080e+06), RES(1.663553233343871940e1, -1.5707965652134757208e0)}, {FN (arccosh), ARG(8.3886080e+06,0.0e+00), RES(1.6635532333438683873e1, 0.0)}, {FN (arccosh), ARG(-8.3886080e+06,0.0e+00), RES(1.6635532333438683873e1, 3.1415926535897932385e0)}, {FN (arccosh), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.6635532333438683873e1, 1.4210854715202104692e-14)}, {FN (arccosh), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.6635532333438683873e1, -1.4210854715202104692e-14)}, {FN (arccosh), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(1.6635532333438683873e1, 3.1415926535897790276e0)}, {FN (arccosh), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(1.6635532333438683873e1, -3.1415926535897790276e0)}, {FN (arccosh), ARG(8.3886080e+06,5.0e-01), RES(1.6635532333438685650e1, 5.9604644775390977930e-8)}, {FN (arccosh), ARG(8.3886080e+06,-5.0e-01), RES(1.6635532333438685650e1, -5.9604644775390977930e-8)}, {FN (arccosh), ARG(-8.3886080e+06,5.0e-01), RES(1.6635532333438685650e1, 3.1415925939851484631e0)}, {FN (arccosh), ARG(-8.3886080e+06,-5.0e-01), RES(1.6635532333438685650e1, -3.1415925939851484631e0)}, {FN (arccosh), ARG(8.3886080e+06,1.0e+00), RES(1.6635532333438690979e1, 1.1920928955078153234e-7)}, {FN (arccosh), ARG(8.3886080e+06,-1.0e+00), RES(1.6635532333438690979e1, -1.1920928955078153234e-7)}, {FN (arccosh), ARG(-8.3886080e+06,1.0e+00), RES(1.6635532333438690979e1, 3.1415925343805036877e0)}, {FN (arccosh), ARG(-8.3886080e+06,-1.0e+00), RES(1.6635532333438690979e1, -3.1415925343805036877e0)}, {FN (arccosh), ARG(8.3886080e+06,2.0e+00), RES(1.6635532333438712295e1, 2.3841857910155967656e-7)}, {FN (arccosh), ARG(8.3886080e+06,-2.0e+00), RES(1.6635532333438712295e1, -2.3841857910155967656e-7)}, {FN (arccosh), ARG(-8.3886080e+06,2.0e+00), RES(1.6635532333438712295e1, 3.1415924151712141369e0)}, {FN (arccosh), ARG(-8.3886080e+06,-2.0e+00), RES(1.6635532333438712295e1, -3.1415924151712141369e0)}, {FN (arccosh), ARG(8.3886080e+06,8.3886080e+06), RES(1.6982105923718660081e1, 7.8539816339745008597e-1)}, {FN (arccosh), ARG(8.3886080e+06,-8.3886080e+06), RES(1.6982105923718660081e1, -7.8539816339745008597e-1)}, {FN (arccosh), ARG(-8.3886080e+06,8.3886080e+06), RES(1.6982105923718660081e1, 2.3561944901923431525e0)}, {FN (arccosh), ARG(-8.3886080e+06,-8.3886080e+06), RES(1.6982105923718660081e1, -2.3561944901923431525e0)}, {FN (arctanh), ARG(0.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arctanh), ARG(0.0e+00,1.19209289550781250e-07), RES(0, 1.1920928955078068531e-7)}, {FN (arctanh), ARG(0.0e+00,-1.19209289550781250e-07), RES(0, -1.1920928955078068531e-7)}, {FN (arctanh), ARG(0.0e+00,5.0e-01), RES(0, 4.6364760900080611621e-1)}, {FN (arctanh), ARG(0.0e+00,-5.0e-01), RES(0, -4.6364760900080611621e-1)}, {FN (arctanh), ARG(0.0e+00,1.0e+00), RES(0, 7.8539816339744830962e-1)}, {FN (arctanh), ARG(0.0e+00,-1.0e+00), RES(0, -7.8539816339744830962e-1)}, {FN (arctanh), ARG(0.0e+00,2.0e+00), RES(0, 1.1071487177940905030e0)}, {FN (arctanh), ARG(0.0e+00,-2.0e+00), RES(0, -1.1071487177940905030e0)}, {FN (arctanh), ARG(0.0e+00,8.3886080e+06), RES(0, 1.5707962075856070685e0)}, {FN (arctanh), ARG(0.0e+00,-8.3886080e+06), RES(0, -1.5707962075856070685e0)}, {FN (arctanh), ARG(1.19209289550781250e-07,0.0e+00), RES(1.1920928955078181469e-7, 0.0)}, {FN (arctanh), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.1920928955078181469e-7, 0.0)}, {FN (arctanh), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.1920928955078012062e-7, 1.1920928955078237938e-7)}, {FN (arctanh), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.1920928955078012062e-7, -1.1920928955078237938e-7)}, {FN (arctanh), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.1920928955078012062e-7, 1.1920928955078237938e-7)}, {FN (arctanh), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.1920928955078012062e-7, -1.1920928955078237938e-7)}, {FN (arctanh), ARG(1.19209289550781250e-07,5.0e-01), RES(9.5367431640625072280e-8, 4.6364760900081066369e-1)}, {FN (arctanh), ARG(1.19209289550781250e-07,-5.0e-01), RES(9.5367431640625072280e-8, -4.6364760900081066369e-1)}, {FN (arctanh), ARG(-1.19209289550781250e-07,5.0e-01), RES(-9.5367431640625072280e-8, 4.6364760900081066369e-1)}, {FN (arctanh), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-9.5367431640625072280e-8, -4.6364760900081066369e-1)}, {FN (arctanh), ARG(1.19209289550781250e-07,1.0e+00), RES(5.9604644775390483828e-8, 7.8539816339745186233e-1)}, {FN (arctanh), ARG(1.19209289550781250e-07,-1.0e+00), RES(5.9604644775390483828e-8, -7.8539816339745186233e-1)}, {FN (arctanh), ARG(-1.19209289550781250e-07,1.0e+00), RES(-5.9604644775390483828e-8, 7.8539816339745186233e-1)}, {FN (arctanh), ARG(-1.19209289550781250e-07,-1.0e+00), RES(-5.9604644775390483828e-8, -7.8539816339745186233e-1)}, {FN (arctanh), ARG(1.19209289550781250e-07,2.0e+00), RES(2.3841857910156200307e-8, 1.1071487177940916399e0)}, {FN (arctanh), ARG(1.19209289550781250e-07,-2.0e+00), RES(2.3841857910156200307e-8, -1.1071487177940916399e0)}, {FN (arctanh), ARG(-1.19209289550781250e-07,2.0e+00), RES(-2.3841857910156200307e-8, 1.1071487177940916399e0)}, {FN (arctanh), ARG(-1.19209289550781250e-07,-2.0e+00), RES(-2.3841857910156200307e-8, -1.1071487177940916399e0)}, {FN (arctanh), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.6940658945085766040e-21, 1.5707962075856070685e0)}, {FN (arctanh), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.6940658945085766040e-21, -1.5707962075856070685e0)}, {FN (arctanh), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(-1.6940658945085766040e-21, 1.5707962075856070685e0)}, {FN (arctanh), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(-1.6940658945085766040e-21, -1.5707962075856070685e0)}, {FN (arctanh), ARG(5.0e-01,0.0e+00), RES(5.4930614433405484570e-1, 0.0)}, {FN (arctanh), ARG(-5.0e-01,0.0e+00), RES(-5.4930614433405484570e-1, 0.0)}, {FN (arctanh), ARG(5.0e-01,1.19209289550781250e-07), RES(5.4930614433404221383e-1, 1.5894571940103932425e-7)}, {FN (arctanh), ARG(5.0e-01,-1.19209289550781250e-07), RES(5.4930614433404221383e-1, -1.5894571940103932425e-7)}, {FN (arctanh), ARG(-5.0e-01,1.19209289550781250e-07), RES(-5.4930614433404221383e-1, 1.5894571940103932425e-7)}, {FN (arctanh), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-5.4930614433404221383e-1, -1.5894571940103932425e-7)}, {FN (arctanh), ARG(5.0e-01,5.0e-01), RES(4.0235947810852509365e-1, 5.5357435889704525151e-1)}, {FN (arctanh), ARG(5.0e-01,-5.0e-01), RES(4.0235947810852509365e-1, -5.5357435889704525151e-1)}, {FN (arctanh), ARG(-5.0e-01,5.0e-01), RES(-4.0235947810852509365e-1, 5.5357435889704525151e-1)}, {FN (arctanh), ARG(-5.0e-01,-5.0e-01), RES(-4.0235947810852509365e-1, -5.5357435889704525151e-1)}, {FN (arctanh), ARG(5.0e-01,1.0e+00), RES(2.3887786125685909036e-1, 8.4757566067082902713e-1)}, {FN (arctanh), ARG(5.0e-01,-1.0e+00), RES(2.3887786125685909036e-1, -8.4757566067082902713e-1)}, {FN (arctanh), ARG(-5.0e-01,1.0e+00), RES(-2.3887786125685909036e-1, 8.4757566067082902713e-1)}, {FN (arctanh), ARG(-5.0e-01,-1.0e+00), RES(-2.3887786125685909036e-1, -8.4757566067082902713e-1)}, {FN (arctanh), ARG(5.0e-01,2.0e+00), RES(9.6415620202996167238e-2, 1.1265564408348223487e0)}, {FN (arctanh), ARG(5.0e-01,-2.0e+00), RES(9.6415620202996167238e-2, -1.1265564408348223487e0)}, {FN (arctanh), ARG(-5.0e-01,2.0e+00), RES(-9.6415620202996167238e-2, 1.1265564408348223487e0)}, {FN (arctanh), ARG(-5.0e-01,-2.0e+00), RES(-9.6415620202996167238e-2, -1.1265564408348223487e0)}, {FN (arctanh), ARG(5.0e-01,8.3886080e+06), RES(7.1054273576008756410e-15, 1.5707962075856070685e0)}, {FN (arctanh), ARG(5.0e-01,-8.3886080e+06), RES(7.1054273576008756410e-15, -1.5707962075856070685e0)}, {FN (arctanh), ARG(-5.0e-01,8.3886080e+06), RES(-7.1054273576008756410e-15, 1.5707962075856070685e0)}, {FN (arctanh), ARG(-5.0e-01,-8.3886080e+06), RES(-7.1054273576008756410e-15, -1.5707962075856070685e0)}, {FN (arctanh), ARG(1.0e+00,1.19209289550781250e-07), RES(8.3177661667193446012e0, 7.8539819319977069731e-1)}, {FN (arctanh), ARG(1.0e+00,-1.19209289550781250e-07), RES(8.3177661667193446012e0, -7.8539819319977069731e-1)}, {FN (arctanh), ARG(-1.0e+00,1.19209289550781250e-07), RES(-8.3177661667193446012e0, 7.8539819319977069731e-1)}, {FN (arctanh), ARG(-1.0e+00,-1.19209289550781250e-07), RES(-8.3177661667193446012e0, -7.8539819319977069731e-1)}, {FN (arctanh), ARG(1.0e+00,5.0e-01), RES(7.0830333601405402006e-1, 9.0788749496088038670e-1)}, {FN (arctanh), ARG(1.0e+00,-5.0e-01), RES(7.0830333601405402006e-1, -9.0788749496088038670e-1)}, {FN (arctanh), ARG(-1.0e+00,5.0e-01), RES(-7.0830333601405402006e-1, 9.0788749496088038670e-1)}, {FN (arctanh), ARG(-1.0e+00,-5.0e-01), RES(-7.0830333601405402006e-1, -9.0788749496088038670e-1)}, {FN (arctanh), ARG(1.0e+00,1.0e+00), RES(4.0235947810852509365e-1, 1.0172219678978513677e0)}, {FN (arctanh), ARG(1.0e+00,-1.0e+00), RES(4.0235947810852509365e-1, -1.0172219678978513677e0)}, {FN (arctanh), ARG(-1.0e+00,1.0e+00), RES(-4.0235947810852509365e-1, 1.0172219678978513677e0)}, {FN (arctanh), ARG(-1.0e+00,-1.0e+00), RES(-4.0235947810852509365e-1, -1.0172219678978513677e0)}, {FN (arctanh), ARG(1.0e+00,2.0e+00), RES(1.7328679513998632735e-1, 1.1780972450961724644e0)}, {FN (arctanh), ARG(1.0e+00,-2.0e+00), RES(1.7328679513998632735e-1, -1.1780972450961724644e0)}, {FN (arctanh), ARG(-1.0e+00,2.0e+00), RES(-1.7328679513998632735e-1, 1.1780972450961724644e0)}, {FN (arctanh), ARG(-1.0e+00,-2.0e+00), RES(-1.7328679513998632735e-1, -1.1780972450961724644e0)}, {FN (arctanh), ARG(1.0e+00,8.3886080e+06), RES(1.4210854715201599821e-14, 1.5707962075856070685e0)}, {FN (arctanh), ARG(1.0e+00,-8.3886080e+06), RES(1.4210854715201599821e-14, -1.5707962075856070685e0)}, {FN (arctanh), ARG(-1.0e+00,8.3886080e+06), RES(-1.4210854715201599821e-14, 1.5707962075856070685e0)}, {FN (arctanh), ARG(-1.0e+00,-8.3886080e+06), RES(-1.4210854715201599821e-14, -1.5707962075856070685e0)}, {FN (arctanh), ARG(2.0e+00,0.0e+00), RES(5.4930614433405484570e-1, -1.5707963267948966192e0)}, {FN (arctanh), ARG(-2.0e+00,0.0e+00), RES(-5.4930614433405484570e-1, 1.5707963267948966192e0)}, {FN (arctanh), ARG(2.0e+00,1.19209289550781250e-07), RES(5.4930614433405168773e-1, 1.5707962870584667690e0)}, {FN (arctanh), ARG(2.0e+00,-1.19209289550781250e-07), RES(5.4930614433405168773e-1, -1.5707962870584667690e0)}, {FN (arctanh), ARG(-2.0e+00,1.19209289550781250e-07), RES(-5.4930614433405168773e-1, 1.5707962870584667690e0)}, {FN (arctanh), ARG(-2.0e+00,-1.19209289550781250e-07), RES(-5.4930614433405168773e-1, -1.5707962870584667690e0)}, {FN (arctanh), ARG(2.0e+00,5.0e-01), RES(5.0037000005253101744e-1, 1.4215468610018069803e0)}, {FN (arctanh), ARG(2.0e+00,-5.0e-01), RES(5.0037000005253101744e-1, -1.4215468610018069803e0)}, {FN (arctanh), ARG(-2.0e+00,5.0e-01), RES(-5.0037000005253101744e-1, 1.4215468610018069803e0)}, {FN (arctanh), ARG(-2.0e+00,-5.0e-01), RES(-5.0037000005253101744e-1, -1.4215468610018069803e0)}, {FN (arctanh), ARG(2.0e+00,1.0e+00), RES(4.0235947810852509365e-1, 1.3389725222944935611e0)}, {FN (arctanh), ARG(2.0e+00,-1.0e+00), RES(4.0235947810852509365e-1, -1.3389725222944935611e0)}, {FN (arctanh), ARG(-2.0e+00,1.0e+00), RES(-4.0235947810852509365e-1, 1.3389725222944935611e0)}, {FN (arctanh), ARG(-2.0e+00,-1.0e+00), RES(-4.0235947810852509365e-1, -1.3389725222944935611e0)}, {FN (arctanh), ARG(2.0e+00,2.0e+00), RES(2.3887786125685909036e-1, 1.3112232696716351433e0)}, {FN (arctanh), ARG(2.0e+00,-2.0e+00), RES(2.3887786125685909036e-1, -1.3112232696716351433e0)}, {FN (arctanh), ARG(-2.0e+00,2.0e+00), RES(-2.3887786125685909036e-1, 1.3112232696716351433e0)}, {FN (arctanh), ARG(-2.0e+00,-2.0e+00), RES(-2.3887786125685909036e-1, -1.3112232696716351433e0)}, {FN (arctanh), ARG(2.0e+00,8.3886080e+06), RES(2.8421709430401987951e-14, 1.5707962075856070685e0)}, {FN (arctanh), ARG(2.0e+00,-8.3886080e+06), RES(2.8421709430401987951e-14, -1.5707962075856070685e0)}, {FN (arctanh), ARG(-2.0e+00,8.3886080e+06), RES(-2.8421709430401987951e-14, 1.5707962075856070685e0)}, {FN (arctanh), ARG(-2.0e+00,-8.3886080e+06), RES(-2.8421709430401987951e-14, -1.5707962075856070685e0)}, {FN (arctanh), ARG(8.3886080e+06,0.0e+00), RES(1.1920928955078181469e-7, -1.5707963267948966192e0)}, {FN (arctanh), ARG(-8.3886080e+06,0.0e+00), RES(-1.1920928955078181469e-7, 1.5707963267948966192e0)}, {FN (arctanh), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.1920928955078181469e-7, 1.5707963267948966192e0)}, {FN (arctanh), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.1920928955078181469e-7, -1.5707963267948966192e0)}, {FN (arctanh), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(-1.1920928955078181469e-7, 1.5707963267948966192e0)}, {FN (arctanh), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(-1.1920928955078181469e-7, -1.5707963267948966192e0)}, {FN (arctanh), ARG(8.3886080e+06,5.0e-01), RES(1.1920928955078139117e-7, 1.5707963267948895138e0)}, {FN (arctanh), ARG(8.3886080e+06,-5.0e-01), RES(1.1920928955078139117e-7, -1.5707963267948895138e0)}, {FN (arctanh), ARG(-8.3886080e+06,5.0e-01), RES(-1.1920928955078139117e-7, 1.5707963267948895138e0)}, {FN (arctanh), ARG(-8.3886080e+06,-5.0e-01), RES(-1.1920928955078139117e-7, -1.5707963267948895138e0)}, {FN (arctanh), ARG(8.3886080e+06,1.0e+00), RES(1.1920928955078012062e-7, 1.5707963267948824084e0)}, {FN (arctanh), ARG(8.3886080e+06,-1.0e+00), RES(1.1920928955078012062e-7, -1.5707963267948824084e0)}, {FN (arctanh), ARG(-8.3886080e+06,1.0e+00), RES(-1.1920928955078012062e-7, 1.5707963267948824084e0)}, {FN (arctanh), ARG(-8.3886080e+06,-1.0e+00), RES(-1.1920928955078012062e-7, -1.5707963267948824084e0)}, {FN (arctanh), ARG(8.3886080e+06,2.0e+00), RES(1.1920928955077503843e-7, 1.5707963267948681975e0)}, {FN (arctanh), ARG(8.3886080e+06,-2.0e+00), RES(1.1920928955077503843e-7, -1.5707963267948681975e0)}, {FN (arctanh), ARG(-8.3886080e+06,2.0e+00), RES(-1.1920928955077503843e-7, 1.5707963267948681975e0)}, {FN (arctanh), ARG(-8.3886080e+06,-2.0e+00), RES(-1.1920928955077503843e-7, -1.5707963267948681975e0)}, {FN (arctanh), ARG(8.3886080e+06,8.3886080e+06), RES(5.9604644775390483828e-8, 1.5707962671902518438e0)}, {FN (arctanh), ARG(8.3886080e+06,-8.3886080e+06), RES(5.9604644775390483828e-8, -1.5707962671902518438e0)}, {FN (arctanh), ARG(-8.3886080e+06,8.3886080e+06), RES(-5.9604644775390483828e-8, 1.5707962671902518438e0)}, {FN (arctanh), ARG(-8.3886080e+06,-8.3886080e+06), RES(-5.9604644775390483828e-8, -1.5707962671902518438e0)}, {FN (csc), ARG(-3.45266983001243932001e-04,0.0e+00), RES(-2.8963094332845964291e3, 0.0)}, {FN (csc), ARG(3.45266983001243932001e-04,0.0e+00), RES(2.8963094332845964291e3, 0.0)}, {FN (csc), ARG(-3.45266983001243932001e-04,1.19209289550781250e-07), RES(-2.8963090880176545869e3, -9.9999986092250876926e-1)}, {FN (csc), ARG(-3.45266983001243932001e-04,-1.19209289550781250e-07), RES(-2.8963090880176545869e3, 9.9999986092250876926e-1)}, {FN (csc), ARG(3.45266983001243932001e-04,1.19209289550781250e-07), RES(2.8963090880176545869e3, -9.9999986092250876926e-1)}, {FN (csc), ARG(3.45266983001243932001e-04,-1.19209289550781250e-07), RES(2.8963090880176545869e3, 9.9999986092250876926e-1)}, {FN (csc), ARG(-3.45266983001243932001e-04,5.0e-01), RES(-1.4337901642789801243e-3, -1.9190337944739187237e0)}, {FN (csc), ARG(-3.45266983001243932001e-04,-5.0e-01), RES(-1.4337901642789801243e-3, 1.9190337944739187237e0)}, {FN (csc), ARG(3.45266983001243932001e-04,5.0e-01), RES(1.4337901642789801243e-3, -1.9190337944739187237e0)}, {FN (csc), ARG(3.45266983001243932001e-04,-5.0e-01), RES(1.4337901642789801243e-3, 1.9190337944739187237e0)}, {FN (csc), ARG(-3.45266983001243932001e-04,1.0e+00), RES(-3.8576176225198860914e-4, -8.5091800407377002734e-1)}, {FN (csc), ARG(-3.45266983001243932001e-04,-1.0e+00), RES(-3.8576176225198860914e-4, 8.5091800407377002734e-1)}, {FN (csc), ARG(3.45266983001243932001e-04,1.0e+00), RES(3.8576176225198860914e-4, -8.5091800407377002734e-1)}, {FN (csc), ARG(3.45266983001243932001e-04,-1.0e+00), RES(3.8576176225198860914e-4, 8.5091800407377002734e-1)}, {FN (csc), ARG(-3.45266983001243932001e-04,2.0e+00), RES(-9.8749461907035665386e-5, -2.7572054583883740768e-1)}, {FN (csc), ARG(-3.45266983001243932001e-04,-2.0e+00), RES(-9.8749461907035665386e-5, 2.7572054583883740768e-1)}, {FN (csc), ARG(3.45266983001243932001e-04,2.0e+00), RES(9.8749461907035665386e-5, -2.7572054583883740768e-1)}, {FN (csc), ARG(3.45266983001243932001e-04,-2.0e+00), RES(9.8749461907035665386e-5, 2.7572054583883740768e-1)}, {FN (csc), ARG(1.57045105981189525579e+00,0.0e+00), RES(1.0000000596046477360e0, 0.0)}, {FN (csc), ARG(-1.57045105981189525579e+00,0.0e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (csc), ARG(1.57045105981189525579e+00,1.19209289550781250e-07), RES(1.0000000596046406306e0, -4.1159035837716456618e-11)}, {FN (csc), ARG(1.57045105981189525579e+00,-1.19209289550781250e-07), RES(1.0000000596046406306e0, 4.1159035837716456618e-11)}, {FN (csc), ARG(-1.57045105981189525579e+00,1.19209289550781250e-07), RES(-1.0000000596046406306e0, -4.1159035837716456618e-11)}, {FN (csc), ARG(-1.57045105981189525579e+00,-1.19209289550781250e-07), RES(-1.0000000596046406306e0, 4.1159035837716456618e-11)}, {FN (csc), ARG(1.57045105981189525579e+00,5.0e-01), RES(8.8681891425248302487e-1, -1.4149533035943115868e-4)}, {FN (csc), ARG(1.57045105981189525579e+00,-5.0e-01), RES(8.8681891425248302487e-1, 1.4149533035943115868e-4)}, {FN (csc), ARG(-1.57045105981189525579e+00,5.0e-01), RES(-8.8681891425248302487e-1, -1.4149533035943115868e-4)}, {FN (csc), ARG(-1.57045105981189525579e+00,-5.0e-01), RES(-8.8681891425248302487e-1, 1.4149533035943115868e-4)}, {FN (csc), ARG(1.57045105981189525579e+00,1.0e+00), RES(6.4805426748157480499e-1, -1.7040802567657401279e-4)}, {FN (csc), ARG(1.57045105981189525579e+00,-1.0e+00), RES(6.4805426748157480499e-1, 1.7040802567657401279e-4)}, {FN (csc), ARG(-1.57045105981189525579e+00,1.0e+00), RES(-6.4805426748157480499e-1, -1.7040802567657401279e-4)}, {FN (csc), ARG(-1.57045105981189525579e+00,-1.0e+00), RES(-6.4805426748157480499e-1, 1.7040802567657401279e-4)}, {FN (csc), ARG(1.57045105981189525579e+00,2.0e+00), RES(2.6580221522968095406e-1, -8.8471445300404633228e-5)}, {FN (csc), ARG(1.57045105981189525579e+00,-2.0e+00), RES(2.6580221522968095406e-1, 8.8471445300404633228e-5)}, {FN (csc), ARG(-1.57045105981189525579e+00,2.0e+00), RES(-2.6580221522968095406e-1, -8.8471445300404633228e-5)}, {FN (csc), ARG(-1.57045105981189525579e+00,-2.0e+00), RES(-2.6580221522968095406e-1, 8.8471445300404633228e-5)}, {FN (csc), ARG(1.57114159377789786021e+00,0.0e+00), RES(1.0000000596046477360e0, 0.0)}, {FN (csc), ARG(-1.57114159377789786021e+00,0.0e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (csc), ARG(1.57114159377789786021e+00,1.19209289550781250e-07), RES(1.0000000596046406306e0, 4.1159035837701857686e-11)}, {FN (csc), ARG(1.57114159377789786021e+00,-1.19209289550781250e-07), RES(1.0000000596046406306e0, -4.1159035837701857686e-11)}, {FN (csc), ARG(-1.57114159377789786021e+00,1.19209289550781250e-07), RES(-1.0000000596046406306e0, 4.1159035837701857686e-11)}, {FN (csc), ARG(-1.57114159377789786021e+00,-1.19209289550781250e-07), RES(-1.0000000596046406306e0, -4.1159035837701857686e-11)}, {FN (csc), ARG(1.57114159377789786021e+00,5.0e-01), RES(8.8681891425248302485e-1, 1.4149533035938097090e-4)}, {FN (csc), ARG(1.57114159377789786021e+00,-5.0e-01), RES(8.8681891425248302485e-1, -1.4149533035938097090e-4)}, {FN (csc), ARG(-1.57114159377789786021e+00,5.0e-01), RES(-8.8681891425248302485e-1, 1.4149533035938097090e-4)}, {FN (csc), ARG(-1.57114159377789786021e+00,-5.0e-01), RES(-8.8681891425248302485e-1, -1.4149533035938097090e-4)}, {FN (csc), ARG(1.57114159377789786021e+00,1.0e+00), RES(6.4805426748157480499e-1, 1.7040802567651356981e-4)}, {FN (csc), ARG(1.57114159377789786021e+00,-1.0e+00), RES(6.4805426748157480499e-1, -1.7040802567651356981e-4)}, {FN (csc), ARG(-1.57114159377789786021e+00,1.0e+00), RES(-6.4805426748157480499e-1, 1.7040802567651356981e-4)}, {FN (csc), ARG(-1.57114159377789786021e+00,-1.0e+00), RES(-6.4805426748157480499e-1, -1.7040802567651356981e-4)}, {FN (csc), ARG(1.57114159377789786021e+00,2.0e+00), RES(2.6580221522968095407e-1, 8.8471445300373252796e-5)}, {FN (csc), ARG(1.57114159377789786021e+00,-2.0e+00), RES(2.6580221522968095407e-1, -8.8471445300373252796e-5)}, {FN (csc), ARG(-1.57114159377789786021e+00,2.0e+00), RES(-2.6580221522968095407e-1, 8.8471445300373252796e-5)}, {FN (csc), ARG(-1.57114159377789786021e+00,-2.0e+00), RES(-2.6580221522968095407e-1, -8.8471445300373252796e-5)}, {FN (csc), ARG(3.14124738660679181379e+00,0.0e+00), RES(2.8963094332830802676e3, 0.0)}, {FN (csc), ARG(-3.14124738660679181379e+00,0.0e+00), RES(-2.8963094332830802676e3, 0.0)}, {FN (csc), ARG(3.14124738660679181379e+00,1.19209289550781250e-07), RES(2.8963090880161384259e3, 9.9999986092146180843e-1)}, {FN (csc), ARG(3.14124738660679181379e+00,-1.19209289550781250e-07), RES(2.8963090880161384259e3, -9.9999986092146180843e-1)}, {FN (csc), ARG(-3.14124738660679181379e+00,1.19209289550781250e-07), RES(-2.8963090880161384259e3, 9.9999986092146180843e-1)}, {FN (csc), ARG(-3.14124738660679181379e+00,-1.19209289550781250e-07), RES(-2.8963090880161384259e3, -9.9999986092146180843e-1)}, {FN (csc), ARG(3.14124738660679181379e+00,5.0e-01), RES(1.4337901642797306848e-3, 1.9190337944739187227e0)}, {FN (csc), ARG(3.14124738660679181379e+00,-5.0e-01), RES(1.4337901642797306848e-3, -1.9190337944739187227e0)}, {FN (csc), ARG(-3.14124738660679181379e+00,5.0e-01), RES(-1.4337901642797306848e-3, 1.9190337944739187227e0)}, {FN (csc), ARG(-3.14124738660679181379e+00,-5.0e-01), RES(-1.4337901642797306848e-3, -1.9190337944739187227e0)}, {FN (csc), ARG(3.14124738660679181379e+00,1.0e+00), RES(3.8576176225219054787e-4, 8.5091800407377002721e-1)}, {FN (csc), ARG(3.14124738660679181379e+00,-1.0e+00), RES(3.8576176225219054787e-4, -8.5091800407377002721e-1)}, {FN (csc), ARG(-3.14124738660679181379e+00,1.0e+00), RES(-3.8576176225219054787e-4, 8.5091800407377002721e-1)}, {FN (csc), ARG(-3.14124738660679181379e+00,-1.0e+00), RES(-3.8576176225219054787e-4, -8.5091800407377002721e-1)}, {FN (csc), ARG(3.14124738660679181379e+00,2.0e+00), RES(9.8749461907087358805e-5, 2.7572054583883740766e-1)}, {FN (csc), ARG(3.14124738660679181379e+00,-2.0e+00), RES(9.8749461907087358805e-5, -2.7572054583883740766e-1)}, {FN (csc), ARG(-3.14124738660679181379e+00,2.0e+00), RES(-9.8749461907087358805e-5, 2.7572054583883740766e-1)}, {FN (csc), ARG(-3.14124738660679181379e+00,-2.0e+00), RES(-9.8749461907087358805e-5, -2.7572054583883740766e-1)}, {FN (csc), ARG(3.14193792057279441821e+00,0.0e+00), RES(-2.8963094332851348839e3, 0.0)}, {FN (csc), ARG(-3.14193792057279441821e+00,0.0e+00), RES(2.8963094332851348839e3, 0.0)}, {FN (csc), ARG(3.14193792057279441821e+00,1.19209289550781250e-07), RES(-2.8963090880181930415e3, 9.9999986092288059049e-1)}, {FN (csc), ARG(3.14193792057279441821e+00,-1.19209289550781250e-07), RES(-2.8963090880181930415e3, -9.9999986092288059049e-1)}, {FN (csc), ARG(-3.14193792057279441821e+00,1.19209289550781250e-07), RES(2.8963090880181930415e3, 9.9999986092288059049e-1)}, {FN (csc), ARG(-3.14193792057279441821e+00,-1.19209289550781250e-07), RES(2.8963090880181930415e3, -9.9999986092288059049e-1)}, {FN (csc), ARG(3.14193792057279441821e+00,5.0e-01), RES(-1.4337901642787135676e-3, 1.9190337944739187241e0)}, {FN (csc), ARG(3.14193792057279441821e+00,-5.0e-01), RES(-1.4337901642787135676e-3, -1.9190337944739187241e0)}, {FN (csc), ARG(-3.14193792057279441821e+00,5.0e-01), RES(1.4337901642787135676e-3, 1.9190337944739187241e0)}, {FN (csc), ARG(-3.14193792057279441821e+00,-5.0e-01), RES(1.4337901642787135676e-3, -1.9190337944739187241e0)}, {FN (csc), ARG(3.14193792057279441821e+00,1.0e+00), RES(-3.8576176225191689193e-4, 8.5091800407377002738e-1)}, {FN (csc), ARG(3.14193792057279441821e+00,-1.0e+00), RES(-3.8576176225191689193e-4, -8.5091800407377002738e-1)}, {FN (csc), ARG(-3.14193792057279441821e+00,1.0e+00), RES(3.8576176225191689193e-4, 8.5091800407377002738e-1)}, {FN (csc), ARG(-3.14193792057279441821e+00,-1.0e+00), RES(3.8576176225191689193e-4, -8.5091800407377002738e-1)}, {FN (csc), ARG(3.14193792057279441821e+00,2.0e+00), RES(-9.8749461907017306810e-5, 2.7572054583883740769e-1)}, {FN (csc), ARG(3.14193792057279441821e+00,-2.0e+00), RES(-9.8749461907017306810e-5, -2.7572054583883740769e-1)}, {FN (csc), ARG(-3.14193792057279441821e+00,2.0e+00), RES(9.8749461907017306810e-5, 2.7572054583883740769e-1)}, {FN (csc), ARG(-3.14193792057279441821e+00,-2.0e+00), RES(9.8749461907017306810e-5, -2.7572054583883740769e-1)}, {FN (csc), ARG(4.71204371340168837179e+00,0.0e+00), RES(-1.0000000596046477361e0, 0.0)}, {FN (csc), ARG(-4.71204371340168837179e+00,0.0e+00), RES(1.0000000596046477361e0, 0.0)}, {FN (csc), ARG(4.71204371340168837179e+00,1.19209289550781250e-07), RES(-1.0000000596046406306e0, 4.1159035837731055550e-11)}, {FN (csc), ARG(4.71204371340168837179e+00,-1.19209289550781250e-07), RES(-1.0000000596046406306e0, -4.1159035837731055550e-11)}, {FN (csc), ARG(-4.71204371340168837179e+00,1.19209289550781250e-07), RES(1.0000000596046406306e0, 4.1159035837731055550e-11)}, {FN (csc), ARG(-4.71204371340168837179e+00,-1.19209289550781250e-07), RES(1.0000000596046406306e0, -4.1159035837731055550e-11)}, {FN (csc), ARG(4.71204371340168837179e+00,5.0e-01), RES(-8.8681891425248302489e-1, 1.4149533035948134646e-4)}, {FN (csc), ARG(4.71204371340168837179e+00,-5.0e-01), RES(-8.8681891425248302489e-1, -1.4149533035948134646e-4)}, {FN (csc), ARG(-4.71204371340168837179e+00,5.0e-01), RES(8.8681891425248302489e-1, 1.4149533035948134646e-4)}, {FN (csc), ARG(-4.71204371340168837179e+00,-5.0e-01), RES(8.8681891425248302489e-1, -1.4149533035948134646e-4)}, {FN (csc), ARG(4.71204371340168837179e+00,1.0e+00), RES(-6.4805426748157480498e-1, 1.7040802567663445577e-4)}, {FN (csc), ARG(4.71204371340168837179e+00,-1.0e+00), RES(-6.4805426748157480498e-1, -1.7040802567663445577e-4)}, {FN (csc), ARG(-4.71204371340168837179e+00,1.0e+00), RES(6.4805426748157480498e-1, 1.7040802567663445577e-4)}, {FN (csc), ARG(-4.71204371340168837179e+00,-1.0e+00), RES(6.4805426748157480498e-1, -1.7040802567663445577e-4)}, {FN (csc), ARG(4.71204371340168837179e+00,2.0e+00), RES(-2.6580221522968095405e-1, 8.8471445300436013659e-5)}, {FN (csc), ARG(4.71204371340168837179e+00,-2.0e+00), RES(-2.6580221522968095405e-1, -8.8471445300436013659e-5)}, {FN (csc), ARG(-4.71204371340168837179e+00,2.0e+00), RES(2.6580221522968095405e-1, 8.8471445300436013659e-5)}, {FN (csc), ARG(-4.71204371340168837179e+00,-2.0e+00), RES(2.6580221522968095405e-1, -8.8471445300436013659e-5)}, {FN (csc), ARG(4.71273424736769097620e+00,0.0e+00), RES(-1.0000000596046477359e0, 0.0)}, {FN (csc), ARG(-4.71273424736769097620e+00,0.0e+00), RES(1.0000000596046477359e0, 0.0)}, {FN (csc), ARG(4.71273424736769097620e+00,1.19209289550781250e-07), RES(-1.0000000596046406305e0, -4.1159035837687258754e-11)}, {FN (csc), ARG(4.71273424736769097620e+00,-1.19209289550781250e-07), RES(-1.0000000596046406305e0, 4.1159035837687258754e-11)}, {FN (csc), ARG(-4.71273424736769097620e+00,1.19209289550781250e-07), RES(1.0000000596046406305e0, -4.1159035837687258754e-11)}, {FN (csc), ARG(-4.71273424736769097620e+00,-1.19209289550781250e-07), RES(1.0000000596046406305e0, 4.1159035837687258754e-11)}, {FN (csc), ARG(4.71273424736769097620e+00,5.0e-01), RES(-8.8681891425248302483e-1, -1.4149533035933078312e-4)}, {FN (csc), ARG(4.71273424736769097620e+00,-5.0e-01), RES(-8.8681891425248302483e-1, 1.4149533035933078312e-4)}, {FN (csc), ARG(-4.71273424736769097620e+00,5.0e-01), RES(8.8681891425248302483e-1, -1.4149533035933078312e-4)}, {FN (csc), ARG(-4.71273424736769097620e+00,-5.0e-01), RES(8.8681891425248302483e-1, 1.4149533035933078312e-4)}, {FN (csc), ARG(4.71273424736769097620e+00,1.0e+00), RES(-6.480542674815748050e-1, -1.7040802567645312683e-4)}, {FN (csc), ARG(4.71273424736769097620e+00,-1.0e+00), RES(-6.480542674815748050e-1, 1.7040802567645312683e-4)}, {FN (csc), ARG(-4.71273424736769097620e+00,1.0e+00), RES(6.480542674815748050e-1, -1.7040802567645312683e-4)}, {FN (csc), ARG(-4.71273424736769097620e+00,-1.0e+00), RES(6.480542674815748050e-1, 1.7040802567645312683e-4)}, {FN (csc), ARG(4.71273424736769097620e+00,2.0e+00), RES(-2.6580221522968095408e-1, -8.8471445300341872364e-5)}, {FN (csc), ARG(4.71273424736769097620e+00,-2.0e+00), RES(-2.6580221522968095408e-1, 8.8471445300341872364e-5)}, {FN (csc), ARG(-4.71273424736769097620e+00,2.0e+00), RES(2.6580221522968095408e-1, -8.8471445300341872364e-5)}, {FN (csc), ARG(-4.71273424736769097620e+00,-2.0e+00), RES(2.6580221522968095408e-1, 8.8471445300341872364e-5)}, {FN (csc), ARG(6.28284004019658492979e+00,0.0e+00), RES(-2.8963094332820529594e3, 0.0)}, {FN (csc), ARG(-6.28284004019658492979e+00,0.0e+00), RES(2.8963094332820529594e3, 0.0)}, {FN (csc), ARG(6.28284004019658492979e+00,1.19209289550781250e-07), RES(-2.8963090880151111181e3, -9.9999986092075241740e-1)}, {FN (csc), ARG(6.28284004019658492979e+00,-1.19209289550781250e-07), RES(-2.8963090880151111181e3, 9.9999986092075241740e-1)}, {FN (csc), ARG(-6.28284004019658492979e+00,1.19209289550781250e-07), RES(2.8963090880151111181e3, -9.9999986092075241740e-1)}, {FN (csc), ARG(-6.28284004019658492979e+00,-1.19209289550781250e-07), RES(2.8963090880151111181e3, 9.9999986092075241740e-1)}, {FN (csc), ARG(6.28284004019658492979e+00,5.0e-01), RES(-1.4337901642802392434e-3, -1.9190337944739187220e0)}, {FN (csc), ARG(6.28284004019658492979e+00,-5.0e-01), RES(-1.4337901642802392434e-3, 1.9190337944739187220e0)}, {FN (csc), ARG(-6.28284004019658492979e+00,5.0e-01), RES(1.4337901642802392434e-3, -1.9190337944739187220e0)}, {FN (csc), ARG(-6.28284004019658492979e+00,-5.0e-01), RES(1.4337901642802392434e-3, 1.9190337944739187220e0)}, {FN (csc), ARG(6.28284004019658492979e+00,1.0e+00), RES(-3.8576176225232737584e-4, -8.5091800407377002712e-1)}, {FN (csc), ARG(6.28284004019658492979e+00,-1.0e+00), RES(-3.8576176225232737584e-4, 8.5091800407377002712e-1)}, {FN (csc), ARG(-6.28284004019658492979e+00,1.0e+00), RES(3.8576176225232737584e-4, -8.5091800407377002712e-1)}, {FN (csc), ARG(-6.28284004019658492979e+00,-1.0e+00), RES(3.8576176225232737584e-4, 8.5091800407377002712e-1)}, {FN (csc), ARG(6.28284004019658492979e+00,2.0e+00), RES(-9.8749461907122384803e-5, -2.7572054583883740765e-1)}, {FN (csc), ARG(6.28284004019658492979e+00,-2.0e+00), RES(-9.8749461907122384803e-5, 2.7572054583883740765e-1)}, {FN (csc), ARG(-6.28284004019658492979e+00,2.0e+00), RES(9.8749461907122384803e-5, -2.7572054583883740765e-1)}, {FN (csc), ARG(-6.28284004019658492979e+00,-2.0e+00), RES(9.8749461907122384803e-5, 2.7572054583883740765e-1)}, {FN (csc), ARG(6.28353057416258753420e+00,0.0e+00), RES(2.8963094332861621921e3, 0.0)}, {FN (csc), ARG(-6.28353057416258753420e+00,0.0e+00), RES(-2.8963094332861621921e3, 0.0)}, {FN (csc), ARG(6.28353057416258753420e+00,1.19209289550781250e-07), RES(2.8963090880192203493e3, -9.9999986092358998153e-1)}, {FN (csc), ARG(6.28353057416258753420e+00,-1.19209289550781250e-07), RES(2.8963090880192203493e3, 9.9999986092358998153e-1)}, {FN (csc), ARG(-6.28353057416258753420e+00,1.19209289550781250e-07), RES(-2.8963090880192203493e3, -9.9999986092358998153e-1)}, {FN (csc), ARG(-6.28353057416258753420e+00,-1.19209289550781250e-07), RES(-2.8963090880192203493e3, 9.9999986092358998153e-1)}, {FN (csc), ARG(6.28353057416258753420e+00,5.0e-01), RES(1.4337901642782050091e-3, -1.9190337944739187248e0)}, {FN (csc), ARG(6.28353057416258753420e+00,-5.0e-01), RES(1.4337901642782050091e-3, 1.9190337944739187248e0)}, {FN (csc), ARG(-6.28353057416258753420e+00,5.0e-01), RES(-1.4337901642782050091e-3, -1.9190337944739187248e0)}, {FN (csc), ARG(-6.28353057416258753420e+00,-5.0e-01), RES(-1.4337901642782050091e-3, 1.9190337944739187248e0)}, {FN (csc), ARG(6.28353057416258753420e+00,1.0e+00), RES(3.8576176225178006396e-4, -8.5091800407377002747e-1)}, {FN (csc), ARG(6.28353057416258753420e+00,-1.0e+00), RES(3.8576176225178006396e-4, 8.5091800407377002747e-1)}, {FN (csc), ARG(-6.28353057416258753420e+00,1.0e+00), RES(-3.8576176225178006396e-4, -8.5091800407377002747e-1)}, {FN (csc), ARG(-6.28353057416258753420e+00,-1.0e+00), RES(-3.8576176225178006396e-4, 8.5091800407377002747e-1)}, {FN (csc), ARG(6.28353057416258753420e+00,2.0e+00), RES(9.8749461906982280812e-5, -2.7572054583883740770e-1)}, {FN (csc), ARG(6.28353057416258753420e+00,-2.0e+00), RES(9.8749461906982280812e-5, 2.7572054583883740770e-1)}, {FN (csc), ARG(-6.28353057416258753420e+00,2.0e+00), RES(-9.8749461906982280812e-5, -2.7572054583883740770e-1)}, {FN (csc), ARG(-6.28353057416258753420e+00,-2.0e+00), RES(-9.8749461906982280812e-5, 2.7572054583883740770e-1)}, {FN (csc), ARG(9.42443269378637893396e+00,0.0e+00), RES(2.8963094332884762317e3, 0.0)}, {FN (csc), ARG(-9.42443269378637893396e+00,0.0e+00), RES(-2.8963094332884762317e3, 0.0)}, {FN (csc), ARG(9.42443269378637893396e+00,1.19209289550781250e-07), RES(2.8963090880215343881e3, 9.9999986092518790411e-1)}, {FN (csc), ARG(9.42443269378637893396e+00,-1.19209289550781250e-07), RES(2.8963090880215343881e3, -9.9999986092518790411e-1)}, {FN (csc), ARG(-9.42443269378637893396e+00,1.19209289550781250e-07), RES(-2.8963090880215343881e3, 9.9999986092518790411e-1)}, {FN (csc), ARG(-9.42443269378637893396e+00,-1.19209289550781250e-07), RES(-2.8963090880215343881e3, -9.9999986092518790411e-1)}, {FN (csc), ARG(9.42443269378637893396e+00,5.0e-01), RES(1.4337901642770594670e-3, 1.9190337944739187263e0)}, {FN (csc), ARG(9.42443269378637893396e+00,-5.0e-01), RES(1.4337901642770594670e-3, -1.9190337944739187263e0)}, {FN (csc), ARG(-9.42443269378637893396e+00,5.0e-01), RES(-1.4337901642770594670e-3, 1.9190337944739187263e0)}, {FN (csc), ARG(-9.42443269378637893396e+00,-5.0e-01), RES(-1.4337901642770594670e-3, -1.9190337944739187263e0)}, {FN (csc), ARG(9.42443269378637893396e+00,1.0e+00), RES(3.8576176225147185523e-4, 8.5091800407377002767e-1)}, {FN (csc), ARG(9.42443269378637893396e+00,-1.0e+00), RES(3.8576176225147185523e-4, -8.5091800407377002767e-1)}, {FN (csc), ARG(-9.42443269378637893396e+00,1.0e+00), RES(-3.8576176225147185523e-4, 8.5091800407377002767e-1)}, {FN (csc), ARG(-9.42443269378637893396e+00,-1.0e+00), RES(-3.8576176225147185523e-4, -8.5091800407377002767e-1)}, {FN (csc), ARG(9.42443269378637893396e+00,2.0e+00), RES(9.874946190690338380e-5, 2.7572054583883740773e-1)}, {FN (csc), ARG(9.42443269378637893396e+00,-2.0e+00), RES(9.874946190690338380e-5, -2.7572054583883740773e-1)}, {FN (csc), ARG(-9.42443269378637893396e+00,2.0e+00), RES(-9.874946190690338380e-5, 2.7572054583883740773e-1)}, {FN (csc), ARG(-9.42443269378637893396e+00,-2.0e+00), RES(-9.874946190690338380e-5, -2.7572054583883740773e-1)}, {FN (csc), ARG(9.42512322775237976202e+00,0.0e+00), RES(-2.8963094332946400807e3, 0.0)}, {FN (csc), ARG(-9.42512322775237976202e+00,0.0e+00), RES(2.8963094332946400807e3, 0.0)}, {FN (csc), ARG(9.42512322775237976202e+00,1.19209289550781250e-07), RES(-2.8963090880276982349e3, 9.9999986092944425030e-1)}, {FN (csc), ARG(9.42512322775237976202e+00,-1.19209289550781250e-07), RES(-2.8963090880276982349e3, -9.9999986092944425030e-1)}, {FN (csc), ARG(-9.42512322775237976202e+00,1.19209289550781250e-07), RES(2.8963090880276982349e3, 9.9999986092944425030e-1)}, {FN (csc), ARG(-9.42512322775237976202e+00,-1.19209289550781250e-07), RES(2.8963090880276982349e3, -9.9999986092944425030e-1)}, {FN (csc), ARG(9.42512322775237976202e+00,5.0e-01), RES(-1.4337901642740081154e-3, 1.9190337944739187304e0)}, {FN (csc), ARG(9.42512322775237976202e+00,-5.0e-01), RES(-1.4337901642740081154e-3, -1.9190337944739187304e0)}, {FN (csc), ARG(-9.42512322775237976202e+00,5.0e-01), RES(1.4337901642740081154e-3, 1.9190337944739187304e0)}, {FN (csc), ARG(-9.42512322775237976202e+00,-5.0e-01), RES(1.4337901642740081154e-3, -1.9190337944739187304e0)}, {FN (csc), ARG(9.42512322775237976202e+00,1.0e+00), RES(-3.8576176225065088741e-4, 8.5091800407377002820e-1)}, {FN (csc), ARG(9.42512322775237976202e+00,-1.0e+00), RES(-3.8576176225065088741e-4, -8.5091800407377002820e-1)}, {FN (csc), ARG(-9.42512322775237976202e+00,1.0e+00), RES(3.8576176225065088741e-4, 8.5091800407377002820e-1)}, {FN (csc), ARG(-9.42512322775237976202e+00,-1.0e+00), RES(3.8576176225065088741e-4, -8.5091800407377002820e-1)}, {FN (csc), ARG(9.42512322775237976202e+00,2.0e+00), RES(-9.8749461906693227814e-5, 2.7572054583883740781e-1)}, {FN (csc), ARG(9.42512322775237976202e+00,-2.0e+00), RES(-9.8749461906693227814e-5, -2.7572054583883740781e-1)}, {FN (csc), ARG(-9.42512322775237976202e+00,2.0e+00), RES(9.8749461906693227814e-5, 2.7572054583883740781e-1)}, {FN (csc), ARG(-9.42512322775237976202e+00,-2.0e+00), RES(9.8749461906693227814e-5, -2.7572054583883740781e-1)}, {FN (sec), ARG(-3.45266983001243932001e-04,0.0e+00), RES(1.0000000596046477360e0, 0.0)}, {FN (sec), ARG(3.45266983001243932001e-04,0.0e+00), RES(1.0000000596046477360e0, 0.0)}, {FN (sec), ARG(-3.45266983001243932001e-04,1.19209289550781250e-07), RES(1.0000000596046406306e0, -4.1159035837702210125e-11)}, {FN (sec), ARG(-3.45266983001243932001e-04,-1.19209289550781250e-07), RES(1.0000000596046406306e0, 4.1159035837702210125e-11)}, {FN (sec), ARG(3.45266983001243932001e-04,1.19209289550781250e-07), RES(1.0000000596046406306e0, 4.1159035837702210125e-11)}, {FN (sec), ARG(3.45266983001243932001e-04,-1.19209289550781250e-07), RES(1.0000000596046406306e0, -4.1159035837702210125e-11)}, {FN (sec), ARG(-3.45266983001243932001e-04,5.0e-01), RES(8.8681891425248302485e-1, -1.4149533035938218250e-4)}, {FN (sec), ARG(-3.45266983001243932001e-04,-5.0e-01), RES(8.8681891425248302485e-1, 1.4149533035938218250e-4)}, {FN (sec), ARG(3.45266983001243932001e-04,5.0e-01), RES(8.8681891425248302485e-1, 1.4149533035938218250e-4)}, {FN (sec), ARG(3.45266983001243932001e-04,-5.0e-01), RES(8.8681891425248302485e-1, -1.4149533035938218250e-4)}, {FN (sec), ARG(-3.45266983001243932001e-04,1.0e+00), RES(6.4805426748157480499e-1, -1.7040802567651502899e-4)}, {FN (sec), ARG(-3.45266983001243932001e-04,-1.0e+00), RES(6.4805426748157480499e-1, 1.7040802567651502899e-4)}, {FN (sec), ARG(3.45266983001243932001e-04,1.0e+00), RES(6.4805426748157480499e-1, 1.7040802567651502899e-4)}, {FN (sec), ARG(3.45266983001243932001e-04,-1.0e+00), RES(6.4805426748157480499e-1, -1.7040802567651502899e-4)}, {FN (sec), ARG(-3.45266983001243932001e-04,2.0e+00), RES(2.6580221522968095407e-1, -8.8471445300374010365e-5)}, {FN (sec), ARG(-3.45266983001243932001e-04,-2.0e+00), RES(2.6580221522968095407e-1, 8.8471445300374010365e-5)}, {FN (sec), ARG(3.45266983001243932001e-04,2.0e+00), RES(2.6580221522968095407e-1, 8.8471445300374010365e-5)}, {FN (sec), ARG(3.45266983001243932001e-04,-2.0e+00), RES(2.6580221522968095407e-1, -8.8471445300374010365e-5)}, {FN (sec), ARG(1.57045105981189525579e+00,0.0e+00), RES(2.8963094332835939217e3, 0.0)}, {FN (sec), ARG(-1.57045105981189525579e+00,0.0e+00), RES(2.8963094332835939217e3, 0.0)}, {FN (sec), ARG(1.57045105981189525579e+00,1.19209289550781250e-07), RES(2.8963090880166520798e3, 9.9999986092181650394e-1)}, {FN (sec), ARG(1.57045105981189525579e+00,-1.19209289550781250e-07), RES(2.8963090880166520798e3, -9.9999986092181650394e-1)}, {FN (sec), ARG(-1.57045105981189525579e+00,1.19209289550781250e-07), RES(2.8963090880166520798e3, -9.9999986092181650394e-1)}, {FN (sec), ARG(-1.57045105981189525579e+00,-1.19209289550781250e-07), RES(2.8963090880166520798e3, 9.9999986092181650394e-1)}, {FN (sec), ARG(1.57045105981189525579e+00,5.0e-01), RES(1.4337901642794764055e-3, 1.9190337944739187231e0)}, {FN (sec), ARG(1.57045105981189525579e+00,-5.0e-01), RES(1.4337901642794764055e-3, -1.9190337944739187231e0)}, {FN (sec), ARG(-1.57045105981189525579e+00,5.0e-01), RES(1.4337901642794764055e-3, -1.9190337944739187231e0)}, {FN (sec), ARG(-1.57045105981189525579e+00,-5.0e-01), RES(1.4337901642794764055e-3, 1.9190337944739187231e0)}, {FN (sec), ARG(1.57045105981189525579e+00,1.0e+00), RES(3.8576176225212213388e-4, 8.5091800407377002725e-1)}, {FN (sec), ARG(1.57045105981189525579e+00,-1.0e+00), RES(3.8576176225212213388e-4, -8.5091800407377002725e-1)}, {FN (sec), ARG(-1.57045105981189525579e+00,1.0e+00), RES(3.8576176225212213388e-4, -8.5091800407377002725e-1)}, {FN (sec), ARG(-1.57045105981189525579e+00,-1.0e+00), RES(3.8576176225212213388e-4, 8.5091800407377002725e-1)}, {FN (sec), ARG(1.57045105981189525579e+00,2.0e+00), RES(9.8749461907069845806e-5, 2.7572054583883740767e-1)}, {FN (sec), ARG(1.57045105981189525579e+00,-2.0e+00), RES(9.8749461907069845806e-5, -2.7572054583883740767e-1)}, {FN (sec), ARG(-1.57045105981189525579e+00,2.0e+00), RES(9.8749461907069845806e-5, -2.7572054583883740767e-1)}, {FN (sec), ARG(-1.57045105981189525579e+00,-2.0e+00), RES(9.8749461907069845806e-5, 2.7572054583883740767e-1)}, {FN (sec), ARG(1.57114159377789786021e+00,0.0e+00), RES(-2.8963094332846212298e3, 0.0)}, {FN (sec), ARG(-1.57114159377789786021e+00,0.0e+00), RES(-2.8963094332846212298e3, 0.0)}, {FN (sec), ARG(1.57114159377789786021e+00,1.19209289550781250e-07), RES(-2.8963090880176793876e3, 9.9999986092252589498e-1)}, {FN (sec), ARG(1.57114159377789786021e+00,-1.19209289550781250e-07), RES(-2.8963090880176793876e3, -9.9999986092252589498e-1)}, {FN (sec), ARG(-1.57114159377789786021e+00,1.19209289550781250e-07), RES(-2.8963090880176793876e3, -9.9999986092252589498e-1)}, {FN (sec), ARG(-1.57114159377789786021e+00,-1.19209289550781250e-07), RES(-2.8963090880176793876e3, 9.9999986092252589498e-1)}, {FN (sec), ARG(1.57114159377789786021e+00,5.0e-01), RES(-1.4337901642789678469e-3, 1.9190337944739187237e0)}, {FN (sec), ARG(1.57114159377789786021e+00,-5.0e-01), RES(-1.4337901642789678469e-3, -1.9190337944739187237e0)}, {FN (sec), ARG(-1.57114159377789786021e+00,5.0e-01), RES(-1.4337901642789678469e-3, -1.9190337944739187237e0)}, {FN (sec), ARG(-1.57114159377789786021e+00,-5.0e-01), RES(-1.4337901642789678469e-3, 1.9190337944739187237e0)}, {FN (sec), ARG(1.57114159377789786021e+00,1.0e+00), RES(-3.8576176225198530591e-4, 8.5091800407377002734e-1)}, {FN (sec), ARG(1.57114159377789786021e+00,-1.0e+00), RES(-3.8576176225198530591e-4, -8.5091800407377002734e-1)}, {FN (sec), ARG(-1.57114159377789786021e+00,1.0e+00), RES(-3.8576176225198530591e-4, -8.5091800407377002734e-1)}, {FN (sec), ARG(-1.57114159377789786021e+00,-1.0e+00), RES(-3.8576176225198530591e-4, 8.5091800407377002734e-1)}, {FN (sec), ARG(1.57114159377789786021e+00,2.0e+00), RES(-9.8749461907034819809e-5, 2.7572054583883740768e-1)}, {FN (sec), ARG(1.57114159377789786021e+00,-2.0e+00), RES(-9.8749461907034819809e-5, -2.7572054583883740768e-1)}, {FN (sec), ARG(-1.57114159377789786021e+00,2.0e+00), RES(-9.8749461907034819809e-5, -2.7572054583883740768e-1)}, {FN (sec), ARG(-1.57114159377789786021e+00,-2.0e+00), RES(-9.8749461907034819809e-5, 2.7572054583883740768e-1)}, {FN (sec), ARG(3.14124738660679181379e+00,0.0e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (sec), ARG(-3.14124738660679181379e+00,0.0e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (sec), ARG(3.14124738660679181379e+00,1.19209289550781250e-07), RES(-1.0000000596046406306e0, 4.1159035837723756084e-11)}, {FN (sec), ARG(3.14124738660679181379e+00,-1.19209289550781250e-07), RES(-1.0000000596046406306e0, -4.1159035837723756084e-11)}, {FN (sec), ARG(-3.14124738660679181379e+00,1.19209289550781250e-07), RES(-1.0000000596046406306e0, -4.1159035837723756084e-11)}, {FN (sec), ARG(-3.14124738660679181379e+00,-1.19209289550781250e-07), RES(-1.0000000596046406306e0, 4.1159035837723756084e-11)}, {FN (sec), ARG(3.14124738660679181379e+00,5.0e-01), RES(-8.8681891425248302488e-1, 1.4149533035945625257e-4)}, {FN (sec), ARG(3.14124738660679181379e+00,-5.0e-01), RES(-8.8681891425248302488e-1, -1.4149533035945625257e-4)}, {FN (sec), ARG(-3.14124738660679181379e+00,5.0e-01), RES(-8.8681891425248302488e-1, -1.4149533035945625257e-4)}, {FN (sec), ARG(-3.14124738660679181379e+00,-5.0e-01), RES(-8.8681891425248302488e-1, 1.4149533035945625257e-4)}, {FN (sec), ARG(3.14124738660679181379e+00,1.0e+00), RES(-6.4805426748157480499e-1, 1.7040802567660423428e-4)}, {FN (sec), ARG(3.14124738660679181379e+00,-1.0e+00), RES(-6.4805426748157480499e-1, -1.7040802567660423428e-4)}, {FN (sec), ARG(-3.14124738660679181379e+00,1.0e+00), RES(-6.4805426748157480499e-1, -1.7040802567660423428e-4)}, {FN (sec), ARG(-3.14124738660679181379e+00,-1.0e+00), RES(-6.4805426748157480499e-1, 1.7040802567660423428e-4)}, {FN (sec), ARG(3.14124738660679181379e+00,2.0e+00), RES(-2.6580221522968095405e-1, 8.8471445300420323443e-5)}, {FN (sec), ARG(3.14124738660679181379e+00,-2.0e+00), RES(-2.6580221522968095405e-1, -8.8471445300420323443e-5)}, {FN (sec), ARG(-3.14124738660679181379e+00,2.0e+00), RES(-2.6580221522968095405e-1, -8.8471445300420323443e-5)}, {FN (sec), ARG(-3.14124738660679181379e+00,-2.0e+00), RES(-2.6580221522968095405e-1, 8.8471445300420323443e-5)}, {FN (sec), ARG(3.14193792057279441821e+00,0.0e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (sec), ARG(-3.14193792057279441821e+00,0.0e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (sec), ARG(3.14193792057279441821e+00,1.19209289550781250e-07), RES(-1.0000000596046406305e0, -4.1159035837694558220e-11)}, {FN (sec), ARG(3.14193792057279441821e+00,-1.19209289550781250e-07), RES(-1.0000000596046406305e0, 4.1159035837694558220e-11)}, {FN (sec), ARG(-3.14193792057279441821e+00,1.19209289550781250e-07), RES(-1.0000000596046406305e0, 4.1159035837694558220e-11)}, {FN (sec), ARG(-3.14193792057279441821e+00,-1.19209289550781250e-07), RES(-1.0000000596046406305e0, -4.1159035837694558220e-11)}, {FN (sec), ARG(3.14193792057279441821e+00,5.0e-01), RES(-8.8681891425248302484e-1, -1.4149533035935587701e-4)}, {FN (sec), ARG(3.14193792057279441821e+00,-5.0e-01), RES(-8.8681891425248302484e-1, 1.4149533035935587701e-4)}, {FN (sec), ARG(-3.14193792057279441821e+00,5.0e-01), RES(-8.8681891425248302484e-1, 1.4149533035935587701e-4)}, {FN (sec), ARG(-3.14193792057279441821e+00,-5.0e-01), RES(-8.8681891425248302484e-1, -1.4149533035935587701e-4)}, {FN (sec), ARG(3.14193792057279441821e+00,1.0e+00), RES(-6.4805426748157480499e-1, -1.7040802567648334832e-4)}, {FN (sec), ARG(3.14193792057279441821e+00,-1.0e+00), RES(-6.4805426748157480499e-1, 1.7040802567648334832e-4)}, {FN (sec), ARG(-3.14193792057279441821e+00,1.0e+00), RES(-6.4805426748157480499e-1, 1.7040802567648334832e-4)}, {FN (sec), ARG(-3.14193792057279441821e+00,-1.0e+00), RES(-6.4805426748157480499e-1, -1.7040802567648334832e-4)}, {FN (sec), ARG(3.14193792057279441821e+00,2.0e+00), RES(-2.6580221522968095407e-1, -8.8471445300357562580e-5)}, {FN (sec), ARG(3.14193792057279441821e+00,-2.0e+00), RES(-2.6580221522968095407e-1, 8.8471445300357562580e-5)}, {FN (sec), ARG(-3.14193792057279441821e+00,2.0e+00), RES(-2.6580221522968095407e-1, 8.8471445300357562580e-5)}, {FN (sec), ARG(-3.14193792057279441821e+00,-2.0e+00), RES(-2.6580221522968095407e-1, -8.8471445300357562580e-5)}, {FN (sec), ARG(4.71204371340168837179e+00,0.0e+00), RES(-2.8963094332825666135e3, 0.0)}, {FN (sec), ARG(-4.71204371340168837179e+00,0.0e+00), RES(-2.8963094332825666135e3, 0.0)}, {FN (sec), ARG(4.71204371340168837179e+00,1.19209289550781250e-07), RES(-2.8963090880156247720e3, -9.9999986092110711291e-1)}, {FN (sec), ARG(4.71204371340168837179e+00,-1.19209289550781250e-07), RES(-2.8963090880156247720e3, 9.9999986092110711291e-1)}, {FN (sec), ARG(-4.71204371340168837179e+00,1.19209289550781250e-07), RES(-2.8963090880156247720e3, 9.9999986092110711291e-1)}, {FN (sec), ARG(-4.71204371340168837179e+00,-1.19209289550781250e-07), RES(-2.8963090880156247720e3, -9.9999986092110711291e-1)}, {FN (sec), ARG(4.71204371340168837179e+00,5.0e-01), RES(-1.4337901642799849641e-3, -1.9190337944739187224e0)}, {FN (sec), ARG(4.71204371340168837179e+00,-5.0e-01), RES(-1.4337901642799849641e-3, 1.9190337944739187224e0)}, {FN (sec), ARG(-4.71204371340168837179e+00,5.0e-01), RES(-1.4337901642799849641e-3, 1.9190337944739187224e0)}, {FN (sec), ARG(-4.71204371340168837179e+00,-5.0e-01), RES(-1.4337901642799849641e-3, -1.9190337944739187224e0)}, {FN (sec), ARG(4.71204371340168837179e+00,1.0e+00), RES(-3.8576176225225896185e-4, -8.5091800407377002716e-1)}, {FN (sec), ARG(4.71204371340168837179e+00,-1.0e+00), RES(-3.8576176225225896185e-4, 8.5091800407377002716e-1)}, {FN (sec), ARG(-4.71204371340168837179e+00,1.0e+00), RES(-3.8576176225225896185e-4, 8.5091800407377002716e-1)}, {FN (sec), ARG(-4.71204371340168837179e+00,-1.0e+00), RES(-3.8576176225225896185e-4, -8.5091800407377002716e-1)}, {FN (sec), ARG(4.71204371340168837179e+00,2.0e+00), RES(-9.8749461907104871804e-5, -2.7572054583883740766e-1)}, {FN (sec), ARG(4.71204371340168837179e+00,-2.0e+00), RES(-9.8749461907104871804e-5, 2.7572054583883740766e-1)}, {FN (sec), ARG(-4.71204371340168837179e+00,2.0e+00), RES(-9.8749461907104871804e-5, 2.7572054583883740766e-1)}, {FN (sec), ARG(-4.71204371340168837179e+00,-2.0e+00), RES(-9.8749461907104871804e-5, -2.7572054583883740766e-1)}, {FN (sec), ARG(4.71273424736769097620e+00,0.0e+00), RES(2.8963094332856485380e3, 0.0)}, {FN (sec), ARG(-4.71273424736769097620e+00,0.0e+00), RES(2.8963094332856485380e3, 0.0)}, {FN (sec), ARG(4.71273424736769097620e+00,1.19209289550781250e-07), RES(2.8963090880187066954e3, -9.9999986092323528601e-1)}, {FN (sec), ARG(4.71273424736769097620e+00,-1.19209289550781250e-07), RES(2.8963090880187066954e3, 9.9999986092323528601e-1)}, {FN (sec), ARG(-4.71273424736769097620e+00,1.19209289550781250e-07), RES(2.8963090880187066954e3, 9.9999986092323528601e-1)}, {FN (sec), ARG(-4.71273424736769097620e+00,-1.19209289550781250e-07), RES(2.8963090880187066954e3, -9.9999986092323528601e-1)}, {FN (sec), ARG(4.71273424736769097620e+00,5.0e-01), RES(1.4337901642784592884e-3, -1.9190337944739187244e0)}, {FN (sec), ARG(4.71273424736769097620e+00,-5.0e-01), RES(1.4337901642784592884e-3, 1.9190337944739187244e0)}, {FN (sec), ARG(-4.71273424736769097620e+00,5.0e-01), RES(1.4337901642784592884e-3, 1.9190337944739187244e0)}, {FN (sec), ARG(-4.71273424736769097620e+00,-5.0e-01), RES(1.4337901642784592884e-3, -1.9190337944739187244e0)}, {FN (sec), ARG(4.71273424736769097620e+00,1.0e+00), RES(3.8576176225184847794e-4, -8.5091800407377002743e-1)}, {FN (sec), ARG(4.71273424736769097620e+00,-1.0e+00), RES(3.8576176225184847794e-4, 8.5091800407377002743e-1)}, {FN (sec), ARG(-4.71273424736769097620e+00,1.0e+00), RES(3.8576176225184847794e-4, 8.5091800407377002743e-1)}, {FN (sec), ARG(-4.71273424736769097620e+00,-1.0e+00), RES(3.8576176225184847794e-4, -8.5091800407377002743e-1)}, {FN (sec), ARG(4.71273424736769097620e+00,2.0e+00), RES(9.8749461906999793811e-5, -2.7572054583883740770e-1)}, {FN (sec), ARG(4.71273424736769097620e+00,-2.0e+00), RES(9.8749461906999793811e-5, 2.7572054583883740770e-1)}, {FN (sec), ARG(-4.71273424736769097620e+00,2.0e+00), RES(9.8749461906999793811e-5, 2.7572054583883740770e-1)}, {FN (sec), ARG(-4.71273424736769097620e+00,-2.0e+00), RES(9.8749461906999793811e-5, -2.7572054583883740770e-1)}, {FN (sec), ARG(6.28284004019658492979e+00,0.0e+00), RES(1.0000000596046477361e0, 0.0)}, {FN (sec), ARG(-6.28284004019658492979e+00,0.0e+00), RES(1.0000000596046477361e0, 0.0)}, {FN (sec), ARG(6.28284004019658492979e+00,1.19209289550781250e-07), RES(1.0000000596046406307e0, -4.1159035837738355016e-11)}, {FN (sec), ARG(6.28284004019658492979e+00,-1.19209289550781250e-07), RES(1.0000000596046406307e0, 4.1159035837738355016e-11)}, {FN (sec), ARG(-6.28284004019658492979e+00,1.19209289550781250e-07), RES(1.0000000596046406307e0, 4.1159035837738355016e-11)}, {FN (sec), ARG(-6.28284004019658492979e+00,-1.19209289550781250e-07), RES(1.0000000596046406307e0, -4.1159035837738355016e-11)}, {FN (sec), ARG(6.28284004019658492979e+00,5.0e-01), RES(8.8681891425248302490e-1, -1.4149533035950644034e-4)}, {FN (sec), ARG(6.28284004019658492979e+00,-5.0e-01), RES(8.8681891425248302490e-1, 1.4149533035950644034e-4)}, {FN (sec), ARG(-6.28284004019658492979e+00,5.0e-01), RES(8.8681891425248302490e-1, 1.4149533035950644034e-4)}, {FN (sec), ARG(-6.28284004019658492979e+00,-5.0e-01), RES(8.8681891425248302490e-1, -1.4149533035950644034e-4)}, {FN (sec), ARG(6.28284004019658492979e+00,1.0e+00), RES(6.4805426748157480498e-1, -1.7040802567666467726e-4)}, {FN (sec), ARG(6.28284004019658492979e+00,-1.0e+00), RES(6.4805426748157480498e-1, 1.7040802567666467726e-4)}, {FN (sec), ARG(-6.28284004019658492979e+00,1.0e+00), RES(6.4805426748157480498e-1, 1.7040802567666467726e-4)}, {FN (sec), ARG(-6.28284004019658492979e+00,-1.0e+00), RES(6.4805426748157480498e-1, -1.7040802567666467726e-4)}, {FN (sec), ARG(6.28284004019658492979e+00,2.0e+00), RES(2.6580221522968095404e-1, -8.8471445300451703875e-5)}, {FN (sec), ARG(6.28284004019658492979e+00,-2.0e+00), RES(2.6580221522968095404e-1, 8.8471445300451703875e-5)}, {FN (sec), ARG(-6.28284004019658492979e+00,2.0e+00), RES(2.6580221522968095404e-1, 8.8471445300451703875e-5)}, {FN (sec), ARG(-6.28284004019658492979e+00,-2.0e+00), RES(2.6580221522968095404e-1, -8.8471445300451703875e-5)}, {FN (sec), ARG(6.28353057416258753420e+00,0.0e+00), RES(1.0000000596046477359e0, 0.0)}, {FN (sec), ARG(-6.28353057416258753420e+00,0.0e+00), RES(1.0000000596046477359e0, 0.0)}, {FN (sec), ARG(6.28353057416258753420e+00,1.19209289550781250e-07), RES(1.0000000596046406305e0, 4.1159035837679959288e-11)}, {FN (sec), ARG(6.28353057416258753420e+00,-1.19209289550781250e-07), RES(1.0000000596046406305e0, -4.1159035837679959288e-11)}, {FN (sec), ARG(-6.28353057416258753420e+00,1.19209289550781250e-07), RES(1.0000000596046406305e0, -4.1159035837679959288e-11)}, {FN (sec), ARG(-6.28353057416258753420e+00,-1.19209289550781250e-07), RES(1.0000000596046406305e0, 4.1159035837679959288e-11)}, {FN (sec), ARG(6.28353057416258753420e+00,5.0e-01), RES(8.8681891425248302482e-1, 1.4149533035930568923e-4)}, {FN (sec), ARG(6.28353057416258753420e+00,-5.0e-01), RES(8.8681891425248302482e-1, -1.4149533035930568923e-4)}, {FN (sec), ARG(-6.28353057416258753420e+00,5.0e-01), RES(8.8681891425248302482e-1, -1.4149533035930568923e-4)}, {FN (sec), ARG(-6.28353057416258753420e+00,-5.0e-01), RES(8.8681891425248302482e-1, 1.4149533035930568923e-4)}, {FN (sec), ARG(6.28353057416258753420e+00,1.0e+00), RES(6.480542674815748050e-1, 1.7040802567642290534e-4)}, {FN (sec), ARG(6.28353057416258753420e+00,-1.0e+00), RES(6.480542674815748050e-1, -1.7040802567642290534e-4)}, {FN (sec), ARG(-6.28353057416258753420e+00,1.0e+00), RES(6.480542674815748050e-1, -1.7040802567642290534e-4)}, {FN (sec), ARG(-6.28353057416258753420e+00,-1.0e+00), RES(6.480542674815748050e-1, 1.7040802567642290534e-4)}, {FN (sec), ARG(6.28353057416258753420e+00,2.0e+00), RES(2.6580221522968095408e-1, 8.8471445300326182148e-5)}, {FN (sec), ARG(6.28353057416258753420e+00,-2.0e+00), RES(2.6580221522968095408e-1, -8.8471445300326182148e-5)}, {FN (sec), ARG(-6.28353057416258753420e+00,2.0e+00), RES(2.6580221522968095408e-1, -8.8471445300326182148e-5)}, {FN (sec), ARG(-6.28353057416258753420e+00,-2.0e+00), RES(2.6580221522968095408e-1, 8.8471445300326182148e-5)}, {FN (sec), ARG(9.42443269378637893396e+00,0.0e+00), RES(-1.0000000596046477358e0, 0.0)}, {FN (sec), ARG(-9.42443269378637893396e+00,0.0e+00), RES(-1.0000000596046477358e0, 0.0)}, {FN (sec), ARG(9.42443269378637893396e+00,1.19209289550781250e-07), RES(-1.0000000596046406304e0, 4.1159035837647074798e-11)}, {FN (sec), ARG(9.42443269378637893396e+00,-1.19209289550781250e-07), RES(-1.0000000596046406304e0, -4.1159035837647074798e-11)}, {FN (sec), ARG(-9.42443269378637893396e+00,1.19209289550781250e-07), RES(-1.0000000596046406304e0, -4.1159035837647074798e-11)}, {FN (sec), ARG(-9.42443269378637893396e+00,-1.19209289550781250e-07), RES(-1.0000000596046406304e0, 4.1159035837647074798e-11)}, {FN (sec), ARG(9.42443269378637893396e+00,5.0e-01), RES(-8.8681891425248302477e-1, 1.4149533035919263990e-4)}, {FN (sec), ARG(9.42443269378637893396e+00,-5.0e-01), RES(-8.8681891425248302477e-1, -1.4149533035919263990e-4)}, {FN (sec), ARG(-9.42443269378637893396e+00,5.0e-01), RES(-8.8681891425248302477e-1, -1.4149533035919263990e-4)}, {FN (sec), ARG(-9.42443269378637893396e+00,-5.0e-01), RES(-8.8681891425248302477e-1, 1.4149533035919263990e-4)}, {FN (sec), ARG(9.42443269378637893396e+00,1.0e+00), RES(-6.4805426748157480501e-1, 1.7040802567628675588e-4)}, {FN (sec), ARG(9.42443269378637893396e+00,-1.0e+00), RES(-6.4805426748157480501e-1, -1.7040802567628675588e-4)}, {FN (sec), ARG(-9.42443269378637893396e+00,1.0e+00), RES(-6.4805426748157480501e-1, -1.7040802567628675588e-4)}, {FN (sec), ARG(-9.42443269378637893396e+00,-1.0e+00), RES(-6.4805426748157480501e-1, 1.7040802567628675588e-4)}, {FN (sec), ARG(9.42443269378637893396e+00,2.0e+00), RES(-2.6580221522968095410e-1, 8.8471445300255496873e-5)}, {FN (sec), ARG(9.42443269378637893396e+00,-2.0e+00), RES(-2.6580221522968095410e-1, -8.8471445300255496873e-5)}, {FN (sec), ARG(-9.42443269378637893396e+00,2.0e+00), RES(-2.6580221522968095410e-1, -8.8471445300255496873e-5)}, {FN (sec), ARG(-9.42443269378637893396e+00,-2.0e+00), RES(-2.6580221522968095410e-1, 8.8471445300255496873e-5)}, {FN (sec), ARG(9.42512322775237976202e+00,0.0e+00), RES(-1.0000000596046477356e0, 0.0)}, {FN (sec), ARG(-9.42512322775237976202e+00,0.0e+00), RES(-1.0000000596046477356e0, 0.0)}, {FN (sec), ARG(9.42512322775237976202e+00,1.19209289550781250e-07), RES(-1.0000000596046406301e0, -4.1159035837559481207e-11)}, {FN (sec), ARG(9.42512322775237976202e+00,-1.19209289550781250e-07), RES(-1.0000000596046406301e0, 4.1159035837559481207e-11)}, {FN (sec), ARG(-9.42512322775237976202e+00,1.19209289550781250e-07), RES(-1.0000000596046406301e0, 4.1159035837559481207e-11)}, {FN (sec), ARG(-9.42512322775237976202e+00,-1.19209289550781250e-07), RES(-1.0000000596046406301e0, -4.1159035837559481207e-11)}, {FN (sec), ARG(9.42512322775237976202e+00,5.0e-01), RES(-8.8681891425248302464e-1, -1.4149533035889151322e-4)}, {FN (sec), ARG(9.42512322775237976202e+00,-5.0e-01), RES(-8.8681891425248302464e-1, 1.4149533035889151322e-4)}, {FN (sec), ARG(-9.42512322775237976202e+00,5.0e-01), RES(-8.8681891425248302464e-1, 1.4149533035889151322e-4)}, {FN (sec), ARG(-9.42512322775237976202e+00,-5.0e-01), RES(-8.8681891425248302464e-1, -1.4149533035889151322e-4)}, {FN (sec), ARG(9.42512322775237976202e+00,1.0e+00), RES(-6.4805426748157480504e-1, -1.704080256759240980e-4)}, {FN (sec), ARG(9.42512322775237976202e+00,-1.0e+00), RES(-6.4805426748157480504e-1, 1.704080256759240980e-4)}, {FN (sec), ARG(-9.42512322775237976202e+00,1.0e+00), RES(-6.4805426748157480504e-1, 1.704080256759240980e-4)}, {FN (sec), ARG(-9.42512322775237976202e+00,-1.0e+00), RES(-6.4805426748157480504e-1, -1.704080256759240980e-4)}, {FN (sec), ARG(9.42512322775237976202e+00,2.0e+00), RES(-2.6580221522968095416e-1, -8.8471445300067214283e-5)}, {FN (sec), ARG(9.42512322775237976202e+00,-2.0e+00), RES(-2.6580221522968095416e-1, 8.8471445300067214283e-5)}, {FN (sec), ARG(-9.42512322775237976202e+00,2.0e+00), RES(-2.6580221522968095416e-1, 8.8471445300067214283e-5)}, {FN (sec), ARG(-9.42512322775237976202e+00,-2.0e+00), RES(-2.6580221522968095416e-1, -8.8471445300067214283e-5)}, {FN (cot), ARG(-3.45266983001243932001e-04,0.0e+00), RES(-2.8963092606511032136e3, 0.0)}, {FN (cot), ARG(3.45266983001243932001e-04,0.0e+00), RES(2.8963092606511032136e3, 0.0)}, {FN (cot), ARG(-3.45266983001243932001e-04,1.19209289550781250e-07), RES(-2.8963089153841613713e3, -9.9999992052715532101e-1)}, {FN (cot), ARG(-3.45266983001243932001e-04,-1.19209289550781250e-07), RES(-2.8963089153841613713e3, 9.9999992052715532101e-1)}, {FN (cot), ARG(3.45266983001243932001e-04,1.19209289550781250e-07), RES(2.8963089153841613713e3, -9.9999992052715532101e-1)}, {FN (cot), ARG(3.45266983001243932001e-04,-1.19209289550781250e-07), RES(2.8963089153841613713e3, 9.9999992052715532101e-1)}, {FN (cot), ARG(-3.45266983001243932001e-04,5.0e-01), RES(-1.2715121175451222247e-3, -2.1639524637389326002e0)}, {FN (cot), ARG(-3.45266983001243932001e-04,-5.0e-01), RES(-1.2715121175451222247e-3, 2.1639524637389326002e0)}, {FN (cot), ARG(3.45266983001243932001e-04,5.0e-01), RES(1.2715121175451222247e-3, -2.1639524637389326002e0)}, {FN (cot), ARG(3.45266983001243932001e-04,-5.0e-01), RES(1.2715121175451222247e-3, 2.1639524637389326002e0)}, {FN (cot), ARG(-3.45266983001243932001e-04,1.0e+00), RES(-2.4999454374267620687e-4, -1.3130351721648674824e0)}, {FN (cot), ARG(-3.45266983001243932001e-04,-1.0e+00), RES(-2.4999454374267620687e-4, 1.3130351721648674824e0)}, {FN (cot), ARG(3.45266983001243932001e-04,1.0e+00), RES(2.4999454374267620687e-4, -1.3130351721648674824e0)}, {FN (cot), ARG(3.45266983001243932001e-04,-1.0e+00), RES(2.4999454374267620687e-4, 1.3130351721648674824e0)}, {FN (cot), ARG(-3.45266983001243932001e-04,2.0e+00), RES(-2.6247825506563736365e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(-3.45266983001243932001e-04,-2.0e+00), RES(-2.6247825506563736365e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(3.45266983001243932001e-04,2.0e+00), RES(2.6247825506563736365e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(3.45266983001243932001e-04,-2.0e+00), RES(2.6247825506563736365e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(1.57045105981189525579e+00,0.0e+00), RES(3.4526699672104134407e-4, 0.0)}, {FN (cot), ARG(-1.57045105981189525579e+00,0.0e+00), RES(-3.4526699672104134407e-4, 0.0)}, {FN (cot), ARG(1.57045105981189525579e+00,1.19209289550781250e-07), RES(3.4526699672103643753e-4, -1.1920930376163652990e-7)}, {FN (cot), ARG(1.57045105981189525579e+00,-1.19209289550781250e-07), RES(3.4526699672103643753e-4, 1.1920930376163652990e-7)}, {FN (cot), ARG(-1.57045105981189525579e+00,1.19209289550781250e-07), RES(-3.4526699672103643753e-4, -1.1920930376163652990e-7)}, {FN (cot), ARG(-1.57045105981189525579e+00,-1.19209289550781250e-07), RES(-3.4526699672103643753e-4, 1.1920930376163652990e-7)}, {FN (cot), ARG(1.57045105981189525579e+00,5.0e-01), RES(2.7153443992665204631e-4, -4.6211720058436229982e-1)}, {FN (cot), ARG(1.57045105981189525579e+00,-5.0e-01), RES(2.7153443992665204631e-4, 4.6211720058436229982e-1)}, {FN (cot), ARG(-1.57045105981189525579e+00,5.0e-01), RES(-2.7153443992665204631e-4, -4.6211720058436229982e-1)}, {FN (cot), ARG(-1.57045105981189525579e+00,-5.0e-01), RES(-2.7153443992665204631e-4, 4.6211720058436229982e-1)}, {FN (cot), ARG(1.57045105981189525579e+00,1.0e+00), RES(1.4500326960279979918e-4, -7.6159419408485704839e-1)}, {FN (cot), ARG(1.57045105981189525579e+00,-1.0e+00), RES(1.4500326960279979918e-4, 7.6159419408485704839e-1)}, {FN (cot), ARG(-1.57045105981189525579e+00,1.0e+00), RES(-1.4500326960279979918e-4, -7.6159419408485704839e-1)}, {FN (cot), ARG(-1.57045105981189525579e+00,-1.0e+00), RES(-1.4500326960279979918e-4, 7.6159419408485704839e-1)}, {FN (cot), ARG(1.57045105981189525579e+00,2.0e+00), RES(2.4393395410443750226e-5, -9.6402758819508310557e-1)}, {FN (cot), ARG(1.57045105981189525579e+00,-2.0e+00), RES(2.4393395410443750226e-5, 9.6402758819508310557e-1)}, {FN (cot), ARG(-1.57045105981189525579e+00,2.0e+00), RES(-2.4393395410443750226e-5, -9.6402758819508310557e-1)}, {FN (cot), ARG(-1.57045105981189525579e+00,-2.0e+00), RES(-2.4393395410443750226e-5, 9.6402758819508310557e-1)}, {FN (cot), ARG(1.57114159377789786021e+00,0.0e+00), RES(-3.4526699672091887937e-4, 0.0)}, {FN (cot), ARG(-1.57114159377789786021e+00,0.0e+00), RES(3.4526699672091887937e-4, 0.0)}, {FN (cot), ARG(1.57114159377789786021e+00,1.19209289550781250e-07), RES(-3.4526699672091397283e-4, -1.1920930376163652989e-7)}, {FN (cot), ARG(1.57114159377789786021e+00,-1.19209289550781250e-07), RES(-3.4526699672091397283e-4, 1.1920930376163652989e-7)}, {FN (cot), ARG(-1.57114159377789786021e+00,1.19209289550781250e-07), RES(3.4526699672091397283e-4, -1.1920930376163652989e-7)}, {FN (cot), ARG(-1.57114159377789786021e+00,-1.19209289550781250e-07), RES(3.4526699672091397283e-4, 1.1920930376163652989e-7)}, {FN (cot), ARG(1.57114159377789786021e+00,5.0e-01), RES(-2.7153443992655573423e-4, -4.6211720058436229979e-1)}, {FN (cot), ARG(1.57114159377789786021e+00,-5.0e-01), RES(-2.7153443992655573423e-4, 4.6211720058436229979e-1)}, {FN (cot), ARG(-1.57114159377789786021e+00,5.0e-01), RES(2.7153443992655573423e-4, -4.6211720058436229979e-1)}, {FN (cot), ARG(-1.57114159377789786021e+00,-5.0e-01), RES(2.7153443992655573423e-4, 4.6211720058436229979e-1)}, {FN (cot), ARG(1.57114159377789786021e+00,1.0e+00), RES(-1.4500326960274836716e-4, -7.6159419408485704836e-1)}, {FN (cot), ARG(1.57114159377789786021e+00,-1.0e+00), RES(-1.4500326960274836716e-4, 7.6159419408485704836e-1)}, {FN (cot), ARG(-1.57114159377789786021e+00,1.0e+00), RES(1.4500326960274836716e-4, -7.6159419408485704836e-1)}, {FN (cot), ARG(-1.57114159377789786021e+00,-1.0e+00), RES(1.4500326960274836716e-4, 7.6159419408485704836e-1)}, {FN (cot), ARG(1.57114159377789786021e+00,2.0e+00), RES(-2.4393395410435097997e-5, -9.6402758819508310556e-1)}, {FN (cot), ARG(1.57114159377789786021e+00,-2.0e+00), RES(-2.4393395410435097997e-5, 9.6402758819508310556e-1)}, {FN (cot), ARG(-1.57114159377789786021e+00,2.0e+00), RES(2.4393395410435097997e-5, -9.6402758819508310556e-1)}, {FN (cot), ARG(-1.57114159377789786021e+00,-2.0e+00), RES(2.4393395410435097997e-5, 9.6402758819508310556e-1)}, {FN (cot), ARG(3.14124738660679181379e+00,0.0e+00), RES(-2.8963092606495870519e3, 0.0)}, {FN (cot), ARG(-3.14124738660679181379e+00,0.0e+00), RES(2.8963092606495870519e3, 0.0)}, {FN (cot), ARG(3.14124738660679181379e+00,1.19209289550781250e-07), RES(-2.8963089153826452102e3, -9.9999992052610836018e-1)}, {FN (cot), ARG(3.14124738660679181379e+00,-1.19209289550781250e-07), RES(-2.8963089153826452102e3, 9.9999992052610836018e-1)}, {FN (cot), ARG(-3.14124738660679181379e+00,1.19209289550781250e-07), RES(2.8963089153826452102e3, -9.9999992052610836018e-1)}, {FN (cot), ARG(-3.14124738660679181379e+00,-1.19209289550781250e-07), RES(2.8963089153826452102e3, 9.9999992052610836018e-1)}, {FN (cot), ARG(3.14124738660679181379e+00,5.0e-01), RES(-1.2715121175457878359e-3, -2.1639524637389325992e0)}, {FN (cot), ARG(3.14124738660679181379e+00,-5.0e-01), RES(-1.2715121175457878359e-3, 2.1639524637389325992e0)}, {FN (cot), ARG(-3.14124738660679181379e+00,5.0e-01), RES(1.2715121175457878359e-3, -2.1639524637389325992e0)}, {FN (cot), ARG(-3.14124738660679181379e+00,-5.0e-01), RES(1.2715121175457878359e-3, 2.1639524637389325992e0)}, {FN (cot), ARG(3.14124738660679181379e+00,1.0e+00), RES(-2.4999454374280707411e-4, -1.3130351721648674823e0)}, {FN (cot), ARG(3.14124738660679181379e+00,-1.0e+00), RES(-2.4999454374280707411e-4, 1.3130351721648674823e0)}, {FN (cot), ARG(-3.14124738660679181379e+00,1.0e+00), RES(2.4999454374280707411e-4, -1.3130351721648674823e0)}, {FN (cot), ARG(-3.14124738660679181379e+00,-1.0e+00), RES(2.4999454374280707411e-4, 1.3130351721648674823e0)}, {FN (cot), ARG(3.14124738660679181379e+00,2.0e+00), RES(-2.6247825506577476589e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(3.14124738660679181379e+00,-2.0e+00), RES(-2.6247825506577476589e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(-3.14124738660679181379e+00,2.0e+00), RES(2.6247825506577476589e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(-3.14124738660679181379e+00,-2.0e+00), RES(2.6247825506577476589e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(3.14193792057279441821e+00,0.0e+00), RES(2.8963092606516416684e3, 0.0)}, {FN (cot), ARG(-3.14193792057279441821e+00,0.0e+00), RES(-2.8963092606516416684e3, 0.0)}, {FN (cot), ARG(3.14193792057279441821e+00,1.19209289550781250e-07), RES(2.8963089153846998260e3, -9.9999992052752714224e-1)}, {FN (cot), ARG(3.14193792057279441821e+00,-1.19209289550781250e-07), RES(2.8963089153846998260e3, 9.9999992052752714224e-1)}, {FN (cot), ARG(-3.14193792057279441821e+00,1.19209289550781250e-07), RES(-2.8963089153846998260e3, -9.9999992052752714224e-1)}, {FN (cot), ARG(-3.14193792057279441821e+00,-1.19209289550781250e-07), RES(-2.8963089153846998260e3, 9.9999992052752714224e-1)}, {FN (cot), ARG(3.14193792057279441821e+00,5.0e-01), RES(1.2715121175448858373e-3, -2.1639524637389326006e0)}, {FN (cot), ARG(3.14193792057279441821e+00,-5.0e-01), RES(1.2715121175448858373e-3, 2.1639524637389326006e0)}, {FN (cot), ARG(-3.14193792057279441821e+00,5.0e-01), RES(-1.2715121175448858373e-3, -2.1639524637389326006e0)}, {FN (cot), ARG(-3.14193792057279441821e+00,-5.0e-01), RES(-1.2715121175448858373e-3, 2.1639524637389326006e0)}, {FN (cot), ARG(3.14193792057279441821e+00,1.0e+00), RES(2.4999454374262973024e-4, -1.3130351721648674824e0)}, {FN (cot), ARG(3.14193792057279441821e+00,-1.0e+00), RES(2.4999454374262973024e-4, 1.3130351721648674824e0)}, {FN (cot), ARG(-3.14193792057279441821e+00,1.0e+00), RES(-2.4999454374262973024e-4, -1.3130351721648674824e0)}, {FN (cot), ARG(-3.14193792057279441821e+00,-1.0e+00), RES(-2.4999454374262973024e-4, 1.3130351721648674824e0)}, {FN (cot), ARG(3.14193792057279441821e+00,2.0e+00), RES(2.6247825506558856616e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(3.14193792057279441821e+00,-2.0e+00), RES(2.6247825506558856616e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(-3.14193792057279441821e+00,2.0e+00), RES(-2.6247825506558856616e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(-3.14193792057279441821e+00,-2.0e+00), RES(-2.6247825506558856616e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(4.71204371340168837179e+00,0.0e+00), RES(3.4526699672116380876e-4, 0.0)}, {FN (cot), ARG(-4.71204371340168837179e+00,0.0e+00), RES(-3.4526699672116380876e-4, 0.0)}, {FN (cot), ARG(4.71204371340168837179e+00,1.19209289550781250e-07), RES(3.4526699672115890222e-4, -1.1920930376163652991e-7)}, {FN (cot), ARG(4.71204371340168837179e+00,-1.19209289550781250e-07), RES(3.4526699672115890222e-4, 1.1920930376163652991e-7)}, {FN (cot), ARG(-4.71204371340168837179e+00,1.19209289550781250e-07), RES(-3.4526699672115890222e-4, -1.1920930376163652991e-7)}, {FN (cot), ARG(-4.71204371340168837179e+00,-1.19209289550781250e-07), RES(-3.4526699672115890222e-4, 1.1920930376163652991e-7)}, {FN (cot), ARG(4.71204371340168837179e+00,5.0e-01), RES(2.7153443992674835838e-4, -4.6211720058436229985e-1)}, {FN (cot), ARG(4.71204371340168837179e+00,-5.0e-01), RES(2.7153443992674835838e-4, 4.6211720058436229985e-1)}, {FN (cot), ARG(-4.71204371340168837179e+00,5.0e-01), RES(-2.7153443992674835838e-4, -4.6211720058436229985e-1)}, {FN (cot), ARG(-4.71204371340168837179e+00,-5.0e-01), RES(-2.7153443992674835838e-4, 4.6211720058436229985e-1)}, {FN (cot), ARG(4.71204371340168837179e+00,1.0e+00), RES(1.4500326960285123120e-4, -7.6159419408485704842e-1)}, {FN (cot), ARG(4.71204371340168837179e+00,-1.0e+00), RES(1.4500326960285123120e-4, 7.6159419408485704842e-1)}, {FN (cot), ARG(-4.71204371340168837179e+00,1.0e+00), RES(-1.4500326960285123120e-4, -7.6159419408485704842e-1)}, {FN (cot), ARG(-4.71204371340168837179e+00,-1.0e+00), RES(-1.4500326960285123120e-4, 7.6159419408485704842e-1)}, {FN (cot), ARG(4.71204371340168837179e+00,2.0e+00), RES(2.4393395410452402454e-5, -9.6402758819508310557e-1)}, {FN (cot), ARG(4.71204371340168837179e+00,-2.0e+00), RES(2.4393395410452402454e-5, 9.6402758819508310557e-1)}, {FN (cot), ARG(-4.71204371340168837179e+00,2.0e+00), RES(-2.4393395410452402454e-5, -9.6402758819508310557e-1)}, {FN (cot), ARG(-4.71204371340168837179e+00,-2.0e+00), RES(-2.4393395410452402454e-5, 9.6402758819508310557e-1)}, {FN (cot), ARG(4.71273424736769097620e+00,0.0e+00), RES(-3.4526699672079641468e-4, 0.0)}, {FN (cot), ARG(-4.71273424736769097620e+00,0.0e+00), RES(3.4526699672079641468e-4, 0.0)}, {FN (cot), ARG(4.71273424736769097620e+00,1.19209289550781250e-07), RES(-3.4526699672079150814e-4, -1.1920930376163652988e-7)}, {FN (cot), ARG(4.71273424736769097620e+00,-1.19209289550781250e-07), RES(-3.4526699672079150814e-4, 1.1920930376163652988e-7)}, {FN (cot), ARG(-4.71273424736769097620e+00,1.19209289550781250e-07), RES(3.4526699672079150814e-4, -1.1920930376163652988e-7)}, {FN (cot), ARG(-4.71273424736769097620e+00,-1.19209289550781250e-07), RES(3.4526699672079150814e-4, 1.1920930376163652988e-7)}, {FN (cot), ARG(4.71273424736769097620e+00,5.0e-01), RES(-2.7153443992645942216e-4, -4.6211720058436229976e-1)}, {FN (cot), ARG(4.71273424736769097620e+00,-5.0e-01), RES(-2.7153443992645942216e-4, 4.6211720058436229976e-1)}, {FN (cot), ARG(-4.71273424736769097620e+00,5.0e-01), RES(2.7153443992645942216e-4, -4.6211720058436229976e-1)}, {FN (cot), ARG(-4.71273424736769097620e+00,-5.0e-01), RES(2.7153443992645942216e-4, 4.6211720058436229976e-1)}, {FN (cot), ARG(4.71273424736769097620e+00,1.0e+00), RES(-1.4500326960269693514e-4, -7.6159419408485704834e-1)}, {FN (cot), ARG(4.71273424736769097620e+00,-1.0e+00), RES(-1.4500326960269693514e-4, 7.6159419408485704834e-1)}, {FN (cot), ARG(-4.71273424736769097620e+00,1.0e+00), RES(1.4500326960269693514e-4, -7.6159419408485704834e-1)}, {FN (cot), ARG(-4.71273424736769097620e+00,-1.0e+00), RES(1.4500326960269693514e-4, 7.6159419408485704834e-1)}, {FN (cot), ARG(4.71273424736769097620e+00,2.0e+00), RES(-2.4393395410426445768e-5, -9.6402758819508310556e-1)}, {FN (cot), ARG(4.71273424736769097620e+00,-2.0e+00), RES(-2.4393395410426445768e-5, 9.6402758819508310556e-1)}, {FN (cot), ARG(-4.71273424736769097620e+00,2.0e+00), RES(2.4393395410426445768e-5, -9.6402758819508310556e-1)}, {FN (cot), ARG(-4.71273424736769097620e+00,-2.0e+00), RES(2.4393395410426445768e-5, 9.6402758819508310556e-1)}, {FN (cot), ARG(6.28284004019658492979e+00,0.0e+00), RES(-2.8963092606485597437e3, 0.0)}, {FN (cot), ARG(-6.28284004019658492979e+00,0.0e+00), RES(2.8963092606485597437e3, 0.0)}, {FN (cot), ARG(6.28284004019658492979e+00,1.19209289550781250e-07), RES(-2.8963089153816179024e3, -9.9999992052539896914e-1)}, {FN (cot), ARG(6.28284004019658492979e+00,-1.19209289550781250e-07), RES(-2.8963089153816179024e3, 9.9999992052539896914e-1)}, {FN (cot), ARG(-6.28284004019658492979e+00,1.19209289550781250e-07), RES(2.8963089153816179024e3, -9.9999992052539896914e-1)}, {FN (cot), ARG(-6.28284004019658492979e+00,-1.19209289550781250e-07), RES(2.8963089153816179024e3, 9.9999992052539896914e-1)}, {FN (cot), ARG(6.28284004019658492979e+00,5.0e-01), RES(-1.2715121175462388352e-3, -2.1639524637389325986e0)}, {FN (cot), ARG(6.28284004019658492979e+00,-5.0e-01), RES(-1.2715121175462388352e-3, 2.1639524637389325986e0)}, {FN (cot), ARG(-6.28284004019658492979e+00,5.0e-01), RES(1.2715121175462388352e-3, -2.1639524637389325986e0)}, {FN (cot), ARG(-6.28284004019658492979e+00,-5.0e-01), RES(1.2715121175462388352e-3, 2.1639524637389325986e0)}, {FN (cot), ARG(6.28284004019658492979e+00,1.0e+00), RES(-2.4999454374289574604e-4, -1.3130351721648674822e0)}, {FN (cot), ARG(6.28284004019658492979e+00,-1.0e+00), RES(-2.4999454374289574604e-4, 1.3130351721648674822e0)}, {FN (cot), ARG(-6.28284004019658492979e+00,1.0e+00), RES(2.4999454374289574604e-4, -1.3130351721648674822e0)}, {FN (cot), ARG(-6.28284004019658492979e+00,-1.0e+00), RES(2.4999454374289574604e-4, 1.3130351721648674822e0)}, {FN (cot), ARG(6.28284004019658492979e+00,2.0e+00), RES(-2.6247825506586786575e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(6.28284004019658492979e+00,-2.0e+00), RES(-2.6247825506586786575e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(-6.28284004019658492979e+00,2.0e+00), RES(2.6247825506586786575e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(-6.28284004019658492979e+00,-2.0e+00), RES(2.6247825506586786575e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(6.28353057416258753420e+00,0.0e+00), RES(2.8963092606526689766e3, 0.0)}, {FN (cot), ARG(-6.28353057416258753420e+00,0.0e+00), RES(-2.8963092606526689766e3, 0.0)}, {FN (cot), ARG(6.28353057416258753420e+00,1.19209289550781250e-07), RES(2.8963089153857271338e3, -9.9999992052823653327e-1)}, {FN (cot), ARG(6.28353057416258753420e+00,-1.19209289550781250e-07), RES(2.8963089153857271338e3, 9.9999992052823653327e-1)}, {FN (cot), ARG(-6.28353057416258753420e+00,1.19209289550781250e-07), RES(-2.8963089153857271338e3, -9.9999992052823653327e-1)}, {FN (cot), ARG(-6.28353057416258753420e+00,-1.19209289550781250e-07), RES(-2.8963089153857271338e3, 9.9999992052823653327e-1)}, {FN (cot), ARG(6.28353057416258753420e+00,5.0e-01), RES(1.2715121175444348380e-3, -2.1639524637389326012e0)}, {FN (cot), ARG(6.28353057416258753420e+00,-5.0e-01), RES(1.2715121175444348380e-3, 2.1639524637389326012e0)}, {FN (cot), ARG(-6.28353057416258753420e+00,5.0e-01), RES(-1.2715121175444348380e-3, -2.1639524637389326012e0)}, {FN (cot), ARG(-6.28353057416258753420e+00,-5.0e-01), RES(-1.2715121175444348380e-3, 2.1639524637389326012e0)}, {FN (cot), ARG(6.28353057416258753420e+00,1.0e+00), RES(2.4999454374254105830e-4, -1.3130351721648674825e0)}, {FN (cot), ARG(6.28353057416258753420e+00,-1.0e+00), RES(2.4999454374254105830e-4, 1.3130351721648674825e0)}, {FN (cot), ARG(-6.28353057416258753420e+00,1.0e+00), RES(-2.4999454374254105830e-4, -1.3130351721648674825e0)}, {FN (cot), ARG(-6.28353057416258753420e+00,-1.0e+00), RES(-2.4999454374254105830e-4, 1.3130351721648674825e0)}, {FN (cot), ARG(6.28353057416258753420e+00,2.0e+00), RES(2.6247825506549546629e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(6.28353057416258753420e+00,-2.0e+00), RES(2.6247825506549546629e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(-6.28353057416258753420e+00,2.0e+00), RES(-2.6247825506549546629e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(-6.28353057416258753420e+00,-2.0e+00), RES(-2.6247825506549546629e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(9.42443269378637893396e+00,0.0e+00), RES(-2.8963092606549830163e3, 0.0)}, {FN (cot), ARG(-9.42443269378637893396e+00,0.0e+00), RES(2.8963092606549830163e3, 0.0)}, {FN (cot), ARG(9.42443269378637893396e+00,1.19209289550781250e-07), RES(-2.8963089153880411727e3, -9.9999992052983445585e-1)}, {FN (cot), ARG(9.42443269378637893396e+00,-1.19209289550781250e-07), RES(-2.8963089153880411727e3, 9.9999992052983445585e-1)}, {FN (cot), ARG(-9.42443269378637893396e+00,1.19209289550781250e-07), RES(2.8963089153880411727e3, -9.9999992052983445585e-1)}, {FN (cot), ARG(-9.42443269378637893396e+00,-1.19209289550781250e-07), RES(2.8963089153880411727e3, 9.9999992052983445585e-1)}, {FN (cot), ARG(9.42443269378637893396e+00,5.0e-01), RES(-1.2715121175434189499e-3, -2.1639524637389326028e0)}, {FN (cot), ARG(9.42443269378637893396e+00,-5.0e-01), RES(-1.2715121175434189499e-3, 2.1639524637389326028e0)}, {FN (cot), ARG(-9.42443269378637893396e+00,5.0e-01), RES(1.2715121175434189499e-3, -2.1639524637389326028e0)}, {FN (cot), ARG(-9.42443269378637893396e+00,-5.0e-01), RES(1.2715121175434189499e-3, 2.1639524637389326028e0)}, {FN (cot), ARG(9.42443269378637893396e+00,1.0e+00), RES(-2.4999454374234132236e-4, -1.3130351721648674827e0)}, {FN (cot), ARG(9.42443269378637893396e+00,-1.0e+00), RES(-2.4999454374234132236e-4, 1.3130351721648674827e0)}, {FN (cot), ARG(-9.42443269378637893396e+00,1.0e+00), RES(2.4999454374234132236e-4, -1.3130351721648674827e0)}, {FN (cot), ARG(-9.42443269378637893396e+00,-1.0e+00), RES(2.4999454374234132236e-4, 1.3130351721648674827e0)}, {FN (cot), ARG(9.42443269378637893396e+00,2.0e+00), RES(-2.6247825506528575631e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(9.42443269378637893396e+00,-2.0e+00), RES(-2.6247825506528575631e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(-9.42443269378637893396e+00,2.0e+00), RES(2.6247825506528575631e-5, -1.0373147113268752620e0)}, {FN (cot), ARG(-9.42443269378637893396e+00,-2.0e+00), RES(2.6247825506528575631e-5, 1.0373147113268752620e0)}, {FN (cot), ARG(9.42512322775237976202e+00,0.0e+00), RES(2.8963092606611468657e3, 0.0)}, {FN (cot), ARG(-9.42512322775237976202e+00,0.0e+00), RES(-2.8963092606611468657e3, 0.0)}, {FN (cot), ARG(9.42512322775237976202e+00,1.19209289550781250e-07), RES(2.8963089153942050199e3, -9.9999992053409080205e-1)}, {FN (cot), ARG(9.42512322775237976202e+00,-1.19209289550781250e-07), RES(2.8963089153942050199e3, 9.9999992053409080205e-1)}, {FN (cot), ARG(-9.42512322775237976202e+00,1.19209289550781250e-07), RES(-2.8963089153942050199e3, -9.9999992053409080205e-1)}, {FN (cot), ARG(-9.42512322775237976202e+00,-1.19209289550781250e-07), RES(-2.8963089153942050199e3, 9.9999992053409080205e-1)}, {FN (cot), ARG(9.42512322775237976202e+00,5.0e-01), RES(1.2715121175407129542e-3, -2.1639524637389326068e0)}, {FN (cot), ARG(9.42512322775237976202e+00,-5.0e-01), RES(1.2715121175407129542e-3, 2.1639524637389326068e0)}, {FN (cot), ARG(-9.42512322775237976202e+00,5.0e-01), RES(-1.2715121175407129542e-3, -2.1639524637389326068e0)}, {FN (cot), ARG(-9.42512322775237976202e+00,-5.0e-01), RES(-1.2715121175407129542e-3, 2.1639524637389326068e0)}, {FN (cot), ARG(9.42512322775237976202e+00,1.0e+00), RES(2.4999454374180929074e-4, -1.3130351721648674832e0)}, {FN (cot), ARG(9.42512322775237976202e+00,-1.0e+00), RES(2.4999454374180929074e-4, 1.3130351721648674832e0)}, {FN (cot), ARG(-9.42512322775237976202e+00,1.0e+00), RES(-2.4999454374180929074e-4, -1.3130351721648674832e0)}, {FN (cot), ARG(-9.42512322775237976202e+00,-1.0e+00), RES(-2.4999454374180929074e-4, 1.3130351721648674832e0)}, {FN (cot), ARG(9.42512322775237976202e+00,2.0e+00), RES(2.6247825506472715712e-5, -1.0373147113268752621e0)}, {FN (cot), ARG(9.42512322775237976202e+00,-2.0e+00), RES(2.6247825506472715712e-5, 1.0373147113268752621e0)}, {FN (cot), ARG(-9.42512322775237976202e+00,2.0e+00), RES(-2.6247825506472715712e-5, -1.0373147113268752621e0)}, {FN (cot), ARG(-9.42512322775237976202e+00,-2.0e+00), RES(-2.6247825506472715712e-5, 1.0373147113268752621e0)}, {FN (arccsc), ARG(0.0e+00,1.19209289550781250e-07), RES(0, -1.6635532333438690979e1)}, {FN (arccsc), ARG(0.0e+00,-1.19209289550781250e-07), RES(0, 1.6635532333438690979e1)}, {FN (arccsc), ARG(0.0e+00,5.0e-01), RES(0, -1.4436354751788103425e0)}, {FN (arccsc), ARG(0.0e+00,-5.0e-01), RES(0, 1.4436354751788103425e0)}, {FN (arccsc), ARG(0.0e+00,1.0e+00), RES(0, -8.8137358701954302523e-1)}, {FN (arccsc), ARG(0.0e+00,-1.0e+00), RES(0, 8.8137358701954302523e-1)}, {FN (arccsc), ARG(0.0e+00,2.0e+00), RES(0, -4.8121182505960344750e-1)}, {FN (arccsc), ARG(0.0e+00,-2.0e+00), RES(0, 4.8121182505960344750e-1)}, {FN (arccsc), ARG(0.0e+00,8.3886080e+06), RES(0, -1.1920928955078096766e-7)}, {FN (arccsc), ARG(0.0e+00,-8.3886080e+06), RES(0, 1.1920928955078096766e-7)}, {FN (arccsc), ARG(1.19209289550781250e-07,0.0e+00), RES(1.5707963267948966192e0, -1.6635532333438683873e1)}, {FN (arccsc), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.5707963267948966192e0, 1.6635532333438683873e1)}, {FN (arccsc), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(7.8539816339744120419e-1, -1.6288958743158714771e1)}, {FN (arccsc), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(7.8539816339744120419e-1, 1.6288958743158714771e1)}, {FN (arccsc), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-7.8539816339744120419e-1, -1.6288958743158714771e1)}, {FN (arccsc), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-7.8539816339744120419e-1, 1.6288958743158714771e1)}, {FN (arccsc), ARG(1.19209289550781250e-07,5.0e-01), RES(2.1324805998799710740e-7, -1.4436354751787798371e0)}, {FN (arccsc), ARG(1.19209289550781250e-07,-5.0e-01), RES(2.1324805998799710740e-7, 1.4436354751787798371e0)}, {FN (arccsc), ARG(-1.19209289550781250e-07,5.0e-01), RES(-2.1324805998799710740e-7, -1.4436354751787798371e0)}, {FN (arccsc), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-2.1324805998799710740e-7, 1.4436354751787798371e0)}, {FN (arccsc), ARG(1.19209289550781250e-07,1.0e+00), RES(8.4293697021787414719e-8, -8.8137358701953548879e-1)}, {FN (arccsc), ARG(1.19209289550781250e-07,-1.0e+00), RES(8.4293697021787414719e-8, 8.8137358701953548879e-1)}, {FN (arccsc), ARG(-1.19209289550781250e-07,1.0e+00), RES(-8.4293697021787414719e-8, -8.8137358701953548879e-1)}, {FN (arccsc), ARG(-1.19209289550781250e-07,-1.0e+00), RES(-8.4293697021787414719e-8, 8.8137358701953548879e-1)}, {FN (arccsc), ARG(1.19209289550781250e-07,2.0e+00), RES(2.6656007498500149811e-8, -4.8121182505960201756e-1)}, {FN (arccsc), ARG(1.19209289550781250e-07,-2.0e+00), RES(2.6656007498500149811e-8, 4.8121182505960201756e-1)}, {FN (arccsc), ARG(-1.19209289550781250e-07,2.0e+00), RES(-2.6656007498500149811e-8, -4.8121182505960201756e-1)}, {FN (arccsc), ARG(-1.19209289550781250e-07,-2.0e+00), RES(-2.6656007498500149811e-8, 4.8121182505960201756e-1)}, {FN (arccsc), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.6940658945085886411e-21, -1.1920928955078096766e-7)}, {FN (arccsc), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.6940658945085886411e-21, 1.1920928955078096766e-7)}, {FN (arccsc), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(-1.6940658945085886411e-21, -1.1920928955078096766e-7)}, {FN (arccsc), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(-1.6940658945085886411e-21, 1.1920928955078096766e-7)}, {FN (arccsc), ARG(5.0e-01,0.0e+00), RES(1.5707963267948966192e0, -1.3169578969248167086e0)}, {FN (arccsc), ARG(-5.0e-01,0.0e+00), RES(-1.5707963267948966192e0, 1.3169578969248167086e0)}, {FN (arccsc), ARG(5.0e-01,1.19209289550781250e-07), RES(1.5707960514928349710e0, -1.3169578969247948296e0)}, {FN (arccsc), ARG(5.0e-01,-1.19209289550781250e-07), RES(1.5707960514928349710e0, 1.3169578969247948296e0)}, {FN (arccsc), ARG(-5.0e-01,1.19209289550781250e-07), RES(-1.5707960514928349710e0, -1.3169578969247948296e0)}, {FN (arccsc), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-1.5707960514928349710e0, 1.3169578969247948296e0)}, {FN (arccsc), ARG(5.0e-01,5.0e-01), RES(6.6623943249251525510e-1, -1.0612750619050356520e0)}, {FN (arccsc), ARG(5.0e-01,-5.0e-01), RES(6.6623943249251525510e-1, 1.0612750619050356520e0)}, {FN (arccsc), ARG(-5.0e-01,5.0e-01), RES(-6.6623943249251525510e-1, -1.0612750619050356520e0)}, {FN (arccsc), ARG(-5.0e-01,-5.0e-01), RES(-6.6623943249251525510e-1, 1.0612750619050356520e0)}, {FN (arccsc), ARG(5.0e-01,1.0e+00), RES(3.1122579724476109533e-1, -7.6388434595371104541e-1)}, {FN (arccsc), ARG(5.0e-01,-1.0e+00), RES(3.1122579724476109533e-1, 7.6388434595371104541e-1)}, {FN (arccsc), ARG(-5.0e-01,1.0e+00), RES(-3.1122579724476109533e-1, -7.6388434595371104541e-1)}, {FN (arccsc), ARG(-5.0e-01,-1.0e+00), RES(-3.1122579724476109533e-1, 7.6388434595371104541e-1)}, {FN (arccsc), ARG(5.0e-01,2.0e+00), RES(1.0654050295275703990e-1, -4.5717847686917515748e-1)}, {FN (arccsc), ARG(5.0e-01,-2.0e+00), RES(1.0654050295275703990e-1, 4.5717847686917515748e-1)}, {FN (arccsc), ARG(-5.0e-01,2.0e+00), RES(-1.0654050295275703990e-1, -4.5717847686917515748e-1)}, {FN (arccsc), ARG(-5.0e-01,-2.0e+00), RES(-1.0654050295275703990e-1, 4.5717847686917515748e-1)}, {FN (arccsc), ARG(5.0e-01,8.3886080e+06), RES(7.1054273576009261281e-15, -1.1920928955078054414e-7)}, {FN (arccsc), ARG(5.0e-01,-8.3886080e+06), RES(7.1054273576009261281e-15, 1.1920928955078054414e-7)}, {FN (arccsc), ARG(-5.0e-01,8.3886080e+06), RES(-7.1054273576009261281e-15, -1.1920928955078054414e-7)}, {FN (arccsc), ARG(-5.0e-01,-8.3886080e+06), RES(-7.1054273576009261281e-15, 1.1920928955078054414e-7)}, {FN (arccsc), ARG(1.0e+00,0.0e+00), RES(1.5707963267948966192e0, 0.0)}, {FN (arccsc), ARG(-1.0e+00,0.0e+00), RES(-1.5707963267948966192e0, 0.0)}, {FN (arccsc), ARG(1.0e+00,1.19209289550781250e-07), RES(1.5704510597947457801e0, -3.4526696585164602772e-4)}, {FN (arccsc), ARG(1.0e+00,-1.19209289550781250e-07), RES(1.5704510597947457801e0, 3.4526696585164602772e-4)}, {FN (arccsc), ARG(-1.0e+00,1.19209289550781250e-07), RES(-1.5704510597947457801e0, -3.4526696585164602772e-4)}, {FN (arccsc), ARG(-1.0e+00,-1.19209289550781250e-07), RES(-1.5704510597947457801e0, 3.4526696585164602772e-4)}, {FN (arccsc), ARG(1.0e+00,5.0e-01), RES(7.7308635671950473342e-1, -5.3321829058411214108e-1)}, {FN (arccsc), ARG(1.0e+00,-5.0e-01), RES(7.7308635671950473342e-1, 5.3321829058411214108e-1)}, {FN (arccsc), ARG(-1.0e+00,5.0e-01), RES(-7.7308635671950473342e-1, -5.3321829058411214108e-1)}, {FN (arccsc), ARG(-1.0e+00,-5.0e-01), RES(-7.7308635671950473342e-1, 5.3321829058411214108e-1)}, {FN (arccsc), ARG(1.0e+00,1.0e+00), RES(4.5227844715119068206e-1, -5.3063753095251782602e-1)}, {FN (arccsc), ARG(1.0e+00,-1.0e+00), RES(4.5227844715119068206e-1, 5.3063753095251782602e-1)}, {FN (arccsc), ARG(-1.0e+00,1.0e+00), RES(-4.5227844715119068206e-1, -5.3063753095251782602e-1)}, {FN (arccsc), ARG(-1.0e+00,-1.0e+00), RES(-4.5227844715119068206e-1, 5.3063753095251782602e-1)}, {FN (arccsc), ARG(1.0e+00,2.0e+00), RES(1.8631805410781552582e-1, -3.9656823011232897892e-1)}, {FN (arccsc), ARG(1.0e+00,-2.0e+00), RES(1.8631805410781552582e-1, 3.9656823011232897892e-1)}, {FN (arccsc), ARG(-1.0e+00,2.0e+00), RES(-1.8631805410781552582e-1, -3.9656823011232897892e-1)}, {FN (arccsc), ARG(-1.0e+00,-2.0e+00), RES(-1.8631805410781552582e-1, 3.9656823011232897892e-1)}, {FN (arccsc), ARG(1.0e+00,8.3886080e+06), RES(1.4210854715201700795e-14, -1.1920928955077927359e-7)}, {FN (arccsc), ARG(1.0e+00,-8.3886080e+06), RES(1.4210854715201700795e-14, 1.1920928955077927359e-7)}, {FN (arccsc), ARG(-1.0e+00,8.3886080e+06), RES(-1.4210854715201700795e-14, -1.1920928955077927359e-7)}, {FN (arccsc), ARG(-1.0e+00,-8.3886080e+06), RES(-1.4210854715201700795e-14, 1.1920928955077927359e-7)}, {FN (arccsc), ARG(2.0e+00,0.0e+00), RES(5.2359877559829887308e-1, 0.0)}, {FN (arccsc), ARG(-2.0e+00,0.0e+00), RES(-5.2359877559829887308e-1, 0.0)}, {FN (arccsc), ARG(2.0e+00,1.19209289550781250e-07), RES(5.2359877559829648006e-1, -3.4412757706023621662e-8)}, {FN (arccsc), ARG(2.0e+00,-1.19209289550781250e-07), RES(5.2359877559829648006e-1, 3.4412757706023621662e-8)}, {FN (arccsc), ARG(-2.0e+00,1.19209289550781250e-07), RES(-5.2359877559829648006e-1, -3.4412757706023621662e-8)}, {FN (arccsc), ARG(-2.0e+00,-1.19209289550781250e-07), RES(-5.2359877559829648006e-1, 3.4412757706023621662e-8)}, {FN (arccsc), ARG(2.0e+00,5.0e-01), RES(4.8530734047334251250e-1, -1.3261586085051183885e-1)}, {FN (arccsc), ARG(2.0e+00,-5.0e-01), RES(4.8530734047334251250e-1, 1.3261586085051183885e-1)}, {FN (arccsc), ARG(-2.0e+00,5.0e-01), RES(-4.8530734047334251250e-1, -1.3261586085051183885e-1)}, {FN (arccsc), ARG(-2.0e+00,-5.0e-01), RES(-4.8530734047334251250e-1, 1.3261586085051183885e-1)}, {FN (arccsc), ARG(2.0e+00,1.0e+00), RES(4.0158639166780606828e-1, -2.1561241855582964497e-1)}, {FN (arccsc), ARG(2.0e+00,-1.0e+00), RES(4.0158639166780606828e-1, 2.1561241855582964497e-1)}, {FN (arccsc), ARG(-2.0e+00,1.0e+00), RES(-4.0158639166780606828e-1, -2.1561241855582964497e-1)}, {FN (arccsc), ARG(-2.0e+00,-1.0e+00), RES(-4.0158639166780606828e-1, 2.1561241855582964497e-1)}, {FN (arccsc), ARG(2.0e+00,2.0e+00), RES(2.4452216513554014646e-1, -2.5489557334055081773e-1)}, {FN (arccsc), ARG(2.0e+00,-2.0e+00), RES(2.4452216513554014646e-1, 2.5489557334055081773e-1)}, {FN (arccsc), ARG(-2.0e+00,2.0e+00), RES(-2.4452216513554014646e-1, -2.5489557334055081773e-1)}, {FN (arccsc), ARG(-2.0e+00,-2.0e+00), RES(-2.4452216513554014646e-1, 2.5489557334055081773e-1)}, {FN (arccsc), ARG(2.0e+00,8.3886080e+06), RES(2.8421709430402189899e-14, -1.1920928955077419139e-7)}, {FN (arccsc), ARG(2.0e+00,-8.3886080e+06), RES(2.8421709430402189899e-14, 1.1920928955077419139e-7)}, {FN (arccsc), ARG(-2.0e+00,8.3886080e+06), RES(-2.8421709430402189899e-14, -1.1920928955077419139e-7)}, {FN (arccsc), ARG(-2.0e+00,-8.3886080e+06), RES(-2.8421709430402189899e-14, 1.1920928955077419139e-7)}, {FN (arccsc), ARG(8.3886080e+06,0.0e+00), RES(1.1920928955078153234e-7, 0.0)}, {FN (arccsc), ARG(-8.3886080e+06,0.0e+00), RES(-1.1920928955078153234e-7, 0.0)}, {FN (arccsc), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.1920928955078153234e-7, -1.6940658945086127152e-21)}, {FN (arccsc), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.1920928955078153234e-7, 1.6940658945086127152e-21)}, {FN (arccsc), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(-1.1920928955078153234e-7, -1.6940658945086127152e-21)}, {FN (arccsc), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(-1.1920928955078153234e-7, 1.6940658945086127152e-21)}, {FN (arccsc), ARG(8.3886080e+06,5.0e-01), RES(1.1920928955078110883e-7, -7.1054273576010271023e-15)}, {FN (arccsc), ARG(8.3886080e+06,-5.0e-01), RES(1.1920928955078110883e-7, 7.1054273576010271023e-15)}, {FN (arccsc), ARG(-8.3886080e+06,5.0e-01), RES(-1.1920928955078110883e-7, -7.1054273576010271023e-15)}, {FN (arccsc), ARG(-8.3886080e+06,-5.0e-01), RES(-1.1920928955078110883e-7, 7.1054273576010271023e-15)}, {FN (arccsc), ARG(8.3886080e+06,1.0e+00), RES(1.1920928955077983828e-7, -1.4210854715201902743e-14)}, {FN (arccsc), ARG(8.3886080e+06,-1.0e+00), RES(1.1920928955077983828e-7, 1.4210854715201902743e-14)}, {FN (arccsc), ARG(-8.3886080e+06,1.0e+00), RES(-1.1920928955077983828e-7, -1.4210854715201902743e-14)}, {FN (arccsc), ARG(-8.3886080e+06,-1.0e+00), RES(-1.1920928955077983828e-7, 1.4210854715201902743e-14)}, {FN (arccsc), ARG(8.3886080e+06,2.0e+00), RES(1.1920928955077475608e-7, -2.8421709430402593796e-14)}, {FN (arccsc), ARG(8.3886080e+06,-2.0e+00), RES(1.1920928955077475608e-7, 2.8421709430402593796e-14)}, {FN (arccsc), ARG(-8.3886080e+06,2.0e+00), RES(-1.1920928955077475608e-7, -2.8421709430402593796e-14)}, {FN (arccsc), ARG(-8.3886080e+06,-2.0e+00), RES(-1.1920928955077475608e-7, 2.8421709430402593796e-14)}, {FN (arccsc), ARG(8.3886080e+06,8.3886080e+06), RES(5.9604644775390554414e-8, -5.9604644775390695586e-8)}, {FN (arccsc), ARG(8.3886080e+06,-8.3886080e+06), RES(5.9604644775390554414e-8, 5.9604644775390695586e-8)}, {FN (arccsc), ARG(-8.3886080e+06,8.3886080e+06), RES(-5.9604644775390554414e-8, -5.9604644775390695586e-8)}, {FN (arccsc), ARG(-8.3886080e+06,-8.3886080e+06), RES(-5.9604644775390554414e-8, 5.9604644775390695586e-8)}, {FN (arcsec), ARG(0.0e+00,1.19209289550781250e-07), RES(1.5707963267948966192e0, 1.6635532333438690979e1)}, {FN (arcsec), ARG(0.0e+00,-1.19209289550781250e-07), RES(1.5707963267948966192e0, -1.6635532333438690979e1)}, {FN (arcsec), ARG(0.0e+00,5.0e-01), RES(1.5707963267948966192e0, 1.4436354751788103425e0)}, {FN (arcsec), ARG(0.0e+00,-5.0e-01), RES(1.5707963267948966192e0, -1.4436354751788103425e0)}, {FN (arcsec), ARG(0.0e+00,1.0e+00), RES(1.5707963267948966192e0, 8.8137358701954302523e-1)}, {FN (arcsec), ARG(0.0e+00,-1.0e+00), RES(1.5707963267948966192e0, -8.8137358701954302523e-1)}, {FN (arcsec), ARG(0.0e+00,2.0e+00), RES(1.5707963267948966192e0, 4.8121182505960344750e-1)}, {FN (arcsec), ARG(0.0e+00,-2.0e+00), RES(1.5707963267948966192e0, -4.8121182505960344750e-1)}, {FN (arcsec), ARG(0.0e+00,8.3886080e+06), RES(1.5707963267948966192e0, 1.1920928955078096766e-7)}, {FN (arcsec), ARG(0.0e+00,-8.3886080e+06), RES(1.5707963267948966192e0, -1.1920928955078096766e-7)}, {FN (arcsec), ARG(1.19209289550781250e-07,0.0e+00), RES(0, 1.6635532333438683873e1)}, {FN (arcsec), ARG(-1.19209289550781250e-07,0.0e+00), RES(3.1415926535897932385e0, -1.6635532333438683873e1)}, {FN (arcsec), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(7.8539816339745541504e-1, 1.6288958743158714771e1)}, {FN (arcsec), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(7.8539816339745541504e-1, -1.6288958743158714771e1)}, {FN (arcsec), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(2.3561944901923378234e0, 1.6288958743158714771e1)}, {FN (arcsec), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(2.3561944901923378234e0, -1.6288958743158714771e1)}, {FN (arcsec), ARG(1.19209289550781250e-07,5.0e-01), RES(1.5707961135468366312e0, 1.4436354751787798371e0)}, {FN (arcsec), ARG(1.19209289550781250e-07,-5.0e-01), RES(1.5707961135468366312e0, -1.4436354751787798371e0)}, {FN (arcsec), ARG(-1.19209289550781250e-07,5.0e-01), RES(1.5707965400429566072e0, 1.4436354751787798371e0)}, {FN (arcsec), ARG(-1.19209289550781250e-07,-5.0e-01), RES(1.5707965400429566072e0, -1.4436354751787798371e0)}, {FN (arcsec), ARG(1.19209289550781250e-07,1.0e+00), RES(1.5707962425011995974e0, 8.8137358701953548879e-1)}, {FN (arcsec), ARG(1.19209289550781250e-07,-1.0e+00), RES(1.5707962425011995974e0, -8.8137358701953548879e-1)}, {FN (arcsec), ARG(-1.19209289550781250e-07,1.0e+00), RES(1.5707964110885936410e0, 8.8137358701953548879e-1)}, {FN (arcsec), ARG(-1.19209289550781250e-07,-1.0e+00), RES(1.5707964110885936410e0, -8.8137358701953548879e-1)}, {FN (arcsec), ARG(1.19209289550781250e-07,2.0e+00), RES(1.5707963001388891207e0, 4.8121182505960201756e-1)}, {FN (arcsec), ARG(1.19209289550781250e-07,-2.0e+00), RES(1.5707963001388891207e0, -4.8121182505960201756e-1)}, {FN (arcsec), ARG(-1.19209289550781250e-07,2.0e+00), RES(1.5707963534509041177e0, 4.8121182505960201756e-1)}, {FN (arcsec), ARG(-1.19209289550781250e-07,-2.0e+00), RES(1.5707963534509041177e0, -4.8121182505960201756e-1)}, {FN (arcsec), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.5707963267948966192e0, 1.1920928955078096766e-7)}, {FN (arcsec), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.5707963267948966192e0, -1.1920928955078096766e-7)}, {FN (arcsec), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(1.5707963267948966192e0, 1.1920928955078096766e-7)}, {FN (arcsec), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(1.5707963267948966192e0, -1.1920928955078096766e-7)}, {FN (arcsec), ARG(5.0e-01,0.0e+00), RES(0, 1.3169578969248167086e0)}, {FN (arcsec), ARG(-5.0e-01,0.0e+00), RES(3.1415926535897932385e0, -1.3169578969248167086e0)}, {FN (arcsec), ARG(5.0e-01,1.19209289550781250e-07), RES(2.7530206164818516969e-7, 1.3169578969247948296e0)}, {FN (arcsec), ARG(5.0e-01,-1.19209289550781250e-07), RES(2.7530206164818516969e-7, -1.3169578969247948296e0)}, {FN (arcsec), ARG(-5.0e-01,1.19209289550781250e-07), RES(3.1415923782877315903e0, 1.3169578969247948296e0)}, {FN (arcsec), ARG(-5.0e-01,-1.19209289550781250e-07), RES(3.1415923782877315903e0, -1.3169578969247948296e0)}, {FN (arcsec), ARG(5.0e-01,5.0e-01), RES(9.0455689430238136413e-1, 1.0612750619050356520e0)}, {FN (arcsec), ARG(5.0e-01,-5.0e-01), RES(9.0455689430238136413e-1, -1.0612750619050356520e0)}, {FN (arcsec), ARG(-5.0e-01,5.0e-01), RES(2.2370357592874118743e0, 1.0612750619050356520e0)}, {FN (arcsec), ARG(-5.0e-01,-5.0e-01), RES(2.2370357592874118743e0, -1.0612750619050356520e0)}, {FN (arcsec), ARG(5.0e-01,1.0e+00), RES(1.2595705295501355239e0, 7.6388434595371104541e-1)}, {FN (arcsec), ARG(5.0e-01,-1.0e+00), RES(1.2595705295501355239e0, -7.6388434595371104541e-1)}, {FN (arcsec), ARG(-5.0e-01,1.0e+00), RES(1.8820221240396577146e0, 7.6388434595371104541e-1)}, {FN (arcsec), ARG(-5.0e-01,-1.0e+00), RES(1.8820221240396577146e0, -7.6388434595371104541e-1)}, {FN (arcsec), ARG(5.0e-01,2.0e+00), RES(1.4642558238421395793e0, 4.5717847686917515748e-1)}, {FN (arcsec), ARG(5.0e-01,-2.0e+00), RES(1.4642558238421395793e0, -4.5717847686917515748e-1)}, {FN (arcsec), ARG(-5.0e-01,2.0e+00), RES(1.6773368297476536591e0, 4.5717847686917515748e-1)}, {FN (arcsec), ARG(-5.0e-01,-2.0e+00), RES(1.6773368297476536591e0, -4.5717847686917515748e-1)}, {FN (arcsec), ARG(5.0e-01,8.3886080e+06), RES(1.5707963267948895138e0, 1.1920928955078054414e-7)}, {FN (arcsec), ARG(5.0e-01,-8.3886080e+06), RES(1.5707963267948895138e0, -1.1920928955078054414e-7)}, {FN (arcsec), ARG(-5.0e-01,8.3886080e+06), RES(1.5707963267949037247e0, 1.1920928955078054414e-7)}, {FN (arcsec), ARG(-5.0e-01,-8.3886080e+06), RES(1.5707963267949037247e0, -1.1920928955078054414e-7)}, {FN (arcsec), ARG(1.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arcsec), ARG(-1.0e+00,0.0e+00), RES(3.1415926535897932385e0, 0.0)}, {FN (arcsec), ARG(1.0e+00,1.19209289550781250e-07), RES(3.4526700015083915182e-4, 3.4526696585164602772e-4)}, {FN (arcsec), ARG(1.0e+00,-1.19209289550781250e-07), RES(3.4526700015083915182e-4, -3.4526696585164602772e-4)}, {FN (arcsec), ARG(-1.0e+00,1.19209289550781250e-07), RES(3.1412473865896423993e0, 3.4526696585164602772e-4)}, {FN (arcsec), ARG(-1.0e+00,-1.19209289550781250e-07), RES(3.1412473865896423993e0, -3.4526696585164602772e-4)}, {FN (arcsec), ARG(1.0e+00,5.0e-01), RES(7.9770997007539188581e-1, 5.3321829058411214108e-1)}, {FN (arcsec), ARG(1.0e+00,-5.0e-01), RES(7.9770997007539188581e-1, -5.3321829058411214108e-1)}, {FN (arcsec), ARG(-1.0e+00,5.0e-01), RES(2.3438826835144013527e0, 5.3321829058411214108e-1)}, {FN (arcsec), ARG(-1.0e+00,-5.0e-01), RES(2.3438826835144013527e0, -5.3321829058411214108e-1)}, {FN (arcsec), ARG(1.0e+00,1.0e+00), RES(1.1185178796437059372e0, 5.3063753095251782602e-1)}, {FN (arcsec), ARG(1.0e+00,-1.0e+00), RES(1.1185178796437059372e0, -5.3063753095251782602e-1)}, {FN (arcsec), ARG(-1.0e+00,1.0e+00), RES(2.0230747739460873013e0, 5.3063753095251782602e-1)}, {FN (arcsec), ARG(-1.0e+00,-1.0e+00), RES(2.0230747739460873013e0, -5.3063753095251782602e-1)}, {FN (arcsec), ARG(1.0e+00,2.0e+00), RES(1.3844782726870810934e0, 3.9656823011232897892e-1)}, {FN (arcsec), ARG(1.0e+00,-2.0e+00), RES(1.3844782726870810934e0, -3.9656823011232897892e-1)}, {FN (arcsec), ARG(-1.0e+00,2.0e+00), RES(1.7571143809027121451e0, 3.9656823011232897892e-1)}, {FN (arcsec), ARG(-1.0e+00,-2.0e+00), RES(1.7571143809027121451e0, -3.9656823011232897892e-1)}, {FN (arcsec), ARG(1.0e+00,8.3886080e+06), RES(1.5707963267948824084e0, 1.1920928955077927359e-7)}, {FN (arcsec), ARG(1.0e+00,-8.3886080e+06), RES(1.5707963267948824084e0, -1.1920928955077927359e-7)}, {FN (arcsec), ARG(-1.0e+00,8.3886080e+06), RES(1.5707963267949108301e0, 1.1920928955077927359e-7)}, {FN (arcsec), ARG(-1.0e+00,-8.3886080e+06), RES(1.5707963267949108301e0, -1.1920928955077927359e-7)}, {FN (arcsec), ARG(2.0e+00,0.0e+00), RES(1.0471975511965977462e0, 0.0)}, {FN (arcsec), ARG(-2.0e+00,0.0e+00), RES(2.0943951023931954923e0, 0.0)}, {FN (arcsec), ARG(2.0e+00,1.19209289550781250e-07), RES(1.0471975511966001392e0, 3.4412757706023621662e-8)}, {FN (arcsec), ARG(2.0e+00,-1.19209289550781250e-07), RES(1.0471975511966001392e0, -3.4412757706023621662e-8)}, {FN (arcsec), ARG(-2.0e+00,1.19209289550781250e-07), RES(2.0943951023931930993e0, 3.4412757706023621662e-8)}, {FN (arcsec), ARG(-2.0e+00,-1.19209289550781250e-07), RES(2.0943951023931930993e0, -3.4412757706023621662e-8)}, {FN (arcsec), ARG(2.0e+00,5.0e-01), RES(1.0854889863215541067e0, 1.3261586085051183885e-1)}, {FN (arcsec), ARG(2.0e+00,-5.0e-01), RES(1.0854889863215541067e0, -1.3261586085051183885e-1)}, {FN (arcsec), ARG(-2.0e+00,5.0e-01), RES(2.0561036672682391317e0, 1.3261586085051183885e-1)}, {FN (arcsec), ARG(-2.0e+00,-5.0e-01), RES(2.0561036672682391317e0, -1.3261586085051183885e-1)}, {FN (arcsec), ARG(2.0e+00,1.0e+00), RES(1.1692099351270905509e0, 2.1561241855582964497e-1)}, {FN (arcsec), ARG(2.0e+00,-1.0e+00), RES(1.1692099351270905509e0, -2.1561241855582964497e-1)}, {FN (arcsec), ARG(-2.0e+00,1.0e+00), RES(1.9723827184627026875e0, 2.1561241855582964497e-1)}, {FN (arcsec), ARG(-2.0e+00,-1.0e+00), RES(1.9723827184627026875e0, -2.1561241855582964497e-1)}, {FN (arcsec), ARG(2.0e+00,2.0e+00), RES(1.3262741616593564728e0, 2.5489557334055081773e-1)}, {FN (arcsec), ARG(2.0e+00,-2.0e+00), RES(1.3262741616593564728e0, -2.5489557334055081773e-1)}, {FN (arcsec), ARG(-2.0e+00,2.0e+00), RES(1.8153184919304367657e0, 2.5489557334055081773e-1)}, {FN (arcsec), ARG(-2.0e+00,-2.0e+00), RES(1.8153184919304367657e0, -2.5489557334055081773e-1)}, {FN (arcsec), ARG(2.0e+00,8.3886080e+06), RES(1.5707963267948681975e0, 1.1920928955077419139e-7)}, {FN (arcsec), ARG(2.0e+00,-8.3886080e+06), RES(1.5707963267948681975e0, -1.1920928955077419139e-7)}, {FN (arcsec), ARG(-2.0e+00,8.3886080e+06), RES(1.5707963267949250409e0, 1.1920928955077419139e-7)}, {FN (arcsec), ARG(-2.0e+00,-8.3886080e+06), RES(1.5707963267949250409e0, -1.1920928955077419139e-7)}, {FN (arcsec), ARG(8.3886080e+06,0.0e+00), RES(1.5707962075856070684e0, 0.0)}, {FN (arcsec), ARG(-8.3886080e+06,0.0e+00), RES(1.570796446004186170e0, 0.0)}, {FN (arcsec), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.5707962075856070684e0, 1.6940658945086127152e-21)}, {FN (arcsec), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.5707962075856070684e0, -1.6940658945086127152e-21)}, {FN (arcsec), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(1.570796446004186170e0, 1.6940658945086127152e-21)}, {FN (arcsec), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(1.570796446004186170e0, -1.6940658945086127152e-21)}, {FN (arcsec), ARG(8.3886080e+06,5.0e-01), RES(1.5707962075856070685e0, 7.1054273576010271023e-15)}, {FN (arcsec), ARG(8.3886080e+06,-5.0e-01), RES(1.5707962075856070685e0, -7.1054273576010271023e-15)}, {FN (arcsec), ARG(-8.3886080e+06,5.0e-01), RES(1.570796446004186170e0, 7.1054273576010271023e-15)}, {FN (arcsec), ARG(-8.3886080e+06,-5.0e-01), RES(1.570796446004186170e0, -7.1054273576010271023e-15)}, {FN (arcsec), ARG(8.3886080e+06,1.0e+00), RES(1.5707962075856070685e0, 1.4210854715201902743e-14)}, {FN (arcsec), ARG(8.3886080e+06,-1.0e+00), RES(1.5707962075856070685e0, -1.4210854715201902743e-14)}, {FN (arcsec), ARG(-8.3886080e+06,1.0e+00), RES(1.570796446004186170e0, 1.4210854715201902743e-14)}, {FN (arcsec), ARG(-8.3886080e+06,-1.0e+00), RES(1.570796446004186170e0, -1.4210854715201902743e-14)}, {FN (arcsec), ARG(8.3886080e+06,2.0e+00), RES(1.5707962075856070685e0, 2.8421709430402593796e-14)}, {FN (arcsec), ARG(8.3886080e+06,-2.0e+00), RES(1.5707962075856070685e0, -2.8421709430402593796e-14)}, {FN (arcsec), ARG(-8.3886080e+06,2.0e+00), RES(1.570796446004186170e0, 2.8421709430402593796e-14)}, {FN (arcsec), ARG(-8.3886080e+06,-2.0e+00), RES(1.570796446004186170e0, -2.8421709430402593796e-14)}, {FN (arcsec), ARG(8.3886080e+06,8.3886080e+06), RES(1.5707962671902518438e0, 5.9604644775390695586e-8)}, {FN (arcsec), ARG(8.3886080e+06,-8.3886080e+06), RES(1.5707962671902518438e0, -5.9604644775390695586e-8)}, {FN (arcsec), ARG(-8.3886080e+06,8.3886080e+06), RES(1.5707963863995413946e0, 5.9604644775390695586e-8)}, {FN (arcsec), ARG(-8.3886080e+06,-8.3886080e+06), RES(1.5707963863995413946e0, -5.9604644775390695586e-8)}, {FN (arccot), ARG(0.0e+00,1.19209289550781250e-07), RES(-1.5707963267948966192e0, -1.1920928955078181469e-7)}, {FN (arccot), ARG(0.0e+00,-1.19209289550781250e-07), RES(1.5707963267948966192e0, 1.1920928955078181469e-7)}, {FN (arccot), ARG(0.0e+00,5.0e-01), RES(-1.5707963267948966192e0, -5.4930614433405484570e-1)}, {FN (arccot), ARG(0.0e+00,-5.0e-01), RES(1.5707963267948966192e0, 5.4930614433405484570e-1)}, {FN (arccot), ARG(0.0e+00,2.0e+00), RES(0, -5.4930614433405484570e-1)}, {FN (arccot), ARG(0.0e+00,-2.0e+00), RES(0, 5.4930614433405484570e-1)}, {FN (arccot), ARG(0.0e+00,8.3886080e+06), RES(0, -1.1920928955078181469e-7)}, {FN (arccot), ARG(0.0e+00,-8.3886080e+06), RES(0, 1.1920928955078181469e-7)}, {FN (arccot), ARG(1.19209289550781250e-07,0.0e+00), RES(1.5707962075856070685e0, 0.0)}, {FN (arccot), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.5707962075856070685e0, 0.0)}, {FN (arccot), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.5707962075856070684e0, -1.1920928955078012062e-7)}, {FN (arccot), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.5707962075856070684e0, 1.1920928955078012062e-7)}, {FN (arccot), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.5707962075856070684e0, -1.1920928955078012062e-7)}, {FN (arccot), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.5707962075856070684e0, 1.1920928955078012062e-7)}, {FN (arccot), ARG(1.19209289550781250e-07,5.0e-01), RES(1.5707961678491772182e0, -5.4930614433404221383e-1)}, {FN (arccot), ARG(1.19209289550781250e-07,-5.0e-01), RES(1.5707961678491772182e0, 5.4930614433404221383e-1)}, {FN (arccot), ARG(-1.19209289550781250e-07,5.0e-01), RES(-1.5707961678491772182e0, -5.4930614433404221383e-1)}, {FN (arccot), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-1.5707961678491772182e0, 5.4930614433404221383e-1)}, {FN (arccot), ARG(1.19209289550781250e-07,1.0e+00), RES(7.8539813359512592192e-1, -8.3177661667193446012e0)}, {FN (arccot), ARG(1.19209289550781250e-07,-1.0e+00), RES(7.8539813359512592192e-1, 8.3177661667193446012e0)}, {FN (arccot), ARG(-1.19209289550781250e-07,1.0e+00), RES(-7.8539813359512592192e-1, -8.3177661667193446012e0)}, {FN (arccot), ARG(-1.19209289550781250e-07,-1.0e+00), RES(-7.8539813359512592192e-1, 8.3177661667193446012e0)}, {FN (arccot), ARG(1.19209289550781250e-07,2.0e+00), RES(3.9736429850260144780e-8, -5.4930614433405168773e-1)}, {FN (arccot), ARG(1.19209289550781250e-07,-2.0e+00), RES(3.9736429850260144780e-8, 5.4930614433405168773e-1)}, {FN (arccot), ARG(-1.19209289550781250e-07,2.0e+00), RES(-3.9736429850260144780e-8, -5.4930614433405168773e-1)}, {FN (arccot), ARG(-1.19209289550781250e-07,-2.0e+00), RES(-3.9736429850260144780e-8, 5.4930614433405168773e-1)}, {FN (arccot), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.6940658945086247523e-21, -1.1920928955078181469e-7)}, {FN (arccot), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.6940658945086247523e-21, 1.1920928955078181469e-7)}, {FN (arccot), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(-1.6940658945086247523e-21, -1.1920928955078181469e-7)}, {FN (arccot), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(-1.6940658945086247523e-21, 1.1920928955078181469e-7)}, {FN (arccot), ARG(5.0e-01,0.0e+00), RES(1.1071487177940905030e0, 0.0)}, {FN (arccot), ARG(-5.0e-01,0.0e+00), RES(-1.1071487177940905030e0, 0.0)}, {FN (arccot), ARG(5.0e-01,1.19209289550781250e-07), RES(1.1071487177940859555e0, -9.5367431640625072280e-8)}, {FN (arccot), ARG(5.0e-01,-1.19209289550781250e-07), RES(1.1071487177940859555e0, 9.5367431640625072280e-8)}, {FN (arccot), ARG(-5.0e-01,1.19209289550781250e-07), RES(-1.1071487177940859555e0, -9.5367431640625072280e-8)}, {FN (arccot), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-1.1071487177940859555e0, 9.5367431640625072280e-8)}, {FN (arccot), ARG(5.0e-01,5.0e-01), RES(1.0172219678978513677e0, -4.0235947810852509365e-1)}, {FN (arccot), ARG(5.0e-01,-5.0e-01), RES(1.0172219678978513677e0, 4.0235947810852509365e-1)}, {FN (arccot), ARG(-5.0e-01,5.0e-01), RES(-1.0172219678978513677e0, -4.0235947810852509365e-1)}, {FN (arccot), ARG(-5.0e-01,-5.0e-01), RES(-1.0172219678978513677e0, 4.0235947810852509365e-1)}, {FN (arccot), ARG(5.0e-01,1.0e+00), RES(6.6290883183401623253e-1, -7.0830333601405402006e-1)}, {FN (arccot), ARG(5.0e-01,-1.0e+00), RES(6.6290883183401623253e-1, 7.0830333601405402006e-1)}, {FN (arccot), ARG(-5.0e-01,1.0e+00), RES(-6.6290883183401623253e-1, -7.0830333601405402006e-1)}, {FN (arccot), ARG(-5.0e-01,-1.0e+00), RES(-6.6290883183401623253e-1, 7.0830333601405402006e-1)}, {FN (arccot), ARG(5.0e-01,2.0e+00), RES(1.4924946579308963897e-1, -5.0037000005253101744e-1)}, {FN (arccot), ARG(5.0e-01,-2.0e+00), RES(1.4924946579308963897e-1, 5.0037000005253101744e-1)}, {FN (arccot), ARG(-5.0e-01,2.0e+00), RES(-1.4924946579308963897e-1, -5.0037000005253101744e-1)}, {FN (arccot), ARG(-5.0e-01,-2.0e+00), RES(-1.4924946579308963897e-1, 5.0037000005253101744e-1)}, {FN (arccot), ARG(5.0e-01,8.3886080e+06), RES(7.1054273576010775894e-15, -1.1920928955078139117e-7)}, {FN (arccot), ARG(5.0e-01,-8.3886080e+06), RES(7.1054273576010775894e-15, 1.1920928955078139117e-7)}, {FN (arccot), ARG(-5.0e-01,8.3886080e+06), RES(-7.1054273576010775894e-15, -1.1920928955078139117e-7)}, {FN (arccot), ARG(-5.0e-01,-8.3886080e+06), RES(-7.1054273576010775894e-15, 1.1920928955078139117e-7)}, {FN (arccot), ARG(1.0e+00,0.0e+00), RES(7.8539816339744830962e-1, 0.0)}, {FN (arccot), ARG(-1.0e+00,0.0e+00), RES(-7.8539816339744830962e-1, 0.0)}, {FN (arccot), ARG(1.0e+00,1.19209289550781250e-07), RES(7.8539816339744475690e-1, -5.9604644775390483828e-8)}, {FN (arccot), ARG(1.0e+00,-1.19209289550781250e-07), RES(7.8539816339744475690e-1, 5.9604644775390483828e-8)}, {FN (arccot), ARG(-1.0e+00,1.19209289550781250e-07), RES(-7.8539816339744475690e-1, -5.9604644775390483828e-8)}, {FN (arccot), ARG(-1.0e+00,-1.19209289550781250e-07), RES(-7.8539816339744475690e-1, 5.9604644775390483828e-8)}, {FN (arccot), ARG(1.0e+00,5.0e-01), RES(7.2322066612406759210e-1, -2.3887786125685909036e-1)}, {FN (arccot), ARG(1.0e+00,-5.0e-01), RES(7.2322066612406759210e-1, 2.3887786125685909036e-1)}, {FN (arccot), ARG(-1.0e+00,5.0e-01), RES(-7.2322066612406759210e-1, -2.3887786125685909036e-1)}, {FN (arccot), ARG(-1.0e+00,-5.0e-01), RES(-7.2322066612406759210e-1, 2.3887786125685909036e-1)}, {FN (arccot), ARG(1.0e+00,1.0e+00), RES(5.5357435889704525151e-1, -4.0235947810852509365e-1)}, {FN (arccot), ARG(1.0e+00,-1.0e+00), RES(5.5357435889704525151e-1, 4.0235947810852509365e-1)}, {FN (arccot), ARG(-1.0e+00,1.0e+00), RES(-5.5357435889704525151e-1, -4.0235947810852509365e-1)}, {FN (arccot), ARG(-1.0e+00,-1.0e+00), RES(-5.5357435889704525151e-1, 4.0235947810852509365e-1)}, {FN (arccot), ARG(1.0e+00,2.0e+00), RES(2.3182380450040305811e-1, -4.0235947810852509365e-1)}, {FN (arccot), ARG(1.0e+00,-2.0e+00), RES(2.3182380450040305811e-1, 4.0235947810852509365e-1)}, {FN (arccot), ARG(-1.0e+00,2.0e+00), RES(-2.3182380450040305811e-1, -4.0235947810852509365e-1)}, {FN (arccot), ARG(-1.0e+00,-2.0e+00), RES(-2.3182380450040305811e-1, 4.0235947810852509365e-1)}, {FN (arccot), ARG(1.0e+00,8.3886080e+06), RES(1.4210854715202003717e-14, -1.1920928955078012062e-7)}, {FN (arccot), ARG(1.0e+00,-8.3886080e+06), RES(1.4210854715202003717e-14, 1.1920928955078012062e-7)}, {FN (arccot), ARG(-1.0e+00,8.3886080e+06), RES(-1.4210854715202003717e-14, -1.1920928955078012062e-7)}, {FN (arccot), ARG(-1.0e+00,-8.3886080e+06), RES(-1.4210854715202003717e-14, 1.1920928955078012062e-7)}, {FN (arccot), ARG(2.0e+00,0.0e+00), RES(4.6364760900080611621e-1, 0.0)}, {FN (arccot), ARG(-2.0e+00,0.0e+00), RES(-4.6364760900080611621e-1, 0.0)}, {FN (arccot), ARG(2.0e+00,1.19209289550781250e-07), RES(4.6364760900080497935e-1, -2.3841857910156200307e-8)}, {FN (arccot), ARG(2.0e+00,-1.19209289550781250e-07), RES(4.6364760900080497935e-1, 2.3841857910156200307e-8)}, {FN (arccot), ARG(-2.0e+00,1.19209289550781250e-07), RES(-4.6364760900080497935e-1, -2.3841857910156200307e-8)}, {FN (arccot), ARG(-2.0e+00,-1.19209289550781250e-07), RES(-4.6364760900080497935e-1, 2.3841857910156200307e-8)}, {FN (arccot), ARG(2.0e+00,5.0e-01), RES(4.4423988596007427049e-1, -9.6415620202996167238e-2)}, {FN (arccot), ARG(2.0e+00,-5.0e-01), RES(4.4423988596007427049e-1, 9.6415620202996167238e-2)}, {FN (arccot), ARG(-2.0e+00,5.0e-01), RES(-4.4423988596007427049e-1, -9.6415620202996167238e-2)}, {FN (arccot), ARG(-2.0e+00,-5.0e-01), RES(-4.4423988596007427049e-1, 9.6415620202996167238e-2)}, {FN (arccot), ARG(2.0e+00,1.0e+00), RES(3.9269908169872415481e-1, -1.7328679513998632735e-1)}, {FN (arccot), ARG(2.0e+00,-1.0e+00), RES(3.9269908169872415481e-1, 1.7328679513998632735e-1)}, {FN (arccot), ARG(-2.0e+00,1.0e+00), RES(-3.9269908169872415481e-1, -1.7328679513998632735e-1)}, {FN (arccot), ARG(-2.0e+00,-1.0e+00), RES(-3.9269908169872415481e-1, 1.7328679513998632735e-1)}, {FN (arccot), ARG(2.0e+00,2.0e+00), RES(2.5957305712326147589e-1, -2.3887786125685909036e-1)}, {FN (arccot), ARG(2.0e+00,-2.0e+00), RES(2.5957305712326147589e-1, 2.3887786125685909036e-1)}, {FN (arccot), ARG(-2.0e+00,2.0e+00), RES(-2.5957305712326147589e-1, -2.3887786125685909036e-1)}, {FN (arccot), ARG(-2.0e+00,-2.0e+00), RES(-2.5957305712326147589e-1, 2.3887786125685909036e-1)}, {FN (arccot), ARG(2.0e+00,8.3886080e+06), RES(2.8421709430402795744e-14, -1.1920928955077503843e-7)}, {FN (arccot), ARG(2.0e+00,-8.3886080e+06), RES(2.8421709430402795744e-14, 1.1920928955077503843e-7)}, {FN (arccot), ARG(-2.0e+00,8.3886080e+06), RES(-2.8421709430402795744e-14, -1.1920928955077503843e-7)}, {FN (arccot), ARG(-2.0e+00,-8.3886080e+06), RES(-2.8421709430402795744e-14, 1.1920928955077503843e-7)}, {FN (arccot), ARG(8.3886080e+06,0.0e+00), RES(1.1920928955078068531e-7, 0.0)}, {FN (arccot), ARG(-8.3886080e+06,0.0e+00), RES(-1.1920928955078068531e-7, 0.0)}, {FN (arccot), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.1920928955078068531e-7, -1.6940658945085766040e-21)}, {FN (arccot), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.1920928955078068531e-7, 1.6940658945085766040e-21)}, {FN (arccot), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(-1.1920928955078068531e-7, -1.6940658945085766040e-21)}, {FN (arccot), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(-1.1920928955078068531e-7, 1.6940658945085766040e-21)}, {FN (arccot), ARG(8.3886080e+06,5.0e-01), RES(1.1920928955078026179e-7, -7.1054273576008756410e-15)}, {FN (arccot), ARG(8.3886080e+06,-5.0e-01), RES(1.1920928955078026179e-7, 7.1054273576008756410e-15)}, {FN (arccot), ARG(-8.3886080e+06,5.0e-01), RES(-1.1920928955078026179e-7, -7.1054273576008756410e-15)}, {FN (arccot), ARG(-8.3886080e+06,-5.0e-01), RES(-1.1920928955078026179e-7, 7.1054273576008756410e-15)}, {FN (arccot), ARG(8.3886080e+06,1.0e+00), RES(1.1920928955077899125e-7, -1.4210854715201599821e-14)}, {FN (arccot), ARG(8.3886080e+06,-1.0e+00), RES(1.1920928955077899125e-7, 1.4210854715201599821e-14)}, {FN (arccot), ARG(-8.3886080e+06,1.0e+00), RES(-1.1920928955077899125e-7, -1.4210854715201599821e-14)}, {FN (arccot), ARG(-8.3886080e+06,-1.0e+00), RES(-1.1920928955077899125e-7, 1.4210854715201599821e-14)}, {FN (arccot), ARG(8.3886080e+06,2.0e+00), RES(1.1920928955077390905e-7, -2.8421709430401987951e-14)}, {FN (arccot), ARG(8.3886080e+06,-2.0e+00), RES(1.1920928955077390905e-7, 2.8421709430401987951e-14)}, {FN (arccot), ARG(-8.3886080e+06,2.0e+00), RES(-1.1920928955077390905e-7, -2.8421709430401987951e-14)}, {FN (arccot), ARG(-8.3886080e+06,-2.0e+00), RES(-1.1920928955077390905e-7, 2.8421709430401987951e-14)}, {FN (arccot), ARG(8.3886080e+06,8.3886080e+06), RES(5.9604644775390766172e-8, -5.9604644775390483828e-8)}, {FN (arccot), ARG(8.3886080e+06,-8.3886080e+06), RES(5.9604644775390766172e-8, 5.9604644775390483828e-8)}, {FN (arccot), ARG(-8.3886080e+06,8.3886080e+06), RES(-5.9604644775390766172e-8, -5.9604644775390483828e-8)}, {FN (arccot), ARG(-8.3886080e+06,-8.3886080e+06), RES(-5.9604644775390766172e-8, 5.9604644775390483828e-8)}, {FN (csch), ARG(0.0e+00,-3.45266983001243932001e-04), RES(0, 2.8963094332845964291e3)}, {FN (csch), ARG(0.0e+00,3.45266983001243932001e-04), RES(0, -2.8963094332845964291e3)}, {FN (csch), ARG(0.0e+00,1.57045105981189525579e+00), RES(0, -1.0000000596046477360e0)}, {FN (csch), ARG(0.0e+00,-1.57045105981189525579e+00), RES(0, 1.0000000596046477360e0)}, {FN (csch), ARG(0.0e+00,1.57114159377789786021e+00), RES(0, -1.0000000596046477360e0)}, {FN (csch), ARG(0.0e+00,-1.57114159377789786021e+00), RES(0, 1.0000000596046477360e0)}, {FN (csch), ARG(0.0e+00,3.14124738660679181379e+00), RES(0, -2.8963094332830802676e3)}, {FN (csch), ARG(0.0e+00,-3.14124738660679181379e+00), RES(0, 2.8963094332830802676e3)}, {FN (csch), ARG(0.0e+00,3.14193792057279441821e+00), RES(0, 2.8963094332851348839e3)}, {FN (csch), ARG(0.0e+00,-3.14193792057279441821e+00), RES(0, -2.8963094332851348839e3)}, {FN (csch), ARG(0.0e+00,4.71204371340168837179e+00), RES(0, 1.0000000596046477361e0)}, {FN (csch), ARG(0.0e+00,-4.71204371340168837179e+00), RES(0, -1.0000000596046477361e0)}, {FN (csch), ARG(0.0e+00,4.71273424736769097620e+00), RES(0, 1.0000000596046477359e0)}, {FN (csch), ARG(0.0e+00,-4.71273424736769097620e+00), RES(0, -1.0000000596046477359e0)}, {FN (csch), ARG(0.0e+00,6.28284004019658492979e+00), RES(0, 2.8963094332820529594e3)}, {FN (csch), ARG(0.0e+00,-6.28284004019658492979e+00), RES(0, -2.8963094332820529594e3)}, {FN (csch), ARG(0.0e+00,6.28353057416258753420e+00), RES(0, -2.8963094332861621921e3)}, {FN (csch), ARG(0.0e+00,-6.28353057416258753420e+00), RES(0, 2.8963094332861621921e3)}, {FN (csch), ARG(0.0e+00,9.42443269378637893396e+00), RES(0, -2.8963094332884762317e3)}, {FN (csch), ARG(0.0e+00,-9.42443269378637893396e+00), RES(0, 2.8963094332884762317e3)}, {FN (csch), ARG(0.0e+00,9.42512322775237976202e+00), RES(0, 2.8963094332946400807e3)}, {FN (csch), ARG(0.0e+00,-9.42512322775237976202e+00), RES(0, -2.8963094332946400807e3)}, {FN (csch), ARG(1.19209289550781250e-07,-3.45266983001243932001e-04), RES(9.9999986092250876926e-1, 2.8963090880176545869e3)}, {FN (csch), ARG(1.19209289550781250e-07,3.45266983001243932001e-04), RES(9.9999986092250876926e-1, -2.8963090880176545869e3)}, {FN (csch), ARG(-1.19209289550781250e-07,-3.45266983001243932001e-04), RES(-9.9999986092250876926e-1, 2.8963090880176545869e3)}, {FN (csch), ARG(-1.19209289550781250e-07,3.45266983001243932001e-04), RES(-9.9999986092250876926e-1, -2.8963090880176545869e3)}, {FN (csch), ARG(1.19209289550781250e-07,1.57045105981189525579e+00), RES(4.1159035837716456618e-11, -1.0000000596046406306e0)}, {FN (csch), ARG(1.19209289550781250e-07,-1.57045105981189525579e+00), RES(4.1159035837716456618e-11, 1.0000000596046406306e0)}, {FN (csch), ARG(-1.19209289550781250e-07,1.57045105981189525579e+00), RES(-4.1159035837716456618e-11, -1.0000000596046406306e0)}, {FN (csch), ARG(-1.19209289550781250e-07,-1.57045105981189525579e+00), RES(-4.1159035837716456618e-11, 1.0000000596046406306e0)}, {FN (csch), ARG(1.19209289550781250e-07,1.57114159377789786021e+00), RES(-4.1159035837701857686e-11, -1.0000000596046406306e0)}, {FN (csch), ARG(1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-4.1159035837701857686e-11, 1.0000000596046406306e0)}, {FN (csch), ARG(-1.19209289550781250e-07,1.57114159377789786021e+00), RES(4.1159035837701857686e-11, -1.0000000596046406306e0)}, {FN (csch), ARG(-1.19209289550781250e-07,-1.57114159377789786021e+00), RES(4.1159035837701857686e-11, 1.0000000596046406306e0)}, {FN (csch), ARG(1.19209289550781250e-07,3.14124738660679181379e+00), RES(-9.9999986092146180843e-1, -2.8963090880161384259e3)}, {FN (csch), ARG(1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-9.9999986092146180843e-1, 2.8963090880161384259e3)}, {FN (csch), ARG(-1.19209289550781250e-07,3.14124738660679181379e+00), RES(9.9999986092146180843e-1, -2.8963090880161384259e3)}, {FN (csch), ARG(-1.19209289550781250e-07,-3.14124738660679181379e+00), RES(9.9999986092146180843e-1, 2.8963090880161384259e3)}, {FN (csch), ARG(1.19209289550781250e-07,3.14193792057279441821e+00), RES(-9.9999986092288059049e-1, 2.8963090880181930415e3)}, {FN (csch), ARG(1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-9.9999986092288059049e-1, -2.8963090880181930415e3)}, {FN (csch), ARG(-1.19209289550781250e-07,3.14193792057279441821e+00), RES(9.9999986092288059049e-1, 2.8963090880181930415e3)}, {FN (csch), ARG(-1.19209289550781250e-07,-3.14193792057279441821e+00), RES(9.9999986092288059049e-1, -2.8963090880181930415e3)}, {FN (csch), ARG(1.19209289550781250e-07,4.71204371340168837179e+00), RES(-4.1159035837731055550e-11, 1.0000000596046406306e0)}, {FN (csch), ARG(1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-4.1159035837731055550e-11, -1.0000000596046406306e0)}, {FN (csch), ARG(-1.19209289550781250e-07,4.71204371340168837179e+00), RES(4.1159035837731055550e-11, 1.0000000596046406306e0)}, {FN (csch), ARG(-1.19209289550781250e-07,-4.71204371340168837179e+00), RES(4.1159035837731055550e-11, -1.0000000596046406306e0)}, {FN (csch), ARG(1.19209289550781250e-07,4.71273424736769097620e+00), RES(4.1159035837687258754e-11, 1.0000000596046406305e0)}, {FN (csch), ARG(1.19209289550781250e-07,-4.71273424736769097620e+00), RES(4.1159035837687258754e-11, -1.0000000596046406305e0)}, {FN (csch), ARG(-1.19209289550781250e-07,4.71273424736769097620e+00), RES(-4.1159035837687258754e-11, 1.0000000596046406305e0)}, {FN (csch), ARG(-1.19209289550781250e-07,-4.71273424736769097620e+00), RES(-4.1159035837687258754e-11, -1.0000000596046406305e0)}, {FN (csch), ARG(1.19209289550781250e-07,6.28284004019658492979e+00), RES(9.9999986092075241740e-1, 2.8963090880151111181e3)}, {FN (csch), ARG(1.19209289550781250e-07,-6.28284004019658492979e+00), RES(9.9999986092075241740e-1, -2.8963090880151111181e3)}, {FN (csch), ARG(-1.19209289550781250e-07,6.28284004019658492979e+00), RES(-9.9999986092075241740e-1, 2.8963090880151111181e3)}, {FN (csch), ARG(-1.19209289550781250e-07,-6.28284004019658492979e+00), RES(-9.9999986092075241740e-1, -2.8963090880151111181e3)}, {FN (csch), ARG(1.19209289550781250e-07,6.28353057416258753420e+00), RES(9.9999986092358998153e-1, -2.8963090880192203493e3)}, {FN (csch), ARG(1.19209289550781250e-07,-6.28353057416258753420e+00), RES(9.9999986092358998153e-1, 2.8963090880192203493e3)}, {FN (csch), ARG(-1.19209289550781250e-07,6.28353057416258753420e+00), RES(-9.9999986092358998153e-1, -2.8963090880192203493e3)}, {FN (csch), ARG(-1.19209289550781250e-07,-6.28353057416258753420e+00), RES(-9.9999986092358998153e-1, 2.8963090880192203493e3)}, {FN (csch), ARG(1.19209289550781250e-07,9.42443269378637893396e+00), RES(-9.9999986092518790411e-1, -2.8963090880215343881e3)}, {FN (csch), ARG(1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-9.9999986092518790411e-1, 2.8963090880215343881e3)}, {FN (csch), ARG(-1.19209289550781250e-07,9.42443269378637893396e+00), RES(9.9999986092518790411e-1, -2.8963090880215343881e3)}, {FN (csch), ARG(-1.19209289550781250e-07,-9.42443269378637893396e+00), RES(9.9999986092518790411e-1, 2.8963090880215343881e3)}, {FN (csch), ARG(1.19209289550781250e-07,9.42512322775237976202e+00), RES(-9.9999986092944425030e-1, 2.8963090880276982349e3)}, {FN (csch), ARG(1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-9.9999986092944425030e-1, -2.8963090880276982349e3)}, {FN (csch), ARG(-1.19209289550781250e-07,9.42512322775237976202e+00), RES(9.9999986092944425030e-1, 2.8963090880276982349e3)}, {FN (csch), ARG(-1.19209289550781250e-07,-9.42512322775237976202e+00), RES(9.9999986092944425030e-1, -2.8963090880276982349e3)}, {FN (csch), ARG(5.0e-01,-3.45266983001243932001e-04), RES(1.9190337944739187237e0, 1.4337901642789801243e-3)}, {FN (csch), ARG(5.0e-01,3.45266983001243932001e-04), RES(1.9190337944739187237e0, -1.4337901642789801243e-3)}, {FN (csch), ARG(-5.0e-01,-3.45266983001243932001e-04), RES(-1.9190337944739187237e0, 1.4337901642789801243e-3)}, {FN (csch), ARG(-5.0e-01,3.45266983001243932001e-04), RES(-1.9190337944739187237e0, -1.4337901642789801243e-3)}, {FN (csch), ARG(5.0e-01,1.57045105981189525579e+00), RES(1.4149533035943115868e-4, -8.8681891425248302487e-1)}, {FN (csch), ARG(5.0e-01,-1.57045105981189525579e+00), RES(1.4149533035943115868e-4, 8.8681891425248302487e-1)}, {FN (csch), ARG(-5.0e-01,1.57045105981189525579e+00), RES(-1.4149533035943115868e-4, -8.8681891425248302487e-1)}, {FN (csch), ARG(-5.0e-01,-1.57045105981189525579e+00), RES(-1.4149533035943115868e-4, 8.8681891425248302487e-1)}, {FN (csch), ARG(5.0e-01,1.57114159377789786021e+00), RES(-1.4149533035938097090e-4, -8.8681891425248302485e-1)}, {FN (csch), ARG(5.0e-01,-1.57114159377789786021e+00), RES(-1.4149533035938097090e-4, 8.8681891425248302485e-1)}, {FN (csch), ARG(-5.0e-01,1.57114159377789786021e+00), RES(1.4149533035938097090e-4, -8.8681891425248302485e-1)}, {FN (csch), ARG(-5.0e-01,-1.57114159377789786021e+00), RES(1.4149533035938097090e-4, 8.8681891425248302485e-1)}, {FN (csch), ARG(5.0e-01,3.14124738660679181379e+00), RES(-1.9190337944739187227e0, -1.4337901642797306848e-3)}, {FN (csch), ARG(5.0e-01,-3.14124738660679181379e+00), RES(-1.9190337944739187227e0, 1.4337901642797306848e-3)}, {FN (csch), ARG(-5.0e-01,3.14124738660679181379e+00), RES(1.9190337944739187227e0, -1.4337901642797306848e-3)}, {FN (csch), ARG(-5.0e-01,-3.14124738660679181379e+00), RES(1.9190337944739187227e0, 1.4337901642797306848e-3)}, {FN (csch), ARG(5.0e-01,3.14193792057279441821e+00), RES(-1.9190337944739187241e0, 1.4337901642787135676e-3)}, {FN (csch), ARG(5.0e-01,-3.14193792057279441821e+00), RES(-1.9190337944739187241e0, -1.4337901642787135676e-3)}, {FN (csch), ARG(-5.0e-01,3.14193792057279441821e+00), RES(1.9190337944739187241e0, 1.4337901642787135676e-3)}, {FN (csch), ARG(-5.0e-01,-3.14193792057279441821e+00), RES(1.9190337944739187241e0, -1.4337901642787135676e-3)}, {FN (csch), ARG(5.0e-01,4.71204371340168837179e+00), RES(-1.4149533035948134646e-4, 8.8681891425248302489e-1)}, {FN (csch), ARG(5.0e-01,-4.71204371340168837179e+00), RES(-1.4149533035948134646e-4, -8.8681891425248302489e-1)}, {FN (csch), ARG(-5.0e-01,4.71204371340168837179e+00), RES(1.4149533035948134646e-4, 8.8681891425248302489e-1)}, {FN (csch), ARG(-5.0e-01,-4.71204371340168837179e+00), RES(1.4149533035948134646e-4, -8.8681891425248302489e-1)}, {FN (csch), ARG(5.0e-01,4.71273424736769097620e+00), RES(1.4149533035933078312e-4, 8.8681891425248302483e-1)}, {FN (csch), ARG(5.0e-01,-4.71273424736769097620e+00), RES(1.4149533035933078312e-4, -8.8681891425248302483e-1)}, {FN (csch), ARG(-5.0e-01,4.71273424736769097620e+00), RES(-1.4149533035933078312e-4, 8.8681891425248302483e-1)}, {FN (csch), ARG(-5.0e-01,-4.71273424736769097620e+00), RES(-1.4149533035933078312e-4, -8.8681891425248302483e-1)}, {FN (csch), ARG(5.0e-01,6.28284004019658492979e+00), RES(1.9190337944739187220e0, 1.4337901642802392434e-3)}, {FN (csch), ARG(5.0e-01,-6.28284004019658492979e+00), RES(1.9190337944739187220e0, -1.4337901642802392434e-3)}, {FN (csch), ARG(-5.0e-01,6.28284004019658492979e+00), RES(-1.9190337944739187220e0, 1.4337901642802392434e-3)}, {FN (csch), ARG(-5.0e-01,-6.28284004019658492979e+00), RES(-1.9190337944739187220e0, -1.4337901642802392434e-3)}, {FN (csch), ARG(5.0e-01,6.28353057416258753420e+00), RES(1.9190337944739187248e0, -1.4337901642782050091e-3)}, {FN (csch), ARG(5.0e-01,-6.28353057416258753420e+00), RES(1.9190337944739187248e0, 1.4337901642782050091e-3)}, {FN (csch), ARG(-5.0e-01,6.28353057416258753420e+00), RES(-1.9190337944739187248e0, -1.4337901642782050091e-3)}, {FN (csch), ARG(-5.0e-01,-6.28353057416258753420e+00), RES(-1.9190337944739187248e0, 1.4337901642782050091e-3)}, {FN (csch), ARG(5.0e-01,9.42443269378637893396e+00), RES(-1.9190337944739187263e0, -1.4337901642770594670e-3)}, {FN (csch), ARG(5.0e-01,-9.42443269378637893396e+00), RES(-1.9190337944739187263e0, 1.4337901642770594670e-3)}, {FN (csch), ARG(-5.0e-01,9.42443269378637893396e+00), RES(1.9190337944739187263e0, -1.4337901642770594670e-3)}, {FN (csch), ARG(-5.0e-01,-9.42443269378637893396e+00), RES(1.9190337944739187263e0, 1.4337901642770594670e-3)}, {FN (csch), ARG(5.0e-01,9.42512322775237976202e+00), RES(-1.9190337944739187304e0, 1.4337901642740081154e-3)}, {FN (csch), ARG(5.0e-01,-9.42512322775237976202e+00), RES(-1.9190337944739187304e0, -1.4337901642740081154e-3)}, {FN (csch), ARG(-5.0e-01,9.42512322775237976202e+00), RES(1.9190337944739187304e0, 1.4337901642740081154e-3)}, {FN (csch), ARG(-5.0e-01,-9.42512322775237976202e+00), RES(1.9190337944739187304e0, -1.4337901642740081154e-3)}, {FN (csch), ARG(1.0e+00,-3.45266983001243932001e-04), RES(8.5091800407377002734e-1, 3.8576176225198860914e-4)}, {FN (csch), ARG(1.0e+00,3.45266983001243932001e-04), RES(8.5091800407377002734e-1, -3.8576176225198860914e-4)}, {FN (csch), ARG(-1.0e+00,-3.45266983001243932001e-04), RES(-8.5091800407377002734e-1, 3.8576176225198860914e-4)}, {FN (csch), ARG(-1.0e+00,3.45266983001243932001e-04), RES(-8.5091800407377002734e-1, -3.8576176225198860914e-4)}, {FN (csch), ARG(1.0e+00,1.57045105981189525579e+00), RES(1.7040802567657401279e-4, -6.4805426748157480499e-1)}, {FN (csch), ARG(1.0e+00,-1.57045105981189525579e+00), RES(1.7040802567657401279e-4, 6.4805426748157480499e-1)}, {FN (csch), ARG(-1.0e+00,1.57045105981189525579e+00), RES(-1.7040802567657401279e-4, -6.4805426748157480499e-1)}, {FN (csch), ARG(-1.0e+00,-1.57045105981189525579e+00), RES(-1.7040802567657401279e-4, 6.4805426748157480499e-1)}, {FN (csch), ARG(1.0e+00,1.57114159377789786021e+00), RES(-1.7040802567651356981e-4, -6.4805426748157480499e-1)}, {FN (csch), ARG(1.0e+00,-1.57114159377789786021e+00), RES(-1.7040802567651356981e-4, 6.4805426748157480499e-1)}, {FN (csch), ARG(-1.0e+00,1.57114159377789786021e+00), RES(1.7040802567651356981e-4, -6.4805426748157480499e-1)}, {FN (csch), ARG(-1.0e+00,-1.57114159377789786021e+00), RES(1.7040802567651356981e-4, 6.4805426748157480499e-1)}, {FN (csch), ARG(1.0e+00,3.14124738660679181379e+00), RES(-8.5091800407377002721e-1, -3.8576176225219054787e-4)}, {FN (csch), ARG(1.0e+00,-3.14124738660679181379e+00), RES(-8.5091800407377002721e-1, 3.8576176225219054787e-4)}, {FN (csch), ARG(-1.0e+00,3.14124738660679181379e+00), RES(8.5091800407377002721e-1, -3.8576176225219054787e-4)}, {FN (csch), ARG(-1.0e+00,-3.14124738660679181379e+00), RES(8.5091800407377002721e-1, 3.8576176225219054787e-4)}, {FN (csch), ARG(1.0e+00,3.14193792057279441821e+00), RES(-8.5091800407377002738e-1, 3.8576176225191689193e-4)}, {FN (csch), ARG(1.0e+00,-3.14193792057279441821e+00), RES(-8.5091800407377002738e-1, -3.8576176225191689193e-4)}, {FN (csch), ARG(-1.0e+00,3.14193792057279441821e+00), RES(8.5091800407377002738e-1, 3.8576176225191689193e-4)}, {FN (csch), ARG(-1.0e+00,-3.14193792057279441821e+00), RES(8.5091800407377002738e-1, -3.8576176225191689193e-4)}, {FN (csch), ARG(1.0e+00,4.71204371340168837179e+00), RES(-1.7040802567663445577e-4, 6.4805426748157480498e-1)}, {FN (csch), ARG(1.0e+00,-4.71204371340168837179e+00), RES(-1.7040802567663445577e-4, -6.4805426748157480498e-1)}, {FN (csch), ARG(-1.0e+00,4.71204371340168837179e+00), RES(1.7040802567663445577e-4, 6.4805426748157480498e-1)}, {FN (csch), ARG(-1.0e+00,-4.71204371340168837179e+00), RES(1.7040802567663445577e-4, -6.4805426748157480498e-1)}, {FN (csch), ARG(1.0e+00,4.71273424736769097620e+00), RES(1.7040802567645312683e-4, 6.480542674815748050e-1)}, {FN (csch), ARG(1.0e+00,-4.71273424736769097620e+00), RES(1.7040802567645312683e-4, -6.480542674815748050e-1)}, {FN (csch), ARG(-1.0e+00,4.71273424736769097620e+00), RES(-1.7040802567645312683e-4, 6.480542674815748050e-1)}, {FN (csch), ARG(-1.0e+00,-4.71273424736769097620e+00), RES(-1.7040802567645312683e-4, -6.480542674815748050e-1)}, {FN (csch), ARG(1.0e+00,6.28284004019658492979e+00), RES(8.5091800407377002712e-1, 3.8576176225232737584e-4)}, {FN (csch), ARG(1.0e+00,-6.28284004019658492979e+00), RES(8.5091800407377002712e-1, -3.8576176225232737584e-4)}, {FN (csch), ARG(-1.0e+00,6.28284004019658492979e+00), RES(-8.5091800407377002712e-1, 3.8576176225232737584e-4)}, {FN (csch), ARG(-1.0e+00,-6.28284004019658492979e+00), RES(-8.5091800407377002712e-1, -3.8576176225232737584e-4)}, {FN (csch), ARG(1.0e+00,6.28353057416258753420e+00), RES(8.5091800407377002747e-1, -3.8576176225178006396e-4)}, {FN (csch), ARG(1.0e+00,-6.28353057416258753420e+00), RES(8.5091800407377002747e-1, 3.8576176225178006396e-4)}, {FN (csch), ARG(-1.0e+00,6.28353057416258753420e+00), RES(-8.5091800407377002747e-1, -3.8576176225178006396e-4)}, {FN (csch), ARG(-1.0e+00,-6.28353057416258753420e+00), RES(-8.5091800407377002747e-1, 3.8576176225178006396e-4)}, {FN (csch), ARG(1.0e+00,9.42443269378637893396e+00), RES(-8.5091800407377002767e-1, -3.8576176225147185523e-4)}, {FN (csch), ARG(1.0e+00,-9.42443269378637893396e+00), RES(-8.5091800407377002767e-1, 3.8576176225147185523e-4)}, {FN (csch), ARG(-1.0e+00,9.42443269378637893396e+00), RES(8.5091800407377002767e-1, -3.8576176225147185523e-4)}, {FN (csch), ARG(-1.0e+00,-9.42443269378637893396e+00), RES(8.5091800407377002767e-1, 3.8576176225147185523e-4)}, {FN (csch), ARG(1.0e+00,9.42512322775237976202e+00), RES(-8.5091800407377002820e-1, 3.8576176225065088741e-4)}, {FN (csch), ARG(1.0e+00,-9.42512322775237976202e+00), RES(-8.5091800407377002820e-1, -3.8576176225065088741e-4)}, {FN (csch), ARG(-1.0e+00,9.42512322775237976202e+00), RES(8.5091800407377002820e-1, 3.8576176225065088741e-4)}, {FN (csch), ARG(-1.0e+00,-9.42512322775237976202e+00), RES(8.5091800407377002820e-1, -3.8576176225065088741e-4)}, {FN (csch), ARG(2.0e+00,-3.45266983001243932001e-04), RES(2.7572054583883740768e-1, 9.8749461907035665386e-5)}, {FN (csch), ARG(2.0e+00,3.45266983001243932001e-04), RES(2.7572054583883740768e-1, -9.8749461907035665386e-5)}, {FN (csch), ARG(-2.0e+00,-3.45266983001243932001e-04), RES(-2.7572054583883740768e-1, 9.8749461907035665386e-5)}, {FN (csch), ARG(-2.0e+00,3.45266983001243932001e-04), RES(-2.7572054583883740768e-1, -9.8749461907035665386e-5)}, {FN (csch), ARG(2.0e+00,1.57045105981189525579e+00), RES(8.8471445300404633228e-5, -2.6580221522968095406e-1)}, {FN (csch), ARG(2.0e+00,-1.57045105981189525579e+00), RES(8.8471445300404633228e-5, 2.6580221522968095406e-1)}, {FN (csch), ARG(-2.0e+00,1.57045105981189525579e+00), RES(-8.8471445300404633228e-5, -2.6580221522968095406e-1)}, {FN (csch), ARG(-2.0e+00,-1.57045105981189525579e+00), RES(-8.8471445300404633228e-5, 2.6580221522968095406e-1)}, {FN (csch), ARG(2.0e+00,1.57114159377789786021e+00), RES(-8.8471445300373252796e-5, -2.6580221522968095407e-1)}, {FN (csch), ARG(2.0e+00,-1.57114159377789786021e+00), RES(-8.8471445300373252796e-5, 2.6580221522968095407e-1)}, {FN (csch), ARG(-2.0e+00,1.57114159377789786021e+00), RES(8.8471445300373252796e-5, -2.6580221522968095407e-1)}, {FN (csch), ARG(-2.0e+00,-1.57114159377789786021e+00), RES(8.8471445300373252796e-5, 2.6580221522968095407e-1)}, {FN (csch), ARG(2.0e+00,3.14124738660679181379e+00), RES(-2.7572054583883740766e-1, -9.8749461907087358805e-5)}, {FN (csch), ARG(2.0e+00,-3.14124738660679181379e+00), RES(-2.7572054583883740766e-1, 9.8749461907087358805e-5)}, {FN (csch), ARG(-2.0e+00,3.14124738660679181379e+00), RES(2.7572054583883740766e-1, -9.8749461907087358805e-5)}, {FN (csch), ARG(-2.0e+00,-3.14124738660679181379e+00), RES(2.7572054583883740766e-1, 9.8749461907087358805e-5)}, {FN (csch), ARG(2.0e+00,3.14193792057279441821e+00), RES(-2.7572054583883740769e-1, 9.8749461907017306810e-5)}, {FN (csch), ARG(2.0e+00,-3.14193792057279441821e+00), RES(-2.7572054583883740769e-1, -9.8749461907017306810e-5)}, {FN (csch), ARG(-2.0e+00,3.14193792057279441821e+00), RES(2.7572054583883740769e-1, 9.8749461907017306810e-5)}, {FN (csch), ARG(-2.0e+00,-3.14193792057279441821e+00), RES(2.7572054583883740769e-1, -9.8749461907017306810e-5)}, {FN (csch), ARG(2.0e+00,4.71204371340168837179e+00), RES(-8.8471445300436013659e-5, 2.6580221522968095405e-1)}, {FN (csch), ARG(2.0e+00,-4.71204371340168837179e+00), RES(-8.8471445300436013659e-5, -2.6580221522968095405e-1)}, {FN (csch), ARG(-2.0e+00,4.71204371340168837179e+00), RES(8.8471445300436013659e-5, 2.6580221522968095405e-1)}, {FN (csch), ARG(-2.0e+00,-4.71204371340168837179e+00), RES(8.8471445300436013659e-5, -2.6580221522968095405e-1)}, {FN (csch), ARG(2.0e+00,4.71273424736769097620e+00), RES(8.8471445300341872364e-5, 2.6580221522968095408e-1)}, {FN (csch), ARG(2.0e+00,-4.71273424736769097620e+00), RES(8.8471445300341872364e-5, -2.6580221522968095408e-1)}, {FN (csch), ARG(-2.0e+00,4.71273424736769097620e+00), RES(-8.8471445300341872364e-5, 2.6580221522968095408e-1)}, {FN (csch), ARG(-2.0e+00,-4.71273424736769097620e+00), RES(-8.8471445300341872364e-5, -2.6580221522968095408e-1)}, {FN (csch), ARG(2.0e+00,6.28284004019658492979e+00), RES(2.7572054583883740765e-1, 9.8749461907122384803e-5)}, {FN (csch), ARG(2.0e+00,-6.28284004019658492979e+00), RES(2.7572054583883740765e-1, -9.8749461907122384803e-5)}, {FN (csch), ARG(-2.0e+00,6.28284004019658492979e+00), RES(-2.7572054583883740765e-1, 9.8749461907122384803e-5)}, {FN (csch), ARG(-2.0e+00,-6.28284004019658492979e+00), RES(-2.7572054583883740765e-1, -9.8749461907122384803e-5)}, {FN (csch), ARG(2.0e+00,6.28353057416258753420e+00), RES(2.7572054583883740770e-1, -9.8749461906982280812e-5)}, {FN (csch), ARG(2.0e+00,-6.28353057416258753420e+00), RES(2.7572054583883740770e-1, 9.8749461906982280812e-5)}, {FN (csch), ARG(-2.0e+00,6.28353057416258753420e+00), RES(-2.7572054583883740770e-1, -9.8749461906982280812e-5)}, {FN (csch), ARG(-2.0e+00,-6.28353057416258753420e+00), RES(-2.7572054583883740770e-1, 9.8749461906982280812e-5)}, {FN (csch), ARG(2.0e+00,9.42443269378637893396e+00), RES(-2.7572054583883740773e-1, -9.874946190690338380e-5)}, {FN (csch), ARG(2.0e+00,-9.42443269378637893396e+00), RES(-2.7572054583883740773e-1, 9.874946190690338380e-5)}, {FN (csch), ARG(-2.0e+00,9.42443269378637893396e+00), RES(2.7572054583883740773e-1, -9.874946190690338380e-5)}, {FN (csch), ARG(-2.0e+00,-9.42443269378637893396e+00), RES(2.7572054583883740773e-1, 9.874946190690338380e-5)}, {FN (csch), ARG(2.0e+00,9.42512322775237976202e+00), RES(-2.7572054583883740781e-1, 9.8749461906693227814e-5)}, {FN (csch), ARG(2.0e+00,-9.42512322775237976202e+00), RES(-2.7572054583883740781e-1, -9.8749461906693227814e-5)}, {FN (csch), ARG(-2.0e+00,9.42512322775237976202e+00), RES(2.7572054583883740781e-1, 9.8749461906693227814e-5)}, {FN (csch), ARG(-2.0e+00,-9.42512322775237976202e+00), RES(2.7572054583883740781e-1, -9.8749461906693227814e-5)}, {FN (sech), ARG(0.0e+00,-3.45266983001243932001e-04), RES(1.0000000596046477360e0, 0.0)}, {FN (sech), ARG(0.0e+00,3.45266983001243932001e-04), RES(1.0000000596046477360e0, 0.0)}, {FN (sech), ARG(0.0e+00,1.57045105981189525579e+00), RES(2.8963094332835939217e3, 0.0)}, {FN (sech), ARG(0.0e+00,-1.57045105981189525579e+00), RES(2.8963094332835939217e3, 0.0)}, {FN (sech), ARG(0.0e+00,1.57114159377789786021e+00), RES(-2.8963094332846212298e3, 0.0)}, {FN (sech), ARG(0.0e+00,-1.57114159377789786021e+00), RES(-2.8963094332846212298e3, 0.0)}, {FN (sech), ARG(0.0e+00,3.14124738660679181379e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (sech), ARG(0.0e+00,-3.14124738660679181379e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (sech), ARG(0.0e+00,3.14193792057279441821e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (sech), ARG(0.0e+00,-3.14193792057279441821e+00), RES(-1.0000000596046477360e0, 0.0)}, {FN (sech), ARG(0.0e+00,4.71204371340168837179e+00), RES(-2.8963094332825666135e3, 0.0)}, {FN (sech), ARG(0.0e+00,-4.71204371340168837179e+00), RES(-2.8963094332825666135e3, 0.0)}, {FN (sech), ARG(0.0e+00,4.71273424736769097620e+00), RES(2.8963094332856485380e3, 0.0)}, {FN (sech), ARG(0.0e+00,-4.71273424736769097620e+00), RES(2.8963094332856485380e3, 0.0)}, {FN (sech), ARG(0.0e+00,6.28284004019658492979e+00), RES(1.0000000596046477361e0, 0.0)}, {FN (sech), ARG(0.0e+00,-6.28284004019658492979e+00), RES(1.0000000596046477361e0, 0.0)}, {FN (sech), ARG(0.0e+00,6.28353057416258753420e+00), RES(1.0000000596046477359e0, 0.0)}, {FN (sech), ARG(0.0e+00,-6.28353057416258753420e+00), RES(1.0000000596046477359e0, 0.0)}, {FN (sech), ARG(0.0e+00,9.42443269378637893396e+00), RES(-1.0000000596046477358e0, 0.0)}, {FN (sech), ARG(0.0e+00,-9.42443269378637893396e+00), RES(-1.0000000596046477358e0, 0.0)}, {FN (sech), ARG(0.0e+00,9.42512322775237976202e+00), RES(-1.0000000596046477356e0, 0.0)}, {FN (sech), ARG(0.0e+00,-9.42512322775237976202e+00), RES(-1.0000000596046477356e0, 0.0)}, {FN (sech), ARG(1.19209289550781250e-07,-3.45266983001243932001e-04), RES(1.0000000596046406306e0, 4.1159035837702210125e-11)}, {FN (sech), ARG(1.19209289550781250e-07,3.45266983001243932001e-04), RES(1.0000000596046406306e0, -4.1159035837702210125e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,-3.45266983001243932001e-04), RES(1.0000000596046406306e0, -4.1159035837702210125e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,3.45266983001243932001e-04), RES(1.0000000596046406306e0, 4.1159035837702210125e-11)}, {FN (sech), ARG(1.19209289550781250e-07,1.57045105981189525579e+00), RES(2.8963090880166520798e3, -9.9999986092181650394e-1)}, {FN (sech), ARG(1.19209289550781250e-07,-1.57045105981189525579e+00), RES(2.8963090880166520798e3, 9.9999986092181650394e-1)}, {FN (sech), ARG(-1.19209289550781250e-07,1.57045105981189525579e+00), RES(2.8963090880166520798e3, 9.9999986092181650394e-1)}, {FN (sech), ARG(-1.19209289550781250e-07,-1.57045105981189525579e+00), RES(2.8963090880166520798e3, -9.9999986092181650394e-1)}, {FN (sech), ARG(1.19209289550781250e-07,1.57114159377789786021e+00), RES(-2.8963090880176793876e3, -9.9999986092252589498e-1)}, {FN (sech), ARG(1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-2.8963090880176793876e3, 9.9999986092252589498e-1)}, {FN (sech), ARG(-1.19209289550781250e-07,1.57114159377789786021e+00), RES(-2.8963090880176793876e3, 9.9999986092252589498e-1)}, {FN (sech), ARG(-1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-2.8963090880176793876e3, -9.9999986092252589498e-1)}, {FN (sech), ARG(1.19209289550781250e-07,3.14124738660679181379e+00), RES(-1.0000000596046406306e0, -4.1159035837723756084e-11)}, {FN (sech), ARG(1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-1.0000000596046406306e0, 4.1159035837723756084e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,3.14124738660679181379e+00), RES(-1.0000000596046406306e0, 4.1159035837723756084e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-1.0000000596046406306e0, -4.1159035837723756084e-11)}, {FN (sech), ARG(1.19209289550781250e-07,3.14193792057279441821e+00), RES(-1.0000000596046406305e0, 4.1159035837694558220e-11)}, {FN (sech), ARG(1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-1.0000000596046406305e0, -4.1159035837694558220e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,3.14193792057279441821e+00), RES(-1.0000000596046406305e0, -4.1159035837694558220e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-1.0000000596046406305e0, 4.1159035837694558220e-11)}, {FN (sech), ARG(1.19209289550781250e-07,4.71204371340168837179e+00), RES(-2.8963090880156247720e3, 9.9999986092110711291e-1)}, {FN (sech), ARG(1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-2.8963090880156247720e3, -9.9999986092110711291e-1)}, {FN (sech), ARG(-1.19209289550781250e-07,4.71204371340168837179e+00), RES(-2.8963090880156247720e3, -9.9999986092110711291e-1)}, {FN (sech), ARG(-1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-2.8963090880156247720e3, 9.9999986092110711291e-1)}, {FN (sech), ARG(1.19209289550781250e-07,4.71273424736769097620e+00), RES(2.8963090880187066954e3, 9.9999986092323528601e-1)}, {FN (sech), ARG(1.19209289550781250e-07,-4.71273424736769097620e+00), RES(2.8963090880187066954e3, -9.9999986092323528601e-1)}, {FN (sech), ARG(-1.19209289550781250e-07,4.71273424736769097620e+00), RES(2.8963090880187066954e3, -9.9999986092323528601e-1)}, {FN (sech), ARG(-1.19209289550781250e-07,-4.71273424736769097620e+00), RES(2.8963090880187066954e3, 9.9999986092323528601e-1)}, {FN (sech), ARG(1.19209289550781250e-07,6.28284004019658492979e+00), RES(1.0000000596046406307e0, 4.1159035837738355016e-11)}, {FN (sech), ARG(1.19209289550781250e-07,-6.28284004019658492979e+00), RES(1.0000000596046406307e0, -4.1159035837738355016e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,6.28284004019658492979e+00), RES(1.0000000596046406307e0, -4.1159035837738355016e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,-6.28284004019658492979e+00), RES(1.0000000596046406307e0, 4.1159035837738355016e-11)}, {FN (sech), ARG(1.19209289550781250e-07,6.28353057416258753420e+00), RES(1.0000000596046406305e0, -4.1159035837679959288e-11)}, {FN (sech), ARG(1.19209289550781250e-07,-6.28353057416258753420e+00), RES(1.0000000596046406305e0, 4.1159035837679959288e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,6.28353057416258753420e+00), RES(1.0000000596046406305e0, 4.1159035837679959288e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,-6.28353057416258753420e+00), RES(1.0000000596046406305e0, -4.1159035837679959288e-11)}, {FN (sech), ARG(1.19209289550781250e-07,9.42443269378637893396e+00), RES(-1.0000000596046406304e0, -4.1159035837647074798e-11)}, {FN (sech), ARG(1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-1.0000000596046406304e0, 4.1159035837647074798e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,9.42443269378637893396e+00), RES(-1.0000000596046406304e0, 4.1159035837647074798e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-1.0000000596046406304e0, -4.1159035837647074798e-11)}, {FN (sech), ARG(1.19209289550781250e-07,9.42512322775237976202e+00), RES(-1.0000000596046406301e0, 4.1159035837559481207e-11)}, {FN (sech), ARG(1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-1.0000000596046406301e0, -4.1159035837559481207e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,9.42512322775237976202e+00), RES(-1.0000000596046406301e0, -4.1159035837559481207e-11)}, {FN (sech), ARG(-1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-1.0000000596046406301e0, 4.1159035837559481207e-11)}, {FN (sech), ARG(5.0e-01,-3.45266983001243932001e-04), RES(8.8681891425248302485e-1, 1.4149533035938218250e-4)}, {FN (sech), ARG(5.0e-01,3.45266983001243932001e-04), RES(8.8681891425248302485e-1, -1.4149533035938218250e-4)}, {FN (sech), ARG(-5.0e-01,-3.45266983001243932001e-04), RES(8.8681891425248302485e-1, -1.4149533035938218250e-4)}, {FN (sech), ARG(-5.0e-01,3.45266983001243932001e-04), RES(8.8681891425248302485e-1, 1.4149533035938218250e-4)}, {FN (sech), ARG(5.0e-01,1.57045105981189525579e+00), RES(1.4337901642794764055e-3, -1.9190337944739187231e0)}, {FN (sech), ARG(5.0e-01,-1.57045105981189525579e+00), RES(1.4337901642794764055e-3, 1.9190337944739187231e0)}, {FN (sech), ARG(-5.0e-01,1.57045105981189525579e+00), RES(1.4337901642794764055e-3, 1.9190337944739187231e0)}, {FN (sech), ARG(-5.0e-01,-1.57045105981189525579e+00), RES(1.4337901642794764055e-3, -1.9190337944739187231e0)}, {FN (sech), ARG(5.0e-01,1.57114159377789786021e+00), RES(-1.4337901642789678469e-3, -1.9190337944739187237e0)}, {FN (sech), ARG(5.0e-01,-1.57114159377789786021e+00), RES(-1.4337901642789678469e-3, 1.9190337944739187237e0)}, {FN (sech), ARG(-5.0e-01,1.57114159377789786021e+00), RES(-1.4337901642789678469e-3, 1.9190337944739187237e0)}, {FN (sech), ARG(-5.0e-01,-1.57114159377789786021e+00), RES(-1.4337901642789678469e-3, -1.9190337944739187237e0)}, {FN (sech), ARG(5.0e-01,3.14124738660679181379e+00), RES(-8.8681891425248302488e-1, -1.4149533035945625257e-4)}, {FN (sech), ARG(5.0e-01,-3.14124738660679181379e+00), RES(-8.8681891425248302488e-1, 1.4149533035945625257e-4)}, {FN (sech), ARG(-5.0e-01,3.14124738660679181379e+00), RES(-8.8681891425248302488e-1, 1.4149533035945625257e-4)}, {FN (sech), ARG(-5.0e-01,-3.14124738660679181379e+00), RES(-8.8681891425248302488e-1, -1.4149533035945625257e-4)}, {FN (sech), ARG(5.0e-01,3.14193792057279441821e+00), RES(-8.8681891425248302484e-1, 1.4149533035935587701e-4)}, {FN (sech), ARG(5.0e-01,-3.14193792057279441821e+00), RES(-8.8681891425248302484e-1, -1.4149533035935587701e-4)}, {FN (sech), ARG(-5.0e-01,3.14193792057279441821e+00), RES(-8.8681891425248302484e-1, -1.4149533035935587701e-4)}, {FN (sech), ARG(-5.0e-01,-3.14193792057279441821e+00), RES(-8.8681891425248302484e-1, 1.4149533035935587701e-4)}, {FN (sech), ARG(5.0e-01,4.71204371340168837179e+00), RES(-1.4337901642799849641e-3, 1.9190337944739187224e0)}, {FN (sech), ARG(5.0e-01,-4.71204371340168837179e+00), RES(-1.4337901642799849641e-3, -1.9190337944739187224e0)}, {FN (sech), ARG(-5.0e-01,4.71204371340168837179e+00), RES(-1.4337901642799849641e-3, -1.9190337944739187224e0)}, {FN (sech), ARG(-5.0e-01,-4.71204371340168837179e+00), RES(-1.4337901642799849641e-3, 1.9190337944739187224e0)}, {FN (sech), ARG(5.0e-01,4.71273424736769097620e+00), RES(1.4337901642784592884e-3, 1.9190337944739187244e0)}, {FN (sech), ARG(5.0e-01,-4.71273424736769097620e+00), RES(1.4337901642784592884e-3, -1.9190337944739187244e0)}, {FN (sech), ARG(-5.0e-01,4.71273424736769097620e+00), RES(1.4337901642784592884e-3, -1.9190337944739187244e0)}, {FN (sech), ARG(-5.0e-01,-4.71273424736769097620e+00), RES(1.4337901642784592884e-3, 1.9190337944739187244e0)}, {FN (sech), ARG(5.0e-01,6.28284004019658492979e+00), RES(8.8681891425248302490e-1, 1.4149533035950644034e-4)}, {FN (sech), ARG(5.0e-01,-6.28284004019658492979e+00), RES(8.8681891425248302490e-1, -1.4149533035950644034e-4)}, {FN (sech), ARG(-5.0e-01,6.28284004019658492979e+00), RES(8.8681891425248302490e-1, -1.4149533035950644034e-4)}, {FN (sech), ARG(-5.0e-01,-6.28284004019658492979e+00), RES(8.8681891425248302490e-1, 1.4149533035950644034e-4)}, {FN (sech), ARG(5.0e-01,6.28353057416258753420e+00), RES(8.8681891425248302482e-1, -1.4149533035930568923e-4)}, {FN (sech), ARG(5.0e-01,-6.28353057416258753420e+00), RES(8.8681891425248302482e-1, 1.4149533035930568923e-4)}, {FN (sech), ARG(-5.0e-01,6.28353057416258753420e+00), RES(8.8681891425248302482e-1, 1.4149533035930568923e-4)}, {FN (sech), ARG(-5.0e-01,-6.28353057416258753420e+00), RES(8.8681891425248302482e-1, -1.4149533035930568923e-4)}, {FN (sech), ARG(5.0e-01,9.42443269378637893396e+00), RES(-8.8681891425248302477e-1, -1.4149533035919263990e-4)}, {FN (sech), ARG(5.0e-01,-9.42443269378637893396e+00), RES(-8.8681891425248302477e-1, 1.4149533035919263990e-4)}, {FN (sech), ARG(-5.0e-01,9.42443269378637893396e+00), RES(-8.8681891425248302477e-1, 1.4149533035919263990e-4)}, {FN (sech), ARG(-5.0e-01,-9.42443269378637893396e+00), RES(-8.8681891425248302477e-1, -1.4149533035919263990e-4)}, {FN (sech), ARG(5.0e-01,9.42512322775237976202e+00), RES(-8.8681891425248302464e-1, 1.4149533035889151322e-4)}, {FN (sech), ARG(5.0e-01,-9.42512322775237976202e+00), RES(-8.8681891425248302464e-1, -1.4149533035889151322e-4)}, {FN (sech), ARG(-5.0e-01,9.42512322775237976202e+00), RES(-8.8681891425248302464e-1, -1.4149533035889151322e-4)}, {FN (sech), ARG(-5.0e-01,-9.42512322775237976202e+00), RES(-8.8681891425248302464e-1, 1.4149533035889151322e-4)}, {FN (sech), ARG(1.0e+00,-3.45266983001243932001e-04), RES(6.4805426748157480499e-1, 1.7040802567651502899e-4)}, {FN (sech), ARG(1.0e+00,3.45266983001243932001e-04), RES(6.4805426748157480499e-1, -1.7040802567651502899e-4)}, {FN (sech), ARG(-1.0e+00,-3.45266983001243932001e-04), RES(6.4805426748157480499e-1, -1.7040802567651502899e-4)}, {FN (sech), ARG(-1.0e+00,3.45266983001243932001e-04), RES(6.4805426748157480499e-1, 1.7040802567651502899e-4)}, {FN (sech), ARG(1.0e+00,1.57045105981189525579e+00), RES(3.8576176225212213388e-4, -8.5091800407377002725e-1)}, {FN (sech), ARG(1.0e+00,-1.57045105981189525579e+00), RES(3.8576176225212213388e-4, 8.5091800407377002725e-1)}, {FN (sech), ARG(-1.0e+00,1.57045105981189525579e+00), RES(3.8576176225212213388e-4, 8.5091800407377002725e-1)}, {FN (sech), ARG(-1.0e+00,-1.57045105981189525579e+00), RES(3.8576176225212213388e-4, -8.5091800407377002725e-1)}, {FN (sech), ARG(1.0e+00,1.57114159377789786021e+00), RES(-3.8576176225198530591e-4, -8.5091800407377002734e-1)}, {FN (sech), ARG(1.0e+00,-1.57114159377789786021e+00), RES(-3.8576176225198530591e-4, 8.5091800407377002734e-1)}, {FN (sech), ARG(-1.0e+00,1.57114159377789786021e+00), RES(-3.8576176225198530591e-4, 8.5091800407377002734e-1)}, {FN (sech), ARG(-1.0e+00,-1.57114159377789786021e+00), RES(-3.8576176225198530591e-4, -8.5091800407377002734e-1)}, {FN (sech), ARG(1.0e+00,3.14124738660679181379e+00), RES(-6.4805426748157480499e-1, -1.7040802567660423428e-4)}, {FN (sech), ARG(1.0e+00,-3.14124738660679181379e+00), RES(-6.4805426748157480499e-1, 1.7040802567660423428e-4)}, {FN (sech), ARG(-1.0e+00,3.14124738660679181379e+00), RES(-6.4805426748157480499e-1, 1.7040802567660423428e-4)}, {FN (sech), ARG(-1.0e+00,-3.14124738660679181379e+00), RES(-6.4805426748157480499e-1, -1.7040802567660423428e-4)}, {FN (sech), ARG(1.0e+00,3.14193792057279441821e+00), RES(-6.4805426748157480499e-1, 1.7040802567648334832e-4)}, {FN (sech), ARG(1.0e+00,-3.14193792057279441821e+00), RES(-6.4805426748157480499e-1, -1.7040802567648334832e-4)}, {FN (sech), ARG(-1.0e+00,3.14193792057279441821e+00), RES(-6.4805426748157480499e-1, -1.7040802567648334832e-4)}, {FN (sech), ARG(-1.0e+00,-3.14193792057279441821e+00), RES(-6.4805426748157480499e-1, 1.7040802567648334832e-4)}, {FN (sech), ARG(1.0e+00,4.71204371340168837179e+00), RES(-3.8576176225225896185e-4, 8.5091800407377002716e-1)}, {FN (sech), ARG(1.0e+00,-4.71204371340168837179e+00), RES(-3.8576176225225896185e-4, -8.5091800407377002716e-1)}, {FN (sech), ARG(-1.0e+00,4.71204371340168837179e+00), RES(-3.8576176225225896185e-4, -8.5091800407377002716e-1)}, {FN (sech), ARG(-1.0e+00,-4.71204371340168837179e+00), RES(-3.8576176225225896185e-4, 8.5091800407377002716e-1)}, {FN (sech), ARG(1.0e+00,4.71273424736769097620e+00), RES(3.8576176225184847794e-4, 8.5091800407377002743e-1)}, {FN (sech), ARG(1.0e+00,-4.71273424736769097620e+00), RES(3.8576176225184847794e-4, -8.5091800407377002743e-1)}, {FN (sech), ARG(-1.0e+00,4.71273424736769097620e+00), RES(3.8576176225184847794e-4, -8.5091800407377002743e-1)}, {FN (sech), ARG(-1.0e+00,-4.71273424736769097620e+00), RES(3.8576176225184847794e-4, 8.5091800407377002743e-1)}, {FN (sech), ARG(1.0e+00,6.28284004019658492979e+00), RES(6.4805426748157480498e-1, 1.7040802567666467726e-4)}, {FN (sech), ARG(1.0e+00,-6.28284004019658492979e+00), RES(6.4805426748157480498e-1, -1.7040802567666467726e-4)}, {FN (sech), ARG(-1.0e+00,6.28284004019658492979e+00), RES(6.4805426748157480498e-1, -1.7040802567666467726e-4)}, {FN (sech), ARG(-1.0e+00,-6.28284004019658492979e+00), RES(6.4805426748157480498e-1, 1.7040802567666467726e-4)}, {FN (sech), ARG(1.0e+00,6.28353057416258753420e+00), RES(6.480542674815748050e-1, -1.7040802567642290534e-4)}, {FN (sech), ARG(1.0e+00,-6.28353057416258753420e+00), RES(6.480542674815748050e-1, 1.7040802567642290534e-4)}, {FN (sech), ARG(-1.0e+00,6.28353057416258753420e+00), RES(6.480542674815748050e-1, 1.7040802567642290534e-4)}, {FN (sech), ARG(-1.0e+00,-6.28353057416258753420e+00), RES(6.480542674815748050e-1, -1.7040802567642290534e-4)}, {FN (sech), ARG(1.0e+00,9.42443269378637893396e+00), RES(-6.4805426748157480501e-1, -1.7040802567628675588e-4)}, {FN (sech), ARG(1.0e+00,-9.42443269378637893396e+00), RES(-6.4805426748157480501e-1, 1.7040802567628675588e-4)}, {FN (sech), ARG(-1.0e+00,9.42443269378637893396e+00), RES(-6.4805426748157480501e-1, 1.7040802567628675588e-4)}, {FN (sech), ARG(-1.0e+00,-9.42443269378637893396e+00), RES(-6.4805426748157480501e-1, -1.7040802567628675588e-4)}, {FN (sech), ARG(1.0e+00,9.42512322775237976202e+00), RES(-6.4805426748157480504e-1, 1.704080256759240980e-4)}, {FN (sech), ARG(1.0e+00,-9.42512322775237976202e+00), RES(-6.4805426748157480504e-1, -1.704080256759240980e-4)}, {FN (sech), ARG(-1.0e+00,9.42512322775237976202e+00), RES(-6.4805426748157480504e-1, -1.704080256759240980e-4)}, {FN (sech), ARG(-1.0e+00,-9.42512322775237976202e+00), RES(-6.4805426748157480504e-1, 1.704080256759240980e-4)}, {FN (sech), ARG(2.0e+00,-3.45266983001243932001e-04), RES(2.6580221522968095407e-1, 8.8471445300374010365e-5)}, {FN (sech), ARG(2.0e+00,3.45266983001243932001e-04), RES(2.6580221522968095407e-1, -8.8471445300374010365e-5)}, {FN (sech), ARG(-2.0e+00,-3.45266983001243932001e-04), RES(2.6580221522968095407e-1, -8.8471445300374010365e-5)}, {FN (sech), ARG(-2.0e+00,3.45266983001243932001e-04), RES(2.6580221522968095407e-1, 8.8471445300374010365e-5)}, {FN (sech), ARG(2.0e+00,1.57045105981189525579e+00), RES(9.8749461907069845806e-5, -2.7572054583883740767e-1)}, {FN (sech), ARG(2.0e+00,-1.57045105981189525579e+00), RES(9.8749461907069845806e-5, 2.7572054583883740767e-1)}, {FN (sech), ARG(-2.0e+00,1.57045105981189525579e+00), RES(9.8749461907069845806e-5, 2.7572054583883740767e-1)}, {FN (sech), ARG(-2.0e+00,-1.57045105981189525579e+00), RES(9.8749461907069845806e-5, -2.7572054583883740767e-1)}, {FN (sech), ARG(2.0e+00,1.57114159377789786021e+00), RES(-9.8749461907034819809e-5, -2.7572054583883740768e-1)}, {FN (sech), ARG(2.0e+00,-1.57114159377789786021e+00), RES(-9.8749461907034819809e-5, 2.7572054583883740768e-1)}, {FN (sech), ARG(-2.0e+00,1.57114159377789786021e+00), RES(-9.8749461907034819809e-5, 2.7572054583883740768e-1)}, {FN (sech), ARG(-2.0e+00,-1.57114159377789786021e+00), RES(-9.8749461907034819809e-5, -2.7572054583883740768e-1)}, {FN (sech), ARG(2.0e+00,3.14124738660679181379e+00), RES(-2.6580221522968095405e-1, -8.8471445300420323443e-5)}, {FN (sech), ARG(2.0e+00,-3.14124738660679181379e+00), RES(-2.6580221522968095405e-1, 8.8471445300420323443e-5)}, {FN (sech), ARG(-2.0e+00,3.14124738660679181379e+00), RES(-2.6580221522968095405e-1, 8.8471445300420323443e-5)}, {FN (sech), ARG(-2.0e+00,-3.14124738660679181379e+00), RES(-2.6580221522968095405e-1, -8.8471445300420323443e-5)}, {FN (sech), ARG(2.0e+00,3.14193792057279441821e+00), RES(-2.6580221522968095407e-1, 8.8471445300357562580e-5)}, {FN (sech), ARG(2.0e+00,-3.14193792057279441821e+00), RES(-2.6580221522968095407e-1, -8.8471445300357562580e-5)}, {FN (sech), ARG(-2.0e+00,3.14193792057279441821e+00), RES(-2.6580221522968095407e-1, -8.8471445300357562580e-5)}, {FN (sech), ARG(-2.0e+00,-3.14193792057279441821e+00), RES(-2.6580221522968095407e-1, 8.8471445300357562580e-5)}, {FN (sech), ARG(2.0e+00,4.71204371340168837179e+00), RES(-9.8749461907104871804e-5, 2.7572054583883740766e-1)}, {FN (sech), ARG(2.0e+00,-4.71204371340168837179e+00), RES(-9.8749461907104871804e-5, -2.7572054583883740766e-1)}, {FN (sech), ARG(-2.0e+00,4.71204371340168837179e+00), RES(-9.8749461907104871804e-5, -2.7572054583883740766e-1)}, {FN (sech), ARG(-2.0e+00,-4.71204371340168837179e+00), RES(-9.8749461907104871804e-5, 2.7572054583883740766e-1)}, {FN (sech), ARG(2.0e+00,4.71273424736769097620e+00), RES(9.8749461906999793811e-5, 2.7572054583883740770e-1)}, {FN (sech), ARG(2.0e+00,-4.71273424736769097620e+00), RES(9.8749461906999793811e-5, -2.7572054583883740770e-1)}, {FN (sech), ARG(-2.0e+00,4.71273424736769097620e+00), RES(9.8749461906999793811e-5, -2.7572054583883740770e-1)}, {FN (sech), ARG(-2.0e+00,-4.71273424736769097620e+00), RES(9.8749461906999793811e-5, 2.7572054583883740770e-1)}, {FN (sech), ARG(2.0e+00,6.28284004019658492979e+00), RES(2.6580221522968095404e-1, 8.8471445300451703875e-5)}, {FN (sech), ARG(2.0e+00,-6.28284004019658492979e+00), RES(2.6580221522968095404e-1, -8.8471445300451703875e-5)}, {FN (sech), ARG(-2.0e+00,6.28284004019658492979e+00), RES(2.6580221522968095404e-1, -8.8471445300451703875e-5)}, {FN (sech), ARG(-2.0e+00,-6.28284004019658492979e+00), RES(2.6580221522968095404e-1, 8.8471445300451703875e-5)}, {FN (sech), ARG(2.0e+00,6.28353057416258753420e+00), RES(2.6580221522968095408e-1, -8.8471445300326182148e-5)}, {FN (sech), ARG(2.0e+00,-6.28353057416258753420e+00), RES(2.6580221522968095408e-1, 8.8471445300326182148e-5)}, {FN (sech), ARG(-2.0e+00,6.28353057416258753420e+00), RES(2.6580221522968095408e-1, 8.8471445300326182148e-5)}, {FN (sech), ARG(-2.0e+00,-6.28353057416258753420e+00), RES(2.6580221522968095408e-1, -8.8471445300326182148e-5)}, {FN (sech), ARG(2.0e+00,9.42443269378637893396e+00), RES(-2.6580221522968095410e-1, -8.8471445300255496873e-5)}, {FN (sech), ARG(2.0e+00,-9.42443269378637893396e+00), RES(-2.6580221522968095410e-1, 8.8471445300255496873e-5)}, {FN (sech), ARG(-2.0e+00,9.42443269378637893396e+00), RES(-2.6580221522968095410e-1, 8.8471445300255496873e-5)}, {FN (sech), ARG(-2.0e+00,-9.42443269378637893396e+00), RES(-2.6580221522968095410e-1, -8.8471445300255496873e-5)}, {FN (sech), ARG(2.0e+00,9.42512322775237976202e+00), RES(-2.6580221522968095416e-1, 8.8471445300067214283e-5)}, {FN (sech), ARG(2.0e+00,-9.42512322775237976202e+00), RES(-2.6580221522968095416e-1, -8.8471445300067214283e-5)}, {FN (sech), ARG(-2.0e+00,9.42512322775237976202e+00), RES(-2.6580221522968095416e-1, -8.8471445300067214283e-5)}, {FN (sech), ARG(-2.0e+00,-9.42512322775237976202e+00), RES(-2.6580221522968095416e-1, 8.8471445300067214283e-5)}, {FN (coth), ARG(0.0e+00,-3.45266983001243932001e-04), RES(0, 2.8963092606511032136e3)}, {FN (coth), ARG(0.0e+00,3.45266983001243932001e-04), RES(0, -2.8963092606511032136e3)}, {FN (coth), ARG(0.0e+00,1.57045105981189525579e+00), RES(0, -3.4526699672104134407e-4)}, {FN (coth), ARG(0.0e+00,-1.57045105981189525579e+00), RES(0, 3.4526699672104134407e-4)}, {FN (coth), ARG(0.0e+00,1.57114159377789786021e+00), RES(0, 3.4526699672091887937e-4)}, {FN (coth), ARG(0.0e+00,-1.57114159377789786021e+00), RES(0, -3.4526699672091887937e-4)}, {FN (coth), ARG(0.0e+00,3.14124738660679181379e+00), RES(0, 2.8963092606495870519e3)}, {FN (coth), ARG(0.0e+00,-3.14124738660679181379e+00), RES(0, -2.8963092606495870519e3)}, {FN (coth), ARG(0.0e+00,3.14193792057279441821e+00), RES(0, -2.8963092606516416684e3)}, {FN (coth), ARG(0.0e+00,-3.14193792057279441821e+00), RES(0, 2.8963092606516416684e3)}, {FN (coth), ARG(0.0e+00,4.71204371340168837179e+00), RES(0, -3.4526699672116380876e-4)}, {FN (coth), ARG(0.0e+00,-4.71204371340168837179e+00), RES(0, 3.4526699672116380876e-4)}, {FN (coth), ARG(0.0e+00,4.71273424736769097620e+00), RES(0, 3.4526699672079641468e-4)}, {FN (coth), ARG(0.0e+00,-4.71273424736769097620e+00), RES(0, -3.4526699672079641468e-4)}, {FN (coth), ARG(0.0e+00,6.28284004019658492979e+00), RES(0, 2.8963092606485597437e3)}, {FN (coth), ARG(0.0e+00,-6.28284004019658492979e+00), RES(0, -2.8963092606485597437e3)}, {FN (coth), ARG(0.0e+00,6.28353057416258753420e+00), RES(0, -2.8963092606526689766e3)}, {FN (coth), ARG(0.0e+00,-6.28353057416258753420e+00), RES(0, 2.8963092606526689766e3)}, {FN (coth), ARG(0.0e+00,9.42443269378637893396e+00), RES(0, 2.8963092606549830163e3)}, {FN (coth), ARG(0.0e+00,-9.42443269378637893396e+00), RES(0, -2.8963092606549830163e3)}, {FN (coth), ARG(0.0e+00,9.42512322775237976202e+00), RES(0, -2.8963092606611468657e3)}, {FN (coth), ARG(0.0e+00,-9.42512322775237976202e+00), RES(0, 2.8963092606611468657e3)}, {FN (coth), ARG(1.19209289550781250e-07,-3.45266983001243932001e-04), RES(9.9999992052715532101e-1, 2.8963089153841613713e3)}, {FN (coth), ARG(1.19209289550781250e-07,3.45266983001243932001e-04), RES(9.9999992052715532101e-1, -2.8963089153841613713e3)}, {FN (coth), ARG(-1.19209289550781250e-07,-3.45266983001243932001e-04), RES(-9.9999992052715532101e-1, 2.8963089153841613713e3)}, {FN (coth), ARG(-1.19209289550781250e-07,3.45266983001243932001e-04), RES(-9.9999992052715532101e-1, -2.8963089153841613713e3)}, {FN (coth), ARG(1.19209289550781250e-07,1.57045105981189525579e+00), RES(1.1920930376163652990e-7, -3.4526699672103643753e-4)}, {FN (coth), ARG(1.19209289550781250e-07,-1.57045105981189525579e+00), RES(1.1920930376163652990e-7, 3.4526699672103643753e-4)}, {FN (coth), ARG(-1.19209289550781250e-07,1.57045105981189525579e+00), RES(-1.1920930376163652990e-7, -3.4526699672103643753e-4)}, {FN (coth), ARG(-1.19209289550781250e-07,-1.57045105981189525579e+00), RES(-1.1920930376163652990e-7, 3.4526699672103643753e-4)}, {FN (coth), ARG(1.19209289550781250e-07,1.57114159377789786021e+00), RES(1.1920930376163652989e-7, 3.4526699672091397283e-4)}, {FN (coth), ARG(1.19209289550781250e-07,-1.57114159377789786021e+00), RES(1.1920930376163652989e-7, -3.4526699672091397283e-4)}, {FN (coth), ARG(-1.19209289550781250e-07,1.57114159377789786021e+00), RES(-1.1920930376163652989e-7, 3.4526699672091397283e-4)}, {FN (coth), ARG(-1.19209289550781250e-07,-1.57114159377789786021e+00), RES(-1.1920930376163652989e-7, -3.4526699672091397283e-4)}, {FN (coth), ARG(1.19209289550781250e-07,3.14124738660679181379e+00), RES(9.9999992052610836018e-1, 2.8963089153826452102e3)}, {FN (coth), ARG(1.19209289550781250e-07,-3.14124738660679181379e+00), RES(9.9999992052610836018e-1, -2.8963089153826452102e3)}, {FN (coth), ARG(-1.19209289550781250e-07,3.14124738660679181379e+00), RES(-9.9999992052610836018e-1, 2.8963089153826452102e3)}, {FN (coth), ARG(-1.19209289550781250e-07,-3.14124738660679181379e+00), RES(-9.9999992052610836018e-1, -2.8963089153826452102e3)}, {FN (coth), ARG(1.19209289550781250e-07,3.14193792057279441821e+00), RES(9.9999992052752714224e-1, -2.8963089153846998260e3)}, {FN (coth), ARG(1.19209289550781250e-07,-3.14193792057279441821e+00), RES(9.9999992052752714224e-1, 2.8963089153846998260e3)}, {FN (coth), ARG(-1.19209289550781250e-07,3.14193792057279441821e+00), RES(-9.9999992052752714224e-1, -2.8963089153846998260e3)}, {FN (coth), ARG(-1.19209289550781250e-07,-3.14193792057279441821e+00), RES(-9.9999992052752714224e-1, 2.8963089153846998260e3)}, {FN (coth), ARG(1.19209289550781250e-07,4.71204371340168837179e+00), RES(1.1920930376163652991e-7, -3.4526699672115890222e-4)}, {FN (coth), ARG(1.19209289550781250e-07,-4.71204371340168837179e+00), RES(1.1920930376163652991e-7, 3.4526699672115890222e-4)}, {FN (coth), ARG(-1.19209289550781250e-07,4.71204371340168837179e+00), RES(-1.1920930376163652991e-7, -3.4526699672115890222e-4)}, {FN (coth), ARG(-1.19209289550781250e-07,-4.71204371340168837179e+00), RES(-1.1920930376163652991e-7, 3.4526699672115890222e-4)}, {FN (coth), ARG(1.19209289550781250e-07,4.71273424736769097620e+00), RES(1.1920930376163652988e-7, 3.4526699672079150814e-4)}, {FN (coth), ARG(1.19209289550781250e-07,-4.71273424736769097620e+00), RES(1.1920930376163652988e-7, -3.4526699672079150814e-4)}, {FN (coth), ARG(-1.19209289550781250e-07,4.71273424736769097620e+00), RES(-1.1920930376163652988e-7, 3.4526699672079150814e-4)}, {FN (coth), ARG(-1.19209289550781250e-07,-4.71273424736769097620e+00), RES(-1.1920930376163652988e-7, -3.4526699672079150814e-4)}, {FN (coth), ARG(1.19209289550781250e-07,6.28284004019658492979e+00), RES(9.9999992052539896914e-1, 2.8963089153816179024e3)}, {FN (coth), ARG(1.19209289550781250e-07,-6.28284004019658492979e+00), RES(9.9999992052539896914e-1, -2.8963089153816179024e3)}, {FN (coth), ARG(-1.19209289550781250e-07,6.28284004019658492979e+00), RES(-9.9999992052539896914e-1, 2.8963089153816179024e3)}, {FN (coth), ARG(-1.19209289550781250e-07,-6.28284004019658492979e+00), RES(-9.9999992052539896914e-1, -2.8963089153816179024e3)}, {FN (coth), ARG(1.19209289550781250e-07,6.28353057416258753420e+00), RES(9.9999992052823653327e-1, -2.8963089153857271338e3)}, {FN (coth), ARG(1.19209289550781250e-07,-6.28353057416258753420e+00), RES(9.9999992052823653327e-1, 2.8963089153857271338e3)}, {FN (coth), ARG(-1.19209289550781250e-07,6.28353057416258753420e+00), RES(-9.9999992052823653327e-1, -2.8963089153857271338e3)}, {FN (coth), ARG(-1.19209289550781250e-07,-6.28353057416258753420e+00), RES(-9.9999992052823653327e-1, 2.8963089153857271338e3)}, {FN (coth), ARG(1.19209289550781250e-07,9.42443269378637893396e+00), RES(9.9999992052983445585e-1, 2.8963089153880411727e3)}, {FN (coth), ARG(1.19209289550781250e-07,-9.42443269378637893396e+00), RES(9.9999992052983445585e-1, -2.8963089153880411727e3)}, {FN (coth), ARG(-1.19209289550781250e-07,9.42443269378637893396e+00), RES(-9.9999992052983445585e-1, 2.8963089153880411727e3)}, {FN (coth), ARG(-1.19209289550781250e-07,-9.42443269378637893396e+00), RES(-9.9999992052983445585e-1, -2.8963089153880411727e3)}, {FN (coth), ARG(1.19209289550781250e-07,9.42512322775237976202e+00), RES(9.9999992053409080205e-1, -2.8963089153942050199e3)}, {FN (coth), ARG(1.19209289550781250e-07,-9.42512322775237976202e+00), RES(9.9999992053409080205e-1, 2.8963089153942050199e3)}, {FN (coth), ARG(-1.19209289550781250e-07,9.42512322775237976202e+00), RES(-9.9999992053409080205e-1, -2.8963089153942050199e3)}, {FN (coth), ARG(-1.19209289550781250e-07,-9.42512322775237976202e+00), RES(-9.9999992053409080205e-1, 2.8963089153942050199e3)}, {FN (coth), ARG(5.0e-01,-3.45266983001243932001e-04), RES(2.1639524637389326002e0, 1.2715121175451222247e-3)}, {FN (coth), ARG(5.0e-01,3.45266983001243932001e-04), RES(2.1639524637389326002e0, -1.2715121175451222247e-3)}, {FN (coth), ARG(-5.0e-01,-3.45266983001243932001e-04), RES(-2.1639524637389326002e0, 1.2715121175451222247e-3)}, {FN (coth), ARG(-5.0e-01,3.45266983001243932001e-04), RES(-2.1639524637389326002e0, -1.2715121175451222247e-3)}, {FN (coth), ARG(5.0e-01,1.57045105981189525579e+00), RES(4.6211720058436229982e-1, -2.7153443992665204631e-4)}, {FN (coth), ARG(5.0e-01,-1.57045105981189525579e+00), RES(4.6211720058436229982e-1, 2.7153443992665204631e-4)}, {FN (coth), ARG(-5.0e-01,1.57045105981189525579e+00), RES(-4.6211720058436229982e-1, -2.7153443992665204631e-4)}, {FN (coth), ARG(-5.0e-01,-1.57045105981189525579e+00), RES(-4.6211720058436229982e-1, 2.7153443992665204631e-4)}, {FN (coth), ARG(5.0e-01,1.57114159377789786021e+00), RES(4.6211720058436229979e-1, 2.7153443992655573423e-4)}, {FN (coth), ARG(5.0e-01,-1.57114159377789786021e+00), RES(4.6211720058436229979e-1, -2.7153443992655573423e-4)}, {FN (coth), ARG(-5.0e-01,1.57114159377789786021e+00), RES(-4.6211720058436229979e-1, 2.7153443992655573423e-4)}, {FN (coth), ARG(-5.0e-01,-1.57114159377789786021e+00), RES(-4.6211720058436229979e-1, -2.7153443992655573423e-4)}, {FN (coth), ARG(5.0e-01,3.14124738660679181379e+00), RES(2.1639524637389325992e0, 1.2715121175457878359e-3)}, {FN (coth), ARG(5.0e-01,-3.14124738660679181379e+00), RES(2.1639524637389325992e0, -1.2715121175457878359e-3)}, {FN (coth), ARG(-5.0e-01,3.14124738660679181379e+00), RES(-2.1639524637389325992e0, 1.2715121175457878359e-3)}, {FN (coth), ARG(-5.0e-01,-3.14124738660679181379e+00), RES(-2.1639524637389325992e0, -1.2715121175457878359e-3)}, {FN (coth), ARG(5.0e-01,3.14193792057279441821e+00), RES(2.1639524637389326006e0, -1.2715121175448858373e-3)}, {FN (coth), ARG(5.0e-01,-3.14193792057279441821e+00), RES(2.1639524637389326006e0, 1.2715121175448858373e-3)}, {FN (coth), ARG(-5.0e-01,3.14193792057279441821e+00), RES(-2.1639524637389326006e0, -1.2715121175448858373e-3)}, {FN (coth), ARG(-5.0e-01,-3.14193792057279441821e+00), RES(-2.1639524637389326006e0, 1.2715121175448858373e-3)}, {FN (coth), ARG(5.0e-01,4.71204371340168837179e+00), RES(4.6211720058436229985e-1, -2.7153443992674835838e-4)}, {FN (coth), ARG(5.0e-01,-4.71204371340168837179e+00), RES(4.6211720058436229985e-1, 2.7153443992674835838e-4)}, {FN (coth), ARG(-5.0e-01,4.71204371340168837179e+00), RES(-4.6211720058436229985e-1, -2.7153443992674835838e-4)}, {FN (coth), ARG(-5.0e-01,-4.71204371340168837179e+00), RES(-4.6211720058436229985e-1, 2.7153443992674835838e-4)}, {FN (coth), ARG(5.0e-01,4.71273424736769097620e+00), RES(4.6211720058436229976e-1, 2.7153443992645942216e-4)}, {FN (coth), ARG(5.0e-01,-4.71273424736769097620e+00), RES(4.6211720058436229976e-1, -2.7153443992645942216e-4)}, {FN (coth), ARG(-5.0e-01,4.71273424736769097620e+00), RES(-4.6211720058436229976e-1, 2.7153443992645942216e-4)}, {FN (coth), ARG(-5.0e-01,-4.71273424736769097620e+00), RES(-4.6211720058436229976e-1, -2.7153443992645942216e-4)}, {FN (coth), ARG(5.0e-01,6.28284004019658492979e+00), RES(2.1639524637389325986e0, 1.2715121175462388352e-3)}, {FN (coth), ARG(5.0e-01,-6.28284004019658492979e+00), RES(2.1639524637389325986e0, -1.2715121175462388352e-3)}, {FN (coth), ARG(-5.0e-01,6.28284004019658492979e+00), RES(-2.1639524637389325986e0, 1.2715121175462388352e-3)}, {FN (coth), ARG(-5.0e-01,-6.28284004019658492979e+00), RES(-2.1639524637389325986e0, -1.2715121175462388352e-3)}, {FN (coth), ARG(5.0e-01,6.28353057416258753420e+00), RES(2.1639524637389326012e0, -1.2715121175444348380e-3)}, {FN (coth), ARG(5.0e-01,-6.28353057416258753420e+00), RES(2.1639524637389326012e0, 1.2715121175444348380e-3)}, {FN (coth), ARG(-5.0e-01,6.28353057416258753420e+00), RES(-2.1639524637389326012e0, -1.2715121175444348380e-3)}, {FN (coth), ARG(-5.0e-01,-6.28353057416258753420e+00), RES(-2.1639524637389326012e0, 1.2715121175444348380e-3)}, {FN (coth), ARG(5.0e-01,9.42443269378637893396e+00), RES(2.1639524637389326028e0, 1.2715121175434189499e-3)}, {FN (coth), ARG(5.0e-01,-9.42443269378637893396e+00), RES(2.1639524637389326028e0, -1.2715121175434189499e-3)}, {FN (coth), ARG(-5.0e-01,9.42443269378637893396e+00), RES(-2.1639524637389326028e0, 1.2715121175434189499e-3)}, {FN (coth), ARG(-5.0e-01,-9.42443269378637893396e+00), RES(-2.1639524637389326028e0, -1.2715121175434189499e-3)}, {FN (coth), ARG(5.0e-01,9.42512322775237976202e+00), RES(2.1639524637389326068e0, -1.2715121175407129542e-3)}, {FN (coth), ARG(5.0e-01,-9.42512322775237976202e+00), RES(2.1639524637389326068e0, 1.2715121175407129542e-3)}, {FN (coth), ARG(-5.0e-01,9.42512322775237976202e+00), RES(-2.1639524637389326068e0, -1.2715121175407129542e-3)}, {FN (coth), ARG(-5.0e-01,-9.42512322775237976202e+00), RES(-2.1639524637389326068e0, 1.2715121175407129542e-3)}, {FN (coth), ARG(1.0e+00,-3.45266983001243932001e-04), RES(1.3130351721648674824e0, 2.4999454374267620687e-4)}, {FN (coth), ARG(1.0e+00,3.45266983001243932001e-04), RES(1.3130351721648674824e0, -2.4999454374267620687e-4)}, {FN (coth), ARG(-1.0e+00,-3.45266983001243932001e-04), RES(-1.3130351721648674824e0, 2.4999454374267620687e-4)}, {FN (coth), ARG(-1.0e+00,3.45266983001243932001e-04), RES(-1.3130351721648674824e0, -2.4999454374267620687e-4)}, {FN (coth), ARG(1.0e+00,1.57045105981189525579e+00), RES(7.6159419408485704839e-1, -1.4500326960279979918e-4)}, {FN (coth), ARG(1.0e+00,-1.57045105981189525579e+00), RES(7.6159419408485704839e-1, 1.4500326960279979918e-4)}, {FN (coth), ARG(-1.0e+00,1.57045105981189525579e+00), RES(-7.6159419408485704839e-1, -1.4500326960279979918e-4)}, {FN (coth), ARG(-1.0e+00,-1.57045105981189525579e+00), RES(-7.6159419408485704839e-1, 1.4500326960279979918e-4)}, {FN (coth), ARG(1.0e+00,1.57114159377789786021e+00), RES(7.6159419408485704836e-1, 1.4500326960274836716e-4)}, {FN (coth), ARG(1.0e+00,-1.57114159377789786021e+00), RES(7.6159419408485704836e-1, -1.4500326960274836716e-4)}, {FN (coth), ARG(-1.0e+00,1.57114159377789786021e+00), RES(-7.6159419408485704836e-1, 1.4500326960274836716e-4)}, {FN (coth), ARG(-1.0e+00,-1.57114159377789786021e+00), RES(-7.6159419408485704836e-1, -1.4500326960274836716e-4)}, {FN (coth), ARG(1.0e+00,3.14124738660679181379e+00), RES(1.3130351721648674823e0, 2.4999454374280707411e-4)}, {FN (coth), ARG(1.0e+00,-3.14124738660679181379e+00), RES(1.3130351721648674823e0, -2.4999454374280707411e-4)}, {FN (coth), ARG(-1.0e+00,3.14124738660679181379e+00), RES(-1.3130351721648674823e0, 2.4999454374280707411e-4)}, {FN (coth), ARG(-1.0e+00,-3.14124738660679181379e+00), RES(-1.3130351721648674823e0, -2.4999454374280707411e-4)}, {FN (coth), ARG(1.0e+00,3.14193792057279441821e+00), RES(1.3130351721648674824e0, -2.4999454374262973024e-4)}, {FN (coth), ARG(1.0e+00,-3.14193792057279441821e+00), RES(1.3130351721648674824e0, 2.4999454374262973024e-4)}, {FN (coth), ARG(-1.0e+00,3.14193792057279441821e+00), RES(-1.3130351721648674824e0, -2.4999454374262973024e-4)}, {FN (coth), ARG(-1.0e+00,-3.14193792057279441821e+00), RES(-1.3130351721648674824e0, 2.4999454374262973024e-4)}, {FN (coth), ARG(1.0e+00,4.71204371340168837179e+00), RES(7.6159419408485704842e-1, -1.4500326960285123120e-4)}, {FN (coth), ARG(1.0e+00,-4.71204371340168837179e+00), RES(7.6159419408485704842e-1, 1.4500326960285123120e-4)}, {FN (coth), ARG(-1.0e+00,4.71204371340168837179e+00), RES(-7.6159419408485704842e-1, -1.4500326960285123120e-4)}, {FN (coth), ARG(-1.0e+00,-4.71204371340168837179e+00), RES(-7.6159419408485704842e-1, 1.4500326960285123120e-4)}, {FN (coth), ARG(1.0e+00,4.71273424736769097620e+00), RES(7.6159419408485704834e-1, 1.4500326960269693514e-4)}, {FN (coth), ARG(1.0e+00,-4.71273424736769097620e+00), RES(7.6159419408485704834e-1, -1.4500326960269693514e-4)}, {FN (coth), ARG(-1.0e+00,4.71273424736769097620e+00), RES(-7.6159419408485704834e-1, 1.4500326960269693514e-4)}, {FN (coth), ARG(-1.0e+00,-4.71273424736769097620e+00), RES(-7.6159419408485704834e-1, -1.4500326960269693514e-4)}, {FN (coth), ARG(1.0e+00,6.28284004019658492979e+00), RES(1.3130351721648674822e0, 2.4999454374289574604e-4)}, {FN (coth), ARG(1.0e+00,-6.28284004019658492979e+00), RES(1.3130351721648674822e0, -2.4999454374289574604e-4)}, {FN (coth), ARG(-1.0e+00,6.28284004019658492979e+00), RES(-1.3130351721648674822e0, 2.4999454374289574604e-4)}, {FN (coth), ARG(-1.0e+00,-6.28284004019658492979e+00), RES(-1.3130351721648674822e0, -2.4999454374289574604e-4)}, {FN (coth), ARG(1.0e+00,6.28353057416258753420e+00), RES(1.3130351721648674825e0, -2.4999454374254105830e-4)}, {FN (coth), ARG(1.0e+00,-6.28353057416258753420e+00), RES(1.3130351721648674825e0, 2.4999454374254105830e-4)}, {FN (coth), ARG(-1.0e+00,6.28353057416258753420e+00), RES(-1.3130351721648674825e0, -2.4999454374254105830e-4)}, {FN (coth), ARG(-1.0e+00,-6.28353057416258753420e+00), RES(-1.3130351721648674825e0, 2.4999454374254105830e-4)}, {FN (coth), ARG(1.0e+00,9.42443269378637893396e+00), RES(1.3130351721648674827e0, 2.4999454374234132236e-4)}, {FN (coth), ARG(1.0e+00,-9.42443269378637893396e+00), RES(1.3130351721648674827e0, -2.4999454374234132236e-4)}, {FN (coth), ARG(-1.0e+00,9.42443269378637893396e+00), RES(-1.3130351721648674827e0, 2.4999454374234132236e-4)}, {FN (coth), ARG(-1.0e+00,-9.42443269378637893396e+00), RES(-1.3130351721648674827e0, -2.4999454374234132236e-4)}, {FN (coth), ARG(1.0e+00,9.42512322775237976202e+00), RES(1.3130351721648674832e0, -2.4999454374180929074e-4)}, {FN (coth), ARG(1.0e+00,-9.42512322775237976202e+00), RES(1.3130351721648674832e0, 2.4999454374180929074e-4)}, {FN (coth), ARG(-1.0e+00,9.42512322775237976202e+00), RES(-1.3130351721648674832e0, -2.4999454374180929074e-4)}, {FN (coth), ARG(-1.0e+00,-9.42512322775237976202e+00), RES(-1.3130351721648674832e0, 2.4999454374180929074e-4)}, {FN (coth), ARG(2.0e+00,-3.45266983001243932001e-04), RES(1.0373147113268752620e0, 2.6247825506563736365e-5)}, {FN (coth), ARG(2.0e+00,3.45266983001243932001e-04), RES(1.0373147113268752620e0, -2.6247825506563736365e-5)}, {FN (coth), ARG(-2.0e+00,-3.45266983001243932001e-04), RES(-1.0373147113268752620e0, 2.6247825506563736365e-5)}, {FN (coth), ARG(-2.0e+00,3.45266983001243932001e-04), RES(-1.0373147113268752620e0, -2.6247825506563736365e-5)}, {FN (coth), ARG(2.0e+00,1.57045105981189525579e+00), RES(9.6402758819508310557e-1, -2.4393395410443750226e-5)}, {FN (coth), ARG(2.0e+00,-1.57045105981189525579e+00), RES(9.6402758819508310557e-1, 2.4393395410443750226e-5)}, {FN (coth), ARG(-2.0e+00,1.57045105981189525579e+00), RES(-9.6402758819508310557e-1, -2.4393395410443750226e-5)}, {FN (coth), ARG(-2.0e+00,-1.57045105981189525579e+00), RES(-9.6402758819508310557e-1, 2.4393395410443750226e-5)}, {FN (coth), ARG(2.0e+00,1.57114159377789786021e+00), RES(9.6402758819508310556e-1, 2.4393395410435097997e-5)}, {FN (coth), ARG(2.0e+00,-1.57114159377789786021e+00), RES(9.6402758819508310556e-1, -2.4393395410435097997e-5)}, {FN (coth), ARG(-2.0e+00,1.57114159377789786021e+00), RES(-9.6402758819508310556e-1, 2.4393395410435097997e-5)}, {FN (coth), ARG(-2.0e+00,-1.57114159377789786021e+00), RES(-9.6402758819508310556e-1, -2.4393395410435097997e-5)}, {FN (coth), ARG(2.0e+00,3.14124738660679181379e+00), RES(1.0373147113268752620e0, 2.6247825506577476589e-5)}, {FN (coth), ARG(2.0e+00,-3.14124738660679181379e+00), RES(1.0373147113268752620e0, -2.6247825506577476589e-5)}, {FN (coth), ARG(-2.0e+00,3.14124738660679181379e+00), RES(-1.0373147113268752620e0, 2.6247825506577476589e-5)}, {FN (coth), ARG(-2.0e+00,-3.14124738660679181379e+00), RES(-1.0373147113268752620e0, -2.6247825506577476589e-5)}, {FN (coth), ARG(2.0e+00,3.14193792057279441821e+00), RES(1.0373147113268752620e0, -2.6247825506558856616e-5)}, {FN (coth), ARG(2.0e+00,-3.14193792057279441821e+00), RES(1.0373147113268752620e0, 2.6247825506558856616e-5)}, {FN (coth), ARG(-2.0e+00,3.14193792057279441821e+00), RES(-1.0373147113268752620e0, -2.6247825506558856616e-5)}, {FN (coth), ARG(-2.0e+00,-3.14193792057279441821e+00), RES(-1.0373147113268752620e0, 2.6247825506558856616e-5)}, {FN (coth), ARG(2.0e+00,4.71204371340168837179e+00), RES(9.6402758819508310557e-1, -2.4393395410452402454e-5)}, {FN (coth), ARG(2.0e+00,-4.71204371340168837179e+00), RES(9.6402758819508310557e-1, 2.4393395410452402454e-5)}, {FN (coth), ARG(-2.0e+00,4.71204371340168837179e+00), RES(-9.6402758819508310557e-1, -2.4393395410452402454e-5)}, {FN (coth), ARG(-2.0e+00,-4.71204371340168837179e+00), RES(-9.6402758819508310557e-1, 2.4393395410452402454e-5)}, {FN (coth), ARG(2.0e+00,4.71273424736769097620e+00), RES(9.6402758819508310556e-1, 2.4393395410426445768e-5)}, {FN (coth), ARG(2.0e+00,-4.71273424736769097620e+00), RES(9.6402758819508310556e-1, -2.4393395410426445768e-5)}, {FN (coth), ARG(-2.0e+00,4.71273424736769097620e+00), RES(-9.6402758819508310556e-1, 2.4393395410426445768e-5)}, {FN (coth), ARG(-2.0e+00,-4.71273424736769097620e+00), RES(-9.6402758819508310556e-1, -2.4393395410426445768e-5)}, {FN (coth), ARG(2.0e+00,6.28284004019658492979e+00), RES(1.0373147113268752620e0, 2.6247825506586786575e-5)}, {FN (coth), ARG(2.0e+00,-6.28284004019658492979e+00), RES(1.0373147113268752620e0, -2.6247825506586786575e-5)}, {FN (coth), ARG(-2.0e+00,6.28284004019658492979e+00), RES(-1.0373147113268752620e0, 2.6247825506586786575e-5)}, {FN (coth), ARG(-2.0e+00,-6.28284004019658492979e+00), RES(-1.0373147113268752620e0, -2.6247825506586786575e-5)}, {FN (coth), ARG(2.0e+00,6.28353057416258753420e+00), RES(1.0373147113268752620e0, -2.6247825506549546629e-5)}, {FN (coth), ARG(2.0e+00,-6.28353057416258753420e+00), RES(1.0373147113268752620e0, 2.6247825506549546629e-5)}, {FN (coth), ARG(-2.0e+00,6.28353057416258753420e+00), RES(-1.0373147113268752620e0, -2.6247825506549546629e-5)}, {FN (coth), ARG(-2.0e+00,-6.28353057416258753420e+00), RES(-1.0373147113268752620e0, 2.6247825506549546629e-5)}, {FN (coth), ARG(2.0e+00,9.42443269378637893396e+00), RES(1.0373147113268752620e0, 2.6247825506528575631e-5)}, {FN (coth), ARG(2.0e+00,-9.42443269378637893396e+00), RES(1.0373147113268752620e0, -2.6247825506528575631e-5)}, {FN (coth), ARG(-2.0e+00,9.42443269378637893396e+00), RES(-1.0373147113268752620e0, 2.6247825506528575631e-5)}, {FN (coth), ARG(-2.0e+00,-9.42443269378637893396e+00), RES(-1.0373147113268752620e0, -2.6247825506528575631e-5)}, {FN (coth), ARG(2.0e+00,9.42512322775237976202e+00), RES(1.0373147113268752621e0, -2.6247825506472715712e-5)}, {FN (coth), ARG(2.0e+00,-9.42512322775237976202e+00), RES(1.0373147113268752621e0, 2.6247825506472715712e-5)}, {FN (coth), ARG(-2.0e+00,9.42512322775237976202e+00), RES(-1.0373147113268752621e0, -2.6247825506472715712e-5)}, {FN (coth), ARG(-2.0e+00,-9.42512322775237976202e+00), RES(-1.0373147113268752621e0, 2.6247825506472715712e-5)}, {FN (arccsch), ARG(0.0e+00,1.19209289550781250e-07), RES(-1.6635532333438683873e1, -1.5707963267948966192e0)}, {FN (arccsch), ARG(0.0e+00,-1.19209289550781250e-07), RES(1.6635532333438683873e1, 1.5707963267948966192e0)}, {FN (arccsch), ARG(0.0e+00,5.0e-01), RES(-1.3169578969248167086e0, -1.5707963267948966192e0)}, {FN (arccsch), ARG(0.0e+00,-5.0e-01), RES(1.3169578969248167086e0, 1.5707963267948966192e0)}, {FN (arccsch), ARG(0.0e+00,1.0e+00), RES(0, -1.5707963267948966192e0)}, {FN (arccsch), ARG(0.0e+00,-1.0e+00), RES(0, 1.5707963267948966192e0)}, {FN (arccsch), ARG(0.0e+00,2.0e+00), RES(0, -5.2359877559829887308e-1)}, {FN (arccsch), ARG(0.0e+00,-2.0e+00), RES(0, 5.2359877559829887308e-1)}, {FN (arccsch), ARG(0.0e+00,8.3886080e+06), RES(0, -1.1920928955078153234e-7)}, {FN (arccsch), ARG(0.0e+00,-8.3886080e+06), RES(0, 1.1920928955078153234e-7)}, {FN (arccsch), ARG(1.19209289550781250e-07,0.0e+00), RES(1.6635532333438690979e1, 0.0)}, {FN (arccsch), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.6635532333438690979e1, 0.0)}, {FN (arccsch), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.6288958743158714771e1, -7.8539816339744120419e-1)}, {FN (arccsch), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.6288958743158714771e1, 7.8539816339744120419e-1)}, {FN (arccsch), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.6288958743158714771e1, -7.8539816339744120419e-1)}, {FN (arccsch), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.6288958743158714771e1, 7.8539816339744120419e-1)}, {FN (arccsch), ARG(1.19209289550781250e-07,5.0e-01), RES(1.3169578969247948296e0, -1.5707960514928349710e0)}, {FN (arccsch), ARG(1.19209289550781250e-07,-5.0e-01), RES(1.3169578969247948296e0, 1.5707960514928349710e0)}, {FN (arccsch), ARG(-1.19209289550781250e-07,5.0e-01), RES(-1.3169578969247948296e0, -1.5707960514928349710e0)}, {FN (arccsch), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-1.3169578969247948296e0, 1.5707960514928349710e0)}, {FN (arccsch), ARG(1.19209289550781250e-07,1.0e+00), RES(3.4526696585164602772e-4, -1.5704510597947457801e0)}, {FN (arccsch), ARG(1.19209289550781250e-07,-1.0e+00), RES(3.4526696585164602772e-4, 1.5704510597947457801e0)}, {FN (arccsch), ARG(-1.19209289550781250e-07,1.0e+00), RES(-3.4526696585164602772e-4, -1.5704510597947457801e0)}, {FN (arccsch), ARG(-1.19209289550781250e-07,-1.0e+00), RES(-3.4526696585164602772e-4, 1.5704510597947457801e0)}, {FN (arccsch), ARG(1.19209289550781250e-07,2.0e+00), RES(3.4412757706023621662e-8, -5.2359877559829648006e-1)}, {FN (arccsch), ARG(1.19209289550781250e-07,-2.0e+00), RES(3.4412757706023621662e-8, 5.2359877559829648006e-1)}, {FN (arccsch), ARG(-1.19209289550781250e-07,2.0e+00), RES(-3.4412757706023621662e-8, -5.2359877559829648006e-1)}, {FN (arccsch), ARG(-1.19209289550781250e-07,-2.0e+00), RES(-3.4412757706023621662e-8, 5.2359877559829648006e-1)}, {FN (arccsch), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.6940658945086127152e-21, -1.1920928955078153234e-7)}, {FN (arccsch), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.6940658945086127152e-21, 1.1920928955078153234e-7)}, {FN (arccsch), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(-1.6940658945086127152e-21, -1.1920928955078153234e-7)}, {FN (arccsch), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(-1.6940658945086127152e-21, 1.1920928955078153234e-7)}, {FN (arccsch), ARG(5.0e-01,0.0e+00), RES(1.4436354751788103425e0, 0.0)}, {FN (arccsch), ARG(-5.0e-01,0.0e+00), RES(-1.4436354751788103425e0, 0.0)}, {FN (arccsch), ARG(5.0e-01,1.19209289550781250e-07), RES(1.4436354751787798371e0, -2.1324805998799710740e-7)}, {FN (arccsch), ARG(5.0e-01,-1.19209289550781250e-07), RES(1.4436354751787798371e0, 2.1324805998799710740e-7)}, {FN (arccsch), ARG(-5.0e-01,1.19209289550781250e-07), RES(-1.4436354751787798371e0, -2.1324805998799710740e-7)}, {FN (arccsch), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-1.4436354751787798371e0, 2.1324805998799710740e-7)}, {FN (arccsch), ARG(5.0e-01,5.0e-01), RES(1.0612750619050356520e0, -6.6623943249251525510e-1)}, {FN (arccsch), ARG(5.0e-01,-5.0e-01), RES(1.0612750619050356520e0, 6.6623943249251525510e-1)}, {FN (arccsch), ARG(-5.0e-01,5.0e-01), RES(-1.0612750619050356520e0, -6.6623943249251525510e-1)}, {FN (arccsch), ARG(-5.0e-01,-5.0e-01), RES(-1.0612750619050356520e0, 6.6623943249251525510e-1)}, {FN (arccsch), ARG(5.0e-01,1.0e+00), RES(5.3321829058411214108e-1, -7.7308635671950473342e-1)}, {FN (arccsch), ARG(5.0e-01,-1.0e+00), RES(5.3321829058411214108e-1, 7.7308635671950473342e-1)}, {FN (arccsch), ARG(-5.0e-01,1.0e+00), RES(-5.3321829058411214108e-1, -7.7308635671950473342e-1)}, {FN (arccsch), ARG(-5.0e-01,-1.0e+00), RES(-5.3321829058411214108e-1, 7.7308635671950473342e-1)}, {FN (arccsch), ARG(5.0e-01,2.0e+00), RES(1.3261586085051183885e-1, -4.8530734047334251250e-1)}, {FN (arccsch), ARG(5.0e-01,-2.0e+00), RES(1.3261586085051183885e-1, 4.8530734047334251250e-1)}, {FN (arccsch), ARG(-5.0e-01,2.0e+00), RES(-1.3261586085051183885e-1, -4.8530734047334251250e-1)}, {FN (arccsch), ARG(-5.0e-01,-2.0e+00), RES(-1.3261586085051183885e-1, 4.8530734047334251250e-1)}, {FN (arccsch), ARG(5.0e-01,8.3886080e+06), RES(7.1054273576010271023e-15, -1.1920928955078110883e-7)}, {FN (arccsch), ARG(5.0e-01,-8.3886080e+06), RES(7.1054273576010271023e-15, 1.1920928955078110883e-7)}, {FN (arccsch), ARG(-5.0e-01,8.3886080e+06), RES(-7.1054273576010271023e-15, -1.1920928955078110883e-7)}, {FN (arccsch), ARG(-5.0e-01,-8.3886080e+06), RES(-7.1054273576010271023e-15, 1.1920928955078110883e-7)}, {FN (arccsch), ARG(1.0e+00,0.0e+00), RES(8.8137358701954302523e-1, 0.0)}, {FN (arccsch), ARG(-1.0e+00,0.0e+00), RES(-8.8137358701954302523e-1, 0.0)}, {FN (arccsch), ARG(1.0e+00,1.19209289550781250e-07), RES(8.8137358701953548879e-1, -8.4293697021787414719e-8)}, {FN (arccsch), ARG(1.0e+00,-1.19209289550781250e-07), RES(8.8137358701953548879e-1, 8.4293697021787414719e-8)}, {FN (arccsch), ARG(-1.0e+00,1.19209289550781250e-07), RES(-8.8137358701953548879e-1, -8.4293697021787414719e-8)}, {FN (arccsch), ARG(-1.0e+00,-1.19209289550781250e-07), RES(-8.8137358701953548879e-1, 8.4293697021787414719e-8)}, {FN (arccsch), ARG(1.0e+00,5.0e-01), RES(7.6388434595371104541e-1, -3.1122579724476109533e-1)}, {FN (arccsch), ARG(1.0e+00,-5.0e-01), RES(7.6388434595371104541e-1, 3.1122579724476109533e-1)}, {FN (arccsch), ARG(-1.0e+00,5.0e-01), RES(-7.6388434595371104541e-1, -3.1122579724476109533e-1)}, {FN (arccsch), ARG(-1.0e+00,-5.0e-01), RES(-7.6388434595371104541e-1, 3.1122579724476109533e-1)}, {FN (arccsch), ARG(1.0e+00,1.0e+00), RES(5.3063753095251782602e-1, -4.5227844715119068206e-1)}, {FN (arccsch), ARG(1.0e+00,-1.0e+00), RES(5.3063753095251782602e-1, 4.5227844715119068206e-1)}, {FN (arccsch), ARG(-1.0e+00,1.0e+00), RES(-5.3063753095251782602e-1, -4.5227844715119068206e-1)}, {FN (arccsch), ARG(-1.0e+00,-1.0e+00), RES(-5.3063753095251782602e-1, 4.5227844715119068206e-1)}, {FN (arccsch), ARG(1.0e+00,2.0e+00), RES(2.1561241855582964497e-1, -4.0158639166780606828e-1)}, {FN (arccsch), ARG(1.0e+00,-2.0e+00), RES(2.1561241855582964497e-1, 4.0158639166780606828e-1)}, {FN (arccsch), ARG(-1.0e+00,2.0e+00), RES(-2.1561241855582964497e-1, -4.0158639166780606828e-1)}, {FN (arccsch), ARG(-1.0e+00,-2.0e+00), RES(-2.1561241855582964497e-1, 4.0158639166780606828e-1)}, {FN (arccsch), ARG(1.0e+00,8.3886080e+06), RES(1.4210854715201902743e-14, -1.1920928955077983828e-7)}, {FN (arccsch), ARG(1.0e+00,-8.3886080e+06), RES(1.4210854715201902743e-14, 1.1920928955077983828e-7)}, {FN (arccsch), ARG(-1.0e+00,8.3886080e+06), RES(-1.4210854715201902743e-14, -1.1920928955077983828e-7)}, {FN (arccsch), ARG(-1.0e+00,-8.3886080e+06), RES(-1.4210854715201902743e-14, 1.1920928955077983828e-7)}, {FN (arccsch), ARG(2.0e+00,0.0e+00), RES(4.8121182505960344750e-1, 0.0)}, {FN (arccsch), ARG(-2.0e+00,0.0e+00), RES(-4.8121182505960344750e-1, 0.0)}, {FN (arccsch), ARG(2.0e+00,1.19209289550781250e-07), RES(4.8121182505960201756e-1, -2.6656007498500149811e-8)}, {FN (arccsch), ARG(2.0e+00,-1.19209289550781250e-07), RES(4.8121182505960201756e-1, 2.6656007498500149811e-8)}, {FN (arccsch), ARG(-2.0e+00,1.19209289550781250e-07), RES(-4.8121182505960201756e-1, -2.6656007498500149811e-8)}, {FN (arccsch), ARG(-2.0e+00,-1.19209289550781250e-07), RES(-4.8121182505960201756e-1, 2.6656007498500149811e-8)}, {FN (arccsch), ARG(2.0e+00,5.0e-01), RES(4.5717847686917515748e-1, -1.0654050295275703990e-1)}, {FN (arccsch), ARG(2.0e+00,-5.0e-01), RES(4.5717847686917515748e-1, 1.0654050295275703990e-1)}, {FN (arccsch), ARG(-2.0e+00,5.0e-01), RES(-4.5717847686917515748e-1, -1.0654050295275703990e-1)}, {FN (arccsch), ARG(-2.0e+00,-5.0e-01), RES(-4.5717847686917515748e-1, 1.0654050295275703990e-1)}, {FN (arccsch), ARG(2.0e+00,1.0e+00), RES(3.9656823011232897892e-1, -1.8631805410781552582e-1)}, {FN (arccsch), ARG(2.0e+00,-1.0e+00), RES(3.9656823011232897892e-1, 1.8631805410781552582e-1)}, {FN (arccsch), ARG(-2.0e+00,1.0e+00), RES(-3.9656823011232897892e-1, -1.8631805410781552582e-1)}, {FN (arccsch), ARG(-2.0e+00,-1.0e+00), RES(-3.9656823011232897892e-1, 1.8631805410781552582e-1)}, {FN (arccsch), ARG(2.0e+00,2.0e+00), RES(2.5489557334055081773e-1, -2.4452216513554014646e-1)}, {FN (arccsch), ARG(2.0e+00,-2.0e+00), RES(2.5489557334055081773e-1, 2.4452216513554014646e-1)}, {FN (arccsch), ARG(-2.0e+00,2.0e+00), RES(-2.5489557334055081773e-1, -2.4452216513554014646e-1)}, {FN (arccsch), ARG(-2.0e+00,-2.0e+00), RES(-2.5489557334055081773e-1, 2.4452216513554014646e-1)}, {FN (arccsch), ARG(2.0e+00,8.3886080e+06), RES(2.8421709430402593796e-14, -1.1920928955077475608e-7)}, {FN (arccsch), ARG(2.0e+00,-8.3886080e+06), RES(2.8421709430402593796e-14, 1.1920928955077475608e-7)}, {FN (arccsch), ARG(-2.0e+00,8.3886080e+06), RES(-2.8421709430402593796e-14, -1.1920928955077475608e-7)}, {FN (arccsch), ARG(-2.0e+00,-8.3886080e+06), RES(-2.8421709430402593796e-14, 1.1920928955077475608e-7)}, {FN (arccsch), ARG(8.3886080e+06,0.0e+00), RES(1.1920928955078096766e-7, 0.0)}, {FN (arccsch), ARG(-8.3886080e+06,0.0e+00), RES(-1.1920928955078096766e-7, 0.0)}, {FN (arccsch), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.1920928955078096766e-7, -1.6940658945085886411e-21)}, {FN (arccsch), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.1920928955078096766e-7, 1.6940658945085886411e-21)}, {FN (arccsch), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(-1.1920928955078096766e-7, -1.6940658945085886411e-21)}, {FN (arccsch), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(-1.1920928955078096766e-7, 1.6940658945085886411e-21)}, {FN (arccsch), ARG(8.3886080e+06,5.0e-01), RES(1.1920928955078054414e-7, -7.1054273576009261281e-15)}, {FN (arccsch), ARG(8.3886080e+06,-5.0e-01), RES(1.1920928955078054414e-7, 7.1054273576009261281e-15)}, {FN (arccsch), ARG(-8.3886080e+06,5.0e-01), RES(-1.1920928955078054414e-7, -7.1054273576009261281e-15)}, {FN (arccsch), ARG(-8.3886080e+06,-5.0e-01), RES(-1.1920928955078054414e-7, 7.1054273576009261281e-15)}, {FN (arccsch), ARG(8.3886080e+06,1.0e+00), RES(1.1920928955077927359e-7, -1.4210854715201700795e-14)}, {FN (arccsch), ARG(8.3886080e+06,-1.0e+00), RES(1.1920928955077927359e-7, 1.4210854715201700795e-14)}, {FN (arccsch), ARG(-8.3886080e+06,1.0e+00), RES(-1.1920928955077927359e-7, -1.4210854715201700795e-14)}, {FN (arccsch), ARG(-8.3886080e+06,-1.0e+00), RES(-1.1920928955077927359e-7, 1.4210854715201700795e-14)}, {FN (arccsch), ARG(8.3886080e+06,2.0e+00), RES(1.1920928955077419139e-7, -2.8421709430402189899e-14)}, {FN (arccsch), ARG(8.3886080e+06,-2.0e+00), RES(1.1920928955077419139e-7, 2.8421709430402189899e-14)}, {FN (arccsch), ARG(-8.3886080e+06,2.0e+00), RES(-1.1920928955077419139e-7, -2.8421709430402189899e-14)}, {FN (arccsch), ARG(-8.3886080e+06,-2.0e+00), RES(-1.1920928955077419139e-7, 2.8421709430402189899e-14)}, {FN (arccsch), ARG(8.3886080e+06,8.3886080e+06), RES(5.9604644775390695586e-8, -5.9604644775390554414e-8)}, {FN (arccsch), ARG(8.3886080e+06,-8.3886080e+06), RES(5.9604644775390695586e-8, 5.9604644775390554414e-8)}, {FN (arccsch), ARG(-8.3886080e+06,8.3886080e+06), RES(-5.9604644775390695586e-8, -5.9604644775390554414e-8)}, {FN (arccsch), ARG(-8.3886080e+06,-8.3886080e+06), RES(-5.9604644775390695586e-8, 5.9604644775390554414e-8)}, {FN (arcsech), ARG(0.0e+00,1.19209289550781250e-07), RES(1.6635532333438690979e1, -1.5707963267948966192e0)}, {FN (arcsech), ARG(0.0e+00,-1.19209289550781250e-07), RES(1.6635532333438690979e1, 1.5707963267948966192e0)}, {FN (arcsech), ARG(0.0e+00,5.0e-01), RES(1.4436354751788103425e0, -1.5707963267948966192e0)}, {FN (arcsech), ARG(0.0e+00,-5.0e-01), RES(1.4436354751788103425e0, 1.5707963267948966192e0)}, {FN (arcsech), ARG(0.0e+00,1.0e+00), RES(8.8137358701954302523e-1, -1.5707963267948966192e0)}, {FN (arcsech), ARG(0.0e+00,-1.0e+00), RES(8.8137358701954302523e-1, 1.5707963267948966192e0)}, {FN (arcsech), ARG(0.0e+00,2.0e+00), RES(4.8121182505960344750e-1, -1.5707963267948966192e0)}, {FN (arcsech), ARG(0.0e+00,-2.0e+00), RES(4.8121182505960344750e-1, 1.5707963267948966192e0)}, {FN (arcsech), ARG(0.0e+00,8.3886080e+06), RES(1.1920928955078096766e-7, -1.5707963267948966192e0)}, {FN (arcsech), ARG(0.0e+00,-8.3886080e+06), RES(1.1920928955078096766e-7, 1.5707963267948966192e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,0.0e+00), RES(1.6635532333438683873e1, 0.0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,0.0e+00), RES(1.6635532333438683873e1, 3.1415926535897932385e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.6288958743158714771e1, -7.8539816339745541504e-1)}, {FN (arcsech), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.6288958743158714771e1, 7.8539816339745541504e-1)}, {FN (arcsech), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(1.6288958743158714771e1, -2.3561944901923378234e0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.6288958743158714771e1, 2.3561944901923378234e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,5.0e-01), RES(1.4436354751787798371e0, -1.5707961135468366312e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,-5.0e-01), RES(1.4436354751787798371e0, 1.5707961135468366312e0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,5.0e-01), RES(1.4436354751787798371e0, -1.5707965400429566072e0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,-5.0e-01), RES(1.4436354751787798371e0, 1.5707965400429566072e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,1.0e+00), RES(8.8137358701953548879e-1, -1.5707962425011995974e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,-1.0e+00), RES(8.8137358701953548879e-1, 1.5707962425011995974e0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,1.0e+00), RES(8.8137358701953548879e-1, -1.5707964110885936410e0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,-1.0e+00), RES(8.8137358701953548879e-1, 1.5707964110885936410e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,2.0e+00), RES(4.8121182505960201756e-1, -1.5707963001388891207e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,-2.0e+00), RES(4.8121182505960201756e-1, 1.5707963001388891207e0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,2.0e+00), RES(4.8121182505960201756e-1, -1.5707963534509041177e0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,-2.0e+00), RES(4.8121182505960201756e-1, 1.5707963534509041177e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.1920928955078096766e-7, -1.5707963267948966192e0)}, {FN (arcsech), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.1920928955078096766e-7, 1.5707963267948966192e0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(1.1920928955078096766e-7, -1.5707963267948966192e0)}, {FN (arcsech), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(1.1920928955078096766e-7, 1.5707963267948966192e0)}, {FN (arcsech), ARG(5.0e-01,0.0e+00), RES(1.3169578969248167086e0, 0.0)}, {FN (arcsech), ARG(-5.0e-01,0.0e+00), RES(1.3169578969248167086e0, 3.1415926535897932385e0)}, {FN (arcsech), ARG(5.0e-01,1.19209289550781250e-07), RES(1.3169578969247948296e0, -2.7530206164818516969e-7)}, {FN (arcsech), ARG(5.0e-01,-1.19209289550781250e-07), RES(1.3169578969247948296e0, 2.7530206164818516969e-7)}, {FN (arcsech), ARG(-5.0e-01,1.19209289550781250e-07), RES(1.3169578969247948296e0, -3.1415923782877315903e0)}, {FN (arcsech), ARG(-5.0e-01,-1.19209289550781250e-07), RES(1.3169578969247948296e0, 3.1415923782877315903e0)}, {FN (arcsech), ARG(5.0e-01,5.0e-01), RES(1.0612750619050356520e0, -9.0455689430238136413e-1)}, {FN (arcsech), ARG(5.0e-01,-5.0e-01), RES(1.0612750619050356520e0, 9.0455689430238136413e-1)}, {FN (arcsech), ARG(-5.0e-01,5.0e-01), RES(1.0612750619050356520e0, -2.2370357592874118743e0)}, {FN (arcsech), ARG(-5.0e-01,-5.0e-01), RES(1.0612750619050356520e0, 2.2370357592874118743e0)}, {FN (arcsech), ARG(5.0e-01,1.0e+00), RES(7.6388434595371104541e-1, -1.2595705295501355239e0)}, {FN (arcsech), ARG(5.0e-01,-1.0e+00), RES(7.6388434595371104541e-1, 1.2595705295501355239e0)}, {FN (arcsech), ARG(-5.0e-01,1.0e+00), RES(7.6388434595371104541e-1, -1.8820221240396577146e0)}, {FN (arcsech), ARG(-5.0e-01,-1.0e+00), RES(7.6388434595371104541e-1, 1.8820221240396577146e0)}, {FN (arcsech), ARG(5.0e-01,2.0e+00), RES(4.5717847686917515748e-1, -1.4642558238421395793e0)}, {FN (arcsech), ARG(5.0e-01,-2.0e+00), RES(4.5717847686917515748e-1, 1.4642558238421395793e0)}, {FN (arcsech), ARG(-5.0e-01,2.0e+00), RES(4.5717847686917515748e-1, -1.6773368297476536591e0)}, {FN (arcsech), ARG(-5.0e-01,-2.0e+00), RES(4.5717847686917515748e-1, 1.6773368297476536591e0)}, {FN (arcsech), ARG(5.0e-01,8.3886080e+06), RES(1.1920928955078054414e-7, -1.5707963267948895138e0)}, {FN (arcsech), ARG(5.0e-01,-8.3886080e+06), RES(1.1920928955078054414e-7, 1.5707963267948895138e0)}, {FN (arcsech), ARG(-5.0e-01,8.3886080e+06), RES(1.1920928955078054414e-7, -1.5707963267949037247e0)}, {FN (arcsech), ARG(-5.0e-01,-8.3886080e+06), RES(1.1920928955078054414e-7, 1.5707963267949037247e0)}, {FN (arcsech), ARG(1.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arcsech), ARG(-1.0e+00,0.0e+00), RES(0, 3.1415926535897932385e0)}, {FN (arcsech), ARG(1.0e+00,1.19209289550781250e-07), RES(3.4526696585164602772e-4, -3.4526700015083915182e-4)}, {FN (arcsech), ARG(1.0e+00,-1.19209289550781250e-07), RES(3.4526696585164602772e-4, 3.4526700015083915182e-4)}, {FN (arcsech), ARG(-1.0e+00,1.19209289550781250e-07), RES(3.4526696585164602772e-4, -3.1412473865896423993e0)}, {FN (arcsech), ARG(-1.0e+00,-1.19209289550781250e-07), RES(3.4526696585164602772e-4, 3.1412473865896423993e0)}, {FN (arcsech), ARG(1.0e+00,5.0e-01), RES(5.3321829058411214108e-1, -7.9770997007539188581e-1)}, {FN (arcsech), ARG(1.0e+00,-5.0e-01), RES(5.3321829058411214108e-1, 7.9770997007539188581e-1)}, {FN (arcsech), ARG(-1.0e+00,5.0e-01), RES(5.3321829058411214108e-1, -2.3438826835144013527e0)}, {FN (arcsech), ARG(-1.0e+00,-5.0e-01), RES(5.3321829058411214108e-1, 2.3438826835144013527e0)}, {FN (arcsech), ARG(1.0e+00,1.0e+00), RES(5.3063753095251782602e-1, -1.1185178796437059372e0)}, {FN (arcsech), ARG(1.0e+00,-1.0e+00), RES(5.3063753095251782602e-1, 1.1185178796437059372e0)}, {FN (arcsech), ARG(-1.0e+00,1.0e+00), RES(5.3063753095251782602e-1, -2.0230747739460873013e0)}, {FN (arcsech), ARG(-1.0e+00,-1.0e+00), RES(5.3063753095251782602e-1, 2.0230747739460873013e0)}, {FN (arcsech), ARG(1.0e+00,2.0e+00), RES(3.9656823011232897892e-1, -1.3844782726870810934e0)}, {FN (arcsech), ARG(1.0e+00,-2.0e+00), RES(3.9656823011232897892e-1, 1.3844782726870810934e0)}, {FN (arcsech), ARG(-1.0e+00,2.0e+00), RES(3.9656823011232897892e-1, -1.7571143809027121451e0)}, {FN (arcsech), ARG(-1.0e+00,-2.0e+00), RES(3.9656823011232897892e-1, 1.7571143809027121451e0)}, {FN (arcsech), ARG(1.0e+00,8.3886080e+06), RES(1.1920928955077927359e-7, -1.5707963267948824084e0)}, {FN (arcsech), ARG(1.0e+00,-8.3886080e+06), RES(1.1920928955077927359e-7, 1.5707963267948824084e0)}, {FN (arcsech), ARG(-1.0e+00,8.3886080e+06), RES(1.1920928955077927359e-7, -1.5707963267949108301e0)}, {FN (arcsech), ARG(-1.0e+00,-8.3886080e+06), RES(1.1920928955077927359e-7, 1.5707963267949108301e0)}, {FN (arcsech), ARG(2.0e+00,0.0e+00), RES(0, 1.0471975511965977462e0)}, {FN (arcsech), ARG(-2.0e+00,0.0e+00), RES(0, 2.0943951023931954923e0)}, {FN (arcsech), ARG(2.0e+00,1.19209289550781250e-07), RES(3.4412757706023621662e-8, -1.0471975511966001392e0)}, {FN (arcsech), ARG(2.0e+00,-1.19209289550781250e-07), RES(3.4412757706023621662e-8, 1.0471975511966001392e0)}, {FN (arcsech), ARG(-2.0e+00,1.19209289550781250e-07), RES(3.4412757706023621662e-8, -2.0943951023931930993e0)}, {FN (arcsech), ARG(-2.0e+00,-1.19209289550781250e-07), RES(3.4412757706023621662e-8, 2.0943951023931930993e0)}, {FN (arcsech), ARG(2.0e+00,5.0e-01), RES(1.3261586085051183885e-1, -1.0854889863215541067e0)}, {FN (arcsech), ARG(2.0e+00,-5.0e-01), RES(1.3261586085051183885e-1, 1.0854889863215541067e0)}, {FN (arcsech), ARG(-2.0e+00,5.0e-01), RES(1.3261586085051183885e-1, -2.0561036672682391317e0)}, {FN (arcsech), ARG(-2.0e+00,-5.0e-01), RES(1.3261586085051183885e-1, 2.0561036672682391317e0)}, {FN (arcsech), ARG(2.0e+00,1.0e+00), RES(2.1561241855582964497e-1, -1.1692099351270905509e0)}, {FN (arcsech), ARG(2.0e+00,-1.0e+00), RES(2.1561241855582964497e-1, 1.1692099351270905509e0)}, {FN (arcsech), ARG(-2.0e+00,1.0e+00), RES(2.1561241855582964497e-1, -1.9723827184627026875e0)}, {FN (arcsech), ARG(-2.0e+00,-1.0e+00), RES(2.1561241855582964497e-1, 1.9723827184627026875e0)}, {FN (arcsech), ARG(2.0e+00,2.0e+00), RES(2.5489557334055081773e-1, -1.3262741616593564728e0)}, {FN (arcsech), ARG(2.0e+00,-2.0e+00), RES(2.5489557334055081773e-1, 1.3262741616593564728e0)}, {FN (arcsech), ARG(-2.0e+00,2.0e+00), RES(2.5489557334055081773e-1, -1.8153184919304367657e0)}, {FN (arcsech), ARG(-2.0e+00,-2.0e+00), RES(2.5489557334055081773e-1, 1.8153184919304367657e0)}, {FN (arcsech), ARG(2.0e+00,8.3886080e+06), RES(1.1920928955077419139e-7, -1.5707963267948681975e0)}, {FN (arcsech), ARG(2.0e+00,-8.3886080e+06), RES(1.1920928955077419139e-7, 1.5707963267948681975e0)}, {FN (arcsech), ARG(-2.0e+00,8.3886080e+06), RES(1.1920928955077419139e-7, -1.5707963267949250409e0)}, {FN (arcsech), ARG(-2.0e+00,-8.3886080e+06), RES(1.1920928955077419139e-7, 1.5707963267949250409e0)}, {FN (arcsech), ARG(8.3886080e+06,0.0e+00), RES(0, 1.5707962075856070684e0)}, {FN (arcsech), ARG(-8.3886080e+06,0.0e+00), RES(0, 1.570796446004186170e0)}, {FN (arcsech), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.6940658945086127152e-21, -1.5707962075856070684e0)}, {FN (arcsech), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.6940658945086127152e-21, 1.5707962075856070684e0)}, {FN (arcsech), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(1.6940658945086127152e-21, -1.570796446004186170e0)}, {FN (arcsech), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(1.6940658945086127152e-21, 1.570796446004186170e0)}, {FN (arcsech), ARG(8.3886080e+06,5.0e-01), RES(7.1054273576010271023e-15, -1.5707962075856070685e0)}, {FN (arcsech), ARG(8.3886080e+06,-5.0e-01), RES(7.1054273576010271023e-15, 1.5707962075856070685e0)}, {FN (arcsech), ARG(-8.3886080e+06,5.0e-01), RES(7.1054273576010271023e-15, -1.570796446004186170e0)}, {FN (arcsech), ARG(-8.3886080e+06,-5.0e-01), RES(7.1054273576010271023e-15, 1.570796446004186170e0)}, {FN (arcsech), ARG(8.3886080e+06,1.0e+00), RES(1.4210854715201902743e-14, -1.5707962075856070685e0)}, {FN (arcsech), ARG(8.3886080e+06,-1.0e+00), RES(1.4210854715201902743e-14, 1.5707962075856070685e0)}, {FN (arcsech), ARG(-8.3886080e+06,1.0e+00), RES(1.4210854715201902743e-14, -1.570796446004186170e0)}, {FN (arcsech), ARG(-8.3886080e+06,-1.0e+00), RES(1.4210854715201902743e-14, 1.570796446004186170e0)}, {FN (arcsech), ARG(8.3886080e+06,2.0e+00), RES(2.8421709430402593796e-14, -1.5707962075856070685e0)}, {FN (arcsech), ARG(8.3886080e+06,-2.0e+00), RES(2.8421709430402593796e-14, 1.5707962075856070685e0)}, {FN (arcsech), ARG(-8.3886080e+06,2.0e+00), RES(2.8421709430402593796e-14, -1.570796446004186170e0)}, {FN (arcsech), ARG(-8.3886080e+06,-2.0e+00), RES(2.8421709430402593796e-14, 1.570796446004186170e0)}, {FN (arcsech), ARG(8.3886080e+06,8.3886080e+06), RES(5.9604644775390695586e-8, -1.5707962671902518438e0)}, {FN (arcsech), ARG(8.3886080e+06,-8.3886080e+06), RES(5.9604644775390695586e-8, 1.5707962671902518438e0)}, {FN (arcsech), ARG(-8.3886080e+06,8.3886080e+06), RES(5.9604644775390695586e-8, -1.5707963863995413946e0)}, {FN (arcsech), ARG(-8.3886080e+06,-8.3886080e+06), RES(5.9604644775390695586e-8, 1.5707963863995413946e0)}, {FN (arccoth), ARG(0.0e+00,1.19209289550781250e-07), RES(0, -1.5707962075856070685e0)}, {FN (arccoth), ARG(0.0e+00,-1.19209289550781250e-07), RES(0, 1.5707962075856070685e0)}, {FN (arccoth), ARG(0.0e+00,5.0e-01), RES(0, -1.1071487177940905030e0)}, {FN (arccoth), ARG(0.0e+00,-5.0e-01), RES(0, 1.1071487177940905030e0)}, {FN (arccoth), ARG(0.0e+00,1.0e+00), RES(0, -7.8539816339744830962e-1)}, {FN (arccoth), ARG(0.0e+00,-1.0e+00), RES(0, 7.8539816339744830962e-1)}, {FN (arccoth), ARG(0.0e+00,2.0e+00), RES(0, -4.6364760900080611621e-1)}, {FN (arccoth), ARG(0.0e+00,-2.0e+00), RES(0, 4.6364760900080611621e-1)}, {FN (arccoth), ARG(0.0e+00,8.3886080e+06), RES(0, -1.1920928955078068531e-7)}, {FN (arccoth), ARG(0.0e+00,-8.3886080e+06), RES(0, 1.1920928955078068531e-7)}, {FN (arccoth), ARG(1.19209289550781250e-07,0.0e+00), RES(1.1920928955078181469e-7, -1.5707963267948966192e0)}, {FN (arccoth), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.1920928955078181469e-7, 1.5707963267948966192e0)}, {FN (arccoth), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.1920928955078012062e-7, -1.5707962075856070684e0)}, {FN (arccoth), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.1920928955078012062e-7, 1.5707962075856070684e0)}, {FN (arccoth), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.1920928955078012062e-7, -1.5707962075856070684e0)}, {FN (arccoth), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.1920928955078012062e-7, 1.5707962075856070684e0)}, {FN (arccoth), ARG(1.19209289550781250e-07,5.0e-01), RES(9.5367431640625072280e-8, -1.1071487177940859555e0)}, {FN (arccoth), ARG(1.19209289550781250e-07,-5.0e-01), RES(9.5367431640625072280e-8, 1.1071487177940859555e0)}, {FN (arccoth), ARG(-1.19209289550781250e-07,5.0e-01), RES(-9.5367431640625072280e-8, -1.1071487177940859555e0)}, {FN (arccoth), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-9.5367431640625072280e-8, 1.1071487177940859555e0)}, {FN (arccoth), ARG(1.19209289550781250e-07,1.0e+00), RES(5.9604644775390483828e-8, -7.8539816339744475690e-1)}, {FN (arccoth), ARG(1.19209289550781250e-07,-1.0e+00), RES(5.9604644775390483828e-8, 7.8539816339744475690e-1)}, {FN (arccoth), ARG(-1.19209289550781250e-07,1.0e+00), RES(-5.9604644775390483828e-8, -7.8539816339744475690e-1)}, {FN (arccoth), ARG(-1.19209289550781250e-07,-1.0e+00), RES(-5.9604644775390483828e-8, 7.8539816339744475690e-1)}, {FN (arccoth), ARG(1.19209289550781250e-07,2.0e+00), RES(2.3841857910156200307e-8, -4.6364760900080497935e-1)}, {FN (arccoth), ARG(1.19209289550781250e-07,-2.0e+00), RES(2.3841857910156200307e-8, 4.6364760900080497935e-1)}, {FN (arccoth), ARG(-1.19209289550781250e-07,2.0e+00), RES(-2.3841857910156200307e-8, -4.6364760900080497935e-1)}, {FN (arccoth), ARG(-1.19209289550781250e-07,-2.0e+00), RES(-2.3841857910156200307e-8, 4.6364760900080497935e-1)}, {FN (arccoth), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.6940658945085766040e-21, -1.1920928955078068531e-7)}, {FN (arccoth), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.6940658945085766040e-21, 1.1920928955078068531e-7)}, {FN (arccoth), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(-1.6940658945085766040e-21, -1.1920928955078068531e-7)}, {FN (arccoth), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(-1.6940658945085766040e-21, 1.1920928955078068531e-7)}, {FN (arccoth), ARG(5.0e-01,0.0e+00), RES(5.4930614433405484570e-1, -1.5707963267948966192e0)}, {FN (arccoth), ARG(-5.0e-01,0.0e+00), RES(-5.4930614433405484570e-1, 1.5707963267948966192e0)}, {FN (arccoth), ARG(5.0e-01,1.19209289550781250e-07), RES(5.4930614433404221383e-1, -1.5707961678491772182e0)}, {FN (arccoth), ARG(5.0e-01,-1.19209289550781250e-07), RES(5.4930614433404221383e-1, 1.5707961678491772182e0)}, {FN (arccoth), ARG(-5.0e-01,1.19209289550781250e-07), RES(-5.4930614433404221383e-1, -1.5707961678491772182e0)}, {FN (arccoth), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-5.4930614433404221383e-1, 1.5707961678491772182e0)}, {FN (arccoth), ARG(5.0e-01,5.0e-01), RES(4.0235947810852509365e-1, -1.0172219678978513677e0)}, {FN (arccoth), ARG(5.0e-01,-5.0e-01), RES(4.0235947810852509365e-1, 1.0172219678978513677e0)}, {FN (arccoth), ARG(-5.0e-01,5.0e-01), RES(-4.0235947810852509365e-1, -1.0172219678978513677e0)}, {FN (arccoth), ARG(-5.0e-01,-5.0e-01), RES(-4.0235947810852509365e-1, 1.0172219678978513677e0)}, {FN (arccoth), ARG(5.0e-01,1.0e+00), RES(2.3887786125685909036e-1, -7.2322066612406759210e-1)}, {FN (arccoth), ARG(5.0e-01,-1.0e+00), RES(2.3887786125685909036e-1, 7.2322066612406759210e-1)}, {FN (arccoth), ARG(-5.0e-01,1.0e+00), RES(-2.3887786125685909036e-1, -7.2322066612406759210e-1)}, {FN (arccoth), ARG(-5.0e-01,-1.0e+00), RES(-2.3887786125685909036e-1, 7.2322066612406759210e-1)}, {FN (arccoth), ARG(5.0e-01,2.0e+00), RES(9.6415620202996167238e-2, -4.4423988596007427049e-1)}, {FN (arccoth), ARG(5.0e-01,-2.0e+00), RES(9.6415620202996167238e-2, 4.4423988596007427049e-1)}, {FN (arccoth), ARG(-5.0e-01,2.0e+00), RES(-9.6415620202996167238e-2, -4.4423988596007427049e-1)}, {FN (arccoth), ARG(-5.0e-01,-2.0e+00), RES(-9.6415620202996167238e-2, 4.4423988596007427049e-1)}, {FN (arccoth), ARG(5.0e-01,8.3886080e+06), RES(7.1054273576008756410e-15, -1.1920928955078026179e-7)}, {FN (arccoth), ARG(5.0e-01,-8.3886080e+06), RES(7.1054273576008756410e-15, 1.1920928955078026179e-7)}, {FN (arccoth), ARG(-5.0e-01,8.3886080e+06), RES(-7.1054273576008756410e-15, -1.1920928955078026179e-7)}, {FN (arccoth), ARG(-5.0e-01,-8.3886080e+06), RES(-7.1054273576008756410e-15, 1.1920928955078026179e-7)}, {FN (arccoth), ARG(1.0e+00,1.19209289550781250e-07), RES(8.3177661667193446012e0, -7.8539813359512592192e-1)}, {FN (arccoth), ARG(1.0e+00,-1.19209289550781250e-07), RES(8.3177661667193446012e0, 7.8539813359512592192e-1)}, {FN (arccoth), ARG(-1.0e+00,1.19209289550781250e-07), RES(-8.3177661667193446012e0, -7.8539813359512592192e-1)}, {FN (arccoth), ARG(-1.0e+00,-1.19209289550781250e-07), RES(-8.3177661667193446012e0, 7.8539813359512592192e-1)}, {FN (arccoth), ARG(1.0e+00,5.0e-01), RES(7.0830333601405402006e-1, -6.6290883183401623253e-1)}, {FN (arccoth), ARG(1.0e+00,-5.0e-01), RES(7.0830333601405402006e-1, 6.6290883183401623253e-1)}, {FN (arccoth), ARG(-1.0e+00,5.0e-01), RES(-7.0830333601405402006e-1, -6.6290883183401623253e-1)}, {FN (arccoth), ARG(-1.0e+00,-5.0e-01), RES(-7.0830333601405402006e-1, 6.6290883183401623253e-1)}, {FN (arccoth), ARG(1.0e+00,1.0e+00), RES(4.0235947810852509365e-1, -5.5357435889704525151e-1)}, {FN (arccoth), ARG(1.0e+00,-1.0e+00), RES(4.0235947810852509365e-1, 5.5357435889704525151e-1)}, {FN (arccoth), ARG(-1.0e+00,1.0e+00), RES(-4.0235947810852509365e-1, -5.5357435889704525151e-1)}, {FN (arccoth), ARG(-1.0e+00,-1.0e+00), RES(-4.0235947810852509365e-1, 5.5357435889704525151e-1)}, {FN (arccoth), ARG(1.0e+00,2.0e+00), RES(1.7328679513998632735e-1, -3.9269908169872415481e-1)}, {FN (arccoth), ARG(1.0e+00,-2.0e+00), RES(1.7328679513998632735e-1, 3.9269908169872415481e-1)}, {FN (arccoth), ARG(-1.0e+00,2.0e+00), RES(-1.7328679513998632735e-1, -3.9269908169872415481e-1)}, {FN (arccoth), ARG(-1.0e+00,-2.0e+00), RES(-1.7328679513998632735e-1, 3.9269908169872415481e-1)}, {FN (arccoth), ARG(1.0e+00,8.3886080e+06), RES(1.4210854715201599821e-14, -1.1920928955077899125e-7)}, {FN (arccoth), ARG(1.0e+00,-8.3886080e+06), RES(1.4210854715201599821e-14, 1.1920928955077899125e-7)}, {FN (arccoth), ARG(-1.0e+00,8.3886080e+06), RES(-1.4210854715201599821e-14, -1.1920928955077899125e-7)}, {FN (arccoth), ARG(-1.0e+00,-8.3886080e+06), RES(-1.4210854715201599821e-14, 1.1920928955077899125e-7)}, {FN (arccoth), ARG(2.0e+00,0.0e+00), RES(5.4930614433405484570e-1, 0.0)}, {FN (arccoth), ARG(-2.0e+00,0.0e+00), RES(-5.4930614433405484570e-1, 0.0)}, {FN (arccoth), ARG(2.0e+00,1.19209289550781250e-07), RES(5.4930614433405168773e-1, -3.9736429850260144780e-8)}, {FN (arccoth), ARG(2.0e+00,-1.19209289550781250e-07), RES(5.4930614433405168773e-1, 3.9736429850260144780e-8)}, {FN (arccoth), ARG(-2.0e+00,1.19209289550781250e-07), RES(-5.4930614433405168773e-1, -3.9736429850260144780e-8)}, {FN (arccoth), ARG(-2.0e+00,-1.19209289550781250e-07), RES(-5.4930614433405168773e-1, 3.9736429850260144780e-8)}, {FN (arccoth), ARG(2.0e+00,5.0e-01), RES(5.0037000005253101744e-1, -1.4924946579308963897e-1)}, {FN (arccoth), ARG(2.0e+00,-5.0e-01), RES(5.0037000005253101744e-1, 1.4924946579308963897e-1)}, {FN (arccoth), ARG(-2.0e+00,5.0e-01), RES(-5.0037000005253101744e-1, -1.4924946579308963897e-1)}, {FN (arccoth), ARG(-2.0e+00,-5.0e-01), RES(-5.0037000005253101744e-1, 1.4924946579308963897e-1)}, {FN (arccoth), ARG(2.0e+00,1.0e+00), RES(4.0235947810852509365e-1, -2.3182380450040305811e-1)}, {FN (arccoth), ARG(2.0e+00,-1.0e+00), RES(4.0235947810852509365e-1, 2.3182380450040305811e-1)}, {FN (arccoth), ARG(-2.0e+00,1.0e+00), RES(-4.0235947810852509365e-1, -2.3182380450040305811e-1)}, {FN (arccoth), ARG(-2.0e+00,-1.0e+00), RES(-4.0235947810852509365e-1, 2.3182380450040305811e-1)}, {FN (arccoth), ARG(2.0e+00,2.0e+00), RES(2.3887786125685909036e-1, -2.5957305712326147589e-1)}, {FN (arccoth), ARG(2.0e+00,-2.0e+00), RES(2.3887786125685909036e-1, 2.5957305712326147589e-1)}, {FN (arccoth), ARG(-2.0e+00,2.0e+00), RES(-2.3887786125685909036e-1, -2.5957305712326147589e-1)}, {FN (arccoth), ARG(-2.0e+00,-2.0e+00), RES(-2.3887786125685909036e-1, 2.5957305712326147589e-1)}, {FN (arccoth), ARG(2.0e+00,8.3886080e+06), RES(2.8421709430401987951e-14, -1.1920928955077390905e-7)}, {FN (arccoth), ARG(2.0e+00,-8.3886080e+06), RES(2.8421709430401987951e-14, 1.1920928955077390905e-7)}, {FN (arccoth), ARG(-2.0e+00,8.3886080e+06), RES(-2.8421709430401987951e-14, -1.1920928955077390905e-7)}, {FN (arccoth), ARG(-2.0e+00,-8.3886080e+06), RES(-2.8421709430401987951e-14, 1.1920928955077390905e-7)}, {FN (arccoth), ARG(8.3886080e+06,0.0e+00), RES(1.1920928955078181469e-7, 0.0)}, {FN (arccoth), ARG(-8.3886080e+06,0.0e+00), RES(-1.1920928955078181469e-7, 0.0)}, {FN (arccoth), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.1920928955078181469e-7, -1.6940658945086247523e-21)}, {FN (arccoth), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.1920928955078181469e-7, 1.6940658945086247523e-21)}, {FN (arccoth), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(-1.1920928955078181469e-7, -1.6940658945086247523e-21)}, {FN (arccoth), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(-1.1920928955078181469e-7, 1.6940658945086247523e-21)}, {FN (arccoth), ARG(8.3886080e+06,5.0e-01), RES(1.1920928955078139117e-7, -7.1054273576010775894e-15)}, {FN (arccoth), ARG(8.3886080e+06,-5.0e-01), RES(1.1920928955078139117e-7, 7.1054273576010775894e-15)}, {FN (arccoth), ARG(-8.3886080e+06,5.0e-01), RES(-1.1920928955078139117e-7, -7.1054273576010775894e-15)}, {FN (arccoth), ARG(-8.3886080e+06,-5.0e-01), RES(-1.1920928955078139117e-7, 7.1054273576010775894e-15)}, {FN (arccoth), ARG(8.3886080e+06,1.0e+00), RES(1.1920928955078012062e-7, -1.4210854715202003717e-14)}, {FN (arccoth), ARG(8.3886080e+06,-1.0e+00), RES(1.1920928955078012062e-7, 1.4210854715202003717e-14)}, {FN (arccoth), ARG(-8.3886080e+06,1.0e+00), RES(-1.1920928955078012062e-7, -1.4210854715202003717e-14)}, {FN (arccoth), ARG(-8.3886080e+06,-1.0e+00), RES(-1.1920928955078012062e-7, 1.4210854715202003717e-14)}, {FN (arccoth), ARG(8.3886080e+06,2.0e+00), RES(1.1920928955077503843e-7, -2.8421709430402795744e-14)}, {FN (arccoth), ARG(8.3886080e+06,-2.0e+00), RES(1.1920928955077503843e-7, 2.8421709430402795744e-14)}, {FN (arccoth), ARG(-8.3886080e+06,2.0e+00), RES(-1.1920928955077503843e-7, -2.8421709430402795744e-14)}, {FN (arccoth), ARG(-8.3886080e+06,-2.0e+00), RES(-1.1920928955077503843e-7, 2.8421709430402795744e-14)}, {FN (arccoth), ARG(8.3886080e+06,8.3886080e+06), RES(5.9604644775390483828e-8, -5.9604644775390766172e-8)}, {FN (arccoth), ARG(8.3886080e+06,-8.3886080e+06), RES(5.9604644775390483828e-8, 5.9604644775390766172e-8)}, {FN (arccoth), ARG(-8.3886080e+06,8.3886080e+06), RES(-5.9604644775390483828e-8, -5.9604644775390766172e-8)}, {FN (arccoth), ARG(-8.3886080e+06,-8.3886080e+06), RES(-5.9604644775390483828e-8, 5.9604644775390766172e-8)}, sources_5316/external/gsl/gsl_specfunc__zeta.c0000664000176700017670000010102111723710247020334 0ustar paulpaul/* specfunc/zeta.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_elementary.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_zeta.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" #define LogTwoPi_ 1.8378770664093454835606594728111235279723 /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* chebyshev fit for (s(t)-1)Zeta[s(t)] * s(t)= (t+1)/2 * -1 <= t <= 1 */ static double zeta_xlt1_data[14] = { 1.48018677156931561235192914649, 0.25012062539889426471999938167, 0.00991137502135360774243761467, -0.00012084759656676410329833091, -4.7585866367662556504652535281e-06, 2.2229946694466391855561441361e-07, -2.2237496498030257121309056582e-09, -1.0173226513229028319420799028e-10, 4.3756643450424558284466248449e-12, -6.2229632593100551465504090814e-14, -6.6116201003272207115277520305e-16, 4.9477279533373912324518463830e-17, -1.0429819093456189719660003522e-18, 6.9925216166580021051464412040e-21, }; static cheb_series zeta_xlt1_cs = { zeta_xlt1_data, 13, -1, 1, 8 }; /* chebyshev fit for (s(t)-1)Zeta[s(t)] * s(t)= (19t+21)/2 * -1 <= t <= 1 */ static double zeta_xgt1_data[30] = { 19.3918515726724119415911269006, 9.1525329692510756181581271500, 0.2427897658867379985365270155, -0.1339000688262027338316641329, 0.0577827064065028595578410202, -0.0187625983754002298566409700, 0.0039403014258320354840823803, -0.0000581508273158127963598882, -0.0003756148907214820704594549, 0.0001892530548109214349092999, -0.0000549032199695513496115090, 8.7086484008939038610413331863e-6, 6.4609477924811889068410083425e-7, -9.6749773915059089205835337136e-7, 3.6585400766767257736982342461e-7, -8.4592516427275164351876072573e-8, 9.9956786144497936572288988883e-9, 1.4260036420951118112457144842e-9, -1.1761968823382879195380320948e-9, 3.7114575899785204664648987295e-10, -7.4756855194210961661210215325e-11, 7.8536934209183700456512982968e-12, 9.9827182259685539619810406271e-13, -7.5276687030192221587850302453e-13, 2.1955026393964279988917878654e-13, -4.1934859852834647427576319246e-14, 4.6341149635933550715779074274e-15, 2.3742488509048340106830309402e-16, -2.7276516388124786119323824391e-16, 7.8473570134636044722154797225e-17 }; static cheb_series zeta_xgt1_cs = { zeta_xgt1_data, 29, -1, 1, 17 }; /* chebyshev fit for Ln[Zeta[s(t)] - 1 - 2^(-s(t))] * s(t)= 10 + 5t * -1 <= t <= 1; 5 <= s <= 15 */ static double zetam1_inter_data[24] = { -21.7509435653088483422022339374, -5.63036877698121782876372020472, 0.0528041358684229425504861579635, -0.0156381809179670789342700883562, 0.00408218474372355881195080781927, -0.0010264867349474874045036628282, 0.000260469880409886900143834962387, -0.0000676175847209968878098566819447, 0.0000179284472587833525426660171124, -4.83238651318556188834107605116e-6, 1.31913788964999288471371329447e-6, -3.63760500656329972578222188542e-7, 1.01146847513194744989748396574e-7, -2.83215225141806501619105289509e-8, 7.97733710252021423361012829496e-9, -2.25850168553956886676250696891e-9, 6.42269392950164306086395744145e-10, -1.83363861846127284505060843614e-10, 5.25309763895283179960368072104e-11, -1.50958687042589821074710575446e-11, 4.34997545516049244697776942981e-12, -1.25597782748190416118082322061e-12, 3.61280740072222650030134104162e-13, -9.66437239205745207188920348801e-14 }; static cheb_series zetam1_inter_cs = { zetam1_inter_data, 22, -1, 1, 12 }; /* assumes s >= 0 and s != 1.0 */ inline static int riemann_zeta_sgt0(double s, gsl_sf_result * result) { if(s < 1.0) { gsl_sf_result c; cheb_eval_e(&zeta_xlt1_cs, 2.0*s - 1.0, &c); result->val = c.val / (s - 1.0); result->err = c.err / fabs(s-1.0) + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(s <= 20.0) { double x = (2.0*s - 21.0)/19.0; gsl_sf_result c; cheb_eval_e(&zeta_xgt1_cs, x, &c); result->val = c.val / (s - 1.0); result->err = c.err / (s - 1.0) + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double f2 = 1.0 - pow(2.0,-s); double f3 = 1.0 - pow(3.0,-s); double f5 = 1.0 - pow(5.0,-s); double f7 = 1.0 - pow(7.0,-s); result->val = 1.0/(f2*f3*f5*f7); result->err = 3.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } inline static int riemann_zeta1ms_slt0(double s, gsl_sf_result * result) { if(s > -19.0) { double x = (-19 - 2.0*s)/19.0; gsl_sf_result c; cheb_eval_e(&zeta_xgt1_cs, x, &c); result->val = c.val / (-s); result->err = c.err / (-s) + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double f2 = 1.0 - pow(2.0,-(1.0-s)); double f3 = 1.0 - pow(3.0,-(1.0-s)); double f5 = 1.0 - pow(5.0,-(1.0-s)); double f7 = 1.0 - pow(7.0,-(1.0-s)); result->val = 1.0/(f2*f3*f5*f7); result->err = 3.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /* works for 5 < s < 15*/ static int riemann_zeta_minus_1_intermediate_s(double s, gsl_sf_result * result) { double t = (s - 10.0)/5.0; gsl_sf_result c; cheb_eval_e(&zetam1_inter_cs, t, &c); result->val = exp(c.val) + pow(2.0, -s); result->err = (c.err + 2.0*GSL_DBL_EPSILON)*result->val; return GSL_SUCCESS; } /* assumes s is large and positive * write: zeta(s) - 1 = zeta(s) * (1 - 1/zeta(s)) * and expand a few terms of the product formula to evaluate 1 - 1/zeta(s) * * works well for s > 15 */ static int riemann_zeta_minus1_large_s(double s, gsl_sf_result * result) { double a = pow( 2.0,-s); double b = pow( 3.0,-s); double c = pow( 5.0,-s); double d = pow( 7.0,-s); double e = pow(11.0,-s); double f = pow(13.0,-s); double t1 = a + b + c + d + e + f; double t2 = a*(b+c+d+e+f) + b*(c+d+e+f) + c*(d+e+f) + d*(e+f) + e*f; /* double t3 = a*(b*(c+d+e+f) + c*(d+e+f) + d*(e+f) + e*f) + b*(c*(d+e+f) + d*(e+f) + e*f) + c*(d*(e+f) + e*f) + d*e*f; double t4 = a*(b*(c*(d + e + f) + d*(e + f) + e*f) + c*(d*(e+f) + e*f) + d*e*f) + b*(c*(d*(e+f) + e*f) + d*e*f) + c*d*e*f; double t5 = b*c*d*e*f + a*c*d*e*f+ a*b*d*e*f+ a*b*c*e*f+ a*b*c*d*f+ a*b*c*d*e; double t6 = a*b*c*d*e*f; */ double numt = t1 - t2 /* + t3 - t4 + t5 - t6 */; double zeta = 1.0/((1.0-a)*(1.0-b)*(1.0-c)*(1.0-d)*(1.0-e)*(1.0-f)); result->val = numt*zeta; result->err = (15.0/s + 1.0) * 6.0*GSL_DBL_EPSILON*result->val; return GSL_SUCCESS; } #if 0 /* zeta(n) */ #define ZETA_POS_TABLE_NMAX 100 static double zeta_pos_int_table_OLD[ZETA_POS_TABLE_NMAX+1] = { -0.50000000000000000000000000000, /* zeta(0) */ 0.0 /* FIXME: DirectedInfinity() */, /* zeta(1) */ 1.64493406684822643647241516665, /* ... */ 1.20205690315959428539973816151, 1.08232323371113819151600369654, 1.03692775514336992633136548646, 1.01734306198444913971451792979, 1.00834927738192282683979754985, 1.00407735619794433937868523851, 1.00200839282608221441785276923, 1.00099457512781808533714595890, 1.00049418860411946455870228253, 1.00024608655330804829863799805, 1.00012271334757848914675183653, 1.00006124813505870482925854511, 1.00003058823630702049355172851, 1.00001528225940865187173257149, 1.00000763719763789976227360029, 1.00000381729326499983985646164, 1.00000190821271655393892565696, 1.00000095396203387279611315204, 1.00000047693298678780646311672, 1.00000023845050272773299000365, 1.00000011921992596531107306779, 1.00000005960818905125947961244, 1.00000002980350351465228018606, 1.00000001490155482836504123466, 1.00000000745071178983542949198, 1.00000000372533402478845705482, 1.00000000186265972351304900640, 1.00000000093132743241966818287, 1.00000000046566290650337840730, 1.00000000023283118336765054920, 1.00000000011641550172700519776, 1.00000000005820772087902700889, 1.00000000002910385044497099687, 1.00000000001455192189104198424, 1.00000000000727595983505748101, 1.00000000000363797954737865119, 1.00000000000181898965030706595, 1.00000000000090949478402638893, 1.00000000000045474737830421540, 1.00000000000022737368458246525, 1.00000000000011368684076802278, 1.00000000000005684341987627586, 1.00000000000002842170976889302, 1.00000000000001421085482803161, 1.00000000000000710542739521085, 1.00000000000000355271369133711, 1.00000000000000177635684357912, 1.00000000000000088817842109308, 1.00000000000000044408921031438, 1.00000000000000022204460507980, 1.00000000000000011102230251411, 1.00000000000000005551115124845, 1.00000000000000002775557562136, 1.00000000000000001387778780973, 1.00000000000000000693889390454, 1.00000000000000000346944695217, 1.00000000000000000173472347605, 1.00000000000000000086736173801, 1.00000000000000000043368086900, 1.00000000000000000021684043450, 1.00000000000000000010842021725, 1.00000000000000000005421010862, 1.00000000000000000002710505431, 1.00000000000000000001355252716, 1.00000000000000000000677626358, 1.00000000000000000000338813179, 1.00000000000000000000169406589, 1.00000000000000000000084703295, 1.00000000000000000000042351647, 1.00000000000000000000021175824, 1.00000000000000000000010587912, 1.00000000000000000000005293956, 1.00000000000000000000002646978, 1.00000000000000000000001323489, 1.00000000000000000000000661744, 1.00000000000000000000000330872, 1.00000000000000000000000165436, 1.00000000000000000000000082718, 1.00000000000000000000000041359, 1.00000000000000000000000020680, 1.00000000000000000000000010340, 1.00000000000000000000000005170, 1.00000000000000000000000002585, 1.00000000000000000000000001292, 1.00000000000000000000000000646, 1.00000000000000000000000000323, 1.00000000000000000000000000162, 1.00000000000000000000000000081, 1.00000000000000000000000000040, 1.00000000000000000000000000020, 1.00000000000000000000000000010, 1.00000000000000000000000000005, 1.00000000000000000000000000003, 1.00000000000000000000000000001, 1.00000000000000000000000000001, 1.00000000000000000000000000000, 1.00000000000000000000000000000, 1.00000000000000000000000000000 }; #endif /* 0 */ /* zeta(n) - 1 */ #define ZETA_POS_TABLE_NMAX 100 static double zetam1_pos_int_table[ZETA_POS_TABLE_NMAX+1] = { -1.5, /* zeta(0) */ 0.0, /* FIXME: Infinity */ /* zeta(1) - 1 */ 0.644934066848226436472415166646, /* zeta(2) - 1 */ 0.202056903159594285399738161511, 0.082323233711138191516003696541, 0.036927755143369926331365486457, 0.017343061984449139714517929790, 0.008349277381922826839797549849, 0.004077356197944339378685238508, 0.002008392826082214417852769232, 0.000994575127818085337145958900, 0.000494188604119464558702282526, 0.000246086553308048298637998047, 0.000122713347578489146751836526, 0.000061248135058704829258545105, 0.000030588236307020493551728510, 0.000015282259408651871732571487, 7.6371976378997622736002935630e-6, 3.8172932649998398564616446219e-6, 1.9082127165539389256569577951e-6, 9.5396203387279611315203868344e-7, 4.7693298678780646311671960437e-7, 2.3845050272773299000364818675e-7, 1.1921992596531107306778871888e-7, 5.9608189051259479612440207935e-8, 2.9803503514652280186063705069e-8, 1.4901554828365041234658506630e-8, 7.4507117898354294919810041706e-9, 3.7253340247884570548192040184e-9, 1.8626597235130490064039099454e-9, 9.3132743241966818287176473502e-10, 4.6566290650337840729892332512e-10, 2.3283118336765054920014559759e-10, 1.1641550172700519775929738354e-10, 5.8207720879027008892436859891e-11, 2.9103850444970996869294252278e-11, 1.4551921891041984235929632245e-11, 7.2759598350574810145208690123e-12, 3.6379795473786511902372363558e-12, 1.8189896503070659475848321007e-12, 9.0949478402638892825331183869e-13, 4.5474737830421540267991120294e-13, 2.2737368458246525152268215779e-13, 1.1368684076802278493491048380e-13, 5.6843419876275856092771829675e-14, 2.8421709768893018554550737049e-14, 1.4210854828031606769834307141e-14, 7.1054273952108527128773544799e-15, 3.5527136913371136732984695340e-15, 1.7763568435791203274733490144e-15, 8.8817842109308159030960913863e-16, 4.4408921031438133641977709402e-16, 2.2204460507980419839993200942e-16, 1.1102230251410661337205445699e-16, 5.5511151248454812437237365905e-17, 2.7755575621361241725816324538e-17, 1.3877787809725232762839094906e-17, 6.9388939045441536974460853262e-18, 3.4694469521659226247442714961e-18, 1.7347234760475765720489729699e-18, 8.6736173801199337283420550673e-19, 4.3368086900206504874970235659e-19, 2.1684043449972197850139101683e-19, 1.0842021724942414063012711165e-19, 5.4210108624566454109187004043e-20, 2.7105054312234688319546213119e-20, 1.3552527156101164581485233996e-20, 6.7762635780451890979952987415e-21, 3.3881317890207968180857031004e-21, 1.6940658945097991654064927471e-21, 8.4703294725469983482469926091e-22, 4.2351647362728333478622704833e-22, 2.1175823681361947318442094398e-22, 1.0587911840680233852265001539e-22, 5.2939559203398703238139123029e-23, 2.6469779601698529611341166842e-23, 1.3234889800848990803094510250e-23, 6.6174449004244040673552453323e-24, 3.3087224502121715889469563843e-24, 1.6543612251060756462299236771e-24, 8.2718061255303444036711056167e-25, 4.1359030627651609260093824555e-25, 2.0679515313825767043959679193e-25, 1.0339757656912870993284095591e-25, 5.1698788284564313204101332166e-26, 2.5849394142282142681277617708e-26, 1.2924697071141066700381126118e-26, 6.4623485355705318034380021611e-27, 3.2311742677852653861348141180e-27, 1.6155871338926325212060114057e-27, 8.0779356694631620331587381863e-28, 4.0389678347315808256222628129e-28, 2.0194839173657903491587626465e-28, 1.0097419586828951533619250700e-28, 5.0487097934144756960847711725e-29, 2.5243548967072378244674341938e-29, 1.2621774483536189043753999660e-29, 6.3108872417680944956826093943e-30, 3.1554436208840472391098412184e-30, 1.5777218104420236166444327830e-30, 7.8886090522101180735205378276e-31 }; #define ZETA_NEG_TABLE_NMAX 99 #define ZETA_NEG_TABLE_SIZE 50 static double zeta_neg_int_table[ZETA_NEG_TABLE_SIZE] = { -0.083333333333333333333333333333, /* zeta(-1) */ 0.008333333333333333333333333333, /* zeta(-3) */ -0.003968253968253968253968253968, /* ... */ 0.004166666666666666666666666667, -0.007575757575757575757575757576, 0.021092796092796092796092796093, -0.083333333333333333333333333333, 0.44325980392156862745098039216, -3.05395433027011974380395433027, 26.4562121212121212121212121212, -281.460144927536231884057971014, 3607.5105463980463980463980464, -54827.583333333333333333333333, 974936.82385057471264367816092, -2.0052695796688078946143462272e+07, 4.7238486772162990196078431373e+08, -1.2635724795916666666666666667e+10, 3.8087931125245368811553022079e+11, -1.2850850499305083333333333333e+13, 4.8241448354850170371581670362e+14, -2.0040310656516252738108421663e+16, 9.1677436031953307756992753623e+17, -4.5979888343656503490437943262e+19, 2.5180471921451095697089023320e+21, -1.5001733492153928733711440151e+23, 9.6899578874635940656497942895e+24, -6.7645882379292820990945242302e+26, 5.0890659468662289689766332916e+28, -4.1147288792557978697665486068e+30, 3.5666582095375556109684574609e+32, -3.3066089876577576725680214670e+34, 3.2715634236478716264211227016e+36, -3.4473782558278053878256455080e+38, 3.8614279832705258893092720200e+40, -4.5892974432454332168863989006e+42, 5.7775386342770431824884825688e+44, -7.6919858759507135167410075972e+46, 1.0813635449971654696354033351e+49, -1.6029364522008965406067102346e+51, 2.5019479041560462843656661499e+53, -4.1067052335810212479752045004e+55, 7.0798774408494580617452972433e+57, -1.2804546887939508790190849756e+60, 2.4267340392333524078020892067e+62, -4.8143218874045769355129570066e+64, 9.9875574175727530680652777408e+66, -2.1645634868435185631335136160e+69, 4.8962327039620553206849224516e+71, /* ... */ -1.1549023923963519663954271692e+74, /* zeta(-97) */ 2.8382249570693706959264156336e+76 /* zeta(-99) */ }; /* coefficients for Maclaurin summation in hzeta() * B_{2j}/(2j)! */ static double hzeta_c[15] = { 1.00000000000000000000000000000, 0.083333333333333333333333333333, -0.00138888888888888888888888888889, 0.000033068783068783068783068783069, -8.2671957671957671957671957672e-07, 2.0876756987868098979210090321e-08, -5.2841901386874931848476822022e-10, 1.3382536530684678832826980975e-11, -3.3896802963225828668301953912e-13, 8.5860620562778445641359054504e-15, -2.1748686985580618730415164239e-16, 5.5090028283602295152026526089e-18, -1.3954464685812523340707686264e-19, 3.5347070396294674716932299778e-21, -8.9535174270375468504026113181e-23 }; #define ETA_POS_TABLE_NMAX 100 static double eta_pos_int_table[ETA_POS_TABLE_NMAX+1] = { 0.50000000000000000000000000000, /* eta(0) */ M_LN2, /* eta(1) */ 0.82246703342411321823620758332, /* ... */ 0.90154267736969571404980362113, 0.94703282949724591757650323447, 0.97211977044690930593565514355, 0.98555109129743510409843924448, 0.99259381992283028267042571313, 0.99623300185264789922728926008, 0.99809429754160533076778303185, 0.99903950759827156563922184570, 0.99951714349806075414409417483, 0.99975768514385819085317967871, 0.99987854276326511549217499282, 0.99993917034597971817095419226, 0.99996955121309923808263293263, 0.99998476421490610644168277496, 0.99999237829204101197693787224, 0.99999618786961011347968922641, 0.99999809350817167510685649297, 0.99999904661158152211505084256, 0.99999952325821554281631666433, 0.99999976161323082254789720494, 0.99999988080131843950322382485, 0.99999994039889239462836140314, 0.99999997019885696283441513311, 0.99999998509923199656878766181, 0.99999999254955048496351585274, 0.99999999627475340010872752767, 0.99999999813736941811218674656, 0.99999999906868228145397862728, 0.99999999953434033145421751469, 0.99999999976716989595149082282, 0.99999999988358485804603047265, 0.99999999994179239904531592388, 0.99999999997089618952980952258, 0.99999999998544809143388476396, 0.99999999999272404460658475006, 0.99999999999636202193316875550, 0.99999999999818101084320873555, 0.99999999999909050538047887809, 0.99999999999954525267653087357, 0.99999999999977262633369589773, 0.99999999999988631316532476488, 0.99999999999994315658215465336, 0.99999999999997157829090808339, 0.99999999999998578914539762720, 0.99999999999999289457268000875, 0.99999999999999644728633373609, 0.99999999999999822364316477861, 0.99999999999999911182158169283, 0.99999999999999955591079061426, 0.99999999999999977795539522974, 0.99999999999999988897769758908, 0.99999999999999994448884878594, 0.99999999999999997224442439010, 0.99999999999999998612221219410, 0.99999999999999999306110609673, 0.99999999999999999653055304826, 0.99999999999999999826527652409, 0.99999999999999999913263826204, 0.99999999999999999956631913101, 0.99999999999999999978315956551, 0.99999999999999999989157978275, 0.99999999999999999994578989138, 0.99999999999999999997289494569, 0.99999999999999999998644747284, 0.99999999999999999999322373642, 0.99999999999999999999661186821, 0.99999999999999999999830593411, 0.99999999999999999999915296705, 0.99999999999999999999957648353, 0.99999999999999999999978824176, 0.99999999999999999999989412088, 0.99999999999999999999994706044, 0.99999999999999999999997353022, 0.99999999999999999999998676511, 0.99999999999999999999999338256, 0.99999999999999999999999669128, 0.99999999999999999999999834564, 0.99999999999999999999999917282, 0.99999999999999999999999958641, 0.99999999999999999999999979320, 0.99999999999999999999999989660, 0.99999999999999999999999994830, 0.99999999999999999999999997415, 0.99999999999999999999999998708, 0.99999999999999999999999999354, 0.99999999999999999999999999677, 0.99999999999999999999999999838, 0.99999999999999999999999999919, 0.99999999999999999999999999960, 0.99999999999999999999999999980, 0.99999999999999999999999999990, 0.99999999999999999999999999995, 0.99999999999999999999999999997, 0.99999999999999999999999999999, 0.99999999999999999999999999999, 1.00000000000000000000000000000, 1.00000000000000000000000000000, 1.00000000000000000000000000000, }; #define ETA_NEG_TABLE_NMAX 99 #define ETA_NEG_TABLE_SIZE 50 static double eta_neg_int_table[ETA_NEG_TABLE_SIZE] = { 0.25000000000000000000000000000, /* eta(-1) */ -0.12500000000000000000000000000, /* eta(-3) */ 0.25000000000000000000000000000, /* ... */ -1.06250000000000000000000000000, 7.75000000000000000000000000000, -86.3750000000000000000000000000, 1365.25000000000000000000000000, -29049.0312500000000000000000000, 800572.750000000000000000000000, -2.7741322625000000000000000000e+7, 1.1805291302500000000000000000e+9, -6.0523980051687500000000000000e+10, 3.6794167785377500000000000000e+12, -2.6170760990658387500000000000e+14, 2.1531418140800295250000000000e+16, -2.0288775575173015930156250000e+18, 2.1708009902623770590275000000e+20, -2.6173826968455814932120125000e+22, 3.5324148876863877826668602500e+24, -5.3042033406864906641493838981e+26, 8.8138218364311576767253114668e+28, -1.6128065107490778547354654864e+31, 3.2355470001722734208527794569e+33, -7.0876727476537493198506645215e+35, 1.6890450341293965779175629389e+38, -4.3639690731216831157655651358e+40, 1.2185998827061261322605065672e+43, -3.6670584803153006180101262324e+45, 1.1859898526302099104271449748e+48, -4.1120769493584015047981746438e+50, 1.5249042436787620309090168687e+53, -6.0349693196941307074572991901e+55, 2.5437161764210695823197691519e+58, -1.1396923802632287851130360170e+61, 5.4180861064753979196802726455e+63, -2.7283654799994373847287197104e+66, 1.4529750514918543238511171663e+69, -8.1705519371067450079777183386e+71, 4.8445781606678367790247757259e+74, -3.0246694206649519336179448018e+77, 1.9858807961690493054169047970e+80, -1.3694474620720086994386818232e+83, 9.9070382984295807826303785989e+85, -7.5103780796592645925968460677e+88, 5.9598418264260880840077992227e+91, -4.9455988887500020399263196307e+94, 4.2873596927020241277675775935e+97, -3.8791952037716162900707994047e+100, 3.6600317773156342245401829308e+103, -3.5978775704117283875784869570e+106 /* eta(-99) */ }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_hzeta_e(const double s, const double q, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s <= 1.0 || q <= 0.0) { DOMAIN_ERROR(result); } else { const double max_bits = 54.0; const double ln_term0 = -s * log(q); if(ln_term0 < GSL_LOG_DBL_MIN + 1.0) { UNDERFLOW_ERROR(result); } else if(ln_term0 > GSL_LOG_DBL_MAX - 1.0) { OVERFLOW_ERROR (result); } else if((s > max_bits && q < 1.0) || (s > 0.5*max_bits && q < 0.25)) { result->val = pow(q, -s); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(s > 0.5*max_bits && q < 1.0) { const double p1 = pow(q, -s); const double p2 = pow(q/(1.0+q), s); const double p3 = pow(q/(2.0+q), s); result->val = p1 * (1.0 + p2 + p3); result->err = GSL_DBL_EPSILON * (0.5*s + 2.0) * fabs(result->val); return GSL_SUCCESS; } else { /* Euler-Maclaurin summation formula * [Moshier, p. 400, with several typo corrections] */ const int jmax = 12; const int kmax = 10; int j, k; const double pmax = pow(kmax + q, -s); double scp = s; double pcp = pmax / (kmax + q); double ans = pmax*((kmax+q)/(s-1.0) + 0.5); for(k=0; kval = ans; result->err = 2.0 * (jmax + 1.0) * GSL_DBL_EPSILON * fabs(ans); return GSL_SUCCESS; } } } int gsl_sf_zeta_e(const double s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s == 1.0) { DOMAIN_ERROR(result); } else if(s >= 0.0) { return riemann_zeta_sgt0(s, result); } else { /* reflection formula, [Abramowitz+Stegun, 23.2.5] */ gsl_sf_result zeta_one_minus_s; const int stat_zoms = riemann_zeta1ms_slt0(s, &zeta_one_minus_s); const double sin_term = (fmod(s,2.0) == 0.0) ? 0.0 : sin(0.5*M_PI*fmod(s,4.0))/M_PI; if(sin_term == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(s > -170) { /* We have to be careful about losing digits * in calculating pow(2 Pi, s). The gamma * function is fine because we were careful * with that implementation. * We keep an array of (2 Pi)^(10 n). */ const double twopi_pow[18] = { 1.0, 9.589560061550901348e+007, 9.195966217409212684e+015, 8.818527036583869903e+023, 8.456579467173150313e+031, 8.109487671573504384e+039, 7.776641909496069036e+047, 7.457457466828644277e+055, 7.151373628461452286e+063, 6.857852693272229709e+071, 6.576379029540265771e+079, 6.306458169130020789e+087, 6.047615938853066678e+095, 5.799397627482402614e+103, 5.561367186955830005e+111, 5.333106466365131227e+119, 5.114214477385391780e+127, 4.904306689854036836e+135 }; const int n = floor((-s)/10.0); const double fs = s + 10.0*n; const double p = pow(2.0*M_PI, fs) / twopi_pow[n]; gsl_sf_result g; const int stat_g = gsl_sf_gamma_e(1.0-s, &g); result->val = p * g.val * sin_term * zeta_one_minus_s.val; result->err = fabs(p * g.val * sin_term) * zeta_one_minus_s.err; result->err += fabs(p * sin_term * zeta_one_minus_s.val) * g.err; result->err += GSL_DBL_EPSILON * (fabs(s)+2.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_g, stat_zoms); } else { /* The actual zeta function may or may not * overflow here. But we have no easy way * to calculate it when the prefactor(s) * overflow. Trying to use log's and exp * is no good because we loose a couple * digits to the exp error amplification. * When we gather a little more patience, * we can implement something here. Until * then just give up. */ OVERFLOW_ERROR(result); } } } int gsl_sf_zeta_int_e(const int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n < 0) { if(!GSL_IS_ODD(n)) { result->val = 0.0; /* exactly zero at even negative integers */ result->err = 0.0; return GSL_SUCCESS; } else if(n > -ZETA_NEG_TABLE_NMAX) { result->val = zeta_neg_int_table[-(n+1)/2]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { return gsl_sf_zeta_e((double)n, result); } } else if(n == 1){ DOMAIN_ERROR(result); } else if(n <= ZETA_POS_TABLE_NMAX){ result->val = 1.0 + zetam1_pos_int_table[n]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = 1.0; result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } } int gsl_sf_zetam1_e(const double s, gsl_sf_result * result) { if(s <= 5.0) { int stat = gsl_sf_zeta_e(s, result); result->val = result->val - 1.0; return stat; } else if(s < 15.0) { return riemann_zeta_minus_1_intermediate_s(s, result); } else { return riemann_zeta_minus1_large_s(s, result); } } int gsl_sf_zetam1_int_e(const int n, gsl_sf_result * result) { if(n < 0) { if(!GSL_IS_ODD(n)) { result->val = -1.0; /* at even negative integers zetam1 == -1 since zeta is exactly zero */ result->err = 0.0; return GSL_SUCCESS; } else if(n > -ZETA_NEG_TABLE_NMAX) { result->val = zeta_neg_int_table[-(n+1)/2] - 1.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* could use gsl_sf_zetam1_e here but subtracting 1 makes no difference for such large values, so go straight to the result */ return gsl_sf_zeta_e((double)n, result); } } else if(n == 1){ DOMAIN_ERROR(result); } else if(n <= ZETA_POS_TABLE_NMAX){ result->val = zetam1_pos_int_table[n]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { return gsl_sf_zetam1_e(n, result); } } int gsl_sf_eta_int_e(int n, gsl_sf_result * result) { if(n > ETA_POS_TABLE_NMAX) { result->val = 1.0; result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(n >= 0) { result->val = eta_pos_int_table[n]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* n < 0 */ if(!GSL_IS_ODD(n)) { /* exactly zero at even negative integers */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(n > -ETA_NEG_TABLE_NMAX) { result->val = eta_neg_int_table[-(n+1)/2]; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result z; gsl_sf_result p; int stat_z = gsl_sf_zeta_int_e(n, &z); int stat_p = gsl_sf_exp_e((1.0-n)*M_LN2, &p); int stat_m = gsl_sf_multiply_e(-p.val, z.val, result); result->err = fabs(p.err * (M_LN2*(1.0-n)) * z.val) + z.err * fabs(p.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_m, stat_p, stat_z); } } } int gsl_sf_eta_e(const double s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s > 100.0) { result->val = 1.0; result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(fabs(s-1.0) < 10.0*GSL_ROOT5_DBL_EPSILON) { double del = s-1.0; double c0 = M_LN2; double c1 = M_LN2 * (M_EULER - 0.5*M_LN2); double c2 = -0.0326862962794492996; double c3 = 0.0015689917054155150; double c4 = 0.00074987242112047532; result->val = c0 + del * (c1 + del * (c2 + del * (c3 + del * c4))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result z; gsl_sf_result p; int stat_z = gsl_sf_zeta_e(s, &z); int stat_p = gsl_sf_exp_e((1.0-s)*M_LN2, &p); int stat_m = gsl_sf_multiply_e(1.0-p.val, z.val, result); result->err = fabs(p.err * (M_LN2*(1.0-s)) * z.val) + z.err * fabs(p.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_m, stat_p, stat_z); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_zeta(const double s) { EVAL_RESULT(gsl_sf_zeta_e(s, &result)); } double gsl_sf_hzeta(const double s, const double a) { EVAL_RESULT(gsl_sf_hzeta_e(s, a, &result)); } double gsl_sf_zeta_int(const int s) { EVAL_RESULT(gsl_sf_zeta_int_e(s, &result)); } double gsl_sf_zetam1(const double s) { EVAL_RESULT(gsl_sf_zetam1_e(s, &result)); } double gsl_sf_zetam1_int(const int s) { EVAL_RESULT(gsl_sf_zetam1_int_e(s, &result)); } double gsl_sf_eta_int(const int s) { EVAL_RESULT(gsl_sf_eta_int_e(s, &result)); } double gsl_sf_eta(const double s) { EVAL_RESULT(gsl_sf_eta_e(s, &result)); } sources_5316/external/gsl/gsl_cblas__ctrsm.c0000664000176700017670000000076211723710247020011 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" #include "gsl_cblas__hypot.c" void cblas_ctrsm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const void *alpha, const void *A, const int lda, void *B, const int ldb) { #define BASE float #include "gsl_cblas__source_trsm_c.h" #undef BASE } sources_5316/external/gsl/gsl_multimin__directional_minimize.c0000664000176700017670000001260011723710247023623 0ustar paulpaul/* multimin/directional_minimize.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Fabrice Rossi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void take_step (const gsl_vector * x, const gsl_vector * p, double step, double lambda, gsl_vector * x1, gsl_vector * dx) { gsl_vector_set_zero (dx); gsl_blas_daxpy (-step * lambda, p, dx); gsl_vector_memcpy (x1, x); gsl_blas_daxpy (1.0, dx, x1); } static void intermediate_point (gsl_multimin_function_fdf * fdf, const gsl_vector * x, const gsl_vector * p, double lambda, double pg, double stepa, double stepc, double fa, double fc, gsl_vector * x1, gsl_vector * dx, gsl_vector * gradient, double * step, double * f) { double stepb, fb; trial: { double u = fabs (pg * lambda * stepc); stepb = 0.5 * stepc * u / ((fc - fa) + u); } take_step (x, p, stepb, lambda, x1, dx); fb = GSL_MULTIMIN_FN_EVAL_F (fdf, x1); #ifdef DEBUG printf ("trying stepb = %g fb = %.18e\n", stepb, fb); #endif if (fb >= fa && stepb > 0.0) { /* downhill step failed, reduce step-size and try again */ fc = fb; stepc = stepb; goto trial; } #ifdef DEBUG printf ("ok!\n"); #endif *step = stepb; *f = fb; GSL_MULTIMIN_FN_EVAL_DF(fdf, x1, gradient); } static void minimize (gsl_multimin_function_fdf * fdf, const gsl_vector * x, const gsl_vector * p, double lambda, double stepa, double stepb, double stepc, double fa, double fb, double fc, double tol, gsl_vector * x1, gsl_vector * dx1, gsl_vector * x2, gsl_vector * dx2, gsl_vector * gradient, double * step, double * f, double * gnorm) { /* Starting at (x0, f0) move along the direction p to find a minimum f(x0 - lambda * p), returning the new point x1 = x0-lambda*p, f1=f(x1) and g1 = grad(f) at x1. */ double u = stepb; double v = stepa; double w = stepc; double fu = fb; double fv = fa; double fw = fc; double old2 = fabs(w - v); double old1 = fabs(v - u); double stepm, fm, pg, gnorm1; int iter = 0; gsl_vector_memcpy (x2, x1); gsl_vector_memcpy (dx2, dx1); *f = fb; *step = stepb; *gnorm = gsl_blas_dnrm2 (gradient); mid_trial: iter++; if (iter > 10) { return; /* MAX ITERATIONS */ } { double dw = w - u; double dv = v - u; double du = 0.0; double e1 = ((fv - fu) * dw * dw + (fu - fw) * dv * dv); double e2 = 2.0 * ((fv - fu) * dw + (fu - fw) * dv); if (e2 != 0.0) { du = e1 / e2; } if (du > 0.0 && du < (stepc - stepb) && fabs(du) < 0.5 * old2) { stepm = u + du; } else if (du < 0.0 && du > (stepa - stepb) && fabs(du) < 0.5 * old2) { stepm = u + du; } else if ((stepc - stepb) > (stepb - stepa)) { stepm = 0.38 * (stepc - stepb) + stepb; } else { stepm = stepb - 0.38 * (stepb - stepa); } } take_step (x, p, stepm, lambda, x1, dx1); fm = GSL_MULTIMIN_FN_EVAL_F (fdf, x1); #ifdef DEBUG printf ("trying stepm = %g fm = %.18e\n", stepm, fm); #endif if (fm > fb) { if (fm < fv) { w = v; v = stepm; fw = fv; fv = fm; } else if (fm < fw) { w = stepm; fw = fm; } if (stepm < stepb) { stepa = stepm; fa = fm; } else { stepc = stepm; fc = fm; } goto mid_trial; } else if (fm <= fb) { old2 = old1; old1 = fabs(u - stepm); w = v; v = u; u = stepm; fw = fv; fv = fu; fu = fm; gsl_vector_memcpy (x2, x1); gsl_vector_memcpy (dx2, dx1); GSL_MULTIMIN_FN_EVAL_DF (fdf, x1, gradient); gsl_blas_ddot (p, gradient, &pg); gnorm1 = gsl_blas_dnrm2 (gradient); #ifdef DEBUG printf ("p: "); gsl_vector_fprintf(stdout, p, "%g"); printf ("g: "); gsl_vector_fprintf(stdout, gradient, "%g"); printf ("gnorm: %.18e\n", gnorm1); printf ("pg: %.18e\n", pg); printf ("orth: %g\n", fabs (pg * lambda/ gnorm1)); #endif *f = fm; *step = stepm; *gnorm = gnorm1; if (fabs (pg * lambda / gnorm1) < tol) { #ifdef DEBUG printf("ok!\n"); #endif return; /* SUCCESS */ } if (stepm < stepb) { stepc = stepb; fc = fb; stepb = stepm; fb = fm; } else { stepa = stepb; fa = fb; stepb = stepm; fb = fm; } goto mid_trial; } } sources_5316/external/gsl/gsl_fft__real_pass_3.c0000664000176700017670000001332311723710247020544 0ustar paulpaul/* fft/real_pass_3.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_real,pass_3) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[]) { size_t k, k1; const size_t factor = 3; const size_t m = n / factor; const size_t q = n / product; const size_t product_1 = product / factor; const ATOMIC tau = sqrt (3.0) / 2.0; for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1; const size_t from1 = from0 + m; const size_t from2 = from1 + m; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC t1 = z1_real + z2_real; const ATOMIC x0_real = z0_real + t1; const ATOMIC x1_real = z0_real - t1 / 2.0; const ATOMIC x1_imag = -tau * (z1_real - z2_real); const size_t to0 = product * k1; const size_t to1 = to0 + 2 * product_1 - 1; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to1 + 1) = x1_imag; } if (product_1 == 1) return; for (k = 1; k < (product_1 + 1) / 2; k++) { const ATOMIC w1_real = GSL_REAL(twiddle1[k - 1]); const ATOMIC w1_imag = -GSL_IMAG(twiddle1[k - 1]); const ATOMIC w2_real = GSL_REAL(twiddle2[k - 1]); const ATOMIC w2_imag = -GSL_IMAG(twiddle2[k - 1]); for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1 + 2 * k - 1; const size_t from1 = from0 + m; const size_t from2 = from1 + m; const ATOMIC f0_real = VECTOR(in,istride,from0); const ATOMIC f0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC f1_real = VECTOR(in,istride,from1); const ATOMIC f1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC f2_real = VECTOR(in,istride,from2); const ATOMIC f2_imag = VECTOR(in,istride,from2 + 1); const ATOMIC z0_real = f0_real; const ATOMIC z0_imag = f0_imag; const ATOMIC z1_real = w1_real * f1_real - w1_imag * f1_imag; const ATOMIC z1_imag = w1_real * f1_imag + w1_imag * f1_real; const ATOMIC z2_real = w2_real * f2_real - w2_imag * f2_imag; const ATOMIC z2_imag = w2_real * f2_imag + w2_imag * f2_real; /* compute x = W(3) z */ /* t1 = z1 + z2 */ const ATOMIC t1_real = z1_real + z2_real; const ATOMIC t1_imag = z1_imag + z2_imag; /* t2 = z0 - t1/2 */ const ATOMIC t2_real = z0_real - t1_real / 2; const ATOMIC t2_imag = z0_imag - t1_imag / 2; /* t3 = (+/-) sin(pi/3)*(z1 - z2) */ const ATOMIC t3_real = -tau * (z1_real - z2_real); const ATOMIC t3_imag = -tau * (z1_imag - z2_imag); /* x0 = z0 + t1 */ const ATOMIC x0_real = z0_real + t1_real; const ATOMIC x0_imag = z0_imag + t1_imag; /* x1 = t2 + i t3 */ const ATOMIC x1_real = t2_real - t3_imag; const ATOMIC x1_imag = t2_imag + t3_real; /* x2 = t2 - i t3 */ const ATOMIC x2_real = t2_real + t3_imag; const ATOMIC x2_imag = t2_imag - t3_real; /* apply twiddle factors */ const size_t to0 = k1 * product + 2 * k - 1; const size_t to1 = to0 + 2 * product_1; const size_t to2 = 2 * product_1 - 2 * k + k1 * product - 1; /* to0 = 1 * x0 */ VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to0 + 1) = x0_imag; /* to1 = 1 * x1 */ VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to1 + 1) = x1_imag; /* to2 = 1 * x2 */ VECTOR(out,ostride,to2) = x2_real; VECTOR(out,ostride,to2 + 1) = -x2_imag; } } if (product_1 % 2 == 1) return; for (k1 = 0; k1 < q; k1++) { const size_t from0 = k1 * product_1 + product_1 - 1; const size_t from1 = from0 + m; const size_t from2 = from1 + m; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC t1 = z1_real - z2_real; const ATOMIC x0_real = z0_real + t1 / 2.0; const ATOMIC x0_imag = -tau * (z1_real + z2_real); const ATOMIC x1_real = z0_real - t1; const size_t to0 = k1 * product + product_1 - 1; const size_t to1 = to0 + 2 * product_1; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to0 + 1) = x0_imag; VECTOR(out,ostride,to1) = x1_real; } return; } sources_5316/external/gsl/gsl_integration__qag.c0000664000176700017670000001551411723710247020671 0ustar paulpaul/* integration/qag.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_integration.h" #include "gsl_integration__initialise.c" #include "gsl_integration__set_initial.c" #include "gsl_integration__qpsrt.c" #include "gsl_integration__util.c" static int qag (const gsl_function *f, const double a, const double b, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double * result, double * abserr, gsl_integration_rule * q) ; int gsl_integration_qag (const gsl_function *f, double a, double b, double epsabs, double epsrel, size_t limit, int key, gsl_integration_workspace * workspace, double * result, double * abserr) { int status ; gsl_integration_rule * integration_rule = gsl_integration_qk15 ; if (key < GSL_INTEG_GAUSS15) { key = GSL_INTEG_GAUSS15 ; } else if (key > GSL_INTEG_GAUSS61) { key = GSL_INTEG_GAUSS61 ; } switch (key) { case GSL_INTEG_GAUSS15: integration_rule = gsl_integration_qk15 ; break ; case GSL_INTEG_GAUSS21: integration_rule = gsl_integration_qk21 ; break ; case GSL_INTEG_GAUSS31: integration_rule = gsl_integration_qk31 ; break ; case GSL_INTEG_GAUSS41: integration_rule = gsl_integration_qk41 ; break ; case GSL_INTEG_GAUSS51: integration_rule = gsl_integration_qk51 ; break ; case GSL_INTEG_GAUSS61: integration_rule = gsl_integration_qk61 ; break ; default: GSL_ERROR("value of key does specify a known integration rule", GSL_EINVAL) ; } status = qag (f, a, b, epsabs, epsrel, limit, workspace, result, abserr, integration_rule) ; return status ; } static int qag (const gsl_function * f, const double a, const double b, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr, gsl_integration_rule * q) { double area, errsum; double result0, abserr0, resabs0, resasc0; double tolerance; size_t iteration = 0; int roundoff_type1 = 0, roundoff_type2 = 0, error_type = 0; double round_off; /* Initialize results */ initialise (workspace, a, b); *result = 0; *abserr = 0; if (limit > workspace->limit) { GSL_ERROR ("iteration limit exceeds available workspace", GSL_EINVAL) ; } if (epsabs <= 0 && (epsrel < 50 * GSL_DBL_EPSILON || epsrel < 0.5e-28)) { GSL_ERROR ("tolerance cannot be acheived with given epsabs and epsrel", GSL_EBADTOL); } /* perform the first integration */ q (f, a, b, &result0, &abserr0, &resabs0, &resasc0); set_initial_result (workspace, result0, abserr0); /* Test on accuracy */ tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (result0)); /* need IEEE rounding here to match original quadpack behavior */ round_off = GSL_COERCE_DBL (50 * GSL_DBL_EPSILON * resabs0); if (abserr0 <= round_off && abserr0 > tolerance) { *result = result0; *abserr = abserr0; GSL_ERROR ("cannot reach tolerance because of roundoff error " "on first attempt", GSL_EROUND); } else if ((abserr0 <= tolerance && abserr0 != resasc0) || abserr0 == 0.0) { *result = result0; *abserr = abserr0; return GSL_SUCCESS; } else if (limit == 1) { *result = result0; *abserr = abserr0; GSL_ERROR ("a maximum of one iteration was insufficient", GSL_EMAXITER); } area = result0; errsum = abserr0; iteration = 1; do { double a1, b1, a2, b2; double a_i, b_i, r_i, e_i; double area1 = 0, area2 = 0, area12 = 0; double error1 = 0, error2 = 0, error12 = 0; double resasc1, resasc2; double resabs1, resabs2; /* Bisect the subinterval with the largest error estimate */ retrieve (workspace, &a_i, &b_i, &r_i, &e_i); a1 = a_i; b1 = 0.5 * (a_i + b_i); a2 = b1; b2 = b_i; q (f, a1, b1, &area1, &error1, &resabs1, &resasc1); q (f, a2, b2, &area2, &error2, &resabs2, &resasc2); area12 = area1 + area2; error12 = error1 + error2; errsum += (error12 - e_i); area += area12 - r_i; if (resasc1 != error1 && resasc2 != error2) { double delta = r_i - area12; if (fabs (delta) <= 1.0e-5 * fabs (area12) && error12 >= 0.99 * e_i) { roundoff_type1++; } if (iteration >= 10 && error12 > e_i) { roundoff_type2++; } } tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (area)); if (errsum > tolerance) { if (roundoff_type1 >= 6 || roundoff_type2 >= 20) { error_type = 2; /* round off error */ } /* set error flag in the case of bad integrand behaviour at a point of the integration range */ if (subinterval_too_small (a1, a2, b2)) { error_type = 3; } } update (workspace, a1, b1, area1, error1, a2, b2, area2, error2); retrieve (workspace, &a_i, &b_i, &r_i, &e_i); iteration++; } while (iteration < limit && !error_type && errsum > tolerance); *result = sum_results (workspace); *abserr = errsum; if (errsum <= tolerance) { return GSL_SUCCESS; } else if (error_type == 2) { GSL_ERROR ("roundoff error prevents tolerance from being achieved", GSL_EROUND); } else if (error_type == 3) { GSL_ERROR ("bad integrand behavior found in the integration interval", GSL_ESING); } else if (iteration == limit) { GSL_ERROR ("maximum number of subdivisions reached", GSL_EMAXITER); } else { GSL_ERROR ("could not integrate function", GSL_EFAILED); } } sources_5316/external/gsl/gsl_fft__hc_pass_n.c0000664000176700017670000002006511723710247020307 0ustar paulpaul/* fft/hc_pass_n.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_halfcomplex,pass_n) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t factor, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]) { size_t k, k1; const size_t m = n / factor; const size_t q = n / product; const size_t product_1 = product / factor; size_t e1, e2; const double d_theta = 2.0 * M_PI / ((double) factor); const ATOMIC cos_d_theta = cos (d_theta); const ATOMIC sin_d_theta = sin (d_theta); for (k1 = 0; k1 < product_1; k1++) { /* compute z = W(factor) x, for x halfcomplex */ ATOMIC dw_real = 1.0, dw_imag = 0.0; for (e1 = 0; e1 < factor; e1++) { ATOMIC sum_real = 0.0; ATOMIC w_real = 1.0, w_imag = 0.0; if (e1 > 0) { ATOMIC tmp_real = dw_real * cos_d_theta - dw_imag * sin_d_theta; ATOMIC tmp_imag = dw_real * sin_d_theta + dw_imag * cos_d_theta; dw_real = tmp_real; dw_imag = tmp_imag; } for (e2 = 0; e2 <= factor - e2; e2++) { ATOMIC z_real, z_imag; if (e2 > 0) { ATOMIC tmp_real = dw_real * w_real - dw_imag * w_imag; ATOMIC tmp_imag = dw_real * w_imag + dw_imag * w_real; w_real = tmp_real; w_imag = tmp_imag; } if (e2 == 0) { size_t from_idx = factor * k1 * q; z_real = VECTOR(in,istride,from_idx); z_imag = 0.0; sum_real += w_real * z_real - w_imag * z_imag; } else if (e2 == factor - e2) { size_t from_idx = factor * q * k1 + 2 * e2 * q - 1; z_real = VECTOR(in,istride,from_idx); z_imag = 0.0; sum_real += w_real * z_real; } else { size_t from_idx = factor * q * k1 + 2 * e2 * q - 1; z_real = VECTOR(in,istride,from_idx); z_imag = VECTOR(in,istride,from_idx + 1); sum_real += 2 * (w_real * z_real - w_imag * z_imag); } } { const size_t to_idx = q * k1 + e1 * m; VECTOR(out,ostride,to_idx) = sum_real; } } } if (q == 1) return; for (k = 1; k < (q + 1) / 2; k++) { for (k1 = 0; k1 < product_1; k1++) { ATOMIC dw_real = 1.0, dw_imag = 0.0; for (e1 = 0; e1 < factor; e1++) { ATOMIC z_real, z_imag; ATOMIC sum_real = 0.0; ATOMIC sum_imag = 0.0; ATOMIC w_real = 1.0, w_imag = 0.0; if (e1 > 0) { ATOMIC t_real = dw_real * cos_d_theta - dw_imag * sin_d_theta; ATOMIC t_imag = dw_real * sin_d_theta + dw_imag * cos_d_theta; dw_real = t_real; dw_imag = t_imag; } for (e2 = 0; e2 < factor; e2++) { if (e2 > 0) { ATOMIC tmp_real = dw_real * w_real - dw_imag * w_imag; ATOMIC tmp_imag = dw_real * w_imag + dw_imag * w_real; w_real = tmp_real; w_imag = tmp_imag; } if (e2 < factor - e2) { const size_t from0 = factor * k1 * q + 2 * k + 2 * e2 * q - 1; z_real = VECTOR(in,istride,from0); z_imag = VECTOR(in,istride,from0 + 1); } else { const size_t from0 = factor * k1 * q - 2 * k + 2 * (factor - e2) * q - 1; z_real = VECTOR(in,istride,from0); z_imag = -VECTOR(in,istride,from0 + 1); } sum_real += w_real * z_real - w_imag * z_imag; sum_imag += w_real * z_imag + w_imag * z_real; } if (k == 0 || e1 == 0) { w_real = 1.0; w_imag = 0.0; } else { size_t tskip = (q + 1) / 2 - 1; w_real = GSL_REAL(twiddle[k - 1 + tskip * (e1 - 1)]); w_imag = GSL_IMAG(twiddle[k - 1 + tskip * (e1 - 1)]); } { const size_t to0 = k1 * q + 2 * k + e1 * m - 1; VECTOR(out,ostride,to0) = w_real * sum_real - w_imag * sum_imag; VECTOR(out,ostride,to0 + 1) = w_real * sum_imag + w_imag * sum_real; } } } } if (q % 2 == 1) return; { double tw_arg = M_PI / ((double) factor); ATOMIC cos_tw_arg = cos (tw_arg); ATOMIC sin_tw_arg = sin (tw_arg); for (k1 = 0; k1 < product_1; k1++) { ATOMIC dw_real = 1.0, dw_imag = 0.0; ATOMIC tw_real = 1.0, tw_imag = 0.0; for (e1 = 0; e1 < factor; e1++) { ATOMIC w_real, w_imag, z_real, z_imag; ATOMIC sum_real = 0.0; if (e1 > 0) { ATOMIC tmp_real = tw_real * cos_tw_arg - tw_imag * sin_tw_arg; ATOMIC tmp_imag = tw_real * sin_tw_arg + tw_imag * cos_tw_arg; tw_real = tmp_real; tw_imag = tmp_imag; } w_real = tw_real; w_imag = tw_imag; if (e1 > 0) { ATOMIC t_real = dw_real * cos_d_theta - dw_imag * sin_d_theta; ATOMIC t_imag = dw_real * sin_d_theta + dw_imag * cos_d_theta; dw_real = t_real; dw_imag = t_imag; } for (e2 = 0; e2 <= factor - e2 - 1; e2++) { if (e2 > 0) { ATOMIC tmp_real = dw_real * w_real - dw_imag * w_imag; ATOMIC tmp_imag = dw_real * w_imag + dw_imag * w_real; w_real = tmp_real; w_imag = tmp_imag; } if (e2 == factor - e2 - 1) { const size_t from0 = factor * k1 * q + q + 2 * e2 * q - 1; z_real = VECTOR(in,istride,from0); z_imag = 0.0; sum_real += w_real * z_real - w_imag * z_imag; } else { const size_t from0 = factor * k1 * q + q + 2 * e2 * q - 1; z_real = VECTOR(in,istride,from0); z_imag = VECTOR(in,istride,from0 + 1); sum_real += 2 * (w_real * z_real - w_imag * z_imag); } } { const size_t to0 = k1 * q + q + e1 * m - 1; VECTOR(out,ostride,to0) = sum_real; } } } } return; } sources_5316/external/gsl/gsl_monte__plain.c0000664000176700017670000000651611723710247020025 0ustar paulpaul/* monte/plain.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Michael Booth * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Plain Monte-Carlo. */ /* Author: MJB */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_monte_plain.h" int gsl_monte_plain_integrate (const gsl_monte_function * f, const double xl[], const double xu[], const size_t dim, const size_t calls, gsl_rng * r, gsl_monte_plain_state * state, double *result, double *abserr) { double vol, m = 0, q = 0; double *x = state->x; size_t n, i; if (dim != state->dim) { GSL_ERROR ("number of dimensions must match allocated size", GSL_EINVAL); } for (i = 0; i < dim; i++) { if (xu[i] <= xl[i]) { GSL_ERROR ("xu must be greater than xl", GSL_EINVAL); } if (xu[i] - xl[i] > GSL_DBL_MAX) { GSL_ERROR ("Range of integration is too large, please rescale", GSL_EINVAL); } } /* Compute the volume of the region */ vol = 1; for (i = 0; i < dim; i++) { vol *= xu[i] - xl[i]; } for (n = 0; n < calls; n++) { /* Choose a random point in the integration region */ for (i = 0; i < dim; i++) { x[i] = xl[i] + gsl_rng_uniform_pos (r) * (xu[i] - xl[i]); } { double fval = GSL_MONTE_FN_EVAL (f, x); /* recurrence for mean and variance */ double d = fval - m; m += d / (n + 1.0); q += d * d * (n / (n + 1.0)); } } *result = vol * m; if (calls < 2) { *abserr = GSL_POSINF; } else { *abserr = vol * sqrt (q / (calls * (calls - 1.0))); } return GSL_SUCCESS; } gsl_monte_plain_state * gsl_monte_plain_alloc (size_t dim) { gsl_monte_plain_state *s = (gsl_monte_plain_state *) malloc (sizeof (gsl_monte_plain_state)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for state struct", GSL_ENOMEM, 0); } s->x = (double *) malloc (dim * sizeof (double)); if (s->x == 0) { free (s); GSL_ERROR_VAL ("failed to allocate space for working vector", GSL_ENOMEM, 0); } s->dim = dim; return s; } /* Set some default values and whatever */ int gsl_monte_plain_init (gsl_monte_plain_state * s) { size_t i; for (i = 0; i < s->dim; i++) { s->x[i] = 0.0; } return GSL_SUCCESS; } void gsl_monte_plain_free (gsl_monte_plain_state * s) { free (s->x); free (s); } sources_5316/external/gsl/gsl_statistics__wmean_source.c0000664000176700017670000000263011723710247022452 0ustar paulpaul/* statistics/wmean_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION (gsl_stats, wmean) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t size) { /* Compute the weighted arithmetic mean M of a dataset using the recurrence relation M(n) = M(n-1) + (data[n] - M(n-1)) (w(n)/(W(n-1) + w(n))) W(n) = W(n-1) + w(n) */ long double wmean = 0; long double W = 0; size_t i; for (i = 0; i < size; i++) { BASE wi = w[i * wstride]; if (wi > 0) { W += wi; wmean += (data[i * stride] - wmean) * (wi / W); } } return wmean; } sources_5316/external/gsl/gsl_integration__qpsrt2.c0000664000176700017670000000371211723710247021351 0ustar paulpaul/* integration/qpsrt2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* The smallest interval has the largest error. Before bisecting decrease the sum of the errors over the larger intervals (error_over_large_intervals) and perform extrapolation. */ static int increase_nrmax (gsl_integration_workspace * workspace); static int increase_nrmax (gsl_integration_workspace * workspace) { int k; int id = workspace->nrmax; int jupbnd; const size_t * level = workspace->level; const size_t * order = workspace->order; size_t limit = workspace->limit ; size_t last = workspace->size - 1 ; if (last > (1 + limit / 2)) { jupbnd = limit + 1 - last; } else { jupbnd = last; } for (k = id; k <= jupbnd; k++) { size_t i_max = order[workspace->nrmax]; workspace->i = i_max ; if (level[i_max] < workspace->maximum_level) { return 1; } workspace->nrmax++; } return 0; } static int large_interval (gsl_integration_workspace * workspace) { size_t i = workspace->i ; const size_t * level = workspace->level; if (level[i] < workspace->maximum_level) { return 1 ; } else { return 0 ; } } sources_5316/external/gsl/gsl_rng__rng.c0000664000176700017670000001043511723710247017147 0ustar paulpaul/* rng/rng.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include "gsl_errno.h" #include "gsl_rng.h" gsl_rng * gsl_rng_alloc (const gsl_rng_type * T) { gsl_rng *r = (gsl_rng *) malloc (sizeof (gsl_rng)); if (r == 0) { GSL_ERROR_VAL ("failed to allocate space for rng struct", GSL_ENOMEM, 0); }; r->state = malloc (T->size); if (r->state == 0) { free (r); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for rng state", GSL_ENOMEM, 0); }; r->type = T; gsl_rng_set (r, gsl_rng_default_seed); /* seed the generator */ return r; } int gsl_rng_memcpy (gsl_rng * dest, const gsl_rng * src) { if (dest->type != src->type) { GSL_ERROR ("generators must be of the same type", GSL_EINVAL); } memcpy (dest->state, src->state, src->type->size); return GSL_SUCCESS; } gsl_rng * gsl_rng_clone (const gsl_rng * q) { gsl_rng *r = (gsl_rng *) malloc (sizeof (gsl_rng)); if (r == 0) { GSL_ERROR_VAL ("failed to allocate space for rng struct", GSL_ENOMEM, 0); }; r->state = malloc (q->type->size); if (r->state == 0) { free (r); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for rng state", GSL_ENOMEM, 0); }; r->type = q->type; memcpy (r->state, q->state, q->type->size); return r; } void gsl_rng_set (const gsl_rng * r, unsigned long int seed) { (r->type->set) (r->state, seed); } #ifndef HIDE_INLINE_STATIC unsigned long int gsl_rng_get (const gsl_rng * r) { return (r->type->get) (r->state); } double gsl_rng_uniform (const gsl_rng * r) { return (r->type->get_double) (r->state); } double gsl_rng_uniform_pos (const gsl_rng * r) { double x ; do { x = (r->type->get_double) (r->state) ; } while (x == 0) ; return x ; } /* Note: to avoid integer overflow in (range+1) we work with scale = range/n = (max-min)/n rather than scale=(max-min+1)/n, this reduces efficiency slightly but avoids having to check for the out of range value. Note that range is typically O(2^32) so the addition of 1 is negligible in most usage. */ unsigned long int gsl_rng_uniform_int (const gsl_rng * r, unsigned long int n) { unsigned long int offset = r->type->min; unsigned long int range = r->type->max - offset; unsigned long int scale; unsigned long int k; if (n > range || n == 0) { GSL_ERROR_VAL ("invalid n, either 0 or exceeds maximum value of generator", GSL_EINVAL, 0) ; } scale = range / n; do { k = (((r->type->get) (r->state)) - offset) / scale; } while (k >= n); return k; } #endif unsigned long int gsl_rng_max (const gsl_rng * r) { return r->type->max; } unsigned long int gsl_rng_min (const gsl_rng * r) { return r->type->min; } const char * gsl_rng_name (const gsl_rng * r) { return r->type->name; } size_t gsl_rng_size (const gsl_rng * r) { return r->type->size; } void * gsl_rng_state (const gsl_rng * r) { return r->state; } void gsl_rng_print_state (const gsl_rng * r) { size_t i; unsigned char *p = (unsigned char *) (r->state); const size_t n = r->type->size; for (i = 0; i < n; i++) { /* FIXME: we're assuming that a char is 8 bits */ printf ("%.2x", *(p + i)); } } void gsl_rng_free (gsl_rng * r) { free (r->state); free (r); } sources_5316/external/gsl/gsl_linalg__balancemat.c0000664000176700017670000001155311723710247021132 0ustar paulpaul/* linalg/balance.c * * Copyright (C) 2006 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Balance a general matrix by scaling the rows and columns, so the * new row and column norms are the same order of magnitude. * * B = D^-1 A D * * where D is a diagonal matrix * * This is necessary for the unsymmetric eigenvalue problem since the * calculation can become numerically unstable for unbalanced * matrices. * * See Golub & Van Loan, "Matrix Computations" (3rd ed), Section 7.5.7 * and Wilkinson & Reinsch, "Handbook for Automatic Computation", II/11 p320. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_linalg.h" #define FLOAT_RADIX 2.0 #define FLOAT_RADIX_SQ (FLOAT_RADIX * FLOAT_RADIX) int gsl_linalg_balance_matrix(gsl_matrix * A, gsl_vector * D) { const size_t N = A->size1; if (N != D->size) { GSL_ERROR ("vector must match matrix size", GSL_EBADLEN); } else { double row_norm, col_norm; int not_converged; gsl_vector_view v; /* initialize D to the identity matrix */ gsl_vector_set_all(D, 1.0); not_converged = 1; while (not_converged) { size_t i, j; double g, f, s; not_converged = 0; for (i = 0; i < N; ++i) { row_norm = 0.0; col_norm = 0.0; for (j = 0; j < N; ++j) { if (j != i) { col_norm += fabs(gsl_matrix_get(A, j, i)); row_norm += fabs(gsl_matrix_get(A, i, j)); } } if ((col_norm == 0.0) || (row_norm == 0.0)) { continue; } g = row_norm / FLOAT_RADIX; f = 1.0; s = col_norm + row_norm; /* * find the integer power of the machine radix which * comes closest to balancing the matrix */ while (col_norm < g) { f *= FLOAT_RADIX; col_norm *= FLOAT_RADIX_SQ; } g = row_norm * FLOAT_RADIX; while (col_norm > g) { f /= FLOAT_RADIX; col_norm /= FLOAT_RADIX_SQ; } if ((row_norm + col_norm) < 0.95 * s * f) { not_converged = 1; g = 1.0 / f; /* * apply similarity transformation D, where * D_{ij} = f_i * delta_{ij} */ /* multiply by D^{-1} on the left */ v = gsl_matrix_row(A, i); gsl_blas_dscal(g, &v.vector); /* multiply by D on the right */ v = gsl_matrix_column(A, i); gsl_blas_dscal(f, &v.vector); /* keep track of transformation */ gsl_vector_set(D, i, gsl_vector_get(D, i) * f); } } } return GSL_SUCCESS; } } /* gsl_linalg_balance_matrix() */ /* gsl_linalg_balance_accum() Accumulate a balancing transformation into a matrix. This is used during the computation of Schur vectors since the Schur vectors computed are the vectors for the balanced matrix. We must at some point accumulate the balancing transformation into the Schur vector matrix to get the vectors for the original matrix. A -> D A where D is the diagonal matrix Inputs: A - matrix to transform D - vector containing diagonal elements of D */ int gsl_linalg_balance_accum(gsl_matrix *A, gsl_vector *D) { const size_t N = A->size1; if (N != D->size) { GSL_ERROR ("vector must match matrix size", GSL_EBADLEN); } else { size_t i; double s; gsl_vector_view r; for (i = 0; i < N; ++i) { s = gsl_vector_get(D, i); r = gsl_matrix_row(A, i); gsl_blas_dscal(s, &r.vector); } return GSL_SUCCESS; } } /* gsl_linalg_balance_accum() */ sources_5316/external/gsl/gsl_vector__reim_source.c0000664000176700017670000000323211723710247021406 0ustar paulpaul/* vector/reim_source.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ QUALIFIED_REAL_VIEW(_gsl_vector, view) FUNCTION(gsl_vector, real) (QUALIFIED_TYPE(gsl_vector) * v) { REAL_TYPE(gsl_vector) s = NULL_VECTOR; s.data = v->data; s.size = v->size; s.stride = MULTIPLICITY * v->stride; s.block = 0; /* FIXME: should be v->block, but cannot point to block of different type */ s.owner = 0; { QUALIFIED_REAL_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; view.vector = s; return view; } } QUALIFIED_REAL_VIEW(_gsl_vector, view) FUNCTION(gsl_vector, imag) (QUALIFIED_TYPE(gsl_vector) * v) { REAL_TYPE(gsl_vector) s = NULL_VECTOR; s.data = v->data + 1; s.size = v->size; s.stride = MULTIPLICITY * v->stride; s.block = 0; /* FIXME: cannot point to block of different type */ s.owner = 0; { QUALIFIED_REAL_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; view.vector = s; return view; } } sources_5316/external/gsl/gsl_fft__c_init.c0000664000176700017670000001120711723710247017615 0ustar paulpaul/* fft/c_init.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ TYPE(gsl_fft_complex_wavetable) * FUNCTION(gsl_fft_complex_wavetable,alloc) (size_t n) { int status ; size_t i; size_t n_factors; size_t t, product, product_1, q; double d_theta; TYPE(gsl_fft_complex_wavetable) * wavetable ; if (n == 0) { GSL_ERROR_VAL ("length n must be positive integer", GSL_EDOM, 0); } wavetable = (TYPE(gsl_fft_complex_wavetable) *) malloc(sizeof(TYPE(gsl_fft_complex_wavetable))); if (wavetable == NULL) { GSL_ERROR_VAL ("failed to allocate struct", GSL_ENOMEM, 0); } wavetable->trig = (TYPE(gsl_complex) *) malloc (n * sizeof (TYPE(gsl_complex))); if (wavetable->trig == NULL) { free(wavetable) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate trigonometric lookup table", GSL_ENOMEM, 0); } wavetable->n = n ; status = fft_complex_factorize (n, &n_factors, wavetable->factor); if (status) { /* exception in constructor, avoid memory leak */ free (wavetable->trig); free (wavetable); GSL_ERROR_VAL ("factorization failed", GSL_EFACTOR, 0); }; wavetable->nf = n_factors; d_theta = -2.0 * M_PI / ((double) n); t = 0; product = 1; for (i = 0; i < n_factors; i++) { size_t j; const size_t factor = wavetable->factor[i]; wavetable->twiddle[i] = wavetable->trig + t; product_1 = product; /* product_1 = p_(i-1) */ product *= factor; q = n / product; for (j = 1; j < factor; j++) { size_t k; size_t m = 0; for (k = 1; k <= q; k++) { double theta; m = m + j * product_1; m = m % n; theta = d_theta * m; /* d_theta*j*k*p_(i-1) */ GSL_REAL(wavetable->trig[t]) = cos (theta); GSL_IMAG(wavetable->trig[t]) = sin (theta); t++; } } } if (t > n) { /* exception in constructor, avoid memory leak */ free (wavetable->trig); free (wavetable); GSL_ERROR_VAL ("overflowed trigonometric lookup table", GSL_ESANITY, 0); } return wavetable; } TYPE(gsl_fft_complex_workspace) * FUNCTION(gsl_fft_complex_workspace,alloc) (size_t n) { TYPE(gsl_fft_complex_workspace) * workspace ; if (n == 0) { GSL_ERROR_VAL ("length n must be positive integer", GSL_EDOM, 0); } workspace = (TYPE(gsl_fft_complex_workspace) *) malloc(sizeof(TYPE(gsl_fft_complex_workspace))); if (workspace == NULL) { GSL_ERROR_VAL ("failed to allocate struct", GSL_ENOMEM, 0); } workspace->n = n ; workspace->scratch = (BASE *) malloc (2 * n * sizeof (BASE)); if (workspace->scratch == NULL) { free(workspace) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate scratch space", GSL_ENOMEM, 0); } return workspace; } void FUNCTION(gsl_fft_complex_wavetable,free) (TYPE(gsl_fft_complex_wavetable) * wavetable) { /* release trigonometric lookup tables */ free (wavetable->trig); wavetable->trig = NULL; free (wavetable) ; } void FUNCTION(gsl_fft_complex_workspace,free) (TYPE(gsl_fft_complex_workspace) * workspace) { /* release scratch space */ free (workspace->scratch); workspace->scratch = NULL; free (workspace) ; } int FUNCTION(gsl_fft_complex,memcpy) (TYPE(gsl_fft_complex_wavetable) * dest, TYPE(gsl_fft_complex_wavetable) * src) { int i, n, nf ; if (dest->n != src->n) { GSL_ERROR ("length of src and dest do not match", GSL_EINVAL); } n = dest->n ; nf = dest->nf ; memcpy(dest->trig, src->trig, n * sizeof (double)) ; for (i = 0 ; i < nf ; i++) { dest->twiddle[i] = dest->trig + (src->twiddle[i] - src->trig) ; } return 0 ; } sources_5316/external/gsl/gsl_cblas__drotmg.c0000664000176700017670000000035011723710247020146 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_drotmg (double *d1, double *d2, double *b1, const double b2, double *P) { #define BASE double #include "gsl_cblas__source_rotmg.h" #undef BASE } sources_5316/external/gsl/gsl_randist__dirichlet.c0000664000176700017670000000774211723710247021215 0ustar paulpaul/* randist/dirichlet.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 2002 Gavin E. Crooks * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_randist.h" #include "gsl_sf_gamma.h" /* The Dirichlet probability distribution of order K-1 is p(\theta_1,...,\theta_K) d\theta_1 ... d\theta_K = (1/Z) \prod_i=1,K \theta_i^{alpha_i - 1} \delta(1 -\sum_i=1,K \theta_i) The normalization factor Z can be expressed in terms of gamma functions: Z = {\prod_i=1,K \Gamma(\alpha_i)} / {\Gamma( \sum_i=1,K \alpha_i)} The K constants, \alpha_1,...,\alpha_K, must be positive. The K parameters, \theta_1,...,\theta_K are nonnegative and sum to 1. The random variates are generated by sampling K values from gamma distributions with parameters a=\alpha_i, b=1, and renormalizing. See A.M. Law, W.D. Kelton, Simulation Modeling and Analysis (1991). Gavin E. Crooks (2002) */ static void ran_dirichlet_small (const gsl_rng * r, const size_t K, const double alpha[], double theta[]); void gsl_ran_dirichlet (const gsl_rng * r, const size_t K, const double alpha[], double theta[]) { size_t i; double norm = 0.0; for (i = 0; i < K; i++) { theta[i] = gsl_ran_gamma (r, alpha[i], 1.0); } for (i = 0; i < K; i++) { norm += theta[i]; } if (norm < GSL_SQRT_DBL_MIN) /* Handle underflow */ { ran_dirichlet_small (r, K, alpha, theta); return; } for (i = 0; i < K; i++) { theta[i] /= norm; } } /* When the values of alpha[] are small, scale the variates to avoid underflow so that the result is not 0/0. Note that the Dirichlet distribution is defined by a ratio of gamma functions so we can take out an arbitrary factor to keep the values in the range of double precision. */ static void ran_dirichlet_small (const gsl_rng * r, const size_t K, const double alpha[], double theta[]) { size_t i; double norm = 0.0, umax = 0; for (i = 0; i < K; i++) { double u = log(gsl_rng_uniform_pos (r)) / alpha[i]; theta[i] = u; if (u > umax || i == 0) { umax = u; } } for (i = 0; i < K; i++) { theta[i] = exp(theta[i] - umax); } for (i = 0; i < K; i++) { theta[i] = theta[i] * gsl_ran_gamma (r, alpha[i] + 1.0, 1.0); } for (i = 0; i < K; i++) { norm += theta[i]; } for (i = 0; i < K; i++) { theta[i] /= norm; } } double gsl_ran_dirichlet_pdf (const size_t K, const double alpha[], const double theta[]) { return exp (gsl_ran_dirichlet_lnpdf (K, alpha, theta)); } double gsl_ran_dirichlet_lnpdf (const size_t K, const double alpha[], const double theta[]) { /*We calculate the log of the pdf to minimize the possibility of overflow */ size_t i; double log_p = 0.0; double sum_alpha = 0.0; for (i = 0; i < K; i++) { log_p += (alpha[i] - 1.0) * log (theta[i]); } for (i = 0; i < K; i++) { sum_alpha += alpha[i]; } log_p += gsl_sf_lngamma (sum_alpha); for (i = 0; i < K; i++) { log_p -= gsl_sf_lngamma (alpha[i]); } return log_p; } sources_5316/external/gsl/gsl_cblas__dspmv.c0000664000176700017670000000061111723710247020003 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dspmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *Ap, const double *X, const int incX, const double beta, double *Y, const int incY) { #define BASE double #include "gsl_cblas__source_spmv.h" #undef BASE } sources_5316/external/gsl/gsl_cdf__weibullinv.c0000664000176700017670000000252611723710247020511 0ustar paulpaul/* cdf/weibullinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_weibull_Pinv (const double P, const double a, const double b) { double x; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return 0.0; } x = a * pow(-log1p(-P), 1/b); return x; } double gsl_cdf_weibull_Qinv (const double Q, const double a, const double b) { double x; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return 0.0; } x = a * pow(-log(Q), 1/b); return x; } sources_5316/external/gsl/gsl_ieee-utils__fp-openbsd.c0000664000176700017670000000574111723710247021701 0ustar paulpaul/* fp-openbsd.c * * Copyright (C) 2001 Jason Beegan * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" /* This is a copy of fp-netbsd.c, modified for openbsd by Toby White --- Brian Gough */ int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { fp_except mode = 0; fp_rnd rnd = 0; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("OpenBSD only supports default precision rounding", GSL_EUNSUP); break; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("OpenBSD only supports default precision rounding", GSL_EUNSUP); break; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("OpenBSD only supports default precision rounding", GSL_EUNSUP); break; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: rnd = FP_RN; fpsetround (rnd); break; case GSL_IEEE_ROUND_DOWN: rnd = FP_RM; fpsetround (rnd); break; case GSL_IEEE_ROUND_UP: rnd = FP_RP; fpsetround (rnd); break; case GSL_IEEE_ROUND_TO_ZERO: rnd = FP_RZ; fpsetround (rnd); break; default: rnd = FP_RN; fpsetround (rnd); } /* Turn on all available exceptions apart from 'inexact'. Denormalized operand exception not available on all platforms. */ mode = FP_X_INV | FP_X_DZ | FP_X_OFL | FP_X_UFL; #ifdef FP_X_DNML mode = mode | FP_X_DNML; #endif if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ FP_X_INV; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { #ifdef FP_X_DNML mode &= ~ FP_X_DNML; #endif } else { #ifndef FP_X_DNML GSL_ERROR ("OpenBSD does not support the denormalized operand exception on this platform. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP); #endif } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ FP_X_DZ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ FP_X_OFL; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ FP_X_UFL; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode |= FP_X_IMP; } else { mode &= ~ FP_X_IMP; } fpsetmask (mode); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__zherk.c0000664000176700017670000000064011723710247017777 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zherk (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const double alpha, const void *A, const int lda, const double beta, void *C, const int ldc) { #define BASE double #include "gsl_cblas__source_herk.h" #undef BASE } sources_5316/external/gsl/gsl_randist__geometric.c0000664000176700017670000000312511723710247021213 0ustar paulpaul/* randist/geometric.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* Geometric distribution (bernoulli trial with probability p) prob(k) = p (1 - p)^(k-1) for n = 1, 2, 3, ... It gives the distribution of "waiting times" for an event that occurs with probability p. */ unsigned int gsl_ran_geometric (const gsl_rng * r, const double p) { double u = gsl_rng_uniform_pos (r); unsigned int k; if (p == 1) { k = 1; } else { k = log (u) / log (1 - p) + 1; } return k; } double gsl_ran_geometric_pdf (const unsigned int k, const double p) { if (k == 0) { return 0 ; } else if (k == 1) { return p ; } else { double P = p * pow (1 - p, k - 1.0); return P; } } sources_5316/external/gsl/gsl_statistics_long_double.h0000664000176700017670000001557011705263724022134 0ustar paulpaul/* statistics/gsl_statistics_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_LONG_DOUBLE_H__ #define __GSL_STATISTICS_LONG_DOUBLE_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_long_double_mean (const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_variance (const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_sd (const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_variance_with_fixed_mean (const long double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_double_sd_with_fixed_mean (const long double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_double_absdev (const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_skew (const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_kurtosis (const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_lag1_autocorrelation (const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_covariance (const long double data1[], const size_t stride1,const long double data2[], const size_t stride2, const size_t n); double gsl_stats_long_double_correlation (const long double data1[], const size_t stride1,const long double data2[], const size_t stride2, const size_t n); double gsl_stats_long_double_variance_m (const long double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_double_sd_m (const long double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_double_absdev_m (const long double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_double_skew_m_sd (const long double data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_long_double_kurtosis_m_sd (const long double data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_long_double_lag1_autocorrelation_m (const long double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_double_covariance_m (const long double data1[], const size_t stride1,const long double data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); /* DEFINED FOR FLOATING POINT TYPES ONLY */ double gsl_stats_long_double_wmean (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_wvariance (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_wsd (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_wvariance_with_fixed_mean (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_double_wsd_with_fixed_mean (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_double_wabsdev (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_wskew (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_wkurtosis (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_wvariance_m (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n, const double wmean); double gsl_stats_long_double_wsd_m (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n, const double wmean); double gsl_stats_long_double_wabsdev_m (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n, const double wmean); double gsl_stats_long_double_wskew_m_sd (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n, const double wmean, const double wsd); double gsl_stats_long_double_wkurtosis_m_sd (const long double w[], const size_t wstride, const long double data[], const size_t stride, const size_t n, const double wmean, const double wsd); /* END OF FLOATING POINT TYPES */ double gsl_stats_long_double_pvariance (const long double data1[], const size_t stride1, const size_t n1, const long double data2[], const size_t stride2, const size_t n2); double gsl_stats_long_double_ttest (const long double data1[], const size_t stride1, const size_t n1, const long double data2[], const size_t stride2, const size_t n2); long double gsl_stats_long_double_max (const long double data[], const size_t stride, const size_t n); long double gsl_stats_long_double_min (const long double data[], const size_t stride, const size_t n); void gsl_stats_long_double_minmax (long double * min, long double * max, const long double data[], const size_t stride, const size_t n); size_t gsl_stats_long_double_max_index (const long double data[], const size_t stride, const size_t n); size_t gsl_stats_long_double_min_index (const long double data[], const size_t stride, const size_t n); void gsl_stats_long_double_minmax_index (size_t * min_index, size_t * max_index, const long double data[], const size_t stride, const size_t n); double gsl_stats_long_double_median_from_sorted_data (const long double sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_long_double_quantile_from_sorted_data (const long double sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_specfunc__legendre_con.c0000664000176700017670000012435211723710247022031 0ustar paulpaul/* specfunc/legendre_con.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_poly.h" #include "gsl_sf_exp.h" #include "gsl_sf_trig.h" #include "gsl_sf_gamma.h" #include "gsl_sf_ellint.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_bessel.h" #include "gsl_sf_hyperg.h" #include "gsl_sf_legendre.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__legendre.h" #define Root_2OverPi_ 0.797884560802865355879892 #define locEPS (1000.0*GSL_DBL_EPSILON) /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ #define RECURSE_LARGE (1.0e-5*GSL_DBL_MAX) #define RECURSE_SMALL (1.0e+5*GSL_DBL_MIN) /* Continued fraction for f_{ell+1}/f_ell * f_ell := P^{-mu-ell}_{-1/2 + I tau}(x), x < 1.0 * * Uses standard CF method from Temme's book. */ static int conicalP_negmu_xlt1_CF1(const double mu, const int ell, const double tau, const double x, gsl_sf_result * result) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 5000; int n = 1; double xi = x/(sqrt(1.0-x)*sqrt(1.0+x)); double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = 1.0; double b1 = 2.0*(mu + ell + 1.0) * xi; double An = b1*Anm1 + a1*Anm2; double Bn = b1*Bnm1 + a1*Bnm2; double an, bn; double fn = An/Bn; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = tau*tau + (mu - 0.5 + ell + n)*(mu - 0.5 + ell + n); bn = 2.0*(ell + mu + n) * xi; An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 2.0*GSL_DBL_EPSILON) break; } result->val = fn; result->err = 4.0 * GSL_DBL_EPSILON * (sqrt(n) + 1.0) * fabs(fn); if(n >= maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /* Continued fraction for f_{ell+1}/f_ell * f_ell := P^{-mu-ell}_{-1/2 + I tau}(x), x >= 1.0 * * Uses Gautschi (Euler) equivalent series. */ static int conicalP_negmu_xgt1_CF1(const double mu, const int ell, const double tau, const double x, gsl_sf_result * result) { const int maxk = 20000; const double gamma = 1.0-1.0/(x*x); const double pre = sqrt(x-1.0)*sqrt(x+1.0) / (x*(2.0*(ell+mu+1.0))); double tk = 1.0; double sum = 1.0; double rhok = 0.0; int k; for(k=1; kval = pre * sum; result->err = fabs(pre * tk); result->err += 2.0 * GSL_DBL_EPSILON * (sqrt(k) + 1.0) * fabs(pre*sum); if(k >= maxk) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /* Implementation of large negative mu asymptotic * [Dunster, Proc. Roy. Soc. Edinburgh 119A, 311 (1991), p. 326] */ inline static double olver_U1(double beta2, double p) { return (p-1.0)/(24.0*(1.0+beta2)) * (3.0 + beta2*(2.0 + 5.0*p*(1.0+p))); } inline static double olver_U2(double beta2, double p) { double beta4 = beta2*beta2; double p2 = p*p; double poly1 = 4.0*beta4 + 84.0*beta2 - 63.0; double poly2 = 16.0*beta4 + 90.0*beta2 - 81.0; double poly3 = beta2*p2*(97.0*beta2 - 432.0 + 77.0*p*(beta2-6.0) - 385.0*beta2*p2*(1.0 + p)); return (1.0-p)/(1152.0*(1.0+beta2)) * (poly1 + poly2 + poly3); } static const double U3c1[] = { -1307.0, -1647.0, 3375.0, 3675.0 }; static const double U3c2[] = { 29366.0, 35835.0, -252360.0, -272630.0, 276810.0, 290499.0 }; static const double U3c3[] = { -29748.0, -8840.0, 1725295.0, 1767025.0, -7313470.0, -754778.0, 6309875.0, 6480045.0 }; static const double U3c4[] = { 2696.0, -16740.0, -524250.0, -183975.0, 14670540.0, 14172939.0, -48206730.0, -48461985.0, 36756720.0, 37182145.0 }; static const double U3c5[] = { 9136.0, 22480.0, 12760.0, -252480.0, -4662165.0, -1705341.0, 92370135.0, 86244015.0, -263678415.0, -260275015.0, 185910725.0, 185910725.0 }; #if 0 static double olver_U3(double beta2, double p) { double beta4 = beta2*beta2; double beta6 = beta4*beta2; double opb2s = (1.0+beta2)*(1.0+beta2); double den = 39813120.0 * opb2s*opb2s; double poly1 = gsl_poly_eval(U3c1, 4, p); double poly2 = gsl_poly_eval(U3c2, 6, p); double poly3 = gsl_poly_eval(U3c3, 8, p); double poly4 = gsl_poly_eval(U3c4, 10, p); double poly5 = gsl_poly_eval(U3c5, 12, p); return (p-1.0)*( 1215.0*poly1 + 324.0*beta2*poly2 + 54.0*beta4*poly3 + 12.0*beta6*poly4 + beta4*beta4*poly5 ) / den; } #endif /* 0 */ /* Large negative mu asymptotic * P^{-mu}_{-1/2 + I tau}, mu -> Inf * |x| < 1 * * [Dunster, Proc. Roy. Soc. Edinburgh 119A, 311 (1991), p. 326] */ int gsl_sf_conicalP_xlt1_large_neg_mu_e(double mu, double tau, double x, gsl_sf_result * result, double * ln_multiplier) { double beta = tau/mu; double beta2 = beta*beta; double S = beta * acos((1.0-beta2)/(1.0+beta2)); double p = x/sqrt(beta2*(1.0-x*x) + 1.0); gsl_sf_result lg_mup1; int lg_stat = gsl_sf_lngamma_e(mu+1.0, &lg_mup1); double ln_pre_1 = 0.5*mu*(S - log(1.0+beta2) + log((1.0-p)/(1.0+p))) - lg_mup1.val; double ln_pre_2 = -0.25 * log(1.0 + beta2*(1.0-x)); double ln_pre_3 = -tau * atan(p*beta); double ln_pre = ln_pre_1 + ln_pre_2 + ln_pre_3; double sum = 1.0 - olver_U1(beta2, p)/mu + olver_U2(beta2, p)/(mu*mu); if(sum == 0.0) { result->val = 0.0; result->err = 0.0; *ln_multiplier = 0.0; return GSL_SUCCESS; } else { int stat_e = gsl_sf_exp_mult_e(ln_pre, sum, result); if(stat_e != GSL_SUCCESS) { result->val = sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(sum); *ln_multiplier = ln_pre; } else { *ln_multiplier = 0.0; } return lg_stat; } } /* Implementation of large tau asymptotic * * A_n^{-mu}, B_n^{-mu} [Olver, p.465, 469] */ inline static double olver_B0_xi(double mu, double xi) { return (1.0 - 4.0*mu*mu)/(8.0*xi) * (1.0/tanh(xi) - 1.0/xi); } static double olver_A1_xi(double mu, double xi, double x) { double B = olver_B0_xi(mu, xi); double psi; if(fabs(x - 1.0) < GSL_ROOT4_DBL_EPSILON) { double y = x - 1.0; double s = -1.0/3.0 + y*(2.0/15.0 - y *(61.0/945.0 - 452.0/14175.0*y)); psi = (4.0*mu*mu - 1.0)/16.0 * s; } else { psi = (4.0*mu*mu - 1.0)/16.0 * (1.0/(x*x-1.0) - 1.0/(xi*xi)); } return 0.5*xi*xi*B*B + (mu+0.5)*B - psi + mu/6.0*(0.25 - mu*mu); } inline static double olver_B0_th(double mu, double theta) { return -(1.0 - 4.0*mu*mu)/(8.0*theta) * (1.0/tan(theta) - 1.0/theta); } static double olver_A1_th(double mu, double theta, double x) { double B = olver_B0_th(mu, theta); double psi; if(fabs(x - 1.0) < GSL_ROOT4_DBL_EPSILON) { double y = 1.0 - x; double s = -1.0/3.0 + y*(2.0/15.0 - y *(61.0/945.0 - 452.0/14175.0*y)); psi = (4.0*mu*mu - 1.0)/16.0 * s; } else { psi = (4.0*mu*mu - 1.0)/16.0 * (1.0/(x*x-1.0) + 1.0/(theta*theta)); } return -0.5*theta*theta*B*B + (mu+0.5)*B - psi + mu/6.0*(0.25 - mu*mu); } /* Large tau uniform asymptotics * P^{-mu}_{-1/2 + I tau} * 1 < x * tau -> Inf * [Olver, p. 469] */ int gsl_sf_conicalP_xgt1_neg_mu_largetau_e(const double mu, const double tau, const double x, double acosh_x, gsl_sf_result * result, double * ln_multiplier) { double xi = acosh_x; double ln_xi_pre; double ln_pre; double sumA, sumB, sum; double arg; gsl_sf_result J_mup1; gsl_sf_result J_mu; double J_mum1; if(xi < GSL_ROOT4_DBL_EPSILON) { ln_xi_pre = -xi*xi/6.0; /* log(1.0 - xi*xi/6.0) */ } else { gsl_sf_result lnshxi; gsl_sf_lnsinh_e(xi, &lnshxi); ln_xi_pre = log(xi) - lnshxi.val; /* log(xi/sinh(xi) */ } ln_pre = 0.5*ln_xi_pre - mu*log(tau); arg = tau*xi; gsl_sf_bessel_Jnu_e(mu + 1.0, arg, &J_mup1); gsl_sf_bessel_Jnu_e(mu, arg, &J_mu); J_mum1 = -J_mup1.val + 2.0*mu/arg*J_mu.val; /* careful of mu < 1 */ sumA = 1.0 - olver_A1_xi(-mu, xi, x)/(tau*tau); sumB = olver_B0_xi(-mu, xi); sum = J_mu.val * sumA - xi/tau * J_mum1 * sumB; if(sum == 0.0) { result->val = 0.0; result->err = 0.0; *ln_multiplier = 0.0; return GSL_SUCCESS; } else { int stat_e = gsl_sf_exp_mult_e(ln_pre, sum, result); if(stat_e != GSL_SUCCESS) { result->val = sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(sum); *ln_multiplier = ln_pre; } else { *ln_multiplier = 0.0; } return GSL_SUCCESS; } } /* Large tau uniform asymptotics * P^{-mu}_{-1/2 + I tau} * -1 < x < 1 * tau -> Inf * [Olver, p. 473] */ int gsl_sf_conicalP_xlt1_neg_mu_largetau_e(const double mu, const double tau, const double x, const double acos_x, gsl_sf_result * result, double * ln_multiplier) { double theta = acos_x; double ln_th_pre; double ln_pre; double sumA, sumB, sum, sumerr; double arg; gsl_sf_result I_mup1, I_mu; double I_mum1; if(theta < GSL_ROOT4_DBL_EPSILON) { ln_th_pre = theta*theta/6.0; /* log(1.0 + theta*theta/6.0) */ } else { ln_th_pre = log(theta/sin(theta)); } ln_pre = 0.5 * ln_th_pre - mu * log(tau); arg = tau*theta; gsl_sf_bessel_Inu_e(mu + 1.0, arg, &I_mup1); gsl_sf_bessel_Inu_e(mu, arg, &I_mu); I_mum1 = I_mup1.val + 2.0*mu/arg * I_mu.val; /* careful of mu < 1 */ sumA = 1.0 - olver_A1_th(-mu, theta, x)/(tau*tau); sumB = olver_B0_th(-mu, theta); sum = I_mu.val * sumA - theta/tau * I_mum1 * sumB; sumerr = fabs(I_mu.err * sumA); sumerr += fabs(I_mup1.err * theta/tau * sumB); sumerr += fabs(I_mu.err * theta/tau * sumB * 2.0 * mu/arg); if(sum == 0.0) { result->val = 0.0; result->err = 0.0; *ln_multiplier = 0.0; return GSL_SUCCESS; } else { int stat_e = gsl_sf_exp_mult_e(ln_pre, sum, result); if(stat_e != GSL_SUCCESS) { result->val = sum; result->err = sumerr; result->err += GSL_DBL_EPSILON * fabs(sum); *ln_multiplier = ln_pre; } else { *ln_multiplier = 0.0; } return GSL_SUCCESS; } } /* Hypergeometric function which appears in the * large x expansion below: * * 2F1(1/4 - mu/2 - I tau/2, 3/4 - mu/2 - I tau/2, 1 - I tau, y) * * Note that for the usage below y = 1/x^2; */ static int conicalP_hyperg_large_x(const double mu, const double tau, const double y, double * reF, double * imF) { const int kmax = 1000; const double re_a = 0.25 - 0.5*mu; const double re_b = 0.75 - 0.5*mu; const double re_c = 1.0; const double im_a = -0.5*tau; const double im_b = -0.5*tau; const double im_c = -tau; double re_sum = 1.0; double im_sum = 0.0; double re_term = 1.0; double im_term = 0.0; int k; for(k=1; k<=kmax; k++) { double re_ak = re_a + k - 1.0; double re_bk = re_b + k - 1.0; double re_ck = re_c + k - 1.0; double im_ak = im_a; double im_bk = im_b; double im_ck = im_c; double den = re_ck*re_ck + im_ck*im_ck; double re_multiplier = ((re_ak*re_bk - im_ak*im_bk)*re_ck + im_ck*(im_ak*re_bk + re_ak*im_bk)) / den; double im_multiplier = ((im_ak*re_bk + re_ak*im_bk)*re_ck - im_ck*(re_ak*re_bk - im_ak*im_bk)) / den; double re_tmp = re_multiplier*re_term - im_multiplier*im_term; double im_tmp = im_multiplier*re_term + re_multiplier*im_term; double asum = fabs(re_sum) + fabs(im_sum); re_term = y/k * re_tmp; im_term = y/k * im_tmp; if(fabs(re_term/asum) < GSL_DBL_EPSILON && fabs(im_term/asum) < GSL_DBL_EPSILON) break; re_sum += re_term; im_sum += im_term; } *reF = re_sum; *imF = im_sum; if(k == kmax) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /* P^{mu}_{-1/2 + I tau} * x->Inf */ int gsl_sf_conicalP_large_x_e(const double mu, const double tau, const double x, gsl_sf_result * result, double * ln_multiplier) { /* 2F1 term */ double y = ( x < 0.5*GSL_SQRT_DBL_MAX ? 1.0/(x*x) : 0.0 ); double reF, imF; int stat_F = conicalP_hyperg_large_x(mu, tau, y, &reF, &imF); /* f = Gamma(+i tau)/Gamma(1/2 - mu + i tau) * FIXME: shift so it's better for tau-> 0 */ gsl_sf_result lgr_num, lgth_num; gsl_sf_result lgr_den, lgth_den; int stat_gn = gsl_sf_lngamma_complex_e(0.0,tau,&lgr_num,&lgth_num); int stat_gd = gsl_sf_lngamma_complex_e(0.5-mu,tau,&lgr_den,&lgth_den); double angle = lgth_num.val - lgth_den.val + atan2(imF,reF); double lnx = log(x); double lnxp1 = log(x+1.0); double lnxm1 = log(x-1.0); double lnpre_const = 0.5*M_LN2 - 0.5*M_LNPI; double lnpre_comm = (mu-0.5)*lnx - 0.5*mu*(lnxp1 + lnxm1); double lnpre_err = GSL_DBL_EPSILON * (0.5*M_LN2 + 0.5*M_LNPI) + GSL_DBL_EPSILON * fabs((mu-0.5)*lnx) + GSL_DBL_EPSILON * fabs(0.5*mu)*(fabs(lnxp1)+fabs(lnxm1)); /* result = pre*|F|*|f| * cos(angle - tau * (log(x)+M_LN2)) */ gsl_sf_result cos_result; int stat_cos = gsl_sf_cos_e(angle + tau*(log(x) + M_LN2), &cos_result); int status = GSL_ERROR_SELECT_4(stat_cos, stat_gd, stat_gn, stat_F); if(cos_result.val == 0.0) { result->val = 0.0; result->err = 0.0; return status; } else { double lnFf_val = 0.5*log(reF*reF+imF*imF) + lgr_num.val - lgr_den.val; double lnFf_err = lgr_num.err + lgr_den.err + GSL_DBL_EPSILON * fabs(lnFf_val); double lnnoc_val = lnpre_const + lnpre_comm + lnFf_val; double lnnoc_err = lnpre_err + lnFf_err + GSL_DBL_EPSILON * fabs(lnnoc_val); int stat_e = gsl_sf_exp_mult_err_e(lnnoc_val, lnnoc_err, cos_result.val, cos_result.err, result); if(stat_e == GSL_SUCCESS) { *ln_multiplier = 0.0; } else { result->val = cos_result.val; result->err = cos_result.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *ln_multiplier = lnnoc_val; } return status; } } /* P^{mu}_{-1/2 + I tau} first hypergeometric representation * -1 < x < 1 * This is more effective for |x| small, however it will work w/o * reservation for any x < 0 because everything is positive * definite in that case. * * [Kolbig, (3)] (note typo in args of gamma functions) * [Bateman, (22)] (correct form) */ static int conicalP_xlt1_hyperg_A(double mu, double tau, double x, gsl_sf_result * result) { double x2 = x*x; double err_amp = 1.0 + 1.0/(GSL_DBL_EPSILON + fabs(1.0-fabs(x))); double pre_val = M_SQRTPI / pow(0.5*sqrt(1-x2), mu); double pre_err = err_amp * GSL_DBL_EPSILON * (fabs(mu)+1.0) * fabs(pre_val) ; gsl_sf_result ln_g1, ln_g2, arg_g1, arg_g2; gsl_sf_result F1, F2; gsl_sf_result pre1, pre2; double t1_val, t1_err; double t2_val, t2_err; int stat_F1 = gsl_sf_hyperg_2F1_conj_e(0.25 - 0.5*mu, 0.5*tau, 0.5, x2, &F1); int stat_F2 = gsl_sf_hyperg_2F1_conj_e(0.75 - 0.5*mu, 0.5*tau, 1.5, x2, &F2); int status = GSL_ERROR_SELECT_2(stat_F1, stat_F2); gsl_sf_lngamma_complex_e(0.75 - 0.5*mu, -0.5*tau, &ln_g1, &arg_g1); gsl_sf_lngamma_complex_e(0.25 - 0.5*mu, -0.5*tau, &ln_g2, &arg_g2); gsl_sf_exp_err_e(-2.0*ln_g1.val, 2.0*ln_g1.err, &pre1); gsl_sf_exp_err_e(-2.0*ln_g2.val, 2.0*ln_g2.err, &pre2); pre2.val *= -2.0*x; pre2.err *= 2.0*fabs(x); pre2.err += GSL_DBL_EPSILON * fabs(pre2.val); t1_val = pre1.val * F1.val; t1_err = fabs(pre1.val) * F1.err + pre1.err * fabs(F1.val); t2_val = pre2.val * F2.val; t2_err = fabs(pre2.val) * F2.err + pre2.err * fabs(F2.val); result->val = pre_val * (t1_val + t2_val); result->err = pre_val * (t1_err + t2_err); result->err += pre_err * fabs(t1_val + t2_val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return status; } /* P^{mu}_{-1/2 + I tau} * defining hypergeometric representation * [Abramowitz+Stegun, 8.1.2] * 1 < x < 3 * effective for x near 1 * */ #if 0 static int conicalP_def_hyperg(double mu, double tau, double x, double * result) { double F; int stat_F = gsl_sf_hyperg_2F1_conj_renorm_e(0.5, tau, 1.0-mu, 0.5*(1.0-x), &F); *result = pow((x+1.0)/(x-1.0), 0.5*mu) * F; return stat_F; } #endif /* 0 */ /* P^{mu}_{-1/2 + I tau} second hypergeometric representation * [Zhurina+Karmazina, (3.1)] * -1 < x < 3 * effective for x near 1 * */ #if 0 static int conicalP_xnear1_hyperg_C(double mu, double tau, double x, double * result) { double ln_pre, arg_pre; double ln_g1, arg_g1; double ln_g2, arg_g2; double F; int stat_F = gsl_sf_hyperg_2F1_conj_renorm_e(0.5+mu, tau, 1.0+mu, 0.5*(1.0-x), &F); gsl_sf_lngamma_complex_e(0.5+mu, tau, &ln_g1, &arg_g1); gsl_sf_lngamma_complex_e(0.5-mu, tau, &ln_g2, &arg_g2); ln_pre = mu*M_LN2 - 0.5*mu*log(fabs(x*x-1.0)) + ln_g1 - ln_g2; arg_pre = arg_g1 - arg_g2; *result = exp(ln_pre) * F; return stat_F; } #endif /* 0 */ /* V0, V1 from Kolbig, m = 0 */ static int conicalP_0_V(const double t, const double f, const double tau, const double sgn, double * V0, double * V1) { double C[8]; double T[8]; double H[8]; double V[12]; int i; T[0] = 1.0; H[0] = 1.0; V[0] = 1.0; for(i=1; i<=7; i++) { T[i] = T[i-1] * t; H[i] = H[i-1] * (t*f); } for(i=1; i<=11; i++) { V[i] = V[i-1] * tau; } C[0] = 1.0; C[1] = (H[1]-1.0)/(8.0*T[1]); C[2] = (9.0*H[2] + 6.0*H[1] - 15.0 - sgn*8.0*T[2])/(128.0*T[2]); C[3] = 5.0*(15.0*H[3] + 27.0*H[2] + 21.0*H[1] - 63.0 - sgn*T[2]*(16.0*H[1]+24.0))/(1024.0*T[3]); C[4] = 7.0*(525.0*H[4] + 1500.0*H[3] + 2430.0*H[2] + 1980.0*H[1] - 6435.0 + 192.0*T[4] - sgn*T[2]*(720.0*H[2]+1600.0*H[1]+2160.0) ) / (32768.0*T[4]); C[5] = 21.0*(2835.0*H[5] + 11025.0*H[4] + 24750.0*H[3] + 38610.0*H[2] + 32175.0*H[1] - 109395.0 + T[4]*(1984.0*H[1]+4032.0) - sgn*T[2]*(4800.0*H[3]+15120.0*H[2]+26400.0*H[1]+34320.0) ) / (262144.0*T[5]); C[6] = 11.0*(218295.0*H[6] + 1071630.0*H[5] + 3009825.0*H[4] + 6142500.0*H[3] + 9398025.0*H[2] + 7936110.0*H[1] - 27776385.0 + T[4]*(254016.0*H[2]+749952.0*H[1]+1100736.0) - sgn*T[2]*(441000.0*H[4] + 1814400.0*H[3] + 4127760.0*H[2] + 6552000.0*H[1] + 8353800.0 + 31232.0*T[4] ) ) / (4194304.0*T[6]); *V0 = C[0] + (-4.0*C[3]/T[1]+C[4])/V[4] + (-192.0*C[5]/T[3]+144.0*C[6]/T[2])/V[8] + sgn * (-C[2]/V[2] + (-24.0*C[4]/T[2]+12.0*C[5]/T[1]-C[6])/V[6] + (-1920.0*C[6]/T[4])/V[10] ); *V1 = C[1]/V[1] + (8.0*(C[3]/T[2]-C[4]/T[1])+C[5])/V[5] + (384.0*C[5]/T[4] - 768.0*C[6]/T[3])/V[9] + sgn * ((2.0*C[2]/T[1]-C[3])/V[3] + (48.0*C[4]/T[3]-72.0*C[5]/T[2] + 18.0*C[6]/T[1])/V[7] + (3840.0*C[6]/T[5])/V[11] ); return GSL_SUCCESS; } /* V0, V1 from Kolbig, m = 1 */ static int conicalP_1_V(const double t, const double f, const double tau, const double sgn, double * V0, double * V1) { double Cm1; double C[8]; double T[8]; double H[8]; double V[12]; int i; T[0] = 1.0; H[0] = 1.0; V[0] = 1.0; for(i=1; i<=7; i++) { T[i] = T[i-1] * t; H[i] = H[i-1] * (t*f); } for(i=1; i<=11; i++) { V[i] = V[i-1] * tau; } Cm1 = -1.0; C[0] = 3.0*(1.0-H[1])/(8.0*T[1]); C[1] = (-15.0*H[2]+6.0*H[1]+9.0+sgn*8.0*T[2])/(128.0*T[2]); C[2] = 3.0*(-35.0*H[3] - 15.0*H[2] + 15.0*H[1] + 35.0 + sgn*T[2]*(32.0*H[1]+8.0))/(1024.0*T[3]); C[3] = (-4725.0*H[4] - 6300.0*H[3] - 3150.0*H[2] + 3780.0*H[1] + 10395.0 -1216.0*T[4] + sgn*T[2]*(6000.0*H[2]+5760.0*H[1]+1680.0)) / (32768.0*T[4]); C[4] = 7.0*(-10395.0*H[5] - 23625.0*H[4] - 28350.0*H[3] - 14850.0*H[2] +19305.0*H[1] + 57915.0 - T[4]*(6336.0*H[1]+6080.0) + sgn*T[2]*(16800.0*H[3] + 30000.0*H[2] + 25920.0*H[1] + 7920.0) ) / (262144.0*T[5]); C[5] = (-2837835.0*H[6] - 9168390.0*H[5] - 16372125.0*H[4] - 18918900*H[3] -10135125.0*H[2] + 13783770.0*H[1] + 43648605.0 -T[4]*(3044160.0*H[2] + 5588352.0*H[1] + 4213440.0) +sgn*T[2]*(5556600.0*H[4] + 14817600.0*H[3] + 20790000.0*H[2] + 17297280.0*H[1] + 5405400.0 + 323072.0*T[4] ) ) / (4194304.0*T[6]); C[6] = 0.0; *V0 = C[0] + (-4.0*C[3]/T[1]+C[4])/V[4] + (-192.0*C[5]/T[3]+144.0*C[6]/T[2])/V[8] + sgn * (-C[2]/V[2] + (-24.0*C[4]/T[2]+12.0*C[5]/T[1]-C[6])/V[6] ); *V1 = C[1]/V[1] + (8.0*(C[3]/T[2]-C[4]/T[1])+C[5])/V[5] + (384.0*C[5]/T[4] - 768.0*C[6]/T[3])/V[9] + sgn * (Cm1*V[1] + (2.0*C[2]/T[1]-C[3])/V[3] + (48.0*C[4]/T[3]-72.0*C[5]/T[2] + 18.0*C[6]/T[1])/V[7] ); return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ /* P^0_{-1/2 + I lambda} */ int gsl_sf_conicalP_0_e(const double lambda, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0) { DOMAIN_ERROR(result); } else if(x == 1.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(lambda == 0.0) { gsl_sf_result K; int stat_K; if(x < 1.0) { const double th = acos(x); const double s = sin(0.5*th); stat_K = gsl_sf_ellint_Kcomp_e(s, GSL_MODE_DEFAULT, &K); result->val = 2.0/M_PI * K.val; result->err = 2.0/M_PI * K.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_K; } else { const double xi = acosh(x); const double c = cosh(0.5*xi); const double t = tanh(0.5*xi); stat_K = gsl_sf_ellint_Kcomp_e(t, GSL_MODE_DEFAULT, &K); result->val = 2.0/M_PI / c * K.val; result->err = 2.0/M_PI / c * K.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_K; } } else if( (x <= 0.0 && lambda < 1000.0) || (x < 0.1 && lambda < 17.0) || (x < 0.2 && lambda < 5.0 ) ) { return conicalP_xlt1_hyperg_A(0.0, lambda, x, result); } else if( (x <= 0.2 && lambda < 17.0) || (x <= 1.5 && lambda < 20.0) ) { return gsl_sf_hyperg_2F1_conj_e(0.5, lambda, 1.0, (1.0-x)/2, result); } else if(1.5 < x && lambda < GSL_MAX(x,20.0)) { gsl_sf_result P; double lm; int stat_P = gsl_sf_conicalP_large_x_e(0.0, lambda, x, &P, &lm ); int stat_e = gsl_sf_exp_mult_err_e(lm, 2.0*GSL_DBL_EPSILON * fabs(lm), P.val, P.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_P); } else { double V0, V1; if(x < 1.0) { double th = acos(x); double sth = sqrt(1.0-x*x); /* sin(th) */ gsl_sf_result I0, I1; int stat_I0 = gsl_sf_bessel_I0_scaled_e(th * lambda, &I0); int stat_I1 = gsl_sf_bessel_I1_scaled_e(th * lambda, &I1); int stat_I = GSL_ERROR_SELECT_2(stat_I0, stat_I1); int stat_V = conicalP_0_V(th, x/sth, lambda, -1.0, &V0, &V1); double bessterm = V0 * I0.val + V1 * I1.val; double besserr = fabs(V0) * I0.err + fabs(V1) * I1.err; double arg1 = th*lambda; double sqts = sqrt(th/sth); int stat_e = gsl_sf_exp_mult_err_e(arg1, 4.0 * GSL_DBL_EPSILON * fabs(arg1), sqts * bessterm, sqts * besserr, result); return GSL_ERROR_SELECT_3(stat_e, stat_V, stat_I); } else { double sh = sqrt(x-1.0)*sqrt(x+1.0); /* sinh(xi) */ double xi = log(x + sh); /* xi = acosh(x) */ gsl_sf_result J0, J1; int stat_J0 = gsl_sf_bessel_J0_e(xi * lambda, &J0); int stat_J1 = gsl_sf_bessel_J1_e(xi * lambda, &J1); int stat_J = GSL_ERROR_SELECT_2(stat_J0, stat_J1); int stat_V = conicalP_0_V(xi, x/sh, lambda, 1.0, &V0, &V1); double bessterm = V0 * J0.val + V1 * J1.val; double besserr = fabs(V0) * J0.err + fabs(V1) * J1.err; double pre_val = sqrt(xi/sh); double pre_err = 2.0 * fabs(pre_val); result->val = pre_val * bessterm; result->err = pre_val * besserr; result->err += pre_err * fabs(bessterm); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_V, stat_J); } } } /* P^1_{-1/2 + I lambda} */ int gsl_sf_conicalP_1_e(const double lambda, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0) { DOMAIN_ERROR(result); } else if(lambda == 0.0) { gsl_sf_result K, E; int stat_K, stat_E; if(x == 1.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 1.0) { if(1.0-x < GSL_SQRT_DBL_EPSILON) { double err_amp = GSL_MAX_DBL(1.0, 1.0/(GSL_DBL_EPSILON + fabs(1.0-x))); result->val = 0.25/M_SQRT2 * sqrt(1.0-x) * (1.0 + 5.0/16.0 * (1.0-x)); result->err = err_amp * 3.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double th = acos(x); const double s = sin(0.5*th); const double c2 = 1.0 - s*s; const double sth = sin(th); const double pre = 2.0/(M_PI*sth); stat_K = gsl_sf_ellint_Kcomp_e(s, GSL_MODE_DEFAULT, &K); stat_E = gsl_sf_ellint_Ecomp_e(s, GSL_MODE_DEFAULT, &E); result->val = pre * (E.val - c2 * K.val); result->err = pre * (E.err + fabs(c2) * K.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_K; } } else { if(x-1.0 < GSL_SQRT_DBL_EPSILON) { double err_amp = GSL_MAX_DBL(1.0, 1.0/(GSL_DBL_EPSILON + fabs(1.0-x))); result->val = -0.25/M_SQRT2 * sqrt(x-1.0) * (1.0 - 5.0/16.0 * (x-1.0)); result->err = err_amp * 3.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double xi = acosh(x); const double c = cosh(0.5*xi); const double t = tanh(0.5*xi); const double sxi = sinh(xi); const double pre = 2.0/(M_PI*sxi) * c; stat_K = gsl_sf_ellint_Kcomp_e(t, GSL_MODE_DEFAULT, &K); stat_E = gsl_sf_ellint_Ecomp_e(t, GSL_MODE_DEFAULT, &E); result->val = pre * (E.val - K.val); result->err = pre * (E.err + K.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_K; } } } else if( (x <= 0.0 && lambda < 1000.0) || (x < 0.1 && lambda < 17.0) || (x < 0.2 && lambda < 5.0 ) ) { return conicalP_xlt1_hyperg_A(1.0, lambda, x, result); } else if( (x <= 0.2 && lambda < 17.0) || (x < 1.5 && lambda < 20.0) ) { const double arg = fabs(x*x - 1.0); const double sgn = GSL_SIGN(1.0 - x); const double pre = 0.5*(lambda*lambda + 0.25) * sgn * sqrt(arg); gsl_sf_result F; int stat_F = gsl_sf_hyperg_2F1_conj_e(1.5, lambda, 2.0, (1.0-x)/2, &F); result->val = pre * F.val; result->err = fabs(pre) * F.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_F; } else if(1.5 <= x && lambda < GSL_MAX(x,20.0)) { gsl_sf_result P; double lm; int stat_P = gsl_sf_conicalP_large_x_e(1.0, lambda, x, &P, &lm ); int stat_e = gsl_sf_exp_mult_err_e(lm, 2.0 * GSL_DBL_EPSILON * fabs(lm), P.val, P.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_P); } else { double V0, V1; if(x < 1.0) { const double sqrt_1mx = sqrt(1.0 - x); const double sqrt_1px = sqrt(1.0 + x); const double th = acos(x); const double sth = sqrt_1mx * sqrt_1px; /* sin(th) */ gsl_sf_result I0, I1; int stat_I0 = gsl_sf_bessel_I0_scaled_e(th * lambda, &I0); int stat_I1 = gsl_sf_bessel_I1_scaled_e(th * lambda, &I1); int stat_I = GSL_ERROR_SELECT_2(stat_I0, stat_I1); int stat_V = conicalP_1_V(th, x/sth, lambda, -1.0, &V0, &V1); double bessterm = V0 * I0.val + V1 * I1.val; double besserr = fabs(V0) * I0.err + fabs(V1) * I1.err + 2.0 * GSL_DBL_EPSILON * fabs(V0 * I0.val) + 2.0 * GSL_DBL_EPSILON * fabs(V1 * I1.val); double arg1 = th * lambda; double sqts = sqrt(th/sth); int stat_e = gsl_sf_exp_mult_err_e(arg1, 2.0 * GSL_DBL_EPSILON * fabs(arg1), sqts * bessterm, sqts * besserr, result); result->err *= 1.0/sqrt_1mx; return GSL_ERROR_SELECT_3(stat_e, stat_V, stat_I); } else { const double sqrt_xm1 = sqrt(x - 1.0); const double sqrt_xp1 = sqrt(x + 1.0); const double sh = sqrt_xm1 * sqrt_xp1; /* sinh(xi) */ const double xi = log(x + sh); /* xi = acosh(x) */ const double xi_lam = xi * lambda; gsl_sf_result J0, J1; const int stat_J0 = gsl_sf_bessel_J0_e(xi_lam, &J0); const int stat_J1 = gsl_sf_bessel_J1_e(xi_lam, &J1); const int stat_J = GSL_ERROR_SELECT_2(stat_J0, stat_J1); const int stat_V = conicalP_1_V(xi, x/sh, lambda, 1.0, &V0, &V1); const double bessterm = V0 * J0.val + V1 * J1.val; const double besserr = fabs(V0) * J0.err + fabs(V1) * J1.err + 512.0 * 2.0 * GSL_DBL_EPSILON * fabs(V0 * J0.val) + 512.0 * 2.0 * GSL_DBL_EPSILON * fabs(V1 * J1.val) + GSL_DBL_EPSILON * fabs(xi_lam * V0 * J1.val) + GSL_DBL_EPSILON * fabs(xi_lam * V1 * J0.val); const double pre = sqrt(xi/sh); result->val = pre * bessterm; result->err = pre * besserr * sqrt_xp1 / sqrt_xm1; result->err += 4.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_V, stat_J); } } } /* P^{1/2}_{-1/2 + I lambda} (x) * [Abramowitz+Stegun 8.6.8, 8.6.12] * checked OK [GJ] Fri May 8 12:24:36 MDT 1998 */ int gsl_sf_conicalP_half_e(const double lambda, const double x, gsl_sf_result * result ) { /* CHECK_POINTER(result) */ if(x <= -1.0) { DOMAIN_ERROR(result); } else if(x < 1.0) { double err_amp = 1.0 + 1.0/(GSL_DBL_EPSILON + fabs(1.0-fabs(x))); double ac = acos(x); double den = sqrt(sqrt(1.0-x)*sqrt(1.0+x)); result->val = Root_2OverPi_ / den * cosh(ac * lambda); result->err = err_amp * 3.0 * GSL_DBL_EPSILON * fabs(result->val); result->err *= fabs(ac * lambda) + 1.0; return GSL_SUCCESS; } else if(x == 1.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* x > 1 */ double err_amp = 1.0 + 1.0/(GSL_DBL_EPSILON + fabs(1.0-fabs(x))); double sq_term = sqrt(x-1.0)*sqrt(x+1.0); double ln_term = log(x + sq_term); double den = sqrt(sq_term); double carg_val = lambda * ln_term; double carg_err = 2.0 * GSL_DBL_EPSILON * fabs(carg_val); gsl_sf_result cos_result; int stat_cos = gsl_sf_cos_err_e(carg_val, carg_err, &cos_result); result->val = Root_2OverPi_ / den * cos_result.val; result->err = err_amp * Root_2OverPi_ / den * cos_result.err; result->err += 4.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_cos; } } /* P^{-1/2}_{-1/2 + I lambda} (x) * [Abramowitz+Stegun 8.6.9, 8.6.14] * checked OK [GJ] Fri May 8 12:24:43 MDT 1998 */ int gsl_sf_conicalP_mhalf_e(const double lambda, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0) { DOMAIN_ERROR(result); } else if(x < 1.0) { double ac = acos(x); double den = sqrt(sqrt(1.0-x)*sqrt(1.0+x)); double arg = ac * lambda; double err_amp = 1.0 + 1.0/(GSL_DBL_EPSILON + fabs(1.0-fabs(x))); if(fabs(arg) < GSL_SQRT_DBL_EPSILON) { result->val = Root_2OverPi_ / den * ac; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->err *= err_amp; } else { result->val = Root_2OverPi_ / (den*lambda) * sinh(arg); result->err = GSL_DBL_EPSILON * (fabs(arg)+1.0) * fabs(result->val); result->err *= err_amp; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return GSL_SUCCESS; } else if(x == 1.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* x > 1 */ double sq_term = sqrt(x-1.0)*sqrt(x+1.0); double ln_term = log(x + sq_term); double den = sqrt(sq_term); double arg_val = lambda * ln_term; double arg_err = 2.0 * GSL_DBL_EPSILON * fabs(arg_val); if(arg_val < GSL_SQRT_DBL_EPSILON) { result->val = Root_2OverPi_ / den * ln_term; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result sin_result; int stat_sin = gsl_sf_sin_err_e(arg_val, arg_err, &sin_result); result->val = Root_2OverPi_ / (den*lambda) * sin_result.val; result->err = Root_2OverPi_ / fabs(den*lambda) * sin_result.err; result->err += 3.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_sin; } } } int gsl_sf_conicalP_sph_reg_e(const int l, const double lambda, const double x, gsl_sf_result * result ) { /* CHECK_POINTER(result) */ if(x <= -1.0 || l < -1) { DOMAIN_ERROR(result); } else if(l == -1) { return gsl_sf_conicalP_half_e(lambda, x, result); } else if(l == 0) { return gsl_sf_conicalP_mhalf_e(lambda, x, result); } else if(x == 1.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 0.0) { double c = 1.0/sqrt(1.0-x*x); gsl_sf_result r_Pellm1; gsl_sf_result r_Pell; int stat_0 = gsl_sf_conicalP_half_e(lambda, x, &r_Pellm1); /* P^( 1/2) */ int stat_1 = gsl_sf_conicalP_mhalf_e(lambda, x, &r_Pell); /* P^(-1/2) */ int stat_P = GSL_ERROR_SELECT_2(stat_0, stat_1); double Pellm1 = r_Pellm1.val; double Pell = r_Pell.val; double Pellp1; int ell; for(ell=0; ellval = Pell; result->err = (0.5*l + 1.0) * GSL_DBL_EPSILON * fabs(Pell); result->err += GSL_DBL_EPSILON * l * fabs(result->val); return stat_P; } else if(x < 1.0) { const double xi = x/(sqrt(1.0-x)*sqrt(1.0+x)); gsl_sf_result rat; gsl_sf_result Phf; int stat_CF1 = conicalP_negmu_xlt1_CF1(0.5, l, lambda, x, &rat); int stat_Phf = gsl_sf_conicalP_half_e(lambda, x, &Phf); double Pellp1 = rat.val * GSL_SQRT_DBL_MIN; double Pell = GSL_SQRT_DBL_MIN; double Pellm1; int ell; for(ell=l; ell>=0; ell--) { double d = (ell+1.0)*(ell+1.0) + lambda*lambda; Pellm1 = (2.0*ell+1.0)*xi * Pell + d * Pellp1; Pellp1 = Pell; Pell = Pellm1; } result->val = GSL_SQRT_DBL_MIN * Phf.val / Pell; result->err = GSL_SQRT_DBL_MIN * Phf.err / fabs(Pell); result->err += fabs(rat.err/rat.val) * (l + 1.0) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Phf, stat_CF1); } else if(x == 1.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* x > 1.0 */ const double xi = x/sqrt((x-1.0)*(x+1.0)); gsl_sf_result rat; int stat_CF1 = conicalP_negmu_xgt1_CF1(0.5, l, lambda, x, &rat); int stat_P; double Pellp1 = rat.val * GSL_SQRT_DBL_MIN; double Pell = GSL_SQRT_DBL_MIN; double Pellm1; int ell; for(ell=l; ell>=0; ell--) { double d = (ell+1.0)*(ell+1.0) + lambda*lambda; Pellm1 = (2.0*ell+1.0)*xi * Pell - d * Pellp1; Pellp1 = Pell; Pell = Pellm1; } if(fabs(Pell) > fabs(Pellp1)){ gsl_sf_result Phf; stat_P = gsl_sf_conicalP_half_e(lambda, x, &Phf); result->val = GSL_SQRT_DBL_MIN * Phf.val / Pell; result->err = 2.0 * GSL_SQRT_DBL_MIN * Phf.err / fabs(Pell); result->err += 2.0 * fabs(rat.err/rat.val) * (l + 1.0) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } else { gsl_sf_result Pmhf; stat_P = gsl_sf_conicalP_mhalf_e(lambda, x, &Pmhf); result->val = GSL_SQRT_DBL_MIN * Pmhf.val / Pellp1; result->err = 2.0 * GSL_SQRT_DBL_MIN * Pmhf.err / fabs(Pellp1); result->err += 2.0 * fabs(rat.err/rat.val) * (l + 1.0) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return GSL_ERROR_SELECT_2(stat_P, stat_CF1); } } int gsl_sf_conicalP_cyl_reg_e(const int m, const double lambda, const double x, gsl_sf_result * result ) { /* CHECK_POINTER(result) */ if(x <= -1.0 || m < -1) { DOMAIN_ERROR(result); } else if(m == -1) { return gsl_sf_conicalP_1_e(lambda, x, result); } else if(m == 0) { return gsl_sf_conicalP_0_e(lambda, x, result); } else if(x == 1.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 0.0) { double c = 1.0/sqrt(1.0-x*x); gsl_sf_result r_Pkm1; gsl_sf_result r_Pk; int stat_0 = gsl_sf_conicalP_1_e(lambda, x, &r_Pkm1); /* P^1 */ int stat_1 = gsl_sf_conicalP_0_e(lambda, x, &r_Pk); /* P^0 */ int stat_P = GSL_ERROR_SELECT_2(stat_0, stat_1); double Pkm1 = r_Pkm1.val; double Pk = r_Pk.val; double Pkp1; int k; for(k=0; kval = Pk; result->err = (m + 2.0) * GSL_DBL_EPSILON * fabs(Pk); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_P; } else if(x < 1.0) { const double xi = x/(sqrt(1.0-x)*sqrt(1.0+x)); gsl_sf_result rat; gsl_sf_result P0; int stat_CF1 = conicalP_negmu_xlt1_CF1(0.0, m, lambda, x, &rat); int stat_P0 = gsl_sf_conicalP_0_e(lambda, x, &P0); double Pkp1 = rat.val * GSL_SQRT_DBL_MIN; double Pk = GSL_SQRT_DBL_MIN; double Pkm1; int k; for(k=m; k>0; k--) { double d = (k+0.5)*(k+0.5) + lambda*lambda; Pkm1 = 2.0*k*xi * Pk + d * Pkp1; Pkp1 = Pk; Pk = Pkm1; } result->val = GSL_SQRT_DBL_MIN * P0.val / Pk; result->err = 2.0 * GSL_SQRT_DBL_MIN * P0.err / fabs(Pk); result->err += 2.0 * fabs(rat.err/rat.val) * (m + 1.0) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_P0, stat_CF1); } else if(x == 1.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* x > 1.0 */ const double xi = x/sqrt((x-1.0)*(x+1.0)); gsl_sf_result rat; int stat_CF1 = conicalP_negmu_xgt1_CF1(0.0, m, lambda, x, &rat); int stat_P; double Pkp1 = rat.val * GSL_SQRT_DBL_MIN; double Pk = GSL_SQRT_DBL_MIN; double Pkm1; int k; for(k=m; k>-1; k--) { double d = (k+0.5)*(k+0.5) + lambda*lambda; Pkm1 = 2.0*k*xi * Pk - d * Pkp1; Pkp1 = Pk; Pk = Pkm1; } if(fabs(Pk) > fabs(Pkp1)){ gsl_sf_result P1; stat_P = gsl_sf_conicalP_1_e(lambda, x, &P1); result->val = GSL_SQRT_DBL_MIN * P1.val / Pk; result->err = 2.0 * GSL_SQRT_DBL_MIN * P1.err / fabs(Pk); result->err += 2.0 * fabs(rat.err/rat.val) * (m+2.0) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } else { gsl_sf_result P0; stat_P = gsl_sf_conicalP_0_e(lambda, x, &P0); result->val = GSL_SQRT_DBL_MIN * P0.val / Pkp1; result->err = 2.0 * GSL_SQRT_DBL_MIN * P0.err / fabs(Pkp1); result->err += 2.0 * fabs(rat.err/rat.val) * (m+2.0) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return GSL_ERROR_SELECT_2(stat_P, stat_CF1); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_conicalP_0(const double lambda, const double x) { EVAL_RESULT(gsl_sf_conicalP_0_e(lambda, x, &result)); } double gsl_sf_conicalP_1(const double lambda, const double x) { EVAL_RESULT(gsl_sf_conicalP_1_e(lambda, x, &result)); } double gsl_sf_conicalP_half(const double lambda, const double x) { EVAL_RESULT(gsl_sf_conicalP_half_e(lambda, x, &result)); } double gsl_sf_conicalP_mhalf(const double lambda, const double x) { EVAL_RESULT(gsl_sf_conicalP_mhalf_e(lambda, x, &result)); } double gsl_sf_conicalP_sph_reg(const int l, const double lambda, const double x) { EVAL_RESULT(gsl_sf_conicalP_sph_reg_e(l, lambda, x, &result)); } double gsl_sf_conicalP_cyl_reg(const int m, const double lambda, const double x) { EVAL_RESULT(gsl_sf_conicalP_cyl_reg_e(m, lambda, x, &result)); } sources_5316/external/gsl/gsl_specfunc__mathieu_coeff.c0000664000176700017670000002046011723710247022176 0ustar paulpaul/* specfunc/mathieu_coeff.c * * Copyright (C) 2002 Lowell Johnson * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Author: L. Johnson */ #include "gsl__config.h" #include #include #include "gsl_sf_mathieu.h" /***************************************************************************** * backward_recurse * * Purpose: ****************************************************************************/ static void backward_recurse_c(double aa, double qq, double xx, double *ff, double *gx, int even_odd, int ni) { int ii, nn; double g1; g1 = *gx; ff[ni] = xx; if (even_odd == 0) { for (ii=0; ii GSL_SF_MATHIEU_COEFF) return GSL_FAILURE; /* Handle the trivial case where q = 0. */ if (qq == 0.0) { for (ii=0; ii GSL_SF_MATHIEU_COEFF) return GSL_FAILURE; /* Handle the trivial case where q = 0. */ if (qq == 0.0) { for (ii=0; ii upper) GSL_ERROR ("lower bound larger than upper_bound", GSL_EINVAL); if ((lower > 0 && upper > 0) || (lower < 0 && upper < 0)) { min_abs = GSL_MIN_DBL(abs_lower, abs_upper) ; } else { min_abs = 0; } tolerance = epsabs + epsrel * min_abs ; if (fabs(upper - lower) < tolerance) return GSL_SUCCESS; return GSL_CONTINUE ; } sources_5316/external/gsl/gsl_sf__hyperg.h0000644000176700017670000000433210710226217017475 0ustar paulpaul/* specfunc/hyperg.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Miscellaneous implementations of use * for evaluation of hypergeometric functions. */ #ifndef _HYPERG_H_ #define _HYPERG_H_ #include "gsl_sf_result.h" /* Direct implementation of 1F1 series. */ int gsl_sf_hyperg_1F1_series_e(const double a, const double b, const double x, gsl_sf_result * result); /* Implementation of the 1F1 related to the * incomplete gamma function: 1F1(1,b,x), b >= 1. */ int gsl_sf_hyperg_1F1_1_e(double b, double x, gsl_sf_result * result); /* 1F1(1,b,x) for integer b >= 1 */ int gsl_sf_hyperg_1F1_1_int_e(int b, double x, gsl_sf_result * result); /* Implementation of large b asymptotic. * [Bateman v. I, 6.13.3 (18)] * [Luke, The Special Functions and Their Approximations v. I, p. 129, 4.8 (4)] * * a^2 << b, |x|/|b| < 1 - delta */ int gsl_sf_hyperg_1F1_large_b_e(const double a, const double b, const double x, gsl_sf_result * result); /* Implementation of large b asymptotic. * * Assumes a > 0 is small, x > 0, and |x|<|b|. */ int gsl_sf_hyperg_U_large_b_e(const double a, const double b, const double x, gsl_sf_result * result, double * ln_multiplier ); /* Implementation of 2F0 asymptotic series. */ int gsl_sf_hyperg_2F0_series_e(const double a, const double b, const double x, int n_trunc, gsl_sf_result * result); #endif /* !_HYPERG_H_ */ sources_5316/external/gsl/gsl_cblas__stbmv.c0000664000176700017670000000063211723710247020010 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_stbmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const float *A, const int lda, float *X, const int incX) { #define BASE float #include "gsl_cblas__source_tbmv_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__dgemv.c0000664000176700017670000000065511723710247017764 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dgemv (const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const double alpha, const double *A, const int lda, const double *X, const int incX, const double beta, double *Y, const int incY) { #define BASE double #include "gsl_cblas__source_gemv_r.h" #undef BASE } sources_5316/external/gsl/gsl_permute_vector_complex_long_double.h0000664000176700017670000000306411705263724024527 0ustar paulpaul/* permutation/gsl_permute_vector_complex_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_COMPLEX_LONG_DOUBLE_H__ #define __GSL_PERMUTE_VECTOR_COMPLEX_LONG_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_complex_long_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_complex_long_double (const gsl_permutation * p, gsl_vector_complex_long_double * v); int gsl_permute_vector_complex_long_double_inverse (const gsl_permutation * p, gsl_vector_complex_long_double * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_COMPLEX_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_permute_int.h0000664000176700017670000000260611705263724017720 0ustar paulpaul/* permutation/gsl_permute_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_INT_H__ #define __GSL_PERMUTE_INT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_int (const size_t * p, int * data, const size_t stride, const size_t n); int gsl_permute_int_inverse (const size_t * p, int * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_INT_H__ */ sources_5316/external/gsl/gsl_min__min.h0000664000176700017670000000174311705263724017153 0ustar paulpaul/* min/min.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #define SAFE_FUNC_CALL(f, x, yp) \ do { \ *yp = GSL_FN_EVAL(f,x); \ if (!gsl_finite(*yp)) \ GSL_ERROR("computed function value is infinite or NaN", GSL_EBADFUNC); \ } while (0) sources_5316/external/gsl/gsl_complex__math.c0000664000176700017670000005601611723710247020200 0ustar paulpaul/* complex/math.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jorma Olavi Tähtinen, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Basic complex arithmetic functions * Original version by Jorma Olavi Tähtinen * * Modified for GSL by Brian Gough, 3/2000 */ /* The following references describe the methods used in these * functions, * * T. E. Hull and Thomas F. Fairgrieve and Ping Tak Peter Tang, * "Implementing Complex Elementary Functions Using Exception * Handling", ACM Transactions on Mathematical Software, Volume 20 * (1994), pp 215-244, Corrigenda, p553 * * Hull et al, "Implementing the complex arcsin and arccosine * functions using exception handling", ACM Transactions on * Mathematical Software, Volume 23 (1997) pp 299-335 * * Abramowitz and Stegun, Handbook of Mathematical Functions, "Inverse * Circular Functions in Terms of Real and Imaginary Parts", Formulas * 4.4.37, 4.4.38, 4.4.39 */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_complex_math.h" /********************************************************************** * Complex numbers **********************************************************************/ #ifndef HIDE_INLINE_STATIC gsl_complex gsl_complex_rect (double x, double y) { /* return z = x + i y */ gsl_complex z; GSL_SET_COMPLEX (&z, x, y); return z; } #endif gsl_complex gsl_complex_polar (double r, double theta) { /* return z = r exp(i theta) */ gsl_complex z; GSL_SET_COMPLEX (&z, r * cos (theta), r * sin (theta)); return z; } /********************************************************************** * Properties of complex numbers **********************************************************************/ double gsl_complex_arg (gsl_complex z) { /* return arg(z), -pi < arg(z) <= +pi */ double x = GSL_REAL (z); double y = GSL_IMAG (z); if (x == 0.0 && y == 0.0) { return 0; } return atan2 (y, x); } double gsl_complex_abs (gsl_complex z) { /* return |z| */ return hypot (GSL_REAL (z), GSL_IMAG (z)); } double gsl_complex_abs2 (gsl_complex z) { /* return |z|^2 */ double x = GSL_REAL (z); double y = GSL_IMAG (z); return (x * x + y * y); } double gsl_complex_logabs (gsl_complex z) { /* return log|z| */ double xabs = fabs (GSL_REAL (z)); double yabs = fabs (GSL_IMAG (z)); double max, u; if (xabs >= yabs) { max = xabs; u = yabs / xabs; } else { max = yabs; u = xabs / yabs; } /* Handle underflow when u is close to 0 */ return log (max) + 0.5 * log1p (u * u); } /*********************************************************************** * Complex arithmetic operators ***********************************************************************/ gsl_complex gsl_complex_add (gsl_complex a, gsl_complex b) { /* z=a+b */ double ar = GSL_REAL (a), ai = GSL_IMAG (a); double br = GSL_REAL (b), bi = GSL_IMAG (b); gsl_complex z; GSL_SET_COMPLEX (&z, ar + br, ai + bi); return z; } gsl_complex gsl_complex_add_real (gsl_complex a, double x) { /* z=a+x */ gsl_complex z; GSL_SET_COMPLEX (&z, GSL_REAL (a) + x, GSL_IMAG (a)); return z; } gsl_complex gsl_complex_add_imag (gsl_complex a, double y) { /* z=a+iy */ gsl_complex z; GSL_SET_COMPLEX (&z, GSL_REAL (a), GSL_IMAG (a) + y); return z; } gsl_complex gsl_complex_sub (gsl_complex a, gsl_complex b) { /* z=a-b */ double ar = GSL_REAL (a), ai = GSL_IMAG (a); double br = GSL_REAL (b), bi = GSL_IMAG (b); gsl_complex z; GSL_SET_COMPLEX (&z, ar - br, ai - bi); return z; } gsl_complex gsl_complex_sub_real (gsl_complex a, double x) { /* z=a-x */ gsl_complex z; GSL_SET_COMPLEX (&z, GSL_REAL (a) - x, GSL_IMAG (a)); return z; } gsl_complex gsl_complex_sub_imag (gsl_complex a, double y) { /* z=a-iy */ gsl_complex z; GSL_SET_COMPLEX (&z, GSL_REAL (a), GSL_IMAG (a) - y); return z; } gsl_complex gsl_complex_mul (gsl_complex a, gsl_complex b) { /* z=a*b */ double ar = GSL_REAL (a), ai = GSL_IMAG (a); double br = GSL_REAL (b), bi = GSL_IMAG (b); gsl_complex z; GSL_SET_COMPLEX (&z, ar * br - ai * bi, ar * bi + ai * br); return z; } gsl_complex gsl_complex_mul_real (gsl_complex a, double x) { /* z=a*x */ gsl_complex z; GSL_SET_COMPLEX (&z, x * GSL_REAL (a), x * GSL_IMAG (a)); return z; } gsl_complex gsl_complex_mul_imag (gsl_complex a, double y) { /* z=a*iy */ gsl_complex z; GSL_SET_COMPLEX (&z, -y * GSL_IMAG (a), y * GSL_REAL (a)); return z; } gsl_complex gsl_complex_div (gsl_complex a, gsl_complex b) { /* z=a/b */ double ar = GSL_REAL (a), ai = GSL_IMAG (a); double br = GSL_REAL (b), bi = GSL_IMAG (b); double s = 1.0 / gsl_complex_abs (b); double sbr = s * br; double sbi = s * bi; double zr = (ar * sbr + ai * sbi) * s; double zi = (ai * sbr - ar * sbi) * s; gsl_complex z; GSL_SET_COMPLEX (&z, zr, zi); return z; } gsl_complex gsl_complex_div_real (gsl_complex a, double x) { /* z=a/x */ gsl_complex z; GSL_SET_COMPLEX (&z, GSL_REAL (a) / x, GSL_IMAG (a) / x); return z; } gsl_complex gsl_complex_div_imag (gsl_complex a, double y) { /* z=a/(iy) */ gsl_complex z; GSL_SET_COMPLEX (&z, GSL_IMAG (a) / y, - GSL_REAL (a) / y); return z; } gsl_complex gsl_complex_conjugate (gsl_complex a) { /* z=conj(a) */ gsl_complex z; GSL_SET_COMPLEX (&z, GSL_REAL (a), -GSL_IMAG (a)); return z; } gsl_complex gsl_complex_negative (gsl_complex a) { /* z=-a */ gsl_complex z; GSL_SET_COMPLEX (&z, -GSL_REAL (a), -GSL_IMAG (a)); return z; } gsl_complex gsl_complex_inverse (gsl_complex a) { /* z=1/a */ double s = 1.0 / gsl_complex_abs (a); gsl_complex z; GSL_SET_COMPLEX (&z, (GSL_REAL (a) * s) * s, -(GSL_IMAG (a) * s) * s); return z; } /********************************************************************** * Elementary complex functions **********************************************************************/ gsl_complex gsl_complex_sqrt (gsl_complex a) { /* z=sqrt(a) */ gsl_complex z; if (GSL_REAL (a) == 0.0 && GSL_IMAG (a) == 0.0) { GSL_SET_COMPLEX (&z, 0, 0); } else { double x = fabs (GSL_REAL (a)); double y = fabs (GSL_IMAG (a)); double w; if (x >= y) { double t = y / x; w = sqrt (x) * sqrt (0.5 * (1.0 + sqrt (1.0 + t * t))); } else { double t = x / y; w = sqrt (y) * sqrt (0.5 * (t + sqrt (1.0 + t * t))); } if (GSL_REAL (a) >= 0.0) { double ai = GSL_IMAG (a); GSL_SET_COMPLEX (&z, w, ai / (2.0 * w)); } else { double ai = GSL_IMAG (a); double vi = (ai >= 0) ? w : -w; GSL_SET_COMPLEX (&z, ai / (2.0 * vi), vi); } } return z; } gsl_complex gsl_complex_sqrt_real (double x) { /* z=sqrt(x) */ gsl_complex z; if (x >= 0) { GSL_SET_COMPLEX (&z, sqrt (x), 0.0); } else { GSL_SET_COMPLEX (&z, 0.0, sqrt (-x)); } return z; } gsl_complex gsl_complex_exp (gsl_complex a) { /* z=exp(a) */ double rho = exp (GSL_REAL (a)); double theta = GSL_IMAG (a); gsl_complex z; GSL_SET_COMPLEX (&z, rho * cos (theta), rho * sin (theta)); return z; } gsl_complex gsl_complex_pow (gsl_complex a, gsl_complex b) { /* z=a^b */ gsl_complex z; if (GSL_REAL (a) == 0 && GSL_IMAG (a) == 0.0) { if (GSL_REAL (b) == 0 && GSL_IMAG (b) == 0.0) { GSL_SET_COMPLEX (&z, 1.0, 0.0); } else { GSL_SET_COMPLEX (&z, 0.0, 0.0); } } else if (GSL_REAL (b) == 1.0 && GSL_IMAG (b) == 0.0) { return a; } else if (GSL_REAL (b) == -1.0 && GSL_IMAG (b) == 0.0) { return gsl_complex_inverse (a); } else { double logr = gsl_complex_logabs (a); double theta = gsl_complex_arg (a); double br = GSL_REAL (b), bi = GSL_IMAG (b); double rho = exp (logr * br - bi * theta); double beta = theta * br + bi * logr; GSL_SET_COMPLEX (&z, rho * cos (beta), rho * sin (beta)); } return z; } gsl_complex gsl_complex_pow_real (gsl_complex a, double b) { /* z=a^b */ gsl_complex z; if (GSL_REAL (a) == 0 && GSL_IMAG (a) == 0) { GSL_SET_COMPLEX (&z, 0, 0); } else { double logr = gsl_complex_logabs (a); double theta = gsl_complex_arg (a); double rho = exp (logr * b); double beta = theta * b; GSL_SET_COMPLEX (&z, rho * cos (beta), rho * sin (beta)); } return z; } gsl_complex gsl_complex_log (gsl_complex a) { /* z=log(a) */ double logr = gsl_complex_logabs (a); double theta = gsl_complex_arg (a); gsl_complex z; GSL_SET_COMPLEX (&z, logr, theta); return z; } gsl_complex gsl_complex_log10 (gsl_complex a) { /* z = log10(a) */ return gsl_complex_mul_real (gsl_complex_log (a), 1 / log (10.)); } gsl_complex gsl_complex_log_b (gsl_complex a, gsl_complex b) { return gsl_complex_div (gsl_complex_log (a), gsl_complex_log (b)); } /*********************************************************************** * Complex trigonometric functions ***********************************************************************/ gsl_complex gsl_complex_sin (gsl_complex a) { /* z = sin(a) */ double R = GSL_REAL (a), I = GSL_IMAG (a); gsl_complex z; if (I == 0.0) { /* avoid returing negative zero (-0.0) for the imaginary part */ GSL_SET_COMPLEX (&z, sin (R), 0.0); } else { GSL_SET_COMPLEX (&z, sin (R) * cosh (I), cos (R) * sinh (I)); } return z; } gsl_complex gsl_complex_cos (gsl_complex a) { /* z = cos(a) */ double R = GSL_REAL (a), I = GSL_IMAG (a); gsl_complex z; if (I == 0.0) { /* avoid returing negative zero (-0.0) for the imaginary part */ GSL_SET_COMPLEX (&z, cos (R), 0.0); } else { GSL_SET_COMPLEX (&z, cos (R) * cosh (I), sin (R) * sinh (-I)); } return z; } gsl_complex gsl_complex_tan (gsl_complex a) { /* z = tan(a) */ double R = GSL_REAL (a), I = GSL_IMAG (a); gsl_complex z; if (fabs (I) < 1) { double D = pow (cos (R), 2.0) + pow (sinh (I), 2.0); GSL_SET_COMPLEX (&z, 0.5 * sin (2 * R) / D, 0.5 * sinh (2 * I) / D); } else { double u = exp (-I); double C = 2 * u / (1 - pow (u, 2.0)); double D = 1 + pow (cos (R), 2.0) * pow (C, 2.0); double S = pow (C, 2.0); double T = 1.0 / tanh (I); GSL_SET_COMPLEX (&z, 0.5 * sin (2 * R) * S / D, T / D); } return z; } gsl_complex gsl_complex_sec (gsl_complex a) { /* z = sec(a) */ gsl_complex z = gsl_complex_cos (a); return gsl_complex_inverse (z); } gsl_complex gsl_complex_csc (gsl_complex a) { /* z = csc(a) */ gsl_complex z = gsl_complex_sin (a); return gsl_complex_inverse(z); } gsl_complex gsl_complex_cot (gsl_complex a) { /* z = cot(a) */ gsl_complex z = gsl_complex_tan (a); return gsl_complex_inverse (z); } /********************************************************************** * Inverse Complex Trigonometric Functions **********************************************************************/ gsl_complex gsl_complex_arcsin (gsl_complex a) { /* z = arcsin(a) */ double R = GSL_REAL (a), I = GSL_IMAG (a); gsl_complex z; if (I == 0) { z = gsl_complex_arcsin_real (R); } else { double x = fabs (R), y = fabs (I); double r = hypot (x + 1, y), s = hypot (x - 1, y); double A = 0.5 * (r + s); double B = x / A; double y2 = y * y; double real, imag; const double A_crossover = 1.5, B_crossover = 0.6417; if (B <= B_crossover) { real = asin (B); } else { if (x <= 1) { double D = 0.5 * (A + x) * (y2 / (r + x + 1) + (s + (1 - x))); real = atan (x / sqrt (D)); } else { double Apx = A + x; double D = 0.5 * (Apx / (r + x + 1) + Apx / (s + (x - 1))); real = atan (x / (y * sqrt (D))); } } if (A <= A_crossover) { double Am1; if (x < 1) { Am1 = 0.5 * (y2 / (r + (x + 1)) + y2 / (s + (1 - x))); } else { Am1 = 0.5 * (y2 / (r + (x + 1)) + (s + (x - 1))); } imag = log1p (Am1 + sqrt (Am1 * (A + 1))); } else { imag = log (A + sqrt (A * A - 1)); } GSL_SET_COMPLEX (&z, (R >= 0) ? real : -real, (I >= 0) ? imag : -imag); } return z; } gsl_complex gsl_complex_arcsin_real (double a) { /* z = arcsin(a) */ gsl_complex z; if (fabs (a) <= 1.0) { GSL_SET_COMPLEX (&z, asin (a), 0.0); } else { if (a < 0.0) { GSL_SET_COMPLEX (&z, -M_PI_2, acosh (-a)); } else { GSL_SET_COMPLEX (&z, M_PI_2, -acosh (a)); } } return z; } gsl_complex gsl_complex_arccos (gsl_complex a) { /* z = arccos(a) */ double R = GSL_REAL (a), I = GSL_IMAG (a); gsl_complex z; if (I == 0) { z = gsl_complex_arccos_real (R); } else { double x = fabs (R), y = fabs (I); double r = hypot (x + 1, y), s = hypot (x - 1, y); double A = 0.5 * (r + s); double B = x / A; double y2 = y * y; double real, imag; const double A_crossover = 1.5, B_crossover = 0.6417; if (B <= B_crossover) { real = acos (B); } else { if (x <= 1) { double D = 0.5 * (A + x) * (y2 / (r + x + 1) + (s + (1 - x))); real = atan (sqrt (D) / x); } else { double Apx = A + x; double D = 0.5 * (Apx / (r + x + 1) + Apx / (s + (x - 1))); real = atan ((y * sqrt (D)) / x); } } if (A <= A_crossover) { double Am1; if (x < 1) { Am1 = 0.5 * (y2 / (r + (x + 1)) + y2 / (s + (1 - x))); } else { Am1 = 0.5 * (y2 / (r + (x + 1)) + (s + (x - 1))); } imag = log1p (Am1 + sqrt (Am1 * (A + 1))); } else { imag = log (A + sqrt (A * A - 1)); } GSL_SET_COMPLEX (&z, (R >= 0) ? real : M_PI - real, (I >= 0) ? -imag : imag); } return z; } gsl_complex gsl_complex_arccos_real (double a) { /* z = arccos(a) */ gsl_complex z; if (fabs (a) <= 1.0) { GSL_SET_COMPLEX (&z, acos (a), 0); } else { if (a < 0.0) { GSL_SET_COMPLEX (&z, M_PI, -acosh (-a)); } else { GSL_SET_COMPLEX (&z, 0, acosh (a)); } } return z; } gsl_complex gsl_complex_arctan (gsl_complex a) { /* z = arctan(a) */ double R = GSL_REAL (a), I = GSL_IMAG (a); gsl_complex z; if (I == 0) { GSL_SET_COMPLEX (&z, atan (R), 0); } else { /* FIXME: This is a naive implementation which does not fully take into account cancellation errors, overflow, underflow etc. It would benefit from the Hull et al treatment. */ double r = hypot (R, I); double imag; double u = 2 * I / (1 + r * r); /* FIXME: the following cross-over should be optimized but 0.1 seems to work ok */ if (fabs (u) < 0.1) { imag = 0.25 * (log1p (u) - log1p (-u)); } else { double A = hypot (R, I + 1); double B = hypot (R, I - 1); imag = 0.5 * log (A / B); } if (R == 0) { if (I > 1) { GSL_SET_COMPLEX (&z, M_PI_2, imag); } else if (I < -1) { GSL_SET_COMPLEX (&z, -M_PI_2, imag); } else { GSL_SET_COMPLEX (&z, 0, imag); }; } else { GSL_SET_COMPLEX (&z, 0.5 * atan2 (2 * R, ((1 + r) * (1 - r))), imag); } } return z; } gsl_complex gsl_complex_arcsec (gsl_complex a) { /* z = arcsec(a) */ gsl_complex z = gsl_complex_inverse (a); return gsl_complex_arccos (z); } gsl_complex gsl_complex_arcsec_real (double a) { /* z = arcsec(a) */ gsl_complex z; if (a <= -1.0 || a >= 1.0) { GSL_SET_COMPLEX (&z, acos (1 / a), 0.0); } else { if (a >= 0.0) { GSL_SET_COMPLEX (&z, 0, acosh (1 / a)); } else { GSL_SET_COMPLEX (&z, M_PI, -acosh (-1 / a)); } } return z; } gsl_complex gsl_complex_arccsc (gsl_complex a) { /* z = arccsc(a) */ gsl_complex z = gsl_complex_inverse (a); return gsl_complex_arcsin (z); } gsl_complex gsl_complex_arccsc_real (double a) { /* z = arccsc(a) */ gsl_complex z; if (a <= -1.0 || a >= 1.0) { GSL_SET_COMPLEX (&z, asin (1 / a), 0.0); } else { if (a >= 0.0) { GSL_SET_COMPLEX (&z, M_PI_2, -acosh (1 / a)); } else { GSL_SET_COMPLEX (&z, -M_PI_2, acosh (-1 / a)); } } return z; } gsl_complex gsl_complex_arccot (gsl_complex a) { /* z = arccot(a) */ gsl_complex z; if (GSL_REAL (a) == 0.0 && GSL_IMAG (a) == 0.0) { GSL_SET_COMPLEX (&z, M_PI_2, 0); } else { z = gsl_complex_inverse (a); z = gsl_complex_arctan (z); } return z; } /********************************************************************** * Complex Hyperbolic Functions **********************************************************************/ gsl_complex gsl_complex_sinh (gsl_complex a) { /* z = sinh(a) */ double R = GSL_REAL (a), I = GSL_IMAG (a); gsl_complex z; GSL_SET_COMPLEX (&z, sinh (R) * cos (I), cosh (R) * sin (I)); return z; } gsl_complex gsl_complex_cosh (gsl_complex a) { /* z = cosh(a) */ double R = GSL_REAL (a), I = GSL_IMAG (a); gsl_complex z; GSL_SET_COMPLEX (&z, cosh (R) * cos (I), sinh (R) * sin (I)); return z; } gsl_complex gsl_complex_tanh (gsl_complex a) { /* z = tanh(a) */ double R = GSL_REAL (a), I = GSL_IMAG (a); gsl_complex z; if (fabs(R) < 1.0) { double D = pow (cos (I), 2.0) + pow (sinh (R), 2.0); GSL_SET_COMPLEX (&z, sinh (R) * cosh (R) / D, 0.5 * sin (2 * I) / D); } else { double D = pow (cos (I), 2.0) + pow (sinh (R), 2.0); double F = 1 + pow (cos (I) / sinh (R), 2.0); GSL_SET_COMPLEX (&z, 1.0 / (tanh (R) * F), 0.5 * sin (2 * I) / D); } return z; } gsl_complex gsl_complex_sech (gsl_complex a) { /* z = sech(a) */ gsl_complex z = gsl_complex_cosh (a); return gsl_complex_inverse (z); } gsl_complex gsl_complex_csch (gsl_complex a) { /* z = csch(a) */ gsl_complex z = gsl_complex_sinh (a); return gsl_complex_inverse (z); } gsl_complex gsl_complex_coth (gsl_complex a) { /* z = coth(a) */ gsl_complex z = gsl_complex_tanh (a); return gsl_complex_inverse (z); } /********************************************************************** * Inverse Complex Hyperbolic Functions **********************************************************************/ gsl_complex gsl_complex_arcsinh (gsl_complex a) { /* z = arcsinh(a) */ gsl_complex z = gsl_complex_mul_imag(a, 1.0); z = gsl_complex_arcsin (z); z = gsl_complex_mul_imag (z, -1.0); return z; } gsl_complex gsl_complex_arccosh (gsl_complex a) { /* z = arccosh(a) */ gsl_complex z = gsl_complex_arccos (a); z = gsl_complex_mul_imag (z, GSL_IMAG(z) > 0 ? -1.0 : 1.0); return z; } gsl_complex gsl_complex_arccosh_real (double a) { /* z = arccosh(a) */ gsl_complex z; if (a >= 1) { GSL_SET_COMPLEX (&z, acosh (a), 0); } else { if (a >= -1.0) { GSL_SET_COMPLEX (&z, 0, acos (a)); } else { GSL_SET_COMPLEX (&z, acosh (-a), M_PI); } } return z; } gsl_complex gsl_complex_arctanh (gsl_complex a) { /* z = arctanh(a) */ if (GSL_IMAG (a) == 0.0) { return gsl_complex_arctanh_real (GSL_REAL (a)); } else { gsl_complex z = gsl_complex_mul_imag(a, 1.0); z = gsl_complex_arctan (z); z = gsl_complex_mul_imag (z, -1.0); return z; } } gsl_complex gsl_complex_arctanh_real (double a) { /* z = arctanh(a) */ gsl_complex z; if (a > -1.0 && a < 1.0) { GSL_SET_COMPLEX (&z, atanh (a), 0); } else { GSL_SET_COMPLEX (&z, atanh (1 / a), (a < 0) ? M_PI_2 : -M_PI_2); } return z; } gsl_complex gsl_complex_arcsech (gsl_complex a) { /* z = arcsech(a); */ gsl_complex t = gsl_complex_inverse (a); return gsl_complex_arccosh (t); } gsl_complex gsl_complex_arccsch (gsl_complex a) { /* z = arccsch(a) */ gsl_complex t = gsl_complex_inverse (a); return gsl_complex_arcsinh (t); } gsl_complex gsl_complex_arccoth (gsl_complex a) { /* z = arccoth(a) */ gsl_complex t = gsl_complex_inverse (a); return gsl_complex_arctanh (t); } sources_5316/external/gsl/gsl_cblas__strsm.c0000664000176700017670000000072511723710247020030 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_strsm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const float alpha, const float *A, const int lda, float *B, const int ldb) { #define BASE float #include "gsl_cblas__source_trsm_r.h" #undef BASE } sources_5316/external/gsl/gsl_ieee-utils__fp-aix.c0000664000176700017670000000624311723710247021026 0ustar paulpaul/* ieee-utils/fp-aix.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Tim Mooney * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { fptrap_t mode = 0 ; fprnd_t rnd = 0 ; switch (precision) { /* I'm not positive about AIX only supporting default precision rounding, * but this is the best assumption until it's proven otherwise. */ case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("AIX only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("AIX only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("AIX only supports default precision rounding", GSL_EUNSUP) ; break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: rnd = FP_RND_RN ; fp_swap_rnd (rnd) ; break ; case GSL_IEEE_ROUND_DOWN: rnd = FP_RND_RM ; fp_swap_rnd (rnd) ; break ; case GSL_IEEE_ROUND_UP: rnd = FP_RND_RP ; fp_swap_rnd (rnd) ; break ; case GSL_IEEE_ROUND_TO_ZERO: rnd = FP_RND_RZ ; fp_swap_rnd (rnd) ; break ; default: rnd = FP_RND_RN ; fp_swap_rnd (rnd) ; } /* Turn on all the exceptions apart from 'inexact' */ mode = TRP_INVALID | TRP_DIV_BY_ZERO | TRP_OVERFLOW | TRP_UNDERFLOW ; if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ TRP_INVALID ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("AIX does not support the denormalized operand exception. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ TRP_DIV_BY_ZERO ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ TRP_OVERFLOW ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ TRP_UNDERFLOW ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode |= TRP_INEXACT ; } else { mode &= ~ TRP_INEXACT ; } /* AIX appears to require two steps -- first enable floating point traps * in general... */ fp_trap(FP_TRAP_SYNC); /* next, enable the traps we're interested in */ fp_enable(mode); return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_multimin__conjugate_pr.c0000664000176700017670000001524311723710247022113 0ustar paulpaul/* multimin/conjugate_pr.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Fabrice Rossi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* conjugate_pr.c -- Conjugate gradient Polak-Ribiere algorithm */ /* Modified by Brian Gough to use single iteration structure */ #include "gsl__config.h" #include "gsl_multimin.h" #include "gsl_blas.h" #include "gsl_multimin__directional_minimize.c" typedef struct { int iter; double step; double max_step; double tol; gsl_vector *x1; gsl_vector *dx1; gsl_vector *x2; double pnorm; gsl_vector *p; double g0norm; gsl_vector *g0; } conjugate_pr_state_t; static int conjugate_pr_alloc (void *vstate, size_t n) { conjugate_pr_state_t *state = (conjugate_pr_state_t *) vstate; state->x1 = gsl_vector_calloc (n); if (state->x1 == 0) { GSL_ERROR ("failed to allocate space for x1", GSL_ENOMEM); } state->dx1 = gsl_vector_calloc (n); if (state->dx1 == 0) { gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for dx1", GSL_ENOMEM); } state->x2 = gsl_vector_calloc (n); if (state->x2 == 0) { gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for x2", GSL_ENOMEM); } state->p = gsl_vector_calloc (n); if (state->p == 0) { gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for p", GSL_ENOMEM); } state->g0 = gsl_vector_calloc (n); if (state->g0 == 0) { gsl_vector_free (state->p); gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } return GSL_SUCCESS; } static int conjugate_pr_set (void *vstate, gsl_multimin_function_fdf * fdf, const gsl_vector * x, double *f, gsl_vector * gradient, double step_size, double tol) { conjugate_pr_state_t *state = (conjugate_pr_state_t *) vstate; state->iter = 0; state->step = step_size; state->max_step = step_size; state->tol = tol; GSL_MULTIMIN_FN_EVAL_F_DF (fdf, x, f, gradient); /* Use the gradient as the initial direction */ gsl_vector_memcpy (state->p, gradient); gsl_vector_memcpy (state->g0, gradient); { double gnorm = gsl_blas_dnrm2 (gradient); state->pnorm = gnorm; state->g0norm = gnorm; } return GSL_SUCCESS; } static void conjugate_pr_free (void *vstate) { conjugate_pr_state_t *state = (conjugate_pr_state_t *) vstate; gsl_vector_free (state->g0); gsl_vector_free (state->p); gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); } static int conjugate_pr_restart (void *vstate) { conjugate_pr_state_t *state = (conjugate_pr_state_t *) vstate; state->iter = 0; return GSL_SUCCESS; } static int conjugate_pr_iterate (void *vstate, gsl_multimin_function_fdf * fdf, gsl_vector * x, double *f, gsl_vector * gradient, gsl_vector * dx) { conjugate_pr_state_t *state = (conjugate_pr_state_t *) vstate; gsl_vector *x1 = state->x1; gsl_vector *dx1 = state->dx1; gsl_vector *x2 = state->x2; gsl_vector *p = state->p; gsl_vector *g0 = state->g0; double pnorm = state->pnorm; double g0norm = state->g0norm; double fa = *f, fb, fc; double dir; double stepa = 0.0, stepb, stepc = state->step, tol = state->tol; double g1norm; double pg; if (pnorm == 0.0 || g0norm == 0.0) { gsl_vector_set_zero (dx); return GSL_ENOPROG; } /* Determine which direction is downhill, +p or -p */ gsl_blas_ddot (p, gradient, &pg); dir = (pg >= 0.0) ? +1.0 : -1.0; /* Compute new trial point at x_c= x - step * p, where p is the current direction */ take_step (x, p, stepc, dir / pnorm, x1, dx); /* Evaluate function and gradient at new point xc */ fc = GSL_MULTIMIN_FN_EVAL_F (fdf, x1); if (fc < fa) { /* Success, reduced the function value */ state->step = stepc * 2.0; *f = fc; gsl_vector_memcpy (x, x1); GSL_MULTIMIN_FN_EVAL_DF (fdf, x1, gradient); return GSL_SUCCESS; } #ifdef DEBUG printf ("got stepc = %g fc = %g\n", stepc, fc); #endif /* Do a line minimisation in the region (xa,fa) (xc,fc) to find an intermediate (xb,fb) satisifying fa > fb < fc. Choose an initial xb based on parabolic interpolation */ intermediate_point (fdf, x, p, dir / pnorm, pg, stepa, stepc, fa, fc, x1, dx1, gradient, &stepb, &fb); if (stepb == 0.0) { return GSL_ENOPROG; } minimize (fdf, x, p, dir / pnorm, stepa, stepb, stepc, fa, fb, fc, tol, x1, dx1, x2, dx, gradient, &(state->step), f, &g1norm); gsl_vector_memcpy (x, x2); /* Choose a new conjugate direction for the next step */ state->iter = (state->iter + 1) % x->size; if (state->iter == 0) { gsl_vector_memcpy (p, gradient); state->pnorm = g1norm; } else { /* p' = g1 - beta * p */ double g0g1, beta; gsl_blas_daxpy (-1.0, gradient, g0); /* g0' = g0 - g1 */ gsl_blas_ddot(g0, gradient, &g0g1); /* g1g0 = (g0-g1).g1 */ beta = g0g1 / (g0norm*g0norm); /* beta = -((g1 - g0).g1)/(g0.g0) */ gsl_blas_dscal (-beta, p); gsl_blas_daxpy (1.0, gradient, p); state->pnorm = gsl_blas_dnrm2 (p); } state->g0norm = g1norm; gsl_vector_memcpy (g0, gradient); #ifdef DEBUG printf ("updated conjugate directions\n"); printf ("p: "); gsl_vector_fprintf (stdout, p, "%g"); printf ("g: "); gsl_vector_fprintf (stdout, gradient, "%g"); #endif return GSL_SUCCESS; } static const gsl_multimin_fdfminimizer_type conjugate_pr_type = { "conjugate_pr", /* name */ sizeof (conjugate_pr_state_t), &conjugate_pr_alloc, &conjugate_pr_set, &conjugate_pr_iterate, &conjugate_pr_restart, &conjugate_pr_free }; const gsl_multimin_fdfminimizer_type * gsl_multimin_fdfminimizer_conjugate_pr = &conjugate_pr_type; sources_5316/external/gsl/templates_off.h0000664000176700017670000000204111705263724017341 0ustar paulpaul#ifdef FUNCTION #undef FUNCTION #endif #ifdef CONCAT4 #undef CONCAT4 #endif #ifdef CONCAT4x #undef CONCAT4x #endif #ifdef CONCAT3 #undef CONCAT3 #endif #ifdef CONCAT3x #undef CONCAT3x #endif #ifdef CONCAT2 #undef CONCAT2 #endif #ifdef CONCAT2x #undef CONCAT2x #endif #ifdef TYPE #undef TYPE #endif #ifdef REAL_TYPE #undef REAL_TYPE #endif #ifdef QUALIFIED_TYPE #undef QUALIFIED_TYPE #endif #ifdef VIEW #undef VIEW #endif #ifdef REAL_VIEW #undef REAL_VIEW #endif #ifdef QUALIFIED_VIEW #undef QUALIFIED_VIEW #endif #ifdef QUALIFIED_REAL_TYPE #undef QUALIFIED_REAL_TYPE #endif #ifdef QUALIFIED_REAL_VIEW #undef QUALIFIED_REAL_VIEW #endif #ifdef USES_LONGDOUBLE #undef USES_LONGDOUBLE #endif #ifdef SHORT_REAL #undef SHORT_REAL #endif #ifndef USE_QUALIFIER #ifdef QUALIFIER #undef QUALIFIER #endif #endif #undef BASE #undef BASE_EPSILON #undef SHORT #undef ATOMIC #undef MULTIPLICITY #undef IN_FORMAT #undef OUT_FORMAT #undef ATOMIC_IO #undef ZERO #undef ONE #undef NAME #undef STRING #undef EXPAND #undef UNSIGNED #ifdef FP #undef FP #endif sources_5316/external/gsl/gsl_ieee-utils__fp-irix.c0000664000176700017670000000541011723710247021213 0ustar paulpaul/* ieee-utils/fp-irix.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Tim Mooney * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { fp_except mode = 0 ; fp_rnd rnd = 0 ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("IRIX only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("IRIX only supports default precision rounding", GSL_EUNSUP) ; break ; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("IRIX only supports default precision rounding", GSL_EUNSUP) ; break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: rnd = FP_RN ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_DOWN: rnd = FP_RM ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_UP: rnd = FP_RP ; fpsetround (rnd) ; break ; case GSL_IEEE_ROUND_TO_ZERO: rnd = FP_RZ ; fpsetround (rnd) ; break ; default: rnd = FP_RN ; fpsetround (rnd) ; } /* Turn on all the exceptions apart from 'inexact' */ mode = FP_X_INV | FP_X_DZ | FP_X_OFL | FP_X_UFL ; if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ FP_X_INV ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("IRIX does not support the denormalized operand exception. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ FP_X_DZ ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ FP_X_OFL ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ FP_X_UFL ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode |= FP_X_IMP ; } else { mode &= ~ FP_X_IMP ; } fpsetmask (mode) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_matrix__init.c0000664000176700017670000000362611723710247020046 0ustar paulpaul#include "gsl__config.h" #include "gsl_errno.h" #include "gsl_matrix.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__init_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_specfunc__beta.c0000664000176700017670000001152311723710247020313 0ustar paulpaul/* specfunc/beta.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_log.h" #include "gsl_sf_psi.h" #include "gsl_sf_gamma.h" #include "gsl_specfunc__error.h" static double isnegint (const double x) { return (x < 0) && (x == floor(x)); } int gsl_sf_lnbeta_e(const double x, const double y, gsl_sf_result * result) { double sgn; int status = gsl_sf_lnbeta_sgn_e(x,y,result,&sgn); if (sgn == -1) { DOMAIN_ERROR(result); } return status; } int gsl_sf_lnbeta_sgn_e(const double x, const double y, gsl_sf_result * result, double * sgn) { /* CHECK_POINTER(result) */ if(x == 0.0 || y == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result); } else if (isnegint(x) || isnegint(y)) { *sgn = 0.0; DOMAIN_ERROR(result); /* not defined for negative integers */ } /* See if we can handle the postive case with min/max < 0.2 */ if (x > 0 && y > 0) { const double max = GSL_MAX(x,y); const double min = GSL_MIN(x,y); const double rat = min/max; if(rat < 0.2) { /* min << max, so be careful * with the subtraction */ double lnpre_val; double lnpre_err; double lnpow_val; double lnpow_err; double t1, t2, t3; gsl_sf_result lnopr; gsl_sf_result gsx, gsy, gsxy; gsl_sf_gammastar_e(x, &gsx); gsl_sf_gammastar_e(y, &gsy); gsl_sf_gammastar_e(x+y, &gsxy); gsl_sf_log_1plusx_e(rat, &lnopr); lnpre_val = log(gsx.val*gsy.val/gsxy.val * M_SQRT2*M_SQRTPI); lnpre_err = gsx.err/gsx.val + gsy.err/gsy.val + gsxy.err/gsxy.val; t1 = min*log(rat); t2 = 0.5*log(min); t3 = (x+y-0.5)*lnopr.val; lnpow_val = t1 - t2 - t3; lnpow_err = GSL_DBL_EPSILON * (fabs(t1) + fabs(t2) + fabs(t3)); lnpow_err += fabs(x+y-0.5) * lnopr.err; result->val = lnpre_val + lnpow_val; result->err = lnpre_err + lnpow_err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *sgn = 1.0; return GSL_SUCCESS; } } /* General case - Fallback */ { gsl_sf_result lgx, lgy, lgxy; double sgx, sgy, sgxy, xy = x+y; int stat_gx = gsl_sf_lngamma_sgn_e(x, &lgx, &sgx); int stat_gy = gsl_sf_lngamma_sgn_e(y, &lgy, &sgy); int stat_gxy = gsl_sf_lngamma_sgn_e(xy, &lgxy, &sgxy); *sgn = sgx * sgy * sgxy; result->val = lgx.val + lgy.val - lgxy.val; result->err = lgx.err + lgy.err + lgxy.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(lgx.val) + fabs(lgy.val) + fabs(lgxy.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_gx, stat_gy, stat_gxy); } } int gsl_sf_beta_e(const double x, const double y, gsl_sf_result * result) { if((x > 0 && y > 0) && x < 50.0 && y < 50.0) { /* Handle the easy case */ gsl_sf_result gx, gy, gxy; gsl_sf_gamma_e(x, &gx); gsl_sf_gamma_e(y, &gy); gsl_sf_gamma_e(x+y, &gxy); result->val = (gx.val*gy.val)/gxy.val; result->err = gx.err * fabs(gy.val/gxy.val); result->err += gy.err * fabs(gx.val/gxy.val); result->err += fabs((gx.val*gy.val)/(gxy.val*gxy.val)) * gxy.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if (isnegint(x) || isnegint(y)) { DOMAIN_ERROR(result); } else if (isnegint(x+y)) { /* infinity in the denominator */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result lb; double sgn; int stat_lb = gsl_sf_lnbeta_sgn_e(x, y, &lb, &sgn); if(stat_lb == GSL_SUCCESS) { int status = gsl_sf_exp_err_e(lb.val, lb.err, result); result->val *= sgn; return status; } else { result->val = 0.0; result->err = 0.0; return stat_lb; } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_lnbeta(const double x, const double y) { EVAL_RESULT(gsl_sf_lnbeta_e(x, y, &result)); } double gsl_sf_beta(const double x, const double y) { EVAL_RESULT(gsl_sf_beta_e(x, y, &result)); } sources_5316/external/gsl/gsl_sf__hyperg.c0000644000176700017670000002110210710226217017462 0ustar paulpaul/* specfunc/hyperg.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Miscellaneous implementations of use * for evaluation of hypergeometric functions. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf__error.h" #include "gsl_sf__hyperg.h" #define SUM_LARGE (1.0e-5*GSL_DBL_MAX) int gsl_sf_hyperg_1F1_series_e(const double a, const double b, const double x, gsl_sf_result * result ) { double an = a; double bn = b; double n = 1.0; double del = 1.0; double abs_del = 1.0; double max_abs_del = 1.0; double sum_val = 1.0; double sum_err = 0.0; while(abs_del/fabs(sum_val) > 0.25*GSL_DBL_EPSILON) { double u, abs_u; if(bn == 0.0) { DOMAIN_ERROR(result); } if(an == 0.0) { result->val = sum_val; result->err = sum_err; result->err += 2.0 * GSL_DBL_EPSILON * n * fabs(sum_val); return GSL_SUCCESS; } if (n > 10000.0) { result->val = sum_val; result->err = sum_err; GSL_ERROR ("hypergeometric series failed to converge", GSL_EFAILED); } u = x * (an/(bn*n)); abs_u = fabs(u); if(abs_u > 1.0 && max_abs_del > GSL_DBL_MAX/abs_u) { result->val = sum_val; result->err = fabs(sum_val); GSL_ERROR ("overflow", GSL_EOVRFLW); } del *= u; sum_val += del; if(fabs(sum_val) > SUM_LARGE) { result->val = sum_val; result->err = fabs(sum_val); GSL_ERROR ("overflow", GSL_EOVRFLW); } abs_del = fabs(del); max_abs_del = GSL_MAX_DBL(abs_del, max_abs_del); sum_err += 2.0*GSL_DBL_EPSILON*abs_del; an += 1.0; bn += 1.0; n += 1.0; } result->val = sum_val; result->err = sum_err; result->err += abs_del; result->err += 2.0 * GSL_DBL_EPSILON * n * fabs(sum_val); return GSL_SUCCESS; } int gsl_sf_hyperg_1F1_large_b_e(const double a, const double b, const double x, gsl_sf_result * result) { if(fabs(x/b) < 1.0) { const double u = x/b; const double v = 1.0/(1.0-u); const double pre = pow(v,a); const double uv = u*v; const double uv2 = uv*uv; const double t1 = a*(a+1.0)/(2.0*b)*uv2; const double t2a = a*(a+1.0)/(24.0*b*b)*uv2; const double t2b = 12.0 + 16.0*(a+2.0)*uv + 3.0*(a+2.0)*(a+3.0)*uv2; const double t2 = t2a*t2b; result->val = pre * (1.0 - t1 + t2); result->err = pre * GSL_DBL_EPSILON * (1.0 + fabs(t1) + fabs(t2)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { DOMAIN_ERROR(result); } } int gsl_sf_hyperg_U_large_b_e(const double a, const double b, const double x, gsl_sf_result * result, double * ln_multiplier ) { double N = floor(b); /* b = N + eps */ double eps = b - N; if(fabs(eps) < GSL_SQRT_DBL_EPSILON) { double lnpre_val; double lnpre_err; gsl_sf_result M; if(b > 1.0) { double tmp = (1.0-b)*log(x); gsl_sf_result lg_bm1; gsl_sf_result lg_a; gsl_sf_lngamma_e(b-1.0, &lg_bm1); gsl_sf_lngamma_e(a, &lg_a); lnpre_val = tmp + x + lg_bm1.val - lg_a.val; lnpre_err = lg_bm1.err + lg_a.err + GSL_DBL_EPSILON * (fabs(x) + fabs(tmp)); gsl_sf_hyperg_1F1_large_b_e(1.0-a, 2.0-b, -x, &M); } else { gsl_sf_result lg_1mb; gsl_sf_result lg_1pamb; gsl_sf_lngamma_e(1.0-b, &lg_1mb); gsl_sf_lngamma_e(1.0+a-b, &lg_1pamb); lnpre_val = lg_1mb.val - lg_1pamb.val; lnpre_err = lg_1mb.err + lg_1pamb.err; gsl_sf_hyperg_1F1_large_b_e(a, b, x, &M); } if(lnpre_val > GSL_LOG_DBL_MAX-10.0) { result->val = M.val; result->err = M.err; *ln_multiplier = lnpre_val; GSL_ERROR ("overflow", GSL_EOVRFLW); } else { gsl_sf_result epre; int stat_e = gsl_sf_exp_err_e(lnpre_val, lnpre_err, &epre); result->val = epre.val * M.val; result->err = epre.val * M.err + epre.err * fabs(M.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *ln_multiplier = 0.0; return stat_e; } } else { double omb_lnx = (1.0-b)*log(x); gsl_sf_result lg_1mb; double sgn_1mb; gsl_sf_result lg_1pamb; double sgn_1pamb; gsl_sf_result lg_bm1; double sgn_bm1; gsl_sf_result lg_a; double sgn_a; gsl_sf_result M1, M2; double lnpre1_val, lnpre2_val; double lnpre1_err, lnpre2_err; double sgpre1, sgpre2; gsl_sf_hyperg_1F1_large_b_e( a, b, x, &M1); gsl_sf_hyperg_1F1_large_b_e(1.0-a, 2.0-b, x, &M2); gsl_sf_lngamma_sgn_e(1.0-b, &lg_1mb, &sgn_1mb); gsl_sf_lngamma_sgn_e(1.0+a-b, &lg_1pamb, &sgn_1pamb); gsl_sf_lngamma_sgn_e(b-1.0, &lg_bm1, &sgn_bm1); gsl_sf_lngamma_sgn_e(a, &lg_a, &sgn_a); lnpre1_val = lg_1mb.val - lg_1pamb.val; lnpre1_err = lg_1mb.err + lg_1pamb.err; lnpre2_val = lg_bm1.val - lg_a.val - omb_lnx - x; lnpre2_err = lg_bm1.err + lg_a.err + GSL_DBL_EPSILON * (fabs(omb_lnx)+fabs(x)); sgpre1 = sgn_1mb * sgn_1pamb; sgpre2 = sgn_bm1 * sgn_a; if(lnpre1_val > GSL_LOG_DBL_MAX-10.0 || lnpre2_val > GSL_LOG_DBL_MAX-10.0) { double max_lnpre_val = GSL_MAX(lnpre1_val,lnpre2_val); double max_lnpre_err = GSL_MAX(lnpre1_err,lnpre2_err); double lp1 = lnpre1_val - max_lnpre_val; double lp2 = lnpre2_val - max_lnpre_val; double t1 = sgpre1*exp(lp1); double t2 = sgpre2*exp(lp2); result->val = t1*M1.val + t2*M2.val; result->err = fabs(t1)*M1.err + fabs(t2)*M2.err; result->err += GSL_DBL_EPSILON * exp(max_lnpre_err) * (fabs(t1*M1.val) + fabs(t2*M2.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *ln_multiplier = max_lnpre_val; GSL_ERROR ("overflow", GSL_EOVRFLW); } else { double t1 = sgpre1*exp(lnpre1_val); double t2 = sgpre2*exp(lnpre2_val); result->val = t1*M1.val + t2*M2.val; result->err = fabs(t1) * M1.err + fabs(t2)*M2.err; result->err += GSL_DBL_EPSILON * (exp(lnpre1_err)*fabs(t1*M1.val) + exp(lnpre2_err)*fabs(t2*M2.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *ln_multiplier = 0.0; return GSL_SUCCESS; } } } /* [Carlson, p.109] says the error in truncating this asymptotic series * is less than the absolute value of the first neglected term. * * A termination argument is provided, so that the series will * be summed at most up to n=n_trunc. If n_trunc is set negative, * then the series is summed until it appears to start diverging. */ int gsl_sf_hyperg_2F0_series_e(const double a, const double b, const double x, int n_trunc, gsl_sf_result * result ) { const int maxiter = 2000; double an = a; double bn = b; double n = 1.0; double sum = 1.0; double del = 1.0; double abs_del = 1.0; double max_abs_del = 1.0; double last_abs_del = 1.0; while(abs_del/fabs(sum) > GSL_DBL_EPSILON && n < maxiter) { double u = an * (bn/n * x); double abs_u = fabs(u); if(abs_u > 1.0 && (max_abs_del > GSL_DBL_MAX/abs_u)) { result->val = sum; result->err = fabs(sum); GSL_ERROR ("overflow", GSL_EOVRFLW); } del *= u; sum += del; abs_del = fabs(del); if(abs_del > last_abs_del) break; /* series is probably starting to grow */ last_abs_del = abs_del; max_abs_del = GSL_MAX(abs_del, max_abs_del); an += 1.0; bn += 1.0; n += 1.0; if(an == 0.0 || bn == 0.0) break; /* series terminated */ if(n_trunc >= 0 && n >= n_trunc) break; /* reached requested timeout */ } result->val = sum; result->err = GSL_DBL_EPSILON * n + abs_del; if(n >= maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } sources_5316/external/gsl/gsl_specfunc__cheb_eval.c0000664000176700017670000000122011723710247021301 0ustar paulpaul static inline int cheb_eval_e(const cheb_series * cs, const double x, gsl_sf_result * result) { int j; double d = 0.0; double dd = 0.0; double y = (2.0*x - cs->a - cs->b) / (cs->b - cs->a); double y2 = 2.0 * y; double e = 0.0; for(j = cs->order; j>=1; j--) { double temp = d; d = y2*d - dd + cs->c[j]; e += fabs(y2*temp) + fabs(dd) + fabs(cs->c[j]); dd = temp; } { double temp = d; d = y*d - dd + 0.5 * cs->c[0]; e += fabs(y*temp) + fabs(dd) + 0.5 * fabs(cs->c[0]); } result->val = d; result->err = GSL_DBL_EPSILON * e + fabs(cs->c[cs->order]); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__source_gemm_c.h0000664000176700017670000001352711705263724021503 0ustar paulpaul/* blas/source_gemm_c.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; INDEX n1, n2; INDEX ldf, ldg; int conjF, conjG, TransF, TransG; const BASE *F, *G; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; if (Order == CblasRowMajor) { n1 = M; n2 = N; F = (const BASE *)A; ldf = lda; conjF = (TransA == CblasConjTrans) ? -1 : 1; TransF = (TransA == CblasNoTrans) ? CblasNoTrans : CblasTrans; G = (const BASE *)B; ldg = ldb; conjG = (TransB == CblasConjTrans) ? -1 : 1; TransG = (TransB == CblasNoTrans) ? CblasNoTrans : CblasTrans; } else { n1 = N; n2 = M; F = (const BASE *)B; ldf = ldb; conjF = (TransB == CblasConjTrans) ? -1 : 1; TransF = (TransB == CblasNoTrans) ? CblasNoTrans : CblasTrans; G = (const BASE *)A; ldg = lda; conjG = (TransA == CblasConjTrans) ? -1 : 1; TransG = (TransA == CblasNoTrans) ? CblasNoTrans : CblasTrans; } /* form y := beta*y */ if (beta_real == 0.0 && beta_imag == 0.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Cij_real = REAL(C, ldc * i + j); const BASE Cij_imag = IMAG(C, ldc * i + j); REAL(C, ldc * i + j) = beta_real * Cij_real - beta_imag * Cij_imag; IMAG(C, ldc * i + j) = beta_real * Cij_imag + beta_imag * Cij_real; } } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; if (TransF == CblasNoTrans && TransG == CblasNoTrans) { /* form C := alpha*A*B + C */ for (k = 0; k < K; k++) { for (i = 0; i < n1; i++) { const BASE Fik_real = CONST_REAL(F, ldf * i + k); const BASE Fik_imag = conjF * CONST_IMAG(F, ldf * i + k); const BASE temp_real = alpha_real * Fik_real - alpha_imag * Fik_imag; const BASE temp_imag = alpha_real * Fik_imag + alpha_imag * Fik_real; if (!(temp_real == 0.0 && temp_imag == 0.0)) { for (j = 0; j < n2; j++) { const BASE Gkj_real = CONST_REAL(G, ldg * k + j); const BASE Gkj_imag = conjG * CONST_IMAG(G, ldg * k + j); REAL(C, ldc * i + j) += temp_real * Gkj_real - temp_imag * Gkj_imag; IMAG(C, ldc * i + j) += temp_real * Gkj_imag + temp_imag * Gkj_real; } } } } } else if (TransF == CblasNoTrans && TransG == CblasTrans) { /* form C := alpha*A*B' + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Fik_real = CONST_REAL(F, ldf * i + k); const BASE Fik_imag = conjF * CONST_IMAG(F, ldf * i + k); const BASE Gjk_real = CONST_REAL(G, ldg * j + k); const BASE Gjk_imag = conjG * CONST_IMAG(G, ldg * j + k); temp_real += Fik_real * Gjk_real - Fik_imag * Gjk_imag; temp_imag += Fik_real * Gjk_imag + Fik_imag * Gjk_real; } REAL(C, ldc * i + j) += alpha_real * temp_real - alpha_imag * temp_imag; IMAG(C, ldc * i + j) += alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (TransF == CblasTrans && TransG == CblasNoTrans) { for (k = 0; k < K; k++) { for (i = 0; i < n1; i++) { const BASE Fki_real = CONST_REAL(F, ldf * k + i); const BASE Fki_imag = conjF * CONST_IMAG(F, ldf * k + i); const BASE temp_real = alpha_real * Fki_real - alpha_imag * Fki_imag; const BASE temp_imag = alpha_real * Fki_imag + alpha_imag * Fki_real; if (!(temp_real == 0.0 && temp_imag == 0.0)) { for (j = 0; j < n2; j++) { const BASE Gkj_real = CONST_REAL(G, ldg * k + j); const BASE Gkj_imag = conjG * CONST_IMAG(G, ldg * k + j); REAL(C, ldc * i + j) += temp_real * Gkj_real - temp_imag * Gkj_imag; IMAG(C, ldc * i + j) += temp_real * Gkj_imag + temp_imag * Gkj_real; } } } } } else if (TransF == CblasTrans && TransG == CblasTrans) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Fki_real = CONST_REAL(F, ldf * k + i); const BASE Fki_imag = conjF * CONST_IMAG(F, ldf * k + i); const BASE Gjk_real = CONST_REAL(G, ldg * j + k); const BASE Gjk_imag = conjG * CONST_IMAG(G, ldg * j + k); temp_real += Fki_real * Gjk_real - Fki_imag * Gjk_imag; temp_imag += Fki_real * Gjk_imag + Fki_imag * Gjk_real; } REAL(C, ldc * i + j) += alpha_real * temp_real - alpha_imag * temp_imag; IMAG(C, ldc * i + j) += alpha_real * temp_imag + alpha_imag * temp_real; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_specfunc__bessel_Y0.c0000664000176700017670000000713511723710247021231 0ustar paulpaul/* specfunc/bessel_Y0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_amp_phase.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besy0, 1980 version, w. fullerton */ /* chebyshev expansions series for by0 on the interval 0. to 1.60000d+01 with weighted error 1.20e-17 log weighted error 16.92 significant figures required 16.15 decimal places required 17.48 */ static double by0_data[13] = { -0.011277839392865573, -0.128345237560420350, -0.104378847997942490, 0.023662749183969695, -0.002090391647700486, 0.000103975453939057, -0.000003369747162423, 0.000000077293842676, -0.000000001324976772, 0.000000000017648232, -0.000000000000188105, 0.000000000000001641, -0.000000000000000011 }; static cheb_series by0_cs = { by0_data, 12, -1, 1, 8 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Y0_e(const double x, gsl_sf_result * result) { const double two_over_pi = 2.0/M_PI; const double xmax = 1.0/GSL_DBL_EPSILON; /* CHECK_POINTER(result) */ if (x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 4.0) { gsl_sf_result J0; gsl_sf_result c; int stat_J0 = gsl_sf_bessel_J0_e(x, &J0); cheb_eval_e(&by0_cs, 0.125*x*x-1.0, &c); result->val = two_over_pi*(-M_LN2 + log(x))*J0.val + 0.375 + c.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + c.err; return stat_J0; } else if(x < xmax) { /* Leading behaviour of phase is x, which is exact, * so the error is bounded. */ const double z = 32.0/(x*x) - 1.0; gsl_sf_result c1; gsl_sf_result c2; gsl_sf_result sp; const int stat_c1 = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bm0_cs, z, &c1); const int stat_c2 = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bth0_cs, z, &c2); const int stat_sp = gsl_sf_bessel_sin_pi4_e(x, c2.val/x, &sp); const double sqrtx = sqrt(x); const double ampl = (0.75 + c1.val) / sqrtx; result->val = ampl * sp.val; result->err = fabs(sp.val) * c1.err/sqrtx + fabs(ampl) * sp.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_sp, stat_c1, stat_c2); } else { UNDERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_Y0(const double x) { EVAL_RESULT(gsl_sf_bessel_Y0_e(x, &result)); } sources_5316/external/gsl/gsl_cdf__flatinv.c0000664000176700017670000000241011723710247017764 0ustar paulpaul/* cdf/flatinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_cdf.h" double gsl_cdf_flat_Pinv (const double P, const double a, const double b) { double x; if (P == 1.0) { return b; } else if (P == 0.0) { return a; } x = (1 - P) * a + P * b; return x; } double gsl_cdf_flat_Qinv (const double Q, const double a, const double b) { double x; if (Q == 0.0) { return b; } else if (Q == 1.0) { return a; } x = Q * a + (1 - Q) * b; return x; } sources_5316/external/gsl/gsl_cblas__cher.c0000664000176700017670000000051411723710247017575 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cher (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const void *X, const int incX, void *A, const int lda) { #define BASE float #include "gsl_cblas__source_her.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__check.h0000664000176700017670000000017611705263724020467 0ustar paulpaul/* check for underflow */ #define CHECK_UNDERFLOW(r) if (fabs((r)->val) < GSL_DBL_MIN) GSL_ERROR("underflow", GSL_EUNDRFLW); sources_5316/external/gsl/gsl_cblas__dgemm.c0000664000176700017670000000075011723710247017747 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dgemm (const enum CBLAS_ORDER Order, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_TRANSPOSE TransB, const int M, const int N, const int K, const double alpha, const double *A, const int lda, const double *B, const int ldb, const double beta, double *C, const int ldc) { #define BASE double #include "gsl_cblas__source_gemm_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__ztbsv.c0000664000176700017670000000067011723710247020027 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" #include "gsl_cblas__hypot.c" void cblas_ztbsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const void *A, const int lda, void *X, const int incX) { #define BASE double #include "gsl_cblas__source_tbsv_c.h" #undef BASE } sources_5316/external/gsl/gsl_fft__real_main.c0000664000176700017670000000765411723710247020312 0ustar paulpaul/* fft/real_main.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_fft_real.h" #include "gsl_fft__real_pass.h" int FUNCTION(gsl_fft_real,transform) (BASE data[], const size_t stride, const size_t n, const TYPE(gsl_fft_real_wavetable) * wavetable, TYPE(gsl_fft_real_workspace) * work) { const size_t nf = wavetable->nf; size_t i; size_t q, product = 1; size_t tskip; size_t product_1; BASE *const scratch = work->scratch; TYPE(gsl_complex) *twiddle1, *twiddle2, *twiddle3, *twiddle4; size_t state = 0; BASE *in = data; size_t istride = stride ; BASE *out = scratch; size_t ostride = 1 ; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } if (n == 1) { /* FFT of one data point is the identity */ return 0; } if (n != wavetable->n) { GSL_ERROR ("wavetable does not match length of data", GSL_EINVAL); } if (n != work->n) { GSL_ERROR ("workspace does not match length of data", GSL_EINVAL); } for (i = 0; i < nf; i++) { const size_t factor = wavetable->factor[i]; product_1 = product; product *= factor; q = n / product; tskip = (product_1 + 1) / 2 - 1; if (state == 0) { in = data; istride = stride; out = scratch; ostride = 1; state = 1; } else { in = scratch; istride = 1; out = data; ostride = stride; state = 0; } if (factor == 2) { twiddle1 = wavetable->twiddle[i]; FUNCTION(fft_real,pass_2) (in, istride, out, ostride, product, n, twiddle1); } else if (factor == 3) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + tskip; FUNCTION(fft_real,pass_3) (in, istride, out, ostride, product, n, twiddle1, twiddle2); } else if (factor == 4) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + tskip; twiddle3 = twiddle2 + tskip; FUNCTION(fft_real,pass_4) (in, istride, out, ostride, product, n, twiddle1, twiddle2, twiddle3); } else if (factor == 5) { twiddle1 = wavetable->twiddle[i]; twiddle2 = twiddle1 + tskip; twiddle3 = twiddle2 + tskip; twiddle4 = twiddle3 + tskip; FUNCTION(fft_real,pass_5) (in, istride, out, ostride, product, n, twiddle1, twiddle2, twiddle3, twiddle4); } else { twiddle1 = wavetable->twiddle[i]; FUNCTION(fft_real,pass_n) (in, istride, out, ostride, factor, product, n, twiddle1); } } if (state == 1) /* copy results back from scratch to data */ { for (i = 0; i < n; i++) { data[stride*i] = scratch[i] ; } } return 0; } sources_5316/external/gsl/gsl_fft__real_pass_n.c0000664000176700017670000002052211723710247020636 0ustar paulpaul/* fft/real_pass_n.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_real,pass_n) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t factor, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]) { size_t k, k1; const size_t m = n / factor; const size_t q = n / product; const size_t product_1 = product / factor; size_t e1, e2; const double d_theta = 2.0 * M_PI / ((double) factor); const ATOMIC cos_d_theta = cos (d_theta); const ATOMIC sin_d_theta = sin (d_theta); for (k1 = 0; k1 < q; k1++) { /* compute x = W(factor) z, for z real */ ATOMIC dw_real = 1.0, dw_imag = 0.0; for (e1 = 0; e1 <= factor - e1; e1++) { ATOMIC sum_real = 0.0; ATOMIC sum_imag = 0.0; ATOMIC w_real = 1.0, w_imag = 0.0; if (e1 > 0) { ATOMIC tmp_real = dw_real * cos_d_theta + dw_imag * sin_d_theta; ATOMIC tmp_imag = -dw_real * sin_d_theta + dw_imag * cos_d_theta; dw_real = tmp_real; dw_imag = tmp_imag; } for (e2 = 0; e2 < factor; e2++) { ATOMIC z_real = VECTOR(in,istride,k1 * product_1 + e2 * m); if (e2 > 0) { ATOMIC tmp_real = dw_real * w_real - dw_imag * w_imag; ATOMIC tmp_imag = dw_real * w_imag + dw_imag * w_real; w_real = tmp_real; w_imag = tmp_imag; } sum_real += w_real * z_real; sum_imag += w_imag * z_real; } if (e1 == 0) { const size_t to0 = product * k1; VECTOR(out,ostride,to0) = sum_real; } else if (e1 < factor - e1) { const size_t to0 = k1 * product + 2 * e1 * product_1 - 1; VECTOR(out,ostride,to0) = sum_real; VECTOR(out,ostride,to0 + 1) = sum_imag; } else if (e1 == factor - e1) { const size_t to0 = k1 * product + 2 * e1 * product_1 - 1; VECTOR(out,ostride,to0) = sum_real; } } } if (product_1 == 1) return; for (k = 1; k < (product_1 + 1) / 2; k++) { for (k1 = 0; k1 < q; k1++) { ATOMIC dw_real = 1.0, dw_imag = 0.0; for (e1 = 0; e1 < factor; e1++) { ATOMIC sum_real = 0.0, sum_imag = 0.0; ATOMIC w_real = 1.0, w_imag = 0.0; if (e1 > 0) { const ATOMIC tmp_real = dw_real * cos_d_theta + dw_imag * sin_d_theta; const ATOMIC tmp_imag = -dw_real * sin_d_theta + dw_imag * cos_d_theta; dw_real = tmp_real; dw_imag = tmp_imag; } for (e2 = 0; e2 < factor; e2++) { int tskip = (product_1 + 1) / 2 - 1; const size_t from0 = k1 * product_1 + 2 * k + e2 * m - 1; ATOMIC tw_real, tw_imag; ATOMIC z_real, z_imag; if (e2 == 0) { tw_real = 1.0; tw_imag = 0.0; } else { const size_t t_index = (k - 1) + (e2 - 1) * tskip; tw_real = GSL_REAL(twiddle[t_index]); tw_imag = -GSL_IMAG(twiddle[t_index]); } { const ATOMIC f0_real = VECTOR(in,istride,from0); const ATOMIC f0_imag = VECTOR(in,istride,from0 + 1); z_real = tw_real * f0_real - tw_imag * f0_imag; z_imag = tw_real * f0_imag + tw_imag * f0_real; } if (e2 > 0) { const ATOMIC tmp_real = dw_real * w_real - dw_imag * w_imag; const ATOMIC tmp_imag = dw_real * w_imag + dw_imag * w_real; w_real = tmp_real; w_imag = tmp_imag; } sum_real += w_real * z_real - w_imag * z_imag; sum_imag += w_real * z_imag + w_imag * z_real; } if (e1 < factor - e1) { const size_t to0 = k1 * product - 1 + 2 * e1 * product_1 + 2 * k; VECTOR(out,ostride,to0) = sum_real; VECTOR(out,ostride,to0 + 1) = sum_imag; } else { const size_t to0 = k1 * product - 1 + 2 * (factor - e1) * product_1 - 2 * k; VECTOR(out,ostride,to0) = sum_real; VECTOR(out,ostride,to0 + 1) = -sum_imag; } } } } if (product_1 % 2 == 1) return; { double tw_arg = M_PI / ((double) factor); ATOMIC cos_tw_arg = cos (tw_arg); ATOMIC sin_tw_arg = -sin (tw_arg); for (k1 = 0; k1 < q; k1++) { ATOMIC dw_real = 1.0, dw_imag = 0.0; for (e1 = 0; e1 < factor; e1++) { ATOMIC z_real, z_imag; ATOMIC sum_real = 0.0; ATOMIC sum_imag = 0.0; ATOMIC w_real = 1.0, w_imag = 0.0; ATOMIC tw_real = 1.0, tw_imag = 0.0; if (e1 > 0) { ATOMIC t_real = dw_real * cos_d_theta + dw_imag * sin_d_theta; ATOMIC t_imag = -dw_real * sin_d_theta + dw_imag * cos_d_theta; dw_real = t_real; dw_imag = t_imag; } for (e2 = 0; e2 < factor; e2++) { if (e2 > 0) { ATOMIC tmp_real = tw_real * cos_tw_arg - tw_imag * sin_tw_arg; ATOMIC tmp_imag = tw_real * sin_tw_arg + tw_imag * cos_tw_arg; tw_real = tmp_real; tw_imag = tmp_imag; } if (e2 > 0) { ATOMIC tmp_real = dw_real * w_real - dw_imag * w_imag; ATOMIC tmp_imag = dw_real * w_imag + dw_imag * w_real; w_real = tmp_real; w_imag = tmp_imag; } { const size_t from0 = k1 * product_1 + 2 * k + e2 * m - 1; const ATOMIC f0_real = VECTOR(in,istride,from0); z_real = tw_real * f0_real; z_imag = tw_imag * f0_real; } sum_real += w_real * z_real - w_imag * z_imag; sum_imag += w_real * z_imag + w_imag * z_real; } if (e1 + 1 < factor - e1) { const size_t to0 = k1 * product - 1 + 2 * e1 * product_1 + 2 * k; VECTOR(out,ostride,to0) = sum_real; VECTOR(out,ostride,to0 + 1) = sum_imag; } else if (e1 + 1 == factor - e1) { const size_t to0 = k1 * product - 1 + 2 * e1 * product_1 + 2 * k; VECTOR(out,ostride,to0) = sum_real; } else { const size_t to0 = k1 * product - 1 + 2 * (factor - e1) * product_1 - 2 * k; VECTOR(out,ostride,to0) = sum_real; VECTOR(out,ostride,to0 + 1) = -sum_imag; } } } } return; } sources_5316/external/gsl/gsl_monte_miser.h0000664000176700017670000000430211705263724017701 0ustar paulpaul/* monte/gsl_monte_miser.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Michael Booth * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: MJB */ #ifndef __GSL_MONTE_MISER_H__ #define __GSL_MONTE_MISER_H__ #include "gsl_rng.h" #include "gsl_monte.h" #include "gsl_monte_plain.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t min_calls; size_t min_calls_per_bisection; double dither; double estimate_frac; double alpha; size_t dim; int estimate_style; int depth; int verbose; double * x; double * xmid; double * sigma_l; double * sigma_r; double * fmax_l; double * fmax_r; double * fmin_l; double * fmin_r; double * fsum_l; double * fsum_r; double * fsum2_l; double * fsum2_r; size_t * hits_l; size_t * hits_r; } gsl_monte_miser_state; int gsl_monte_miser_integrate(gsl_monte_function * f, const double xl[], const double xh[], size_t dim, size_t calls, gsl_rng *r, gsl_monte_miser_state* state, double *result, double *abserr); gsl_monte_miser_state* gsl_monte_miser_alloc(size_t dim); int gsl_monte_miser_init(gsl_monte_miser_state* state); void gsl_monte_miser_free(gsl_monte_miser_state* state); __END_DECLS #endif /* __GSL_MONTE_MISER_H__ */ sources_5316/external/gsl/gsl_ode-initval__rk2simp.c0000664000176700017670000002162211723710247021375 0ustar paulpaul/* ode-initval/rk2simp.c * * Copyright (C) 2004 Tuomo Keskitalo * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Runge-Kutta 2, Gaussian implicit. Also known as implicit midpoint rule. Non-linear equations solved by linearization, LU-decomposition and matrix inversion. For reference, see eg. Ascher, U.M., Petzold, L.R., Computer methods for ordinary differential and differential-algebraic equations, SIAM, Philadelphia, 1998. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_linalg.h" #include "gsl_ode-initval__odeiv_util.h" typedef struct { double *Y1; double *y0; double *y0_orig; double *ytmp; double *dfdy; /* Jacobian */ double *dfdt; /* time derivatives, not used */ double *y_onestep; gsl_permutation *p; } rk2simp_state_t; static void * rk2simp_alloc (size_t dim) { rk2simp_state_t *state = (rk2simp_state_t *) malloc (sizeof (rk2simp_state_t)); if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for rk2simp_state", GSL_ENOMEM); } state->Y1 = (double *) malloc (dim * sizeof (double)); if (state->Y1 == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for Y1", GSL_ENOMEM); } state->y0 = (double *) malloc (dim * sizeof (double)); if (state->y0 == 0) { free (state->Y1); free (state); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } state->y0_orig = (double *) malloc (dim * sizeof (double)); if (state->y0_orig == 0) { free (state->Y1); free (state->y0); free (state); GSL_ERROR_NULL ("failed to allocate space for y0_orig", GSL_ENOMEM); } state->ytmp = (double *) malloc (dim * sizeof (double)); if (state->ytmp == 0) { free (state->Y1); free (state->y0); free (state->y0_orig); free (state); GSL_ERROR_NULL ("failed to allocate space for ytmp", GSL_ENOMEM); } state->dfdy = (double *) malloc (dim * dim * sizeof (double)); if (state->dfdy == 0) { free (state->Y1); free (state->y0); free (state->y0_orig); free (state->ytmp); free (state); GSL_ERROR_NULL ("failed to allocate space for dfdy", GSL_ENOMEM); } state->dfdt = (double *) malloc (dim * sizeof (double)); if (state->dfdt == 0) { free (state->Y1); free (state->y0); free (state->y0_orig); free (state->ytmp); free (state->dfdy); free (state); GSL_ERROR_NULL ("failed to allocate space for dfdt", GSL_ENOMEM); } state->y_onestep = (double *) malloc (dim * sizeof (double)); if (state->y_onestep == 0) { free (state->Y1); free (state->y0); free (state->y0_orig); free (state->ytmp); free (state->dfdy); free (state->dfdt); free (state); GSL_ERROR_NULL ("failed to allocate space for y_onestep", GSL_ENOMEM); } state->p = gsl_permutation_alloc (dim); if (state->p == 0) { free (state->Y1); free (state->y0); free (state->y0_orig); free (state->ytmp); free (state->dfdy); free (state->dfdt); free (state); GSL_ERROR_NULL ("failed to allocate space for p", GSL_ENOMEM); } return state; } static int rk2simp_step (double *y, rk2simp_state_t * state, const double h, const double t, const size_t dim, const gsl_odeiv_system * sys) { /* Makes a Runge-Kutta 2nd order semi-implicit advance with step size h. y0 is initial values of variables y. The linearized semi-implicit equations to calculate are: Y1 = y0 + h/2 * (1 - h/2 * df/dy)^(-1) * f(t + h/2, y0) y = y0 + h * f(t + h/2, Y1) */ const double *y0 = state->y0; double *Y1 = state->Y1; double *ytmp = state->ytmp; size_t i; int s, ps; gsl_matrix_view J = gsl_matrix_view_array (state->dfdy, dim, dim); /* First solve Y1. Calculate the inverse matrix (1 - h/2 * df/dy)^-1 */ /* Create matrix to J */ s = GSL_ODEIV_JA_EVAL (sys, t, y0, state->dfdy, state->dfdt); if (s != GSL_SUCCESS) { return s; } gsl_matrix_scale (&J.matrix, -h / 2.0); gsl_matrix_add_diagonal(&J.matrix, 1.0); /* Invert it by LU-decomposition to invmat */ s += gsl_linalg_LU_decomp (&J.matrix, state->p, &ps); if (s != GSL_SUCCESS) { return GSL_EFAILED; } /* Evaluate f(t + h/2, y0) */ s = GSL_ODEIV_FN_EVAL (sys, t + 0.5 * h, y0, ytmp); if (s != GSL_SUCCESS) { return s; } /* Calculate Y1 = y0 + h/2 * ((1-h/2 * df/dy)^-1) ytmp */ { gsl_vector_const_view y0_view = gsl_vector_const_view_array(y0, dim); gsl_vector_view ytmp_view = gsl_vector_view_array(ytmp, dim); gsl_vector_view Y1_view = gsl_vector_view_array(Y1, dim); s = gsl_linalg_LU_solve (&J.matrix, state->p, &ytmp_view.vector, &Y1_view.vector); gsl_vector_scale (&Y1_view.vector, 0.5 * h); gsl_vector_add (&Y1_view.vector, &y0_view.vector); } /* And finally evaluation of f(t + h/2, Y1) and calculation of y */ s = GSL_ODEIV_FN_EVAL (sys, t + 0.5 * h, Y1, ytmp); if (s != GSL_SUCCESS) { return s; } for (i = 0; i < dim; i++) { y[i] = y0[i] + h * ytmp[i]; } return s; } static int rk2simp_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { rk2simp_state_t *state = (rk2simp_state_t *) vstate; size_t i; double *y0 = state->y0; double *y0_orig = state->y0_orig; double *y_onestep = state->y_onestep; /* Error estimation is done by step doubling procedure */ DBL_MEMCPY (y0, y, dim); /* Save initial values in case of failure */ DBL_MEMCPY (y0_orig, y, dim); /* First traverse h with one step (save to y_onestep) */ DBL_MEMCPY (y_onestep, y, dim); { int s = rk2simp_step (y_onestep, state, h, t, dim, sys); if (s != GSL_SUCCESS) { return s; } } /* Then with two steps with half step length (save to y) */ { int s = rk2simp_step (y, state, h / 2.0, t, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } DBL_MEMCPY (y0, y, dim); { int s = rk2simp_step (y, state, h / 2.0, t + h / 2.0, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } /* Derivatives at output */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } /* Error estimation */ for (i = 0; i < dim; i++) { yerr[i] = 4.0 * (y[i] - y_onestep[i]) / 3.0; } return GSL_SUCCESS; } static int rk2simp_reset (void *vstate, size_t dim) { rk2simp_state_t *state = (rk2simp_state_t *) vstate; DBL_ZERO_MEMSET (state->Y1, dim); DBL_ZERO_MEMSET (state->y0, dim); DBL_ZERO_MEMSET (state->y0_orig, dim); DBL_ZERO_MEMSET (state->ytmp, dim); DBL_ZERO_MEMSET (state->dfdt, dim * dim); DBL_ZERO_MEMSET (state->dfdt, dim); DBL_ZERO_MEMSET (state->y_onestep, dim); return GSL_SUCCESS; } static unsigned int rk2simp_order (void *vstate) { rk2simp_state_t *state = (rk2simp_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 2; } static void rk2simp_free (void *vstate) { rk2simp_state_t *state = (rk2simp_state_t *) vstate; free (state->Y1); free (state->y0); free (state->y0_orig); free (state->ytmp); free (state->dfdy); free (state->dfdt); free (state->y_onestep); gsl_permutation_free (state->p); free (state); } static const gsl_odeiv_step_type rk2simp_type = { "rk2simp", /* name */ 0, /* can use dydt_in? */ 1, /* gives exact dydt_out? */ &rk2simp_alloc, &rk2simp_apply, &rk2simp_reset, &rk2simp_order, &rk2simp_free }; const gsl_odeiv_step_type *gsl_odeiv_step_rk2simp = &rk2simp_type; sources_5316/external/gsl/gsl_cblas__zsyr2k.c0000664000176700017670000000070311723710247020120 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zsyr2k (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc) { #define BASE double #include "gsl_cblas__source_syr2k_c.h" #undef BASE } sources_5316/external/gsl/gsl_ieee-utils__make_rep.c0000664000176700017670000001071011723710247021417 0ustar paulpaul/* ieee-utils/make_rep.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_ieee_utils.h" #include "gsl_ieee-utils__endian.c" #include "gsl_ieee-utils__standardize.c" static void sprint_nybble(int i, char *s) ; static void sprint_byte(int i, char *s) ; static int determine_ieee_type (int non_zero, int exponent, int max_exponent); /* For the IEEE float format the bits are found from the following masks, sign = 0x80000000 exponent = 0x7f800000 mantisssa = 0x007fffff For the IEEE double format the masks are, sign = 0x8000000000000000 exponent = 0x7ff0000000000000 mantissa = 0x000fffffffffffff */ void gsl_ieee_float_to_rep (const float * x, gsl_ieee_float_rep * r) { int e, non_zero; union { float f; struct { unsigned char byte[4] ; } ieee ; } u; u.f = *x ; if (little_endian_p()) make_float_bigendian(&(u.f)) ; /* note that r->sign is signed, u.ieee.byte is unsigned */ if (u.ieee.byte[3]>>7) { r->sign = 1 ; } else { r->sign = 0 ; } e = (u.ieee.byte[3] & 0x7f) << 1 | (u.ieee.byte[2] & 0x80)>>7 ; r->exponent = e - 127 ; sprint_byte((u.ieee.byte[2] & 0x7f) << 1,r->mantissa) ; sprint_byte(u.ieee.byte[1],r->mantissa + 7) ; sprint_byte(u.ieee.byte[0],r->mantissa + 15) ; r->mantissa[23] = '\0' ; non_zero = u.ieee.byte[0] || u.ieee.byte[1] || (u.ieee.byte[2] & 0x7f); r->type = determine_ieee_type (non_zero, e, 255) ; } void gsl_ieee_double_to_rep (const double * x, gsl_ieee_double_rep * r) { int e, non_zero; union { double d; struct { unsigned char byte[8]; } ieee ; } u; u.d= *x ; if (little_endian_p()) make_double_bigendian(&(u.d)) ; /* note that r->sign is signed, u.ieee.byte is unsigned */ if (u.ieee.byte[7]>>7) { r->sign = 1 ; } else { r->sign = 0 ; } e =(u.ieee.byte[7] & 0x7f)<<4 ^ (u.ieee.byte[6] & 0xf0)>>4 ; r->exponent = e - 1023 ; sprint_nybble(u.ieee.byte[6],r->mantissa) ; sprint_byte(u.ieee.byte[5],r->mantissa + 4) ; sprint_byte(u.ieee.byte[4],r->mantissa + 12) ; sprint_byte(u.ieee.byte[3],r->mantissa + 20) ; sprint_byte(u.ieee.byte[2],r->mantissa + 28) ; sprint_byte(u.ieee.byte[1],r->mantissa + 36) ; sprint_byte(u.ieee.byte[0],r->mantissa + 44) ; r->mantissa[52] = '\0' ; non_zero = (u.ieee.byte[0] || u.ieee.byte[1] || u.ieee.byte[2] || u.ieee.byte[3] || u.ieee.byte[4] || u.ieee.byte[5] || (u.ieee.byte[6] & 0x0f)) ; r->type = determine_ieee_type (non_zero, e, 2047) ; } /* A table of character representations of nybbles */ static char nybble[16][5]={ /* include space for the \0 */ "0000", "0001", "0010", "0011", "0100", "0101", "0110", "0111", "1000", "1001", "1010", "1011", "1100", "1101", "1110", "1111" } ; static void sprint_nybble(int i, char *s) { char *c ; c=nybble[i & 0x0f ]; *s=c[0] ; *(s+1)=c[1] ; *(s+2)=c[2] ; *(s+3)=c[3] ; } static void sprint_byte(int i, char *s) { char *c ; c=nybble[(i & 0xf0)>>4]; *s=c[0] ; *(s+1)=c[1] ; *(s+2)=c[2] ; *(s+3)=c[3] ; c=nybble[i & 0x0f]; *(s+4)=c[0] ; *(s+5)=c[1] ; *(s+6)=c[2] ; *(s+7)=c[3] ; } static int determine_ieee_type (int non_zero, int exponent, int max_exponent) { if (exponent == max_exponent) { if (non_zero) { return GSL_IEEE_TYPE_NAN ; } else { return GSL_IEEE_TYPE_INF ; } } else if (exponent == 0) { if (non_zero) { return GSL_IEEE_TYPE_DENORMAL ; } else { return GSL_IEEE_TYPE_ZERO ; } } else { return GSL_IEEE_TYPE_NORMAL ; } } sources_5316/external/gsl/gsl_matrix__matrix_source.c0000664000176700017670000000614211723710247021763 0ustar paulpaul/* matrix/matrix_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef HIDE_INLINE_STATIC BASE FUNCTION (gsl_matrix, get) (const TYPE (gsl_matrix) * m, const size_t i, const size_t j) { BASE zero = ZERO; if (gsl_check_range) { if (i >= m->size1) /* size_t is unsigned, can't be negative */ { GSL_ERROR_VAL ("first index out of range", GSL_EINVAL, zero); } else if (j >= m->size2) /* size_t is unsigned, can't be negative */ { GSL_ERROR_VAL ("second index out of range", GSL_EINVAL, zero); } } return *(BASE *) (m->data + MULTIPLICITY * (i * m->tda + j)); } void FUNCTION (gsl_matrix, set) (TYPE (gsl_matrix) * m, const size_t i, const size_t j, const BASE x) { if (gsl_check_range) { if (i >= m->size1) /* size_t is unsigned, can't be negative */ { GSL_ERROR_VOID ("first index out of range", GSL_EINVAL); } else if (j >= m->size2) /* size_t is unsigned, can't be negative */ { GSL_ERROR_VOID ("second index out of range", GSL_EINVAL); } } *(BASE *) (m->data + MULTIPLICITY * (i * m->tda + j)) = x; } BASE * FUNCTION (gsl_matrix, ptr) (TYPE (gsl_matrix) * m, const size_t i, const size_t j) { if (gsl_check_range) { if (i >= m->size1) /* size_t is unsigned, can't be negative */ { GSL_ERROR_NULL ("first index out of range", GSL_EINVAL); } else if (j >= m->size2) /* size_t is unsigned, can't be negative */ { GSL_ERROR_NULL ("second index out of range", GSL_EINVAL); } } return (BASE *) (m->data + MULTIPLICITY * (i * m->tda + j)); } const BASE * FUNCTION (gsl_matrix, const_ptr) (const TYPE (gsl_matrix) * m, const size_t i, const size_t j) { if (gsl_check_range) { if (i >= m->size1) /* size_t is unsigned, can't be negative */ { GSL_ERROR_NULL ("first index out of range", GSL_EINVAL); } else if (j >= m->size2) /* size_t is unsigned, can't be negative */ { GSL_ERROR_NULL ("second index out of range", GSL_EINVAL); } } return (const BASE *) (m->data + MULTIPLICITY * (i * m->tda + j)); } #endif sources_5316/external/gsl/gsl_cblas__source_axpy_c.h0000664000176700017670000000247211705263724021534 0ustar paulpaul/* blas/source_axpy_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); if (fabs(alpha_real) == 0 && fabs(alpha_imag) == 0) { return; } for (i = 0; i < N; i++) { const BASE x_real = CONST_REAL(X, ix); const BASE x_imag = CONST_IMAG(X, ix); REAL(Y, iy) += (alpha_real * x_real - alpha_imag * x_imag); IMAG(Y, iy) += (alpha_real * x_imag + alpha_imag * x_real); ix += incX; iy += incY; } } sources_5316/external/gsl/gsl_specfunc__bessel_Ynu.c0000664000176700017670000000660411723710247021514 0ustar paulpaul/* specfunc/bessel_Ynu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_olver.h" #include "gsl_specfunc__bessel_temme.h" /* Perform forward recurrence for Y_nu(x) and Y'_nu(x) * * Y_{nu+1} = nu/x Y_nu - Y'_nu * Y'_{nu+1} = -(nu+1)/x Y_{nu+1} + Y_nu */ #if 0 static int bessel_Y_recur(const double nu_min, const double x, const int kmax, const double Y_start, const double Yp_start, double * Y_end, double * Yp_end) { double x_inv = 1.0/x; double nu = nu_min; double Y_nu = Y_start; double Yp_nu = Yp_start; int k; for(k=1; k<=kmax; k++) { double nuox = nu*x_inv; double Y_nu_save = Y_nu; Y_nu = -Yp_nu + nuox * Y_nu; Yp_nu = Y_nu_save - (nuox+x_inv) * Y_nu; nu += 1.0; } *Y_end = Y_nu; *Yp_end = Yp_nu; return GSL_SUCCESS; } #endif /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Ynu_e(double nu, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else if(nu > 50.0) { return gsl_sf_bessel_Ynu_asymp_Olver_e(nu, x, result); } else { /* -1/2 <= mu <= 1/2 */ int N = (int)(nu + 0.5); double mu = nu - N; gsl_sf_result Y_mu, Y_mup1; int stat_mu; double Ynm1; double Yn; double Ynp1; int n; if(x < 2.0) { /* Determine Ymu, Ymup1 directly. This is really * an optimization since this case could as well * be handled by a call to gsl_sf_bessel_JY_mu_restricted(), * as below. */ stat_mu = gsl_sf_bessel_Y_temme(mu, x, &Y_mu, &Y_mup1); } else { /* Determine Ymu, Ymup1 and Jmu, Jmup1. */ gsl_sf_result J_mu, J_mup1; stat_mu = gsl_sf_bessel_JY_mu_restricted(mu, x, &J_mu, &J_mup1, &Y_mu, &Y_mup1); } /* Forward recursion to get Ynu, Ynup1. */ Ynm1 = Y_mu.val; Yn = Y_mup1.val; for(n=1; n<=N; n++) { Ynp1 = 2.0*(mu+n)/x * Yn - Ynm1; Ynm1 = Yn; Yn = Ynp1; } result->val = Ynm1; /* Y_nu */ result->err = (N + 1.0) * fabs(Ynm1) * (fabs(Y_mu.err/Y_mu.val) + fabs(Y_mup1.err/Y_mup1.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Ynm1); return stat_mu; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_Ynu(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_Ynu_e(nu, x, &result)); } sources_5316/external/gsl/gsl_sf__bessel_K0.c0000644000176700017670000001352710707442037020015 0ustar paulpaul/* specfunc/bessel_K0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC bk0(), bk0e() */ /* chebyshev expansions series for bk0 on the interval 0. to 4.00000d+00 with weighted error 3.57e-19 log weighted error 18.45 significant figures required 17.99 decimal places required 18.97 series for ak0 on the interval 1.25000d-01 to 5.00000d-01 with weighted error 5.34e-17 log weighted error 16.27 significant figures required 14.92 decimal places required 16.89 series for ak02 on the interval 0. to 1.25000d-01 with weighted error 2.34e-17 log weighted error 16.63 significant figures required 14.67 decimal places required 17.20 */ static double bk0_data[11] = { -0.03532739323390276872, 0.3442898999246284869, 0.03597993651536150163, 0.00126461541144692592, 0.00002286212103119451, 0.00000025347910790261, 0.00000000190451637722, 0.00000000001034969525, 0.00000000000004259816, 0.00000000000000013744, 0.00000000000000000035 }; static cheb_series bk0_cs = { bk0_data, 10, -1, 1, 10 }; static double ak0_data[17] = { -0.07643947903327941, -0.02235652605699819, 0.00077341811546938, -0.00004281006688886, 0.00000308170017386, -0.00000026393672220, 0.00000002563713036, -0.00000000274270554, 0.00000000031694296, -0.00000000003902353, 0.00000000000506804, -0.00000000000068895, 0.00000000000009744, -0.00000000000001427, 0.00000000000000215, -0.00000000000000033, 0.00000000000000005 }; static cheb_series ak0_cs = { ak0_data, 16, -1, 1, 10 }; static double ak02_data[14] = { -0.01201869826307592, -0.00917485269102569, 0.00014445509317750, -0.00000401361417543, 0.00000015678318108, -0.00000000777011043, 0.00000000046111825, -0.00000000003158592, 0.00000000000243501, -0.00000000000020743, 0.00000000000001925, -0.00000000000000192, 0.00000000000000020, -0.00000000000000002 }; static cheb_series ak02_cs = { ak02_data, 13, -1, 1, 8 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_K0_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x <= 2.0) { const double lx = log(x); const double ex = exp(x); int stat_I0; gsl_sf_result I0; gsl_sf_result c; cheb_eval_e(&bk0_cs, 0.5*x*x-1.0, &c); stat_I0 = gsl_sf_bessel_I0_e(x, &I0); result->val = ex * ((-lx+M_LN2)*I0.val - 0.25 + c.val); result->err = ex * ((M_LN2+fabs(lx))*I0.err + c.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_I0; } else if(x <= 8.0) { const double sx = sqrt(x); gsl_sf_result c; cheb_eval_e(&ak0_cs, (16.0/x-5.0)/3.0, &c); result->val = (1.25 + c.val) / sx; result->err = c.err / sx; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sx = sqrt(x); gsl_sf_result c; cheb_eval_e(&ak02_cs, 16.0/x-1.0, &c); result->val = (1.25 + c.val) / sx; result->err = (c.err + GSL_DBL_EPSILON) / sx; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_K0_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x <= 2.0) { const double lx = log(x); int stat_I0; gsl_sf_result I0; gsl_sf_result c; cheb_eval_e(&bk0_cs, 0.5*x*x-1.0, &c); stat_I0 = gsl_sf_bessel_I0_e(x, &I0); result->val = (-lx+M_LN2)*I0.val - 0.25 + c.val; result->err = (fabs(lx) + M_LN2) * I0.err + c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_I0; } else { gsl_sf_result K0_scaled; int stat_K0 = gsl_sf_bessel_K0_scaled_e(x, &K0_scaled); int stat_e = gsl_sf_exp_mult_err_e(-x, GSL_DBL_EPSILON*fabs(x), K0_scaled.val, K0_scaled.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K0); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_K0_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_K0_scaled_e(x, &result)); } double gsl_sf_bessel_K0(const double x) { EVAL_RESULT(gsl_sf_bessel_K0_e(x, &result)); } sources_5316/external/gsl/gsl_qrng__qrng.c0000664000176700017670000000423111723710247017506 0ustar paulpaul/* Author: G. Jungman */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_qrng.h" gsl_qrng * gsl_qrng_alloc (const gsl_qrng_type * T, unsigned int dimension) { gsl_qrng * q = (gsl_qrng *) malloc (sizeof (gsl_qrng)); if (q == 0) { GSL_ERROR_VAL ("allocation failed for qrng struct", GSL_ENOMEM, 0); }; q->dimension = dimension; q->state_size = T->state_size(dimension); q->state = malloc (q->state_size); if (q->state == 0) { free (q); GSL_ERROR_VAL ("allocation failed for qrng state", GSL_ENOMEM, 0); }; q->type = T; T->init_state(q->state, q->dimension); return q; } void gsl_qrng_init (gsl_qrng * q) { (q->type->init_state) (q->state, q->dimension); } int gsl_qrng_memcpy (gsl_qrng * dest, const gsl_qrng * src) { if (dest->type != src->type) { GSL_ERROR ("generators must be of the same type", GSL_EINVAL); } dest->dimension = src->dimension; dest->state_size = src->state_size; memcpy (dest->state, src->state, src->state_size); return GSL_SUCCESS; } gsl_qrng * gsl_qrng_clone (const gsl_qrng * q) { gsl_qrng * r = (gsl_qrng *) malloc (sizeof (gsl_qrng)); if (r == 0) { GSL_ERROR_VAL ("failed to allocate space for rng struct", GSL_ENOMEM, 0); }; r->dimension = q->dimension; r->state_size = q->state_size; r->state = malloc (r->state_size); if (r->state == 0) { free (r); GSL_ERROR_VAL ("failed to allocate space for rng state", GSL_ENOMEM, 0); }; r->type = q->type; memcpy (r->state, q->state, q->state_size); return r; } #ifndef HIDE_INLINE_STATIC int gsl_qrng_get (const gsl_qrng * q, double x[]) { return (q->type->get) (q->state, q->dimension, x); } #endif const char * gsl_qrng_name (const gsl_qrng * q) { return q->type->name; } size_t gsl_qrng_size (const gsl_qrng * q) { return q->state_size; } void * gsl_qrng_state (const gsl_qrng * q) { return q->state; } void gsl_qrng_free (gsl_qrng * q) { if(q != 0) { if(q->state != 0) free (q->state); free (q); } } sources_5316/external/gsl/gsl_sf__bessel_Jnu.c0000644000176700017670000001217310707442037020273 0ustar paulpaul/* specfunc/bessel_Jnu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_olver.h" #include "gsl_sf__bessel_temme.h" /* Evaluate at large enough nu to apply asymptotic * results and apply backward recurrence. */ #if 0 static int bessel_J_recur_asymp(const double nu, const double x, gsl_sf_result * Jnu, gsl_sf_result * Jnup1) { const double nu_cut = 25.0; int n; int steps = ceil(nu_cut - nu) + 1; gsl_sf_result r_Jnp1; gsl_sf_result r_Jn; int stat_O1 = gsl_sf_bessel_Jnu_asymp_Olver_e(nu + steps + 1.0, x, &r_Jnp1); int stat_O2 = gsl_sf_bessel_Jnu_asymp_Olver_e(nu + steps, x, &r_Jn); double r_fe = fabs(r_Jnp1.err/r_Jnp1.val) + fabs(r_Jn.err/r_Jn.val); double Jnp1 = r_Jnp1.val; double Jn = r_Jn.val; double Jnm1; double Jnp1_save; for(n=steps; n>0; n--) { Jnm1 = 2.0*(nu+n)/x * Jn - Jnp1; Jnp1 = Jn; Jnp1_save = Jn; Jn = Jnm1; } Jnu->val = Jn; Jnu->err = (r_fe + GSL_DBL_EPSILON * (steps + 1.0)) * fabs(Jn); Jnup1->val = Jnp1_save; Jnup1->err = (r_fe + GSL_DBL_EPSILON * (steps + 1.0)) * fabs(Jnp1_save); return GSL_ERROR_SELECT_2(stat_O1, stat_O2); } #endif /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Jnu_e(const double nu, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { if(nu == 0.0) { result->val = 1.0; result->err = 0.0; } else { result->val = 0.0; result->err = 0.0; } return GSL_SUCCESS; } else if(x*x < 10.0*(nu+1.0)) { return gsl_sf_bessel_IJ_taylor_e(nu, x, -1, 100, GSL_DBL_EPSILON, result); } else if(nu > 50.0) { return gsl_sf_bessel_Jnu_asymp_Olver_e(nu, x, result); } else if(x > 1000.0) { /* We need this to avoid feeding large x to CF1; note that * due to the above check, we know that n <= 50. See similar * block in bessel_Jn.c. */ return gsl_sf_bessel_Jnu_asympx_e(nu, x, result); } else { /* -1/2 <= mu <= 1/2 */ int N = (int)(nu + 0.5); double mu = nu - N; /* Determine the J ratio at nu. */ double Jnup1_Jnu; double sgn_Jnu; const int stat_CF1 = gsl_sf_bessel_J_CF1(nu, x, &Jnup1_Jnu, &sgn_Jnu); if(x < 2.0) { /* Determine Y_mu, Y_mup1 directly and recurse forward to nu. * Then use the CF1 information to solve for J_nu and J_nup1. */ gsl_sf_result Y_mu, Y_mup1; const int stat_mu = gsl_sf_bessel_Y_temme(mu, x, &Y_mu, &Y_mup1); double Ynm1 = Y_mu.val; double Yn = Y_mup1.val; double Ynp1 = 0.0; int n; for(n=1; nval = 2.0/(M_PI*x) / (Jnup1_Jnu*Yn - Ynp1); result->err = GSL_DBL_EPSILON * (N + 2.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mu, stat_CF1); } else { /* Recurse backward from nu to mu, determining the J ratio * at mu. Use this together with a Steed method CF2 to * determine the actual J_mu, and thus obtain the normalization. */ double Jmu; double Jmup1_Jmu; double sgn_Jmu; double Jmuprime_Jmu; double P, Q; const int stat_CF2 = gsl_sf_bessel_JY_steed_CF2(mu, x, &P, &Q); double gamma; double Jnp1 = sgn_Jnu * GSL_SQRT_DBL_MIN * Jnup1_Jnu; double Jn = sgn_Jnu * GSL_SQRT_DBL_MIN; double Jnm1; int n; for(n=N; n>0; n--) { Jnm1 = 2.0*(mu+n)/x * Jn - Jnp1; Jnp1 = Jn; Jn = Jnm1; } Jmup1_Jmu = Jnp1/Jn; sgn_Jmu = GSL_SIGN(Jn); Jmuprime_Jmu = mu/x - Jmup1_Jmu; gamma = (P - Jmuprime_Jmu)/Q; Jmu = sgn_Jmu * sqrt(2.0/(M_PI*x) / (Q + gamma*(P-Jmuprime_Jmu))); result->val = Jmu * (sgn_Jnu * GSL_SQRT_DBL_MIN) / Jn; result->err = 2.0 * GSL_DBL_EPSILON * (N + 2.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_CF2, stat_CF1); } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_Jnu(const double nu, const double x) { EVAL_RESULT(gsl_sf_bessel_Jnu_e(nu, x, &result)); } sources_5316/external/gsl/gsl_vector_double.h0000664000176700017670000001462711705263724020227 0ustar paulpaul/* vector/gsl_vector_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_DOUBLE_H__ #define __GSL_VECTOR_DOUBLE_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; double *data; gsl_block *block; int owner; } gsl_vector; typedef struct { gsl_vector vector; } _gsl_vector_view; typedef _gsl_vector_view gsl_vector_view; typedef struct { gsl_vector vector; } _gsl_vector_const_view; typedef const _gsl_vector_const_view gsl_vector_const_view; /* Allocation */ gsl_vector *gsl_vector_alloc (const size_t n); gsl_vector *gsl_vector_calloc (const size_t n); gsl_vector *gsl_vector_alloc_from_block (gsl_block * b, const size_t offset, const size_t n, const size_t stride); gsl_vector *gsl_vector_alloc_from_vector (gsl_vector * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_free (gsl_vector * v); /* Views */ _gsl_vector_view gsl_vector_view_array (double *v, size_t n); _gsl_vector_view gsl_vector_view_array_with_stride (double *base, size_t stride, size_t n); _gsl_vector_const_view gsl_vector_const_view_array (const double *v, size_t n); _gsl_vector_const_view gsl_vector_const_view_array_with_stride (const double *base, size_t stride, size_t n); _gsl_vector_view gsl_vector_subvector (gsl_vector *v, size_t i, size_t n); _gsl_vector_view gsl_vector_subvector_with_stride (gsl_vector *v, size_t i, size_t stride, size_t n); _gsl_vector_const_view gsl_vector_const_subvector (const gsl_vector *v, size_t i, size_t n); _gsl_vector_const_view gsl_vector_const_subvector_with_stride (const gsl_vector *v, size_t i, size_t stride, size_t n); /* Operations */ double gsl_vector_get (const gsl_vector * v, const size_t i); void gsl_vector_set (gsl_vector * v, const size_t i, double x); double *gsl_vector_ptr (gsl_vector * v, const size_t i); const double *gsl_vector_const_ptr (const gsl_vector * v, const size_t i); void gsl_vector_set_zero (gsl_vector * v); void gsl_vector_set_all (gsl_vector * v, double x); int gsl_vector_set_basis (gsl_vector * v, size_t i); int gsl_vector_fread (FILE * stream, gsl_vector * v); int gsl_vector_fwrite (FILE * stream, const gsl_vector * v); int gsl_vector_fscanf (FILE * stream, gsl_vector * v); int gsl_vector_fprintf (FILE * stream, const gsl_vector * v, const char *format); int gsl_vector_memcpy (gsl_vector * dest, const gsl_vector * src); int gsl_vector_reverse (gsl_vector * v); int gsl_vector_swap (gsl_vector * v, gsl_vector * w); int gsl_vector_swap_elements (gsl_vector * v, const size_t i, const size_t j); double gsl_vector_max (const gsl_vector * v); double gsl_vector_min (const gsl_vector * v); void gsl_vector_minmax (const gsl_vector * v, double * min_out, double * max_out); size_t gsl_vector_max_index (const gsl_vector * v); size_t gsl_vector_min_index (const gsl_vector * v); void gsl_vector_minmax_index (const gsl_vector * v, size_t * imin, size_t * imax); int gsl_vector_add (gsl_vector * a, const gsl_vector * b); int gsl_vector_sub (gsl_vector * a, const gsl_vector * b); int gsl_vector_mul (gsl_vector * a, const gsl_vector * b); int gsl_vector_div (gsl_vector * a, const gsl_vector * b); int gsl_vector_scale (gsl_vector * a, const double x); int gsl_vector_add_constant (gsl_vector * a, const double x); int gsl_vector_isnull (const gsl_vector * v); int gsl_vector_ispos (const gsl_vector * v); int gsl_vector_isneg (const gsl_vector * v); int gsl_vector_isnonneg (const gsl_vector * v); #ifdef HAVE_INLINE extern inline double gsl_vector_get (const gsl_vector * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_set (gsl_vector * v, const size_t i, double x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline double * gsl_vector_ptr (gsl_vector * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (double *) (v->data + i * v->stride); } extern inline const double * gsl_vector_const_ptr (const gsl_vector * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const double *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_DOUBLE_H__ */ sources_5316/external/gsl/gsl_sf__psi.c0000644000176700017670000006037510707442037017004 0ustar paulpaul/* specfunc/psi.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2005, 2006 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_zeta.h" #include "gsl_sf_psi.h" #include "gsl_complex_math.h" #include #include "gsl_sf__error.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* Chebyshev fit for f(y) = Re(Psi(1+Iy)) + M_EULER - y^2/(1+y^2) - y^2/(2(4+y^2)) * 1 < y < 10 * ==> * y(x) = (9x + 11)/2, -1 < x < 1 * x(y) = (2y - 11)/9 * * g(x) := f(y(x)) */ static double r1py_data[] = { 1.59888328244976954803168395603, 0.67905625353213463845115658455, -0.068485802980122530009506482524, -0.005788184183095866792008831182, 0.008511258167108615980419855648, -0.004042656134699693434334556409, 0.001352328406159402601778462956, -0.000311646563930660566674525382, 0.000018507563785249135437219139, 0.000028348705427529850296492146, -0.000019487536014574535567541960, 8.0709788710834469408621587335e-06, -2.2983564321340518037060346561e-06, 3.0506629599604749843855962658e-07, 1.3042238632418364610774284846e-07, -1.2308657181048950589464690208e-07, 5.7710855710682427240667414345e-08, -1.8275559342450963966092636354e-08, 3.1020471300626589420759518930e-09, 6.8989327480593812470039430640e-10, -8.7182290258923059852334818997e-10, 4.4069147710243611798213548777e-10, -1.4727311099198535963467200277e-10, 2.7589682523262644748825844248e-11, 4.1871826756975856411554363568e-12, -6.5673460487260087541400767340e-12, 3.4487900886723214020103638000e-12, -1.1807251417448690607973794078e-12, 2.3798314343969589258709315574e-13, 2.1663630410818831824259465821e-15 }; static cheb_series r1py_cs = { r1py_data, 29, -1,1, 18 }; /* Chebyshev fits from SLATEC code for psi(x) Series for PSI on the interval 0. to 1.00000D+00 with weighted error 2.03E-17 log weighted error 16.69 significant figures required 16.39 decimal places required 17.37 Series for APSI on the interval 0. to 2.50000D-01 with weighted error 5.54E-17 log weighted error 16.26 significant figures required 14.42 decimal places required 16.86 */ static double psics_data[23] = { -.038057080835217922, .491415393029387130, -.056815747821244730, .008357821225914313, -.001333232857994342, .000220313287069308, -.000037040238178456, .000006283793654854, -.000001071263908506, .000000183128394654, -.000000031353509361, .000000005372808776, -.000000000921168141, .000000000157981265, -.000000000027098646, .000000000004648722, -.000000000000797527, .000000000000136827, -.000000000000023475, .000000000000004027, -.000000000000000691, .000000000000000118, -.000000000000000020 }; static cheb_series psi_cs = { psics_data, 22, -1, 1, 17 }; static double apsics_data[16] = { -.0204749044678185, -.0101801271534859, .0000559718725387, -.0000012917176570, .0000000572858606, -.0000000038213539, .0000000003397434, -.0000000000374838, .0000000000048990, -.0000000000007344, .0000000000001233, -.0000000000000228, .0000000000000045, -.0000000000000009, .0000000000000002, -.0000000000000000 }; static cheb_series apsi_cs = { apsics_data, 15, -1, 1, 9 }; #define PSI_TABLE_NMAX 100 static double psi_table[PSI_TABLE_NMAX+1] = { 0.0, /* Infinity */ /* psi(0) */ -M_EULER, /* psi(1) */ 0.42278433509846713939348790992, /* ... */ 0.92278433509846713939348790992, 1.25611766843180047272682124325, 1.50611766843180047272682124325, 1.70611766843180047272682124325, 1.87278433509846713939348790992, 2.01564147795560999653634505277, 2.14064147795560999653634505277, 2.25175258906672110764745616389, 2.35175258906672110764745616389, 2.44266167997581201673836525479, 2.52599501330914535007169858813, 2.60291809023222227314862166505, 2.67434666166079370172005023648, 2.74101332832746036838671690315, 2.80351332832746036838671690315, 2.86233685773922507426906984432, 2.91789241329478062982462539988, 2.97052399224214905087725697883, 3.02052399224214905087725697883, 3.06814303986119666992487602645, 3.11359758531574212447033057190, 3.15707584618530734186163491973, 3.1987425128519740085283015864, 3.2387425128519740085283015864, 3.2772040513135124700667631249, 3.3142410883505495071038001619, 3.3499553740648352213895144476, 3.3844381326855248765619282407, 3.4177714660188582098952615740, 3.4500295305349872421533260902, 3.4812795305349872421533260902, 3.5115825608380175451836291205, 3.5409943255438998981248055911, 3.5695657541153284695533770196, 3.5973435318931062473311547974, 3.6243705589201332743581818244, 3.6506863483938174848844976139, 3.6763273740348431259101386396, 3.7013273740348431259101386396, 3.7257176179372821503003825420, 3.7495271417468059598241920658, 3.7727829557002943319172153216, 3.7955102284275670591899425943, 3.8177324506497892814121648166, 3.8394715810845718901078169905, 3.8607481768292527411716467777, 3.8815815101625860745049801110, 3.9019896734278921969539597029, 3.9219896734278921969539597029, 3.9415975165651470989147440166, 3.9608282857959163296839747858, 3.9796962103242182164764276160, 3.9982147288427367349949461345, 4.0163965470245549168131279527, 4.0342536898816977739559850956, 4.0517975495308205809735289552, 4.0690389288411654085597358518, 4.0859880813835382899156680552, 4.1026547480502049565823347218, 4.1190481906731557762544658694, 4.1351772229312202923834981274, 4.1510502388042361653993711433, 4.1666752388042361653993711433, 4.1820598541888515500147557587, 4.1972113693403667015299072739, 4.2121367424746950597388624977, 4.2268426248276362362094507330, 4.2413353784508246420065521823, 4.2556210927365389277208378966, 4.2697055997787924488475984600, 4.2835944886676813377364873489, 4.2972931188046676391063503626, 4.3108066323181811526198638761, 4.3241399656515144859531972094, 4.3372978603883565912163551041, 4.3502848733753695782293421171, 4.3631053861958823987421626300, 4.3757636140439836645649474401, 4.3882636140439836645649474401, 4.4006092930563293435772931191, 4.4128044150075488557724150703, 4.4248526077786331931218126607, 4.4367573696833950978837174226, 4.4485220755657480390601880108, 4.4601499825424922251066996387, 4.4716442354160554434975042364, 4.4830078717796918071338678728, 4.4942438268358715824147667492, 4.5053549379469826935258778603, 4.5163439489359936825368668713, 4.5272135141533849868846929582, 4.5379662023254279976373811303, 4.5486045001977684231692960239, 4.5591308159872421073798223397, 4.5695474826539087740464890064, 4.5798567610044242379640147796, 4.5900608426370772991885045755, 4.6001618527380874001986055856 }; #define PSI_1_TABLE_NMAX 100 static double psi_1_table[PSI_1_TABLE_NMAX+1] = { 0.0, /* Infinity */ /* psi(1,0) */ M_PI*M_PI/6.0, /* psi(1,1) */ 0.644934066848226436472415, /* ... */ 0.394934066848226436472415, 0.2838229557371153253613041, 0.2213229557371153253613041, 0.1813229557371153253613041, 0.1535451779593375475835263, 0.1331370146940314251345467, 0.1175120146940314251345467, 0.1051663356816857461222010, 0.0951663356816857461222010, 0.0869018728717683907503002, 0.0799574284273239463058557, 0.0740402686640103368384001, 0.0689382278476838062261552, 0.0644937834032393617817108, 0.0605875334032393617817108, 0.0571273257907826143768665, 0.0540409060376961946237801, 0.0512708229352031198315363, 0.0487708229352031198315363, 0.0465032492390579951149830, 0.0444371335365786562720078, 0.0425467743683366902984728, 0.0408106632572255791873617, 0.0392106632572255791873617, 0.0377313733163971768204978, 0.0363596312039143235969038, 0.0350841209998326909438426, 0.0338950603577399442137594, 0.0327839492466288331026483, 0.0317433665203020901265817, 0.03076680402030209012658168, 0.02984853037475571730748159, 0.02898347847164153045627052, 0.02816715194102928555831133, 0.02739554700275768062003973, 0.02666508681283803124093089, 0.02597256603721476254286995, 0.02531510384129102815759710, 0.02469010384129102815759710, 0.02409521984367056414807896, 0.02352832641963428296894063, 0.02298749353699501850166102, 0.02247096461137518379091722, 0.02197713745088135663042339, 0.02150454765882086513703965, 0.02105185413233829383780923, 0.02061782635456051606003145, 0.02020133322669712580597065, 0.01980133322669712580597065, 0.01941686571420193164987683, 0.01904704322899483105816086, 0.01869104465298913508094477, 0.01834810912486842177504628, 0.01801753061247172756017024, 0.01769865306145131939690494, 0.01739086605006319997554452, 0.01709360088954001329302371, 0.01680632711763538818529605, 0.01652854933985761040751827, 0.01625980437882562975715546, 0.01599965869724394401313881, 0.01574770606433893015574400, 0.01550356543933893015574400, 0.01526687904880638577704578, 0.01503731063741979257227076, 0.01481454387422086185273411, 0.01459828089844231513993134, 0.01438824099085987447620523, 0.01418415935820681325171544, 0.01398578601958352422176106, 0.01379288478501562298719316, 0.01360523231738567365335942, 0.01342261726990576130858221, 0.01324483949212798353080444, 0.01307170929822216635628920, 0.01290304679189732236910755, 0.01273868124291638877278934, 0.01257845051066194236996928, 0.01242220051066194236996928, 0.01226978472038606978956995, 0.01212106372098095378719041, 0.01197590477193174490346273, 0.01183418141592267460867815, 0.01169577311142440471248438, 0.01156056489076458859566448, 0.01142844704164317229232189, 0.01129931481023821361463594, 0.01117306812421372175754719, 0.01104961133409026496742374, 0.01092885297157366069257770, 0.01081070552355853781923177, 0.01069508522063334415522437, 0.01058191183901270133041676, 0.01047110851491297833872701, 0.01036260157046853389428257, 0.01025632035036012704977199, /* ... */ 0.01015219706839427948625679, /* psi(1,99) */ 0.01005016666333357139524567 /* psi(1,100) */ }; /* digamma for x both positive and negative; we do both * cases here because of the way we use even/odd parts * of the function */ static int psi_x(const double x, gsl_sf_result * result) { const double y = fabs(x); if(x == 0.0 || x == -1.0 || x == -2.0) { DOMAIN_ERROR(result); } else if(y >= 2.0) { const double t = 8.0/(y*y)-1.0; gsl_sf_result result_c; cheb_eval_e(&apsi_cs, t, &result_c); if(x < 0.0) { const double s = sin(M_PI*x); const double c = cos(M_PI*x); if(fabs(s) < 2.0*GSL_SQRT_DBL_MIN) { DOMAIN_ERROR(result); } else { result->val = log(y) - 0.5/x + result_c.val - M_PI * c/s; result->err = M_PI*fabs(x)*GSL_DBL_EPSILON/(s*s); result->err += result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } else { result->val = log(y) - 0.5/x + result_c.val; result->err = result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } else { /* -2 < x < 2 */ gsl_sf_result result_c; if(x < -1.0) { /* x = -2 + v */ const double v = x + 2.0; const double t1 = 1.0/x; const double t2 = 1.0/(x+1.0); const double t3 = 1.0/v; cheb_eval_e(&psi_cs, 2.0*v-1.0, &result_c); result->val = -(t1 + t2 + t3) + result_c.val; result->err = GSL_DBL_EPSILON * (fabs(t1) + fabs(x/(t2*t2)) + fabs(x/(t3*t3))); result->err += result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 0.0) { /* x = -1 + v */ const double v = x + 1.0; const double t1 = 1.0/x; const double t2 = 1.0/v; cheb_eval_e(&psi_cs, 2.0*v-1.0, &result_c); result->val = -(t1 + t2) + result_c.val; result->err = GSL_DBL_EPSILON * (fabs(t1) + fabs(x/(t2*t2))); result->err += result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 1.0) { /* x = v */ const double t1 = 1.0/x; cheb_eval_e(&psi_cs, 2.0*x-1.0, &result_c); result->val = -t1 + result_c.val; result->err = GSL_DBL_EPSILON * t1; result->err += result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* x = 1 + v */ const double v = x - 1.0; return cheb_eval_e(&psi_cs, 2.0*v-1.0, result); } } } /* psi(z) for large |z| in the right half-plane; [Abramowitz + Stegun, 6.3.18] */ static gsl_complex psi_complex_asymp(gsl_complex z) { /* coefficients in the asymptotic expansion for large z; * let w = z^(-2) and write the expression in the form * * ln(z) - 1/(2z) - 1/12 w (1 + c1 w + c2 w + c3 w + ... ) */ static const double c1 = -0.1; static const double c2 = 1.0/21.0; static const double c3 = -0.05; gsl_complex zi = gsl_complex_inverse(z); gsl_complex w = gsl_complex_mul(zi, zi); gsl_complex cs; /* Horner method evaluation of term in parentheses */ gsl_complex sum; sum = gsl_complex_mul_real(w, c3/c2); sum = gsl_complex_add_real(sum, 1.0); sum = gsl_complex_mul_real(sum, c2/c1); sum = gsl_complex_mul(sum, w); sum = gsl_complex_add_real(sum, 1.0); sum = gsl_complex_mul_real(sum, c1); sum = gsl_complex_mul(sum, w); sum = gsl_complex_add_real(sum, 1.0); /* correction added to log(z) */ cs = gsl_complex_mul(sum, w); cs = gsl_complex_mul_real(cs, -1.0/12.0); cs = gsl_complex_add(cs, gsl_complex_mul_real(zi, -0.5)); return gsl_complex_add(gsl_complex_log(z), cs); } /* psi(z) for complex z in the right half-plane */ static int psi_complex_rhp( gsl_complex z, gsl_sf_result * result_re, gsl_sf_result * result_im ) { int n_recurse = 0; int i; gsl_complex a; if(GSL_REAL(z) == 0.0 && GSL_IMAG(z) == 0.0) { result_re->val = 0.0; result_im->val = 0.0; result_re->err = 0.0; result_im->err = 0.0; return GSL_EDOM; } /* compute the number of recurrences to apply */ if(GSL_REAL(z) < 20.0 && fabs(GSL_IMAG(z)) < 20.0) { const double sp = sqrt(20.0 + GSL_IMAG(z)); const double sn = sqrt(20.0 - GSL_IMAG(z)); const double rhs = sp*sn - GSL_REAL(z); if(rhs > 0.0) n_recurse = ceil(rhs); } /* compute asymptotic at the large value z + n_recurse */ a = psi_complex_asymp(gsl_complex_add_real(z, n_recurse)); result_re->err = 2.0 * GSL_DBL_EPSILON * fabs(GSL_REAL(a)); result_im->err = 2.0 * GSL_DBL_EPSILON * fabs(GSL_IMAG(a)); /* descend recursively, if necessary */ for(i = n_recurse; i >= 1; --i) { gsl_complex zn = gsl_complex_add_real(z, i - 1.0); gsl_complex zn_inverse = gsl_complex_inverse(zn); a = gsl_complex_sub(a, zn_inverse); /* accumulate the error, to catch cancellations */ result_re->err += 2.0 * GSL_DBL_EPSILON * fabs(GSL_REAL(zn_inverse)); result_im->err += 2.0 * GSL_DBL_EPSILON * fabs(GSL_IMAG(zn_inverse)); } result_re->val = GSL_REAL(a); result_im->val = GSL_IMAG(a); result_re->err += 2.0 * GSL_DBL_EPSILON * fabs(result_re->val); result_im->err += 2.0 * GSL_DBL_EPSILON * fabs(result_im->val); return GSL_SUCCESS; } /* generic polygamma; assumes n >= 0 and x > 0 */ static int psi_n_xg0(const int n, const double x, gsl_sf_result * result) { if(n == 0) { return gsl_sf_psi_e(x, result); } else { /* Abramowitz + Stegun 6.4.10 */ gsl_sf_result ln_nf; gsl_sf_result hzeta; int stat_hz = gsl_sf_hzeta_e(n+1.0, x, &hzeta); int stat_nf = gsl_sf_lnfact_e((unsigned int) n, &ln_nf); int stat_e = gsl_sf_exp_mult_err_e(ln_nf.val, ln_nf.err, hzeta.val, hzeta.err, result); if(GSL_IS_EVEN(n)) result->val = -result->val; return GSL_ERROR_SELECT_3(stat_e, stat_nf, stat_hz); } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_psi_int_e(const int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n <= 0) { DOMAIN_ERROR(result); } else if(n <= PSI_TABLE_NMAX) { result->val = psi_table[n]; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* Abramowitz+Stegun 6.3.18 */ const double c2 = -1.0/12.0; const double c3 = 1.0/120.0; const double c4 = -1.0/252.0; const double c5 = 1.0/240.0; const double ni2 = (1.0/n)*(1.0/n); const double ser = ni2 * (c2 + ni2 * (c3 + ni2 * (c4 + ni2*c5))); result->val = log(n) - 0.5/n + ser; result->err = GSL_DBL_EPSILON * (fabs(log(n)) + fabs(0.5/n) + fabs(ser)); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_psi_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ return psi_x(x, result); } int gsl_sf_psi_1piy_e(const double y, gsl_sf_result * result) { const double ay = fabs(y); /* CHECK_POINTER(result) */ if(ay > 1000.0) { /* [Abramowitz+Stegun, 6.3.19] */ const double yi2 = 1.0/(ay*ay); const double lny = log(ay); const double sum = yi2 * (1.0/12.0 + 1.0/120.0 * yi2 + 1.0/252.0 * yi2*yi2); result->val = lny + sum; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(lny) + fabs(sum)); return GSL_SUCCESS; } else if(ay > 10.0) { /* [Abramowitz+Stegun, 6.3.19] */ const double yi2 = 1.0/(ay*ay); const double lny = log(ay); const double sum = yi2 * (1.0/12.0 + yi2 * (1.0/120.0 + yi2 * (1.0/252.0 + yi2 * (1.0/240.0 + yi2 * (1.0/132.0 + 691.0/32760.0 * yi2))))); result->val = lny + sum; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(lny) + fabs(sum)); return GSL_SUCCESS; } else if(ay > 1.0){ const double y2 = ay*ay; const double x = (2.0*ay - 11.0)/9.0; const double v = y2*(1.0/(1.0+y2) + 0.5/(4.0+y2)); gsl_sf_result result_c; cheb_eval_e(&r1py_cs, x, &result_c); result->val = result_c.val - M_EULER + v; result->err = result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(v) + M_EULER + fabs(result_c.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->err *= 5.0; /* FIXME: losing a digit somewhere... maybe at x=... ? */ return GSL_SUCCESS; } else { /* [Abramowitz+Stegun, 6.3.17] * * -M_EULER + y^2 Sum[1/n 1/(n^2 + y^2), {n,1,M}] * + Sum[1/n^3, {n,M+1,Infinity}] * - y^2 Sum[1/n^5, {n,M+1,Infinity}] * + y^4 Sum[1/n^7, {n,M+1,Infinity}] * - y^6 Sum[1/n^9, {n,M+1,Infinity}] * + O(y^8) * * We take M=50 for at least 15 digit precision. */ const int M = 50; const double y2 = y*y; const double c0 = 0.00019603999466879846570; const double c2 = 3.8426659205114376860e-08; const double c4 = 1.0041592839497643554e-11; const double c6 = 2.9516743763500191289e-15; const double p = c0 + y2 *(-c2 + y2*(c4 - y2*c6)); double sum = 0.0; double v; int n; for(n=1; n<=M; n++) { sum += 1.0/(n * (n*n + y*y)); } v = y2 * (sum + p); result->val = -M_EULER + v; result->err = GSL_DBL_EPSILON * (M_EULER + fabs(v)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_psi_1_int_e(const int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n <= 0) { DOMAIN_ERROR(result); } else if(n <= PSI_1_TABLE_NMAX) { result->val = psi_1_table[n]; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { /* Abramowitz+Stegun 6.4.12 * double-precision for n > 100 */ const double c0 = -1.0/30.0; const double c1 = 1.0/42.0; const double c2 = -1.0/30.0; const double ni2 = (1.0/n)*(1.0/n); const double ser = ni2*ni2 * (c0 + ni2*(c1 + c2*ni2)); result->val = (1.0 + 0.5/n + 1.0/(6.0*n*n) + ser) / n; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } } int gsl_sf_psi_1_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0 || x == -1.0 || x == -2.0) { DOMAIN_ERROR(result); } else if(x > 0.0) { return psi_n_xg0(1, x, result); } else if(x > -5.0) { /* Abramowitz + Stegun 6.4.6 */ int M = -floor(x); double fx = x + M; double sum = 0.0; int m; if(fx == 0.0) DOMAIN_ERROR(result); for(m = 0; m < M; ++m) sum += 1.0/((x+m)*(x+m)); { int stat_psi = psi_n_xg0(1, fx, result); result->val += sum; result->err += M * GSL_DBL_EPSILON * sum; return stat_psi; } } else { /* Abramowitz + Stegun 6.4.7 */ const double sin_px = sin(M_PI * x); const double d = M_PI*M_PI/(sin_px*sin_px); gsl_sf_result r; int stat_psi = psi_n_xg0(1, 1.0-x, &r); result->val = d - r.val; result->err = r.err + 2.0*GSL_DBL_EPSILON*d; return stat_psi; } } int gsl_sf_psi_n_e(const int n, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n == 0) { return gsl_sf_psi_e(x, result); } else if(n == 1) { return gsl_sf_psi_1_e(x, result); } else if(n < 0 || x <= 0.0) { DOMAIN_ERROR(result); } else { gsl_sf_result ln_nf; gsl_sf_result hzeta; int stat_hz = gsl_sf_hzeta_e(n+1.0, x, &hzeta); int stat_nf = gsl_sf_lnfact_e((unsigned int) n, &ln_nf); int stat_e = gsl_sf_exp_mult_err_e(ln_nf.val, ln_nf.err, hzeta.val, hzeta.err, result); if(GSL_IS_EVEN(n)) result->val = -result->val; return GSL_ERROR_SELECT_3(stat_e, stat_nf, stat_hz); } } int gsl_sf_complex_psi_e( const double x, const double y, gsl_sf_result * result_re, gsl_sf_result * result_im ) { if(x >= 0.0) { gsl_complex z = gsl_complex_rect(x, y); return psi_complex_rhp(z, result_re, result_im); } else { /* reflection formula [Abramowitz+Stegun, 6.3.7] */ gsl_complex z = gsl_complex_rect(x, y); gsl_complex omz = gsl_complex_rect(1.0 - x, -y); gsl_complex zpi = gsl_complex_mul_real(z, M_PI); gsl_complex cotzpi = gsl_complex_cot(zpi); int ret_val = psi_complex_rhp(omz, result_re, result_im); if(GSL_IS_REAL(GSL_REAL(cotzpi)) && GSL_IS_REAL(GSL_IMAG(cotzpi))) { result_re->val -= M_PI * GSL_REAL(cotzpi); result_im->val -= M_PI * GSL_IMAG(cotzpi); return ret_val; } else { GSL_ERROR("singularity", GSL_EDOM); } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_psi_int(const int n) { EVAL_RESULT(gsl_sf_psi_int_e(n, &result)); } double gsl_sf_psi(const double x) { EVAL_RESULT(gsl_sf_psi_e(x, &result)); } double gsl_sf_psi_1piy(const double x) { EVAL_RESULT(gsl_sf_psi_1piy_e(x, &result)); } double gsl_sf_psi_1_int(const int n) { EVAL_RESULT(gsl_sf_psi_1_int_e(n, &result)); } double gsl_sf_psi_1(const double x) { EVAL_RESULT(gsl_sf_psi_1_e(x, &result)); } double gsl_sf_psi_n(const int n, const double x) { EVAL_RESULT(gsl_sf_psi_n_e(n, x, &result)); } sources_5316/external/gsl/gsl_sf_gamma.h0000664000176700017670000001710011705263724017132 0ustar paulpaul/* specfunc/gsl_sf_gamma.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_GAMMA_H__ #define __GSL_SF_GAMMA_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Log[Gamma(x)], x not a negative integer * Uses real Lanczos method. * Returns the real part of Log[Gamma[x]] when x < 0, * i.e. Log[|Gamma[x]|]. * * exceptions: GSL_EDOM, GSL_EROUND */ int gsl_sf_lngamma_e(double x, gsl_sf_result * result); double gsl_sf_lngamma(const double x); /* Log[Gamma(x)], x not a negative integer * Uses real Lanczos method. Determines * the sign of Gamma[x] as well as Log[|Gamma[x]|] for x < 0. * So Gamma[x] = sgn * Exp[result_lg]. * * exceptions: GSL_EDOM, GSL_EROUND */ int gsl_sf_lngamma_sgn_e(double x, gsl_sf_result * result_lg, double *sgn); /* Gamma(x), x not a negative integer * Uses real Lanczos method. * * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EROUND */ int gsl_sf_gamma_e(const double x, gsl_sf_result * result); double gsl_sf_gamma(const double x); /* Regulated Gamma Function, x > 0 * Gamma^*(x) = Gamma(x)/(Sqrt[2Pi] x^(x-1/2) exp(-x)) * = (1 + 1/(12x) + ...), x->Inf * A useful suggestion of Temme. * * exceptions: GSL_EDOM */ int gsl_sf_gammastar_e(const double x, gsl_sf_result * result); double gsl_sf_gammastar(const double x); /* 1/Gamma(x) * Uses real Lanczos method. * * exceptions: GSL_EUNDRFLW, GSL_EROUND */ int gsl_sf_gammainv_e(const double x, gsl_sf_result * result); double gsl_sf_gammainv(const double x); /* Log[Gamma(z)] for z complex, z not a negative integer * Uses complex Lanczos method. Note that the phase part (arg) * is not well-determined when |z| is very large, due * to inevitable roundoff in restricting to (-Pi,Pi]. * This will raise the GSL_ELOSS exception when it occurs. * The absolute value part (lnr), however, never suffers. * * Calculates: * lnr = log|Gamma(z)| * arg = arg(Gamma(z)) in (-Pi, Pi] * * exceptions: GSL_EDOM, GSL_ELOSS */ int gsl_sf_lngamma_complex_e(double zr, double zi, gsl_sf_result * lnr, gsl_sf_result * arg); /* x^n / n! * * x >= 0.0, n >= 0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_taylorcoeff_e(const int n, const double x, gsl_sf_result * result); double gsl_sf_taylorcoeff(const int n, const double x); /* n! * * exceptions: GSL_EDOM, GSL_OVRFLW */ int gsl_sf_fact_e(const unsigned int n, gsl_sf_result * result); double gsl_sf_fact(const unsigned int n); /* n!! = n(n-2)(n-4) ... * * exceptions: GSL_EDOM, GSL_OVRFLW */ int gsl_sf_doublefact_e(const unsigned int n, gsl_sf_result * result); double gsl_sf_doublefact(const unsigned int n); /* log(n!) * Faster than ln(Gamma(n+1)) for n < 170; defers for larger n. * * exceptions: none */ int gsl_sf_lnfact_e(const unsigned int n, gsl_sf_result * result); double gsl_sf_lnfact(const unsigned int n); /* log(n!!) * * exceptions: none */ int gsl_sf_lndoublefact_e(const unsigned int n, gsl_sf_result * result); double gsl_sf_lndoublefact(const unsigned int n); /* log(n choose m) * * exceptions: GSL_EDOM */ int gsl_sf_lnchoose_e(unsigned int n, unsigned int m, gsl_sf_result * result); double gsl_sf_lnchoose(unsigned int n, unsigned int m); /* n choose m * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_choose_e(unsigned int n, unsigned int m, gsl_sf_result * result); double gsl_sf_choose(unsigned int n, unsigned int m); /* Logarithm of Pochhammer (Apell) symbol * log( (a)_x ) * where (a)_x := Gamma[a + x]/Gamma[a] * * a > 0, a+x > 0 * * exceptions: GSL_EDOM */ int gsl_sf_lnpoch_e(const double a, const double x, gsl_sf_result * result); double gsl_sf_lnpoch(const double a, const double x); /* Logarithm of Pochhammer (Apell) symbol, with sign information. * result = log( |(a)_x| ) * sgn = sgn( (a)_x ) * where (a)_x := Gamma[a + x]/Gamma[a] * * a != neg integer, a+x != neg integer * * exceptions: GSL_EDOM */ int gsl_sf_lnpoch_sgn_e(const double a, const double x, gsl_sf_result * result, double * sgn); /* Pochhammer (Apell) symbol * (a)_x := Gamma[a + x]/Gamma[x] * * a != neg integer, a+x != neg integer * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_poch_e(const double a, const double x, gsl_sf_result * result); double gsl_sf_poch(const double a, const double x); /* Relative Pochhammer (Apell) symbol * ((a,x) - 1)/x * where (a,x) = (a)_x := Gamma[a + x]/Gamma[a] * * exceptions: GSL_EDOM */ int gsl_sf_pochrel_e(const double a, const double x, gsl_sf_result * result); double gsl_sf_pochrel(const double a, const double x); /* Normalized Incomplete Gamma Function * * Q(a,x) = 1/Gamma(a) Integral[ t^(a-1) e^(-t), {t,x,Infinity} ] * * a >= 0, x >= 0 * Q(a,0) := 1 * Q(0,x) := 0, x != 0 * * exceptions: GSL_EDOM */ int gsl_sf_gamma_inc_Q_e(const double a, const double x, gsl_sf_result * result); double gsl_sf_gamma_inc_Q(const double a, const double x); /* Complementary Normalized Incomplete Gamma Function * * P(a,x) = 1/Gamma(a) Integral[ t^(a-1) e^(-t), {t,0,x} ] * * a > 0, x >= 0 * * exceptions: GSL_EDOM */ int gsl_sf_gamma_inc_P_e(const double a, const double x, gsl_sf_result * result); double gsl_sf_gamma_inc_P(const double a, const double x); /* Non-normalized Incomplete Gamma Function * * Gamma(a,x) := Integral[ t^(a-1) e^(-t), {t,x,Infinity} ] * * x >= 0.0 * Gamma(a, 0) := Gamma(a) * * exceptions: GSL_EDOM */ int gsl_sf_gamma_inc_e(const double a, const double x, gsl_sf_result * result); double gsl_sf_gamma_inc(const double a, const double x); /* Logarithm of Beta Function * Log[B(a,b)] * * a > 0, b > 0 * exceptions: GSL_EDOM */ int gsl_sf_lnbeta_e(const double a, const double b, gsl_sf_result * result); double gsl_sf_lnbeta(const double a, const double b); int gsl_sf_lnbeta_sgn_e(const double x, const double y, gsl_sf_result * result, double * sgn); /* Beta Function * B(a,b) * * a > 0, b > 0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_beta_e(const double a, const double b, gsl_sf_result * result); double gsl_sf_beta(const double a, const double b); /* Normalized Incomplete Beta Function * B_x(a,b)/B(a,b) * * a > 0, b > 0, 0 <= x <= 1 * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_beta_inc_e(const double a, const double b, const double x, gsl_sf_result * result); double gsl_sf_beta_inc(const double a, const double b, const double x); /* The maximum x such that gamma(x) is not * considered an overflow. */ #define GSL_SF_GAMMA_XMAX 171.0 /* The maximum n such that gsl_sf_fact(n) does not give an overflow. */ #define GSL_SF_FACT_NMAX 170 /* The maximum n such that gsl_sf_doublefact(n) does not give an overflow. */ #define GSL_SF_DOUBLEFACT_NMAX 297 __END_DECLS #endif /* __GSL_SF_GAMMA_H__ */ sources_5316/external/gsl/gsl_sys__coerce.c0000664000176700017670000000252511723710247017652 0ustar paulpaul/* sys/coerce.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include double gsl_coerce_double (const double x); double gsl_coerce_double (const double x) { volatile double y; y = x; return y; } float gsl_coerce_float (const float x); float gsl_coerce_float (const float x) { volatile float y; y = x; return y; } /* The following function is not needed, but is included for completeness */ long double gsl_coerce_long_double (const long double x); long double gsl_coerce_long_double (const long double x) { volatile long double y; y = x; return y; } sources_5316/external/gsl/gsl_specfunc__mathieu_workspace.c0000664000176700017670000001323611723710247023115 0ustar paulpaul/* specfunc/mathieu_workspace.c * * Copyright (C) 2003 Lowell Johnson * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Author: L. Johnson */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_mathieu.h" gsl_sf_mathieu_workspace *gsl_sf_mathieu_alloc(const size_t nn, const double qq) { gsl_sf_mathieu_workspace *workspace; unsigned int even_order = nn/2 + 1, odd_order = (nn + 1)/2, extra_values; /* Compute the maximum number of extra terms required for 10^-18 root accuracy for a given value of q (contributed by Brian Gladman). */ extra_values = (int)(2.1*pow(fabs(qq), 0.37)) + 9; if (nn + 1 == 0) { GSL_ERROR_NULL("matrix dimension must be positive integer", GSL_EINVAL); } workspace = (gsl_sf_mathieu_workspace *)malloc(sizeof(gsl_sf_mathieu_workspace)); if (workspace == NULL) { GSL_ERROR_NULL("failed to allocate space for workspace", GSL_ENOMEM); } /* Extend matrices to ensure accuracy. */ even_order += extra_values; odd_order += extra_values; workspace->size = nn; workspace->even_order = even_order; workspace->odd_order = odd_order; workspace->extra_values = extra_values; /* Allocate space for the characteristic values. */ workspace->aa = (double *)malloc((nn+1)*sizeof(double)); if (workspace->aa == NULL) { free(workspace); GSL_ERROR_NULL("Error allocating memory for characteristic a values", GSL_ENOMEM); } workspace->bb = (double *)malloc((nn+1)*sizeof(double)); if (workspace->bb == NULL) { free(workspace->aa); free(workspace); GSL_ERROR_NULL("Error allocating memory for characteristic b values", GSL_ENOMEM); } /* Since even_order is always >= odd_order, dimension the arrays for even_order. */ workspace->dd = (double *)malloc(even_order*sizeof(double)); if (workspace->dd == NULL) { free(workspace->aa); free(workspace->bb); free(workspace); GSL_ERROR_NULL("failed to allocate space for diagonal", GSL_ENOMEM); } workspace->ee = (double *)malloc(even_order*sizeof(double)); if (workspace->ee == NULL) { free(workspace->dd); free(workspace->aa); free(workspace->bb); free(workspace); GSL_ERROR_NULL("failed to allocate space for diagonal", GSL_ENOMEM); } workspace->tt = (double *)malloc(3*even_order*sizeof(double)); if (workspace->tt == NULL) { free(workspace->ee); free(workspace->dd); free(workspace->aa); free(workspace->bb); free(workspace); GSL_ERROR_NULL("failed to allocate space for diagonal", GSL_ENOMEM); } workspace->e2 = (double *)malloc(even_order*sizeof(double)); if (workspace->e2 == NULL) { free(workspace->tt); free(workspace->ee); free(workspace->dd); free(workspace->aa); free(workspace->bb); free(workspace); GSL_ERROR_NULL("failed to allocate space for diagonal", GSL_ENOMEM); } workspace->zz = (double *)malloc(even_order*even_order*sizeof(double)); if (workspace->zz == NULL) { free(workspace->e2); free(workspace->tt); free(workspace->ee); free(workspace->dd); free(workspace->aa); free(workspace->bb); free(workspace); GSL_ERROR_NULL("failed to allocate space for diagonal", GSL_ENOMEM); } workspace->eval = gsl_vector_alloc(even_order); if (workspace->eval == NULL) { free(workspace->zz); free(workspace->e2); free(workspace->tt); free(workspace->ee); free(workspace->dd); free(workspace->aa); free(workspace->bb); free(workspace); GSL_ERROR_NULL("failed to allocate space for eval", GSL_ENOMEM); } workspace->evec = gsl_matrix_alloc(even_order, even_order); if (workspace->evec == NULL) { gsl_vector_free (workspace->eval); free(workspace->zz); free(workspace->e2); free(workspace->tt); free(workspace->ee); free(workspace->dd); free(workspace->aa); free(workspace->bb); free(workspace); GSL_ERROR_NULL("failed to allocate space for evec", GSL_ENOMEM); } workspace->wmat = gsl_eigen_symmv_alloc(even_order); if (workspace->wmat == NULL) { gsl_matrix_free (workspace->evec); gsl_vector_free (workspace->eval); free(workspace->zz); free(workspace->e2); free(workspace->tt); free(workspace->ee); free(workspace->dd); free(workspace->aa); free(workspace->bb); free(workspace); GSL_ERROR_NULL("failed to allocate space for wmat", GSL_ENOMEM); } return workspace; } void gsl_sf_mathieu_free(gsl_sf_mathieu_workspace *workspace) { gsl_vector_free(workspace->eval); gsl_matrix_free(workspace->evec); gsl_eigen_symmv_free(workspace->wmat); free(workspace->aa); free(workspace->bb); free(workspace->dd); free(workspace->ee); free(workspace->tt); free(workspace->e2); free(workspace->zz); free(workspace); } sources_5316/external/gsl/gsl_histogram__pdf2d.c0000664000176700017670000001052411723710247020566 0ustar paulpaul/* histogram/pdf2d.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram.h" #include "gsl_histogram2d.h" #include "gsl_histogram__find.c" int gsl_histogram2d_pdf_sample (const gsl_histogram2d_pdf * p, double r1, double r2, double *x, double *y) { size_t k; int status; /* Wrap the exclusive top of the bin down to the inclusive bottom of the bin. Since this is a single point it should not affect the distribution. */ if (r2 == 1.0) { r2 = 0.0; } if (r1 == 1.0) { r1 = 0.0; } status = find (p->nx * p->ny, p->sum, r1, &k); if (status) { GSL_ERROR ("cannot find r1 in cumulative pdf", GSL_EDOM); } else { size_t i = k / p->ny; size_t j = k - (i * p->ny); double delta = (r1 - p->sum[k]) / (p->sum[k + 1] - p->sum[k]); *x = p->xrange[i] + delta * (p->xrange[i + 1] - p->xrange[i]); *y = p->yrange[j] + r2 * (p->yrange[j + 1] - p->yrange[j]); return GSL_SUCCESS; } } gsl_histogram2d_pdf * gsl_histogram2d_pdf_alloc (const size_t nx, const size_t ny) { const size_t n = nx * ny; gsl_histogram2d_pdf *p; if (n == 0) { GSL_ERROR_VAL ("histogram2d pdf length n must be positive integer", GSL_EDOM, 0); } p = (gsl_histogram2d_pdf *) malloc (sizeof (gsl_histogram2d_pdf)); if (p == 0) { GSL_ERROR_VAL ("failed to allocate space for histogram2d pdf struct", GSL_ENOMEM, 0); } p->xrange = (double *) malloc ((nx + 1) * sizeof (double)); if (p->xrange == 0) { free (p); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram2d pdf xranges", GSL_ENOMEM, 0); } p->yrange = (double *) malloc ((ny + 1) * sizeof (double)); if (p->yrange == 0) { free (p->xrange); free (p); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram2d pdf yranges", GSL_ENOMEM, 0); } p->sum = (double *) malloc ((n + 1) * sizeof (double)); if (p->sum == 0) { free (p->yrange); free (p->xrange); free (p); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for histogram2d pdf sums", GSL_ENOMEM, 0); } p->nx = nx; p->ny = ny; return p; } int gsl_histogram2d_pdf_init (gsl_histogram2d_pdf * p, const gsl_histogram2d * h) { size_t i; const size_t nx = p->nx; const size_t ny = p->ny; const size_t n = nx * ny; if (nx != h->nx || ny != h->ny) { GSL_ERROR ("histogram2d size must match pdf size", GSL_EDOM); } for (i = 0; i < n; i++) { if (h->bin[i] < 0) { GSL_ERROR ("histogram bins must be non-negative to compute" "a probability distribution", GSL_EDOM); } } for (i = 0; i < nx + 1; i++) { p->xrange[i] = h->xrange[i]; } for (i = 0; i < ny + 1; i++) { p->yrange[i] = h->yrange[i]; } { double mean = 0, sum = 0; for (i = 0; i < n; i++) { mean += (h->bin[i] - mean) / ((double) (i + 1)); } p->sum[0] = 0; for (i = 0; i < n; i++) { sum += (h->bin[i] / mean) / n; p->sum[i + 1] = sum; } } return GSL_SUCCESS; } void gsl_histogram2d_pdf_free (gsl_histogram2d_pdf * p) { free (p->xrange); free (p->yrange); free (p->sum); free (p); } sources_5316/external/gsl/gsl_sf_coulomb.h0000664000176700017670000001045211705263724017513 0ustar paulpaul/* specfunc/gsl_sf_coulomb.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_COULOMB_H__ #define __GSL_SF_COULOMB_H__ #include "gsl_mode.h" #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Normalized hydrogenic bound states, radial dependence. */ /* R_1 := 2Z sqrt(Z) exp(-Z r) */ int gsl_sf_hydrogenicR_1_e(const double Z, const double r, gsl_sf_result * result); double gsl_sf_hydrogenicR_1(const double Z, const double r); /* R_n := norm exp(-Z r/n) (2Z/n)^l Laguerre[n-l-1, 2l+1, 2Z/n r] * * normalization such that psi(n,l,r) = R_n Y_{lm} */ int gsl_sf_hydrogenicR_e(const int n, const int l, const double Z, const double r, gsl_sf_result * result); double gsl_sf_hydrogenicR(const int n, const int l, const double Z, const double r); /* Coulomb wave functions F_{lam_F}(eta,x), G_{lam_G}(eta,x) * and their derivatives; lam_G := lam_F - k_lam_G * * lam_F, lam_G > -0.5 * x > 0.0 * * Conventions of Abramowitz+Stegun. * * Because there can be a large dynamic range of values, * overflows are handled gracefully. If an overflow occurs, * GSL_EOVRFLW is signalled and exponent(s) are returned * through exp_F, exp_G. These are such that * * F_L(eta,x) = fc[k_L] * exp(exp_F) * G_L(eta,x) = gc[k_L] * exp(exp_G) * F_L'(eta,x) = fcp[k_L] * exp(exp_F) * G_L'(eta,x) = gcp[k_L] * exp(exp_G) */ int gsl_sf_coulomb_wave_FG_e(const double eta, const double x, const double lam_F, const int k_lam_G, gsl_sf_result * F, gsl_sf_result * Fp, gsl_sf_result * G, gsl_sf_result * Gp, double * exp_F, double * exp_G); /* F_L(eta,x) as array */ int gsl_sf_coulomb_wave_F_array( double lam_min, int kmax, double eta, double x, double * fc_array, double * F_exponent ); /* F_L(eta,x), G_L(eta,x) as arrays */ int gsl_sf_coulomb_wave_FG_array(double lam_min, int kmax, double eta, double x, double * fc_array, double * gc_array, double * F_exponent, double * G_exponent ); /* F_L(eta,x), G_L(eta,x), F'_L(eta,x), G'_L(eta,x) as arrays */ int gsl_sf_coulomb_wave_FGp_array(double lam_min, int kmax, double eta, double x, double * fc_array, double * fcp_array, double * gc_array, double * gcp_array, double * F_exponent, double * G_exponent ); /* Coulomb wave function divided by the argument, * F(eta, x)/x. This is the function which reduces to * spherical Bessel functions in the limit eta->0. */ int gsl_sf_coulomb_wave_sphF_array(double lam_min, int kmax, double eta, double x, double * fc_array, double * F_exponent ); /* Coulomb wave function normalization constant. * [Abramowitz+Stegun 14.1.8, 14.1.9] */ int gsl_sf_coulomb_CL_e(double L, double eta, gsl_sf_result * result); int gsl_sf_coulomb_CL_array(double Lmin, int kmax, double eta, double * cl); __END_DECLS #endif /* __GSL_SF_COULOMB_H__ */ sources_5316/external/gsl/gsl_statistics_char.h0000664000176700017670000001036711705263724020557 0ustar paulpaul/* statistics/gsl_statistics_char.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_CHAR_H__ #define __GSL_STATISTICS_CHAR_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_char_mean (const char data[], const size_t stride, const size_t n); double gsl_stats_char_variance (const char data[], const size_t stride, const size_t n); double gsl_stats_char_sd (const char data[], const size_t stride, const size_t n); double gsl_stats_char_variance_with_fixed_mean (const char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_char_sd_with_fixed_mean (const char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_char_absdev (const char data[], const size_t stride, const size_t n); double gsl_stats_char_skew (const char data[], const size_t stride, const size_t n); double gsl_stats_char_kurtosis (const char data[], const size_t stride, const size_t n); double gsl_stats_char_lag1_autocorrelation (const char data[], const size_t stride, const size_t n); double gsl_stats_char_covariance (const char data1[], const size_t stride1,const char data2[], const size_t stride2, const size_t n); double gsl_stats_char_correlation (const char data1[], const size_t stride1,const char data2[], const size_t stride2, const size_t n); double gsl_stats_char_variance_m (const char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_char_sd_m (const char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_char_absdev_m (const char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_char_skew_m_sd (const char data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_char_kurtosis_m_sd (const char data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_char_lag1_autocorrelation_m (const char data[], const size_t stride, const size_t n, const double mean); double gsl_stats_char_covariance_m (const char data1[], const size_t stride1,const char data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); double gsl_stats_char_pvariance (const char data1[], const size_t stride1, const size_t n1, const char data2[], const size_t stride2, const size_t n2); double gsl_stats_char_ttest (const char data1[], const size_t stride1, const size_t n1, const char data2[], const size_t stride2, const size_t n2); char gsl_stats_char_max (const char data[], const size_t stride, const size_t n); char gsl_stats_char_min (const char data[], const size_t stride, const size_t n); void gsl_stats_char_minmax (char * min, char * max, const char data[], const size_t stride, const size_t n); size_t gsl_stats_char_max_index (const char data[], const size_t stride, const size_t n); size_t gsl_stats_char_min_index (const char data[], const size_t stride, const size_t n); void gsl_stats_char_minmax_index (size_t * min_index, size_t * max_index, const char data[], const size_t stride, const size_t n); double gsl_stats_char_median_from_sorted_data (const char sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_char_quantile_from_sorted_data (const char sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_CHAR_H__ */ sources_5316/external/gsl/gsl_histogram__copy.c0000664000176700017670000000414111723710247020537 0ustar paulpaul/* gsl_histogram_copy.c * Copyright (C) 2000 Simone Piccardi * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File gsl_histogram_copy.c: * Routine to copy an histogram. * Need GSL library and headers. * * Author: S. Piccardi * Jan. 2000 * ***************************************************************/ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram.h" /* * gsl_histogram_copy: * copy the contents of an histogram into another */ int gsl_histogram_memcpy (gsl_histogram * dest, const gsl_histogram * src) { size_t n = src->n; size_t i; if (dest->n != src->n) { GSL_ERROR ("histograms have different sizes, cannot copy", GSL_EINVAL); } for (i = 0; i <= n; i++) { dest->range[i] = src->range[i]; } for (i = 0; i < n; i++) { dest->bin[i] = src->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram_duplicate: * duplicate an histogram creating * an identical new one */ gsl_histogram * gsl_histogram_clone (const gsl_histogram * src) { size_t n = src->n; size_t i; gsl_histogram *h; h = gsl_histogram_calloc_range (n, src->range); if (h == 0) { GSL_ERROR_VAL ("failed to allocate space for histogram struct", GSL_ENOMEM, 0); } for (i = 0; i < n; i++) { h->bin[i] = src->bin[i]; } return h; } sources_5316/external/gsl/gsl_permute_char.h0000664000176700017670000000261611705263724020044 0ustar paulpaul/* permutation/gsl_permute_char.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_CHAR_H__ #define __GSL_PERMUTE_CHAR_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_char (const size_t * p, char * data, const size_t stride, const size_t n); int gsl_permute_char_inverse (const size_t * p, char * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_CHAR_H__ */ sources_5316/external/gsl/gsl_chebyshev.h0000664000176700017670000001025411705263724017343 0ustar paulpaul/* cheb/gsl_chebyshev.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_CHEBYSHEV_H__ #define __GSL_CHEBYSHEV_H__ #include "gsl_math.h" #include "gsl_mode.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* data for a Chebyshev series over a given interval */ struct gsl_cheb_series_struct { double * c; /* coefficients */ size_t order; /* order of expansion */ double a; /* lower interval point */ double b; /* upper interval point */ /* The following exists (mostly) for the benefit * of the implementation. It is an effective single * precision order, for use in single precision * evaluation. Users can use it if they like, but * only they know how to calculate it, since it is * specific to the approximated function. By default, * order_sp = order. * It is used explicitly only by the gsl_cheb_eval_mode * functions, which are not meant for casual use. */ size_t order_sp; /* Additional elements not used by specfunc */ double * f; /* function evaluated at chebyschev points */ }; typedef struct gsl_cheb_series_struct gsl_cheb_series; /* Calculate a Chebyshev series of specified order over * a specified interval, for a given function. * Return 0 on failure. */ gsl_cheb_series * gsl_cheb_alloc(const size_t order); /* Free a Chebyshev series previously calculated with gsl_cheb_alloc(). */ void gsl_cheb_free(gsl_cheb_series * cs); /* Calculate a Chebyshev series using the storage provided. * Uses the interval (a,b) and the order with which it * was initially created. * */ int gsl_cheb_init(gsl_cheb_series * cs, const gsl_function * func, const double a, const double b); /* Evaluate a Chebyshev series at a given point. * No errors can occur for a struct obtained from gsl_cheb_new(). */ double gsl_cheb_eval(const gsl_cheb_series * cs, const double x); int gsl_cheb_eval_err(const gsl_cheb_series * cs, const double x, double * result, double * abserr); /* Evaluate a Chebyshev series at a given point, to (at most) the given order. * No errors can occur for a struct obtained from gsl_cheb_new(). */ double gsl_cheb_eval_n(const gsl_cheb_series * cs, const size_t order, const double x); int gsl_cheb_eval_n_err(const gsl_cheb_series * cs, const size_t order, const double x, double * result, double * abserr); /* Evaluate a Chebyshev series at a given point, using the default * order for double precision mode(s) and the single precision * order for other modes. * No errors can occur for a struct obtained from gsl_cheb_new(). */ double gsl_cheb_eval_mode(const gsl_cheb_series * cs, const double x, gsl_mode_t mode); int gsl_cheb_eval_mode_e(const gsl_cheb_series * cs, const double x, gsl_mode_t mode, double * result, double * abserr); /* Compute the derivative of a Chebyshev series. */ int gsl_cheb_calc_deriv(gsl_cheb_series * deriv, const gsl_cheb_series * cs); /* Compute the integral of a Chebyshev series. The * integral is fixed by the condition that it equals zero at * the left end-point, ie it is precisely * Integrate[cs(t; a,b), {t, a, x}] */ int gsl_cheb_calc_integ(gsl_cheb_series * integ, const gsl_cheb_series * cs); __END_DECLS #endif /* __GSL_CHEBYSHEV_H__ */ sources_5316/external/gsl/gsl_vector_char.h0000664000176700017670000001566311705263724017673 0ustar paulpaul/* vector/gsl_vector_char.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_CHAR_H__ #define __GSL_VECTOR_CHAR_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_char.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; char *data; gsl_block_char *block; int owner; } gsl_vector_char; typedef struct { gsl_vector_char vector; } _gsl_vector_char_view; typedef _gsl_vector_char_view gsl_vector_char_view; typedef struct { gsl_vector_char vector; } _gsl_vector_char_const_view; typedef const _gsl_vector_char_const_view gsl_vector_char_const_view; /* Allocation */ gsl_vector_char *gsl_vector_char_alloc (const size_t n); gsl_vector_char *gsl_vector_char_calloc (const size_t n); gsl_vector_char *gsl_vector_char_alloc_from_block (gsl_block_char * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_char *gsl_vector_char_alloc_from_vector (gsl_vector_char * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_char_free (gsl_vector_char * v); /* Views */ _gsl_vector_char_view gsl_vector_char_view_array (char *v, size_t n); _gsl_vector_char_view gsl_vector_char_view_array_with_stride (char *base, size_t stride, size_t n); _gsl_vector_char_const_view gsl_vector_char_const_view_array (const char *v, size_t n); _gsl_vector_char_const_view gsl_vector_char_const_view_array_with_stride (const char *base, size_t stride, size_t n); _gsl_vector_char_view gsl_vector_char_subvector (gsl_vector_char *v, size_t i, size_t n); _gsl_vector_char_view gsl_vector_char_subvector_with_stride (gsl_vector_char *v, size_t i, size_t stride, size_t n); _gsl_vector_char_const_view gsl_vector_char_const_subvector (const gsl_vector_char *v, size_t i, size_t n); _gsl_vector_char_const_view gsl_vector_char_const_subvector_with_stride (const gsl_vector_char *v, size_t i, size_t stride, size_t n); /* Operations */ char gsl_vector_char_get (const gsl_vector_char * v, const size_t i); void gsl_vector_char_set (gsl_vector_char * v, const size_t i, char x); char *gsl_vector_char_ptr (gsl_vector_char * v, const size_t i); const char *gsl_vector_char_const_ptr (const gsl_vector_char * v, const size_t i); void gsl_vector_char_set_zero (gsl_vector_char * v); void gsl_vector_char_set_all (gsl_vector_char * v, char x); int gsl_vector_char_set_basis (gsl_vector_char * v, size_t i); int gsl_vector_char_fread (FILE * stream, gsl_vector_char * v); int gsl_vector_char_fwrite (FILE * stream, const gsl_vector_char * v); int gsl_vector_char_fscanf (FILE * stream, gsl_vector_char * v); int gsl_vector_char_fprintf (FILE * stream, const gsl_vector_char * v, const char *format); int gsl_vector_char_memcpy (gsl_vector_char * dest, const gsl_vector_char * src); int gsl_vector_char_reverse (gsl_vector_char * v); int gsl_vector_char_swap (gsl_vector_char * v, gsl_vector_char * w); int gsl_vector_char_swap_elements (gsl_vector_char * v, const size_t i, const size_t j); char gsl_vector_char_max (const gsl_vector_char * v); char gsl_vector_char_min (const gsl_vector_char * v); void gsl_vector_char_minmax (const gsl_vector_char * v, char * min_out, char * max_out); size_t gsl_vector_char_max_index (const gsl_vector_char * v); size_t gsl_vector_char_min_index (const gsl_vector_char * v); void gsl_vector_char_minmax_index (const gsl_vector_char * v, size_t * imin, size_t * imax); int gsl_vector_char_add (gsl_vector_char * a, const gsl_vector_char * b); int gsl_vector_char_sub (gsl_vector_char * a, const gsl_vector_char * b); int gsl_vector_char_mul (gsl_vector_char * a, const gsl_vector_char * b); int gsl_vector_char_div (gsl_vector_char * a, const gsl_vector_char * b); int gsl_vector_char_scale (gsl_vector_char * a, const double x); int gsl_vector_char_add_constant (gsl_vector_char * a, const double x); int gsl_vector_char_isnull (const gsl_vector_char * v); int gsl_vector_char_ispos (const gsl_vector_char * v); int gsl_vector_char_isneg (const gsl_vector_char * v); int gsl_vector_char_isnonneg (const gsl_vector_char * v); #ifdef HAVE_INLINE extern inline char gsl_vector_char_get (const gsl_vector_char * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_char_set (gsl_vector_char * v, const size_t i, char x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline char * gsl_vector_char_ptr (gsl_vector_char * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (char *) (v->data + i * v->stride); } extern inline const char * gsl_vector_char_const_ptr (const gsl_vector_char * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const char *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_CHAR_H__ */ sources_5316/external/gsl/gsl_multimin__vector_bfgs2.c0000664000176700017670000002030411723710247022012 0ustar paulpaul/* multimin/vector_bfgs2.c * * Copyright (C) 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA * 02110-1301, USA. */ /* vector_bfgs2.c -- Fletcher's implementation of the BFGS method, from R.Fletcher, "Practical Method's of Optimization", Second Edition, ISBN 0471915475. Algorithms 2.6.2 and 2.6.4. */ /* Thanks to Alan Irwin irwin@beluga.phys.uvic.ca. for suggesting this algorithm and providing sample fortran benchmarks */ #include "gsl__config.h" #include "gsl_multimin.h" #include "gsl_blas.h" #include "gsl_multimin__linear_minimize.c" #include "gsl_multimin__linear_wrapper.c" typedef struct { int iter; double step; double g0norm; double pnorm; double delta_f; double fp0; /* f'(0) for f(x-alpha*p) */ gsl_vector *x0; gsl_vector *g0; gsl_vector *p; /* work space */ gsl_vector *dx0; gsl_vector *dg0; gsl_vector *x_alpha; gsl_vector *g_alpha; /* wrapper function */ wrapper_t wrap; /* minimization parameters */ double rho; double sigma; double tau1; double tau2; double tau3; int order; } vector_bfgs2_state_t; static int vector_bfgs2_alloc (void *vstate, size_t n) { vector_bfgs2_state_t *state = (vector_bfgs2_state_t *) vstate; state->p = gsl_vector_calloc (n); if (state->p == 0) { GSL_ERROR ("failed to allocate space for p", GSL_ENOMEM); } state->x0 = gsl_vector_calloc (n); if (state->x0 == 0) { gsl_vector_free (state->p); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } state->g0 = gsl_vector_calloc (n); if (state->g0 == 0) { gsl_vector_free (state->x0); gsl_vector_free (state->p); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } state->dx0 = gsl_vector_calloc (n); if (state->dx0 == 0) { gsl_vector_free (state->g0); gsl_vector_free (state->x0); gsl_vector_free (state->p); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } state->dg0 = gsl_vector_calloc (n); if (state->dg0 == 0) { gsl_vector_free (state->dx0); gsl_vector_free (state->g0); gsl_vector_free (state->x0); gsl_vector_free (state->p); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } state->x_alpha = gsl_vector_calloc (n); if (state->x_alpha == 0) { gsl_vector_free (state->dg0); gsl_vector_free (state->dx0); gsl_vector_free (state->g0); gsl_vector_free (state->x0); gsl_vector_free (state->p); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } state->g_alpha = gsl_vector_calloc (n); if (state->g_alpha == 0) { gsl_vector_free (state->x_alpha); gsl_vector_free (state->dg0); gsl_vector_free (state->dx0); gsl_vector_free (state->g0); gsl_vector_free (state->x0); gsl_vector_free (state->p); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } return GSL_SUCCESS; } static int vector_bfgs2_set (void *vstate, gsl_multimin_function_fdf * fdf, const gsl_vector * x, double *f, gsl_vector * gradient, double step_size, double tol) { vector_bfgs2_state_t *state = (vector_bfgs2_state_t *) vstate; state->iter = 0; state->step = step_size; state->delta_f = 0; GSL_MULTIMIN_FN_EVAL_F_DF (fdf, x, f, gradient); /* Use the gradient as the initial direction */ gsl_vector_memcpy (state->x0, x); gsl_vector_memcpy (state->g0, gradient); state->g0norm = gsl_blas_dnrm2 (state->g0); gsl_vector_memcpy (state->p, gradient); gsl_blas_dscal (-1 / state->g0norm, state->p); state->pnorm = gsl_blas_dnrm2 (state->p); /* should be 1 */ state->fp0 = -state->g0norm; /* Prepare the wrapper */ prepare_wrapper (&state->wrap, fdf, state->x0, *f, state->g0, state->p, state->x_alpha, state->g_alpha); /* Prepare 1d minimisation parameters */ state->rho = 0.01; state->sigma = tol; state->tau1 = 9; state->tau2 = 0.05; state->tau3 = 0.5; state->order = 3; /* use cubic interpolation where possible */ return GSL_SUCCESS; } static void vector_bfgs2_free (void *vstate) { vector_bfgs2_state_t *state = (vector_bfgs2_state_t *) vstate; gsl_vector_free (state->x_alpha); gsl_vector_free (state->g_alpha); gsl_vector_free (state->dg0); gsl_vector_free (state->dx0); gsl_vector_free (state->g0); gsl_vector_free (state->x0); gsl_vector_free (state->p); } static int vector_bfgs2_restart (void *vstate) { vector_bfgs2_state_t *state = (vector_bfgs2_state_t *) vstate; state->iter = 0; return GSL_SUCCESS; } static int vector_bfgs2_iterate (void *vstate, gsl_multimin_function_fdf * fdf, gsl_vector * x, double *f, gsl_vector * gradient, gsl_vector * dx) { vector_bfgs2_state_t *state = (vector_bfgs2_state_t *) vstate; double alpha = 0.0, alpha1; gsl_vector *x0 = state->x0; gsl_vector *g0 = state->g0; gsl_vector *p = state->p; double g0norm = state->g0norm; double pnorm = state->pnorm; double delta_f = state->delta_f; double pg, dir; int status; double f0 = *f; if (pnorm == 0.0 || g0norm == 0.0 || state->fp0 == 0) { gsl_vector_set_zero (dx); return GSL_ENOPROG; } if (delta_f < 0) { double del = GSL_MAX_DBL (-delta_f, 10 * GSL_DBL_EPSILON * fabs(f0)); alpha1 = GSL_MIN_DBL (1.0, 2.0 * del / (-state->fp0)); } else { alpha1 = fabs(state->step); } /* line minimisation, with cubic interpolation (order = 3) */ status = minimize (&state->wrap.fdf_linear, state->rho, state->sigma, state->tau1, state->tau2, state->tau3, state->order, alpha1, &alpha); if (status != GSL_SUCCESS) { return status; } update_position (&(state->wrap), alpha, x, f, gradient); state->delta_f = *f - f0; /* Choose a new direction for the next step */ { /* This is the BFGS update: */ /* p' = g1 - A dx - B dg */ /* A = - (1+ dg.dg/dx.dg) B + dg.g/dx.dg */ /* B = dx.g/dx.dg */ gsl_vector *dx0 = state->dx0; gsl_vector *dg0 = state->dg0; double dxg, dgg, dxdg, dgnorm, A, B; /* dx0 = x - x0 */ gsl_vector_memcpy (dx0, x); gsl_blas_daxpy (-1.0, x0, dx0); gsl_vector_memcpy (dx, dx0); /* keep a copy */ /* dg0 = g - g0 */ gsl_vector_memcpy (dg0, gradient); gsl_blas_daxpy (-1.0, g0, dg0); gsl_blas_ddot (dx0, gradient, &dxg); gsl_blas_ddot (dg0, gradient, &dgg); gsl_blas_ddot (dx0, dg0, &dxdg); dgnorm = gsl_blas_dnrm2 (dg0); if (dxdg != 0) { B = dxg / dxdg; A = -(1.0 + dgnorm * dgnorm / dxdg) * B + dgg / dxdg; } else { B = 0; A = 0; } gsl_vector_memcpy (p, gradient); gsl_blas_daxpy (-A, dx0, p); gsl_blas_daxpy (-B, dg0, p); } gsl_vector_memcpy (g0, gradient); gsl_vector_memcpy (x0, x); state->g0norm = gsl_blas_dnrm2 (g0); state->pnorm = gsl_blas_dnrm2 (p); /* update direction and fp0 */ gsl_blas_ddot (p, gradient, &pg); dir = (pg >= 0.0) ? -1.0 : +1.0; gsl_blas_dscal (dir / state->pnorm, p); state->pnorm = gsl_blas_dnrm2 (p); gsl_blas_ddot (p, g0, &state->fp0); change_direction (&state->wrap); return GSL_SUCCESS; } static const gsl_multimin_fdfminimizer_type vector_bfgs2_type = { "vector_bfgs2", /* name */ sizeof (vector_bfgs2_state_t), &vector_bfgs2_alloc, &vector_bfgs2_set, &vector_bfgs2_iterate, &vector_bfgs2_restart, &vector_bfgs2_free }; const gsl_multimin_fdfminimizer_type * gsl_multimin_fdfminimizer_vector_bfgs2 = &vector_bfgs2_type; sources_5316/external/gsl/gsl_randist__discrete.c0000664000176700017670000003146011723710247021042 0ustar paulpaul/* randist/discrete.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Random Discrete Events Given K discrete events with different probabilities P[k] produce a value k consistent with its probability. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ /* * Based on: Alastair J Walker, An efficient method for generating * discrete random variables with general distributions, ACM Trans * Math Soft 3, 253-256 (1977). See also: D. E. Knuth, The Art of * Computer Programming, Volume 2 (Seminumerical algorithms), 3rd * edition, Addison-Wesley (1997), p120. * Walker's algorithm does some preprocessing, and provides two * arrays: floating point F[k] and integer A[k]. A value k is chosen * from 0..K-1 with equal likelihood, and then a uniform random number * u is compared to F[k]. If it is less than F[k], then k is * returned. Otherwise, A[k] is returned. * Walker's original paper describes an O(K^2) algorithm for setting * up the F and A arrays. I found this disturbing since I wanted to * use very large values of K. I'm sure I'm not the first to realize * this, but in fact the preprocessing can be done in O(K) steps. * A figure of merit for the preprocessing is the average value for * the F[k]'s (that is, SUM_k F[k]/K); this corresponds to the * probability that k is returned, instead of A[k], thereby saving a * redirection. Walker's O(K^2) preprocessing will generally improve * that figure of merit, compared to my cheaper O(K) method; from some * experiments with a perl script, I get values of around 0.6 for my * method and just under 0.75 for Walker's. Knuth has pointed out * that finding _the_ optimum lookup tables, which maximize the * average F[k], is a combinatorially difficult problem. But any * valid preprocessing will still provide O(1) time for the call to * gsl_ran_discrete(). I find that if I artificially set F[k]=1 -- * ie, better than optimum! -- I get a speedup of maybe 20%, so that's * the maximum I could expect from the most expensive preprocessing. * Folding in the difference of 0.6 vs 0.75, I'd estimate that the * speedup would be less than 10%. * I've not implemented it here, but one compromise is to sort the * probabilities once, and then work from the two ends inward. This * requires O(K log K), still lots cheaper than O(K^2), and from my * experiments with the perl script, the figure of merit is within * about 0.01 for K up to 1000, and no sign of diverging (in fact, * they seemed to be converging, but it's hard to say with just a * handful of runs). * The O(K) algorithm goes through all the p_k's and decides if they * are "smalls" or "bigs" according to whether they are less than or * greater than the mean value 1/K. The indices to the smalls and the * bigs are put in separate stacks, and then we work through the * stacks together. For each small, we pair it up with the next big * in the stack (Walker always wanted to pair up the smallest small * with the biggest big). The small "borrows" from the big just * enough to bring the small up to mean. This reduces the size of the * big, so the (smaller) big is compared again to the mean, and if it * is smaller, it gets "popped" from the big stack and "pushed" to the * small stack. Otherwise, it stays put. Since every time we pop a * small, we are able to deal with it right then and there, and we * never have to pop more than K smalls, then the algorithm is O(K). * This implementation sets up two separate stacks, and allocates K * elements between them. Since neither stack ever grows, we do an * extra O(K) pass through the data to determine how many smalls and * bigs there are to begin with and allocate appropriately. In all * there are 2*K*sizeof(double) transient bytes of memory that are * used than returned, and K*(sizeof(int)+sizeof(double)) bytes used * in the lookup table. * Walker spoke of using two random numbers (an integer 0..K-1, and a * floating point u in [0,1]), but Knuth points out that one can just * use the integer and fractional parts of K*u where u is in [0,1]. * In fact, Knuth further notes that taking F'[k]=(k+F[k])/K, one can * directly compare u to F'[k] without having to explicitly set * u=K*u-int(K*u). * Usage: * Starting with an array of probabilities P, initialize and do * preprocessing with a call to: * gsl_rng *r; * gsl_ran_discrete_t *f; * f = gsl_ran_discrete_preproc(K,P); * Then, whenever a random index 0..K-1 is desired, use * k = gsl_ran_discrete(r,f); * Note that several different randevent struct's can be * simultaneously active. * Aside: A very clever alternative approach is described in * Abramowitz and Stegun, p 950, citing: Marsaglia, Random variables * and computers, Proc Third Prague Conference in Probability Theory, * 1962. A more accesible reference is: G. Marsaglia, Generating * discrete random numbers in a computer, Comm ACM 6, 37-38 (1963). * If anybody is interested, I (jt) have also coded up this version as * part of another software package. However, I've done some * comparisons, and the Walker method is both faster and more stingy * with memory. So, in the end I decided not to include it with the * GSL package. * Written 26 Jan 1999, James Theiler, jt@lanl.gov * Adapted to GSL, 30 Jan 1999, jt */ #include "gsl__config.h" #include #include #include #include "gsl_errno.h" #include "gsl_rng.h" #include "gsl_randist.h" #define DEBUG 0 #define KNUTH_CONVENTION 1 /* Saves a few steps of arithmetic * in the call to gsl_ran_discrete() */ /*** Begin Stack (this code is used just in this file) ***/ /* Stack code converted to use unsigned indices (i.e. s->i == 0 now means an empty stack, instead of -1), for consistency and to give a bigger allowable range. BJG */ typedef struct { size_t N; /* max number of elts on stack */ size_t *v; /* array of values on the stack */ size_t i; /* index of top of stack */ } gsl_stack_t; static gsl_stack_t * new_stack(size_t N) { gsl_stack_t *s; s = (gsl_stack_t *)malloc(sizeof(gsl_stack_t)); s->N = N; s->i = 0; /* indicates stack is empty */ s->v = (size_t *)malloc(sizeof(size_t)*N); return s; } static void push_stack(gsl_stack_t *s, size_t v) { if ((s->i) >= (s->N)) { fprintf(stderr,"Cannot push stack!\n"); abort(); /* FIXME: fatal!! */ } (s->v)[s->i] = v; s->i += 1; } static size_t pop_stack(gsl_stack_t *s) { if ((s->i) == 0) { fprintf(stderr,"Cannot pop stack!\n"); abort(); /* FIXME: fatal!! */ } s->i -= 1; return ((s->v)[s->i]); } static inline size_t size_stack(const gsl_stack_t *s) { return s->i; } static void free_stack(gsl_stack_t *s) { free((char *)(s->v)); free((char *)s); } /*** End Stack ***/ /*** Begin Walker's Algorithm ***/ gsl_ran_discrete_t * gsl_ran_discrete_preproc(size_t Kevents, const double *ProbArray) { size_t k,b,s; gsl_ran_discrete_t *g; size_t nBigs, nSmalls; gsl_stack_t *Bigs; gsl_stack_t *Smalls; double *E; double pTotal = 0.0, mean, d; if (Kevents < 1) { /* Could probably treat Kevents=1 as a special case */ GSL_ERROR_VAL ("number of events must be a positive integer", GSL_EINVAL, 0); } /* Make sure elements of ProbArray[] are positive. * Won't enforce that sum is unity; instead will just normalize */ for (k=0; kK = Kevents; g->F = (double *)malloc(sizeof(double)*Kevents); g->A = (size_t *)malloc(sizeof(size_t)*Kevents); E = (double *)malloc(sizeof(double)*Kevents); if (E==NULL) { GSL_ERROR_VAL ("Cannot allocate memory for randevent", GSL_ENOMEM, 0); } for (k=0; k 0) { s = pop_stack(Smalls); if (size_stack(Bigs) == 0) { (g->A)[s]=s; (g->F)[s]=1.0; continue; } b = pop_stack(Bigs); (g->A)[s]=b; (g->F)[s]=Kevents*E[s]; #if DEBUG fprintf(stderr,"s=%2d, A=%2d, F=%.4f\n",s,(g->A)[s],(g->F)[s]); #endif d = mean - E[s]; E[s] += d; /* now E[s] == mean */ E[b] -= d; if (E[b] < mean) { push_stack(Smalls,b); /* no longer big, join ranks of the small */ } else if (E[b] > mean) { push_stack(Bigs,b); /* still big, put it back where you found it */ } else { /* E[b]==mean implies it is finished too */ (g->A)[b]=b; (g->F)[b]=1.0; } } while (size_stack(Bigs) > 0) { b = pop_stack(Bigs); (g->A)[b]=b; (g->F)[b]=1.0; } /* Stacks have been emptied, and A and F have been filled */ if ( size_stack(Smalls) != 0) { GSL_ERROR_VAL ("Smalls stack has not been emptied", GSL_ESANITY, 0 ); } #if 0 /* if 1, then artificially set all F[k]'s to unity. This will * give wrong answers, but you'll get them faster. But, not * that much faster (I get maybe 20%); that's an upper bound * on what the optimal preprocessing would give. */ for (k=0; kF)[k] = 1.0; } #endif #if KNUTH_CONVENTION /* For convenience, set F'[k]=(k+F[k])/K */ /* This saves some arithmetic in gsl_ran_discrete(); I find that * it doesn't actually make much difference. */ for (k=0; kF)[k] += k; (g->F)[k] /= Kevents; } #endif free_stack(Bigs); free_stack(Smalls); free((char *)E); return g; } size_t gsl_ran_discrete(const gsl_rng *r, const gsl_ran_discrete_t *g) { size_t c=0; double u,f; u = gsl_rng_uniform(r); #if KNUTH_CONVENTION c = (u*(g->K)); #else u *= g->K; c = u; u -= c; #endif f = (g->F)[c]; /* fprintf(stderr,"c,f,u: %d %.4f %f\n",c,f,u); */ if (f == 1.0) return c; if (u < f) { return c; } else { return (g->A)[c]; } } void gsl_ran_discrete_free(gsl_ran_discrete_t *g) { free((char *)(g->A)); free((char *)(g->F)); free((char *)g); } double gsl_ran_discrete_pdf(size_t k, const gsl_ran_discrete_t *g) { size_t i,K; double f,p=0; K= g->K; if (k>K) return 0; for (i=0; iF)[i]; #if KNUTH_CONVENTION f = K*f-i; #endif if (i==k) { p += f; } else if (k == (g->A)[i]) { p += 1.0 - f; } } return p/K; } sources_5316/external/gsl/gsl_cdf__pascal.c0000664000176700017670000000237611723710247017577 0ustar paulpaul/* cdf/pascal.c * * Copyright (C) 2006, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" /* The Pascal distribution is a negative binomial with valued integer n */ double gsl_cdf_pascal_P (const unsigned int k, const double p, const unsigned int n) { double P = gsl_cdf_negative_binomial_P (k, p, (double) n); return P; } double gsl_cdf_pascal_Q (const unsigned int k, const double p, const unsigned int n) { double Q = gsl_cdf_negative_binomial_Q (k, p, (double) n); return Q; } sources_5316/external/gsl/gsl_specfunc__log.c0000664000176700017670000001543111723710247020163 0ustar paulpaul/* specfunc/log.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_log.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* Chebyshev expansion for log(1 + x(t))/x(t) * * x(t) = (4t-1)/(2(4-t)) * t(x) = (8x+1)/(2(x+2)) * -1/2 < x < 1/2 * -1 < t < 1 */ static double lopx_data[21] = { 2.16647910664395270521272590407, -0.28565398551049742084877469679, 0.01517767255690553732382488171, -0.00200215904941415466274422081, 0.00019211375164056698287947962, -0.00002553258886105542567601400, 2.9004512660400621301999384544e-06, -3.8873813517057343800270917900e-07, 4.7743678729400456026672697926e-08, -6.4501969776090319441714445454e-09, 8.2751976628812389601561347296e-10, -1.1260499376492049411710290413e-10, 1.4844576692270934446023686322e-11, -2.0328515972462118942821556033e-12, 2.7291231220549214896095654769e-13, -3.7581977830387938294437434651e-14, 5.1107345870861673561462339876e-15, -7.0722150011433276578323272272e-16, 9.7089758328248469219003866867e-17, -1.3492637457521938883731579510e-17, 1.8657327910677296608121390705e-18 }; static cheb_series lopx_cs = { lopx_data, 20, -1, 1, 10 }; /* Chebyshev expansion for (log(1 + x(t)) - x(t))/x(t)^2 * * x(t) = (4t-1)/(2(4-t)) * t(x) = (8x+1)/(2(x+2)) * -1/2 < x < 1/2 * -1 < t < 1 */ static double lopxmx_data[20] = { -1.12100231323744103373737274541, 0.19553462773379386241549597019, -0.01467470453808083971825344956, 0.00166678250474365477643629067, -0.00018543356147700369785746902, 0.00002280154021771635036301071, -2.8031253116633521699214134172e-06, 3.5936568872522162983669541401e-07, -4.6241857041062060284381167925e-08, 6.0822637459403991012451054971e-09, -8.0339824424815790302621320732e-10, 1.0751718277499375044851551587e-10, -1.4445310914224613448759230882e-11, 1.9573912180610336168921438426e-12, -2.6614436796793061741564104510e-13, 3.6402634315269586532158344584e-14, -4.9937495922755006545809120531e-15, 6.8802890218846809524646902703e-16, -9.5034129794804273611403251480e-17, 1.3170135013050997157326965813e-17 }; static cheb_series lopxmx_cs = { lopxmx_data, 19, -1, 1, 9 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_log_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else { result->val = log(x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_log_abs_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0) { DOMAIN_ERROR(result); } else { result->val = log(fabs(x)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_complex_log_e(const double zr, const double zi, gsl_sf_result * lnr, gsl_sf_result * theta) { /* CHECK_POINTER(lnr) */ /* CHECK_POINTER(theta) */ if(zr != 0.0 || zi != 0.0) { const double ax = fabs(zr); const double ay = fabs(zi); const double min = GSL_MIN(ax, ay); const double max = GSL_MAX(ax, ay); lnr->val = log(max) + 0.5 * log(1.0 + (min/max)*(min/max)); lnr->err = 2.0 * GSL_DBL_EPSILON * fabs(lnr->val); theta->val = atan2(zi, zr); theta->err = GSL_DBL_EPSILON * fabs(lnr->val); return GSL_SUCCESS; } else { DOMAIN_ERROR_2(lnr, theta); } } int gsl_sf_log_1plusx_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0) { DOMAIN_ERROR(result); } else if(fabs(x) < GSL_ROOT6_DBL_EPSILON) { const double c1 = -0.5; const double c2 = 1.0/3.0; const double c3 = -1.0/4.0; const double c4 = 1.0/5.0; const double c5 = -1.0/6.0; const double c6 = 1.0/7.0; const double c7 = -1.0/8.0; const double c8 = 1.0/9.0; const double c9 = -1.0/10.0; const double t = c5 + x*(c6 + x*(c7 + x*(c8 + x*c9))); result->val = x * (1.0 + x*(c1 + x*(c2 + x*(c3 + x*(c4 + x*t))))); result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(fabs(x) < 0.5) { double t = 0.5*(8.0*x + 1.0)/(x+2.0); gsl_sf_result c; cheb_eval_e(&lopx_cs, t, &c); result->val = x * c.val; result->err = fabs(x * c.err); return GSL_SUCCESS; } else { result->val = log(1.0 + x); result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_log_1plusx_mx_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0) { DOMAIN_ERROR(result); } else if(fabs(x) < GSL_ROOT5_DBL_EPSILON) { const double c1 = -0.5; const double c2 = 1.0/3.0; const double c3 = -1.0/4.0; const double c4 = 1.0/5.0; const double c5 = -1.0/6.0; const double c6 = 1.0/7.0; const double c7 = -1.0/8.0; const double c8 = 1.0/9.0; const double c9 = -1.0/10.0; const double t = c5 + x*(c6 + x*(c7 + x*(c8 + x*c9))); result->val = x*x * (c1 + x*(c2 + x*(c3 + x*(c4 + x*t)))); result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(fabs(x) < 0.5) { double t = 0.5*(8.0*x + 1.0)/(x+2.0); gsl_sf_result c; cheb_eval_e(&lopxmx_cs, t, &c); result->val = x*x * c.val; result->err = x*x * c.err; return GSL_SUCCESS; } else { const double lterm = log(1.0 + x); result->val = lterm - x; result->err = GSL_DBL_EPSILON * (fabs(lterm) + fabs(x)); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_log(const double x) { EVAL_RESULT(gsl_sf_log_e(x, &result)); } double gsl_sf_log_abs(const double x) { EVAL_RESULT(gsl_sf_log_abs_e(x, &result)); } double gsl_sf_log_1plusx(const double x) { EVAL_RESULT(gsl_sf_log_1plusx_e(x, &result)); } double gsl_sf_log_1plusx_mx(const double x) { EVAL_RESULT(gsl_sf_log_1plusx_mx_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__source_copy_r.h0000664000176700017670000000172111705263724021540 0ustar paulpaul/* blas/source_copy_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { Y[iy] = X[ix]; ix += incX; iy += incY; } } sources_5316/external/gsl/gsl_rng__ranlux.c0000664000176700017670000001242511723710247017673 0ustar paulpaul/* rng/ranlux.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is a lagged fibonacci generator with skipping developed by Luescher. The sequence is a series of 24-bit integers, x_n, x_n = d_n + b_n where d_n = x_{n-10} - x_{n-24} - c_{n-1}, b_n = 0 if d_n >= 0 and b_n = 2^24 if d_n < 0, c_n = 0 if d_n >= 0 and c_n = 1 if d_n < 0, where after 24 samples a group of p integers are "skipped", to reduce correlations. By default p = 199, but can be increased to 365. The period of the generator is around 10^171. From: M. Luescher, "A portable high-quality random number generator for lattice field theory calculations", Computer Physics Communications, 79 (1994) 100-110. Available on the net as hep-lat/9309020 at http://xxx.lanl.gov/ See also, F. James, "RANLUX: A Fortran implementation of the high-quality pseudo-random number generator of Luscher", Computer Physics Communications, 79 (1994) 111-114 Kenneth G. Hamilton, F. James, "Acceleration of RANLUX", Computer Physics Communications, 101 (1997) 241-248 Kenneth G. Hamilton, "Assembler RANLUX for PCs", Computer Physics Communications, 101 (1997) 249-253 */ static inline unsigned long int ranlux_get (void *vstate); static double ranlux_get_double (void *vstate); static void ranlux_set_lux (void *state, unsigned long int s, unsigned int luxury); static void ranlux_set (void *state, unsigned long int s); static void ranlux389_set (void *state, unsigned long int s); static const unsigned long int mask_lo = 0x00ffffffUL; /* 2^24 - 1 */ static const unsigned long int mask_hi = ~0x00ffffffUL; static const unsigned long int two24 = 16777216; /* 2^24 */ typedef struct { unsigned int i; unsigned int j; unsigned int n; unsigned int skip; unsigned int carry; unsigned long int u[24]; } ranlux_state_t; static inline unsigned long int increment_state (ranlux_state_t * state); static inline unsigned long int increment_state (ranlux_state_t * state) { unsigned int i = state->i; unsigned int j = state->j; long int delta = state->u[j] - state->u[i] - state->carry; if (delta & mask_hi) { state->carry = 1; delta &= mask_lo; } else { state->carry = 0; } state->u[i] = delta; if (i == 0) { i = 23; } else { i--; } state->i = i; if (j == 0) { j = 23; } else { j--; } state->j = j; return delta; } static inline unsigned long int ranlux_get (void *vstate) { ranlux_state_t *state = (ranlux_state_t *) vstate; const unsigned int skip = state->skip; unsigned long int r = increment_state (state); state->n++; if (state->n == 24) { unsigned int i; state->n = 0; for (i = 0; i < skip; i++) increment_state (state); } return r; } static double ranlux_get_double (void *vstate) { return ranlux_get (vstate) / 16777216.0; } static void ranlux_set_lux (void *vstate, unsigned long int s, unsigned int luxury) { ranlux_state_t *state = (ranlux_state_t *) vstate; int i; long int seed; if (s == 0) s = 314159265; /* default seed is 314159265 */ seed = s; /* This is the initialization algorithm of F. James, widely in use for RANLUX. */ for (i = 0; i < 24; i++) { unsigned long int k = seed / 53668; seed = 40014 * (seed - k * 53668) - k * 12211; if (seed < 0) { seed += 2147483563; } state->u[i] = seed % two24; } state->i = 23; state->j = 9; state->n = 0; state->skip = luxury - 24; if (state->u[23] & mask_hi) { state->carry = 1; } else { state->carry = 0; } } static void ranlux_set (void *vstate, unsigned long int s) { ranlux_set_lux (vstate, s, 223); } static void ranlux389_set (void *vstate, unsigned long int s) { ranlux_set_lux (vstate, s, 389); } static const gsl_rng_type ranlux_type = {"ranlux", /* name */ 0x00ffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ranlux_state_t), &ranlux_set, &ranlux_get, &ranlux_get_double}; static const gsl_rng_type ranlux389_type = {"ranlux389", /* name */ 0x00ffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ranlux_state_t), &ranlux389_set, &ranlux_get, &ranlux_get_double}; const gsl_rng_type *gsl_rng_ranlux = &ranlux_type; const gsl_rng_type *gsl_rng_ranlux389 = &ranlux389_type; sources_5316/external/gsl/gsl_cblas__sgbmv.c0000664000176700017670000000070311723710247017772 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_sgbmv (const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const int KL, const int KU, const float alpha, const float *A, const int lda, const float *X, const int incX, const float beta, float *Y, const int incY) { #define BASE float #include "gsl_cblas__source_gbmv_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__dspr.c0000664000176700017670000000050411723710247017623 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dspr (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *X, const int incX, double *Ap) { #define BASE double #include "gsl_cblas__source_spr.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_trsv_c.h0000664000176700017670000001774111705263724021556 0ustar paulpaul/* blas/source_trsv_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (TransA == CblasConjTrans) ? -1 : 1; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; const int nonunit = (Diag == CblasNonUnit); INDEX i, j; INDEX ix, jx; if (N == 0) return; /* form x := inv( A )*x */ if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { ix = OFFSET(N, incX) + incX * (N - 1); if (nonunit) { const BASE a_real = CONST_REAL(A, lda * (N - 1) + (N - 1)); const BASE a_imag = conj * CONST_IMAG(A, lda * (N - 1) + (N - 1)); const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (x_real * b_real + x_imag * b_imag) / s; IMAG(X, ix) = (x_imag * b_real - b_imag * x_real) / s; } ix -= incX; for (i = N - 1; i > 0 && i--;) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); jx = ix + incX; for (j = i + 1; j < N; j++) { const BASE Aij_real = CONST_REAL(A, lda * i + j); const BASE Aij_imag = conj * CONST_IMAG(A, lda * i + j); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(A, lda * i + i); const BASE a_imag = conj * CONST_IMAG(A, lda * i + i); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { /* forward substitution */ ix = OFFSET(N, incX); if (nonunit) { const BASE a_real = CONST_REAL(A, lda * 0 + 0); const BASE a_imag = conj * CONST_IMAG(A, lda * 0 + 0); const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (x_real * b_real + x_imag * b_imag) / s; IMAG(X, ix) = (x_imag * b_real - b_imag * x_real) / s; } ix += incX; for (i = 1; i < N; i++) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE Aij_real = CONST_REAL(A, lda * i + j); const BASE Aij_imag = conj * CONST_IMAG(A, lda * i + j); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(A, lda * i + i); const BASE a_imag = conj * CONST_IMAG(A, lda * i + i); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := inv( A' )*x */ /* forward substitution */ ix = OFFSET(N, incX); if (nonunit) { const BASE a_real = CONST_REAL(A, lda * 0 + 0); const BASE a_imag = conj * CONST_IMAG(A, lda * 0 + 0); const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (x_real * b_real + x_imag * b_imag) / s; IMAG(X, ix) = (x_imag * b_real - b_imag * x_real) / s; } ix += incX; for (i = 1; i < N; i++) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE Aij_real = CONST_REAL(A, lda * j + i); const BASE Aij_imag = conj * CONST_IMAG(A, lda * j + i); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(A, lda * i + i); const BASE a_imag = conj * CONST_IMAG(A, lda * i + i); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { /* backsubstitution */ ix = OFFSET(N, incX) + incX * (N - 1); if (nonunit) { const BASE a_real = CONST_REAL(A, lda * (N - 1) + (N - 1)); const BASE a_imag = conj * CONST_IMAG(A, lda * (N - 1) + (N - 1)); const BASE x_real = REAL(X, ix); const BASE x_imag = IMAG(X, ix); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (x_real * b_real + x_imag * b_imag) / s; IMAG(X, ix) = (x_imag * b_real - b_imag * x_real) / s; } ix -= incX; for (i = N - 1; i > 0 && i--;) { BASE tmp_real = REAL(X, ix); BASE tmp_imag = IMAG(X, ix); jx = ix + incX; for (j = i + 1; j < N; j++) { const BASE Aij_real = CONST_REAL(A, lda * j + i); const BASE Aij_imag = conj * CONST_IMAG(A, lda * j + i); const BASE x_real = REAL(X, jx); const BASE x_imag = IMAG(X, jx); tmp_real -= Aij_real * x_real - Aij_imag * x_imag; tmp_imag -= Aij_real * x_imag + Aij_imag * x_real; jx += incX; } if (nonunit) { const BASE a_real = CONST_REAL(A, lda * i + i); const BASE a_imag = conj * CONST_IMAG(A, lda * i + i); const BASE s = xhypot(a_real, a_imag); const BASE b_real = a_real / s; const BASE b_imag = a_imag / s; REAL(X, ix) = (tmp_real * b_real + tmp_imag * b_imag) / s; IMAG(X, ix) = (tmp_imag * b_real - tmp_real * b_imag) / s; } else { REAL(X, ix) = tmp_real; IMAG(X, ix) = tmp_imag; } ix -= incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_multiroots__fdjac.c0000664000176700017670000000561311723710247021065 0ustar paulpaul/* multiroots/fdjac.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_multiroots.h" int gsl_multiroot_fdjacobian (gsl_multiroot_function * F, const gsl_vector * x, const gsl_vector * f, double epsrel, gsl_matrix * jacobian) { const size_t n = x->size; const size_t m = f->size; const size_t n1 = jacobian->size1; const size_t n2 = jacobian->size2; int status = 0; if (m != n1 || n != n2) { GSL_ERROR ("function and jacobian are not conformant", GSL_EBADLEN); } { size_t i,j; gsl_vector *x1, *f1; x1 = gsl_vector_alloc (n); if (x1 == 0) { GSL_ERROR ("failed to allocate space for x1 workspace", GSL_ENOMEM); } f1 = gsl_vector_alloc (m); if (f1 == 0) { gsl_vector_free (x1); GSL_ERROR ("failed to allocate space for f1 workspace", GSL_ENOMEM); } gsl_vector_memcpy (x1, x); /* copy x into x1 */ for (j = 0; j < n; j++) { double xj = gsl_vector_get (x, j); double dx = epsrel * fabs (xj); if (dx == 0) { dx = epsrel; } gsl_vector_set (x1, j, xj + dx); { int f_stat = GSL_MULTIROOT_FN_EVAL (F, x1, f1); if (f_stat != GSL_SUCCESS) { status = GSL_EBADFUNC; break; /* n.b. avoid memory leak for x1,f1 */ } } gsl_vector_set (x1, j, xj); for (i = 0; i < m; i++) { double g1 = gsl_vector_get (f1, i); double g0 = gsl_vector_get (f, i); gsl_matrix_set (jacobian, i, j, (g1 - g0) / dx); } { gsl_vector_view col = gsl_matrix_column (jacobian, j); int null_col = gsl_vector_isnull (&col.vector); /* if column is null, return an error - this may be due to dx being too small. Try increasing epsrel */ if (null_col) { status = GSL_ESING; } } } gsl_vector_free (x1); gsl_vector_free (f1); } if (status) return status; else return GSL_SUCCESS; } sources_5316/external/gsl/gsl_sf__bessel_amp_phase.c0000644000176700017670000001105410707442037021471 0ustar paulpaul/* specfunc/bessel_amp_phase.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf__bessel_amp_phase.h" /* chebyshev expansions for amplitude and phase functions used in bessel evaluations These are the same for J0,Y0 and for J1,Y1, so they sit outside those functions. */ static double bm0_data[21] = { 0.09284961637381644, -0.00142987707403484, 0.00002830579271257, -0.00000143300611424, 0.00000012028628046, -0.00000001397113013, 0.00000000204076188, -0.00000000035399669, 0.00000000007024759, -0.00000000001554107, 0.00000000000376226, -0.00000000000098282, 0.00000000000027408, -0.00000000000008091, 0.00000000000002511, -0.00000000000000814, 0.00000000000000275, -0.00000000000000096, 0.00000000000000034, -0.00000000000000012, 0.00000000000000004 }; const cheb_series _gsl_sf_bessel_amp_phase_bm0_cs = { bm0_data, 20, -1, 1, 10 }; static double bth0_data[24] = { -0.24639163774300119, 0.001737098307508963, -0.000062183633402968, 0.000004368050165742, -0.000000456093019869, 0.000000062197400101, -0.000000010300442889, 0.000000001979526776, -0.000000000428198396, 0.000000000102035840, -0.000000000026363898, 0.000000000007297935, -0.000000000002144188, 0.000000000000663693, -0.000000000000215126, 0.000000000000072659, -0.000000000000025465, 0.000000000000009229, -0.000000000000003448, 0.000000000000001325, -0.000000000000000522, 0.000000000000000210, -0.000000000000000087, 0.000000000000000036 }; const cheb_series _gsl_sf_bessel_amp_phase_bth0_cs = { bth0_data, 23, -1, 1, 12 }; static double bm1_data[21] = { 0.1047362510931285, 0.00442443893702345, -0.00005661639504035, 0.00000231349417339, -0.00000017377182007, 0.00000001893209930, -0.00000000265416023, 0.00000000044740209, -0.00000000008691795, 0.00000000001891492, -0.00000000000451884, 0.00000000000116765, -0.00000000000032265, 0.00000000000009450, -0.00000000000002913, 0.00000000000000939, -0.00000000000000315, 0.00000000000000109, -0.00000000000000039, 0.00000000000000014, -0.00000000000000005, }; const cheb_series _gsl_sf_bessel_amp_phase_bm1_cs = { bm1_data, 20, -1, 1, 10 }; static double bth1_data[24] = { 0.74060141026313850, -0.004571755659637690, 0.000119818510964326, -0.000006964561891648, 0.000000655495621447, -0.000000084066228945, 0.000000013376886564, -0.000000002499565654, 0.000000000529495100, -0.000000000124135944, 0.000000000031656485, -0.000000000008668640, 0.000000000002523758, -0.000000000000775085, 0.000000000000249527, -0.000000000000083773, 0.000000000000029205, -0.000000000000010534, 0.000000000000003919, -0.000000000000001500, 0.000000000000000589, -0.000000000000000237, 0.000000000000000097, -0.000000000000000040, }; const cheb_series _gsl_sf_bessel_amp_phase_bth1_cs = { bth1_data, 23, -1, 1, 12 }; int gsl_sf_bessel_asymp_Mnu_e(const double nu, const double x, double * result) { const double r = 2.0*nu/x; const double r2 = r*r; const double x2 = x*x; const double term1 = (r2-1.0/x2)/8.0; const double term2 = (r2-1.0/x2)*(r2-9.0/x2)*3.0/128.0; const double Mnu2_c = 2.0/(M_PI) * (1.0 + term1 + term2); *result = sqrt(Mnu2_c)/sqrt(x); /* will never underflow this way */ return GSL_SUCCESS; } int gsl_sf_bessel_asymp_thetanu_corr_e(const double nu, const double x, double * result) { const double r = 2.0*nu/x; const double r2 = r*r; const double x2 = x*x; const double term1 = x*(r2 - 1.0/x2)/8.0; const double term2 = x*(r2 - 1.0/x2)*(r2 - 25.0/x2)/384.0; *result = (-0.25*M_PI + term1 + term2); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cdf__geometric.c0000664000176700017670000000333011723710247020301 0ustar paulpaul/* cdf/geometric.c * * Copyright (C) 2004 Jason H. Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_cdf.h" #include "gsl_cdf__error.h" /* Pr (X <= k), i.e., the probability of n or fewer failures until the first success. */ double gsl_cdf_geometric_P (const unsigned int k, const double p) { double P, a, q; if (p > 1.0 || p < 0.0) { CDF_ERROR ("p < 0 or p > 1", GSL_EDOM); } if (k < 1) { return 0.0; } q = 1.0 - p; a = (double) k; if (p < 0.5) { P = -expm1 (a * log1p (-p)); } else { P = 1.0 - pow (q, a); } return P; } double gsl_cdf_geometric_Q (const unsigned int k, const double p) { double Q, a, q; if (p > 1.0 || p < 0.0) { CDF_ERROR ("p < 0 or p > 1", GSL_EDOM); } if (k < 1) { Q = 1.0; } q = 1.0 - p; a = (double) k; if (p < 0.5) { Q = exp (a * log1p (-p)); } else { Q = pow (q, a); } return Q; } sources_5316/external/gsl/gsl_permute_long_double.h0000664000176700017670000000270611705263724021420 0ustar paulpaul/* permutation/gsl_permute_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_LONG_DOUBLE_H__ #define __GSL_PERMUTE_LONG_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_long_double (const size_t * p, long double * data, const size_t stride, const size_t n); int gsl_permute_long_double_inverse (const size_t * p, long double * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_sys__prec.c0000664000176700017670000000364111723710247017343 0ustar paulpaul/* sys/prec.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_machine.h" #include "gsl_precision.h" const double gsl_prec_eps[_GSL_PREC_T_NUM] = { GSL_DBL_EPSILON, GSL_FLT_EPSILON, GSL_SFLT_EPSILON }; const double gsl_prec_sqrt_eps[_GSL_PREC_T_NUM] = { GSL_SQRT_DBL_EPSILON, GSL_SQRT_FLT_EPSILON, GSL_SQRT_SFLT_EPSILON }; const double gsl_prec_root3_eps[_GSL_PREC_T_NUM] = { GSL_ROOT3_DBL_EPSILON, GSL_ROOT3_FLT_EPSILON, GSL_ROOT3_SFLT_EPSILON }; const double gsl_prec_root4_eps[_GSL_PREC_T_NUM] = { GSL_ROOT4_DBL_EPSILON, GSL_ROOT4_FLT_EPSILON, GSL_ROOT4_SFLT_EPSILON }; const double gsl_prec_root5_eps[_GSL_PREC_T_NUM] = { GSL_ROOT5_DBL_EPSILON, GSL_ROOT5_FLT_EPSILON, GSL_ROOT5_SFLT_EPSILON }; const double gsl_prec_root6_eps[_GSL_PREC_T_NUM] = { GSL_ROOT6_DBL_EPSILON, GSL_ROOT6_FLT_EPSILON, GSL_ROOT6_SFLT_EPSILON }; typedef unsigned int gsl_mode_t; #ifndef HIDE_INLINE_STATIC /* We need this somewhere, in case the inline is ignored. */ unsigned int GSL_MODE_PREC(gsl_mode_t mt); unsigned int GSL_MODE_PREC(gsl_mode_t mt) { return (mt & (unsigned int)7); } #endif sources_5316/external/gsl/gsl_permutation__permutation.c0000664000176700017670000001270511723710247022513 0ustar paulpaul/* permutation/permutation.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_permutation.h" size_t gsl_permutation_size (const gsl_permutation * p) { return p->size ; } size_t * gsl_permutation_data (const gsl_permutation * p) { return p->data ; } #ifndef HIDE_INLINE_STATIC size_t gsl_permutation_get (const gsl_permutation * p, const size_t i) { if (gsl_check_range) { if (i >= p->size) /* size_t is unsigned, can't be negative */ { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } } return p->data[i]; } #endif int gsl_permutation_swap (gsl_permutation * p, const size_t i, const size_t j) { const size_t size = p->size ; if (i >= size) { GSL_ERROR("first index is out of range", GSL_EINVAL); } if (j >= size) { GSL_ERROR("second index is out of range", GSL_EINVAL); } if (i != j) { size_t tmp = p->data[i]; p->data[i] = p->data[j]; p->data[j] = tmp; } return GSL_SUCCESS; } int gsl_permutation_valid (gsl_permutation * p) { const size_t size = p->size ; size_t i, j ; for (i = 0; i < size; i++) { if (p->data[i] >= size) { GSL_ERROR("permutation index outside range", GSL_FAILURE) ; } for (j = 0; j < i; j++) { if (p->data[i] == p->data[j]) { GSL_ERROR("duplicate permutation index", GSL_FAILURE) ; } } } return GSL_SUCCESS; } void gsl_permutation_reverse (gsl_permutation * p) { const size_t size = p->size ; size_t i ; for (i = 0; i < (size / 2); i++) { size_t j = size - i - 1; size_t tmp = p->data[i] ; p->data[i] = p->data[j] ; p->data[j] = tmp ; } } int gsl_permutation_inverse (gsl_permutation * inv, const gsl_permutation * p) { const size_t size = p->size ; size_t i ; if (inv->size != size) { GSL_ERROR("permutation lengths are not equal", GSL_EBADLEN); } for (i = 0; i < size; i++) { inv->data[p->data[i]] = i ; } return GSL_SUCCESS ; } int gsl_permutation_next (gsl_permutation * p) { /* Replaces p with the next permutation (in the standard lexicographical * ordering). Returns GSL_FAILURE if there is no next permutation. */ const size_t size = p->size; size_t i, j, k; if (size < 2) { return GSL_FAILURE; } i = size - 2; while ((p->data[i] > p->data[i+1]) && (i != 0)) { i--; } if ((i == 0) && (p->data[0] > p->data[1])) { return GSL_FAILURE; } k = i + 1; for (j = i + 2; j < size; j++ ) { if ((p->data[j] > p->data[i]) && (p->data[j] < p->data[k])) { k = j; } } /* swap i and k */ { size_t tmp = p->data[i]; p->data[i] = p->data[k]; p->data[k] = tmp; } for (j = i + 1; j <= ((size + i) / 2); j++) { size_t tmp = p->data[j]; p->data[j] = p->data[size + i - j]; p->data[size + i - j] = tmp; } return GSL_SUCCESS; } int gsl_permutation_prev (gsl_permutation * p) { const size_t size = p->size; size_t i, j, k; if (size < 2) { return GSL_FAILURE; } i = size - 2; while ((p->data[i] < p->data[i+1]) && (i != 0)) { i--; } if ((i == 0) && (p->data[0] < p->data[1])) { return GSL_FAILURE; } k = i + 1; for (j = i + 2; j < size; j++ ) { if ((p->data[j] < p->data[i]) && (p->data[j] > p->data[k])) { k = j; } } /* swap i and k */ { size_t tmp = p->data[i]; p->data[i] = p->data[k]; p->data[k] = tmp; } for (j = i + 1; j <= ((size + i) / 2); j++) { size_t tmp = p->data[j]; p->data[j] = p->data[size + i - j]; p->data[size + i - j] = tmp; } return GSL_SUCCESS; } int gsl_permutation_mul (gsl_permutation * p, const gsl_permutation * pa, const gsl_permutation * pb) { size_t i; const size_t size = p->size; if (pa->size != size) { GSL_ERROR("size of result does not match size of pa", GSL_EINVAL); } if (pb->size != size) { GSL_ERROR("size of result does not match size of pb", GSL_EINVAL); } for (i = 0; i < size; i++) { p->data[i] = pb->data[pa->data[i]]; } return GSL_SUCCESS; } int gsl_permutation_memcpy (gsl_permutation * dest, const gsl_permutation * src) { const size_t src_size = src->size; const size_t dest_size = dest->size; if (src_size != dest_size) { GSL_ERROR ("permutation lengths are not equal", GSL_EBADLEN); } { size_t j; for (j = 0; j < src_size; j++) { dest->data[j] = src->data[j]; } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_sf_expint.h0000664000176700017670000001045111705263724017361 0ustar paulpaul/* specfunc/gsl_sf_expint.h * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_EXPINT_H__ #define __GSL_SF_EXPINT_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* E_1(x) := Re[ Integrate[ Exp[-xt]/t, {t,1,Infinity}] ] * * x != 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_expint_E1_e(const double x, gsl_sf_result * result); double gsl_sf_expint_E1(const double x); /* E_2(x) := Re[ Integrate[ Exp[-xt]/t^2, {t,1,Infinity}] ] * * x != 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_expint_E2_e(const double x, gsl_sf_result * result); double gsl_sf_expint_E2(const double x); /* E_n(x) := Re[ Integrate[ Exp[-xt]/t^n, {t,1,Infinity}] ] * * x != 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_expint_En_e(const int n, const double x, gsl_sf_result * result); double gsl_sf_expint_En(const int n, const double x); /* E_1_scaled(x) := exp(x) E_1(x) * * x != 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_expint_E1_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_expint_E1_scaled(const double x); /* E_2_scaled(x) := exp(x) E_2(x) * * x != 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_expint_E2_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_expint_E2_scaled(const double x); /* E_n_scaled(x) := exp(x) E_n(x) * * x != 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_expint_En_scaled_e(const int n, const double x, gsl_sf_result * result); double gsl_sf_expint_En_scaled(const int n, const double x); /* Ei(x) := - PV Integrate[ Exp[-t]/t, {t,-x,Infinity}] * := PV Integrate[ Exp[t]/t, {t,-Infinity,x}] * * x != 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_expint_Ei_e(const double x, gsl_sf_result * result); double gsl_sf_expint_Ei(const double x); /* Ei_scaled(x) := exp(-x) Ei(x) * * x != 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_expint_Ei_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_expint_Ei_scaled(const double x); /* Shi(x) := Integrate[ Sinh[t]/t, {t,0,x}] * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_Shi_e(const double x, gsl_sf_result * result); double gsl_sf_Shi(const double x); /* Chi(x) := Re[ M_EULER + log(x) + Integrate[(Cosh[t]-1)/t, {t,0,x}] ] * * x != 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_Chi_e(const double x, gsl_sf_result * result); double gsl_sf_Chi(const double x); /* Ei_3(x) := Integral[ Exp[-t^3], {t,0,x}] * * x >= 0.0 * exceptions: GSL_EDOM */ int gsl_sf_expint_3_e(const double x, gsl_sf_result * result); double gsl_sf_expint_3(double x); /* Si(x) := Integrate[ Sin[t]/t, {t,0,x}] * * exceptions: none */ int gsl_sf_Si_e(const double x, gsl_sf_result * result); double gsl_sf_Si(const double x); /* Ci(x) := -Integrate[ Cos[t]/t, {t,x,Infinity}] * * x > 0.0 * exceptions: GSL_EDOM */ int gsl_sf_Ci_e(const double x, gsl_sf_result * result); double gsl_sf_Ci(const double x); /* AtanInt(x) := Integral[ Arctan[t]/t, {t,0,x}] * * * exceptions: */ int gsl_sf_atanint_e(const double x, gsl_sf_result * result); double gsl_sf_atanint(const double x); __END_DECLS #endif /* __GSL_SF_EXPINT_H__ */ sources_5316/external/gsl/gsl_block__block.c0000664000176700017670000000362511723710247017762 0ustar paulpaul#include "gsl__config.h" #include "gsl_errno.h" #include "gsl_block.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_block__block_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_eigen__jacobi.c0000664000176700017670000001363111723710247020112 0ustar paulpaul/* eigen/jacobi.c * * Copyright (C) 2004, 2007 Brian Gough, Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_eigen.h" /* Algorithm 8.4.3 - Cyclic Jacobi. Golub & Van Loan, Matrix Computations */ static inline double symschur2 (gsl_matrix * A, size_t p, size_t q, double *c, double *s) { double Apq = gsl_matrix_get (A, p, q); if (Apq != 0.0) { double App = gsl_matrix_get (A, p, p); double Aqq = gsl_matrix_get (A, q, q); double tau = (Aqq - App) / (2.0 * Apq); double t, c1; if (tau >= 0.0) { t = 1.0 / (tau + hypot (1.0, tau)); } else { t = -1.0 / (-tau + hypot (1.0, tau)); } c1 = 1.0 / hypot (1.0, t); *c = c1; *s = t * c1; } else { *c = 1.0; *s = 0.0; } /* reduction in off(A) is 2*(A_pq)^2 */ return fabs (Apq); } inline static void apply_jacobi_L (gsl_matrix * A, size_t p, size_t q, double c, double s) { size_t j; const size_t N = A->size2; /* Apply rotation to matrix A, A' = J^T A */ for (j = 0; j < N; j++) { double Apj = gsl_matrix_get (A, p, j); double Aqj = gsl_matrix_get (A, q, j); gsl_matrix_set (A, p, j, Apj * c - Aqj * s); gsl_matrix_set (A, q, j, Apj * s + Aqj * c); } } inline static void apply_jacobi_R (gsl_matrix * A, size_t p, size_t q, double c, double s) { size_t i; const size_t M = A->size1; /* Apply rotation to matrix A, A' = A J */ for (i = 0; i < M; i++) { double Aip = gsl_matrix_get (A, i, p); double Aiq = gsl_matrix_get (A, i, q); gsl_matrix_set (A, i, p, Aip * c - Aiq * s); gsl_matrix_set (A, i, q, Aip * s + Aiq * c); } } inline static double norm (gsl_matrix * A) { size_t i, j, M = A->size1, N = A->size2; double sum = 0.0, scale = 0.0, ssq = 1.0; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { double Aij = gsl_matrix_get (A, i, j); if (Aij != 0.0) { double ax = fabs (Aij); if (scale < ax) { ssq = 1.0 + ssq * (scale / ax) * (scale / ax); scale = ax; } else { ssq += (ax / scale) * (ax / scale); } } } } sum = scale * sqrt (ssq); return sum; } int gsl_eigen_jacobi (gsl_matrix * a, gsl_vector * eval, gsl_matrix * evec, unsigned int max_rot, unsigned int *nrot) { size_t i, p, q; const size_t M = a->size1, N = a->size2; double red, redsum = 0.0; if (M != N) { GSL_ERROR ("eigenproblem requires square matrix", GSL_ENOTSQR); } else if (M != evec->size1 || M != evec->size2) { GSL_ERROR ("eigenvector matrix must match input matrix", GSL_EBADLEN); } else if (M != eval->size) { GSL_ERROR ("eigenvalue vector must match input matrix", GSL_EBADLEN); } gsl_vector_set_zero (eval); gsl_matrix_set_identity (evec); for (i = 0; i < max_rot; i++) { double nrm = norm (a); if (nrm == 0.0) break; for (p = 0; p < N; p++) { for (q = p + 1; q < N; q++) { double c, s; red = symschur2 (a, p, q, &c, &s); redsum += red; /* Compute A <- J^T A J */ apply_jacobi_L (a, p, q, c, s); apply_jacobi_R (a, p, q, c, s); /* Compute V <- V J */ apply_jacobi_R (evec, p, q, c, s); } } } *nrot = i; for (p = 0; p < N; p++) { double ep = gsl_matrix_get (a, p, p); gsl_vector_set (eval, p, ep); } if (i == max_rot) { return GSL_EMAXITER; } return GSL_SUCCESS; } int gsl_eigen_invert_jacobi (const gsl_matrix * a, gsl_matrix * ainv, unsigned int max_rot) { if (a->size1 != a->size2 || ainv->size1 != ainv->size2) { GSL_ERROR("jacobi method requires square matrix", GSL_ENOTSQR); } else if (a->size1 != ainv->size2) { GSL_ERROR ("inverse matrix must match input matrix", GSL_EBADLEN); } { const size_t n = a->size2; size_t i,j,k; unsigned int nrot = 0; int status; gsl_vector * eval = gsl_vector_alloc(n); gsl_matrix * evec = gsl_matrix_alloc(n, n); gsl_matrix * tmp = gsl_matrix_alloc(n, n); gsl_matrix_memcpy (tmp, a); status = gsl_eigen_jacobi(tmp, eval, evec, max_rot, &nrot); for(i=0; ival = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if((ax <= 1.0 && ay >= 1.0) || (ay <= 1.0 && ax >= 1.0)) { /* Straddling 1.0 is always safe. */ result->val = x*y; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double f = 1.0 - 2.0 * GSL_DBL_EPSILON; const double min = GSL_MIN_DBL(fabs(x), fabs(y)); const double max = GSL_MAX_DBL(fabs(x), fabs(y)); if(max < 0.9 * GSL_SQRT_DBL_MAX || min < (f * DBL_MAX)/max) { result->val = GSL_COERCE_DBL(x*y); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } } int gsl_sf_multiply_err_e(const double x, const double dx, const double y, const double dy, gsl_sf_result * result) { int status = gsl_sf_multiply_e(x, y, result); result->err += fabs(dx*y) + fabs(dy*x); return status; } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_multiply(const double x, const double y) { EVAL_RESULT(gsl_sf_multiply_e(x, y, &result)); } sources_5316/external/gsl/gsl_multifit__lmder.c0000664000176700017670000002267711723710247020546 0ustar paulpaul/* multfit/lmder.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multifit_nlin.h" #include "gsl_blas.h" #include "gsl_linalg.h" #include "gsl_permutation.h" typedef struct { size_t iter; double xnorm; double fnorm; double delta; double par; gsl_matrix *r; gsl_vector *tau; gsl_vector *diag; gsl_vector *qtf; gsl_vector *newton; gsl_vector *gradient; gsl_vector *x_trial; gsl_vector *f_trial; gsl_vector *df; gsl_vector *sdiag; gsl_vector *rptdx; gsl_vector *w; gsl_vector *work1; gsl_permutation * perm; } lmder_state_t; static int lmder_alloc (void *vstate, size_t n, size_t p); static int lmder_set (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static int lmsder_set (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static int set (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx, int scale); static int lmder_iterate (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static void lmder_free (void *vstate); static int iterate (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx, int scale); #include "gsl_multifit__lmutil.c" #include "gsl_multifit__lmpar.c" #include "gsl_multifit__lmset.c" #include "gsl_multifit__lmiterate.c" static int lmder_alloc (void *vstate, size_t n, size_t p) { lmder_state_t *state = (lmder_state_t *) vstate; gsl_matrix *r; gsl_vector *tau, *diag, *qtf, *newton, *gradient, *x_trial, *f_trial, *df, *sdiag, *rptdx, *w, *work1; gsl_permutation *perm; r = gsl_matrix_calloc (n, p); if (r == 0) { GSL_ERROR ("failed to allocate space for r", GSL_ENOMEM); } state->r = r; tau = gsl_vector_calloc (GSL_MIN(n, p)); if (tau == 0) { gsl_matrix_free (r); GSL_ERROR ("failed to allocate space for tau", GSL_ENOMEM); } state->tau = tau; diag = gsl_vector_calloc (p); if (diag == 0) { gsl_matrix_free (r); gsl_vector_free (tau); GSL_ERROR ("failed to allocate space for diag", GSL_ENOMEM); } state->diag = diag; qtf = gsl_vector_calloc (n); if (qtf == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); GSL_ERROR ("failed to allocate space for qtf", GSL_ENOMEM); } state->qtf = qtf; newton = gsl_vector_calloc (p); if (newton == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); GSL_ERROR ("failed to allocate space for newton", GSL_ENOMEM); } state->newton = newton; gradient = gsl_vector_calloc (p); if (gradient == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); GSL_ERROR ("failed to allocate space for gradient", GSL_ENOMEM); } state->gradient = gradient; x_trial = gsl_vector_calloc (p); if (x_trial == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); GSL_ERROR ("failed to allocate space for x_trial", GSL_ENOMEM); } state->x_trial = x_trial; f_trial = gsl_vector_calloc (n); if (f_trial == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); GSL_ERROR ("failed to allocate space for f_trial", GSL_ENOMEM); } state->f_trial = f_trial; df = gsl_vector_calloc (n); if (df == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); GSL_ERROR ("failed to allocate space for df", GSL_ENOMEM); } state->df = df; sdiag = gsl_vector_calloc (p); if (sdiag == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); GSL_ERROR ("failed to allocate space for sdiag", GSL_ENOMEM); } state->sdiag = sdiag; rptdx = gsl_vector_calloc (n); if (rptdx == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (sdiag); GSL_ERROR ("failed to allocate space for rptdx", GSL_ENOMEM); } state->rptdx = rptdx; w = gsl_vector_calloc (n); if (w == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (sdiag); gsl_vector_free (rptdx); GSL_ERROR ("failed to allocate space for w", GSL_ENOMEM); } state->w = w; work1 = gsl_vector_calloc (p); if (work1 == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (sdiag); gsl_vector_free (rptdx); gsl_vector_free (w); GSL_ERROR ("failed to allocate space for work1", GSL_ENOMEM); } state->work1 = work1; perm = gsl_permutation_calloc (p); if (perm == 0) { gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (sdiag); gsl_vector_free (rptdx); gsl_vector_free (w); gsl_vector_free (work1); GSL_ERROR ("failed to allocate space for perm", GSL_ENOMEM); } state->perm = perm; return GSL_SUCCESS; } static int lmder_set (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { int status = set (vstate, fdf, x, f, J, dx, 0); return status ; } static int lmsder_set (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { int status = set (vstate, fdf, x, f, J, dx, 1); return status ; } static int lmder_iterate (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { int status = iterate (vstate, fdf, x, f, J, dx, 0); return status; } static int lmsder_iterate (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { int status = iterate (vstate, fdf, x, f, J, dx, 1); return status; } static void lmder_free (void *vstate) { lmder_state_t *state = (lmder_state_t *) vstate; gsl_permutation_free (state->perm); gsl_vector_free (state->work1); gsl_vector_free (state->w); gsl_vector_free (state->rptdx); gsl_vector_free (state->sdiag); gsl_vector_free (state->df); gsl_vector_free (state->f_trial); gsl_vector_free (state->x_trial); gsl_vector_free (state->gradient); gsl_vector_free (state->newton); gsl_vector_free (state->qtf); gsl_vector_free (state->diag); gsl_vector_free (state->tau); gsl_matrix_free (state->r); } static const gsl_multifit_fdfsolver_type lmder_type = { "lmder", /* name */ sizeof (lmder_state_t), &lmder_alloc, &lmder_set, &lmder_iterate, &lmder_free }; static const gsl_multifit_fdfsolver_type lmsder_type = { "lmsder", /* name */ sizeof (lmder_state_t), &lmder_alloc, &lmsder_set, &lmsder_iterate, &lmder_free }; const gsl_multifit_fdfsolver_type *gsl_multifit_fdfsolver_lmder = &lmder_type; const gsl_multifit_fdfsolver_type *gsl_multifit_fdfsolver_lmsder = &lmsder_type; sources_5316/external/gsl/gsl_poly__solve_cubic.c0000664000176700017670000000567511723710247021065 0ustar paulpaul/* poly/solve_cubic.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* solve_cubic.c - finds the real roots of x^3 + a x^2 + b x + c = 0 */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_poly.h" #define SWAP(a,b) do { double tmp = b ; b = a ; a = tmp ; } while(0) int gsl_poly_solve_cubic (double a, double b, double c, double *x0, double *x1, double *x2) { double q = (a * a - 3 * b); double r = (2 * a * a * a - 9 * a * b + 27 * c); double Q = q / 9; double R = r / 54; double Q3 = Q * Q * Q; double R2 = R * R; double CR2 = 729 * r * r; double CQ3 = 2916 * q * q * q; if (R == 0 && Q == 0) { *x0 = - a / 3 ; *x1 = - a / 3 ; *x2 = - a / 3 ; return 3 ; } else if (CR2 == CQ3) { /* this test is actually R2 == Q3, written in a form suitable for exact computation with integers */ /* Due to finite precision some double roots may be missed, and considered to be a pair of complex roots z = x +/- epsilon i close to the real axis. */ double sqrtQ = sqrt (Q); if (R > 0) { *x0 = -2 * sqrtQ - a / 3; *x1 = sqrtQ - a / 3; *x2 = sqrtQ - a / 3; } else { *x0 = - sqrtQ - a / 3; *x1 = - sqrtQ - a / 3; *x2 = 2 * sqrtQ - a / 3; } return 3 ; } else if (CR2 < CQ3) /* equivalent to R2 < Q3 */ { double sqrtQ = sqrt (Q); double sqrtQ3 = sqrtQ * sqrtQ * sqrtQ; double theta = acos (R / sqrtQ3); double norm = -2 * sqrtQ; *x0 = norm * cos (theta / 3) - a / 3; *x1 = norm * cos ((theta + 2.0 * M_PI) / 3) - a / 3; *x2 = norm * cos ((theta - 2.0 * M_PI) / 3) - a / 3; /* Sort *x0, *x1, *x2 into increasing order */ if (*x0 > *x1) SWAP(*x0, *x1) ; if (*x1 > *x2) { SWAP(*x1, *x2) ; if (*x0 > *x1) SWAP(*x0, *x1) ; } return 3; } else { double sgnR = (R >= 0 ? 1 : -1); double A = -sgnR * pow (fabs (R) + sqrt (R2 - Q3), 1.0/3.0); double B = Q / A ; *x0 = A + B - a / 3; return 1; } } sources_5316/external/gsl/gsl_cdf__logisticinv.c0000664000176700017670000000247211723710247020663 0ustar paulpaul/* cdf/logisticinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_logistic_Pinv (const double P, const double a) { double x; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return GSL_NEGINF; } x = a * log(P/(1-P)); return x; } double gsl_cdf_logistic_Qinv (const double Q, const double a) { double x; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return GSL_NEGINF; } x = a * log((1-Q)/Q); return x; } sources_5316/external/gsl/gsl_cblas__zhemm.c0000664000176700017670000000066611723710247020004 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zhemm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc) { #define BASE double #include "gsl_cblas__source_hemm.h" #undef BASE } sources_5316/external/gsl/gsl_roots.h0000664000176700017670000000721011705263724016527 0ustar paulpaul/* roots/gsl_roots.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_ROOTS_H__ #define __GSL_ROOTS_H__ #include #include "gsl_types.h" #include "gsl_math.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { const char *name; size_t size; int (*set) (void *state, gsl_function * f, double * root, double x_lower, double x_upper); int (*iterate) (void *state, gsl_function * f, double * root, double * x_lower, double * x_upper); } gsl_root_fsolver_type; typedef struct { const gsl_root_fsolver_type * type; gsl_function * function ; double root ; double x_lower; double x_upper; void *state; } gsl_root_fsolver; typedef struct { const char *name; size_t size; int (*set) (void *state, gsl_function_fdf * f, double * root); int (*iterate) (void *state, gsl_function_fdf * f, double * root); } gsl_root_fdfsolver_type; typedef struct { const gsl_root_fdfsolver_type * type; gsl_function_fdf * fdf ; double root ; void *state; } gsl_root_fdfsolver; gsl_root_fsolver * gsl_root_fsolver_alloc (const gsl_root_fsolver_type * T); void gsl_root_fsolver_free (gsl_root_fsolver * s); int gsl_root_fsolver_set (gsl_root_fsolver * s, gsl_function * f, double x_lower, double x_upper); int gsl_root_fsolver_iterate (gsl_root_fsolver * s); const char * gsl_root_fsolver_name (const gsl_root_fsolver * s); double gsl_root_fsolver_root (const gsl_root_fsolver * s); double gsl_root_fsolver_x_lower (const gsl_root_fsolver * s); double gsl_root_fsolver_x_upper (const gsl_root_fsolver * s); gsl_root_fdfsolver * gsl_root_fdfsolver_alloc (const gsl_root_fdfsolver_type * T); int gsl_root_fdfsolver_set (gsl_root_fdfsolver * s, gsl_function_fdf * fdf, double root); int gsl_root_fdfsolver_iterate (gsl_root_fdfsolver * s); void gsl_root_fdfsolver_free (gsl_root_fdfsolver * s); const char * gsl_root_fdfsolver_name (const gsl_root_fdfsolver * s); double gsl_root_fdfsolver_root (const gsl_root_fdfsolver * s); int gsl_root_test_interval (double x_lower, double x_upper, double epsabs, double epsrel); int gsl_root_test_residual (double f, double epsabs); int gsl_root_test_delta (double x1, double x0, double epsabs, double epsrel); GSL_VAR const gsl_root_fsolver_type * gsl_root_fsolver_bisection; GSL_VAR const gsl_root_fsolver_type * gsl_root_fsolver_brent; GSL_VAR const gsl_root_fsolver_type * gsl_root_fsolver_falsepos; GSL_VAR const gsl_root_fdfsolver_type * gsl_root_fdfsolver_newton; GSL_VAR const gsl_root_fdfsolver_type * gsl_root_fdfsolver_secant; GSL_VAR const gsl_root_fdfsolver_type * gsl_root_fdfsolver_steffenson; __END_DECLS #endif /* __GSL_ROOTS_H__ */ sources_5316/external/gsl/gsl_sf__gamma.c0000644000176700017670000016654610707442037017302 0ustar paulpaul/* specfunc/gamma.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_log.h" #include "gsl_sf_psi.h" #include "gsl_sf_trig.h" #include "gsl_sf_gamma.h" #include "gsl_sf__error.h" #include "gsl_sf__check.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" #define LogRootTwoPi_ 0.9189385332046727418 /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ static struct {int n; double f; long i; } fact_table[GSL_SF_FACT_NMAX + 1] = { { 0, 1.0, 1L }, { 1, 1.0, 1L }, { 2, 2.0, 2L }, { 3, 6.0, 6L }, { 4, 24.0, 24L }, { 5, 120.0, 120L }, { 6, 720.0, 720L }, { 7, 5040.0, 5040L }, { 8, 40320.0, 40320L }, { 9, 362880.0, 362880L }, { 10, 3628800.0, 3628800L }, { 11, 39916800.0, 39916800L }, { 12, 479001600.0, 479001600L }, { 13, 6227020800.0, 0 }, { 14, 87178291200.0, 0 }, { 15, 1307674368000.0, 0 }, { 16, 20922789888000.0, 0 }, { 17, 355687428096000.0, 0 }, { 18, 6402373705728000.0, 0 }, { 19, 121645100408832000.0, 0 }, { 20, 2432902008176640000.0, 0 }, { 21, 51090942171709440000.0, 0 }, { 22, 1124000727777607680000.0, 0 }, { 23, 25852016738884976640000.0, 0 }, { 24, 620448401733239439360000.0, 0 }, { 25, 15511210043330985984000000.0, 0 }, { 26, 403291461126605635584000000.0, 0 }, { 27, 10888869450418352160768000000.0, 0 }, { 28, 304888344611713860501504000000.0, 0 }, { 29, 8841761993739701954543616000000.0, 0 }, { 30, 265252859812191058636308480000000.0, 0 }, { 31, 8222838654177922817725562880000000.0, 0 }, { 32, 263130836933693530167218012160000000.0, 0 }, { 33, 8683317618811886495518194401280000000.0, 0 }, { 34, 2.95232799039604140847618609644e38, 0 }, { 35, 1.03331479663861449296666513375e40, 0 }, { 36, 3.71993326789901217467999448151e41, 0 }, { 37, 1.37637530912263450463159795816e43, 0 }, { 38, 5.23022617466601111760007224100e44, 0 }, { 39, 2.03978820811974433586402817399e46, 0 }, { 40, 8.15915283247897734345611269600e47, 0 }, { 41, 3.34525266131638071081700620534e49, 0 }, { 42, 1.40500611775287989854314260624e51, 0 }, { 43, 6.04152630633738356373551320685e52, 0 }, { 44, 2.65827157478844876804362581101e54, 0 }, { 45, 1.19622220865480194561963161496e56, 0 }, { 46, 5.50262215981208894985030542880e57, 0 }, { 47, 2.58623241511168180642964355154e59, 0 }, { 48, 1.24139155925360726708622890474e61, 0 }, { 49, 6.08281864034267560872252163321e62, 0 }, { 50, 3.04140932017133780436126081661e64, 0 }, { 51, 1.55111875328738228022424301647e66, 0 }, { 52, 8.06581751709438785716606368564e67, 0 }, { 53, 4.27488328406002556429801375339e69, 0 }, { 54, 2.30843697339241380472092742683e71, 0 }, { 55, 1.26964033536582759259651008476e73, 0 }, { 56, 7.10998587804863451854045647464e74, 0 }, { 57, 4.05269195048772167556806019054e76, 0 }, { 58, 2.35056133128287857182947491052e78, 0 }, { 59, 1.38683118545689835737939019720e80, 0 }, { 60, 8.32098711274139014427634118320e81, 0 }, { 61, 5.07580213877224798800856812177e83, 0 }, { 62, 3.14699732603879375256531223550e85, 0 }, { 63, 1.982608315404440064116146708360e87, 0 }, { 64, 1.268869321858841641034333893350e89, 0 }, { 65, 8.247650592082470666723170306800e90, 0 }, { 66, 5.443449390774430640037292402480e92, 0 }, { 67, 3.647111091818868528824985909660e94, 0 }, { 68, 2.480035542436830599600990418570e96, 0 }, { 69, 1.711224524281413113724683388810e98, 0 }, { 70, 1.197857166996989179607278372170e100, 0 }, { 71, 8.504785885678623175211676442400e101, 0 }, { 72, 6.123445837688608686152407038530e103, 0 }, { 73, 4.470115461512684340891257138130e105, 0 }, { 74, 3.307885441519386412259530282210e107, 0 }, { 75, 2.480914081139539809194647711660e109, 0 }, { 76, 1.885494701666050254987932260860e111, 0 }, { 77, 1.451830920282858696340707840860e113, 0 }, { 78, 1.132428117820629783145752115870e115, 0 }, { 79, 8.946182130782975286851441715400e116, 0 }, { 80, 7.156945704626380229481153372320e118, 0 }, { 81, 5.797126020747367985879734231580e120, 0 }, { 82, 4.753643337012841748421382069890e122, 0 }, { 83, 3.945523969720658651189747118010e124, 0 }, { 84, 3.314240134565353266999387579130e126, 0 }, { 85, 2.817104114380550276949479442260e128, 0 }, { 86, 2.422709538367273238176552320340e130, 0 }, { 87, 2.107757298379527717213600518700e132, 0 }, { 88, 1.854826422573984391147968456460e134, 0 }, { 89, 1.650795516090846108121691926250e136, 0 }, { 90, 1.485715964481761497309522733620e138, 0 }, { 91, 1.352001527678402962551665687590e140, 0 }, { 92, 1.243841405464130725547532432590e142, 0 }, { 93, 1.156772507081641574759205162310e144, 0 }, { 94, 1.087366156656743080273652852570e146, 0 }, { 95, 1.032997848823905926259970209940e148, 0 }, { 96, 9.916779348709496892095714015400e149, 0 }, { 97, 9.619275968248211985332842594960e151, 0 }, { 98, 9.426890448883247745626185743100e153, 0 }, { 99, 9.332621544394415268169923885600e155, 0 }, { 100, 9.33262154439441526816992388563e157, 0 }, { 101, 9.42594775983835942085162312450e159, 0 }, { 102, 9.61446671503512660926865558700e161, 0 }, { 103, 9.90290071648618040754671525458e163, 0 }, { 104, 1.02990167451456276238485838648e166, 0 }, { 105, 1.08139675824029090050410130580e168, 0 }, { 106, 1.146280563734708354534347384148e170, 0 }, { 107, 1.226520203196137939351751701040e172, 0 }, { 108, 1.324641819451828974499891837120e174, 0 }, { 109, 1.443859583202493582204882102460e176, 0 }, { 110, 1.588245541522742940425370312710e178, 0 }, { 111, 1.762952551090244663872161047110e180, 0 }, { 112, 1.974506857221074023536820372760e182, 0 }, { 113, 2.231192748659813646596607021220e184, 0 }, { 114, 2.543559733472187557120132004190e186, 0 }, { 115, 2.925093693493015690688151804820e188, 0 }, { 116, 3.393108684451898201198256093590e190, 0 }, { 117, 3.96993716080872089540195962950e192, 0 }, { 118, 4.68452584975429065657431236281e194, 0 }, { 119, 5.57458576120760588132343171174e196, 0 }, { 120, 6.68950291344912705758811805409e198, 0 }, { 121, 8.09429852527344373968162284545e200, 0 }, { 122, 9.87504420083360136241157987140e202, 0 }, { 123, 1.21463043670253296757662432419e205, 0 }, { 124, 1.50614174151114087979501416199e207, 0 }, { 125, 1.88267717688892609974376770249e209, 0 }, { 126, 2.37217324288004688567714730514e211, 0 }, { 127, 3.01266001845765954480997707753e213, 0 }, { 128, 3.85620482362580421735677065923e215, 0 }, { 129, 4.97450422247728744039023415041e217, 0 }, { 130, 6.46685548922047367250730439554e219, 0 }, { 131, 8.47158069087882051098456875820e221, 0 }, { 132, 1.11824865119600430744996307608e224, 0 }, { 133, 1.48727070609068572890845089118e226, 0 }, { 134, 1.99294274616151887673732419418e228, 0 }, { 135, 2.69047270731805048359538766215e230, 0 }, { 136, 3.65904288195254865768972722052e232, 0 }, { 137, 5.01288874827499166103492629211e234, 0 }, { 138, 6.91778647261948849222819828311e236, 0 }, { 139, 9.61572319694108900419719561353e238, 0 }, { 140, 1.34620124757175246058760738589e241, 0 }, { 141, 1.89814375907617096942852641411e243, 0 }, { 142, 2.69536413788816277658850750804e245, 0 }, { 143, 3.85437071718007277052156573649e247, 0 }, { 144, 5.55029383273930478955105466055e249, 0 }, { 145, 8.04792605747199194484902925780e251, 0 }, { 146, 1.17499720439091082394795827164e254, 0 }, { 147, 1.72724589045463891120349865931e256, 0 }, { 148, 2.55632391787286558858117801578e258, 0 }, { 149, 3.80892263763056972698595524351e260, 0 }, { 150, 5.71338395644585459047893286526e262, 0 }, { 151, 8.62720977423324043162318862650e264, 0 }, { 152, 1.31133588568345254560672467123e267, 0 }, { 153, 2.00634390509568239477828874699e269, 0 }, { 154, 3.08976961384735088795856467036e271, 0 }, { 155, 4.78914290146339387633577523906e273, 0 }, { 156, 7.47106292628289444708380937294e275, 0 }, { 157, 1.17295687942641442819215807155e278, 0 }, { 158, 1.85327186949373479654360975305e280, 0 }, { 159, 2.94670227249503832650433950735e282, 0 }, { 160, 4.71472363599206132240694321176e284, 0 }, { 161, 7.59070505394721872907517857094e286, 0 }, { 162, 1.22969421873944943411017892849e289, 0 }, { 163, 2.00440157654530257759959165344e291, 0 }, { 164, 3.28721858553429622726333031164e293, 0 }, { 165, 5.42391066613158877498449501421e295, 0 }, { 166, 9.00369170577843736647426172359e297, 0 }, { 167, 1.50361651486499904020120170784e300, 0 }, { 168, 2.52607574497319838753801886917e302, 0 }, { 169, 4.26906800900470527493925188890e304, 0 }, { 170, 7.25741561530799896739672821113e306, 0 }, /* { 171, 1.24101807021766782342484052410e309, 0 }, { 172, 2.13455108077438865629072570146e311, 0 }, { 173, 3.69277336973969237538295546352e313, 0 }, { 174, 6.42542566334706473316634250653e315, 0 }, { 175, 1.12444949108573632830410993864e318, 0 }, { 176, 1.97903110431089593781523349201e320, 0 }, { 177, 3.50288505463028580993296328086e322, 0 }, { 178, 6.23513539724190874168067463993e324, 0 }, { 179, 1.11608923610630166476084076055e327, 0 }, { 180, 2.00896062499134299656951336898e329, 0 }, { 181, 3.63621873123433082379081919786e331, 0 }, { 182, 6.61791809084648209929929094011e333, 0 }, { 183, 1.21107901062490622417177024204e336, 0 }, { 184, 2.22838537954982745247605724535e338, 0 }, { 185, 4.12251295216718078708070590390e340, 0 }, { 186, 7.66787409103095626397011298130e342, 0 }, { 187, 1.43389245502278882136241112750e345, 0 }, { 188, 2.69571781544284298416133291969e347, 0 }, { 189, 5.09490667118697324006491921822e349, 0 }, { 190, 9.68032267525524915612334651460e351, 0 }, { 191, 1.84894163097375258881955918429e354, 0 }, { 192, 3.54996793146960497053355363384e356, 0 }, { 193, 6.85143810773633759312975851330e358, 0 }, { 194, 1.32917899290084949306717315158e361, 0 }, { 195, 2.59189903615665651148098764559e363, 0 }, { 196, 5.08012211086704676250273578535e365, 0 }, { 197, 1.00078405584080821221303894971e368, 0 }, { 198, 1.98155243056480026018181712043e370, 0 }, { 199, 3.94328933682395251776181606966e372, 0 }, { 200, 7.88657867364790503552363213932e374, 0 } */ }; static struct {int n; double f; long i; } doub_fact_table[GSL_SF_DOUBLEFACT_NMAX + 1] = { { 0, 1.000000000000000000000000000, 1L }, { 1, 1.000000000000000000000000000, 1L }, { 2, 2.000000000000000000000000000, 2L }, { 3, 3.000000000000000000000000000, 3L }, { 4, 8.000000000000000000000000000, 8L }, { 5, 15.00000000000000000000000000, 15L }, { 6, 48.00000000000000000000000000, 48L }, { 7, 105.0000000000000000000000000, 105L }, { 8, 384.0000000000000000000000000, 384L }, { 9, 945.0000000000000000000000000, 945L }, { 10, 3840.000000000000000000000000, 3840L }, { 11, 10395.00000000000000000000000, 10395L }, { 12, 46080.00000000000000000000000, 46080L }, { 13, 135135.0000000000000000000000, 135135L }, { 14, 645120.00000000000000000000000, 645120L }, { 15, 2.02702500000000000000000000000e6, 2027025L }, { 16, 1.03219200000000000000000000000e7, 10321920L }, { 17, 3.4459425000000000000000000000e7, 34459425L }, { 18, 1.85794560000000000000000000000e8, 185794560L }, { 19, 6.5472907500000000000000000000e8, 0 }, { 20, 3.7158912000000000000000000000e9, 0 }, { 21, 1.37493105750000000000000000000e10, 0 }, { 22, 8.1749606400000000000000000000e10, 0 }, { 23, 3.1623414322500000000000000000e11, 0 }, { 24, 1.96199055360000000000000000000e12, 0 }, { 25, 7.9058535806250000000000000000e12, 0 }, { 26, 5.1011754393600000000000000000e13, 0 }, { 27, 2.13458046676875000000000000000e14, 0 }, { 28, 1.42832912302080000000000000000e15, 0 }, { 29, 6.1902833536293750000000000000e15, 0 }, { 30, 4.2849873690624000000000000000e16, 0 }, { 31, 1.91898783962510625000000000000e17, 0 }, { 32, 1.37119595809996800000000000000e18, 0 }, { 33, 6.3326598707628506250000000000e18, 0 }, { 34, 4.6620662575398912000000000000e19, 0 }, { 35, 2.21643095476699771875000000000e20, 0 }, { 36, 1.67834385271436083200000000000e21, 0 }, { 37, 8.2007945326378915593750000000e21, 0 }, { 38, 6.3777066403145711616000000000e22, 0 }, { 39, 3.1983098677287777081562500000e23, 0 }, { 40, 2.55108265612582846464000000000e24, 0 }, { 41, 1.31130704576879886034406250000e25, 0 }, { 42, 1.07145471557284795514880000000e26, 0 }, { 43, 5.6386202968058350994794687500e26, 0 }, { 44, 4.7144007485205310026547200000e27, 0 }, { 45, 2.53737913356262579476576093750e28, 0 }, { 46, 2.16862434431944426122117120000e29, 0 }, { 47, 1.19256819277443412353990764062e30, 0 }, { 48, 1.04093968527333324538616217600e31, 0 }, { 49, 5.8435841445947272053455474391e31, 0 }, { 50, 5.2046984263666662269308108800e32, 0 }, { 51, 2.98022791374331087472622919392e33, 0 }, { 52, 2.70644318171066643800402165760e34, 0 }, { 53, 1.57952079428395476360490147278e35, 0 }, { 54, 1.46147931812375987652217169510e36, 0 }, { 55, 8.6873643685617511998269581003e36, 0 }, { 56, 8.1842841814930553085241614926e37, 0 }, { 57, 4.9517976900801981839013661172e38, 0 }, { 58, 4.7468848252659720789440136657e39, 0 }, { 59, 2.92156063714731692850180600912e40, 0 }, { 60, 2.84813089515958324736640819942e41, 0 }, { 61, 1.78215198865986332638610166557e42, 0 }, { 62, 1.76584115499894161336717308364e43, 0 }, { 63, 1.12275575285571389562324404931e44, 0 }, { 64, 1.13013833919932263255499077353e45, 0 }, { 65, 7.2979123935621403215510863205e45, 0 }, { 66, 7.4589130387155293748629391053e46, 0 }, { 67, 4.8896013036866340154392278347e47, 0 }, { 68, 5.0720608663265599749067985916e48, 0 }, { 69, 3.3738248995437774706530672060e49, 0 }, { 70, 3.5504426064285919824347590141e50, 0 }, { 71, 2.39541567867608200416367771623e51, 0 }, { 72, 2.55631867662858622735302649017e52, 0 }, { 73, 1.74865344543353986303948473285e53, 0 }, { 74, 1.89167582070515380824123960272e54, 0 }, { 75, 1.31149008407515489727961354964e55, 0 }, { 76, 1.43767362373591689426334209807e56, 0 }, { 77, 1.00984736473786927090530243322e57, 0 }, { 78, 1.12138542651401517752540683649e58, 0 }, { 79, 7.9777941814291672401518892225e58, 0 }, { 80, 8.9710834121121214202032546920e59, 0 }, { 81, 6.4620132869576254645230302702e60, 0 }, { 82, 7.3562883979319395645666688474e61, 0 }, { 83, 5.3634710281748291355541151243e62, 0 }, { 84, 6.1792822542628292342360018318e63, 0 }, { 85, 4.5589503739486047652209978556e64, 0 }, { 86, 5.3141827386660331414429615754e65, 0 }, { 87, 3.9662868253352861457422681344e66, 0 }, { 88, 4.6764808100261091644698061863e67, 0 }, { 89, 3.5299952745484046697106186396e68, 0 }, { 90, 4.2088327290234982480228255677e69, 0 }, { 91, 3.2122956998390482494366629620e70, 0 }, { 92, 3.8721261107016183881809995223e71, 0 }, { 93, 2.98743500085031487197609655470e72, 0 }, { 94, 3.6397985440595212848901395509e73, 0 }, { 95, 2.83806325080779912837729172696e74, 0 }, { 96, 3.4942066022971404334945339689e75, 0 }, { 97, 2.75292135328356515452597297515e76, 0 }, { 98, 3.4243224702511976248246432895e77, 0 }, { 99, 2.72539213975072950298071324540e78, 0 }, { 100, 3.4243224702511976248246432895e79, 0 }, { 101, 2.75264606114823679801052037785e80, 0 }, { 102, 3.4928089196562215773211361553e81, 0 }, { 103, 2.83522544298268390195083598919e82, 0 }, { 104, 3.6325212764424704404139816015e83, 0 }, { 105, 2.97698671513181809704837778865e84, 0 }, { 106, 3.8504725530290186668388204976e85, 0 }, { 107, 3.1853757851910453638417642339e86, 0 }, { 108, 4.1585103572713401601859261374e87, 0 }, { 109, 3.4720596058582394465875230149e88, 0 }, { 110, 4.5743613929984741762045187512e89, 0 }, { 111, 3.8539861625026457857121505465e90, 0 }, { 112, 5.1232847601582910773490610013e91, 0 }, { 113, 4.3550043636279897378547301176e92, 0 }, { 114, 5.8405446265804518281779295415e93, 0 }, { 115, 5.0082550181721881985329396352e94, 0 }, { 116, 6.7750317668333241206863982681e95, 0 }, { 117, 5.8596583712614601922835393732e96, 0 }, { 118, 7.9945374848633224624099499564e97, 0 }, { 119, 6.9729934618011376288174118541e98, 0 }, { 120, 9.5934449818359869548919399477e99, 0 }, { 121, 8.4373220887793765308690683435e100, 0 }, { 122, 1.17040028778399040849681667362e102, 0 }, { 123, 1.03779061691986331329689540625e103, 0 }, { 124, 1.45129635685214810653605267528e104, 0 }, { 125, 1.29723827114982914162111925781e105, 0 }, { 126, 1.82863340963370661423542637086e106, 0 }, { 127, 1.64749260436028300985882145742e107, 0 }, { 128, 2.34065076433114446622134575470e108, 0 }, { 129, 2.12526545962476508271787968008e109, 0 }, { 130, 3.04284599363048780608774948111e110, 0 }, { 131, 2.78409775210844225836042238090e111, 0 }, { 132, 4.0165567115922439040358293151e112, 0 }, { 133, 3.7028500103042282036193617666e113, 0 }, { 134, 5.3821859935336068314080112822e114, 0 }, { 135, 4.9988475139107080748861383849e115, 0 }, { 136, 7.3197729512057052907148953438e116, 0 }, { 137, 6.8484210940576700625940095873e117, 0 }, { 138, 1.01012866726638733011865555744e119, 0 }, { 139, 9.5193053207401613870056733264e119, 0 }, { 140, 1.41418013417294226216611778042e121, 0 }, { 141, 1.34222205022436275556779993902e122, 0 }, { 142, 2.00813579052557801227588724819e123, 0 }, { 143, 1.91937753182083874046195391280e124, 0 }, { 144, 2.89171553835683233767727763739e125, 0 }, { 145, 2.78309742114021617366983317355e126, 0 }, { 146, 4.2219046860009752130088253506e127, 0 }, { 147, 4.0911532090761177752946547651e128, 0 }, { 148, 6.2484189352814433152530615189e129, 0 }, { 149, 6.0958182815234154851890356000e130, 0 }, { 150, 9.3726284029221649728795922783e131, 0 }, { 151, 9.2046856051003573826354437561e132, 0 }, { 152, 1.42463951724416907587769802630e134, 0 }, { 153, 1.40831689758035467954322289468e135, 0 }, { 154, 2.19394485655602037685165496051e136, 0 }, { 155, 2.18289119124954975329199548675e137, 0 }, { 156, 3.4225539762273917878885817384e138, 0 }, { 157, 3.4271391702617931126684329142e139, 0 }, { 158, 5.4076352824392790248639591467e140, 0 }, { 159, 5.4491512807162510491428083336e141, 0 }, { 160, 8.6522164519028464397823346347e142, 0 }, { 161, 8.7731335619531641891199214170e143, 0 }, { 162, 1.40165906520826112324473821082e145, 0 }, { 163, 1.43002077059836576282654719098e146, 0 }, { 164, 2.29872086694154824212137066574e147, 0 }, { 165, 2.35953427148730350866380286512e148, 0 }, { 166, 3.8158766391229700819214753051e149, 0 }, { 167, 3.9404222333837968594685507847e150, 0 }, { 168, 6.4106727537265897376280785126e151, 0 }, { 169, 6.6593135744186166925018508262e152, 0 }, { 170, 1.08981436813352025539677334714e154, 0 }, { 171, 1.13874262122558345441781649128e155, 0 }, { 172, 1.87448071318965483928245015709e156, 0 }, { 173, 1.97002473472025937614282252992e157, 0 }, { 174, 3.2615964409499994203514632733e158, 0 }, { 175, 3.4475432857604539082499394274e159, 0 }, { 176, 5.7404097360719989798185753611e160, 0 }, { 177, 6.1021516157960034176023927864e161, 0 }, { 178, 1.02179293302081581840770641427e163, 0 }, { 179, 1.09228513922748461175082830877e164, 0 }, { 180, 1.83922727943746847313387154568e165, 0 }, { 181, 1.97703610200174714726899923887e166, 0 }, { 182, 3.3473936485761926211036462131e167, 0 }, { 183, 3.6179760666631972795022686071e168, 0 }, { 184, 6.1592043133801944228307090322e169, 0 }, { 185, 6.6932557233269149670791969232e170, 0 }, { 186, 1.14561200228871616264651187999e172, 0 }, { 187, 1.25163882026213309884380982464e173, 0 }, { 188, 2.15375056430278638577544233437e174, 0 }, { 189, 2.36559737029543155681480056857e175, 0 }, { 190, 4.0921260721752941329733404353e176, 0 }, { 191, 4.5182909772642742735162690860e177, 0 }, { 192, 7.8568820585765647353088136358e178, 0 }, { 193, 8.7203015861200493478863993359e179, 0 }, { 194, 1.52423511936385355864990984535e181, 0 }, { 195, 1.70045880929340962283784787050e182, 0 }, { 196, 2.98750083395315297495382329688e183, 0 }, { 197, 3.3499038543080169569905603049e184, 0 }, { 198, 5.9152516512272428904085701278e185, 0 }, { 199, 6.6663086700729537444112150067e186, 0 }, { 200, 1.18305033024544857808171402556e188, 0 }, { 201, 1.33992804268466370262665421635e189, 0 }, { 202, 2.38976166709580612772506233164e190, 0 }, { 203, 2.72005392664986731633210805920e191, 0 }, { 204, 4.8751138008754445005591271565e192, 0 }, { 205, 5.5761105496322279984808215214e193, 0 }, { 206, 1.00427344298034156711518019425e195, 0 }, { 207, 1.15425488377387119568553005492e196, 0 }, { 208, 2.08888876139911045959957480403e197, 0 }, { 209, 2.41239270708739079898275781478e198, 0 }, { 210, 4.3866663989381319651591070885e199, 0 }, { 211, 5.0901486119543945858536189892e200, 0 }, { 212, 9.2997327657488397661373070276e201, 0 }, { 213, 1.08420165434628604678682084470e203, 0 }, { 214, 1.99014281187025170995338370390e204, 0 }, { 215, 2.33103355684451500059166481610e205, 0 }, { 216, 4.2987084736397436934993088004e206, 0 }, { 217, 5.0583428183525975512839126509e207, 0 }, { 218, 9.3711844725346412518284931849e208, 0 }, { 219, 1.10777707721921886373117687056e210, 0 }, { 220, 2.06166058395762107540226850068e211, 0 }, { 221, 2.44818734065447368884590088393e212, 0 }, { 222, 4.5768864963859187873930360715e213, 0 }, { 223, 5.4594577696594763261263589712e214, 0 }, { 224, 1.02522257519044580837604008002e216, 0 }, { 225, 1.22837799817338217337843076851e217, 0 }, { 226, 2.31700301993040752692985058084e218, 0 }, { 227, 2.78841805585357753356903784452e219, 0 }, { 228, 5.2827668854413291614000593243e220, 0 }, { 229, 6.3854773479046925518730966640e221, 0 }, { 230, 1.21503638365150570712201364459e223, 0 }, { 231, 1.47504526736598397948268532937e224, 0 }, { 232, 2.81888441007149324052307165546e225, 0 }, { 233, 3.4368554729627426721946568174e226, 0 }, { 234, 6.5961895195672941828239876738e227, 0 }, { 235, 8.0766103614624452796574435210e228, 0 }, { 236, 1.55670072661788142714646109101e230, 0 }, { 237, 1.91415665566659953127881411447e231, 0 }, { 238, 3.7049477293505577966085773966e232, 0 }, { 239, 4.5748344070431728797563657336e233, 0 }, { 240, 8.8918745504413387118605857518e234, 0 }, { 241, 1.10253509209740466402128414180e236, 0 }, { 242, 2.15183364120680396827026175195e237, 0 }, { 243, 2.67916027379669333357172046456e238, 0 }, { 244, 5.2504740845446016825794386748e239, 0 }, { 245, 6.5639426708018986672507151382e240, 0 }, { 246, 1.29161662479797201391454191399e242, 0 }, { 247, 1.62129383968806897081092663913e243, 0 }, { 248, 3.2032092294989705945080639467e244, 0 }, { 249, 4.0370216608232917373192073314e245, 0 }, { 250, 8.0080230737474264862701598667e246, 0 }, { 251, 1.01329243686664622606712104019e248, 0 }, { 252, 2.01802181458435147454008028642e249, 0 }, { 253, 2.56362986527261495194981623168e250, 0 }, { 254, 5.1257754090442527453318039275e251, 0 }, { 255, 6.5372561564451681274720313908e252, 0 }, { 256, 1.31219850471532870280494180544e254, 0 }, { 257, 1.68007483220640820876031206743e255, 0 }, { 258, 3.3854721421655480532367498580e256, 0 }, { 259, 4.3513938154145972606892082546e257, 0 }, { 260, 8.8022275696304249384155496309e258, 0 }, { 261, 1.13571378582320988503988335446e260, 0 }, { 262, 2.30618362324317133386487400329e261, 0 }, { 263, 2.98692725671504199765489322224e262, 0 }, { 264, 6.0883247653619723214032673687e263, 0 }, { 265, 7.9153572302948612937854670389e264, 0 }, { 266, 1.61949438758628463749326912007e266, 0 }, { 267, 2.11340038048872796544071969939e267, 0 }, { 268, 4.3402449587312428284819612418e268, 0 }, { 269, 5.6850470235146782270355359914e269, 0 }, { 270, 1.17186613885743556369012953528e271, 0 }, { 271, 1.54064774337247779952663025366e272, 0 }, { 272, 3.1874758976922247332371523360e273, 0 }, { 273, 4.2059683394068643927077005925e274, 0 }, { 274, 8.7336839596766957690697974006e275, 0 }, { 275, 1.15664129333688770799461766294e277, 0 }, { 276, 2.41049677287076803226326408256e278, 0 }, { 277, 3.2038963825431789511450909263e279, 0 }, { 278, 6.7011810285807351296918741495e280, 0 }, { 279, 8.9388709072954692736948036845e281, 0 }, { 280, 1.87633068800260583631372476186e283, 0 }, { 281, 2.51182272495002686590823983534e284, 0 }, { 282, 5.2912525401673484584047038284e285, 0 }, { 283, 7.1084583116085760305203187340e286, 0 }, { 284, 1.50271572140752696218693588728e288, 0 }, { 285, 2.02591061880844416869829083919e289, 0 }, { 286, 4.2977669632255271118546366376e290, 0 }, { 287, 5.8143634759802347641640947085e291, 0 }, { 288, 1.23775688540895180821413535163e293, 0 }, { 289, 1.68035104455828784684342337075e294, 0 }, { 290, 3.5894949676859602438209925197e295, 0 }, { 291, 4.8898215396646176343143620089e296, 0 }, { 292, 1.04813253056430039119572981576e298, 0 }, { 293, 1.43271771112173296685410806860e299, 0 }, { 294, 3.08150963985904315011544565835e300, 0 }, { 295, 4.2265172478091122522196188024e301, 0 }, { 296, 9.1212685339827677243417191487e302, 0 }, { 297, 1.25527562259930633890922678431e304, 0 }, /* { 298, 2.71813802312686478185383230631e305, 0 }, { 299, 3.7532741115719259533385880851e306, 0 }, { 300, 8.1544140693805943455614969189e307, } */ }; /* Chebyshev coefficients for Gamma*(3/4(t+1)+1/2), -1val = (zr+0.5)*log1_r.val - zi*log1_i.val - (zr+7.5) + LogRootTwoPi_ + logAg_r.val; yi->val = zi*log1_r.val + (zr+0.5)*log1_i.val - zi + logAg_i.val; yr->err = 4.0 * GSL_DBL_EPSILON * fabs(yr->val); yi->err = 4.0 * GSL_DBL_EPSILON * fabs(yi->val); yi_tmp_val = yi->val; yi_tmp_err = yi->err; gsl_sf_angle_restrict_symm_err_e(yi_tmp_val, yi); yi->err += yi_tmp_err; return GSL_SUCCESS; } /* Lanczos method for real x > 0; * gamma=7, truncated at 1/(z+8) * [J. SIAM Numer. Anal, Ser. B, 1 (1964) 86] */ static int lngamma_lanczos(double x, gsl_sf_result * result) { int k; double Ag; double term1, term2; x -= 1.0; /* Lanczos writes z! instead of Gamma(z) */ Ag = lanczos_7_c[0]; for(k=1; k<=8; k++) { Ag += lanczos_7_c[k]/(x+k); } /* (x+0.5)*log(x+7.5) - (x+7.5) + LogRootTwoPi_ + log(Ag(x)) */ term1 = (x+0.5)*log((x+7.5)/M_E); term2 = LogRootTwoPi_ + log(Ag); result->val = term1 + (term2 - 7.0); result->err = 2.0 * GSL_DBL_EPSILON * (fabs(term1) + fabs(term2) + 7.0); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* x = eps near zero * gives double-precision for |eps| < 0.02 */ static int lngamma_sgn_0(double eps, gsl_sf_result * lng, double * sgn) { /* calculate series for g(eps) = Gamma(eps) eps - 1/(1+eps) - eps/2 */ const double c1 = -0.07721566490153286061; const double c2 = -0.01094400467202744461; const double c3 = 0.09252092391911371098; const double c4 = -0.01827191316559981266; const double c5 = 0.01800493109685479790; const double c6 = -0.00685088537872380685; const double c7 = 0.00399823955756846603; const double c8 = -0.00189430621687107802; const double c9 = 0.00097473237804513221; const double c10 = -0.00048434392722255893; const double g6 = c6+eps*(c7+eps*(c8 + eps*(c9 + eps*c10))); const double g = eps*(c1+eps*(c2+eps*(c3+eps*(c4+eps*(c5+eps*g6))))); /* calculate Gamma(eps) eps, a positive quantity */ const double gee = g + 1.0/(1.0+eps) + 0.5*eps; lng->val = log(gee/fabs(eps)); lng->err = 4.0 * GSL_DBL_EPSILON * fabs(lng->val); *sgn = GSL_SIGN(eps); return GSL_SUCCESS; } /* x near a negative integer * Calculates sign as well as log(|gamma(x)|). * x = -N + eps * assumes N >= 1 */ static int lngamma_sgn_sing(int N, double eps, gsl_sf_result * lng, double * sgn) { if(eps == 0.0) { lng->val = 0.0; lng->err = 0.0; *sgn = 0.0; GSL_ERROR ("error", GSL_EDOM); } else if(N == 1) { /* calculate series for * g = eps gamma(-1+eps) + 1 + eps/2 (1+3eps)/(1-eps^2) * double-precision for |eps| < 0.02 */ const double c0 = 0.07721566490153286061; const double c1 = 0.08815966957356030521; const double c2 = -0.00436125434555340577; const double c3 = 0.01391065882004640689; const double c4 = -0.00409427227680839100; const double c5 = 0.00275661310191541584; const double c6 = -0.00124162645565305019; const double c7 = 0.00065267976121802783; const double c8 = -0.00032205261682710437; const double c9 = 0.00016229131039545456; const double g5 = c5 + eps*(c6 + eps*(c7 + eps*(c8 + eps*c9))); const double g = eps*(c0 + eps*(c1 + eps*(c2 + eps*(c3 + eps*(c4 + eps*g5))))); /* calculate eps gamma(-1+eps), a negative quantity */ const double gam_e = g - 1.0 - 0.5*eps*(1.0+3.0*eps)/(1.0 - eps*eps); lng->val = log(fabs(gam_e)/fabs(eps)); lng->err = 2.0 * GSL_DBL_EPSILON * fabs(lng->val); *sgn = ( eps > 0.0 ? -1.0 : 1.0 ); return GSL_SUCCESS; } else { double g; /* series for sin(Pi(N+1-eps))/(Pi eps) modulo the sign * double-precision for |eps| < 0.02 */ const double cs1 = -1.6449340668482264365; const double cs2 = 0.8117424252833536436; const double cs3 = -0.1907518241220842137; const double cs4 = 0.0261478478176548005; const double cs5 = -0.0023460810354558236; const double e2 = eps*eps; const double sin_ser = 1.0 + e2*(cs1+e2*(cs2+e2*(cs3+e2*(cs4+e2*cs5)))); /* calculate series for ln(gamma(1+N-eps)) * double-precision for |eps| < 0.02 */ double aeps = fabs(eps); double c1, c2, c3, c4, c5, c6, c7; double lng_ser; gsl_sf_result c0; gsl_sf_result psi_0; gsl_sf_result psi_1; gsl_sf_result psi_2; gsl_sf_result psi_3; gsl_sf_result psi_4; gsl_sf_result psi_5; gsl_sf_result psi_6; psi_2.val = 0.0; psi_3.val = 0.0; psi_4.val = 0.0; psi_5.val = 0.0; psi_6.val = 0.0; gsl_sf_lnfact_e(N, &c0); gsl_sf_psi_int_e(N+1, &psi_0); gsl_sf_psi_1_int_e(N+1, &psi_1); if(aeps > 0.00001) gsl_sf_psi_n_e(2, N+1.0, &psi_2); if(aeps > 0.0002) gsl_sf_psi_n_e(3, N+1.0, &psi_3); if(aeps > 0.001) gsl_sf_psi_n_e(4, N+1.0, &psi_4); if(aeps > 0.005) gsl_sf_psi_n_e(5, N+1.0, &psi_5); if(aeps > 0.01) gsl_sf_psi_n_e(6, N+1.0, &psi_6); c1 = psi_0.val; c2 = psi_1.val/2.0; c3 = psi_2.val/6.0; c4 = psi_3.val/24.0; c5 = psi_4.val/120.0; c6 = psi_5.val/720.0; c7 = psi_6.val/5040.0; lng_ser = c0.val-eps*(c1-eps*(c2-eps*(c3-eps*(c4-eps*(c5-eps*(c6-eps*c7)))))); /* calculate * g = ln(|eps gamma(-N+eps)|) * = -ln(gamma(1+N-eps)) + ln(|eps Pi/sin(Pi(N+1+eps))|) */ g = -lng_ser - log(sin_ser); lng->val = g - log(fabs(eps)); lng->err = c0.err + 2.0 * GSL_DBL_EPSILON * (fabs(g) + fabs(lng->val)); *sgn = ( GSL_IS_ODD(N) ? -1.0 : 1.0 ) * ( eps > 0.0 ? 1.0 : -1.0 ); return GSL_SUCCESS; } } /* This gets bad near the negative half axis. However, this * region can be avoided by use of the reflection formula, as usual. * Only the first two terms of the series are kept. */ #if 0 static int lngamma_complex_stirling(const double zr, const double zi, double * lg_r, double * arg) { double re_zinv, im_zinv; double re_zinv2, im_zinv2; double re_zinv3, im_zinv3; double re_zhlnz, im_zhlnz; double r, lnr, theta; gsl_sf_complex_log_e(zr, zi, &lnr, &theta); /* z = r e^{i theta} */ r = exp(lnr); re_zinv = (zr/r)/r; im_zinv = -(zi/r)/r; re_zinv2 = re_zinv*re_zinv - im_zinv*im_zinv; re_zinv2 = 2.0*re_zinv*im_zinv; re_zinv3 = re_zinv2*re_zinv - im_zinv2*im_zinv; re_zinv3 = re_zinv2*im_zinv + im_zinv2*re_zinv; re_zhlnz = (zr - 0.5)*lnr - zi*theta; im_zhlnz = zi*lnr + zr*theta; *lg_r = re_zhlnz - zr + 0.5*(M_LN2+M_LNPI) + re_zinv/12.0 - re_zinv3/360.0; *arg = im_zhlnz - zi + 1.0/12.0*im_zinv - im_zinv3/360.0; return GSL_SUCCESS; } #endif /* 0 */ inline static int lngamma_1_pade(const double eps, gsl_sf_result * result) { /* Use (2,2) Pade for Log[Gamma[1+eps]]/eps * plus a correction series. */ const double n1 = -1.0017419282349508699871138440; const double n2 = 1.7364839209922879823280541733; const double d1 = 1.2433006018858751556055436011; const double d2 = 5.0456274100274010152489597514; const double num = (eps + n1) * (eps + n2); const double den = (eps + d1) * (eps + d2); const double pade = 2.0816265188662692474880210318 * num / den; const double c0 = 0.004785324257581753; const double c1 = -0.01192457083645441; const double c2 = 0.01931961413960498; const double c3 = -0.02594027398725020; const double c4 = 0.03141928755021455; const double eps5 = eps*eps*eps*eps*eps; const double corr = eps5 * (c0 + eps*(c1 + eps*(c2 + eps*(c3 + c4*eps)))); result->val = eps * (pade + corr); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } inline static int lngamma_2_pade(const double eps, gsl_sf_result * result) { /* Use (2,2) Pade for Log[Gamma[2+eps]]/eps * plus a correction series. */ const double n1 = 1.000895834786669227164446568; const double n2 = 4.209376735287755081642901277; const double d1 = 2.618851904903217274682578255; const double d2 = 10.85766559900983515322922936; const double num = (eps + n1) * (eps + n2); const double den = (eps + d1) * (eps + d2); const double pade = 2.85337998765781918463568869 * num/den; const double c0 = 0.0001139406357036744; const double c1 = -0.0001365435269792533; const double c2 = 0.0001067287169183665; const double c3 = -0.0000693271800931282; const double c4 = 0.0000407220927867950; const double eps5 = eps*eps*eps*eps*eps; const double corr = eps5 * (c0 + eps*(c1 + eps*(c2 + eps*(c3 + c4*eps)))); result->val = eps * (pade + corr); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* series for gammastar(x) * double-precision for x > 10.0 */ static int gammastar_ser(const double x, gsl_sf_result * result) { /* Use the Stirling series for the correction to Log(Gamma(x)), * which is better behaved and easier to compute than the * regular Stirling series for Gamma(x). */ const double y = 1.0/(x*x); const double c0 = 1.0/12.0; const double c1 = -1.0/360.0; const double c2 = 1.0/1260.0; const double c3 = -1.0/1680.0; const double c4 = 1.0/1188.0; const double c5 = -691.0/360360.0; const double c6 = 1.0/156.0; const double c7 = -3617.0/122400.0; const double ser = c0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*(c6 + y*c7)))))); result->val = exp(ser/x); result->err = 2.0 * GSL_DBL_EPSILON * result->val * GSL_MAX_DBL(1.0, ser/x); return GSL_SUCCESS; } /* Chebyshev expansion for log(gamma(x)/gamma(8)) * 5 < x < 10 * -1 < t < 1 */ static double gamma_5_10_data[24] = { -1.5285594096661578881275075214, 4.8259152300595906319768555035, 0.2277712320977614992970601978, -0.0138867665685617873604917300, 0.0012704876495201082588139723, -0.0001393841240254993658962470, 0.0000169709242992322702260663, -2.2108528820210580075775889168e-06, 3.0196602854202309805163918716e-07, -4.2705675000079118380587357358e-08, 6.2026423818051402794663551945e-09, -9.1993973208880910416311405656e-10, 1.3875551258028145778301211638e-10, -2.1218861491906788718519522978e-11, 3.2821736040381439555133562600e-12, -5.1260001009953791220611135264e-13, 8.0713532554874636696982146610e-14, -1.2798522376569209083811628061e-14, 2.0417711600852502310258808643e-15, -3.2745239502992355776882614137e-16, 5.2759418422036579482120897453e-17, -8.5354147151695233960425725513e-18, 1.3858639703888078291599886143e-18, -2.2574398807738626571560124396e-19 }; static const cheb_series gamma_5_10_cs = { gamma_5_10_data, 23, -1, 1, 11 }; /* gamma(x) for x >= 1/2 * assumes x >= 1/2 */ static int gamma_xgthalf(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.5) { result->val = 1.77245385090551602729817; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if (x <= (GSL_SF_FACT_NMAX + 1.0) && x == floor(x)) { int n = (int) floor (x); result->val = fact_table[n - 1].f; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(fabs(x - 1.0) < 0.01) { /* Use series for Gamma[1+eps] - 1/(1+eps). */ const double eps = x - 1.0; const double c1 = 0.4227843350984671394; const double c2 = -0.01094400467202744461; const double c3 = 0.09252092391911371098; const double c4 = -0.018271913165599812664; const double c5 = 0.018004931096854797895; const double c6 = -0.006850885378723806846; const double c7 = 0.003998239557568466030; result->val = 1.0/x + eps*(c1+eps*(c2+eps*(c3+eps*(c4+eps*(c5+eps*(c6+eps*c7)))))); result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(fabs(x - 2.0) < 0.01) { /* Use series for Gamma[1 + eps]. */ const double eps = x - 2.0; const double c1 = 0.4227843350984671394; const double c2 = 0.4118403304264396948; const double c3 = 0.08157691924708626638; const double c4 = 0.07424901075351389832; const double c5 = -0.00026698206874501476832; const double c6 = 0.011154045718130991049; const double c7 = -0.002852645821155340816; const double c8 = 0.0021039333406973880085; result->val = 1.0 + eps*(c1+eps*(c2+eps*(c3+eps*(c4+eps*(c5+eps*(c6+eps*(c7+eps*c8))))))); result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < 5.0) { /* Exponentiating the logarithm is fine, as * long as the exponential is not so large * that it greatly amplifies the error. */ gsl_sf_result lg; lngamma_lanczos(x, &lg); result->val = exp(lg.val); result->err = result->val * (lg.err + 2.0 * GSL_DBL_EPSILON); return GSL_SUCCESS; } else if(x < 10.0) { /* This is a sticky area. The logarithm * is too large and the gammastar series * is not good. */ const double gamma_8 = 5040.0; const double t = (2.0*x - 15.0)/5.0; gsl_sf_result c; cheb_eval_e(&gamma_5_10_cs, t, &c); result->val = exp(c.val) * gamma_8; result->err = result->val * c.err; result->err += 2.0 * GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else if(x < GSL_SF_GAMMA_XMAX) { /* We do not want to exponentiate the logarithm * if x is large because of the inevitable * inflation of the error. So we carefully * use pow() and exp() with exact quantities. */ double p = pow(x, 0.5*x); double e = exp(-x); double q = (p * e) * p; double pre = M_SQRT2 * M_SQRTPI * q/sqrt(x); gsl_sf_result gstar; int stat_gs = gammastar_ser(x, &gstar); result->val = pre * gstar.val; result->err = (x + 2.5) * GSL_DBL_EPSILON * result->val; return stat_gs; } else { OVERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_lngamma_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(fabs(x - 1.0) < 0.01) { /* Note that we must amplify the errors * from the Pade evaluations because of * the way we must pass the argument, i.e. * writing (1-x) is a loss of precision * when x is near 1. */ int stat = lngamma_1_pade(x - 1.0, result); result->err *= 1.0/(GSL_DBL_EPSILON + fabs(x - 1.0)); return stat; } else if(fabs(x - 2.0) < 0.01) { int stat = lngamma_2_pade(x - 2.0, result); result->err *= 1.0/(GSL_DBL_EPSILON + fabs(x - 2.0)); return stat; } else if(x >= 0.5) { return lngamma_lanczos(x, result); } else if(x == 0.0) { DOMAIN_ERROR(result); } else if(fabs(x) < 0.02) { double sgn; return lngamma_sgn_0(x, result, &sgn); } else if(x > -0.5/(GSL_DBL_EPSILON*M_PI)) { /* Try to extract a fractional * part from x. */ double z = 1.0 - x; double s = sin(M_PI*z); double as = fabs(s); if(s == 0.0) { DOMAIN_ERROR(result); } else if(as < M_PI*0.015) { /* x is near a negative integer, -N */ if(x < INT_MIN + 2.0) { result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EROUND); } else { int N = -(int)(x - 0.5); double eps = x + N; double sgn; return lngamma_sgn_sing(N, eps, result, &sgn); } } else { gsl_sf_result lg_z; lngamma_lanczos(z, &lg_z); result->val = M_LNPI - (log(as) + lg_z.val); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + lg_z.err; return GSL_SUCCESS; } } else { /* |x| was too large to extract any fractional part */ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EROUND); } } int gsl_sf_lngamma_sgn_e(double x, gsl_sf_result * result_lg, double * sgn) { if(fabs(x - 1.0) < 0.01) { int stat = lngamma_1_pade(x - 1.0, result_lg); result_lg->err *= 1.0/(GSL_DBL_EPSILON + fabs(x - 1.0)); *sgn = 1.0; return stat; } else if(fabs(x - 2.0) < 0.01) { int stat = lngamma_2_pade(x - 2.0, result_lg); result_lg->err *= 1.0/(GSL_DBL_EPSILON + fabs(x - 2.0)); *sgn = 1.0; return stat; } else if(x >= 0.5) { *sgn = 1.0; return lngamma_lanczos(x, result_lg); } else if(x == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result_lg); } else if(fabs(x) < 0.02) { return lngamma_sgn_0(x, result_lg, sgn); } else if(x > -0.5/(GSL_DBL_EPSILON*M_PI)) { /* Try to extract a fractional * part from x. */ double z = 1.0 - x; double s = sin(M_PI*x); double as = fabs(s); if(s == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result_lg); } else if(as < M_PI*0.015) { /* x is near a negative integer, -N */ if(x < INT_MIN + 2.0) { result_lg->val = 0.0; result_lg->err = 0.0; *sgn = 0.0; GSL_ERROR ("error", GSL_EROUND); } else { int N = -(int)(x - 0.5); double eps = x + N; return lngamma_sgn_sing(N, eps, result_lg, sgn); } } else { gsl_sf_result lg_z; lngamma_lanczos(z, &lg_z); *sgn = (s > 0.0 ? 1.0 : -1.0); result_lg->val = M_LNPI - (log(as) + lg_z.val); result_lg->err = 2.0 * GSL_DBL_EPSILON * fabs(result_lg->val) + lg_z.err; return GSL_SUCCESS; } } else { /* |x| was too large to extract any fractional part */ result_lg->val = 0.0; result_lg->err = 0.0; *sgn = 0.0; GSL_ERROR ("x too large to extract fraction part", GSL_EROUND); } } int gsl_sf_gamma_e(const double x, gsl_sf_result * result) { if(x < 0.5) { int rint_x = (int)floor(x+0.5); double f_x = x - rint_x; double sgn_gamma = ( GSL_IS_EVEN(rint_x) ? 1.0 : -1.0 ); double sin_term = sgn_gamma * sin(M_PI * f_x) / M_PI; if(sin_term == 0.0) { DOMAIN_ERROR(result); } else if(x > -169.0) { gsl_sf_result g; gamma_xgthalf(1.0-x, &g); if(fabs(sin_term) * g.val * GSL_DBL_MIN < 1.0) { result->val = 1.0/(sin_term * g.val); result->err = fabs(g.err/g.val) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } else { /* It is hard to control it here. * We can only exponentiate the * logarithm and eat the loss of * precision. */ gsl_sf_result lng; double sgn; int stat_lng = gsl_sf_lngamma_sgn_e(x, &lng, &sgn); int stat_e = gsl_sf_exp_mult_err_e(lng.val, lng.err, sgn, 0.0, result); return GSL_ERROR_SELECT_2(stat_e, stat_lng); } } else { return gamma_xgthalf(x, result); } } int gsl_sf_gammastar_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 0.5) { gsl_sf_result lg; const int stat_lg = gsl_sf_lngamma_e(x, &lg); const double lx = log(x); const double c = 0.5*(M_LN2+M_LNPI); const double lnr_val = lg.val - (x-0.5)*lx + x - c; const double lnr_err = lg.err + 2.0 * GSL_DBL_EPSILON *((x+0.5)*fabs(lx) + c); const int stat_e = gsl_sf_exp_err_e(lnr_val, lnr_err, result); return GSL_ERROR_SELECT_2(stat_lg, stat_e); } else if(x < 2.0) { const double t = 4.0/3.0*(x-0.5) - 1.0; return cheb_eval_e(&gstar_a_cs, t, result); } else if(x < 10.0) { const double t = 0.25*(x-2.0) - 1.0; gsl_sf_result c; cheb_eval_e(&gstar_b_cs, t, &c); result->val = c.val/(x*x) + 1.0 + 1.0/(12.0*x); result->err = c.err/(x*x); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 1.0/GSL_ROOT4_DBL_EPSILON) { return gammastar_ser(x, result); } else if(x < 1.0/GSL_DBL_EPSILON) { /* Use Stirling formula for Gamma(x). */ const double xi = 1.0/x; result->val = 1.0 + xi/12.0*(1.0 + xi/24.0*(1.0 - xi*(139.0/180.0 + 571.0/8640.0*xi))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = 1.0; result->err = 1.0/x; return GSL_SUCCESS; } } int gsl_sf_gammainv_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if (x <= 0.0 && x == floor(x)) { /* negative integer */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 0.5) { gsl_sf_result lng; double sgn; int stat_lng = gsl_sf_lngamma_sgn_e(x, &lng, &sgn); if(stat_lng == GSL_EDOM) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(stat_lng != GSL_SUCCESS) { result->val = 0.0; result->err = 0.0; return stat_lng; } else { return gsl_sf_exp_mult_err_e(-lng.val, lng.err, sgn, 0.0, result); } } else { gsl_sf_result g; int stat_g = gamma_xgthalf(x, &g); if(stat_g == GSL_EOVRFLW) { UNDERFLOW_ERROR(result); } else { result->val = 1.0/g.val; result->err = fabs(g.err/g.val) * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } } int gsl_sf_lngamma_complex_e(double zr, double zi, gsl_sf_result * lnr, gsl_sf_result * arg) { if(zr <= 0.5) { /* Transform to right half plane using reflection; * in fact we do a little better by stopping at 1/2. */ double x = 1.0-zr; double y = -zi; gsl_sf_result a, b; gsl_sf_result lnsin_r, lnsin_i; int stat_l = lngamma_lanczos_complex(x, y, &a, &b); int stat_s = gsl_sf_complex_logsin_e(M_PI*zr, M_PI*zi, &lnsin_r, &lnsin_i); if(stat_s == GSL_SUCCESS) { int stat_r; lnr->val = M_LNPI - lnsin_r.val - a.val; lnr->err = lnsin_r.err + a.err + 2.0 * GSL_DBL_EPSILON * fabs(lnr->val); arg->val = -lnsin_i.val - b.val; arg->err = lnsin_i.err + b.err + 2.0 * GSL_DBL_EPSILON * fabs(arg->val); stat_r = gsl_sf_angle_restrict_symm_e(&(arg->val)); return GSL_ERROR_SELECT_2(stat_r, stat_l); } else { DOMAIN_ERROR_2(lnr,arg); } } else { /* otherwise plain vanilla Lanczos */ return lngamma_lanczos_complex(zr, zi, lnr, arg); } } int gsl_sf_taylorcoeff_e(const int n, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < 0.0 || n < 0) { DOMAIN_ERROR(result); } else if(n == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(n == 1) { result->val = x; result->err = 0.0; return GSL_SUCCESS; } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { const double log2pi = M_LNPI + M_LN2; const double ln_test = n*(log(x)+1.0) + 1.0 - (n+0.5)*log(n+1.0) + 0.5*log2pi; if(ln_test < GSL_LOG_DBL_MIN+1.0) { UNDERFLOW_ERROR(result); } else if(ln_test > GSL_LOG_DBL_MAX-1.0) { OVERFLOW_ERROR(result); } else { double product = 1.0; int k; for(k=1; k<=n; k++) { product *= (x/k); } result->val = product; result->err = n * GSL_DBL_EPSILON * product; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } } int gsl_sf_fact_e(const unsigned int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n < 18) { result->val = fact_table[n].f; result->err = 0.0; return GSL_SUCCESS; } else if(n <= GSL_SF_FACT_NMAX){ result->val = fact_table[n].f; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_doublefact_e(const unsigned int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n < 26) { result->val = doub_fact_table[n].f; result->err = 0.0; return GSL_SUCCESS; } else if(n <= GSL_SF_DOUBLEFACT_NMAX){ result->val = doub_fact_table[n].f; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_lnfact_e(const unsigned int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n <= GSL_SF_FACT_NMAX){ result->val = log(fact_table[n].f); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_lngamma_e(n+1.0, result); return GSL_SUCCESS; } } int gsl_sf_lndoublefact_e(const unsigned int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n <= GSL_SF_DOUBLEFACT_NMAX){ result->val = log(doub_fact_table[n].f); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(GSL_IS_ODD(n)) { gsl_sf_result lg; gsl_sf_lngamma_e(0.5*(n+2.0), &lg); result->val = 0.5*(n+1.0) * M_LN2 - 0.5*M_LNPI + lg.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + lg.err; return GSL_SUCCESS; } else { gsl_sf_result lg; gsl_sf_lngamma_e(0.5*n+1.0, &lg); result->val = 0.5*n*M_LN2 + lg.val; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + lg.err; return GSL_SUCCESS; } } int gsl_sf_lnchoose_e(unsigned int n, unsigned int m, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(m > n) { DOMAIN_ERROR(result); } else if(m == n || m == 0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result nf; gsl_sf_result mf; gsl_sf_result nmmf; if(m*2 > n) m = n-m; gsl_sf_lnfact_e(n, &nf); gsl_sf_lnfact_e(m, &mf); gsl_sf_lnfact_e(n-m, &nmmf); result->val = nf.val - mf.val - nmmf.val; result->err = nf.err + mf.err + nmmf.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_choose_e(unsigned int n, unsigned int m, gsl_sf_result * result) { if(m > n) { DOMAIN_ERROR(result); } else if(m == n || m == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if (n <= GSL_SF_FACT_NMAX) { result->val = (fact_table[n].f / fact_table[m].f) / fact_table[n-m].f; result->err = 6.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { if(m*2 < n) m = n-m; if (n - m < 64) /* compute product for a manageable number of terms */ { double prod = 1.0; unsigned int k; for(k=n; k>=m+1; k--) { double tk = (double)k / (double)(k-m); if(tk > GSL_DBL_MAX/prod) { OVERFLOW_ERROR(result); } prod *= tk; } result->val = prod; result->err = 2.0 * GSL_DBL_EPSILON * prod * fabs(n-m); return GSL_SUCCESS; } else { gsl_sf_result lc; const int stat_lc = gsl_sf_lnchoose_e (n, m, &lc); const int stat_e = gsl_sf_exp_err_e(lc.val, lc.err, result); return GSL_ERROR_SELECT_2(stat_lc, stat_e); } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_fact(const unsigned int n) { EVAL_RESULT(gsl_sf_fact_e(n, &result)); } double gsl_sf_lnfact(const unsigned int n) { EVAL_RESULT(gsl_sf_lnfact_e(n, &result)); } double gsl_sf_doublefact(const unsigned int n) { EVAL_RESULT(gsl_sf_doublefact_e(n, &result)); } double gsl_sf_lndoublefact(const unsigned int n) { EVAL_RESULT(gsl_sf_lndoublefact_e(n, &result)); } double gsl_sf_lngamma(const double x) { EVAL_RESULT(gsl_sf_lngamma_e(x, &result)); } double gsl_sf_gamma(const double x) { EVAL_RESULT(gsl_sf_gamma_e(x, &result)); } double gsl_sf_gammastar(const double x) { EVAL_RESULT(gsl_sf_gammastar_e(x, &result)); } double gsl_sf_gammainv(const double x) { EVAL_RESULT(gsl_sf_gammainv_e(x, &result)); } double gsl_sf_taylorcoeff(const int n, const double x) { EVAL_RESULT(gsl_sf_taylorcoeff_e(n, x, &result)); } double gsl_sf_choose(unsigned int n, unsigned int m) { EVAL_RESULT(gsl_sf_choose_e(n, m, &result)); } double gsl_sf_lnchoose(unsigned int n, unsigned int m) { EVAL_RESULT(gsl_sf_lnchoose_e(n, m, &result)); } sources_5316/external/gsl/gsl_fft__c_pass_5.c0000664000176700017670000001703511723710247020051 0ustar paulpaul/* fft/c_pass_5.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int FUNCTION(fft_complex,pass_5) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[]) { size_t i = 0, j = 0; size_t k, k1; const size_t factor = 5; const size_t m = n / factor; const size_t q = n / product; const size_t p_1 = product / factor; const size_t jump = (factor - 1) * p_1; const ATOMIC sin_2pi_by_5 = sin (2.0 * M_PI / 5.0); const ATOMIC sin_2pi_by_10 = sin (2.0 * M_PI / 10.0); for (k = 0; k < q; k++) { ATOMIC w1_real, w1_imag, w2_real, w2_imag, w3_real, w3_imag, w4_real, w4_imag; if (k == 0) { w1_real = 1.0; w1_imag = 0.0; w2_real = 1.0; w2_imag = 0.0; w3_real = 1.0; w3_imag = 0.0; w4_real = 1.0; w4_imag = 0.0; } else { if (sign == gsl_fft_forward) { /* forward tranform */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = GSL_IMAG(twiddle2[k - 1]); w3_real = GSL_REAL(twiddle3[k - 1]); w3_imag = GSL_IMAG(twiddle3[k - 1]); w4_real = GSL_REAL(twiddle4[k - 1]); w4_imag = GSL_IMAG(twiddle4[k - 1]); } else { /* backward tranform: w -> conjugate(w) */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = -GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = -GSL_IMAG(twiddle2[k - 1]); w3_real = GSL_REAL(twiddle3[k - 1]); w3_imag = -GSL_IMAG(twiddle3[k - 1]); w4_real = GSL_REAL(twiddle4[k - 1]); w4_imag = -GSL_IMAG(twiddle4[k - 1]); } } for (k1 = 0; k1 < p_1; k1++) { ATOMIC x0_real, x0_imag, x1_real, x1_imag, x2_real, x2_imag, x3_real, x3_imag, x4_real, x4_imag; const ATOMIC z0_real = REAL(in,istride,i); const ATOMIC z0_imag = IMAG(in,istride,i); const ATOMIC z1_real = REAL(in,istride,i + m); const ATOMIC z1_imag = IMAG(in,istride,i + m); const ATOMIC z2_real = REAL(in,istride,i + 2*m); const ATOMIC z2_imag = IMAG(in,istride,i + 2*m); const ATOMIC z3_real = REAL(in,istride,i + 3*m); const ATOMIC z3_imag = IMAG(in,istride,i + 3*m); const ATOMIC z4_real = REAL(in,istride,i + 4*m); const ATOMIC z4_imag = IMAG(in,istride,i + 4*m); /* compute x = W(5) z */ /* t1 = z1 + z4 */ const ATOMIC t1_real = z1_real + z4_real; const ATOMIC t1_imag = z1_imag + z4_imag; /* t2 = z2 + z3 */ const ATOMIC t2_real = z2_real + z3_real; const ATOMIC t2_imag = z2_imag + z3_imag; /* t3 = z1 - z4 */ const ATOMIC t3_real = z1_real - z4_real; const ATOMIC t3_imag = z1_imag - z4_imag; /* t4 = z2 - z3 */ const ATOMIC t4_real = z2_real - z3_real; const ATOMIC t4_imag = z2_imag - z3_imag; /* t5 = t1 + t2 */ const ATOMIC t5_real = t1_real + t2_real; const ATOMIC t5_imag = t1_imag + t2_imag; /* t6 = (sqrt(5)/4)(t1 - t2) */ const ATOMIC t6_real = (sqrt (5.0) / 4.0) * (t1_real - t2_real); const ATOMIC t6_imag = (sqrt (5.0) / 4.0) * (t1_imag - t2_imag); /* t7 = z0 - ((t5)/4) */ const ATOMIC t7_real = z0_real - t5_real / 4.0; const ATOMIC t7_imag = z0_imag - t5_imag / 4.0; /* t8 = t7 + t6 */ const ATOMIC t8_real = t7_real + t6_real; const ATOMIC t8_imag = t7_imag + t6_imag; /* t9 = t7 - t6 */ const ATOMIC t9_real = t7_real - t6_real; const ATOMIC t9_imag = t7_imag - t6_imag; /* t10 = sin(2 pi/5) t3 + sin(2 pi/10) t4 */ const ATOMIC t10_real = ((int) sign) * (sin_2pi_by_5 * t3_real + sin_2pi_by_10 * t4_real); const ATOMIC t10_imag = ((int) sign) * (sin_2pi_by_5 * t3_imag + sin_2pi_by_10 * t4_imag); /* t11 = sin(2 pi/10) t3 - sin(2 pi/5) t4 */ const ATOMIC t11_real = ((int) sign) * (sin_2pi_by_10 * t3_real - sin_2pi_by_5 * t4_real); const ATOMIC t11_imag = ((int) sign) * (sin_2pi_by_10 * t3_imag - sin_2pi_by_5 * t4_imag); /* x0 = z0 + t5 */ x0_real = z0_real + t5_real; x0_imag = z0_imag + t5_imag; /* x1 = t8 + i t10 */ x1_real = t8_real - t10_imag; x1_imag = t8_imag + t10_real; /* x2 = t9 + i t11 */ x2_real = t9_real - t11_imag; x2_imag = t9_imag + t11_real; /* x3 = t9 - i t11 */ x3_real = t9_real + t11_imag; x3_imag = t9_imag - t11_real; /* x4 = t8 - i t10 */ x4_real = t8_real + t10_imag; x4_imag = t8_imag - t10_real; /* apply twiddle factors */ /* to0 = 1 * x0 */ REAL(out,ostride,j) = x0_real; IMAG(out,ostride,j) = x0_imag; /* to1 = w1 * x1 */ REAL(out,ostride,j + p_1) = w1_real * x1_real - w1_imag * x1_imag; IMAG(out,ostride,j + p_1) = w1_real * x1_imag + w1_imag * x1_real; /* to2 = w2 * x2 */ REAL(out,ostride,j + 2*p_1) = w2_real * x2_real - w2_imag * x2_imag; IMAG(out,ostride,j+2*p_1) = w2_real * x2_imag + w2_imag * x2_real; /* to3 = w3 * x3 */ REAL(out,ostride,j+3*p_1) = w3_real * x3_real - w3_imag * x3_imag; IMAG(out,ostride,j+3*p_1) = w3_real * x3_imag + w3_imag * x3_real; /* to4 = w4 * x4 */ REAL(out,ostride,j+4*p_1) = w4_real * x4_real - w4_imag * x4_imag; IMAG(out,ostride,j+4*p_1) = w4_real * x4_imag + w4_imag * x4_real; i++; j++; } j += jump; } return 0; } sources_5316/external/gsl/gsl_matrix__getset_source.c0000664000176700017670000001167611723710247021762 0ustar paulpaul/**********************************************************************/ /* The functions below are obsolete */ /**********************************************************************/ int FUNCTION (gsl_matrix, get_row) (TYPE (gsl_vector) * v, const TYPE (gsl_matrix) * m, const size_t i) { const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; if (i >= M) { GSL_ERROR ("row index is out of range", GSL_EINVAL); } if (v->size != N) { GSL_ERROR ("matrix row size and vector length are not equal", GSL_EBADLEN); } { ATOMIC *v_data = v->data; const ATOMIC *row_data = m->data + MULTIPLICITY * i * tda; const size_t stride = v->stride ; size_t j; for (j = 0; j < N; j++) { unsigned int k; for (k = 0; k < MULTIPLICITY; k++) { v_data[MULTIPLICITY * stride * j + k] = row_data[MULTIPLICITY * j + k]; } } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, get_col) (TYPE (gsl_vector) * v, const TYPE (gsl_matrix) * m, const size_t j) { const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; if (j >= N) { GSL_ERROR ("column index is out of range", GSL_EINVAL); } if (v->size != M) { GSL_ERROR ("matrix column size and vector length are not equal", GSL_EBADLEN); } { ATOMIC *v_data = v->data; const ATOMIC *column_data = m->data + MULTIPLICITY * j; const size_t stride = v->stride ; size_t i; for (i = 0; i < M; i++) { unsigned int k; for (k = 0; k < MULTIPLICITY; k++) { v_data[stride * MULTIPLICITY * i + k] = column_data[MULTIPLICITY * i * tda + k]; } } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, set_row) (TYPE (gsl_matrix) * m, const size_t i, const TYPE (gsl_vector) * v) { const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; if (i >= M) { GSL_ERROR ("row index is out of range", GSL_EINVAL); } if (v->size != N) { GSL_ERROR ("matrix row size and vector length are not equal", GSL_EBADLEN); } { const ATOMIC *v_data = v->data; ATOMIC *row_data = m->data + MULTIPLICITY * i * tda; const size_t stride = v->stride ; size_t j; for (j = 0; j < N; j++) { unsigned int k; for (k = 0; k < MULTIPLICITY; k++) { row_data[MULTIPLICITY*j + k] = v_data[MULTIPLICITY * stride * j + k]; } } } return GSL_SUCCESS; } int FUNCTION (gsl_matrix, set_col) (TYPE (gsl_matrix) * m, const size_t j, const TYPE (gsl_vector) * v) { const size_t M = m->size1; const size_t N = m->size2; const size_t tda = m->tda; if (j >= N) { GSL_ERROR ("column index is out of range", GSL_EINVAL); } if (v->size != M) { GSL_ERROR ("matrix column size and vector length are not equal", GSL_EBADLEN); } { const ATOMIC *v_data = v->data; ATOMIC *column_data = m->data + MULTIPLICITY * j; const size_t stride = v->stride ; size_t i; for (i = 0; i < M; i++) { unsigned int k; for (k = 0; k < MULTIPLICITY; k++) { column_data[MULTIPLICITY * i * tda + k] = v_data[MULTIPLICITY * stride * i + k]; } } } return GSL_SUCCESS; } TYPE (gsl_vector) * FUNCTION (gsl_vector, alloc_row_from_matrix) (TYPE(gsl_matrix) * m, const size_t i) { TYPE (gsl_vector) * v; const size_t M = m->size1; if (i >= M) { GSL_ERROR_VAL ("row index is out of range", GSL_EINVAL, 0); } v = (TYPE (gsl_vector) *) malloc (sizeof (TYPE (gsl_vector))); if (v == 0) { GSL_ERROR_VAL ("failed to allocate space for vector struct", GSL_ENOMEM, 0); } v->data = m->data + MULTIPLICITY * i * m->tda ; v->size = m->size2; v->stride = 1; v->block = 0; return v; } TYPE (gsl_vector) * FUNCTION (gsl_vector, alloc_col_from_matrix) (TYPE(gsl_matrix) * m, const size_t j) { TYPE (gsl_vector) * v; const size_t N = m->size2; if (j >= N) { GSL_ERROR_VAL ("column index is out of range", GSL_EINVAL, 0); } v = (TYPE (gsl_vector) *) malloc (sizeof (TYPE (gsl_vector))); if (v == 0) { GSL_ERROR_VAL ("failed to allocate space for vector struct", GSL_ENOMEM, 0); } v->data = m->data + MULTIPLICITY * j ; v->size = m->size1; v->stride = m->tda; v->block = 0; return v; } sources_5316/external/gsl/gsl_wavelet.h0000664000176700017670000000620311705263724017031 0ustar paulpaul/* wavelet/gsl_wavelet.h * * Copyright (C) 2004 Ivo Alxneit * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_WAVELET_H__ #define __GSL_WAVELET_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS #ifndef GSL_DISABLE_DEPRECATED typedef enum { forward = 1, backward = -1, gsl_wavelet_forward = 1, gsl_wavelet_backward = -1 } gsl_wavelet_direction; #else typedef enum { gsl_wavelet_forward = 1, gsl_wavelet_backward = -1 } gsl_wavelet_direction; #endif typedef struct { const char *name; int (*init) (const double **h1, const double **g1, const double **h2, const double **g2, size_t * nc, size_t * offset, size_t member); } gsl_wavelet_type; typedef struct { const gsl_wavelet_type *type; const double *h1; const double *g1; const double *h2; const double *g2; size_t nc; size_t offset; } gsl_wavelet; typedef struct { double *scratch; size_t n; } gsl_wavelet_workspace; GSL_VAR const gsl_wavelet_type *gsl_wavelet_daubechies; GSL_VAR const gsl_wavelet_type *gsl_wavelet_daubechies_centered; GSL_VAR const gsl_wavelet_type *gsl_wavelet_haar; GSL_VAR const gsl_wavelet_type *gsl_wavelet_haar_centered; GSL_VAR const gsl_wavelet_type *gsl_wavelet_bspline; GSL_VAR const gsl_wavelet_type *gsl_wavelet_bspline_centered; gsl_wavelet *gsl_wavelet_alloc (const gsl_wavelet_type * T, size_t k); void gsl_wavelet_free (gsl_wavelet * w); const char *gsl_wavelet_name (const gsl_wavelet * w); gsl_wavelet_workspace *gsl_wavelet_workspace_alloc (size_t n); void gsl_wavelet_workspace_free (gsl_wavelet_workspace * work); int gsl_wavelet_transform (const gsl_wavelet * w, double *data, size_t stride, size_t n, gsl_wavelet_direction dir, gsl_wavelet_workspace * work); int gsl_wavelet_transform_forward (const gsl_wavelet * w, double *data, size_t stride, size_t n, gsl_wavelet_workspace * work); int gsl_wavelet_transform_inverse (const gsl_wavelet * w, double *data, size_t stride, size_t n, gsl_wavelet_workspace * work); __END_DECLS #endif /* __GSL_WAVELET_H__ */ sources_5316/external/gsl/gsl_eigen__symm.c0000664000176700017670000001114211723710247017643 0ustar paulpaul/* eigen/symm.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_linalg.h" #include "gsl_eigen.h" /* Compute eigenvalues/eigenvectors of real symmetric matrix using reduction to tridiagonal form, followed by QR iteration with implicit shifts. See Golub & Van Loan, "Matrix Computations" (3rd ed), Section 8.3 */ #include "gsl_eigen__qrstep.c" gsl_eigen_symm_workspace * gsl_eigen_symm_alloc (const size_t n) { gsl_eigen_symm_workspace *w; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = ((gsl_eigen_symm_workspace *) malloc (sizeof (gsl_eigen_symm_workspace))); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->d = (double *) malloc (n * sizeof (double)); if (w->d == 0) { GSL_ERROR_NULL ("failed to allocate space for diagonal", GSL_ENOMEM); } w->sd = (double *) malloc (n * sizeof (double)); if (w->sd == 0) { GSL_ERROR_NULL ("failed to allocate space for subdiagonal", GSL_ENOMEM); } w->size = n; return w; } void gsl_eigen_symm_free (gsl_eigen_symm_workspace * w) { free (w->sd); free (w->d); free (w); } int gsl_eigen_symm (gsl_matrix * A, gsl_vector * eval, gsl_eigen_symm_workspace * w) { if (A->size1 != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if (eval->size != A->size1) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else { const size_t N = A->size1; double *const d = w->d; double *const sd = w->sd; size_t a, b; /* handle special case */ if (N == 1) { double A00 = gsl_matrix_get (A, 0, 0); gsl_vector_set (eval, 0, A00); return GSL_SUCCESS; } /* use sd as the temporary workspace for the decomposition, since we can discard the tau result immediately if we are not computing eigenvectors */ { gsl_vector_view d_vec = gsl_vector_view_array (d, N); gsl_vector_view sd_vec = gsl_vector_view_array (sd, N - 1); gsl_vector_view tau = gsl_vector_view_array (sd, N - 1); gsl_linalg_symmtd_decomp (A, &tau.vector); gsl_linalg_symmtd_unpack_T (A, &d_vec.vector, &sd_vec.vector); } /* Make an initial pass through the tridiagonal decomposition to remove off-diagonal elements which are effectively zero */ chop_small_elements (N, d, sd); /* Progressively reduce the matrix until it is diagonal */ b = N - 1; while (b > 0) { if (sd[b - 1] == 0.0 || isnan(sd[b - 1])) { b--; continue; } /* Find the largest unreduced block (a,b) starting from b and working backwards */ a = b - 1; while (a > 0) { if (sd[a - 1] == 0.0) { break; } a--; } { const size_t n_block = b - a + 1; double *d_block = d + a; double *sd_block = sd + a; /* apply QR reduction with implicit deflation to the unreduced block */ qrstep (n_block, d_block, sd_block, NULL, NULL); /* remove any small off-diagonal elements */ chop_small_elements (n_block, d_block, sd_block); } } { gsl_vector_view d_vec = gsl_vector_view_array (d, N); gsl_vector_memcpy (eval, &d_vec.vector); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_vector__swap.c0000664000176700017670000000362611723710247020053 0ustar paulpaul#include "gsl__config.h" #include "gsl_errno.h" #include "gsl_vector.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__swap_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_specfunc__bessel_sequence.c0000664000176700017670000001025411723710247022545 0ustar paulpaul/* specfunc/bessel_sequence.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #define DYDX_p(p,u,x) (-(p)/(x) + (((nu)*(nu))/((x)*(x))-1.0)*(u)) #define DYDX_u(p,u,x) (p) static int rk_step(double nu, double x, double dx, double * Jp, double * J) { double p_0 = *Jp; double u_0 = *J; double p_1 = dx * DYDX_p(p_0, u_0, x); double u_1 = dx * DYDX_u(p_0, u_0, x); double p_2 = dx * DYDX_p(p_0 + 0.5*p_1, u_0 + 0.5*u_1, x + 0.5*dx); double u_2 = dx * DYDX_u(p_0 + 0.5*p_1, u_0 + 0.5*u_1, x + 0.5*dx); double p_3 = dx * DYDX_p(p_0 + 0.5*p_2, u_0 + 0.5*u_2, x + 0.5*dx); double u_3 = dx * DYDX_u(p_0 + 0.5*p_2, u_0 + 0.5*u_2, x + 0.5*dx); double p_4 = dx * DYDX_p(p_0 + p_3, u_0 + u_3, x + dx); double u_4 = dx * DYDX_u(p_0 + p_3, u_0 + u_3, x + dx); *Jp = p_0 + p_1/6.0 + p_2/3.0 + p_3/3.0 + p_4/6.0; *J = u_0 + u_1/6.0 + u_2/3.0 + u_3/3.0 + u_4/6.0; return GSL_SUCCESS; } int gsl_sf_bessel_sequence_Jnu_e(double nu, gsl_mode_t mode, size_t size, double * v) { /* CHECK_POINTER(v) */ if(nu < 0.0) { GSL_ERROR ("domain error", GSL_EDOM); } else if(size == 0) { GSL_ERROR ("error", GSL_EINVAL); } else { const gsl_prec_t goal = GSL_MODE_PREC(mode); const double dx_array[] = { 0.001, 0.03, 0.1 }; /* double, single, approx */ const double dx_nominal = dx_array[goal]; const int cnu = (int) ceil(nu); const double nu13 = pow(nu,1.0/3.0); const double smalls[] = { 0.01, 0.02, 0.4, 0.7, 1.3, 2.0, 2.5, 3.2, 3.5, 4.5, 6.0 }; const double x_small = ( nu >= 10.0 ? nu - nu13 : smalls[cnu] ); gsl_sf_result J0, J1; double Jp, J; double x; size_t i = 0; /* Calculate the first point. */ x = v[0]; gsl_sf_bessel_Jnu_e(nu, x, &J0); v[0] = J0.val; ++i; /* Step over the idiot case where the * first point was actually zero. */ if(x == 0.0) { if(v[1] <= x) { /* Strict ordering failure. */ GSL_ERROR ("error", GSL_EFAILED); } x = v[1]; gsl_sf_bessel_Jnu_e(nu, x, &J0); v[1] = J0.val; ++i; } /* Calculate directly as long as the argument * is small. This is necessary because the * integration is not very good there. */ while(v[i] < x_small && i < size) { if(v[i] <= x) { /* Strict ordering failure. */ GSL_ERROR ("error", GSL_EFAILED); } x = v[i]; gsl_sf_bessel_Jnu_e(nu, x, &J0); v[i] = J0.val; ++i; } /* At this point we are ready to integrate. * The value of x is the last calculated * point, which has the value J0; v[i] is * the next point we need to calculate. We * calculate nu+1 at x as well to get * the derivative, then we go forward. */ gsl_sf_bessel_Jnu_e(nu+1.0, x, &J1); J = J0.val; Jp = -J1.val + nu/x * J0.val; while(i < size) { const double dv = v[i] - x; const int Nd = (int) ceil(dv/dx_nominal); const double dx = dv / Nd; double xj; int j; if(v[i] <= x) { /* Strict ordering failure. */ GSL_ERROR ("error", GSL_EFAILED); } /* Integrate over interval up to next sample point. */ for(j=0, xj=x; j 20) { /* NTERMS IS TOO BIG, MAYBE D1MACH(3) IS BAD */ /* nterms = 20; */ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_ESANITY); } for(k=2; k<=nterms; k++) { double gbk = 0.0; for(j=1; j<=k; j++) { gbk += bern[k-j+1]*gbern[j]; } gbern[k+1] = -rho*gbk/k; term *= (2*k-2-x)*(2*k-1-x)*var2; poly1 += gbern[k+1]*term; } } stat_dexprl = gsl_sf_expm1_e(q, &dexprl); if(stat_dexprl != GSL_SUCCESS) { result->val = 0.0; result->err = 0.0; return stat_dexprl; } dexprl.val = dexprl.val/q; poly1 *= (x - 1.0); dpoch1 = dexprl.val * (alnvar + q * poly1) + poly1; for(i=incr-1; i >= 0; i--) { /* C WE HAVE DPOCH1(B,X), BUT BP IS SMALL, SO WE USE BACKWARDS RECURSION C TO OBTAIN DPOCH1(BP,X). */ double binv = 1.0/(bp+i); dpoch1 = (dpoch1 - binv) / (1.0 + x*binv); } if(bp == a) { result->val = dpoch1; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(incr) + 1.0) * fabs(result->val); return GSL_SUCCESS; } else { /* C WE HAVE DPOCH1(BP,X), BUT A IS LT -0.5. WE THEREFORE USE A C REFLECTION FORMULA TO OBTAIN DPOCH1(A,X). */ double sinpxx = sin(M_PI*x)/x; double sinpx2 = sin(0.5*M_PI*x); double t1 = sinpxx/tan(M_PI*b); double t2 = 2.0*sinpx2*(sinpx2/x); double trig = t1 - t2; result->val = dpoch1 * (1.0 + x*trig) + trig; result->err = (fabs(dpoch1*x) + 1.0) * GSL_DBL_EPSILON * (fabs(t1) + fabs(t2)); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(incr) + 1.0) * fabs(result->val); return GSL_SUCCESS; } } } /* Assumes a>0 and a+x>0. */ static int lnpoch_pos(const double a, const double x, gsl_sf_result * result) { double absx = fabs(x); if(absx > 0.1*a || absx*log(GSL_MAX_DBL(a,2.0)) > 0.1) { if(a < GSL_SF_GAMMA_XMAX && a+x < GSL_SF_GAMMA_XMAX) { /* If we can do it by calculating the gamma functions * directly, then that will be more accurate than * doing the subtraction of the logs. */ gsl_sf_result g1; gsl_sf_result g2; gsl_sf_gammainv_e(a, &g1); gsl_sf_gammainv_e(a+x, &g2); result->val = -log(g2.val/g1.val); result->err = g1.err/fabs(g1.val) + g2.err/fabs(g2.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* Otherwise we must do the subtraction. */ gsl_sf_result lg1; gsl_sf_result lg2; int stat_1 = gsl_sf_lngamma_e(a, &lg1); int stat_2 = gsl_sf_lngamma_e(a+x, &lg2); result->val = lg2.val - lg1.val; result->err = lg2.err + lg1.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_1, stat_2); } } else if(absx < 0.1*a && a > 15.0) { /* Be careful about the implied subtraction. * Note that both a+x and and a must be * large here since a is not small * and x is not relatively large. * So we calculate using Stirling for Log[Gamma(z)]. * * Log[Gamma(a+x)/Gamma(a)] = x(Log[a]-1) + (x+a-1/2)Log[1+x/a] * + (1/(1+eps) - 1) / (12 a) * - (1/(1+eps)^3 - 1) / (360 a^3) * + (1/(1+eps)^5 - 1) / (1260 a^5) * - (1/(1+eps)^7 - 1) / (1680 a^7) * + ... */ const double eps = x/a; const double den = 1.0 + eps; const double d3 = den*den*den; const double d5 = d3*den*den; const double d7 = d5*den*den; const double c1 = -eps/den; const double c3 = -eps*(3.0+eps*(3.0+eps))/d3; const double c5 = -eps*(5.0+eps*(10.0+eps*(10.0+eps*(5.0+eps))))/d5; const double c7 = -eps*(7.0+eps*(21.0+eps*(35.0+eps*(35.0+eps*(21.0+eps*(7.0+eps))))))/d7; const double p8 = gsl_sf_pow_int(1.0+eps,8); const double c8 = 1.0/p8 - 1.0; /* these need not */ const double c9 = 1.0/(p8*(1.0+eps)) - 1.0; /* be very accurate */ const double a4 = a*a*a*a; const double a6 = a4*a*a; const double ser_1 = c1 + c3/(30.0*a*a) + c5/(105.0*a4) + c7/(140.0*a6); const double ser_2 = c8/(99.0*a6*a*a) - 691.0/360360.0 * c9/(a6*a4); const double ser = (ser_1 + ser_2)/ (12.0*a); double term1 = x * log(a/M_E); double term2; gsl_sf_result ln_1peps; gsl_sf_log_1plusx_e(eps, &ln_1peps); /* log(1 + x/a) */ term2 = (x + a - 0.5) * ln_1peps.val; result->val = term1 + term2 + ser; result->err = GSL_DBL_EPSILON*fabs(term1); result->err += fabs((x + a - 0.5)*ln_1peps.err); result->err += fabs(ln_1peps.val) * GSL_DBL_EPSILON * (fabs(x) + fabs(a) + 0.5); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result poch_rel; int stat_p = pochrel_smallx(a, x, &poch_rel); double eps = x*poch_rel.val; int stat_e = gsl_sf_log_1plusx_e(eps, result); result->err = 2.0 * fabs(x * poch_rel.err / (1.0 + eps)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_e, stat_p); } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_lnpoch_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(a <= 0.0 || a+x <= 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { return lnpoch_pos(a, x, result); } } int gsl_sf_lnpoch_sgn_e(const double a, const double x, gsl_sf_result * result, double * sgn) { if(a == 0.0 || a+x == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result); } else if(x == 0.0) { *sgn = 1.0; result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(a > 0.0 && a+x > 0.0) { *sgn = 1.0; return lnpoch_pos(a, x, result); } else if(a < 0.0 && a+x < 0.0) { /* Reduce to positive case using reflection. */ double sin_1 = sin(M_PI * (1.0 - a)); double sin_2 = sin(M_PI * (1.0 - a - x)); if(sin_1 == 0.0 || sin_2 == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result); } else { gsl_sf_result lnp_pos; int stat_pp = lnpoch_pos(1.0-a, -x, &lnp_pos); double lnterm = log(fabs(sin_1/sin_2)); result->val = lnterm - lnp_pos.val; result->err = lnp_pos.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(1.0-a) + fabs(1.0-a-x)) * fabs(lnterm); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *sgn = GSL_SIGN(sin_1*sin_2); return stat_pp; } } else { /* Evaluate gamma ratio directly. */ gsl_sf_result lg_apn; gsl_sf_result lg_a; double s_apn, s_a; int stat_apn = gsl_sf_lngamma_sgn_e(a+x, &lg_apn, &s_apn); int stat_a = gsl_sf_lngamma_sgn_e(a, &lg_a, &s_a); if(stat_apn == GSL_SUCCESS && stat_a == GSL_SUCCESS) { result->val = lg_apn.val - lg_a.val; result->err = lg_apn.err + lg_a.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *sgn = s_a * s_apn; return GSL_SUCCESS; } else if(stat_apn == GSL_EDOM || stat_a == GSL_EDOM){ *sgn = 0.0; DOMAIN_ERROR(result); } else { result->val = 0.0; result->err = 0.0; *sgn = 0.0; return GSL_FAILURE; } } } int gsl_sf_poch_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result lnpoch; double sgn; int stat_lnpoch = gsl_sf_lnpoch_sgn_e(a, x, &lnpoch, &sgn); int stat_exp = gsl_sf_exp_err_e(lnpoch.val, lnpoch.err, result); result->val *= sgn; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_exp, stat_lnpoch); } } int gsl_sf_pochrel_e(const double a, const double x, gsl_sf_result * result) { const double absx = fabs(x); const double absa = fabs(a); /* CHECK_POINTER(result) */ if(absx > 0.1*absa || absx*log(GSL_MAX(absa,2.0)) > 0.1) { gsl_sf_result lnpoch; double sgn; int stat_poch = gsl_sf_lnpoch_sgn_e(a, x, &lnpoch, &sgn); if(lnpoch.val > GSL_LOG_DBL_MAX) { OVERFLOW_ERROR(result); } else { const double el = exp(lnpoch.val); result->val = (sgn*el - 1.0)/x; result->err = fabs(result->val) * (lnpoch.err + 2.0 * GSL_DBL_EPSILON); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(sgn*el) + 1.0) / fabs(x); return stat_poch; } } else { return pochrel_smallx(a, x, result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_lnpoch(const double a, const double x) { EVAL_RESULT(gsl_sf_lnpoch_e(a, x, &result)); } double gsl_sf_poch(const double a, const double x) { EVAL_RESULT(gsl_sf_poch_e(a, x, &result)); } double gsl_sf_pochrel(const double a, const double x) { EVAL_RESULT(gsl_sf_pochrel_e(a, x, &result)); } sources_5316/external/gsl/gsl_statistics__minmax_source.c0000664000176700017670000001021611723710247022633 0ustar paulpaul/* statistics/minmax_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ BASE FUNCTION (gsl_stats,max) (const BASE data[], const size_t stride, const size_t n) { /* finds the largest member of a dataset */ BASE max = data[0 * stride]; size_t i; for (i = 0; i < n; i++) { BASE xi = data[i * stride]; if (xi > max) max = xi; #ifdef FP if (isnan (xi)) return xi; #endif } return max; } BASE FUNCTION (gsl_stats,min) (const BASE data[], const size_t stride, const size_t n) { /* finds the smallest member of a dataset */ BASE min = data[0 * stride]; size_t i; for (i = 0; i < n; i++) { BASE xi = data[i * stride]; if (xi < min) min = xi; #ifdef FP if (isnan (xi)) return xi; #endif } return min; } void FUNCTION (gsl_stats,minmax) (BASE * min_out, BASE * max_out, const BASE data[], const size_t stride, const size_t n) { /* finds the smallest and largest members of a dataset */ BASE min = data[0 * stride]; BASE max = data[0 * stride]; size_t i; for (i = 0; i < n; i++) { BASE xi = data[i * stride]; if (xi < min) min = xi; if (xi > max) max = xi; #ifdef FP if (isnan (xi)) { min = xi; max = xi; break; } #endif } *min_out = min; *max_out = max; } size_t FUNCTION (gsl_stats,max_index) (const BASE data[], const size_t stride, const size_t n) { /* finds the index of the largest member of a dataset */ /* if there is more than one largest value then we choose the first */ BASE max = data[0 * stride]; size_t i, max_index = 0; for (i = 0; i < n; i++) { BASE xi = data[i * stride]; if (xi > max) { max = xi; max_index = i; } #ifdef FP if (isnan (xi)) { return i; } #endif } return max_index; } size_t FUNCTION (gsl_stats,min_index) (const BASE data[], const size_t stride, const size_t n) { /* finds the index of the smallest member of a dataset */ /* if there is more than one largest value then we choose the first */ BASE min = data[0 * stride]; size_t i, min_index = 0; for (i = 0; i < n; i++) { BASE xi = data[i * stride]; if (xi < min) { min = xi; min_index = i; } #ifdef FP if (isnan (xi)) { return i; } #endif } return min_index; } void FUNCTION (gsl_stats,minmax_index) (size_t * min_index_out, size_t * max_index_out, const BASE data[], const size_t stride, const size_t n) { /* finds the smallest and largest members of a dataset */ BASE min = data[0 * stride]; BASE max = data[0 * stride]; size_t i, min_index = 0, max_index = 0; for (i = 0; i < n; i++) { BASE xi = data[i * stride]; if (xi < min) { min = xi; min_index = i; } if (xi > max) { max = xi; max_index = i; } #ifdef FP if (isnan (xi)) { min_index = i; max_index = i; break; } #endif } *min_index_out = min_index; *max_index_out = max_index; } sources_5316/external/gsl/gsl_matrix_ulong.h0000664000176700017670000002723011705263724020075 0ustar paulpaul/* matrix/gsl_matrix_ulong.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_ULONG_H__ #define __GSL_MATRIX_ULONG_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_ulong.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; unsigned long * data; gsl_block_ulong * block; int owner; } gsl_matrix_ulong; typedef struct { gsl_matrix_ulong matrix; } _gsl_matrix_ulong_view; typedef _gsl_matrix_ulong_view gsl_matrix_ulong_view; typedef struct { gsl_matrix_ulong matrix; } _gsl_matrix_ulong_const_view; typedef const _gsl_matrix_ulong_const_view gsl_matrix_ulong_const_view; /* Allocation */ gsl_matrix_ulong * gsl_matrix_ulong_alloc (const size_t n1, const size_t n2); gsl_matrix_ulong * gsl_matrix_ulong_calloc (const size_t n1, const size_t n2); gsl_matrix_ulong * gsl_matrix_ulong_alloc_from_block (gsl_block_ulong * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_ulong * gsl_matrix_ulong_alloc_from_matrix (gsl_matrix_ulong * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_ulong * gsl_vector_ulong_alloc_row_from_matrix (gsl_matrix_ulong * m, const size_t i); gsl_vector_ulong * gsl_vector_ulong_alloc_col_from_matrix (gsl_matrix_ulong * m, const size_t j); void gsl_matrix_ulong_free (gsl_matrix_ulong * m); /* Views */ _gsl_matrix_ulong_view gsl_matrix_ulong_submatrix (gsl_matrix_ulong * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_ulong_view gsl_matrix_ulong_row (gsl_matrix_ulong * m, const size_t i); _gsl_vector_ulong_view gsl_matrix_ulong_column (gsl_matrix_ulong * m, const size_t j); _gsl_vector_ulong_view gsl_matrix_ulong_diagonal (gsl_matrix_ulong * m); _gsl_vector_ulong_view gsl_matrix_ulong_subdiagonal (gsl_matrix_ulong * m, const size_t k); _gsl_vector_ulong_view gsl_matrix_ulong_superdiagonal (gsl_matrix_ulong * m, const size_t k); _gsl_vector_ulong_view gsl_matrix_ulong_subrow (gsl_matrix_ulong * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_ulong_view gsl_matrix_ulong_subcolumn (gsl_matrix_ulong * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_ulong_view gsl_matrix_ulong_view_array (unsigned long * base, const size_t n1, const size_t n2); _gsl_matrix_ulong_view gsl_matrix_ulong_view_array_with_tda (unsigned long * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_ulong_view gsl_matrix_ulong_view_vector (gsl_vector_ulong * v, const size_t n1, const size_t n2); _gsl_matrix_ulong_view gsl_matrix_ulong_view_vector_with_tda (gsl_vector_ulong * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_ulong_const_view gsl_matrix_ulong_const_submatrix (const gsl_matrix_ulong * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_ulong_const_view gsl_matrix_ulong_const_row (const gsl_matrix_ulong * m, const size_t i); _gsl_vector_ulong_const_view gsl_matrix_ulong_const_column (const gsl_matrix_ulong * m, const size_t j); _gsl_vector_ulong_const_view gsl_matrix_ulong_const_diagonal (const gsl_matrix_ulong * m); _gsl_vector_ulong_const_view gsl_matrix_ulong_const_subdiagonal (const gsl_matrix_ulong * m, const size_t k); _gsl_vector_ulong_const_view gsl_matrix_ulong_const_superdiagonal (const gsl_matrix_ulong * m, const size_t k); _gsl_vector_ulong_const_view gsl_matrix_ulong_const_subrow (const gsl_matrix_ulong * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_ulong_const_view gsl_matrix_ulong_const_subcolumn (const gsl_matrix_ulong * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_ulong_const_view gsl_matrix_ulong_const_view_array (const unsigned long * base, const size_t n1, const size_t n2); _gsl_matrix_ulong_const_view gsl_matrix_ulong_const_view_array_with_tda (const unsigned long * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_ulong_const_view gsl_matrix_ulong_const_view_vector (const gsl_vector_ulong * v, const size_t n1, const size_t n2); _gsl_matrix_ulong_const_view gsl_matrix_ulong_const_view_vector_with_tda (const gsl_vector_ulong * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ unsigned long gsl_matrix_ulong_get(const gsl_matrix_ulong * m, const size_t i, const size_t j); void gsl_matrix_ulong_set(gsl_matrix_ulong * m, const size_t i, const size_t j, const unsigned long x); unsigned long * gsl_matrix_ulong_ptr(gsl_matrix_ulong * m, const size_t i, const size_t j); const unsigned long * gsl_matrix_ulong_const_ptr(const gsl_matrix_ulong * m, const size_t i, const size_t j); void gsl_matrix_ulong_set_zero (gsl_matrix_ulong * m); void gsl_matrix_ulong_set_identity (gsl_matrix_ulong * m); void gsl_matrix_ulong_set_all (gsl_matrix_ulong * m, unsigned long x); int gsl_matrix_ulong_fread (FILE * stream, gsl_matrix_ulong * m) ; int gsl_matrix_ulong_fwrite (FILE * stream, const gsl_matrix_ulong * m) ; int gsl_matrix_ulong_fscanf (FILE * stream, gsl_matrix_ulong * m); int gsl_matrix_ulong_fprintf (FILE * stream, const gsl_matrix_ulong * m, const char * format); int gsl_matrix_ulong_memcpy(gsl_matrix_ulong * dest, const gsl_matrix_ulong * src); int gsl_matrix_ulong_swap(gsl_matrix_ulong * m1, gsl_matrix_ulong * m2); int gsl_matrix_ulong_swap_rows(gsl_matrix_ulong * m, const size_t i, const size_t j); int gsl_matrix_ulong_swap_columns(gsl_matrix_ulong * m, const size_t i, const size_t j); int gsl_matrix_ulong_swap_rowcol(gsl_matrix_ulong * m, const size_t i, const size_t j); int gsl_matrix_ulong_transpose (gsl_matrix_ulong * m); int gsl_matrix_ulong_transpose_memcpy (gsl_matrix_ulong * dest, const gsl_matrix_ulong * src); unsigned long gsl_matrix_ulong_max (const gsl_matrix_ulong * m); unsigned long gsl_matrix_ulong_min (const gsl_matrix_ulong * m); void gsl_matrix_ulong_minmax (const gsl_matrix_ulong * m, unsigned long * min_out, unsigned long * max_out); void gsl_matrix_ulong_max_index (const gsl_matrix_ulong * m, size_t * imax, size_t *jmax); void gsl_matrix_ulong_min_index (const gsl_matrix_ulong * m, size_t * imin, size_t *jmin); void gsl_matrix_ulong_minmax_index (const gsl_matrix_ulong * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_ulong_isnull (const gsl_matrix_ulong * m); int gsl_matrix_ulong_ispos (const gsl_matrix_ulong * m); int gsl_matrix_ulong_isneg (const gsl_matrix_ulong * m); int gsl_matrix_ulong_isnonneg (const gsl_matrix_ulong * m); int gsl_matrix_ulong_add (gsl_matrix_ulong * a, const gsl_matrix_ulong * b); int gsl_matrix_ulong_sub (gsl_matrix_ulong * a, const gsl_matrix_ulong * b); int gsl_matrix_ulong_mul_elements (gsl_matrix_ulong * a, const gsl_matrix_ulong * b); int gsl_matrix_ulong_div_elements (gsl_matrix_ulong * a, const gsl_matrix_ulong * b); int gsl_matrix_ulong_scale (gsl_matrix_ulong * a, const double x); int gsl_matrix_ulong_add_constant (gsl_matrix_ulong * a, const double x); int gsl_matrix_ulong_add_diagonal (gsl_matrix_ulong * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_ulong_get_row(gsl_vector_ulong * v, const gsl_matrix_ulong * m, const size_t i); int gsl_matrix_ulong_get_col(gsl_vector_ulong * v, const gsl_matrix_ulong * m, const size_t j); int gsl_matrix_ulong_set_row(gsl_matrix_ulong * m, const size_t i, const gsl_vector_ulong * v); int gsl_matrix_ulong_set_col(gsl_matrix_ulong * m, const size_t j, const gsl_vector_ulong * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline unsigned long gsl_matrix_ulong_get(const gsl_matrix_ulong * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_ulong_set(gsl_matrix_ulong * m, const size_t i, const size_t j, const unsigned long x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline unsigned long * gsl_matrix_ulong_ptr(gsl_matrix_ulong * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (unsigned long *) (m->data + (i * m->tda + j)) ; } extern inline const unsigned long * gsl_matrix_ulong_const_ptr(const gsl_matrix_ulong * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const unsigned long *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_ULONG_H__ */ sources_5316/external/gsl/gsl_cblas__dsyrk.c0000664000176700017670000000064611723710247020016 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dsyrk (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const double alpha, const double *A, const int lda, const double beta, double *C, const int ldc) { #define BASE double #include "gsl_cblas__source_syrk_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__zaxpy.c0000664000176700017670000000041511723710247020027 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zaxpy (const int N, const void *alpha, const void *X, const int incX, void *Y, const int incY) { #define BASE double #include "gsl_cblas__source_axpy_c.h" #undef BASE } sources_5316/external/gsl/gsl_randist__shuffle.c0000664000176700017670000000672011723710247020675 0ustar paulpaul/* randist/shuffle.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_rng.h" #include "gsl_randist.h" /* Inline swap and copy functions for moving objects around */ static inline void swap (void * base, size_t size, size_t i, size_t j) { register char * a = size * i + (char *) base ; register char * b = size * j + (char *) base ; register size_t s = size ; if (i == j) return ; do { char tmp = *a; *a++ = *b; *b++ = tmp; } while (--s > 0); } static inline void copy (void * dest, size_t i, void * src, size_t j, size_t size) { register char * a = size * i + (char *) dest ; register char * b = size * j + (char *) src ; register size_t s = size ; do { *a++ = *b++; } while (--s > 0); } /* Randomly permute (shuffle) N indices Supply an array x[N] with nmemb members, each of size size and on return it will be shuffled into a random order. The algorithm is from Knuth, SemiNumerical Algorithms, v2, p139, who cites Moses and Oakford, and Durstenfeld */ void gsl_ran_shuffle (const gsl_rng * r, void * base, size_t n, size_t size) { size_t i ; for (i = n - 1; i > 0; i--) { size_t j = gsl_rng_uniform_int(r, i+1); /* originally (i + 1) * gsl_rng_uniform (r) */ swap (base, size, i, j) ; } } int gsl_ran_choose (const gsl_rng * r, void * dest, size_t k, void * src, size_t n, size_t size) { size_t i, j = 0; /* Choose k out of n items, return an array x[] of the k items. These items will prevserve the relative order of the original input -- you can use shuffle() to randomize the output if you wish */ if (k > n) { GSL_ERROR ("k is greater than n, cannot sample more than n items", GSL_EINVAL) ; } for (i = 0; i < n && j < k; i++) { if ((n - i) * gsl_rng_uniform (r) < k - j) { copy (dest, j, src, i, size) ; j++ ; } } return GSL_SUCCESS; } void gsl_ran_sample (const gsl_rng * r, void * dest, size_t k, void * src, size_t n, size_t size) { size_t i, j = 0; /* Choose k out of n items, with replacement */ for (i = 0; i < k; i++) { j = gsl_rng_uniform_int (r, n); /* originally n * gsl_rng_uniform (r) */ copy (dest, i, src, j, size) ; } } sources_5316/external/gsl/gsl_const_cgs.h0000664000176700017670000001503111705263724017343 0ustar paulpaul/* const/gsl_const_cgs.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, * 2006 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_CONST_CGS__ #define __GSL_CONST_CGS__ #define GSL_CONST_CGS_SPEED_OF_LIGHT (2.99792458e10) /* cm / s */ #define GSL_CONST_CGS_GRAVITATIONAL_CONSTANT (6.673e-8) /* cm^3 / g s^2 */ #define GSL_CONST_CGS_PLANCKS_CONSTANT_H (6.62606876e-27) /* g cm^2 / s */ #define GSL_CONST_CGS_PLANCKS_CONSTANT_HBAR (1.05457159642e-27) /* g cm^2 / s */ #define GSL_CONST_CGS_ASTRONOMICAL_UNIT (1.49597870691e13) /* cm */ #define GSL_CONST_CGS_LIGHT_YEAR (9.46053620707e17) /* cm */ #define GSL_CONST_CGS_PARSEC (3.08567758135e18) /* cm */ #define GSL_CONST_CGS_GRAV_ACCEL (9.80665e2) /* cm / s^2 */ #define GSL_CONST_CGS_ELECTRON_VOLT (1.602176462e-12) /* g cm^2 / s^2 */ #define GSL_CONST_CGS_MASS_ELECTRON (9.10938188e-28) /* g */ #define GSL_CONST_CGS_MASS_MUON (1.88353109e-25) /* g */ #define GSL_CONST_CGS_MASS_PROTON (1.67262158e-24) /* g */ #define GSL_CONST_CGS_MASS_NEUTRON (1.67492716e-24) /* g */ #define GSL_CONST_CGS_RYDBERG (2.17987190389e-11) /* g cm^2 / s^2 */ #define GSL_CONST_CGS_BOLTZMANN (1.3806503e-16) /* g cm^2 / K s^2 */ #define GSL_CONST_CGS_BOHR_MAGNETON (9.27400899e-20) /* A cm^2 */ #define GSL_CONST_CGS_NUCLEAR_MAGNETON (5.05078317e-23) /* A cm^2 */ #define GSL_CONST_CGS_ELECTRON_MAGNETIC_MOMENT (9.28476362e-20) /* A cm^2 */ #define GSL_CONST_CGS_PROTON_MAGNETIC_MOMENT (1.410606633e-22) /* A cm^2 */ #define GSL_CONST_CGS_MOLAR_GAS (8.314472e7) /* g cm^2 / K mol s^2 */ #define GSL_CONST_CGS_STANDARD_GAS_VOLUME (2.2710981e4) /* cm^3 / mol */ #define GSL_CONST_CGS_MINUTE (6e1) /* s */ #define GSL_CONST_CGS_HOUR (3.6e3) /* s */ #define GSL_CONST_CGS_DAY (8.64e4) /* s */ #define GSL_CONST_CGS_WEEK (6.048e5) /* s */ #define GSL_CONST_CGS_INCH (2.54e0) /* cm */ #define GSL_CONST_CGS_FOOT (3.048e1) /* cm */ #define GSL_CONST_CGS_YARD (9.144e1) /* cm */ #define GSL_CONST_CGS_MILE (1.609344e5) /* cm */ #define GSL_CONST_CGS_NAUTICAL_MILE (1.852e5) /* cm */ #define GSL_CONST_CGS_FATHOM (1.8288e2) /* cm */ #define GSL_CONST_CGS_MIL (2.54e-3) /* cm */ #define GSL_CONST_CGS_POINT (3.52777777778e-2) /* cm */ #define GSL_CONST_CGS_TEXPOINT (3.51459803515e-2) /* cm */ #define GSL_CONST_CGS_MICRON (1e-4) /* cm */ #define GSL_CONST_CGS_ANGSTROM (1e-8) /* cm */ #define GSL_CONST_CGS_HECTARE (1e8) /* cm^2 */ #define GSL_CONST_CGS_ACRE (4.04685642241e7) /* cm^2 */ #define GSL_CONST_CGS_BARN (1e-24) /* cm^2 */ #define GSL_CONST_CGS_LITER (1e3) /* cm^3 */ #define GSL_CONST_CGS_US_GALLON (3.78541178402e3) /* cm^3 */ #define GSL_CONST_CGS_QUART (9.46352946004e2) /* cm^3 */ #define GSL_CONST_CGS_PINT (4.73176473002e2) /* cm^3 */ #define GSL_CONST_CGS_CUP (2.36588236501e2) /* cm^3 */ #define GSL_CONST_CGS_FLUID_OUNCE (2.95735295626e1) /* cm^3 */ #define GSL_CONST_CGS_TABLESPOON (1.47867647813e1) /* cm^3 */ #define GSL_CONST_CGS_TEASPOON (4.92892159375e0) /* cm^3 */ #define GSL_CONST_CGS_CANADIAN_GALLON (4.54609e3) /* cm^3 */ #define GSL_CONST_CGS_UK_GALLON (4.546092e3) /* cm^3 */ #define GSL_CONST_CGS_MILES_PER_HOUR (4.4704e1) /* cm / s */ #define GSL_CONST_CGS_KILOMETERS_PER_HOUR (2.77777777778e1) /* cm / s */ #define GSL_CONST_CGS_KNOT (5.14444444444e1) /* cm / s */ #define GSL_CONST_CGS_POUND_MASS (4.5359237e2) /* g */ #define GSL_CONST_CGS_OUNCE_MASS (2.8349523125e1) /* g */ #define GSL_CONST_CGS_TON (9.0718474e5) /* g */ #define GSL_CONST_CGS_METRIC_TON (1e6) /* g */ #define GSL_CONST_CGS_UK_TON (1.0160469088e6) /* g */ #define GSL_CONST_CGS_TROY_OUNCE (3.1103475e1) /* g */ #define GSL_CONST_CGS_CARAT (2e-1) /* g */ #define GSL_CONST_CGS_UNIFIED_ATOMIC_MASS (1.66053873e-24) /* g */ #define GSL_CONST_CGS_GRAM_FORCE (9.80665e2) /* cm g / s^2 */ #define GSL_CONST_CGS_POUND_FORCE (4.44822161526e5) /* cm g / s^2 */ #define GSL_CONST_CGS_KILOPOUND_FORCE (4.44822161526e8) /* cm g / s^2 */ #define GSL_CONST_CGS_POUNDAL (1.38255e4) /* cm g / s^2 */ #define GSL_CONST_CGS_CALORIE (4.1868e7) /* g cm^2 / s^2 */ #define GSL_CONST_CGS_BTU (1.05505585262e10) /* g cm^2 / s^2 */ #define GSL_CONST_CGS_THERM (1.05506e15) /* g cm^2 / s^2 */ #define GSL_CONST_CGS_HORSEPOWER (7.457e9) /* g cm^2 / s^3 */ #define GSL_CONST_CGS_BAR (1e6) /* g / cm s^2 */ #define GSL_CONST_CGS_STD_ATMOSPHERE (1.01325e6) /* g / cm s^2 */ #define GSL_CONST_CGS_TORR (1.33322368421e3) /* g / cm s^2 */ #define GSL_CONST_CGS_METER_OF_MERCURY (1.33322368421e6) /* g / cm s^2 */ #define GSL_CONST_CGS_INCH_OF_MERCURY (3.38638815789e4) /* g / cm s^2 */ #define GSL_CONST_CGS_INCH_OF_WATER (2.490889e3) /* g / cm s^2 */ #define GSL_CONST_CGS_PSI (6.89475729317e4) /* g / cm s^2 */ #define GSL_CONST_CGS_POISE (1e0) /* g / cm s */ #define GSL_CONST_CGS_STOKES (1e0) /* cm^2 / s */ #define GSL_CONST_CGS_FARADAY (9.6485341472e4) /* A s / mol */ #define GSL_CONST_CGS_ELECTRON_CHARGE (1.602176462e-19) /* A s */ #define GSL_CONST_CGS_GAUSS (1e-1) /* g / A s^2 */ #define GSL_CONST_CGS_STILB (1e0) /* cd / cm^2 */ #define GSL_CONST_CGS_LUMEN (1e0) /* cd sr */ #define GSL_CONST_CGS_LUX (1e-4) /* cd sr / cm^2 */ #define GSL_CONST_CGS_PHOT (1e0) /* cd sr / cm^2 */ #define GSL_CONST_CGS_FOOTCANDLE (1.076e-3) /* cd sr / cm^2 */ #define GSL_CONST_CGS_LAMBERT (1e0) /* cd sr / cm^2 */ #define GSL_CONST_CGS_FOOTLAMBERT (1.07639104e-3) /* cd sr / cm^2 */ #define GSL_CONST_CGS_CURIE (3.7e10) /* 1 / s */ #define GSL_CONST_CGS_ROENTGEN (2.58e-7) /* A s / g */ #define GSL_CONST_CGS_RAD (1e2) /* cm^2 / s^2 */ #define GSL_CONST_CGS_SOLAR_MASS (1.98892e33) /* g */ #define GSL_CONST_CGS_BOHR_RADIUS (5.291772083e-9) /* cm */ #define GSL_CONST_CGS_NEWTON (1e5) /* cm g / s^2 */ #define GSL_CONST_CGS_DYNE (1e0) /* cm g / s^2 */ #define GSL_CONST_CGS_JOULE (1e7) /* g cm^2 / s^2 */ #define GSL_CONST_CGS_ERG (1e0) /* g cm^2 / s^2 */ #define GSL_CONST_CGS_STEFAN_BOLTZMANN_CONSTANT (5.67039934436e-5) /* g / K^4 s^3 */ #define GSL_CONST_CGS_THOMSON_CROSS_SECTION (6.65245853542e-25) /* cm^2 */ #endif /* __GSL_CONST_CGS__ */ sources_5316/external/gsl/gsl_statistics_ulong.h0000664000176700017670000001114411705263724020760 0ustar paulpaul/* statistics/gsl_statistics_ulong.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_ULONG_H__ #define __GSL_STATISTICS_ULONG_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_ulong_mean (const unsigned long data[], const size_t stride, const size_t n); double gsl_stats_ulong_variance (const unsigned long data[], const size_t stride, const size_t n); double gsl_stats_ulong_sd (const unsigned long data[], const size_t stride, const size_t n); double gsl_stats_ulong_variance_with_fixed_mean (const unsigned long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ulong_sd_with_fixed_mean (const unsigned long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ulong_absdev (const unsigned long data[], const size_t stride, const size_t n); double gsl_stats_ulong_skew (const unsigned long data[], const size_t stride, const size_t n); double gsl_stats_ulong_kurtosis (const unsigned long data[], const size_t stride, const size_t n); double gsl_stats_ulong_lag1_autocorrelation (const unsigned long data[], const size_t stride, const size_t n); double gsl_stats_ulong_covariance (const unsigned long data1[], const size_t stride1,const unsigned long data2[], const size_t stride2, const size_t n); double gsl_stats_ulong_correlation (const unsigned long data1[], const size_t stride1,const unsigned long data2[], const size_t stride2, const size_t n); double gsl_stats_ulong_variance_m (const unsigned long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ulong_sd_m (const unsigned long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ulong_absdev_m (const unsigned long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ulong_skew_m_sd (const unsigned long data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_ulong_kurtosis_m_sd (const unsigned long data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_ulong_lag1_autocorrelation_m (const unsigned long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_ulong_covariance_m (const unsigned long data1[], const size_t stride1,const unsigned long data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); double gsl_stats_ulong_pvariance (const unsigned long data1[], const size_t stride1, const size_t n1, const unsigned long data2[], const size_t stride2, const size_t n2); double gsl_stats_ulong_ttest (const unsigned long data1[], const size_t stride1, const size_t n1, const unsigned long data2[], const size_t stride2, const size_t n2); unsigned long gsl_stats_ulong_max (const unsigned long data[], const size_t stride, const size_t n); unsigned long gsl_stats_ulong_min (const unsigned long data[], const size_t stride, const size_t n); void gsl_stats_ulong_minmax (unsigned long * min, unsigned long * max, const unsigned long data[], const size_t stride, const size_t n); size_t gsl_stats_ulong_max_index (const unsigned long data[], const size_t stride, const size_t n); size_t gsl_stats_ulong_min_index (const unsigned long data[], const size_t stride, const size_t n); void gsl_stats_ulong_minmax_index (size_t * min_index, size_t * max_index, const unsigned long data[], const size_t stride, const size_t n); double gsl_stats_ulong_median_from_sorted_data (const unsigned long sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_ulong_quantile_from_sorted_data (const unsigned long sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_ULONG_H__ */ sources_5316/external/gsl/gsl_cdf__gaussinv.c0000664000176700017670000001004411723710247020162 0ustar paulpaul/* cdf/inverse_normal.c * * Copyright (C) 2002 Przemyslaw Sliwa and Jason H. Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * Computes the inverse normal cumulative distribution function * according to the algorithm shown in * * Wichura, M.J. (1988). * Algorithm AS 241: The Percentage Points of the Normal Distribution. * Applied Statistics, 37, 477-484. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_math.h" #include "gsl_cdf.h" #include "gsl_cdf__rat_eval.h" static double small (double q) { const double a[8] = { 3.387132872796366608, 133.14166789178437745, 1971.5909503065514427, 13731.693765509461125, 45921.953931549871457, 67265.770927008700853, 33430.575583588128105, 2509.0809287301226727 }; const double b[8] = { 1.0, 42.313330701600911252, 687.1870074920579083, 5394.1960214247511077, 21213.794301586595867, 39307.89580009271061, 28729.085735721942674, 5226.495278852854561 }; double r = 0.180625 - q * q; double x = q * rat_eval (a, 8, b, 8, r); return x; } static double intermediate (double r) { const double a[] = { 1.42343711074968357734, 4.6303378461565452959, 5.7694972214606914055, 3.64784832476320460504, 1.27045825245236838258, 0.24178072517745061177, 0.0227238449892691845833, 7.7454501427834140764e-4 }; const double b[] = { 1.0, 2.05319162663775882187, 1.6763848301838038494, 0.68976733498510000455, 0.14810397642748007459, 0.0151986665636164571966, 5.475938084995344946e-4, 1.05075007164441684324e-9 }; double x = rat_eval (a, 8, b, 8, (r - 1.6)); return x; } static double tail (double r) { const double a[] = { 6.6579046435011037772, 5.4637849111641143699, 1.7848265399172913358, 0.29656057182850489123, 0.026532189526576123093, 0.0012426609473880784386, 2.71155556874348757815e-5, 2.01033439929228813265e-7 }; const double b[] = { 1.0, 0.59983220655588793769, 0.13692988092273580531, 0.0148753612908506148525, 7.868691311456132591e-4, 1.8463183175100546818e-5, 1.4215117583164458887e-7, 2.04426310338993978564e-15 }; double x = rat_eval (a, 8, b, 8, (r - 5.0)); return x; } double gsl_cdf_ugaussian_Pinv (const double P) { double r, x, pp; double dP = P - 0.5; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return GSL_NEGINF; } if (fabs (dP) <= 0.425) { x = small (dP); return x; } pp = (P < 0.5) ? P : 1.0 - P; r = sqrt (-log (pp)); if (r <= 5.0) { x = intermediate (r); } else { x = tail (r); } if (P < 0.5) { return -x; } else { return x; } } double gsl_cdf_ugaussian_Qinv (const double Q) { double r, x, pp; double dQ = Q - 0.5; if (Q == 1.0) { return GSL_NEGINF; } else if (Q == 0.0) { return GSL_POSINF; } if (fabs (dQ) <= 0.425) { x = small (dQ); return -x; } pp = (Q < 0.5) ? Q : 1.0 - Q; r = sqrt (-log (pp)); if (r <= 5.0) { x = intermediate (r); } else { x = tail (r); } if (Q < 0.5) { return x; } else { return -x; } } double gsl_cdf_gaussian_Pinv (const double P, const double sigma) { return sigma * gsl_cdf_ugaussian_Pinv (P); } double gsl_cdf_gaussian_Qinv (const double Q, const double sigma) { return sigma * gsl_cdf_ugaussian_Qinv (Q); } sources_5316/external/gsl/gsl_linalg__svdstep.c0000664000176700017670000003006611723710247020533 0ustar paulpaul/* linalg/svdstep.c * * Copyright (C) 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void chop_small_elements (gsl_vector * d, gsl_vector * f) { const size_t N = d->size; double d_i = gsl_vector_get (d, 0); size_t i; for (i = 0; i < N - 1; i++) { double f_i = gsl_vector_get (f, i); double d_ip1 = gsl_vector_get (d, i + 1); if (fabs (f_i) < GSL_DBL_EPSILON * (fabs (d_i) + fabs (d_ip1))) { gsl_vector_set (f, i, 0.0); } d_i = d_ip1; } } static double trailing_eigenvalue (const gsl_vector * d, const gsl_vector * f) { const size_t n = d->size; double da = gsl_vector_get (d, n - 2); double db = gsl_vector_get (d, n - 1); double fa = (n > 2) ? gsl_vector_get (f, n - 3) : 0.0; double fb = gsl_vector_get (f, n - 2); double ta = da * da + fa * fa; double tb = db * db + fb * fb; double tab = da * fb; double dt = (ta - tb) / 2.0; double mu; if (dt >= 0) { mu = tb - (tab * tab) / (dt + hypot (dt, tab)); } else { mu = tb + (tab * tab) / ((-dt) + hypot (dt, tab)); } return mu; } static void create_schur (double d0, double f0, double d1, double * c, double * s) { double apq = 2.0 * d0 * f0; if (d0 == 0 || f0 == 0) { *c = 1.0; *s = 0.0; return; } /* Check if we need to rescale to avoid underflow/overflow */ if (fabs(d0) < GSL_SQRT_DBL_MIN || fabs(d0) > GSL_SQRT_DBL_MAX || fabs(f0) < GSL_SQRT_DBL_MIN || fabs(f0) > GSL_SQRT_DBL_MAX || fabs(d1) < GSL_SQRT_DBL_MIN || fabs(d1) > GSL_SQRT_DBL_MAX) { double scale; int d0_exp, f0_exp; frexp(d0, &d0_exp); frexp(f0, &f0_exp); /* Bring |d0*f0| into the range GSL_DBL_MIN to GSL_DBL_MAX */ scale = ldexp(1.0, -(d0_exp + f0_exp)/4); d0 *= scale; f0 *= scale; d1 *= scale; apq = 2.0 * d0 * f0; } if (apq != 0.0) { double t; double tau = (f0*f0 + (d1 + d0)*(d1 - d0)) / apq; if (tau >= 0.0) { t = 1.0/(tau + hypot(1.0, tau)); } else { t = -1.0/(-tau + hypot(1.0, tau)); } *c = 1.0 / hypot(1.0, t); *s = t * (*c); } else { *c = 1.0; *s = 0.0; } } static void svd2 (gsl_vector * d, gsl_vector * f, gsl_matrix * U, gsl_matrix * V) { size_t i; double c, s, a11, a12, a21, a22; const size_t M = U->size1; const size_t N = V->size1; double d0 = gsl_vector_get (d, 0); double f0 = gsl_vector_get (f, 0); double d1 = gsl_vector_get (d, 1); if (d0 == 0.0) { /* Eliminate off-diagonal element in [0,f0;0,d1] to make [d,0;0,0] */ create_givens (f0, d1, &c, &s); /* compute B <= G^T B X, where X = [0,1;1,0] */ gsl_vector_set (d, 0, c * f0 - s * d1); gsl_vector_set (f, 0, s * f0 + c * d1); gsl_vector_set (d, 1, 0.0); /* Compute U <= U G */ for (i = 0; i < M; i++) { double Uip = gsl_matrix_get (U, i, 0); double Uiq = gsl_matrix_get (U, i, 1); gsl_matrix_set (U, i, 0, c * Uip - s * Uiq); gsl_matrix_set (U, i, 1, s * Uip + c * Uiq); } /* Compute V <= V X */ gsl_matrix_swap_columns (V, 0, 1); return; } else if (d1 == 0.0) { /* Eliminate off-diagonal element in [d0,f0;0,0] */ create_givens (d0, f0, &c, &s); /* compute B <= B G */ gsl_vector_set (d, 0, d0 * c - f0 * s); gsl_vector_set (f, 0, 0.0); /* Compute V <= V G */ for (i = 0; i < N; i++) { double Vip = gsl_matrix_get (V, i, 0); double Viq = gsl_matrix_get (V, i, 1); gsl_matrix_set (V, i, 0, c * Vip - s * Viq); gsl_matrix_set (V, i, 1, s * Vip + c * Viq); } return; } else { /* Make columns orthogonal, A = [d0, f0; 0, d1] * G */ create_schur (d0, f0, d1, &c, &s); /* compute B <= B G */ a11 = c * d0 - s * f0; a21 = - s * d1; a12 = s * d0 + c * f0; a22 = c * d1; /* Compute V <= V G */ for (i = 0; i < N; i++) { double Vip = gsl_matrix_get (V, i, 0); double Viq = gsl_matrix_get (V, i, 1); gsl_matrix_set (V, i, 0, c * Vip - s * Viq); gsl_matrix_set (V, i, 1, s * Vip + c * Viq); } /* Eliminate off-diagonal elements, bring column with largest norm to first column */ if (hypot(a11, a21) < hypot(a12,a22)) { double t1, t2; /* B <= B X */ t1 = a11; a11 = a12; a12 = t1; t2 = a21; a21 = a22; a22 = t2; /* V <= V X */ gsl_matrix_swap_columns(V, 0, 1); } create_givens (a11, a21, &c, &s); /* compute B <= G^T B */ gsl_vector_set (d, 0, c * a11 - s * a21); gsl_vector_set (f, 0, c * a12 - s * a22); gsl_vector_set (d, 1, s * a12 + c * a22); /* Compute U <= U G */ for (i = 0; i < M; i++) { double Uip = gsl_matrix_get (U, i, 0); double Uiq = gsl_matrix_get (U, i, 1); gsl_matrix_set (U, i, 0, c * Uip - s * Uiq); gsl_matrix_set (U, i, 1, s * Uip + c * Uiq); } return; } } static void chase_out_intermediate_zero (gsl_vector * d, gsl_vector * f, gsl_matrix * U, size_t k0) { #if !USE_BLAS const size_t M = U->size1; #endif const size_t n = d->size; double c, s; double x, y; size_t k; x = gsl_vector_get (f, k0); y = gsl_vector_get (d, k0+1); for (k = k0; k < n - 1; k++) { create_givens (y, -x, &c, &s); /* Compute U <= U G */ #ifdef USE_BLAS { gsl_vector_view Uk0 = gsl_matrix_column(U,k0); gsl_vector_view Ukp1 = gsl_matrix_column(U,k+1); gsl_blas_drot(&Uk0.vector, &Ukp1.vector, c, -s); } #else { size_t i; for (i = 0; i < M; i++) { double Uip = gsl_matrix_get (U, i, k0); double Uiq = gsl_matrix_get (U, i, k + 1); gsl_matrix_set (U, i, k0, c * Uip - s * Uiq); gsl_matrix_set (U, i, k + 1, s * Uip + c * Uiq); } } #endif /* compute B <= G^T B */ gsl_vector_set (d, k + 1, s * x + c * y); if (k == k0) gsl_vector_set (f, k, c * x - s * y ); if (k < n - 2) { double z = gsl_vector_get (f, k + 1); gsl_vector_set (f, k + 1, c * z); x = -s * z ; y = gsl_vector_get (d, k + 2); } } } static void chase_out_trailing_zero (gsl_vector * d, gsl_vector * f, gsl_matrix * V) { #if !USE_BLAS const size_t N = V->size1; #endif const size_t n = d->size; double c, s; double x, y; size_t k; x = gsl_vector_get (d, n - 2); y = gsl_vector_get (f, n - 2); for (k = n - 1; k > 0 && k--;) { create_givens (x, y, &c, &s); /* Compute V <= V G where G = [c, s ; -s, c] */ #ifdef USE_BLAS { gsl_vector_view Vp = gsl_matrix_column(V,k); gsl_vector_view Vq = gsl_matrix_column(V,n-1); gsl_blas_drot(&Vp.vector, &Vq.vector, c, -s); } #else { size_t i; for (i = 0; i < N; i++) { double Vip = gsl_matrix_get (V, i, k); double Viq = gsl_matrix_get (V, i, n - 1); gsl_matrix_set (V, i, k, c * Vip - s * Viq); gsl_matrix_set (V, i, n - 1, s * Vip + c * Viq); } } #endif /* compute B <= B G */ gsl_vector_set (d, k, c * x - s * y); if (k == n - 2) gsl_vector_set (f, k, s * x + c * y ); if (k > 0) { double z = gsl_vector_get (f, k - 1); gsl_vector_set (f, k - 1, c * z); x = gsl_vector_get (d, k - 1); y = s * z ; } } } static void qrstep (gsl_vector * d, gsl_vector * f, gsl_matrix * U, gsl_matrix * V) { #if !USE_BLAS const size_t M = U->size1; const size_t N = V->size1; #endif const size_t n = d->size; double y, z; double ak, bk, zk, ap, bp, aq, bq; size_t i, k; if (n == 1) return; /* shouldn't happen */ /* Compute 2x2 svd directly */ if (n == 2) { svd2 (d, f, U, V); return; } /* Chase out any zeroes on the diagonal */ for (i = 0; i < n - 1; i++) { double d_i = gsl_vector_get (d, i); if (d_i == 0.0) { chase_out_intermediate_zero (d, f, U, i); return; } } /* Chase out any zero at the end of the diagonal */ { double d_nm1 = gsl_vector_get (d, n - 1); if (d_nm1 == 0.0) { chase_out_trailing_zero (d, f, V); return; } } /* Apply QR reduction steps to the diagonal and offdiagonal */ { double d0 = gsl_vector_get (d, 0); double f0 = gsl_vector_get (f, 0); double d1 = gsl_vector_get (d, 1); double f1 = gsl_vector_get (f, 1); { double mu = trailing_eigenvalue (d, f); y = d0 * d0 - mu; z = d0 * f0; } /* Set up the recurrence for Givens rotations on a bidiagonal matrix */ ak = 0; bk = 0; ap = d0; bp = f0; aq = d1; bq = f1; } for (k = 0; k < n - 1; k++) { double c, s; create_givens (y, z, &c, &s); /* Compute V <= V G */ #ifdef USE_BLAS { gsl_vector_view Vk = gsl_matrix_column(V,k); gsl_vector_view Vkp1 = gsl_matrix_column(V,k+1); gsl_blas_drot(&Vk.vector, &Vkp1.vector, c, -s); } #else for (i = 0; i < N; i++) { double Vip = gsl_matrix_get (V, i, k); double Viq = gsl_matrix_get (V, i, k + 1); gsl_matrix_set (V, i, k, c * Vip - s * Viq); gsl_matrix_set (V, i, k + 1, s * Vip + c * Viq); } #endif /* compute B <= B G */ { double bk1 = c * bk - s * z; double ap1 = c * ap - s * bp; double bp1 = s * ap + c * bp; double zp1 = -s * aq; double aq1 = c * aq; if (k > 0) { gsl_vector_set (f, k - 1, bk1); } ak = ap1; bk = bp1; zk = zp1; ap = aq1; if (k < n - 2) { bp = gsl_vector_get (f, k + 1); } else { bp = 0.0; } y = ak; z = zk; } create_givens (y, z, &c, &s); /* Compute U <= U G */ #ifdef USE_BLAS { gsl_vector_view Uk = gsl_matrix_column(U,k); gsl_vector_view Ukp1 = gsl_matrix_column(U,k+1); gsl_blas_drot(&Uk.vector, &Ukp1.vector, c, -s); } #else for (i = 0; i < M; i++) { double Uip = gsl_matrix_get (U, i, k); double Uiq = gsl_matrix_get (U, i, k + 1); gsl_matrix_set (U, i, k, c * Uip - s * Uiq); gsl_matrix_set (U, i, k + 1, s * Uip + c * Uiq); } #endif /* compute B <= G^T B */ { double ak1 = c * ak - s * zk; double bk1 = c * bk - s * ap; double zk1 = -s * bp; double ap1 = s * bk + c * ap; double bp1 = c * bp; gsl_vector_set (d, k, ak1); ak = ak1; bk = bk1; zk = zk1; ap = ap1; bp = bp1; if (k < n - 2) { aq = gsl_vector_get (d, k + 2); } else { aq = 0.0; } y = bk; z = zk; } } gsl_vector_set (f, n - 2, bk); gsl_vector_set (d, n - 1, ap); } sources_5316/external/gsl/gsl_cblas__ztrsv.c0000664000176700017670000000065311723710247020050 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" #include "gsl_cblas__hypot.c" void cblas_ztrsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *A, const int lda, void *X, const int incX) { #define BASE double #include "gsl_cblas__source_trsv_c.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__dtrmv.c0000664000176700017670000000062011723710247020006 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dtrmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const double *A, const int lda, double *X, const int incX) { #define BASE double #include "gsl_cblas__source_trmv_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__srotm.c0000664000176700017670000000040311723710247020015 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_srotm (const int N, float *X, const int incX, float *Y, const int incY, const float *P) { #define BASE float #include "gsl_cblas__source_rotm.h" #undef BASE } sources_5316/external/gsl/gsl_sys__invhyp.c0000664000176700017670000000416711723710247017733 0ustar paulpaul/* sys/invhyp.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_machine.h" double gsl_acosh (const double x) { if (x > 1.0 / GSL_SQRT_DBL_EPSILON) { return log (x) + M_LN2; } else if (x > 2) { return log (2 * x - 1 / (sqrt (x * x - 1) + x)); } else if (x > 1) { double t = x - 1; return log1p (t + sqrt (2 * t + t * t)); } else if (x == 1) { return 0; } else { return GSL_NAN; } } double gsl_asinh (const double x) { double a = fabs (x); double s = (x < 0) ? -1 : 1; if (a > 1 / GSL_SQRT_DBL_EPSILON) { return s * (log (a) + M_LN2); } else if (a > 2) { return s * log (2 * a + 1 / (a + sqrt (a * a + 1))); } else if (a > GSL_SQRT_DBL_EPSILON) { double a2 = a * a; return s * log1p (a + a2 / (1 + sqrt (1 + a2))); } else { return x; } } double gsl_atanh (const double x) { double a = fabs (x); double s = (x < 0) ? -1 : 1; if (a > 1) { return GSL_NAN; } else if (a == 1) { return (x < 0) ? GSL_NEGINF : GSL_POSINF; } else if (a >= 0.5) { return s * 0.5 * log1p (2 * a / (1 - a)); } else if (a > GSL_DBL_EPSILON) { return s * 0.5 * log1p (2 * a + 2 * a * a / (1 - a)); } else { return x; } } sources_5316/external/gsl/gsl_sort__sortvecind_source.c0000664000176700017670000000467711723710247022335 0ustar paulpaul/* * Implement Heap sort -- direct and indirect sorting * Based on descriptions in Sedgewick "Algorithms in C" * * Copyright (C) 1999 Thomas Walter * * 18 February 2000: Modified for GSL by Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ static inline void FUNCTION (index, downheap) (size_t * p, const BASE * data, const size_t stride, const size_t N, size_t k); static inline void FUNCTION (index, downheap) (size_t * p, const BASE * data, const size_t stride, const size_t N, size_t k) { const size_t pki = p[k]; while (k <= N / 2) { size_t j = 2 * k; if (j < N && data[p[j] * stride] < data[p[j + 1] * stride]) { j++; } if (!(data[pki * stride] < data[p[j] * stride])) /* avoid infinite loop if nan */ { break; } p[k] = p[j]; k = j; } p[k] = pki; } void FUNCTION (gsl_sort, index) (size_t * p, const BASE * data, const size_t stride, const size_t n) { size_t N; size_t i, k; if (n == 0) { return; /* No data to sort */ } /* set permutation to identity */ for (i = 0 ; i < n ; i++) { p[i] = i ; } /* We have n_data elements, last element is at 'n_data-1', first at '0' Set N to the last element number. */ N = n - 1; k = N / 2; k++; /* Compensate the first use of 'k--' */ do { k--; FUNCTION (index, downheap) (p, data, stride, N, k); } while (k > 0); while (N > 0) { /* first swap the elements */ size_t tmp = p[0]; p[0] = p[N]; p[N] = tmp; /* then process the heap */ N--; FUNCTION (index, downheap) (p, data, stride, N, 0); } } int FUNCTION (gsl_sort_vector, index) (gsl_permutation * permutation, const TYPE (gsl_vector) * v) { if (permutation->size != v->size) { GSL_ERROR ("permutation and vector lengths are not equal", GSL_EBADLEN); } FUNCTION (gsl_sort, index) (permutation->data, v->data, v->stride, v->size) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_dft_complex.h0000664000176700017670000000341211705263724017665 0ustar paulpaul/* fft/gsl_dft_complex.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_DFT_COMPLEX_H__ #define __GSL_DFT_COMPLEX_H__ #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_fft.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_dft_complex_forward (const double data[], const size_t stride, const size_t n, double result[]); int gsl_dft_complex_backward (const double data[], const size_t stride, const size_t n, double result[]); int gsl_dft_complex_inverse (const double data[], const size_t stride, const size_t n, double result[]); int gsl_dft_complex_transform (const double data[], const size_t stride, const size_t n, double result[], const gsl_fft_direction sign); __END_DECLS #endif /* __GSL_DFT_COMPLEX_H__ */ sources_5316/external/gsl/gsl_integration__reset.c0000664000176700017670000000032311723710247021233 0ustar paulpaulstatic inline void reset_nrmax (gsl_integration_workspace * workspace); static inline void reset_nrmax (gsl_integration_workspace * workspace) { workspace->nrmax = 0; workspace->i = workspace->order[0] ; } sources_5316/external/gsl/gsl_cblas__source_syr2k_c.h0000664000176700017670000001636111705263724021627 0ustar paulpaul/* blas/source_syr2k_c.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; int uplo, trans; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; if (Order == CblasRowMajor) { uplo = Uplo; trans = Trans; } else { uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; trans = (Trans == CblasNoTrans) ? CblasTrans : CblasNoTrans; } /* form C := beta*C */ if (beta_real == 0.0 && beta_imag == 0.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { const BASE Cij_real = REAL(C, ldc * i + j); const BASE Cij_imag = IMAG(C, ldc * i + j); REAL(C, ldc * i + j) = beta_real * Cij_real - beta_imag * Cij_imag; IMAG(C, ldc * i + j) = beta_real * Cij_imag + beta_imag * Cij_real; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { const BASE Cij_real = REAL(C, ldc * i + j); const BASE Cij_imag = IMAG(C, ldc * i + j); REAL(C, ldc * i + j) = beta_real * Cij_real - beta_imag * Cij_imag; IMAG(C, ldc * i + j) = beta_real * Cij_imag + beta_imag * Cij_real; } } } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; if (uplo == CblasUpper && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Bik_real = CONST_REAL(B, i * ldb + k); const BASE Bik_imag = CONST_IMAG(B, i * ldb + k); const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); const BASE Bjk_real = CONST_REAL(B, j * ldb + k); const BASE Bjk_imag = CONST_IMAG(B, j * ldb + k); temp_real += ((Aik_real * Bjk_real - Aik_imag * Bjk_imag) + (Bik_real * Ajk_real - Bik_imag * Ajk_imag)); temp_imag += ((Aik_real * Bjk_imag + Aik_imag * Bjk_real) + (Bik_real * Ajk_imag + Bik_imag * Ajk_real)); } REAL(C, i * ldc + j) += alpha_real * temp_real - alpha_imag * temp_imag; IMAG(C, i * ldc + j) += alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (uplo == CblasUpper && trans == CblasTrans) { for (k = 0; k < K; k++) { for (i = 0; i < N; i++) { BASE Aki_real = CONST_REAL(A, k * lda + i); BASE Aki_imag = CONST_IMAG(A, k * lda + i); BASE Bki_real = CONST_REAL(B, k * ldb + i); BASE Bki_imag = CONST_IMAG(B, k * ldb + i); BASE temp1_real = alpha_real * Aki_real - alpha_imag * Aki_imag; BASE temp1_imag = alpha_real * Aki_imag + alpha_imag * Aki_real; BASE temp2_real = alpha_real * Bki_real - alpha_imag * Bki_imag; BASE temp2_imag = alpha_real * Bki_imag + alpha_imag * Bki_real; for (j = i; j < N; j++) { BASE Akj_real = CONST_REAL(A, k * lda + j); BASE Akj_imag = CONST_IMAG(A, k * lda + j); BASE Bkj_real = CONST_REAL(B, k * ldb + j); BASE Bkj_imag = CONST_IMAG(B, k * ldb + j); REAL(C, i * lda + j) += (temp1_real * Bkj_real - temp1_imag * Bkj_imag) + (temp2_real * Akj_real - temp2_imag * Akj_imag); IMAG(C, i * lda + j) += (temp1_real * Bkj_imag + temp1_imag * Bkj_real) + (temp2_real * Akj_imag + temp2_imag * Akj_real); } } } } else if (uplo == CblasLower && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Bik_real = CONST_REAL(B, i * ldb + k); const BASE Bik_imag = CONST_IMAG(B, i * ldb + k); const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); const BASE Bjk_real = CONST_REAL(B, j * ldb + k); const BASE Bjk_imag = CONST_IMAG(B, j * ldb + k); temp_real += ((Aik_real * Bjk_real - Aik_imag * Bjk_imag) + (Bik_real * Ajk_real - Bik_imag * Ajk_imag)); temp_imag += ((Aik_real * Bjk_imag + Aik_imag * Bjk_real) + (Bik_real * Ajk_imag + Bik_imag * Ajk_real)); } REAL(C, i * ldc + j) += alpha_real * temp_real - alpha_imag * temp_imag; IMAG(C, i * ldc + j) += alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (uplo == CblasLower && trans == CblasTrans) { for (k = 0; k < K; k++) { for (i = 0; i < N; i++) { BASE Aki_real = CONST_REAL(A, k * lda + i); BASE Aki_imag = CONST_IMAG(A, k * lda + i); BASE Bki_real = CONST_REAL(B, k * ldb + i); BASE Bki_imag = CONST_IMAG(B, k * ldb + i); BASE temp1_real = alpha_real * Aki_real - alpha_imag * Aki_imag; BASE temp1_imag = alpha_real * Aki_imag + alpha_imag * Aki_real; BASE temp2_real = alpha_real * Bki_real - alpha_imag * Bki_imag; BASE temp2_imag = alpha_real * Bki_imag + alpha_imag * Bki_real; for (j = 0; j <= i; j++) { BASE Akj_real = CONST_REAL(A, k * lda + j); BASE Akj_imag = CONST_IMAG(A, k * lda + j); BASE Bkj_real = CONST_REAL(B, k * ldb + j); BASE Bkj_imag = CONST_IMAG(B, k * ldb + j); REAL(C, i * lda + j) += (temp1_real * Bkj_real - temp1_imag * Bkj_imag) + (temp2_real * Akj_real - temp2_imag * Akj_imag); IMAG(C, i * lda + j) += (temp1_real * Bkj_imag + temp1_imag * Bkj_real) + (temp2_real * Akj_imag + temp2_imag * Akj_real); } } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_eigen.h0000664000176700017670000003153511705263724016457 0ustar paulpaul/* eigen/gsl_eigen.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2006, 2007 Gerard Jungman, Brian Gough, Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_EIGEN_H__ #define __GSL_EIGEN_H__ #include "gsl_vector.h" #include "gsl_matrix.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; double * d; double * sd; } gsl_eigen_symm_workspace; gsl_eigen_symm_workspace * gsl_eigen_symm_alloc (const size_t n); void gsl_eigen_symm_free (gsl_eigen_symm_workspace * w); int gsl_eigen_symm (gsl_matrix * A, gsl_vector * eval, gsl_eigen_symm_workspace * w); typedef struct { size_t size; double * d; double * sd; double * gc; double * gs; } gsl_eigen_symmv_workspace; gsl_eigen_symmv_workspace * gsl_eigen_symmv_alloc (const size_t n); void gsl_eigen_symmv_free (gsl_eigen_symmv_workspace * w); int gsl_eigen_symmv (gsl_matrix * A, gsl_vector * eval, gsl_matrix * evec, gsl_eigen_symmv_workspace * w); typedef struct { size_t size; double * d; double * sd; double * tau; } gsl_eigen_herm_workspace; gsl_eigen_herm_workspace * gsl_eigen_herm_alloc (const size_t n); void gsl_eigen_herm_free (gsl_eigen_herm_workspace * w); int gsl_eigen_herm (gsl_matrix_complex * A, gsl_vector * eval, gsl_eigen_herm_workspace * w); typedef struct { size_t size; double * d; double * sd; double * tau; double * gc; double * gs; } gsl_eigen_hermv_workspace; gsl_eigen_hermv_workspace * gsl_eigen_hermv_alloc (const size_t n); void gsl_eigen_hermv_free (gsl_eigen_hermv_workspace * w); int gsl_eigen_hermv (gsl_matrix_complex * A, gsl_vector * eval, gsl_matrix_complex * evec, gsl_eigen_hermv_workspace * w); typedef struct { size_t size; /* matrix size */ size_t max_iterations; /* max iterations since last eigenvalue found */ size_t n_iter; /* number of iterations since last eigenvalue found */ size_t n_evals; /* number of eigenvalues found so far */ int compute_t; /* compute Schur form T = Z^t A Z */ gsl_matrix *H; /* pointer to Hessenberg matrix */ gsl_matrix *Z; /* pointer to Schur vector matrix */ } gsl_eigen_francis_workspace; gsl_eigen_francis_workspace * gsl_eigen_francis_alloc (void); void gsl_eigen_francis_free (gsl_eigen_francis_workspace * w); void gsl_eigen_francis_T (const int compute_t, gsl_eigen_francis_workspace * w); int gsl_eigen_francis (gsl_matrix * H, gsl_vector_complex * eval, gsl_eigen_francis_workspace * w); int gsl_eigen_francis_Z (gsl_matrix * H, gsl_vector_complex * eval, gsl_matrix * Z, gsl_eigen_francis_workspace * w); typedef struct { size_t size; /* size of matrices */ gsl_vector *diag; /* diagonal matrix elements from balancing */ gsl_vector *tau; /* Householder coefficients */ gsl_matrix *Z; /* pointer to Z matrix */ int do_balance; /* perform balancing transformation? */ size_t n_evals; /* number of eigenvalues found */ gsl_eigen_francis_workspace *francis_workspace_p; } gsl_eigen_nonsymm_workspace; gsl_eigen_nonsymm_workspace * gsl_eigen_nonsymm_alloc (const size_t n); void gsl_eigen_nonsymm_free (gsl_eigen_nonsymm_workspace * w); void gsl_eigen_nonsymm_params (const int compute_t, const int balance, gsl_eigen_nonsymm_workspace *w); int gsl_eigen_nonsymm (gsl_matrix * A, gsl_vector_complex * eval, gsl_eigen_nonsymm_workspace * w); int gsl_eigen_nonsymm_Z (gsl_matrix * A, gsl_vector_complex * eval, gsl_matrix * Z, gsl_eigen_nonsymm_workspace * w); typedef struct { size_t size; /* size of matrices */ gsl_vector *work; /* scratch workspace */ gsl_vector *work2; /* scratch workspace */ gsl_vector *work3; /* scratch workspace */ gsl_matrix *Z; /* pointer to Schur vectors */ gsl_eigen_nonsymm_workspace *nonsymm_workspace_p; } gsl_eigen_nonsymmv_workspace; gsl_eigen_nonsymmv_workspace * gsl_eigen_nonsymmv_alloc (const size_t n); void gsl_eigen_nonsymmv_free (gsl_eigen_nonsymmv_workspace * w); int gsl_eigen_nonsymmv (gsl_matrix * A, gsl_vector_complex * eval, gsl_matrix_complex * evec, gsl_eigen_nonsymmv_workspace * w); int gsl_eigen_nonsymmv_Z (gsl_matrix * A, gsl_vector_complex * eval, gsl_matrix_complex * evec, gsl_matrix * Z, gsl_eigen_nonsymmv_workspace * w); typedef struct { size_t size; /* size of matrices */ gsl_eigen_symm_workspace *symm_workspace_p; } gsl_eigen_gensymm_workspace; gsl_eigen_gensymm_workspace * gsl_eigen_gensymm_alloc (const size_t n); void gsl_eigen_gensymm_free (gsl_eigen_gensymm_workspace * w); int gsl_eigen_gensymm (gsl_matrix * A, gsl_matrix * B, gsl_vector * eval, gsl_eigen_gensymm_workspace * w); int gsl_eigen_gensymm_standardize (gsl_matrix * A, const gsl_matrix * B); typedef struct { size_t size; /* size of matrices */ gsl_eigen_symmv_workspace *symmv_workspace_p; } gsl_eigen_gensymmv_workspace; gsl_eigen_gensymmv_workspace * gsl_eigen_gensymmv_alloc (const size_t n); void gsl_eigen_gensymmv_free (gsl_eigen_gensymmv_workspace * w); int gsl_eigen_gensymmv (gsl_matrix * A, gsl_matrix * B, gsl_vector * eval, gsl_matrix * evec, gsl_eigen_gensymmv_workspace * w); typedef struct { size_t size; /* size of matrices */ gsl_eigen_herm_workspace *herm_workspace_p; } gsl_eigen_genherm_workspace; gsl_eigen_genherm_workspace * gsl_eigen_genherm_alloc (const size_t n); void gsl_eigen_genherm_free (gsl_eigen_genherm_workspace * w); int gsl_eigen_genherm (gsl_matrix_complex * A, gsl_matrix_complex * B, gsl_vector * eval, gsl_eigen_genherm_workspace * w); int gsl_eigen_genherm_standardize (gsl_matrix_complex * A, const gsl_matrix_complex * B); typedef struct { size_t size; /* size of matrices */ gsl_eigen_hermv_workspace *hermv_workspace_p; } gsl_eigen_genhermv_workspace; gsl_eigen_genhermv_workspace * gsl_eigen_genhermv_alloc (const size_t n); void gsl_eigen_genhermv_free (gsl_eigen_genhermv_workspace * w); int gsl_eigen_genhermv (gsl_matrix_complex * A, gsl_matrix_complex * B, gsl_vector * eval, gsl_matrix_complex * evec, gsl_eigen_genhermv_workspace * w); typedef struct { size_t size; /* size of matrices */ gsl_vector *work; /* scratch workspace */ size_t n_evals; /* number of eigenvalues found */ size_t max_iterations; /* maximum QZ iterations allowed */ size_t n_iter; /* number of iterations since last eigenvalue found */ double eshift; /* exceptional shift counter */ int needtop; /* need to compute top index? */ double atol; /* tolerance for splitting A matrix */ double btol; /* tolerance for splitting B matrix */ double ascale; /* scaling factor for shifts */ double bscale; /* scaling factor for shifts */ gsl_matrix *H; /* pointer to hessenberg matrix */ gsl_matrix *R; /* pointer to upper triangular matrix */ int compute_s; /* compute generalized Schur form S */ int compute_t; /* compute generalized Schur form T */ gsl_matrix *Q; /* pointer to left Schur vectors */ gsl_matrix *Z; /* pointer to right Schur vectors */ } gsl_eigen_gen_workspace; gsl_eigen_gen_workspace * gsl_eigen_gen_alloc (const size_t n); void gsl_eigen_gen_free (gsl_eigen_gen_workspace * w); void gsl_eigen_gen_params (const int compute_s, const int compute_t, const int balance, gsl_eigen_gen_workspace * w); int gsl_eigen_gen (gsl_matrix * A, gsl_matrix * B, gsl_vector_complex * alpha, gsl_vector * beta, gsl_eigen_gen_workspace * w); int gsl_eigen_gen_QZ (gsl_matrix * A, gsl_matrix * B, gsl_vector_complex * alpha, gsl_vector * beta, gsl_matrix * Q, gsl_matrix * Z, gsl_eigen_gen_workspace * w); typedef struct { size_t size; /* size of matrices */ gsl_vector *work1; /* 1-norm of columns of A */ gsl_vector *work2; /* 1-norm of columns of B */ gsl_vector *work3; /* real part of eigenvector */ gsl_vector *work4; /* imag part of eigenvector */ gsl_vector *work5; /* real part of back-transformed eigenvector */ gsl_vector *work6; /* imag part of back-transformed eigenvector */ gsl_matrix *Q; /* pointer to left Schur vectors */ gsl_matrix *Z; /* pointer to right Schur vectors */ gsl_eigen_gen_workspace *gen_workspace_p; } gsl_eigen_genv_workspace; gsl_eigen_genv_workspace * gsl_eigen_genv_alloc (const size_t n); void gsl_eigen_genv_free (gsl_eigen_genv_workspace * w); int gsl_eigen_genv (gsl_matrix * A, gsl_matrix * B, gsl_vector_complex * alpha, gsl_vector * beta, gsl_matrix_complex * evec, gsl_eigen_genv_workspace * w); int gsl_eigen_genv_QZ (gsl_matrix * A, gsl_matrix * B, gsl_vector_complex * alpha, gsl_vector * beta, gsl_matrix_complex * evec, gsl_matrix * Q, gsl_matrix * Z, gsl_eigen_genv_workspace * w); typedef enum { GSL_EIGEN_SORT_VAL_ASC, GSL_EIGEN_SORT_VAL_DESC, GSL_EIGEN_SORT_ABS_ASC, GSL_EIGEN_SORT_ABS_DESC } gsl_eigen_sort_t; /* Sort eigensystem results based on eigenvalues. * Sorts in order of increasing value or increasing * absolute value. * * exceptions: GSL_EBADLEN */ int gsl_eigen_symmv_sort(gsl_vector * eval, gsl_matrix * evec, gsl_eigen_sort_t sort_type); int gsl_eigen_hermv_sort(gsl_vector * eval, gsl_matrix_complex * evec, gsl_eigen_sort_t sort_type); int gsl_eigen_nonsymmv_sort(gsl_vector_complex * eval, gsl_matrix_complex * evec, gsl_eigen_sort_t sort_type); int gsl_eigen_gensymmv_sort (gsl_vector * eval, gsl_matrix * evec, gsl_eigen_sort_t sort_type); int gsl_eigen_genhermv_sort (gsl_vector * eval, gsl_matrix_complex * evec, gsl_eigen_sort_t sort_type); int gsl_eigen_genv_sort (gsl_vector_complex * alpha, gsl_vector * beta, gsl_matrix_complex * evec, gsl_eigen_sort_t sort_type); /* Prototypes for the schur module */ int gsl_schur_gen_eigvals(const gsl_matrix *A, const gsl_matrix *B, double *wr1, double *wr2, double *wi, double *scale1, double *scale2); int gsl_schur_solve_equation(double ca, const gsl_matrix *A, double z, double d1, double d2, const gsl_vector *b, gsl_vector *x, double *s, double *xnorm, double smin); int gsl_schur_solve_equation_z(double ca, const gsl_matrix *A, gsl_complex *z, double d1, double d2, const gsl_vector_complex *b, gsl_vector_complex *x, double *s, double *xnorm, double smin); /* The following functions are obsolete: */ /* Eigensolve by Jacobi Method * * The data in the matrix input is destroyed. * * exceptions: */ int gsl_eigen_jacobi(gsl_matrix * matrix, gsl_vector * eval, gsl_matrix * evec, unsigned int max_rot, unsigned int * nrot); /* Invert by Jacobi Method * * exceptions: */ int gsl_eigen_invert_jacobi(const gsl_matrix * matrix, gsl_matrix * ainv, unsigned int max_rot); __END_DECLS #endif /* __GSL_EIGEN_H__ */ sources_5316/external/gsl/gsl_statistics__quantiles_source.c0000664000176700017670000000272511723710247023355 0ustar paulpaul/* statistics/quantiles_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,quantile_from_sorted_data) (const BASE sorted_data[], const size_t stride, const size_t n, const double f) { const double index = f * (n - 1) ; const size_t lhs = (int)index ; const double delta = index - lhs ; double result; if (n == 0) return 0.0 ; if (lhs == n - 1) { result = sorted_data[lhs * stride] ; } else { result = (1 - delta) * sorted_data[lhs * stride] + delta * sorted_data[(lhs + 1) * stride] ; } return result ; } sources_5316/external/gsl/gsl_specfunc__bessel_olver.h0000664000176700017670000000223211705263724022071 0ustar paulpaul/* specfunc/bessel_olver.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef BESSEL_OLVER_H_ #define BESSEL_OLVER_H_ #include "gsl_sf_result.h" int gsl_sf_bessel_Jnu_asymp_Olver_e(double nu, double x, gsl_sf_result * result); int gsl_sf_bessel_Ynu_asymp_Olver_e(double nu, double x, gsl_sf_result * result); double gsl_sf_bessel_Olver_zofmzeta(double minus_zeta); #endif /* !BESSEL_OLVER_H_ */ sources_5316/external/gsl/gsl_poly__balance.c0000664000176700017670000000615111723710247020143 0ustar paulpaul/* poly/balance.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void balance_companion_matrix (double *m, size_t n); #define RADIX 2 #define RADIX2 (RADIX*RADIX) static void balance_companion_matrix (double *m, size_t nc) { int not_converged = 1; double row_norm = 0; double col_norm = 0; while (not_converged) { size_t i, j; double g, f, s; not_converged = 0; for (i = 0; i < nc; i++) { /* column norm, excluding the diagonal */ if (i != nc - 1) { col_norm = fabs (MAT (m, i + 1, i, nc)); } else { col_norm = 0; for (j = 0; j < nc - 1; j++) { col_norm += fabs (MAT (m, j, nc - 1, nc)); } } /* row norm, excluding the diagonal */ if (i == 0) { row_norm = fabs (MAT (m, 0, nc - 1, nc)); } else if (i == nc - 1) { row_norm = fabs (MAT (m, i, i - 1, nc)); } else { row_norm = (fabs (MAT (m, i, i - 1, nc)) + fabs (MAT (m, i, nc - 1, nc))); } if (col_norm == 0 || row_norm == 0) { continue; } g = row_norm / RADIX; f = 1; s = col_norm + row_norm; while (col_norm < g) { f *= RADIX; col_norm *= RADIX2; } g = row_norm * RADIX; while (col_norm > g) { f /= RADIX; col_norm /= RADIX2; } if ((row_norm + col_norm) < 0.95 * s * f) { not_converged = 1; g = 1 / f; if (i == 0) { MAT (m, 0, nc - 1, nc) *= g; } else { MAT (m, i, i - 1, nc) *= g; MAT (m, i, nc - 1, nc) *= g; } if (i == nc - 1) { for (j = 0; j < nc; j++) { MAT (m, j, i, nc) *= f; } } else { MAT (m, i + 1, i, nc) *= f; } } } } } sources_5316/external/gsl/gsl_permute_long.h0000664000176700017670000000261611705263724020066 0ustar paulpaul/* permutation/gsl_permute_long.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_LONG_H__ #define __GSL_PERMUTE_LONG_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_long (const size_t * p, long * data, const size_t stride, const size_t n); int gsl_permute_long_inverse (const size_t * p, long * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_LONG_H__ */ sources_5316/external/gsl/gsl_cblas__srotg.c0000664000176700017670000000031511723710247020011 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_srotg (float *a, float *b, float *c, float *s) { #define BASE float #include "gsl_cblas__source_rotg.h" #undef BASE } sources_5316/external/gsl/gsl_fft__c_pass_3.c0000664000176700017670000001050711723710247020044 0ustar paulpaul/* fft/c_pass_3.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int FUNCTION(fft_complex,pass_3) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) * twiddle1, const TYPE(gsl_complex) * twiddle2) { size_t i = 0, j = 0; size_t k, k1; const size_t factor = 3; const size_t m = n / factor; const size_t q = n / product; const size_t product_1 = product / factor; const size_t jump = (factor - 1) * product_1; const ATOMIC tau = sqrt (3.0) / 2.0; for (k = 0; k < q; k++) { ATOMIC w1_real, w1_imag, w2_real, w2_imag; if (k == 0) { w1_real = 1.0; w1_imag = 0.0; w2_real = 1.0; w2_imag = 0.0; } else { if (sign == gsl_fft_forward) { /* forward tranform */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = GSL_IMAG(twiddle2[k - 1]); } else { /* backward tranform: w -> conjugate(w) */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = -GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = -GSL_IMAG(twiddle2[k - 1]); } } for (k1 = 0; k1 < product_1; k1++) { const ATOMIC z0_real = REAL(in,istride,i); const ATOMIC z0_imag = IMAG(in,istride,i); const ATOMIC z1_real = REAL(in,istride,i+m); const ATOMIC z1_imag = IMAG(in,istride,i+m); const ATOMIC z2_real = REAL(in,istride,i+2*m); const ATOMIC z2_imag = IMAG(in,istride,i+2*m); /* compute x = W(3) z */ /* t1 = z1 + z2 */ const ATOMIC t1_real = z1_real + z2_real; const ATOMIC t1_imag = z1_imag + z2_imag; /* t2 = z0 - t1/2 */ const ATOMIC t2_real = z0_real - t1_real / 2.0; const ATOMIC t2_imag = z0_imag - t1_imag / 2.0; /* t3 = (+/-) sin(pi/3)*(z1 - z2) */ const ATOMIC t3_real = ((int) sign) * tau * (z1_real - z2_real); const ATOMIC t3_imag = ((int) sign) * tau * (z1_imag - z2_imag); /* x0 = z0 + t1 */ const ATOMIC x0_real = z0_real + t1_real; const ATOMIC x0_imag = z0_imag + t1_imag; /* x1 = t2 + i t3 */ const ATOMIC x1_real = t2_real - t3_imag; const ATOMIC x1_imag = t2_imag + t3_real; /* x2 = t2 - i t3 */ const ATOMIC x2_real = t2_real + t3_imag; const ATOMIC x2_imag = t2_imag - t3_real; /* apply twiddle factors */ /* to0 = 1 * x0 */ REAL(out,ostride,j) = x0_real; IMAG(out,ostride,j) = x0_imag; /* to1 = w1 * x1 */ REAL(out,ostride,j+product_1) = w1_real * x1_real - w1_imag * x1_imag; IMAG(out,ostride,j+product_1) = w1_real * x1_imag + w1_imag * x1_real; /* to2 = w2 * x2 */ REAL(out,ostride,j+2*product_1) = w2_real * x2_real - w2_imag * x2_imag; IMAG(out,ostride,j+2*product_1) = w2_real * x2_imag + w2_imag * x2_real; i++; j++; } j += jump; } return 0; } sources_5316/external/gsl/gsl_histogram__find.c0000664000176700017670000000361611723710247020513 0ustar paulpaul/* histogram/find.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* determines whether to optimize for linear ranges */ #define LINEAR_OPT 1 static int find (const size_t n, const double range[], const double x, size_t * i); static int find (const size_t n, const double range[], const double x, size_t * i) { size_t i_linear, lower, upper, mid; if (x < range[0]) { return -1; } if (x >= range[n]) { return +1; } /* optimize for linear case */ #ifdef LINEAR_OPT { double u = (x - range[0]) / (range[n] - range[0]); i_linear = (size_t) (u * n); } if (x >= range[i_linear] && x < range[i_linear + 1]) { *i = i_linear; return 0; } #endif /* perform binary search */ upper = n ; lower = 0 ; while (upper - lower > 1) { mid = (upper + lower) / 2 ; if (x >= range[mid]) { lower = mid ; } else { upper = mid ; } } *i = lower ; /* sanity check the result */ if (x < range[lower] || x >= range[lower + 1]) { GSL_ERROR ("x not found in range", GSL_ESANITY); } return 0; } sources_5316/external/gsl/gsl_histogram__oper2d.c0000664000176700017670000001025211723710247020760 0ustar paulpaul/* gsl_histogram2d_oper.c * Copyright (C) 2000 Simone Piccardi * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File gsl_histogram2d_oper.c: * Routine to make operation on 2D histograms. * Need GSL library and header. * Contains the routines: * gsl_histogram2d_same_binning check if two histograms have the same binning * gsl_histogram2d_add add two histogram * gsl_histogram2d_sub subctract two histogram * gsl_histogram2d_mult multiply two histogram * gsl_histogram2d_div divide two histogram * gsl_histogram2d_scale scale histogram contents * * Author: S. Piccardi * Jan. 2000 * ***************************************************************/ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram2d.h" /* * gsl_histogram2d_same_binning: * control if two histogram have the * same binning */ int gsl_histogram2d_equal_bins_p (const gsl_histogram2d * h1, const gsl_histogram2d * h2) { if ((h1->nx != h2->nx) || (h1->ny != h2->ny)) { return 0; } { size_t i; /* init ranges */ for (i = 0; i <= (h1->nx); i++) { if (h1->xrange[i] != h2->xrange[i]) { return 0; } } for (i = 0; i <= (h1->ny); i++) { if (h1->yrange[i] != h2->yrange[i]) { return 0; } } } return 1; } /* * gsl_histogram2d_add: * add two histogram */ int gsl_histogram2d_add (gsl_histogram2d * h1, const gsl_histogram2d * h2) { size_t i; if (!gsl_histogram2d_equal_bins_p (h1, h2)) { GSL_ERROR ("histograms have different binning", GSL_EINVAL); } for (i = 0; i < (h1->nx) * (h1->ny); i++) { h1->bin[i] += h2->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram2d_sub: * subtract two histogram */ int gsl_histogram2d_sub (gsl_histogram2d * h1, const gsl_histogram2d * h2) { size_t i; if (!gsl_histogram2d_equal_bins_p (h1, h2)) { GSL_ERROR ("histograms have different binning", GSL_EINVAL); } for (i = 0; i < (h1->nx) * (h1->ny); i++) { h1->bin[i] -= h2->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram2d_mult: * multiply two histogram */ int gsl_histogram2d_mul (gsl_histogram2d * h1, const gsl_histogram2d * h2) { size_t i; if (!gsl_histogram2d_equal_bins_p (h1, h2)) { GSL_ERROR ("histograms have different binning", GSL_EINVAL); } for (i = 0; i < (h1->nx) * (h1->ny); i++) { h1->bin[i] *= h2->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram2d_div: * divide two histogram */ int gsl_histogram2d_div (gsl_histogram2d * h1, const gsl_histogram2d * h2) { size_t i; if (!gsl_histogram2d_equal_bins_p (h1, h2)) { GSL_ERROR ("histograms have different binning", GSL_EINVAL); } for (i = 0; i < (h1->nx) * (h1->ny); i++) { h1->bin[i] /= h2->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram2d_scale: * scale a histogram by a numeric factor */ int gsl_histogram2d_scale (gsl_histogram2d * h, double scale) { size_t i; for (i = 0; i < (h->nx) * (h->ny); i++) { h->bin[i] *= scale; } return GSL_SUCCESS; } /* * gsl_histogram2d_shift: * shift a histogram by a numeric offset */ int gsl_histogram2d_shift (gsl_histogram2d * h, double shift) { size_t i; for (i = 0; i < (h->nx) * (h->ny); i++) { h->bin[i] += shift; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_sf__bessel.h0000644000176700017670000000604010707442037017460 0ustar paulpaul/* specfunc/bessel.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef _BESSEL_H_ #define _BESSEL_H_ #include "gsl_sf_result.h" /* Taylor expansion for J_nu(x) or I_nu(x) * sign = -1 ==> Jnu * sign = +1 ==> Inu */ int gsl_sf_bessel_IJ_taylor_e(const double nu, const double x, const int sign, const int kmax, const double threshold, gsl_sf_result * result ); int gsl_sf_bessel_Jnu_asympx_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Ynu_asympx_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Inu_scaled_asympx_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Knu_scaled_asympx_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Inu_scaled_asymp_unif_e(const double nu, const double x, gsl_sf_result * result); int gsl_sf_bessel_Knu_scaled_asymp_unif_e(const double nu, const double x, gsl_sf_result * result); /* ratio = J_{nu+1}(x) / J_nu(x) * sgn = sgn(J_nu(x)) */ int gsl_sf_bessel_J_CF1(const double nu, const double x, double * ratio, double * sgn); /* ratio = I_{nu+1}(x) / I_nu(x) */ int gsl_sf_bessel_I_CF1_ser(const double nu, const double x, double * ratio); /* Evaluate the Steed method continued fraction CF2 for * * (J' + i Y')/(J + i Y) := P + i Q */ int gsl_sf_bessel_JY_steed_CF2(const double nu, const double x, double * P, double * Q); int gsl_sf_bessel_JY_mu_restricted(const double mu, const double x, gsl_sf_result * Jmu, gsl_sf_result * Jmup1, gsl_sf_result * Ymu, gsl_sf_result * Ymup1); int gsl_sf_bessel_K_scaled_steed_temme_CF2(const double nu, const double x, double * K_nu, double * K_nup1, double * Kp_nu); /* These are of use in calculating the oscillating * Bessel functions. * cos(y - pi/4 + eps) * sin(y - pi/4 + eps) */ int gsl_sf_bessel_cos_pi4_e(double y, double eps, gsl_sf_result * result); int gsl_sf_bessel_sin_pi4_e(double y, double eps, gsl_sf_result * result); #endif /* !_BESSEL_H_ */ sources_5316/external/gsl/gsl_specfunc__erfc.c0000664000176700017670000002776111723710247020332 0ustar paulpaul/* specfunc/erfc.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: J. Theiler (modifications by G. Jungman) */ /* * See Hart et al, Computer Approximations, John Wiley and Sons, New York (1968) * (This applies only to the erfc8 stuff, which is the part * of the original code that survives. I have replaced much of * the other stuff with Chebyshev fits. These are simpler and * more precise than the original approximations. [GJ]) */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_erf.h" #include "gsl_specfunc__check.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" #define LogRootPi_ 0.57236494292470008706 static double erfc8_sum(double x) { /* estimates erfc(x) valid for 8 < x < 100 */ /* This is based on index 5725 in Hart et al */ static double P[] = { 2.97886562639399288862, 7.409740605964741794425, 6.1602098531096305440906, 5.019049726784267463450058, 1.275366644729965952479585264, 0.5641895835477550741253201704 }; static double Q[] = { 3.3690752069827527677, 9.608965327192787870698, 17.08144074746600431571095, 12.0489519278551290360340491, 9.396034016235054150430579648, 2.260528520767326969591866945, 1.0 }; double num=0.0, den=0.0; int i; num = P[5]; for (i=4; i>=0; --i) { num = x*num + P[i]; } den = Q[6]; for (i=5; i>=0; --i) { den = x*den + Q[i]; } return num/den; } inline static double erfc8(double x) { double e; e = erfc8_sum(x); e *= exp(-x*x); return e; } inline static double log_erfc8(double x) { double e; e = erfc8_sum(x); e = log(e) - x*x; return e; } #if 0 /* Abramowitz+Stegun, 7.2.14 */ static double erfcasympsum(double x) { int i; double e = 1.; double coef = 1.; for (i=1; i<5; ++i) { /* coef *= -(2*i-1)/(2*x*x); ??? [GJ] */ coef *= -(2*i+1)/(i*(4*x*x*x*x)); e += coef; /* if (fabs(coef) < 1.0e-15) break; if (fabs(coef) > 1.0e10) break; [GJ]: These tests are not useful. This function is only used below. Took them out; they gum up the pipeline. */ } return e; } #endif /* 0 */ /* Abramowitz+Stegun, 7.1.5 */ static int erfseries(double x, gsl_sf_result * result) { double coef = x; double e = coef; double del; int k; for (k=1; k<30; ++k) { coef *= -x*x/k; del = coef/(2.0*k+1.0); e += del; } result->val = 2.0 / M_SQRTPI * e; result->err = 2.0 / M_SQRTPI * (fabs(del) + GSL_DBL_EPSILON); return GSL_SUCCESS; } /* Chebyshev fit for erfc((t+1)/2), -1 < t < 1 */ static double erfc_xlt1_data[20] = { 1.06073416421769980345174155056, -0.42582445804381043569204735291, 0.04955262679620434040357683080, 0.00449293488768382749558001242, -0.00129194104658496953494224761, -0.00001836389292149396270416979, 0.00002211114704099526291538556, -5.23337485234257134673693179020e-7, -2.78184788833537885382530989578e-7, 1.41158092748813114560316684249e-8, 2.72571296330561699984539141865e-9, -2.06343904872070629406401492476e-10, -2.14273991996785367924201401812e-11, 2.22990255539358204580285098119e-12, 1.36250074650698280575807934155e-13, -1.95144010922293091898995913038e-14, -6.85627169231704599442806370690e-16, 1.44506492869699938239521607493e-16, 2.45935306460536488037576200030e-18, -9.29599561220523396007359328540e-19 }; static cheb_series erfc_xlt1_cs = { erfc_xlt1_data, 19, -1, 1, 12 }; /* Chebyshev fit for erfc(x) exp(x^2), 1 < x < 5, x = 2t + 3, -1 < t < 1 */ static double erfc_x15_data[25] = { 0.44045832024338111077637466616, -0.143958836762168335790826895326, 0.044786499817939267247056666937, -0.013343124200271211203618353102, 0.003824682739750469767692372556, -0.001058699227195126547306482530, 0.000283859419210073742736310108, -0.000073906170662206760483959432, 0.000018725312521489179015872934, -4.62530981164919445131297264430e-6, 1.11558657244432857487884006422e-6, -2.63098662650834130067808832725e-7, 6.07462122724551777372119408710e-8, -1.37460865539865444777251011793e-8, 3.05157051905475145520096717210e-9, -6.65174789720310713757307724790e-10, 1.42483346273207784489792999706e-10, -3.00141127395323902092018744545e-11, 6.22171792645348091472914001250e-12, -1.26994639225668496876152836555e-12, 2.55385883033257575402681845385e-13, -5.06258237507038698392265499770e-14, 9.89705409478327321641264227110e-15, -1.90685978789192181051961024995e-15, 3.50826648032737849245113757340e-16 }; static cheb_series erfc_x15_cs = { erfc_x15_data, 24, -1, 1, 16 }; /* Chebyshev fit for erfc(x) x exp(x^2), 5 < x < 10, x = (5t + 15)/2, -1 < t < 1 */ static double erfc_x510_data[20] = { 1.11684990123545698684297865808, 0.003736240359381998520654927536, -0.000916623948045470238763619870, 0.000199094325044940833965078819, -0.000040276384918650072591781859, 7.76515264697061049477127605790e-6, -1.44464794206689070402099225301e-6, 2.61311930343463958393485241947e-7, -4.61833026634844152345304095560e-8, 8.00253111512943601598732144340e-9, -1.36291114862793031395712122089e-9, 2.28570483090160869607683087722e-10, -3.78022521563251805044056974560e-11, 6.17253683874528285729910462130e-12, -9.96019290955316888445830597430e-13, 1.58953143706980770269506726000e-13, -2.51045971047162509999527428316e-14, 3.92607828989125810013581287560e-15, -6.07970619384160374392535453420e-16, 9.12600607264794717315507477670e-17 }; static cheb_series erfc_x510_cs = { erfc_x510_data, 19, -1, 1, 12 }; #if 0 inline static double erfc_asymptotic(double x) { return exp(-x*x)/x * erfcasympsum(x) / M_SQRTPI; } inline static double log_erfc_asymptotic(double x) { return log(erfcasympsum(x)/x) - x*x - LogRootPi_; } #endif /* 0 */ /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_erfc_e(double x, gsl_sf_result * result) { const double ax = fabs(x); double e_val, e_err; /* CHECK_POINTER(result) */ if(ax <= 1.0) { double t = 2.0*ax - 1.0; gsl_sf_result c; cheb_eval_e(&erfc_xlt1_cs, t, &c); e_val = c.val; e_err = c.err; } else if(ax <= 5.0) { double ex2 = exp(-x*x); double t = 0.5*(ax-3.0); gsl_sf_result c; cheb_eval_e(&erfc_x15_cs, t, &c); e_val = ex2 * c.val; e_err = ex2 * (c.err + 2.0*fabs(x)*GSL_DBL_EPSILON); } else if(ax < 10.0) { double exterm = exp(-x*x) / ax; double t = (2.0*ax - 15.0)/5.0; gsl_sf_result c; cheb_eval_e(&erfc_x510_cs, t, &c); e_val = exterm * c.val; e_err = exterm * (c.err + 2.0*fabs(x)*GSL_DBL_EPSILON + GSL_DBL_EPSILON); } else { e_val = erfc8(ax); e_err = (x*x + 1.0) * GSL_DBL_EPSILON * fabs(e_val); } if(x < 0.0) { result->val = 2.0 - e_val; result->err = e_err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } else { result->val = e_val; result->err = e_err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return GSL_SUCCESS; } int gsl_sf_log_erfc_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x*x < 10.0*GSL_ROOT6_DBL_EPSILON) { const double y = x / M_SQRTPI; /* series for -1/2 Log[Erfc[Sqrt[Pi] y]] */ const double c3 = (4.0 - M_PI)/3.0; const double c4 = 2.0*(1.0 - M_PI/3.0); const double c5 = -0.001829764677455021; /* (96.0 - 40.0*M_PI + 3.0*M_PI*M_PI)/30.0 */ const double c6 = 0.02629651521057465; /* 2.0*(120.0 - 60.0*M_PI + 7.0*M_PI*M_PI)/45.0 */ const double c7 = -0.01621575378835404; const double c8 = 0.00125993961762116; const double c9 = 0.00556964649138; const double c10 = -0.0045563339802; const double c11 = 0.0009461589032; const double c12 = 0.0013200243174; const double c13 = -0.00142906; const double c14 = 0.00048204; double series = c8 + y*(c9 + y*(c10 + y*(c11 + y*(c12 + y*(c13 + c14*y))))); series = y*(1.0 + y*(1.0 + y*(c3 + y*(c4 + y*(c5 + y*(c6 + y*(c7 + y*series))))))); result->val = -2.0 * series; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* don't like use of log1p(); added above series stuff for small x instead, should be ok [GJ] else if (fabs(x) < 1.0) { gsl_sf_result result_erf; gsl_sf_erf_e(x, &result_erf); result->val = log1p(-result_erf.val); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } */ else if(x > 8.0) { result->val = log_erfc8(x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result result_erfc; gsl_sf_erfc_e(x, &result_erfc); result->val = log(result_erfc.val); result->err = fabs(result_erfc.err / result_erfc.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_erf_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(fabs(x) < 1.0) { return erfseries(x, result); } else { gsl_sf_result result_erfc; gsl_sf_erfc_e(x, &result_erfc); result->val = 1.0 - result_erfc.val; result->err = result_erfc.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_erf_Z_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { const double ex2 = exp(-x*x/2.0); result->val = ex2 / (M_SQRT2 * M_SQRTPI); result->err = fabs(x * result->val) * GSL_DBL_EPSILON; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_erf_Q_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { gsl_sf_result result_erfc; int stat = gsl_sf_erfc_e(x/M_SQRT2, &result_erfc); result->val = 0.5 * result_erfc.val; result->err = 0.5 * result_erfc.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } } int gsl_sf_hazard_e(double x, gsl_sf_result * result) { if(x < 25.0) { gsl_sf_result result_ln_erfc; const int stat_l = gsl_sf_log_erfc_e(x/M_SQRT2, &result_ln_erfc); const double lnc = -0.22579135264472743236; /* ln(sqrt(2/pi)) */ const double arg = lnc - 0.5*x*x - result_ln_erfc.val; const int stat_e = gsl_sf_exp_e(arg, result); result->err += 3.0 * (1.0 + fabs(x)) * GSL_DBL_EPSILON * fabs(result->val); result->err += fabs(result_ln_erfc.err * result->val); return GSL_ERROR_SELECT_2(stat_l, stat_e); } else { const double ix2 = 1.0/(x*x); const double corrB = 1.0 - 9.0*ix2 * (1.0 - 11.0*ix2); const double corrM = 1.0 - 5.0*ix2 * (1.0 - 7.0*ix2 * corrB); const double corrT = 1.0 - ix2 * (1.0 - 3.0*ix2*corrM); result->val = x / corrT; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_erfc(double x) { EVAL_RESULT(gsl_sf_erfc_e(x, &result)); } double gsl_sf_log_erfc(double x) { EVAL_RESULT(gsl_sf_log_erfc_e(x, &result)); } double gsl_sf_erf(double x) { EVAL_RESULT(gsl_sf_erf_e(x, &result)); } double gsl_sf_erf_Z(double x) { EVAL_RESULT(gsl_sf_erf_Z_e(x, &result)); } double gsl_sf_erf_Q(double x) { EVAL_RESULT(gsl_sf_erf_Q_e(x, &result)); } double gsl_sf_hazard(double x) { EVAL_RESULT(gsl_sf_hazard_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__source_gbmv_c.h0000664000176700017670000001342511705263724021506 0ustar paulpaul/* blas/source_gbmv_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; INDEX lenX, lenY, L, U; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if (M == 0 || N == 0) return; if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; if (TransA == CblasNoTrans) { lenX = N; lenY = M; L = KL; U = KU; } else { lenX = M; lenY = N; L = KU; U = KL; } /* form y := beta*y */ if (beta_real == 0.0 && beta_imag == 0.0) { INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { REAL(Y, iy) = 0.0; IMAG(Y, iy) = 0.0; iy += incY; } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { const BASE y_real = REAL(Y, iy); const BASE y_imag = IMAG(Y, iy); const BASE tmpR = y_real * beta_real - y_imag * beta_imag; const BASE tmpI = y_real * beta_imag + y_imag * beta_real; REAL(Y, iy) = tmpR; IMAG(Y, iy) = tmpI; iy += incY; } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; if ((order == CblasRowMajor && TransA == CblasNoTrans) || (order == CblasColMajor && TransA == CblasTrans)) { /* form y := alpha*A*x + y */ INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { BASE dotR = 0.0; BASE dotI = 0.0; const INDEX j_min = (i > L ? i - L : 0); const INDEX j_max = GSL_MIN(lenX, i + U + 1); INDEX ix = OFFSET(lenX, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE x_real = CONST_REAL(X, ix); const BASE x_imag = CONST_IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + (L + j - i)); const BASE A_imag = CONST_IMAG(A, lda * i + (L + j - i)); dotR += A_real * x_real - A_imag * x_imag; dotI += A_real * x_imag + A_imag * x_real; ix += incX; } REAL(Y, iy) += alpha_real * dotR - alpha_imag * dotI; IMAG(Y, iy) += alpha_real * dotI + alpha_imag * dotR; iy += incY; } } else if ((order == CblasRowMajor && TransA == CblasTrans) || (order == CblasColMajor && TransA == CblasNoTrans)) { /* form y := alpha*A'*x + y */ INDEX ix = OFFSET(lenX, incX); for (j = 0; j < lenX; j++) { const BASE x_real = CONST_REAL(X, ix); const BASE x_imag = CONST_IMAG(X, ix); BASE tmpR = alpha_real * x_real - alpha_imag * x_imag; BASE tmpI = alpha_real * x_imag + alpha_imag * x_real; if (!(tmpR == 0.0 && tmpI == 0.0)) { const INDEX i_min = (j > U ? j - U : 0); const INDEX i_max = GSL_MIN(lenY, j + L + 1); INDEX iy = OFFSET(lenY, incY) + i_min * incY; for (i = i_min; i < i_max; i++) { const BASE A_real = CONST_REAL(A, lda * j + (U + i - j)); const BASE A_imag = CONST_IMAG(A, lda * j + (U + i - j)); REAL(Y, iy) += A_real * tmpR - A_imag * tmpI; IMAG(Y, iy) += A_real * tmpI + A_imag * tmpR; iy += incY; } } ix += incX; } } else if (order == CblasRowMajor && TransA == CblasConjTrans) { /* form y := alpha*A^H*x + y */ INDEX ix = OFFSET(lenX, incX); for (j = 0; j < lenX; j++) { const BASE x_real = CONST_REAL(X, ix); const BASE x_imag = CONST_IMAG(X, ix); BASE tmpR = alpha_real * x_real - alpha_imag * x_imag; BASE tmpI = alpha_real * x_imag + alpha_imag * x_real; if (!(tmpR == 0.0 && tmpI == 0.0)) { const INDEX i_min = (j > U ? j - U : 0); const INDEX i_max = GSL_MIN(lenY, j + L + 1); INDEX iy = OFFSET(lenY, incY) + i_min * incY; for (i = i_min; i < i_max; i++) { const BASE A_real = CONST_REAL(A, lda * j + (U + i - j)); const BASE A_imag = CONST_IMAG(A, lda * j + (U + i - j)); REAL(Y, iy) += A_real * tmpR - (-A_imag) * tmpI; IMAG(Y, iy) += A_real * tmpI + (-A_imag) * tmpR; iy += incY; } } ix += incX; } } else if (order == CblasColMajor && TransA == CblasConjTrans) { /* form y := alpha*A^H*x + y */ INDEX iy = OFFSET(lenY, incY); for (i = 0; i < lenY; i++) { BASE dotR = 0.0; BASE dotI = 0.0; const INDEX j_min = (i > L ? i - L : 0); const INDEX j_max = GSL_MIN(lenX, i + U + 1); INDEX ix = OFFSET(lenX, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE x_real = CONST_REAL(X, ix); const BASE x_imag = CONST_IMAG(X, ix); const BASE A_real = CONST_REAL(A, lda * i + (L + j - i)); const BASE A_imag = CONST_IMAG(A, lda * i + (L + j - i)); dotR += A_real * x_real - (-A_imag) * x_imag; dotI += A_real * x_imag + (-A_imag) * x_real; ix += incX; } REAL(Y, iy) += alpha_real * dotR - alpha_imag * dotI; IMAG(Y, iy) += alpha_real * dotI + alpha_imag * dotR; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_fft__c_pass_4.c0000664000176700017670000001221511723710247020043 0ustar paulpaul/* fft/c_pass_4.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int FUNCTION(fft_complex,pass_4) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const gsl_fft_direction sign, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[]) { size_t i = 0, j = 0; size_t k, k1; const size_t factor = 4; const size_t m = n / factor; const size_t q = n / product; const size_t p_1 = product / factor; const size_t jump = (factor - 1) * p_1; for (k = 0; k < q; k++) { ATOMIC w1_real, w1_imag, w2_real, w2_imag, w3_real, w3_imag; if (k == 0) { w1_real = 1.0; w1_imag = 0.0; w2_real = 1.0; w2_imag = 0.0; w3_real = 1.0; w3_imag = 0.0; } else { if (sign == gsl_fft_forward) { /* forward tranform */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = GSL_IMAG(twiddle2[k - 1]); w3_real = GSL_REAL(twiddle3[k - 1]); w3_imag = GSL_IMAG(twiddle3[k - 1]); } else { /* backward tranform: w -> conjugate(w) */ w1_real = GSL_REAL(twiddle1[k - 1]); w1_imag = -GSL_IMAG(twiddle1[k - 1]); w2_real = GSL_REAL(twiddle2[k - 1]); w2_imag = -GSL_IMAG(twiddle2[k - 1]); w3_real = GSL_REAL(twiddle3[k - 1]); w3_imag = -GSL_IMAG(twiddle3[k - 1]); } } for (k1 = 0; k1 < p_1; k1++) { const ATOMIC z0_real = REAL(in,istride,i); const ATOMIC z0_imag = IMAG(in,istride,i); const ATOMIC z1_real = REAL(in,istride,i+m); const ATOMIC z1_imag = IMAG(in,istride,i+m); const ATOMIC z2_real = REAL(in,istride,i+2*m); const ATOMIC z2_imag = IMAG(in,istride,i+2*m); const ATOMIC z3_real = REAL(in,istride,i+3*m); const ATOMIC z3_imag = IMAG(in,istride,i+3*m); /* compute x = W(4) z */ /* t1 = z0 + z2 */ const ATOMIC t1_real = z0_real + z2_real; const ATOMIC t1_imag = z0_imag + z2_imag; /* t2 = z1 + z3 */ const ATOMIC t2_real = z1_real + z3_real; const ATOMIC t2_imag = z1_imag + z3_imag; /* t3 = z0 - z2 */ const ATOMIC t3_real = z0_real - z2_real; const ATOMIC t3_imag = z0_imag - z2_imag; /* t4 = (+/-) (z1 - z3) */ const ATOMIC t4_real = ((int) sign) * (z1_real - z3_real); const ATOMIC t4_imag = ((int) sign) * (z1_imag - z3_imag); /* x0 = t1 + t2 */ const ATOMIC x0_real = t1_real + t2_real; const ATOMIC x0_imag = t1_imag + t2_imag; /* x1 = t3 + i t4 */ const ATOMIC x1_real = t3_real - t4_imag; const ATOMIC x1_imag = t3_imag + t4_real; /* x2 = t1 - t2 */ const ATOMIC x2_real = t1_real - t2_real; const ATOMIC x2_imag = t1_imag - t2_imag; /* x3 = t3 - i t4 */ const ATOMIC x3_real = t3_real + t4_imag; const ATOMIC x3_imag = t3_imag - t4_real; /* apply twiddle factors */ /* to0 = 1 * x0 */ REAL(out,ostride,j) = x0_real; IMAG(out,ostride,j) = x0_imag; /* to1 = w1 * x1 */ REAL(out, ostride, j + p_1) = w1_real * x1_real - w1_imag * x1_imag; IMAG(out, ostride, j + p_1) = w1_real * x1_imag + w1_imag * x1_real; /* to2 = w2 * x2 */ REAL(out, ostride, j + 2 * p_1) = w2_real * x2_real - w2_imag * x2_imag; IMAG(out, ostride, j + 2 * p_1) = w2_real * x2_imag + w2_imag * x2_real; /* to3 = w3 * x3 */ REAL(out, ostride, j + 3 * p_1) = w3_real * x3_real - w3_imag * x3_imag; IMAG(out, ostride, j + 3 * p_1) = w3_real * x3_imag + w3_imag * x3_real; i++; j++; } j += jump; } return 0; } sources_5316/external/gsl/gsl_pow_int.h0000664000176700017670000000476011705263724017047 0ustar paulpaul/* gsl_pow_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_POW_INT_H__ #define __GSL_POW_INT_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS #ifdef HAVE_INLINE extern inline double gsl_pow_2(const double x); extern inline double gsl_pow_3(const double x); extern inline double gsl_pow_4(const double x); extern inline double gsl_pow_5(const double x); extern inline double gsl_pow_6(const double x); extern inline double gsl_pow_7(const double x); extern inline double gsl_pow_8(const double x); extern inline double gsl_pow_9(const double x); extern inline double gsl_pow_2(const double x) { return x*x; } extern inline double gsl_pow_3(const double x) { return x*x*x; } extern inline double gsl_pow_4(const double x) { double x2 = x*x; return x2*x2; } extern inline double gsl_pow_5(const double x) { double x2 = x*x; return x2*x2*x; } extern inline double gsl_pow_6(const double x) { double x2 = x*x; return x2*x2*x2; } extern inline double gsl_pow_7(const double x) { double x3 = x*x*x; return x3*x3*x; } extern inline double gsl_pow_8(const double x) { double x2 = x*x; double x4 = x2*x2; return x4*x4; } extern inline double gsl_pow_9(const double x) { double x3 = x*x*x; return x3*x3*x3; } #else double gsl_pow_2(const double x); double gsl_pow_3(const double x); double gsl_pow_4(const double x); double gsl_pow_5(const double x); double gsl_pow_6(const double x); double gsl_pow_7(const double x); double gsl_pow_8(const double x); double gsl_pow_9(const double x); #endif double gsl_pow_int(double x, int n); __END_DECLS #endif /* __GSL_POW_INT_H__ */ sources_5316/external/gsl/gsl_combination__file.c0000664000176700017670000000464111723710247021016 0ustar paulpaul/* combination/file.c * based on permutation/file.c by Brian Gough * * Copyright (C) 2001 Szymon Jaroszewicz * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_combination.h" #define IN_FORMAT "%lu" int gsl_combination_fread (FILE * stream, gsl_combination * c) { size_t k = c->k ; size_t * data = c->data ; size_t items = fread (data, sizeof (size_t), k, stream); if (items != k) { GSL_ERROR ("fread failed", GSL_EFAILED); } return GSL_SUCCESS; } int gsl_combination_fwrite (FILE * stream, const gsl_combination * c) { size_t k = c->k ; size_t * data = c->data ; size_t items = fwrite (data, sizeof (size_t), k, stream); if (items != k) { GSL_ERROR ("fwrite failed", GSL_EFAILED); } return GSL_SUCCESS; } int gsl_combination_fprintf (FILE * stream, const gsl_combination * c, const char *format) { size_t k = c->k ; size_t * data = c->data ; size_t i; for (i = 0; i < k; i++) { int status = fprintf (stream, format, data[i]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } } return GSL_SUCCESS; } int gsl_combination_fscanf (FILE * stream, gsl_combination * c) { size_t k = c->k ; size_t * data = c->data ; size_t i; for (i = 0; i < k; i++) { unsigned long j ; /* FIXME: what if size_t != unsigned long ??? want read in size_t but have to read in unsigned long to avoid error from compiler */ int status = fscanf (stream, IN_FORMAT, &j); if (status != 1) { GSL_ERROR ("fscanf failed", GSL_EFAILED); } data[i] = j; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cdf__fdist.c0000664000176700017670000000341111723710247017434 0ustar paulpaul/* cdf/fdist.c * * Copyright (C) 2002 Przemyslaw Sliwa and Jason H. Stover. * Copyright (C) 2006, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include "gsl__config.h" #include #include "gsl_cdf.h" #include "gsl_sf_gamma.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_cdf__error.h" #include "gsl_cdf__beta_inc.c" /* * Lower tail. */ double gsl_cdf_fdist_P (const double x, const double nu1, const double nu2) { double P; double r = nu2 / nu1; if (x < r) { double u = x / (r + x); P = beta_inc_AXPY (1.0, 0.0, nu1 / 2.0, nu2 / 2.0, u); } else { double u = r / (r + x); P = beta_inc_AXPY (-1.0, 1.0, nu2 / 2.0, nu1 / 2.0, u); } return P; } /* * Upper tail. */ double gsl_cdf_fdist_Q (const double x, const double nu1, const double nu2) { double Q; double r = nu2 / nu1; if (x < r) { double u = x / (r + x); Q = beta_inc_AXPY (-1.0, 1.0, nu1 / 2.0, nu2 / 2.0, u); } else { double u = r / (r + x); Q = beta_inc_AXPY (1.0, 0.0, nu2 / 2.0, nu1 / 2.0, u); } return Q; } sources_5316/external/gsl/gsl_ode-initval__cstd.c0000664000176700017670000001056011723710247020742 0ustar paulpaul/* ode-initval/cstd.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_math.h" #include "gsl_odeiv.h" typedef struct { double eps_abs; double eps_rel; double a_y; double a_dydt; } std_control_state_t; static void * std_control_alloc (void) { std_control_state_t * s = (std_control_state_t *) malloc (sizeof(std_control_state_t)); if (s == 0) { GSL_ERROR_NULL ("failed to allocate space for std_control_state", GSL_ENOMEM); } return s; } static int std_control_init (void * vstate, double eps_abs, double eps_rel, double a_y, double a_dydt) { std_control_state_t * s = (std_control_state_t *) vstate; if (eps_abs < 0) { GSL_ERROR ("eps_abs is negative", GSL_EINVAL); } else if (eps_rel < 0) { GSL_ERROR ("eps_rel is negative", GSL_EINVAL); } else if (a_y < 0) { GSL_ERROR ("a_y is negative", GSL_EINVAL); } else if (a_dydt < 0) { GSL_ERROR ("a_dydt is negative", GSL_EINVAL); } s->eps_rel = eps_rel; s->eps_abs = eps_abs; s->a_y = a_y; s->a_dydt = a_dydt; return GSL_SUCCESS; } static int std_control_hadjust(void * vstate, size_t dim, unsigned int ord, const double y[], const double yerr[], const double yp[], double * h) { std_control_state_t *state = (std_control_state_t *) vstate; const double eps_abs = state->eps_abs; const double eps_rel = state->eps_rel; const double a_y = state->a_y; const double a_dydt = state->a_dydt; const double S = 0.9; const double h_old = *h; double rmax = DBL_MIN; size_t i; for(i=0; i 1.1) { /* decrease step, no more than factor of 5, but a fraction S more than scaling suggests (for better accuracy) */ double r = S / pow(rmax, 1.0/ord); if (r < 0.2) r = 0.2; *h = r * h_old; return GSL_ODEIV_HADJ_DEC; } else if(rmax < 0.5) { /* increase step, no more than factor of 5 */ double r = S / pow(rmax, 1.0/(ord+1.0)); if (r > 5.0) r = 5.0; if (r < 1.0) /* don't allow any decrease caused by S<1 */ r = 1.0; *h = r * h_old; return GSL_ODEIV_HADJ_INC; } else { /* no change */ return GSL_ODEIV_HADJ_NIL; } } static void std_control_free (void * vstate) { std_control_state_t *state = (std_control_state_t *) vstate; free (state); } static const gsl_odeiv_control_type std_control_type = {"standard", /* name */ &std_control_alloc, &std_control_init, &std_control_hadjust, &std_control_free}; const gsl_odeiv_control_type *gsl_odeiv_control_standard = &std_control_type; gsl_odeiv_control * gsl_odeiv_control_standard_new(double eps_abs, double eps_rel, double a_y, double a_dydt) { gsl_odeiv_control * c = gsl_odeiv_control_alloc (gsl_odeiv_control_standard); int status = gsl_odeiv_control_init (c, eps_abs, eps_rel, a_y, a_dydt); if (status != GSL_SUCCESS) { gsl_odeiv_control_free (c); GSL_ERROR_NULL ("error trying to initialize control", status); } return c; } gsl_odeiv_control * gsl_odeiv_control_y_new(double eps_abs, double eps_rel) { return gsl_odeiv_control_standard_new(eps_abs, eps_rel, 1.0, 0.0); } gsl_odeiv_control * gsl_odeiv_control_yp_new(double eps_abs, double eps_rel) { return gsl_odeiv_control_standard_new(eps_abs, eps_rel, 0.0, 1.0); } sources_5316/external/gsl/gsl_sf_gegenbauer.h0000664000176700017670000000414611705263724020162 0ustar paulpaul/* specfunc/gsl_sf_gegenbauer.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_GEGENBAUER_H__ #define __GSL_SF_GEGENBAUER_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Evaluate Gegenbauer polynomials * using explicit representations. * * exceptions: none */ int gsl_sf_gegenpoly_1_e(double lambda, double x, gsl_sf_result * result); int gsl_sf_gegenpoly_2_e(double lambda, double x, gsl_sf_result * result); int gsl_sf_gegenpoly_3_e(double lambda, double x, gsl_sf_result * result); double gsl_sf_gegenpoly_1(double lambda, double x); double gsl_sf_gegenpoly_2(double lambda, double x); double gsl_sf_gegenpoly_3(double lambda, double x); /* Evaluate Gegenbauer polynomials. * * lambda > -1/2, n >= 0 * exceptions: GSL_EDOM */ int gsl_sf_gegenpoly_n_e(int n, double lambda, double x, gsl_sf_result * result); double gsl_sf_gegenpoly_n(int n, double lambda, double x); /* Calculate array of Gegenbauer polynomials * for n = (0, 1, 2, ... nmax) * * lambda > -1/2, nmax >= 0 * exceptions: GSL_EDOM */ int gsl_sf_gegenpoly_array(int nmax, double lambda, double x, double * result_array); __END_DECLS #endif /* __GSL_SF_GEGENBAUER_H__ */ sources_5316/external/gsl/gsl_eigen__gensymmv.c0000664000176700017670000001213511723710247020526 0ustar paulpaul/* eigen/gensymmv.c * * Copyright (C) 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include "gsl__config.h" #include "gsl_eigen.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_blas.h" #include "gsl_vector.h" #include "gsl_matrix.h" /* * This module computes the eigenvalues and eigenvectors of a real * generalized symmetric-definite eigensystem A x = \lambda B x, where * A and B are symmetric, and B is positive-definite. */ static void gensymmv_normalize_eigenvectors(gsl_matrix *evec); /* gsl_eigen_gensymmv_alloc() Allocate a workspace for solving the generalized symmetric-definite eigenvalue problem. The size of this workspace is O(4n). Inputs: n - size of matrices Return: pointer to workspace */ gsl_eigen_gensymmv_workspace * gsl_eigen_gensymmv_alloc(const size_t n) { gsl_eigen_gensymmv_workspace *w; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = calloc (1, sizeof (gsl_eigen_gensymmv_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->size = n; w->symmv_workspace_p = gsl_eigen_symmv_alloc(n); if (!w->symmv_workspace_p) { gsl_eigen_gensymmv_free(w); GSL_ERROR_NULL("failed to allocate space for symmv workspace", GSL_ENOMEM); } return (w); } /* gsl_eigen_gensymmv_alloc() */ /* gsl_eigen_gensymmv_free() Free workspace w */ void gsl_eigen_gensymmv_free (gsl_eigen_gensymmv_workspace * w) { if (w->symmv_workspace_p) gsl_eigen_symmv_free(w->symmv_workspace_p); free(w); } /* gsl_eigen_gensymmv_free() */ /* gsl_eigen_gensymmv() Solve the generalized symmetric-definite eigenvalue problem A x = \lambda B x for the eigenvalues \lambda and eigenvectors x. Inputs: A - real symmetric matrix B - real symmetric and positive definite matrix eval - where to store eigenvalues evec - where to store eigenvectors w - workspace Return: success or error */ int gsl_eigen_gensymmv (gsl_matrix * A, gsl_matrix * B, gsl_vector * eval, gsl_matrix * evec, gsl_eigen_gensymmv_workspace * w) { const size_t N = A->size1; /* check matrix and vector sizes */ if (N != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if ((N != B->size1) || (N != B->size2)) { GSL_ERROR ("B matrix dimensions must match A", GSL_EBADLEN); } else if (eval->size != N) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (evec->size1 != evec->size2) { GSL_ERROR ("eigenvector matrix must be square", GSL_ENOTSQR); } else if (evec->size1 != N) { GSL_ERROR ("eigenvector matrix has wrong size", GSL_EBADLEN); } else if (w->size != N) { GSL_ERROR ("matrix size does not match workspace", GSL_EBADLEN); } else { int s; /* compute Cholesky factorization of B */ s = gsl_linalg_cholesky_decomp(B); if (s != GSL_SUCCESS) return s; /* B is not positive definite */ /* transform to standard symmetric eigenvalue problem */ gsl_eigen_gensymm_standardize(A, B); /* compute eigenvalues and eigenvectors */ s = gsl_eigen_symmv(A, eval, evec, w->symmv_workspace_p); if (s != GSL_SUCCESS) return s; /* backtransform eigenvectors: evec -> L^{-T} evec */ gsl_blas_dtrsm(CblasLeft, CblasLower, CblasTrans, CblasNonUnit, 1.0, B, evec); /* the blas call destroyed the normalization - renormalize */ gensymmv_normalize_eigenvectors(evec); return GSL_SUCCESS; } } /* gsl_eigen_gensymmv() */ /******************************************** * INTERNAL ROUTINES * ********************************************/ /* gensymmv_normalize_eigenvectors() Normalize eigenvectors so that their Euclidean norm is 1 Inputs: evec - eigenvectors */ static void gensymmv_normalize_eigenvectors(gsl_matrix *evec) { const size_t N = evec->size1; size_t i; /* looping */ for (i = 0; i < N; ++i) { gsl_vector_view vi = gsl_matrix_column(evec, i); double scale = 1.0 / gsl_blas_dnrm2(&vi.vector); gsl_blas_dscal(scale, &vi.vector); } } /* gensymmv_normalize_eigenvectors() */ sources_5316/external/gsl/gsl_vector__init.c0000664000176700017670000000362311723710247020041 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_vector.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__init_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_fft_complex_float.h0000664000176700017670000001233111705263724021054 0ustar paulpaul/* fft/gsl_fft_complex_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_FFT_COMPLEX_FLOAT_H__ #define __GSL_FFT_COMPLEX_FLOAT_H__ #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_fft.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Power of 2 routines */ int gsl_fft_complex_float_radix2_forward (gsl_complex_packed_array_float data, const size_t stride, const size_t n); int gsl_fft_complex_float_radix2_backward (gsl_complex_packed_array_float data, const size_t stride, const size_t n); int gsl_fft_complex_float_radix2_inverse (gsl_complex_packed_array_float data, const size_t stride, const size_t n); int gsl_fft_complex_float_radix2_transform (gsl_complex_packed_array_float data, const size_t stride, const size_t n, const gsl_fft_direction sign); int gsl_fft_complex_float_radix2_dif_forward (gsl_complex_packed_array_float data, const size_t stride, const size_t n); int gsl_fft_complex_float_radix2_dif_backward (gsl_complex_packed_array_float data, const size_t stride, const size_t n); int gsl_fft_complex_float_radix2_dif_inverse (gsl_complex_packed_array_float data, const size_t stride, const size_t n); int gsl_fft_complex_float_radix2_dif_transform (gsl_complex_packed_array_float data, const size_t stride, const size_t n, const gsl_fft_direction sign); /* Mixed Radix general-N routines */ typedef struct { size_t n; size_t nf; size_t factor[64]; gsl_complex_float *twiddle[64]; gsl_complex_float *trig; } gsl_fft_complex_wavetable_float; typedef struct { size_t n; float *scratch; } gsl_fft_complex_workspace_float; gsl_fft_complex_wavetable_float *gsl_fft_complex_wavetable_float_alloc (size_t n); void gsl_fft_complex_wavetable_float_free (gsl_fft_complex_wavetable_float * wavetable); gsl_fft_complex_workspace_float *gsl_fft_complex_workspace_float_alloc (size_t n); void gsl_fft_complex_workspace_float_free (gsl_fft_complex_workspace_float * workspace); int gsl_fft_complex_float_memcpy (gsl_fft_complex_wavetable_float * dest, gsl_fft_complex_wavetable_float * src); int gsl_fft_complex_float_forward (gsl_complex_packed_array_float data, const size_t stride, const size_t n, const gsl_fft_complex_wavetable_float * wavetable, gsl_fft_complex_workspace_float * work); int gsl_fft_complex_float_backward (gsl_complex_packed_array_float data, const size_t stride, const size_t n, const gsl_fft_complex_wavetable_float * wavetable, gsl_fft_complex_workspace_float * work); int gsl_fft_complex_float_inverse (gsl_complex_packed_array_float data, const size_t stride, const size_t n, const gsl_fft_complex_wavetable_float * wavetable, gsl_fft_complex_workspace_float * work); int gsl_fft_complex_float_transform (gsl_complex_packed_array_float data, const size_t stride, const size_t n, const gsl_fft_complex_wavetable_float * wavetable, gsl_fft_complex_workspace_float * work, const gsl_fft_direction sign); __END_DECLS #endif /* __GSL_FFT_COMPLEX_FLOAT_H__ */ sources_5316/external/gsl/gsl_ieee-utils__fp-gnum68k.c0000664000176700017670000000526311723710247021545 0ustar paulpaul/* ieee-utils/fp-gnum68k.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl_errno.h" #include "gsl_ieee_utils.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { unsigned short mode = 0 ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: mode |= _FPU_SINGLE ; break ; case GSL_IEEE_DOUBLE_PRECISION: mode |= _FPU_DOUBLE ; break ; case GSL_IEEE_EXTENDED_PRECISION: mode |= _FPU_EXTENDED ; break ; default: mode |= _FPU_EXTENDED ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: mode |= _FPU_RC_NEAREST ; break ; case GSL_IEEE_ROUND_DOWN: mode |= _FPU_RC_DOWN ; break ; case GSL_IEEE_ROUND_UP: mode |= _FPU_RC_UP ; break ; case GSL_IEEE_ROUND_TO_ZERO: mode |= _FPU_RC_ZERO ; break ; default: mode |= _FPU_RC_NEAREST ; } /* FIXME: I don't have documentation for the M68K so I'm not sure about the mapping of the exceptions below. Maybe someone who does know could correct this. */ if (exception_mask & GSL_IEEE_MASK_INVALID) mode |= _FPU_MASK_OPERR ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("the denormalized operand exception has not been implemented for m68k yet. Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; /*mode |= _FPU_MASK_DM ; ???? */ } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode |= _FPU_MASK_DZ ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode |= _FPU_MASK_OVFL ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode |= _FPU_MASK_UNFL ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode &= ~ (_FPU_MASK_INEX1 | _FPU_MASK_INEX2) ; } else { mode |= (_FPU_MASK_INEX1 | _FPU_MASK_INEX2) ; } _FPU_SETCW(mode) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_permute_vector_complex_float.h0000664000176700017670000000277611705263724023354 0ustar paulpaul/* permutation/gsl_permute_vector_complex_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_COMPLEX_FLOAT_H__ #define __GSL_PERMUTE_VECTOR_COMPLEX_FLOAT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_complex_float.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_complex_float (const gsl_permutation * p, gsl_vector_complex_float * v); int gsl_permute_vector_complex_float_inverse (const gsl_permutation * p, gsl_vector_complex_float * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_COMPLEX_FLOAT_H__ */ sources_5316/external/gsl/gsl_histogram__urand.c0000664000176700017670000000173611723710247020705 0ustar paulpaul/* histogram/urand.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static double urand (void); static double urand (void) { static unsigned long int x = 1; x = (1103515245 * x + 12345) & 0x7fffffffUL ; return x / 2147483648.0 ; } sources_5316/external/gsl/gsl_matrix_float.h0000664000176700017670000002677011705263724020066 0ustar paulpaul/* matrix/gsl_matrix_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_FLOAT_H__ #define __GSL_MATRIX_FLOAT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_float.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; float * data; gsl_block_float * block; int owner; } gsl_matrix_float; typedef struct { gsl_matrix_float matrix; } _gsl_matrix_float_view; typedef _gsl_matrix_float_view gsl_matrix_float_view; typedef struct { gsl_matrix_float matrix; } _gsl_matrix_float_const_view; typedef const _gsl_matrix_float_const_view gsl_matrix_float_const_view; /* Allocation */ gsl_matrix_float * gsl_matrix_float_alloc (const size_t n1, const size_t n2); gsl_matrix_float * gsl_matrix_float_calloc (const size_t n1, const size_t n2); gsl_matrix_float * gsl_matrix_float_alloc_from_block (gsl_block_float * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_float * gsl_matrix_float_alloc_from_matrix (gsl_matrix_float * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_float * gsl_vector_float_alloc_row_from_matrix (gsl_matrix_float * m, const size_t i); gsl_vector_float * gsl_vector_float_alloc_col_from_matrix (gsl_matrix_float * m, const size_t j); void gsl_matrix_float_free (gsl_matrix_float * m); /* Views */ _gsl_matrix_float_view gsl_matrix_float_submatrix (gsl_matrix_float * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_float_view gsl_matrix_float_row (gsl_matrix_float * m, const size_t i); _gsl_vector_float_view gsl_matrix_float_column (gsl_matrix_float * m, const size_t j); _gsl_vector_float_view gsl_matrix_float_diagonal (gsl_matrix_float * m); _gsl_vector_float_view gsl_matrix_float_subdiagonal (gsl_matrix_float * m, const size_t k); _gsl_vector_float_view gsl_matrix_float_superdiagonal (gsl_matrix_float * m, const size_t k); _gsl_vector_float_view gsl_matrix_float_subrow (gsl_matrix_float * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_float_view gsl_matrix_float_subcolumn (gsl_matrix_float * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_float_view gsl_matrix_float_view_array (float * base, const size_t n1, const size_t n2); _gsl_matrix_float_view gsl_matrix_float_view_array_with_tda (float * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_float_view gsl_matrix_float_view_vector (gsl_vector_float * v, const size_t n1, const size_t n2); _gsl_matrix_float_view gsl_matrix_float_view_vector_with_tda (gsl_vector_float * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_float_const_view gsl_matrix_float_const_submatrix (const gsl_matrix_float * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_float_const_view gsl_matrix_float_const_row (const gsl_matrix_float * m, const size_t i); _gsl_vector_float_const_view gsl_matrix_float_const_column (const gsl_matrix_float * m, const size_t j); _gsl_vector_float_const_view gsl_matrix_float_const_diagonal (const gsl_matrix_float * m); _gsl_vector_float_const_view gsl_matrix_float_const_subdiagonal (const gsl_matrix_float * m, const size_t k); _gsl_vector_float_const_view gsl_matrix_float_const_superdiagonal (const gsl_matrix_float * m, const size_t k); _gsl_vector_float_const_view gsl_matrix_float_const_subrow (const gsl_matrix_float * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_float_const_view gsl_matrix_float_const_subcolumn (const gsl_matrix_float * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_float_const_view gsl_matrix_float_const_view_array (const float * base, const size_t n1, const size_t n2); _gsl_matrix_float_const_view gsl_matrix_float_const_view_array_with_tda (const float * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_float_const_view gsl_matrix_float_const_view_vector (const gsl_vector_float * v, const size_t n1, const size_t n2); _gsl_matrix_float_const_view gsl_matrix_float_const_view_vector_with_tda (const gsl_vector_float * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ float gsl_matrix_float_get(const gsl_matrix_float * m, const size_t i, const size_t j); void gsl_matrix_float_set(gsl_matrix_float * m, const size_t i, const size_t j, const float x); float * gsl_matrix_float_ptr(gsl_matrix_float * m, const size_t i, const size_t j); const float * gsl_matrix_float_const_ptr(const gsl_matrix_float * m, const size_t i, const size_t j); void gsl_matrix_float_set_zero (gsl_matrix_float * m); void gsl_matrix_float_set_identity (gsl_matrix_float * m); void gsl_matrix_float_set_all (gsl_matrix_float * m, float x); int gsl_matrix_float_fread (FILE * stream, gsl_matrix_float * m) ; int gsl_matrix_float_fwrite (FILE * stream, const gsl_matrix_float * m) ; int gsl_matrix_float_fscanf (FILE * stream, gsl_matrix_float * m); int gsl_matrix_float_fprintf (FILE * stream, const gsl_matrix_float * m, const char * format); int gsl_matrix_float_memcpy(gsl_matrix_float * dest, const gsl_matrix_float * src); int gsl_matrix_float_swap(gsl_matrix_float * m1, gsl_matrix_float * m2); int gsl_matrix_float_swap_rows(gsl_matrix_float * m, const size_t i, const size_t j); int gsl_matrix_float_swap_columns(gsl_matrix_float * m, const size_t i, const size_t j); int gsl_matrix_float_swap_rowcol(gsl_matrix_float * m, const size_t i, const size_t j); int gsl_matrix_float_transpose (gsl_matrix_float * m); int gsl_matrix_float_transpose_memcpy (gsl_matrix_float * dest, const gsl_matrix_float * src); float gsl_matrix_float_max (const gsl_matrix_float * m); float gsl_matrix_float_min (const gsl_matrix_float * m); void gsl_matrix_float_minmax (const gsl_matrix_float * m, float * min_out, float * max_out); void gsl_matrix_float_max_index (const gsl_matrix_float * m, size_t * imax, size_t *jmax); void gsl_matrix_float_min_index (const gsl_matrix_float * m, size_t * imin, size_t *jmin); void gsl_matrix_float_minmax_index (const gsl_matrix_float * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_float_isnull (const gsl_matrix_float * m); int gsl_matrix_float_ispos (const gsl_matrix_float * m); int gsl_matrix_float_isneg (const gsl_matrix_float * m); int gsl_matrix_float_isnonneg (const gsl_matrix_float * m); int gsl_matrix_float_add (gsl_matrix_float * a, const gsl_matrix_float * b); int gsl_matrix_float_sub (gsl_matrix_float * a, const gsl_matrix_float * b); int gsl_matrix_float_mul_elements (gsl_matrix_float * a, const gsl_matrix_float * b); int gsl_matrix_float_div_elements (gsl_matrix_float * a, const gsl_matrix_float * b); int gsl_matrix_float_scale (gsl_matrix_float * a, const double x); int gsl_matrix_float_add_constant (gsl_matrix_float * a, const double x); int gsl_matrix_float_add_diagonal (gsl_matrix_float * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_float_get_row(gsl_vector_float * v, const gsl_matrix_float * m, const size_t i); int gsl_matrix_float_get_col(gsl_vector_float * v, const gsl_matrix_float * m, const size_t j); int gsl_matrix_float_set_row(gsl_matrix_float * m, const size_t i, const gsl_vector_float * v); int gsl_matrix_float_set_col(gsl_matrix_float * m, const size_t j, const gsl_vector_float * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline float gsl_matrix_float_get(const gsl_matrix_float * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_float_set(gsl_matrix_float * m, const size_t i, const size_t j, const float x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline float * gsl_matrix_float_ptr(gsl_matrix_float * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (float *) (m->data + (i * m->tda + j)) ; } extern inline const float * gsl_matrix_float_const_ptr(const gsl_matrix_float * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const float *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_FLOAT_H__ */ sources_5316/external/gsl/gsl_multiroots__hybrid.c0000664000176700017670000003472711723710247021307 0ustar paulpaul/* multiroots/hybrid.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multiroots.h" #include "gsl_linalg.h" #include "gsl_multiroots__dogleg.c" typedef struct { size_t iter; size_t ncfail; size_t ncsuc; size_t nslow1; size_t nslow2; double fnorm; double delta; gsl_matrix *J; gsl_matrix *q; gsl_matrix *r; gsl_vector *tau; gsl_vector *diag; gsl_vector *qtf; gsl_vector *newton; gsl_vector *gradient; gsl_vector *x_trial; gsl_vector *f_trial; gsl_vector *df; gsl_vector *qtdf; gsl_vector *rdx; gsl_vector *w; gsl_vector *v; } hybrid_state_t; static int hybrid_alloc (void *vstate, size_t n); static int hybrid_set (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx); static int hybrids_set (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx); static int set (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx, int scale); static int hybrid_iterate (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx); static void hybrid_free (void *vstate); static int iterate (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx, int scale); static int hybrid_alloc (void *vstate, size_t n) { hybrid_state_t *state = (hybrid_state_t *) vstate; gsl_matrix *J, *q, *r; gsl_vector *tau, *diag, *qtf, *newton, *gradient, *x_trial, *f_trial, *df, *qtdf, *rdx, *w, *v; J = gsl_matrix_calloc (n, n); if (J == 0) { GSL_ERROR ("failed to allocate space for J", GSL_ENOMEM); } state->J = J; q = gsl_matrix_calloc (n, n); if (q == 0) { gsl_matrix_free (J); GSL_ERROR ("failed to allocate space for q", GSL_ENOMEM); } state->q = q; r = gsl_matrix_calloc (n, n); if (r == 0) { gsl_matrix_free (J); gsl_matrix_free (q); GSL_ERROR ("failed to allocate space for r", GSL_ENOMEM); } state->r = r; tau = gsl_vector_calloc (n); if (tau == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); GSL_ERROR ("failed to allocate space for tau", GSL_ENOMEM); } state->tau = tau; diag = gsl_vector_calloc (n); if (diag == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); GSL_ERROR ("failed to allocate space for diag", GSL_ENOMEM); } state->diag = diag; qtf = gsl_vector_calloc (n); if (qtf == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); GSL_ERROR ("failed to allocate space for qtf", GSL_ENOMEM); } state->qtf = qtf; newton = gsl_vector_calloc (n); if (newton == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); GSL_ERROR ("failed to allocate space for newton", GSL_ENOMEM); } state->newton = newton; gradient = gsl_vector_calloc (n); if (gradient == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); GSL_ERROR ("failed to allocate space for gradient", GSL_ENOMEM); } state->gradient = gradient; x_trial = gsl_vector_calloc (n); if (x_trial == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); GSL_ERROR ("failed to allocate space for x_trial", GSL_ENOMEM); } state->x_trial = x_trial; f_trial = gsl_vector_calloc (n); if (f_trial == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); GSL_ERROR ("failed to allocate space for f_trial", GSL_ENOMEM); } state->f_trial = f_trial; df = gsl_vector_calloc (n); if (df == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); GSL_ERROR ("failed to allocate space for df", GSL_ENOMEM); } state->df = df; qtdf = gsl_vector_calloc (n); if (qtdf == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); GSL_ERROR ("failed to allocate space for qtdf", GSL_ENOMEM); } state->qtdf = qtdf; rdx = gsl_vector_calloc (n); if (rdx == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (qtdf); GSL_ERROR ("failed to allocate space for rdx", GSL_ENOMEM); } state->rdx = rdx; w = gsl_vector_calloc (n); if (w == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (qtdf); gsl_vector_free (rdx); GSL_ERROR ("failed to allocate space for w", GSL_ENOMEM); } state->w = w; v = gsl_vector_calloc (n); if (v == 0) { gsl_matrix_free (J); gsl_matrix_free (q); gsl_matrix_free (r); gsl_vector_free (tau); gsl_vector_free (diag); gsl_vector_free (qtf); gsl_vector_free (newton); gsl_vector_free (gradient); gsl_vector_free (x_trial); gsl_vector_free (f_trial); gsl_vector_free (df); gsl_vector_free (qtdf); gsl_vector_free (rdx); gsl_vector_free (w); GSL_ERROR ("failed to allocate space for v", GSL_ENOMEM); } state->v = v; return GSL_SUCCESS; } static int hybrid_set (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx) { int status = set (vstate, func, x, f, dx, 0); return status; } static int hybrids_set (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx) { int status = set (vstate, func, x, f, dx, 1); return status; } static int set (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx, int scale) { hybrid_state_t *state = (hybrid_state_t *) vstate; gsl_matrix *J = state->J; gsl_matrix *q = state->q; gsl_matrix *r = state->r; gsl_vector *tau = state->tau; gsl_vector *diag = state->diag; int status; status = GSL_MULTIROOT_FN_EVAL (func, x, f); if (status) { return status; } status = gsl_multiroot_fdjacobian (func, x, f, GSL_SQRT_DBL_EPSILON, J); if (status) { return status; } state->iter = 1; state->fnorm = enorm (f); state->ncfail = 0; state->ncsuc = 0; state->nslow1 = 0; state->nslow2 = 0; gsl_vector_set_all (dx, 0.0); /* Store column norms in diag */ if (scale) compute_diag (J, diag); else gsl_vector_set_all (diag, 1.0); /* Set delta to factor |D x| or to factor if |D x| is zero */ state->delta = compute_delta (diag, x); /* Factorize J into QR decomposition */ status = gsl_linalg_QR_decomp (J, tau); if (status) { return status; } status = gsl_linalg_QR_unpack (J, tau, q, r); return status; } static int hybrid_iterate (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx) { int status = iterate (vstate, func, x, f, dx, 0); return status; } static int hybrids_iterate (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx) { int status = iterate (vstate, func, x, f, dx, 1); return status; } static int iterate (void *vstate, gsl_multiroot_function * func, gsl_vector * x, gsl_vector * f, gsl_vector * dx, int scale) { hybrid_state_t *state = (hybrid_state_t *) vstate; const double fnorm = state->fnorm; gsl_matrix *J = state->J; gsl_matrix *q = state->q; gsl_matrix *r = state->r; gsl_vector *tau = state->tau; gsl_vector *diag = state->diag; gsl_vector *qtf = state->qtf; gsl_vector *x_trial = state->x_trial; gsl_vector *f_trial = state->f_trial; gsl_vector *df = state->df; gsl_vector *qtdf = state->qtdf; gsl_vector *rdx = state->rdx; gsl_vector *w = state->w; gsl_vector *v = state->v; double prered, actred; double pnorm, fnorm1, fnorm1p; double ratio; double p1 = 0.1, p5 = 0.5, p001 = 0.001, p0001 = 0.0001; /* Compute qtf = Q^T f */ compute_qtf (q, f, qtf); /* Compute dogleg step */ dogleg (r, qtf, diag, state->delta, state->newton, state->gradient, dx); /* Take a trial step */ compute_trial_step (x, dx, state->x_trial); pnorm = scaled_enorm (diag, dx); if (state->iter == 1) { if (pnorm < state->delta) { state->delta = pnorm; } } /* Evaluate function at x + p */ { int status = GSL_MULTIROOT_FN_EVAL (func, x_trial, f_trial); if (status != GSL_SUCCESS) { return GSL_EBADFUNC; } } /* Set df = f_trial - f */ compute_df (f_trial, f, df); /* Compute the scaled actual reduction */ fnorm1 = enorm (f_trial); actred = compute_actual_reduction (fnorm, fnorm1); /* Compute rdx = R dx */ compute_rdx (r, dx, rdx); /* Compute the scaled predicted reduction phi1p = |Q^T f + R dx| */ fnorm1p = enorm_sum (qtf, rdx); prered = compute_predicted_reduction (fnorm, fnorm1p); /* Compute the ratio of the actual to predicted reduction */ if (prered > 0) { ratio = actred / prered; } else { ratio = 0; } /* Update the step bound */ if (ratio < p1) { state->ncsuc = 0; state->ncfail++; state->delta *= p5; } else { state->ncfail = 0; state->ncsuc++; if (ratio >= p5 || state->ncsuc > 1) state->delta = GSL_MAX (state->delta, pnorm / p5); if (fabs (ratio - 1) <= p1) state->delta = pnorm / p5; } /* Test for successful iteration */ if (ratio >= p0001) { gsl_vector_memcpy (x, x_trial); gsl_vector_memcpy (f, f_trial); state->fnorm = fnorm1; state->iter++; } /* Determine the progress of the iteration */ state->nslow1++; if (actred >= p001) state->nslow1 = 0; if (actred >= p1) state->nslow2 = 0; if (state->ncfail == 2) { gsl_multiroot_fdjacobian (func, x, f, GSL_SQRT_DBL_EPSILON, J); state->nslow2++; if (state->iter == 1) { if (scale) compute_diag (J, diag); state->delta = compute_delta (diag, x); } else { if (scale) update_diag (J, diag); } /* Factorize J into QR decomposition */ gsl_linalg_QR_decomp (J, tau); gsl_linalg_QR_unpack (J, tau, q, r); return GSL_SUCCESS; } /* Compute qtdf = Q^T df, w = (Q^T df - R dx)/|dx|, v = D^2 dx/|dx| */ compute_qtf (q, df, qtdf); compute_wv (qtdf, rdx, dx, diag, pnorm, w, v); /* Rank-1 update of the jacobian Q'R' = Q(R + w v^T) */ gsl_linalg_QR_update (q, r, w, v); /* No progress as measured by jacobian evaluations */ if (state->nslow2 == 5) { return GSL_ENOPROGJ; } /* No progress as measured by function evaluations */ if (state->nslow1 == 10) { return GSL_ENOPROG; } return GSL_SUCCESS; } static void hybrid_free (void *vstate) { hybrid_state_t *state = (hybrid_state_t *) vstate; gsl_vector_free (state->v); gsl_vector_free (state->w); gsl_vector_free (state->rdx); gsl_vector_free (state->qtdf); gsl_vector_free (state->df); gsl_vector_free (state->f_trial); gsl_vector_free (state->x_trial); gsl_vector_free (state->gradient); gsl_vector_free (state->newton); gsl_vector_free (state->qtf); gsl_vector_free (state->diag); gsl_vector_free (state->tau); gsl_matrix_free (state->r); gsl_matrix_free (state->q); gsl_matrix_free (state->J); } static const gsl_multiroot_fsolver_type hybrid_type = { "hybrid", /* name */ sizeof (hybrid_state_t), &hybrid_alloc, &hybrid_set, &hybrid_iterate, &hybrid_free }; static const gsl_multiroot_fsolver_type hybrids_type = { "hybrids", /* name */ sizeof (hybrid_state_t), &hybrid_alloc, &hybrids_set, &hybrids_iterate, &hybrid_free }; const gsl_multiroot_fsolver_type *gsl_multiroot_fsolver_hybrid = &hybrid_type; const gsl_multiroot_fsolver_type *gsl_multiroot_fsolver_hybrids = &hybrids_type; sources_5316/external/gsl/gsl_matrix__oper.c0000664000176700017670000000372511723710247020050 0ustar paulpaul#include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_matrix.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__oper_complex_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__oper_complex_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__oper_complex_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__oper_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_sf__bessel_zero.c0000644000176700017670000007021710707442037020521 0ustar paulpaul/* specfunc/bessel_zero.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_airy.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel_olver.h" /* For Chebyshev expansions of the roots as functions of nu, * see [G. Nemeth, Mathematical Approximation of Special Functions]. * This gives the fits for all nu and s <= 10. * I made the fits for other values of s myself [GJ]. */ /* Chebyshev expansion: j_{nu,1} = c_k T_k*(nu/2), nu <= 2 */ static const double coef_jnu1_a[] = { 3.801775243633476, 1.360704737511120, -0.030707710261106, 0.004526823746202, -0.000808682832134, 0.000159218792489, -0.000033225189761, 0.000007205599763, -0.000001606110397, 0.000000365439424, -0.000000084498039, 0.000000019793815, -0.000000004687054, 0.000000001120052, -0.000000000269767, 0.000000000065420, -0.000000000015961, 0.000000000003914, -0.000000000000965, 0.000000000000239, -0.000000000000059, 0.000000000000015, -0.000000000000004, 0.000000000000001 }; /* Chebyshev expansion: j_{nu,1} = nu c_k T_k*((2/nu)^(2/3)), nu >= 2 */ static const double coef_jnu1_b[] = { 1.735063412537096, 0.784478100951978, 0.048881473180370, -0.000578279783021, -0.000038984957864, 0.000005758297879, -0.000000327583229, -0.000000003853878, 0.000000002284653, -0.000000000153079, -0.000000000000895, 0.000000000000283, 0.000000000000043, 0.000000000000010, -0.000000000000003 }; /* Chebyshev expansion: j_{nu,2} = c_k T_k*(nu/2), nu <= 2 */ static const double coef_jnu2_a[] = { 6.992370244046161, 1.446379282056534, -0.023458616207293, 0.002172149448700, -0.000246262775620, 0.000030990180959, -0.000004154183047, 0.000000580766328, -0.000000083648175, 0.000000012317355, -0.000000001844887, 0.000000000280076, -0.000000000042986, 0.000000000006658, -0.000000000001039, 0.000000000000163, -0.000000000000026, 0.000000000000004, -0.000000000000001 }; /* Chebyshev expansion: j_{nu,2} = nu c_k T_k*((2/nu)^(2/3)), nu >= 2 */ static const double coef_jnu2_b[] = { 2.465611864263400, 1.607952988471069, 0.138758034431497, -0.003687791182054, -0.000051276007868, 0.000045113570749, -0.000007579172152, 0.000000736469208, -0.000000011118527, -0.000000011919884, 0.000000002696788, -0.000000000314488, 0.000000000008124, 0.000000000005211, -0.000000000001292, 0.000000000000158, -0.000000000000004, -0.000000000000003, 0.000000000000001 }; /* Chebyshev expansion: j_{nu,3} = c_k T_k*(nu/3), nu <= 3 */ static const double coef_jnu3_a[] = { 10.869647065239236, 2.177524286141710, -0.034822817125293, 0.003167249102413, -0.000353960349344, 0.000044039086085, -0.000005851380981, 0.000000812575483, -0.000000116463617, 0.000000017091246, -0.000000002554376, 0.000000000387335, -0.000000000059428, 0.000000000009207, -0.000000000001438, 0.000000000000226, -0.000000000000036, 0.000000000000006, -0.000000000000001 }; /* Chebyshev expansion: j_{nu,3} = nu c_k T_k*((3/nu)^(2/3)), nu >= 3 */ static const double coef_jnu3_b[] = { 2.522816775173244, 1.673199424973720, 0.146431617506314, -0.004049001763912, -0.000039517767244, 0.000048781729288, -0.000008729705695, 0.000000928737310, -0.000000028388244, -0.000000012927432, 0.000000003441008, -0.000000000471695, 0.000000000025590, 0.000000000005502, -0.000000000001881, 0.000000000000295, -0.000000000000020, -0.000000000000003, 0.000000000000001 }; /* Chebyshev expansion: j_{nu,4} = c_k T_k*(nu/4), nu <= 4 */ static const double coef_jnu4_a[] = { 14.750310252773009, 2.908010932941708, -0.046093293420315, 0.004147172321412, -0.000459092310473, 0.000056646951906, -0.000007472351546, 0.000001031210065, -0.000000147008137, 0.000000021475218, -0.000000003197208, 0.000000000483249, -0.000000000073946, 0.000000000011431, -0.000000000001782, 0.000000000000280, -0.000000000000044, 0.000000000000007, -0.000000000000001 }; /* Chebyshev expansion: j_{nu,4} = nu c_k T_k*((4/nu)^(2/3)), nu >= 4 */ static const double coef_jnu4_b[] = { 2.551681323117914, 1.706177978336572, 0.150357658406131, -0.004234001378590, -0.000033854229898, 0.000050763551485, -0.000009337464057, 0.000001029717834, -0.000000037474196, -0.000000013450153, 0.000000003836180, -0.000000000557404, 0.000000000035748, 0.000000000005487, -0.000000000002187, 0.000000000000374, -0.000000000000031, -0.000000000000003, 0.000000000000001 }; /* Chebyshev expansion: j_{nu,5} = c_k T_k*(nu/5), nu <= 5 */ static const double coef_jnu5_a[] = { 18.632261081028211, 3.638249012596966, -0.057329705998828, 0.005121709126820, -0.000563325259487, 0.000069100826174, -0.000009066603030, 0.000001245181383, -0.000000176737282, 0.000000025716695, -0.000000003815184, 0.000000000574839, -0.000000000087715, 0.000000000013526, -0.000000000002104, 0.000000000000330, -0.000000000000052, 0.000000000000008, -0.000000000000001 }; /* Chebyshev expansion: j_{nu,5} = nu c_k T_k*((5/nu)^(2/3)), nu >= 5 */ /* FIXME: There is something wrong with this fit, in about the * 9th or 10th decimal place. */ static const double coef_jnu5_b[] = { 2.569079487591442, 1.726073360882134, 0.152740776809531, -0.004346449660148, -0.000030512461856, 0.000052000821080, -0.000009713343981, 0.000001091997863, -0.000000043061707, -0.000000013779413, 0.000000004082870, -0.000000000611259, 0.000000000042242, 0.000000000005448, -0.000000000002377, 0.000000000000424, -0.000000000000038, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,6} = c_k T_k*(nu/6), nu <= 6 */ static const double coef_jnu6_a[] = { 22.514836143374042, 4.368367257557198, -0.068550155285562, 0.006093776505822, -0.000667152784957, 0.000081486022398, -0.000010649011647, 0.000001457089679, -0.000000206105082, 0.000000029894724, -0.000000004422012, 0.000000000664471, -0.000000000101140, 0.000000000015561, -0.000000000002416, 0.000000000000378, -0.000000000000060, 0.000000000000009, -0.000000000000002 }; /* Chebyshev expansion: j_{nu,6} = nu c_k T_k*((6/nu)^(2/3)), nu >= 6 */ static const double coef_jnu6_b[] = { 2.580710285494837, 1.739380728566154, 0.154340696401691, -0.004422028860168, -0.000028305272624, 0.000052845975269, -0.000009968794373, 0.000001134252926, -0.000000046841241, -0.000000014007555, 0.000000004251816, -0.000000000648213, 0.000000000046728, 0.000000000005414, -0.000000000002508, 0.000000000000459, -0.000000000000043, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,7} = c_k T_k*(nu/7), nu <= 7 */ static const double coef_jnu7_a[] = { 26.397760539730869, 5.098418721711790, -0.079761896398948, 0.007064521280487, -0.000770766522482, 0.000093835449636, -0.000012225308542, 0.000001667939800, -0.000000235288157, 0.000000034040347, -0.000000005023142, 0.000000000753101, -0.000000000114389, 0.000000000017564, -0.000000000002722, 0.000000000000425, -0.000000000000067, 0.000000000000011, -0.000000000000002 }; /* Chebyshev expansion: j_{nu,7} = nu c_k T_k*((7/nu)^(2/3)), nu >= 7 */ static const double coef_jnu7_b[] = { 2.589033335856773, 1.748907007612678, 0.155488900387653, -0.004476317805688, -0.000026737952924, 0.000053459680946, -0.000010153699240, 0.000001164804272, -0.000000049566917, -0.000000014175403, 0.000000004374840, -0.000000000675135, 0.000000000050004, 0.000000000005387, -0.000000000002603, 0.000000000000485, -0.000000000000047, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,8} = c_k T_k*(nu/8), nu <= 8 */ static const double coef_jnu8_a[] = { 30.280900001606662, 5.828429205461221, -0.090968381181069, 0.008034479731033, -0.000874254899080, 0.000106164151611, -0.000013798098749, 0.000001878187386, -0.000000264366627, 0.000000038167685, -0.000000005621060, 0.000000000841165, -0.000000000127538, 0.000000000019550, -0.000000000003025, 0.000000000000472, -0.000000000000074, 0.000000000000012, -0.000000000000002 }; /* Chebyshev expansion: j_{nu,8} = nu c_k T_k*((8/nu)^(2/3)), nu >= 8 */ static const double coef_jnu8_b[] = { 2.595283877150078, 1.756063044986928, 0.156352972371030, -0.004517201896761, -0.000025567187878, 0.000053925472558, -0.000010293734486, 0.000001187923085, -0.000000051625122, -0.000000014304212, 0.000000004468450, -0.000000000695620, 0.000000000052500, 0.000000000005367, -0.000000000002676, 0.000000000000505, -0.000000000000050, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,9} = c_k T_k*(nu/9), nu <= 9 */ static const double coef_jnu9_a[] = { 34.164181213238386, 6.558412747925228, -0.102171455365016, 0.009003934361201, -0.000977663914535, 0.000118479876579, -0.000015368714220, 0.000002088064285, -0.000000293381154, 0.000000042283900, -0.000000006217033, 0.000000000928887, -0.000000000140627, 0.000000000021526, -0.000000000003326, 0.000000000000518, -0.000000000000081, 0.000000000000013, -0.000000000000002 }; /* Chebyshev expansion: j_{nu,9} = nu c_k T_k*((9/nu)^(2/3)), nu >= 9 */ static const double coef_jnu9_b[] = { 2.600150240905079, 1.761635491694032, 0.157026743724010, -0.004549100368716, -0.000024659248617, 0.000054291035068, -0.000010403464334, 0.000001206027524, -0.000000053234089, -0.000000014406241, 0.000000004542078, -0.000000000711728, 0.000000000054464, 0.000000000005350, -0.000000000002733, 0.000000000000521, -0.000000000000052, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,10} = c_k T_k*(nu/10), nu <= 10 */ static const double coef_jnu10_a[] = { 38.047560766184647, 7.288377637926008, -0.113372193277897, 0.009973047509098, -0.001081019701335, 0.000130786983847, -0.000016937898538, 0.000002297699179, -0.000000322354218, 0.000000046392941, -0.000000006811759, 0.000000001016395, -0.000000000153677, 0.000000000023486, -0.000000000003616, 0.000000000000561, -0.000000000000095, 0.000000000000027, -0.000000000000013, 0.000000000000005 }; /* Chebyshev expansion: j_{nu,10} = nu c_k T_k*((10/nu)^(2/3)), nu >= 10 */ static const double coef_jnu10_b[] = { 2.604046346867949, 1.766097596481182, 0.157566834446511, -0.004574682244089, -0.000023934500688, 0.000054585558231, -0.000010491765415, 0.000001220589364, -0.000000054526331, -0.000000014489078, 0.000000004601510, -0.000000000724727, 0.000000000056049, 0.000000000005337, -0.000000000002779, 0.000000000000533, -0.000000000000054, -0.000000000000002, 0.000000000000002 }; /* Chebyshev expansion: j_{nu,11} = c_k T_k*(nu/22), nu <= 22 */ static const double coef_jnu11_a[] = { 49.5054081076848637, 15.33692279367165101, -0.33677234163517130, 0.04623235772920729, -0.00781084960665093, 0.00147217395434708, -0.00029695043846867, 0.00006273356860235, -0.00001370575125628, 3.07171282012e-6, -7.0235041249e-7, 1.6320559339e-7, -3.843117306e-8, 9.15083800e-9, -2.19957642e-9, 5.3301703e-10, -1.3007541e-10, 3.193827e-11, -7.88605e-12, 1.95918e-12, -4.9020e-13, 1.2207e-13, -2.820e-14, 5.25e-15, -1.88e-15, 2.80e-15, -2.45e-15 }; /* Chebyshev expansion: j_{nu,12} = c_k T_k*(nu/24), nu <= 24 */ static const double coef_jnu12_a[] = { 54.0787833216641519, 16.7336367772863598, -0.36718411124537953, 0.05035523375053820, -0.00849884978867533, 0.00160027692813434, -0.00032248114889921, 0.00006806354127199, -0.00001485665901339, 3.32668783672e-6, -7.5998952729e-7, 1.7644939709e-7, -4.151538210e-8, 9.87722772e-9, -2.37230133e-9, 5.7442875e-10, -1.4007767e-10, 3.437166e-11, -8.48215e-12, 2.10554e-12, -5.2623e-13, 1.3189e-13, -3.175e-14, 5.73e-15, 5.6e-16, -8.7e-16, -6.5e-16 }; /* Chebyshev expansion: j_{nu,13} = c_k T_k*(nu/26), nu <= 26 */ static const double coef_jnu13_a[] = { 58.6521941921708890, 18.1303398137970284, -0.39759381380126650, 0.05447765240465494, -0.00918674227679980, 0.00172835361420579, -0.00034800528297612, 0.00007339183835188, -0.00001600713368099, 3.58154960392e-6, -8.1759873497e-7, 1.8968523220e-7, -4.459745253e-8, 1.060304419e-8, -2.54487624e-9, 6.1580214e-10, -1.5006751e-10, 3.679707e-11, -9.07159e-12, 2.24713e-12, -5.5943e-13, 1.4069e-13, -3.679e-14, 1.119e-14, -4.99e-15, 3.43e-15, -2.85e-15, 2.3e-15, -1.7e-15, 8.7e-16 }; /* Chebyshev expansion: j_{nu,14} = c_k T_k*(nu/28), nu <= 28 */ static const double coef_jnu14_a[] = { 63.2256329577315566, 19.5270342832914901, -0.42800190567884337, 0.05859971627729398, -0.00987455163523582, 0.00185641011402081, -0.00037352439419968, 0.00007871886257265, -0.00001715728110045, 3.83632624437e-6, -8.7518558668e-7, 2.0291515353e-7, -4.767795233e-8, 1.132844415e-8, -2.71734219e-9, 6.5714886e-10, -1.6005342e-10, 3.922557e-11, -9.66637e-12, 2.39379e-12, -5.9541e-13, 1.4868e-13, -3.726e-14, 9.37e-15, -2.36e-15, 6.0e-16 }; /* Chebyshev expansion: j_{nu,15} = c_k T_k*(nu/30), nu <= 30 */ static const double coef_jnu15_a[] = { 67.7990939565631635, 20.9237219226859859, -0.45840871823085836, 0.06272149946755639, -0.01056229551143042, 0.00198445078693100, -0.00039903958650729, 0.00008404489865469, -0.00001830717574922, 4.09103745566e-6, -9.3275533309e-7, 2.1614056403e-7, -5.075725222e-8, 1.205352081e-8, -2.88971837e-9, 6.9846848e-10, -1.7002946e-10, 4.164941e-11, -1.025859e-11, 2.53921e-12, -6.3128e-13, 1.5757e-13, -3.947e-14, 9.92e-15, -2.50e-15, 6.3e-16 }; /* Chebyshev expansion: j_{nu,16} = c_k T_k*(nu/32), nu <= 32 */ static const double coef_jnu16_a[] = { 72.3725729616724770, 22.32040402918608585, -0.48881449782358690, 0.06684305681828766, -0.01124998690363398, 0.00211247882775445, -0.00042455166484632, 0.00008937015316346, -0.00001945687139551, 4.34569739281e-6, -9.9031173548e-7, 2.2936247195e-7, -5.383562595e-8, 1.277835103e-8, -3.06202860e-9, 7.3977037e-10, -1.8000071e-10, 4.407196e-11, -1.085046e-11, 2.68453e-12, -6.6712e-13, 1.6644e-13, -4.168e-14, 1.047e-14, -2.64e-15, 6.7e-16 }; /* Chebyshev expansion: j_{nu,17} = c_k T_k*(nu/34), nu <= 34 */ static const double coef_jnu17_a[] = { 76.9460667535209549, 23.71708159112252670, -0.51921943142405352, 0.07096442978067622, -0.01193763559341369, 0.00224049662974902, -0.00045006122941781, 0.00009469477941684, -0.00002060640777107, 4.60031647195e-6, -1.04785755046e-6, 2.4258161247e-7, -5.691327087e-8, 1.350298805e-8, -3.23428733e-9, 7.8105847e-10, -1.8996825e-10, 4.649350e-11, -1.144205e-11, 2.82979e-12, -7.0294e-13, 1.7531e-13, -4.388e-14, 1.102e-14, -2.78e-15, 7.0e-16 }; /* Chebyshev expansion: j_{nu,18} = c_k T_k*(nu/36), nu <= 36 */ static const double coef_jnu18_a[] = { 81.5195728368096659, 25.11375537470259305, -0.54962366347317668, 0.07508565026117689, -0.01262524908033818, 0.00236850602019778, -0.00047556873651929, 0.00010001889347161, -0.00002175581482429, 4.85490251239e-6, -1.10539483940e-6, 2.5579853343e-7, -5.999033352e-8, 1.422747129e-8, -3.40650521e-9, 8.2233565e-10, -1.9993286e-10, 4.891426e-11, -1.203343e-11, 2.97498e-12, -7.3875e-13, 1.8418e-13, -4.608e-14, 1.157e-14, -2.91e-15, 7.4e-16 }; /* Chebyshev expansion: j_{nu,19} = c_k T_k*(nu/38), nu <= 38 */ static const double coef_jnu19_a[] = { 86.0930892477047512, 26.51042598308271729, -0.58002730731948358, 0.07920674321589394, -0.01331283320930301, 0.00249650841778073, -0.00050107453900793, 0.00010534258471335, -0.00002290511552874, 5.10946148897e-6, -1.16292517157e-6, 2.6901365037e-7, -6.306692473e-8, 1.495183048e-8, -3.57869025e-9, 8.6360410e-10, -2.0989514e-10, 5.133439e-11, -1.262465e-11, 3.12013e-12, -7.7455e-13, 1.9304e-13, -4.829e-14, 1.212e-14, -3.05e-15, 7.7e-16 }; /* Chebyshev expansion: j_{nu,20} = c_k T_k*(nu/40), nu <= 40 */ static const double coef_jnu20_a[] = { 90.6666144195163770, 27.9070938975436823, -0.61043045315390591, 0.08332772844325554, -0.01400039260208282, 0.00262450494035660, -0.00052657891389470, 0.00011066592304919, -0.00002405432778364, 5.36399803946e-6, -1.22044976064e-6, 2.8222728362e-7, -6.614312964e-8, 1.567608839e-8, -3.75084856e-9, 9.0486546e-10, -2.1985553e-10, 5.375401e-11, -1.321572e-11, 3.26524e-12, -8.1033e-13, 2.0190e-13, -5.049e-14, 1.267e-14, -3.19e-15, 8.0e-16, -2.0e-16 }; static const double * coef_jnu_a[] = { 0, coef_jnu1_a, coef_jnu2_a, coef_jnu3_a, coef_jnu4_a, coef_jnu5_a, coef_jnu6_a, coef_jnu7_a, coef_jnu8_a, coef_jnu9_a, coef_jnu10_a, coef_jnu11_a, coef_jnu12_a, coef_jnu13_a, coef_jnu14_a, coef_jnu15_a, coef_jnu16_a, coef_jnu17_a, coef_jnu18_a, coef_jnu19_a, coef_jnu20_a }; static const size_t size_jnu_a[] = { 0, sizeof(coef_jnu1_a)/sizeof(double), sizeof(coef_jnu2_a)/sizeof(double), sizeof(coef_jnu3_a)/sizeof(double), sizeof(coef_jnu4_a)/sizeof(double), sizeof(coef_jnu5_a)/sizeof(double), sizeof(coef_jnu6_a)/sizeof(double), sizeof(coef_jnu7_a)/sizeof(double), sizeof(coef_jnu8_a)/sizeof(double), sizeof(coef_jnu9_a)/sizeof(double), sizeof(coef_jnu10_a)/sizeof(double), sizeof(coef_jnu11_a)/sizeof(double), sizeof(coef_jnu12_a)/sizeof(double), sizeof(coef_jnu13_a)/sizeof(double), sizeof(coef_jnu14_a)/sizeof(double), sizeof(coef_jnu15_a)/sizeof(double), sizeof(coef_jnu16_a)/sizeof(double), sizeof(coef_jnu17_a)/sizeof(double), sizeof(coef_jnu18_a)/sizeof(double), sizeof(coef_jnu19_a)/sizeof(double), sizeof(coef_jnu20_a)/sizeof(double) }; static const double * coef_jnu_b[] = { 0, coef_jnu1_b, coef_jnu2_b, coef_jnu3_b, coef_jnu4_b, coef_jnu5_b, coef_jnu6_b, coef_jnu7_b, coef_jnu8_b, coef_jnu9_b, coef_jnu10_b }; static const size_t size_jnu_b[] = { 0, sizeof(coef_jnu1_b)/sizeof(double), sizeof(coef_jnu2_b)/sizeof(double), sizeof(coef_jnu3_b)/sizeof(double), sizeof(coef_jnu4_b)/sizeof(double), sizeof(coef_jnu5_b)/sizeof(double), sizeof(coef_jnu6_b)/sizeof(double), sizeof(coef_jnu7_b)/sizeof(double), sizeof(coef_jnu8_b)/sizeof(double), sizeof(coef_jnu9_b)/sizeof(double), sizeof(coef_jnu10_b)/sizeof(double) }; /* Evaluate Clenshaw recurrence for * a T* Chebyshev series. * sizeof(c) = N+1 */ static double clenshaw(const double * c, int N, double u) { double B_np1 = 0.0; double B_n = c[N]; double B_nm1; int n; for(n=N; n>0; n--) { B_nm1 = 2.0*(2.0*u-1.0) * B_n - B_np1 + c[n-1]; B_np1 = B_n; B_n = B_nm1; } return B_n - (2.0*u-1.0)*B_np1; } /* correction terms to leading McMahon expansion * [Abramowitz+Stegun 9.5.12] * [Olver, Royal Society Math. Tables, v. 7] * We factor out a beta, so that this is a multiplicative * correction: * j_{nu,s} = beta(s,nu) * mcmahon_correction(nu, beta(s,nu)) * macmahon_correction --> 1 as s --> Inf */ static double mcmahon_correction(const double mu, const double beta) { const double eb = 8.0*beta; const double ebsq = eb*eb; if(mu < GSL_DBL_EPSILON) { /* Prevent division by zero below. */ const double term1 = 1.0/ebsq; const double term2 = -4.0*31.0/(3*ebsq*ebsq); const double term3 = 32.0*3779.0/(15.0*ebsq*ebsq*ebsq); const double term4 = -64.0*6277237.0/(105.0*ebsq*ebsq*ebsq*ebsq); const double term5 = 512.0*2092163573.0/(315.0*ebsq*ebsq*ebsq*ebsq*ebsq); return 1.0 + 8.0*(term1 + term2 + term3 + term4 + term5); } else { /* Here we do things in terms of 1/mu, which * is purely to prevent overflow in the very * unlikely case that mu is really big. */ const double mi = 1.0/mu; const double r = mu/ebsq; const double n2 = 4.0/3.0 * (7.0 - 31.0*mi); const double n3 = 32.0/15.0 * (83.0 + (-982.0 + 3779.0*mi)*mi); const double n4 = 64.0/105.0 * (6949.0 + (-153855.0 + (1585743.0 - 6277237.0*mi)*mi)*mi); const double n5 = 512.0/315.0 * (70197.0 + (-2479316.0 + (48010494.0 + (-512062548.0 + 2092163573.0*mi)*mi)*mi)*mi); const double n6 = 2048.0/3465.0 * (5592657.0 + (-287149133.0 + (8903961290.0 + (-179289628602.0 + (1982611456181.0 - 8249725736393.0*mi)*mi)*mi)*mi)*mi); const double term1 = (1.0 - mi) * r; const double term2 = term1 * n2 * r; const double term3 = term1 * n3 * r*r; const double term4 = term1 * n4 * r*r*r; const double term5 = term1 * n5 * r*r*r*r; const double term6 = term1 * n6 * r*r*r*r*r; return 1.0 - 8.0*(term1 + term2 + term3 + term4 + term5 + term6); } } /* Assumes z >= 1.0 */ static double olver_b0(double z, double minus_zeta) { if(z < 1.02) { const double a = 1.0-z; const double c0 = 0.0179988721413553309252458658183; const double c1 = 0.0111992982212877614645974276203; const double c2 = 0.0059404069786014304317781160605; const double c3 = 0.0028676724516390040844556450173; const double c4 = 0.0012339189052567271708525111185; const double c5 = 0.0004169250674535178764734660248; const double c6 = 0.0000330173385085949806952777365; const double c7 = -0.0001318076238578203009990106425; const double c8 = -0.0001906870370050847239813945647; return c0 + a*(c1 + a*(c2 + a*(c3 + a*(c4 + a*(c5 + a*(c6 + a*(c7 + a*c8))))))); } else { const double abs_zeta = minus_zeta; const double t = 1.0/(z*sqrt(1.0 - 1.0/(z*z))); return -5.0/(48.0*abs_zeta*abs_zeta) + t*(3.0 + 5.0*t*t)/(24.0*sqrt(abs_zeta)); } } inline static double olver_f1(double z, double minus_zeta) { const double b0 = olver_b0(z, minus_zeta); const double h2 = sqrt(4.0*minus_zeta/(z*z-1.0)); /* FIXME */ return 0.5 * z * h2 * b0; } int gsl_sf_bessel_zero_J0_e(unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s == 0){ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EINVAL); } else { /* See [F. Lether, J. Comp. Appl .Math. 67, 167 (1996)]. */ static const double P[] = { 1567450796.0/12539606369.0, 8903660.0/2365861.0, 10747040.0/536751.0, 17590991.0/1696654.0 }; static const double Q[] = { 1.0, 29354255.0/954518.0, 76900001.0/431847.0, 67237052.0/442411.0 }; const double beta = (s - 0.25) * M_PI; const double bi2 = 1.0/(beta*beta); const double R33num = P[0] + bi2 * (P[1] + bi2 * (P[2] + P[3] * bi2)); const double R33den = Q[0] + bi2 * (Q[1] + bi2 * (Q[2] + Q[3] * bi2)); const double R33 = R33num/R33den; result->val = beta + R33/beta; result->err = fabs(3.0e-15 * result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_zero_J1_e(unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s == 0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* See [M. Branders et al., J. Comp. Phys. 42, 403 (1981)]. */ static const double a[] = { -0.362804405737084, 0.120341279038597, 0.439454547101171e-01, 0.159340088474713e-02 }; static const double b[] = { 1.0, -0.325641790801361, -0.117453445968927, -0.424906902601794e-02 }; const double beta = (s + 0.25) * M_PI; const double bi2 = 1.0/(beta*beta); const double Rnum = a[3] + bi2 * (a[2] + bi2 * (a[1] + bi2 * a[0])); const double Rden = b[3] + bi2 * (b[2] + bi2 * (b[1] + bi2 * b[0])); const double R = Rnum/Rden; result->val = beta * (1.0 + R*bi2); result->err = fabs(2.0e-14 * result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_zero_Jnu_e(double nu, unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(nu <= -1.0) { DOMAIN_ERROR(result); } else if(s == 0) { result->val = 0.0; result->err = 0.0; if (nu == 0.0) { GSL_ERROR ("no zero-th root for nu = 0.0", GSL_EINVAL); } return GSL_SUCCESS; } else if(nu < 0.0) { /* This can be done, I'm just lazy now. */ result->val = 0.0; result->err = 0.0; GSL_ERROR("unimplemented", GSL_EUNIMPL); } else if(s == 1) { /* Chebyshev fits for the first positive zero. * For some reason Nemeth made this different from the others. */ if(nu < 2.0) { const double * c = coef_jnu_a[s]; const size_t L = size_jnu_a[s]; const double arg = nu/2.0; const double chb = clenshaw(c, L-1, arg); result->val = chb; result->err = 2.0e-15 * result->val; } else { const double * c = coef_jnu_b[s]; const size_t L = size_jnu_b[s]; const double arg = pow(2.0/nu, 2.0/3.0); const double chb = clenshaw(c, L-1, arg); result->val = nu * chb; result->err = 2.0e-15 * result->val; } return GSL_SUCCESS; } else if(s <= 10) { /* Chebyshev fits for the first 10 positive zeros. */ if(nu < s) { const double * c = coef_jnu_a[s]; const size_t L = size_jnu_a[s]; const double arg = nu/s; const double chb = clenshaw(c, L-1, arg); result->val = chb; result->err = 2.0e-15 * result->val; } else { const double * c = coef_jnu_b[s]; const size_t L = size_jnu_b[s]; const double arg = pow(s/nu, 2.0/3.0); const double chb = clenshaw(c, L-1, arg); result->val = nu * chb; result->err = 2.0e-15 * result->val; /* FIXME: truth in advertising for the screwed up * s = 5 fit. Need to fix that. */ if(s == 5) { result->err *= 5.0e+06; } } return GSL_SUCCESS; } else if(s > 0.5*nu && s <= 20) { /* Chebyshev fits for 10 < s <= 20. */ const double * c = coef_jnu_a[s]; const size_t L = size_jnu_a[s]; const double arg = nu/(2.0*s); const double chb = clenshaw(c, L-1, arg); result->val = chb; result->err = 4.0e-15 * chb; return GSL_SUCCESS; } else if(s > 2.0 * nu) { /* McMahon expansion if s is large compared to nu. */ const double beta = (s + 0.5*nu - 0.25) * M_PI; const double mc = mcmahon_correction(4.0*nu*nu, beta); gsl_sf_result rat12; gsl_sf_pow_int_e(nu/beta, 14, &rat12); result->val = beta * mc; result->err = 4.0 * fabs(beta) * rat12.val; result->err += 4.0 * fabs(GSL_DBL_EPSILON * result->val); return GSL_SUCCESS; } else { /* Olver uniform asymptotic. */ gsl_sf_result as; const int stat_as = gsl_sf_airy_zero_Ai_e(s, &as); const double minus_zeta = -pow(nu,-2.0/3.0) * as.val; const double z = gsl_sf_bessel_Olver_zofmzeta(minus_zeta); const double f1 = olver_f1(z, minus_zeta); result->val = nu * (z + f1/(nu*nu)); result->err = 0.001/(nu*nu*nu); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_as; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_zero_J0(unsigned int s) { EVAL_RESULT(gsl_sf_bessel_zero_J0_e(s, &result)); } double gsl_sf_bessel_zero_J1(unsigned int s) { EVAL_RESULT(gsl_sf_bessel_zero_J1_e(s, &result)); } double gsl_sf_bessel_zero_Jnu(double nu, unsigned int s) { EVAL_RESULT(gsl_sf_bessel_zero_Jnu_e(nu, s, &result)); } sources_5316/external/gsl/gsl_sf__exp.c0000644000176700017670000003672610707442037017010 0ustar paulpaul/* specfunc/exp.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_gamma.h" #include "gsl_sf_exp.h" #include "gsl_sf__error.h" /* Evaluate the continued fraction for exprel. * [Abramowitz+Stegun, 4.2.41] */ static int exprel_n_CF(const int N, const double x, gsl_sf_result * result) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 5000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = 1.0; double b1 = 1.0; double a2 = -x; double b2 = N+1; double an, bn; double fn; double An = b1*Anm1 + a1*Anm2; /* A1 */ double Bn = b1*Bnm1 + a1*Bnm2; /* B1 */ /* One explicit step, before we get to the main pattern. */ n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; An = b2*Anm1 + a2*Anm2; /* A2 */ Bn = b2*Bnm1 + a2*Bnm2; /* B2 */ fn = An/Bn; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = ( GSL_IS_ODD(n) ? ((n-1)/2)*x : -(N+(n/2)-1)*x ); bn = N + n - 1; An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 2.0*GSL_DBL_EPSILON) break; } result->val = fn; result->err = 2.0*(n+1.0)*GSL_DBL_EPSILON*fabs(fn); if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_exp_e(const double x, gsl_sf_result * result) { if(x > GSL_LOG_DBL_MAX) { OVERFLOW_ERROR(result); } else if(x < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else { result->val = exp(x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_exp_e10_e(const double x, gsl_sf_result_e10 * result) { if(x > INT_MAX-1) { OVERFLOW_ERROR_E10(result); } else if(x < INT_MIN+1) { UNDERFLOW_ERROR_E10(result); } else { const int N = (int) floor(x/M_LN10); result->val = exp(x-N*M_LN10); result->err = 2.0 * (fabs(x)+1.0) * GSL_DBL_EPSILON * fabs(result->val); result->e10 = N; return GSL_SUCCESS; } } int gsl_sf_exp_mult_e(const double x, const double y, gsl_sf_result * result) { const double ay = fabs(y); if(y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if( ( x < 0.5*GSL_LOG_DBL_MAX && x > 0.5*GSL_LOG_DBL_MIN) && (ay < 0.8*GSL_SQRT_DBL_MAX && ay > 1.2*GSL_SQRT_DBL_MIN) ) { const double ex = exp(x); result->val = y * ex; result->err = (2.0 + fabs(x)) * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double ly = log(ay); const double lnr = x + ly; if(lnr > GSL_LOG_DBL_MAX - 0.01) { OVERFLOW_ERROR(result); } else if(lnr < GSL_LOG_DBL_MIN + 0.01) { UNDERFLOW_ERROR(result); } else { const double sy = GSL_SIGN(y); const double M = floor(x); const double N = floor(ly); const double a = x - M; const double b = ly - N; const double berr = 2.0 * GSL_DBL_EPSILON * (fabs(ly) + fabs(N)); result->val = sy * exp(M+N) * exp(a+b); result->err = berr * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * (M + N + 1.0) * fabs(result->val); return GSL_SUCCESS; } } } int gsl_sf_exp_mult_e10_e(const double x, const double y, gsl_sf_result_e10 * result) { const double ay = fabs(y); if(y == 0.0) { result->val = 0.0; result->err = 0.0; result->e10 = 0; return GSL_SUCCESS; } else if( ( x < 0.5*GSL_LOG_DBL_MAX && x > 0.5*GSL_LOG_DBL_MIN) && (ay < 0.8*GSL_SQRT_DBL_MAX && ay > 1.2*GSL_SQRT_DBL_MIN) ) { const double ex = exp(x); result->val = y * ex; result->err = (2.0 + fabs(x)) * GSL_DBL_EPSILON * fabs(result->val); result->e10 = 0; return GSL_SUCCESS; } else { const double ly = log(ay); const double l10_val = (x + ly)/M_LN10; if(l10_val > INT_MAX-1) { OVERFLOW_ERROR_E10(result); } else if(l10_val < INT_MIN+1) { UNDERFLOW_ERROR_E10(result); } else { const double sy = GSL_SIGN(y); const int N = (int) floor(l10_val); const double arg_val = (l10_val - N) * M_LN10; const double arg_err = 2.0 * GSL_DBL_EPSILON * fabs(ly); result->val = sy * exp(arg_val); result->err = arg_err * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->e10 = N; return GSL_SUCCESS; } } } int gsl_sf_exp_mult_err_e(const double x, const double dx, const double y, const double dy, gsl_sf_result * result) { const double ay = fabs(y); if(y == 0.0) { result->val = 0.0; result->err = fabs(dy * exp(x)); return GSL_SUCCESS; } else if( ( x < 0.5*GSL_LOG_DBL_MAX && x > 0.5*GSL_LOG_DBL_MIN) && (ay < 0.8*GSL_SQRT_DBL_MAX && ay > 1.2*GSL_SQRT_DBL_MIN) ) { double ex = exp(x); result->val = y * ex; result->err = ex * (fabs(dy) + fabs(y*dx)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double ly = log(ay); const double lnr = x + ly; if(lnr > GSL_LOG_DBL_MAX - 0.01) { OVERFLOW_ERROR(result); } else if(lnr < GSL_LOG_DBL_MIN + 0.01) { UNDERFLOW_ERROR(result); } else { const double sy = GSL_SIGN(y); const double M = floor(x); const double N = floor(ly); const double a = x - M; const double b = ly - N; const double eMN = exp(M+N); const double eab = exp(a+b); result->val = sy * eMN * eab; result->err = eMN * eab * 2.0*GSL_DBL_EPSILON; result->err += eMN * eab * fabs(dy/y); result->err += eMN * eab * fabs(dx); return GSL_SUCCESS; } } } int gsl_sf_exp_mult_err_e10_e(const double x, const double dx, const double y, const double dy, gsl_sf_result_e10 * result) { const double ay = fabs(y); if(y == 0.0) { result->val = 0.0; result->err = fabs(dy * exp(x)); result->e10 = 0; return GSL_SUCCESS; } else if( ( x < 0.5*GSL_LOG_DBL_MAX && x > 0.5*GSL_LOG_DBL_MIN) && (ay < 0.8*GSL_SQRT_DBL_MAX && ay > 1.2*GSL_SQRT_DBL_MIN) ) { const double ex = exp(x); result->val = y * ex; result->err = ex * (fabs(dy) + fabs(y*dx)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->e10 = 0; return GSL_SUCCESS; } else { const double ly = log(ay); const double l10_val = (x + ly)/M_LN10; if(l10_val > INT_MAX-1) { OVERFLOW_ERROR_E10(result); } else if(l10_val < INT_MIN+1) { UNDERFLOW_ERROR_E10(result); } else { const double sy = GSL_SIGN(y); const int N = (int) floor(l10_val); const double arg_val = (l10_val - N) * M_LN10; const double arg_err = dy/fabs(y) + dx + 2.0*GSL_DBL_EPSILON*fabs(arg_val); result->val = sy * exp(arg_val); result->err = arg_err * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->e10 = N; return GSL_SUCCESS; } } } int gsl_sf_expm1_e(const double x, gsl_sf_result * result) { const double cut = 0.002; if(x < GSL_LOG_DBL_MIN) { result->val = -1.0; result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < -cut) { result->val = exp(x) - 1.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < cut) { result->val = x * (1.0 + 0.5*x*(1.0 + x/3.0*(1.0 + 0.25*x*(1.0 + 0.2*x)))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < GSL_LOG_DBL_MAX) { result->val = exp(x) - 1.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_exprel_e(const double x, gsl_sf_result * result) { const double cut = 0.002; if(x < GSL_LOG_DBL_MIN) { result->val = -1.0/x; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -cut) { result->val = (exp(x) - 1.0)/x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < cut) { result->val = (1.0 + 0.5*x*(1.0 + x/3.0*(1.0 + 0.25*x*(1.0 + 0.2*x)))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < GSL_LOG_DBL_MAX) { result->val = (exp(x) - 1.0)/x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_exprel_2_e(double x, gsl_sf_result * result) { const double cut = 0.002; if(x < GSL_LOG_DBL_MIN) { result->val = -2.0/x*(1.0 + 1.0/x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -cut) { result->val = 2.0*(exp(x) - 1.0 - x)/(x*x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < cut) { result->val = (1.0 + 1.0/3.0*x*(1.0 + 0.25*x*(1.0 + 0.2*x*(1.0 + 1.0/6.0*x)))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < GSL_LOG_DBL_MAX) { result->val = 2.0*(exp(x) - 1.0 - x)/(x*x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_exprel_n_e(const int N, const double x, gsl_sf_result * result) { if(N < 0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(fabs(x) < GSL_ROOT3_DBL_EPSILON * N) { result->val = 1.0 + x/(N+1) * (1.0 + x/(N+2)); result->err = 2.0 * GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(N == 0) { return gsl_sf_exp_e(x, result); } else if(N == 1) { return gsl_sf_exprel_e(x, result); } else if(N == 2) { return gsl_sf_exprel_2_e(x, result); } else { if(x > N && (-x + N*(1.0 + log(x/N)) < GSL_LOG_DBL_EPSILON)) { /* x is much larger than n. * Ignore polynomial part, so * exprel_N(x) ~= e^x N!/x^N */ gsl_sf_result lnf_N; double lnr_val; double lnr_err; double lnterm; gsl_sf_lnfact_e(N, &lnf_N); lnterm = N*log(x); lnr_val = x + lnf_N.val - lnterm; lnr_err = GSL_DBL_EPSILON * (fabs(x) + fabs(lnf_N.val) + fabs(lnterm)); lnr_err += lnf_N.err; return gsl_sf_exp_err_e(lnr_val, lnr_err, result); } else if(x > N) { /* Write the identity * exprel_n(x) = e^x n! / x^n (1 - Gamma[n,x]/Gamma[n]) * then use the asymptotic expansion * Gamma[n,x] ~ x^(n-1) e^(-x) (1 + (n-1)/x + (n-1)(n-2)/x^2 + ...) */ double ln_x = log(x); gsl_sf_result lnf_N; double lg_N; double lnpre_val; double lnpre_err; gsl_sf_lnfact_e(N, &lnf_N); /* log(N!) */ lg_N = lnf_N.val - log(N); /* log(Gamma(N)) */ lnpre_val = x + lnf_N.val - N*ln_x; lnpre_err = GSL_DBL_EPSILON * (fabs(x) + fabs(lnf_N.val) + fabs(N*ln_x)); lnpre_err += lnf_N.err; if(lnpre_val < GSL_LOG_DBL_MAX - 5.0) { int stat_eG; gsl_sf_result bigG_ratio; gsl_sf_result pre; int stat_ex = gsl_sf_exp_err_e(lnpre_val, lnpre_err, &pre); double ln_bigG_ratio_pre = -x + (N-1)*ln_x - lg_N; double bigGsum = 1.0; double term = 1.0; int k; for(k=1; kval = pre.val * (1.0 - bigG_ratio.val); result->err = pre.val * (2.0*GSL_DBL_EPSILON + bigG_ratio.err); result->err += pre.err * fabs(1.0 - bigG_ratio.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_ex; } else { result->val = 0.0; result->err = 0.0; return stat_eG; } } else { OVERFLOW_ERROR(result); } } else if(x > -10.0*N) { return exprel_n_CF(N, x, result); } else { /* x -> -Inf asymptotic: * exprel_n(x) ~ e^x n!/x^n - n/x (1 + (n-1)/x + (n-1)(n-2)/x + ...) * ~ - n/x (1 + (n-1)/x + (n-1)(n-2)/x + ...) */ double sum = 1.0; double term = 1.0; int k; for(k=1; kval = -N/x * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } } int gsl_sf_exp_err_e(const double x, const double dx, gsl_sf_result * result) { const double adx = fabs(dx); /* CHECK_POINTER(result) */ if(x + adx > GSL_LOG_DBL_MAX) { OVERFLOW_ERROR(result); } else if(x - adx < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else { const double ex = exp(x); const double edx = exp(adx); result->val = ex; result->err = ex * GSL_MAX_DBL(GSL_DBL_EPSILON, edx - 1.0/edx); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_exp_err_e10_e(const double x, const double dx, gsl_sf_result_e10 * result) { const double adx = fabs(dx); /* CHECK_POINTER(result) */ if(x + adx > INT_MAX - 1) { OVERFLOW_ERROR_E10(result); } else if(x - adx < INT_MIN + 1) { UNDERFLOW_ERROR_E10(result); } else { const int N = (int)floor(x/M_LN10); const double ex = exp(x-N*M_LN10); result->val = ex; result->err = ex * (2.0 * GSL_DBL_EPSILON * (fabs(x) + 1.0) + adx); result->e10 = N; return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_exp(const double x) { EVAL_RESULT(gsl_sf_exp_e(x, &result)); } double gsl_sf_exp_mult(const double x, const double y) { EVAL_RESULT(gsl_sf_exp_mult_e(x, y, &result)); } double gsl_sf_expm1(const double x) { EVAL_RESULT(gsl_sf_expm1_e(x, &result)); } double gsl_sf_exprel(const double x) { EVAL_RESULT(gsl_sf_exprel_e(x, &result)); } double gsl_sf_exprel_2(const double x) { EVAL_RESULT(gsl_sf_exprel_2_e(x, &result)); } double gsl_sf_exprel_n(const int n, const double x) { EVAL_RESULT(gsl_sf_exprel_n_e(n, x, &result)); } sources_5316/external/gsl/gsl_ode-initval__rk4imp.c0000664000176700017670000002150611723710247021215 0ustar paulpaul/* ode-initval/rk4imp.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Runge-Kutta 4, Gaussian implicit */ /* Author: G. Jungman */ /* Error estimation by step doubling, see eg. Ascher, U.M., Petzold, L.R., Computer methods for ordinary differential and differential-algebraic equations, SIAM, Philadelphia, 1998. Method coefficients can also be found in it. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" typedef struct { double *k1nu; double *k2nu; double *ytmp1; double *ytmp2; double *y0; double *y0_orig; double *y_onestep; } rk4imp_state_t; static void * rk4imp_alloc (size_t dim) { rk4imp_state_t *state = (rk4imp_state_t *) malloc (sizeof (rk4imp_state_t)); if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for rk4imp_state", GSL_ENOMEM); } state->k1nu = (double *) malloc (dim * sizeof (double)); if (state->k1nu == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for k1nu", GSL_ENOMEM); } state->k2nu = (double *) malloc (dim * sizeof (double)); if (state->k2nu == 0) { free (state->k1nu); free (state); GSL_ERROR_NULL ("failed to allocate space for k2nu", GSL_ENOMEM); } state->ytmp1 = (double *) malloc (dim * sizeof (double)); if (state->ytmp1 == 0) { free (state->k2nu); free (state->k1nu); free (state); GSL_ERROR_NULL ("failed to allocate space for ytmp1", GSL_ENOMEM); } state->ytmp2 = (double *) malloc (dim * sizeof (double)); if (state->ytmp2 == 0) { free (state->ytmp1); free (state->k2nu); free (state->k1nu); free (state); GSL_ERROR_NULL ("failed to allocate space for ytmp2", GSL_ENOMEM); } state->y0 = (double *) malloc (dim * sizeof (double)); if (state->y0 == 0) { free (state->ytmp2); free (state->ytmp1); free (state->k2nu); free (state->k1nu); free (state); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } state->y0_orig = (double *) malloc (dim * sizeof (double)); if (state->y0_orig == 0) { free (state->y0); free (state->ytmp2); free (state->ytmp1); free (state->k2nu); free (state->k1nu); free (state); GSL_ERROR_NULL ("failed to allocate space for y0_orig", GSL_ENOMEM); } state->y_onestep = (double *) malloc (dim * sizeof (double)); if (state->y_onestep == 0) { free (state->y0_orig); free (state->y0); free (state->ytmp2); free (state->ytmp1); free (state->k2nu); free (state->k1nu); free (state); GSL_ERROR_NULL ("failed to allocate space for y_onestep", GSL_ENOMEM); } return state; } static int rk4imp_step (double *y, rk4imp_state_t *state, const double h, const double t, const size_t dim, const gsl_odeiv_system *sys) { /* Makes a Runge-Kutta 4th order implicit advance with step size h. y0 is initial values of variables y. The implicit matrix equations to solve are: Y1 = y0 + h * a11 * f(t + h * c1, Y1) + h * a12 * f(t + h * c2, Y2) Y2 = y0 + h * a21 * f(t + h * c1, Y1) + h * a22 * f(t + h * c2, Y2) y = y0 + h * b1 * f(t + h * c1, Y1) + h * b2 * f(t + h * c2, Y2) with constant coefficients a, b and c. For this method they are: b=[0.5 0.5] c=[(3-sqrt(3))/6 (3+sqrt(3))/6] a11=1/4, a12=(3-2*sqrt(3))/12, a21=(3+2*sqrt(3))/12 and a22=1/4 */ const double ir3 = 1.0 / M_SQRT3; const int iter_steps = 3; int nu; size_t i; double *const k1nu = state->k1nu; double *const k2nu = state->k2nu; double *const ytmp1 = state->ytmp1; double *const ytmp2 = state->ytmp2; /* iterative solution of Y1 and Y2. Note: This method does not check for convergence of the iterative solution! */ for (nu = 0; nu < iter_steps; nu++) { for (i = 0; i < dim; i++) { ytmp1[i] = y[i] + h * (0.25 * k1nu[i] + 0.5 * (0.5 - ir3) * k2nu[i]); ytmp2[i] = y[i] + h * (0.25 * k2nu[i] + 0.5 * (0.5 + ir3) * k1nu[i]); } { int s = GSL_ODEIV_FN_EVAL (sys, t + 0.5 * h * (1.0 - ir3), ytmp1, k1nu); if (s != GSL_SUCCESS) { return s; } } { int s = GSL_ODEIV_FN_EVAL (sys, t + 0.5 * h * (1.0 + ir3), ytmp2, k2nu); if (s != GSL_SUCCESS) { return s; } } } /* assignment */ for (i = 0; i < dim; i++) { const double d_i = 0.5 * (k1nu[i] + k2nu[i]); y[i] += h * d_i; } return GSL_SUCCESS; } static int rk4imp_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { rk4imp_state_t *state = (rk4imp_state_t *) vstate; size_t i; double *y0 = state->y0; double *y0_orig = state->y0_orig; double *y_onestep = state->y_onestep; double *k1nu = state->k1nu; double *k2nu = state->k2nu; /* Initialization step */ DBL_MEMCPY (y0, y, dim); /* Save initial values in case of failure */ DBL_MEMCPY (y0_orig, y, dim); if (dydt_in != 0) { DBL_MEMCPY (k1nu, dydt_in, dim); } else { int s = GSL_ODEIV_FN_EVAL (sys, t, y, k1nu); if (s != GSL_SUCCESS) { return s; } } DBL_MEMCPY (k2nu, k1nu, dim); /* First traverse h with one step (save to y_onestep) */ DBL_MEMCPY (y_onestep, y, dim); { int s = rk4imp_step (y_onestep, state, h, t, dim, sys); if (s != GSL_SUCCESS) { return s; } } /* Then with two steps with half step length (save to y) */ { int s = rk4imp_step (y, state, h/2.0, t, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } DBL_MEMCPY (y0, y, dim); { int s = GSL_ODEIV_FN_EVAL (sys, t + h/2.0, y, k1nu); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } DBL_MEMCPY (k2nu, k1nu, dim); { int s = rk4imp_step (y, state, h/2.0, t + h/2.0, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } /* Derivatives at output */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } /* Error estimation */ /* Denominator in step doubling error equation * yerr = 0.5 * | y(onestep) - y(twosteps) | / (2^order - 1) */ for (i = 0; i < dim; i++) { yerr[i] = 8.0 * 0.5 * (y[i] - y_onestep[i]) / 15.0; } return GSL_SUCCESS; } static int rk4imp_reset (void *vstate, size_t dim) { rk4imp_state_t *state = (rk4imp_state_t *) vstate; DBL_ZERO_MEMSET (state->y_onestep, dim); DBL_ZERO_MEMSET (state->y0_orig, dim); DBL_ZERO_MEMSET (state->y0, dim); DBL_ZERO_MEMSET (state->k1nu, dim); DBL_ZERO_MEMSET (state->k2nu, dim); DBL_ZERO_MEMSET (state->ytmp1, dim); DBL_ZERO_MEMSET (state->ytmp2, dim); return GSL_SUCCESS; } static unsigned int rk4imp_order (void *vstate) { rk4imp_state_t *state = (rk4imp_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 4; } static void rk4imp_free (void *vstate) { rk4imp_state_t *state = (rk4imp_state_t *) vstate; free (state->y_onestep); free (state->y0_orig); free (state->y0); free (state->k1nu); free (state->k2nu); free (state->ytmp1); free (state->ytmp2); free (state); } static const gsl_odeiv_step_type rk4imp_type = { "rk4imp", /* name */ 1, /* can use dydt_in? */ 1, /* gives exact dydt_out? */ &rk4imp_alloc, &rk4imp_apply, &rk4imp_reset, &rk4imp_order, &rk4imp_free }; const gsl_odeiv_step_type *gsl_odeiv_step_rk4imp = &rk4imp_type; sources_5316/external/gsl/gsl_poly__zsolve.c0000664000176700017670000000414511723710247020101 0ustar paulpaul/* poly/zsolve.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* zsolve.c - finds the complex roots of = 0 */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_poly.h" /* C-style matrix elements */ #define MAT(m,i,j,n) ((m)[(i)*(n) + (j)]) /* Fortran-style matrix elements */ #define FMAT(m,i,j,n) ((m)[((i)-1)*(n) + ((j)-1)]) #include "gsl_poly__companion.c" #include "gsl_poly__balance.c" #include "gsl_poly__qr.c" int gsl_poly_complex_solve (const double *a, size_t n, gsl_poly_complex_workspace * w, gsl_complex_packed_ptr z) { int status; double *m; if (n == 0) { GSL_ERROR ("number of terms must be a positive integer", GSL_EINVAL); } if (n == 1) { GSL_ERROR ("cannot solve for only one term", GSL_EINVAL); } if (a[n - 1] == 0) { GSL_ERROR ("leading term of polynomial must be non-zero", GSL_EINVAL) ; } if (w->nc != n - 1) { GSL_ERROR ("size of workspace does not match polynomial", GSL_EINVAL); } m = w->matrix; set_companion_matrix (a, n - 1, m); balance_companion_matrix (m, n - 1); status = qr_companion (m, n - 1, z); if (status) { GSL_ERROR("root solving qr method failed to converge", GSL_EFAILED); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_specfunc__psi.c0000664000176700017670000006042511723710247020200 0ustar paulpaul/* specfunc/psi.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2005, 2006 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_zeta.h" #include "gsl_sf_psi.h" #include "gsl_complex_math.h" #include #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* Chebyshev fit for f(y) = Re(Psi(1+Iy)) + M_EULER - y^2/(1+y^2) - y^2/(2(4+y^2)) * 1 < y < 10 * ==> * y(x) = (9x + 11)/2, -1 < x < 1 * x(y) = (2y - 11)/9 * * g(x) := f(y(x)) */ static double r1py_data[] = { 1.59888328244976954803168395603, 0.67905625353213463845115658455, -0.068485802980122530009506482524, -0.005788184183095866792008831182, 0.008511258167108615980419855648, -0.004042656134699693434334556409, 0.001352328406159402601778462956, -0.000311646563930660566674525382, 0.000018507563785249135437219139, 0.000028348705427529850296492146, -0.000019487536014574535567541960, 8.0709788710834469408621587335e-06, -2.2983564321340518037060346561e-06, 3.0506629599604749843855962658e-07, 1.3042238632418364610774284846e-07, -1.2308657181048950589464690208e-07, 5.7710855710682427240667414345e-08, -1.8275559342450963966092636354e-08, 3.1020471300626589420759518930e-09, 6.8989327480593812470039430640e-10, -8.7182290258923059852334818997e-10, 4.4069147710243611798213548777e-10, -1.4727311099198535963467200277e-10, 2.7589682523262644748825844248e-11, 4.1871826756975856411554363568e-12, -6.5673460487260087541400767340e-12, 3.4487900886723214020103638000e-12, -1.1807251417448690607973794078e-12, 2.3798314343969589258709315574e-13, 2.1663630410818831824259465821e-15 }; static cheb_series r1py_cs = { r1py_data, 29, -1,1, 18 }; /* Chebyshev fits from SLATEC code for psi(x) Series for PSI on the interval 0. to 1.00000D+00 with weighted error 2.03E-17 log weighted error 16.69 significant figures required 16.39 decimal places required 17.37 Series for APSI on the interval 0. to 2.50000D-01 with weighted error 5.54E-17 log weighted error 16.26 significant figures required 14.42 decimal places required 16.86 */ static double psics_data[23] = { -.038057080835217922, .491415393029387130, -.056815747821244730, .008357821225914313, -.001333232857994342, .000220313287069308, -.000037040238178456, .000006283793654854, -.000001071263908506, .000000183128394654, -.000000031353509361, .000000005372808776, -.000000000921168141, .000000000157981265, -.000000000027098646, .000000000004648722, -.000000000000797527, .000000000000136827, -.000000000000023475, .000000000000004027, -.000000000000000691, .000000000000000118, -.000000000000000020 }; static cheb_series psi_cs = { psics_data, 22, -1, 1, 17 }; static double apsics_data[16] = { -.0204749044678185, -.0101801271534859, .0000559718725387, -.0000012917176570, .0000000572858606, -.0000000038213539, .0000000003397434, -.0000000000374838, .0000000000048990, -.0000000000007344, .0000000000001233, -.0000000000000228, .0000000000000045, -.0000000000000009, .0000000000000002, -.0000000000000000 }; static cheb_series apsi_cs = { apsics_data, 15, -1, 1, 9 }; #define PSI_TABLE_NMAX 100 static double psi_table[PSI_TABLE_NMAX+1] = { 0.0, /* Infinity */ /* psi(0) */ -M_EULER, /* psi(1) */ 0.42278433509846713939348790992, /* ... */ 0.92278433509846713939348790992, 1.25611766843180047272682124325, 1.50611766843180047272682124325, 1.70611766843180047272682124325, 1.87278433509846713939348790992, 2.01564147795560999653634505277, 2.14064147795560999653634505277, 2.25175258906672110764745616389, 2.35175258906672110764745616389, 2.44266167997581201673836525479, 2.52599501330914535007169858813, 2.60291809023222227314862166505, 2.67434666166079370172005023648, 2.74101332832746036838671690315, 2.80351332832746036838671690315, 2.86233685773922507426906984432, 2.91789241329478062982462539988, 2.97052399224214905087725697883, 3.02052399224214905087725697883, 3.06814303986119666992487602645, 3.11359758531574212447033057190, 3.15707584618530734186163491973, 3.1987425128519740085283015864, 3.2387425128519740085283015864, 3.2772040513135124700667631249, 3.3142410883505495071038001619, 3.3499553740648352213895144476, 3.3844381326855248765619282407, 3.4177714660188582098952615740, 3.4500295305349872421533260902, 3.4812795305349872421533260902, 3.5115825608380175451836291205, 3.5409943255438998981248055911, 3.5695657541153284695533770196, 3.5973435318931062473311547974, 3.6243705589201332743581818244, 3.6506863483938174848844976139, 3.6763273740348431259101386396, 3.7013273740348431259101386396, 3.7257176179372821503003825420, 3.7495271417468059598241920658, 3.7727829557002943319172153216, 3.7955102284275670591899425943, 3.8177324506497892814121648166, 3.8394715810845718901078169905, 3.8607481768292527411716467777, 3.8815815101625860745049801110, 3.9019896734278921969539597029, 3.9219896734278921969539597029, 3.9415975165651470989147440166, 3.9608282857959163296839747858, 3.9796962103242182164764276160, 3.9982147288427367349949461345, 4.0163965470245549168131279527, 4.0342536898816977739559850956, 4.0517975495308205809735289552, 4.0690389288411654085597358518, 4.0859880813835382899156680552, 4.1026547480502049565823347218, 4.1190481906731557762544658694, 4.1351772229312202923834981274, 4.1510502388042361653993711433, 4.1666752388042361653993711433, 4.1820598541888515500147557587, 4.1972113693403667015299072739, 4.2121367424746950597388624977, 4.2268426248276362362094507330, 4.2413353784508246420065521823, 4.2556210927365389277208378966, 4.2697055997787924488475984600, 4.2835944886676813377364873489, 4.2972931188046676391063503626, 4.3108066323181811526198638761, 4.3241399656515144859531972094, 4.3372978603883565912163551041, 4.3502848733753695782293421171, 4.3631053861958823987421626300, 4.3757636140439836645649474401, 4.3882636140439836645649474401, 4.4006092930563293435772931191, 4.4128044150075488557724150703, 4.4248526077786331931218126607, 4.4367573696833950978837174226, 4.4485220755657480390601880108, 4.4601499825424922251066996387, 4.4716442354160554434975042364, 4.4830078717796918071338678728, 4.4942438268358715824147667492, 4.5053549379469826935258778603, 4.5163439489359936825368668713, 4.5272135141533849868846929582, 4.5379662023254279976373811303, 4.5486045001977684231692960239, 4.5591308159872421073798223397, 4.5695474826539087740464890064, 4.5798567610044242379640147796, 4.5900608426370772991885045755, 4.6001618527380874001986055856 }; #define PSI_1_TABLE_NMAX 100 static double psi_1_table[PSI_1_TABLE_NMAX+1] = { 0.0, /* Infinity */ /* psi(1,0) */ M_PI*M_PI/6.0, /* psi(1,1) */ 0.644934066848226436472415, /* ... */ 0.394934066848226436472415, 0.2838229557371153253613041, 0.2213229557371153253613041, 0.1813229557371153253613041, 0.1535451779593375475835263, 0.1331370146940314251345467, 0.1175120146940314251345467, 0.1051663356816857461222010, 0.0951663356816857461222010, 0.0869018728717683907503002, 0.0799574284273239463058557, 0.0740402686640103368384001, 0.0689382278476838062261552, 0.0644937834032393617817108, 0.0605875334032393617817108, 0.0571273257907826143768665, 0.0540409060376961946237801, 0.0512708229352031198315363, 0.0487708229352031198315363, 0.0465032492390579951149830, 0.0444371335365786562720078, 0.0425467743683366902984728, 0.0408106632572255791873617, 0.0392106632572255791873617, 0.0377313733163971768204978, 0.0363596312039143235969038, 0.0350841209998326909438426, 0.0338950603577399442137594, 0.0327839492466288331026483, 0.0317433665203020901265817, 0.03076680402030209012658168, 0.02984853037475571730748159, 0.02898347847164153045627052, 0.02816715194102928555831133, 0.02739554700275768062003973, 0.02666508681283803124093089, 0.02597256603721476254286995, 0.02531510384129102815759710, 0.02469010384129102815759710, 0.02409521984367056414807896, 0.02352832641963428296894063, 0.02298749353699501850166102, 0.02247096461137518379091722, 0.02197713745088135663042339, 0.02150454765882086513703965, 0.02105185413233829383780923, 0.02061782635456051606003145, 0.02020133322669712580597065, 0.01980133322669712580597065, 0.01941686571420193164987683, 0.01904704322899483105816086, 0.01869104465298913508094477, 0.01834810912486842177504628, 0.01801753061247172756017024, 0.01769865306145131939690494, 0.01739086605006319997554452, 0.01709360088954001329302371, 0.01680632711763538818529605, 0.01652854933985761040751827, 0.01625980437882562975715546, 0.01599965869724394401313881, 0.01574770606433893015574400, 0.01550356543933893015574400, 0.01526687904880638577704578, 0.01503731063741979257227076, 0.01481454387422086185273411, 0.01459828089844231513993134, 0.01438824099085987447620523, 0.01418415935820681325171544, 0.01398578601958352422176106, 0.01379288478501562298719316, 0.01360523231738567365335942, 0.01342261726990576130858221, 0.01324483949212798353080444, 0.01307170929822216635628920, 0.01290304679189732236910755, 0.01273868124291638877278934, 0.01257845051066194236996928, 0.01242220051066194236996928, 0.01226978472038606978956995, 0.01212106372098095378719041, 0.01197590477193174490346273, 0.01183418141592267460867815, 0.01169577311142440471248438, 0.01156056489076458859566448, 0.01142844704164317229232189, 0.01129931481023821361463594, 0.01117306812421372175754719, 0.01104961133409026496742374, 0.01092885297157366069257770, 0.01081070552355853781923177, 0.01069508522063334415522437, 0.01058191183901270133041676, 0.01047110851491297833872701, 0.01036260157046853389428257, 0.01025632035036012704977199, /* ... */ 0.01015219706839427948625679, /* psi(1,99) */ 0.01005016666333357139524567 /* psi(1,100) */ }; /* digamma for x both positive and negative; we do both * cases here because of the way we use even/odd parts * of the function */ static int psi_x(const double x, gsl_sf_result * result) { const double y = fabs(x); if(x == 0.0 || x == -1.0 || x == -2.0) { DOMAIN_ERROR(result); } else if(y >= 2.0) { const double t = 8.0/(y*y)-1.0; gsl_sf_result result_c; cheb_eval_e(&apsi_cs, t, &result_c); if(x < 0.0) { const double s = sin(M_PI*x); const double c = cos(M_PI*x); if(fabs(s) < 2.0*GSL_SQRT_DBL_MIN) { DOMAIN_ERROR(result); } else { result->val = log(y) - 0.5/x + result_c.val - M_PI * c/s; result->err = M_PI*fabs(x)*GSL_DBL_EPSILON/(s*s); result->err += result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } else { result->val = log(y) - 0.5/x + result_c.val; result->err = result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } else { /* -2 < x < 2 */ gsl_sf_result result_c; if(x < -1.0) { /* x = -2 + v */ const double v = x + 2.0; const double t1 = 1.0/x; const double t2 = 1.0/(x+1.0); const double t3 = 1.0/v; cheb_eval_e(&psi_cs, 2.0*v-1.0, &result_c); result->val = -(t1 + t2 + t3) + result_c.val; result->err = GSL_DBL_EPSILON * (fabs(t1) + fabs(x/(t2*t2)) + fabs(x/(t3*t3))); result->err += result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 0.0) { /* x = -1 + v */ const double v = x + 1.0; const double t1 = 1.0/x; const double t2 = 1.0/v; cheb_eval_e(&psi_cs, 2.0*v-1.0, &result_c); result->val = -(t1 + t2) + result_c.val; result->err = GSL_DBL_EPSILON * (fabs(t1) + fabs(x/(t2*t2))); result->err += result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 1.0) { /* x = v */ const double t1 = 1.0/x; cheb_eval_e(&psi_cs, 2.0*x-1.0, &result_c); result->val = -t1 + result_c.val; result->err = GSL_DBL_EPSILON * t1; result->err += result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* x = 1 + v */ const double v = x - 1.0; return cheb_eval_e(&psi_cs, 2.0*v-1.0, result); } } } /* psi(z) for large |z| in the right half-plane; [Abramowitz + Stegun, 6.3.18] */ static gsl_complex psi_complex_asymp(gsl_complex z) { /* coefficients in the asymptotic expansion for large z; * let w = z^(-2) and write the expression in the form * * ln(z) - 1/(2z) - 1/12 w (1 + c1 w + c2 w + c3 w + ... ) */ static const double c1 = -0.1; static const double c2 = 1.0/21.0; static const double c3 = -0.05; gsl_complex zi = gsl_complex_inverse(z); gsl_complex w = gsl_complex_mul(zi, zi); gsl_complex cs; /* Horner method evaluation of term in parentheses */ gsl_complex sum; sum = gsl_complex_mul_real(w, c3/c2); sum = gsl_complex_add_real(sum, 1.0); sum = gsl_complex_mul_real(sum, c2/c1); sum = gsl_complex_mul(sum, w); sum = gsl_complex_add_real(sum, 1.0); sum = gsl_complex_mul_real(sum, c1); sum = gsl_complex_mul(sum, w); sum = gsl_complex_add_real(sum, 1.0); /* correction added to log(z) */ cs = gsl_complex_mul(sum, w); cs = gsl_complex_mul_real(cs, -1.0/12.0); cs = gsl_complex_add(cs, gsl_complex_mul_real(zi, -0.5)); return gsl_complex_add(gsl_complex_log(z), cs); } /* psi(z) for complex z in the right half-plane */ static int psi_complex_rhp( gsl_complex z, gsl_sf_result * result_re, gsl_sf_result * result_im ) { int n_recurse = 0; int i; gsl_complex a; if(GSL_REAL(z) == 0.0 && GSL_IMAG(z) == 0.0) { result_re->val = 0.0; result_im->val = 0.0; result_re->err = 0.0; result_im->err = 0.0; return GSL_EDOM; } /* compute the number of recurrences to apply */ if(GSL_REAL(z) < 20.0 && fabs(GSL_IMAG(z)) < 20.0) { const double sp = sqrt(20.0 + GSL_IMAG(z)); const double sn = sqrt(20.0 - GSL_IMAG(z)); const double rhs = sp*sn - GSL_REAL(z); if(rhs > 0.0) n_recurse = ceil(rhs); } /* compute asymptotic at the large value z + n_recurse */ a = psi_complex_asymp(gsl_complex_add_real(z, n_recurse)); result_re->err = 2.0 * GSL_DBL_EPSILON * fabs(GSL_REAL(a)); result_im->err = 2.0 * GSL_DBL_EPSILON * fabs(GSL_IMAG(a)); /* descend recursively, if necessary */ for(i = n_recurse; i >= 1; --i) { gsl_complex zn = gsl_complex_add_real(z, i - 1.0); gsl_complex zn_inverse = gsl_complex_inverse(zn); a = gsl_complex_sub(a, zn_inverse); /* accumulate the error, to catch cancellations */ result_re->err += 2.0 * GSL_DBL_EPSILON * fabs(GSL_REAL(zn_inverse)); result_im->err += 2.0 * GSL_DBL_EPSILON * fabs(GSL_IMAG(zn_inverse)); } result_re->val = GSL_REAL(a); result_im->val = GSL_IMAG(a); result_re->err += 2.0 * GSL_DBL_EPSILON * fabs(result_re->val); result_im->err += 2.0 * GSL_DBL_EPSILON * fabs(result_im->val); return GSL_SUCCESS; } /* generic polygamma; assumes n >= 0 and x > 0 */ static int psi_n_xg0(const int n, const double x, gsl_sf_result * result) { if(n == 0) { return gsl_sf_psi_e(x, result); } else { /* Abramowitz + Stegun 6.4.10 */ gsl_sf_result ln_nf; gsl_sf_result hzeta; int stat_hz = gsl_sf_hzeta_e(n+1.0, x, &hzeta); int stat_nf = gsl_sf_lnfact_e((unsigned int) n, &ln_nf); int stat_e = gsl_sf_exp_mult_err_e(ln_nf.val, ln_nf.err, hzeta.val, hzeta.err, result); if(GSL_IS_EVEN(n)) result->val = -result->val; return GSL_ERROR_SELECT_3(stat_e, stat_nf, stat_hz); } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_psi_int_e(const int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n <= 0) { DOMAIN_ERROR(result); } else if(n <= PSI_TABLE_NMAX) { result->val = psi_table[n]; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* Abramowitz+Stegun 6.3.18 */ const double c2 = -1.0/12.0; const double c3 = 1.0/120.0; const double c4 = -1.0/252.0; const double c5 = 1.0/240.0; const double ni2 = (1.0/n)*(1.0/n); const double ser = ni2 * (c2 + ni2 * (c3 + ni2 * (c4 + ni2*c5))); result->val = log(n) - 0.5/n + ser; result->err = GSL_DBL_EPSILON * (fabs(log(n)) + fabs(0.5/n) + fabs(ser)); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_psi_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ return psi_x(x, result); } int gsl_sf_psi_1piy_e(const double y, gsl_sf_result * result) { const double ay = fabs(y); /* CHECK_POINTER(result) */ if(ay > 1000.0) { /* [Abramowitz+Stegun, 6.3.19] */ const double yi2 = 1.0/(ay*ay); const double lny = log(ay); const double sum = yi2 * (1.0/12.0 + 1.0/120.0 * yi2 + 1.0/252.0 * yi2*yi2); result->val = lny + sum; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(lny) + fabs(sum)); return GSL_SUCCESS; } else if(ay > 10.0) { /* [Abramowitz+Stegun, 6.3.19] */ const double yi2 = 1.0/(ay*ay); const double lny = log(ay); const double sum = yi2 * (1.0/12.0 + yi2 * (1.0/120.0 + yi2 * (1.0/252.0 + yi2 * (1.0/240.0 + yi2 * (1.0/132.0 + 691.0/32760.0 * yi2))))); result->val = lny + sum; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(lny) + fabs(sum)); return GSL_SUCCESS; } else if(ay > 1.0){ const double y2 = ay*ay; const double x = (2.0*ay - 11.0)/9.0; const double v = y2*(1.0/(1.0+y2) + 0.5/(4.0+y2)); gsl_sf_result result_c; cheb_eval_e(&r1py_cs, x, &result_c); result->val = result_c.val - M_EULER + v; result->err = result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(v) + M_EULER + fabs(result_c.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->err *= 5.0; /* FIXME: losing a digit somewhere... maybe at x=... ? */ return GSL_SUCCESS; } else { /* [Abramowitz+Stegun, 6.3.17] * * -M_EULER + y^2 Sum[1/n 1/(n^2 + y^2), {n,1,M}] * + Sum[1/n^3, {n,M+1,Infinity}] * - y^2 Sum[1/n^5, {n,M+1,Infinity}] * + y^4 Sum[1/n^7, {n,M+1,Infinity}] * - y^6 Sum[1/n^9, {n,M+1,Infinity}] * + O(y^8) * * We take M=50 for at least 15 digit precision. */ const int M = 50; const double y2 = y*y; const double c0 = 0.00019603999466879846570; const double c2 = 3.8426659205114376860e-08; const double c4 = 1.0041592839497643554e-11; const double c6 = 2.9516743763500191289e-15; const double p = c0 + y2 *(-c2 + y2*(c4 - y2*c6)); double sum = 0.0; double v; int n; for(n=1; n<=M; n++) { sum += 1.0/(n * (n*n + y*y)); } v = y2 * (sum + p); result->val = -M_EULER + v; result->err = GSL_DBL_EPSILON * (M_EULER + fabs(v)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_psi_1_int_e(const int n, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n <= 0) { DOMAIN_ERROR(result); } else if(n <= PSI_1_TABLE_NMAX) { result->val = psi_1_table[n]; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { /* Abramowitz+Stegun 6.4.12 * double-precision for n > 100 */ const double c0 = -1.0/30.0; const double c1 = 1.0/42.0; const double c2 = -1.0/30.0; const double ni2 = (1.0/n)*(1.0/n); const double ser = ni2*ni2 * (c0 + ni2*(c1 + c2*ni2)); result->val = (1.0 + 0.5/n + 1.0/(6.0*n*n) + ser) / n; result->err = GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } } int gsl_sf_psi_1_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0 || x == -1.0 || x == -2.0) { DOMAIN_ERROR(result); } else if(x > 0.0) { return psi_n_xg0(1, x, result); } else if(x > -5.0) { /* Abramowitz + Stegun 6.4.6 */ int M = -floor(x); double fx = x + M; double sum = 0.0; int m; if(fx == 0.0) DOMAIN_ERROR(result); for(m = 0; m < M; ++m) sum += 1.0/((x+m)*(x+m)); { int stat_psi = psi_n_xg0(1, fx, result); result->val += sum; result->err += M * GSL_DBL_EPSILON * sum; return stat_psi; } } else { /* Abramowitz + Stegun 6.4.7 */ const double sin_px = sin(M_PI * x); const double d = M_PI*M_PI/(sin_px*sin_px); gsl_sf_result r; int stat_psi = psi_n_xg0(1, 1.0-x, &r); result->val = d - r.val; result->err = r.err + 2.0*GSL_DBL_EPSILON*d; return stat_psi; } } int gsl_sf_psi_n_e(const int n, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n == 0) { return gsl_sf_psi_e(x, result); } else if(n == 1) { return gsl_sf_psi_1_e(x, result); } else if(n < 0 || x <= 0.0) { DOMAIN_ERROR(result); } else { gsl_sf_result ln_nf; gsl_sf_result hzeta; int stat_hz = gsl_sf_hzeta_e(n+1.0, x, &hzeta); int stat_nf = gsl_sf_lnfact_e((unsigned int) n, &ln_nf); int stat_e = gsl_sf_exp_mult_err_e(ln_nf.val, ln_nf.err, hzeta.val, hzeta.err, result); if(GSL_IS_EVEN(n)) result->val = -result->val; return GSL_ERROR_SELECT_3(stat_e, stat_nf, stat_hz); } } int gsl_sf_complex_psi_e( const double x, const double y, gsl_sf_result * result_re, gsl_sf_result * result_im ) { if(x >= 0.0) { gsl_complex z = gsl_complex_rect(x, y); return psi_complex_rhp(z, result_re, result_im); } else { /* reflection formula [Abramowitz+Stegun, 6.3.7] */ gsl_complex z = gsl_complex_rect(x, y); gsl_complex omz = gsl_complex_rect(1.0 - x, -y); gsl_complex zpi = gsl_complex_mul_real(z, M_PI); gsl_complex cotzpi = gsl_complex_cot(zpi); int ret_val = psi_complex_rhp(omz, result_re, result_im); if(GSL_IS_REAL(GSL_REAL(cotzpi)) && GSL_IS_REAL(GSL_IMAG(cotzpi))) { result_re->val -= M_PI * GSL_REAL(cotzpi); result_im->val -= M_PI * GSL_IMAG(cotzpi); return ret_val; } else { GSL_ERROR("singularity", GSL_EDOM); } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_psi_int(const int n) { EVAL_RESULT(gsl_sf_psi_int_e(n, &result)); } double gsl_sf_psi(const double x) { EVAL_RESULT(gsl_sf_psi_e(x, &result)); } double gsl_sf_psi_1piy(const double x) { EVAL_RESULT(gsl_sf_psi_1piy_e(x, &result)); } double gsl_sf_psi_1_int(const int n) { EVAL_RESULT(gsl_sf_psi_1_int_e(n, &result)); } double gsl_sf_psi_1(const double x) { EVAL_RESULT(gsl_sf_psi_1_e(x, &result)); } double gsl_sf_psi_n(const int n, const double x) { EVAL_RESULT(gsl_sf_psi_n_e(n, x, &result)); } sources_5316/external/gsl/gsl_cblas__saxpy.c0000664000176700017670000000041611723710247020021 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_saxpy (const int N, const float alpha, const float *X, const int incX, float *Y, const int incY) { #define BASE float #include "gsl_cblas__source_axpy_r.h" #undef BASE } sources_5316/external/gsl/gsl_sf__erfc.c0000644000176700017670000002773110707442037017127 0ustar paulpaul/* specfunc/erfc.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: J. Theiler (modifications by G. Jungman) */ /* * See Hart et al, Computer Approximations, John Wiley and Sons, New York (1968) * (This applies only to the erfc8 stuff, which is the part * of the original code that survives. I have replaced much of * the other stuff with Chebyshev fits. These are simpler and * more precise than the original approximations. [GJ]) */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_erf.h" #include "gsl_sf__check.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" #define LogRootPi_ 0.57236494292470008706 static double erfc8_sum(double x) { /* estimates erfc(x) valid for 8 < x < 100 */ /* This is based on index 5725 in Hart et al */ static double P[] = { 2.97886562639399288862, 7.409740605964741794425, 6.1602098531096305440906, 5.019049726784267463450058, 1.275366644729965952479585264, 0.5641895835477550741253201704 }; static double Q[] = { 3.3690752069827527677, 9.608965327192787870698, 17.08144074746600431571095, 12.0489519278551290360340491, 9.396034016235054150430579648, 2.260528520767326969591866945, 1.0 }; double num=0.0, den=0.0; int i; num = P[5]; for (i=4; i>=0; --i) { num = x*num + P[i]; } den = Q[6]; for (i=5; i>=0; --i) { den = x*den + Q[i]; } return num/den; } inline static double erfc8(double x) { double e; e = erfc8_sum(x); e *= exp(-x*x); return e; } inline static double log_erfc8(double x) { double e; e = erfc8_sum(x); e = log(e) - x*x; return e; } #if 0 /* Abramowitz+Stegun, 7.2.14 */ static double erfcasympsum(double x) { int i; double e = 1.; double coef = 1.; for (i=1; i<5; ++i) { /* coef *= -(2*i-1)/(2*x*x); ??? [GJ] */ coef *= -(2*i+1)/(i*(4*x*x*x*x)); e += coef; /* if (fabs(coef) < 1.0e-15) break; if (fabs(coef) > 1.0e10) break; [GJ]: These tests are not useful. This function is only used below. Took them out; they gum up the pipeline. */ } return e; } #endif /* 0 */ /* Abramowitz+Stegun, 7.1.5 */ static int erfseries(double x, gsl_sf_result * result) { double coef = x; double e = coef; double del; int k; for (k=1; k<30; ++k) { coef *= -x*x/k; del = coef/(2.0*k+1.0); e += del; } result->val = 2.0 / M_SQRTPI * e; result->err = 2.0 / M_SQRTPI * (fabs(del) + GSL_DBL_EPSILON); return GSL_SUCCESS; } /* Chebyshev fit for erfc((t+1)/2), -1 < t < 1 */ static double erfc_xlt1_data[20] = { 1.06073416421769980345174155056, -0.42582445804381043569204735291, 0.04955262679620434040357683080, 0.00449293488768382749558001242, -0.00129194104658496953494224761, -0.00001836389292149396270416979, 0.00002211114704099526291538556, -5.23337485234257134673693179020e-7, -2.78184788833537885382530989578e-7, 1.41158092748813114560316684249e-8, 2.72571296330561699984539141865e-9, -2.06343904872070629406401492476e-10, -2.14273991996785367924201401812e-11, 2.22990255539358204580285098119e-12, 1.36250074650698280575807934155e-13, -1.95144010922293091898995913038e-14, -6.85627169231704599442806370690e-16, 1.44506492869699938239521607493e-16, 2.45935306460536488037576200030e-18, -9.29599561220523396007359328540e-19 }; static cheb_series erfc_xlt1_cs = { erfc_xlt1_data, 19, -1, 1, 12 }; /* Chebyshev fit for erfc(x) exp(x^2), 1 < x < 5, x = 2t + 3, -1 < t < 1 */ static double erfc_x15_data[25] = { 0.44045832024338111077637466616, -0.143958836762168335790826895326, 0.044786499817939267247056666937, -0.013343124200271211203618353102, 0.003824682739750469767692372556, -0.001058699227195126547306482530, 0.000283859419210073742736310108, -0.000073906170662206760483959432, 0.000018725312521489179015872934, -4.62530981164919445131297264430e-6, 1.11558657244432857487884006422e-6, -2.63098662650834130067808832725e-7, 6.07462122724551777372119408710e-8, -1.37460865539865444777251011793e-8, 3.05157051905475145520096717210e-9, -6.65174789720310713757307724790e-10, 1.42483346273207784489792999706e-10, -3.00141127395323902092018744545e-11, 6.22171792645348091472914001250e-12, -1.26994639225668496876152836555e-12, 2.55385883033257575402681845385e-13, -5.06258237507038698392265499770e-14, 9.89705409478327321641264227110e-15, -1.90685978789192181051961024995e-15, 3.50826648032737849245113757340e-16 }; static cheb_series erfc_x15_cs = { erfc_x15_data, 24, -1, 1, 16 }; /* Chebyshev fit for erfc(x) x exp(x^2), 5 < x < 10, x = (5t + 15)/2, -1 < t < 1 */ static double erfc_x510_data[20] = { 1.11684990123545698684297865808, 0.003736240359381998520654927536, -0.000916623948045470238763619870, 0.000199094325044940833965078819, -0.000040276384918650072591781859, 7.76515264697061049477127605790e-6, -1.44464794206689070402099225301e-6, 2.61311930343463958393485241947e-7, -4.61833026634844152345304095560e-8, 8.00253111512943601598732144340e-9, -1.36291114862793031395712122089e-9, 2.28570483090160869607683087722e-10, -3.78022521563251805044056974560e-11, 6.17253683874528285729910462130e-12, -9.96019290955316888445830597430e-13, 1.58953143706980770269506726000e-13, -2.51045971047162509999527428316e-14, 3.92607828989125810013581287560e-15, -6.07970619384160374392535453420e-16, 9.12600607264794717315507477670e-17 }; static cheb_series erfc_x510_cs = { erfc_x510_data, 19, -1, 1, 12 }; #if 0 inline static double erfc_asymptotic(double x) { return exp(-x*x)/x * erfcasympsum(x) / M_SQRTPI; } inline static double log_erfc_asymptotic(double x) { return log(erfcasympsum(x)/x) - x*x - LogRootPi_; } #endif /* 0 */ /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_erfc_e(double x, gsl_sf_result * result) { const double ax = fabs(x); double e_val, e_err; /* CHECK_POINTER(result) */ if(ax <= 1.0) { double t = 2.0*ax - 1.0; gsl_sf_result c; cheb_eval_e(&erfc_xlt1_cs, t, &c); e_val = c.val; e_err = c.err; } else if(ax <= 5.0) { double ex2 = exp(-x*x); double t = 0.5*(ax-3.0); gsl_sf_result c; cheb_eval_e(&erfc_x15_cs, t, &c); e_val = ex2 * c.val; e_err = ex2 * (c.err + 2.0*fabs(x)*GSL_DBL_EPSILON); } else if(ax < 10.0) { double exterm = exp(-x*x) / ax; double t = (2.0*ax - 15.0)/5.0; gsl_sf_result c; cheb_eval_e(&erfc_x510_cs, t, &c); e_val = exterm * c.val; e_err = exterm * (c.err + 2.0*fabs(x)*GSL_DBL_EPSILON + GSL_DBL_EPSILON); } else { e_val = erfc8(ax); e_err = (x*x + 1.0) * GSL_DBL_EPSILON * fabs(e_val); } if(x < 0.0) { result->val = 2.0 - e_val; result->err = e_err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } else { result->val = e_val; result->err = e_err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return GSL_SUCCESS; } int gsl_sf_log_erfc_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x*x < 10.0*GSL_ROOT6_DBL_EPSILON) { const double y = x / M_SQRTPI; /* series for -1/2 Log[Erfc[Sqrt[Pi] y]] */ const double c3 = (4.0 - M_PI)/3.0; const double c4 = 2.0*(1.0 - M_PI/3.0); const double c5 = -0.001829764677455021; /* (96.0 - 40.0*M_PI + 3.0*M_PI*M_PI)/30.0 */ const double c6 = 0.02629651521057465; /* 2.0*(120.0 - 60.0*M_PI + 7.0*M_PI*M_PI)/45.0 */ const double c7 = -0.01621575378835404; const double c8 = 0.00125993961762116; const double c9 = 0.00556964649138; const double c10 = -0.0045563339802; const double c11 = 0.0009461589032; const double c12 = 0.0013200243174; const double c13 = -0.00142906; const double c14 = 0.00048204; double series = c8 + y*(c9 + y*(c10 + y*(c11 + y*(c12 + y*(c13 + c14*y))))); series = y*(1.0 + y*(1.0 + y*(c3 + y*(c4 + y*(c5 + y*(c6 + y*(c7 + y*series))))))); result->val = -2.0 * series; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* don't like use of log1p(); added above series stuff for small x instead, should be ok [GJ] else if (fabs(x) < 1.0) { gsl_sf_result result_erf; gsl_sf_erf_e(x, &result_erf); result->val = log1p(-result_erf.val); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } */ else if(x > 8.0) { result->val = log_erfc8(x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result result_erfc; gsl_sf_erfc_e(x, &result_erfc); result->val = log(result_erfc.val); result->err = fabs(result_erfc.err / result_erfc.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_erf_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(fabs(x) < 1.0) { return erfseries(x, result); } else { gsl_sf_result result_erfc; gsl_sf_erfc_e(x, &result_erfc); result->val = 1.0 - result_erfc.val; result->err = result_erfc.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_erf_Z_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { const double ex2 = exp(-x*x/2.0); result->val = ex2 / (M_SQRT2 * M_SQRTPI); result->err = fabs(x * result->val) * GSL_DBL_EPSILON; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } int gsl_sf_erf_Q_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { gsl_sf_result result_erfc; int stat = gsl_sf_erfc_e(x/M_SQRT2, &result_erfc); result->val = 0.5 * result_erfc.val; result->err = 0.5 * result_erfc.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } } int gsl_sf_hazard_e(double x, gsl_sf_result * result) { if(x < 25.0) { gsl_sf_result result_ln_erfc; const int stat_l = gsl_sf_log_erfc_e(x/M_SQRT2, &result_ln_erfc); const double lnc = -0.22579135264472743236; /* ln(sqrt(2/pi)) */ const double arg = lnc - 0.5*x*x - result_ln_erfc.val; const int stat_e = gsl_sf_exp_e(arg, result); result->err += 3.0 * (1.0 + fabs(x)) * GSL_DBL_EPSILON * fabs(result->val); result->err += fabs(result_ln_erfc.err * result->val); return GSL_ERROR_SELECT_2(stat_l, stat_e); } else { const double ix2 = 1.0/(x*x); const double corrB = 1.0 - 9.0*ix2 * (1.0 - 11.0*ix2); const double corrM = 1.0 - 5.0*ix2 * (1.0 - 7.0*ix2 * corrB); const double corrT = 1.0 - ix2 * (1.0 - 3.0*ix2*corrM); result->val = x / corrT; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_erfc(double x) { EVAL_RESULT(gsl_sf_erfc_e(x, &result)); } double gsl_sf_log_erfc(double x) { EVAL_RESULT(gsl_sf_log_erfc_e(x, &result)); } double gsl_sf_erf(double x) { EVAL_RESULT(gsl_sf_erf_e(x, &result)); } double gsl_sf_erf_Z(double x) { EVAL_RESULT(gsl_sf_erf_Z_e(x, &result)); } double gsl_sf_erf_Q(double x) { EVAL_RESULT(gsl_sf_erf_Q_e(x, &result)); } double gsl_sf_hazard(double x) { EVAL_RESULT(gsl_sf_hazard_e(x, &result)); } sources_5316/external/gsl/gsl_sf__hyperg_U.c0000644000176700017670000012737610710226217017772 0ustar paulpaul/* specfunc/hyperg_U.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_bessel.h" #include "gsl_sf_laguerre.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_hyperg.h" #include "gsl_sf__error.h" #include "gsl_sf__hyperg.h" #define INT_THRESHOLD (1000.0*GSL_DBL_EPSILON) #define SERIES_EVAL_OK(a,b,x) ((fabs(a) < 5 && b < 5 && x < 2.0) || (fabs(a) < 10 && b < 10 && x < 1.0)) #define ASYMP_EVAL_OK(a,b,x) (GSL_MAX_DBL(fabs(a),1.0)*GSL_MAX_DBL(fabs(1.0+a-b),1.0) < 0.99*fabs(x)) /* Log[U(a,2a,x)] * [Abramowitz+stegun, 13.6.21] * Assumes x > 0, a > 1/2. */ static int hyperg_lnU_beq2a(const double a, const double x, gsl_sf_result * result) { const double lx = log(x); const double nu = a - 0.5; const double lnpre = 0.5*(x - M_LNPI) - nu*lx; gsl_sf_result lnK; gsl_sf_bessel_lnKnu_e(nu, 0.5*x, &lnK); result->val = lnpre + lnK.val; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(0.5*x) + 0.5*M_LNPI + fabs(nu*lx)); result->err += lnK.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* Evaluate u_{N+1}/u_N by Steed's continued fraction method. * * u_N := Gamma[a+N]/Gamma[a] U(a + N, b, x) * * u_{N+1}/u_N = (a+N) U(a+N+1,b,x)/U(a+N,b,x) */ static int hyperg_U_CF1(const double a, const double b, const int N, const double x, double * result, int * count) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 20000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = -(a + N); double b1 = (b - 2.0*a - x - 2.0*(N+1)); double An = b1*Anm1 + a1*Anm2; double Bn = b1*Bnm1 + a1*Bnm2; double an, bn; double fn = An/Bn; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = -(a + N + n - b)*(a + N + n - 1.0); bn = (b - 2.0*a - x - 2.0*(N+n)); An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 10.0*GSL_DBL_EPSILON) break; } *result = fn; *count = n; if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /* Large x asymptotic for x^a U(a,b,x) * Based on SLATEC D9CHU() [W. Fullerton] * * Uses a rational approximation due to Luke. * See [Luke, Algorithms for the Computation of Special Functions, p. 252] * [Luke, Utilitas Math. (1977)] * * z^a U(a,b,z) ~ 2F0(a,1+a-b,-1/z) * * This assumes that a is not a negative integer and * that 1+a-b is not a negative integer. If one of them * is, then the 2F0 actually terminates, the above * relation is an equality, and the sum should be * evaluated directly [see below]. */ static int d9chu(const double a, const double b, const double x, gsl_sf_result * result) { const double EPS = 8.0 * GSL_DBL_EPSILON; /* EPS = 4.0D0*D1MACH(4) */ const int maxiter = 500; double aa[4], bb[4]; int i; double bp = 1.0 + a - b; double ab = a*bp; double ct2 = 2.0 * (x - ab); double sab = a + bp; double ct3 = sab + 1.0 + ab; double anbn = ct3 + sab + 3.0; double ct1 = 1.0 + 2.0*x/anbn; bb[0] = 1.0; aa[0] = 1.0; bb[1] = 1.0 + 2.0*x/ct3; aa[1] = 1.0 + ct2/ct3; bb[2] = 1.0 + 6.0*ct1*x/ct3; aa[2] = 1.0 + 6.0*ab/anbn + 3.0*ct1*ct2/ct3; for(i=4; ival = aa[3]/bb[3]; result->err = 8.0 * GSL_DBL_EPSILON * fabs(result->val); if(i == maxiter) { GSL_ERROR ("error", GSL_EMAXITER); } else { return GSL_SUCCESS; } } /* Evaluate asymptotic for z^a U(a,b,z) ~ 2F0(a,1+a-b,-1/z) * We check for termination of the 2F0 as a special case. * Assumes x > 0. * Also assumes a,b are not too large compared to x. */ static int hyperg_zaU_asymp(const double a, const double b, const double x, gsl_sf_result *result) { const double ap = a; const double bp = 1.0 + a - b; const double rintap = floor(ap + 0.5); const double rintbp = floor(bp + 0.5); const int ap_neg_int = ( ap < 0.0 && fabs(ap - rintap) < INT_THRESHOLD ); const int bp_neg_int = ( bp < 0.0 && fabs(bp - rintbp) < INT_THRESHOLD ); if(ap_neg_int || bp_neg_int) { /* Evaluate 2F0 polynomial. */ double mxi = -1.0/x; double nmax = -(int)(GSL_MIN(ap,bp) - 0.1); double tn = 1.0; double sum = 1.0; double n = 1.0; double sum_err = 0.0; while(n <= nmax) { double apn = (ap+n-1.0); double bpn = (bp+n-1.0); tn *= ((apn/n)*mxi)*bpn; sum += tn; sum_err += 2.0 * GSL_DBL_EPSILON * fabs(tn); n += 1.0; } result->val = sum; result->err = sum_err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(nmax)+1.0) * fabs(sum); return GSL_SUCCESS; } else { return d9chu(a,b,x,result); } } /* Evaluate finite sum which appears below. */ static int hyperg_U_finite_sum(int N, double a, double b, double x, double xeps, gsl_sf_result * result) { int i; double sum_val; double sum_err; if(N <= 0) { double t_val = 1.0; double t_err = 0.0; gsl_sf_result poch; int stat_poch; sum_val = 1.0; sum_err = 0.0; for(i=1; i<= -N; i++) { const double xi1 = i - 1; const double mult = (a+xi1)*x/((b+xi1)*(xi1+1.0)); t_val *= mult; t_err += fabs(mult) * t_err + fabs(t_val) * 8.0 * 2.0 * GSL_DBL_EPSILON; sum_val += t_val; sum_err += t_err; } stat_poch = gsl_sf_poch_e(1.0+a-b, -a, &poch); result->val = sum_val * poch.val; result->err = fabs(sum_val) * poch.err + sum_err * fabs(poch.val); result->err += fabs(poch.val) * (fabs(N) + 2.0) * GSL_DBL_EPSILON * fabs(sum_val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->err *= 2.0; /* FIXME: fudge factor... why is the error estimate too small? */ return stat_poch; } else { const int M = N - 2; if(M < 0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result gbm1; gsl_sf_result gamr; int stat_gbm1; int stat_gamr; double t_val = 1.0; double t_err = 0.0; sum_val = 1.0; sum_err = 0.0; for(i=1; i<=M; i++) { const double mult = (a-b+i)*x/((1.0-b+i)*i); t_val *= mult; t_err += t_err * fabs(mult) + fabs(t_val) * 8.0 * 2.0 * GSL_DBL_EPSILON; sum_val += t_val; sum_err += t_err; } stat_gbm1 = gsl_sf_gamma_e(b-1.0, &gbm1); stat_gamr = gsl_sf_gammainv_e(a, &gamr); if(stat_gbm1 == GSL_SUCCESS) { gsl_sf_result powx1N; int stat_p = gsl_sf_pow_int_e(x, 1-N, &powx1N); double pe_val = powx1N.val * xeps; double pe_err = powx1N.err * fabs(xeps) + 2.0 * GSL_DBL_EPSILON * fabs(pe_val); double coeff_val = gbm1.val * gamr.val * pe_val; double coeff_err = gbm1.err * fabs(gamr.val * pe_val) + gamr.err * fabs(gbm1.val * pe_val) + fabs(gbm1.val * gamr.val) * pe_err + 2.0 * GSL_DBL_EPSILON * fabs(coeff_val); result->val = sum_val * coeff_val; result->err = fabs(sum_val) * coeff_err + sum_err * fabs(coeff_val); result->err += 2.0 * GSL_DBL_EPSILON * (M+2.0) * fabs(result->val); result->err *= 2.0; /* FIXME: fudge factor... why is the error estimate too small? */ return stat_p; } else { result->val = 0.0; result->err = 0.0; return stat_gbm1; } } } } /* Based on SLATEC DCHU() [W. Fullerton] * Assumes x > 0. * This is just a series summation method, and * it is not good for large a. * * I patched up the window for 1+a-b near zero. [GJ] */ static int hyperg_U_series(const double a, const double b, const double x, gsl_sf_result * result) { const double EPS = 2.0 * GSL_DBL_EPSILON; /* EPS = D1MACH(3) */ const double SQRT_EPS = M_SQRT2 * GSL_SQRT_DBL_EPSILON; if(fabs(1.0 + a - b) < SQRT_EPS) { /* Original Comment: ALGORITHM IS BAD WHEN 1+A-B IS NEAR ZERO FOR SMALL X */ /* We can however do the following: * U(a,b,x) = U(a,a+1,x) when 1+a-b=0 * and U(a,a+1,x) = x^(-a). */ double lnr = -a * log(x); int stat_e = gsl_sf_exp_e(lnr, result); result->err += 2.0 * SQRT_EPS * fabs(result->val); return stat_e; } else { double aintb = ( b < 0.0 ? ceil(b-0.5) : floor(b+0.5) ); double beps = b - aintb; int N = aintb; double lnx = log(x); double xeps = exp(-beps*lnx); /* Evaluate finite sum. */ gsl_sf_result sum; int stat_sum = hyperg_U_finite_sum(N, a, b, x, xeps, &sum); /* Evaluate infinite sum. */ int istrt = ( N < 1 ? 1-N : 0 ); double xi = istrt; gsl_sf_result gamr; gsl_sf_result powx; int stat_gamr = gsl_sf_gammainv_e(1.0+a-b, &gamr); int stat_powx = gsl_sf_pow_int_e(x, istrt, &powx); double sarg = beps*M_PI; double sfact = ( sarg != 0.0 ? sarg/sin(sarg) : 1.0 ); double factor_val = sfact * ( GSL_IS_ODD(N) ? -1.0 : 1.0 ) * gamr.val * powx.val; double factor_err = fabs(gamr.val) * powx.err + fabs(powx.val) * gamr.err + 2.0 * GSL_DBL_EPSILON * fabs(factor_val); gsl_sf_result pochai; gsl_sf_result gamri1; gsl_sf_result gamrni; int stat_pochai = gsl_sf_poch_e(a, xi, &pochai); int stat_gamri1 = gsl_sf_gammainv_e(xi + 1.0, &gamri1); int stat_gamrni = gsl_sf_gammainv_e(aintb + xi, &gamrni); int stat_gam123 = GSL_ERROR_SELECT_3(stat_gamr, stat_gamri1, stat_gamrni); int stat_gamall = GSL_ERROR_SELECT_4(stat_sum, stat_gam123, stat_pochai, stat_powx); gsl_sf_result pochaxibeps; gsl_sf_result gamrxi1beps; int stat_pochaxibeps = gsl_sf_poch_e(a, xi-beps, &pochaxibeps); int stat_gamrxi1beps = gsl_sf_gammainv_e(xi + 1.0 - beps, &gamrxi1beps); int stat_all = GSL_ERROR_SELECT_3(stat_gamall, stat_pochaxibeps, stat_gamrxi1beps); double b0_val = factor_val * pochaxibeps.val * gamrni.val * gamrxi1beps.val; double b0_err = fabs(factor_val * pochaxibeps.val * gamrni.val) * gamrxi1beps.err + fabs(factor_val * pochaxibeps.val * gamrxi1beps.val) * gamrni.err + fabs(factor_val * gamrni.val * gamrxi1beps.val) * pochaxibeps.err + fabs(pochaxibeps.val * gamrni.val * gamrxi1beps.val) * factor_err + 2.0 * GSL_DBL_EPSILON * fabs(b0_val); if(fabs(xeps-1.0) < 0.5) { /* C X**(-BEPS) IS CLOSE TO 1.0D0, SO WE MUST BE C CAREFUL IN EVALUATING THE DIFFERENCES. */ int i; gsl_sf_result pch1ai; gsl_sf_result pch1i; gsl_sf_result poch1bxibeps; int stat_pch1ai = gsl_sf_pochrel_e(a + xi, -beps, &pch1ai); int stat_pch1i = gsl_sf_pochrel_e(xi + 1.0 - beps, beps, &pch1i); int stat_poch1bxibeps = gsl_sf_pochrel_e(b+xi, -beps, &poch1bxibeps); double c0_t1_val = beps*pch1ai.val*pch1i.val; double c0_t1_err = fabs(beps) * fabs(pch1ai.val) * pch1i.err + fabs(beps) * fabs(pch1i.val) * pch1ai.err + 2.0 * GSL_DBL_EPSILON * fabs(c0_t1_val); double c0_t2_val = -poch1bxibeps.val + pch1ai.val - pch1i.val + c0_t1_val; double c0_t2_err = poch1bxibeps.err + pch1ai.err + pch1i.err + c0_t1_err + 2.0 * GSL_DBL_EPSILON * fabs(c0_t2_val); double c0_val = factor_val * pochai.val * gamrni.val * gamri1.val * c0_t2_val; double c0_err = fabs(factor_val * pochai.val * gamrni.val * gamri1.val) * c0_t2_err + fabs(factor_val * pochai.val * gamrni.val * c0_t2_val) * gamri1.err + fabs(factor_val * pochai.val * gamri1.val * c0_t2_val) * gamrni.err + fabs(factor_val * gamrni.val * gamri1.val * c0_t2_val) * pochai.err + fabs(pochai.val * gamrni.val * gamri1.val * c0_t2_val) * factor_err + 2.0 * GSL_DBL_EPSILON * fabs(c0_val); /* C XEPS1 = (1.0 - X**(-BEPS))/BEPS = (X**(-BEPS) - 1.0)/(-BEPS) */ gsl_sf_result dexprl; int stat_dexprl = gsl_sf_exprel_e(-beps*lnx, &dexprl); double xeps1_val = lnx * dexprl.val; double xeps1_err = 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(beps*lnx)) * fabs(dexprl.val) + fabs(lnx) * dexprl.err + 2.0 * GSL_DBL_EPSILON * fabs(xeps1_val); double dchu_val = sum.val + c0_val + xeps1_val*b0_val; double dchu_err = sum.err + c0_err + fabs(xeps1_val)*b0_err + xeps1_err * fabs(b0_val) + fabs(b0_val*lnx)*dexprl.err + 2.0 * GSL_DBL_EPSILON * (fabs(sum.val) + fabs(c0_val) + fabs(xeps1_val*b0_val)); double xn = N; double t_val; double t_err; stat_all = GSL_ERROR_SELECT_5(stat_all, stat_dexprl, stat_poch1bxibeps, stat_pch1i, stat_pch1ai); for(i=1; i<2000; i++) { const double xi = istrt + i; const double xi1 = istrt + i - 1; const double tmp = (a-1.0)*(xn+2.0*xi-1.0) + xi*(xi-beps); const double b0_multiplier = (a+xi1-beps)*x/((xn+xi1)*(xi-beps)); const double c0_multiplier_1 = (a+xi1)*x/((b+xi1)*xi); const double c0_multiplier_2 = tmp / (xi*(b+xi1)*(a+xi1-beps)); b0_val *= b0_multiplier; b0_err += fabs(b0_multiplier) * b0_err + fabs(b0_val) * 8.0 * 2.0 * GSL_DBL_EPSILON; c0_val = c0_multiplier_1 * c0_val - c0_multiplier_2 * b0_val; c0_err = fabs(c0_multiplier_1) * c0_err + fabs(c0_multiplier_2) * b0_err + fabs(c0_val) * 8.0 * 2.0 * GSL_DBL_EPSILON + fabs(b0_val * c0_multiplier_2) * 16.0 * 2.0 * GSL_DBL_EPSILON; t_val = c0_val + xeps1_val*b0_val; t_err = c0_err + fabs(xeps1_val)*b0_err; t_err += fabs(b0_val*lnx) * dexprl.err; t_err += fabs(b0_val)*xeps1_err; dchu_val += t_val; dchu_err += t_err; if(fabs(t_val) < EPS*fabs(dchu_val)) break; } result->val = dchu_val; result->err = 2.0 * dchu_err; result->err += 2.0 * fabs(t_val); result->err += 4.0 * GSL_DBL_EPSILON * (i+2.0) * fabs(dchu_val); result->err *= 2.0; /* FIXME: fudge factor */ if(i >= 2000) { GSL_ERROR ("error", GSL_EMAXITER); } else { return stat_all; } } else { /* C X**(-BEPS) IS VERY DIFFERENT FROM 1.0, SO THE C STRAIGHTFORWARD FORMULATION IS STABLE. */ int i; double dchu_val; double dchu_err; double t_val; double t_err; gsl_sf_result dgamrbxi; int stat_dgamrbxi = gsl_sf_gammainv_e(b+xi, &dgamrbxi); double a0_val = factor_val * pochai.val * dgamrbxi.val * gamri1.val / beps; double a0_err = fabs(factor_val * pochai.val * dgamrbxi.val / beps) * gamri1.err + fabs(factor_val * pochai.val * gamri1.val / beps) * dgamrbxi.err + fabs(factor_val * dgamrbxi.val * gamri1.val / beps) * pochai.err + fabs(pochai.val * dgamrbxi.val * gamri1.val / beps) * factor_err + 2.0 * GSL_DBL_EPSILON * fabs(a0_val); stat_all = GSL_ERROR_SELECT_2(stat_all, stat_dgamrbxi); b0_val = xeps * b0_val / beps; b0_err = fabs(xeps / beps) * b0_err + 4.0 * GSL_DBL_EPSILON * fabs(b0_val); dchu_val = sum.val + a0_val - b0_val; dchu_err = sum.err + a0_err + b0_err + 2.0 * GSL_DBL_EPSILON * (fabs(sum.val) + fabs(a0_val) + fabs(b0_val)); for(i=1; i<2000; i++) { double xi = istrt + i; double xi1 = istrt + i - 1; double a0_multiplier = (a+xi1)*x/((b+xi1)*xi); double b0_multiplier = (a+xi1-beps)*x/((aintb+xi1)*(xi-beps)); a0_val *= a0_multiplier; a0_err += fabs(a0_multiplier) * a0_err; b0_val *= b0_multiplier; b0_err += fabs(b0_multiplier) * b0_err; t_val = a0_val - b0_val; t_err = a0_err + b0_err; dchu_val += t_val; dchu_err += t_err; if(fabs(t_val) < EPS*fabs(dchu_val)) break; } result->val = dchu_val; result->err = 2.0 * dchu_err; result->err += 2.0 * fabs(t_val); result->err += 4.0 * GSL_DBL_EPSILON * (i+2.0) * fabs(dchu_val); result->err *= 2.0; /* FIXME: fudge factor */ if(i >= 2000) { GSL_ERROR ("error", GSL_EMAXITER); } else { return stat_all; } } } } /* Assumes b > 0 and x > 0. */ static int hyperg_U_small_ab(const double a, const double b, const double x, gsl_sf_result * result) { if(a == -1.0) { /* U(-1,c+1,x) = Laguerre[c,0,x] = -b + x */ result->val = -b + x; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(b) + fabs(x)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(a == 0.0) { /* U(0,c+1,x) = Laguerre[c,0,x] = 1 */ result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(ASYMP_EVAL_OK(a,b,x)) { double p = pow(x, -a); gsl_sf_result asymp; int stat_asymp = hyperg_zaU_asymp(a, b, x, &asymp); result->val = asymp.val * p; result->err = asymp.err * p; result->err += fabs(asymp.val) * GSL_DBL_EPSILON * fabs(a) * p; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_asymp; } else { return hyperg_U_series(a, b, x, result); } } /* Assumes b > 0 and x > 0. */ static int hyperg_U_small_a_bgt0(const double a, const double b, const double x, gsl_sf_result * result, double * ln_multiplier ) { if(a == 0.0) { result->val = 1.0; result->err = 1.0; *ln_multiplier = 0.0; return GSL_SUCCESS; } else if( (b > 5000.0 && x < 0.90 * fabs(b)) || (b > 500.0 && x < 0.50 * fabs(b)) ) { int stat = gsl_sf_hyperg_U_large_b_e(a, b, x, result, ln_multiplier); if(stat == GSL_EOVRFLW) return GSL_SUCCESS; else return stat; } else if(b > 15.0) { /* Recurse up from b near 1. */ double eps = b - floor(b); double b0 = 1.0 + eps; gsl_sf_result r_Ubm1; gsl_sf_result r_Ub; int stat_0 = hyperg_U_small_ab(a, b0, x, &r_Ubm1); int stat_1 = hyperg_U_small_ab(a, b0+1.0, x, &r_Ub); double Ubm1 = r_Ubm1.val; double Ub = r_Ub.val; double Ubp1; double bp; for(bp = b0+1.0; bpval = Ub; result->err = (fabs(r_Ubm1.err/r_Ubm1.val) + fabs(r_Ub.err/r_Ub.val)) * fabs(Ub); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(b-b0)+1.0) * fabs(Ub); *ln_multiplier = 0.0; return GSL_ERROR_SELECT_2(stat_0, stat_1); } else { *ln_multiplier = 0.0; return hyperg_U_small_ab(a, b, x, result); } } /* We use this to keep track of large * dynamic ranges in the recursions. * This can be important because sometimes * we want to calculate a very large and * a very small number and the answer is * the product, of order 1. This happens, * for instance, when we apply a Kummer * transform to make b positive and * both x and b are large. */ #define RESCALE_2(u0,u1,factor,count) \ do { \ double au0 = fabs(u0); \ if(au0 > factor) { \ u0 /= factor; \ u1 /= factor; \ count++; \ } \ else if(au0 < 1.0/factor) { \ u0 *= factor; \ u1 *= factor; \ count--; \ } \ } while (0) /* Specialization to b >= 1, for integer parameters. * Assumes x > 0. */ static int hyperg_U_int_bge1(const int a, const int b, const double x, gsl_sf_result_e10 * result) { if(a == 0) { result->val = 1.0; result->err = 0.0; result->e10 = 0; return GSL_SUCCESS; } else if(a == -1) { result->val = -b + x; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(b) + fabs(x)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->e10 = 0; return GSL_SUCCESS; } else if(b == a + 1) { /* U(a,a+1,x) = x^(-a) */ return gsl_sf_exp_e10_e(-a*log(x), result); } else if(ASYMP_EVAL_OK(a,b,x)) { const double ln_pre_val = -a*log(x); const double ln_pre_err = 2.0 * GSL_DBL_EPSILON * fabs(ln_pre_val); gsl_sf_result asymp; int stat_asymp = hyperg_zaU_asymp(a, b, x, &asymp); int stat_e = gsl_sf_exp_mult_err_e10_e(ln_pre_val, ln_pre_err, asymp.val, asymp.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_asymp); } else if(SERIES_EVAL_OK(a,b,x)) { gsl_sf_result ser; const int stat_ser = hyperg_U_series(a, b, x, &ser); result->val = ser.val; result->err = ser.err; result->e10 = 0; return stat_ser; } else if(a < 0) { /* Recurse backward from a = -1,0. */ int scale_count = 0; const double scale_factor = GSL_SQRT_DBL_MAX; gsl_sf_result lnm; gsl_sf_result y; double lnscale; double Uap1 = 1.0; /* U(0,b,x) */ double Ua = -b + x; /* U(-1,b,x) */ double Uam1; int ap; for(ap=-1; ap>a; ap--) { Uam1 = ap*(b-ap-1.0)*Uap1 + (x+2.0*ap-b)*Ua; Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count); } lnscale = log(scale_factor); lnm.val = scale_count*lnscale; lnm.err = 2.0 * GSL_DBL_EPSILON * fabs(lnm.val); y.val = Ua; y.err = 4.0 * GSL_DBL_EPSILON * (fabs(a)+1.0) * fabs(Ua); return gsl_sf_exp_mult_err_e10_e(lnm.val, lnm.err, y.val, y.err, result); } else if(b >= 2.0*a + x) { /* Recurse forward from a = 0,1. */ int scale_count = 0; const double scale_factor = GSL_SQRT_DBL_MAX; gsl_sf_result r_Ua; gsl_sf_result lnm; gsl_sf_result y; double lnscale; double lm; int stat_1 = hyperg_U_small_a_bgt0(1.0, b, x, &r_Ua, &lm); /* U(1,b,x) */ int stat_e; double Uam1 = 1.0; /* U(0,b,x) */ double Ua = r_Ua.val; double Uap1; int ap; Uam1 *= exp(-lm); for(ap=1; apa_target; ap--) { Uam1 = -((b-2.0*ap-x)*Ua + ap*(1.0+ap-b)*Uap1); Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count); } if(Ua == 0.0) { result->val = 0.0; result->err = 0.0; result->e10 = 0; GSL_ERROR ("error", GSL_EZERODIV); } else { double lnscl = -scale_count*log(scale_factor); double lnpre_val = lnU_target + lnscl; double lnpre_err = 2.0 * GSL_DBL_EPSILON * (fabs(lnU_target) + fabs(lnscl)); double oUa_err = 2.0 * (fabs(a_target-a) + CF1_count + 1.0) * GSL_DBL_EPSILON * fabs(1.0/Ua); int stat_e = gsl_sf_exp_mult_err_e10_e(lnpre_val, lnpre_err, 1.0/Ua, oUa_err, result); return GSL_ERROR_SELECT_2(stat_e, stat_CF1); } } else { /* Recurse backward to near the b=2a+x line, then * determine normalization by either direct evaluation * or by a forward recursion. The direct evaluation * is needed when x is small (which is precisely * when it is easy to do). */ const double scale_factor = GSL_SQRT_DBL_MAX; int scale_count_for = 0; int scale_count_bck = 0; int a0 = 1; int a1 = a0 + ceil(0.5*(b-x) - a0); double Ua1_bck_val; double Ua1_bck_err; double Ua1_for_val; double Ua1_for_err; int stat_for; int stat_bck; gsl_sf_result lm_for; { /* Recurse back to determine U(a1,b), sans normalization. */ double ru; int CF1_count; int stat_CF1 = hyperg_U_CF1(a, b, 0, x, &ru, &CF1_count); double Ua = 1.0; double Uap1 = ru/a * Ua; double Uam1; int ap; for(ap=a; ap>a1; ap--) { Uam1 = -((b-2.0*ap-x)*Ua + ap*(1.0+ap-b)*Uap1); Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count_bck); } Ua1_bck_val = Ua; Ua1_bck_err = 2.0 * GSL_DBL_EPSILON * (fabs(a1-a)+CF1_count+1.0) * fabs(Ua); stat_bck = stat_CF1; } if(b == 2*a1 && a1 > 1) { /* This can happen when x is small, which is * precisely when we need to be careful with * this evaluation. */ hyperg_lnU_beq2a((double)a1, x, &lm_for); Ua1_for_val = 1.0; Ua1_for_err = 0.0; stat_for = GSL_SUCCESS; } else if(b == 2*a1 - 1 && a1 > 1) { /* Similar to the above. Happens when x is small. * Use * U(a,2a-1) = (x U(a,2a) - U(a-1,2(a-1))) / (2a - 2) */ gsl_sf_result lnU00, lnU12; gsl_sf_result U00, U12; hyperg_lnU_beq2a(a1-1.0, x, &lnU00); hyperg_lnU_beq2a(a1, x, &lnU12); if(lnU00.val > lnU12.val) { lm_for.val = lnU00.val; lm_for.err = lnU00.err; U00.val = 1.0; U00.err = 0.0; gsl_sf_exp_err_e(lnU12.val - lm_for.val, lnU12.err + lm_for.err, &U12); } else { lm_for.val = lnU12.val; lm_for.err = lnU12.err; U12.val = 1.0; U12.err = 0.0; gsl_sf_exp_err_e(lnU00.val - lm_for.val, lnU00.err + lm_for.err, &U00); } Ua1_for_val = (x * U12.val - U00.val) / (2.0*a1 - 2.0); Ua1_for_err = (fabs(x)*U12.err + U00.err) / fabs(2.0*a1 - 2.0); Ua1_for_err += 2.0 * GSL_DBL_EPSILON * fabs(Ua1_for_val); stat_for = GSL_SUCCESS; } else { /* Recurse forward to determine U(a1,b) with * absolute normalization. */ gsl_sf_result r_Ua; double Uam1 = 1.0; /* U(a0-1,b,x) = U(0,b,x) */ double Ua; double Uap1; int ap; double lm_for_local; stat_for = hyperg_U_small_a_bgt0(a0, b, x, &r_Ua, &lm_for_local); /* U(1,b,x) */ Ua = r_Ua.val; Uam1 *= exp(-lm_for_local); lm_for.val = lm_for_local; lm_for.err = 0.0; for(ap=a0; apval = 0.0; result->err = 0.0; result->e10 = 0; GSL_ERROR ("error", GSL_EZERODIV); } else if(Ua1_for_val == 0.0) { /* Should never happen. */ UNDERFLOW_ERROR_E10(result); } else { double lns = (scale_count_for - scale_count_bck)*log(scale_factor); double ln_for_val = log(fabs(Ua1_for_val)); double ln_for_err = GSL_DBL_EPSILON + fabs(Ua1_for_err/Ua1_for_val); double ln_bck_val = log(fabs(Ua1_bck_val)); double ln_bck_err = GSL_DBL_EPSILON + fabs(Ua1_bck_err/Ua1_bck_val); double lnr_val = lm_for.val + ln_for_val - ln_bck_val + lns; double lnr_err = lm_for.err + ln_for_err + ln_bck_err + 2.0 * GSL_DBL_EPSILON * (fabs(lm_for.val) + fabs(ln_for_val) + fabs(ln_bck_val) + fabs(lns)); double sgn = GSL_SIGN(Ua1_for_val) * GSL_SIGN(Ua1_bck_val); int stat_e = gsl_sf_exp_err_e10_e(lnr_val, lnr_err, result); result->val *= sgn; return GSL_ERROR_SELECT_3(stat_e, stat_bck, stat_for); } } } } /* Handle b >= 1 for generic a,b values. */ static int hyperg_U_bge1(const double a, const double b, const double x, gsl_sf_result_e10 * result) { const double rinta = floor(a+0.5); const int a_neg_integer = (a < 0.0 && fabs(a - rinta) < INT_THRESHOLD); if(a == 0.0) { result->val = 1.0; result->err = 0.0; result->e10 = 0; return GSL_SUCCESS; } else if(a_neg_integer && fabs(rinta) < INT_MAX) { /* U(-n,b,x) = (-1)^n n! Laguerre[n,b-1,x] */ const int n = -(int)rinta; const double sgn = (GSL_IS_ODD(n) ? -1.0 : 1.0); gsl_sf_result lnfact; gsl_sf_result L; const int stat_L = gsl_sf_laguerre_n_e(n, b-1.0, x, &L); gsl_sf_lnfact_e(n, &lnfact); { const int stat_e = gsl_sf_exp_mult_err_e10_e(lnfact.val, lnfact.err, sgn*L.val, L.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_L); } } else if(ASYMP_EVAL_OK(a,b,x)) { const double ln_pre_val = -a*log(x); const double ln_pre_err = 2.0 * GSL_DBL_EPSILON * fabs(ln_pre_val); gsl_sf_result asymp; int stat_asymp = hyperg_zaU_asymp(a, b, x, &asymp); int stat_e = gsl_sf_exp_mult_err_e10_e(ln_pre_val, ln_pre_err, asymp.val, asymp.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_asymp); } else if(fabs(a) <= 1.0) { gsl_sf_result rU; double ln_multiplier; int stat_U = hyperg_U_small_a_bgt0(a, b, x, &rU, &ln_multiplier); int stat_e = gsl_sf_exp_mult_err_e10_e(ln_multiplier, 2.0*GSL_DBL_EPSILON*fabs(ln_multiplier), rU.val, rU.err, result); return GSL_ERROR_SELECT_2(stat_U, stat_e); } else if(SERIES_EVAL_OK(a,b,x)) { gsl_sf_result ser; const int stat_ser = hyperg_U_series(a, b, x, &ser); result->val = ser.val; result->err = ser.err; result->e10 = 0; return stat_ser; } else if(a < 0.0) { /* Recurse backward on a and then upward on b. */ const double scale_factor = GSL_SQRT_DBL_MAX; const double a0 = a - floor(a) - 1.0; const double b0 = b - floor(b) + 1.0; int scale_count = 0; double lm_0, lm_1; double lm_max; gsl_sf_result r_Uap1; gsl_sf_result r_Ua; int stat_0 = hyperg_U_small_a_bgt0(a0+1.0, b0, x, &r_Uap1, &lm_0); int stat_1 = hyperg_U_small_a_bgt0(a0, b0, x, &r_Ua, &lm_1); int stat_e; double Uap1 = r_Uap1.val; double Ua = r_Ua.val; double Uam1; double ap; lm_max = GSL_MAX(lm_0, lm_1); Uap1 *= exp(lm_0-lm_max); Ua *= exp(lm_1-lm_max); /* Downward recursion on a. */ for(ap=a0; ap>a+0.1; ap -= 1.0) { Uam1 = ap*(b0-ap-1.0)*Uap1 + (x+2.0*ap-b0)*Ua; Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count); } if(b < 2.0) { /* b == b0, so no recursion necessary */ const double lnscale = log(scale_factor); gsl_sf_result lnm; gsl_sf_result y; lnm.val = lm_max + scale_count * lnscale; lnm.err = 2.0 * GSL_DBL_EPSILON * (fabs(lm_max) + scale_count * fabs(lnscale)); y.val = Ua; y.err = fabs(r_Uap1.err/r_Uap1.val) * fabs(Ua); y.err += fabs(r_Ua.err/r_Ua.val) * fabs(Ua); y.err += 2.0 * GSL_DBL_EPSILON * (fabs(a-a0) + 1.0) * fabs(Ua); y.err *= fabs(lm_0-lm_max) + 1.0; y.err *= fabs(lm_1-lm_max) + 1.0; stat_e = gsl_sf_exp_mult_err_e10_e(lnm.val, lnm.err, y.val, y.err, result); } else { /* Upward recursion on b. */ const double err_mult = fabs(b-b0) + fabs(a-a0) + 1.0; const double lnscale = log(scale_factor); gsl_sf_result lnm; gsl_sf_result y; double Ubm1 = Ua; /* U(a,b0) */ double Ub = (a*(b0-a-1.0)*Uap1 + (a+x)*Ua)/x; /* U(a,b0+1) */ double Ubp1; double bp; for(bp=b0+1.0; bp= 2*a + x) { /* Recurse forward from a near zero. * Note that we cannot cross the singularity at * the line b=a+1, because the only way we could * be in that little wedge is if a < 1. But we * have already dealt with the small a case. */ int scale_count = 0; const double a0 = a - floor(a); const double scale_factor = GSL_SQRT_DBL_MAX; double lnscale; double lm_0, lm_1, lm_max; gsl_sf_result r_Uam1; gsl_sf_result r_Ua; int stat_0 = hyperg_U_small_a_bgt0(a0-1.0, b, x, &r_Uam1, &lm_0); int stat_1 = hyperg_U_small_a_bgt0(a0, b, x, &r_Ua, &lm_1); int stat_e; gsl_sf_result lnm; gsl_sf_result y; double Uam1 = r_Uam1.val; double Ua = r_Ua.val; double Uap1; double ap; lm_max = GSL_MAX(lm_0, lm_1); Uam1 *= exp(lm_0-lm_max); Ua *= exp(lm_1-lm_max); for(ap=a0; apa0+0.1; ap -= 1.0) { Uam1 = -((b-2.0*ap-x)*Ua + ap*(1.0+ap-b)*Uap1); Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count); } stat_U0 = hyperg_U_small_a_bgt0(a0, b, x, &U0, &lm_0); lnscale = log(scale_factor); lnm.val = lm_0 - scale_count * lnscale; lnm.err = 2.0 * GSL_DBL_EPSILON * (fabs(lm_0) + fabs(scale_count * lnscale)); y.val = GSL_SQRT_DBL_MIN*(U0.val/Ua); y.err = GSL_SQRT_DBL_MIN*(U0.err/fabs(Ua)); y.err += 2.0 * GSL_DBL_EPSILON * (fabs(a0-a) + CF1_count + 1.0) * fabs(y.val); stat_e = gsl_sf_exp_mult_err_e10_e(lnm.val, lnm.err, y.val, y.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_U0, stat_CF1); } else { /* Recurse backward to near the b=2a+x line, then * forward from a near zero to get the normalization. */ int scale_count_for = 0; int scale_count_bck = 0; const double scale_factor = GSL_SQRT_DBL_MAX; const double eps = a - floor(a); const double a0 = ( eps == 0.0 ? 1.0 : eps ); const double a1 = a0 + ceil(0.5*(b-x) - a0); gsl_sf_result lnm; gsl_sf_result y; double lm_for; double lnscale; double Ua1_bck; double Ua1_for; int stat_for; int stat_bck; int stat_e; int CF1_count; { /* Recurse back to determine U(a1,b), sans normalization. */ double Uap1; double Ua; double Uam1; double ap; double ru; double r; int stat_CF1 = hyperg_U_CF1(a, b, 0, x, &ru, &CF1_count); r = ru/a; Ua = GSL_SQRT_DBL_MIN; Uap1 = r * Ua; for(ap=a; ap>a1+0.1; ap -= 1.0) { Uam1 = -((b-2.0*ap-x)*Ua + ap*(1.0+ap-b)*Uap1); Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count_bck); } Ua1_bck = Ua; stat_bck = stat_CF1; } { /* Recurse forward to determine U(a1,b) with * absolute normalization. */ gsl_sf_result r_Uam1; gsl_sf_result r_Ua; double lm_0, lm_1; int stat_0 = hyperg_U_small_a_bgt0(a0-1.0, b, x, &r_Uam1, &lm_0); int stat_1 = hyperg_U_small_a_bgt0(a0, b, x, &r_Ua, &lm_1); double Uam1 = r_Uam1.val; double Ua = r_Ua.val; double Uap1; double ap; lm_for = GSL_MAX(lm_0, lm_1); Uam1 *= exp(lm_0 - lm_for); Ua *= exp(lm_1 - lm_for); for(ap=a0; ap= 1) { return hyperg_U_int_bge1(a, b, x, result); } else { /* Use the reflection formula * U(a,b,x) = x^(1-b) U(1+a-b,2-b,x) */ gsl_sf_result_e10 U; double ln_x = log(x); int ap = 1 + a - b; int bp = 2 - b; int stat_e; int stat_U = hyperg_U_int_bge1(ap, bp, x, &U); double ln_pre_val = (1.0-b)*ln_x; double ln_pre_err = 2.0 * GSL_DBL_EPSILON * (fabs(b)+1.0) * fabs(ln_x); ln_pre_err += 2.0 * GSL_DBL_EPSILON * fabs(1.0-b); /* error in log(x) */ stat_e = gsl_sf_exp_mult_err_e10_e(ln_pre_val + U.e10*M_LN10, ln_pre_err, U.val, U.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_U); } } } int gsl_sf_hyperg_U_e10_e(const double a, const double b, const double x, gsl_sf_result_e10 * result) { const double rinta = floor(a + 0.5); const double rintb = floor(b + 0.5); const int a_integer = ( fabs(a - rinta) < INT_THRESHOLD ); const int b_integer = ( fabs(b - rintb) < INT_THRESHOLD ); /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR_E10(result); } else if(a == 0.0) { result->val = 1.0; result->err = 0.0; result->e10 = 0; return GSL_SUCCESS; } else if(a_integer && b_integer) { return gsl_sf_hyperg_U_int_e10_e(rinta, rintb, x, result); } else { if(b >= 1.0) { /* Use b >= 1 function. */ return hyperg_U_bge1(a, b, x, result); } else { /* Use the reflection formula * U(a,b,x) = x^(1-b) U(1+a-b,2-b,x) */ const double lnx = log(x); const double ln_pre_val = (1.0-b)*lnx; const double ln_pre_err = fabs(lnx) * 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(b)); const double ap = 1.0 + a - b; const double bp = 2.0 - b; gsl_sf_result_e10 U; int stat_U = hyperg_U_bge1(ap, bp, x, &U); int stat_e = gsl_sf_exp_mult_err_e10_e(ln_pre_val + U.e10*M_LN10, ln_pre_err, U.val, U.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_U); } } } int gsl_sf_hyperg_U_int_e(const int a, const int b, const double x, gsl_sf_result * result) { gsl_sf_result_e10 re; int stat_U = gsl_sf_hyperg_U_int_e10_e(a, b, x, &re); int stat_c = gsl_sf_result_smash_e(&re, result); return GSL_ERROR_SELECT_2(stat_c, stat_U); } int gsl_sf_hyperg_U_e(const double a, const double b, const double x, gsl_sf_result * result) { gsl_sf_result_e10 re; int stat_U = gsl_sf_hyperg_U_e10_e(a, b, x, &re); int stat_c = gsl_sf_result_smash_e(&re, result); return GSL_ERROR_SELECT_2(stat_c, stat_U); } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_hyperg_U_int(const int a, const int b, const double x) { EVAL_RESULT(gsl_sf_hyperg_U_int_e(a, b, x, &result)); } double gsl_sf_hyperg_U(const double a, const double b, const double x) { EVAL_RESULT(gsl_sf_hyperg_U_e(a, b, x, &result)); } sources_5316/external/gsl/gsl_histogram__file.c0000664000176700017670000000564511723710247020516 0ustar paulpaul/* histogram/file.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_block.h" #include "gsl_histogram.h" int gsl_histogram_fread (FILE * stream, gsl_histogram * h) { int status = gsl_block_raw_fread (stream, h->range, h->n + 1, 1); if (status) return status; status = gsl_block_raw_fread (stream, h->bin, h->n, 1); return status; } int gsl_histogram_fwrite (FILE * stream, const gsl_histogram * h) { int status = gsl_block_raw_fwrite (stream, h->range, h->n + 1, 1); if (status) return status; status = gsl_block_raw_fwrite (stream, h->bin, h->n, 1); return status; } int gsl_histogram_fprintf (FILE * stream, const gsl_histogram * h, const char *range_format, const char *bin_format) { size_t i; const size_t n = h->n; for (i = 0; i < n; i++) { int status = fprintf (stream, range_format, h->range[i]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } status = putc (' ', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } status = fprintf (stream, range_format, h->range[i + 1]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } status = putc (' ', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } status = fprintf (stream, bin_format, h->bin[i]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } status = putc ('\n', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } } return GSL_SUCCESS; } int gsl_histogram_fscanf (FILE * stream, gsl_histogram * h) { size_t i; const size_t n = h->n; double upper; for (i = 0; i < n; i++) { int status = fscanf (stream, "%lg %lg %lg", h->range + i, &upper, h->bin + i); if (status != 3) { GSL_ERROR ("fscanf failed", GSL_EFAILED); } } h->range[n] = upper; return GSL_SUCCESS; } sources_5316/external/gsl/gsl_specfunc__coulomb.c0000664000176700017670000011500211723710247021035 0ustar paulpaul/* specfunc/coulomb.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Evaluation of Coulomb wave functions F_L(eta, x), G_L(eta, x), * and their derivatives. A combination of Steed's method, asymptotic * results, and power series. * * Steed's method: * [Barnett, CPC 21, 297 (1981)] * Power series and other methods: * [Biedenharn et al., PR 97, 542 (1954)] * [Bardin et al., CPC 3, 73 (1972)] * [Abad+Sesma, CPC 71, 110 (1992)] */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_psi.h" #include "gsl_sf_airy.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_gamma.h" #include "gsl_sf_coulomb.h" #include "gsl_specfunc__error.h" /* the L=0 normalization constant * [Abramowitz+Stegun 14.1.8] */ static double C0sq(double eta) { double twopieta = 2.0*M_PI*eta; if(fabs(eta) < GSL_DBL_EPSILON) { return 1.0; } else if(twopieta > GSL_LOG_DBL_MAX) { return 0.0; } else { gsl_sf_result scale; gsl_sf_expm1_e(twopieta, &scale); return twopieta/scale.val; } } /* the full definition of C_L(eta) for any valid L and eta * [Abramowitz and Stegun 14.1.7] * This depends on the complex gamma function. For large * arguments the phase of the complex gamma function is not * very accurately determined. However the modulus is, and that * is all that we need to calculate C_L. * * This is not valid for L <= -3/2 or L = -1. */ static int CLeta(double L, double eta, gsl_sf_result * result) { gsl_sf_result ln1; /* log of numerator Gamma function */ gsl_sf_result ln2; /* log of denominator Gamma function */ double sgn = 1.0; double arg_val, arg_err; if(fabs(eta/(L+1.0)) < GSL_DBL_EPSILON) { gsl_sf_lngamma_e(L+1.0, &ln1); } else { gsl_sf_result p1; /* phase of numerator Gamma -- not used */ gsl_sf_lngamma_complex_e(L+1.0, eta, &ln1, &p1); /* should be ok */ } gsl_sf_lngamma_e(2.0*(L+1.0), &ln2); if(L < -1.0) sgn = -sgn; arg_val = L*M_LN2 - 0.5*eta*M_PI + ln1.val - ln2.val; arg_err = ln1.err + ln2.err; arg_err += GSL_DBL_EPSILON * (fabs(L*M_LN2) + fabs(0.5*eta*M_PI)); return gsl_sf_exp_err_e(arg_val, arg_err, result); } int gsl_sf_coulomb_CL_e(double lam, double eta, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(lam <= -1.0) { DOMAIN_ERROR(result); } else if(fabs(lam) < GSL_DBL_EPSILON) { /* saves a calculation of complex_lngamma(), otherwise not necessary */ result->val = sqrt(C0sq(eta)); result->err = 2.0 * GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { return CLeta(lam, eta, result); } } /* cl[0] .. cl[kmax] = C_{lam_min}(eta) .. C_{lam_min+kmax}(eta) */ int gsl_sf_coulomb_CL_array(double lam_min, int kmax, double eta, double * cl) { int k; gsl_sf_result cl_0; gsl_sf_coulomb_CL_e(lam_min, eta, &cl_0); cl[0] = cl_0.val; for(k=1; k<=kmax; k++) { double L = lam_min + k; cl[k] = cl[k-1] * hypot(L, eta)/(L*(2.0*L+1.0)); } return GSL_SUCCESS; } /* Evaluate the series for Phi_L(eta,x) and Phi_L*(eta,x) * [Abramowitz+Stegun 14.1.5] * [Abramowitz+Stegun 14.1.13] * * The sequence of coefficients A_k^L is * manifestly well-controlled for L >= -1/2 * and eta < 10. * * This makes sense since this is the region * away from threshold, and you expect * the evaluation to become easier as you * get farther from threshold. * * Empirically, this is quite well-behaved for * L >= -1/2 * eta < 10 * x < 10 */ #if 0 static int coulomb_Phi_series(const double lam, const double eta, const double x, double * result, double * result_star) { int kmin = 5; int kmax = 200; int k; double Akm2 = 1.0; double Akm1 = eta/(lam+1.0); double Ak; double xpow = x; double sum = Akm2 + Akm1*x; double sump = (lam+1.0)*Akm2 + (lam+2.0)*Akm1*x; double prev_abs_del = fabs(Akm1*x); double prev_abs_del_p = (lam+2.0) * prev_abs_del; for(k=2; k kmin ) break; /* We need to keep track of the previous delta because when * eta is near zero the odd terms of the sum are very small * and this could lead to premature termination. */ prev_abs_del = abs_del; prev_abs_del_p = abs_del_p; Akm2 = Akm1; Akm1 = Ak; } *result = sum; *result_star = sump; if(k==kmax) { GSL_ERROR ("error", GSL_EMAXITER); } else { return GSL_SUCCESS; } } #endif /* 0 */ /* Determine the connection phase, phi_lambda. * See coulomb_FG_series() below. We have * to be careful about sin(phi)->0. Note that * there is an underflow condition for large * positive eta in any case. */ static int coulomb_connection(const double lam, const double eta, double * cos_phi, double * sin_phi) { if(eta > -GSL_LOG_DBL_MIN/2.0*M_PI-1.0) { *cos_phi = 1.0; *sin_phi = 0.0; GSL_ERROR ("error", GSL_EUNDRFLW); } else if(eta > -GSL_LOG_DBL_EPSILON/(4.0*M_PI)) { const double eps = 2.0 * exp(-2.0*M_PI*eta); const double tpl = tan(M_PI * lam); const double dth = eps * tpl / (tpl*tpl + 1.0); *cos_phi = -1.0 + 0.5 * dth*dth; *sin_phi = -dth; return GSL_SUCCESS; } else { double X = tanh(M_PI * eta) / tan(M_PI * lam); double phi = -atan(X) - (lam + 0.5) * M_PI; *cos_phi = cos(phi); *sin_phi = sin(phi); return GSL_SUCCESS; } } /* Evaluate the Frobenius series for F_lam(eta,x) and G_lam(eta,x). * Homegrown algebra. Evaluates the series for F_{lam} and * F_{-lam-1}, then uses * G_{lam} = (F_{lam} cos(phi) - F_{-lam-1}) / sin(phi) * where * phi = Arg[Gamma[1+lam+I eta]] - Arg[Gamma[-lam + I eta]] - (lam+1/2)Pi * = Arg[Sin[Pi(-lam+I eta)] - (lam+1/2)Pi * = atan2(-cos(lam Pi)sinh(eta Pi), -sin(lam Pi)cosh(eta Pi)) - (lam+1/2)Pi * * = -atan(X) - (lam+1/2) Pi, X = tanh(eta Pi)/tan(lam Pi) * * Not appropriate for lam <= -1/2, lam = 0, or lam >= 1/2. */ static int coulomb_FG_series(const double lam, const double eta, const double x, gsl_sf_result * F, gsl_sf_result * G) { const int max_iter = 800; gsl_sf_result ClamA; gsl_sf_result ClamB; int stat_A = CLeta(lam, eta, &ClamA); int stat_B = CLeta(-lam-1.0, eta, &ClamB); const double tlp1 = 2.0*lam + 1.0; const double pow_x = pow(x, lam); double cos_phi_lam; double sin_phi_lam; double uA_mm2 = 1.0; /* uA sum is for F_{lam} */ double uA_mm1 = x*eta/(lam+1.0); double uA_m; double uB_mm2 = 1.0; /* uB sum is for F_{-lam-1} */ double uB_mm1 = -x*eta/lam; double uB_m; double A_sum = uA_mm2 + uA_mm1; double B_sum = uB_mm2 + uB_mm1; double A_abs_del_prev = fabs(A_sum); double B_abs_del_prev = fabs(B_sum); gsl_sf_result FA, FB; int m = 2; int stat_conn = coulomb_connection(lam, eta, &cos_phi_lam, &sin_phi_lam); if(stat_conn == GSL_EUNDRFLW) { F->val = 0.0; /* FIXME: should this be set to Inf too like G? */ F->err = 0.0; OVERFLOW_ERROR(G); } while(m < max_iter) { double abs_dA; double abs_dB; uA_m = x*(2.0*eta*uA_mm1 - x*uA_mm2)/(m*(m+tlp1)); uB_m = x*(2.0*eta*uB_mm1 - x*uB_mm2)/(m*(m-tlp1)); A_sum += uA_m; B_sum += uB_m; abs_dA = fabs(uA_m); abs_dB = fabs(uB_m); if(m > 15) { /* Don't bother checking until we have gone out a little ways; * a minor optimization. Also make sure to check both the * current and the previous increment because the odd and even * terms of the sum can have very different behaviour, depending * on the value of eta. */ double max_abs_dA = GSL_MAX(abs_dA, A_abs_del_prev); double max_abs_dB = GSL_MAX(abs_dB, B_abs_del_prev); double abs_A = fabs(A_sum); double abs_B = fabs(B_sum); if( max_abs_dA/(max_abs_dA + abs_A) < 4.0*GSL_DBL_EPSILON && max_abs_dB/(max_abs_dB + abs_B) < 4.0*GSL_DBL_EPSILON ) break; } A_abs_del_prev = abs_dA; B_abs_del_prev = abs_dB; uA_mm2 = uA_mm1; uA_mm1 = uA_m; uB_mm2 = uB_mm1; uB_mm1 = uB_m; m++; } FA.val = A_sum * ClamA.val * pow_x * x; FA.err = fabs(A_sum) * ClamA.err * pow_x * x + 2.0*GSL_DBL_EPSILON*fabs(FA.val); FB.val = B_sum * ClamB.val / pow_x; FB.err = fabs(B_sum) * ClamB.err / pow_x + 2.0*GSL_DBL_EPSILON*fabs(FB.val); F->val = FA.val; F->err = FA.err; G->val = (FA.val * cos_phi_lam - FB.val)/sin_phi_lam; G->err = (FA.err * fabs(cos_phi_lam) + FB.err)/fabs(sin_phi_lam); if(m >= max_iter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_ERROR_SELECT_2(stat_A, stat_B); } /* Evaluate the Frobenius series for F_0(eta,x) and G_0(eta,x). * See [Bardin et al., CPC 3, 73 (1972), (14)-(17)]; * note the misprint in (17): nu_0=1 is correct, not nu_0=0. */ static int coulomb_FG0_series(const double eta, const double x, gsl_sf_result * F, gsl_sf_result * G) { const int max_iter = 800; const double x2 = x*x; const double tex = 2.0*eta*x; gsl_sf_result C0; int stat_CL = CLeta(0.0, eta, &C0); gsl_sf_result r1pie; int psi_stat = gsl_sf_psi_1piy_e(eta, &r1pie); double u_mm2 = 0.0; /* u_0 */ double u_mm1 = x; /* u_1 */ double u_m; double v_mm2 = 1.0; /* nu_0 */ double v_mm1 = tex*(2.0*M_EULER-1.0+r1pie.val); /* nu_1 */ double v_m; double u_sum = u_mm2 + u_mm1; double v_sum = v_mm2 + v_mm1; double u_abs_del_prev = fabs(u_sum); double v_abs_del_prev = fabs(v_sum); int m = 2; double u_sum_err = 2.0 * GSL_DBL_EPSILON * fabs(u_sum); double v_sum_err = 2.0 * GSL_DBL_EPSILON * fabs(v_sum); double ln2x = log(2.0*x); while(m < max_iter) { double abs_du; double abs_dv; double m_mm1 = m*(m-1.0); u_m = (tex*u_mm1 - x2*u_mm2)/m_mm1; v_m = (tex*v_mm1 - x2*v_mm2 - 2.0*eta*(2*m-1)*u_m)/m_mm1; u_sum += u_m; v_sum += v_m; abs_du = fabs(u_m); abs_dv = fabs(v_m); u_sum_err += 2.0 * GSL_DBL_EPSILON * abs_du; v_sum_err += 2.0 * GSL_DBL_EPSILON * abs_dv; if(m > 15) { /* Don't bother checking until we have gone out a little ways; * a minor optimization. Also make sure to check both the * current and the previous increment because the odd and even * terms of the sum can have very different behaviour, depending * on the value of eta. */ double max_abs_du = GSL_MAX(abs_du, u_abs_del_prev); double max_abs_dv = GSL_MAX(abs_dv, v_abs_del_prev); double abs_u = fabs(u_sum); double abs_v = fabs(v_sum); if( max_abs_du/(max_abs_du + abs_u) < 40.0*GSL_DBL_EPSILON && max_abs_dv/(max_abs_dv + abs_v) < 40.0*GSL_DBL_EPSILON ) break; } u_abs_del_prev = abs_du; v_abs_del_prev = abs_dv; u_mm2 = u_mm1; u_mm1 = u_m; v_mm2 = v_mm1; v_mm1 = v_m; m++; } F->val = C0.val * u_sum; F->err = C0.err * fabs(u_sum); F->err += fabs(C0.val) * u_sum_err; F->err += 2.0 * GSL_DBL_EPSILON * fabs(F->val); G->val = (v_sum + 2.0*eta*u_sum * ln2x) / C0.val; G->err = (fabs(v_sum) + fabs(2.0*eta*u_sum * ln2x)) / fabs(C0.val) * fabs(C0.err/C0.val); G->err += (v_sum_err + fabs(2.0*eta*u_sum_err*ln2x)) / fabs(C0.val); G->err += 2.0 * GSL_DBL_EPSILON * fabs(G->val); if(m == max_iter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_ERROR_SELECT_2(psi_stat, stat_CL); } /* Evaluate the Frobenius series for F_{-1/2}(eta,x) and G_{-1/2}(eta,x). * Homegrown algebra. */ static int coulomb_FGmhalf_series(const double eta, const double x, gsl_sf_result * F, gsl_sf_result * G) { const int max_iter = 800; const double rx = sqrt(x); const double x2 = x*x; const double tex = 2.0*eta*x; gsl_sf_result Cmhalf; int stat_CL = CLeta(-0.5, eta, &Cmhalf); double u_mm2 = 1.0; /* u_0 */ double u_mm1 = tex * u_mm2; /* u_1 */ double u_m; double v_mm2, v_mm1, v_m; double f_sum, g_sum; double tmp1; gsl_sf_result rpsi_1pe; gsl_sf_result rpsi_1p2e; int m = 2; gsl_sf_psi_1piy_e(eta, &rpsi_1pe); gsl_sf_psi_1piy_e(2.0*eta, &rpsi_1p2e); v_mm2 = 2.0*M_EULER - M_LN2 - rpsi_1pe.val + 2.0*rpsi_1p2e.val; v_mm1 = tex*(v_mm2 - 2.0*u_mm2); f_sum = u_mm2 + u_mm1; g_sum = v_mm2 + v_mm1; while(m < max_iter) { double m2 = m*m; u_m = (tex*u_mm1 - x2*u_mm2)/m2; v_m = (tex*v_mm1 - x2*v_mm2 - 2.0*m*u_m)/m2; f_sum += u_m; g_sum += v_m; if( f_sum != 0.0 && g_sum != 0.0 && (fabs(u_m/f_sum) + fabs(v_m/g_sum) < 10.0*GSL_DBL_EPSILON)) break; u_mm2 = u_mm1; u_mm1 = u_m; v_mm2 = v_mm1; v_mm1 = v_m; m++; } F->val = Cmhalf.val * rx * f_sum; F->err = Cmhalf.err * fabs(rx * f_sum) + 2.0*GSL_DBL_EPSILON*fabs(F->val); tmp1 = f_sum*log(x); G->val = -rx*(tmp1 + g_sum)/Cmhalf.val; G->err = fabs(rx)*(fabs(tmp1) + fabs(g_sum))/fabs(Cmhalf.val) * fabs(Cmhalf.err/Cmhalf.val); if(m == max_iter) GSL_ERROR ("error", GSL_EMAXITER); else return stat_CL; } /* Evolve the backwards recurrence for F,F'. * * F_{lam-1} = (S_lam F_lam + F_lam') / R_lam * F_{lam-1}' = (S_lam F_{lam-1} - R_lam F_lam) * where * R_lam = sqrt(1 + (eta/lam)^2) * S_lam = lam/x + eta/lam * */ static int coulomb_F_recur(double lam_min, int kmax, double eta, double x, double F_lam_max, double Fp_lam_max, double * F_lam_min, double * Fp_lam_min ) { double x_inv = 1.0/x; double fcl = F_lam_max; double fpl = Fp_lam_max; double lam_max = lam_min + kmax; double lam = lam_max; int k; for(k=kmax-1; k>=0; k--) { double el = eta/lam; double rl = hypot(1.0, el); double sl = el + lam*x_inv; double fc_lm1; fc_lm1 = (fcl*sl + fpl)/rl; fpl = fc_lm1*sl - fcl*rl; fcl = fc_lm1; lam -= 1.0; } *F_lam_min = fcl; *Fp_lam_min = fpl; return GSL_SUCCESS; } /* Evolve the forward recurrence for G,G'. * * G_{lam+1} = (S_lam G_lam - G_lam')/R_lam * G_{lam+1}' = R_{lam+1} G_lam - S_lam G_{lam+1} * * where S_lam and R_lam are as above in the F recursion. */ static int coulomb_G_recur(const double lam_min, const int kmax, const double eta, const double x, const double G_lam_min, const double Gp_lam_min, double * G_lam_max, double * Gp_lam_max ) { double x_inv = 1.0/x; double gcl = G_lam_min; double gpl = Gp_lam_min; double lam = lam_min + 1.0; int k; for(k=1; k<=kmax; k++) { double el = eta/lam; double rl = hypot(1.0, el); double sl = el + lam*x_inv; double gcl1 = (sl*gcl - gpl)/rl; gpl = rl*gcl - sl*gcl1; gcl = gcl1; lam += 1.0; } *G_lam_max = gcl; *Gp_lam_max = gpl; return GSL_SUCCESS; } /* Evaluate the first continued fraction, giving * the ratio F'/F at the upper lambda value. * We also determine the sign of F at that point, * since it is the sign of the last denominator * in the continued fraction. */ static int coulomb_CF1(double lambda, double eta, double x, double * fcl_sign, double * result, int * count ) { const double CF1_small = 1.e-30; const double CF1_abort = 1.0e+05; const double CF1_acc = 2.0*GSL_DBL_EPSILON; const double x_inv = 1.0/x; const double px = lambda + 1.0 + CF1_abort; double pk = lambda + 1.0; double F = eta/pk + pk*x_inv; double D, C; double df; *fcl_sign = 1.0; *count = 0; if(fabs(F) < CF1_small) F = CF1_small; D = 0.0; C = F; do { double pk1 = pk + 1.0; double ek = eta / pk; double rk2 = 1.0 + ek*ek; double tk = (pk + pk1)*(x_inv + ek/pk1); D = tk - rk2 * D; C = tk - rk2 / C; if(fabs(C) < CF1_small) C = CF1_small; if(fabs(D) < CF1_small) D = CF1_small; D = 1.0/D; df = D * C; F = F * df; if(D < 0.0) { /* sign of result depends on sign of denominator */ *fcl_sign = - *fcl_sign; } pk = pk1; if( pk > px ) { *result = F; GSL_ERROR ("error", GSL_ERUNAWAY); } ++(*count); } while(fabs(df-1.0) > CF1_acc); *result = F; return GSL_SUCCESS; } #if 0 static int old_coulomb_CF1(const double lambda, double eta, double x, double * fcl_sign, double * result ) { const double CF1_abort = 1.e5; const double CF1_acc = 10.0*GSL_DBL_EPSILON; const double x_inv = 1.0/x; const double px = lambda + 1.0 + CF1_abort; double pk = lambda + 1.0; double D; double df; double F; double p; double pk1; double ek; double fcl = 1.0; double tk; while(1) { ek = eta/pk; F = (ek + pk*x_inv)*fcl + (fcl - 1.0)*x_inv; pk1 = pk + 1.0; if(fabs(eta*x + pk*pk1) > CF1_acc) break; fcl = (1.0 + ek*ek)/(1.0 + eta*eta/(pk1*pk1)); pk = 2.0 + pk; } D = 1.0/((pk + pk1)*(x_inv + ek/pk1)); df = -fcl*(1.0 + ek*ek)*D; if(fcl != 1.0) fcl = -1.0; if(D < 0.0) fcl = -fcl; F = F + df; p = 1.0; do { pk = pk1; pk1 = pk + 1.0; ek = eta / pk; tk = (pk + pk1)*(x_inv + ek/pk1); D = tk - D*(1.0+ek*ek); if(fabs(D) < sqrt(CF1_acc)) { p += 1.0; if(p > 2.0) { printf("HELP............\n"); } } D = 1.0/D; if(D < 0.0) { /* sign of result depends on sign of denominator */ fcl = -fcl; } df = df*(D*tk - 1.0); F = F + df; if( pk > px ) { GSL_ERROR ("error", GSL_ERUNAWAY); } } while(fabs(df) > fabs(F)*CF1_acc); *fcl_sign = fcl; *result = F; return GSL_SUCCESS; } #endif /* 0 */ /* Evaluate the second continued fraction to * obtain the ratio * (G' + i F')/(G + i F) := P + i Q * at the specified lambda value. */ static int coulomb_CF2(const double lambda, const double eta, const double x, double * result_P, double * result_Q, int * count ) { int status = GSL_SUCCESS; const double CF2_acc = 4.0*GSL_DBL_EPSILON; const double CF2_abort = 2.0e+05; const double wi = 2.0*eta; const double x_inv = 1.0/x; const double e2mm1 = eta*eta + lambda*(lambda + 1.0); double ar = -e2mm1; double ai = eta; double br = 2.0*(x - eta); double bi = 2.0; double dr = br/(br*br + bi*bi); double di = -bi/(br*br + bi*bi); double dp = -x_inv*(ar*di + ai*dr); double dq = x_inv*(ar*dr - ai*di); double A, B, C, D; double pk = 0.0; double P = 0.0; double Q = 1.0 - eta*x_inv; *count = 0; do { P += dp; Q += dq; pk += 2.0; ar += pk; ai += wi; bi += 2.0; D = ar*dr - ai*di + br; di = ai*dr + ar*di + bi; C = 1.0/(D*D + di*di); dr = C*D; di = -C*di; A = br*dr - bi*di - 1.; B = bi*dr + br*di; C = dp*A - dq*B; dq = dp*B + dq*A; dp = C; if(pk > CF2_abort) { status = GSL_ERUNAWAY; break; } ++(*count); } while(fabs(dp)+fabs(dq) > (fabs(P)+fabs(Q))*CF2_acc); if(Q < CF2_abort*GSL_DBL_EPSILON*fabs(P)) { status = GSL_ELOSS; } *result_P = P; *result_Q = Q; return status; } /* WKB evaluation of F, G. Assumes 0 < x < turning point. * Overflows are trapped, GSL_EOVRFLW is signalled, * and an exponent is returned such that: * * result_F = fjwkb * exp(-exponent) * result_G = gjwkb * exp( exponent) * * See [Biedenharn et al. Phys. Rev. 97, 542-554 (1955), Section IV] * * Unfortunately, this is not very accurate in general. The * test cases typically have 3-4 digits of precision. One could * argue that this is ok for general use because, for instance, * F is exponentially small in this region and so the absolute * accuracy is still roughly acceptable. But it would be better * to have a systematic method for improving the precision. See * the Abad+Sesma method discussion below. */ static int coulomb_jwkb(const double lam, const double eta, const double x, gsl_sf_result * fjwkb, gsl_sf_result * gjwkb, double * exponent) { const double llp1 = lam*(lam+1.0) + 6.0/35.0; const double llp1_eff = GSL_MAX(llp1, 0.0); const double rho_ghalf = sqrt(x*(2.0*eta - x) + llp1_eff); const double sinh_arg = sqrt(llp1_eff/(eta*eta+llp1_eff)) * rho_ghalf / x; const double sinh_inv = log(sinh_arg + hypot(1.0,sinh_arg)); const double phi = fabs(rho_ghalf - eta*atan2(rho_ghalf,x-eta) - sqrt(llp1_eff) * sinh_inv); const double zeta_half = pow(3.0*phi/2.0, 1.0/3.0); const double prefactor = sqrt(M_PI*phi*x/(6.0 * rho_ghalf)); double F = prefactor * 3.0/zeta_half; double G = prefactor * 3.0/zeta_half; /* Note the sqrt(3) from Bi normalization */ double F_exp; double G_exp; const double airy_scale_exp = phi; gsl_sf_result ai; gsl_sf_result bi; gsl_sf_airy_Ai_scaled_e(zeta_half*zeta_half, GSL_MODE_DEFAULT, &ai); gsl_sf_airy_Bi_scaled_e(zeta_half*zeta_half, GSL_MODE_DEFAULT, &bi); F *= ai.val; G *= bi.val; F_exp = log(F) - airy_scale_exp; G_exp = log(G) + airy_scale_exp; if(G_exp >= GSL_LOG_DBL_MAX) { fjwkb->val = F; gjwkb->val = G; fjwkb->err = 1.0e-3 * fabs(F); /* FIXME: real error here ... could be smaller */ gjwkb->err = 1.0e-3 * fabs(G); *exponent = airy_scale_exp; GSL_ERROR ("error", GSL_EOVRFLW); } else { fjwkb->val = exp(F_exp); gjwkb->val = exp(G_exp); fjwkb->err = 1.0e-3 * fabs(fjwkb->val); gjwkb->err = 1.0e-3 * fabs(gjwkb->val); *exponent = 0.0; return GSL_SUCCESS; } } /* Asymptotic evaluation of F and G below the minimal turning point. * * This is meant to be a drop-in replacement for coulomb_jwkb(). * It uses the expressions in [Abad+Sesma]. This requires some * work because I am not sure where it is valid. They mumble * something about |x| < |lam|^(-1/2) or 8|eta x| > lam when |x| < 1. * This seems true, but I thought the result was based on a uniform * expansion and could be controlled by simply using more terms. */ #if 0 static int coulomb_AS_xlt2eta(const double lam, const double eta, const double x, gsl_sf_result * f_AS, gsl_sf_result * g_AS, double * exponent) { /* no time to do this now... */ } #endif /* 0 */ /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_coulomb_wave_FG_e(const double eta, const double x, const double lam_F, const int k_lam_G, /* lam_G = lam_F - k_lam_G */ gsl_sf_result * F, gsl_sf_result * Fp, gsl_sf_result * G, gsl_sf_result * Gp, double * exp_F, double * exp_G) { const double lam_G = lam_F - k_lam_G; if(x < 0.0 || lam_F <= -0.5 || lam_G <= -0.5) { GSL_SF_RESULT_SET(F, 0.0, 0.0); GSL_SF_RESULT_SET(Fp, 0.0, 0.0); GSL_SF_RESULT_SET(G, 0.0, 0.0); GSL_SF_RESULT_SET(Gp, 0.0, 0.0); *exp_F = 0.0; *exp_G = 0.0; GSL_ERROR ("domain error", GSL_EDOM); } else if(x == 0.0) { gsl_sf_result C0; CLeta(0.0, eta, &C0); GSL_SF_RESULT_SET(F, 0.0, 0.0); GSL_SF_RESULT_SET(Fp, 0.0, 0.0); GSL_SF_RESULT_SET(G, 0.0, 0.0); /* FIXME: should be Inf */ GSL_SF_RESULT_SET(Gp, 0.0, 0.0); /* FIXME: should be Inf */ *exp_F = 0.0; *exp_G = 0.0; if(lam_F == 0.0){ GSL_SF_RESULT_SET(Fp, C0.val, C0.err); } if(lam_G == 0.0) { GSL_SF_RESULT_SET(Gp, 1.0/C0.val, fabs(C0.err/C0.val)/fabs(C0.val)); } GSL_ERROR ("domain error", GSL_EDOM); /* After all, since we are asking for G, this is a domain error... */ } else if(x < 1.2 && 2.0*M_PI*eta < 0.9*(-GSL_LOG_DBL_MIN) && fabs(eta*x) < 10.0) { /* Reduce to a small lambda value and use the series * representations for F and G. We cannot allow eta to * be large and positive because the connection formula * for G_lam is badly behaved due to an underflow in sin(phi_lam) * [see coulomb_FG_series() and coulomb_connection() above]. * Note that large negative eta is ok however. */ const double SMALL = GSL_SQRT_DBL_EPSILON; const int N = (int)(lam_F + 0.5); const int span = GSL_MAX(k_lam_G, N); const double lam_min = lam_F - N; /* -1/2 <= lam_min < 1/2 */ double F_lam_F, Fp_lam_F; double G_lam_G, Gp_lam_G; double F_lam_F_err, Fp_lam_F_err; double Fp_over_F_lam_F; double F_sign_lam_F; double F_lam_min_unnorm, Fp_lam_min_unnorm; double Fp_over_F_lam_min; gsl_sf_result F_lam_min; gsl_sf_result G_lam_min, Gp_lam_min; double F_scale; double Gerr_frac; double F_scale_frac_err; double F_unnorm_frac_err; /* Determine F'/F at lam_F. */ int CF1_count; int stat_CF1 = coulomb_CF1(lam_F, eta, x, &F_sign_lam_F, &Fp_over_F_lam_F, &CF1_count); int stat_ser; int stat_Fr; int stat_Gr; /* Recurse down with unnormalized F,F' values. */ F_lam_F = SMALL; Fp_lam_F = Fp_over_F_lam_F * F_lam_F; if(span != 0) { stat_Fr = coulomb_F_recur(lam_min, span, eta, x, F_lam_F, Fp_lam_F, &F_lam_min_unnorm, &Fp_lam_min_unnorm ); } else { F_lam_min_unnorm = F_lam_F; Fp_lam_min_unnorm = Fp_lam_F; stat_Fr = GSL_SUCCESS; } /* Determine F and G at lam_min. */ if(lam_min == -0.5) { stat_ser = coulomb_FGmhalf_series(eta, x, &F_lam_min, &G_lam_min); } else if(lam_min == 0.0) { stat_ser = coulomb_FG0_series(eta, x, &F_lam_min, &G_lam_min); } else if(lam_min == 0.5) { /* This cannot happen. */ F->val = F_lam_F; F->err = 2.0 * GSL_DBL_EPSILON * fabs(F->val); Fp->val = Fp_lam_F; Fp->err = 2.0 * GSL_DBL_EPSILON * fabs(Fp->val); G->val = G_lam_G; G->err = 2.0 * GSL_DBL_EPSILON * fabs(G->val); Gp->val = Gp_lam_G; Gp->err = 2.0 * GSL_DBL_EPSILON * fabs(Gp->val); *exp_F = 0.0; *exp_G = 0.0; GSL_ERROR ("error", GSL_ESANITY); } else { stat_ser = coulomb_FG_series(lam_min, eta, x, &F_lam_min, &G_lam_min); } /* Determine remaining quantities. */ Fp_over_F_lam_min = Fp_lam_min_unnorm / F_lam_min_unnorm; Gp_lam_min.val = Fp_over_F_lam_min*G_lam_min.val - 1.0/F_lam_min.val; Gp_lam_min.err = fabs(Fp_over_F_lam_min)*G_lam_min.err; Gp_lam_min.err += fabs(1.0/F_lam_min.val) * fabs(F_lam_min.err/F_lam_min.val); F_scale = F_lam_min.val / F_lam_min_unnorm; /* Apply scale to the original F,F' values. */ F_scale_frac_err = fabs(F_lam_min.err/F_lam_min.val); F_unnorm_frac_err = 2.0*GSL_DBL_EPSILON*(CF1_count+span+1); F_lam_F *= F_scale; F_lam_F_err = fabs(F_lam_F) * (F_unnorm_frac_err + F_scale_frac_err); Fp_lam_F *= F_scale; Fp_lam_F_err = fabs(Fp_lam_F) * (F_unnorm_frac_err + F_scale_frac_err); /* Recurse up to get the required G,G' values. */ stat_Gr = coulomb_G_recur(lam_min, GSL_MAX(N-k_lam_G,0), eta, x, G_lam_min.val, Gp_lam_min.val, &G_lam_G, &Gp_lam_G ); F->val = F_lam_F; F->err = F_lam_F_err; F->err += 2.0 * GSL_DBL_EPSILON * fabs(F_lam_F); Fp->val = Fp_lam_F; Fp->err = Fp_lam_F_err; Fp->err += 2.0 * GSL_DBL_EPSILON * fabs(Fp_lam_F); Gerr_frac = fabs(G_lam_min.err/G_lam_min.val) + fabs(Gp_lam_min.err/Gp_lam_min.val); G->val = G_lam_G; G->err = Gerr_frac * fabs(G_lam_G); G->err += 2.0 * (CF1_count+1) * GSL_DBL_EPSILON * fabs(G->val); Gp->val = Gp_lam_G; Gp->err = Gerr_frac * fabs(Gp->val); Gp->err += 2.0 * (CF1_count+1) * GSL_DBL_EPSILON * fabs(Gp->val); *exp_F = 0.0; *exp_G = 0.0; return GSL_ERROR_SELECT_4(stat_ser, stat_CF1, stat_Fr, stat_Gr); } else if(x < 2.0*eta) { /* Use WKB approximation to obtain F and G at the two * lambda values, and use the Wronskian and the * continued fractions for F'/F to obtain F' and G'. */ gsl_sf_result F_lam_F, G_lam_F; gsl_sf_result F_lam_G, G_lam_G; double exp_lam_F, exp_lam_G; int stat_lam_F; int stat_lam_G; int stat_CF1_lam_F; int stat_CF1_lam_G; int CF1_count; double Fp_over_F_lam_F; double Fp_over_F_lam_G; double F_sign_lam_F; double F_sign_lam_G; stat_lam_F = coulomb_jwkb(lam_F, eta, x, &F_lam_F, &G_lam_F, &exp_lam_F); if(k_lam_G == 0) { stat_lam_G = stat_lam_F; F_lam_G = F_lam_F; G_lam_G = G_lam_F; exp_lam_G = exp_lam_F; } else { stat_lam_G = coulomb_jwkb(lam_G, eta, x, &F_lam_G, &G_lam_G, &exp_lam_G); } stat_CF1_lam_F = coulomb_CF1(lam_F, eta, x, &F_sign_lam_F, &Fp_over_F_lam_F, &CF1_count); if(k_lam_G == 0) { stat_CF1_lam_G = stat_CF1_lam_F; F_sign_lam_G = F_sign_lam_F; Fp_over_F_lam_G = Fp_over_F_lam_F; } else { stat_CF1_lam_G = coulomb_CF1(lam_G, eta, x, &F_sign_lam_G, &Fp_over_F_lam_G, &CF1_count); } F->val = F_lam_F.val; F->err = F_lam_F.err; G->val = G_lam_G.val; G->err = G_lam_G.err; Fp->val = Fp_over_F_lam_F * F_lam_F.val; Fp->err = fabs(Fp_over_F_lam_F) * F_lam_F.err; Fp->err += 2.0*GSL_DBL_EPSILON*fabs(Fp->val); Gp->val = Fp_over_F_lam_G * G_lam_G.val - 1.0/F_lam_G.val; Gp->err = fabs(Fp_over_F_lam_G) * G_lam_G.err; Gp->err += fabs(1.0/F_lam_G.val) * fabs(F_lam_G.err/F_lam_G.val); *exp_F = exp_lam_F; *exp_G = exp_lam_G; if(stat_lam_F == GSL_EOVRFLW || stat_lam_G == GSL_EOVRFLW) { GSL_ERROR ("overflow", GSL_EOVRFLW); } else { return GSL_ERROR_SELECT_2(stat_lam_F, stat_lam_G); } } else { /* x > 2 eta, so we know that we can find a lambda value such * that x is above the turning point. We do this, evaluate * using Steed's method at that oscillatory point, then * use recursion on F and G to obtain the required values. * * lam_0 = a value of lambda such that x is below the turning point * lam_min = minimum of lam_0 and the requested lam_G, since * we must go at least as low as lam_G */ const double SMALL = GSL_SQRT_DBL_EPSILON; const double C = sqrt(1.0 + 4.0*x*(x-2.0*eta)); const int N = ceil(lam_F - C + 0.5); const double lam_0 = lam_F - GSL_MAX(N, 0); const double lam_min = GSL_MIN(lam_0, lam_G); double F_lam_F, Fp_lam_F; double G_lam_G, Gp_lam_G; double F_lam_min_unnorm, Fp_lam_min_unnorm; double F_lam_min, Fp_lam_min; double G_lam_min, Gp_lam_min; double Fp_over_F_lam_F; double Fp_over_F_lam_min; double F_sign_lam_F, F_sign_lam_min; double P_lam_min, Q_lam_min; double alpha; double gamma; double F_scale; int CF1_count; int CF2_count; int stat_CF1 = coulomb_CF1(lam_F, eta, x, &F_sign_lam_F, &Fp_over_F_lam_F, &CF1_count); int stat_CF2; int stat_Fr; int stat_Gr; int F_recur_count; int G_recur_count; double err_amplify; F_lam_F = F_sign_lam_F * SMALL; /* unnormalized */ Fp_lam_F = Fp_over_F_lam_F * F_lam_F; /* Backward recurrence to get F,Fp at lam_min */ F_recur_count = GSL_MAX(k_lam_G, N); stat_Fr = coulomb_F_recur(lam_min, F_recur_count, eta, x, F_lam_F, Fp_lam_F, &F_lam_min_unnorm, &Fp_lam_min_unnorm ); Fp_over_F_lam_min = Fp_lam_min_unnorm / F_lam_min_unnorm; /* Steed evaluation to complete evaluation of F,Fp,G,Gp at lam_min */ stat_CF2 = coulomb_CF2(lam_min, eta, x, &P_lam_min, &Q_lam_min, &CF2_count); alpha = Fp_over_F_lam_min - P_lam_min; gamma = alpha/Q_lam_min; F_sign_lam_min = GSL_SIGN(F_lam_min_unnorm) ; F_lam_min = F_sign_lam_min / sqrt(alpha*alpha/Q_lam_min + Q_lam_min); Fp_lam_min = Fp_over_F_lam_min * F_lam_min; G_lam_min = gamma * F_lam_min; Gp_lam_min = (P_lam_min * gamma - Q_lam_min) * F_lam_min; /* Apply scale to values of F,Fp at lam_F (the top). */ F_scale = F_lam_min / F_lam_min_unnorm; F_lam_F *= F_scale; Fp_lam_F *= F_scale; /* Forward recurrence to get G,Gp at lam_G (the top). */ G_recur_count = GSL_MAX(N-k_lam_G,0); stat_Gr = coulomb_G_recur(lam_min, G_recur_count, eta, x, G_lam_min, Gp_lam_min, &G_lam_G, &Gp_lam_G ); err_amplify = CF1_count + CF2_count + F_recur_count + G_recur_count + 1; F->val = F_lam_F; F->err = 8.0*err_amplify*GSL_DBL_EPSILON * fabs(F->val); Fp->val = Fp_lam_F; Fp->err = 8.0*err_amplify*GSL_DBL_EPSILON * fabs(Fp->val); G->val = G_lam_G; G->err = 8.0*err_amplify*GSL_DBL_EPSILON * fabs(G->val); Gp->val = Gp_lam_G; Gp->err = 8.0*err_amplify*GSL_DBL_EPSILON * fabs(Gp->val); *exp_F = 0.0; *exp_G = 0.0; return GSL_ERROR_SELECT_4(stat_CF1, stat_CF2, stat_Fr, stat_Gr); } } int gsl_sf_coulomb_wave_F_array(double lam_min, int kmax, double eta, double x, double * fc_array, double * F_exp) { if(x == 0.0) { int k; *F_exp = 0.0; for(k=0; k<=kmax; k++) { fc_array[k] = 0.0; } if(lam_min == 0.0){ gsl_sf_result f_0; CLeta(0.0, eta, &f_0); fc_array[0] = f_0.val; } return GSL_SUCCESS; } else { const double x_inv = 1.0/x; const double lam_max = lam_min + kmax; gsl_sf_result F, Fp; gsl_sf_result G, Gp; double G_exp; int stat_FG = gsl_sf_coulomb_wave_FG_e(eta, x, lam_max, 0, &F, &Fp, &G, &Gp, F_exp, &G_exp); double fcl = F.val; double fpl = Fp.val; double lam = lam_max; int k; fc_array[kmax] = F.val; for(k=kmax-1; k>=0; k--) { double el = eta/lam; double rl = hypot(1.0, el); double sl = el + lam*x_inv; double fc_lm1 = (fcl*sl + fpl)/rl; fc_array[k] = fc_lm1; fpl = fc_lm1*sl - fcl*rl; fcl = fc_lm1; lam -= 1.0; } return stat_FG; } } int gsl_sf_coulomb_wave_FG_array(double lam_min, int kmax, double eta, double x, double * fc_array, double * gc_array, double * F_exp, double * G_exp) { const double x_inv = 1.0/x; const double lam_max = lam_min + kmax; gsl_sf_result F, Fp; gsl_sf_result G, Gp; int stat_FG = gsl_sf_coulomb_wave_FG_e(eta, x, lam_max, kmax, &F, &Fp, &G, &Gp, F_exp, G_exp); double fcl = F.val; double fpl = Fp.val; double lam = lam_max; int k; double gcl, gpl; fc_array[kmax] = F.val; for(k=kmax-1; k>=0; k--) { double el = eta/lam; double rl = hypot(1.0, el); double sl = el + lam*x_inv; double fc_lm1; fc_lm1 = (fcl*sl + fpl)/rl; fc_array[k] = fc_lm1; fpl = fc_lm1*sl - fcl*rl; fcl = fc_lm1; lam -= 1.0; } gcl = G.val; gpl = Gp.val; lam = lam_min + 1.0; gc_array[0] = G.val; for(k=1; k<=kmax; k++) { double el = eta/lam; double rl = hypot(1.0, el); double sl = el + lam*x_inv; double gcl1 = (sl*gcl - gpl)/rl; gc_array[k] = gcl1; gpl = rl*gcl - sl*gcl1; gcl = gcl1; lam += 1.0; } return stat_FG; } int gsl_sf_coulomb_wave_FGp_array(double lam_min, int kmax, double eta, double x, double * fc_array, double * fcp_array, double * gc_array, double * gcp_array, double * F_exp, double * G_exp) { const double x_inv = 1.0/x; const double lam_max = lam_min + kmax; gsl_sf_result F, Fp; gsl_sf_result G, Gp; int stat_FG = gsl_sf_coulomb_wave_FG_e(eta, x, lam_max, kmax, &F, &Fp, &G, &Gp, F_exp, G_exp); double fcl = F.val; double fpl = Fp.val; double lam = lam_max; int k; double gcl, gpl; fc_array[kmax] = F.val; fcp_array[kmax] = Fp.val; for(k=kmax-1; k>=0; k--) { double el = eta/lam; double rl = hypot(1.0, el); double sl = el + lam*x_inv; double fc_lm1; fc_lm1 = (fcl*sl + fpl)/rl; fc_array[k] = fc_lm1; fpl = fc_lm1*sl - fcl*rl; fcp_array[k] = fpl; fcl = fc_lm1; lam -= 1.0; } gcl = G.val; gpl = Gp.val; lam = lam_min + 1.0; gc_array[0] = G.val; gcp_array[0] = Gp.val; for(k=1; k<=kmax; k++) { double el = eta/lam; double rl = hypot(1.0, el); double sl = el + lam*x_inv; double gcl1 = (sl*gcl - gpl)/rl; gc_array[k] = gcl1; gpl = rl*gcl - sl*gcl1; gcp_array[k] = gpl; gcl = gcl1; lam += 1.0; } return stat_FG; } int gsl_sf_coulomb_wave_sphF_array(double lam_min, int kmax, double eta, double x, double * fc_array, double * F_exp) { if(x < 0.0 || lam_min < -0.5) { GSL_ERROR ("domain error", GSL_EDOM); } else if(x < 10.0/GSL_DBL_MAX) { int k; for(k=0; k<=kmax; k++) { fc_array[k] = 0.0; } if(lam_min == 0.0) { fc_array[0] = sqrt(C0sq(eta)); } *F_exp = 0.0; if(x == 0.0) return GSL_SUCCESS; else GSL_ERROR ("underflow", GSL_EUNDRFLW); } else { int k; int stat_F = gsl_sf_coulomb_wave_F_array(lam_min, kmax, eta, x, fc_array, F_exp); for(k=0; k<=kmax; k++) { fc_array[k] = fc_array[k] / x; } return stat_F; } } sources_5316/external/gsl/gsl_cblas__ctrmm.c0000664000176700017670000000072311723710247020000 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ctrmm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const void *alpha, const void *A, const int lda, void *B, const int ldb) { #define BASE float #include "gsl_cblas__source_trmm_c.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__ctrmv.c0000664000176700017670000000061311723710247020007 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ctrmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *A, const int lda, void *X, const int incX) { #define BASE float #include "gsl_cblas__source_trmv_c.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_dot_c.h0000664000176700017670000000250011705263724021331 0ustar paulpaul/* blas/source_dot_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { BASE r_real = 0.0; BASE r_imag = 0.0; INDEX i; INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE x_real = CONST_REAL(X, ix); const BASE x_imag = CONST_IMAG(X, ix); const BASE y_real = CONST_REAL(Y, iy); const BASE y_imag = CONST_IMAG(Y, iy); r_real += x_real * y_real - CONJ_SIGN * x_imag * y_imag; r_imag += x_real * y_imag + CONJ_SIGN * x_imag * y_real; ix += incX; iy += incY; } REAL0(result) = r_real; IMAG0(result) = r_imag; } sources_5316/external/gsl/gsl_sf__bessel_amp_phase.h0000644000176700017670000000277710707442037021512 0ustar paulpaul/* specfunc/bessel_amp_phase.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef _BESSEL_AMP_PHASE_H_ #define _BESSEL_AMP_PHASE_H_ #include "gsl_sf__chebyshev.h" extern const cheb_series _gsl_sf_bessel_amp_phase_bm0_cs; extern const cheb_series _gsl_sf_bessel_amp_phase_bth0_cs; extern const cheb_series _gsl_sf_bessel_amp_phase_bm1_cs; extern const cheb_series _gsl_sf_bessel_amp_phase_bth1_cs; /* large argument expansions [Abramowitz+Stegun, 9.2.28-29] * * thetanu_corr = thetanu - x + 1/2 nu Pi * * assumes x > 0 */ int gsl_sf_bessel_asymp_Mnu_e(const double nu, const double x, double * result); int gsl_sf_bessel_asymp_thetanu_corr_e(const double nu, const double x, double * result); /* w/o x term */ #endif /* !_BESSEL_AMP_PHASE_H_ */ sources_5316/external/gsl/gsl_monte__vegas.c0000664000176700017670000005160111723710247020022 0ustar paulpaul/* monte/vegas.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Michael Booth * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: MJB */ /* Modified by: Brian Gough, 12/2000 */ /* This is an implementation of the adaptive Monte-Carlo algorithm of G. P. Lepage, originally described in J. Comp. Phys. 27, 192(1978). The current version of the algorithm was described in the Cornell preprint CLNS-80/447 of March, 1980. This code follows most closely the c version by D.R.Yennie, coded in 1984. The input coordinates are x[j], with upper and lower limits xu[j] and xl[j]. The integration length in the j-th direction is delx[j]. Each coordinate x[j] is rescaled to a variable y[j] in the range 0 to 1. The range is divided into bins with boundaries xi[i][j], where i=0 corresponds to y=0 and i=bins to y=1. The grid is refined (ie, bins are adjusted) using d[i][j] which is some variation on the squared sum. A third parameter used in defining the real coordinate using random numbers is called z. It ranges from 0 to bins. Its integer part gives the lower index of the bin into which a call is to be placed, and the remainder gives the location inside the bin. When stratified sampling is used the bins are grouped into boxes, and the algorithm allocates an equal number of function calls to each box. The variable alpha controls how "stiff" the rebinning algorithm is. alpha = 0 means never change the grid. Alpha is typically set between 1 and 2. */ /* configuration headers */ #include "gsl__config.h" /* standard headers */ #include #include /* gsl headers */ #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_rng.h" #include "gsl_monte_vegas.h" /* lib-specific headers */ #define BINS_MAX 50 /* even integer, will be divided by two */ /* A separable grid with coordinates and values */ #define COORD(s,i,j) ((s)->xi[(i)*(s)->dim + (j)]) #define NEW_COORD(s,i) ((s)->xin[(i)]) #define VALUE(s,i,j) ((s)->d[(i)*(s)->dim + (j)]) /* predeclare functions */ typedef int coord; static void init_grid (gsl_monte_vegas_state * s, double xl[], double xu[], size_t dim); static void reset_grid_values (gsl_monte_vegas_state * s); static void init_box_coord (gsl_monte_vegas_state * s, coord box[]); static int change_box_coord (gsl_monte_vegas_state * s, coord box[]); static void accumulate_distribution (gsl_monte_vegas_state * s, coord bin[], double y); static void random_point (double x[], coord bin[], double *bin_vol, const coord box[], const double xl[], const double xu[], gsl_monte_vegas_state * s, gsl_rng * r); static void resize_grid (gsl_monte_vegas_state * s, unsigned int bins); static void refine_grid (gsl_monte_vegas_state * s); static void print_lim (gsl_monte_vegas_state * state, double xl[], double xu[], unsigned long dim); static void print_head (gsl_monte_vegas_state * state, unsigned long num_dim, unsigned long calls, unsigned int it_num, unsigned int bins, unsigned int boxes); static void print_res (gsl_monte_vegas_state * state, unsigned int itr, double res, double err, double cum_res, double cum_err, double chi_sq); static void print_dist (gsl_monte_vegas_state * state, unsigned long dim); static void print_grid (gsl_monte_vegas_state * state, unsigned long dim); int gsl_monte_vegas_integrate (gsl_monte_function * f, double xl[], double xu[], size_t dim, size_t calls, gsl_rng * r, gsl_monte_vegas_state * state, double *result, double *abserr) { double cum_int, cum_sig; size_t i, k, it; if (dim != state->dim) { GSL_ERROR ("number of dimensions must match allocated size", GSL_EINVAL); } for (i = 0; i < dim; i++) { if (xu[i] <= xl[i]) { GSL_ERROR ("xu must be greater than xl", GSL_EINVAL); } if (xu[i] - xl[i] > GSL_DBL_MAX) { GSL_ERROR ("Range of integration is too large, please rescale", GSL_EINVAL); } } if (state->stage == 0) { init_grid (state, xl, xu, dim); if (state->verbose >= 0) { print_lim (state, xl, xu, dim); } } if (state->stage <= 1) { state->wtd_int_sum = 0; state->sum_wgts = 0; state->chi_sum = 0; state->it_num = 1; state->samples = 0; } if (state->stage <= 2) { unsigned int bins = state->bins_max; unsigned int boxes = 1; if (state->mode != GSL_VEGAS_MODE_IMPORTANCE_ONLY) { /* shooting for 2 calls/box */ boxes = floor (pow (calls / 2.0, 1.0 / dim)); state->mode = GSL_VEGAS_MODE_IMPORTANCE; if (2 * boxes >= state->bins_max) { /* if bins/box < 2 */ int box_per_bin = GSL_MAX (boxes / state->bins_max, 1); bins = GSL_MIN(boxes / box_per_bin, state->bins_max); boxes = box_per_bin * bins; state->mode = GSL_VEGAS_MODE_STRATIFIED; } } { double tot_boxes = pow ((double) boxes, (double) dim); state->calls_per_box = GSL_MAX (calls / tot_boxes, 2); calls = state->calls_per_box * tot_boxes; } /* total volume of x-space/(avg num of calls/bin) */ state->jac = state->vol * pow ((double) bins, (double) dim) / calls; state->boxes = boxes; /* If the number of bins changes from the previous invocation, bins are expanded or contracted accordingly, while preserving bin density */ if (bins != state->bins) { resize_grid (state, bins); if (state->verbose > 1) { print_grid (state, dim); } } if (state->verbose >= 0) { print_head (state, dim, calls, state->it_num, state->bins, state->boxes); } } state->it_start = state->it_num; cum_int = 0.0; cum_sig = 0.0; state->chisq = 0.0; for (it = 0; it < state->iterations; it++) { double intgrl = 0.0, intgrl_sq = 0.0; double sig = 0.0; double wgt; size_t calls_per_box = state->calls_per_box; double jacbin = state->jac; double *x = state->x; coord *bin = state->bin; state->it_num = state->it_start + it; reset_grid_values (state); init_box_coord (state, state->box); do { double m = 0, q = 0; double f_sq_sum = 0.0; for (k = 0; k < calls_per_box; k++) { double fval, bin_vol; random_point (x, bin, &bin_vol, state->box, xl, xu, state, r); fval = jacbin * bin_vol * GSL_MONTE_FN_EVAL (f, x); /* recurrence for mean and variance */ { double d = fval - m; m += d / (k + 1.0); q += d * d * (k / (k + 1.0)); } if (state->mode != GSL_VEGAS_MODE_STRATIFIED) { double f_sq = fval * fval; accumulate_distribution (state, bin, f_sq); } } intgrl += m * calls_per_box; f_sq_sum = q * calls_per_box ; sig += f_sq_sum ; if (state->mode == GSL_VEGAS_MODE_STRATIFIED) { accumulate_distribution (state, bin, f_sq_sum); } } while (change_box_coord (state, state->box)); /* Compute final results for this iteration */ sig = sig / (calls_per_box - 1.0) ; if (sig > 0) { wgt = 1.0 / sig; } else if (state->sum_wgts > 0) { wgt = state->sum_wgts / state->samples; } else { wgt = 0.0; } intgrl_sq = intgrl * intgrl; state->result = intgrl; state->sigma = sqrt(sig); if (wgt > 0.0) { state->samples++ ; state->sum_wgts += wgt; state->wtd_int_sum += intgrl * wgt; state->chi_sum += intgrl_sq * wgt; cum_int = state->wtd_int_sum / state->sum_wgts; cum_sig = sqrt (1 / state->sum_wgts); if (state->samples > 1) { state->chisq = (state->chi_sum - state->wtd_int_sum * cum_int) / (state->samples - 1.0); } } else { cum_int += (intgrl - cum_int) / (it + 1.0); cum_sig = 0.0; } if (state->verbose >= 0) { print_res (state, state->it_num, intgrl, sqrt (sig), cum_int, cum_sig, state->chisq); if (it + 1 == state->iterations && state->verbose > 0) { print_grid (state, dim); } } if (state->verbose > 1) { print_dist (state, dim); } refine_grid (state); if (state->verbose > 1) { print_grid (state, dim); } } /* By setting stage to 1 further calls will generate independent estimates based on the same grid, although it may be rebinned. */ state->stage = 1; *result = cum_int; *abserr = cum_sig; return GSL_SUCCESS; } gsl_monte_vegas_state * gsl_monte_vegas_alloc (size_t dim) { gsl_monte_vegas_state *s = (gsl_monte_vegas_state *) malloc (sizeof (gsl_monte_vegas_state)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for vegas state struct", GSL_ENOMEM, 0); } s->delx = (double *) malloc (dim * sizeof (double)); if (s->delx == 0) { free (s); GSL_ERROR_VAL ("failed to allocate space for delx", GSL_ENOMEM, 0); } s->d = (double *) malloc (BINS_MAX * dim * sizeof (double)); if (s->d == 0) { free (s->delx); free (s); GSL_ERROR_VAL ("failed to allocate space for d", GSL_ENOMEM, 0); } s->xi = (double *) malloc ((BINS_MAX + 1) * dim * sizeof (double)); if (s->xi == 0) { free (s->d); free (s->delx); free (s); GSL_ERROR_VAL ("failed to allocate space for xi", GSL_ENOMEM, 0); } s->xin = (double *) malloc ((BINS_MAX + 1) * sizeof (double)); if (s->xin == 0) { free (s->xi); free (s->d); free (s->delx); free (s); GSL_ERROR_VAL ("failed to allocate space for xin", GSL_ENOMEM, 0); } s->weight = (double *) malloc (BINS_MAX * sizeof (double)); if (s->weight == 0) { free (s->xin); free (s->xi); free (s->d); free (s->delx); free (s); GSL_ERROR_VAL ("failed to allocate space for xin", GSL_ENOMEM, 0); } s->box = (coord *) malloc (dim * sizeof (coord)); if (s->box == 0) { free (s->weight); free (s->xin); free (s->xi); free (s->d); free (s->delx); free (s); GSL_ERROR_VAL ("failed to allocate space for box", GSL_ENOMEM, 0); } s->bin = (coord *) malloc (dim * sizeof (coord)); if (s->bin == 0) { free (s->box); free (s->weight); free (s->xin); free (s->xi); free (s->d); free (s->delx); free (s); GSL_ERROR_VAL ("failed to allocate space for bin", GSL_ENOMEM, 0); } s->x = (double *) malloc (dim * sizeof (double)); if (s->x == 0) { free (s->bin); free (s->box); free (s->weight); free (s->xin); free (s->xi); free (s->d); free (s->delx); free (s); GSL_ERROR_VAL ("failed to allocate space for x", GSL_ENOMEM, 0); } s->dim = dim; s->bins_max = BINS_MAX; gsl_monte_vegas_init (s); return s; } /* Set some default values and whatever */ int gsl_monte_vegas_init (gsl_monte_vegas_state * state) { state->stage = 0; state->alpha = 1.5; state->verbose = -1; state->iterations = 5; state->mode = GSL_VEGAS_MODE_IMPORTANCE; state->chisq = 0; state->bins = state->bins_max; state->ostream = stdout; return GSL_SUCCESS; } void gsl_monte_vegas_free (gsl_monte_vegas_state * s) { free (s->x); free (s->delx); free (s->d); free (s->xi); free (s->xin); free (s->weight); free (s->box); free (s->bin); free (s); } static void init_box_coord (gsl_monte_vegas_state * s, coord box[]) { size_t i; size_t dim = s->dim; for (i = 0; i < dim; i++) { box[i] = 0; } } /* change_box_coord steps through the box coord like {0,0}, {0, 1}, {0, 2}, {0, 3}, {1, 0}, {1, 1}, {1, 2}, ... */ static int change_box_coord (gsl_monte_vegas_state * s, coord box[]) { int j = s->dim - 1; int ng = s->boxes; while (j >= 0) { box[j] = (box[j] + 1) % ng; if (box[j] != 0) { return 1; } j--; } return 0; } static void init_grid (gsl_monte_vegas_state * s, double xl[], double xu[], size_t dim) { size_t j; double vol = 1.0; s->bins = 1; for (j = 0; j < dim; j++) { double dx = xu[j] - xl[j]; s->delx[j] = dx; vol *= dx; COORD (s, 0, j) = 0.0; COORD (s, 1, j) = 1.0; } s->vol = vol; } static void reset_grid_values (gsl_monte_vegas_state * s) { size_t i, j; size_t dim = s->dim; size_t bins = s->bins; for (i = 0; i < bins; i++) { for (j = 0; j < dim; j++) { VALUE (s, i, j) = 0.0; } } } static void accumulate_distribution (gsl_monte_vegas_state * s, coord bin[], double y) { size_t j; size_t dim = s->dim; for (j = 0; j < dim; j++) { int i = bin[j]; VALUE (s, i, j) += y; } } static void random_point (double x[], coord bin[], double *bin_vol, const coord box[], const double xl[], const double xu[], gsl_monte_vegas_state * s, gsl_rng * r) { /* Use the random number generator r to return a random position x in a given box. The value of bin gives the bin location of the random position (there may be several bins within a given box) */ double vol = 1.0; size_t j; size_t dim = s->dim; size_t bins = s->bins; size_t boxes = s->boxes; DISCARD_POINTER(xu); /* prevent warning about unused parameter */ for (j = 0; j < dim; ++j) { /* box[j] + ran gives the position in the box units, while z is the position in bin units. */ double z = ((box[j] + gsl_rng_uniform_pos (r)) / boxes) * bins; int k = z; double y, bin_width; bin[j] = k; if (k == 0) { bin_width = COORD (s, 1, j); y = z * bin_width; } else { bin_width = COORD (s, k + 1, j) - COORD (s, k, j); y = COORD (s, k, j) + (z - k) * bin_width; } x[j] = xl[j] + y * s->delx[j]; vol *= bin_width; } *bin_vol = vol; } static void resize_grid (gsl_monte_vegas_state * s, unsigned int bins) { size_t j, k; size_t dim = s->dim; /* weight is ratio of bin sizes */ double pts_per_bin = (double) s->bins / (double) bins; for (j = 0; j < dim; j++) { double xold; double xnew = 0; double dw = 0; int i = 1; for (k = 1; k <= s->bins; k++) { dw += 1.0; xold = xnew; xnew = COORD (s, k, j); for (; dw > pts_per_bin; i++) { dw -= pts_per_bin; NEW_COORD (s, i) = xnew - (xnew - xold) * dw; } } for (k = 1 ; k < bins; k++) { COORD(s, k, j) = NEW_COORD(s, k); } COORD (s, bins, j) = 1; } s->bins = bins; } static void refine_grid (gsl_monte_vegas_state * s) { size_t i, j, k; size_t dim = s->dim; size_t bins = s->bins; for (j = 0; j < dim; j++) { double grid_tot_j, tot_weight; double * weight = s->weight; double oldg = VALUE (s, 0, j); double newg = VALUE (s, 1, j); VALUE (s, 0, j) = (oldg + newg) / 2; grid_tot_j = VALUE (s, 0, j); /* This implements gs[i][j] = (gs[i-1][j]+gs[i][j]+gs[i+1][j])/3 */ for (i = 1; i < bins - 1; i++) { double rc = oldg + newg; oldg = newg; newg = VALUE (s, i + 1, j); VALUE (s, i, j) = (rc + newg) / 3; grid_tot_j += VALUE (s, i, j); } VALUE (s, bins - 1, j) = (newg + oldg) / 2; grid_tot_j += VALUE (s, bins - 1, j); tot_weight = 0; for (i = 0; i < bins; i++) { weight[i] = 0; if (VALUE (s, i, j) > 0) { oldg = grid_tot_j / VALUE (s, i, j); /* damped change */ weight[i] = pow (((oldg - 1) / oldg / log (oldg)), s->alpha); } tot_weight += weight[i]; #ifdef DEBUG printf("weight[%d] = %g\n", i, weight[i]); #endif } { double pts_per_bin = tot_weight / bins; double xold; double xnew = 0; double dw = 0; i = 1; for (k = 0; k < bins; k++) { dw += weight[k]; xold = xnew; xnew = COORD (s, k + 1, j); for (; dw > pts_per_bin; i++) { dw -= pts_per_bin; NEW_COORD (s, i) = xnew - (xnew - xold) * dw / weight[k]; } } for (k = 1 ; k < bins ; k++) { COORD(s, k, j) = NEW_COORD(s, k); } COORD (s, bins, j) = 1; } } } static void print_lim (gsl_monte_vegas_state * state, double xl[], double xu[], unsigned long dim) { unsigned long j; fprintf (state->ostream, "The limits of integration are:\n"); for (j = 0; j < dim; ++j) fprintf (state->ostream, "\nxl[%lu]=%f xu[%lu]=%f", j, xl[j], j, xu[j]); fprintf (state->ostream, "\n"); fflush (state->ostream); } static void print_head (gsl_monte_vegas_state * state, unsigned long num_dim, unsigned long calls, unsigned int it_num, unsigned int bins, unsigned int boxes) { fprintf (state->ostream, "\nnum_dim=%lu, calls=%lu, it_num=%d, max_it_num=%d ", num_dim, calls, it_num, state->iterations); fprintf (state->ostream, "verb=%d, alph=%.2f,\nmode=%d, bins=%d, boxes=%d\n", state->verbose, state->alpha, state->mode, bins, boxes); fprintf (state->ostream, "\n single.......iteration "); fprintf (state->ostream, "accumulated......results \n"); fprintf (state->ostream, "iteration integral sigma integral "); fprintf (state->ostream, " sigma chi-sq/it\n\n"); fflush (state->ostream); } static void print_res (gsl_monte_vegas_state * state, unsigned int itr, double res, double err, double cum_res, double cum_err, double chi_sq) { fprintf (state->ostream, "%4d %6.4e %10.2e %6.4e %8.2e %10.2e\n", itr, res, err, cum_res, cum_err, chi_sq); fflush (state->ostream); } static void print_dist (gsl_monte_vegas_state * state, unsigned long dim) { unsigned long i, j; int p = state->verbose; if (p < 1) return; for (j = 0; j < dim; ++j) { fprintf (state->ostream, "\n axis %lu \n", j); fprintf (state->ostream, " x g\n"); for (i = 0; i < state->bins; i++) { fprintf (state->ostream, "weight [%11.2e , %11.2e] = ", COORD (state, i, j), COORD(state,i+1,j)); fprintf (state->ostream, " %11.2e\n", VALUE (state, i, j)); } fprintf (state->ostream, "\n"); } fprintf (state->ostream, "\n"); fflush (state->ostream); } static void print_grid (gsl_monte_vegas_state * state, unsigned long dim) { unsigned long i, j; int p = state->verbose; if (p < 1) return; for (j = 0; j < dim; ++j) { fprintf (state->ostream, "\n axis %lu \n", j); fprintf (state->ostream, " x \n"); for (i = 0; i <= state->bins; i++) { fprintf (state->ostream, "%11.2e", COORD (state, i, j)); if (i % 5 == 4) fprintf (state->ostream, "\n"); } fprintf (state->ostream, "\n"); } fprintf (state->ostream, "\n"); fflush (state->ostream); } sources_5316/external/gsl/gsl_linalg__tridiag.c0000664000176700017670000003670711723710247020476 0ustar paulpaul/* linalg/tridiag.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2002, 2004, 2007 Gerard Jungman, Brian Gough, David Necas * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_linalg__tridiag.h" #include "gsl_linalg.h" /* for description of method see [Engeln-Mullges + Uhlig, p. 92] * * diag[0] offdiag[0] 0 ..... * offdiag[0] diag[1] offdiag[1] ..... * 0 offdiag[1] diag[2] * 0 0 offdiag[2] ..... */ static int solve_tridiag( const double diag[], size_t d_stride, const double offdiag[], size_t o_stride, const double b[], size_t b_stride, double x[], size_t x_stride, size_t N) { int status = GSL_SUCCESS; double *gamma = (double *) malloc (N * sizeof (double)); double *alpha = (double *) malloc (N * sizeof (double)); double *c = (double *) malloc (N * sizeof (double)); double *z = (double *) malloc (N * sizeof (double)); if (gamma == 0 || alpha == 0 || c == 0 || z == 0) { GSL_ERROR("failed to allocate working space", GSL_ENOMEM); } else { size_t i, j; /* Cholesky decomposition A = L.D.L^t lower_diag(L) = gamma diag(D) = alpha */ alpha[0] = diag[0]; gamma[0] = offdiag[0] / alpha[0]; if (alpha[0] == 0) { status = GSL_EZERODIV; } for (i = 1; i < N - 1; i++) { alpha[i] = diag[d_stride * i] - offdiag[o_stride*(i - 1)] * gamma[i - 1]; gamma[i] = offdiag[o_stride * i] / alpha[i]; if (alpha[i] == 0) { status = GSL_EZERODIV; } } if (N > 1) { alpha[N - 1] = diag[d_stride * (N - 1)] - offdiag[o_stride*(N - 2)] * gamma[N - 2]; } /* update RHS */ z[0] = b[0]; for (i = 1; i < N; i++) { z[i] = b[b_stride * i] - gamma[i - 1] * z[i - 1]; } for (i = 0; i < N; i++) { c[i] = z[i] / alpha[i]; } /* backsubstitution */ x[x_stride * (N - 1)] = c[N - 1]; if (N >= 2) { for (i = N - 2, j = 0; j <= N - 2; j++, i--) { x[x_stride * i] = c[i] - gamma[i] * x[x_stride * (i + 1)]; } } } if (z != 0) free (z); if (c != 0) free (c); if (alpha != 0) free (alpha); if (gamma != 0) free (gamma); if (status == GSL_EZERODIV) { GSL_ERROR ("matrix must be positive definite", status); } return status; } /* plain gauss elimination, only not bothering with the zeroes * * diag[0] abovediag[0] 0 ..... * belowdiag[0] diag[1] abovediag[1] ..... * 0 belowdiag[1] diag[2] * 0 0 belowdiag[2] ..... */ static int solve_tridiag_nonsym( const double diag[], size_t d_stride, const double abovediag[], size_t a_stride, const double belowdiag[], size_t b_stride, const double rhs[], size_t r_stride, double x[], size_t x_stride, size_t N) { int status = GSL_SUCCESS; double *alpha = (double *) malloc (N * sizeof (double)); double *z = (double *) malloc (N * sizeof (double)); if (alpha == 0 || z == 0) { GSL_ERROR("failed to allocate working space", GSL_ENOMEM); } else { size_t i, j; /* Bidiagonalization (eliminating belowdiag) & rhs update diag' = alpha rhs' = z */ alpha[0] = diag[0]; z[0] = rhs[0]; if (alpha[0] == 0) { status = GSL_EZERODIV; } for (i = 1; i < N; i++) { const double t = belowdiag[b_stride*(i - 1)]/alpha[i-1]; alpha[i] = diag[d_stride*i] - t*abovediag[a_stride*(i - 1)]; z[i] = rhs[r_stride*i] - t*z[i-1]; if (alpha[i] == 0) { status = GSL_EZERODIV; } } /* backsubstitution */ x[x_stride * (N - 1)] = z[N - 1]/alpha[N - 1]; if (N >= 2) { for (i = N - 2, j = 0; j <= N - 2; j++, i--) { x[x_stride * i] = (z[i] - abovediag[a_stride*i] * x[x_stride * (i + 1)])/alpha[i]; } } } if (z != 0) free (z); if (alpha != 0) free (alpha); if (status == GSL_EZERODIV) { GSL_ERROR ("matrix must be positive definite", status); } return status; } /* for description of method see [Engeln-Mullges + Uhlig, p. 96] * * diag[0] offdiag[0] 0 ..... offdiag[N-1] * offdiag[0] diag[1] offdiag[1] ..... * 0 offdiag[1] diag[2] * 0 0 offdiag[2] ..... * ... ... * offdiag[N-1] ... * */ static int solve_cyc_tridiag( const double diag[], size_t d_stride, const double offdiag[], size_t o_stride, const double b[], size_t b_stride, double x[], size_t x_stride, size_t N) { int status = GSL_SUCCESS; double * delta = (double *) malloc (N * sizeof (double)); double * gamma = (double *) malloc (N * sizeof (double)); double * alpha = (double *) malloc (N * sizeof (double)); double * c = (double *) malloc (N * sizeof (double)); double * z = (double *) malloc (N * sizeof (double)); if (delta == 0 || gamma == 0 || alpha == 0 || c == 0 || z == 0) { GSL_ERROR("failed to allocate working space", GSL_ENOMEM); } else { size_t i, j; double sum = 0.0; /* factor */ if (N == 1) { x[0] = b[0] / diag[0]; return GSL_SUCCESS; } alpha[0] = diag[0]; gamma[0] = offdiag[0] / alpha[0]; delta[0] = offdiag[o_stride * (N-1)] / alpha[0]; if (alpha[0] == 0) { status = GSL_EZERODIV; } for (i = 1; i < N - 2; i++) { alpha[i] = diag[d_stride * i] - offdiag[o_stride * (i-1)] * gamma[i - 1]; gamma[i] = offdiag[o_stride * i] / alpha[i]; delta[i] = -delta[i - 1] * offdiag[o_stride * (i-1)] / alpha[i]; if (alpha[i] == 0) { status = GSL_EZERODIV; } } for (i = 0; i < N - 2; i++) { sum += alpha[i] * delta[i] * delta[i]; } alpha[N - 2] = diag[d_stride * (N - 2)] - offdiag[o_stride * (N - 3)] * gamma[N - 3]; gamma[N - 2] = (offdiag[o_stride * (N - 2)] - offdiag[o_stride * (N - 3)] * delta[N - 3]) / alpha[N - 2]; alpha[N - 1] = diag[d_stride * (N - 1)] - sum - alpha[(N - 2)] * gamma[N - 2] * gamma[N - 2]; /* update */ z[0] = b[0]; for (i = 1; i < N - 1; i++) { z[i] = b[b_stride * i] - z[i - 1] * gamma[i - 1]; } sum = 0.0; for (i = 0; i < N - 2; i++) { sum += delta[i] * z[i]; } z[N - 1] = b[b_stride * (N - 1)] - sum - gamma[N - 2] * z[N - 2]; for (i = 0; i < N; i++) { c[i] = z[i] / alpha[i]; } /* backsubstitution */ x[x_stride * (N - 1)] = c[N - 1]; x[x_stride * (N - 2)] = c[N - 2] - gamma[N - 2] * x[x_stride * (N - 1)]; if (N >= 3) { for (i = N - 3, j = 0; j <= N - 3; j++, i--) { x[x_stride * i] = c[i] - gamma[i] * x[x_stride * (i + 1)] - delta[i] * x[x_stride * (N - 1)]; } } } if (z != 0) free (z); if (c != 0) free (c); if (alpha != 0) free (alpha); if (gamma != 0) free (gamma); if (delta != 0) free (delta); if (status == GSL_EZERODIV) { GSL_ERROR ("matrix must be positive definite", status); } return status; } /* solve following system w/o the corner elements and then use * Sherman-Morrison formula to compensate for them * * diag[0] abovediag[0] 0 ..... belowdiag[N-1] * belowdiag[0] diag[1] abovediag[1] ..... * 0 belowdiag[1] diag[2] * 0 0 belowdiag[2] ..... * ... ... * abovediag[N-1] ... */ static int solve_cyc_tridiag_nonsym( const double diag[], size_t d_stride, const double abovediag[], size_t a_stride, const double belowdiag[], size_t b_stride, const double rhs[], size_t r_stride, double x[], size_t x_stride, size_t N) { int status = GSL_SUCCESS; double *alpha = (double *) malloc (N * sizeof (double)); double *zb = (double *) malloc (N * sizeof (double)); double *zu = (double *) malloc (N * sizeof (double)); double *w = (double *) malloc (N * sizeof (double)); if (alpha == 0 || zb == 0 || zu == 0 || w == 0) { GSL_ERROR("failed to allocate working space", GSL_ENOMEM); } else { double beta; /* Bidiagonalization (eliminating belowdiag) & rhs update diag' = alpha rhs' = zb rhs' for Aq=u is zu */ zb[0] = rhs[0]; if (diag[0] != 0) beta = -diag[0]; else beta = 1; { const double q = 1 - abovediag[0]*belowdiag[0]/(diag[0]*diag[d_stride]); if (fabs(q/beta) > 0.5 && fabs(q/beta) < 2) { beta *= (fabs(q/beta) < 1) ? 0.5 : 2; } } zu[0] = beta; alpha[0] = diag[0] - beta; if (alpha[0] == 0) { status = GSL_EZERODIV; } { size_t i; for (i = 1; i+1 < N; i++) { const double t = belowdiag[b_stride*(i - 1)]/alpha[i-1]; alpha[i] = diag[d_stride*i] - t*abovediag[a_stride*(i - 1)]; zb[i] = rhs[r_stride*i] - t*zb[i-1]; zu[i] = -t*zu[i-1]; /* FIXME!!! */ if (alpha[i] == 0) { status = GSL_EZERODIV; } } } { const size_t i = N-1; const double t = belowdiag[b_stride*(i - 1)]/alpha[i-1]; alpha[i] = diag[d_stride*i] - abovediag[a_stride*i]*belowdiag[b_stride*i]/beta - t*abovediag[a_stride*(i - 1)]; zb[i] = rhs[r_stride*i] - t*zb[i-1]; zu[i] = abovediag[a_stride*i] - t*zu[i-1]; /* FIXME!!! */ if (alpha[i] == 0) { status = GSL_EZERODIV; } } /* backsubstitution */ { size_t i, j; w[N-1] = zu[N-1]/alpha[N-1]; x[N-1] = zb[N-1]/alpha[N-1]; for (i = N - 2, j = 0; j <= N - 2; j++, i--) { w[i] = (zu[i] - abovediag[a_stride*i] * w[i+1])/alpha[i]; x[i*x_stride] = (zb[i] - abovediag[a_stride*i] * x[x_stride*(i + 1)])/alpha[i]; } } /* Sherman-Morrison */ { const double vw = w[0] + belowdiag[b_stride*(N - 1)]/beta * w[N-1]; const double vx = x[0] + belowdiag[b_stride*(N - 1)]/beta * x[x_stride*(N - 1)]; /* FIXME!!! */ if (vw + 1 == 0) { status = GSL_EZERODIV; } { size_t i; for (i = 0; i < N; i++) x[i] -= vx/(1 + vw)*w[i]; } } } if (zb != 0) free (zb); if (zu != 0) free (zu); if (w != 0) free (w); if (alpha != 0) free (alpha); if (status == GSL_EZERODIV) { GSL_ERROR ("matrix must be positive definite", status); } return status; } int gsl_linalg_solve_symm_tridiag( const gsl_vector * diag, const gsl_vector * offdiag, const gsl_vector * rhs, gsl_vector * solution) { if(diag->size != rhs->size) { GSL_ERROR ("size of diag must match rhs", GSL_EBADLEN); } else if (offdiag->size != rhs->size-1) { GSL_ERROR ("size of offdiag must match rhs-1", GSL_EBADLEN); } else if (solution->size != rhs->size) { GSL_ERROR ("size of solution must match rhs", GSL_EBADLEN); } else { return solve_tridiag(diag->data, diag->stride, offdiag->data, offdiag->stride, rhs->data, rhs->stride, solution->data, solution->stride, diag->size); } } int gsl_linalg_solve_tridiag( const gsl_vector * diag, const gsl_vector * abovediag, const gsl_vector * belowdiag, const gsl_vector * rhs, gsl_vector * solution) { if(diag->size != rhs->size) { GSL_ERROR ("size of diag must match rhs", GSL_EBADLEN); } else if (abovediag->size != rhs->size-1) { GSL_ERROR ("size of abovediag must match rhs-1", GSL_EBADLEN); } else if (belowdiag->size != rhs->size-1) { GSL_ERROR ("size of belowdiag must match rhs-1", GSL_EBADLEN); } else if (solution->size != rhs->size) { GSL_ERROR ("size of solution must match rhs", GSL_EBADLEN); } else { return solve_tridiag_nonsym(diag->data, diag->stride, abovediag->data, abovediag->stride, belowdiag->data, belowdiag->stride, rhs->data, rhs->stride, solution->data, solution->stride, diag->size); } } int gsl_linalg_solve_symm_cyc_tridiag( const gsl_vector * diag, const gsl_vector * offdiag, const gsl_vector * rhs, gsl_vector * solution) { if(diag->size != rhs->size) { GSL_ERROR ("size of diag must match rhs", GSL_EBADLEN); } else if (offdiag->size != rhs->size) { GSL_ERROR ("size of offdiag must match rhs", GSL_EBADLEN); } else if (solution->size != rhs->size) { GSL_ERROR ("size of solution must match rhs", GSL_EBADLEN); } else if (diag->size < 3) { GSL_ERROR ("size of cyclic system must be 3 or more", GSL_EBADLEN); } else { return solve_cyc_tridiag(diag->data, diag->stride, offdiag->data, offdiag->stride, rhs->data, rhs->stride, solution->data, solution->stride, diag->size); } } int gsl_linalg_solve_cyc_tridiag( const gsl_vector * diag, const gsl_vector * abovediag, const gsl_vector * belowdiag, const gsl_vector * rhs, gsl_vector * solution) { if(diag->size != rhs->size) { GSL_ERROR ("size of diag must match rhs", GSL_EBADLEN); } else if (abovediag->size != rhs->size) { GSL_ERROR ("size of abovediag must match rhs", GSL_EBADLEN); } else if (belowdiag->size != rhs->size) { GSL_ERROR ("size of belowdiag must match rhs", GSL_EBADLEN); } else if (solution->size != rhs->size) { GSL_ERROR ("size of solution must match rhs", GSL_EBADLEN); } else if (diag->size < 3) { GSL_ERROR ("size of cyclic system must be 3 or more", GSL_EBADLEN); } else { return solve_cyc_tridiag_nonsym(diag->data, diag->stride, abovediag->data, abovediag->stride, belowdiag->data, belowdiag->stride, rhs->data, rhs->stride, solution->data, solution->stride, diag->size); } } sources_5316/external/gsl/gsl_ode-initval__rk2.c0000664000176700017670000001220011723710247020474 0ustar paulpaul/* ode-initval/rk2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Runge-Kutta 2(3), Euler-Cauchy */ /* Author: G. Jungman */ /* Reference: Abramowitz & Stegun, section 25.5. Runge-Kutta 2nd (25.5.7) and 3rd (25.5.8) order methods */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" typedef struct { double *k1; double *k2; double *k3; double *ytmp; } rk2_state_t; static void * rk2_alloc (size_t dim) { rk2_state_t *state = (rk2_state_t *) malloc (sizeof (rk2_state_t)); if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for rk2_state", GSL_ENOMEM); } state->k1 = (double *) malloc (dim * sizeof (double)); if (state->k1 == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for k1", GSL_ENOMEM); } state->k2 = (double *) malloc (dim * sizeof (double)); if (state->k2 == 0) { free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k2", GSL_ENOMEM); } state->k3 = (double *) malloc (dim * sizeof (double)); if (state->k3 == 0) { free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k2", GSL_ENOMEM); } state->ytmp = (double *) malloc (dim * sizeof (double)); if (state->ytmp == 0) { free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k2", GSL_ENOMEM); } return state; } static int rk2_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { rk2_state_t *state = (rk2_state_t *) vstate; size_t i; double *const k1 = state->k1; double *const k2 = state->k2; double *const k3 = state->k3; double *const ytmp = state->ytmp; /* k1 step */ /* k1 = f(t,y) */ if (dydt_in != NULL) { DBL_MEMCPY (k1, dydt_in, dim); } else { int s = GSL_ODEIV_FN_EVAL (sys, t, y, k1); if (s != GSL_SUCCESS) { return s; } } /* k2 step */ /* k2 = f(t + 0.5*h, y + 0.5*k1) */ for (i = 0; i < dim; i++) { ytmp[i] = y[i] + 0.5 * h * k1[i]; } { int s = GSL_ODEIV_FN_EVAL (sys, t + 0.5 * h, ytmp, k2); if (s != GSL_SUCCESS) { return s; } } /* k3 step */ /* for 3rd order estimates, is used for error estimation k3 = f(t + h, y - k1 + 2*k2) */ for (i = 0; i < dim; i++) { ytmp[i] = y[i] + h * (-k1[i] + 2.0 * k2[i]); } { int s = GSL_ODEIV_FN_EVAL (sys, t + h, ytmp, k3); if (s != GSL_SUCCESS) { return s; } } /* final sum */ for (i = 0; i < dim; i++) { /* Save original values if derivative evaluation below fails */ ytmp[i] = y[i]; { const double ksum3 = (k1[i] + 4.0 * k2[i] + k3[i]) / 6.0; y[i] += h * ksum3; } } /* Derivatives at output */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore original values */ DBL_MEMCPY (y, ytmp, dim); return s; } } /* Error estimation */ for (i = 0; i < dim; i++) { const double ksum3 = (k1[i] + 4.0 * k2[i] + k3[i]) / 6.0; yerr[i] = h * (k2[i] - ksum3); } return GSL_SUCCESS; } static int rk2_reset (void *vstate, size_t dim) { rk2_state_t *state = (rk2_state_t *) vstate; DBL_ZERO_MEMSET (state->k1, dim); DBL_ZERO_MEMSET (state->k2, dim); DBL_ZERO_MEMSET (state->k3, dim); DBL_ZERO_MEMSET (state->ytmp, dim); return GSL_SUCCESS; } static unsigned int rk2_order (void *vstate) { rk2_state_t *state = (rk2_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 2; } static void rk2_free (void *vstate) { rk2_state_t *state = (rk2_state_t *) vstate; free (state->k1); free (state->k2); free (state->k3); free (state->ytmp); free (state); } static const gsl_odeiv_step_type rk2_type = { "rk2", /* name */ 1, /* can use dydt_in */ 1, /* gives exact dydt_out */ &rk2_alloc, &rk2_apply, &rk2_reset, &rk2_order, &rk2_free }; const gsl_odeiv_step_type *gsl_odeiv_step_rk2 = &rk2_type; sources_5316/external/gsl/gsl_sort_vector_double.h0000664000176700017670000000332311705263724021265 0ustar paulpaul/* sort/gsl_sort_vector_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_DOUBLE_H__ #define __GSL_SORT_VECTOR_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector (gsl_vector * v); int gsl_sort_vector_index (gsl_permutation * p, const gsl_vector * v); int gsl_sort_vector_smallest (double * dest, const size_t k, const gsl_vector * v); int gsl_sort_vector_largest (double * dest, const size_t k, const gsl_vector * v); int gsl_sort_vector_smallest_index (size_t * p, const size_t k, const gsl_vector * v); int gsl_sort_vector_largest_index (size_t * p, const size_t k, const gsl_vector * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_DOUBLE_H__ */ sources_5316/external/gsl/gsl_statistics_short.h0000664000176700017670000001047411705263724021000 0ustar paulpaul/* statistics/gsl_statistics_short.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_SHORT_H__ #define __GSL_STATISTICS_SHORT_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_short_mean (const short data[], const size_t stride, const size_t n); double gsl_stats_short_variance (const short data[], const size_t stride, const size_t n); double gsl_stats_short_sd (const short data[], const size_t stride, const size_t n); double gsl_stats_short_variance_with_fixed_mean (const short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_short_sd_with_fixed_mean (const short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_short_absdev (const short data[], const size_t stride, const size_t n); double gsl_stats_short_skew (const short data[], const size_t stride, const size_t n); double gsl_stats_short_kurtosis (const short data[], const size_t stride, const size_t n); double gsl_stats_short_lag1_autocorrelation (const short data[], const size_t stride, const size_t n); double gsl_stats_short_covariance (const short data1[], const size_t stride1,const short data2[], const size_t stride2, const size_t n); double gsl_stats_short_correlation (const short data1[], const size_t stride1,const short data2[], const size_t stride2, const size_t n); double gsl_stats_short_variance_m (const short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_short_sd_m (const short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_short_absdev_m (const short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_short_skew_m_sd (const short data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_short_kurtosis_m_sd (const short data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_short_lag1_autocorrelation_m (const short data[], const size_t stride, const size_t n, const double mean); double gsl_stats_short_covariance_m (const short data1[], const size_t stride1,const short data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); double gsl_stats_short_pvariance (const short data1[], const size_t stride1, const size_t n1, const short data2[], const size_t stride2, const size_t n2); double gsl_stats_short_ttest (const short data1[], const size_t stride1, const size_t n1, const short data2[], const size_t stride2, const size_t n2); short gsl_stats_short_max (const short data[], const size_t stride, const size_t n); short gsl_stats_short_min (const short data[], const size_t stride, const size_t n); void gsl_stats_short_minmax (short * min, short * max, const short data[], const size_t stride, const size_t n); size_t gsl_stats_short_max_index (const short data[], const size_t stride, const size_t n); size_t gsl_stats_short_min_index (const short data[], const size_t stride, const size_t n); void gsl_stats_short_minmax_index (size_t * min_index, size_t * max_index, const short data[], const size_t stride, const size_t n); double gsl_stats_short_median_from_sorted_data (const short sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_short_quantile_from_sorted_data (const short sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_SHORT_H__ */ sources_5316/external/gsl/gsl_randist__beta.c0000664000176700017670000000351011723710247020146 0ustar paulpaul/* randist/beta.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_randist.h" #include "gsl_sf_gamma.h" /* The beta distribution has the form p(x) dx = (Gamma(a + b)/(Gamma(a) Gamma(b))) x^(a-1) (1-x)^(b-1) dx The method used here is the one described in Knuth */ double gsl_ran_beta (const gsl_rng * r, const double a, const double b) { double x1 = gsl_ran_gamma (r, a, 1.0); double x2 = gsl_ran_gamma (r, b, 1.0); return x1 / (x1 + x2); } double gsl_ran_beta_pdf (const double x, const double a, const double b) { if (x < 0 || x > 1) { return 0 ; } else { double p; double gab = gsl_sf_lngamma (a + b); double ga = gsl_sf_lngamma (a); double gb = gsl_sf_lngamma (b); if (x == 0.0 || x == 1.0) { p = exp (gab - ga - gb) * pow (x, a - 1) * pow (1 - x, b - 1); } else { p = exp (gab - ga - gb + log(x) * (a - 1) + log1p(-x) * (b - 1)); } return p; } } sources_5316/external/gsl/gsl_cblas.h0000664000176700017670000010161511705263724016451 0ustar paulpaul/* blas/gsl_cblas.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* This is a copy of the CBLAS standard header. * We carry this around so we do not have to * break our model for flexible BLAS functionality. */ #ifndef __GSL_CBLAS_H__ #define __GSL_CBLAS_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus #define __BEGIN_DECLS extern "C" { #define __END_DECLS } #else #define __BEGIN_DECLS /* empty */ #define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* * Enumerated and derived types */ #define CBLAS_INDEX size_t /* this may vary between platforms */ enum CBLAS_ORDER {CblasRowMajor=101, CblasColMajor=102}; enum CBLAS_TRANSPOSE {CblasNoTrans=111, CblasTrans=112, CblasConjTrans=113}; enum CBLAS_UPLO {CblasUpper=121, CblasLower=122}; enum CBLAS_DIAG {CblasNonUnit=131, CblasUnit=132}; enum CBLAS_SIDE {CblasLeft=141, CblasRight=142}; /* * =========================================================================== * Prototypes for level 1 BLAS functions (complex are recast as routines) * =========================================================================== */ float cblas_sdsdot(const int N, const float alpha, const float *X, const int incX, const float *Y, const int incY); double cblas_dsdot(const int N, const float *X, const int incX, const float *Y, const int incY); float cblas_sdot(const int N, const float *X, const int incX, const float *Y, const int incY); double cblas_ddot(const int N, const double *X, const int incX, const double *Y, const int incY); /* * Functions having prefixes Z and C only */ void cblas_cdotu_sub(const int N, const void *X, const int incX, const void *Y, const int incY, void *dotu); void cblas_cdotc_sub(const int N, const void *X, const int incX, const void *Y, const int incY, void *dotc); void cblas_zdotu_sub(const int N, const void *X, const int incX, const void *Y, const int incY, void *dotu); void cblas_zdotc_sub(const int N, const void *X, const int incX, const void *Y, const int incY, void *dotc); /* * Functions having prefixes S D SC DZ */ float cblas_snrm2(const int N, const float *X, const int incX); float cblas_sasum(const int N, const float *X, const int incX); double cblas_dnrm2(const int N, const double *X, const int incX); double cblas_dasum(const int N, const double *X, const int incX); float cblas_scnrm2(const int N, const void *X, const int incX); float cblas_scasum(const int N, const void *X, const int incX); double cblas_dznrm2(const int N, const void *X, const int incX); double cblas_dzasum(const int N, const void *X, const int incX); /* * Functions having standard 4 prefixes (S D C Z) */ CBLAS_INDEX cblas_isamax(const int N, const float *X, const int incX); CBLAS_INDEX cblas_idamax(const int N, const double *X, const int incX); CBLAS_INDEX cblas_icamax(const int N, const void *X, const int incX); CBLAS_INDEX cblas_izamax(const int N, const void *X, const int incX); /* * =========================================================================== * Prototypes for level 1 BLAS routines * =========================================================================== */ /* * Routines with standard 4 prefixes (s, d, c, z) */ void cblas_sswap(const int N, float *X, const int incX, float *Y, const int incY); void cblas_scopy(const int N, const float *X, const int incX, float *Y, const int incY); void cblas_saxpy(const int N, const float alpha, const float *X, const int incX, float *Y, const int incY); void cblas_dswap(const int N, double *X, const int incX, double *Y, const int incY); void cblas_dcopy(const int N, const double *X, const int incX, double *Y, const int incY); void cblas_daxpy(const int N, const double alpha, const double *X, const int incX, double *Y, const int incY); void cblas_cswap(const int N, void *X, const int incX, void *Y, const int incY); void cblas_ccopy(const int N, const void *X, const int incX, void *Y, const int incY); void cblas_caxpy(const int N, const void *alpha, const void *X, const int incX, void *Y, const int incY); void cblas_zswap(const int N, void *X, const int incX, void *Y, const int incY); void cblas_zcopy(const int N, const void *X, const int incX, void *Y, const int incY); void cblas_zaxpy(const int N, const void *alpha, const void *X, const int incX, void *Y, const int incY); /* * Routines with S and D prefix only */ void cblas_srotg(float *a, float *b, float *c, float *s); void cblas_srotmg(float *d1, float *d2, float *b1, const float b2, float *P); void cblas_srot(const int N, float *X, const int incX, float *Y, const int incY, const float c, const float s); void cblas_srotm(const int N, float *X, const int incX, float *Y, const int incY, const float *P); void cblas_drotg(double *a, double *b, double *c, double *s); void cblas_drotmg(double *d1, double *d2, double *b1, const double b2, double *P); void cblas_drot(const int N, double *X, const int incX, double *Y, const int incY, const double c, const double s); void cblas_drotm(const int N, double *X, const int incX, double *Y, const int incY, const double *P); /* * Routines with S D C Z CS and ZD prefixes */ void cblas_sscal(const int N, const float alpha, float *X, const int incX); void cblas_dscal(const int N, const double alpha, double *X, const int incX); void cblas_cscal(const int N, const void *alpha, void *X, const int incX); void cblas_zscal(const int N, const void *alpha, void *X, const int incX); void cblas_csscal(const int N, const float alpha, void *X, const int incX); void cblas_zdscal(const int N, const double alpha, void *X, const int incX); /* * =========================================================================== * Prototypes for level 2 BLAS * =========================================================================== */ /* * Routines with standard 4 prefixes (S, D, C, Z) */ void cblas_sgemv(const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const float alpha, const float *A, const int lda, const float *X, const int incX, const float beta, float *Y, const int incY); void cblas_sgbmv(const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const int KL, const int KU, const float alpha, const float *A, const int lda, const float *X, const int incX, const float beta, float *Y, const int incY); void cblas_strmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const float *A, const int lda, float *X, const int incX); void cblas_stbmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const float *A, const int lda, float *X, const int incX); void cblas_stpmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const float *Ap, float *X, const int incX); void cblas_strsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const float *A, const int lda, float *X, const int incX); void cblas_stbsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const float *A, const int lda, float *X, const int incX); void cblas_stpsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const float *Ap, float *X, const int incX); void cblas_dgemv(const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const double alpha, const double *A, const int lda, const double *X, const int incX, const double beta, double *Y, const int incY); void cblas_dgbmv(const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const int KL, const int KU, const double alpha, const double *A, const int lda, const double *X, const int incX, const double beta, double *Y, const int incY); void cblas_dtrmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const double *A, const int lda, double *X, const int incX); void cblas_dtbmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const double *A, const int lda, double *X, const int incX); void cblas_dtpmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const double *Ap, double *X, const int incX); void cblas_dtrsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const double *A, const int lda, double *X, const int incX); void cblas_dtbsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const double *A, const int lda, double *X, const int incX); void cblas_dtpsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const double *Ap, double *X, const int incX); void cblas_cgemv(const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_cgbmv(const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const int KL, const int KU, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_ctrmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *A, const int lda, void *X, const int incX); void cblas_ctbmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const void *A, const int lda, void *X, const int incX); void cblas_ctpmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *Ap, void *X, const int incX); void cblas_ctrsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *A, const int lda, void *X, const int incX); void cblas_ctbsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const void *A, const int lda, void *X, const int incX); void cblas_ctpsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *Ap, void *X, const int incX); void cblas_zgemv(const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_zgbmv(const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const int KL, const int KU, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_ztrmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *A, const int lda, void *X, const int incX); void cblas_ztbmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const void *A, const int lda, void *X, const int incX); void cblas_ztpmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *Ap, void *X, const int incX); void cblas_ztrsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *A, const int lda, void *X, const int incX); void cblas_ztbsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const void *A, const int lda, void *X, const int incX); void cblas_ztpsv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *Ap, void *X, const int incX); /* * Routines with S and D prefixes only */ void cblas_ssymv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *A, const int lda, const float *X, const int incX, const float beta, float *Y, const int incY); void cblas_ssbmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const int K, const float alpha, const float *A, const int lda, const float *X, const int incX, const float beta, float *Y, const int incY); void cblas_sspmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *Ap, const float *X, const int incX, const float beta, float *Y, const int incY); void cblas_sger(const enum CBLAS_ORDER order, const int M, const int N, const float alpha, const float *X, const int incX, const float *Y, const int incY, float *A, const int lda); void cblas_ssyr(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *X, const int incX, float *A, const int lda); void cblas_sspr(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *X, const int incX, float *Ap); void cblas_ssyr2(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *X, const int incX, const float *Y, const int incY, float *A, const int lda); void cblas_sspr2(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *X, const int incX, const float *Y, const int incY, float *A); void cblas_dsymv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *A, const int lda, const double *X, const int incX, const double beta, double *Y, const int incY); void cblas_dsbmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const int K, const double alpha, const double *A, const int lda, const double *X, const int incX, const double beta, double *Y, const int incY); void cblas_dspmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *Ap, const double *X, const int incX, const double beta, double *Y, const int incY); void cblas_dger(const enum CBLAS_ORDER order, const int M, const int N, const double alpha, const double *X, const int incX, const double *Y, const int incY, double *A, const int lda); void cblas_dsyr(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *X, const int incX, double *A, const int lda); void cblas_dspr(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *X, const int incX, double *Ap); void cblas_dsyr2(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *X, const int incX, const double *Y, const int incY, double *A, const int lda); void cblas_dspr2(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *X, const int incX, const double *Y, const int incY, double *A); /* * Routines with C and Z prefixes only */ void cblas_chemv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_chbmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const int K, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_chpmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *Ap, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_cgeru(const enum CBLAS_ORDER order, const int M, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda); void cblas_cgerc(const enum CBLAS_ORDER order, const int M, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda); void cblas_cher(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const void *X, const int incX, void *A, const int lda); void cblas_chpr(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const void *X, const int incX, void *A); void cblas_cher2(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda); void cblas_chpr2(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *Ap); void cblas_zhemv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_zhbmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const int K, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_zhpmv(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *Ap, const void *X, const int incX, const void *beta, void *Y, const int incY); void cblas_zgeru(const enum CBLAS_ORDER order, const int M, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda); void cblas_zgerc(const enum CBLAS_ORDER order, const int M, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda); void cblas_zher(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const void *X, const int incX, void *A, const int lda); void cblas_zhpr(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const void *X, const int incX, void *A); void cblas_zher2(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda); void cblas_zhpr2(const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *Ap); /* * =========================================================================== * Prototypes for level 3 BLAS * =========================================================================== */ /* * Routines with standard 4 prefixes (S, D, C, Z) */ void cblas_sgemm(const enum CBLAS_ORDER Order, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_TRANSPOSE TransB, const int M, const int N, const int K, const float alpha, const float *A, const int lda, const float *B, const int ldb, const float beta, float *C, const int ldc); void cblas_ssymm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const float alpha, const float *A, const int lda, const float *B, const int ldb, const float beta, float *C, const int ldc); void cblas_ssyrk(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const float alpha, const float *A, const int lda, const float beta, float *C, const int ldc); void cblas_ssyr2k(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const float alpha, const float *A, const int lda, const float *B, const int ldb, const float beta, float *C, const int ldc); void cblas_strmm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const float alpha, const float *A, const int lda, float *B, const int ldb); void cblas_strsm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const float alpha, const float *A, const int lda, float *B, const int ldb); void cblas_dgemm(const enum CBLAS_ORDER Order, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_TRANSPOSE TransB, const int M, const int N, const int K, const double alpha, const double *A, const int lda, const double *B, const int ldb, const double beta, double *C, const int ldc); void cblas_dsymm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const double alpha, const double *A, const int lda, const double *B, const int ldb, const double beta, double *C, const int ldc); void cblas_dsyrk(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const double alpha, const double *A, const int lda, const double beta, double *C, const int ldc); void cblas_dsyr2k(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const double alpha, const double *A, const int lda, const double *B, const int ldb, const double beta, double *C, const int ldc); void cblas_dtrmm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const double alpha, const double *A, const int lda, double *B, const int ldb); void cblas_dtrsm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const double alpha, const double *A, const int lda, double *B, const int ldb); void cblas_cgemm(const enum CBLAS_ORDER Order, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_TRANSPOSE TransB, const int M, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc); void cblas_csymm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc); void cblas_csyrk(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *beta, void *C, const int ldc); void cblas_csyr2k(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc); void cblas_ctrmm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const void *alpha, const void *A, const int lda, void *B, const int ldb); void cblas_ctrsm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const void *alpha, const void *A, const int lda, void *B, const int ldb); void cblas_zgemm(const enum CBLAS_ORDER Order, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_TRANSPOSE TransB, const int M, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc); void cblas_zsymm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc); void cblas_zsyrk(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *beta, void *C, const int ldc); void cblas_zsyr2k(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc); void cblas_ztrmm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const void *alpha, const void *A, const int lda, void *B, const int ldb); void cblas_ztrsm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const void *alpha, const void *A, const int lda, void *B, const int ldb); /* * Routines with prefixes C and Z only */ void cblas_chemm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc); void cblas_cherk(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const float alpha, const void *A, const int lda, const float beta, void *C, const int ldc); void cblas_cher2k(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const float beta, void *C, const int ldc); void cblas_zhemm(const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc); void cblas_zherk(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const double alpha, const void *A, const int lda, const double beta, void *C, const int ldc); void cblas_zher2k(const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const double beta, void *C, const int ldc); void cblas_xerbla(int p, const char *rout, const char *form, ...); __END_DECLS #endif /* __GSL_CBLAS_H__ */ sources_5316/external/gsl/gsl_rng__borosh13.c0000664000176700017670000000423211723710247020017 0ustar paulpaul/* rng/borosh13.c * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth * The Art of Computer Programming * Volume 2 * Third Edition * Addison-Wesley * Page 106-108 * * It is called "Borosh - Niederreiter" * * This implementation copyright (C) 2001 Carlo Perassi and * (C) 2003 Heiko Bauke. */ #include "gsl__config.h" #include #include "gsl_rng.h" #define AA 1812433253UL #define MM 0xffffffffUL /* 2 ^ 32 - 1 */ static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); typedef struct { unsigned long int x; } ran_state_t; static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; state->x = (AA * state->x) & MM; return state->x; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 4294967296.0; } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; if (s == 0) s = 1; /* default seed is 1 */ state->x = s & MM; return; } static const gsl_rng_type ran_type = { "borosh13", /* name */ MM, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_borosh13 = &ran_type; sources_5316/external/gsl/gsl_sort__sortind.c0000664000176700017670000000472611723710247020252 0ustar paulpaul/* * Implement Heap sort -- direct and indirect sorting * Based on descriptions in Sedgewick "Algorithms in C" * Copyright (C) 1999 Thomas Walter * * 18 February 2000: Modified for GSL by Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ #include "gsl__config.h" #include #include "gsl_heapsort.h" static inline void downheap (size_t * p, const void *data, const size_t size, const size_t N, size_t k, gsl_comparison_fn_t compare); #define CMP(data,size,j,k) (compare((const char *)(data) + (size) * (j), (const char *)(data) + (size) * (k))) static inline void downheap (size_t * p, const void *data, const size_t size, const size_t N, size_t k, gsl_comparison_fn_t compare) { const size_t pki = p[k]; while (k <= N / 2) { size_t j = 2 * k; if (j < N && CMP (data, size, p[j], p[j + 1]) < 0) { j++; } if (CMP (data, size, pki, p[j]) >= 0) { break; } p[k] = p[j]; k = j; } p[k] = pki; } int gsl_heapsort_index (size_t * p, const void *data, size_t count, size_t size, gsl_comparison_fn_t compare) { /* Sort the array in ascending order. This is a true inplace algorithm with N log N operations. Worst case (an already sorted array) is something like 20% slower */ size_t i, k, N; if (count == 0) { return GSL_SUCCESS; /* No data to sort */ } for (i = 0; i < count; i++) { p[i] = i ; /* set permutation to identity */ } /* We have n_data elements, last element is at 'n_data-1', first at '0' Set N to the last element number. */ N = count - 1; k = N / 2; k++; /* Compensate the first use of 'k--' */ do { k--; downheap (p, data, size, N, k, compare); } while (k > 0); while (N > 0) { /* first swap the elements */ size_t tmp = p[0]; p[0] = p[N]; p[N] = tmp; /* then process the heap */ N--; downheap (p, data, size, N, 0, compare); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_sf_lambert.h0000664000176700017670000000342111705263724017477 0ustar paulpaul/* specfunc/gsl_sf_lambert.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_LAMBERT_H__ #define __GSL_SF_LAMBERT_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Lambert's Function W_0(x) * * W_0(x) is the principal branch of the * implicit function defined by W e^W = x. * * -1/E < x < \infty * * exceptions: GSL_EMAXITER; */ int gsl_sf_lambert_W0_e(double x, gsl_sf_result * result); double gsl_sf_lambert_W0(double x); /* Lambert's Function W_{-1}(x) * * W_{-1}(x) is the second real branch of the * implicit function defined by W e^W = x. * It agrees with W_0(x) when x >= 0. * * -1/E < x < \infty * * exceptions: GSL_MAXITER; */ int gsl_sf_lambert_Wm1_e(double x, gsl_sf_result * result); double gsl_sf_lambert_Wm1(double x); __END_DECLS #endif /* __GSL_SF_LAMBERT_H__ */ sources_5316/external/gsl/gsl_integration__qc25f.c0000664000176700017670000001035111723710247021033 0ustar paulpaul/* integration/qc25f.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ struct fn_fourier_params { gsl_function *function; double omega; }; static double fn_sin (double t, void *params); static double fn_cos (double t, void *params); static void qc25f (gsl_function * f, double a, double b, gsl_integration_qawo_table * wf, size_t level, double *result, double *abserr, double *resabs, double *resasc); static void qc25f (gsl_function * f, double a, double b, gsl_integration_qawo_table * wf, size_t level, double *result, double *abserr, double *resabs, double *resasc) { const double center = 0.5 * (a + b); const double half_length = 0.5 * (b - a); const double omega = wf->omega ; const double par = omega * half_length; if (fabs (par) < 2) { gsl_function weighted_function; struct fn_fourier_params fn_params; fn_params.function = f; fn_params.omega = omega; if (wf->sine == GSL_INTEG_SINE) { weighted_function.function = &fn_sin; } else { weighted_function.function = &fn_cos; } weighted_function.params = &fn_params; gsl_integration_qk15 (&weighted_function, a, b, result, abserr, resabs, resasc); return; } else { double *moment; double cheb12[13], cheb24[25]; double result_abs, res12_cos, res12_sin, res24_cos, res24_sin; double est_cos, est_sin; double c, s; size_t i; gsl_integration_qcheb (f, a, b, cheb12, cheb24); if (level >= wf->n) { /* table overflow should not happen, check before calling */ GSL_ERROR_VOID("table overflow in internal function", GSL_ESANITY); } /* obtain moments from the table */ moment = wf->chebmo + 25 * level; res12_cos = cheb12[12] * moment[12]; res12_sin = 0 ; for (i = 0; i < 6; i++) { size_t k = 10 - 2 * i; res12_cos += cheb12[k] * moment[k]; res12_sin += cheb12[k + 1] * moment[k + 1]; } res24_cos = cheb24[24] * moment[24]; res24_sin = 0 ; result_abs = fabs(cheb24[24]) ; for (i = 0; i < 12; i++) { size_t k = 22 - 2 * i; res24_cos += cheb24[k] * moment[k]; res24_sin += cheb24[k + 1] * moment[k + 1]; result_abs += fabs(cheb24[k]) + fabs(cheb24[k+1]); } est_cos = fabs(res24_cos - res12_cos); est_sin = fabs(res24_sin - res12_sin); c = half_length * cos(center * omega); s = half_length * sin(center * omega); if (wf->sine == GSL_INTEG_SINE) { *result = c * res24_sin + s * res24_cos; *abserr = fabs(c * est_sin) + fabs(s * est_cos); } else { *result = c * res24_cos - s * res24_sin; *abserr = fabs(c * est_cos) + fabs(s * est_sin); } *resabs = result_abs * half_length; *resasc = GSL_DBL_MAX; return; } } static double fn_sin (double x, void *params) { struct fn_fourier_params *p = (struct fn_fourier_params *) params; gsl_function *f = p->function; double w = p->omega; double wx = w * x; double sinwx = sin(wx) ; return GSL_FN_EVAL (f, x) * sinwx; } static double fn_cos (double x, void *params) { struct fn_fourier_params *p = (struct fn_fourier_params *) params; gsl_function *f = p->function; double w = p->omega; double wx = w * x; double coswx = cos(wx) ; return GSL_FN_EVAL (f, x) * coswx ; } sources_5316/external/gsl/gsl_integration__qcheb.c0000664000176700017670000001341011723710247021174 0ustar paulpaul/* integration/qcheb.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_integration.h" /* This function computes the 12-th order and 24-th order Chebyshev approximations to f(x) on [a,b] */ void gsl_integration_qcheb (gsl_function * f, double a, double b, double *cheb12, double *cheb24) { size_t i; double fval[25], v[12]; /* These are the values of cos(pi*k/24) for k=1..11 needed for the Chebyshev expansion of f(x) */ const double x[11] = { 0.9914448613738104, 0.9659258262890683, 0.9238795325112868, 0.8660254037844386, 0.7933533402912352, 0.7071067811865475, 0.6087614290087206, 0.5000000000000000, 0.3826834323650898, 0.2588190451025208, 0.1305261922200516 }; const double center = 0.5 * (b + a); const double half_length = 0.5 * (b - a); fval[0] = 0.5 * GSL_FN_EVAL (f, b); fval[12] = GSL_FN_EVAL (f, center); fval[24] = 0.5 * GSL_FN_EVAL (f, a); for (i = 1; i < 12; i++) { const size_t j = 24 - i; const double u = half_length * x[i-1]; fval[i] = GSL_FN_EVAL(f, center + u); fval[j] = GSL_FN_EVAL(f, center - u); } for (i = 0; i < 12; i++) { const size_t j = 24 - i; v[i] = fval[i] - fval[j]; fval[i] = fval[i] + fval[j]; } { const double alam1 = v[0] - v[8]; const double alam2 = x[5] * (v[2] - v[6] - v[10]); cheb12[3] = alam1 + alam2; cheb12[9] = alam1 - alam2; } { const double alam1 = v[1] - v[7] - v[9]; const double alam2 = v[3] - v[5] - v[11]; { const double alam = x[2] * alam1 + x[8] * alam2; cheb24[3] = cheb12[3] + alam; cheb24[21] = cheb12[3] - alam; } { const double alam = x[8] * alam1 - x[2] * alam2; cheb24[9] = cheb12[9] + alam; cheb24[15] = cheb12[9] - alam; } } { const double part1 = x[3] * v[4]; const double part2 = x[7] * v[8]; const double part3 = x[5] * v[6]; { const double alam1 = v[0] + part1 + part2; const double alam2 = x[1] * v[2] + part3 + x[9] * v[10]; cheb12[1] = alam1 + alam2; cheb12[11] = alam1 - alam2; } { const double alam1 = v[0] - part1 + part2; const double alam2 = x[9] * v[2] - part3 + x[1] * v[10]; cheb12[5] = alam1 + alam2; cheb12[7] = alam1 - alam2; } } { const double alam = (x[0] * v[1] + x[2] * v[3] + x[4] * v[5] + x[6] * v[7] + x[8] * v[9] + x[10] * v[11]); cheb24[1] = cheb12[1] + alam; cheb24[23] = cheb12[1] - alam; } { const double alam = (x[10] * v[1] - x[8] * v[3] + x[6] * v[5] - x[4] * v[7] + x[2] * v[9] - x[0] * v[11]); cheb24[11] = cheb12[11] + alam; cheb24[13] = cheb12[11] - alam; } { const double alam = (x[4] * v[1] - x[8] * v[3] - x[0] * v[5] - x[10] * v[7] + x[2] * v[9] + x[6] * v[11]); cheb24[5] = cheb12[5] + alam; cheb24[19] = cheb12[5] - alam; } { const double alam = (x[6] * v[1] - x[2] * v[3] - x[10] * v[5] + x[0] * v[7] - x[8] * v[9] - x[4] * v[11]); cheb24[7] = cheb12[7] + alam; cheb24[17] = cheb12[7] - alam; } for (i = 0; i < 6; i++) { const size_t j = 12 - i; v[i] = fval[i] - fval[j]; fval[i] = fval[i] + fval[j]; } { const double alam1 = v[0] + x[7] * v[4]; const double alam2 = x[3] * v[2]; cheb12[2] = alam1 + alam2; cheb12[10] = alam1 - alam2; } cheb12[6] = v[0] - v[4]; { const double alam = x[1] * v[1] + x[5] * v[3] + x[9] * v[5]; cheb24[2] = cheb12[2] + alam; cheb24[22] = cheb12[2] - alam; } { const double alam = x[5] * (v[1] - v[3] - v[5]); cheb24[6] = cheb12[6] + alam; cheb24[18] = cheb12[6] - alam; } { const double alam = x[9] * v[1] - x[5] * v[3] + x[1] * v[5]; cheb24[10] = cheb12[10] + alam; cheb24[14] = cheb12[10] - alam; } for (i = 0; i < 3; i++) { const size_t j = 6 - i; v[i] = fval[i] - fval[j]; fval[i] = fval[i] + fval[j]; } cheb12[4] = v[0] + x[7] * v[2]; cheb12[8] = fval[0] - x[7] * fval[2]; { const double alam = x[3] * v[1]; cheb24[4] = cheb12[4] + alam; cheb24[20] = cheb12[4] - alam; } { const double alam = x[7] * fval[1] - fval[3]; cheb24[8] = cheb12[8] + alam; cheb24[16] = cheb12[8] - alam; } cheb12[0] = fval[0] + fval[2]; { const double alam = fval[1] + fval[3]; cheb24[0] = cheb12[0] + alam; cheb24[24] = cheb12[0] - alam; } cheb12[12] = v[0] - v[2]; cheb24[12] = cheb12[12]; for (i = 1; i < 12; i++) { cheb12[i] *= 1.0 / 6.0; } cheb12[0] *= 1.0 / 12.0; cheb12[12] *= 1.0 / 12.0; for (i = 1; i < 24; i++) { cheb24[i] *= 1.0 / 12.0; } cheb24[0] *= 1.0 / 24.0; cheb24[24] *= 1.0 / 24.0; } sources_5316/external/gsl/gsl_cblas__sasum.c0000664000176700017670000000032511723710247020004 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" float cblas_sasum (const int N, const float *X, const int incX) { #define BASE float #include "gsl_cblas__source_asum_r.h" #undef BASE } sources_5316/external/gsl/gsl_statistics__mean_source.c0000664000176700017670000000230311723710247022260 0ustar paulpaul/* statistics/mean_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION (gsl_stats, mean) (const BASE data[], const size_t stride, const size_t size) { /* Compute the arithmetic mean of a dataset using the recurrence relation mean_(n) = mean(n-1) + (data[n] - mean(n-1))/(n+1) */ long double mean = 0; size_t i; for (i = 0; i < size; i++) { mean += (data[i * stride] - mean) / (i + 1); } return mean; } sources_5316/external/gsl/gsl_rng__randu.c0000664000176700017670000000502311723710247017467 0ustar paulpaul/* rng/randu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is a reincarnation of the infamously bad RANDU generator. The sequence is, x_{n+1} = (a x_n) mod m with a = 65539 and m = 2^31 = 2147483648. The seed specifies the initial value, x_1. The theoretical value of x_{10001} is 1623524161. The period of this generator is 2^29. Note: Knuth describes this generator as "really horrible". From: Park and Miller, "Random Number Generators: Good ones are hard to find" Communications of the ACM, October 1988, Volume 31, No 10, pages 1192-1201. */ static inline unsigned long int randu_get (void *vstate); static double randu_get_double (void *vstate); static void randu_set (void *state, unsigned long int s); static const long int a = 65539; /* static const unsigned long int m = 2147483648UL; */ typedef struct { unsigned long int x; } randu_state_t; static inline unsigned long int randu_get (void *vstate) { randu_state_t *state = (randu_state_t *) vstate; /* The following line relies on unsigned 32-bit arithmetic */ state->x = (a * state->x) & 0x7fffffffUL; return state->x; } static double randu_get_double (void *vstate) { return randu_get (vstate) / 2147483648.0 ; } static void randu_set (void *vstate, unsigned long int s) { randu_state_t *state = (randu_state_t *) vstate; if (s == 0) s = 1; /* default seed is 1 */ state->x = s; return; } static const gsl_rng_type randu_type = {"randu", /* name */ 0x7fffffffUL, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (randu_state_t), &randu_set, &randu_get, &randu_get_double}; const gsl_rng_type *gsl_rng_randu = &randu_type; sources_5316/external/gsl/gsl_sf__hyperg_2F1.c0000644000176700017670000006600410710226217020104 0ustar paulpaul/* specfunc/hyperg_2F1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_gamma.h" #include "gsl_sf_psi.h" #include "gsl_sf_hyperg.h" #include "gsl_sf__error.h" #define locEPS (1000.0*GSL_DBL_EPSILON) /* Assumes c != negative integer. */ static int hyperg_2F1_series(const double a, const double b, const double c, const double x, gsl_sf_result * result ) { double sum_pos = 1.0; double sum_neg = 0.0; double del_pos = 1.0; double del_neg = 0.0; double del = 1.0; double k = 0.0; int i = 0; if(fabs(c) < GSL_DBL_EPSILON) { result->val = 0.0; /* FIXME: ?? */ result->err = 1.0; GSL_ERROR ("error", GSL_EDOM); } do { if(++i > 30000) { result->val = sum_pos - sum_neg; result->err = del_pos + del_neg; result->err += 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += 2.0 * GSL_DBL_EPSILON * (2.0*sqrt(k)+1.0) * fabs(result->val); GSL_ERROR ("error", GSL_EMAXITER); } del *= (a+k)*(b+k) * x / ((c+k) * (k+1.0)); /* Gauss series */ if(del > 0.0) { del_pos = del; sum_pos += del; } else if(del == 0.0) { /* Exact termination (a or b was a negative integer). */ del_pos = 0.0; del_neg = 0.0; break; } else { del_neg = -del; sum_neg -= del; } k += 1.0; } while(fabs((del_pos + del_neg)/(sum_pos-sum_neg)) > GSL_DBL_EPSILON); result->val = sum_pos - sum_neg; result->err = del_pos + del_neg; result->err += 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += 2.0 * GSL_DBL_EPSILON * (2.0*sqrt(k) + 1.0) * fabs(result->val); return GSL_SUCCESS; } /* a = aR + i aI, b = aR - i aI */ static int hyperg_2F1_conj_series(const double aR, const double aI, const double c, double x, gsl_sf_result * result) { if(c == 0.0) { result->val = 0.0; /* FIXME: should be Inf */ result->err = 0.0; GSL_ERROR ("error", GSL_EDOM); } else { double sum_pos = 1.0; double sum_neg = 0.0; double del_pos = 1.0; double del_neg = 0.0; double del = 1.0; double k = 0.0; do { del *= ((aR+k)*(aR+k) + aI*aI)/((k+1.0)*(c+k)) * x; if(del >= 0.0) { del_pos = del; sum_pos += del; } else { del_neg = -del; sum_neg -= del; } if(k > 30000) { result->val = sum_pos - sum_neg; result->err = del_pos + del_neg; result->err += 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += 2.0 * GSL_DBL_EPSILON * (2.0*sqrt(k)+1.0) * fabs(result->val); GSL_ERROR ("error", GSL_EMAXITER); } k += 1.0; } while(fabs((del_pos + del_neg)/(sum_pos - sum_neg)) > GSL_DBL_EPSILON); result->val = sum_pos - sum_neg; result->err = del_pos + del_neg; result->err += 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += 2.0 * GSL_DBL_EPSILON * (2.0*sqrt(k) + 1.0) * fabs(result->val); return GSL_SUCCESS; } } /* Luke's rational approximation. The most accesible * discussion is in [Kolbig, CPC 23, 51 (1981)]. * The convergence is supposedly guaranteed for x < 0. * You have to read Luke's books to see this and other * results. Unfortunately, the stability is not so * clear to me, although it seems very efficient when * it works. */ static int hyperg_2F1_luke(const double a, const double b, const double c, const double xin, gsl_sf_result * result) { int stat_iter; const double RECUR_BIG = 1.0e+50; const int nmax = 20000; int n = 3; const double x = -xin; const double x3 = x*x*x; const double t0 = a*b/c; const double t1 = (a+1.0)*(b+1.0)/(2.0*c); const double t2 = (a+2.0)*(b+2.0)/(2.0*(c+1.0)); double F = 1.0; double prec; double Bnm3 = 1.0; /* B0 */ double Bnm2 = 1.0 + t1 * x; /* B1 */ double Bnm1 = 1.0 + t2 * x * (1.0 + t1/3.0 * x); /* B2 */ double Anm3 = 1.0; /* A0 */ double Anm2 = Bnm2 - t0 * x; /* A1 */ double Anm1 = Bnm1 - t0*(1.0 + t2*x)*x + t0 * t1 * (c/(c+1.0)) * x*x; /* A2 */ while(1) { double npam1 = n + a - 1; double npbm1 = n + b - 1; double npcm1 = n + c - 1; double npam2 = n + a - 2; double npbm2 = n + b - 2; double npcm2 = n + c - 2; double tnm1 = 2*n - 1; double tnm3 = 2*n - 3; double tnm5 = 2*n - 5; double n2 = n*n; double F1 = (3.0*n2 + (a+b-6)*n + 2 - a*b - 2*(a+b)) / (2*tnm3*npcm1); double F2 = -(3.0*n2 - (a+b+6)*n + 2 - a*b)*npam1*npbm1/(4*tnm1*tnm3*npcm2*npcm1); double F3 = (npam2*npam1*npbm2*npbm1*(n-a-2)*(n-b-2)) / (8*tnm3*tnm3*tnm5*(n+c-3)*npcm2*npcm1); double E = -npam1*npbm1*(n-c-1) / (2*tnm3*npcm2*npcm1); double An = (1.0+F1*x)*Anm1 + (E + F2*x)*x*Anm2 + F3*x3*Anm3; double Bn = (1.0+F1*x)*Bnm1 + (E + F2*x)*x*Bnm2 + F3*x3*Bnm3; double r = An/Bn; prec = fabs((F - r)/F); F = r; if(prec < GSL_DBL_EPSILON || n > nmax) break; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; Anm3 /= RECUR_BIG; Bnm3 /= RECUR_BIG; } else if(fabs(An) < 1.0/RECUR_BIG || fabs(Bn) < 1.0/RECUR_BIG) { An *= RECUR_BIG; Bn *= RECUR_BIG; Anm1 *= RECUR_BIG; Bnm1 *= RECUR_BIG; Anm2 *= RECUR_BIG; Bnm2 *= RECUR_BIG; Anm3 *= RECUR_BIG; Bnm3 *= RECUR_BIG; } n++; Bnm3 = Bnm2; Bnm2 = Bnm1; Bnm1 = Bn; Anm3 = Anm2; Anm2 = Anm1; Anm1 = An; } result->val = F; result->err = 2.0 * fabs(prec * F); result->err += 2.0 * GSL_DBL_EPSILON * (n+1.0) * fabs(F); /* FIXME: just a hack: there's a lot of shit going on here */ result->err *= 8.0 * (fabs(a) + fabs(b) + 1.0); stat_iter = (n >= nmax ? GSL_EMAXITER : GSL_SUCCESS ); return stat_iter; } /* Luke's rational approximation for the * case a = aR + i aI, b = aR - i aI. */ static int hyperg_2F1_conj_luke(const double aR, const double aI, const double c, const double xin, gsl_sf_result * result) { int stat_iter; const double RECUR_BIG = 1.0e+50; const int nmax = 10000; int n = 3; const double x = -xin; const double x3 = x*x*x; const double atimesb = aR*aR + aI*aI; const double apb = 2.0*aR; const double t0 = atimesb/c; const double t1 = (atimesb + apb + 1.0)/(2.0*c); const double t2 = (atimesb + 2.0*apb + 4.0)/(2.0*(c+1.0)); double F = 1.0; double prec; double Bnm3 = 1.0; /* B0 */ double Bnm2 = 1.0 + t1 * x; /* B1 */ double Bnm1 = 1.0 + t2 * x * (1.0 + t1/3.0 * x); /* B2 */ double Anm3 = 1.0; /* A0 */ double Anm2 = Bnm2 - t0 * x; /* A1 */ double Anm1 = Bnm1 - t0*(1.0 + t2*x)*x + t0 * t1 * (c/(c+1.0)) * x*x; /* A2 */ while(1) { double nm1 = n - 1; double nm2 = n - 2; double npam1_npbm1 = atimesb + nm1*apb + nm1*nm1; double npam2_npbm2 = atimesb + nm2*apb + nm2*nm2; double npcm1 = nm1 + c; double npcm2 = nm2 + c; double tnm1 = 2*n - 1; double tnm3 = 2*n - 3; double tnm5 = 2*n - 5; double n2 = n*n; double F1 = (3.0*n2 + (apb-6)*n + 2 - atimesb - 2*apb) / (2*tnm3*npcm1); double F2 = -(3.0*n2 - (apb+6)*n + 2 - atimesb)*npam1_npbm1/(4*tnm1*tnm3*npcm2*npcm1); double F3 = (npam2_npbm2*npam1_npbm1*(nm2*nm2 - nm2*apb + atimesb)) / (8*tnm3*tnm3*tnm5*(n+c-3)*npcm2*npcm1); double E = -npam1_npbm1*(n-c-1) / (2*tnm3*npcm2*npcm1); double An = (1.0+F1*x)*Anm1 + (E + F2*x)*x*Anm2 + F3*x3*Anm3; double Bn = (1.0+F1*x)*Bnm1 + (E + F2*x)*x*Bnm2 + F3*x3*Bnm3; double r = An/Bn; prec = fabs(F - r)/fabs(F); F = r; if(prec < GSL_DBL_EPSILON || n > nmax) break; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; Anm3 /= RECUR_BIG; Bnm3 /= RECUR_BIG; } else if(fabs(An) < 1.0/RECUR_BIG || fabs(Bn) < 1.0/RECUR_BIG) { An *= RECUR_BIG; Bn *= RECUR_BIG; Anm1 *= RECUR_BIG; Bnm1 *= RECUR_BIG; Anm2 *= RECUR_BIG; Bnm2 *= RECUR_BIG; Anm3 *= RECUR_BIG; Bnm3 *= RECUR_BIG; } n++; Bnm3 = Bnm2; Bnm2 = Bnm1; Bnm1 = Bn; Anm3 = Anm2; Anm2 = Anm1; Anm1 = An; } result->val = F; result->err = 2.0 * fabs(prec * F); result->err += 2.0 * GSL_DBL_EPSILON * (n+1.0) * fabs(F); /* FIXME: see above */ result->err *= 8.0 * (fabs(aR) + fabs(aI) + 1.0); stat_iter = (n >= nmax ? GSL_EMAXITER : GSL_SUCCESS ); return stat_iter; } /* Do the reflection described in [Moshier, p. 334]. * Assumes a,b,c != neg integer. */ static int hyperg_2F1_reflect(const double a, const double b, const double c, const double x, gsl_sf_result * result) { const double d = c - a - b; const int intd = floor(d+0.5); const int d_integer = ( fabs(d - intd) < locEPS ); if(d_integer) { const double ln_omx = log(1.0 - x); const double ad = fabs(d); int stat_F2 = GSL_SUCCESS; double sgn_2; gsl_sf_result F1; gsl_sf_result F2; double d1, d2; gsl_sf_result lng_c; gsl_sf_result lng_ad2; gsl_sf_result lng_bd2; int stat_c; int stat_ad2; int stat_bd2; if(d >= 0.0) { d1 = d; d2 = 0.0; } else { d1 = 0.0; d2 = d; } stat_ad2 = gsl_sf_lngamma_e(a+d2, &lng_ad2); stat_bd2 = gsl_sf_lngamma_e(b+d2, &lng_bd2); stat_c = gsl_sf_lngamma_e(c, &lng_c); /* Evaluate F1. */ if(ad < GSL_DBL_EPSILON) { /* d = 0 */ F1.val = 0.0; F1.err = 0.0; } else { gsl_sf_result lng_ad; gsl_sf_result lng_ad1; gsl_sf_result lng_bd1; int stat_ad = gsl_sf_lngamma_e(ad, &lng_ad); int stat_ad1 = gsl_sf_lngamma_e(a+d1, &lng_ad1); int stat_bd1 = gsl_sf_lngamma_e(b+d1, &lng_bd1); if(stat_ad1 == GSL_SUCCESS && stat_bd1 == GSL_SUCCESS && stat_ad == GSL_SUCCESS) { /* Gamma functions in the denominator are ok. * Proceed with evaluation. */ int i; double sum1 = 1.0; double term = 1.0; double ln_pre1_val = lng_ad.val + lng_c.val + d2*ln_omx - lng_ad1.val - lng_bd1.val; double ln_pre1_err = lng_ad.err + lng_c.err + lng_ad1.err + lng_bd1.err + GSL_DBL_EPSILON * fabs(ln_pre1_val); int stat_e; /* Do F1 sum. */ for(i=1; ival = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EOVRFLW); } } stat_F2 = GSL_ERROR_SELECT_2(stat_F2, stat_dall); } else { /* Gamma functions in the denominator not ok. * So the F2 term is zero. */ F2.val = 0.0; F2.err = 0.0; } /* end F2 evaluation */ sgn_2 = ( GSL_IS_ODD(intd) ? -1.0 : 1.0 ); result->val = F1.val + sgn_2 * F2.val; result->err = F1.err + F2. err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(F1.val) + fabs(F2.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_F2; } else { /* d not an integer */ gsl_sf_result pre1, pre2; double sgn1, sgn2; gsl_sf_result F1, F2; int status_F1, status_F2; /* These gamma functions appear in the denominator, so we * catch their harmless domain errors and set the terms to zero. */ gsl_sf_result ln_g1ca, ln_g1cb, ln_g2a, ln_g2b; double sgn_g1ca, sgn_g1cb, sgn_g2a, sgn_g2b; int stat_1ca = gsl_sf_lngamma_sgn_e(c-a, &ln_g1ca, &sgn_g1ca); int stat_1cb = gsl_sf_lngamma_sgn_e(c-b, &ln_g1cb, &sgn_g1cb); int stat_2a = gsl_sf_lngamma_sgn_e(a, &ln_g2a, &sgn_g2a); int stat_2b = gsl_sf_lngamma_sgn_e(b, &ln_g2b, &sgn_g2b); int ok1 = (stat_1ca == GSL_SUCCESS && stat_1cb == GSL_SUCCESS); int ok2 = (stat_2a == GSL_SUCCESS && stat_2b == GSL_SUCCESS); gsl_sf_result ln_gc, ln_gd, ln_gmd; double sgn_gc, sgn_gd, sgn_gmd; gsl_sf_lngamma_sgn_e( c, &ln_gc, &sgn_gc); gsl_sf_lngamma_sgn_e( d, &ln_gd, &sgn_gd); gsl_sf_lngamma_sgn_e(-d, &ln_gmd, &sgn_gmd); sgn1 = sgn_gc * sgn_gd * sgn_g1ca * sgn_g1cb; sgn2 = sgn_gc * sgn_gmd * sgn_g2a * sgn_g2b; if(ok1 && ok2) { double ln_pre1_val = ln_gc.val + ln_gd.val - ln_g1ca.val - ln_g1cb.val; double ln_pre2_val = ln_gc.val + ln_gmd.val - ln_g2a.val - ln_g2b.val + d*log(1.0-x); double ln_pre1_err = ln_gc.err + ln_gd.err + ln_g1ca.err + ln_g1cb.err; double ln_pre2_err = ln_gc.err + ln_gmd.err + ln_g2a.err + ln_g2b.err; if(ln_pre1_val < GSL_LOG_DBL_MAX && ln_pre2_val < GSL_LOG_DBL_MAX) { gsl_sf_exp_err_e(ln_pre1_val, ln_pre1_err, &pre1); gsl_sf_exp_err_e(ln_pre2_val, ln_pre2_err, &pre2); pre1.val *= sgn1; pre2.val *= sgn2; } else { OVERFLOW_ERROR(result); } } else if(ok1 && !ok2) { double ln_pre1_val = ln_gc.val + ln_gd.val - ln_g1ca.val - ln_g1cb.val; double ln_pre1_err = ln_gc.err + ln_gd.err + ln_g1ca.err + ln_g1cb.err; if(ln_pre1_val < GSL_LOG_DBL_MAX) { gsl_sf_exp_err_e(ln_pre1_val, ln_pre1_err, &pre1); pre1.val *= sgn1; pre2.val = 0.0; pre2.err = 0.0; } else { OVERFLOW_ERROR(result); } } else if(!ok1 && ok2) { double ln_pre2_val = ln_gc.val + ln_gmd.val - ln_g2a.val - ln_g2b.val + d*log(1.0-x); double ln_pre2_err = ln_gc.err + ln_gmd.err + ln_g2a.err + ln_g2b.err; if(ln_pre2_val < GSL_LOG_DBL_MAX) { pre1.val = 0.0; pre1.err = 0.0; gsl_sf_exp_err_e(ln_pre2_val, ln_pre2_err, &pre2); pre2.val *= sgn2; } else { OVERFLOW_ERROR(result); } } else { pre1.val = 0.0; pre2.val = 0.0; UNDERFLOW_ERROR(result); } status_F1 = hyperg_2F1_series( a, b, 1.0-d, 1.0-x, &F1); status_F2 = hyperg_2F1_series(c-a, c-b, 1.0+d, 1.0-x, &F2); result->val = pre1.val*F1.val + pre2.val*F2.val; result->err = fabs(pre1.val*F1.err) + fabs(pre2.val*F2.err); result->err += fabs(pre1.err*F1.val) + fabs(pre2.err*F2.val); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(pre1.val*F1.val) + fabs(pre2.val*F2.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } static int pow_omx(const double x, const double p, gsl_sf_result * result) { double ln_omx; double ln_result; if(fabs(x) < GSL_ROOT5_DBL_EPSILON) { ln_omx = -x*(1.0 + x*(1.0/2.0 + x*(1.0/3.0 + x/4.0 + x*x/5.0))); } else { ln_omx = log(1.0-x); } ln_result = p * ln_omx; return gsl_sf_exp_err_e(ln_result, GSL_DBL_EPSILON * fabs(ln_result), result); } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_hyperg_2F1_e(double a, double b, const double c, const double x, gsl_sf_result * result) { const double d = c - a - b; const double rinta = floor(a + 0.5); const double rintb = floor(b + 0.5); const double rintc = floor(c + 0.5); const int a_neg_integer = ( a < 0.0 && fabs(a - rinta) < locEPS ); const int b_neg_integer = ( b < 0.0 && fabs(b - rintb) < locEPS ); const int c_neg_integer = ( c < 0.0 && fabs(c - rintc) < locEPS ); result->val = 0.0; result->err = 0.0; if(x < -1.0 || 1.0 <= x) { DOMAIN_ERROR(result); } if(c_neg_integer) { if(! (a_neg_integer && a > c + 0.1)) DOMAIN_ERROR(result); if(! (b_neg_integer && b > c + 0.1)) DOMAIN_ERROR(result); } if(fabs(c-b) < locEPS || fabs(c-a) < locEPS) { return pow_omx(x, d, result); /* (1-x)^(c-a-b) */ } if(a >= 0.0 && b >= 0.0 && c >=0.0 && x >= 0.0 && x < 0.995) { /* Series has all positive definite * terms and x is not close to 1. */ return hyperg_2F1_series(a, b, c, x, result); } if(fabs(a) < 10.0 && fabs(b) < 10.0) { /* a and b are not too large, so we attempt * variations on the series summation. */ if(a_neg_integer) { return hyperg_2F1_series(rinta, b, c, x, result); } if(b_neg_integer) { return hyperg_2F1_series(a, rintb, c, x, result); } if(x < -0.25) { return hyperg_2F1_luke(a, b, c, x, result); } else if(x < 0.5) { return hyperg_2F1_series(a, b, c, x, result); } else { if(fabs(c) > 10.0) { return hyperg_2F1_series(a, b, c, x, result); } else { return hyperg_2F1_reflect(a, b, c, x, result); } } } else { /* Either a or b or both large. * Introduce some new variables ap,bp so that bp is * the larger in magnitude. */ double ap, bp; if(fabs(a) > fabs(b)) { bp = a; ap = b; } else { bp = b; ap = a; } if(x < 0.0) { /* What the hell, maybe Luke will converge. */ return hyperg_2F1_luke(a, b, c, x, result); } if(GSL_MAX_DBL(fabs(a),1.0)*fabs(bp)*fabs(x) < 2.0*fabs(c)) { /* If c is large enough or x is small enough, * we can attempt the series anyway. */ return hyperg_2F1_series(a, b, c, x, result); } if(fabs(bp*bp*x*x) < 0.001*fabs(bp) && fabs(a) < 10.0) { /* The famous but nearly worthless "large b" asymptotic. */ int stat = gsl_sf_hyperg_1F1_e(a, c, bp*x, result); result->err = 0.001 * fabs(result->val); return stat; } /* We give up. */ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EUNIMPL); } } int gsl_sf_hyperg_2F1_conj_e(const double aR, const double aI, const double c, const double x, gsl_sf_result * result) { const double ax = fabs(x); const double rintc = floor(c + 0.5); const int c_neg_integer = ( c < 0.0 && fabs(c - rintc) < locEPS ); result->val = 0.0; result->err = 0.0; if(ax >= 1.0 || c_neg_integer || c == 0.0) { DOMAIN_ERROR(result); } if( (ax < 0.25 && fabs(aR) < 20.0 && fabs(aI) < 20.0) || (c > 0.0 && x > 0.0) ) { return hyperg_2F1_conj_series(aR, aI, c, x, result); } else if(fabs(aR) < 10.0 && fabs(aI) < 10.0) { if(x < -0.25) { return hyperg_2F1_conj_luke(aR, aI, c, x, result); } else { return hyperg_2F1_conj_series(aR, aI, c, x, result); } } else { if(x < 0.0) { /* What the hell, maybe Luke will converge. */ return hyperg_2F1_conj_luke(aR, aI, c, x, result); } /* Give up. */ result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_EUNIMPL); } } int gsl_sf_hyperg_2F1_renorm_e(const double a, const double b, const double c, const double x, gsl_sf_result * result ) { const double rinta = floor(a + 0.5); const double rintb = floor(b + 0.5); const double rintc = floor(c + 0.5); const int a_neg_integer = ( a < 0.0 && fabs(a - rinta) < locEPS ); const int b_neg_integer = ( b < 0.0 && fabs(b - rintb) < locEPS ); const int c_neg_integer = ( c < 0.0 && fabs(c - rintc) < locEPS ); if(c_neg_integer) { if((a_neg_integer && a > c+0.1) || (b_neg_integer && b > c+0.1)) { /* 2F1 terminates early */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* 2F1 does not terminate early enough, so something survives */ /* [Abramowitz+Stegun, 15.1.2] */ gsl_sf_result g1, g2, g3, g4, g5; double s1, s2, s3, s4, s5; int stat = 0; stat += gsl_sf_lngamma_sgn_e(a-c+1, &g1, &s1); stat += gsl_sf_lngamma_sgn_e(b-c+1, &g2, &s2); stat += gsl_sf_lngamma_sgn_e(a, &g3, &s3); stat += gsl_sf_lngamma_sgn_e(b, &g4, &s4); stat += gsl_sf_lngamma_sgn_e(-c+2, &g5, &s5); if(stat != 0) { DOMAIN_ERROR(result); } else { gsl_sf_result F; int stat_F = gsl_sf_hyperg_2F1_e(a-c+1, b-c+1, -c+2, x, &F); double ln_pre_val = g1.val + g2.val - g3.val - g4.val - g5.val; double ln_pre_err = g1.err + g2.err + g3.err + g4.err + g5.err; double sg = s1 * s2 * s3 * s4 * s5; int stat_e = gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, sg * F.val, F.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_F); } } } else { /* generic c */ gsl_sf_result F; gsl_sf_result lng; double sgn; int stat_g = gsl_sf_lngamma_sgn_e(c, &lng, &sgn); int stat_F = gsl_sf_hyperg_2F1_e(a, b, c, x, &F); int stat_e = gsl_sf_exp_mult_err_e(-lng.val, lng.err, sgn*F.val, F.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_F, stat_g); } } int gsl_sf_hyperg_2F1_conj_renorm_e(const double aR, const double aI, const double c, const double x, gsl_sf_result * result ) { const double rintc = floor(c + 0.5); const double rinta = floor(aR + 0.5); const int a_neg_integer = ( aR < 0.0 && fabs(aR-rinta) < locEPS && aI == 0.0); const int c_neg_integer = ( c < 0.0 && fabs(c - rintc) < locEPS ); if(c_neg_integer) { if(a_neg_integer && aR > c+0.1) { /* 2F1 terminates early */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* 2F1 does not terminate early enough, so something survives */ /* [Abramowitz+Stegun, 15.1.2] */ gsl_sf_result g1, g2; gsl_sf_result g3; gsl_sf_result a1, a2; int stat = 0; stat += gsl_sf_lngamma_complex_e(aR-c+1, aI, &g1, &a1); stat += gsl_sf_lngamma_complex_e(aR, aI, &g2, &a2); stat += gsl_sf_lngamma_e(-c+2.0, &g3); if(stat != 0) { DOMAIN_ERROR(result); } else { gsl_sf_result F; int stat_F = gsl_sf_hyperg_2F1_conj_e(aR-c+1, aI, -c+2, x, &F); double ln_pre_val = 2.0*(g1.val - g2.val) - g3.val; double ln_pre_err = 2.0 * (g1.err + g2.err) + g3.err; int stat_e = gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, F.val, F.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_F); } } } else { /* generic c */ gsl_sf_result F; gsl_sf_result lng; double sgn; int stat_g = gsl_sf_lngamma_sgn_e(c, &lng, &sgn); int stat_F = gsl_sf_hyperg_2F1_conj_e(aR, aI, c, x, &F); int stat_e = gsl_sf_exp_mult_err_e(-lng.val, lng.err, sgn*F.val, F.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_F, stat_g); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_hyperg_2F1(double a, double b, double c, double x) { EVAL_RESULT(gsl_sf_hyperg_2F1_e(a, b, c, x, &result)); } double gsl_sf_hyperg_2F1_conj(double aR, double aI, double c, double x) { EVAL_RESULT(gsl_sf_hyperg_2F1_conj_e(aR, aI, c, x, &result)); } double gsl_sf_hyperg_2F1_renorm(double a, double b, double c, double x) { EVAL_RESULT(gsl_sf_hyperg_2F1_renorm_e(a, b, c, x, &result)); } double gsl_sf_hyperg_2F1_conj_renorm(double aR, double aI, double c, double x) { EVAL_RESULT(gsl_sf_hyperg_2F1_conj_renorm_e(aR, aI, c, x, &result)); } sources_5316/external/gsl/gsl_integration__qc25c.c0000664000176700017670000000606011723710247021032 0ustar paulpaul/* integration/qc25c.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ struct fn_cauchy_params { gsl_function *function; double singularity; }; static double fn_cauchy (double t, void *params); static void compute_moments (double cc, double *moment); static void qc25c (gsl_function * f, double a, double b, double c, double *result, double *abserr, int *err_reliable); static void qc25c (gsl_function * f, double a, double b, double c, double *result, double *abserr, int *err_reliable) { double cc = (2 * c - b - a) / (b - a); if (fabs (cc) > 1.1) { double resabs, resasc; gsl_function weighted_function; struct fn_cauchy_params fn_params; fn_params.function = f; fn_params.singularity = c; weighted_function.function = &fn_cauchy; weighted_function.params = &fn_params; gsl_integration_qk15 (&weighted_function, a, b, result, abserr, &resabs, &resasc); if (*abserr == resasc) { *err_reliable = 0; } else { *err_reliable = 1; } return; } else { double cheb12[13], cheb24[25], moment[25]; double res12 = 0, res24 = 0; size_t i; gsl_integration_qcheb (f, a, b, cheb12, cheb24); compute_moments (cc, moment); for (i = 0; i < 13; i++) { res12 += cheb12[i] * moment[i]; } for (i = 0; i < 25; i++) { res24 += cheb24[i] * moment[i]; } *result = res24; *abserr = fabs(res24 - res12) ; *err_reliable = 0; return; } } static double fn_cauchy (double x, void *params) { struct fn_cauchy_params *p = (struct fn_cauchy_params *) params; gsl_function *f = p->function; double c = p->singularity; return GSL_FN_EVAL (f, x) / (x - c); } static void compute_moments (double cc, double *moment) { size_t k; double a0 = log (fabs ((1.0 - cc) / (1.0 + cc))); double a1 = 2 + a0 * cc; moment[0] = a0; moment[1] = a1; for (k = 2; k < 25; k++) { double a2; if ((k % 2) == 0) { a2 = 2.0 * cc * a1 - a0; } else { const double km1 = k - 1.0; a2 = 2.0 * cc * a1 - a0 - 4.0 / (km1 * km1 - 1.0); } moment[k] = a2; a0 = a1; a1 = a2; } } sources_5316/external/gsl/gsl_cdf__tdistinv.c0000664000176700017670000001200511723710247020166 0ustar paulpaul/* cdf/tdistinv.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 2002 Jason H. Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include "gsl__config.h" #include #include "gsl_cdf.h" #include "gsl_math.h" #include "gsl_randist.h" #include "gsl_sf_gamma.h" #include static double inv_cornish_fisher (double z, double nu) { double a = 1 / (nu - 0.5); double b = 48.0 / (a * a); double cf1 = z * (3 + z * z); double cf2 = z * (945 + z * z * (360 + z * z * (63 + z * z * 4))); double y = z - cf1 / b + cf2 / (10 * b * b); double t = GSL_SIGN (z) * sqrt (nu * expm1 (a * y * y)); return t; } double gsl_cdf_tdist_Pinv (const double P, const double nu) { double x, ptail; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return GSL_NEGINF; } if (nu == 1.0) { x = tan (M_PI * (P - 0.5)); } else if (nu == 2.0) { double a = 2 * P - 1; x = a / sqrt (2 * (1 - a * a)); } ptail = (P < 0.5) ? P : 1 - P; if (sqrt (M_PI * nu / 2) * ptail > pow (0.05, nu / 2)) { double xg = gsl_cdf_ugaussian_Pinv (P); x = inv_cornish_fisher (xg, nu); } else { /* Use an asymptotic expansion of the tail of integral */ double beta = gsl_sf_beta (0.5, nu / 2); if (P < 0.5) { x = -sqrt (nu) * pow (beta * nu * P, -1.0 / nu); } else { x = sqrt (nu) * pow (beta * nu * (1 - P), -1.0 / nu); } /* Correct nu -> nu/(1+nu/x^2) in the leading term to account for higher order terms. This avoids overestimating x, which makes the iteration unstable due to the rapidly decreasing tails of the distribution. */ x /= sqrt (1 + nu / (x * x)); } { double dP, phi; unsigned int n = 0; start: dP = P - gsl_cdf_tdist_P (x, nu); phi = gsl_ran_tdist_pdf (x, nu); if (dP == 0.0 || n++ > 32) goto end; { double lambda = dP / phi; double step0 = lambda; double step1 = ((nu + 1) * x / (x * x + nu)) * (lambda * lambda / 4.0); double step = step0; if (fabs (step1) < fabs (step0)) { step += step1; } if (P > 0.5 && x + step < 0) x /= 2; else if (P < 0.5 && x + step > 0) x /= 2; else x += step; if (fabs (step) > 1e-10 * fabs (x)) goto start; } end: if (fabs(dP) > GSL_SQRT_DBL_EPSILON * P) { GSL_ERROR_VAL("inverse failed to converge", GSL_EFAILED, GSL_NAN); } return x; } } double gsl_cdf_tdist_Qinv (const double Q, const double nu) { double x, qtail; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return GSL_NEGINF; } if (nu == 1.0) { x = tan (M_PI * (0.5 - Q)); } else if (nu == 2.0) { double a = 2 * (1 - Q) - 1; x = a / sqrt (2 * (1 - a * a)); } qtail = (Q < 0.5) ? Q : 1 - Q; if (sqrt (M_PI * nu / 2) * qtail > pow (0.05, nu / 2)) { double xg = gsl_cdf_ugaussian_Qinv (Q); x = inv_cornish_fisher (xg, nu); } else { /* Use an asymptotic expansion of the tail of integral */ double beta = gsl_sf_beta (0.5, nu / 2); if (Q < 0.5) { x = sqrt (nu) * pow (beta * nu * Q, -1.0 / nu); } else { x = -sqrt (nu) * pow (beta * nu * (1 - Q), -1.0 / nu); } /* Correct nu -> nu/(1+nu/x^2) in the leading term to account for higher order terms. This avoids overestimating x, which makes the iteration unstable due to the rapidly decreasing tails of the distribution. */ x /= sqrt (1 + nu / (x * x)); } { double dQ, phi; unsigned int n = 0; start: dQ = Q - gsl_cdf_tdist_Q (x, nu); phi = gsl_ran_tdist_pdf (x, nu); if (dQ == 0.0 || n++ > 32) goto end; { double lambda = - dQ / phi; double step0 = lambda; double step1 = ((nu + 1) * x / (x * x + nu)) * (lambda * lambda / 4.0); double step = step0; if (fabs (step1) < fabs (step0)) { step += step1; } if (Q < 0.5 && x + step < 0) x /= 2; else if (Q > 0.5 && x + step > 0) x /= 2; else x += step; if (fabs (step) > 1e-10 * fabs (x)) goto start; } } end: return x; } sources_5316/external/gsl/gsl_histogram__params2d.c0000664000176700017670000000263211723710247021301 0ustar paulpaul/* histogram/params2d.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_histogram2d.h" double gsl_histogram2d_xmax (const gsl_histogram2d * h) { const int nx = h->nx; return h->xrange[nx]; } double gsl_histogram2d_xmin (const gsl_histogram2d * h) { return h->xrange[0]; } double gsl_histogram2d_ymax (const gsl_histogram2d * h) { const int ny = h->ny; return h->yrange[ny]; } double gsl_histogram2d_ymin (const gsl_histogram2d * h) { return h->yrange[0]; } size_t gsl_histogram2d_nx (const gsl_histogram2d * h) { return h->nx; } size_t gsl_histogram2d_ny (const gsl_histogram2d * h) { return h->ny; } sources_5316/external/gsl/gsl_cdf__rayleigh.c0000664000176700017670000000216611723710247020135 0ustar paulpaul/* cdf/rayleigh.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_rayleigh_P (const double x, const double sigma) { double u = x / sigma; double P = -expm1 (-u*u/2); return P; } double gsl_cdf_rayleigh_Q (const double x, const double sigma) { double u = x / sigma; double Q = exp (-u*u/2); return Q; } sources_5316/external/gsl/gsl_statistics__p_variance_source.c0000664000176700017670000000266411723710247023461 0ustar paulpaul/* statistics/p_variance_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,pvariance) (const BASE data1[], const size_t stride1, const size_t n1, const BASE data2[], const size_t stride2, const size_t n2) { /* Find the pooled variance of two datasets */ const double var1 = FUNCTION(gsl_stats,variance) (data1, stride1, n1); const double var2 = FUNCTION(gsl_stats,variance) (data2, stride2, n2); /* calculate the pooled variance */ const double pooled_variance = (((n1 - 1) * var1) + ((n2 - 1) * var2)) / (n1 + n2 - 2); return pooled_variance; } sources_5316/external/gsl/gsl_rng__cmrg.c0000664000176700017670000001231111723710247017304 0ustar paulpaul/* rng/cmrg.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is a combined multiple recursive generator. The sequence is, z_n = (x_n - y_n) mod m1 where the two underlying generators x and y are, x_n = (a_{1} x_{n-1} + a_{2} x_{n-2} + a_{3} x_{n-3}) mod m1 y_n = (b_{1} y_{n-1} + b_{2} y_{n-2} + b_{3} y_{n-3}) mod m2 with coefficients a11 ... a23, a_{1} = 0, a_{2} = 63308, a_{3} = -183326 b_{1} = 86098, b_{2} = 0, b_{3} = -539608 and moduli m1, m2, m1 = 2^31 - 1 = 2147483647 m2 = 2^31 - 2000169 = 2145483479 We initialize the generator with x_1 = s_1 MOD m1, x_2 = s_2 MOD m1, x_3 = s_3 MOD m1 y_1 = s_4 MOD m2, y_2 = s_5 MOD m2, y_3 = s_6 MOD m2 where s_n = (69069 * s_{n-1}) mod 2^32 and s_0 = s is the user-supplied seed. NOTE: According to the paper the initial values for x_n must lie in the range 0 <= x_n <= (m1 - 1) and the initial values for y_n must lie in the range 0 <= y_n <= (m2 - 1), with at least one non-zero value -- our seeding procedure satisfies these constraints. We then use 7 iterations of the generator to "warm up" the internal state. The theoretical value of z_{10008} is 719452880. The subscript 10008 means (1) seed the generator with s=1, (2) do the seven warm-up iterations that are part of the seeding process, (3) then do 10000 actual iterations. The period of this generator is about 2^205. From: P. L'Ecuyer, "Combined Multiple Recursive Random Number Generators," Operations Research, 44, 5 (1996), 816--822. This is available on the net from L'Ecuyer's home page, http://www.iro.umontreal.ca/~lecuyer/myftp/papers/combmrg.ps ftp://ftp.iro.umontreal.ca/pub/simulation/lecuyer/papers/combmrg.ps */ static inline unsigned long int cmrg_get (void *vstate); static double cmrg_get_double (void *vstate); static void cmrg_set (void *state, unsigned long int s); static const long int m1 = 2147483647, m2 = 2145483479; static const long int a2 = 63308, qa2 = 33921, ra2 = 12979; static const long int a3 = -183326, qa3 = 11714, ra3 = 2883; static const long int b1 = 86098, qb1 = 24919, rb1 = 7417; static const long int b3 = -539608, qb3 = 3976, rb3 = 2071; typedef struct { long int x1, x2, x3; /* first component */ long int y1, y2, y3; /* second component */ } cmrg_state_t; static inline unsigned long int cmrg_get (void *vstate) { cmrg_state_t *state = (cmrg_state_t *) vstate; /* Component 1 */ { long int h3 = state->x3 / qa3; long int p3 = -a3 * (state->x3 - h3 * qa3) - h3 * ra3; long int h2 = state->x2 / qa2; long int p2 = a2 * (state->x2 - h2 * qa2) - h2 * ra2; if (p3 < 0) p3 += m1; if (p2 < 0) p2 += m1; state->x3 = state->x2; state->x2 = state->x1; state->x1 = p2 - p3; if (state->x1 < 0) state->x1 += m1; } /* Component 2 */ { long int h3 = state->y3 / qb3; long int p3 = -b3 * (state->y3 - h3 * qb3) - h3 * rb3; long int h1 = state->y1 / qb1; long int p1 = b1 * (state->y1 - h1 * qb1) - h1 * rb1; if (p3 < 0) p3 += m2; if (p1 < 0) p1 += m2; state->y3 = state->y2; state->y2 = state->y1; state->y1 = p1 - p3; if (state->y1 < 0) state->y1 += m2; } if (state->x1 < state->y1) return (state->x1 - state->y1 + m1); else return (state->x1 - state->y1); } static double cmrg_get_double (void *vstate) { return cmrg_get (vstate) / 2147483647.0 ; } static void cmrg_set (void *vstate, unsigned long int s) { /* An entirely adhoc way of seeding! This does **not** come from L'Ecuyer et al */ cmrg_state_t *state = (cmrg_state_t *) vstate; if (s == 0) s = 1; /* default seed is 1 */ #define LCG(n) ((69069 * n) & 0xffffffffUL) s = LCG (s); state->x1 = s % m1; s = LCG (s); state->x2 = s % m1; s = LCG (s); state->x3 = s % m1; s = LCG (s); state->y1 = s % m2; s = LCG (s); state->y2 = s % m2; s = LCG (s); state->y3 = s % m2; /* "warm it up" */ cmrg_get (state); cmrg_get (state); cmrg_get (state); cmrg_get (state); cmrg_get (state); cmrg_get (state); cmrg_get (state); } static const gsl_rng_type cmrg_type = {"cmrg", /* name */ 2147483646, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (cmrg_state_t), &cmrg_set, &cmrg_get, &cmrg_get_double}; const gsl_rng_type *gsl_rng_cmrg = &cmrg_type; sources_5316/external/gsl/gsl_cblas__source_trsm_c.h0000664000176700017670000003472311705263724021544 0ustar paulpaul/* blas/source_trsm_c.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; INDEX n1, n2; const int nonunit = (Diag == CblasNonUnit); const int conj = (TransA == CblasConjTrans) ? -1 : 1; int side, uplo, trans; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); if (Order == CblasRowMajor) { n1 = M; n2 = N; side = Side; uplo = Uplo; trans = TransA; trans = (TransA == CblasNoTrans) ? CblasNoTrans : CblasTrans; } else { n1 = N; n2 = M; side = (Side == CblasLeft) ? CblasRight : CblasLeft; /* exchanged */ uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; /* exchanged */ trans = (TransA == CblasNoTrans) ? CblasNoTrans : CblasTrans; /* same */ } if (side == CblasLeft && uplo == CblasUpper && trans == CblasNoTrans) { /* form B := alpha * inv(TriU(A)) *B */ if (!(alpha_real == 1.0 && alpha_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = alpha_real * Bij_real - alpha_imag * Bij_imag; IMAG(B, ldb * i + j) = alpha_real * Bij_imag + alpha_imag * Bij_real; } } } for (i = n1; i > 0 && i--;) { if (nonunit) { const BASE Aii_real = CONST_REAL(A, lda * i + i); const BASE Aii_imag = conj * CONST_IMAG(A, lda * i + i); const BASE s = xhypot(Aii_real, Aii_imag); const BASE a_real = Aii_real / s; const BASE a_imag = Aii_imag / s; for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = (Bij_real * a_real + Bij_imag * a_imag) / s; IMAG(B, ldb * i + j) = (Bij_imag * a_real - Bij_real * a_imag) / s; } } for (k = 0; k < i; k++) { const BASE Aki_real = CONST_REAL(A, k * lda + i); const BASE Aki_imag = conj * CONST_IMAG(A, k * lda + i); for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * k + j) -= Aki_real * Bij_real - Aki_imag * Bij_imag; IMAG(B, ldb * k + j) -= Aki_real * Bij_imag + Aki_imag * Bij_real; } } } } else if (side == CblasLeft && uplo == CblasUpper && trans == CblasTrans) { /* form B := alpha * inv(TriU(A))' *B */ if (!(alpha_real == 1.0 && alpha_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = alpha_real * Bij_real - alpha_imag * Bij_imag; IMAG(B, ldb * i + j) = alpha_real * Bij_imag + alpha_imag * Bij_real; } } } for (i = 0; i < n1; i++) { if (nonunit) { const BASE Aii_real = CONST_REAL(A, lda * i + i); const BASE Aii_imag = conj * CONST_IMAG(A, lda * i + i); const BASE s = xhypot(Aii_real, Aii_imag); const BASE a_real = Aii_real / s; const BASE a_imag = Aii_imag / s; for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = (Bij_real * a_real + Bij_imag * a_imag) / s; IMAG(B, ldb * i + j) = (Bij_imag * a_real - Bij_real * a_imag) / s; } } for (k = i + 1; k < n1; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = conj * CONST_IMAG(A, i * lda + k); for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * k + j) -= Aik_real * Bij_real - Aik_imag * Bij_imag; IMAG(B, ldb * k + j) -= Aik_real * Bij_imag + Aik_imag * Bij_real; } } } } else if (side == CblasLeft && uplo == CblasLower && trans == CblasNoTrans) { /* form B := alpha * inv(TriL(A))*B */ if (!(alpha_real == 1.0 && alpha_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = alpha_real * Bij_real - alpha_imag * Bij_imag; IMAG(B, ldb * i + j) = alpha_real * Bij_imag + alpha_imag * Bij_real; } } } for (i = 0; i < n1; i++) { if (nonunit) { const BASE Aii_real = CONST_REAL(A, lda * i + i); const BASE Aii_imag = conj * CONST_IMAG(A, lda * i + i); const BASE s = xhypot(Aii_real, Aii_imag); const BASE a_real = Aii_real / s; const BASE a_imag = Aii_imag / s; for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = (Bij_real * a_real + Bij_imag * a_imag) / s; IMAG(B, ldb * i + j) = (Bij_imag * a_real - Bij_real * a_imag) / s; } } for (k = i + 1; k < n1; k++) { const BASE Aki_real = CONST_REAL(A, k * lda + i); const BASE Aki_imag = conj * CONST_IMAG(A, k * lda + i); for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * k + j) -= Aki_real * Bij_real - Aki_imag * Bij_imag; IMAG(B, ldb * k + j) -= Aki_real * Bij_imag + Aki_imag * Bij_real; } } } } else if (side == CblasLeft && uplo == CblasLower && trans == CblasTrans) { /* form B := alpha * TriL(A)' *B */ if (!(alpha_real == 1.0 && alpha_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = alpha_real * Bij_real - alpha_imag * Bij_imag; IMAG(B, ldb * i + j) = alpha_real * Bij_imag + alpha_imag * Bij_real; } } } for (i = n1; i > 0 && i--;) { if (nonunit) { const BASE Aii_real = CONST_REAL(A, lda * i + i); const BASE Aii_imag = conj * CONST_IMAG(A, lda * i + i); const BASE s = xhypot(Aii_real, Aii_imag); const BASE a_real = Aii_real / s; const BASE a_imag = Aii_imag / s; for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = (Bij_real * a_real + Bij_imag * a_imag) / s; IMAG(B, ldb * i + j) = (Bij_imag * a_real - Bij_real * a_imag) / s; } } for (k = 0; k < i; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = conj * CONST_IMAG(A, i * lda + k); for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * k + j) -= Aik_real * Bij_real - Aik_imag * Bij_imag; IMAG(B, ldb * k + j) -= Aik_real * Bij_imag + Aik_imag * Bij_real; } } } } else if (side == CblasRight && uplo == CblasUpper && trans == CblasNoTrans) { /* form B := alpha * B * inv(TriU(A)) */ if (!(alpha_real == 1.0 && alpha_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = alpha_real * Bij_real - alpha_imag * Bij_imag; IMAG(B, ldb * i + j) = alpha_real * Bij_imag + alpha_imag * Bij_real; } } } for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { if (nonunit) { const BASE Ajj_real = CONST_REAL(A, lda * j + j); const BASE Ajj_imag = conj * CONST_IMAG(A, lda * j + j); const BASE s = xhypot(Ajj_real, Ajj_imag); const BASE a_real = Ajj_real / s; const BASE a_imag = Ajj_imag / s; const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = (Bij_real * a_real + Bij_imag * a_imag) / s; IMAG(B, ldb * i + j) = (Bij_imag * a_real - Bij_real * a_imag) / s; } { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); for (k = j + 1; k < n2; k++) { const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = conj * CONST_IMAG(A, j * lda + k); REAL(B, ldb * i + k) -= Ajk_real * Bij_real - Ajk_imag * Bij_imag; IMAG(B, ldb * i + k) -= Ajk_real * Bij_imag + Ajk_imag * Bij_real; } } } } } else if (side == CblasRight && uplo == CblasUpper && trans == CblasTrans) { /* form B := alpha * B * inv(TriU(A))' */ if (!(alpha_real == 1.0 && alpha_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = alpha_real * Bij_real - alpha_imag * Bij_imag; IMAG(B, ldb * i + j) = alpha_real * Bij_imag + alpha_imag * Bij_real; } } } for (i = 0; i < n1; i++) { for (j = n2; j > 0 && j--;) { if (nonunit) { const BASE Ajj_real = CONST_REAL(A, lda * j + j); const BASE Ajj_imag = conj * CONST_IMAG(A, lda * j + j); const BASE s = xhypot(Ajj_real, Ajj_imag); const BASE a_real = Ajj_real / s; const BASE a_imag = Ajj_imag / s; const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = (Bij_real * a_real + Bij_imag * a_imag) / s; IMAG(B, ldb * i + j) = (Bij_imag * a_real - Bij_real * a_imag) / s; } { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); for (k = 0; k < j; k++) { const BASE Akj_real = CONST_REAL(A, k * lda + j); const BASE Akj_imag = conj * CONST_IMAG(A, k * lda + j); REAL(B, ldb * i + k) -= Akj_real * Bij_real - Akj_imag * Bij_imag; IMAG(B, ldb * i + k) -= Akj_real * Bij_imag + Akj_imag * Bij_real; } } } } } else if (side == CblasRight && uplo == CblasLower && trans == CblasNoTrans) { /* form B := alpha * B * inv(TriL(A)) */ if (!(alpha_real == 1.0 && alpha_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = alpha_real * Bij_real - alpha_imag * Bij_imag; IMAG(B, ldb * i + j) = alpha_real * Bij_imag + alpha_imag * Bij_real; } } } for (i = 0; i < n1; i++) { for (j = n2; j > 0 && j--;) { if (nonunit) { const BASE Ajj_real = CONST_REAL(A, lda * j + j); const BASE Ajj_imag = conj * CONST_IMAG(A, lda * j + j); const BASE s = xhypot(Ajj_real, Ajj_imag); const BASE a_real = Ajj_real / s; const BASE a_imag = Ajj_imag / s; const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = (Bij_real * a_real + Bij_imag * a_imag) / s; IMAG(B, ldb * i + j) = (Bij_imag * a_real - Bij_real * a_imag) / s; } { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); for (k = 0; k < j; k++) { const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = conj * CONST_IMAG(A, j * lda + k); REAL(B, ldb * i + k) -= Ajk_real * Bij_real - Ajk_imag * Bij_imag; IMAG(B, ldb * i + k) -= Ajk_real * Bij_imag + Ajk_imag * Bij_real; } } } } } else if (side == CblasRight && uplo == CblasLower && trans == CblasTrans) { /* form B := alpha * B * inv(TriL(A))' */ if (!(alpha_real == 1.0 && alpha_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = alpha_real * Bij_real - alpha_imag * Bij_imag; IMAG(B, ldb * i + j) = alpha_real * Bij_imag + alpha_imag * Bij_real; } } } for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { if (nonunit) { const BASE Ajj_real = CONST_REAL(A, lda * j + j); const BASE Ajj_imag = conj * CONST_IMAG(A, lda * j + j); const BASE s = xhypot(Ajj_real, Ajj_imag); const BASE a_real = Ajj_real / s; const BASE a_imag = Ajj_imag / s; const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); REAL(B, ldb * i + j) = (Bij_real * a_real + Bij_imag * a_imag) / s; IMAG(B, ldb * i + j) = (Bij_imag * a_real - Bij_real * a_imag) / s; } { const BASE Bij_real = REAL(B, ldb * i + j); const BASE Bij_imag = IMAG(B, ldb * i + j); for (k = j + 1; k < n2; k++) { const BASE Akj_real = CONST_REAL(A, k * lda + j); const BASE Akj_imag = conj * CONST_IMAG(A, k * lda + j); REAL(B, ldb * i + k) -= Akj_real * Bij_real - Akj_imag * Bij_imag; IMAG(B, ldb * i + k) -= Akj_real * Bij_imag + Akj_imag * Bij_real; } } } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_cblas__zhbmv.c0000664000176700017670000000063411723710247020005 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zhbmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const int K, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE double #include "gsl_cblas__source_hbmv.h" #undef BASE } sources_5316/external/gsl/gsl_rng__default.c0000664000176700017670000000457511723710247020015 0ustar paulpaul/* rng/default.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include "gsl_rng.h" #include "gsl_errno.h" /* The initial defaults are defined in the file mt.c, so we can get access to the static parts of the default generator. */ const gsl_rng_type * gsl_rng_env_setup (void) { unsigned long int seed = 0; const char *p = getenv ("GSL_RNG_TYPE"); if (p) { const gsl_rng_type **t, **t0 = gsl_rng_types_setup (); gsl_rng_default = 0; /* check GSL_RNG_TYPE against the names of all the generators */ for (t = t0; *t != 0; t++) { if (strcmp (p, (*t)->name) == 0) { gsl_rng_default = *t; break; } } if (gsl_rng_default == 0) { int i = 0; fprintf (stderr, "GSL_RNG_TYPE=%s not recognized\n", p); fprintf (stderr, "Valid generator types are:\n"); for (t = t0; *t != 0; t++) { fprintf (stderr, " %18s", (*t)->name); if ((++i) % 4 == 0) { fputc ('\n', stderr); } } fputc ('\n', stderr); GSL_ERROR_VAL ("unknown generator", GSL_EINVAL, 0); } fprintf (stderr, "GSL_RNG_TYPE=%s\n", gsl_rng_default->name); } else { gsl_rng_default = gsl_rng_mt19937; } p = getenv ("GSL_RNG_SEED"); if (p) { seed = strtoul (p, 0, 0); fprintf (stderr, "GSL_RNG_SEED=%lu\n", seed); }; gsl_rng_default_seed = seed; return gsl_rng_default; } sources_5316/external/gsl/gsl_sf__bessel_olver.h0000644000176700017670000000223210707442037020666 0ustar paulpaul/* specfunc/bessel_olver.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef BESSEL_OLVER_H_ #define BESSEL_OLVER_H_ #include "gsl_sf_result.h" int gsl_sf_bessel_Jnu_asymp_Olver_e(double nu, double x, gsl_sf_result * result); int gsl_sf_bessel_Ynu_asymp_Olver_e(double nu, double x, gsl_sf_result * result); double gsl_sf_bessel_Olver_zofmzeta(double minus_zeta); #endif /* !BESSEL_OLVER_H_ */ sources_5316/external/gsl/gsl_specfunc__bessel.c0000664000176700017670000006453111723710247020664 0ustar paulpaul/* specfunc/bessel.c * * Copyright (C) 1996,1997,1998,1999,2000,2001,2002,2003 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Miscellaneous support functions for Bessel function evaluations. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_airy.h" #include "gsl_sf_elementary.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_trig.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel_amp_phase.h" #include "gsl_specfunc__bessel_temme.h" #include "gsl_specfunc__bessel.h" #define CubeRoot2_ 1.25992104989487316476721060728 /* Debye functions [Abramowitz+Stegun, 9.3.9-10] */ inline static double debye_u1(const double * tpow) { return (3.0*tpow[1] - 5.0*tpow[3])/24.0; } inline static double debye_u2(const double * tpow) { return (81.0*tpow[2] - 462.0*tpow[4] + 385.0*tpow[6])/1152.0; } inline static double debye_u3(const double * tpow) { return (30375.0*tpow[3] - 369603.0*tpow[5] + 765765.0*tpow[7] - 425425.0*tpow[9])/414720.0; } inline static double debye_u4(const double * tpow) { return (4465125.0*tpow[4] - 94121676.0*tpow[6] + 349922430.0*tpow[8] - 446185740.0*tpow[10] + 185910725.0*tpow[12])/39813120.0; } inline static double debye_u5(const double * tpow) { return (1519035525.0*tpow[5] - 49286948607.0*tpow[7] + 284499769554.0*tpow[9] - 614135872350.0*tpow[11] + 566098157625.0*tpow[13] - 188699385875.0*tpow[15])/6688604160.0; } #if 0 inline static double debye_u6(const double * tpow) { return (2757049477875.0*tpow[6] - 127577298354750.0*tpow[8] + 1050760774457901.0*tpow[10] - 3369032068261860.0*tpow[12] + 5104696716244125.0*tpow[14] - 3685299006138750.0*tpow[16] + 1023694168371875.0*tpow[18])/4815794995200.0; } #endif /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_IJ_taylor_e(const double nu, const double x, const int sign, const int kmax, const double threshold, gsl_sf_result * result ) { /* CHECK_POINTER(result) */ if(nu < 0.0 || x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { if(nu == 0.0) { result->val = 1.0; result->err = 0.0; } else { result->val = 0.0; result->err = 0.0; } return GSL_SUCCESS; } else { gsl_sf_result prefactor; /* (x/2)^nu / Gamma(nu+1) */ gsl_sf_result sum; int stat_pre; int stat_sum; int stat_mul; if(nu == 0.0) { prefactor.val = 1.0; prefactor.err = 0.0; stat_pre = GSL_SUCCESS; } else if(nu < INT_MAX-1) { /* Separate the integer part and use * y^nu / Gamma(nu+1) = y^N /N! y^f / (N+1)_f, * to control the error. */ const int N = (int)floor(nu + 0.5); const double f = nu - N; gsl_sf_result poch_factor; gsl_sf_result tc_factor; const int stat_poch = gsl_sf_poch_e(N+1.0, f, &poch_factor); const int stat_tc = gsl_sf_taylorcoeff_e(N, 0.5*x, &tc_factor); const double p = pow(0.5*x,f); prefactor.val = tc_factor.val * p / poch_factor.val; prefactor.err = tc_factor.err * p / poch_factor.val; prefactor.err += fabs(prefactor.val) / poch_factor.val * poch_factor.err; prefactor.err += 2.0 * GSL_DBL_EPSILON * fabs(prefactor.val); stat_pre = GSL_ERROR_SELECT_2(stat_tc, stat_poch); } else { gsl_sf_result lg; const int stat_lg = gsl_sf_lngamma_e(nu+1.0, &lg); const double term1 = nu*log(0.5*x); const double term2 = lg.val; const double ln_pre = term1 - term2; const double ln_pre_err = GSL_DBL_EPSILON * (fabs(term1)+fabs(term2)) + lg.err; const int stat_ex = gsl_sf_exp_err_e(ln_pre, ln_pre_err, &prefactor); stat_pre = GSL_ERROR_SELECT_2(stat_ex, stat_lg); } /* Evaluate the sum. * [Abramowitz+Stegun, 9.1.10] * [Abramowitz+Stegun, 9.6.7] */ { const double y = sign * 0.25 * x*x; double sumk = 1.0; double term = 1.0; int k; for(k=1; k<=kmax; k++) { term *= y/((nu+k)*k); sumk += term; if(fabs(term/sumk) < threshold) break; } sum.val = sumk; sum.err = threshold * fabs(sumk); stat_sum = ( k >= kmax ? GSL_EMAXITER : GSL_SUCCESS ); } stat_mul = gsl_sf_multiply_err_e(prefactor.val, prefactor.err, sum.val, sum.err, result); return GSL_ERROR_SELECT_3(stat_mul, stat_pre, stat_sum); } } /* x >> nu*nu+1 * error ~ O( ((nu*nu+1)/x)^4 ) * * empirical error analysis: * choose GSL_ROOT4_MACH_EPS * x > (nu*nu + 1) * * This is not especially useful. When the argument gets * large enough for this to apply, the cos() and sin() * start loosing digits. However, this seems inevitable * for this particular method. * * Wed Jun 25 14:39:38 MDT 2003 [GJ] * This function was inconsistent since the Q term did not * go to relative order eps^2. That's why the error estimate * originally given was screwy (it didn't make sense that the * "empirical" error was coming out O(eps^3)). * With Q to proper order, the error is O(eps^4). */ int gsl_sf_bessel_Jnu_asympx_e(const double nu, const double x, gsl_sf_result * result) { double mu = 4.0*nu*nu; double mum1 = mu-1.0; double mum9 = mu-9.0; double mum25 = mu-25.0; double chi = x - (0.5*nu + 0.25)*M_PI; double P = 1.0 - mum1*mum9/(128.0*x*x); double Q = mum1/(8.0*x) * (1.0 - mum9*mum25/(384.0*x*x)); double pre = sqrt(2.0/(M_PI*x)); double c = cos(chi); double s = sin(chi); double r = mu/x; result->val = pre * (c*P - s*Q); result->err = pre * GSL_DBL_EPSILON * (1.0 + fabs(x)) * (fabs(c*P) + fabs(s*Q)); result->err += pre * fabs(0.1*r*r*r*r); return GSL_SUCCESS; } /* x >> nu*nu+1 */ int gsl_sf_bessel_Ynu_asympx_e(const double nu, const double x, gsl_sf_result * result) { double ampl; double theta; double alpha = x; double beta = -0.5*nu*M_PI; int stat_a = gsl_sf_bessel_asymp_Mnu_e(nu, x, &l); int stat_t = gsl_sf_bessel_asymp_thetanu_corr_e(nu, x, &theta); double sin_alpha = sin(alpha); double cos_alpha = cos(alpha); double sin_chi = sin(beta + theta); double cos_chi = cos(beta + theta); double sin_term = sin_alpha * cos_chi + sin_chi * cos_alpha; double sin_term_mag = fabs(sin_alpha * cos_chi) + fabs(sin_chi * cos_alpha); result->val = ampl * sin_term; result->err = fabs(ampl) * GSL_DBL_EPSILON * sin_term_mag; result->err += fabs(result->val) * 2.0 * GSL_DBL_EPSILON; if(fabs(alpha) > 1.0/GSL_DBL_EPSILON) { result->err *= 0.5 * fabs(alpha); } else if(fabs(alpha) > 1.0/GSL_SQRT_DBL_EPSILON) { result->err *= 256.0 * fabs(alpha) * GSL_SQRT_DBL_EPSILON; } return GSL_ERROR_SELECT_2(stat_t, stat_a); } /* x >> nu*nu+1 */ int gsl_sf_bessel_Inu_scaled_asympx_e(const double nu, const double x, gsl_sf_result * result) { double mu = 4.0*nu*nu; double mum1 = mu-1.0; double mum9 = mu-9.0; double pre = 1.0/sqrt(2.0*M_PI*x); double r = mu/x; result->val = pre * (1.0 - mum1/(8.0*x) + mum1*mum9/(128.0*x*x)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * fabs(0.1*r*r*r); return GSL_SUCCESS; } /* x >> nu*nu+1 */ int gsl_sf_bessel_Knu_scaled_asympx_e(const double nu, const double x, gsl_sf_result * result) { double mu = 4.0*nu*nu; double mum1 = mu-1.0; double mum9 = mu-9.0; double pre = sqrt(M_PI/(2.0*x)); double r = nu/x; result->val = pre * (1.0 + mum1/(8.0*x) + mum1*mum9/(128.0*x*x)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) + pre * fabs(0.1*r*r*r); return GSL_SUCCESS; } /* nu -> Inf; uniform in x > 0 [Abramowitz+Stegun, 9.7.7] * * error: * The error has the form u_N(t)/nu^N where 0 <= t <= 1. * It is not hard to show that |u_N(t)| is small for such t. * We have N=6 here, and |u_6(t)| < 0.025, so the error is clearly * bounded by 0.025/nu^6. This gives the asymptotic bound on nu * seen below as nu ~ 100. For general MACH_EPS it will be * nu > 0.5 / MACH_EPS^(1/6) * When t is small, the bound is even better because |u_N(t)| vanishes * as t->0. In fact u_N(t) ~ C t^N as t->0, with C ~= 0.1. * We write * err_N <= min(0.025, C(1/(1+(x/nu)^2))^3) / nu^6 * therefore * min(0.29/nu^2, 0.5/(nu^2+x^2)) < MACH_EPS^{1/3} * and this is the general form. * * empirical error analysis, assuming 14 digit requirement: * choose x > 50.000 nu ==> nu > 3 * choose x > 10.000 nu ==> nu > 15 * choose x > 2.000 nu ==> nu > 50 * choose x > 1.000 nu ==> nu > 75 * choose x > 0.500 nu ==> nu > 80 * choose x > 0.100 nu ==> nu > 83 * * This makes sense. For x << nu, the error will be of the form u_N(1)/nu^N, * since the polynomial term will be evaluated near t=1, so the bound * on nu will become constant for small x. Furthermore, increasing x with * nu fixed will decrease the error. */ int gsl_sf_bessel_Inu_scaled_asymp_unif_e(const double nu, const double x, gsl_sf_result * result) { int i; double z = x/nu; double root_term = hypot(1.0,z); double pre = 1.0/sqrt(2.0*M_PI*nu * root_term); double eta = root_term + log(z/(1.0+root_term)); double ex_arg = ( z < 1.0/GSL_ROOT3_DBL_EPSILON ? nu*(-z + eta) : -0.5*nu/z*(1.0 - 1.0/(12.0*z*z)) ); gsl_sf_result ex_result; int stat_ex = gsl_sf_exp_e(ex_arg, &ex_result); if(stat_ex == GSL_SUCCESS) { double t = 1.0/root_term; double sum; double tpow[16]; tpow[0] = 1.0; for(i=1; i<16; i++) tpow[i] = t * tpow[i-1]; sum = 1.0 + debye_u1(tpow)/nu + debye_u2(tpow)/(nu*nu) + debye_u3(tpow)/(nu*nu*nu) + debye_u4(tpow)/(nu*nu*nu*nu) + debye_u5(tpow)/(nu*nu*nu*nu*nu); result->val = pre * ex_result.val * sum; result->err = pre * ex_result.val / (nu*nu*nu*nu*nu*nu); result->err += pre * ex_result.err * fabs(sum); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = 0.0; result->err = 0.0; return stat_ex; } } /* nu -> Inf; uniform in x > 0 [Abramowitz+Stegun, 9.7.8] * * error: * identical to that above for Inu_scaled */ int gsl_sf_bessel_Knu_scaled_asymp_unif_e(const double nu, const double x, gsl_sf_result * result) { int i; double z = x/nu; double root_term = hypot(1.0,z); double pre = sqrt(M_PI/(2.0*nu*root_term)); double eta = root_term + log(z/(1.0+root_term)); double ex_arg = ( z < 1.0/GSL_ROOT3_DBL_EPSILON ? nu*(z - eta) : 0.5*nu/z*(1.0 + 1.0/(12.0*z*z)) ); gsl_sf_result ex_result; int stat_ex = gsl_sf_exp_e(ex_arg, &ex_result); if(stat_ex == GSL_SUCCESS) { double t = 1.0/root_term; double sum; double tpow[16]; tpow[0] = 1.0; for(i=1; i<16; i++) tpow[i] = t * tpow[i-1]; sum = 1.0 - debye_u1(tpow)/nu + debye_u2(tpow)/(nu*nu) - debye_u3(tpow)/(nu*nu*nu) + debye_u4(tpow)/(nu*nu*nu*nu) - debye_u5(tpow)/(nu*nu*nu*nu*nu); result->val = pre * ex_result.val * sum; result->err = pre * ex_result.err * fabs(sum); result->err += pre * ex_result.val / (nu*nu*nu*nu*nu*nu); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = 0.0; result->err = 0.0; return stat_ex; } } /* Evaluate J_mu(x),J_{mu+1}(x) and Y_mu(x),Y_{mu+1}(x) for |mu| < 1/2 */ int gsl_sf_bessel_JY_mu_restricted(const double mu, const double x, gsl_sf_result * Jmu, gsl_sf_result * Jmup1, gsl_sf_result * Ymu, gsl_sf_result * Ymup1) { /* CHECK_POINTER(Jmu) */ /* CHECK_POINTER(Jmup1) */ /* CHECK_POINTER(Ymu) */ /* CHECK_POINTER(Ymup1) */ if(x < 0.0 || fabs(mu) > 0.5) { Jmu->val = 0.0; Jmu->err = 0.0; Jmup1->val = 0.0; Jmup1->err = 0.0; Ymu->val = 0.0; Ymu->err = 0.0; Ymup1->val = 0.0; Ymup1->err = 0.0; GSL_ERROR ("error", GSL_EDOM); } else if(x == 0.0) { if(mu == 0.0) { Jmu->val = 1.0; Jmu->err = 0.0; } else { Jmu->val = 0.0; Jmu->err = 0.0; } Jmup1->val = 0.0; Jmup1->err = 0.0; Ymu->val = 0.0; Ymu->err = 0.0; Ymup1->val = 0.0; Ymup1->err = 0.0; GSL_ERROR ("error", GSL_EDOM); } else { int stat_Y; int stat_J; if(x < 2.0) { /* Use Taylor series for J and the Temme series for Y. * The Taylor series for J requires nu > 0, so we shift * up one and use the recursion relation to get Jmu, in * case mu < 0. */ gsl_sf_result Jmup2; int stat_J1 = gsl_sf_bessel_IJ_taylor_e(mu+1.0, x, -1, 100, GSL_DBL_EPSILON, Jmup1); int stat_J2 = gsl_sf_bessel_IJ_taylor_e(mu+2.0, x, -1, 100, GSL_DBL_EPSILON, &Jmup2); double c = 2.0*(mu+1.0)/x; Jmu->val = c * Jmup1->val - Jmup2.val; Jmu->err = c * Jmup1->err + Jmup2.err; Jmu->err += 2.0 * GSL_DBL_EPSILON * fabs(Jmu->val); stat_J = GSL_ERROR_SELECT_2(stat_J1, stat_J2); stat_Y = gsl_sf_bessel_Y_temme(mu, x, Ymu, Ymup1); return GSL_ERROR_SELECT_2(stat_J, stat_Y); } else if(x < 1000.0) { double P, Q; double J_ratio; double J_sgn; const int stat_CF1 = gsl_sf_bessel_J_CF1(mu, x, &J_ratio, &J_sgn); const int stat_CF2 = gsl_sf_bessel_JY_steed_CF2(mu, x, &P, &Q); double Jprime_J_ratio = mu/x - J_ratio; double gamma = (P - Jprime_J_ratio)/Q; Jmu->val = J_sgn * sqrt(2.0/(M_PI*x) / (Q + gamma*(P-Jprime_J_ratio))); Jmu->err = 4.0 * GSL_DBL_EPSILON * fabs(Jmu->val); Jmup1->val = J_ratio * Jmu->val; Jmup1->err = fabs(J_ratio) * Jmu->err; Ymu->val = gamma * Jmu->val; Ymu->err = fabs(gamma) * Jmu->err; Ymup1->val = Ymu->val * (mu/x - P - Q/gamma); Ymup1->err = Ymu->err * fabs(mu/x - P - Q/gamma) + 4.0*GSL_DBL_EPSILON*fabs(Ymup1->val); return GSL_ERROR_SELECT_2(stat_CF1, stat_CF2); } else { /* Use asymptotics for large argument. */ const int stat_J0 = gsl_sf_bessel_Jnu_asympx_e(mu, x, Jmu); const int stat_J1 = gsl_sf_bessel_Jnu_asympx_e(mu+1.0, x, Jmup1); const int stat_Y0 = gsl_sf_bessel_Ynu_asympx_e(mu, x, Ymu); const int stat_Y1 = gsl_sf_bessel_Ynu_asympx_e(mu+1.0, x, Ymup1); stat_J = GSL_ERROR_SELECT_2(stat_J0, stat_J1); stat_Y = GSL_ERROR_SELECT_2(stat_Y0, stat_Y1); return GSL_ERROR_SELECT_2(stat_J, stat_Y); } } } int gsl_sf_bessel_J_CF1(const double nu, const double x, double * ratio, double * sgn) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 10000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = x/(2.0*(nu+1.0)); double An = Anm1 + a1*Anm2; double Bn = Bnm1 + a1*Bnm2; double an; double fn = An/Bn; double dn = a1; double s = 1.0; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = -x*x/(4.0*(nu+n-1.0)*(nu+n)); An = Anm1 + an*Anm2; Bn = Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; dn = 1.0 / (2.0*(nu+n)/x - dn); if(dn < 0.0) s = -s; if(fabs(del - 1.0) < 2.0*GSL_DBL_EPSILON) break; } *ratio = fn; *sgn = s; if(n >= maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /* Evaluate the continued fraction CF1 for J_{nu+1}/J_nu * using Gautschi (Euler) equivalent series. * This exhibits an annoying problem because the * a_k are not positive definite (in fact they are all negative). * There are cases when rho_k blows up. Example: nu=1,x=4. */ #if 0 int gsl_sf_bessel_J_CF1_ser(const double nu, const double x, double * ratio, double * sgn) { const int maxk = 20000; double tk = 1.0; double sum = 1.0; double rhok = 0.0; double dk = 0.0; double s = 1.0; int k; for(k=1; k 2 is a good cutoff. * Also requires |nu| < 1/2. */ int gsl_sf_bessel_K_scaled_steed_temme_CF2(const double nu, const double x, double * K_nu, double * K_nup1, double * Kp_nu) { const int maxiter = 10000; int i = 1; double bi = 2.0*(1.0 + x); double di = 1.0/bi; double delhi = di; double hi = di; double qi = 0.0; double qip1 = 1.0; double ai = -(0.25 - nu*nu); double a1 = ai; double ci = -ai; double Qi = -ai; double s = 1.0 + Qi*delhi; for(i=2; i<=maxiter; i++) { double dels; double tmp; ai -= 2.0*(i-1); ci = -ai*ci/i; tmp = (qi - bi*qip1)/ai; qi = qip1; qip1 = tmp; Qi += ci*qip1; bi += 2.0; di = 1.0/(bi + ai*di); delhi = (bi*di - 1.0) * delhi; hi += delhi; dels = Qi*delhi; s += dels; if(fabs(dels/s) < GSL_DBL_EPSILON) break; } hi *= -a1; *K_nu = sqrt(M_PI/(2.0*x)) / s; *K_nup1 = *K_nu * (nu + x + 0.5 - hi)/x; *Kp_nu = - *K_nup1 + nu/x * *K_nu; if(i == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } int gsl_sf_bessel_cos_pi4_e(double y, double eps, gsl_sf_result * result) { const double sy = sin(y); const double cy = cos(y); const double s = sy + cy; const double d = sy - cy; const double abs_sum = fabs(cy) + fabs(sy); double seps; double ceps; if(fabs(eps) < GSL_ROOT5_DBL_EPSILON) { const double e2 = eps*eps; seps = eps * (1.0 - e2/6.0 * (1.0 - e2/20.0)); ceps = 1.0 - e2/2.0 * (1.0 - e2/12.0); } else { seps = sin(eps); ceps = cos(eps); } result->val = (ceps * s - seps * d)/ M_SQRT2; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(ceps) + fabs(seps)) * abs_sum / M_SQRT2; /* Try to account for error in evaluation of sin(y), cos(y). * This is a little sticky because we don't really know * how the library routines are doing their argument reduction. * However, we will make a reasonable guess. * FIXME ? */ if(y > 1.0/GSL_DBL_EPSILON) { result->err *= 0.5 * y; } else if(y > 1.0/GSL_SQRT_DBL_EPSILON) { result->err *= 256.0 * y * GSL_SQRT_DBL_EPSILON; } return GSL_SUCCESS; } int gsl_sf_bessel_sin_pi4_e(double y, double eps, gsl_sf_result * result) { const double sy = sin(y); const double cy = cos(y); const double s = sy + cy; const double d = sy - cy; const double abs_sum = fabs(cy) + fabs(sy); double seps; double ceps; if(fabs(eps) < GSL_ROOT5_DBL_EPSILON) { const double e2 = eps*eps; seps = eps * (1.0 - e2/6.0 * (1.0 - e2/20.0)); ceps = 1.0 - e2/2.0 * (1.0 - e2/12.0); } else { seps = sin(eps); ceps = cos(eps); } result->val = (ceps * d + seps * s)/ M_SQRT2; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(ceps) + fabs(seps)) * abs_sum / M_SQRT2; /* Try to account for error in evaluation of sin(y), cos(y). * See above. * FIXME ? */ if(y > 1.0/GSL_DBL_EPSILON) { result->err *= 0.5 * y; } else if(y > 1.0/GSL_SQRT_DBL_EPSILON) { result->err *= 256.0 * y * GSL_SQRT_DBL_EPSILON; } return GSL_SUCCESS; } /************************************************************************ * * Asymptotic approximations 8.11.5, 8.12.5, and 8.42.7 from G.N.Watson, A Treatise on the Theory of Bessel Functions, 2nd Edition (Cambridge University Press, 1944). Higher terms in expansion for x near l given by Airey in Phil. Mag. 31, 520 (1916). This approximation is accurate to near 0.1% at the boundaries between the asymptotic regions; well away from the boundaries the accuracy is better than 10^{-5}. * * ************************************************************************/ #if 0 double besselJ_meissel(double nu, double x) { double beta = pow(nu, 0.325); double result; /* Fitted matching points. */ double llimit = 1.1 * beta; double ulimit = 1.3 * beta; double nu2 = nu * nu; if (nu < 5. && x < 1.) { /* Small argument and order. Use a Taylor expansion. */ int k; double xo2 = 0.5 * x; double gamfactor = pow(nu,nu) * exp(-nu) * sqrt(nu * 2. * M_PI) * (1. + 1./(12.*nu) + 1./(288.*nu*nu)); double prefactor = pow(xo2, nu) / gamfactor; double C[5]; C[0] = 1.; C[1] = -C[0] / (nu+1.); C[2] = -C[1] / (2.*(nu+2.)); C[3] = -C[2] / (3.*(nu+3.)); C[4] = -C[3] / (4.*(nu+4.)); result = 0.; for(k=0; k<5; k++) result += C[k] * pow(xo2, 2.*k); result *= prefactor; } else if(x < nu - llimit) { /* Small x region: x << l. */ double z = x / nu; double z2 = z*z; double rtomz2 = sqrt(1.-z2); double omz2_2 = (1.-z2)*(1.-z2); /* Calculate Meissel exponent. */ double term1 = 1./(24.*nu) * ((2.+3.*z2)/((1.-z2)*rtomz2) -2.); double term2 = - z2*(4. + z2)/(16.*nu2*(1.-z2)*omz2_2); double V_nu = term1 + term2; /* Calculate the harmless prefactor. */ double sterlingsum = 1. + 1./(12.*nu) + 1./(288*nu2); double harmless = 1. / (sqrt(rtomz2*2.*M_PI*nu) * sterlingsum); /* Calculate the logarithm of the nu dependent prefactor. */ double ln_nupre = rtomz2 + log(z) - log(1. + rtomz2); result = harmless * exp(nu*ln_nupre - V_nu); } else if(x < nu + ulimit) { /* Intermediate region 1: x near nu. */ double eps = 1.-nu/x; double eps_x = eps * x; double eps_x_2 = eps_x * eps_x; double xo6 = x/6.; double B[6]; static double gam[6] = {2.67894, 1.35412, 1., 0.89298, 0.902745, 1.}; static double sf[6] = {0.866025, 0.866025, 0., -0.866025, -0.866025, 0.}; /* Some terms are identically zero, because sf[] can be zero. * Some terms do not appear in the result. */ B[0] = 1.; B[1] = eps_x; /* B[2] = 0.5 * eps_x_2 - 1./20.; */ B[3] = eps_x * (eps_x_2/6. - 1./15.); B[4] = eps_x_2 * (eps_x_2 - 1.)/24. + 1./280.; /* B[5] = eps_x * (eps_x_2*(0.5*eps_x_2 - 1.)/60. + 43./8400.); */ result = B[0] * gam[0] * sf[0] / pow(xo6, 1./3.); result += B[1] * gam[1] * sf[1] / pow(xo6, 2./3.); result += B[3] * gam[3] * sf[3] / pow(xo6, 4./3.); result += B[4] * gam[4] * sf[4] / pow(xo6, 5./3.); result /= (3.*M_PI); } else { /* Region of very large argument. Use expansion * for x>>l, and we need not be very exacting. */ double secb = x/nu; double sec2b= secb*secb; double cotb = 1./sqrt(sec2b-1.); /* cotb=cot(beta) */ double beta = acos(nu/x); double trigarg = nu/cotb - nu*beta - 0.25 * M_PI; double cot3b = cotb * cotb * cotb; double cot6b = cot3b * cot3b; double sum1, sum2, expterm, prefactor, trigcos; sum1 = 2.0 + 3.0 * sec2b; trigarg -= sum1 * cot3b / (24.0 * nu); trigcos = cos(trigarg); sum2 = 4.0 + sec2b; expterm = sum2 * sec2b * cot6b / (16.0 * nu2); expterm = exp(-expterm); prefactor = sqrt(2. * cotb / (nu * M_PI)); result = prefactor * expterm * trigcos; } return result; } #endif sources_5316/external/gsl/gsl_sf__chebyshev.h0000644000176700017670000000227210707442037020166 0ustar paulpaul/* specfunc/chebyshev.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* data for a Chebyshev series over a given interval */ struct cheb_series_struct { double * c; /* coefficients */ int order; /* order of expansion */ double a; /* lower interval point */ double b; /* upper interval point */ int order_sp; /* effective single precision order */ }; typedef struct cheb_series_struct cheb_series; sources_5316/external/gsl/gsl_err__strerror.c0000664000176700017670000000651311723710247020247 0ustar paulpaul/* err/strerror.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" const char * gsl_strerror (const int gsl_errno) { switch (gsl_errno) { case GSL_SUCCESS: return "success" ; case GSL_FAILURE: return "failure" ; case GSL_CONTINUE: return "the iteration has not converged yet"; case GSL_EDOM: return "input domain error" ; case GSL_ERANGE: return "output range error" ; case GSL_EFAULT: return "invalid pointer" ; case GSL_EINVAL: return "invalid argument supplied by user" ; case GSL_EFAILED: return "generic failure" ; case GSL_EFACTOR: return "factorization failed" ; case GSL_ESANITY: return "sanity check failed - shouldn't happen" ; case GSL_ENOMEM: return "malloc failed" ; case GSL_EBADFUNC: return "problem with user-supplied function"; case GSL_ERUNAWAY: return "iterative process is out of control"; case GSL_EMAXITER: return "exceeded max number of iterations" ; case GSL_EZERODIV: return "tried to divide by zero" ; case GSL_EBADTOL: return "specified tolerance is invalid or theoretically unattainable" ; case GSL_ETOL: return "failed to reach the specified tolerance" ; case GSL_EUNDRFLW: return "underflow" ; case GSL_EOVRFLW: return "overflow" ; case GSL_ELOSS: return "loss of accuracy" ; case GSL_EROUND: return "roundoff error" ; case GSL_EBADLEN: return "matrix/vector sizes are not conformant" ; case GSL_ENOTSQR: return "matrix not square" ; case GSL_ESING: return "singularity or extremely bad function behavior detected" ; case GSL_EDIVERGE: return "integral or series is divergent" ; case GSL_EUNSUP: return "the required feature is not supported by this hardware platform"; case GSL_EUNIMPL: return "the requested feature is not (yet) implemented"; case GSL_ECACHE: return "cache limit exceeded"; case GSL_ETABLE: return "table limit exceeded"; case GSL_ENOPROG: return "iteration is not making progress towards solution"; case GSL_ENOPROGJ: return "jacobian evaluations are not improving the solution"; case GSL_ETOLF: return "cannot reach the specified tolerance in F"; case GSL_ETOLX: return "cannot reach the specified tolerance in X"; case GSL_ETOLG: return "cannot reach the specified tolerance in gradient"; case GSL_EOF: return "end of file"; default: return "unknown error code" ; } } sources_5316/external/gsl/gsl_histogram.h0000664000176700017670000001005411705263724017356 0ustar paulpaul/* histogram/gsl_histogram.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_HISTOGRAM_H__ #define __GSL_HISTOGRAM_H__ #include #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t n ; double * range ; double * bin ; } gsl_histogram ; typedef struct { size_t n ; double * range ; double * sum ; } gsl_histogram_pdf ; gsl_histogram * gsl_histogram_alloc (size_t n); gsl_histogram * gsl_histogram_calloc (size_t n); gsl_histogram * gsl_histogram_calloc_uniform (const size_t n, const double xmin, const double xmax); void gsl_histogram_free (gsl_histogram * h); int gsl_histogram_increment (gsl_histogram * h, double x); int gsl_histogram_accumulate (gsl_histogram * h, double x, double weight); int gsl_histogram_find (const gsl_histogram * h, const double x, size_t * i); double gsl_histogram_get (const gsl_histogram * h, size_t i); int gsl_histogram_get_range (const gsl_histogram * h, size_t i, double * lower, double * upper); double gsl_histogram_max (const gsl_histogram * h); double gsl_histogram_min (const gsl_histogram * h); size_t gsl_histogram_bins (const gsl_histogram * h); void gsl_histogram_reset (gsl_histogram * h); gsl_histogram * gsl_histogram_calloc_range(size_t n, double * range); int gsl_histogram_set_ranges (gsl_histogram * h, const double range[], size_t size); int gsl_histogram_set_ranges_uniform (gsl_histogram * h, double xmin, double xmax); int gsl_histogram_memcpy(gsl_histogram * dest, const gsl_histogram * source); gsl_histogram * gsl_histogram_clone(const gsl_histogram * source); double gsl_histogram_max_val (const gsl_histogram * h); size_t gsl_histogram_max_bin (const gsl_histogram * h); double gsl_histogram_min_val (const gsl_histogram * h); size_t gsl_histogram_min_bin (const gsl_histogram * h); int gsl_histogram_equal_bins_p(const gsl_histogram *h1, const gsl_histogram *h2); int gsl_histogram_add(gsl_histogram *h1, const gsl_histogram *h2); int gsl_histogram_sub(gsl_histogram *h1, const gsl_histogram *h2); int gsl_histogram_mul(gsl_histogram *h1, const gsl_histogram *h2); int gsl_histogram_div(gsl_histogram *h1, const gsl_histogram *h2); int gsl_histogram_scale(gsl_histogram *h, double scale); int gsl_histogram_shift (gsl_histogram * h, double shift); double gsl_histogram_sigma (const gsl_histogram * h); double gsl_histogram_mean (const gsl_histogram * h); double gsl_histogram_sum (const gsl_histogram * h); int gsl_histogram_fwrite (FILE * stream, const gsl_histogram * h) ; int gsl_histogram_fread (FILE * stream, gsl_histogram * h); int gsl_histogram_fprintf (FILE * stream, const gsl_histogram * h, const char * range_format, const char * bin_format); int gsl_histogram_fscanf (FILE * stream, gsl_histogram * h); gsl_histogram_pdf * gsl_histogram_pdf_alloc (const size_t n); int gsl_histogram_pdf_init (gsl_histogram_pdf * p, const gsl_histogram * h); void gsl_histogram_pdf_free (gsl_histogram_pdf * p); double gsl_histogram_pdf_sample (const gsl_histogram_pdf * p, double r); __END_DECLS #endif /* __GSL_HISTOGRAM_H__ */ sources_5316/external/gsl/gsl_cblas__source_axpy_r.h0000664000176700017670000000251711705263724021553 0ustar paulpaul/* blas/source_axpy_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i; if (alpha == 0.0) { return; } if (incX == 1 && incY == 1) { const INDEX m = N % 4; for (i = 0; i < m; i++) { Y[i] += alpha * X[i]; } for (i = m; i + 3 < N; i += 4) { Y[i] += alpha * X[i]; Y[i + 1] += alpha * X[i + 1]; Y[i + 2] += alpha * X[i + 2]; Y[i + 3] += alpha * X[i + 3]; } } else { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { Y[iy] += alpha * X[ix]; ix += incX; iy += incY; } } } sources_5316/external/gsl/gsl_rng__ranlxd.c0000664000176700017670000001321511723710247017650 0ustar paulpaul/* rng/ranlxd.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is an implementation of Martin Luescher's second generation double-precision (48-bit) version of the RANLUX generator. Thanks to Martin Luescher for providing information on this generator. */ static inline unsigned long int ranlxd_get (void *vstate); static double ranlxd_get_double (void *vstate); static void ranlxd_set_lux (void *state, unsigned long int s, unsigned int luxury); static void ranlxd1_set (void *state, unsigned long int s); static void ranlxd2_set (void *state, unsigned long int s); static const int next[12] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0}; static const double one_bit = 1.0 / 281474976710656.0; /* 1/2^48 */ #define RANLUX_STEP(x1,x2,i1,i2,i3) \ x1=xdbl[i1] - xdbl[i2]; \ if (x2 < 0) \ { \ x1-=one_bit; \ x2+=1; \ } \ xdbl[i3]=x2 typedef struct { double xdbl[12]; double carry; unsigned int ir; unsigned int jr; unsigned int ir_old; unsigned int pr; } ranlxd_state_t; static inline void increment_state (ranlxd_state_t * state); static inline void increment_state (ranlxd_state_t * state) { int k, kmax; double y1, y2, y3; double *xdbl = state->xdbl; double carry = state->carry; unsigned int ir = state->ir; unsigned int jr = state->jr; for (k = 0; ir > 0; ++k) { y1 = xdbl[jr] - xdbl[ir]; y2 = y1 - carry; if (y2 < 0) { carry = one_bit; y2 += 1; } else { carry = 0; } xdbl[ir] = y2; ir = next[ir]; jr = next[jr]; } kmax = state->pr - 12; for (; k <= kmax; k += 12) { y1 = xdbl[7] - xdbl[0]; y1 -= carry; RANLUX_STEP (y2, y1, 8, 1, 0); RANLUX_STEP (y3, y2, 9, 2, 1); RANLUX_STEP (y1, y3, 10, 3, 2); RANLUX_STEP (y2, y1, 11, 4, 3); RANLUX_STEP (y3, y2, 0, 5, 4); RANLUX_STEP (y1, y3, 1, 6, 5); RANLUX_STEP (y2, y1, 2, 7, 6); RANLUX_STEP (y3, y2, 3, 8, 7); RANLUX_STEP (y1, y3, 4, 9, 8); RANLUX_STEP (y2, y1, 5, 10, 9); RANLUX_STEP (y3, y2, 6, 11, 10); if (y3 < 0) { carry = one_bit; y3 += 1; } else { carry = 0; } xdbl[11] = y3; } kmax = state->pr; for (; k < kmax; ++k) { y1 = xdbl[jr] - xdbl[ir]; y2 = y1 - carry; if (y2 < 0) { carry = one_bit; y2 += 1; } else { carry = 0; } xdbl[ir] = y2; ir = next[ir]; jr = next[jr]; } state->ir = ir; state->ir_old = ir; state->jr = jr; state->carry = carry; } static inline unsigned long int ranlxd_get (void *vstate) { return ranlxd_get_double (vstate) * 4294967296.0; /* 2^32 */ } static double ranlxd_get_double (void *vstate) { ranlxd_state_t *state = (ranlxd_state_t *) vstate; int ir = state->ir; state->ir = next[ir]; if (state->ir == state->ir_old) increment_state (state); return state->xdbl[state->ir]; } static void ranlxd_set_lux (void *vstate, unsigned long int s, unsigned int luxury) { ranlxd_state_t *state = (ranlxd_state_t *) vstate; int ibit, jbit, i, k, l, xbit[31]; double x, y; long int seed; if (s == 0) s = 1; /* default seed is 1 */ seed = s; i = seed & 0xFFFFFFFFUL; for (k = 0; k < 31; ++k) { xbit[k] = i % 2; i /= 2; } ibit = 0; jbit = 18; for (k = 0; k < 12; ++k) { x = 0; for (l = 1; l <= 48; ++l) { y = (double) ((xbit[ibit] + 1) % 2); x += x + y; xbit[ibit] = (xbit[ibit] + xbit[jbit]) % 2; ibit = (ibit + 1) % 31; jbit = (jbit + 1) % 31; } state->xdbl[k] = one_bit * x; } state->carry = 0; state->ir = 11; state->jr = 7; state->ir_old = 0; state->pr = luxury; } static void ranlxd1_set (void *vstate, unsigned long int s) { ranlxd_set_lux (vstate, s, 202); } static void ranlxd2_set (void *vstate, unsigned long int s) { ranlxd_set_lux (vstate, s, 397); } static const gsl_rng_type ranlxd1_type = {"ranlxd1", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ranlxd_state_t), &ranlxd1_set, &ranlxd_get, &ranlxd_get_double}; static const gsl_rng_type ranlxd2_type = {"ranlxd2", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ranlxd_state_t), &ranlxd2_set, &ranlxd_get, &ranlxd_get_double}; const gsl_rng_type *gsl_rng_ranlxd1 = &ranlxd1_type; const gsl_rng_type *gsl_rng_ranlxd2 = &ranlxd2_type; sources_5316/external/gsl/gsl_block__block_source.c0000664000176700017670000000175611723710247021345 0ustar paulpaul/* block/block_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ size_t FUNCTION(gsl_block,size) (const TYPE(gsl_block) * b) { return b->size ; } ATOMIC * FUNCTION(gsl_block,data) (const TYPE(gsl_block) * b) { return b->data ; } sources_5316/external/gsl/gsl_matrix__prop_source.c0000664000176700017670000000547211723710247021444 0ustar paulpaul/* matrix/prop_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_matrix, isnull) (const TYPE (gsl_matrix) * m) { const size_t size1 = m->size1; const size_t size2 = m->size2; const size_t tda = m->tda ; size_t i, j, k; for (i = 0; i < size1 ; i++) { for (j = 0; j < size2; j++) { for (k = 0; k < MULTIPLICITY; k++) { if (m->data[(i * tda + j) * MULTIPLICITY + k] != 0.0) { return 0; } } } } return 1; } int FUNCTION (gsl_matrix, ispos) (const TYPE (gsl_matrix) * m) { const size_t size1 = m->size1; const size_t size2 = m->size2; const size_t tda = m->tda ; size_t i, j, k; for (i = 0; i < size1 ; i++) { for (j = 0; j < size2; j++) { for (k = 0; k < MULTIPLICITY; k++) { if (m->data[(i * tda + j) * MULTIPLICITY + k] <= 0.0) { return 0; } } } } return 1; } int FUNCTION (gsl_matrix, isneg) (const TYPE (gsl_matrix) * m) { const size_t size1 = m->size1; const size_t size2 = m->size2; const size_t tda = m->tda ; size_t i, j, k; for (i = 0; i < size1 ; i++) { for (j = 0; j < size2; j++) { for (k = 0; k < MULTIPLICITY; k++) { if (m->data[(i * tda + j) * MULTIPLICITY + k] >= 0.0) { return 0; } } } } return 1; } int FUNCTION (gsl_matrix, isnonneg) (const TYPE (gsl_matrix) * m) { const size_t size1 = m->size1; const size_t size2 = m->size2; const size_t tda = m->tda ; size_t i, j, k; for (i = 0; i < size1 ; i++) { for (j = 0; j < size2; j++) { for (k = 0; k < MULTIPLICITY; k++) { if (m->data[(i * tda + j) * MULTIPLICITY + k] < 0.0) { return 0; } } } } return 1; } sources_5316/external/gsl/gsl_histogram__copy2d.c0000664000176700017670000000447211723710247020774 0ustar paulpaul/* gsl_histogram2d_copy.c * Copyright (C) 2000 Simone Piccardi * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File gsl_histogram2d_copy.c: * Routine to copy a 2D histogram. * Need GSL library and header. * * Author: S. Piccardi * Jan. 2000 * ***************************************************************/ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_histogram2d.h" /* * gsl_histogram2d_copy: * copy the contents of an histogram into another */ int gsl_histogram2d_memcpy (gsl_histogram2d * dest, const gsl_histogram2d * src) { size_t nx = src->nx; size_t ny = src->ny; size_t i; if (dest->nx != src->nx || dest->ny != src->ny) { GSL_ERROR ("histograms have different sizes, cannot copy", GSL_EINVAL); } for (i = 0; i <= nx; i++) { dest->xrange[i] = src->xrange[i]; } for (i = 0; i <= ny; i++) { dest->yrange[i] = src->yrange[i]; } for (i = 0; i < nx * ny; i++) { dest->bin[i] = src->bin[i]; } return GSL_SUCCESS; } /* * gsl_histogram2d_duplicate: * duplicate an histogram creating * an identical new one */ gsl_histogram2d * gsl_histogram2d_clone (const gsl_histogram2d * src) { size_t nx = src->nx; size_t ny = src->ny; size_t i; gsl_histogram2d *h; h = gsl_histogram2d_calloc_range (nx, ny, src->xrange, src->yrange); if (h == 0) { GSL_ERROR_VAL ("failed to allocate space for histogram struct", GSL_ENOMEM, 0); } for (i = 0; i < nx * ny; i++) { h->bin[i] = src->bin[i]; } return h; } sources_5316/external/gsl/gsl_matrix_short.h0000664000176700017670000002677011705263724020120 0ustar paulpaul/* matrix/gsl_matrix_short.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_SHORT_H__ #define __GSL_MATRIX_SHORT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_short.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; short * data; gsl_block_short * block; int owner; } gsl_matrix_short; typedef struct { gsl_matrix_short matrix; } _gsl_matrix_short_view; typedef _gsl_matrix_short_view gsl_matrix_short_view; typedef struct { gsl_matrix_short matrix; } _gsl_matrix_short_const_view; typedef const _gsl_matrix_short_const_view gsl_matrix_short_const_view; /* Allocation */ gsl_matrix_short * gsl_matrix_short_alloc (const size_t n1, const size_t n2); gsl_matrix_short * gsl_matrix_short_calloc (const size_t n1, const size_t n2); gsl_matrix_short * gsl_matrix_short_alloc_from_block (gsl_block_short * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_short * gsl_matrix_short_alloc_from_matrix (gsl_matrix_short * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_short * gsl_vector_short_alloc_row_from_matrix (gsl_matrix_short * m, const size_t i); gsl_vector_short * gsl_vector_short_alloc_col_from_matrix (gsl_matrix_short * m, const size_t j); void gsl_matrix_short_free (gsl_matrix_short * m); /* Views */ _gsl_matrix_short_view gsl_matrix_short_submatrix (gsl_matrix_short * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_short_view gsl_matrix_short_row (gsl_matrix_short * m, const size_t i); _gsl_vector_short_view gsl_matrix_short_column (gsl_matrix_short * m, const size_t j); _gsl_vector_short_view gsl_matrix_short_diagonal (gsl_matrix_short * m); _gsl_vector_short_view gsl_matrix_short_subdiagonal (gsl_matrix_short * m, const size_t k); _gsl_vector_short_view gsl_matrix_short_superdiagonal (gsl_matrix_short * m, const size_t k); _gsl_vector_short_view gsl_matrix_short_subrow (gsl_matrix_short * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_short_view gsl_matrix_short_subcolumn (gsl_matrix_short * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_short_view gsl_matrix_short_view_array (short * base, const size_t n1, const size_t n2); _gsl_matrix_short_view gsl_matrix_short_view_array_with_tda (short * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_short_view gsl_matrix_short_view_vector (gsl_vector_short * v, const size_t n1, const size_t n2); _gsl_matrix_short_view gsl_matrix_short_view_vector_with_tda (gsl_vector_short * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_short_const_view gsl_matrix_short_const_submatrix (const gsl_matrix_short * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_short_const_view gsl_matrix_short_const_row (const gsl_matrix_short * m, const size_t i); _gsl_vector_short_const_view gsl_matrix_short_const_column (const gsl_matrix_short * m, const size_t j); _gsl_vector_short_const_view gsl_matrix_short_const_diagonal (const gsl_matrix_short * m); _gsl_vector_short_const_view gsl_matrix_short_const_subdiagonal (const gsl_matrix_short * m, const size_t k); _gsl_vector_short_const_view gsl_matrix_short_const_superdiagonal (const gsl_matrix_short * m, const size_t k); _gsl_vector_short_const_view gsl_matrix_short_const_subrow (const gsl_matrix_short * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_short_const_view gsl_matrix_short_const_subcolumn (const gsl_matrix_short * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_short_const_view gsl_matrix_short_const_view_array (const short * base, const size_t n1, const size_t n2); _gsl_matrix_short_const_view gsl_matrix_short_const_view_array_with_tda (const short * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_short_const_view gsl_matrix_short_const_view_vector (const gsl_vector_short * v, const size_t n1, const size_t n2); _gsl_matrix_short_const_view gsl_matrix_short_const_view_vector_with_tda (const gsl_vector_short * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ short gsl_matrix_short_get(const gsl_matrix_short * m, const size_t i, const size_t j); void gsl_matrix_short_set(gsl_matrix_short * m, const size_t i, const size_t j, const short x); short * gsl_matrix_short_ptr(gsl_matrix_short * m, const size_t i, const size_t j); const short * gsl_matrix_short_const_ptr(const gsl_matrix_short * m, const size_t i, const size_t j); void gsl_matrix_short_set_zero (gsl_matrix_short * m); void gsl_matrix_short_set_identity (gsl_matrix_short * m); void gsl_matrix_short_set_all (gsl_matrix_short * m, short x); int gsl_matrix_short_fread (FILE * stream, gsl_matrix_short * m) ; int gsl_matrix_short_fwrite (FILE * stream, const gsl_matrix_short * m) ; int gsl_matrix_short_fscanf (FILE * stream, gsl_matrix_short * m); int gsl_matrix_short_fprintf (FILE * stream, const gsl_matrix_short * m, const char * format); int gsl_matrix_short_memcpy(gsl_matrix_short * dest, const gsl_matrix_short * src); int gsl_matrix_short_swap(gsl_matrix_short * m1, gsl_matrix_short * m2); int gsl_matrix_short_swap_rows(gsl_matrix_short * m, const size_t i, const size_t j); int gsl_matrix_short_swap_columns(gsl_matrix_short * m, const size_t i, const size_t j); int gsl_matrix_short_swap_rowcol(gsl_matrix_short * m, const size_t i, const size_t j); int gsl_matrix_short_transpose (gsl_matrix_short * m); int gsl_matrix_short_transpose_memcpy (gsl_matrix_short * dest, const gsl_matrix_short * src); short gsl_matrix_short_max (const gsl_matrix_short * m); short gsl_matrix_short_min (const gsl_matrix_short * m); void gsl_matrix_short_minmax (const gsl_matrix_short * m, short * min_out, short * max_out); void gsl_matrix_short_max_index (const gsl_matrix_short * m, size_t * imax, size_t *jmax); void gsl_matrix_short_min_index (const gsl_matrix_short * m, size_t * imin, size_t *jmin); void gsl_matrix_short_minmax_index (const gsl_matrix_short * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_short_isnull (const gsl_matrix_short * m); int gsl_matrix_short_ispos (const gsl_matrix_short * m); int gsl_matrix_short_isneg (const gsl_matrix_short * m); int gsl_matrix_short_isnonneg (const gsl_matrix_short * m); int gsl_matrix_short_add (gsl_matrix_short * a, const gsl_matrix_short * b); int gsl_matrix_short_sub (gsl_matrix_short * a, const gsl_matrix_short * b); int gsl_matrix_short_mul_elements (gsl_matrix_short * a, const gsl_matrix_short * b); int gsl_matrix_short_div_elements (gsl_matrix_short * a, const gsl_matrix_short * b); int gsl_matrix_short_scale (gsl_matrix_short * a, const double x); int gsl_matrix_short_add_constant (gsl_matrix_short * a, const double x); int gsl_matrix_short_add_diagonal (gsl_matrix_short * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_short_get_row(gsl_vector_short * v, const gsl_matrix_short * m, const size_t i); int gsl_matrix_short_get_col(gsl_vector_short * v, const gsl_matrix_short * m, const size_t j); int gsl_matrix_short_set_row(gsl_matrix_short * m, const size_t i, const gsl_vector_short * v); int gsl_matrix_short_set_col(gsl_matrix_short * m, const size_t j, const gsl_vector_short * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline short gsl_matrix_short_get(const gsl_matrix_short * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_short_set(gsl_matrix_short * m, const size_t i, const size_t j, const short x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline short * gsl_matrix_short_ptr(gsl_matrix_short * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (short *) (m->data + (i * m->tda + j)) ; } extern inline const short * gsl_matrix_short_const_ptr(const gsl_matrix_short * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const short *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_SHORT_H__ */ sources_5316/external/gsl/gsl_ode-initval__gear1.c0000664000176700017670000001405311723710247021005 0ustar paulpaul/* ode-initval/gear1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Gear 1. This is the implicit Euler a.k.a backward Euler method. */ /* Author: G. Jungman */ /* Error estimation by step doubling, see eg. Ascher, U.M., Petzold, L.R., Computer methods for ordinary differential and differential-algebraic equations, SIAM, Philadelphia, 1998. The method is also described in eg. this reference. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" typedef struct { double *k; double *y0; double *y0_orig; double *y_onestep; } gear1_state_t; static void * gear1_alloc (size_t dim) { gear1_state_t *state = (gear1_state_t *) malloc (sizeof (gear1_state_t)); if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for gear1_state", GSL_ENOMEM); } state->k = (double *) malloc (dim * sizeof (double)); if (state->k == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for k", GSL_ENOMEM); } state->y0 = (double *) malloc (dim * sizeof (double)); if (state->y0 == 0) { free (state->k); free (state); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } state->y0_orig = (double *) malloc (dim * sizeof (double)); if (state->y0_orig == 0) { free (state->y0); free (state->k); free (state); GSL_ERROR_NULL ("failed to allocate space for y0_orig", GSL_ENOMEM); } state->y_onestep = (double *) malloc (dim * sizeof (double)); if (state->y_onestep == 0) { free (state->y0_orig); free (state->y0); free (state->k); free (state); GSL_ERROR_NULL ("failed to allocate space for y_onestep", GSL_ENOMEM); } return state; } static int gear1_step (double *y, gear1_state_t *state, const double h, const double t, const size_t dim, const gsl_odeiv_system *sys) { /* Makes an implicit Euler advance with step size h. y0 is the initial values of variables y. The implicit matrix equations to solve are: k = y0 + h * f(t + h, k) y = y0 + h * f(t + h, k) */ const int iter_steps = 3; int nu; size_t i; double *y0 = state->y0; double *k = state->k; /* Iterative solution of k = y0 + h * f(t + h, k) Note: This method does not check for convergence of the iterative solution! */ for (nu = 0; nu < iter_steps; nu++) { int s = GSL_ODEIV_FN_EVAL(sys, t + h, y, k); if (s != GSL_SUCCESS) { return s; } for (i=0; iy0; double *y0_orig = state->y0_orig; double *y_onestep = state->y_onestep; /* initialization */ DBL_MEMCPY(y0, y, dim); /* Save initial values for possible failures */ DBL_MEMCPY (y0_orig, y, dim); /* First traverse h with one step (save to y_onestep) */ DBL_MEMCPY (y_onestep, y, dim); { int s = gear1_step (y_onestep, state, h, t, dim, sys); if (s != GSL_SUCCESS) { return s; } } /* Then with two steps with half step length (save to y) */ { int s = gear1_step (y, state, h / 2.0, t, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } DBL_MEMCPY (y0, y, dim); { int s = gear1_step (y, state, h / 2.0, t + h / 2.0, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } /* Cleanup update */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } /* Error estimation */ for (i = 0; i < dim; i++) { yerr[i] = 4.0 * (y[i] - y_onestep[i]); } return GSL_SUCCESS; } static int gear1_reset (void *vstate, size_t dim) { gear1_state_t *state = (gear1_state_t *) vstate; DBL_ZERO_MEMSET (state->y_onestep, dim); DBL_ZERO_MEMSET (state->y0_orig, dim); DBL_ZERO_MEMSET (state->y0, dim); DBL_ZERO_MEMSET (state->k, dim); return GSL_SUCCESS; } static unsigned int gear1_order (void *vstate) { gear1_state_t *state = (gear1_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 1; } static void gear1_free (void *vstate) { gear1_state_t *state = (gear1_state_t *) vstate; free (state->y_onestep); free (state->y0_orig); free (state->y0); free (state->k); free (state); } static const gsl_odeiv_step_type gear1_type = { "gear1", /* name */ 0, /* can use dydt_in? */ 1, /* gives exact dydt_out? */ &gear1_alloc, &gear1_apply, &gear1_reset, &gear1_order, &gear1_free }; const gsl_odeiv_step_type *gsl_odeiv_step_gear1 = &gear1_type; sources_5316/external/gsl/gsl_fft__hc_pass_3.c0000664000176700017670000001235711723710247020221 0ustar paulpaul/* fft/hc_pass_3.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_halfcomplex,pass_3) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[]) { size_t i, j, k, k1, jump; size_t factor, q, m, product_1; ATOMIC tau = sqrt (3.0) / 2.0; i = 0; j = 0; factor = 3; m = n / factor; q = n / product; product_1 = product / factor; jump = (factor - 1) * q; for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 3 * k1 * q; const size_t from1 = from0 + 2 * q - 1; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC t1_real = 2 * z1_real; const ATOMIC t2_real = z0_real - z1_real; const ATOMIC t3_imag = 2 * tau * z1_imag; const size_t to0 = q * k1; const size_t to1 = to0 + m; const size_t to2 = to1 + m; VECTOR(out,ostride,to0) = z0_real + t1_real; VECTOR(out,ostride,to1) = t2_real - t3_imag; VECTOR(out,ostride,to2) = t2_real + t3_imag; } if (q == 1) return; for (k = 1; k < (q + 1) / 2; k++) { const ATOMIC w1_real = GSL_REAL(twiddle1[k - 1]); const ATOMIC w1_imag = GSL_IMAG(twiddle1[k - 1]); const ATOMIC w2_real = GSL_REAL(twiddle2[k - 1]); const ATOMIC w2_imag = GSL_IMAG(twiddle2[k - 1]); for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 3 * k1 * q + 2 * k - 1; const size_t from1 = from0 + 2 * q; const size_t from2 = 3 * k1 * q - 2 * k + 2 * q - 1; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC z2_imag = -VECTOR(in,istride,from2 + 1); /* compute x = W(3) z */ /* t1 = z1 + z2 */ const ATOMIC t1_real = z1_real + z2_real; const ATOMIC t1_imag = z1_imag + z2_imag; /* t2 = z0 - t1/2 */ const ATOMIC t2_real = z0_real - t1_real / 2.0; const ATOMIC t2_imag = z0_imag - t1_imag / 2.0; /* t3 = sin(pi/3)*(z1 - z2) */ const ATOMIC t3_real = tau * (z1_real - z2_real); const ATOMIC t3_imag = tau * (z1_imag - z2_imag); /* x0 = z0 + t1 */ const ATOMIC x0_real = z0_real + t1_real; const ATOMIC x0_imag = z0_imag + t1_imag; /* x1 = t2 + i t3 */ const ATOMIC x1_real = t2_real - t3_imag; const ATOMIC x1_imag = t2_imag + t3_real; /* x2 = t2 - i t3 */ const ATOMIC x2_real = t2_real + t3_imag; const ATOMIC x2_imag = t2_imag - t3_real; const size_t to0 = k1 * q + 2 * k - 1; const size_t to1 = to0 + m; const size_t to2 = to1 + m; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to0 + 1) = x0_imag; VECTOR(out,ostride,to1) = w1_real * x1_real - w1_imag * x1_imag; VECTOR(out,ostride,to1 + 1) = w1_imag * x1_real + w1_real * x1_imag; VECTOR(out,ostride,to2) = w2_real * x2_real - w2_imag * x2_imag; VECTOR(out,ostride,to2 + 1) = w2_imag * x2_real + w2_real * x2_imag; } } if (q % 2 == 1) return; for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 3 * k1 * q + q - 1; const size_t from1 = from0 + 2 * q; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC t1_real = z0_real - z1_real; const ATOMIC t2_real = 2 * tau * z0_imag; const ATOMIC x0_real = 2 * z0_real + z1_real; const ATOMIC x1_real = t1_real - t2_real; const ATOMIC x2_real = -t1_real - t2_real; const size_t to0 = k1 * q + q - 1; const size_t to1 = to0 + m; const size_t to2 = to1 + m; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to2) = x2_real; } return; } sources_5316/external/gsl/gsl_cblas__zdscal.c0000664000176700017670000000034511723710247020136 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zdscal (const int N, const double alpha, void *X, const int incX) { #define BASE double #include "gsl_cblas__source_scal_c_s.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__atanint.c0000664000176700017670000000573711723710247021050 0ustar paulpaul/* specfunc/atanint.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_mode.h" #include "gsl_sf_expint.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" static double atanint_data[21] = { 1.91040361296235937512, -0.4176351437656746940e-01, 0.275392550786367434e-02, -0.25051809526248881e-03, 0.2666981285121171e-04, -0.311890514107001e-05, 0.38833853132249e-06, -0.5057274584964e-07, 0.681225282949e-08, -0.94212561654e-09, 0.13307878816e-09, -0.1912678075e-10, 0.278912620e-11, -0.41174820e-12, 0.6142987e-13, -0.924929e-14, 0.140387e-14, -0.21460e-15, 0.3301e-16, -0.511e-17, 0.79e-18, }; static cheb_series atanint_cs = { atanint_data, 20, -1, 1, 10 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_atanint_e(const double x, gsl_sf_result * result) { const double ax = fabs(x); const double sgn = GSL_SIGN(x); /* CHECK_POINTER(result) */ if(ax == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 0.5*GSL_SQRT_DBL_EPSILON) { result->val = x; result->err = 0.0; return GSL_SUCCESS; } else if(ax <= 1.0) { const double t = 2.0 * (x*x - 0.5); gsl_sf_result result_c; cheb_eval_e(&atanint_cs, t, &result_c); result->val = x * result_c.val; result->err = x * result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(ax < 1.0/GSL_SQRT_DBL_EPSILON) { const double t = 2.0 * (1.0/(x*x) - 0.5); gsl_sf_result result_c; cheb_eval_e(&atanint_cs, t, &result_c); result->val = sgn * (0.5*M_PI*log(ax) + result_c.val/ax); result->err = result_c.err/ax + fabs(result->val*GSL_DBL_EPSILON); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = sgn * 0.5*M_PI*log(ax); result->err = 2.0 * fabs(result->val * GSL_DBL_EPSILON); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_atanint(const double x) { EVAL_RESULT(gsl_sf_atanint_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__dsymv.c0000664000176700017670000000062711723710247020023 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dsymv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *A, const int lda, const double *X, const int incX, const double beta, double *Y, const int incY) { #define BASE double #include "gsl_cblas__source_symv.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__zsymm.c0000664000176700017670000000067011723710247020036 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zsymm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc) { #define BASE double #include "gsl_cblas__source_symm_c.h" #undef BASE } sources_5316/external/gsl/gsl_ntuple__ntuple.c0000664000176700017670000001046611723710247020415 0ustar paulpaul/* histogram/ntuple.c * * Copyright (C) 2000 Simone Piccardi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Jan/2001 Modified by Brian Gough. Minor changes for GSL */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_ntuple.h" /* * gsl_ntuple_open: * Initialize an ntuple structure and create the related file */ gsl_ntuple * gsl_ntuple_create (char *filename, void *ntuple_data, size_t size) { gsl_ntuple *ntuple = (gsl_ntuple *)malloc (sizeof (gsl_ntuple)); if (ntuple == 0) { GSL_ERROR_VAL ("failed to allocate space for ntuple struct", GSL_ENOMEM, 0); } ntuple->ntuple_data = ntuple_data; ntuple->size = size; ntuple->file = fopen (filename, "wb"); if (ntuple->file == 0) { free (ntuple); GSL_ERROR_VAL ("unable to create ntuple file", GSL_EFAILED, 0); } return ntuple; } /* * gsl_ntuple_open: * Initialize an ntuple structure and open the related file */ gsl_ntuple * gsl_ntuple_open (char *filename, void *ntuple_data, size_t size) { gsl_ntuple *ntuple = (gsl_ntuple *)malloc (sizeof (gsl_ntuple)); if (ntuple == 0) { GSL_ERROR_VAL ("failed to allocate space for ntuple struct", GSL_ENOMEM, 0); } ntuple->ntuple_data = ntuple_data; ntuple->size = size; ntuple->file = fopen (filename, "rb"); if (ntuple->file == 0) { free (ntuple); GSL_ERROR_VAL ("unable to open ntuple file for reading", GSL_EFAILED, 0); } return ntuple; } /* * gsl_ntuple_write: * write to file a data row, must be used in a loop! */ int gsl_ntuple_write (gsl_ntuple * ntuple) { size_t nwrite; nwrite = fwrite (ntuple->ntuple_data, ntuple->size, 1, ntuple->file); if (nwrite != 1) { GSL_ERROR ("failed to write ntuple entry to file", GSL_EFAILED); } return GSL_SUCCESS; } /* the following function is a synonym for gsl_ntuple_write */ int gsl_ntuple_bookdata (gsl_ntuple * ntuple) { return gsl_ntuple_write (ntuple); } /* * gsl_ntuple_read: * read form file a data row, must be used in a loop! */ int gsl_ntuple_read (gsl_ntuple * ntuple) { size_t nread; nread = fread (ntuple->ntuple_data, ntuple->size, 1, ntuple->file); if (nread == 0 && feof(ntuple->file)) { return GSL_EOF; } if (nread != 1) { GSL_ERROR ("failed to read ntuple entry from file", GSL_EFAILED); } return GSL_SUCCESS; } /* * gsl_ntuple_project: * fill an histogram with an ntuple file contents, use * SelVal and SelFunc user defined functions to get * the value to book and the selection funtion */ #define EVAL(f,x) ((*((f)->function))(x,(f)->params)) int gsl_ntuple_project (gsl_histogram * h, gsl_ntuple * ntuple, gsl_ntuple_value_fn * value_func, gsl_ntuple_select_fn * select_func) { size_t nread; do { nread = fread (ntuple->ntuple_data, ntuple->size, 1, ntuple->file); if (nread == 0 && feof(ntuple->file)) { break ; } if (nread != 1) { GSL_ERROR ("failed to read ntuple for projection", GSL_EFAILED); } if (EVAL(select_func, ntuple->ntuple_data)) { gsl_histogram_increment (h, EVAL(value_func, ntuple->ntuple_data)); } } while (1); return GSL_SUCCESS; } /* * gsl_ntuple_close: * close the ntuple file and free the memory */ int gsl_ntuple_close (gsl_ntuple * ntuple) { int status = fclose (ntuple->file); if (status) { GSL_ERROR ("failed to close ntuple file", GSL_EFAILED); } free (ntuple); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_err__stream.c0000664000176700017670000000345411723710247017661 0ustar paulpaul/* err/stream.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include "gsl_errno.h" #include "gsl_message.h" FILE * gsl_stream = NULL ; gsl_stream_handler_t * gsl_stream_handler = NULL; void gsl_stream_printf (const char *label, const char *file, int line, const char *reason) { if (gsl_stream == NULL) { gsl_stream = stderr; } if (gsl_stream_handler) { (*gsl_stream_handler) (label, file, line, reason); return; } fprintf (gsl_stream, "gsl: %s:%d: %s: %s\n", file, line, label, reason); } gsl_stream_handler_t * gsl_set_stream_handler (gsl_stream_handler_t * new_handler) { gsl_stream_handler_t * previous_handler = gsl_stream_handler; gsl_stream_handler = new_handler; return previous_handler; } FILE * gsl_set_stream (FILE * new_stream) { FILE * previous_stream; if (gsl_stream == NULL) { gsl_stream = stderr; } previous_stream = gsl_stream; gsl_stream = new_stream; return previous_stream; } sources_5316/external/gsl/gsl_cblas__ddot.c0000664000176700017670000000052211723710247017605 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" double cblas_ddot (const int N, const double *X, const int incX, const double *Y, const int incY) { #define INIT_VAL 0.0 #define ACC_TYPE double #define BASE double #include "gsl_cblas__source_dot_r.h" #undef ACC_TYPE #undef BASE #undef INIT_VAL } sources_5316/external/gsl/gsl_cblas__source_hpr2.h0000664000176700017670000001036011705263724021117 0ustar paulpaul/* blas/source_hpr2.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (order == CblasColMajor) ? -1 : 1; INDEX i, j; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); if (alpha_real == 0.0 && alpha_imag == 0.0) return; if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE Xi_real = CONST_REAL(X, ix); const BASE Xi_imag = CONST_IMAG(X, ix); /* tmp1 = alpha Xi */ const BASE tmp1_real = alpha_real * Xi_real - alpha_imag * Xi_imag; const BASE tmp1_imag = alpha_imag * Xi_real + alpha_real * Xi_imag; const BASE Yi_real = CONST_REAL(Y, iy); const BASE Yi_imag = CONST_IMAG(Y, iy); /* tmp2 = conj(alpha) Yi */ const BASE tmp2_real = alpha_real * Yi_real + alpha_imag * Yi_imag; const BASE tmp2_imag = -alpha_imag * Yi_real + alpha_real * Yi_imag; INDEX jx = ix + incX; INDEX jy = iy + incY; /* Aij = alpha*Xi*conj(Yj) + conj(alpha)*Yi*conj(Xj) */ REAL(Ap, TPUP(N, i, i)) += 2 * (tmp1_real * Yi_real + tmp1_imag * Yi_imag); IMAG(Ap, TPUP(N, i, i)) = 0; for (j = i + 1; j < N; j++) { const BASE Xj_real = CONST_REAL(X, jx); const BASE Xj_imag = CONST_IMAG(X, jx); const BASE Yj_real = CONST_REAL(Y, jy); const BASE Yj_imag = CONST_IMAG(Y, jy); REAL(Ap, TPUP(N, i, j)) += ((tmp1_real * Yj_real + tmp1_imag * Yj_imag) + (tmp2_real * Xj_real + tmp2_imag * Xj_imag)); IMAG(Ap, TPUP(N, i, j)) += conj * ((tmp1_imag * Yj_real - tmp1_real * Yj_imag) + (tmp2_imag * Xj_real - tmp2_real * Xj_imag)); jx += incX; jy += incY; } ix += incX; iy += incY; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE Xi_real = CONST_REAL(X, ix); const BASE Xi_imag = CONST_IMAG(X, ix); const BASE tmp1_real = alpha_real * Xi_real - alpha_imag * Xi_imag; const BASE tmp1_imag = alpha_imag * Xi_real + alpha_real * Xi_imag; const BASE Yi_real = CONST_REAL(Y, iy); const BASE Yi_imag = CONST_IMAG(Y, iy); const BASE tmp2_real = alpha_real * Yi_real + alpha_imag * Yi_imag; const BASE tmp2_imag = -alpha_imag * Yi_real + alpha_real * Yi_imag; INDEX jx = OFFSET(N, incX); INDEX jy = OFFSET(N, incY); /* Aij = alpha*Xi*conj(Yj) + conj(alpha)*Yi*conj(Xj) */ for (j = 0; j < i; j++) { const BASE Xj_real = CONST_REAL(X, jx); const BASE Xj_imag = CONST_IMAG(X, jx); const BASE Yj_real = CONST_REAL(Y, jy); const BASE Yj_imag = CONST_IMAG(Y, jy); REAL(Ap, TPLO(N, i, j)) += ((tmp1_real * Yj_real + tmp1_imag * Yj_imag) + (tmp2_real * Xj_real + tmp2_imag * Xj_imag)); IMAG(Ap, TPLO(N, i, j)) += conj * ((tmp1_imag * Yj_real - tmp1_real * Yj_imag) + (tmp2_imag * Xj_real - tmp2_real * Xj_imag)); jx += incX; jy += incY; } REAL(Ap, TPLO(N, i, i)) += 2 * (tmp1_real * Yi_real + tmp1_imag * Yi_imag); IMAG(Ap, TPLO(N, i, i)) = 0; ix += incX; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_ieee_utils.h0000664000176700017670000000523311705263724017513 0ustar paulpaul/* ieee-utils/gsl_ieee_utils.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_IEEE_UTILS_H__ #define __GSL_IEEE_UTILS_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS enum { GSL_IEEE_TYPE_NAN = 1, GSL_IEEE_TYPE_INF = 2, GSL_IEEE_TYPE_NORMAL = 3, GSL_IEEE_TYPE_DENORMAL = 4, GSL_IEEE_TYPE_ZERO = 5 } ; typedef struct { int sign ; char mantissa[24] ; /* Actual bits are 0..22, element 23 is \0 */ int exponent ; int type ; } gsl_ieee_float_rep ; typedef struct { int sign ; char mantissa[53] ; /* Actual bits are 0..51, element 52 is \0 */ int exponent ; int type ; } gsl_ieee_double_rep ; void gsl_ieee_printf_float (const float * x) ; void gsl_ieee_printf_double (const double * x) ; void gsl_ieee_fprintf_float (FILE * stream, const float * x) ; void gsl_ieee_fprintf_double (FILE * stream, const double * x) ; void gsl_ieee_float_to_rep (const float * x, gsl_ieee_float_rep * r) ; void gsl_ieee_double_to_rep (const double * x, gsl_ieee_double_rep * r) ; enum { GSL_IEEE_SINGLE_PRECISION = 1, GSL_IEEE_DOUBLE_PRECISION = 2, GSL_IEEE_EXTENDED_PRECISION = 3 } ; enum { GSL_IEEE_ROUND_TO_NEAREST = 1, GSL_IEEE_ROUND_DOWN = 2, GSL_IEEE_ROUND_UP = 3, GSL_IEEE_ROUND_TO_ZERO = 4 } ; enum { GSL_IEEE_MASK_INVALID = 1, GSL_IEEE_MASK_DENORMALIZED = 2, GSL_IEEE_MASK_DIVISION_BY_ZERO = 4, GSL_IEEE_MASK_OVERFLOW = 8, GSL_IEEE_MASK_UNDERFLOW = 16, GSL_IEEE_MASK_ALL = 31, GSL_IEEE_TRAP_INEXACT = 32 } ; void gsl_ieee_env_setup (void) ; int gsl_ieee_read_mode_string (const char * description, int * precision, int * rounding, int * exception_mask) ; int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) ; __END_DECLS #endif /* __GSL_IEEE_UTILS_H__ */ sources_5316/external/gsl/gsl_cblas__source_spmv.h0000664000176700017670000000531311705263724021233 0ustar paulpaul/* blas/source_spmv.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; if (alpha == 0.0 && beta == 1.0) return; /* form y := beta*y */ if (beta == 0.0) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { Y[iy] = 0.0; iy += incY; } } else if (beta != 1.0) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { Y[iy] *= beta; iy += incY; } } if (alpha == 0.0) return; /* form y := alpha*A*x + y */ if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { BASE tmp1 = alpha * X[ix]; BASE tmp2 = 0.0; const INDEX j_min = i + 1; const INDEX j_max = N; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; Y[iy] += tmp1 * Ap[TPUP(N, i, i)]; for (j = j_min; j < j_max; j++) { const BASE apk = Ap[TPUP(N, i, j)]; Y[jy] += tmp1 * apk; tmp2 += apk * X[jx]; jy += incY; jx += incX; } Y[iy] += alpha * tmp2; ix += incX; iy += incY; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { BASE tmp1 = alpha * X[ix]; BASE tmp2 = 0.0; const INDEX j_min = 0; const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; Y[iy] += tmp1 * Ap[TPLO(N, i, i)]; for (j = j_min; j < j_max; j++) { const BASE apk = Ap[TPLO(N, i, j)]; Y[jy] += tmp1 * apk; tmp2 += apk * X[jx]; jy += incY; jx += incX; } Y[iy] += alpha * tmp2; ix += incX; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_fft__dft.c0000664000176700017670000000075211723710247017130 0ustar paulpaul#include "gsl__config.h" #include #include #include #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_dft_complex.h" #include "gsl_dft_complex_float.h" #include "gsl_fft__complex_internal.h" #define BASE_DOUBLE #include "templates_on.h" #include "gsl_fft__dft_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_fft__dft_source.c" #include "templates_off.h" #undef BASE_FLOAT sources_5316/external/gsl/gsl_statistics__wkurtosis.c0000664000176700017670000000076311723710247022042 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__wkurtosis_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__wkurtosis_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__wkurtosis_source.c" #include "templates_off.h" #undef BASE_FLOAT sources_5316/external/gsl/gsl_ieee-utils__fp-darwin.c0000664000176700017670000000554211723710247021532 0ustar paulpaul/* ieee-utils/fp-darwin.c * * Copyright (C) 2001 Rodney Sparapani * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { ppc_fp_scr_t fp_scr = get_fp_scr() ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("powerpc only supports default precision rounding", GSL_EUNSUP); break ; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("powerpc only supports default precision rounding", GSL_EUNSUP); break ; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("powerpc only supports default precision rounding", GSL_EUNSUP); break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: fp_scr.rn = RN_NEAREST ; break ; case GSL_IEEE_ROUND_DOWN: fp_scr.rn = RN_TOWARD_MINUS ; break ; case GSL_IEEE_ROUND_UP: fp_scr.rn = RN_TOWARD_PLUS ; break ; case GSL_IEEE_ROUND_TO_ZERO: fp_scr.rn = RN_TOWARD_ZERO ; break ; default: fp_scr.rn = RN_NEAREST ; } if (exception_mask & GSL_IEEE_MASK_INVALID) fp_scr.ve = 0 ; //ve bit: invalid op exception enable if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("powerpc does not support the denormalized operand exception. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) fp_scr.ze = 0 ; //ze bit: zero divide exception enable if (exception_mask & GSL_IEEE_MASK_OVERFLOW) fp_scr.oe = 0 ; //oe bit: overflow exception enable if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) fp_scr.ue = 0 ; //ue bit: underflow exception enable if (exception_mask & GSL_IEEE_TRAP_INEXACT) { fp_scr.xe = 1 ; //xe bit: inexact exception enable } else { fp_scr.xe = 01 ; } set_fp_scr(fp_scr); return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_cblas__source_her2.h0000664000176700017670000001032211705263724021102 0ustar paulpaul/* blas/source_her2.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (order == CblasColMajor) ? -1 : 1; INDEX i, j; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); if (alpha_real == 0.0 && alpha_imag == 0.0) return; if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE Xi_real = CONST_REAL(X, ix); const BASE Xi_imag = CONST_IMAG(X, ix); /* tmp1 = alpha Xi */ const BASE tmp1_real = alpha_real * Xi_real - alpha_imag * Xi_imag; const BASE tmp1_imag = alpha_imag * Xi_real + alpha_real * Xi_imag; const BASE Yi_real = CONST_REAL(Y, iy); const BASE Yi_imag = CONST_IMAG(Y, iy); /* tmp2 = conj(alpha) Yi */ const BASE tmp2_real = alpha_real * Yi_real + alpha_imag * Yi_imag; const BASE tmp2_imag = -alpha_imag * Yi_real + alpha_real * Yi_imag; INDEX jx = ix + incX; INDEX jy = iy + incY; /* Aij = alpha*Xi*conj(Yj) + conj(alpha)*Yi*conj(Xj) */ REAL(A, lda * i + i) += 2 * (tmp1_real * Yi_real + tmp1_imag * Yi_imag); IMAG(A, lda * i + i) = 0; for (j = i + 1; j < N; j++) { const BASE Xj_real = CONST_REAL(X, jx); const BASE Xj_imag = CONST_IMAG(X, jx); const BASE Yj_real = CONST_REAL(Y, jy); const BASE Yj_imag = CONST_IMAG(Y, jy); REAL(A, lda * i + j) += ((tmp1_real * Yj_real + tmp1_imag * Yj_imag) + (tmp2_real * Xj_real + tmp2_imag * Xj_imag)); IMAG(A, lda * i + j) += conj * ((tmp1_imag * Yj_real - tmp1_real * Yj_imag) + (tmp2_imag * Xj_real - tmp2_real * Xj_imag)); jx += incX; jy += incY; } ix += incX; iy += incY; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE Xi_real = CONST_REAL(X, ix); const BASE Xi_imag = CONST_IMAG(X, ix); const BASE tmp1_real = alpha_real * Xi_real - alpha_imag * Xi_imag; const BASE tmp1_imag = alpha_imag * Xi_real + alpha_real * Xi_imag; const BASE Yi_real = CONST_REAL(Y, iy); const BASE Yi_imag = CONST_IMAG(Y, iy); const BASE tmp2_real = alpha_real * Yi_real + alpha_imag * Yi_imag; const BASE tmp2_imag = -alpha_imag * Yi_real + alpha_real * Yi_imag; INDEX jx = OFFSET(N, incX); INDEX jy = OFFSET(N, incY); /* Aij = alpha*Xi*conj(Yj) + conj(alpha)*Yi*conj(Xj) */ for (j = 0; j < i; j++) { const BASE Xj_real = CONST_REAL(X, jx); const BASE Xj_imag = CONST_IMAG(X, jx); const BASE Yj_real = CONST_REAL(Y, jy); const BASE Yj_imag = CONST_IMAG(Y, jy); REAL(A, lda * i + j) += ((tmp1_real * Yj_real + tmp1_imag * Yj_imag) + (tmp2_real * Xj_real + tmp2_imag * Xj_imag)); IMAG(A, lda * i + j) += conj * ((tmp1_imag * Yj_real - tmp1_real * Yj_imag) + (tmp2_imag * Xj_real - tmp2_real * Xj_imag)); jx += incX; jy += incY; } REAL(A, lda * i + i) += 2 * (tmp1_real * Yi_real + tmp1_imag * Yi_imag); IMAG(A, lda * i + i) = 0; ix += incX; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_randist__gausstail.c0000664000176700017670000000513011723710247021227 0ustar paulpaul/* randist/gausstail.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_randist.h" #include "gsl_sf_erf.h" double gsl_ran_gaussian_tail (const gsl_rng * r, const double a, const double sigma) { /* Returns a gaussian random variable larger than a * This implementation does one-sided upper-tailed deviates. */ double s = a / sigma; if (s < 1) { /* For small s, use a direct rejection method. The limit s < 1 can be adjusted to optimise the overall efficiency */ double x; do { x = gsl_ran_gaussian (r, 1.0); } while (x < s); return x * sigma; } else { /* Use the "supertail" deviates from the last two steps * of Marsaglia's rectangle-wedge-tail method, as described * in Knuth, v2, 3rd ed, pp 123-128. (See also exercise 11, p139, * and the solution, p586.) */ double u, v, x; do { u = gsl_rng_uniform (r); do { v = gsl_rng_uniform (r); } while (v == 0.0); x = sqrt (s * s - 2 * log (v)); } while (x * u > s); return x * sigma; } } double gsl_ran_gaussian_tail_pdf (const double x, const double a, const double sigma) { if (x < a) { return 0; } else { double N, p; double u = x / sigma ; double f = gsl_sf_erfc (a / (sqrt (2.0) * sigma)); N = 0.5 * f; p = (1 / (N * sqrt (2 * M_PI) * sigma)) * exp (-u * u / 2); return p; } } double gsl_ran_ugaussian_tail (const gsl_rng * r, const double a) { return gsl_ran_gaussian_tail (r, a, 1.0) ; } double gsl_ran_ugaussian_tail_pdf (const double x, const double a) { return gsl_ran_gaussian_tail_pdf (x, a, 1.0) ; } sources_5316/external/gsl/gsl_block_complex_float.h0000664000176700017670000000477111705263724021400 0ustar paulpaul/* block/gsl_block_complex_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_COMPLEX_FLOAT_H__ #define __GSL_BLOCK_COMPLEX_FLOAT_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_complex_float_struct { size_t size; float *data; }; typedef struct gsl_block_complex_float_struct gsl_block_complex_float; gsl_block_complex_float *gsl_block_complex_float_alloc (const size_t n); gsl_block_complex_float *gsl_block_complex_float_calloc (const size_t n); void gsl_block_complex_float_free (gsl_block_complex_float * b); int gsl_block_complex_float_fread (FILE * stream, gsl_block_complex_float * b); int gsl_block_complex_float_fwrite (FILE * stream, const gsl_block_complex_float * b); int gsl_block_complex_float_fscanf (FILE * stream, gsl_block_complex_float * b); int gsl_block_complex_float_fprintf (FILE * stream, const gsl_block_complex_float * b, const char *format); int gsl_block_complex_float_raw_fread (FILE * stream, float * b, const size_t n, const size_t stride); int gsl_block_complex_float_raw_fwrite (FILE * stream, const float * b, const size_t n, const size_t stride); int gsl_block_complex_float_raw_fscanf (FILE * stream, float * b, const size_t n, const size_t stride); int gsl_block_complex_float_raw_fprintf (FILE * stream, const float * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_complex_float_size (const gsl_block_complex_float * b); float * gsl_block_complex_float_data (const gsl_block_complex_float * b); __END_DECLS #endif /* __GSL_BLOCK_COMPLEX_FLOAT_H__ */ sources_5316/external/gsl/gsl_ode-initval__bsimp.c0000664000176700017670000003276011723710247021125 0ustar paulpaul/* ode-initval/bsimp.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Bulirsch-Stoer Implicit */ /* Author: G. Jungman */ /* Bader-Deuflhard implicit extrapolative stepper. * [Numer. Math., 41, 373 (1983)] */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_linalg.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" #define SEQUENCE_COUNT 8 #define SEQUENCE_MAX 7 /* Bader-Deuflhard extrapolation sequence */ static const int bd_sequence[SEQUENCE_COUNT] = { 2, 6, 10, 14, 22, 34, 50, 70 }; typedef struct { gsl_matrix *d; /* workspace for extrapolation */ gsl_matrix *a_mat; /* workspace for linear system matrix */ gsl_permutation *p_vec; /* workspace for LU permutation */ double x[SEQUENCE_MAX]; /* workspace for extrapolation */ /* state info */ size_t k_current; size_t k_choice; double h_next; double eps; /* workspace for extrapolation step */ double *yp; double *y_save; double *yerr_save; double *y_extrap_save; double *y_extrap_sequence; double *extrap_work; double *dfdt; double *y_temp; double *delta_temp; double *weight; gsl_matrix *dfdy; /* workspace for the basic stepper */ double *rhs_temp; double *delta; /* order of last step */ size_t order; } bsimp_state_t; /* Compute weighting factor */ static void compute_weights (const double y[], double w[], size_t dim) { size_t i; for (i = 0; i < dim; i++) { double u = fabs(y[i]); w[i] = (u > 0.0) ? u : 1.0; } } /* Calculate a choice for the "order" of the method, using the * Deuflhard criteria. */ static size_t bsimp_deuf_kchoice (double eps, size_t dimension) { const double safety_f = 0.25; const double small_eps = safety_f * eps; double a_work[SEQUENCE_COUNT]; double alpha[SEQUENCE_MAX][SEQUENCE_MAX]; int i, k; a_work[0] = bd_sequence[0] + 1.0; for (k = 0; k < SEQUENCE_MAX; k++) { a_work[k + 1] = a_work[k] + bd_sequence[k + 1]; } for (i = 0; i < SEQUENCE_MAX; i++) { alpha[i][i] = 1.0; for (k = 0; k < i; k++) { const double tmp1 = a_work[k + 1] - a_work[i + 1]; const double tmp2 = (a_work[i + 1] - a_work[0] + 1.0) * (2 * k + 1); alpha[k][i] = pow (small_eps, tmp1 / tmp2); } } a_work[0] += dimension; for (k = 0; k < SEQUENCE_MAX; k++) { a_work[k + 1] = a_work[k] + bd_sequence[k + 1]; } for (k = 0; k < SEQUENCE_MAX - 1; k++) { if (a_work[k + 2] > a_work[k + 1] * alpha[k][k + 1]) break; } return k; } static void poly_extrap (gsl_matrix * d, const double x[], const unsigned int i_step, const double x_i, const double y_i[], double y_0[], double y_0_err[], double work[], const size_t dim) { size_t j, k; DBL_MEMCPY (y_0_err, y_i, dim); DBL_MEMCPY (y_0, y_i, dim); if (i_step == 0) { for (j = 0; j < dim; j++) { gsl_matrix_set (d, 0, j, y_i[j]); } } else { DBL_MEMCPY (work, y_i, dim); for (k = 0; k < i_step; k++) { double delta = 1.0 / (x[i_step - k - 1] - x_i); const double f1 = delta * x_i; const double f2 = delta * x[i_step - k - 1]; for (j = 0; j < dim; j++) { const double q_kj = gsl_matrix_get (d, k, j); gsl_matrix_set (d, k, j, y_0_err[j]); delta = work[j] - q_kj; y_0_err[j] = f1 * delta; work[j] = f2 * delta; y_0[j] += y_0_err[j]; } } for (j = 0; j < dim; j++) { gsl_matrix_set (d, i_step, j, y_0_err[j]); } } } /* Basic implicit Bulirsch-Stoer step. Divide the step h_total into * n_step smaller steps and do the Bader-Deuflhard semi-implicit * iteration. */ static int bsimp_step_local (void *vstate, size_t dim, const double t0, const double h_total, const unsigned int n_step, const double y[], const double yp[], const double dfdt[], const gsl_matrix * dfdy, double y_out[], const gsl_odeiv_system * sys) { bsimp_state_t *state = (bsimp_state_t *) vstate; gsl_matrix *const a_mat = state->a_mat; gsl_permutation *const p_vec = state->p_vec; double *const delta = state->delta; double *const y_temp = state->y_temp; double *const delta_temp = state->delta_temp; double *const rhs_temp = state->rhs_temp; double *const w = state->weight; gsl_vector_view y_temp_vec = gsl_vector_view_array (y_temp, dim); gsl_vector_view delta_temp_vec = gsl_vector_view_array (delta_temp, dim); gsl_vector_view rhs_temp_vec = gsl_vector_view_array (rhs_temp, dim); const double h = h_total / n_step; double t = t0 + h; double sum; /* This is the factor sigma referred to in equation 3.4 of the paper. A relative change in y exceeding sigma indicates a runaway behavior. According to the authors suitable values for sigma are >>1. I have chosen a value of 100*dim. BJG */ const double max_sum = 100.0 * dim; int signum, status; size_t i, j; size_t n_inter; /* Calculate the matrix for the linear system. */ for (i = 0; i < dim; i++) { for (j = 0; j < dim; j++) { gsl_matrix_set (a_mat, i, j, -h * gsl_matrix_get (dfdy, i, j)); } gsl_matrix_set (a_mat, i, i, gsl_matrix_get (a_mat, i, i) + 1.0); } /* LU decomposition for the linear system. */ gsl_linalg_LU_decomp (a_mat, p_vec, &signum); /* Compute weighting factors */ compute_weights (y, w, dim); /* Initial step. */ for (i = 0; i < dim; i++) { y_temp[i] = h * (yp[i] + h * dfdt[i]); } gsl_linalg_LU_solve (a_mat, p_vec, &y_temp_vec.vector, &delta_temp_vec.vector); sum = 0.0; for (i = 0; i < dim; i++) { const double di = delta_temp[i]; delta[i] = di; y_temp[i] = y[i] + di; sum += fabs(di) / w[i]; } if (sum > max_sum) { return GSL_EFAILED ; } /* Intermediate steps. */ status = GSL_ODEIV_FN_EVAL (sys, t, y_temp, y_out); if (status) { return status; } for (n_inter = 1; n_inter < n_step; n_inter++) { for (i = 0; i < dim; i++) { rhs_temp[i] = h * y_out[i] - delta[i]; } gsl_linalg_LU_solve (a_mat, p_vec, &rhs_temp_vec.vector, &delta_temp_vec.vector); sum = 0.0; for (i = 0; i < dim; i++) { delta[i] += 2.0 * delta_temp[i]; y_temp[i] += delta[i]; sum += fabs(delta[i]) / w[i]; } if (sum > max_sum) { return GSL_EFAILED ; } t += h; status = GSL_ODEIV_FN_EVAL (sys, t, y_temp, y_out); if (status) { return status; } } /* Final step. */ for (i = 0; i < dim; i++) { rhs_temp[i] = h * y_out[i] - delta[i]; } gsl_linalg_LU_solve (a_mat, p_vec, &rhs_temp_vec.vector, &delta_temp_vec.vector); sum = 0.0; for (i = 0; i < dim; i++) { y_out[i] = y_temp[i] + delta_temp[i]; sum += fabs(delta_temp[i]) / w[i]; } if (sum > max_sum) { return GSL_EFAILED ; } return GSL_SUCCESS; } static void * bsimp_alloc (size_t dim) { bsimp_state_t *state = (bsimp_state_t *) malloc (sizeof (bsimp_state_t)); state->d = gsl_matrix_alloc (SEQUENCE_MAX, dim); state->a_mat = gsl_matrix_alloc (dim, dim); state->p_vec = gsl_permutation_alloc (dim); state->yp = (double *) malloc (dim * sizeof (double)); state->y_save = (double *) malloc (dim * sizeof (double)); state->yerr_save = (double *) malloc (dim * sizeof (double)); state->y_extrap_save = (double *) malloc (dim * sizeof (double)); state->y_extrap_sequence = (double *) malloc (dim * sizeof (double)); state->extrap_work = (double *) malloc (dim * sizeof (double)); state->dfdt = (double *) malloc (dim * sizeof (double)); state->y_temp = (double *) malloc (dim * sizeof (double)); state->delta_temp = (double *) malloc (dim * sizeof(double)); state->weight = (double *) malloc (dim * sizeof(double)); state->dfdy = gsl_matrix_alloc (dim, dim); state->rhs_temp = (double *) malloc (dim * sizeof(double)); state->delta = (double *) malloc (dim * sizeof (double)); { size_t k_choice = bsimp_deuf_kchoice (GSL_SQRT_DBL_EPSILON, dim); /*FIXME: choice of epsilon? */ state->k_choice = k_choice; state->k_current = k_choice; state->order = 2 * k_choice; } state->h_next = -GSL_SQRT_DBL_MAX; return state; } /* Perform the basic semi-implicit extrapolation * step, of size h, at a Deuflhard determined order. */ static int bsimp_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { bsimp_state_t *state = (bsimp_state_t *) vstate; double *const x = state->x; double *const yp = state->yp; double *const y_save = state->y_save; double *const yerr_save = state->yerr_save; double *const y_extrap_sequence = state->y_extrap_sequence; double *const y_extrap_save = state->y_extrap_save; double *const extrap_work = state->extrap_work; double *const dfdt = state->dfdt; gsl_matrix *d = state->d; gsl_matrix *dfdy = state->dfdy; const double t_local = t; size_t i, k; if (h + t_local == t_local) { return GSL_EUNDRFLW; /* FIXME: error condition */ } DBL_MEMCPY (y_extrap_save, y, dim); /* Save inputs */ DBL_MEMCPY (y_save, y, dim); DBL_MEMCPY (yerr_save, yerr, dim); /* Evaluate the derivative. */ if (dydt_in != NULL) { DBL_MEMCPY (yp, dydt_in, dim); } else { int s = GSL_ODEIV_FN_EVAL (sys, t_local, y, yp); if (s != GSL_SUCCESS) { return s; } } /* Evaluate the Jacobian for the system. */ { int s = GSL_ODEIV_JA_EVAL (sys, t_local, y, dfdy->data, dfdt); if (s != GSL_SUCCESS) { return s; } } /* Make a series of refined extrapolations, * up to the specified maximum order, which * was calculated based on the Deuflhard * criterion upon state initialization. */ for (k = 0; k <= state->k_current; k++) { const unsigned int N = bd_sequence[k]; const double r = (h / N); const double x_k = r * r; int status = bsimp_step_local (state, dim, t_local, h, N, y_extrap_save, yp, dfdt, dfdy, y_extrap_sequence, sys); if (status == GSL_EFAILED) { /* If the local step fails, set the error to infinity in order to force a reduction in the step size */ for (i = 0; i < dim; i++) { yerr[i] = GSL_POSINF; } break; } else if (status != GSL_SUCCESS) { return status; } x[k] = x_k; poly_extrap (d, x, k, x_k, y_extrap_sequence, y, yerr, extrap_work, dim); } /* Evaluate dydt_out[]. */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { DBL_MEMCPY (y, y_save, dim); DBL_MEMCPY (yerr, yerr_save, dim); return s; } } return GSL_SUCCESS; } static unsigned int bsimp_order (void *vstate) { bsimp_state_t *state = (bsimp_state_t *) vstate; return state->order; } static int bsimp_reset (void *vstate, size_t dim) { bsimp_state_t *state = (bsimp_state_t *) vstate; state->h_next = 0; DBL_ZERO_MEMSET (state->yp, dim); return GSL_SUCCESS; } static void bsimp_free (void * vstate) { bsimp_state_t *state = (bsimp_state_t *) vstate; free (state->delta); free (state->rhs_temp); gsl_matrix_free (state->dfdy); free (state->weight); free (state->delta_temp); free (state->y_temp); free (state->dfdt); free (state->extrap_work); free (state->y_extrap_sequence); free (state->y_extrap_save); free (state->y_save); free (state->yerr_save); free (state->yp); gsl_permutation_free (state->p_vec); gsl_matrix_free (state->a_mat); gsl_matrix_free (state->d); free (state); } static const gsl_odeiv_step_type bsimp_type = { "bsimp", /* name */ 1, /* can use dydt_in */ 1, /* gives exact dydt_out */ &bsimp_alloc, &bsimp_apply, &bsimp_reset, &bsimp_order, &bsimp_free }; const gsl_odeiv_step_type *gsl_odeiv_step_bsimp = &bsimp_type; sources_5316/external/gsl/gsl_sf_mathieu.h0000664000176700017670000000754111705263724017514 0ustar paulpaul/* specfunc/gsl_sf_mathieu.h * * Copyright (C) 2002 Lowell Johnson * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Author: L. Johnson */ #ifndef __GSL_SF_MATHIEU_H__ #define __GSL_SF_MATHIEU_H__ #include "gsl_sf_result.h" #include "gsl_eigen.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS #define GSL_SF_MATHIEU_COEFF 100 typedef struct { size_t size; size_t even_order; size_t odd_order; int extra_values; double qa; /* allow for caching of results: not implemented yet */ double qb; /* allow for caching of results: not implemented yet */ double *aa; double *bb; double *dd; double *ee; double *tt; double *e2; double *zz; gsl_vector *eval; gsl_matrix *evec; gsl_eigen_symmv_workspace *wmat; } gsl_sf_mathieu_workspace; /* Compute an array of characteristic (eigen) values from the recurrence matrices for the Mathieu equations. */ int gsl_sf_mathieu_a_array(int order_min, int order_max, double qq, gsl_sf_mathieu_workspace *work, double result_array[]); int gsl_sf_mathieu_b_array(int order_min, int order_max, double qq, gsl_sf_mathieu_workspace *work, double result_array[]); /* Compute the characteristic value for a Mathieu function of order n and type ntype. */ int gsl_sf_mathieu_a(int order, double qq, gsl_sf_result *result); int gsl_sf_mathieu_b(int order, double qq, gsl_sf_result *result); /* Compute the Fourier coefficients for a Mathieu function. */ int gsl_sf_mathieu_a_coeff(int order, double qq, double aa, double coeff[]); int gsl_sf_mathieu_b_coeff(int order, double qq, double aa, double coeff[]); /* Allocate computational storage space for eigenvalue solution. */ gsl_sf_mathieu_workspace *gsl_sf_mathieu_alloc(const size_t nn, const double qq); void gsl_sf_mathieu_free(gsl_sf_mathieu_workspace *workspace); /* Compute an angular Mathieu function. */ int gsl_sf_mathieu_ce(int order, double qq, double zz, gsl_sf_result *result); int gsl_sf_mathieu_se(int order, double qq, double zz, gsl_sf_result *result); int gsl_sf_mathieu_ce_array(int nmin, int nmax, double qq, double zz, gsl_sf_mathieu_workspace *work, double result_array[]); int gsl_sf_mathieu_se_array(int nmin, int nmax, double qq, double zz, gsl_sf_mathieu_workspace *work, double result_array[]); /* Compute a radial Mathieu function. */ int gsl_sf_mathieu_Mc(int kind, int order, double qq, double zz, gsl_sf_result *result); int gsl_sf_mathieu_Ms(int kind, int order, double qq, double zz, gsl_sf_result *result); int gsl_sf_mathieu_Mc_array(int kind, int nmin, int nmax, double qq, double zz, gsl_sf_mathieu_workspace *work, double result_array[]); int gsl_sf_mathieu_Ms_array(int kind, int nmin, int nmax, double qq, double zz, gsl_sf_mathieu_workspace *work, double result_array[]); __END_DECLS #endif /* !__GSL_SF_MATHIEU_H__ */ sources_5316/external/gsl/gsl_cblas__ztpmv.c0000664000176700017670000000056111723710247020036 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ztpmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *Ap, void *X, const int incX) { #define BASE double #include "gsl_cblas__source_tpmv_c.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__icamax.c0000664000176700017670000000033411723710247020116 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" CBLAS_INDEX cblas_icamax (const int N, const void *X, const int incX) { #define BASE float #include "gsl_cblas__source_iamax_c.h" #undef BASE } sources_5316/external/gsl/gsl_roots__fsolver.c0000664000176700017670000000507211723710247020422 0ustar paulpaul/* roots/fsolver.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_roots.h" gsl_root_fsolver * gsl_root_fsolver_alloc (const gsl_root_fsolver_type * T) { gsl_root_fsolver * s = (gsl_root_fsolver *) malloc (sizeof (gsl_root_fsolver)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for root solver struct", GSL_ENOMEM, 0); }; s->state = malloc (T->size); if (s->state == 0) { free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for root solver state", GSL_ENOMEM, 0); }; s->type = T ; s->function = NULL ; return s; } int gsl_root_fsolver_set (gsl_root_fsolver * s, gsl_function * f, double x_lower, double x_upper) { if (x_lower > x_upper) { GSL_ERROR ("invalid interval (lower > upper)", GSL_EINVAL); } s->function = f; s->root = 0.5 * (x_lower + x_upper); /* initial estimate */ s->x_lower = x_lower; s->x_upper = x_upper; return (s->type->set) (s->state, s->function, &(s->root), x_lower, x_upper); } int gsl_root_fsolver_iterate (gsl_root_fsolver * s) { return (s->type->iterate) (s->state, s->function, &(s->root), &(s->x_lower), &(s->x_upper)); } void gsl_root_fsolver_free (gsl_root_fsolver * s) { free (s->state); free (s); } const char * gsl_root_fsolver_name (const gsl_root_fsolver * s) { return s->type->name; } double gsl_root_fsolver_root (const gsl_root_fsolver * s) { return s->root; } double gsl_root_fsolver_x_lower (const gsl_root_fsolver * s) { return s->x_lower; } double gsl_root_fsolver_x_upper (const gsl_root_fsolver * s) { return s->x_upper; } sources_5316/external/gsl/gsl_sort_int.h0000664000176700017670000000345611705263724017232 0ustar paulpaul/* sort/gsl_sort_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_INT_H__ #define __GSL_SORT_INT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_int (int * data, const size_t stride, const size_t n); void gsl_sort_int_index (size_t * p, const int * data, const size_t stride, const size_t n); int gsl_sort_int_smallest (int * dest, const size_t k, const int * src, const size_t stride, const size_t n); int gsl_sort_int_smallest_index (size_t * p, const size_t k, const int * src, const size_t stride, const size_t n); int gsl_sort_int_largest (int * dest, const size_t k, const int * src, const size_t stride, const size_t n); int gsl_sort_int_largest_index (size_t * p, const size_t k, const int * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_INT_H__ */ sources_5316/external/gsl/gsl_multiroots__dogleg.c0000664000176700017670000002257211723710247021262 0ustar paulpaul/* multiroots/dogleg.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl_multiroots__enorm.c" static void compute_diag (const gsl_matrix * J, gsl_vector * diag); static void update_diag (const gsl_matrix * J, gsl_vector * diag); static double compute_delta (gsl_vector * diag, gsl_vector * x); static void compute_df (const gsl_vector * f_trial, const gsl_vector * f, gsl_vector * df); static void compute_wv (const gsl_vector * qtdf, const gsl_vector *rdx, const gsl_vector *dx, const gsl_vector *diag, double pnorm, gsl_vector * w, gsl_vector * v); static double scaled_enorm (const gsl_vector * d, const gsl_vector * f); static double scaled_enorm (const gsl_vector * d, const gsl_vector * f) { double e2 = 0 ; size_t i, n = f->size ; for (i = 0; i < n ; i++) { double fi= gsl_vector_get(f, i); double di= gsl_vector_get(d, i); double u = di * fi; e2 += u * u ; } return sqrt(e2); } static double enorm_sum (const gsl_vector * a, const gsl_vector * b); static double enorm_sum (const gsl_vector * a, const gsl_vector * b) { double e2 = 0 ; size_t i, n = a->size ; for (i = 0; i < n ; i++) { double ai= gsl_vector_get(a, i); double bi= gsl_vector_get(b, i); double u = ai + bi; e2 += u * u ; } return sqrt(e2); } static void compute_wv (const gsl_vector * qtdf, const gsl_vector *rdx, const gsl_vector *dx, const gsl_vector *diag, double pnorm, gsl_vector * w, gsl_vector * v) { size_t i, n = qtdf->size; for (i = 0; i < n; i++) { double qtdfi = gsl_vector_get (qtdf, i); double rdxi = gsl_vector_get (rdx, i); double dxi = gsl_vector_get (dx, i); double diagi = gsl_vector_get (diag, i); gsl_vector_set (w, i, (qtdfi - rdxi) / pnorm); gsl_vector_set (v, i, diagi * diagi * dxi / pnorm); } } static void compute_df (const gsl_vector * f_trial, const gsl_vector * f, gsl_vector * df) { size_t i, n = f->size; for (i = 0; i < n; i++) { double dfi = gsl_vector_get (f_trial, i) - gsl_vector_get (f, i); gsl_vector_set (df, i, dfi); } } static void compute_diag (const gsl_matrix * J, gsl_vector * diag) { size_t i, j, n = diag->size; for (j = 0; j < n; j++) { double sum = 0; for (i = 0; i < n; i++) { double Jij = gsl_matrix_get (J, i, j); sum += Jij * Jij; } if (sum == 0) sum = 1.0; gsl_vector_set (diag, j, sqrt (sum)); } } static void update_diag (const gsl_matrix * J, gsl_vector * diag) { size_t i, j, n = diag->size; for (j = 0; j < n; j++) { double cnorm, diagj, sum = 0; for (i = 0; i < n; i++) { double Jij = gsl_matrix_get (J, i, j); sum += Jij * Jij; } if (sum == 0) sum = 1.0; cnorm = sqrt (sum); diagj = gsl_vector_get (diag, j); if (cnorm > diagj) gsl_vector_set (diag, j, cnorm); } } static double compute_delta (gsl_vector * diag, gsl_vector * x) { double Dx = scaled_enorm (diag, x); double factor = 100; return (Dx > 0) ? factor * Dx : factor; } static double compute_actual_reduction (double fnorm, double fnorm1) { double actred; if (fnorm1 < fnorm) { double u = fnorm1 / fnorm; actred = 1 - u * u; } else { actred = -1; } return actred; } static double compute_predicted_reduction (double fnorm, double fnorm1) { double prered; if (fnorm1 < fnorm) { double u = fnorm1 / fnorm; prered = 1 - u * u; } else { prered = 0; } return prered; } static void compute_qtf (const gsl_matrix * q, const gsl_vector * f, gsl_vector * qtf) { size_t i, j, N = f->size ; for (j = 0; j < N; j++) { double sum = 0; for (i = 0; i < N; i++) sum += gsl_matrix_get (q, i, j) * gsl_vector_get (f, i); gsl_vector_set (qtf, j, sum); } } static void compute_rdx (const gsl_matrix * r, const gsl_vector * dx, gsl_vector * rdx) { size_t i, j, N = dx->size ; for (i = 0; i < N; i++) { double sum = 0; for (j = i; j < N; j++) { sum += gsl_matrix_get (r, i, j) * gsl_vector_get (dx, j); } gsl_vector_set (rdx, i, sum); } } static void compute_trial_step (gsl_vector *x, gsl_vector * dx, gsl_vector * x_trial) { size_t i, N = x->size; for (i = 0; i < N; i++) { double pi = gsl_vector_get (dx, i); double xi = gsl_vector_get (x, i); gsl_vector_set (x_trial, i, xi + pi); } } static int newton_direction (const gsl_matrix * r, const gsl_vector * qtf, gsl_vector * p) { const size_t N = r->size2; size_t i; int status; status = gsl_linalg_R_solve (r, qtf, p); #ifdef DEBUG printf("rsolve status = %d\n", status); #endif for (i = 0; i < N; i++) { double pi = gsl_vector_get (p, i); gsl_vector_set (p, i, -pi); } return status; } static void gradient_direction (const gsl_matrix * r, const gsl_vector * qtf, const gsl_vector * diag, gsl_vector * g) { const size_t M = r->size1; const size_t N = r->size2; size_t i, j; for (j = 0; j < M; j++) { double sum = 0; double dj; for (i = 0; i < N; i++) { sum += gsl_matrix_get (r, i, j) * gsl_vector_get (qtf, i); } dj = gsl_vector_get (diag, j); gsl_vector_set (g, j, -sum / dj); } } static void minimum_step (double gnorm, const gsl_vector * diag, gsl_vector * g) { const size_t N = g->size; size_t i; for (i = 0; i < N; i++) { double gi = gsl_vector_get (g, i); double di = gsl_vector_get (diag, i); gsl_vector_set (g, i, (gi / gnorm) / di); } } static void compute_Rg (const gsl_matrix * r, const gsl_vector * gradient, gsl_vector * Rg) { const size_t N = r->size2; size_t i, j; for (i = 0; i < N; i++) { double sum = 0; for (j = i; j < N; j++) { double gj = gsl_vector_get (gradient, j); double rij = gsl_matrix_get (r, i, j); sum += rij * gj; } gsl_vector_set (Rg, i, sum); } } static void scaled_addition (double alpha, gsl_vector * newton, double beta, gsl_vector * gradient, gsl_vector * p) { const size_t N = p->size; size_t i; for (i = 0; i < N; i++) { double ni = gsl_vector_get (newton, i); double gi = gsl_vector_get (gradient, i); gsl_vector_set (p, i, alpha * ni + beta * gi); } } static int dogleg (const gsl_matrix * r, const gsl_vector * qtf, const gsl_vector * diag, double delta, gsl_vector * newton, gsl_vector * gradient, gsl_vector * p) { double qnorm, gnorm, sgnorm, bnorm, temp; newton_direction (r, qtf, newton); #ifdef DEBUG printf("newton = "); gsl_vector_fprintf(stdout, newton, "%g"); printf("\n"); #endif qnorm = scaled_enorm (diag, newton); if (qnorm <= delta) { gsl_vector_memcpy (p, newton); #ifdef DEBUG printf("took newton (qnorm = %g <= delta = %g)\n", qnorm, delta); #endif return GSL_SUCCESS; } gradient_direction (r, qtf, diag, gradient); #ifdef DEBUG printf("grad = "); gsl_vector_fprintf(stdout, gradient, "%g"); printf("\n"); #endif gnorm = enorm (gradient); if (gnorm == 0) { double alpha = delta / qnorm; double beta = 0; scaled_addition (alpha, newton, beta, gradient, p); #ifdef DEBUG printf("took scaled newton because gnorm = 0\n"); #endif return GSL_SUCCESS; } minimum_step (gnorm, diag, gradient); compute_Rg (r, gradient, p); /* Use p as temporary space to compute Rg */ #ifdef DEBUG printf("mingrad = "); gsl_vector_fprintf(stdout, gradient, "%g"); printf("\n"); printf("Rg = "); gsl_vector_fprintf(stdout, p, "%g"); printf("\n"); #endif temp = enorm (p); sgnorm = (gnorm / temp) / temp; if (sgnorm > delta) { double alpha = 0; double beta = delta; scaled_addition (alpha, newton, beta, gradient, p); #ifdef DEBUG printf("took gradient\n"); #endif return GSL_SUCCESS; } bnorm = enorm (qtf); { double bg = bnorm / gnorm; double bq = bnorm / qnorm; double dq = delta / qnorm; double dq2 = dq * dq; double sd = sgnorm / delta; double sd2 = sd * sd; double t1 = bg * bq * sd; double u = t1 - dq; double t2 = t1 - dq * sd2 + sqrt (u * u + (1-dq2) * (1 - sd2)); double alpha = dq * (1 - sd2) / t2; double beta = (1 - alpha) * sgnorm; #ifdef DEBUG printf("bnorm = %g\n", bnorm); printf("gnorm = %g\n", gnorm); printf("qnorm = %g\n", qnorm); printf("delta = %g\n", delta); printf("alpha = %g beta = %g\n", alpha, beta); printf("took scaled combination of newton and gradient\n"); #endif scaled_addition (alpha, newton, beta, gradient, p); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__dzasum.c0000664000176700017670000000032711723710247020161 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" double cblas_dzasum (const int N, const void *X, const int incX) { #define BASE double #include "gsl_cblas__source_asum_c.h" #undef BASE } sources_5316/external/gsl/gsl_ode-initval__gear2.c0000664000176700017670000002050311723710247021003 0ustar paulpaul/* ode-initval/gear2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Gear 2 */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_ode-initval__odeiv_util.h" #include "gsl_odeiv.h" /* gear2 state object */ typedef struct { int primed; /* flag indicating that yim1 is ready */ double t_primed; /* system was primed for this value of t */ double last_h; /* last step size */ gsl_odeiv_step *primer; /* stepper to use for priming */ double *yim1; /* y_{i-1} */ double *k; /* work space */ double *y0; /* work space */ double *y0_orig; double *y_onestep; int stutter; } gear2_state_t; static void * gear2_alloc (size_t dim) { gear2_state_t *state = (gear2_state_t *) malloc (sizeof (gear2_state_t)); if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for gear2_state", GSL_ENOMEM); } state->yim1 = (double *) malloc (dim * sizeof (double)); if (state->yim1 == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for yim1", GSL_ENOMEM); } state->k = (double *) malloc (dim * sizeof (double)); if (state->k == 0) { free (state->yim1); free (state); GSL_ERROR_NULL ("failed to allocate space for k", GSL_ENOMEM); } state->y0 = (double *) malloc (dim * sizeof (double)); if (state->y0 == 0) { free (state->k); free (state->yim1); free (state); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } state->y0_orig = (double *) malloc (dim * sizeof (double)); if (state->y0_orig == 0) { free (state->y0); free (state->k); free (state->yim1); free (state); GSL_ERROR_NULL ("failed to allocate space for y0_orig", GSL_ENOMEM); } state->y_onestep = (double *) malloc (dim * sizeof (double)); if (state->y_onestep == 0) { free (state->y0_orig); free (state->y0); free (state->k); free (state->yim1); free (state); GSL_ERROR_NULL ("failed to allocate space for y0_orig", GSL_ENOMEM); } state->primed = 0; state->primer = gsl_odeiv_step_alloc (gsl_odeiv_step_rk4imp, dim); if (state->primer == 0) { free (state->y_onestep); free (state->y0_orig); free (state->y0); free (state->k); free (state->yim1); free (state); GSL_ERROR_NULL ("failed to allocate space for primer", GSL_ENOMEM); } state->last_h = 0.0; return state; } static int gear2_step (double *y, gear2_state_t * state, const double h, const double t, const size_t dim, const gsl_odeiv_system * sys) { /* Makes a Gear2 advance with step size h. y0 is the initial values of variables y. The implicit matrix equations to solve are: k = y0 + h * f(t + h, k) y = y0 + h * f(t + h, k) */ const int iter_steps = 3; int nu; size_t i; double *y0 = state->y0; double *yim1 = state->yim1; double *k = state->k; /* Iterative solution of k = y0 + h * f(t + h, k) Note: This method does not check for convergence of the iterative solution! */ for (nu = 0; nu < iter_steps; nu++) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, k); if (s != GSL_SUCCESS) { return s; } for (i = 0; i < dim; i++) { y[i] = ((4.0 * y0[i] - yim1[i]) + 2.0 * h * k[i]) / 3.0; } } return GSL_SUCCESS; } static int gear2_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { gear2_state_t *state = (gear2_state_t *) vstate; state->stutter = 0; if (state->primed == 0 || t == state->t_primed || h != state->last_h) { /* Execute a single-step method to prime the process. Note that * we do this if the step size changes, so frequent step size * changes will cause the method to stutter. * * Note that we reuse this method if the time has not changed, * which can occur when the adaptive driver is attempting to find * an appropriate step-size on its first iteration */ int status; DBL_MEMCPY (state->yim1, y, dim); status = gsl_odeiv_step_apply (state->primer, t, h, y, yerr, dydt_in, dydt_out, sys); /* Make note of step size and indicate readiness for a Gear step. */ state->primed = 1; state->t_primed = t; state->last_h = h; state->stutter = 1; return status; } else { /* We have a previous y value in the buffer, and the step * sizes match, so we go ahead with the Gear step. */ double *const k = state->k; double *const y0 = state->y0; double *const y0_orig = state->y0_orig; double *const yim1 = state->yim1; double *y_onestep = state->y_onestep; int s; size_t i; DBL_MEMCPY (y0, y, dim); /* iterative solution */ if (dydt_out != NULL) { DBL_MEMCPY (k, dydt_out, dim); } /* First traverse h with one step (save to y_onestep) */ DBL_MEMCPY (y_onestep, y, dim); s = gear2_step (y_onestep, state, h, t, dim, sys); if (s != GSL_SUCCESS) { return s; } /* Then with two steps with half step length (save to y) */ s = gear2_step (y, state, h / 2.0, t, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } DBL_MEMCPY (y0, y, dim); s = gear2_step (y, state, h / 2.0, t + h / 2.0, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } /* Cleanup update */ if (dydt_out != NULL) { s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } /* Estimate error and update the state buffer. */ for (i = 0; i < dim; i++) { yerr[i] = 4.0 * (y[i] - y_onestep[i]); yim1[i] = y0[i]; } /* Make note of step size. */ state->last_h = h; return 0; } } static int gear2_reset (void *vstate, size_t dim) { gear2_state_t *state = (gear2_state_t *) vstate; DBL_ZERO_MEMSET (state->yim1, dim); DBL_ZERO_MEMSET (state->k, dim); DBL_ZERO_MEMSET (state->y0, dim); state->primed = 0; state->last_h = 0.0; return GSL_SUCCESS; } static unsigned int gear2_order (void *vstate) { gear2_state_t *state = (gear2_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 3; } static void gear2_free (void *vstate) { gear2_state_t *state = (gear2_state_t *) vstate; free (state->yim1); free (state->k); free (state->y0); free (state->y0_orig); free (state->y_onestep); gsl_odeiv_step_free (state->primer); free (state); } static const gsl_odeiv_step_type gear2_type = { "gear2", /* name */ 1, /* can use dydt_in */ 0, /* gives exact dydt_out */ &gear2_alloc, &gear2_apply, &gear2_reset, &gear2_order, &gear2_free }; const gsl_odeiv_step_type *gsl_odeiv_step_gear2 = &gear2_type; sources_5316/external/gsl/gsl_statistics__quantiles.c0000664000176700017670000000305411723710247021771 0ustar paulpaul#include "gsl__config.h" #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__quantiles_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_statistics__lag1.c0000664000176700017670000000276411723710247020617 0ustar paulpaul#include "gsl__config.h" #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__lag1_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_sum__levin_u.c0000664000176700017670000001575611723710247020053 0ustar paulpaul/* sum/levin_u.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_test.h" #include "gsl_errno.h" #include "gsl_sum.h" int gsl_sum_levin_u_accel (const double *array, const size_t array_size, gsl_sum_levin_u_workspace * w, double *sum_accel, double *abserr) { return gsl_sum_levin_u_minmax (array, array_size, 0, array_size - 1, w, sum_accel, abserr); } int gsl_sum_levin_u_minmax (const double *array, const size_t array_size, const size_t min_terms, const size_t max_terms, gsl_sum_levin_u_workspace * w, double *sum_accel, double *abserr) { if (array_size == 0) { *sum_accel = 0.0; *abserr = 0.0; w->sum_plain = 0.0; w->terms_used = 0; return GSL_SUCCESS; } else if (array_size == 1) { *sum_accel = array[0]; *abserr = 0.0; w->sum_plain = array[0]; w->terms_used = 1; return GSL_SUCCESS; } else { const double SMALL = 0.01; const size_t nmax = GSL_MAX (max_terms, array_size) - 1; double noise_n = 0.0, noise_nm1 = 0.0; double trunc_n = 0.0, trunc_nm1 = 0.0; double actual_trunc_n = 0.0, actual_trunc_nm1 = 0.0; double result_n = 0.0, result_nm1 = 0.0; double variance = 0; size_t n; unsigned int i; int better = 0; int before = 0; int converging = 0; double least_trunc = GSL_DBL_MAX; double least_trunc_noise = GSL_DBL_MAX; double least_trunc_result; /* Calculate specified minimum number of terms. No convergence tests are made, and no truncation information is stored. */ for (n = 0; n < min_terms; n++) { const double t = array[n]; result_nm1 = result_n; gsl_sum_levin_u_step (t, n, nmax, w, &result_n); } least_trunc_result = result_n; variance = 0; for (i = 0; i < n; i++) { double dn = w->dsum[i] * GSL_MACH_EPS * array[i]; variance += dn * dn; } noise_n = sqrt (variance); /* Calculate up to maximum number of terms. Check truncation condition. */ for (; n <= nmax; n++) { const double t = array[n]; result_nm1 = result_n; gsl_sum_levin_u_step (t, n, nmax, w, &result_n); /* Compute the truncation error directly */ actual_trunc_nm1 = actual_trunc_n; actual_trunc_n = fabs (result_n - result_nm1); /* Average results to make a more reliable estimate of the real truncation error */ trunc_nm1 = trunc_n; trunc_n = 0.5 * (actual_trunc_n + actual_trunc_nm1); noise_nm1 = noise_n; variance = 0; for (i = 0; i <= n; i++) { double dn = w->dsum[i] * GSL_MACH_EPS * array[i]; variance += dn * dn; } noise_n = sqrt (variance); /* Determine if we are in the convergence region. */ better = (trunc_n < trunc_nm1 || trunc_n < SMALL * fabs (result_n)); converging = converging || (better && before); before = better; if (converging) { if (trunc_n < least_trunc) { /* Found a low truncation point in the convergence region. Save it. */ least_trunc_result = result_n; least_trunc = trunc_n; least_trunc_noise = noise_n; } if (noise_n > trunc_n / 3.0) break; if (trunc_n < 10.0 * GSL_MACH_EPS * fabs (result_n)) break; } } if (converging) { /* Stopped in the convergence region. Return result and error estimate. */ *sum_accel = least_trunc_result; *abserr = GSL_MAX_DBL (least_trunc, least_trunc_noise); w->terms_used = n; return GSL_SUCCESS; } else { /* Never reached the convergence region. Use the last calculated values. */ *sum_accel = result_n; *abserr = GSL_MAX_DBL (trunc_n, noise_n); w->terms_used = n; return GSL_SUCCESS; } } } int gsl_sum_levin_u_step (const double term, const size_t n, const size_t nmax, gsl_sum_levin_u_workspace * w, double *sum_accel) { #define I(i,j) ((i)*(nmax+1) + (j)) if (n == 0) { *sum_accel = term; w->sum_plain = term; w->q_den[0] = 1.0 / term; w->q_num[0] = 1.0; w->dq_den[I (0, 0)] = -1.0 / (term * term); w->dq_num[I (0, 0)] = 0.0; w->dsum[0] = 1.0; return GSL_SUCCESS; } else { double result; double factor = 1.0; double ratio = (double) n / (n + 1.0); unsigned int i; int j; w->sum_plain += term; w->q_den[n] = 1.0 / (term * (n + 1.0) * (n + 1.0)); w->q_num[n] = w->sum_plain * w->q_den[n]; for (i = 0; i < n; i++) { w->dq_den[I (i, n)] = 0; w->dq_num[I (i, n)] = w->q_den[n]; } w->dq_den[I (n, n)] = -w->q_den[n] / term; w->dq_num[I (n, n)] = w->q_den[n] + w->sum_plain * (w->dq_den[I (n, n)]); for (j = n - 1; j >= 0; j--) { double c = factor * (j + 1) / (n + 1); factor *= ratio; w->q_den[j] = w->q_den[j + 1] - c * w->q_den[j]; w->q_num[j] = w->q_num[j + 1] - c * w->q_num[j]; for (i = 0; i < n; i++) { w->dq_den[I (i, j)] = w->dq_den[I (i, j + 1)] - c * w->dq_den[I (i, j)]; w->dq_num[I (i, j)] = w->dq_num[I (i, j + 1)] - c * w->dq_num[I (i, j)]; } w->dq_den[I (n, j)] = w->dq_den[I (n, j + 1)]; w->dq_num[I (n, j)] = w->dq_num[I (n, j + 1)]; } result = w->q_num[0] / w->q_den[0]; *sum_accel = result; for (i = 0; i <= n; i++) { w->dsum[i] = (w->dq_num[I (i, 0)] - result * w->dq_den[I (i, 0)]) / w->q_den[0]; } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_ode-initval__cscal.c0000664000176700017670000001115011723710247021066 0ustar paulpaul/* ode-initval/cscal.c * * Copyright (C) 2002, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include "gsl_errno.h" #include "gsl_math.h" #include "gsl_odeiv.h" typedef struct { double eps_abs; double eps_rel; double a_y; double a_dydt; double * scale_abs; } sc_control_state_t; static void * sc_control_alloc (void) { sc_control_state_t * s = (sc_control_state_t *) malloc (sizeof(sc_control_state_t)); if (s == 0) { GSL_ERROR_NULL ("failed to allocate space for sc_control_state", GSL_ENOMEM); } return s; } static int sc_control_init (void * vstate, double eps_abs, double eps_rel, double a_y, double a_dydt) { sc_control_state_t * s = (sc_control_state_t *) vstate; if (eps_abs < 0) { GSL_ERROR ("eps_abs is negative", GSL_EINVAL); } else if (eps_rel < 0) { GSL_ERROR ("eps_rel is negative", GSL_EINVAL); } else if (a_y < 0) { GSL_ERROR ("a_y is negative", GSL_EINVAL); } else if (a_dydt < 0) { GSL_ERROR ("a_dydt is negative", GSL_EINVAL); } s->eps_rel = eps_rel; s->eps_abs = eps_abs; s->a_y = a_y; s->a_dydt = a_dydt; return GSL_SUCCESS; } static int sc_control_hadjust(void * vstate, size_t dim, unsigned int ord, const double y[], const double yerr[], const double yp[], double * h) { sc_control_state_t *state = (sc_control_state_t *) vstate; const double eps_abs = state->eps_abs; const double eps_rel = state->eps_rel; const double a_y = state->a_y; const double a_dydt = state->a_dydt; const double * scale_abs = state->scale_abs; const double S = 0.9; const double h_old = *h; double rmax = DBL_MIN; size_t i; for(i=0; i 1.1) { /* decrease step, no more than factor of 5, but a fraction S more than scaling suggests (for better accuracy) */ double r = S / pow(rmax, 1.0/ord); if (r < 0.2) r = 0.2; *h = r * h_old; return GSL_ODEIV_HADJ_DEC; } else if(rmax < 0.5) { /* increase step, no more than factor of 5 */ double r = S / pow(rmax, 1.0/(ord+1.0)); if (r > 5.0) r = 5.0; if (r < 1.0) /* don't allow any decrease caused by S<1 */ r = 1.0; *h = r * h_old; return GSL_ODEIV_HADJ_INC; } else { /* no change */ return GSL_ODEIV_HADJ_NIL; } } static void sc_control_free (void * vstate) { sc_control_state_t *state = (sc_control_state_t *) vstate; free (state->scale_abs); free (state); } static const gsl_odeiv_control_type sc_control_type = {"scaled", /* name */ &sc_control_alloc, &sc_control_init, &sc_control_hadjust, &sc_control_free}; const gsl_odeiv_control_type *gsl_odeiv_control_scaled = &sc_control_type; gsl_odeiv_control * gsl_odeiv_control_scaled_new(double eps_abs, double eps_rel, double a_y, double a_dydt, const double scale_abs[], size_t dim) { gsl_odeiv_control * c = gsl_odeiv_control_alloc (gsl_odeiv_control_scaled); int status = gsl_odeiv_control_init (c, eps_abs, eps_rel, a_y, a_dydt); if (status != GSL_SUCCESS) { gsl_odeiv_control_free (c); GSL_ERROR_NULL ("error trying to initialize control", status); } { sc_control_state_t * s = (sc_control_state_t *) c->state; s->scale_abs = (double *)malloc(dim * sizeof(double)); if (s->scale_abs == 0) { free (s); GSL_ERROR_NULL ("failed to allocate space for scale_abs", GSL_ENOMEM); } memcpy(s->scale_abs, scale_abs, dim * sizeof(double)); } return c; } sources_5316/external/gsl/gsl_sf__bessel_In.c0000644000176700017670000001445110707442037020106 0ustar paulpaul/* specfunc/bessel_In.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_In_scaled_e(int n, const double x, gsl_sf_result * result) { const double ax = fabs(x); n = abs(n); /* I(-n, z) = I(n, z) */ /* CHECK_POINTER(result) */ if(n == 0) { return gsl_sf_bessel_I0_scaled_e(x, result); } else if(n == 1) { return gsl_sf_bessel_I1_scaled_e(x, result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x*x < 10.0*(n+1.0)/M_E) { gsl_sf_result t; double ex = exp(-ax); int stat_In = gsl_sf_bessel_IJ_taylor_e((double)n, ax, 1, 50, GSL_DBL_EPSILON, &t); result->val = t.val * ex; result->err = t.err * ex; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return stat_In; } else if(n < 150 && ax < 1e7) { gsl_sf_result I0_scaled; int stat_I0 = gsl_sf_bessel_I0_scaled_e(ax, &I0_scaled); double rat; int stat_CF1 = gsl_sf_bessel_I_CF1_ser((double)n, ax, &rat); double Ikp1 = rat * GSL_SQRT_DBL_MIN; double Ik = GSL_SQRT_DBL_MIN; double Ikm1; int k; for(k=n; k >= 1; k--) { Ikm1 = Ikp1 + 2.0*k/ax * Ik; Ikp1 = Ik; Ik = Ikm1; } result->val = I0_scaled.val * (GSL_SQRT_DBL_MIN / Ik); result->err = I0_scaled.err * (GSL_SQRT_DBL_MIN / Ik); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return GSL_ERROR_SELECT_2(stat_I0, stat_CF1); } else if( GSL_MIN( 0.29/(n*n), 0.5/(n*n + x*x) ) < 0.5*GSL_ROOT3_DBL_EPSILON) { int stat_as = gsl_sf_bessel_Inu_scaled_asymp_unif_e((double)n, ax, result); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return stat_as; } else { const int nhi = 2 + (int) (1.2 / GSL_ROOT6_DBL_EPSILON); gsl_sf_result r_Ikp1; gsl_sf_result r_Ik; int stat_a1 = gsl_sf_bessel_Inu_scaled_asymp_unif_e(nhi+1.0, ax, &r_Ikp1); int stat_a2 = gsl_sf_bessel_Inu_scaled_asymp_unif_e((double)nhi, ax, &r_Ik); double Ikp1 = r_Ikp1.val; double Ik = r_Ik.val; double Ikm1; int k; for(k=nhi; k > n; k--) { Ikm1 = Ikp1 + 2.0*k/ax * Ik; Ikp1 = Ik; Ik = Ikm1; } result->val = Ik; result->err = Ik * (r_Ikp1.err/r_Ikp1.val + r_Ik.err/r_Ik.val); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return GSL_ERROR_SELECT_2(stat_a1, stat_a2); } } int gsl_sf_bessel_In_scaled_array(const int nmin, const int nmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(nmax < nmin || nmin < 0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; GSL_ERROR ("domain error", GSL_EDOM); } else if(x == 0.0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; if(nmin == 0) result_array[0] = 1.0; return GSL_SUCCESS; } else if(nmax == 0) { gsl_sf_result I0_scaled; int stat = gsl_sf_bessel_I0_scaled_e(x, &I0_scaled); result_array[0] = I0_scaled.val; return stat; } else { const double ax = fabs(x); const double two_over_x = 2.0/ax; /* starting values */ gsl_sf_result r_Inp1; gsl_sf_result r_In; int stat_0 = gsl_sf_bessel_In_scaled_e(nmax+1, ax, &r_Inp1); int stat_1 = gsl_sf_bessel_In_scaled_e(nmax, ax, &r_In); double Inp1 = r_Inp1.val; double In = r_In.val; double Inm1; int n; for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = In; Inm1 = Inp1 + n * two_over_x * In; Inp1 = In; In = Inm1; } /* deal with signs */ if(x < 0.0) { for(n=nmin; n<=nmax; n++) { if(GSL_IS_ODD(n)) result_array[n-nmin] = -result_array[n-nmin]; } } return GSL_ERROR_SELECT_2(stat_0, stat_1); } } int gsl_sf_bessel_In_e(const int n_in, const double x, gsl_sf_result * result) { const double ax = fabs(x); const int n = abs(n_in); /* I(-n, z) = I(n, z) */ gsl_sf_result In_scaled; const int stat_In_scaled = gsl_sf_bessel_In_scaled_e(n, ax, &In_scaled); /* In_scaled is always less than 1, * so this overflow check is conservative. */ if(ax > GSL_LOG_DBL_MAX - 1.0) { OVERFLOW_ERROR(result); } else { const double ex = exp(ax); result->val = ex * In_scaled.val; result->err = ex * In_scaled.err; result->err += ax * GSL_DBL_EPSILON * fabs(result->val); if(x < 0.0 && GSL_IS_ODD(n)) result->val = -result->val; return stat_In_scaled; } } int gsl_sf_bessel_In_array(const int nmin, const int nmax, const double x, double * result_array) { double ax = fabs(x); /* CHECK_POINTER(result_array) */ if(ax > GSL_LOG_DBL_MAX - 1.0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; /* FIXME: should be Inf */ GSL_ERROR ("overflow", GSL_EOVRFLW); } else { int j; double eax = exp(ax); int status = gsl_sf_bessel_In_scaled_array(nmin, nmax, x, result_array); for(j=0; j<=nmax-nmin; j++) result_array[j] *= eax; return status; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_In_scaled(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_In_scaled_e(n, x, &result)); } double gsl_sf_bessel_In(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_In_e(n, x, &result)); } sources_5316/external/gsl/gsl_rng__tt.c0000664000176700017670000000741611723710247017015 0ustar paulpaul/* rng/tt.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is the TT800 twisted GSFR generator for 32 bit integers. It has been superceded by MT19937 (mt.c). The period is 2^800. This implementation is based on tt800.c, July 8th 1996 version by M. Matsumoto, email: matumoto@math.keio.ac.jp From: Makoto Matsumoto and Yoshiharu Kurita, "Twisted GFSR Generators II", ACM Transactions on Modelling and Computer Simulation, Vol. 4, No. 3, 1994, pages 254-266. */ static inline unsigned long int tt_get (void *vstate); static double tt_get_double (void *vstate); static void tt_set (void *state, unsigned long int s); #define N 25 #define M 7 typedef struct { int n; unsigned long int x[N]; } tt_state_t; static inline unsigned long int tt_get (void *vstate) { tt_state_t *state = (tt_state_t *) vstate; /* this is the magic vector, a */ const unsigned long mag01[2] = {0x00000000, 0x8ebfd028UL}; unsigned long int y; unsigned long int *const x = state->x; int n = state->n; if (n >= N) { int i; for (i = 0; i < N - M; i++) { x[i] = x[i + M] ^ (x[i] >> 1) ^ mag01[x[i] % 2]; } for (; i < N; i++) { x[i] = x[i + (M - N)] ^ (x[i] >> 1) ^ mag01[x[i] % 2]; }; n = 0; } y = x[n]; y ^= (y << 7) & 0x2b5b2500UL; /* s and b, magic vectors */ y ^= (y << 15) & 0xdb8b0000UL; /* t and c, magic vectors */ y &= 0xffffffffUL; /* you may delete this line if word size = 32 */ /* The following line was added by Makoto Matsumoto in the 1996 version to improve lower bit's correlation. Delete this line to use the code published in 1994. */ y ^= (y >> 16); /* added to the 1994 version */ state->n = n + 1; return y; } static double tt_get_double (void * vstate) { return tt_get (vstate) / 4294967296.0 ; } static void tt_set (void *vstate, unsigned long int s) { tt_state_t *state = (tt_state_t *) vstate; const tt_state_t init_state = {0, {0x95f24dabUL, 0x0b685215UL, 0xe76ccae7UL, 0xaf3ec239UL, 0x715fad23UL, 0x24a590adUL, 0x69e4b5efUL, 0xbf456141UL, 0x96bc1b7bUL, 0xa7bdf825UL, 0xc1de75b7UL, 0x8858a9c9UL, 0x2da87693UL, 0xb657f9ddUL, 0xffdc8a9fUL, 0x8121da71UL, 0x8b823ecbUL, 0x885d05f5UL, 0x4e20cd47UL, 0x5a9ad5d9UL, 0x512c0c03UL, 0xea857ccdUL, 0x4cc1d30fUL, 0x8891a8a1UL, 0xa6b7aadbUL}}; if (s == 0) /* default seed is given explicitly in the original code */ { *state = init_state; } else { int i; state->n = 0; state->x[0] = s & 0xffffffffUL; for (i = 1; i < N; i++) state->x[i] = (69069 * state->x[i - 1]) & 0xffffffffUL; } return; } static const gsl_rng_type tt_type = {"tt800", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (tt_state_t), &tt_set, &tt_get, &tt_get_double}; const gsl_rng_type *gsl_rng_tt800 = &tt_type; sources_5316/external/gsl/gsl_vector__subvector_source.c0000664000176700017670000000456611723710247022501 0ustar paulpaul/* vector/subvector_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ QUALIFIED_VIEW(_gsl_vector, view) FUNCTION(gsl_vector, subvector) (QUALIFIED_TYPE(gsl_vector) * v, size_t offset, size_t n) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (n == 0) { GSL_ERROR_VAL ("vector length n must be positive integer", GSL_EINVAL, view); } if (offset + (n - 1) >= v->size) { GSL_ERROR_VAL ("view would extend past end of vector", GSL_EINVAL, view); } { TYPE(gsl_vector) s = NULL_VECTOR; s.data = v->data + MULTIPLICITY * v->stride * offset ; s.size = n; s.stride = v->stride; s.block = v->block; s.owner = 0; view.vector = s; return view; } } QUALIFIED_VIEW(_gsl_vector, view) FUNCTION(gsl_vector, subvector_with_stride) (QUALIFIED_TYPE(gsl_vector) * v, size_t offset, size_t stride, size_t n) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (n == 0) { GSL_ERROR_VAL ("vector length n must be positive integer", GSL_EINVAL, view); } if (stride == 0) { GSL_ERROR_VAL ("stride must be positive integer", GSL_EINVAL, view); } if (offset + (n - 1) * stride >= v->size) { GSL_ERROR_VAL ("view would extend past end of vector", GSL_EINVAL, view); } { TYPE(gsl_vector) s = NULL_VECTOR; s.data = v->data + MULTIPLICITY * v->stride * offset ; s.size = n; s.stride = v->stride * stride; s.block = v->block; s.owner = 0; view.vector = s; return view; } } sources_5316/external/gsl/gsl_diff.h0000664000176700017670000000275411705263724016301 0ustar paulpaul/* diff/gsl_diff.h * * Copyright (C) 2000 David Morrison * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_DIFF_H__ #define __GSL_DIFF_H__ #include "gsl_math.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_diff_central (const gsl_function *f, double x, double *result, double *abserr); int gsl_diff_backward (const gsl_function *f, double x, double *result, double *abserr); int gsl_diff_forward (const gsl_function *f, double x, double *result, double *abserr); __END_DECLS #endif /* __GSL_DIFF_H__ */ sources_5316/external/gsl/gsl_histogram__maxval2d.c0000664000176700017670000000637511723710247021316 0ustar paulpaul/* gsl_histogram2d_maxval.c * Copyright (C) 2000 Simone Piccardi * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File gsl_histogram2d_maxval.c: * Routine to find maximum and minumum content of a 2D hisogram. * Need GSL library and header. * Contains the routines: * gsl_histogram2d_max_val find max content values * gsl_histogram2d_min_val find min content values * gsl_histogram2d_bin_max find coordinates of max contents bin * gsl_histogram2d_bin_min find coordinates of min contents bin * * Author: S. Piccardi * Jan. 2000 * ***************************************************************/ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_histogram2d.h" /* * Return the maximum contents value of a 2D histogram */ double gsl_histogram2d_max_val (const gsl_histogram2d * h) { const size_t nx = h->nx; const size_t ny = h->ny; size_t i; double max = h->bin[0 * ny + 0]; for (i = 0; i < nx * ny; i++) { if (h->bin[i] > max) { max = h->bin[i]; } } return max; } /* * Find the bin index for maximum value of a 2D histogram */ void gsl_histogram2d_max_bin (const gsl_histogram2d * h, size_t * imax_out, size_t * jmax_out) { const size_t nx = h->nx; const size_t ny = h->ny; size_t imax = 0, jmax = 0, i, j; double max = h->bin[0 * ny + 0]; for (i = 0; i < nx; i++) { for (j = 0; j < ny; j++) { double x = h->bin[i * ny + j]; if (x > max) { max = x; imax = i; jmax = j; } } } *imax_out = imax; *jmax_out = jmax; } /* * Return the minimum contents value of a 2D histogram */ double gsl_histogram2d_min_val (const gsl_histogram2d * h) { const size_t nx = h->nx; const size_t ny = h->ny; size_t i; double min = h->bin[0 * ny + 0]; for (i = 0; i < nx * ny; i++) { if (h->bin[i] < min) { min = h->bin[i]; } } return min; } /* * Find the bin index for minimum value of a 2D histogram */ void gsl_histogram2d_min_bin (const gsl_histogram2d * h, size_t * imin_out, size_t * jmin_out) { const size_t nx = h->nx; const size_t ny = h->ny; size_t imin = 0, jmin = 0, i, j; double min = h->bin[0 * ny + 0]; for (i = 0; i < nx; i++) { for (j = 0; j < ny; j++) { double x = h->bin[i * ny + j]; if (x < min) { min = x; imin = i; jmin = j; } } } *imin_out = imin; *jmin_out = jmin; } sources_5316/external/gsl/gsl_linalg__symmtd.c0000664000176700017670000001501511723710247020355 0ustar paulpaul/* linalg/sytd.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Factorise a symmetric matrix A into * * A = Q T Q' * * where Q is orthogonal and T is symmetric tridiagonal. Only the * diagonal and lower triangular part of A is referenced and modified. * * On exit, T is stored in the diagonal and first subdiagonal of * A. Since T is symmetric the upper diagonal is not stored. * * Q is stored as a packed set of Householder transformations in the * lower triangular part of the input matrix below the first subdiagonal. * * The full matrix for Q can be obtained as the product * * Q = Q_1 Q_2 ... Q_(N-2) * * where * * Q_i = (I - tau_i * v_i * v_i') * * and where v_i is a Householder vector * * v_i = [0, ... , 0, 1, A(i+1,i), A(i+2,i), ... , A(N,i)] * * This storage scheme is the same as in LAPACK. See LAPACK's * ssytd2.f for details. * * See Golub & Van Loan, "Matrix Computations" (3rd ed), Section 8.3 * * Note: this description uses 1-based indices. The code below uses * 0-based indices */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_linalg.h" int gsl_linalg_symmtd_decomp (gsl_matrix * A, gsl_vector * tau) { if (A->size1 != A->size2) { GSL_ERROR ("symmetric tridiagonal decomposition requires square matrix", GSL_ENOTSQR); } else if (tau->size + 1 != A->size1) { GSL_ERROR ("size of tau must be (matrix size - 1)", GSL_EBADLEN); } else { const size_t N = A->size1; size_t i; for (i = 0 ; i < N - 2; i++) { gsl_vector_view c = gsl_matrix_column (A, i); gsl_vector_view v = gsl_vector_subvector (&c.vector, i + 1, N - (i + 1)); double tau_i = gsl_linalg_householder_transform (&v.vector); /* Apply the transformation H^T A H to the remaining columns */ if (tau_i != 0.0) { gsl_matrix_view m = gsl_matrix_submatrix (A, i + 1, i + 1, N - (i+1), N - (i+1)); double ei = gsl_vector_get(&v.vector, 0); gsl_vector_view x = gsl_vector_subvector (tau, i, N-(i+1)); gsl_vector_set (&v.vector, 0, 1.0); /* x = tau * A * v */ gsl_blas_dsymv (CblasLower, tau_i, &m.matrix, &v.vector, 0.0, &x.vector); /* w = x - (1/2) tau * (x' * v) * v */ { double xv, alpha; gsl_blas_ddot(&x.vector, &v.vector, &xv); alpha = - (tau_i / 2.0) * xv; gsl_blas_daxpy(alpha, &v.vector, &x.vector); } /* apply the transformation A = A - v w' - w v' */ gsl_blas_dsyr2(CblasLower, -1.0, &v.vector, &x.vector, &m.matrix); gsl_vector_set (&v.vector, 0, ei); } gsl_vector_set (tau, i, tau_i); } return GSL_SUCCESS; } } /* Form the orthogonal matrix Q from the packed QR matrix */ int gsl_linalg_symmtd_unpack (const gsl_matrix * A, const gsl_vector * tau, gsl_matrix * Q, gsl_vector * diag, gsl_vector * sdiag) { if (A->size1 != A->size2) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } else if (tau->size + 1 != A->size1) { GSL_ERROR ("size of tau must be (matrix size - 1)", GSL_EBADLEN); } else if (Q->size1 != A->size1 || Q->size2 != A->size1) { GSL_ERROR ("size of Q must match size of A", GSL_EBADLEN); } else if (diag->size != A->size1) { GSL_ERROR ("size of diagonal must match size of A", GSL_EBADLEN); } else if (sdiag->size + 1 != A->size1) { GSL_ERROR ("size of subdiagonal must be (matrix size - 1)", GSL_EBADLEN); } else { const size_t N = A->size1; size_t i; /* Initialize Q to the identity */ gsl_matrix_set_identity (Q); for (i = N - 2; i > 0 && i--;) { gsl_vector_const_view c = gsl_matrix_const_column (A, i); gsl_vector_const_view h = gsl_vector_const_subvector (&c.vector, i + 1, N - (i+1)); double ti = gsl_vector_get (tau, i); gsl_matrix_view m = gsl_matrix_submatrix (Q, i + 1, i + 1, N-(i+1), N-(i+1)); gsl_linalg_householder_hm (ti, &h.vector, &m.matrix); } /* Copy diagonal into diag */ for (i = 0; i < N; i++) { double Aii = gsl_matrix_get (A, i, i); gsl_vector_set (diag, i, Aii); } /* Copy subdiagonal into sd */ for (i = 0; i < N - 1; i++) { double Aji = gsl_matrix_get (A, i+1, i); gsl_vector_set (sdiag, i, Aji); } return GSL_SUCCESS; } } int gsl_linalg_symmtd_unpack_T (const gsl_matrix * A, gsl_vector * diag, gsl_vector * sdiag) { if (A->size1 != A->size2) { GSL_ERROR ("matrix A must be square", GSL_ENOTSQR); } else if (diag->size != A->size1) { GSL_ERROR ("size of diagonal must match size of A", GSL_EBADLEN); } else if (sdiag->size + 1 != A->size1) { GSL_ERROR ("size of subdiagonal must be (matrix size - 1)", GSL_EBADLEN); } else { const size_t N = A->size1; size_t i; /* Copy diagonal into diag */ for (i = 0; i < N; i++) { double Aii = gsl_matrix_get (A, i, i); gsl_vector_set (diag, i, Aii); } /* Copy subdiagonal into sdiag */ for (i = 0; i < N - 1; i++) { double Aij = gsl_matrix_get (A, i+1, i); gsl_vector_set (sdiag, i, Aij); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_randist__logarithmic.c0000664000176700017670000000351411723710247021541 0ustar paulpaul/* randist/logarithmic.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* Logarithmic distribution prob(n) = p^n / (n log(1/(1-p)) for n = 1, 2, 3, ... We use Kemp's second accelerated generator, from Luc Devroye's book on "Non-Uniform Random Variate Generation", Springer */ unsigned int gsl_ran_logarithmic (const gsl_rng * r, const double p) { double c = log (1-p) ; double v = gsl_rng_uniform_pos (r); if (v >= p) { return 1 ; } else { double u = gsl_rng_uniform_pos (r); double q = 1 - exp (c * u); if (v <= q*q) { double x = 1 + log(v)/log(q) ; return x ; } else if (v <= q) { return 2; } else { return 1 ; } } } double gsl_ran_logarithmic_pdf (const unsigned int k, const double p) { if (k == 0) { return 0 ; } else { double P = pow(p, (double)k) / (double) k / log(1/(1-p)) ; return P; } } sources_5316/external/gsl/gsl_cblas__stpmv.c0000664000176700017670000000056211723710247020030 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_stpmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const float *Ap, float *X, const int incX) { #define BASE float #include "gsl_cblas__source_tpmv_r.h" #undef BASE } sources_5316/external/gsl/gsl_histogram__stat.c0000664000176700017670000000614111723710247020542 0ustar paulpaul/* gsl_histogram_stat.c * Copyright (C) 2000 Simone Piccardi * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ /*************************************************************** * * File gsl_histogram_stat.c: * Routines for statisticalcomputations on histograms. * Need GSL library and header. * Contains the routines: * gsl_histogram_mean compute histogram mean * gsl_histogram_sigma compute histogram sigma * * Author: S. Piccardi * Jan. 2000 * ***************************************************************/ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_histogram.h" /* FIXME: We skip negative values in the histogram h->bin[i] < 0, since those correspond to negative weights (BJG) */ double gsl_histogram_mean (const gsl_histogram * h) { const size_t n = h->n; size_t i; /* Compute the bin-weighted arithmetic mean M of a histogram using the recurrence relation M(n) = M(n-1) + (x[n] - M(n-1)) (w(n)/(W(n-1) + w(n))) W(n) = W(n-1) + w(n) */ long double wmean = 0; long double W = 0; for (i = 0; i < n; i++) { double xi = (h->range[i + 1] + h->range[i]) / 2; double wi = h->bin[i]; if (wi > 0) { W += wi; wmean += (xi - wmean) * (wi / W); } } return wmean; } double gsl_histogram_sigma (const gsl_histogram * h) { const size_t n = h->n; size_t i; long double wvariance = 0 ; long double wmean = 0; long double W = 0; /* FIXME: should use a single pass formula here, as given in N.J.Higham 'Accuracy and Stability of Numerical Methods', p.12 */ /* Compute the mean */ for (i = 0; i < n; i++) { double xi = (h->range[i + 1] + h->range[i]) / 2; double wi = h->bin[i]; if (wi > 0) { W += wi; wmean += (xi - wmean) * (wi / W); } } /* Compute the variance */ W = 0.0; for (i = 0; i < n; i++) { double xi = ((h->range[i + 1]) + (h->range[i])) / 2; double wi = h->bin[i]; if (wi > 0) { const long double delta = (xi - wmean); W += wi ; wvariance += (delta * delta - wvariance) * (wi / W); } } { double sigma = sqrt (wvariance) ; return sigma; } } /* sum up all bins of histogram */ double gsl_histogram_sum(const gsl_histogram * h) { double sum=0; size_t i=0; size_t n; n=h->n; while(i < n) sum += h->bin[i++]; return sum; } sources_5316/external/gsl/gsl_cblas__sger.c0000664000176700017670000000053711723710247017621 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_sger (const enum CBLAS_ORDER order, const int M, const int N, const float alpha, const float *X, const int incX, const float *Y, const int incY, float *A, const int lda) { #define BASE float #include "gsl_cblas__source_ger.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_hemm.h0000664000176700017670000001766211705263724021206 0ustar paulpaul/* blas/source_hemm.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; INDEX n1, n2; int uplo, side; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; if (Order == CblasRowMajor) { n1 = M; n2 = N; uplo = Uplo; side = Side; } else { n1 = N; n2 = M; uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; side = (Side == CblasLeft) ? CblasRight : CblasLeft; } /* form y := beta*y */ if (beta_real == 0.0 && beta_imag == 0.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Cij_real = REAL(C, ldc * i + j); const BASE Cij_imag = IMAG(C, ldc * i + j); REAL(C, ldc * i + j) = beta_real * Cij_real - beta_imag * Cij_imag; IMAG(C, ldc * i + j) = beta_real * Cij_imag + beta_imag * Cij_real; } } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; if (side == CblasLeft && uplo == CblasUpper) { /* form C := alpha*A*B + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = CONST_REAL(B, ldb * i + j); const BASE Bij_imag = CONST_IMAG(B, ldb * i + j); const BASE temp1_real = alpha_real * Bij_real - alpha_imag * Bij_imag; const BASE temp1_imag = alpha_real * Bij_imag + alpha_imag * Bij_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; { const BASE Aii_real = CONST_REAL(A, i * lda + i); /* const BASE Aii_imag = 0.0; */ REAL(C, i * ldc + j) += temp1_real * Aii_real; IMAG(C, i * ldc + j) += temp1_imag * Aii_real; } for (k = i + 1; k < n1; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Bkj_real = CONST_REAL(B, ldb * k + j); const BASE Bkj_imag = CONST_IMAG(B, ldb * k + j); REAL(C, k * ldc + j) += Aik_real * temp1_real - (-Aik_imag) * temp1_imag; IMAG(C, k * ldc + j) += Aik_real * temp1_imag + (-Aik_imag) * temp1_real; temp2_real += Aik_real * Bkj_real - Aik_imag * Bkj_imag; temp2_imag += Aik_real * Bkj_imag + Aik_imag * Bkj_real; } REAL(C, i * ldc + j) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(C, i * ldc + j) += alpha_real * temp2_imag + alpha_imag * temp2_real; } } } else if (side == CblasLeft && uplo == CblasLower) { /* form C := alpha*A*B + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = CONST_REAL(B, ldb * i + j); const BASE Bij_imag = CONST_IMAG(B, ldb * i + j); const BASE temp1_real = alpha_real * Bij_real - alpha_imag * Bij_imag; const BASE temp1_imag = alpha_real * Bij_imag + alpha_imag * Bij_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; for (k = 0; k < i; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Bkj_real = CONST_REAL(B, ldb * k + j); const BASE Bkj_imag = CONST_IMAG(B, ldb * k + j); REAL(C, k * ldc + j) += Aik_real * temp1_real - (-Aik_imag) * temp1_imag; IMAG(C, k * ldc + j) += Aik_real * temp1_imag + (-Aik_imag) * temp1_real; temp2_real += Aik_real * Bkj_real - Aik_imag * Bkj_imag; temp2_imag += Aik_real * Bkj_imag + Aik_imag * Bkj_real; } { const BASE Aii_real = CONST_REAL(A, i * lda + i); /* const BASE Aii_imag = 0.0; */ REAL(C, i * ldc + j) += temp1_real * Aii_real; IMAG(C, i * ldc + j) += temp1_imag * Aii_real; } REAL(C, i * ldc + j) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(C, i * ldc + j) += alpha_real * temp2_imag + alpha_imag * temp2_real; } } } else if (side == CblasRight && uplo == CblasUpper) { /* form C := alpha*B*A + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = CONST_REAL(B, ldb * i + j); const BASE Bij_imag = CONST_IMAG(B, ldb * i + j); const BASE temp1_real = alpha_real * Bij_real - alpha_imag * Bij_imag; const BASE temp1_imag = alpha_real * Bij_imag + alpha_imag * Bij_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; { const BASE Ajj_real = CONST_REAL(A, j * lda + j); /* const BASE Ajj_imag = 0.0; */ REAL(C, i * ldc + j) += temp1_real * Ajj_real; IMAG(C, i * ldc + j) += temp1_imag * Ajj_real; } for (k = j + 1; k < n2; k++) { const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); const BASE Bik_real = CONST_REAL(B, ldb * i + k); const BASE Bik_imag = CONST_IMAG(B, ldb * i + k); REAL(C, i * ldc + k) += temp1_real * Ajk_real - temp1_imag * Ajk_imag; IMAG(C, i * ldc + k) += temp1_real * Ajk_imag + temp1_imag * Ajk_real; temp2_real += Bik_real * Ajk_real - Bik_imag * (-Ajk_imag); temp2_imag += Bik_real * (-Ajk_imag) + Bik_imag * Ajk_real; } REAL(C, i * ldc + j) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(C, i * ldc + j) += alpha_real * temp2_imag + alpha_imag * temp2_real; } } } else if (side == CblasRight && uplo == CblasLower) { /* form C := alpha*B*A + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = CONST_REAL(B, ldb * i + j); const BASE Bij_imag = CONST_IMAG(B, ldb * i + j); const BASE temp1_real = alpha_real * Bij_real - alpha_imag * Bij_imag; const BASE temp1_imag = alpha_real * Bij_imag + alpha_imag * Bij_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; for (k = 0; k < j; k++) { const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); const BASE Bik_real = CONST_REAL(B, ldb * i + k); const BASE Bik_imag = CONST_IMAG(B, ldb * i + k); REAL(C, i * ldc + k) += temp1_real * Ajk_real - temp1_imag * Ajk_imag; IMAG(C, i * ldc + k) += temp1_real * Ajk_imag + temp1_imag * Ajk_real; temp2_real += Bik_real * Ajk_real - Bik_imag * (-Ajk_imag); temp2_imag += Bik_real * (-Ajk_imag) + Bik_imag * Ajk_real; } { const BASE Ajj_real = CONST_REAL(A, j * lda + j); /* const BASE Ajj_imag = 0.0; */ REAL(C, i * ldc + j) += temp1_real * Ajj_real; IMAG(C, i * ldc + j) += temp1_imag * Ajj_real; } REAL(C, i * ldc + j) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(C, i * ldc + j) += alpha_real * temp2_imag + alpha_imag * temp2_real; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_check_range.h0000664000176700017670000000304711705263724017616 0ustar paulpaul/* vector/gsl_check_range.h * * Copyright (C) 2003, 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_CHECK_RANGE_H__ #define __GSL_CHECK_RANGE_H__ #include #include "gsl_types.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS GSL_VAR int gsl_check_range; /* Turn range checking on by default, unless the user defines GSL_RANGE_CHECK_OFF, or defines GSL_RANGE_CHECK to 0 explicitly */ #ifdef GSL_RANGE_CHECK_OFF # ifndef GSL_RANGE_CHECK # define GSL_RANGE_CHECK 0 # else # error "cannot set both GSL_RANGE_CHECK and GSL_RANGE_CHECK_OFF" # endif #else # ifndef GSL_RANGE_CHECK # define GSL_RANGE_CHECK 1 # endif #endif __END_DECLS #endif /* __GSL_CHECK_RANGE_H__ */ sources_5316/external/gsl/gsl_cblas__zher2.c0000664000176700017670000000056011723710247017707 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zher2 (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda) { #define BASE double #include "gsl_cblas__source_her2.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__airy.c0000664000176700017670000005606511723710247020356 0ustar paulpaul/* specfunc/airy.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_airy.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__check.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval_mode.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* chebyshev expansions for Airy modulus and phase based on SLATEC r9aimp() Series for AM21 on the interval -1.25000D-01 to 0. with weighted error 2.89E-17 log weighted error 16.54 significant figures required 14.15 decimal places required 17.34 Series for ATH1 on the interval -1.25000D-01 to 0. with weighted error 2.53E-17 log weighted error 16.60 significant figures required 15.15 decimal places required 17.38 Series for AM22 on the interval -1.00000D+00 to -1.25000D-01 with weighted error 2.99E-17 log weighted error 16.52 significant figures required 14.57 decimal places required 17.28 Series for ATH2 on the interval -1.00000D+00 to -1.25000D-01 with weighted error 2.57E-17 log weighted error 16.59 significant figures required 15.07 decimal places required 17.34 */ static double am21_data[37] = { 0.0065809191761485, 0.0023675984685722, 0.0001324741670371, 0.0000157600904043, 0.0000027529702663, 0.0000006102679017, 0.0000001595088468, 0.0000000471033947, 0.0000000152933871, 0.0000000053590722, 0.0000000020000910, 0.0000000007872292, 0.0000000003243103, 0.0000000001390106, 0.0000000000617011, 0.0000000000282491, 0.0000000000132979, 0.0000000000064188, 0.0000000000031697, 0.0000000000015981, 0.0000000000008213, 0.0000000000004296, 0.0000000000002284, 0.0000000000001232, 0.0000000000000675, 0.0000000000000374, 0.0000000000000210, 0.0000000000000119, 0.0000000000000068, 0.0000000000000039, 0.0000000000000023, 0.0000000000000013, 0.0000000000000008, 0.0000000000000005, 0.0000000000000003, 0.0000000000000001, 0.0000000000000001 }; static cheb_series am21_cs = { am21_data, 36, -1, 1, 20 }; static double ath1_data[36] = { -0.07125837815669365, -0.00590471979831451, -0.00012114544069499, -0.00000988608542270, -0.00000138084097352, -0.00000026142640172, -0.00000006050432589, -0.00000001618436223, -0.00000000483464911, -0.00000000157655272, -0.00000000055231518, -0.00000000020545441, -0.00000000008043412, -0.00000000003291252, -0.00000000001399875, -0.00000000000616151, -0.00000000000279614, -0.00000000000130428, -0.00000000000062373, -0.00000000000030512, -0.00000000000015239, -0.00000000000007758, -0.00000000000004020, -0.00000000000002117, -0.00000000000001132, -0.00000000000000614, -0.00000000000000337, -0.00000000000000188, -0.00000000000000105, -0.00000000000000060, -0.00000000000000034, -0.00000000000000020, -0.00000000000000011, -0.00000000000000007, -0.00000000000000004, -0.00000000000000002 }; static cheb_series ath1_cs = { ath1_data, 35, -1, 1, 15 }; static double am22_data[33] = { -0.01562844480625341, 0.00778336445239681, 0.00086705777047718, 0.00015696627315611, 0.00003563962571432, 0.00000924598335425, 0.00000262110161850, 0.00000079188221651, 0.00000025104152792, 0.00000008265223206, 0.00000002805711662, 0.00000000976821090, 0.00000000347407923, 0.00000000125828132, 0.00000000046298826, 0.00000000017272825, 0.00000000006523192, 0.00000000002490471, 0.00000000000960156, 0.00000000000373448, 0.00000000000146417, 0.00000000000057826, 0.00000000000022991, 0.00000000000009197, 0.00000000000003700, 0.00000000000001496, 0.00000000000000608, 0.00000000000000248, 0.00000000000000101, 0.00000000000000041, 0.00000000000000017, 0.00000000000000007, 0.00000000000000002 }; static cheb_series am22_cs = { am22_data, 32, -1, 1, 15 }; static double ath2_data[32] = { 0.00440527345871877, -0.03042919452318455, -0.00138565328377179, -0.00018044439089549, -0.00003380847108327, -0.00000767818353522, -0.00000196783944371, -0.00000054837271158, -0.00000016254615505, -0.00000005053049981, -0.00000001631580701, -0.00000000543420411, -0.00000000185739855, -0.00000000064895120, -0.00000000023105948, -0.00000000008363282, -0.00000000003071196, -0.00000000001142367, -0.00000000000429811, -0.00000000000163389, -0.00000000000062693, -0.00000000000024260, -0.00000000000009461, -0.00000000000003716, -0.00000000000001469, -0.00000000000000584, -0.00000000000000233, -0.00000000000000093, -0.00000000000000037, -0.00000000000000015, -0.00000000000000006, -0.00000000000000002 }; static cheb_series ath2_cs = { ath2_data, 31, -1, 1, 16 }; /* Airy modulus and phase for x < -1 */ static int airy_mod_phase(const double x, gsl_mode_t mode, gsl_sf_result * mod, gsl_sf_result * phase) { gsl_sf_result result_m; gsl_sf_result result_p; double m, p; double sqx; if(x < -2.0) { double z = 16.0/(x*x*x) + 1.0; cheb_eval_mode_e(&am21_cs, z, mode, &result_m); cheb_eval_mode_e(&ath1_cs, z, mode, &result_p); } else if(x <= -1.0) { double z = (16.0/(x*x*x) + 9.0)/7.0; cheb_eval_mode_e(&am22_cs, z, mode, &result_m); cheb_eval_mode_e(&ath2_cs, z, mode, &result_p); } else { mod->val = 0.0; mod->err = 0.0; phase->val = 0.0; phase->err = 0.0; GSL_ERROR ("x is greater than 1.0", GSL_EDOM); } m = 0.3125 + result_m.val; p = -0.625 + result_p.val; sqx = sqrt(-x); mod->val = sqrt(m/sqx); mod->err = fabs(mod->val) * (GSL_DBL_EPSILON + fabs(result_m.err/result_m.val)); phase->val = M_PI_4 - x*sqx * p; phase->err = fabs(phase->val) * (GSL_DBL_EPSILON + fabs(result_p.err/result_p.val)); return GSL_SUCCESS; } /* Chebyshev series for Ai(x) with x in [-1,1] based on SLATEC ai(x) series for aif on the interval -1.00000d+00 to 1.00000d+00 with weighted error 1.09e-19 log weighted error 18.96 significant figures required 17.76 decimal places required 19.44 series for aig on the interval -1.00000d+00 to 1.00000d+00 with weighted error 1.51e-17 log weighted error 16.82 significant figures required 15.19 decimal places required 17.27 */ static double ai_data_f[9] = { -0.03797135849666999750, 0.05919188853726363857, 0.00098629280577279975, 0.00000684884381907656, 0.00000002594202596219, 0.00000000006176612774, 0.00000000000010092454, 0.00000000000000012014, 0.00000000000000000010 }; static cheb_series aif_cs = { ai_data_f, 8, -1, 1, 8 }; static double ai_data_g[8] = { 0.01815236558116127, 0.02157256316601076, 0.00025678356987483, 0.00000142652141197, 0.00000000457211492, 0.00000000000952517, 0.00000000000001392, 0.00000000000000001 }; static cheb_series aig_cs = { ai_data_g, 7, -1, 1, 7 }; /* Chebvyshev series for Bi(x) with x in [-1,1] based on SLATEC bi(x) series for bif on the interval -1.00000d+00 to 1.00000d+00 with weighted error 1.88e-19 log weighted error 18.72 significant figures required 17.74 decimal places required 19.20 series for big on the interval -1.00000d+00 to 1.00000d+00 with weighted error 2.61e-17 log weighted error 16.58 significant figures required 15.17 decimal places required 17.03 */ static double data_bif[9] = { -0.01673021647198664948, 0.10252335834249445610, 0.00170830925073815165, 0.00001186254546774468, 0.00000004493290701779, 0.00000000010698207143, 0.00000000000017480643, 0.00000000000000020810, 0.00000000000000000018 }; static cheb_series bif_cs = { data_bif, 8, -1, 1, 8 }; static double data_big[8] = { 0.02246622324857452, 0.03736477545301955, 0.00044476218957212, 0.00000247080756363, 0.00000000791913533, 0.00000000001649807, 0.00000000000002411, 0.00000000000000002 }; static cheb_series big_cs = { data_big, 7, -1, 1, 7 }; /* Chebyshev series for Bi(x) with x in [1,8] based on SLATEC bi(x) */ static double data_bif2[10] = { 0.0998457269381604100, 0.4786249778630055380, 0.0251552119604330118, 0.0005820693885232645, 0.0000074997659644377, 0.0000000613460287034, 0.0000000003462753885, 0.0000000000014288910, 0.0000000000000044962, 0.0000000000000000111 }; static cheb_series bif2_cs = { data_bif2, 9, -1, 1, 9 }; static double data_big2[10] = { 0.033305662145514340, 0.161309215123197068, 0.0063190073096134286, 0.0001187904568162517, 0.0000013045345886200, 0.0000000093741259955, 0.0000000000474580188, 0.0000000000001783107, 0.0000000000000005167, 0.0000000000000000011 }; static cheb_series big2_cs = { data_big2, 9, -1, 1, 9 }; /* chebyshev for Ai(x) asymptotic factor based on SLATEC aie() Series for AIP on the interval 0. to 1.00000D+00 with weighted error 5.10E-17 log weighted error 16.29 significant figures required 14.41 decimal places required 17.06 [GJ] Sun Apr 19 18:14:31 EDT 1998 There was something wrong with these coefficients. I was getting errors after 3 or 4 digits. So I recomputed this table. Now I get double precision agreement with Mathematica. But it does not seem possible that the small differences here would account for the original discrepancy. There must have been something wrong with my original usage... */ static double data_aip[36] = { -0.0187519297793867540198, -0.0091443848250055004725, 0.0009010457337825074652, -0.0001394184127221491507, 0.0000273815815785209370, -0.0000062750421119959424, 0.0000016064844184831521, -0.0000004476392158510354, 0.0000001334635874651668, -0.0000000420735334263215, 0.0000000139021990246364, -0.0000000047831848068048, 0.0000000017047897907465, -0.0000000006268389576018, 0.0000000002369824276612, -0.0000000000918641139267, 0.0000000000364278543037, -0.0000000000147475551725, 0.0000000000060851006556, -0.0000000000025552772234, 0.0000000000010906187250, -0.0000000000004725870319, 0.0000000000002076969064, -0.0000000000000924976214, 0.0000000000000417096723, -0.0000000000000190299093, 0.0000000000000087790676, -0.0000000000000040927557, 0.0000000000000019271068, -0.0000000000000009160199, 0.0000000000000004393567, -0.0000000000000002125503, 0.0000000000000001036735, -0.0000000000000000509642, 0.0000000000000000252377, -0.0000000000000000125793 /* -.0187519297793868 -.0091443848250055, .0009010457337825, -.0001394184127221, .0000273815815785, -.0000062750421119, .0000016064844184, -.0000004476392158, .0000001334635874, -.0000000420735334, .0000000139021990, -.0000000047831848, .0000000017047897, -.0000000006268389, .0000000002369824, -.0000000000918641, .0000000000364278, -.0000000000147475, .0000000000060851, -.0000000000025552, .0000000000010906, -.0000000000004725, .0000000000002076, -.0000000000000924, .0000000000000417, -.0000000000000190, .0000000000000087, -.0000000000000040, .0000000000000019, -.0000000000000009, .0000000000000004, -.0000000000000002, .0000000000000001, -.0000000000000000 */ }; static cheb_series aip_cs = { data_aip, 35, -1, 1, 17 }; /* chebyshev for Bi(x) asymptotic factor based on SLATEC bie() Series for BIP on the interval 1.25000D-01 to 3.53553D-01 with weighted error 1.91E-17 log weighted error 16.72 significant figures required 15.35 decimal places required 17.41 Series for BIP2 on the interval 0. to 1.25000D-01 with weighted error 1.05E-18 log weighted error 17.98 significant figures required 16.74 decimal places required 18.71 */ static double data_bip[24] = { -0.08322047477943447, 0.01146118927371174, 0.00042896440718911, -0.00014906639379950, -0.00001307659726787, 0.00000632759839610, -0.00000042226696982, -0.00000019147186298, 0.00000006453106284, -0.00000000784485467, -0.00000000096077216, 0.00000000070004713, -0.00000000017731789, 0.00000000002272089, 0.00000000000165404, -0.00000000000185171, 0.00000000000059576, -0.00000000000012194, 0.00000000000001334, 0.00000000000000172, -0.00000000000000145, 0.00000000000000049, -0.00000000000000011, 0.00000000000000001 }; static cheb_series bip_cs = { data_bip, 23, -1, 1, 14 }; static double data_bip2[29] = { -0.113596737585988679, 0.0041381473947881595, 0.0001353470622119332, 0.0000104273166530153, 0.0000013474954767849, 0.0000001696537405438, -0.0000000100965008656, -0.0000000167291194937, -0.0000000045815364485, 0.0000000003736681366, 0.0000000005766930320, 0.0000000000621812650, -0.0000000000632941202, -0.0000000000149150479, 0.0000000000078896213, 0.0000000000024960513, -0.0000000000012130075, -0.0000000000003740493, 0.0000000000002237727, 0.0000000000000474902, -0.0000000000000452616, -0.0000000000000030172, 0.0000000000000091058, -0.0000000000000009814, -0.0000000000000016429, 0.0000000000000005533, 0.0000000000000002175, -0.0000000000000001737, -0.0000000000000000010 }; static cheb_series bip2_cs = { data_bip2, 28, -1, 1, 10 }; /* assumes x >= 1.0 */ inline static int airy_aie(const double x, gsl_mode_t mode, gsl_sf_result * result) { double sqx = sqrt(x); double z = 2.0/(x*sqx) - 1.0; double y = sqrt(sqx); gsl_sf_result result_c; cheb_eval_mode_e(&aip_cs, z, mode, &result_c); result->val = (0.28125 + result_c.val)/y; result->err = result_c.err/y + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* assumes x >= 2.0 */ static int airy_bie(const double x, gsl_mode_t mode, gsl_sf_result * result) { const double ATR = 8.7506905708484345; const double BTR = -2.0938363213560543; if(x < 4.0) { double sqx = sqrt(x); double z = ATR/(x*sqx) + BTR; double y = sqrt(sqx); gsl_sf_result result_c; cheb_eval_mode_e(&bip_cs, z, mode, &result_c); result->val = (0.625 + result_c.val)/y; result->err = result_c.err/y + GSL_DBL_EPSILON * fabs(result->val); } else { double sqx = sqrt(x); double z = 16.0/(x*sqx) - 1.0; double y = sqrt(sqx); gsl_sf_result result_c; cheb_eval_mode_e(&bip2_cs, z, mode, &result_c); result->val = (0.625 + result_c.val)/y; result->err = result_c.err/y + GSL_DBL_EPSILON * fabs(result->val); } return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_airy_Ai_e(const double x, const gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result mod; gsl_sf_result theta; gsl_sf_result cos_result; int stat_mp = airy_mod_phase(x, mode, &mod, &theta); int stat_cos = gsl_sf_cos_err_e(theta.val, theta.err, &cos_result); result->val = mod.val * cos_result.val; result->err = fabs(mod.val * cos_result.err) + fabs(cos_result.val * mod.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mp, stat_cos); } else if(x <= 1.0) { const double z = x*x*x; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&aif_cs, z, mode, &result_c0); cheb_eval_mode_e(&aig_cs, z, mode, &result_c1); result->val = 0.375 + (result_c0.val - x*(0.25 + result_c1.val)); result->err = result_c0.err + fabs(x*result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double x32 = x * sqrt(x); double s = exp(-2.0*x32/3.0); gsl_sf_result result_aie; int stat_aie = airy_aie(x, mode, &result_aie); result->val = result_aie.val * s; result->err = result_aie.err * s + result->val * x32 * GSL_DBL_EPSILON; result->err += GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return stat_aie; } } int gsl_sf_airy_Ai_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result mod; gsl_sf_result theta; gsl_sf_result cos_result; int stat_mp = airy_mod_phase(x, mode, &mod, &theta); int stat_cos = gsl_sf_cos_err_e(theta.val, theta.err, &cos_result); result->val = mod.val * cos_result.val; result->err = fabs(mod.val * cos_result.err) + fabs(cos_result.val * mod.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mp, stat_cos); } else if(x <= 1.0) { const double z = x*x*x; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&aif_cs, z, mode, &result_c0); cheb_eval_mode_e(&aig_cs, z, mode, &result_c1); result->val = 0.375 + (result_c0.val - x*(0.25 + result_c1.val)); result->err = result_c0.err + fabs(x*result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); if(x > 0.0) { const double scale = exp(2.0/3.0 * sqrt(z)); result->val *= scale; result->err *= scale; } return GSL_SUCCESS; } else { return airy_aie(x, mode, result); } } int gsl_sf_airy_Bi_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result mod; gsl_sf_result theta; gsl_sf_result sin_result; int stat_mp = airy_mod_phase(x, mode, &mod, &theta); int stat_sin = gsl_sf_sin_err_e(theta.val, theta.err, &sin_result); result->val = mod.val * sin_result.val; result->err = fabs(mod.val * sin_result.err) + fabs(sin_result.val * mod.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mp, stat_sin); } else if(x < 1.0) { const double z = x*x*x; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&bif_cs, z, mode, &result_c0); cheb_eval_mode_e(&big_cs, z, mode, &result_c1); result->val = 0.625 + result_c0.val + x*(0.4375 + result_c1.val); result->err = result_c0.err + fabs(x * result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x <= 2.0) { const double z = (2.0*x*x*x - 9.0)/7.0; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&bif2_cs, z, mode, &result_c0); cheb_eval_mode_e(&big2_cs, z, mode, &result_c1); result->val = 1.125 + result_c0.val + x*(0.625 + result_c1.val); result->err = result_c0.err + fabs(x * result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double y = 2.0*x*sqrt(x)/3.0; const double s = exp(y); if(y > GSL_LOG_DBL_MAX - 1.0) { OVERFLOW_ERROR(result); } else { gsl_sf_result result_bie; int stat_bie = airy_bie(x, mode, &result_bie); result->val = result_bie.val * s; result->err = result_bie.err * s + fabs(1.5*y * (GSL_DBL_EPSILON * result->val)); result->err += GSL_DBL_EPSILON * fabs(result->val); return stat_bie; } } } int gsl_sf_airy_Bi_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result mod; gsl_sf_result theta; gsl_sf_result sin_result; int stat_mp = airy_mod_phase(x, mode, &mod, &theta); int stat_sin = gsl_sf_sin_err_e(theta.val, theta.err, &sin_result); result->val = mod.val * sin_result.val; result->err = fabs(mod.val * sin_result.err) + fabs(sin_result.val * mod.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mp, stat_sin); } else if(x < 1.0) { const double z = x*x*x; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&bif_cs, z, mode, &result_c0); cheb_eval_mode_e(&big_cs, z, mode, &result_c1); result->val = 0.625 + result_c0.val + x*(0.4375 + result_c1.val); result->err = result_c0.err + fabs(x * result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); if(x > 0.0) { const double scale = exp(-2.0/3.0 * sqrt(z)); result->val *= scale; result->err *= scale; } return GSL_SUCCESS; } else if(x <= 2.0) { const double x3 = x*x*x; const double z = (2.0*x3 - 9.0)/7.0; const double s = exp(-2.0/3.0 * sqrt(x3)); gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&bif2_cs, z, mode, &result_c0); cheb_eval_mode_e(&big2_cs, z, mode, &result_c1); result->val = s * (1.125 + result_c0.val + x*(0.625 + result_c1.val)); result->err = s * (result_c0.err + fabs(x * result_c1.err)); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { return airy_bie(x, mode, result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_airy_Ai(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Ai_e(x, mode, &result)); } double gsl_sf_airy_Ai_scaled(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Ai_scaled_e(x, mode, &result)); } double gsl_sf_airy_Bi(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Bi_e(x, mode, &result)); } double gsl_sf_airy_Bi_scaled(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Bi_scaled_e(x, mode, &result)); } sources_5316/external/gsl/gsl_block__file.c0000664000176700017670000000473011723710247017605 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_block.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_block__fwrite_source.c" #include "gsl_block__fprintf_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_block_short.h0000664000176700017670000000442111705263724017673 0ustar paulpaul/* block/gsl_block_short.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_SHORT_H__ #define __GSL_BLOCK_SHORT_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_short_struct { size_t size; short *data; }; typedef struct gsl_block_short_struct gsl_block_short; gsl_block_short *gsl_block_short_alloc (const size_t n); gsl_block_short *gsl_block_short_calloc (const size_t n); void gsl_block_short_free (gsl_block_short * b); int gsl_block_short_fread (FILE * stream, gsl_block_short * b); int gsl_block_short_fwrite (FILE * stream, const gsl_block_short * b); int gsl_block_short_fscanf (FILE * stream, gsl_block_short * b); int gsl_block_short_fprintf (FILE * stream, const gsl_block_short * b, const char *format); int gsl_block_short_raw_fread (FILE * stream, short * b, const size_t n, const size_t stride); int gsl_block_short_raw_fwrite (FILE * stream, const short * b, const size_t n, const size_t stride); int gsl_block_short_raw_fscanf (FILE * stream, short * b, const size_t n, const size_t stride); int gsl_block_short_raw_fprintf (FILE * stream, const short * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_short_size (const gsl_block_short * b); short * gsl_block_short_data (const gsl_block_short * b); __END_DECLS #endif /* __GSL_BLOCK_SHORT_H__ */ sources_5316/external/gsl/gsl_specfunc__bessel_i.c0000664000176700017670000002153611723710247021172 0ustar paulpaul/* specfunc/bessel_i.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" /* i_{l+1}/i_l */ static int bessel_il_CF1(const int l, const double x, const double threshold, double * ratio) { const int kmax = 2000; double tk = 1.0; double sum = 1.0; double rhok = 0.0; int k; for(k=1; k<=kmax; k++) { double ak = (x/(2.0*l+1.0+2.0*k)) * (x/(2.0*l+3.0+2.0*k)); rhok = -ak*(1.0 + rhok)/(1.0 + ak*(1.0 + rhok)); tk *= rhok; sum += tk; if(fabs(tk/sum) < threshold) break; } *ratio = x/(2.0*l+3.0) * sum; if(k == kmax) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_i0_scaled_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 0.2) { const double eax = exp(-ax); const double y = ax*ax; const double c1 = 1.0/6.0; const double c2 = 1.0/120.0; const double c3 = 1.0/5040.0; const double c4 = 1.0/362880.0; const double c5 = 1.0/39916800.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*c5)))); result->val = eax * sum; result->err = 2.0 * GSL_DBL_EPSILON * result->val; } else if(ax < -0.5*GSL_LOG_DBL_EPSILON) { result->val = (1.0 - exp(-2.0*ax))/(2.0*ax); result->err = 2.0 * GSL_DBL_EPSILON * result->val; } else { result->val = 1.0/(2.0*ax); result->err = 2.0 * GSL_DBL_EPSILON * result->val; } return GSL_SUCCESS; } int gsl_sf_bessel_i1_scaled_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 3.0*GSL_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(ax < 0.25) { const double eax = exp(-ax); const double y = x*x; const double c1 = 1.0/10.0; const double c2 = 1.0/280.0; const double c3 = 1.0/15120.0; const double c4 = 1.0/1330560.0; const double c5 = 1.0/172972800.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*c5)))); result->val = eax * x/3.0 * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double ex = exp(-2.0*ax); result->val = 0.5 * (ax*(1.0+ex) - (1.0-ex)) / (ax*ax); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(x < 0.0) result->val = -result->val; return GSL_SUCCESS; } } int gsl_sf_bessel_i2_scaled_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(ax < 4.0*GSL_SQRT_DBL_MIN) { UNDERFLOW_ERROR(result); } else if(ax < 0.25) { const double y = x*x; const double c1 = 1.0/14.0; const double c2 = 1.0/504.0; const double c3 = 1.0/33264.0; const double c4 = 1.0/3459456.0; const double c5 = 1.0/518918400.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*c5)))); const double pre = exp(-ax) * x*x/15.0; result->val = pre * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double ex = exp(-2.0*ax); double x2 = x*x; result->val = 0.5 * ((3.0+x2)*(1.0-ex) - 3.0*ax*(1.0+ex))/(ax*ax*ax); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_il_scaled_e(const int l, double x, gsl_sf_result * result) { double sgn = 1.0; double ax = fabs(x); if(x < 0.0) { /* i_l(-x) = (-1)^l i_l(x) */ sgn = ( GSL_IS_ODD(l) ? -1.0 : 1.0 ); x = -x; } if(l < 0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = ( l == 0 ? 1.0 : 0.0 ); result->err = 0.0; return GSL_SUCCESS; } else if(l == 0) { gsl_sf_result il; int stat_il = gsl_sf_bessel_i0_scaled_e(x, &il); result->val = sgn * il.val; result->err = il.err; return stat_il; } else if(l == 1) { gsl_sf_result il; int stat_il = gsl_sf_bessel_i1_scaled_e(x, &il); result->val = sgn * il.val; result->err = il.err; return stat_il; } else if(l == 2) { gsl_sf_result il; int stat_il = gsl_sf_bessel_i2_scaled_e(x, &il); result->val = sgn * il.val; result->err = il.err; return stat_il; } else if(x*x < 10.0*(l+1.5)/M_E) { gsl_sf_result b; int stat = gsl_sf_bessel_IJ_taylor_e(l+0.5, x, 1, 50, GSL_DBL_EPSILON, &b); double pre = exp(-ax) * sqrt((0.5*M_PI)/x); result->val = sgn * pre * b.val; result->err = pre * b.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } else if(l < 150) { gsl_sf_result i0_scaled; int stat_i0 = gsl_sf_bessel_i0_scaled_e(ax, &i0_scaled); double rat; int stat_CF1 = bessel_il_CF1(l, ax, GSL_DBL_EPSILON, &rat); double iellp1 = rat * GSL_SQRT_DBL_MIN; double iell = GSL_SQRT_DBL_MIN; double iellm1; int ell; for(ell = l; ell >= 1; ell--) { iellm1 = iellp1 + (2*ell + 1)/x * iell; iellp1 = iell; iell = iellm1; } result->val = sgn * i0_scaled.val * (GSL_SQRT_DBL_MIN / iell); result->err = i0_scaled.err * (GSL_SQRT_DBL_MIN / iell); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_i0, stat_CF1); } else if(GSL_MIN(0.29/(l*l+1.0), 0.5/(l*l+1.0+x*x)) < 0.5*GSL_ROOT3_DBL_EPSILON) { int status = gsl_sf_bessel_Inu_scaled_asymp_unif_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= sgn * pre; result->err *= pre; return status; } else { /* recurse down from safe values */ double rt_term = sqrt((0.5*M_PI)/x); const int LMAX = 2 + (int) (1.2 / GSL_ROOT6_DBL_EPSILON); gsl_sf_result r_iellp1; gsl_sf_result r_iell; int stat_a1 = gsl_sf_bessel_Inu_scaled_asymp_unif_e(LMAX + 1 + 0.5, x, &r_iellp1); int stat_a2 = gsl_sf_bessel_Inu_scaled_asymp_unif_e(LMAX + 0.5, x, &r_iell); double iellp1 = r_iellp1.val; double iell = r_iell.val; double iellm1 = 0.0; int ell; iellp1 *= rt_term; iell *= rt_term; for(ell = LMAX; ell >= l+1; ell--) { iellm1 = iellp1 + (2*ell + 1)/x * iell; iellp1 = iell; iell = iellm1; } result->val = sgn * iellm1; result->err = fabs(result->val)*(GSL_DBL_EPSILON + fabs(r_iellp1.err/r_iellp1.val) + fabs(r_iell.err/r_iell.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_a1, stat_a2); } } int gsl_sf_bessel_il_scaled_array(const int lmax, const double x, double * result_array) { if(x == 0.0) { int ell; result_array[0] = 1.0; for (ell = lmax; ell >= 1; ell--) { result_array[ell] = 0.0; }; return GSL_SUCCESS; } else { int ell; gsl_sf_result r_iellp1; gsl_sf_result r_iell; int stat_0 = gsl_sf_bessel_il_scaled_e(lmax+1, x, &r_iellp1); int stat_1 = gsl_sf_bessel_il_scaled_e(lmax, x, &r_iell); double iellp1 = r_iellp1.val; double iell = r_iell.val; double iellm1; result_array[lmax] = iell; for(ell = lmax; ell >= 1; ell--) { iellm1 = iellp1 + (2*ell + 1)/x * iell; iellp1 = iell; iell = iellm1; result_array[ell-1] = iellm1; } return GSL_ERROR_SELECT_2(stat_0, stat_1); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_i0_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_i0_scaled_e(x, &result)); } double gsl_sf_bessel_i1_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_i1_scaled_e(x, &result)); } double gsl_sf_bessel_i2_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_i2_scaled_e(x, &result)); } double gsl_sf_bessel_il_scaled(const int l, const double x) { EVAL_RESULT(gsl_sf_bessel_il_scaled_e(l, x, &result)); } sources_5316/external/gsl/gsl_min__fsolver.c0000664000176700017670000001163011723710247020034 0ustar paulpaul/* min/fsolver.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_min.h" #include "gsl_min__min.h" static int compute_f_values (gsl_function * f, double x_minimum, double * f_minimum, double x_lower, double * f_lower, double x_upper, double * f_upper); static int compute_f_values (gsl_function * f, double x_minimum, double * f_minimum, double x_lower, double * f_lower, double x_upper, double * f_upper) { SAFE_FUNC_CALL(f, x_lower, f_lower); SAFE_FUNC_CALL(f, x_upper, f_upper); SAFE_FUNC_CALL(f, x_minimum, f_minimum); return GSL_SUCCESS; } int gsl_min_fminimizer_set (gsl_min_fminimizer * s, gsl_function * f, double x_minimum, double x_lower, double x_upper) { int status ; double f_minimum, f_lower, f_upper; status = compute_f_values (f, x_minimum, &f_minimum, x_lower, &f_lower, x_upper, &f_upper); if (status != GSL_SUCCESS) { return status ; } status = gsl_min_fminimizer_set_with_values (s, f, x_minimum, f_minimum, x_lower, f_lower, x_upper, f_upper); return status; } gsl_min_fminimizer * gsl_min_fminimizer_alloc (const gsl_min_fminimizer_type * T) { gsl_min_fminimizer * s = (gsl_min_fminimizer *) malloc (sizeof (gsl_min_fminimizer)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for minimizer struct", GSL_ENOMEM, 0); }; s->state = malloc (T->size); if (s->state == 0) { free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for minimizer state", GSL_ENOMEM, 0); }; s->type = T ; s->function = NULL; return s; } int gsl_min_fminimizer_set_with_values (gsl_min_fminimizer * s, gsl_function * f, double x_minimum, double f_minimum, double x_lower, double f_lower, double x_upper, double f_upper) { s->function = f; s->x_minimum = x_minimum; s->x_lower = x_lower; s->x_upper = x_upper; if (x_lower > x_upper) { GSL_ERROR ("invalid interval (lower > upper)", GSL_EINVAL); } if (x_minimum >= x_upper || x_minimum <= x_lower) { GSL_ERROR ("x_minimum must lie inside interval (lower < x < upper)", GSL_EINVAL); } s->f_lower = f_lower; s->f_upper = f_upper; s->f_minimum = f_minimum; if (f_minimum >= f_lower || f_minimum >= f_upper) { GSL_ERROR ("endpoints do not enclose a minimum", GSL_EINVAL); } return (s->type->set) (s->state, s->function, x_minimum, f_minimum, x_lower, f_lower, x_upper, f_upper); } int gsl_min_fminimizer_iterate (gsl_min_fminimizer * s) { return (s->type->iterate) (s->state, s->function, &(s->x_minimum), &(s->f_minimum), &(s->x_lower), &(s->f_lower), &(s->x_upper), &(s->f_upper)); } void gsl_min_fminimizer_free (gsl_min_fminimizer * s) { free (s->state); free (s); } const char * gsl_min_fminimizer_name (const gsl_min_fminimizer * s) { return s->type->name; } /* Deprecated, use x_minimum instead */ double gsl_min_fminimizer_minimum (const gsl_min_fminimizer * s) { return s->x_minimum; } double gsl_min_fminimizer_x_minimum (const gsl_min_fminimizer * s) { return s->x_minimum; } double gsl_min_fminimizer_x_lower (const gsl_min_fminimizer * s) { return s->x_lower; } double gsl_min_fminimizer_x_upper (const gsl_min_fminimizer * s) { return s->x_upper; } double gsl_min_fminimizer_f_minimum (const gsl_min_fminimizer * s) { return s->f_minimum; } double gsl_min_fminimizer_f_lower (const gsl_min_fminimizer * s) { return s->f_lower; } double gsl_min_fminimizer_f_upper (const gsl_min_fminimizer * s) { return s->f_upper; } sources_5316/external/gsl/gsl_matrix_long.h0000664000176700017670000002643611705263724017717 0ustar paulpaul/* matrix/gsl_matrix_long.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_LONG_H__ #define __GSL_MATRIX_LONG_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_long.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; long * data; gsl_block_long * block; int owner; } gsl_matrix_long; typedef struct { gsl_matrix_long matrix; } _gsl_matrix_long_view; typedef _gsl_matrix_long_view gsl_matrix_long_view; typedef struct { gsl_matrix_long matrix; } _gsl_matrix_long_const_view; typedef const _gsl_matrix_long_const_view gsl_matrix_long_const_view; /* Allocation */ gsl_matrix_long * gsl_matrix_long_alloc (const size_t n1, const size_t n2); gsl_matrix_long * gsl_matrix_long_calloc (const size_t n1, const size_t n2); gsl_matrix_long * gsl_matrix_long_alloc_from_block (gsl_block_long * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_long * gsl_matrix_long_alloc_from_matrix (gsl_matrix_long * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_long * gsl_vector_long_alloc_row_from_matrix (gsl_matrix_long * m, const size_t i); gsl_vector_long * gsl_vector_long_alloc_col_from_matrix (gsl_matrix_long * m, const size_t j); void gsl_matrix_long_free (gsl_matrix_long * m); /* Views */ _gsl_matrix_long_view gsl_matrix_long_submatrix (gsl_matrix_long * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_long_view gsl_matrix_long_row (gsl_matrix_long * m, const size_t i); _gsl_vector_long_view gsl_matrix_long_column (gsl_matrix_long * m, const size_t j); _gsl_vector_long_view gsl_matrix_long_diagonal (gsl_matrix_long * m); _gsl_vector_long_view gsl_matrix_long_subdiagonal (gsl_matrix_long * m, const size_t k); _gsl_vector_long_view gsl_matrix_long_superdiagonal (gsl_matrix_long * m, const size_t k); _gsl_vector_long_view gsl_matrix_long_subrow (gsl_matrix_long * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_long_view gsl_matrix_long_subcolumn (gsl_matrix_long * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_long_view gsl_matrix_long_view_array (long * base, const size_t n1, const size_t n2); _gsl_matrix_long_view gsl_matrix_long_view_array_with_tda (long * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_long_view gsl_matrix_long_view_vector (gsl_vector_long * v, const size_t n1, const size_t n2); _gsl_matrix_long_view gsl_matrix_long_view_vector_with_tda (gsl_vector_long * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_long_const_view gsl_matrix_long_const_submatrix (const gsl_matrix_long * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_long_const_view gsl_matrix_long_const_row (const gsl_matrix_long * m, const size_t i); _gsl_vector_long_const_view gsl_matrix_long_const_column (const gsl_matrix_long * m, const size_t j); _gsl_vector_long_const_view gsl_matrix_long_const_diagonal (const gsl_matrix_long * m); _gsl_vector_long_const_view gsl_matrix_long_const_subdiagonal (const gsl_matrix_long * m, const size_t k); _gsl_vector_long_const_view gsl_matrix_long_const_superdiagonal (const gsl_matrix_long * m, const size_t k); _gsl_vector_long_const_view gsl_matrix_long_const_subrow (const gsl_matrix_long * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_long_const_view gsl_matrix_long_const_subcolumn (const gsl_matrix_long * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_long_const_view gsl_matrix_long_const_view_array (const long * base, const size_t n1, const size_t n2); _gsl_matrix_long_const_view gsl_matrix_long_const_view_array_with_tda (const long * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_long_const_view gsl_matrix_long_const_view_vector (const gsl_vector_long * v, const size_t n1, const size_t n2); _gsl_matrix_long_const_view gsl_matrix_long_const_view_vector_with_tda (const gsl_vector_long * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ long gsl_matrix_long_get(const gsl_matrix_long * m, const size_t i, const size_t j); void gsl_matrix_long_set(gsl_matrix_long * m, const size_t i, const size_t j, const long x); long * gsl_matrix_long_ptr(gsl_matrix_long * m, const size_t i, const size_t j); const long * gsl_matrix_long_const_ptr(const gsl_matrix_long * m, const size_t i, const size_t j); void gsl_matrix_long_set_zero (gsl_matrix_long * m); void gsl_matrix_long_set_identity (gsl_matrix_long * m); void gsl_matrix_long_set_all (gsl_matrix_long * m, long x); int gsl_matrix_long_fread (FILE * stream, gsl_matrix_long * m) ; int gsl_matrix_long_fwrite (FILE * stream, const gsl_matrix_long * m) ; int gsl_matrix_long_fscanf (FILE * stream, gsl_matrix_long * m); int gsl_matrix_long_fprintf (FILE * stream, const gsl_matrix_long * m, const char * format); int gsl_matrix_long_memcpy(gsl_matrix_long * dest, const gsl_matrix_long * src); int gsl_matrix_long_swap(gsl_matrix_long * m1, gsl_matrix_long * m2); int gsl_matrix_long_swap_rows(gsl_matrix_long * m, const size_t i, const size_t j); int gsl_matrix_long_swap_columns(gsl_matrix_long * m, const size_t i, const size_t j); int gsl_matrix_long_swap_rowcol(gsl_matrix_long * m, const size_t i, const size_t j); int gsl_matrix_long_transpose (gsl_matrix_long * m); int gsl_matrix_long_transpose_memcpy (gsl_matrix_long * dest, const gsl_matrix_long * src); long gsl_matrix_long_max (const gsl_matrix_long * m); long gsl_matrix_long_min (const gsl_matrix_long * m); void gsl_matrix_long_minmax (const gsl_matrix_long * m, long * min_out, long * max_out); void gsl_matrix_long_max_index (const gsl_matrix_long * m, size_t * imax, size_t *jmax); void gsl_matrix_long_min_index (const gsl_matrix_long * m, size_t * imin, size_t *jmin); void gsl_matrix_long_minmax_index (const gsl_matrix_long * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_long_isnull (const gsl_matrix_long * m); int gsl_matrix_long_ispos (const gsl_matrix_long * m); int gsl_matrix_long_isneg (const gsl_matrix_long * m); int gsl_matrix_long_isnonneg (const gsl_matrix_long * m); int gsl_matrix_long_add (gsl_matrix_long * a, const gsl_matrix_long * b); int gsl_matrix_long_sub (gsl_matrix_long * a, const gsl_matrix_long * b); int gsl_matrix_long_mul_elements (gsl_matrix_long * a, const gsl_matrix_long * b); int gsl_matrix_long_div_elements (gsl_matrix_long * a, const gsl_matrix_long * b); int gsl_matrix_long_scale (gsl_matrix_long * a, const double x); int gsl_matrix_long_add_constant (gsl_matrix_long * a, const double x); int gsl_matrix_long_add_diagonal (gsl_matrix_long * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_long_get_row(gsl_vector_long * v, const gsl_matrix_long * m, const size_t i); int gsl_matrix_long_get_col(gsl_vector_long * v, const gsl_matrix_long * m, const size_t j); int gsl_matrix_long_set_row(gsl_matrix_long * m, const size_t i, const gsl_vector_long * v); int gsl_matrix_long_set_col(gsl_matrix_long * m, const size_t j, const gsl_vector_long * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline long gsl_matrix_long_get(const gsl_matrix_long * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_long_set(gsl_matrix_long * m, const size_t i, const size_t j, const long x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline long * gsl_matrix_long_ptr(gsl_matrix_long * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (long *) (m->data + (i * m->tda + j)) ; } extern inline const long * gsl_matrix_long_const_ptr(const gsl_matrix_long * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const long *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_LONG_H__ */ sources_5316/external/gsl/gsl_cblas__dtbmv.c0000664000176700017670000000063511723710247017774 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dtbmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const double *A, const int lda, double *X, const int incX) { #define BASE double #include "gsl_cblas__source_tbmv_r.h" #undef BASE } sources_5316/external/gsl/gsl_permute_complex_float.h0000664000176700017670000000273711705263724021767 0ustar paulpaul/* permutation/gsl_permute_complex_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_COMPLEX_FLOAT_H__ #define __GSL_PERMUTE_COMPLEX_FLOAT_H__ #include #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_complex_float (const size_t * p, float * data, const size_t stride, const size_t n); int gsl_permute_complex_float_inverse (const size_t * p, float * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_COMPLEX_FLOAT_H__ */ sources_5316/external/gsl/gsl_permute_vector_uint.h0000664000176700017670000000265511705263724021473 0ustar paulpaul/* permutation/gsl_permute_vector_uint.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_UINT_H__ #define __GSL_PERMUTE_VECTOR_UINT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_uint.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_uint (const gsl_permutation * p, gsl_vector_uint * v); int gsl_permute_vector_uint_inverse (const gsl_permutation * p, gsl_vector_uint * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_UINT_H__ */ sources_5316/external/gsl/gsl_ieee-utils__standardize.c0000664000176700017670000000257611723710247022157 0ustar paulpaul/* ieee-utils/standardize.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void make_float_bigendian (float * x); static void make_double_bigendian (double * x); static void make_float_bigendian (float * x) { union { float f; unsigned char b[4]; } u,v; u.f = *x ; v.b[0]=u.b[3] ; v.b[1]=u.b[2] ; v.b[2]=u.b[1] ; v.b[3]=u.b[0] ; *x=v.f ; } static void make_double_bigendian (double * x) { union { double d; unsigned char b[8]; } u,v; u.d = *x ; v.b[0]=u.b[7] ; v.b[1]=u.b[6] ; v.b[2]=u.b[5] ; v.b[3]=u.b[4] ; v.b[4]=u.b[3] ; v.b[5]=u.b[2] ; v.b[6]=u.b[1] ; v.b[7]=u.b[0] ; *x=v.d ; } sources_5316/external/gsl/gsl_statistics__absdev_source.c0000664000176700017670000000305011723710247022604 0ustar paulpaul/* statistics/absdev_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,absdev) (const BASE data[], const size_t stride, const size_t n) { const double mean = FUNCTION(gsl_stats,mean)(data, stride, n); return FUNCTION(gsl_stats,absdev_m)(data, stride, n, mean); } double FUNCTION(gsl_stats,absdev_m) (const BASE data[], const size_t stride, const size_t n, const double mean) { /* takes a dataset and finds the absolute deviation */ double sum = 0, absdev; size_t i; /* find the sum of the absolute deviations */ for (i = 0; i < n; i++) { const double delta = fabs(data[i * stride] - mean); sum += delta; } absdev = sum / n; return absdev; } sources_5316/external/gsl/gsl_sf__laguerre.c0000644000176700017670000002335110710226217020002 0ustar paulpaul/* specfunc/laguerre.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_laguerre.h" #include "gsl_sf__error.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on the large 2b-4a asymptotic for 1F1 * [Abramowitz+Stegun, 13.5.21] * L^a_n(x) = (a+1)_n / n! 1F1(-n,a+1,x) * * The second term (ser_term2) is from Slater,"The Confluent * Hypergeometric Function" p.73. I think there may be an error in * the first term of the expression given there, comparing with AS * 13.5.21 (cf sin(a\pi+\Theta) vs sin(a\pi) + sin(\Theta)) - but the * second term appears correct. * */ static int laguerre_large_n(const int n, const double alpha, const double x, gsl_sf_result * result) { const double a = -n; const double b = alpha + 1.0; const double eta = 2.0*b - 4.0*a; const double cos2th = x/eta; const double sin2th = 1.0 - cos2th; const double eps = asin(sqrt(cos2th)); /* theta = pi/2 - eps */ const double pre_h = 0.25*M_PI*M_PI*eta*eta*cos2th*sin2th; gsl_sf_result lg_b; gsl_sf_result lnfact; int stat_lg = gsl_sf_lngamma_e(b+n, &lg_b); int stat_lf = gsl_sf_lnfact_e(n, &lnfact); double pre_term1 = 0.5*(1.0-b)*log(0.25*x*eta); double pre_term2 = 0.25*log(pre_h); double lnpre_val = lg_b.val - lnfact.val + 0.5*x + pre_term1 - pre_term2; double lnpre_err = lg_b.err + lnfact.err + GSL_DBL_EPSILON * (fabs(pre_term1)+fabs(pre_term2)); double phi1 = 0.25*eta*(2*eps + sin(2.0*eps)); double ser_term1 = -sin(phi1); double A1 = (1.0/12.0)*(5.0/(4.0*sin2th)+(3.0*b*b-6.0*b+2.0)*sin2th - 1.0); double ser_term2 = -A1 * cos(phi1)/(0.25*eta*sin(2.0*eps)); double ser_val = ser_term1 + ser_term2; double ser_err = ser_term2*ser_term2 + GSL_DBL_EPSILON * (fabs(ser_term1) + fabs(ser_term2)); int stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, ser_val, ser_err, result); result->err += 2.0 * GSL_SQRT_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_e, stat_lf, stat_lg); } /* Evaluate polynomial based on confluent hypergeometric representation. * * L^a_n(x) = (a+1)_n / n! 1F1(-n,a+1,x) * * assumes n > 0 and a != negative integer greater than -n */ static int laguerre_n_cp(const int n, const double a, const double x, gsl_sf_result * result) { gsl_sf_result lnfact; gsl_sf_result lg1; gsl_sf_result lg2; double s1, s2; int stat_f = gsl_sf_lnfact_e(n, &lnfact); int stat_g1 = gsl_sf_lngamma_sgn_e(a+1.0+n, &lg1, &s1); int stat_g2 = gsl_sf_lngamma_sgn_e(a+1.0, &lg2, &s2); double poly_1F1_val = 1.0; double poly_1F1_err = 0.0; int stat_e; int k; double lnpre_val = (lg1.val - lg2.val) - lnfact.val; double lnpre_err = lg1.err + lg2.err + lnfact.err + 2.0 * GSL_DBL_EPSILON * fabs(lnpre_val); for(k=n-1; k>=0; k--) { double t = (-n+k)/(a+1.0+k) * (x/(k+1)); double r = t + 1.0/poly_1F1_val; if(r > 0.9*GSL_DBL_MAX/poly_1F1_val) { /* internal error only, don't call the error handler */ INTERNAL_OVERFLOW_ERROR(result); } else { /* Collect the Horner terms. */ poly_1F1_val = 1.0 + t * poly_1F1_val; poly_1F1_err += GSL_DBL_EPSILON + fabs(t) * poly_1F1_err; } } stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, poly_1F1_val, poly_1F1_err, result); return GSL_ERROR_SELECT_4(stat_e, stat_f, stat_g1, stat_g2); } /* Evaluate the polynomial based on the confluent hypergeometric * function in a safe way, with no restriction on the arguments. * * assumes x != 0 */ static int laguerre_n_poly_safe(const int n, const double a, const double x, gsl_sf_result * result) { const double b = a + 1.0; const double mx = -x; const double tc_sgn = (x < 0.0 ? 1.0 : (GSL_IS_ODD(n) ? -1.0 : 1.0)); gsl_sf_result tc; int stat_tc = gsl_sf_taylorcoeff_e(n, fabs(x), &tc); if(stat_tc == GSL_SUCCESS) { double term = tc.val * tc_sgn; double sum_val = term; double sum_err = tc.err; int k; for(k=n-1; k>=0; k--) { term *= ((b+k)/(n-k))*(k+1.0)/mx; sum_val += term; sum_err += 4.0 * GSL_DBL_EPSILON * fabs(term); } result->val = sum_val; result->err = sum_err + 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(stat_tc == GSL_EOVRFLW) { result->val = 0.0; /* FIXME: should be Inf */ result->err = 0.0; return stat_tc; } else { result->val = 0.0; result->err = 0.0; return stat_tc; } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_laguerre_1_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { result->val = 1.0 + a - x; result->err = 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(a) + fabs(x)); return GSL_SUCCESS; } } int gsl_sf_laguerre_2_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(a == -2.0) { result->val = 0.5*x*x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double c0 = 0.5 * (2.0+a)*(1.0+a); double c1 = -(2.0+a); double c2 = -0.5/(2.0+a); result->val = c0 + c1*x*(1.0 + c2*x); result->err = 2.0 * GSL_DBL_EPSILON * (fabs(c0) + 2.0 * fabs(c1*x) * (1.0 + 2.0 * fabs(c2*x))); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_laguerre_3_e(const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(a == -2.0) { double x2_6 = x*x/6.0; result->val = x2_6 * (3.0 - x); result->err = x2_6 * (3.0 + fabs(x)) * 2.0 * GSL_DBL_EPSILON; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(a == -3.0) { result->val = -x*x/6.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double c0 = (3.0+a)*(2.0+a)*(1.0+a) / 6.0; double c1 = -c0 * 3.0 / (1.0+a); double c2 = -1.0/(2.0+a); double c3 = -1.0/(3.0*(3.0+a)); result->val = c0 + c1*x*(1.0 + c2*x*(1.0 + c3*x)); result->err = 1.0 + 2.0 * fabs(c3*x); result->err = 1.0 + 2.0 * fabs(c2*x) * result->err; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(c0) + 2.0 * fabs(c1*x) * result->err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_laguerre_n_e(const int n, const double a, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(n < 0) { DOMAIN_ERROR(result); } else if(n == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(n == 1) { result->val = 1.0 + a - x; result->err = 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(a) + fabs(x)); return GSL_SUCCESS; } else if(x == 0.0) { double product = a + 1.0; int k; for(k=2; k<=n; k++) { product *= (a + k)/k; } result->val = product; result->err = 2.0 * (n + 1.0) * GSL_DBL_EPSILON * fabs(product) + GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < 0.0 && a > -1.0) { /* In this case all the terms in the polynomial * are of the same sign. Note that this also * catches overflows correctly. */ return laguerre_n_cp(n, a, x, result); } else if(n < 5 || (x > 0.0 && a < -n-1)) { /* Either the polynomial will not lose too much accuracy * or all the terms are negative. In any case, * the error estimate here is good. We try both * explicit summation methods, as they have different * characteristics. One may underflow/overflow while the * other does not. */ if(laguerre_n_cp(n, a, x, result) == GSL_SUCCESS) return GSL_SUCCESS; else return laguerre_n_poly_safe(n, a, x, result); } else if(n > 1.0e+07 && x > 0.0 && a > -1.0 && x < 2.0*(a+1.0)+4.0*n) { return laguerre_large_n(n, a, x, result); } else if(a >= 0.0 || (x > 0.0 && a < -n-1)) { gsl_sf_result lg2; int stat_lg2 = gsl_sf_laguerre_2_e(a, x, &lg2); double Lkm1 = 1.0 + a - x; double Lk = lg2.val; double Lkp1; int k; for(k=2; kval = Lk; result->err = (fabs(lg2.err/lg2.val) + GSL_DBL_EPSILON) * n * fabs(Lk); return stat_lg2; } else { /* Despair... or magic? */ return laguerre_n_poly_safe(n, a, x, result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_laguerre_1(double a, double x) { EVAL_RESULT(gsl_sf_laguerre_1_e(a, x, &result)); } double gsl_sf_laguerre_2(double a, double x) { EVAL_RESULT(gsl_sf_laguerre_2_e(a, x, &result)); } double gsl_sf_laguerre_3(double a, double x) { EVAL_RESULT(gsl_sf_laguerre_3_e(a, x, &result)); } double gsl_sf_laguerre_n(int n, double a, double x) { EVAL_RESULT(gsl_sf_laguerre_n_e(n, a, x, &result)); } sources_5316/external/gsl/gsl_rng__file.c0000664000176700017670000000257211723710247017303 0ustar paulpaul/* rng/file.c * * Copyright (C) 2003 Olaf Lenz * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_rng.h" int gsl_rng_fread (FILE * stream, gsl_rng * r) { size_t n = r->type->size ; char * state = r->state; size_t items = fread (state, 1, n, stream); if (items != n) { GSL_ERROR ("fread failed", GSL_EFAILED); } return GSL_SUCCESS; } int gsl_rng_fwrite (FILE * stream, const gsl_rng * r) { size_t n = r->type->size ; char * state = r->state; size_t items = fwrite (state, 1, n, stream); if (items != n) { GSL_ERROR ("fwrite failed", GSL_EFAILED); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_integration__qk51.c0000664000176700017670000001034611723710247020700 0ustar paulpaul/* integration/qk51.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_integration.h" /* Gauss quadrature weights and kronrod quadrature abscissae and weights as evaluated with 80 decimal digit arithmetic by L. W. Fullerton, Bell Labs, Nov. 1981. */ static const double xgk[26] = /* abscissae of the 51-point kronrod rule */ { 0.999262104992609834193457486540341, 0.995556969790498097908784946893902, 0.988035794534077247637331014577406, 0.976663921459517511498315386479594, 0.961614986425842512418130033660167, 0.942974571228974339414011169658471, 0.920747115281701561746346084546331, 0.894991997878275368851042006782805, 0.865847065293275595448996969588340, 0.833442628760834001421021108693570, 0.797873797998500059410410904994307, 0.759259263037357630577282865204361, 0.717766406813084388186654079773298, 0.673566368473468364485120633247622, 0.626810099010317412788122681624518, 0.577662930241222967723689841612654, 0.526325284334719182599623778158010, 0.473002731445714960522182115009192, 0.417885382193037748851814394594572, 0.361172305809387837735821730127641, 0.303089538931107830167478909980339, 0.243866883720988432045190362797452, 0.183718939421048892015969888759528, 0.122864692610710396387359818808037, 0.061544483005685078886546392366797, 0.000000000000000000000000000000000 }; /* xgk[1], xgk[3], ... abscissae of the 25-point gauss rule. xgk[0], xgk[2], ... abscissae to optimally extend the 25-point gauss rule */ static const double wg[13] = /* weights of the 25-point gauss rule */ { 0.011393798501026287947902964113235, 0.026354986615032137261901815295299, 0.040939156701306312655623487711646, 0.054904695975835191925936891540473, 0.068038333812356917207187185656708, 0.080140700335001018013234959669111, 0.091028261982963649811497220702892, 0.100535949067050644202206890392686, 0.108519624474263653116093957050117, 0.114858259145711648339325545869556, 0.119455763535784772228178126512901, 0.122242442990310041688959518945852, 0.123176053726715451203902873079050 }; static const double wgk[26] = /* weights of the 51-point kronrod rule */ { 0.001987383892330315926507851882843, 0.005561932135356713758040236901066, 0.009473973386174151607207710523655, 0.013236229195571674813656405846976, 0.016847817709128298231516667536336, 0.020435371145882835456568292235939, 0.024009945606953216220092489164881, 0.027475317587851737802948455517811, 0.030792300167387488891109020215229, 0.034002130274329337836748795229551, 0.037116271483415543560330625367620, 0.040083825504032382074839284467076, 0.042872845020170049476895792439495, 0.045502913049921788909870584752660, 0.047982537138836713906392255756915, 0.050277679080715671963325259433440, 0.052362885806407475864366712137873, 0.054251129888545490144543370459876, 0.055950811220412317308240686382747, 0.057437116361567832853582693939506, 0.058689680022394207961974175856788, 0.059720340324174059979099291932562, 0.060539455376045862945360267517565, 0.061128509717053048305859030416293, 0.061471189871425316661544131965264, 0.061580818067832935078759824240066 }; /* wgk[25] was calculated from the values of wgk[0..24] */ void gsl_integration_qk51 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc) { double fv1[26], fv2[26]; gsl_integration_qk (26, xgk, wg, wgk, fv1, fv2, f, a, b, result, abserr, resabs, resasc); } sources_5316/external/gsl/gsl_integration__qelg.c0000664000176700017670000001311611723710247021045 0ustar paulpaul/* integration/qelg.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ struct extrapolation_table { size_t n; double rlist2[52]; size_t nres; double res3la[3]; }; static void initialise_table (struct extrapolation_table *table); static void append_table (struct extrapolation_table *table, double y); static void initialise_table (struct extrapolation_table *table) { table->n = 0; table->nres = 0; } #ifdef JUNK static void initialise_table (struct extrapolation_table *table, double y) { table->n = 0; table->rlist2[0] = y; table->nres = 0; } #endif static void append_table (struct extrapolation_table *table, double y) { size_t n; n = table->n; table->rlist2[n] = y; table->n++; } /* static inline void qelg (size_t * n, double epstab[], double * result, double * abserr, double res3la[], size_t * nres); */ static inline void qelg (struct extrapolation_table *table, double *result, double *abserr); static inline void qelg (struct extrapolation_table *table, double *result, double *abserr) { double *epstab = table->rlist2; double *res3la = table->res3la; const size_t n = table->n - 1; const double current = epstab[n]; double absolute = GSL_DBL_MAX; double relative = 5 * GSL_DBL_EPSILON * fabs (current); const size_t newelm = n / 2; const size_t n_orig = n; size_t n_final = n; size_t i; const size_t nres_orig = table->nres; *result = current; *abserr = GSL_DBL_MAX; if (n < 2) { *result = current; *abserr = GSL_MAX_DBL (absolute, relative); return; } epstab[n + 2] = epstab[n]; epstab[n] = GSL_DBL_MAX; for (i = 0; i < newelm; i++) { double res = epstab[n - 2 * i + 2]; double e0 = epstab[n - 2 * i - 2]; double e1 = epstab[n - 2 * i - 1]; double e2 = res; double e1abs = fabs (e1); double delta2 = e2 - e1; double err2 = fabs (delta2); double tol2 = GSL_MAX_DBL (fabs (e2), e1abs) * GSL_DBL_EPSILON; double delta3 = e1 - e0; double err3 = fabs (delta3); double tol3 = GSL_MAX_DBL (e1abs, fabs (e0)) * GSL_DBL_EPSILON; double e3, delta1, err1, tol1, ss; if (err2 <= tol2 && err3 <= tol3) { /* If e0, e1 and e2 are equal to within machine accuracy, convergence is assumed. */ *result = res; absolute = err2 + err3; relative = 5 * GSL_DBL_EPSILON * fabs (res); *abserr = GSL_MAX_DBL (absolute, relative); return; } e3 = epstab[n - 2 * i]; epstab[n - 2 * i] = e1; delta1 = e1 - e3; err1 = fabs (delta1); tol1 = GSL_MAX_DBL (e1abs, fabs (e3)) * GSL_DBL_EPSILON; /* If two elements are very close to each other, omit a part of the table by adjusting the value of n */ if (err1 <= tol1 || err2 <= tol2 || err3 <= tol3) { n_final = 2 * i; break; } ss = (1 / delta1 + 1 / delta2) - 1 / delta3; /* Test to detect irregular behaviour in the table, and eventually omit a part of the table by adjusting the value of n. */ if (fabs (ss * e1) <= 0.0001) { n_final = 2 * i; break; } /* Compute a new element and eventually adjust the value of result. */ res = e1 + 1 / ss; epstab[n - 2 * i] = res; { const double error = err2 + fabs (res - e2) + err3; if (error <= *abserr) { *abserr = error; *result = res; } } } /* Shift the table */ { const size_t limexp = 50 - 1; if (n_final == limexp) { n_final = 2 * (limexp / 2); } } if (n_orig % 2 == 1) { for (i = 0; i <= newelm; i++) { epstab[1 + i * 2] = epstab[i * 2 + 3]; } } else { for (i = 0; i <= newelm; i++) { epstab[i * 2] = epstab[i * 2 + 2]; } } if (n_orig != n_final) { for (i = 0; i <= n_final; i++) { epstab[i] = epstab[n_orig - n_final + i]; } } table->n = n_final + 1; if (nres_orig < 3) { res3la[nres_orig] = *result; *abserr = GSL_DBL_MAX; } else { /* Compute error estimate */ *abserr = (fabs (*result - res3la[2]) + fabs (*result - res3la[1]) + fabs (*result - res3la[0])); res3la[0] = res3la[1]; res3la[1] = res3la[2]; res3la[2] = *result; } /* In QUADPACK the variable table->nres is incremented at the top of qelg, so it increases on every call. This leads to the array res3la being accessed when its elements are still undefined, so I have moved the update to this point so that its value more useful. */ table->nres = nres_orig + 1; *abserr = GSL_MAX_DBL (*abserr, 5 * GSL_DBL_EPSILON * fabs (*result)); return; } sources_5316/external/gsl/gsl_poly.h0000664000176700017670000000704211705263724016347 0ustar paulpaul/* poly/gsl_poly.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_POLY_H__ #define __GSL_POLY_H__ #include #include "gsl_complex.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Evaluate polynomial * * c[0] + c[1] x + c[2] x^2 + ... + c[len-1] x^(len-1) * * exceptions: none */ double gsl_poly_eval(const double c[], const int len, const double x); #ifdef HAVE_INLINE extern inline double gsl_poly_eval(const double c[], const int len, const double x) { int i; double ans = c[len-1]; for(i=len-1; i>0; i--) ans = c[i-1] + x * ans; return ans; } #endif /* HAVE_INLINE */ /* Work with divided-difference polynomials, Abramowitz & Stegun 25.2.26 */ int gsl_poly_dd_init (double dd[], const double x[], const double y[], size_t size); double gsl_poly_dd_eval (const double dd[], const double xa[], const size_t size, const double x); #ifdef HAVE_INLINE extern inline double gsl_poly_dd_eval(const double dd[], const double xa[], const size_t size, const double x) { size_t i; double y = dd[size - 1]; for (i = size - 1; i--;) y = dd[i] + (x - xa[i]) * y; return y; } #endif /* HAVE_INLINE */ int gsl_poly_dd_taylor (double c[], double xp, const double dd[], const double x[], size_t size, double w[]); /* Solve for real or complex roots of the standard quadratic equation, * returning the number of real roots. * * Roots are returned ordered. */ int gsl_poly_solve_quadratic (double a, double b, double c, double * x0, double * x1); int gsl_poly_complex_solve_quadratic (double a, double b, double c, gsl_complex * z0, gsl_complex * z1); /* Solve for real roots of the cubic equation * x^3 + a x^2 + b x + c = 0, returning the * number of real roots. * * Roots are returned ordered. */ int gsl_poly_solve_cubic (double a, double b, double c, double * x0, double * x1, double * x2); int gsl_poly_complex_solve_cubic (double a, double b, double c, gsl_complex * z0, gsl_complex * z1, gsl_complex * z2); /* Solve for the complex roots of a general real polynomial */ typedef struct { size_t nc ; double * matrix ; } gsl_poly_complex_workspace ; gsl_poly_complex_workspace * gsl_poly_complex_workspace_alloc (size_t n); void gsl_poly_complex_workspace_free (gsl_poly_complex_workspace * w); int gsl_poly_complex_solve (const double * a, size_t n, gsl_poly_complex_workspace * w, gsl_complex_packed_ptr z); __END_DECLS #endif /* __GSL_POLY_H__ */ sources_5316/external/gsl/gsl_statistics__skew.c0000664000176700017670000000300711723710247020733 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__skew_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_deriv__deriv.c0000664000176700017670000001342111723710247020013 0ustar paulpaul/* deriv/deriv.c * * Copyright (C) 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_deriv.h" static void central_deriv (const gsl_function * f, double x, double h, double *result, double *abserr_round, double *abserr_trunc) { /* Compute the derivative using the 5-point rule (x-h, x-h/2, x, x+h/2, x+h). Note that the central point is not used. Compute the error using the difference between the 5-point and the 3-point rule (x-h,x,x+h). Again the central point is not used. */ double fm1 = GSL_FN_EVAL (f, x - h); double fp1 = GSL_FN_EVAL (f, x + h); double fmh = GSL_FN_EVAL (f, x - h / 2); double fph = GSL_FN_EVAL (f, x + h / 2); double r3 = 0.5 * (fp1 - fm1); double r5 = (4.0 / 3.0) * (fph - fmh) - (1.0 / 3.0) * r3; double e3 = (fabs (fp1) + fabs (fm1)) * GSL_DBL_EPSILON; double e5 = 2.0 * (fabs (fph) + fabs (fmh)) * GSL_DBL_EPSILON + e3; /* The next term is due to finite precision in x+h = O (eps * x) */ double dy = GSL_MAX (fabs (r3 / h), fabs (r5 / h)) *(fabs (x) / h) * GSL_DBL_EPSILON; /* The truncation error in the r5 approximation itself is O(h^4). However, for safety, we estimate the error from r5-r3, which is O(h^2). By scaling h we will minimise this estimated error, not the actual truncation error in r5. */ *result = r5 / h; *abserr_trunc = fabs ((r5 - r3) / h); /* Estimated truncation error O(h^2) */ *abserr_round = fabs (e5 / h) + dy; /* Rounding error (cancellations) */ } int gsl_deriv_central (const gsl_function * f, double x, double h, double *result, double *abserr) { double r_0, round, trunc, error; central_deriv (f, x, h, &r_0, &round, &trunc); error = round + trunc; if (round < trunc && (round > 0 && trunc > 0)) { double r_opt, round_opt, trunc_opt, error_opt; /* Compute an optimised stepsize to minimize the total error, using the scaling of the truncation error (O(h^2)) and rounding error (O(1/h)). */ double h_opt = h * pow (round / (2.0 * trunc), 1.0 / 3.0); central_deriv (f, x, h_opt, &r_opt, &round_opt, &trunc_opt); error_opt = round_opt + trunc_opt; /* Check that the new error is smaller, and that the new derivative is consistent with the error bounds of the original estimate. */ if (error_opt < error && fabs (r_opt - r_0) < 4.0 * error) { r_0 = r_opt; error = error_opt; } } *result = r_0; *abserr = error; return GSL_SUCCESS; } static void forward_deriv (const gsl_function * f, double x, double h, double *result, double *abserr_round, double *abserr_trunc) { /* Compute the derivative using the 4-point rule (x+h/4, x+h/2, x+3h/4, x+h). Compute the error using the difference between the 4-point and the 2-point rule (x+h/2,x+h). */ double f1 = GSL_FN_EVAL (f, x + h / 4.0); double f2 = GSL_FN_EVAL (f, x + h / 2.0); double f3 = GSL_FN_EVAL (f, x + (3.0 / 4.0) * h); double f4 = GSL_FN_EVAL (f, x + h); double r2 = 2.0*(f4 - f2); double r4 = (22.0 / 3.0) * (f4 - f3) - (62.0 / 3.0) * (f3 - f2) + (52.0 / 3.0) * (f2 - f1); /* Estimate the rounding error for r4 */ double e4 = 2 * 20.67 * (fabs (f4) + fabs (f3) + fabs (f2) + fabs (f1)) * GSL_DBL_EPSILON; /* The next term is due to finite precision in x+h = O (eps * x) */ double dy = GSL_MAX (fabs (r2 / h), fabs (r4 / h)) * fabs (x / h) * GSL_DBL_EPSILON; /* The truncation error in the r4 approximation itself is O(h^3). However, for safety, we estimate the error from r4-r2, which is O(h). By scaling h we will minimise this estimated error, not the actual truncation error in r4. */ *result = r4 / h; *abserr_trunc = fabs ((r4 - r2) / h); /* Estimated truncation error O(h) */ *abserr_round = fabs (e4 / h) + dy; } int gsl_deriv_forward (const gsl_function * f, double x, double h, double *result, double *abserr) { double r_0, round, trunc, error; forward_deriv (f, x, h, &r_0, &round, &trunc); error = round + trunc; if (round < trunc && (round > 0 && trunc > 0)) { double r_opt, round_opt, trunc_opt, error_opt; /* Compute an optimised stepsize to minimize the total error, using the scaling of the estimated truncation error (O(h)) and rounding error (O(1/h)). */ double h_opt = h * pow (round / (trunc), 1.0 / 2.0); forward_deriv (f, x, h_opt, &r_opt, &round_opt, &trunc_opt); error_opt = round_opt + trunc_opt; /* Check that the new error is smaller, and that the new derivative is consistent with the error bounds of the original estimate. */ if (error_opt < error && fabs (r_opt - r_0) < 4.0 * error) { r_0 = r_opt; error = error_opt; } } *result = r_0; *abserr = error; return GSL_SUCCESS; } int gsl_deriv_backward (const gsl_function * f, double x, double h, double *result, double *abserr) { return gsl_deriv_forward (f, x, -h, result, abserr); } sources_5316/external/gsl/gsl_specfunc__bessel_I1.c0000664000176700017670000001531511723710247021211 0ustar paulpaul/* specfunc/bessel_I1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" #define ROOT_EIGHT (2.0*M_SQRT2) /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besi1(), besi1e() */ /* chebyshev expansions series for bi1 on the interval 0. to 9.00000d+00 with weighted error 2.40e-17 log weighted error 16.62 significant figures required 16.23 decimal places required 17.14 series for ai1 on the interval 1.25000d-01 to 3.33333d-01 with weighted error 6.98e-17 log weighted error 16.16 significant figures required 14.53 decimal places required 16.82 series for ai12 on the interval 0. to 1.25000d-01 with weighted error 3.55e-17 log weighted error 16.45 significant figures required 14.69 decimal places required 17.12 */ static double bi1_data[11] = { -0.001971713261099859, 0.407348876675464810, 0.034838994299959456, 0.001545394556300123, 0.000041888521098377, 0.000000764902676483, 0.000000010042493924, 0.000000000099322077, 0.000000000000766380, 0.000000000000004741, 0.000000000000000024 }; static cheb_series bi1_cs = { bi1_data, 10, -1, 1, 10 }; static double ai1_data[21] = { -0.02846744181881479, -0.01922953231443221, -0.00061151858579437, -0.00002069971253350, 0.00000858561914581, 0.00000104949824671, -0.00000029183389184, -0.00000001559378146, 0.00000001318012367, -0.00000000144842341, -0.00000000029085122, 0.00000000012663889, -0.00000000001664947, -0.00000000000166665, 0.00000000000124260, -0.00000000000027315, 0.00000000000002023, 0.00000000000000730, -0.00000000000000333, 0.00000000000000071, -0.00000000000000006 }; static cheb_series ai1_cs = { ai1_data, 20, -1, 1, 11 }; static double ai12_data[22] = { 0.02857623501828014, -0.00976109749136147, -0.00011058893876263, -0.00000388256480887, -0.00000025122362377, -0.00000002631468847, -0.00000000383538039, -0.00000000055897433, -0.00000000001897495, 0.00000000003252602, 0.00000000001412580, 0.00000000000203564, -0.00000000000071985, -0.00000000000040836, -0.00000000000002101, 0.00000000000004273, 0.00000000000001041, -0.00000000000000382, -0.00000000000000186, 0.00000000000000033, 0.00000000000000028, -0.00000000000000003 }; static cheb_series ai12_cs = { ai12_data, 21, -1, 1, 9 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_I1_scaled_e(const double x, gsl_sf_result * result) { const double xmin = 2.0 * GSL_DBL_MIN; const double x_small = ROOT_EIGHT * GSL_SQRT_DBL_EPSILON; const double y = fabs(x); /* CHECK_POINTER(result) */ if(y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(y < xmin) { UNDERFLOW_ERROR(result); } else if(y < x_small) { result->val = 0.5*x; result->err = 0.0; return GSL_SUCCESS; } else if(y <= 3.0) { const double ey = exp(-y); gsl_sf_result c; cheb_eval_e(&bi1_cs, y*y/4.5-1.0, &c); result->val = x * ey * (0.875 + c.val); result->err = ey * c.err + y * GSL_DBL_EPSILON * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(y <= 8.0) { const double sy = sqrt(y); gsl_sf_result c; double b; double s; cheb_eval_e(&ai1_cs, (48.0/y-11.0)/5.0, &c); b = (0.375 + c.val) / sy; s = (x > 0.0 ? 1.0 : -1.0); result->val = s * b; result->err = c.err / sy; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sy = sqrt(y); gsl_sf_result c; double b; double s; cheb_eval_e(&ai12_cs, 16.0/y-1.0, &c); b = (0.375 + c.val) / sy; s = (x > 0.0 ? 1.0 : -1.0); result->val = s * b; result->err = c.err / sy; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_I1_e(const double x, gsl_sf_result * result) { const double xmin = 2.0 * GSL_DBL_MIN; const double x_small = ROOT_EIGHT * GSL_SQRT_DBL_EPSILON; const double y = fabs(x); /* CHECK_POINTER(result) */ if(y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(y < xmin) { UNDERFLOW_ERROR(result); } else if(y < x_small) { result->val = 0.5*x; result->err = 0.0; return GSL_SUCCESS; } else if(y <= 3.0) { gsl_sf_result c; cheb_eval_e(&bi1_cs, y*y/4.5-1.0, &c); result->val = x * (0.875 + c.val); result->err = y * c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(y < GSL_LOG_DBL_MAX) { const double ey = exp(y); gsl_sf_result I1_scaled; gsl_sf_bessel_I1_scaled_e(x, &I1_scaled); result->val = ey * I1_scaled.val; result->err = ey * I1_scaled.err + y * GSL_DBL_EPSILON * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_I1_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_I1_scaled_e(x, &result)); } double gsl_sf_bessel_I1(const double x) { EVAL_RESULT(gsl_sf_bessel_I1_e(x, &result)); } sources_5316/external/gsl/gsl_cdf__flat.c0000664000176700017670000000245311723710247017256 0ustar paulpaul/* cdf/flat.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_flat_P (const double x, const double a, const double b) { double P; if (x < a) { P = 0; } else if (x > b) { P = 1; } else { P = (x-a)/(b-a); } return P; } double gsl_cdf_flat_Q (const double x, const double a, const double b) { double Q; if (x < a) { Q = 1; } else if (x > b) { Q = 0; } else { Q = (b-x)/(b-a); } return Q; } sources_5316/external/gsl/gsl_cblas__ssyr2k.c0000664000176700017670000000072311723710247020113 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ssyr2k (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const float alpha, const float *A, const int lda, const float *B, const int ldb, const float beta, float *C, const int ldc) { #define BASE float #include "gsl_cblas__source_syr2k_r.h" #undef BASE } sources_5316/external/gsl/gsl_ieee-utils__fp-os2emx.c0000664000176700017670000000451711723710247021464 0ustar paulpaul/* ieee-utils/fp-os2.c * * Copyright (C) 2001 Henry Sobotka * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { unsigned mode = 0; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: _control87(PC_24, MCW_PC); break ; case GSL_IEEE_DOUBLE_PRECISION: _control87(PC_53, MCW_PC); break ; case GSL_IEEE_EXTENDED_PRECISION: _control87(PC_64, MCW_PC); break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: _control87(RC_NEAR, MCW_RC); break ; case GSL_IEEE_ROUND_DOWN: _control87(RC_DOWN, MCW_RC); break ; case GSL_IEEE_ROUND_UP: _control87(RC_UP, MCW_RC); break ; case GSL_IEEE_ROUND_TO_ZERO: _control87(RC_CHOP, MCW_RC); break ; default: _control87(RC_NEAR, MCW_RC); } /* Turn on all the exceptions apart from 'inexact' */ mode = EM_INVALID | EM_DENORMAL | EM_ZERODIVIDE | EM_OVERFLOW | EM_UNDERFLOW; if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ EM_INVALID; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) mode &= ~ EM_DENORMAL; if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ EM_ZERODIVIDE; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ EM_OVERFLOW; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ EM_UNDERFLOW; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode |= EM_INEXACT; } else { mode &= ~ EM_INEXACT; } _control87(mode, MCW_EM); return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_cblas__sspr2.c0000664000176700017670000000054511723710247017731 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_sspr2 (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *X, const int incX, const float *Y, const int incY, float *Ap) { #define BASE double #include "gsl_cblas__source_spr2.h" #undef BASE } sources_5316/external/gsl/gsl_randist__lognormal.c0000664000176700017670000000360411723710247021231 0ustar paulpaul/* randist/lognormal.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The lognormal distribution has the form p(x) dx = 1/(x * sqrt(2 pi sigma^2)) exp(-(ln(x) - zeta)^2/2 sigma^2) dx for x > 0. Lognormal random numbers are the exponentials of gaussian random numbers */ double gsl_ran_lognormal (const gsl_rng * r, const double zeta, const double sigma) { double u, v, r2, normal, z; do { /* choose x,y in uniform square (-1,-1) to (+1,+1) */ u = -1 + 2 * gsl_rng_uniform (r); v = -1 + 2 * gsl_rng_uniform (r); /* see if it is in the unit circle */ r2 = u * u + v * v; } while (r2 > 1.0 || r2 == 0); normal = u * sqrt (-2.0 * log (r2) / r2); z = exp (sigma * normal + zeta); return z; } double gsl_ran_lognormal_pdf (const double x, const double zeta, const double sigma) { if (x <= 0) { return 0 ; } else { double u = (log (x) - zeta)/sigma; double p = 1 / (x * fabs(sigma) * sqrt (2 * M_PI)) * exp (-(u * u) /2); return p; } } sources_5316/external/gsl/gsl_ode-initval__rk4.c0000664000176700017670000001661311723710247020512 0ustar paulpaul/* ode-initval/rk4.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Runge-Kutta 4th order, Classical */ /* Author: G. Jungman */ /* Reference: Abramowitz & Stegun, section 25.5. equation 25.5.10 Error estimation by step doubling, see eg. Ascher, U.M., Petzold, L.R., Computer methods for ordinary differential and differential-algebraic equations, SIAM, Philadelphia, 1998. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" typedef struct { double *k; double *k1; double *y0; double *ytmp; double *y_onestep; } rk4_state_t; static void * rk4_alloc (size_t dim) { rk4_state_t *state = (rk4_state_t *) malloc (sizeof (rk4_state_t)); if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for rk4_state", GSL_ENOMEM); } state->k = (double *) malloc (dim * sizeof (double)); if (state->k == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for k", GSL_ENOMEM); } state->k1 = (double *) malloc (dim * sizeof (double)); if (state->k1 == 0) { free (state); free (state->k); GSL_ERROR_NULL ("failed to allocate space for k1", GSL_ENOMEM); } state->y0 = (double *) malloc (dim * sizeof (double)); if (state->y0 == 0) { free (state->k); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } state->ytmp = (double *) malloc (dim * sizeof (double)); if (state->ytmp == 0) { free (state->y0); free (state->k); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for ytmp", GSL_ENOMEM); } state->y_onestep = (double *) malloc (dim * sizeof (double)); if (state->y_onestep == 0) { free (state->ytmp); free (state->y0); free (state->k); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for ytmp", GSL_ENOMEM); } return state; } static int rk4_step (double *y, const rk4_state_t *state, const double h, const double t, const size_t dim, const gsl_odeiv_system *sys) { /* Makes a Runge-Kutta 4th order advance with step size h. */ /* initial values of variables y. */ const double *y0 = state->y0; /* work space */ double *ytmp = state->ytmp; /* Runge-Kutta coefficients. Contains values of coefficient k1 in the beginning */ double *k = state->k; size_t i; /* k1 step */ for (i = 0; i < dim; i++) { y[i] += h / 6.0 * k[i]; ytmp[i] = y0[i] + 0.5 * h * k[i]; } /* k2 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + 0.5 * h, ytmp, k); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) { y[i] += h / 3.0 * k[i]; ytmp[i] = y0[i] + 0.5 * h * k[i]; } /* k3 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + 0.5 * h, ytmp, k); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) { y[i] += h / 3.0 * k[i]; ytmp[i] = y0[i] + h * k[i]; } /* k4 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + h, ytmp, k); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) { y[i] += h / 6.0 * k[i]; } return GSL_SUCCESS; } static int rk4_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { rk4_state_t *state = (rk4_state_t *) vstate; size_t i; double *const k = state->k; double *const k1 = state->k1; double *const y0 = state->y0; double *const y_onestep = state->y_onestep; DBL_MEMCPY (y0, y, dim); if (dydt_in != NULL) { DBL_MEMCPY (k, dydt_in, dim); } else { int s = GSL_ODEIV_FN_EVAL (sys, t, y0, k); if (s != GSL_SUCCESS) { return s; } } /* Error estimation is done by step doubling procedure */ /* Save first point derivatives*/ DBL_MEMCPY (k1, k, dim); /* First traverse h with one step (save to y_onestep) */ DBL_MEMCPY (y_onestep, y, dim); { int s = rk4_step (y_onestep, state, h, t, dim, sys); if (s != GSL_SUCCESS) { return s; } } /* Then with two steps with half step length (save to y) */ DBL_MEMCPY (k, k1, dim); { int s = rk4_step (y, state, h/2.0, t, dim, sys); if (s != GSL_SUCCESS) { /* Restore original values */ DBL_MEMCPY (y, y0, dim); return s; } } /* Update before second step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + h/2.0, y, k); if (s != GSL_SUCCESS) { /* Restore original values */ DBL_MEMCPY (y, y0, dim); return s; } } /* Save original y0 to k1 for possible failures */ DBL_MEMCPY (k1, y0, dim); /* Update y0 for second step */ DBL_MEMCPY (y0, y, dim); { int s = rk4_step (y, state, h/2.0, t + h/2.0, dim, sys); if (s != GSL_SUCCESS) { /* Restore original values */ DBL_MEMCPY (y, k1, dim); return s; } } /* Derivatives at output */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore original values */ DBL_MEMCPY (y, k1, dim); return s; } } /* Error estimation yerr = C * 0.5 * | y(onestep) - y(twosteps) | / (2^order - 1) constant C is approximately 8.0 to ensure 90% of samples lie within the error (assuming a gaussian distribution with prior p(sigma)=1/sigma.) */ for (i = 0; i < dim; i++) { yerr[i] = 4.0 * (y[i] - y_onestep[i]) / 15.0; } return GSL_SUCCESS; } static int rk4_reset (void *vstate, size_t dim) { rk4_state_t *state = (rk4_state_t *) vstate; DBL_ZERO_MEMSET (state->k, dim); DBL_ZERO_MEMSET (state->k1, dim); DBL_ZERO_MEMSET (state->y0, dim); DBL_ZERO_MEMSET (state->ytmp, dim); DBL_ZERO_MEMSET (state->y_onestep, dim); return GSL_SUCCESS; } static unsigned int rk4_order (void *vstate) { rk4_state_t *state = (rk4_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 4; } static void rk4_free (void *vstate) { rk4_state_t *state = (rk4_state_t *) vstate; free (state->k); free (state->k1); free (state->y0); free (state->ytmp); free (state->y_onestep); free (state); } static const gsl_odeiv_step_type rk4_type = { "rk4", /* name */ 1, /* can use dydt_in */ 1, /* gives exact dydt_out */ &rk4_alloc, &rk4_apply, &rk4_reset, &rk4_order, &rk4_free }; const gsl_odeiv_step_type *gsl_odeiv_step_rk4 = &rk4_type; sources_5316/external/gsl/gsl_vector__swap_source.c0000664000176700017670000000507311723710247021431 0ustar paulpaul/* vector/swap_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_vector, swap) (TYPE (gsl_vector) * v, TYPE (gsl_vector) * w) { ATOMIC * d1 = v->data ; ATOMIC * d2 = w->data ; const size_t size = v->size ; const size_t s1 = MULTIPLICITY * v->stride ; const size_t s2 = MULTIPLICITY * w->stride ; size_t i, k ; if (v->size != w->size) { GSL_ERROR("vector lengths must be equal", GSL_EINVAL); } for (i = 0; i < size; i++) { for (k = 0; k < MULTIPLICITY; k++) { ATOMIC tmp = d1[i*s1 + k]; d1[i*s1+k] = d2[i*s2 + k]; d2[i*s2+k] = tmp; } } return GSL_SUCCESS; } int FUNCTION (gsl_vector, swap_elements) (TYPE (gsl_vector) * v, const size_t i, const size_t j) { ATOMIC * data = v->data ; const size_t size = v->size ; const size_t stride = v->stride ; if (i >= size) { GSL_ERROR("first index is out of range", GSL_EINVAL); } if (j >= size) { GSL_ERROR("second index is out of range", GSL_EINVAL); } if (i != j) { const size_t s = MULTIPLICITY * stride ; size_t k ; for (k = 0; k < MULTIPLICITY; k++) { ATOMIC tmp = data[j*s + k]; data[j*s+k] = data[i*s + k]; data[i*s+k] = tmp; } } return GSL_SUCCESS; } int FUNCTION (gsl_vector, reverse) (TYPE (gsl_vector) * v) { ATOMIC * data = v->data ; const size_t size = v->size ; const size_t stride = v->stride ; const size_t s = MULTIPLICITY * stride ; size_t i ; for (i = 0 ; i < (size / 2) ; i++) { size_t j = size - i - 1 ; size_t k; for (k = 0; k < MULTIPLICITY; k++) { ATOMIC tmp = data[j*s + k]; data[j*s+k] = data[i*s + k]; data[i*s+k] = tmp; } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_sf__airy.c0000644000176700017670000005602710707442037017154 0ustar paulpaul/* specfunc/airy.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_airy.h" #include "gsl_sf__error.h" #include "gsl_sf__check.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval_mode.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* chebyshev expansions for Airy modulus and phase based on SLATEC r9aimp() Series for AM21 on the interval -1.25000D-01 to 0. with weighted error 2.89E-17 log weighted error 16.54 significant figures required 14.15 decimal places required 17.34 Series for ATH1 on the interval -1.25000D-01 to 0. with weighted error 2.53E-17 log weighted error 16.60 significant figures required 15.15 decimal places required 17.38 Series for AM22 on the interval -1.00000D+00 to -1.25000D-01 with weighted error 2.99E-17 log weighted error 16.52 significant figures required 14.57 decimal places required 17.28 Series for ATH2 on the interval -1.00000D+00 to -1.25000D-01 with weighted error 2.57E-17 log weighted error 16.59 significant figures required 15.07 decimal places required 17.34 */ static double am21_data[37] = { 0.0065809191761485, 0.0023675984685722, 0.0001324741670371, 0.0000157600904043, 0.0000027529702663, 0.0000006102679017, 0.0000001595088468, 0.0000000471033947, 0.0000000152933871, 0.0000000053590722, 0.0000000020000910, 0.0000000007872292, 0.0000000003243103, 0.0000000001390106, 0.0000000000617011, 0.0000000000282491, 0.0000000000132979, 0.0000000000064188, 0.0000000000031697, 0.0000000000015981, 0.0000000000008213, 0.0000000000004296, 0.0000000000002284, 0.0000000000001232, 0.0000000000000675, 0.0000000000000374, 0.0000000000000210, 0.0000000000000119, 0.0000000000000068, 0.0000000000000039, 0.0000000000000023, 0.0000000000000013, 0.0000000000000008, 0.0000000000000005, 0.0000000000000003, 0.0000000000000001, 0.0000000000000001 }; static cheb_series am21_cs = { am21_data, 36, -1, 1, 20 }; static double ath1_data[36] = { -0.07125837815669365, -0.00590471979831451, -0.00012114544069499, -0.00000988608542270, -0.00000138084097352, -0.00000026142640172, -0.00000006050432589, -0.00000001618436223, -0.00000000483464911, -0.00000000157655272, -0.00000000055231518, -0.00000000020545441, -0.00000000008043412, -0.00000000003291252, -0.00000000001399875, -0.00000000000616151, -0.00000000000279614, -0.00000000000130428, -0.00000000000062373, -0.00000000000030512, -0.00000000000015239, -0.00000000000007758, -0.00000000000004020, -0.00000000000002117, -0.00000000000001132, -0.00000000000000614, -0.00000000000000337, -0.00000000000000188, -0.00000000000000105, -0.00000000000000060, -0.00000000000000034, -0.00000000000000020, -0.00000000000000011, -0.00000000000000007, -0.00000000000000004, -0.00000000000000002 }; static cheb_series ath1_cs = { ath1_data, 35, -1, 1, 15 }; static double am22_data[33] = { -0.01562844480625341, 0.00778336445239681, 0.00086705777047718, 0.00015696627315611, 0.00003563962571432, 0.00000924598335425, 0.00000262110161850, 0.00000079188221651, 0.00000025104152792, 0.00000008265223206, 0.00000002805711662, 0.00000000976821090, 0.00000000347407923, 0.00000000125828132, 0.00000000046298826, 0.00000000017272825, 0.00000000006523192, 0.00000000002490471, 0.00000000000960156, 0.00000000000373448, 0.00000000000146417, 0.00000000000057826, 0.00000000000022991, 0.00000000000009197, 0.00000000000003700, 0.00000000000001496, 0.00000000000000608, 0.00000000000000248, 0.00000000000000101, 0.00000000000000041, 0.00000000000000017, 0.00000000000000007, 0.00000000000000002 }; static cheb_series am22_cs = { am22_data, 32, -1, 1, 15 }; static double ath2_data[32] = { 0.00440527345871877, -0.03042919452318455, -0.00138565328377179, -0.00018044439089549, -0.00003380847108327, -0.00000767818353522, -0.00000196783944371, -0.00000054837271158, -0.00000016254615505, -0.00000005053049981, -0.00000001631580701, -0.00000000543420411, -0.00000000185739855, -0.00000000064895120, -0.00000000023105948, -0.00000000008363282, -0.00000000003071196, -0.00000000001142367, -0.00000000000429811, -0.00000000000163389, -0.00000000000062693, -0.00000000000024260, -0.00000000000009461, -0.00000000000003716, -0.00000000000001469, -0.00000000000000584, -0.00000000000000233, -0.00000000000000093, -0.00000000000000037, -0.00000000000000015, -0.00000000000000006, -0.00000000000000002 }; static cheb_series ath2_cs = { ath2_data, 31, -1, 1, 16 }; /* Airy modulus and phase for x < -1 */ static int airy_mod_phase(const double x, gsl_mode_t mode, gsl_sf_result * mod, gsl_sf_result * phase) { gsl_sf_result result_m; gsl_sf_result result_p; double m, p; double sqx; if(x < -2.0) { double z = 16.0/(x*x*x) + 1.0; cheb_eval_mode_e(&am21_cs, z, mode, &result_m); cheb_eval_mode_e(&ath1_cs, z, mode, &result_p); } else if(x <= -1.0) { double z = (16.0/(x*x*x) + 9.0)/7.0; cheb_eval_mode_e(&am22_cs, z, mode, &result_m); cheb_eval_mode_e(&ath2_cs, z, mode, &result_p); } else { mod->val = 0.0; mod->err = 0.0; phase->val = 0.0; phase->err = 0.0; GSL_ERROR ("x is greater than 1.0", GSL_EDOM); } m = 0.3125 + result_m.val; p = -0.625 + result_p.val; sqx = sqrt(-x); mod->val = sqrt(m/sqx); mod->err = fabs(mod->val) * (GSL_DBL_EPSILON + fabs(result_m.err/result_m.val)); phase->val = M_PI_4 - x*sqx * p; phase->err = fabs(phase->val) * (GSL_DBL_EPSILON + fabs(result_p.err/result_p.val)); return GSL_SUCCESS; } /* Chebyshev series for Ai(x) with x in [-1,1] based on SLATEC ai(x) series for aif on the interval -1.00000d+00 to 1.00000d+00 with weighted error 1.09e-19 log weighted error 18.96 significant figures required 17.76 decimal places required 19.44 series for aig on the interval -1.00000d+00 to 1.00000d+00 with weighted error 1.51e-17 log weighted error 16.82 significant figures required 15.19 decimal places required 17.27 */ static double ai_data_f[9] = { -0.03797135849666999750, 0.05919188853726363857, 0.00098629280577279975, 0.00000684884381907656, 0.00000002594202596219, 0.00000000006176612774, 0.00000000000010092454, 0.00000000000000012014, 0.00000000000000000010 }; static cheb_series aif_cs = { ai_data_f, 8, -1, 1, 8 }; static double ai_data_g[8] = { 0.01815236558116127, 0.02157256316601076, 0.00025678356987483, 0.00000142652141197, 0.00000000457211492, 0.00000000000952517, 0.00000000000001392, 0.00000000000000001 }; static cheb_series aig_cs = { ai_data_g, 7, -1, 1, 7 }; /* Chebvyshev series for Bi(x) with x in [-1,1] based on SLATEC bi(x) series for bif on the interval -1.00000d+00 to 1.00000d+00 with weighted error 1.88e-19 log weighted error 18.72 significant figures required 17.74 decimal places required 19.20 series for big on the interval -1.00000d+00 to 1.00000d+00 with weighted error 2.61e-17 log weighted error 16.58 significant figures required 15.17 decimal places required 17.03 */ static double data_bif[9] = { -0.01673021647198664948, 0.10252335834249445610, 0.00170830925073815165, 0.00001186254546774468, 0.00000004493290701779, 0.00000000010698207143, 0.00000000000017480643, 0.00000000000000020810, 0.00000000000000000018 }; static cheb_series bif_cs = { data_bif, 8, -1, 1, 8 }; static double data_big[8] = { 0.02246622324857452, 0.03736477545301955, 0.00044476218957212, 0.00000247080756363, 0.00000000791913533, 0.00000000001649807, 0.00000000000002411, 0.00000000000000002 }; static cheb_series big_cs = { data_big, 7, -1, 1, 7 }; /* Chebyshev series for Bi(x) with x in [1,8] based on SLATEC bi(x) */ static double data_bif2[10] = { 0.0998457269381604100, 0.4786249778630055380, 0.0251552119604330118, 0.0005820693885232645, 0.0000074997659644377, 0.0000000613460287034, 0.0000000003462753885, 0.0000000000014288910, 0.0000000000000044962, 0.0000000000000000111 }; static cheb_series bif2_cs = { data_bif2, 9, -1, 1, 9 }; static double data_big2[10] = { 0.033305662145514340, 0.161309215123197068, 0.0063190073096134286, 0.0001187904568162517, 0.0000013045345886200, 0.0000000093741259955, 0.0000000000474580188, 0.0000000000001783107, 0.0000000000000005167, 0.0000000000000000011 }; static cheb_series big2_cs = { data_big2, 9, -1, 1, 9 }; /* chebyshev for Ai(x) asymptotic factor based on SLATEC aie() Series for AIP on the interval 0. to 1.00000D+00 with weighted error 5.10E-17 log weighted error 16.29 significant figures required 14.41 decimal places required 17.06 [GJ] Sun Apr 19 18:14:31 EDT 1998 There was something wrong with these coefficients. I was getting errors after 3 or 4 digits. So I recomputed this table. Now I get double precision agreement with Mathematica. But it does not seem possible that the small differences here would account for the original discrepancy. There must have been something wrong with my original usage... */ static double data_aip[36] = { -0.0187519297793867540198, -0.0091443848250055004725, 0.0009010457337825074652, -0.0001394184127221491507, 0.0000273815815785209370, -0.0000062750421119959424, 0.0000016064844184831521, -0.0000004476392158510354, 0.0000001334635874651668, -0.0000000420735334263215, 0.0000000139021990246364, -0.0000000047831848068048, 0.0000000017047897907465, -0.0000000006268389576018, 0.0000000002369824276612, -0.0000000000918641139267, 0.0000000000364278543037, -0.0000000000147475551725, 0.0000000000060851006556, -0.0000000000025552772234, 0.0000000000010906187250, -0.0000000000004725870319, 0.0000000000002076969064, -0.0000000000000924976214, 0.0000000000000417096723, -0.0000000000000190299093, 0.0000000000000087790676, -0.0000000000000040927557, 0.0000000000000019271068, -0.0000000000000009160199, 0.0000000000000004393567, -0.0000000000000002125503, 0.0000000000000001036735, -0.0000000000000000509642, 0.0000000000000000252377, -0.0000000000000000125793 /* -.0187519297793868 -.0091443848250055, .0009010457337825, -.0001394184127221, .0000273815815785, -.0000062750421119, .0000016064844184, -.0000004476392158, .0000001334635874, -.0000000420735334, .0000000139021990, -.0000000047831848, .0000000017047897, -.0000000006268389, .0000000002369824, -.0000000000918641, .0000000000364278, -.0000000000147475, .0000000000060851, -.0000000000025552, .0000000000010906, -.0000000000004725, .0000000000002076, -.0000000000000924, .0000000000000417, -.0000000000000190, .0000000000000087, -.0000000000000040, .0000000000000019, -.0000000000000009, .0000000000000004, -.0000000000000002, .0000000000000001, -.0000000000000000 */ }; static cheb_series aip_cs = { data_aip, 35, -1, 1, 17 }; /* chebyshev for Bi(x) asymptotic factor based on SLATEC bie() Series for BIP on the interval 1.25000D-01 to 3.53553D-01 with weighted error 1.91E-17 log weighted error 16.72 significant figures required 15.35 decimal places required 17.41 Series for BIP2 on the interval 0. to 1.25000D-01 with weighted error 1.05E-18 log weighted error 17.98 significant figures required 16.74 decimal places required 18.71 */ static double data_bip[24] = { -0.08322047477943447, 0.01146118927371174, 0.00042896440718911, -0.00014906639379950, -0.00001307659726787, 0.00000632759839610, -0.00000042226696982, -0.00000019147186298, 0.00000006453106284, -0.00000000784485467, -0.00000000096077216, 0.00000000070004713, -0.00000000017731789, 0.00000000002272089, 0.00000000000165404, -0.00000000000185171, 0.00000000000059576, -0.00000000000012194, 0.00000000000001334, 0.00000000000000172, -0.00000000000000145, 0.00000000000000049, -0.00000000000000011, 0.00000000000000001 }; static cheb_series bip_cs = { data_bip, 23, -1, 1, 14 }; static double data_bip2[29] = { -0.113596737585988679, 0.0041381473947881595, 0.0001353470622119332, 0.0000104273166530153, 0.0000013474954767849, 0.0000001696537405438, -0.0000000100965008656, -0.0000000167291194937, -0.0000000045815364485, 0.0000000003736681366, 0.0000000005766930320, 0.0000000000621812650, -0.0000000000632941202, -0.0000000000149150479, 0.0000000000078896213, 0.0000000000024960513, -0.0000000000012130075, -0.0000000000003740493, 0.0000000000002237727, 0.0000000000000474902, -0.0000000000000452616, -0.0000000000000030172, 0.0000000000000091058, -0.0000000000000009814, -0.0000000000000016429, 0.0000000000000005533, 0.0000000000000002175, -0.0000000000000001737, -0.0000000000000000010 }; static cheb_series bip2_cs = { data_bip2, 28, -1, 1, 10 }; /* assumes x >= 1.0 */ inline static int airy_aie(const double x, gsl_mode_t mode, gsl_sf_result * result) { double sqx = sqrt(x); double z = 2.0/(x*sqx) - 1.0; double y = sqrt(sqx); gsl_sf_result result_c; cheb_eval_mode_e(&aip_cs, z, mode, &result_c); result->val = (0.28125 + result_c.val)/y; result->err = result_c.err/y + GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* assumes x >= 2.0 */ static int airy_bie(const double x, gsl_mode_t mode, gsl_sf_result * result) { const double ATR = 8.7506905708484345; const double BTR = -2.0938363213560543; if(x < 4.0) { double sqx = sqrt(x); double z = ATR/(x*sqx) + BTR; double y = sqrt(sqx); gsl_sf_result result_c; cheb_eval_mode_e(&bip_cs, z, mode, &result_c); result->val = (0.625 + result_c.val)/y; result->err = result_c.err/y + GSL_DBL_EPSILON * fabs(result->val); } else { double sqx = sqrt(x); double z = 16.0/(x*sqx) - 1.0; double y = sqrt(sqx); gsl_sf_result result_c; cheb_eval_mode_e(&bip2_cs, z, mode, &result_c); result->val = (0.625 + result_c.val)/y; result->err = result_c.err/y + GSL_DBL_EPSILON * fabs(result->val); } return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_airy_Ai_e(const double x, const gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result mod; gsl_sf_result theta; gsl_sf_result cos_result; int stat_mp = airy_mod_phase(x, mode, &mod, &theta); int stat_cos = gsl_sf_cos_err_e(theta.val, theta.err, &cos_result); result->val = mod.val * cos_result.val; result->err = fabs(mod.val * cos_result.err) + fabs(cos_result.val * mod.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mp, stat_cos); } else if(x <= 1.0) { const double z = x*x*x; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&aif_cs, z, mode, &result_c0); cheb_eval_mode_e(&aig_cs, z, mode, &result_c1); result->val = 0.375 + (result_c0.val - x*(0.25 + result_c1.val)); result->err = result_c0.err + fabs(x*result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { double x32 = x * sqrt(x); double s = exp(-2.0*x32/3.0); gsl_sf_result result_aie; int stat_aie = airy_aie(x, mode, &result_aie); result->val = result_aie.val * s; result->err = result_aie.err * s + result->val * x32 * GSL_DBL_EPSILON; result->err += GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return stat_aie; } } int gsl_sf_airy_Ai_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result mod; gsl_sf_result theta; gsl_sf_result cos_result; int stat_mp = airy_mod_phase(x, mode, &mod, &theta); int stat_cos = gsl_sf_cos_err_e(theta.val, theta.err, &cos_result); result->val = mod.val * cos_result.val; result->err = fabs(mod.val * cos_result.err) + fabs(cos_result.val * mod.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mp, stat_cos); } else if(x <= 1.0) { const double z = x*x*x; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&aif_cs, z, mode, &result_c0); cheb_eval_mode_e(&aig_cs, z, mode, &result_c1); result->val = 0.375 + (result_c0.val - x*(0.25 + result_c1.val)); result->err = result_c0.err + fabs(x*result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); if(x > 0.0) { const double scale = exp(2.0/3.0 * sqrt(z)); result->val *= scale; result->err *= scale; } return GSL_SUCCESS; } else { return airy_aie(x, mode, result); } } int gsl_sf_airy_Bi_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result mod; gsl_sf_result theta; gsl_sf_result sin_result; int stat_mp = airy_mod_phase(x, mode, &mod, &theta); int stat_sin = gsl_sf_sin_err_e(theta.val, theta.err, &sin_result); result->val = mod.val * sin_result.val; result->err = fabs(mod.val * sin_result.err) + fabs(sin_result.val * mod.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mp, stat_sin); } else if(x < 1.0) { const double z = x*x*x; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&bif_cs, z, mode, &result_c0); cheb_eval_mode_e(&big_cs, z, mode, &result_c1); result->val = 0.625 + result_c0.val + x*(0.4375 + result_c1.val); result->err = result_c0.err + fabs(x * result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x <= 2.0) { const double z = (2.0*x*x*x - 9.0)/7.0; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&bif2_cs, z, mode, &result_c0); cheb_eval_mode_e(&big2_cs, z, mode, &result_c1); result->val = 1.125 + result_c0.val + x*(0.625 + result_c1.val); result->err = result_c0.err + fabs(x * result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double y = 2.0*x*sqrt(x)/3.0; const double s = exp(y); if(y > GSL_LOG_DBL_MAX - 1.0) { OVERFLOW_ERROR(result); } else { gsl_sf_result result_bie; int stat_bie = airy_bie(x, mode, &result_bie); result->val = result_bie.val * s; result->err = result_bie.err * s + fabs(1.5*y * (GSL_DBL_EPSILON * result->val)); result->err += GSL_DBL_EPSILON * fabs(result->val); return stat_bie; } } } int gsl_sf_airy_Bi_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < -1.0) { gsl_sf_result mod; gsl_sf_result theta; gsl_sf_result sin_result; int stat_mp = airy_mod_phase(x, mode, &mod, &theta); int stat_sin = gsl_sf_sin_err_e(theta.val, theta.err, &sin_result); result->val = mod.val * sin_result.val; result->err = fabs(mod.val * sin_result.err) + fabs(sin_result.val * mod.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_mp, stat_sin); } else if(x < 1.0) { const double z = x*x*x; gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&bif_cs, z, mode, &result_c0); cheb_eval_mode_e(&big_cs, z, mode, &result_c1); result->val = 0.625 + result_c0.val + x*(0.4375 + result_c1.val); result->err = result_c0.err + fabs(x * result_c1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); if(x > 0.0) { const double scale = exp(-2.0/3.0 * sqrt(z)); result->val *= scale; result->err *= scale; } return GSL_SUCCESS; } else if(x <= 2.0) { const double x3 = x*x*x; const double z = (2.0*x3 - 9.0)/7.0; const double s = exp(-2.0/3.0 * sqrt(x3)); gsl_sf_result result_c0; gsl_sf_result result_c1; cheb_eval_mode_e(&bif2_cs, z, mode, &result_c0); cheb_eval_mode_e(&big2_cs, z, mode, &result_c1); result->val = s * (1.125 + result_c0.val + x*(0.625 + result_c1.val)); result->err = s * (result_c0.err + fabs(x * result_c1.err)); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { return airy_bie(x, mode, result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_airy_Ai(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Ai_e(x, mode, &result)); } double gsl_sf_airy_Ai_scaled(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Ai_scaled_e(x, mode, &result)); } double gsl_sf_airy_Bi(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Bi_e(x, mode, &result)); } double gsl_sf_airy_Bi_scaled(const double x, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_airy_Bi_scaled_e(x, mode, &result)); } sources_5316/external/gsl/gsl_cblas__csyr2k.c0000664000176700017670000000070211723710247020070 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_csyr2k (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc) { #define BASE float #include "gsl_cblas__source_syr2k_c.h" #undef BASE } sources_5316/external/gsl/gsl_permute_uint.h0000664000176700017670000000263611705263724020110 0ustar paulpaul/* permutation/gsl_permute_uint.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_UINT_H__ #define __GSL_PERMUTE_UINT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_uint (const size_t * p, unsigned int * data, const size_t stride, const size_t n); int gsl_permute_uint_inverse (const size_t * p, unsigned int * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_UINT_H__ */ sources_5316/external/gsl/gsl_ieee-utils__fp-gnusparc.c0000664000176700017670000000465211723710247022071 0ustar paulpaul/* ieee-utils/fp-gnusparc.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl_errno.h" #include "gsl_ieee_utils.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { unsigned short mode = 0 ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: mode |= _FPU_SINGLE ; break ; case GSL_IEEE_DOUBLE_PRECISION: mode |= _FPU_DOUBLE ; break ; case GSL_IEEE_EXTENDED_PRECISION: mode |= _FPU_EXTENDED ; break ; default: mode |= _FPU_EXTENDED ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: mode |= _FPU_RC_NEAREST ; break ; case GSL_IEEE_ROUND_DOWN: mode |= _FPU_RC_DOWN ; break ; case GSL_IEEE_ROUND_UP: mode |= _FPU_RC_UP ; break ; case GSL_IEEE_ROUND_TO_ZERO: mode |= _FPU_RC_ZERO ; break ; default: mode |= _FPU_RC_NEAREST ; } if (exception_mask & GSL_IEEE_MASK_INVALID) mode |= _FPU_MASK_IM ; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("sparc does not support the denormalized operand exception. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode |= _FPU_MASK_ZM ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode |= _FPU_MASK_OM ; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode |= _FPU_MASK_UM ; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode &= ~ _FPU_MASK_PM ; } else { mode |= _FPU_MASK_PM ; } _FPU_SETCW(mode) ; return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_specfunc__elljac.c0000664000176700017670000000654511723710247020642 0ustar paulpaul/* specfunc/elljac.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_elljac.h" /* GJ: See [Thompson, Atlas for Computing Mathematical Functions] */ /* BJG 2005-07: New algorithm based on Algorithm 5 from Numerische Mathematik 7, 78-90 (1965) "Numerical Calculation of Elliptic Integrals and Elliptic Functions" R. Bulirsch. Minor tweak is to avoid division by zero when sin(x u_l) = 0 by computing reflected values sn(K-u) cn(K-u) dn(K-u) and using transformation from Abramowitz & Stegun table 16.8 column "K-u"*/ int gsl_sf_elljac_e(double u, double m, double * sn, double * cn, double * dn) { if(fabs(m) > 1.0) { *sn = 0.0; *cn = 0.0; *dn = 0.0; GSL_ERROR ("|m| > 1.0", GSL_EDOM); } else if(fabs(m) < 2.0*GSL_DBL_EPSILON) { *sn = sin(u); *cn = cos(u); *dn = 1.0; return GSL_SUCCESS; } else if(fabs(m - 1.0) < 2.0*GSL_DBL_EPSILON) { *sn = tanh(u); *cn = 1.0/cosh(u); *dn = *cn; return GSL_SUCCESS; } else { int status = GSL_SUCCESS; const int N = 16; double mu[16]; double nu[16]; double c[16]; double d[16]; double sin_umu, cos_umu, t, r; int n = 0; mu[0] = 1.0; nu[0] = sqrt(1.0 - m); while( fabs(mu[n] - nu[n]) > 4.0 * GSL_DBL_EPSILON * fabs(mu[n]+nu[n])) { mu[n+1] = 0.5 * (mu[n] + nu[n]); nu[n+1] = sqrt(mu[n] * nu[n]); ++n; if(n >= N - 1) { status = GSL_EMAXITER; break; } } sin_umu = sin(u * mu[n]); cos_umu = cos(u * mu[n]); /* Since sin(u*mu(n)) can be zero we switch to computing sn(K-u), cn(K-u), dn(K-u) when |sin| < |cos| */ if (fabs(sin_umu) < fabs(cos_umu)) { t = sin_umu / cos_umu; c[n] = mu[n] * t; d[n] = 1.0; while(n > 0) { n--; c[n] = d[n+1] * c[n+1]; r = (c[n+1] * c[n+1]) / mu[n+1]; d[n] = (r + nu[n]) / (r + mu[n]); } *dn = sqrt(1.0-m) / d[n]; *cn = (*dn) * GSL_SIGN(cos_umu) / gsl_hypot(1.0, c[n]); *sn = (*cn) * c[n] /sqrt(1.0-m); } else { t = cos_umu / sin_umu; c[n] = mu[n] * t; d[n] = 1.0; while(n > 0) { --n; c[n] = d[n+1] * c[n+1]; r = (c[n+1] * c[n+1]) / mu[n+1]; d[n] = (r + nu[n]) / (r + mu[n]); } *dn = d[n]; *sn = GSL_SIGN(sin_umu) / gsl_hypot(1.0, c[n]); *cn = c[n] * (*sn); } return status; } } sources_5316/external/gsl/gsl_multifit__lmset.c0000664000176700017670000000247311723710247020557 0ustar paulpaulstatic int set (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx, int scale) { lmder_state_t *state = (lmder_state_t *) vstate; gsl_matrix *r = state->r; gsl_vector *tau = state->tau; gsl_vector *diag = state->diag; gsl_vector *work1 = state->work1; gsl_permutation *perm = state->perm; int signum; GSL_MULTIFIT_FN_EVAL_F_DF (fdf, x, f, J); state->par = 0; state->iter = 1; state->fnorm = enorm (f); gsl_vector_set_all (dx, 0.0); /* store column norms in diag */ if (scale) { compute_diag (J, diag); } else { gsl_vector_set_all (diag, 1.0); } /* set delta to 100 |D x| or to 100 if |D x| is zero */ state->xnorm = scaled_enorm (diag, x); state->delta = compute_delta (diag, x); /* Factorize J into QR decomposition */ gsl_matrix_memcpy (r, J); gsl_linalg_QRPT_decomp (r, tau, perm, &signum, work1); gsl_vector_set_zero (state->rptdx); gsl_vector_set_zero (state->w); /* Zero the trial vector, as in the alloc function */ gsl_vector_set_zero (state->f_trial); #ifdef DEBUG printf("r = "); gsl_matrix_fprintf(stdout, r, "%g"); printf("perm = "); gsl_permutation_fprintf(stdout, perm, "%d"); printf("tau = "); gsl_vector_fprintf(stdout, tau, "%g"); #endif return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__cdotc_sub.c0000664000176700017670000000047211723710247020624 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cdotc_sub (const int N, const void *X, const int incX, const void *Y, const int incY, void *result) { #define BASE float #define CONJ_SIGN (-1.0) #include "gsl_cblas__source_dot_c.h" #undef CONJ_SIGN #undef BASE } sources_5316/external/gsl/gsl_linalg__qrpt.c0000664000176700017670000003106611723710247020032 0ustar paulpaul/* linalg/qrpt.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_permute_vector.h" #include "gsl_blas.h" #include "gsl_linalg.h" #define REAL double #include "gsl_linalg__givens.c" #include "gsl_linalg__apply_givens.c" /* Factorise a general M x N matrix A into * * A P = Q R * * where Q is orthogonal (M x M) and R is upper triangular (M x N). * When A is rank deficient, r = rank(A) < n, then the permutation is * used to ensure that the lower n - r rows of R are zero and the first * r columns of Q form an orthonormal basis for A. * * Q is stored as a packed set of Householder transformations in the * strict lower triangular part of the input matrix. * * R is stored in the diagonal and upper triangle of the input matrix. * * P: column j of P is column k of the identity matrix, where k = * permutation->data[j] * * The full matrix for Q can be obtained as the product * * Q = Q_k .. Q_2 Q_1 * * where k = MIN(M,N) and * * Q_i = (I - tau_i * v_i * v_i') * * and where v_i is a Householder vector * * v_i = [1, m(i+1,i), m(i+2,i), ... , m(M,i)] * * This storage scheme is the same as in LAPACK. See LAPACK's * dgeqpf.f for details. * */ int gsl_linalg_QRPT_decomp (gsl_matrix * A, gsl_vector * tau, gsl_permutation * p, int *signum, gsl_vector * norm) { const size_t M = A->size1; const size_t N = A->size2; if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (p->size != N) { GSL_ERROR ("permutation size must be N", GSL_EBADLEN); } else if (norm->size != N) { GSL_ERROR ("norm size must be N", GSL_EBADLEN); } else { size_t i; *signum = 1; gsl_permutation_init (p); /* set to identity */ /* Compute column norms and store in workspace */ for (i = 0; i < N; i++) { gsl_vector_view c = gsl_matrix_column (A, i); double x = gsl_blas_dnrm2 (&c.vector); gsl_vector_set (norm, i, x); } for (i = 0; i < GSL_MIN (M, N); i++) { /* Bring the column of largest norm into the pivot position */ double max_norm = gsl_vector_get(norm, i); size_t j, kmax = i; for (j = i + 1; j < N; j++) { double x = gsl_vector_get (norm, j); if (x > max_norm) { max_norm = x; kmax = j; } } if (kmax != i) { gsl_matrix_swap_columns (A, i, kmax); gsl_permutation_swap (p, i, kmax); gsl_vector_swap_elements(norm,i,kmax); (*signum) = -(*signum); } /* Compute the Householder transformation to reduce the j-th column of the matrix to a multiple of the j-th unit vector */ { gsl_vector_view c_full = gsl_matrix_column (A, i); gsl_vector_view c = gsl_vector_subvector (&c_full.vector, i, M - i); double tau_i = gsl_linalg_householder_transform (&c.vector); gsl_vector_set (tau, i, tau_i); /* Apply the transformation to the remaining columns */ if (i + 1 < N) { gsl_matrix_view m = gsl_matrix_submatrix (A, i, i + 1, M - i, N - (i+1)); gsl_linalg_householder_hm (tau_i, &c.vector, &m.matrix); } } /* Update the norms of the remaining columns too */ if (i + 1 < M) { for (j = i + 1; j < N; j++) { double x = gsl_vector_get (norm, j); if (x > 0.0) { double y = 0; double temp= gsl_matrix_get (A, i, j) / x; if (fabs (temp) >= 1) y = 0.0; else y = x * sqrt (1 - temp * temp); /* recompute norm to prevent loss of accuracy */ if (fabs (y / x) < sqrt (20.0) * GSL_SQRT_DBL_EPSILON) { gsl_vector_view c_full = gsl_matrix_column (A, j); gsl_vector_view c = gsl_vector_subvector(&c_full.vector, i+1, M - (i+1)); y = gsl_blas_dnrm2 (&c.vector); } gsl_vector_set (norm, j, y); } } } } return GSL_SUCCESS; } } int gsl_linalg_QRPT_decomp2 (const gsl_matrix * A, gsl_matrix * q, gsl_matrix * r, gsl_vector * tau, gsl_permutation * p, int *signum, gsl_vector * norm) { const size_t M = A->size1; const size_t N = A->size2; if (q->size1 != M || q->size2 !=M) { GSL_ERROR ("q must be M x M", GSL_EBADLEN); } else if (r->size1 != M || r->size2 !=N) { GSL_ERROR ("r must be M x N", GSL_EBADLEN); } else if (tau->size != GSL_MIN (M, N)) { GSL_ERROR ("size of tau must be MIN(M,N)", GSL_EBADLEN); } else if (p->size != N) { GSL_ERROR ("permutation size must be N", GSL_EBADLEN); } else if (norm->size != N) { GSL_ERROR ("norm size must be N", GSL_EBADLEN); } gsl_matrix_memcpy (r, A); gsl_linalg_QRPT_decomp (r, tau, p, signum, norm); /* FIXME: aliased arguments depends on behavior of unpack routine! */ gsl_linalg_QR_unpack (r, tau, q, r); return GSL_SUCCESS; } /* Solves the system A x = b using the Q R P^T factorisation, R z = Q^T b x = P z; to obtain x. Based on SLATEC code. */ int gsl_linalg_QRPT_solve (const gsl_matrix * QR, const gsl_vector * tau, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x) { if (QR->size1 != QR->size2) { GSL_ERROR ("QR matrix must be square", GSL_ENOTSQR); } else if (QR->size1 != p->size) { GSL_ERROR ("matrix size must match permutation size", GSL_EBADLEN); } else if (QR->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (QR->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { gsl_vector_memcpy (x, b); gsl_linalg_QRPT_svx (QR, tau, p, x); return GSL_SUCCESS; } } int gsl_linalg_QRPT_svx (const gsl_matrix * QR, const gsl_vector * tau, const gsl_permutation * p, gsl_vector * x) { if (QR->size1 != QR->size2) { GSL_ERROR ("QR matrix must be square", GSL_ENOTSQR); } else if (QR->size1 != p->size) { GSL_ERROR ("matrix size must match permutation size", GSL_EBADLEN); } else if (QR->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* compute sol = Q^T b */ gsl_linalg_QR_QTvec (QR, tau, x); /* Solve R x = sol, storing x inplace in sol */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, QR, x); gsl_permute_vector_inverse (p, x); return GSL_SUCCESS; } } int gsl_linalg_QRPT_QRsolve (const gsl_matrix * Q, const gsl_matrix * R, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x) { if (Q->size1 != Q->size2 || R->size1 != R->size2) { return GSL_ENOTSQR; } else if (Q->size1 != p->size || Q->size1 != R->size1 || Q->size1 != b->size) { return GSL_EBADLEN; } else { /* compute b' = Q^T b */ gsl_blas_dgemv (CblasTrans, 1.0, Q, b, 0.0, x); /* Solve R x = b', storing x inplace */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, R, x); /* Apply permutation to solution in place */ gsl_permute_vector_inverse (p, x); return GSL_SUCCESS; } } int gsl_linalg_QRPT_Rsolve (const gsl_matrix * QR, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x) { if (QR->size1 != QR->size2) { GSL_ERROR ("QR matrix must be square", GSL_ENOTSQR); } else if (QR->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (QR->size2 != x->size) { GSL_ERROR ("matrix size must match x size", GSL_EBADLEN); } else if (p->size != x->size) { GSL_ERROR ("permutation size must match x size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve R x = b, storing x inplace */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, QR, x); gsl_permute_vector_inverse (p, x); return GSL_SUCCESS; } } int gsl_linalg_QRPT_Rsvx (const gsl_matrix * QR, const gsl_permutation * p, gsl_vector * x) { if (QR->size1 != QR->size2) { GSL_ERROR ("QR matrix must be square", GSL_ENOTSQR); } else if (QR->size2 != x->size) { GSL_ERROR ("matrix size must match x size", GSL_EBADLEN); } else if (p->size != x->size) { GSL_ERROR ("permutation size must match x size", GSL_EBADLEN); } else { /* Solve R x = b, storing x inplace */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, QR, x); gsl_permute_vector_inverse (p, x); return GSL_SUCCESS; } } /* Update a Q R P^T factorisation for A P= Q R , A' = A + u v^T, Q' R' P^-1 = QR P^-1 + u v^T = Q (R + Q^T u v^T P ) P^-1 = Q (R + w v^T P) P^-1 where w = Q^T u. Algorithm from Golub and Van Loan, "Matrix Computations", Section 12.5 (Updating Matrix Factorizations, Rank-One Changes) */ int gsl_linalg_QRPT_update (gsl_matrix * Q, gsl_matrix * R, const gsl_permutation * p, gsl_vector * w, const gsl_vector * v) { if (Q->size1 != Q->size2 || R->size1 != R->size2) { return GSL_ENOTSQR; } else if (R->size1 != Q->size2 || v->size != Q->size2 || w->size != Q->size2) { return GSL_EBADLEN; } else { size_t j, k; const size_t M = Q->size1; const size_t N = Q->size2; double w0; /* Apply Given's rotations to reduce w to (|w|, 0, 0, ... , 0) J_1^T .... J_(n-1)^T w = +/- |w| e_1 simultaneously applied to R, H = J_1^T ... J^T_(n-1) R so that H is upper Hessenberg. (12.5.2) */ for (k = N - 1; k > 0; k--) { double c, s; double wk = gsl_vector_get (w, k); double wkm1 = gsl_vector_get (w, k - 1); create_givens (wkm1, wk, &c, &s); apply_givens_vec (w, k - 1, k, c, s); apply_givens_qr (M, N, Q, R, k - 1, k, c, s); } w0 = gsl_vector_get (w, 0); /* Add in w v^T (Equation 12.5.3) */ for (j = 0; j < N; j++) { double r0j = gsl_matrix_get (R, 0, j); size_t p_j = gsl_permutation_get (p, j); double vj = gsl_vector_get (v, p_j); gsl_matrix_set (R, 0, j, r0j + w0 * vj); } /* Apply Givens transformations R' = G_(n-1)^T ... G_1^T H Equation 12.5.4 */ for (k = 1; k < N; k++) { double c, s; double diag = gsl_matrix_get (R, k - 1, k - 1); double offdiag = gsl_matrix_get (R, k, k - 1); create_givens (diag, offdiag, &c, &s); apply_givens_qr (M, N, Q, R, k - 1, k, c, s); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_randist__sphere.c0000664000176700017670000000663411723710247020533 0ustar paulpaul/* randist/sphere.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" void gsl_ran_dir_2d (const gsl_rng * r, double *x, double *y) { /* This method avoids trig, but it does take an average of 8/pi = * 2.55 calls to the RNG, instead of one for the direct * trigonometric method. */ double u, v, s; do { u = -1 + 2 * gsl_rng_uniform (r); v = -1 + 2 * gsl_rng_uniform (r); s = u * u + v * v; } while (s > 1.0 || s == 0.0); /* This is the Von Neumann trick. See Knuth, v2, 3rd ed, p140 * (exercise 23). Note, no sin, cos, or sqrt ! */ *x = (u * u - v * v) / s; *y = 2 * u * v / s; /* Here is the more straightforward approach, * s = sqrt (s); *x = u / s; *y = v / s; * It has fewer total operations, but one of them is a sqrt */ } void gsl_ran_dir_2d_trig_method (const gsl_rng * r, double *x, double *y) { /* This is the obvious solution... */ /* It ain't clever, but since sin/cos are often hardware accelerated, * it can be faster -- it is on my home Pentium -- than von Neumann's * solution, or slower -- as it is on my Sun Sparc 20 at work */ double t = 6.2831853071795864 * gsl_rng_uniform (r); /* 2*PI */ *x = cos (t); *y = sin (t); } void gsl_ran_dir_3d (const gsl_rng * r, double *x, double *y, double *z) { double s, a; /* This is a variant of the algorithm for computing a random point * on the unit sphere; the algorithm is suggested in Knuth, v2, * 3rd ed, p136; and attributed to Robert E Knop, CACM, 13 (1970), * 326. */ /* Begin with the polar method for getting x,y inside a unit circle */ do { *x = -1 + 2 * gsl_rng_uniform (r); *y = -1 + 2 * gsl_rng_uniform (r); s = (*x) * (*x) + (*y) * (*y); } while (s > 1.0); *z = -1 + 2 * s; /* z uniformly distributed from -1 to 1 */ a = 2 * sqrt (1 - s); /* factor to adjust x,y so that x^2+y^2 * is equal to 1-z^2 */ *x *= a; *y *= a; } void gsl_ran_dir_nd (const gsl_rng * r, size_t n, double *x) { double d; size_t i; /* See Knuth, v2, 3rd ed, p135-136. The method is attributed to * G. W. Brown, in Modern Mathematics for the Engineer (1956). * The idea is that gaussians G(x) have the property that * G(x)G(y)G(z)G(...) is radially symmetric, a function only * r = sqrt(x^2+y^2+...) */ d = 0; do { for (i = 0; i < n; ++i) { x[i] = gsl_ran_gaussian (r, 1.0); d += x[i] * x[i]; } } while (d == 0); d = sqrt (d); for (i = 0; i < n; ++i) { x[i] /= d; } } sources_5316/external/gsl/gsl_matrix_char.h0000664000176700017670000002643611705263724017675 0ustar paulpaul/* matrix/gsl_matrix_char.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_CHAR_H__ #define __GSL_MATRIX_CHAR_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_char.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; char * data; gsl_block_char * block; int owner; } gsl_matrix_char; typedef struct { gsl_matrix_char matrix; } _gsl_matrix_char_view; typedef _gsl_matrix_char_view gsl_matrix_char_view; typedef struct { gsl_matrix_char matrix; } _gsl_matrix_char_const_view; typedef const _gsl_matrix_char_const_view gsl_matrix_char_const_view; /* Allocation */ gsl_matrix_char * gsl_matrix_char_alloc (const size_t n1, const size_t n2); gsl_matrix_char * gsl_matrix_char_calloc (const size_t n1, const size_t n2); gsl_matrix_char * gsl_matrix_char_alloc_from_block (gsl_block_char * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_char * gsl_matrix_char_alloc_from_matrix (gsl_matrix_char * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_char * gsl_vector_char_alloc_row_from_matrix (gsl_matrix_char * m, const size_t i); gsl_vector_char * gsl_vector_char_alloc_col_from_matrix (gsl_matrix_char * m, const size_t j); void gsl_matrix_char_free (gsl_matrix_char * m); /* Views */ _gsl_matrix_char_view gsl_matrix_char_submatrix (gsl_matrix_char * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_char_view gsl_matrix_char_row (gsl_matrix_char * m, const size_t i); _gsl_vector_char_view gsl_matrix_char_column (gsl_matrix_char * m, const size_t j); _gsl_vector_char_view gsl_matrix_char_diagonal (gsl_matrix_char * m); _gsl_vector_char_view gsl_matrix_char_subdiagonal (gsl_matrix_char * m, const size_t k); _gsl_vector_char_view gsl_matrix_char_superdiagonal (gsl_matrix_char * m, const size_t k); _gsl_vector_char_view gsl_matrix_char_subrow (gsl_matrix_char * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_char_view gsl_matrix_char_subcolumn (gsl_matrix_char * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_char_view gsl_matrix_char_view_array (char * base, const size_t n1, const size_t n2); _gsl_matrix_char_view gsl_matrix_char_view_array_with_tda (char * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_char_view gsl_matrix_char_view_vector (gsl_vector_char * v, const size_t n1, const size_t n2); _gsl_matrix_char_view gsl_matrix_char_view_vector_with_tda (gsl_vector_char * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_char_const_view gsl_matrix_char_const_submatrix (const gsl_matrix_char * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_char_const_view gsl_matrix_char_const_row (const gsl_matrix_char * m, const size_t i); _gsl_vector_char_const_view gsl_matrix_char_const_column (const gsl_matrix_char * m, const size_t j); _gsl_vector_char_const_view gsl_matrix_char_const_diagonal (const gsl_matrix_char * m); _gsl_vector_char_const_view gsl_matrix_char_const_subdiagonal (const gsl_matrix_char * m, const size_t k); _gsl_vector_char_const_view gsl_matrix_char_const_superdiagonal (const gsl_matrix_char * m, const size_t k); _gsl_vector_char_const_view gsl_matrix_char_const_subrow (const gsl_matrix_char * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_char_const_view gsl_matrix_char_const_subcolumn (const gsl_matrix_char * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_char_const_view gsl_matrix_char_const_view_array (const char * base, const size_t n1, const size_t n2); _gsl_matrix_char_const_view gsl_matrix_char_const_view_array_with_tda (const char * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_char_const_view gsl_matrix_char_const_view_vector (const gsl_vector_char * v, const size_t n1, const size_t n2); _gsl_matrix_char_const_view gsl_matrix_char_const_view_vector_with_tda (const gsl_vector_char * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ char gsl_matrix_char_get(const gsl_matrix_char * m, const size_t i, const size_t j); void gsl_matrix_char_set(gsl_matrix_char * m, const size_t i, const size_t j, const char x); char * gsl_matrix_char_ptr(gsl_matrix_char * m, const size_t i, const size_t j); const char * gsl_matrix_char_const_ptr(const gsl_matrix_char * m, const size_t i, const size_t j); void gsl_matrix_char_set_zero (gsl_matrix_char * m); void gsl_matrix_char_set_identity (gsl_matrix_char * m); void gsl_matrix_char_set_all (gsl_matrix_char * m, char x); int gsl_matrix_char_fread (FILE * stream, gsl_matrix_char * m) ; int gsl_matrix_char_fwrite (FILE * stream, const gsl_matrix_char * m) ; int gsl_matrix_char_fscanf (FILE * stream, gsl_matrix_char * m); int gsl_matrix_char_fprintf (FILE * stream, const gsl_matrix_char * m, const char * format); int gsl_matrix_char_memcpy(gsl_matrix_char * dest, const gsl_matrix_char * src); int gsl_matrix_char_swap(gsl_matrix_char * m1, gsl_matrix_char * m2); int gsl_matrix_char_swap_rows(gsl_matrix_char * m, const size_t i, const size_t j); int gsl_matrix_char_swap_columns(gsl_matrix_char * m, const size_t i, const size_t j); int gsl_matrix_char_swap_rowcol(gsl_matrix_char * m, const size_t i, const size_t j); int gsl_matrix_char_transpose (gsl_matrix_char * m); int gsl_matrix_char_transpose_memcpy (gsl_matrix_char * dest, const gsl_matrix_char * src); char gsl_matrix_char_max (const gsl_matrix_char * m); char gsl_matrix_char_min (const gsl_matrix_char * m); void gsl_matrix_char_minmax (const gsl_matrix_char * m, char * min_out, char * max_out); void gsl_matrix_char_max_index (const gsl_matrix_char * m, size_t * imax, size_t *jmax); void gsl_matrix_char_min_index (const gsl_matrix_char * m, size_t * imin, size_t *jmin); void gsl_matrix_char_minmax_index (const gsl_matrix_char * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_char_isnull (const gsl_matrix_char * m); int gsl_matrix_char_ispos (const gsl_matrix_char * m); int gsl_matrix_char_isneg (const gsl_matrix_char * m); int gsl_matrix_char_isnonneg (const gsl_matrix_char * m); int gsl_matrix_char_add (gsl_matrix_char * a, const gsl_matrix_char * b); int gsl_matrix_char_sub (gsl_matrix_char * a, const gsl_matrix_char * b); int gsl_matrix_char_mul_elements (gsl_matrix_char * a, const gsl_matrix_char * b); int gsl_matrix_char_div_elements (gsl_matrix_char * a, const gsl_matrix_char * b); int gsl_matrix_char_scale (gsl_matrix_char * a, const double x); int gsl_matrix_char_add_constant (gsl_matrix_char * a, const double x); int gsl_matrix_char_add_diagonal (gsl_matrix_char * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_char_get_row(gsl_vector_char * v, const gsl_matrix_char * m, const size_t i); int gsl_matrix_char_get_col(gsl_vector_char * v, const gsl_matrix_char * m, const size_t j); int gsl_matrix_char_set_row(gsl_matrix_char * m, const size_t i, const gsl_vector_char * v); int gsl_matrix_char_set_col(gsl_matrix_char * m, const size_t j, const gsl_vector_char * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline char gsl_matrix_char_get(const gsl_matrix_char * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_char_set(gsl_matrix_char * m, const size_t i, const size_t j, const char x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline char * gsl_matrix_char_ptr(gsl_matrix_char * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (char *) (m->data + (i * m->tda + j)) ; } extern inline const char * gsl_matrix_char_const_ptr(const gsl_matrix_char * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const char *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_CHAR_H__ */ sources_5316/external/gsl/gsl_rng__vax.c0000664000176700017670000000421311723710247017154 0ustar paulpaul/* rng/vax.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is the old vax generator MTH$RANDOM. The sequence is, x_{n+1} = (a x_n + c) mod m with a = 69069, c = 1 and m = 2^32. The seed specifies the initial value, x_1. The theoretical value of x_{10001} is 3051034865. The period of this generator is 2^32. */ static inline unsigned long int vax_get (void *vstate); static double vax_get_double (void *vstate); static void vax_set (void *state, unsigned long int s); typedef struct { unsigned long int x; } vax_state_t; static inline unsigned long int vax_get (void *vstate) { vax_state_t *state = (vax_state_t *) vstate; state->x = (69069 * state->x + 1) & 0xffffffffUL; return state->x; } static double vax_get_double (void *vstate) { return vax_get (vstate) / 4294967296.0 ; } static void vax_set (void *vstate, unsigned long int s) { vax_state_t *state = (vax_state_t *) vstate; /* default seed is 0. The constant term c stops the series from collapsing to 0,0,0,0,0,... */ state->x = s; return; } static const gsl_rng_type vax_type = {"vax", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (vax_state_t), &vax_set, &vax_get, &vax_get_double}; const gsl_rng_type *gsl_rng_vax = &vax_type; sources_5316/external/gsl/gsl_specfunc__mathieu_charv.c0000664000176700017670000005462211723710247022226 0ustar paulpaul/* specfunc/mathieu_charv.c * * Copyright (C) 2002 Lowell Johnson * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Author: L. Johnson */ #include "gsl__config.h" #include #include #include #include "gsl_math.h" #include "gsl_eigen.h" #include "gsl_errno.h" #include "gsl_sf_mathieu.h" /* prototypes */ static double solve_cubic(double c2, double c1, double c0); static double ceer(int order, double qq, double aa, int nterms) { double term, term1; int ii, n1; if (order == 0) term = 0.0; else { term = 2.0*qq*qq/aa; if (order != 2) { n1 = order/2 - 1; for (ii=0; ii= 0) { double t1 = rr + sqrt(ww); ss = fabs(t1)/t1*pow(fabs(t1), 1/3.); t1 = rr - sqrt(ww); tt = fabs(t1)/t1*pow(fabs(t1), 1/3.); } else { double theta = acos(rr/sqrt(-qq*qq*qq)); ss = 2*sqrt(-qq)*cos((theta + 4*M_PI)/3.); tt = 0.0; } return (ss + tt - c2/3); } /* Compute an initial approximation for the characteristic value. */ static double approx_c(int order, double qq) { double approx; double c0, c1, c2; if (order < 0) { GSL_ERROR_VAL("Undefined order for Mathieu function", GSL_EINVAL, 0.0); } switch (order) { case 0: if (qq <= 4) return (2 - sqrt(4 + 2*qq*qq)); /* Eqn. 31 */ else return asymptotic(order, qq); break; case 1: if (qq <= 4) return (5 + 0.5*(qq - sqrt(5*qq*qq - 16*qq + 64))); /* Eqn. 32 */ else return asymptotic(order, qq); break; case 2: if (qq <= 3) { c2 = -8.0; /* Eqn. 33 */ c1 = -48 - 3*qq*qq; c0 = 20*qq*qq; } else return asymptotic(order, qq); break; case 3: if (qq <= 6.25) { c2 = -qq - 8; /* Eqn. 34 */ c1 = 16*qq - 128 - 2*qq*qq; c0 = qq*qq*(qq + 8); } else return asymptotic(order, qq); break; default: if (order < 70) { if (1.7*order > 2*sqrt(qq)) { /* Eqn. 30 */ double n2 = (double)(order*order); double n22 = (double)((n2 - 1)*(n2 - 1)); double q2 = qq*qq; double q4 = q2*q2; approx = n2 + 0.5*q2/(n2 - 1); approx += (5*n2 + 7)*q4/(32*n22*(n2 - 1)*(n2 - 4)); approx += (9*n2*n2 + 58*n2 + 29)*q4*q2/ (64*n22*n22*(n2 - 1)*(n2 - 4)*(n2 - 9)); if (1.4*order < 2*sqrt(qq)) { approx += asymptotic(order, qq); approx *= 0.5; } } else approx = asymptotic(order, qq); return approx; } else return order*order; } /* Solve the cubic x^3 + c2*x^2 + c1*x + c0 = 0 */ approx = solve_cubic(c2, c1, c0); if ( approx < 0 && sqrt(qq) > 0.1*order ) return asymptotic(order-1, qq); else return (order*order + fabs(approx)); } static double approx_s(int order, double qq) { double approx; double c0, c1, c2; if (order < 1) { GSL_ERROR_VAL("Undefined order for Mathieu function", GSL_EINVAL, 0.0); } switch (order) { case 1: if (qq <= 4) return (5 - 0.5*(qq + sqrt(5*qq*qq + 16*qq + 64))); /* Eqn. 35 */ else return asymptotic(order-1, qq); break; case 2: if (qq <= 5) return (10 - sqrt(36 + qq*qq)); /* Eqn. 36 */ else return asymptotic(order-1, qq); break; case 3: if (qq <= 6.25) { c2 = qq - 8; /* Eqn. 37 */ c1 = -128 - 16*qq - 2*qq*qq; c0 = qq*qq*(8 - qq); } else return asymptotic(order-1, qq); break; default: if (order < 70) { if (1.7*order > 2*sqrt(qq)) { /* Eqn. 30 */ double n2 = (double)(order*order); double n22 = (double)((n2 - 1)*(n2 - 1)); double q2 = qq*qq; double q4 = q2*q2; approx = n2 + 0.5*q2/(n2 - 1); approx += (5*n2 + 7)*q4/(32*n22*(n2 - 1)*(n2 - 4)); approx += (9*n2*n2 + 58*n2 + 29)*q4*q2/ (64*n22*n22*(n2 - 1)*(n2 - 4)*(n2 - 9)); if (1.4*order < 2*sqrt(qq)) { approx += asymptotic(order-1, qq); approx *= 0.5; } } else approx = asymptotic(order-1, qq); return approx; } else return order*order; } /* Solve the cubic x^3 + c2*x^2 + c1*x + c0 = 0 */ approx = solve_cubic(c2, c1, c0); if ( approx < 0 && sqrt(qq) > 0.1*order ) return asymptotic(order-1, qq); else return (order*order + fabs(approx)); } int gsl_sf_mathieu_a(int order, double qq, gsl_sf_result *result) { int even_odd, nterms = 50, ii, counter = 0, maxcount = 200; double a1, a2, fa, fa1, dela, aa_orig, da = 0.025, aa; even_odd = 0; if (order % 2 != 0) even_odd = 1; /* If the argument is 0, then the coefficient is simply the square of the order. */ if (qq == 0) { result->val = order*order; result->err = 0.0; return GSL_SUCCESS; } /* Use symmetry characteristics of the functions to handle cases with negative order and/or argument q. See Abramowitz & Stegun, 20.8.3. */ if (order < 0) order *= -1; if (qq < 0.0) { if (even_odd == 0) return gsl_sf_mathieu_a(order, -qq, result); else return gsl_sf_mathieu_b(order, -qq, result); } /* Compute an initial approximation for the characteristic value. */ aa = approx_c(order, qq); /* Save the original approximation for later comparison. */ aa_orig = aa; /* Loop as long as the final value is not near the approximate value (with a max limit to avoid potential infinite loop). */ while (counter < maxcount) { a1 = aa + 0.001; ii = 0; if (even_odd == 0) fa1 = ceer(order, qq, a1, nterms); else fa1 = ceor(order, qq, a1, nterms); for (;;) { if (even_odd == 0) fa = ceer(order, qq, aa, nterms); else fa = ceor(order, qq, aa, nterms); a2 = a1; a1 = aa; if (fa == fa1) { result->err = GSL_DBL_EPSILON; break; } aa -= (aa - a2)/(fa - fa1)*fa; dela = fabs(aa - a2); if (dela < GSL_DBL_EPSILON) { result->err = GSL_DBL_EPSILON; break; } if (ii > 20) { result->err = dela; break; } fa1 = fa; ii++; } /* If the solution found is not near the original approximation, tweak the approximate value, and try again. */ if (fabs(aa - aa_orig) > (3 + 0.01*order*fabs(aa_orig))) { counter++; if (counter == maxcount) { result->err = fabs(aa - aa_orig); break; } if (aa > aa_orig) aa = aa_orig - da*counter; else aa = aa_orig + da*counter; continue; } else break; } result->val = aa; /* If we went through the maximum number of retries and still didn't find the solution, let us know. */ if (counter == maxcount) { GSL_ERROR("Wrong characteristic Mathieu value", GSL_EFAILED); } return GSL_SUCCESS; } int gsl_sf_mathieu_b(int order, double qq, gsl_sf_result *result) { int even_odd, nterms = 50, ii, counter = 0, maxcount = 200; double a1, a2, fa, fa1, dela, aa_orig, da = 0.025, aa; even_odd = 0; if (order % 2 != 0) even_odd = 1; /* The order cannot be 0. */ if (order == 0) { GSL_ERROR("Characteristic value undefined for order 0", GSL_EFAILED); } /* If the argument is 0, then the coefficient is simply the square of the order. */ if (qq == 0) { result->val = order*order; result->err = 0.0; return GSL_SUCCESS; } /* Use symmetry characteristics of the functions to handle cases with negative order and/or argument q. See Abramowitz & Stegun, 20.8.3. */ if (order < 0) order *= -1; if (qq < 0.0) { if (even_odd == 0) return gsl_sf_mathieu_b(order, -qq, result); else return gsl_sf_mathieu_a(order, -qq, result); } /* Compute an initial approximation for the characteristic value. */ aa = approx_s(order, qq); /* Save the original approximation for later comparison. */ aa_orig = aa; /* Loop as long as the final value is not near the approximate value (with a max limit to avoid potential infinite loop). */ while (counter < maxcount) { a1 = aa + 0.001; ii = 0; if (even_odd == 0) fa1 = seer(order, qq, a1, nterms); else fa1 = seor(order, qq, a1, nterms); for (;;) { if (even_odd == 0) fa = seer(order, qq, aa, nterms); else fa = seor(order, qq, aa, nterms); a2 = a1; a1 = aa; if (fa == fa1) { result->err = GSL_DBL_EPSILON; break; } aa -= (aa - a2)/(fa - fa1)*fa; dela = fabs(aa - a2); if (dela < 1e-18) { result->err = GSL_DBL_EPSILON; break; } if (ii > 20) { result->err = dela; break; } fa1 = fa; ii++; } /* If the solution found is not near the original approximation, tweak the approximate value, and try again. */ if (fabs(aa - aa_orig) > (3 + 0.01*order*fabs(aa_orig))) { counter++; if (counter == maxcount) { result->err = fabs(aa - aa_orig); break; } if (aa > aa_orig) aa = aa_orig - da*counter; else aa = aa_orig + da*counter; continue; } else break; } result->val = aa; /* If we went through the maximum number of retries and still didn't find the solution, let us know. */ if (counter == maxcount) { GSL_ERROR("Wrong characteristic Mathieu value", GSL_EFAILED); } return GSL_SUCCESS; } /* Eigenvalue solutions for characteristic values below. */ /* figi.c converted from EISPACK Fortran FIGI.F. * * given a nonsymmetric tridiagonal matrix such that the products * of corresponding pairs of off-diagonal elements are all * non-negative, this subroutine reduces it to a symmetric * tridiagonal matrix with the same eigenvalues. if, further, * a zero product only occurs when both factors are zero, * the reduced matrix is similar to the original matrix. * * on input * * n is the order of the matrix. * * t contains the input matrix. its subdiagonal is * stored in the last n-1 positions of the first column, * its diagonal in the n positions of the second column, * and its superdiagonal in the first n-1 positions of * the third column. t(1,1) and t(n,3) are arbitrary. * * on output * * t is unaltered. * * d contains the diagonal elements of the symmetric matrix. * * e contains the subdiagonal elements of the symmetric * matrix in its last n-1 positions. e(1) is not set. * * e2 contains the squares of the corresponding elements of e. * e2 may coincide with e if the squares are not needed. * * ierr is set to * zero for normal return, * n+i if t(i,1)*t(i-1,3) is negative, * -(3*n+i) if t(i,1)*t(i-1,3) is zero with one factor * non-zero. in this case, the eigenvectors of * the symmetric matrix are not simply related * to those of t and should not be sought. * * questions and comments should be directed to burton s. garbow, * mathematics and computer science div, argonne national laboratory * * this version dated august 1983. */ static int figi(int nn, double *tt, double *dd, double *ee, double *e2) { int ii; for (ii=0; iieven_order, odd_order = work->odd_order, extra_values = work->extra_values, ii, jj; int status; double *tt = work->tt, *dd = work->dd, *ee = work->ee, *e2 = work->e2, *zz = work->zz, *aa = work->aa; gsl_matrix_view mat, evec; gsl_vector_view eval; gsl_eigen_symmv_workspace *wmat = work->wmat; if (order_max > work->size || order_max <= order_min || order_min < 0) { GSL_ERROR ("invalid range [order_min,order_max]", GSL_EINVAL); } /* Convert the nonsymmetric tridiagonal matrix to a symmetric tridiagonal form. */ tt[0] = 0.0; tt[1] = 0.0; tt[2] = qq; for (ii=1; iieval, 0, even_order); evec = gsl_matrix_submatrix(work->evec, 0, 0, even_order, even_order); gsl_eigen_symmv(&mat.matrix, &eval.vector, &evec.matrix, wmat); gsl_eigen_symmv_sort(&eval.vector, &evec.matrix, GSL_EIGEN_SORT_VAL_ASC); for (ii=0; iieval, 0, odd_order); evec = gsl_matrix_submatrix(work->evec, 0, 0, odd_order, odd_order); gsl_eigen_symmv(&mat.matrix, &eval.vector, &evec.matrix, wmat); gsl_eigen_symmv_sort(&eval.vector, &evec.matrix, GSL_EIGEN_SORT_VAL_ASC); for (ii=0; iieven_order-1, odd_order = work->odd_order, extra_values = work->extra_values, ii, jj; double *zz = work->zz, *bb = work->bb; gsl_matrix_view mat, evec; gsl_vector_view eval; gsl_eigen_symmv_workspace *wmat = work->wmat; if (order_max > work->size || order_max <= order_min || order_min < 0) { GSL_ERROR ("invalid range [order_min,order_max]", GSL_EINVAL); } /* Fill the period \pi matrix. */ for (ii=0; iieval, 0, even_order); evec = gsl_matrix_submatrix(work->evec, 0, 0, even_order, even_order); gsl_eigen_symmv(&mat.matrix, &eval.vector, &evec.matrix, wmat); gsl_eigen_symmv_sort(&eval.vector, &evec.matrix, GSL_EIGEN_SORT_VAL_ASC); bb[0] = 0.0; for (ii=0; iieval, 0, odd_order); evec = gsl_matrix_submatrix(work->evec, 0, 0, odd_order, odd_order); gsl_eigen_symmv(&mat.matrix, &eval.vector, &evec.matrix, wmat); gsl_eigen_symmv_sort(&eval.vector, &evec.matrix, GSL_EIGEN_SORT_VAL_ASC); for (ii=0; ii K) ? i - K : 0; const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; for (j = j_min; j < j_max; j++) { BASE Aij = A[(K - i + j) + i * lda]; Y[jy] += tmp1 * Aij; tmp2 += Aij * X[jx]; jx += incX; jy += incY; } Y[iy] += tmp1 * A[K + i * lda] + alpha * tmp2; ix += incX; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_specfunc__transport.c0000664000176700017670000003114111723710247021432 0ustar paulpaul/* specfunc/transport.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_transport.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__check.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" static double transport2_data[18] = { 1.671760446434538503, -0.147735359946794490, 0.148213819946936338e-01, -0.14195330326305613e-02, 0.1306541324415708e-03, -0.117155795867579e-04, 0.10333498445756e-05, -0.901911304223e-07, 0.78177169833e-08, -0.6744565684e-09, 0.579946394e-10, -0.49747619e-11, 0.425961e-12, -0.36422e-13, 0.3111e-14, -0.265e-15, 0.23e-16, -0.19e-17 }; static cheb_series transport2_cs = { transport2_data, 17, -1, 1, 9 }; static double transport3_data[18] = { 0.762012543243872007, -0.105674387705058533, 0.119778084819657810e-01, -0.12144015203698307e-02, 0.1155099769392855e-03, -0.105815992124423e-04, 0.9474663385302e-06, -0.836221212858e-07, 0.73109099278e-08, -0.6350594779e-09, 0.549118282e-10, -0.47321395e-11, 0.4067695e-12, -0.348971e-13, 0.29892e-14, -0.256e-15, 0.219e-16, -0.19e-17 }; static cheb_series transport3_cs = { transport3_data, 17, -1, 1, 9 }; static double transport4_data[18] = { 0.4807570994615110579, -0.8175378810321083956e-01, 0.1002700665975162973e-01, -0.10599339359820151e-02, 0.1034506245030405e-03, -0.96442705485899e-05, 0.8745544408515e-06, -0.779321207981e-07, 0.68649886141e-08, -0.5999571076e-09, 0.521366241e-10, -0.45118382e-11, 0.3892159e-12, -0.334936e-13, 0.28767e-14, -0.2467e-15, 0.211e-16, -0.18e-17 }; static cheb_series transport4_cs = { transport4_data, 17, -1, 1, 9 }; static double transport5_data[18] = { 0.347777777133910789, -0.66456988976050428e-01, 0.8611072656883309e-02, -0.9396682223755538e-03, 0.936324806081513e-04, -0.88571319340833e-05, 0.811914989145e-06, -0.72957654233e-07, 0.646971455e-08, -0.568490283e-09, 0.49625598e-10, -0.4310940e-11, 0.373100e-12, -0.32198e-13, 0.2772e-14, -0.238e-15, 0.21e-16, -0.18e-17 }; static cheb_series transport5_cs = { transport5_data, 17, -1, 1, 9 }; static double transport_sumexp(const int numexp, const int order, const double t, double x) { double rk = (double)numexp; double sumexp = 0.0; int k; for(k=1; k<=numexp; k++) { double sum2 = 1.0; double xk = 1.0/(rk*x); double xk1 = 1.0; int j; for(j=1; j<=order; j++) { sum2 = sum2*xk1*xk + 1.0; xk1 += 1.0; } sumexp *= t; sumexp += sum2; rk -= 1.0; } return sumexp; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_transport_2_e(const double x, gsl_sf_result * result) { const double val_infinity = 3.289868133696452873; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x < 3.0*GSL_SQRT_DBL_EPSILON) { result->val = x; result->err = GSL_DBL_EPSILON*fabs(x) + x*x/2.0; return GSL_SUCCESS; } else if(x <= 4.0) { double t = (x*x/8.0 - 0.5) - 0.5; gsl_sf_result result_c; cheb_eval_e(&transport2_cs, t, &result_c); result->val = x * result_c.val; result->err = x * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -GSL_LOG_DBL_EPSILON) { const int numexp = (int)((-GSL_LOG_DBL_EPSILON)/x) + 1; const double sumexp = transport_sumexp(numexp, 2, exp(-x), x); const double t = 2.0 * log(x) - x + log(sumexp); if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + fabs(t) * et); } return GSL_SUCCESS; } else if(x < 2.0/GSL_DBL_EPSILON) { const int numexp = 1; const double sumexp = transport_sumexp(numexp, 2, 1.0, x); const double t = 2.0 * log(x) - x + log(sumexp); if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } else { const double t = 2.0 * log(x) - x; if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } } int gsl_sf_transport_3_e(const double x, gsl_sf_result * result) { const double val_infinity = 7.212341418957565712; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 3.0*GSL_SQRT_DBL_EPSILON) { result->val = 0.5*x*x; result->err = 2.0 * GSL_DBL_EPSILON * result->val; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } else if(x <= 4.0) { const double x2 = x*x; const double t = (x2/8.0 - 0.5) - 0.5; gsl_sf_result result_c; cheb_eval_e(&transport3_cs, t, &result_c); result->val = x2 * result_c.val; result->err = x2 * result_c.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -GSL_LOG_DBL_EPSILON) { const int numexp = (int)((-GSL_LOG_DBL_EPSILON)/x) + 1; const double sumexp = transport_sumexp(numexp, 3, exp(-x), x); const double t = 3.0 * log(x) - x + log(sumexp); if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + fabs(t) * et); } return GSL_SUCCESS; } else if(x < 3.0/GSL_DBL_EPSILON) { const int numexp = 1; const double sumexp = transport_sumexp(numexp, 3, 1.0, x); const double t = 3.0 * log(x) - x + log(sumexp); if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } else { const double t = 3.0 * log(x) - x; if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } } int gsl_sf_transport_4_e(const double x, gsl_sf_result * result) { const double val_infinity = 25.97575760906731660; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 3.0*GSL_SQRT_DBL_EPSILON) { result->val = x*x*x/3.0; result->err = 3.0 * GSL_DBL_EPSILON * result->val; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } else if(x <= 4.0) { const double x2 = x*x; const double t = (x2/8.0 - 0.5) - 0.5; gsl_sf_result result_c; cheb_eval_e(&transport4_cs, t, &result_c); result->val = x2*x * result_c.val; result->err = x2*x * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -GSL_LOG_DBL_EPSILON) { const int numexp = (int)((-GSL_LOG_DBL_EPSILON)/x) + 1; const double sumexp = transport_sumexp(numexp, 4, exp(-x), x); const double t = 4.0 * log(x) - x + log(sumexp); if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } else if(x < 3.0/GSL_DBL_EPSILON) { const int numexp = 1; const double sumexp = transport_sumexp(numexp, 4, 1.0, x); const double t = 4.0 * log(x) - x + log(sumexp); if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } else { const double t = 4.0 * log(x) - x; if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } } int gsl_sf_transport_5_e(const double x, gsl_sf_result * result) { const double val_infinity = 124.4313306172043912; /* CHECK_POINTER(result) */ if(x < 0.0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x < 3.0*GSL_SQRT_DBL_EPSILON) { result->val = x*x*x*x/4.0; result->err = 4.0 * GSL_DBL_EPSILON * result->val; CHECK_UNDERFLOW(result); return GSL_SUCCESS; } else if(x <= 4.0) { const double x2 = x*x; const double t = (x2/8.0 - 0.5) - 0.5; gsl_sf_result result_c; cheb_eval_e(&transport5_cs, t, &result_c); result->val = x2*x2 * result_c.val; result->err = x2*x2 * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -GSL_LOG_DBL_EPSILON) { const int numexp = (int)((-GSL_LOG_DBL_EPSILON)/x) + 1; const double sumexp = transport_sumexp(numexp, 5, exp(-x), x); const double t = 5.0 * log(x) - x + log(sumexp); if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } else if(x < 3.0/GSL_DBL_EPSILON) { const int numexp = 1; const double sumexp = transport_sumexp(numexp, 5, 1.0, x); const double t = 5.0 * log(x) - x + log(sumexp); if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } else { const double t = 5.0 * log(x) - x; if(t < GSL_LOG_DBL_EPSILON) { result->val = val_infinity; result->err = 2.0 * GSL_DBL_EPSILON * val_infinity; } else { const double et = exp(t); result->val = val_infinity - et; result->err = 2.0 * GSL_DBL_EPSILON * (val_infinity + (fabs(t)+1.0) * et); } return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_transport_2(const double x) { EVAL_RESULT(gsl_sf_transport_2_e(x, &result)); } double gsl_sf_transport_3(const double x) { EVAL_RESULT(gsl_sf_transport_3_e(x, &result)); } double gsl_sf_transport_4(const double x) { EVAL_RESULT(gsl_sf_transport_4_e(x, &result)); } double gsl_sf_transport_5(const double x) { EVAL_RESULT(gsl_sf_transport_5_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__dtrsv.c0000664000176700017670000000062011723710247020014 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dtrsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const double *A, const int lda, double *X, const int incX) { #define BASE double #include "gsl_cblas__source_trsv_r.h" #undef BASE } sources_5316/external/gsl/gsl_multimin__convergence.c0000664000176700017670000000264311723710247021731 0ustar paulpaul/* multimin/convergence.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Fabrice Rossi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_multimin.h" #include "gsl_blas.h" int gsl_multimin_test_gradient (const gsl_vector *g, double epsabs) { double norm; if (epsabs < 0.0) { GSL_ERROR ("absolute tolerance is negative", GSL_EBADTOL); } norm = gsl_blas_dnrm2(g); if (norm < epsabs) { return GSL_SUCCESS; } return GSL_CONTINUE; } int gsl_multimin_test_size (const double size, double epsabs) { if (epsabs < 0.0) { GSL_ERROR ("absolute tolerance is negative", GSL_EBADTOL); } if (size < epsabs) { return GSL_SUCCESS; } return GSL_CONTINUE; } sources_5316/external/gsl/gsl_statistics__lag1_source.c0000664000176700017670000000327511723710247022175 0ustar paulpaul/* statistics/lag1_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,lag1_autocorrelation) (const BASE data[], const size_t stride, const size_t n) { const double mean = FUNCTION(gsl_stats,mean) (data, stride, n); return FUNCTION(gsl_stats,lag1_autocorrelation_m)(data, stride, n, mean); } double FUNCTION(gsl_stats,lag1_autocorrelation_m) (const BASE data[], const size_t stride, const size_t size, const double mean) { /* Compute the lag-1 autocorrelation of a dataset using the recurrence relation */ size_t i; long double r1 ; long double q = 0 ; long double v = (data[0 * stride] - mean) * (data[0 * stride] - mean) ; for (i = 1; i < size ; i++) { const long double delta0 = (data[(i-1) * stride] - mean); const long double delta1 = (data[i * stride] - mean); q += (delta0 * delta1 - q)/(i + 1); v += (delta1 * delta1 - v)/(i + 1); } r1 = q / v ; return r1; } sources_5316/external/gsl/gsl_sf__check.h0000644000176700017670000000017610707442037017264 0ustar paulpaul/* check for underflow */ #define CHECK_UNDERFLOW(r) if (fabs((r)->val) < GSL_DBL_MIN) GSL_ERROR("underflow", GSL_EUNDRFLW); sources_5316/external/gsl/gsl_specfunc__bessel_olver.c0000664000176700017670000007622311723710247022074 0ustar paulpaul/* specfunc/bessel_olver.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_airy.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_olver.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /* fit for f(x) = zofmzeta((x+1)/2), 0 <= mzeta <= 1 */ static double zofmzeta_a_data[20] = { 2.9332563730829348990, 0.4896518224847036624, 0.0228637617355380860, -0.0001715731377284693, -0.0000105927538148751, 1.0595602530419e-6, -4.68016051691e-8, 5.8310020e-12, 1.766537581e-10, -1.45034640e-11, 4.357772e-13, 4.60971e-14, -2.57571e-14, 2.26468e-14, -2.22053e-14, 2.08593e-14, -1.84454e-14, 1.50150e-14, -1.06506e-14, 5.5375e-15 }; static cheb_series zofmzeta_a_cs = { zofmzeta_a_data, 19, -1,1, 8 }; /* fit for f(x) = zofmzeta((9x+11)/2), 1 <= mzeta <= 10 */ static double zofmzeta_b_data[30] = { 22.40725276466303489, 10.39808258825165581, 1.092050144486018425, -0.071111274777921604, 0.008990125336059704, -0.001201950338088875, 0.000106686807968315, 0.000017406491576830, -0.000014946669657805, 6.189984487752e-6, -2.049466715178e-6, 5.87189458020e-7, -1.46077514157e-7, 2.9803936132e-8, -3.817692108e-9, -4.66980416e-10, 5.83860334e-10, -2.78825299e-10, 1.01682688e-10, -3.1209928e-11, 8.111122e-12, -1.663986e-12, 1.81364e-13, 5.3414e-14, -4.7234e-14, 2.1689e-14, -7.815e-15, 2.371e-15, -6.04e-16, 1.20e-16 }; static cheb_series zofmzeta_b_cs = { zofmzeta_b_data, 29, -1,1, 15 }; /* fit for f(x) = zofmzeta(mz(x))/mz(x)^(3/2), * mz(x) = (2/(x+1))^(2/3) 10 * 10 <= mzeta <= Inf */ static double zofmzeta_c_data[11] = { 1.3824761227122911500, 0.0244856101686774245, -0.0000842866496282540, 1.4656076569771e-6, -3.14874099476e-8, 7.561134833e-10, -1.94531643e-11, 5.245878e-13, -1.46380e-14, 4.192e-16, -1.23e-17 }; static cheb_series zofmzeta_c_cs = { zofmzeta_c_data, 10, -1,1, 6 }; /* Invert [Abramowitz+Stegun, 9.3.39]. * Assumes minus_zeta >= 0. */ double gsl_sf_bessel_Olver_zofmzeta(double minus_zeta) { if(minus_zeta < 1.0) { const double x = 2.0*minus_zeta - 1.0; gsl_sf_result c; cheb_eval_e(&zofmzeta_a_cs, x, &c); return c.val; } else if(minus_zeta < 10.0) { const double x = (2.0*minus_zeta - 11.0)/9.0; gsl_sf_result c; cheb_eval_e(&zofmzeta_b_cs, x, &c); return c.val; } else { const double TEN_32 = 31.62277660168379332; /* 10^(3/2) */ const double p = pow(minus_zeta, 3.0/2.0); const double x = 2.0*TEN_32/p - 1.0; gsl_sf_result c; cheb_eval_e(&zofmzeta_c_cs, x, &c); return c.val * p; } } /* Chebyshev fit for f(x) = z(x)^6 A_3(z(x)), z(x) = 22/(10(x+1)) */ static double A3_gt1_data[31] = { -0.123783199829515294670493131190, 0.104636462534700704670877382304, -0.067500816575851826744877535903, 0.035563362418888483652711005520, -0.0160738524035979408472979609051, 0.0064497878252851092073278056238, -0.00235408261133449663958121821593, 0.00079545702851302155411892534965, -0.00025214920745855079895784825637, 0.00007574004596069392921153301833, -0.00002172917966339623434407978263, 5.9914810727868915476543145465e-06, -1.5958781571808992162953719817e-06, 4.1232986512903717525448312012e-07, -1.0369725993417659101913919101e-07, 2.5457982304266541145999235022e-08, -6.1161715053791743082427422443e-09, 1.4409346199138658887871461320e-09, -3.3350445956255561668232014995e-10, 7.5950686572918996453336138108e-11, -1.7042296334409430377389900278e-11, 3.7723525020626230919721640081e-12, -8.2460237635733980528416501227e-13, 1.7816961527997797696251868875e-13, -3.8084101506541792942694560802e-14, 8.0593669930916099079755351563e-15, -1.6896565961641739017452636964e-15, 3.5115651805888443184822853595e-16, -7.2384771938569255638904297651e-17, 1.4806598977677176106283840244e-17, -3.0069285750787303634897997963e-18 }; static cheb_series A3_gt1_cs = { A3_gt1_data, 30, -1,1, 17 }; /* chebyshev expansion for f(x) = z(x)^8 A_4(z(x)), z(x) = 12/(5(x+1)) */ static double A4_gt1_data[30] = { 1.15309329391198493586724229008, -1.01812701728669338904729927846, 0.71964022270555684403652781941, -0.42359963977172689685150061355, 0.215024488759339557817435404261, -0.096751915348145944032096342479, 0.039413982058824310099856035361, -0.014775225692561697963781115014, 0.005162114514159370516947823271, -0.00169783446445524322560925166335, 0.00052995667873006847211519193478, -0.00015802027574996477115667974856, 0.000045254366680989687988902825193, -0.000012503722965474638015488600967, 3.3457656998119148699124716204e-06, -8.6981575241150758412492331833e-07, 2.2030895484325645640823940625e-07, -5.4493369492600677068285936533e-08, 1.3190457281724829107139385556e-08, -3.1301560183377379158951191769e-09, 7.2937802527123344842593076131e-10, -1.6712080137945140407348940109e-10, 3.7700053248213600430503521194e-11, -8.3824538848817227637828899571e-12, 1.8388741910049766865274037194e-12, -3.9835919980753778560117573063e-13, 8.5288827136546615604290389711e-14, -1.8060227869114416998653266836e-14, 3.7849342199690728470461022877e-15, -7.8552867468122209577151823365e-16 }; static cheb_series A4_gt1_cs = { A4_gt1_data, 17, /* 29, */ -1, 1, 17 }; /* Chebyshev fit for f(x) = z(x)^3 B_2(z(x)), z(x) = 12/(5(x+1)) */ static double B2_gt1_data[40] = { 0.00118587147272683864479328868589, 0.00034820459990648274622193981840, -0.00030411304425639768103075864567, 0.00002812066284012343531484682886, 0.00004493525295901613184489898748, -0.00003037629997093072196779489677, 0.00001125979647123875721949743970, -2.4832533969517775991951008218e-06, -9.9003813640537799587086928278e-08, 4.9259859656183110299492296029e-07, -3.7644120964426705960749504975e-07, 2.2887828521334625189639122509e-07, -1.3202687370822203731489855050e-07, 7.7019669092537400811434860763e-08, -4.6589706973010511603890144294e-08, 2.9396476233013923711978522963e-08, -1.9293230611988282919101954538e-08, 1.3099107013728717842406906896e-08, -9.1509111940885962831104149355e-09, 6.5483472971925614347299375295e-09, -4.7831253582139967461241674569e-09, 3.5562625457426178152760148639e-09, -2.6853389444008414186916562103e-09, 2.0554738667134200145781857289e-09, -1.5923172019517426277886522758e-09, 1.2465923213464381457319481498e-09, -9.8494846881180588507969988989e-10, 7.8438674499372126663957464312e-10, -6.2877567918342950225937136855e-10, 5.0662318868755257959686944117e-10, -4.0962270881243451160378710952e-10, 3.3168684677374908553161911299e-10, -2.6829406619847450633596163305e-10, 2.1603988122184568375561077873e-10, -1.7232373309560278402012124481e-10, 1.3512709089611470626617830434e-10, -1.0285354732538663013167579792e-10, 7.4211345443901713467637018423e-11, -4.8124980266864320351456993068e-11, 2.3666534694476306077416831958e-11 }; static cheb_series B2_gt1_cs = { B2_gt1_data, 39, -1, 1, 30 }; /* Chebyshev fit for f(x) = z(x)^6 B_3(z(x)), z(x) = 12/(5(x+1)) */ static double B3_gt1_data[30] = { -0.0102445379362695740863663926486, 0.0036618484329295342954730801917, 0.0026154252498599303282569321117, -0.0036187389410353156728771706336, 0.0021878564157692275944613452462, -0.0008219952303590803584426516821, 0.0001281773889155631494321316520, 0.0001000944653368032985720548637, -0.0001288293344663774273453147788, 0.00010136264202696513867821487205, -0.00007000275849659556221916572733, 0.00004694886396757430431607955146, -0.00003190003869717837686356945696, 0.00002231453668447775219665947479, -0.00001611102197712439539300336438, 0.00001196634424990735214466633513, -9.0986920398931223804111374679e-06, 7.0492613694235423068926562567e-06, -5.5425216624642184684300615394e-06, 4.4071884714230296614449244106e-06, -3.5328595506791663127928952625e-06, 2.84594975572077091520522824686e-06, -2.29592697828824392391071619788e-06, 1.84714740375289956396370322228e-06, -1.47383331248116454652025598620e-06, 1.15687781098593231076084710267e-06, -8.8174688524627071175315084910e-07, 6.3705856964426840441434605593e-07, -4.1358791499961929237755474814e-07, 2.0354151158738819867477996807e-07 }; static cheb_series B3_gt1_cs = { B3_gt1_data, 29, -1, 1, 29 }; /* Chebyshev fit for f(x) = z(x) B_2(z(x)), z(x) = 2(x+1)/5 */ static double B2_lt1_data[40] = { 0.00073681565841337130021924199490, 0.00033803599647571227535304316937, -0.00008251723219239754024210552679, -0.00003390879948656432545900779710, 0.00001961398056848881816694014889, -2.35593745904151401624656805567e-06, -1.79055017080406086541563835433e-06, 1.33129571185610681090725934031e-06, -5.38879444715436544130673956170e-07, 1.49603056041381416881299945557e-07, -1.83377228267274327911131293091e-08, -1.33191430762944336526965187651e-08, 1.60642096463700438411396889489e-08, -1.28932576330421806740136816643e-08, 9.6169275086179165484403221944e-09, -7.1818502280703532276832887290e-09, 5.4744009217215145730697754561e-09, -4.2680446690508456935030086136e-09, 3.3941665009266174865683284781e-09, -2.7440714072221673882163135170e-09, 2.2488361522108255229193038962e-09, -1.8638240716608748862087923337e-09, 1.5592350940805373500866440401e-09, -1.3145743937732330609242633070e-09, 1.1153716777215047842790244968e-09, -9.5117576805266622854647303110e-10, 8.1428799553234876296804561100e-10, -6.9893770813548773664326279169e-10, 6.0073113636087448745018831981e-10, -5.1627434258513453901420776514e-10, 4.4290993195074905891788459756e-10, -3.7852978599966867611179315200e-10, 3.2143959338863177145307610452e-10, -2.7025926680620777594992221143e-10, 2.2384857772457918539228234321e-10, -1.8125071664276678046551271701e-10, 1.4164870008713668767293008546e-10, -1.0433101857132782485813325981e-10, 6.8663910168392483929411418190e-11, -3.4068313177952244040559740439e-11 }; static cheb_series B2_lt1_cs = { B2_lt1_data, 39, -1, 1, 39 }; /* Chebyshev fit for f(x) = B_3(2(x+1)/5) */ static double B3_lt1_data[40] = { -0.00137160820526992057354001614451, -0.00025474937951101049982680561302, 0.00024762975547895881652073467771, 0.00005229657281480196749313930265, -0.00007488354272621512385016593760, 0.00001416880012891046449980449746, 0.00001528986060172183690742576230, -0.00001668672297078590514293325326, 0.00001061765189536459018739585094, -5.8220577442406209989680801335e-06, 3.3322423743855900506302033234e-06, -2.23292405803003860894449897815e-06, 1.74816651036678291794777245325e-06, -1.49581306041395051804547535093e-06, 1.32759146107893129050610165582e-06, -1.19376077392564467408373553343e-06, 1.07878303863211630544654040875e-06, -9.7743335011819134006676476250e-07, 8.8729318903693324226127054792e-07, -8.0671146292125665050876015280e-07, 7.3432860378667354971042255937e-07, -6.6897926072697370325310483359e-07, 6.0966619703735610352576581485e-07, -5.5554095284507959561958605420e-07, 5.0588335673197236002812826526e-07, -4.6008146297767601862670079590e-07, 4.1761348515688145911438168306e-07, -3.7803230006989446874174476515e-07, 3.4095248501364300041684648230e-07, -3.0603959751354749520615015472e-07, 2.7300134179365690589640458993e-07, -2.4158028250762304756044254231e-07, 2.1154781038298751985689113868e-07, -1.8269911328756771201465223313e-07, 1.5484895085808513749026173074e-07, -1.2782806851555809369226440495e-07, 1.0148011725394892565174207341e-07, -7.5658969771439627809239950461e-08, 5.0226342286491286957075289622e-08, -2.5049645660259882970547555831e-08 }; static cheb_series B3_lt1_cs = { B3_lt1_data, 39, -1, 1, 39 }; /* Chebyshev fit for f(x) = A_3(9(x+1)/20) */ static double A3_lt1_data[40] = { -0.00017982561472134418587634980117, -0.00036558603837525275836608884064, -0.00002819398055929628850294406363, 0.00016704539863875736769812786067, -0.00007098969970347674307623044850, -8.4470843942344237748899879940e-06, 0.0000273413090343147765148014327150, -0.0000199073838489821681991178018081, 0.0000100004176278235088881096950105, -3.9739852013143676487867902026e-06, 1.2265357766449574306882693267e-06, -1.88755584306424047416914864854e-07, -1.37482206060161206336523452036e-07, 2.10326379301853336795686477738e-07, -2.05583778245412633433934301948e-07, 1.82377384812654863038691147988e-07, -1.58130247846381041027699152436e-07, 1.36966982725588978654041029615e-07, -1.19250280944620257443805710485e-07, 1.04477169029350256435316644493e-07, -9.2064832489437534542041040184e-08, 8.1523798290458784610230199344e-08, -7.2471794980050867512294061891e-08, 6.4614432955971132569968860233e-08, -5.7724095125560946811081322985e-08, 5.1623107567436835158110947901e-08, -4.6171250746798606260216486042e-08, 4.1256621998650164023254101585e-08, -3.6788925543159819135102047082e-08, 3.2694499457951844422299750661e-08, -2.89125899697964696586521743928e-08, 2.53925288725374047626589488217e-08, -2.20915707933726481321465184207e-08, 1.89732166352720474944407102940e-08, -1.60058977893259856012119939554e-08, 1.31619294542205876946742394494e-08, -1.04166651771938038563454275883e-08, 7.7478015858156185064152078434e-09, -5.1347942579352613057675111787e-09, 2.5583541594586723967261504321e-09 }; static cheb_series A3_lt1_cs = { A3_lt1_data, 39, -1, 1, 39 }; /* chebyshev fit for f(x) = A_4(2(x+1)/5) */ static double A4_lt1_data[30] = { 0.00009054703770051610946958226736, 0.00033066000498098017589672988293, 0.00019737453734363989127226073272, -0.00015490809725932037720034762889, -0.00004514948935538730085479280454, 0.00007976881782603940889444573924, -0.00003314566154544740986264993251, -1.88212148790135672249935711657e-06, 0.0000114788756505519986352882940648, -9.2263039911196207101468331210e-06, 5.1401128250377780476084336340e-06, -2.38418218951722002658891397905e-06, 1.00664292214481531598338960828e-06, -4.23224678096490060264249970540e-07, 2.00132031535793489976535190025e-07, -1.18689501178886741400633921047e-07, 8.7819524319114212999768013738e-08, -7.3964150324206644900787216386e-08, 6.5780431507637165113885884236e-08, -5.9651053193022652369837650411e-08, 5.4447762662767276209052293773e-08, -4.9802057381568863702541294988e-08, 4.5571368194694340198117635845e-08, -4.1682117173547642845382848197e-08, 3.8084701352766049815367147717e-08, -3.4740302885185237434662649907e-08, 3.1616557064701510611273692060e-08, -2.8685739487689556252374879267e-08, 2.5923752117132254429002796600e-08, -2.3309428552190587304662883477e-08 }; static cheb_series A4_lt1_cs = { A4_lt1_data, 29, -1, 1, 29 }; static double olver_B0(double z, double abs_zeta) { if(z < 0.98) { const double t = 1.0/sqrt(1.0-z*z); return -5.0/(48.0*abs_zeta*abs_zeta) + t*(-3.0 + 5.0*t*t)/(24.0*sqrt(abs_zeta)); } else if(z < 1.02) { const double a = 1.0-z; const double c0 = 0.0179988721413553309252458658183; const double c1 = 0.0111992982212877614645974276203; const double c2 = 0.0059404069786014304317781160605; const double c3 = 0.0028676724516390040844556450173; const double c4 = 0.0012339189052567271708525111185; const double c5 = 0.0004169250674535178764734660248; const double c6 = 0.0000330173385085949806952777365; const double c7 = -0.0001318076238578203009990106425; const double c8 = -0.0001906870370050847239813945647; return c0 + a*(c1 + a*(c2 + a*(c3 + a*(c4 + a*(c5 + a*(c6 + a*(c7 + a*c8))))))); } else { const double t = 1.0/(z*sqrt(1.0 - 1.0/(z*z))); return -5.0/(48.0*abs_zeta*abs_zeta) + t*(3.0 + 5.0*t*t)/(24.0*sqrt(abs_zeta)); } } static double olver_B1(double z, double abs_zeta) { if(z < 0.88) { const double t = 1.0/sqrt(1.0-z*z); const double t2 = t*t; const double rz = sqrt(abs_zeta); const double z32 = rz*rz*rz; const double z92 = z32*z32*z32; const double term1 = t*t*t * (30375.0 - 369603.0*t2 + 765765.0*t2*t2 - 425425.0*t2*t2*t2)/414720.0; const double term2 = 85085.0/(663552.0*z92); const double term3 = 385.0/110592.*t*(3.0-5.0*t2)/(abs_zeta*abs_zeta*abs_zeta); const double term4 = 5.0/55296.0*t2*(81.0 - 462.0*t2 + 385.0*t2*t2)/z32; return -(term1 + term2 + term3 + term4)/rz; } else if(z < 1.12) { const double a = 1.0-z; const double c0 = -0.00149282953213429172050073403334; const double c1 = -0.00175640941909277865678308358128; const double c2 = -0.00113346148874174912576929663517; const double c3 = -0.00034691090981382974689396961817; const double c4 = 0.00022752516104839243675693256916; const double c5 = 0.00051764145724244846447294636552; const double c6 = 0.00058906174858194233998714243010; const double c7 = 0.00053485514521888073087240392846; const double c8 = 0.00042891792986220150647633418796; const double c9 = 0.00031639765900613633260381972850; const double c10 = 0.00021908147678699592975840749194; return c0+a*(c1+a*(c2+a*(c3+a*(c4+a*(c5+a*(c6+a*(c7+a*(c8+a*(c9+a*c10))))))))); } else { const double t = 1.0/(z*sqrt(1.0 - 1.0/(z*z))); const double t2 = t*t; const double rz = sqrt(abs_zeta); const double z32 = rz*rz*rz; const double z92 = z32*z32*z32; const double term1 = -t2*t * (30375.0 + 369603.0*t2 + 765765.0*t2*t2 + 425425.0*t2*t2*t2)/414720.0; const double term2 = 85085.0/(663552.0*z92); const double term3 = -385.0/110592.0*t*(3.0+5.0*t2)/(abs_zeta*abs_zeta*abs_zeta); const double term4 = 5.0/55296.0*t2*(81.0 + 462.0*t2 + 385.0*t2*t2)/z32; return (term1 + term2 + term3 + term4)/rz; } } static double olver_B2(double z, double abs_zeta) { if(z < 0.8) { const double x = 5.0*z/2.0 - 1.0; gsl_sf_result c; cheb_eval_e(&B2_lt1_cs, x, &c); return c.val / z; } else if(z <= 1.2) { const double a = 1.0-z; const double c0 = 0.00055221307672129279005986982501; const double c1 = 0.00089586516310476929281129228969; const double c2 = 0.00067015003441569770883539158863; const double c3 = 0.00010166263361949045682945811828; const double c4 = -0.00044086345133806887291336488582; const double c5 = -0.00073963081508788743392883072523; const double c6 = -0.00076745494377839561259903887331; const double c7 = -0.00060829038106040362291568012663; const double c8 = -0.00037128707528893496121336168683; const double c9 = -0.00014116325105702609866850307176; return c0+a*(c1+a*(c2+a*(c3+a*(c4+a*(c5+a*(c6+a*(c7+a*(c8+a*c9)))))))); } else { const double zi = 1.0/z; const double x = 12.0/5.0 * zi - 1.0; gsl_sf_result c; cheb_eval_e(&B2_gt1_cs, x, &c); return c.val * zi*zi*zi; } } static double olver_B3(double z, double abs_zeta) { if(z < 0.8) { const double x = 5.0*z/2.0 - 1.0; gsl_sf_result c; cheb_eval_e(&B3_lt1_cs, x, &c); return c.val; } else if(z < 1.2) { const double a = 1.0-z; const double c0 = -0.00047461779655995980754441833105; const double c1 = -0.00095572913429464297452176811898; const double c2 = -0.00080369634512082892655558133973; const double c3 = -0.00000727921669154784138080600339; const double c4 = 0.00093162500331581345235746518994; const double c5 = 0.00149848796913751497227188612403; const double c6 = 0.00148406039675949727870390426462; return c0 + a*(c1 + a*(c2 + a*(c3 + a*(c4 + a*(c5 + a*c6))))); } else { const double x = 12.0/(5.0*z) - 1.0; const double zi2 = 1.0/(z*z); gsl_sf_result c; cheb_eval_e(&B3_gt1_cs, x, &c); return c.val * zi2*zi2*zi2; } } static double olver_A1(double z, double abs_zeta, double * err) { if(z < 0.98) { double t = 1.0/sqrt(1.0-z*z); double rz = sqrt(abs_zeta); double t2 = t*t; double term1 = t2*(81.0 - 462.0*t2 + 385.0*t2*t2)/1152.0; double term2 = -455.0/(4608.0*abs_zeta*abs_zeta*abs_zeta); double term3 = 7.0*t*(-3.0 + 5.0*t2)/(1152.0*rz*rz*rz); *err = 2.0 * GSL_DBL_EPSILON * (fabs(term1) + fabs(term2) + fabs(term3)); return term1 + term2 + term3; } else if(z < 1.02) { const double a = 1.0-z; const double c0 = -0.00444444444444444444444444444444; const double c1 = -0.00184415584415584415584415584416; const double c2 = 0.00056812076812076812076812076812; const double c3 = 0.00168137865661675185484709294233; const double c4 = 0.00186744042139000122193399504324; const double c5 = 0.00161330105833747826430066790326; const double c6 = 0.00123177312220625816558607537838; const double c7 = 0.00087334711007377573881689318421; const double c8 = 0.00059004942455353250141217015410; const double sum = c0+a*(c1+a*(c2+a*(c3+a*(c4+a*(c5+a*(c6+a*(c7+a*c8))))))); *err = 2.0 * GSL_DBL_EPSILON * fabs(sum); return sum; } else { const double t = 1.0/(z*sqrt(1.0 - 1.0/(z*z))); const double rz = sqrt(abs_zeta); const double t2 = t*t; const double term1 = -t2*(81.0 + 462.0*t2 + 385.0*t2*t2)/1152.0; const double term2 = 455.0/(4608.0*abs_zeta*abs_zeta*abs_zeta); const double term3 = -7.0*t*(3.0 + 5.0*t2)/(1152.0*rz*rz*rz); *err = 2.0 * GSL_DBL_EPSILON * (fabs(term1) + fabs(term2) + fabs(term3)); return term1 + term2 + term3; } } static double olver_A2(double z, double abs_zeta) { if(z < 0.88) { double t = 1.0/sqrt(1.0-z*z); double t2 = t*t; double t4 = t2*t2; double t6 = t4*t2; double t8 = t4*t4; double rz = sqrt(abs_zeta); double z3 = abs_zeta*abs_zeta*abs_zeta; double z32 = rz*rz*rz; double z92 = z3*z32; double term1 = t4*(4465125.0 - 94121676.0*t2 + 349922430.0*t4 - 446185740.0*t6 + 185910725.0*t8)/39813120.0; double term2 = -40415375.0/(127401984.0*z3*z3); double term3 = -95095.0/15925248.0*t*(3.0-5.0*t2)/z92; double term4 = -455.0/5308416.0 *t2*(81.0 - 462.0*t2 + 385.0*t4)/z3; double term5 = -7.0/19906560.0*t*t2*(30375.0 - 369603.0*t2 + 765765.0*t4 - 425425.0*t6)/z32; return term1 + term2 + term3 + term4 + term5; } else if(z < 1.12) { double a = 1.0-z; const double c0 = 0.000693735541354588973636592684210; const double c1 = 0.000464483490365843307019777608010; const double c2 = -0.000289036254605598132482570468291; const double c3 = -0.000874764943953712638574497548110; const double c4 = -0.001029716376139865629968584679350; const double c5 = -0.000836857329713810600584714031650; const double c6 = -0.000488910893527218954998270124540; const double c7 = -0.000144236747940817220502256810151; const double c8 = 0.000114363800986163478038576460325; const double c9 = 0.000266806881492777536223944807117; const double c10 = -0.011975517576151069627471048587000; return c0+a*(c1+a*(c2+a*(c3+a*(c4+a*(c5+a*(c6+a*(c7+a*(c8+a*(c9+a*c10))))))))); } else { const double t = 1.0/(z*sqrt(1.0 - 1.0/(z*z))); const double t2 = t*t; const double t4 = t2*t2; const double t6 = t4*t2; const double t8 = t4*t4; const double rz = sqrt(abs_zeta); const double z3 = abs_zeta*abs_zeta*abs_zeta; const double z32 = rz*rz*rz; const double z92 = z3*z32; const double term1 = t4*(4465125.0 + 94121676.0*t2 + 349922430.0*t4 + 446185740.0*t6 + 185910725.0*t8)/39813120.0; const double term2 = -40415375.0/(127401984.0*z3*z3); const double term3 = 95095.0/15925248.0*t*(3.0+5.0*t2)/z92; const double term4 = -455.0/5308416.0 *t2*(81.0 + 462.0*t2 + 385.0*t4)/z3; const double term5 = 7.0/19906560.0*t*t2*(30375.0 + 369603.0*t2 + 765765.0*t4 + 425425.0*t6)/z32; return term1 + term2 + term3 + term4 + term5; } } static double olver_A3(double z, double abs_zeta) { if(z < 0.9) { const double x = 20.0*z/9.0 - 1.0; gsl_sf_result c; cheb_eval_e(&A3_lt1_cs, x, &c); return c.val; } else if(z < 1.1) { double a = 1.0-z; const double c0 = -0.000354211971457743840771125759200; const double c1 = -0.000312322527890318832782774881353; const double c2 = 0.000277947465383133980329617631915; const double c3 = 0.000919803044747966977054155192400; const double c4 = 0.001147600388275977640983696906320; const double c5 = 0.000869239326123625742931772044544; const double c6 = 0.000287392257282507334785281718027; return c0 + a*(c1 + a*(c2 + a*(c3 + a*(c4 + a*(c5 + a*c6))))); } else { const double x = 11.0/(5.0*z) - 1.0; const double zi2 = 1.0/(z*z); gsl_sf_result c; cheb_eval_e(&A3_gt1_cs, x, &c); return c.val * zi2*zi2*zi2; } } static double olver_A4(double z, double abs_zeta) { if(z < 0.8) { const double x = 5.0*z/2.0 - 1.0; gsl_sf_result c; cheb_eval_e(&A4_lt1_cs, x, &c); return c.val; } else if(z < 1.2) { double a = 1.0-z; const double c0 = 0.00037819419920177291402661228437; const double c1 = 0.00040494390552363233477213857527; const double c2 = -0.00045764735528936113047289344569; const double c3 = -0.00165361044229650225813161341879; const double c4 = -0.00217527517983360049717137015539; const double c5 = -0.00152003287866490735107772795537; return c0 + a*(c1 + a*(c2 + a*(c3 + a*(c4 + a*c5)))); } else { const double x = 12.0/(5.0*z) - 1.0; const double zi2 = 1.0/(z*z); gsl_sf_result c; cheb_eval_e(&A4_gt1_cs, x, &c); return c.val * zi2*zi2*zi2*zi2; } } inline static double olver_Asum(double nu, double z, double abs_zeta, double * err) { double nu2 = nu*nu; double A1_err; double A1 = olver_A1(z, abs_zeta, &A1_err); double A2 = olver_A2(z, abs_zeta); double A3 = olver_A3(z, abs_zeta); double A4 = olver_A4(z, abs_zeta); *err = A1_err/nu2 + GSL_DBL_EPSILON; return 1.0 + A1/nu2 + A2/(nu2*nu2) + A3/(nu2*nu2*nu2) + A4/(nu2*nu2*nu2*nu2); } inline static double olver_Bsum(double nu, double z, double abs_zeta) { double nu2 = nu*nu; double B0 = olver_B0(z, abs_zeta); double B1 = olver_B1(z, abs_zeta); double B2 = olver_B2(z, abs_zeta); double B3 = olver_B3(z, abs_zeta); return B0 + B1/nu2 + B2/(nu2*nu2) + B3/(nu2*nu2*nu2*nu2); } /* uniform asymptotic, nu -> Inf, [Abramowitz+Stegun, 9.3.35] * * error: * nu = 2: uniformly good to > 6D * nu = 5: uniformly good to > 8D * nu = 10: uniformly good to > 10D * nu = 20: uniformly good to > 13D * */ int gsl_sf_bessel_Jnu_asymp_Olver_e(double nu, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0 || nu <= 0.0) { DOMAIN_ERROR(result); } else { double zeta, abs_zeta; double arg; double pre; double asum, bsum, asum_err; gsl_sf_result ai; gsl_sf_result aip; double z = x/nu; double crnu = pow(nu, 1.0/3.0); double nu3 = nu*nu*nu; double nu11 = nu3*nu3*nu3*nu*nu; int stat_a, stat_ap; if(fabs(1.0-z) < 0.02) { const double a = 1.0-z; const double c0 = 1.25992104989487316476721060728; const double c1 = 0.37797631496846194943016318218; const double c2 = 0.230385563409348235843147082474; const double c3 = 0.165909603649648694839821892031; const double c4 = 0.12931387086451008907; const double c5 = 0.10568046188858133991; const double c6 = 0.08916997952268186978; const double c7 = 0.07700014900618802456; pre = c0 + a*(c1 + a*(c2 + a*(c3 + a*(c4 + a*(c5 + a*(c6 + a*c7)))))); zeta = a * pre; pre = sqrt(2.0*sqrt(pre/(1.0+z))); abs_zeta = fabs(zeta); } else if(z < 1.0) { double rt = sqrt(1.0 - z*z); abs_zeta = pow(1.5*(log((1.0+rt)/z) - rt), 2.0/3.0); zeta = abs_zeta; pre = sqrt(2.0*sqrt(abs_zeta/(rt*rt))); } else { /* z > 1 */ double rt = z * sqrt(1.0 - 1.0/(z*z)); abs_zeta = pow(1.5*(rt - acos(1.0/z)), 2.0/3.0); zeta = -abs_zeta; pre = sqrt(2.0*sqrt(abs_zeta/(rt*rt))); } asum = olver_Asum(nu, z, abs_zeta, &asum_err); bsum = olver_Bsum(nu, z, abs_zeta); arg = crnu*crnu * zeta; stat_a = gsl_sf_airy_Ai_e(arg, GSL_MODE_DEFAULT, &ai); stat_ap = gsl_sf_airy_Ai_deriv_e(arg, GSL_MODE_DEFAULT, &aip); result->val = pre * (ai.val*asum/crnu + aip.val*bsum/(nu*crnu*crnu)); result->err = pre * (ai.err * fabs(asum/crnu)); result->err += pre * fabs(ai.val) * asum_err / crnu; result->err += pre * fabs(ai.val * asum) / (crnu*nu11); result->err += 8.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_a, stat_ap); } } /* uniform asymptotic, nu -> Inf, [Abramowitz+Stegun, 9.3.36] * * error: * nu = 2: uniformly good to > 6D * nu = 5: uniformly good to > 8D * nu = 10: uniformly good to > 10D * nu = 20: uniformly good to > 13D */ int gsl_sf_bessel_Ynu_asymp_Olver_e(double nu, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0 || nu <= 0.0) { DOMAIN_ERROR(result); } else { double zeta, abs_zeta; double arg; double pre; double asum, bsum, asum_err; gsl_sf_result bi; gsl_sf_result bip; double z = x/nu; double crnu = pow(nu, 1.0/3.0); double nu3 = nu*nu*nu; double nu11 = nu3*nu3*nu3*nu*nu; int stat_b, stat_d; if(fabs(1.0-z) < 0.02) { const double a = 1.0-z; const double c0 = 1.25992104989487316476721060728; const double c1 = 0.37797631496846194943016318218; const double c2 = 0.230385563409348235843147082474; const double c3 = 0.165909603649648694839821892031; const double c4 = 0.12931387086451008907; const double c5 = 0.10568046188858133991; const double c6 = 0.08916997952268186978; const double c7 = 0.07700014900618802456; pre = c0 + a*(c1 + a*(c2 + a*(c3 + a*(c4 + a*(c5 + a*(c6 + a*c7)))))); zeta = a * pre; pre = sqrt(2.0*sqrt(pre/(1.0+z))); abs_zeta = fabs(zeta); } else if(z < 1.0) { double rt = sqrt(1.0 - z*z); abs_zeta = pow(1.5*(log((1.0+rt)/z) - rt), 2.0/3.0); zeta = abs_zeta; pre = sqrt(2.0*sqrt(abs_zeta/(rt*rt))); } else { /* z > 1 */ double rt = z * sqrt(1.0 - 1.0/(z*z)); double ac = acos(1.0/z); abs_zeta = pow(1.5*(rt - ac), 2.0/3.0); zeta = -abs_zeta; pre = sqrt(2.0*sqrt(abs_zeta)/rt); } asum = olver_Asum(nu, z, abs_zeta, &asum_err); bsum = olver_Bsum(nu, z, abs_zeta); arg = crnu*crnu * zeta; stat_b = gsl_sf_airy_Bi_e(arg, GSL_MODE_DEFAULT, &bi); stat_d = gsl_sf_airy_Bi_deriv_e(arg, GSL_MODE_DEFAULT, &bip); result->val = -pre * (bi.val*asum/crnu + bip.val*bsum/(nu*crnu*crnu)); result->err = pre * (bi.err * fabs(asum/crnu)); result->err += pre * fabs(bi.val) * asum_err / crnu; result->err += pre * fabs(bi.val*asum) / (crnu*nu11); result->err += 8.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_b, stat_d); } } sources_5316/external/gsl/gsl_cblas__xerbla.c0000664000176700017670000000230211723710247020126 0ustar paulpaul/* xerbla.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_xerbla (int p, const char *rout, const char *form, ...) { va_list ap; va_start (ap, form); if (p) { fprintf (stderr, "Parameter %d to routine %s was incorrect\n", p, rout); } vfprintf (stderr, form, ap); va_end (ap); abort (); } sources_5316/external/gsl/gsl_min.h0000664000176700017670000000756011705263724016154 0ustar paulpaul/* min/gsl_min.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MIN_H__ #define __GSL_MIN_H__ #include #include "gsl_types.h" #include "gsl_math.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { const char *name; size_t size; int (*set) (void *state, gsl_function * f, double x_minimum, double f_minimum, double x_lower, double f_lower, double x_upper, double f_upper); int (*iterate) (void *state, gsl_function * f, double * x_minimum, double * f_minimum, double * x_lower, double * f_lower, double * x_upper, double * f_upper); } gsl_min_fminimizer_type; typedef struct { const gsl_min_fminimizer_type * type; gsl_function * function ; double x_minimum ; double x_lower ; double x_upper ; double f_minimum, f_lower, f_upper; void *state; } gsl_min_fminimizer; gsl_min_fminimizer * gsl_min_fminimizer_alloc (const gsl_min_fminimizer_type * T) ; void gsl_min_fminimizer_free (gsl_min_fminimizer * s); int gsl_min_fminimizer_set (gsl_min_fminimizer * s, gsl_function * f, double x_minimum, double x_lower, double x_upper); int gsl_min_fminimizer_set_with_values (gsl_min_fminimizer * s, gsl_function * f, double x_minimum, double f_minimum, double x_lower, double f_lower, double x_upper, double f_upper); int gsl_min_fminimizer_iterate (gsl_min_fminimizer * s); const char * gsl_min_fminimizer_name (const gsl_min_fminimizer * s); double gsl_min_fminimizer_x_minimum (const gsl_min_fminimizer * s); double gsl_min_fminimizer_x_lower (const gsl_min_fminimizer * s); double gsl_min_fminimizer_x_upper (const gsl_min_fminimizer * s); double gsl_min_fminimizer_f_minimum (const gsl_min_fminimizer * s); double gsl_min_fminimizer_f_lower (const gsl_min_fminimizer * s); double gsl_min_fminimizer_f_upper (const gsl_min_fminimizer * s); /* Deprecated, use x_minimum instead */ double gsl_min_fminimizer_minimum (const gsl_min_fminimizer * s); int gsl_min_test_interval (double x_lower, double x_upper, double epsabs, double epsrel); GSL_VAR const gsl_min_fminimizer_type * gsl_min_fminimizer_goldensection; GSL_VAR const gsl_min_fminimizer_type * gsl_min_fminimizer_brent; typedef int (*gsl_min_bracketing_function)(gsl_function *f, double *x_minimum,double * f_minimum, double *x_lower, double * f_lower, double *x_upper, double * f_upper, size_t eval_max); int gsl_min_find_bracket(gsl_function *f,double *x_minimum,double * f_minimum, double *x_lower, double * f_lower, double *x_upper, double * f_upper, size_t eval_max); __END_DECLS #endif /* __GSL_MIN_H__ */ sources_5316/external/gsl/gsl_sort_vector_ulong.h0000664000176700017670000000344411705263724021143 0ustar paulpaul/* sort/gsl_sort_vector_ulong.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_ULONG_H__ #define __GSL_SORT_VECTOR_ULONG_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_ulong.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_ulong (gsl_vector_ulong * v); int gsl_sort_vector_ulong_index (gsl_permutation * p, const gsl_vector_ulong * v); int gsl_sort_vector_ulong_smallest (unsigned long * dest, const size_t k, const gsl_vector_ulong * v); int gsl_sort_vector_ulong_largest (unsigned long * dest, const size_t k, const gsl_vector_ulong * v); int gsl_sort_vector_ulong_smallest_index (size_t * p, const size_t k, const gsl_vector_ulong * v); int gsl_sort_vector_ulong_largest_index (size_t * p, const size_t k, const gsl_vector_ulong * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_ULONG_H__ */ sources_5316/external/gsl/gsl_linalg__multiply.c0000664000176700017670000001000111723710247020705 0ustar paulpaul/* linalg/multiply.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_linalg.h" #define SWAP_SIZE_T(a, b) do { size_t swap_tmp = a; a = b; b = swap_tmp; } while(0) int gsl_linalg_matmult (const gsl_matrix * A, const gsl_matrix * B, gsl_matrix * C) { if (A->size2 != B->size1 || A->size1 != C->size1 || B->size2 != C->size2) { GSL_ERROR ("matrix sizes are not conformant", GSL_EBADLEN); } else { double a, b; double temp; size_t i, j, k; for (i = 0; i < C->size1; i++) { for (j = 0; j < C->size2; j++) { a = gsl_matrix_get (A, i, 0); b = gsl_matrix_get (B, 0, j); temp = a * b; for (k = 1; k < A->size2; k++) { a = gsl_matrix_get (A, i, k); b = gsl_matrix_get (B, k, j); temp += a * b; } gsl_matrix_set (C, i, j, temp); } } return GSL_SUCCESS; } } int gsl_linalg_matmult_mod (const gsl_matrix * A, gsl_linalg_matrix_mod_t modA, const gsl_matrix * B, gsl_linalg_matrix_mod_t modB, gsl_matrix * C) { if (modA == GSL_LINALG_MOD_NONE && modB == GSL_LINALG_MOD_NONE) { return gsl_linalg_matmult (A, B, C); } else { size_t dim1_A = A->size1; size_t dim2_A = A->size2; size_t dim1_B = B->size1; size_t dim2_B = B->size2; size_t dim1_C = C->size1; size_t dim2_C = C->size2; if (modA & GSL_LINALG_MOD_TRANSPOSE) SWAP_SIZE_T (dim1_A, dim2_A); if (modB & GSL_LINALG_MOD_TRANSPOSE) SWAP_SIZE_T (dim1_B, dim2_B); if (dim2_A != dim1_B || dim1_A != dim1_C || dim2_B != dim2_C) { GSL_ERROR ("matrix sizes are not conformant", GSL_EBADLEN); } else { double a, b; double temp; size_t i, j, k; size_t a1, a2, b1, b2; for (i = 0; i < dim1_C; i++) { for (j = 0; j < dim2_C; j++) { a1 = i; a2 = 0; b1 = 0; b2 = j; if (modA & GSL_LINALG_MOD_TRANSPOSE) SWAP_SIZE_T (a1, a2); if (modB & GSL_LINALG_MOD_TRANSPOSE) SWAP_SIZE_T (b1, b2); a = gsl_matrix_get (A, a1, a2); b = gsl_matrix_get (B, b1, b2); temp = a * b; for (k = 1; k < dim2_A; k++) { a1 = i; a2 = k; b1 = k; b2 = j; if (modA & GSL_LINALG_MOD_TRANSPOSE) SWAP_SIZE_T (a1, a2); if (modB & GSL_LINALG_MOD_TRANSPOSE) SWAP_SIZE_T (b1, b2); a = gsl_matrix_get (A, a1, a2); b = gsl_matrix_get (B, b1, b2); temp += a * b; } gsl_matrix_set (C, i, j, temp); } } return GSL_SUCCESS; } } } sources_5316/external/gsl/gsl_specfunc__sinint.c0000664000176700017670000002566411723710247020717 0ustar paulpaul/* specfunc/sinint.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_expint.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC r9sifg.f, W. Fullerton */ /* series for f1 on the interval 2.00000e-02 to 6.25000e-02 with weighted error 2.82e-17 log weighted error 16.55 significant figures required 15.36 decimal places required 17.20 */ static double f1_data[20] = { -0.1191081969051363610, -0.0247823144996236248, 0.0011910281453357821, -0.0000927027714388562, 0.0000093373141568271, -0.0000011058287820557, 0.0000001464772071460, -0.0000000210694496288, 0.0000000032293492367, -0.0000000005206529618, 0.0000000000874878885, -0.0000000000152176187, 0.0000000000027257192, -0.0000000000005007053, 0.0000000000000940241, -0.0000000000000180014, 0.0000000000000035063, -0.0000000000000006935, 0.0000000000000001391, -0.0000000000000000282 }; static cheb_series f1_cs = { f1_data, 19, -1, 1, 10 }; /* series for f2 on the interval 0.00000e+00 to 2.00000e-02 with weighted error 4.32e-17 log weighted error 16.36 significant figures required 14.75 decimal places required 17.10 */ static double f2_data[29] = { -0.0348409253897013234, -0.0166842205677959686, 0.0006752901241237738, -0.0000535066622544701, 0.0000062693421779007, -0.0000009526638801991, 0.0000001745629224251, -0.0000000368795403065, 0.0000000087202677705, -0.0000000022601970392, 0.0000000006324624977, -0.0000000001888911889, 0.0000000000596774674, -0.0000000000198044313, 0.0000000000068641396, -0.0000000000024731020, 0.0000000000009226360, -0.0000000000003552364, 0.0000000000001407606, -0.0000000000000572623, 0.0000000000000238654, -0.0000000000000101714, 0.0000000000000044259, -0.0000000000000019634, 0.0000000000000008868, -0.0000000000000004074, 0.0000000000000001901, -0.0000000000000000900, 0.0000000000000000432 }; static cheb_series f2_cs = { f2_data, 28, -1, 1, 14 }; /* series for g1 on the interval 2.00000e-02 to 6.25000e-02 with weighted error 5.48e-17 log weighted error 16.26 significant figures required 15.47 decimal places required 16.92 */ static double g1_data[21] = { -0.3040578798253495954, -0.0566890984597120588, 0.0039046158173275644, -0.0003746075959202261, 0.0000435431556559844, -0.0000057417294453025, 0.0000008282552104503, -0.0000001278245892595, 0.0000000207978352949, -0.0000000035313205922, 0.0000000006210824236, -0.0000000001125215474, 0.0000000000209088918, -0.0000000000039715832, 0.0000000000007690431, -0.0000000000001514697, 0.0000000000000302892, -0.0000000000000061400, 0.0000000000000012601, -0.0000000000000002615, 0.0000000000000000548 }; static cheb_series g1_cs = { g1_data, 20, -1, 1, 13 }; /* series for g2 on the interval 0.00000e+00 to 2.00000e-02 with weighted error 5.01e-17 log weighted error 16.30 significant figures required 15.12 decimal places required 17.07 */ static double g2_data[34] = { -0.0967329367532432218, -0.0452077907957459871, 0.0028190005352706523, -0.0002899167740759160, 0.0000407444664601121, -0.0000071056382192354, 0.0000014534723163019, -0.0000003364116512503, 0.0000000859774367886, -0.0000000238437656302, 0.0000000070831906340, -0.0000000022318068154, 0.0000000007401087359, -0.0000000002567171162, 0.0000000000926707021, -0.0000000000346693311, 0.0000000000133950573, -0.0000000000053290754, 0.0000000000021775312, -0.0000000000009118621, 0.0000000000003905864, -0.0000000000001708459, 0.0000000000000762015, -0.0000000000000346151, 0.0000000000000159996, -0.0000000000000075213, 0.0000000000000035970, -0.0000000000000017530, 0.0000000000000008738, -0.0000000000000004487, 0.0000000000000002397, -0.0000000000000001347, 0.0000000000000000801, -0.0000000000000000501 }; static cheb_series g2_cs = { g2_data, 33, -1, 1, 20 }; /* x >= 4.0 */ static void fg_asymp(const double x, gsl_sf_result * f, gsl_sf_result * g) { /* xbig = sqrt (1.0/r1mach(3)) xmaxf = exp (amin1(-alog(r1mach(1)), alog(r1mach(2))) - 0.01) xmaxg = 1.0/sqrt(r1mach(1)) xbnd = sqrt(50.0) */ const double xbig = 1.0/GSL_SQRT_DBL_EPSILON; const double xmaxf = 1.0/GSL_DBL_MIN; const double xmaxg = 1.0/GSL_SQRT_DBL_MIN; const double xbnd = 7.07106781187; const double x2 = x*x; if(x <= xbnd) { gsl_sf_result result_c1; gsl_sf_result result_c2; cheb_eval_e(&f1_cs, (1.0/x2-0.04125)/0.02125, &result_c1); cheb_eval_e(&g1_cs, (1.0/x2-0.04125)/0.02125, &result_c2); f->val = (1.0 + result_c1.val)/x; g->val = (1.0 + result_c2.val)/x2; f->err = result_c1.err/x + 2.0 * GSL_DBL_EPSILON * fabs(f->val); g->err = result_c2.err/x2 + 2.0 * GSL_DBL_EPSILON * fabs(g->val); } else if(x <= xbig) { gsl_sf_result result_c1; gsl_sf_result result_c2; cheb_eval_e(&f2_cs, 100.0/x2-1.0, &result_c1); cheb_eval_e(&g2_cs, 100.0/x2-1.0, &result_c2); f->val = (1.0 + result_c1.val)/x; g->val = (1.0 + result_c2.val)/x2; f->err = result_c1.err/x + 2.0 * GSL_DBL_EPSILON * fabs(f->val); g->err = result_c2.err/x2 + 2.0 * GSL_DBL_EPSILON * fabs(g->val); } else { f->val = (x < xmaxf ? 1.0/x : 0.0); g->val = (x < xmaxg ? 1.0/x2 : 0.0); f->err = 2.0 * GSL_DBL_EPSILON * fabs(f->val); g->err = 2.0 * GSL_DBL_EPSILON * fabs(g->val); } return; } /* based on SLATEC si.f, W. Fullerton series for si on the interval 0.00000e+00 to 1.60000e+01 with weighted error 1.22e-17 log weighted error 16.91 significant figures required 16.37 decimal places required 17.45 */ static double si_data[12] = { -0.1315646598184841929, -0.2776578526973601892, 0.0354414054866659180, -0.0025631631447933978, 0.0001162365390497009, -0.0000035904327241606, 0.0000000802342123706, -0.0000000013562997693, 0.0000000000179440722, -0.0000000000001908387, 0.0000000000000016670, -0.0000000000000000122 }; static cheb_series si_cs = { si_data, 11, -1, 1, 9 }; /* series for ci on the interval 0.00000e+00 to 1.60000e+01 with weighted error 1.94e-18 log weighted error 17.71 significant figures required 17.74 decimal places required 18.27 */ static double ci_data[13] = { -0.34004281856055363156, -1.03302166401177456807, 0.19388222659917082877, -0.01918260436019865894, 0.00110789252584784967, -0.00004157234558247209, 0.00000109278524300229, -0.00000002123285954183, 0.00000000031733482164, -0.00000000000376141548, 0.00000000000003622653, -0.00000000000000028912, 0.00000000000000000194 }; static cheb_series ci_cs = { ci_data, 12, -1, 1, 9 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_Si_e(const double x, gsl_sf_result * result) { double ax = fabs(x); /* CHECK_POINTER(result) */ if(ax < GSL_SQRT_DBL_EPSILON) { result->val = x; result->err = 0.0; return GSL_SUCCESS; } else if(ax <= 4.0) { gsl_sf_result result_c; cheb_eval_e(&si_cs, (x*x-8.0)*0.125, &result_c); result->val = x * (0.75 + result_c.val); result->err = ax * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* Note there is no loss of precision * here bcause of the leading constant. */ gsl_sf_result f; gsl_sf_result g; fg_asymp(ax, &f, &g); result->val = 0.5 * M_PI - f.val*cos(ax) - g.val*sin(ax); result->err = f.err + g.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(x < 0.0) result->val = -result->val; return GSL_SUCCESS; } } int gsl_sf_Ci_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x <= 4.0) { const double lx = log(x); const double y = (x*x-8.0)*0.125; gsl_sf_result result_c; cheb_eval_e(&ci_cs, y, &result_c); result->val = lx - 0.5 + result_c.val; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(lx) + 0.5) + result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result sin_result; gsl_sf_result cos_result; int stat_sin = gsl_sf_sin_e(x, &sin_result); int stat_cos = gsl_sf_cos_e(x, &cos_result); gsl_sf_result f; gsl_sf_result g; fg_asymp(x, &f, &g); result->val = f.val*sin_result.val - g.val*cos_result.val; result->err = fabs(f.err*sin_result.val); result->err += fabs(g.err*cos_result.val); result->err += fabs(f.val*sin_result.err); result->err += fabs(g.val*cos_result.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_sin, stat_cos); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_Si(const double x) { EVAL_RESULT(gsl_sf_Si_e(x, &result)); } double gsl_sf_Ci(const double x) { EVAL_RESULT(gsl_sf_Ci_e(x, &result)); } sources_5316/external/gsl/gsl_eigen__herm.c0000664000176700017670000001120611723710247017612 0ustar paulpaul/* eigen/herm.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_linalg.h" #include "gsl_eigen.h" /* Compute eigenvalues of complex hermitian matrix using reduction to real symmetric tridiagonal form, followed by QR iteration with implicit shifts. See Golub & Van Loan, "Matrix Computations" (3rd ed), Section 8.3 */ #include "gsl_eigen__qrstep.c" gsl_eigen_herm_workspace * gsl_eigen_herm_alloc (const size_t n) { gsl_eigen_herm_workspace * w ; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = (gsl_eigen_herm_workspace *) malloc (sizeof(gsl_eigen_herm_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->d = (double *) malloc (n * sizeof (double)); if (w->d == 0) { GSL_ERROR_NULL ("failed to allocate space for diagonal", GSL_ENOMEM); } w->sd = (double *) malloc (n * sizeof (double)); if (w->sd == 0) { GSL_ERROR_NULL ("failed to allocate space for subdiagonal", GSL_ENOMEM); } w->tau = (double *) malloc (2 * n * sizeof (double)); if (w->tau == 0) { GSL_ERROR_NULL ("failed to allocate space for tau", GSL_ENOMEM); } w->size = n; return w; } void gsl_eigen_herm_free (gsl_eigen_herm_workspace * w) { free (w->tau); free (w->sd); free (w->d); free(w); } int gsl_eigen_herm (gsl_matrix_complex * A, gsl_vector * eval, gsl_eigen_herm_workspace * w) { if (A->size1 != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if (eval->size != A->size1) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else { const size_t N = A->size1; double *const d = w->d; double *const sd = w->sd; size_t a, b; /* handle special case */ if (N == 1) { gsl_complex A00 = gsl_matrix_complex_get (A, 0, 0); gsl_vector_set (eval, 0, GSL_REAL(A00)); return GSL_SUCCESS; } { gsl_vector_view d_vec = gsl_vector_view_array (d, N); gsl_vector_view sd_vec = gsl_vector_view_array (sd, N - 1); gsl_vector_complex_view tau_vec = gsl_vector_complex_view_array (w->tau, N-1); gsl_linalg_hermtd_decomp (A, &tau_vec.vector); gsl_linalg_hermtd_unpack_T (A, &d_vec.vector, &sd_vec.vector); } /* Make an initial pass through the tridiagonal decomposition to remove off-diagonal elements which are effectively zero */ chop_small_elements (N, d, sd); /* Progressively reduce the matrix until it is diagonal */ b = N - 1; while (b > 0) { if (sd[b - 1] == 0.0 || isnan(sd[b - 1])) { b--; continue; } /* Find the largest unreduced block (a,b) starting from b and working backwards */ a = b - 1; while (a > 0) { if (sd[a - 1] == 0.0) { break; } a--; } { const size_t n_block = b - a + 1; double *d_block = d + a; double *sd_block = sd + a; /* apply QR reduction with implicit deflation to the unreduced block */ qrstep (n_block, d_block, sd_block, NULL, NULL); /* remove any small off-diagonal elements */ chop_small_elements (n_block, d_block, sd_block); } } { gsl_vector_view d_vec = gsl_vector_view_array (d, N); gsl_vector_memcpy (eval, &d_vec.vector); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_vector__copy.c0000664000176700017670000000362611723710247020053 0ustar paulpaul#include "gsl__config.h" #include "gsl_vector.h" #include "gsl_errno.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__copy_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_rng__ranf.c0000664000176700017670000001020111723710247017276 0ustar paulpaul/* rng/ranf.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_rng.h" /* This is the CRAY RANF generator. The generator returns the upper 32 bits from each term of the sequence, x_{n+1} = (a x_n) mod m using 48-bit unsigned arithmetic, with a = 0x2875A2E7B175 and m = 2^48. The seed specifies the lower 32 bits of the initial value, x_1, with the lowest bit set (to prevent the seed taking an even value), and the upper 16 bits set to 0. There is a subtlety in the implementation of the seed. The initial state is put one step back by multiplying by the modular inverse of a mod m. This is done for compatibility with the original CRAY implementation. Note, you can only seed the generator with integers up to 2^32, while the CRAY uses wide integers which can cover all 2^48 states of the generator. The theoretical value of x_{10001} is 141091827447341. The period of this generator is 2^{46}. */ static inline void ranf_advance (void *vstate); static unsigned long int ranf_get (void *vstate); static double ranf_get_double (void *vstate); static void ranf_set (void *state, unsigned long int s); static const unsigned short int a0 = 0xB175 ; static const unsigned short int a1 = 0xA2E7 ; static const unsigned short int a2 = 0x2875 ; typedef struct { unsigned short int x0, x1, x2; } ranf_state_t; static inline void ranf_advance (void *vstate) { ranf_state_t *state = (ranf_state_t *) vstate; const unsigned long int x0 = (unsigned long int) state->x0 ; const unsigned long int x1 = (unsigned long int) state->x1 ; const unsigned long int x2 = (unsigned long int) state->x2 ; unsigned long int r ; r = a0 * x0 ; state->x0 = (r & 0xFFFF) ; r >>= 16 ; r += a0 * x1 + a1 * x0 ; state->x1 = (r & 0xFFFF) ; r >>= 16 ; r += a0 * x2 + a1 * x1 + a2 * x0 ; state->x2 = (r & 0xFFFF) ; } static unsigned long int ranf_get (void *vstate) { unsigned long int x1, x2; ranf_state_t *state = (ranf_state_t *) vstate; ranf_advance (state) ; x1 = (unsigned long int) state->x1; x2 = (unsigned long int) state->x2; return (x2 << 16) + x1; } static double ranf_get_double (void * vstate) { ranf_state_t *state = (ranf_state_t *) vstate; ranf_advance (state) ; return (ldexp((double) state->x2, -16) + ldexp((double) state->x1, -32) + ldexp((double) state->x0, -48)) ; } static void ranf_set (void *vstate, unsigned long int s) { ranf_state_t *state = (ranf_state_t *) vstate; unsigned short int x0, x1, x2 ; unsigned long int r ; unsigned long int b0 = 0xD6DD ; unsigned long int b1 = 0xB894 ; unsigned long int b2 = 0x5CEE ; if (s == 0) /* default seed */ { x0 = 0x9CD1 ; x1 = 0x53FC ; x2 = 0x9482 ; } else { x0 = (s | 1) & 0xFFFF ; x1 = s >> 16 & 0xFFFF ; x2 = 0 ; } r = b0 * x0 ; state->x0 = (r & 0xFFFF) ; r >>= 16 ; r += b0 * x1 + b1 * x0 ; state->x1 = (r & 0xFFFF) ; r >>= 16 ; r += b0 * x2 + b1 * x1 + b2 * x0 ; state->x2 = (r & 0xFFFF) ; return; } static const gsl_rng_type ranf_type = {"ranf", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ranf_state_t), &ranf_set, &ranf_get, &ranf_get_double }; const gsl_rng_type *gsl_rng_ranf = &ranf_type; sources_5316/external/gsl/gsl_integration.h0000664000176700017670000002146511705263724017714 0ustar paulpaul/* integration/gsl_integration.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_INTEGRATION_H__ #define __GSL_INTEGRATION_H__ #include #include "gsl_math.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Workspace for adaptive integrators */ typedef struct { size_t limit; size_t size; size_t nrmax; size_t i; size_t maximum_level; double *alist; double *blist; double *rlist; double *elist; size_t *order; size_t *level; } gsl_integration_workspace; gsl_integration_workspace * gsl_integration_workspace_alloc (const size_t n); void gsl_integration_workspace_free (gsl_integration_workspace * w); /* Workspace for QAWS integrator */ typedef struct { double alpha; double beta; int mu; int nu; double ri[25]; double rj[25]; double rg[25]; double rh[25]; } gsl_integration_qaws_table; gsl_integration_qaws_table * gsl_integration_qaws_table_alloc (double alpha, double beta, int mu, int nu); int gsl_integration_qaws_table_set (gsl_integration_qaws_table * t, double alpha, double beta, int mu, int nu); void gsl_integration_qaws_table_free (gsl_integration_qaws_table * t); /* Workspace for QAWO integrator */ enum gsl_integration_qawo_enum { GSL_INTEG_COSINE, GSL_INTEG_SINE }; typedef struct { size_t n; double omega; double L; double par; enum gsl_integration_qawo_enum sine; double *chebmo; } gsl_integration_qawo_table; gsl_integration_qawo_table * gsl_integration_qawo_table_alloc (double omega, double L, enum gsl_integration_qawo_enum sine, size_t n); int gsl_integration_qawo_table_set (gsl_integration_qawo_table * t, double omega, double L, enum gsl_integration_qawo_enum sine); int gsl_integration_qawo_table_set_length (gsl_integration_qawo_table * t, double L); void gsl_integration_qawo_table_free (gsl_integration_qawo_table * t); /* Definition of an integration rule */ typedef void gsl_integration_rule (const gsl_function * f, double a, double b, double *result, double *abserr, double *defabs, double *resabs); void gsl_integration_qk15 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc); void gsl_integration_qk21 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc); void gsl_integration_qk31 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc); void gsl_integration_qk41 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc); void gsl_integration_qk51 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc); void gsl_integration_qk61 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc); void gsl_integration_qcheb (gsl_function * f, double a, double b, double *cheb12, double *cheb24); /* The low-level integration rules in QUADPACK are identified by small integers (1-6). We'll use symbolic constants to refer to them. */ enum { GSL_INTEG_GAUSS15 = 1, /* 15 point Gauss-Kronrod rule */ GSL_INTEG_GAUSS21 = 2, /* 21 point Gauss-Kronrod rule */ GSL_INTEG_GAUSS31 = 3, /* 31 point Gauss-Kronrod rule */ GSL_INTEG_GAUSS41 = 4, /* 41 point Gauss-Kronrod rule */ GSL_INTEG_GAUSS51 = 5, /* 51 point Gauss-Kronrod rule */ GSL_INTEG_GAUSS61 = 6 /* 61 point Gauss-Kronrod rule */ }; void gsl_integration_qk (const int n, const double xgk[], const double wg[], const double wgk[], double fv1[], double fv2[], const gsl_function *f, double a, double b, double * result, double * abserr, double * resabs, double * resasc); int gsl_integration_qng (const gsl_function * f, double a, double b, double epsabs, double epsrel, double *result, double *abserr, size_t * neval); int gsl_integration_qag (const gsl_function * f, double a, double b, double epsabs, double epsrel, size_t limit, int key, gsl_integration_workspace * workspace, double *result, double *abserr); int gsl_integration_qagi (gsl_function * f, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr); int gsl_integration_qagiu (gsl_function * f, double a, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr); int gsl_integration_qagil (gsl_function * f, double b, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr); int gsl_integration_qags (const gsl_function * f, double a, double b, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr); int gsl_integration_qagp (const gsl_function * f, double *pts, size_t npts, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr); int gsl_integration_qawc (gsl_function *f, const double a, const double b, const double c, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double * result, double * abserr); int gsl_integration_qaws (gsl_function * f, const double a, const double b, gsl_integration_qaws_table * t, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr); int gsl_integration_qawo (gsl_function * f, const double a, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, gsl_integration_qawo_table * wf, double *result, double *abserr); int gsl_integration_qawf (gsl_function * f, const double a, const double epsabs, const size_t limit, gsl_integration_workspace * workspace, gsl_integration_workspace * cycle_workspace, gsl_integration_qawo_table * wf, double *result, double *abserr); __END_DECLS #endif /* __GSL_INTEGRATION_H__ */ sources_5316/external/gsl/gsl_cdf__beta_inc.c0000664000176700017670000001104611723710247020072 0ustar paulpaul/* specfunc/beta_inc.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Modified for cdfs by Brian Gough, June 2003 */ static double beta_cont_frac (const double a, const double b, const double x, const double epsabs) { const unsigned int max_iter = 512; /* control iterations */ const double cutoff = 2.0 * GSL_DBL_MIN; /* control the zero cutoff */ unsigned int iter_count = 0; double cf; /* standard initialization for continued fraction */ double num_term = 1.0; double den_term = 1.0 - (a + b) * x / (a + 1.0); if (fabs (den_term) < cutoff) den_term = GSL_NAN; den_term = 1.0 / den_term; cf = den_term; while (iter_count < max_iter) { const int k = iter_count + 1; double coeff = k * (b - k) * x / (((a - 1.0) + 2 * k) * (a + 2 * k)); double delta_frac; /* first step */ den_term = 1.0 + coeff * den_term; num_term = 1.0 + coeff / num_term; if (fabs (den_term) < cutoff) den_term = GSL_NAN; if (fabs (num_term) < cutoff) num_term = GSL_NAN; den_term = 1.0 / den_term; delta_frac = den_term * num_term; cf *= delta_frac; coeff = -(a + k) * (a + b + k) * x / ((a + 2 * k) * (a + 2 * k + 1.0)); /* second step */ den_term = 1.0 + coeff * den_term; num_term = 1.0 + coeff / num_term; if (fabs (den_term) < cutoff) den_term = GSL_NAN; if (fabs (num_term) < cutoff) num_term = GSL_NAN; den_term = 1.0 / den_term; delta_frac = den_term * num_term; cf *= delta_frac; if (fabs (delta_frac - 1.0) < 2.0 * GSL_DBL_EPSILON) break; if (cf * fabs (delta_frac - 1.0) < epsabs) break; ++iter_count; } if (iter_count >= max_iter) return GSL_NAN; return cf; } /* The function beta_inc_AXPY(A,Y,a,b,x) computes A * beta_inc(a,b,x) + Y taking account of possible cancellations when using the hypergeometric transformation beta_inc(a,b,x)=1-beta_inc(b,a,1-x). It also adjusts the accuracy of beta_inc() to fit the overall absolute error when A*beta_inc is added to Y. (e.g. if Y >> A*beta_inc then the accuracy of beta_inc can be reduced) */ static double beta_inc_AXPY (const double A, const double Y, const double a, const double b, const double x) { if (x == 0.0) { return A * 0 + Y; } else if (x == 1.0) { return A * 1 + Y; } else { double ln_beta = gsl_sf_lnbeta (a, b); double ln_pre = -ln_beta + a * log (x) + b * log1p (-x); double prefactor = exp (ln_pre); if (x < (a + 1.0) / (a + b + 2.0)) { /* Apply continued fraction directly. */ double epsabs = fabs (Y / (A * prefactor / a)) * GSL_DBL_EPSILON; double cf = beta_cont_frac (a, b, x, epsabs); return A * (prefactor * cf / a) + Y; } else { /* Apply continued fraction after hypergeometric transformation. */ double epsabs = fabs ((A + Y) / (A * prefactor / b)) * GSL_DBL_EPSILON; double cf = beta_cont_frac (b, a, 1.0 - x, epsabs); double term = prefactor * cf / b; if (A == -Y) { return -A * term; } else { return A * (1 - term) + Y; } } } } /* Direct series evaluation for testing purposes only */ #if 0 static double beta_series (const double a, const double b, const double x, const double epsabs) { double f = x / (1 - x); double c = (b - 1) / (a + 1) * f; double s = 1; double n = 0; s += c; do { n++; c *= -f * (2 + n - b) / (2 + n + a); s += c; } while (n < 512 && fabs (c) > GSL_DBL_EPSILON * fabs (s) + epsabs); s /= (1 - x); return s; } #endif sources_5316/external/gsl/gsl_mode.h0000664000176700017670000000451711705263724016314 0ustar paulpaul/* gsl_mode.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: B. Gough and G. Jungman */ #ifndef __GSL_MODE_H__ #define __GSL_MODE_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Some functions can take a mode argument. This * is a rough method to do things like control * the precision of the algorithm. This mainly * occurs in special functions, but we figured * it was ok to have a general facility. * * The mode type is 32-bit field. Most of * the fields are currently unused. Users * '|' various predefined constants to get * a desired mode. */ typedef unsigned int gsl_mode_t; /* Here are the predefined constants. * Note that the precision constants * are special because they are used * to index arrays, so do not change * them. The precision information is * in the low order 3 bits of gsl_mode_t * (the third bit is currently unused). */ /* Note that "0" is double precision, * so that you get that by default if * you forget a flag. */ #define GSL_PREC_DOUBLE 0 #define GSL_PREC_SINGLE 1 #define GSL_PREC_APPROX 2 #ifdef HAVE_INLINE extern inline unsigned int GSL_MODE_PREC(gsl_mode_t mt); extern inline unsigned int GSL_MODE_PREC(gsl_mode_t mt) { return (mt & (unsigned int)7); } #else /* HAVE_INLINE */ #define GSL_MODE_PREC(mt) ((mt) & (unsigned int)7) #endif /* HAVE_INLINE */ /* Here are some predefined generic modes. */ #define GSL_MODE_DEFAULT 0 __END_DECLS #endif /* __GSL_MODE_H__ */ sources_5316/external/gsl/GSL_LISTOFFILES0000664000176700017670000000272707701244177016570 0ustar paulpaulcomplex/gsl_complex.h config.h err/error.c err/gsl_errno.h err/gsl_message.h err/stream.c gsl_machine.h gsl_math.h gsl_mode.h gsl_nan.h gsl_pow_int.h gsl_precision.h gsl_types.h poly/gsl_poly.h poly/zsolve.c specfunc/airy.c specfunc/bessel.c specfunc/bessel.h specfunc/bessel_I0.c specfunc/bessel_I1.c specfunc/bessel_In.c specfunc/bessel_Inu.c specfunc/bessel_J0.c specfunc/bessel_J1.c specfunc/bessel_Jn.c specfunc/bessel_Jnu.c specfunc/bessel_K0.c specfunc/bessel_K1.c specfunc/bessel_Kn.c specfunc/bessel_Knu.c specfunc/bessel_Y0.c specfunc/bessel_Y1.c specfunc/bessel_Yn.c specfunc/bessel_Ynu.c specfunc/bessel_amp_phase.c specfunc/bessel_amp_phase.h specfunc/bessel_i.c specfunc/bessel_j.c specfunc/bessel_k.c specfunc/bessel_olver.h specfunc/bessel_temme.c specfunc/bessel_temme.h specfunc/bessel_y.c specfunc/bessel_zero.c specfunc/beta.c specfunc/beta_inc.c specfunc/chebyshev.h specfunc/check.h specfunc/elementary.c specfunc/erfc.c specfunc/error.h specfunc/eval.h specfunc/exp.c specfunc/gamma.c specfunc/gamma_inc.c specfunc/gsl_sf_airy.h specfunc/gsl_sf_bessel.h specfunc/gsl_sf_elementary.h specfunc/gsl_sf_erf.h specfunc/gsl_sf_exp.h specfunc/gsl_sf_gamma.h specfunc/gsl_sf_log.h specfunc/gsl_sf_pow_int.h specfunc/gsl_sf_psi.h specfunc/gsl_sf_result.h specfunc/gsl_sf_trig.h specfunc/gsl_sf_zeta.h specfunc/log.c specfunc/poch.c specfunc/pow_int.c specfunc/psi.c specfunc/result.c specfunc/trig.c specfunc/zeta.c sys/coerce.c sys/fdiv.c sys/gsl_sys.h sys/infnan.c sys/pow_int.c sources_5316/external/gsl/gsl_cblas__csymm.c0000664000176700017670000000066711723710247020015 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_csymm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const void *beta, void *C, const int ldc) { #define BASE float #include "gsl_cblas__source_symm_c.h" #undef BASE } sources_5316/external/gsl/gsl_randist__exppow.c0000664000176700017670000000635711723710247020571 0ustar paulpaul/* randist/exppow.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2006, 2007 James Theiler, Brian Gough * Copyright (C) 2006 Giulio Bottazzi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_sf_gamma.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The exponential power probability distribution is p(x) dx = (1/(2 a Gamma(1+1/b))) * exp(-|x/a|^b) dx for -infty < x < infty. For b = 1 it reduces to the Laplace distribution. The exponential power distribution is related to the gamma distribution by E = a * pow(G(1/b),1/b), where E is an exponential power variate and G is a gamma variate. We use this relation for b < 1. For b >=1 we use rejection methods based on the laplace and gaussian distributions which should be faster. For b>4 we revert to the gamma method. See P. R. Tadikamalla, "Random Sampling from the Exponential Power Distribution", Journal of the American Statistical Association, September 1980, Volume 75, Number 371, pages 683-686. */ double gsl_ran_exppow (const gsl_rng * r, const double a, const double b) { if (b < 1 || b > 4) { double u = gsl_rng_uniform (r); double v = gsl_ran_gamma (r, 1 / b, 1.0); double z = a * pow (v, 1 / b); if (u > 0.5) { return z; } else { return -z; } } else if (b == 1) { /* Laplace distribution */ return gsl_ran_laplace (r, a); } else if (b < 2) { /* Use laplace distribution for rejection method, from Tadikamalla */ double x, h, u; double B = pow (1 / b, 1 / b); do { x = gsl_ran_laplace (r, B); u = gsl_rng_uniform_pos (r); h = -pow (fabs (x), b) + fabs (x) / B - 1 + (1 / b); } while (log (u) > h); return a * x; } else if (b == 2) { /* Gaussian distribution */ return gsl_ran_gaussian (r, a / sqrt (2.0)); } else { /* Use gaussian for rejection method, from Tadikamalla */ double x, h, u; double B = pow (1 / b, 1 / b); do { x = gsl_ran_gaussian (r, B); u = gsl_rng_uniform_pos (r); h = -pow (fabs (x), b) + (x * x) / (2 * B * B) + (1 / b) - 0.5; } while (log (u) > h); return a * x; } } double gsl_ran_exppow_pdf (const double x, const double a, const double b) { double p; double lngamma = gsl_sf_lngamma (1 + 1 / b); p = (1 / (2 * a)) * exp (-pow (fabs (x / a), b) - lngamma); return p; } sources_5316/external/gsl/gsl_cblas__source_trsv_r.h0000664000176700017670000000726011705263724021570 0ustar paulpaul/* blas/source_trsv_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int nonunit = (Diag == CblasNonUnit); INDEX ix, jx; INDEX i, j; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; if (N == 0) return; /* form x := inv( A )*x */ if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { /* backsubstitution */ ix = OFFSET(N, incX) + incX * (N - 1); if (nonunit) { X[ix] = X[ix] / A[lda * (N - 1) + (N - 1)]; } ix -= incX; for (i = N - 1; i > 0 && i--;) { BASE tmp = X[ix]; jx = ix + incX; for (j = i + 1; j < N; j++) { const BASE Aij = A[lda * i + j]; tmp -= Aij * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / A[lda * i + i]; } else { X[ix] = tmp; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { /* forward substitution */ ix = OFFSET(N, incX); if (nonunit) { X[ix] = X[ix] / A[lda * 0 + 0]; } ix += incX; for (i = 1; i < N; i++) { BASE tmp = X[ix]; jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE Aij = A[lda * i + j]; tmp -= Aij * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / A[lda * i + i]; } else { X[ix] = tmp; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := inv( A' )*x */ /* forward substitution */ ix = OFFSET(N, incX); if (nonunit) { X[ix] = X[ix] / A[lda * 0 + 0]; } ix += incX; for (i = 1; i < N; i++) { BASE tmp = X[ix]; jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE Aji = A[lda * j + i]; tmp -= Aji * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / A[lda * i + i]; } else { X[ix] = tmp; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { /* backsubstitution */ ix = OFFSET(N, incX) + (N - 1) * incX; if (nonunit) { X[ix] = X[ix] / A[lda * (N - 1) + (N - 1)]; } ix -= incX; for (i = N - 1; i > 0 && i--;) { BASE tmp = X[ix]; jx = ix + incX; for (j = i + 1; j < N; j++) { const BASE Aji = A[lda * j + i]; tmp -= Aji * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / A[lda * i + i]; } else { X[ix] = tmp; } ix -= incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_cblas__zher2k.c0000664000176700017670000000070211723710247020060 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zher2k (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *B, const int ldb, const double beta, void *C, const int ldc) { #define BASE double #include "gsl_cblas__source_her2k.h" #undef BASE } sources_5316/external/gsl/gsl_const_num.h0000664000176700017670000000331711705263724017372 0ustar paulpaul/* const/gsl_const_num.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, * 2006 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_CONST_NUM__ #define __GSL_CONST_NUM__ #define GSL_CONST_NUM_FINE_STRUCTURE (7.297352533e-3) /* 1 */ #define GSL_CONST_NUM_AVOGADRO (6.02214199e23) /* 1 / mol */ #define GSL_CONST_NUM_YOTTA (1e24) /* 1 */ #define GSL_CONST_NUM_ZETTA (1e21) /* 1 */ #define GSL_CONST_NUM_EXA (1e18) /* 1 */ #define GSL_CONST_NUM_PETA (1e15) /* 1 */ #define GSL_CONST_NUM_TERA (1e12) /* 1 */ #define GSL_CONST_NUM_GIGA (1e9) /* 1 */ #define GSL_CONST_NUM_MEGA (1e6) /* 1 */ #define GSL_CONST_NUM_KILO (1e3) /* 1 */ #define GSL_CONST_NUM_MILLI (1e-3) /* 1 */ #define GSL_CONST_NUM_MICRO (1e-6) /* 1 */ #define GSL_CONST_NUM_NANO (1e-9) /* 1 */ #define GSL_CONST_NUM_PICO (1e-12) /* 1 */ #define GSL_CONST_NUM_FEMTO (1e-15) /* 1 */ #define GSL_CONST_NUM_ATTO (1e-18) /* 1 */ #define GSL_CONST_NUM_ZEPTO (1e-21) /* 1 */ #define GSL_CONST_NUM_YOCTO (1e-24) /* 1 */ #endif /* __GSL_CONST_NUM__ */ sources_5316/external/gsl/gsl_sf__hyperg_1F1.c0000644000176700017670000017035010710226217020103 0ustar paulpaul/* specfunc/hyperg_1F1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_elementary.h" #include "gsl_sf_exp.h" #include "gsl_sf_bessel.h" #include "gsl_sf_gamma.h" #include "gsl_sf_laguerre.h" #include "gsl_sf_hyperg.h" #include "gsl_sf__error.h" #include "gsl_sf__hyperg.h" #define _1F1_INT_THRESHOLD (100.0*GSL_DBL_EPSILON) /* Asymptotic result for 1F1(a, b, x) x -> -Infinity. * Assumes b-a != neg integer and b != neg integer. */ static int hyperg_1F1_asymp_negx(const double a, const double b, const double x, gsl_sf_result * result) { gsl_sf_result lg_b; gsl_sf_result lg_bma; double sgn_b; double sgn_bma; int stat_b = gsl_sf_lngamma_sgn_e(b, &lg_b, &sgn_b); int stat_bma = gsl_sf_lngamma_sgn_e(b-a, &lg_bma, &sgn_bma); if(stat_b == GSL_SUCCESS && stat_bma == GSL_SUCCESS) { gsl_sf_result F; int stat_F = gsl_sf_hyperg_2F0_series_e(a, 1.0+a-b, -1.0/x, -1, &F); if(F.val != 0) { double ln_term_val = a*log(-x); double ln_term_err = 2.0 * GSL_DBL_EPSILON * (fabs(a) + fabs(ln_term_val)); double ln_pre_val = lg_b.val - lg_bma.val - ln_term_val; double ln_pre_err = lg_b.err + lg_bma.err + ln_term_err; int stat_e = gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, sgn_bma*sgn_b*F.val, F.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_F); } else { result->val = 0.0; result->err = 0.0; return stat_F; } } else { DOMAIN_ERROR(result); } } /* Asymptotic result for 1F1(a, b, x) x -> +Infinity * Assumes b != neg integer and a != neg integer */ static int hyperg_1F1_asymp_posx(const double a, const double b, const double x, gsl_sf_result * result) { gsl_sf_result lg_b; gsl_sf_result lg_a; double sgn_b; double sgn_a; int stat_b = gsl_sf_lngamma_sgn_e(b, &lg_b, &sgn_b); int stat_a = gsl_sf_lngamma_sgn_e(a, &lg_a, &sgn_a); if(stat_a == GSL_SUCCESS && stat_b == GSL_SUCCESS) { gsl_sf_result F; int stat_F = gsl_sf_hyperg_2F0_series_e(b-a, 1.0-a, 1.0/x, -1, &F); if(stat_F == GSL_SUCCESS && F.val != 0) { double lnx = log(x); double ln_term_val = (a-b)*lnx; double ln_term_err = 2.0 * GSL_DBL_EPSILON * (fabs(a) + fabs(b)) * fabs(lnx) + 2.0 * GSL_DBL_EPSILON * fabs(a-b); double ln_pre_val = lg_b.val - lg_a.val + ln_term_val + x; double ln_pre_err = lg_b.err + lg_a.err + ln_term_err + 2.0 * GSL_DBL_EPSILON * fabs(x); int stat_e = gsl_sf_exp_mult_err_e(ln_pre_val, ln_pre_err, sgn_a*sgn_b*F.val, F.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_F); } else { result->val = 0.0; result->err = 0.0; return stat_F; } } else { DOMAIN_ERROR(result); } } /* Asymptotic result from Slater 4.3.7 * * To get the general series, write M(a,b,x) as * * M(a,b,x)=sum ((a)_n/(b)_n) (x^n / n!) * * and expand (b)_n in inverse powers of b as follows * * -log(1/(b)_n) = sum_(k=0)^(n-1) log(b+k) * = n log(b) + sum_(k=0)^(n-1) log(1+k/b) * * Do a taylor expansion of the log in 1/b and sum the resulting terms * using the standard algebraic formulas for finite sums of powers of * k. This should then give * * M(a,b,x) = sum_(n=0)^(inf) (a_n/n!) (x/b)^n * (1 - n(n-1)/(2b) * + (n-1)n(n+1)(3n-2)/(24b^2) + ... * * which can be summed explicitly. The trick for summing it is to take * derivatives of sum_(i=0)^(inf) a_n*y^n/n! = (1-y)^(-a); * * [BJG 16/01/2007] */ static int hyperg_1F1_largebx(const double a, const double b, const double x, gsl_sf_result * result) { double y = x/b; double f = exp(-a*log1p(-y)); double t1 = -((a*(a+1.0))/(2*b))*pow((y/(1.0-y)),2.0); double t2 = (1/(24*b*b))*((a*(a+1)*y*y)/pow(1-y,4))*(12+8*(2*a+1)*y+(3*a*a-a-2)*y*y); double t3 = (-1/(48*b*b*b*pow(1-y,6)))*a*((a + 1)*((y*((a + 1)*(a*(y*(y*((y*(a - 2) + 16)*(a - 1)) + 72)) + 96)) + 24)*pow(y, 2))); result->val = f * (1 + t1 + t2 + t3); result->err = 2*fabs(f*t3) + 2*GSL_DBL_EPSILON*fabs(result->val); return GSL_SUCCESS; } /* Asymptotic result for x < 2b-4a, 2b-4a large. * [Abramowitz+Stegun, 13.5.21] * * assumes 0 <= x/(2b-4a) <= 1 */ static int hyperg_1F1_large2bm4a(const double a, const double b, const double x, gsl_sf_result * result) { double eta = 2.0*b - 4.0*a; double cos2th = x/eta; double sin2th = 1.0 - cos2th; double th = acos(sqrt(cos2th)); double pre_h = 0.25*M_PI*M_PI*eta*eta*cos2th*sin2th; gsl_sf_result lg_b; int stat_lg = gsl_sf_lngamma_e(b, &lg_b); double t1 = 0.5*(1.0-b)*log(0.25*x*eta); double t2 = 0.25*log(pre_h); double lnpre_val = lg_b.val + 0.5*x + t1 - t2; double lnpre_err = lg_b.err + 2.0 * GSL_DBL_EPSILON * (fabs(0.5*x) + fabs(t1) + fabs(t2)); #if SMALL_ANGLE const double eps = asin(sqrt(cos2th)); /* theta = pi/2 - eps */ double s1 = (fmod(a, 1.0) == 0.0) ? 0.0 : sin(a*M_PI); double eta_reduc = (fmod(eta + 1, 4.0) == 0.0) ? 0.0 : fmod(eta + 1, 8.0); double phi1 = 0.25*eta_reduc*M_PI; double phi2 = 0.25*eta*(2*eps + sin(2.0*eps)); double s2 = sin(phi1 - phi2); #else double s1 = sin(a*M_PI); double s2 = sin(0.25*eta*(2.0*th - sin(2.0*th)) + 0.25*M_PI); #endif double ser_val = s1 + s2; double ser_err = 2.0 * GSL_DBL_EPSILON * (fabs(s1) + fabs(s2)); int stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, ser_val, ser_err, result); return GSL_ERROR_SELECT_2(stat_e, stat_lg); } /* Luke's rational approximation. * See [Luke, Algorithms for the Computation of Mathematical Functions, p.182] * * Like the case of the 2F1 rational approximations, these are * probably guaranteed to converge for x < 0, barring gross * numerical instability in the pre-asymptotic regime. */ static int hyperg_1F1_luke(const double a, const double c, const double xin, gsl_sf_result * result) { const double RECUR_BIG = 1.0e+50; const int nmax = 5000; int n = 3; const double x = -xin; const double x3 = x*x*x; const double t0 = a/c; const double t1 = (a+1.0)/(2.0*c); const double t2 = (a+2.0)/(2.0*(c+1.0)); double F = 1.0; double prec; double Bnm3 = 1.0; /* B0 */ double Bnm2 = 1.0 + t1 * x; /* B1 */ double Bnm1 = 1.0 + t2 * x * (1.0 + t1/3.0 * x); /* B2 */ double Anm3 = 1.0; /* A0 */ double Anm2 = Bnm2 - t0 * x; /* A1 */ double Anm1 = Bnm1 - t0*(1.0 + t2*x)*x + t0 * t1 * (c/(c+1.0)) * x*x; /* A2 */ while(1) { double npam1 = n + a - 1; double npcm1 = n + c - 1; double npam2 = n + a - 2; double npcm2 = n + c - 2; double tnm1 = 2*n - 1; double tnm3 = 2*n - 3; double tnm5 = 2*n - 5; double F1 = (n-a-2) / (2*tnm3*npcm1); double F2 = (n+a)*npam1 / (4*tnm1*tnm3*npcm2*npcm1); double F3 = -npam2*npam1*(n-a-2) / (8*tnm3*tnm3*tnm5*(n+c-3)*npcm2*npcm1); double E = -npam1*(n-c-1) / (2*tnm3*npcm2*npcm1); double An = (1.0+F1*x)*Anm1 + (E + F2*x)*x*Anm2 + F3*x3*Anm3; double Bn = (1.0+F1*x)*Bnm1 + (E + F2*x)*x*Bnm2 + F3*x3*Bnm3; double r = An/Bn; prec = fabs((F - r)/F); F = r; if(prec < GSL_DBL_EPSILON || n > nmax) break; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; Anm3 /= RECUR_BIG; Bnm3 /= RECUR_BIG; } else if(fabs(An) < 1.0/RECUR_BIG || fabs(Bn) < 1.0/RECUR_BIG) { An *= RECUR_BIG; Bn *= RECUR_BIG; Anm1 *= RECUR_BIG; Bnm1 *= RECUR_BIG; Anm2 *= RECUR_BIG; Bnm2 *= RECUR_BIG; Anm3 *= RECUR_BIG; Bnm3 *= RECUR_BIG; } n++; Bnm3 = Bnm2; Bnm2 = Bnm1; Bnm1 = Bn; Anm3 = Anm2; Anm2 = Anm1; Anm1 = An; } result->val = F; result->err = 2.0 * fabs(F * prec); result->err += 2.0 * GSL_DBL_EPSILON * (n-1.0) * fabs(F); return GSL_SUCCESS; } /* Series for 1F1(1,b,x) * b > 0 */ static int hyperg_1F1_1_series(const double b, const double x, gsl_sf_result * result) { double sum_val = 1.0; double sum_err = 0.0; double term = 1.0; double n = 1.0; while(fabs(term/sum_val) > 0.25*GSL_DBL_EPSILON) { term *= x/(b+n-1); sum_val += term; sum_err += 8.0*GSL_DBL_EPSILON*fabs(term) + GSL_DBL_EPSILON*fabs(sum_val); n += 1.0; } result->val = sum_val; result->err = sum_err; result->err += 2.0 * fabs(term); return GSL_SUCCESS; } /* 1F1(1,b,x) * b >= 1, b integer */ static int hyperg_1F1_1_int(const int b, const double x, gsl_sf_result * result) { if(b < 1) { DOMAIN_ERROR(result); } else if(b == 1) { return gsl_sf_exp_e(x, result); } else if(b == 2) { return gsl_sf_exprel_e(x, result); } else if(b == 3) { return gsl_sf_exprel_2_e(x, result); } else { return gsl_sf_exprel_n_e(b-1, x, result); } } /* 1F1(1,b,x) * b >=1, b real * * checked OK: [GJ] Thu Oct 1 16:46:35 MDT 1998 */ static int hyperg_1F1_1(const double b, const double x, gsl_sf_result * result) { double ax = fabs(x); double ib = floor(b + 0.1); if(b < 1.0) { DOMAIN_ERROR(result); } else if(b == 1.0) { return gsl_sf_exp_e(x, result); } else if(b >= 1.4*ax) { return hyperg_1F1_1_series(b, x, result); } else if(fabs(b - ib) < _1F1_INT_THRESHOLD && ib < INT_MAX) { return hyperg_1F1_1_int((int)ib, x, result); } else if(x > 0.0) { if(x > 100.0 && b < 0.75*x) { return hyperg_1F1_asymp_posx(1.0, b, x, result); } else if(b < 1.0e+05) { /* Recurse backward on b, from a * chosen offset point. For x > 0, * which holds here, this should * be a stable direction. */ const double off = ceil(1.4*x-b) + 1.0; double bp = b + off; gsl_sf_result M; int stat_s = hyperg_1F1_1_series(bp, x, &M); const double err_rat = M.err / fabs(M.val); while(bp > b+0.1) { /* M(1,b-1) = x/(b-1) M(1,b) + 1 */ bp -= 1.0; M.val = 1.0 + x/bp * M.val; } result->val = M.val; result->err = err_rat * fabs(M.val); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(off)+1.0) * fabs(M.val); return stat_s; } else if (fabs(x) < fabs(b) && fabs(x) < sqrt(fabs(b)) * fabs(b-x)) { return hyperg_1F1_largebx(1.0, b, x, result); } else if (fabs(x) > fabs(b)) { return hyperg_1F1_1_series(b, x, result); } else { return hyperg_1F1_large2bm4a(1.0, b, x, result); } } else { /* x <= 0 and b not large compared to |x| */ if(ax < 10.0 && b < 10.0) { return hyperg_1F1_1_series(b, x, result); } else if(ax >= 100.0 && GSL_MAX_DBL(fabs(2.0-b),1.0) < 0.99*ax) { return hyperg_1F1_asymp_negx(1.0, b, x, result); } else { return hyperg_1F1_luke(1.0, b, x, result); } } } /* 1F1(a,b,x)/Gamma(b) for b->0 * [limit of Abramowitz+Stegun 13.3.7] */ static int hyperg_1F1_renorm_b0(const double a, const double x, gsl_sf_result * result) { double eta = a*x; if(eta > 0.0) { double root_eta = sqrt(eta); gsl_sf_result I1_scaled; int stat_I = gsl_sf_bessel_I1_scaled_e(2.0*root_eta, &I1_scaled); if(I1_scaled.val <= 0.0) { result->val = 0.0; result->err = 0.0; return GSL_ERROR_SELECT_2(stat_I, GSL_EDOM); } else { /* Note that 13.3.7 contains higher terms which are zeroth order in b. These make a non-negligible contribution to the sum. With the first correction term, the I1 above is replaced by I1 + (2/3)*a*(x/(4a))**(3/2)*I2(2*root_eta). We will add this as part of the result and error estimate. */ const double corr1 =(2.0/3.0)*a*pow(x/(4.0*a),1.5)*gsl_sf_bessel_In_scaled(2, 2.0*root_eta) ; const double lnr_val = 0.5*x + 0.5*log(eta) + fabs(2.0*root_eta) + log(I1_scaled.val+corr1); const double lnr_err = GSL_DBL_EPSILON * (1.5*fabs(x) + 1.0) + fabs((I1_scaled.err+corr1)/I1_scaled.val); return gsl_sf_exp_err_e(lnr_val, lnr_err, result); } } else if(eta == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { /* eta < 0 */ double root_eta = sqrt(-eta); gsl_sf_result J1; int stat_J = gsl_sf_bessel_J1_e(2.0*root_eta, &J1); if(J1.val <= 0.0) { result->val = 0.0; result->err = 0.0; return GSL_ERROR_SELECT_2(stat_J, GSL_EDOM); } else { const double t1 = 0.5*x; const double t2 = 0.5*log(-eta); const double t3 = fabs(x); const double t4 = log(J1.val); const double lnr_val = t1 + t2 + t3 + t4; const double lnr_err = GSL_DBL_EPSILON * (1.5*fabs(x) + 1.0) + fabs(J1.err/J1.val); gsl_sf_result ex; int stat_e = gsl_sf_exp_err_e(lnr_val, lnr_err, &ex); result->val = -ex.val; result->err = ex.err; return stat_e; } } } /* 1F1'(a,b,x)/1F1(a,b,x) * Uses Gautschi's version of the CF. * [Gautschi, Math. Comp. 31, 994 (1977)] * * Supposedly this suffers from the "anomalous convergence" * problem when b < x. I have seen anomalous convergence * in several of the continued fractions associated with * 1F1(a,b,x). This particular CF formulation seems stable * for b > x. However, it does display a painful artifact * of the anomalous convergence; the convergence plateaus * unless b >>> x. For example, even for b=1000, x=1, this * method locks onto a ratio which is only good to about * 4 digits. Apparently the rest of the digits are hiding * way out on the plateau, but finite-precision lossage * means you will never get them. */ #if 0 static int hyperg_1F1_CF1_p(const double a, const double b, const double x, double * result) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 5000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = 1.0; double b1 = 1.0; double An = b1*Anm1 + a1*Anm2; double Bn = b1*Bnm1 + a1*Bnm2; double an, bn; double fn = An/Bn; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = (a+n)*x/((b-x+n-1)*(b-x+n)); bn = 1.0; An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 10.0*GSL_DBL_EPSILON) break; } *result = a/(b-x) * fn; if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } #endif /* 0 */ /* 1F1'(a,b,x)/1F1(a,b,x) * Uses Gautschi's series transformation of the * continued fraction. This is apparently the best * method for getting this ratio in the stable region. * The convergence is monotone and supergeometric * when b > x. * Assumes a >= -1. */ static int hyperg_1F1_CF1_p_ser(const double a, const double b, const double x, double * result) { if(a == 0.0) { *result = 0.0; return GSL_SUCCESS; } else { const int maxiter = 5000; double sum = 1.0; double pk = 1.0; double rhok = 0.0; int k; for(k=1; k RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 10.0*GSL_DBL_EPSILON) break; } *result = fn; if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } #endif /* 0 */ /* 1F1(a,b+1,x)/1F1(a,b,x) * * This seemed to suffer from "anomalous convergence". * However, I have no theory for this recurrence. */ #if 0 static int hyperg_1F1_CF1_b(const double a, const double b, const double x, double * result) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 5000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = b + 1.0; double b1 = (b + 1.0) * (b - x); double An = b1*Anm1 + a1*Anm2; double Bn = b1*Bnm1 + a1*Bnm2; double an, bn; double fn = An/Bn; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = (b + n) * (b + n - 1.0 - a) * x; bn = (b + n) * (b + n - 1.0 - x); An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 10.0*GSL_DBL_EPSILON) break; } *result = fn; if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } #endif /* 0 */ /* 1F1(a,b,x) * |a| <= 1, b > 0 */ static int hyperg_1F1_small_a_bgt0(const double a, const double b, const double x, gsl_sf_result * result) { const double bma = b-a; const double oma = 1.0-a; const double ap1mb = 1.0+a-b; const double abs_bma = fabs(bma); const double abs_oma = fabs(oma); const double abs_ap1mb = fabs(ap1mb); const double ax = fabs(x); if(a == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(a == 1.0 && b >= 1.0) { return hyperg_1F1_1(b, x, result); } else if(a == -1.0) { result->val = 1.0 + a/b * x; result->err = GSL_DBL_EPSILON * (1.0 + fabs(a/b * x)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(b >= 1.4*ax) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if(x > 0.0) { if(x > 100.0 && abs_bma*abs_oma < 0.5*x) { return hyperg_1F1_asymp_posx(a, b, x, result); } else if(b < 5.0e+06) { /* Recurse backward on b from * a suitably high point. */ const double b_del = ceil(1.4*x-b) + 1.0; double bp = b + b_del; gsl_sf_result r_Mbp1; gsl_sf_result r_Mb; double Mbp1; double Mb; double Mbm1; int stat_0 = gsl_sf_hyperg_1F1_series_e(a, bp+1.0, x, &r_Mbp1); int stat_1 = gsl_sf_hyperg_1F1_series_e(a, bp, x, &r_Mb); const double err_rat = fabs(r_Mbp1.err/r_Mbp1.val) + fabs(r_Mb.err/r_Mb.val); Mbp1 = r_Mbp1.val; Mb = r_Mb.val; while(bp > b+0.1) { /* Do backward recursion. */ Mbm1 = ((x+bp-1.0)*Mb - x*(bp-a)/bp*Mbp1)/(bp-1.0); bp -= 1.0; Mbp1 = Mb; Mb = Mbm1; } result->val = Mb; result->err = err_rat * (fabs(b_del)+1.0) * fabs(Mb); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Mb); return GSL_ERROR_SELECT_2(stat_0, stat_1); } else if (fabs(x) < fabs(b) && fabs(a*x) < sqrt(fabs(b)) * fabs(b-x)) { return hyperg_1F1_largebx(a, b, x, result); } else { return hyperg_1F1_large2bm4a(a, b, x, result); } } else { /* x < 0 and b not large compared to |x| */ if(ax < 10.0 && b < 10.0) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if(ax >= 100.0 && GSL_MAX(abs_ap1mb,1.0) < 0.99*ax) { return hyperg_1F1_asymp_negx(a, b, x, result); } else { return hyperg_1F1_luke(a, b, x, result); } } } /* 1F1(b+eps,b,x) * |eps|<=1, b > 0 */ static int hyperg_1F1_beps_bgt0(const double eps, const double b, const double x, gsl_sf_result * result) { if(b > fabs(x) && fabs(eps) < GSL_SQRT_DBL_EPSILON) { /* If b-a is very small and x/b is not too large we can * use this explicit approximation. * * 1F1(b+eps,b,x) = exp(ax/b) (1 - eps x^2 (v2 + v3 x + ...) + ...) * * v2 = a/(2b^2(b+1)) * v3 = a(b-2a)/(3b^3(b+1)(b+2)) * ... * * See [Luke, Mathematical Functions and Their Approximations, p.292] * * This cannot be used for b near a negative integer or zero. * Also, if x/b is large the deviation from exp(x) behaviour grows. */ double a = b + eps; gsl_sf_result exab; int stat_e = gsl_sf_exp_e(a*x/b, &exab); double v2 = a/(2.0*b*b*(b+1.0)); double v3 = a*(b-2.0*a)/(3.0*b*b*b*(b+1.0)*(b+2.0)); double v = v2 + v3 * x; double f = (1.0 - eps*x*x*v); result->val = exab.val * f; result->err = exab.err * fabs(f); result->err += fabs(exab.val) * GSL_DBL_EPSILON * (1.0 + fabs(eps*x*x*v)); result->err += 4.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_e; } else { /* Otherwise use a Kummer transformation to reduce * it to the small a case. */ gsl_sf_result Kummer_1F1; int stat_K = hyperg_1F1_small_a_bgt0(-eps, b, -x, &Kummer_1F1); if(Kummer_1F1.val != 0.0) { int stat_e = gsl_sf_exp_mult_err_e(x, 2.0*GSL_DBL_EPSILON*fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else { result->val = 0.0; result->err = 0.0; return stat_K; } } } /* 1F1(a,2a,x) = Gamma(a + 1/2) E(x) (|x|/4)^(-a+1/2) scaled_I(a-1/2,|x|/2) * * E(x) = exp(x) x > 0 * = 1 x < 0 * * a >= 1/2 */ static int hyperg_1F1_beq2a_pos(const double a, const double x, gsl_sf_result * result) { if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result I; int stat_I = gsl_sf_bessel_Inu_scaled_e(a-0.5, 0.5*fabs(x), &I); gsl_sf_result lg; int stat_g = gsl_sf_lngamma_e(a + 0.5, &lg); double ln_term = (0.5-a)*log(0.25*fabs(x)); double lnpre_val = lg.val + GSL_MAX_DBL(x,0.0) + ln_term; double lnpre_err = lg.err + GSL_DBL_EPSILON * (fabs(ln_term) + fabs(x)); int stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, I.val, I.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_g, stat_I); } } /* Determine middle parts of diagonal recursion along b=2a * from two endpoints, i.e. * * given: M(a,b) and M(a+1,b+2) * get: M(a+1,b+1) and M(a,b+1) */ #if 0 inline static int hyperg_1F1_diag_step(const double a, const double b, const double x, const double Mab, const double Map1bp2, double * Map1bp1, double * Mabp1) { if(a == b) { *Map1bp1 = Mab; *Mabp1 = Mab - x/(b+1.0) * Map1bp2; } else { *Map1bp1 = Mab - x * (a-b)/(b*(b+1.0)) * Map1bp2; *Mabp1 = (a * *Map1bp1 - b * Mab)/(a-b); } return GSL_SUCCESS; } #endif /* 0 */ /* Determine endpoint of diagonal recursion. * * given: M(a,b) and M(a+1,b+2) * get: M(a+1,b) and M(a+1,b+1) */ #if 0 inline static int hyperg_1F1_diag_end_step(const double a, const double b, const double x, const double Mab, const double Map1bp2, double * Map1b, double * Map1bp1) { *Map1bp1 = Mab - x * (a-b)/(b*(b+1.0)) * Map1bp2; *Map1b = Mab + x/b * *Map1bp1; return GSL_SUCCESS; } #endif /* 0 */ /* Handle the case of a and b both positive integers. * Assumes a > 0 and b > 0. */ static int hyperg_1F1_ab_posint(const int a, const int b, const double x, gsl_sf_result * result) { double ax = fabs(x); if(a == b) { return gsl_sf_exp_e(x, result); /* 1F1(a,a,x) */ } else if(a == 1) { return gsl_sf_exprel_n_e(b-1, x, result); /* 1F1(1,b,x) */ } else if(b == a + 1) { gsl_sf_result K; int stat_K = gsl_sf_exprel_n_e(a, -x, &K); /* 1F1(1,1+a,-x) */ int stat_e = gsl_sf_exp_mult_err_e(x, 2.0 * GSL_DBL_EPSILON * fabs(x), K.val, K.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if(a == b + 1) { gsl_sf_result ex; int stat_e = gsl_sf_exp_e(x, &ex); result->val = ex.val * (1.0 + x/b); result->err = ex.err * (1.0 + x/b); result->err += ex.val * GSL_DBL_EPSILON * (1.0 + fabs(x/b)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_e; } else if(a == b + 2) { gsl_sf_result ex; int stat_e = gsl_sf_exp_e(x, &ex); double poly = (1.0 + x/b*(2.0 + x/(b+1.0))); result->val = ex.val * poly; result->err = ex.err * fabs(poly); result->err += ex.val * GSL_DBL_EPSILON * (1.0 + fabs(x/b) * (2.0 + fabs(x/(b+1.0)))); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_e; } else if(b == 2*a) { return hyperg_1F1_beq2a_pos(a, x, result); /* 1F1(a,2a,x) */ } else if( ( b < 10 && a < 10 && ax < 5.0 ) || ( b > a*ax ) || ( b > a && ax < 5.0 ) ) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if(b > a && b >= 2*a + x) { /* Use the Gautschi CF series, then * recurse backward to a=0 for normalization. * This will work for either sign of x. */ double rap; int stat_CF1 = hyperg_1F1_CF1_p_ser(a, b, x, &rap); double ra = 1.0 + x/a * rap; double Ma = GSL_SQRT_DBL_MIN; double Map1 = ra * Ma; double Mnp1 = Map1; double Mn = Ma; double Mnm1; int n; for(n=a; n>0; n--) { Mnm1 = (n * Mnp1 - (2*n-b+x) * Mn) / (b-n); Mnp1 = Mn; Mn = Mnm1; } result->val = Ma/Mn; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(a) + 1.0) * fabs(Ma/Mn); return stat_CF1; } else if(b > a && b < 2*a + x && b > x) { /* Use the Gautschi series representation of * the continued fraction. Then recurse forward * to the a=b line for normalization. This will * work for either sign of x, although we do need * to check for b > x, for when x is positive. */ double rap; int stat_CF1 = hyperg_1F1_CF1_p_ser(a, b, x, &rap); double ra = 1.0 + x/a * rap; gsl_sf_result ex; int stat_ex; double Ma = GSL_SQRT_DBL_MIN; double Map1 = ra * Ma; double Mnm1 = Ma; double Mn = Map1; double Mnp1; int n; for(n=a+1; nval = ex.val * Ma/Mn; result->err = ex.err * fabs(Ma/Mn); result->err += 4.0 * GSL_DBL_EPSILON * (fabs(b-a)+1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_ex, stat_CF1); } else if(x >= 0.0) { if(b < a) { /* The point b,b is below the b=2a+x line. * Forward recursion on a from b,b+1 is possible. * Note that a > b + 1 as well, since we already tried a = b + 1. */ if(x + log(fabs(x/b)) < GSL_LOG_DBL_MAX-2.0) { double ex = exp(x); int n; double Mnm1 = ex; /* 1F1(b,b,x) */ double Mn = ex * (1.0 + x/b); /* 1F1(b+1,b,x) */ double Mnp1; for(n=b+1; nval = Mn; result->err = (x + 1.0) * GSL_DBL_EPSILON * fabs(Mn); result->err *= fabs(a-b)+1.0; return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } else { /* b > a * b < 2a + x * b <= x (otherwise we would have finished above) * * Gautschi anomalous convergence region. However, we can * recurse forward all the way from a=0,1 because we are * always underneath the b=2a+x line. */ gsl_sf_result r_Mn; double Mnm1 = 1.0; /* 1F1(0,b,x) */ double Mn; /* 1F1(1,b,x) */ double Mnp1; int n; gsl_sf_exprel_n_e(b-1, x, &r_Mn); Mn = r_Mn.val; for(n=1; nval = Mn; result->err = fabs(Mn) * (1.0 + fabs(a)) * fabs(r_Mn.err / r_Mn.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Mn); return GSL_SUCCESS; } } else { /* x < 0 * b < a (otherwise we would have tripped one of the above) */ if(a <= 0.5*(b-x) || a >= -x) { /* Gautschi continued fraction is in the anomalous region, * so we must find another way. We recurse down in b, * from the a=b line. */ double ex = exp(x); double Manp1 = ex; double Man = ex * (1.0 + x/(a-1.0)); double Manm1; int n; for(n=a-1; n>b; n--) { Manm1 = (-n*(1-n-x)*Man - x*(n-a)*Manp1)/(n*(n-1.0)); Manp1 = Man; Man = Manm1; } result->val = Man; result->err = (fabs(x) + 1.0) * GSL_DBL_EPSILON * fabs(Man); result->err *= fabs(b-a)+1.0; return GSL_SUCCESS; } else { /* Pick a0 such that b ~= 2a0 + x, then * recurse down in b from a0,a0 to determine * the values near the line b=2a+x. Then recurse * forward on a from a0. */ int a0 = ceil(0.5*(b-x)); double Ma0b; /* M(a0,b) */ double Ma0bp1; /* M(a0,b+1) */ double Ma0p1b; /* M(a0+1,b) */ double Mnm1; double Mn; double Mnp1; int n; { double ex = exp(x); double Ma0np1 = ex; double Ma0n = ex * (1.0 + x/(a0-1.0)); double Ma0nm1; for(n=a0-1; n>b; n--) { Ma0nm1 = (-n*(1-n-x)*Ma0n - x*(n-a0)*Ma0np1)/(n*(n-1.0)); Ma0np1 = Ma0n; Ma0n = Ma0nm1; } Ma0bp1 = Ma0np1; Ma0b = Ma0n; Ma0p1b = (b*(a0+x)*Ma0b + x*(a0-b)*Ma0bp1)/(a0*b); } /* Initialise the recurrence correctly BJG */ if (a0 >= a) { Mn = Ma0b; } else if (a0 + 1>= a) { Mn = Ma0p1b; } else { Mnm1 = Ma0b; Mn = Ma0p1b; for(n=a0+1; nval = Mn; result->err = (fabs(x) + 1.0) * GSL_DBL_EPSILON * fabs(Mn); result->err *= fabs(b-a)+1.0; return GSL_SUCCESS; } } } /* Evaluate a <= 0, a integer, cases directly. (Polynomial; Horner) * When the terms are all positive, this * must work. We will assume this here. */ static int hyperg_1F1_a_negint_poly(const int a, const double b, const double x, gsl_sf_result * result) { if(a == 0) { result->val = 1.0; result->err = 1.0; return GSL_SUCCESS; } else { int N = -a; double poly = 1.0; int k; for(k=N-1; k>=0; k--) { double t = (a+k)/(b+k) * (x/(k+1)); double r = t + 1.0/poly; if(r > 0.9*GSL_DBL_MAX/poly) { OVERFLOW_ERROR(result); } else { poly *= r; /* P_n = 1 + t_n P_{n-1} */ } } result->val = poly; result->err = 2.0 * (sqrt(N) + 1.0) * GSL_DBL_EPSILON * fabs(poly); return GSL_SUCCESS; } } /* Evaluate negative integer a case by relation * to Laguerre polynomials. This is more general than * the direct polynomial evaluation, but is safe * for all values of x. * * 1F1(-n,b,x) = n!/(b)_n Laguerre[n,b-1,x] * = n B(b,n) Laguerre[n,b-1,x] * * assumes b is not a negative integer */ static int hyperg_1F1_a_negint_lag(const int a, const double b, const double x, gsl_sf_result * result) { const int n = -a; gsl_sf_result lag; const int stat_l = gsl_sf_laguerre_n_e(n, b-1.0, x, &lag); if(b < 0.0) { gsl_sf_result lnfact; gsl_sf_result lng1; gsl_sf_result lng2; double s1, s2; const int stat_f = gsl_sf_lnfact_e(n, &lnfact); const int stat_g1 = gsl_sf_lngamma_sgn_e(b + n, &lng1, &s1); const int stat_g2 = gsl_sf_lngamma_sgn_e(b, &lng2, &s2); const double lnpre_val = lnfact.val - (lng1.val - lng2.val); const double lnpre_err = lnfact.err + lng1.err + lng2.err + 2.0 * GSL_DBL_EPSILON * fabs(lnpre_val); const int stat_e = gsl_sf_exp_mult_err_e(lnpre_val, lnpre_err, s1*s2*lag.val, lag.err, result); return GSL_ERROR_SELECT_5(stat_e, stat_l, stat_g1, stat_g2, stat_f); } else { gsl_sf_result lnbeta; gsl_sf_lnbeta_e(b, n, &lnbeta); if(fabs(lnbeta.val) < 0.1) { /* As we have noted, when B(x,y) is near 1, * evaluating log(B(x,y)) is not accurate. * Instead we evaluate B(x,y) directly. */ const double ln_term_val = log(1.25*n); const double ln_term_err = 2.0 * GSL_DBL_EPSILON * ln_term_val; gsl_sf_result beta; int stat_b = gsl_sf_beta_e(b, n, &beta); int stat_e = gsl_sf_exp_mult_err_e(ln_term_val, ln_term_err, lag.val, lag.err, result); result->val *= beta.val/1.25; result->err *= beta.val/1.25; return GSL_ERROR_SELECT_3(stat_e, stat_l, stat_b); } else { /* B(x,y) was not near 1, so it is safe to use * the logarithmic values. */ const double ln_n = log(n); const double ln_term_val = lnbeta.val + ln_n; const double ln_term_err = lnbeta.err + 2.0 * GSL_DBL_EPSILON * fabs(ln_n); int stat_e = gsl_sf_exp_mult_err_e(ln_term_val, ln_term_err, lag.val, lag.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_l); } } } /* Handle negative integer a case for x > 0 and * generic b. * * Combine [Abramowitz+Stegun, 13.6.9 + 13.6.27] * M(-n,b,x) = (-1)^n / (b)_n U(-n,b,x) = n! / (b)_n Laguerre^(b-1)_n(x) */ #if 0 static int hyperg_1F1_a_negint_U(const int a, const double b, const double x, gsl_sf_result * result) { const int n = -a; const double sgn = ( GSL_IS_ODD(n) ? -1.0 : 1.0 ); double sgpoch; gsl_sf_result lnpoch; gsl_sf_result U; const int stat_p = gsl_sf_lnpoch_sgn_e(b, n, &lnpoch, &sgpoch); const int stat_U = gsl_sf_hyperg_U_e(-n, b, x, &U); const int stat_e = gsl_sf_exp_mult_err_e(-lnpoch.val, lnpoch.err, sgn * sgpoch * U.val, U.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_U, stat_p); } #endif /* Assumes a <= -1, b <= -1, and b <= a. */ static int hyperg_1F1_ab_negint(const int a, const int b, const double x, gsl_sf_result * result) { if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(x > 0.0) { return hyperg_1F1_a_negint_poly(a, b, x, result); } else { /* Apply a Kummer transformation to make x > 0 so * we can evaluate the polynomial safely. Of course, * this assumes b <= a, which must be true for * a<0 and b<0, since otherwise the thing is undefined. */ gsl_sf_result K; int stat_K = hyperg_1F1_a_negint_poly(b-a, b, -x, &K); int stat_e = gsl_sf_exp_mult_err_e(x, 2.0 * GSL_DBL_EPSILON * fabs(x), K.val, K.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } } /* [Abramowitz+Stegun, 13.1.3] * * M(a,b,x) = Gamma(1+a-b)/Gamma(2-b) x^(1-b) * * { Gamma(b)/Gamma(a) M(1+a-b,2-b,x) - (b-1) U(1+a-b,2-b,x) } * * b not an integer >= 2 * a-b not a negative integer */ static int hyperg_1F1_U(const double a, const double b, const double x, gsl_sf_result * result) { const double bp = 2.0 - b; const double ap = a - b + 1.0; gsl_sf_result lg_ap, lg_bp; double sg_ap; int stat_lg0 = gsl_sf_lngamma_sgn_e(ap, &lg_ap, &sg_ap); int stat_lg1 = gsl_sf_lngamma_e(bp, &lg_bp); int stat_lg2 = GSL_ERROR_SELECT_2(stat_lg0, stat_lg1); double t1 = (bp-1.0) * log(x); double lnpre_val = lg_ap.val - lg_bp.val + t1; double lnpre_err = lg_ap.err + lg_bp.err + 2.0 * GSL_DBL_EPSILON * fabs(t1); gsl_sf_result lg_2mbp, lg_1papmbp; double sg_2mbp, sg_1papmbp; int stat_lg3 = gsl_sf_lngamma_sgn_e(2.0-bp, &lg_2mbp, &sg_2mbp); int stat_lg4 = gsl_sf_lngamma_sgn_e(1.0+ap-bp, &lg_1papmbp, &sg_1papmbp); int stat_lg5 = GSL_ERROR_SELECT_2(stat_lg3, stat_lg4); double lnc1_val = lg_2mbp.val - lg_1papmbp.val; double lnc1_err = lg_2mbp.err + lg_1papmbp.err + GSL_DBL_EPSILON * (fabs(lg_2mbp.val) + fabs(lg_1papmbp.val)); gsl_sf_result M; gsl_sf_result_e10 U; int stat_F = gsl_sf_hyperg_1F1_e(ap, bp, x, &M); int stat_U = gsl_sf_hyperg_U_e10_e(ap, bp, x, &U); int stat_FU = GSL_ERROR_SELECT_2(stat_F, stat_U); gsl_sf_result_e10 term_M; int stat_e0 = gsl_sf_exp_mult_err_e10_e(lnc1_val, lnc1_err, sg_2mbp*sg_1papmbp*M.val, M.err, &term_M); const double ombp = 1.0 - bp; const double Uee_val = U.e10*M_LN10; const double Uee_err = 2.0 * GSL_DBL_EPSILON * fabs(Uee_val); const double Mee_val = term_M.e10*M_LN10; const double Mee_err = 2.0 * GSL_DBL_EPSILON * fabs(Mee_val); int stat_e1; /* Do a little dance with the exponential prefactors * to avoid overflows in intermediate results. */ if(Uee_val > Mee_val) { const double factorM_val = exp(Mee_val-Uee_val); const double factorM_err = 2.0 * GSL_DBL_EPSILON * (fabs(Mee_val-Uee_val)+1.0) * factorM_val; const double inner_val = term_M.val*factorM_val - ombp*U.val; const double inner_err = term_M.err*factorM_val + fabs(ombp) * U.err + fabs(term_M.val) * factorM_err + GSL_DBL_EPSILON * (fabs(term_M.val*factorM_val) + fabs(ombp*U.val)); stat_e1 = gsl_sf_exp_mult_err_e(lnpre_val+Uee_val, lnpre_err+Uee_err, sg_ap*inner_val, inner_err, result); } else { const double factorU_val = exp(Uee_val - Mee_val); const double factorU_err = 2.0 * GSL_DBL_EPSILON * (fabs(Mee_val-Uee_val)+1.0) * factorU_val; const double inner_val = term_M.val - ombp*factorU_val*U.val; const double inner_err = term_M.err + fabs(ombp*factorU_val*U.err) + fabs(ombp*factorU_err*U.val) + GSL_DBL_EPSILON * (fabs(term_M.val) + fabs(ombp*factorU_val*U.val)); stat_e1 = gsl_sf_exp_mult_err_e(lnpre_val+Mee_val, lnpre_err+Mee_err, sg_ap*inner_val, inner_err, result); } return GSL_ERROR_SELECT_5(stat_e1, stat_e0, stat_FU, stat_lg5, stat_lg2); } /* Handle case of generic positive a, b. * Assumes b-a is not a negative integer. */ static int hyperg_1F1_ab_pos(const double a, const double b, const double x, gsl_sf_result * result) { const double ax = fabs(x); if( ( b < 10.0 && a < 10.0 && ax < 5.0 ) || ( b > a*ax ) || ( b > a && ax < 5.0 ) ) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if( x < -100.0 && GSL_MAX_DBL(fabs(a),1.0)*GSL_MAX_DBL(fabs(1.0+a-b),1.0) < 0.7*fabs(x) ) { /* Large negative x asymptotic. */ return hyperg_1F1_asymp_negx(a, b, x, result); } else if( x > 100.0 && GSL_MAX_DBL(fabs(b-a),1.0)*GSL_MAX_DBL(fabs(1.0-a),1.0) < 0.7*fabs(x) ) { /* Large positive x asymptotic. */ return hyperg_1F1_asymp_posx(a, b, x, result); } else if(fabs(b-a) <= 1.0) { /* Directly handle b near a. */ return hyperg_1F1_beps_bgt0(a-b, b, x, result); /* a = b + eps */ } else if(b > a && b >= 2*a + x) { /* Use the Gautschi CF series, then * recurse backward to a near 0 for normalization. * This will work for either sign of x. */ double rap; int stat_CF1 = hyperg_1F1_CF1_p_ser(a, b, x, &rap); double ra = 1.0 + x/a * rap; double Ma = GSL_SQRT_DBL_MIN; double Map1 = ra * Ma; double Mnp1 = Map1; double Mn = Ma; double Mnm1; gsl_sf_result Mn_true; int stat_Mt; double n; for(n=a; n>0.5; n -= 1.0) { Mnm1 = (n * Mnp1 - (2.0*n-b+x) * Mn) / (b-n); Mnp1 = Mn; Mn = Mnm1; } stat_Mt = hyperg_1F1_small_a_bgt0(n, b, x, &Mn_true); result->val = (Ma/Mn) * Mn_true.val; result->err = fabs(Ma/Mn) * Mn_true.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(a)+1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Mt, stat_CF1); } else if(b > a && b < 2*a + x && b > x) { /* Use the Gautschi series representation of * the continued fraction. Then recurse forward * to near the a=b line for normalization. This will * work for either sign of x, although we do need * to check for b > x, which is relevant when x is positive. */ gsl_sf_result Mn_true; int stat_Mt; double rap; int stat_CF1 = hyperg_1F1_CF1_p_ser(a, b, x, &rap); double ra = 1.0 + x/a * rap; double Ma = GSL_SQRT_DBL_MIN; double Mnm1 = Ma; double Mn = ra * Mnm1; double Mnp1; double n; for(n=a+1.0; nval = Ma/Mn * Mn_true.val; result->err = fabs(Ma/Mn) * Mn_true.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(b-a)+1.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Mt, stat_CF1); } else if(x >= 0.0) { if(b < a) { /* Forward recursion on a from a=b+eps-1,b+eps. */ double N = floor(a-b); double eps = a - b - N; gsl_sf_result r_M0; gsl_sf_result r_M1; int stat_0 = hyperg_1F1_beps_bgt0(eps-1.0, b, x, &r_M0); int stat_1 = hyperg_1F1_beps_bgt0(eps, b, x, &r_M1); double M0 = r_M0.val; double M1 = r_M1.val; double Mam1 = M0; double Ma = M1; double Map1; double ap; double start_pair = fabs(M0) + fabs(M1); double minim_pair = GSL_DBL_MAX; double pair_ratio; double rat_0 = fabs(r_M0.err/r_M0.val); double rat_1 = fabs(r_M1.err/r_M1.val); for(ap=b+eps; apval = Ma; result->err = 2.0 * (rat_0 + rat_1 + GSL_DBL_EPSILON) * (fabs(b-a)+1.0) * fabs(Ma); result->err += 2.0 * (rat_0 + rat_1) * pair_ratio*pair_ratio * fabs(Ma); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Ma); return GSL_ERROR_SELECT_2(stat_0, stat_1); } else { /* b > a * b < 2a + x * b <= x * * Recurse forward on a from a=eps,eps+1. */ double eps = a - floor(a); gsl_sf_result r_Mnm1; gsl_sf_result r_Mn; int stat_0 = hyperg_1F1_small_a_bgt0(eps, b, x, &r_Mnm1); int stat_1 = hyperg_1F1_small_a_bgt0(eps+1.0, b, x, &r_Mn); double Mnm1 = r_Mnm1.val; double Mn = r_Mn.val; double Mnp1; double n; double start_pair = fabs(Mn) + fabs(Mnm1); double minim_pair = GSL_DBL_MAX; double pair_ratio; double rat_0 = fabs(r_Mnm1.err/r_Mnm1.val); double rat_1 = fabs(r_Mn.err/r_Mn.val); for(n=eps+1.0; nval = Mn; result->err = 2.0 * (rat_0 + rat_1 + GSL_DBL_EPSILON) * (fabs(a)+1.0) * fabs(Mn); result->err += 2.0 * (rat_0 + rat_1) * pair_ratio*pair_ratio * fabs(Mn); result->err += 2.0 * GSL_DBL_EPSILON * fabs(Mn); return GSL_ERROR_SELECT_2(stat_0, stat_1); } } else { /* x < 0 * b < a */ if(a <= 0.5*(b-x) || a >= -x) { /* Recurse down in b, from near the a=b line, b=a+eps,a+eps-1. */ double N = floor(a - b); double eps = 1.0 + N - a + b; gsl_sf_result r_Manp1; gsl_sf_result r_Man; int stat_0 = hyperg_1F1_beps_bgt0(-eps, a+eps, x, &r_Manp1); int stat_1 = hyperg_1F1_beps_bgt0(1.0-eps, a+eps-1.0, x, &r_Man); double Manp1 = r_Manp1.val; double Man = r_Man.val; double Manm1; double n; double start_pair = fabs(Manp1) + fabs(Man); double minim_pair = GSL_DBL_MAX; double pair_ratio; double rat_0 = fabs(r_Manp1.err/r_Manp1.val); double rat_1 = fabs(r_Man.err/r_Man.val); for(n=a+eps-1.0; n>b+0.1; n -= 1.0) { Manm1 = (-n*(1-n-x)*Man - x*(n-a)*Manp1)/(n*(n-1.0)); Manp1 = Man; Man = Manm1; minim_pair = GSL_MIN_DBL(fabs(Manp1) + fabs(Man), minim_pair); } /* FIXME: this is a nasty little hack; there is some (transient?) instability in this recurrence for some values. I can tell when it happens, which is when this pair_ratio is large. But I do not know how to measure the error in terms of it. I guessed quadratic below, but it is probably worse than that. */ pair_ratio = start_pair/minim_pair; result->val = Man; result->err = 2.0 * (rat_0 + rat_1 + GSL_DBL_EPSILON) * (fabs(b-a)+1.0) * fabs(Man); result->err *= pair_ratio*pair_ratio + 1.0; return GSL_ERROR_SELECT_2(stat_0, stat_1); } else { /* Pick a0 such that b ~= 2a0 + x, then * recurse down in b from a0,a0 to determine * the values near the line b=2a+x. Then recurse * forward on a from a0. */ double epsa = a - floor(a); double a0 = floor(0.5*(b-x)) + epsa; double N = floor(a0 - b); double epsb = 1.0 + N - a0 + b; double Ma0b; double Ma0bp1; double Ma0p1b; int stat_a0; double Mnm1; double Mn; double Mnp1; double n; double err_rat; { gsl_sf_result r_Ma0np1; gsl_sf_result r_Ma0n; int stat_0 = hyperg_1F1_beps_bgt0(-epsb, a0+epsb, x, &r_Ma0np1); int stat_1 = hyperg_1F1_beps_bgt0(1.0-epsb, a0+epsb-1.0, x, &r_Ma0n); double Ma0np1 = r_Ma0np1.val; double Ma0n = r_Ma0n.val; double Ma0nm1; err_rat = fabs(r_Ma0np1.err/r_Ma0np1.val) + fabs(r_Ma0n.err/r_Ma0n.val); for(n=a0+epsb-1.0; n>b+0.1; n -= 1.0) { Ma0nm1 = (-n*(1-n-x)*Ma0n - x*(n-a0)*Ma0np1)/(n*(n-1.0)); Ma0np1 = Ma0n; Ma0n = Ma0nm1; } Ma0bp1 = Ma0np1; Ma0b = Ma0n; Ma0p1b = (b*(a0+x)*Ma0b+x*(a0-b)*Ma0bp1)/(a0*b); /* right-down hook */ stat_a0 = GSL_ERROR_SELECT_2(stat_0, stat_1); } /* Initialise the recurrence correctly BJG */ if (a0 >= a - 0.1) { Mn = Ma0b; } else if (a0 + 1>= a - 0.1) { Mn = Ma0p1b; } else { Mnm1 = Ma0b; Mn = Ma0p1b; for(n=a0+1.0; nval = Mn; result->err = (err_rat + GSL_DBL_EPSILON) * (fabs(b-a)+1.0) * fabs(Mn); return stat_a0; } } } /* Assumes b != integer * Assumes a != integer when x > 0 * Assumes b-a != neg integer when x < 0 */ static int hyperg_1F1_ab_neg(const double a, const double b, const double x, gsl_sf_result * result) { const double bma = b - a; const double abs_x = fabs(x); const double abs_a = fabs(a); const double abs_b = fabs(b); const double size_a = GSL_MAX(abs_a, 1.0); const double size_b = GSL_MAX(abs_b, 1.0); const int bma_integer = ( bma - floor(bma+0.5) < _1F1_INT_THRESHOLD ); if( (abs_a < 10.0 && abs_b < 10.0 && abs_x < 5.0) || (b > 0.8*GSL_MAX(fabs(a),1.0)*fabs(x)) ) { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if( x > 0.0 && size_b > size_a && size_a*log(M_E*x/size_b) < GSL_LOG_DBL_EPSILON+7.0 ) { /* Series terms are positive definite up until * there is a sign change. But by then the * terms are small due to the last condition. */ return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } else if( (abs_x < 5.0 && fabs(bma) < 10.0 && abs_b < 10.0) || (b > 0.8*GSL_MAX_DBL(fabs(bma),1.0)*abs_x) ) { /* Use Kummer transformation to render series safe. */ gsl_sf_result Kummer_1F1; int stat_K = gsl_sf_hyperg_1F1_series_e(bma, b, -x, &Kummer_1F1); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if( x < -30.0 && GSL_MAX_DBL(fabs(a),1.0)*GSL_MAX_DBL(fabs(1.0+a-b),1.0) < 0.99*fabs(x) ) { /* Large negative x asymptotic. * Note that we do not check if b-a is a negative integer. */ return hyperg_1F1_asymp_negx(a, b, x, result); } else if( x > 100.0 && GSL_MAX_DBL(fabs(bma),1.0)*GSL_MAX_DBL(fabs(1.0-a),1.0) < 0.99*fabs(x) ) { /* Large positive x asymptotic. * Note that we do not check if a is a negative integer. */ return hyperg_1F1_asymp_posx(a, b, x, result); } else if(x > 0.0 && !(bma_integer && bma > 0.0)) { return hyperg_1F1_U(a, b, x, result); } else { /* FIXME: if all else fails, try the series... BJG */ if (x < 0.0) { /* Apply Kummer Transformation */ int status = gsl_sf_hyperg_1F1_series_e(b-a, b, -x, result); double K_factor = exp(x); result->val *= K_factor; result->err *= K_factor; return status; } else { int status = gsl_sf_hyperg_1F1_series_e(a, b, x, result); return status; } /* Sadness... */ /* result->val = 0.0; */ /* result->err = 0.0; */ /* GSL_ERROR ("error", GSL_EUNIMPL); */ } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_hyperg_1F1_int_e(const int a, const int b, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(a == b) { return gsl_sf_exp_e(x, result); } else if(b == 0) { DOMAIN_ERROR(result); } else if(a == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(b < 0 && (a < b || a > 0)) { /* Standard domain error due to singularity. */ DOMAIN_ERROR(result); } else if(x > 100.0 && GSL_MAX_DBL(1.0,fabs(b-a))*GSL_MAX_DBL(1.0,fabs(1-a)) < 0.5 * x) { /* x -> +Inf asymptotic */ return hyperg_1F1_asymp_posx(a, b, x, result); } else if(x < -100.0 && GSL_MAX_DBL(1.0,fabs(a))*GSL_MAX_DBL(1.0,fabs(1+a-b)) < 0.5 * fabs(x)) { /* x -> -Inf asymptotic */ return hyperg_1F1_asymp_negx(a, b, x, result); } else if(a < 0 && b < 0) { return hyperg_1F1_ab_negint(a, b, x, result); } else if(a < 0 && b > 0) { /* Use Kummer to reduce it to the positive integer case. * Note that b > a, strictly, since we already trapped b = a. */ gsl_sf_result Kummer_1F1; int stat_K = hyperg_1F1_ab_posint(b-a, b, -x, &Kummer_1F1); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else { /* a > 0 and b > 0 */ return hyperg_1F1_ab_posint(a, b, x, result); } } int gsl_sf_hyperg_1F1_e(const double a, const double b, const double x, gsl_sf_result * result ) { const double bma = b - a; const double rinta = floor(a + 0.5); const double rintb = floor(b + 0.5); const double rintbma = floor(bma + 0.5); const int a_integer = ( fabs(a-rinta) < _1F1_INT_THRESHOLD && rinta > INT_MIN && rinta < INT_MAX ); const int b_integer = ( fabs(b-rintb) < _1F1_INT_THRESHOLD && rintb > INT_MIN && rintb < INT_MAX ); const int bma_integer = ( fabs(bma-rintbma) < _1F1_INT_THRESHOLD && rintbma > INT_MIN && rintbma < INT_MAX ); const int b_neg_integer = ( b < -0.1 && b_integer ); const int a_neg_integer = ( a < -0.1 && a_integer ); const int bma_neg_integer = ( bma < -0.1 && bma_integer ); /* CHECK_POINTER(result) */ if(x == 0.0) { /* Testing for this before testing a and b * is somewhat arbitrary. The result is that * we have 1F1(a,0,0) = 1. */ result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(b == 0.0) { DOMAIN_ERROR(result); } else if(a == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(a == b) { /* case: a==b; exp(x) * It's good to test exact equality now. * We also test approximate equality later. */ return gsl_sf_exp_e(x, result); } else if(fabs(b) < _1F1_INT_THRESHOLD && fabs(a) < _1F1_INT_THRESHOLD) { /* a and b near zero: 1 + a/b (exp(x)-1) */ /* Note that neither a nor b is zero, since * we eliminated that with the above tests. */ gsl_sf_result exm1; int stat_e = gsl_sf_expm1_e(x, &exm1); double sa = ( a > 0.0 ? 1.0 : -1.0 ); double sb = ( b > 0.0 ? 1.0 : -1.0 ); double lnab = log(fabs(a/b)); /* safe */ gsl_sf_result hx; int stat_hx = gsl_sf_exp_mult_err_e(lnab, GSL_DBL_EPSILON * fabs(lnab), sa * sb * exm1.val, exm1.err, &hx); result->val = (hx.val == GSL_DBL_MAX ? hx.val : 1.0 + hx.val); /* FIXME: excessive paranoia ? what is DBL_MAX+1 ?*/ result->err = hx.err; return GSL_ERROR_SELECT_2(stat_hx, stat_e); } else if (fabs(b) < _1F1_INT_THRESHOLD && fabs(x*a) < 1) { /* b near zero and a not near zero */ const double m_arg = 1.0/(0.5*b); gsl_sf_result F_renorm; int stat_F = hyperg_1F1_renorm_b0(a, x, &F_renorm); int stat_m = gsl_sf_multiply_err_e(m_arg, 2.0 * GSL_DBL_EPSILON * m_arg, 0.5*F_renorm.val, 0.5*F_renorm.err, result); return GSL_ERROR_SELECT_2(stat_m, stat_F); } else if(a_integer && b_integer) { /* Check for reduction to the integer case. * Relies on the arbitrary "near an integer" test. */ return gsl_sf_hyperg_1F1_int_e((int)rinta, (int)rintb, x, result); } else if(b_neg_integer && !(a_neg_integer && a > b)) { /* Standard domain error due to * uncancelled singularity. */ DOMAIN_ERROR(result); } else if(a_neg_integer) { return hyperg_1F1_a_negint_lag((int)rinta, b, x, result); } else if(b > 0.0) { if(-1.0 <= a && a <= 1.0) { /* Handle small a explicitly. */ return hyperg_1F1_small_a_bgt0(a, b, x, result); } else if(bma_neg_integer) { /* Catch this now, to avoid problems in the * generic evaluation code. */ gsl_sf_result Kummer_1F1; int stat_K = hyperg_1F1_a_negint_lag((int)rintbma, b, -x, &Kummer_1F1); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if(a < 0.0 && fabs(x) < 100.0) { /* Use Kummer to reduce it to the generic positive case. * Note that b > a, strictly, since we already trapped b = a. * Also b-(b-a)=a, and a is not a negative integer here, * so the generic evaluation is safe. */ gsl_sf_result Kummer_1F1; int stat_K = hyperg_1F1_ab_pos(b-a, b, -x, &Kummer_1F1); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), Kummer_1F1.val, Kummer_1F1.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if (a > 0) { /* a > 0.0 */ return hyperg_1F1_ab_pos(a, b, x, result); } else { return gsl_sf_hyperg_1F1_series_e(a, b, x, result); } } else { /* b < 0.0 */ if(bma_neg_integer && x < 0.0) { /* Handle this now to prevent problems * in the generic evaluation. */ gsl_sf_result K; int stat_K; int stat_e; if(a < 0.0) { /* Kummer transformed version of safe polynomial. * The condition a < 0 is equivalent to b < b-a, * which is the condition required for the series * to be positive definite here. */ stat_K = hyperg_1F1_a_negint_poly((int)rintbma, b, -x, &K); } else { /* Generic eval for negative integer a. */ stat_K = hyperg_1F1_a_negint_lag((int)rintbma, b, -x, &K); } stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), K.val, K.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else if(a > 0.0) { /* Use Kummer to reduce it to the generic negative case. */ gsl_sf_result K; int stat_K = hyperg_1F1_ab_neg(b-a, b, -x, &K); int stat_e = gsl_sf_exp_mult_err_e(x, GSL_DBL_EPSILON * fabs(x), K.val, K.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K); } else { return hyperg_1F1_ab_neg(a, b, x, result); } } } #if 0 /* Luke in the canonical case. */ if(x < 0.0 && !a_neg_integer && !bma_neg_integer) { double prec; return hyperg_1F1_luke(a, b, x, result, &prec); } /* Luke with Kummer transformation. */ if(x > 0.0 && !a_neg_integer && !bma_neg_integer) { double prec; double Kummer_1F1; double ex; int stat_F = hyperg_1F1_luke(b-a, b, -x, &Kummer_1F1, &prec); int stat_e = gsl_sf_exp_e(x, &ex); if(stat_F == GSL_SUCCESS && stat_e == GSL_SUCCESS) { double lnr = log(fabs(Kummer_1F1)) + x; if(lnr < GSL_LOG_DBL_MAX) { *result = ex * Kummer_1F1; return GSL_SUCCESS; } else { *result = GSL_POSINF; GSL_ERROR ("overflow", GSL_EOVRFLW); } } else if(stat_F != GSL_SUCCESS) { *result = 0.0; return stat_F; } else { *result = 0.0; return stat_e; } } #endif /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_hyperg_1F1_int(const int m, const int n, double x) { EVAL_RESULT(gsl_sf_hyperg_1F1_int_e(m, n, x, &result)); } double gsl_sf_hyperg_1F1(double a, double b, double x) { EVAL_RESULT(gsl_sf_hyperg_1F1_e(a, b, x, &result)); } sources_5316/external/gsl/gsl_cblas__strmm.c0000664000176700017670000000072511723710247020022 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_strmm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const float alpha, const float *A, const int lda, float *B, const int ldb) { #define BASE float #include "gsl_cblas__source_trmm_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__scnrm2.c0000664000176700017670000000032511723710247020060 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" float cblas_scnrm2 (const int N, const void *X, const int incX) { #define BASE float #include "gsl_cblas__source_nrm2_c.h" #undef BASE } sources_5316/external/gsl/gsl_cdf__rat_eval.h0000664000176700017670000000055411705263724020135 0ustar paulpaulstatic double rat_eval (const double a[], const size_t na, const double b[], const size_t nb, const double x) { size_t i, j; double u, v, r; u = a[na - 1]; for (i = na - 1; i > 0; i--) { u = x * u + a[i - 1]; } v = b[nb - 1]; for (j = nb - 1; j > 0; j--) { v = x * v + b[j - 1]; } r = u / v; return r; } sources_5316/external/gsl/gsl_err__message.c0000664000176700017670000000230411723710247020003 0ustar paulpaul/* err/message.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include "gsl_errno.h" #include "gsl_message.h" unsigned int gsl_message_mask = GSL_MESSAGE_MASK; void gsl_message (const char * reason, const char * file, int line, unsigned int mask) { if (mask & gsl_message_mask) { gsl_stream_printf ("MESSAGE", file, line, reason); } } sources_5316/external/gsl/gsl_sort__sortvec_source.c0000664000176700017670000000415711723710247021633 0ustar paulpaul/* * Implement Heap sort -- direct and indirect sorting * Based on descriptions in Sedgewick "Algorithms in C" * * Copyright (C) 1999 Thomas Walter * * 18 February 2000: Modified for GSL by Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ static inline void FUNCTION (my, downheap) (BASE * data, const size_t stride, const size_t N, size_t k); static inline void FUNCTION (my, downheap) (BASE * data, const size_t stride, const size_t N, size_t k) { BASE v = data[k * stride]; while (k <= N / 2) { size_t j = 2 * k; if (j < N && data[j * stride] < data[(j + 1) * stride]) { j++; } if (!(v < data[j * stride])) /* avoid infinite loop if nan */ { break; } data[k * stride] = data[j * stride]; k = j; } data[k * stride] = v; } void TYPE (gsl_sort) (BASE * data, const size_t stride, const size_t n) { size_t N; size_t k; if (n == 0) { return; /* No data to sort */ } /* We have n_data elements, last element is at 'n_data-1', first at '0' Set N to the last element number. */ N = n - 1; k = N / 2; k++; /* Compensate the first use of 'k--' */ do { k--; FUNCTION (my, downheap) (data, stride, N, k); } while (k > 0); while (N > 0) { /* first swap the elements */ BASE tmp = data[0 * stride]; data[0 * stride] = data[N * stride]; data[N * stride] = tmp; /* then process the heap */ N--; FUNCTION (my, downheap) (data, stride, N, 0); } } void TYPE (gsl_sort_vector) (TYPE (gsl_vector) * v) { TYPE (gsl_sort) (v->data, v->stride, v->size) ; } sources_5316/external/gsl/gsl_multiroots.h0000664000176700017670000001377011705263724017612 0ustar paulpaul/* multiroots/gsl_multiroots.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MULTIROOTS_H__ #define __GSL_MULTIROOTS_H__ #include #include "gsl_types.h" #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Definition of vector-valued functions with parameters based on gsl_vector */ struct gsl_multiroot_function_struct { int (* f) (const gsl_vector * x, void * params, gsl_vector * f); size_t n; void * params; }; typedef struct gsl_multiroot_function_struct gsl_multiroot_function ; #define GSL_MULTIROOT_FN_EVAL(F,x,y) (*((F)->f))(x,(F)->params,(y)) int gsl_multiroot_fdjacobian (gsl_multiroot_function * F, const gsl_vector * x, const gsl_vector * f, double epsrel, gsl_matrix * jacobian); typedef struct { const char *name; size_t size; int (*alloc) (void *state, size_t n); int (*set) (void *state, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx); int (*iterate) (void *state, gsl_multiroot_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx); void (*free) (void *state); } gsl_multiroot_fsolver_type; typedef struct { const gsl_multiroot_fsolver_type * type; gsl_multiroot_function * function ; gsl_vector * x ; gsl_vector * f ; gsl_vector * dx ; void *state; } gsl_multiroot_fsolver; gsl_multiroot_fsolver * gsl_multiroot_fsolver_alloc (const gsl_multiroot_fsolver_type * T, size_t n); void gsl_multiroot_fsolver_free (gsl_multiroot_fsolver * s); int gsl_multiroot_fsolver_set (gsl_multiroot_fsolver * s, gsl_multiroot_function * f, const gsl_vector * x); int gsl_multiroot_fsolver_iterate (gsl_multiroot_fsolver * s); const char * gsl_multiroot_fsolver_name (const gsl_multiroot_fsolver * s); gsl_vector * gsl_multiroot_fsolver_root (const gsl_multiroot_fsolver * s); gsl_vector * gsl_multiroot_fsolver_dx (const gsl_multiroot_fsolver * s); gsl_vector * gsl_multiroot_fsolver_f (const gsl_multiroot_fsolver * s); /* Definition of vector-valued functions and gradient with parameters based on gsl_vector */ struct gsl_multiroot_function_fdf_struct { int (* f) (const gsl_vector * x, void * params, gsl_vector * f); int (* df) (const gsl_vector * x, void * params, gsl_matrix * df); int (* fdf) (const gsl_vector * x, void * params, gsl_vector * f, gsl_matrix *df); size_t n; void * params; }; typedef struct gsl_multiroot_function_fdf_struct gsl_multiroot_function_fdf ; #define GSL_MULTIROOT_FN_EVAL_F(F,x,y) ((*((F)->f))(x,(F)->params,(y))) #define GSL_MULTIROOT_FN_EVAL_DF(F,x,dy) ((*((F)->df))(x,(F)->params,(dy))) #define GSL_MULTIROOT_FN_EVAL_F_DF(F,x,y,dy) ((*((F)->fdf))(x,(F)->params,(y),(dy))) typedef struct { const char *name; size_t size; int (*alloc) (void *state, size_t n); int (*set) (void *state, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); int (*iterate) (void *state, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); void (*free) (void *state); } gsl_multiroot_fdfsolver_type; typedef struct { const gsl_multiroot_fdfsolver_type * type; gsl_multiroot_function_fdf * fdf ; gsl_vector * x; gsl_vector * f; gsl_matrix * J; gsl_vector * dx; void *state; } gsl_multiroot_fdfsolver; gsl_multiroot_fdfsolver * gsl_multiroot_fdfsolver_alloc (const gsl_multiroot_fdfsolver_type * T, size_t n); int gsl_multiroot_fdfsolver_set (gsl_multiroot_fdfsolver * s, gsl_multiroot_function_fdf * fdf, const gsl_vector * x); int gsl_multiroot_fdfsolver_iterate (gsl_multiroot_fdfsolver * s); void gsl_multiroot_fdfsolver_free (gsl_multiroot_fdfsolver * s); const char * gsl_multiroot_fdfsolver_name (const gsl_multiroot_fdfsolver * s); gsl_vector * gsl_multiroot_fdfsolver_root (const gsl_multiroot_fdfsolver * s); gsl_vector * gsl_multiroot_fdfsolver_dx (const gsl_multiroot_fdfsolver * s); gsl_vector * gsl_multiroot_fdfsolver_f (const gsl_multiroot_fdfsolver * s); int gsl_multiroot_test_delta (const gsl_vector * dx, const gsl_vector * x, double epsabs, double epsrel); int gsl_multiroot_test_residual (const gsl_vector * f, double epsabs); GSL_VAR const gsl_multiroot_fsolver_type * gsl_multiroot_fsolver_dnewton; GSL_VAR const gsl_multiroot_fsolver_type * gsl_multiroot_fsolver_broyden; GSL_VAR const gsl_multiroot_fsolver_type * gsl_multiroot_fsolver_hybrid; GSL_VAR const gsl_multiroot_fsolver_type * gsl_multiroot_fsolver_hybrids; GSL_VAR const gsl_multiroot_fdfsolver_type * gsl_multiroot_fdfsolver_newton; GSL_VAR const gsl_multiroot_fdfsolver_type * gsl_multiroot_fdfsolver_gnewton; GSL_VAR const gsl_multiroot_fdfsolver_type * gsl_multiroot_fdfsolver_hybridj; GSL_VAR const gsl_multiroot_fdfsolver_type * gsl_multiroot_fdfsolver_hybridsj; __END_DECLS #endif /* __GSL_MULTIROOTS_H__ */ sources_5316/external/gsl/gsl_vector_ushort.h0000664000176700017670000001656111705263724020300 0ustar paulpaul/* vector/gsl_vector_ushort.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_USHORT_H__ #define __GSL_VECTOR_USHORT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_ushort.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; unsigned short *data; gsl_block_ushort *block; int owner; } gsl_vector_ushort; typedef struct { gsl_vector_ushort vector; } _gsl_vector_ushort_view; typedef _gsl_vector_ushort_view gsl_vector_ushort_view; typedef struct { gsl_vector_ushort vector; } _gsl_vector_ushort_const_view; typedef const _gsl_vector_ushort_const_view gsl_vector_ushort_const_view; /* Allocation */ gsl_vector_ushort *gsl_vector_ushort_alloc (const size_t n); gsl_vector_ushort *gsl_vector_ushort_calloc (const size_t n); gsl_vector_ushort *gsl_vector_ushort_alloc_from_block (gsl_block_ushort * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_ushort *gsl_vector_ushort_alloc_from_vector (gsl_vector_ushort * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_ushort_free (gsl_vector_ushort * v); /* Views */ _gsl_vector_ushort_view gsl_vector_ushort_view_array (unsigned short *v, size_t n); _gsl_vector_ushort_view gsl_vector_ushort_view_array_with_stride (unsigned short *base, size_t stride, size_t n); _gsl_vector_ushort_const_view gsl_vector_ushort_const_view_array (const unsigned short *v, size_t n); _gsl_vector_ushort_const_view gsl_vector_ushort_const_view_array_with_stride (const unsigned short *base, size_t stride, size_t n); _gsl_vector_ushort_view gsl_vector_ushort_subvector (gsl_vector_ushort *v, size_t i, size_t n); _gsl_vector_ushort_view gsl_vector_ushort_subvector_with_stride (gsl_vector_ushort *v, size_t i, size_t stride, size_t n); _gsl_vector_ushort_const_view gsl_vector_ushort_const_subvector (const gsl_vector_ushort *v, size_t i, size_t n); _gsl_vector_ushort_const_view gsl_vector_ushort_const_subvector_with_stride (const gsl_vector_ushort *v, size_t i, size_t stride, size_t n); /* Operations */ unsigned short gsl_vector_ushort_get (const gsl_vector_ushort * v, const size_t i); void gsl_vector_ushort_set (gsl_vector_ushort * v, const size_t i, unsigned short x); unsigned short *gsl_vector_ushort_ptr (gsl_vector_ushort * v, const size_t i); const unsigned short *gsl_vector_ushort_const_ptr (const gsl_vector_ushort * v, const size_t i); void gsl_vector_ushort_set_zero (gsl_vector_ushort * v); void gsl_vector_ushort_set_all (gsl_vector_ushort * v, unsigned short x); int gsl_vector_ushort_set_basis (gsl_vector_ushort * v, size_t i); int gsl_vector_ushort_fread (FILE * stream, gsl_vector_ushort * v); int gsl_vector_ushort_fwrite (FILE * stream, const gsl_vector_ushort * v); int gsl_vector_ushort_fscanf (FILE * stream, gsl_vector_ushort * v); int gsl_vector_ushort_fprintf (FILE * stream, const gsl_vector_ushort * v, const char *format); int gsl_vector_ushort_memcpy (gsl_vector_ushort * dest, const gsl_vector_ushort * src); int gsl_vector_ushort_reverse (gsl_vector_ushort * v); int gsl_vector_ushort_swap (gsl_vector_ushort * v, gsl_vector_ushort * w); int gsl_vector_ushort_swap_elements (gsl_vector_ushort * v, const size_t i, const size_t j); unsigned short gsl_vector_ushort_max (const gsl_vector_ushort * v); unsigned short gsl_vector_ushort_min (const gsl_vector_ushort * v); void gsl_vector_ushort_minmax (const gsl_vector_ushort * v, unsigned short * min_out, unsigned short * max_out); size_t gsl_vector_ushort_max_index (const gsl_vector_ushort * v); size_t gsl_vector_ushort_min_index (const gsl_vector_ushort * v); void gsl_vector_ushort_minmax_index (const gsl_vector_ushort * v, size_t * imin, size_t * imax); int gsl_vector_ushort_add (gsl_vector_ushort * a, const gsl_vector_ushort * b); int gsl_vector_ushort_sub (gsl_vector_ushort * a, const gsl_vector_ushort * b); int gsl_vector_ushort_mul (gsl_vector_ushort * a, const gsl_vector_ushort * b); int gsl_vector_ushort_div (gsl_vector_ushort * a, const gsl_vector_ushort * b); int gsl_vector_ushort_scale (gsl_vector_ushort * a, const double x); int gsl_vector_ushort_add_constant (gsl_vector_ushort * a, const double x); int gsl_vector_ushort_isnull (const gsl_vector_ushort * v); int gsl_vector_ushort_ispos (const gsl_vector_ushort * v); int gsl_vector_ushort_isneg (const gsl_vector_ushort * v); int gsl_vector_ushort_isnonneg (const gsl_vector_ushort * v); #ifdef HAVE_INLINE extern inline unsigned short gsl_vector_ushort_get (const gsl_vector_ushort * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_ushort_set (gsl_vector_ushort * v, const size_t i, unsigned short x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline unsigned short * gsl_vector_ushort_ptr (gsl_vector_ushort * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (unsigned short *) (v->data + i * v->stride); } extern inline const unsigned short * gsl_vector_ushort_const_ptr (const gsl_vector_ushort * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const unsigned short *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_USHORT_H__ */ sources_5316/external/gsl/gsl_cblas__zhpmv.c0000664000176700017670000000056411723710247020025 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zhpmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *Ap, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE double #include "gsl_cblas__source_hpmv.h" #undef BASE } sources_5316/external/gsl/gsl_integration__qk61.c0000664000176700017670000001117511723710247020702 0ustar paulpaul/* integration/qk61.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_integration.h" /* Gauss quadrature weights and kronrod quadrature abscissae and weights as evaluated with 80 decimal digit arithmetic by L. W. Fullerton, Bell Labs, Nov. 1981. */ static const double xgk[31] = /* abscissae of the 61-point kronrod rule */ { 0.999484410050490637571325895705811, 0.996893484074649540271630050918695, 0.991630996870404594858628366109486, 0.983668123279747209970032581605663, 0.973116322501126268374693868423707, 0.960021864968307512216871025581798, 0.944374444748559979415831324037439, 0.926200047429274325879324277080474, 0.905573307699907798546522558925958, 0.882560535792052681543116462530226, 0.857205233546061098958658510658944, 0.829565762382768397442898119732502, 0.799727835821839083013668942322683, 0.767777432104826194917977340974503, 0.733790062453226804726171131369528, 0.697850494793315796932292388026640, 0.660061064126626961370053668149271, 0.620526182989242861140477556431189, 0.579345235826361691756024932172540, 0.536624148142019899264169793311073, 0.492480467861778574993693061207709, 0.447033769538089176780609900322854, 0.400401254830394392535476211542661, 0.352704725530878113471037207089374, 0.304073202273625077372677107199257, 0.254636926167889846439805129817805, 0.204525116682309891438957671002025, 0.153869913608583546963794672743256, 0.102806937966737030147096751318001, 0.051471842555317695833025213166723, 0.000000000000000000000000000000000 }; /* xgk[1], xgk[3], ... abscissae of the 30-point gauss rule. xgk[0], xgk[2], ... abscissae to optimally extend the 30-point gauss rule */ static const double wg[15] = /* weights of the 30-point gauss rule */ { 0.007968192496166605615465883474674, 0.018466468311090959142302131912047, 0.028784707883323369349719179611292, 0.038799192569627049596801936446348, 0.048402672830594052902938140422808, 0.057493156217619066481721689402056, 0.065974229882180495128128515115962, 0.073755974737705206268243850022191, 0.080755895229420215354694938460530, 0.086899787201082979802387530715126, 0.092122522237786128717632707087619, 0.096368737174644259639468626351810, 0.099593420586795267062780282103569, 0.101762389748405504596428952168554, 0.102852652893558840341285636705415 }; static const double wgk[31] = /* weights of the 61-point kronrod rule */ { 0.001389013698677007624551591226760, 0.003890461127099884051267201844516, 0.006630703915931292173319826369750, 0.009273279659517763428441146892024, 0.011823015253496341742232898853251, 0.014369729507045804812451432443580, 0.016920889189053272627572289420322, 0.019414141193942381173408951050128, 0.021828035821609192297167485738339, 0.024191162078080601365686370725232, 0.026509954882333101610601709335075, 0.028754048765041292843978785354334, 0.030907257562387762472884252943092, 0.032981447057483726031814191016854, 0.034979338028060024137499670731468, 0.036882364651821229223911065617136, 0.038678945624727592950348651532281, 0.040374538951535959111995279752468, 0.041969810215164246147147541285970, 0.043452539701356069316831728117073, 0.044814800133162663192355551616723, 0.046059238271006988116271735559374, 0.047185546569299153945261478181099, 0.048185861757087129140779492298305, 0.049055434555029778887528165367238, 0.049795683427074206357811569379942, 0.050405921402782346840893085653585, 0.050881795898749606492297473049805, 0.051221547849258772170656282604944, 0.051426128537459025933862879215781, 0.051494729429451567558340433647099 }; void gsl_integration_qk61 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc) { double fv1[31], fv2[31]; gsl_integration_qk (31, xgk, wg, wgk, fv1, fv2, f, a, b, result, abserr, resabs, resasc); } sources_5316/external/gsl/gsl_eigen__gen.c0000664000176700017670000016621111723710247017437 0ustar paulpaul/* eigen/gen.c * * Copyright (C) 2006, 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl__config.h" #include "gsl_eigen.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_blas.h" #include "gsl_vector.h" #include "gsl_vector_complex.h" #include "gsl_matrix.h" /* * This module computes the eigenvalues of a real generalized * eigensystem A x = \lambda B x. Left and right Schur vectors * are optionally computed as well. * * Based on the algorithm from Moler and Stewart * [1] C. Moler, G. Stewart, "An Algorithm for Generalized Matrix * Eigenvalue Problems", SIAM J. Numer. Anal., Vol 10, No 2, 1973. * * This algorithm is also described in the book * [2] Golub & Van Loan, "Matrix Computations" (3rd ed), algorithm 7.7.3 * * This file contains routines based on original code from LAPACK * which is distributed under the modified BSD license. */ #define GEN_ESHIFT_COEFF (1.736) static void gen_schur_decomp(gsl_matrix *H, gsl_matrix *R, gsl_vector_complex *alpha, gsl_vector *beta, gsl_eigen_gen_workspace *w); static inline int gen_qzstep(gsl_matrix *H, gsl_matrix *R, gsl_eigen_gen_workspace *w); static inline void gen_qzstep_d(gsl_matrix *H, gsl_matrix *R, gsl_eigen_gen_workspace *w); static void gen_tri_split_top(gsl_matrix *H, gsl_matrix *R, gsl_eigen_gen_workspace *w); static inline void gen_tri_chase_zero(gsl_matrix *H, gsl_matrix *R, size_t q, gsl_eigen_gen_workspace *w); static inline void gen_tri_zero_H(gsl_matrix *H, gsl_matrix *R, gsl_eigen_gen_workspace *w); static inline size_t gen_search_small_elements(gsl_matrix *H, gsl_matrix *R, int *flag, gsl_eigen_gen_workspace *w); static int gen_schur_standardize1(gsl_matrix *A, gsl_matrix *B, double *alphar, double *beta, gsl_eigen_gen_workspace *w); static int gen_schur_standardize2(gsl_matrix *A, gsl_matrix *B, gsl_complex *alpha1, gsl_complex *alpha2, double *beta1, double *beta2, gsl_eigen_gen_workspace *w); static int gen_compute_eigenvals(gsl_matrix *A, gsl_matrix *B, gsl_complex *alpha1, gsl_complex *alpha2, double *beta1, double *beta2); static void gen_store_eigval1(const gsl_matrix *H, const double a, const double b, gsl_vector_complex *alpha, gsl_vector *beta, gsl_eigen_gen_workspace *w); static void gen_store_eigval2(const gsl_matrix *H, const gsl_complex *alpha1, const double beta1, const gsl_complex *alpha2, const double beta2, gsl_vector_complex *alpha, gsl_vector *beta, gsl_eigen_gen_workspace *w); static inline size_t gen_get_submatrix(const gsl_matrix *A, const gsl_matrix *B); /*FIX**/ inline static double normF (gsl_matrix * A); inline static void create_givens (const double a, const double b, double *c, double *s); /* gsl_eigen_gen_alloc() Allocate a workspace for solving the generalized eigenvalue problem. The size of this workspace is O(n) Inputs: n - size of matrices Return: pointer to workspace */ gsl_eigen_gen_workspace * gsl_eigen_gen_alloc(const size_t n) { gsl_eigen_gen_workspace *w; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = calloc (1, sizeof (gsl_eigen_gen_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->size = n; w->max_iterations = 30 * n; w->n_evals = 0; w->n_iter = 0; w->needtop = 0; w->atol = 0.0; w->btol = 0.0; w->ascale = 0.0; w->bscale = 0.0; w->eshift = 0.0; w->H = NULL; w->R = NULL; w->compute_s = 0; w->compute_t = 0; w->Q = NULL; w->Z = NULL; w->work = gsl_vector_alloc(n); if (w->work == 0) { gsl_eigen_gen_free(w); GSL_ERROR_NULL ("failed to allocate space for additional workspace", GSL_ENOMEM); } return (w); } /* gsl_eigen_gen_alloc() */ /* gsl_eigen_gen_free() Free workspace w */ void gsl_eigen_gen_free (gsl_eigen_gen_workspace * w) { if (w->work) gsl_vector_free(w->work); free(w); } /* gsl_eigen_gen_free() */ /* gsl_eigen_gen_params() Set parameters which define how we solve the eigenvalue problem Inputs: compute_s - 1 if we want to compute S, 0 if not compute_t - 1 if we want to compute T, 0 if not balance - 1 if we want to balance matrices, 0 if not w - gen workspace Return: none */ void gsl_eigen_gen_params (const int compute_s, const int compute_t, const int balance, gsl_eigen_gen_workspace *w) { w->compute_s = compute_s; w->compute_t = compute_t; } /* gsl_eigen_gen_params() */ /* gsl_eigen_gen() Solve the generalized eigenvalue problem A x = \lambda B x for the eigenvalues \lambda. Inputs: A - general real matrix B - general real matrix alpha - where to store eigenvalue numerators beta - where to store eigenvalue denominators w - workspace Return: success or error */ int gsl_eigen_gen (gsl_matrix * A, gsl_matrix * B, gsl_vector_complex * alpha, gsl_vector * beta, gsl_eigen_gen_workspace * w) { const size_t N = A->size1; /* check matrix and vector sizes */ if (N != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if ((N != B->size1) || (N != B->size2)) { GSL_ERROR ("B matrix dimensions must match A", GSL_EBADLEN); } else if (alpha->size != N || beta->size != N) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (w->size != N) { GSL_ERROR ("matrix size does not match workspace", GSL_EBADLEN); } else { double anorm, bnorm; /* compute the Hessenberg-Triangular reduction of (A, B) */ gsl_linalg_hesstri_decomp(A, B, w->Q, w->Z, w->work); /* save pointers to original matrices */ w->H = A; w->R = B; w->n_evals = 0; w->n_iter = 0; w->eshift = 0.0; /* determine if we need to compute top indices in QZ step */ w->needtop = w->Q != 0 || w->Z != 0 || w->compute_t || w->compute_s; /* compute matrix norms */ anorm = normF(A); bnorm = normF(B); /* compute tolerances and scaling factors */ w->atol = GSL_MAX(GSL_DBL_MIN, GSL_DBL_EPSILON * anorm); w->btol = GSL_MAX(GSL_DBL_MIN, GSL_DBL_EPSILON * bnorm); w->ascale = 1.0 / GSL_MAX(GSL_DBL_MIN, anorm); w->bscale = 1.0 / GSL_MAX(GSL_DBL_MIN, bnorm); /* compute the generalized Schur decomposition and eigenvalues */ gen_schur_decomp(A, B, alpha, beta, w); if (w->n_evals != N) return GSL_EMAXITER; return GSL_SUCCESS; } } /* gsl_eigen_gen() */ /* gsl_eigen_gen_QZ() Solve the generalized eigenvalue problem A x = \lambda B x for the eigenvalues \lambda. Optionally compute left and/or right Schur vectors Q and Z which satisfy: A = Q S Z^t B = Q T Z^t where (S, T) is the generalized Schur form of (A, B) Inputs: A - general real matrix B - general real matrix alpha - where to store eigenvalue numerators beta - where to store eigenvalue denominators Q - if non-null, where to store left Schur vectors Z - if non-null, where to store right Schur vectors w - workspace Return: success or error */ int gsl_eigen_gen_QZ (gsl_matrix * A, gsl_matrix * B, gsl_vector_complex * alpha, gsl_vector * beta, gsl_matrix * Q, gsl_matrix * Z, gsl_eigen_gen_workspace * w) { if (Q && (A->size1 != Q->size1 || A->size1 != Q->size2)) { GSL_ERROR("Q matrix has wrong dimensions", GSL_EBADLEN); } else if (Z && (A->size1 != Z->size1 || A->size1 != Z->size2)) { GSL_ERROR("Z matrix has wrong dimensions", GSL_EBADLEN); } else { int s; w->Q = Q; w->Z = Z; s = gsl_eigen_gen(A, B, alpha, beta, w); w->Q = NULL; w->Z = NULL; return s; } } /* gsl_eigen_gen_QZ() */ /******************************************** * INTERNAL ROUTINES * ********************************************/ /* gen_schur_decomp() Compute the generalized Schur decomposition of the matrix pencil (H, R) which is in Hessenberg-Triangular form Inputs: H - upper hessenberg matrix R - upper triangular matrix alpha - (output) where to store eigenvalue numerators beta - (output) where to store eigenvalue denominators w - workspace Return: none Notes: 1) w->n_evals is updated to keep track of how many eigenvalues are found */ static void gen_schur_decomp(gsl_matrix *H, gsl_matrix *R, gsl_vector_complex *alpha, gsl_vector *beta, gsl_eigen_gen_workspace *w) { size_t N; gsl_matrix_view h, r; gsl_matrix_view vh, vr; size_t q; /* index of small subdiagonal element */ gsl_complex z1, z2; /* complex values */ double a, b; int s; int flag; N = H->size1; h = gsl_matrix_submatrix(H, 0, 0, N, N); r = gsl_matrix_submatrix(R, 0, 0, N, N); while ((N > 1) && (w->n_iter)++ < w->max_iterations) { q = gen_search_small_elements(&h.matrix, &r.matrix, &flag, w); if (flag == 0) { /* no small elements found - do a QZ sweep */ s = gen_qzstep(&h.matrix, &r.matrix, w); if (s == GSL_CONTINUE) { /* * (h, r) is a 2-by-2 block with complex eigenvalues - * standardize and read off eigenvalues */ s = gen_schur_standardize2(&h.matrix, &r.matrix, &z1, &z2, &a, &b, w); if (s != GSL_SUCCESS) { /* * if we get here, then the standardization process * perturbed the eigenvalues onto the real line - * continue QZ iteration to break them into 1-by-1 * blocks */ continue; } gen_store_eigval2(&h.matrix, &z1, a, &z2, b, alpha, beta, w); N = 0; } /* if (s) */ continue; } /* if (flag == 0) */ else if (flag == 2) { if (q == 0) { /* * the leading element of R is zero, split off a block * at the top */ gen_tri_split_top(&h.matrix, &r.matrix, w); } else { /* * we found a small element on the diagonal of R - chase the * zero to the bottom of the active block and then zero * H(n, n - 1) to split off a 1-by-1 block */ if (q != N - 1) gen_tri_chase_zero(&h.matrix, &r.matrix, q, w); /* now zero H(n, n - 1) */ gen_tri_zero_H(&h.matrix, &r.matrix, w); } /* continue so the next iteration detects the zero in H */ continue; } /* * a small subdiagonal element of H was found - one or two * eigenvalues have converged or the matrix has split into * two smaller matrices */ if (q == (N - 1)) { /* * the last subdiagonal element of the hessenberg matrix is 0 - * H_{NN} / R_{NN} is a real eigenvalue - standardize so * R_{NN} > 0 */ vh = gsl_matrix_submatrix(&h.matrix, q, q, 1, 1); vr = gsl_matrix_submatrix(&r.matrix, q, q, 1, 1); gen_schur_standardize1(&vh.matrix, &vr.matrix, &a, &b, w); gen_store_eigval1(&vh.matrix, a, b, alpha, beta, w); --N; h = gsl_matrix_submatrix(&h.matrix, 0, 0, N, N); r = gsl_matrix_submatrix(&r.matrix, 0, 0, N, N); } else if (q == (N - 2)) { /* bottom right 2-by-2 block may have converged */ vh = gsl_matrix_submatrix(&h.matrix, q, q, 2, 2); vr = gsl_matrix_submatrix(&r.matrix, q, q, 2, 2); s = gen_schur_standardize2(&vh.matrix, &vr.matrix, &z1, &z2, &a, &b, w); if (s != GSL_SUCCESS) { /* * this 2-by-2 block contains real eigenvalues that * have not yet separated into 1-by-1 blocks - * recursively call gen_schur_decomp() to finish off * this block */ gen_schur_decomp(&vh.matrix, &vr.matrix, alpha, beta, w); } else { /* we got 2 complex eigenvalues */ gen_store_eigval2(&vh.matrix, &z1, a, &z2, b, alpha, beta, w); } N -= 2; h = gsl_matrix_submatrix(&h.matrix, 0, 0, N, N); r = gsl_matrix_submatrix(&r.matrix, 0, 0, N, N); } else if (q == 1) { /* H_{11} / R_{11} is an eigenvalue */ vh = gsl_matrix_submatrix(&h.matrix, 0, 0, 1, 1); vr = gsl_matrix_submatrix(&r.matrix, 0, 0, 1, 1); gen_schur_standardize1(&vh.matrix, &vr.matrix, &a, &b, w); gen_store_eigval1(&vh.matrix, a, b, alpha, beta, w); --N; h = gsl_matrix_submatrix(&h.matrix, 1, 1, N, N); r = gsl_matrix_submatrix(&r.matrix, 1, 1, N, N); } else if (q == 2) { /* upper left 2-by-2 block may have converged */ vh = gsl_matrix_submatrix(&h.matrix, 0, 0, 2, 2); vr = gsl_matrix_submatrix(&r.matrix, 0, 0, 2, 2); s = gen_schur_standardize2(&vh.matrix, &vr.matrix, &z1, &z2, &a, &b, w); if (s != GSL_SUCCESS) { /* * this 2-by-2 block contains real eigenvalues that * have not yet separated into 1-by-1 blocks - * recursively call gen_schur_decomp() to finish off * this block */ gen_schur_decomp(&vh.matrix, &vr.matrix, alpha, beta, w); } else { /* we got 2 complex eigenvalues */ gen_store_eigval2(&vh.matrix, &z1, a, &z2, b, alpha, beta, w); } N -= 2; h = gsl_matrix_submatrix(&h.matrix, 2, 2, N, N); r = gsl_matrix_submatrix(&r.matrix, 2, 2, N, N); } else { /* * There is a zero element on the subdiagonal somewhere * in the middle of the matrix - we can now operate * separately on the two submatrices split by this * element. q is the row index of the zero element. */ /* operate on lower right (N - q)-by-(N - q) block first */ vh = gsl_matrix_submatrix(&h.matrix, q, q, N - q, N - q); vr = gsl_matrix_submatrix(&r.matrix, q, q, N - q, N - q); gen_schur_decomp(&vh.matrix, &vr.matrix, alpha, beta, w); /* operate on upper left q-by-q block */ vh = gsl_matrix_submatrix(&h.matrix, 0, 0, q, q); vr = gsl_matrix_submatrix(&r.matrix, 0, 0, q, q); gen_schur_decomp(&vh.matrix, &vr.matrix, alpha, beta, w); N = 0; } } /* while ((N > 1) && (w->n_iter)++ < w->max_iterations) */ /* handle special case of N = 1 */ if (N == 1) { gen_schur_standardize1(&h.matrix, &r.matrix, &a, &b, w); gen_store_eigval1(&h.matrix, a, b, alpha, beta, w); } } /* gen_schur_decomp() */ /* gen_qzstep() This routine determines what type of QZ step to perform on the generalized matrix pair (H, R). If the pair is 3-by-3 or bigger, we look at the bottom right 2-by-2 block. If this block has complex eigenvalues, we perform a Francis double shift QZ sweep. If it has real eigenvalues, we perform an implicit single shift QZ sweep. If the pair is 2-by-2 with real eigenvalues, we perform a single shift sweep. If it has complex eigenvalues, we return GSL_CONTINUE to notify the calling function that a 2-by-2 block with complex eigenvalues has converged, so that it may then call gen_schur_standardize2(). In the real eigenvalue case, we want to continue doing QZ sweeps to break it up into two 1-by-1 blocks. See LAPACK routine DHGEQZ and [1] for more information. Inputs: H - upper Hessenberg matrix (at least 2-by-2) R - upper triangular matrix (at least 2-by-2) w - workspace Return: GSL_SUCCESS on normal completion GSL_CONTINUE if we detect a 2-by-2 block with complex eigenvalues */ static inline int gen_qzstep(gsl_matrix *H, gsl_matrix *R, gsl_eigen_gen_workspace *w) { const size_t N = H->size1; gsl_matrix_view vh, vr; /* views of bottom right 2-by-2 block */ double wr1, wr2, wi; double scale1, scale2, scale; double cs, sn; /* givens rotation */ double temp, /* temporary variables */ temp2; size_t j; /* looping */ gsl_vector_view xv, yv; /* temporary views */ size_t top; size_t rows; if (w->n_iter % 10 == 0) { /* * Exceptional shift - we have gone 10 iterations without finding * a new eigenvalue, do a single shift sweep with an * exceptional shift */ if ((GSL_DBL_MIN * w->max_iterations) * fabs(gsl_matrix_get(H, N - 2, N - 1)) < fabs(gsl_matrix_get(R, N - 2, N - 2))) { w->eshift += gsl_matrix_get(H, N - 2, N - 1) / gsl_matrix_get(R, N - 2, N - 2); } else w->eshift += 1.0 / (GSL_DBL_MIN * w->max_iterations); if ((w->eshift < GSL_DBL_EPSILON) && (GSL_DBL_MIN * w->max_iterations) * fabs(gsl_matrix_get(H, N - 1, N - 2)) < fabs(gsl_matrix_get(R, N - 2, N - 2))) { w->eshift = GEN_ESHIFT_COEFF * (w->ascale * gsl_matrix_get(H, N - 1, N - 2)) / (w->bscale * gsl_matrix_get(R, N - 2, N - 2)); } scale1 = 1.0; wr1 = w->eshift; } else { /* * Compute generalized eigenvalues of bottom right 2-by-2 block * to be used as shifts - wr1 is the Wilkinson shift */ vh = gsl_matrix_submatrix(H, N - 2, N - 2, 2, 2); vr = gsl_matrix_submatrix(R, N - 2, N - 2, 2, 2); gsl_schur_gen_eigvals(&vh.matrix, &vr.matrix, &wr1, &wr2, &wi, &scale1, &scale2); if (wi != 0.0) { /* complex eigenvalues */ if (N == 2) { /* * its a 2-by-2 block with complex eigenvalues - notify * the calling function to deflate */ return (GSL_CONTINUE); } else { /* do a francis double shift sweep */ gen_qzstep_d(H, R, w); } return GSL_SUCCESS; } } /* real eigenvalues - perform single shift QZ step */ temp = GSL_MIN(w->ascale, 1.0) * (0.5 / GSL_DBL_MIN); if (scale1 > temp) scale = temp / scale1; else scale = 1.0; temp = GSL_MIN(w->bscale, 1.0) * (0.5 / GSL_DBL_MIN); if (fabs(wr1) > temp) scale = GSL_MIN(scale, temp / fabs(wr1)); scale1 *= scale; wr1 *= scale; if (w->needtop) { /* get absolute index of this matrix relative to original matrix */ top = gen_get_submatrix(w->H, H); } temp = scale1*gsl_matrix_get(H, 0, 0) - wr1*gsl_matrix_get(R, 0, 0); temp2 = scale1*gsl_matrix_get(H, 1, 0); create_givens(temp, temp2, &cs, &sn); sn = -sn; for (j = 0; j < N - 1; ++j) { if (j > 0) { temp = gsl_matrix_get(H, j, j - 1); temp2 = gsl_matrix_get(H, j + 1, j - 1); create_givens(temp, temp2, &cs, &sn); sn = -sn; /* apply to column (j - 1) */ temp = cs * gsl_matrix_get(H, j, j - 1) + sn * gsl_matrix_get(H, j + 1, j - 1); gsl_matrix_set(H, j, j - 1, temp); gsl_matrix_set(H, j + 1, j - 1, 0.0); } /* apply G to H(j:j+1,:) and T(j:j+1,:) */ if (w->compute_s) { xv = gsl_matrix_subrow(w->H, top + j, top + j, w->size - top - j); yv = gsl_matrix_subrow(w->H, top + j + 1, top + j, w->size - top - j); } else { xv = gsl_matrix_subrow(H, j, j, N - j); yv = gsl_matrix_subrow(H, j + 1, j, N - j); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); if (w->compute_t) { xv = gsl_matrix_subrow(w->R, top + j, top + j, w->size - top - j); yv = gsl_matrix_subrow(w->R, top + j + 1, top + j, w->size - top - j); } else { xv = gsl_matrix_subrow(R, j, j, N - j); yv = gsl_matrix_subrow(R, j + 1, j, N - j); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); if (w->Q) { /* accumulate Q: Q -> QG */ xv = gsl_matrix_column(w->Q, top + j); yv = gsl_matrix_column(w->Q, top + j + 1); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } temp = gsl_matrix_get(R, j + 1, j + 1); temp2 = gsl_matrix_get(R, j + 1, j); create_givens(temp, temp2, &cs, &sn); rows = GSL_MIN(j + 3, N); if (w->compute_s) { xv = gsl_matrix_subcolumn(w->H, top + j, 0, top + rows); yv = gsl_matrix_subcolumn(w->H, top + j + 1, 0, top + rows); } else { xv = gsl_matrix_subcolumn(H, j, 0, rows); yv = gsl_matrix_subcolumn(H, j + 1, 0, rows); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); rows = GSL_MIN(j + 2, N); if (w->compute_t) { xv = gsl_matrix_subcolumn(w->R, top + j, 0, top + rows); yv = gsl_matrix_subcolumn(w->R, top + j + 1, 0, top + rows); } else { xv = gsl_matrix_subcolumn(R, j, 0, rows); yv = gsl_matrix_subcolumn(R, j + 1, 0, rows); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); if (w->Z) { /* accumulate Z: Z -> ZG */ xv = gsl_matrix_column(w->Z, top + j); yv = gsl_matrix_column(w->Z, top + j + 1); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } } /* for (j = 0; j < N - 1; ++j) */ return GSL_SUCCESS; } /* gen_qzstep() */ /* gen_qzstep_d() Perform an implicit double shift QZ step. See Golub & Van Loan, "Matrix Computations" (3rd ed), algorithm 7.7.2 Inputs: H - upper Hessenberg matrix (at least 3-by-3) R - upper triangular matrix (at least 3-by-3) w - workspace */ static inline void gen_qzstep_d(gsl_matrix *H, gsl_matrix *R, gsl_eigen_gen_workspace *w) { const size_t N = H->size1; size_t j; /* looping */ double dat[3]; /* householder vector */ double tau; /* householder coefficient */ gsl_vector_view v2, v3; /* views into 'dat' */ gsl_matrix_view m; /* temporary view */ double tmp; size_t q, r; size_t top; /* location of H in original matrix */ double scale; double AB11, /* various matrix element ratios */ AB22, ABNN, ABMM, AMNBNN, ANMBMM, A21B11, A12B22, A32B22, B12B22, BMNBNN; v2 = gsl_vector_view_array(dat, 2); v3 = gsl_vector_view_array(dat, 3); if (w->needtop) { /* get absolute index of this matrix relative to original matrix */ top = gen_get_submatrix(w->H, H); } /* * Similar to the QR method, we take the shifts to be the two * zeros of the problem * * det[H(n-1:n,n-1:n) - s*R(n-1:n,n-1:n)] = 0 * * The initial householder vector elements are then given by * Eq. 4.1 of [1], which are designed to reduce errors when * off diagonal elements are small. */ ABMM = (w->ascale * gsl_matrix_get(H, N - 2, N - 2)) / (w->bscale * gsl_matrix_get(R, N - 2, N - 2)); ABNN = (w->ascale * gsl_matrix_get(H, N - 1, N - 1)) / (w->bscale * gsl_matrix_get(R, N - 1, N - 1)); AB11 = (w->ascale * gsl_matrix_get(H, 0, 0)) / (w->bscale * gsl_matrix_get(R, 0, 0)); AB22 = (w->ascale * gsl_matrix_get(H, 1, 1)) / (w->bscale * gsl_matrix_get(R, 1, 1)); AMNBNN = (w->ascale * gsl_matrix_get(H, N - 2, N - 1)) / (w->bscale * gsl_matrix_get(R, N - 1, N - 1)); ANMBMM = (w->ascale * gsl_matrix_get(H, N - 1, N - 2)) / (w->bscale * gsl_matrix_get(R, N - 2, N - 2)); BMNBNN = gsl_matrix_get(R, N - 2, N - 1) / gsl_matrix_get(R, N - 1, N - 1); A21B11 = (w->ascale * gsl_matrix_get(H, 1, 0)) / (w->bscale * gsl_matrix_get(R, 0, 0)); A12B22 = (w->ascale * gsl_matrix_get(H, 0, 1)) / (w->bscale * gsl_matrix_get(R, 1, 1)); A32B22 = (w->ascale * gsl_matrix_get(H, 2, 1)) / (w->bscale * gsl_matrix_get(R, 1, 1)); B12B22 = gsl_matrix_get(R, 0, 1) / gsl_matrix_get(R, 1, 1); /* * These are the Eqs (4.1) of [1], just multiplied by the factor * (A_{21} / B_{11}) */ dat[0] = (ABMM - AB11) * (ABNN - AB11) - (AMNBNN * ANMBMM) + (ANMBMM * BMNBNN * AB11) + (A12B22 - (AB11 * B12B22)) * A21B11; dat[1] = ((AB22 - AB11) - (A21B11 * B12B22) - (ABMM - AB11) - (ABNN - AB11) + (ANMBMM * BMNBNN)) * A21B11; dat[2] = A32B22 * A21B11; scale = fabs(dat[0]) + fabs(dat[1]) + fabs(dat[2]); if (scale != 0.0) { dat[0] /= scale; dat[1] /= scale; dat[2] /= scale; } for (j = 0; j < N - 2; ++j) { r = GSL_MIN(j + 4, N); /* * Find householder Q so that * * Q [x y z]^t = [ * 0 0 ]^t */ tau = gsl_linalg_householder_transform(&v3.vector); if (tau != 0.0) { /* * q is the initial column to start applying the householder * transformation. The GSL_MAX() simply ensures we don't * try to apply it to column (-1), since we are zeroing out * column (j - 1) except for the first iteration which * introduces the bulge. */ q = (size_t) GSL_MAX(0, (int)j - 1); /* H -> QH, R -> QR */ if (w->compute_s) { /* * We are computing the Schur form S, so we need to * transform the whole matrix H */ m = gsl_matrix_submatrix(w->H, top + j, top + q, 3, w->size - top - q); gsl_linalg_householder_hm(tau, &v3.vector, &m.matrix); } else { /* just transform the active block */ m = gsl_matrix_submatrix(H, j, q, 3, N - q); gsl_linalg_householder_hm(tau, &v3.vector, &m.matrix); } if (w->compute_t) { /* * We are computing the Schur form T, so we need to * transform the whole matrix R */ m = gsl_matrix_submatrix(w->R, top + j, top + j, 3, w->size - top - j); gsl_linalg_householder_hm(tau, &v3.vector, &m.matrix); } else { /* just transform the active block */ m = gsl_matrix_submatrix(R, j, j, 3, N - j); gsl_linalg_householder_hm(tau, &v3.vector, &m.matrix); } if (w->Q) { /* accumulate the transformation into Q */ m = gsl_matrix_submatrix(w->Q, 0, top + j, w->size, 3); gsl_linalg_householder_mh(tau, &v3.vector, &m.matrix); } } /* if (tau != 0.0) */ /* * Find householder Z so that * * [ r_{j+2,j} r_{j+2, j+1}, r_{j+2, j+2} ] Z = [ 0 0 * ] * * This isn't exactly what gsl_linalg_householder_transform * does, so we need to rotate the input vector so it preserves * the last element, and then rotate it back afterwards. * * So instead of transforming [x y z], we transform [z x y], * and the resulting HH vector [1 v2 v3] -> [v2 v3 1] but * then needs to be scaled to have the first element = 1, so * it becomes [1 v3/v2 1/v2] (tau must also be scaled accordingly). */ dat[0] = gsl_matrix_get(R, j + 2, j + 2); dat[1] = gsl_matrix_get(R, j + 2, j); dat[2] = gsl_matrix_get(R, j + 2, j + 1); scale = fabs(dat[0]) + fabs(dat[1]) + fabs(dat[2]); if (scale != 0.0) { dat[0] /= scale; dat[1] /= scale; dat[2] /= scale; } tau = gsl_linalg_householder_transform(&v3.vector); if (tau != 0.0) { /* rotate back */ tmp = gsl_vector_get(&v3.vector, 1); gsl_vector_set(&v3.vector, 1, gsl_vector_get(&v3.vector, 2)/tmp); gsl_vector_set(&v3.vector, 2, 1.0 / tmp); tau *= tmp * tmp; /* H -> HZ, R -> RZ */ if (w->compute_s) { m = gsl_matrix_submatrix(w->H, 0, top + j, top + r, 3); gsl_linalg_householder_mh(tau, &v3.vector, &m.matrix); } else { m = gsl_matrix_submatrix(H, 0, j, r, 3); gsl_linalg_householder_mh(tau, &v3.vector, &m.matrix); } if (w->compute_t) { m = gsl_matrix_submatrix(w->R, 0, top + j, top + j + 3, 3); gsl_linalg_householder_mh(tau, &v3.vector, &m.matrix); } else { m = gsl_matrix_submatrix(R, 0, j, j + 3, 3); gsl_linalg_householder_mh(tau, &v3.vector, &m.matrix); } if (w->Z) { /* accumulate transformation into Z */ m = gsl_matrix_submatrix(w->Z, 0, top + j, w->size, 3); gsl_linalg_householder_mh(tau, &v3.vector, &m.matrix); } } /* if (tau != 0.0) */ /* * Find householder Z so that * * [ r_{j+1,j} r_{j+1, j+1} ] Z = [ 0 * ] */ dat[0] = gsl_matrix_get(R, j + 1, j + 1); dat[1] = gsl_matrix_get(R, j + 1, j); scale = fabs(dat[0]) + fabs(dat[1]); if (scale != 0.0) { dat[0] /= scale; dat[1] /= scale; } tau = gsl_linalg_householder_transform(&v2.vector); if (tau != 0.0) { /* rotate back */ tmp = gsl_vector_get(&v2.vector, 1); gsl_vector_set(&v2.vector, 1, 1.0 / tmp); tau *= tmp * tmp; /* H -> HZ, R -> RZ */ if (w->compute_s) { m = gsl_matrix_submatrix(w->H, 0, top + j, top + r, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } else { m = gsl_matrix_submatrix(H, 0, j, r, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } if (w->compute_t) { m = gsl_matrix_submatrix(w->R, 0, top + j, top + j + 3, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } else { m = gsl_matrix_submatrix(R, 0, j, j + 3, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } if (w->Z) { /* accumulate transformation into Z */ m = gsl_matrix_submatrix(w->Z, 0, top + j, w->size, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } } /* if (tau != 0.0) */ dat[0] = gsl_matrix_get(H, j + 1, j); dat[1] = gsl_matrix_get(H, j + 2, j); if (j < N - 3) dat[2] = gsl_matrix_get(H, j + 3, j); scale = fabs(dat[0]) + fabs(dat[1]) + fabs(dat[2]); if (scale != 0.0) { dat[0] /= scale; dat[1] /= scale; dat[2] /= scale; } } /* for (j = 0; j < N - 2; ++j) */ /* * Find Householder Q so that * * Q [ x y ]^t = [ * 0 ]^t */ scale = fabs(dat[0]) + fabs(dat[1]); if (scale != 0.0) { dat[0] /= scale; dat[1] /= scale; } tau = gsl_linalg_householder_transform(&v2.vector); if (w->compute_s) { m = gsl_matrix_submatrix(w->H, top + N - 2, top + N - 3, 2, w->size - top - N + 3); gsl_linalg_householder_hm(tau, &v2.vector, &m.matrix); } else { m = gsl_matrix_submatrix(H, N - 2, N - 3, 2, 3); gsl_linalg_householder_hm(tau, &v2.vector, &m.matrix); } if (w->compute_t) { m = gsl_matrix_submatrix(w->R, top + N - 2, top + N - 2, 2, w->size - top - N + 2); gsl_linalg_householder_hm(tau, &v2.vector, &m.matrix); } else { m = gsl_matrix_submatrix(R, N - 2, N - 2, 2, 2); gsl_linalg_householder_hm(tau, &v2.vector, &m.matrix); } if (w->Q) { /* accumulate the transformation into Q */ m = gsl_matrix_submatrix(w->Q, 0, top + N - 2, w->size, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } /* * Find Householder Z so that * * [ b_{n,n-1} b_{nn} ] Z = [ 0 * ] */ dat[0] = gsl_matrix_get(R, N - 1, N - 1); dat[1] = gsl_matrix_get(R, N - 1, N - 2); scale = fabs(dat[0]) + fabs(dat[1]); if (scale != 0.0) { dat[0] /= scale; dat[1] /= scale; } tau = gsl_linalg_householder_transform(&v2.vector); /* rotate back */ tmp = gsl_vector_get(&v2.vector, 1); gsl_vector_set(&v2.vector, 1, 1.0 / tmp); tau *= tmp * tmp; if (w->compute_s) { m = gsl_matrix_submatrix(w->H, 0, top + N - 2, top + N, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } else { m = gsl_matrix_submatrix(H, 0, N - 2, N, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } if (w->compute_t) { m = gsl_matrix_submatrix(w->R, 0, top + N - 2, top + N, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } else { m = gsl_matrix_submatrix(R, 0, N - 2, N, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } if (w->Z) { /* accumulate the transformation into Z */ m = gsl_matrix_submatrix(w->Z, 0, top + N - 2, w->size, 2); gsl_linalg_householder_mh(tau, &v2.vector, &m.matrix); } } /* gen_qzstep_d() */ /* gen_tri_split_top() This routine is called when the leading element on the diagonal of R has become negligible. Split off a 1-by-1 block at the top. Inputs: H - upper hessenberg matrix R - upper triangular matrix w - workspace */ static void gen_tri_split_top(gsl_matrix *H, gsl_matrix *R, gsl_eigen_gen_workspace *w) { const size_t N = H->size1; size_t j, top; double cs, sn; gsl_vector_view xv, yv; if (w->needtop) top = gen_get_submatrix(w->H, H); j = 0; create_givens(gsl_matrix_get(H, j, j), gsl_matrix_get(H, j + 1, j), &cs, &sn); sn = -sn; if (w->compute_s) { xv = gsl_matrix_subrow(w->H, top + j, top, w->size - top); yv = gsl_matrix_subrow(w->H, top + j + 1, top, w->size - top); } else { xv = gsl_matrix_row(H, j); yv = gsl_matrix_row(H, j + 1); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); gsl_matrix_set(H, j + 1, j, 0.0); if (w->compute_t) { xv = gsl_matrix_subrow(w->R, top + j, top + 1, w->size - top - 1); yv = gsl_matrix_subrow(w->R, top + j + 1, top + 1, w->size - top - 1); } else { xv = gsl_matrix_subrow(R, j, 1, N - 1); yv = gsl_matrix_subrow(R, j + 1, 1, N - 1); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); if (w->Q) { xv = gsl_matrix_column(w->Q, top + j); yv = gsl_matrix_column(w->Q, top + j + 1); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } } /* gen_tri_split_top() */ /* gen_tri_chase_zero() This routine is called when an element on the diagonal of R has become negligible. Chase the zero to the bottom of the active block so we can split off a 1-by-1 block. Inputs: H - upper hessenberg matrix R - upper triangular matrix q - index such that R(q,q) = 0 (q must be > 0) w - workspace */ static inline void gen_tri_chase_zero(gsl_matrix *H, gsl_matrix *R, size_t q, gsl_eigen_gen_workspace *w) { const size_t N = H->size1; size_t j, top; double cs, sn; gsl_vector_view xv, yv; if (w->needtop) top = gen_get_submatrix(w->H, H); for (j = q; j < N - 1; ++j) { create_givens(gsl_matrix_get(R, j, j + 1), gsl_matrix_get(R, j + 1, j + 1), &cs, &sn); sn = -sn; if (w->compute_t) { xv = gsl_matrix_subrow(w->R, top + j, top + j + 1, w->size - top - j - 1); yv = gsl_matrix_subrow(w->R, top + j + 1, top + j + 1, w->size - top - j - 1); } else { xv = gsl_matrix_subrow(R, j, j + 1, N - j - 1); yv = gsl_matrix_subrow(R, j + 1, j + 1, N - j - 1); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); gsl_matrix_set(R, j + 1, j + 1, 0.0); if (w->compute_s) { xv = gsl_matrix_subrow(w->H, top + j, top + j - 1, w->size - top - j + 1); yv = gsl_matrix_subrow(w->H, top + j + 1, top + j - 1, w->size - top - j + 1); } else { xv = gsl_matrix_subrow(H, j, j - 1, N - j + 1); yv = gsl_matrix_subrow(H, j + 1, j - 1, N - j + 1); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); if (w->Q) { /* accumulate Q */ xv = gsl_matrix_column(w->Q, top + j); yv = gsl_matrix_column(w->Q, top + j + 1); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } create_givens(gsl_matrix_get(H, j + 1, j), gsl_matrix_get(H, j + 1, j - 1), &cs, &sn); sn = -sn; if (w->compute_s) { xv = gsl_matrix_subcolumn(w->H, top + j, 0, top + j + 2); yv = gsl_matrix_subcolumn(w->H, top + j - 1, 0, top + j + 2); } else { xv = gsl_matrix_subcolumn(H, j, 0, j + 2); yv = gsl_matrix_subcolumn(H, j - 1, 0, j + 2); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); gsl_matrix_set(H, j + 1, j - 1, 0.0); if (w->compute_t) { xv = gsl_matrix_subcolumn(w->R, top + j, 0, top + j + 1); yv = gsl_matrix_subcolumn(w->R, top + j - 1, 0, top + j + 1); } else { xv = gsl_matrix_subcolumn(R, j, 0, j + 1); yv = gsl_matrix_subcolumn(R, j - 1, 0, j + 1); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); if (w->Z) { /* accumulate Z */ xv = gsl_matrix_column(w->Z, top + j); yv = gsl_matrix_column(w->Z, top + j - 1); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } } } /* gen_tri_chase_zero() */ /* gen_tri_zero_H() Companion function to get_tri_chase_zero(). After the zero on the diagonal of R has been chased to the bottom, we zero the element H(n, n - 1) in order to split off a 1-by-1 block. */ static inline void gen_tri_zero_H(gsl_matrix *H, gsl_matrix *R, gsl_eigen_gen_workspace *w) { const size_t N = H->size1; size_t top; double cs, sn; gsl_vector_view xv, yv; if (w->needtop) top = gen_get_submatrix(w->H, H); create_givens(gsl_matrix_get(H, N - 1, N - 1), gsl_matrix_get(H, N - 1, N - 2), &cs, &sn); sn = -sn; if (w->compute_s) { xv = gsl_matrix_subcolumn(w->H, top + N - 1, 0, top + N); yv = gsl_matrix_subcolumn(w->H, top + N - 2, 0, top + N); } else { xv = gsl_matrix_column(H, N - 1); yv = gsl_matrix_column(H, N - 2); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); gsl_matrix_set(H, N - 1, N - 2, 0.0); if (w->compute_t) { xv = gsl_matrix_subcolumn(w->R, top + N - 1, 0, top + N - 1); yv = gsl_matrix_subcolumn(w->R, top + N - 2, 0, top + N - 1); } else { xv = gsl_matrix_subcolumn(R, N - 1, 0, N - 1); yv = gsl_matrix_subcolumn(R, N - 2, 0, N - 1); } gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); if (w->Z) { /* accumulate Z */ xv = gsl_matrix_column(w->Z, top + N - 1); yv = gsl_matrix_column(w->Z, top + N - 2); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } } /* gen_tri_zero_H() */ /* gen_search_small_elements() This routine searches for small elements in the matrix pencil (H, R) to determine if any eigenvalues have converged. Tests: 1. Test if the Hessenberg matrix has a small subdiagonal element: H(i, i - 1) < tolerance 2. Test if the Triangular matrix has a small diagonal element: R(i, i) < tolerance Possible outcomes: (A) Neither test passed: in this case 'flag' is set to 0 and the function returns 0 (B) Test 1 passes and 2 does not: in this case 'flag' is set to 1 and we return the row index i such that H(i, i - 1) < tol (C) Test 2 passes and 1 does not: in this case 'flag' is set to 2 and we return the index i such that R(i, i) < tol (D) Tests 1 and 2 both pass: in this case 'flag' is set to 3 and we return the index i such that H(i, i - 1) < tol and R(i, i) < tol Inputs: H - upper Hessenberg matrix R - upper Triangular matrix flag - (output) flag set on output (see above) w - workspace Return: see above */ static inline size_t gen_search_small_elements(gsl_matrix *H, gsl_matrix *R, int *flag, gsl_eigen_gen_workspace *w) { const size_t N = H->size1; int k; size_t i; int pass1 = 0; int pass2 = 0; for (k = (int) N - 1; k >= 0; --k) { i = (size_t) k; if (i != 0 && fabs(gsl_matrix_get(H, i, i - 1)) <= w->atol) { gsl_matrix_set(H, i, i - 1, 0.0); pass1 = 1; } if (fabs(gsl_matrix_get(R, i, i)) < w->btol) { gsl_matrix_set(R, i, i, 0.0); pass2 = 1; } if (pass1 && !pass2) /* case B */ { *flag = 1; return (i); } else if (!pass1 && pass2) /* case C */ { *flag = 2; return (i); } else if (pass1 && pass2) /* case D */ { *flag = 3; return (i); } } /* neither test passed: case A */ *flag = 0; return (0); } /* gen_search_subdiag_small_elements() */ /* gen_schur_standardize1() This function is called when a 1-by-1 block has converged - convert the block to standard form and update the Schur forms and vectors if required. Standard form here means that the diagonal element of B is positive. Inputs: A - 1-by-1 matrix in Schur form S B - 1-by-1 matrix in Schur form T alphar - where to store real part of eigenvalue numerator beta - where to store eigenvalue denominator w - workspace Return: success */ static int gen_schur_standardize1(gsl_matrix *A, gsl_matrix *B, double *alphar, double *beta, gsl_eigen_gen_workspace *w) { size_t i; size_t top; /* * it is a 1-by-1 block - the only requirement is that * B_{00} is > 0, so if it isn't apply a -I transformation */ if (gsl_matrix_get(B, 0, 0) < 0.0) { if (w->needtop) top = gen_get_submatrix(w->H, A); if (w->compute_t) { for (i = 0; i <= top; ++i) gsl_matrix_set(w->R, i, top, -gsl_matrix_get(w->R, i, top)); } else gsl_matrix_set(B, 0, 0, -gsl_matrix_get(B, 0, 0)); if (w->compute_s) { for (i = 0; i <= top; ++i) gsl_matrix_set(w->H, i, top, -gsl_matrix_get(w->H, i, top)); } else gsl_matrix_set(A, 0, 0, -gsl_matrix_get(A, 0, 0)); if (w->Z) { for (i = 0; i < w->size; ++i) gsl_matrix_set(w->Z, i, top, -gsl_matrix_get(w->Z, i, top)); } } *alphar = gsl_matrix_get(A, 0, 0); *beta = gsl_matrix_get(B, 0, 0); return GSL_SUCCESS; } /* gen_schur_standardize1() */ /* gen_schur_standardize2() This function is called when a 2-by-2 generalized block has converged. Convert the block to standard form, which means B is rotated so that B = [ B11 0 ] with B11, B22 non-negative [ 0 B22 ] If the resulting block (A, B) has complex eigenvalues, they are computed. Otherwise, the function will return GSL_CONTINUE to notify caller that we need to do more single shift sweeps to convert the 2-by-2 block into two 1-by-1 blocks. Inputs: A - 2-by-2 submatrix of schur form S B - 2-by-2 submatrix of schur form T alpha1 - (output) where to store eigenvalue 1 numerator alpha2 - (output) where to store eigenvalue 2 numerator beta1 - (output) where to store eigenvalue 1 denominator beta2 - (output) where to store eigenvalue 2 denominator w - workspace Return: GSL_SUCCESS if block has complex eigenvalues (they are computed) GSL_CONTINUE if block has real eigenvalues (they are not computed) */ static int gen_schur_standardize2(gsl_matrix *A, gsl_matrix *B, gsl_complex *alpha1, gsl_complex *alpha2, double *beta1, double *beta2, gsl_eigen_gen_workspace *w) { double datB[4], datV[4], datS[2], work[2]; gsl_matrix_view uv = gsl_matrix_view_array(datB, 2, 2); gsl_matrix_view vv = gsl_matrix_view_array(datV, 2, 2); gsl_vector_view sv = gsl_vector_view_array(datS, 2); gsl_vector_view wv = gsl_vector_view_array(work, 2); double B11, B22; size_t top; double det; double cr, sr, cl, sl; gsl_vector_view xv, yv; int s; if (w->needtop) top = gen_get_submatrix(w->H, A); /* * Rotate B so that * * B = [ B11 0 ] * [ 0 B22 ] * * with B11 non-negative */ gsl_matrix_memcpy(&uv.matrix, B); gsl_linalg_SV_decomp(&uv.matrix, &vv.matrix, &sv.vector, &wv.vector); /* * Right now, B = U S V^t, where S = diag(s) * * The SVD routine may have computed reflection matrices U and V, * but it would be much nicer to have rotations since we won't have * to use BLAS mat-mat multiplications to update our matrices, * and can instead use drot. So convert them to rotations if * necessary */ det = gsl_matrix_get(&vv.matrix, 0, 0) * gsl_matrix_get(&vv.matrix, 1, 1) - gsl_matrix_get(&vv.matrix, 0, 1) * gsl_matrix_get(&vv.matrix, 1, 0); if (det < 0.0) { /* V is a reflection, convert it to a rotation by inserting * F = [1 0; 0 -1] so that: * * B = U S [1 0] [1 0] V^t * [0 -1] [0 -1] * * so S -> S F and V -> V F where F is the reflection matrix * We just need to invert S22 since the first column of V * will remain unchanged and we can just read off the CS and SN * parameters. */ datS[1] = -datS[1]; } cr = gsl_matrix_get(&vv.matrix, 0, 0); sr = gsl_matrix_get(&vv.matrix, 1, 0); /* same for U */ det = gsl_matrix_get(&uv.matrix, 0, 0) * gsl_matrix_get(&uv.matrix, 1, 1) - gsl_matrix_get(&uv.matrix, 0, 1) * gsl_matrix_get(&uv.matrix, 1, 0); if (det < 0.0) datS[1] = -datS[1]; cl = gsl_matrix_get(&uv.matrix, 0, 0); sl = gsl_matrix_get(&uv.matrix, 1, 0); B11 = gsl_vector_get(&sv.vector, 0); B22 = gsl_vector_get(&sv.vector, 1); /* make sure B11 is positive */ if (B11 < 0.0) { B11 = -B11; B22 = -B22; cr = -cr; sr = -sr; } /* * At this point, * * [ S11 0 ] = [ CSL SNL ] B [ CSR -SNR ] * [ 0 S22 ] [-SNL CSL ] [ SNR CSR ] * * apply rotations to H and rest of R */ if (w->compute_s) { xv = gsl_matrix_subrow(w->H, top, top, w->size - top); yv = gsl_matrix_subrow(w->H, top + 1, top, w->size - top); gsl_blas_drot(&xv.vector, &yv.vector, cl, sl); xv = gsl_matrix_subcolumn(w->H, top, 0, top + 2); yv = gsl_matrix_subcolumn(w->H, top + 1, 0, top + 2); gsl_blas_drot(&xv.vector, &yv.vector, cr, sr); } else { xv = gsl_matrix_row(A, 0); yv = gsl_matrix_row(A, 1); gsl_blas_drot(&xv.vector, &yv.vector, cl, sl); xv = gsl_matrix_column(A, 0); yv = gsl_matrix_column(A, 1); gsl_blas_drot(&xv.vector, &yv.vector, cr, sr); } if (w->compute_t) { if (top != (w->size - 2)) { xv = gsl_matrix_subrow(w->R, top, top + 2, w->size - top - 2); yv = gsl_matrix_subrow(w->R, top + 1, top + 2, w->size - top - 2); gsl_blas_drot(&xv.vector, &yv.vector, cl, sl); } if (top != 0) { xv = gsl_matrix_subcolumn(w->R, top, 0, top); yv = gsl_matrix_subcolumn(w->R, top + 1, 0, top); gsl_blas_drot(&xv.vector, &yv.vector, cr, sr); } } if (w->Q) { xv = gsl_matrix_column(w->Q, top); yv = gsl_matrix_column(w->Q, top + 1); gsl_blas_drot(&xv.vector, &yv.vector, cl, sl); } if (w->Z) { xv = gsl_matrix_column(w->Z, top); yv = gsl_matrix_column(w->Z, top + 1); gsl_blas_drot(&xv.vector, &yv.vector, cr, sr); } gsl_matrix_set(B, 0, 0, B11); gsl_matrix_set(B, 0, 1, 0.0); gsl_matrix_set(B, 1, 0, 0.0); gsl_matrix_set(B, 1, 1, B22); /* if B22 is < 0, make it positive by negating its column */ if (B22 < 0.0) { size_t i; if (w->compute_s) { for (i = 0; i < top + 2; ++i) gsl_matrix_set(w->H, i, top + 1, -gsl_matrix_get(w->H, i, top + 1)); } else { gsl_matrix_set(A, 0, 1, -gsl_matrix_get(A, 0, 1)); gsl_matrix_set(A, 1, 1, -gsl_matrix_get(A, 1, 1)); } if (w->compute_t) { for (i = 0; i < top + 2; ++i) gsl_matrix_set(w->R, i, top + 1, -gsl_matrix_get(w->R, i, top + 1)); } else { gsl_matrix_set(B, 0, 1, -gsl_matrix_get(B, 0, 1)); gsl_matrix_set(B, 1, 1, -gsl_matrix_get(B, 1, 1)); } if (w->Z) { xv = gsl_matrix_column(w->Z, top + 1); gsl_vector_scale(&xv.vector, -1.0); } } /* our block is now in standard form - compute eigenvalues */ s = gen_compute_eigenvals(A, B, alpha1, alpha2, beta1, beta2); return s; } /* gen_schur_standardize2() */ /* gen_compute_eigenvals() Compute the complex eigenvalues of a 2-by-2 block Return: GSL_CONTINUE if block contains real eigenvalues (they are not computed) GSL_SUCCESS on normal completion */ static int gen_compute_eigenvals(gsl_matrix *A, gsl_matrix *B, gsl_complex *alpha1, gsl_complex *alpha2, double *beta1, double *beta2) { double wr1, wr2, wi, scale1, scale2; double s1inv; double A11, A12, A21, A22; double B11, B22; double c11r, c11i, c12, c21, c22r, c22i; double cz, cq; double szr, szi, sqr, sqi; double a1r, a1i, a2r, a2i, b1r, b1i, b1a, b2r, b2i, b2a; double alphar, alphai; double t1, an, bn, tempr, tempi, wabs; /* * This function is called from gen_schur_standardize2() and * its possible the standardization has perturbed the eigenvalues * onto the real line - so check for this before computing them */ gsl_schur_gen_eigvals(A, B, &wr1, &wr2, &wi, &scale1, &scale2); if (wi == 0.0) return GSL_CONTINUE; /* real eigenvalues - continue QZ iteration */ /* complex eigenvalues - compute alpha and beta */ s1inv = 1.0 / scale1; A11 = gsl_matrix_get(A, 0, 0); A12 = gsl_matrix_get(A, 0, 1); A21 = gsl_matrix_get(A, 1, 0); A22 = gsl_matrix_get(A, 1, 1); B11 = gsl_matrix_get(B, 0, 0); B22 = gsl_matrix_get(B, 1, 1); c11r = scale1 * A11 - wr1 * B11; c11i = -wi * B11; c12 = scale1 * A12; c21 = scale1 * A21; c22r = scale1 * A22 - wr1 * B22; c22i = -wi * B22; if (fabs(c11r) + fabs(c11i) + fabs(c12) > fabs(c21) + fabs(c22r) + fabs(c22i)) { t1 = gsl_hypot3(c12, c11r, c11i); if (t1 != 0.0) { cz = c12 / t1; szr = -c11r / t1; szi = -c11i / t1; } else { cz = 0.0; szr = 1.0; szi = 0.0; } } else { cz = hypot(c22r, c22i); if (cz <= GSL_DBL_MIN) { cz = 0.0; szr = 1.0; szi = 0.0; } else { tempr = c22r / cz; tempi = c22i / cz; t1 = hypot(cz, c21); cz /= t1; szr = -c21*tempr / t1; szi = c21*tempi / t1; } } an = fabs(A11) + fabs(A12) + fabs(A21) + fabs(A22); bn = fabs(B11) + fabs(B22); wabs = fabs(wr1) + fabs(wi); if (scale1*an > wabs*bn) { cq = cz * B11; if (cq <= GSL_DBL_MIN) { cq = 0.0; sqr = 1.0; sqi = 0.0; } else { sqr = szr * B22; sqi = -szi * B22; } } else { a1r = cz * A11 + szr * A12; a1i = szi * A12; a2r = cz * A21 + szr * A22; a2i = szi * A22; cq = hypot(a1r, a1i); if (cq <= GSL_DBL_MIN) { cq = 0.0; sqr = 1.0; sqi = 0.0; } else { tempr = a1r / cq; tempi = a1i / cq; sqr = tempr * a2r + tempi * a2i; sqi = tempi * a2r - tempr * a2i; } } t1 = gsl_hypot3(cq, sqr, sqi); cq /= t1; sqr /= t1; sqi /= t1; tempr = sqr*szr - sqi*szi; tempi = sqr*szi + sqi*szr; b1r = cq*cz*B11 + tempr*B22; b1i = tempi*B22; b1a = hypot(b1r, b1i); b2r = cq*cz*B22 + tempr*B11; b2i = -tempi*B11; b2a = hypot(b2r, b2i); *beta1 = b1a; *beta2 = b2a; alphar = (wr1 * b1a) * s1inv; alphai = (wi * b1a) * s1inv; GSL_SET_COMPLEX(alpha1, alphar, alphai); alphar = (wr1 * b2a) * s1inv; alphai = -(wi * b2a) * s1inv; GSL_SET_COMPLEX(alpha2, alphar, alphai); return GSL_SUCCESS; } /* gen_compute_eigenvals() */ /* gen_store_eigval1() Store eigenvalue of a 1-by-1 block into the alpha and beta output vectors. This routine ensures that eigenvalues are stored in the same order as they appear in the Schur form and updates various internal workspace quantities. */ static void gen_store_eigval1(const gsl_matrix *H, const double a, const double b, gsl_vector_complex *alpha, gsl_vector *beta, gsl_eigen_gen_workspace *w) { size_t top = gen_get_submatrix(w->H, H); gsl_complex z; GSL_SET_COMPLEX(&z, a, 0.0); gsl_vector_complex_set(alpha, top, z); gsl_vector_set(beta, top, b); w->n_evals += 1; w->n_iter = 0; w->eshift = 0.0; } /* gen_store_eigval1() */ /* gen_store_eigval2() Store eigenvalues of a 2-by-2 block into the alpha and beta output vectors. This routine ensures that eigenvalues are stored in the same order as they appear in the Schur form and updates various internal workspace quantities. */ static void gen_store_eigval2(const gsl_matrix *H, const gsl_complex *alpha1, const double beta1, const gsl_complex *alpha2, const double beta2, gsl_vector_complex *alpha, gsl_vector *beta, gsl_eigen_gen_workspace *w) { size_t top = gen_get_submatrix(w->H, H); gsl_vector_complex_set(alpha, top, *alpha1); gsl_vector_set(beta, top, beta1); gsl_vector_complex_set(alpha, top + 1, *alpha2); gsl_vector_set(beta, top + 1, beta2); w->n_evals += 2; w->n_iter = 0; w->eshift = 0.0; } /* gen_store_eigval2() */ /* gen_get_submatrix() B is a submatrix of A. The goal of this function is to compute the indices in A of where the matrix B resides */ static inline size_t gen_get_submatrix(const gsl_matrix *A, const gsl_matrix *B) { size_t diff; double ratio; size_t top; diff = (size_t) (B->data - A->data); /* B is on the diagonal of A, so measure distance in units of tda+1 */ ratio = (double)diff / ((double) (A->tda + 1)); top = (size_t) floor(ratio); return top; } /* gen_get_submatrix() */ /* Frobenius norm */ inline static double normF (gsl_matrix * A) { size_t i, j, M = A->size1, N = A->size2; double sum = 0.0, scale = 0.0, ssq = 1.0; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { double Aij = gsl_matrix_get (A, i, j); if (Aij != 0.0) { double ax = fabs (Aij); if (scale < ax) { ssq = 1.0 + ssq * (scale / ax) * (scale / ax); scale = ax; } else { ssq += (ax / scale) * (ax / scale); } } } } sum = scale * sqrt (ssq); return sum; } /* Generate a Givens rotation (cos,sin) which takes v=(x,y) to (|v|,0) From Golub and Van Loan, "Matrix Computations", Section 5.1.8 */ inline static void create_givens (const double a, const double b, double *c, double *s) { if (b == 0) { *c = 1; *s = 0; } else if (fabs (b) > fabs (a)) { double t = -a / b; double s1 = 1.0 / sqrt (1 + t * t); *s = s1; *c = s1 * t; } else { double t = -b / a; double c1 = 1.0 / sqrt (1 + t * t); *c = c1; *s = c1 * t; } } sources_5316/external/gsl/gsl_statistics__wmean.c0000664000176700017670000000072611723710247021076 0ustar paulpaul#include "gsl__config.h" #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__wmean_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__wmean_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__wmean_source.c" #include "templates_off.h" #undef BASE_FLOAT sources_5316/external/gsl/gsl_cblas__source_tbsv_r.h0000664000176700017670000000746011705263724021552 0ustar paulpaul/* blas/source_tbsv_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int nonunit = (Diag == CblasNonUnit); INDEX i, j; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; if (N == 0) return; /* form x := inv( A )*x */ if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { /* backsubstitution */ INDEX ix = OFFSET(N, incX) + incX * (N - 1); for (i = N; i > 0 && i--;) { BASE tmp = X[ix]; const INDEX j_min = i + 1; const INDEX j_max = GSL_MIN(N, i + K + 1); INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE Aij = A[lda * i + (j - i)]; tmp -= Aij * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / A[lda * i + 0]; } else { X[ix] = tmp; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { /* forward substitution */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE tmp = X[ix]; const INDEX j_min = (i > K ? i - K : 0); const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE Aij = A[lda * i + (K + j - i)]; tmp -= Aij * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / A[lda * i + K]; } else { X[ix] = tmp; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := inv( A' )*x */ /* forward substitution */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE tmp = X[ix]; const INDEX j_min = (K > i ? 0 : i - K); const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE Aji = A[(i - j) + lda * j]; tmp -= Aji * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / A[0 + lda * i]; } else { X[ix] = tmp; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { /* backsubstitution */ INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { BASE tmp = X[ix]; const INDEX j_min = i + 1; const INDEX j_max = GSL_MIN(N, i + K + 1); INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { const BASE Aji = A[(K + i - j) + lda * j]; tmp -= Aji * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / A[K + lda * i]; } else { X[ix] = tmp; } ix -= incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_blas.h0000664000176700017670000005264211705263724016313 0ustar paulpaul/* blas/gsl_blas.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * Author: G. Jungman */ #ifndef __GSL_BLAS_H__ #define __GSL_BLAS_H__ #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas_types.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* ======================================================================== * Level 1 * ======================================================================== */ int gsl_blas_sdsdot (float alpha, const gsl_vector_float * X, const gsl_vector_float * Y, float * result ); int gsl_blas_dsdot (const gsl_vector_float * X, const gsl_vector_float * Y, double * result ); int gsl_blas_sdot (const gsl_vector_float * X, const gsl_vector_float * Y, float * result ); int gsl_blas_ddot (const gsl_vector * X, const gsl_vector * Y, double * result ); int gsl_blas_cdotu (const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_complex_float * dotu); int gsl_blas_cdotc (const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_complex_float * dotc); int gsl_blas_zdotu (const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_complex * dotu); int gsl_blas_zdotc (const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_complex * dotc); float gsl_blas_snrm2 (const gsl_vector_float * X); float gsl_blas_sasum (const gsl_vector_float * X); double gsl_blas_dnrm2 (const gsl_vector * X); double gsl_blas_dasum (const gsl_vector * X); float gsl_blas_scnrm2 (const gsl_vector_complex_float * X); float gsl_blas_scasum (const gsl_vector_complex_float * X); double gsl_blas_dznrm2 (const gsl_vector_complex * X); double gsl_blas_dzasum (const gsl_vector_complex * X); CBLAS_INDEX_t gsl_blas_isamax (const gsl_vector_float * X); CBLAS_INDEX_t gsl_blas_idamax (const gsl_vector * X); CBLAS_INDEX_t gsl_blas_icamax (const gsl_vector_complex_float * X); CBLAS_INDEX_t gsl_blas_izamax (const gsl_vector_complex * X); int gsl_blas_sswap (gsl_vector_float * X, gsl_vector_float * Y); int gsl_blas_scopy (const gsl_vector_float * X, gsl_vector_float * Y); int gsl_blas_saxpy (float alpha, const gsl_vector_float * X, gsl_vector_float * Y); int gsl_blas_dswap (gsl_vector * X, gsl_vector * Y); int gsl_blas_dcopy (const gsl_vector * X, gsl_vector * Y); int gsl_blas_daxpy (double alpha, const gsl_vector * X, gsl_vector * Y); int gsl_blas_cswap (gsl_vector_complex_float * X, gsl_vector_complex_float * Y); int gsl_blas_ccopy (const gsl_vector_complex_float * X, gsl_vector_complex_float * Y); int gsl_blas_caxpy (const gsl_complex_float alpha, const gsl_vector_complex_float * X, gsl_vector_complex_float * Y); int gsl_blas_zswap (gsl_vector_complex * X, gsl_vector_complex * Y); int gsl_blas_zcopy (const gsl_vector_complex * X, gsl_vector_complex * Y); int gsl_blas_zaxpy (const gsl_complex alpha, const gsl_vector_complex * X, gsl_vector_complex * Y); int gsl_blas_srotg (float a[], float b[], float c[], float s[]); int gsl_blas_srotmg (float d1[], float d2[], float b1[], float b2, float P[]); int gsl_blas_srot (gsl_vector_float * X, gsl_vector_float * Y, float c, float s); int gsl_blas_srotm (gsl_vector_float * X, gsl_vector_float * Y, const float P[]); int gsl_blas_drotg (double a[], double b[], double c[], double s[]); int gsl_blas_drotmg (double d1[], double d2[], double b1[], double b2, double P[]); int gsl_blas_drot (gsl_vector * X, gsl_vector * Y, const double c, const double s); int gsl_blas_drotm (gsl_vector * X, gsl_vector * Y, const double P[]); void gsl_blas_sscal (float alpha, gsl_vector_float * X); void gsl_blas_dscal (double alpha, gsl_vector * X); void gsl_blas_cscal (const gsl_complex_float alpha, gsl_vector_complex_float * X); void gsl_blas_zscal (const gsl_complex alpha, gsl_vector_complex * X); void gsl_blas_csscal (float alpha, gsl_vector_complex_float * X); void gsl_blas_zdscal (double alpha, gsl_vector_complex * X); /* =========================================================================== * Level 2 * =========================================================================== */ /* * Routines with standard 4 prefixes (S, D, C, Z) */ int gsl_blas_sgemv (CBLAS_TRANSPOSE_t TransA, float alpha, const gsl_matrix_float * A, const gsl_vector_float * X, float beta, gsl_vector_float * Y); int gsl_blas_strmv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_float * A, gsl_vector_float * X); int gsl_blas_strsv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_float * A, gsl_vector_float * X); int gsl_blas_dgemv (CBLAS_TRANSPOSE_t TransA, double alpha, const gsl_matrix * A, const gsl_vector * X, double beta, gsl_vector * Y); int gsl_blas_dtrmv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix * A, gsl_vector * X); int gsl_blas_dtrsv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix * A, gsl_vector * X); int gsl_blas_cgemv (CBLAS_TRANSPOSE_t TransA, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_vector_complex_float * X, const gsl_complex_float beta, gsl_vector_complex_float * Y); int gsl_blas_ctrmv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_complex_float * A, gsl_vector_complex_float * X); int gsl_blas_ctrsv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_complex_float * A, gsl_vector_complex_float * X); int gsl_blas_zgemv (CBLAS_TRANSPOSE_t TransA, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_vector_complex * X, const gsl_complex beta, gsl_vector_complex * Y); int gsl_blas_ztrmv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_complex * A, gsl_vector_complex * X); int gsl_blas_ztrsv (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_matrix_complex * A, gsl_vector_complex *X); /* * Routines with S and D prefixes only */ int gsl_blas_ssymv (CBLAS_UPLO_t Uplo, float alpha, const gsl_matrix_float * A, const gsl_vector_float * X, float beta, gsl_vector_float * Y); int gsl_blas_sger (float alpha, const gsl_vector_float * X, const gsl_vector_float * Y, gsl_matrix_float * A); int gsl_blas_ssyr (CBLAS_UPLO_t Uplo, float alpha, const gsl_vector_float * X, gsl_matrix_float * A); int gsl_blas_ssyr2 (CBLAS_UPLO_t Uplo, float alpha, const gsl_vector_float * X, const gsl_vector_float * Y, gsl_matrix_float * A); int gsl_blas_dsymv (CBLAS_UPLO_t Uplo, double alpha, const gsl_matrix * A, const gsl_vector * X, double beta, gsl_vector * Y); int gsl_blas_dger (double alpha, const gsl_vector * X, const gsl_vector * Y, gsl_matrix * A); int gsl_blas_dsyr (CBLAS_UPLO_t Uplo, double alpha, const gsl_vector * X, gsl_matrix * A); int gsl_blas_dsyr2 (CBLAS_UPLO_t Uplo, double alpha, const gsl_vector * X, const gsl_vector * Y, gsl_matrix * A); /* * Routines with C and Z prefixes only */ int gsl_blas_chemv (CBLAS_UPLO_t Uplo, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_vector_complex_float * X, const gsl_complex_float beta, gsl_vector_complex_float * Y); int gsl_blas_cgeru (const gsl_complex_float alpha, const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_matrix_complex_float * A); int gsl_blas_cgerc (const gsl_complex_float alpha, const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_matrix_complex_float * A); int gsl_blas_cher (CBLAS_UPLO_t Uplo, float alpha, const gsl_vector_complex_float * X, gsl_matrix_complex_float * A); int gsl_blas_cher2 (CBLAS_UPLO_t Uplo, const gsl_complex_float alpha, const gsl_vector_complex_float * X, const gsl_vector_complex_float * Y, gsl_matrix_complex_float * A); int gsl_blas_zhemv (CBLAS_UPLO_t Uplo, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_vector_complex * X, const gsl_complex beta, gsl_vector_complex * Y); int gsl_blas_zgeru (const gsl_complex alpha, const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_matrix_complex * A); int gsl_blas_zgerc (const gsl_complex alpha, const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_matrix_complex * A); int gsl_blas_zher (CBLAS_UPLO_t Uplo, double alpha, const gsl_vector_complex * X, gsl_matrix_complex * A); int gsl_blas_zher2 (CBLAS_UPLO_t Uplo, const gsl_complex alpha, const gsl_vector_complex * X, const gsl_vector_complex * Y, gsl_matrix_complex * A); /* * =========================================================================== * Prototypes for level 3 BLAS * =========================================================================== */ /* * Routines with standard 4 prefixes (S, D, C, Z) */ int gsl_blas_sgemm (CBLAS_TRANSPOSE_t TransA, CBLAS_TRANSPOSE_t TransB, float alpha, const gsl_matrix_float * A, const gsl_matrix_float * B, float beta, gsl_matrix_float * C); int gsl_blas_ssymm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, float alpha, const gsl_matrix_float * A, const gsl_matrix_float * B, float beta, gsl_matrix_float * C); int gsl_blas_ssyrk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, float alpha, const gsl_matrix_float * A, float beta, gsl_matrix_float * C); int gsl_blas_ssyr2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, float alpha, const gsl_matrix_float * A, const gsl_matrix_float * B, float beta, gsl_matrix_float * C); int gsl_blas_strmm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, float alpha, const gsl_matrix_float * A, gsl_matrix_float * B); int gsl_blas_strsm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, float alpha, const gsl_matrix_float * A, gsl_matrix_float * B); int gsl_blas_dgemm (CBLAS_TRANSPOSE_t TransA, CBLAS_TRANSPOSE_t TransB, double alpha, const gsl_matrix * A, const gsl_matrix * B, double beta, gsl_matrix * C); int gsl_blas_dsymm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, double alpha, const gsl_matrix * A, const gsl_matrix * B, double beta, gsl_matrix * C); int gsl_blas_dsyrk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, double alpha, const gsl_matrix * A, double beta, gsl_matrix * C); int gsl_blas_dsyr2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, double alpha, const gsl_matrix * A, const gsl_matrix * B, double beta, gsl_matrix * C); int gsl_blas_dtrmm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, double alpha, const gsl_matrix * A, gsl_matrix * B); int gsl_blas_dtrsm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, double alpha, const gsl_matrix * A, gsl_matrix * B); int gsl_blas_cgemm (CBLAS_TRANSPOSE_t TransA, CBLAS_TRANSPOSE_t TransB, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, const gsl_complex_float beta, gsl_matrix_complex_float * C); int gsl_blas_csymm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, const gsl_complex_float beta, gsl_matrix_complex_float * C); int gsl_blas_csyrk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_complex_float beta, gsl_matrix_complex_float * C); int gsl_blas_csyr2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, const gsl_complex_float beta, gsl_matrix_complex_float * C); int gsl_blas_ctrmm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, gsl_matrix_complex_float * B); int gsl_blas_ctrsm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, gsl_matrix_complex_float * B); int gsl_blas_zgemm (CBLAS_TRANSPOSE_t TransA, CBLAS_TRANSPOSE_t TransB, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, const gsl_complex beta, gsl_matrix_complex * C); int gsl_blas_zsymm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, const gsl_complex beta, gsl_matrix_complex * C); int gsl_blas_zsyrk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_complex beta, gsl_matrix_complex * C); int gsl_blas_zsyr2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, const gsl_complex beta, gsl_matrix_complex *C); int gsl_blas_ztrmm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_complex alpha, const gsl_matrix_complex * A, gsl_matrix_complex * B); int gsl_blas_ztrsm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t TransA, CBLAS_DIAG_t Diag, const gsl_complex alpha, const gsl_matrix_complex * A, gsl_matrix_complex * B); /* * Routines with prefixes C and Z only */ int gsl_blas_chemm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, const gsl_complex_float beta, gsl_matrix_complex_float * C); int gsl_blas_cherk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, float alpha, const gsl_matrix_complex_float * A, float beta, gsl_matrix_complex_float * C); int gsl_blas_cher2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex_float alpha, const gsl_matrix_complex_float * A, const gsl_matrix_complex_float * B, float beta, gsl_matrix_complex_float * C); int gsl_blas_zhemm (CBLAS_SIDE_t Side, CBLAS_UPLO_t Uplo, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, const gsl_complex beta, gsl_matrix_complex * C); int gsl_blas_zherk (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, double alpha, const gsl_matrix_complex * A, double beta, gsl_matrix_complex * C); int gsl_blas_zher2k (CBLAS_UPLO_t Uplo, CBLAS_TRANSPOSE_t Trans, const gsl_complex alpha, const gsl_matrix_complex * A, const gsl_matrix_complex * B, double beta, gsl_matrix_complex * C); __END_DECLS #endif /* __GSL_BLAS_H__ */ sources_5316/external/gsl/gsl_sf__bessel_J0.c0000644000176700017670000000631710707442037020013 0ustar paulpaul/* specfunc/bessel_J0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_mode.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_amp_phase.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_sf__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besj0, 1977 version, w. fullerton */ /* chebyshev expansions for Bessel functions series for bj0 on the interval 0. to 1.60000d+01 with weighted error 7.47e-18 log weighted error 17.13 significant figures required 16.98 decimal places required 17.68 */ static double bj0_data[13] = { 0.100254161968939137, -0.665223007764405132, 0.248983703498281314, -0.0332527231700357697, 0.0023114179304694015, -0.0000991127741995080, 0.0000028916708643998, -0.0000000612108586630, 0.0000000009838650793, -0.0000000000124235515, 0.0000000000001265433, -0.0000000000000010619, 0.0000000000000000074, }; static cheb_series bj0_cs = { bj0_data, 12, -1, 1, 9 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_J0_e(const double x, gsl_sf_result * result) { double y = fabs(x); /* CHECK_POINTER(result) */ if(y < 2.0*GSL_SQRT_DBL_EPSILON) { result->val = 1.0; result->err = y*y; return GSL_SUCCESS; } else if(y <= 4.0) { return cheb_eval_e(&bj0_cs, 0.125*y*y - 1.0, result); } else { const double z = 32.0/(y*y) - 1.0; gsl_sf_result ca; gsl_sf_result ct; gsl_sf_result cp; const int stat_ca = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bm0_cs, z, &ca); const int stat_ct = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bth0_cs, z, &ct); const int stat_cp = gsl_sf_bessel_cos_pi4_e(y, ct.val/y, &cp); const double sqrty = sqrt(y); const double ampl = (0.75 + ca.val) / sqrty; result->val = ampl * cp.val; result->err = fabs(cp.val) * ca.err/sqrty + fabs(ampl) * cp.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_ca, stat_ct, stat_cp); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_J0(const double x) { EVAL_RESULT(gsl_sf_bessel_J0_e(x, &result)); } sources_5316/external/gsl/gsl_bspline__bspline.c0000664000176700017670000003001711723710247020661 0ustar paulpaul/* bspline/bspline.c * * Copyright (C) 2006 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_bspline.h" /* * This module contains routines related to calculating B-splines. * The algorithms used are described in * * [1] Carl de Boor, "A Practical Guide to Splines", Springer * Verlag, 1978. */ static int bspline_eval_all(const double x, gsl_vector *B, size_t *idx, gsl_bspline_workspace *w); static inline size_t bspline_find_interval(const double x, int *flag, gsl_bspline_workspace *w); /* gsl_bspline_alloc() Allocate space for a bspline workspace. The size of the workspace is O(5k + nbreak) Inputs: k - spline order (cubic = 4) nbreak - number of breakpoints Return: pointer to workspace */ gsl_bspline_workspace * gsl_bspline_alloc(const size_t k, const size_t nbreak) { if (k == 0) { GSL_ERROR_NULL("k must be at least 1", GSL_EINVAL); } else if (nbreak < 2) { GSL_ERROR_NULL("nbreak must be at least 2", GSL_EINVAL); } else { gsl_bspline_workspace *w; w = (gsl_bspline_workspace *) calloc(1, sizeof(gsl_bspline_workspace)); if (w == 0) { GSL_ERROR_NULL("failed to allocate space for workspace", GSL_ENOMEM); } w->k = k; w->km1 = k - 1; w->nbreak = nbreak; w->l = nbreak - 1; w->n = w->l + k - 1; w->knots = gsl_vector_alloc(w->n + k); if (w->knots == 0) { gsl_bspline_free(w); GSL_ERROR_NULL("failed to allocate space for knots vector", GSL_ENOMEM); } w->deltal = gsl_vector_alloc(k); w->deltar = gsl_vector_alloc(k); if (!w->deltal || !w->deltar) { gsl_bspline_free(w); GSL_ERROR_NULL("failed to allocate space for delta vectors", GSL_ENOMEM); } w->B = gsl_vector_alloc(k); if (w->B == 0) { gsl_bspline_free(w); GSL_ERROR_NULL("failed to allocate space for temporary spline vector", GSL_ENOMEM); } return (w); } } /* gsl_bspline_alloc() */ /* Return number of coefficients */ size_t gsl_bspline_ncoeffs (gsl_bspline_workspace * w) { return w->n; } /* Return order */ size_t gsl_bspline_order (gsl_bspline_workspace * w) { return w->k; } /* Return number of breakpoints */ size_t gsl_bspline_nbreak (gsl_bspline_workspace * w) { return w->nbreak; } double gsl_bspline_breakpoint (size_t i, gsl_bspline_workspace * w) { size_t j = i + w->k - 1; return gsl_vector_get(w->knots, j); } /* gsl_bspline_free() Free a bspline workspace Inputs: w - workspace to free Return: none */ void gsl_bspline_free(gsl_bspline_workspace *w) { if (!w) return; if (w->knots) gsl_vector_free(w->knots); if (w->deltal) gsl_vector_free(w->deltal); if (w->deltar) gsl_vector_free(w->deltar); if (w->B) gsl_vector_free(w->B); free(w); } /* gsl_bspline_free() */ /* gsl_bspline_knots() Compute the knots from the given breakpoints: knots(1:k) = breakpts(1) knots(k+1:k+l-1) = breakpts(i), i = 2 .. l knots(n+1:n+k) = breakpts(l + 1) where l is the number of polynomial pieces (l = nbreak - 1) and n = k + l - 1 (using matlab syntax for the arrays) The repeated knots at the beginning and end of the interval correspond to the continuity condition there. See pg. 119 of [1]. Inputs: breakpts - breakpoints w - bspline workspace Return: success or error */ int gsl_bspline_knots(const gsl_vector *breakpts, gsl_bspline_workspace *w) { if (breakpts->size != w->nbreak) { GSL_ERROR("breakpts vector has wrong size", GSL_EBADLEN); } else { size_t i; /* looping */ for (i = 0; i < w->k; ++i) gsl_vector_set(w->knots, i, gsl_vector_get(breakpts, 0)); for (i = 1; i < w->l; ++i) { gsl_vector_set(w->knots, w->k - 1 + i, gsl_vector_get(breakpts, i)); } for (i = w->n; i < w->n + w->k; ++i) gsl_vector_set(w->knots, i, gsl_vector_get(breakpts, w->l)); return GSL_SUCCESS; } } /* gsl_bspline_knots() */ /* gsl_bspline_knots_uniform() Construct uniformly spaced knots on the interval [a,b] using the previously specified number of breakpoints. 'a' is the position of the first breakpoint and 'b' is the position of the last breakpoint. Inputs: a - left side of interval b - right side of interval w - bspline workspace Return: success or error Notes: 1) w->knots is modified to contain the uniformly spaced knots 2) The knots vector is set up as follows (using octave syntax): knots(1:k) = a knots(k+1:k+l-1) = a + i*delta, i = 1 .. l - 1 knots(n+1:n+k) = b */ int gsl_bspline_knots_uniform(const double a, const double b, gsl_bspline_workspace *w) { size_t i; /* looping */ double delta; /* interval spacing */ double x; delta = (b - a) / (double) w->l; for (i = 0; i < w->k; ++i) gsl_vector_set(w->knots, i, a); x = a + delta; for (i = 0; i < w->l - 1; ++i) { gsl_vector_set(w->knots, w->k + i, x); x += delta; } for (i = w->n; i < w->n + w->k; ++i) gsl_vector_set(w->knots, i, b); return GSL_SUCCESS; } /* gsl_bspline_knots_uniform() */ /* gsl_bspline_eval() Evaluate the basis functions B_i(x) for all i. This is basically a wrapper function for bspline_eval_all() which formats the output in a nice way. Inputs: x - point for evaluation B - (output) where to store B_i(x) values the length of this vector is n = nbreak + k - 2 = l + k - 1 = w->n w - bspline workspace Return: success or error Notes: The w->knots vector must be initialized prior to calling this function (see gsl_bspline_knots()) */ int gsl_bspline_eval(const double x, gsl_vector *B, gsl_bspline_workspace *w) { if (B->size != w->n) { GSL_ERROR("B vector length does not match n", GSL_EBADLEN); } else { size_t i; /* looping */ size_t idx = 0; size_t start; /* first non-zero spline */ /* find all non-zero B_i(x) values */ bspline_eval_all(x, w->B, &idx, w); /* store values in appropriate part of given vector */ start = idx - w->k + 1; for (i = 0; i < start; ++i) gsl_vector_set(B, i, 0.0); for (i = start; i <= idx; ++i) gsl_vector_set(B, i, gsl_vector_get(w->B, i - start)); for (i = idx + 1; i < w->n; ++i) gsl_vector_set(B, i, 0.0); return GSL_SUCCESS; } } /* gsl_bspline_eval() */ /**************************************** * INTERNAL ROUTINES * ****************************************/ /* bspline_eval_all() Evaluate all non-zero B-splines B_i(x) using algorithm (8) of chapter X of [1] The idea is something like this. Given x \in [t_i, t_{i+1}] with t_i < t_{i+1} and the t_i are knots, the values of the B-splines not automatically zero fit into a triangular array as follows: 0 0 0 B_{i-2,3} B_{i-1,2} B_{i,1} B_{i-1,3} ... B_{i,2} 0 B_{i,3} 0 0 where B_{i,k} is the ith B-spline of order k. The boundary 0s indicate that those B-splines not in the table vanish at x. To compute the non-zero B-splines of a given order k, we use Eqs. (4) and (5) of chapter X of [1]: (4) B_{i,1}(x) = { 1, t_i <= x < t_{i+1} 0, else } (5) B_{i,k}(x) = (x - t_i) ----------------- B_{i,k-1}(x) (t_{i+k-1} - t_i) t_{i+k} - x + ----------------- B_{i+1,k-1}(x) t_{i+k} - t_{i+1} So (4) gives us the first column of the table and we can use the recurrence relation (5) to get the rest of the columns. Inputs: x - point at which to evaluate splines B - (output) where to store B-spline values (length k) idx - (output) B-spline function index of last output value (B_{idx}(x) is stored in the last slot of 'B') w - bspline workspace Return: success or error Notes: 1) the w->knots vector must be initialized before calling this function 2) On output, B contains: B = [B_{i-k+1,k}, B_{i-k+2,k}, ..., B_{i-1,k}, B_{i,k}] where 'i' is stored in 'idx' on output 3) based on PPPACK bsplvb */ static int bspline_eval_all(const double x, gsl_vector *B, size_t *idx, gsl_bspline_workspace *w) { if (B->size != w->k) { GSL_ERROR("B vector not of length k", GSL_EBADLEN); } else { size_t i; /* spline index */ size_t j; /* looping */ size_t ii; /* looping */ int flag = 0; /* error flag */ double saved; double term; i = bspline_find_interval(x, &flag, w); if (flag == -1) { GSL_ERROR("x outside of knot interval", GSL_EINVAL); } else if (flag == 1) { if (x <= gsl_vector_get(w->knots, i) + GSL_DBL_EPSILON) { --i; } else { GSL_ERROR("x outside of knot interval", GSL_EINVAL); } } *idx = i; gsl_vector_set(B, 0, 1.0); for (j = 0; j < w->k - 1; ++j) { gsl_vector_set(w->deltar, j, gsl_vector_get(w->knots, i + j + 1) - x); gsl_vector_set(w->deltal, j, x - gsl_vector_get(w->knots, i - j)); saved = 0.0; for (ii = 0; ii <= j; ++ii) { term = gsl_vector_get(B, ii) / (gsl_vector_get(w->deltar, ii) + gsl_vector_get(w->deltal, j - ii)); gsl_vector_set(B, ii, saved + gsl_vector_get(w->deltar, ii) * term); saved = gsl_vector_get(w->deltal, j - ii) * term; } gsl_vector_set(B, j + 1, saved); } return GSL_SUCCESS; } } /* bspline_eval_all() */ /* bspline_find_interval() Find knot interval such that t_i <= x < t_{i + 1} where the t_i are knot values. Inputs: x - x value flag - (output) error flag w - bspline workspace Return: i (index in w->knots corresponding to left limit of interval) Notes: The error conditions are reported as follows: Condition Return value Flag --------- ------------ ---- x < t_0 0 -1 t_i <= x < t_{i+1} i 0 t_{n+k-1} <= x l+k-1 +1 */ static inline size_t bspline_find_interval(const double x, int *flag, gsl_bspline_workspace *w) { size_t i; if (x < gsl_vector_get(w->knots, 0)) { *flag = -1; return 0; } /* find i such that t_i <= x < t_{i+1} */ for (i = w->k - 1; i < w->k + w->l - 1; ++i) { const double ti = gsl_vector_get(w->knots, i); const double tip1 = gsl_vector_get(w->knots, i + 1); if (tip1 < ti) { GSL_ERROR("knots vector is not increasing", GSL_EINVAL); } if (ti <= x && x < tip1) break; } if (i == w->k + w->l - 1) *flag = 1; else *flag = 0; return i; } /* bspline_find_interval() */ sources_5316/external/gsl/gsl_rng__coveyou.c0000664000176700017670000000431311723710247020050 0ustar paulpaul/* rng/coveyou.c * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth * The Art of Computer Programming * Volume 2 * Third Edition * Addison-Wesley * Section 3.2.2 * * This implementation copyright (C) 2001 Carlo Perassi * and (C) 2003 Heiko Bauke. * Carlo Perassi reorganized the code to use the rng framework of GSL. */ #include "gsl__config.h" #include #include "gsl_rng.h" #define MM 0xffffffffUL /* 2 ^ 32 - 1 */ static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); typedef struct { unsigned long int x; } ran_state_t; static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; state->x = (state->x * (state->x + 1)) & MM; return state->x; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 4294967296.0; } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; unsigned long int diff = ((s % 4UL) - 2UL) % MM; if (diff) state->x = (s - diff) & MM; else state->x = s & MM; return; } static const gsl_rng_type ran_type = { "coveyou", /* name */ MM-1, /* RAND_MAX */ 2, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_coveyou = &ran_type; sources_5316/external/gsl/gsl_statistics__wvariance.c0000664000176700017670000000076311723710247021747 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__wvariance_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__wvariance_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__wvariance_source.c" #include "templates_off.h" #undef BASE_FLOAT sources_5316/external/gsl/gsl_histogram__get2d.c0000664000176700017670000000473711723710247020605 0ustar paulpaul/* histogram/get2d.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_histogram2d.h" #include "gsl_histogram__find.c" double gsl_histogram2d_get (const gsl_histogram2d * h, const size_t i, const size_t j) { const size_t nx = h->nx; const size_t ny = h->ny; if (i >= nx) { GSL_ERROR_VAL ("index i lies outside valid range of 0 .. nx - 1", GSL_EDOM, 0); } if (j >= ny) { GSL_ERROR_VAL ("index j lies outside valid range of 0 .. ny - 1", GSL_EDOM, 0); } return h->bin[i * ny + j]; } int gsl_histogram2d_get_xrange (const gsl_histogram2d * h, const size_t i, double *xlower, double *xupper) { const size_t nx = h->nx; if (i >= nx) { GSL_ERROR ("index i lies outside valid range of 0 .. nx - 1", GSL_EDOM); } *xlower = h->xrange[i]; *xupper = h->xrange[i + 1]; return GSL_SUCCESS; } int gsl_histogram2d_get_yrange (const gsl_histogram2d * h, const size_t j, double *ylower, double *yupper) { const size_t ny = h->ny; if (j >= ny) { GSL_ERROR ("index j lies outside valid range of 0 .. ny - 1", GSL_EDOM); } *ylower = h->yrange[j]; *yupper = h->yrange[j + 1]; return GSL_SUCCESS; } int gsl_histogram2d_find (const gsl_histogram2d * h, const double x, const double y, size_t * i, size_t * j) { int status = find (h->nx, h->xrange, x, i); if (status) { GSL_ERROR ("x not found in range of h", GSL_EDOM); } status = find (h->ny, h->yrange, y, j); if (status) { GSL_ERROR ("y not found in range of h", GSL_EDOM); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_matrix__view.c0000664000176700017670000000746211723710247020057 0ustar paulpaul#include "gsl__config.h" #include "gsl_errno.h" #include "gsl_matrix.h" #include "gsl_matrix__view.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_CHAR #define USE_QUALIFIER #define QUALIFIER const #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__view_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_matrix_complex_float.h0000664000176700017670000003161511705263724021607 0ustar paulpaul/* matrix/gsl_matrix_complex_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_COMPLEX_FLOAT_H__ #define __GSL_MATRIX_COMPLEX_FLOAT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_check_range.h" #include "gsl_vector_complex_float.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; float * data; gsl_block_complex_float * block; int owner; } gsl_matrix_complex_float ; typedef struct { gsl_matrix_complex_float matrix; } _gsl_matrix_complex_float_view; typedef _gsl_matrix_complex_float_view gsl_matrix_complex_float_view; typedef struct { gsl_matrix_complex_float matrix; } _gsl_matrix_complex_float_const_view; typedef const _gsl_matrix_complex_float_const_view gsl_matrix_complex_float_const_view; /* Allocation */ gsl_matrix_complex_float * gsl_matrix_complex_float_alloc (const size_t n1, const size_t n2); gsl_matrix_complex_float * gsl_matrix_complex_float_calloc (const size_t n1, const size_t n2); gsl_matrix_complex_float * gsl_matrix_complex_float_alloc_from_block (gsl_block_complex_float * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_complex_float * gsl_matrix_complex_float_alloc_from_matrix (gsl_matrix_complex_float * b, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_complex_float * gsl_vector_complex_float_alloc_row_from_matrix (gsl_matrix_complex_float * m, const size_t i); gsl_vector_complex_float * gsl_vector_complex_float_alloc_col_from_matrix (gsl_matrix_complex_float * m, const size_t j); void gsl_matrix_complex_float_free (gsl_matrix_complex_float * m); /* Views */ _gsl_matrix_complex_float_view gsl_matrix_complex_float_submatrix (gsl_matrix_complex_float * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_complex_float_view gsl_matrix_complex_float_row (gsl_matrix_complex_float * m, const size_t i); _gsl_vector_complex_float_view gsl_matrix_complex_float_column (gsl_matrix_complex_float * m, const size_t j); _gsl_vector_complex_float_view gsl_matrix_complex_float_diagonal (gsl_matrix_complex_float * m); _gsl_vector_complex_float_view gsl_matrix_complex_float_subdiagonal (gsl_matrix_complex_float * m, const size_t k); _gsl_vector_complex_float_view gsl_matrix_complex_float_superdiagonal (gsl_matrix_complex_float * m, const size_t k); _gsl_vector_complex_float_view gsl_matrix_complex_float_subrow (gsl_matrix_complex_float * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_complex_float_view gsl_matrix_complex_float_subcolumn (gsl_matrix_complex_float * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_complex_float_view gsl_matrix_complex_float_view_array (float * base, const size_t n1, const size_t n2); _gsl_matrix_complex_float_view gsl_matrix_complex_float_view_array_with_tda (float * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_complex_float_view gsl_matrix_complex_float_view_vector (gsl_vector_complex_float * v, const size_t n1, const size_t n2); _gsl_matrix_complex_float_view gsl_matrix_complex_float_view_vector_with_tda (gsl_vector_complex_float * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_complex_float_const_view gsl_matrix_complex_float_const_submatrix (const gsl_matrix_complex_float * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_complex_float_const_view gsl_matrix_complex_float_const_row (const gsl_matrix_complex_float * m, const size_t i); _gsl_vector_complex_float_const_view gsl_matrix_complex_float_const_column (const gsl_matrix_complex_float * m, const size_t j); _gsl_vector_complex_float_const_view gsl_matrix_complex_float_const_diagonal (const gsl_matrix_complex_float * m); _gsl_vector_complex_float_const_view gsl_matrix_complex_float_const_subdiagonal (const gsl_matrix_complex_float * m, const size_t k); _gsl_vector_complex_float_const_view gsl_matrix_complex_float_const_superdiagonal (const gsl_matrix_complex_float * m, const size_t k); _gsl_vector_complex_float_const_view gsl_matrix_complex_float_const_subrow (const gsl_matrix_complex_float * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_complex_float_const_view gsl_matrix_complex_float_const_subcolumn (const gsl_matrix_complex_float * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_complex_float_const_view gsl_matrix_complex_float_const_view_array (const float * base, const size_t n1, const size_t n2); _gsl_matrix_complex_float_const_view gsl_matrix_complex_float_const_view_array_with_tda (const float * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_complex_float_const_view gsl_matrix_complex_float_const_view_vector (const gsl_vector_complex_float * v, const size_t n1, const size_t n2); _gsl_matrix_complex_float_const_view gsl_matrix_complex_float_const_view_vector_with_tda (const gsl_vector_complex_float * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ gsl_complex_float gsl_matrix_complex_float_get(const gsl_matrix_complex_float * m, const size_t i, const size_t j); void gsl_matrix_complex_float_set(gsl_matrix_complex_float * m, const size_t i, const size_t j, const gsl_complex_float x); gsl_complex_float * gsl_matrix_complex_float_ptr(gsl_matrix_complex_float * m, const size_t i, const size_t j); const gsl_complex_float * gsl_matrix_complex_float_const_ptr(const gsl_matrix_complex_float * m, const size_t i, const size_t j); void gsl_matrix_complex_float_set_zero (gsl_matrix_complex_float * m); void gsl_matrix_complex_float_set_identity (gsl_matrix_complex_float * m); void gsl_matrix_complex_float_set_all (gsl_matrix_complex_float * m, gsl_complex_float x); int gsl_matrix_complex_float_fread (FILE * stream, gsl_matrix_complex_float * m) ; int gsl_matrix_complex_float_fwrite (FILE * stream, const gsl_matrix_complex_float * m) ; int gsl_matrix_complex_float_fscanf (FILE * stream, gsl_matrix_complex_float * m); int gsl_matrix_complex_float_fprintf (FILE * stream, const gsl_matrix_complex_float * m, const char * format); int gsl_matrix_complex_float_memcpy(gsl_matrix_complex_float * dest, const gsl_matrix_complex_float * src); int gsl_matrix_complex_float_swap(gsl_matrix_complex_float * m1, gsl_matrix_complex_float * m2); int gsl_matrix_complex_float_swap_rows(gsl_matrix_complex_float * m, const size_t i, const size_t j); int gsl_matrix_complex_float_swap_columns(gsl_matrix_complex_float * m, const size_t i, const size_t j); int gsl_matrix_complex_float_swap_rowcol(gsl_matrix_complex_float * m, const size_t i, const size_t j); int gsl_matrix_complex_float_transpose (gsl_matrix_complex_float * m); int gsl_matrix_complex_float_transpose_memcpy (gsl_matrix_complex_float * dest, const gsl_matrix_complex_float * src); int gsl_matrix_complex_float_isnull (const gsl_matrix_complex_float * m); int gsl_matrix_complex_float_ispos (const gsl_matrix_complex_float * m); int gsl_matrix_complex_float_isneg (const gsl_matrix_complex_float * m); int gsl_matrix_complex_float_isnonneg (const gsl_matrix_complex_float * m); int gsl_matrix_complex_float_add (gsl_matrix_complex_float * a, const gsl_matrix_complex_float * b); int gsl_matrix_complex_float_sub (gsl_matrix_complex_float * a, const gsl_matrix_complex_float * b); int gsl_matrix_complex_float_mul_elements (gsl_matrix_complex_float * a, const gsl_matrix_complex_float * b); int gsl_matrix_complex_float_div_elements (gsl_matrix_complex_float * a, const gsl_matrix_complex_float * b); int gsl_matrix_complex_float_scale (gsl_matrix_complex_float * a, const gsl_complex_float x); int gsl_matrix_complex_float_add_constant (gsl_matrix_complex_float * a, const gsl_complex_float x); int gsl_matrix_complex_float_add_diagonal (gsl_matrix_complex_float * a, const gsl_complex_float x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_complex_float_get_row(gsl_vector_complex_float * v, const gsl_matrix_complex_float * m, const size_t i); int gsl_matrix_complex_float_get_col(gsl_vector_complex_float * v, const gsl_matrix_complex_float * m, const size_t j); int gsl_matrix_complex_float_set_row(gsl_matrix_complex_float * m, const size_t i, const gsl_vector_complex_float * v); int gsl_matrix_complex_float_set_col(gsl_matrix_complex_float * m, const size_t j, const gsl_vector_complex_float * v); #ifdef HAVE_INLINE extern inline gsl_complex_float gsl_matrix_complex_float_get(const gsl_matrix_complex_float * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK gsl_complex_float zero = {{0,0}}; if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, zero) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, zero) ; } #endif return *(gsl_complex_float *)(m->data + 2*(i * m->tda + j)) ; } extern inline void gsl_matrix_complex_float_set(gsl_matrix_complex_float * m, const size_t i, const size_t j, const gsl_complex_float x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif *(gsl_complex_float *)(m->data + 2*(i * m->tda + j)) = x ; } extern inline gsl_complex_float * gsl_matrix_complex_float_ptr(gsl_matrix_complex_float * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (gsl_complex_float *)(m->data + 2*(i * m->tda + j)) ; } extern inline const gsl_complex_float * gsl_matrix_complex_float_const_ptr(const gsl_matrix_complex_float * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const gsl_complex_float *)(m->data + 2*(i * m->tda + j)) ; } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_MATRIX_COMPLEX_FLOAT_H__ */ sources_5316/external/gsl/gsl_multimin__simplex.c0000664000176700017670000002600011723710247021105 0ustar paulpaul/* multimin/simplex.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 2002 Tuomo Keskitalo, Ivo Alxneit * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* - Originally written by Tuomo Keskitalo - Corrections to nmsimplex_iterate and other functions by Ivo Alxneit - Additional help by Brian Gough */ /* The Simplex method of Nelder and Mead, also known as the polytope search alogorithm. Ref: Nelder, J.A., Mead, R., Computer Journal 7 (1965) pp. 308-313. This implementation uses n+1 corner points in the simplex. */ #include "gsl__config.h" #include #include "gsl_blas.h" #include "gsl_multimin.h" typedef struct { gsl_matrix *x1; /* simplex corner points */ gsl_vector *y1; /* function value at corner points */ gsl_vector *ws1; /* workspace 1 for algorithm */ gsl_vector *ws2; /* workspace 2 for algorithm */ } nmsimplex_state_t; static double nmsimplex_move_corner (const double coeff, const nmsimplex_state_t * state, size_t corner, gsl_vector * xc, const gsl_multimin_function * f) { /* moves a simplex corner scaled by coeff (negative value represents mirroring by the middle point of the "other" corner points) and gives new corner in xc and function value at xc as a return value */ gsl_matrix *x1 = state->x1; size_t i, j; double newval, mp; for (j = 0; j < x1->size2; j++) { mp = 0.0; for (i = 0; i < x1->size1; i++) { if (i != corner) { mp += (gsl_matrix_get (x1, i, j)); } } mp /= (double) (x1->size1 - 1); newval = mp - coeff * (mp - gsl_matrix_get (x1, corner, j)); gsl_vector_set (xc, j, newval); } newval = GSL_MULTIMIN_FN_EVAL (f, xc); return newval; } static int nmsimplex_contract_by_best (nmsimplex_state_t * state, size_t best, gsl_vector * xc, gsl_multimin_function * f) { /* Function contracts the simplex in respect to best valued corner. That is, all corners besides the best corner are moved. */ /* the xc vector is simply work space here */ gsl_matrix *x1 = state->x1; gsl_vector *y1 = state->y1; size_t i, j; double newval; int status = GSL_SUCCESS; for (i = 0; i < x1->size1; i++) { if (i != best) { for (j = 0; j < x1->size2; j++) { newval = 0.5 * (gsl_matrix_get (x1, i, j) + gsl_matrix_get (x1, best, j)); gsl_matrix_set (x1, i, j, newval); } /* evaluate function in the new point */ gsl_matrix_get_row (xc, x1, i); newval = GSL_MULTIMIN_FN_EVAL (f, xc); gsl_vector_set (y1, i, newval); /* notify caller that we found at least one bad function value. we finish the contraction (and do not abort) to allow the user to handle the situation */ if(!gsl_finite(newval)) { status = GSL_EBADFUNC; } } } return status; } static int nmsimplex_calc_center (const nmsimplex_state_t * state, gsl_vector * mp) { /* calculates the center of the simplex to mp */ gsl_matrix *x1 = state->x1; size_t i, j; double val; for (j = 0; j < x1->size2; j++) { val = 0.0; for (i = 0; i < x1->size1; i++) { val += gsl_matrix_get (x1, i, j); } val /= x1->size1; gsl_vector_set (mp, j, val); } return GSL_SUCCESS; } static double nmsimplex_size (nmsimplex_state_t * state) { /* calculates simplex size as average sum of length of vectors from simplex center to corner points: ( sum ( || y - y_middlepoint || ) ) / n */ gsl_vector *s = state->ws1; gsl_vector *mp = state->ws2; gsl_matrix *x1 = state->x1; size_t i; double ss = 0.0; /* Calculate middle point */ nmsimplex_calc_center (state, mp); for (i = 0; i < x1->size1; i++) { gsl_matrix_get_row (s, x1, i); gsl_blas_daxpy (-1.0, mp, s); ss += gsl_blas_dnrm2 (s); } return ss / (double) (x1->size1); } static int nmsimplex_alloc (void *vstate, size_t n) { nmsimplex_state_t *state = (nmsimplex_state_t *) vstate; if (n == 0) { GSL_ERROR("invalid number of parameters specified", GSL_EINVAL); } state->x1 = gsl_matrix_alloc (n + 1, n); if (state->x1 == NULL) { GSL_ERROR ("failed to allocate space for x1", GSL_ENOMEM); } state->y1 = gsl_vector_alloc (n + 1); if (state->y1 == NULL) { gsl_matrix_free(state->x1); GSL_ERROR ("failed to allocate space for y", GSL_ENOMEM); } state->ws1 = gsl_vector_alloc (n); if (state->ws1 == NULL) { gsl_matrix_free(state->x1); gsl_vector_free(state->y1); GSL_ERROR ("failed to allocate space for ws1", GSL_ENOMEM); } state->ws2 = gsl_vector_alloc (n); if (state->ws2 == NULL) { gsl_matrix_free(state->x1); gsl_vector_free(state->y1); gsl_vector_free(state->ws1); GSL_ERROR ("failed to allocate space for ws2", GSL_ENOMEM); } return GSL_SUCCESS; } static int nmsimplex_set (void *vstate, gsl_multimin_function * f, const gsl_vector * x, double *size, const gsl_vector * step_size) { int status; size_t i; double val; nmsimplex_state_t *state = (nmsimplex_state_t *) vstate; gsl_vector *xtemp = state->ws1; if (xtemp->size != x->size) { GSL_ERROR("incompatible size of x", GSL_EINVAL); } if (xtemp->size != step_size->size) { GSL_ERROR("incompatible size of step_size", GSL_EINVAL); } /* first point is the original x0 */ val = GSL_MULTIMIN_FN_EVAL (f, x); if (!gsl_finite(val)) { GSL_ERROR("non-finite function value encountered", GSL_EBADFUNC); } gsl_matrix_set_row (state->x1, 0, x); gsl_vector_set (state->y1, 0, val); /* following points are initialized to x0 + step_size */ for (i = 0; i < x->size; i++) { status = gsl_vector_memcpy (xtemp, x); if (status != 0) { GSL_ERROR ("vector memcopy failed", GSL_EFAILED); } val = gsl_vector_get (xtemp, i) + gsl_vector_get (step_size, i); gsl_vector_set (xtemp, i, val); val = GSL_MULTIMIN_FN_EVAL (f, xtemp); if (!gsl_finite(val)) { GSL_ERROR("non-finite function value encountered", GSL_EBADFUNC); } gsl_matrix_set_row (state->x1, i + 1, xtemp); gsl_vector_set (state->y1, i + 1, val); } /* Initialize simplex size */ *size = nmsimplex_size (state); return GSL_SUCCESS; } static void nmsimplex_free (void *vstate) { nmsimplex_state_t *state = (nmsimplex_state_t *) vstate; gsl_matrix_free (state->x1); gsl_vector_free (state->y1); gsl_vector_free (state->ws1); gsl_vector_free (state->ws2); } static int nmsimplex_iterate (void *vstate, gsl_multimin_function * f, gsl_vector * x, double *size, double *fval) { /* Simplex iteration tries to minimize function f value */ /* Includes corrections from Ivo Alxneit */ nmsimplex_state_t *state = (nmsimplex_state_t *) vstate; /* xc and xc2 vectors store tried corner point coordinates */ gsl_vector *xc = state->ws1; gsl_vector *xc2 = state->ws2; gsl_vector *y1 = state->y1; gsl_matrix *x1 = state->x1; size_t n = y1->size; size_t i; size_t hi = 0, s_hi = 0, lo = 0; double dhi, ds_hi, dlo; int status; double val, val2; if (xc->size != x->size) { GSL_ERROR("incompatible size of x", GSL_EINVAL); } /* get index of highest, second highest and lowest point */ dhi = ds_hi = dlo = gsl_vector_get (y1, 0); for (i = 1; i < n; i++) { val = (gsl_vector_get (y1, i)); if (val < dlo) { dlo = val; lo = i; } else if (val > dhi) { ds_hi = dhi; s_hi = hi; dhi = val; hi = i; } else if (val > ds_hi) { ds_hi = val; s_hi = i; } } /* reflect the highest value */ val = nmsimplex_move_corner (-1.0, state, hi, xc, f); if (gsl_finite(val) && val < gsl_vector_get (y1, lo)) { /* reflected point becomes lowest point, try expansion */ val2 = nmsimplex_move_corner (-2.0, state, hi, xc2, f); if (gsl_finite(val2) && val2 < gsl_vector_get (y1, lo)) { gsl_matrix_set_row (x1, hi, xc2); gsl_vector_set (y1, hi, val2); } else { gsl_matrix_set_row (x1, hi, xc); gsl_vector_set (y1, hi, val); } } /* reflection does not improve things enough or we got a non-finite (illegal) function value */ else if (!gsl_finite(val) || val > gsl_vector_get (y1, s_hi)) { if (gsl_finite(val) && val <= gsl_vector_get (y1, hi)) { /* if trial point is better than highest point, replace highest point */ gsl_matrix_set_row (x1, hi, xc); gsl_vector_set (y1, hi, val); } /* try one dimensional contraction */ val2 = nmsimplex_move_corner (0.5, state, hi, xc2, f); if (gsl_finite(val2) && val2 <= gsl_vector_get (y1, hi)) { gsl_matrix_set_row (state->x1, hi, xc2); gsl_vector_set (y1, hi, val2); } else { /* contract the whole simplex in respect to the best point */ status = nmsimplex_contract_by_best (state, lo, xc, f); if (status != GSL_SUCCESS) { GSL_ERROR ("nmsimplex_contract_by_best failed", GSL_EFAILED); } } } else { /* trial point is better than second highest point. Replace highest point by it */ gsl_matrix_set_row (x1, hi, xc); gsl_vector_set (y1, hi, val); } /* return lowest point of simplex as x */ lo = gsl_vector_min_index (y1); gsl_matrix_get_row (x, x1, lo); *fval = gsl_vector_get (y1, lo); /* Update simplex size */ *size = nmsimplex_size (state); return GSL_SUCCESS; } static const gsl_multimin_fminimizer_type nmsimplex_type = { "nmsimplex", /* name */ sizeof (nmsimplex_state_t), &nmsimplex_alloc, &nmsimplex_set, &nmsimplex_iterate, &nmsimplex_free }; const gsl_multimin_fminimizer_type * gsl_multimin_fminimizer_nmsimplex = &nmsimplex_type; sources_5316/external/gsl/gsl_sf_zeta.h0000664000176700017670000000551211705263724017017 0ustar paulpaul/* specfunc/gsl_sf_zeta.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_ZETA_H__ #define __GSL_SF_ZETA_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Riemann Zeta Function * zeta(n) = Sum[ k^(-n), {k,1,Infinity} ] * * n=integer, n != 1 * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_zeta_int_e(const int n, gsl_sf_result * result); double gsl_sf_zeta_int(const int n); /* Riemann Zeta Function * zeta(x) = Sum[ k^(-s), {k,1,Infinity} ], s != 1.0 * * s != 1.0 * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_zeta_e(const double s, gsl_sf_result * result); double gsl_sf_zeta(const double s); /* Riemann Zeta Function minus 1 * useful for evaluating the fractional part * of Riemann zeta for large argument * * s != 1.0 * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_zetam1_e(const double s, gsl_sf_result * result); double gsl_sf_zetam1(const double s); /* Riemann Zeta Function minus 1 for integer arg * useful for evaluating the fractional part * of Riemann zeta for large argument * * s != 1.0 * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_zetam1_int_e(const int s, gsl_sf_result * result); double gsl_sf_zetam1_int(const int s); /* Hurwitz Zeta Function * zeta(s,q) = Sum[ (k+q)^(-s), {k,0,Infinity} ] * * s > 1.0, q > 0.0 * exceptions: GSL_EDOM, GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_hzeta_e(const double s, const double q, gsl_sf_result * result); double gsl_sf_hzeta(const double s, const double q); /* Eta Function * eta(n) = (1-2^(1-n)) zeta(n) * * exceptions: GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_eta_int_e(int n, gsl_sf_result * result); double gsl_sf_eta_int(const int n); /* Eta Function * eta(s) = (1-2^(1-s)) zeta(s) * * exceptions: GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_eta_e(const double s, gsl_sf_result * result); double gsl_sf_eta(const double s); __END_DECLS #endif /* __GSL_SF_ZETA_H__ */ sources_5316/external/gsl/gsl_sf__cheb_eval_mode.c0000644000176700017670000000125010707442037021110 0ustar paulpaulstatic inline int cheb_eval_mode_e(const cheb_series * cs, const double x, gsl_mode_t mode, gsl_sf_result * result) { int j; double d = 0.0; double dd = 0.0; double y = (2.*x - cs->a - cs->b) / (cs->b - cs->a); double y2 = 2.0 * y; int eval_order; if(GSL_MODE_PREC(mode) == GSL_PREC_DOUBLE) eval_order = cs->order; else eval_order = cs->order_sp; for(j = eval_order; j>=1; j--) { double temp = d; d = y2*d - dd + cs->c[j]; dd = temp; } result->val = y*d - dd + 0.5 * cs->c[0]; result->err = GSL_DBL_EPSILON * fabs(result->val) + fabs(cs->c[eval_order]); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_vector_complex_double.h0000664000176700017670000001661011705263724021750 0ustar paulpaul/* vector/gsl_vector_complex_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_COMPLEX_DOUBLE_H__ #define __GSL_VECTOR_COMPLEX_DOUBLE_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_check_range.h" #include "gsl_vector_double.h" #include "gsl_vector_complex.h" #include "gsl_block_complex_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; double *data; gsl_block_complex *block; int owner; } gsl_vector_complex; typedef struct { gsl_vector_complex vector; } _gsl_vector_complex_view; typedef _gsl_vector_complex_view gsl_vector_complex_view; typedef struct { gsl_vector_complex vector; } _gsl_vector_complex_const_view; typedef const _gsl_vector_complex_const_view gsl_vector_complex_const_view; /* Allocation */ gsl_vector_complex *gsl_vector_complex_alloc (const size_t n); gsl_vector_complex *gsl_vector_complex_calloc (const size_t n); gsl_vector_complex * gsl_vector_complex_alloc_from_block (gsl_block_complex * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_complex * gsl_vector_complex_alloc_from_vector (gsl_vector_complex * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_complex_free (gsl_vector_complex * v); /* Views */ _gsl_vector_complex_view gsl_vector_complex_view_array (double *base, size_t n); _gsl_vector_complex_view gsl_vector_complex_view_array_with_stride (double *base, size_t stride, size_t n); _gsl_vector_complex_const_view gsl_vector_complex_const_view_array (const double *base, size_t n); _gsl_vector_complex_const_view gsl_vector_complex_const_view_array_with_stride (const double *base, size_t stride, size_t n); _gsl_vector_complex_view gsl_vector_complex_subvector (gsl_vector_complex *base, size_t i, size_t n); _gsl_vector_complex_view gsl_vector_complex_subvector_with_stride (gsl_vector_complex *v, size_t i, size_t stride, size_t n); _gsl_vector_complex_const_view gsl_vector_complex_const_subvector (const gsl_vector_complex *base, size_t i, size_t n); _gsl_vector_complex_const_view gsl_vector_complex_const_subvector_with_stride (const gsl_vector_complex *v, size_t i, size_t stride, size_t n); _gsl_vector_view gsl_vector_complex_real (gsl_vector_complex *v); _gsl_vector_view gsl_vector_complex_imag (gsl_vector_complex *v); _gsl_vector_const_view gsl_vector_complex_const_real (const gsl_vector_complex *v); _gsl_vector_const_view gsl_vector_complex_const_imag (const gsl_vector_complex *v); /* Operations */ gsl_complex gsl_vector_complex_get (const gsl_vector_complex * v, const size_t i); void gsl_vector_complex_set (gsl_vector_complex * v, const size_t i, gsl_complex z); gsl_complex *gsl_vector_complex_ptr (gsl_vector_complex * v, const size_t i); const gsl_complex *gsl_vector_complex_const_ptr (const gsl_vector_complex * v, const size_t i); void gsl_vector_complex_set_zero (gsl_vector_complex * v); void gsl_vector_complex_set_all (gsl_vector_complex * v, gsl_complex z); int gsl_vector_complex_set_basis (gsl_vector_complex * v, size_t i); int gsl_vector_complex_fread (FILE * stream, gsl_vector_complex * v); int gsl_vector_complex_fwrite (FILE * stream, const gsl_vector_complex * v); int gsl_vector_complex_fscanf (FILE * stream, gsl_vector_complex * v); int gsl_vector_complex_fprintf (FILE * stream, const gsl_vector_complex * v, const char *format); int gsl_vector_complex_memcpy (gsl_vector_complex * dest, const gsl_vector_complex * src); int gsl_vector_complex_reverse (gsl_vector_complex * v); int gsl_vector_complex_swap (gsl_vector_complex * v, gsl_vector_complex * w); int gsl_vector_complex_swap_elements (gsl_vector_complex * v, const size_t i, const size_t j); int gsl_vector_complex_isnull (const gsl_vector_complex * v); int gsl_vector_complex_ispos (const gsl_vector_complex * v); int gsl_vector_complex_isneg (const gsl_vector_complex * v); int gsl_vector_complex_isnonneg (const gsl_vector_complex * v); #ifdef HAVE_INLINE extern inline gsl_complex gsl_vector_complex_get (const gsl_vector_complex * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { gsl_complex zero = {{0, 0}}; GSL_ERROR_VAL ("index out of range", GSL_EINVAL, zero); } #endif return *GSL_COMPLEX_AT (v, i); } extern inline void gsl_vector_complex_set (gsl_vector_complex * v, const size_t i, gsl_complex z) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif *GSL_COMPLEX_AT (v, i) = z; } extern inline gsl_complex * gsl_vector_complex_ptr (gsl_vector_complex * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return GSL_COMPLEX_AT (v, i); } extern inline const gsl_complex * gsl_vector_complex_const_ptr (const gsl_vector_complex * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return GSL_COMPLEX_AT (v, i); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_COMPLEX_DOUBLE_H__ */ sources_5316/external/gsl/gsl_cblas__source_symm_c.h0000664000176700017670000002023711705263724021537 0ustar paulpaul/* blas/source_symm_c.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; INDEX n1, n2; int uplo, side; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; if (Order == CblasRowMajor) { n1 = M; n2 = N; uplo = Uplo; side = Side; } else { n1 = N; n2 = M; uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; side = (Side == CblasLeft) ? CblasRight : CblasLeft; } /* form y := beta*y */ if (beta_real == 0.0 && beta_imag == 0.0) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Cij_real = REAL(C, ldc * i + j); const BASE Cij_imag = IMAG(C, ldc * i + j); REAL(C, ldc * i + j) = beta_real * Cij_real - beta_imag * Cij_imag; IMAG(C, ldc * i + j) = beta_real * Cij_imag + beta_imag * Cij_real; } } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; if (side == CblasLeft && uplo == CblasUpper) { /* form C := alpha*A*B + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = CONST_REAL(B, ldb * i + j); const BASE Bij_imag = CONST_IMAG(B, ldb * i + j); const BASE temp1_real = alpha_real * Bij_real - alpha_imag * Bij_imag; const BASE temp1_imag = alpha_real * Bij_imag + alpha_imag * Bij_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; { const BASE Aii_real = CONST_REAL(A, i * lda + i); const BASE Aii_imag = CONST_IMAG(A, i * lda + i); REAL(C, i * ldc + j) += temp1_real * Aii_real - temp1_imag * Aii_imag; IMAG(C, i * ldc + j) += temp1_real * Aii_imag + temp1_imag * Aii_real; } for (k = i + 1; k < n1; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Bkj_real = CONST_REAL(B, ldb * k + j); const BASE Bkj_imag = CONST_IMAG(B, ldb * k + j); REAL(C, k * ldc + j) += Aik_real * temp1_real - Aik_imag * temp1_imag; IMAG(C, k * ldc + j) += Aik_real * temp1_imag + Aik_imag * temp1_real; temp2_real += Aik_real * Bkj_real - Aik_imag * Bkj_imag; temp2_imag += Aik_real * Bkj_imag + Aik_imag * Bkj_real; } REAL(C, i * ldc + j) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(C, i * ldc + j) += alpha_real * temp2_imag + alpha_imag * temp2_real; } } } else if (side == CblasLeft && uplo == CblasLower) { /* form C := alpha*A*B + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = CONST_REAL(B, ldb * i + j); const BASE Bij_imag = CONST_IMAG(B, ldb * i + j); const BASE temp1_real = alpha_real * Bij_real - alpha_imag * Bij_imag; const BASE temp1_imag = alpha_real * Bij_imag + alpha_imag * Bij_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; for (k = 0; k < i; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Bkj_real = CONST_REAL(B, ldb * k + j); const BASE Bkj_imag = CONST_IMAG(B, ldb * k + j); REAL(C, k * ldc + j) += Aik_real * temp1_real - Aik_imag * temp1_imag; IMAG(C, k * ldc + j) += Aik_real * temp1_imag + Aik_imag * temp1_real; temp2_real += Aik_real * Bkj_real - Aik_imag * Bkj_imag; temp2_imag += Aik_real * Bkj_imag + Aik_imag * Bkj_real; } { const BASE Aii_real = CONST_REAL(A, i * lda + i); const BASE Aii_imag = CONST_IMAG(A, i * lda + i); REAL(C, i * ldc + j) += temp1_real * Aii_real - temp1_imag * Aii_imag; IMAG(C, i * ldc + j) += temp1_real * Aii_imag + temp1_imag * Aii_real; } REAL(C, i * ldc + j) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(C, i * ldc + j) += alpha_real * temp2_imag + alpha_imag * temp2_real; } } } else if (side == CblasRight && uplo == CblasUpper) { /* form C := alpha*B*A + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = CONST_REAL(B, ldb * i + j); const BASE Bij_imag = CONST_IMAG(B, ldb * i + j); const BASE temp1_real = alpha_real * Bij_real - alpha_imag * Bij_imag; const BASE temp1_imag = alpha_real * Bij_imag + alpha_imag * Bij_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; { const BASE Ajj_real = CONST_REAL(A, j * lda + j); const BASE Ajj_imag = CONST_IMAG(A, j * lda + j); REAL(C, i * ldc + j) += temp1_real * Ajj_real - temp1_imag * Ajj_imag; IMAG(C, i * ldc + j) += temp1_real * Ajj_imag + temp1_imag * Ajj_real; } for (k = j + 1; k < n2; k++) { const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); const BASE Bik_real = CONST_REAL(B, ldb * i + k); const BASE Bik_imag = CONST_IMAG(B, ldb * i + k); REAL(C, i * ldc + k) += temp1_real * Ajk_real - temp1_imag * Ajk_imag; IMAG(C, i * ldc + k) += temp1_real * Ajk_imag + temp1_imag * Ajk_real; temp2_real += Bik_real * Ajk_real - Bik_imag * Ajk_imag; temp2_imag += Bik_real * Ajk_imag + Bik_imag * Ajk_real; } REAL(C, i * ldc + j) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(C, i * ldc + j) += alpha_real * temp2_imag + alpha_imag * temp2_real; } } } else if (side == CblasRight && uplo == CblasLower) { /* form C := alpha*B*A + C */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { const BASE Bij_real = CONST_REAL(B, ldb * i + j); const BASE Bij_imag = CONST_IMAG(B, ldb * i + j); const BASE temp1_real = alpha_real * Bij_real - alpha_imag * Bij_imag; const BASE temp1_imag = alpha_real * Bij_imag + alpha_imag * Bij_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; for (k = 0; k < j; k++) { const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = CONST_IMAG(A, j * lda + k); const BASE Bik_real = CONST_REAL(B, ldb * i + k); const BASE Bik_imag = CONST_IMAG(B, ldb * i + k); REAL(C, i * ldc + k) += temp1_real * Ajk_real - temp1_imag * Ajk_imag; IMAG(C, i * ldc + k) += temp1_real * Ajk_imag + temp1_imag * Ajk_real; temp2_real += Bik_real * Ajk_real - Bik_imag * Ajk_imag; temp2_imag += Bik_real * Ajk_imag + Bik_imag * Ajk_real; } { const BASE Ajj_real = CONST_REAL(A, j * lda + j); const BASE Ajj_imag = CONST_IMAG(A, j * lda + j); REAL(C, i * ldc + j) += temp1_real * Ajj_real - temp1_imag * Ajj_imag; IMAG(C, i * ldc + j) += temp1_real * Ajj_imag + temp1_imag * Ajj_real; } REAL(C, i * ldc + j) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(C, i * ldc + j) += alpha_real * temp2_imag + alpha_imag * temp2_real; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_fft_real.h0000664000176700017670000000425411705263724017150 0ustar paulpaul/* fft/gsl_fft_real.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_FFT_REAL_H__ #define __GSL_FFT_REAL_H__ #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_fft.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_fft_real_radix2_transform (double data[], const size_t stride, const size_t n) ; typedef struct { size_t n; size_t nf; size_t factor[64]; gsl_complex *twiddle[64]; gsl_complex *trig; } gsl_fft_real_wavetable; typedef struct { size_t n; double *scratch; } gsl_fft_real_workspace; gsl_fft_real_wavetable * gsl_fft_real_wavetable_alloc (size_t n); void gsl_fft_real_wavetable_free (gsl_fft_real_wavetable * wavetable); gsl_fft_real_workspace * gsl_fft_real_workspace_alloc (size_t n); void gsl_fft_real_workspace_free (gsl_fft_real_workspace * workspace); int gsl_fft_real_transform (double data[], const size_t stride, const size_t n, const gsl_fft_real_wavetable * wavetable, gsl_fft_real_workspace * work); int gsl_fft_real_unpack (const double real_coefficient[], double complex_coefficient[], const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_FFT_REAL_H__ */ sources_5316/external/gsl/gsl_specfunc.h0000664000176700017670000000025111705263724017165 0ustar paulpaul/* Author: G. Jungman */ /* Convenience header */ #ifndef __GSL_SPECFUNC_H__ #define __GSL_SPECFUNC_H__ #include "gsl_sf.h" #endif /* __GSL_SPECFUNC_H__ */ sources_5316/external/gsl/gsl_cblas__zgeru.c0000664000176700017670000000054111723710247020010 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zgeru (const enum CBLAS_ORDER order, const int M, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda) { #define BASE double #include "gsl_cblas__source_geru.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_tpmv_r.h0000664000176700017670000000630311705263724021555 0ustar paulpaul/* blas/source_tpmv_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; const int nonunit = (Diag == CblasNonUnit); const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; if (N == 0) return; if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { /* form x:= A*x */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE atmp = Ap[TPUP(N, i, i)]; BASE temp = (nonunit ? X[ix] * atmp : X[ix]); INDEX jx = OFFSET(N, incX) + (i + 1) * incX; for (j = i + 1; j < N; j++) { atmp = Ap[TPUP(N, i, j)]; temp += atmp * X[jx]; jx += incX; } X[ix] = temp; ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { BASE atmp = Ap[TPLO(N, i, i)]; BASE temp = (nonunit ? X[ix] * atmp : X[ix]); INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { atmp = Ap[TPLO(N, i, j)]; temp += atmp * X[jx]; jx += incX; } X[ix] = temp; ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := A'*x */ INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { BASE atmp = Ap[TPUP(N, i, i)]; BASE temp = (nonunit ? X[ix] * atmp : X[ix]); INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { atmp = Ap[TPUP(N, j, i)]; temp += atmp * X[jx]; jx += incX; } X[ix] = temp; ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE atmp = Ap[TPLO(N, i, i)]; BASE temp = (nonunit ? X[ix] * atmp : X[ix]); INDEX jx = OFFSET(N, incX) + (i + 1) * incX; for (j = i + 1; j < N; j++) { atmp = Ap[TPLO(N, j, i)]; temp += atmp * X[jx]; jx += incX; } X[ix] = temp; ix += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_rng__taus.c0000664000176700017670000001266511723710247017344 0ustar paulpaul/* rng/taus.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is a maximally equidistributed combined Tausworthe generator. The sequence is, x_n = (s1_n ^ s2_n ^ s3_n) s1_{n+1} = (((s1_n & 4294967294) <<12) ^ (((s1_n <<13) ^ s1_n) >>19)) s2_{n+1} = (((s2_n & 4294967288) << 4) ^ (((s2_n << 2) ^ s2_n) >>25)) s3_{n+1} = (((s3_n & 4294967280) <<17) ^ (((s3_n << 3) ^ s3_n) >>11)) computed modulo 2^32. In the three formulas above '^' means exclusive-or (C-notation), not exponentiation. Note that the algorithm relies on the properties of 32-bit unsigned integers (it is formally defined on bit-vectors of length 32). I have added a bitmask to make it work on 64 bit machines. We initialize the generator with s1_1 .. s3_1 = s_n MOD m, where s_n = (69069 * s_{n-1}) mod 2^32, and s_0 = s is the user-supplied seed. The theoretical value of x_{10007} is 2733957125. The subscript 10007 means (1) seed the generator with s=1 (2) do six warm-up iterations, (3) then do 10000 actual iterations. The period of this generator is about 2^88. From: P. L'Ecuyer, "Maximally Equidistributed Combined Tausworthe Generators", Mathematics of Computation, 65, 213 (1996), 203--213. This is available on the net from L'Ecuyer's home page, http://www.iro.umontreal.ca/~lecuyer/myftp/papers/tausme.ps ftp://ftp.iro.umontreal.ca/pub/simulation/lecuyer/papers/tausme.ps Update: April 2002 There is an erratum in the paper "Tables of Maximally Equidistributed Combined LFSR Generators", Mathematics of Computation, 68, 225 (1999), 261--269: http://www.iro.umontreal.ca/~lecuyer/myftp/papers/tausme2.ps ... the k_j most significant bits of z_j must be non- zero, for each j. (Note: this restriction also applies to the computer code given in [4], but was mistakenly not mentioned in that paper.) This affects the seeding procedure by imposing the requirement s1 > 1, s2 > 7, s3 > 15. The generator taus2 has been added to satisfy this requirement. The original taus generator is unchanged. Update: November 2002 There was a bug in the correction to the seeding procedure for s2. It affected the following seeds 254679140 1264751179 1519430319 2274823218 2529502358 3284895257 3539574397 (s2 < 8). */ static inline unsigned long int taus_get (void *vstate); static double taus_get_double (void *vstate); static void taus_set (void *state, unsigned long int s); typedef struct { unsigned long int s1, s2, s3; } taus_state_t; static inline unsigned long taus_get (void *vstate) { taus_state_t *state = (taus_state_t *) vstate; #define MASK 0xffffffffUL #define TAUSWORTHE(s,a,b,c,d) (((s &c) <>b) state->s1 = TAUSWORTHE (state->s1, 13, 19, 4294967294UL, 12); state->s2 = TAUSWORTHE (state->s2, 2, 25, 4294967288UL, 4); state->s3 = TAUSWORTHE (state->s3, 3, 11, 4294967280UL, 17); return (state->s1 ^ state->s2 ^ state->s3); } static double taus_get_double (void *vstate) { return taus_get (vstate) / 4294967296.0 ; } static void taus_set (void *vstate, unsigned long int s) { taus_state_t *state = (taus_state_t *) vstate; if (s == 0) s = 1; /* default seed is 1 */ #define LCG(n) ((69069 * n) & 0xffffffffUL) state->s1 = LCG (s); state->s2 = LCG (state->s1); state->s3 = LCG (state->s2); /* "warm it up" */ taus_get (state); taus_get (state); taus_get (state); taus_get (state); taus_get (state); taus_get (state); return; } static void taus2_set (void *vstate, unsigned long int s) { taus_state_t *state = (taus_state_t *) vstate; if (s == 0) s = 1; /* default seed is 1 */ #define LCG(n) ((69069 * n) & 0xffffffffUL) state->s1 = LCG (s); if (state->s1 < 2) state->s1 += 2UL; state->s2 = LCG (state->s1); if (state->s2 < 8) state->s2 += 8UL; state->s3 = LCG (state->s2); if (state->s3 < 16) state->s3 += 16UL; /* "warm it up" */ taus_get (state); taus_get (state); taus_get (state); taus_get (state); taus_get (state); taus_get (state); return; } static const gsl_rng_type taus_type = {"taus", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (taus_state_t), &taus_set, &taus_get, &taus_get_double}; const gsl_rng_type *gsl_rng_taus = &taus_type; static const gsl_rng_type taus2_type = {"taus2", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (taus_state_t), &taus2_set, &taus_get, &taus_get_double}; const gsl_rng_type *gsl_rng_taus2 = &taus2_type; sources_5316/external/gsl/gsl_statistics_long.h0000664000176700017670000001036711705263724020601 0ustar paulpaul/* statistics/gsl_statistics_long.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_LONG_H__ #define __GSL_STATISTICS_LONG_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_long_mean (const long data[], const size_t stride, const size_t n); double gsl_stats_long_variance (const long data[], const size_t stride, const size_t n); double gsl_stats_long_sd (const long data[], const size_t stride, const size_t n); double gsl_stats_long_variance_with_fixed_mean (const long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_sd_with_fixed_mean (const long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_absdev (const long data[], const size_t stride, const size_t n); double gsl_stats_long_skew (const long data[], const size_t stride, const size_t n); double gsl_stats_long_kurtosis (const long data[], const size_t stride, const size_t n); double gsl_stats_long_lag1_autocorrelation (const long data[], const size_t stride, const size_t n); double gsl_stats_long_covariance (const long data1[], const size_t stride1,const long data2[], const size_t stride2, const size_t n); double gsl_stats_long_correlation (const long data1[], const size_t stride1,const long data2[], const size_t stride2, const size_t n); double gsl_stats_long_variance_m (const long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_sd_m (const long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_absdev_m (const long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_skew_m_sd (const long data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_long_kurtosis_m_sd (const long data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_long_lag1_autocorrelation_m (const long data[], const size_t stride, const size_t n, const double mean); double gsl_stats_long_covariance_m (const long data1[], const size_t stride1,const long data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); double gsl_stats_long_pvariance (const long data1[], const size_t stride1, const size_t n1, const long data2[], const size_t stride2, const size_t n2); double gsl_stats_long_ttest (const long data1[], const size_t stride1, const size_t n1, const long data2[], const size_t stride2, const size_t n2); long gsl_stats_long_max (const long data[], const size_t stride, const size_t n); long gsl_stats_long_min (const long data[], const size_t stride, const size_t n); void gsl_stats_long_minmax (long * min, long * max, const long data[], const size_t stride, const size_t n); size_t gsl_stats_long_max_index (const long data[], const size_t stride, const size_t n); size_t gsl_stats_long_min_index (const long data[], const size_t stride, const size_t n); void gsl_stats_long_minmax_index (size_t * min_index, size_t * max_index, const long data[], const size_t stride, const size_t n); double gsl_stats_long_median_from_sorted_data (const long sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_long_quantile_from_sorted_data (const long sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_LONG_H__ */ sources_5316/external/gsl/gsl_integration__qagp.c0000664000176700017670000002731411723710247021052 0ustar paulpaul/* integration/qagp.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_integration.h" static int qagp (const gsl_function *f, const double *pts, const size_t npts, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr, gsl_integration_rule * q); #include "gsl_integration__initialise.c" #include "gsl_integration__qpsrt.c" #include "gsl_integration__util.c" #include "gsl_integration__append.c" #include "gsl_integration__reset.c" #include "gsl_integration__qelg.c" #include "gsl_integration__qpsrt2.c" #include "gsl_integration__ptsort.c" #include "gsl_integration__positivity.c" int gsl_integration_qagp (const gsl_function *f, double * pts, size_t npts, double epsabs, double epsrel, size_t limit, gsl_integration_workspace * workspace, double * result, double * abserr) { int status = qagp (f, pts, npts, epsabs, epsrel, limit, workspace, result, abserr, &gsl_integration_qk21) ; return status ; } static int qagp (const gsl_function * f, const double *pts, const size_t npts, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr, gsl_integration_rule * q) { double area, errsum; double res_ext, err_ext; double result0, abserr0, resabs0; double tolerance; double ertest = 0; double error_over_large_intervals = 0; double reseps = 0, abseps = 0, correc = 0; size_t ktmin = 0; int roundoff_type1 = 0, roundoff_type2 = 0, roundoff_type3 = 0; int error_type = 0, error_type2 = 0; size_t iteration = 0; int positive_integrand = 0; int extrapolate = 0; int disallow_extrapolation = 0; struct extrapolation_table table; const size_t nint = npts - 1; /* number of intervals */ size_t *ndin = workspace->level; /* temporarily alias ndin to level */ size_t i; /* Initialize results */ *result = 0; *abserr = 0; /* Test on validity of parameters */ if (limit > workspace->limit) { GSL_ERROR ("iteration limit exceeds available workspace", GSL_EINVAL) ; } if (npts > workspace->limit) { GSL_ERROR ("npts exceeds size of workspace", GSL_EINVAL); } if (epsabs <= 0 && (epsrel < 50 * GSL_DBL_EPSILON || epsrel < 0.5e-28)) { GSL_ERROR ("tolerance cannot be acheived with given epsabs and epsrel", GSL_EBADTOL); } /* Check that the integration range and break points are an ascending sequence */ for (i = 0; i < nint; i++) { if (pts[i + 1] < pts[i]) { GSL_ERROR ("points are not in an ascending sequence", GSL_EINVAL); } } /* Perform the first integration */ result0 = 0; abserr0 = 0; resabs0 = 0; initialise (workspace, 0.0, 0.0) ; for (i = 0; i < nint; i++) { double area1, error1, resabs1, resasc1; const double a1 = pts[i]; const double b1 = pts[i + 1]; q (f, a1, b1, &area1, &error1, &resabs1, &resasc1); result0 = result0 + area1; abserr0 = abserr0 + error1; resabs0 = resabs0 + resabs1; append_interval (workspace, a1, b1, area1, error1); if (error1 == resasc1 && error1 != 0.0) { ndin[i] = 1; } else { ndin[i] = 0; } } /* Compute the initial error estimate */ errsum = 0.0; for (i = 0; i < nint; i++) { if (ndin[i]) { workspace->elist[i] = abserr0; } errsum = errsum + workspace->elist[i]; } for (i = 0; i < nint; i++) { workspace->level[i] = 0; } /* Sort results into order of decreasing error via the indirection array order[] */ sort_results (workspace); /* Test on accuracy */ tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (result0)); if (abserr0 <= 100 * GSL_DBL_EPSILON * resabs0 && abserr0 > tolerance) { *result = result0; *abserr = abserr0; GSL_ERROR ("cannot reach tolerance because of roundoff error" "on first attempt", GSL_EROUND); } else if (abserr0 <= tolerance) { *result = result0; *abserr = abserr0; return GSL_SUCCESS; } else if (limit == 1) { *result = result0; *abserr = abserr0; GSL_ERROR ("a maximum of one iteration was insufficient", GSL_EMAXITER); } /* Initialization */ initialise_table (&table); append_table (&table, result0); area = result0; res_ext = result0; err_ext = GSL_DBL_MAX; error_over_large_intervals = errsum; ertest = tolerance; positive_integrand = test_positivity (result0, resabs0); iteration = nint - 1; do { size_t current_level; double a1, b1, a2, b2; double a_i, b_i, r_i, e_i; double area1 = 0, area2 = 0, area12 = 0; double error1 = 0, error2 = 0, error12 = 0; double resasc1, resasc2; double resabs1, resabs2; double last_e_i; /* Bisect the subinterval with the largest error estimate */ retrieve (workspace, &a_i, &b_i, &r_i, &e_i); current_level = workspace->level[workspace->i] + 1; a1 = a_i; b1 = 0.5 * (a_i + b_i); a2 = b1; b2 = b_i; iteration++; q (f, a1, b1, &area1, &error1, &resabs1, &resasc1); q (f, a2, b2, &area2, &error2, &resabs2, &resasc2); area12 = area1 + area2; error12 = error1 + error2; last_e_i = e_i; /* Improve previous approximations to the integral and test for accuracy. We write these expressions in the same way as the original QUADPACK code so that the rounding errors are the same, which makes testing easier. */ errsum = errsum + error12 - e_i; area = area + area12 - r_i; tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (area)); if (resasc1 != error1 && resasc2 != error2) { double delta = r_i - area12; if (fabs (delta) <= 1.0e-5 * fabs (area12) && error12 >= 0.99 * e_i) { if (!extrapolate) { roundoff_type1++; } else { roundoff_type2++; } } if (i > 10 && error12 > e_i) { roundoff_type3++; } } /* Test for roundoff and eventually set error flag */ if (roundoff_type1 + roundoff_type2 >= 10 || roundoff_type3 >= 20) { error_type = 2; /* round off error */ } if (roundoff_type2 >= 5) { error_type2 = 1; } /* set error flag in the case of bad integrand behaviour at a point of the integration range */ if (subinterval_too_small (a1, a2, b2)) { error_type = 4; } /* append the newly-created intervals to the list */ update (workspace, a1, b1, area1, error1, a2, b2, area2, error2); if (errsum <= tolerance) { goto compute_result; } if (error_type) { break; } if (iteration >= limit - 1) { error_type = 1; break; } if (disallow_extrapolation) { continue; } error_over_large_intervals += -last_e_i; if (current_level < workspace->maximum_level) { error_over_large_intervals += error12; } if (!extrapolate) { /* test whether the interval to be bisected next is the smallest interval. */ if (large_interval (workspace)) continue; extrapolate = 1; workspace->nrmax = 1; } /* The smallest interval has the largest error. Before bisecting decrease the sum of the errors over the larger intervals (error_over_large_intervals) and perform extrapolation. */ if (!error_type2 && error_over_large_intervals > ertest) { if (increase_nrmax (workspace)) continue; } /* Perform extrapolation */ append_table (&table, area); if (table.n < 3) { goto skip_extrapolation; } qelg (&table, &reseps, &abseps); ktmin++; if (ktmin > 5 && err_ext < 0.001 * errsum) { error_type = 5; } if (abseps < err_ext) { ktmin = 0; err_ext = abseps; res_ext = reseps; correc = error_over_large_intervals; ertest = GSL_MAX_DBL (epsabs, epsrel * fabs (reseps)); if (err_ext <= ertest) break; } /* Prepare bisection of the smallest interval. */ if (table.n == 1) { disallow_extrapolation = 1; } if (error_type == 5) { break; } skip_extrapolation: reset_nrmax (workspace); extrapolate = 0; error_over_large_intervals = errsum; } while (iteration < limit); *result = res_ext; *abserr = err_ext; if (err_ext == GSL_DBL_MAX) goto compute_result; if (error_type || error_type2) { if (error_type2) { err_ext += correc; } if (error_type == 0) error_type = 3; if (result != 0 && area != 0) { if (err_ext / fabs (res_ext) > errsum / fabs (area)) goto compute_result; } else if (err_ext > errsum) { goto compute_result; } else if (area == 0.0) { goto return_error; } } /* Test on divergence. */ { double max_area = GSL_MAX_DBL (fabs (res_ext), fabs (area)); if (!positive_integrand && max_area < 0.01 * resabs0) goto return_error; } { double ratio = res_ext / area; if (ratio < 0.01 || ratio > 100 || errsum > fabs (area)) error_type = 6; } goto return_error; compute_result: *result = sum_results (workspace); *abserr = errsum; return_error: if (error_type > 2) error_type--; if (error_type == 0) { return GSL_SUCCESS; } else if (error_type == 1) { GSL_ERROR ("number of iterations was insufficient", GSL_EMAXITER); } else if (error_type == 2) { GSL_ERROR ("cannot reach tolerance because of roundoff error", GSL_EROUND); } else if (error_type == 3) { GSL_ERROR ("bad integrand behavior found in the integration interval", GSL_ESING); } else if (error_type == 4) { GSL_ERROR ("roundoff error detected in the extrapolation table", GSL_EROUND); } else if (error_type == 5) { GSL_ERROR ("integral is divergent, or slowly convergent", GSL_EDIVERGE); } else { GSL_ERROR ("could not integrate function", GSL_EFAILED); } } sources_5316/external/gsl/gsl_fft__complex_internal.h0000664000176700017670000000055611705263724021730 0ustar paulpaul/* Handling of packed complex types... not meant for client consumption. */ #ifndef COMPLEX_INTERNAL_H_ #define COMPLEX_INTERNAL_H_ #define VECTOR(a,stride,i) ((a)[(stride)*(i)]) #define REAL(a,stride,i) ((a)[2*(stride)*(i)]) #define IMAG(a,stride,i) ((a)[2*(stride)*(i)+1]) #define REAL0(a) ((a)[0]) #define IMAG0(a) ((a)[1]) #endif /* !COMPLEX_INTERNAL_H_ */ sources_5316/external/gsl/gsl_sum__levin_utrunc.c0000664000176700017670000001353511723710247021120 0ustar paulpaul/* sum/levin_utrunc.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_test.h" #include "gsl_errno.h" #include "gsl_sum.h" int gsl_sum_levin_utrunc_accel (const double *array, const size_t array_size, gsl_sum_levin_utrunc_workspace * w, double *sum_accel, double *abserr_trunc) { return gsl_sum_levin_utrunc_minmax (array, array_size, 0, array_size - 1, w, sum_accel, abserr_trunc); } int gsl_sum_levin_utrunc_minmax (const double *array, const size_t array_size, const size_t min_terms, const size_t max_terms, gsl_sum_levin_utrunc_workspace * w, double *sum_accel, double *abserr_trunc) { if (array_size == 0) { *sum_accel = 0.0; *abserr_trunc = 0.0; w->sum_plain = 0.0; w->terms_used = 0; return GSL_SUCCESS; } else if (array_size == 1) { *sum_accel = array[0]; *abserr_trunc = GSL_POSINF; w->sum_plain = array[0]; w->terms_used = 1; return GSL_SUCCESS; } else { const double SMALL = 0.01; const size_t nmax = GSL_MAX (max_terms, array_size) - 1; double trunc_n = 0.0, trunc_nm1 = 0.0; double actual_trunc_n = 0.0, actual_trunc_nm1 = 0.0; double result_n = 0.0, result_nm1 = 0.0; size_t n; int better = 0; int before = 0; int converging = 0; double least_trunc = GSL_DBL_MAX; double result_least_trunc; /* Calculate specified minimum number of terms. No convergence tests are made, and no truncation information is stored. */ for (n = 0; n < min_terms; n++) { const double t = array[n]; result_nm1 = result_n; gsl_sum_levin_utrunc_step (t, n, w, &result_n); } /* Assume the result after the minimum calculation is the best. */ result_least_trunc = result_n; /* Calculate up to maximum number of terms. Check truncation condition. */ for (; n <= nmax; n++) { const double t = array[n]; result_nm1 = result_n; gsl_sum_levin_utrunc_step (t, n, w, &result_n); /* Compute the truncation error directly */ actual_trunc_nm1 = actual_trunc_n; actual_trunc_n = fabs (result_n - result_nm1); /* Average results to make a more reliable estimate of the real truncation error */ trunc_nm1 = trunc_n; trunc_n = 0.5 * (actual_trunc_n + actual_trunc_nm1); /* Determine if we are in the convergence region. */ better = (trunc_n < trunc_nm1 || trunc_n < SMALL * fabs (result_n)); converging = converging || (better && before); before = better; if (converging) { if (trunc_n < least_trunc) { /* Found a low truncation point in the convergence region. Save it. */ least_trunc = trunc_n; result_least_trunc = result_n; } if (fabs (trunc_n / result_n) < 10.0 * GSL_MACH_EPS) break; } } if (converging) { /* Stopped in the convergence region. Return result and error estimate. */ *sum_accel = result_least_trunc; *abserr_trunc = least_trunc; w->terms_used = n; return GSL_SUCCESS; } else { /* Never reached the convergence region. Use the last calculated values. */ *sum_accel = result_n; *abserr_trunc = trunc_n; w->terms_used = n; return GSL_SUCCESS; } } } int gsl_sum_levin_utrunc_step (const double term, const size_t n, gsl_sum_levin_utrunc_workspace * w, double *sum_accel) { if (term == 0.0) { /* This is actually harmless when treated in this way. A term which is exactly zero is simply ignored; the state is not changed. We return GSL_EZERODIV as an indicator that this occured. */ return GSL_EZERODIV; } else if (n == 0) { *sum_accel = term; w->sum_plain = term; w->q_den[0] = 1.0 / term; w->q_num[0] = 1.0; return GSL_SUCCESS; } else { double factor = 1.0; double ratio = (double) n / (n + 1.0); int j; w->sum_plain += term; w->q_den[n] = 1.0 / (term * (n + 1.0) * (n + 1.0)); w->q_num[n] = w->sum_plain * w->q_den[n]; for (j = n - 1; j >= 0; j--) { double c = factor * (j + 1) / (n + 1); factor *= ratio; w->q_den[j] = w->q_den[j + 1] - c * w->q_den[j]; w->q_num[j] = w->q_num[j + 1] - c * w->q_num[j]; } *sum_accel = w->q_num[0] / w->q_den[0]; return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_statistics__wabsdev_source.c0000664000176700017670000000327111723710247023000 0ustar paulpaul/* statistics/wabsdev_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,wabsdev) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n) { const double wmean = FUNCTION(gsl_stats,wmean)(w, wstride, data, stride, n); return FUNCTION(gsl_stats,wabsdev_m)(w, wstride, data, stride, n, wmean); } double FUNCTION(gsl_stats,wabsdev_m) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n, const double wmean) { /* Compute the weighted absolute deviation of a dataset */ long double wabsdev = 0; long double W = 0; size_t i; /* find the sum of the absolute deviations */ for (i = 0; i < n; i++) { BASE wi = w[i * wstride]; if (wi > 0) { const long double delta = fabs(data[i * stride] - wmean); W += wi ; wabsdev += (delta - wabsdev) * (wi / W); } } return wabsdev; } sources_5316/external/gsl/gsl_specfunc__hyperg_U.c0000664000176700017670000012742011723710247021166 0ustar paulpaul/* specfunc/hyperg_U.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_bessel.h" #include "gsl_sf_laguerre.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_hyperg.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__hyperg.h" #define INT_THRESHOLD (1000.0*GSL_DBL_EPSILON) #define SERIES_EVAL_OK(a,b,x) ((fabs(a) < 5 && b < 5 && x < 2.0) || (fabs(a) < 10 && b < 10 && x < 1.0)) #define ASYMP_EVAL_OK(a,b,x) (GSL_MAX_DBL(fabs(a),1.0)*GSL_MAX_DBL(fabs(1.0+a-b),1.0) < 0.99*fabs(x)) /* Log[U(a,2a,x)] * [Abramowitz+stegun, 13.6.21] * Assumes x > 0, a > 1/2. */ static int hyperg_lnU_beq2a(const double a, const double x, gsl_sf_result * result) { const double lx = log(x); const double nu = a - 0.5; const double lnpre = 0.5*(x - M_LNPI) - nu*lx; gsl_sf_result lnK; gsl_sf_bessel_lnKnu_e(nu, 0.5*x, &lnK); result->val = lnpre + lnK.val; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(0.5*x) + 0.5*M_LNPI + fabs(nu*lx)); result->err += lnK.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /* Evaluate u_{N+1}/u_N by Steed's continued fraction method. * * u_N := Gamma[a+N]/Gamma[a] U(a + N, b, x) * * u_{N+1}/u_N = (a+N) U(a+N+1,b,x)/U(a+N,b,x) */ static int hyperg_U_CF1(const double a, const double b, const int N, const double x, double * result, int * count) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 20000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = -(a + N); double b1 = (b - 2.0*a - x - 2.0*(N+1)); double An = b1*Anm1 + a1*Anm2; double Bn = b1*Bnm1 + a1*Bnm2; double an, bn; double fn = An/Bn; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = -(a + N + n - b)*(a + N + n - 1.0); bn = (b - 2.0*a - x - 2.0*(N+n)); An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 10.0*GSL_DBL_EPSILON) break; } *result = fn; *count = n; if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /* Large x asymptotic for x^a U(a,b,x) * Based on SLATEC D9CHU() [W. Fullerton] * * Uses a rational approximation due to Luke. * See [Luke, Algorithms for the Computation of Special Functions, p. 252] * [Luke, Utilitas Math. (1977)] * * z^a U(a,b,z) ~ 2F0(a,1+a-b,-1/z) * * This assumes that a is not a negative integer and * that 1+a-b is not a negative integer. If one of them * is, then the 2F0 actually terminates, the above * relation is an equality, and the sum should be * evaluated directly [see below]. */ static int d9chu(const double a, const double b, const double x, gsl_sf_result * result) { const double EPS = 8.0 * GSL_DBL_EPSILON; /* EPS = 4.0D0*D1MACH(4) */ const int maxiter = 500; double aa[4], bb[4]; int i; double bp = 1.0 + a - b; double ab = a*bp; double ct2 = 2.0 * (x - ab); double sab = a + bp; double ct3 = sab + 1.0 + ab; double anbn = ct3 + sab + 3.0; double ct1 = 1.0 + 2.0*x/anbn; bb[0] = 1.0; aa[0] = 1.0; bb[1] = 1.0 + 2.0*x/ct3; aa[1] = 1.0 + ct2/ct3; bb[2] = 1.0 + 6.0*ct1*x/ct3; aa[2] = 1.0 + 6.0*ab/anbn + 3.0*ct1*ct2/ct3; for(i=4; ival = aa[3]/bb[3]; result->err = 8.0 * GSL_DBL_EPSILON * fabs(result->val); if(i == maxiter) { GSL_ERROR ("error", GSL_EMAXITER); } else { return GSL_SUCCESS; } } /* Evaluate asymptotic for z^a U(a,b,z) ~ 2F0(a,1+a-b,-1/z) * We check for termination of the 2F0 as a special case. * Assumes x > 0. * Also assumes a,b are not too large compared to x. */ static int hyperg_zaU_asymp(const double a, const double b, const double x, gsl_sf_result *result) { const double ap = a; const double bp = 1.0 + a - b; const double rintap = floor(ap + 0.5); const double rintbp = floor(bp + 0.5); const int ap_neg_int = ( ap < 0.0 && fabs(ap - rintap) < INT_THRESHOLD ); const int bp_neg_int = ( bp < 0.0 && fabs(bp - rintbp) < INT_THRESHOLD ); if(ap_neg_int || bp_neg_int) { /* Evaluate 2F0 polynomial. */ double mxi = -1.0/x; double nmax = -(int)(GSL_MIN(ap,bp) - 0.1); double tn = 1.0; double sum = 1.0; double n = 1.0; double sum_err = 0.0; while(n <= nmax) { double apn = (ap+n-1.0); double bpn = (bp+n-1.0); tn *= ((apn/n)*mxi)*bpn; sum += tn; sum_err += 2.0 * GSL_DBL_EPSILON * fabs(tn); n += 1.0; } result->val = sum; result->err = sum_err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(nmax)+1.0) * fabs(sum); return GSL_SUCCESS; } else { return d9chu(a,b,x,result); } } /* Evaluate finite sum which appears below. */ static int hyperg_U_finite_sum(int N, double a, double b, double x, double xeps, gsl_sf_result * result) { int i; double sum_val; double sum_err; if(N <= 0) { double t_val = 1.0; double t_err = 0.0; gsl_sf_result poch; int stat_poch; sum_val = 1.0; sum_err = 0.0; for(i=1; i<= -N; i++) { const double xi1 = i - 1; const double mult = (a+xi1)*x/((b+xi1)*(xi1+1.0)); t_val *= mult; t_err += fabs(mult) * t_err + fabs(t_val) * 8.0 * 2.0 * GSL_DBL_EPSILON; sum_val += t_val; sum_err += t_err; } stat_poch = gsl_sf_poch_e(1.0+a-b, -a, &poch); result->val = sum_val * poch.val; result->err = fabs(sum_val) * poch.err + sum_err * fabs(poch.val); result->err += fabs(poch.val) * (fabs(N) + 2.0) * GSL_DBL_EPSILON * fabs(sum_val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->err *= 2.0; /* FIXME: fudge factor... why is the error estimate too small? */ return stat_poch; } else { const int M = N - 2; if(M < 0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result gbm1; gsl_sf_result gamr; int stat_gbm1; int stat_gamr; double t_val = 1.0; double t_err = 0.0; sum_val = 1.0; sum_err = 0.0; for(i=1; i<=M; i++) { const double mult = (a-b+i)*x/((1.0-b+i)*i); t_val *= mult; t_err += t_err * fabs(mult) + fabs(t_val) * 8.0 * 2.0 * GSL_DBL_EPSILON; sum_val += t_val; sum_err += t_err; } stat_gbm1 = gsl_sf_gamma_e(b-1.0, &gbm1); stat_gamr = gsl_sf_gammainv_e(a, &gamr); if(stat_gbm1 == GSL_SUCCESS) { gsl_sf_result powx1N; int stat_p = gsl_sf_pow_int_e(x, 1-N, &powx1N); double pe_val = powx1N.val * xeps; double pe_err = powx1N.err * fabs(xeps) + 2.0 * GSL_DBL_EPSILON * fabs(pe_val); double coeff_val = gbm1.val * gamr.val * pe_val; double coeff_err = gbm1.err * fabs(gamr.val * pe_val) + gamr.err * fabs(gbm1.val * pe_val) + fabs(gbm1.val * gamr.val) * pe_err + 2.0 * GSL_DBL_EPSILON * fabs(coeff_val); result->val = sum_val * coeff_val; result->err = fabs(sum_val) * coeff_err + sum_err * fabs(coeff_val); result->err += 2.0 * GSL_DBL_EPSILON * (M+2.0) * fabs(result->val); result->err *= 2.0; /* FIXME: fudge factor... why is the error estimate too small? */ return stat_p; } else { result->val = 0.0; result->err = 0.0; return stat_gbm1; } } } } /* Based on SLATEC DCHU() [W. Fullerton] * Assumes x > 0. * This is just a series summation method, and * it is not good for large a. * * I patched up the window for 1+a-b near zero. [GJ] */ static int hyperg_U_series(const double a, const double b, const double x, gsl_sf_result * result) { const double EPS = 2.0 * GSL_DBL_EPSILON; /* EPS = D1MACH(3) */ const double SQRT_EPS = M_SQRT2 * GSL_SQRT_DBL_EPSILON; if(fabs(1.0 + a - b) < SQRT_EPS) { /* Original Comment: ALGORITHM IS BAD WHEN 1+A-B IS NEAR ZERO FOR SMALL X */ /* We can however do the following: * U(a,b,x) = U(a,a+1,x) when 1+a-b=0 * and U(a,a+1,x) = x^(-a). */ double lnr = -a * log(x); int stat_e = gsl_sf_exp_e(lnr, result); result->err += 2.0 * SQRT_EPS * fabs(result->val); return stat_e; } else { double aintb = ( b < 0.0 ? ceil(b-0.5) : floor(b+0.5) ); double beps = b - aintb; int N = aintb; double lnx = log(x); double xeps = exp(-beps*lnx); /* Evaluate finite sum. */ gsl_sf_result sum; int stat_sum = hyperg_U_finite_sum(N, a, b, x, xeps, &sum); /* Evaluate infinite sum. */ int istrt = ( N < 1 ? 1-N : 0 ); double xi = istrt; gsl_sf_result gamr; gsl_sf_result powx; int stat_gamr = gsl_sf_gammainv_e(1.0+a-b, &gamr); int stat_powx = gsl_sf_pow_int_e(x, istrt, &powx); double sarg = beps*M_PI; double sfact = ( sarg != 0.0 ? sarg/sin(sarg) : 1.0 ); double factor_val = sfact * ( GSL_IS_ODD(N) ? -1.0 : 1.0 ) * gamr.val * powx.val; double factor_err = fabs(gamr.val) * powx.err + fabs(powx.val) * gamr.err + 2.0 * GSL_DBL_EPSILON * fabs(factor_val); gsl_sf_result pochai; gsl_sf_result gamri1; gsl_sf_result gamrni; int stat_pochai = gsl_sf_poch_e(a, xi, &pochai); int stat_gamri1 = gsl_sf_gammainv_e(xi + 1.0, &gamri1); int stat_gamrni = gsl_sf_gammainv_e(aintb + xi, &gamrni); int stat_gam123 = GSL_ERROR_SELECT_3(stat_gamr, stat_gamri1, stat_gamrni); int stat_gamall = GSL_ERROR_SELECT_4(stat_sum, stat_gam123, stat_pochai, stat_powx); gsl_sf_result pochaxibeps; gsl_sf_result gamrxi1beps; int stat_pochaxibeps = gsl_sf_poch_e(a, xi-beps, &pochaxibeps); int stat_gamrxi1beps = gsl_sf_gammainv_e(xi + 1.0 - beps, &gamrxi1beps); int stat_all = GSL_ERROR_SELECT_3(stat_gamall, stat_pochaxibeps, stat_gamrxi1beps); double b0_val = factor_val * pochaxibeps.val * gamrni.val * gamrxi1beps.val; double b0_err = fabs(factor_val * pochaxibeps.val * gamrni.val) * gamrxi1beps.err + fabs(factor_val * pochaxibeps.val * gamrxi1beps.val) * gamrni.err + fabs(factor_val * gamrni.val * gamrxi1beps.val) * pochaxibeps.err + fabs(pochaxibeps.val * gamrni.val * gamrxi1beps.val) * factor_err + 2.0 * GSL_DBL_EPSILON * fabs(b0_val); if(fabs(xeps-1.0) < 0.5) { /* C X**(-BEPS) IS CLOSE TO 1.0D0, SO WE MUST BE C CAREFUL IN EVALUATING THE DIFFERENCES. */ int i; gsl_sf_result pch1ai; gsl_sf_result pch1i; gsl_sf_result poch1bxibeps; int stat_pch1ai = gsl_sf_pochrel_e(a + xi, -beps, &pch1ai); int stat_pch1i = gsl_sf_pochrel_e(xi + 1.0 - beps, beps, &pch1i); int stat_poch1bxibeps = gsl_sf_pochrel_e(b+xi, -beps, &poch1bxibeps); double c0_t1_val = beps*pch1ai.val*pch1i.val; double c0_t1_err = fabs(beps) * fabs(pch1ai.val) * pch1i.err + fabs(beps) * fabs(pch1i.val) * pch1ai.err + 2.0 * GSL_DBL_EPSILON * fabs(c0_t1_val); double c0_t2_val = -poch1bxibeps.val + pch1ai.val - pch1i.val + c0_t1_val; double c0_t2_err = poch1bxibeps.err + pch1ai.err + pch1i.err + c0_t1_err + 2.0 * GSL_DBL_EPSILON * fabs(c0_t2_val); double c0_val = factor_val * pochai.val * gamrni.val * gamri1.val * c0_t2_val; double c0_err = fabs(factor_val * pochai.val * gamrni.val * gamri1.val) * c0_t2_err + fabs(factor_val * pochai.val * gamrni.val * c0_t2_val) * gamri1.err + fabs(factor_val * pochai.val * gamri1.val * c0_t2_val) * gamrni.err + fabs(factor_val * gamrni.val * gamri1.val * c0_t2_val) * pochai.err + fabs(pochai.val * gamrni.val * gamri1.val * c0_t2_val) * factor_err + 2.0 * GSL_DBL_EPSILON * fabs(c0_val); /* C XEPS1 = (1.0 - X**(-BEPS))/BEPS = (X**(-BEPS) - 1.0)/(-BEPS) */ gsl_sf_result dexprl; int stat_dexprl = gsl_sf_exprel_e(-beps*lnx, &dexprl); double xeps1_val = lnx * dexprl.val; double xeps1_err = 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(beps*lnx)) * fabs(dexprl.val) + fabs(lnx) * dexprl.err + 2.0 * GSL_DBL_EPSILON * fabs(xeps1_val); double dchu_val = sum.val + c0_val + xeps1_val*b0_val; double dchu_err = sum.err + c0_err + fabs(xeps1_val)*b0_err + xeps1_err * fabs(b0_val) + fabs(b0_val*lnx)*dexprl.err + 2.0 * GSL_DBL_EPSILON * (fabs(sum.val) + fabs(c0_val) + fabs(xeps1_val*b0_val)); double xn = N; double t_val; double t_err; stat_all = GSL_ERROR_SELECT_5(stat_all, stat_dexprl, stat_poch1bxibeps, stat_pch1i, stat_pch1ai); for(i=1; i<2000; i++) { const double xi = istrt + i; const double xi1 = istrt + i - 1; const double tmp = (a-1.0)*(xn+2.0*xi-1.0) + xi*(xi-beps); const double b0_multiplier = (a+xi1-beps)*x/((xn+xi1)*(xi-beps)); const double c0_multiplier_1 = (a+xi1)*x/((b+xi1)*xi); const double c0_multiplier_2 = tmp / (xi*(b+xi1)*(a+xi1-beps)); b0_val *= b0_multiplier; b0_err += fabs(b0_multiplier) * b0_err + fabs(b0_val) * 8.0 * 2.0 * GSL_DBL_EPSILON; c0_val = c0_multiplier_1 * c0_val - c0_multiplier_2 * b0_val; c0_err = fabs(c0_multiplier_1) * c0_err + fabs(c0_multiplier_2) * b0_err + fabs(c0_val) * 8.0 * 2.0 * GSL_DBL_EPSILON + fabs(b0_val * c0_multiplier_2) * 16.0 * 2.0 * GSL_DBL_EPSILON; t_val = c0_val + xeps1_val*b0_val; t_err = c0_err + fabs(xeps1_val)*b0_err; t_err += fabs(b0_val*lnx) * dexprl.err; t_err += fabs(b0_val)*xeps1_err; dchu_val += t_val; dchu_err += t_err; if(fabs(t_val) < EPS*fabs(dchu_val)) break; } result->val = dchu_val; result->err = 2.0 * dchu_err; result->err += 2.0 * fabs(t_val); result->err += 4.0 * GSL_DBL_EPSILON * (i+2.0) * fabs(dchu_val); result->err *= 2.0; /* FIXME: fudge factor */ if(i >= 2000) { GSL_ERROR ("error", GSL_EMAXITER); } else { return stat_all; } } else { /* C X**(-BEPS) IS VERY DIFFERENT FROM 1.0, SO THE C STRAIGHTFORWARD FORMULATION IS STABLE. */ int i; double dchu_val; double dchu_err; double t_val; double t_err; gsl_sf_result dgamrbxi; int stat_dgamrbxi = gsl_sf_gammainv_e(b+xi, &dgamrbxi); double a0_val = factor_val * pochai.val * dgamrbxi.val * gamri1.val / beps; double a0_err = fabs(factor_val * pochai.val * dgamrbxi.val / beps) * gamri1.err + fabs(factor_val * pochai.val * gamri1.val / beps) * dgamrbxi.err + fabs(factor_val * dgamrbxi.val * gamri1.val / beps) * pochai.err + fabs(pochai.val * dgamrbxi.val * gamri1.val / beps) * factor_err + 2.0 * GSL_DBL_EPSILON * fabs(a0_val); stat_all = GSL_ERROR_SELECT_2(stat_all, stat_dgamrbxi); b0_val = xeps * b0_val / beps; b0_err = fabs(xeps / beps) * b0_err + 4.0 * GSL_DBL_EPSILON * fabs(b0_val); dchu_val = sum.val + a0_val - b0_val; dchu_err = sum.err + a0_err + b0_err + 2.0 * GSL_DBL_EPSILON * (fabs(sum.val) + fabs(a0_val) + fabs(b0_val)); for(i=1; i<2000; i++) { double xi = istrt + i; double xi1 = istrt + i - 1; double a0_multiplier = (a+xi1)*x/((b+xi1)*xi); double b0_multiplier = (a+xi1-beps)*x/((aintb+xi1)*(xi-beps)); a0_val *= a0_multiplier; a0_err += fabs(a0_multiplier) * a0_err; b0_val *= b0_multiplier; b0_err += fabs(b0_multiplier) * b0_err; t_val = a0_val - b0_val; t_err = a0_err + b0_err; dchu_val += t_val; dchu_err += t_err; if(fabs(t_val) < EPS*fabs(dchu_val)) break; } result->val = dchu_val; result->err = 2.0 * dchu_err; result->err += 2.0 * fabs(t_val); result->err += 4.0 * GSL_DBL_EPSILON * (i+2.0) * fabs(dchu_val); result->err *= 2.0; /* FIXME: fudge factor */ if(i >= 2000) { GSL_ERROR ("error", GSL_EMAXITER); } else { return stat_all; } } } } /* Assumes b > 0 and x > 0. */ static int hyperg_U_small_ab(const double a, const double b, const double x, gsl_sf_result * result) { if(a == -1.0) { /* U(-1,c+1,x) = Laguerre[c,0,x] = -b + x */ result->val = -b + x; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(b) + fabs(x)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(a == 0.0) { /* U(0,c+1,x) = Laguerre[c,0,x] = 1 */ result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(ASYMP_EVAL_OK(a,b,x)) { double p = pow(x, -a); gsl_sf_result asymp; int stat_asymp = hyperg_zaU_asymp(a, b, x, &asymp); result->val = asymp.val * p; result->err = asymp.err * p; result->err += fabs(asymp.val) * GSL_DBL_EPSILON * fabs(a) * p; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_asymp; } else { return hyperg_U_series(a, b, x, result); } } /* Assumes b > 0 and x > 0. */ static int hyperg_U_small_a_bgt0(const double a, const double b, const double x, gsl_sf_result * result, double * ln_multiplier ) { if(a == 0.0) { result->val = 1.0; result->err = 1.0; *ln_multiplier = 0.0; return GSL_SUCCESS; } else if( (b > 5000.0 && x < 0.90 * fabs(b)) || (b > 500.0 && x < 0.50 * fabs(b)) ) { int stat = gsl_sf_hyperg_U_large_b_e(a, b, x, result, ln_multiplier); if(stat == GSL_EOVRFLW) return GSL_SUCCESS; else return stat; } else if(b > 15.0) { /* Recurse up from b near 1. */ double eps = b - floor(b); double b0 = 1.0 + eps; gsl_sf_result r_Ubm1; gsl_sf_result r_Ub; int stat_0 = hyperg_U_small_ab(a, b0, x, &r_Ubm1); int stat_1 = hyperg_U_small_ab(a, b0+1.0, x, &r_Ub); double Ubm1 = r_Ubm1.val; double Ub = r_Ub.val; double Ubp1; double bp; for(bp = b0+1.0; bpval = Ub; result->err = (fabs(r_Ubm1.err/r_Ubm1.val) + fabs(r_Ub.err/r_Ub.val)) * fabs(Ub); result->err += 2.0 * GSL_DBL_EPSILON * (fabs(b-b0)+1.0) * fabs(Ub); *ln_multiplier = 0.0; return GSL_ERROR_SELECT_2(stat_0, stat_1); } else { *ln_multiplier = 0.0; return hyperg_U_small_ab(a, b, x, result); } } /* We use this to keep track of large * dynamic ranges in the recursions. * This can be important because sometimes * we want to calculate a very large and * a very small number and the answer is * the product, of order 1. This happens, * for instance, when we apply a Kummer * transform to make b positive and * both x and b are large. */ #define RESCALE_2(u0,u1,factor,count) \ do { \ double au0 = fabs(u0); \ if(au0 > factor) { \ u0 /= factor; \ u1 /= factor; \ count++; \ } \ else if(au0 < 1.0/factor) { \ u0 *= factor; \ u1 *= factor; \ count--; \ } \ } while (0) /* Specialization to b >= 1, for integer parameters. * Assumes x > 0. */ static int hyperg_U_int_bge1(const int a, const int b, const double x, gsl_sf_result_e10 * result) { if(a == 0) { result->val = 1.0; result->err = 0.0; result->e10 = 0; return GSL_SUCCESS; } else if(a == -1) { result->val = -b + x; result->err = 2.0 * GSL_DBL_EPSILON * (fabs(b) + fabs(x)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->e10 = 0; return GSL_SUCCESS; } else if(b == a + 1) { /* U(a,a+1,x) = x^(-a) */ return gsl_sf_exp_e10_e(-a*log(x), result); } else if(ASYMP_EVAL_OK(a,b,x)) { const double ln_pre_val = -a*log(x); const double ln_pre_err = 2.0 * GSL_DBL_EPSILON * fabs(ln_pre_val); gsl_sf_result asymp; int stat_asymp = hyperg_zaU_asymp(a, b, x, &asymp); int stat_e = gsl_sf_exp_mult_err_e10_e(ln_pre_val, ln_pre_err, asymp.val, asymp.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_asymp); } else if(SERIES_EVAL_OK(a,b,x)) { gsl_sf_result ser; const int stat_ser = hyperg_U_series(a, b, x, &ser); result->val = ser.val; result->err = ser.err; result->e10 = 0; return stat_ser; } else if(a < 0) { /* Recurse backward from a = -1,0. */ int scale_count = 0; const double scale_factor = GSL_SQRT_DBL_MAX; gsl_sf_result lnm; gsl_sf_result y; double lnscale; double Uap1 = 1.0; /* U(0,b,x) */ double Ua = -b + x; /* U(-1,b,x) */ double Uam1; int ap; for(ap=-1; ap>a; ap--) { Uam1 = ap*(b-ap-1.0)*Uap1 + (x+2.0*ap-b)*Ua; Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count); } lnscale = log(scale_factor); lnm.val = scale_count*lnscale; lnm.err = 2.0 * GSL_DBL_EPSILON * fabs(lnm.val); y.val = Ua; y.err = 4.0 * GSL_DBL_EPSILON * (fabs(a)+1.0) * fabs(Ua); return gsl_sf_exp_mult_err_e10_e(lnm.val, lnm.err, y.val, y.err, result); } else if(b >= 2.0*a + x) { /* Recurse forward from a = 0,1. */ int scale_count = 0; const double scale_factor = GSL_SQRT_DBL_MAX; gsl_sf_result r_Ua; gsl_sf_result lnm; gsl_sf_result y; double lnscale; double lm; int stat_1 = hyperg_U_small_a_bgt0(1.0, b, x, &r_Ua, &lm); /* U(1,b,x) */ int stat_e; double Uam1 = 1.0; /* U(0,b,x) */ double Ua = r_Ua.val; double Uap1; int ap; Uam1 *= exp(-lm); for(ap=1; apa_target; ap--) { Uam1 = -((b-2.0*ap-x)*Ua + ap*(1.0+ap-b)*Uap1); Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count); } if(Ua == 0.0) { result->val = 0.0; result->err = 0.0; result->e10 = 0; GSL_ERROR ("error", GSL_EZERODIV); } else { double lnscl = -scale_count*log(scale_factor); double lnpre_val = lnU_target + lnscl; double lnpre_err = 2.0 * GSL_DBL_EPSILON * (fabs(lnU_target) + fabs(lnscl)); double oUa_err = 2.0 * (fabs(a_target-a) + CF1_count + 1.0) * GSL_DBL_EPSILON * fabs(1.0/Ua); int stat_e = gsl_sf_exp_mult_err_e10_e(lnpre_val, lnpre_err, 1.0/Ua, oUa_err, result); return GSL_ERROR_SELECT_2(stat_e, stat_CF1); } } else { /* Recurse backward to near the b=2a+x line, then * determine normalization by either direct evaluation * or by a forward recursion. The direct evaluation * is needed when x is small (which is precisely * when it is easy to do). */ const double scale_factor = GSL_SQRT_DBL_MAX; int scale_count_for = 0; int scale_count_bck = 0; int a0 = 1; int a1 = a0 + ceil(0.5*(b-x) - a0); double Ua1_bck_val; double Ua1_bck_err; double Ua1_for_val; double Ua1_for_err; int stat_for; int stat_bck; gsl_sf_result lm_for; { /* Recurse back to determine U(a1,b), sans normalization. */ double ru; int CF1_count; int stat_CF1 = hyperg_U_CF1(a, b, 0, x, &ru, &CF1_count); double Ua = 1.0; double Uap1 = ru/a * Ua; double Uam1; int ap; for(ap=a; ap>a1; ap--) { Uam1 = -((b-2.0*ap-x)*Ua + ap*(1.0+ap-b)*Uap1); Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count_bck); } Ua1_bck_val = Ua; Ua1_bck_err = 2.0 * GSL_DBL_EPSILON * (fabs(a1-a)+CF1_count+1.0) * fabs(Ua); stat_bck = stat_CF1; } if(b == 2*a1 && a1 > 1) { /* This can happen when x is small, which is * precisely when we need to be careful with * this evaluation. */ hyperg_lnU_beq2a((double)a1, x, &lm_for); Ua1_for_val = 1.0; Ua1_for_err = 0.0; stat_for = GSL_SUCCESS; } else if(b == 2*a1 - 1 && a1 > 1) { /* Similar to the above. Happens when x is small. * Use * U(a,2a-1) = (x U(a,2a) - U(a-1,2(a-1))) / (2a - 2) */ gsl_sf_result lnU00, lnU12; gsl_sf_result U00, U12; hyperg_lnU_beq2a(a1-1.0, x, &lnU00); hyperg_lnU_beq2a(a1, x, &lnU12); if(lnU00.val > lnU12.val) { lm_for.val = lnU00.val; lm_for.err = lnU00.err; U00.val = 1.0; U00.err = 0.0; gsl_sf_exp_err_e(lnU12.val - lm_for.val, lnU12.err + lm_for.err, &U12); } else { lm_for.val = lnU12.val; lm_for.err = lnU12.err; U12.val = 1.0; U12.err = 0.0; gsl_sf_exp_err_e(lnU00.val - lm_for.val, lnU00.err + lm_for.err, &U00); } Ua1_for_val = (x * U12.val - U00.val) / (2.0*a1 - 2.0); Ua1_for_err = (fabs(x)*U12.err + U00.err) / fabs(2.0*a1 - 2.0); Ua1_for_err += 2.0 * GSL_DBL_EPSILON * fabs(Ua1_for_val); stat_for = GSL_SUCCESS; } else { /* Recurse forward to determine U(a1,b) with * absolute normalization. */ gsl_sf_result r_Ua; double Uam1 = 1.0; /* U(a0-1,b,x) = U(0,b,x) */ double Ua; double Uap1; int ap; double lm_for_local; stat_for = hyperg_U_small_a_bgt0(a0, b, x, &r_Ua, &lm_for_local); /* U(1,b,x) */ Ua = r_Ua.val; Uam1 *= exp(-lm_for_local); lm_for.val = lm_for_local; lm_for.err = 0.0; for(ap=a0; apval = 0.0; result->err = 0.0; result->e10 = 0; GSL_ERROR ("error", GSL_EZERODIV); } else if(Ua1_for_val == 0.0) { /* Should never happen. */ UNDERFLOW_ERROR_E10(result); } else { double lns = (scale_count_for - scale_count_bck)*log(scale_factor); double ln_for_val = log(fabs(Ua1_for_val)); double ln_for_err = GSL_DBL_EPSILON + fabs(Ua1_for_err/Ua1_for_val); double ln_bck_val = log(fabs(Ua1_bck_val)); double ln_bck_err = GSL_DBL_EPSILON + fabs(Ua1_bck_err/Ua1_bck_val); double lnr_val = lm_for.val + ln_for_val - ln_bck_val + lns; double lnr_err = lm_for.err + ln_for_err + ln_bck_err + 2.0 * GSL_DBL_EPSILON * (fabs(lm_for.val) + fabs(ln_for_val) + fabs(ln_bck_val) + fabs(lns)); double sgn = GSL_SIGN(Ua1_for_val) * GSL_SIGN(Ua1_bck_val); int stat_e = gsl_sf_exp_err_e10_e(lnr_val, lnr_err, result); result->val *= sgn; return GSL_ERROR_SELECT_3(stat_e, stat_bck, stat_for); } } } } /* Handle b >= 1 for generic a,b values. */ static int hyperg_U_bge1(const double a, const double b, const double x, gsl_sf_result_e10 * result) { const double rinta = floor(a+0.5); const int a_neg_integer = (a < 0.0 && fabs(a - rinta) < INT_THRESHOLD); if(a == 0.0) { result->val = 1.0; result->err = 0.0; result->e10 = 0; return GSL_SUCCESS; } else if(a_neg_integer && fabs(rinta) < INT_MAX) { /* U(-n,b,x) = (-1)^n n! Laguerre[n,b-1,x] */ const int n = -(int)rinta; const double sgn = (GSL_IS_ODD(n) ? -1.0 : 1.0); gsl_sf_result lnfact; gsl_sf_result L; const int stat_L = gsl_sf_laguerre_n_e(n, b-1.0, x, &L); gsl_sf_lnfact_e(n, &lnfact); { const int stat_e = gsl_sf_exp_mult_err_e10_e(lnfact.val, lnfact.err, sgn*L.val, L.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_L); } } else if(ASYMP_EVAL_OK(a,b,x)) { const double ln_pre_val = -a*log(x); const double ln_pre_err = 2.0 * GSL_DBL_EPSILON * fabs(ln_pre_val); gsl_sf_result asymp; int stat_asymp = hyperg_zaU_asymp(a, b, x, &asymp); int stat_e = gsl_sf_exp_mult_err_e10_e(ln_pre_val, ln_pre_err, asymp.val, asymp.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_asymp); } else if(fabs(a) <= 1.0) { gsl_sf_result rU; double ln_multiplier; int stat_U = hyperg_U_small_a_bgt0(a, b, x, &rU, &ln_multiplier); int stat_e = gsl_sf_exp_mult_err_e10_e(ln_multiplier, 2.0*GSL_DBL_EPSILON*fabs(ln_multiplier), rU.val, rU.err, result); return GSL_ERROR_SELECT_2(stat_U, stat_e); } else if(SERIES_EVAL_OK(a,b,x)) { gsl_sf_result ser; const int stat_ser = hyperg_U_series(a, b, x, &ser); result->val = ser.val; result->err = ser.err; result->e10 = 0; return stat_ser; } else if(a < 0.0) { /* Recurse backward on a and then upward on b. */ const double scale_factor = GSL_SQRT_DBL_MAX; const double a0 = a - floor(a) - 1.0; const double b0 = b - floor(b) + 1.0; int scale_count = 0; double lm_0, lm_1; double lm_max; gsl_sf_result r_Uap1; gsl_sf_result r_Ua; int stat_0 = hyperg_U_small_a_bgt0(a0+1.0, b0, x, &r_Uap1, &lm_0); int stat_1 = hyperg_U_small_a_bgt0(a0, b0, x, &r_Ua, &lm_1); int stat_e; double Uap1 = r_Uap1.val; double Ua = r_Ua.val; double Uam1; double ap; lm_max = GSL_MAX(lm_0, lm_1); Uap1 *= exp(lm_0-lm_max); Ua *= exp(lm_1-lm_max); /* Downward recursion on a. */ for(ap=a0; ap>a+0.1; ap -= 1.0) { Uam1 = ap*(b0-ap-1.0)*Uap1 + (x+2.0*ap-b0)*Ua; Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count); } if(b < 2.0) { /* b == b0, so no recursion necessary */ const double lnscale = log(scale_factor); gsl_sf_result lnm; gsl_sf_result y; lnm.val = lm_max + scale_count * lnscale; lnm.err = 2.0 * GSL_DBL_EPSILON * (fabs(lm_max) + scale_count * fabs(lnscale)); y.val = Ua; y.err = fabs(r_Uap1.err/r_Uap1.val) * fabs(Ua); y.err += fabs(r_Ua.err/r_Ua.val) * fabs(Ua); y.err += 2.0 * GSL_DBL_EPSILON * (fabs(a-a0) + 1.0) * fabs(Ua); y.err *= fabs(lm_0-lm_max) + 1.0; y.err *= fabs(lm_1-lm_max) + 1.0; stat_e = gsl_sf_exp_mult_err_e10_e(lnm.val, lnm.err, y.val, y.err, result); } else { /* Upward recursion on b. */ const double err_mult = fabs(b-b0) + fabs(a-a0) + 1.0; const double lnscale = log(scale_factor); gsl_sf_result lnm; gsl_sf_result y; double Ubm1 = Ua; /* U(a,b0) */ double Ub = (a*(b0-a-1.0)*Uap1 + (a+x)*Ua)/x; /* U(a,b0+1) */ double Ubp1; double bp; for(bp=b0+1.0; bp= 2*a + x) { /* Recurse forward from a near zero. * Note that we cannot cross the singularity at * the line b=a+1, because the only way we could * be in that little wedge is if a < 1. But we * have already dealt with the small a case. */ int scale_count = 0; const double a0 = a - floor(a); const double scale_factor = GSL_SQRT_DBL_MAX; double lnscale; double lm_0, lm_1, lm_max; gsl_sf_result r_Uam1; gsl_sf_result r_Ua; int stat_0 = hyperg_U_small_a_bgt0(a0-1.0, b, x, &r_Uam1, &lm_0); int stat_1 = hyperg_U_small_a_bgt0(a0, b, x, &r_Ua, &lm_1); int stat_e; gsl_sf_result lnm; gsl_sf_result y; double Uam1 = r_Uam1.val; double Ua = r_Ua.val; double Uap1; double ap; lm_max = GSL_MAX(lm_0, lm_1); Uam1 *= exp(lm_0-lm_max); Ua *= exp(lm_1-lm_max); for(ap=a0; apa0+0.1; ap -= 1.0) { Uam1 = -((b-2.0*ap-x)*Ua + ap*(1.0+ap-b)*Uap1); Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count); } stat_U0 = hyperg_U_small_a_bgt0(a0, b, x, &U0, &lm_0); lnscale = log(scale_factor); lnm.val = lm_0 - scale_count * lnscale; lnm.err = 2.0 * GSL_DBL_EPSILON * (fabs(lm_0) + fabs(scale_count * lnscale)); y.val = GSL_SQRT_DBL_MIN*(U0.val/Ua); y.err = GSL_SQRT_DBL_MIN*(U0.err/fabs(Ua)); y.err += 2.0 * GSL_DBL_EPSILON * (fabs(a0-a) + CF1_count + 1.0) * fabs(y.val); stat_e = gsl_sf_exp_mult_err_e10_e(lnm.val, lnm.err, y.val, y.err, result); return GSL_ERROR_SELECT_3(stat_e, stat_U0, stat_CF1); } else { /* Recurse backward to near the b=2a+x line, then * forward from a near zero to get the normalization. */ int scale_count_for = 0; int scale_count_bck = 0; const double scale_factor = GSL_SQRT_DBL_MAX; const double eps = a - floor(a); const double a0 = ( eps == 0.0 ? 1.0 : eps ); const double a1 = a0 + ceil(0.5*(b-x) - a0); gsl_sf_result lnm; gsl_sf_result y; double lm_for; double lnscale; double Ua1_bck; double Ua1_for; int stat_for; int stat_bck; int stat_e; int CF1_count; { /* Recurse back to determine U(a1,b), sans normalization. */ double Uap1; double Ua; double Uam1; double ap; double ru; double r; int stat_CF1 = hyperg_U_CF1(a, b, 0, x, &ru, &CF1_count); r = ru/a; Ua = GSL_SQRT_DBL_MIN; Uap1 = r * Ua; for(ap=a; ap>a1+0.1; ap -= 1.0) { Uam1 = -((b-2.0*ap-x)*Ua + ap*(1.0+ap-b)*Uap1); Uap1 = Ua; Ua = Uam1; RESCALE_2(Ua,Uap1,scale_factor,scale_count_bck); } Ua1_bck = Ua; stat_bck = stat_CF1; } { /* Recurse forward to determine U(a1,b) with * absolute normalization. */ gsl_sf_result r_Uam1; gsl_sf_result r_Ua; double lm_0, lm_1; int stat_0 = hyperg_U_small_a_bgt0(a0-1.0, b, x, &r_Uam1, &lm_0); int stat_1 = hyperg_U_small_a_bgt0(a0, b, x, &r_Ua, &lm_1); double Uam1 = r_Uam1.val; double Ua = r_Ua.val; double Uap1; double ap; lm_for = GSL_MAX(lm_0, lm_1); Uam1 *= exp(lm_0 - lm_for); Ua *= exp(lm_1 - lm_for); for(ap=a0; ap= 1) { return hyperg_U_int_bge1(a, b, x, result); } else { /* Use the reflection formula * U(a,b,x) = x^(1-b) U(1+a-b,2-b,x) */ gsl_sf_result_e10 U; double ln_x = log(x); int ap = 1 + a - b; int bp = 2 - b; int stat_e; int stat_U = hyperg_U_int_bge1(ap, bp, x, &U); double ln_pre_val = (1.0-b)*ln_x; double ln_pre_err = 2.0 * GSL_DBL_EPSILON * (fabs(b)+1.0) * fabs(ln_x); ln_pre_err += 2.0 * GSL_DBL_EPSILON * fabs(1.0-b); /* error in log(x) */ stat_e = gsl_sf_exp_mult_err_e10_e(ln_pre_val + U.e10*M_LN10, ln_pre_err, U.val, U.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_U); } } } int gsl_sf_hyperg_U_e10_e(const double a, const double b, const double x, gsl_sf_result_e10 * result) { const double rinta = floor(a + 0.5); const double rintb = floor(b + 0.5); const int a_integer = ( fabs(a - rinta) < INT_THRESHOLD ); const int b_integer = ( fabs(b - rintb) < INT_THRESHOLD ); /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR_E10(result); } else if(a == 0.0) { result->val = 1.0; result->err = 0.0; result->e10 = 0; return GSL_SUCCESS; } else if(a_integer && b_integer) { return gsl_sf_hyperg_U_int_e10_e(rinta, rintb, x, result); } else { if(b >= 1.0) { /* Use b >= 1 function. */ return hyperg_U_bge1(a, b, x, result); } else { /* Use the reflection formula * U(a,b,x) = x^(1-b) U(1+a-b,2-b,x) */ const double lnx = log(x); const double ln_pre_val = (1.0-b)*lnx; const double ln_pre_err = fabs(lnx) * 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(b)); const double ap = 1.0 + a - b; const double bp = 2.0 - b; gsl_sf_result_e10 U; int stat_U = hyperg_U_bge1(ap, bp, x, &U); int stat_e = gsl_sf_exp_mult_err_e10_e(ln_pre_val + U.e10*M_LN10, ln_pre_err, U.val, U.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_U); } } } int gsl_sf_hyperg_U_int_e(const int a, const int b, const double x, gsl_sf_result * result) { gsl_sf_result_e10 re; int stat_U = gsl_sf_hyperg_U_int_e10_e(a, b, x, &re); int stat_c = gsl_sf_result_smash_e(&re, result); return GSL_ERROR_SELECT_2(stat_c, stat_U); } int gsl_sf_hyperg_U_e(const double a, const double b, const double x, gsl_sf_result * result) { gsl_sf_result_e10 re; int stat_U = gsl_sf_hyperg_U_e10_e(a, b, x, &re); int stat_c = gsl_sf_result_smash_e(&re, result); return GSL_ERROR_SELECT_2(stat_c, stat_U); } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_hyperg_U_int(const int a, const int b, const double x) { EVAL_RESULT(gsl_sf_hyperg_U_int_e(a, b, x, &result)); } double gsl_sf_hyperg_U(const double a, const double b, const double x) { EVAL_RESULT(gsl_sf_hyperg_U_e(a, b, x, &result)); } sources_5316/external/gsl/gsl_integration__initialise.c0000664000176700017670000000240311723710247022244 0ustar paulpaul/* integration/initialise.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static inline void initialise (gsl_integration_workspace * workspace, double a, double b); static inline void initialise (gsl_integration_workspace * workspace, double a, double b) { workspace->size = 0; workspace->nrmax = 0; workspace->i = 0; workspace->alist[0] = a; workspace->blist[0] = b; workspace->rlist[0] = 0.0; workspace->elist[0] = 0.0; workspace->order[0] = 0; workspace->level[0] = 0; workspace->maximum_level = 0; } sources_5316/external/gsl/gsl_cblas__dswap.c0000664000176700017670000000037011723710247017772 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dswap (const int N, double *X, const int incX, double *Y, const int incY) { #define BASE double #include "gsl_cblas__source_swap_r.h" #undef BASE } sources_5316/external/gsl/gsl_block__fprintf_source.c0000664000176700017670000000757011723710247021723 0ustar paulpaul/* block/fprintf_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #if !(USES_LONGDOUBLE && !HAVE_PRINTF_LONGDOUBLE) int FUNCTION (gsl_block, fprintf) (FILE * stream, const TYPE(gsl_block) * b, const char *format) { size_t n = b->size ; ATOMIC * data = b->data ; size_t i; for (i = 0; i < n; i++) { int k; int status; for (k = 0; k < MULTIPLICITY; k++) { if (k > 0) { status = putc (' ', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } } status = fprintf (stream, format, data[MULTIPLICITY * i + k]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } } status = putc ('\n', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } } return 0; } int FUNCTION (gsl_block, fscanf) (FILE * stream, TYPE(gsl_block) * b) { size_t n = b->size ; ATOMIC * data = b->data ; size_t i; for (i = 0; i < n; i++) { int k; for (k = 0; k < MULTIPLICITY; k++) { ATOMIC_IO tmp ; int status = fscanf (stream, IN_FORMAT, &tmp) ; data [MULTIPLICITY * i + k] = tmp; if (status != 1) { GSL_ERROR ("fscanf failed", GSL_EFAILED); } } } return GSL_SUCCESS; } int FUNCTION (gsl_block, raw_fprintf) (FILE * stream, const ATOMIC * data, const size_t n, const size_t stride, const char *format) { size_t i; for (i = 0; i < n; i++) { int k; int status; for (k = 0; k < MULTIPLICITY; k++) { if (k > 0) { status = putc (' ', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } } status = fprintf (stream, format, data[MULTIPLICITY * i * stride + k]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } } status = putc ('\n', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } } return 0; } int FUNCTION (gsl_block, raw_fscanf) (FILE * stream, ATOMIC * data, const size_t n, const size_t stride) { size_t i; for (i = 0; i < n; i++) { int k; for (k = 0; k < MULTIPLICITY; k++) { ATOMIC_IO tmp; int status = fscanf (stream, IN_FORMAT, &tmp) ; data [MULTIPLICITY * i * stride + k] = tmp; if (status != 1) GSL_ERROR ("fscanf failed", GSL_EFAILED); } } return GSL_SUCCESS; } #endif sources_5316/external/gsl/gsl_dft_complex_float.h0000664000176700017670000000346211705263724021057 0ustar paulpaul/* fft/gsl_dft_complex_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_DFT_COMPLEX_FLOAT_H__ #define __GSL_DFT_COMPLEX_FLOAT_H__ #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_fft.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_dft_complex_float_forward (const float data[], const size_t stride, const size_t n, float result[]); int gsl_dft_complex_float_backward (const float data[], const size_t stride, const size_t n, float result[]); int gsl_dft_complex_float_inverse (const float data[], const size_t stride, const size_t n, float result[]); int gsl_dft_complex_float_transform (const float data[], const size_t stride, const size_t n, float result[], const gsl_fft_direction sign); __END_DECLS #endif /* __GSL_DFT_COMPLEX_FLOAT_H__ */ sources_5316/external/gsl/gsl_ieee-utils__fp.c0000664000176700017670000000310011723710247020234 0ustar paulpaul#include "gsl__config.h" #if HAVE_GNUSPARC_IEEE_INTERFACE #include "gsl_ieee-utils__fp-gnusparc.c" #elif HAVE_GNUM68K_IEEE_INTERFACE #include "gsl_ieee-utils__fp-gnum68k.c" #elif HAVE_GNUPPC_IEEE_INTERFACE #include "gsl_ieee-utils__fp-gnuppc.c" #elif HAVE_GNUX86_IEEE_INTERFACE #include "gsl_ieee-utils__fp-gnux86.c" #elif HAVE_HPUX11_IEEE_INTERFACE #include "gsl_ieee-utils__fp-hpux11.c" #elif HAVE_HPUX_IEEE_INTERFACE #include "gsl_ieee-utils__fp-hpux.c" #elif HAVE_SUNOS4_IEEE_INTERFACE #include "gsl_ieee-utils__fp-sunos4.c" #elif HAVE_SOLARIS_IEEE_INTERFACE #include "gsl_ieee-utils__fp-solaris.c" #elif HAVE_IRIX_IEEE_INTERFACE #include "gsl_ieee-utils__fp-irix.c" #elif HAVE_AIX_IEEE_INTERFACE #include "gsl_ieee-utils__fp-aix.c" #elif HAVE_TRU64_IEEE_INTERFACE #include "gsl_ieee-utils__fp-tru64.c" #elif HAVE_FREEBSD_IEEE_INTERFACE #include "gsl_ieee-utils__fp-freebsd.c" #elif HAVE_OS2EMX_IEEE_INTERFACE #include "gsl_ieee-utils__fp-os2emx.c" #elif HAVE_NETBSD_IEEE_INTERFACE #include "gsl_ieee-utils__fp-netbsd.c" #elif HAVE_OPENBSD_IEEE_INTERFACE #include "gsl_ieee-utils__fp-openbsd.c" /* Try to handle universal binaries */ #elif HAVE_DARWIN_IEEE_INTERFACE # if defined(__i386__) # include "gsl_ieee-utils__fp-darwin86.c" #else # include "gsl_ieee-utils__fp-darwin.c" # endif #elif HAVE_DARWIN86_IEEE_INTERFACE # if defined(__ppc__) # include "gsl_ieee-utils__fp-darwin.c" # else # include "gsl_ieee-utils__fp-darwin86.c" #endif #elif HAVE_DECL_FEENABLEEXCEPT || HAVE_DECL_FESETTRAPENABLE #include "gsl_ieee-utils__fp-gnuc99.c" #else #include "gsl_ieee-utils__fp-unknown.c" #endif sources_5316/external/gsl/gsl_cblas__scasum.c0000664000176700017670000000032511723710247020147 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" float cblas_scasum (const int N, const void *X, const int incX) { #define BASE float #include "gsl_cblas__source_asum_c.h" #undef BASE } sources_5316/external/gsl/gsl_min__golden.c0000664000176700017670000000655711723710247017640 0ustar paulpaul/* min/golden.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* goldensection.c -- goldensection minimum finding algorithm */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_min.h" #include "gsl_min__min.h" typedef struct { double dummy; } goldensection_state_t; static int goldensection_init (void * vstate, gsl_function * f, double x_minimum, double f_minimum, double x_lower, double f_lower, double x_upper, double f_upper); static int goldensection_iterate (void * vstate, gsl_function * f, double * x_minimum, double * f_minimum, double * x_lower, double * f_lower, double * x_upper, double * f_upper); static int goldensection_init (void * vstate, gsl_function * f, double x_minimum, double f_minimum, double x_lower, double f_lower, double x_upper, double f_upper) { goldensection_state_t * state = (goldensection_state_t *) vstate; /* no initialization required, prevent warnings about unused variables */ state = 0; f = 0; x_minimum = 0; f_minimum = 0; x_lower = 0; f_lower = 0; x_upper = 0; f_upper = 0; return GSL_SUCCESS; } static int goldensection_iterate (void * vstate, gsl_function * f, double * x_minimum, double * f_minimum, double * x_lower, double * f_lower, double * x_upper, double * f_upper) { goldensection_state_t * state = (goldensection_state_t *) vstate; const double x_center = *x_minimum ; const double x_left = *x_lower ; const double x_right = *x_upper ; const double f_min = *f_minimum; const double golden = 0.3819660; /* golden = (3 - sqrt(5))/2 */ const double w_lower = (x_center - x_left); const double w_upper = (x_right - x_center); double x_new, f_new; state = 0 ; /* avoid warning about unused parameters */ x_new = x_center + golden * ((w_upper > w_lower) ? w_upper : -w_lower) ; SAFE_FUNC_CALL (f, x_new, &f_new); if (f_new < f_min) { *x_minimum = x_new ; *f_minimum = f_new ; return GSL_SUCCESS; } else if (x_new < x_center && f_new > f_min) { *x_lower = x_new ; *f_lower = f_new ; return GSL_SUCCESS; } else if (x_new > x_center && f_new > f_min) { *x_upper = x_new ; *f_upper = f_new ; return GSL_SUCCESS; } else { return GSL_FAILURE; } } static const gsl_min_fminimizer_type goldensection_type = {"goldensection", /* name */ sizeof (goldensection_state_t), &goldensection_init, &goldensection_iterate}; const gsl_min_fminimizer_type * gsl_min_fminimizer_goldensection = &goldensection_type; sources_5316/external/gsl/gsl_fft__bitreverse.h0000664000176700017670000000250711705263724020535 0ustar paulpaul/* fft/bitreverse.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static int FUNCTION(fft_complex,bitreverse_order) (BASE data[], const size_t stride, const size_t n, size_t logn) ; static int FUNCTION(fft_real,bitreverse_order) (BASE data[], const size_t stride, const size_t n, size_t logn) ; sources_5316/external/gsl/gsl_sort__sort.c0000664000176700017670000000524011723710247017547 0ustar paulpaul/* * Implement Heap sort -- direct and indirect sorting * Based on descriptions in Sedgewick "Algorithms in C" * * Copyright (C) 1999 Thomas Walter * * 18 February 2000: Modified for GSL by Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ #include "gsl__config.h" #include #include "gsl_heapsort.h" static inline void swap (void *base, size_t size, size_t i, size_t j); static inline void downheap (void *data, const size_t size, const size_t N, size_t k, gsl_comparison_fn_t compare); /* Inline swap function for moving objects around */ static inline void swap (void *base, size_t size, size_t i, size_t j) { register char *a = size * i + (char *) base; register char *b = size * j + (char *) base; register size_t s = size; if (i == j) return; do { char tmp = *a; *a++ = *b; *b++ = tmp; } while (--s > 0); } #define CMP(data,size,j,k) (compare((char *)(data) + (size) * (j), (char *)(data) + (size) * (k))) static inline void downheap (void *data, const size_t size, const size_t N, size_t k, gsl_comparison_fn_t compare) { while (k <= N / 2) { size_t j = 2 * k; if (j < N && CMP (data, size, j, j + 1) < 0) { j++; } if (CMP (data, size, k, j) < 0) { swap (data, size, j, k); } else { break; } k = j; } } void gsl_heapsort (void *data, size_t count, size_t size, gsl_comparison_fn_t compare) { /* Sort the array in ascending order. This is a true inplace algorithm with N log N operations. Worst case (an already sorted array) is something like 20% slower */ size_t N; size_t k; if (count == 0) { return; /* No data to sort */ } /* We have n_data elements, last element is at 'n_data-1', first at '0' Set N to the last element number. */ N = count - 1; k = N / 2; k++; /* Compensate the first use of 'k--' */ do { k--; downheap (data, size, N, k, compare); } while (k > 0); while (N > 0) { /* first swap the elements */ swap (data, size, 0, N); /* then process the heap */ N--; downheap (data, size, N, 0, compare); } } sources_5316/external/gsl/gsl_permute_vector_float.h0000664000176700017670000000266611705263724021623 0ustar paulpaul/* permutation/gsl_permute_vector_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_FLOAT_H__ #define __GSL_PERMUTE_VECTOR_FLOAT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_float.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_float (const gsl_permutation * p, gsl_vector_float * v); int gsl_permute_vector_float_inverse (const gsl_permutation * p, gsl_vector_float * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_FLOAT_H__ */ sources_5316/external/gsl/gsl_cblas__sspmv.c0000664000176700017670000000056611723710247020033 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_sspmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *Ap, const float *X, const int incX, const float beta, float *Y, const int incY) { #define BASE float #include "gsl_cblas__source_spmv.h" #undef BASE } sources_5316/external/gsl/gsl_complex__results_real.h0000664000176700017670000002060411705263724021755 0ustar paulpaul {FN (sqrt_real), -1.0e+01, RES(0, 3.1622776601683793320e0)}, {FN (sqrt_real), -2.0e+00, RES(0, 1.4142135623730950488e0)}, {FN (sqrt_real), -1.0e+00, RES(0, 1)}, {FN (sqrt_real), -7.50e-01, RES(0, 8.6602540378443864676e-1)}, {FN (sqrt_real), -5.0e-01, RES(0, 7.0710678118654752440e-1)}, {FN (sqrt_real), -1.250e-01, RES(0, 3.5355339059327376220e-1)}, {FN (sqrt_real), -3.45266983001243932001e-04, RES(0, 1.8581361171917517303e-2)}, {FN (sqrt_real), -1.19209289550781250e-07, RES(0, 3.4526698300124390840e-4)}, {FN (sqrt_real), 0.0e+00, RES(0e0, 0.0)}, {FN (sqrt_real), 1.19209289550781250e-07, RES(3.4526698300124390840e-4, 0.0)}, {FN (sqrt_real), 3.45266983001243932001e-04, RES(1.8581361171917517303e-2, 0.0)}, {FN (sqrt_real), 1.250e-01, RES(3.5355339059327376220e-1, 0.0)}, {FN (sqrt_real), 5.0e-01, RES(7.0710678118654752440e-1, 0.0)}, {FN (sqrt_real), 7.50e-01, RES(8.6602540378443864676e-1, 0.0)}, {FN (sqrt_real), 1.0e+00, RES(1e0, 0.0)}, {FN (sqrt_real), 2.0e+00, RES(1.4142135623730950488e0, 0.0)}, {FN (sqrt_real), 1.0e+01, RES(3.1622776601683793320e0, 0.0)}, {FN (arcsin_real), -1.0e+01, RES(-1.5707963267948966192e0, 2.9932228461263808979e0)}, {FN (arcsin_real), -2.0e+00, RES(-1.5707963267948966192e0, 1.3169578969248167086e0)}, {FN (arcsin_real), -1.0e+00, RES(-1.5707963267948966192e0, 0.0)}, {FN (arcsin_real), -7.50e-01, RES(-8.4806207898148100805e-1, 0.0)}, {FN (arcsin_real), -5.0e-01, RES(-5.2359877559829887308e-1, 0.0)}, {FN (arcsin_real), -1.250e-01, RES(-1.2532783116806539687e-1, 0.0)}, {FN (arcsin_real), -3.45266983001243932001e-04, RES(-3.4526698986108292481e-4, 0.0)}, {FN (arcsin_real), -1.19209289550781250e-07, RES(-1.1920928955078153234e-7, 0.0)}, {FN (arcsin_real), 0.0e+00, RES(0e0, 0.0)}, {FN (arcsin_real), 1.19209289550781250e-07, RES(1.1920928955078153234e-7, 0.0)}, {FN (arcsin_real), 3.45266983001243932001e-04, RES(3.4526698986108292481e-4, 0.0)}, {FN (arcsin_real), 1.250e-01, RES(1.2532783116806539687e-1, 0.0)}, {FN (arcsin_real), 5.0e-01, RES(5.2359877559829887308e-1, 0.0)}, {FN (arcsin_real), 7.50e-01, RES(8.4806207898148100805e-1, 0.0)}, {FN (arcsin_real), 1.0e+00, RES(1.5707963267948966192e0, 0.0)}, {FN (arcsin_real), 2.0e+00, RES(1.5707963267948966192e0, -1.3169578969248167086e0)}, {FN (arcsin_real), 1.0e+01, RES(1.5707963267948966192e0, -2.9932228461263808979e0)}, {FN (arccos_real), -1.0e+01, RES(3.1415926535897932385e0, -2.9932228461263808979e0)}, {FN (arccos_real), -2.0e+00, RES(3.1415926535897932385e0, -1.3169578969248167086e0)}, {FN (arccos_real), -1.0e+00, RES(3.1415926535897932385e0, 0.0)}, {FN (arccos_real), -7.50e-01, RES(2.4188584057763776273e0, 0.0)}, {FN (arccos_real), -5.0e-01, RES(2.0943951023931954923e0, 0.0)}, {FN (arccos_real), -1.250e-01, RES(1.6961241579629620161e0, 0.0)}, {FN (arccos_real), -3.45266983001243932001e-04, RES(1.5711415937847577022e0, 0.0)}, {FN (arccos_real), -1.19209289550781250e-07, RES(1.570796446004186170e0, 0.0)}, {FN (arccos_real), 0.0e+00, RES(1.5707963267948966192e0, 0.0)}, {FN (arccos_real), 1.19209289550781250e-07, RES(1.5707962075856070684e0, 0.0)}, {FN (arccos_real), 3.45266983001243932001e-04, RES(1.5704510598050355363e0, 0.0)}, {FN (arccos_real), 1.250e-01, RES(1.4454684956268312224e0, 0.0)}, {FN (arccos_real), 5.0e-01, RES(1.0471975511965977462e0, 0.0)}, {FN (arccos_real), 7.50e-01, RES(7.2273424781341561118e-1, 0.0)}, {FN (arccos_real), 1.0e+00, RES(0e0, 0.0)}, {FN (arccos_real), 2.0e+00, RES(0, 1.3169578969248167086e0)}, {FN (arccos_real), 1.0e+01, RES(0, 2.9932228461263808979e0)}, {FN (arccosh_real), -1.0e+01, RES(2.9932228461263808979e0, 3.1415926535897932385e0)}, {FN (arccosh_real), -2.0e+00, RES(1.3169578969248167086e0, 3.1415926535897932385e0)}, {FN (arccosh_real), -1.0e+00, RES(0, 3.1415926535897932385e0)}, {FN (arccosh_real), -7.50e-01, RES(0, 2.4188584057763776273e0)}, {FN (arccosh_real), -5.0e-01, RES(0, 2.0943951023931954923e0)}, {FN (arccosh_real), -1.250e-01, RES(0, 1.6961241579629620161e0)}, {FN (arccosh_real), -3.45266983001243932001e-04, RES(0, 1.5711415937847577022e0)}, {FN (arccosh_real), -1.19209289550781250e-07, RES(0, 1.570796446004186170e0)}, {FN (arccosh_real), 0.0e+00, RES(0, 1.5707963267948966192e0)}, {FN (arccosh_real), 1.19209289550781250e-07, RES(0, 1.5707962075856070684e0)}, {FN (arccosh_real), 3.45266983001243932001e-04, RES(0, 1.5704510598050355363e0)}, {FN (arccosh_real), 1.250e-01, RES(0, 1.4454684956268312224e0)}, {FN (arccosh_real), 5.0e-01, RES(0, 1.0471975511965977462e0)}, {FN (arccosh_real), 7.50e-01, RES(0, 7.2273424781341561118e-1)}, {FN (arccosh_real), 1.0e+00, RES(0e0, 0.0)}, {FN (arccosh_real), 2.0e+00, RES(1.3169578969248167086e0, 0.0)}, {FN (arccosh_real), 1.0e+01, RES(2.9932228461263808979e0, 0.0)}, {FN (arctanh_real), -1.0e+01, RES(-1.0033534773107558064e-1, 1.5707963267948966192e0)}, {FN (arctanh_real), -2.0e+00, RES(-5.4930614433405484570e-1, 1.5707963267948966192e0)}, {FN (arctanh_real), -7.50e-01, RES(-9.7295507452765665255e-1, 0.0)}, {FN (arctanh_real), -5.0e-01, RES(-5.4930614433405484570e-1, 0.0)}, {FN (arctanh_real), -1.250e-01, RES(-1.2565721414045303884e-1, 0.0)}, {FN (arctanh_real), -3.45266983001243932001e-04, RES(-3.4526699672092216295e-4, 0.0)}, {FN (arctanh_real), -1.19209289550781250e-07, RES(-1.1920928955078181469e-7, 0.0)}, {FN (arctanh_real), 0.0e+00, RES(0e0, 0.0)}, {FN (arctanh_real), 1.19209289550781250e-07, RES(1.1920928955078181469e-7, 0.0)}, {FN (arctanh_real), 3.45266983001243932001e-04, RES(3.4526699672092216295e-4, 0.0)}, {FN (arctanh_real), 1.250e-01, RES(1.2565721414045303884e-1, 0.0)}, {FN (arctanh_real), 5.0e-01, RES(5.4930614433405484570e-1, 0.0)}, {FN (arctanh_real), 7.50e-01, RES(9.7295507452765665255e-1, 0.0)}, {FN (arctanh_real), 2.0e+00, RES(5.4930614433405484570e-1, -1.5707963267948966192e0)}, {FN (arctanh_real), 1.0e+01, RES(1.0033534773107558064e-1, -1.5707963267948966192e0)}, {FN (arccsc_real), -1.0e+01, RES(-1.0016742116155979635e-1, 0.0)}, {FN (arccsc_real), -2.0e+00, RES(-5.2359877559829887308e-1, 0.0)}, {FN (arccsc_real), -1.0e+00, RES(-1.5707963267948966192e0, 0.0)}, {FN (arccsc_real), -7.50e-01, RES(-1.5707963267948966192e0, 7.9536546122390563053e-1)}, {FN (arccsc_real), -5.0e-01, RES(-1.5707963267948966192e0, 1.3169578969248167086e0)}, {FN (arccsc_real), -1.250e-01, RES(-1.5707963267948966192e0, 2.7686593833135738327e0)}, {FN (arccsc_real), -3.45266983001243932001e-04, RES(-1.5707963267948966192e0, 8.6643397271969925794e0)}, {FN (arccsc_real), -1.19209289550781250e-07, RES(-1.5707963267948966192e0, 1.6635532333438683873e1)}, {FN (arccsc_real), 1.19209289550781250e-07, RES(1.5707963267948966192e0, -1.6635532333438683873e1)}, {FN (arccsc_real), 3.45266983001243932001e-04, RES(1.5707963267948966192e0, -8.6643397271969925794e0)}, {FN (arccsc_real), 1.250e-01, RES(1.5707963267948966192e0, -2.7686593833135738327e0)}, {FN (arccsc_real), 5.0e-01, RES(1.5707963267948966192e0, -1.3169578969248167086e0)}, {FN (arccsc_real), 7.50e-01, RES(1.5707963267948966192e0, -7.9536546122390563053e-1)}, {FN (arccsc_real), 1.0e+00, RES(1.5707963267948966192e0, 0.0)}, {FN (arccsc_real), 2.0e+00, RES(5.2359877559829887308e-1, 0.0)}, {FN (arccsc_real), 1.0e+01, RES(1.0016742116155979635e-1, 0.0)}, {FN (arcsec_real), -1.0e+01, RES(1.6709637479564564156e0, 0.0)}, {FN (arcsec_real), -2.0e+00, RES(2.0943951023931954923e0, 0.0)}, {FN (arcsec_real), -1.0e+00, RES(3.1415926535897932385e0, 0.0)}, {FN (arcsec_real), -7.50e-01, RES(3.1415926535897932385e0, -7.9536546122390563053e-1)}, {FN (arcsec_real), -5.0e-01, RES(3.1415926535897932385e0, -1.3169578969248167086e0)}, {FN (arcsec_real), -1.250e-01, RES(3.1415926535897932385e0, -2.7686593833135738327e0)}, {FN (arcsec_real), -3.45266983001243932001e-04, RES(3.1415926535897932385e0, -8.6643397271969925794e0)}, {FN (arcsec_real), -1.19209289550781250e-07, RES(3.1415926535897932385e0, -1.6635532333438683873e1)}, {FN (arcsec_real), 1.19209289550781250e-07, RES(0, 1.6635532333438683873e1)}, {FN (arcsec_real), 3.45266983001243932001e-04, RES(0, 8.6643397271969925794e0)}, {FN (arcsec_real), 1.250e-01, RES(0, 2.7686593833135738327e0)}, {FN (arcsec_real), 5.0e-01, RES(0, 1.3169578969248167086e0)}, {FN (arcsec_real), 7.50e-01, RES(0, 7.9536546122390563053e-1)}, {FN (arcsec_real), 1.0e+00, RES(0e0, 0.0)}, {FN (arcsec_real), 2.0e+00, RES(1.0471975511965977462e0, 0.0)}, {FN (arcsec_real), 1.0e+01, RES(1.4706289056333368229e0, 0.0)}, sources_5316/external/gsl/gsl_fft__bitreverse.c0000664000176700017670000000476011723710247020530 0ustar paulpaul/* fft/bitreverse.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_fft.h" #include "gsl_fft__complex_internal.h" #include "gsl_fft__bitreverse.h" static int FUNCTION(fft_complex,bitreverse_order) (BASE data[], const size_t stride, const size_t n, size_t logn) { /* This is the Goldrader bit-reversal algorithm */ size_t i; size_t j = 0; logn = 0 ; /* not needed for this algorithm */ for (i = 0; i < n - 1; i++) { size_t k = n / 2 ; if (i < j) { const BASE tmp_real = REAL(data,stride,i); const BASE tmp_imag = IMAG(data,stride,i); REAL(data,stride,i) = REAL(data,stride,j); IMAG(data,stride,i) = IMAG(data,stride,j); REAL(data,stride,j) = tmp_real; IMAG(data,stride,j) = tmp_imag; } while (k <= j) { j = j - k ; k = k / 2 ; } j += k ; } return 0; } static int FUNCTION(fft_real,bitreverse_order) (BASE data[], const size_t stride, const size_t n, size_t logn) { /* This is the Goldrader bit-reversal algorithm */ size_t i; size_t j = 0; logn = 0 ; /* not needed for this algorithm */ for (i = 0; i < n - 1; i++) { size_t k = n / 2 ; if (i < j) { const BASE tmp = VECTOR(data,stride,i); VECTOR(data,stride,i) = VECTOR(data,stride,j); VECTOR(data,stride,j) = tmp; } while (k <= j) { j = j - k ; k = k / 2 ; } j += k ; } return 0; } sources_5316/external/gsl/gsl_randist__hyperg.c0000664000176700017670000000541611723710247020540 0ustar paulpaul/* randist/hyperg.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" #include "gsl_sf_gamma.h" /* The hypergeometric distribution has the form, prob(k) = choose(n1,t) choose(n2, t-k) / choose(n1+n2,t) where choose(a,b) = a!/(b!(a-b)!) n1 + n2 is the total population (tagged plus untagged) n1 is the tagged population t is the number of samples taken (without replacement) k is the number of tagged samples found */ unsigned int gsl_ran_hypergeometric (const gsl_rng * r, unsigned int n1, unsigned int n2, unsigned int t) { const unsigned int n = n1 + n2; unsigned int i = 0; unsigned int a = n1; unsigned int b = n1 + n2; unsigned int k = 0; if (t > n) { t = n ; } if (t < n / 2) { for (i = 0 ; i < t ; i++) { double u = gsl_rng_uniform(r) ; if (b * u < a) { k++ ; if (k == n1) return k ; a-- ; } b-- ; } return k; } else { for (i = 0 ; i < n - t ; i++) { double u = gsl_rng_uniform(r) ; if (b * u < a) { k++ ; if (k == n1) return n1 - k ; a-- ; } b-- ; } return n1 - k; } } double gsl_ran_hypergeometric_pdf (const unsigned int k, const unsigned int n1, const unsigned int n2, unsigned int t) { if (t > n1 + n2) { t = n1 + n2 ; } if (k > n1 || k > t) { return 0 ; } else if (t > n2 && k + n2 < t ) { return 0 ; } else { double p; double c1 = gsl_sf_lnchoose(n1,k); double c2 = gsl_sf_lnchoose(n2,t-k); double c3 = gsl_sf_lnchoose(n1+n2,t); p = exp(c1 + c2 - c3) ; return p; } } sources_5316/external/gsl/gsl_eigen__symmv.c0000664000176700017670000001341711723710247020040 0ustar paulpaul/* eigen/symmv.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_linalg.h" #include "gsl_eigen.h" /* Compute eigenvalues/eigenvectors of real symmetric matrix using reduction to tridiagonal form, followed by QR iteration with implicit shifts. See Golub & Van Loan, "Matrix Computations" (3rd ed), Section 8.3 */ #include "gsl_eigen__qrstep.c" gsl_eigen_symmv_workspace * gsl_eigen_symmv_alloc (const size_t n) { gsl_eigen_symmv_workspace * w ; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w= ((gsl_eigen_symmv_workspace *) malloc (sizeof(gsl_eigen_symmv_workspace))); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->d = (double *) malloc (n * sizeof (double)); if (w->d == 0) { GSL_ERROR_NULL ("failed to allocate space for diagonal", GSL_ENOMEM); } w->sd = (double *) malloc (n * sizeof (double)); if (w->sd == 0) { GSL_ERROR_NULL ("failed to allocate space for subdiagonal", GSL_ENOMEM); } w->gc = (double *) malloc (n * sizeof (double)); if (w->gc == 0) { GSL_ERROR_NULL ("failed to allocate space for cosines", GSL_ENOMEM); } w->gs = (double *) malloc (n * sizeof (double)); if (w->gs == 0) { GSL_ERROR_NULL ("failed to allocate space for sines", GSL_ENOMEM); } w->size = n; return w; } void gsl_eigen_symmv_free (gsl_eigen_symmv_workspace * w) { free(w->gs); free(w->gc); free(w->sd); free(w->d); free(w); } int gsl_eigen_symmv (gsl_matrix * A, gsl_vector * eval, gsl_matrix * evec, gsl_eigen_symmv_workspace * w) { if (A->size1 != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if (eval->size != A->size1) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (evec->size1 != A->size1 || evec->size2 != A->size1) { GSL_ERROR ("eigenvector matrix must match matrix size", GSL_EBADLEN); } else { double *const d = w->d; double *const sd = w->sd; const size_t N = A->size1; size_t a, b; /* handle special case */ if (N == 1) { double A00 = gsl_matrix_get (A, 0, 0); gsl_vector_set (eval, 0, A00); gsl_matrix_set (evec, 0, 0, 1.0); return GSL_SUCCESS; } /* use sd as the temporary workspace for the decomposition when computing eigenvectors */ { gsl_vector_view d_vec = gsl_vector_view_array (d, N); gsl_vector_view sd_vec = gsl_vector_view_array (sd, N - 1); gsl_vector_view tau = gsl_vector_view_array (sd, N - 1); gsl_linalg_symmtd_decomp (A, &tau.vector); gsl_linalg_symmtd_unpack (A, &tau.vector, evec, &d_vec.vector, &sd_vec.vector); } /* Make an initial pass through the tridiagonal decomposition to remove off-diagonal elements which are effectively zero */ chop_small_elements (N, d, sd); /* Progressively reduce the matrix until it is diagonal */ b = N - 1; while (b > 0) { if (sd[b - 1] == 0.0 || isnan(sd[b - 1])) { b--; continue; } /* Find the largest unreduced block (a,b) starting from b and working backwards */ a = b - 1; while (a > 0) { if (sd[a - 1] == 0.0) { break; } a--; } { size_t i; const size_t n_block = b - a + 1; double *d_block = d + a; double *sd_block = sd + a; double * const gc = w->gc; double * const gs = w->gs; /* apply QR reduction with implicit deflation to the unreduced block */ qrstep (n_block, d_block, sd_block, gc, gs); /* Apply Givens rotation Gij(c,s) to matrix Q, Q <- Q G */ for (i = 0; i < n_block - 1; i++) { const double c = gc[i], s = gs[i]; size_t k; for (k = 0; k < N; k++) { double qki = gsl_matrix_get (evec, k, a + i); double qkj = gsl_matrix_get (evec, k, a + i + 1); gsl_matrix_set (evec, k, a + i, qki * c - qkj * s); gsl_matrix_set (evec, k, a + i + 1, qki * s + qkj * c); } } /* remove any small off-diagonal elements */ chop_small_elements (N, d, sd); } } { gsl_vector_view d_vec = gsl_vector_view_array (d, N); gsl_vector_memcpy (eval, &d_vec.vector); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_cblas__source_rotg.h0000664000176700017670000000246511705263724021226 0ustar paulpaul/* blas/source_rotg.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const BASE roe = (fabs(*a) > fabs(*b) ? *a : *b); const BASE scale = fabs(*a) + fabs(*b); BASE r, z; if (scale != 0.0) { const BASE aos = *a / scale; const BASE bos = *b / scale; r = scale * sqrt(aos * aos + bos * bos); r = GSL_SIGN(roe) * r; *c = *a / r; *s = *b / r; z = 1.0; if (fabs(*a) > fabs(*b)) z = *s; if (fabs(*b) >= fabs(*a) && *c != 0.0) z = 1.0 / (*c); } else { *c = 1.0; *s = 0.0; r = 0.0; z = 0.0; } *a = r; *b = z; } sources_5316/external/gsl/gsl_sort__subsetind_source.c0000664000176700017670000000574111723710247022146 0ustar paulpaul/* sort/subsetind_source.c * * Copyright (C) 1999,2000,2001 Thomas Walter, Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ /* find the k-th smallest elements of the vector data, in ascending order */ int FUNCTION (gsl_sort, smallest_index) (size_t * p, const size_t k, const BASE * src, const size_t stride, const size_t n) { size_t i, j; BASE xbound; if (k > n) { GSL_ERROR ("subset length k exceeds vector length n", GSL_EINVAL); } if (k == 0 || n == 0) { return GSL_SUCCESS; } /* take the first element */ j = 1; xbound = src[0 * stride]; p[0] = 0; /* examine the remaining elements */ for (i = 1; i < n; i++) { size_t i1; BASE xi = src[i * stride]; if (j < k) { j++; } else if (xi >= xbound) { continue; } for (i1 = j - 1; i1 > 0 ; i1--) { if (xi > src[p[i1 - 1] * stride]) break; p[i1] = p[i1 - 1]; } p[i1] = i; xbound = src[p[j-1] * stride]; } return GSL_SUCCESS; } int FUNCTION (gsl_sort_vector,smallest_index) (size_t * p, const size_t k, const TYPE (gsl_vector) * v) { return FUNCTION (gsl_sort, smallest_index) (p, k, v->data, v->stride, v->size); } int FUNCTION (gsl_sort, largest_index) (size_t * p, const size_t k, const BASE * src, const size_t stride, const size_t n) { size_t i, j; BASE xbound; if (k > n) { GSL_ERROR ("subset length k exceeds vector length n", GSL_EINVAL); } if (k == 0 || n == 0) { return GSL_SUCCESS; } /* take the first element */ j = 1; xbound = src[0 * stride]; p[0] = 0; /* examine the remaining elements */ for (i = 1; i < n; i++) { size_t i1; BASE xi = src[i * stride]; if (j < k) { j++; } else if (xi <= xbound) { continue; } for (i1 = j - 1; i1 > 0 ; i1--) { if (xi < src[stride * p[i1 - 1]]) break; p[i1] = p[i1 - 1]; } p[i1] = i; xbound = src[stride * p[j-1]]; } return GSL_SUCCESS; } int FUNCTION (gsl_sort_vector,largest_index) (size_t * p, const size_t k, const TYPE (gsl_vector) * v) { return FUNCTION (gsl_sort, largest_index) (p, k, v->data, v->stride, v->size); } sources_5316/external/gsl/gsl_cdf__gamma.c0000664000176700017670000000274611723710247017417 0ustar paulpaul/* cdf/cdf_gamma.c * * Copyright (C) 2003 Jason Stover. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * Author: J. Stover */ #include "gsl__config.h" #include #include "gsl_cdf.h" #include "gsl_math.h" #include "gsl_sf_gamma.h" double gsl_cdf_gamma_P (const double x, const double a, const double b) { double P; double y = x / b; if (x <= 0.0) { return 0.0; } if (y > a) { P = 1 - gsl_sf_gamma_inc_Q (a, y); } else { P = gsl_sf_gamma_inc_P (a, y); } return P; } double gsl_cdf_gamma_Q (const double x, const double a, const double b) { double Q; double y = x / b; if (x <= 0.0) { return 1.0; } if (y < a) { Q = 1 - gsl_sf_gamma_inc_P (a, y); } else { Q = gsl_sf_gamma_inc_Q (a, y); } return Q; } sources_5316/external/gsl/gsl_fft__compare.h0000664000176700017670000000251211705263724020005 0ustar paulpaul/* fft/compare.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION(compare_complex,results) (const char *name_a, const BASE a[], const char *name_b, const BASE b[], size_t stride, size_t n, const double allowed_ticks); int FUNCTION(compare_real,results) (const char *name_a, const BASE a[], const char *name_b, const BASE b[], size_t stride, size_t n, const double allowed_ticks); sources_5316/external/gsl/gsl_matrix__rowcol_source.c0000664000176700017670000001157411723710247021771 0ustar paulpaul/* matrix/rowcol_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ QUALIFIED_VIEW(_gsl_vector,view) FUNCTION (gsl_matrix, row) (QUALIFIED_TYPE(gsl_matrix) * m, const size_t i) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (i >= m->size1) { GSL_ERROR_VAL ("row index is out of range", GSL_EINVAL, view); } { TYPE(gsl_vector) v = NULL_VECTOR; v.data = m->data + i * MULTIPLICITY * m->tda; v.size = m->size2; v.stride = 1; v.block = m->block; v.owner = 0; view.vector = v; return view; } } QUALIFIED_VIEW(_gsl_vector,view) FUNCTION (gsl_matrix, column) (QUALIFIED_TYPE(gsl_matrix) * m, const size_t j) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (j >= m->size2) { GSL_ERROR_VAL ("column index is out of range", GSL_EINVAL, view); } { TYPE(gsl_vector) v = NULL_VECTOR; v.data = m->data + j * MULTIPLICITY; v.size = m->size1; v.stride = m->tda; v.block = m->block; v.owner = 0; view.vector = v; return view; } } QUALIFIED_VIEW(_gsl_vector,view) FUNCTION (gsl_matrix, diagonal) (QUALIFIED_TYPE(gsl_matrix) * m) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; TYPE(gsl_vector) v = NULL_VECTOR; v.data = m->data; v.size = GSL_MIN(m->size1,m->size2); v.stride = m->tda + 1; v.block = m->block; v.owner = 0; view.vector = v; return view; } QUALIFIED_VIEW(_gsl_vector,view) FUNCTION (gsl_matrix, subdiagonal) (QUALIFIED_TYPE(gsl_matrix) * m, const size_t k) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (k >= m->size1) { GSL_ERROR_VAL ("subdiagonal index is out of range", GSL_EINVAL, view); } { TYPE(gsl_vector) v = NULL_VECTOR; v.data = m->data + k * MULTIPLICITY * m->tda; v.size = GSL_MIN(m->size1 - k, m->size2); v.stride = m->tda + 1; v.block = m->block; v.owner = 0; view.vector = v; return view; } } QUALIFIED_VIEW(_gsl_vector,view) FUNCTION (gsl_matrix, superdiagonal) (QUALIFIED_TYPE(gsl_matrix) * m, const size_t k) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (k >= m->size2) { GSL_ERROR_VAL ("column index is out of range", GSL_EINVAL, view); } { TYPE(gsl_vector) v = NULL_VECTOR; v.data = m->data + k * MULTIPLICITY; v.size = GSL_MIN(m->size1, m->size2 - k); v.stride = m->tda + 1; v.block = m->block; v.owner = 0; view.vector = v; return view; } } QUALIFIED_VIEW(_gsl_vector,view) FUNCTION (gsl_matrix, subrow) (QUALIFIED_TYPE(gsl_matrix) * m, const size_t i, const size_t offset, const size_t n) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (i >= m->size1) { GSL_ERROR_VAL ("row index is out of range", GSL_EINVAL, view); } else if (n == 0) { GSL_ERROR_VAL ("vector length n must be positive integer", GSL_EINVAL, view); } else if (offset + n > m->size1) { GSL_ERROR_VAL ("dimension n overflows matrix", GSL_EINVAL, view); } { TYPE(gsl_vector) v = NULL_VECTOR; v.data = m->data + MULTIPLICITY * (i * m->tda + offset); v.size = n; v.stride = 1; v.block = m->block; v.owner = 0; view.vector = v; return view; } } QUALIFIED_VIEW(_gsl_vector,view) FUNCTION (gsl_matrix, subcolumn) (QUALIFIED_TYPE(gsl_matrix) * m, const size_t j, const size_t offset, const size_t n) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (j >= m->size2) { GSL_ERROR_VAL ("column index is out of range", GSL_EINVAL, view); } else if (n == 0) { GSL_ERROR_VAL ("vector length n must be positive integer", GSL_EINVAL, view); } else if (offset + n > m->size2) { GSL_ERROR_VAL ("dimension n overflows matrix", GSL_EINVAL, view); } { TYPE(gsl_vector) v = NULL_VECTOR; v.data = m->data + MULTIPLICITY * (offset * m->tda + j); v.size = n; v.stride = m->tda; v.block = m->block; v.owner = 0; view.vector = v; return view; } } sources_5316/external/gsl/gsl_cblas__zgbmv.c0000664000176700017670000000070111723710247017777 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zgbmv (const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const int KL, const int KU, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE double #include "gsl_cblas__source_gbmv_c.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_syr.h0000664000176700017670000000323311705263724021062 0ustar paulpaul/* blas/source_syr.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; if (N == 0) return; if (alpha == 0.0) return; if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { const BASE tmp = alpha * X[ix]; INDEX jx = ix; for (j = i; j < N; j++) { A[lda * i + j] += X[jx] * tmp; jx += incX; } ix += incX; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { const BASE tmp = alpha * X[ix]; INDEX jx = OFFSET(N, incX); for (j = 0; j <= i; j++) { A[lda * i + j] += X[jx] * tmp; jx += incX; } ix += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_rng__types.c0000664000176700017670000000520511723710247017524 0ustar paulpaul/* rng/types.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #define N 100 const gsl_rng_type * gsl_rng_generator_types[N]; #define ADD(t) {if (i==N) abort(); gsl_rng_generator_types[i] = (t); i++; }; const gsl_rng_type ** gsl_rng_types_setup (void) { int i = 0; ADD(gsl_rng_borosh13); ADD(gsl_rng_cmrg); ADD(gsl_rng_coveyou); ADD(gsl_rng_fishman18); ADD(gsl_rng_fishman20); ADD(gsl_rng_fishman2x); ADD(gsl_rng_gfsr4); ADD(gsl_rng_knuthran); ADD(gsl_rng_knuthran2); ADD(gsl_rng_knuthran2002); ADD(gsl_rng_lecuyer21); ADD(gsl_rng_minstd); ADD(gsl_rng_mrg); ADD(gsl_rng_mt19937); ADD(gsl_rng_mt19937_1999); ADD(gsl_rng_mt19937_1998); ADD(gsl_rng_r250); ADD(gsl_rng_ran0); ADD(gsl_rng_ran1); ADD(gsl_rng_ran2); ADD(gsl_rng_ran3); ADD(gsl_rng_rand); ADD(gsl_rng_rand48); ADD(gsl_rng_random128_bsd); ADD(gsl_rng_random128_glibc2); ADD(gsl_rng_random128_libc5); ADD(gsl_rng_random256_bsd); ADD(gsl_rng_random256_glibc2); ADD(gsl_rng_random256_libc5); ADD(gsl_rng_random32_bsd); ADD(gsl_rng_random32_glibc2); ADD(gsl_rng_random32_libc5); ADD(gsl_rng_random64_bsd); ADD(gsl_rng_random64_glibc2); ADD(gsl_rng_random64_libc5); ADD(gsl_rng_random8_bsd); ADD(gsl_rng_random8_glibc2); ADD(gsl_rng_random8_libc5); ADD(gsl_rng_random_bsd); ADD(gsl_rng_random_glibc2); ADD(gsl_rng_random_libc5); ADD(gsl_rng_randu); ADD(gsl_rng_ranf); ADD(gsl_rng_ranlux); ADD(gsl_rng_ranlux389); ADD(gsl_rng_ranlxd1); ADD(gsl_rng_ranlxd2); ADD(gsl_rng_ranlxs0); ADD(gsl_rng_ranlxs1); ADD(gsl_rng_ranlxs2); ADD(gsl_rng_ranmar); ADD(gsl_rng_slatec); ADD(gsl_rng_taus); ADD(gsl_rng_taus2); ADD(gsl_rng_taus113); ADD(gsl_rng_transputer); ADD(gsl_rng_tt800); ADD(gsl_rng_uni); ADD(gsl_rng_uni32); ADD(gsl_rng_vax); ADD(gsl_rng_waterman14); ADD(gsl_rng_zuf); ADD(0); return gsl_rng_generator_types; } sources_5316/external/gsl/gsl_linalg__tridiag.h0000664000176700017670000000363711705263724020502 0ustar paulpaul/* linalg/tridiag.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2002 Gerard Jungman, * Brian Gough, David Necas * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Low level tridiagonal solvers. * Used internally in other areas of GSL. */ #ifndef __GSL_TRIDIAG_H__ #define __GSL_TRIDIAG_H__ #include static int solve_tridiag_nonsym( const double diag[], size_t d_stride, const double abovediag[], size_t a_stride, const double belowdiag[], size_t b_stride, const double rhs[], size_t r_stride, double x[], size_t x_stride, size_t N ); static int solve_tridiag( const double diag[], size_t d_stride, const double offdiag[], size_t o_stride, const double b[], size_t b_stride, double x[], size_t x_stride, size_t N); static int solve_cyc_tridiag( const double diag[], size_t d_stride, const double offdiag[], size_t o_stride, const double b[], size_t b_stride, double x[], size_t x_stride, size_t N ); static int solve_cyc_tridiag_nonsym( const double diag[], size_t d_stride, const double abovediag[], size_t a_stride, const double belowdiag[], size_t b_stride, const double rhs[], size_t r_stride, double x[], size_t x_stride, size_t N); #endif /* __GSL_TRIDIAG_H__ */ sources_5316/external/gsl/gsl_cblas__dtrsm.c0000664000176700017670000000073111723710247020006 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dtrsm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int M, const int N, const double alpha, const double *A, const int lda, double *B, const int ldb) { #define BASE double #include "gsl_cblas__source_trsm_r.h" #undef BASE } sources_5316/external/gsl/gsl_combination__init.c0000664000176700017670000000530011723710247021033 0ustar paulpaul/* combination/init.c * based on permutation/init.c by Brian Gough * * Copyright (C) 2001 Szymon Jaroszewicz * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_combination.h" gsl_combination * gsl_combination_alloc (const size_t n, const size_t k) { gsl_combination * c; if (n == 0) { GSL_ERROR_VAL ("combination parameter n must be positive integer", GSL_EDOM, 0); } if (k > n) { GSL_ERROR_VAL ("combination length k must be an integer less than or equal to n", GSL_EDOM, 0); } c = (gsl_combination *) malloc (sizeof (gsl_combination)); if (c == 0) { GSL_ERROR_VAL ("failed to allocate space for combination struct", GSL_ENOMEM, 0); } if (k > 0) { c->data = (size_t *) malloc (k * sizeof (size_t)); if (c->data == 0) { free (c); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for combination data", GSL_ENOMEM, 0); } } else { c->data = 0; } c->n = n; c->k = k; return c; } gsl_combination * gsl_combination_calloc (const size_t n, const size_t k) { size_t i; gsl_combination * c = gsl_combination_alloc (n, k); if (c == 0) return 0; /* initialize combination to identity */ for (i = 0; i < k; i++) { c->data[i] = i; } return c; } void gsl_combination_init_first (gsl_combination * c) { const size_t k = c->k ; size_t i; /* initialize combination to identity */ for (i = 0; i < k; i++) { c->data[i] = i; } } void gsl_combination_init_last (gsl_combination * c) { const size_t k = c->k ; size_t i; size_t n = c->n; /* initialize combination to identity */ for (i = 0; i < k; i++) { c->data[i] = n - k + i; } } void gsl_combination_free (gsl_combination * c) { if (c->k > 0) free (c->data); free (c); } sources_5316/external/gsl/gsl_matrix__prop.c0000664000176700017670000000362611723710247020063 0ustar paulpaul#include "gsl__config.h" #include "gsl_matrix.h" #include "gsl_errno.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__prop_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_version.h0000664000176700017670000000061711705263724017052 0ustar paulpaul#ifndef __GSL_VERSION_H__ #define __GSL_VERSION_H__ #include "gsl_types.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS #define GSL_VERSION "1.10" GSL_VAR const char * gsl_version; __END_DECLS #endif /* __GSL_VERSION_H__ */ sources_5316/external/gsl/gsl_cblas__sdsdot.c0000664000176700017670000000054711723710247020162 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" float cblas_sdsdot (const int N, const float alpha, const float *X, const int incX, const float *Y, const int incY) { #define INIT_VAL alpha #define ACC_TYPE double #define BASE float #include "gsl_cblas__source_dot_r.h" #undef ACC_TYPE #undef BASE #undef INIT_VAL } sources_5316/external/gsl/gsl_sum__work_u.c0000664000176700017670000000410211723710247017677 0ustar paulpaul#include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sum.h" gsl_sum_levin_u_workspace * gsl_sum_levin_u_alloc (size_t n) { gsl_sum_levin_u_workspace * w; if (n == 0) { GSL_ERROR_VAL ("length n must be positive integer", GSL_EDOM, 0); } w = (gsl_sum_levin_u_workspace *) malloc(sizeof(gsl_sum_levin_u_workspace)); if (w == NULL) { GSL_ERROR_VAL ("failed to allocate struct", GSL_ENOMEM, 0); } w->q_num = (double *) malloc (n * sizeof (double)); if (w->q_num == NULL) { free(w) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate space for q_num", GSL_ENOMEM, 0); } w->q_den = (double *) malloc (n * sizeof (double)); if (w->q_den == NULL) { free (w->q_num); free (w) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate space for q_den", GSL_ENOMEM, 0); } w->dq_num = (double *) malloc (n * n * sizeof (double)); if (w->dq_num == NULL) { free (w->q_den); free (w->q_num); free(w) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate space for dq_num", GSL_ENOMEM, 0); } w->dq_den = (double *) malloc (n * n * sizeof (double)); if (w->dq_den == NULL) { free (w->dq_num); free (w->q_den); free (w->q_num); free (w) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate space for dq_den", GSL_ENOMEM, 0); } w->dsum = (double *) malloc (n * sizeof (double)); if (w->dsum == NULL) { free (w->dq_den); free (w->dq_num); free (w->q_den); free (w->q_num); free (w) ; /* error in constructor, prevent memory leak */ GSL_ERROR_VAL ("failed to allocate space for dsum", GSL_ENOMEM, 0); } w->size = n; w->terms_used = 0; w->sum_plain = 0; return w; } void gsl_sum_levin_u_free (gsl_sum_levin_u_workspace * w) { free (w->dsum); free (w->dq_den); free (w->dq_num); free (w->q_den); free (w->q_num); free (w); } sources_5316/external/gsl/gsl_integration__qaws.c0000664000176700017670000001335511723710247021075 0ustar paulpaul/* integration/qaws.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_integration.h" #include "gsl_integration__initialise.c" #include "gsl_integration__append.c" #include "gsl_integration__qpsrt.c" #include "gsl_integration__util.c" #include "gsl_integration__qc25s.c" int gsl_integration_qaws (gsl_function * f, const double a, const double b, gsl_integration_qaws_table * t, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, double *result, double *abserr) { double area, errsum; double result0, abserr0; double tolerance; size_t iteration = 0; int roundoff_type1 = 0, roundoff_type2 = 0, error_type = 0; /* Initialize results */ initialise (workspace, a, b); *result = 0; *abserr = 0; if (limit > workspace->limit) { GSL_ERROR ("iteration limit exceeds available workspace", GSL_EINVAL) ; } if (b <= a) { GSL_ERROR ("limits must form an ascending sequence, a < b", GSL_EINVAL) ; } if (epsabs <= 0 && (epsrel < 50 * GSL_DBL_EPSILON || epsrel < 0.5e-28)) { GSL_ERROR ("tolerance cannot be acheived with given epsabs and epsrel", GSL_EBADTOL); } /* perform the first integration */ { double area1, area2; double error1, error2; int err_reliable1, err_reliable2; double a1 = a; double b1 = 0.5 * (a + b); double a2 = b1; double b2 = b; qc25s (f, a, b, a1, b1, t, &area1, &error1, &err_reliable1); qc25s (f, a, b, a2, b2, t, &area2, &error2, &err_reliable2); if (error1 > error2) { append_interval (workspace, a1, b1, area1, error1); append_interval (workspace, a2, b2, area2, error2); } else { append_interval (workspace, a2, b2, area2, error2); append_interval (workspace, a1, b1, area1, error1); } result0 = area1 + area2; abserr0 = error1 + error2; } /* Test on accuracy */ tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (result0)); /* Test on accuracy, use 0.01 relative error as an extra safety margin on the first iteration (ignored for subsequent iterations) */ if (abserr0 < tolerance && abserr0 < 0.01 * fabs(result0)) { *result = result0; *abserr = abserr0; return GSL_SUCCESS; } else if (limit == 1) { *result = result0; *abserr = abserr0; GSL_ERROR ("a maximum of one iteration was insufficient", GSL_EMAXITER); } area = result0; errsum = abserr0; iteration = 2; do { double a1, b1, a2, b2; double a_i, b_i, r_i, e_i; double area1 = 0, area2 = 0, area12 = 0; double error1 = 0, error2 = 0, error12 = 0; int err_reliable1, err_reliable2; /* Bisect the subinterval with the largest error estimate */ retrieve (workspace, &a_i, &b_i, &r_i, &e_i); a1 = a_i; b1 = 0.5 * (a_i + b_i); a2 = b1; b2 = b_i; qc25s (f, a, b, a1, b1, t, &area1, &error1, &err_reliable1); qc25s (f, a, b, a2, b2, t, &area2, &error2, &err_reliable2); area12 = area1 + area2; error12 = error1 + error2; errsum += (error12 - e_i); area += area12 - r_i; if (err_reliable1 && err_reliable2) { double delta = r_i - area12; if (fabs (delta) <= 1.0e-5 * fabs (area12) && error12 >= 0.99 * e_i) { roundoff_type1++; } if (iteration >= 10 && error12 > e_i) { roundoff_type2++; } } tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (area)); if (errsum > tolerance) { if (roundoff_type1 >= 6 || roundoff_type2 >= 20) { error_type = 2; /* round off error */ } /* set error flag in the case of bad integrand behaviour at a point of the integration range */ if (subinterval_too_small (a1, a2, b2)) { error_type = 3; } } update (workspace, a1, b1, area1, error1, a2, b2, area2, error2); retrieve (workspace, &a_i, &b_i, &r_i, &e_i); iteration++; } while (iteration < limit && !error_type && errsum > tolerance); *result = sum_results (workspace); *abserr = errsum; if (errsum <= tolerance) { return GSL_SUCCESS; } else if (error_type == 2) { GSL_ERROR ("roundoff error prevents tolerance from being achieved", GSL_EROUND); } else if (error_type == 3) { GSL_ERROR ("bad integrand behavior found in the integration interval", GSL_ESING); } else if (iteration == limit) { GSL_ERROR ("maximum number of subdivisions reached", GSL_EMAXITER); } else { GSL_ERROR ("could not integrate function", GSL_EFAILED); } } sources_5316/external/gsl/gsl_rng__ran0.c0000664000176700017670000000504511723710247017222 0ustar paulpaul/* rng/ran0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_rng.h" /* This is an implementation of the algorithm used in Numerical Recipe's ran0 generator. It is the same as MINSTD with an XOR mask of 123459876 on the seed. The period of this generator is 2^31. Note, if you choose a seed of 123459876 it would give a degenerate series 0,0,0,0, ... I've made that into an error. */ static inline unsigned long int ran0_get (void *vstate); static double ran0_get_double (void *vstate); static void ran0_set (void *state, unsigned long int s); static const long int m = 2147483647, a = 16807, q = 127773, r = 2836; static const unsigned long int mask = 123459876; typedef struct { unsigned long int x; } ran0_state_t; static inline unsigned long int ran0_get (void *vstate) { ran0_state_t *state = (ran0_state_t *) vstate; const unsigned long int x = state->x; const long int h = x / q; const long int t = a * (x - h * q) - h * r; if (t < 0) { state->x = t + m; } else { state->x = t; } return state->x; } static double ran0_get_double (void *vstate) { return ran0_get (vstate) / 2147483647.0 ; } static void ran0_set (void *vstate, unsigned long int s) { ran0_state_t *state = (ran0_state_t *) vstate; if (s == mask) { GSL_ERROR_VOID ("ran0 should not use seed == mask", GSL_EINVAL); } state->x = s ^ mask; return; } static const gsl_rng_type ran0_type = {"ran0", /* name */ 2147483646, /* RAND_MAX */ 1, /* RAND_MIN */ sizeof (ran0_state_t), &ran0_set, &ran0_get, &ran0_get_double}; const gsl_rng_type *gsl_rng_ran0 = &ran0_type; sources_5316/external/gsl/gsl_rng__ranlxs.c0000664000176700017670000001571211723710247017673 0ustar paulpaul/* rng/ranlxs.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is an implementation of M. Luescher's second generation version of the RANLUX generator. Thanks to Martin Luescher for providing information on this generator. */ static unsigned long int ranlxs_get (void *vstate); static inline double ranlxs_get_double (void *vstate); static void ranlxs_set_lux (void *state, unsigned long int s, unsigned int luxury); static void ranlxs0_set (void *state, unsigned long int s); static void ranlxs1_set (void *state, unsigned long int s); static void ranlxs2_set (void *state, unsigned long int s); static const int next[12] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 0}; static const int snext[24] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 0}; static const double sbase = 16777216.0; /* 2^24 */ static const double sone_bit = 1.0 / 16777216.0; /* 1/2^24 */ static const double one_bit = 1.0 / 281474976710656.0; /* 1/2^48 */ static const double shift = 268435456.0; /* 2^28 */ #define RANLUX_STEP(x1,x2,i1,i2,i3) \ x1=xdbl[i1] - xdbl[i2]; \ if (x2 < 0) \ { \ x1-=one_bit; \ x2+=1; \ } \ xdbl[i3]=x2 typedef struct { double xdbl[12], ydbl[12]; /* doubles first so they are 8-byte aligned */ double carry; float xflt[24]; unsigned int ir; unsigned int jr; unsigned int is; unsigned int is_old; unsigned int pr; } ranlxs_state_t; static void increment_state (ranlxs_state_t * state); static void increment_state (ranlxs_state_t * state) { int k, kmax, m; double x, y1, y2, y3; float *xflt = state->xflt; double *xdbl = state->xdbl; double *ydbl = state->ydbl; double carry = state->carry; unsigned int ir = state->ir; unsigned int jr = state->jr; for (k = 0; ir > 0; ++k) { y1 = xdbl[jr] - xdbl[ir]; y2 = y1 - carry; if (y2 < 0) { carry = one_bit; y2 += 1; } else { carry = 0; } xdbl[ir] = y2; ir = next[ir]; jr = next[jr]; } kmax = state->pr - 12; for (; k <= kmax; k += 12) { y1 = xdbl[7] - xdbl[0]; y1 -= carry; RANLUX_STEP (y2, y1, 8, 1, 0); RANLUX_STEP (y3, y2, 9, 2, 1); RANLUX_STEP (y1, y3, 10, 3, 2); RANLUX_STEP (y2, y1, 11, 4, 3); RANLUX_STEP (y3, y2, 0, 5, 4); RANLUX_STEP (y1, y3, 1, 6, 5); RANLUX_STEP (y2, y1, 2, 7, 6); RANLUX_STEP (y3, y2, 3, 8, 7); RANLUX_STEP (y1, y3, 4, 9, 8); RANLUX_STEP (y2, y1, 5, 10, 9); RANLUX_STEP (y3, y2, 6, 11, 10); if (y3 < 0) { carry = one_bit; y3 += 1; } else { carry = 0; } xdbl[11] = y3; } kmax = state->pr; for (; k < kmax; ++k) { y1 = xdbl[jr] - xdbl[ir]; y2 = y1 - carry; if (y2 < 0) { carry = one_bit; y2 += 1; } else { carry = 0; } xdbl[ir] = y2; ydbl[ir] = y2 + shift; ir = next[ir]; jr = next[jr]; } ydbl[ir] = xdbl[ir] + shift; for (k = next[ir]; k > 0;) { ydbl[k] = xdbl[k] + shift; k = next[k]; } for (k = 0, m = 0; k < 12; ++k) { x = xdbl[k]; y2 = ydbl[k] - shift; if (y2 > x) y2 -= sone_bit; y1 = (x - y2) * sbase; xflt[m++] = (float) y1; xflt[m++] = (float) y2; } state->ir = ir; state->is = 2 * ir; state->is_old = 2 * ir; state->jr = jr; state->carry = carry; } static inline double ranlxs_get_double (void *vstate) { ranlxs_state_t *state = (ranlxs_state_t *) vstate; const unsigned int is = snext[state->is]; state->is = is; if (is == state->is_old) increment_state (state); return state->xflt[state->is]; } static unsigned long int ranlxs_get (void *vstate) { return ranlxs_get_double (vstate) * 16777216.0; /* 2^24 */ } static void ranlxs_set_lux (void *vstate, unsigned long int s, unsigned int luxury) { ranlxs_state_t *state = (ranlxs_state_t *) vstate; int ibit, jbit, i, k, m, xbit[31]; double x, y; long int seed; if (s == 0) s = 1; /* default seed is 1 */ seed = s; i = seed & 0xFFFFFFFFUL; for (k = 0; k < 31; ++k) { xbit[k] = i % 2; i /= 2; } ibit = 0; jbit = 18; for (k = 0; k < 12; ++k) { x = 0; for (m = 1; m <= 48; ++m) { y = (double) xbit[ibit]; x += x + y; xbit[ibit] = (xbit[ibit] + xbit[jbit]) % 2; ibit = (ibit + 1) % 31; jbit = (jbit + 1) % 31; } state->xdbl[k] = one_bit * x; } state->carry = 0; state->ir = 0; state->jr = 7; state->is = 23; state->is_old = 0; state->pr = luxury; } static void ranlxs0_set (void *vstate, unsigned long int s) { ranlxs_set_lux (vstate, s, 109); } void ranlxs1_set (void *vstate, unsigned long int s) { ranlxs_set_lux (vstate, s, 202); } static void ranlxs2_set (void *vstate, unsigned long int s) { ranlxs_set_lux (vstate, s, 397); } static const gsl_rng_type ranlxs0_type = {"ranlxs0", /* name */ 0x00ffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ranlxs_state_t), &ranlxs0_set, &ranlxs_get, &ranlxs_get_double}; static const gsl_rng_type ranlxs1_type = {"ranlxs1", /* name */ 0x00ffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ranlxs_state_t), &ranlxs1_set, &ranlxs_get, &ranlxs_get_double}; static const gsl_rng_type ranlxs2_type = {"ranlxs2", /* name */ 0x00ffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ranlxs_state_t), &ranlxs2_set, &ranlxs_get, &ranlxs_get_double}; const gsl_rng_type *gsl_rng_ranlxs0 = &ranlxs0_type; const gsl_rng_type *gsl_rng_ranlxs1 = &ranlxs1_type; const gsl_rng_type *gsl_rng_ranlxs2 = &ranlxs2_type; sources_5316/external/gsl/gsl_cblas__chbmv.c0000664000176700017670000000063311723710247017755 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_chbmv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const int K, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE float #include "gsl_cblas__source_hbmv.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__bessel_K0.c0000664000176700017670000001355711723710247021220 0ustar paulpaul/* specfunc/bessel_K0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC bk0(), bk0e() */ /* chebyshev expansions series for bk0 on the interval 0. to 4.00000d+00 with weighted error 3.57e-19 log weighted error 18.45 significant figures required 17.99 decimal places required 18.97 series for ak0 on the interval 1.25000d-01 to 5.00000d-01 with weighted error 5.34e-17 log weighted error 16.27 significant figures required 14.92 decimal places required 16.89 series for ak02 on the interval 0. to 1.25000d-01 with weighted error 2.34e-17 log weighted error 16.63 significant figures required 14.67 decimal places required 17.20 */ static double bk0_data[11] = { -0.03532739323390276872, 0.3442898999246284869, 0.03597993651536150163, 0.00126461541144692592, 0.00002286212103119451, 0.00000025347910790261, 0.00000000190451637722, 0.00000000001034969525, 0.00000000000004259816, 0.00000000000000013744, 0.00000000000000000035 }; static cheb_series bk0_cs = { bk0_data, 10, -1, 1, 10 }; static double ak0_data[17] = { -0.07643947903327941, -0.02235652605699819, 0.00077341811546938, -0.00004281006688886, 0.00000308170017386, -0.00000026393672220, 0.00000002563713036, -0.00000000274270554, 0.00000000031694296, -0.00000000003902353, 0.00000000000506804, -0.00000000000068895, 0.00000000000009744, -0.00000000000001427, 0.00000000000000215, -0.00000000000000033, 0.00000000000000005 }; static cheb_series ak0_cs = { ak0_data, 16, -1, 1, 10 }; static double ak02_data[14] = { -0.01201869826307592, -0.00917485269102569, 0.00014445509317750, -0.00000401361417543, 0.00000015678318108, -0.00000000777011043, 0.00000000046111825, -0.00000000003158592, 0.00000000000243501, -0.00000000000020743, 0.00000000000001925, -0.00000000000000192, 0.00000000000000020, -0.00000000000000002 }; static cheb_series ak02_cs = { ak02_data, 13, -1, 1, 8 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_K0_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x <= 2.0) { const double lx = log(x); const double ex = exp(x); int stat_I0; gsl_sf_result I0; gsl_sf_result c; cheb_eval_e(&bk0_cs, 0.5*x*x-1.0, &c); stat_I0 = gsl_sf_bessel_I0_e(x, &I0); result->val = ex * ((-lx+M_LN2)*I0.val - 0.25 + c.val); result->err = ex * ((M_LN2+fabs(lx))*I0.err + c.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_I0; } else if(x <= 8.0) { const double sx = sqrt(x); gsl_sf_result c; cheb_eval_e(&ak0_cs, (16.0/x-5.0)/3.0, &c); result->val = (1.25 + c.val) / sx; result->err = c.err / sx; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sx = sqrt(x); gsl_sf_result c; cheb_eval_e(&ak02_cs, 16.0/x-1.0, &c); result->val = (1.25 + c.val) / sx; result->err = (c.err + GSL_DBL_EPSILON) / sx; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_K0_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x <= 2.0) { const double lx = log(x); int stat_I0; gsl_sf_result I0; gsl_sf_result c; cheb_eval_e(&bk0_cs, 0.5*x*x-1.0, &c); stat_I0 = gsl_sf_bessel_I0_e(x, &I0); result->val = (-lx+M_LN2)*I0.val - 0.25 + c.val; result->err = (fabs(lx) + M_LN2) * I0.err + c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_I0; } else { gsl_sf_result K0_scaled; int stat_K0 = gsl_sf_bessel_K0_scaled_e(x, &K0_scaled); int stat_e = gsl_sf_exp_mult_err_e(-x, GSL_DBL_EPSILON*fabs(x), K0_scaled.val, K0_scaled.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_K0); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_K0_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_K0_scaled_e(x, &result)); } double gsl_sf_bessel_K0(const double x) { EVAL_RESULT(gsl_sf_bessel_K0_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__source_trmv_r.h0000664000176700017670000000673211705263724021565 0ustar paulpaul/* blas/source_trmv_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; const int nonunit = (Diag == CblasNonUnit); const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { /* form x := A*x */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE temp = 0.0; const INDEX j_min = i + 1; const INDEX j_max = N; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { temp += X[jx] * A[lda * i + j]; jx += incX; } if (nonunit) { X[ix] = temp + X[ix] * A[lda * i + i]; } else { X[ix] += temp; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { BASE temp = 0.0; const INDEX j_min = 0; const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { temp += X[jx] * A[lda * i + j]; jx += incX; } if (nonunit) { X[ix] = temp + X[ix] * A[lda * i + i]; } else { X[ix] += temp; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := A'*x */ INDEX ix = OFFSET(N, incX) + (N - 1) * incX; for (i = N; i > 0 && i--;) { BASE temp = 0.0; const INDEX j_min = 0; const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; for (j = j_min; j < j_max; j++) { temp += X[jx] * A[lda * j + i]; jx += incX; } if (nonunit) { X[ix] = temp + X[ix] * A[lda * i + i]; } else { X[ix] += temp; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { BASE temp = 0.0; const INDEX j_min = i + 1; const INDEX j_max = N; INDEX jx = OFFSET(N, incX) + (i + 1) * incX; for (j = j_min; j < j_max; j++) { temp += X[jx] * A[lda * j + i]; jx += incX; } if (nonunit) { X[ix] = temp + X[ix] * A[lda * i + i]; } else { X[ix] += temp; } ix += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_fit.h0000664000176700017670000000531011705263724016142 0ustar paulpaul/* fit/gsl_fit.h * * Copyright (C) 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_FIT_H__ #define __GSL_FIT_H__ #include #include "gsl_math.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_fit_linear (const double * x, const size_t xstride, const double * y, const size_t ystride, const size_t n, double * c0, double * c1, double * cov00, double * cov01, double * cov11, double * sumsq); int gsl_fit_wlinear (const double * x, const size_t xstride, const double * w, const size_t wstride, const double * y, const size_t ystride, const size_t n, double * c0, double * c1, double * cov00, double * cov01, double * cov11, double * chisq); int gsl_fit_linear_est (const double x, const double c0, const double c1, const double cov00, const double cov01, const double cov11, double *y, double *y_err); int gsl_fit_mul (const double * x, const size_t xstride, const double * y, const size_t ystride, const size_t n, double * c1, double * cov11, double * sumsq); int gsl_fit_wmul (const double * x, const size_t xstride, const double * w, const size_t wstride, const double * y, const size_t ystride, const size_t n, double * c1, double * cov11, double * sumsq); int gsl_fit_mul_est (const double x, const double c1, const double cov11, double *y, double *y_err); __END_DECLS #endif /* __GSL_FIT_H__ */ sources_5316/external/gsl/gsl_cblas__ssymv.c0000664000176700017670000000062111723710247020034 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ssymv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *A, const int lda, const float *X, const int incX, const float beta, float *Y, const int incY) { #define BASE float #include "gsl_cblas__source_symv.h" #undef BASE } sources_5316/external/gsl/gsl_linalg__apply_givens.c0000664000176700017670000000743311723710247021545 0ustar paulpaul/* linalg/apply_givens.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2007 Gerard Jungman, Brian Gough * Copyright (C) 2004 Joerg Wensch, modifications for LQ. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ inline static void apply_givens_qr (size_t M, size_t N, gsl_matrix * Q, gsl_matrix * R, size_t i, size_t j, double c, double s) { size_t k; /* Apply rotation to matrix Q, Q' = Q G */ #if USE_BLAS { gsl_matrix_view Q0M = gsl_matrix_submatrix(Q,0,0,M,j+1); gsl_vector_view Qi = gsl_matrix_column(&Q0M.matrix,i); gsl_vector_view Qj = gsl_matrix_column(&Q0M.matrix,j); gsl_blas_drot(&Qi.vector, &Qj.vector, c, -s); } #else for (k = 0; k < M; k++) { double qki = gsl_matrix_get (Q, k, i); double qkj = gsl_matrix_get (Q, k, j); gsl_matrix_set (Q, k, i, qki * c - qkj * s); gsl_matrix_set (Q, k, j, qki * s + qkj * c); } #endif /* Apply rotation to matrix R, R' = G^T R (note: upper triangular so zero for column < row) */ #if USE_BLAS { k = GSL_MIN(i,j); gsl_matrix_view R0 = gsl_matrix_submatrix(R, 0, k, j+1, N-k); gsl_vector_view Ri = gsl_matrix_row(&R0.matrix,i); gsl_vector_view Rj = gsl_matrix_row(&R0.matrix,j); gsl_blas_drot(&Ri.vector, &Rj.vector, c, -s); } #else for (k = GSL_MIN (i, j); k < N; k++) { double rik = gsl_matrix_get (R, i, k); double rjk = gsl_matrix_get (R, j, k); gsl_matrix_set (R, i, k, c * rik - s * rjk); gsl_matrix_set (R, j, k, s * rik + c * rjk); } #endif } inline static void apply_givens_lq (size_t M, size_t N, gsl_matrix * Q, gsl_matrix * L, size_t i, size_t j, double c, double s) { size_t k; /* Apply rotation to matrix Q, Q' = G Q */ #if USE_BLAS { gsl_matrix_view Q0M = gsl_matrix_submatrix(Q,0,0,j+1,M); gsl_vector_view Qi = gsl_matrix_row(&Q0M.matrix,i); gsl_vector_view Qj = gsl_matrix_row(&Q0M.matrix,j); gsl_blas_drot(&Qi.vector, &Qj.vector, c, -s); } #else for (k = 0; k < M; k++) { double qik = gsl_matrix_get (Q, i, k); double qjk = gsl_matrix_get (Q, j, k); gsl_matrix_set (Q, i, k, qik * c - qjk * s); gsl_matrix_set (Q, j, k, qik * s + qjk * c); } #endif /* Apply rotation to matrix L, L' = L G^T (note: lower triangular so zero for column > row) */ #if USE_BLAS { k = GSL_MIN(i,j); gsl_matrix_view L0 = gsl_matrix_submatrix(L, k, 0, N-k, j+1); gsl_vector_view Li = gsl_matrix_column(&L0.matrix,i); gsl_vector_view Lj = gsl_matrix_column(&L0.matrix,j); gsl_blas_drot(&Li.vector, &Lj.vector, c, -s); } #else for (k = GSL_MIN (i, j); k < N; k++) { double lki = gsl_matrix_get (L, k, i); double lkj = gsl_matrix_get (L, k, j); gsl_matrix_set (L, k, i, c * lki - s * lkj); gsl_matrix_set (L, k, j, s * lki + c * lkj); } #endif } inline static void apply_givens_vec (gsl_vector * v, size_t i, size_t j, double c, double s) { /* Apply rotation to vector v' = G^T v */ double vi = gsl_vector_get (v, i); double vj = gsl_vector_get (v, j); gsl_vector_set (v, i, c * vi - s * vj); gsl_vector_set (v, j, s * vi + c * vj); } sources_5316/external/gsl/gsl_blas_types.h0000664000176700017670000000304711705263724017532 0ustar paulpaul/* blas/gsl_blas_types.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * Author: G. Jungman */ /* Based on draft BLAST C interface specification [Jul 7 1998] */ #ifndef __GSL_BLAS_TYPES_H__ #define __GSL_BLAS_TYPES_H__ #include "gsl_cblas.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef CBLAS_INDEX CBLAS_INDEX_t; typedef enum CBLAS_ORDER CBLAS_ORDER_t; typedef enum CBLAS_TRANSPOSE CBLAS_TRANSPOSE_t; typedef enum CBLAS_UPLO CBLAS_UPLO_t; typedef enum CBLAS_DIAG CBLAS_DIAG_t; typedef enum CBLAS_SIDE CBLAS_SIDE_t; /* typedef gsl_complex COMPLEX; */ __END_DECLS #endif /* __GSL_BLAS_TYPES_H__ */ sources_5316/external/gsl/gsl_sf__beta.c0000644000176700017670000001150710707442037017115 0ustar paulpaul/* specfunc/beta.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_log.h" #include "gsl_sf_psi.h" #include "gsl_sf_gamma.h" #include "gsl_sf__error.h" static double isnegint (const double x) { return (x < 0) && (x == floor(x)); } int gsl_sf_lnbeta_e(const double x, const double y, gsl_sf_result * result) { double sgn; int status = gsl_sf_lnbeta_sgn_e(x,y,result,&sgn); if (sgn == -1) { DOMAIN_ERROR(result); } return status; } int gsl_sf_lnbeta_sgn_e(const double x, const double y, gsl_sf_result * result, double * sgn) { /* CHECK_POINTER(result) */ if(x == 0.0 || y == 0.0) { *sgn = 0.0; DOMAIN_ERROR(result); } else if (isnegint(x) || isnegint(y)) { *sgn = 0.0; DOMAIN_ERROR(result); /* not defined for negative integers */ } /* See if we can handle the postive case with min/max < 0.2 */ if (x > 0 && y > 0) { const double max = GSL_MAX(x,y); const double min = GSL_MIN(x,y); const double rat = min/max; if(rat < 0.2) { /* min << max, so be careful * with the subtraction */ double lnpre_val; double lnpre_err; double lnpow_val; double lnpow_err; double t1, t2, t3; gsl_sf_result lnopr; gsl_sf_result gsx, gsy, gsxy; gsl_sf_gammastar_e(x, &gsx); gsl_sf_gammastar_e(y, &gsy); gsl_sf_gammastar_e(x+y, &gsxy); gsl_sf_log_1plusx_e(rat, &lnopr); lnpre_val = log(gsx.val*gsy.val/gsxy.val * M_SQRT2*M_SQRTPI); lnpre_err = gsx.err/gsx.val + gsy.err/gsy.val + gsxy.err/gsxy.val; t1 = min*log(rat); t2 = 0.5*log(min); t3 = (x+y-0.5)*lnopr.val; lnpow_val = t1 - t2 - t3; lnpow_err = GSL_DBL_EPSILON * (fabs(t1) + fabs(t2) + fabs(t3)); lnpow_err += fabs(x+y-0.5) * lnopr.err; result->val = lnpre_val + lnpow_val; result->err = lnpre_err + lnpow_err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); *sgn = 1.0; return GSL_SUCCESS; } } /* General case - Fallback */ { gsl_sf_result lgx, lgy, lgxy; double sgx, sgy, sgxy, xy = x+y; int stat_gx = gsl_sf_lngamma_sgn_e(x, &lgx, &sgx); int stat_gy = gsl_sf_lngamma_sgn_e(y, &lgy, &sgy); int stat_gxy = gsl_sf_lngamma_sgn_e(xy, &lgxy, &sgxy); *sgn = sgx * sgy * sgxy; result->val = lgx.val + lgy.val - lgxy.val; result->err = lgx.err + lgy.err + lgxy.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(lgx.val) + fabs(lgy.val) + fabs(lgxy.val)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_gx, stat_gy, stat_gxy); } } int gsl_sf_beta_e(const double x, const double y, gsl_sf_result * result) { if((x > 0 && y > 0) && x < 50.0 && y < 50.0) { /* Handle the easy case */ gsl_sf_result gx, gy, gxy; gsl_sf_gamma_e(x, &gx); gsl_sf_gamma_e(y, &gy); gsl_sf_gamma_e(x+y, &gxy); result->val = (gx.val*gy.val)/gxy.val; result->err = gx.err * fabs(gy.val/gxy.val); result->err += gy.err * fabs(gx.val/gxy.val); result->err += fabs((gx.val*gy.val)/(gxy.val*gxy.val)) * gxy.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if (isnegint(x) || isnegint(y)) { DOMAIN_ERROR(result); } else if (isnegint(x+y)) { /* infinity in the denominator */ result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result lb; double sgn; int stat_lb = gsl_sf_lnbeta_sgn_e(x, y, &lb, &sgn); if(stat_lb == GSL_SUCCESS) { int status = gsl_sf_exp_err_e(lb.val, lb.err, result); result->val *= sgn; return status; } else { result->val = 0.0; result->err = 0.0; return stat_lb; } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_lnbeta(const double x, const double y) { EVAL_RESULT(gsl_sf_lnbeta_e(x, y, &result)); } double gsl_sf_beta(const double x, const double y) { EVAL_RESULT(gsl_sf_beta_e(x, y, &result)); } sources_5316/external/gsl/gsl_eigen__genv.c0000664000176700017670000007002011723710247017615 0ustar paulpaul/* eigen/genv.c * * Copyright (C) 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include "gsl__config.h" #include "gsl_eigen.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_blas.h" #include "gsl_vector.h" #include "gsl_vector_complex.h" #include "gsl_matrix.h" #include "gsl_errno.h" /* * This module computes the eigenvalues and eigenvectors of a * real generalized eigensystem A x = \lambda B x. Left and right * Schur vectors are optionally computed as well. * * This file contains routines based on original code from LAPACK * which is distributed under the modified BSD license. */ static int genv_get_right_eigenvectors(const gsl_matrix *S, const gsl_matrix *T, gsl_matrix *Z, gsl_matrix_complex *evec, gsl_eigen_genv_workspace *w); static void genv_normalize_eigenvectors(gsl_vector_complex *alpha, gsl_matrix_complex *evec); /* gsl_eigen_genv_alloc() Allocate a workspace for solving the generalized eigenvalue problem. The size of this workspace is O(7n). Inputs: n - size of matrices Return: pointer to workspace */ gsl_eigen_genv_workspace * gsl_eigen_genv_alloc(const size_t n) { gsl_eigen_genv_workspace *w; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = calloc (1, sizeof (gsl_eigen_genv_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->size = n; w->Q = NULL; w->Z = NULL; w->gen_workspace_p = gsl_eigen_gen_alloc(n); if (w->gen_workspace_p == 0) { gsl_eigen_genv_free(w); GSL_ERROR_NULL ("failed to allocate space for gen workspace", GSL_ENOMEM); } /* compute the full Schur forms */ gsl_eigen_gen_params(1, 1, 1, w->gen_workspace_p); w->work1 = gsl_vector_alloc(n); w->work2 = gsl_vector_alloc(n); w->work3 = gsl_vector_alloc(n); w->work4 = gsl_vector_alloc(n); w->work5 = gsl_vector_alloc(n); w->work6 = gsl_vector_alloc(n); if (w->work1 == 0 || w->work2 == 0 || w->work3 == 0 || w->work4 == 0 || w->work5 == 0 || w->work6 == 0) { gsl_eigen_genv_free(w); GSL_ERROR_NULL ("failed to allocate space for additional workspace", GSL_ENOMEM); } return (w); } /* gsl_eigen_genv_alloc() */ /* gsl_eigen_genv_free() Free workspace w */ void gsl_eigen_genv_free(gsl_eigen_genv_workspace *w) { if (w->gen_workspace_p) gsl_eigen_gen_free(w->gen_workspace_p); if (w->work1) gsl_vector_free(w->work1); if (w->work2) gsl_vector_free(w->work2); if (w->work3) gsl_vector_free(w->work3); if (w->work4) gsl_vector_free(w->work4); if (w->work5) gsl_vector_free(w->work5); if (w->work6) gsl_vector_free(w->work6); free(w); } /* gsl_eigen_genv_free() */ /* gsl_eigen_genv() Solve the generalized eigenvalue problem A x = \lambda B x for the eigenvalues \lambda and right eigenvectors x. Inputs: A - general real matrix B - general real matrix alpha - (output) where to store eigenvalue numerators beta - (output) where to store eigenvalue denominators evec - (output) where to store eigenvectors w - workspace Return: success or error */ int gsl_eigen_genv (gsl_matrix * A, gsl_matrix * B, gsl_vector_complex * alpha, gsl_vector * beta, gsl_matrix_complex *evec, gsl_eigen_genv_workspace * w) { const size_t N = A->size1; /* check matrix and vector sizes */ if (N != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if ((N != B->size1) || (N != B->size2)) { GSL_ERROR ("B matrix dimensions must match A", GSL_EBADLEN); } else if (alpha->size != N || beta->size != N) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (w->size != N) { GSL_ERROR ("matrix size does not match workspace", GSL_EBADLEN); } else if (evec->size1 != N) { GSL_ERROR ("eigenvector matrix has wrong size", GSL_EBADLEN); } else { int s; gsl_matrix Z; /* * We need a place to store the right Schur vectors, so we will * treat evec as a real matrix and store them in the left * half - the factor of 2 in the tda corresponds to the * complex multiplicity */ Z.size1 = N; Z.size2 = N; Z.tda = 2 * N; Z.data = evec->data; Z.block = 0; Z.owner = 0; s = gsl_eigen_gen_QZ(A, B, alpha, beta, w->Q, &Z, w->gen_workspace_p); if (w->Z) { /* save right Schur vectors */ gsl_matrix_memcpy(w->Z, &Z); } /* only compute eigenvectors if we found all eigenvalues */ if (s == GSL_SUCCESS) { /* compute eigenvectors */ s = genv_get_right_eigenvectors(A, B, &Z, evec, w); if (s == GSL_SUCCESS) genv_normalize_eigenvectors(alpha, evec); } return s; } } /* gsl_eigen_genv() */ /* gsl_eigen_genv_QZ() Solve the generalized eigenvalue problem A x = \lambda B x for the eigenvalues \lambda and right eigenvectors x. Optionally compute left and/or right Schur vectors Q and Z which satisfy: A = Q S Z^t B = Q T Z^t where (S, T) is the generalized Schur form of (A, B) Inputs: A - general real matrix B - general real matrix alpha - (output) where to store eigenvalue numerators beta - (output) where to store eigenvalue denominators evec - (output) where to store eigenvectors Q - (output) if non-null, where to store left Schur vectors Z - (output) if non-null, where to store right Schur vectors w - workspace Return: success or error */ int gsl_eigen_genv_QZ (gsl_matrix * A, gsl_matrix * B, gsl_vector_complex * alpha, gsl_vector * beta, gsl_matrix_complex * evec, gsl_matrix * Q, gsl_matrix * Z, gsl_eigen_genv_workspace * w) { if (Q && (A->size1 != Q->size1 || A->size1 != Q->size2)) { GSL_ERROR("Q matrix has wrong dimensions", GSL_EBADLEN); } else if (Z && (A->size1 != Z->size1 || A->size1 != Z->size2)) { GSL_ERROR("Z matrix has wrong dimensions", GSL_EBADLEN); } else { int s; w->Q = Q; w->Z = Z; s = gsl_eigen_genv(A, B, alpha, beta, evec, w); w->Q = NULL; w->Z = NULL; return s; } } /* gsl_eigen_genv_QZ() */ /******************************************** * INTERNAL ROUTINES * ********************************************/ /* genv_get_right_eigenvectors() Compute right eigenvectors of the Schur form (S, T) and then backtransform them using the right Schur vectors to get right eigenvectors of the original system. Inputs: S - upper quasi-triangular Schur form of A T - upper triangular Schur form of B Z - right Schur vectors evec - (output) where to store eigenvectors w - workspace Return: success or error Notes: 1) based on LAPACK routine DTGEVC 2) eigenvectors are stored in the order that their eigenvalues appear in the Schur form */ static int genv_get_right_eigenvectors(const gsl_matrix *S, const gsl_matrix *T, gsl_matrix *Z, gsl_matrix_complex *evec, gsl_eigen_genv_workspace *w) { const size_t N = w->size; const double small = GSL_DBL_MIN * N / GSL_DBL_EPSILON; const double big = 1.0 / small; const double bignum = 1.0 / (GSL_DBL_MIN * N); size_t i, j, k, end; int is; double anorm, bnorm; double temp, temp2, temp2r, temp2i; double ascale, bscale; double salfar, sbeta; double acoef, bcoefr, bcoefi, acoefa, bcoefa; double creala, cimaga, crealb, cimagb, cre2a, cim2a, cre2b, cim2b; double dmin, xmax; double scale; size_t nw, na; int lsa, lsb; int complex_pair; gsl_complex z_zero, z_one; double bdiag[2] = { 0.0, 0.0 }; double sum[4]; int il2by2; size_t jr, jc, ja; double xscale; gsl_vector_complex_view ecol; gsl_vector_view re, im, re2, im2; GSL_SET_COMPLEX(&z_zero, 0.0, 0.0); GSL_SET_COMPLEX(&z_one, 1.0, 0.0); /* * Compute the 1-norm of each column of (S, T) excluding elements * belonging to the diagonal blocks to check for possible overflow * in the triangular solver */ anorm = fabs(gsl_matrix_get(S, 0, 0)); if (N > 1) anorm += fabs(gsl_matrix_get(S, 1, 0)); bnorm = fabs(gsl_matrix_get(T, 0, 0)); gsl_vector_set(w->work1, 0, 0.0); gsl_vector_set(w->work2, 0, 0.0); for (j = 1; j < N; ++j) { temp = temp2 = 0.0; if (gsl_matrix_get(S, j, j - 1) == 0.0) end = j; else end = j - 1; for (i = 0; i < end; ++i) { temp += fabs(gsl_matrix_get(S, i, j)); temp2 += fabs(gsl_matrix_get(T, i, j)); } gsl_vector_set(w->work1, j, temp); gsl_vector_set(w->work2, j, temp2); for (i = end; i < GSL_MIN(j + 2, N); ++i) { temp += fabs(gsl_matrix_get(S, i, j)); temp2 += fabs(gsl_matrix_get(T, i, j)); } anorm = GSL_MAX(anorm, temp); bnorm = GSL_MAX(bnorm, temp2); } ascale = 1.0 / GSL_MAX(anorm, GSL_DBL_MIN); bscale = 1.0 / GSL_MAX(bnorm, GSL_DBL_MIN); complex_pair = 0; for (k = 0; k < N; ++k) { size_t je = N - 1 - k; if (complex_pair) { complex_pair = 0; continue; } nw = 1; if (je > 0) { if (gsl_matrix_get(S, je, je - 1) != 0.0) { complex_pair = 1; nw = 2; } } if (!complex_pair) { if (fabs(gsl_matrix_get(S, je, je)) <= GSL_DBL_MIN && fabs(gsl_matrix_get(T, je, je)) <= GSL_DBL_MIN) { /* singular matrix pencil - unit eigenvector */ for (i = 0; i < N; ++i) gsl_matrix_complex_set(evec, i, je, z_zero); gsl_matrix_complex_set(evec, je, je, z_one); continue; } /* clear vector */ for (i = 0; i < N; ++i) gsl_vector_set(w->work3, i, 0.0); } else { /* clear vectors */ for (i = 0; i < N; ++i) { gsl_vector_set(w->work3, i, 0.0); gsl_vector_set(w->work4, i, 0.0); } } if (!complex_pair) { /* real eigenvalue */ temp = 1.0 / GSL_MAX(GSL_DBL_MIN, GSL_MAX(fabs(gsl_matrix_get(S, je, je)) * ascale, fabs(gsl_matrix_get(T, je, je)) * bscale)); salfar = (temp * gsl_matrix_get(S, je, je)) * ascale; sbeta = (temp * gsl_matrix_get(T, je, je)) * bscale; acoef = sbeta * ascale; bcoefr = salfar * bscale; bcoefi = 0.0; /* scale to avoid underflow */ scale = 1.0; lsa = fabs(sbeta) >= GSL_DBL_MIN && fabs(acoef) < small; lsb = fabs(salfar) >= GSL_DBL_MIN && fabs(bcoefr) < small; if (lsa) scale = (small / fabs(sbeta)) * GSL_MIN(anorm, big); if (lsb) scale = GSL_MAX(scale, (small / fabs(salfar)) * GSL_MIN(bnorm, big)); if (lsa || lsb) { scale = GSL_MIN(scale, 1.0 / (GSL_DBL_MIN * GSL_MAX(1.0, GSL_MAX(fabs(acoef), fabs(bcoefr))))); if (lsa) acoef = ascale * (scale * sbeta); else acoef *= scale; if (lsb) bcoefr = bscale * (scale * salfar); else bcoefr *= scale; } acoefa = fabs(acoef); bcoefa = fabs(bcoefr); /* first component is 1 */ gsl_vector_set(w->work3, je, 1.0); xmax = 1.0; /* compute contribution from column je of A and B to sum */ for (i = 0; i < je; ++i) { gsl_vector_set(w->work3, i, bcoefr*gsl_matrix_get(T, i, je) - acoef * gsl_matrix_get(S, i, je)); } } else { gsl_matrix_const_view vs = gsl_matrix_const_submatrix(S, je - 1, je - 1, 2, 2); gsl_matrix_const_view vt = gsl_matrix_const_submatrix(T, je - 1, je - 1, 2, 2); /* complex eigenvalue */ gsl_schur_gen_eigvals(&vs.matrix, &vt.matrix, &bcoefr, &temp2, &bcoefi, &acoef, &temp); if (bcoefi == 0.0) { GSL_ERROR("gsl_schur_gen_eigvals failed on complex block", GSL_FAILURE); } /* scale to avoid over/underflow */ acoefa = fabs(acoef); bcoefa = fabs(bcoefr) + fabs(bcoefi); scale = 1.0; if (acoefa*GSL_DBL_EPSILON < GSL_DBL_MIN && acoefa >= GSL_DBL_MIN) scale = (GSL_DBL_MIN / GSL_DBL_EPSILON) / acoefa; if (bcoefa*GSL_DBL_EPSILON < GSL_DBL_MIN && bcoefa >= GSL_DBL_MIN) scale = GSL_MAX(scale, (GSL_DBL_MIN/GSL_DBL_EPSILON) / bcoefa); if (GSL_DBL_MIN*acoefa > ascale) scale = ascale / (GSL_DBL_MIN * acoefa); if (GSL_DBL_MIN*bcoefa > bscale) scale = GSL_MIN(scale, bscale / (GSL_DBL_MIN*bcoefa)); if (scale != 1.0) { acoef *= scale; acoefa = fabs(acoef); bcoefr *= scale; bcoefi *= scale; bcoefa = fabs(bcoefr) + fabs(bcoefi); } /* compute first two components of eigenvector */ temp = acoef * gsl_matrix_get(S, je, je - 1); temp2r = acoef * gsl_matrix_get(S, je, je) - bcoefr * gsl_matrix_get(T, je, je); temp2i = -bcoefi * gsl_matrix_get(T, je, je); if (fabs(temp) >= fabs(temp2r) + fabs(temp2i)) { gsl_vector_set(w->work3, je, 1.0); gsl_vector_set(w->work4, je, 0.0); gsl_vector_set(w->work3, je - 1, -temp2r / temp); gsl_vector_set(w->work4, je - 1, -temp2i / temp); } else { gsl_vector_set(w->work3, je - 1, 1.0); gsl_vector_set(w->work4, je - 1, 0.0); temp = acoef * gsl_matrix_get(S, je - 1, je); gsl_vector_set(w->work3, je, (bcoefr*gsl_matrix_get(T, je - 1, je - 1) - acoef*gsl_matrix_get(S, je - 1, je - 1)) / temp); gsl_vector_set(w->work4, je, bcoefi*gsl_matrix_get(T, je - 1, je - 1) / temp); } xmax = GSL_MAX(fabs(gsl_vector_get(w->work3, je)) + fabs(gsl_vector_get(w->work4, je)), fabs(gsl_vector_get(w->work3, je - 1)) + fabs(gsl_vector_get(w->work4, je - 1))); /* compute contribution from column je and je - 1 */ creala = acoef * gsl_vector_get(w->work3, je - 1); cimaga = acoef * gsl_vector_get(w->work4, je - 1); crealb = bcoefr * gsl_vector_get(w->work3, je - 1) - bcoefi * gsl_vector_get(w->work4, je - 1); cimagb = bcoefi * gsl_vector_get(w->work3, je - 1) + bcoefr * gsl_vector_get(w->work4, je - 1); cre2a = acoef * gsl_vector_get(w->work3, je); cim2a = acoef * gsl_vector_get(w->work4, je); cre2b = bcoefr * gsl_vector_get(w->work3, je) - bcoefi * gsl_vector_get(w->work4, je); cim2b = bcoefi * gsl_vector_get(w->work3, je) + bcoefr * gsl_vector_get(w->work4, je); for (i = 0; i < je - 1; ++i) { gsl_vector_set(w->work3, i, -creala * gsl_matrix_get(S, i, je - 1) + crealb * gsl_matrix_get(T, i, je - 1) - cre2a * gsl_matrix_get(S, i, je) + cre2b * gsl_matrix_get(T, i, je)); gsl_vector_set(w->work4, i, -cimaga * gsl_matrix_get(S, i, je - 1) + cimagb * gsl_matrix_get(T, i, je - 1) - cim2a * gsl_matrix_get(S, i, je) + cim2b * gsl_matrix_get(T, i, je)); } } dmin = GSL_MAX(GSL_DBL_MIN, GSL_MAX(GSL_DBL_EPSILON*acoefa*anorm, GSL_DBL_EPSILON*bcoefa*bnorm)); /* triangular solve of (a A - b B) x = 0 */ il2by2 = 0; for (is = (int) je - (int) nw; is >= 0; --is) { j = (size_t) is; if (!il2by2 && j > 0) { if (gsl_matrix_get(S, j, j - 1) != 0.0) { il2by2 = 1; continue; } } bdiag[0] = gsl_matrix_get(T, j, j); if (il2by2) { na = 2; bdiag[1] = gsl_matrix_get(T, j + 1, j + 1); } else na = 1; if (nw == 1) { gsl_matrix_const_view sv = gsl_matrix_const_submatrix(S, j, j, na, na); gsl_vector_view xv, bv; bv = gsl_vector_subvector(w->work3, j, na); /* * the loop below expects the solution in the first column * of sum, so set stride to 2 */ xv = gsl_vector_view_array_with_stride(sum, 2, na); gsl_schur_solve_equation(acoef, &sv.matrix, bcoefr, bdiag[0], bdiag[1], &bv.vector, &xv.vector, &scale, &temp, dmin); } else { double bdat[4]; gsl_matrix_const_view sv = gsl_matrix_const_submatrix(S, j, j, na, na); gsl_vector_complex_view xv = gsl_vector_complex_view_array(sum, na); gsl_vector_complex_view bv = gsl_vector_complex_view_array(bdat, na); gsl_complex z; bdat[0] = gsl_vector_get(w->work3, j); bdat[1] = gsl_vector_get(w->work4, j); if (na == 2) { bdat[2] = gsl_vector_get(w->work3, j + 1); bdat[3] = gsl_vector_get(w->work4, j + 1); } GSL_SET_COMPLEX(&z, bcoefr, bcoefi); gsl_schur_solve_equation_z(acoef, &sv.matrix, &z, bdiag[0], bdiag[1], &bv.vector, &xv.vector, &scale, &temp, dmin); } if (scale < 1.0) { for (jr = 0; jr <= je; ++jr) { gsl_vector_set(w->work3, jr, scale * gsl_vector_get(w->work3, jr)); if (nw == 2) { gsl_vector_set(w->work4, jr, scale * gsl_vector_get(w->work4, jr)); } } } xmax = GSL_MAX(scale * xmax, temp); for (jr = 0; jr < na; ++jr) { gsl_vector_set(w->work3, j + jr, sum[jr*na]); if (nw == 2) gsl_vector_set(w->work4, j + jr, sum[jr*na + 1]); } if (j > 0) { xscale = 1.0 / GSL_MAX(1.0, xmax); temp = acoefa * gsl_vector_get(w->work1, j) + bcoefa * gsl_vector_get(w->work2, j); if (il2by2) { temp = GSL_MAX(temp, acoefa * gsl_vector_get(w->work1, j + 1) + bcoefa * gsl_vector_get(w->work2, j + 1)); } temp = GSL_MAX(temp, GSL_MAX(acoefa, bcoefa)); if (temp > bignum * xscale) { for (jr = 0; jr <= je; ++jr) { gsl_vector_set(w->work3, jr, xscale * gsl_vector_get(w->work3, jr)); if (nw == 2) { gsl_vector_set(w->work4, jr, xscale * gsl_vector_get(w->work4, jr)); } } xmax *= xscale; } for (ja = 0; ja < na; ++ja) { if (complex_pair) { creala = acoef * gsl_vector_get(w->work3, j + ja); cimaga = acoef * gsl_vector_get(w->work4, j + ja); crealb = bcoefr * gsl_vector_get(w->work3, j + ja) - bcoefi * gsl_vector_get(w->work4, j + ja); cimagb = bcoefi * gsl_vector_get(w->work3, j + ja) + bcoefr * gsl_vector_get(w->work4, j + ja); for (jr = 0; jr <= j - 1; ++jr) { gsl_vector_set(w->work3, jr, gsl_vector_get(w->work3, jr) - creala * gsl_matrix_get(S, jr, j + ja) + crealb * gsl_matrix_get(T, jr, j + ja)); gsl_vector_set(w->work4, jr, gsl_vector_get(w->work4, jr) - cimaga * gsl_matrix_get(S, jr, j + ja) + cimagb * gsl_matrix_get(T, jr, j + ja)); } } else { creala = acoef * gsl_vector_get(w->work3, j + ja); crealb = bcoefr * gsl_vector_get(w->work3, j + ja); for (jr = 0; jr <= j - 1; ++jr) { gsl_vector_set(w->work3, jr, gsl_vector_get(w->work3, jr) - creala * gsl_matrix_get(S, jr, j + ja) + crealb * gsl_matrix_get(T, jr, j + ja)); } } /* if (!complex_pair) */ } /* for (ja = 0; ja < na; ++ja) */ } /* if (j > 0) */ il2by2 = 0; } /* for (i = 0; i < je - nw; ++i) */ for (jr = 0; jr < N; ++jr) { gsl_vector_set(w->work5, jr, gsl_vector_get(w->work3, 0) * gsl_matrix_get(Z, jr, 0)); if (nw == 2) { gsl_vector_set(w->work6, jr, gsl_vector_get(w->work4, 0) * gsl_matrix_get(Z, jr, 0)); } } for (jc = 1; jc <= je; ++jc) { for (jr = 0; jr < N; ++jr) { gsl_vector_set(w->work5, jr, gsl_vector_get(w->work5, jr) + gsl_vector_get(w->work3, jc) * gsl_matrix_get(Z, jr, jc)); if (nw == 2) { gsl_vector_set(w->work6, jr, gsl_vector_get(w->work6, jr) + gsl_vector_get(w->work4, jc) * gsl_matrix_get(Z, jr, jc)); } } } /* store the eigenvector */ if (complex_pair) { ecol = gsl_matrix_complex_column(evec, je - 1); re = gsl_vector_complex_real(&ecol.vector); im = gsl_vector_complex_imag(&ecol.vector); ecol = gsl_matrix_complex_column(evec, je); re2 = gsl_vector_complex_real(&ecol.vector); im2 = gsl_vector_complex_imag(&ecol.vector); } else { ecol = gsl_matrix_complex_column(evec, je); re = gsl_vector_complex_real(&ecol.vector); im = gsl_vector_complex_imag(&ecol.vector); } for (jr = 0; jr < N; ++jr) { gsl_vector_set(&re.vector, jr, gsl_vector_get(w->work5, jr)); if (complex_pair) { gsl_vector_set(&im.vector, jr, gsl_vector_get(w->work6, jr)); gsl_vector_set(&re2.vector, jr, gsl_vector_get(w->work5, jr)); gsl_vector_set(&im2.vector, jr, -gsl_vector_get(w->work6, jr)); } else { gsl_vector_set(&im.vector, jr, 0.0); } } /* scale eigenvector */ xmax = 0.0; if (complex_pair) { for (j = 0; j < N; ++j) { xmax = GSL_MAX(xmax, fabs(gsl_vector_get(&re.vector, j)) + fabs(gsl_vector_get(&im.vector, j))); } } else { for (j = 0; j < N; ++j) { xmax = GSL_MAX(xmax, fabs(gsl_vector_get(&re.vector, j))); } } if (xmax > GSL_DBL_MIN) { xscale = 1.0 / xmax; for (j = 0; j < N; ++j) { gsl_vector_set(&re.vector, j, gsl_vector_get(&re.vector, j) * xscale); if (complex_pair) { gsl_vector_set(&im.vector, j, gsl_vector_get(&im.vector, j) * xscale); gsl_vector_set(&re2.vector, j, gsl_vector_get(&re2.vector, j) * xscale); gsl_vector_set(&im2.vector, j, gsl_vector_get(&im2.vector, j) * xscale); } } } } /* for (k = 0; k < N; ++k) */ return GSL_SUCCESS; } /* genv_get_right_eigenvectors() */ /* genv_normalize_eigenvectors() Normalize eigenvectors so that their Euclidean norm is 1 Inputs: alpha - eigenvalue numerators evec - eigenvectors */ static void genv_normalize_eigenvectors(gsl_vector_complex *alpha, gsl_matrix_complex *evec) { const size_t N = evec->size1; size_t i; /* looping */ gsl_complex ai; gsl_vector_complex_view vi; gsl_vector_view re, im; double scale; /* scaling factor */ for (i = 0; i < N; ++i) { ai = gsl_vector_complex_get(alpha, i); vi = gsl_matrix_complex_column(evec, i); re = gsl_vector_complex_real(&vi.vector); if (GSL_IMAG(ai) == 0.0) { scale = 1.0 / gsl_blas_dnrm2(&re.vector); gsl_blas_dscal(scale, &re.vector); } else if (GSL_IMAG(ai) > 0.0) { im = gsl_vector_complex_imag(&vi.vector); scale = 1.0 / gsl_hypot(gsl_blas_dnrm2(&re.vector), gsl_blas_dnrm2(&im.vector)); gsl_blas_zdscal(scale, &vi.vector); vi = gsl_matrix_complex_column(evec, i + 1); gsl_blas_zdscal(scale, &vi.vector); } } } /* genv_normalize_eigenvectors() */ sources_5316/external/gsl/gsl_matrix_ushort.h0000664000176700017670000002756211705263724020305 0ustar paulpaul/* matrix/gsl_matrix_ushort.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_USHORT_H__ #define __GSL_MATRIX_USHORT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_vector_ushort.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; unsigned short * data; gsl_block_ushort * block; int owner; } gsl_matrix_ushort; typedef struct { gsl_matrix_ushort matrix; } _gsl_matrix_ushort_view; typedef _gsl_matrix_ushort_view gsl_matrix_ushort_view; typedef struct { gsl_matrix_ushort matrix; } _gsl_matrix_ushort_const_view; typedef const _gsl_matrix_ushort_const_view gsl_matrix_ushort_const_view; /* Allocation */ gsl_matrix_ushort * gsl_matrix_ushort_alloc (const size_t n1, const size_t n2); gsl_matrix_ushort * gsl_matrix_ushort_calloc (const size_t n1, const size_t n2); gsl_matrix_ushort * gsl_matrix_ushort_alloc_from_block (gsl_block_ushort * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_ushort * gsl_matrix_ushort_alloc_from_matrix (gsl_matrix_ushort * m, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_ushort * gsl_vector_ushort_alloc_row_from_matrix (gsl_matrix_ushort * m, const size_t i); gsl_vector_ushort * gsl_vector_ushort_alloc_col_from_matrix (gsl_matrix_ushort * m, const size_t j); void gsl_matrix_ushort_free (gsl_matrix_ushort * m); /* Views */ _gsl_matrix_ushort_view gsl_matrix_ushort_submatrix (gsl_matrix_ushort * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_ushort_view gsl_matrix_ushort_row (gsl_matrix_ushort * m, const size_t i); _gsl_vector_ushort_view gsl_matrix_ushort_column (gsl_matrix_ushort * m, const size_t j); _gsl_vector_ushort_view gsl_matrix_ushort_diagonal (gsl_matrix_ushort * m); _gsl_vector_ushort_view gsl_matrix_ushort_subdiagonal (gsl_matrix_ushort * m, const size_t k); _gsl_vector_ushort_view gsl_matrix_ushort_superdiagonal (gsl_matrix_ushort * m, const size_t k); _gsl_vector_ushort_view gsl_matrix_ushort_subrow (gsl_matrix_ushort * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_ushort_view gsl_matrix_ushort_subcolumn (gsl_matrix_ushort * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_ushort_view gsl_matrix_ushort_view_array (unsigned short * base, const size_t n1, const size_t n2); _gsl_matrix_ushort_view gsl_matrix_ushort_view_array_with_tda (unsigned short * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_ushort_view gsl_matrix_ushort_view_vector (gsl_vector_ushort * v, const size_t n1, const size_t n2); _gsl_matrix_ushort_view gsl_matrix_ushort_view_vector_with_tda (gsl_vector_ushort * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_ushort_const_view gsl_matrix_ushort_const_submatrix (const gsl_matrix_ushort * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_ushort_const_view gsl_matrix_ushort_const_row (const gsl_matrix_ushort * m, const size_t i); _gsl_vector_ushort_const_view gsl_matrix_ushort_const_column (const gsl_matrix_ushort * m, const size_t j); _gsl_vector_ushort_const_view gsl_matrix_ushort_const_diagonal (const gsl_matrix_ushort * m); _gsl_vector_ushort_const_view gsl_matrix_ushort_const_subdiagonal (const gsl_matrix_ushort * m, const size_t k); _gsl_vector_ushort_const_view gsl_matrix_ushort_const_superdiagonal (const gsl_matrix_ushort * m, const size_t k); _gsl_vector_ushort_const_view gsl_matrix_ushort_const_subrow (const gsl_matrix_ushort * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_ushort_const_view gsl_matrix_ushort_const_subcolumn (const gsl_matrix_ushort * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_ushort_const_view gsl_matrix_ushort_const_view_array (const unsigned short * base, const size_t n1, const size_t n2); _gsl_matrix_ushort_const_view gsl_matrix_ushort_const_view_array_with_tda (const unsigned short * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_ushort_const_view gsl_matrix_ushort_const_view_vector (const gsl_vector_ushort * v, const size_t n1, const size_t n2); _gsl_matrix_ushort_const_view gsl_matrix_ushort_const_view_vector_with_tda (const gsl_vector_ushort * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ unsigned short gsl_matrix_ushort_get(const gsl_matrix_ushort * m, const size_t i, const size_t j); void gsl_matrix_ushort_set(gsl_matrix_ushort * m, const size_t i, const size_t j, const unsigned short x); unsigned short * gsl_matrix_ushort_ptr(gsl_matrix_ushort * m, const size_t i, const size_t j); const unsigned short * gsl_matrix_ushort_const_ptr(const gsl_matrix_ushort * m, const size_t i, const size_t j); void gsl_matrix_ushort_set_zero (gsl_matrix_ushort * m); void gsl_matrix_ushort_set_identity (gsl_matrix_ushort * m); void gsl_matrix_ushort_set_all (gsl_matrix_ushort * m, unsigned short x); int gsl_matrix_ushort_fread (FILE * stream, gsl_matrix_ushort * m) ; int gsl_matrix_ushort_fwrite (FILE * stream, const gsl_matrix_ushort * m) ; int gsl_matrix_ushort_fscanf (FILE * stream, gsl_matrix_ushort * m); int gsl_matrix_ushort_fprintf (FILE * stream, const gsl_matrix_ushort * m, const char * format); int gsl_matrix_ushort_memcpy(gsl_matrix_ushort * dest, const gsl_matrix_ushort * src); int gsl_matrix_ushort_swap(gsl_matrix_ushort * m1, gsl_matrix_ushort * m2); int gsl_matrix_ushort_swap_rows(gsl_matrix_ushort * m, const size_t i, const size_t j); int gsl_matrix_ushort_swap_columns(gsl_matrix_ushort * m, const size_t i, const size_t j); int gsl_matrix_ushort_swap_rowcol(gsl_matrix_ushort * m, const size_t i, const size_t j); int gsl_matrix_ushort_transpose (gsl_matrix_ushort * m); int gsl_matrix_ushort_transpose_memcpy (gsl_matrix_ushort * dest, const gsl_matrix_ushort * src); unsigned short gsl_matrix_ushort_max (const gsl_matrix_ushort * m); unsigned short gsl_matrix_ushort_min (const gsl_matrix_ushort * m); void gsl_matrix_ushort_minmax (const gsl_matrix_ushort * m, unsigned short * min_out, unsigned short * max_out); void gsl_matrix_ushort_max_index (const gsl_matrix_ushort * m, size_t * imax, size_t *jmax); void gsl_matrix_ushort_min_index (const gsl_matrix_ushort * m, size_t * imin, size_t *jmin); void gsl_matrix_ushort_minmax_index (const gsl_matrix_ushort * m, size_t * imin, size_t * jmin, size_t * imax, size_t * jmax); int gsl_matrix_ushort_isnull (const gsl_matrix_ushort * m); int gsl_matrix_ushort_ispos (const gsl_matrix_ushort * m); int gsl_matrix_ushort_isneg (const gsl_matrix_ushort * m); int gsl_matrix_ushort_isnonneg (const gsl_matrix_ushort * m); int gsl_matrix_ushort_add (gsl_matrix_ushort * a, const gsl_matrix_ushort * b); int gsl_matrix_ushort_sub (gsl_matrix_ushort * a, const gsl_matrix_ushort * b); int gsl_matrix_ushort_mul_elements (gsl_matrix_ushort * a, const gsl_matrix_ushort * b); int gsl_matrix_ushort_div_elements (gsl_matrix_ushort * a, const gsl_matrix_ushort * b); int gsl_matrix_ushort_scale (gsl_matrix_ushort * a, const double x); int gsl_matrix_ushort_add_constant (gsl_matrix_ushort * a, const double x); int gsl_matrix_ushort_add_diagonal (gsl_matrix_ushort * a, const double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_ushort_get_row(gsl_vector_ushort * v, const gsl_matrix_ushort * m, const size_t i); int gsl_matrix_ushort_get_col(gsl_vector_ushort * v, const gsl_matrix_ushort * m, const size_t j); int gsl_matrix_ushort_set_row(gsl_matrix_ushort * m, const size_t i, const gsl_vector_ushort * v); int gsl_matrix_ushort_set_col(gsl_matrix_ushort * m, const size_t j, const gsl_vector_ushort * v); /* inline functions if you are using GCC */ #ifdef HAVE_INLINE extern inline unsigned short gsl_matrix_ushort_get(const gsl_matrix_ushort * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, 0) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, 0) ; } #endif return m->data[i * m->tda + j] ; } extern inline void gsl_matrix_ushort_set(gsl_matrix_ushort * m, const size_t i, const size_t j, const unsigned short x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif m->data[i * m->tda + j] = x ; } extern inline unsigned short * gsl_matrix_ushort_ptr(gsl_matrix_ushort * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (unsigned short *) (m->data + (i * m->tda + j)) ; } extern inline const unsigned short * gsl_matrix_ushort_const_ptr(const gsl_matrix_ushort * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const unsigned short *) (m->data + (i * m->tda + j)) ; } #endif __END_DECLS #endif /* __GSL_MATRIX_USHORT_H__ */ sources_5316/external/gsl/gsl_block__init.c0000664000176700017670000000360411723710247017630 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_block.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_block__init_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_sf__bessel_temme.h0000644000176700017670000000234510707442037020653 0ustar paulpaul/* specfunc/bessel_temme.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef BESSEL_TEMME_H_ #define BESSEL_TEMME_H_ #include "gsl_sf_result.h" int gsl_sf_bessel_Y_temme(const double nu, const double x, gsl_sf_result * Y_nu, gsl_sf_result * Y_nup1); int gsl_sf_bessel_K_scaled_temme(const double nu, const double x, double * K_nu, double * K_nup1, double * Kp_nu); #endif /* !BESSEL_TEMME_H_ */ sources_5316/external/gsl/gsl_cblas__source_hpr.h0000664000176700017670000000536311705263724021044 0ustar paulpaul/* blas/source_hpr.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (order == CblasColMajor) ? -1 : 1; INDEX i, j; if (alpha == 0.0) return; if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { const BASE tmp_real = alpha * CONST_REAL(X, ix); const BASE tmp_imag = alpha * conj * CONST_IMAG(X, ix); INDEX jx = ix; { const BASE X_real = CONST_REAL(X, jx); const BASE X_imag = -conj * CONST_IMAG(X, jx); REAL(Ap, TPUP(N, i, i)) += X_real * tmp_real - X_imag * tmp_imag; IMAG(Ap, TPUP(N, i, i)) = 0; jx += incX; } for (j = i + 1; j < N; j++) { const BASE X_real = CONST_REAL(X, jx); const BASE X_imag = -conj * CONST_IMAG(X, jx); REAL(Ap, TPUP(N, i, j)) += X_real * tmp_real - X_imag * tmp_imag; IMAG(Ap, TPUP(N, i, j)) += X_imag * tmp_real + X_real * tmp_imag; jx += incX; } ix += incX; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { const BASE tmp_real = alpha * CONST_REAL(X, ix); const BASE tmp_imag = alpha * conj * CONST_IMAG(X, ix); INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE X_real = CONST_REAL(X, jx); const BASE X_imag = -conj * CONST_IMAG(X, jx); REAL(Ap, TPLO(N, i, j)) += X_real * tmp_real - X_imag * tmp_imag; IMAG(Ap, TPLO(N, i, j)) += X_imag * tmp_real + X_real * tmp_imag; jx += incX; } { const BASE X_real = CONST_REAL(X, jx); const BASE X_imag = -conj * CONST_IMAG(X, jx); REAL(Ap, TPLO(N, i, i)) += X_real * tmp_real - X_imag * tmp_imag; IMAG(Ap, TPLO(N, i, i)) = 0; jx += incX; } ix += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_sf__bessel_Y1.c0000644000176700017670000001015610707442037020027 0ustar paulpaul/* specfunc/bessel_Y1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_amp_phase.h" #include "gsl_sf__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besy1, 1977 version, w. fullerton */ /* chebyshev expansions series for by1 on the interval 0. to 1.60000d+01 with weighted error 1.87e-18 log weighted error 17.73 significant figures required 17.83 decimal places required 18.30 */ static double by1_data[14] = { 0.03208047100611908629, 1.262707897433500450, 0.00649996189992317500, -0.08936164528860504117, 0.01325088122175709545, -0.00089790591196483523, 0.00003647361487958306, -0.00000100137438166600, 0.00000001994539657390, -0.00000000030230656018, 0.00000000000360987815, -0.00000000000003487488, 0.00000000000000027838, -0.00000000000000000186 }; static cheb_series by1_cs = { by1_data, 13, -1, 1, 10 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Y1_e(const double x, gsl_sf_result * result) { const double two_over_pi = 2.0/M_PI; const double xmin = 1.571*GSL_DBL_MIN; /*exp ( amax1(alog(r1mach(1)), -alog(r1mach(2)))+.01) */ const double x_small = 2.0 * GSL_SQRT_DBL_EPSILON; const double xmax = 1.0/GSL_DBL_EPSILON; /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < xmin) { OVERFLOW_ERROR(result); } else if(x < x_small) { const double lnterm = log(0.5*x); gsl_sf_result J1; gsl_sf_result c; int status = gsl_sf_bessel_J1_e(x, &J1); cheb_eval_e(&by1_cs, -1.0, &c); result->val = two_over_pi * lnterm * J1.val + (0.5 + c.val)/x; result->err = fabs(lnterm) * (fabs(GSL_DBL_EPSILON * J1.val) + J1.err) + c.err/x; return status; } else if(x < 4.0) { const double lnterm = log(0.5*x); int status; gsl_sf_result J1; gsl_sf_result c; cheb_eval_e(&by1_cs, 0.125*x*x-1.0, &c); status = gsl_sf_bessel_J1_e(x, &J1); result->val = two_over_pi * lnterm * J1.val + (0.5 + c.val)/x; result->err = fabs(lnterm) * (fabs(GSL_DBL_EPSILON * J1.val) + J1.err) + c.err/x; return status; } else if(x < xmax) { const double z = 32.0/(x*x) - 1.0; gsl_sf_result ca; gsl_sf_result ct; gsl_sf_result cp; const int stat_ca = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bm1_cs, z, &ca); const int stat_ct = cheb_eval_e(&_gsl_sf_bessel_amp_phase_bth1_cs, z, &ct); const int stat_cp = gsl_sf_bessel_cos_pi4_e(x, ct.val/x, &cp); const double sqrtx = sqrt(x); const double ampl = (0.75 + ca.val) / sqrtx; result->val = -ampl * cp.val; result->err = fabs(cp.val) * ca.err/sqrtx + fabs(ampl) * cp.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_ca, stat_ct, stat_cp); } else { UNDERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_Y1(const double x) { EVAL_RESULT(gsl_sf_bessel_Y1_e(x, &result)); } sources_5316/external/gsl/gsl_matrix__rowcol.c0000664000176700017670000000763011723710247020407 0ustar paulpaul#include "gsl__config.h" #include "gsl_math.h" #include "gsl_matrix.h" #include "gsl_vector.h" #include "gsl_errno.h" #include "gsl_matrix__view.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_CHAR #define USE_QUALIFIER #define QUALIFIER const #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_matrix__rowcol_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_specfunc__bessel_Jn.c0000664000176700017670000001176711723710247021316 0ustar paulpaul/* specfunc/bessel_Jn.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_amp_phase.h" #include "gsl_specfunc__bessel_olver.h" #include "gsl_sf_bessel.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Jn_e(int n, double x, gsl_sf_result * result) { int sign = 1; if(n < 0) { /* reduce to case n >= 0 */ n = -n; if(GSL_IS_ODD(n)) sign = -sign; } if(x < 0.0) { /* reduce to case x >= 0. */ x = -x; if(GSL_IS_ODD(n)) sign = -sign; } /* CHECK_POINTER(result) */ if(n == 0) { gsl_sf_result b0; int stat_J0 = gsl_sf_bessel_J0_e(x, &b0); result->val = sign * b0.val; result->err = b0.err; return stat_J0; } else if(n == 1) { gsl_sf_result b1; int stat_J1 = gsl_sf_bessel_J1_e(x, &b1); result->val = sign * b1.val; result->err = b1.err; return stat_J1; } else { if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x*x < 10.0*(n+1.0)*GSL_ROOT5_DBL_EPSILON) { gsl_sf_result b; int status = gsl_sf_bessel_IJ_taylor_e((double)n, x, -1, 50, GSL_DBL_EPSILON, &b); result->val = sign * b.val; result->err = b.err; result->err += GSL_DBL_EPSILON * fabs(result->val); return status; } else if(GSL_ROOT4_DBL_EPSILON * x > (n*n+1.0)) { int status = gsl_sf_bessel_Jnu_asympx_e((double)n, x, result); result->val *= sign; return status; } else if(n > 50) { int status = gsl_sf_bessel_Jnu_asymp_Olver_e((double)n, x, result); result->val *= sign; return status; } else if(x > 1000.0) { /* We need this to avoid feeding large x to CF1; note that * due to the above check, we know that n <= 50. */ int status = gsl_sf_bessel_Jnu_asympx_e((double)n, x, result); result->val *= sign; return status; } else { double ans; double err; double ratio; double sgn; int stat_b; int stat_CF1 = gsl_sf_bessel_J_CF1((double)n, x, &ratio, &sgn); /* backward recurrence */ double Jkp1 = GSL_SQRT_DBL_MIN * ratio; double Jk = GSL_SQRT_DBL_MIN; double Jkm1; int k; for(k=n; k>0; k--) { Jkm1 = 2.0*k/x * Jk - Jkp1; Jkp1 = Jk; Jk = Jkm1; } if(fabs(Jkp1) > fabs(Jk)) { gsl_sf_result b1; stat_b = gsl_sf_bessel_J1_e(x, &b1); ans = b1.val/Jkp1 * GSL_SQRT_DBL_MIN; err = b1.err/Jkp1 * GSL_SQRT_DBL_MIN; } else { gsl_sf_result b0; stat_b = gsl_sf_bessel_J0_e(x, &b0); ans = b0.val/Jk * GSL_SQRT_DBL_MIN; err = b0.err/Jk * GSL_SQRT_DBL_MIN; } result->val = sign * ans; result->err = fabs(err); return GSL_ERROR_SELECT_2(stat_CF1, stat_b); } } } int gsl_sf_bessel_Jn_array(int nmin, int nmax, double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(nmin < 0 || nmax < nmin) { int n; for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = 0.0; } GSL_ERROR ("domain error", GSL_EDOM); } else if(x == 0.0) { int n; for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = 0.0; } if(nmin == 0) result_array[0] = 1.0; return GSL_SUCCESS; } else { gsl_sf_result r_Jnp1; gsl_sf_result r_Jn; int stat_np1 = gsl_sf_bessel_Jn_e(nmax+1, x, &r_Jnp1); int stat_n = gsl_sf_bessel_Jn_e(nmax, x, &r_Jn); int stat = GSL_ERROR_SELECT_2(stat_np1, stat_n); double Jnp1 = r_Jnp1.val; double Jn = r_Jn.val; double Jnm1; int n; if(stat == GSL_SUCCESS) { for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = Jn; Jnm1 = -Jnp1 + 2.0*n/x * Jn; Jnp1 = Jn; Jn = Jnm1; } } else { for(n=nmax; n>=nmin; n--) { result_array[n-nmin] = 0.0; } } return stat; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_Jn(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_Jn_e(n, x, &result)); } sources_5316/external/gsl/gsl_statistics__wvariance_source.c0000664000176700017670000000775111723710247023333 0ustar paulpaul/* statistics/wvariance_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static double FUNCTION(compute,wvariance) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n, const double wmean); static double FUNCTION(compute,factor) (const BASE w[], const size_t wstride, const size_t n); static double FUNCTION(compute,wvariance) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n, const double wmean) { /* takes a dataset and finds the weighted variance */ long double wvariance = 0 ; long double W = 0; size_t i; /* find the sum of the squares */ for (i = 0; i < n; i++) { BASE wi = w[i * wstride]; if (wi > 0) { const long double delta = (data[i * stride] - wmean); W += wi ; wvariance += (delta * delta - wvariance) * (wi / W); } } return wvariance ; } static double FUNCTION(compute,factor) (const BASE w[], const size_t wstride, const size_t n) { /* Find the factor ``N/(N-1)'' which multiplies the raw std dev */ long double a = 0 ; long double b = 0; long double factor; size_t i; /* find the sum of the squares */ for (i = 0; i < n; i++) { BASE wi = w[i * wstride]; if (wi > 0) { a += wi ; b += wi * wi ; } } factor = (a*a) / ((a*a) - b); return factor ; } double FUNCTION(gsl_stats,wvariance_with_fixed_mean) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n, const double wmean) { const double wvariance = FUNCTION(compute,wvariance) (w, wstride, data, stride, n, wmean); return wvariance; } double FUNCTION(gsl_stats,wsd_with_fixed_mean) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n, const double wmean) { const double wvariance = FUNCTION(compute,wvariance) (w, wstride, data, stride, n, wmean); const double wsd = sqrt (wvariance); return wsd; } double FUNCTION(gsl_stats,wvariance_m) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n, const double wmean) { const double variance = FUNCTION(compute,wvariance) (w, wstride, data, stride, n, wmean); const double scale = FUNCTION(compute,factor)(w, wstride, n); return scale * variance; } double FUNCTION(gsl_stats,wsd_m) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n, const double wmean) { const double variance = FUNCTION(compute,wvariance) (w, wstride, data, stride, n, wmean); const double scale = FUNCTION(compute,factor)(w, wstride, n); const double wsd = sqrt(scale * variance) ; return wsd; } double FUNCTION(gsl_stats,wsd) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n) { const double wmean = FUNCTION(gsl_stats,wmean) (w, wstride, data, stride, n); return FUNCTION(gsl_stats,wsd_m) (w, wstride, data, stride, n, wmean) ; } double FUNCTION(gsl_stats,wvariance) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n) { const double wmean = FUNCTION(gsl_stats,wmean) (w, wstride, data, stride, n); return FUNCTION(gsl_stats,wvariance_m)(w, wstride, data, stride, n, wmean); } sources_5316/external/gsl/gsl_const_mksa.h0000664000176700017670000001554611705263724017535 0ustar paulpaul/* const/gsl_const_mksa.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, * 2006 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_CONST_MKSA__ #define __GSL_CONST_MKSA__ #define GSL_CONST_MKSA_SPEED_OF_LIGHT (2.99792458e8) /* m / s */ #define GSL_CONST_MKSA_GRAVITATIONAL_CONSTANT (6.673e-11) /* m^3 / kg s^2 */ #define GSL_CONST_MKSA_PLANCKS_CONSTANT_H (6.62606876e-34) /* kg m^2 / s */ #define GSL_CONST_MKSA_PLANCKS_CONSTANT_HBAR (1.05457159642e-34) /* kg m^2 / s */ #define GSL_CONST_MKSA_ASTRONOMICAL_UNIT (1.49597870691e11) /* m */ #define GSL_CONST_MKSA_LIGHT_YEAR (9.46053620707e15) /* m */ #define GSL_CONST_MKSA_PARSEC (3.08567758135e16) /* m */ #define GSL_CONST_MKSA_GRAV_ACCEL (9.80665e0) /* m / s^2 */ #define GSL_CONST_MKSA_ELECTRON_VOLT (1.602176462e-19) /* kg m^2 / s^2 */ #define GSL_CONST_MKSA_MASS_ELECTRON (9.10938188e-31) /* kg */ #define GSL_CONST_MKSA_MASS_MUON (1.88353109e-28) /* kg */ #define GSL_CONST_MKSA_MASS_PROTON (1.67262158e-27) /* kg */ #define GSL_CONST_MKSA_MASS_NEUTRON (1.67492716e-27) /* kg */ #define GSL_CONST_MKSA_RYDBERG (2.17987190389e-18) /* kg m^2 / s^2 */ #define GSL_CONST_MKSA_BOLTZMANN (1.3806503e-23) /* kg m^2 / K s^2 */ #define GSL_CONST_MKSA_BOHR_MAGNETON (9.27400899e-24) /* A m^2 */ #define GSL_CONST_MKSA_NUCLEAR_MAGNETON (5.05078317e-27) /* A m^2 */ #define GSL_CONST_MKSA_ELECTRON_MAGNETIC_MOMENT (9.28476362e-24) /* A m^2 */ #define GSL_CONST_MKSA_PROTON_MAGNETIC_MOMENT (1.410606633e-26) /* A m^2 */ #define GSL_CONST_MKSA_MOLAR_GAS (8.314472e0) /* kg m^2 / K mol s^2 */ #define GSL_CONST_MKSA_STANDARD_GAS_VOLUME (2.2710981e-2) /* m^3 / mol */ #define GSL_CONST_MKSA_MINUTE (6e1) /* s */ #define GSL_CONST_MKSA_HOUR (3.6e3) /* s */ #define GSL_CONST_MKSA_DAY (8.64e4) /* s */ #define GSL_CONST_MKSA_WEEK (6.048e5) /* s */ #define GSL_CONST_MKSA_INCH (2.54e-2) /* m */ #define GSL_CONST_MKSA_FOOT (3.048e-1) /* m */ #define GSL_CONST_MKSA_YARD (9.144e-1) /* m */ #define GSL_CONST_MKSA_MILE (1.609344e3) /* m */ #define GSL_CONST_MKSA_NAUTICAL_MILE (1.852e3) /* m */ #define GSL_CONST_MKSA_FATHOM (1.8288e0) /* m */ #define GSL_CONST_MKSA_MIL (2.54e-5) /* m */ #define GSL_CONST_MKSA_POINT (3.52777777778e-4) /* m */ #define GSL_CONST_MKSA_TEXPOINT (3.51459803515e-4) /* m */ #define GSL_CONST_MKSA_MICRON (1e-6) /* m */ #define GSL_CONST_MKSA_ANGSTROM (1e-10) /* m */ #define GSL_CONST_MKSA_HECTARE (1e4) /* m^2 */ #define GSL_CONST_MKSA_ACRE (4.04685642241e3) /* m^2 */ #define GSL_CONST_MKSA_BARN (1e-28) /* m^2 */ #define GSL_CONST_MKSA_LITER (1e-3) /* m^3 */ #define GSL_CONST_MKSA_US_GALLON (3.78541178402e-3) /* m^3 */ #define GSL_CONST_MKSA_QUART (9.46352946004e-4) /* m^3 */ #define GSL_CONST_MKSA_PINT (4.73176473002e-4) /* m^3 */ #define GSL_CONST_MKSA_CUP (2.36588236501e-4) /* m^3 */ #define GSL_CONST_MKSA_FLUID_OUNCE (2.95735295626e-5) /* m^3 */ #define GSL_CONST_MKSA_TABLESPOON (1.47867647813e-5) /* m^3 */ #define GSL_CONST_MKSA_TEASPOON (4.92892159375e-6) /* m^3 */ #define GSL_CONST_MKSA_CANADIAN_GALLON (4.54609e-3) /* m^3 */ #define GSL_CONST_MKSA_UK_GALLON (4.546092e-3) /* m^3 */ #define GSL_CONST_MKSA_MILES_PER_HOUR (4.4704e-1) /* m / s */ #define GSL_CONST_MKSA_KILOMETERS_PER_HOUR (2.77777777778e-1) /* m / s */ #define GSL_CONST_MKSA_KNOT (5.14444444444e-1) /* m / s */ #define GSL_CONST_MKSA_POUND_MASS (4.5359237e-1) /* kg */ #define GSL_CONST_MKSA_OUNCE_MASS (2.8349523125e-2) /* kg */ #define GSL_CONST_MKSA_TON (9.0718474e2) /* kg */ #define GSL_CONST_MKSA_METRIC_TON (1e3) /* kg */ #define GSL_CONST_MKSA_UK_TON (1.0160469088e3) /* kg */ #define GSL_CONST_MKSA_TROY_OUNCE (3.1103475e-2) /* kg */ #define GSL_CONST_MKSA_CARAT (2e-4) /* kg */ #define GSL_CONST_MKSA_UNIFIED_ATOMIC_MASS (1.66053873e-27) /* kg */ #define GSL_CONST_MKSA_GRAM_FORCE (9.80665e-3) /* kg m / s^2 */ #define GSL_CONST_MKSA_POUND_FORCE (4.44822161526e0) /* kg m / s^2 */ #define GSL_CONST_MKSA_KILOPOUND_FORCE (4.44822161526e3) /* kg m / s^2 */ #define GSL_CONST_MKSA_POUNDAL (1.38255e-1) /* kg m / s^2 */ #define GSL_CONST_MKSA_CALORIE (4.1868e0) /* kg m^2 / s^2 */ #define GSL_CONST_MKSA_BTU (1.05505585262e3) /* kg m^2 / s^2 */ #define GSL_CONST_MKSA_THERM (1.05506e8) /* kg m^2 / s^2 */ #define GSL_CONST_MKSA_HORSEPOWER (7.457e2) /* kg m^2 / s^3 */ #define GSL_CONST_MKSA_BAR (1e5) /* kg / m s^2 */ #define GSL_CONST_MKSA_STD_ATMOSPHERE (1.01325e5) /* kg / m s^2 */ #define GSL_CONST_MKSA_TORR (1.33322368421e2) /* kg / m s^2 */ #define GSL_CONST_MKSA_METER_OF_MERCURY (1.33322368421e5) /* kg / m s^2 */ #define GSL_CONST_MKSA_INCH_OF_MERCURY (3.38638815789e3) /* kg / m s^2 */ #define GSL_CONST_MKSA_INCH_OF_WATER (2.490889e2) /* kg / m s^2 */ #define GSL_CONST_MKSA_PSI (6.89475729317e3) /* kg / m s^2 */ #define GSL_CONST_MKSA_POISE (1e-1) /* kg m^-1 s^-1 */ #define GSL_CONST_MKSA_STOKES (1e-4) /* m^2 / s */ #define GSL_CONST_MKSA_FARADAY (9.6485341472e4) /* A s / mol */ #define GSL_CONST_MKSA_ELECTRON_CHARGE (1.602176462e-19) /* A s */ #define GSL_CONST_MKSA_GAUSS (1e-4) /* kg / A s^2 */ #define GSL_CONST_MKSA_STILB (1e4) /* cd / m^2 */ #define GSL_CONST_MKSA_LUMEN (1e0) /* cd sr */ #define GSL_CONST_MKSA_LUX (1e0) /* cd sr / m^2 */ #define GSL_CONST_MKSA_PHOT (1e4) /* cd sr / m^2 */ #define GSL_CONST_MKSA_FOOTCANDLE (1.076e1) /* cd sr / m^2 */ #define GSL_CONST_MKSA_LAMBERT (1e4) /* cd sr / m^2 */ #define GSL_CONST_MKSA_FOOTLAMBERT (1.07639104e1) /* cd sr / m^2 */ #define GSL_CONST_MKSA_CURIE (3.7e10) /* 1 / s */ #define GSL_CONST_MKSA_ROENTGEN (2.58e-4) /* A s / kg */ #define GSL_CONST_MKSA_RAD (1e-2) /* m^2 / s^2 */ #define GSL_CONST_MKSA_SOLAR_MASS (1.98892e30) /* kg */ #define GSL_CONST_MKSA_BOHR_RADIUS (5.291772083e-11) /* m */ #define GSL_CONST_MKSA_NEWTON (1e0) /* kg m / s^2 */ #define GSL_CONST_MKSA_DYNE (1e-5) /* kg m / s^2 */ #define GSL_CONST_MKSA_JOULE (1e0) /* kg m^2 / s^2 */ #define GSL_CONST_MKSA_ERG (1e-7) /* kg m^2 / s^2 */ #define GSL_CONST_MKSA_STEFAN_BOLTZMANN_CONSTANT (5.67039934436e-8) /* kg / K^4 s^3 */ #define GSL_CONST_MKSA_THOMSON_CROSS_SECTION (6.65245853542e-29) /* m^2 */ #define GSL_CONST_MKSA_VACUUM_PERMITTIVITY (8.854187817e-12) /* A^2 s^4 / kg m^3 */ #define GSL_CONST_MKSA_VACUUM_PERMEABILITY (1.25663706144e-6) /* kg m / A^2 s^2 */ #define GSL_CONST_MKSA_DEBYE (3.33564095198e-30) /* A s^2 / m^2 */ #endif /* __GSL_CONST_MKSA__ */ sources_5316/external/gsl/gsl_cdf__gumbel2inv.c0000664000176700017670000000253211723710247020400 0ustar paulpaul/* cdf/gumbel2inv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_gumbel2_Pinv (const double P, const double a, const double b) { double x; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return 0.0; } x = pow(b / (-log(P)), 1/a); return x; } double gsl_cdf_gumbel2_Qinv (const double Q, const double a, const double b) { double x; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return 0.0; } x = pow(b / (-log1p(-Q)), 1/a); return x; } sources_5316/external/gsl/gsl_ode-initval__control.c0000664000176700017670000000426111723710247021466 0ustar paulpaul/* ode-initval/control.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_odeiv.h" gsl_odeiv_control * gsl_odeiv_control_alloc(const gsl_odeiv_control_type * T) { gsl_odeiv_control * c = (gsl_odeiv_control *) malloc(sizeof(gsl_odeiv_control)); if(c == 0) { GSL_ERROR_NULL ("failed to allocate space for control struct", GSL_ENOMEM); }; c->type = T; c->state = c->type->alloc(); if (c->state == 0) { free (c); /* exception in constructor, avoid memory leak */ GSL_ERROR_NULL ("failed to allocate space for control state", GSL_ENOMEM); }; return c; } int gsl_odeiv_control_init(gsl_odeiv_control * c, double eps_abs, double eps_rel, double a_y, double a_dydt) { return c->type->init (c->state, eps_abs, eps_rel, a_y, a_dydt); } void gsl_odeiv_control_free(gsl_odeiv_control * c) { c->type->free(c->state); free(c); } const char * gsl_odeiv_control_name(const gsl_odeiv_control * c) { return c->type->name; } int gsl_odeiv_control_hadjust (gsl_odeiv_control * c, gsl_odeiv_step * s, const double y[], const double yerr[], const double dydt[], double * h) { return c->type->hadjust(c->state, s->dimension, s->type->order(s->state), y, yerr, dydt, h); } sources_5316/external/gsl/gsl_matrix__oper_source.c0000664000176700017670000001011711723710247021421 0ustar paulpaul/* matrix/oper_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION(gsl_matrix, add) (TYPE(gsl_matrix) * a, const TYPE(gsl_matrix) * b) { const size_t M = a->size1; const size_t N = a->size2; if (b->size1 != M || b->size2 != N) { GSL_ERROR ("matrices must have same dimensions", GSL_EBADLEN); } else { const size_t tda_a = a->tda; const size_t tda_b = b->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { a->data[i * tda_a + j] += b->data[i * tda_b + j]; } } return GSL_SUCCESS; } } int FUNCTION(gsl_matrix, sub) (TYPE(gsl_matrix) * a, const TYPE(gsl_matrix) * b) { const size_t M = a->size1; const size_t N = a->size2; if (b->size1 != M || b->size2 != N) { GSL_ERROR ("matrices must have same dimensions", GSL_EBADLEN); } else { const size_t tda_a = a->tda; const size_t tda_b = b->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { a->data[i * tda_a + j] -= b->data[i * tda_b + j]; } } return GSL_SUCCESS; } } int FUNCTION(gsl_matrix, mul_elements) (TYPE(gsl_matrix) * a, const TYPE(gsl_matrix) * b) { const size_t M = a->size1; const size_t N = a->size2; if (b->size1 != M || b->size2 != N) { GSL_ERROR ("matrices must have same dimensions", GSL_EBADLEN); } else { const size_t tda_a = a->tda; const size_t tda_b = b->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { a->data[i * tda_a + j] *= b->data[i * tda_b + j]; } } return GSL_SUCCESS; } } int FUNCTION(gsl_matrix, div_elements) (TYPE(gsl_matrix) * a, const TYPE(gsl_matrix) * b) { const size_t M = a->size1; const size_t N = a->size2; if (b->size1 != M || b->size2 != N) { GSL_ERROR ("matrices must have same dimensions", GSL_EBADLEN); } else { const size_t tda_a = a->tda; const size_t tda_b = b->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { a->data[i * tda_a + j] /= b->data[i * tda_b + j]; } } return GSL_SUCCESS; } } int FUNCTION(gsl_matrix, scale) (TYPE(gsl_matrix) * a, const double x) { const size_t M = a->size1; const size_t N = a->size2; const size_t tda = a->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { a->data[i * tda + j] *= x; } } return GSL_SUCCESS; } int FUNCTION(gsl_matrix, add_constant) (TYPE(gsl_matrix) * a, const double x) { const size_t M = a->size1; const size_t N = a->size2; const size_t tda = a->tda; size_t i, j; for (i = 0; i < M; i++) { for (j = 0; j < N; j++) { a->data[i * tda + j] += x; } } return GSL_SUCCESS; } int FUNCTION(gsl_matrix, add_diagonal) (TYPE(gsl_matrix) * a, const double x) { const size_t M = a->size1; const size_t N = a->size2; const size_t tda = a->tda; const size_t loop_lim = ( M < N ? M : N ); size_t i; for (i = 0; i < loop_lim; i++) { a->data[i * tda + i] += x; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_eigen__nonsymmv.c0000664000176700017670000007521411723710247020556 0ustar paulpaul/* eigen/nonsymmv.c * * Copyright (C) 2006 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_complex.h" #include "gsl_complex_math.h" #include "gsl_eigen.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_blas.h" #include "gsl_cblas.h" #include "gsl_vector.h" #include "gsl_vector_complex.h" #include "gsl_matrix.h" /* * This module computes the eigenvalues and eigenvectors of a real * nonsymmetric matrix. * * This file contains routines based on original code from LAPACK * which is distributed under the modified BSD license. The LAPACK * routines used are DTREVC and DLALN2. */ #define GSL_NONSYMMV_SMLNUM (2.0 * GSL_DBL_MIN) #define GSL_NONSYMMV_BIGNUM ((1.0 - GSL_DBL_EPSILON) / GSL_NONSYMMV_SMLNUM) static void nonsymmv_get_right_eigenvectors(gsl_matrix *T, gsl_matrix *Z, gsl_vector_complex *eval, gsl_matrix_complex *evec, gsl_eigen_nonsymmv_workspace *w); static void nonsymmv_normalize_eigenvectors(gsl_vector_complex *eval, gsl_matrix_complex *evec); /* gsl_eigen_nonsymmv_alloc() Allocate a workspace for solving the nonsymmetric eigenvalue problem. The size of this workspace is O(5n). Inputs: n - size of matrices Return: pointer to workspace */ gsl_eigen_nonsymmv_workspace * gsl_eigen_nonsymmv_alloc(const size_t n) { gsl_eigen_nonsymmv_workspace *w; if (n == 0) { GSL_ERROR_NULL ("matrix dimension must be positive integer", GSL_EINVAL); } w = (gsl_eigen_nonsymmv_workspace *) calloc (1, sizeof (gsl_eigen_nonsymmv_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } w->size = n; w->Z = NULL; w->nonsymm_workspace_p = gsl_eigen_nonsymm_alloc(n); if (w->nonsymm_workspace_p == 0) { gsl_eigen_nonsymmv_free(w); GSL_ERROR_NULL ("failed to allocate space for nonsymm workspace", GSL_ENOMEM); } /* * set parameters to compute the full Schur form T and balance * the matrices */ gsl_eigen_nonsymm_params(1, 1, w->nonsymm_workspace_p); w->work = gsl_vector_alloc(n); w->work2 = gsl_vector_alloc(n); w->work3 = gsl_vector_alloc(n); if (w->work == 0 || w->work2 == 0 || w->work3 == 0) { gsl_eigen_nonsymmv_free(w); GSL_ERROR_NULL ("failed to allocate space for nonsymmv additional workspace", GSL_ENOMEM); } return (w); } /* gsl_eigen_nonsymmv_alloc() */ /* gsl_eigen_nonsymmv_free() Free workspace w */ void gsl_eigen_nonsymmv_free (gsl_eigen_nonsymmv_workspace * w) { if (w->nonsymm_workspace_p) gsl_eigen_nonsymm_free(w->nonsymm_workspace_p); if (w->work) gsl_vector_free(w->work); if (w->work2) gsl_vector_free(w->work2); if (w->work3) gsl_vector_free(w->work3); free(w); } /* gsl_eigen_nonsymmv_free() */ /* gsl_eigen_nonsymmv() Solve the nonsymmetric eigensystem problem A x = \lambda x for the eigenvalues \lambda and right eigenvectors x Inputs: A - general real matrix eval - where to store eigenvalues evec - where to store eigenvectors w - workspace Return: success or error */ int gsl_eigen_nonsymmv (gsl_matrix * A, gsl_vector_complex * eval, gsl_matrix_complex * evec, gsl_eigen_nonsymmv_workspace * w) { const size_t N = A->size1; /* check matrix and vector sizes */ if (N != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if (eval->size != N) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (evec->size1 != evec->size2) { GSL_ERROR ("eigenvector matrix must be square", GSL_ENOTSQR); } else if (evec->size1 != N) { GSL_ERROR ("eigenvector matrix has wrong size", GSL_EBADLEN); } else { int s; gsl_matrix Z; /* * We need a place to store the Schur vectors, so we will * treat evec as a real matrix and store them in the left * half - the factor of 2 in the tda corresponds to the * complex multiplicity */ Z.size1 = N; Z.size2 = N; Z.tda = 2 * N; Z.data = evec->data; Z.block = 0; Z.owner = 0; /* compute eigenvalues, Schur form, and Schur vectors */ s = gsl_eigen_nonsymm_Z(A, eval, &Z, w->nonsymm_workspace_p); if (w->Z) { /* * save the Schur vectors in user supplied matrix, since * they will be destroyed when computing eigenvectors */ gsl_matrix_memcpy(w->Z, &Z); } /* only compute eigenvectors if we found all eigenvalues */ if (s == GSL_SUCCESS) { /* compute eigenvectors */ nonsymmv_get_right_eigenvectors(A, &Z, eval, evec, w); /* normalize so that Euclidean norm is 1 */ nonsymmv_normalize_eigenvectors(eval, evec); } return s; } } /* gsl_eigen_nonsymmv() */ /* gsl_eigen_nonsymmv_Z() Compute eigenvalues and eigenvectors of a real nonsymmetric matrix and also save the Schur vectors. See comments in gsl_eigen_nonsymm_Z for more information. Inputs: A - real nonsymmetric matrix eval - where to store eigenvalues evec - where to store eigenvectors Z - where to store Schur vectors w - nonsymmv workspace Return: success or error */ int gsl_eigen_nonsymmv_Z (gsl_matrix * A, gsl_vector_complex * eval, gsl_matrix_complex * evec, gsl_matrix * Z, gsl_eigen_nonsymmv_workspace * w) { /* check matrix and vector sizes */ if (A->size1 != A->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues/eigenvectors", GSL_ENOTSQR); } else if (eval->size != A->size1) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else if (evec->size1 != evec->size2) { GSL_ERROR ("eigenvector matrix must be square", GSL_ENOTSQR); } else if (evec->size1 != A->size1) { GSL_ERROR ("eigenvector matrix has wrong size", GSL_EBADLEN); } else if ((Z->size1 != Z->size2) || (Z->size1 != A->size1)) { GSL_ERROR ("Z matrix has wrong dimensions", GSL_EBADLEN); } else { int s; w->Z = Z; s = gsl_eigen_nonsymmv(A, eval, evec, w); w->Z = NULL; return s; } } /* gsl_eigen_nonsymmv_Z() */ /******************************************** * INTERNAL ROUTINES * ********************************************/ /* nonsymmv_get_right_eigenvectors() Compute the right eigenvectors of the Schur form T and then backtransform them using the Schur vectors to get right eigenvectors of the original matrix. Inputs: T - Schur form Z - Schur vectors eval - where to store eigenvalues (to ensure that the correct eigenvalue is stored in the same position as the eigenvectors) evec - where to store eigenvectors w - nonsymmv workspace Return: none Notes: 1) based on LAPACK routine DTREVC - the algorithm used is backsubstitution on the upper quasi triangular system T followed by backtransformation by Z to get vectors of the original matrix. 2) The Schur vectors in Z are destroyed and replaced with eigenvectors stored with the same storage scheme as DTREVC. The eigenvectors are also stored in 'evec' 3) The matrix T is unchanged on output 4) Each eigenvector is normalized so that the element of largest magnitude has magnitude 1; here the magnitude of a complex number (x,y) is taken to be |x| + |y| */ static void nonsymmv_get_right_eigenvectors(gsl_matrix *T, gsl_matrix *Z, gsl_vector_complex *eval, gsl_matrix_complex *evec, gsl_eigen_nonsymmv_workspace *w) { const size_t N = T->size1; const double smlnum = GSL_DBL_MIN * N / GSL_DBL_EPSILON; const double bignum = (1.0 - GSL_DBL_EPSILON) / smlnum; int i; /* looping */ size_t iu, /* looping */ ju, ii; gsl_complex lambda; /* current eigenvalue */ double lambda_re, /* Re(lambda) */ lambda_im; /* Im(lambda) */ gsl_matrix_view Tv, /* temporary views */ Zv; gsl_vector_view y, /* temporary views */ y2, ev, ev2; double dat[4], /* scratch arrays */ dat_X[4]; double scale; /* scale factor */ double xnorm; /* |X| */ gsl_vector_complex_view ecol, /* column of evec */ ecol2; int complex_pair; /* complex eigenvalue pair? */ double smin; /* * Compute 1-norm of each column of upper triangular part of T * to control overflow in triangular solver */ gsl_vector_set(w->work3, 0, 0.0); for (ju = 1; ju < N; ++ju) { gsl_vector_set(w->work3, ju, 0.0); for (iu = 0; iu < ju; ++iu) { gsl_vector_set(w->work3, ju, gsl_vector_get(w->work3, ju) + fabs(gsl_matrix_get(T, iu, ju))); } } for (i = (int) N - 1; i >= 0; --i) { iu = (size_t) i; /* get current eigenvalue and store it in lambda */ lambda_re = gsl_matrix_get(T, iu, iu); if (iu != 0 && gsl_matrix_get(T, iu, iu - 1) != 0.0) { lambda_im = sqrt(fabs(gsl_matrix_get(T, iu, iu - 1))) * sqrt(fabs(gsl_matrix_get(T, iu - 1, iu))); } else { lambda_im = 0.0; } GSL_SET_COMPLEX(&lambda, lambda_re, lambda_im); smin = GSL_MAX(GSL_DBL_EPSILON * (fabs(lambda_re) + fabs(lambda_im)), smlnum); smin = GSL_MAX(smin, GSL_NONSYMMV_SMLNUM); if (lambda_im == 0.0) { int k, l; gsl_vector_view bv, xv; /* real eigenvector */ /* * The ordering of eigenvalues in 'eval' is arbitrary and * does not necessarily follow the Schur form T, so store * lambda in the right slot in eval to ensure it corresponds * to the eigenvector we are about to compute */ gsl_vector_complex_set(eval, iu, lambda); /* * We need to solve the system: * * (T(1:iu-1, 1:iu-1) - lambda*I)*X = -T(1:iu-1,iu) */ /* construct right hand side */ for (k = 0; k < i; ++k) { gsl_vector_set(w->work, (size_t) k, -gsl_matrix_get(T, (size_t) k, iu)); } gsl_vector_set(w->work, iu, 1.0); for (l = i - 1; l >= 0; --l) { size_t lu = (size_t) l; if (lu == 0) complex_pair = 0; else complex_pair = gsl_matrix_get(T, lu, lu - 1) != 0.0; if (!complex_pair) { double x; /* * 1-by-1 diagonal block - solve the system: * * (T_{ll} - lambda)*x = -T_{l(iu)} */ Tv = gsl_matrix_submatrix(T, lu, lu, 1, 1); bv = gsl_vector_view_array(dat, 1); gsl_vector_set(&bv.vector, 0, gsl_vector_get(w->work, lu)); xv = gsl_vector_view_array(dat_X, 1); gsl_schur_solve_equation(1.0, &Tv.matrix, lambda_re, 1.0, 1.0, &bv.vector, &xv.vector, &scale, &xnorm, smin); /* scale x to avoid overflow */ x = gsl_vector_get(&xv.vector, 0); if (xnorm > 1.0) { if (gsl_vector_get(w->work3, lu) > bignum / xnorm) { x /= xnorm; scale /= xnorm; } } if (scale != 1.0) { gsl_vector_view wv; wv = gsl_vector_subvector(w->work, 0, iu + 1); gsl_blas_dscal(scale, &wv.vector); } gsl_vector_set(w->work, lu, x); if (lu > 0) { gsl_vector_view v1, v2; /* update right hand side */ v1 = gsl_matrix_subcolumn(T, lu, 0, lu); v2 = gsl_vector_subvector(w->work, 0, lu); gsl_blas_daxpy(-x, &v1.vector, &v2.vector); } /* if (l > 0) */ } /* if (!complex_pair) */ else { double x11, x21; /* * 2-by-2 diagonal block */ Tv = gsl_matrix_submatrix(T, lu - 1, lu - 1, 2, 2); bv = gsl_vector_view_array(dat, 2); gsl_vector_set(&bv.vector, 0, gsl_vector_get(w->work, lu - 1)); gsl_vector_set(&bv.vector, 1, gsl_vector_get(w->work, lu)); xv = gsl_vector_view_array(dat_X, 2); gsl_schur_solve_equation(1.0, &Tv.matrix, lambda_re, 1.0, 1.0, &bv.vector, &xv.vector, &scale, &xnorm, smin); /* scale X(1,1) and X(2,1) to avoid overflow */ x11 = gsl_vector_get(&xv.vector, 0); x21 = gsl_vector_get(&xv.vector, 1); if (xnorm > 1.0) { double beta; beta = GSL_MAX(gsl_vector_get(w->work3, lu - 1), gsl_vector_get(w->work3, lu)); if (beta > bignum / xnorm) { x11 /= xnorm; x21 /= xnorm; scale /= xnorm; } } /* scale if necessary */ if (scale != 1.0) { gsl_vector_view wv; wv = gsl_vector_subvector(w->work, 0, iu + 1); gsl_blas_dscal(scale, &wv.vector); } gsl_vector_set(w->work, lu - 1, x11); gsl_vector_set(w->work, lu, x21); /* update right hand side */ if (lu > 1) { gsl_vector_view v1, v2; v1 = gsl_matrix_subcolumn(T, lu - 1, 0, lu - 1); v2 = gsl_vector_subvector(w->work, 0, lu - 1); gsl_blas_daxpy(-x11, &v1.vector, &v2.vector); v1 = gsl_matrix_subcolumn(T, lu, 0, lu - 1); gsl_blas_daxpy(-x21, &v1.vector, &v2.vector); } --l; } /* if (complex_pair) */ } /* for (l = i - 1; l >= 0; --l) */ /* * At this point, w->work is an eigenvector of the * Schur form T. To get an eigenvector of the original * matrix, we multiply on the left by Z, the matrix of * Schur vectors */ ecol = gsl_matrix_complex_column(evec, iu); y = gsl_matrix_column(Z, iu); if (iu > 0) { gsl_vector_view x; Zv = gsl_matrix_submatrix(Z, 0, 0, N, iu); x = gsl_vector_subvector(w->work, 0, iu); /* compute Z * w->work and store it in Z(:,iu) */ gsl_blas_dgemv(CblasNoTrans, 1.0, &Zv.matrix, &x.vector, gsl_vector_get(w->work, iu), &y.vector); } /* if (iu > 0) */ /* store eigenvector into evec */ ev = gsl_vector_complex_real(&ecol.vector); ev2 = gsl_vector_complex_imag(&ecol.vector); scale = 0.0; for (ii = 0; ii < N; ++ii) { double a = gsl_vector_get(&y.vector, ii); /* store real part of eigenvector */ gsl_vector_set(&ev.vector, ii, a); /* set imaginary part to 0 */ gsl_vector_set(&ev2.vector, ii, 0.0); if (fabs(a) > scale) scale = fabs(a); } if (scale != 0.0) scale = 1.0 / scale; /* scale by magnitude of largest element */ gsl_blas_dscal(scale, &ev.vector); } /* if (GSL_IMAG(lambda) == 0.0) */ else { gsl_vector_complex_view bv, xv; size_t k; int l; gsl_complex lambda2; /* complex eigenvector */ /* * Store the complex conjugate eigenvalues in the right * slots in eval */ GSL_SET_REAL(&lambda2, GSL_REAL(lambda)); GSL_SET_IMAG(&lambda2, -GSL_IMAG(lambda)); gsl_vector_complex_set(eval, iu - 1, lambda); gsl_vector_complex_set(eval, iu, lambda2); /* * First solve: * * [ T(i:i+1,i:i+1) - lambda*I ] * X = 0 */ if (fabs(gsl_matrix_get(T, iu - 1, iu)) >= fabs(gsl_matrix_get(T, iu, iu - 1))) { gsl_vector_set(w->work, iu - 1, 1.0); gsl_vector_set(w->work2, iu, lambda_im / gsl_matrix_get(T, iu - 1, iu)); } else { gsl_vector_set(w->work, iu - 1, -lambda_im / gsl_matrix_get(T, iu, iu - 1)); gsl_vector_set(w->work2, iu, 1.0); } gsl_vector_set(w->work, iu, 0.0); gsl_vector_set(w->work2, iu - 1, 0.0); /* construct right hand side */ for (k = 0; k < iu - 1; ++k) { gsl_vector_set(w->work, k, -gsl_vector_get(w->work, iu - 1) * gsl_matrix_get(T, k, iu - 1)); gsl_vector_set(w->work2, k, -gsl_vector_get(w->work2, iu) * gsl_matrix_get(T, k, iu)); } /* * We must solve the upper quasi-triangular system: * * [ T(1:i-2,1:i-2) - lambda*I ] * X = s*(work + i*work2) */ for (l = i - 2; l >= 0; --l) { size_t lu = (size_t) l; if (lu == 0) complex_pair = 0; else complex_pair = gsl_matrix_get(T, lu, lu - 1) != 0.0; if (!complex_pair) { gsl_complex bval; gsl_complex x; /* * 1-by-1 diagonal block - solve the system: * * (T_{ll} - lambda)*x = work + i*work2 */ Tv = gsl_matrix_submatrix(T, lu, lu, 1, 1); bv = gsl_vector_complex_view_array(dat, 1); xv = gsl_vector_complex_view_array(dat_X, 1); GSL_SET_COMPLEX(&bval, gsl_vector_get(w->work, lu), gsl_vector_get(w->work2, lu)); gsl_vector_complex_set(&bv.vector, 0, bval); gsl_schur_solve_equation_z(1.0, &Tv.matrix, &lambda, 1.0, 1.0, &bv.vector, &xv.vector, &scale, &xnorm, smin); if (xnorm > 1.0) { if (gsl_vector_get(w->work3, lu) > bignum / xnorm) { gsl_blas_zdscal(1.0/xnorm, &xv.vector); scale /= xnorm; } } /* scale if necessary */ if (scale != 1.0) { gsl_vector_view wv; wv = gsl_vector_subvector(w->work, 0, iu + 1); gsl_blas_dscal(scale, &wv.vector); wv = gsl_vector_subvector(w->work2, 0, iu + 1); gsl_blas_dscal(scale, &wv.vector); } x = gsl_vector_complex_get(&xv.vector, 0); gsl_vector_set(w->work, lu, GSL_REAL(x)); gsl_vector_set(w->work2, lu, GSL_IMAG(x)); /* update the right hand side */ if (lu > 0) { gsl_vector_view v1, v2; v1 = gsl_matrix_subcolumn(T, lu, 0, lu); v2 = gsl_vector_subvector(w->work, 0, lu); gsl_blas_daxpy(-GSL_REAL(x), &v1.vector, &v2.vector); v2 = gsl_vector_subvector(w->work2, 0, lu); gsl_blas_daxpy(-GSL_IMAG(x), &v1.vector, &v2.vector); } /* if (lu > 0) */ } /* if (!complex_pair) */ else { gsl_complex b1, b2, x1, x2; /* * 2-by-2 diagonal block - solve the system */ Tv = gsl_matrix_submatrix(T, lu - 1, lu - 1, 2, 2); bv = gsl_vector_complex_view_array(dat, 2); xv = gsl_vector_complex_view_array(dat_X, 2); GSL_SET_COMPLEX(&b1, gsl_vector_get(w->work, lu - 1), gsl_vector_get(w->work2, lu - 1)); GSL_SET_COMPLEX(&b2, gsl_vector_get(w->work, lu), gsl_vector_get(w->work2, lu)); gsl_vector_complex_set(&bv.vector, 0, b1); gsl_vector_complex_set(&bv.vector, 1, b2); gsl_schur_solve_equation_z(1.0, &Tv.matrix, &lambda, 1.0, 1.0, &bv.vector, &xv.vector, &scale, &xnorm, smin); x1 = gsl_vector_complex_get(&xv.vector, 0); x2 = gsl_vector_complex_get(&xv.vector, 1); if (xnorm > 1.0) { double beta; beta = GSL_MAX(gsl_vector_get(w->work3, lu - 1), gsl_vector_get(w->work3, lu)); if (beta > bignum / xnorm) { gsl_blas_zdscal(1.0/xnorm, &xv.vector); scale /= xnorm; } } /* scale if necessary */ if (scale != 1.0) { gsl_vector_view wv; wv = gsl_vector_subvector(w->work, 0, iu + 1); gsl_blas_dscal(scale, &wv.vector); wv = gsl_vector_subvector(w->work2, 0, iu + 1); gsl_blas_dscal(scale, &wv.vector); } gsl_vector_set(w->work, lu - 1, GSL_REAL(x1)); gsl_vector_set(w->work, lu, GSL_REAL(x2)); gsl_vector_set(w->work2, lu - 1, GSL_IMAG(x1)); gsl_vector_set(w->work2, lu, GSL_IMAG(x2)); /* update right hand side */ if (lu > 1) { gsl_vector_view v1, v2, v3, v4; v1 = gsl_matrix_subcolumn(T, lu - 1, 0, lu - 1); v4 = gsl_matrix_subcolumn(T, lu, 0, lu - 1); v2 = gsl_vector_subvector(w->work, 0, lu - 1); v3 = gsl_vector_subvector(w->work2, 0, lu - 1); gsl_blas_daxpy(-GSL_REAL(x1), &v1.vector, &v2.vector); gsl_blas_daxpy(-GSL_REAL(x2), &v4.vector, &v2.vector); gsl_blas_daxpy(-GSL_IMAG(x1), &v1.vector, &v3.vector); gsl_blas_daxpy(-GSL_IMAG(x2), &v4.vector, &v3.vector); } /* if (lu > 1) */ --l; } /* if (complex_pair) */ } /* for (l = i - 2; l >= 0; --l) */ /* * At this point, work + i*work2 is an eigenvector * of T - backtransform to get an eigenvector of the * original matrix */ y = gsl_matrix_column(Z, iu - 1); y2 = gsl_matrix_column(Z, iu); if (iu > 1) { gsl_vector_view x; /* compute real part of eigenvectors */ Zv = gsl_matrix_submatrix(Z, 0, 0, N, iu - 1); x = gsl_vector_subvector(w->work, 0, iu - 1); gsl_blas_dgemv(CblasNoTrans, 1.0, &Zv.matrix, &x.vector, gsl_vector_get(w->work, iu - 1), &y.vector); /* now compute the imaginary part */ x = gsl_vector_subvector(w->work2, 0, iu - 1); gsl_blas_dgemv(CblasNoTrans, 1.0, &Zv.matrix, &x.vector, gsl_vector_get(w->work2, iu), &y2.vector); } else { gsl_blas_dscal(gsl_vector_get(w->work, iu - 1), &y.vector); gsl_blas_dscal(gsl_vector_get(w->work2, iu), &y2.vector); } /* * Now store the eigenvectors into evec - the real parts * are Z(:,iu - 1) and the imaginary parts are * +/- Z(:,iu) */ /* get views of the two eigenvector slots */ ecol = gsl_matrix_complex_column(evec, iu - 1); ecol2 = gsl_matrix_complex_column(evec, iu); /* * save imaginary part first as it may get overwritten * when copying the real part due to our storage scheme * in Z/evec */ ev = gsl_vector_complex_imag(&ecol.vector); ev2 = gsl_vector_complex_imag(&ecol2.vector); scale = 0.0; for (ii = 0; ii < N; ++ii) { double a = gsl_vector_get(&y2.vector, ii); scale = GSL_MAX(scale, fabs(a) + fabs(gsl_vector_get(&y.vector, ii))); gsl_vector_set(&ev.vector, ii, a); gsl_vector_set(&ev2.vector, ii, -a); } /* now save the real part */ ev = gsl_vector_complex_real(&ecol.vector); ev2 = gsl_vector_complex_real(&ecol2.vector); for (ii = 0; ii < N; ++ii) { double a = gsl_vector_get(&y.vector, ii); gsl_vector_set(&ev.vector, ii, a); gsl_vector_set(&ev2.vector, ii, a); } if (scale != 0.0) scale = 1.0 / scale; /* scale by largest element magnitude */ gsl_blas_zdscal(scale, &ecol.vector); gsl_blas_zdscal(scale, &ecol2.vector); /* * decrement i since we took care of two eigenvalues at * the same time */ --i; } /* if (GSL_IMAG(lambda) != 0.0) */ } /* for (i = (int) N - 1; i >= 0; --i) */ } /* nonsymmv_get_right_eigenvectors() */ /* nonsymmv_normalize_eigenvectors() Normalize eigenvectors so that their Euclidean norm is 1 Inputs: eval - eigenvalues evec - eigenvectors */ static void nonsymmv_normalize_eigenvectors(gsl_vector_complex *eval, gsl_matrix_complex *evec) { const size_t N = evec->size1; size_t i; /* looping */ gsl_complex ei; gsl_vector_complex_view vi; gsl_vector_view re, im; double scale; /* scaling factor */ for (i = 0; i < N; ++i) { ei = gsl_vector_complex_get(eval, i); vi = gsl_matrix_complex_column(evec, i); re = gsl_vector_complex_real(&vi.vector); if (GSL_IMAG(ei) == 0.0) { scale = 1.0 / gsl_blas_dnrm2(&re.vector); gsl_blas_dscal(scale, &re.vector); } else if (GSL_IMAG(ei) > 0.0) { im = gsl_vector_complex_imag(&vi.vector); scale = 1.0 / gsl_hypot(gsl_blas_dnrm2(&re.vector), gsl_blas_dnrm2(&im.vector)); gsl_blas_zdscal(scale, &vi.vector); vi = gsl_matrix_complex_column(evec, i + 1); gsl_blas_zdscal(scale, &vi.vector); } } } /* nonsymmv_normalize_eigenvectors() */ sources_5316/external/gsl/gsl_specfunc__trig.c0000664000176700017670000004645611723710247020362 0ustar paulpaul/* specfunc/trig.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_log.h" #include "gsl_sf_trig.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /* sinh(x) series * double-precision for |x| < 1.0 */ inline static int sinh_series(const double x, double * result) { const double y = x*x; const double c0 = 1.0/6.0; const double c1 = 1.0/120.0; const double c2 = 1.0/5040.0; const double c3 = 1.0/362880.0; const double c4 = 1.0/39916800.0; const double c5 = 1.0/6227020800.0; const double c6 = 1.0/1307674368000.0; const double c7 = 1.0/355687428096000.0; *result = x*(1.0 + y*(c0+y*(c1+y*(c2+y*(c3+y*(c4+y*(c5+y*(c6+y*c7)))))))); return GSL_SUCCESS; } /* cosh(x)-1 series * double-precision for |x| < 1.0 */ inline static int cosh_m1_series(const double x, double * result) { const double y = x*x; const double c0 = 0.5; const double c1 = 1.0/24.0; const double c2 = 1.0/720.0; const double c3 = 1.0/40320.0; const double c4 = 1.0/3628800.0; const double c5 = 1.0/479001600.0; const double c6 = 1.0/87178291200.0; const double c7 = 1.0/20922789888000.0; const double c8 = 1.0/6402373705728000.0; *result = y*(c0+y*(c1+y*(c2+y*(c3+y*(c4+y*(c5+y*(c6+y*(c7+y*c8)))))))); return GSL_SUCCESS; } /* Chebyshev expansion for f(t) = sinc((t+1)/2), -1 < t < 1 */ static double sinc_data[17] = { 1.133648177811747875422, -0.532677564732557348781, -0.068293048346633177859, 0.033403684226353715020, 0.001485679893925747818, -0.000734421305768455295, -0.000016837282388837229, 0.000008359950146618018, 0.000000117382095601192, -0.000000058413665922724, -0.000000000554763755743, 0.000000000276434190426, 0.000000000001895374892, -0.000000000000945237101, -0.000000000000004900690, 0.000000000000002445383, 0.000000000000000009925 }; static cheb_series sinc_cs = { sinc_data, 16, -1, 1, 10 }; /* Chebyshev expansion for f(t) = g((t+1)Pi/8), -1val = x * (1.0 - x2/6.0); result->err = fabs(x*x2*x2 / 100.0); return GSL_SUCCESS; } else { double sgn_result = sgn_x; double y = floor(abs_x/(0.25*M_PI)); int octant = y - ldexp(floor(ldexp(y,-3)),3); int stat_cs; double z; if(GSL_IS_ODD(octant)) { octant += 1; octant &= 07; y += 1.0; } if(octant > 3) { octant -= 4; sgn_result = -sgn_result; } z = ((abs_x - y * P1) - y * P2) - y * P3; if(octant == 0) { gsl_sf_result sin_cs_result; const double t = 8.0*fabs(z)/M_PI - 1.0; stat_cs = cheb_eval_e(&sin_cs, t, &sin_cs_result); result->val = z * (1.0 + z*z * sin_cs_result.val); } else { /* octant == 2 */ gsl_sf_result cos_cs_result; const double t = 8.0*fabs(z)/M_PI - 1.0; stat_cs = cheb_eval_e(&cos_cs, t, &cos_cs_result); result->val = 1.0 - 0.5*z*z * (1.0 - z*z * cos_cs_result.val); } result->val *= sgn_result; if(abs_x > 1.0/GSL_DBL_EPSILON) { result->err = fabs(result->val); } else if(abs_x > 100.0/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * abs_x * GSL_DBL_EPSILON * fabs(result->val); } else if(abs_x > 0.1/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * GSL_SQRT_DBL_EPSILON * fabs(result->val); } else { result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return stat_cs; } } } int gsl_sf_cos_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { const double P1 = 7.85398125648498535156e-1; const double P2 = 3.77489470793079817668e-8; const double P3 = 2.69515142907905952645e-15; const double abs_x = fabs(x); if(abs_x < GSL_ROOT4_DBL_EPSILON) { const double x2 = x*x; result->val = 1.0 - 0.5*x2; result->err = fabs(x2*x2/12.0); return GSL_SUCCESS; } else { double sgn_result = 1.0; double y = floor(abs_x/(0.25*M_PI)); int octant = y - ldexp(floor(ldexp(y,-3)),3); int stat_cs; double z; if(GSL_IS_ODD(octant)) { octant += 1; octant &= 07; y += 1.0; } if(octant > 3) { octant -= 4; sgn_result = -sgn_result; } if(octant > 1) { sgn_result = -sgn_result; } z = ((abs_x - y * P1) - y * P2) - y * P3; if(octant == 0) { gsl_sf_result cos_cs_result; const double t = 8.0*fabs(z)/M_PI - 1.0; stat_cs = cheb_eval_e(&cos_cs, t, &cos_cs_result); result->val = 1.0 - 0.5*z*z * (1.0 - z*z * cos_cs_result.val); } else { /* octant == 2 */ gsl_sf_result sin_cs_result; const double t = 8.0*fabs(z)/M_PI - 1.0; stat_cs = cheb_eval_e(&sin_cs, t, &sin_cs_result); result->val = z * (1.0 + z*z * sin_cs_result.val); } result->val *= sgn_result; if(abs_x > 1.0/GSL_DBL_EPSILON) { result->err = fabs(result->val); } else if(abs_x > 100.0/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * abs_x * GSL_DBL_EPSILON * fabs(result->val); } else if(abs_x > 0.1/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * GSL_SQRT_DBL_EPSILON * fabs(result->val); } else { result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return stat_cs; } } } int gsl_sf_hypot_e(const double x, const double y, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0 && y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { const double a = fabs(x); const double b = fabs(y); const double min = GSL_MIN_DBL(a,b); const double max = GSL_MAX_DBL(a,b); const double rat = min/max; const double root_term = sqrt(1.0 + rat*rat); if(max < GSL_DBL_MAX/root_term) { result->val = max * root_term; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } } int gsl_sf_complex_sin_e(const double zr, const double zi, gsl_sf_result * szr, gsl_sf_result * szi) { /* CHECK_POINTER(szr) */ /* CHECK_POINTER(szi) */ if(fabs(zi) < 1.0) { double ch_m1, sh; sinh_series(zi, &sh); cosh_m1_series(zi, &ch_m1); szr->val = sin(zr)*(ch_m1 + 1.0); szi->val = cos(zr)*sh; szr->err = 2.0 * GSL_DBL_EPSILON * fabs(szr->val); szi->err = 2.0 * GSL_DBL_EPSILON * fabs(szi->val); return GSL_SUCCESS; } else if(fabs(zi) < GSL_LOG_DBL_MAX) { double ex = exp(zi); double ch = 0.5*(ex+1.0/ex); double sh = 0.5*(ex-1.0/ex); szr->val = sin(zr)*ch; szi->val = cos(zr)*sh; szr->err = 2.0 * GSL_DBL_EPSILON * fabs(szr->val); szi->err = 2.0 * GSL_DBL_EPSILON * fabs(szi->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR_2(szr, szi); } } int gsl_sf_complex_cos_e(const double zr, const double zi, gsl_sf_result * czr, gsl_sf_result * czi) { /* CHECK_POINTER(czr) */ /* CHECK_POINTER(czi) */ if(fabs(zi) < 1.0) { double ch_m1, sh; sinh_series(zi, &sh); cosh_m1_series(zi, &ch_m1); czr->val = cos(zr)*(ch_m1 + 1.0); czi->val = -sin(zr)*sh; czr->err = 2.0 * GSL_DBL_EPSILON * fabs(czr->val); czi->err = 2.0 * GSL_DBL_EPSILON * fabs(czi->val); return GSL_SUCCESS; } else if(fabs(zi) < GSL_LOG_DBL_MAX) { double ex = exp(zi); double ch = 0.5*(ex+1.0/ex); double sh = 0.5*(ex-1.0/ex); czr->val = cos(zr)*ch; czi->val = -sin(zr)*sh; czr->err = 2.0 * GSL_DBL_EPSILON * fabs(czr->val); czi->err = 2.0 * GSL_DBL_EPSILON * fabs(czi->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR_2(czr,czi); } } int gsl_sf_complex_logsin_e(const double zr, const double zi, gsl_sf_result * lszr, gsl_sf_result * lszi) { /* CHECK_POINTER(lszr) */ /* CHECK_POINTER(lszi) */ if(zi > 60.0) { lszr->val = -M_LN2 + zi; lszi->val = 0.5*M_PI - zr; lszr->err = 2.0 * GSL_DBL_EPSILON * fabs(lszr->val); lszi->err = 2.0 * GSL_DBL_EPSILON * fabs(lszi->val); } else if(zi < -60.0) { lszr->val = -M_LN2 - zi; lszi->val = -0.5*M_PI + zr; lszr->err = 2.0 * GSL_DBL_EPSILON * fabs(lszr->val); lszi->err = 2.0 * GSL_DBL_EPSILON * fabs(lszi->val); } else { gsl_sf_result sin_r, sin_i; int status; gsl_sf_complex_sin_e(zr, zi, &sin_r, &sin_i); /* ok by construction */ status = gsl_sf_complex_log_e(sin_r.val, sin_i.val, lszr, lszi); if(status == GSL_EDOM) { DOMAIN_ERROR_2(lszr, lszi); } } return gsl_sf_angle_restrict_symm_e(&(lszi->val)); } int gsl_sf_lnsinh_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(fabs(x) < 1.0) { double eps; sinh_series(x, &eps); result->val = log(eps); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -0.5*GSL_LOG_DBL_EPSILON) { result->val = x + log(0.5*(1.0 - exp(-2.0*x))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = -M_LN2 + x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_lncosh_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(fabs(x) < 1.0) { double eps; cosh_m1_series(x, &eps); return gsl_sf_log_1plusx_e(eps, result); } else if(x < -0.5*GSL_LOG_DBL_EPSILON) { result->val = x + log(0.5*(1.0 + exp(-2.0*x))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = -M_LN2 + x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /* inline int gsl_sf_sincos_e(const double theta, double * s, double * c) { double tan_half = tan(0.5 * theta); double den = 1. + tan_half*tan_half; double cos_theta = (1.0 - tan_half*tan_half) / den; double sin_theta = 2.0 * tan_half / den; } */ int gsl_sf_polar_to_rect(const double r, const double theta, gsl_sf_result * x, gsl_sf_result * y) { double t = theta; int status = gsl_sf_angle_restrict_symm_e(&t); double c = cos(t); double s = sin(t); x->val = r * cos(t); y->val = r * sin(t); x->err = r * fabs(s * GSL_DBL_EPSILON * t); x->err += 2.0 * GSL_DBL_EPSILON * fabs(x->val); y->err = r * fabs(c * GSL_DBL_EPSILON * t); y->err += 2.0 * GSL_DBL_EPSILON * fabs(y->val); return status; } int gsl_sf_rect_to_polar(const double x, const double y, gsl_sf_result * r, gsl_sf_result * theta) { int stat_h = gsl_sf_hypot_e(x, y, r); if(r->val > 0.0) { theta->val = atan2(y, x); theta->err = 2.0 * GSL_DBL_EPSILON * fabs(theta->val); return stat_h; } else { DOMAIN_ERROR(theta); } } int gsl_sf_angle_restrict_symm_err_e(const double theta, gsl_sf_result * result) { /* synthetic extended precision constants */ const double P1 = 4 * 7.8539812564849853515625e-01; const double P2 = 4 * 3.7748947079307981766760e-08; const double P3 = 4 * 2.6951514290790594840552e-15; const double TwoPi = 2*(P1 + P2 + P3); const double y = GSL_SIGN(theta) * 2 * floor(fabs(theta)/TwoPi); double r = ((theta - y*P1) - y*P2) - y*P3; if(r > M_PI) { r = (((r-2*P1)-2*P2)-2*P3); } /* r-TwoPi */ else if (r < -M_PI) r = (((r+2*P1)+2*P2)+2*P3); /* r+TwoPi */ result->val = r; if(fabs(theta) > 0.0625/GSL_DBL_EPSILON) { result->val = GSL_NAN; result->err = GSL_NAN; GSL_ERROR ("error", GSL_ELOSS); } else if(fabs(theta) > 0.0625/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val - theta); return GSL_SUCCESS; } else { double delta = fabs(result->val - theta); result->err = 2.0 * GSL_DBL_EPSILON * ((delta < M_PI) ? delta : M_PI); return GSL_SUCCESS; } } int gsl_sf_angle_restrict_pos_err_e(const double theta, gsl_sf_result * result) { /* synthetic extended precision constants */ const double P1 = 4 * 7.85398125648498535156e-01; const double P2 = 4 * 3.77489470793079817668e-08; const double P3 = 4 * 2.69515142907905952645e-15; const double TwoPi = 2*(P1 + P2 + P3); const double y = 2*floor(theta/TwoPi); double r = ((theta - y*P1) - y*P2) - y*P3; if(r > TwoPi) {r = (((r-2*P1)-2*P2)-2*P3); } /* r-TwoPi */ else if (r < 0) { /* may happen due to FP rounding */ r = (((r+2*P1)+2*P2)+2*P3); /* r+TwoPi */ } result->val = r; if(fabs(theta) > 0.0625/GSL_DBL_EPSILON) { result->val = GSL_NAN; result->err = fabs(result->val); GSL_ERROR ("error", GSL_ELOSS); } else if(fabs(theta) > 0.0625/GSL_SQRT_DBL_EPSILON) { result->err = GSL_DBL_EPSILON * fabs(result->val - theta); return GSL_SUCCESS; } else { double delta = fabs(result->val - theta); result->err = 2.0 * GSL_DBL_EPSILON * ((delta < M_PI) ? delta : M_PI); return GSL_SUCCESS; } } int gsl_sf_angle_restrict_symm_e(double * theta) { gsl_sf_result r; int stat = gsl_sf_angle_restrict_symm_err_e(*theta, &r); *theta = r.val; return stat; } int gsl_sf_angle_restrict_pos_e(double * theta) { gsl_sf_result r; int stat = gsl_sf_angle_restrict_pos_err_e(*theta, &r); *theta = r.val; return stat; } int gsl_sf_sin_err_e(const double x, const double dx, gsl_sf_result * result) { int stat_s = gsl_sf_sin_e(x, result); result->err += fabs(cos(x) * dx); result->err += GSL_DBL_EPSILON * fabs(result->val); return stat_s; } int gsl_sf_cos_err_e(const double x, const double dx, gsl_sf_result * result) { int stat_c = gsl_sf_cos_e(x, result); result->err += fabs(sin(x) * dx); result->err += GSL_DBL_EPSILON * fabs(result->val); return stat_c; } #if 0 int gsl_sf_sin_pi_x_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(-100.0 < x && x < 100.0) { result->val = sin(M_PI * x) / (M_PI * x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double N = floor(x + 0.5); const double f = x - N; if(N < INT_MAX && N > INT_MIN) { /* Make it an integer if we can. Saves another * call to floor(). */ const int intN = (int)N; const double sign = ( GSL_IS_ODD(intN) ? -1.0 : 1.0 ); result->val = sign * sin(M_PI * f); result->err = GSL_DBL_EPSILON * fabs(result->val); } else if(N > 2.0/GSL_DBL_EPSILON || N < -2.0/GSL_DBL_EPSILON) { /* All integer-valued floating point numbers * bigger than 2/eps=2^53 are actually even. */ result->val = 0.0; result->err = 0.0; } else { const double resN = N - 2.0*floor(0.5*N); /* 0 for even N, 1 for odd N */ const double sign = ( fabs(resN) > 0.5 ? -1.0 : 1.0 ); result->val = sign * sin(M_PI*f); result->err = GSL_DBL_EPSILON * fabs(result->val); } return GSL_SUCCESS; } } #endif int gsl_sf_sinc_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { const double ax = fabs(x); if(ax < 0.8) { /* Do not go to the limit of the fit since * there is a zero there and the Chebyshev * accuracy will go to zero. */ return cheb_eval_e(&sinc_cs, 2.0*ax-1.0, result); } else if(ax < 100.0) { /* Small arguments are no problem. * We trust the library sin() to * roughly machine precision. */ result->val = sin(M_PI * ax)/(M_PI * ax); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* Large arguments must be handled separately. */ const double r = M_PI*ax; gsl_sf_result s; int stat_s = gsl_sf_sin_e(r, &s); result->val = s.val/r; result->err = s.err/r + 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_s; } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_sin(const double x) { EVAL_RESULT(gsl_sf_sin_e(x, &result)); } double gsl_sf_cos(const double x) { EVAL_RESULT(gsl_sf_cos_e(x, &result)); } double gsl_sf_hypot(const double x, const double y) { EVAL_RESULT(gsl_sf_hypot_e(x, y, &result)); } double gsl_sf_lnsinh(const double x) { EVAL_RESULT(gsl_sf_lnsinh_e(x, &result)); } double gsl_sf_lncosh(const double x) { EVAL_RESULT(gsl_sf_lncosh_e(x, &result)); } double gsl_sf_angle_restrict_symm(const double theta) { double result = theta; EVAL_DOUBLE(gsl_sf_angle_restrict_symm_e(&result)); } double gsl_sf_angle_restrict_pos(const double theta) { double result = theta; EVAL_DOUBLE(gsl_sf_angle_restrict_pos_e(&result)); } #if 0 double gsl_sf_sin_pi_x(const double x) { EVAL_RESULT(gsl_sf_sin_pi_x_e(x, &result)); } #endif double gsl_sf_sinc(const double x) { EVAL_RESULT(gsl_sf_sinc_e(x, &result)); } sources_5316/external/gsl/gsl_sf_dilog.h0000664000176700017670000001010711705263724017146 0ustar paulpaul/* specfunc/gsl_sf_dilog.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_DILOG_H__ #define __GSL_SF_DILOG_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Real part of DiLogarithm(x), for real argument. * In Lewin's notation, this is Li_2(x). * * Li_2(x) = - Re[ Integrate[ Log[1-s] / s, {s, 0, x}] ] * * The function in the complex plane has a branch point * at z = 1; we place the cut in the conventional way, * on [1, +infty). This means that the value for real x > 1 * is a matter of definition; however, this choice does not * affect the real part and so is not relevant to the * interpretation of this implemented function. */ int gsl_sf_dilog_e(const double x, gsl_sf_result * result); double gsl_sf_dilog(const double x); /* DiLogarithm(z), for complex argument z = x + i y. * Computes the principal branch. * * Recall that the branch cut is on the real axis with x > 1. * The imaginary part of the computed value on the cut is given * by -Pi*log(x), which is the limiting value taken approaching * from y < 0. This is a conventional choice, though there is no * true standardized choice. * * Note that there is no canonical way to lift the defining * contour to the full Riemann surface because of the appearance * of a "hidden branch point" at z = 0 on non-principal sheets. * Experts will know the simple algebraic prescription for * obtaining the sheet they want; non-experts will not want * to know anything about it. This is why GSL chooses to compute * only on the principal branch. */ int gsl_sf_complex_dilog_xy_e( const double x, const double y, gsl_sf_result * result_re, gsl_sf_result * result_im ); /* DiLogarithm(z), for complex argument z = r Exp[i theta]. * Computes the principal branch, thereby assuming an * implicit reduction of theta to the range (-2 pi, 2 pi). * * If theta is identically zero, the imaginary part is computed * as if approaching from y > 0. For other values of theta no * special consideration is given, since it is assumed that * no other machine representations of multiples of pi will * produce y = 0 precisely. This assumption depends on some * subtle properties of the machine arithmetic, such as * correct rounding and monotonicity of the underlying * implementation of sin() and cos(). * * This function is ok, but the interface is confusing since * it makes it appear that the branch structure is resolved. * Furthermore the handling of values close to the branch * cut is subtle. Perhap this interface should be deprecated. */ int gsl_sf_complex_dilog_e( const double r, const double theta, gsl_sf_result * result_re, gsl_sf_result * result_im ); /* Spence integral; spence(s) := Li_2(1-s) * * This function has a branch point at 0; we place the * cut on (-infty,0). Because of our choice for the value * of Li_2(z) on the cut, spence(s) is continuous as * s approaches the cut from above. In other words, * we define spence(x) = spence(x + i 0+). */ int gsl_sf_complex_spence_xy_e( const double x, const double y, gsl_sf_result * real_sp, gsl_sf_result * imag_sp ); __END_DECLS #endif /* __GSL_SF_DILOG_H__ */ sources_5316/external/gsl/gsl_cdf__beta.c0000664000176700017670000000260511723710247017242 0ustar paulpaul/* cdf/cdf_beta.c * * Copyright (C) 2003, 2007 Brian Gough. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include "gsl__config.h" #include #include "gsl_cdf.h" #include "gsl_sf_gamma.h" #include "gsl_math.h" #include "gsl_cdf__beta_inc.c" double gsl_cdf_beta_P (const double x, const double a, const double b) { double P; if (x <= 0.0 ) { return 0.0; } if ( x >= 1.0 ) { return 1.0; } P = beta_inc_AXPY (1.0, 0.0, a, b, x); return P; } double gsl_cdf_beta_Q (const double x, const double a, const double b) { double Q; if ( x >= 1.0) { return 0.0; } if ( x <= 0.0 ) { return 1.0; } Q = beta_inc_AXPY (-1.0, 1.0, a, b, x); return Q; } sources_5316/external/gsl/gsl_cblas__caxpy.c0000664000176700017670000000041411723710247017777 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_caxpy (const int N, const void *alpha, const void *X, const int incX, void *Y, const int incY) { #define BASE float #include "gsl_cblas__source_axpy_c.h" #undef BASE } sources_5316/external/gsl/gsl_integration__qawo.c0000664000176700017670000002533011723710247021065 0ustar paulpaul/* integration/qawo.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_integration.h" #include "gsl_integration__initialise.c" #include "gsl_integration__set_initial.c" #include "gsl_integration__reset.c" #include "gsl_integration__qpsrt.c" #include "gsl_integration__util.c" #include "gsl_integration__qpsrt2.c" #include "gsl_integration__qelg.c" #include "gsl_integration__positivity.c" #include "gsl_integration__qc25f.c" int gsl_integration_qawo (gsl_function * f, const double a, const double epsabs, const double epsrel, const size_t limit, gsl_integration_workspace * workspace, gsl_integration_qawo_table * wf, double *result, double *abserr) { double area, errsum; double res_ext, err_ext; double result0, abserr0, resabs0, resasc0; double tolerance; double ertest = 0; double error_over_large_intervals = 0; double reseps = 0, abseps = 0, correc = 0; size_t ktmin = 0; int roundoff_type1 = 0, roundoff_type2 = 0, roundoff_type3 = 0; int error_type = 0, error_type2 = 0; size_t iteration = 0; int positive_integrand = 0; int extrapolate = 0; int extall = 0; int disallow_extrapolation = 0; struct extrapolation_table table; double b = a + wf->L ; double abs_omega = fabs (wf->omega) ; /* Initialize results */ initialise (workspace, a, b); *result = 0; *abserr = 0; if (limit > workspace->limit) { GSL_ERROR ("iteration limit exceeds available workspace", GSL_EINVAL) ; } /* Test on accuracy */ if (epsabs <= 0 && (epsrel < 50 * GSL_DBL_EPSILON || epsrel < 0.5e-28)) { GSL_ERROR ("tolerance cannot be acheived with given epsabs and epsrel", GSL_EBADTOL); } /* Perform the first integration */ qc25f (f, a, b, wf, 0, &result0, &abserr0, &resabs0, &resasc0); set_initial_result (workspace, result0, abserr0); tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (result0)); if (abserr0 <= 100 * GSL_DBL_EPSILON * resabs0 && abserr0 > tolerance) { *result = result0; *abserr = abserr0; GSL_ERROR ("cannot reach tolerance because of roundoff error" "on first attempt", GSL_EROUND); } else if ((abserr0 <= tolerance && abserr0 != resasc0) || abserr0 == 0.0) { *result = result0; *abserr = abserr0; return GSL_SUCCESS; } else if (limit == 1) { *result = result0; *abserr = abserr0; GSL_ERROR ("a maximum of one iteration was insufficient", GSL_EMAXITER); } /* Initialization */ initialise_table (&table); if (0.5 * abs_omega * fabs(b - a) <= 2) { append_table (&table, result0); extall = 1; } area = result0; errsum = abserr0; res_ext = result0; err_ext = GSL_DBL_MAX; positive_integrand = test_positivity (result0, resabs0); iteration = 1; do { size_t current_level; double a1, b1, a2, b2; double a_i, b_i, r_i, e_i; double area1 = 0, area2 = 0, area12 = 0; double error1 = 0, error2 = 0, error12 = 0; double resasc1, resasc2; double resabs1, resabs2; double last_e_i; /* Bisect the subinterval with the largest error estimate */ retrieve (workspace, &a_i, &b_i, &r_i, &e_i); current_level = workspace->level[workspace->i] + 1; if (current_level >= wf->n) { error_type = -1 ; /* exceeded limit of table */ break ; } a1 = a_i; b1 = 0.5 * (a_i + b_i); a2 = b1; b2 = b_i; iteration++; qc25f (f, a1, b1, wf, current_level, &area1, &error1, &resabs1, &resasc1); qc25f (f, a2, b2, wf, current_level, &area2, &error2, &resabs2, &resasc2); area12 = area1 + area2; error12 = error1 + error2; last_e_i = e_i; /* Improve previous approximations to the integral and test for accuracy. We write these expressions in the same way as the original QUADPACK code so that the rounding errors are the same, which makes testing easier. */ errsum = errsum + error12 - e_i; area = area + area12 - r_i; tolerance = GSL_MAX_DBL (epsabs, epsrel * fabs (area)); if (resasc1 != error1 && resasc2 != error2) { double delta = r_i - area12; if (fabs (delta) <= 1.0e-5 * fabs (area12) && error12 >= 0.99 * e_i) { if (!extrapolate) { roundoff_type1++; } else { roundoff_type2++; } } if (iteration > 10 && error12 > e_i) { roundoff_type3++; } } /* Test for roundoff and eventually set error flag */ if (roundoff_type1 + roundoff_type2 >= 10 || roundoff_type3 >= 20) { error_type = 2; /* round off error */ } if (roundoff_type2 >= 5) { error_type2 = 1; } /* set error flag in the case of bad integrand behaviour at a point of the integration range */ if (subinterval_too_small (a1, a2, b2)) { error_type = 4; } /* append the newly-created intervals to the list */ update (workspace, a1, b1, area1, error1, a2, b2, area2, error2); if (errsum <= tolerance) { goto compute_result; } if (error_type) { break; } if (iteration >= limit - 1) { error_type = 1; break; } /* set up variables on first iteration */ if (iteration == 2 && extall) { error_over_large_intervals = errsum; ertest = tolerance; append_table (&table, area); continue; } if (disallow_extrapolation) { continue; } if (extall) { error_over_large_intervals += -last_e_i; if (current_level < workspace->maximum_level) { error_over_large_intervals += error12; } if (extrapolate) goto label70; } if (large_interval(workspace)) { continue; } if (extall) { extrapolate = 1; workspace->nrmax = 1; } else { /* test whether the interval to be bisected next is the smallest interval. */ size_t i = workspace->i; double width = workspace->blist[i] - workspace->alist[i]; if (0.25 * fabs(width) * abs_omega > 2) continue; extall = 1; error_over_large_intervals = errsum; ertest = tolerance; continue; } label70: if (!error_type2 && error_over_large_intervals > ertest) { if (increase_nrmax (workspace)) continue; } /* Perform extrapolation */ append_table (&table, area); if (table.n < 3) { reset_nrmax(workspace); extrapolate = 0; error_over_large_intervals = errsum; continue; } qelg (&table, &reseps, &abseps); ktmin++; if (ktmin > 5 && err_ext < 0.001 * errsum) { error_type = 5; } if (abseps < err_ext) { ktmin = 0; err_ext = abseps; res_ext = reseps; correc = error_over_large_intervals; ertest = GSL_MAX_DBL (epsabs, epsrel * fabs (reseps)); if (err_ext <= ertest) break; } /* Prepare bisection of the smallest interval. */ if (table.n == 1) { disallow_extrapolation = 1; } if (error_type == 5) { break; } /* work on interval with largest error */ reset_nrmax (workspace); extrapolate = 0; error_over_large_intervals = errsum; } while (iteration < limit); *result = res_ext; *abserr = err_ext; if (err_ext == GSL_DBL_MAX) goto compute_result; if (error_type || error_type2) { if (error_type2) { err_ext += correc; } if (error_type == 0) error_type = 3; if (result != 0 && area != 0) { if (err_ext / fabs (res_ext) > errsum / fabs (area)) goto compute_result; } else if (err_ext > errsum) { goto compute_result; } else if (area == 0.0) { goto return_error; } } /* Test on divergence. */ { double max_area = GSL_MAX_DBL (fabs (res_ext), fabs (area)); if (!positive_integrand && max_area < 0.01 * resabs0) goto return_error; } { double ratio = res_ext / area; if (ratio < 0.01 || ratio > 100 || errsum > fabs (area)) error_type = 6; } goto return_error; compute_result: *result = sum_results (workspace); *abserr = errsum; return_error: if (error_type > 2) error_type--; if (error_type == 0) { return GSL_SUCCESS; } else if (error_type == 1) { GSL_ERROR ("number of iterations was insufficient", GSL_EMAXITER); } else if (error_type == 2) { GSL_ERROR ("cannot reach tolerance because of roundoff error", GSL_EROUND); } else if (error_type == 3) { GSL_ERROR ("bad integrand behavior found in the integration interval", GSL_ESING); } else if (error_type == 4) { GSL_ERROR ("roundoff error detected in extrapolation table", GSL_EROUND); } else if (error_type == 5) { GSL_ERROR ("integral is divergent, or slowly convergent", GSL_EDIVERGE); } else if (error_type == -1) { GSL_ERROR ("exceeded limit of trigonometric table", GSL_ETABLE); } else { GSL_ERROR ("could not integrate function", GSL_EFAILED); } } sources_5316/external/gsl/gsl_roots__falsepos.c0000664000176700017670000001106511723710247020555 0ustar paulpaul/* roots/falsepos.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* falsepos.c -- falsepos root finding algorithm The false position algorithm uses bracketing by linear interpolation. If a linear interpolation step would decrease the size of the bracket by less than a bisection step would then the algorithm takes a bisection step instead. The last linear interpolation estimate of the root is used. If a bisection step causes it to fall outside the brackets then it is replaced by the bisection estimate (x_upper + x_lower)/2. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_roots.h" #include "gsl_roots__roots.h" typedef struct { double f_lower, f_upper; } falsepos_state_t; static int falsepos_init (void * vstate, gsl_function * f, double * root, double x_lower, double x_upper); static int falsepos_iterate (void * vstate, gsl_function * f, double * root, double * x_lower, double * x_upper); static int falsepos_init (void * vstate, gsl_function * f, double * root, double x_lower, double x_upper) { falsepos_state_t * state = (falsepos_state_t *) vstate; double f_lower, f_upper ; *root = 0.5 * (x_lower + x_upper); SAFE_FUNC_CALL (f, x_lower, &f_lower); SAFE_FUNC_CALL (f, x_upper, &f_upper); state->f_lower = f_lower; state->f_upper = f_upper; if ((f_lower < 0.0 && f_upper < 0.0) || (f_lower > 0.0 && f_upper > 0.0)) { GSL_ERROR ("endpoints do not straddle y=0", GSL_EINVAL); } return GSL_SUCCESS; } static int falsepos_iterate (void * vstate, gsl_function * f, double * root, double * x_lower, double * x_upper) { falsepos_state_t * state = (falsepos_state_t *) vstate; double x_linear, f_linear; double x_bisect, f_bisect; double x_left = *x_lower ; double x_right = *x_upper ; double f_lower = state->f_lower; double f_upper = state->f_upper; double w ; if (f_lower == 0.0) { *root = x_left ; *x_upper = x_left; return GSL_SUCCESS; } if (f_upper == 0.0) { *root = x_right ; *x_lower = x_right; return GSL_SUCCESS; } /* Draw a line between f(*lower_bound) and f(*upper_bound) and note where it crosses the X axis; that's where we will split the interval. */ x_linear = x_right - (f_upper * (x_left - x_right) / (f_lower - f_upper)); SAFE_FUNC_CALL (f, x_linear, &f_linear); if (f_linear == 0.0) { *root = x_linear; *x_lower = x_linear; *x_upper = x_linear; return GSL_SUCCESS; } /* Discard the half of the interval which doesn't contain the root. */ if ((f_lower > 0.0 && f_linear < 0.0) || (f_lower < 0.0 && f_linear > 0.0)) { *root = x_linear ; *x_upper = x_linear; state->f_upper = f_linear; w = x_linear - x_left ; } else { *root = x_linear ; *x_lower = x_linear; state->f_lower = f_linear; w = x_right - x_linear; } if (w < 0.5 * (x_right - x_left)) { return GSL_SUCCESS ; } x_bisect = 0.5 * (x_left + x_right); SAFE_FUNC_CALL (f, x_bisect, &f_bisect); if ((f_lower > 0.0 && f_bisect < 0.0) || (f_lower < 0.0 && f_bisect > 0.0)) { *x_upper = x_bisect; state->f_upper = f_bisect; if (*root > x_bisect) *root = 0.5 * (x_left + x_bisect) ; } else { *x_lower = x_bisect; state->f_lower = f_bisect; if (*root < x_bisect) *root = 0.5 * (x_bisect + x_right) ; } return GSL_SUCCESS; } static const gsl_root_fsolver_type falsepos_type = {"falsepos", /* name */ sizeof (falsepos_state_t), &falsepos_init, &falsepos_iterate}; const gsl_root_fsolver_type * gsl_root_fsolver_falsepos = &falsepos_type; sources_5316/external/gsl/gsl_cblas__scopy.c0000664000176700017670000000037311723710247020014 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_scopy (const int N, const float *X, const int incX, float *Y, const int incY) { #define BASE float #include "gsl_cblas__source_copy_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__cgerc.c0000664000176700017670000000054011723710247017736 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cgerc (const enum CBLAS_ORDER order, const int M, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *A, const int lda) { #define BASE float #include "gsl_cblas__source_gerc.h" #undef BASE } sources_5316/external/gsl/gsl_integration__qk41.c0000664000176700017670000000725711723710247020706 0ustar paulpaul/* integration/qk41.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_integration.h" /* Gauss quadrature weights and kronrod quadrature abscissae and weights as evaluated with 80 decimal digit arithmetic by L. W. Fullerton, Bell Labs, Nov. 1981. */ static const double xgk[21] = /* abscissae of the 41-point kronrod rule */ { 0.998859031588277663838315576545863, 0.993128599185094924786122388471320, 0.981507877450250259193342994720217, 0.963971927277913791267666131197277, 0.940822633831754753519982722212443, 0.912234428251325905867752441203298, 0.878276811252281976077442995113078, 0.839116971822218823394529061701521, 0.795041428837551198350638833272788, 0.746331906460150792614305070355642, 0.693237656334751384805490711845932, 0.636053680726515025452836696226286, 0.575140446819710315342946036586425, 0.510867001950827098004364050955251, 0.443593175238725103199992213492640, 0.373706088715419560672548177024927, 0.301627868114913004320555356858592, 0.227785851141645078080496195368575, 0.152605465240922675505220241022678, 0.076526521133497333754640409398838, 0.000000000000000000000000000000000 }; /* xgk[1], xgk[3], ... abscissae of the 20-point gauss rule. xgk[0], xgk[2], ... abscissae to optimally extend the 20-point gauss rule */ static const double wg[11] = /* weights of the 20-point gauss rule */ { 0.017614007139152118311861962351853, 0.040601429800386941331039952274932, 0.062672048334109063569506535187042, 0.083276741576704748724758143222046, 0.101930119817240435036750135480350, 0.118194531961518417312377377711382, 0.131688638449176626898494499748163, 0.142096109318382051329298325067165, 0.149172986472603746787828737001969, 0.152753387130725850698084331955098 }; static const double wgk[21] = /* weights of the 41-point kronrod rule */ { 0.003073583718520531501218293246031, 0.008600269855642942198661787950102, 0.014626169256971252983787960308868, 0.020388373461266523598010231432755, 0.025882133604951158834505067096153, 0.031287306777032798958543119323801, 0.036600169758200798030557240707211, 0.041668873327973686263788305936895, 0.046434821867497674720231880926108, 0.050944573923728691932707670050345, 0.055195105348285994744832372419777, 0.059111400880639572374967220648594, 0.062653237554781168025870122174255, 0.065834597133618422111563556969398, 0.068648672928521619345623411885368, 0.071054423553444068305790361723210, 0.073030690332786667495189417658913, 0.074582875400499188986581418362488, 0.075704497684556674659542775376617, 0.076377867672080736705502835038061, 0.076600711917999656445049901530102 }; void gsl_integration_qk41 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc) { double fv1[21], fv2[21]; gsl_integration_qk (21, xgk, wg, wgk, fv1, fv2, f, a, b, result, abserr, resabs, resasc); } sources_5316/external/gsl/gsl_integration__qng.c0000664000176700017670000001242011723710247020677 0ustar paulpaul/* integration/qng.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_integration.h" #include "gsl_integration__err.c" #include "gsl_integration__qng.h" int gsl_integration_qng (const gsl_function *f, double a, double b, double epsabs, double epsrel, double * result, double * abserr, size_t * neval) { double fv1[5], fv2[5], fv3[5], fv4[5]; double savfun[21]; /* array of function values which have been computed */ double res10, res21, res43, res87; /* 10, 21, 43 and 87 point results */ double result_kronrod, err ; double resabs; /* approximation to the integral of abs(f) */ double resasc; /* approximation to the integral of abs(f-i/(b-a)) */ const double half_length = 0.5 * (b - a); const double abs_half_length = fabs (half_length); const double center = 0.5 * (b + a); const double f_center = GSL_FN_EVAL(f, center); int k ; if (epsabs <= 0 && (epsrel < 50 * GSL_DBL_EPSILON || epsrel < 0.5e-28)) { * result = 0; * abserr = 0; * neval = 0; GSL_ERROR ("tolerance cannot be acheived with given epsabs and epsrel", GSL_EBADTOL); }; /* Compute the integral using the 10- and 21-point formula. */ res10 = 0; res21 = w21b[5] * f_center; resabs = w21b[5] * fabs (f_center); for (k = 0; k < 5; k++) { const double abscissa = half_length * x1[k]; const double fval1 = GSL_FN_EVAL(f, center + abscissa); const double fval2 = GSL_FN_EVAL(f, center - abscissa); const double fval = fval1 + fval2; res10 += w10[k] * fval; res21 += w21a[k] * fval; resabs += w21a[k] * (fabs (fval1) + fabs (fval2)); savfun[k] = fval; fv1[k] = fval1; fv2[k] = fval2; } for (k = 0; k < 5; k++) { const double abscissa = half_length * x2[k]; const double fval1 = GSL_FN_EVAL(f, center + abscissa); const double fval2 = GSL_FN_EVAL(f, center - abscissa); const double fval = fval1 + fval2; res21 += w21b[k] * fval; resabs += w21b[k] * (fabs (fval1) + fabs (fval2)); savfun[k + 5] = fval; fv3[k] = fval1; fv4[k] = fval2; } resabs *= abs_half_length ; { const double mean = 0.5 * res21; resasc = w21b[5] * fabs (f_center - mean); for (k = 0; k < 5; k++) { resasc += (w21a[k] * (fabs (fv1[k] - mean) + fabs (fv2[k] - mean)) + w21b[k] * (fabs (fv3[k] - mean) + fabs (fv4[k] - mean))); } resasc *= abs_half_length ; } result_kronrod = res21 * half_length; err = rescale_error ((res21 - res10) * half_length, resabs, resasc) ; /* test for convergence. */ if (err < epsabs || err < epsrel * fabs (result_kronrod)) { * result = result_kronrod ; * abserr = err ; * neval = 21; return GSL_SUCCESS; } /* compute the integral using the 43-point formula. */ res43 = w43b[11] * f_center; for (k = 0; k < 10; k++) { res43 += savfun[k] * w43a[k]; } for (k = 0; k < 11; k++) { const double abscissa = half_length * x3[k]; const double fval = (GSL_FN_EVAL(f, center + abscissa) + GSL_FN_EVAL(f, center - abscissa)); res43 += fval * w43b[k]; savfun[k + 10] = fval; } /* test for convergence */ result_kronrod = res43 * half_length; err = rescale_error ((res43 - res21) * half_length, resabs, resasc); if (err < epsabs || err < epsrel * fabs (result_kronrod)) { * result = result_kronrod ; * abserr = err ; * neval = 43; return GSL_SUCCESS; } /* compute the integral using the 87-point formula. */ res87 = w87b[22] * f_center; for (k = 0; k < 21; k++) { res87 += savfun[k] * w87a[k]; } for (k = 0; k < 22; k++) { const double abscissa = half_length * x4[k]; res87 += w87b[k] * (GSL_FN_EVAL(f, center + abscissa) + GSL_FN_EVAL(f, center - abscissa)); } /* test for convergence */ result_kronrod = res87 * half_length ; err = rescale_error ((res87 - res43) * half_length, resabs, resasc); if (err < epsabs || err < epsrel * fabs (result_kronrod)) { * result = result_kronrod ; * abserr = err ; * neval = 87; return GSL_SUCCESS; } /* failed to converge */ * result = result_kronrod ; * abserr = err ; * neval = 87; GSL_ERROR("failed to reach tolerance with highest-order rule", GSL_ETOL) ; } sources_5316/external/gsl/gsl_cblas__dcopy.c0000664000176700017670000000037611723710247020000 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dcopy (const int N, const double *X, const int incX, double *Y, const int incY) { #define BASE double #include "gsl_cblas__source_copy_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__stbsv.c0000664000176700017670000000063211723710247020016 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_stbsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const float *A, const int lda, float *X, const int incX) { #define BASE float #include "gsl_cblas__source_tbsv_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__dsyr2k.c0000664000176700017670000000073111723710247020073 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dsyr2k (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const double alpha, const double *A, const int lda, const double *B, const int ldb, const double beta, double *C, const int ldc) { #define BASE double #include "gsl_cblas__source_syr2k_r.h" #undef BASE } sources_5316/external/gsl/templates_on.h0000664000176700017670000001433711705263724017216 0ustar paulpaul/* If BASE is undefined we use function names like gsl_name() and assume that we are using doubles. If BASE is defined we used function names like gsl_BASE_name() and use BASE as the base datatype */ #if defined(BASE_GSL_COMPLEX_LONG) #define BASE gsl_complex_long_double #define SHORT complex_long_double #define SHORT_REAL long_double #define ATOMIC long double #define USES_LONGDOUBLE 1 #define MULTIPLICITY 2 #define FP 1 #define IN_FORMAT "%Lg" #define OUT_FORMAT "%Lg" #define ATOMIC_IO ATOMIC #define ZERO {{0.0L,0.0L}} #define ONE {{1.0L,0.0L}} #define BASE_EPSILON GSL_DBL_EPSILON #elif defined(BASE_GSL_COMPLEX) #define BASE gsl_complex #define SHORT complex #define SHORT_REAL #define ATOMIC double #define MULTIPLICITY 2 #define FP 1 #define IN_FORMAT "%lg" #define OUT_FORMAT "%g" #define ATOMIC_IO ATOMIC #define ZERO {{0.0,0.0}} #define ONE {{1.0,0.0}} #define BASE_EPSILON GSL_DBL_EPSILON #elif defined(BASE_GSL_COMPLEX_FLOAT) #define BASE gsl_complex_float #define SHORT complex_float #define SHORT_REAL float #define ATOMIC float #define MULTIPLICITY 2 #define FP 1 #define IN_FORMAT "%g" #define OUT_FORMAT "%g" #define ATOMIC_IO ATOMIC #define ZERO {{0.0F,0.0F}} #define ONE {{1.0F,0.0F}} #define BASE_EPSILON GSL_FLT_EPSILON #elif defined(BASE_LONG_DOUBLE) #define BASE long double #define SHORT long_double #define ATOMIC long double #define USES_LONGDOUBLE 1 #define MULTIPLICITY 1 #define FP 1 #define IN_FORMAT "%Lg" #define OUT_FORMAT "%Lg" #define ATOMIC_IO ATOMIC #define ZERO 0.0L #define ONE 1.0L #define BASE_EPSILON GSL_DBL_EPSILON #elif defined(BASE_DOUBLE) #define BASE double #define SHORT #define ATOMIC double #define MULTIPLICITY 1 #define FP 1 #define IN_FORMAT "%lg" #define OUT_FORMAT "%g" #define ATOMIC_IO ATOMIC #define ZERO 0.0 #define ONE 1.0 #define BASE_EPSILON GSL_DBL_EPSILON #elif defined(BASE_FLOAT) #define BASE float #define SHORT float #define ATOMIC float #define MULTIPLICITY 1 #define FP 1 #define IN_FORMAT "%g" #define OUT_FORMAT "%g" #define ATOMIC_IO ATOMIC #define ZERO 0.0F #define ONE 1.0F #define BASE_EPSILON GSL_FLT_EPSILON #elif defined(BASE_ULONG) #define BASE unsigned long #define SHORT ulong #define ATOMIC unsigned long #define MULTIPLICITY 1 #define IN_FORMAT "%lu" #define OUT_FORMAT "%lu" #define ATOMIC_IO ATOMIC #define ZERO 0UL #define ONE 1UL #define UNSIGNED 1 #elif defined(BASE_LONG) #define BASE long #define SHORT long #define ATOMIC long #define MULTIPLICITY 1 #define IN_FORMAT "%ld" #define OUT_FORMAT "%ld" #define ATOMIC_IO ATOMIC #define ZERO 0L #define ONE 1L #elif defined(BASE_UINT) #define BASE unsigned int #define SHORT uint #define ATOMIC unsigned int #define MULTIPLICITY 1 #define IN_FORMAT "%u" #define OUT_FORMAT "%u" #define ATOMIC_IO ATOMIC #define ZERO 0U #define ONE 1U #define UNSIGNED 1 #elif defined(BASE_INT) #define BASE int #define SHORT int #define ATOMIC int #define MULTIPLICITY 1 #define IN_FORMAT "%d" #define OUT_FORMAT "%d" #define ATOMIC_IO ATOMIC #define ZERO 0 #define ONE 1 #elif defined(BASE_USHORT) #define BASE unsigned short #define SHORT ushort #define ATOMIC unsigned short #define MULTIPLICITY 1 #define IN_FORMAT "%hu" #define OUT_FORMAT "%hu" #define ATOMIC_IO ATOMIC #define ZERO 0U #define ONE 1U #define UNSIGNED 1 #elif defined(BASE_SHORT) #define BASE short #define SHORT short #define ATOMIC short #define MULTIPLICITY 1 #define IN_FORMAT "%hd" #define OUT_FORMAT "%hd" #define ATOMIC_IO ATOMIC #define ZERO 0 #define ONE 1 #elif defined(BASE_UCHAR) #define BASE unsigned char #define SHORT uchar #define ATOMIC unsigned char #define MULTIPLICITY 1 #define IN_FORMAT "%u" #define OUT_FORMAT "%u" #define ATOMIC_IO unsigned int #define ZERO 0U #define ONE 1U #define UNSIGNED 1 #elif defined(BASE_CHAR) #define BASE char #define SHORT char #define ATOMIC char #define MULTIPLICITY 1 #define IN_FORMAT "%d" #define OUT_FORMAT "%d" #define ATOMIC_IO int #define ZERO 0 #define ONE 1 #ifdef __CHAR_UNSIGNED__ #define UNSIGNED 1 #endif #else #error unknown BASE_ directive in source.h #endif #define CONCAT2x(a,b) a ## _ ## b #define CONCAT2(a,b) CONCAT2x(a,b) #define CONCAT3x(a,b,c) a ## _ ## b ## _ ## c #define CONCAT3(a,b,c) CONCAT3x(a,b,c) #define CONCAT4x(a,b,c,d) a ## _ ## b ## _ ## c ## _ ## d #define CONCAT4(a,b,c,d) CONCAT4x(a,b,c,d) #ifndef USE_QUALIFIER #define QUALIFIER #endif #ifdef USE_QUALIFIER #if defined(BASE_DOUBLE) #define FUNCTION(dir,name) CONCAT3(dir,QUALIFIER,name) #define TYPE(dir) dir #define VIEW(dir,name) CONCAT2(dir,name) #define QUALIFIED_TYPE(dir) QUALIFIER dir #define QUALIFIED_VIEW(dir,name) CONCAT3(dir,QUALIFIER,name) #else #define FUNCTION(a,c) CONCAT4(a,SHORT,QUALIFIER,c) #define TYPE(dir) CONCAT2(dir,SHORT) #define VIEW(dir,name) CONCAT3(dir,SHORT,name) #define QUALIFIED_TYPE(dir) QUALIFIER CONCAT2(dir,SHORT) #define QUALIFIED_VIEW(dir,name) CONCAT4(dir,SHORT,QUALIFIER,name) #endif #if defined(BASE_GSL_COMPLEX) #define REAL_TYPE(dir) dir #define REAL_VIEW(dir,name) CONCAT2(dir,name) #define QUALIFIED_REAL_TYPE(dir) QUALIFIER dir #define QUALIFIED_REAL_VIEW(dir,name) CONCAT3(dir,QUALIFIER,name) #else #define REAL_TYPE(dir) CONCAT2(dir,SHORT_REAL) #define REAL_VIEW(dir,name) CONCAT3(dir,SHORT_REAL,name) #define QUALIFIED_REAL_TYPE(dir) QUALIFIER CONCAT2(dir,SHORT_REAL) #define QUALIFIED_REAL_VIEW(dir,name) CONCAT4(dir,SHORT_REAL,QUALIFIER,name) #endif #else #if defined(BASE_DOUBLE) #define FUNCTION(dir,name) CONCAT2(dir,name) #define TYPE(dir) dir #define VIEW(dir,name) CONCAT2(dir,name) #define QUALIFIED_TYPE(dir) TYPE(dir) #define QUALIFIED_VIEW(dir,name) CONCAT2(dir,name) #else #define FUNCTION(a,c) CONCAT3(a,SHORT,c) #define TYPE(dir) CONCAT2(dir,SHORT) #define VIEW(dir,name) CONCAT3(dir,SHORT,name) #define QUALIFIED_TYPE(dir) TYPE(dir) #define QUALIFIED_VIEW(dir,name) CONCAT3(dir,SHORT,name) #endif #if defined(BASE_GSL_COMPLEX) #define REAL_TYPE(dir) dir #define REAL_VIEW(dir,name) CONCAT2(dir,name) #define QUALIFIED_REAL_TYPE(dir) dir #define QUALIFIED_REAL_VIEW(dir,name) CONCAT2(dir,name) #else #define REAL_TYPE(dir) CONCAT2(dir,SHORT_REAL) #define REAL_VIEW(dir,name) CONCAT3(dir,SHORT_REAL,name) #define QUALIFIED_REAL_TYPE(dir) CONCAT2(dir,SHORT_REAL) #define QUALIFIED_REAL_VIEW(dir,name) CONCAT3(dir,SHORT_REAL,name) #endif #endif #define STRING(x) #x #define EXPAND(x) STRING(x) #define NAME(x) EXPAND(TYPE(x)) sources_5316/external/gsl/gsl_bspline.h0000664000176700017670000000442011705263724017015 0ustar paulpaul/* bspline/gsl_bspline.h * * Copyright (C) 2006 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BSPLINE_H__ #define __GSL_BSPLINE_H__ #include #include "gsl_math.h" #include "gsl_vector.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t k; /* spline order */ size_t km1; /* k - 1 (polynomial order) */ size_t l; /* number of polynomial pieces on interval */ size_t nbreak; /* number of breakpoints (l + 1) */ size_t n; /* number of bspline basis functions (l + k - 1) */ gsl_vector *knots; /* knots vector */ gsl_vector *deltal; /* left delta */ gsl_vector *deltar; /* right delta */ gsl_vector *B; /* temporary spline results */ } gsl_bspline_workspace; gsl_bspline_workspace * gsl_bspline_alloc(const size_t k, const size_t nbreak); void gsl_bspline_free(gsl_bspline_workspace *w); size_t gsl_bspline_ncoeffs (gsl_bspline_workspace * w); size_t gsl_bspline_order (gsl_bspline_workspace * w); size_t gsl_bspline_nbreak (gsl_bspline_workspace * w); double gsl_bspline_breakpoint (size_t i, gsl_bspline_workspace * w); int gsl_bspline_knots(const gsl_vector *breakpts, gsl_bspline_workspace *w); int gsl_bspline_knots_uniform(const double a, const double b, gsl_bspline_workspace *w); int gsl_bspline_eval(const double x, gsl_vector *B, gsl_bspline_workspace *w); __END_DECLS #endif /* __GSL_BSPLINE_H__ */ sources_5316/external/gsl/gsl_cblas__source_syr2.h0000664000176700017670000000371711705263724021153 0ustar paulpaul/* blas/source_syr2.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; if (N == 0) return; if (alpha == 0.0) return; if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE tmp1 = alpha * X[ix]; const BASE tmp2 = alpha * Y[iy]; INDEX jx = ix; INDEX jy = iy; for (j = i; j < N; j++) { A[lda * i + j] += tmp1 * Y[jy] + tmp2 * X[jx]; jx += incX; jy += incY; } ix += incX; iy += incY; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE tmp1 = alpha * X[ix]; const BASE tmp2 = alpha * Y[iy]; INDEX jx = OFFSET(N, incX); INDEX jy = OFFSET(N, incY); for (j = 0; j <= i; j++) { A[lda * i + j] += tmp1 * Y[jy] + tmp2 * X[jx]; jx += incX; jy += incY; } ix += incX; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_multiroots__enorm.c0000664000176700017670000000205311723710247021131 0ustar paulpaul/* multiroots/enorm.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static double enorm (const gsl_vector * f); static double enorm (const gsl_vector * f) { double e2 = 0 ; size_t i, n = f->size ; for (i = 0; i < n ; i++) { double fi= gsl_vector_get(f, i); e2 += fi * fi ; } return sqrt(e2); } sources_5316/external/gsl/gsl_permutation__permute_source.c0000664000176700017670000000756311723710247023213 0ustar paulpaul/* permutation/permute_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* In-place Permutations permute: OUT[i] = IN[perm[i]] i = 0 .. N-1 invpermute: OUT[perm[i]] = IN[i] i = 0 .. N-1 PERM is an index map, i.e. a vector which contains a permutation of the integers 0 .. N-1. From Knuth "Sorting and Searching", Volume 3 (3rd ed), Section 5.2 Exercise 10 (answers), p 617 FIXME: these have not been fully tested. */ int TYPE (gsl_permute) (const size_t * p, ATOMIC * data, const size_t stride, const size_t n) { size_t i, k, pk; for (i = 0; i < n; i++) { k = p[i]; while (k > i) k = p[k]; if (k < i) continue ; /* Now have k == i, i.e the least in its cycle */ pk = p[k]; if (pk == i) continue ; /* shuffle the elements of the cycle */ { unsigned int a; ATOMIC t[MULTIPLICITY]; for (a = 0; a < MULTIPLICITY; a++) t[a] = data[i*stride*MULTIPLICITY + a]; while (pk != i) { for (a = 0; a < MULTIPLICITY; a++) { ATOMIC r1 = data[pk*stride*MULTIPLICITY + a]; data[k*stride*MULTIPLICITY + a] = r1; } k = pk; pk = p[k]; }; for (a = 0; a < MULTIPLICITY; a++) data[k*stride*MULTIPLICITY + a] = t[a]; } } return GSL_SUCCESS; } int FUNCTION (gsl_permute,inverse) (const size_t * p, ATOMIC * data, const size_t stride, const size_t n) { size_t i, k, pk; for (i = 0; i < n; i++) { k = p[i]; while (k > i) k = p[k]; if (k < i) continue ; /* Now have k == i, i.e the least in its cycle */ pk = p[k]; if (pk == i) continue ; /* shuffle the elements of the cycle in the inverse direction */ { unsigned int a; ATOMIC t[MULTIPLICITY]; for (a = 0; a < MULTIPLICITY; a++) t[a] = data[k*stride*MULTIPLICITY+a]; while (pk != i) { for (a = 0; a < MULTIPLICITY; a++) { ATOMIC r1 = data[pk*stride*MULTIPLICITY + a]; data[pk*stride*MULTIPLICITY + a] = t[a]; t[a] = r1; } k = pk; pk = p[k]; }; for (a = 0; a < MULTIPLICITY; a++) data[pk*stride*MULTIPLICITY+a] = t[a]; } } return GSL_SUCCESS; } int TYPE (gsl_permute_vector) (const gsl_permutation * p, TYPE (gsl_vector) * v) { if (v->size != p->size) { GSL_ERROR ("vector and permutation must be the same length", GSL_EBADLEN); } TYPE (gsl_permute) (p->data, v->data, v->stride, v->size) ; return GSL_SUCCESS; } int FUNCTION (gsl_permute_vector,inverse) (const gsl_permutation * p, TYPE (gsl_vector) * v) { if (v->size != p->size) { GSL_ERROR ("vector and permutation must be the same length", GSL_EBADLEN); } FUNCTION (gsl_permute,inverse) (p->data, v->data, v->stride, v->size) ; return GSL_SUCCESS; } sources_5316/external/gsl/gsl_fft__c_radix2.c0000664000176700017670000002045111723710247020044 0ustar paulpaul/* fft/c_radix2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION(gsl_fft_complex,radix2_forward) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n) { gsl_fft_direction sign = gsl_fft_forward; int status = FUNCTION(gsl_fft_complex,radix2_transform) (data, stride, n, sign); return status; } int FUNCTION(gsl_fft_complex,radix2_backward) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n) { gsl_fft_direction sign = gsl_fft_backward; int status = FUNCTION(gsl_fft_complex,radix2_transform) (data, stride, n, sign); return status; } int FUNCTION(gsl_fft_complex,radix2_inverse) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n) { gsl_fft_direction sign = gsl_fft_backward; int status = FUNCTION(gsl_fft_complex,radix2_transform) (data, stride, n, sign); if (status) { return status; } /* normalize inverse fft with 1/n */ { const ATOMIC norm = 1.0 / n; size_t i; for (i = 0; i < n; i++) { REAL(data,stride,i) *= norm; IMAG(data,stride,i) *= norm; } } return status; } int FUNCTION(gsl_fft_complex,radix2_transform) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n, const gsl_fft_direction sign) { int result ; size_t dual; size_t bit; size_t logn = 0; int status; if (n == 1) /* identity operation */ { return 0 ; } /* make sure that n is a power of 2 */ result = fft_binary_logn(n) ; if (result == -1) { GSL_ERROR ("n is not a power of 2", GSL_EINVAL); } else { logn = result ; } /* bit reverse the ordering of input data for decimation in time algorithm */ status = FUNCTION(fft_complex,bitreverse_order) (data, stride, n, logn) ; /* apply fft recursion */ dual = 1; for (bit = 0; bit < logn; bit++) { ATOMIC w_real = 1.0; ATOMIC w_imag = 0.0; const double theta = 2.0 * ((int) sign) * M_PI / (2.0 * (double) dual); const ATOMIC s = sin (theta); const ATOMIC t = sin (theta / 2.0); const ATOMIC s2 = 2.0 * t * t; size_t a, b; /* a = 0 */ for (b = 0; b < n; b += 2 * dual) { const size_t i = b ; const size_t j = b + dual; const ATOMIC z1_real = REAL(data,stride,j) ; const ATOMIC z1_imag = IMAG(data,stride,j) ; const ATOMIC wd_real = z1_real ; const ATOMIC wd_imag = z1_imag ; REAL(data,stride,j) = REAL(data,stride,i) - wd_real; IMAG(data,stride,j) = IMAG(data,stride,i) - wd_imag; REAL(data,stride,i) += wd_real; IMAG(data,stride,i) += wd_imag; } /* a = 1 .. (dual-1) */ for (a = 1; a < dual; a++) { /* trignometric recurrence for w-> exp(i theta) w */ { const ATOMIC tmp_real = w_real - s * w_imag - s2 * w_real; const ATOMIC tmp_imag = w_imag + s * w_real - s2 * w_imag; w_real = tmp_real; w_imag = tmp_imag; } for (b = 0; b < n; b += 2 * dual) { const size_t i = b + a; const size_t j = b + a + dual; const ATOMIC z1_real = REAL(data,stride,j) ; const ATOMIC z1_imag = IMAG(data,stride,j) ; const ATOMIC wd_real = w_real * z1_real - w_imag * z1_imag; const ATOMIC wd_imag = w_real * z1_imag + w_imag * z1_real; REAL(data,stride,j) = REAL(data,stride,i) - wd_real; IMAG(data,stride,j) = IMAG(data,stride,i) - wd_imag; REAL(data,stride,i) += wd_real; IMAG(data,stride,i) += wd_imag; } } dual *= 2; } return 0; } int FUNCTION(gsl_fft_complex,radix2_dif_forward) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n) { gsl_fft_direction sign = gsl_fft_forward; int status = FUNCTION(gsl_fft_complex,radix2_dif_transform) (data, stride, n, sign); return status; } int FUNCTION(gsl_fft_complex,radix2_dif_backward) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n) { gsl_fft_direction sign = gsl_fft_backward; int status = FUNCTION(gsl_fft_complex,radix2_dif_transform) (data, stride, n, sign); return status; } int FUNCTION(gsl_fft_complex,radix2_dif_inverse) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n) { gsl_fft_direction sign = gsl_fft_backward; int status = FUNCTION(gsl_fft_complex,radix2_dif_transform) (data, stride, n, sign); if (status) { return status; } /* normalize inverse fft with 1/n */ { const ATOMIC norm = 1.0 / n; size_t i; for (i = 0; i < n; i++) { REAL(data,stride,i) *= norm; IMAG(data,stride,i) *= norm; } } return status; } int FUNCTION(gsl_fft_complex,radix2_dif_transform) (TYPE(gsl_complex_packed_array) data, const size_t stride, const size_t n, const gsl_fft_direction sign) { int result ; size_t dual; size_t bit; size_t logn = 0; int status; if (n == 1) /* identity operation */ { return 0 ; } /* make sure that n is a power of 2 */ result = fft_binary_logn(n) ; if (result == -1) { GSL_ERROR ("n is not a power of 2", GSL_EINVAL); } else { logn = result ; } /* apply fft recursion */ dual = n / 2; for (bit = 0; bit < logn; bit++) { ATOMIC w_real = 1.0; ATOMIC w_imag = 0.0; const double theta = 2.0 * ((int) sign) * M_PI / ((double) (2 * dual)); const ATOMIC s = sin (theta); const ATOMIC t = sin (theta / 2.0); const ATOMIC s2 = 2.0 * t * t; size_t a, b; for (b = 0; b < dual; b++) { for (a = 0; a < n; a+= 2 * dual) { const size_t i = b + a; const size_t j = b + a + dual; const ATOMIC t1_real = REAL(data,stride,i) + REAL(data,stride,j); const ATOMIC t1_imag = IMAG(data,stride,i) + IMAG(data,stride,j); const ATOMIC t2_real = REAL(data,stride,i) - REAL(data,stride,j); const ATOMIC t2_imag = IMAG(data,stride,i) - IMAG(data,stride,j); REAL(data,stride,i) = t1_real; IMAG(data,stride,i) = t1_imag; REAL(data,stride,j) = w_real*t2_real - w_imag * t2_imag; IMAG(data,stride,j) = w_real*t2_imag + w_imag * t2_real; } /* trignometric recurrence for w-> exp(i theta) w */ { const ATOMIC tmp_real = w_real - s * w_imag - s2 * w_real; const ATOMIC tmp_imag = w_imag + s * w_real - s2 * w_imag; w_real = tmp_real; w_imag = tmp_imag; } } dual /= 2; } /* bit reverse the ordering of output data for decimation in frequency algorithm */ status = FUNCTION(fft_complex,bitreverse_order)(data, stride, n, logn) ; return 0; } sources_5316/external/gsl/gsl_linalg__hessenberg.c0000664000176700017670000003100111723710247021156 0ustar paulpaul/* linalg/hessenberg.c * * Copyright (C) 2006 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_linalg.h" #include "gsl_matrix.h" #include "gsl_vector.h" /* gsl_linalg_hessenberg_decomp() Compute the Householder reduction to Hessenberg form of a square N-by-N matrix A. H = U^t A U See Golub & Van Loan, "Matrix Computations" (3rd ed), algorithm 7.4.2 Inputs: A - matrix to reduce tau - where to store scalar factors in Householder matrices; this vector must be of length N, where N is the order of A Return: GSL_SUCCESS unless error occurs Notes: on output, the upper triangular portion of A (including the diagaonal and subdiagonal) contains the Hessenberg matrix. The lower triangular portion (below the subdiagonal) contains the Householder vectors which can be used to construct the similarity transform matrix U. The matrix U is U = U(1) U(2) ... U(n - 2) where U(i) = I - tau(i) * v(i) * v(i)^t and the vector v(i) is stored in column i of the matrix A underneath the subdiagonal. So the first element of v(i) is stored in row i + 2, column i, the second element at row i + 3, column i, and so on. Also note that for the purposes of computing U(i), v(1:i) = 0, v(i + 1) = 1, and v(i+2:n) is what is stored in column i of A beneath the subdiagonal. */ int gsl_linalg_hessenberg_decomp(gsl_matrix *A, gsl_vector *tau) { const size_t N = A->size1; if (N != A->size2) { GSL_ERROR ("Hessenberg reduction requires square matrix", GSL_ENOTSQR); } else if (N != tau->size) { GSL_ERROR ("tau vector must match matrix size", GSL_EBADLEN); } else if (N < 3) { /* nothing to do */ return GSL_SUCCESS; } else { size_t i; /* looping */ gsl_vector_view c, /* matrix column */ hv; /* householder vector */ gsl_matrix_view m; double tau_i; /* beta in algorithm 7.4.2 */ for (i = 0; i < N - 2; ++i) { /* * make a copy of A(i + 1:n, i) and store it in the section * of 'tau' that we haven't stored coefficients in yet */ c = gsl_matrix_subcolumn(A, i, i + 1, N - i - 1); hv = gsl_vector_subvector(tau, i + 1, N - (i + 1)); gsl_vector_memcpy(&hv.vector, &c.vector); /* compute householder transformation of A(i+1:n,i) */ tau_i = gsl_linalg_householder_transform(&hv.vector); /* apply left householder matrix (I - tau_i v v') to A */ m = gsl_matrix_submatrix(A, i + 1, i, N - (i + 1), N - i); gsl_linalg_householder_hm(tau_i, &hv.vector, &m.matrix); /* apply right householder matrix (I - tau_i v v') to A */ m = gsl_matrix_submatrix(A, 0, i + 1, N, N - (i + 1)); gsl_linalg_householder_mh(tau_i, &hv.vector, &m.matrix); /* save Householder coefficient */ gsl_vector_set(tau, i, tau_i); /* * store Householder vector below the subdiagonal in column * i of the matrix. hv(1) does not need to be stored since * it is always 1. */ c = gsl_vector_subvector(&c.vector, 1, c.vector.size - 1); hv = gsl_vector_subvector(&hv.vector, 1, hv.vector.size - 1); gsl_vector_memcpy(&c.vector, &hv.vector); } return GSL_SUCCESS; } } /* gsl_linalg_hessenberg_decomp() */ /* gsl_linalg_hessenberg_unpack() Construct the matrix U which transforms a matrix A into its upper Hessenberg form: H = U^t A U by unpacking the information stored in H from gsl_linalg_hessenberg(). U is a product of Householder matrices: U = U(1) U(2) ... U(n - 2) where U(i) = I - tau(i) * v(i) * v(i)^t The v(i) are stored in the lower triangular part of H by gsl_linalg_hessenberg(). The tau(i) are stored in the vector tau. Inputs: H - Hessenberg matrix computed from gsl_linalg_hessenberg() tau - tau vector computed from gsl_linalg_hessenberg() U - (output) where to store similarity matrix Return: success or error */ int gsl_linalg_hessenberg_unpack(gsl_matrix * H, gsl_vector * tau, gsl_matrix * U) { int s; gsl_matrix_set_identity(U); s = gsl_linalg_hessenberg_unpack_accum(H, tau, U); return s; } /* gsl_linalg_hessenberg_unpack() */ /* gsl_linalg_hessenberg_unpack_accum() This routine is the same as gsl_linalg_hessenberg_unpack(), except instead of storing the similarity matrix in U, it accumulates it, so that U -> U * [ U(1) U(2) ... U(n - 2) ] instead of: U -> U(1) U(2) ... U(n - 2) Inputs: H - Hessenberg matrix computed from gsl_linalg_hessenberg() tau - tau vector computed from gsl_linalg_hessenberg() V - (input/output) where to accumulate similarity matrix Return: success or error Notes: 1) On input, V needs to be initialized. The Householder matrices are accumulated into V, so on output, V_out = V_in * U(1) * U(2) * ... * U(n - 2) so if you just want the product of the Householder matrices, initialize V to the identity matrix before calling this function. 2) V does not have to be square, but must have the same number of columns as the order of H */ int gsl_linalg_hessenberg_unpack_accum(gsl_matrix * H, gsl_vector * tau, gsl_matrix * V) { const size_t N = H->size1; if (N != H->size2) { GSL_ERROR ("Hessenberg reduction requires square matrix", GSL_ENOTSQR); } else if (N != tau->size) { GSL_ERROR ("tau vector must match matrix size", GSL_EBADLEN); } else if (N != V->size2) { GSL_ERROR ("V matrix has wrong dimension", GSL_EBADLEN); } else { size_t j; /* looping */ double tau_j; /* householder coefficient */ gsl_vector_view c, /* matrix column */ hv; /* householder vector */ gsl_matrix_view m; if (N < 3) { /* nothing to do */ return GSL_SUCCESS; } for (j = 0; j < (N - 2); ++j) { c = gsl_matrix_column(H, j); tau_j = gsl_vector_get(tau, j); /* * get a view to the householder vector in column j, but * make sure hv(2) starts at the element below the * subdiagonal, since hv(1) was never stored and is always * 1 */ hv = gsl_vector_subvector(&c.vector, j + 1, N - (j + 1)); /* * Only operate on part of the matrix since the first * j + 1 entries of the real householder vector are 0 * * V -> V * U(j) * * Note here that V->size1 is not necessarily equal to N */ m = gsl_matrix_submatrix(V, 0, j + 1, V->size1, N - (j + 1)); /* apply right Householder matrix to V */ gsl_linalg_householder_mh(tau_j, &hv.vector, &m.matrix); } return GSL_SUCCESS; } } /* gsl_linalg_hessenberg_unpack_accum() */ /* gsl_linalg_hessenberg_set_zero() Zero out the lower triangular portion of the Hessenberg matrix H. This is useful when Householder vectors may be stored in the lower part of H, but eigenvalue solvers need some scratch space with zeros. */ int gsl_linalg_hessenberg_set_zero(gsl_matrix * H) { const size_t N = H->size1; size_t i, j; if (N < 3) return GSL_SUCCESS; for (j = 0; j < N - 2; ++j) { for (i = j + 2; i < N; ++i) { gsl_matrix_set(H, i, j, 0.0); } } return GSL_SUCCESS; } /* gsl_linalg_hessenberg_set_zero() */ /* gsl_linalg_hessenberg_submatrix() This routine does the same thing as gsl_linalg_hessenberg(), except that it operates on a submatrix of a larger matrix, but updates the larger matrix with the Householder transformations. For example, suppose M = [ M_{11} | M_{12} | M_{13} ] [ 0 | A | M_{23} ] [ 0 | 0 | M_{33} ] where M_{11} and M_{33} are already in Hessenberg form, and we just want to reduce A to Hessenberg form. Applying the transformations to A alone will cause the larger matrix M to lose its similarity information. So this routine updates M_{12} and M_{23} as A gets reduced. Inputs: M - total matrix A - (sub)matrix to reduce top - row index of top of A in M tau - where to store scalar factors in Householder matrices; this vector must be of length N, where N is the order of A Return: GSL_SUCCESS unless error occurs Notes: on output, the upper triangular portion of A (including the diagaonal and subdiagonal) contains the Hessenberg matrix. The lower triangular portion (below the subdiagonal) contains the Householder vectors which can be used to construct the similarity transform matrix U. The matrix U is U = U(1) U(2) ... U(n - 2) where U(i) = I - tau(i) * v(i) * v(i)^t and the vector v(i) is stored in column i of the matrix A underneath the subdiagonal. So the first element of v(i) is stored in row i + 2, column i, the second element at row i + 3, column i, and so on. Also note that for the purposes of computing U(i), v(1:i) = 0, v(i + 1) = 1, and v(i+2:n) is what is stored in column i of A beneath the subdiagonal. */ int gsl_linalg_hessenberg_submatrix(gsl_matrix *M, gsl_matrix *A, size_t top, gsl_vector *tau) { const size_t N = A->size1; const size_t N_M = M->size1; if (N != A->size2) { GSL_ERROR ("Hessenberg reduction requires square matrix", GSL_ENOTSQR); } else if (N != tau->size) { GSL_ERROR ("tau vector must match matrix size", GSL_EBADLEN); } else if (N < 3) { /* nothing to do */ return GSL_SUCCESS; } else { size_t i; /* looping */ gsl_vector_view c, /* matrix column */ hv; /* householder vector */ gsl_matrix_view m; double tau_i; /* beta in algorithm 7.4.2 */ for (i = 0; i < N - 2; ++i) { /* * make a copy of A(i + 1:n, i) and store it in the section * of 'tau' that we haven't stored coefficients in yet */ c = gsl_matrix_subcolumn(A, i, i + 1, N - i - 1); hv = gsl_vector_subvector(tau, i + 1, N - (i + 1)); gsl_vector_memcpy(&hv.vector, &c.vector); /* compute householder transformation of A(i+1:n,i) */ tau_i = gsl_linalg_householder_transform(&hv.vector); /* * apply left householder matrix (I - tau_i v v') to * [ A | M_{23} ] */ m = gsl_matrix_submatrix(M, top + i + 1, top + i, N - (i + 1), N_M - top - i); gsl_linalg_householder_hm(tau_i, &hv.vector, &m.matrix); /* * apply right householder matrix (I - tau_i v v') to * * [ M_{12} ] * [ A ] */ m = gsl_matrix_submatrix(M, 0, top + i + 1, top + N, N - (i + 1)); gsl_linalg_householder_mh(tau_i, &hv.vector, &m.matrix); /* save Householder coefficient */ gsl_vector_set(tau, i, tau_i); /* * store Householder vector below the subdiagonal in column * i of the matrix. hv(1) does not need to be stored since * it is always 1. */ c = gsl_vector_subvector(&c.vector, 1, c.vector.size - 1); hv = gsl_vector_subvector(&hv.vector, 1, hv.vector.size - 1); gsl_vector_memcpy(&c.vector, &hv.vector); } return GSL_SUCCESS; } } /* gsl_linalg_hessenberg_submatrix() */ sources_5316/external/gsl/gsl_fft__signals_source.c0000664000176700017670000001615011723710247021372 0ustar paulpaul/* fft/signals_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl_fft__signals.h" int FUNCTION(fft_signal,complex_pulse) (const size_t k, const size_t n, const size_t stride, const BASE z_real, const BASE z_imag, BASE data[], BASE fft[]) { size_t j; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } /* gsl_complex pulse at position k, data[j] = z * delta_{jk} */ for (j = 0; j < n; j++) { REAL(data,stride,j) = 0.0; IMAG(data,stride,j) = 0.0; } REAL(data,stride,k % n) = z_real; IMAG(data,stride,k % n) = z_imag; /* fourier transform, fft[j] = z * exp(-2 pi i j k / n) */ for (j = 0; j < n; j++) { const double arg = -2 * M_PI * ((double) ((j * k) % n)) / ((double) n); const BASE w_real = (BASE)cos (arg); const BASE w_imag = (BASE)sin (arg); REAL(fft,stride,j) = w_real * z_real - w_imag * z_imag; IMAG(fft,stride,j) = w_real * z_imag + w_imag * z_real; } return 0; } int FUNCTION(fft_signal,complex_constant) (const size_t n, const size_t stride, const BASE z_real, const BASE z_imag, BASE data[], BASE fft[]) { size_t j; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } /* constant, data[j] = z */ for (j = 0; j < n; j++) { REAL(data,stride,j) = z_real; IMAG(data,stride,j) = z_imag; } /* fourier transform, fft[j] = n z delta_{j0} */ for (j = 0; j < n; j++) { REAL(fft,stride,j) = 0.0; IMAG(fft,stride,j) = 0.0; } REAL(fft,stride,0) = ((BASE) n) * z_real; IMAG(fft,stride,0) = ((BASE) n) * z_imag; return 0; } int FUNCTION(fft_signal,complex_exp) (const int k, const size_t n, const size_t stride, const BASE z_real, const BASE z_imag, BASE data[], BASE fft[]) { size_t j; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } /* exponential, data[j] = z * exp(2 pi i j k) */ for (j = 0; j < n; j++) { const double arg = 2 * M_PI * ((double) ((j * k) % n)) / ((double) n); const BASE w_real = (BASE)cos (arg); const BASE w_imag = (BASE)sin (arg); REAL(data,stride,j) = w_real * z_real - w_imag * z_imag; IMAG(data,stride,j) = w_real * z_imag + w_imag * z_real; } /* fourier transform, fft[j] = z * delta{(j - k),0} */ for (j = 0; j < n; j++) { REAL(fft,stride,j) = 0.0; IMAG(fft,stride,j) = 0.0; } { int freq; if (k <= 0) { freq = (n-k) % n ; } else { freq = (k % n); }; REAL(fft,stride,freq) = ((BASE) n) * z_real; IMAG(fft,stride,freq) = ((BASE) n) * z_imag; } return 0; } int FUNCTION(fft_signal,complex_exppair) (const int k1, const int k2, const size_t n, const size_t stride, const BASE z1_real, const BASE z1_imag, const BASE z2_real, const BASE z2_imag, BASE data[], BASE fft[]) { size_t j; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } /* exponential, data[j] = z1 * exp(2 pi i j k1) + z2 * exp(2 pi i j k2) */ for (j = 0; j < n; j++) { const double arg1 = 2 * M_PI * ((double) ((j * k1) % n)) / ((double) n); const BASE w1_real = (BASE)cos (arg1); const BASE w1_imag = (BASE)sin (arg1); const double arg2 = 2 * M_PI * ((double) ((j * k2) % n)) / ((double) n); const BASE w2_real = (BASE)cos (arg2); const BASE w2_imag = (BASE)sin (arg2); REAL(data,stride,j) = w1_real * z1_real - w1_imag * z1_imag; IMAG(data,stride,j) = w1_real * z1_imag + w1_imag * z1_real; REAL(data,stride,j) += w2_real * z2_real - w2_imag * z2_imag; IMAG(data,stride,j) += w2_real * z2_imag + w2_imag * z2_real; } /* fourier transform, fft[j] = z1 * delta{(j - k1),0} + z2 * delta{(j - k2,0)} */ for (j = 0; j < n; j++) { REAL(fft,stride,j) = 0.0; IMAG(fft,stride,j) = 0.0; } { int freq1, freq2; if (k1 <= 0) { freq1 = (n - k1) % n; } else { freq1 = (k1 % n); }; if (k2 <= 0) { freq2 = (n - k2) % n; } else { freq2 = (k2 % n); }; REAL(fft,stride,freq1) += ((BASE) n) * z1_real; IMAG(fft,stride,freq1) += ((BASE) n) * z1_imag; REAL(fft,stride,freq2) += ((BASE) n) * z2_real; IMAG(fft,stride,freq2) += ((BASE) n) * z2_imag; } return 0; } int FUNCTION(fft_signal,complex_noise) (const size_t n, const size_t stride, BASE data[], BASE fft[]) { size_t i; int status; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } for (i = 0; i < n; i++) { REAL(data,stride,i) = (BASE)urand(); IMAG(data,stride,i) = (BASE)urand(); } /* compute the dft */ status = FUNCTION(gsl_dft_complex,forward) (data, stride, n, fft); return status; } int FUNCTION(fft_signal,real_noise) (const size_t n, const size_t stride, BASE data[], BASE fft[]) { size_t i; int status; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } for (i = 0; i < n; i++) { REAL(data,stride,i) = (BASE)urand(); IMAG(data,stride,i) = 0.0; } /* compute the dft */ status = FUNCTION(gsl_dft_complex,forward) (data, stride, n, fft); return status; } sources_5316/external/gsl/gsl_multimin__conjugate_fr.c0000664000176700017670000001475311723710247022106 0ustar paulpaul/* multimin/conjugate_fr.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Fabrice Rossi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* conjugate_fr.c -- Conjugate gradient Fletcher-Reeve algorithm */ /* Modified by Brian Gough to use single iteration structure */ #include "gsl__config.h" #include "gsl_multimin.h" #include "gsl_blas.h" #include "gsl_multimin__directional_minimize.c" typedef struct { int iter; double step; double max_step; double tol; gsl_vector *x1; gsl_vector *dx1; gsl_vector *x2; double pnorm; gsl_vector *p; double g0norm; gsl_vector *g0; } conjugate_fr_state_t; static int conjugate_fr_alloc (void *vstate, size_t n) { conjugate_fr_state_t *state = (conjugate_fr_state_t *) vstate; state->x1 = gsl_vector_calloc (n); if (state->x1 == 0) { GSL_ERROR ("failed to allocate space for x1", GSL_ENOMEM); } state->dx1 = gsl_vector_calloc (n); if (state->dx1 == 0) { gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for dx1", GSL_ENOMEM); } state->x2 = gsl_vector_calloc (n); if (state->x2 == 0) { gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for x2", GSL_ENOMEM); } state->p = gsl_vector_calloc (n); if (state->p == 0) { gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for p", GSL_ENOMEM); } state->g0 = gsl_vector_calloc (n); if (state->g0 == 0) { gsl_vector_free (state->p); gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); GSL_ERROR ("failed to allocate space for g0", GSL_ENOMEM); } return GSL_SUCCESS; } static int conjugate_fr_set (void *vstate, gsl_multimin_function_fdf * fdf, const gsl_vector * x, double *f, gsl_vector * gradient, double step_size, double tol) { conjugate_fr_state_t *state = (conjugate_fr_state_t *) vstate; state->iter = 0; state->step = step_size; state->max_step = step_size; state->tol = tol; GSL_MULTIMIN_FN_EVAL_F_DF (fdf, x, f, gradient); /* Use the gradient as the initial direction */ gsl_vector_memcpy (state->p, gradient); gsl_vector_memcpy (state->g0, gradient); { double gnorm = gsl_blas_dnrm2 (gradient); state->pnorm = gnorm; state->g0norm = gnorm; } return GSL_SUCCESS; } static void conjugate_fr_free (void *vstate) { conjugate_fr_state_t *state = (conjugate_fr_state_t *) vstate; gsl_vector_free (state->g0); gsl_vector_free (state->p); gsl_vector_free (state->x2); gsl_vector_free (state->dx1); gsl_vector_free (state->x1); } static int conjugate_fr_restart (void *vstate) { conjugate_fr_state_t *state = (conjugate_fr_state_t *) vstate; state->iter = 0; return GSL_SUCCESS; } static int conjugate_fr_iterate (void *vstate, gsl_multimin_function_fdf * fdf, gsl_vector * x, double *f, gsl_vector * gradient, gsl_vector * dx) { conjugate_fr_state_t *state = (conjugate_fr_state_t *) vstate; gsl_vector *x1 = state->x1; gsl_vector *dx1 = state->dx1; gsl_vector *x2 = state->x2; gsl_vector *p = state->p; gsl_vector *g0 = state->g0; double pnorm = state->pnorm; double g0norm = state->g0norm; double fa = *f, fb, fc; double dir; double stepa = 0.0, stepb, stepc = state->step, tol = state->tol; double g1norm; double pg; if (pnorm == 0.0 || g0norm == 0.0) { gsl_vector_set_zero (dx); return GSL_ENOPROG; } /* Determine which direction is downhill, +p or -p */ gsl_blas_ddot (p, gradient, &pg); dir = (pg >= 0.0) ? +1.0 : -1.0; /* Compute new trial point at x_c= x - step * p, where p is the current direction */ take_step (x, p, stepc, dir / pnorm, x1, dx); /* Evaluate function and gradient at new point xc */ fc = GSL_MULTIMIN_FN_EVAL_F (fdf, x1); if (fc < fa) { /* Success, reduced the function value */ state->step = stepc * 2.0; *f = fc; gsl_vector_memcpy (x, x1); GSL_MULTIMIN_FN_EVAL_DF (fdf, x1, gradient); return GSL_SUCCESS; } #ifdef DEBUG printf ("got stepc = %g fc = %g\n", stepc, fc); #endif /* Do a line minimisation in the region (xa,fa) (xc,fc) to find an intermediate (xb,fb) satisifying fa > fb < fc. Choose an initial xb based on parabolic interpolation */ intermediate_point (fdf, x, p, dir / pnorm, pg, stepa, stepc, fa, fc, x1, dx1, gradient, &stepb, &fb); if (stepb == 0.0) { return GSL_ENOPROG; } minimize (fdf, x, p, dir / pnorm, stepa, stepb, stepc, fa, fb, fc, tol, x1, dx1, x2, dx, gradient, &(state->step), f, &g1norm); gsl_vector_memcpy (x, x2); /* Choose a new conjugate direction for the next step */ state->iter = (state->iter + 1) % x->size; if (state->iter == 0) { gsl_vector_memcpy (p, gradient); state->pnorm = g1norm; } else { /* p' = g1 - beta * p */ double beta = -pow (g1norm / g0norm, 2.0); gsl_blas_dscal (-beta, p); gsl_blas_daxpy (1.0, gradient, p); state->pnorm = gsl_blas_dnrm2 (p); } state->g0norm = g1norm; gsl_vector_memcpy (g0, gradient); #ifdef DEBUG printf ("updated conjugate directions\n"); printf ("p: "); gsl_vector_fprintf (stdout, p, "%g"); printf ("g: "); gsl_vector_fprintf (stdout, gradient, "%g"); #endif return GSL_SUCCESS; } static const gsl_multimin_fdfminimizer_type conjugate_fr_type = { "conjugate_fr", /* name */ sizeof (conjugate_fr_state_t), &conjugate_fr_alloc, &conjugate_fr_set, &conjugate_fr_iterate, &conjugate_fr_restart, &conjugate_fr_free }; const gsl_multimin_fdfminimizer_type * gsl_multimin_fdfminimizer_conjugate_fr = &conjugate_fr_type; sources_5316/external/gsl/gsl_sort_short.h0000664000176700017670000000352211705263724017571 0ustar paulpaul/* sort/gsl_sort_short.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_SHORT_H__ #define __GSL_SORT_SHORT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_short (short * data, const size_t stride, const size_t n); void gsl_sort_short_index (size_t * p, const short * data, const size_t stride, const size_t n); int gsl_sort_short_smallest (short * dest, const size_t k, const short * src, const size_t stride, const size_t n); int gsl_sort_short_smallest_index (size_t * p, const size_t k, const short * src, const size_t stride, const size_t n); int gsl_sort_short_largest (short * dest, const size_t k, const short * src, const size_t stride, const size_t n); int gsl_sort_short_largest_index (size_t * p, const size_t k, const short * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_SHORT_H__ */ sources_5316/external/gsl/gsl_sf__result.c0000644000176700017670000000452610707442037017523 0ustar paulpaul/* specfunc/result.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_result.h" int gsl_sf_result_smash_e(const gsl_sf_result_e10 * re, gsl_sf_result * r) { if(re->e10 == 0) { /* nothing to smash */ r->val = re->val; r->err = re->err; return GSL_SUCCESS; } else { const double av = fabs(re->val); const double ae = fabs(re->err); if( GSL_SQRT_DBL_MIN < av && av < GSL_SQRT_DBL_MAX && GSL_SQRT_DBL_MIN < ae && ae < GSL_SQRT_DBL_MAX && 0.49*GSL_LOG_DBL_MIN < re->e10 && re->e10 < 0.49*GSL_LOG_DBL_MAX ) { const double scale = exp(re->e10 * M_LN10); r->val = re->val * scale; r->err = re->err * scale; return GSL_SUCCESS; } else { return gsl_sf_exp_mult_err_e(re->e10*M_LN10, 0.0, re->val, re->err, r); } } /* int stat_v; int stat_e; if(re->val == 0.0) { r->val = 0.0; stat_v = GSL_SUCCESS; } else { gsl_sf_result r_val; const double s = GSL_SIGN(re->val); const double x_v = re->e10*M_LN10 + log(fabs(re->val)); stat_v = gsl_sf_exp_e(x_v, &r_val); r->val = s * r_val.val; } if(re->err == 0.0) { r->err = 0.0; stat_e = GSL_SUCCESS; } else if(re->val != 0.0) { r->err = fabs(r->val * re->err/re->val); stat_e = GSL_SUCCESS; } else { gsl_sf_result r_err; const double x_e = re->e10*M_LN10 + log(fabs(re->err)); stat_e = gsl_sf_exp_e(x_e, &r_err); r->err = r_err.val; } return GSL_ERROR_SELECT_2(stat_v, stat_e); */ } sources_5316/external/gsl/gsl_rng__ran3.c0000664000176700017670000000571211723710247017226 0ustar paulpaul/* rng/ran3.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is an implementation of the algorithm used in Knuths's subtractive generator, with the Numerical Recipe's ran3 paramters. It is a subtractive lagged fibonnaci generator. */ static inline unsigned long int ran3_get (void *vstate); static double ran3_get_double (void *vstate); static void ran3_set (void *state, unsigned long int s); #define M_BIG 1000000000 #define M_SEED 161803398 typedef struct { unsigned int x; unsigned int y; unsigned long int buffer[56]; } ran3_state_t; static inline unsigned long int ran3_get (void *vstate) { ran3_state_t *state = (ran3_state_t *) vstate; long int j; state->x++; if (state->x == 56) state->x = 1; state->y++; if (state->y == 56) state->y = 1; j = state->buffer[state->x] - state->buffer[state->y]; if (j < 0) j += M_BIG; state->buffer[state->x] = j; return j; } static double ran3_get_double (void *vstate) { return ran3_get (vstate) / (double) M_BIG ; } static void ran3_set (void *vstate, unsigned long int s) { ran3_state_t *state = (ran3_state_t *) vstate; int i, i1; long int j, k; if (s == 0) s = 1; /* default seed is 1 */ j = (M_SEED - s) % M_BIG; /* the zeroth element is never used, but we initialize it for consistency between states */ state->buffer[0] = 0; state->buffer[55] = j; k = 1; for (i = 1; i < 55; i++) { int n = (21 * i) % 55; state->buffer[n] = k; k = j - k; if (k < 0) k += M_BIG; j = state->buffer[n]; } for (i1 = 0; i1 < 4; i1++) { for (i = 1; i < 56; i++) { long int t = state->buffer[i] - state->buffer[1 + (i + 30) % 55]; if (t < 0) t += M_BIG; state->buffer[i] = t; } } state->x = 0; state->y = 31; return; } static const gsl_rng_type ran3_type = {"ran3", /* name */ M_BIG, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ran3_state_t), &ran3_set, &ran3_get, &ran3_get_double}; const gsl_rng_type *gsl_rng_ran3 = &ran3_type; sources_5316/external/gsl/gsl_randist__logistic.c0000664000176700017670000000257111723710247021056 0ustar paulpaul/* randist/logistic.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* The logistic distribution has the form, p(x) dx = (1/a) exp(-x/a) / (1 + exp(-x/a))^2 dx for -infty < x < infty */ double gsl_ran_logistic (const gsl_rng * r, const double a) { double x, z; do { x = gsl_rng_uniform_pos (r); } while (x == 1); z = log (x / (1 - x)); return a * z; } double gsl_ran_logistic_pdf (const double x, const double a) { double u = exp (-fabs(x)/a); double p = u / (fabs(a) * (1 + u) * (1 + u)); return p; } sources_5316/external/gsl/gsl_integration__qng.h0000664000176700017670000001543511705263724020720 0ustar paulpaul/* integration/qng.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Gauss-Kronrod-Patterson quadrature coefficients for use in quadpack routine qng. These coefficients were calculated with 101 decimal digit arithmetic by L. W. Fullerton, Bell Labs, Nov 1981. */ /* x1, abscissae common to the 10-, 21-, 43- and 87-point rule */ static const double x1[5] = { 0.973906528517171720077964012084452, 0.865063366688984510732096688423493, 0.679409568299024406234327365114874, 0.433395394129247190799265943165784, 0.148874338981631210884826001129720 } ; /* w10, weights of the 10-point formula */ static const double w10[5] = { 0.066671344308688137593568809893332, 0.149451349150580593145776339657697, 0.219086362515982043995534934228163, 0.269266719309996355091226921569469, 0.295524224714752870173892994651338 } ; /* x2, abscissae common to the 21-, 43- and 87-point rule */ static const double x2[5] = { 0.995657163025808080735527280689003, 0.930157491355708226001207180059508, 0.780817726586416897063717578345042, 0.562757134668604683339000099272694, 0.294392862701460198131126603103866 } ; /* w21a, weights of the 21-point formula for abscissae x1 */ static const double w21a[5] = { 0.032558162307964727478818972459390, 0.075039674810919952767043140916190, 0.109387158802297641899210590325805, 0.134709217311473325928054001771707, 0.147739104901338491374841515972068 } ; /* w21b, weights of the 21-point formula for abscissae x2 */ static const double w21b[6] = { 0.011694638867371874278064396062192, 0.054755896574351996031381300244580, 0.093125454583697605535065465083366, 0.123491976262065851077958109831074, 0.142775938577060080797094273138717, 0.149445554002916905664936468389821 } ; /* x3, abscissae common to the 43- and 87-point rule */ static const double x3[11] = { 0.999333360901932081394099323919911, 0.987433402908088869795961478381209, 0.954807934814266299257919200290473, 0.900148695748328293625099494069092, 0.825198314983114150847066732588520, 0.732148388989304982612354848755461, 0.622847970537725238641159120344323, 0.499479574071056499952214885499755, 0.364901661346580768043989548502644, 0.222254919776601296498260928066212, 0.074650617461383322043914435796506 } ; /* w43a, weights of the 43-point formula for abscissae x1, x3 */ static const double w43a[10] = { 0.016296734289666564924281974617663, 0.037522876120869501461613795898115, 0.054694902058255442147212685465005, 0.067355414609478086075553166302174, 0.073870199632393953432140695251367, 0.005768556059769796184184327908655, 0.027371890593248842081276069289151, 0.046560826910428830743339154433824, 0.061744995201442564496240336030883, 0.071387267268693397768559114425516 } ; /* w43b, weights of the 43-point formula for abscissae x3 */ static const double w43b[12] = { 0.001844477640212414100389106552965, 0.010798689585891651740465406741293, 0.021895363867795428102523123075149, 0.032597463975345689443882222526137, 0.042163137935191811847627924327955, 0.050741939600184577780189020092084, 0.058379395542619248375475369330206, 0.064746404951445885544689259517511, 0.069566197912356484528633315038405, 0.072824441471833208150939535192842, 0.074507751014175118273571813842889, 0.074722147517403005594425168280423 } ; /* x4, abscissae of the 87-point rule */ static const double x4[22] = { 0.999902977262729234490529830591582, 0.997989895986678745427496322365960, 0.992175497860687222808523352251425, 0.981358163572712773571916941623894, 0.965057623858384619128284110607926, 0.943167613133670596816416634507426, 0.915806414685507209591826430720050, 0.883221657771316501372117548744163, 0.845710748462415666605902011504855, 0.803557658035230982788739474980964, 0.757005730685495558328942793432020, 0.706273209787321819824094274740840, 0.651589466501177922534422205016736, 0.593223374057961088875273770349144, 0.531493605970831932285268948562671, 0.466763623042022844871966781659270, 0.399424847859218804732101665817923, 0.329874877106188288265053371824597, 0.258503559202161551802280975429025, 0.185695396568346652015917141167606, 0.111842213179907468172398359241362, 0.037352123394619870814998165437704 } ; /* w87a, weights of the 87-point formula for abscissae x1, x2, x3 */ static const double w87a[21] = { 0.008148377384149172900002878448190, 0.018761438201562822243935059003794, 0.027347451050052286161582829741283, 0.033677707311637930046581056957588, 0.036935099820427907614589586742499, 0.002884872430211530501334156248695, 0.013685946022712701888950035273128, 0.023280413502888311123409291030404, 0.030872497611713358675466394126442, 0.035693633639418770719351355457044, 0.000915283345202241360843392549948, 0.005399280219300471367738743391053, 0.010947679601118931134327826856808, 0.016298731696787335262665703223280, 0.021081568889203835112433060188190, 0.025370969769253827243467999831710, 0.029189697756475752501446154084920, 0.032373202467202789685788194889595, 0.034783098950365142750781997949596, 0.036412220731351787562801163687577, 0.037253875503047708539592001191226 } ; /* w87b, weights of the 87-point formula for abscissae x4 */ static const double w87b[23] = { 0.000274145563762072350016527092881, 0.001807124155057942948341311753254, 0.004096869282759164864458070683480, 0.006758290051847378699816577897424, 0.009549957672201646536053581325377, 0.012329447652244853694626639963780, 0.015010447346388952376697286041943, 0.017548967986243191099665352925900, 0.019938037786440888202278192730714, 0.022194935961012286796332102959499, 0.024339147126000805470360647041454, 0.026374505414839207241503786552615, 0.028286910788771200659968002987960, 0.030052581128092695322521110347341, 0.031646751371439929404586051078883, 0.033050413419978503290785944862689, 0.034255099704226061787082821046821, 0.035262412660156681033782717998428, 0.036076989622888701185500318003895, 0.036698604498456094498018047441094, 0.037120549269832576114119958413599, 0.037334228751935040321235449094698, 0.037361073762679023410321241766599 } ; sources_5316/external/gsl/gsl_fft__real_unpack.c0000664000176700017670000000246511723710247020642 0ustar paulpaul/* fft/real_unpack.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl_fft__complex_internal.h" int FUNCTION(gsl_fft_real,unpack) (const BASE real_coefficient[], BASE complex_coefficient[], const size_t stride, const size_t n) { size_t i; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } for (i = 0; i < n; i++) { REAL(complex_coefficient,stride,i) = real_coefficient[i * stride]; IMAG(complex_coefficient,stride,i) = 0.0; } return 0; } sources_5316/external/gsl/gsl_wavelet__wavelet.c0000664000176700017670000000604311723710247020711 0ustar paulpaul/* wavelet/wavelet.c * * Copyright (C) 2004 Ivo Alxneit * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_wavelet.h" gsl_wavelet * gsl_wavelet_alloc (const gsl_wavelet_type * T, size_t k) { int status; gsl_wavelet *w = (gsl_wavelet *) malloc (sizeof (gsl_wavelet)); if (w == NULL) { GSL_ERROR_VAL ("failed to allocate space for wavelet struct", GSL_ENOMEM, 0); }; w->type = T; status = (T->init) (&(w->h1), &(w->g1), &(w->h2), &(w->g2), &(w->nc), &(w->offset), k); if (status) { free (w); GSL_ERROR_VAL ("invalid wavelet member", GSL_EINVAL, 0); } return w; } void gsl_wavelet_free (gsl_wavelet * w) { free (w); } const char * gsl_wavelet_name (const gsl_wavelet * w) { return w->type->name; } /* Let's not export this for now (BJG) */ #if 0 void gsl_wavelet_print (const gsl_wavelet * w) { size_t n = w->nc; size_t i; printf ("Wavelet type: %s\n", w->type->name); printf (" h1(%d):%12.8f g1(%d):%12.8f h2(%d):%12.8f g2(%d):%12.8f\n", 0, w->h1[0], 0, w->g1[0], 0, w->h2[0], 0, w->g2[0]); for (i = 1; i < (n < 10 ? n : 10); i++) { printf (" h1(%d):%12.8f g1(%d):%12.8f h2(%d):%12.8f g2(%d):%12.8f\n", i, w->h1[i], i, w->g1[i], i, w->h2[i], i, w->g2[i]); } for (; i < n; i++) { printf ("h1(%d):%12.8f g1(%d):%12.8f h2(%d):%12.8f g2(%d):%12.8f\n", i, w->h1[i], i, w->g1[i], i, w->h2[i], i, w->g2[i]); } } #endif gsl_wavelet_workspace * gsl_wavelet_workspace_alloc (size_t n) { gsl_wavelet_workspace *work; if (n == 0) { GSL_ERROR_VAL ("length n must be positive integer", GSL_EDOM, 0); } work = (gsl_wavelet_workspace *) malloc (sizeof (gsl_wavelet_workspace)); if (work == NULL) { GSL_ERROR_VAL ("failed to allocate struct", GSL_ENOMEM, 0); } work->n = n; work->scratch = (double *) malloc (n * sizeof (double)); if (work->scratch == NULL) { /* error in constructor, prevent memory leak */ free (work); GSL_ERROR_VAL ("failed to allocate scratch space", GSL_ENOMEM, 0); } return work; } void gsl_wavelet_workspace_free (gsl_wavelet_workspace * work) { /* release scratch space */ free (work->scratch); work->scratch = NULL; free (work); } sources_5316/external/gsl/gsl_ieee-utils__fp-unknown.c0000664000176700017670000000212611723710247021740 0ustar paulpaul/* ieee-utils/fp-unknown.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { GSL_ERROR ( "the IEEE interface for this platform is unsupported or could not be " "determined at configure time\n", GSL_EUNSUP) ; } sources_5316/external/gsl/gsl_complex.h0000664000176700017670000000645611705263724017043 0ustar paulpaul/* complex/gsl_complex.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_COMPLEX_H__ #define __GSL_COMPLEX_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* two consecutive built-in types as a complex number */ typedef double * gsl_complex_packed ; typedef float * gsl_complex_packed_float ; typedef long double * gsl_complex_packed_long_double ; typedef const double * gsl_const_complex_packed ; typedef const float * gsl_const_complex_packed_float ; typedef const long double * gsl_const_complex_packed_long_double ; /* 2N consecutive built-in types as N complex numbers */ typedef double * gsl_complex_packed_array ; typedef float * gsl_complex_packed_array_float ; typedef long double * gsl_complex_packed_array_long_double ; typedef const double * gsl_const_complex_packed_array ; typedef const float * gsl_const_complex_packed_array_float ; typedef const long double * gsl_const_complex_packed_array_long_double ; /* Yes... this seems weird. Trust us. The point is just that sometimes you want to make it obvious that something is an output value. The fact that it lacks a 'const' may not be enough of a clue for people in some contexts. */ typedef double * gsl_complex_packed_ptr ; typedef float * gsl_complex_packed_float_ptr ; typedef long double * gsl_complex_packed_long_double_ptr ; typedef const double * gsl_const_complex_packed_ptr ; typedef const float * gsl_const_complex_packed_float_ptr ; typedef const long double * gsl_const_complex_packed_long_double_ptr ; typedef struct { long double dat[2]; } gsl_complex_long_double; typedef struct { double dat[2]; } gsl_complex; typedef struct { float dat[2]; } gsl_complex_float; #define GSL_REAL(z) ((z).dat[0]) #define GSL_IMAG(z) ((z).dat[1]) #define GSL_COMPLEX_P(zp) ((zp)->dat) #define GSL_COMPLEX_P_REAL(zp) ((zp)->dat[0]) #define GSL_COMPLEX_P_IMAG(zp) ((zp)->dat[1]) #define GSL_COMPLEX_EQ(z1,z2) (((z1).dat[0] == (z2).dat[0]) && ((z1).dat[1] == (z2).dat[1])) #define GSL_SET_COMPLEX(zp,x,y) do {(zp)->dat[0]=(x); (zp)->dat[1]=(y);} while(0) #define GSL_SET_REAL(zp,x) do {(zp)->dat[0]=(x);} while(0) #define GSL_SET_IMAG(zp,y) do {(zp)->dat[1]=(y);} while(0) #define GSL_SET_COMPLEX_PACKED(zp,n,x,y) do {*((zp)+2*(n))=(x); *((zp)+(2*(n)+1))=(y);} while(0) __END_DECLS #endif /* __GSL_COMPLEX_H__ */ sources_5316/external/gsl/gsl_message.h0000664000176700017670000000456011705263724017012 0ustar paulpaul/* err/gsl_message.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MESSAGE_H__ #define __GSL_MESSAGE_H__ #include "gsl_types.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Provide a general messaging service for client use. Messages can * be selectively turned off at compile time by defining an * appropriate message mask. Client code which uses the GSL_MESSAGE() * macro must provide a mask which is or'ed with the GSL_MESSAGE_MASK. * * The messaging service can be completely turned off * by defining GSL_MESSAGING_OFF. */ void gsl_message(const char * message, const char * file, int line, unsigned int mask); #ifndef GSL_MESSAGE_MASK #define GSL_MESSAGE_MASK 0xffffffffu /* default all messages allowed */ #endif GSL_VAR unsigned int gsl_message_mask ; /* Provide some symolic masks for client ease of use. */ enum { GSL_MESSAGE_MASK_A = 1, GSL_MESSAGE_MASK_B = 2, GSL_MESSAGE_MASK_C = 4, GSL_MESSAGE_MASK_D = 8, GSL_MESSAGE_MASK_E = 16, GSL_MESSAGE_MASK_F = 32, GSL_MESSAGE_MASK_G = 64, GSL_MESSAGE_MASK_H = 128 } ; #ifdef GSL_MESSAGING_OFF /* throw away messages */ #define GSL_MESSAGE(message, mask) do { } while(0) #else /* output all messages */ #define GSL_MESSAGE(message, mask) \ do { \ if (mask & GSL_MESSAGE_MASK) \ gsl_message (message, __FILE__, __LINE__, mask) ; \ } while (0) #endif __END_DECLS #endif /* __GSL_MESSAGE_H__ */ sources_5316/external/gsl/gsl_test.h0000664000176700017670000000347211705263724016346 0ustar paulpaul/* err/gsl_test.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_TEST_H__ #define __GSL_TEST_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_test (int status, const char *test_description, ...); void gsl_test_rel (double result, double expected, double relative_error, const char *test_description, ...) ; void gsl_test_abs (double result, double expected, double absolute_error, const char *test_description, ...) ; void gsl_test_factor (double result, double expected, double factor, const char *test_description, ...) ; void gsl_test_int (int result, int expected, const char *test_description, ...) ; void gsl_test_str (const char * result, const char * expected, const char *test_description, ...) ; void gsl_test_verbose (int verbose) ; int gsl_test_summary (void) ; __END_DECLS #endif /* __GSL_TEST_H__ */ sources_5316/external/gsl/gsl_cblas__ctrsv.c0000664000176700017670000000065211723710247020020 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" #include "gsl_cblas__hypot.c" void cblas_ctrsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const void *A, const int lda, void *X, const int incX) { #define BASE float #include "gsl_cblas__source_trsv_c.h" #undef BASE } sources_5316/external/gsl/gsl_rng__knuthran2002.c0000664000176700017670000001143111723710247020514 0ustar paulpaul/* rng/knuthran2002.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 2001, 2007 Brian Gough, Carlo Perassi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth, The Art of Computer Programming, Volume 2, Section 3.6 * Third Edition, Addison-Wesley, * * The modifications introduced in the 9th printing (2002) are * included here; there's no backwards compatibility with the * original. [ see http://www-cs-faculty.stanford.edu/~knuth/taocp.html ] * */ #include "gsl__config.h" #include #include "gsl_rng.h" #define BUFLEN 1009 /* length of the buffer aa[] */ #define KK 100 /* the long lag */ #define LL 37 /* the short lag */ #define MM (1L << 30) /* the modulus */ #define TT 70 /* guaranteed separation between streams */ #define is_odd(x) ((x) & 1) /* the units bit of x */ #define mod_diff(x, y) (((x) - (y)) & (MM - 1)) /* (x - y) mod MM */ static inline void ran_array (long int aa[], unsigned int n, long int ran_x[]); static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); typedef struct { unsigned int i; long int aa[BUFLEN]; long int ran_x[KK]; /* the generator state */ } ran_state_t; static inline void ran_array (long int aa[], unsigned int n, long int ran_x[]) { unsigned int i; unsigned int j; for (j = 0; j < KK; j++) aa[j] = ran_x[j]; for (; j < n; j++) aa[j] = mod_diff (aa[j - KK], aa[j - LL]); for (i = 0; i < LL; i++, j++) ran_x[i] = mod_diff (aa[j - KK], aa[j - LL]); for (; i < KK; i++, j++) ran_x[i] = mod_diff (aa[j - KK], ran_x[i - LL]); } static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; unsigned int i = state->i; unsigned long int v; if (i == 0) { /* fill buffer with new random numbers */ ran_array (state->aa, BUFLEN, state->ran_x); } v = state->aa[i]; state->i = (i + 1) % KK; return v; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 1073741824.0; /* RAND_MAX + 1 */ } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; long x[KK + KK - 1]; /* the preparation buffer */ register int j; register int t; register long ss; if (s == 0 ) s = 314159; /* default seed used by Knuth */ ss = (s + 2)&(MM-2); for (j = 0; j < KK; j++) { x[j] = ss; /* bootstrap the buffer */ ss <<= 1; if (ss >= MM) /* cyclic shift 29 bits */ ss -= MM - 2; } x[1]++; /* make x[1] (and only x[1]) odd */ ss = s & (MM - 1); t = TT - 1; while (t) { for (j = KK - 1; j > 0; j--) /* square */ { x[j + j] = x[j]; x[j + j - 1] = 0; } for (j = KK + KK - 2; j >= KK; j--) { x[j - (KK - LL)] = mod_diff (x[j - (KK - LL)], x[j]); x[j - KK] = mod_diff (x[j - KK], x[j]); } if (is_odd (ss)) { /* multiply by "z" */ for (j = KK; j > 0; j--) { x[j] = x[j - 1]; } x[0] = x[KK]; /* shift the buffer cyclically */ x[LL] = mod_diff (x[LL], x[KK]); } if (ss) ss >>= 1; else t--; } for (j = 0; j < LL; j++) state->ran_x[j + KK - LL] = x[j]; for (; j < KK; j++) state->ran_x[j - LL] = x[j]; for (j = 0; j< 10; j++) ran_array(x, KK+KK-1, state->ran_x); /* warm things up */ state->i = 0; return; } static const gsl_rng_type ran_type = { "knuthran2002", /* name */ 0x3fffffffUL, /* RAND_MAX = (2 ^ 30) - 1 */ 0, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_knuthran2002 = &ran_type; sources_5316/external/gsl/gsl_vector__oper_source.c0000664000176700017670000000623111723710247021421 0ustar paulpaul/* vector/oper_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION(gsl_vector, add) (TYPE(gsl_vector) * a, const TYPE(gsl_vector) * b) { const size_t N = a->size; if (b->size != N) { GSL_ERROR ("vectors must have same length", GSL_EBADLEN); } else { const size_t stride_a = a->stride; const size_t stride_b = b->stride; size_t i; for (i = 0; i < N; i++) { a->data[i * stride_a] += b->data[i * stride_b]; } return GSL_SUCCESS; } } int FUNCTION(gsl_vector, sub) (TYPE(gsl_vector) * a, const TYPE(gsl_vector) * b) { const size_t N = a->size; if (b->size != N) { GSL_ERROR ("vectors must have same length", GSL_EBADLEN); } else { const size_t stride_a = a->stride; const size_t stride_b = b->stride; size_t i; for (i = 0; i < N; i++) { a->data[i * stride_a] -= b->data[i * stride_b]; } return GSL_SUCCESS; } } int FUNCTION(gsl_vector, mul) (TYPE(gsl_vector) * a, const TYPE(gsl_vector) * b) { const size_t N = a->size; if (b->size != N) { GSL_ERROR ("vectors must have same length", GSL_EBADLEN); } else { const size_t stride_a = a->stride; const size_t stride_b = b->stride; size_t i; for (i = 0; i < N; i++) { a->data[i * stride_a] *= b->data[i * stride_b]; } return GSL_SUCCESS; } } int FUNCTION(gsl_vector, div) (TYPE(gsl_vector) * a, const TYPE(gsl_vector) * b) { const size_t N = a->size; if (b->size != N) { GSL_ERROR ("vectors must have same length", GSL_EBADLEN); } else { const size_t stride_a = a->stride; const size_t stride_b = b->stride; size_t i; for (i = 0; i < N; i++) { a->data[i * stride_a] /= b->data[i * stride_b]; } return GSL_SUCCESS; } } int FUNCTION(gsl_vector, scale) (TYPE(gsl_vector) * a, const double x) { const size_t N = a->size; const size_t stride = a->stride; size_t i; for (i = 0; i < N; i++) { a->data[i * stride] *= x; } return GSL_SUCCESS; } int FUNCTION(gsl_vector, add_constant) (TYPE(gsl_vector) * a, const double x) { const size_t N = a->size; const size_t stride = a->stride; size_t i; for (i = 0; i < N; i++) { a->data[i * stride] += x; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_linalg__svd.c0000664000176700017670000004202611723710247017636 0ustar paulpaul/* linalg/svd.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2004, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_linalg.h" #include "gsl_linalg__givens.c" #include "gsl_linalg__svdstep.c" /* Factorise a general M x N matrix A into, * * A = U D V^T * * where U is a column-orthogonal M x N matrix (U^T U = I), * D is a diagonal N x N matrix, * and V is an N x N orthogonal matrix (V^T V = V V^T = I) * * U is stored in the original matrix A, which has the same size * * V is stored as a separate matrix (not V^T). You must take the * transpose to form the product above. * * The diagonal matrix D is stored in the vector S, D_ii = S_i */ int gsl_linalg_SV_decomp (gsl_matrix * A, gsl_matrix * V, gsl_vector * S, gsl_vector * work) { size_t a, b, i, j, iter; const size_t M = A->size1; const size_t N = A->size2; const size_t K = GSL_MIN (M, N); if (M < N) { GSL_ERROR ("svd of MxN matrix, Msize1 != N) { GSL_ERROR ("square matrix V must match second dimension of matrix A", GSL_EBADLEN); } else if (V->size1 != V->size2) { GSL_ERROR ("matrix V must be square", GSL_ENOTSQR); } else if (S->size != N) { GSL_ERROR ("length of vector S must match second dimension of matrix A", GSL_EBADLEN); } else if (work->size != N) { GSL_ERROR ("length of workspace must match second dimension of matrix A", GSL_EBADLEN); } /* Handle the case of N = 1 (SVD of a column vector) */ if (N == 1) { gsl_vector_view column = gsl_matrix_column (A, 0); double norm = gsl_blas_dnrm2 (&column.vector); gsl_vector_set (S, 0, norm); gsl_matrix_set (V, 0, 0, 1.0); if (norm != 0.0) { gsl_blas_dscal (1.0/norm, &column.vector); } return GSL_SUCCESS; } { gsl_vector_view f = gsl_vector_subvector (work, 0, K - 1); /* bidiagonalize matrix A, unpack A into U S V */ gsl_linalg_bidiag_decomp (A, S, &f.vector); gsl_linalg_bidiag_unpack2 (A, S, &f.vector, V); /* apply reduction steps to B=(S,Sd) */ chop_small_elements (S, &f.vector); /* Progressively reduce the matrix until it is diagonal */ b = N - 1; iter = 0; while (b > 0) { double fbm1 = gsl_vector_get (&f.vector, b - 1); if (fbm1 == 0.0 || gsl_isnan (fbm1)) { b--; continue; } /* Find the largest unreduced block (a,b) starting from b and working backwards */ a = b - 1; while (a > 0) { double fam1 = gsl_vector_get (&f.vector, a - 1); if (fam1 == 0.0 || gsl_isnan (fam1)) { break; } a--; } iter++; if (iter > 100 * N) { GSL_ERROR("SVD decomposition failed to converge", GSL_EMAXITER); } { const size_t n_block = b - a + 1; gsl_vector_view S_block = gsl_vector_subvector (S, a, n_block); gsl_vector_view f_block = gsl_vector_subvector (&f.vector, a, n_block - 1); gsl_matrix_view U_block = gsl_matrix_submatrix (A, 0, a, A->size1, n_block); gsl_matrix_view V_block = gsl_matrix_submatrix (V, 0, a, V->size1, n_block); qrstep (&S_block.vector, &f_block.vector, &U_block.matrix, &V_block.matrix); /* remove any small off-diagonal elements */ chop_small_elements (&S_block.vector, &f_block.vector); } } } /* Make singular values positive by reflections if necessary */ for (j = 0; j < K; j++) { double Sj = gsl_vector_get (S, j); if (Sj < 0.0) { for (i = 0; i < N; i++) { double Vij = gsl_matrix_get (V, i, j); gsl_matrix_set (V, i, j, -Vij); } gsl_vector_set (S, j, -Sj); } } /* Sort singular values into decreasing order */ for (i = 0; i < K; i++) { double S_max = gsl_vector_get (S, i); size_t i_max = i; for (j = i + 1; j < K; j++) { double Sj = gsl_vector_get (S, j); if (Sj > S_max) { S_max = Sj; i_max = j; } } if (i_max != i) { /* swap eigenvalues */ gsl_vector_swap_elements (S, i, i_max); /* swap eigenvectors */ gsl_matrix_swap_columns (A, i, i_max); gsl_matrix_swap_columns (V, i, i_max); } } return GSL_SUCCESS; } /* Modified algorithm which is better for M>>N */ int gsl_linalg_SV_decomp_mod (gsl_matrix * A, gsl_matrix * X, gsl_matrix * V, gsl_vector * S, gsl_vector * work) { size_t i, j; const size_t M = A->size1; const size_t N = A->size2; if (M < N) { GSL_ERROR ("svd of MxN matrix, Msize1 != N) { GSL_ERROR ("square matrix V must match second dimension of matrix A", GSL_EBADLEN); } else if (V->size1 != V->size2) { GSL_ERROR ("matrix V must be square", GSL_ENOTSQR); } else if (X->size1 != N) { GSL_ERROR ("square matrix X must match second dimension of matrix A", GSL_EBADLEN); } else if (X->size1 != X->size2) { GSL_ERROR ("matrix X must be square", GSL_ENOTSQR); } else if (S->size != N) { GSL_ERROR ("length of vector S must match second dimension of matrix A", GSL_EBADLEN); } else if (work->size != N) { GSL_ERROR ("length of workspace must match second dimension of matrix A", GSL_EBADLEN); } if (N == 1) { gsl_vector_view column = gsl_matrix_column (A, 0); double norm = gsl_blas_dnrm2 (&column.vector); gsl_vector_set (S, 0, norm); gsl_matrix_set (V, 0, 0, 1.0); if (norm != 0.0) { gsl_blas_dscal (1.0/norm, &column.vector); } return GSL_SUCCESS; } /* Convert A into an upper triangular matrix R */ for (i = 0; i < N; i++) { gsl_vector_view c = gsl_matrix_column (A, i); gsl_vector_view v = gsl_vector_subvector (&c.vector, i, M - i); double tau_i = gsl_linalg_householder_transform (&v.vector); /* Apply the transformation to the remaining columns */ if (i + 1 < N) { gsl_matrix_view m = gsl_matrix_submatrix (A, i, i + 1, M - i, N - (i + 1)); gsl_linalg_householder_hm (tau_i, &v.vector, &m.matrix); } gsl_vector_set (S, i, tau_i); } /* Copy the upper triangular part of A into X */ for (i = 0; i < N; i++) { for (j = 0; j < i; j++) { gsl_matrix_set (X, i, j, 0.0); } { double Aii = gsl_matrix_get (A, i, i); gsl_matrix_set (X, i, i, Aii); } for (j = i + 1; j < N; j++) { double Aij = gsl_matrix_get (A, i, j); gsl_matrix_set (X, i, j, Aij); } } /* Convert A into an orthogonal matrix L */ for (j = N; j > 0 && j--;) { /* Householder column transformation to accumulate L */ double tj = gsl_vector_get (S, j); gsl_matrix_view m = gsl_matrix_submatrix (A, j, j, M - j, N - j); gsl_linalg_householder_hm1 (tj, &m.matrix); } /* unpack R into X V S */ gsl_linalg_SV_decomp (X, V, S, work); /* Multiply L by X, to obtain U = L X, stored in U */ { gsl_vector_view sum = gsl_vector_subvector (work, 0, N); for (i = 0; i < M; i++) { gsl_vector_view L_i = gsl_matrix_row (A, i); gsl_vector_set_zero (&sum.vector); for (j = 0; j < N; j++) { double Lij = gsl_vector_get (&L_i.vector, j); gsl_vector_view X_j = gsl_matrix_row (X, j); gsl_blas_daxpy (Lij, &X_j.vector, &sum.vector); } gsl_vector_memcpy (&L_i.vector, &sum.vector); } } return GSL_SUCCESS; } /* Solves the system A x = b using the SVD factorization * * A = U S V^T * * to obtain x. For M x N systems it finds the solution in the least * squares sense. */ int gsl_linalg_SV_solve (const gsl_matrix * U, const gsl_matrix * V, const gsl_vector * S, const gsl_vector * b, gsl_vector * x) { if (U->size1 != b->size) { GSL_ERROR ("first dimension of matrix U must size of vector b", GSL_EBADLEN); } else if (U->size2 != S->size) { GSL_ERROR ("length of vector S must match second dimension of matrix U", GSL_EBADLEN); } else if (V->size1 != V->size2) { GSL_ERROR ("matrix V must be square", GSL_ENOTSQR); } else if (S->size != V->size1) { GSL_ERROR ("length of vector S must match size of matrix V", GSL_EBADLEN); } else if (V->size2 != x->size) { GSL_ERROR ("size of matrix V must match size of vector x", GSL_EBADLEN); } else { const size_t N = U->size2; size_t i; gsl_vector *w = gsl_vector_calloc (N); gsl_blas_dgemv (CblasTrans, 1.0, U, b, 0.0, w); for (i = 0; i < N; i++) { double wi = gsl_vector_get (w, i); double alpha = gsl_vector_get (S, i); if (alpha != 0) alpha = 1.0 / alpha; gsl_vector_set (w, i, alpha * wi); } gsl_blas_dgemv (CblasNoTrans, 1.0, V, w, 0.0, x); gsl_vector_free (w); return GSL_SUCCESS; } } /* This is a the jacobi version */ /* Author: G. Jungman */ /* * Algorithm due to J.C. Nash, Compact Numerical Methods for * Computers (New York: Wiley and Sons, 1979), chapter 3. * See also Algorithm 4.1 in * James Demmel, Kresimir Veselic, "Jacobi's Method is more * accurate than QR", Lapack Working Note 15 (LAWN15), October 1989. * Available from netlib. * * Based on code by Arthur Kosowsky, Rutgers University * kosowsky@physics.rutgers.edu * * Another relevant paper is, P.P.M. De Rijk, "A One-Sided Jacobi * Algorithm for computing the singular value decomposition on a * vector computer", SIAM Journal of Scientific and Statistical * Computing, Vol 10, No 2, pp 359-371, March 1989. * */ int gsl_linalg_SV_decomp_jacobi (gsl_matrix * A, gsl_matrix * Q, gsl_vector * S) { if (A->size1 < A->size2) { /* FIXME: only implemented M>=N case so far */ GSL_ERROR ("svd of MxN matrix, Msize1 != A->size2) { GSL_ERROR ("square matrix Q must match second dimension of matrix A", GSL_EBADLEN); } else if (Q->size1 != Q->size2) { GSL_ERROR ("matrix Q must be square", GSL_ENOTSQR); } else if (S->size != A->size2) { GSL_ERROR ("length of vector S must match second dimension of matrix A", GSL_EBADLEN); } else { const size_t M = A->size1; const size_t N = A->size2; size_t i, j, k; /* Initialize the rotation counter and the sweep counter. */ int count = 1; int sweep = 0; int sweepmax = 5*N; double tolerance = 10 * M * GSL_DBL_EPSILON; /* Always do at least 12 sweeps. */ sweepmax = GSL_MAX (sweepmax, 12); /* Set Q to the identity matrix. */ gsl_matrix_set_identity (Q); /* Store the column error estimates in S, for use during the orthogonalization */ for (j = 0; j < N; j++) { gsl_vector_view cj = gsl_matrix_column (A, j); double sj = gsl_blas_dnrm2 (&cj.vector); gsl_vector_set(S, j, GSL_DBL_EPSILON * sj); } /* Orthogonalize A by plane rotations. */ while (count > 0 && sweep <= sweepmax) { /* Initialize rotation counter. */ count = N * (N - 1) / 2; for (j = 0; j < N - 1; j++) { for (k = j + 1; k < N; k++) { double a = 0.0; double b = 0.0; double p = 0.0; double q = 0.0; double cosine, sine; double v; double abserr_a, abserr_b; int sorted, orthog, noisya, noisyb; gsl_vector_view cj = gsl_matrix_column (A, j); gsl_vector_view ck = gsl_matrix_column (A, k); gsl_blas_ddot (&cj.vector, &ck.vector, &p); p *= 2.0 ; /* equation 9a: p = 2 x.y */ a = gsl_blas_dnrm2 (&cj.vector); b = gsl_blas_dnrm2 (&ck.vector); q = a * a - b * b; v = hypot(p, q); /* test for columns j,k orthogonal, or dominant errors */ abserr_a = gsl_vector_get(S,j); abserr_b = gsl_vector_get(S,k); sorted = (gsl_coerce_double(a) >= gsl_coerce_double(b)); orthog = (fabs (p) <= tolerance * gsl_coerce_double(a * b)); noisya = (a < abserr_a); noisyb = (b < abserr_b); if (sorted && (orthog || noisya || noisyb)) { count--; continue; } /* calculate rotation angles */ if (v == 0 || !sorted) { cosine = 0.0; sine = 1.0; } else { cosine = sqrt((v + q) / (2.0 * v)); sine = p / (2.0 * v * cosine); } /* apply rotation to A */ for (i = 0; i < M; i++) { const double Aik = gsl_matrix_get (A, i, k); const double Aij = gsl_matrix_get (A, i, j); gsl_matrix_set (A, i, j, Aij * cosine + Aik * sine); gsl_matrix_set (A, i, k, -Aij * sine + Aik * cosine); } gsl_vector_set(S, j, fabs(cosine) * abserr_a + fabs(sine) * abserr_b); gsl_vector_set(S, k, fabs(sine) * abserr_a + fabs(cosine) * abserr_b); /* apply rotation to Q */ for (i = 0; i < N; i++) { const double Qij = gsl_matrix_get (Q, i, j); const double Qik = gsl_matrix_get (Q, i, k); gsl_matrix_set (Q, i, j, Qij * cosine + Qik * sine); gsl_matrix_set (Q, i, k, -Qij * sine + Qik * cosine); } } } /* Sweep completed. */ sweep++; } /* * Orthogonalization complete. Compute singular values. */ { double prev_norm = -1.0; for (j = 0; j < N; j++) { gsl_vector_view column = gsl_matrix_column (A, j); double norm = gsl_blas_dnrm2 (&column.vector); /* Determine if singular value is zero, according to the criteria used in the main loop above (i.e. comparison with norm of previous column). */ if (norm == 0.0 || prev_norm == 0.0 || (j > 0 && norm <= tolerance * prev_norm)) { gsl_vector_set (S, j, 0.0); /* singular */ gsl_vector_set_zero (&column.vector); /* annihilate column */ prev_norm = 0.0; } else { gsl_vector_set (S, j, norm); /* non-singular */ gsl_vector_scale (&column.vector, 1.0 / norm); /* normalize column */ prev_norm = norm; } } } if (count > 0) { /* reached sweep limit */ GSL_ERROR ("Jacobi iterations did not reach desired tolerance", GSL_ETOL); } return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_sys__pow_int.c0000664000176700017670000000335411723710247020072 0ustar paulpaul/* sys/pow_int.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_pow_int.h" #ifndef HIDE_INLINE_STATIC double gsl_pow_2(const double x) { return x*x; } double gsl_pow_3(const double x) { return x*x*x; } double gsl_pow_4(const double x) { double x2 = x*x; return x2*x2; } double gsl_pow_5(const double x) { double x2 = x*x; return x2*x2*x; } double gsl_pow_6(const double x) { double x2 = x*x; return x2*x2*x2; } double gsl_pow_7(const double x) { double x3 = x*x*x; return x3*x3*x; } double gsl_pow_8(const double x) { double x2 = x*x; double x4 = x2*x2; return x4*x4; } double gsl_pow_9(const double x) { double x3 = x*x*x; return x3*x3*x3; } #endif double gsl_pow_int(double x, int n) { double value = 1.0; if(n < 0) { x = 1.0/x; n = -n; } /* repeated squaring method * returns 0.0^0 = 1.0, so continuous in x */ do { if(n & 1) value *= x; /* for n odd */ n >>= 1; x *= x; } while (n); return value; } sources_5316/external/gsl/gsl_multifit__fsolver.c0000664000176700017670000000734111723710247021112 0ustar paulpaul/* multifit/fsolver.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_multifit_nlin.h" gsl_multifit_fsolver * gsl_multifit_fsolver_alloc (const gsl_multifit_fsolver_type * T, size_t n, size_t p) { int status; gsl_multifit_fsolver * s; if (n < p) { GSL_ERROR_VAL ("insufficient data points, n < p", GSL_EINVAL, 0); } s = (gsl_multifit_fsolver *) malloc (sizeof (gsl_multifit_fsolver)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for multifit solver struct", GSL_ENOMEM, 0); } s->x = gsl_vector_calloc (p); if (s->x == 0) { free (s); GSL_ERROR_VAL ("failed to allocate space for x", GSL_ENOMEM, 0); } s->f = gsl_vector_calloc (n); if (s->f == 0) { gsl_vector_free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for f", GSL_ENOMEM, 0); } s->dx = gsl_vector_calloc (p); if (s->dx == 0) { gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); GSL_ERROR_VAL ("failed to allocate space for dx", GSL_ENOMEM, 0); } s->state = malloc (T->size); if (s->state == 0) { gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for multifit solver state", GSL_ENOMEM, 0); } s->type = T ; status = (s->type->alloc)(s->state, n, p); if (status != GSL_SUCCESS) { (s->type->free)(s->state); free (s->state); gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to set solver", status, 0); } s->function = NULL; return s; } int gsl_multifit_fsolver_set (gsl_multifit_fsolver * s, gsl_multifit_function * f, const gsl_vector * x) { if (s->f->size != f->n) { GSL_ERROR ("function size does not match solver", GSL_EBADLEN); } if (s->x->size != x->size) { GSL_ERROR ("vector length does not match solver", GSL_EBADLEN); } s->function = f; gsl_vector_memcpy(s->x,x); return (s->type->set) (s->state, s->function, s->x, s->f, s->dx); } int gsl_multifit_fsolver_iterate (gsl_multifit_fsolver * s) { return (s->type->iterate) (s->state, s->function, s->x, s->f, s->dx); } void gsl_multifit_fsolver_free (gsl_multifit_fsolver * s) { (s->type->free) (s->state); free (s->state); gsl_vector_free (s->dx); gsl_vector_free (s->x); gsl_vector_free (s->f); free (s); } const char * gsl_multifit_fsolver_name (const gsl_multifit_fsolver * s) { return s->type->name; } gsl_vector * gsl_multifit_fsolver_position (const gsl_multifit_fsolver * s) { return s->x; } sources_5316/external/gsl/gsl_integration__qk21.c0000664000176700017670000000534011723710247020673 0ustar paulpaul/* integration/qk21.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_integration.h" /* Gauss quadrature weights and kronrod quadrature abscissae and weights as evaluated with 80 decimal digit arithmetic by L. W. Fullerton, Bell Labs, Nov. 1981. */ static const double xgk[11] = /* abscissae of the 21-point kronrod rule */ { 0.995657163025808080735527280689003, 0.973906528517171720077964012084452, 0.930157491355708226001207180059508, 0.865063366688984510732096688423493, 0.780817726586416897063717578345042, 0.679409568299024406234327365114874, 0.562757134668604683339000099272694, 0.433395394129247190799265943165784, 0.294392862701460198131126603103866, 0.148874338981631210884826001129720, 0.000000000000000000000000000000000 }; /* xgk[1], xgk[3], ... abscissae of the 10-point gauss rule. xgk[0], xgk[2], ... abscissae to optimally extend the 10-point gauss rule */ static const double wg[5] = /* weights of the 10-point gauss rule */ { 0.066671344308688137593568809893332, 0.149451349150580593145776339657697, 0.219086362515982043995534934228163, 0.269266719309996355091226921569469, 0.295524224714752870173892994651338 }; static const double wgk[11] = /* weights of the 21-point kronrod rule */ { 0.011694638867371874278064396062192, 0.032558162307964727478818972459390, 0.054755896574351996031381300244580, 0.075039674810919952767043140916190, 0.093125454583697605535065465083366, 0.109387158802297641899210590325805, 0.123491976262065851077958109831074, 0.134709217311473325928054001771707, 0.142775938577060080797094273138717, 0.147739104901338491374841515972068, 0.149445554002916905664936468389821 }; void gsl_integration_qk21 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc) { double fv1[11], fv2[11]; gsl_integration_qk (11, xgk, wg, wgk, fv1, fv2, f, a, b, result, abserr, resabs, resasc); } sources_5316/external/gsl/gsl_cblas__dnrm2.c0000664000176700017670000000033011723710247017672 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" double cblas_dnrm2 (const int N, const double *X, const int incX) { #define BASE double #include "gsl_cblas__source_nrm2_r.h" #undef BASE } sources_5316/external/gsl/gsl_sort_long.h0000664000176700017670000000350011705263724017365 0ustar paulpaul/* sort/gsl_sort_long.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_LONG_H__ #define __GSL_SORT_LONG_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_long (long * data, const size_t stride, const size_t n); void gsl_sort_long_index (size_t * p, const long * data, const size_t stride, const size_t n); int gsl_sort_long_smallest (long * dest, const size_t k, const long * src, const size_t stride, const size_t n); int gsl_sort_long_smallest_index (size_t * p, const size_t k, const long * src, const size_t stride, const size_t n); int gsl_sort_long_largest (long * dest, const size_t k, const long * src, const size_t stride, const size_t n); int gsl_sort_long_largest_index (size_t * p, const size_t k, const long * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_LONG_H__ */ sources_5316/external/gsl/gsl_cblas__dasum.c0000664000176700017670000000033011723710247017761 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" double cblas_dasum (const int N, const double *X, const int incX) { #define BASE double #include "gsl_cblas__source_asum_r.h" #undef BASE } sources_5316/external/gsl/gsl_ode-initval__rk8pd.c0000664000176700017670000002744011723710247021042 0ustar paulpaul/* ode-initval/rk8pd.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Runge-Kutta 8(9), Prince-Dormand * * High Order Embedded Runge-Kutta Formulae * P.J. Prince and J.R. Dormand * J. Comp. Appl. Math.,7, pp. 67-75, 1981 */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" /* Prince-Dormand constants */ static const double Abar[] = { 14005451.0 / 335480064.0, 0.0, 0.0, 0.0, 0.0, -59238493.0 / 1068277825.0, 181606767.0 / 758867731.0, 561292985.0 / 797845732.0, -1041891430.0 / 1371343529.0, 760417239.0 / 1151165299.0, 118820643.0 / 751138087.0, -528747749.0 / 2220607170.0, 1.0 / 4.0 }; static const double A[] = { 13451932.0 / 455176623.0, 0.0, 0.0, 0.0, 0.0, -808719846.0 / 976000145.0, 1757004468.0 / 5645159321.0, 656045339.0 / 265891186.0, -3867574721.0 / 1518517206.0, 465885868.0 / 322736535.0, 53011238.0 / 667516719.0, 2.0 / 45.0 }; static const double ah[] = { 1.0 / 18.0, 1.0 / 12.0, 1.0 / 8.0, 5.0 / 16.0, 3.0 / 8.0, 59.0 / 400.0, 93.0 / 200.0, 5490023248.0 / 9719169821.0, 13.0 / 20.0, 1201146811.0 / 1299019798.0 }; static const double b21 = 1.0 / 18.0; static const double b3[] = { 1.0 / 48.0, 1.0 / 16.0 }; static const double b4[] = { 1.0 / 32.0, 0.0, 3.0 / 32.0 }; static const double b5[] = { 5.0 / 16.0, 0.0, -75.0 / 64.0, 75.0 / 64.0 }; static const double b6[] = { 3.0 / 80.0, 0.0, 0.0, 3.0 / 16.0, 3.0 / 20.0 }; static const double b7[] = { 29443841.0 / 614563906.0, 0.0, 0.0, 77736538.0 / 692538347.0, -28693883.0 / 1125000000.0, 23124283.0 / 1800000000.0 }; static const double b8[] = { 16016141.0 / 946692911.0, 0.0, 0.0, 61564180.0 / 158732637.0, 22789713.0 / 633445777.0, 545815736.0 / 2771057229.0, -180193667.0 / 1043307555.0 }; static const double b9[] = { 39632708.0 / 573591083.0, 0.0, 0.0, -433636366.0 / 683701615.0, -421739975.0 / 2616292301.0, 100302831.0 / 723423059.0, 790204164.0 / 839813087.0, 800635310.0 / 3783071287.0 }; static const double b10[] = { 246121993.0 / 1340847787.0, 0.0, 0.0, -37695042795.0 / 15268766246.0, -309121744.0 / 1061227803.0, -12992083.0 / 490766935.0, 6005943493.0 / 2108947869.0, 393006217.0 / 1396673457.0, 123872331.0 / 1001029789.0 }; static const double b11[] = { -1028468189.0 / 846180014.0, 0.0, 0.0, 8478235783.0 / 508512852.0, 1311729495.0 / 1432422823.0, -10304129995.0 / 1701304382.0, -48777925059.0 / 3047939560.0, 15336726248.0 / 1032824649.0, -45442868181.0 / 3398467696.0, 3065993473.0 / 597172653.0 }; static const double b12[] = { 185892177.0 / 718116043.0, 0.0, 0.0, -3185094517.0 / 667107341.0, -477755414.0 / 1098053517.0, -703635378.0 / 230739211.0, 5731566787.0 / 1027545527.0, 5232866602.0 / 850066563.0, -4093664535.0 / 808688257.0, 3962137247.0 / 1805957418.0, 65686358.0 / 487910083.0 }; static const double b13[] = { 403863854.0 / 491063109.0, 0.0, 0.0, -5068492393.0 / 434740067.0, -411421997.0 / 543043805.0, 652783627.0 / 914296604.0, 11173962825.0 / 925320556.0, -13158990841.0 / 6184727034.0, 3936647629.0 / 1978049680.0, -160528059.0 / 685178525.0, 248638103.0 / 1413531060.0, 0.0 }; typedef struct { double *k[13]; double *ytmp; double *y0; } rk8pd_state_t; static void * rk8pd_alloc (size_t dim) { rk8pd_state_t *state = (rk8pd_state_t *) malloc (sizeof (rk8pd_state_t)); int i, j; if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for rk8pd_state", GSL_ENOMEM); } state->ytmp = (double *) malloc (dim * sizeof (double)); if (state->ytmp == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for ytmp", GSL_ENOMEM); } state->y0 = (double *) malloc (dim * sizeof (double)); if (state->y0 == 0) { free (state->ytmp); free (state); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } for (i = 0; i < 13; i++) { state->k[i] = (double *) malloc (dim * sizeof (double)); if (state->k[i] == 0) { for (j = 0; j < i; j++) { free (state->k[j]); } free (state->y0); free (state->ytmp); free (state); GSL_ERROR_NULL ("failed to allocate space for k's", GSL_ENOMEM); } } return state; } static int rk8pd_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { rk8pd_state_t *state = (rk8pd_state_t *) vstate; size_t i; double *const ytmp = state->ytmp; double *const y0 = state->y0; /* Note that k1 is stored in state->k[0] due to zero-based indexing */ double *const k1 = state->k[0]; double *const k2 = state->k[1]; double *const k3 = state->k[2]; double *const k4 = state->k[3]; double *const k5 = state->k[4]; double *const k6 = state->k[5]; double *const k7 = state->k[6]; double *const k8 = state->k[7]; double *const k9 = state->k[8]; double *const k10 = state->k[9]; double *const k11 = state->k[10]; double *const k12 = state->k[11]; double *const k13 = state->k[12]; DBL_MEMCPY (y0, y, dim); /* k1 step */ if (dydt_in != NULL) { DBL_MEMCPY (k1, dydt_in, dim); } else { int s = GSL_ODEIV_FN_EVAL (sys, t, y, k1); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + b21 * h * k1[i]; /* k2 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[0] * h, ytmp, k2); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b3[0] * k1[i] + b3[1] * k2[i]); /* k3 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[1] * h, ytmp, k3); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b4[0] * k1[i] + b4[2] * k3[i]); /* k4 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[2] * h, ytmp, k4); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b5[0] * k1[i] + b5[2] * k3[i] + b5[3] * k4[i]); /* k5 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[3] * h, ytmp, k5); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b6[0] * k1[i] + b6[3] * k4[i] + b6[4] * k5[i]); /* k6 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[4] * h, ytmp, k6); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b7[0] * k1[i] + b7[3] * k4[i] + b7[4] * k5[i] + b7[5] * k6[i]); /* k7 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[5] * h, ytmp, k7); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b8[0] * k1[i] + b8[3] * k4[i] + b8[4] * k5[i] + b8[5] * k6[i] + b8[6] * k7[i]); /* k8 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[6] * h, ytmp, k8); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b9[0] * k1[i] + b9[3] * k4[i] + b9[4] * k5[i] + b9[5] * k6[i] + b9[6] * k7[i] + b9[7] * k8[i]); /* k9 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[7] * h, ytmp, k9); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b10[0] * k1[i] + b10[3] * k4[i] + b10[4] * k5[i] + b10[5] * k6[i] + b10[6] * k7[i] + b10[7] * k8[i] + b10[8] * k9[i]); /* k10 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[8] * h, ytmp, k10); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b11[0] * k1[i] + b11[3] * k4[i] + b11[4] * k5[i] + b11[5] * k6[i] + b11[6] * k7[i] + b11[7] * k8[i] + b11[8] * k9[i] + b11[9] * k10[i]); /* k11 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[9] * h, ytmp, k11); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b12[0] * k1[i] + b12[3] * k4[i] + b12[4] * k5[i] + b12[5] * k6[i] + b12[6] * k7[i] + b12[7] * k8[i] + b12[8] * k9[i] + b12[9] * k10[i] + b12[10] * k11[i]); /* k12 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + h, ytmp, k12); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b13[0] * k1[i] + b13[3] * k4[i] + b13[4] * k5[i] + b13[5] * k6[i] + b13[6] * k7[i] + b13[7] * k8[i] + b13[8] * k9[i] + b13[9] * k10[i] + b13[10] * k11[i] + b13[11] * k12[i]); /* k13 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + h, ytmp, k13); if (s != GSL_SUCCESS) { return s; } } /* final sum */ for (i = 0; i < dim; i++) { const double ksum8 = Abar[0] * k1[i] + Abar[5] * k6[i] + Abar[6] * k7[i] + Abar[7] * k8[i] + Abar[8] * k9[i] + Abar[9] * k10[i] + Abar[10] * k11[i] + Abar[11] * k12[i] + Abar[12] * k13[i]; y[i] += h * ksum8; } /* Evaluate dydt_out[]. */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore initial values */ DBL_MEMCPY (y, y0, dim); return s; } } /* error estimate */ for (i = 0; i < dim; i++) { const double ksum8 = Abar[0] * k1[i] + Abar[5] * k6[i] + Abar[6] * k7[i] + Abar[7] * k8[i] + Abar[8] * k9[i] + Abar[9] * k10[i] + Abar[10] * k11[i] + Abar[11] * k12[i] + Abar[12] * k13[i]; const double ksum7 = A[0] * k1[i] + A[5] * k6[i] + A[6] * k7[i] + A[7] * k8[i] + A[8] * k9[i] + A[9] * k10[i] + A[10] * k11[i] + A[11] * k12[i]; yerr[i] = h * (ksum7 - ksum8); } return GSL_SUCCESS; } static int rk8pd_reset (void *vstate, size_t dim) { rk8pd_state_t *state = (rk8pd_state_t *) vstate; int i; for (i = 0; i < 13; i++) { DBL_ZERO_MEMSET (state->k[i], dim); } DBL_ZERO_MEMSET (state->y0, dim); DBL_ZERO_MEMSET (state->ytmp, dim); return GSL_SUCCESS; } static unsigned int rk8pd_order (void *vstate) { rk8pd_state_t *state = (rk8pd_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 8; } static void rk8pd_free (void *vstate) { rk8pd_state_t *state = (rk8pd_state_t *) vstate; int i; for (i = 0; i < 13; i++) { free (state->k[i]); } free (state->y0); free (state->ytmp); free (state); } static const gsl_odeiv_step_type rk8pd_type = { "rk8pd", /* name */ 1, /* can use dydt_in */ 1, /* gives exact dydt_out */ &rk8pd_alloc, &rk8pd_apply, &rk8pd_reset, &rk8pd_order, &rk8pd_free }; const gsl_odeiv_step_type *gsl_odeiv_step_rk8pd = &rk8pd_type; sources_5316/external/gsl/gsl_statistics__p_variance.c0000664000176700017670000000306711723710247022077 0ustar paulpaul#include "gsl__config.h" #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__p_variance_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_fft_halfcomplex.h0000664000176700017670000000570411705263724020530 0ustar paulpaul/* fft/gsl_fft_halfcomplex.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_FFT_HALFCOMPLEX_H__ #define __GSL_FFT_HALFCOMPLEX_H__ #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_fft.h" #include "gsl_fft_real.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_fft_halfcomplex_radix2_backward (double data[], const size_t stride, const size_t n); int gsl_fft_halfcomplex_radix2_inverse (double data[], const size_t stride, const size_t n); int gsl_fft_halfcomplex_radix2_transform (double data[], const size_t stride, const size_t n); typedef struct { size_t n; size_t nf; size_t factor[64]; gsl_complex *twiddle[64]; gsl_complex *trig; } gsl_fft_halfcomplex_wavetable; gsl_fft_halfcomplex_wavetable * gsl_fft_halfcomplex_wavetable_alloc (size_t n); void gsl_fft_halfcomplex_wavetable_free (gsl_fft_halfcomplex_wavetable * wavetable); int gsl_fft_halfcomplex_backward (double data[], const size_t stride, const size_t n, const gsl_fft_halfcomplex_wavetable * wavetable, gsl_fft_real_workspace * work); int gsl_fft_halfcomplex_inverse (double data[], const size_t stride, const size_t n, const gsl_fft_halfcomplex_wavetable * wavetable, gsl_fft_real_workspace * work); int gsl_fft_halfcomplex_transform (double data[], const size_t stride, const size_t n, const gsl_fft_halfcomplex_wavetable * wavetable, gsl_fft_real_workspace * work); int gsl_fft_halfcomplex_unpack (const double halfcomplex_coefficient[], double complex_coefficient[], const size_t stride, const size_t n); int gsl_fft_halfcomplex_radix2_unpack (const double halfcomplex_coefficient[], double complex_coefficient[], const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_FFT_HALFCOMPLEX_H__ */ sources_5316/external/gsl/gsl_matrix_complex_long_double.h0000664000176700017670000003415511705263724022775 0ustar paulpaul/* matrix/gsl_matrix_complex_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MATRIX_COMPLEX_LONG_DOUBLE_H__ #define __GSL_MATRIX_COMPLEX_LONG_DOUBLE_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_check_range.h" #include "gsl_vector_complex_long_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size1; size_t size2; size_t tda; long double * data; gsl_block_complex_long_double * block; int owner; } gsl_matrix_complex_long_double ; typedef struct { gsl_matrix_complex_long_double matrix; } _gsl_matrix_complex_long_double_view; typedef _gsl_matrix_complex_long_double_view gsl_matrix_complex_long_double_view; typedef struct { gsl_matrix_complex_long_double matrix; } _gsl_matrix_complex_long_double_const_view; typedef const _gsl_matrix_complex_long_double_const_view gsl_matrix_complex_long_double_const_view; /* Allocation */ gsl_matrix_complex_long_double * gsl_matrix_complex_long_double_alloc (const size_t n1, const size_t n2); gsl_matrix_complex_long_double * gsl_matrix_complex_long_double_calloc (const size_t n1, const size_t n2); gsl_matrix_complex_long_double * gsl_matrix_complex_long_double_alloc_from_block (gsl_block_complex_long_double * b, const size_t offset, const size_t n1, const size_t n2, const size_t d2); gsl_matrix_complex_long_double * gsl_matrix_complex_long_double_alloc_from_matrix (gsl_matrix_complex_long_double * b, const size_t k1, const size_t k2, const size_t n1, const size_t n2); gsl_vector_complex_long_double * gsl_vector_complex_long_double_alloc_row_from_matrix (gsl_matrix_complex_long_double * m, const size_t i); gsl_vector_complex_long_double * gsl_vector_complex_long_double_alloc_col_from_matrix (gsl_matrix_complex_long_double * m, const size_t j); void gsl_matrix_complex_long_double_free (gsl_matrix_complex_long_double * m); /* Views */ _gsl_matrix_complex_long_double_view gsl_matrix_complex_long_double_submatrix (gsl_matrix_complex_long_double * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_complex_long_double_view gsl_matrix_complex_long_double_row (gsl_matrix_complex_long_double * m, const size_t i); _gsl_vector_complex_long_double_view gsl_matrix_complex_long_double_column (gsl_matrix_complex_long_double * m, const size_t j); _gsl_vector_complex_long_double_view gsl_matrix_complex_long_double_diagonal (gsl_matrix_complex_long_double * m); _gsl_vector_complex_long_double_view gsl_matrix_complex_long_double_subdiagonal (gsl_matrix_complex_long_double * m, const size_t k); _gsl_vector_complex_long_double_view gsl_matrix_complex_long_double_superdiagonal (gsl_matrix_complex_long_double * m, const size_t k); _gsl_vector_complex_long_double_view gsl_matrix_complex_long_double_subrow (gsl_matrix_complex_long_double * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_complex_long_double_view gsl_matrix_complex_long_double_subcolumn (gsl_matrix_complex_long_double * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_complex_long_double_view gsl_matrix_complex_long_double_view_array (long double * base, const size_t n1, const size_t n2); _gsl_matrix_complex_long_double_view gsl_matrix_complex_long_double_view_array_with_tda (long double * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_complex_long_double_view gsl_matrix_complex_long_double_view_vector (gsl_vector_complex_long_double * v, const size_t n1, const size_t n2); _gsl_matrix_complex_long_double_view gsl_matrix_complex_long_double_view_vector_with_tda (gsl_vector_complex_long_double * v, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_complex_long_double_const_view gsl_matrix_complex_long_double_const_submatrix (const gsl_matrix_complex_long_double * m, const size_t i, const size_t j, const size_t n1, const size_t n2); _gsl_vector_complex_long_double_const_view gsl_matrix_complex_long_double_const_row (const gsl_matrix_complex_long_double * m, const size_t i); _gsl_vector_complex_long_double_const_view gsl_matrix_complex_long_double_const_column (const gsl_matrix_complex_long_double * m, const size_t j); _gsl_vector_complex_long_double_const_view gsl_matrix_complex_long_double_const_diagonal (const gsl_matrix_complex_long_double * m); _gsl_vector_complex_long_double_const_view gsl_matrix_complex_long_double_const_subdiagonal (const gsl_matrix_complex_long_double * m, const size_t k); _gsl_vector_complex_long_double_const_view gsl_matrix_complex_long_double_const_superdiagonal (const gsl_matrix_complex_long_double * m, const size_t k); _gsl_vector_complex_long_double_const_view gsl_matrix_complex_long_double_const_subrow (const gsl_matrix_complex_long_double * m, const size_t i, const size_t offset, const size_t n); _gsl_vector_complex_long_double_const_view gsl_matrix_complex_long_double_const_subcolumn (const gsl_matrix_complex_long_double * m, const size_t j, const size_t offset, const size_t n); _gsl_matrix_complex_long_double_const_view gsl_matrix_complex_long_double_const_view_array (const long double * base, const size_t n1, const size_t n2); _gsl_matrix_complex_long_double_const_view gsl_matrix_complex_long_double_const_view_array_with_tda (const long double * base, const size_t n1, const size_t n2, const size_t tda); _gsl_matrix_complex_long_double_const_view gsl_matrix_complex_long_double_const_view_vector (const gsl_vector_complex_long_double * v, const size_t n1, const size_t n2); _gsl_matrix_complex_long_double_const_view gsl_matrix_complex_long_double_const_view_vector_with_tda (const gsl_vector_complex_long_double * v, const size_t n1, const size_t n2, const size_t tda); /* Operations */ gsl_complex_long_double gsl_matrix_complex_long_double_get(const gsl_matrix_complex_long_double * m, const size_t i, const size_t j); void gsl_matrix_complex_long_double_set(gsl_matrix_complex_long_double * m, const size_t i, const size_t j, const gsl_complex_long_double x); gsl_complex_long_double * gsl_matrix_complex_long_double_ptr(gsl_matrix_complex_long_double * m, const size_t i, const size_t j); const gsl_complex_long_double * gsl_matrix_complex_long_double_const_ptr(const gsl_matrix_complex_long_double * m, const size_t i, const size_t j); void gsl_matrix_complex_long_double_set_zero (gsl_matrix_complex_long_double * m); void gsl_matrix_complex_long_double_set_identity (gsl_matrix_complex_long_double * m); void gsl_matrix_complex_long_double_set_all (gsl_matrix_complex_long_double * m, gsl_complex_long_double x); int gsl_matrix_complex_long_double_fread (FILE * stream, gsl_matrix_complex_long_double * m) ; int gsl_matrix_complex_long_double_fwrite (FILE * stream, const gsl_matrix_complex_long_double * m) ; int gsl_matrix_complex_long_double_fscanf (FILE * stream, gsl_matrix_complex_long_double * m); int gsl_matrix_complex_long_double_fprintf (FILE * stream, const gsl_matrix_complex_long_double * m, const char * format); int gsl_matrix_complex_long_double_memcpy(gsl_matrix_complex_long_double * dest, const gsl_matrix_complex_long_double * src); int gsl_matrix_complex_long_double_swap(gsl_matrix_complex_long_double * m1, gsl_matrix_complex_long_double * m2); int gsl_matrix_complex_long_double_swap_rows(gsl_matrix_complex_long_double * m, const size_t i, const size_t j); int gsl_matrix_complex_long_double_swap_columns(gsl_matrix_complex_long_double * m, const size_t i, const size_t j); int gsl_matrix_complex_long_double_swap_rowcol(gsl_matrix_complex_long_double * m, const size_t i, const size_t j); int gsl_matrix_complex_long_double_transpose (gsl_matrix_complex_long_double * m); int gsl_matrix_complex_long_double_transpose_memcpy (gsl_matrix_complex_long_double * dest, const gsl_matrix_complex_long_double * src); int gsl_matrix_complex_long_double_isnull (const gsl_matrix_complex_long_double * m); int gsl_matrix_complex_long_double_ispos (const gsl_matrix_complex_long_double * m); int gsl_matrix_complex_long_double_isneg (const gsl_matrix_complex_long_double * m); int gsl_matrix_complex_long_double_isnonneg (const gsl_matrix_complex_long_double * m); int gsl_matrix_complex_long_double_add (gsl_matrix_complex_long_double * a, const gsl_matrix_complex_long_double * b); int gsl_matrix_complex_long_double_sub (gsl_matrix_complex_long_double * a, const gsl_matrix_complex_long_double * b); int gsl_matrix_complex_long_double_mul_elements (gsl_matrix_complex_long_double * a, const gsl_matrix_complex_long_double * b); int gsl_matrix_complex_long_double_div_elements (gsl_matrix_complex_long_double * a, const gsl_matrix_complex_long_double * b); int gsl_matrix_complex_long_double_scale (gsl_matrix_complex_long_double * a, const gsl_complex_long_double x); int gsl_matrix_complex_long_double_add_constant (gsl_matrix_complex_long_double * a, const gsl_complex_long_double x); int gsl_matrix_complex_long_double_add_diagonal (gsl_matrix_complex_long_double * a, const gsl_complex_long_double x); /***********************************************************************/ /* The functions below are obsolete */ /***********************************************************************/ int gsl_matrix_complex_long_double_get_row(gsl_vector_complex_long_double * v, const gsl_matrix_complex_long_double * m, const size_t i); int gsl_matrix_complex_long_double_get_col(gsl_vector_complex_long_double * v, const gsl_matrix_complex_long_double * m, const size_t j); int gsl_matrix_complex_long_double_set_row(gsl_matrix_complex_long_double * m, const size_t i, const gsl_vector_complex_long_double * v); int gsl_matrix_complex_long_double_set_col(gsl_matrix_complex_long_double * m, const size_t j, const gsl_vector_complex_long_double * v); #ifdef HAVE_INLINE extern inline gsl_complex_long_double gsl_matrix_complex_long_double_get(const gsl_matrix_complex_long_double * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK gsl_complex_long_double zero = {{0,0}}; if (i >= m->size1) { GSL_ERROR_VAL("first index out of range", GSL_EINVAL, zero) ; } else if (j >= m->size2) { GSL_ERROR_VAL("second index out of range", GSL_EINVAL, zero) ; } #endif return *(gsl_complex_long_double *)(m->data + 2*(i * m->tda + j)) ; } extern inline void gsl_matrix_complex_long_double_set(gsl_matrix_complex_long_double * m, const size_t i, const size_t j, const gsl_complex_long_double x) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_VOID("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_VOID("second index out of range", GSL_EINVAL) ; } #endif *(gsl_complex_long_double *)(m->data + 2*(i * m->tda + j)) = x ; } extern inline gsl_complex_long_double * gsl_matrix_complex_long_double_ptr(gsl_matrix_complex_long_double * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (gsl_complex_long_double *)(m->data + 2*(i * m->tda + j)) ; } extern inline const gsl_complex_long_double * gsl_matrix_complex_long_double_const_ptr(const gsl_matrix_complex_long_double * m, const size_t i, const size_t j) { #if GSL_RANGE_CHECK if (i >= m->size1) { GSL_ERROR_NULL("first index out of range", GSL_EINVAL) ; } else if (j >= m->size2) { GSL_ERROR_NULL("second index out of range", GSL_EINVAL) ; } #endif return (const gsl_complex_long_double *)(m->data + 2*(i * m->tda + j)) ; } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_MATRIX_COMPLEX_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_randist__weibull.c0000664000176700017670000000304711723710247020703 0ustar paulpaul/* randist/weibull.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* The Weibull distribution has the form, p(x) dx = (b/a) (x/a)^(b-1) exp(-(x/a)^b) dx */ double gsl_ran_weibull (const gsl_rng * r, const double a, const double b) { double x = gsl_rng_uniform_pos (r); double z = pow (-log (x), 1 / b); return a * z; } double gsl_ran_weibull_pdf (const double x, const double a, const double b) { if (x < 0) { return 0 ; } else if (x == 0) { if (b == 1) return 1/a ; else return 0 ; } else if (b == 1) { return exp(-x/a)/a ; } else { double p = (b/a) * exp (-pow (x/a, b) + (b - 1) * log (x/a)); return p; } } sources_5316/external/gsl/gsl_specfunc__shint.c0000664000176700017670000000767111723710247020536 0ustar paulpaul/* specfunc/shint.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_expint.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC shi.f, W. Fullerton series for shi on the interval 0.00000e+00 to 1.40625e-01 with weighted error 4.67e-20 log weighted error 19.33 significant figures required 17.07 decimal places required 19.75 */ static double shi_data[7] = { 0.0078372685688900950695, 0.0039227664934234563973, 0.0000041346787887617267, 0.0000000024707480372883, 0.0000000000009379295591, 0.0000000000000002451817, 0.0000000000000000000467 }; static cheb_series shi_cs = { shi_data, 6, -1, 1, 6 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_Shi_e(const double x, gsl_sf_result * result) { const double xsml = GSL_SQRT_DBL_EPSILON; /* sqrt (r1mach(3)) */ const double ax = fabs(x); if(ax < xsml) { result->val = x; result->err = 0.0; return GSL_SUCCESS; } else if(ax <= 0.375) { gsl_sf_result result_c; cheb_eval_e(&shi_cs, 128.0*x*x/9.0-1.0, &result_c); result->val = x * (1.0 + result_c.val); result->err = x * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result result_Ei; gsl_sf_result result_E1; int status_Ei = gsl_sf_expint_Ei_e(x, &result_Ei); int status_E1 = gsl_sf_expint_E1_e(x, &result_E1); result->val = 0.5*(result_Ei.val + result_E1.val); result->err = 0.5*(result_Ei.err + result_E1.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if(status_Ei == GSL_EUNDRFLW && status_E1 == GSL_EUNDRFLW) { GSL_ERROR ("underflow", GSL_EUNDRFLW); } else if(status_Ei == GSL_EOVRFLW || status_E1 == GSL_EOVRFLW) { GSL_ERROR ("overflow", GSL_EOVRFLW); } else { return GSL_SUCCESS; } } } int gsl_sf_Chi_e(const double x, gsl_sf_result * result) { gsl_sf_result result_Ei; gsl_sf_result result_E1; int status_Ei = gsl_sf_expint_Ei_e(x, &result_Ei); int status_E1 = gsl_sf_expint_E1_e(x, &result_E1); if(status_Ei == GSL_EDOM || status_E1 == GSL_EDOM) { DOMAIN_ERROR(result); } else if(status_Ei == GSL_EUNDRFLW && status_E1 == GSL_EUNDRFLW) { UNDERFLOW_ERROR(result); } else if(status_Ei == GSL_EOVRFLW || status_E1 == GSL_EOVRFLW) { OVERFLOW_ERROR(result); } else { result->val = 0.5 * (result_Ei.val - result_E1.val); result->err = 0.5 * (result_Ei.err + result_E1.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_Shi(const double x) { EVAL_RESULT(gsl_sf_Shi_e(x, &result)); } double gsl_sf_Chi(const double x) { EVAL_RESULT(gsl_sf_Chi_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__srot.c0000664000176700017670000000041611723710247017644 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_srot (const int N, float *X, const int incX, float *Y, const int incY, const float c, const float s) { #define BASE float #include "gsl_cblas__source_rot.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_herk.h0000664000176700017670000001205511705263724021200 0ustar paulpaul/* blas/source_herk.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; int uplo, trans; if (beta == 1.0 && (alpha == 0.0 || K == 0)) return; if (Order == CblasRowMajor) { uplo = Uplo; trans = Trans; } else { uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; trans = (Trans == CblasNoTrans) ? CblasConjTrans : CblasNoTrans; } /* form y := beta*y */ if (beta == 0.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } else { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { REAL(C, ldc * i + j) = 0.0; IMAG(C, ldc * i + j) = 0.0; } } } } else if (beta != 1.0) { if (uplo == CblasUpper) { for (i = 0; i < N; i++) { REAL(C, ldc * i + i) *= beta; IMAG(C, ldc * i + i) = 0; for (j = i + 1; j < N; j++) { REAL(C, ldc * i + j) *= beta; IMAG(C, ldc * i + j) *= beta; } } } else { for (i = 0; i < N; i++) { for (j = 0; j < i; j++) { REAL(C, ldc * i + j) *= beta; IMAG(C, ldc * i + j) *= beta; } REAL(C, ldc * i + i) *= beta; IMAG(C, ldc * i + i) = 0; } } } else { /* set imaginary part of Aii to zero */ for (i = 0; i < N; i++) { IMAG(C, ldc * i + i) = 0.0; } } if (alpha == 0.0) return; if (uplo == CblasUpper && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = -CONST_IMAG(A, j * lda + k); temp_real += Aik_real * Ajk_real - Aik_imag * Ajk_imag; temp_imag += Aik_real * Ajk_imag + Aik_imag * Ajk_real; } REAL(C, i * ldc + j) += alpha * temp_real; IMAG(C, i * ldc + j) += alpha * temp_imag; } } } else if (uplo == CblasUpper && trans == CblasConjTrans) { for (i = 0; i < N; i++) { for (j = i; j < N; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aki_real = CONST_REAL(A, k * lda + i); const BASE Aki_imag = -CONST_IMAG(A, k * lda + i); const BASE Akj_real = CONST_REAL(A, k * lda + j); const BASE Akj_imag = CONST_IMAG(A, k * lda + j); temp_real += Aki_real * Akj_real - Aki_imag * Akj_imag; temp_imag += Aki_real * Akj_imag + Aki_imag * Akj_real; } REAL(C, i * ldc + j) += alpha * temp_real; IMAG(C, i * ldc + j) += alpha * temp_imag; } } } else if (uplo == CblasLower && trans == CblasNoTrans) { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = CONST_IMAG(A, i * lda + k); const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = -CONST_IMAG(A, j * lda + k); temp_real += Aik_real * Ajk_real - Aik_imag * Ajk_imag; temp_imag += Aik_real * Ajk_imag + Aik_imag * Ajk_real; } REAL(C, i * ldc + j) += alpha * temp_real; IMAG(C, i * ldc + j) += alpha * temp_imag; } } } else if (uplo == CblasLower && trans == CblasConjTrans) { for (i = 0; i < N; i++) { for (j = 0; j <= i; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < K; k++) { const BASE Aki_real = CONST_REAL(A, k * lda + i); const BASE Aki_imag = -CONST_IMAG(A, k * lda + i); const BASE Akj_real = CONST_REAL(A, k * lda + j); const BASE Akj_imag = CONST_IMAG(A, k * lda + j); temp_real += Aki_real * Akj_real - Aki_imag * Akj_imag; temp_imag += Aki_real * Akj_imag + Aki_imag * Akj_real; } REAL(C, i * ldc + j) += alpha * temp_real; IMAG(C, i * ldc + j) += alpha * temp_imag; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_poly__companion.c0000664000176700017670000000226411723710247020542 0ustar paulpaul/* poly/companion.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void set_companion_matrix (const double *a, size_t n, double *m); static void set_companion_matrix (const double *a, size_t nc, double *m) { size_t i, j; for (i = 0; i < nc; i++) for (j = 0; j < nc; j++) MAT (m, i, j, nc) = 0.0; for (i = 1; i < nc; i++) MAT (m, i, i - 1, nc) = 1.0; for (i = 0; i < nc; i++) MAT (m, i, nc - 1, nc) = -a[i] / a[nc]; } sources_5316/external/gsl/gsl_block__fwrite_source.c0000664000176700017670000000551311723710247021546 0ustar paulpaul/* block/fwrite_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_block, fread) (FILE * stream, TYPE(gsl_block) * b) { size_t n = b->size ; ATOMIC * data = b->data ; size_t items = fread (data, MULTIPLICITY * sizeof (ATOMIC), n, stream); if (items != n) { GSL_ERROR ("fread failed", GSL_EFAILED); } return 0; } int FUNCTION (gsl_block, fwrite) (FILE * stream, const TYPE(gsl_block) * b) { size_t n = b->size ; ATOMIC * data = b->data ; size_t items = fwrite (data, MULTIPLICITY * sizeof (ATOMIC), n, stream); if (items != n) { GSL_ERROR ("fwrite failed", GSL_EFAILED); } return 0; } int FUNCTION (gsl_block, raw_fread) (FILE * stream, ATOMIC * data, const size_t n, const size_t stride) { if (stride == 1) { size_t items = fread (data, MULTIPLICITY * sizeof (ATOMIC), n, stream); if (items != n) { GSL_ERROR ("fread failed", GSL_EFAILED); } } else { size_t i; for (i = 0; i < n; i++) { size_t item = fread (data + MULTIPLICITY * i * stride, MULTIPLICITY * sizeof (ATOMIC), 1, stream); if (item != 1) { GSL_ERROR ("fread failed", GSL_EFAILED); } } } return GSL_SUCCESS; } int FUNCTION (gsl_block, raw_fwrite) (FILE * stream, const ATOMIC * data, const size_t n, const size_t stride) { if (stride == 1) { size_t items = fwrite (data, MULTIPLICITY * sizeof (ATOMIC), n, stream); if (items != n) { GSL_ERROR ("fwrite failed", GSL_EFAILED); } } else { size_t i; for (i = 0; i < n; i++) { size_t item = fwrite (data + MULTIPLICITY * i * stride, MULTIPLICITY * sizeof (ATOMIC), 1, stream); if (item != 1) { GSL_ERROR ("fwrite failed", GSL_EFAILED); } } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_heapsort.h0000664000176700017670000000265211705263724017213 0ustar paulpaul/* sort/gsl_heapsort.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_HEAPSORT_H__ #define __GSL_HEAPSORT_H__ #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef int (*gsl_comparison_fn_t) (const void *, const void *); void gsl_heapsort (void * array, size_t count, size_t size, gsl_comparison_fn_t compare); int gsl_heapsort_index (size_t * p, const void * array, size_t count, size_t size, gsl_comparison_fn_t compare); __END_DECLS #endif /* __GSL_HEAPSORT_H__ */ sources_5316/external/gsl/gsl_randist__pareto.c0000664000176700017670000000254411723710247020533 0ustar paulpaul/* randist/pareto.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* The Pareto distribution has the form, p(x) dx = (a/b) / (x/b)^(a+1) dx for x >= b */ double gsl_ran_pareto (const gsl_rng * r, double a, const double b) { double x = gsl_rng_uniform_pos (r); double z = pow (x, -1 / a); return b * z; } double gsl_ran_pareto_pdf (const double x, const double a, const double b) { if (x >= b) { double p = (a/b) / pow (x/b, a + 1); return p; } else { return 0; } } sources_5316/external/gsl/gsl_ntuple.h0000664000176700017670000000413511705263724016673 0ustar paulpaul/* histogram/ntuple.h * * Copyright (C) 2000 Simone Piccardi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * */ /* Jan/2001 Modified by Brian Gough. Minor changes for GSL */ #ifndef __GSL_NTUPLE_H__ #define __GSL_NTUPLE_H__ #include #include #include "gsl_errno.h" #include "gsl_histogram.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { FILE * file; void * ntuple_data; size_t size; } gsl_ntuple; typedef struct { int (* function) (void * ntuple_data, void * params); void * params; } gsl_ntuple_select_fn; typedef struct { double (* function) (void * ntuple_data, void * params); void * params; } gsl_ntuple_value_fn; gsl_ntuple * gsl_ntuple_open (char * filename, void * ntuple_data, size_t size); gsl_ntuple * gsl_ntuple_create (char * filename, void * ntuple_data, size_t size); int gsl_ntuple_write (gsl_ntuple * ntuple); int gsl_ntuple_read (gsl_ntuple * ntuple); int gsl_ntuple_bookdata (gsl_ntuple * ntuple); /* synonym for write */ int gsl_ntuple_project (gsl_histogram * h, gsl_ntuple * ntuple, gsl_ntuple_value_fn *value_func, gsl_ntuple_select_fn *select_func); int gsl_ntuple_close (gsl_ntuple * ntuple); __END_DECLS #endif /* __GSL_NTUPLE_H__ */ sources_5316/external/gsl/gsl_cblas__source_tpsv_r.h0000664000176700017670000000736411705263724021573 0ustar paulpaul/* blas/source_tpsv_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; const int nonunit = (Diag == CblasNonUnit); const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; if (N == 0) return; /* form x := inv( A )*x */ if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { /* backsubstitution */ INDEX ix = OFFSET(N, incX) + incX * (N - 1); if (nonunit) { X[ix] = X[ix] / Ap[TPUP(N, (N - 1), (N - 1))]; } ix -= incX; for (i = N - 1; i > 0 && i--;) { BASE tmp = X[ix]; INDEX jx = ix + incX; for (j = i + 1; j < N; j++) { const BASE Aij = Ap[TPUP(N, i, j)]; tmp -= Aij * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / Ap[TPUP(N, i, i)]; } else { X[ix] = tmp; } ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { /* forward substitution */ INDEX ix = OFFSET(N, incX); if (nonunit) { X[ix] = X[ix] / Ap[TPLO(N, 0, 0)]; } ix += incX; for (i = 1; i < N; i++) { BASE tmp = X[ix]; INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE Aij = Ap[TPLO(N, i, j)]; tmp -= Aij * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / Ap[TPLO(N, i, j)]; } else { X[ix] = tmp; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := inv( A' )*x */ /* forward substitution */ INDEX ix = OFFSET(N, incX); if (nonunit) { X[ix] = X[ix] / Ap[TPUP(N, 0, 0)]; } ix += incX; for (i = 1; i < N; i++) { BASE tmp = X[ix]; INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE Aji = Ap[TPUP(N, j, i)]; tmp -= Aji * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / Ap[TPUP(N, i, i)]; } else { X[ix] = tmp; } ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { /* backsubstitution */ INDEX ix = OFFSET(N, incX) + (N - 1) * incX; if (nonunit) { X[ix] = X[ix] / Ap[TPLO(N, (N - 1), (N - 1))]; } ix -= incX; for (i = N - 1; i > 0 && i--;) { BASE tmp = X[ix]; INDEX jx = ix + incX; for (j = i + 1; j < N; j++) { const BASE Aji = Ap[TPLO(N, j, i)]; tmp -= Aji * X[jx]; jx += incX; } if (nonunit) { X[ix] = tmp / Ap[TPLO(N, i, i)]; } else { X[ix] = tmp; } ix -= incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_statistics_double.h0000664000176700017670000001407511705263724021114 0ustar paulpaul/* statistics/gsl_statistics_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_DOUBLE_H__ #define __GSL_STATISTICS_DOUBLE_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_mean (const double data[], const size_t stride, const size_t n); double gsl_stats_variance (const double data[], const size_t stride, const size_t n); double gsl_stats_sd (const double data[], const size_t stride, const size_t n); double gsl_stats_variance_with_fixed_mean (const double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_sd_with_fixed_mean (const double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_absdev (const double data[], const size_t stride, const size_t n); double gsl_stats_skew (const double data[], const size_t stride, const size_t n); double gsl_stats_kurtosis (const double data[], const size_t stride, const size_t n); double gsl_stats_lag1_autocorrelation (const double data[], const size_t stride, const size_t n); double gsl_stats_covariance (const double data1[], const size_t stride1,const double data2[], const size_t stride2, const size_t n); double gsl_stats_correlation (const double data1[], const size_t stride1,const double data2[], const size_t stride2, const size_t n); double gsl_stats_variance_m (const double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_sd_m (const double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_absdev_m (const double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_skew_m_sd (const double data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_kurtosis_m_sd (const double data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_lag1_autocorrelation_m (const double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_covariance_m (const double data1[], const size_t stride1,const double data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); /* DEFINED FOR FLOATING POINT TYPES ONLY */ double gsl_stats_wmean (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n); double gsl_stats_wvariance (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n); double gsl_stats_wsd (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n); double gsl_stats_wvariance_with_fixed_mean (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_wsd_with_fixed_mean (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n, const double mean); double gsl_stats_wabsdev (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n); double gsl_stats_wskew (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n); double gsl_stats_wkurtosis (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n); double gsl_stats_wvariance_m (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n, const double wmean); double gsl_stats_wsd_m (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n, const double wmean); double gsl_stats_wabsdev_m (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n, const double wmean); double gsl_stats_wskew_m_sd (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n, const double wmean, const double wsd); double gsl_stats_wkurtosis_m_sd (const double w[], const size_t wstride, const double data[], const size_t stride, const size_t n, const double wmean, const double wsd); /* END OF FLOATING POINT TYPES */ double gsl_stats_pvariance (const double data1[], const size_t stride1, const size_t n1, const double data2[], const size_t stride2, const size_t n2); double gsl_stats_ttest (const double data1[], const size_t stride1, const size_t n1, const double data2[], const size_t stride2, const size_t n2); double gsl_stats_max (const double data[], const size_t stride, const size_t n); double gsl_stats_min (const double data[], const size_t stride, const size_t n); void gsl_stats_minmax (double * min, double * max, const double data[], const size_t stride, const size_t n); size_t gsl_stats_max_index (const double data[], const size_t stride, const size_t n); size_t gsl_stats_min_index (const double data[], const size_t stride, const size_t n); void gsl_stats_minmax_index (size_t * min_index, size_t * max_index, const double data[], const size_t stride, const size_t n); double gsl_stats_median_from_sorted_data (const double sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_quantile_from_sorted_data (const double sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_DOUBLE_H__ */ sources_5316/external/gsl/gsl_siman__siman.c0000664000176700017670000001772011723710247020015 0ustar paulpaul/* siman/siman.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000 Mark Galassi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_machine.h" #include "gsl_rng.h" #include "gsl_siman.h" static inline double boltzmann(double E, double new_E, double T, gsl_siman_params_t *params) { double x = -(new_E - E) / (params->k * T); /* avoid underflow errors for large uphill steps */ return (x < GSL_LOG_DBL_MIN) ? 0.0 : exp(x); } static inline void copy_state(void *src, void *dst, size_t size, gsl_siman_copy_t copyfunc) { if (copyfunc) { copyfunc(src, dst); } else { memcpy(dst, src, size); } } /* implementation of a basic simulated annealing algorithm */ void gsl_siman_solve (const gsl_rng * r, void *x0_p, gsl_siman_Efunc_t Ef, gsl_siman_step_t take_step, gsl_siman_metric_t distance, gsl_siman_print_t print_position, gsl_siman_copy_t copyfunc, gsl_siman_copy_construct_t copy_constructor, gsl_siman_destroy_t destructor, size_t element_size, gsl_siman_params_t params) { void *x, *new_x, *best_x; double E, new_E, best_E; int i; double T, T_factor; int n_evals = 1, n_iter = 0, n_accepts, n_rejects, n_eless; /* this function requires that either the dynamic functions (copy, copy_constructor and destrcutor) are passed, or that an element size is given */ assert((copyfunc != NULL && copy_constructor != NULL && destructor != NULL) || (element_size != 0)); distance = 0 ; /* This parameter is not currently used */ E = Ef(x0_p); if (copyfunc) { x = copy_constructor(x0_p); new_x = copy_constructor(x0_p); best_x = copy_constructor(x0_p); } else { x = (void *) malloc (element_size); memcpy (x, x0_p, element_size); new_x = (void *) malloc (element_size); best_x = (void *) malloc (element_size); memcpy (best_x, x0_p, element_size); } best_E = E; T = params.t_initial; T_factor = 1.0 / params.mu_t; if (print_position) { printf ("#-iter #-evals temperature position energy\n"); } while (1) { n_accepts = 0; n_rejects = 0; n_eless = 0; for (i = 0; i < params.iters_fixed_T; ++i) { copy_state(x, new_x, element_size, copyfunc); take_step (r, new_x, params.step_size); new_E = Ef (new_x); if(new_E <= best_E){ if (copyfunc) { copyfunc(new_x,best_x); } else { memcpy (best_x, new_x, element_size); } best_E=new_E; } ++n_evals; /* keep track of Ef() evaluations */ /* now take the crucial step: see if the new point is accepted or not, as determined by the boltzmann probability */ if (new_E < E) { if (new_E < best_E) { copy_state(new_x, best_x, element_size, copyfunc); best_E = new_E; } /* yay! take a step */ copy_state(new_x, x, element_size, copyfunc); E = new_E; ++n_eless; } else if (gsl_rng_uniform(r) < boltzmann(E, new_E, T, ¶ms)) { /* yay! take a step */ copy_state(new_x, x, element_size, copyfunc); E = new_E; ++n_accepts; } else { ++n_rejects; } } if (print_position) { /* see if we need to print stuff as we go */ /* printf("%5d %12g %5d %3d %3d %3d", n_iter, T, n_evals, */ /* 100*n_eless/n_steps, 100*n_accepts/n_steps, */ /* 100*n_rejects/n_steps); */ printf ("%5d %7d %12g", n_iter, n_evals, T); print_position (x); printf (" %12g %12g\n", E, best_E); } /* apply the cooling schedule to the temperature */ /* FIXME: I should also introduce a cooling schedule for the iters */ T *= T_factor; ++n_iter; if (T < params.t_min) { break; } } /* at the end, copy the result onto the initial point, so we pass it back to the caller */ copy_state(best_x, x0_p, element_size, copyfunc); if (copyfunc) { destructor(x); destructor(new_x); destructor(best_x); } else { free (x); free (new_x); free (best_x); } } /* implementation of a simulated annealing algorithm with many tries */ void gsl_siman_solve_many (const gsl_rng * r, void *x0_p, gsl_siman_Efunc_t Ef, gsl_siman_step_t take_step, gsl_siman_metric_t distance, gsl_siman_print_t print_position, size_t element_size, gsl_siman_params_t params) { /* the new set of trial points, and their energies and probabilities */ void *x, *new_x; double *energies, *probs, *sum_probs; double Ex; /* energy of the chosen point */ double T, T_factor; /* the temperature and a step multiplier */ int i; double u; /* throw the die to choose a new "x" */ int n_iter; if (print_position) { printf ("#-iter temperature position"); printf (" delta_pos energy\n"); } x = (void *) malloc (params.n_tries * element_size); new_x = (void *) malloc (params.n_tries * element_size); energies = (double *) malloc (params.n_tries * sizeof (double)); probs = (double *) malloc (params.n_tries * sizeof (double)); sum_probs = (double *) malloc (params.n_tries * sizeof (double)); T = params.t_initial; T_factor = 1.0 / params.mu_t; memcpy (x, x0_p, element_size); n_iter = 0; while (1) { Ex = Ef (x); for (i = 0; i < params.n_tries - 1; ++i) { /* only go to N_TRIES-2 */ /* center the new_x[] around x, then pass it to take_step() */ sum_probs[i] = 0; memcpy ((char *)new_x + i * element_size, x, element_size); take_step (r, (char *)new_x + i * element_size, params.step_size); energies[i] = Ef ((char *)new_x + i * element_size); probs[i] = boltzmann(Ex, energies[i], T, ¶ms); } /* now add in the old value of "x", so it is a contendor */ memcpy ((char *)new_x + (params.n_tries - 1) * element_size, x, element_size); energies[params.n_tries - 1] = Ex; probs[params.n_tries - 1] = boltzmann(Ex, energies[i], T, ¶ms); /* now throw biased die to see which new_x[i] we choose */ sum_probs[0] = probs[0]; for (i = 1; i < params.n_tries; ++i) { sum_probs[i] = sum_probs[i - 1] + probs[i]; } u = gsl_rng_uniform (r) * sum_probs[params.n_tries - 1]; for (i = 0; i < params.n_tries; ++i) { if (u < sum_probs[i]) { memcpy (x, (char *) new_x + i * element_size, element_size); break; } } if (print_position) { printf ("%5d\t%12g\t", n_iter, T); print_position (x); printf ("\t%12g\t%12g\n", distance (x, x0_p), Ex); } T *= T_factor; ++n_iter; if (T < params.t_min) { break; } } /* now return the value via x0_p */ memcpy (x0_p, x, element_size); /* printf("the result is: %g (E=%g)\n", x, Ex); */ free (x); free (new_x); free (energies); free (probs); free (sum_probs); } sources_5316/external/gsl/gsl_specfunc__bessel_y.c0000664000176700017670000001725211723710247021212 0ustar paulpaul/* specfunc/bessel_y.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_gamma.h" #include "gsl_sf_trig.h" #include "gsl_sf_bessel.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__bessel.h" #include "gsl_specfunc__bessel_olver.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* [Abramowitz+Stegun, 10.1.3] * with lmax=15, precision ~ 15D for x < 3 * * checked OK [GJ] Wed May 13 15:41:25 MDT 1998 */ static int bessel_yl_small_x(int l, const double x, gsl_sf_result * result) { gsl_sf_result num_fact; double den = gsl_sf_pow_int(x, l+1); int stat_df = gsl_sf_doublefact_e(2*l-1, &num_fact); if(stat_df != GSL_SUCCESS || den == 0.0) { OVERFLOW_ERROR(result); } else { const int lmax = 200; double t = -0.5*x*x; double sum = 1.0; double t_coeff = 1.0; double t_power = 1.0; double delta; int i; for(i=1; i<=lmax; i++) { t_coeff /= i*(2*(i-l) - 1); t_power *= t; delta = t_power*t_coeff; sum += delta; if(fabs(delta/sum) < 0.5*GSL_DBL_EPSILON) break; } result->val = -num_fact.val/den * sum; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_y0_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(1.0/GSL_DBL_MAX > 0.0 && x < 1.0/GSL_DBL_MAX) { OVERFLOW_ERROR(result); } else { gsl_sf_result cos_result; const int stat = gsl_sf_cos_e(x, &cos_result); result->val = -cos_result.val/x; result->err = fabs(cos_result.err/x); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } } int gsl_sf_bessel_y1_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 1.0/GSL_SQRT_DBL_MAX) { OVERFLOW_ERROR(result); } else if(x < 0.25) { const double y = x*x; const double c1 = 1.0/2.0; const double c2 = -1.0/8.0; const double c3 = 1.0/144.0; const double c4 = -1.0/5760.0; const double c5 = 1.0/403200.0; const double c6 = -1.0/43545600.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*c6))))); result->val = -sum/y; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result cos_result; gsl_sf_result sin_result; const int stat_cos = gsl_sf_cos_e(x, &cos_result); const int stat_sin = gsl_sf_sin_e(x, &sin_result); const double cx = cos_result.val; const double sx = sin_result.val; result->val = -(cx/x + sx)/x; result->err = (fabs(cos_result.err/x) + sin_result.err)/fabs(x); result->err += GSL_DBL_EPSILON * (fabs(sx/x) + fabs(cx/(x*x))); return GSL_ERROR_SELECT_2(stat_cos, stat_sin); } } int gsl_sf_bessel_y2_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 1.0/GSL_ROOT3_DBL_MAX) { OVERFLOW_ERROR(result); } else if(x < 0.5) { const double y = x*x; const double c1 = 1.0/6.0; const double c2 = 1.0/24.0; const double c3 = -1.0/144.0; const double c4 = 1.0/3456.0; const double c5 = -1.0/172800.0; const double c6 = 1.0/14515200.0; const double c7 = -1.0/1828915200.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*(c6 + y*c7)))))); result->val = -3.0/(x*x*x) * sum; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { gsl_sf_result cos_result; gsl_sf_result sin_result; const int stat_cos = gsl_sf_cos_e(x, &cos_result); const int stat_sin = gsl_sf_sin_e(x, &sin_result); const double sx = sin_result.val; const double cx = cos_result.val; const double a = 3.0/(x*x); result->val = (1.0 - a)/x * cx - a * sx; result->err = cos_result.err * fabs((1.0 - a)/x) + sin_result.err * fabs(a); result->err += GSL_DBL_EPSILON * (fabs(cx/x) + fabs(sx/(x*x))); return GSL_ERROR_SELECT_2(stat_cos, stat_sin); } } int gsl_sf_bessel_yl_e(int l, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(l < 0 || x <= 0.0) { DOMAIN_ERROR(result); } else if(l == 0) { return gsl_sf_bessel_y0_e(x, result); } else if(l == 1) { return gsl_sf_bessel_y1_e(x, result); } else if(l == 2) { return gsl_sf_bessel_y2_e(x, result); } else if(x < 3.0) { return bessel_yl_small_x(l, x, result); } else if(GSL_ROOT3_DBL_EPSILON * x > (l*l + l + 1.0)) { int status = gsl_sf_bessel_Ynu_asympx_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= pre; result->err *= pre; return status; } else if(l > 40) { int status = gsl_sf_bessel_Ynu_asymp_Olver_e(l + 0.5, x, result); double pre = sqrt((0.5*M_PI)/x); result->val *= pre; result->err *= pre; return status; } else { /* recurse upward */ gsl_sf_result r_by; gsl_sf_result r_bym; int stat_1 = gsl_sf_bessel_y1_e(x, &r_by); int stat_0 = gsl_sf_bessel_y0_e(x, &r_bym); double bym = r_bym.val; double by = r_by.val; double byp; int j; for(j=1; jval = by; result->err = fabs(result->val) * (GSL_DBL_EPSILON + fabs(r_by.err/r_by.val) + fabs(r_bym.err/r_bym.val)); return GSL_ERROR_SELECT_2(stat_1, stat_0); } } int gsl_sf_bessel_yl_array(const int lmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(lmax < 0 || x <= 0.0) { GSL_ERROR ("error", GSL_EDOM); } else if (lmax == 0) { gsl_sf_result result; int stat = gsl_sf_bessel_y0_e(x, &result); result_array[0] = result.val; return stat; } else { gsl_sf_result r_yell; gsl_sf_result r_yellm1; int stat_1 = gsl_sf_bessel_y1_e(x, &r_yell); int stat_0 = gsl_sf_bessel_y0_e(x, &r_yellm1); double yellp1; double yell = r_yell.val; double yellm1 = r_yellm1.val; int ell; result_array[0] = yellm1; result_array[1] = yell; for(ell = 1; ell < lmax; ell++) { yellp1 = (2*ell+1)/x * yell - yellm1; result_array[ell+1] = yellp1; yellm1 = yell; yell = yellp1; } return GSL_ERROR_SELECT_2(stat_0, stat_1); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_bessel_y0(const double x) { EVAL_RESULT(gsl_sf_bessel_y0_e(x, &result)); } double gsl_sf_bessel_y1(const double x) { EVAL_RESULT(gsl_sf_bessel_y1_e(x, &result)); } double gsl_sf_bessel_y2(const double x) { EVAL_RESULT(gsl_sf_bessel_y2_e(x, &result)); } double gsl_sf_bessel_yl(const int l, const double x) { EVAL_RESULT(gsl_sf_bessel_yl_e(l, x, &result)); } sources_5316/external/gsl/gsl_specfunc__coupling.c0000664000176700017670000003261711723710247021227 0ustar paulpaul/* specfunc/coupling.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_gamma.h" #include "gsl_sf_coupling.h" #include "gsl_specfunc__error.h" inline static int locMax3(const int a, const int b, const int c) { int d = GSL_MAX(a, b); return GSL_MAX(d, c); } inline static int locMin3(const int a, const int b, const int c) { int d = GSL_MIN(a, b); return GSL_MIN(d, c); } inline static int locMin5(const int a, const int b, const int c, const int d, const int e) { int f = GSL_MIN(a, b); int g = GSL_MIN(c, d); int h = GSL_MIN(f, g); return GSL_MIN(e, h); } /* See: [Thompson, Atlas for Computing Mathematical Functions] */ static int delta(int ta, int tb, int tc, gsl_sf_result * d) { gsl_sf_result f1, f2, f3, f4; int status = 0; status += gsl_sf_fact_e((ta + tb - tc)/2, &f1); status += gsl_sf_fact_e((ta + tc - tb)/2, &f2); status += gsl_sf_fact_e((tb + tc - ta)/2, &f3); status += gsl_sf_fact_e((ta + tb + tc)/2 + 1, &f4); if(status != 0) { OVERFLOW_ERROR(d); } d->val = f1.val * f2.val * f3.val / f4.val; d->err = 4.0 * GSL_DBL_EPSILON * fabs(d->val); return GSL_SUCCESS; } static int triangle_selection_fails(int two_ja, int two_jb, int two_jc) { return ((two_jb < abs(two_ja - two_jc)) || (two_jb > two_ja + two_jc)); } static int m_selection_fails(int two_ja, int two_jb, int two_jc, int two_ma, int two_mb, int two_mc) { return ( abs(two_ma) > two_ja || abs(two_mb) > two_jb || abs(two_mc) > two_jc || GSL_IS_ODD(two_ja + two_ma) || GSL_IS_ODD(two_jb + two_mb) || GSL_IS_ODD(two_jc + two_mc) || (two_ma + two_mb + two_mc) != 0 ); } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_coupling_3j_e (int two_ja, int two_jb, int two_jc, int two_ma, int two_mb, int two_mc, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(two_ja < 0 || two_jb < 0 || two_jc < 0) { DOMAIN_ERROR(result); } else if ( triangle_selection_fails(two_ja, two_jb, two_jc) || m_selection_fails(two_ja, two_jb, two_jc, two_ma, two_mb, two_mc) ) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { int jca = (-two_ja + two_jb + two_jc) / 2, jcb = ( two_ja - two_jb + two_jc) / 2, jcc = ( two_ja + two_jb - two_jc) / 2, jmma = ( two_ja - two_ma) / 2, jmmb = ( two_jb - two_mb) / 2, jmmc = ( two_jc - two_mc) / 2, jpma = ( two_ja + two_ma) / 2, jpmb = ( two_jb + two_mb) / 2, jpmc = ( two_jc + two_mc) / 2, jsum = ( two_ja + two_jb + two_jc) / 2, kmin = locMax3 (0, jpmb - jmmc, jmma - jpmc), kmax = locMin3 (jcc, jmma, jpmb), k, sign = GSL_IS_ODD (kmin - jpma + jmmb) ? -1 : 1, status = 0; double sum_pos = 0.0, sum_neg = 0.0, norm, term; gsl_sf_result bc1, bc2, bc3, bcn1, bcn2, bcd1, bcd2, bcd3, bcd4; status += gsl_sf_choose_e (two_ja, jcc , &bcn1); status += gsl_sf_choose_e (two_jb, jcc , &bcn2); status += gsl_sf_choose_e (jsum+1, jcc , &bcd1); status += gsl_sf_choose_e (two_ja, jmma, &bcd2); status += gsl_sf_choose_e (two_jb, jmmb, &bcd3); status += gsl_sf_choose_e (two_jc, jpmc, &bcd4); if (status != 0) { OVERFLOW_ERROR (result); } norm = sqrt (bcn1.val * bcn2.val) / sqrt (bcd1.val * bcd2.val * bcd3.val * bcd4.val * ((double) two_jc + 1.0)); for (k = kmin; k <= kmax; k++) { status += gsl_sf_choose_e (jcc, k, &bc1); status += gsl_sf_choose_e (jcb, jmma - k, &bc2); status += gsl_sf_choose_e (jca, jpmb - k, &bc3); if (status != 0) { OVERFLOW_ERROR (result); } term = bc1.val * bc2.val * bc3.val; if (sign < 0) { sum_neg += norm * term; } else { sum_pos += norm * term; } sign = -sign; } result->val = sum_pos - sum_neg; result->err = 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += 2.0 * GSL_DBL_EPSILON * (kmax - kmin) * fabs(result->val); return GSL_SUCCESS; } } #if ! defined (GSL_DISABLE_DEPRECATED) int gsl_sf_coupling_6j_INCORRECT_e(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, gsl_sf_result * result) { return gsl_sf_coupling_6j_e(two_ja, two_jb, two_je, two_jd, two_jc, two_jf, result); } #endif int gsl_sf_coupling_6j_e(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if( two_ja < 0 || two_jb < 0 || two_jc < 0 || two_jd < 0 || two_je < 0 || two_jf < 0 ) { DOMAIN_ERROR(result); } else if( triangle_selection_fails(two_ja, two_jb, two_jc) || triangle_selection_fails(two_ja, two_je, two_jf) || triangle_selection_fails(two_jb, two_jd, two_jf) || triangle_selection_fails(two_je, two_jd, two_jc) ) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { gsl_sf_result n1; gsl_sf_result d1, d2, d3, d4, d5, d6; double norm; int tk, tkmin, tkmax; double phase; double sum_pos = 0.0; double sum_neg = 0.0; double sumsq_err = 0.0; int status = 0; status += delta(two_ja, two_jb, two_jc, &d1); status += delta(two_ja, two_je, two_jf, &d2); status += delta(two_jb, two_jd, two_jf, &d3); status += delta(two_je, two_jd, two_jc, &d4); if(status != GSL_SUCCESS) { OVERFLOW_ERROR(result); } norm = sqrt(d1.val) * sqrt(d2.val) * sqrt(d3.val) * sqrt(d4.val); tkmin = locMax3(0, two_ja + two_jd - two_jc - two_jf, two_jb + two_je - two_jc - two_jf); tkmax = locMin5(two_ja + two_jb + two_je + two_jd + 2, two_ja + two_jb - two_jc, two_je + two_jd - two_jc, two_ja + two_je - two_jf, two_jb + two_jd - two_jf); phase = GSL_IS_ODD((two_ja + two_jb + two_je + two_jd + tkmin)/2) ? -1.0 : 1.0; for(tk=tkmin; tk<=tkmax; tk += 2) { double term; double term_err; gsl_sf_result den_1, den_2; gsl_sf_result d1_a, d1_b; status = 0; status += gsl_sf_fact_e((two_ja + two_jb + two_je + two_jd - tk)/2 + 1, &n1); status += gsl_sf_fact_e(tk/2, &d1_a); status += gsl_sf_fact_e((two_jc + two_jf - two_ja - two_jd + tk)/2, &d1_b); status += gsl_sf_fact_e((two_jc + two_jf - two_jb - two_je + tk)/2, &d2); status += gsl_sf_fact_e((two_ja + two_jb - two_jc - tk)/2, &d3); status += gsl_sf_fact_e((two_je + two_jd - two_jc - tk)/2, &d4); status += gsl_sf_fact_e((two_ja + two_je - two_jf - tk)/2, &d5); status += gsl_sf_fact_e((two_jb + two_jd - two_jf - tk)/2, &d6); if(status != GSL_SUCCESS) { OVERFLOW_ERROR(result); } d1.val = d1_a.val * d1_b.val; d1.err = d1_a.err * fabs(d1_b.val) + fabs(d1_a.val) * d1_b.err; den_1.val = d1.val*d2.val*d3.val; den_1.err = d1.err * fabs(d2.val*d3.val); den_1.err += d2.err * fabs(d1.val*d3.val); den_1.err += d3.err * fabs(d1.val*d2.val); den_2.val = d4.val*d5.val*d6.val; den_2.err = d4.err * fabs(d5.val*d6.val); den_2.err += d5.err * fabs(d4.val*d6.val); den_2.err += d6.err * fabs(d4.val*d5.val); term = phase * n1.val / den_1.val / den_2.val; phase = -phase; term_err = n1.err / fabs(den_1.val) / fabs(den_2.val); term_err += fabs(term / den_1.val) * den_1.err; term_err += fabs(term / den_2.val) * den_2.err; if(term >= 0.0) { sum_pos += norm*term; } else { sum_neg -= norm*term; } sumsq_err += norm*norm * term_err*term_err; } result->val = sum_pos - sum_neg; result->err = 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += sqrt(sumsq_err / (0.5*(tkmax-tkmin)+1.0)); result->err += 2.0 * GSL_DBL_EPSILON * (tkmax - tkmin + 2.0) * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_coupling_RacahW_e(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, gsl_sf_result * result) { int status = gsl_sf_coupling_6j_e(two_ja, two_jb, two_je, two_jd, two_jc, two_jf, result); int phase_sum = (two_ja + two_jb + two_jc + two_jd)/2; result->val *= ( GSL_IS_ODD(phase_sum) ? -1.0 : 1.0 ); return status; } int gsl_sf_coupling_9j_e(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, int two_jg, int two_jh, int two_ji, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if( two_ja < 0 || two_jb < 0 || two_jc < 0 || two_jd < 0 || two_je < 0 || two_jf < 0 || two_jg < 0 || two_jh < 0 || two_ji < 0 ) { DOMAIN_ERROR(result); } else if( triangle_selection_fails(two_ja, two_jb, two_jc) || triangle_selection_fails(two_jd, two_je, two_jf) || triangle_selection_fails(two_jg, two_jh, two_ji) || triangle_selection_fails(two_ja, two_jd, two_jg) || triangle_selection_fails(two_jb, two_je, two_jh) || triangle_selection_fails(two_jc, two_jf, two_ji) ) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { int tk; int tkmin = locMax3(abs(two_ja-two_ji), abs(two_jh-two_jd), abs(two_jb-two_jf)); int tkmax = locMin3(two_ja + two_ji, two_jh + two_jd, two_jb + two_jf); double sum_pos = 0.0; double sum_neg = 0.0; double sumsq_err = 0.0; double phase; for(tk=tkmin; tk<=tkmax; tk += 2) { gsl_sf_result s1, s2, s3; double term; double term_err; int status = 0; status += gsl_sf_coupling_6j_e(two_ja, two_ji, tk, two_jh, two_jd, two_jg, &s1); status += gsl_sf_coupling_6j_e(two_jb, two_jf, tk, two_jd, two_jh, two_je, &s2); status += gsl_sf_coupling_6j_e(two_ja, two_ji, tk, two_jf, two_jb, two_jc, &s3); if(status != GSL_SUCCESS) { OVERFLOW_ERROR(result); } term = s1.val * s2.val * s3.val; term_err = s1.err * fabs(s2.val*s3.val); term_err += s2.err * fabs(s1.val*s3.val); term_err += s3.err * fabs(s1.val*s2.val); if(term >= 0.0) { sum_pos += (tk + 1) * term; } else { sum_neg -= (tk + 1) * term; } sumsq_err += ((tk+1) * term_err) * ((tk+1) * term_err); } phase = GSL_IS_ODD(tkmin) ? -1.0 : 1.0; result->val = phase * (sum_pos - sum_neg); result->err = 2.0 * GSL_DBL_EPSILON * (sum_pos + sum_neg); result->err += sqrt(sumsq_err / (0.5*(tkmax-tkmin)+1.0)); result->err += 2.0 * GSL_DBL_EPSILON * (tkmax-tkmin + 2.0) * fabs(result->val); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_coupling_3j(int two_ja, int two_jb, int two_jc, int two_ma, int two_mb, int two_mc) { EVAL_RESULT(gsl_sf_coupling_3j_e(two_ja, two_jb, two_jc, two_ma, two_mb, two_mc, &result)); } #if ! defined (GSL_DISABLE_DEPRECATED) double gsl_sf_coupling_6j_INCORRECT(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf) { EVAL_RESULT(gsl_sf_coupling_6j_INCORRECT_e(two_ja, two_jb, two_jc, two_jd, two_je, two_jf, &result)); } #endif double gsl_sf_coupling_6j(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf) { EVAL_RESULT(gsl_sf_coupling_6j_e(two_ja, two_jb, two_jc, two_jd, two_je, two_jf, &result)); } double gsl_sf_coupling_RacahW(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf) { EVAL_RESULT(gsl_sf_coupling_RacahW_e(two_ja, two_jb, two_jc, two_jd, two_je, two_jf, &result)); } double gsl_sf_coupling_9j(int two_ja, int two_jb, int two_jc, int two_jd, int two_je, int two_jf, int two_jg, int two_jh, int two_ji) { EVAL_RESULT(gsl_sf_coupling_9j_e(two_ja, two_jb, two_jc, two_jd, two_je, two_jf, two_jg, two_jh, two_ji, &result)); } sources_5316/external/gsl/gsl_cblas__source_trmm_c.h0000664000176700017670000003003011705263724021521 0ustar paulpaul/* blas/source_trmm_c.h * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j, k; INDEX n1, n2; const int nonunit = (Diag == CblasNonUnit); const int conj = (TransA == CblasConjTrans) ? -1 : 1; int side, uplo, trans; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); if (Order == CblasRowMajor) { n1 = M; n2 = N; side = Side; uplo = Uplo; trans = (TransA == CblasNoTrans) ? CblasNoTrans : CblasTrans; } else { n1 = N; n2 = M; side = (Side == CblasLeft) ? CblasRight : CblasLeft; /* exchanged */ uplo = (Uplo == CblasUpper) ? CblasLower : CblasUpper; /* exchanged */ trans = (TransA == CblasNoTrans) ? CblasNoTrans : CblasTrans; /* same */ } if (side == CblasLeft && uplo == CblasUpper && trans == CblasNoTrans) { /* form B := alpha * TriU(A)*B */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; if (nonunit) { const BASE Aii_real = CONST_REAL(A, i * lda + i); const BASE Aii_imag = conj * CONST_IMAG(A, i * lda + i); const BASE Bij_real = REAL(B, i * ldb + j); const BASE Bij_imag = IMAG(B, i * ldb + j); temp_real = Aii_real * Bij_real - Aii_imag * Bij_imag; temp_imag = Aii_real * Bij_imag + Aii_imag * Bij_real; } else { temp_real = REAL(B, i * ldb + j); temp_imag = IMAG(B, i * ldb + j); } for (k = i + 1; k < n1; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = conj * CONST_IMAG(A, i * lda + k); const BASE Bkj_real = REAL(B, k * ldb + j); const BASE Bkj_imag = IMAG(B, k * ldb + j); temp_real += Aik_real * Bkj_real - Aik_imag * Bkj_imag; temp_imag += Aik_real * Bkj_imag + Aik_imag * Bkj_real; } REAL(B, ldb * i + j) = alpha_real * temp_real - alpha_imag * temp_imag; IMAG(B, ldb * i + j) = alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (side == CblasLeft && uplo == CblasUpper && trans == CblasTrans) { /* form B := alpha * (TriU(A))' *B */ for (i = n1; i > 0 && i--;) { for (j = 0; j < n2; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < i; k++) { const BASE Aki_real = CONST_REAL(A, k * lda + i); const BASE Aki_imag = conj * CONST_IMAG(A, k * lda + i); const BASE Bkj_real = REAL(B, k * ldb + j); const BASE Bkj_imag = IMAG(B, k * ldb + j); temp_real += Aki_real * Bkj_real - Aki_imag * Bkj_imag; temp_imag += Aki_real * Bkj_imag + Aki_imag * Bkj_real; } if (nonunit) { const BASE Aii_real = CONST_REAL(A, i * lda + i); const BASE Aii_imag = conj * CONST_IMAG(A, i * lda + i); const BASE Bij_real = REAL(B, i * ldb + j); const BASE Bij_imag = IMAG(B, i * ldb + j); temp_real += Aii_real * Bij_real - Aii_imag * Bij_imag; temp_imag += Aii_real * Bij_imag + Aii_imag * Bij_real; } else { temp_real += REAL(B, i * ldb + j); temp_imag += IMAG(B, i * ldb + j); } REAL(B, ldb * i + j) = alpha_real * temp_real - alpha_imag * temp_imag; IMAG(B, ldb * i + j) = alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (side == CblasLeft && uplo == CblasLower && trans == CblasNoTrans) { /* form B := alpha * TriL(A)*B */ for (i = n1; i > 0 && i--;) { for (j = 0; j < n2; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < i; k++) { const BASE Aik_real = CONST_REAL(A, i * lda + k); const BASE Aik_imag = conj * CONST_IMAG(A, i * lda + k); const BASE Bkj_real = REAL(B, k * ldb + j); const BASE Bkj_imag = IMAG(B, k * ldb + j); temp_real += Aik_real * Bkj_real - Aik_imag * Bkj_imag; temp_imag += Aik_real * Bkj_imag + Aik_imag * Bkj_real; } if (nonunit) { const BASE Aii_real = CONST_REAL(A, i * lda + i); const BASE Aii_imag = conj * CONST_IMAG(A, i * lda + i); const BASE Bij_real = REAL(B, i * ldb + j); const BASE Bij_imag = IMAG(B, i * ldb + j); temp_real += Aii_real * Bij_real - Aii_imag * Bij_imag; temp_imag += Aii_real * Bij_imag + Aii_imag * Bij_real; } else { temp_real += REAL(B, i * ldb + j); temp_imag += IMAG(B, i * ldb + j); } REAL(B, ldb * i + j) = alpha_real * temp_real - alpha_imag * temp_imag; IMAG(B, ldb * i + j) = alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (side == CblasLeft && uplo == CblasLower && trans == CblasTrans) { /* form B := alpha * TriL(A)' *B */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; if (nonunit) { const BASE Aii_real = CONST_REAL(A, i * lda + i); const BASE Aii_imag = conj * CONST_IMAG(A, i * lda + i); const BASE Bij_real = REAL(B, i * ldb + j); const BASE Bij_imag = IMAG(B, i * ldb + j); temp_real = Aii_real * Bij_real - Aii_imag * Bij_imag; temp_imag = Aii_real * Bij_imag + Aii_imag * Bij_real; } else { temp_real = REAL(B, i * ldb + j); temp_imag = IMAG(B, i * ldb + j); } for (k = i + 1; k < n1; k++) { const BASE Aki_real = CONST_REAL(A, k * lda + i); const BASE Aki_imag = conj * CONST_IMAG(A, k * lda + i); const BASE Bkj_real = REAL(B, k * ldb + j); const BASE Bkj_imag = IMAG(B, k * ldb + j); temp_real += Aki_real * Bkj_real - Aki_imag * Bkj_imag; temp_imag += Aki_real * Bkj_imag + Aki_imag * Bkj_real; } REAL(B, ldb * i + j) = alpha_real * temp_real - alpha_imag * temp_imag; IMAG(B, ldb * i + j) = alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (side == CblasRight && uplo == CblasUpper && trans == CblasNoTrans) { /* form B := alpha * B * TriU(A) */ for (i = 0; i < n1; i++) { for (j = n2; j > 0 && j--;) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < j; k++) { const BASE Akj_real = CONST_REAL(A, k * lda + j); const BASE Akj_imag = conj * CONST_IMAG(A, k * lda + j); const BASE Bik_real = REAL(B, i * ldb + k); const BASE Bik_imag = IMAG(B, i * ldb + k); temp_real += Akj_real * Bik_real - Akj_imag * Bik_imag; temp_imag += Akj_real * Bik_imag + Akj_imag * Bik_real; } if (nonunit) { const BASE Ajj_real = CONST_REAL(A, j * lda + j); const BASE Ajj_imag = conj * CONST_IMAG(A, j * lda + j); const BASE Bij_real = REAL(B, i * ldb + j); const BASE Bij_imag = IMAG(B, i * ldb + j); temp_real += Ajj_real * Bij_real - Ajj_imag * Bij_imag; temp_imag += Ajj_real * Bij_imag + Ajj_imag * Bij_real; } else { temp_real += REAL(B, i * ldb + j); temp_imag += IMAG(B, i * ldb + j); } REAL(B, ldb * i + j) = alpha_real * temp_real - alpha_imag * temp_imag; IMAG(B, ldb * i + j) = alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (side == CblasRight && uplo == CblasUpper && trans == CblasTrans) { /* form B := alpha * B * (TriU(A))' */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; if (nonunit) { const BASE Ajj_real = CONST_REAL(A, j * lda + j); const BASE Ajj_imag = conj * CONST_IMAG(A, j * lda + j); const BASE Bij_real = REAL(B, i * ldb + j); const BASE Bij_imag = IMAG(B, i * ldb + j); temp_real = Ajj_real * Bij_real - Ajj_imag * Bij_imag; temp_imag = Ajj_real * Bij_imag + Ajj_imag * Bij_real; } else { temp_real = REAL(B, i * ldb + j); temp_imag = IMAG(B, i * ldb + j); } for (k = j + 1; k < n2; k++) { const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = conj * CONST_IMAG(A, j * lda + k); const BASE Bik_real = REAL(B, i * ldb + k); const BASE Bik_imag = IMAG(B, i * ldb + k); temp_real += Ajk_real * Bik_real - Ajk_imag * Bik_imag; temp_imag += Ajk_real * Bik_imag + Ajk_imag * Bik_real; } REAL(B, ldb * i + j) = alpha_real * temp_real - alpha_imag * temp_imag; IMAG(B, ldb * i + j) = alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (side == CblasRight && uplo == CblasLower && trans == CblasNoTrans) { /* form B := alpha *B * TriL(A) */ for (i = 0; i < n1; i++) { for (j = 0; j < n2; j++) { BASE temp_real = 0.0; BASE temp_imag = 0.0; if (nonunit) { const BASE Ajj_real = CONST_REAL(A, j * lda + j); const BASE Ajj_imag = conj * CONST_IMAG(A, j * lda + j); const BASE Bij_real = REAL(B, i * ldb + j); const BASE Bij_imag = IMAG(B, i * ldb + j); temp_real = Ajj_real * Bij_real - Ajj_imag * Bij_imag; temp_imag = Ajj_real * Bij_imag + Ajj_imag * Bij_real; } else { temp_real = REAL(B, i * ldb + j); temp_imag = IMAG(B, i * ldb + j); } for (k = j + 1; k < n2; k++) { const BASE Akj_real = CONST_REAL(A, k * lda + j); const BASE Akj_imag = conj * CONST_IMAG(A, k * lda + j); const BASE Bik_real = REAL(B, i * ldb + k); const BASE Bik_imag = IMAG(B, i * ldb + k); temp_real += Akj_real * Bik_real - Akj_imag * Bik_imag; temp_imag += Akj_real * Bik_imag + Akj_imag * Bik_real; } REAL(B, ldb * i + j) = alpha_real * temp_real - alpha_imag * temp_imag; IMAG(B, ldb * i + j) = alpha_real * temp_imag + alpha_imag * temp_real; } } } else if (side == CblasRight && uplo == CblasLower && trans == CblasTrans) { /* form B := alpha * B * TriL(A)' */ for (i = 0; i < n1; i++) { for (j = n2; j > 0 && j--;) { BASE temp_real = 0.0; BASE temp_imag = 0.0; for (k = 0; k < j; k++) { const BASE Ajk_real = CONST_REAL(A, j * lda + k); const BASE Ajk_imag = conj * CONST_IMAG(A, j * lda + k); const BASE Bik_real = REAL(B, i * ldb + k); const BASE Bik_imag = IMAG(B, i * ldb + k); temp_real += Ajk_real * Bik_real - Ajk_imag * Bik_imag; temp_imag += Ajk_real * Bik_imag + Ajk_imag * Bik_real; } if (nonunit) { const BASE Ajj_real = CONST_REAL(A, j * lda + j); const BASE Ajj_imag = conj * CONST_IMAG(A, j * lda + j); const BASE Bij_real = REAL(B, i * ldb + j); const BASE Bij_imag = IMAG(B, i * ldb + j); temp_real += Ajj_real * Bij_real - Ajj_imag * Bij_imag; temp_imag += Ajj_real * Bij_imag + Ajj_imag * Bij_real; } else { temp_real += REAL(B, i * ldb + j); temp_imag += IMAG(B, i * ldb + j); } REAL(B, ldb * i + j) = alpha_real * temp_real - alpha_imag * temp_imag; IMAG(B, ldb * i + j) = alpha_real * temp_imag + alpha_imag * temp_real; } } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_cblas__dsyr.c0000664000176700017670000000052211723710247017634 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dsyr (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *X, const int incX, double *A, const int lda) { #define BASE double #include "gsl_cblas__source_syr.h" #undef BASE } sources_5316/external/gsl/gsl_sf__trig.c0000644000176700017670000004642610707442037017157 0ustar paulpaul/* specfunc/trig.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_log.h" #include "gsl_sf_trig.h" #include "gsl_sf__error.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" /* sinh(x) series * double-precision for |x| < 1.0 */ inline static int sinh_series(const double x, double * result) { const double y = x*x; const double c0 = 1.0/6.0; const double c1 = 1.0/120.0; const double c2 = 1.0/5040.0; const double c3 = 1.0/362880.0; const double c4 = 1.0/39916800.0; const double c5 = 1.0/6227020800.0; const double c6 = 1.0/1307674368000.0; const double c7 = 1.0/355687428096000.0; *result = x*(1.0 + y*(c0+y*(c1+y*(c2+y*(c3+y*(c4+y*(c5+y*(c6+y*c7)))))))); return GSL_SUCCESS; } /* cosh(x)-1 series * double-precision for |x| < 1.0 */ inline static int cosh_m1_series(const double x, double * result) { const double y = x*x; const double c0 = 0.5; const double c1 = 1.0/24.0; const double c2 = 1.0/720.0; const double c3 = 1.0/40320.0; const double c4 = 1.0/3628800.0; const double c5 = 1.0/479001600.0; const double c6 = 1.0/87178291200.0; const double c7 = 1.0/20922789888000.0; const double c8 = 1.0/6402373705728000.0; *result = y*(c0+y*(c1+y*(c2+y*(c3+y*(c4+y*(c5+y*(c6+y*(c7+y*c8)))))))); return GSL_SUCCESS; } /* Chebyshev expansion for f(t) = sinc((t+1)/2), -1 < t < 1 */ static double sinc_data[17] = { 1.133648177811747875422, -0.532677564732557348781, -0.068293048346633177859, 0.033403684226353715020, 0.001485679893925747818, -0.000734421305768455295, -0.000016837282388837229, 0.000008359950146618018, 0.000000117382095601192, -0.000000058413665922724, -0.000000000554763755743, 0.000000000276434190426, 0.000000000001895374892, -0.000000000000945237101, -0.000000000000004900690, 0.000000000000002445383, 0.000000000000000009925 }; static cheb_series sinc_cs = { sinc_data, 16, -1, 1, 10 }; /* Chebyshev expansion for f(t) = g((t+1)Pi/8), -1val = x * (1.0 - x2/6.0); result->err = fabs(x*x2*x2 / 100.0); return GSL_SUCCESS; } else { double sgn_result = sgn_x; double y = floor(abs_x/(0.25*M_PI)); int octant = y - ldexp(floor(ldexp(y,-3)),3); int stat_cs; double z; if(GSL_IS_ODD(octant)) { octant += 1; octant &= 07; y += 1.0; } if(octant > 3) { octant -= 4; sgn_result = -sgn_result; } z = ((abs_x - y * P1) - y * P2) - y * P3; if(octant == 0) { gsl_sf_result sin_cs_result; const double t = 8.0*fabs(z)/M_PI - 1.0; stat_cs = cheb_eval_e(&sin_cs, t, &sin_cs_result); result->val = z * (1.0 + z*z * sin_cs_result.val); } else { /* octant == 2 */ gsl_sf_result cos_cs_result; const double t = 8.0*fabs(z)/M_PI - 1.0; stat_cs = cheb_eval_e(&cos_cs, t, &cos_cs_result); result->val = 1.0 - 0.5*z*z * (1.0 - z*z * cos_cs_result.val); } result->val *= sgn_result; if(abs_x > 1.0/GSL_DBL_EPSILON) { result->err = fabs(result->val); } else if(abs_x > 100.0/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * abs_x * GSL_DBL_EPSILON * fabs(result->val); } else if(abs_x > 0.1/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * GSL_SQRT_DBL_EPSILON * fabs(result->val); } else { result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return stat_cs; } } } int gsl_sf_cos_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { const double P1 = 7.85398125648498535156e-1; const double P2 = 3.77489470793079817668e-8; const double P3 = 2.69515142907905952645e-15; const double abs_x = fabs(x); if(abs_x < GSL_ROOT4_DBL_EPSILON) { const double x2 = x*x; result->val = 1.0 - 0.5*x2; result->err = fabs(x2*x2/12.0); return GSL_SUCCESS; } else { double sgn_result = 1.0; double y = floor(abs_x/(0.25*M_PI)); int octant = y - ldexp(floor(ldexp(y,-3)),3); int stat_cs; double z; if(GSL_IS_ODD(octant)) { octant += 1; octant &= 07; y += 1.0; } if(octant > 3) { octant -= 4; sgn_result = -sgn_result; } if(octant > 1) { sgn_result = -sgn_result; } z = ((abs_x - y * P1) - y * P2) - y * P3; if(octant == 0) { gsl_sf_result cos_cs_result; const double t = 8.0*fabs(z)/M_PI - 1.0; stat_cs = cheb_eval_e(&cos_cs, t, &cos_cs_result); result->val = 1.0 - 0.5*z*z * (1.0 - z*z * cos_cs_result.val); } else { /* octant == 2 */ gsl_sf_result sin_cs_result; const double t = 8.0*fabs(z)/M_PI - 1.0; stat_cs = cheb_eval_e(&sin_cs, t, &sin_cs_result); result->val = z * (1.0 + z*z * sin_cs_result.val); } result->val *= sgn_result; if(abs_x > 1.0/GSL_DBL_EPSILON) { result->err = fabs(result->val); } else if(abs_x > 100.0/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * abs_x * GSL_DBL_EPSILON * fabs(result->val); } else if(abs_x > 0.1/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * GSL_SQRT_DBL_EPSILON * fabs(result->val); } else { result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); } return stat_cs; } } } int gsl_sf_hypot_e(const double x, const double y, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0 && y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else { const double a = fabs(x); const double b = fabs(y); const double min = GSL_MIN_DBL(a,b); const double max = GSL_MAX_DBL(a,b); const double rat = min/max; const double root_term = sqrt(1.0 + rat*rat); if(max < GSL_DBL_MAX/root_term) { result->val = max * root_term; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } } int gsl_sf_complex_sin_e(const double zr, const double zi, gsl_sf_result * szr, gsl_sf_result * szi) { /* CHECK_POINTER(szr) */ /* CHECK_POINTER(szi) */ if(fabs(zi) < 1.0) { double ch_m1, sh; sinh_series(zi, &sh); cosh_m1_series(zi, &ch_m1); szr->val = sin(zr)*(ch_m1 + 1.0); szi->val = cos(zr)*sh; szr->err = 2.0 * GSL_DBL_EPSILON * fabs(szr->val); szi->err = 2.0 * GSL_DBL_EPSILON * fabs(szi->val); return GSL_SUCCESS; } else if(fabs(zi) < GSL_LOG_DBL_MAX) { double ex = exp(zi); double ch = 0.5*(ex+1.0/ex); double sh = 0.5*(ex-1.0/ex); szr->val = sin(zr)*ch; szi->val = cos(zr)*sh; szr->err = 2.0 * GSL_DBL_EPSILON * fabs(szr->val); szi->err = 2.0 * GSL_DBL_EPSILON * fabs(szi->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR_2(szr, szi); } } int gsl_sf_complex_cos_e(const double zr, const double zi, gsl_sf_result * czr, gsl_sf_result * czi) { /* CHECK_POINTER(czr) */ /* CHECK_POINTER(czi) */ if(fabs(zi) < 1.0) { double ch_m1, sh; sinh_series(zi, &sh); cosh_m1_series(zi, &ch_m1); czr->val = cos(zr)*(ch_m1 + 1.0); czi->val = -sin(zr)*sh; czr->err = 2.0 * GSL_DBL_EPSILON * fabs(czr->val); czi->err = 2.0 * GSL_DBL_EPSILON * fabs(czi->val); return GSL_SUCCESS; } else if(fabs(zi) < GSL_LOG_DBL_MAX) { double ex = exp(zi); double ch = 0.5*(ex+1.0/ex); double sh = 0.5*(ex-1.0/ex); czr->val = cos(zr)*ch; czi->val = -sin(zr)*sh; czr->err = 2.0 * GSL_DBL_EPSILON * fabs(czr->val); czi->err = 2.0 * GSL_DBL_EPSILON * fabs(czi->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR_2(czr,czi); } } int gsl_sf_complex_logsin_e(const double zr, const double zi, gsl_sf_result * lszr, gsl_sf_result * lszi) { /* CHECK_POINTER(lszr) */ /* CHECK_POINTER(lszi) */ if(zi > 60.0) { lszr->val = -M_LN2 + zi; lszi->val = 0.5*M_PI - zr; lszr->err = 2.0 * GSL_DBL_EPSILON * fabs(lszr->val); lszi->err = 2.0 * GSL_DBL_EPSILON * fabs(lszi->val); } else if(zi < -60.0) { lszr->val = -M_LN2 - zi; lszi->val = -0.5*M_PI + zr; lszr->err = 2.0 * GSL_DBL_EPSILON * fabs(lszr->val); lszi->err = 2.0 * GSL_DBL_EPSILON * fabs(lszi->val); } else { gsl_sf_result sin_r, sin_i; int status; gsl_sf_complex_sin_e(zr, zi, &sin_r, &sin_i); /* ok by construction */ status = gsl_sf_complex_log_e(sin_r.val, sin_i.val, lszr, lszi); if(status == GSL_EDOM) { DOMAIN_ERROR_2(lszr, lszi); } } return gsl_sf_angle_restrict_symm_e(&(lszi->val)); } int gsl_sf_lnsinh_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(fabs(x) < 1.0) { double eps; sinh_series(x, &eps); result->val = log(eps); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -0.5*GSL_LOG_DBL_EPSILON) { result->val = x + log(0.5*(1.0 - exp(-2.0*x))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = -M_LN2 + x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_lncosh_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(fabs(x) < 1.0) { double eps; cosh_m1_series(x, &eps); return gsl_sf_log_1plusx_e(eps, result); } else if(x < -0.5*GSL_LOG_DBL_EPSILON) { result->val = x + log(0.5*(1.0 + exp(-2.0*x))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = -M_LN2 + x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /* inline int gsl_sf_sincos_e(const double theta, double * s, double * c) { double tan_half = tan(0.5 * theta); double den = 1. + tan_half*tan_half; double cos_theta = (1.0 - tan_half*tan_half) / den; double sin_theta = 2.0 * tan_half / den; } */ int gsl_sf_polar_to_rect(const double r, const double theta, gsl_sf_result * x, gsl_sf_result * y) { double t = theta; int status = gsl_sf_angle_restrict_symm_e(&t); double c = cos(t); double s = sin(t); x->val = r * cos(t); y->val = r * sin(t); x->err = r * fabs(s * GSL_DBL_EPSILON * t); x->err += 2.0 * GSL_DBL_EPSILON * fabs(x->val); y->err = r * fabs(c * GSL_DBL_EPSILON * t); y->err += 2.0 * GSL_DBL_EPSILON * fabs(y->val); return status; } int gsl_sf_rect_to_polar(const double x, const double y, gsl_sf_result * r, gsl_sf_result * theta) { int stat_h = gsl_sf_hypot_e(x, y, r); if(r->val > 0.0) { theta->val = atan2(y, x); theta->err = 2.0 * GSL_DBL_EPSILON * fabs(theta->val); return stat_h; } else { DOMAIN_ERROR(theta); } } int gsl_sf_angle_restrict_symm_err_e(const double theta, gsl_sf_result * result) { /* synthetic extended precision constants */ const double P1 = 4 * 7.8539812564849853515625e-01; const double P2 = 4 * 3.7748947079307981766760e-08; const double P3 = 4 * 2.6951514290790594840552e-15; const double TwoPi = 2*(P1 + P2 + P3); const double y = GSL_SIGN(theta) * 2 * floor(fabs(theta)/TwoPi); double r = ((theta - y*P1) - y*P2) - y*P3; if(r > M_PI) { r = (((r-2*P1)-2*P2)-2*P3); } /* r-TwoPi */ else if (r < -M_PI) r = (((r+2*P1)+2*P2)+2*P3); /* r+TwoPi */ result->val = r; if(fabs(theta) > 0.0625/GSL_DBL_EPSILON) { result->val = GSL_NAN; result->err = GSL_NAN; GSL_ERROR ("error", GSL_ELOSS); } else if(fabs(theta) > 0.0625/GSL_SQRT_DBL_EPSILON) { result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val - theta); return GSL_SUCCESS; } else { double delta = fabs(result->val - theta); result->err = 2.0 * GSL_DBL_EPSILON * ((delta < M_PI) ? delta : M_PI); return GSL_SUCCESS; } } int gsl_sf_angle_restrict_pos_err_e(const double theta, gsl_sf_result * result) { /* synthetic extended precision constants */ const double P1 = 4 * 7.85398125648498535156e-01; const double P2 = 4 * 3.77489470793079817668e-08; const double P3 = 4 * 2.69515142907905952645e-15; const double TwoPi = 2*(P1 + P2 + P3); const double y = 2*floor(theta/TwoPi); double r = ((theta - y*P1) - y*P2) - y*P3; if(r > TwoPi) {r = (((r-2*P1)-2*P2)-2*P3); } /* r-TwoPi */ else if (r < 0) { /* may happen due to FP rounding */ r = (((r+2*P1)+2*P2)+2*P3); /* r+TwoPi */ } result->val = r; if(fabs(theta) > 0.0625/GSL_DBL_EPSILON) { result->val = GSL_NAN; result->err = fabs(result->val); GSL_ERROR ("error", GSL_ELOSS); } else if(fabs(theta) > 0.0625/GSL_SQRT_DBL_EPSILON) { result->err = GSL_DBL_EPSILON * fabs(result->val - theta); return GSL_SUCCESS; } else { double delta = fabs(result->val - theta); result->err = 2.0 * GSL_DBL_EPSILON * ((delta < M_PI) ? delta : M_PI); return GSL_SUCCESS; } } int gsl_sf_angle_restrict_symm_e(double * theta) { gsl_sf_result r; int stat = gsl_sf_angle_restrict_symm_err_e(*theta, &r); *theta = r.val; return stat; } int gsl_sf_angle_restrict_pos_e(double * theta) { gsl_sf_result r; int stat = gsl_sf_angle_restrict_pos_err_e(*theta, &r); *theta = r.val; return stat; } int gsl_sf_sin_err_e(const double x, const double dx, gsl_sf_result * result) { int stat_s = gsl_sf_sin_e(x, result); result->err += fabs(cos(x) * dx); result->err += GSL_DBL_EPSILON * fabs(result->val); return stat_s; } int gsl_sf_cos_err_e(const double x, const double dx, gsl_sf_result * result) { int stat_c = gsl_sf_cos_e(x, result); result->err += fabs(sin(x) * dx); result->err += GSL_DBL_EPSILON * fabs(result->val); return stat_c; } #if 0 int gsl_sf_sin_pi_x_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(-100.0 < x && x < 100.0) { result->val = sin(M_PI * x) / (M_PI * x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double N = floor(x + 0.5); const double f = x - N; if(N < INT_MAX && N > INT_MIN) { /* Make it an integer if we can. Saves another * call to floor(). */ const int intN = (int)N; const double sign = ( GSL_IS_ODD(intN) ? -1.0 : 1.0 ); result->val = sign * sin(M_PI * f); result->err = GSL_DBL_EPSILON * fabs(result->val); } else if(N > 2.0/GSL_DBL_EPSILON || N < -2.0/GSL_DBL_EPSILON) { /* All integer-valued floating point numbers * bigger than 2/eps=2^53 are actually even. */ result->val = 0.0; result->err = 0.0; } else { const double resN = N - 2.0*floor(0.5*N); /* 0 for even N, 1 for odd N */ const double sign = ( fabs(resN) > 0.5 ? -1.0 : 1.0 ); result->val = sign * sin(M_PI*f); result->err = GSL_DBL_EPSILON * fabs(result->val); } return GSL_SUCCESS; } } #endif int gsl_sf_sinc_e(double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { const double ax = fabs(x); if(ax < 0.8) { /* Do not go to the limit of the fit since * there is a zero there and the Chebyshev * accuracy will go to zero. */ return cheb_eval_e(&sinc_cs, 2.0*ax-1.0, result); } else if(ax < 100.0) { /* Small arguments are no problem. * We trust the library sin() to * roughly machine precision. */ result->val = sin(M_PI * ax)/(M_PI * ax); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { /* Large arguments must be handled separately. */ const double r = M_PI*ax; gsl_sf_result s; int stat_s = gsl_sf_sin_e(r, &s); result->val = s.val/r; result->err = s.err/r + 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_s; } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_sin(const double x) { EVAL_RESULT(gsl_sf_sin_e(x, &result)); } double gsl_sf_cos(const double x) { EVAL_RESULT(gsl_sf_cos_e(x, &result)); } double gsl_sf_hypot(const double x, const double y) { EVAL_RESULT(gsl_sf_hypot_e(x, y, &result)); } double gsl_sf_lnsinh(const double x) { EVAL_RESULT(gsl_sf_lnsinh_e(x, &result)); } double gsl_sf_lncosh(const double x) { EVAL_RESULT(gsl_sf_lncosh_e(x, &result)); } double gsl_sf_angle_restrict_symm(const double theta) { double result = theta; EVAL_DOUBLE(gsl_sf_angle_restrict_symm_e(&result)); } double gsl_sf_angle_restrict_pos(const double theta) { double result = theta; EVAL_DOUBLE(gsl_sf_angle_restrict_pos_e(&result)); } #if 0 double gsl_sf_sin_pi_x(const double x) { EVAL_RESULT(gsl_sf_sin_pi_x_e(x, &result)); } #endif double gsl_sf_sinc(const double x) { EVAL_RESULT(gsl_sf_sinc_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__source_symv.h0000664000176700017670000000530411705263724021244 0ustar paulpaul/* blas/source_symv.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; if (alpha == 0.0 && beta == 1.0) return; /* form y := beta*y */ if (beta == 0.0) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { Y[iy] = 0.0; iy += incY; } } else if (beta != 1.0) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { Y[iy] *= beta; iy += incY; } } if (alpha == 0.0) return; /* form y := alpha*A*x + y */ if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { BASE temp1 = alpha * X[ix]; BASE temp2 = 0.0; const INDEX j_min = i + 1; const INDEX j_max = N; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; Y[iy] += temp1 * A[lda * i + i]; for (j = j_min; j < j_max; j++) { Y[jy] += temp1 * A[lda * i + j]; temp2 += X[jx] * A[lda * i + j]; jx += incX; jy += incY; } Y[iy] += alpha * temp2; ix += incX; iy += incY; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX) + (N - 1) * incX; INDEX iy = OFFSET(N, incY) + (N - 1) * incY; for (i = N; i > 0 && i--;) { BASE temp1 = alpha * X[ix]; BASE temp2 = 0.0; const INDEX j_min = 0; const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; Y[iy] += temp1 * A[lda * i + i]; for (j = j_min; j < j_max; j++) { Y[jy] += temp1 * A[lda * i + j]; temp2 += X[jx] * A[lda * i + j]; jx += incX; jy += incY; } Y[iy] += alpha * temp2; ix -= incX; iy -= incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_multifit__gradient.c0000664000176700017670000000216211723710247021223 0ustar paulpaul/* multifit/covar.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multifit_nlin.h" #include "gsl_blas.h" int gsl_multifit_gradient (const gsl_matrix * J, const gsl_vector * f, gsl_vector * g) { int status = gsl_blas_dgemv (CblasTrans, 1.0, J, f, 0.0, g); return status; } sources_5316/external/gsl/gsl_cblas__stpsv.c0000664000176700017670000000056211723710247020036 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_stpsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const float *Ap, float *X, const int incX) { #define BASE float #include "gsl_cblas__source_tpsv_r.h" #undef BASE } sources_5316/external/gsl/gsl_fft__hc_init.c0000664000176700017670000000634311723710247017772 0ustar paulpaul/* fft/hc_init.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ TYPE(gsl_fft_halfcomplex_wavetable) * FUNCTION(gsl_fft_halfcomplex_wavetable,alloc) (size_t n) { int status; size_t i; size_t n_factors; size_t t, product, product_1, q; double d_theta; TYPE(gsl_fft_halfcomplex_wavetable) * wavetable ; if (n == 0) { GSL_ERROR_VAL ("length n must be positive integer", GSL_EDOM, 0); } wavetable = (TYPE(gsl_fft_halfcomplex_wavetable) *) malloc(sizeof(TYPE(gsl_fft_halfcomplex_wavetable))); if (wavetable == NULL) { GSL_ERROR_VAL ("failed to allocate struct", GSL_ENOMEM, 0); } wavetable->trig = (TYPE(gsl_complex) *) malloc (n * sizeof (TYPE(gsl_complex))); if (wavetable->trig == NULL) { /* error in constructor, prevent memory leak */ free(wavetable) ; GSL_ERROR_VAL ("failed to allocate trigonometric lookup table", GSL_ENOMEM, 0); } wavetable->n = n ; status = fft_halfcomplex_factorize (n, &n_factors, wavetable->factor); if (status) { /* error in constructor, prevent memory leak */ free(wavetable->trig) ; free(wavetable) ; GSL_ERROR_VAL ("factorization failed", GSL_EFACTOR, 0); } wavetable->nf = n_factors; d_theta = 2.0 * M_PI / ((double) n); t = 0; product = 1; for (i = 0; i < n_factors; i++) { size_t j; const size_t factor = wavetable->factor[i]; wavetable->twiddle[i] = wavetable->trig + t; product_1 = product; /* product_1 = p_(i-1) */ product *= factor; q = n / product; for (j = 1; j < factor; j++) { size_t k; size_t m = 0; for (k = 1; k < (q + 1) / 2; k++) { double theta; m = m + j * product_1; m = m % n; theta = d_theta * m; /* d_theta*j*k*product_1 */ GSL_REAL(wavetable->trig[t]) = cos (theta); GSL_IMAG(wavetable->trig[t]) = sin (theta); t++; } } } if (t > (n / 2)) { /* error in constructor, prevent memory leak */ free(wavetable->trig) ; free(wavetable) ; GSL_ERROR_VAL ("overflowed trigonometric lookup table", GSL_ESANITY, 0); } return wavetable; } void FUNCTION(gsl_fft_halfcomplex_wavetable,free) (TYPE(gsl_fft_halfcomplex_wavetable) * wavetable) { /* release trigonometric lookup tables */ free (wavetable->trig); wavetable->trig = NULL; free (wavetable); } sources_5316/external/gsl/gsl_cblas__cdotu_sub.c0000664000176700017670000000046711723710247020652 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_cdotu_sub (const int N, const void *X, const int incX, const void *Y, const int incY, void *result) { #define BASE float #define CONJ_SIGN 1.0 #include "gsl_cblas__source_dot_c.h" #undef CONJ_SIGN #undef BASE } sources_5316/external/gsl/gsl_cblas__dtbsv.c0000664000176700017670000000063511723710247020002 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dtbsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const double *A, const int lda, double *X, const int incX) { #define BASE double #include "gsl_cblas__source_tbsv_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__drot.c0000664000176700017670000000042311723710247017623 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_drot (const int N, double *X, const int incX, double *Y, const int incY, const double c, const double s) { #define BASE double #include "gsl_cblas__source_rot.h" #undef BASE } sources_5316/external/gsl/gsl_sys__infnan.c0000664000176700017670000000454611723710247017670 0ustar paulpaul/* sys/infnan.c * * Copyright (C) 2001, 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #if HAVE_IEEEFP_H #include #endif double gsl_nan (void); double gsl_posinf (void); double gsl_neginf (void); double gsl_fdiv (const double x, const double y); double gsl_nan (void) { return gsl_fdiv (0.0, 0.0); } double gsl_posinf (void) { return gsl_fdiv (+1.0, 0.0); } double gsl_neginf (void) { return gsl_fdiv (-1.0, 0.0); } int gsl_isnan (const double x); int gsl_isinf (const double x); int gsl_finite (const double x); #if defined(_MSC_VER) /* Microsoft Visual C++ */ #include int gsl_isnan (const double x) { return _isnan(x); } int gsl_isinf (const double x) { int fpc = _fpclass(x); if (fpc == _FPCLASS_PINF) return +1; else if (fpc == _FPCLASS_NINF) return -1; else return 0; } int gsl_finite (const double x) { return _finite(x); } #else # if HAVE_DECL_ISFINITE int gsl_finite (const double x) { return isfinite(x); } # elif HAVE_DECL_FINITE int gsl_finite (const double x) { return finite(x); } # elif HAVE_IEEE_COMPARISONS int gsl_finite (const double x) { const double y = x - x; int status = (y == y); return status; } # endif # if HAVE_DECL_ISNAN int gsl_isnan (const double x) { return isnan(x); } #elif HAVE_IEEE_COMPARISONS int gsl_isnan (const double x) { int status = (x != x); return status; } # endif # if HAVE_DECL_ISINF int gsl_isinf (const double x) { return isinf(x); } # else int gsl_isinf (const double x) { if (! gsl_finite(x) && ! gsl_isnan(x)) { return (x > 0 ? +1 : -1); } else { return 0; } } # endif #endif sources_5316/external/gsl/gsl_permute_vector_complex_double.h0000664000176700017670000000275311705263724023514 0ustar paulpaul/* permutation/gsl_permute_vector_complex_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_COMPLEX_DOUBLE_H__ #define __GSL_PERMUTE_VECTOR_COMPLEX_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_complex_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_complex (const gsl_permutation * p, gsl_vector_complex * v); int gsl_permute_vector_complex_inverse (const gsl_permutation * p, gsl_vector_complex * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_COMPLEX_DOUBLE_H__ */ sources_5316/external/gsl/gsl_roots__brent.c0000664000176700017670000001147111723710247020054 0ustar paulpaul/* roots/brent.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* brent.c -- brent root finding algorithm */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_roots.h" #include "gsl_roots__roots.h" typedef struct { double a, b, c, d, e; double fa, fb, fc; } brent_state_t; static int brent_init (void * vstate, gsl_function * f, double * root, double x_lower, double x_upper); static int brent_iterate (void * vstate, gsl_function * f, double * root, double * x_lower, double * x_upper); static int brent_init (void * vstate, gsl_function * f, double * root, double x_lower, double x_upper) { brent_state_t * state = (brent_state_t *) vstate; double f_lower, f_upper ; *root = 0.5 * (x_lower + x_upper) ; SAFE_FUNC_CALL (f, x_lower, &f_lower); SAFE_FUNC_CALL (f, x_upper, &f_upper); state->a = x_lower; state->fa = f_lower; state->b = x_upper; state->fb = f_upper; state->c = x_upper; state->fc = f_upper; state->d = x_upper - x_lower ; state->e = x_upper - x_lower ; if ((f_lower < 0.0 && f_upper < 0.0) || (f_lower > 0.0 && f_upper > 0.0)) { GSL_ERROR ("endpoints do not straddle y=0", GSL_EINVAL); } return GSL_SUCCESS; } static int brent_iterate (void * vstate, gsl_function * f, double * root, double * x_lower, double * x_upper) { brent_state_t * state = (brent_state_t *) vstate; double tol, m; int ac_equal = 0; double a = state->a, b = state->b, c = state->c; double fa = state->fa, fb = state->fb, fc = state->fc; double d = state->d, e = state->e; if ((fb < 0 && fc < 0) || (fb > 0 && fc > 0)) { ac_equal = 1; c = a; fc = fa; d = b - a; e = b - a; } if (fabs (fc) < fabs (fb)) { ac_equal = 1; a = b; b = c; c = a; fa = fb; fb = fc; fc = fa; } tol = 0.5 * GSL_DBL_EPSILON * fabs (b); m = 0.5 * (c - b); if (fb == 0) { *root = b; *x_lower = b; *x_upper = b; return GSL_SUCCESS; } if (fabs (m) <= tol) { *root = b; if (b < c) { *x_lower = b; *x_upper = c; } else { *x_lower = c; *x_upper = b; } return GSL_SUCCESS; } if (fabs (e) < tol || fabs (fa) <= fabs (fb)) { d = m; /* use bisection */ e = m; } else { double p, q, r; /* use inverse cubic interpolation */ double s = fb / fa; if (ac_equal) { p = 2 * m * s; q = 1 - s; } else { q = fa / fc; r = fb / fc; p = s * (2 * m * q * (q - r) - (b - a) * (r - 1)); q = (q - 1) * (r - 1) * (s - 1); } if (p > 0) { q = -q; } else { p = -p; } if (2 * p < GSL_MIN (3 * m * q - fabs (tol * q), fabs (e * q))) { e = d; d = p / q; } else { /* interpolation failed, fall back to bisection */ d = m; e = m; } } a = b; fa = fb; if (fabs (d) > tol) { b += d; } else { b += (m > 0 ? +tol : -tol); } SAFE_FUNC_CALL (f, b, &fb); state->a = a ; state->b = b ; state->c = c ; state->d = d ; state->e = e ; state->fa = fa ; state->fb = fb ; state->fc = fc ; /* Update the best estimate of the root and bounds on each iteration */ *root = b; if ((fb < 0 && fc < 0) || (fb > 0 && fc > 0)) { c = a; } if (b < c) { *x_lower = b; *x_upper = c; } else { *x_lower = c; *x_upper = b; } return GSL_SUCCESS ; } static const gsl_root_fsolver_type brent_type = {"brent", /* name */ sizeof (brent_state_t), &brent_init, &brent_iterate}; const gsl_root_fsolver_type * gsl_root_fsolver_brent = &brent_type; sources_5316/external/gsl/gsl_cblas__isamax.c0000664000176700017670000000033511723710247020137 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" CBLAS_INDEX cblas_isamax (const int N, const float *X, const int incX) { #define BASE float #include "gsl_cblas__source_iamax_r.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__ssymm.c0000664000176700017670000000067211723710247020031 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ssymm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const float alpha, const float *A, const int lda, const float *B, const int ldb, const float beta, float *C, const int ldc) { #define BASE float #include "gsl_cblas__source_symm_r.h" #undef BASE } sources_5316/external/gsl/gsl_sf_airy.h0000664000176700017670000000716511705263724017026 0ustar paulpaul/* specfunc/gsl_sf_airy.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_AIRY_H__ #define __GSL_SF_AIRY_H__ #include "gsl_mode.h" #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Airy function Ai(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_airy_Ai_e(const double x, const gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_airy_Ai(const double x, gsl_mode_t mode); /* Airy function Bi(x) * * exceptions: GSL_EOVRFLW */ int gsl_sf_airy_Bi_e(const double x, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_airy_Bi(const double x, gsl_mode_t mode); /* scaled Ai(x): * Ai(x) x < 0 * exp(+2/3 x^{3/2}) Ai(x) x > 0 * * exceptions: none */ int gsl_sf_airy_Ai_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_airy_Ai_scaled(const double x, gsl_mode_t mode); /* scaled Bi(x): * Bi(x) x < 0 * exp(-2/3 x^{3/2}) Bi(x) x > 0 * * exceptions: none */ int gsl_sf_airy_Bi_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_airy_Bi_scaled(const double x, gsl_mode_t mode); /* derivative Ai'(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_airy_Ai_deriv_e(const double x, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_airy_Ai_deriv(const double x, gsl_mode_t mode); /* derivative Bi'(x) * * exceptions: GSL_EOVRFLW */ int gsl_sf_airy_Bi_deriv_e(const double x, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_airy_Bi_deriv(const double x, gsl_mode_t mode); /* scaled derivative Ai'(x): * Ai'(x) x < 0 * exp(+2/3 x^{3/2}) Ai'(x) x > 0 * * exceptions: none */ int gsl_sf_airy_Ai_deriv_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_airy_Ai_deriv_scaled(const double x, gsl_mode_t mode); /* scaled derivative: * Bi'(x) x < 0 * exp(-2/3 x^{3/2}) Bi'(x) x > 0 * * exceptions: none */ int gsl_sf_airy_Bi_deriv_scaled_e(const double x, gsl_mode_t mode, gsl_sf_result * result); double gsl_sf_airy_Bi_deriv_scaled(const double x, gsl_mode_t mode); /* Zeros of Ai(x) */ int gsl_sf_airy_zero_Ai_e(unsigned int s, gsl_sf_result * result); double gsl_sf_airy_zero_Ai(unsigned int s); /* Zeros of Bi(x) */ int gsl_sf_airy_zero_Bi_e(unsigned int s, gsl_sf_result * result); double gsl_sf_airy_zero_Bi(unsigned int s); /* Zeros of Ai'(x) */ int gsl_sf_airy_zero_Ai_deriv_e(unsigned int s, gsl_sf_result * result); double gsl_sf_airy_zero_Ai_deriv(unsigned int s); /* Zeros of Bi'(x) */ int gsl_sf_airy_zero_Bi_deriv_e(unsigned int s, gsl_sf_result * result); double gsl_sf_airy_zero_Bi_deriv(unsigned int s); __END_DECLS #endif /* __GSL_SF_AIRY_H__ */ sources_5316/external/gsl/gsl_vector__copy_source.c0000664000176700017670000000300711723710247021424 0ustar paulpaul/* vector/copy_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_vector, memcpy) (TYPE (gsl_vector) * dest, const TYPE (gsl_vector) * src) { const size_t src_size = src->size; const size_t dest_size = dest->size; if (src_size != dest_size) { GSL_ERROR ("vector lengths are not equal", GSL_EBADLEN); } { const size_t src_stride = src->stride ; const size_t dest_stride = dest->stride ; size_t j; for (j = 0; j < src_size; j++) { size_t k; for (k = 0; k < MULTIPLICITY; k++) { dest->data[MULTIPLICITY * dest_stride * j + k] = src->data[MULTIPLICITY * src_stride * j + k]; } } } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__zhpr2.c0000664000176700017670000000054211723710247017722 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zhpr2 (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *X, const int incX, const void *Y, const int incY, void *Ap) { #define BASE double #include "gsl_cblas__source_hpr2.h" #undef BASE } sources_5316/external/gsl/gsl_statistics__wskew.c0000664000176700017670000000075011723710247021124 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__wskew_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__wskew_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__wskew_source.c" #include "templates_off.h" #undef BASE_FLOAT sources_5316/external/gsl/gsl_integration__append.c0000664000176700017670000000233511723710247021365 0ustar paulpaul/* integration/append.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static inline void append_interval (gsl_integration_workspace * workspace, double a1, double b1, double area1, double error1) { const size_t i_new = workspace->size ; workspace->alist[i_new] = a1; workspace->blist[i_new] = b1; workspace->rlist[i_new] = area1; workspace->elist[i_new] = error1; workspace->order[i_new] = i_new; workspace->level[i_new] = 0; workspace->size++; } sources_5316/external/gsl/gsl_sort_vector_short.h0000664000176700017670000000342411705263724021154 0ustar paulpaul/* sort/gsl_sort_vector_short.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_SHORT_H__ #define __GSL_SORT_VECTOR_SHORT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_short.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_short (gsl_vector_short * v); int gsl_sort_vector_short_index (gsl_permutation * p, const gsl_vector_short * v); int gsl_sort_vector_short_smallest (short * dest, const size_t k, const gsl_vector_short * v); int gsl_sort_vector_short_largest (short * dest, const size_t k, const gsl_vector_short * v); int gsl_sort_vector_short_smallest_index (size_t * p, const size_t k, const gsl_vector_short * v); int gsl_sort_vector_short_largest_index (size_t * p, const size_t k, const gsl_vector_short * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_SHORT_H__ */ sources_5316/external/gsl/gsl_cblas__source_ger.h0000664000176700017670000000270411705263724021024 0ustar paulpaul/* blas/source_ger.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; if (order == CblasRowMajor) { INDEX ix = OFFSET(M, incX); for (i = 0; i < M; i++) { const BASE tmp = alpha * X[ix]; INDEX jy = OFFSET(N, incY); for (j = 0; j < N; j++) { A[lda * i + j] += Y[jy] * tmp; jy += incY; } ix += incX; } } else if (order == CblasColMajor) { INDEX jy = OFFSET(N, incY); for (j = 0; j < N; j++) { const BASE tmp = alpha * Y[jy]; INDEX ix = OFFSET(M, incX); for (i = 0; i < M; i++) { A[i + lda * j] += X[ix] * tmp; ix += incX; } jy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_specfunc__coulomb_bound.c0000664000176700017670000000727611723710247022241 0ustar paulpaul/* specfunc/coulomb_bound.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_laguerre.h" #include "gsl_sf_coulomb.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__check.h" /* normalization for hydrogenic wave functions */ static int R_norm(const int n, const int l, const double Z, gsl_sf_result * result) { double A = 2.0*Z/n; double pre = sqrt(A*A*A /(2.0*n)); gsl_sf_result ln_a, ln_b; gsl_sf_result ex; int stat_a = gsl_sf_lnfact_e(n+l, &ln_a); int stat_b = gsl_sf_lnfact_e(n-l-1, &ln_b); double diff_val = 0.5*(ln_b.val - ln_a.val); double diff_err = 0.5*(ln_b.err + ln_a.err) + GSL_DBL_EPSILON * fabs(diff_val); int stat_e = gsl_sf_exp_err_e(diff_val, diff_err, &ex); result->val = pre * ex.val; result->err = pre * ex.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_e, stat_a, stat_b); } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_hydrogenicR_1_e(const double Z, const double r, gsl_sf_result * result) { if(Z > 0.0 && r >= 0.0) { double A = 2.0*Z; double norm = A*sqrt(Z); double ea = exp(-Z*r); result->val = norm*ea; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val) * fabs(Z*r); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } else { DOMAIN_ERROR(result); } } int gsl_sf_hydrogenicR_e(const int n, const int l, const double Z, const double r, gsl_sf_result * result) { if(n < 1 || l > n-1 || Z <= 0.0 || r < 0.0) { DOMAIN_ERROR(result); } else { double A = 2.0*Z/n; gsl_sf_result norm; int stat_norm = R_norm(n, l, Z, &norm); double rho = A*r; double ea = exp(-0.5*rho); double pp = gsl_sf_pow_int(rho, l); gsl_sf_result lag; int stat_lag = gsl_sf_laguerre_n_e(n-l-1, 2*l+1, rho, &lag); double W_val = norm.val * ea * pp; double W_err = norm.err * ea * pp; W_err += norm.val * ((0.5*rho + 1.0) * GSL_DBL_EPSILON) * ea * pp; W_err += norm.val * ea * ((l+1.0) * GSL_DBL_EPSILON) * pp; result->val = W_val * lag.val; result->err = W_val * lag.err + W_err * fabs(lag.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); if ((l == 0 || (r > 0 && l > 0)) && lag.val != 0.0 && stat_lag == GSL_SUCCESS && stat_norm == GSL_SUCCESS) { CHECK_UNDERFLOW(result); }; return GSL_ERROR_SELECT_2(stat_lag, stat_norm); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_hydrogenicR_1(const double Z, const double r) { EVAL_RESULT(gsl_sf_hydrogenicR_1_e(Z, r, &result)); } double gsl_sf_hydrogenicR(const int n, const int l, const double Z, const double r) { EVAL_RESULT(gsl_sf_hydrogenicR_e(n, l, Z, r, &result)); } sources_5316/external/gsl/gsl_ode-initval__rkck.c0000664000176700017670000002050011723710247020732 0ustar paulpaul/* ode-initval/rkck.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Runge-Kutta 4(5), Cash-Karp */ /* Reference: Cash, J.R., Karp, A.H., ACM Transactions of Mathematical Software, vol. 16 (1990) 201-222. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" /* Cash-Karp constants */ static const double ah[] = { 1.0 / 5.0, 0.3, 3.0 / 5.0, 1.0, 7.0 / 8.0 }; static const double b21 = 1.0 / 5.0; static const double b3[] = { 3.0 / 40.0, 9.0 / 40.0 }; static const double b4[] = { 0.3, -0.9, 1.2 }; static const double b5[] = { -11.0 / 54.0, 2.5, -70.0 / 27.0, 35.0 / 27.0 }; static const double b6[] = { 1631.0 / 55296.0, 175.0 / 512.0, 575.0 / 13824.0, 44275.0 / 110592.0, 253.0 / 4096.0 }; static const double c1 = 37.0 / 378.0; static const double c3 = 250.0 / 621.0; static const double c4 = 125.0 / 594.0; static const double c6 = 512.0 / 1771.0; /* These are the differences of fifth and fourth order coefficients for error estimation */ static const double ec[] = { 0.0, 37.0 / 378.0 - 2825.0 / 27648.0, 0.0, 250.0 / 621.0 - 18575.0 / 48384.0, 125.0 / 594.0 - 13525.0 / 55296.0, -277.0 / 14336.0, 512.0 / 1771.0 - 0.25 }; typedef struct { double *k1; double *k2; double *k3; double *k4; double *k5; double *k6; double *y0; double *ytmp; } rkck_state_t; static void * rkck_alloc (size_t dim) { rkck_state_t *state = (rkck_state_t *) malloc (sizeof (rkck_state_t)); if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for rkck_state", GSL_ENOMEM); } state->k1 = (double *) malloc (dim * sizeof (double)); if (state->k1 == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for k1", GSL_ENOMEM); } state->k2 = (double *) malloc (dim * sizeof (double)); if (state->k2 == 0) { free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k2", GSL_ENOMEM); } state->k3 = (double *) malloc (dim * sizeof (double)); if (state->k3 == 0) { free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k3", GSL_ENOMEM); } state->k4 = (double *) malloc (dim * sizeof (double)); if (state->k4 == 0) { free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k4", GSL_ENOMEM); } state->k5 = (double *) malloc (dim * sizeof (double)); if (state->k5 == 0) { free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k5", GSL_ENOMEM); } state->k6 = (double *) malloc (dim * sizeof (double)); if (state->k6 == 0) { free (state->k5); free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for k6", GSL_ENOMEM); } state->y0 = (double *) malloc (dim * sizeof (double)); if (state->y0 == 0) { free (state->k6); free (state->k5); free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } state->ytmp = (double *) malloc (dim * sizeof (double)); if (state->ytmp == 0) { free (state->y0); free (state->k6); free (state->k5); free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); GSL_ERROR_NULL ("failed to allocate space for ytmp", GSL_ENOMEM); } return state; } static int rkck_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { rkck_state_t *state = (rkck_state_t *) vstate; size_t i; double *const k1 = state->k1; double *const k2 = state->k2; double *const k3 = state->k3; double *const k4 = state->k4; double *const k5 = state->k5; double *const k6 = state->k6; double *const ytmp = state->ytmp; double *const y0 = state->y0; DBL_MEMCPY (y0, y, dim); /* k1 step */ if (dydt_in != NULL) { DBL_MEMCPY (k1, dydt_in, dim); } else { int s = GSL_ODEIV_FN_EVAL (sys, t, y, k1); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + b21 * h * k1[i]; /* k2 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[0] * h, ytmp, k2); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b3[0] * k1[i] + b3[1] * k2[i]); /* k3 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[1] * h, ytmp, k3); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b4[0] * k1[i] + b4[1] * k2[i] + b4[2] * k3[i]); /* k4 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[2] * h, ytmp, k4); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b5[0] * k1[i] + b5[1] * k2[i] + b5[2] * k3[i] + b5[3] * k4[i]); /* k5 step */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[3] * h, ytmp, k5); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) ytmp[i] = y[i] + h * (b6[0] * k1[i] + b6[1] * k2[i] + b6[2] * k3[i] + b6[3] * k4[i] + b6[4] * k5[i]); /* k6 step and final sum */ { int s = GSL_ODEIV_FN_EVAL (sys, t + ah[4] * h, ytmp, k6); if (s != GSL_SUCCESS) { return s; } } for (i = 0; i < dim; i++) { const double d_i = c1 * k1[i] + c3 * k3[i] + c4 * k4[i] + c6 * k6[i]; y[i] += h * d_i; } /* Evaluate dydt_out[]. */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore initial values */ DBL_MEMCPY (y, y0, dim); return s; } } /* difference between 4th and 5th order */ for (i = 0; i < dim; i++) { yerr[i] = h * (ec[1] * k1[i] + ec[3] * k3[i] + ec[4] * k4[i] + ec[5] * k5[i] + ec[6] * k6[i]); } return GSL_SUCCESS; } static int rkck_reset (void *vstate, size_t dim) { rkck_state_t *state = (rkck_state_t *) vstate; DBL_ZERO_MEMSET (state->k1, dim); DBL_ZERO_MEMSET (state->k2, dim); DBL_ZERO_MEMSET (state->k3, dim); DBL_ZERO_MEMSET (state->k4, dim); DBL_ZERO_MEMSET (state->k5, dim); DBL_ZERO_MEMSET (state->k6, dim); DBL_ZERO_MEMSET (state->ytmp, dim); DBL_ZERO_MEMSET (state->y0, dim); return GSL_SUCCESS; } static unsigned int rkck_order (void *vstate) { rkck_state_t *state = (rkck_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 5; /* FIXME: should this be 4? */ } static void rkck_free (void *vstate) { rkck_state_t *state = (rkck_state_t *) vstate; free (state->ytmp); free (state->y0); free (state->k6); free (state->k5); free (state->k4); free (state->k3); free (state->k2); free (state->k1); free (state); } static const gsl_odeiv_step_type rkck_type = { "rkck", /* name */ 1, /* can use dydt_in */ 1, /* gives exact dydt_out */ &rkck_alloc, &rkck_apply, &rkck_reset, &rkck_order, &rkck_free }; const gsl_odeiv_step_type *gsl_odeiv_step_rkck = &rkck_type; sources_5316/external/gsl/gsl_statistics__wkurtosis_source.c0000664000176700017670000000427011723710247023417 0ustar paulpaul/* statistics/wkurtosis_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,wkurtosis) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n) { const double wmean = FUNCTION(gsl_stats,wmean)(w, wstride, data, stride, n); const double wsd = FUNCTION(gsl_stats,wsd_m)(w, wstride, data, stride, n, wmean); return FUNCTION(gsl_stats,wkurtosis_m_sd)(w, wstride, data, stride, n, wmean, wsd); } double FUNCTION(gsl_stats,wkurtosis_m_sd) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n, const double wmean, const double wsd) { /* takes a dataset and finds the kurtosis */ long double wavg = 0, kurtosis; long double W = 0; size_t i; /* find the fourth moment the deviations, normalized by the sd */ /* we use a recurrence relation to stably update a running value so there aren't any large sums that can overflow */ for (i = 0; i < n; i++) { BASE wi = w[i * wstride]; if (wi > 0) { const long double x = (data[i * stride] - wmean) / wsd; W += wi ; wavg += (x * x * x * x - wavg) * (wi / W); } } kurtosis = wavg - 3.0; /* makes kurtosis zero for a Gaussian */ return kurtosis; } sources_5316/external/gsl/gsl_cblas__dspr2.c0000664000176700017670000000055111723710247017707 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dspr2 (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *X, const int incX, const double *Y, const int incY, double *Ap) { #define BASE double #include "gsl_cblas__source_spr2.h" #undef BASE } sources_5316/external/gsl/gsl_linalg__householdercomplex.c0000664000176700017670000001644611723710247022762 0ustar paulpaul/* linalg/householdercomplex.c * * Copyright (C) 2001, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Computes a householder transformation matrix H such that * * H' v = -/+ |v| e_1 * * where e_1 is the first unit vector. On exit the matrix H can be * computed from the return values (tau, v) * * H = I - tau * w * w' * * where w = (1, v(2), ..., v(N)). The nonzero element of the result * vector -/+|v| e_1 is stored in v(1). * * Note that the matrix H' in the householder transformation is the * hermitian conjugate of H. To compute H'v, pass the conjugate of * tau as the first argument to gsl_linalg_householder_hm() rather * than tau itself. See the LAPACK function CLARFG for details of this * convention. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_blas.h" #include "gsl_complex_math.h" #include "gsl_linalg.h" gsl_complex gsl_linalg_complex_householder_transform (gsl_vector_complex * v) { /* replace v[0:n-1] with a householder vector (v[0:n-1]) and coefficient tau that annihilate v[1:n-1] */ const size_t n = v->size ; if (n == 1) { gsl_complex alpha = gsl_vector_complex_get (v, 0) ; double absa = gsl_complex_abs (alpha); double beta_r = - (GSL_REAL(alpha) >= 0 ? +1 : -1) * absa ; gsl_complex tau; if (beta_r == 0.0) { GSL_REAL(tau) = 0.0; GSL_IMAG(tau) = 0.0; } else { GSL_REAL(tau) = (beta_r - GSL_REAL(alpha)) / beta_r ; GSL_IMAG(tau) = - GSL_IMAG(alpha) / beta_r ; { gsl_complex beta = gsl_complex_rect (beta_r, 0.0); gsl_vector_complex_set (v, 0, beta) ; } } return tau; } else { gsl_complex tau ; double beta_r; gsl_vector_complex_view x = gsl_vector_complex_subvector (v, 1, n - 1) ; gsl_complex alpha = gsl_vector_complex_get (v, 0) ; double absa = gsl_complex_abs (alpha); double xnorm = gsl_blas_dznrm2 (&x.vector); if (xnorm == 0 && GSL_IMAG(alpha) == 0) { gsl_complex zero = gsl_complex_rect(0.0, 0.0); return zero; /* tau = 0 */ } beta_r = - (GSL_REAL(alpha) >= 0 ? +1 : -1) * hypot(absa, xnorm) ; GSL_REAL(tau) = (beta_r - GSL_REAL(alpha)) / beta_r ; GSL_IMAG(tau) = - GSL_IMAG(alpha) / beta_r ; { gsl_complex amb = gsl_complex_sub_real(alpha, beta_r); gsl_complex s = gsl_complex_inverse(amb); gsl_blas_zscal (s, &x.vector); } { gsl_complex beta = gsl_complex_rect (beta_r, 0.0); gsl_vector_complex_set (v, 0, beta) ; } return tau; } } int gsl_linalg_complex_householder_hm (gsl_complex tau, const gsl_vector_complex * v, gsl_matrix_complex * A) { /* applies a householder transformation v,tau to matrix m */ size_t i, j; if (GSL_REAL(tau) == 0.0 && GSL_IMAG(tau) == 0.0) { return GSL_SUCCESS; } /* w = (v' A)^T */ for (j = 0; j < A->size2; j++) { gsl_complex tauwj; gsl_complex wj = gsl_matrix_complex_get(A,0,j); for (i = 1; i < A->size1; i++) /* note, computed for v(0) = 1 above */ { gsl_complex Aij = gsl_matrix_complex_get(A,i,j); gsl_complex vi = gsl_vector_complex_get(v,i); gsl_complex Av = gsl_complex_mul (Aij, gsl_complex_conjugate(vi)); wj = gsl_complex_add (wj, Av); } tauwj = gsl_complex_mul (tau, wj); /* A = A - v w^T */ { gsl_complex A0j = gsl_matrix_complex_get (A, 0, j); gsl_complex Atw = gsl_complex_sub (A0j, tauwj); /* store A0j - tau * wj */ gsl_matrix_complex_set (A, 0, j, Atw); } for (i = 1; i < A->size1; i++) { gsl_complex vi = gsl_vector_complex_get (v, i); gsl_complex tauvw = gsl_complex_mul(vi, tauwj); gsl_complex Aij = gsl_matrix_complex_get (A, i, j); gsl_complex Atwv = gsl_complex_sub (Aij, tauvw); /* store Aij - tau * vi * wj */ gsl_matrix_complex_set (A, i, j, Atwv); } } return GSL_SUCCESS; } int gsl_linalg_complex_householder_mh (gsl_complex tau, const gsl_vector_complex * v, gsl_matrix_complex * A) { /* applies a householder transformation v,tau to matrix m on the right */ size_t i, j; if (GSL_REAL(tau) == 0.0 && GSL_IMAG(tau) == 0.0) { return GSL_SUCCESS; } /* A -> A - A*tau*v*v^h */ for (i = 0; i < A->size1; i++) { gsl_complex tauwi; gsl_complex Ai0 = gsl_matrix_complex_get (A, i, 0); gsl_complex wi = Ai0; /* compute w = A v */ for (j = 1; j < A->size2; j++) /* note, computed for v(0) = 1 above */ { gsl_complex Aij = gsl_matrix_complex_get(A, i, j); gsl_complex vj = gsl_vector_complex_get(v, j); gsl_complex Av = gsl_complex_mul (Aij, vj); wi = gsl_complex_add (wi, Av); } tauwi = gsl_complex_mul (tau, wi); /* A = A - w v^H */ { gsl_complex Atw = gsl_complex_sub (Ai0, tauwi); /* store Ai0 - tau * wi */ gsl_matrix_complex_set (A, i, 0, Atw); } for (j = 1; j < A->size2; j++) { gsl_complex vj = gsl_vector_complex_get (v, j); gsl_complex tauwv = gsl_complex_mul(gsl_complex_conjugate(vj), tauwi); gsl_complex Aij = gsl_matrix_complex_get (A, i, j); gsl_complex Atwv = gsl_complex_sub (Aij, tauwv); /* store Aij - tau * wi * conj(vj) */ gsl_matrix_complex_set (A, i, j, Atwv); } } return GSL_SUCCESS; } int gsl_linalg_complex_householder_hv (gsl_complex tau, const gsl_vector_complex * v, gsl_vector_complex * w) { const size_t N = v->size; if (GSL_REAL(tau) == 0.0 && GSL_IMAG(tau) == 0.0) return GSL_SUCCESS; { /* compute z = v'w */ gsl_complex z0 = gsl_vector_complex_get(w,0); gsl_complex z1, z; gsl_complex tz, ntz; gsl_vector_complex_const_view v1 = gsl_vector_complex_const_subvector(v, 1, N-1); gsl_vector_complex_view w1 = gsl_vector_complex_subvector(w, 1, N-1); gsl_blas_zdotc(&v1.vector, &w1.vector, &z1); z = gsl_complex_add (z0, z1); tz = gsl_complex_mul(tau, z); ntz = gsl_complex_negative (tz); /* compute w = w - tau * (v'w) * v */ { gsl_complex w0 = gsl_vector_complex_get(w, 0); gsl_complex w0ntz = gsl_complex_add (w0, ntz); gsl_vector_complex_set (w, 0, w0ntz); } gsl_blas_zaxpy(ntz, &v1.vector, &w1.vector); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_poly__solve_quadratic.c0000664000176700017670000000373011723710247021743 0ustar paulpaul/* poly/solve_quadratic.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* solve_quadratic.c - finds the real roots of a x^2 + b x + c = 0 */ #include "gsl__config.h" #include #include "gsl_poly.h" int gsl_poly_solve_quadratic (double a, double b, double c, double *x0, double *x1) { double disc = b * b - 4 * a * c; if (a == 0) /* Handle linear case */ { if (b == 0) { return 0; } else { *x0 = -c / b; return 1; }; } if (disc > 0) { if (b == 0) { double r = fabs (0.5 * sqrt (disc) / a); *x0 = -r; *x1 = r; } else { double sgnb = (b > 0 ? 1 : -1); double temp = -0.5 * (b + sgnb * sqrt (disc)); double r1 = temp / a ; double r2 = c / temp ; if (r1 < r2) { *x0 = r1 ; *x1 = r2 ; } else { *x0 = r2 ; *x1 = r1 ; } } return 2; } else if (disc == 0) { *x0 = -0.5 * b / a ; *x1 = -0.5 * b / a ; return 2 ; } else { return 0; } } sources_5316/external/gsl/gsl_specfunc__beta_inc.c0000664000176700017670000001337011723710247021146 0ustar paulpaul/* specfunc/beta_inc.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_log.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_hyperg.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__check.h" static double isnegint (const double x) { return (x < 0) && (x == floor(x)); } static int beta_cont_frac( const double a, const double b, const double x, gsl_sf_result * result ) { const unsigned int max_iter = 512; /* control iterations */ const double cutoff = 2.0 * GSL_DBL_MIN; /* control the zero cutoff */ unsigned int iter_count = 0; double cf; /* standard initialization for continued fraction */ double num_term = 1.0; double den_term = 1.0 - (a+b)*x/(a+1.0); if (fabs(den_term) < cutoff) den_term = cutoff; den_term = 1.0/den_term; cf = den_term; while(iter_count < max_iter) { const int k = iter_count + 1; double coeff = k*(b-k)*x/(((a-1.0)+2*k)*(a+2*k)); double delta_frac; /* first step */ den_term = 1.0 + coeff*den_term; num_term = 1.0 + coeff/num_term; if(fabs(den_term) < cutoff) den_term = cutoff; if(fabs(num_term) < cutoff) num_term = cutoff; den_term = 1.0/den_term; delta_frac = den_term * num_term; cf *= delta_frac; coeff = -(a+k)*(a+b+k)*x/((a+2*k)*(a+2*k+1.0)); /* second step */ den_term = 1.0 + coeff*den_term; num_term = 1.0 + coeff/num_term; if(fabs(den_term) < cutoff) den_term = cutoff; if(fabs(num_term) < cutoff) num_term = cutoff; den_term = 1.0/den_term; delta_frac = den_term*num_term; cf *= delta_frac; if(fabs(delta_frac-1.0) < 2.0*GSL_DBL_EPSILON) break; ++iter_count; } result->val = cf; result->err = iter_count * 4.0 * GSL_DBL_EPSILON * fabs(cf); if(iter_count >= max_iter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_beta_inc_e( const double a, const double b, const double x, gsl_sf_result * result ) { if(x < 0.0 || x > 1.0) { DOMAIN_ERROR(result); } else if (isnegint(a) || isnegint(b)) { DOMAIN_ERROR(result); } else if (isnegint(a+b)) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if(x == 1.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if (a <= 0 || b <= 0) { gsl_sf_result f, beta; int stat; const int stat_f = gsl_sf_hyperg_2F1_e(a, 1-b, a+1, x, &f); const int stat_beta = gsl_sf_beta_e(a, b, &beta); double prefactor = (pow(x, a) / a); result->val = prefactor * f.val / beta.val; result->err = fabs(prefactor) * f.err/ fabs(beta.val) + fabs(result->val/beta.val) * beta.err; stat = GSL_ERROR_SELECT_2(stat_f, stat_beta); if(stat == GSL_SUCCESS) { CHECK_UNDERFLOW(result); } return stat; } else { gsl_sf_result ln_beta; gsl_sf_result ln_x; gsl_sf_result ln_1mx; gsl_sf_result prefactor; const int stat_ln_beta = gsl_sf_lnbeta_e(a, b, &ln_beta); const int stat_ln_1mx = gsl_sf_log_1plusx_e(-x, &ln_1mx); const int stat_ln_x = gsl_sf_log_e(x, &ln_x); const int stat_ln = GSL_ERROR_SELECT_3(stat_ln_beta, stat_ln_1mx, stat_ln_x); const double ln_pre_val = -ln_beta.val + a * ln_x.val + b * ln_1mx.val; const double ln_pre_err = ln_beta.err + fabs(a*ln_x.err) + fabs(b*ln_1mx.err); const int stat_exp = gsl_sf_exp_err_e(ln_pre_val, ln_pre_err, &prefactor); if(stat_ln != GSL_SUCCESS) { result->val = 0.0; result->err = 0.0; GSL_ERROR ("error", GSL_ESANITY); } if(x < (a + 1.0)/(a+b+2.0)) { /* Apply continued fraction directly. */ gsl_sf_result cf; const int stat_cf = beta_cont_frac(a, b, x, &cf); int stat; result->val = prefactor.val * cf.val / a; result->err = (fabs(prefactor.err * cf.val) + fabs(prefactor.val * cf.err))/a; stat = GSL_ERROR_SELECT_2(stat_exp, stat_cf); if(stat == GSL_SUCCESS) { CHECK_UNDERFLOW(result); } return stat; } else { /* Apply continued fraction after hypergeometric transformation. */ gsl_sf_result cf; const int stat_cf = beta_cont_frac(b, a, 1.0-x, &cf); int stat; const double term = prefactor.val * cf.val / b; result->val = 1.0 - term; result->err = fabs(prefactor.err * cf.val)/b; result->err += fabs(prefactor.val * cf.err)/b; result->err += 2.0 * GSL_DBL_EPSILON * (1.0 + fabs(term)); stat = GSL_ERROR_SELECT_2(stat_exp, stat_cf); if(stat == GSL_SUCCESS) { CHECK_UNDERFLOW(result); } return stat; } } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_beta_inc(const double a, const double b, const double x) { EVAL_RESULT(gsl_sf_beta_inc_e(a, b, x, &result)); } sources_5316/external/gsl/gsl_roots__secant.c0000664000176700017670000000554711723710247020226 0ustar paulpaul/* roots/secant.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* secant.c -- secant root finding algorithm The secant algorithm is a variant of the Newton algorithm with the derivative term replaced by a numerical estimate from the last two function evaluations. x[i+1] = x[i] - f(x[i]) / f'_est where f'_est = (f(x[i]) - f(x[i-1])) / (x[i] - x[i-1]) The exact derivative is used for the initial value of f'_est. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_roots.h" #include "gsl_roots__roots.h" typedef struct { double f; double df; } secant_state_t; static int secant_init (void * vstate, gsl_function_fdf * fdf, double * root); static int secant_iterate (void * vstate, gsl_function_fdf * fdf, double * root); static int secant_init (void * vstate, gsl_function_fdf * fdf, double * root) { secant_state_t * state = (secant_state_t *) vstate; const double x = *root; GSL_FN_FDF_EVAL_F_DF (fdf, x, &(state->f), &(state->df)); return GSL_SUCCESS; } static int secant_iterate (void * vstate, gsl_function_fdf * fdf, double * root) { secant_state_t * state = (secant_state_t *) vstate; const double x = *root ; const double f = state->f; const double df = state->df; double x_new, f_new, df_new; if (state->df == 0.0) { GSL_ERROR("derivative is zero", GSL_EZERODIV); } x_new = x - (f / df); f_new = GSL_FN_FDF_EVAL_F(fdf, x_new) ; df_new = (f_new - f) / (x_new - x) ; *root = x_new ; state->f = f_new ; state->df = df_new ; if (!gsl_finite (f_new)) { GSL_ERROR ("function value is not finite", GSL_EBADFUNC); } if (!gsl_finite (df_new)) { GSL_ERROR ("derivative value is not finite", GSL_EBADFUNC); } return GSL_SUCCESS; } static const gsl_root_fdfsolver_type secant_type = {"secant", /* name */ sizeof (secant_state_t), &secant_init, &secant_iterate}; const gsl_root_fdfsolver_type * gsl_root_fdfsolver_secant = &secant_type; sources_5316/external/gsl/gsl_complex__results1.h0000664000176700017670000013176111705263724021042 0ustar paulpaul {FN (arg), ARG(0.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arg), ARG(0.0e+00,1.19209289550781250e-07), RES(1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(0.0e+00,-1.19209289550781250e-07), RES(-1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(0.0e+00,5.0e-01), RES(1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(0.0e+00,-5.0e-01), RES(-1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(0.0e+00,1.0e+00), RES(1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(0.0e+00,-1.0e+00), RES(-1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(0.0e+00,2.0e+00), RES(1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(0.0e+00,-2.0e+00), RES(-1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(0.0e+00,8.3886080e+06), RES(1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(0.0e+00,-8.3886080e+06), RES(-1.5707963267948966192e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,0.0e+00), RES(0e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,0.0e+00), RES(3.1415926535897932385e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(-7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(2.3561944901923449288e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-2.3561944901923449288e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,5.0e-01), RES(1.5707960883763175177e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,-5.0e-01), RES(-1.5707960883763175177e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,5.0e-01), RES(1.5707965652134757208e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-1.5707965652134757208e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,1.0e+00), RES(1.5707962075856070685e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,-1.0e+00), RES(-1.5707962075856070685e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,1.0e+00), RES(1.570796446004186170e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,-1.0e+00), RES(-1.570796446004186170e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,2.0e+00), RES(1.5707962671902518438e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,-2.0e+00), RES(-1.5707962671902518438e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,2.0e+00), RES(1.5707963863995413946e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,-2.0e+00), RES(-1.5707963863995413946e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.5707963267948824084e0, 0.0)}, {FN (arg), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(-1.5707963267948824084e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(1.5707963267949108301e0, 0.0)}, {FN (arg), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(-1.5707963267949108301e0, 0.0)}, {FN (arg), ARG(5.0e-01,0.0e+00), RES(0e0, 0.0)}, {FN (arg), ARG(-5.0e-01,0.0e+00), RES(3.1415926535897932385e0, 0.0)}, {FN (arg), ARG(5.0e-01,1.19209289550781250e-07), RES(2.3841857910155798249e-7, 0.0)}, {FN (arg), ARG(5.0e-01,-1.19209289550781250e-07), RES(-2.3841857910155798249e-7, 0.0)}, {FN (arg), ARG(-5.0e-01,1.19209289550781250e-07), RES(3.1415924151712141369e0, 0.0)}, {FN (arg), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-3.1415924151712141369e0, 0.0)}, {FN (arg), ARG(5.0e-01,5.0e-01), RES(7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(5.0e-01,-5.0e-01), RES(-7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(-5.0e-01,5.0e-01), RES(2.3561944901923449288e0, 0.0)}, {FN (arg), ARG(-5.0e-01,-5.0e-01), RES(-2.3561944901923449288e0, 0.0)}, {FN (arg), ARG(5.0e-01,1.0e+00), RES(1.1071487177940905030e0, 0.0)}, {FN (arg), ARG(5.0e-01,-1.0e+00), RES(-1.1071487177940905030e0, 0.0)}, {FN (arg), ARG(-5.0e-01,1.0e+00), RES(2.0344439357957027354e0, 0.0)}, {FN (arg), ARG(-5.0e-01,-1.0e+00), RES(-2.0344439357957027354e0, 0.0)}, {FN (arg), ARG(5.0e-01,2.0e+00), RES(1.3258176636680324651e0, 0.0)}, {FN (arg), ARG(5.0e-01,-2.0e+00), RES(-1.3258176636680324651e0, 0.0)}, {FN (arg), ARG(-5.0e-01,2.0e+00), RES(1.8157749899217607734e0, 0.0)}, {FN (arg), ARG(-5.0e-01,-2.0e+00), RES(-1.8157749899217607734e0, 0.0)}, {FN (arg), ARG(5.0e-01,8.3886080e+06), RES(1.5707962671902518438e0, 0.0)}, {FN (arg), ARG(5.0e-01,-8.3886080e+06), RES(-1.5707962671902518438e0, 0.0)}, {FN (arg), ARG(-5.0e-01,8.3886080e+06), RES(1.5707963863995413946e0, 0.0)}, {FN (arg), ARG(-5.0e-01,-8.3886080e+06), RES(-1.5707963863995413946e0, 0.0)}, {FN (arg), ARG(1.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arg), ARG(-1.0e+00,0.0e+00), RES(3.1415926535897932385e0, 0.0)}, {FN (arg), ARG(1.0e+00,1.19209289550781250e-07), RES(1.1920928955078068531e-7, 0.0)}, {FN (arg), ARG(1.0e+00,-1.19209289550781250e-07), RES(-1.1920928955078068531e-7, 0.0)}, {FN (arg), ARG(-1.0e+00,1.19209289550781250e-07), RES(3.1415925343805036877e0, 0.0)}, {FN (arg), ARG(-1.0e+00,-1.19209289550781250e-07), RES(-3.1415925343805036877e0, 0.0)}, {FN (arg), ARG(1.0e+00,5.0e-01), RES(4.6364760900080611621e-1, 0.0)}, {FN (arg), ARG(1.0e+00,-5.0e-01), RES(-4.6364760900080611621e-1, 0.0)}, {FN (arg), ARG(-1.0e+00,5.0e-01), RES(2.6779450445889871222e0, 0.0)}, {FN (arg), ARG(-1.0e+00,-5.0e-01), RES(-2.6779450445889871222e0, 0.0)}, {FN (arg), ARG(1.0e+00,1.0e+00), RES(7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(1.0e+00,-1.0e+00), RES(-7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(-1.0e+00,1.0e+00), RES(2.3561944901923449288e0, 0.0)}, {FN (arg), ARG(-1.0e+00,-1.0e+00), RES(-2.3561944901923449288e0, 0.0)}, {FN (arg), ARG(1.0e+00,2.0e+00), RES(1.1071487177940905030e0, 0.0)}, {FN (arg), ARG(1.0e+00,-2.0e+00), RES(-1.1071487177940905030e0, 0.0)}, {FN (arg), ARG(-1.0e+00,2.0e+00), RES(2.0344439357957027354e0, 0.0)}, {FN (arg), ARG(-1.0e+00,-2.0e+00), RES(-2.0344439357957027354e0, 0.0)}, {FN (arg), ARG(1.0e+00,8.3886080e+06), RES(1.5707962075856070685e0, 0.0)}, {FN (arg), ARG(1.0e+00,-8.3886080e+06), RES(-1.5707962075856070685e0, 0.0)}, {FN (arg), ARG(-1.0e+00,8.3886080e+06), RES(1.570796446004186170e0, 0.0)}, {FN (arg), ARG(-1.0e+00,-8.3886080e+06), RES(-1.570796446004186170e0, 0.0)}, {FN (arg), ARG(2.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (arg), ARG(-2.0e+00,0.0e+00), RES(3.1415926535897932385e0, 0.0)}, {FN (arg), ARG(2.0e+00,1.19209289550781250e-07), RES(5.9604644775390554414e-8, 0.0)}, {FN (arg), ARG(2.0e+00,-1.19209289550781250e-07), RES(-5.9604644775390554414e-8, 0.0)}, {FN (arg), ARG(-2.0e+00,1.19209289550781250e-07), RES(3.1415925939851484631e0, 0.0)}, {FN (arg), ARG(-2.0e+00,-1.19209289550781250e-07), RES(-3.1415925939851484631e0, 0.0)}, {FN (arg), ARG(2.0e+00,5.0e-01), RES(2.4497866312686415417e-1, 0.0)}, {FN (arg), ARG(2.0e+00,-5.0e-01), RES(-2.4497866312686415417e-1, 0.0)}, {FN (arg), ARG(-2.0e+00,5.0e-01), RES(2.8966139904629290843e0, 0.0)}, {FN (arg), ARG(-2.0e+00,-5.0e-01), RES(-2.8966139904629290843e0, 0.0)}, {FN (arg), ARG(2.0e+00,1.0e+00), RES(4.6364760900080611621e-1, 0.0)}, {FN (arg), ARG(2.0e+00,-1.0e+00), RES(-4.6364760900080611621e-1, 0.0)}, {FN (arg), ARG(-2.0e+00,1.0e+00), RES(2.6779450445889871222e0, 0.0)}, {FN (arg), ARG(-2.0e+00,-1.0e+00), RES(-2.6779450445889871222e0, 0.0)}, {FN (arg), ARG(2.0e+00,2.0e+00), RES(7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(2.0e+00,-2.0e+00), RES(-7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(-2.0e+00,2.0e+00), RES(2.3561944901923449288e0, 0.0)}, {FN (arg), ARG(-2.0e+00,-2.0e+00), RES(-2.3561944901923449288e0, 0.0)}, {FN (arg), ARG(2.0e+00,8.3886080e+06), RES(1.5707960883763175177e0, 0.0)}, {FN (arg), ARG(2.0e+00,-8.3886080e+06), RES(-1.5707960883763175177e0, 0.0)}, {FN (arg), ARG(-2.0e+00,8.3886080e+06), RES(1.5707965652134757208e0, 0.0)}, {FN (arg), ARG(-2.0e+00,-8.3886080e+06), RES(-1.5707965652134757208e0, 0.0)}, {FN (arg), ARG(8.3886080e+06,0.0e+00), RES(0e0, 0.0)}, {FN (arg), ARG(-8.3886080e+06,0.0e+00), RES(3.1415926535897932385e0, 0.0)}, {FN (arg), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.4210854715202003717e-14, 0.0)}, {FN (arg), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(-1.4210854715202003717e-14, 0.0)}, {FN (arg), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(3.1415926535897790276e0, 0.0)}, {FN (arg), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(-3.1415926535897790276e0, 0.0)}, {FN (arg), ARG(8.3886080e+06,5.0e-01), RES(5.9604644775390554414e-8, 0.0)}, {FN (arg), ARG(8.3886080e+06,-5.0e-01), RES(-5.9604644775390554414e-8, 0.0)}, {FN (arg), ARG(-8.3886080e+06,5.0e-01), RES(3.1415925939851484631e0, 0.0)}, {FN (arg), ARG(-8.3886080e+06,-5.0e-01), RES(-3.1415925939851484631e0, 0.0)}, {FN (arg), ARG(8.3886080e+06,1.0e+00), RES(1.1920928955078068531e-7, 0.0)}, {FN (arg), ARG(8.3886080e+06,-1.0e+00), RES(-1.1920928955078068531e-7, 0.0)}, {FN (arg), ARG(-8.3886080e+06,1.0e+00), RES(3.1415925343805036877e0, 0.0)}, {FN (arg), ARG(-8.3886080e+06,-1.0e+00), RES(-3.1415925343805036877e0, 0.0)}, {FN (arg), ARG(8.3886080e+06,2.0e+00), RES(2.3841857910155798249e-7, 0.0)}, {FN (arg), ARG(8.3886080e+06,-2.0e+00), RES(-2.3841857910155798249e-7, 0.0)}, {FN (arg), ARG(-8.3886080e+06,2.0e+00), RES(3.1415924151712141369e0, 0.0)}, {FN (arg), ARG(-8.3886080e+06,-2.0e+00), RES(-3.1415924151712141369e0, 0.0)}, {FN (arg), ARG(8.3886080e+06,8.3886080e+06), RES(7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(8.3886080e+06,-8.3886080e+06), RES(-7.8539816339744830962e-1, 0.0)}, {FN (arg), ARG(-8.3886080e+06,8.3886080e+06), RES(2.3561944901923449288e0, 0.0)}, {FN (arg), ARG(-8.3886080e+06,-8.3886080e+06), RES(-2.3561944901923449288e0, 0.0)}, {FN (abs), ARG(0.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (abs), ARG(0.0e+00,1.19209289550781250e-07), RES(1.1920928955078125e-7, 0.0)}, {FN (abs), ARG(0.0e+00,-1.19209289550781250e-07), RES(1.1920928955078125e-7, 0.0)}, {FN (abs), ARG(0.0e+00,5.0e-01), RES(5e-1, 0.0)}, {FN (abs), ARG(0.0e+00,-5.0e-01), RES(5e-1, 0.0)}, {FN (abs), ARG(0.0e+00,1.0e+00), RES(1e0, 0.0)}, {FN (abs), ARG(0.0e+00,-1.0e+00), RES(1e0, 0.0)}, {FN (abs), ARG(0.0e+00,2.0e+00), RES(2e0, 0.0)}, {FN (abs), ARG(0.0e+00,-2.0e+00), RES(2e0, 0.0)}, {FN (abs), ARG(0.0e+00,8.3886080e+06), RES(8.388608e6, 0.0)}, {FN (abs), ARG(0.0e+00,-8.3886080e+06), RES(8.388608e6, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,0.0e+00), RES(1.1920928955078125e-7, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,0.0e+00), RES(1.1920928955078125e-7, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(1.6858739404357612715e-7, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.6858739404357612715e-7, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(1.6858739404357612715e-7, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(1.6858739404357612715e-7, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,5.0e-01), RES(5.0000000000001421085e-1, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,-5.0e-01), RES(5.0000000000001421085e-1, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,5.0e-01), RES(5.0000000000001421085e-1, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,-5.0e-01), RES(5.0000000000001421085e-1, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,1.0e+00), RES(1.0000000000000071054e0, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,-1.0e+00), RES(1.0000000000000071054e0, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,1.0e+00), RES(1.0000000000000071054e0, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,-1.0e+00), RES(1.0000000000000071054e0, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,2.0e+00), RES(2.0000000000000035527e0, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,-2.0e+00), RES(2.0000000000000035527e0, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,2.0e+00), RES(2.0000000000000035527e0, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,-2.0e+00), RES(2.0000000000000035527e0, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,8.3886080e+06), RES(8.3886080e6, 0.0)}, {FN (abs), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(8.3886080e6, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(8.3886080e6, 0.0)}, {FN (abs), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(8.3886080e6, 0.0)}, {FN (abs), ARG(5.0e-01,0.0e+00), RES(5e-1, 0.0)}, {FN (abs), ARG(-5.0e-01,0.0e+00), RES(5e-1, 0.0)}, {FN (abs), ARG(5.0e-01,1.19209289550781250e-07), RES(5.0000000000001421085e-1, 0.0)}, {FN (abs), ARG(5.0e-01,-1.19209289550781250e-07), RES(5.0000000000001421085e-1, 0.0)}, {FN (abs), ARG(-5.0e-01,1.19209289550781250e-07), RES(5.0000000000001421085e-1, 0.0)}, {FN (abs), ARG(-5.0e-01,-1.19209289550781250e-07), RES(5.0000000000001421085e-1, 0.0)}, {FN (abs), ARG(5.0e-01,5.0e-01), RES(7.0710678118654752440e-1, 0.0)}, {FN (abs), ARG(5.0e-01,-5.0e-01), RES(7.0710678118654752440e-1, 0.0)}, {FN (abs), ARG(-5.0e-01,5.0e-01), RES(7.0710678118654752440e-1, 0.0)}, {FN (abs), ARG(-5.0e-01,-5.0e-01), RES(7.0710678118654752440e-1, 0.0)}, {FN (abs), ARG(5.0e-01,1.0e+00), RES(1.1180339887498948482e0, 0.0)}, {FN (abs), ARG(5.0e-01,-1.0e+00), RES(1.1180339887498948482e0, 0.0)}, {FN (abs), ARG(-5.0e-01,1.0e+00), RES(1.1180339887498948482e0, 0.0)}, {FN (abs), ARG(-5.0e-01,-1.0e+00), RES(1.1180339887498948482e0, 0.0)}, {FN (abs), ARG(5.0e-01,2.0e+00), RES(2.0615528128088302749e0, 0.0)}, {FN (abs), ARG(5.0e-01,-2.0e+00), RES(2.0615528128088302749e0, 0.0)}, {FN (abs), ARG(-5.0e-01,2.0e+00), RES(2.0615528128088302749e0, 0.0)}, {FN (abs), ARG(-5.0e-01,-2.0e+00), RES(2.0615528128088302749e0, 0.0)}, {FN (abs), ARG(5.0e-01,8.3886080e+06), RES(8.3886080000000149012e6, 0.0)}, {FN (abs), ARG(5.0e-01,-8.3886080e+06), RES(8.3886080000000149012e6, 0.0)}, {FN (abs), ARG(-5.0e-01,8.3886080e+06), RES(8.3886080000000149012e6, 0.0)}, {FN (abs), ARG(-5.0e-01,-8.3886080e+06), RES(8.3886080000000149012e6, 0.0)}, {FN (abs), ARG(1.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (abs), ARG(-1.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (abs), ARG(1.0e+00,1.19209289550781250e-07), RES(1.0000000000000071054e0, 0.0)}, {FN (abs), ARG(1.0e+00,-1.19209289550781250e-07), RES(1.0000000000000071054e0, 0.0)}, {FN (abs), ARG(-1.0e+00,1.19209289550781250e-07), RES(1.0000000000000071054e0, 0.0)}, {FN (abs), ARG(-1.0e+00,-1.19209289550781250e-07), RES(1.0000000000000071054e0, 0.0)}, {FN (abs), ARG(1.0e+00,5.0e-01), RES(1.1180339887498948482e0, 0.0)}, {FN (abs), ARG(1.0e+00,-5.0e-01), RES(1.1180339887498948482e0, 0.0)}, {FN (abs), ARG(-1.0e+00,5.0e-01), RES(1.1180339887498948482e0, 0.0)}, {FN (abs), ARG(-1.0e+00,-5.0e-01), RES(1.1180339887498948482e0, 0.0)}, {FN (abs), ARG(1.0e+00,1.0e+00), RES(1.4142135623730950488e0, 0.0)}, {FN (abs), ARG(1.0e+00,-1.0e+00), RES(1.4142135623730950488e0, 0.0)}, {FN (abs), ARG(-1.0e+00,1.0e+00), RES(1.4142135623730950488e0, 0.0)}, {FN (abs), ARG(-1.0e+00,-1.0e+00), RES(1.4142135623730950488e0, 0.0)}, {FN (abs), ARG(1.0e+00,2.0e+00), RES(2.2360679774997896964e0, 0.0)}, {FN (abs), ARG(1.0e+00,-2.0e+00), RES(2.2360679774997896964e0, 0.0)}, {FN (abs), ARG(-1.0e+00,2.0e+00), RES(2.2360679774997896964e0, 0.0)}, {FN (abs), ARG(-1.0e+00,-2.0e+00), RES(2.2360679774997896964e0, 0.0)}, {FN (abs), ARG(1.0e+00,8.3886080e+06), RES(8.3886080000000596046e6, 0.0)}, {FN (abs), ARG(1.0e+00,-8.3886080e+06), RES(8.3886080000000596046e6, 0.0)}, {FN (abs), ARG(-1.0e+00,8.3886080e+06), RES(8.3886080000000596046e6, 0.0)}, {FN (abs), ARG(-1.0e+00,-8.3886080e+06), RES(8.3886080000000596046e6, 0.0)}, {FN (abs), ARG(2.0e+00,0.0e+00), RES(2e0, 0.0)}, {FN (abs), ARG(-2.0e+00,0.0e+00), RES(2e0, 0.0)}, {FN (abs), ARG(2.0e+00,1.19209289550781250e-07), RES(2.0000000000000035527e0, 0.0)}, {FN (abs), ARG(2.0e+00,-1.19209289550781250e-07), RES(2.0000000000000035527e0, 0.0)}, {FN (abs), ARG(-2.0e+00,1.19209289550781250e-07), RES(2.0000000000000035527e0, 0.0)}, {FN (abs), ARG(-2.0e+00,-1.19209289550781250e-07), RES(2.0000000000000035527e0, 0.0)}, {FN (abs), ARG(2.0e+00,5.0e-01), RES(2.0615528128088302749e0, 0.0)}, {FN (abs), ARG(2.0e+00,-5.0e-01), RES(2.0615528128088302749e0, 0.0)}, {FN (abs), ARG(-2.0e+00,5.0e-01), RES(2.0615528128088302749e0, 0.0)}, {FN (abs), ARG(-2.0e+00,-5.0e-01), RES(2.0615528128088302749e0, 0.0)}, {FN (abs), ARG(2.0e+00,1.0e+00), RES(2.2360679774997896964e0, 0.0)}, {FN (abs), ARG(2.0e+00,-1.0e+00), RES(2.2360679774997896964e0, 0.0)}, {FN (abs), ARG(-2.0e+00,1.0e+00), RES(2.2360679774997896964e0, 0.0)}, {FN (abs), ARG(-2.0e+00,-1.0e+00), RES(2.2360679774997896964e0, 0.0)}, {FN (abs), ARG(2.0e+00,2.0e+00), RES(2.8284271247461900976e0, 0.0)}, {FN (abs), ARG(2.0e+00,-2.0e+00), RES(2.8284271247461900976e0, 0.0)}, {FN (abs), ARG(-2.0e+00,2.0e+00), RES(2.8284271247461900976e0, 0.0)}, {FN (abs), ARG(-2.0e+00,-2.0e+00), RES(2.8284271247461900976e0, 0.0)}, {FN (abs), ARG(2.0e+00,8.3886080e+06), RES(8.3886080000002384186e6, 0.0)}, {FN (abs), ARG(2.0e+00,-8.3886080e+06), RES(8.3886080000002384186e6, 0.0)}, {FN (abs), ARG(-2.0e+00,8.3886080e+06), RES(8.3886080000002384186e6, 0.0)}, {FN (abs), ARG(-2.0e+00,-8.3886080e+06), RES(8.3886080000002384186e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,0.0e+00), RES(8.388608e6, 0.0)}, {FN (abs), ARG(-8.3886080e+06,0.0e+00), RES(8.388608e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,1.19209289550781250e-07), RES(8.3886080e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(8.3886080e6, 0.0)}, {FN (abs), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(8.3886080e6, 0.0)}, {FN (abs), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(8.3886080e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,5.0e-01), RES(8.3886080000000149012e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,-5.0e-01), RES(8.3886080000000149012e6, 0.0)}, {FN (abs), ARG(-8.3886080e+06,5.0e-01), RES(8.3886080000000149012e6, 0.0)}, {FN (abs), ARG(-8.3886080e+06,-5.0e-01), RES(8.3886080000000149012e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,1.0e+00), RES(8.3886080000000596046e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,-1.0e+00), RES(8.3886080000000596046e6, 0.0)}, {FN (abs), ARG(-8.3886080e+06,1.0e+00), RES(8.3886080000000596046e6, 0.0)}, {FN (abs), ARG(-8.3886080e+06,-1.0e+00), RES(8.3886080000000596046e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,2.0e+00), RES(8.3886080000002384186e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,-2.0e+00), RES(8.3886080000002384186e6, 0.0)}, {FN (abs), ARG(-8.3886080e+06,2.0e+00), RES(8.3886080000002384186e6, 0.0)}, {FN (abs), ARG(-8.3886080e+06,-2.0e+00), RES(8.3886080000002384186e6, 0.0)}, {FN (abs), ARG(8.3886080e+06,8.3886080e+06), RES(1.1863283203031444111e7, 0.0)}, {FN (abs), ARG(8.3886080e+06,-8.3886080e+06), RES(1.1863283203031444111e7, 0.0)}, {FN (abs), ARG(-8.3886080e+06,8.3886080e+06), RES(1.1863283203031444111e7, 0.0)}, {FN (abs), ARG(-8.3886080e+06,-8.3886080e+06), RES(1.1863283203031444111e7, 0.0)}, {FN (abs2), ARG(0.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (abs2), ARG(0.0e+00,1.19209289550781250e-07), RES(1.4210854715202003717e-14, 0.0)}, {FN (abs2), ARG(0.0e+00,-1.19209289550781250e-07), RES(1.4210854715202003717e-14, 0.0)}, {FN (abs2), ARG(0.0e+00,5.0e-01), RES(2.5e-1, 0.0)}, {FN (abs2), ARG(0.0e+00,-5.0e-01), RES(2.5e-1, 0.0)}, {FN (abs2), ARG(0.0e+00,1.0e+00), RES(1e0, 0.0)}, {FN (abs2), ARG(0.0e+00,-1.0e+00), RES(1e0, 0.0)}, {FN (abs2), ARG(0.0e+00,2.0e+00), RES(4e0, 0.0)}, {FN (abs2), ARG(0.0e+00,-2.0e+00), RES(4e0, 0.0)}, {FN (abs2), ARG(0.0e+00,8.3886080e+06), RES(7.0368744177664e13, 0.0)}, {FN (abs2), ARG(0.0e+00,-8.3886080e+06), RES(7.0368744177664e13, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,0.0e+00), RES(1.4210854715202003717e-14, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,0.0e+00), RES(1.4210854715202003717e-14, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(2.8421709430404007435e-14, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(2.8421709430404007435e-14, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(2.8421709430404007435e-14, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(2.8421709430404007435e-14, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,5.0e-01), RES(2.5000000000001421085e-1, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,-5.0e-01), RES(2.5000000000001421085e-1, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,5.0e-01), RES(2.5000000000001421085e-1, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,-5.0e-01), RES(2.5000000000001421085e-1, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,1.0e+00), RES(1.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,-1.0e+00), RES(1.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,1.0e+00), RES(1.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,-1.0e+00), RES(1.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,2.0e+00), RES(4.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,-2.0e+00), RES(4.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,2.0e+00), RES(4.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,-2.0e+00), RES(4.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,8.3886080e+06), RES(7.03687441776640e13, 0.0)}, {FN (abs2), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(7.03687441776640e13, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(7.03687441776640e13, 0.0)}, {FN (abs2), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(7.03687441776640e13, 0.0)}, {FN (abs2), ARG(5.0e-01,0.0e+00), RES(2.5e-1, 0.0)}, {FN (abs2), ARG(-5.0e-01,0.0e+00), RES(2.5e-1, 0.0)}, {FN (abs2), ARG(5.0e-01,1.19209289550781250e-07), RES(2.5000000000001421085e-1, 0.0)}, {FN (abs2), ARG(5.0e-01,-1.19209289550781250e-07), RES(2.5000000000001421085e-1, 0.0)}, {FN (abs2), ARG(-5.0e-01,1.19209289550781250e-07), RES(2.5000000000001421085e-1, 0.0)}, {FN (abs2), ARG(-5.0e-01,-1.19209289550781250e-07), RES(2.5000000000001421085e-1, 0.0)}, {FN (abs2), ARG(5.0e-01,5.0e-01), RES(5e-1, 0.0)}, {FN (abs2), ARG(5.0e-01,-5.0e-01), RES(5e-1, 0.0)}, {FN (abs2), ARG(-5.0e-01,5.0e-01), RES(5e-1, 0.0)}, {FN (abs2), ARG(-5.0e-01,-5.0e-01), RES(5e-1, 0.0)}, {FN (abs2), ARG(5.0e-01,1.0e+00), RES(1.25e0, 0.0)}, {FN (abs2), ARG(5.0e-01,-1.0e+00), RES(1.25e0, 0.0)}, {FN (abs2), ARG(-5.0e-01,1.0e+00), RES(1.25e0, 0.0)}, {FN (abs2), ARG(-5.0e-01,-1.0e+00), RES(1.25e0, 0.0)}, {FN (abs2), ARG(5.0e-01,2.0e+00), RES(4.25e0, 0.0)}, {FN (abs2), ARG(5.0e-01,-2.0e+00), RES(4.25e0, 0.0)}, {FN (abs2), ARG(-5.0e-01,2.0e+00), RES(4.25e0, 0.0)}, {FN (abs2), ARG(-5.0e-01,-2.0e+00), RES(4.25e0, 0.0)}, {FN (abs2), ARG(5.0e-01,8.3886080e+06), RES(7.036874417766425e13, 0.0)}, {FN (abs2), ARG(5.0e-01,-8.3886080e+06), RES(7.036874417766425e13, 0.0)}, {FN (abs2), ARG(-5.0e-01,8.3886080e+06), RES(7.036874417766425e13, 0.0)}, {FN (abs2), ARG(-5.0e-01,-8.3886080e+06), RES(7.036874417766425e13, 0.0)}, {FN (abs2), ARG(1.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (abs2), ARG(-1.0e+00,0.0e+00), RES(1e0, 0.0)}, {FN (abs2), ARG(1.0e+00,1.19209289550781250e-07), RES(1.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(1.0e+00,-1.19209289550781250e-07), RES(1.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(-1.0e+00,1.19209289550781250e-07), RES(1.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(-1.0e+00,-1.19209289550781250e-07), RES(1.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(1.0e+00,5.0e-01), RES(1.25e0, 0.0)}, {FN (abs2), ARG(1.0e+00,-5.0e-01), RES(1.25e0, 0.0)}, {FN (abs2), ARG(-1.0e+00,5.0e-01), RES(1.25e0, 0.0)}, {FN (abs2), ARG(-1.0e+00,-5.0e-01), RES(1.25e0, 0.0)}, {FN (abs2), ARG(1.0e+00,1.0e+00), RES(2e0, 0.0)}, {FN (abs2), ARG(1.0e+00,-1.0e+00), RES(2e0, 0.0)}, {FN (abs2), ARG(-1.0e+00,1.0e+00), RES(2e0, 0.0)}, {FN (abs2), ARG(-1.0e+00,-1.0e+00), RES(2e0, 0.0)}, {FN (abs2), ARG(1.0e+00,2.0e+00), RES(5e0, 0.0)}, {FN (abs2), ARG(1.0e+00,-2.0e+00), RES(5e0, 0.0)}, {FN (abs2), ARG(-1.0e+00,2.0e+00), RES(5e0, 0.0)}, {FN (abs2), ARG(-1.0e+00,-2.0e+00), RES(5e0, 0.0)}, {FN (abs2), ARG(1.0e+00,8.3886080e+06), RES(7.0368744177665e13, 0.0)}, {FN (abs2), ARG(1.0e+00,-8.3886080e+06), RES(7.0368744177665e13, 0.0)}, {FN (abs2), ARG(-1.0e+00,8.3886080e+06), RES(7.0368744177665e13, 0.0)}, {FN (abs2), ARG(-1.0e+00,-8.3886080e+06), RES(7.0368744177665e13, 0.0)}, {FN (abs2), ARG(2.0e+00,0.0e+00), RES(4e0, 0.0)}, {FN (abs2), ARG(-2.0e+00,0.0e+00), RES(4e0, 0.0)}, {FN (abs2), ARG(2.0e+00,1.19209289550781250e-07), RES(4.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(2.0e+00,-1.19209289550781250e-07), RES(4.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(-2.0e+00,1.19209289550781250e-07), RES(4.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(-2.0e+00,-1.19209289550781250e-07), RES(4.0000000000000142109e0, 0.0)}, {FN (abs2), ARG(2.0e+00,5.0e-01), RES(4.25e0, 0.0)}, {FN (abs2), ARG(2.0e+00,-5.0e-01), RES(4.25e0, 0.0)}, {FN (abs2), ARG(-2.0e+00,5.0e-01), RES(4.25e0, 0.0)}, {FN (abs2), ARG(-2.0e+00,-5.0e-01), RES(4.25e0, 0.0)}, {FN (abs2), ARG(2.0e+00,1.0e+00), RES(5e0, 0.0)}, {FN (abs2), ARG(2.0e+00,-1.0e+00), RES(5e0, 0.0)}, {FN (abs2), ARG(-2.0e+00,1.0e+00), RES(5e0, 0.0)}, {FN (abs2), ARG(-2.0e+00,-1.0e+00), RES(5e0, 0.0)}, {FN (abs2), ARG(2.0e+00,2.0e+00), RES(8e0, 0.0)}, {FN (abs2), ARG(2.0e+00,-2.0e+00), RES(8e0, 0.0)}, {FN (abs2), ARG(-2.0e+00,2.0e+00), RES(8e0, 0.0)}, {FN (abs2), ARG(-2.0e+00,-2.0e+00), RES(8e0, 0.0)}, {FN (abs2), ARG(2.0e+00,8.3886080e+06), RES(7.0368744177668e13, 0.0)}, {FN (abs2), ARG(2.0e+00,-8.3886080e+06), RES(7.0368744177668e13, 0.0)}, {FN (abs2), ARG(-2.0e+00,8.3886080e+06), RES(7.0368744177668e13, 0.0)}, {FN (abs2), ARG(-2.0e+00,-8.3886080e+06), RES(7.0368744177668e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,0.0e+00), RES(7.0368744177664e13, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,0.0e+00), RES(7.0368744177664e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,1.19209289550781250e-07), RES(7.03687441776640e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(7.03687441776640e13, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(7.03687441776640e13, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(7.03687441776640e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,5.0e-01), RES(7.036874417766425e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,-5.0e-01), RES(7.036874417766425e13, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,5.0e-01), RES(7.036874417766425e13, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,-5.0e-01), RES(7.036874417766425e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,1.0e+00), RES(7.0368744177665e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,-1.0e+00), RES(7.0368744177665e13, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,1.0e+00), RES(7.0368744177665e13, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,-1.0e+00), RES(7.0368744177665e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,2.0e+00), RES(7.0368744177668e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,-2.0e+00), RES(7.0368744177668e13, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,2.0e+00), RES(7.0368744177668e13, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,-2.0e+00), RES(7.0368744177668e13, 0.0)}, {FN (abs2), ARG(8.3886080e+06,8.3886080e+06), RES(1.40737488355328e14, 0.0)}, {FN (abs2), ARG(8.3886080e+06,-8.3886080e+06), RES(1.40737488355328e14, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,8.3886080e+06), RES(1.40737488355328e14, 0.0)}, {FN (abs2), ARG(-8.3886080e+06,-8.3886080e+06), RES(1.40737488355328e14, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,0.0e+00), RES(-1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,0.0e+00), RES(-1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.5595811562598769462e1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.5595811562598769462e1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.5595811562598769462e1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.5595811562598769462e1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,5.0e-01), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-5.0e-01), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,5.0e-01), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,1.0e+00), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-1.0e+00), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,1.0e+00), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-1.0e+00), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,2.0e+00), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-2.0e+00), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,2.0e+00), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-2.0e+00), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(5.0e-01,0.0e+00), RES(-6.9314718055994530942e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,0.0e+00), RES(-6.9314718055994530942e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,-1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,5.0e-01), RES(-3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,-5.0e-01), RES(-3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,5.0e-01), RES(-3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-5.0e-01), RES(-3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,1.0e+00), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,-1.0e+00), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,1.0e+00), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-1.0e+00), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,2.0e+00), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,-2.0e+00), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,2.0e+00), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-2.0e+00), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,8.3886080e+06), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(5.0e-01,-8.3886080e+06), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(-5.0e-01,8.3886080e+06), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-8.3886080e+06), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(1.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (logabs), ARG(-1.0e+00,0.0e+00), RES(0e0, 0.0)}, {FN (logabs), ARG(1.0e+00,1.19209289550781250e-07), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(1.0e+00,-1.19209289550781250e-07), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(-1.0e+00,1.19209289550781250e-07), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(-1.0e+00,-1.19209289550781250e-07), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(1.0e+00,5.0e-01), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,-5.0e-01), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,5.0e-01), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,-5.0e-01), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,1.0e+00), RES(3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,-1.0e+00), RES(3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,1.0e+00), RES(3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,-1.0e+00), RES(3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,2.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,-2.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,2.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,-2.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,8.3886080e+06), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(1.0e+00,-8.3886080e+06), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(-1.0e+00,8.3886080e+06), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(-1.0e+00,-8.3886080e+06), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(2.0e+00,0.0e+00), RES(6.9314718055994530942e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,0.0e+00), RES(6.9314718055994530942e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,1.19209289550781250e-07), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,-1.19209289550781250e-07), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,1.19209289550781250e-07), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,-1.19209289550781250e-07), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,5.0e-01), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,-5.0e-01), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,5.0e-01), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,-5.0e-01), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,1.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,-1.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,1.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,-1.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,2.0e+00), RES(1.0397207708399179641e0, 0.0)}, {FN (logabs), ARG(2.0e+00,-2.0e+00), RES(1.0397207708399179641e0, 0.0)}, {FN (logabs), ARG(-2.0e+00,2.0e+00), RES(1.0397207708399179641e0, 0.0)}, {FN (logabs), ARG(-2.0e+00,-2.0e+00), RES(1.0397207708399179641e0, 0.0)}, {FN (logabs), ARG(2.0e+00,8.3886080e+06), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(2.0e+00,-8.3886080e+06), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(-2.0e+00,8.3886080e+06), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(-2.0e+00,-8.3886080e+06), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,0.0e+00), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,0.0e+00), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,5.0e-01), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-5.0e-01), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,5.0e-01), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-5.0e-01), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,1.0e+00), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-1.0e+00), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,1.0e+00), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-1.0e+00), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,2.0e+00), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-2.0e+00), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,2.0e+00), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-2.0e+00), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,8.3886080e+06), RES(1.6288958743158714771e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-8.3886080e+06), RES(1.6288958743158714771e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,8.3886080e+06), RES(1.6288958743158714771e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-8.3886080e+06), RES(1.6288958743158714771e1, 0.0)}, {FN (logabs), ARG(0.0e+00,1.19209289550781250e-07), RES(-1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(0.0e+00,-1.19209289550781250e-07), RES(-1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(0.0e+00,5.0e-01), RES(-6.9314718055994530942e-1, 0.0)}, {FN (logabs), ARG(0.0e+00,-5.0e-01), RES(-6.9314718055994530942e-1, 0.0)}, {FN (logabs), ARG(0.0e+00,1.0e+00), RES(0e0, 0.0)}, {FN (logabs), ARG(0.0e+00,-1.0e+00), RES(0e0, 0.0)}, {FN (logabs), ARG(0.0e+00,2.0e+00), RES(6.9314718055994530942e-1, 0.0)}, {FN (logabs), ARG(0.0e+00,-2.0e+00), RES(6.9314718055994530942e-1, 0.0)}, {FN (logabs), ARG(0.0e+00,8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(0.0e+00,-8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.5595811562598769462e1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.5595811562598769462e1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,1.19209289550781250e-07), RES(-1.5595811562598769462e1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-1.19209289550781250e-07), RES(-1.5595811562598769462e1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,5.0e-01), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-5.0e-01), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,5.0e-01), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-5.0e-01), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,1.0e+00), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-1.0e+00), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,1.0e+00), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-1.0e+00), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,2.0e+00), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-2.0e+00), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,2.0e+00), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-2.0e+00), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(1.19209289550781250e-07,-8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-1.19209289550781250e-07,-8.3886080e+06), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(5.0e-01,1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,-1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-1.19209289550781250e-07), RES(-6.9314718055991688771e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,5.0e-01), RES(-3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,-5.0e-01), RES(-3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,5.0e-01), RES(-3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-5.0e-01), RES(-3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,1.0e+00), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,-1.0e+00), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,1.0e+00), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-1.0e+00), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,2.0e+00), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,-2.0e+00), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,2.0e+00), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-2.0e+00), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(5.0e-01,8.3886080e+06), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(5.0e-01,-8.3886080e+06), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(-5.0e-01,8.3886080e+06), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(-5.0e-01,-8.3886080e+06), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(1.0e+00,1.19209289550781250e-07), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(1.0e+00,-1.19209289550781250e-07), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(-1.0e+00,1.19209289550781250e-07), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(-1.0e+00,-1.19209289550781250e-07), RES(7.1054273576009513716e-15, 0.0)}, {FN (logabs), ARG(1.0e+00,5.0e-01), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,-5.0e-01), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,5.0e-01), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,-5.0e-01), RES(1.1157177565710487788e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,1.0e+00), RES(3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,-1.0e+00), RES(3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,1.0e+00), RES(3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,-1.0e+00), RES(3.4657359027997265471e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,2.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,-2.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,2.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(-1.0e+00,-2.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(1.0e+00,8.3886080e+06), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(1.0e+00,-8.3886080e+06), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(-1.0e+00,8.3886080e+06), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(-1.0e+00,-8.3886080e+06), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(2.0e+00,1.19209289550781250e-07), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,-1.19209289550781250e-07), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,1.19209289550781250e-07), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,-1.19209289550781250e-07), RES(6.9314718055994708577e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,5.0e-01), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,-5.0e-01), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,5.0e-01), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,-5.0e-01), RES(7.2345949146816273071e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,1.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,-1.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,1.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(-2.0e+00,-1.0e+00), RES(8.0471895621705018730e-1, 0.0)}, {FN (logabs), ARG(2.0e+00,2.0e+00), RES(1.0397207708399179641e0, 0.0)}, {FN (logabs), ARG(2.0e+00,-2.0e+00), RES(1.0397207708399179641e0, 0.0)}, {FN (logabs), ARG(-2.0e+00,2.0e+00), RES(1.0397207708399179641e0, 0.0)}, {FN (logabs), ARG(-2.0e+00,-2.0e+00), RES(1.0397207708399179641e0, 0.0)}, {FN (logabs), ARG(2.0e+00,8.3886080e+06), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(2.0e+00,-8.3886080e+06), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(-2.0e+00,8.3886080e+06), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(-2.0e+00,-8.3886080e+06), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,1.19209289550781250e-07), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-1.19209289550781250e-07), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,1.19209289550781250e-07), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-1.19209289550781250e-07), RES(1.5942385152878742117e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,5.0e-01), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-5.0e-01), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,5.0e-01), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-5.0e-01), RES(1.5942385152878743893e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,1.0e+00), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-1.0e+00), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,1.0e+00), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-1.0e+00), RES(1.5942385152878749222e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,2.0e+00), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-2.0e+00), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,2.0e+00), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-2.0e+00), RES(1.5942385152878770538e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,8.3886080e+06), RES(1.6288958743158714771e1, 0.0)}, {FN (logabs), ARG(8.3886080e+06,-8.3886080e+06), RES(1.6288958743158714771e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,8.3886080e+06), RES(1.6288958743158714771e1, 0.0)}, {FN (logabs), ARG(-8.3886080e+06,-8.3886080e+06), RES(1.6288958743158714771e1, 0.0)}, sources_5316/external/gsl/gsl_statistics_int.h0000664000176700017670000001026211705263724020426 0ustar paulpaul/* statistics/gsl_statistics_int.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_STATISTICS_INT_H__ #define __GSL_STATISTICS_INT_H__ #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_stats_int_mean (const int data[], const size_t stride, const size_t n); double gsl_stats_int_variance (const int data[], const size_t stride, const size_t n); double gsl_stats_int_sd (const int data[], const size_t stride, const size_t n); double gsl_stats_int_variance_with_fixed_mean (const int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_int_sd_with_fixed_mean (const int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_int_absdev (const int data[], const size_t stride, const size_t n); double gsl_stats_int_skew (const int data[], const size_t stride, const size_t n); double gsl_stats_int_kurtosis (const int data[], const size_t stride, const size_t n); double gsl_stats_int_lag1_autocorrelation (const int data[], const size_t stride, const size_t n); double gsl_stats_int_covariance (const int data1[], const size_t stride1,const int data2[], const size_t stride2, const size_t n); double gsl_stats_int_correlation (const int data1[], const size_t stride1,const int data2[], const size_t stride2, const size_t n); double gsl_stats_int_variance_m (const int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_int_sd_m (const int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_int_absdev_m (const int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_int_skew_m_sd (const int data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_int_kurtosis_m_sd (const int data[], const size_t stride, const size_t n, const double mean, const double sd); double gsl_stats_int_lag1_autocorrelation_m (const int data[], const size_t stride, const size_t n, const double mean); double gsl_stats_int_covariance_m (const int data1[], const size_t stride1,const int data2[], const size_t stride2, const size_t n, const double mean1, const double mean2); double gsl_stats_int_pvariance (const int data1[], const size_t stride1, const size_t n1, const int data2[], const size_t stride2, const size_t n2); double gsl_stats_int_ttest (const int data1[], const size_t stride1, const size_t n1, const int data2[], const size_t stride2, const size_t n2); int gsl_stats_int_max (const int data[], const size_t stride, const size_t n); int gsl_stats_int_min (const int data[], const size_t stride, const size_t n); void gsl_stats_int_minmax (int * min, int * max, const int data[], const size_t stride, const size_t n); size_t gsl_stats_int_max_index (const int data[], const size_t stride, const size_t n); size_t gsl_stats_int_min_index (const int data[], const size_t stride, const size_t n); void gsl_stats_int_minmax_index (size_t * min_index, size_t * max_index, const int data[], const size_t stride, const size_t n); double gsl_stats_int_median_from_sorted_data (const int sorted_data[], const size_t stride, const size_t n) ; double gsl_stats_int_quantile_from_sorted_data (const int sorted_data[], const size_t stride, const size_t n, const double f) ; __END_DECLS #endif /* __GSL_STATISTICS_INT_H__ */ sources_5316/external/gsl/gsl_sf__bessel_I0.c0000644000176700017670000001421510707442037020006 0ustar paulpaul/* specfunc/bessel_I0.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besi0 */ /* chebyshev expansions series for bi0 on the interval 0. to 9.00000d+00 with weighted error 2.46e-18 log weighted error 17.61 significant figures required 17.90 decimal places required 18.15 series for ai0 on the interval 1.25000d-01 to 3.33333d-01 with weighted error 7.87e-17 log weighted error 16.10 significant figures required 14.69 decimal places required 16.76 series for ai02 on the interval 0. to 1.25000d-01 with weighted error 3.79e-17 log weighted error 16.42 significant figures required 14.86 decimal places required 17.09 */ static double bi0_data[12] = { -.07660547252839144951, 1.92733795399380827000, .22826445869203013390, .01304891466707290428, .00043442709008164874, .00000942265768600193, .00000014340062895106, .00000000161384906966, .00000000001396650044, .00000000000009579451, .00000000000000053339, .00000000000000000245 }; static cheb_series bi0_cs = { bi0_data, 11, -1, 1, 11 }; static double ai0_data[21] = { .07575994494023796, .00759138081082334, .00041531313389237, .00001070076463439, -.00000790117997921, -.00000078261435014, .00000027838499429, .00000000825247260, -.00000001204463945, .00000000155964859, .00000000022925563, -.00000000011916228, .00000000001757854, .00000000000112822, -.00000000000114684, .00000000000027155, -.00000000000002415, -.00000000000000608, .00000000000000314, -.00000000000000071, .00000000000000007 }; static cheb_series ai0_cs = { ai0_data, 20, -1, 1, 13 }; static double ai02_data[22] = { .05449041101410882, .00336911647825569, .00006889758346918, .00000289137052082, .00000020489185893, .00000002266668991, .00000000339623203, .00000000049406022, .00000000001188914, -.00000000003149915, -.00000000001321580, -.00000000000179419, .00000000000071801, .00000000000038529, .00000000000001539, -.00000000000004151, -.00000000000000954, .00000000000000382, .00000000000000176, -.00000000000000034, -.00000000000000027, .00000000000000003 }; static cheb_series ai02_cs = { ai02_data, 21, -1, 1, 11 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_I0_scaled_e(const double x, gsl_sf_result * result) { double y = fabs(x); /* CHECK_POINTER(result) */ if(y < 2.0 * GSL_SQRT_DBL_EPSILON) { result->val = 1.0 - y; result->err = 0.5*y*y; return GSL_SUCCESS; } else if(y <= 3.0) { const double ey = exp(-y); gsl_sf_result c; cheb_eval_e(&bi0_cs, y*y/4.5-1.0, &c); result->val = ey * (2.75 + c.val); result->err = GSL_DBL_EPSILON * fabs(result->val) + ey * c.err; return GSL_SUCCESS; } else if(y <= 8.0) { const double sy = sqrt(y); gsl_sf_result c; cheb_eval_e(&ai0_cs, (48.0/y-11.0)/5.0, &c); result->val = (0.375 + c.val) / sy; result->err = 2.0 * GSL_DBL_EPSILON * (0.375 + fabs(c.val)) / sy; result->err += c.err / sy; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sy = sqrt(y); gsl_sf_result c; cheb_eval_e(&ai02_cs, 16.0/y-1.0, &c); result->val = (0.375 + c.val) / sy; result->err = 2.0 * GSL_DBL_EPSILON * (0.375 + fabs(c.val)) / sy; result->err += c.err / sy; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_I0_e(const double x, gsl_sf_result * result) { double y = fabs(x); /* CHECK_POINTER(result) */ if(y < 2.0 * GSL_SQRT_DBL_EPSILON) { result->val = 1.0; result->err = 0.5*y*y; return GSL_SUCCESS; } else if(y <= 3.0) { gsl_sf_result c; cheb_eval_e(&bi0_cs, y*y/4.5-1.0, &c); result->val = 2.75 + c.val; result->err = GSL_DBL_EPSILON * (2.75 + fabs(c.val)); result->err += c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(y < GSL_LOG_DBL_MAX - 1.0) { const double ey = exp(y); gsl_sf_result b_scaled; gsl_sf_bessel_I0_scaled_e(x, &b_scaled); result->val = ey * b_scaled.val; result->err = ey * b_scaled.err + y*GSL_DBL_EPSILON*fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_I0_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_I0_scaled_e(x, &result); ) } double gsl_sf_bessel_I0(const double x) { EVAL_RESULT(gsl_sf_bessel_I0_e(x, &result); ) } sources_5316/external/gsl/gsl_permutation__canonical.c0000664000176700017670000000702511723710247022072 0ustar paulpaul/* permutation/permutation.c * * Copyright (C) 2001, 2002 Nicolas Darnis * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Modified for GSL by Brian Gough. * Use in-place algorithms, no need for workspace * Use conventions for canonical form given in Knuth (opposite of Sedgewick) */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_permutation.h" int gsl_permutation_linear_to_canonical (gsl_permutation * q, const gsl_permutation * p) { const size_t n = p->size; size_t i, k, s; size_t t = n; const size_t *const pp = p->data; size_t *const qq = q->data; if (q->size != p->size) { GSL_ERROR ("size of q does not match size of p", GSL_EINVAL); } for (i = 0; i < n; i++) { k = pp[i]; s = 1; while (k > i) { k = pp[k]; s++; } if (k < i) continue; /* Now have k == i, i.e the least in its cycle, and s == cycle length */ t -= s; qq[t] = i; k = pp[i]; s = 1; while (k > i) { qq[t + s] = k; k = pp[k]; s++; } if (t == 0) break; } return GSL_SUCCESS; } int gsl_permutation_canonical_to_linear (gsl_permutation * p, const gsl_permutation * q) { size_t i, k, kk, first; const size_t n = p->size; size_t *const pp = p->data; const size_t *const qq = q->data; if (q->size != p->size) { GSL_ERROR ("size of q does not match size of p", GSL_EINVAL); } for (i = 0; i < n; i++) { pp[i] = i; } k = qq[0]; first = pp[k]; for (i = 1; i < n; i++) { kk = qq[i]; if (kk > first) { pp[k] = pp[kk]; k = kk; } else { pp[k] = first; k = kk; first = pp[kk]; } } pp[k] = first; return GSL_SUCCESS; } size_t gsl_permutation_inversions (const gsl_permutation * p) { size_t count = 0; size_t i, j; const size_t size = p->size; for (i = 0; i < size - 1; i++) { for (j = i + 1; j < size; j++) { if (p->data[i] > p->data[j]) { count++; } } } return count; } size_t gsl_permutation_linear_cycles (const gsl_permutation * p) { size_t i, k; size_t count = 0; const size_t size = p->size; for (i = 0; i < size; i++) { k = p->data[i]; while (k > i) { k = p->data[k]; } if (k < i) continue; count++; } return count; } size_t gsl_permutation_canonical_cycles (const gsl_permutation * p) { size_t i; size_t count = 1; size_t min = p->data[0]; for (i = 0; i < p->size; i++) { if (p->data[i] < min) { min = p->data[i]; count++; } } return count; } sources_5316/external/gsl/gsl_cblas__sspr.c0000664000176700017670000000050011723710247017636 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_sspr (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *X, const int incX, float *Ap) { #define BASE float #include "gsl_cblas__source_spr.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_tpmv_c.h0000664000176700017670000001361211705263724021537 0ustar paulpaul/* blas/source_tpmv_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { INDEX i, j; const int conj = (TransA == CblasConjTrans) ? -1 : 1; const int Trans = (TransA != CblasConjTrans) ? TransA : CblasTrans; const int nonunit = (Diag == CblasNonUnit); if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasLower)) { /* form x:= A*x */ INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { const BASE Aii_real = CONST_REAL(Ap, TPUP(N, i, i)); const BASE Aii_imag = conj * CONST_IMAG(Ap, TPUP(N, i, i)); BASE temp_r; BASE temp_i; if (nonunit) { BASE x_real = REAL(X, ix); BASE x_imag = IMAG(X, ix); temp_r = Aii_real * x_real - Aii_imag * x_imag; temp_i = Aii_real * x_imag + Aii_imag * x_real; } else { temp_r = REAL(X, ix); temp_i = IMAG(X, ix); } { INDEX jx = OFFSET(N, incX) + (i + 1) * incX; for (j = i + 1; j < N; j++) { const BASE Aij_real = CONST_REAL(Ap, TPUP(N, i, j)); const BASE Aij_imag = conj * CONST_IMAG(Ap, TPUP(N, i, j)); BASE x_real = REAL(X, jx); BASE x_imag = IMAG(X, jx); temp_r += Aij_real * x_real - Aij_imag * x_imag; temp_i += Aij_real * x_imag + Aij_imag * x_real; jx += incX; } } REAL(X, ix) = temp_r; IMAG(X, ix) = temp_i; ix += incX; } } else if ((order == CblasRowMajor && Trans == CblasNoTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX) + incX * (N - 1); for (i = N; i > 0 && i--;) { const BASE Aii_real = CONST_REAL(Ap, TPLO(N, i, i)); const BASE Aii_imag = conj * CONST_IMAG(Ap, TPLO(N, i, i)); BASE temp_r; BASE temp_i; if (nonunit) { BASE x_real = REAL(X, ix); BASE x_imag = IMAG(X, ix); temp_r = Aii_real * x_real - Aii_imag * x_imag; temp_i = Aii_real * x_imag + Aii_imag * x_real; } else { temp_r = REAL(X, ix); temp_i = IMAG(X, ix); } { INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { const BASE Aij_real = CONST_REAL(Ap, TPLO(N, i, j)); const BASE Aij_imag = conj * CONST_IMAG(Ap, TPLO(N, i, j)); BASE x_real = REAL(X, jx); BASE x_imag = IMAG(X, jx); temp_r += Aij_real * x_real - Aij_imag * x_imag; temp_i += Aij_real * x_imag + Aij_imag * x_real; jx += incX; } } REAL(X, ix) = temp_r; IMAG(X, ix) = temp_i; ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasUpper) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasLower)) { /* form x := A'*x */ INDEX ix = OFFSET(N, incX) + incX * (N - 1); for (i = N; i > 0 && i--;) { const BASE Aii_real = CONST_REAL(Ap, TPUP(N, i, i)); const BASE Aii_imag = conj * CONST_IMAG(Ap, TPUP(N, i, i)); BASE temp_r; BASE temp_i; if (nonunit) { BASE x_real = REAL(X, ix); BASE x_imag = IMAG(X, ix); temp_r = Aii_real * x_real - Aii_imag * x_imag; temp_i = Aii_real * x_imag + Aii_imag * x_real; } else { temp_r = REAL(X, ix); temp_i = IMAG(X, ix); } { INDEX jx = OFFSET(N, incX); for (j = 0; j < i; j++) { BASE x_real = REAL(X, jx); BASE x_imag = IMAG(X, jx); const BASE Aji_real = CONST_REAL(Ap, TPUP(N, j, i)); const BASE Aji_imag = conj * CONST_IMAG(Ap, TPUP(N, j, i)); temp_r += Aji_real * x_real - Aji_imag * x_imag; temp_i += Aji_real * x_imag + Aji_imag * x_real; jx += incX; } } REAL(X, ix) = temp_r; IMAG(X, ix) = temp_i; ix -= incX; } } else if ((order == CblasRowMajor && Trans == CblasTrans && Uplo == CblasLower) || (order == CblasColMajor && Trans == CblasNoTrans && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); for (i = 0; i < N; i++) { const BASE Aii_real = CONST_REAL(Ap, TPLO(N, i, i)); const BASE Aii_imag = conj * CONST_IMAG(Ap, TPLO(N, i, i)); BASE temp_r; BASE temp_i; if (nonunit) { BASE x_real = REAL(X, ix); BASE x_imag = IMAG(X, ix); temp_r = Aii_real * x_real - Aii_imag * x_imag; temp_i = Aii_real * x_imag + Aii_imag * x_real; } else { temp_r = REAL(X, ix); temp_i = IMAG(X, ix); } { INDEX jx = OFFSET(N, incX) + (i + 1) * incX; for (j = i + 1; j < N; j++) { BASE x_real = REAL(X, jx); BASE x_imag = IMAG(X, jx); const BASE Aji_real = CONST_REAL(Ap, TPLO(N, j, i)); const BASE Aji_imag = conj * CONST_IMAG(Ap, TPLO(N, j, i)); temp_r += Aji_real * x_real - Aji_imag * x_imag; temp_i += Aji_real * x_imag + Aji_imag * x_real; jx += incX; } } REAL(X, ix) = temp_r; IMAG(X, ix) = temp_i; ix += incX; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_dht__dht.c0000664000176700017670000001125511723710247017132 0ustar paulpaul/* dht/dht.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_math.h" #include "gsl_sf_bessel.h" #include "gsl_dht.h" gsl_dht * gsl_dht_alloc (size_t size) { gsl_dht * t; if(size == 0) { GSL_ERROR_VAL("size == 0", GSL_EDOM, 0); } t = (gsl_dht *)malloc(sizeof(gsl_dht)); if(t == 0) { GSL_ERROR_VAL("out of memory", GSL_ENOMEM, 0); } t->size = size; t->xmax = -1.0; /* Make it clear that this needs to be calculated. */ t->nu = -1.0; t->j = (double *)malloc((size+2)*sizeof(double)); if(t->j == 0) { free(t); GSL_ERROR_VAL("could not allocate memory for j", GSL_ENOMEM, 0); } t->Jjj = (double *)malloc(size*(size+1)/2 * sizeof(double)); if(t->Jjj == 0) { free(t->j); free(t); GSL_ERROR_VAL("could not allocate memory for Jjj", GSL_ENOMEM, 0); } t->J2 = (double *)malloc((size+1)*sizeof(double)); if(t->J2 == 0) { free(t->Jjj); free(t->j); free(t); GSL_ERROR_VAL("could not allocate memory for J2", GSL_ENOMEM, 0); } return t; } /* Handle internal calculation of Bessel zeros. */ static int dht_bessel_zeros(gsl_dht * t) { unsigned int s; gsl_sf_result z; int stat_z = 0; t->j[0] = 0.0; for(s=1; s < t->size + 2; s++) { stat_z += gsl_sf_bessel_zero_Jnu_e(t->nu, s, &z); t->j[s] = z.val; } if(stat_z != 0) { GSL_ERROR("could not compute bessel zeroes", GSL_EFAILED); } else { return GSL_SUCCESS; } } gsl_dht * gsl_dht_new (size_t size, double nu, double xmax) { int status; gsl_dht * dht = gsl_dht_alloc (size); if (dht == 0) return 0; status = gsl_dht_init(dht, nu, xmax); if (status) return 0; return dht; } int gsl_dht_init(gsl_dht * t, double nu, double xmax) { if(xmax <= 0.0) { GSL_ERROR ("xmax is not positive", GSL_EDOM); } else if(nu < 0.0) { GSL_ERROR ("nu is negative", GSL_EDOM); } else { size_t n, m; int stat_bz = GSL_SUCCESS; int stat_J = 0; double jN; if(nu != t->nu) { /* Recalculate Bessel zeros if necessary. */ t->nu = nu; stat_bz = dht_bessel_zeros(t); } jN = t->j[t->size+1]; t->xmax = xmax; t->kmax = jN / xmax; t->J2[0] = 0.0; for(m=1; msize+1; m++) { gsl_sf_result J; stat_J += gsl_sf_bessel_Jnu_e(nu + 1.0, t->j[m], &J); t->J2[m] = J.val * J.val; } /* J_nu(j[n] j[m] / j[N]) = Jjj[n(n-1)/2 + m - 1], 1 <= n,m <= size */ for(n=1; nsize+1; n++) { for(m=1; m<=n; m++) { double arg = t->j[n] * t->j[m] / jN; gsl_sf_result J; stat_J += gsl_sf_bessel_Jnu_e(nu, arg, &J); t->Jjj[n*(n-1)/2 + m - 1] = J.val; } } if(stat_J != 0) { GSL_ERROR("error computing bessel function", GSL_EFAILED); } else { return stat_bz; } } } double gsl_dht_x_sample(const gsl_dht * t, int n) { return t->j[n+1]/t->j[t->size+1] * t->xmax; } double gsl_dht_k_sample(const gsl_dht * t, int n) { return t->j[n+1] / t->xmax; } void gsl_dht_free(gsl_dht * t) { free(t->J2); free(t->Jjj); free(t->j); free(t); } int gsl_dht_apply(const gsl_dht * t, double * f_in, double * f_out) { const double jN = t->j[t->size + 1]; const double r = t->xmax / jN; size_t m; size_t i; for(m=0; msize; m++) { double sum = 0.0; double Y; for(i=0; isize; i++) { /* Need to find max and min so that we * address the symmetric Jjj matrix properly. * FIXME: we can presumably optimize this * by just running over the elements of Jjj * in a deterministic manner. */ size_t m_local; size_t n_local; if(i < m) { m_local = i; n_local = m; } else { m_local = m; n_local = i; } Y = t->Jjj[n_local*(n_local+1)/2 + m_local] / t->J2[i+1]; sum += Y * f_in[i]; } f_out[m] = sum * 2.0 * r*r; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_sf__bessel_Inu.c0000644000176700017670000000655110707442037020275 0ustar paulpaul/* specfunc/bessel_Inu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_gamma.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" #include "gsl_sf__bessel_temme.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Inu_scaled_e(double nu, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x < 0.0 || nu < 0.0) { DOMAIN_ERROR(result); } else if(x*x < 10.0*(nu+1.0)) { gsl_sf_result b; double ex = exp(-x); int stat = gsl_sf_bessel_IJ_taylor_e(nu, x, 1, 100, GSL_DBL_EPSILON, &b); result->val = b.val * ex; result->err = b.err * ex; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat; } else if(0.5/(nu*nu + x*x) < GSL_ROOT3_DBL_EPSILON) { return gsl_sf_bessel_Inu_scaled_asymp_unif_e(nu, x, result); } else { int N = (int)(nu + 0.5); double mu = nu - N; /* -1/2 <= mu <= 1/2 */ double K_mu, K_mup1, Kp_mu; double K_nu, K_nup1, K_num1; double I_nu_ratio; int stat_Irat; int stat_Kmu; int n; /* obtain K_mu, K_mup1 */ if(x < 2.0) { stat_Kmu = gsl_sf_bessel_K_scaled_temme(mu, x, &K_mu, &K_mup1, &Kp_mu); } else { stat_Kmu = gsl_sf_bessel_K_scaled_steed_temme_CF2(mu, x, &K_mu, &K_mup1, &Kp_mu); } /* recurse forward to obtain K_num1, K_nu */ K_nu = K_mu; K_nup1 = K_mup1; for(n=0; nval = 1.0/(x * (K_nup1 + I_nu_ratio * K_nu)); result->err = GSL_DBL_EPSILON * (0.5*N + 2.0) * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Kmu, stat_Irat); } } int gsl_sf_bessel_Inu_e(double nu, double x, gsl_sf_result * result) { gsl_sf_result b; int stat_I = gsl_sf_bessel_Inu_scaled_e(nu, x, &b); int stat_e = gsl_sf_exp_mult_err_e(x, fabs(x*GSL_DBL_EPSILON), b.val, b.err, result); return GSL_ERROR_SELECT_2(stat_e, stat_I); } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_Inu_scaled(double nu, double x) { EVAL_RESULT(gsl_sf_bessel_Inu_scaled_e(nu, x, &result)); } double gsl_sf_bessel_Inu(double nu, double x) { EVAL_RESULT(gsl_sf_bessel_Inu_e(nu, x, &result)); } sources_5316/external/gsl/gsl_vector__view_source.c0000664000176700017670000000402711723710247021427 0ustar paulpaul/* vector/view_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ QUALIFIED_VIEW(_gsl_vector,view) FUNCTION(gsl_vector, view_array) (QUALIFIER ATOMIC * base, size_t n) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (n == 0) { GSL_ERROR_VAL ("vector length n must be positive integer", GSL_EINVAL, view); } { TYPE(gsl_vector) v = NULL_VECTOR; v.data = (ATOMIC *)base ; v.size = n; v.stride = 1; v.block = 0; v.owner = 0; view.vector = v; return view; } } QUALIFIED_VIEW(_gsl_vector,view) FUNCTION(gsl_vector, view_array_with_stride) (QUALIFIER ATOMIC * base, size_t stride, size_t n) { QUALIFIED_VIEW(_gsl_vector,view) view = NULL_VECTOR_VIEW; if (n == 0) { GSL_ERROR_VAL ("vector length n must be positive integer", GSL_EINVAL, view); } if (stride == 0) { GSL_ERROR_VAL ("stride must be positive integer", GSL_EINVAL, view); } { TYPE(gsl_vector) v = NULL_VECTOR; v.data = (ATOMIC *)base ; v.size = n; v.stride = stride; v.block = 0; v.owner = 0; view.vector = v; return view; } } sources_5316/external/gsl/gsl_sf__bessel_K1.c0000644000176700017670000001377610707442037020024 0ustar paulpaul/* specfunc/bessel_K1.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_exp.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* based on SLATEC besk1(), besk1e() */ /* chebyshev expansions series for bk1 on the interval 0. to 4.00000d+00 with weighted error 7.02e-18 log weighted error 17.15 significant figures required 16.73 decimal places required 17.67 series for ak1 on the interval 1.25000d-01 to 5.00000d-01 with weighted error 6.06e-17 log weighted error 16.22 significant figures required 15.41 decimal places required 16.83 series for ak12 on the interval 0. to 1.25000d-01 with weighted error 2.58e-17 log weighted error 16.59 significant figures required 15.22 decimal places required 17.16 */ static double bk1_data[11] = { 0.0253002273389477705, -0.3531559607765448760, -0.1226111808226571480, -0.0069757238596398643, -0.0001730288957513052, -0.0000024334061415659, -0.0000000221338763073, -0.0000000001411488392, -0.0000000000006666901, -0.0000000000000024274, -0.0000000000000000070 }; static cheb_series bk1_cs = { bk1_data, 10, -1, 1, 8 }; static double ak1_data[17] = { 0.27443134069738830, 0.07571989953199368, -0.00144105155647540, 0.00006650116955125, -0.00000436998470952, 0.00000035402774997, -0.00000003311163779, 0.00000000344597758, -0.00000000038989323, 0.00000000004720819, -0.00000000000604783, 0.00000000000081284, -0.00000000000011386, 0.00000000000001654, -0.00000000000000248, 0.00000000000000038, -0.00000000000000006 }; static cheb_series ak1_cs = { ak1_data, 16, -1, 1, 9 }; static double ak12_data[14] = { 0.06379308343739001, 0.02832887813049721, -0.00024753706739052, 0.00000577197245160, -0.00000020689392195, 0.00000000973998344, -0.00000000055853361, 0.00000000003732996, -0.00000000000282505, 0.00000000000023720, -0.00000000000002176, 0.00000000000000215, -0.00000000000000022, 0.00000000000000002 }; static cheb_series ak12_cs = { ak12_data, 13, -1, 1, 7 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_K1_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*GSL_DBL_MIN) { OVERFLOW_ERROR(result); } else if(x <= 2.0) { const double lx = log(x); const double ex = exp(x); int stat_I1; gsl_sf_result I1; gsl_sf_result c; cheb_eval_e(&bk1_cs, 0.5*x*x-1.0, &c); stat_I1 = gsl_sf_bessel_I1_e(x, &I1); result->val = ex * ((lx-M_LN2)*I1.val + (0.75 + c.val)/x); result->err = ex * (c.err/x + fabs(lx)*I1.err); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_I1; } else if(x <= 8.0) { const double sx = sqrt(x); gsl_sf_result c; cheb_eval_e(&ak1_cs, (16.0/x-5.0)/3.0, &c); result->val = (1.25 + c.val) / sx; result->err = c.err / sx; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double sx = sqrt(x); gsl_sf_result c; cheb_eval_e(&ak12_cs, 16.0/x-1.0, &c); result->val = (1.25 + c.val) / sx; result->err = c.err / sx; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_bessel_K1_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(x < 2.0*GSL_DBL_MIN) { OVERFLOW_ERROR(result); } else if(x <= 2.0) { const double lx = log(x); int stat_I1; gsl_sf_result I1; gsl_sf_result c; cheb_eval_e(&bk1_cs, 0.5*x*x-1.0, &c); stat_I1 = gsl_sf_bessel_I1_e(x, &I1); result->val = (lx-M_LN2)*I1.val + (0.75 + c.val)/x; result->err = c.err/x + fabs(lx)*I1.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_I1; } else { gsl_sf_result K1_scaled; int stat_K1 = gsl_sf_bessel_K1_scaled_e(x, &K1_scaled); int stat_e = gsl_sf_exp_mult_err_e(-x, 0.0, K1_scaled.val, K1_scaled.err, result); result->err = fabs(result->val) * (GSL_DBL_EPSILON*fabs(x) + K1_scaled.err/K1_scaled.val); return GSL_ERROR_SELECT_2(stat_e, stat_K1); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_K1_scaled(const double x) { EVAL_RESULT(gsl_sf_bessel_K1_scaled_e(x, &result)); } double gsl_sf_bessel_K1(const double x) { EVAL_RESULT(gsl_sf_bessel_K1_e(x, &result)); } sources_5316/external/gsl/gsl_diff__diff.c0000664000176700017670000001123311723710247017410 0ustar paulpaul/* diff/diff.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 David Morrison * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_diff.h" int gsl_diff_backward (const gsl_function * f, double x, double *result, double *abserr) { /* Construct a divided difference table with a fairly large step size to get a very rough estimate of f''. Use this to estimate the step size which will minimize the error in calculating f'. */ int i, k; double h = GSL_SQRT_DBL_EPSILON; double a[3], d[3], a2; /* Algorithm based on description on pg. 204 of Conte and de Boor (CdB) - coefficients of Newton form of polynomial of degree 2. */ for (i = 0; i < 3; i++) { a[i] = x + (i - 2.0) * h; d[i] = GSL_FN_EVAL (f, a[i]); } for (k = 1; k < 4; k++) { for (i = 0; i < 3 - k; i++) { d[i] = (d[i + 1] - d[i]) / (a[i + k] - a[i]); } } /* Adapt procedure described on pg. 282 of CdB to find best value of step size. */ a2 = fabs (d[0] + d[1] + d[2]); if (a2 < 100.0 * GSL_SQRT_DBL_EPSILON) { a2 = 100.0 * GSL_SQRT_DBL_EPSILON; } h = sqrt (GSL_SQRT_DBL_EPSILON / (2.0 * a2)); if (h > 100.0 * GSL_SQRT_DBL_EPSILON) { h = 100.0 * GSL_SQRT_DBL_EPSILON; } *result = (GSL_FN_EVAL (f, x) - GSL_FN_EVAL (f, x - h)) / h; *abserr = fabs (10.0 * a2 * h); return GSL_SUCCESS; } int gsl_diff_forward (const gsl_function * f, double x, double *result, double *abserr) { /* Construct a divided difference table with a fairly large step size to get a very rough estimate of f''. Use this to estimate the step size which will minimize the error in calculating f'. */ int i, k; double h = GSL_SQRT_DBL_EPSILON; double a[3], d[3], a2; /* Algorithm based on description on pg. 204 of Conte and de Boor (CdB) - coefficients of Newton form of polynomial of degree 2. */ for (i = 0; i < 3; i++) { a[i] = x + i * h; d[i] = GSL_FN_EVAL (f, a[i]); } for (k = 1; k < 4; k++) { for (i = 0; i < 3 - k; i++) { d[i] = (d[i + 1] - d[i]) / (a[i + k] - a[i]); } } /* Adapt procedure described on pg. 282 of CdB to find best value of step size. */ a2 = fabs (d[0] + d[1] + d[2]); if (a2 < 100.0 * GSL_SQRT_DBL_EPSILON) { a2 = 100.0 * GSL_SQRT_DBL_EPSILON; } h = sqrt (GSL_SQRT_DBL_EPSILON / (2.0 * a2)); if (h > 100.0 * GSL_SQRT_DBL_EPSILON) { h = 100.0 * GSL_SQRT_DBL_EPSILON; } *result = (GSL_FN_EVAL (f, x + h) - GSL_FN_EVAL (f, x)) / h; *abserr = fabs (10.0 * a2 * h); return GSL_SUCCESS; } int gsl_diff_central (const gsl_function * f, double x, double *result, double *abserr) { /* Construct a divided difference table with a fairly large step size to get a very rough estimate of f'''. Use this to estimate the step size which will minimize the error in calculating f'. */ int i, k; double h = GSL_SQRT_DBL_EPSILON; double a[4], d[4], a3; /* Algorithm based on description on pg. 204 of Conte and de Boor (CdB) - coefficients of Newton form of polynomial of degree 3. */ for (i = 0; i < 4; i++) { a[i] = x + (i - 2.0) * h; d[i] = GSL_FN_EVAL (f, a[i]); } for (k = 1; k < 5; k++) { for (i = 0; i < 4 - k; i++) { d[i] = (d[i + 1] - d[i]) / (a[i + k] - a[i]); } } /* Adapt procedure described on pg. 282 of CdB to find best value of step size. */ a3 = fabs (d[0] + d[1] + d[2] + d[3]); if (a3 < 100.0 * GSL_SQRT_DBL_EPSILON) { a3 = 100.0 * GSL_SQRT_DBL_EPSILON; } h = pow (GSL_SQRT_DBL_EPSILON / (2.0 * a3), 1.0 / 3.0); if (h > 100.0 * GSL_SQRT_DBL_EPSILON) { h = 100.0 * GSL_SQRT_DBL_EPSILON; } *result = (GSL_FN_EVAL (f, x + h) - GSL_FN_EVAL (f, x - h)) / (2.0 * h); *abserr = fabs (100.0 * a3 * h * h); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_ieee-utils__fp-gnuc99.c0000664000176700017670000001045011723710247021356 0ustar paulpaul/* ieee-utils/fp-gnuc99.c * * Copyright (C) 2003, 2004, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #define _GNU_SOURCE 1 #include #include #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { int mode; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("single precision rounding is not supported by ", GSL_EUNSUP) ; break ; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("double precision rounding is not supported by ", GSL_EUNSUP) ; break ; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("extended precision rounding is not supported by ", GSL_EUNSUP) ; break ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: #ifdef FE_TONEAREST fesetround (FE_TONEAREST) ; #else GSL_ERROR ("round-to-nearest is not supported by ", GSL_EUNSUP) ; #endif break ; case GSL_IEEE_ROUND_DOWN: #ifdef FE_DOWNWARD fesetround (FE_DOWNWARD) ; #else GSL_ERROR ("round-down is not supported by ", GSL_EUNSUP) ; #endif break ; case GSL_IEEE_ROUND_UP: #ifdef FE_UPWARD fesetround (FE_UPWARD) ; #else GSL_ERROR ("round-up is not supported by ", GSL_EUNSUP) ; #endif break ; case GSL_IEEE_ROUND_TO_ZERO: #ifdef FE_TOWARDZERO fesetround (FE_TOWARDZERO) ; #else GSL_ERROR ("round-toward-zero is not supported by ", GSL_EUNSUP) ; #endif break ; default: #ifdef FE_TONEAREST fesetround (FE_TONEAREST) ; #else GSL_ERROR ("default round-to-nearest mode is not supported by ", GSL_EUNSUP) ; #endif } /* Turn on all the exceptions apart from 'inexact' */ mode = 0; #ifdef FE_INVALID mode |= FE_INVALID; #endif #ifdef FE_DIVBYZERO mode |= FE_DIVBYZERO; #endif #ifdef FE_OVERFLOW mode |= FE_OVERFLOW ; #endif #ifdef FE_UNDERFLOW mode |= FE_UNDERFLOW ; #endif if (exception_mask & GSL_IEEE_MASK_INVALID) { #ifdef FE_INVALID mode &= ~ FE_INVALID ; #else GSL_ERROR ("invalid operation exception not supported by ", GSL_EUNSUP); #endif } if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { /* do nothing */ } else { GSL_ERROR ("denormalized operand exception not supported by . " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) { #ifdef FE_DIVBYZERO mode &= ~ FE_DIVBYZERO ; #else GSL_ERROR ("division by zero exception not supported by ", GSL_EUNSUP); #endif } if (exception_mask & GSL_IEEE_MASK_OVERFLOW) { #ifdef FE_OVERFLOW mode &= ~ FE_OVERFLOW ; #else GSL_ERROR ("overflow exception not supported by ", GSL_EUNSUP); #endif } if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) { #ifdef FE_UNDERFLOW mode &= ~ FE_UNDERFLOW ; #else GSL_ERROR ("underflow exception not supported by ", GSL_EUNSUP); #endif } if (exception_mask & GSL_IEEE_TRAP_INEXACT) { #ifdef FE_INEXACT mode |= FE_INEXACT ; #else GSL_ERROR ("inexact exception not supported by ", GSL_EUNSUP); #endif } else { #ifdef FE_INEXACT mode &= ~ FE_INEXACT ; #else /* do nothing */ #endif } #if HAVE_DECL_FEENABLEEXCEPT feenableexcept (mode) ; #elif HAVE_DECL_FESETTRAPENABLE fesettrapenable (mode); #else GSL_ERROR ("unknown exception trap method", GSL_EUNSUP) #endif return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_statistics__absdev.c0000664000176700017670000000303311723710247021225 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__absdev_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_vector__oper.c0000664000176700017670000000273011723710247020041 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_vector.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__oper_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_statistics__wskew_source.c0000664000176700017670000000400711723710247022503 0ustar paulpaul/* statistics/wskew_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,wskew) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n) { const double wmean = FUNCTION(gsl_stats,wmean)(w, wstride, data, stride, n); const double wsd = FUNCTION(gsl_stats,wsd_m)(w, wstride, data, stride, n, wmean); return FUNCTION(gsl_stats,wskew_m_sd)(w, wstride, data, stride, n, wmean, wsd); } double FUNCTION(gsl_stats,wskew_m_sd) (const BASE w[], const size_t wstride, const BASE data[], const size_t stride, const size_t n, const double wmean, const double wsd) { /* Compute the weighted skewness of a dataset */ long double wskew = 0; long double W = 0; size_t i; /* find the sum of the cubed deviations, normalized by the sd. */ /* we use a recurrence relation to stably update a running value so there aren't any large sums that can overflow */ for (i = 0; i < n; i++) { BASE wi = w[i * wstride]; if (wi > 0) { const long double x = (data[i * stride] - wmean) / wsd; W += wi ; wskew += (x * x * x - wskew) * (wi / W); } } return wskew; } sources_5316/external/gsl/gsl_rng__zuf.c0000664000176700017670000000671211723710247017170 0ustar paulpaul/* rng/zuf.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* It is crucial that m == n-273 mod 607 at all times; For speed of execution, however, this is never enforced. Instead is is set in the initializer: note 607-273=334 Note also that the state.u[607] is not initialized */ static inline unsigned long int zuf_get (void *vstate); static double zuf_get_double (void *vstate); static void zuf_set (void *state, unsigned long int s); static const unsigned long int zuf_randmax = 16777216; /* 2^24 */ typedef struct { int n; unsigned long int u[607]; } zuf_state_t; /* The zufall package was implemented with float's, which is to say 24 bits of precision. Since I'm using long's instead, my RANDMAX reflects this. */ static inline unsigned long int zuf_get (void *vstate) { zuf_state_t *state = (zuf_state_t *) vstate; const int n = state->n; const int m = (n - 273 + 607) % 607; unsigned long int t = state->u[n] + state->u[m]; while (t > zuf_randmax) t -= zuf_randmax; state->u[n] = t; if (n == 606) { state->n = 0; } else { state->n = n + 1; } return t; } static double zuf_get_double (void *vstate) { return zuf_get (vstate) / 16777216.0 ; } static void zuf_set (void *vstate, unsigned long int s) { /* A very elaborate seeding procedure is provided with the zufall package; this is virtually a copy of that procedure */ /* Initialized data */ long int kl = 9373; long int ij = 1802; /* Local variables */ long int i, j, k, l, m; double x, y; long int ii, jj; zuf_state_t *state = (zuf_state_t *) vstate; state->n = 0; /* generates initial seed buffer by linear congruential */ /* method. Taken from Marsaglia, FSU report FSU-SCRI-87-50 */ /* variable seed should be 0 < seed <31328 */ if (s == 0) s = 1802; /* default seed is 1802 */ ij = s; i = ij / 177 % 177 + 2; j = ij % 177 + 2; k = kl / 169 % 178 + 1; l = kl % 169; for (ii = 0; ii < 607; ++ii) { x = 0.0; y = 0.5; /* 24 bits?? */ for (jj = 1; jj <= 24; ++jj) { m = i * j % 179 * k % 179; i = j; j = k; k = m; l = (l * 53 + 1) % 169; if (l * m % 64 >= 32) { x += y; } y *= 0.5; } state->u[ii] = (unsigned long int) (x * zuf_randmax); } } static const gsl_rng_type zuf_type = {"zuf", /* name */ 0x00ffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (zuf_state_t), &zuf_set, &zuf_get, &zuf_get_double}; const gsl_rng_type *gsl_rng_zuf = &zuf_type; sources_5316/external/gsl/gsl_statistics__ttest.c0000664000176700017670000000302211723710247021122 0ustar paulpaul#include "gsl__config.h" #include #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__ttest_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_block_ulong.h0000664000176700017670000000450111705263724017657 0ustar paulpaul/* block/gsl_block_ulong.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_BLOCK_ULONG_H__ #define __GSL_BLOCK_ULONG_H__ #include #include "gsl_errno.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS struct gsl_block_ulong_struct { size_t size; unsigned long *data; }; typedef struct gsl_block_ulong_struct gsl_block_ulong; gsl_block_ulong *gsl_block_ulong_alloc (const size_t n); gsl_block_ulong *gsl_block_ulong_calloc (const size_t n); void gsl_block_ulong_free (gsl_block_ulong * b); int gsl_block_ulong_fread (FILE * stream, gsl_block_ulong * b); int gsl_block_ulong_fwrite (FILE * stream, const gsl_block_ulong * b); int gsl_block_ulong_fscanf (FILE * stream, gsl_block_ulong * b); int gsl_block_ulong_fprintf (FILE * stream, const gsl_block_ulong * b, const char *format); int gsl_block_ulong_raw_fread (FILE * stream, unsigned long * b, const size_t n, const size_t stride); int gsl_block_ulong_raw_fwrite (FILE * stream, const unsigned long * b, const size_t n, const size_t stride); int gsl_block_ulong_raw_fscanf (FILE * stream, unsigned long * b, const size_t n, const size_t stride); int gsl_block_ulong_raw_fprintf (FILE * stream, const unsigned long * b, const size_t n, const size_t stride, const char *format); size_t gsl_block_ulong_size (const gsl_block_ulong * b); unsigned long * gsl_block_ulong_data (const gsl_block_ulong * b); __END_DECLS #endif /* __GSL_BLOCK_ULONG_H__ */ sources_5316/external/gsl/gsl_rng__fishman2x.c0000664000176700017670000000551611723710247020264 0ustar paulpaul/* rng/fishman2x.c * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth * The Art of Computer Programming * Volume 2 * Third Edition * Addison-Wesley * Page 108 * * It is called "Fishman - L'Ecuyer" * * This implementation copyright (C) 2001 Carlo Perassi * and (C) 2003 Heiko Bauke. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* Fishman */ #define AAA_F 48271UL #define MMM_F 0x7fffffffUL /* 2 ^ 31 - 1 */ #define QQQ_F 44488UL #define RRR_F 3399UL /* L'Ecuyer */ #define AAA_L 40692UL #define MMM_L 0x7fffff07UL /* 2 ^ 31 - 249 */ #define QQQ_L 52774UL #define RRR_L 3791UL static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); typedef struct { unsigned long int x; unsigned long int y; unsigned long int z; } ran_state_t; static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; long int y, r; r = RRR_F * (state->x / QQQ_F); y = AAA_F * (state->x % QQQ_F) - r; if (y < 0) y += MMM_F; state->x = y; r = RRR_L * (state->y / QQQ_L); y = AAA_L * (state->y % QQQ_L) - r; if (y < 0) y += MMM_L; state->y = y; state->z = (state->x > state->y) ? (state->x - state->y) : MMM_F + state->x - state->y; return state->z; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 2147483647.0; } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; if ((s % MMM_F) == 0 || (s % MMM_L) == 0) s = 1; /* default seed is 1 */ state->x = s % MMM_F; state->y = s % MMM_L; state->z = (state->x > state->y) ? (state->x - state->y) : MMM_F + state->x - state->y; return; } static const gsl_rng_type ran_type = { "fishman2x", /* name */ MMM_F - 1, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_fishman2x = &ran_type; sources_5316/external/gsl/gsl_rng__gfsr4.c0000664000176700017670000001261211723710247017405 0ustar paulpaul/* This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA From Robert M. Ziff, "Four-tap shift-register-sequence random-number generators," Computers in Physics 12(4), Jul/Aug 1998, pp 385-392. A generalized feedback shift-register (GFSR) is basically an xor-sum of particular past lagged values. A four-tap register looks like: ra[nd] = ra[nd-A] ^ ra[nd-B] ^ ra[nd-C] ^ ra[nd-D] Ziff notes that "it is now widely known" that two-tap registers have serious flaws, the most obvious one being the three-point correlation that comes from the defn of the generator. Nice mathematical properties can be derived for GFSR's, and numerics bears out the claim that 4-tap GFSR's with appropriately chosen offsets are as random as can be measured, using the author's test. This implementation uses the values suggested the the author's example on p392, but altered to fit the GSL framework. The "state" is 2^14 longs, or 64Kbytes; 2^14 is the smallest power of two that is larger than D, the largest offset. We really only need a state with the last D values, but by going to a power of two, we can do a masking operation instead of a modulo, and this is presumably faster, though I haven't actually tried it. The article actually suggested a short/fast hack: #define RandomInteger (++nd, ra[nd&M]=ra[(nd-A)&M]\ ^ra[(nd-B)&M]^ra[(nd-C)&M]^ra[(nd-D)&M]) so that (as long as you've defined nd,ra[M+1]), then you ca do things like: 'if (RandomInteger < p) {...}'. Note that n&M varies from 0 to M, *including* M, so that the array has to be of size M+1. Since M+1 is a power of two, n&M is a potentially quicker implementation of the equivalent n%(M+1). This implementation copyright (C) 1998 James Theiler, based on the example mt.c in the GSL, as implemented by Brian Gough. */ #include "gsl__config.h" #include #include "gsl_rng.h" static inline unsigned long int gfsr4_get (void *vstate); static double gfsr4_get_double (void *vstate); static void gfsr4_set (void *state, unsigned long int s); /* Magic numbers */ #define A 471 #define B 1586 #define C 6988 #define D 9689 #define M 16383 /* = 2^14-1 */ /* #define M 0x0003fff */ typedef struct { int nd; unsigned long ra[M+1]; } gfsr4_state_t; static inline unsigned long gfsr4_get (void *vstate) { gfsr4_state_t *state = (gfsr4_state_t *) vstate; state->nd = ((state->nd)+1)&M; return state->ra[(state->nd)] = state->ra[((state->nd)+(M+1-A))&M]^ state->ra[((state->nd)+(M+1-B))&M]^ state->ra[((state->nd)+(M+1-C))&M]^ state->ra[((state->nd)+(M+1-D))&M]; } static double gfsr4_get_double (void * vstate) { return gfsr4_get (vstate) / 4294967296.0 ; } static void gfsr4_set (void *vstate, unsigned long int s) { gfsr4_state_t *state = (gfsr4_state_t *) vstate; int i, j; /* Masks for turning on the diagonal bit and turning off the leftmost bits */ unsigned long int msb = 0x80000000UL; unsigned long int mask = 0xffffffffUL; if (s == 0) s = 4357; /* the default seed is 4357 */ /* We use the congruence s_{n+1} = (69069*s_n) mod 2^32 to initialize the state. This works because ANSI-C unsigned long integer arithmetic is automatically modulo 2^32 (or a higher power of two), so we can safely ignore overflow. */ #define LCG(n) ((69069 * n) & 0xffffffffUL) /* Brian Gough suggests this to avoid low-order bit correlations */ for (i = 0; i <= M; i++) { unsigned long t = 0 ; unsigned long bit = msb ; for (j = 0; j < 32; j++) { s = LCG(s) ; if (s & msb) t |= bit ; bit >>= 1 ; } state->ra[i] = t ; } /* Perform the "orthogonalization" of the matrix */ /* Based on the orthogonalization used in r250, as suggested initially * by Kirkpatrick and Stoll, and pointed out to me by Brian Gough */ /* BJG: note that this orthogonalisation doesn't have any effect here because the the initial 6695 elements do not participate in the calculation. For practical purposes this orthogonalisation is somewhat irrelevant, because the probability of the original sequence being degenerate should be exponentially small. */ for (i=0; i<32; ++i) { int k=7+i*3; state->ra[k] &= mask; /* Turn off bits left of the diagonal */ state->ra[k] |= msb; /* Turn on the diagonal bit */ mask >>= 1; msb >>= 1; } state->nd = i; } static const gsl_rng_type gfsr4_type = {"gfsr4", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (gfsr4_state_t), &gfsr4_set, &gfsr4_get, &gfsr4_get_double}; const gsl_rng_type *gsl_rng_gfsr4 = &gfsr4_type; sources_5316/external/gsl/gsl_linalg__hh.c0000664000176700017670000001104611723710247017437 0ustar paulpaul/* linalg/hh.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_linalg.h" #define REAL double /* [Engeln-Mullges + Uhlig, Alg. 4.42] */ int gsl_linalg_HH_solve (gsl_matrix * A, const gsl_vector * b, gsl_vector * x) { if (A->size1 > A->size2) { /* System is underdetermined. */ GSL_ERROR ("System is underdetermined", GSL_EINVAL); } else if (A->size2 != x->size) { GSL_ERROR ("matrix and vector sizes must be equal", GSL_EBADLEN); } else { int status ; gsl_vector_memcpy (x, b); status = gsl_linalg_HH_svx (A, x); return status ; } } int gsl_linalg_HH_svx (gsl_matrix * A, gsl_vector * x) { if (A->size1 > A->size2) { /* System is underdetermined. */ GSL_ERROR ("System is underdetermined", GSL_EINVAL); } else if (A->size2 != x->size) { GSL_ERROR ("matrix and vector sizes must be equal", GSL_EBADLEN); } else { const size_t N = A->size1; const size_t M = A->size2; size_t i, j, k; REAL *d = (REAL *) malloc (N * sizeof (REAL)); if (d == 0) { GSL_ERROR ("could not allocate memory for workspace", GSL_ENOMEM); } /* Perform Householder transformation. */ for (i = 0; i < N; i++) { const REAL aii = gsl_matrix_get (A, i, i); REAL alpha; REAL f; REAL ak; REAL max_norm = 0.0; REAL r = 0.0; for (k = i; k < M; k++) { REAL aki = gsl_matrix_get (A, k, i); r += aki * aki; } if (r == 0.0) { /* Rank of matrix is less than size1. */ free (d); GSL_ERROR ("matrix is rank deficient", GSL_ESING); } alpha = sqrt (r) * GSL_SIGN (aii); ak = 1.0 / (r + alpha * aii); gsl_matrix_set (A, i, i, aii + alpha); d[i] = -alpha; for (k = i + 1; k < N; k++) { REAL norm = 0.0; f = 0.0; for (j = i; j < M; j++) { REAL ajk = gsl_matrix_get (A, j, k); REAL aji = gsl_matrix_get (A, j, i); norm += ajk * ajk; f += ajk * aji; } max_norm = GSL_MAX (max_norm, norm); f *= ak; for (j = i; j < M; j++) { REAL ajk = gsl_matrix_get (A, j, k); REAL aji = gsl_matrix_get (A, j, i); gsl_matrix_set (A, j, k, ajk - f * aji); } } if (fabs (alpha) < 2.0 * GSL_DBL_EPSILON * sqrt (max_norm)) { /* Apparent singularity. */ free (d); GSL_ERROR("apparent singularity detected", GSL_ESING); } /* Perform update of RHS. */ f = 0.0; for (j = i; j < M; j++) { f += gsl_vector_get (x, j) * gsl_matrix_get (A, j, i); } f *= ak; for (j = i; j < M; j++) { REAL xj = gsl_vector_get (x, j); REAL aji = gsl_matrix_get (A, j, i); gsl_vector_set (x, j, xj - f * aji); } } /* Perform back-substitution. */ for (i = N; i > 0 && i--;) { REAL xi = gsl_vector_get (x, i); REAL sum = 0.0; for (k = i + 1; k < N; k++) { sum += gsl_matrix_get (A, i, k) * gsl_vector_get (x, k); } gsl_vector_set (x, i, (xi - sum) / d[i]); } free (d); return GSL_SUCCESS; } } sources_5316/external/gsl/gsl_vector_long.h0000664000176700017670000001566311705263724017715 0ustar paulpaul/* vector/gsl_vector_long.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_LONG_H__ #define __GSL_VECTOR_LONG_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_long.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; long *data; gsl_block_long *block; int owner; } gsl_vector_long; typedef struct { gsl_vector_long vector; } _gsl_vector_long_view; typedef _gsl_vector_long_view gsl_vector_long_view; typedef struct { gsl_vector_long vector; } _gsl_vector_long_const_view; typedef const _gsl_vector_long_const_view gsl_vector_long_const_view; /* Allocation */ gsl_vector_long *gsl_vector_long_alloc (const size_t n); gsl_vector_long *gsl_vector_long_calloc (const size_t n); gsl_vector_long *gsl_vector_long_alloc_from_block (gsl_block_long * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_long *gsl_vector_long_alloc_from_vector (gsl_vector_long * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_long_free (gsl_vector_long * v); /* Views */ _gsl_vector_long_view gsl_vector_long_view_array (long *v, size_t n); _gsl_vector_long_view gsl_vector_long_view_array_with_stride (long *base, size_t stride, size_t n); _gsl_vector_long_const_view gsl_vector_long_const_view_array (const long *v, size_t n); _gsl_vector_long_const_view gsl_vector_long_const_view_array_with_stride (const long *base, size_t stride, size_t n); _gsl_vector_long_view gsl_vector_long_subvector (gsl_vector_long *v, size_t i, size_t n); _gsl_vector_long_view gsl_vector_long_subvector_with_stride (gsl_vector_long *v, size_t i, size_t stride, size_t n); _gsl_vector_long_const_view gsl_vector_long_const_subvector (const gsl_vector_long *v, size_t i, size_t n); _gsl_vector_long_const_view gsl_vector_long_const_subvector_with_stride (const gsl_vector_long *v, size_t i, size_t stride, size_t n); /* Operations */ long gsl_vector_long_get (const gsl_vector_long * v, const size_t i); void gsl_vector_long_set (gsl_vector_long * v, const size_t i, long x); long *gsl_vector_long_ptr (gsl_vector_long * v, const size_t i); const long *gsl_vector_long_const_ptr (const gsl_vector_long * v, const size_t i); void gsl_vector_long_set_zero (gsl_vector_long * v); void gsl_vector_long_set_all (gsl_vector_long * v, long x); int gsl_vector_long_set_basis (gsl_vector_long * v, size_t i); int gsl_vector_long_fread (FILE * stream, gsl_vector_long * v); int gsl_vector_long_fwrite (FILE * stream, const gsl_vector_long * v); int gsl_vector_long_fscanf (FILE * stream, gsl_vector_long * v); int gsl_vector_long_fprintf (FILE * stream, const gsl_vector_long * v, const char *format); int gsl_vector_long_memcpy (gsl_vector_long * dest, const gsl_vector_long * src); int gsl_vector_long_reverse (gsl_vector_long * v); int gsl_vector_long_swap (gsl_vector_long * v, gsl_vector_long * w); int gsl_vector_long_swap_elements (gsl_vector_long * v, const size_t i, const size_t j); long gsl_vector_long_max (const gsl_vector_long * v); long gsl_vector_long_min (const gsl_vector_long * v); void gsl_vector_long_minmax (const gsl_vector_long * v, long * min_out, long * max_out); size_t gsl_vector_long_max_index (const gsl_vector_long * v); size_t gsl_vector_long_min_index (const gsl_vector_long * v); void gsl_vector_long_minmax_index (const gsl_vector_long * v, size_t * imin, size_t * imax); int gsl_vector_long_add (gsl_vector_long * a, const gsl_vector_long * b); int gsl_vector_long_sub (gsl_vector_long * a, const gsl_vector_long * b); int gsl_vector_long_mul (gsl_vector_long * a, const gsl_vector_long * b); int gsl_vector_long_div (gsl_vector_long * a, const gsl_vector_long * b); int gsl_vector_long_scale (gsl_vector_long * a, const double x); int gsl_vector_long_add_constant (gsl_vector_long * a, const double x); int gsl_vector_long_isnull (const gsl_vector_long * v); int gsl_vector_long_ispos (const gsl_vector_long * v); int gsl_vector_long_isneg (const gsl_vector_long * v); int gsl_vector_long_isnonneg (const gsl_vector_long * v); #ifdef HAVE_INLINE extern inline long gsl_vector_long_get (const gsl_vector_long * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_long_set (gsl_vector_long * v, const size_t i, long x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline long * gsl_vector_long_ptr (gsl_vector_long * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (long *) (v->data + i * v->stride); } extern inline const long * gsl_vector_long_const_ptr (const gsl_vector_long * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const long *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_LONG_H__ */ sources_5316/external/gsl/gsl_cblas__zgemv.c0000664000176700017670000000064511723710247020011 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zgemv (const enum CBLAS_ORDER order, const enum CBLAS_TRANSPOSE TransA, const int M, const int N, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE double #include "gsl_cblas__source_gemv_c.h" #undef BASE } sources_5316/external/gsl/gsl_rng__slatec.c0000664000176700017670000001662011723710247017636 0ustar paulpaul/* rng/slatec.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /** * ====================================================================== * NIST Guide to Available Math Software. * Source for module RAND from package CMLIB. * Retrieved from TIBER on Fri Oct 11 11:43:42 1996. * ====================================================================== FUNCTION RAND(R) C***BEGIN PROLOGUE RAND C***DATE WRITTEN 770401 (YYMMDD) C***REVISION DATE 820801 (YYMMDD) C***CATEGORY NO. L6A21 C***KEYWORDS RANDOM NUMBER,SPECIAL FUNCTION,UNIFORM C***AUTHOR FULLERTON, W., (LANL) C***PURPOSE Generates a uniformly distributed random number. C***DESCRIPTION C C This pseudo-random number generator is portable among a wide C variety of computers. RAND(R) undoubtedly is not as good as many C readily available installation dependent versions, and so this C routine is not recommended for widespread usage. Its redeeming C feature is that the exact same random numbers (to within final round- C off error) can be generated from machine to machine. Thus, programs C that make use of random numbers can be easily transported to and C checked in a new environment. C The random numbers are generated by the linear congruential C method described, e.g., by Knuth in Seminumerical Methods (p.9), C Addison-Wesley, 1969. Given the I-th number of a pseudo-random C sequence, the I+1 -st number is generated from C X(I+1) = (A*X(I) + C) MOD M, C where here M = 2**22 = 4194304, C = 1731 and several suitable values C of the multiplier A are discussed below. Both the multiplier A and C random number X are represented in double precision as two 11-bit C words. The constants are chosen so that the period is the maximum C possible, 4194304. C In order that the same numbers be generated from machine to C machine, it is necessary that 23-bit integers be reducible modulo C 2**11 exactly, that 23-bit integers be added exactly, and that 11-bit C integers be multiplied exactly. Furthermore, if the restart option C is used (where R is between 0 and 1), then the product R*2**22 = C R*4194304 must be correct to the nearest integer. C The first four random numbers should be .0004127026, C .6750836372, .1614754200, and .9086198807. The tenth random number C is .5527787209, and the hundredth is .3600893021 . The thousandth C number should be .2176990509 . C In order to generate several effectively independent sequences C with the same generator, it is necessary to know the random number C for several widely spaced calls. The I-th random number times 2**22, C where I=K*P/8 and P is the period of the sequence (P = 2**22), is C still of the form L*P/8. In particular we find the I-th random C number multiplied by 2**22 is given by C I = 0 1*P/8 2*P/8 3*P/8 4*P/8 5*P/8 6*P/8 7*P/8 8*P/8 C RAND= 0 5*P/8 2*P/8 7*P/8 4*P/8 1*P/8 6*P/8 3*P/8 0 C Thus the 4*P/8 = 2097152 random number is 2097152/2**22. C Several multipliers have been subjected to the spectral test C (see Knuth, p. 82). Four suitable multipliers roughly in order of C goodness according to the spectral test are C 3146757 = 1536*2048 + 1029 = 2**21 + 2**20 + 2**10 + 5 C 2098181 = 1024*2048 + 1029 = 2**21 + 2**10 + 5 C 3146245 = 1536*2048 + 517 = 2**21 + 2**20 + 2**9 + 5 C 2776669 = 1355*2048 + 1629 = 5**9 + 7**7 + 1 C C In the table below LOG10(NU(I)) gives roughly the number of C random decimal digits in the random numbers considered I at a time. C C is the primary measure of goodness. In both cases bigger is better. C C LOG10 NU(I) C(I) C A I=2 I=3 I=4 I=5 I=2 I=3 I=4 I=5 C C 3146757 3.3 2.0 1.6 1.3 3.1 1.3 4.6 2.6 C 2098181 3.3 2.0 1.6 1.2 3.2 1.3 4.6 1.7 C 3146245 3.3 2.2 1.5 1.1 3.2 4.2 1.1 0.4 C 2776669 3.3 2.1 1.6 1.3 2.5 2.0 1.9 2.6 C Best C Possible 3.3 2.3 1.7 1.4 3.6 5.9 9.7 14.9 C C Input Argument -- C R If R=0., the next random number of the sequence is generated. C If R .LT. 0., the last generated number will be returned for C possible use in a restart procedure. C If R .GT. 0., the sequence of random numbers will start with C the seed R mod 1. This seed is also returned as the value of C RAND provided the arithmetic is done exactly. C C Output Value -- C RAND a pseudo-random number between 0. and 1. C***REFERENCES (NONE) C***ROUTINES CALLED (NONE) C***END PROLOGUE RAND DATA IA1, IA0, IA1MA0 /1536, 1029, 507/ DATA IC /1731/ DATA IX1, IX0 /0, 0/ C***FIRST EXECUTABLE STATEMENT RAND IF (R.LT.0.) GO TO 10 IF (R.GT.0.) GO TO 20 C C A*X = 2**22*IA1*IX1 + 2**11*(IA1*IX1 + (IA1-IA0)*(IX0-IX1) C + IA0*IX0) + IA0*IX0 C IY0 = IA0*IX0 IY1 = IA1*IX1 + IA1MA0*(IX0-IX1) + IY0 IY0 = IY0 + IC IX0 = MOD (IY0, 2048) IY1 = IY1 + (IY0-IX0)/2048 IX1 = MOD (IY1, 2048) C 10 RAND = IX1*2048 + IX0 RAND = RAND / 4194304. RETURN C 20 IX1 = AMOD(R,1.)*4194304. + 0.5 IX0 = MOD (IX1, 2048) IX1 = (IX1-IX0)/2048 GO TO 10 C END **/ #include "gsl__config.h" #include #include "gsl_rng.h" static inline unsigned long int slatec_get (void *vstate); static double slatec_get_double (void *vstate); static void slatec_set (void *state, unsigned long int s); typedef struct { long int x0, x1; } slatec_state_t; static const long P = 4194304; static const long a1 = 1536; static const long a0 = 1029; static const long a1ma0 = 507; static const long c = 1731; static inline unsigned long int slatec_get (void *vstate) { long y0, y1; slatec_state_t *state = (slatec_state_t *) vstate; y0 = a0 * state->x0; y1 = a1 * state->x1 + a1ma0 * (state->x0 - state->x1) + y0; y0 = y0 + c; state->x0 = y0 % 2048; y1 = y1 + (y0 - state->x0) / 2048; state->x1 = y1 % 2048; return state->x1 * 2048 + state->x0; } static double slatec_get_double (void *vstate) { return slatec_get (vstate) / 4194304.0 ; } static void slatec_set (void *vstate, unsigned long int s) { slatec_state_t *state = (slatec_state_t *) vstate; /* Only eight seeds are permitted. This is pretty limiting, but at least we are guaranteed that the eight sequences are different */ s = s % 8; s *= P / 8; state->x0 = s % 2048; state->x1 = (s - state->x0) / 2048; } static const gsl_rng_type slatec_type = {"slatec", /* name */ 4194303, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (slatec_state_t), &slatec_set, &slatec_get, &slatec_get_double}; const gsl_rng_type *gsl_rng_slatec = &slatec_type; sources_5316/external/gsl/gsl_ode-initval__rk2imp.c0000664000176700017670000001620211723710247021210 0ustar paulpaul/* ode-initval/rk2imp.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Runge-Kutta 2, Gaussian implicit. Also known as the implicit midpoint rule. */ /* Author: G. Jungman */ /* Error estimation by step doubling, see eg. Ascher, U.M., Petzold, L.R., Computer methods for ordinary differential and differential-algebraic equations, SIAM, Philadelphia, 1998. The method is also described in eg. this reference. */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_odeiv.h" #include "gsl_ode-initval__odeiv_util.h" typedef struct { double *Y1; double *y0; double *ytmp; double *y_onestep; double *y0_orig; } rk2imp_state_t; static void * rk2imp_alloc (size_t dim) { rk2imp_state_t *state = (rk2imp_state_t *) malloc (sizeof (rk2imp_state_t)); if (state == 0) { GSL_ERROR_NULL ("failed to allocate space for rk2imp_state", GSL_ENOMEM); } state->Y1 = (double *) malloc (dim * sizeof (double)); if (state->Y1 == 0) { free (state); GSL_ERROR_NULL ("failed to allocate space for Y1", GSL_ENOMEM); } state->ytmp = (double *) malloc (dim * sizeof (double)); if (state->ytmp == 0) { free (state->Y1); free (state); GSL_ERROR_NULL ("failed to allocate space for ytmp", GSL_ENOMEM); } state->y0 = (double *) malloc (dim * sizeof (double)); if (state->y0 == 0) { free (state->Y1); free (state->ytmp); free (state); GSL_ERROR_NULL ("failed to allocate space for y0", GSL_ENOMEM); } state->y_onestep = (double *) malloc (dim * sizeof (double)); if (state->y_onestep == 0) { free (state->Y1); free (state->ytmp); free (state->y0); free (state); GSL_ERROR_NULL ("failed to allocate space for y_onestep", GSL_ENOMEM); } state->y0_orig = (double *) malloc (dim * sizeof (double)); if (state->y0_orig == 0) { free (state->y_onestep); free (state->Y1); free (state->ytmp); free (state->y0); free (state); GSL_ERROR_NULL ("failed to allocate space for y0_orig", GSL_ENOMEM); } return state; } static int rk2imp_step (double *y, rk2imp_state_t *state, const double h, const double t, const size_t dim, const gsl_odeiv_system *sys) { /* Makes a Runge-Kutta 2nd order implicit advance with step size h. y0 is initial values of variables y. The implicit matrix equations to solve are: Y1 = y0 + h/2 * f(t + h/2, Y1) y = y0 + h * f(t + h/2, Y1) */ const double *y0 = state->y0; double *Y1 = state->Y1; double *ytmp = state->ytmp; int max_iter=3; int nu; size_t i; /* iterative solution of Y1 = y0 + h/2 * f(t + h/2, Y1) Y1 should include initial values at call. Note: This method does not check for convergence of the iterative solution! */ for (nu = 0; nu < max_iter; nu++) { for (i = 0; i < dim; i++) { ytmp[i] = y0[i] + 0.5 * h * Y1[i]; } { int s = GSL_ODEIV_FN_EVAL (sys, t + 0.5 * h, ytmp, Y1); if (s != GSL_SUCCESS) { return s; } } } /* assignment */ for (i = 0; i < dim; i++) { y[i] = y0[i] + h * Y1[i]; } return GSL_SUCCESS; } static int rk2imp_apply (void *vstate, size_t dim, double t, double h, double y[], double yerr[], const double dydt_in[], double dydt_out[], const gsl_odeiv_system * sys) { rk2imp_state_t *state = (rk2imp_state_t *) vstate; size_t i; double *Y1 = state->Y1; double *y0 = state->y0; double *y_onestep = state->y_onestep; double *y0_orig = state->y0_orig; /* Error estimation is done by step doubling procedure */ /* initialization step */ DBL_MEMCPY (y0, y, dim); /* Save initial values for possible failures */ DBL_MEMCPY (y0_orig, y, dim); if (dydt_in != NULL) { DBL_MEMCPY (Y1, dydt_in, dim); } else { int s = GSL_ODEIV_FN_EVAL (sys, t, y, Y1); if (s != GSL_SUCCESS) { return s; } } /* First traverse h with one step (save to y_onestep) */ DBL_MEMCPY (y_onestep, y, dim); { int s = rk2imp_step (y_onestep, state, h, t, dim, sys); if (s != GSL_SUCCESS) { return s; } } /* Then with two steps with half step length (save to y) */ { int s = rk2imp_step (y, state, h / 2.0, t, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } DBL_MEMCPY (y0, y, dim); { int s = GSL_ODEIV_FN_EVAL (sys, t + h / 2.0, y, Y1); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } { int s = rk2imp_step (y, state, h / 2.0, t + h / 2.0, dim, sys); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } /* Derivatives at output */ if (dydt_out != NULL) { int s = GSL_ODEIV_FN_EVAL (sys, t + h, y, dydt_out); if (s != GSL_SUCCESS) { /* Restore original y vector */ DBL_MEMCPY (y, y0_orig, dim); return s; } } /* Error estimation */ for (i = 0; i < dim; i++) { yerr[i] = 4.0 * (y[i] - y_onestep[i]) / 3.0; } return GSL_SUCCESS; } static int rk2imp_reset (void *vstate, size_t dim) { rk2imp_state_t *state = (rk2imp_state_t *) vstate; DBL_ZERO_MEMSET (state->Y1, dim); DBL_ZERO_MEMSET (state->ytmp, dim); DBL_ZERO_MEMSET (state->y0, dim); DBL_ZERO_MEMSET (state->y_onestep, dim); DBL_ZERO_MEMSET (state->y0_orig, dim); return GSL_SUCCESS; } static unsigned int rk2imp_order (void *vstate) { rk2imp_state_t *state = (rk2imp_state_t *) vstate; state = 0; /* prevent warnings about unused parameters */ return 2; } static void rk2imp_free (void *vstate) { rk2imp_state_t *state = (rk2imp_state_t *) vstate; free (state->Y1); free (state->ytmp); free (state->y0); free (state->y_onestep); free (state->y0_orig); free (state); } static const gsl_odeiv_step_type rk2imp_type = { "rk2imp", /* name */ 1, /* can use dydt_in */ 1, /* gives exact dydt_out */ &rk2imp_alloc, &rk2imp_apply, &rk2imp_reset, &rk2imp_order, &rk2imp_free }; const gsl_odeiv_step_type *gsl_odeiv_step_rk2imp = &rk2imp_type; sources_5316/external/gsl/gsl_vector__vector.c0000664000176700017670000000547511723710247020407 0ustar paulpaul/* vector/vector.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_vector.h" /* turn off range checking at runtime if zero */ int gsl_check_range = 1; #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_vector__vector_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_statistics.h0000664000176700017670000000073311705263724017556 0ustar paulpaul#ifndef __GSL_STATISTICS_H__ #define __GSL_STATISTICS_H__ #include "gsl_statistics_long_double.h" #include "gsl_statistics_double.h" #include "gsl_statistics_float.h" #include "gsl_statistics_ulong.h" #include "gsl_statistics_long.h" #include "gsl_statistics_uint.h" #include "gsl_statistics_int.h" #include "gsl_statistics_ushort.h" #include "gsl_statistics_short.h" #include "gsl_statistics_uchar.h" #include "gsl_statistics_char.h" #endif /* __GSL_STATISTICS_H__ */ sources_5316/external/gsl/gsl_multifit_nlin.h0000664000176700017670000001277011705263724020245 0ustar paulpaul/* multifit_nlin/gsl_multifit_nlin.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_MULTIFIT_NLIN_H__ #define __GSL_MULTIFIT_NLIN_H__ #include #include "gsl_types.h" #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_multifit_gradient (const gsl_matrix * J, const gsl_vector * f, gsl_vector * g); int gsl_multifit_covar (const gsl_matrix * J, double epsrel, gsl_matrix * covar); /* Definition of vector-valued functions with parameters based on gsl_vector */ struct gsl_multifit_function_struct { int (* f) (const gsl_vector * x, void * params, gsl_vector * f); size_t n; /* number of functions */ size_t p; /* number of independent variables */ void * params; }; typedef struct gsl_multifit_function_struct gsl_multifit_function ; #define GSL_MULTIFIT_FN_EVAL(F,x,y) (*((F)->f))(x,(F)->params,(y)) typedef struct { const char *name; size_t size; int (*alloc) (void *state, size_t n, size_t p); int (*set) (void *state, gsl_multifit_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx); int (*iterate) (void *state, gsl_multifit_function * function, gsl_vector * x, gsl_vector * f, gsl_vector * dx); void (*free) (void *state); } gsl_multifit_fsolver_type; typedef struct { const gsl_multifit_fsolver_type * type; gsl_multifit_function * function ; gsl_vector * x ; gsl_vector * f ; gsl_vector * dx ; void *state; } gsl_multifit_fsolver; gsl_multifit_fsolver * gsl_multifit_fsolver_alloc (const gsl_multifit_fsolver_type * T, size_t n, size_t p); void gsl_multifit_fsolver_free (gsl_multifit_fsolver * s); int gsl_multifit_fsolver_set (gsl_multifit_fsolver * s, gsl_multifit_function * f, const gsl_vector * x); int gsl_multifit_fsolver_iterate (gsl_multifit_fsolver * s); const char * gsl_multifit_fsolver_name (const gsl_multifit_fsolver * s); gsl_vector * gsl_multifit_fsolver_position (const gsl_multifit_fsolver * s); /* Definition of vector-valued functions and gradient with parameters based on gsl_vector */ struct gsl_multifit_function_fdf_struct { int (* f) (const gsl_vector * x, void * params, gsl_vector * f); int (* df) (const gsl_vector * x, void * params, gsl_matrix * df); int (* fdf) (const gsl_vector * x, void * params, gsl_vector * f, gsl_matrix *df); size_t n; /* number of functions */ size_t p; /* number of independent variables */ void * params; }; typedef struct gsl_multifit_function_fdf_struct gsl_multifit_function_fdf ; #define GSL_MULTIFIT_FN_EVAL_F(F,x,y) ((*((F)->f))(x,(F)->params,(y))) #define GSL_MULTIFIT_FN_EVAL_DF(F,x,dy) ((*((F)->df))(x,(F)->params,(dy))) #define GSL_MULTIFIT_FN_EVAL_F_DF(F,x,y,dy) ((*((F)->fdf))(x,(F)->params,(y),(dy))) typedef struct { const char *name; size_t size; int (*alloc) (void *state, size_t n, size_t p); int (*set) (void *state, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); int (*iterate) (void *state, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); void (*free) (void *state); } gsl_multifit_fdfsolver_type; typedef struct { const gsl_multifit_fdfsolver_type * type; gsl_multifit_function_fdf * fdf ; gsl_vector * x; gsl_vector * f; gsl_matrix * J; gsl_vector * dx; void *state; } gsl_multifit_fdfsolver; gsl_multifit_fdfsolver * gsl_multifit_fdfsolver_alloc (const gsl_multifit_fdfsolver_type * T, size_t n, size_t p); int gsl_multifit_fdfsolver_set (gsl_multifit_fdfsolver * s, gsl_multifit_function_fdf * fdf, const gsl_vector * x); int gsl_multifit_fdfsolver_iterate (gsl_multifit_fdfsolver * s); void gsl_multifit_fdfsolver_free (gsl_multifit_fdfsolver * s); const char * gsl_multifit_fdfsolver_name (const gsl_multifit_fdfsolver * s); gsl_vector * gsl_multifit_fdfsolver_position (const gsl_multifit_fdfsolver * s); int gsl_multifit_test_delta (const gsl_vector * dx, const gsl_vector * x, double epsabs, double epsrel); int gsl_multifit_test_gradient (const gsl_vector * g, double epsabs); /* extern const gsl_multifit_fsolver_type * gsl_multifit_fsolver_gradient; */ GSL_VAR const gsl_multifit_fdfsolver_type * gsl_multifit_fdfsolver_lmder; GSL_VAR const gsl_multifit_fdfsolver_type * gsl_multifit_fdfsolver_lmsder; __END_DECLS #endif /* __GSL_MULTIFIT_NLIN_H__ */ sources_5316/external/gsl/gsl_histogram__file2d.c0000664000176700017670000001063511723710247020737 0ustar paulpaul/* histogram/file2d.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_block.h" #include "gsl_histogram2d.h" int gsl_histogram2d_fread (FILE * stream, gsl_histogram2d * h) { int status = gsl_block_raw_fread (stream, h->xrange, h->nx + 1, 1); if (status) return status; status = gsl_block_raw_fread (stream, h->yrange, h->ny + 1, 1); if (status) return status; status = gsl_block_raw_fread (stream, h->bin, h->nx * h->ny, 1); return status; } int gsl_histogram2d_fwrite (FILE * stream, const gsl_histogram2d * h) { int status = gsl_block_raw_fwrite (stream, h->xrange, h->nx + 1, 1); if (status) return status; status = gsl_block_raw_fwrite (stream, h->yrange, h->ny + 1, 1); if (status) return status; status = gsl_block_raw_fwrite (stream, h->bin, h->nx * h->ny, 1); return status; } int gsl_histogram2d_fprintf (FILE * stream, const gsl_histogram2d * h, const char *range_format, const char *bin_format) { size_t i, j; const size_t nx = h->nx; const size_t ny = h->ny; int status; for (i = 0; i < nx; i++) { for (j = 0; j < ny; j++) { status = fprintf (stream, range_format, h->xrange[i]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } status = putc (' ', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } status = fprintf (stream, range_format, h->xrange[i + 1]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } status = putc (' ', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } status = fprintf (stream, range_format, h->yrange[j]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } status = putc (' ', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } status = fprintf (stream, range_format, h->yrange[j + 1]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } status = putc (' ', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } status = fprintf (stream, bin_format, h->bin[i * ny + j]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } status = putc ('\n', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } } status = putc ('\n', stream); if (status == EOF) { GSL_ERROR ("putc failed", GSL_EFAILED); } } return GSL_SUCCESS; } int gsl_histogram2d_fscanf (FILE * stream, gsl_histogram2d * h) { size_t i, j; const size_t nx = h->nx; const size_t ny = h->ny; double xupper, yupper; for (i = 0; i < nx; i++) { for (j = 0; j < ny; j++) { int status = fscanf (stream, "%lg %lg %lg %lg %lg", h->xrange + i, &xupper, h->yrange + j, &yupper, h->bin + i * ny + j); if (status != 5) { GSL_ERROR ("fscanf failed", GSL_EFAILED); } } h->yrange[ny] = yupper; } h->xrange[nx] = xupper; return GSL_SUCCESS; } sources_5316/external/gsl/gsl_sf__cheb_eval.c0000644000176700017670000000122010707442037020101 0ustar paulpaul static inline int cheb_eval_e(const cheb_series * cs, const double x, gsl_sf_result * result) { int j; double d = 0.0; double dd = 0.0; double y = (2.0*x - cs->a - cs->b) / (cs->b - cs->a); double y2 = 2.0 * y; double e = 0.0; for(j = cs->order; j>=1; j--) { double temp = d; d = y2*d - dd + cs->c[j]; e += fabs(y2*temp) + fabs(dd) + fabs(cs->c[j]); dd = temp; } { double temp = d; d = y*d - dd + 0.5 * cs->c[0]; e += fabs(y*temp) + fabs(dd) + 0.5 * fabs(cs->c[0]); } result->val = d; result->err = GSL_DBL_EPSILON * e + fabs(cs->c[cs->order]); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_sf__bessel_Kn.c0000644000176700017670000001470710707442037020114 0ustar paulpaul/* specfunc/bessel_Kn.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_gamma.h" #include "gsl_sf_psi.h" #include "gsl_sf_bessel.h" #include "gsl_sf__error.h" #include "gsl_sf__bessel.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* [Abramowitz+Stegun, 9.6.11] * assumes n >= 1 */ static int bessel_Kn_scaled_small_x(const int n, const double x, gsl_sf_result * result) { int k; double y = 0.25 * x * x; double ln_x_2 = log(0.5*x); double ex = exp(x); gsl_sf_result ln_nm1_fact; double k_term; double term1, sum1, ln_pre1; double term2, sum2, pre2; gsl_sf_lnfact_e((unsigned int)(n-1), &ln_nm1_fact); ln_pre1 = -n*ln_x_2 + ln_nm1_fact.val; if(ln_pre1 > GSL_LOG_DBL_MAX - 3.0) GSL_ERROR ("error", GSL_EOVRFLW); sum1 = 1.0; k_term = 1.0; for(k=1; k<=n-1; k++) { k_term *= -y/(k * (n-k)); sum1 += k_term; } term1 = 0.5 * exp(ln_pre1) * sum1; pre2 = 0.5 * exp(n*ln_x_2); if(pre2 > 0.0) { const int KMAX = 20; gsl_sf_result psi_n; gsl_sf_result npk_fact; double yk = 1.0; double k_fact = 1.0; double psi_kp1 = -M_EULER; double psi_npkp1; gsl_sf_psi_int_e(n, &psi_n); gsl_sf_fact_e((unsigned int)n, &npk_fact); psi_npkp1 = psi_n.val + 1.0/n; sum2 = (psi_kp1 + psi_npkp1 - 2.0*ln_x_2)/npk_fact.val; for(k=1; kval = ex * (term1 + term2); result->err = ex * GSL_DBL_EPSILON * (fabs(ln_pre1)*fabs(term1) + fabs(term2)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_bessel_Kn_scaled_e(int n, const double x, gsl_sf_result * result) { n = abs(n); /* K(-n, z) = K(n, z) */ /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else if(n == 0) { return gsl_sf_bessel_K0_scaled_e(x, result); } else if(n == 1) { return gsl_sf_bessel_K1_scaled_e(x, result); } else if(x <= 5.0) { return bessel_Kn_scaled_small_x(n, x, result); } else if(GSL_ROOT3_DBL_EPSILON * x > 0.25 * (n*n + 1)) { return gsl_sf_bessel_Knu_scaled_asympx_e((double)n, x, result); } else if(GSL_MIN(0.29/(n*n), 0.5/(n*n + x*x)) < GSL_ROOT3_DBL_EPSILON) { return gsl_sf_bessel_Knu_scaled_asymp_unif_e((double)n, x, result); } else { /* Upward recurrence. [Gradshteyn + Ryzhik, 8.471.1] */ double two_over_x = 2.0/x; gsl_sf_result r_b_jm1; gsl_sf_result r_b_j; int stat_0 = gsl_sf_bessel_K0_scaled_e(x, &r_b_jm1); int stat_1 = gsl_sf_bessel_K1_scaled_e(x, &r_b_j); double b_jm1 = r_b_jm1.val; double b_j = r_b_j.val; double b_jp1; int j; for(j=1; jval = b_j; result->err = n * (fabs(b_j) * (fabs(r_b_jm1.err/r_b_jm1.val) + fabs(r_b_j.err/r_b_j.val))); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_2(stat_0, stat_1); } } int gsl_sf_bessel_Kn_e(const int n, const double x, gsl_sf_result * result) { const int status = gsl_sf_bessel_Kn_scaled_e(n, x, result); const double ex = exp(-x); result->val *= ex; result->err *= ex; result->err += x * GSL_DBL_EPSILON * fabs(result->val); return status; } int gsl_sf_bessel_Kn_scaled_array(const int nmin, const int nmax, const double x, double * result_array) { /* CHECK_POINTER(result_array) */ if(nmin < 0 || nmax < nmin || x <= 0.0) { int j; for(j=0; j<=nmax-nmin; j++) result_array[j] = 0.0; GSL_ERROR ("domain error", GSL_EDOM); } else if(nmax == 0) { gsl_sf_result b; int stat = gsl_sf_bessel_K0_scaled_e(x, &b); result_array[0] = b.val; return stat; } else { double two_over_x = 2.0/x; gsl_sf_result r_Knm1; gsl_sf_result r_Kn; int stat_0 = gsl_sf_bessel_Kn_scaled_e(nmin, x, &r_Knm1); int stat_1 = gsl_sf_bessel_Kn_scaled_e(nmin+1, x, &r_Kn); int stat = GSL_ERROR_SELECT_2(stat_0, stat_1); double Knp1; double Kn = r_Kn.val; double Knm1 = r_Knm1.val; int n; for(n=nmin+1; n<=nmax+1; n++) { if(Knm1 < GSL_DBL_MAX) { result_array[n-1-nmin] = Knm1; Knp1 = Knm1 + n * two_over_x * Kn; Knm1 = Kn; Kn = Knp1; } else { /* Overflow. Set the rest of the elements to * zero and bug out. * FIXME: Note: this relies on the convention * that the test x < DBL_MIN fails for x not * a number. This may be only an IEEE convention, * so the portability is unclear. */ int j; for(j=n; j<=nmax+1; j++) result_array[j-1-nmin] = 0.0; GSL_ERROR ("overflow", GSL_EOVRFLW); } } return stat; } } int gsl_sf_bessel_Kn_array(const int nmin, const int nmax, const double x, double * result_array) { int status = gsl_sf_bessel_Kn_scaled_array(nmin, nmax, x, result_array); double ex = exp(-x); int i; for(i=0; i<=nmax-nmin; i++) result_array[i] *= ex; return status; } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_bessel_Kn_scaled(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_Kn_scaled_e(n, x, &result)); } double gsl_sf_bessel_Kn(const int n, const double x) { EVAL_RESULT(gsl_sf_bessel_Kn_e(n, x, &result)); } sources_5316/external/gsl/gsl_permute_vector_short.h0000664000176700017670000000266611705263724021655 0ustar paulpaul/* permutation/gsl_permute_vector_short.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_SHORT_H__ #define __GSL_PERMUTE_VECTOR_SHORT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_short.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_short (const gsl_permutation * p, gsl_vector_short * v); int gsl_permute_vector_short_inverse (const gsl_permutation * p, gsl_vector_short * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_SHORT_H__ */ sources_5316/external/gsl/gsl_permute_short.h0000664000176700017670000000262611705263724020267 0ustar paulpaul/* permutation/gsl_permute_short.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_SHORT_H__ #define __GSL_PERMUTE_SHORT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_short (const size_t * p, short * data, const size_t stride, const size_t n); int gsl_permute_short_inverse (const size_t * p, short * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_SHORT_H__ */ sources_5316/external/gsl/gsl_multiroots__newton.c0000664000176700017670000000715711723710247021335 0ustar paulpaul/* multiroots/newton.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_multiroots.h" #include "gsl_linalg.h" typedef struct { gsl_matrix * lu; gsl_permutation * permutation; } newton_state_t; static int newton_alloc (void * vstate, size_t n); static int newton_set (void * vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static int newton_iterate (void * vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx); static void newton_free (void * vstate); static int newton_alloc (void * vstate, size_t n) { newton_state_t * state = (newton_state_t *) vstate; gsl_permutation * p; gsl_matrix * m; m = gsl_matrix_calloc (n,n); if (m == 0) { GSL_ERROR ("failed to allocate space for lu", GSL_ENOMEM); } state->lu = m ; p = gsl_permutation_calloc (n); if (p == 0) { gsl_matrix_free(m); GSL_ERROR ("failed to allocate space for permutation", GSL_ENOMEM); } state->permutation = p ; return GSL_SUCCESS; } static int newton_set (void * vstate, gsl_multiroot_function_fdf * FDF, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { newton_state_t * state = (newton_state_t *) vstate; size_t i, n = FDF->n ; state = 0 ; /* avoid warnings about unused parameters */ GSL_MULTIROOT_FN_EVAL_F_DF (FDF, x, f, J); for (i = 0; i < n; i++) { gsl_vector_set (dx, i, 0.0); } return GSL_SUCCESS; } static int newton_iterate (void * vstate, gsl_multiroot_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx) { newton_state_t * state = (newton_state_t *) vstate; int signum; size_t i; size_t n = fdf->n ; gsl_matrix_memcpy (state->lu, J); gsl_linalg_LU_decomp (state->lu, state->permutation, &signum); gsl_linalg_LU_solve (state->lu, state->permutation, f, dx); for (i = 0; i < n; i++) { double e = gsl_vector_get (dx, i); double y = gsl_vector_get (x, i); gsl_vector_set (dx, i, -e); gsl_vector_set (x, i, y - e); } { int status = GSL_MULTIROOT_FN_EVAL_F_DF (fdf, x, f, J); if (status != GSL_SUCCESS) { return GSL_EBADFUNC; } } return GSL_SUCCESS; } static void newton_free (void * vstate) { newton_state_t * state = (newton_state_t *) vstate; gsl_matrix_free(state->lu); gsl_permutation_free(state->permutation); } static const gsl_multiroot_fdfsolver_type newton_type = {"newton", /* name */ sizeof (newton_state_t), &newton_alloc, &newton_set, &newton_iterate, &newton_free}; const gsl_multiroot_fdfsolver_type * gsl_multiroot_fdfsolver_newton = &newton_type; sources_5316/external/gsl/gsl_vector__view.h0000664000176700017670000000011711705263724020053 0ustar paulpaul#define NULL_VECTOR {0, 0, 0, 0, 0} #define NULL_VECTOR_VIEW {{0, 0, 0, 0, 0}} sources_5316/external/gsl/gsl_eigen__qrstep.c0000664000176700017670000000770711723710247020210 0ustar paulpaul/* eigen/qrstep.c * * Copyright (C) 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* remove off-diagonal elements which are neglegible compared with the neighboring diagonal elements */ static void chop_small_elements (const size_t N, const double d[], double sd[]) { double d_i = d[0]; size_t i; for (i = 0; i < N - 1; i++) { double sd_i = sd[i]; double d_ip1 = d[i + 1]; if (fabs (sd_i) < GSL_DBL_EPSILON * (fabs (d_i) + fabs (d_ip1))) { sd[i] = 0.0; } d_i = d_ip1; } } /* Generate a Givens rotation (cos,sin) which takes v=(x,y) to (|v|,0) From Golub and Van Loan, "Matrix Computations", Section 5.1.8 */ inline static void create_givens (const double a, const double b, double *c, double *s) { if (b == 0) { *c = 1; *s = 0; } else if (fabs (b) > fabs (a)) { double t = -a / b; double s1 = 1.0 / sqrt (1 + t * t); *s = s1; *c = s1 * t; } else { double t = -b / a; double c1 = 1.0 / sqrt (1 + t * t); *c = c1; *s = c1 * t; } } inline static double trailing_eigenvalue (const size_t n, const double d[], const double sd[]) { double ta = d[n - 2]; double tb = d[n - 1]; double tab = sd[n - 2]; double dt = (ta - tb) / 2.0; double mu; if (dt > 0) { mu = tb - tab * (tab / (dt + hypot (dt, tab))); } else if (dt == 0) { mu = tb - fabs(tab); } else { mu = tb + tab * (tab / ((-dt) + hypot (dt, tab))); } return mu; } static void qrstep (const size_t n, double d[], double sd[], double gc[], double gs[]) { double x, z; double ak, bk, zk, ap, bp, aq, bq; size_t k; double mu = trailing_eigenvalue (n, d, sd); x = d[0] - mu; z = sd[0]; ak = 0; bk = 0; zk = 0; ap = d[0]; bp = sd[0]; aq = d[1]; if (n == 2) { double c, s; create_givens (x, z, &c, &s); if (gc != NULL) gc[0] = c; if (gs != NULL) gs[0] = s; { double ap1 = c * (c * ap - s * bp) + s * (s * aq - c * bp); double bp1 = c * (s * ap + c * bp) - s * (s * bp + c * aq); double aq1 = s * (s * ap + c * bp) + c * (s * bp + c * aq); ak = ap1; bk = bp1; ap = aq1; } d[0] = ak; sd[0] = bk; d[1] = ap; return; } bq = sd[1]; for (k = 0; k < n - 1; k++) { double c, s; create_givens (x, z, &c, &s); /* store Givens rotation */ if (gc != NULL) gc[k] = c; if (gs != NULL) gs[k] = s; /* compute G' T G */ { double bk1 = c * bk - s * zk; double ap1 = c * (c * ap - s * bp) + s * (s * aq - c * bp); double bp1 = c * (s * ap + c * bp) - s * (s * bp + c * aq); double zp1 = -s * bq; double aq1 = s * (s * ap + c * bp) + c * (s * bp + c * aq); double bq1 = c * bq; ak = ap1; bk = bp1; zk = zp1; ap = aq1; bp = bq1; if (k < n - 2) aq = d[k + 2]; if (k < n - 3) bq = sd[k + 2]; d[k] = ak; if (k > 0) sd[k - 1] = bk1; if (k < n - 2) sd[k + 1] = bp; x = bk; z = zk; } } /* k = n - 1 */ d[k] = ap; sd[k - 1] = bk; } sources_5316/external/gsl/gsl_specfunc__ellint.c0000664000176700017670000004601011723710247020666 0ustar paulpaul/* specfunc/ellint.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_precision.h" #include "gsl_sf_ellint.h" #include "gsl_specfunc__error.h" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ inline static double locMAX3(double x, double y, double z) { double xy = GSL_MAX(x, y); return GSL_MAX(xy, z); } inline static double locMAX4(double x, double y, double z, double w) { double xy = GSL_MAX(x, y); double xyz = GSL_MAX(xy, z); return GSL_MAX(xyz, w); } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ /* based on Carlson's algorithms: [B. C. Carlson Numer. Math. 33, 1 (1979)] see also: [B.C. Carlson, Special Functions of Applied Mathematics (1977)] */ /* According to Carlson's algorithm, the errtol parameter typically effects the relative error in the following way: relative error < 16 errtol^6 / (1 - 2 errtol) errtol precision ------ ---------- 0.001 1.0e-17 0.003 2.0e-14 0.01 2.0e-11 0.03 2.0e-8 0.1 2.0e-5 */ int gsl_sf_ellint_RC_e(double x, double y, gsl_mode_t mode, gsl_sf_result * result) { const double lolim = 5.0 * GSL_DBL_MIN; const double uplim = 0.2 * GSL_DBL_MAX; const gsl_prec_t goal = GSL_MODE_PREC(mode); const double errtol = ( goal == GSL_PREC_DOUBLE ? 0.001 : 0.03 ); const double prec = gsl_prec_eps[goal]; if(x < 0.0 || y < 0.0 || x + y < lolim) { DOMAIN_ERROR(result); } else if(GSL_MAX(x, y) < uplim) { const double c1 = 1.0 / 7.0; const double c2 = 9.0 / 22.0; double xn = x; double yn = y; double mu, sn, lamda, s; while(1) { mu = (xn + yn + yn) / 3.0; sn = (yn + mu) / mu - 2.0; if (fabs(sn) < errtol) break; lamda = 2.0 * sqrt(xn) * sqrt(yn) + yn; xn = (xn + lamda) * 0.25; yn = (yn + lamda) * 0.25; } s = sn * sn * (0.3 + sn * (c1 + sn * (0.375 + sn * c2))); result->val = (1.0 + s) / sqrt(mu); result->err = prec * fabs(result->val); return GSL_SUCCESS; } else { DOMAIN_ERROR(result); } } int gsl_sf_ellint_RD_e(double x, double y, double z, gsl_mode_t mode, gsl_sf_result * result) { const gsl_prec_t goal = GSL_MODE_PREC(mode); const double errtol = ( goal == GSL_PREC_DOUBLE ? 0.001 : 0.03 ); const double prec = gsl_prec_eps[goal]; const double lolim = 2.0/pow(GSL_DBL_MAX, 2.0/3.0); const double uplim = pow(0.1*errtol/GSL_DBL_MIN, 2.0/3.0); if(GSL_MIN(x,y) < 0.0 || GSL_MIN(x+y,z) < lolim) { DOMAIN_ERROR(result); } else if(locMAX3(x,y,z) < uplim) { const double c1 = 3.0 / 14.0; const double c2 = 1.0 / 6.0; const double c3 = 9.0 / 22.0; const double c4 = 3.0 / 26.0; double xn = x; double yn = y; double zn = z; double sigma = 0.0; double power4 = 1.0; double ea, eb, ec, ed, ef, s1, s2; double mu, xndev, yndev, zndev; while(1) { double xnroot, ynroot, znroot, lamda; double epslon; mu = (xn + yn + 3.0 * zn) * 0.2; xndev = (mu - xn) / mu; yndev = (mu - yn) / mu; zndev = (mu - zn) / mu; epslon = locMAX3(fabs(xndev), fabs(yndev), fabs(zndev)); if (epslon < errtol) break; xnroot = sqrt(xn); ynroot = sqrt(yn); znroot = sqrt(zn); lamda = xnroot * (ynroot + znroot) + ynroot * znroot; sigma += power4 / (znroot * (zn + lamda)); power4 *= 0.25; xn = (xn + lamda) * 0.25; yn = (yn + lamda) * 0.25; zn = (zn + lamda) * 0.25; } ea = xndev * yndev; eb = zndev * zndev; ec = ea - eb; ed = ea - 6.0 * eb; ef = ed + ec + ec; s1 = ed * (- c1 + 0.25 * c3 * ed - 1.5 * c4 * zndev * ef); s2 = zndev * (c2 * ef + zndev * (- c3 * ec + zndev * c4 * ea)); result->val = 3.0 * sigma + power4 * (1.0 + s1 + s2) / (mu * sqrt(mu)); result->err = prec * fabs(result->val); return GSL_SUCCESS; } else { DOMAIN_ERROR(result); } } int gsl_sf_ellint_RF_e(double x, double y, double z, gsl_mode_t mode, gsl_sf_result * result) { const double lolim = 5.0 * GSL_DBL_MIN; const double uplim = 0.2 * GSL_DBL_MAX; const gsl_prec_t goal = GSL_MODE_PREC(mode); const double errtol = ( goal == GSL_PREC_DOUBLE ? 0.001 : 0.03 ); const double prec = gsl_prec_eps[goal]; if(x < 0.0 || y < 0.0 || z < 0.0) { DOMAIN_ERROR(result); } else if(x+y < lolim || x+z < lolim || y+z < lolim) { DOMAIN_ERROR(result); } else if(locMAX3(x,y,z) < uplim) { const double c1 = 1.0 / 24.0; const double c2 = 3.0 / 44.0; const double c3 = 1.0 / 14.0; double xn = x; double yn = y; double zn = z; double mu, xndev, yndev, zndev, e2, e3, s; while(1) { double epslon, lamda; double xnroot, ynroot, znroot; mu = (xn + yn + zn) / 3.0; xndev = 2.0 - (mu + xn) / mu; yndev = 2.0 - (mu + yn) / mu; zndev = 2.0 - (mu + zn) / mu; epslon = locMAX3(fabs(xndev), fabs(yndev), fabs(zndev)); if (epslon < errtol) break; xnroot = sqrt(xn); ynroot = sqrt(yn); znroot = sqrt(zn); lamda = xnroot * (ynroot + znroot) + ynroot * znroot; xn = (xn + lamda) * 0.25; yn = (yn + lamda) * 0.25; zn = (zn + lamda) * 0.25; } e2 = xndev * yndev - zndev * zndev; e3 = xndev * yndev * zndev; s = 1.0 + (c1 * e2 - 0.1 - c2 * e3) * e2 + c3 * e3; result->val = s / sqrt(mu); result->err = prec * fabs(result->val); return GSL_SUCCESS; } else { DOMAIN_ERROR(result); } } int gsl_sf_ellint_RJ_e(double x, double y, double z, double p, gsl_mode_t mode, gsl_sf_result * result) { const gsl_prec_t goal = GSL_MODE_PREC(mode); const double errtol = ( goal == GSL_PREC_DOUBLE ? 0.001 : 0.03 ); const double prec = gsl_prec_eps[goal]; const double lolim = pow(5.0 * GSL_DBL_MIN, 1.0/3.0); const double uplim = 0.3 * pow(0.2 * GSL_DBL_MAX, 1.0/3.0); if(x < 0.0 || y < 0.0 || z < 0.0) { DOMAIN_ERROR(result); } else if(x + y < lolim || x + z < lolim || y + z < lolim || p < lolim) { DOMAIN_ERROR(result); } else if(locMAX4(x,y,z,p) < uplim) { const double c1 = 3.0 / 14.0; const double c2 = 1.0 / 3.0; const double c3 = 3.0 / 22.0; const double c4 = 3.0 / 26.0; double xn = x; double yn = y; double zn = z; double pn = p; double sigma = 0.0; double power4 = 1.0; double mu, xndev, yndev, zndev, pndev; double ea, eb, ec, e2, e3, s1, s2, s3; while(1) { double xnroot, ynroot, znroot; double lamda, alfa, beta; double epslon; gsl_sf_result rcresult; int rcstatus; mu = (xn + yn + zn + pn + pn) * 0.2; xndev = (mu - xn) / mu; yndev = (mu - yn) / mu; zndev = (mu - zn) / mu; pndev = (mu - pn) / mu; epslon = locMAX4(fabs(xndev), fabs(yndev), fabs(zndev), fabs(pndev)); if(epslon < errtol) break; xnroot = sqrt(xn); ynroot = sqrt(yn); znroot = sqrt(zn); lamda = xnroot * (ynroot + znroot) + ynroot * znroot; alfa = pn * (xnroot + ynroot + znroot) + xnroot * ynroot * znroot; alfa = alfa * alfa; beta = pn * (pn + lamda) * (pn + lamda); rcstatus = gsl_sf_ellint_RC_e(alfa, beta, mode, &rcresult); if(rcstatus != GSL_SUCCESS) { result->val = 0.0; result->err = 0.0; return rcstatus; } sigma += power4 * rcresult.val; power4 *= 0.25; xn = (xn + lamda) * 0.25; yn = (yn + lamda) * 0.25; zn = (zn + lamda) * 0.25; pn = (pn + lamda) * 0.25; } ea = xndev * (yndev + zndev) + yndev * zndev; eb = xndev * yndev * zndev; ec = pndev * pndev; e2 = ea - 3.0 * ec; e3 = eb + 2.0 * pndev * (ea - ec); s1 = 1.0 + e2 * (- c1 + 0.75 * c3 * e2 - 1.5 * c4 * e3); s2 = eb * (0.5 * c2 + pndev * (- c3 - c3 + pndev * c4)); s3 = pndev * ea * (c2 - pndev * c3) - c2 * pndev * ec; result->val = 3.0 * sigma + power4 * (s1 + s2 + s3) / (mu * sqrt(mu)); result->err = prec * fabs(result->val); return GSL_SUCCESS; } else { DOMAIN_ERROR(result); } } /* [Carlson, Numer. Math. 33 (1979) 1, (4.1)] */ int gsl_sf_ellint_F_e(double phi, double k, gsl_mode_t mode, gsl_sf_result * result) { /* Angular reduction to -pi/2 < phi < pi/2 (we should really use an exact reduction but this will have to do for now) BJG */ double nc = floor(phi/M_PI + 0.5); double phi_red = phi - nc * M_PI; phi = phi_red; { double sin_phi = sin(phi); double sin2_phi = sin_phi*sin_phi; double x = 1.0 - sin2_phi; double y = 1.0 - k*k*sin2_phi; gsl_sf_result rf; int status = gsl_sf_ellint_RF_e(x, y, 1.0, mode, &rf); result->val = sin_phi * rf.val; result->err = GSL_DBL_EPSILON * fabs(result->val) + fabs(sin_phi*rf.err); if (nc == 0) { return status; } else { gsl_sf_result rk; /* add extra terms from periodicity */ const int rkstatus = gsl_sf_ellint_Kcomp_e(k, mode, &rk); result->val += 2*nc*rk.val; result->err += 2*fabs(nc)*rk.err; return GSL_ERROR_SELECT_2(status, rkstatus); } } } /* [Carlson, Numer. Math. 33 (1979) 1, (4.2)] */ int gsl_sf_ellint_E_e(double phi, double k, gsl_mode_t mode, gsl_sf_result * result) { /* Angular reduction to -pi/2 < phi < pi/2 (we should really use an exact reduction but this will have to do for now) BJG */ double nc = floor(phi/M_PI + 0.5); double phi_red = phi - nc * M_PI; phi = phi_red; { const double sin_phi = sin(phi); const double sin2_phi = sin_phi * sin_phi; const double x = 1.0 - sin2_phi; const double y = 1.0 - k*k*sin2_phi; if(x < GSL_DBL_EPSILON) { gsl_sf_result re; const int status = gsl_sf_ellint_Ecomp_e(k, mode, &re); /* could use A&S 17.4.14 to improve the value below */ result->val = 2*nc*re.val + GSL_SIGN(sin_phi) * re.val; result->err = 2*fabs(nc)*re.err + re.err; return status; } else { gsl_sf_result rf, rd; const double sin3_phi = sin2_phi * sin_phi; const int rfstatus = gsl_sf_ellint_RF_e(x, y, 1.0, mode, &rf); const int rdstatus = gsl_sf_ellint_RD_e(x, y, 1.0, mode, &rd); result->val = sin_phi * rf.val - k*k/3.0 * sin3_phi * rd.val; result->err = GSL_DBL_EPSILON * fabs(sin_phi * rf.val); result->err += fabs(sin_phi*rf.err); result->err += k*k/3.0 * GSL_DBL_EPSILON * fabs(sin3_phi * rd.val); result->err += k*k/3.0 * fabs(sin3_phi*rd.err); if (nc == 0) { return GSL_ERROR_SELECT_2(rfstatus, rdstatus); } else { gsl_sf_result re; /* add extra terms from periodicity */ const int restatus = gsl_sf_ellint_Ecomp_e(k, mode, &re); result->val += 2*nc*re.val; result->err += 2*fabs(nc)*re.err; return GSL_ERROR_SELECT_3(rfstatus, rdstatus, restatus); } } } } /* [Carlson, Numer. Math. 33 (1979) 1, (4.3)] */ int gsl_sf_ellint_P_e(double phi, double k, double n, gsl_mode_t mode, gsl_sf_result * result) { /* Angular reduction to -pi/2 < phi < pi/2 (we should really use an exact reduction but this will have to do for now) BJG */ double nc = floor(phi/M_PI + 0.5); double phi_red = phi - nc * M_PI; phi = phi_red; /* FIXME: need to handle the case of small x, as for E,F */ { const double sin_phi = sin(phi); const double sin2_phi = sin_phi * sin_phi; const double sin3_phi = sin2_phi * sin_phi; const double x = 1.0 - sin2_phi; const double y = 1.0 - k*k*sin2_phi; gsl_sf_result rf; gsl_sf_result rj; const int rfstatus = gsl_sf_ellint_RF_e(x, y, 1.0, mode, &rf); const int rjstatus = gsl_sf_ellint_RJ_e(x, y, 1.0, 1.0 + n*sin2_phi, mode, &rj); result->val = sin_phi * rf.val - n/3.0*sin3_phi * rj.val; result->err = GSL_DBL_EPSILON * fabs(sin_phi * rf.val); result->err += fabs(sin_phi * rf.err); result->err += n/3.0 * GSL_DBL_EPSILON * fabs(sin3_phi*rj.val); result->err += n/3.0 * fabs(sin3_phi*rj.err); if (nc == 0) { return GSL_ERROR_SELECT_2(rfstatus, rjstatus); } else { gsl_sf_result rp; /* add extra terms from periodicity */ const int rpstatus = gsl_sf_ellint_Pcomp_e(k, n, mode, &rp); result->val += 2*nc*rp.val; result->err += 2*fabs(nc)*rp.err; return GSL_ERROR_SELECT_3(rfstatus, rjstatus, rpstatus); } } } /* [Carlson, Numer. Math. 33 (1979) 1, (4.4)] */ int gsl_sf_ellint_D_e(double phi, double k, double n, gsl_mode_t mode, gsl_sf_result * result) { /* Angular reduction to -pi/2 < phi < pi/2 (we should really use an exact reduction but this will have to do for now) BJG */ double nc = floor(phi/M_PI + 0.5); double phi_red = phi - nc * M_PI; phi = phi_red; /* FIXME: need to handle the case of small x, as for E,F */ { const double sin_phi = sin(phi); const double sin2_phi = sin_phi * sin_phi; const double sin3_phi = sin2_phi * sin_phi; const double x = 1.0 - sin2_phi; const double y = 1.0 - k*k*sin2_phi; gsl_sf_result rd; const int status = gsl_sf_ellint_RD_e(x, y, 1.0, mode, &rd); result->val = sin3_phi/3.0 * rd.val; result->err = GSL_DBL_EPSILON * fabs(result->val) + fabs(sin3_phi/3.0 * rd.err); if (nc == 0) { return status; } else { gsl_sf_result rd; /* add extra terms from periodicity */ const int rdstatus = gsl_sf_ellint_Dcomp_e(k, mode, &rd); result->val += 2*nc*rd.val; result->err += 2*fabs(nc)*rd.err; return GSL_ERROR_SELECT_2(status, rdstatus); } } } int gsl_sf_ellint_Dcomp_e(double k, gsl_mode_t mode, gsl_sf_result * result) { if(k*k >= 1.0) { DOMAIN_ERROR(result); } else { const double y = 1.0 - k*k; /* FIXME: still need to handle k~=~1 */ gsl_sf_result rd; const int status = gsl_sf_ellint_RD_e(0.0, y, 1.0, mode, &rd); result->val = (1.0/3.0) * rd.val; result->err = GSL_DBL_EPSILON * fabs(result->val) + fabs(1.0/3.0 * rd.err); return status; } } /* [Carlson, Numer. Math. 33 (1979) 1, (4.5)] */ int gsl_sf_ellint_Kcomp_e(double k, gsl_mode_t mode, gsl_sf_result * result) { if(k*k >= 1.0) { DOMAIN_ERROR(result); } else if(k*k >= 1.0 - GSL_SQRT_DBL_EPSILON) { /* [Abramowitz+Stegun, 17.3.33] */ const double y = 1.0 - k*k; const double a[] = { 1.38629436112, 0.09666344259, 0.03590092383 }; const double b[] = { 0.5, 0.12498593597, 0.06880248576 }; const double ta = a[0] + y*(a[1] + y*a[2]); const double tb = -log(y) * (b[0] * y*(b[1] + y*b[2])); result->val = ta + tb; result->err = 2.0 * GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { /* This was previously computed as, return gsl_sf_ellint_RF_e(0.0, 1.0 - k*k, 1.0, mode, result); but this underestimated the total error for small k, since the argument y=1-k^2 is not exact (there is an absolute error of GSL_DBL_EPSILON near y=0 due to cancellation in the subtraction). Taking the singular behavior of -log(y) above gives an error of 0.5*epsilon/y near y=0. (BJG) */ double y = 1.0 - k*k; int status = gsl_sf_ellint_RF_e(0.0, y, 1.0, mode, result); result->err += 0.5 * GSL_DBL_EPSILON / y; return status ; } } /* [Carlson, Numer. Math. 33 (1979) 1, (4.6)] */ int gsl_sf_ellint_Ecomp_e(double k, gsl_mode_t mode, gsl_sf_result * result) { if(k*k >= 1.0) { DOMAIN_ERROR(result); } else if(k*k >= 1.0 - GSL_SQRT_DBL_EPSILON) { /* [Abramowitz+Stegun, 17.3.36] */ const double y = 1.0 - k*k; const double a[] = { 0.44325141463, 0.06260601220, 0.04757383546 }; const double b[] = { 0.24998368310, 0.09200180037, 0.04069697526 }; const double ta = 1.0 + y*(a[0] + y*(a[1] + a[2]*y)); const double tb = -y*log(y) * (b[0] + y*(b[1] + b[2]*y)); result->val = ta + tb; result->err = 2.0 * GSL_DBL_EPSILON * result->val; return GSL_SUCCESS; } else { gsl_sf_result rf; gsl_sf_result rd; const double y = 1.0 - k*k; const int rfstatus = gsl_sf_ellint_RF_e(0.0, y, 1.0, mode, &rf); const int rdstatus = gsl_sf_ellint_RD_e(0.0, y, 1.0, mode, &rd); result->val = rf.val - k*k/3.0 * rd.val; result->err = rf.err + k*k/3.0 * rd.err; return GSL_ERROR_SELECT_2(rfstatus, rdstatus); } } /* [Carlson, Numer. Math. 33 (1979) 1, (4.3) phi=pi/2] */ int gsl_sf_ellint_Pcomp_e(double k, double n, gsl_mode_t mode, gsl_sf_result * result) { if(k*k >= 1.0) { DOMAIN_ERROR(result); } /* FIXME: need to handle k ~=~ 1 cancellations */ else { gsl_sf_result rf; gsl_sf_result rj; const double y = 1.0 - k*k; const int rfstatus = gsl_sf_ellint_RF_e(0.0, y, 1.0, mode, &rf); const int rjstatus = gsl_sf_ellint_RJ_e(0.0, y, 1.0, 1.0 + n, mode, &rj); result->val = rf.val - (n/3.0) * rj.val; result->err = rf.err + fabs(n/3.0) * rj.err; return GSL_ERROR_SELECT_2(rfstatus, rjstatus); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_ellint_Kcomp(double k, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_Kcomp_e(k, mode, &result)); } double gsl_sf_ellint_Ecomp(double k, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_Ecomp_e(k, mode, &result)); } double gsl_sf_ellint_Pcomp(double k, double n, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_Pcomp_e(k, n, mode, &result)); } double gsl_sf_ellint_Dcomp(double k, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_Dcomp_e(k, mode, &result)); } double gsl_sf_ellint_F(double phi, double k, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_F_e(phi, k, mode, &result)); } double gsl_sf_ellint_E(double phi, double k, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_E_e(phi, k, mode, &result)); } double gsl_sf_ellint_P(double phi, double k, double n, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_P_e(phi, k, n, mode, &result)); } double gsl_sf_ellint_D(double phi, double k, double n, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_D_e(phi, k, n, mode, &result)); } double gsl_sf_ellint_RC(double x, double y, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_RC_e(x, y, mode, &result)); } double gsl_sf_ellint_RD(double x, double y, double z, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_RD_e(x, y, z, mode, &result)); } double gsl_sf_ellint_RF(double x, double y, double z, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_RF_e(x, y, z, mode, &result)); } double gsl_sf_ellint_RJ(double x, double y, double z, double p, gsl_mode_t mode) { EVAL_RESULT(gsl_sf_ellint_RJ_e(x, y, z, p, mode, &result)); } sources_5316/external/gsl/gsl_randist__flat.c0000664000176700017670000000260511723710247020165 0ustar paulpaul/* randist/flat.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* This is the uniform distribution in the range [a, b) p(x) dx = 1/(b-a) dx if a <= x < b ..... = 0 otherwise */ double gsl_ran_flat (const gsl_rng * r, const double a, const double b) { double u = gsl_rng_uniform (r); /* A uniform distribution over [a,b] */ return a * (1 - u) + b * u; } double gsl_ran_flat_pdf (double x, const double a, const double b) { if (x < b && x >= a) { return 1 / (b - a); } else { return 0; } } sources_5316/external/gsl/gsl_cblas__ctbsv.c0000664000176700017670000000066711723710247020006 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" #include "gsl_cblas__hypot.c" void cblas_ctbsv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE TransA, const enum CBLAS_DIAG Diag, const int N, const int K, const void *A, const int lda, void *X, const int incX) { #define BASE float #include "gsl_cblas__source_tbsv_c.h" #undef BASE } sources_5316/external/gsl/gsl_fft__urand.c0000664000176700017670000000171211723710247017461 0ustar paulpaul/* fft/urand.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double urand (void); double urand (void) { static unsigned long int x = 1; x = (1103515245 * x + 12345) & 0x7fffffffUL ; return x / 2147483648.0 ; } sources_5316/external/gsl/gsl_sort_vector_ushort.h0000664000176700017670000000346711705263724021350 0ustar paulpaul/* sort/gsl_sort_vector_ushort.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_USHORT_H__ #define __GSL_SORT_VECTOR_USHORT_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_ushort.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_ushort (gsl_vector_ushort * v); int gsl_sort_vector_ushort_index (gsl_permutation * p, const gsl_vector_ushort * v); int gsl_sort_vector_ushort_smallest (unsigned short * dest, const size_t k, const gsl_vector_ushort * v); int gsl_sort_vector_ushort_largest (unsigned short * dest, const size_t k, const gsl_vector_ushort * v); int gsl_sort_vector_ushort_smallest_index (size_t * p, const size_t k, const gsl_vector_ushort * v); int gsl_sort_vector_ushort_largest_index (size_t * p, const size_t k, const gsl_vector_ushort * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_USHORT_H__ */ sources_5316/external/gsl/gsl_fft__signals.c0000664000176700017670000000102011723710247020000 0ustar paulpaul#include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_complex.h" #include "gsl_errno.h" #include "gsl_dft_complex.h" #include "gsl_dft_complex_float.h" #include "gsl_fft__complex_internal.h" #include "gsl_fft__urand.c" #define BASE_DOUBLE #include "templates_on.h" #include "gsl_fft__signals_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_fft__signals_source.c" #include "templates_off.h" #undef BASE_FLOAT sources_5316/external/gsl/gsl_statistics__median.c0000664000176700017670000000301311723710247021214 0ustar paulpaul#include "gsl__config.h" #include "gsl_statistics.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_statistics__median_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_randist__pascal.c0000664000176700017670000000322211723710247020476 0ustar paulpaul/* randist/pascal.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" #include "gsl_randist.h" /* The Pascal distribution is a negative binomial with valued integer n prob(k) = (n - 1 + k)!/(n!(k - 1)!) * p^n (1-p)^k for k = 0, 1, ..., n */ unsigned int gsl_ran_pascal (const gsl_rng * r, double p, unsigned int n) { /* This is a separate interface for the pascal distribution so that it can be optimized differently from the negative binomial in future. e.g. if n < 10 it might be faster to generate the Pascal distributions as the sum of geometric variates directly. */ unsigned int k = gsl_ran_negative_binomial (r, p, (double) n); return k; } double gsl_ran_pascal_pdf (const unsigned int k, const double p, unsigned int n) { double P = gsl_ran_negative_binomial_pdf (k, p, (double) n); return P; } sources_5316/external/gsl/gsl_permute_vector.h0000664000176700017670000000124511705263724020426 0ustar paulpaul#ifndef __GSL_PERMUTE_VECTOR_H__ #define __GSL_PERMUTE_VECTOR_H__ #include "gsl_permute_vector_complex_long_double.h" #include "gsl_permute_vector_complex_double.h" #include "gsl_permute_vector_complex_float.h" #include "gsl_permute_vector_long_double.h" #include "gsl_permute_vector_double.h" #include "gsl_permute_vector_float.h" #include "gsl_permute_vector_ulong.h" #include "gsl_permute_vector_long.h" #include "gsl_permute_vector_uint.h" #include "gsl_permute_vector_int.h" #include "gsl_permute_vector_ushort.h" #include "gsl_permute_vector_short.h" #include "gsl_permute_vector_uchar.h" #include "gsl_permute_vector_char.h" #endif /* __GSL_PERMUTE_VECTOR_H__ */ sources_5316/external/gsl/gsl_monte__miser.c0000664000176700017670000004037211723710247020037 0ustar paulpaul/* monte/miser.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Michael Booth * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* MISER. Based on the algorithm described in the following article, W.H. Press, G.R. Farrar, "Recursive Stratified Sampling for Multidimensional Monte Carlo Integration", Computers in Physics, v4 (1990), pp190-195. */ /* Author: MJB */ /* Modified by Brian Gough 12/2000 */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_rng.h" #include "gsl_monte.h" #include "gsl_monte_miser.h" static int estimate_corrmc (gsl_monte_function * f, const double xl[], const double xu[], size_t dim, size_t calls, gsl_rng * r, gsl_monte_miser_state * state, double *result, double *abserr, const double xmid[], double sigma_l[], double sigma_r[]); int gsl_monte_miser_integrate (gsl_monte_function * f, const double xl[], const double xu[], size_t dim, size_t calls, gsl_rng * r, gsl_monte_miser_state * state, double *result, double *abserr) { size_t n, estimate_calls, calls_l, calls_r; const size_t min_calls = state->min_calls; size_t i; size_t i_bisect; int found_best; double res_est = 0, err_est = 0; double res_r = 0, err_r = 0, res_l = 0, err_l = 0; double xbi_l, xbi_m, xbi_r, s; double vol; double weight_l, weight_r; double *x = state->x; double *xmid = state->xmid; double *sigma_l = state->sigma_l, *sigma_r = state->sigma_r; if (dim != state->dim) { GSL_ERROR ("number of dimensions must match allocated size", GSL_EINVAL); } for (i = 0; i < dim; i++) { if (xu[i] <= xl[i]) { GSL_ERROR ("xu must be greater than xl", GSL_EINVAL); } if (xu[i] - xl[i] > GSL_DBL_MAX) { GSL_ERROR ("Range of integration is too large, please rescale", GSL_EINVAL); } } if (state->alpha < 0) { GSL_ERROR ("alpha must be non-negative", GSL_EINVAL); } /* Compute volume */ vol = 1; for (i = 0; i < dim; i++) { vol *= xu[i] - xl[i]; } if (calls < state->min_calls_per_bisection) { double m = 0.0, q = 0.0; if (calls < 2) { GSL_ERROR ("insufficient calls for subvolume", GSL_EFAILED); } for (n = 0; n < calls; n++) { /* Choose a random point in the integration region */ for (i = 0; i < dim; i++) { x[i] = xl[i] + gsl_rng_uniform_pos (r) * (xu[i] - xl[i]); } { double fval = GSL_MONTE_FN_EVAL (f, x); /* recurrence for mean and variance */ double d = fval - m; m += d / (n + 1.0); q += d * d * (n / (n + 1.0)); } } *result = vol * m; *abserr = vol * sqrt (q / (calls * (calls - 1.0))); return GSL_SUCCESS; } estimate_calls = GSL_MAX (min_calls, calls * (state->estimate_frac)); if (estimate_calls < 4 * dim) { GSL_ERROR ("insufficient calls to sample all halfspaces", GSL_ESANITY); } /* Flip coins to bisect the integration region with some fuzz */ for (i = 0; i < dim; i++) { s = (gsl_rng_uniform (r) - 0.5) >= 0.0 ? state->dither : -state->dither; state->xmid[i] = (0.5 + s) * xl[i] + (0.5 - s) * xu[i]; } /* The idea is to chose the direction to bisect based on which will give the smallest total variance. We could (and may do so later) use MC to compute these variances. But the NR guys simply estimate the variances by finding the min and max function values for each half-region for each bisection. */ estimate_corrmc (f, xl, xu, dim, estimate_calls, r, state, &res_est, &err_est, xmid, sigma_l, sigma_r); /* We have now used up some calls for the estimation */ calls -= estimate_calls; /* Now find direction with the smallest total "variance" */ { double best_var = GSL_DBL_MAX; double beta = 2.0 / (1.0 + state->alpha); found_best = 0; i_bisect = 0; weight_l = weight_r = 1.0; for (i = 0; i < dim; i++) { if (sigma_l[i] >= 0 && sigma_r[i] >= 0) { /* estimates are okay */ double var = pow (sigma_l[i], beta) + pow (sigma_r[i], beta); if (var <= best_var) { found_best = 1; best_var = var; i_bisect = i; weight_l = pow (sigma_l[i], beta); weight_r = pow (sigma_r[i], beta); } } else { if (sigma_l[i] < 0) { GSL_ERROR ("no points in left-half space!", GSL_ESANITY); } if (sigma_r[i] < 0) { GSL_ERROR ("no points in right-half space!", GSL_ESANITY); } } } } if (!found_best) { /* All estimates were the same, so chose a direction at random */ i_bisect = gsl_rng_uniform_int (r, dim); } xbi_l = xl[i_bisect]; xbi_m = xmid[i_bisect]; xbi_r = xu[i_bisect]; /* Get the actual fractional sizes of the two "halves", and distribute the remaining calls among them */ { double fraction_l = fabs ((xbi_m - xbi_l) / (xbi_r - xbi_l)); double fraction_r = 1 - fraction_l; double a = fraction_l * weight_l; double b = fraction_r * weight_r; calls_l = min_calls + (calls - 2 * min_calls) * a / (a + b); calls_r = min_calls + (calls - 2 * min_calls) * b / (a + b); } /* Compute the integral for the left hand side of the bisection */ /* Due to the recursive nature of the algorithm we must allocate some new memory for each recursive call */ { int status; double *xu_tmp = (double *) malloc (dim * sizeof (double)); if (xu_tmp == 0) { GSL_ERROR_VAL ("out of memory for left workspace", GSL_ENOMEM, 0); } for (i = 0; i < dim; i++) { xu_tmp[i] = xu[i]; } xu_tmp[i_bisect] = xbi_m; status = gsl_monte_miser_integrate (f, xl, xu_tmp, dim, calls_l, r, state, &res_l, &err_l); free (xu_tmp); if (status != GSL_SUCCESS) { return status; } } /* Compute the integral for the right hand side of the bisection */ { int status; double *xl_tmp = (double *) malloc (dim * sizeof (double)); if (xl_tmp == 0) { GSL_ERROR_VAL ("out of memory for right workspace", GSL_ENOMEM, 0); } for (i = 0; i < dim; i++) { xl_tmp[i] = xl[i]; } xl_tmp[i_bisect] = xbi_m; status = gsl_monte_miser_integrate (f, xl_tmp, xu, dim, calls_r, r, state, &res_r, &err_r); free (xl_tmp); if (status != GSL_SUCCESS) { return status; } } *result = res_l + res_r; *abserr = sqrt (err_l * err_l + err_r * err_r); return GSL_SUCCESS; } gsl_monte_miser_state * gsl_monte_miser_alloc (size_t dim) { gsl_monte_miser_state *s = (gsl_monte_miser_state *) malloc (sizeof (gsl_monte_miser_state)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for miser state struct", GSL_ENOMEM, 0); } s->x = (double *) malloc (dim * sizeof (double)); if (s->x == 0) { free (s); GSL_ERROR_VAL ("failed to allocate space for x", GSL_ENOMEM, 0); } s->xmid = (double *) malloc (dim * sizeof (double)); if (s->xmid == 0) { free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for xmid", GSL_ENOMEM, 0); } s->sigma_l = (double *) malloc (dim * sizeof (double)); if (s->sigma_l == 0) { free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for sigma_l", GSL_ENOMEM, 0); } s->sigma_r = (double *) malloc (dim * sizeof (double)); if (s->sigma_r == 0) { free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for sigma_r", GSL_ENOMEM, 0); } s->fmax_l = (double *) malloc (dim * sizeof (double)); if (s->fmax_l == 0) { free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fmax_l", GSL_ENOMEM, 0); } s->fmax_r = (double *) malloc (dim * sizeof (double)); if (s->fmax_r == 0) { free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fmax_r", GSL_ENOMEM, 0); } s->fmin_l = (double *) malloc (dim * sizeof (double)); if (s->fmin_l == 0) { free (s->fmax_r); free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fmin_l", GSL_ENOMEM, 0); } s->fmin_r = (double *) malloc (dim * sizeof (double)); if (s->fmin_r == 0) { free (s->fmin_l); free (s->fmax_r); free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fmin_r", GSL_ENOMEM, 0); } s->fsum_l = (double *) malloc (dim * sizeof (double)); if (s->fsum_l == 0) { free (s->fmin_r); free (s->fmin_l); free (s->fmax_r); free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fsum_l", GSL_ENOMEM, 0); } s->fsum_r = (double *) malloc (dim * sizeof (double)); if (s->fsum_r == 0) { free (s->fsum_l); free (s->fmin_r); free (s->fmin_l); free (s->fmax_r); free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fsum_r", GSL_ENOMEM, 0); } s->fsum2_l = (double *) malloc (dim * sizeof (double)); if (s->fsum2_l == 0) { free (s->fsum_r); free (s->fsum_l); free (s->fmin_r); free (s->fmin_l); free (s->fmax_r); free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fsum2_l", GSL_ENOMEM, 0); } s->fsum2_r = (double *) malloc (dim * sizeof (double)); if (s->fsum2_r == 0) { free (s->fsum2_l); free (s->fsum_r); free (s->fsum_l); free (s->fmin_r); free (s->fmin_l); free (s->fmax_r); free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fsum2_r", GSL_ENOMEM, 0); } s->hits_r = (size_t *) malloc (dim * sizeof (size_t)); if (s->hits_r == 0) { free (s->fsum2_r); free (s->fsum2_l); free (s->fsum_r); free (s->fsum_l); free (s->fmin_r); free (s->fmin_l); free (s->fmax_r); free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fsum2_r", GSL_ENOMEM, 0); } s->hits_l = (size_t *) malloc (dim * sizeof (size_t)); if (s->hits_l == 0) { free (s->hits_r); free (s->fsum2_r); free (s->fsum2_l); free (s->fsum_r); free (s->fsum_l); free (s->fmin_r); free (s->fmin_l); free (s->fmax_r); free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); GSL_ERROR_VAL ("failed to allocate space for fsum2_r", GSL_ENOMEM, 0); } s->dim = dim; gsl_monte_miser_init (s); return s; } int gsl_monte_miser_init (gsl_monte_miser_state * s) { /* We use 8 points in each halfspace to estimate the variance. There are 2*dim halfspaces. A variance estimate requires a minimum of 2 points. */ s->min_calls = 16 * s->dim; s->min_calls_per_bisection = 32 * s->min_calls; s->estimate_frac = 0.1; s->alpha = 2.0; s->dither = 0.0; return GSL_SUCCESS; } void gsl_monte_miser_free (gsl_monte_miser_state * s) { free (s->hits_r); free (s->hits_l); free (s->fsum2_r); free (s->fsum2_l); free (s->fsum_r); free (s->fsum_l); free (s->fmin_r); free (s->fmin_l); free (s->fmax_r); free (s->fmax_l); free (s->sigma_r); free (s->sigma_l); free (s->xmid); free (s->x); free (s); } static int estimate_corrmc (gsl_monte_function * f, const double xl[], const double xu[], size_t dim, size_t calls, gsl_rng * r, gsl_monte_miser_state * state, double *result, double *abserr, const double xmid[], double sigma_l[], double sigma_r[]) { size_t i, n; double *x = state->x; double *fsum_l = state->fsum_l; double *fsum_r = state->fsum_r; double *fsum2_l = state->fsum2_l; double *fsum2_r = state->fsum2_r; size_t *hits_l = state->hits_l; size_t *hits_r = state->hits_r; double m = 0.0, q = 0.0; double vol = 1.0; for (i = 0; i < dim; i++) { vol *= xu[i] - xl[i]; hits_l[i] = hits_r[i] = 0; fsum_l[i] = fsum_r[i] = 0.0; fsum2_l[i] = fsum2_r[i] = 0.0; sigma_l[i] = sigma_r[i] = -1; } for (n = 0; n < calls; n++) { double fval; unsigned int j = (n/2) % dim; unsigned int side = (n % 2); for (i = 0; i < dim; i++) { double z = gsl_rng_uniform_pos (r) ; if (i != j) { x[i] = xl[i] + z * (xu[i] - xl[i]); } else { if (side == 0) { x[i] = xmid[i] + z * (xu[i] - xmid[i]); } else { x[i] = xl[i] + z * (xmid[i] - xl[i]); } } } fval = GSL_MONTE_FN_EVAL (f, x); /* recurrence for mean and variance */ { double d = fval - m; m += d / (n + 1.0); q += d * d * (n / (n + 1.0)); } /* compute the variances on each side of the bisection */ for (i = 0; i < dim; i++) { if (x[i] <= xmid[i]) { fsum_l[i] += fval; fsum2_l[i] += fval * fval; hits_l[i]++; } else { fsum_r[i] += fval; fsum2_r[i] += fval * fval; hits_r[i]++; } } } for (i = 0; i < dim; i++) { double fraction_l = (xmid[i] - xl[i]) / (xu[i] - xl[i]); if (hits_l[i] > 0) { fsum_l[i] /= hits_l[i]; sigma_l[i] = sqrt (fsum2_l[i] - fsum_l[i] * fsum_l[i] / hits_l[i]); sigma_l[i] *= fraction_l * vol / hits_l[i]; } if (hits_r[i] > 0) { fsum_r[i] /= hits_r[i]; sigma_r[i] = sqrt (fsum2_r[i] - fsum_r[i] * fsum_r[i] / hits_r[i]); sigma_r[i] *= (1 - fraction_l) * vol / hits_r[i]; } } *result = vol * m; if (calls < 2) { *abserr = GSL_POSINF; } else { *abserr = vol * sqrt (q / (calls * (calls - 1.0))); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cdf__weibull.c0000664000176700017670000000214711723710247017773 0ustar paulpaul/* cdf/weibull.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_weibull_P (const double x, const double a, const double b) { double P = -expm1 (-pow(x/a, b)); return P; } double gsl_cdf_weibull_Q (const double x, const double a, const double b) { double Q = exp (-pow(x/a, b)); return Q; } sources_5316/external/gsl/gsl_linalg__lu.c0000664000176700017670000001636211723710247017466 0ustar paulpaul/* linalg/lu.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include #include #include "gsl_math.h" #include "gsl_vector.h" #include "gsl_matrix.h" #include "gsl_permute_vector.h" #include "gsl_blas.h" #include "gsl_linalg.h" #define REAL double /* Factorise a general N x N matrix A into, * * P A = L U * * where P is a permutation matrix, L is unit lower triangular and U * is upper triangular. * * L is stored in the strict lower triangular part of the input * matrix. The diagonal elements of L are unity and are not stored. * * U is stored in the diagonal and upper triangular part of the * input matrix. * * P is stored in the permutation p. Column j of P is column k of the * identity matrix, where k = permutation->data[j] * * signum gives the sign of the permutation, (-1)^n, where n is the * number of interchanges in the permutation. * * See Golub & Van Loan, Matrix Computations, Algorithm 3.4.1 (Gauss * Elimination with Partial Pivoting). */ int gsl_linalg_LU_decomp (gsl_matrix * A, gsl_permutation * p, int *signum) { if (A->size1 != A->size2) { GSL_ERROR ("LU decomposition requires square matrix", GSL_ENOTSQR); } else if (p->size != A->size1) { GSL_ERROR ("permutation length must match matrix size", GSL_EBADLEN); } else { const size_t N = A->size1; size_t i, j, k; *signum = 1; gsl_permutation_init (p); for (j = 0; j < N - 1; j++) { /* Find maximum in the j-th column */ REAL ajj, max = fabs (gsl_matrix_get (A, j, j)); size_t i_pivot = j; for (i = j + 1; i < N; i++) { REAL aij = fabs (gsl_matrix_get (A, i, j)); if (aij > max) { max = aij; i_pivot = i; } } if (i_pivot != j) { gsl_matrix_swap_rows (A, j, i_pivot); gsl_permutation_swap (p, j, i_pivot); *signum = -(*signum); } ajj = gsl_matrix_get (A, j, j); if (ajj != 0.0) { for (i = j + 1; i < N; i++) { REAL aij = gsl_matrix_get (A, i, j) / ajj; gsl_matrix_set (A, i, j, aij); for (k = j + 1; k < N; k++) { REAL aik = gsl_matrix_get (A, i, k); REAL ajk = gsl_matrix_get (A, j, k); gsl_matrix_set (A, i, k, aik - aij * ajk); } } } } return GSL_SUCCESS; } } int gsl_linalg_LU_solve (const gsl_matrix * LU, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x) { if (LU->size1 != LU->size2) { GSL_ERROR ("LU matrix must be square", GSL_ENOTSQR); } else if (LU->size1 != p->size) { GSL_ERROR ("permutation length must match matrix size", GSL_EBADLEN); } else if (LU->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (LU->size2 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Copy x <- b */ gsl_vector_memcpy (x, b); /* Solve for x */ gsl_linalg_LU_svx (LU, p, x); return GSL_SUCCESS; } } int gsl_linalg_LU_svx (const gsl_matrix * LU, const gsl_permutation * p, gsl_vector * x) { if (LU->size1 != LU->size2) { GSL_ERROR ("LU matrix must be square", GSL_ENOTSQR); } else if (LU->size1 != p->size) { GSL_ERROR ("permutation length must match matrix size", GSL_EBADLEN); } else if (LU->size1 != x->size) { GSL_ERROR ("matrix size must match solution/rhs size", GSL_EBADLEN); } else { /* Apply permutation to RHS */ gsl_permute_vector (p, x); /* Solve for c using forward-substitution, L c = P b */ gsl_blas_dtrsv (CblasLower, CblasNoTrans, CblasUnit, LU, x); /* Perform back-substitution, U x = c */ gsl_blas_dtrsv (CblasUpper, CblasNoTrans, CblasNonUnit, LU, x); return GSL_SUCCESS; } } int gsl_linalg_LU_refine (const gsl_matrix * A, const gsl_matrix * LU, const gsl_permutation * p, const gsl_vector * b, gsl_vector * x, gsl_vector * residual) { if (A->size1 != A->size2) { GSL_ERROR ("matrix a must be square", GSL_ENOTSQR); } if (LU->size1 != LU->size2) { GSL_ERROR ("LU matrix must be square", GSL_ENOTSQR); } else if (A->size1 != LU->size2) { GSL_ERROR ("LU matrix must be decomposition of a", GSL_ENOTSQR); } else if (LU->size1 != p->size) { GSL_ERROR ("permutation length must match matrix size", GSL_EBADLEN); } else if (LU->size1 != b->size) { GSL_ERROR ("matrix size must match b size", GSL_EBADLEN); } else if (LU->size1 != x->size) { GSL_ERROR ("matrix size must match solution size", GSL_EBADLEN); } else { /* Compute residual, residual = (A * x - b) */ gsl_vector_memcpy (residual, b); gsl_blas_dgemv (CblasNoTrans, 1.0, A, x, -1.0, residual); /* Find correction, delta = - (A^-1) * residual, and apply it */ gsl_linalg_LU_svx (LU, p, residual); gsl_blas_daxpy (-1.0, residual, x); return GSL_SUCCESS; } } int gsl_linalg_LU_invert (const gsl_matrix * LU, const gsl_permutation * p, gsl_matrix * inverse) { size_t i, n = LU->size1; int status = GSL_SUCCESS; gsl_matrix_set_identity (inverse); for (i = 0; i < n; i++) { gsl_vector_view c = gsl_matrix_column (inverse, i); int status_i = gsl_linalg_LU_svx (LU, p, &(c.vector)); if (status_i) status = status_i; } return status; } double gsl_linalg_LU_det (gsl_matrix * LU, int signum) { size_t i, n = LU->size1; double det = (double) signum; for (i = 0; i < n; i++) { det *= gsl_matrix_get (LU, i, i); } return det; } double gsl_linalg_LU_lndet (gsl_matrix * LU) { size_t i, n = LU->size1; double lndet = 0.0; for (i = 0; i < n; i++) { lndet += log (fabs (gsl_matrix_get (LU, i, i))); } return lndet; } int gsl_linalg_LU_sgndet (gsl_matrix * LU, int signum) { size_t i, n = LU->size1; int s = signum; for (i = 0; i < n; i++) { double u = gsl_matrix_get (LU, i, i); if (u < 0) { s *= -1; } else if (u == 0) { s = 0; break; } } return s; } sources_5316/external/gsl/gsl_rng__uni.c0000664000176700017670000001367311723710247017163 0ustar paulpaul/* rng/uni.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /** This is a lagged Fibonacci generator which supposedly excellent statistical properties (I do not concur) I got it from the net and translated into C. * ====================================================================== * NIST Guide to Available Math Software. * Fullsource for module UNI from package CMLIB. * Retrieved from CAMSUN on Tue Oct 8 14:04:10 1996. * ====================================================================== C***BEGIN PROLOGUE UNI C***DATE WRITTEN 810915 C***REVISION DATE 830805 C***CATEGORY NO. L6A21 C***KEYWORDS RANDOM NUMBERS, UNIFORM RANDOM NUMBERS C***AUTHOR BLUE, JAMES, SCIENTIFIC COMPUTING DIVISION, NBS C KAHANER, DAVID, SCIENTIFIC COMPUTING DIVISION, NBS C MARSAGLIA, GEORGE, COMPUTER SCIENCE DEPT., WASH STATE UNIV C C***PURPOSE THIS ROUTINE GENERATES QUASI UNIFORM RANDOM NUMBERS ON [0,1 C AND CAN BE USED ON ANY COMPUTER WITH WHICH ALLOWS INTEGERS C AT LEAST AS LARGE AS 32767. C***DESCRIPTION C C THIS ROUTINE GENERATES QUASI UNIFORM RANDOM NUMBERS ON THE INTER C [0,1). IT CAN BE USED WITH ANY COMPUTER WHICH ALLOWS C INTEGERS AT LEAST AS LARGE AS 32767. C C C USE C FIRST TIME.... C Z = UNI(JD) C HERE JD IS ANY N O N - Z E R O INTEGER. C THIS CAUSES INITIALIZATION OF THE PROGRAM C AND THE FIRST RANDOM NUMBER TO BE RETURNED AS Z. C SUBSEQUENT TIMES... C Z = UNI(0) C CAUSES THE NEXT RANDOM NUMBER TO BE RETURNED AS Z. C C C.................................................................. C NOTE: USERS WHO WISH TO TRANSPORT THIS PROGRAM FROM ONE COMPUTER C TO ANOTHER SHOULD READ THE FOLLOWING INFORMATION..... C C MACHINE DEPENDENCIES... C MDIG = A LOWER BOUND ON THE NUMBER OF BINARY DIGITS AVAILABLE C FOR REPRESENTING INTEGERS, INCLUDING THE SIGN BIT. C THIS VALUE MUST BE AT LEAST 16, BUT MAY BE INCREASED C IN LINE WITH REMARK A BELOW. C C REMARKS... C A. THIS PROGRAM CAN BE USED IN TWO WAYS: C (1) TO OBTAIN REPEATABLE RESULTS ON DIFFERENT COMPUTERS, C SET 'MDIG' TO THE SMALLEST OF ITS VALUES ON EACH, OR, C (2) TO ALLOW THE LONGEST SEQUENCE OF RANDOM NUMBERS TO BE C GENERATED WITHOUT CYCLING (REPEATING) SET 'MDIG' TO THE C LARGEST POSSIBLE VALUE. C B. THE SEQUENCE OF NUMBERS GENERATED DEPENDS ON THE INITIAL C INPUT 'JD' AS WELL AS THE VALUE OF 'MDIG'. C IF MDIG=16 ONE SHOULD FIND THAT Editors Note: set the seed using 152 in order to get uni(305) -jt C THE FIRST EVALUATION C Z=UNI(305) GIVES Z=.027832881... C THE SECOND EVALUATION C Z=UNI(0) GIVES Z=.56102176... C THE THIRD EVALUATION C Z=UNI(0) GIVES Z=.41456343... C THE THOUSANDTH EVALUATION C Z=UNI(0) GIVES Z=.19797357... C C***REFERENCES MARSAGLIA G., "COMMENTS ON THE PERFECT UNIFORM RANDOM C NUMBER GENERATOR", UNPUBLISHED NOTES, WASH S. U. C***ROUTINES CALLED I1MACH,XERROR C***END PROLOGUE UNI **/ #include "gsl__config.h" #include #include "gsl_rng.h" static inline unsigned long int uni_get (void *vstate); static double uni_get_double (void *vstate); static void uni_set (void *state, unsigned long int s); static const unsigned int MDIG = 16; /* Machine digits in int */ static const unsigned int m1 = 32767; /* 2^(MDIG-1) - 1 */ static const unsigned int m2 = 256; /* 2^(MDIG/2) */ typedef struct { int i, j; unsigned long m[17]; } uni_state_t; static inline unsigned long uni_get (void *vstate) { uni_state_t *state = (uni_state_t *) vstate; const int i = state->i; const int j = state->j; /* important k not be unsigned */ long k = state->m[i] - state->m[j]; if (k < 0) k += m1; state->m[j] = k; if (i == 0) { state->i = 16; } else { (state->i)--; } if (j == 0) { state->j = 16; } else { (state->j)--; } return k; } static double uni_get_double (void *vstate) { return uni_get (vstate) / 32767.0 ; } static void uni_set (void *vstate, unsigned long int s) { unsigned int i, seed, k0, k1, j0, j1; uni_state_t *state = (uni_state_t *) vstate; /* For this routine, the seeding is very elaborate! */ /* A flaw in this approach is that seeds 1,2 give exactly the same random number sequence! */ s = 2 * s + 1; /* enforce seed be odd */ seed = (s < m1 ? s : m1); /* seed should be less than m1 */ k0 = 9069 % m2; k1 = 9069 / m2; j0 = seed % m2; j1 = seed / m2; for (i = 0; i < 17; ++i) { seed = j0 * k0; j1 = (seed / m2 + j0 * k1 + j1 * k0) % (m2 / 2); j0 = seed % m2; state->m[i] = j0 + m2 * j1; } state->i = 4; state->j = 16; return; } static const gsl_rng_type uni_type = {"uni", /* name */ 32766, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (uni_state_t), &uni_set, &uni_get, &uni_get_double}; const gsl_rng_type *gsl_rng_uni = &uni_type; sources_5316/external/gsl/gsl_eigen__francis.c0000664000176700017670000007147111723710247020316 0ustar paulpaul/* eigen/francis.c * * Copyright (C) 2006, 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_eigen.h" #include "gsl_linalg.h" #include "gsl_math.h" #include "gsl_blas.h" #include "gsl_vector.h" #include "gsl_vector_complex.h" #include "gsl_matrix.h" #include "gsl_cblas.h" #include "gsl_complex.h" #include "gsl_complex_math.h" /* * This module computes the eigenvalues of a real upper hessenberg * matrix, using the classical double shift Francis QR algorithm. * It will also optionally compute the full Schur form and matrix of * Schur vectors. * * See Golub & Van Loan, "Matrix Computations" (3rd ed), * algorithm 7.5.2 */ /* exceptional shift coefficients - these values are from LAPACK DLAHQR */ #define GSL_FRANCIS_COEFF1 (0.75) #define GSL_FRANCIS_COEFF2 (-0.4375) static inline void francis_schur_decomp(gsl_matrix * H, gsl_vector_complex * eval, gsl_eigen_francis_workspace * w); static inline size_t francis_search_subdiag_small_elements(gsl_matrix * A); static inline int francis_qrstep(gsl_matrix * H, gsl_eigen_francis_workspace * w); static inline void francis_schur_standardize(gsl_matrix *A, gsl_complex *eval1, gsl_complex *eval2, gsl_eigen_francis_workspace *w); static inline size_t francis_get_submatrix(gsl_matrix *A, gsl_matrix *B); static void francis_standard_form(gsl_matrix *A, double *cs, double *sn); /* gsl_eigen_francis_alloc() Allocate a workspace for solving the nonsymmetric eigenvalue problem. The size of this workspace is O(1) Inputs: none Return: pointer to workspace */ gsl_eigen_francis_workspace * gsl_eigen_francis_alloc(void) { gsl_eigen_francis_workspace *w; w = (gsl_eigen_francis_workspace *) calloc (1, sizeof (gsl_eigen_francis_workspace)); if (w == 0) { GSL_ERROR_NULL ("failed to allocate space for workspace", GSL_ENOMEM); } /* these are filled in later */ w->size = 0; w->max_iterations = 0; w->n_iter = 0; w->n_evals = 0; w->compute_t = 0; w->Z = NULL; w->H = NULL; return (w); } /* gsl_eigen_francis_alloc() */ /* gsl_eigen_francis_free() Free francis workspace w */ void gsl_eigen_francis_free (gsl_eigen_francis_workspace *w) { free(w); } /* gsl_eigen_francis_free() */ /* gsl_eigen_francis_T() Called when we want to compute the Schur form T, or no longer compute the Schur form T Inputs: compute_t - 1 to compute T, 0 to not compute T w - francis workspace */ void gsl_eigen_francis_T (const int compute_t, gsl_eigen_francis_workspace *w) { w->compute_t = compute_t; } /* gsl_eigen_francis() Solve the nonsymmetric eigenvalue problem H x = \lambda x for the eigenvalues \lambda using algorithm 7.5.2 of Golub & Van Loan, "Matrix Computations" (3rd ed) Inputs: H - upper hessenberg matrix eval - where to store eigenvalues w - workspace Return: success or error - if error code is returned, then the QR procedure did not converge in the allowed number of iterations. In the event of non- convergence, the number of eigenvalues found will still be stored in the beginning of eval, Notes: On output, the diagonal of H contains 1-by-1 or 2-by-2 blocks containing the eigenvalues. If T is desired, H will contain the full Schur form on output. */ int gsl_eigen_francis (gsl_matrix * H, gsl_vector_complex * eval, gsl_eigen_francis_workspace * w) { /* check matrix and vector sizes */ if (H->size1 != H->size2) { GSL_ERROR ("matrix must be square to compute eigenvalues", GSL_ENOTSQR); } else if (eval->size != H->size1) { GSL_ERROR ("eigenvalue vector must match matrix size", GSL_EBADLEN); } else { const size_t N = H->size1; int j; /* * Set internal parameters which depend on matrix size. * The Francis solver can be called with any size matrix * since the workspace does not depend on N. * Furthermore, multishift solvers which call the Francis * solver may need to call it with different sized matrices */ w->size = N; w->max_iterations = 30 * N; /* * save a pointer to original matrix since francis_schur_decomp * is recursive */ w->H = H; w->n_iter = 0; w->n_evals = 0; /* * zero out the first two subdiagonals (below the main subdiagonal) * needed as scratch space by the QR sweep routine */ for (j = 0; j < (int) N - 3; ++j) { gsl_matrix_set(H, (size_t) j + 2, (size_t) j, 0.0); gsl_matrix_set(H, (size_t) j + 3, (size_t) j, 0.0); } if (N > 2) gsl_matrix_set(H, N - 1, N - 3, 0.0); /* * compute Schur decomposition of H and store eigenvalues * into eval */ francis_schur_decomp(H, eval, w); if (w->n_evals != N) return GSL_EMAXITER; return GSL_SUCCESS; } } /* gsl_eigen_francis() */ /* gsl_eigen_francis_Z() Solve the nonsymmetric eigenvalue problem for a Hessenberg matrix H x = \lambda x for the eigenvalues \lambda using the Francis double-shift method. Here we compute the real Schur form T = Q^t H Q with the diagonal blocks of T giving us the eigenvalues. Q is the matrix of Schur vectors. Originally, H was obtained from a general nonsymmetric matrix A via a transformation H = U^t A U so that T = (UQ)^t A (UQ) = Z^t A Z Z is the matrix of Schur vectors computed by this algorithm Inputs: H - upper hessenberg matrix eval - where to store eigenvalues Z - where to store Schur vectors w - workspace Notes: 1) If T is computed, it is stored in H on output. Otherwise, the diagonal of H will contain 1-by-1 and 2-by-2 blocks containing the eigenvalues. 2) The matrix Z must be initialized to the Hessenberg similarity matrix U. Or if you want the eigenvalues of H, initialize Z to the identity matrix. */ int gsl_eigen_francis_Z (gsl_matrix * H, gsl_vector_complex * eval, gsl_matrix * Z, gsl_eigen_francis_workspace * w) { int s; /* set internal Z pointer so we know to accumulate transformations */ w->Z = Z; s = gsl_eigen_francis(H, eval, w); w->Z = NULL; return s; } /* gsl_eigen_francis_Z() */ /******************************************** * INTERNAL ROUTINES * ********************************************/ /* francis_schur_decomp() Compute the Schur decomposition of the matrix H Inputs: H - hessenberg matrix eval - where to store eigenvalues w - workspace Return: none */ static inline void francis_schur_decomp(gsl_matrix * H, gsl_vector_complex * eval, gsl_eigen_francis_workspace * w) { gsl_matrix_view m; /* active matrix we are working on */ size_t N; /* size of matrix */ size_t q; /* index of small subdiagonal element */ gsl_complex lambda1, /* eigenvalues */ lambda2; N = H->size1; m = gsl_matrix_submatrix(H, 0, 0, N, N); while ((N > 2) && ((w->n_iter)++ < w->max_iterations)) { q = francis_search_subdiag_small_elements(&m.matrix); if (q == 0) { /* * no small subdiagonal element found - perform a QR * sweep on the active reduced hessenberg matrix */ francis_qrstep(&m.matrix, w); continue; } /* * a small subdiagonal element was found - one or two eigenvalues * have converged or the matrix has split into two smaller matrices */ if (q == (N - 1)) { /* * the last subdiagonal element of the matrix is 0 - * m_{NN} is a real eigenvalue */ GSL_SET_COMPLEX(&lambda1, gsl_matrix_get(&m.matrix, q, q), 0.0); gsl_vector_complex_set(eval, w->n_evals, lambda1); w->n_evals += 1; w->n_iter = 0; --N; m = gsl_matrix_submatrix(&m.matrix, 0, 0, N, N); } else if (q == (N - 2)) { gsl_matrix_view v; /* * The bottom right 2-by-2 block of m is an eigenvalue * system */ v = gsl_matrix_submatrix(&m.matrix, q, q, 2, 2); francis_schur_standardize(&v.matrix, &lambda1, &lambda2, w); gsl_vector_complex_set(eval, w->n_evals, lambda1); gsl_vector_complex_set(eval, w->n_evals + 1, lambda2); w->n_evals += 2; w->n_iter = 0; N -= 2; m = gsl_matrix_submatrix(&m.matrix, 0, 0, N, N); } else if (q == 1) { /* the first matrix element is an eigenvalue */ GSL_SET_COMPLEX(&lambda1, gsl_matrix_get(&m.matrix, 0, 0), 0.0); gsl_vector_complex_set(eval, w->n_evals, lambda1); w->n_evals += 1; w->n_iter = 0; --N; m = gsl_matrix_submatrix(&m.matrix, 1, 1, N, N); } else if (q == 2) { gsl_matrix_view v; /* the upper left 2-by-2 block is an eigenvalue system */ v = gsl_matrix_submatrix(&m.matrix, 0, 0, 2, 2); francis_schur_standardize(&v.matrix, &lambda1, &lambda2, w); gsl_vector_complex_set(eval, w->n_evals, lambda1); gsl_vector_complex_set(eval, w->n_evals + 1, lambda2); w->n_evals += 2; w->n_iter = 0; N -= 2; m = gsl_matrix_submatrix(&m.matrix, 2, 2, N, N); } else { gsl_matrix_view v; /* * There is a zero element on the subdiagonal somewhere * in the middle of the matrix - we can now operate * separately on the two submatrices split by this * element. q is the row index of the zero element. */ /* operate on lower right (N - q)-by-(N - q) block first */ v = gsl_matrix_submatrix(&m.matrix, q, q, N - q, N - q); francis_schur_decomp(&v.matrix, eval, w); /* operate on upper left q-by-q block */ v = gsl_matrix_submatrix(&m.matrix, 0, 0, q, q); francis_schur_decomp(&v.matrix, eval, w); N = 0; } } /* handle special cases of N = 1 or 2 */ if (N == 1) { GSL_SET_COMPLEX(&lambda1, gsl_matrix_get(&m.matrix, 0, 0), 0.0); gsl_vector_complex_set(eval, w->n_evals, lambda1); w->n_evals += 1; w->n_iter = 0; } else if (N == 2) { francis_schur_standardize(&m.matrix, &lambda1, &lambda2, w); gsl_vector_complex_set(eval, w->n_evals, lambda1); gsl_vector_complex_set(eval, w->n_evals + 1, lambda2); w->n_evals += 2; w->n_iter = 0; } } /* francis_schur_decomp() */ /* francis_qrstep() Perform a Francis QR step. See Golub & Van Loan, "Matrix Computations" (3rd ed), algorithm 7.5.1 Inputs: H - upper Hessenberg matrix w - workspace Notes: The matrix H must be "reduced", ie: have no tiny subdiagonal elements. When computing the first householder reflection, we divide by H_{21} so it is necessary that this element is not zero. When a subdiagonal element becomes negligible, the calling function should call this routine with the submatrices split by that element, so that we don't divide by zeros. */ static inline int francis_qrstep(gsl_matrix * H, gsl_eigen_francis_workspace * w) { const size_t N = H->size1; size_t i; /* looping */ gsl_matrix_view m; double tau_i; /* householder coefficient */ double dat[3]; /* householder vector */ double scale; /* scale factor to avoid overflow */ gsl_vector_view v2, v3; size_t q, r; size_t top = 0; /* location of H in original matrix */ double s, disc; double h_nn, /* H(n,n) */ h_nm1nm1, /* H(n-1,n-1) */ h_cross, /* H(n,n-1) * H(n-1,n) */ h_tmp1, h_tmp2; v2 = gsl_vector_view_array(dat, 2); v3 = gsl_vector_view_array(dat, 3); if ((w->n_iter % 10) == 0) { /* * exceptional shifts: we have gone 10 iterations * without finding a new eigenvalue, try a new choice of shifts. * See LAPACK routine DLAHQR */ s = fabs(gsl_matrix_get(H, N - 1, N - 2)) + fabs(gsl_matrix_get(H, N - 2, N - 3)); h_nn = gsl_matrix_get(H, N - 1, N - 1) + GSL_FRANCIS_COEFF1 * s; h_nm1nm1 = h_nn; h_cross = GSL_FRANCIS_COEFF2 * s * s; } else { /* * normal shifts - compute Rayleigh quotient and use * Wilkinson shift if possible */ h_nn = gsl_matrix_get(H, N - 1, N - 1); h_nm1nm1 = gsl_matrix_get(H, N - 2, N - 2); h_cross = gsl_matrix_get(H, N - 1, N - 2) * gsl_matrix_get(H, N - 2, N - 1); disc = 0.5 * (h_nm1nm1 - h_nn); disc = disc * disc + h_cross; if (disc > 0.0) { double ave; /* real roots - use Wilkinson's shift twice */ disc = sqrt(disc); ave = 0.5 * (h_nm1nm1 + h_nn); if (fabs(h_nm1nm1) - fabs(h_nn) > 0.0) { h_nm1nm1 = h_nm1nm1 * h_nn - h_cross; h_nn = h_nm1nm1 / (disc * GSL_SIGN(ave) + ave); } else { h_nn = disc * GSL_SIGN(ave) + ave; } h_nm1nm1 = h_nn; h_cross = 0.0; } } h_tmp1 = h_nm1nm1 - gsl_matrix_get(H, 0, 0); h_tmp2 = h_nn - gsl_matrix_get(H, 0, 0); /* * These formulas are equivalent to those in Golub & Van Loan * for the normal shift case - the terms have been rearranged * to reduce possible roundoff error when subdiagonal elements * are small */ dat[0] = (h_tmp1*h_tmp2 - h_cross) / gsl_matrix_get(H, 1, 0) + gsl_matrix_get(H, 0, 1); dat[1] = gsl_matrix_get(H, 1, 1) - gsl_matrix_get(H, 0, 0) - h_tmp1 - h_tmp2; dat[2] = gsl_matrix_get(H, 2, 1); scale = fabs(dat[0]) + fabs(dat[1]) + fabs(dat[2]); if (scale != 0.0) { /* scale to prevent overflow or underflow */ dat[0] /= scale; dat[1] /= scale; dat[2] /= scale; } if (w->Z || w->compute_t) { /* * get absolute indices of this (sub)matrix relative to the * original Hessenberg matrix */ top = francis_get_submatrix(w->H, H); } for (i = 0; i < N - 2; ++i) { tau_i = gsl_linalg_householder_transform(&v3.vector); if (tau_i != 0.0) { /* q = max(1, i - 1) */ q = (1 > ((int)i - 1)) ? 0 : (i - 1); /* r = min(i + 3, N - 1) */ r = ((i + 3) < (N - 1)) ? (i + 3) : (N - 1); if (w->compute_t) { /* * We are computing the Schur form T, so we * need to transform the whole matrix H * * H -> P_k^t H P_k * * where P_k is the current Householder matrix */ /* apply left householder matrix (I - tau_i v v') to H */ m = gsl_matrix_submatrix(w->H, top + i, top + q, 3, w->size - top - q); gsl_linalg_householder_hm(tau_i, &v3.vector, &m.matrix); /* apply right householder matrix (I - tau_i v v') to H */ m = gsl_matrix_submatrix(w->H, 0, top + i, top + r + 1, 3); gsl_linalg_householder_mh(tau_i, &v3.vector, &m.matrix); } else { /* * We are not computing the Schur form T, so we * only need to transform the active block */ /* apply left householder matrix (I - tau_i v v') to H */ m = gsl_matrix_submatrix(H, i, q, 3, N - q); gsl_linalg_householder_hm(tau_i, &v3.vector, &m.matrix); /* apply right householder matrix (I - tau_i v v') to H */ m = gsl_matrix_submatrix(H, 0, i, r + 1, 3); gsl_linalg_householder_mh(tau_i, &v3.vector, &m.matrix); } if (w->Z) { /* accumulate the similarity transformation into Z */ m = gsl_matrix_submatrix(w->Z, 0, top + i, w->size, 3); gsl_linalg_householder_mh(tau_i, &v3.vector, &m.matrix); } } /* if (tau_i != 0.0) */ dat[0] = gsl_matrix_get(H, i + 1, i); dat[1] = gsl_matrix_get(H, i + 2, i); if (i < (N - 3)) { dat[2] = gsl_matrix_get(H, i + 3, i); } scale = fabs(dat[0]) + fabs(dat[1]) + fabs(dat[2]); if (scale != 0.0) { /* scale to prevent overflow or underflow */ dat[0] /= scale; dat[1] /= scale; dat[2] /= scale; } } /* for (i = 0; i < N - 2; ++i) */ scale = fabs(dat[0]) + fabs(dat[1]); if (scale != 0.0) { /* scale to prevent overflow or underflow */ dat[0] /= scale; dat[1] /= scale; } tau_i = gsl_linalg_householder_transform(&v2.vector); if (w->compute_t) { m = gsl_matrix_submatrix(w->H, top + N - 2, top + N - 3, 2, w->size - top - N + 3); gsl_linalg_householder_hm(tau_i, &v2.vector, &m.matrix); m = gsl_matrix_submatrix(w->H, 0, top + N - 2, top + N, 2); gsl_linalg_householder_mh(tau_i, &v2.vector, &m.matrix); } else { m = gsl_matrix_submatrix(H, N - 2, N - 3, 2, 3); gsl_linalg_householder_hm(tau_i, &v2.vector, &m.matrix); m = gsl_matrix_submatrix(H, 0, N - 2, N, 2); gsl_linalg_householder_mh(tau_i, &v2.vector, &m.matrix); } if (w->Z) { /* accumulate transformation into Z */ m = gsl_matrix_submatrix(w->Z, 0, top + N - 2, w->size, 2); gsl_linalg_householder_mh(tau_i, &v2.vector, &m.matrix); } return GSL_SUCCESS; } /* francis_qrstep() */ /* francis_search_subdiag_small_elements() Search for a small subdiagonal element starting from the bottom of a matrix A. A small element is one that satisfies: |A_{i,i-1}| <= eps * (|A_{i,i}| + |A_{i-1,i-1}|) Inputs: A - matrix (must be at least 3-by-3) Return: row index of small subdiagonal element or 0 if not found Notes: the first small element that is found (starting from bottom) is set to zero */ static inline size_t francis_search_subdiag_small_elements(gsl_matrix * A) { const size_t N = A->size1; size_t i; double dpel = gsl_matrix_get(A, N - 2, N - 2); for (i = N - 1; i > 0; --i) { double sel = gsl_matrix_get(A, i, i - 1); double del = gsl_matrix_get(A, i, i); if ((sel == 0.0) || (fabs(sel) < GSL_DBL_EPSILON * (fabs(del) + fabs(dpel)))) { gsl_matrix_set(A, i, i - 1, 0.0); return (i); } dpel = del; } return (0); } /* francis_search_subdiag_small_elements() */ /* francis_schur_standardize() Convert a 2-by-2 diagonal block in the Schur form to standard form and update the rest of T and Z matrices if required. Inputs: A - 2-by-2 matrix eval1 - where to store eigenvalue 1 eval2 - where to store eigenvalue 2 w - francis workspace */ static inline void francis_schur_standardize(gsl_matrix *A, gsl_complex *eval1, gsl_complex *eval2, gsl_eigen_francis_workspace *w) { const size_t N = w->size; double cs, sn; size_t top; /* * figure out where the submatrix A resides in the * original matrix H */ top = francis_get_submatrix(w->H, A); /* convert 2-by-2 block to standard form */ francis_standard_form(A, &cs, &sn); /* set eigenvalues */ GSL_SET_REAL(eval1, gsl_matrix_get(A, 0, 0)); GSL_SET_REAL(eval2, gsl_matrix_get(A, 1, 1)); if (gsl_matrix_get(A, 1, 0) == 0.0) { GSL_SET_IMAG(eval1, 0.0); GSL_SET_IMAG(eval2, 0.0); } else { double tmp = sqrt(fabs(gsl_matrix_get(A, 0, 1)) * fabs(gsl_matrix_get(A, 1, 0))); GSL_SET_IMAG(eval1, tmp); GSL_SET_IMAG(eval2, -tmp); } if (w->compute_t) { gsl_vector_view xv, yv; /* * The above call to francis_standard_form transformed a 2-by-2 block * of T into upper triangular form via the transformation * * U = [ CS -SN ] * [ SN CS ] * * The original matrix T was * * T = [ T_{11} | T_{12} | T_{13} ] * [ 0* | A | T_{23} ] * [ 0 | 0* | T_{33} ] * * where 0* indicates all zeros except for possibly * one subdiagonal element next to A. * * After francis_standard_form, T looks like this: * * T = [ T_{11} | T_{12} | T_{13} ] * [ 0* | U^t A U | T_{23} ] * [ 0 | 0* | T_{33} ] * * since only the 2-by-2 block of A was changed. However, * in order to be able to back transform T at the end, * we need to apply the U transformation to the rest * of the matrix T since there is no way to apply a * similarity transformation to T and change only the * middle 2-by-2 block. In other words, let * * M = [ I 0 0 ] * [ 0 U 0 ] * [ 0 0 I ] * * and compute * * M^t T M = [ T_{11} | T_{12} U | T_{13} ] * [ U^t 0* | U^t A U | U^t T_{23} ] * [ 0 | 0* U | T_{33} ] * * So basically we need to apply the transformation U * to the i x 2 matrix T_{12} and the 2 x (n - i + 2) * matrix T_{23}, where i is the index of the top of A * in T. * * The BLAS routine drot() is suited for this. */ if (top < (N - 2)) { /* transform the 2 rows of T_{23} */ xv = gsl_matrix_subrow(w->H, top, top + 2, N - top - 2); yv = gsl_matrix_subrow(w->H, top + 1, top + 2, N - top - 2); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } if (top > 0) { /* transform the 2 columns of T_{12} */ xv = gsl_matrix_subcolumn(w->H, top, 0, top); yv = gsl_matrix_subcolumn(w->H, top + 1, 0, top); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } } /* if (w->compute_t) */ if (w->Z) { gsl_vector_view xv, yv; /* * Accumulate the transformation in Z. Here, Z -> Z * M * * So: * * Z -> [ Z_{11} | Z_{12} U | Z_{13} ] * [ Z_{21} | Z_{22} U | Z_{23} ] * [ Z_{31} | Z_{32} U | Z_{33} ] * * So we just need to apply drot() to the 2 columns * starting at index 'top' */ xv = gsl_matrix_column(w->Z, top); yv = gsl_matrix_column(w->Z, top + 1); gsl_blas_drot(&xv.vector, &yv.vector, cs, sn); } /* if (w->Z) */ } /* francis_schur_standardize() */ /* francis_get_submatrix() B is a submatrix of A. The goal of this function is to compute the indices in A of where the matrix B resides */ static inline size_t francis_get_submatrix(gsl_matrix *A, gsl_matrix *B) { size_t diff; double ratio; size_t top; diff = (size_t) (B->data - A->data); ratio = (double)diff / ((double) (A->tda + 1)); top = (size_t) floor(ratio); return top; } /* francis_get_submatrix() */ /* francis_standard_form() Compute the Schur factorization of a real 2-by-2 matrix in standard form: [ A B ] = [ CS -SN ] [ T11 T12 ] [ CS SN ] [ C D ] [ SN CS ] [ T21 T22 ] [-SN CS ] where either: 1) T21 = 0 so that T11 and T22 are real eigenvalues of the matrix, or 2) T11 = T22 and T21*T12 < 0, so that T11 +/- sqrt(|T21*T12|) are complex conjugate eigenvalues Inputs: A - 2-by-2 matrix cs - where to store cosine parameter of rotation matrix sn - where to store sine parameter of rotation matrix Notes: 1) based on LAPACK routine DLANV2 2) On output, A is modified to contain the matrix in standard form */ static void francis_standard_form(gsl_matrix *A, double *cs, double *sn) { double a, b, c, d; /* input matrix values */ double tmp; double p, z; double bcmax, bcmis, scale; double tau, sigma; double cs1, sn1; double aa, bb, cc, dd; double sab, sac; a = gsl_matrix_get(A, 0, 0); b = gsl_matrix_get(A, 0, 1); c = gsl_matrix_get(A, 1, 0); d = gsl_matrix_get(A, 1, 1); if (c == 0.0) { /* * matrix is already upper triangular - set rotation matrix * to the identity */ *cs = 1.0; *sn = 0.0; } else if (b == 0.0) { /* swap rows and columns to make it upper triangular */ *cs = 0.0; *sn = 1.0; tmp = d; d = a; a = tmp; b = -c; c = 0.0; } else if (((a - d) == 0.0) && (GSL_SIGN(b) != GSL_SIGN(c))) { /* the matrix has complex eigenvalues with a == d */ *cs = 1.0; *sn = 0.0; } else { tmp = a - d; p = 0.5 * tmp; bcmax = GSL_MAX(fabs(b), fabs(c)); bcmis = GSL_MIN(fabs(b), fabs(c)) * GSL_SIGN(b) * GSL_SIGN(c); scale = GSL_MAX(fabs(p), bcmax); z = (p / scale) * p + (bcmax / scale) * bcmis; if (z >= 4.0 * GSL_DBL_EPSILON) { /* real eigenvalues, compute a and d */ z = p + GSL_SIGN(p) * fabs(sqrt(scale) * sqrt(z)); a = d + z; d -= (bcmax / z) * bcmis; /* compute b and the rotation matrix */ tau = gsl_hypot(c, z); *cs = z / tau; *sn = c / tau; b -= c; c = 0.0; } else { /* * complex eigenvalues, or real (almost) equal eigenvalues - * make diagonal elements equal */ sigma = b + c; tau = gsl_hypot(sigma, tmp); *cs = sqrt(0.5 * (1.0 + fabs(sigma) / tau)); *sn = -(p / (tau * (*cs))) * GSL_SIGN(sigma); /* * Compute [ AA BB ] = [ A B ] [ CS -SN ] * [ CC DD ] [ C D ] [ SN CS ] */ aa = a * (*cs) + b * (*sn); bb = -a * (*sn) + b * (*cs); cc = c * (*cs) + d * (*sn); dd = -c * (*sn) + d * (*cs); /* * Compute [ A B ] = [ CS SN ] [ AA BB ] * [ C D ] [-SN CS ] [ CC DD ] */ a = aa * (*cs) + cc * (*sn); b = bb * (*cs) + dd * (*sn); c = -aa * (*sn) + cc * (*cs); d = -bb * (*sn) + dd * (*cs); tmp = 0.5 * (a + d); a = d = tmp; if (c != 0.0) { if (b != 0.0) { if (GSL_SIGN(b) == GSL_SIGN(c)) { /* * real eigenvalues: reduce to upper triangular * form */ sab = sqrt(fabs(b)); sac = sqrt(fabs(c)); p = GSL_SIGN(c) * fabs(sab * sac); tau = 1.0 / sqrt(fabs(b + c)); a = tmp + p; d = tmp - p; b -= c; c = 0.0; cs1 = sab * tau; sn1 = sac * tau; tmp = (*cs) * cs1 - (*sn) * sn1; *sn = (*cs) * sn1 + (*sn) * cs1; *cs = tmp; } } else { b = -c; c = 0.0; tmp = *cs; *cs = -(*sn); *sn = tmp; } } } } /* set new matrix elements */ gsl_matrix_set(A, 0, 0, a); gsl_matrix_set(A, 0, 1, b); gsl_matrix_set(A, 1, 0, c); gsl_matrix_set(A, 1, 1, d); } /* francis_standard_form() */ sources_5316/external/gsl/gsl_cblas__source_hpmv.h0000664000176700017670000001165011705263724021221 0ustar paulpaul/* blas/source_hpmv.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { const int conj = (order == CblasColMajor) ? -1 : 1; INDEX i, j; const BASE alpha_real = CONST_REAL0(alpha); const BASE alpha_imag = CONST_IMAG0(alpha); const BASE beta_real = CONST_REAL0(beta); const BASE beta_imag = CONST_IMAG0(beta); if ((alpha_real == 0.0 && alpha_imag == 0.0) && (beta_real == 1.0 && beta_imag == 0.0)) return; /* form y := beta*y */ if (beta_real == 0.0 && beta_imag == 0.0) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { REAL(Y, iy) = 0.0; IMAG(Y, iy) = 0.0; iy += incY; } } else if (!(beta_real == 1.0 && beta_imag == 0.0)) { INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { const BASE y_real = REAL(Y, iy); const BASE y_imag = IMAG(Y, iy); const BASE tmpR = y_real * beta_real - y_imag * beta_imag; const BASE tmpI = y_real * beta_imag + y_imag * beta_real; REAL(Y, iy) = tmpR; IMAG(Y, iy) = tmpI; iy += incY; } } if (alpha_real == 0.0 && alpha_imag == 0.0) return; /* form y := alpha*A*x + y */ if ((order == CblasRowMajor && Uplo == CblasUpper) || (order == CblasColMajor && Uplo == CblasLower)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { BASE x_real = CONST_REAL(X, ix); BASE x_imag = CONST_IMAG(X, ix); BASE temp1_real = alpha_real * x_real - alpha_imag * x_imag; BASE temp1_imag = alpha_real * x_imag + alpha_imag * x_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; const INDEX j_min = i + 1; const INDEX j_max = N; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; BASE Aii_real = CONST_REAL(Ap, TPUP(N, i, i)); /* Aii_imag is zero */ REAL(Y, iy) += temp1_real * Aii_real; IMAG(Y, iy) += temp1_imag * Aii_real; for (j = j_min; j < j_max; j++) { BASE Aij_real = CONST_REAL(Ap, TPUP(N, i, j)); BASE Aij_imag = conj * CONST_IMAG(Ap, TPUP(N, i, j)); REAL(Y, jy) += temp1_real * Aij_real - temp1_imag * (-Aij_imag); IMAG(Y, jy) += temp1_real * (-Aij_imag) + temp1_imag * Aij_real; x_real = CONST_REAL(X, jx); x_imag = CONST_IMAG(X, jx); temp2_real += x_real * Aij_real - x_imag * Aij_imag; temp2_imag += x_real * Aij_imag + x_imag * Aij_real; jx += incX; jy += incY; } REAL(Y, iy) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(Y, iy) += alpha_real * temp2_imag + alpha_imag * temp2_real; ix += incX; iy += incY; } } else if ((order == CblasRowMajor && Uplo == CblasLower) || (order == CblasColMajor && Uplo == CblasUpper)) { INDEX ix = OFFSET(N, incX); INDEX iy = OFFSET(N, incY); for (i = 0; i < N; i++) { BASE x_real = CONST_REAL(X, ix); BASE x_imag = CONST_IMAG(X, ix); BASE temp1_real = alpha_real * x_real - alpha_imag * x_imag; BASE temp1_imag = alpha_real * x_imag + alpha_imag * x_real; BASE temp2_real = 0.0; BASE temp2_imag = 0.0; const INDEX j_min = 0; const INDEX j_max = i; INDEX jx = OFFSET(N, incX) + j_min * incX; INDEX jy = OFFSET(N, incY) + j_min * incY; BASE Aii_real = CONST_REAL(Ap, TPLO(N, i, i)); /* Aii_imag is zero */ REAL(Y, iy) += temp1_real * Aii_real; IMAG(Y, iy) += temp1_imag * Aii_real; for (j = j_min; j < j_max; j++) { BASE Aij_real = CONST_REAL(Ap, TPLO(N, i, j)); BASE Aij_imag = conj * CONST_IMAG(Ap, TPLO(N, i, j)); REAL(Y, jy) += temp1_real * Aij_real - temp1_imag * (-Aij_imag); IMAG(Y, jy) += temp1_real * (-Aij_imag) + temp1_imag * Aij_real; x_real = CONST_REAL(X, jx); x_imag = CONST_IMAG(X, jx); temp2_real += x_real * Aij_real - x_imag * Aij_imag; temp2_imag += x_real * Aij_imag + x_imag * Aij_real; jx += incX; jy += incY; } REAL(Y, iy) += alpha_real * temp2_real - alpha_imag * temp2_imag; IMAG(Y, iy) += alpha_real * temp2_imag + alpha_imag * temp2_real; ix += incX; iy += incY; } } else { BLAS_ERROR("unrecognized operation"); } } sources_5316/external/gsl/gsl_permute_uchar.h0000664000176700017670000000264611705263724020234 0ustar paulpaul/* permutation/gsl_permute_uchar.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_UCHAR_H__ #define __GSL_PERMUTE_UCHAR_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_uchar (const size_t * p, unsigned char * data, const size_t stride, const size_t n); int gsl_permute_uchar_inverse (const size_t * p, unsigned char * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_UCHAR_H__ */ sources_5316/external/gsl/gsl_sf__log.c0000644000176700017670000001540110707442037016760 0ustar paulpaul/* specfunc/log.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_log.h" #include "gsl_sf__error.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* Chebyshev expansion for log(1 + x(t))/x(t) * * x(t) = (4t-1)/(2(4-t)) * t(x) = (8x+1)/(2(x+2)) * -1/2 < x < 1/2 * -1 < t < 1 */ static double lopx_data[21] = { 2.16647910664395270521272590407, -0.28565398551049742084877469679, 0.01517767255690553732382488171, -0.00200215904941415466274422081, 0.00019211375164056698287947962, -0.00002553258886105542567601400, 2.9004512660400621301999384544e-06, -3.8873813517057343800270917900e-07, 4.7743678729400456026672697926e-08, -6.4501969776090319441714445454e-09, 8.2751976628812389601561347296e-10, -1.1260499376492049411710290413e-10, 1.4844576692270934446023686322e-11, -2.0328515972462118942821556033e-12, 2.7291231220549214896095654769e-13, -3.7581977830387938294437434651e-14, 5.1107345870861673561462339876e-15, -7.0722150011433276578323272272e-16, 9.7089758328248469219003866867e-17, -1.3492637457521938883731579510e-17, 1.8657327910677296608121390705e-18 }; static cheb_series lopx_cs = { lopx_data, 20, -1, 1, 10 }; /* Chebyshev expansion for (log(1 + x(t)) - x(t))/x(t)^2 * * x(t) = (4t-1)/(2(4-t)) * t(x) = (8x+1)/(2(x+2)) * -1/2 < x < 1/2 * -1 < t < 1 */ static double lopxmx_data[20] = { -1.12100231323744103373737274541, 0.19553462773379386241549597019, -0.01467470453808083971825344956, 0.00166678250474365477643629067, -0.00018543356147700369785746902, 0.00002280154021771635036301071, -2.8031253116633521699214134172e-06, 3.5936568872522162983669541401e-07, -4.6241857041062060284381167925e-08, 6.0822637459403991012451054971e-09, -8.0339824424815790302621320732e-10, 1.0751718277499375044851551587e-10, -1.4445310914224613448759230882e-11, 1.9573912180610336168921438426e-12, -2.6614436796793061741564104510e-13, 3.6402634315269586532158344584e-14, -4.9937495922755006545809120531e-15, 6.8802890218846809524646902703e-16, -9.5034129794804273611403251480e-17, 1.3170135013050997157326965813e-17 }; static cheb_series lopxmx_cs = { lopxmx_data, 19, -1, 1, 9 }; /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_log_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= 0.0) { DOMAIN_ERROR(result); } else { result->val = log(x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_log_abs_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x == 0.0) { DOMAIN_ERROR(result); } else { result->val = log(fabs(x)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_complex_log_e(const double zr, const double zi, gsl_sf_result * lnr, gsl_sf_result * theta) { /* CHECK_POINTER(lnr) */ /* CHECK_POINTER(theta) */ if(zr != 0.0 || zi != 0.0) { const double ax = fabs(zr); const double ay = fabs(zi); const double min = GSL_MIN(ax, ay); const double max = GSL_MAX(ax, ay); lnr->val = log(max) + 0.5 * log(1.0 + (min/max)*(min/max)); lnr->err = 2.0 * GSL_DBL_EPSILON * fabs(lnr->val); theta->val = atan2(zi, zr); theta->err = GSL_DBL_EPSILON * fabs(lnr->val); return GSL_SUCCESS; } else { DOMAIN_ERROR_2(lnr, theta); } } int gsl_sf_log_1plusx_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0) { DOMAIN_ERROR(result); } else if(fabs(x) < GSL_ROOT6_DBL_EPSILON) { const double c1 = -0.5; const double c2 = 1.0/3.0; const double c3 = -1.0/4.0; const double c4 = 1.0/5.0; const double c5 = -1.0/6.0; const double c6 = 1.0/7.0; const double c7 = -1.0/8.0; const double c8 = 1.0/9.0; const double c9 = -1.0/10.0; const double t = c5 + x*(c6 + x*(c7 + x*(c8 + x*c9))); result->val = x * (1.0 + x*(c1 + x*(c2 + x*(c3 + x*(c4 + x*t))))); result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(fabs(x) < 0.5) { double t = 0.5*(8.0*x + 1.0)/(x+2.0); gsl_sf_result c; cheb_eval_e(&lopx_cs, t, &c); result->val = x * c.val; result->err = fabs(x * c.err); return GSL_SUCCESS; } else { result->val = log(1.0 + x); result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_log_1plusx_mx_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0) { DOMAIN_ERROR(result); } else if(fabs(x) < GSL_ROOT5_DBL_EPSILON) { const double c1 = -0.5; const double c2 = 1.0/3.0; const double c3 = -1.0/4.0; const double c4 = 1.0/5.0; const double c5 = -1.0/6.0; const double c6 = 1.0/7.0; const double c7 = -1.0/8.0; const double c8 = 1.0/9.0; const double c9 = -1.0/10.0; const double t = c5 + x*(c6 + x*(c7 + x*(c8 + x*c9))); result->val = x*x * (c1 + x*(c2 + x*(c3 + x*(c4 + x*t)))); result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(fabs(x) < 0.5) { double t = 0.5*(8.0*x + 1.0)/(x+2.0); gsl_sf_result c; cheb_eval_e(&lopxmx_cs, t, &c); result->val = x*x * c.val; result->err = x*x * c.err; return GSL_SUCCESS; } else { const double lterm = log(1.0 + x); result->val = lterm - x; result->err = GSL_DBL_EPSILON * (fabs(lterm) + fabs(x)); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_log(const double x) { EVAL_RESULT(gsl_sf_log_e(x, &result)); } double gsl_sf_log_abs(const double x) { EVAL_RESULT(gsl_sf_log_abs_e(x, &result)); } double gsl_sf_log_1plusx(const double x) { EVAL_RESULT(gsl_sf_log_1plusx_e(x, &result)); } double gsl_sf_log_1plusx_mx(const double x) { EVAL_RESULT(gsl_sf_log_1plusx_mx_e(x, &result)); } sources_5316/external/gsl/gsl_specfunc__gegenbauer.c0000664000176700017670000001162511723710247021507 0ustar paulpaul/* specfunc/gegenbauer.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_gegenbauer.h" #include "gsl_specfunc__error.h" /* See: [Thompson, Atlas for Computing Mathematical Functions] */ int gsl_sf_gegenpoly_1_e(double lambda, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(lambda == 0.0) { result->val = 2.0*x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = 2.0*lambda*x; result->err = 4.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_gegenpoly_2_e(double lambda, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(lambda == 0.0) { const double txx = 2.0*x*x; result->val = -1.0 + txx; result->err = 2.0 * GSL_DBL_EPSILON * fabs(txx); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { result->val = lambda*(-1.0 + 2.0*(1.0+lambda)*x*x); result->err = GSL_DBL_EPSILON * (2.0 * fabs(result->val) + fabs(lambda)); return GSL_SUCCESS; } } int gsl_sf_gegenpoly_3_e(double lambda, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(lambda == 0.0) { result->val = x*(-2.0 + 4.0/3.0*x*x); result->err = GSL_DBL_EPSILON * (2.0 * fabs(result->val) + fabs(x)); return GSL_SUCCESS; } else { double c = 4.0 + lambda*(6.0 + 2.0*lambda); result->val = 2.0*lambda * x * ( -1.0 - lambda + c*x*x/3.0 ); result->err = GSL_DBL_EPSILON * (2.0 * fabs(result->val) + fabs(lambda * x)); return GSL_SUCCESS; } } int gsl_sf_gegenpoly_n_e(int n, double lambda, double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(lambda <= -0.5 || n < 0) { DOMAIN_ERROR(result); } else if(n == 0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(n == 1) { return gsl_sf_gegenpoly_1_e(lambda, x, result); } else if(n == 2) { return gsl_sf_gegenpoly_2_e(lambda, x, result); } else if(n == 3) { return gsl_sf_gegenpoly_3_e(lambda, x, result); } else { if(lambda == 0.0 && (x >= -1.0 || x <= 1.0)) { /* 2 T_n(x)/n */ const double z = n * acos(x); result->val = 2.0 * cos(z) / n; result->err = 2.0 * GSL_DBL_EPSILON * fabs(z * result->val); return GSL_SUCCESS; } else { int k; gsl_sf_result g2; gsl_sf_result g3; int stat_g2 = gsl_sf_gegenpoly_2_e(lambda, x, &g2); int stat_g3 = gsl_sf_gegenpoly_3_e(lambda, x, &g3); int stat_g = GSL_ERROR_SELECT_2(stat_g2, stat_g3); double gkm2 = g2.val; double gkm1 = g3.val; double gk = 0.0; for(k=4; k<=n; k++) { gk = (2.0*(k+lambda-1.0)*x*gkm1 - (k+2.0*lambda-2.0)*gkm2) / k; gkm2 = gkm1; gkm1 = gk; } result->val = gk; result->err = 2.0 * GSL_DBL_EPSILON * 0.5 * n * fabs(gk); return stat_g; } } } int gsl_sf_gegenpoly_array(int nmax, double lambda, double x, double * result_array) { int k; /* CHECK_POINTER(result_array) */ if(lambda <= -0.5 || nmax < 0) { GSL_ERROR("domain error", GSL_EDOM); } /* n == 0 */ result_array[0] = 1.0; if(nmax == 0) return GSL_SUCCESS; /* n == 1 */ if(lambda == 0.0) result_array[1] = 2.0*x; else result_array[1] = 2.0*lambda*x; /* n <= nmax */ for(k=2; k<=nmax; k++) { double term1 = 2.0*(k+lambda-1.0) * x * result_array[k-1]; double term2 = (k+2.0*lambda-2.0) * result_array[k-2]; result_array[k] = (term1 - term2) / k; } return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_gegenpoly_1(double lambda, double x) { EVAL_RESULT(gsl_sf_gegenpoly_1_e(lambda, x, &result)); } double gsl_sf_gegenpoly_2(double lambda, double x) { EVAL_RESULT(gsl_sf_gegenpoly_2_e(lambda, x, &result)); } double gsl_sf_gegenpoly_3(double lambda, double x) { EVAL_RESULT(gsl_sf_gegenpoly_3_e(lambda, x, &result)); } double gsl_sf_gegenpoly_n(int n, double lambda, double x) { EVAL_RESULT(gsl_sf_gegenpoly_n_e(n, lambda, x, &result)); } sources_5316/external/gsl/gsl_histogram2d.h0000664000176700017670000001301211705263724017601 0ustar paulpaul/* histogram/gsl_histogram2d.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_HISTOGRAM2D_H__ #define __GSL_HISTOGRAM2D_H__ #include #include #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t nx, ny ; double * xrange ; double * yrange ; double * bin ; } gsl_histogram2d ; typedef struct { size_t nx, ny ; double * xrange ; double * yrange ; double * sum ; } gsl_histogram2d_pdf ; gsl_histogram2d * gsl_histogram2d_alloc (const size_t nx, const size_t ny); gsl_histogram2d * gsl_histogram2d_calloc (const size_t nx, const size_t ny); gsl_histogram2d * gsl_histogram2d_calloc_uniform (const size_t nx, const size_t ny, const double xmin, const double xmax, const double ymin, const double ymax); void gsl_histogram2d_free (gsl_histogram2d * h); int gsl_histogram2d_increment (gsl_histogram2d * h, double x, double y); int gsl_histogram2d_accumulate (gsl_histogram2d * h, double x, double y, double weight); int gsl_histogram2d_find (const gsl_histogram2d * h, const double x, const double y, size_t * i, size_t * j); double gsl_histogram2d_get (const gsl_histogram2d * h, const size_t i, const size_t j); int gsl_histogram2d_get_xrange (const gsl_histogram2d * h, const size_t i, double * xlower, double * xupper); int gsl_histogram2d_get_yrange (const gsl_histogram2d * h, const size_t j, double * ylower, double * yupper); double gsl_histogram2d_xmax (const gsl_histogram2d * h); double gsl_histogram2d_xmin (const gsl_histogram2d * h); size_t gsl_histogram2d_nx (const gsl_histogram2d * h); double gsl_histogram2d_ymax (const gsl_histogram2d * h); double gsl_histogram2d_ymin (const gsl_histogram2d * h); size_t gsl_histogram2d_ny (const gsl_histogram2d * h); void gsl_histogram2d_reset (gsl_histogram2d * h); gsl_histogram2d * gsl_histogram2d_calloc_range(size_t nx, size_t ny, double *xrange, double *yrange); int gsl_histogram2d_set_ranges_uniform (gsl_histogram2d * h, double xmin, double xmax, double ymin, double ymax); int gsl_histogram2d_set_ranges (gsl_histogram2d * h, const double xrange[], size_t xsize, const double yrange[], size_t ysize); int gsl_histogram2d_memcpy(gsl_histogram2d *dest, const gsl_histogram2d *source); gsl_histogram2d * gsl_histogram2d_clone(const gsl_histogram2d * source); double gsl_histogram2d_max_val(const gsl_histogram2d *h); void gsl_histogram2d_max_bin (const gsl_histogram2d *h, size_t *i, size_t *j); double gsl_histogram2d_min_val(const gsl_histogram2d *h); void gsl_histogram2d_min_bin (const gsl_histogram2d *h, size_t *i, size_t *j); double gsl_histogram2d_xmean (const gsl_histogram2d * h); double gsl_histogram2d_ymean (const gsl_histogram2d * h); double gsl_histogram2d_xsigma (const gsl_histogram2d * h); double gsl_histogram2d_ysigma (const gsl_histogram2d * h); double gsl_histogram2d_cov (const gsl_histogram2d * h); double gsl_histogram2d_sum (const gsl_histogram2d *h); int gsl_histogram2d_equal_bins_p(const gsl_histogram2d *h1, const gsl_histogram2d *h2) ; int gsl_histogram2d_add(gsl_histogram2d *h1, const gsl_histogram2d *h2); int gsl_histogram2d_sub(gsl_histogram2d *h1, const gsl_histogram2d *h2); int gsl_histogram2d_mul(gsl_histogram2d *h1, const gsl_histogram2d *h2); int gsl_histogram2d_div(gsl_histogram2d *h1, const gsl_histogram2d *h2); int gsl_histogram2d_scale(gsl_histogram2d *h, double scale); int gsl_histogram2d_shift(gsl_histogram2d *h, double shift); int gsl_histogram2d_fwrite (FILE * stream, const gsl_histogram2d * h) ; int gsl_histogram2d_fread (FILE * stream, gsl_histogram2d * h); int gsl_histogram2d_fprintf (FILE * stream, const gsl_histogram2d * h, const char * range_format, const char * bin_format); int gsl_histogram2d_fscanf (FILE * stream, gsl_histogram2d * h); gsl_histogram2d_pdf * gsl_histogram2d_pdf_alloc (const size_t nx, const size_t ny); int gsl_histogram2d_pdf_init (gsl_histogram2d_pdf * p, const gsl_histogram2d * h); void gsl_histogram2d_pdf_free (gsl_histogram2d_pdf * p); int gsl_histogram2d_pdf_sample (const gsl_histogram2d_pdf * p, double r1, double r2, double * x, double * y); __END_DECLS #endif /* __GSL_HISTOGRAM2D_H__ */ sources_5316/external/gsl/gsl_rng__ranmar.c0000664000176700017670000000757111723710247017650 0ustar paulpaul/* rng/ranmar.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is the RANMAR lagged fibonacci generator of Marsaglia, Zaman and Tsang. The sequence is a series of 24-bit integers, x_n, x_n = (y_n - c_n + 2^24) mod 2^24 where, y_n = (y_{n-97) - y_{n-33} + 2^24) mod 2^24 c_n = (c_{n-1} - 7654321 + 2^24 - 3) mod (2^24 - 3) The period of this generator is 2^144. The generator provides about 900 million different subsequences each of length O(10^30). Thus each seed up to 900,000,000 gives an independent sequence. Although it was good in its day this generator now has known statistical defects and has been superseded by RANLUX. From: F. James, "A Review of Pseudorandom number generators", Computer Physics Communications 60, 329 (1990). G. Marsaglia, A. Zaman and W.W. Tsang, Stat. Prob. Lett. 9, 35 (1990) */ static inline unsigned long int ranmar_get (void *vstate); static double ranmar_get_double (void *vstate); static void ranmar_set (void *state, unsigned long int s); static const unsigned long int two24 = 16777216; /* 2^24 */ typedef struct { unsigned int i; unsigned int j; long int carry; unsigned long int u[97]; } ranmar_state_t; static inline unsigned long int ranmar_get (void *vstate) { ranmar_state_t *state = (ranmar_state_t *) vstate; unsigned int i = state->i; unsigned int j = state->j; long int carry = state->carry; long int delta = state->u[i] - state->u[j]; if (delta < 0) delta += two24 ; state->u[i] = delta; if (i == 0) { i = 96; } else { i--; } state->i = i; if (j == 0) { j = 96; } else { j--; } state->j = j; carry += - 7654321 ; if (carry < 0) carry += two24 - 3; state->carry = carry ; delta += - carry ; if (delta < 0) delta += two24 ; return delta; } static double ranmar_get_double (void *vstate) { return ranmar_get (vstate) / 16777216.0 ; } static void ranmar_set (void *vstate, unsigned long int s) { ranmar_state_t *state = (ranmar_state_t *) vstate; unsigned long int ij = s / 30082 ; unsigned long int kl = s % 30082 ; int i = (ij / 177) % 177 + 2 ; int j = (ij % 177) + 2 ; int k = (kl / 169) % 178 + 1 ; int l = (kl % 169) ; int a, b; for (a = 0; a < 97; a++) { unsigned long int sum = 0 ; unsigned long int t = two24 ; for (b = 0; b < 24; b++) { unsigned long int m = (((i * j) % 179) * k) % 179 ; i = j ; j = k ; k = m ; l = (53 * l + 1) % 169 ; t >>= 1 ; if ((l * m) % 64 >= 32) sum += t ; } state->u[a] = sum ; } state->i = 96; state->j = 32; state->carry = 362436 ; } static const gsl_rng_type ranmar_type = {"ranmar", /* name */ 0x00ffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (ranmar_state_t), &ranmar_set, &ranmar_get, &ranmar_get_double}; const gsl_rng_type *gsl_rng_ranmar = &ranmar_type; sources_5316/external/gsl/gsl_sort_long_double.h0000664000176700017670000000367611705263724020735 0ustar paulpaul/* sort/gsl_sort_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_LONG_DOUBLE_H__ #define __GSL_SORT_LONG_DOUBLE_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_long_double (long double * data, const size_t stride, const size_t n); void gsl_sort_long_double_index (size_t * p, const long double * data, const size_t stride, const size_t n); int gsl_sort_long_double_smallest (long double * dest, const size_t k, const long double * src, const size_t stride, const size_t n); int gsl_sort_long_double_smallest_index (size_t * p, const size_t k, const long double * src, const size_t stride, const size_t n); int gsl_sort_long_double_largest (long double * dest, const size_t k, const long double * src, const size_t stride, const size_t n); int gsl_sort_long_double_largest_index (size_t * p, const size_t k, const long double * src, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_SORT_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_cdf__error.h0000664000176700017670000000021411705263724017462 0ustar paulpaul/* CDF_ERROR: call the error handler, and return a NAN. */ #define CDF_ERROR(reason, gsl_errno) GSL_ERROR_VAL(reason, gsl_errno, GSL_NAN) sources_5316/external/gsl/gsl_vector_complex_float.h0000664000176700017670000002006511705263724021602 0ustar paulpaul/* vector/gsl_vector_complex_float.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_COMPLEX_FLOAT_H__ #define __GSL_VECTOR_COMPLEX_FLOAT_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_complex.h" #include "gsl_check_range.h" #include "gsl_vector_float.h" #include "gsl_vector_complex.h" #include "gsl_block_complex_float.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; float *data; gsl_block_complex_float *block; int owner; } gsl_vector_complex_float; typedef struct { gsl_vector_complex_float vector; } _gsl_vector_complex_float_view; typedef _gsl_vector_complex_float_view gsl_vector_complex_float_view; typedef struct { gsl_vector_complex_float vector; } _gsl_vector_complex_float_const_view; typedef const _gsl_vector_complex_float_const_view gsl_vector_complex_float_const_view; /* Allocation */ gsl_vector_complex_float *gsl_vector_complex_float_alloc (const size_t n); gsl_vector_complex_float *gsl_vector_complex_float_calloc (const size_t n); gsl_vector_complex_float * gsl_vector_complex_float_alloc_from_block (gsl_block_complex_float * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_complex_float * gsl_vector_complex_float_alloc_from_vector (gsl_vector_complex_float * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_complex_float_free (gsl_vector_complex_float * v); /* Views */ _gsl_vector_complex_float_view gsl_vector_complex_float_view_array (float *base, size_t n); _gsl_vector_complex_float_view gsl_vector_complex_float_view_array_with_stride (float *base, size_t stride, size_t n); _gsl_vector_complex_float_const_view gsl_vector_complex_float_const_view_array (const float *base, size_t n); _gsl_vector_complex_float_const_view gsl_vector_complex_float_const_view_array_with_stride (const float *base, size_t stride, size_t n); _gsl_vector_complex_float_view gsl_vector_complex_float_subvector (gsl_vector_complex_float *base, size_t i, size_t n); _gsl_vector_complex_float_view gsl_vector_complex_float_subvector_with_stride (gsl_vector_complex_float *v, size_t i, size_t stride, size_t n); _gsl_vector_complex_float_const_view gsl_vector_complex_float_const_subvector (const gsl_vector_complex_float *base, size_t i, size_t n); _gsl_vector_complex_float_const_view gsl_vector_complex_float_const_subvector_with_stride (const gsl_vector_complex_float *v, size_t i, size_t stride, size_t n); _gsl_vector_float_view gsl_vector_complex_float_real (gsl_vector_complex_float *v); _gsl_vector_float_view gsl_vector_complex_float_imag (gsl_vector_complex_float *v); _gsl_vector_float_const_view gsl_vector_complex_float_const_real (const gsl_vector_complex_float *v); _gsl_vector_float_const_view gsl_vector_complex_float_const_imag (const gsl_vector_complex_float *v); /* Operations */ gsl_complex_float gsl_vector_complex_float_get (const gsl_vector_complex_float * v, const size_t i); void gsl_vector_complex_float_set (gsl_vector_complex_float * v, const size_t i, gsl_complex_float z); gsl_complex_float *gsl_vector_complex_float_ptr (gsl_vector_complex_float * v, const size_t i); const gsl_complex_float *gsl_vector_complex_float_const_ptr (const gsl_vector_complex_float * v, const size_t i); void gsl_vector_complex_float_set_zero (gsl_vector_complex_float * v); void gsl_vector_complex_float_set_all (gsl_vector_complex_float * v, gsl_complex_float z); int gsl_vector_complex_float_set_basis (gsl_vector_complex_float * v, size_t i); int gsl_vector_complex_float_fread (FILE * stream, gsl_vector_complex_float * v); int gsl_vector_complex_float_fwrite (FILE * stream, const gsl_vector_complex_float * v); int gsl_vector_complex_float_fscanf (FILE * stream, gsl_vector_complex_float * v); int gsl_vector_complex_float_fprintf (FILE * stream, const gsl_vector_complex_float * v, const char *format); int gsl_vector_complex_float_memcpy (gsl_vector_complex_float * dest, const gsl_vector_complex_float * src); int gsl_vector_complex_float_reverse (gsl_vector_complex_float * v); int gsl_vector_complex_float_swap (gsl_vector_complex_float * v, gsl_vector_complex_float * w); int gsl_vector_complex_float_swap_elements (gsl_vector_complex_float * v, const size_t i, const size_t j); int gsl_vector_complex_float_isnull (const gsl_vector_complex_float * v); int gsl_vector_complex_float_ispos (const gsl_vector_complex_float * v); int gsl_vector_complex_float_isneg (const gsl_vector_complex_float * v); int gsl_vector_complex_float_isnonneg (const gsl_vector_complex_float * v); #ifdef HAVE_INLINE extern inline gsl_complex_float gsl_vector_complex_float_get (const gsl_vector_complex_float * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { gsl_complex_float zero = {{0, 0}}; GSL_ERROR_VAL ("index out of range", GSL_EINVAL, zero); } #endif return *GSL_COMPLEX_FLOAT_AT (v, i); } extern inline void gsl_vector_complex_float_set (gsl_vector_complex_float * v, const size_t i, gsl_complex_float z) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif *GSL_COMPLEX_FLOAT_AT (v, i) = z; } extern inline gsl_complex_float * gsl_vector_complex_float_ptr (gsl_vector_complex_float * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return GSL_COMPLEX_FLOAT_AT (v, i); } extern inline const gsl_complex_float * gsl_vector_complex_float_const_ptr (const gsl_vector_complex_float * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return GSL_COMPLEX_FLOAT_AT (v, i); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_COMPLEX_FLOAT_H__ */ sources_5316/external/gsl/gsl_multifit__qrsolv.c0000664000176700017670000001324711723710247020762 0ustar paulpaul/* This function computes the solution to the least squares system phi = [ A x = b , lambda D x = 0 ]^2 where A is an M by N matrix, D is an N by N diagonal matrix, lambda is a scalar parameter and b is a vector of length M. The function requires the factorization of A into A = Q R P^T, where Q is an orthogonal matrix, R is an upper triangular matrix with diagonal elements of non-increasing magnitude and P is a permuation matrix. The system above is then equivalent to [ R z = Q^T b, P^T (lambda D) P z = 0 ] where x = P z. If this system does not have full rank then a least squares solution is obtained. On output the function also provides an upper triangular matrix S such that P^T (A^T A + lambda^2 D^T D) P = S^T S Parameters, r: On input, contains the full upper triangle of R. On output the strict lower triangle contains the transpose of the strict upper triangle of S, and the diagonal of S is stored in sdiag. The full upper triangle of R is not modified. p: the encoded form of the permutation matrix P. column j of P is column p[j] of the identity matrix. lambda, diag: contains the scalar lambda and the diagonal elements of the matrix D qtb: contains the product Q^T b x: on output contains the least squares solution of the system wa: is a workspace of length N */ static int qrsolv (gsl_matrix * r, const gsl_permutation * p, const double lambda, const gsl_vector * diag, const gsl_vector * qtb, gsl_vector * x, gsl_vector * sdiag, gsl_vector * wa) { size_t n = r->size2; size_t i, j, k, nsing; /* Copy r and qtb to preserve input and initialise s. In particular, save the diagonal elements of r in x */ for (j = 0; j < n; j++) { double rjj = gsl_matrix_get (r, j, j); double qtbj = gsl_vector_get (qtb, j); for (i = j + 1; i < n; i++) { double rji = gsl_matrix_get (r, j, i); gsl_matrix_set (r, i, j, rji); } gsl_vector_set (x, j, rjj); gsl_vector_set (wa, j, qtbj); } /* Eliminate the diagonal matrix d using a Givens rotation */ for (j = 0; j < n; j++) { double qtbpj; size_t pj = gsl_permutation_get (p, j); double diagpj = lambda * gsl_vector_get (diag, pj); if (diagpj == 0) { continue; } gsl_vector_set (sdiag, j, diagpj); for (k = j + 1; k < n; k++) { gsl_vector_set (sdiag, k, 0.0); } /* The transformations to eliminate the row of d modify only a single element of qtb beyond the first n, which is initially zero */ qtbpj = 0; for (k = j; k < n; k++) { /* Determine a Givens rotation which eliminates the appropriate element in the current row of d */ double sine, cosine; double wak = gsl_vector_get (wa, k); double rkk = gsl_matrix_get (r, k, k); double sdiagk = gsl_vector_get (sdiag, k); if (sdiagk == 0) { continue; } if (fabs (rkk) < fabs (sdiagk)) { double cotangent = rkk / sdiagk; sine = 0.5 / sqrt (0.25 + 0.25 * cotangent * cotangent); cosine = sine * cotangent; } else { double tangent = sdiagk / rkk; cosine = 0.5 / sqrt (0.25 + 0.25 * tangent * tangent); sine = cosine * tangent; } /* Compute the modified diagonal element of r and the modified element of [qtb,0] */ { double new_rkk = cosine * rkk + sine * sdiagk; double new_wak = cosine * wak + sine * qtbpj; qtbpj = -sine * wak + cosine * qtbpj; gsl_matrix_set(r, k, k, new_rkk); gsl_vector_set(wa, k, new_wak); } /* Accumulate the transformation in the row of s */ for (i = k + 1; i < n; i++) { double rik = gsl_matrix_get (r, i, k); double sdiagi = gsl_vector_get (sdiag, i); double new_rik = cosine * rik + sine * sdiagi; double new_sdiagi = -sine * rik + cosine * sdiagi; gsl_matrix_set(r, i, k, new_rik); gsl_vector_set(sdiag, i, new_sdiagi); } } /* Store the corresponding diagonal element of s and restore the corresponding diagonal element of r */ { double rjj = gsl_matrix_get (r, j, j); double xj = gsl_vector_get(x, j); gsl_vector_set (sdiag, j, rjj); gsl_matrix_set (r, j, j, xj); } } /* Solve the triangular system for z. If the system is singular then obtain a least squares solution */ nsing = n; for (j = 0; j < n; j++) { double sdiagj = gsl_vector_get (sdiag, j); if (sdiagj == 0) { nsing = j; break; } } for (j = nsing; j < n; j++) { gsl_vector_set (wa, j, 0.0); } for (k = 0; k < nsing; k++) { double sum = 0; j = (nsing - 1) - k; for (i = j + 1; i < nsing; i++) { sum += gsl_matrix_get(r, i, j) * gsl_vector_get(wa, i); } { double waj = gsl_vector_get (wa, j); double sdiagj = gsl_vector_get (sdiag, j); gsl_vector_set (wa, j, (waj - sum) / sdiagj); } } /* Permute the components of z back to the components of x */ for (j = 0; j < n; j++) { size_t pj = gsl_permutation_get (p, j); double waj = gsl_vector_get (wa, j); gsl_vector_set (x, pj, waj); } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_matrix__view.h0000664000176700017670000000024511705263724020057 0ustar paulpaul#define NULL_VECTOR {0, 0, 0, 0, 0} #define NULL_VECTOR_VIEW {{0, 0, 0, 0, 0}} #define NULL_MATRIX {0, 0, 0, 0, 0, 0} #define NULL_MATRIX_VIEW {{0, 0, 0, 0, 0, 0}} sources_5316/external/gsl/gsl_specfunc__chebyshev.h0000664000176700017670000000227211705263724021371 0ustar paulpaul/* specfunc/chebyshev.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* data for a Chebyshev series over a given interval */ struct cheb_series_struct { double * c; /* coefficients */ int order; /* order of expansion */ double a; /* lower interval point */ double b; /* upper interval point */ int order_sp; /* effective single precision order */ }; typedef struct cheb_series_struct cheb_series; sources_5316/external/gsl/gsl_ieee-utils__fp-sunos4.c0000664000176700017670000000631211723710247021475 0ustar paulpaul/* ieee-utils/fp-sunos4.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { char * out ; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: ieee_flags ("set", "precision", "single", out) ; break ; case GSL_IEEE_DOUBLE_PRECISION: ieee_flags ("set", "precision", "double", out) ; break ; case GSL_IEEE_EXTENDED_PRECISION: ieee_flags ("set", "precision", "extended", out) ; break ; default: ieee_flags ("set", "precision", "extended", out) ; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: ieee_flags ("set", "direction", "nearest", out) ; break ; case GSL_IEEE_ROUND_DOWN: ieee_flags ("set", "direction", "negative", out) ; break ; case GSL_IEEE_ROUND_UP: ieee_flags ("set", "direction", "positive", out) ; break ; case GSL_IEEE_ROUND_TO_ZERO: ieee_flags ("set", "direction", "tozero", out) ; break ; default: ieee_flags ("set", "direction", "nearest", out) ; } if (exception_mask & GSL_IEEE_MASK_INVALID) { ieee_handler ("set", "invalid", SIGFPE_IGNORE) ; } else { ieee_handler ("set", "invalid", SIGFPE_ABORT) ; } if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { ieee_handler ("set", "denormalized", SIGFPE_IGNORE) ; } else { GSL_ERROR ("sunos4 does not support the denormalized operand exception. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP) ; } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) { ieee_handler ("set", "division", SIGFPE_IGNORE) ; } else { ieee_handler ("set", "division", SIGFPE_ABORT) ; } if (exception_mask & GSL_IEEE_MASK_OVERFLOW) { ieee_handler ("set", "overflow", SIGFPE_IGNORE) ; } else { ieee_handler ("set", "overflow", SIGFPE_ABORT) ; } if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) { ieee_handler ("set", "underflow", SIGFPE_IGNORE) ; } else { ieee_handler ("set", "underflow", SIGFPE_ABORT) ; } if (exception_mask & GSL_IEEE_TRAP_INEXACT) { ieee_handler ("set", "inexact", SIGFPE_ABORT) ; } else { ieee_handler ("set", "inexact", SIGFPE_IGNORE) ; } return GSL_SUCCESS ; } sources_5316/external/gsl/gsl_cblas__drotg.c0000664000176700017670000000032211723710247017770 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_drotg (double *a, double *b, double *c, double *s) { #define BASE double #include "gsl_cblas__source_rotg.h" #undef BASE } sources_5316/external/gsl/gsl_min__brent.c0000664000176700017670000001172011723710247017466 0ustar paulpaul/* min/brent.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* brent.c -- brent minimum finding algorithm */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_min.h" #include "gsl_min__min.h" typedef struct { double d, e, v, w; double f_v, f_w; } brent_state_t; static int brent_init (void *vstate, gsl_function * f, double x_minimum, double f_minimum, double x_lower, double f_lower, double x_upper, double f_upper); static int brent_iterate (void *vstate, gsl_function * f, double *x_minimum, double * f_minimum, double * x_lower, double * f_lower, double * x_upper, double * f_upper); static int brent_init (void *vstate, gsl_function * f, double x_minimum, double f_minimum, double x_lower, double f_lower, double x_upper, double f_upper) { brent_state_t *state = (brent_state_t *) vstate; const double golden = 0.3819660; /* golden = (3 - sqrt(5))/2 */ double v = x_lower + golden * (x_upper - x_lower); double w = v; double f_vw; x_minimum = 0 ; /* avoid warnings about unused varibles */ f_minimum = 0 ; f_lower = 0 ; f_upper = 0 ; state->v = v; state->w = w; state->d = 0; state->e = 0; SAFE_FUNC_CALL (f, v, &f_vw); state->f_v = f_vw; state->f_w = f_vw; return GSL_SUCCESS; } static int brent_iterate (void *vstate, gsl_function * f, double *x_minimum, double * f_minimum, double * x_lower, double * f_lower, double * x_upper, double * f_upper) { brent_state_t *state = (brent_state_t *) vstate; const double x_left = *x_lower; const double x_right = *x_upper; const double z = *x_minimum; double d = state->e; double e = state->d; double u, f_u; const double v = state->v; const double w = state->w; const double f_v = state->f_v; const double f_w = state->f_w; const double f_z = *f_minimum; const double golden = 0.3819660; /* golden = (3 - sqrt(5))/2 */ const double w_lower = (z - x_left); const double w_upper = (x_right - z); const double tolerance = GSL_SQRT_DBL_EPSILON * fabs (z); double p = 0, q = 0, r = 0; const double midpoint = 0.5 * (x_left + x_right); if (fabs (e) > tolerance) { /* fit parabola */ r = (z - w) * (f_z - f_v); q = (z - v) * (f_z - f_w); p = (z - v) * q - (z - w) * r; q = 2 * (q - r); if (q > 0) { p = -p; } else { q = -q; } r = e; e = d; } if (fabs (p) < fabs (0.5 * q * r) && p < q * w_lower && p < q * w_upper) { double t2 = 2 * tolerance ; d = p / q; u = z + d; if ((u - x_left) < t2 || (x_right - u) < t2) { d = (z < midpoint) ? tolerance : -tolerance ; } } else { e = (z < midpoint) ? x_right - z : -(z - x_left) ; d = golden * e; } if (fabs (d) >= tolerance) { u = z + d; } else { u = z + ((d > 0) ? tolerance : -tolerance) ; } state->e = e; state->d = d; SAFE_FUNC_CALL(f, u, &f_u); if (f_u <= f_z) { if (u < z) { *x_upper = z; *f_upper = f_z; } else { *x_lower = z; *f_lower = f_z; } state->v = w; state->f_v = f_w; state->w = z; state->f_w = f_z; *x_minimum = u; *f_minimum = f_u; return GSL_SUCCESS; } else { if (u < z) { *x_lower = u; *f_lower = f_u; return GSL_SUCCESS; } else { *x_upper = u; *f_upper = f_u; return GSL_SUCCESS; } if (f_u <= f_w || w == z) { state->v = w; state->f_v = f_w; state->w = u; state->f_w = f_u; return GSL_SUCCESS; } else if (f_u <= f_v || v == z || v == w) { state->v = u; state->f_v = f_u; return GSL_SUCCESS; } } return GSL_FAILURE; } static const gsl_min_fminimizer_type brent_type = {"brent", /* name */ sizeof (brent_state_t), &brent_init, &brent_iterate}; const gsl_min_fminimizer_type *gsl_min_fminimizer_brent = &brent_type; sources_5316/external/gsl/gsl_specfunc__airy_zero.c0000664000176700017670000003253211723710247021406 0ustar paulpaul/* specfunc/airy_zero.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_airy.h" #include "gsl_specfunc__error.h" static const double zero_Ai[] = { 0, -2.338107410459767039, -4.087949444130970617, -5.520559828095551059, -6.786708090071758999, -7.944133587120853123, -9.022650853340980380, -10.04017434155808593, -11.00852430373326289, -11.93601556323626252, -12.82877675286575720, -13.69148903521071793, -14.52782995177533498, -15.34075513597799686, -16.13268515694577144, -16.90563399742994263, -17.661300105697057509, -18.401132599207115416, -19.126380474246952144, -19.838129891721499701, -20.537332907677566360, -21.224829943642096955, -21.901367595585130707, -22.567612917496502831, -23.224165001121681061, -23.871564455535918567, -24.510301236589677490, -25.140821166148963748, -25.763531400982756459, -26.378805052137232374, -26.986985111606367686, -27.588387809882444812, -28.183305502632644923, -28.772009165237435382, -29.354750558766287963, -29.931764119086555913, -30.503268611418505287, -31.069468585183755604, -31.63055565801265934, -32.18670965295205069, -32.73809960900026913, -33.28488468190140188, -33.82721494950865194, -34.36523213386365906, -34.89907025034531210, -35.42885619274788846, -35.95471026189862926, -36.47674664437480896, -36.99507384699450161, -37.50979509200501613, -38.02100867725525443, -38.52880830509424882, -39.03328338327251391, -39.53451930072301805, -40.03259768075417603, -40.52759661388971821, -41.01959087233248966, -41.50865210780525018, -41.99484903432643004, -42.47824759730839188, -42.95891113021656009, -43.43690049989685412, -43.91227424156370168, -44.38508868433939023, -44.85539806814583243, -45.32325465267043011, -45.78870881905730086, -46.25180916491254629, -46.71260259315651633, -47.17113439520631705, -47.62744832892739292, -48.08158669175325711, -48.53359038933679845, -48.98349900006458366, -49.43135083573678341, -49.87718299868941729, -50.32103143561221860, -50.76293098829428522, -51.20291544151056412, -51.64101756824489758, -52.07726917242964943, -52.51170112936766183, -52.94434342398931824, -53.37522518708567514, -53.80437472964785717, -54.23181957543308298, -54.65758649186871111, -55.08170151939748312, -55.50418999935962251, -55.92507660050055598, -56.34438534418670066, -56.76213962840595327, -57.17836225062417808, -57.59307542956407782, -58.00630082596830627, -58.41805956240450934, -58.82837224216613231, -59.23725896731927534, -59.64473935594259360, -60.05083255860419805, -60.45555727411669871 }; static const size_t size_zero_Ai = sizeof(zero_Ai)/sizeof(double); static const double zero_Bi[] = { 0, -1.173713222709127925, -3.271093302836352716, -4.830737841662015933, -6.169852128310251260, -7.376762079367763714, -8.491948846509388013, -9.538194379346238887, -10.52991350670535792, -11.47695355127877944, -12.38641713858273875, -13.26363952294180555, -14.11275680906865779, -14.93705741215416404, -15.739210351190482771, -16.521419550634379054, -17.285531624581242533, -18.033113287225001572, -18.765508284480081041, -19.483880132989234014, -20.189244785396202420, -20.882495994193175768, -21.564425284712977653, -22.235737881803385167, -22.897065554219793474, -23.548977079642448269, -24.191986850649000086, -24.826562012152892172, -25.453128427085131994, -26.072075698466804494, -26.683761425120990449, -27.288514830076298204, -27.886639871735962459, -28.478417925678661737, -29.064110107777650305, -29.643959295918396591, -30.218191897047274645, -30.787019397921766297, -31.350639731255585371, -31.90923848358456965, -32.46298996683685318, -33.01205817205683814, -33.55659762084006113, -34.09675412765602851, -34.63266548426775468, -35.16446207582101720, -35.69226743681080479, -36.21619875398748222, -36.73636732230120657, -37.25287895916828697, -37.76583438165180116, -38.27532955056003997, -38.78145598496327279, -39.28430105019802461, -39.78394822205711298, -40.28047732954369150, -40.77396477829068148, -41.26448375650675678, -41.75210442510106287, -42.23689409345656643, -42.71891738216253539, -43.19823637387693118, -43.67491075336673948, -44.14899793766617113, -44.62055319719727274, -45.08962976861312825, -45.55627896004907928, -46.02055024940102076, -46.48249137619078661, -46.94214842752602207, -47.39956591861496210, -47.85478686825452176, -48.30785286967246692, -48.75880415707066192, -49.20767966818603897, -49.65451710315861501, -50.09935297997125482, -50.54222268670364757, -50.98316053082286586, -51.42219978571468262, -51.85937273464332870, -52.29471071231240525, -52.72824414418606069, -53.16000258371716397, -53.59001474761792882, -54.01830854929815828, -54.44491113058688729, -54.86984889184461534, -55.29314752056546491, -55.71483201856140365, -56.13492672781406761, -56.55345535507366411, -56.97044099527886475, -57.38590615386647834, -57.79987276803497897, -58.21236222702161974, -58.62339539144885603, -59.03299261179210306, -59.44117374601743460, -59.84795817643466996, -60.25336482580837088 }; static const size_t size_zero_Bi = sizeof(zero_Bi)/sizeof(double); static const double zero_Aip[] = { 0, -1.018792971647471089, -3.248197582179836738, -4.820099211178735639, -6.163307355639486822, -7.372177255047770177, -8.488486734019722133, -9.535449052433547471, -10.52766039695740728, -11.47505663348024529, -12.384788371845747325, -13.262218961665210382, -14.111501970462995282, -14.935937196720517467, -15.738201373692538303, -16.520503825433793542, -17.284695050216437357, -18.032344622504393395, -18.764798437665954740, -19.483221656567231178, -20.188631509463373154, -20.881922755516737701, -21.563887723198974958, -22.235232285348913331, -22.896588738874619001, -23.548526295928801574, -24.191559709526353841, -24.826156425921155001, -25.452742561777649948, -26.071707935173912515, -26.683410328322449767, -27.288179121523985029, -27.886318408768461192, -28.478109683102278108, -29.063814162638199090, -29.643674814632015921, -30.217918124468574603, -30.786755648012502519, -31.350385379083034671, -31.90899295843046320, -32.46275274623847982, -33.01182877663428709, -33.55637560978942190, -34.09653909480913771, -34.63245705463586589, -35.16425990255340758, -35.69207119851046870, -36.21600815233519918, -36.73618207994680321, -37.25269881785414827, -37.76565910053887108, -38.27515890473087933, -38.78128976408036876, -39.28413905729859644, -39.78379027246823278, -40.28032324990371935, -40.77381440566486637, -41.26433693758643383, -41.75196101547722703, -42.23675395695976012, -42.71878039026198233, -43.19810240513270670, -43.67477969292950869, -44.14886967681966886, -44.62042763293925724, -45.08950680327102630, -45.55615850092696446, -46.02043220845493728, -46.48237566972975615, -46.94203497593635633, -47.39945464610575493, -47.85467770262241617, -48.30774574208398774, -48.75869900186057804, -49.20757642267037247, -49.65441570746105074, -50.09925337686182515, -50.54212482144867502, -50.98306435104524282, -51.42210524126365311, -51.85927977747301469, -52.29461929636838876, -52.72815422529939506, -53.15991411950524351, -53.58992769739169611, -54.01822287397517367, -54.44482679260982599, -54.86976585510479430, -55.29306575033103518, -55.71475148140987392, -56.13484739156885235, -56.55337718874437424, -56.97036396900508167, -57.38583023886477265, -57.79979793654895377, -58.21228845227477578, -58.62332264760009139, -59.03292087389367419, -59.44110298997521892, -59.84788837897058171, -60.25329596442479317 }; static const size_t size_zero_Aip = sizeof(zero_Aip)/sizeof(double); static const double zero_Bip[] = { 0, -2.294439682614123247, -4.073155089071828216, -5.512395729663599496, -6.781294445990305390, -7.940178689168578927, -9.019583358794239067, -10.037696334908545802, -11.006462667712289940, -11.934261645014844663, -12.827258309177217640, -13.690155826835049101, -14.526645763485711410, -15.339693082242404109, -16.131724782385900578, -16.904759411889649958, -17.660498743114976102, -18.400394367181703280, -19.125697156412638066, -19.837494718415910503, -20.536740241453273980, -21.224275044889266569, -21.900846445139208281, -22.567122080497200470, -23.223701521208962116, -23.871125771677973595, -24.509885117016242729, -25.140425655367878908, -25.763154776913454319, -26.378445791146615697, -26.986641859775034987, -27.588059359225600573, -28.182990771292975456, -28.771707180886056250, -29.354460444612957224, -29.931485082026055160, -30.502999931936645516, -31.069209608721234058, -31.63030578754333679, -32.18646834257807369, -32.73786635840274752, -33.28465903151424981, -33.82699647630635587, -34.36502044767239631, -34.89886499060196419, -35.42865702564380962, -35.95451687785511190, -36.47655875580547918, -36.99489118631672770, -37.50961740986809593, -38.02083574095788210 }; static const size_t size_zero_Bip = sizeof(zero_Bip)/sizeof(double); /* [Abramowitz+Stegun, 10.4.105] */ static double zero_f(double z) { const double pre = pow(z, 2.0/3.0); const double zi2 = 1.0/(z*z); const double zi4 = zi2 * zi2; const double t1 = 5.0/48.0 * zi2; const double t2 = -5.0/36.0 * zi4; const double t3 = 77125.0/82944.0 * zi4 * zi2; const double t4 = -108056875.0/6967296.0 * zi4 * zi4; return pre * (1.0 + t1 + t2 + t3 + t4); } static double zero_g(double z) { const double pre = pow(z, 2.0/3.0); const double zi2 = 1.0/(z*z); const double zi4 = zi2 * zi2; const double t1 = -7.0/48.0 * zi2; const double t2 = 35.0/288.0 * zi4; const double t3 = -181223.0/207360.0 * zi4 * zi2; const double t4 = 18683371.0/1244160.0 * zi4 * zi4; return pre * (1.0 + t1 + t2 + t3 + t4); } int gsl_sf_airy_zero_Ai_e(unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s < 1) { DOMAIN_ERROR_MSG("s is less than 1", result); } else if(s < size_zero_Ai) { result->val = zero_Ai[s]; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double z = 3.0*M_PI/8.0 * (4.0*s - 1.0); const double f = zero_f(z); result->val = -f; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_airy_zero_Bi_e(unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s < 1) { DOMAIN_ERROR_MSG("s is less than 1", result); } else if(s < size_zero_Bi) { result->val = zero_Bi[s]; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double z = 3.0*M_PI/8.0 * (4.0*s - 3.0); const double f = zero_f(z); result->val = -f; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_airy_zero_Ai_deriv_e(unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s < 1) { DOMAIN_ERROR_MSG("s is less than 1", result); } else if(s < size_zero_Aip) { result->val = zero_Aip[s]; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double z = 3.0*M_PI/8.0 * (4.0*s - 3.0); const double g = zero_g(z); result->val = -g; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_airy_zero_Bi_deriv_e(unsigned int s, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(s < 1) { DOMAIN_ERROR_MSG("s is less than 1", result); } else if(s < size_zero_Bip) { result->val = zero_Bip[s]; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double z = 3.0*M_PI/8.0 * (4.0*s - 1.0); const double g = zero_g(z); result->val = -g; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_airy_zero_Ai(unsigned int s) { EVAL_RESULT(gsl_sf_airy_zero_Ai_e(s, &result)); } double gsl_sf_airy_zero_Bi(unsigned int s) { EVAL_RESULT(gsl_sf_airy_zero_Bi_e(s, &result)); } double gsl_sf_airy_zero_Ai_deriv(unsigned int s) { EVAL_RESULT(gsl_sf_airy_zero_Ai_deriv_e(s, &result)); } double gsl_sf_airy_zero_Bi_deriv(unsigned int s) { EVAL_RESULT(gsl_sf_airy_zero_Bi_deriv_e(s, &result)); } sources_5316/external/gsl/gsl_sys__fcmp.c0000664000176700017670000000321011723710247017327 0ustar paulpaul/* sys/gsl_compare.c * * Copyright (C) 2002 Gert Van den Eynde * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * * Based on fcmp 1.2.2 Copyright (c) 1998-2000 Theodore C. Belding * University of Michigan Center for the Study of Complex Systems * Ted.Belding@umich.edu * */ #include "gsl__config.h" #include "gsl_sys.h" #include int gsl_fcmp (const double x1, const double x2, const double epsilon) { int exponent; double delta, difference; /* Find exponent of largest absolute value */ { double max = (fabs (x1) > fabs (x2)) ? x1 : x2; frexp (max, &exponent); } /* Form a neighborhood of size 2 * delta */ delta = ldexp (epsilon, exponent); difference = x1 - x2; if (difference > delta) /* x1 > x2 */ { return 1; } else if (difference < -delta) /* x1 < x2 */ { return -1; } else /* -delta <= difference <= delta */ { return 0; /* x1 ~=~ x2 */ } } sources_5316/external/gsl/gsl_vector__file_source.c0000664000176700017670000000443411723710247021376 0ustar paulpaul/* vector/file_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION (gsl_vector, fread) (FILE * stream, TYPE (gsl_vector) * v) { int status = FUNCTION (gsl_block, raw_fread) (stream, v->data, v->size, v->stride); return status; } int FUNCTION (gsl_vector, fwrite) (FILE * stream, const TYPE (gsl_vector) * v) { int status = FUNCTION (gsl_block, raw_fwrite) (stream, v->data, v->size, v->stride); return status; } #if !(USES_LONGDOUBLE && !HAVE_PRINTF_LONGDOUBLE) int FUNCTION (gsl_vector, fprintf) (FILE * stream, const TYPE (gsl_vector) * v, const char *format) { int status = FUNCTION (gsl_block, raw_fprintf) (stream, v->data, v->size, v->stride, format); return status; } int FUNCTION (gsl_vector, fscanf) (FILE * stream, TYPE (gsl_vector) * v) { int status = FUNCTION (gsl_block, raw_fscanf) (stream, v->data, v->size, v->stride); return status; } #endif sources_5316/external/gsl/gsl_fft__hc_pass_5.c0000664000176700017670000002275511723710247020226 0ustar paulpaul/* fft/hc_pass_5.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_halfcomplex,pass_5) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[]) { size_t i, j, k, k1, jump; size_t factor, q, m, product_1; const ATOMIC sina = sin (2.0 * M_PI / 5.0); const ATOMIC sinb = sin (2.0 * M_PI / 10.0); i = 0; j = 0; factor = 5; m = n / factor; q = n / product; product_1 = product / factor; jump = (factor - 1) * q; for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 5 * k1 * q; const size_t from1 = from0 + 2 * q - 1; const size_t from2 = from1 + 2 * q; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC z2_imag = VECTOR(in,istride,from2 + 1); const ATOMIC t1_real = 2 * (z1_real + z2_real); const ATOMIC t2_real = 2 * (sqrt (5.0) / 4.0) * (z1_real - z2_real); const ATOMIC t3_real = z0_real - t1_real / 4.0; const ATOMIC t4_real = t2_real + t3_real; const ATOMIC t5_real = -t2_real + t3_real; const ATOMIC t6_imag = 2 * (sina * z1_imag + sinb * z2_imag); const ATOMIC t7_imag = 2 * (sinb * z1_imag - sina * z2_imag); const ATOMIC x0_real = z0_real + t1_real; const ATOMIC x1_real = t4_real - t6_imag; const ATOMIC x2_real = t5_real - t7_imag; const ATOMIC x3_real = t5_real + t7_imag; const ATOMIC x4_real = t4_real + t6_imag; const size_t to0 = q * k1; const size_t to1 = to0 + m; const size_t to2 = to1 + m; const size_t to3 = to2 + m; const size_t to4 = to3 + m; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to2) = x2_real; VECTOR(out,ostride,to3) = x3_real; VECTOR(out,ostride,to4) = x4_real; } if (q == 1) return; for (k = 1; k < (q + 1) / 2; k++) { const ATOMIC w1_real = GSL_REAL(twiddle1[k - 1]); const ATOMIC w1_imag = GSL_IMAG(twiddle1[k - 1]); const ATOMIC w2_real = GSL_REAL(twiddle2[k - 1]); const ATOMIC w2_imag = GSL_IMAG(twiddle2[k - 1]); const ATOMIC w3_real = GSL_REAL(twiddle3[k - 1]); const ATOMIC w3_imag = GSL_IMAG(twiddle3[k - 1]); const ATOMIC w4_real = GSL_REAL(twiddle4[k - 1]); const ATOMIC w4_imag = GSL_IMAG(twiddle4[k - 1]); for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 5 * k1 * q + 2 * k - 1; const size_t from1 = from0 + 2 * q; const size_t from2 = from1 + 2 * q; const size_t from3 = 5 * k1 * q - 2 * k + 2 * q - 1; const size_t from4 = from3 + 2 * q; const ATOMIC z0_real = VECTOR(in,istride,from0); const ATOMIC z0_imag = VECTOR(in,istride,from0 + 1); const ATOMIC z1_real = VECTOR(in,istride,from1); const ATOMIC z1_imag = VECTOR(in,istride,from1 + 1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC z2_imag = VECTOR(in,istride,from2 + 1); const ATOMIC z3_real = VECTOR(in,istride,from4); const ATOMIC z3_imag = -VECTOR(in,istride,from4 + 1); const ATOMIC z4_real = VECTOR(in,istride,from3); const ATOMIC z4_imag = -VECTOR(in,istride,from3 + 1); /* compute x = W(5) z */ /* t1 = z1 + z4 */ const ATOMIC t1_real = z1_real + z4_real; const ATOMIC t1_imag = z1_imag + z4_imag; /* t2 = z2 + z3 */ const ATOMIC t2_real = z2_real + z3_real; const ATOMIC t2_imag = z2_imag + z3_imag; /* t3 = z1 - z4 */ const ATOMIC t3_real = z1_real - z4_real; const ATOMIC t3_imag = z1_imag - z4_imag; /* t4 = z2 - z3 */ const ATOMIC t4_real = z2_real - z3_real; const ATOMIC t4_imag = z2_imag - z3_imag; /* t5 = t1 + t2 */ const ATOMIC t5_real = t1_real + t2_real; const ATOMIC t5_imag = t1_imag + t2_imag; /* t6 = (sqrt(5)/4)(t1 - t2) */ const ATOMIC t6_real = (sqrt (5.0) / 4.0) * (t1_real - t2_real); const ATOMIC t6_imag = (sqrt (5.0) / 4.0) * (t1_imag - t2_imag); /* t7 = z0 - ((t5)/4) */ const ATOMIC t7_real = z0_real - t5_real / 4.0; const ATOMIC t7_imag = z0_imag - t5_imag / 4.0; /* t8 = t7 + t6 */ const ATOMIC t8_real = t7_real + t6_real; const ATOMIC t8_imag = t7_imag + t6_imag; /* t9 = t7 - t6 */ const ATOMIC t9_real = t7_real - t6_real; const ATOMIC t9_imag = t7_imag - t6_imag; /* t10 = sin(2 pi/5) t3 + sin(2 pi/10) t4 */ const ATOMIC t10_real = sina * t3_real + sinb * t4_real; const ATOMIC t10_imag = sina * t3_imag + sinb * t4_imag; /* t11 = sin(2 pi/10) t3 - sin(2 pi/5) t4 */ const ATOMIC t11_real = sinb * t3_real - sina * t4_real; const ATOMIC t11_imag = sinb * t3_imag - sina * t4_imag; /* x0 = z0 + t5 */ const ATOMIC x0_real = z0_real + t5_real; const ATOMIC x0_imag = z0_imag + t5_imag; /* x1 = t8 + i t10 */ const ATOMIC x1_real = t8_real - t10_imag; const ATOMIC x1_imag = t8_imag + t10_real; /* x2 = t9 + i t11 */ const ATOMIC x2_real = t9_real - t11_imag; const ATOMIC x2_imag = t9_imag + t11_real; /* x3 = t9 - i t11 */ const ATOMIC x3_real = t9_real + t11_imag; const ATOMIC x3_imag = t9_imag - t11_real; /* x4 = t8 - i t10 */ const ATOMIC x4_real = t8_real + t10_imag; const ATOMIC x4_imag = t8_imag - t10_real; const size_t to0 = k1 * q + 2 * k - 1; const size_t to1 = to0 + m; const size_t to2 = to1 + m; const size_t to3 = to2 + m; const size_t to4 = to3 + m; /* apply twiddle factors */ /* to0 = 1 * x0 */ VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to0 + 1) = x0_imag; /* to1 = w1 * x1 */ VECTOR(out,ostride,to1) = w1_real * x1_real - w1_imag * x1_imag; VECTOR(out,ostride,to1 + 1) = w1_real * x1_imag + w1_imag * x1_real; /* to2 = w2 * x2 */ VECTOR(out,ostride,to2) = w2_real * x2_real - w2_imag * x2_imag; VECTOR(out,ostride,to2 + 1) = w2_real * x2_imag + w2_imag * x2_real; /* to3 = w3 * x3 */ VECTOR(out,ostride,to3) = w3_real * x3_real - w3_imag * x3_imag; VECTOR(out,ostride,to3 + 1) = w3_real * x3_imag + w3_imag * x3_real; /* to4 = w4 * x4 */ VECTOR(out,ostride,to4) = w4_real * x4_real - w4_imag * x4_imag; VECTOR(out,ostride,to4 + 1) = w4_real * x4_imag + w4_imag * x4_real; } } if (q % 2 == 1) return; for (k1 = 0; k1 < product_1; k1++) { const size_t from0 = 5 * k1 * q + q - 1; const size_t from1 = from0 + 2 * q; const size_t from2 = from1 + 2 * q; const ATOMIC z0_real = 2 * VECTOR(in,istride,from0); const ATOMIC z0_imag = 2 * VECTOR(in,istride,from0 + 1); const ATOMIC z1_real = 2 * VECTOR(in,istride,from1); const ATOMIC z1_imag = 2 * VECTOR(in,istride,from1 + 1); const ATOMIC z2_real = VECTOR(in,istride,from2); const ATOMIC t1_real = z0_real + z1_real; const ATOMIC t2_real = (t1_real / 4.0) - z2_real; const ATOMIC t3_real = (sqrt (5.0) / 4.0) * (z0_real - z1_real); const ATOMIC t4_real = sinb * z0_imag + sina * z1_imag; const ATOMIC t5_real = sina * z0_imag - sinb * z1_imag; const ATOMIC t6_real = t3_real + t2_real; const ATOMIC t7_real = t3_real - t2_real; const ATOMIC x0_real = t1_real + z2_real; const ATOMIC x1_real = t6_real - t4_real; const ATOMIC x2_real = t7_real - t5_real; const ATOMIC x3_real = -t7_real - t5_real; const ATOMIC x4_real = -t6_real - t4_real; const size_t to0 = k1 * q + q - 1; const size_t to1 = to0 + m; const size_t to2 = to1 + m; const size_t to3 = to2 + m; const size_t to4 = to3 + m; VECTOR(out,ostride,to0) = x0_real; VECTOR(out,ostride,to1) = x1_real; VECTOR(out,ostride,to2) = x2_real; VECTOR(out,ostride,to3) = x3_real; VECTOR(out,ostride,to4) = x4_real; } return; } sources_5316/external/gsl/gsl_cdf__logistic.c0000664000176700017670000000244611723710247020147 0ustar paulpaul/* cdf/logistic.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_logistic_P (const double x, const double a) { double P; double u = x / a; if (u >= 0) { P = 1 / (1 + exp (-u)); } else { P = exp (u) / (1 + exp (u)); } return P; } double gsl_cdf_logistic_Q (const double x, const double a) { double Q; double u = x / a; if (u >= 0) { Q = exp (-u) / (1 + exp (-u)); } else { Q = 1 / (1 + exp (u)); } return Q; } sources_5316/external/gsl/gsl_vector_long_double.h0000664000176700017670000001763411705263724021247 0ustar paulpaul/* vector/gsl_vector_long_double.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_VECTOR_LONG_DOUBLE_H__ #define __GSL_VECTOR_LONG_DOUBLE_H__ #include #include "gsl_types.h" #include "gsl_errno.h" #include "gsl_check_range.h" #include "gsl_block_long_double.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS typedef struct { size_t size; size_t stride; long double *data; gsl_block_long_double *block; int owner; } gsl_vector_long_double; typedef struct { gsl_vector_long_double vector; } _gsl_vector_long_double_view; typedef _gsl_vector_long_double_view gsl_vector_long_double_view; typedef struct { gsl_vector_long_double vector; } _gsl_vector_long_double_const_view; typedef const _gsl_vector_long_double_const_view gsl_vector_long_double_const_view; /* Allocation */ gsl_vector_long_double *gsl_vector_long_double_alloc (const size_t n); gsl_vector_long_double *gsl_vector_long_double_calloc (const size_t n); gsl_vector_long_double *gsl_vector_long_double_alloc_from_block (gsl_block_long_double * b, const size_t offset, const size_t n, const size_t stride); gsl_vector_long_double *gsl_vector_long_double_alloc_from_vector (gsl_vector_long_double * v, const size_t offset, const size_t n, const size_t stride); void gsl_vector_long_double_free (gsl_vector_long_double * v); /* Views */ _gsl_vector_long_double_view gsl_vector_long_double_view_array (long double *v, size_t n); _gsl_vector_long_double_view gsl_vector_long_double_view_array_with_stride (long double *base, size_t stride, size_t n); _gsl_vector_long_double_const_view gsl_vector_long_double_const_view_array (const long double *v, size_t n); _gsl_vector_long_double_const_view gsl_vector_long_double_const_view_array_with_stride (const long double *base, size_t stride, size_t n); _gsl_vector_long_double_view gsl_vector_long_double_subvector (gsl_vector_long_double *v, size_t i, size_t n); _gsl_vector_long_double_view gsl_vector_long_double_subvector_with_stride (gsl_vector_long_double *v, size_t i, size_t stride, size_t n); _gsl_vector_long_double_const_view gsl_vector_long_double_const_subvector (const gsl_vector_long_double *v, size_t i, size_t n); _gsl_vector_long_double_const_view gsl_vector_long_double_const_subvector_with_stride (const gsl_vector_long_double *v, size_t i, size_t stride, size_t n); /* Operations */ long double gsl_vector_long_double_get (const gsl_vector_long_double * v, const size_t i); void gsl_vector_long_double_set (gsl_vector_long_double * v, const size_t i, long double x); long double *gsl_vector_long_double_ptr (gsl_vector_long_double * v, const size_t i); const long double *gsl_vector_long_double_const_ptr (const gsl_vector_long_double * v, const size_t i); void gsl_vector_long_double_set_zero (gsl_vector_long_double * v); void gsl_vector_long_double_set_all (gsl_vector_long_double * v, long double x); int gsl_vector_long_double_set_basis (gsl_vector_long_double * v, size_t i); int gsl_vector_long_double_fread (FILE * stream, gsl_vector_long_double * v); int gsl_vector_long_double_fwrite (FILE * stream, const gsl_vector_long_double * v); int gsl_vector_long_double_fscanf (FILE * stream, gsl_vector_long_double * v); int gsl_vector_long_double_fprintf (FILE * stream, const gsl_vector_long_double * v, const char *format); int gsl_vector_long_double_memcpy (gsl_vector_long_double * dest, const gsl_vector_long_double * src); int gsl_vector_long_double_reverse (gsl_vector_long_double * v); int gsl_vector_long_double_swap (gsl_vector_long_double * v, gsl_vector_long_double * w); int gsl_vector_long_double_swap_elements (gsl_vector_long_double * v, const size_t i, const size_t j); long double gsl_vector_long_double_max (const gsl_vector_long_double * v); long double gsl_vector_long_double_min (const gsl_vector_long_double * v); void gsl_vector_long_double_minmax (const gsl_vector_long_double * v, long double * min_out, long double * max_out); size_t gsl_vector_long_double_max_index (const gsl_vector_long_double * v); size_t gsl_vector_long_double_min_index (const gsl_vector_long_double * v); void gsl_vector_long_double_minmax_index (const gsl_vector_long_double * v, size_t * imin, size_t * imax); int gsl_vector_long_double_add (gsl_vector_long_double * a, const gsl_vector_long_double * b); int gsl_vector_long_double_sub (gsl_vector_long_double * a, const gsl_vector_long_double * b); int gsl_vector_long_double_mul (gsl_vector_long_double * a, const gsl_vector_long_double * b); int gsl_vector_long_double_div (gsl_vector_long_double * a, const gsl_vector_long_double * b); int gsl_vector_long_double_scale (gsl_vector_long_double * a, const double x); int gsl_vector_long_double_add_constant (gsl_vector_long_double * a, const double x); int gsl_vector_long_double_isnull (const gsl_vector_long_double * v); int gsl_vector_long_double_ispos (const gsl_vector_long_double * v); int gsl_vector_long_double_isneg (const gsl_vector_long_double * v); int gsl_vector_long_double_isnonneg (const gsl_vector_long_double * v); #ifdef HAVE_INLINE extern inline long double gsl_vector_long_double_get (const gsl_vector_long_double * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VAL ("index out of range", GSL_EINVAL, 0); } #endif return v->data[i * v->stride]; } extern inline void gsl_vector_long_double_set (gsl_vector_long_double * v, const size_t i, long double x) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_VOID ("index out of range", GSL_EINVAL); } #endif v->data[i * v->stride] = x; } extern inline long double * gsl_vector_long_double_ptr (gsl_vector_long_double * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (long double *) (v->data + i * v->stride); } extern inline const long double * gsl_vector_long_double_const_ptr (const gsl_vector_long_double * v, const size_t i) { #if GSL_RANGE_CHECK if (i >= v->size) { GSL_ERROR_NULL ("index out of range", GSL_EINVAL); } #endif return (const long double *) (v->data + i * v->stride); } #endif /* HAVE_INLINE */ __END_DECLS #endif /* __GSL_VECTOR_LONG_DOUBLE_H__ */ sources_5316/external/gsl/gsl_rng__r250.c0000664000176700017670000001132511723710247017050 0ustar paulpaul/* rng/r250.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is a shift-register random number generator. The sequence is x_n = x_{n-103} ^ x_{n-250} ("^" means XOR) defined on 32-bit words. BJG: Note that this implementation actually uses the sequence, x_n = x_{n-147} ^ x_{n-250} which generates the outputs in time-reversed order but is otherwise completely equivalent. The first 250 elements x_1 .. x_250 are first initialized as x_n = s_n, where s_n = (69069*s_{n-1}) mod 2^32 and s_0=s is the user-supplied seed. To ensure that the sequence does not lie on a subspace we force 32 of the entries to be linearly independent. We take the 32 elements x[3], x[10], x[17], x[24], ..., 213 and apply the following operations, x[3] &= 11111111111111111111111111111111 x[3] |= 10000000000000000000000000000000 x[10] &= 01111111111111111111111111111111 x[10] |= 01000000000000000000000000000000 x[17] &= 00111111111111111111111111111111 x[17] |= 00100000000000000000000000000000 .... ... x[206] &= 00000000000000000000000000000111 x[206] |= 00000000000000000000000000000100 x[213] &= 00000000000000000000000000000011 x[213] |= 00000000000000000000000000000010 x[220] &= 00000000000000000000000000000001 x[220] |= 00000000000000000000000000000001 i.e. if we consider the bits of the 32 elements as forming a 32x32 array then we are setting the diagonal bits of the array to one and masking the lower triangle below the diagonal to zero. With this initialization procedure the theoretical value of x_{10001} is 1100653588 for s = 1 (Actually I got this by running the original code). The subscript 10001 means (1) seed the generator with s = 1 and then do 10000 actual iterations. The period of this generator is about 2^250. The algorithm works for any number of bits. It is implemented here for 32 bits. From: S. Kirkpatrick and E. Stoll, "A very fast shift-register sequence random number generator", Journal of Computational Physics, 40, 517-526 (1981). */ static inline unsigned long int r250_get (void *vstate); static double r250_get_double (void *vstate); static void r250_set (void *state, unsigned long int s); typedef struct { int i; unsigned long x[250]; } r250_state_t; static inline unsigned long int r250_get (void *vstate) { r250_state_t *state = (r250_state_t *) vstate; unsigned long int k; int j; int i = state->i; if (i >= 147) { j = i - 147; } else { j = i + 103; } k = state->x[i] ^ state->x[j]; state->x[i] = k; if (i >= 249) { state->i = 0; } else { state->i = i + 1; } return k; } static double r250_get_double (void *vstate) { return r250_get (vstate) / 4294967296.0 ; } static void r250_set (void *vstate, unsigned long int s) { r250_state_t *state = (r250_state_t *) vstate; int i; if (s == 0) s = 1; /* default seed is 1 */ state->i = 0; #define LCG(n) ((69069 * n) & 0xffffffffUL) for (i = 0; i < 250; i++) /* Fill the buffer */ { s = LCG (s); state->x[i] = s; } { /* Masks for turning on the diagonal bit and turning off the leftmost bits */ unsigned long int msb = 0x80000000UL; unsigned long int mask = 0xffffffffUL; for (i = 0; i < 32; i++) { int k = 7 * i + 3; /* Select a word to operate on */ state->x[k] &= mask; /* Turn off bits left of the diagonal */ state->x[k] |= msb; /* Turn on the diagonal bit */ mask >>= 1; msb >>= 1; } } return; } static const gsl_rng_type r250_type = {"r250", /* name */ 0xffffffffUL, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (r250_state_t), &r250_set, &r250_get, &r250_get_double}; const gsl_rng_type *gsl_rng_r250 = &r250_type; sources_5316/external/gsl/gsl_fit__linear.c0000664000176700017670000002033611723710247017630 0ustar paulpaul/* fit/linear.c * * Copyright (C) 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_fit.h" /* Fit the data (x_i, y_i) to the linear relationship Y = c0 + c1 x returning, c0, c1 -- coefficients cov00, cov01, cov11 -- variance-covariance matrix of c0 and c1, sumsq -- sum of squares of residuals This fit can be used in the case where the errors for the data are uknown, but assumed equal for all points. The resulting variance-covariance matrix estimates the error in the coefficients from the observed variance of the points around the best fit line. */ int gsl_fit_linear (const double *x, const size_t xstride, const double *y, const size_t ystride, const size_t n, double *c0, double *c1, double *cov_00, double *cov_01, double *cov_11, double *sumsq) { double m_x = 0, m_y = 0, m_dx2 = 0, m_dxdy = 0; size_t i; for (i = 0; i < n; i++) { m_x += (x[i * xstride] - m_x) / (i + 1.0); m_y += (y[i * ystride] - m_y) / (i + 1.0); } for (i = 0; i < n; i++) { const double dx = x[i * xstride] - m_x; const double dy = y[i * ystride] - m_y; m_dx2 += (dx * dx - m_dx2) / (i + 1.0); m_dxdy += (dx * dy - m_dxdy) / (i + 1.0); } /* In terms of y = a + b x */ { double s2 = 0, d2 = 0; double b = m_dxdy / m_dx2; double a = m_y - m_x * b; *c0 = a; *c1 = b; /* Compute chi^2 = \sum (y_i - (a + b * x_i))^2 */ for (i = 0; i < n; i++) { const double dx = x[i * xstride] - m_x; const double dy = y[i * ystride] - m_y; const double d = dy - b * dx; d2 += d * d; } s2 = d2 / (n - 2.0); /* chisq per degree of freedom */ *cov_00 = s2 * (1.0 / n) * (1 + m_x * m_x / m_dx2); *cov_11 = s2 * 1.0 / (n * m_dx2); *cov_01 = s2 * (-m_x) / (n * m_dx2); *sumsq = d2; } return GSL_SUCCESS; } /* Fit the weighted data (x_i, w_i, y_i) to the linear relationship Y = c0 + c1 x returning, c0, c1 -- coefficients s0, s1 -- the standard deviations of c0 and c1, r -- the correlation coefficient between c0 and c1, chisq -- weighted sum of squares of residuals */ int gsl_fit_wlinear (const double *x, const size_t xstride, const double *w, const size_t wstride, const double *y, const size_t ystride, const size_t n, double *c0, double *c1, double *cov_00, double *cov_01, double *cov_11, double *chisq) { /* compute the weighted means and weighted deviations from the means */ /* wm denotes a "weighted mean", wm(f) = (sum_i w_i f_i) / (sum_i w_i) */ double W = 0, wm_x = 0, wm_y = 0, wm_dx2 = 0, wm_dxdy = 0; size_t i; for (i = 0; i < n; i++) { const double wi = w[i * wstride]; if (wi > 0) { W += wi; wm_x += (x[i * xstride] - wm_x) * (wi / W); wm_y += (y[i * ystride] - wm_y) * (wi / W); } } W = 0; /* reset the total weight */ for (i = 0; i < n; i++) { const double wi = w[i * wstride]; if (wi > 0) { const double dx = x[i * xstride] - wm_x; const double dy = y[i * ystride] - wm_y; W += wi; wm_dx2 += (dx * dx - wm_dx2) * (wi / W); wm_dxdy += (dx * dy - wm_dxdy) * (wi / W); } } /* In terms of y = a + b x */ { double d2 = 0; double b = wm_dxdy / wm_dx2; double a = wm_y - wm_x * b; *c0 = a; *c1 = b; *cov_00 = (1 / W) * (1 + wm_x * wm_x / wm_dx2); *cov_11 = 1 / (W * wm_dx2); *cov_01 = -wm_x / (W * wm_dx2); /* Compute chi^2 = \sum w_i (y_i - (a + b * x_i))^2 */ for (i = 0; i < n; i++) { const double wi = w[i * wstride]; if (wi > 0) { const double dx = x[i * xstride] - wm_x; const double dy = y[i * ystride] - wm_y; const double d = dy - b * dx; d2 += wi * d * d; } } *chisq = d2; } return GSL_SUCCESS; } int gsl_fit_linear_est (const double x, const double c0, const double c1, const double cov00, const double cov01, const double cov11, double *y, double *y_err) { *y = c0 + c1 * x; *y_err = sqrt (cov00 + x * (2 * cov01 + cov11 * x)); return GSL_SUCCESS; } int gsl_fit_mul (const double *x, const size_t xstride, const double *y, const size_t ystride, const size_t n, double *c1, double *cov_11, double *sumsq) { double m_x = 0, m_y = 0, m_dx2 = 0, m_dxdy = 0; size_t i; for (i = 0; i < n; i++) { m_x += (x[i * xstride] - m_x) / (i + 1.0); m_y += (y[i * ystride] - m_y) / (i + 1.0); } for (i = 0; i < n; i++) { const double dx = x[i * xstride] - m_x; const double dy = y[i * ystride] - m_y; m_dx2 += (dx * dx - m_dx2) / (i + 1.0); m_dxdy += (dx * dy - m_dxdy) / (i + 1.0); } /* In terms of y = b x */ { double s2 = 0, d2 = 0; double b = (m_x * m_y + m_dxdy) / (m_x * m_x + m_dx2); *c1 = b; /* Compute chi^2 = \sum (y_i - b * x_i)^2 */ for (i = 0; i < n; i++) { const double dx = x[i * xstride] - m_x; const double dy = y[i * ystride] - m_y; const double d = (m_y - b * m_x) + dy - b * dx; d2 += d * d; } s2 = d2 / (n - 1.0); /* chisq per degree of freedom */ *cov_11 = s2 * 1.0 / (n * (m_x * m_x + m_dx2)); *sumsq = d2; } return GSL_SUCCESS; } int gsl_fit_wmul (const double *x, const size_t xstride, const double *w, const size_t wstride, const double *y, const size_t ystride, const size_t n, double *c1, double *cov_11, double *chisq) { /* compute the weighted means and weighted deviations from the means */ /* wm denotes a "weighted mean", wm(f) = (sum_i w_i f_i) / (sum_i w_i) */ double W = 0, wm_x = 0, wm_y = 0, wm_dx2 = 0, wm_dxdy = 0; size_t i; for (i = 0; i < n; i++) { const double wi = w[i * wstride]; if (wi > 0) { W += wi; wm_x += (x[i * xstride] - wm_x) * (wi / W); wm_y += (y[i * ystride] - wm_y) * (wi / W); } } W = 0; /* reset the total weight */ for (i = 0; i < n; i++) { const double wi = w[i * wstride]; if (wi > 0) { const double dx = x[i * xstride] - wm_x; const double dy = y[i * ystride] - wm_y; W += wi; wm_dx2 += (dx * dx - wm_dx2) * (wi / W); wm_dxdy += (dx * dy - wm_dxdy) * (wi / W); } } /* In terms of y = b x */ { double d2 = 0; double b = (wm_x * wm_y + wm_dxdy) / (wm_x * wm_x + wm_dx2); *c1 = b; *cov_11 = 1 / (W * (wm_x * wm_x + wm_dx2)); /* Compute chi^2 = \sum w_i (y_i - b * x_i)^2 */ for (i = 0; i < n; i++) { const double wi = w[i * wstride]; if (wi > 0) { const double dx = x[i * xstride] - wm_x; const double dy = y[i * ystride] - wm_y; const double d = (wm_y - b * wm_x) + (dy - b * dx); d2 += wi * d * d; } } *chisq = d2; } return GSL_SUCCESS; } int gsl_fit_mul_est (const double x, const double c1, const double cov11, double *y, double *y_err) { *y = c1 * x; *y_err = sqrt (cov11) * fabs (x); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_cblas__sscal.c0000664000176700017670000000034111723710247017757 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_sscal (const int N, const float alpha, float *X, const int incX) { #define BASE float #include "gsl_cblas__source_scal_r.h" #undef BASE } sources_5316/external/gsl/gsl_roots__bisection.c0000664000176700017670000000660511723710247020724 0ustar paulpaul/* roots/bisection.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* bisection.c -- bisection root finding algorithm */ #include "gsl__config.h" #include #include #include #include #include #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_roots.h" #include "gsl_roots__roots.h" typedef struct { double f_lower, f_upper; } bisection_state_t; static int bisection_init (void * vstate, gsl_function * f, double * root, double x_lower, double x_upper); static int bisection_iterate (void * vstate, gsl_function * f, double * root, double * x_lower, double * x_upper); static int bisection_init (void * vstate, gsl_function * f, double * root, double x_lower, double x_upper) { bisection_state_t * state = (bisection_state_t *) vstate; double f_lower, f_upper ; *root = 0.5 * (x_lower + x_upper) ; SAFE_FUNC_CALL (f, x_lower, &f_lower); SAFE_FUNC_CALL (f, x_upper, &f_upper); state->f_lower = f_lower; state->f_upper = f_upper; if ((f_lower < 0.0 && f_upper < 0.0) || (f_lower > 0.0 && f_upper > 0.0)) { GSL_ERROR ("endpoints do not straddle y=0", GSL_EINVAL); } return GSL_SUCCESS; } static int bisection_iterate (void * vstate, gsl_function * f, double * root, double * x_lower, double * x_upper) { bisection_state_t * state = (bisection_state_t *) vstate; double x_bisect, f_bisect; const double x_left = *x_lower ; const double x_right = *x_upper ; const double f_lower = state->f_lower; const double f_upper = state->f_upper; if (f_lower == 0.0) { *root = x_left ; *x_upper = x_left; return GSL_SUCCESS; } if (f_upper == 0.0) { *root = x_right ; *x_lower = x_right; return GSL_SUCCESS; } x_bisect = (x_left + x_right) / 2.0; SAFE_FUNC_CALL (f, x_bisect, &f_bisect); if (f_bisect == 0.0) { *root = x_bisect; *x_lower = x_bisect; *x_upper = x_bisect; return GSL_SUCCESS; } /* Discard the half of the interval which doesn't contain the root. */ if ((f_lower > 0.0 && f_bisect < 0.0) || (f_lower < 0.0 && f_bisect > 0.0)) { *root = 0.5 * (x_left + x_bisect) ; *x_upper = x_bisect; state->f_upper = f_bisect; } else { *root = 0.5 * (x_bisect + x_right) ; *x_lower = x_bisect; state->f_lower = f_bisect; } return GSL_SUCCESS; } static const gsl_root_fsolver_type bisection_type = {"bisection", /* name */ sizeof (bisection_state_t), &bisection_init, &bisection_iterate}; const gsl_root_fsolver_type * gsl_root_fsolver_bisection = &bisection_type; sources_5316/external/gsl/gsl_integration__workspace.c0000664000176700017670000000740511723710247022117 0ustar paulpaul/* integration/workspace.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_integration.h" #include "gsl_errno.h" gsl_integration_workspace * gsl_integration_workspace_alloc (const size_t n) { gsl_integration_workspace * w ; if (n == 0) { GSL_ERROR_VAL ("workspace length n must be positive integer", GSL_EDOM, 0); } w = (gsl_integration_workspace *) malloc (sizeof (gsl_integration_workspace)); if (w == 0) { GSL_ERROR_VAL ("failed to allocate space for workspace struct", GSL_ENOMEM, 0); } w->alist = (double *) malloc (n * sizeof (double)); if (w->alist == 0) { free (w); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for alist ranges", GSL_ENOMEM, 0); } w->blist = (double *) malloc (n * sizeof (double)); if (w->blist == 0) { free (w->alist); free (w); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for blist ranges", GSL_ENOMEM, 0); } w->rlist = (double *) malloc (n * sizeof (double)); if (w->rlist == 0) { free (w->blist); free (w->alist); free (w); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for rlist ranges", GSL_ENOMEM, 0); } w->elist = (double *) malloc (n * sizeof (double)); if (w->elist == 0) { free (w->rlist); free (w->blist); free (w->alist); free (w); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for elist ranges", GSL_ENOMEM, 0); } w->order = (size_t *) malloc (n * sizeof (size_t)); if (w->order == 0) { free (w->elist); free (w->rlist); free (w->blist); free (w->alist); free (w); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for order ranges", GSL_ENOMEM, 0); } w->level = (size_t *) malloc (n * sizeof (size_t)); if (w->level == 0) { free (w->order); free (w->elist); free (w->rlist); free (w->blist); free (w->alist); free (w); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for order ranges", GSL_ENOMEM, 0); } w->size = 0 ; w->limit = n ; w->maximum_level = 0 ; return w ; } void gsl_integration_workspace_free (gsl_integration_workspace * w) { free (w->level) ; free (w->order) ; free (w->elist) ; free (w->rlist) ; free (w->blist) ; free (w->alist) ; free (w) ; } /* size_t gsl_integration_workspace_limit (gsl_integration_workspace * w) { return w->limit ; } size_t gsl_integration_workspace_size (gsl_integration_workspace * w) { return w->size ; } */ sources_5316/external/gsl/gsl_statistics__ttest_source.c0000664000176700017670000000324111723710247022505 0ustar paulpaul/* statistics/ttest_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ double FUNCTION(gsl_stats,ttest) (const BASE data1[], const size_t stride1, const size_t n1, const BASE data2[], const size_t stride2, const size_t n2) { /* runs a t-test between two datasets representing independent samples. Tests to see if the difference between means of the samples is different from zero */ /* find means for the two samples */ const double mean1 = FUNCTION(gsl_stats,mean) (data1, stride1, n1); const double mean2 = FUNCTION(gsl_stats,mean) (data2, stride2, n2); /* find pooled variance for the two samples */ const double pv = FUNCTION(gsl_stats,pvariance) (data1, stride1, n1, data2, stride2, n2); /* calculate the t statistic */ const double t = (mean1 - mean2) / (sqrt (pv * ((1.0 / n1) + (1.0 / n2)))); return t; } sources_5316/external/gsl/gsl_const_mks.h0000664000176700017670000001537511705263724017374 0ustar paulpaul/* const/gsl_const_mks.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, * 2006 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_CONST_MKS__ #define __GSL_CONST_MKS__ #define GSL_CONST_MKS_SPEED_OF_LIGHT (2.99792458e8) /* m / s */ #define GSL_CONST_MKS_GRAVITATIONAL_CONSTANT (6.673e-11) /* m^3 / kg s^2 */ #define GSL_CONST_MKS_PLANCKS_CONSTANT_H (6.62606876e-34) /* kg m^2 / s */ #define GSL_CONST_MKS_PLANCKS_CONSTANT_HBAR (1.05457159642e-34) /* kg m^2 / s */ #define GSL_CONST_MKS_ASTRONOMICAL_UNIT (1.49597870691e11) /* m */ #define GSL_CONST_MKS_LIGHT_YEAR (9.46053620707e15) /* m */ #define GSL_CONST_MKS_PARSEC (3.08567758135e16) /* m */ #define GSL_CONST_MKS_GRAV_ACCEL (9.80665e0) /* m / s^2 */ #define GSL_CONST_MKS_ELECTRON_VOLT (1.602176462e-19) /* kg m^2 / s^2 */ #define GSL_CONST_MKS_MASS_ELECTRON (9.10938188e-31) /* kg */ #define GSL_CONST_MKS_MASS_MUON (1.88353109e-28) /* kg */ #define GSL_CONST_MKS_MASS_PROTON (1.67262158e-27) /* kg */ #define GSL_CONST_MKS_MASS_NEUTRON (1.67492716e-27) /* kg */ #define GSL_CONST_MKS_RYDBERG (2.17987190389e-18) /* kg m^2 / s^2 */ #define GSL_CONST_MKS_BOLTZMANN (1.3806503e-23) /* kg m^2 / K s^2 */ #define GSL_CONST_MKS_BOHR_MAGNETON (9.27400899e-24) /* A m^2 */ #define GSL_CONST_MKS_NUCLEAR_MAGNETON (5.05078317e-27) /* A m^2 */ #define GSL_CONST_MKS_ELECTRON_MAGNETIC_MOMENT (9.28476362e-24) /* A m^2 */ #define GSL_CONST_MKS_PROTON_MAGNETIC_MOMENT (1.410606633e-26) /* A m^2 */ #define GSL_CONST_MKS_MOLAR_GAS (8.314472e0) /* kg m^2 / K mol s^2 */ #define GSL_CONST_MKS_STANDARD_GAS_VOLUME (2.2710981e-2) /* m^3 / mol */ #define GSL_CONST_MKS_MINUTE (6e1) /* s */ #define GSL_CONST_MKS_HOUR (3.6e3) /* s */ #define GSL_CONST_MKS_DAY (8.64e4) /* s */ #define GSL_CONST_MKS_WEEK (6.048e5) /* s */ #define GSL_CONST_MKS_INCH (2.54e-2) /* m */ #define GSL_CONST_MKS_FOOT (3.048e-1) /* m */ #define GSL_CONST_MKS_YARD (9.144e-1) /* m */ #define GSL_CONST_MKS_MILE (1.609344e3) /* m */ #define GSL_CONST_MKS_NAUTICAL_MILE (1.852e3) /* m */ #define GSL_CONST_MKS_FATHOM (1.8288e0) /* m */ #define GSL_CONST_MKS_MIL (2.54e-5) /* m */ #define GSL_CONST_MKS_POINT (3.52777777778e-4) /* m */ #define GSL_CONST_MKS_TEXPOINT (3.51459803515e-4) /* m */ #define GSL_CONST_MKS_MICRON (1e-6) /* m */ #define GSL_CONST_MKS_ANGSTROM (1e-10) /* m */ #define GSL_CONST_MKS_HECTARE (1e4) /* m^2 */ #define GSL_CONST_MKS_ACRE (4.04685642241e3) /* m^2 */ #define GSL_CONST_MKS_BARN (1e-28) /* m^2 */ #define GSL_CONST_MKS_LITER (1e-3) /* m^3 */ #define GSL_CONST_MKS_US_GALLON (3.78541178402e-3) /* m^3 */ #define GSL_CONST_MKS_QUART (9.46352946004e-4) /* m^3 */ #define GSL_CONST_MKS_PINT (4.73176473002e-4) /* m^3 */ #define GSL_CONST_MKS_CUP (2.36588236501e-4) /* m^3 */ #define GSL_CONST_MKS_FLUID_OUNCE (2.95735295626e-5) /* m^3 */ #define GSL_CONST_MKS_TABLESPOON (1.47867647813e-5) /* m^3 */ #define GSL_CONST_MKS_TEASPOON (4.92892159375e-6) /* m^3 */ #define GSL_CONST_MKS_CANADIAN_GALLON (4.54609e-3) /* m^3 */ #define GSL_CONST_MKS_UK_GALLON (4.546092e-3) /* m^3 */ #define GSL_CONST_MKS_MILES_PER_HOUR (4.4704e-1) /* m / s */ #define GSL_CONST_MKS_KILOMETERS_PER_HOUR (2.77777777778e-1) /* m / s */ #define GSL_CONST_MKS_KNOT (5.14444444444e-1) /* m / s */ #define GSL_CONST_MKS_POUND_MASS (4.5359237e-1) /* kg */ #define GSL_CONST_MKS_OUNCE_MASS (2.8349523125e-2) /* kg */ #define GSL_CONST_MKS_TON (9.0718474e2) /* kg */ #define GSL_CONST_MKS_METRIC_TON (1e3) /* kg */ #define GSL_CONST_MKS_UK_TON (1.0160469088e3) /* kg */ #define GSL_CONST_MKS_TROY_OUNCE (3.1103475e-2) /* kg */ #define GSL_CONST_MKS_CARAT (2e-4) /* kg */ #define GSL_CONST_MKS_UNIFIED_ATOMIC_MASS (1.66053873e-27) /* kg */ #define GSL_CONST_MKS_GRAM_FORCE (9.80665e-3) /* kg m / s^2 */ #define GSL_CONST_MKS_POUND_FORCE (4.44822161526e0) /* kg m / s^2 */ #define GSL_CONST_MKS_KILOPOUND_FORCE (4.44822161526e3) /* kg m / s^2 */ #define GSL_CONST_MKS_POUNDAL (1.38255e-1) /* kg m / s^2 */ #define GSL_CONST_MKS_CALORIE (4.1868e0) /* kg m^2 / s^2 */ #define GSL_CONST_MKS_BTU (1.05505585262e3) /* kg m^2 / s^2 */ #define GSL_CONST_MKS_THERM (1.05506e8) /* kg m^2 / s^2 */ #define GSL_CONST_MKS_HORSEPOWER (7.457e2) /* kg m^2 / s^3 */ #define GSL_CONST_MKS_BAR (1e5) /* kg / m s^2 */ #define GSL_CONST_MKS_STD_ATMOSPHERE (1.01325e5) /* kg / m s^2 */ #define GSL_CONST_MKS_TORR (1.33322368421e2) /* kg / m s^2 */ #define GSL_CONST_MKS_METER_OF_MERCURY (1.33322368421e5) /* kg / m s^2 */ #define GSL_CONST_MKS_INCH_OF_MERCURY (3.38638815789e3) /* kg / m s^2 */ #define GSL_CONST_MKS_INCH_OF_WATER (2.490889e2) /* kg / m s^2 */ #define GSL_CONST_MKS_PSI (6.89475729317e3) /* kg / m s^2 */ #define GSL_CONST_MKS_POISE (1e-1) /* kg m^-1 s^-1 */ #define GSL_CONST_MKS_STOKES (1e-4) /* m^2 / s */ #define GSL_CONST_MKS_FARADAY (9.6485341472e4) /* A s / mol */ #define GSL_CONST_MKS_ELECTRON_CHARGE (1.602176462e-19) /* A s */ #define GSL_CONST_MKS_GAUSS (1e-4) /* kg / A s^2 */ #define GSL_CONST_MKS_STILB (1e4) /* cd / m^2 */ #define GSL_CONST_MKS_LUMEN (1e0) /* cd sr */ #define GSL_CONST_MKS_LUX (1e0) /* cd sr / m^2 */ #define GSL_CONST_MKS_PHOT (1e4) /* cd sr / m^2 */ #define GSL_CONST_MKS_FOOTCANDLE (1.076e1) /* cd sr / m^2 */ #define GSL_CONST_MKS_LAMBERT (1e4) /* cd sr / m^2 */ #define GSL_CONST_MKS_FOOTLAMBERT (1.07639104e1) /* cd sr / m^2 */ #define GSL_CONST_MKS_CURIE (3.7e10) /* 1 / s */ #define GSL_CONST_MKS_ROENTGEN (2.58e-4) /* A s / kg */ #define GSL_CONST_MKS_RAD (1e-2) /* m^2 / s^2 */ #define GSL_CONST_MKS_SOLAR_MASS (1.98892e30) /* kg */ #define GSL_CONST_MKS_BOHR_RADIUS (5.291772083e-11) /* m */ #define GSL_CONST_MKS_NEWTON (1e0) /* kg m / s^2 */ #define GSL_CONST_MKS_DYNE (1e-5) /* kg m / s^2 */ #define GSL_CONST_MKS_JOULE (1e0) /* kg m^2 / s^2 */ #define GSL_CONST_MKS_ERG (1e-7) /* kg m^2 / s^2 */ #define GSL_CONST_MKS_STEFAN_BOLTZMANN_CONSTANT (5.67039934436e-8) /* kg / K^4 s^3 */ #define GSL_CONST_MKS_THOMSON_CROSS_SECTION (6.65245853542e-29) /* m^2 */ #define GSL_CONST_MKS_VACUUM_PERMITTIVITY (8.854187817e-12) /* A^2 s^4 / kg m^3 */ #define GSL_CONST_MKS_VACUUM_PERMEABILITY (1.25663706144e-6) /* kg m / A^2 s^2 */ #define GSL_CONST_MKS_DEBYE (3.33564095198e-30) /* A s^2 / m^2 */ #endif /* __GSL_CONST_MKS__ */ sources_5316/external/gsl/gsl_siman__siman_tsp.c0000664000176700017670000002241011723710247020673 0ustar paulpaul/* siman/siman_tsp.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Mark Galassi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include #include "gsl_math.h" #include "gsl_rng.h" #include "gsl_siman.h" #include "gsl_ieee_utils.h" /* set up parameters for this simulated annealing run */ #define N_TRIES 200 /* how many points do we try before stepping */ #define ITERS_FIXED_T 2000 /* how many iterations for each T? */ #define STEP_SIZE 1.0 /* max step size in random walk */ #define K 1.0 /* Boltzmann constant */ #define T_INITIAL 5000.0 /* initial temperature */ #define MU_T 1.002 /* damping factor for temperature */ #define T_MIN 5.0e-1 gsl_siman_params_t params = {N_TRIES, ITERS_FIXED_T, STEP_SIZE, K, T_INITIAL, MU_T, T_MIN}; struct s_tsp_city { const char * name; double lat, longitude; /* coordinates */ }; typedef struct s_tsp_city Stsp_city; void prepare_distance_matrix(void); void exhaustive_search(void); void print_distance_matrix(void); double city_distance(Stsp_city c1, Stsp_city c2); double Etsp(void *xp); double Mtsp(void *xp, void *yp); void Stsp(const gsl_rng * r, void *xp, double step_size); void Ptsp(void *xp); /* in this table, latitude and longitude are obtained from the US Census Bureau, at http://www.census.gov/cgi-bin/gazetteer */ Stsp_city cities[] = {{"Santa Fe", 35.68, 105.95}, {"Phoenix", 33.54, 112.07}, {"Albuquerque", 35.12, 106.62}, {"Clovis", 34.41, 103.20}, {"Durango", 37.29, 107.87}, {"Dallas", 32.79, 96.77}, {"Tesuque", 35.77, 105.92}, {"Grants", 35.15, 107.84}, {"Los Alamos", 35.89, 106.28}, {"Las Cruces", 32.34, 106.76}, {"Cortez", 37.35, 108.58}, {"Gallup", 35.52, 108.74}}; #define N_CITIES (sizeof(cities)/sizeof(Stsp_city)) double distance_matrix[N_CITIES][N_CITIES]; /* distance between two cities */ double city_distance(Stsp_city c1, Stsp_city c2) { const double earth_radius = 6375.000; /* 6000KM approximately */ /* sin and cos of lat and long; must convert to radians */ double sla1 = sin(c1.lat*M_PI/180), cla1 = cos(c1.lat*M_PI/180), slo1 = sin(c1.longitude*M_PI/180), clo1 = cos(c1.longitude*M_PI/180); double sla2 = sin(c2.lat*M_PI/180), cla2 = cos(c2.lat*M_PI/180), slo2 = sin(c2.longitude*M_PI/180), clo2 = cos(c2.longitude*M_PI/180); double x1 = cla1*clo1; double x2 = cla2*clo2; double y1 = cla1*slo1; double y2 = cla2*slo2; double z1 = sla1; double z2 = sla2; double dot_product = x1*x2 + y1*y2 + z1*z2; double angle = acos(dot_product); /* distance is the angle (in radians) times the earth radius */ return angle*earth_radius; } /* energy for the travelling salesman problem */ double Etsp(void *xp) { /* an array of N_CITIES integers describing the order */ int *route = (int *) xp; double E = 0; unsigned int i; for (i = 0; i < N_CITIES; ++i) { /* use the distance_matrix to optimize this calculation; it had better be allocated!! */ E += distance_matrix[route[i]][route[(i + 1) % N_CITIES]]; } return E; } double Mtsp(void *xp, void *yp) { int *route1 = (int *) xp, *route2 = (int *) yp; double distance = 0; unsigned int i; for (i = 0; i < N_CITIES; ++i) { distance += ((route1[i] == route2[i]) ? 0 : 1); } return distance; } /* take a step through the TSP space */ void Stsp(const gsl_rng * r, void *xp, double step_size) { int x1, x2, dummy; int *route = (int *) xp; step_size = 0 ; /* prevent warnings about unused parameter */ /* pick the two cities to swap in the matrix; we leave the first city fixed */ x1 = (gsl_rng_get (r) % (N_CITIES-1)) + 1; do { x2 = (gsl_rng_get (r) % (N_CITIES-1)) + 1; } while (x2 == x1); dummy = route[x1]; route[x1] = route[x2]; route[x2] = dummy; } void Ptsp(void *xp) { unsigned int i; int *route = (int *) xp; printf(" ["); for (i = 0; i < N_CITIES; ++i) { printf(" %d ", route[i]); } printf("] "); } int main(void) { int x_initial[N_CITIES]; unsigned int i; const gsl_rng * r = gsl_rng_alloc (gsl_rng_env_setup()) ; gsl_ieee_env_setup (); prepare_distance_matrix(); /* set up a trivial initial route */ printf("# initial order of cities:\n"); for (i = 0; i < N_CITIES; ++i) { printf("# \"%s\"\n", cities[i].name); x_initial[i] = i; } printf("# distance matrix is:\n"); print_distance_matrix(); printf("# initial coordinates of cities (longitude and latitude)\n"); /* this can be plotted with */ /* ./siman_tsp > hhh ; grep city_coord hhh | awk '{print $2 " " $3}' | xyplot -ps -d "xy" > c.eps */ for (i = 0; i < N_CITIES+1; ++i) { printf("###initial_city_coord: %g %g \"%s\"\n", -cities[x_initial[i % N_CITIES]].longitude, cities[x_initial[i % N_CITIES]].lat, cities[x_initial[i % N_CITIES]].name); } /* exhaustive_search(); */ gsl_siman_solve(r, x_initial, Etsp, Stsp, Mtsp, Ptsp, NULL, NULL, NULL, N_CITIES*sizeof(int), params); printf("# final order of cities:\n"); for (i = 0; i < N_CITIES; ++i) { printf("# \"%s\"\n", cities[x_initial[i]].name); } printf("# final coordinates of cities (longitude and latitude)\n"); /* this can be plotted with */ /* ./siman_tsp > hhh ; grep city_coord hhh | awk '{print $2 " " $3}' | xyplot -ps -d "xy" > c.eps */ for (i = 0; i < N_CITIES+1; ++i) { printf("###final_city_coord: %g %g %s\n", -cities[x_initial[i % N_CITIES]].longitude, cities[x_initial[i % N_CITIES]].lat, cities[x_initial[i % N_CITIES]].name); } printf("# "); fflush(stdout); #if 0 system("date"); #endif /* 0 */ fflush(stdout); return 0; } void prepare_distance_matrix() { unsigned int i, j; double dist; for (i = 0; i < N_CITIES; ++i) { for (j = 0; j < N_CITIES; ++j) { if (i == j) { dist = 0; } else { dist = city_distance(cities[i], cities[j]); } distance_matrix[i][j] = dist; } } } void print_distance_matrix() { unsigned int i, j; for (i = 0; i < N_CITIES; ++i) { printf("# "); for (j = 0; j < N_CITIES; ++j) { printf("%15.8f ", distance_matrix[i][j]); } printf("\n"); } } /* [only works for 12] search the entire space for solutions */ static double best_E = 1.0e100, second_E = 1.0e100, third_E = 1.0e100; static int best_route[N_CITIES]; static int second_route[N_CITIES]; static int third_route[N_CITIES]; static void do_all_perms(int *route, int n); void exhaustive_search() { static int initial_route[N_CITIES] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11}; printf("\n# "); fflush(stdout); #if 0 system("date"); #endif fflush(stdout); do_all_perms(initial_route, 1); printf("\n# "); fflush(stdout); #if 0 system("date"); #endif /* 0 */ fflush(stdout); printf("# exhaustive best route: "); Ptsp(best_route); printf("\n# its energy is: %g\n", best_E); printf("# exhaustive second_best route: "); Ptsp(second_route); printf("\n# its energy is: %g\n", second_E); printf("# exhaustive third_best route: "); Ptsp(third_route); printf("\n# its energy is: %g\n", third_E); } /* James Theiler's recursive algorithm for generating all routes */ static void do_all_perms(int *route, int n) { if (n == (N_CITIES-1)) { /* do it! calculate the energy/cost for that route */ double E; E = Etsp(route); /* TSP energy function */ /* now save the best 3 energies and routes */ if (E < best_E) { third_E = second_E; memcpy(third_route, second_route, N_CITIES*sizeof(*route)); second_E = best_E; memcpy(second_route, best_route, N_CITIES*sizeof(*route)); best_E = E; memcpy(best_route, route, N_CITIES*sizeof(*route)); } else if (E < second_E) { third_E = second_E; memcpy(third_route, second_route, N_CITIES*sizeof(*route)); second_E = E; memcpy(second_route, route, N_CITIES*sizeof(*route)); } else if (E < third_E) { third_E = E; memcpy(route, third_route, N_CITIES*sizeof(*route)); } } else { int new_route[N_CITIES]; unsigned int j; int swap_tmp; memcpy(new_route, route, N_CITIES*sizeof(*route)); for (j = n; j < N_CITIES; ++j) { swap_tmp = new_route[j]; new_route[j] = new_route[n]; new_route[n] = swap_tmp; do_all_perms(new_route, n+1); } } } sources_5316/external/gsl/gsl_permutation__file.c0000664000176700017670000000462611723710247021066 0ustar paulpaul/* permutation/file.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_errno.h" #include "gsl_permutation.h" #define IN_FORMAT "%lu" int gsl_permutation_fread (FILE * stream, gsl_permutation * p) { size_t n = p->size ; size_t * data = p->data ; size_t items = fread (data, sizeof (size_t), n, stream); if (items != n) { GSL_ERROR ("fread failed", GSL_EFAILED); } return GSL_SUCCESS; } int gsl_permutation_fwrite (FILE * stream, const gsl_permutation * p) { size_t n = p->size ; size_t * data = p->data ; size_t items = fwrite (data, sizeof (size_t), n, stream); if (items != n) { GSL_ERROR ("fwrite failed", GSL_EFAILED); } return GSL_SUCCESS; } int gsl_permutation_fprintf (FILE * stream, const gsl_permutation * p, const char *format) { size_t n = p->size ; size_t * data = p->data ; size_t i; for (i = 0; i < n; i++) { int status = fprintf (stream, format, data[i]); if (status < 0) { GSL_ERROR ("fprintf failed", GSL_EFAILED); } } return GSL_SUCCESS; } int gsl_permutation_fscanf (FILE * stream, gsl_permutation * p) { size_t n = p->size ; size_t * data = p->data ; size_t i; for (i = 0; i < n; i++) { unsigned long j ; /* FIXME: what if size_t != unsigned long ??? want read in size_t but have to read in unsigned long to avoid error from compiler */ int status = fscanf (stream, IN_FORMAT, &j); if (status != 1) { GSL_ERROR ("fscanf failed", GSL_EFAILED); } data[i] = j; } return GSL_SUCCESS; } sources_5316/external/gsl/gsl_roots__roots.h0000664000176700017670000000240311705263724020113 0ustar paulpaul/* roots/roots.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* roots.h -- declarations for internal root finding and RF support stuff. */ #ifndef __ROOTS_H__ #define __ROOTS_H__ /* Call the pointed-to function with argument x, put its result in y, and return an error if the function value is Inf/Nan. */ #define SAFE_FUNC_CALL(f, x, yp) \ do { \ *yp = GSL_FN_EVAL(f,x); \ if (!gsl_finite(*yp)) \ GSL_ERROR("function value is not finite", GSL_EBADFUNC); \ } while (0) #endif /* __ROOTS_H__ */ sources_5316/external/gsl/gsl_statistics__variance_source.c0000664000176700017670000000544011723710247023135 0ustar paulpaul/* statistics/variance_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Jim Davies, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static double FUNCTION(compute,variance) (const BASE data[], const size_t stride, const size_t n, const double mean); static double FUNCTION(compute,variance) (const BASE data[], const size_t stride, const size_t n, const double mean) { /* takes a dataset and finds the variance */ long double variance = 0 ; size_t i; /* find the sum of the squares */ for (i = 0; i < n; i++) { const long double delta = (data[i * stride] - mean); variance += (delta * delta - variance) / (i + 1); } return variance ; } double FUNCTION(gsl_stats,variance_with_fixed_mean) (const BASE data[], const size_t stride, const size_t n, const double mean) { const double variance = FUNCTION(compute,variance) (data, stride, n, mean); return variance; } double FUNCTION(gsl_stats,sd_with_fixed_mean) (const BASE data[], const size_t stride, const size_t n, const double mean) { const double variance = FUNCTION(compute,variance) (data, stride, n, mean); const double sd = sqrt (variance); return sd; } double FUNCTION(gsl_stats,variance_m) (const BASE data[], const size_t stride, const size_t n, const double mean) { const double variance = FUNCTION(compute,variance) (data, stride, n, mean); return variance * ((double)n / (double)(n - 1)); } double FUNCTION(gsl_stats,sd_m) (const BASE data[], const size_t stride, const size_t n, const double mean) { const double variance = FUNCTION(compute,variance) (data, stride, n, mean); const double sd = sqrt (variance * ((double)n / (double)(n - 1))); return sd; } double FUNCTION(gsl_stats,variance) (const BASE data[], const size_t stride, const size_t n) { const double mean = FUNCTION(gsl_stats,mean) (data, stride, n); return FUNCTION(gsl_stats,variance_m)(data, stride, n, mean); } double FUNCTION(gsl_stats,sd) (const BASE data[], const size_t stride, const size_t n) { const double mean = FUNCTION(gsl_stats,mean) (data, stride, n); return FUNCTION(gsl_stats,sd_m) (data, stride, n, mean); } sources_5316/external/gsl/gsl_integration__qpsrt.c0000664000176700017670000000545611723710247021276 0ustar paulpaul/* integration/qpsrt.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static inline void qpsrt (gsl_integration_workspace * workspace); static inline void qpsrt (gsl_integration_workspace * workspace) { const size_t last = workspace->size - 1; const size_t limit = workspace->limit; double * elist = workspace->elist; size_t * order = workspace->order; double errmax ; double errmin ; int i, k, top; size_t i_nrmax = workspace->nrmax; size_t i_maxerr = order[i_nrmax] ; /* Check whether the list contains more than two error estimates */ if (last < 2) { order[0] = 0 ; order[1] = 1 ; workspace->i = i_maxerr ; return ; } errmax = elist[i_maxerr] ; /* This part of the routine is only executed if, due to a difficult integrand, subdivision increased the error estimate. In the normal case the insert procedure should start after the nrmax-th largest error estimate. */ while (i_nrmax > 0 && errmax > elist[order[i_nrmax - 1]]) { order[i_nrmax] = order[i_nrmax - 1] ; i_nrmax-- ; } /* Compute the number of elements in the list to be maintained in descending order. This number depends on the number of subdivisions still allowed. */ if(last < (limit/2 + 2)) { top = last ; } else { top = limit - last + 1; } /* Insert errmax by traversing the list top-down, starting comparison from the element elist(order(i_nrmax+1)). */ i = i_nrmax + 1 ; /* The order of the tests in the following line is important to prevent a segmentation fault */ while (i < top && errmax < elist[order[i]]) { order[i-1] = order[i] ; i++ ; } order[i-1] = i_maxerr ; /* Insert errmin by traversing the list bottom-up */ errmin = elist[last] ; k = top - 1 ; while (k > i - 2 && errmin >= elist[order[k]]) { order[k+1] = order[k] ; k-- ; } order[k+1] = last ; /* Set i_max and e_max */ i_maxerr = order[i_nrmax] ; workspace->i = i_maxerr ; workspace->nrmax = i_nrmax ; } sources_5316/external/gsl/gsl_integration__qmomo.c0000664000176700017670000001037411723710247021250 0ustar paulpaul/* integration/qmomo.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_integration.h" #include "gsl_errno.h" static void initialise (double * ri, double * rj, double * rg, double * rh, double alpha, double beta); gsl_integration_qaws_table * gsl_integration_qaws_table_alloc (double alpha, double beta, int mu, int nu) { gsl_integration_qaws_table * t; if (alpha < -1.0) { GSL_ERROR_VAL ("alpha must be greater than -1.0", GSL_EINVAL, 0); } if (beta < -1.0) { GSL_ERROR_VAL ("beta must be greater than -1.0", GSL_EINVAL, 0); } if (mu != 0 && mu != 1) { GSL_ERROR_VAL ("mu must be 0 or 1", GSL_EINVAL, 0); } if (nu != 0 && nu != 1) { GSL_ERROR_VAL ("nu must be 0 or 1", GSL_EINVAL, 0); } t = (gsl_integration_qaws_table *) malloc(sizeof(gsl_integration_qaws_table)); if (t == 0) { GSL_ERROR_VAL ("failed to allocate space for qaws_table struct", GSL_ENOMEM, 0); } t->alpha = alpha; t->beta = beta; t->mu = mu; t->nu = nu; initialise (t->ri, t->rj, t->rg, t->rh, alpha, beta); return t; } int gsl_integration_qaws_table_set (gsl_integration_qaws_table * t, double alpha, double beta, int mu, int nu) { if (alpha < -1.0) { GSL_ERROR ("alpha must be greater than -1.0", GSL_EINVAL); } if (beta < -1.0) { GSL_ERROR ("beta must be greater than -1.0", GSL_EINVAL); } if (mu != 0 && mu != 1) { GSL_ERROR ("mu must be 0 or 1", GSL_EINVAL); } if (nu != 0 && nu != 1) { GSL_ERROR ("nu must be 0 or 1", GSL_EINVAL); } t->alpha = alpha; t->beta = beta; t->mu = mu; t->nu = nu; initialise (t->ri, t->rj, t->rg, t->rh, alpha, beta); return GSL_SUCCESS; } void gsl_integration_qaws_table_free (gsl_integration_qaws_table * t) { free (t); } static void initialise (double * ri, double * rj, double * rg, double * rh, double alpha, double beta) { const double alpha_p1 = alpha + 1.0; const double beta_p1 = beta + 1.0; const double alpha_p2 = alpha + 2.0; const double beta_p2 = beta + 2.0; const double r_alpha = pow (2.0, alpha_p1); const double r_beta = pow (2.0, beta_p1); size_t i; double an, anm1; ri[0] = r_alpha / alpha_p1; ri[1] = ri[0] * alpha / alpha_p2; an = 2.0; anm1 = 1.0; for (i = 2; i < 25; i++) { ri[i] = -(r_alpha + an * (an - alpha_p2) * ri[i - 1]) / (anm1 * (an + alpha_p1)); anm1 = an; an = an + 1.0; } rj[0] = r_beta / beta_p1; rj[1] = rj[0] * beta / beta_p2; an = 2.0; anm1 = 1.0; for (i = 2; i < 25; i++) { rj[i] = -(r_beta + an * (an - beta_p2) * rj[i - 1]) / (anm1 * (an + beta_p1)); anm1 = an; an = an + 1.0; } rg[0] = -ri[0] / alpha_p1; rg[1] = -rg[0] - 2.0 * r_alpha / (alpha_p2 * alpha_p2); an = 2.0; anm1 = 1.0; for (i = 2; i < 25; i++) { rg[i] = -(an * (an - alpha_p2) * rg[i - 1] - an * ri[i - 1] + anm1 * ri[i]) / (anm1 * (an + alpha_p1)); anm1 = an; an = an + 1.0; } rh[0] = -rj[0] / beta_p1; rh[1] = -rh[0] - 2.0 * r_beta / (beta_p2 * beta_p2); an = 2.0; anm1 = 1.0; for (i = 2; i < 25; i++) { rh[i] = -(an * (an - beta_p2) * rh[i - 1] - an * rj[i - 1] + anm1 * rj[i]) / (anm1 * (an + beta_p1)); anm1 = an; an = an + 1.0; } for (i = 1; i < 25; i += 2) { rj[i] *= -1; rh[i] *= -1; } } sources_5316/external/gsl/gsl_cblas__snrm2.c0000664000176700017670000000032511723710247017715 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" float cblas_snrm2 (const int N, const float *X, const int incX) { #define BASE float #include "gsl_cblas__source_nrm2_r.h" #undef BASE } sources_5316/external/gsl/gsl_sort__subsetind.c0000664000176700017670000000412311723710247020557 0ustar paulpaul/* sort/subsetind.c * * Copyright (C) 2001, 2007 Brian Gough * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 3, or (at your option) any * later version. * * This source is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * for more details. */ #include "gsl__config.h" #include "gsl_errno.h" #include "gsl_vector.h" #include "gsl_sort.h" #include "gsl_sort_vector.h" #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_sort__subsetind_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_ieee-utils__fp-netbsd.c0000664000176700017670000000560011723710247021520 0ustar paulpaul/* fp-netbsd.c * * Copyright (C) 2001 Jason Beegan * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include "gsl_ieee_utils.h" #include "gsl_errno.h" int gsl_ieee_set_mode (int precision, int rounding, int exception_mask) { fp_except mode = 0; fp_rnd rnd = 0; switch (precision) { case GSL_IEEE_SINGLE_PRECISION: GSL_ERROR ("NetBSD only supports default precision rounding", GSL_EUNSUP); break; case GSL_IEEE_DOUBLE_PRECISION: GSL_ERROR ("NetBSD only supports default precision rounding", GSL_EUNSUP); break; case GSL_IEEE_EXTENDED_PRECISION: GSL_ERROR ("NetBSD only supports default precision rounding", GSL_EUNSUP); break; } switch (rounding) { case GSL_IEEE_ROUND_TO_NEAREST: rnd = FP_RN; fpsetround (rnd); break; case GSL_IEEE_ROUND_DOWN: rnd = FP_RM; fpsetround (rnd); break; case GSL_IEEE_ROUND_UP: rnd = FP_RP; fpsetround (rnd); break; case GSL_IEEE_ROUND_TO_ZERO: rnd = FP_RZ; fpsetround (rnd); break; default: rnd = FP_RN; fpsetround (rnd); } /* Turn on all available exceptions apart from 'inexact'. Denormalized operand exception not available on all platforms. */ mode = FP_X_INV | FP_X_DZ | FP_X_OFL | FP_X_UFL; #ifdef FP_X_DNML mode = mode | FP_X_DNML; #endif if (exception_mask & GSL_IEEE_MASK_INVALID) mode &= ~ FP_X_INV; if (exception_mask & GSL_IEEE_MASK_DENORMALIZED) { #ifdef FP_X_DNML mode &= ~ FP_X_DNML; #endif } else { #ifndef FP_X_DNML GSL_ERROR ("NetBSD does not support the denormalized operand exception on this platform. " "Use 'mask-denormalized' to work around this.", GSL_EUNSUP); #endif } if (exception_mask & GSL_IEEE_MASK_DIVISION_BY_ZERO) mode &= ~ FP_X_DZ; if (exception_mask & GSL_IEEE_MASK_OVERFLOW) mode &= ~ FP_X_OFL; if (exception_mask & GSL_IEEE_MASK_UNDERFLOW) mode &= ~ FP_X_UFL; if (exception_mask & GSL_IEEE_TRAP_INEXACT) { mode |= FP_X_IMP; } else { mode &= ~ FP_X_IMP; } fpsetmask (mode); return GSL_SUCCESS; } sources_5316/external/gsl/gsl_specfunc__hyperg.h0000664000176700017670000000433211705263724020706 0ustar paulpaul/* specfunc/hyperg.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ /* Miscellaneous implementations of use * for evaluation of hypergeometric functions. */ #ifndef _HYPERG_H_ #define _HYPERG_H_ #include "gsl_sf_result.h" /* Direct implementation of 1F1 series. */ int gsl_sf_hyperg_1F1_series_e(const double a, const double b, const double x, gsl_sf_result * result); /* Implementation of the 1F1 related to the * incomplete gamma function: 1F1(1,b,x), b >= 1. */ int gsl_sf_hyperg_1F1_1_e(double b, double x, gsl_sf_result * result); /* 1F1(1,b,x) for integer b >= 1 */ int gsl_sf_hyperg_1F1_1_int_e(int b, double x, gsl_sf_result * result); /* Implementation of large b asymptotic. * [Bateman v. I, 6.13.3 (18)] * [Luke, The Special Functions and Their Approximations v. I, p. 129, 4.8 (4)] * * a^2 << b, |x|/|b| < 1 - delta */ int gsl_sf_hyperg_1F1_large_b_e(const double a, const double b, const double x, gsl_sf_result * result); /* Implementation of large b asymptotic. * * Assumes a > 0 is small, x > 0, and |x|<|b|. */ int gsl_sf_hyperg_U_large_b_e(const double a, const double b, const double x, gsl_sf_result * result, double * ln_multiplier ); /* Implementation of 2F0 asymptotic series. */ int gsl_sf_hyperg_2F0_series_e(const double a, const double b, const double x, int n_trunc, gsl_sf_result * result); #endif /* !_HYPERG_H_ */ sources_5316/external/gsl/gsl_cblas__zsyrk.c0000664000176700017670000000064011723710247020036 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zsyrk (const enum CBLAS_ORDER Order, const enum CBLAS_UPLO Uplo, const enum CBLAS_TRANSPOSE Trans, const int N, const int K, const void *alpha, const void *A, const int lda, const void *beta, void *C, const int ldc) { #define BASE double #include "gsl_cblas__source_syrk_c.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__zhemv.c0000664000176700017670000000061711723710247020011 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_zhemv (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const void *alpha, const void *A, const int lda, const void *X, const int incX, const void *beta, void *Y, const int incY) { #define BASE double #include "gsl_cblas__source_hemv.h" #undef BASE } sources_5316/external/gsl/gsl_sf__error.h0000644000176700017670000000343510707442037017341 0ustar paulpaul#define OVERFLOW_ERROR(result) do { (result)->val = GSL_POSINF; (result)->err = GSL_POSINF; GSL_ERROR ("overflow", GSL_EOVRFLW); } while(0) #define UNDERFLOW_ERROR(result) do { (result)->val = 0.0; (result)->err = GSL_DBL_MIN; GSL_ERROR ("underflow", GSL_EUNDRFLW); } while(0) #define INTERNAL_OVERFLOW_ERROR(result) do { (result)->val = GSL_POSINF; (result)->err = GSL_POSINF; return GSL_EOVRFLW; } while(0) #define INTERNAL_UNDERFLOW_ERROR(result) do { (result)->val = 0.0; (result)->err = GSL_DBL_MIN; return GSL_EUNDRFLW; } while(0) #define DOMAIN_ERROR(result) do { (result)->val = GSL_NAN; (result)->err = GSL_NAN; GSL_ERROR ("domain error", GSL_EDOM); } while(0) #define DOMAIN_ERROR_MSG(msg, result) do { (result)->val = GSL_NAN; (result)->err = GSL_NAN; GSL_ERROR ((msg), GSL_EDOM); } while(0) #define DOMAIN_ERROR_E10(result) do { (result)->val = GSL_NAN; (result)->err = GSL_NAN; (result)->e10 = 0 ; GSL_ERROR ("domain error", GSL_EDOM); } while(0) #define OVERFLOW_ERROR_E10(result) do { (result)->val = GSL_POSINF; (result)->err = GSL_POSINF; (result)->e10 = 0; GSL_ERROR ("overflow", GSL_EOVRFLW); } while(0) #define UNDERFLOW_ERROR_E10(result) do { (result)->val = 0.0; (result)->err = GSL_DBL_MIN; (result)->e10 = 0; GSL_ERROR ("underflow", GSL_EUNDRFLW); } while(0) #define OVERFLOW_ERROR_2(r1,r2) do { (r1)->val = GSL_POSINF; (r1)->err = GSL_POSINF; (r2)->val = GSL_POSINF ; (r2)->err=GSL_POSINF; GSL_ERROR ("overflow", GSL_EOVRFLW); } while(0) #define UNDERFLOW_ERROR_2(r1,r2) do { (r1)->val = 0.0; (r1)->err = GSL_DBL_MIN; (r2)->val = 0.0 ; (r2)->err = GSL_DBL_MIN; GSL_ERROR ("underflow", GSL_EUNDRFLW); } while(0) #define DOMAIN_ERROR_2(r1,r2) do { (r1)->val = GSL_NAN; (r1)->err = GSL_NAN; (r2)->val = GSL_NAN; (r2)->err = GSL_NAN; GSL_ERROR ("domain error", GSL_EDOM); } while(0) sources_5316/external/gsl/gsl_sf__pow_int.c0000644000176700017670000000357310707442037017665 0ustar paulpaul/* specfunc/pow_int.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_pow_int.h" /*-*-*-*-*-*-*-*-*-*-*-* Functions w/ Error handling *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_pow_int_e(double x, int n, gsl_sf_result * result) { double value = 1.0; int count = 0; /* CHECK_POINTER(result) */ if(n < 0) { n = -n; if(x == 0.0) { double u = 1.0 / x; result->val = (n % 2) ? u : (u * u) ; /* correct sign of infinity */ result->err = GSL_POSINF; GSL_ERROR ("overflow", GSL_EOVRFLW); } x = 1.0/x; } /* repeated squaring method * returns 0.0^0 = 1.0, so continuous in x */ do { if(GSL_IS_ODD(n)) value *= x; n >>= 1; x *= x; ++count; } while (n); result->val = value; result->err = 2.0 * GSL_DBL_EPSILON * (count + 1.0) * fabs(value); return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_pow_int(const double x, const int n) { EVAL_RESULT(gsl_sf_pow_int_e(x, n, &result)); } sources_5316/external/gsl/gsl_eigen__schur.c0000664000176700017670000005275111723710247020015 0ustar paulpaul/* eigen/schur.c * * Copyright (C) 2006, 2007 Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_eigen.h" #include "gsl_math.h" #include "gsl_matrix.h" #include "gsl_vector.h" #include "gsl_vector_complex.h" #include "gsl_blas.h" #include "gsl_complex.h" #include "gsl_complex_math.h" /* * This module contains some routines related to manipulating the * Schur form of a matrix which are needed by the eigenvalue solvers * * This file contains routines based on original code from LAPACK * which is distributed under the modified BSD license. */ #define GSL_SCHUR_SMLNUM (2.0 * GSL_DBL_MIN) #define GSL_SCHUR_BIGNUM ((1.0 - GSL_DBL_EPSILON) / GSL_SCHUR_SMLNUM) /* gsl_schur_gen_eigvals() Compute the eigenvalues of a 2-by-2 generalized block. Inputs: A - 2-by-2 matrix B - 2-by-2 upper triangular matrix wr1 - (output) see notes wr2 - (output) see notes wi - (output) see notes scale1 - (output) see notes scale2 - (output) see notes Return: success Notes: 1) If the block contains real eigenvalues, then wi is set to 0, and wr1, wr2, scale1, and scale2 are set such that: eval1 = wr1 * scale1 eval2 = wr2 * scale2 If the block contains complex eigenvalues, then wr1, wr2, scale1, scale2, and wi are set such that: wr1 = wr2 = scale1 * Re(eval) wi = scale1 * Im(eval) wi is always non-negative 2) This routine is based on LAPACK DLAG2 */ int gsl_schur_gen_eigvals(const gsl_matrix *A, const gsl_matrix *B, double *wr1, double *wr2, double *wi, double *scale1, double *scale2) { const double safemin = GSL_DBL_MIN * 1.0e2; const double safemax = 1.0 / safemin; const double rtmin = sqrt(safemin); const double rtmax = 1.0 / rtmin; double anorm, bnorm; double ascale, bscale, bsize; double s1, s2; double A11, A12, A21, A22; double B11, B12, B22; double binv11, binv22; double bmin; double as11, as12, as22, abi22; double pp, qq, shift, ss, discr, r; /* scale A */ anorm = GSL_MAX(GSL_MAX(fabs(gsl_matrix_get(A, 0, 0)) + fabs(gsl_matrix_get(A, 1, 0)), fabs(gsl_matrix_get(A, 0, 1)) + fabs(gsl_matrix_get(A, 1, 1))), safemin); ascale = 1.0 / anorm; A11 = ascale * gsl_matrix_get(A, 0, 0); A12 = ascale * gsl_matrix_get(A, 0, 1); A21 = ascale * gsl_matrix_get(A, 1, 0); A22 = ascale * gsl_matrix_get(A, 1, 1); /* perturb B if necessary to ensure non-singularity */ B11 = gsl_matrix_get(B, 0, 0); B12 = gsl_matrix_get(B, 0, 1); B22 = gsl_matrix_get(B, 1, 1); bmin = rtmin * GSL_MAX(fabs(B11), GSL_MAX(fabs(B12), GSL_MAX(fabs(B22), rtmin))); if (fabs(B11) < bmin) B11 = GSL_SIGN(B11) * bmin; if (fabs(B22) < bmin) B22 = GSL_SIGN(B22) * bmin; /* scale B */ bnorm = GSL_MAX(fabs(B11), GSL_MAX(fabs(B12) + fabs(B22), safemin)); bsize = GSL_MAX(fabs(B11), fabs(B22)); bscale = 1.0 / bsize; B11 *= bscale; B12 *= bscale; B22 *= bscale; /* compute larger eigenvalue */ binv11 = 1.0 / B11; binv22 = 1.0 / B22; s1 = A11 * binv11; s2 = A22 * binv22; if (fabs(s1) <= fabs(s2)) { as12 = A12 - s1 * B12; as22 = A22 - s1 * B22; ss = A21 * (binv11 * binv22); abi22 = as22 * binv22 - ss * B12; pp = 0.5 * abi22; shift = s1; } else { as12 = A12 - s2 * B12; as11 = A11 - s2 * B11; ss = A21 * (binv11 * binv22); abi22 = -ss * B12; pp = 0.5 * (as11 * binv11 + abi22); shift = s2; } qq = ss * as12; if (fabs(pp * rtmin) >= 1.0) { discr = (rtmin * pp) * (rtmin * pp) + qq * safemin; r = sqrt(fabs(discr)) * rtmax; } else if (pp * pp + fabs(qq) <= safemin) { discr = (rtmax * pp) * (rtmax * pp) + qq * safemax; r = sqrt(fabs(discr)) * rtmin; } else { discr = pp * pp + qq; r = sqrt(fabs(discr)); } if (discr >= 0.0 || r == 0.0) { double sum = pp + GSL_SIGN(pp) * r; double diff = pp - GSL_SIGN(pp) * r; double wbig = shift + sum; double wsmall = shift + diff; /* compute smaller eigenvalue */ if (0.5 * fabs(wbig) > GSL_MAX(fabs(wsmall), safemin)) { double wdet = (A11*A22 - A12*A21) * (binv11 * binv22); wsmall = wdet / wbig; } /* choose (real) eigenvalue closest to 2,2 element of AB^{-1} for wr1 */ if (pp > abi22) { *wr1 = GSL_MIN(wbig, wsmall); *wr2 = GSL_MAX(wbig, wsmall); } else { *wr1 = GSL_MAX(wbig, wsmall); *wr2 = GSL_MIN(wbig, wsmall); } *wi = 0.0; } else { /* complex eigenvalues */ *wr1 = shift + pp; *wr2 = *wr1; *wi = r; } /* compute scaling */ { const double fuzzy1 = 1.0 + 1.0e-5; double c1, c2, c3, c4, c5; double wabs, wsize, wscale; c1 = bsize * (safemin * GSL_MAX(1.0, ascale)); c2 = safemin * GSL_MAX(1.0, bnorm); c3 = bsize * safemin; if (ascale <= 1.0 && bsize <= 1.0) c4 = GSL_MIN(1.0, (ascale / safemin) * bsize); else c4 = 1.0; if (ascale <= 1.0 || bsize <= 1.0) c5 = GSL_MIN(1.0, ascale * bsize); else c5 = 1.0; /* scale first eigenvalue */ wabs = fabs(*wr1) + fabs(*wi); wsize = GSL_MAX(safemin, GSL_MAX(c1, GSL_MAX(fuzzy1 * (wabs*c2 + c3), GSL_MIN(c4, 0.5 * GSL_MAX(wabs, c5))))); if (wsize != 1.0) { wscale = 1.0 / wsize; if (wsize > 1.0) { *scale1 = (GSL_MAX(ascale, bsize) * wscale) * GSL_MIN(ascale, bsize); } else { *scale1 = (GSL_MIN(ascale, bsize) * wscale) * GSL_MAX(ascale, bsize); } *wr1 *= wscale; if (*wi != 0.0) { *wi *= wscale; *wr2 = *wr1; *scale2 = *scale1; } } else { *scale1 = ascale * bsize; *scale2 = *scale1; } /* scale second eigenvalue if real */ if (*wi == 0.0) { wsize = GSL_MAX(safemin, GSL_MAX(c1, GSL_MAX(fuzzy1 * (fabs(*wr2) * c2 + c3), GSL_MIN(c4, 0.5 * GSL_MAX(fabs(*wr2), c5))))); if (wsize != 1.0) { wscale = 1.0 / wsize; if (wsize > 1.0) { *scale2 = (GSL_MAX(ascale, bsize) * wscale) * GSL_MIN(ascale, bsize); } else { *scale2 = (GSL_MIN(ascale, bsize) * wscale) * GSL_MAX(ascale, bsize); } *wr2 *= wscale; } else { *scale2 = ascale * bsize; } } } return GSL_SUCCESS; } /* gsl_schur_gen_eigvals() */ /* gsl_schur_solve_equation() Solve the equation which comes up in the back substitution when computing eigenvectors corresponding to real eigenvalues. The equation that is solved is: (ca*A - z*D)*x = s*b where A is n-by-n with n = 1 or 2 D is a n-by-n diagonal matrix b and x are n-by-1 real vectors s is a scaling factor set by this function to prevent overflow in x Inputs: ca - coefficient multiplying A A - square matrix (n-by-n) z - real scalar (eigenvalue) d1 - (1,1) element in diagonal matrix D d2 - (2,2) element in diagonal matrix D b - right hand side vector x - (output) where to store solution s - (output) scale factor xnorm - (output) infinity norm of X smin - lower bound on singular values of A - if ca*A - z*D is less than this value, we'll use smin*I instead. This value should be a safe distance above underflow. Return: success Notes: 1) A and b are not changed on output 2) Based on lapack routine DLALN2 */ int gsl_schur_solve_equation(double ca, const gsl_matrix *A, double z, double d1, double d2, const gsl_vector *b, gsl_vector *x, double *s, double *xnorm, double smin) { size_t N = A->size1; double bnorm; double scale = 1.0; if (N == 1) { double c, /* denominator */ cnorm; /* |c| */ /* we have a 1-by-1 (real) scalar system to solve */ c = ca * gsl_matrix_get(A, 0, 0) - z * d1; cnorm = fabs(c); if (cnorm < smin) { /* set c = smin*I */ c = smin; cnorm = smin; } /* check scaling for x = b / c */ bnorm = fabs(gsl_vector_get(b, 0)); if (cnorm < 1.0 && bnorm > 1.0) { if (bnorm > GSL_SCHUR_BIGNUM*cnorm) scale = 1.0 / bnorm; } /* compute x */ gsl_vector_set(x, 0, gsl_vector_get(b, 0) * scale / c); *xnorm = fabs(gsl_vector_get(x, 0)); } /* if (N == 1) */ else { double cr[2][2]; double *crv; double cmax; size_t icmax, j; double bval1, bval2; double ur11, ur12, ur22, ur11r; double cr21, cr22; double lr21; double b1, b2, bbnd; double x1, x2; double temp; size_t ipivot[4][4] = { { 0, 1, 2, 3 }, { 1, 0, 3, 2 }, { 2, 3, 0, 1 }, { 3, 2, 1, 0 } }; int rswap[4] = { 0, 1, 0, 1 }; int zswap[4] = { 0, 0, 1, 1 }; /* * we have a 2-by-2 real system to solve: * * ( ca * [ A11 A12 ] - z * [ D1 0 ] ) [ x1 ] = [ b1 ] * ( [ A21 A22 ] [ 0 D2 ] ) [ x2 ] [ b2 ] * * (z real) */ crv = (double *) cr; /* * compute the real part of C = ca*A - z*D - use column ordering * here since porting from lapack */ cr[0][0] = ca * gsl_matrix_get(A, 0, 0) - z * d1; cr[1][1] = ca * gsl_matrix_get(A, 1, 1) - z * d2; cr[0][1] = ca * gsl_matrix_get(A, 1, 0); cr[1][0] = ca * gsl_matrix_get(A, 0, 1); /* find the largest element in C */ cmax = 0.0; icmax = 0; for (j = 0; j < 4; ++j) { if (fabs(crv[j]) > cmax) { cmax = fabs(crv[j]); icmax = j; } } bval1 = gsl_vector_get(b, 0); bval2 = gsl_vector_get(b, 1); /* if norm(C) < smin, use smin*I */ if (cmax < smin) { bnorm = GSL_MAX(fabs(bval1), fabs(bval2)); if (smin < 1.0 && bnorm > 1.0) { if (bnorm > GSL_SCHUR_BIGNUM*smin) scale = 1.0 / bnorm; } temp = scale / smin; gsl_vector_set(x, 0, temp * bval1); gsl_vector_set(x, 1, temp * bval2); *xnorm = temp * bnorm; *s = scale; return GSL_SUCCESS; } /* gaussian elimination with complete pivoting */ ur11 = crv[icmax]; cr21 = crv[ipivot[1][icmax]]; ur12 = crv[ipivot[2][icmax]]; cr22 = crv[ipivot[3][icmax]]; ur11r = 1.0 / ur11; lr21 = ur11r * cr21; ur22 = cr22 - ur12 * lr21; /* if smaller pivot < smin, use smin */ if (fabs(ur22) < smin) ur22 = smin; if (rswap[icmax]) { b1 = bval2; b2 = bval1; } else { b1 = bval1; b2 = bval2; } b2 -= lr21 * b1; bbnd = GSL_MAX(fabs(b1 * (ur22 * ur11r)), fabs(b2)); if (bbnd > 1.0 && fabs(ur22) < 1.0) { if (bbnd >= GSL_SCHUR_BIGNUM * fabs(ur22)) scale = 1.0 / bbnd; } x2 = (b2 * scale) / ur22; x1 = (scale * b1) * ur11r - x2 * (ur11r * ur12); if (zswap[icmax]) { gsl_vector_set(x, 0, x2); gsl_vector_set(x, 1, x1); } else { gsl_vector_set(x, 0, x1); gsl_vector_set(x, 1, x2); } *xnorm = GSL_MAX(fabs(x1), fabs(x2)); /* further scaling if norm(A) norm(X) > overflow */ if (*xnorm > 1.0 && cmax > 1.0) { if (*xnorm > GSL_SCHUR_BIGNUM / cmax) { temp = cmax / GSL_SCHUR_BIGNUM; gsl_blas_dscal(temp, x); *xnorm *= temp; scale *= temp; } } } /* if (N == 2) */ *s = scale; return GSL_SUCCESS; } /* gsl_schur_solve_equation() */ /* gsl_schur_solve_equation_z() Solve the equation which comes up in the back substitution when computing eigenvectors corresponding to complex eigenvalues. The equation that is solved is: (ca*A - z*D)*x = s*b where A is n-by-n with n = 1 or 2 D is a n-by-n diagonal matrix b and x are n-by-1 complex vectors s is a scaling factor set by this function to prevent overflow in x Inputs: ca - coefficient multiplying A A - square matrix (n-by-n) z - complex scalar (eigenvalue) d1 - (1,1) element in diagonal matrix D d2 - (2,2) element in diagonal matrix D b - right hand side vector x - (output) where to store solution s - (output) scale factor xnorm - (output) infinity norm of X smin - lower bound on singular values of A - if ca*A - z*D is less than this value, we'll use smin*I instead. This value should be a safe distance above underflow. Notes: 1) A and b are not changed on output 2) Based on lapack routine DLALN2 */ int gsl_schur_solve_equation_z(double ca, const gsl_matrix *A, gsl_complex *z, double d1, double d2, const gsl_vector_complex *b, gsl_vector_complex *x, double *s, double *xnorm, double smin) { size_t N = A->size1; double scale = 1.0; double bnorm; if (N == 1) { double cr, /* denominator */ ci, cnorm; /* |c| */ gsl_complex bval, c, xval, tmp; /* we have a 1-by-1 (complex) scalar system to solve */ /* c = ca*a - z*d1 */ cr = ca * gsl_matrix_get(A, 0, 0) - GSL_REAL(*z) * d1; ci = -GSL_IMAG(*z) * d1; cnorm = fabs(cr) + fabs(ci); if (cnorm < smin) { /* set c = smin*I */ cr = smin; ci = 0.0; cnorm = smin; } /* check scaling for x = b / c */ bval = gsl_vector_complex_get(b, 0); bnorm = fabs(GSL_REAL(bval)) + fabs(GSL_IMAG(bval)); if (cnorm < 1.0 && bnorm > 1.0) { if (bnorm > GSL_SCHUR_BIGNUM*cnorm) scale = 1.0 / bnorm; } /* compute x */ GSL_SET_COMPLEX(&tmp, scale*GSL_REAL(bval), scale*GSL_IMAG(bval)); GSL_SET_COMPLEX(&c, cr, ci); xval = gsl_complex_div(tmp, c); gsl_vector_complex_set(x, 0, xval); *xnorm = fabs(GSL_REAL(xval)) + fabs(GSL_IMAG(xval)); } /* if (N == 1) */ else { double cr[2][2], ci[2][2]; double *civ, *crv; double cmax; gsl_complex bval1, bval2; gsl_complex xval1, xval2; double xr1, xi1; size_t icmax; size_t j; double temp; double ur11, ur12, ur22, ui11, ui12, ui22, ur11r, ui11r; double ur12s, ui12s; double u22abs; double lr21, li21; double cr21, cr22, ci21, ci22; double br1, bi1, br2, bi2, bbnd; gsl_complex b1, b2; size_t ipivot[4][4] = { { 0, 1, 2, 3 }, { 1, 0, 3, 2 }, { 2, 3, 0, 1 }, { 3, 2, 1, 0 } }; int rswap[4] = { 0, 1, 0, 1 }; int zswap[4] = { 0, 0, 1, 1 }; /* * complex 2-by-2 system: * * ( ca * [ A11 A12 ] - z * [ D1 0 ] ) [ X1 ] = [ B1 ] * ( [ A21 A22 ] [ 0 D2] ) [ X2 ] [ B2 ] * * (z complex) * * where the X and B values are complex. */ civ = (double *) ci; crv = (double *) cr; /* * compute the real part of C = ca*A - z*D - use column ordering * here since porting from lapack */ cr[0][0] = ca*gsl_matrix_get(A, 0, 0) - GSL_REAL(*z)*d1; cr[1][1] = ca*gsl_matrix_get(A, 1, 1) - GSL_REAL(*z)*d2; cr[0][1] = ca*gsl_matrix_get(A, 1, 0); cr[1][0] = ca*gsl_matrix_get(A, 0, 1); /* compute the imaginary part */ ci[0][0] = -GSL_IMAG(*z) * d1; ci[0][1] = 0.0; ci[1][0] = 0.0; ci[1][1] = -GSL_IMAG(*z) * d2; cmax = 0.0; icmax = 0; for (j = 0; j < 4; ++j) { if (fabs(crv[j]) + fabs(civ[j]) > cmax) { cmax = fabs(crv[j]) + fabs(civ[j]); icmax = j; } } bval1 = gsl_vector_complex_get(b, 0); bval2 = gsl_vector_complex_get(b, 1); /* if norm(C) < smin, use smin*I */ if (cmax < smin) { bnorm = GSL_MAX(fabs(GSL_REAL(bval1)) + fabs(GSL_IMAG(bval1)), fabs(GSL_REAL(bval2)) + fabs(GSL_IMAG(bval2))); if (smin < 1.0 && bnorm > 1.0) { if (bnorm > GSL_SCHUR_BIGNUM*smin) scale = 1.0 / bnorm; } temp = scale / smin; xval1 = gsl_complex_mul_real(bval1, temp); xval2 = gsl_complex_mul_real(bval2, temp); gsl_vector_complex_set(x, 0, xval1); gsl_vector_complex_set(x, 1, xval2); *xnorm = temp * bnorm; *s = scale; return GSL_SUCCESS; } /* gaussian elimination with complete pivoting */ ur11 = crv[icmax]; ui11 = civ[icmax]; cr21 = crv[ipivot[1][icmax]]; ci21 = civ[ipivot[1][icmax]]; ur12 = crv[ipivot[2][icmax]]; ui12 = civ[ipivot[2][icmax]]; cr22 = crv[ipivot[3][icmax]]; ci22 = civ[ipivot[3][icmax]]; if (icmax == 0 || icmax == 3) { /* off diagonals of pivoted C are real */ if (fabs(ur11) > fabs(ui11)) { temp = ui11 / ur11; ur11r = 1.0 / (ur11 * (1.0 + temp*temp)); ui11r = -temp * ur11r; } else { temp = ur11 / ui11; ui11r = -1.0 / (ui11 * (1.0 + temp*temp)); ur11r = -temp*ui11r; } lr21 = cr21 * ur11r; li21 = cr21 * ui11r; ur12s = ur12 * ur11r; ui12s = ur12 * ui11r; ur22 = cr22 - ur12 * lr21; ui22 = ci22 - ur12 * li21; } else { /* diagonals of pivoted C are real */ ur11r = 1.0 / ur11; ui11r = 0.0; lr21 = cr21 * ur11r; li21 = ci21 * ur11r; ur12s = ur12 * ur11r; ui12s = ui12 * ur11r; ur22 = cr22 - ur12 * lr21 + ui12 * li21; ui22 = -ur12 * li21 - ui12 * lr21; } u22abs = fabs(ur22) + fabs(ui22); /* if smaller pivot < smin, use smin */ if (u22abs < smin) { ur22 = smin; ui22 = 0.0; } if (rswap[icmax]) { br2 = GSL_REAL(bval1); bi2 = GSL_IMAG(bval1); br1 = GSL_REAL(bval2); bi1 = GSL_IMAG(bval2); } else { br1 = GSL_REAL(bval1); bi1 = GSL_IMAG(bval1); br2 = GSL_REAL(bval2); bi2 = GSL_IMAG(bval2); } br2 += li21*bi1 - lr21*br1; bi2 -= li21*br1 + lr21*bi1; bbnd = GSL_MAX((fabs(br1) + fabs(bi1)) * (u22abs * (fabs(ur11r) + fabs(ui11r))), fabs(br2) + fabs(bi2)); if (bbnd > 1.0 && u22abs < 1.0) { if (bbnd >= GSL_SCHUR_BIGNUM*u22abs) { scale = 1.0 / bbnd; br1 *= scale; bi1 *= scale; br2 *= scale; bi2 *= scale; } } GSL_SET_COMPLEX(&b1, br2, bi2); GSL_SET_COMPLEX(&b2, ur22, ui22); xval2 = gsl_complex_div(b1, b2); xr1 = ur11r*br1 - ui11r*bi1 - ur12s*GSL_REAL(xval2) + ui12s*GSL_IMAG(xval2); xi1 = ui11r*br1 + ur11r*bi1 - ui12s*GSL_REAL(xval2) - ur12s*GSL_IMAG(xval2); GSL_SET_COMPLEX(&xval1, xr1, xi1); if (zswap[icmax]) { gsl_vector_complex_set(x, 0, xval2); gsl_vector_complex_set(x, 1, xval1); } else { gsl_vector_complex_set(x, 0, xval1); gsl_vector_complex_set(x, 1, xval2); } *xnorm = GSL_MAX(fabs(GSL_REAL(xval1)) + fabs(GSL_IMAG(xval1)), fabs(GSL_REAL(xval2)) + fabs(GSL_IMAG(xval2))); /* further scaling if norm(A) norm(X) > overflow */ if (*xnorm > 1.0 && cmax > 1.0) { if (*xnorm > GSL_SCHUR_BIGNUM / cmax) { temp = cmax / GSL_SCHUR_BIGNUM; gsl_blas_zdscal(temp, x); *xnorm *= temp; scale *= temp; } } } /* if (N == 2) */ *s = scale; return GSL_SUCCESS; } /* gsl_schur_solve_equation_z() */ sources_5316/external/gsl/gsl_cblas__dsyr2.c0000664000176700017670000000056711723710247017727 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dsyr2 (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const double alpha, const double *X, const int incX, const double *Y, const int incY, double *A, const int lda) { #define BASE double #include "gsl_cblas__source_syr2.h" #undef BASE } sources_5316/external/gsl/gsl_permutation__permute.c0000664000176700017670000000407711723710247021630 0ustar paulpaul#include "gsl__config.h" #include "gsl_errno.h" #include "gsl_vector.h" #include "gsl_permute.h" #include "gsl_permute_vector.h" #define BASE_GSL_COMPLEX_LONG #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_LONG #define BASE_GSL_COMPLEX #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX #define BASE_GSL_COMPLEX_FLOAT #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_GSL_COMPLEX_FLOAT #define BASE_LONG_DOUBLE #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_LONG_DOUBLE #define BASE_DOUBLE #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_DOUBLE #define BASE_FLOAT #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_FLOAT #define BASE_ULONG #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_ULONG #define BASE_LONG #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_LONG #define BASE_UINT #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_UINT #define BASE_INT #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_INT #define BASE_USHORT #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_USHORT #define BASE_SHORT #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_SHORT #define BASE_UCHAR #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_UCHAR #define BASE_CHAR #include "templates_on.h" #include "gsl_permutation__permute_source.c" #include "templates_off.h" #undef BASE_CHAR sources_5316/external/gsl/gsl_sys.h0000664000176700017670000000364211705263724016204 0ustar paulpaul/* sys/gsl_sys.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SYS_H__ #define __GSL_SYS_H__ #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS double gsl_log1p (const double x); double gsl_expm1 (const double x); double gsl_hypot (const double x, const double y); double gsl_hypot3 (const double x, const double y, const double z); double gsl_acosh (const double x); double gsl_asinh (const double x); double gsl_atanh (const double x); int gsl_isnan (const double x); int gsl_isinf (const double x); int gsl_finite (const double x); double gsl_nan (void); double gsl_posinf (void); double gsl_neginf (void); double gsl_fdiv (const double x, const double y); double gsl_coerce_double (const double x); float gsl_coerce_float (const float x); long double gsl_coerce_long_double (const long double x); double gsl_ldexp(const double x, const int e); double gsl_frexp(const double x, int * e); int gsl_fcmp (const double x1, const double x2, const double epsilon); __END_DECLS #endif /* __GSL_SYS_H__ */ sources_5316/external/gsl/gsl_specfunc__exp.c0000664000176700017670000003674211723710247020206 0ustar paulpaul/* specfunc/exp.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_gamma.h" #include "gsl_sf_exp.h" #include "gsl_specfunc__error.h" /* Evaluate the continued fraction for exprel. * [Abramowitz+Stegun, 4.2.41] */ static int exprel_n_CF(const int N, const double x, gsl_sf_result * result) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 5000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = 1.0; double b1 = 1.0; double a2 = -x; double b2 = N+1; double an, bn; double fn; double An = b1*Anm1 + a1*Anm2; /* A1 */ double Bn = b1*Bnm1 + a1*Bnm2; /* B1 */ /* One explicit step, before we get to the main pattern. */ n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; An = b2*Anm1 + a2*Anm2; /* A2 */ Bn = b2*Bnm1 + a2*Bnm2; /* B2 */ fn = An/Bn; while(n < maxiter) { double old_fn; double del; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; an = ( GSL_IS_ODD(n) ? ((n-1)/2)*x : -(N+(n/2)-1)*x ); bn = N + n - 1; An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 2.0*GSL_DBL_EPSILON) break; } result->val = fn; result->err = 2.0*(n+1.0)*GSL_DBL_EPSILON*fabs(fn); if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_exp_e(const double x, gsl_sf_result * result) { if(x > GSL_LOG_DBL_MAX) { OVERFLOW_ERROR(result); } else if(x < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else { result->val = exp(x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_exp_e10_e(const double x, gsl_sf_result_e10 * result) { if(x > INT_MAX-1) { OVERFLOW_ERROR_E10(result); } else if(x < INT_MIN+1) { UNDERFLOW_ERROR_E10(result); } else { const int N = (int) floor(x/M_LN10); result->val = exp(x-N*M_LN10); result->err = 2.0 * (fabs(x)+1.0) * GSL_DBL_EPSILON * fabs(result->val); result->e10 = N; return GSL_SUCCESS; } } int gsl_sf_exp_mult_e(const double x, const double y, gsl_sf_result * result) { const double ay = fabs(y); if(y == 0.0) { result->val = 0.0; result->err = 0.0; return GSL_SUCCESS; } else if( ( x < 0.5*GSL_LOG_DBL_MAX && x > 0.5*GSL_LOG_DBL_MIN) && (ay < 0.8*GSL_SQRT_DBL_MAX && ay > 1.2*GSL_SQRT_DBL_MIN) ) { const double ex = exp(x); result->val = y * ex; result->err = (2.0 + fabs(x)) * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double ly = log(ay); const double lnr = x + ly; if(lnr > GSL_LOG_DBL_MAX - 0.01) { OVERFLOW_ERROR(result); } else if(lnr < GSL_LOG_DBL_MIN + 0.01) { UNDERFLOW_ERROR(result); } else { const double sy = GSL_SIGN(y); const double M = floor(x); const double N = floor(ly); const double a = x - M; const double b = ly - N; const double berr = 2.0 * GSL_DBL_EPSILON * (fabs(ly) + fabs(N)); result->val = sy * exp(M+N) * exp(a+b); result->err = berr * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * (M + N + 1.0) * fabs(result->val); return GSL_SUCCESS; } } } int gsl_sf_exp_mult_e10_e(const double x, const double y, gsl_sf_result_e10 * result) { const double ay = fabs(y); if(y == 0.0) { result->val = 0.0; result->err = 0.0; result->e10 = 0; return GSL_SUCCESS; } else if( ( x < 0.5*GSL_LOG_DBL_MAX && x > 0.5*GSL_LOG_DBL_MIN) && (ay < 0.8*GSL_SQRT_DBL_MAX && ay > 1.2*GSL_SQRT_DBL_MIN) ) { const double ex = exp(x); result->val = y * ex; result->err = (2.0 + fabs(x)) * GSL_DBL_EPSILON * fabs(result->val); result->e10 = 0; return GSL_SUCCESS; } else { const double ly = log(ay); const double l10_val = (x + ly)/M_LN10; if(l10_val > INT_MAX-1) { OVERFLOW_ERROR_E10(result); } else if(l10_val < INT_MIN+1) { UNDERFLOW_ERROR_E10(result); } else { const double sy = GSL_SIGN(y); const int N = (int) floor(l10_val); const double arg_val = (l10_val - N) * M_LN10; const double arg_err = 2.0 * GSL_DBL_EPSILON * fabs(ly); result->val = sy * exp(arg_val); result->err = arg_err * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->e10 = N; return GSL_SUCCESS; } } } int gsl_sf_exp_mult_err_e(const double x, const double dx, const double y, const double dy, gsl_sf_result * result) { const double ay = fabs(y); if(y == 0.0) { result->val = 0.0; result->err = fabs(dy * exp(x)); return GSL_SUCCESS; } else if( ( x < 0.5*GSL_LOG_DBL_MAX && x > 0.5*GSL_LOG_DBL_MIN) && (ay < 0.8*GSL_SQRT_DBL_MAX && ay > 1.2*GSL_SQRT_DBL_MIN) ) { double ex = exp(x); result->val = y * ex; result->err = ex * (fabs(dy) + fabs(y*dx)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { const double ly = log(ay); const double lnr = x + ly; if(lnr > GSL_LOG_DBL_MAX - 0.01) { OVERFLOW_ERROR(result); } else if(lnr < GSL_LOG_DBL_MIN + 0.01) { UNDERFLOW_ERROR(result); } else { const double sy = GSL_SIGN(y); const double M = floor(x); const double N = floor(ly); const double a = x - M; const double b = ly - N; const double eMN = exp(M+N); const double eab = exp(a+b); result->val = sy * eMN * eab; result->err = eMN * eab * 2.0*GSL_DBL_EPSILON; result->err += eMN * eab * fabs(dy/y); result->err += eMN * eab * fabs(dx); return GSL_SUCCESS; } } } int gsl_sf_exp_mult_err_e10_e(const double x, const double dx, const double y, const double dy, gsl_sf_result_e10 * result) { const double ay = fabs(y); if(y == 0.0) { result->val = 0.0; result->err = fabs(dy * exp(x)); result->e10 = 0; return GSL_SUCCESS; } else if( ( x < 0.5*GSL_LOG_DBL_MAX && x > 0.5*GSL_LOG_DBL_MIN) && (ay < 0.8*GSL_SQRT_DBL_MAX && ay > 1.2*GSL_SQRT_DBL_MIN) ) { const double ex = exp(x); result->val = y * ex; result->err = ex * (fabs(dy) + fabs(y*dx)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->e10 = 0; return GSL_SUCCESS; } else { const double ly = log(ay); const double l10_val = (x + ly)/M_LN10; if(l10_val > INT_MAX-1) { OVERFLOW_ERROR_E10(result); } else if(l10_val < INT_MIN+1) { UNDERFLOW_ERROR_E10(result); } else { const double sy = GSL_SIGN(y); const int N = (int) floor(l10_val); const double arg_val = (l10_val - N) * M_LN10; const double arg_err = dy/fabs(y) + dx + 2.0*GSL_DBL_EPSILON*fabs(arg_val); result->val = sy * exp(arg_val); result->err = arg_err * fabs(result->val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); result->e10 = N; return GSL_SUCCESS; } } } int gsl_sf_expm1_e(const double x, gsl_sf_result * result) { const double cut = 0.002; if(x < GSL_LOG_DBL_MIN) { result->val = -1.0; result->err = GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(x < -cut) { result->val = exp(x) - 1.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < cut) { result->val = x * (1.0 + 0.5*x*(1.0 + x/3.0*(1.0 + 0.25*x*(1.0 + 0.2*x)))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < GSL_LOG_DBL_MAX) { result->val = exp(x) - 1.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_exprel_e(const double x, gsl_sf_result * result) { const double cut = 0.002; if(x < GSL_LOG_DBL_MIN) { result->val = -1.0/x; result->err = GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -cut) { result->val = (exp(x) - 1.0)/x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < cut) { result->val = (1.0 + 0.5*x*(1.0 + x/3.0*(1.0 + 0.25*x*(1.0 + 0.2*x)))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < GSL_LOG_DBL_MAX) { result->val = (exp(x) - 1.0)/x; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_exprel_2_e(double x, gsl_sf_result * result) { const double cut = 0.002; if(x < GSL_LOG_DBL_MIN) { result->val = -2.0/x*(1.0 + 1.0/x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < -cut) { result->val = 2.0*(exp(x) - 1.0 - x)/(x*x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < cut) { result->val = (1.0 + 1.0/3.0*x*(1.0 + 0.25*x*(1.0 + 0.2*x*(1.0 + 1.0/6.0*x)))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < GSL_LOG_DBL_MAX) { result->val = 2.0*(exp(x) - 1.0 - x)/(x*x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { OVERFLOW_ERROR(result); } } int gsl_sf_exprel_n_e(const int N, const double x, gsl_sf_result * result) { if(N < 0) { DOMAIN_ERROR(result); } else if(x == 0.0) { result->val = 1.0; result->err = 0.0; return GSL_SUCCESS; } else if(fabs(x) < GSL_ROOT3_DBL_EPSILON * N) { result->val = 1.0 + x/(N+1) * (1.0 + x/(N+2)); result->err = 2.0 * GSL_DBL_EPSILON; return GSL_SUCCESS; } else if(N == 0) { return gsl_sf_exp_e(x, result); } else if(N == 1) { return gsl_sf_exprel_e(x, result); } else if(N == 2) { return gsl_sf_exprel_2_e(x, result); } else { if(x > N && (-x + N*(1.0 + log(x/N)) < GSL_LOG_DBL_EPSILON)) { /* x is much larger than n. * Ignore polynomial part, so * exprel_N(x) ~= e^x N!/x^N */ gsl_sf_result lnf_N; double lnr_val; double lnr_err; double lnterm; gsl_sf_lnfact_e(N, &lnf_N); lnterm = N*log(x); lnr_val = x + lnf_N.val - lnterm; lnr_err = GSL_DBL_EPSILON * (fabs(x) + fabs(lnf_N.val) + fabs(lnterm)); lnr_err += lnf_N.err; return gsl_sf_exp_err_e(lnr_val, lnr_err, result); } else if(x > N) { /* Write the identity * exprel_n(x) = e^x n! / x^n (1 - Gamma[n,x]/Gamma[n]) * then use the asymptotic expansion * Gamma[n,x] ~ x^(n-1) e^(-x) (1 + (n-1)/x + (n-1)(n-2)/x^2 + ...) */ double ln_x = log(x); gsl_sf_result lnf_N; double lg_N; double lnpre_val; double lnpre_err; gsl_sf_lnfact_e(N, &lnf_N); /* log(N!) */ lg_N = lnf_N.val - log(N); /* log(Gamma(N)) */ lnpre_val = x + lnf_N.val - N*ln_x; lnpre_err = GSL_DBL_EPSILON * (fabs(x) + fabs(lnf_N.val) + fabs(N*ln_x)); lnpre_err += lnf_N.err; if(lnpre_val < GSL_LOG_DBL_MAX - 5.0) { int stat_eG; gsl_sf_result bigG_ratio; gsl_sf_result pre; int stat_ex = gsl_sf_exp_err_e(lnpre_val, lnpre_err, &pre); double ln_bigG_ratio_pre = -x + (N-1)*ln_x - lg_N; double bigGsum = 1.0; double term = 1.0; int k; for(k=1; kval = pre.val * (1.0 - bigG_ratio.val); result->err = pre.val * (2.0*GSL_DBL_EPSILON + bigG_ratio.err); result->err += pre.err * fabs(1.0 - bigG_ratio.val); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_ex; } else { result->val = 0.0; result->err = 0.0; return stat_eG; } } else { OVERFLOW_ERROR(result); } } else if(x > -10.0*N) { return exprel_n_CF(N, x, result); } else { /* x -> -Inf asymptotic: * exprel_n(x) ~ e^x n!/x^n - n/x (1 + (n-1)/x + (n-1)(n-2)/x + ...) * ~ - n/x (1 + (n-1)/x + (n-1)(n-2)/x + ...) */ double sum = 1.0; double term = 1.0; int k; for(k=1; kval = -N/x * sum; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } } int gsl_sf_exp_err_e(const double x, const double dx, gsl_sf_result * result) { const double adx = fabs(dx); /* CHECK_POINTER(result) */ if(x + adx > GSL_LOG_DBL_MAX) { OVERFLOW_ERROR(result); } else if(x - adx < GSL_LOG_DBL_MIN) { UNDERFLOW_ERROR(result); } else { const double ex = exp(x); const double edx = exp(adx); result->val = ex; result->err = ex * GSL_MAX_DBL(GSL_DBL_EPSILON, edx - 1.0/edx); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } } int gsl_sf_exp_err_e10_e(const double x, const double dx, gsl_sf_result_e10 * result) { const double adx = fabs(dx); /* CHECK_POINTER(result) */ if(x + adx > INT_MAX - 1) { OVERFLOW_ERROR_E10(result); } else if(x - adx < INT_MIN + 1) { UNDERFLOW_ERROR_E10(result); } else { const int N = (int)floor(x/M_LN10); const double ex = exp(x-N*M_LN10); result->val = ex; result->err = ex * (2.0 * GSL_DBL_EPSILON * (fabs(x) + 1.0) + adx); result->e10 = N; return GSL_SUCCESS; } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_exp(const double x) { EVAL_RESULT(gsl_sf_exp_e(x, &result)); } double gsl_sf_exp_mult(const double x, const double y) { EVAL_RESULT(gsl_sf_exp_mult_e(x, y, &result)); } double gsl_sf_expm1(const double x) { EVAL_RESULT(gsl_sf_expm1_e(x, &result)); } double gsl_sf_exprel(const double x) { EVAL_RESULT(gsl_sf_exprel_e(x, &result)); } double gsl_sf_exprel_2(const double x) { EVAL_RESULT(gsl_sf_exprel_2_e(x, &result)); } double gsl_sf_exprel_n(const int n, const double x) { EVAL_RESULT(gsl_sf_exprel_n_e(n, x, &result)); } sources_5316/external/gsl/gsl_cdf__laplaceinv.c0000664000176700017670000000271511723710247020447 0ustar paulpaul/* cdf/laplaceinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_laplace_Pinv (const double P, const double a) { double x; if (P == 1.0) { return GSL_POSINF; } else if (P == 0.0) { return GSL_NEGINF; } if (P < 0.5) { x = a * log(2*P); } else { x = -a * log(2*(1-P)); } return x; } double gsl_cdf_laplace_Qinv (const double Q, const double a) { double x; if (Q == 0.0) { return GSL_POSINF; } else if (Q == 1.0) { return GSL_NEGINF; } if (Q < 0.5) { x = -a * log(2*Q); } else { x = a * log(2*(1-Q)); } return x; } sources_5316/external/gsl/gsl_roots__fdfsolver.c0000664000176700017670000000413311723710247020731 0ustar paulpaul/* roots/fdfsolver.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Reid Priedhorsky, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include #include "gsl_errno.h" #include "gsl_roots.h" gsl_root_fdfsolver * gsl_root_fdfsolver_alloc (const gsl_root_fdfsolver_type * T) { gsl_root_fdfsolver * s = (gsl_root_fdfsolver *) malloc (sizeof (gsl_root_fdfsolver)); if (s == 0) { GSL_ERROR_VAL ("failed to allocate space for root solver struct", GSL_ENOMEM, 0); }; s->state = malloc (T->size); if (s->state == 0) { free (s); /* exception in constructor, avoid memory leak */ GSL_ERROR_VAL ("failed to allocate space for root solver state", GSL_ENOMEM, 0); }; s->type = T ; s->fdf = NULL; return s; } int gsl_root_fdfsolver_set (gsl_root_fdfsolver * s, gsl_function_fdf * f, double root) { s->fdf = f; s->root = root; return (s->type->set) (s->state, s->fdf, &(s->root)); } int gsl_root_fdfsolver_iterate (gsl_root_fdfsolver * s) { return (s->type->iterate) (s->state, s->fdf, &(s->root)); } void gsl_root_fdfsolver_free (gsl_root_fdfsolver * s) { free (s->state); free (s); } const char * gsl_root_fdfsolver_name (const gsl_root_fdfsolver * s) { return s->type->name; } double gsl_root_fdfsolver_root (const gsl_root_fdfsolver * s) { return s->root; } sources_5316/external/gsl/gsl_fft__hc_unpack.c0000664000176700017670000000547611723710247020316 0ustar paulpaul/* fft/hc_unpack.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION(gsl_fft_halfcomplex,unpack) (const BASE halfcomplex_coefficient[], BASE complex_coefficient[], const size_t stride, const size_t n) { size_t i; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } REAL(complex_coefficient,stride,0) = halfcomplex_coefficient[0]; IMAG(complex_coefficient,stride,0) = 0.0; for (i = 1; i < n - i; i++) { const ATOMIC hc_real = halfcomplex_coefficient[(2 * i - 1) * stride]; const ATOMIC hc_imag = halfcomplex_coefficient[2 * i * stride]; REAL(complex_coefficient,stride,i) = hc_real; IMAG(complex_coefficient,stride,i) = hc_imag; REAL(complex_coefficient,stride,n - i) = hc_real; IMAG(complex_coefficient,stride,n - i) = -hc_imag; } if (i == n - i) { REAL(complex_coefficient,stride,i) = halfcomplex_coefficient[(n - 1) * stride]; IMAG(complex_coefficient,stride,i) = 0.0; } return 0; } int FUNCTION(gsl_fft_halfcomplex,radix2_unpack) (const BASE halfcomplex_coefficient[], BASE complex_coefficient[], const size_t stride, const size_t n) { size_t i; if (n == 0) { GSL_ERROR ("length n must be positive integer", GSL_EDOM); } REAL(complex_coefficient,stride,0) = halfcomplex_coefficient[0]; IMAG(complex_coefficient,stride,0) = 0.0; for (i = 1; i < n - i; i++) { const ATOMIC hc_real = halfcomplex_coefficient[i * stride]; const ATOMIC hc_imag = halfcomplex_coefficient[(n - i) * stride]; REAL(complex_coefficient,stride,i) = hc_real; IMAG(complex_coefficient,stride,i) = hc_imag; REAL(complex_coefficient,stride,n - i) = hc_real; IMAG(complex_coefficient,stride,n - i) = -hc_imag; } if (i == n - i) { REAL(complex_coefficient,stride,i) = halfcomplex_coefficient[i * stride]; IMAG(complex_coefficient,stride,i) = 0.0; } return 0; } sources_5316/external/gsl/gsl_vector__init_source.c0000664000176700017670000001204111723710247021413 0ustar paulpaul/* vector/init_source.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ TYPE (gsl_vector) * FUNCTION (gsl_vector, alloc) (const size_t n) { TYPE (gsl_block) * block; TYPE (gsl_vector) * v; if (n == 0) { GSL_ERROR_VAL ("vector length n must be positive integer", GSL_EINVAL, 0); } v = (TYPE (gsl_vector) *) malloc (sizeof (TYPE (gsl_vector))); if (v == 0) { GSL_ERROR_VAL ("failed to allocate space for vector struct", GSL_ENOMEM, 0); } block = FUNCTION (gsl_block,alloc) (n); if (block == 0) { free (v) ; GSL_ERROR_VAL ("failed to allocate space for block", GSL_ENOMEM, 0); } v->data = block->data ; v->size = n; v->stride = 1; v->block = block; v->owner = 1; return v; } TYPE (gsl_vector) * FUNCTION (gsl_vector, calloc) (const size_t n) { size_t i; TYPE (gsl_vector) * v = FUNCTION (gsl_vector, alloc) (n); if (v == 0) return 0; /* initialize vector to zero */ for (i = 0; i < MULTIPLICITY * n; i++) { v->data[i] = 0; } return v; } TYPE (gsl_vector) * FUNCTION (gsl_vector, alloc_from_block) (TYPE(gsl_block) * block, const size_t offset, const size_t n, const size_t stride) { TYPE (gsl_vector) * v; if (n == 0) { GSL_ERROR_VAL ("vector length n must be positive integer", GSL_EINVAL, 0); } if (stride == 0) { GSL_ERROR_VAL ("stride must be positive integer", GSL_EINVAL, 0); } if (block->size <= offset + (n - 1) * stride) { GSL_ERROR_VAL ("vector would extend past end of block", GSL_EINVAL, 0); } v = (TYPE (gsl_vector) *) malloc (sizeof (TYPE (gsl_vector))); if (v == 0) { GSL_ERROR_VAL ("failed to allocate space for vector struct", GSL_ENOMEM, 0); } v->data = block->data + MULTIPLICITY * offset ; v->size = n; v->stride = stride; v->block = block; v->owner = 0; return v; } TYPE (gsl_vector) * FUNCTION (gsl_vector, alloc_from_vector) (TYPE(gsl_vector) * w, const size_t offset, const size_t n, const size_t stride) { TYPE (gsl_vector) * v; if (n == 0) { GSL_ERROR_VAL ("vector length n must be positive integer", GSL_EINVAL, 0); } if (stride == 0) { GSL_ERROR_VAL ("stride must be positive integer", GSL_EINVAL, 0); } if (offset + (n - 1) * stride >= w->size) { GSL_ERROR_VAL ("vector would extend past end of block", GSL_EINVAL, 0); } v = (TYPE (gsl_vector) *) malloc (sizeof (TYPE (gsl_vector))); if (v == 0) { GSL_ERROR_VAL ("failed to allocate space for vector struct", GSL_ENOMEM, 0); } v->data = w->data + MULTIPLICITY * w->stride * offset ; v->size = n; v->stride = stride * w->stride; v->block = w->block; v->owner = 0; return v; } void FUNCTION (gsl_vector, free) (TYPE (gsl_vector) * v) { if (v->owner) { FUNCTION(gsl_block, free) (v->block) ; } free (v); } void FUNCTION (gsl_vector, set_all) (TYPE (gsl_vector) * v, BASE x) { ATOMIC * const data = v->data; const size_t n = v->size; const size_t stride = v->stride; size_t i; for (i = 0; i < n; i++) { *(BASE *) (data + MULTIPLICITY * i * stride) = x; } } void FUNCTION (gsl_vector, set_zero) (TYPE (gsl_vector) * v) { ATOMIC * const data = v->data; const size_t n = v->size; const size_t stride = v->stride; const BASE zero = ZERO ; size_t i; for (i = 0; i < n; i++) { *(BASE *) (data + MULTIPLICITY * i * stride) = zero; } } int FUNCTION (gsl_vector, set_basis) (TYPE (gsl_vector) * v, size_t i) { ATOMIC * const data = v->data; const size_t n = v->size; const size_t stride = v->stride; const BASE zero = ZERO ; const BASE one = ONE; size_t k; if (i >= n) { GSL_ERROR ("index out of range", GSL_EINVAL); } for (k = 0; k < n; k++) { *(BASE *) (data + MULTIPLICITY * k * stride) = zero; } *(BASE *) (data + MULTIPLICITY * i * stride) = one; return GSL_SUCCESS; } sources_5316/external/gsl/gsl_fft__real_pass.h0000664000176700017670000000655311705263724020341 0ustar paulpaul/* fft/real_pass.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ static void FUNCTION(fft_real,pass_2) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]); static void FUNCTION(fft_real,pass_3) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[]); static void FUNCTION(fft_real,pass_4) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[]); static void FUNCTION(fft_real,pass_5) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle1[], const TYPE(gsl_complex) twiddle2[], const TYPE(gsl_complex) twiddle3[], const TYPE(gsl_complex) twiddle4[]); static void FUNCTION(fft_real,pass_n) (const BASE in[], const size_t istride, BASE out[], const size_t ostride, const size_t factor, const size_t product, const size_t n, const TYPE(gsl_complex) twiddle[]); sources_5316/external/gsl/gsl_cblas__ccopy.c0000664000176700017670000000037111723710247017772 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ccopy (const int N, const void *X, const int incX, void *Y, const int incY) { #define BASE float #include "gsl_cblas__source_copy_c.h" #undef BASE } sources_5316/external/gsl/gsl_cblas__source_iamax_c.h0000664000176700017670000000215011705263724021643 0ustar paulpaul/* blas/source_iamax_c.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { BASE max = 0.0; INDEX ix = 0; INDEX i; CBLAS_INDEX result = 0; if (incX <= 0) { return 0; } for (i = 0; i < N; i++) { const BASE a = fabs(CONST_REAL(X, ix)) + fabs(CONST_IMAG(X, ix)); if (a > max) { max = a; result = i; } ix += incX; } return result; } sources_5316/external/gsl/gsl_multifit__lmiterate.c0000664000176700017670000001216111723710247021414 0ustar paulpaulstatic int iterate (void *vstate, gsl_multifit_function_fdf * fdf, gsl_vector * x, gsl_vector * f, gsl_matrix * J, gsl_vector * dx, int scale) { lmder_state_t *state = (lmder_state_t *) vstate; gsl_matrix *r = state->r; gsl_vector *tau = state->tau; gsl_vector *diag = state->diag; gsl_vector *qtf = state->qtf; gsl_vector *x_trial = state->x_trial; gsl_vector *f_trial = state->f_trial; gsl_vector *rptdx = state->rptdx; gsl_vector *newton = state->newton; gsl_vector *gradient = state->gradient; gsl_vector *sdiag = state->sdiag; gsl_vector *w = state->w; gsl_vector *work1 = state->work1; gsl_permutation *perm = state->perm; double prered, actred; double pnorm, fnorm1, fnorm1p, gnorm; double ratio; double dirder; int iter = 0; double p1 = 0.1, p25 = 0.25, p5 = 0.5, p75 = 0.75, p0001 = 0.0001; if (state->fnorm == 0.0) { return GSL_SUCCESS; } /* Compute qtf = Q^T f */ gsl_vector_memcpy (qtf, f); gsl_linalg_QR_QTvec (r, tau, qtf); /* Compute norm of scaled gradient */ compute_gradient_direction (r, perm, qtf, diag, gradient); { size_t iamax = gsl_blas_idamax (gradient); gnorm = fabs(gsl_vector_get (gradient, iamax) / state->fnorm); } /* Determine the Levenberg-Marquardt parameter */ lm_iteration: iter++ ; { int status = lmpar (r, perm, qtf, diag, state->delta, &(state->par), newton, gradient, sdiag, dx, w); if (status) return status; } /* Take a trial step */ gsl_vector_scale (dx, -1.0); /* reverse the step to go downhill */ compute_trial_step (x, dx, state->x_trial); pnorm = scaled_enorm (diag, dx); if (state->iter == 1) { if (pnorm < state->delta) { #ifdef DEBUG printf("set delta = pnorm = %g\n" , pnorm); #endif state->delta = pnorm; } } /* Evaluate function at x + p */ /* return immediately if evaluation raised error */ { int status = GSL_MULTIFIT_FN_EVAL_F (fdf, x_trial, f_trial); if (status) return status; } fnorm1 = enorm (f_trial); /* Compute the scaled actual reduction */ actred = compute_actual_reduction (state->fnorm, fnorm1); #ifdef DEBUG printf("lmiterate: fnorm = %g fnorm1 = %g actred = %g\n", state->fnorm, fnorm1, actred); printf("r = "); gsl_matrix_fprintf(stdout, r, "%g"); printf("perm = "); gsl_permutation_fprintf(stdout, perm, "%d"); printf("dx = "); gsl_vector_fprintf(stdout, dx, "%g"); #endif /* Compute rptdx = R P^T dx, noting that |J dx| = |R P^T dx| */ compute_rptdx (r, perm, dx, rptdx); #ifdef DEBUG printf("rptdx = "); gsl_vector_fprintf(stdout, rptdx, "%g"); #endif fnorm1p = enorm (rptdx); /* Compute the scaled predicted reduction = |J dx|^2 + 2 par |D dx|^2 */ { double t1 = fnorm1p / state->fnorm; double t2 = (sqrt(state->par) * pnorm) / state->fnorm; prered = t1 * t1 + t2 * t2 / p5; dirder = -(t1 * t1 + t2 * t2); } /* compute the ratio of the actual to predicted reduction */ if (prered > 0) { ratio = actred / prered; } else { ratio = 0; } #ifdef DEBUG printf("lmiterate: prered = %g dirder = %g ratio = %g\n", prered, dirder,ratio); #endif /* update the step bound */ if (ratio > p25) { #ifdef DEBUG printf("ratio > p25\n"); #endif if (state->par == 0 || ratio >= p75) { state->delta = pnorm / p5; state->par *= p5; #ifdef DEBUG printf("updated step bounds: delta = %g, par = %g\n", state->delta, state->par); #endif } } else { double temp = (actred >= 0) ? p5 : p5*dirder / (dirder + p5 * actred); #ifdef DEBUG printf("ratio < p25\n"); #endif if (p1 * fnorm1 >= state->fnorm || temp < p1 ) { temp = p1; } state->delta = temp * GSL_MIN_DBL (state->delta, pnorm/p1); state->par /= temp; #ifdef DEBUG printf("updated step bounds: delta = %g, par = %g\n", state->delta, state->par); #endif } /* test for successful iteration, termination and stringent tolerances */ if (ratio >= p0001) { gsl_vector_memcpy (x, x_trial); gsl_vector_memcpy (f, f_trial); /* return immediately if evaluation raised error */ { int status = GSL_MULTIFIT_FN_EVAL_DF (fdf, x_trial, J); if (status) return status; } /* wa2_j = diag_j * x_j */ state->xnorm = scaled_enorm(diag, x); state->fnorm = fnorm1; state->iter++; /* Rescale if necessary */ if (scale) { update_diag (J, diag); } { int signum; gsl_matrix_memcpy (r, J); gsl_linalg_QRPT_decomp (r, tau, perm, &signum, work1); } return GSL_SUCCESS; } else if (fabs(actred) <= GSL_DBL_EPSILON && prered <= GSL_DBL_EPSILON && p5 * ratio <= 1.0) { return GSL_ETOLF ; } else if (state->delta <= GSL_DBL_EPSILON * state->xnorm) { return GSL_ETOLX; } else if (gnorm <= GSL_DBL_EPSILON) { return GSL_ETOLG; } else if (iter < 10) { /* Repeat inner loop if unsuccessful */ goto lm_iteration; } return GSL_CONTINUE; } sources_5316/external/gsl/gsl_sf_bessel.h0000664000176700017670000003335011705263724017332 0ustar paulpaul/* specfunc/gsl_sf_bessel.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_BESSEL_H__ #define __GSL_SF_BESSEL_H__ #include #include "gsl_mode.h" #include "gsl_precision.h" #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* Regular Bessel Function J_0(x) * * exceptions: none */ int gsl_sf_bessel_J0_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_J0(const double x); /* Regular Bessel Function J_1(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_J1_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_J1(const double x); /* Regular Bessel Function J_n(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_Jn_e(int n, double x, gsl_sf_result * result); double gsl_sf_bessel_Jn(const int n, const double x); /* Regular Bessel Function J_n(x), nmin <= n <= nmax * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_Jn_array(int nmin, int nmax, double x, double * result_array); /* Irregular Bessel function Y_0(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_Y0_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_Y0(const double x); /* Irregular Bessel function Y_1(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_bessel_Y1_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_Y1(const double x); /* Irregular Bessel function Y_n(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_bessel_Yn_e(int n,const double x, gsl_sf_result * result); double gsl_sf_bessel_Yn(const int n,const double x); /* Irregular Bessel function Y_n(x), nmin <= n <= nmax * * x > 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_bessel_Yn_array(const int nmin, const int nmax, const double x, double * result_array); /* Regular modified Bessel function I_0(x) * * exceptions: GSL_EOVRFLW */ int gsl_sf_bessel_I0_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_I0(const double x); /* Regular modified Bessel function I_1(x) * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_bessel_I1_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_I1(const double x); /* Regular modified Bessel function I_n(x) * * exceptions: GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_bessel_In_e(const int n, const double x, gsl_sf_result * result); double gsl_sf_bessel_In(const int n, const double x); /* Regular modified Bessel function I_n(x) for n=nmin,...,nmax * * nmin >=0, nmax >= nmin * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_bessel_In_array(const int nmin, const int nmax, const double x, double * result_array); /* Scaled regular modified Bessel function * exp(-|x|) I_0(x) * * exceptions: none */ int gsl_sf_bessel_I0_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_I0_scaled(const double x); /* Scaled regular modified Bessel function * exp(-|x|) I_1(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_I1_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_I1_scaled(const double x); /* Scaled regular modified Bessel function * exp(-|x|) I_n(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_In_scaled_e(int n, const double x, gsl_sf_result * result); double gsl_sf_bessel_In_scaled(const int n, const double x); /* Scaled regular modified Bessel function * exp(-|x|) I_n(x) for n=nmin,...,nmax * * nmin >=0, nmax >= nmin * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_In_scaled_array(const int nmin, const int nmax, const double x, double * result_array); /* Irregular modified Bessel function K_0(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_K0_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_K0(const double x); /* Irregular modified Bessel function K_1(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_bessel_K1_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_K1(const double x); /* Irregular modified Bessel function K_n(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_bessel_Kn_e(const int n, const double x, gsl_sf_result * result); double gsl_sf_bessel_Kn(const int n, const double x); /* Irregular modified Bessel function K_n(x) for n=nmin,...,nmax * * x > 0.0, nmin >=0, nmax >= nmin * exceptions: GSL_EDOM, GSL_EOVRFLW, GSL_EUNDRFLW */ int gsl_sf_bessel_Kn_array(const int nmin, const int nmax, const double x, double * result_array); /* Scaled irregular modified Bessel function * exp(x) K_0(x) * * x > 0.0 * exceptions: GSL_EDOM */ int gsl_sf_bessel_K0_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_K0_scaled(const double x); /* Scaled irregular modified Bessel function * exp(x) K_1(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_K1_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_K1_scaled(const double x); /* Scaled irregular modified Bessel function * exp(x) K_n(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_Kn_scaled_e(int n, const double x, gsl_sf_result * result); double gsl_sf_bessel_Kn_scaled(const int n, const double x); /* Scaled irregular modified Bessel function exp(x) K_n(x) for n=nmin,...,nmax * * x > 0.0, nmin >=0, nmax >= nmin * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_Kn_scaled_array(const int nmin, const int nmax, const double x, double * result_array); /* Regular spherical Bessel function j_0(x) = sin(x)/x * * exceptions: none */ int gsl_sf_bessel_j0_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_j0(const double x); /* Regular spherical Bessel function j_1(x) = (sin(x)/x - cos(x))/x * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_j1_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_j1(const double x); /* Regular spherical Bessel function j_2(x) = ((3/x^2 - 1)sin(x) - 3cos(x)/x)/x * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_j2_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_j2(const double x); /* Regular spherical Bessel function j_l(x) * * l >= 0, x >= 0.0 * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_jl_e(const int l, const double x, gsl_sf_result * result); double gsl_sf_bessel_jl(const int l, const double x); /* Regular spherical Bessel function j_l(x) for l=0,1,...,lmax * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_jl_array(const int lmax, const double x, double * result_array); /* Regular spherical Bessel function j_l(x) for l=0,1,...,lmax * Uses Steed's method. * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_jl_steed_array(const int lmax, const double x, double * jl_x_array); /* Irregular spherical Bessel function y_0(x) * * exceptions: none */ int gsl_sf_bessel_y0_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_y0(const double x); /* Irregular spherical Bessel function y_1(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_y1_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_y1(const double x); /* Irregular spherical Bessel function y_2(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_y2_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_y2(const double x); /* Irregular spherical Bessel function y_l(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_yl_e(int l, const double x, gsl_sf_result * result); double gsl_sf_bessel_yl(const int l, const double x); /* Irregular spherical Bessel function y_l(x) for l=0,1,...,lmax * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_yl_array(const int lmax, const double x, double * result_array); /* Regular scaled modified spherical Bessel function * * Exp[-|x|] i_0(x) * * exceptions: none */ int gsl_sf_bessel_i0_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_i0_scaled(const double x); /* Regular scaled modified spherical Bessel function * * Exp[-|x|] i_1(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_i1_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_i1_scaled(const double x); /* Regular scaled modified spherical Bessel function * * Exp[-|x|] i_2(x) * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_i2_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_i2_scaled(const double x); /* Regular scaled modified spherical Bessel functions * * Exp[-|x|] i_l(x) * * i_l(x) = Sqrt[Pi/(2x)] BesselI[l+1/2,x] * * l >= 0 * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_il_scaled_e(const int l, double x, gsl_sf_result * result); double gsl_sf_bessel_il_scaled(const int l, const double x); /* Regular scaled modified spherical Bessel functions * * Exp[-|x|] i_l(x) * for l=0,1,...,lmax * * exceptions: GSL_EUNDRFLW */ int gsl_sf_bessel_il_scaled_array(const int lmax, const double x, double * result_array); /* Irregular scaled modified spherical Bessel function * Exp[x] k_0(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_k0_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_k0_scaled(const double x); /* Irregular modified spherical Bessel function * Exp[x] k_1(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_bessel_k1_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_k1_scaled(const double x); /* Irregular modified spherical Bessel function * Exp[x] k_2(x) * * x > 0.0 * exceptions: GSL_EDOM, GSL_EUNDRFLW, GSL_EOVRFLW */ int gsl_sf_bessel_k2_scaled_e(const double x, gsl_sf_result * result); double gsl_sf_bessel_k2_scaled(const double x); /* Irregular modified spherical Bessel function * Exp[x] k_l[x] * * k_l(x) = Sqrt[Pi/(2x)] BesselK[l+1/2,x] * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_kl_scaled_e(int l, const double x, gsl_sf_result * result); double gsl_sf_bessel_kl_scaled(const int l, const double x); /* Irregular scaled modified spherical Bessel function * Exp[x] k_l(x) * * for l=0,1,...,lmax * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_kl_scaled_array(const int lmax, const double x, double * result_array); /* Regular cylindrical Bessel function J_nu(x) * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_Jnu_e(const double nu, const double x, gsl_sf_result * result); double gsl_sf_bessel_Jnu(const double nu, const double x); /* Irregular cylindrical Bessel function Y_nu(x) * * exceptions: */ int gsl_sf_bessel_Ynu_e(double nu, double x, gsl_sf_result * result); double gsl_sf_bessel_Ynu(const double nu, const double x); /* Regular cylindrical Bessel function J_nu(x) * evaluated at a series of x values. The array * contains the x values. They are assumed to be * strictly ordered and positive. The array is * over-written with the values of J_nu(x_i). * * exceptions: GSL_EDOM, GSL_EINVAL */ int gsl_sf_bessel_sequence_Jnu_e(double nu, gsl_mode_t mode, size_t size, double * v); /* Scaled modified cylindrical Bessel functions * * Exp[-|x|] BesselI[nu, x] * x >= 0, nu >= 0 * * exceptions: GSL_EDOM */ int gsl_sf_bessel_Inu_scaled_e(double nu, double x, gsl_sf_result * result); double gsl_sf_bessel_Inu_scaled(double nu, double x); /* Modified cylindrical Bessel functions * * BesselI[nu, x] * x >= 0, nu >= 0 * * exceptions: GSL_EDOM, GSL_EOVRFLW */ int gsl_sf_bessel_Inu_e(double nu, double x, gsl_sf_result * result); double gsl_sf_bessel_Inu(double nu, double x); /* Scaled modified cylindrical Bessel functions * * Exp[+|x|] BesselK[nu, x] * x > 0, nu >= 0 * * exceptions: GSL_EDOM */ int gsl_sf_bessel_Knu_scaled_e(const double nu, const double x, gsl_sf_result * result); double gsl_sf_bessel_Knu_scaled(const double nu, const double x); /* Modified cylindrical Bessel functions * * BesselK[nu, x] * x > 0, nu >= 0 * * exceptions: GSL_EDOM, GSL_EUNDRFLW */ int gsl_sf_bessel_Knu_e(const double nu, const double x, gsl_sf_result * result); double gsl_sf_bessel_Knu(const double nu, const double x); /* Logarithm of modified cylindrical Bessel functions. * * Log[BesselK[nu, x]] * x > 0, nu >= 0 * * exceptions: GSL_EDOM */ int gsl_sf_bessel_lnKnu_e(const double nu, const double x, gsl_sf_result * result); double gsl_sf_bessel_lnKnu(const double nu, const double x); /* s'th positive zero of the Bessel function J_0(x). * * exceptions: */ int gsl_sf_bessel_zero_J0_e(unsigned int s, gsl_sf_result * result); double gsl_sf_bessel_zero_J0(unsigned int s); /* s'th positive zero of the Bessel function J_1(x). * * exceptions: */ int gsl_sf_bessel_zero_J1_e(unsigned int s, gsl_sf_result * result); double gsl_sf_bessel_zero_J1(unsigned int s); /* s'th positive zero of the Bessel function J_nu(x). * * exceptions: */ int gsl_sf_bessel_zero_Jnu_e(double nu, unsigned int s, gsl_sf_result * result); double gsl_sf_bessel_zero_Jnu(double nu, unsigned int s); __END_DECLS #endif /* __GSL_SF_BESSEL_H__ */ sources_5316/external/gsl/gsl_rng__mrg.c0000664000176700017670000000760111723710247017147 0ustar paulpaul/* rng/mrg.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_rng.h" /* This is a fifth-order multiple recursive generator. The sequence is, x_n = (a_1 x_{n-1} + a_5 x_{n-5}) mod m with a_1 = 107374182, a_2 = a_3 = a_4 = 0, a_5 = 104480 and m = 2^31-1. We initialize the generator with x_n = s_n MOD m for n = 1..5, where s_n = (69069 * s_{n-1}) mod 2^32, and s_0 = s is the user-supplied seed. NOTE: According to the paper the seeds must lie in the range [0, 2^31 - 2] with at least one non-zero value -- our seeding procedure satisfies these constraints. We then use 6 iterations of the generator to "warm up" the internal state. With this initialization procedure the theoretical value of z_{10006} is 2064828650 for s = 1. The subscript 10006 means (1) seed the generator with s = 1, (2) do the 6 warm-up iterations that are part of the seeding process, (3) then do 10000 actual iterations. The period of this generator is about 2^155. From: P. L'Ecuyer, F. Blouin, and R. Coutre, "A search for good multiple recursive random number generators", ACM Transactions on Modeling and Computer Simulation 3, 87-98 (1993). */ static inline unsigned long int mrg_get (void *vstate); static double mrg_get_double (void *vstate); static void mrg_set (void *state, unsigned long int s); static const long int m = 2147483647; static const long int a1 = 107374182, q1 = 20, r1 = 7; static const long int a5 = 104480, q5 = 20554, r5 = 1727; typedef struct { long int x1, x2, x3, x4, x5; } mrg_state_t; static inline unsigned long int mrg_get (void *vstate) { mrg_state_t *state = (mrg_state_t *) vstate; long int p1, h1, p5, h5; h5 = state->x5 / q5; p5 = a5 * (state->x5 - h5 * q5) - h5 * r5; if (p5 > 0) p5 -= m; h1 = state->x1 / q1; p1 = a1 * (state->x1 - h1 * q1) - h1 * r1; if (p1 < 0) p1 += m; state->x5 = state->x4; state->x4 = state->x3; state->x3 = state->x2; state->x2 = state->x1; state->x1 = p1 + p5; if (state->x1 < 0) state->x1 += m; return state->x1; } static double mrg_get_double (void *vstate) { return mrg_get (vstate) / 2147483647.0 ; } static void mrg_set (void *vstate, unsigned long int s) { /* An entirely adhoc way of seeding! This does **not** come from L'Ecuyer et al */ mrg_state_t *state = (mrg_state_t *) vstate; if (s == 0) s = 1; /* default seed is 1 */ #define LCG(n) ((69069 * n) & 0xffffffffUL) s = LCG (s); state->x1 = s % m; s = LCG (s); state->x2 = s % m; s = LCG (s); state->x3 = s % m; s = LCG (s); state->x4 = s % m; s = LCG (s); state->x5 = s % m; /* "warm it up" with at least 5 calls to go through all the x values */ mrg_get (state); mrg_get (state); mrg_get (state); mrg_get (state); mrg_get (state); mrg_get (state); return; } static const gsl_rng_type mrg_type = {"mrg", /* name */ 2147483646, /* RAND_MAX */ 0, /* RAND_MIN */ sizeof (mrg_state_t), &mrg_set, &mrg_get, &mrg_get_double}; const gsl_rng_type *gsl_rng_mrg = &mrg_type; sources_5316/external/gsl/gsl_cblas__source_asum_r.h0000664000176700017670000000173211705263724021535 0ustar paulpaul/* blas/source_asum_r.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ { BASE r = 0.0; INDEX i; INDEX ix = 0; if (incX <= 0) { return 0; } for (i = 0; i < N; i++) { r += fabs(X[ix]); ix += incX; } return r; } sources_5316/external/gsl/gsl_sf__expint.c0000644000176700017670000003667010710226217017513 0ustar paulpaul/* specfunc/expint.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_expint.h" #include "gsl_sf_gamma.h" #include "gsl_sf__error.h" #include "gsl_sf__check.h" #include "gsl_sf__chebyshev.h" #include "gsl_sf__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* Chebyshev expansions: based on SLATEC e1.f, W. Fullerton Series for AE11 on the interval -1.00000D-01 to 0. with weighted error 1.76E-17 log weighted error 16.75 significant figures required 15.70 decimal places required 17.55 Series for AE12 on the interval -2.50000D-01 to -1.00000D-01 with weighted error 5.83E-17 log weighted error 16.23 significant figures required 15.76 decimal places required 16.93 Series for E11 on the interval -4.00000D+00 to -1.00000D+00 with weighted error 1.08E-18 log weighted error 17.97 significant figures required 19.02 decimal places required 18.61 Series for E12 on the interval -1.00000D+00 to 1.00000D+00 with weighted error 3.15E-18 log weighted error 17.50 approx significant figures required 15.8 decimal places required 18.10 Series for AE13 on the interval 2.50000D-01 to 1.00000D+00 with weighted error 2.34E-17 log weighted error 16.63 significant figures required 16.14 decimal places required 17.33 Series for AE14 on the interval 0. to 2.50000D-01 with weighted error 5.41E-17 log weighted error 16.27 significant figures required 15.38 decimal places required 16.97 */ static double AE11_data[39] = { 0.121503239716065790, -0.065088778513550150, 0.004897651357459670, -0.000649237843027216, 0.000093840434587471, 0.000000420236380882, -0.000008113374735904, 0.000002804247688663, 0.000000056487164441, -0.000000344809174450, 0.000000058209273578, 0.000000038711426349, -0.000000012453235014, -0.000000005118504888, 0.000000002148771527, 0.000000000868459898, -0.000000000343650105, -0.000000000179796603, 0.000000000047442060, 0.000000000040423282, -0.000000000003543928, -0.000000000008853444, -0.000000000000960151, 0.000000000001692921, 0.000000000000607990, -0.000000000000224338, -0.000000000000200327, -0.000000000000006246, 0.000000000000045571, 0.000000000000016383, -0.000000000000005561, -0.000000000000006074, -0.000000000000000862, 0.000000000000001223, 0.000000000000000716, -0.000000000000000024, -0.000000000000000201, -0.000000000000000082, 0.000000000000000017 }; static cheb_series AE11_cs = { AE11_data, 38, -1, 1, 20 }; static double AE12_data[25] = { 0.582417495134726740, -0.158348850905782750, -0.006764275590323141, 0.005125843950185725, 0.000435232492169391, -0.000143613366305483, -0.000041801320556301, -0.000002713395758640, 0.000001151381913647, 0.000000420650022012, 0.000000066581901391, 0.000000000662143777, -0.000000002844104870, -0.000000000940724197, -0.000000000177476602, -0.000000000015830222, 0.000000000002905732, 0.000000000001769356, 0.000000000000492735, 0.000000000000093709, 0.000000000000010707, -0.000000000000000537, -0.000000000000000716, -0.000000000000000244, -0.000000000000000058 }; static cheb_series AE12_cs = { AE12_data, 24, -1, 1, 15 }; static double E11_data[19] = { -16.11346165557149402600, 7.79407277874268027690, -1.95540581886314195070, 0.37337293866277945612, -0.05692503191092901938, 0.00721107776966009185, -0.00078104901449841593, 0.00007388093356262168, -0.00000620286187580820, 0.00000046816002303176, -0.00000003209288853329, 0.00000000201519974874, -0.00000000011673686816, 0.00000000000627627066, -0.00000000000031481541, 0.00000000000001479904, -0.00000000000000065457, 0.00000000000000002733, -0.00000000000000000108 }; static cheb_series E11_cs = { E11_data, 18, -1, 1, 13 }; static double E12_data[16] = { -0.03739021479220279500, 0.04272398606220957700, -0.13031820798497005440, 0.01441912402469889073, -0.00134617078051068022, 0.00010731029253063780, -0.00000742999951611943, 0.00000045377325690753, -0.00000002476417211390, 0.00000000122076581374, -0.00000000005485141480, 0.00000000000226362142, -0.00000000000008635897, 0.00000000000000306291, -0.00000000000000010148, 0.00000000000000000315 }; static cheb_series E12_cs = { E12_data, 15, -1, 1, 10 }; static double AE13_data[25] = { -0.605773246640603460, -0.112535243483660900, 0.013432266247902779, -0.001926845187381145, 0.000309118337720603, -0.000053564132129618, 0.000009827812880247, -0.000001885368984916, 0.000000374943193568, -0.000000076823455870, 0.000000016143270567, -0.000000003466802211, 0.000000000758754209, -0.000000000168864333, 0.000000000038145706, -0.000000000008733026, 0.000000000002023672, -0.000000000000474132, 0.000000000000112211, -0.000000000000026804, 0.000000000000006457, -0.000000000000001568, 0.000000000000000383, -0.000000000000000094, 0.000000000000000023 }; static cheb_series AE13_cs = { AE13_data, 24, -1, 1, 15 }; static double AE14_data[26] = { -0.18929180007530170, -0.08648117855259871, 0.00722410154374659, -0.00080975594575573, 0.00010999134432661, -0.00001717332998937, 0.00000298562751447, -0.00000056596491457, 0.00000011526808397, -0.00000002495030440, 0.00000000569232420, -0.00000000135995766, 0.00000000033846628, -0.00000000008737853, 0.00000000002331588, -0.00000000000641148, 0.00000000000181224, -0.00000000000052538, 0.00000000000015592, -0.00000000000004729, 0.00000000000001463, -0.00000000000000461, 0.00000000000000148, -0.00000000000000048, 0.00000000000000016, -0.00000000000000005 }; static cheb_series AE14_cs = { AE14_data, 25, -1, 1, 13 }; /* implementation for E1, allowing for scaling by exp(x) */ static int expint_E1_impl(const double x, gsl_sf_result * result, const int scale) { const double xmaxt = -GSL_LOG_DBL_MIN; /* XMAXT = -LOG (R1MACH(1)) */ const double xmax = xmaxt - log(xmaxt); /* XMAX = XMAXT - LOG(XMAXT) */ /* CHECK_POINTER(result) */ if(x < -xmax && !scale) { OVERFLOW_ERROR(result); } else if(x <= -10.0) { const double s = 1.0/x * ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_c; cheb_eval_e(&AE11_cs, 20.0/x+1.0, &result_c); result->val = s * (1.0 + result_c.val); result->err = s * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(x) + 1.0) * fabs(result->val); return GSL_SUCCESS; } else if(x <= -4.0) { const double s = 1.0/x * ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_c; cheb_eval_e(&AE12_cs, (40.0/x+7.0)/3.0, &result_c); result->val = s * (1.0 + result_c.val); result->err = s * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x <= -1.0) { const double ln_term = -log(fabs(x)); const double scale_factor = ( scale ? exp(x) : 1.0 ); gsl_sf_result result_c; cheb_eval_e(&E11_cs, (2.0*x+5.0)/3.0, &result_c); result->val = scale_factor * (ln_term + result_c.val); result->err = scale_factor * (result_c.err + GSL_DBL_EPSILON * fabs(ln_term)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x == 0.0) { DOMAIN_ERROR(result); } else if(x <= 1.0) { const double ln_term = -log(fabs(x)); const double scale_factor = ( scale ? exp(x) : 1.0 ); gsl_sf_result result_c; cheb_eval_e(&E12_cs, x, &result_c); result->val = scale_factor * (ln_term - 0.6875 + x + result_c.val); result->err = scale_factor * (result_c.err + GSL_DBL_EPSILON * fabs(ln_term)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x <= 4.0) { const double s = 1.0/x * ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_c; cheb_eval_e(&AE13_cs, (8.0/x-5.0)/3.0, &result_c); result->val = s * (1.0 + result_c.val); result->err = s * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x <= xmax || scale) { const double s = 1.0/x * ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_c; cheb_eval_e(&AE14_cs, 8.0/x-1.0, &result_c); result->val = s * (1.0 + result_c.val); result->err = s * (GSL_DBL_EPSILON + result_c.err); result->err += 2.0 * (x + 1.0) * GSL_DBL_EPSILON * fabs(result->val); if(result->val == 0.0) UNDERFLOW_ERROR(result); else return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } static int expint_E2_impl(const double x, gsl_sf_result * result, const int scale) { const double xmaxt = -GSL_LOG_DBL_MIN; const double xmax = xmaxt - log(xmaxt); /* CHECK_POINTER(result) */ if(x < -xmax && !scale) { OVERFLOW_ERROR(result); } else if (x == 0.0) { result->val = (scale ? 1.0 : 1.0); result->err = 0.0; return GSL_SUCCESS; } else if(x < 100.0) { const double ex = ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_E1; int stat_E1 = expint_E1_impl(x, &result_E1, scale); result->val = ex - x*result_E1.val; result->err = GSL_DBL_EPSILON*ex + fabs(x) * result_E1.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_E1; } else if(x < xmax || scale) { const double s = ( scale ? 1.0 : exp(-x) ); const double c1 = -2.0; const double c2 = 6.0; const double c3 = -24.0; const double c4 = 120.0; const double c5 = -720.0; const double c6 = 5040.0; const double c7 = -40320.0; const double c8 = 362880.0; const double c9 = -3628800.0; const double c10 = 39916800.0; const double c11 = -479001600.0; const double c12 = 6227020800.0; const double c13 = -87178291200.0; const double y = 1.0/x; const double sum6 = c6+y*(c7+y*(c8+y*(c9+y*(c10+y*(c11+y*(c12+y*c13)))))); const double sum = y*(c1+y*(c2+y*(c3+y*(c4+y*(c5+y*sum6))))); result->val = s * (1.0 + sum)/x; result->err = 2.0 * (x + 1.0) * GSL_DBL_EPSILON * result->val; if(result->val == 0.0) UNDERFLOW_ERROR(result); else return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } static int expint_En_impl(const int n, const double x, gsl_sf_result * result, const int scale) { if (n < 0) { DOMAIN_ERROR(result); } else if (n == 0) { if (x == 0) { DOMAIN_ERROR(result); } else { result->val = (scale ? 1.0 : exp(-x)) / x; result->err = 2 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } else if (n == 1) { return expint_E1_impl(x, result, scale); } else if (n == 2) { return expint_E2_impl(x, result, scale); } else { if(x < 0) { DOMAIN_ERROR(result); } if (x == 0) { result->val = (scale ? exp(x) : 1 ) * (1/(n-1.0)); result->err = 2 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } else { gsl_sf_result result_g; double prefactor = pow(x, n-1); int status = gsl_sf_gamma_inc_e (1-n, x, &result_g); double scale_factor = ( scale ? exp(x) : 1.0 ); result->val = scale_factor * prefactor * result_g.val; result->err = 2 * GSL_DBL_EPSILON * fabs(result->val); result->err += 2 * fabs(scale_factor * prefactor * result_g.err); if (status == GSL_SUCCESS) CHECK_UNDERFLOW(result); return status; } } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_expint_E1_e(const double x, gsl_sf_result * result) { return expint_E1_impl(x, result, 0); } int gsl_sf_expint_E1_scaled_e(const double x, gsl_sf_result * result) { return expint_E1_impl(x, result, 1); } int gsl_sf_expint_E2_e(const double x, gsl_sf_result * result) { return expint_E2_impl(x, result, 0); } int gsl_sf_expint_E2_scaled_e(const double x, gsl_sf_result * result) { return expint_E2_impl(x, result, 1); } int gsl_sf_expint_En_e(const int n, const double x, gsl_sf_result * result) { return expint_En_impl(n, x, result, 0); } int gsl_sf_expint_En_scaled_e(const int n, const double x, gsl_sf_result * result) { return expint_En_impl(n, x, result, 1); } int gsl_sf_expint_Ei_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { int status = gsl_sf_expint_E1_e(-x, result); result->val = -result->val; return status; } } int gsl_sf_expint_Ei_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { int status = gsl_sf_expint_E1_scaled_e(-x, result); result->val = -result->val; return status; } } #if 0 static double recurse_En(int n, double x, double E1) { int i; double En = E1; double ex = exp(-x); for(i=2; i<=n; i++) { En = 1./(i-1) * (ex - x * En); } return En; } #endif /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_sf__eval.h" double gsl_sf_expint_E1(const double x) { EVAL_RESULT(gsl_sf_expint_E1_e(x, &result)); } double gsl_sf_expint_E1_scaled(const double x) { EVAL_RESULT(gsl_sf_expint_E1_scaled_e(x, &result)); } double gsl_sf_expint_E2(const double x) { EVAL_RESULT(gsl_sf_expint_E2_e(x, &result)); } double gsl_sf_expint_E2_scaled(const double x) { EVAL_RESULT(gsl_sf_expint_E2_scaled_e(x, &result)); } double gsl_sf_expint_En(const int n, const double x) { EVAL_RESULT(gsl_sf_expint_En_e(n, x, &result)); } double gsl_sf_expint_En_scaled(const int n, const double x) { EVAL_RESULT(gsl_sf_expint_En_scaled_e(n, x, &result)); } double gsl_sf_expint_Ei(const double x) { EVAL_RESULT(gsl_sf_expint_Ei_e(x, &result)); } double gsl_sf_expint_Ei_scaled(const double x) { EVAL_RESULT(gsl_sf_expint_Ei_scaled_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__dsymm.c0000664000176700017670000000071511723710247020010 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_dsymm (const enum CBLAS_ORDER Order, const enum CBLAS_SIDE Side, const enum CBLAS_UPLO Uplo, const int M, const int N, const double alpha, const double *A, const int lda, const double *B, const int ldb, const double beta, double *C, const int ldc) { #define BASE double #include "gsl_cblas__source_symm_r.h" #undef BASE } sources_5316/external/gsl/gsl_randist__erlang.c0000664000176700017670000000274011723710247020507 0ustar paulpaul/* randist/erlang.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 James Theiler, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_sf_gamma.h" #include "gsl_rng.h" #include "gsl_randist.h" /* The sum of N samples from an exponential distribution gives an Erlang distribution p(x) dx = x^(n-1) exp (-x/a) / ((n-1)!a^n) dx for x = 0 ... +infty */ double gsl_ran_erlang (const gsl_rng * r, const double a, const double n) { return gsl_ran_gamma (r, n, a); } double gsl_ran_erlang_pdf (const double x, const double a, const double n) { if (x <= 0) { return 0 ; } else { double p; double lngamma = gsl_sf_lngamma (n); p = exp ((n - 1) * log (x/a) - x/a - lngamma) / a; return p; } } sources_5316/external/gsl/gsl_fft__hc_radix2.c0000664000176700017670000001133511723710247020215 0ustar paulpaul/* fft/hc_radix2.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ int FUNCTION(gsl_fft_halfcomplex,radix2_backward) (BASE data[], const size_t stride, const size_t n) { int status = FUNCTION(gsl_fft_halfcomplex,radix2_transform) (data, stride, n) ; return status ; } int FUNCTION(gsl_fft_halfcomplex,radix2_inverse) (BASE data[], const size_t stride, const size_t n) { int status = FUNCTION(gsl_fft_halfcomplex,radix2_transform) (data, stride, n); if (status) { return status; } /* normalize inverse fft with 1/n */ { const ATOMIC norm = 1.0 / n; size_t i; for (i = 0; i < n; i++) { data[stride*i] *= norm; } } return status; } int FUNCTION(gsl_fft_halfcomplex,radix2_transform) (BASE data[], const size_t stride, const size_t n) { int result ; size_t p, p_1, q; size_t i; size_t logn = 0; int status; if (n == 1) /* identity operation */ { return 0 ; } /* make sure that n is a power of 2 */ result = fft_binary_logn(n) ; if (result == -1) { GSL_ERROR ("n is not a power of 2", GSL_EINVAL); } else { logn = result ; } /* apply fft recursion */ p = n; q = 1 ; p_1 = n/2 ; for (i = 1; i <= logn; i++) { size_t a, b; /* a = 0 */ for (b = 0; b < q; b++) { const ATOMIC z0 = VECTOR(data,stride,b*p); const ATOMIC z1 = VECTOR(data,stride,b*p + p_1); const ATOMIC t0_real = z0 + z1 ; const ATOMIC t1_real = z0 - z1 ; VECTOR(data,stride,b*p) = t0_real; VECTOR(data,stride,b*p + p_1) = t1_real ; } /* a = 1 ... p_{i-1}/2 - 1 */ { ATOMIC w_real = 1.0; ATOMIC w_imag = 0.0; const ATOMIC theta = 2.0 * M_PI / p; const ATOMIC s = sin (theta); const ATOMIC t = sin (theta / 2.0); const ATOMIC s2 = 2.0 * t * t; for (a = 1; a < (p_1)/2; a++) { /* trignometric recurrence for w-> exp(i theta) w */ { const ATOMIC tmp_real = w_real - s * w_imag - s2 * w_real; const ATOMIC tmp_imag = w_imag + s * w_real - s2 * w_imag; w_real = tmp_real; w_imag = tmp_imag; } for (b = 0; b < q; b++) { ATOMIC z0_real = VECTOR(data,stride,b*p + a) ; ATOMIC z0_imag = VECTOR(data,stride,b*p + p - a) ; ATOMIC z1_real = VECTOR(data,stride,b*p + p_1 - a) ; ATOMIC z1_imag = -VECTOR(data,stride,b*p + p_1 + a) ; /* t0 = z0 + z1 */ ATOMIC t0_real = z0_real + z1_real; ATOMIC t0_imag = z0_imag + z1_imag; /* t1 = (z0 - z1) */ ATOMIC t1_real = z0_real - z1_real; ATOMIC t1_imag = z0_imag - z1_imag; VECTOR(data,stride,b*p + a) = t0_real ; VECTOR(data,stride,b*p + p_1 - a) = t0_imag ; VECTOR(data,stride,b*p + p_1 + a) = (w_real * t1_real - w_imag * t1_imag) ; VECTOR(data,stride,b*p + p - a) = (w_real * t1_imag + w_imag * t1_real) ; } } } if (p_1 > 1) { for (b = 0; b < q; b++) { VECTOR(data,stride,b*p + p_1/2) *= 2 ; VECTOR(data,stride,b*p + p_1 + p_1/2) *= -2 ; } } p_1 = p_1 / 2 ; p = p / 2 ; q = q * 2 ; } /* bit reverse the ordering of output data for decimation in frequency algorithm */ status = FUNCTION(fft_real,bitreverse_order)(data, stride, n, logn) ; return 0; } sources_5316/external/gsl/gsl_integration__qk31.c0000664000176700017670000000627211723710247020701 0ustar paulpaul/* integration/qk31.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include "gsl_integration.h" /* Gauss quadrature weights and kronrod quadrature abscissae and weights as evaluated with 80 decimal digit arithmetic by L. W. Fullerton, Bell Labs, Nov. 1981. */ static const double xgk[16] = /* abscissae of the 31-point kronrod rule */ { 0.998002298693397060285172840152271, 0.987992518020485428489565718586613, 0.967739075679139134257347978784337, 0.937273392400705904307758947710209, 0.897264532344081900882509656454496, 0.848206583410427216200648320774217, 0.790418501442465932967649294817947, 0.724417731360170047416186054613938, 0.650996741297416970533735895313275, 0.570972172608538847537226737253911, 0.485081863640239680693655740232351, 0.394151347077563369897207370981045, 0.299180007153168812166780024266389, 0.201194093997434522300628303394596, 0.101142066918717499027074231447392, 0.000000000000000000000000000000000 }; /* xgk[1], xgk[3], ... abscissae of the 15-point gauss rule. xgk[0], xgk[2], ... abscissae to optimally extend the 15-point gauss rule */ static const double wg[8] = /* weights of the 15-point gauss rule */ { 0.030753241996117268354628393577204, 0.070366047488108124709267416450667, 0.107159220467171935011869546685869, 0.139570677926154314447804794511028, 0.166269205816993933553200860481209, 0.186161000015562211026800561866423, 0.198431485327111576456118326443839, 0.202578241925561272880620199967519 }; static const double wgk[16] = /* weights of the 31-point kronrod rule */ { 0.005377479872923348987792051430128, 0.015007947329316122538374763075807, 0.025460847326715320186874001019653, 0.035346360791375846222037948478360, 0.044589751324764876608227299373280, 0.053481524690928087265343147239430, 0.062009567800670640285139230960803, 0.069854121318728258709520077099147, 0.076849680757720378894432777482659, 0.083080502823133021038289247286104, 0.088564443056211770647275443693774, 0.093126598170825321225486872747346, 0.096642726983623678505179907627589, 0.099173598721791959332393173484603, 0.100769845523875595044946662617570, 0.101330007014791549017374792767493 }; void gsl_integration_qk31 (const gsl_function * f, double a, double b, double *result, double *abserr, double *resabs, double *resasc) { double fv1[16], fv2[16]; gsl_integration_qk (16, xgk, wg, wgk, fv1, fv2, f, a, b, result, abserr, resabs, resasc); } sources_5316/external/gsl/gsl_cdf__exponentialinv.c0000664000176700017670000000212611723710247021370 0ustar paulpaul/* cdf/exponentialinv.c * * Copyright (C) 2003, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" #include "gsl_cdf.h" double gsl_cdf_exponential_Pinv (const double P, const double mu) { double x = -mu * log1p (-P); return x; } double gsl_cdf_exponential_Qinv (const double Q, const double mu) { double x = -mu * log (Q); return x; } sources_5316/external/gsl/gsl_rng__knuthran.c0000664000176700017670000001135011723710247020210 0ustar paulpaul/* rng/knuthran.c * * Copyright (C) 2001, 2007 Brian Gough, Carlo Perassi * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* * This generator is taken from * * Donald E. Knuth * The Art of Computer Programming * Volume 2 * Third Edition * Addison-Wesley * Section 3.6 * * The comments are taken from the book * Our comments are signed */ #include "gsl__config.h" #include #include "gsl_rng.h" #define BUFLEN 2009 /* [Brian]: length of the buffer aa[] */ #define KK 100 /* the long lag */ #define LL 37 /* the short lag */ #define MM (1L << 30) /* the modulus */ #define TT 70 /* guaranteed separation between streams */ #define evenize(x) ((x) & (MM - 2)) /* make x even */ #define is_odd(x) ((x) & 1) /* the units bit of x */ #define mod_diff(x, y) (((x) - (y)) & (MM - 1)) /* (x - y) mod MM */ static inline void ran_array (unsigned long int aa[], unsigned int n, unsigned long int ran_x[]); static inline unsigned long int ran_get (void *vstate); static double ran_get_double (void *vstate); static void ran_set (void *state, unsigned long int s); typedef struct { unsigned int i; unsigned long int aa[BUFLEN]; /* [Carlo]: I can't pass n to ran_array like Knuth does */ unsigned long int ran_x[KK]; /* the generator state */ } ran_state_t; static inline void ran_array (unsigned long int aa[], unsigned int n, unsigned long int ran_x[]) { unsigned int i; unsigned int j; for (j = 0; j < KK; j++) aa[j] = ran_x[j]; for (; j < n; j++) aa[j] = mod_diff (aa[j - KK], aa[j - LL]); for (i = 0; i < LL; i++, j++) ran_x[i] = mod_diff (aa[j - KK], aa[j - LL]); for (; i < KK; i++, j++) ran_x[i] = mod_diff (aa[j - KK], ran_x[i - LL]); } static inline unsigned long int ran_get (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; unsigned int i = state->i; if (i == 0) { /* fill buffer with new random numbers */ ran_array (state->aa, BUFLEN, state->ran_x); } state->i = (i + 1) % BUFLEN; return state->aa[i]; } static double ran_get_double (void *vstate) { ran_state_t *state = (ran_state_t *) vstate; return ran_get (state) / 1073741824.0; /* [Carlo]: RAND_MAX + 1 */ } static void ran_set (void *vstate, unsigned long int s) { ran_state_t *state = (ran_state_t *) vstate; long x[KK + KK - 1]; /* the preparation buffer */ register int j; register int t; register long ss = evenize (s + 2); for (j = 0; j < KK; j++) { x[j] = ss; /* bootstrap the buffer */ ss <<= 1; if (ss >= MM) /* cyclic shift 29 bits */ ss -= MM - 2; } for (; j < KK + KK - 1; j++) x[j] = 0; x[1]++; /* make x[1] (and only x[1]) odd */ ss = s & (MM - 1); t = TT - 1; while (t) { for (j = KK - 1; j > 0; j--) /* square */ x[j + j] = x[j]; for (j = KK + KK - 2; j > KK - LL; j -= 2) x[KK + KK - 1 - j] = evenize (x[j]); for (j = KK + KK - 2; j >= KK; j--) if (is_odd (x[j])) { x[j - (KK - LL)] = mod_diff (x[j - (KK - LL)], x[j]); x[j - KK] = mod_diff (x[j - KK], x[j]); } if (is_odd (ss)) { /* multiply by "z" */ for (j = KK; j > 0; j--) x[j] = x[j - 1]; x[0] = x[KK]; /* shift the buffer cyclically */ if (is_odd (x[KK])) x[LL] = mod_diff (x[LL], x[KK]); } if (ss) ss >>= 1; else t--; } state->i = 0; for (j = 0; j < LL; j++) state->ran_x[j + KK - LL] = x[j]; for (; j < KK; j++) state->ran_x[j - LL] = x[j]; return; } static const gsl_rng_type ran_type = { "knuthran", /* name */ 0x3fffffffUL, /* RAND_MAX *//* [Carlo]: (2 ^ 30) - 1 */ 0, /* RAND_MIN */ sizeof (ran_state_t), &ran_set, &ran_get, &ran_get_double }; const gsl_rng_type *gsl_rng_knuthran = &ran_type; sources_5316/external/gsl/gsl_sf_laguerre.h0000664000176700017670000000371411705263724017664 0ustar paulpaul/* specfunc/gsl_sf_laguerre.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #ifndef __GSL_SF_LAGUERRE_H__ #define __GSL_SF_LAGUERRE_H__ #include "gsl_sf_result.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS /* L^a_n(x) = (a+1)_n / n! 1F1(-n,a+1,x) */ /* Evaluate generalized Laguerre polynomials * using explicit representations. * * exceptions: none */ int gsl_sf_laguerre_1_e(const double a, const double x, gsl_sf_result * result); int gsl_sf_laguerre_2_e(const double a, const double x, gsl_sf_result * result); int gsl_sf_laguerre_3_e(const double a, const double x, gsl_sf_result * result); double gsl_sf_laguerre_1(double a, double x); double gsl_sf_laguerre_2(double a, double x); double gsl_sf_laguerre_3(double a, double x); /* Evaluate generalized Laguerre polynomials. * * a > -1.0 * n >= 0 * exceptions: GSL_EDOM */ int gsl_sf_laguerre_n_e(const int n, const double a, const double x, gsl_sf_result * result); double gsl_sf_laguerre_n(int n, double a, double x); __END_DECLS #endif /* __GSL_SF_LAGUERRE_H__ */ sources_5316/external/gsl/gsl_permute_ulong.h0000664000176700017670000000264611705263724020256 0ustar paulpaul/* permutation/gsl_permute_ulong.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_ULONG_H__ #define __GSL_PERMUTE_ULONG_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_ulong (const size_t * p, unsigned long * data, const size_t stride, const size_t n); int gsl_permute_ulong_inverse (const size_t * p, unsigned long * data, const size_t stride, const size_t n); __END_DECLS #endif /* __GSL_PERMUTE_ULONG_H__ */ sources_5316/external/gsl/gsl_permute.h0000664000176700017670000000105611705263724017044 0ustar paulpaul#ifndef __GSL_PERMUTE_H__ #define __GSL_PERMUTE_H__ #include "gsl_permute_complex_long_double.h" #include "gsl_permute_complex_double.h" #include "gsl_permute_complex_float.h" #include "gsl_permute_long_double.h" #include "gsl_permute_double.h" #include "gsl_permute_float.h" #include "gsl_permute_ulong.h" #include "gsl_permute_long.h" #include "gsl_permute_uint.h" #include "gsl_permute_int.h" #include "gsl_permute_ushort.h" #include "gsl_permute_short.h" #include "gsl_permute_uchar.h" #include "gsl_permute_char.h" #endif /* __GSL_PERMUTE_H__ */ sources_5316/external/gsl/gsl_permute_vector_ulong.h0000664000176700017670000000266611705263724021642 0ustar paulpaul/* permutation/gsl_permute_vector_ulong.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_PERMUTE_VECTOR_ULONG_H__ #define __GSL_PERMUTE_VECTOR_ULONG_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_ulong.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS int gsl_permute_vector_ulong (const gsl_permutation * p, gsl_vector_ulong * v); int gsl_permute_vector_ulong_inverse (const gsl_permutation * p, gsl_vector_ulong * v); __END_DECLS #endif /* __GSL_PERMUTE_VECTOR_ULONG_H__ */ sources_5316/external/gsl/gsl_sort_vector_char.h0000664000176700017670000000340111705263724020725 0ustar paulpaul/* sort/gsl_sort_vector_char.h * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Thomas Walter, Brian Gough * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef __GSL_SORT_VECTOR_CHAR_H__ #define __GSL_SORT_VECTOR_CHAR_H__ #include #include "gsl_errno.h" #include "gsl_permutation.h" #include "gsl_vector_char.h" #undef __BEGIN_DECLS #undef __END_DECLS #ifdef __cplusplus # define __BEGIN_DECLS extern "C" { # define __END_DECLS } #else # define __BEGIN_DECLS /* empty */ # define __END_DECLS /* empty */ #endif __BEGIN_DECLS void gsl_sort_vector_char (gsl_vector_char * v); int gsl_sort_vector_char_index (gsl_permutation * p, const gsl_vector_char * v); int gsl_sort_vector_char_smallest (char * dest, const size_t k, const gsl_vector_char * v); int gsl_sort_vector_char_largest (char * dest, const size_t k, const gsl_vector_char * v); int gsl_sort_vector_char_smallest_index (size_t * p, const size_t k, const gsl_vector_char * v); int gsl_sort_vector_char_largest_index (size_t * p, const size_t k, const gsl_vector_char * v); __END_DECLS #endif /* __GSL_SORT_VECTOR_CHAR_H__ */ sources_5316/external/gsl/gsl_sys__hypot.c0000664000176700017670000000342711723710247017557 0ustar paulpaul/* sys/hypot.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2007 Gerard Jungman, Brian Gough, Patrick Alken * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "gsl__config.h" #include #include "gsl_math.h" double gsl_hypot (const double x, const double y); double gsl_hypot3 (const double x, const double y, const double z); double gsl_hypot (const double x, const double y) { double xabs = fabs(x) ; double yabs = fabs(y) ; double min, max; if (xabs < yabs) { min = xabs ; max = yabs ; } else { min = yabs ; max = xabs ; } if (min == 0) { return max ; } { double u = min / max ; return max * sqrt (1 + u * u) ; } } double gsl_hypot3(const double x, const double y, const double z) { double xabs = fabs(x); double yabs = fabs(y); double zabs = fabs(z); double w = GSL_MAX(xabs, GSL_MAX(yabs, zabs)); if (w == 0.0) { return (0.0); } else { double r = w * sqrt((xabs / w) * (xabs / w) + (yabs / w) * (yabs / w) + (zabs / w) * (zabs / w)); return r; } } sources_5316/external/gsl/gsl_specfunc__expint.c0000664000176700017670000003672611723710247020723 0ustar paulpaul/* specfunc/expint.c * * Copyright (C) 2007 Brian Gough * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_expint.h" #include "gsl_sf_gamma.h" #include "gsl_specfunc__error.h" #include "gsl_specfunc__check.h" #include "gsl_specfunc__chebyshev.h" #include "gsl_specfunc__cheb_eval.c" /*-*-*-*-*-*-*-*-*-*-*-* Private Section *-*-*-*-*-*-*-*-*-*-*-*/ /* Chebyshev expansions: based on SLATEC e1.f, W. Fullerton Series for AE11 on the interval -1.00000D-01 to 0. with weighted error 1.76E-17 log weighted error 16.75 significant figures required 15.70 decimal places required 17.55 Series for AE12 on the interval -2.50000D-01 to -1.00000D-01 with weighted error 5.83E-17 log weighted error 16.23 significant figures required 15.76 decimal places required 16.93 Series for E11 on the interval -4.00000D+00 to -1.00000D+00 with weighted error 1.08E-18 log weighted error 17.97 significant figures required 19.02 decimal places required 18.61 Series for E12 on the interval -1.00000D+00 to 1.00000D+00 with weighted error 3.15E-18 log weighted error 17.50 approx significant figures required 15.8 decimal places required 18.10 Series for AE13 on the interval 2.50000D-01 to 1.00000D+00 with weighted error 2.34E-17 log weighted error 16.63 significant figures required 16.14 decimal places required 17.33 Series for AE14 on the interval 0. to 2.50000D-01 with weighted error 5.41E-17 log weighted error 16.27 significant figures required 15.38 decimal places required 16.97 */ static double AE11_data[39] = { 0.121503239716065790, -0.065088778513550150, 0.004897651357459670, -0.000649237843027216, 0.000093840434587471, 0.000000420236380882, -0.000008113374735904, 0.000002804247688663, 0.000000056487164441, -0.000000344809174450, 0.000000058209273578, 0.000000038711426349, -0.000000012453235014, -0.000000005118504888, 0.000000002148771527, 0.000000000868459898, -0.000000000343650105, -0.000000000179796603, 0.000000000047442060, 0.000000000040423282, -0.000000000003543928, -0.000000000008853444, -0.000000000000960151, 0.000000000001692921, 0.000000000000607990, -0.000000000000224338, -0.000000000000200327, -0.000000000000006246, 0.000000000000045571, 0.000000000000016383, -0.000000000000005561, -0.000000000000006074, -0.000000000000000862, 0.000000000000001223, 0.000000000000000716, -0.000000000000000024, -0.000000000000000201, -0.000000000000000082, 0.000000000000000017 }; static cheb_series AE11_cs = { AE11_data, 38, -1, 1, 20 }; static double AE12_data[25] = { 0.582417495134726740, -0.158348850905782750, -0.006764275590323141, 0.005125843950185725, 0.000435232492169391, -0.000143613366305483, -0.000041801320556301, -0.000002713395758640, 0.000001151381913647, 0.000000420650022012, 0.000000066581901391, 0.000000000662143777, -0.000000002844104870, -0.000000000940724197, -0.000000000177476602, -0.000000000015830222, 0.000000000002905732, 0.000000000001769356, 0.000000000000492735, 0.000000000000093709, 0.000000000000010707, -0.000000000000000537, -0.000000000000000716, -0.000000000000000244, -0.000000000000000058 }; static cheb_series AE12_cs = { AE12_data, 24, -1, 1, 15 }; static double E11_data[19] = { -16.11346165557149402600, 7.79407277874268027690, -1.95540581886314195070, 0.37337293866277945612, -0.05692503191092901938, 0.00721107776966009185, -0.00078104901449841593, 0.00007388093356262168, -0.00000620286187580820, 0.00000046816002303176, -0.00000003209288853329, 0.00000000201519974874, -0.00000000011673686816, 0.00000000000627627066, -0.00000000000031481541, 0.00000000000001479904, -0.00000000000000065457, 0.00000000000000002733, -0.00000000000000000108 }; static cheb_series E11_cs = { E11_data, 18, -1, 1, 13 }; static double E12_data[16] = { -0.03739021479220279500, 0.04272398606220957700, -0.13031820798497005440, 0.01441912402469889073, -0.00134617078051068022, 0.00010731029253063780, -0.00000742999951611943, 0.00000045377325690753, -0.00000002476417211390, 0.00000000122076581374, -0.00000000005485141480, 0.00000000000226362142, -0.00000000000008635897, 0.00000000000000306291, -0.00000000000000010148, 0.00000000000000000315 }; static cheb_series E12_cs = { E12_data, 15, -1, 1, 10 }; static double AE13_data[25] = { -0.605773246640603460, -0.112535243483660900, 0.013432266247902779, -0.001926845187381145, 0.000309118337720603, -0.000053564132129618, 0.000009827812880247, -0.000001885368984916, 0.000000374943193568, -0.000000076823455870, 0.000000016143270567, -0.000000003466802211, 0.000000000758754209, -0.000000000168864333, 0.000000000038145706, -0.000000000008733026, 0.000000000002023672, -0.000000000000474132, 0.000000000000112211, -0.000000000000026804, 0.000000000000006457, -0.000000000000001568, 0.000000000000000383, -0.000000000000000094, 0.000000000000000023 }; static cheb_series AE13_cs = { AE13_data, 24, -1, 1, 15 }; static double AE14_data[26] = { -0.18929180007530170, -0.08648117855259871, 0.00722410154374659, -0.00080975594575573, 0.00010999134432661, -0.00001717332998937, 0.00000298562751447, -0.00000056596491457, 0.00000011526808397, -0.00000002495030440, 0.00000000569232420, -0.00000000135995766, 0.00000000033846628, -0.00000000008737853, 0.00000000002331588, -0.00000000000641148, 0.00000000000181224, -0.00000000000052538, 0.00000000000015592, -0.00000000000004729, 0.00000000000001463, -0.00000000000000461, 0.00000000000000148, -0.00000000000000048, 0.00000000000000016, -0.00000000000000005 }; static cheb_series AE14_cs = { AE14_data, 25, -1, 1, 13 }; /* implementation for E1, allowing for scaling by exp(x) */ static int expint_E1_impl(const double x, gsl_sf_result * result, const int scale) { const double xmaxt = -GSL_LOG_DBL_MIN; /* XMAXT = -LOG (R1MACH(1)) */ const double xmax = xmaxt - log(xmaxt); /* XMAX = XMAXT - LOG(XMAXT) */ /* CHECK_POINTER(result) */ if(x < -xmax && !scale) { OVERFLOW_ERROR(result); } else if(x <= -10.0) { const double s = 1.0/x * ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_c; cheb_eval_e(&AE11_cs, 20.0/x+1.0, &result_c); result->val = s * (1.0 + result_c.val); result->err = s * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * (fabs(x) + 1.0) * fabs(result->val); return GSL_SUCCESS; } else if(x <= -4.0) { const double s = 1.0/x * ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_c; cheb_eval_e(&AE12_cs, (40.0/x+7.0)/3.0, &result_c); result->val = s * (1.0 + result_c.val); result->err = s * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x <= -1.0) { const double ln_term = -log(fabs(x)); const double scale_factor = ( scale ? exp(x) : 1.0 ); gsl_sf_result result_c; cheb_eval_e(&E11_cs, (2.0*x+5.0)/3.0, &result_c); result->val = scale_factor * (ln_term + result_c.val); result->err = scale_factor * (result_c.err + GSL_DBL_EPSILON * fabs(ln_term)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x == 0.0) { DOMAIN_ERROR(result); } else if(x <= 1.0) { const double ln_term = -log(fabs(x)); const double scale_factor = ( scale ? exp(x) : 1.0 ); gsl_sf_result result_c; cheb_eval_e(&E12_cs, x, &result_c); result->val = scale_factor * (ln_term - 0.6875 + x + result_c.val); result->err = scale_factor * (result_c.err + GSL_DBL_EPSILON * fabs(ln_term)); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x <= 4.0) { const double s = 1.0/x * ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_c; cheb_eval_e(&AE13_cs, (8.0/x-5.0)/3.0, &result_c); result->val = s * (1.0 + result_c.val); result->err = s * result_c.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x <= xmax || scale) { const double s = 1.0/x * ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_c; cheb_eval_e(&AE14_cs, 8.0/x-1.0, &result_c); result->val = s * (1.0 + result_c.val); result->err = s * (GSL_DBL_EPSILON + result_c.err); result->err += 2.0 * (x + 1.0) * GSL_DBL_EPSILON * fabs(result->val); if(result->val == 0.0) UNDERFLOW_ERROR(result); else return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } static int expint_E2_impl(const double x, gsl_sf_result * result, const int scale) { const double xmaxt = -GSL_LOG_DBL_MIN; const double xmax = xmaxt - log(xmaxt); /* CHECK_POINTER(result) */ if(x < -xmax && !scale) { OVERFLOW_ERROR(result); } else if (x == 0.0) { result->val = (scale ? 1.0 : 1.0); result->err = 0.0; return GSL_SUCCESS; } else if(x < 100.0) { const double ex = ( scale ? 1.0 : exp(-x) ); gsl_sf_result result_E1; int stat_E1 = expint_E1_impl(x, &result_E1, scale); result->val = ex - x*result_E1.val; result->err = GSL_DBL_EPSILON*ex + fabs(x) * result_E1.err; result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return stat_E1; } else if(x < xmax || scale) { const double s = ( scale ? 1.0 : exp(-x) ); const double c1 = -2.0; const double c2 = 6.0; const double c3 = -24.0; const double c4 = 120.0; const double c5 = -720.0; const double c6 = 5040.0; const double c7 = -40320.0; const double c8 = 362880.0; const double c9 = -3628800.0; const double c10 = 39916800.0; const double c11 = -479001600.0; const double c12 = 6227020800.0; const double c13 = -87178291200.0; const double y = 1.0/x; const double sum6 = c6+y*(c7+y*(c8+y*(c9+y*(c10+y*(c11+y*(c12+y*c13)))))); const double sum = y*(c1+y*(c2+y*(c3+y*(c4+y*(c5+y*sum6))))); result->val = s * (1.0 + sum)/x; result->err = 2.0 * (x + 1.0) * GSL_DBL_EPSILON * result->val; if(result->val == 0.0) UNDERFLOW_ERROR(result); else return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } static int expint_En_impl(const int n, const double x, gsl_sf_result * result, const int scale) { if (n < 0) { DOMAIN_ERROR(result); } else if (n == 0) { if (x == 0) { DOMAIN_ERROR(result); } else { result->val = (scale ? 1.0 : exp(-x)) / x; result->err = 2 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } } else if (n == 1) { return expint_E1_impl(x, result, scale); } else if (n == 2) { return expint_E2_impl(x, result, scale); } else { if(x < 0) { DOMAIN_ERROR(result); } if (x == 0) { result->val = (scale ? exp(x) : 1 ) * (1/(n-1.0)); result->err = 2 * GSL_DBL_EPSILON * fabs(result->val); CHECK_UNDERFLOW(result); return GSL_SUCCESS; } else { gsl_sf_result result_g; double prefactor = pow(x, n-1); int status = gsl_sf_gamma_inc_e (1-n, x, &result_g); double scale_factor = ( scale ? exp(x) : 1.0 ); result->val = scale_factor * prefactor * result_g.val; result->err = 2 * GSL_DBL_EPSILON * fabs(result->val); result->err += 2 * fabs(scale_factor * prefactor * result_g.err); if (status == GSL_SUCCESS) CHECK_UNDERFLOW(result); return status; } } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_expint_E1_e(const double x, gsl_sf_result * result) { return expint_E1_impl(x, result, 0); } int gsl_sf_expint_E1_scaled_e(const double x, gsl_sf_result * result) { return expint_E1_impl(x, result, 1); } int gsl_sf_expint_E2_e(const double x, gsl_sf_result * result) { return expint_E2_impl(x, result, 0); } int gsl_sf_expint_E2_scaled_e(const double x, gsl_sf_result * result) { return expint_E2_impl(x, result, 1); } int gsl_sf_expint_En_e(const int n, const double x, gsl_sf_result * result) { return expint_En_impl(n, x, result, 0); } int gsl_sf_expint_En_scaled_e(const int n, const double x, gsl_sf_result * result) { return expint_En_impl(n, x, result, 1); } int gsl_sf_expint_Ei_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { int status = gsl_sf_expint_E1_e(-x, result); result->val = -result->val; return status; } } int gsl_sf_expint_Ei_scaled_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ { int status = gsl_sf_expint_E1_scaled_e(-x, result); result->val = -result->val; return status; } } #if 0 static double recurse_En(int n, double x, double E1) { int i; double En = E1; double ex = exp(-x); for(i=2; i<=n; i++) { En = 1./(i-1) * (ex - x * En); } return En; } #endif /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_expint_E1(const double x) { EVAL_RESULT(gsl_sf_expint_E1_e(x, &result)); } double gsl_sf_expint_E1_scaled(const double x) { EVAL_RESULT(gsl_sf_expint_E1_scaled_e(x, &result)); } double gsl_sf_expint_E2(const double x) { EVAL_RESULT(gsl_sf_expint_E2_e(x, &result)); } double gsl_sf_expint_E2_scaled(const double x) { EVAL_RESULT(gsl_sf_expint_E2_scaled_e(x, &result)); } double gsl_sf_expint_En(const int n, const double x) { EVAL_RESULT(gsl_sf_expint_En_e(n, x, &result)); } double gsl_sf_expint_En_scaled(const int n, const double x) { EVAL_RESULT(gsl_sf_expint_En_scaled_e(n, x, &result)); } double gsl_sf_expint_Ei(const double x) { EVAL_RESULT(gsl_sf_expint_Ei_e(x, &result)); } double gsl_sf_expint_Ei_scaled(const double x) { EVAL_RESULT(gsl_sf_expint_Ei_scaled_e(x, &result)); } sources_5316/external/gsl/gsl_cblas__ssyr2.c0000664000176700017670000000056211723710247017741 0ustar paulpaul#include "gsl_math.h" #include "gsl_cblas.h" #include "gsl_cblas__cblas.h" void cblas_ssyr2 (const enum CBLAS_ORDER order, const enum CBLAS_UPLO Uplo, const int N, const float alpha, const float *X, const int incX, const float *Y, const int incY, float *A, const int lda) { #define BASE float #include "gsl_cblas__source_syr2.h" #undef BASE } sources_5316/external/gsl/gsl_specfunc__legendre_Qn.c0000664000176700017670000002277211723710247021633 0ustar paulpaul/* specfunc/legendre_Qn.c * * Copyright (C) 1996, 1997, 1998, 1999, 2000 Gerard Jungman * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ /* Author: G. Jungman */ #include "gsl__config.h" #include "gsl_math.h" #include "gsl_errno.h" #include "gsl_sf_bessel.h" #include "gsl_sf_elementary.h" #include "gsl_sf_exp.h" #include "gsl_sf_pow_int.h" #include "gsl_sf_legendre.h" #include "gsl_specfunc__error.h" /* Evaluate f_{ell+1}/f_ell * f_ell := Q^{b}_{a+ell}(x) * x > 1 */ static int legendreQ_CF1_xgt1(int ell, double a, double b, double x, double * result) { const double RECUR_BIG = GSL_SQRT_DBL_MAX; const int maxiter = 5000; int n = 1; double Anm2 = 1.0; double Bnm2 = 0.0; double Anm1 = 0.0; double Bnm1 = 1.0; double a1 = ell + 1.0 + a + b; double b1 = (2.0*(ell+1.0+a) + 1.0) * x; double An = b1*Anm1 + a1*Anm2; double Bn = b1*Bnm1 + a1*Bnm2; double an, bn; double fn = An/Bn; while(n < maxiter) { double old_fn; double del; double lna; n++; Anm2 = Anm1; Bnm2 = Bnm1; Anm1 = An; Bnm1 = Bn; lna = ell + n + a; an = b*b - lna*lna; bn = (2.0*lna + 1.0) * x; An = bn*Anm1 + an*Anm2; Bn = bn*Bnm1 + an*Bnm2; if(fabs(An) > RECUR_BIG || fabs(Bn) > RECUR_BIG) { An /= RECUR_BIG; Bn /= RECUR_BIG; Anm1 /= RECUR_BIG; Bnm1 /= RECUR_BIG; Anm2 /= RECUR_BIG; Bnm2 /= RECUR_BIG; } old_fn = fn; fn = An/Bn; del = old_fn/fn; if(fabs(del - 1.0) < 4.0*GSL_DBL_EPSILON) break; } *result = fn; if(n == maxiter) GSL_ERROR ("error", GSL_EMAXITER); else return GSL_SUCCESS; } /* Uniform asymptotic for Q_l(x). * Assumes x > -1.0 and x != 1.0. * Discards second order and higher terms. */ static int legendre_Ql_asymp_unif(const double ell, const double x, gsl_sf_result * result) { if(x < 1.0) { double u = ell + 0.5; double th = acos(x); gsl_sf_result Y0, Y1; int stat_Y0, stat_Y1; int stat_m; double pre; double B00; double sum; /* B00 = 1/8 (1 - th cot(th) / th^2 * pre = sqrt(th/sin(th)) */ if(th < GSL_ROOT4_DBL_EPSILON) { B00 = (1.0 + th*th/15.0)/24.0; pre = 1.0 + th*th/12.0; } else { double sin_th = sqrt(1.0 - x*x); double cot_th = x / sin_th; B00 = 1.0/8.0 * (1.0 - th * cot_th) / (th*th); pre = sqrt(th/sin_th); } stat_Y0 = gsl_sf_bessel_Y0_e(u*th, &Y0); stat_Y1 = gsl_sf_bessel_Y1_e(u*th, &Y1); sum = -0.5*M_PI * (Y0.val + th/u * Y1.val * B00); stat_m = gsl_sf_multiply_e(pre, sum, result); result->err += 0.5*M_PI * fabs(pre) * (Y0.err + fabs(th/u*B00)*Y1.err); result->err += GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_m, stat_Y0, stat_Y1); } else { double u = ell + 0.5; double xi = acosh(x); gsl_sf_result K0_scaled, K1_scaled; int stat_K0, stat_K1; int stat_e; double pre; double B00; double sum; /* B00 = -1/8 (1 - xi coth(xi) / xi^2 * pre = sqrt(xi/sinh(xi)) */ if(xi < GSL_ROOT4_DBL_EPSILON) { B00 = (1.0-xi*xi/15.0)/24.0; pre = 1.0 - xi*xi/12.0; } else { double sinh_xi = sqrt(x*x - 1.0); double coth_xi = x / sinh_xi; B00 = -1.0/8.0 * (1.0 - xi * coth_xi) / (xi*xi); pre = sqrt(xi/sinh_xi); } stat_K0 = gsl_sf_bessel_K0_scaled_e(u*xi, &K0_scaled); stat_K1 = gsl_sf_bessel_K1_scaled_e(u*xi, &K1_scaled); sum = K0_scaled.val - xi/u * K1_scaled.val * B00; stat_e = gsl_sf_exp_mult_e(-u*xi, pre * sum, result); result->err = GSL_DBL_EPSILON * fabs(result->val) * fabs(u*xi); result->err += 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_ERROR_SELECT_3(stat_e, stat_K0, stat_K1); } } /*-*-*-*-*-*-*-*-*-*-*-* Functions with Error Codes *-*-*-*-*-*-*-*-*-*-*-*/ int gsl_sf_legendre_Q0_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0 || x == 1.0) { DOMAIN_ERROR(result); } else if(x*x < GSL_ROOT6_DBL_EPSILON) { /* |x| <~ 0.05 */ const double c3 = 1.0/3.0; const double c5 = 1.0/5.0; const double c7 = 1.0/7.0; const double c9 = 1.0/9.0; const double c11 = 1.0/11.0; const double y = x * x; const double series = 1.0 + y*(c3 + y*(c5 + y*(c7 + y*(c9 + y*c11)))); result->val = x * series; result->err = 2.0 * GSL_DBL_EPSILON * fabs(x); return GSL_SUCCESS; } else if(x < 1.0) { result->val = 0.5 * log((1.0+x)/(1.0-x)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 10.0) { result->val = 0.5 * log((x+1.0)/(x-1.0)); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x*GSL_DBL_MIN < 2.0) { const double y = 1.0/(x*x); const double c1 = 1.0/3.0; const double c2 = 1.0/5.0; const double c3 = 1.0/7.0; const double c4 = 1.0/9.0; const double c5 = 1.0/11.0; const double c6 = 1.0/13.0; const double c7 = 1.0/15.0; result->val = (1.0/x) * (1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*(c6 + y*c7))))))); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } int gsl_sf_legendre_Q1_e(const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0 || x == 1.0) { DOMAIN_ERROR(result); } else if(x*x < GSL_ROOT6_DBL_EPSILON) { /* |x| <~ 0.05 */ const double c3 = 1.0/3.0; const double c5 = 1.0/5.0; const double c7 = 1.0/7.0; const double c9 = 1.0/9.0; const double c11 = 1.0/11.0; const double y = x * x; const double series = 1.0 + y*(c3 + y*(c5 + y*(c7 + y*(c9 + y*c11)))); result->val = x * x * series - 1.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 1.0){ result->val = 0.5 * x * (log((1.0+x)/(1.0-x))) - 1.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x < 6.0) { result->val = 0.5 * x * log((x+1.0)/(x-1.0)) - 1.0; result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else if(x*GSL_SQRT_DBL_MIN < 0.99/M_SQRT3) { const double y = 1/(x*x); const double c1 = 3.0/5.0; const double c2 = 3.0/7.0; const double c3 = 3.0/9.0; const double c4 = 3.0/11.0; const double c5 = 3.0/13.0; const double c6 = 3.0/15.0; const double c7 = 3.0/17.0; const double c8 = 3.0/19.0; const double sum = 1.0 + y*(c1 + y*(c2 + y*(c3 + y*(c4 + y*(c5 + y*(c6 + y*(c7 + y*c8))))))); result->val = sum / (3.0*x*x); result->err = 2.0 * GSL_DBL_EPSILON * fabs(result->val); return GSL_SUCCESS; } else { UNDERFLOW_ERROR(result); } } int gsl_sf_legendre_Ql_e(const int l, const double x, gsl_sf_result * result) { /* CHECK_POINTER(result) */ if(x <= -1.0 || x == 1.0 || l < 0) { DOMAIN_ERROR(result); } else if(l == 0) { return gsl_sf_legendre_Q0_e(x, result); } else if(l == 1) { return gsl_sf_legendre_Q1_e(x, result); } else if(l > 100000) { return legendre_Ql_asymp_unif(l, x, result); } else if(x < 1.0){ /* Forward recurrence. */ gsl_sf_result Q0, Q1; int stat_Q0 = gsl_sf_legendre_Q0_e(x, &Q0); int stat_Q1 = gsl_sf_legendre_Q1_e(x, &Q1); double Qellm1 = Q0.val; double Qell = Q1.val; double Qellp1; int ell; for(ell=1; ellval = Qell; result->err = GSL_DBL_EPSILON * l * fabs(result->val); return GSL_ERROR_SELECT_2(stat_Q0, stat_Q1); } else { /* x > 1.0 */ double rat; int stat_CF1 = legendreQ_CF1_xgt1(l, 0.0, 0.0, x, &rat); int stat_Q; double Qellp1 = rat * GSL_SQRT_DBL_MIN; double Qell = GSL_SQRT_DBL_MIN; double Qellm1; int ell; for(ell=l; ell>0; ell--) { Qellm1 = (x * (2.0*ell + 1.0) * Qell - (ell+1.0) * Qellp1) / ell; Qellp1 = Qell; Qell = Qellm1; } if(fabs(Qell) > fabs(Qellp1)) { gsl_sf_result Q0; stat_Q = gsl_sf_legendre_Q0_e(x, &Q0); result->val = GSL_SQRT_DBL_MIN * Q0.val / Qell; result->err = l * GSL_DBL_EPSILON * fabs(result->val); } else { gsl_sf_result Q1; stat_Q = gsl_sf_legendre_Q1_e(x, &Q1); result->val = GSL_SQRT_DBL_MIN * Q1.val / Qellp1; result->err = l * GSL_DBL_EPSILON * fabs(result->val); } return GSL_ERROR_SELECT_2(stat_Q, stat_CF1); } } /*-*-*-*-*-*-*-*-*-* Functions w/ Natural Prototypes *-*-*-*-*-*-*-*-*-*-*/ #include "gsl_specfunc__eval.h" double gsl_sf_legendre_Q0(const double x) { EVAL_RESULT(gsl_sf_legendre_Q0_e(x, &result)); } double gsl_sf_legendre_Q1(const double x) { EVAL_RESULT(gsl_sf_legendre_Q1_e(x, &result)); } double gsl_sf_legendre_Ql(const int l, const double x) { EVAL_RESULT(gsl_sf_legendre_Ql_e(l, x, &result)); } sources_5316/external/gsl/gsl_machine.h0000664000176700017670000000733511705263724016775 0ustar paulpaul/* Author: B. Gough and G. Jungman */ #ifndef __GSL_MACHINE_H__ #define __GSL_MACHINE_H__ #include #include /* magic constants; mostly for the benefit of the implementation */ /* -*-MACHINE CONSTANTS-*- * * PLATFORM: Whiz-O-Matic 9000 * FP_PLATFORM: IEEE-Virtual * HOSTNAME: nnn.lanl.gov * DATE: Fri Nov 20 17:53:26 MST 1998 */ #define GSL_DBL_EPSILON 2.2204460492503131e-16 #define GSL_SQRT_DBL_EPSILON 1.4901161193847656e-08 #define GSL_ROOT3_DBL_EPSILON 6.0554544523933429e-06 #define GSL_ROOT4_DBL_EPSILON 1.2207031250000000e-04 #define GSL_ROOT5_DBL_EPSILON 7.4009597974140505e-04 #define GSL_ROOT6_DBL_EPSILON 2.4607833005759251e-03 #define GSL_LOG_DBL_EPSILON (-3.6043653389117154e+01) #define GSL_DBL_MIN 2.2250738585072014e-308 #define GSL_SQRT_DBL_MIN 1.4916681462400413e-154 #define GSL_ROOT3_DBL_MIN 2.8126442852362996e-103 #define GSL_ROOT4_DBL_MIN 1.2213386697554620e-77 #define GSL_ROOT5_DBL_MIN 2.9476022969691763e-62 #define GSL_ROOT6_DBL_MIN 5.3034368905798218e-52 #define GSL_LOG_DBL_MIN (-7.0839641853226408e+02) #define GSL_DBL_MAX 1.7976931348623157e+308 #define GSL_SQRT_DBL_MAX 1.3407807929942596e+154 #define GSL_ROOT3_DBL_MAX 5.6438030941222897e+102 #define GSL_ROOT4_DBL_MAX 1.1579208923731620e+77 #define GSL_ROOT5_DBL_MAX 4.4765466227572707e+61 #define GSL_ROOT6_DBL_MAX 2.3756689782295612e+51 #define GSL_LOG_DBL_MAX 7.0978271289338397e+02 #define GSL_FLT_EPSILON 1.1920928955078125e-07 #define GSL_SQRT_FLT_EPSILON 3.4526698300124393e-04 #define GSL_ROOT3_FLT_EPSILON 4.9215666011518501e-03 #define GSL_ROOT4_FLT_EPSILON 1.8581361171917516e-02 #define GSL_ROOT5_FLT_EPSILON 4.1234622211652937e-02 #define GSL_ROOT6_FLT_EPSILON 7.0153878019335827e-02 #define GSL_LOG_FLT_EPSILON (-1.5942385152878742e+01) #define GSL_FLT_MIN 1.1754943508222875e-38 #define GSL_SQRT_FLT_MIN 1.0842021724855044e-19 #define GSL_ROOT3_FLT_MIN 2.2737367544323241e-13 #define GSL_ROOT4_FLT_MIN 3.2927225399135965e-10 #define GSL_ROOT5_FLT_MIN 2.5944428542140822e-08 #define GSL_ROOT6_FLT_MIN 4.7683715820312542e-07 #define GSL_LOG_FLT_MIN (-8.7336544750553102e+01) #define GSL_FLT_MAX 3.4028234663852886e+38 #define GSL_SQRT_FLT_MAX 1.8446743523953730e+19 #define GSL_ROOT3_FLT_MAX 6.9814635196223242e+12 #define GSL_ROOT4_FLT_MAX 4.2949672319999986e+09 #define GSL_ROOT5_FLT_MAX 5.0859007855960041e+07 #define GSL_ROOT6_FLT_MAX 2.6422459233807749e+06 #define GSL_LOG_FLT_MAX 8.8722839052068352e+01 #define GSL_SFLT_EPSILON 4.8828125000000000e-04 #define GSL_SQRT_SFLT_EPSILON 2.2097086912079612e-02 #define GSL_ROOT3_SFLT_EPSILON 7.8745065618429588e-02 #define GSL_ROOT4_SFLT_EPSILON 1.4865088937534013e-01 #define GSL_ROOT5_SFLT_EPSILON 2.1763764082403100e-01 #define GSL_ROOT6_SFLT_EPSILON 2.8061551207734325e-01 #define GSL_LOG_SFLT_EPSILON (-7.6246189861593985e+00) /* !MACHINE CONSTANTS! */ /* a little internal backwards compatibility */ #define GSL_MACH_EPS GSL_DBL_EPSILON /* Here are the constants related to or derived from * machine constants. These are not to be confused with * the constants that define various precision levels * for the precision/error system. * * This information is determined at configure time * and is platform dependent. Edit at your own risk. * * PLATFORM: WHIZ-O-MATIC * CONFIG-DATE: Thu Nov 19 19:27:18 MST 1998 * CONFIG-HOST: nnn.lanl.gov */ /* machine precision constants */ /* #define GSL_MACH_EPS 1.0e-15 */ #define GSL_SQRT_MACH_EPS 3.2e-08 #define GSL_ROOT3_MACH_EPS 1.0e-05 #define GSL_ROOT4_MACH_EPS 0.000178 #define GSL_ROOT5_MACH_EPS 0.00100 #define GSL_ROOT6_MACH_EPS 0.00316 #define GSL_LOG_MACH_EPS (-34.54) #endif /* __GSL_MACHINE_H__ */ sources_5316/kar/0000755000176700017670000000000011647316236012511 5ustar paulpaulsources_5316/kar/longchar.h0000644000176700017670000001205211614424562014453 0ustar paulpaul#ifndef _longchar_h_ #define _longchar_h_ /* longchar.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include /********** NON-ASCII CHARACTERS **********/ /* System-independent representation of some non-ASCII symbols. These symbols are represented by a backslash (\) plus two ASCII symbols. In 1992, we needed this because Praat is multilingual. Nowadays, we have Unicode, which is a system-independent representation as well. Still, backslash sequences are useful if your computer does not have a fast input method for the symbols you want to use, which is likely to happen with phonetic characters. - For the characters of the following languages, we supply backslash sequences as well as size and PostScript information: English, Dutch, German, French, Spanish, Portuguese, Italian, Danish, Swedish, Norwegian, Welsh, Luxemburgian, Frisian. - For the characters of the following languages, we supply backslash sequences (PostScript will not work yet): Hungarian, Polish, Czech, Rumanian, Icelandic, Serbocroat, Turkish, Greek, Hebrew. - By supporting Unicode, we also support other alphabets, such as Arabic, Chinese, Cyrillic, and Devanagari; since we have no backslash support for these, you need a specialized input method to enter them into Praat. */ /* Alphabets. */ #define Longchar_ROMAN 0 #define Longchar_SYMBOL 1 #define Longchar_PHONETIC 2 #define Longchar_DINGBATS 3 #define Longchar_RIGHT_TO_LEFT 4 /********** Conversion of Roman native and generic string encodings. **********/ wchar_t * Longchar_nativizeW (const wchar_t *generic, wchar_t *native, int educateQuotes); char * Longchar_genericize (const char *native, char *generic); wchar_t *Longchar_genericizeW (const wchar_t *native, wchar_t *generic); /* Function: Copies the string 'native' to the string 'generic', interpreting non-ASCII native characters as belonging to the Roman alphabet. Returns 'generic' as a convenience. 'generic' can become at most three times as long as 'native'. Usage: translating user input into a generic string. */ typedef struct structLongchar_Info { unsigned char first, second; /* First and second character of two-byte encoding. */ /* For ASCII characters, 'second' is a space. */ unsigned char alphabet; /* Roman, Symbol, Phonetic, or Dingbats. */ struct { const char *name; /* The PostScript name, starting with a slash. */ /* The widths in thousands of the height. */ short times, timesBold, timesItalic, timesBoldItalic; /* Times. */ short helvetica, helveticaBold; /* Helvetica. */ short palatino, palatinoBold, palatinoItalic, palatinoBoldItalic; /* Palatino. */ /* Courier width always 600. */ } ps; /* PostScript properties. */ unsigned short xwinEncoding; /* The one-byte encoding for X11 (ISO8859-1 for Roman). */ unsigned short winEncoding; /* The one-byte encoding for Windows (ISO8859-1 for Roman; SILDoulosIPA 1993). */ unsigned short macEncoding; /* The one-byte encoding for Macintosh (Mac for Roman; SILDoulosIPA 1993). */ unsigned short psEncoding; /* The one-byte encoding for PostScript (Mac-Praat, TeX-xipa-Praat). */ unsigned long unicode; /* The four-byte encoding for Unicode. */ unsigned short unicodeDecomposition [6]; /* Diacritics decoupled from the base character. */ } *Longchar_Info; Longchar_Info Longchar_getInfo (char kar1, char kar2); Longchar_Info Longchar_getInfoFromNative (wchar_t kar); /* If no info found, these two routines return the info for a space. */ /* How should we represent the dumb ASCII double quote (")? The dumb quote is converted to a left or right double quote, on Macintosh, PostScript, and Windows (ISO8859-1 has no left and right double quotes). You can enforce the way your double quotes look by using one of these generic symbols: - \"l for a left double quote - \"r for a right double quote - \"" for a straight double quote There is no translation for single quotes, because some languages use the right single quote as an apostrophe in unpredictable positions. You can get a left single quote by typing "`", which looks like a grave accent on Macintosh; you will get a right single quote or apostrophe by typing a "'", which looks like a straight quote on Macintosh. Thus, the string typed as "`hallo'" will give you left and right quotes, even on Macintosh. (Reading this note in Xwindows may feel somewhat funny.) */ /* End of file longchar.h */ #endif sources_5316/kar/Makefile0000644000176700017670000000053011631437461014144 0ustar paulpaul# Makefile of the library "kar" # Paul Boersma, 6 September 2011 include ../makefile.defs OBJECTS = ipaSerifRegularPS.o ipaSerifRegular24.o longchar.o .PHONY: all clean all: libkar.a clean: $(RM) $(OBJECTS) $(RM) libkar.a libkar.a: $(OBJECTS) touch libkar.a rm libkar.a ar cq libkar.a $(OBJECTS) $(RANLIB) libkar.a $(OBJECTS): *.h sources_5316/kar/UnicodeData.h0000644000176700017670000616754610633615026015064 0ustar paulpaul#define UNICODE_SPACE 0x0020 #define UNITEXT_SPACE L"\u0020" #define UNICODE_EXCLAMATION_MARK 0x0021 #define UNITEXT_EXCLAMATION_MARK L"\u0021" #define UNICODE_QUOTATION_MARK 0x0022 #define UNITEXT_QUOTATION_MARK L"\u0022" #define UNICODE_NUMBER_SIGN 0x0023 #define UNITEXT_NUMBER_SIGN L"\u0023" #define UNICODE_DOLLAR_SIGN 0x0024 #define UNITEXT_DOLLAR_SIGN L"\u0024" #define UNICODE_PERCENT_SIGN 0x0025 #define UNITEXT_PERCENT_SIGN L"\u0025" #define UNICODE_AMPERSAND 0x0026 #define UNITEXT_AMPERSAND L"\u0026" #define UNICODE_APOSTROPHE 0x0027 #define UNITEXT_APOSTROPHE L"\u0027" #define UNICODE_LEFT_PARENTHESIS 0x0028 #define UNITEXT_LEFT_PARENTHESIS L"\u0028" #define UNICODE_RIGHT_PARENTHESIS 0x0029 #define UNITEXT_RIGHT_PARENTHESIS L"\u0029" #define UNICODE_ASTERISK 0x002a #define UNITEXT_ASTERISK L"\u002a" #define UNICODE_PLUS_SIGN 0x002b #define UNITEXT_PLUS_SIGN L"\u002b" #define UNICODE_COMMA 0x002c #define UNITEXT_COMMA L"\u002c" #define UNICODE_HYPHEN_MINUS 0x002d #define UNITEXT_HYPHEN_MINUS L"\u002d" #define UNICODE_FULL_STOP 0x002e #define UNITEXT_FULL_STOP L"\u002e" #define UNICODE_SOLIDUS 0x002f #define UNITEXT_SOLIDUS L"\u002f" #define UNICODE_DIGIT_ZERO 0x0030 #define UNITEXT_DIGIT_ZERO L"\u0030" #define UNICODE_DIGIT_ONE 0x0031 #define UNITEXT_DIGIT_ONE L"\u0031" #define UNICODE_DIGIT_TWO 0x0032 #define UNITEXT_DIGIT_TWO L"\u0032" #define UNICODE_DIGIT_THREE 0x0033 #define UNITEXT_DIGIT_THREE L"\u0033" #define UNICODE_DIGIT_FOUR 0x0034 #define UNITEXT_DIGIT_FOUR L"\u0034" #define UNICODE_DIGIT_FIVE 0x0035 #define UNITEXT_DIGIT_FIVE L"\u0035" #define UNICODE_DIGIT_SIX 0x0036 #define UNITEXT_DIGIT_SIX L"\u0036" #define UNICODE_DIGIT_SEVEN 0x0037 #define UNITEXT_DIGIT_SEVEN L"\u0037" #define UNICODE_DIGIT_EIGHT 0x0038 #define UNITEXT_DIGIT_EIGHT L"\u0038" #define UNICODE_DIGIT_NINE 0x0039 #define UNITEXT_DIGIT_NINE L"\u0039" #define UNICODE_COLON 0x003a #define UNITEXT_COLON L"\u003a" #define UNICODE_SEMICOLON 0x003b #define UNITEXT_SEMICOLON L"\u003b" #define UNICODE_LESS_THAN_SIGN 0x003c #define UNITEXT_LESS_THAN_SIGN L"\u003c" #define UNICODE_EQUALS_SIGN 0x003d #define UNITEXT_EQUALS_SIGN L"\u003d" #define UNICODE_GREATER_THAN_SIGN 0x003e #define UNITEXT_GREATER_THAN_SIGN L"\u003e" #define UNICODE_QUESTION_MARK 0x003f #define UNITEXT_QUESTION_MARK L"\u003f" #define UNICODE_COMMERCIAL_AT 0x0040 #define UNITEXT_COMMERCIAL_AT L"\u0040" #define UNICODE_LATIN_CAPITAL_LETTER_A 0x0041 #define UNITEXT_LATIN_CAPITAL_LETTER_A L"\u0041" #define UNICODE_LATIN_CAPITAL_LETTER_B 0x0042 #define UNITEXT_LATIN_CAPITAL_LETTER_B L"\u0042" #define UNICODE_LATIN_CAPITAL_LETTER_C 0x0043 #define UNITEXT_LATIN_CAPITAL_LETTER_C L"\u0043" #define UNICODE_LATIN_CAPITAL_LETTER_D 0x0044 #define UNITEXT_LATIN_CAPITAL_LETTER_D L"\u0044" #define UNICODE_LATIN_CAPITAL_LETTER_E 0x0045 #define UNITEXT_LATIN_CAPITAL_LETTER_E L"\u0045" #define UNICODE_LATIN_CAPITAL_LETTER_F 0x0046 #define UNITEXT_LATIN_CAPITAL_LETTER_F L"\u0046" #define UNICODE_LATIN_CAPITAL_LETTER_G 0x0047 #define UNITEXT_LATIN_CAPITAL_LETTER_G L"\u0047" #define UNICODE_LATIN_CAPITAL_LETTER_H 0x0048 #define UNITEXT_LATIN_CAPITAL_LETTER_H L"\u0048" #define UNICODE_LATIN_CAPITAL_LETTER_I 0x0049 #define UNITEXT_LATIN_CAPITAL_LETTER_I L"\u0049" #define UNICODE_LATIN_CAPITAL_LETTER_J 0x004a #define UNITEXT_LATIN_CAPITAL_LETTER_J L"\u004a" #define UNICODE_LATIN_CAPITAL_LETTER_K 0x004b #define UNITEXT_LATIN_CAPITAL_LETTER_K L"\u004b" #define UNICODE_LATIN_CAPITAL_LETTER_L 0x004c #define UNITEXT_LATIN_CAPITAL_LETTER_L L"\u004c" #define UNICODE_LATIN_CAPITAL_LETTER_M 0x004d #define UNITEXT_LATIN_CAPITAL_LETTER_M L"\u004d" #define UNICODE_LATIN_CAPITAL_LETTER_N 0x004e #define UNITEXT_LATIN_CAPITAL_LETTER_N L"\u004e" #define UNICODE_LATIN_CAPITAL_LETTER_O 0x004f #define UNITEXT_LATIN_CAPITAL_LETTER_O L"\u004f" #define UNICODE_LATIN_CAPITAL_LETTER_P 0x0050 #define UNITEXT_LATIN_CAPITAL_LETTER_P L"\u0050" #define UNICODE_LATIN_CAPITAL_LETTER_Q 0x0051 #define UNITEXT_LATIN_CAPITAL_LETTER_Q L"\u0051" #define UNICODE_LATIN_CAPITAL_LETTER_R 0x0052 #define UNITEXT_LATIN_CAPITAL_LETTER_R L"\u0052" #define UNICODE_LATIN_CAPITAL_LETTER_S 0x0053 #define UNITEXT_LATIN_CAPITAL_LETTER_S L"\u0053" #define UNICODE_LATIN_CAPITAL_LETTER_T 0x0054 #define UNITEXT_LATIN_CAPITAL_LETTER_T L"\u0054" #define UNICODE_LATIN_CAPITAL_LETTER_U 0x0055 #define UNITEXT_LATIN_CAPITAL_LETTER_U L"\u0055" #define UNICODE_LATIN_CAPITAL_LETTER_V 0x0056 #define UNITEXT_LATIN_CAPITAL_LETTER_V L"\u0056" #define UNICODE_LATIN_CAPITAL_LETTER_W 0x0057 #define UNITEXT_LATIN_CAPITAL_LETTER_W L"\u0057" #define UNICODE_LATIN_CAPITAL_LETTER_X 0x0058 #define UNITEXT_LATIN_CAPITAL_LETTER_X L"\u0058" #define UNICODE_LATIN_CAPITAL_LETTER_Y 0x0059 #define UNITEXT_LATIN_CAPITAL_LETTER_Y L"\u0059" #define UNICODE_LATIN_CAPITAL_LETTER_Z 0x005a #define UNITEXT_LATIN_CAPITAL_LETTER_Z L"\u005a" #define UNICODE_LEFT_SQUARE_BRACKET 0x005b #define UNITEXT_LEFT_SQUARE_BRACKET L"\u005b" #define UNICODE_REVERSE_SOLIDUS 0x005c #define UNITEXT_REVERSE_SOLIDUS L"\u005c" #define UNICODE_RIGHT_SQUARE_BRACKET 0x005d #define UNITEXT_RIGHT_SQUARE_BRACKET L"\u005d" #define UNICODE_CIRCUMFLEX_ACCENT 0x005e #define UNITEXT_CIRCUMFLEX_ACCENT L"\u005e" #define UNICODE_LOW_LINE 0x005f #define UNITEXT_LOW_LINE L"\u005f" #define UNICODE_GRAVE_ACCENT 0x0060 #define UNITEXT_GRAVE_ACCENT L"\u0060" #define UNICODE_LATIN_SMALL_LETTER_A 0x0061 #define UNITEXT_LATIN_SMALL_LETTER_A L"\u0061" #define UNICODE_LATIN_SMALL_LETTER_B 0x0062 #define UNITEXT_LATIN_SMALL_LETTER_B L"\u0062" #define UNICODE_LATIN_SMALL_LETTER_C 0x0063 #define UNITEXT_LATIN_SMALL_LETTER_C L"\u0063" #define UNICODE_LATIN_SMALL_LETTER_D 0x0064 #define UNITEXT_LATIN_SMALL_LETTER_D L"\u0064" #define UNICODE_LATIN_SMALL_LETTER_E 0x0065 #define UNITEXT_LATIN_SMALL_LETTER_E L"\u0065" #define UNICODE_LATIN_SMALL_LETTER_F 0x0066 #define UNITEXT_LATIN_SMALL_LETTER_F L"\u0066" #define UNICODE_LATIN_SMALL_LETTER_G 0x0067 #define UNITEXT_LATIN_SMALL_LETTER_G L"\u0067" #define UNICODE_LATIN_SMALL_LETTER_H 0x0068 #define UNITEXT_LATIN_SMALL_LETTER_H L"\u0068" #define UNICODE_LATIN_SMALL_LETTER_I 0x0069 #define UNITEXT_LATIN_SMALL_LETTER_I L"\u0069" #define UNICODE_LATIN_SMALL_LETTER_J 0x006a #define UNITEXT_LATIN_SMALL_LETTER_J L"\u006a" #define UNICODE_LATIN_SMALL_LETTER_K 0x006b #define UNITEXT_LATIN_SMALL_LETTER_K L"\u006b" #define UNICODE_LATIN_SMALL_LETTER_L 0x006c #define UNITEXT_LATIN_SMALL_LETTER_L L"\u006c" #define UNICODE_LATIN_SMALL_LETTER_M 0x006d #define UNITEXT_LATIN_SMALL_LETTER_M L"\u006d" #define UNICODE_LATIN_SMALL_LETTER_N 0x006e #define UNITEXT_LATIN_SMALL_LETTER_N L"\u006e" #define UNICODE_LATIN_SMALL_LETTER_O 0x006f #define UNITEXT_LATIN_SMALL_LETTER_O L"\u006f" #define UNICODE_LATIN_SMALL_LETTER_P 0x0070 #define UNITEXT_LATIN_SMALL_LETTER_P L"\u0070" #define UNICODE_LATIN_SMALL_LETTER_Q 0x0071 #define UNITEXT_LATIN_SMALL_LETTER_Q L"\u0071" #define UNICODE_LATIN_SMALL_LETTER_R 0x0072 #define UNITEXT_LATIN_SMALL_LETTER_R L"\u0072" #define UNICODE_LATIN_SMALL_LETTER_S 0x0073 #define UNITEXT_LATIN_SMALL_LETTER_S L"\u0073" #define UNICODE_LATIN_SMALL_LETTER_T 0x0074 #define UNITEXT_LATIN_SMALL_LETTER_T L"\u0074" #define UNICODE_LATIN_SMALL_LETTER_U 0x0075 #define UNITEXT_LATIN_SMALL_LETTER_U L"\u0075" #define UNICODE_LATIN_SMALL_LETTER_V 0x0076 #define UNITEXT_LATIN_SMALL_LETTER_V L"\u0076" #define UNICODE_LATIN_SMALL_LETTER_W 0x0077 #define UNITEXT_LATIN_SMALL_LETTER_W L"\u0077" #define UNICODE_LATIN_SMALL_LETTER_X 0x0078 #define UNITEXT_LATIN_SMALL_LETTER_X L"\u0078" #define UNICODE_LATIN_SMALL_LETTER_Y 0x0079 #define UNITEXT_LATIN_SMALL_LETTER_Y L"\u0079" #define UNICODE_LATIN_SMALL_LETTER_Z 0x007a #define UNITEXT_LATIN_SMALL_LETTER_Z L"\u007a" #define UNICODE_LEFT_CURLY_BRACKET 0x007b #define UNITEXT_LEFT_CURLY_BRACKET L"\u007b" #define UNICODE_VERTICAL_LINE 0x007c #define UNITEXT_VERTICAL_LINE L"\u007c" #define UNICODE_RIGHT_CURLY_BRACKET 0x007d #define UNITEXT_RIGHT_CURLY_BRACKET L"\u007d" #define UNICODE_TILDE 0x007e #define UNITEXT_TILDE L"\u007e" #define UNICODE_NO_BREAK_SPACE 0x00a0 #define UNITEXT_NO_BREAK_SPACE L"\u00a0" #define UNICODE_INVERTED_EXCLAMATION_MARK 0x00a1 #define UNITEXT_INVERTED_EXCLAMATION_MARK L"\u00a1" #define UNICODE_CENT_SIGN 0x00a2 #define UNITEXT_CENT_SIGN L"\u00a2" #define UNICODE_POUND_SIGN 0x00a3 #define UNITEXT_POUND_SIGN L"\u00a3" #define UNICODE_CURRENCY_SIGN 0x00a4 #define UNITEXT_CURRENCY_SIGN L"\u00a4" #define UNICODE_YEN_SIGN 0x00a5 #define UNITEXT_YEN_SIGN L"\u00a5" #define UNICODE_BROKEN_BAR 0x00a6 #define UNITEXT_BROKEN_BAR L"\u00a6" #define UNICODE_SECTION_SIGN 0x00a7 #define UNITEXT_SECTION_SIGN L"\u00a7" #define UNICODE_DIAERESIS 0x00a8 #define UNITEXT_DIAERESIS L"\u00a8" #define UNICODE_COPYRIGHT_SIGN 0x00a9 #define UNITEXT_COPYRIGHT_SIGN L"\u00a9" #define UNICODE_FEMININE_ORDINAL_INDICATOR 0x00aa #define UNITEXT_FEMININE_ORDINAL_INDICATOR L"\u00aa" #define UNICODE_LEFT_POINTING_DOUBLE_ANGLE_QUOTATION_MARK 0x00ab #define UNITEXT_LEFT_POINTING_DOUBLE_ANGLE_QUOTATION_MARK L"\u00ab" #define UNICODE_NOT_SIGN 0x00ac #define UNITEXT_NOT_SIGN L"\u00ac" #define UNICODE_SOFT_HYPHEN 0x00ad #define UNITEXT_SOFT_HYPHEN L"\u00ad" #define UNICODE_REGISTERED_SIGN 0x00ae #define UNITEXT_REGISTERED_SIGN L"\u00ae" #define UNICODE_MACRON 0x00af #define UNITEXT_MACRON L"\u00af" #define UNICODE_DEGREE_SIGN 0x00b0 #define UNITEXT_DEGREE_SIGN L"\u00b0" #define UNICODE_PLUS_MINUS_SIGN 0x00b1 #define UNITEXT_PLUS_MINUS_SIGN L"\u00b1" #define UNICODE_SUPERSCRIPT_TWO 0x00b2 #define UNITEXT_SUPERSCRIPT_TWO L"\u00b2" #define UNICODE_SUPERSCRIPT_THREE 0x00b3 #define UNITEXT_SUPERSCRIPT_THREE L"\u00b3" #define UNICODE_ACUTE_ACCENT 0x00b4 #define UNITEXT_ACUTE_ACCENT L"\u00b4" #define UNICODE_MICRO_SIGN 0x00b5 #define UNITEXT_MICRO_SIGN L"\u00b5" #define UNICODE_PILCROW_SIGN 0x00b6 #define UNITEXT_PILCROW_SIGN L"\u00b6" #define UNICODE_MIDDLE_DOT 0x00b7 #define UNITEXT_MIDDLE_DOT L"\u00b7" #define UNICODE_CEDILLA 0x00b8 #define UNITEXT_CEDILLA L"\u00b8" #define UNICODE_SUPERSCRIPT_ONE 0x00b9 #define UNITEXT_SUPERSCRIPT_ONE L"\u00b9" #define UNICODE_MASCULINE_ORDINAL_INDICATOR 0x00ba #define UNITEXT_MASCULINE_ORDINAL_INDICATOR L"\u00ba" #define UNICODE_RIGHT_POINTING_DOUBLE_ANGLE_QUOTATION_MARK 0x00bb #define UNITEXT_RIGHT_POINTING_DOUBLE_ANGLE_QUOTATION_MARK L"\u00bb" #define UNICODE_VULGAR_FRACTION_ONE_QUARTER 0x00bc #define UNITEXT_VULGAR_FRACTION_ONE_QUARTER L"\u00bc" #define UNICODE_VULGAR_FRACTION_ONE_HALF 0x00bd #define UNITEXT_VULGAR_FRACTION_ONE_HALF L"\u00bd" #define UNICODE_VULGAR_FRACTION_THREE_QUARTERS 0x00be #define UNITEXT_VULGAR_FRACTION_THREE_QUARTERS L"\u00be" #define UNICODE_INVERTED_QUESTION_MARK 0x00bf #define UNITEXT_INVERTED_QUESTION_MARK L"\u00bf" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_GRAVE 0x00c0 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_GRAVE L"\u00c0" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_ACUTE 0x00c1 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_ACUTE L"\u00c1" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX 0x00c2 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX L"\u00c2" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_TILDE 0x00c3 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_TILDE L"\u00c3" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_DIAERESIS 0x00c4 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_DIAERESIS L"\u00c4" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_RING_ABOVE 0x00c5 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_RING_ABOVE L"\u00c5" #define UNICODE_LATIN_CAPITAL_LETTER_AE 0x00c6 #define UNITEXT_LATIN_CAPITAL_LETTER_AE L"\u00c6" #define UNICODE_LATIN_CAPITAL_LETTER_C_WITH_CEDILLA 0x00c7 #define UNITEXT_LATIN_CAPITAL_LETTER_C_WITH_CEDILLA L"\u00c7" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_GRAVE 0x00c8 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_GRAVE L"\u00c8" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_ACUTE 0x00c9 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_ACUTE L"\u00c9" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX 0x00ca #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX L"\u00ca" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_DIAERESIS 0x00cb #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_DIAERESIS L"\u00cb" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_GRAVE 0x00cc #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_GRAVE L"\u00cc" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_ACUTE 0x00cd #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_ACUTE L"\u00cd" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_CIRCUMFLEX 0x00ce #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_CIRCUMFLEX L"\u00ce" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_DIAERESIS 0x00cf #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_DIAERESIS L"\u00cf" #define UNICODE_LATIN_CAPITAL_LETTER_ETH 0x00d0 #define UNITEXT_LATIN_CAPITAL_LETTER_ETH L"\u00d0" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_TILDE 0x00d1 #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_TILDE L"\u00d1" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_GRAVE 0x00d2 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_GRAVE L"\u00d2" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_ACUTE 0x00d3 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_ACUTE L"\u00d3" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX 0x00d4 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX L"\u00d4" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_TILDE 0x00d5 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_TILDE L"\u00d5" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DIAERESIS 0x00d6 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_DIAERESIS L"\u00d6" #define UNICODE_MULTIPLICATION_SIGN 0x00d7 #define UNITEXT_MULTIPLICATION_SIGN L"\u00d7" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_STROKE 0x00d8 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_STROKE L"\u00d8" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_GRAVE 0x00d9 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_GRAVE L"\u00d9" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_ACUTE 0x00da #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_ACUTE L"\u00da" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_CIRCUMFLEX 0x00db #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_CIRCUMFLEX L"\u00db" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS 0x00dc #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS L"\u00dc" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_ACUTE 0x00dd #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_ACUTE L"\u00dd" #define UNICODE_LATIN_CAPITAL_LETTER_THORN 0x00de #define UNITEXT_LATIN_CAPITAL_LETTER_THORN L"\u00de" #define UNICODE_LATIN_SMALL_LETTER_SHARP_S 0x00df #define UNITEXT_LATIN_SMALL_LETTER_SHARP_S L"\u00df" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_GRAVE 0x00e0 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_GRAVE L"\u00e0" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_ACUTE 0x00e1 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_ACUTE L"\u00e1" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX 0x00e2 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX L"\u00e2" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_TILDE 0x00e3 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_TILDE L"\u00e3" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_DIAERESIS 0x00e4 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_DIAERESIS L"\u00e4" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_RING_ABOVE 0x00e5 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_RING_ABOVE L"\u00e5" #define UNICODE_LATIN_SMALL_LETTER_AE 0x00e6 #define UNITEXT_LATIN_SMALL_LETTER_AE L"\u00e6" #define UNICODE_LATIN_SMALL_LETTER_C_WITH_CEDILLA 0x00e7 #define UNITEXT_LATIN_SMALL_LETTER_C_WITH_CEDILLA L"\u00e7" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_GRAVE 0x00e8 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_GRAVE L"\u00e8" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_ACUTE 0x00e9 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_ACUTE L"\u00e9" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX 0x00ea #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX L"\u00ea" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_DIAERESIS 0x00eb #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_DIAERESIS L"\u00eb" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_GRAVE 0x00ec #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_GRAVE L"\u00ec" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_ACUTE 0x00ed #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_ACUTE L"\u00ed" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_CIRCUMFLEX 0x00ee #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_CIRCUMFLEX L"\u00ee" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_DIAERESIS 0x00ef #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_DIAERESIS L"\u00ef" #define UNICODE_LATIN_SMALL_LETTER_ETH 0x00f0 #define UNITEXT_LATIN_SMALL_LETTER_ETH L"\u00f0" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_TILDE 0x00f1 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_TILDE L"\u00f1" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_GRAVE 0x00f2 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_GRAVE L"\u00f2" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_ACUTE 0x00f3 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_ACUTE L"\u00f3" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX 0x00f4 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX L"\u00f4" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_TILDE 0x00f5 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_TILDE L"\u00f5" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_DIAERESIS 0x00f6 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_DIAERESIS L"\u00f6" #define UNICODE_DIVISION_SIGN 0x00f7 #define UNITEXT_DIVISION_SIGN L"\u00f7" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_STROKE 0x00f8 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_STROKE L"\u00f8" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_GRAVE 0x00f9 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_GRAVE L"\u00f9" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_ACUTE 0x00fa #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_ACUTE L"\u00fa" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_CIRCUMFLEX 0x00fb #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_CIRCUMFLEX L"\u00fb" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_DIAERESIS 0x00fc #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_DIAERESIS L"\u00fc" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_ACUTE 0x00fd #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_ACUTE L"\u00fd" #define UNICODE_LATIN_SMALL_LETTER_THORN 0x00fe #define UNITEXT_LATIN_SMALL_LETTER_THORN L"\u00fe" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_DIAERESIS 0x00ff #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_DIAERESIS L"\u00ff" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_MACRON 0x0100 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_MACRON L"\u0100" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_MACRON 0x0101 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_MACRON L"\u0101" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_BREVE 0x0102 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_BREVE L"\u0102" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_BREVE 0x0103 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_BREVE L"\u0103" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_OGONEK 0x0104 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_OGONEK L"\u0104" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_OGONEK 0x0105 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_OGONEK L"\u0105" #define UNICODE_LATIN_CAPITAL_LETTER_C_WITH_ACUTE 0x0106 #define UNITEXT_LATIN_CAPITAL_LETTER_C_WITH_ACUTE L"\u0106" #define UNICODE_LATIN_SMALL_LETTER_C_WITH_ACUTE 0x0107 #define UNITEXT_LATIN_SMALL_LETTER_C_WITH_ACUTE L"\u0107" #define UNICODE_LATIN_CAPITAL_LETTER_C_WITH_CIRCUMFLEX 0x0108 #define UNITEXT_LATIN_CAPITAL_LETTER_C_WITH_CIRCUMFLEX L"\u0108" #define UNICODE_LATIN_SMALL_LETTER_C_WITH_CIRCUMFLEX 0x0109 #define UNITEXT_LATIN_SMALL_LETTER_C_WITH_CIRCUMFLEX L"\u0109" #define UNICODE_LATIN_CAPITAL_LETTER_C_WITH_DOT_ABOVE 0x010a #define UNITEXT_LATIN_CAPITAL_LETTER_C_WITH_DOT_ABOVE L"\u010a" #define UNICODE_LATIN_SMALL_LETTER_C_WITH_DOT_ABOVE 0x010b #define UNITEXT_LATIN_SMALL_LETTER_C_WITH_DOT_ABOVE L"\u010b" #define UNICODE_LATIN_CAPITAL_LETTER_C_WITH_CARON 0x010c #define UNITEXT_LATIN_CAPITAL_LETTER_C_WITH_CARON L"\u010c" #define UNICODE_LATIN_SMALL_LETTER_C_WITH_CARON 0x010d #define UNITEXT_LATIN_SMALL_LETTER_C_WITH_CARON L"\u010d" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_CARON 0x010e #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_CARON L"\u010e" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_CARON 0x010f #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_CARON L"\u010f" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_STROKE 0x0110 #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_STROKE L"\u0110" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_STROKE 0x0111 #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_STROKE L"\u0111" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_MACRON 0x0112 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_MACRON L"\u0112" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_MACRON 0x0113 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_MACRON L"\u0113" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_BREVE 0x0114 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_BREVE L"\u0114" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_BREVE 0x0115 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_BREVE L"\u0115" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_DOT_ABOVE 0x0116 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_DOT_ABOVE L"\u0116" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_DOT_ABOVE 0x0117 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_DOT_ABOVE L"\u0117" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_OGONEK 0x0118 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_OGONEK L"\u0118" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_OGONEK 0x0119 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_OGONEK L"\u0119" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CARON 0x011a #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CARON L"\u011a" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CARON 0x011b #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CARON L"\u011b" #define UNICODE_LATIN_CAPITAL_LETTER_G_WITH_CIRCUMFLEX 0x011c #define UNITEXT_LATIN_CAPITAL_LETTER_G_WITH_CIRCUMFLEX L"\u011c" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_CIRCUMFLEX 0x011d #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_CIRCUMFLEX L"\u011d" #define UNICODE_LATIN_CAPITAL_LETTER_G_WITH_BREVE 0x011e #define UNITEXT_LATIN_CAPITAL_LETTER_G_WITH_BREVE L"\u011e" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_BREVE 0x011f #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_BREVE L"\u011f" #define UNICODE_LATIN_CAPITAL_LETTER_G_WITH_DOT_ABOVE 0x0120 #define UNITEXT_LATIN_CAPITAL_LETTER_G_WITH_DOT_ABOVE L"\u0120" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_DOT_ABOVE 0x0121 #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_DOT_ABOVE L"\u0121" #define UNICODE_LATIN_CAPITAL_LETTER_G_WITH_CEDILLA 0x0122 #define UNITEXT_LATIN_CAPITAL_LETTER_G_WITH_CEDILLA L"\u0122" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_CEDILLA 0x0123 #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_CEDILLA L"\u0123" #define UNICODE_LATIN_CAPITAL_LETTER_H_WITH_CIRCUMFLEX 0x0124 #define UNITEXT_LATIN_CAPITAL_LETTER_H_WITH_CIRCUMFLEX L"\u0124" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_CIRCUMFLEX 0x0125 #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_CIRCUMFLEX L"\u0125" #define UNICODE_LATIN_CAPITAL_LETTER_H_WITH_STROKE 0x0126 #define UNITEXT_LATIN_CAPITAL_LETTER_H_WITH_STROKE L"\u0126" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_STROKE 0x0127 #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_STROKE L"\u0127" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_TILDE 0x0128 #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_TILDE L"\u0128" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_TILDE 0x0129 #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_TILDE L"\u0129" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_MACRON 0x012a #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_MACRON L"\u012a" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_MACRON 0x012b #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_MACRON L"\u012b" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_BREVE 0x012c #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_BREVE L"\u012c" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_BREVE 0x012d #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_BREVE L"\u012d" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_OGONEK 0x012e #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_OGONEK L"\u012e" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_OGONEK 0x012f #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_OGONEK L"\u012f" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_DOT_ABOVE 0x0130 #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_DOT_ABOVE L"\u0130" #define UNICODE_LATIN_SMALL_LETTER_DOTLESS_I 0x0131 #define UNITEXT_LATIN_SMALL_LETTER_DOTLESS_I L"\u0131" #define UNICODE_LATIN_CAPITAL_LIGATURE_IJ 0x0132 #define UNITEXT_LATIN_CAPITAL_LIGATURE_IJ L"\u0132" #define UNICODE_LATIN_SMALL_LIGATURE_IJ 0x0133 #define UNITEXT_LATIN_SMALL_LIGATURE_IJ L"\u0133" #define UNICODE_LATIN_CAPITAL_LETTER_J_WITH_CIRCUMFLEX 0x0134 #define UNITEXT_LATIN_CAPITAL_LETTER_J_WITH_CIRCUMFLEX L"\u0134" #define UNICODE_LATIN_SMALL_LETTER_J_WITH_CIRCUMFLEX 0x0135 #define UNITEXT_LATIN_SMALL_LETTER_J_WITH_CIRCUMFLEX L"\u0135" #define UNICODE_LATIN_CAPITAL_LETTER_K_WITH_CEDILLA 0x0136 #define UNITEXT_LATIN_CAPITAL_LETTER_K_WITH_CEDILLA L"\u0136" #define UNICODE_LATIN_SMALL_LETTER_K_WITH_CEDILLA 0x0137 #define UNITEXT_LATIN_SMALL_LETTER_K_WITH_CEDILLA L"\u0137" #define UNICODE_LATIN_SMALL_LETTER_KRA 0x0138 #define UNITEXT_LATIN_SMALL_LETTER_KRA L"\u0138" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_ACUTE 0x0139 #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_ACUTE L"\u0139" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_ACUTE 0x013a #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_ACUTE L"\u013a" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_CEDILLA 0x013b #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_CEDILLA L"\u013b" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_CEDILLA 0x013c #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_CEDILLA L"\u013c" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_CARON 0x013d #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_CARON L"\u013d" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_CARON 0x013e #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_CARON L"\u013e" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_MIDDLE_DOT 0x013f #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_MIDDLE_DOT L"\u013f" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_MIDDLE_DOT 0x0140 #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_MIDDLE_DOT L"\u0140" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_STROKE 0x0141 #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_STROKE L"\u0141" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_STROKE 0x0142 #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_STROKE L"\u0142" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_ACUTE 0x0143 #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_ACUTE L"\u0143" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_ACUTE 0x0144 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_ACUTE L"\u0144" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_CEDILLA 0x0145 #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_CEDILLA L"\u0145" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_CEDILLA 0x0146 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_CEDILLA L"\u0146" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_CARON 0x0147 #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_CARON L"\u0147" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_CARON 0x0148 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_CARON L"\u0148" #define UNICODE_LATIN_SMALL_LETTER_N_PRECEDED_BY_APOSTROPHE 0x0149 #define UNITEXT_LATIN_SMALL_LETTER_N_PRECEDED_BY_APOSTROPHE L"\u0149" #define UNICODE_LATIN_CAPITAL_LETTER_ENG 0x014a #define UNITEXT_LATIN_CAPITAL_LETTER_ENG L"\u014a" #define UNICODE_LATIN_SMALL_LETTER_ENG 0x014b #define UNITEXT_LATIN_SMALL_LETTER_ENG L"\u014b" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_MACRON 0x014c #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_MACRON L"\u014c" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_MACRON 0x014d #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_MACRON L"\u014d" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_BREVE 0x014e #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_BREVE L"\u014e" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_BREVE 0x014f #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_BREVE L"\u014f" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DOUBLE_ACUTE 0x0150 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_DOUBLE_ACUTE L"\u0150" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_DOUBLE_ACUTE 0x0151 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_DOUBLE_ACUTE L"\u0151" #define UNICODE_LATIN_CAPITAL_LIGATURE_OE 0x0152 #define UNITEXT_LATIN_CAPITAL_LIGATURE_OE L"\u0152" #define UNICODE_LATIN_SMALL_LIGATURE_OE 0x0153 #define UNITEXT_LATIN_SMALL_LIGATURE_OE L"\u0153" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_ACUTE 0x0154 #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_ACUTE L"\u0154" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_ACUTE 0x0155 #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_ACUTE L"\u0155" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_CEDILLA 0x0156 #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_CEDILLA L"\u0156" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_CEDILLA 0x0157 #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_CEDILLA L"\u0157" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_CARON 0x0158 #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_CARON L"\u0158" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_CARON 0x0159 #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_CARON L"\u0159" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_ACUTE 0x015a #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_ACUTE L"\u015a" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_ACUTE 0x015b #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_ACUTE L"\u015b" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_CIRCUMFLEX 0x015c #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_CIRCUMFLEX L"\u015c" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_CIRCUMFLEX 0x015d #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_CIRCUMFLEX L"\u015d" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_CEDILLA 0x015e #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_CEDILLA L"\u015e" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_CEDILLA 0x015f #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_CEDILLA L"\u015f" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_CARON 0x0160 #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_CARON L"\u0160" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_CARON 0x0161 #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_CARON L"\u0161" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_CEDILLA 0x0162 #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_CEDILLA L"\u0162" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_CEDILLA 0x0163 #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_CEDILLA L"\u0163" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_CARON 0x0164 #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_CARON L"\u0164" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_CARON 0x0165 #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_CARON L"\u0165" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_STROKE 0x0166 #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_STROKE L"\u0166" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_STROKE 0x0167 #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_STROKE L"\u0167" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_TILDE 0x0168 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_TILDE L"\u0168" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_TILDE 0x0169 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_TILDE L"\u0169" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_MACRON 0x016a #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_MACRON L"\u016a" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_MACRON 0x016b #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_MACRON L"\u016b" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_BREVE 0x016c #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_BREVE L"\u016c" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_BREVE 0x016d #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_BREVE L"\u016d" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_RING_ABOVE 0x016e #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_RING_ABOVE L"\u016e" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_RING_ABOVE 0x016f #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_RING_ABOVE L"\u016f" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DOUBLE_ACUTE 0x0170 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_DOUBLE_ACUTE L"\u0170" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_DOUBLE_ACUTE 0x0171 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_DOUBLE_ACUTE L"\u0171" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_OGONEK 0x0172 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_OGONEK L"\u0172" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_OGONEK 0x0173 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_OGONEK L"\u0173" #define UNICODE_LATIN_CAPITAL_LETTER_W_WITH_CIRCUMFLEX 0x0174 #define UNITEXT_LATIN_CAPITAL_LETTER_W_WITH_CIRCUMFLEX L"\u0174" #define UNICODE_LATIN_SMALL_LETTER_W_WITH_CIRCUMFLEX 0x0175 #define UNITEXT_LATIN_SMALL_LETTER_W_WITH_CIRCUMFLEX L"\u0175" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_CIRCUMFLEX 0x0176 #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_CIRCUMFLEX L"\u0176" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_CIRCUMFLEX 0x0177 #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_CIRCUMFLEX L"\u0177" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_DIAERESIS 0x0178 #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_DIAERESIS L"\u0178" #define UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_ACUTE 0x0179 #define UNITEXT_LATIN_CAPITAL_LETTER_Z_WITH_ACUTE L"\u0179" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_ACUTE 0x017a #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_ACUTE L"\u017a" #define UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_DOT_ABOVE 0x017b #define UNITEXT_LATIN_CAPITAL_LETTER_Z_WITH_DOT_ABOVE L"\u017b" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_DOT_ABOVE 0x017c #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_DOT_ABOVE L"\u017c" #define UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_CARON 0x017d #define UNITEXT_LATIN_CAPITAL_LETTER_Z_WITH_CARON L"\u017d" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_CARON 0x017e #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_CARON L"\u017e" #define UNICODE_LATIN_SMALL_LETTER_LONG_S 0x017f #define UNITEXT_LATIN_SMALL_LETTER_LONG_S L"\u017f" #define UNICODE_LATIN_SMALL_LETTER_B_WITH_STROKE 0x0180 #define UNITEXT_LATIN_SMALL_LETTER_B_WITH_STROKE L"\u0180" #define UNICODE_LATIN_CAPITAL_LETTER_B_WITH_HOOK 0x0181 #define UNITEXT_LATIN_CAPITAL_LETTER_B_WITH_HOOK L"\u0181" #define UNICODE_LATIN_CAPITAL_LETTER_B_WITH_TOPBAR 0x0182 #define UNITEXT_LATIN_CAPITAL_LETTER_B_WITH_TOPBAR L"\u0182" #define UNICODE_LATIN_SMALL_LETTER_B_WITH_TOPBAR 0x0183 #define UNITEXT_LATIN_SMALL_LETTER_B_WITH_TOPBAR L"\u0183" #define UNICODE_LATIN_CAPITAL_LETTER_TONE_SIX 0x0184 #define UNITEXT_LATIN_CAPITAL_LETTER_TONE_SIX L"\u0184" #define UNICODE_LATIN_SMALL_LETTER_TONE_SIX 0x0185 #define UNITEXT_LATIN_SMALL_LETTER_TONE_SIX L"\u0185" #define UNICODE_LATIN_CAPITAL_LETTER_OPEN_O 0x0186 #define UNITEXT_LATIN_CAPITAL_LETTER_OPEN_O L"\u0186" #define UNICODE_LATIN_CAPITAL_LETTER_C_WITH_HOOK 0x0187 #define UNITEXT_LATIN_CAPITAL_LETTER_C_WITH_HOOK L"\u0187" #define UNICODE_LATIN_SMALL_LETTER_C_WITH_HOOK 0x0188 #define UNITEXT_LATIN_SMALL_LETTER_C_WITH_HOOK L"\u0188" #define UNICODE_LATIN_CAPITAL_LETTER_AFRICAN_D 0x0189 #define UNITEXT_LATIN_CAPITAL_LETTER_AFRICAN_D L"\u0189" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_HOOK 0x018a #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_HOOK L"\u018a" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_TOPBAR 0x018b #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_TOPBAR L"\u018b" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_TOPBAR 0x018c #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_TOPBAR L"\u018c" #define UNICODE_LATIN_SMALL_LETTER_TURNED_DELTA 0x018d #define UNITEXT_LATIN_SMALL_LETTER_TURNED_DELTA L"\u018d" #define UNICODE_LATIN_CAPITAL_LETTER_REVERSED_E 0x018e #define UNITEXT_LATIN_CAPITAL_LETTER_REVERSED_E L"\u018e" #define UNICODE_LATIN_CAPITAL_LETTER_SCHWA 0x018f #define UNITEXT_LATIN_CAPITAL_LETTER_SCHWA L"\u018f" #define UNICODE_LATIN_CAPITAL_LETTER_OPEN_E 0x0190 #define UNITEXT_LATIN_CAPITAL_LETTER_OPEN_E L"\u0190" #define UNICODE_LATIN_CAPITAL_LETTER_F_WITH_HOOK 0x0191 #define UNITEXT_LATIN_CAPITAL_LETTER_F_WITH_HOOK L"\u0191" #define UNICODE_LATIN_SMALL_LETTER_F_WITH_HOOK 0x0192 #define UNITEXT_LATIN_SMALL_LETTER_F_WITH_HOOK L"\u0192" #define UNICODE_LATIN_CAPITAL_LETTER_G_WITH_HOOK 0x0193 #define UNITEXT_LATIN_CAPITAL_LETTER_G_WITH_HOOK L"\u0193" #define UNICODE_LATIN_CAPITAL_LETTER_GAMMA 0x0194 #define UNITEXT_LATIN_CAPITAL_LETTER_GAMMA L"\u0194" #define UNICODE_LATIN_SMALL_LETTER_HV 0x0195 #define UNITEXT_LATIN_SMALL_LETTER_HV L"\u0195" #define UNICODE_LATIN_CAPITAL_LETTER_IOTA 0x0196 #define UNITEXT_LATIN_CAPITAL_LETTER_IOTA L"\u0196" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_STROKE 0x0197 #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_STROKE L"\u0197" #define UNICODE_LATIN_CAPITAL_LETTER_K_WITH_HOOK 0x0198 #define UNITEXT_LATIN_CAPITAL_LETTER_K_WITH_HOOK L"\u0198" #define UNICODE_LATIN_SMALL_LETTER_K_WITH_HOOK 0x0199 #define UNITEXT_LATIN_SMALL_LETTER_K_WITH_HOOK L"\u0199" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_BAR 0x019a #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_BAR L"\u019a" #define UNICODE_LATIN_SMALL_LETTER_LAMBDA_WITH_STROKE 0x019b #define UNITEXT_LATIN_SMALL_LETTER_LAMBDA_WITH_STROKE L"\u019b" #define UNICODE_LATIN_CAPITAL_LETTER_TURNED_M 0x019c #define UNITEXT_LATIN_CAPITAL_LETTER_TURNED_M L"\u019c" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_LEFT_HOOK 0x019d #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_LEFT_HOOK L"\u019d" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_LONG_RIGHT_LEG 0x019e #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_LONG_RIGHT_LEG L"\u019e" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_MIDDLE_TILDE 0x019f #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_MIDDLE_TILDE L"\u019f" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_HORN 0x01a0 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_HORN L"\u01a0" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_HORN 0x01a1 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_HORN L"\u01a1" #define UNICODE_LATIN_CAPITAL_LETTER_OI 0x01a2 #define UNITEXT_LATIN_CAPITAL_LETTER_OI L"\u01a2" #define UNICODE_LATIN_SMALL_LETTER_OI 0x01a3 #define UNITEXT_LATIN_SMALL_LETTER_OI L"\u01a3" #define UNICODE_LATIN_CAPITAL_LETTER_P_WITH_HOOK 0x01a4 #define UNITEXT_LATIN_CAPITAL_LETTER_P_WITH_HOOK L"\u01a4" #define UNICODE_LATIN_SMALL_LETTER_P_WITH_HOOK 0x01a5 #define UNITEXT_LATIN_SMALL_LETTER_P_WITH_HOOK L"\u01a5" #define UNICODE_LATIN_LETTER_YR 0x01a6 #define UNITEXT_LATIN_LETTER_YR L"\u01a6" #define UNICODE_LATIN_CAPITAL_LETTER_TONE_TWO 0x01a7 #define UNITEXT_LATIN_CAPITAL_LETTER_TONE_TWO L"\u01a7" #define UNICODE_LATIN_SMALL_LETTER_TONE_TWO 0x01a8 #define UNITEXT_LATIN_SMALL_LETTER_TONE_TWO L"\u01a8" #define UNICODE_LATIN_CAPITAL_LETTER_ESH 0x01a9 #define UNITEXT_LATIN_CAPITAL_LETTER_ESH L"\u01a9" #define UNICODE_LATIN_LETTER_REVERSED_ESH_LOOP 0x01aa #define UNITEXT_LATIN_LETTER_REVERSED_ESH_LOOP L"\u01aa" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_PALATAL_HOOK 0x01ab #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_PALATAL_HOOK L"\u01ab" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_HOOK 0x01ac #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_HOOK L"\u01ac" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_HOOK 0x01ad #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_HOOK L"\u01ad" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_RETROFLEX_HOOK 0x01ae #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_RETROFLEX_HOOK L"\u01ae" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_HORN 0x01af #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_HORN L"\u01af" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_HORN 0x01b0 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_HORN L"\u01b0" #define UNICODE_LATIN_CAPITAL_LETTER_UPSILON 0x01b1 #define UNITEXT_LATIN_CAPITAL_LETTER_UPSILON L"\u01b1" #define UNICODE_LATIN_CAPITAL_LETTER_V_WITH_HOOK 0x01b2 #define UNITEXT_LATIN_CAPITAL_LETTER_V_WITH_HOOK L"\u01b2" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_HOOK 0x01b3 #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_HOOK L"\u01b3" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_HOOK 0x01b4 #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_HOOK L"\u01b4" #define UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_STROKE 0x01b5 #define UNITEXT_LATIN_CAPITAL_LETTER_Z_WITH_STROKE L"\u01b5" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_STROKE 0x01b6 #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_STROKE L"\u01b6" #define UNICODE_LATIN_CAPITAL_LETTER_EZH 0x01b7 #define UNITEXT_LATIN_CAPITAL_LETTER_EZH L"\u01b7" #define UNICODE_LATIN_CAPITAL_LETTER_EZH_REVERSED 0x01b8 #define UNITEXT_LATIN_CAPITAL_LETTER_EZH_REVERSED L"\u01b8" #define UNICODE_LATIN_SMALL_LETTER_EZH_REVERSED 0x01b9 #define UNITEXT_LATIN_SMALL_LETTER_EZH_REVERSED L"\u01b9" #define UNICODE_LATIN_SMALL_LETTER_EZH_WITH_TAIL 0x01ba #define UNITEXT_LATIN_SMALL_LETTER_EZH_WITH_TAIL L"\u01ba" #define UNICODE_LATIN_LETTER_TWO_WITH_STROKE 0x01bb #define UNITEXT_LATIN_LETTER_TWO_WITH_STROKE L"\u01bb" #define UNICODE_LATIN_CAPITAL_LETTER_TONE_FIVE 0x01bc #define UNITEXT_LATIN_CAPITAL_LETTER_TONE_FIVE L"\u01bc" #define UNICODE_LATIN_SMALL_LETTER_TONE_FIVE 0x01bd #define UNITEXT_LATIN_SMALL_LETTER_TONE_FIVE L"\u01bd" #define UNICODE_LATIN_LETTER_INVERTED_GLOTTAL_STOP_WITH_STROKE 0x01be #define UNITEXT_LATIN_LETTER_INVERTED_GLOTTAL_STOP_WITH_STROKE L"\u01be" #define UNICODE_LATIN_LETTER_WYNN 0x01bf #define UNITEXT_LATIN_LETTER_WYNN L"\u01bf" #define UNICODE_LATIN_LETTER_DENTAL_CLICK 0x01c0 #define UNITEXT_LATIN_LETTER_DENTAL_CLICK L"\u01c0" #define UNICODE_LATIN_LETTER_LATERAL_CLICK 0x01c1 #define UNITEXT_LATIN_LETTER_LATERAL_CLICK L"\u01c1" #define UNICODE_LATIN_LETTER_ALVEOLAR_CLICK 0x01c2 #define UNITEXT_LATIN_LETTER_ALVEOLAR_CLICK L"\u01c2" #define UNICODE_LATIN_LETTER_RETROFLEX_CLICK 0x01c3 #define UNITEXT_LATIN_LETTER_RETROFLEX_CLICK L"\u01c3" #define UNICODE_LATIN_CAPITAL_LETTER_DZ_WITH_CARON 0x01c4 #define UNITEXT_LATIN_CAPITAL_LETTER_DZ_WITH_CARON L"\u01c4" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_SMALL_LETTER_Z_WITH_CARON 0x01c5 #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_SMALL_LETTER_Z_WITH_CARON L"\u01c5" #define UNICODE_LATIN_SMALL_LETTER_DZ_WITH_CARON 0x01c6 #define UNITEXT_LATIN_SMALL_LETTER_DZ_WITH_CARON L"\u01c6" #define UNICODE_LATIN_CAPITAL_LETTER_LJ 0x01c7 #define UNITEXT_LATIN_CAPITAL_LETTER_LJ L"\u01c7" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_SMALL_LETTER_J 0x01c8 #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_SMALL_LETTER_J L"\u01c8" #define UNICODE_LATIN_SMALL_LETTER_LJ 0x01c9 #define UNITEXT_LATIN_SMALL_LETTER_LJ L"\u01c9" #define UNICODE_LATIN_CAPITAL_LETTER_NJ 0x01ca #define UNITEXT_LATIN_CAPITAL_LETTER_NJ L"\u01ca" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_SMALL_LETTER_J 0x01cb #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_SMALL_LETTER_J L"\u01cb" #define UNICODE_LATIN_SMALL_LETTER_NJ 0x01cc #define UNITEXT_LATIN_SMALL_LETTER_NJ L"\u01cc" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_CARON 0x01cd #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_CARON L"\u01cd" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_CARON 0x01ce #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_CARON L"\u01ce" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_CARON 0x01cf #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_CARON L"\u01cf" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_CARON 0x01d0 #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_CARON L"\u01d0" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_CARON 0x01d1 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_CARON L"\u01d1" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_CARON 0x01d2 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_CARON L"\u01d2" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_CARON 0x01d3 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_CARON L"\u01d3" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_CARON 0x01d4 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_CARON L"\u01d4" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_AND_MACRON 0x01d5 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_AND_MACRON L"\u01d5" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_AND_MACRON 0x01d6 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_AND_MACRON L"\u01d6" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_AND_ACUTE 0x01d7 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_AND_ACUTE L"\u01d7" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_AND_ACUTE 0x01d8 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_AND_ACUTE L"\u01d8" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_AND_CARON 0x01d9 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_AND_CARON L"\u01d9" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_AND_CARON 0x01da #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_AND_CARON L"\u01da" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_AND_GRAVE 0x01db #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_AND_GRAVE L"\u01db" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_AND_GRAVE 0x01dc #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_AND_GRAVE L"\u01dc" #define UNICODE_LATIN_SMALL_LETTER_TURNED_E 0x01dd #define UNITEXT_LATIN_SMALL_LETTER_TURNED_E L"\u01dd" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_DIAERESIS_AND_MACRON 0x01de #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_DIAERESIS_AND_MACRON L"\u01de" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_DIAERESIS_AND_MACRON 0x01df #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_DIAERESIS_AND_MACRON L"\u01df" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_DOT_ABOVE_AND_MACRON 0x01e0 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_DOT_ABOVE_AND_MACRON L"\u01e0" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_DOT_ABOVE_AND_MACRON 0x01e1 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_DOT_ABOVE_AND_MACRON L"\u01e1" #define UNICODE_LATIN_CAPITAL_LETTER_AE_WITH_MACRON 0x01e2 #define UNITEXT_LATIN_CAPITAL_LETTER_AE_WITH_MACRON L"\u01e2" #define UNICODE_LATIN_SMALL_LETTER_AE_WITH_MACRON 0x01e3 #define UNITEXT_LATIN_SMALL_LETTER_AE_WITH_MACRON L"\u01e3" #define UNICODE_LATIN_CAPITAL_LETTER_G_WITH_STROKE 0x01e4 #define UNITEXT_LATIN_CAPITAL_LETTER_G_WITH_STROKE L"\u01e4" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_STROKE 0x01e5 #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_STROKE L"\u01e5" #define UNICODE_LATIN_CAPITAL_LETTER_G_WITH_CARON 0x01e6 #define UNITEXT_LATIN_CAPITAL_LETTER_G_WITH_CARON L"\u01e6" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_CARON 0x01e7 #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_CARON L"\u01e7" #define UNICODE_LATIN_CAPITAL_LETTER_K_WITH_CARON 0x01e8 #define UNITEXT_LATIN_CAPITAL_LETTER_K_WITH_CARON L"\u01e8" #define UNICODE_LATIN_SMALL_LETTER_K_WITH_CARON 0x01e9 #define UNITEXT_LATIN_SMALL_LETTER_K_WITH_CARON L"\u01e9" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_OGONEK 0x01ea #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_OGONEK L"\u01ea" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_OGONEK 0x01eb #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_OGONEK L"\u01eb" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_OGONEK_AND_MACRON 0x01ec #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_OGONEK_AND_MACRON L"\u01ec" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_OGONEK_AND_MACRON 0x01ed #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_OGONEK_AND_MACRON L"\u01ed" #define UNICODE_LATIN_CAPITAL_LETTER_EZH_WITH_CARON 0x01ee #define UNITEXT_LATIN_CAPITAL_LETTER_EZH_WITH_CARON L"\u01ee" #define UNICODE_LATIN_SMALL_LETTER_EZH_WITH_CARON 0x01ef #define UNITEXT_LATIN_SMALL_LETTER_EZH_WITH_CARON L"\u01ef" #define UNICODE_LATIN_SMALL_LETTER_J_WITH_CARON 0x01f0 #define UNITEXT_LATIN_SMALL_LETTER_J_WITH_CARON L"\u01f0" #define UNICODE_LATIN_CAPITAL_LETTER_DZ 0x01f1 #define UNITEXT_LATIN_CAPITAL_LETTER_DZ L"\u01f1" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_SMALL_LETTER_Z 0x01f2 #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_SMALL_LETTER_Z L"\u01f2" #define UNICODE_LATIN_SMALL_LETTER_DZ 0x01f3 #define UNITEXT_LATIN_SMALL_LETTER_DZ L"\u01f3" #define UNICODE_LATIN_CAPITAL_LETTER_G_WITH_ACUTE 0x01f4 #define UNITEXT_LATIN_CAPITAL_LETTER_G_WITH_ACUTE L"\u01f4" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_ACUTE 0x01f5 #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_ACUTE L"\u01f5" #define UNICODE_LATIN_CAPITAL_LETTER_HWAIR 0x01f6 #define UNITEXT_LATIN_CAPITAL_LETTER_HWAIR L"\u01f6" #define UNICODE_LATIN_CAPITAL_LETTER_WYNN 0x01f7 #define UNITEXT_LATIN_CAPITAL_LETTER_WYNN L"\u01f7" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_GRAVE 0x01f8 #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_GRAVE L"\u01f8" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_GRAVE 0x01f9 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_GRAVE L"\u01f9" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_RING_ABOVE_AND_ACUTE 0x01fa #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_RING_ABOVE_AND_ACUTE L"\u01fa" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_RING_ABOVE_AND_ACUTE 0x01fb #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_RING_ABOVE_AND_ACUTE L"\u01fb" #define UNICODE_LATIN_CAPITAL_LETTER_AE_WITH_ACUTE 0x01fc #define UNITEXT_LATIN_CAPITAL_LETTER_AE_WITH_ACUTE L"\u01fc" #define UNICODE_LATIN_SMALL_LETTER_AE_WITH_ACUTE 0x01fd #define UNITEXT_LATIN_SMALL_LETTER_AE_WITH_ACUTE L"\u01fd" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_STROKE_AND_ACUTE 0x01fe #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_STROKE_AND_ACUTE L"\u01fe" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_STROKE_AND_ACUTE 0x01ff #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_STROKE_AND_ACUTE L"\u01ff" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_DOUBLE_GRAVE 0x0200 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_DOUBLE_GRAVE L"\u0200" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_DOUBLE_GRAVE 0x0201 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_DOUBLE_GRAVE L"\u0201" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_INVERTED_BREVE 0x0202 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_INVERTED_BREVE L"\u0202" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_INVERTED_BREVE 0x0203 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_INVERTED_BREVE L"\u0203" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_DOUBLE_GRAVE 0x0204 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_DOUBLE_GRAVE L"\u0204" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_DOUBLE_GRAVE 0x0205 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_DOUBLE_GRAVE L"\u0205" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_INVERTED_BREVE 0x0206 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_INVERTED_BREVE L"\u0206" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_INVERTED_BREVE 0x0207 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_INVERTED_BREVE L"\u0207" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_DOUBLE_GRAVE 0x0208 #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_DOUBLE_GRAVE L"\u0208" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_DOUBLE_GRAVE 0x0209 #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_DOUBLE_GRAVE L"\u0209" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_INVERTED_BREVE 0x020a #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_INVERTED_BREVE L"\u020a" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_INVERTED_BREVE 0x020b #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_INVERTED_BREVE L"\u020b" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DOUBLE_GRAVE 0x020c #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_DOUBLE_GRAVE L"\u020c" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_DOUBLE_GRAVE 0x020d #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_DOUBLE_GRAVE L"\u020d" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_INVERTED_BREVE 0x020e #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_INVERTED_BREVE L"\u020e" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_INVERTED_BREVE 0x020f #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_INVERTED_BREVE L"\u020f" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_DOUBLE_GRAVE 0x0210 #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_DOUBLE_GRAVE L"\u0210" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_DOUBLE_GRAVE 0x0211 #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_DOUBLE_GRAVE L"\u0211" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_INVERTED_BREVE 0x0212 #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_INVERTED_BREVE L"\u0212" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_INVERTED_BREVE 0x0213 #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_INVERTED_BREVE L"\u0213" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DOUBLE_GRAVE 0x0214 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_DOUBLE_GRAVE L"\u0214" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_DOUBLE_GRAVE 0x0215 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_DOUBLE_GRAVE L"\u0215" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_INVERTED_BREVE 0x0216 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_INVERTED_BREVE L"\u0216" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_INVERTED_BREVE 0x0217 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_INVERTED_BREVE L"\u0217" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_COMMA_BELOW 0x0218 #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_COMMA_BELOW L"\u0218" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_COMMA_BELOW 0x0219 #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_COMMA_BELOW L"\u0219" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_COMMA_BELOW 0x021a #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_COMMA_BELOW L"\u021a" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_COMMA_BELOW 0x021b #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_COMMA_BELOW L"\u021b" #define UNICODE_LATIN_CAPITAL_LETTER_YOGH 0x021c #define UNITEXT_LATIN_CAPITAL_LETTER_YOGH L"\u021c" #define UNICODE_LATIN_SMALL_LETTER_YOGH 0x021d #define UNITEXT_LATIN_SMALL_LETTER_YOGH L"\u021d" #define UNICODE_LATIN_CAPITAL_LETTER_H_WITH_CARON 0x021e #define UNITEXT_LATIN_CAPITAL_LETTER_H_WITH_CARON L"\u021e" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_CARON 0x021f #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_CARON L"\u021f" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_LONG_RIGHT_LEG 0x0220 #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_LONG_RIGHT_LEG L"\u0220" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_CURL 0x0221 #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_CURL L"\u0221" #define UNICODE_LATIN_CAPITAL_LETTER_OU 0x0222 #define UNITEXT_LATIN_CAPITAL_LETTER_OU L"\u0222" #define UNICODE_LATIN_SMALL_LETTER_OU 0x0223 #define UNITEXT_LATIN_SMALL_LETTER_OU L"\u0223" #define UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_HOOK 0x0224 #define UNITEXT_LATIN_CAPITAL_LETTER_Z_WITH_HOOK L"\u0224" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_HOOK 0x0225 #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_HOOK L"\u0225" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_DOT_ABOVE 0x0226 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_DOT_ABOVE L"\u0226" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_DOT_ABOVE 0x0227 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_DOT_ABOVE L"\u0227" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CEDILLA 0x0228 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CEDILLA L"\u0228" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CEDILLA 0x0229 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CEDILLA L"\u0229" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DIAERESIS_AND_MACRON 0x022a #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_DIAERESIS_AND_MACRON L"\u022a" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_DIAERESIS_AND_MACRON 0x022b #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_DIAERESIS_AND_MACRON L"\u022b" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_TILDE_AND_MACRON 0x022c #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_TILDE_AND_MACRON L"\u022c" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_TILDE_AND_MACRON 0x022d #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_TILDE_AND_MACRON L"\u022d" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DOT_ABOVE 0x022e #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_DOT_ABOVE L"\u022e" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_DOT_ABOVE 0x022f #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_DOT_ABOVE L"\u022f" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DOT_ABOVE_AND_MACRON 0x0230 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_DOT_ABOVE_AND_MACRON L"\u0230" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_DOT_ABOVE_AND_MACRON 0x0231 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_DOT_ABOVE_AND_MACRON L"\u0231" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_MACRON 0x0232 #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_MACRON L"\u0232" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_MACRON 0x0233 #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_MACRON L"\u0233" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_CURL 0x0234 #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_CURL L"\u0234" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_CURL 0x0235 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_CURL L"\u0235" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_CURL 0x0236 #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_CURL L"\u0236" #define UNICODE_LATIN_SMALL_LETTER_DOTLESS_J 0x0237 #define UNITEXT_LATIN_SMALL_LETTER_DOTLESS_J L"\u0237" #define UNICODE_LATIN_SMALL_LETTER_DB_DIGRAPH 0x0238 #define UNITEXT_LATIN_SMALL_LETTER_DB_DIGRAPH L"\u0238" #define UNICODE_LATIN_SMALL_LETTER_QP_DIGRAPH 0x0239 #define UNITEXT_LATIN_SMALL_LETTER_QP_DIGRAPH L"\u0239" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_STROKE 0x023a #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_STROKE L"\u023a" #define UNICODE_LATIN_CAPITAL_LETTER_C_WITH_STROKE 0x023b #define UNITEXT_LATIN_CAPITAL_LETTER_C_WITH_STROKE L"\u023b" #define UNICODE_LATIN_SMALL_LETTER_C_WITH_STROKE 0x023c #define UNITEXT_LATIN_SMALL_LETTER_C_WITH_STROKE L"\u023c" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_BAR 0x023d #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_BAR L"\u023d" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_DIAGONAL_STROKE 0x023e #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_DIAGONAL_STROKE L"\u023e" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_SWASH_TAIL 0x023f #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_SWASH_TAIL L"\u023f" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_SWASH_TAIL 0x0240 #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_SWASH_TAIL L"\u0240" #define UNICODE_LATIN_CAPITAL_LETTER_GLOTTAL_STOP 0x0241 #define UNITEXT_LATIN_CAPITAL_LETTER_GLOTTAL_STOP L"\u0241" #define UNICODE_LATIN_SMALL_LETTER_GLOTTAL_STOP 0x0242 #define UNITEXT_LATIN_SMALL_LETTER_GLOTTAL_STOP L"\u0242" #define UNICODE_LATIN_CAPITAL_LETTER_B_WITH_STROKE 0x0243 #define UNITEXT_LATIN_CAPITAL_LETTER_B_WITH_STROKE L"\u0243" #define UNICODE_LATIN_CAPITAL_LETTER_U_BAR 0x0244 #define UNITEXT_LATIN_CAPITAL_LETTER_U_BAR L"\u0244" #define UNICODE_LATIN_CAPITAL_LETTER_TURNED_V 0x0245 #define UNITEXT_LATIN_CAPITAL_LETTER_TURNED_V L"\u0245" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_STROKE 0x0246 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_STROKE L"\u0246" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_STROKE 0x0247 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_STROKE L"\u0247" #define UNICODE_LATIN_CAPITAL_LETTER_J_WITH_STROKE 0x0248 #define UNITEXT_LATIN_CAPITAL_LETTER_J_WITH_STROKE L"\u0248" #define UNICODE_LATIN_SMALL_LETTER_J_WITH_STROKE 0x0249 #define UNITEXT_LATIN_SMALL_LETTER_J_WITH_STROKE L"\u0249" #define UNICODE_LATIN_CAPITAL_LETTER_SMALL_Q_WITH_HOOK_TAIL 0x024a #define UNITEXT_LATIN_CAPITAL_LETTER_SMALL_Q_WITH_HOOK_TAIL L"\u024a" #define UNICODE_LATIN_SMALL_LETTER_Q_WITH_HOOK_TAIL 0x024b #define UNITEXT_LATIN_SMALL_LETTER_Q_WITH_HOOK_TAIL L"\u024b" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_STROKE 0x024c #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_STROKE L"\u024c" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_STROKE 0x024d #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_STROKE L"\u024d" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_STROKE 0x024e #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_STROKE L"\u024e" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_STROKE 0x024f #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_STROKE L"\u024f" #define UNICODE_LATIN_SMALL_LETTER_TURNED_A 0x0250 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_A L"\u0250" #define UNICODE_LATIN_SMALL_LETTER_ALPHA 0x0251 #define UNITEXT_LATIN_SMALL_LETTER_ALPHA L"\u0251" #define UNICODE_LATIN_SMALL_LETTER_TURNED_ALPHA 0x0252 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_ALPHA L"\u0252" #define UNICODE_LATIN_SMALL_LETTER_B_WITH_HOOK 0x0253 #define UNITEXT_LATIN_SMALL_LETTER_B_WITH_HOOK L"\u0253" #define UNICODE_LATIN_SMALL_LETTER_OPEN_O 0x0254 #define UNITEXT_LATIN_SMALL_LETTER_OPEN_O L"\u0254" #define UNICODE_LATIN_SMALL_LETTER_C_WITH_CURL 0x0255 #define UNITEXT_LATIN_SMALL_LETTER_C_WITH_CURL L"\u0255" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_TAIL 0x0256 #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_TAIL L"\u0256" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_HOOK 0x0257 #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_HOOK L"\u0257" #define UNICODE_LATIN_SMALL_LETTER_REVERSED_E 0x0258 #define UNITEXT_LATIN_SMALL_LETTER_REVERSED_E L"\u0258" #define UNICODE_LATIN_SMALL_LETTER_SCHWA 0x0259 #define UNITEXT_LATIN_SMALL_LETTER_SCHWA L"\u0259" #define UNICODE_LATIN_SMALL_LETTER_SCHWA_WITH_HOOK 0x025a #define UNITEXT_LATIN_SMALL_LETTER_SCHWA_WITH_HOOK L"\u025a" #define UNICODE_LATIN_SMALL_LETTER_OPEN_E 0x025b #define UNITEXT_LATIN_SMALL_LETTER_OPEN_E L"\u025b" #define UNICODE_LATIN_SMALL_LETTER_REVERSED_OPEN_E 0x025c #define UNITEXT_LATIN_SMALL_LETTER_REVERSED_OPEN_E L"\u025c" #define UNICODE_LATIN_SMALL_LETTER_REVERSED_OPEN_E_WITH_HOOK 0x025d #define UNITEXT_LATIN_SMALL_LETTER_REVERSED_OPEN_E_WITH_HOOK L"\u025d" #define UNICODE_LATIN_SMALL_LETTER_CLOSED_REVERSED_OPEN_E 0x025e #define UNITEXT_LATIN_SMALL_LETTER_CLOSED_REVERSED_OPEN_E L"\u025e" #define UNICODE_LATIN_SMALL_LETTER_DOTLESS_J_WITH_STROKE 0x025f #define UNITEXT_LATIN_SMALL_LETTER_DOTLESS_J_WITH_STROKE L"\u025f" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_HOOK 0x0260 #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_HOOK L"\u0260" #define UNICODE_LATIN_SMALL_LETTER_SCRIPT_G 0x0261 #define UNITEXT_LATIN_SMALL_LETTER_SCRIPT_G L"\u0261" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_G 0x0262 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_G L"\u0262" #define UNICODE_LATIN_SMALL_LETTER_GAMMA 0x0263 #define UNITEXT_LATIN_SMALL_LETTER_GAMMA L"\u0263" #define UNICODE_LATIN_SMALL_LETTER_RAMS_HORN 0x0264 #define UNITEXT_LATIN_SMALL_LETTER_RAMS_HORN L"\u0264" #define UNICODE_LATIN_SMALL_LETTER_TURNED_H 0x0265 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_H L"\u0265" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_HOOK 0x0266 #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_HOOK L"\u0266" #define UNICODE_LATIN_SMALL_LETTER_HENG_WITH_HOOK 0x0267 #define UNITEXT_LATIN_SMALL_LETTER_HENG_WITH_HOOK L"\u0267" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_STROKE 0x0268 #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_STROKE L"\u0268" #define UNICODE_LATIN_SMALL_LETTER_IOTA 0x0269 #define UNITEXT_LATIN_SMALL_LETTER_IOTA L"\u0269" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_I 0x026a #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_I L"\u026a" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_MIDDLE_TILDE 0x026b #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_MIDDLE_TILDE L"\u026b" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_BELT 0x026c #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_BELT L"\u026c" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_RETROFLEX_HOOK 0x026d #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_RETROFLEX_HOOK L"\u026d" #define UNICODE_LATIN_SMALL_LETTER_LEZH 0x026e #define UNITEXT_LATIN_SMALL_LETTER_LEZH L"\u026e" #define UNICODE_LATIN_SMALL_LETTER_TURNED_M 0x026f #define UNITEXT_LATIN_SMALL_LETTER_TURNED_M L"\u026f" #define UNICODE_LATIN_SMALL_LETTER_TURNED_M_WITH_LONG_LEG 0x0270 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_M_WITH_LONG_LEG L"\u0270" #define UNICODE_LATIN_SMALL_LETTER_M_WITH_HOOK 0x0271 #define UNITEXT_LATIN_SMALL_LETTER_M_WITH_HOOK L"\u0271" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_LEFT_HOOK 0x0272 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_LEFT_HOOK L"\u0272" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_RETROFLEX_HOOK 0x0273 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_RETROFLEX_HOOK L"\u0273" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_N 0x0274 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_N L"\u0274" #define UNICODE_LATIN_SMALL_LETTER_BARRED_O 0x0275 #define UNITEXT_LATIN_SMALL_LETTER_BARRED_O L"\u0275" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_OE 0x0276 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_OE L"\u0276" #define UNICODE_LATIN_SMALL_LETTER_CLOSED_OMEGA 0x0277 #define UNITEXT_LATIN_SMALL_LETTER_CLOSED_OMEGA L"\u0277" #define UNICODE_LATIN_SMALL_LETTER_PHI 0x0278 #define UNITEXT_LATIN_SMALL_LETTER_PHI L"\u0278" #define UNICODE_LATIN_SMALL_LETTER_TURNED_R 0x0279 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_R L"\u0279" #define UNICODE_LATIN_SMALL_LETTER_TURNED_R_WITH_LONG_LEG 0x027a #define UNITEXT_LATIN_SMALL_LETTER_TURNED_R_WITH_LONG_LEG L"\u027a" #define UNICODE_LATIN_SMALL_LETTER_TURNED_R_WITH_HOOK 0x027b #define UNITEXT_LATIN_SMALL_LETTER_TURNED_R_WITH_HOOK L"\u027b" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_LONG_LEG 0x027c #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_LONG_LEG L"\u027c" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_TAIL 0x027d #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_TAIL L"\u027d" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_FISHHOOK 0x027e #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_FISHHOOK L"\u027e" #define UNICODE_LATIN_SMALL_LETTER_REVERSED_R_WITH_FISHHOOK 0x027f #define UNITEXT_LATIN_SMALL_LETTER_REVERSED_R_WITH_FISHHOOK L"\u027f" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_R 0x0280 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_R L"\u0280" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_INVERTED_R 0x0281 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_INVERTED_R L"\u0281" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_HOOK 0x0282 #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_HOOK L"\u0282" #define UNICODE_LATIN_SMALL_LETTER_ESH 0x0283 #define UNITEXT_LATIN_SMALL_LETTER_ESH L"\u0283" #define UNICODE_LATIN_SMALL_LETTER_DOTLESS_J_WITH_STROKE_AND_HOOK 0x0284 #define UNITEXT_LATIN_SMALL_LETTER_DOTLESS_J_WITH_STROKE_AND_HOOK L"\u0284" #define UNICODE_LATIN_SMALL_LETTER_SQUAT_REVERSED_ESH 0x0285 #define UNITEXT_LATIN_SMALL_LETTER_SQUAT_REVERSED_ESH L"\u0285" #define UNICODE_LATIN_SMALL_LETTER_ESH_WITH_CURL 0x0286 #define UNITEXT_LATIN_SMALL_LETTER_ESH_WITH_CURL L"\u0286" #define UNICODE_LATIN_SMALL_LETTER_TURNED_T 0x0287 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_T L"\u0287" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_RETROFLEX_HOOK 0x0288 #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_RETROFLEX_HOOK L"\u0288" #define UNICODE_LATIN_SMALL_LETTER_U_BAR 0x0289 #define UNITEXT_LATIN_SMALL_LETTER_U_BAR L"\u0289" #define UNICODE_LATIN_SMALL_LETTER_UPSILON 0x028a #define UNITEXT_LATIN_SMALL_LETTER_UPSILON L"\u028a" #define UNICODE_LATIN_SMALL_LETTER_V_WITH_HOOK 0x028b #define UNITEXT_LATIN_SMALL_LETTER_V_WITH_HOOK L"\u028b" #define UNICODE_LATIN_SMALL_LETTER_TURNED_V 0x028c #define UNITEXT_LATIN_SMALL_LETTER_TURNED_V L"\u028c" #define UNICODE_LATIN_SMALL_LETTER_TURNED_W 0x028d #define UNITEXT_LATIN_SMALL_LETTER_TURNED_W L"\u028d" #define UNICODE_LATIN_SMALL_LETTER_TURNED_Y 0x028e #define UNITEXT_LATIN_SMALL_LETTER_TURNED_Y L"\u028e" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_Y 0x028f #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_Y L"\u028f" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_RETROFLEX_HOOK 0x0290 #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_RETROFLEX_HOOK L"\u0290" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_CURL 0x0291 #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_CURL L"\u0291" #define UNICODE_LATIN_SMALL_LETTER_EZH 0x0292 #define UNITEXT_LATIN_SMALL_LETTER_EZH L"\u0292" #define UNICODE_LATIN_SMALL_LETTER_EZH_WITH_CURL 0x0293 #define UNITEXT_LATIN_SMALL_LETTER_EZH_WITH_CURL L"\u0293" #define UNICODE_LATIN_LETTER_GLOTTAL_STOP 0x0294 #define UNITEXT_LATIN_LETTER_GLOTTAL_STOP L"\u0294" #define UNICODE_LATIN_LETTER_PHARYNGEAL_VOICED_FRICATIVE 0x0295 #define UNITEXT_LATIN_LETTER_PHARYNGEAL_VOICED_FRICATIVE L"\u0295" #define UNICODE_LATIN_LETTER_INVERTED_GLOTTAL_STOP 0x0296 #define UNITEXT_LATIN_LETTER_INVERTED_GLOTTAL_STOP L"\u0296" #define UNICODE_LATIN_LETTER_STRETCHED_C 0x0297 #define UNITEXT_LATIN_LETTER_STRETCHED_C L"\u0297" #define UNICODE_LATIN_LETTER_BILABIAL_CLICK 0x0298 #define UNITEXT_LATIN_LETTER_BILABIAL_CLICK L"\u0298" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_B 0x0299 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_B L"\u0299" #define UNICODE_LATIN_SMALL_LETTER_CLOSED_OPEN_E 0x029a #define UNITEXT_LATIN_SMALL_LETTER_CLOSED_OPEN_E L"\u029a" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_G_WITH_HOOK 0x029b #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_G_WITH_HOOK L"\u029b" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_H 0x029c #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_H L"\u029c" #define UNICODE_LATIN_SMALL_LETTER_J_WITH_CROSSED_TAIL 0x029d #define UNITEXT_LATIN_SMALL_LETTER_J_WITH_CROSSED_TAIL L"\u029d" #define UNICODE_LATIN_SMALL_LETTER_TURNED_K 0x029e #define UNITEXT_LATIN_SMALL_LETTER_TURNED_K L"\u029e" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_L 0x029f #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_L L"\u029f" #define UNICODE_LATIN_SMALL_LETTER_Q_WITH_HOOK 0x02a0 #define UNITEXT_LATIN_SMALL_LETTER_Q_WITH_HOOK L"\u02a0" #define UNICODE_LATIN_LETTER_GLOTTAL_STOP_WITH_STROKE 0x02a1 #define UNITEXT_LATIN_LETTER_GLOTTAL_STOP_WITH_STROKE L"\u02a1" #define UNICODE_LATIN_LETTER_REVERSED_GLOTTAL_STOP_WITH_STROKE 0x02a2 #define UNITEXT_LATIN_LETTER_REVERSED_GLOTTAL_STOP_WITH_STROKE L"\u02a2" #define UNICODE_LATIN_SMALL_LETTER_DZ_DIGRAPH 0x02a3 #define UNITEXT_LATIN_SMALL_LETTER_DZ_DIGRAPH L"\u02a3" #define UNICODE_LATIN_SMALL_LETTER_DEZH_DIGRAPH 0x02a4 #define UNITEXT_LATIN_SMALL_LETTER_DEZH_DIGRAPH L"\u02a4" #define UNICODE_LATIN_SMALL_LETTER_DZ_DIGRAPH_WITH_CURL 0x02a5 #define UNITEXT_LATIN_SMALL_LETTER_DZ_DIGRAPH_WITH_CURL L"\u02a5" #define UNICODE_LATIN_SMALL_LETTER_TS_DIGRAPH 0x02a6 #define UNITEXT_LATIN_SMALL_LETTER_TS_DIGRAPH L"\u02a6" #define UNICODE_LATIN_SMALL_LETTER_TESH_DIGRAPH 0x02a7 #define UNITEXT_LATIN_SMALL_LETTER_TESH_DIGRAPH L"\u02a7" #define UNICODE_LATIN_SMALL_LETTER_TC_DIGRAPH_WITH_CURL 0x02a8 #define UNITEXT_LATIN_SMALL_LETTER_TC_DIGRAPH_WITH_CURL L"\u02a8" #define UNICODE_LATIN_SMALL_LETTER_FENG_DIGRAPH 0x02a9 #define UNITEXT_LATIN_SMALL_LETTER_FENG_DIGRAPH L"\u02a9" #define UNICODE_LATIN_SMALL_LETTER_LS_DIGRAPH 0x02aa #define UNITEXT_LATIN_SMALL_LETTER_LS_DIGRAPH L"\u02aa" #define UNICODE_LATIN_SMALL_LETTER_LZ_DIGRAPH 0x02ab #define UNITEXT_LATIN_SMALL_LETTER_LZ_DIGRAPH L"\u02ab" #define UNICODE_LATIN_LETTER_BILABIAL_PERCUSSIVE 0x02ac #define UNITEXT_LATIN_LETTER_BILABIAL_PERCUSSIVE L"\u02ac" #define UNICODE_LATIN_LETTER_BIDENTAL_PERCUSSIVE 0x02ad #define UNITEXT_LATIN_LETTER_BIDENTAL_PERCUSSIVE L"\u02ad" #define UNICODE_LATIN_SMALL_LETTER_TURNED_H_WITH_FISHHOOK 0x02ae #define UNITEXT_LATIN_SMALL_LETTER_TURNED_H_WITH_FISHHOOK L"\u02ae" #define UNICODE_LATIN_SMALL_LETTER_TURNED_H_WITH_FISHHOOK_AND_TAIL 0x02af #define UNITEXT_LATIN_SMALL_LETTER_TURNED_H_WITH_FISHHOOK_AND_TAIL L"\u02af" #define UNICODE_MODIFIER_LETTER_SMALL_H 0x02b0 #define UNITEXT_MODIFIER_LETTER_SMALL_H L"\u02b0" #define UNICODE_MODIFIER_LETTER_SMALL_H_WITH_HOOK 0x02b1 #define UNITEXT_MODIFIER_LETTER_SMALL_H_WITH_HOOK L"\u02b1" #define UNICODE_MODIFIER_LETTER_SMALL_J 0x02b2 #define UNITEXT_MODIFIER_LETTER_SMALL_J L"\u02b2" #define UNICODE_MODIFIER_LETTER_SMALL_R 0x02b3 #define UNITEXT_MODIFIER_LETTER_SMALL_R L"\u02b3" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_R 0x02b4 #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_R L"\u02b4" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_R_WITH_HOOK 0x02b5 #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_R_WITH_HOOK L"\u02b5" #define UNICODE_MODIFIER_LETTER_SMALL_CAPITAL_INVERTED_R 0x02b6 #define UNITEXT_MODIFIER_LETTER_SMALL_CAPITAL_INVERTED_R L"\u02b6" #define UNICODE_MODIFIER_LETTER_SMALL_W 0x02b7 #define UNITEXT_MODIFIER_LETTER_SMALL_W L"\u02b7" #define UNICODE_MODIFIER_LETTER_SMALL_Y 0x02b8 #define UNITEXT_MODIFIER_LETTER_SMALL_Y L"\u02b8" #define UNICODE_MODIFIER_LETTER_PRIME 0x02b9 #define UNITEXT_MODIFIER_LETTER_PRIME L"\u02b9" #define UNICODE_MODIFIER_LETTER_DOUBLE_PRIME 0x02ba #define UNITEXT_MODIFIER_LETTER_DOUBLE_PRIME L"\u02ba" #define UNICODE_MODIFIER_LETTER_TURNED_COMMA 0x02bb #define UNITEXT_MODIFIER_LETTER_TURNED_COMMA L"\u02bb" #define UNICODE_MODIFIER_LETTER_APOSTROPHE 0x02bc #define UNITEXT_MODIFIER_LETTER_APOSTROPHE L"\u02bc" #define UNICODE_MODIFIER_LETTER_REVERSED_COMMA 0x02bd #define UNITEXT_MODIFIER_LETTER_REVERSED_COMMA L"\u02bd" #define UNICODE_MODIFIER_LETTER_RIGHT_HALF_RING 0x02be #define UNITEXT_MODIFIER_LETTER_RIGHT_HALF_RING L"\u02be" #define UNICODE_MODIFIER_LETTER_LEFT_HALF_RING 0x02bf #define UNITEXT_MODIFIER_LETTER_LEFT_HALF_RING L"\u02bf" #define UNICODE_MODIFIER_LETTER_GLOTTAL_STOP 0x02c0 #define UNITEXT_MODIFIER_LETTER_GLOTTAL_STOP L"\u02c0" #define UNICODE_MODIFIER_LETTER_REVERSED_GLOTTAL_STOP 0x02c1 #define UNITEXT_MODIFIER_LETTER_REVERSED_GLOTTAL_STOP L"\u02c1" #define UNICODE_MODIFIER_LETTER_LEFT_ARROWHEAD 0x02c2 #define UNITEXT_MODIFIER_LETTER_LEFT_ARROWHEAD L"\u02c2" #define UNICODE_MODIFIER_LETTER_RIGHT_ARROWHEAD 0x02c3 #define UNITEXT_MODIFIER_LETTER_RIGHT_ARROWHEAD L"\u02c3" #define UNICODE_MODIFIER_LETTER_UP_ARROWHEAD 0x02c4 #define UNITEXT_MODIFIER_LETTER_UP_ARROWHEAD L"\u02c4" #define UNICODE_MODIFIER_LETTER_DOWN_ARROWHEAD 0x02c5 #define UNITEXT_MODIFIER_LETTER_DOWN_ARROWHEAD L"\u02c5" #define UNICODE_MODIFIER_LETTER_CIRCUMFLEX_ACCENT 0x02c6 #define UNITEXT_MODIFIER_LETTER_CIRCUMFLEX_ACCENT L"\u02c6" #define UNICODE_CARON 0x02c7 #define UNITEXT_CARON L"\u02c7" #define UNICODE_MODIFIER_LETTER_VERTICAL_LINE 0x02c8 #define UNITEXT_MODIFIER_LETTER_VERTICAL_LINE L"\u02c8" #define UNICODE_MODIFIER_LETTER_MACRON 0x02c9 #define UNITEXT_MODIFIER_LETTER_MACRON L"\u02c9" #define UNICODE_MODIFIER_LETTER_ACUTE_ACCENT 0x02ca #define UNITEXT_MODIFIER_LETTER_ACUTE_ACCENT L"\u02ca" #define UNICODE_MODIFIER_LETTER_GRAVE_ACCENT 0x02cb #define UNITEXT_MODIFIER_LETTER_GRAVE_ACCENT L"\u02cb" #define UNICODE_MODIFIER_LETTER_LOW_VERTICAL_LINE 0x02cc #define UNITEXT_MODIFIER_LETTER_LOW_VERTICAL_LINE L"\u02cc" #define UNICODE_MODIFIER_LETTER_LOW_MACRON 0x02cd #define UNITEXT_MODIFIER_LETTER_LOW_MACRON L"\u02cd" #define UNICODE_MODIFIER_LETTER_LOW_GRAVE_ACCENT 0x02ce #define UNITEXT_MODIFIER_LETTER_LOW_GRAVE_ACCENT L"\u02ce" #define UNICODE_MODIFIER_LETTER_LOW_ACUTE_ACCENT 0x02cf #define UNITEXT_MODIFIER_LETTER_LOW_ACUTE_ACCENT L"\u02cf" #define UNICODE_MODIFIER_LETTER_TRIANGULAR_COLON 0x02d0 #define UNITEXT_MODIFIER_LETTER_TRIANGULAR_COLON L"\u02d0" #define UNICODE_MODIFIER_LETTER_HALF_TRIANGULAR_COLON 0x02d1 #define UNITEXT_MODIFIER_LETTER_HALF_TRIANGULAR_COLON L"\u02d1" #define UNICODE_MODIFIER_LETTER_CENTRED_RIGHT_HALF_RING 0x02d2 #define UNITEXT_MODIFIER_LETTER_CENTRED_RIGHT_HALF_RING L"\u02d2" #define UNICODE_MODIFIER_LETTER_CENTRED_LEFT_HALF_RING 0x02d3 #define UNITEXT_MODIFIER_LETTER_CENTRED_LEFT_HALF_RING L"\u02d3" #define UNICODE_MODIFIER_LETTER_UP_TACK 0x02d4 #define UNITEXT_MODIFIER_LETTER_UP_TACK L"\u02d4" #define UNICODE_MODIFIER_LETTER_DOWN_TACK 0x02d5 #define UNITEXT_MODIFIER_LETTER_DOWN_TACK L"\u02d5" #define UNICODE_MODIFIER_LETTER_PLUS_SIGN 0x02d6 #define UNITEXT_MODIFIER_LETTER_PLUS_SIGN L"\u02d6" #define UNICODE_MODIFIER_LETTER_MINUS_SIGN 0x02d7 #define UNITEXT_MODIFIER_LETTER_MINUS_SIGN L"\u02d7" #define UNICODE_BREVE 0x02d8 #define UNITEXT_BREVE L"\u02d8" #define UNICODE_DOT_ABOVE 0x02d9 #define UNITEXT_DOT_ABOVE L"\u02d9" #define UNICODE_RING_ABOVE 0x02da #define UNITEXT_RING_ABOVE L"\u02da" #define UNICODE_OGONEK 0x02db #define UNITEXT_OGONEK L"\u02db" #define UNICODE_SMALL_TILDE 0x02dc #define UNITEXT_SMALL_TILDE L"\u02dc" #define UNICODE_DOUBLE_ACUTE_ACCENT 0x02dd #define UNITEXT_DOUBLE_ACUTE_ACCENT L"\u02dd" #define UNICODE_MODIFIER_LETTER_RHOTIC_HOOK 0x02de #define UNITEXT_MODIFIER_LETTER_RHOTIC_HOOK L"\u02de" #define UNICODE_MODIFIER_LETTER_CROSS_ACCENT 0x02df #define UNITEXT_MODIFIER_LETTER_CROSS_ACCENT L"\u02df" #define UNICODE_MODIFIER_LETTER_SMALL_GAMMA 0x02e0 #define UNITEXT_MODIFIER_LETTER_SMALL_GAMMA L"\u02e0" #define UNICODE_MODIFIER_LETTER_SMALL_L 0x02e1 #define UNITEXT_MODIFIER_LETTER_SMALL_L L"\u02e1" #define UNICODE_MODIFIER_LETTER_SMALL_S 0x02e2 #define UNITEXT_MODIFIER_LETTER_SMALL_S L"\u02e2" #define UNICODE_MODIFIER_LETTER_SMALL_X 0x02e3 #define UNITEXT_MODIFIER_LETTER_SMALL_X L"\u02e3" #define UNICODE_MODIFIER_LETTER_SMALL_REVERSED_GLOTTAL_STOP 0x02e4 #define UNITEXT_MODIFIER_LETTER_SMALL_REVERSED_GLOTTAL_STOP L"\u02e4" #define UNICODE_MODIFIER_LETTER_EXTRA_HIGH_TONE_BAR 0x02e5 #define UNITEXT_MODIFIER_LETTER_EXTRA_HIGH_TONE_BAR L"\u02e5" #define UNICODE_MODIFIER_LETTER_HIGH_TONE_BAR 0x02e6 #define UNITEXT_MODIFIER_LETTER_HIGH_TONE_BAR L"\u02e6" #define UNICODE_MODIFIER_LETTER_MID_TONE_BAR 0x02e7 #define UNITEXT_MODIFIER_LETTER_MID_TONE_BAR L"\u02e7" #define UNICODE_MODIFIER_LETTER_LOW_TONE_BAR 0x02e8 #define UNITEXT_MODIFIER_LETTER_LOW_TONE_BAR L"\u02e8" #define UNICODE_MODIFIER_LETTER_EXTRA_LOW_TONE_BAR 0x02e9 #define UNITEXT_MODIFIER_LETTER_EXTRA_LOW_TONE_BAR L"\u02e9" #define UNICODE_MODIFIER_LETTER_YIN_DEPARTING_TONE_MARK 0x02ea #define UNITEXT_MODIFIER_LETTER_YIN_DEPARTING_TONE_MARK L"\u02ea" #define UNICODE_MODIFIER_LETTER_YANG_DEPARTING_TONE_MARK 0x02eb #define UNITEXT_MODIFIER_LETTER_YANG_DEPARTING_TONE_MARK L"\u02eb" #define UNICODE_MODIFIER_LETTER_VOICING 0x02ec #define UNITEXT_MODIFIER_LETTER_VOICING L"\u02ec" #define UNICODE_MODIFIER_LETTER_UNASPIRATED 0x02ed #define UNITEXT_MODIFIER_LETTER_UNASPIRATED L"\u02ed" #define UNICODE_MODIFIER_LETTER_DOUBLE_APOSTROPHE 0x02ee #define UNITEXT_MODIFIER_LETTER_DOUBLE_APOSTROPHE L"\u02ee" #define UNICODE_MODIFIER_LETTER_LOW_DOWN_ARROWHEAD 0x02ef #define UNITEXT_MODIFIER_LETTER_LOW_DOWN_ARROWHEAD L"\u02ef" #define UNICODE_MODIFIER_LETTER_LOW_UP_ARROWHEAD 0x02f0 #define UNITEXT_MODIFIER_LETTER_LOW_UP_ARROWHEAD L"\u02f0" #define UNICODE_MODIFIER_LETTER_LOW_LEFT_ARROWHEAD 0x02f1 #define UNITEXT_MODIFIER_LETTER_LOW_LEFT_ARROWHEAD L"\u02f1" #define UNICODE_MODIFIER_LETTER_LOW_RIGHT_ARROWHEAD 0x02f2 #define UNITEXT_MODIFIER_LETTER_LOW_RIGHT_ARROWHEAD L"\u02f2" #define UNICODE_MODIFIER_LETTER_LOW_RING 0x02f3 #define UNITEXT_MODIFIER_LETTER_LOW_RING L"\u02f3" #define UNICODE_MODIFIER_LETTER_MIDDLE_GRAVE_ACCENT 0x02f4 #define UNITEXT_MODIFIER_LETTER_MIDDLE_GRAVE_ACCENT L"\u02f4" #define UNICODE_MODIFIER_LETTER_MIDDLE_DOUBLE_GRAVE_ACCENT 0x02f5 #define UNITEXT_MODIFIER_LETTER_MIDDLE_DOUBLE_GRAVE_ACCENT L"\u02f5" #define UNICODE_MODIFIER_LETTER_MIDDLE_DOUBLE_ACUTE_ACCENT 0x02f6 #define UNITEXT_MODIFIER_LETTER_MIDDLE_DOUBLE_ACUTE_ACCENT L"\u02f6" #define UNICODE_MODIFIER_LETTER_LOW_TILDE 0x02f7 #define UNITEXT_MODIFIER_LETTER_LOW_TILDE L"\u02f7" #define UNICODE_MODIFIER_LETTER_RAISED_COLON 0x02f8 #define UNITEXT_MODIFIER_LETTER_RAISED_COLON L"\u02f8" #define UNICODE_MODIFIER_LETTER_BEGIN_HIGH_TONE 0x02f9 #define UNITEXT_MODIFIER_LETTER_BEGIN_HIGH_TONE L"\u02f9" #define UNICODE_MODIFIER_LETTER_END_HIGH_TONE 0x02fa #define UNITEXT_MODIFIER_LETTER_END_HIGH_TONE L"\u02fa" #define UNICODE_MODIFIER_LETTER_BEGIN_LOW_TONE 0x02fb #define UNITEXT_MODIFIER_LETTER_BEGIN_LOW_TONE L"\u02fb" #define UNICODE_MODIFIER_LETTER_END_LOW_TONE 0x02fc #define UNITEXT_MODIFIER_LETTER_END_LOW_TONE L"\u02fc" #define UNICODE_MODIFIER_LETTER_SHELF 0x02fd #define UNITEXT_MODIFIER_LETTER_SHELF L"\u02fd" #define UNICODE_MODIFIER_LETTER_OPEN_SHELF 0x02fe #define UNITEXT_MODIFIER_LETTER_OPEN_SHELF L"\u02fe" #define UNICODE_MODIFIER_LETTER_LOW_LEFT_ARROW 0x02ff #define UNITEXT_MODIFIER_LETTER_LOW_LEFT_ARROW L"\u02ff" #define UNICODE_COMBINING_GRAVE_ACCENT 0x0300 #define UNITEXT_COMBINING_GRAVE_ACCENT L"\u0300" #define UNICODE_COMBINING_ACUTE_ACCENT 0x0301 #define UNITEXT_COMBINING_ACUTE_ACCENT L"\u0301" #define UNICODE_COMBINING_CIRCUMFLEX_ACCENT 0x0302 #define UNITEXT_COMBINING_CIRCUMFLEX_ACCENT L"\u0302" #define UNICODE_COMBINING_TILDE 0x0303 #define UNITEXT_COMBINING_TILDE L"\u0303" #define UNICODE_COMBINING_MACRON 0x0304 #define UNITEXT_COMBINING_MACRON L"\u0304" #define UNICODE_COMBINING_OVERLINE 0x0305 #define UNITEXT_COMBINING_OVERLINE L"\u0305" #define UNICODE_COMBINING_BREVE 0x0306 #define UNITEXT_COMBINING_BREVE L"\u0306" #define UNICODE_COMBINING_DOT_ABOVE 0x0307 #define UNITEXT_COMBINING_DOT_ABOVE L"\u0307" #define UNICODE_COMBINING_DIAERESIS 0x0308 #define UNITEXT_COMBINING_DIAERESIS L"\u0308" #define UNICODE_COMBINING_HOOK_ABOVE 0x0309 #define UNITEXT_COMBINING_HOOK_ABOVE L"\u0309" #define UNICODE_COMBINING_RING_ABOVE 0x030a #define UNITEXT_COMBINING_RING_ABOVE L"\u030a" #define UNICODE_COMBINING_DOUBLE_ACUTE_ACCENT 0x030b #define UNITEXT_COMBINING_DOUBLE_ACUTE_ACCENT L"\u030b" #define UNICODE_COMBINING_CARON 0x030c #define UNITEXT_COMBINING_CARON L"\u030c" #define UNICODE_COMBINING_VERTICAL_LINE_ABOVE 0x030d #define UNITEXT_COMBINING_VERTICAL_LINE_ABOVE L"\u030d" #define UNICODE_COMBINING_DOUBLE_VERTICAL_LINE_ABOVE 0x030e #define UNITEXT_COMBINING_DOUBLE_VERTICAL_LINE_ABOVE L"\u030e" #define UNICODE_COMBINING_DOUBLE_GRAVE_ACCENT 0x030f #define UNITEXT_COMBINING_DOUBLE_GRAVE_ACCENT L"\u030f" #define UNICODE_COMBINING_CANDRABINDU 0x0310 #define UNITEXT_COMBINING_CANDRABINDU L"\u0310" #define UNICODE_COMBINING_INVERTED_BREVE 0x0311 #define UNITEXT_COMBINING_INVERTED_BREVE L"\u0311" #define UNICODE_COMBINING_TURNED_COMMA_ABOVE 0x0312 #define UNITEXT_COMBINING_TURNED_COMMA_ABOVE L"\u0312" #define UNICODE_COMBINING_COMMA_ABOVE 0x0313 #define UNITEXT_COMBINING_COMMA_ABOVE L"\u0313" #define UNICODE_COMBINING_REVERSED_COMMA_ABOVE 0x0314 #define UNITEXT_COMBINING_REVERSED_COMMA_ABOVE L"\u0314" #define UNICODE_COMBINING_COMMA_ABOVE_RIGHT 0x0315 #define UNITEXT_COMBINING_COMMA_ABOVE_RIGHT L"\u0315" #define UNICODE_COMBINING_GRAVE_ACCENT_BELOW 0x0316 #define UNITEXT_COMBINING_GRAVE_ACCENT_BELOW L"\u0316" #define UNICODE_COMBINING_ACUTE_ACCENT_BELOW 0x0317 #define UNITEXT_COMBINING_ACUTE_ACCENT_BELOW L"\u0317" #define UNICODE_COMBINING_LEFT_TACK_BELOW 0x0318 #define UNITEXT_COMBINING_LEFT_TACK_BELOW L"\u0318" #define UNICODE_COMBINING_RIGHT_TACK_BELOW 0x0319 #define UNITEXT_COMBINING_RIGHT_TACK_BELOW L"\u0319" #define UNICODE_COMBINING_LEFT_ANGLE_ABOVE 0x031a #define UNITEXT_COMBINING_LEFT_ANGLE_ABOVE L"\u031a" #define UNICODE_COMBINING_HORN 0x031b #define UNITEXT_COMBINING_HORN L"\u031b" #define UNICODE_COMBINING_LEFT_HALF_RING_BELOW 0x031c #define UNITEXT_COMBINING_LEFT_HALF_RING_BELOW L"\u031c" #define UNICODE_COMBINING_UP_TACK_BELOW 0x031d #define UNITEXT_COMBINING_UP_TACK_BELOW L"\u031d" #define UNICODE_COMBINING_DOWN_TACK_BELOW 0x031e #define UNITEXT_COMBINING_DOWN_TACK_BELOW L"\u031e" #define UNICODE_COMBINING_PLUS_SIGN_BELOW 0x031f #define UNITEXT_COMBINING_PLUS_SIGN_BELOW L"\u031f" #define UNICODE_COMBINING_MINUS_SIGN_BELOW 0x0320 #define UNITEXT_COMBINING_MINUS_SIGN_BELOW L"\u0320" #define UNICODE_COMBINING_PALATALIZED_HOOK_BELOW 0x0321 #define UNITEXT_COMBINING_PALATALIZED_HOOK_BELOW L"\u0321" #define UNICODE_COMBINING_RETROFLEX_HOOK_BELOW 0x0322 #define UNITEXT_COMBINING_RETROFLEX_HOOK_BELOW L"\u0322" #define UNICODE_COMBINING_DOT_BELOW 0x0323 #define UNITEXT_COMBINING_DOT_BELOW L"\u0323" #define UNICODE_COMBINING_DIAERESIS_BELOW 0x0324 #define UNITEXT_COMBINING_DIAERESIS_BELOW L"\u0324" #define UNICODE_COMBINING_RING_BELOW 0x0325 #define UNITEXT_COMBINING_RING_BELOW L"\u0325" #define UNICODE_COMBINING_COMMA_BELOW 0x0326 #define UNITEXT_COMBINING_COMMA_BELOW L"\u0326" #define UNICODE_COMBINING_CEDILLA 0x0327 #define UNITEXT_COMBINING_CEDILLA L"\u0327" #define UNICODE_COMBINING_OGONEK 0x0328 #define UNITEXT_COMBINING_OGONEK L"\u0328" #define UNICODE_COMBINING_VERTICAL_LINE_BELOW 0x0329 #define UNITEXT_COMBINING_VERTICAL_LINE_BELOW L"\u0329" #define UNICODE_COMBINING_BRIDGE_BELOW 0x032a #define UNITEXT_COMBINING_BRIDGE_BELOW L"\u032a" #define UNICODE_COMBINING_INVERTED_DOUBLE_ARCH_BELOW 0x032b #define UNITEXT_COMBINING_INVERTED_DOUBLE_ARCH_BELOW L"\u032b" #define UNICODE_COMBINING_CARON_BELOW 0x032c #define UNITEXT_COMBINING_CARON_BELOW L"\u032c" #define UNICODE_COMBINING_CIRCUMFLEX_ACCENT_BELOW 0x032d #define UNITEXT_COMBINING_CIRCUMFLEX_ACCENT_BELOW L"\u032d" #define UNICODE_COMBINING_BREVE_BELOW 0x032e #define UNITEXT_COMBINING_BREVE_BELOW L"\u032e" #define UNICODE_COMBINING_INVERTED_BREVE_BELOW 0x032f #define UNITEXT_COMBINING_INVERTED_BREVE_BELOW L"\u032f" #define UNICODE_COMBINING_TILDE_BELOW 0x0330 #define UNITEXT_COMBINING_TILDE_BELOW L"\u0330" #define UNICODE_COMBINING_MACRON_BELOW 0x0331 #define UNITEXT_COMBINING_MACRON_BELOW L"\u0331" #define UNICODE_COMBINING_LOW_LINE 0x0332 #define UNITEXT_COMBINING_LOW_LINE L"\u0332" #define UNICODE_COMBINING_DOUBLE_LOW_LINE 0x0333 #define UNITEXT_COMBINING_DOUBLE_LOW_LINE L"\u0333" #define UNICODE_COMBINING_TILDE_OVERLAY 0x0334 #define UNITEXT_COMBINING_TILDE_OVERLAY L"\u0334" #define UNICODE_COMBINING_SHORT_STROKE_OVERLAY 0x0335 #define UNITEXT_COMBINING_SHORT_STROKE_OVERLAY L"\u0335" #define UNICODE_COMBINING_LONG_STROKE_OVERLAY 0x0336 #define UNITEXT_COMBINING_LONG_STROKE_OVERLAY L"\u0336" #define UNICODE_COMBINING_SHORT_SOLIDUS_OVERLAY 0x0337 #define UNITEXT_COMBINING_SHORT_SOLIDUS_OVERLAY L"\u0337" #define UNICODE_COMBINING_LONG_SOLIDUS_OVERLAY 0x0338 #define UNITEXT_COMBINING_LONG_SOLIDUS_OVERLAY L"\u0338" #define UNICODE_COMBINING_RIGHT_HALF_RING_BELOW 0x0339 #define UNITEXT_COMBINING_RIGHT_HALF_RING_BELOW L"\u0339" #define UNICODE_COMBINING_INVERTED_BRIDGE_BELOW 0x033a #define UNITEXT_COMBINING_INVERTED_BRIDGE_BELOW L"\u033a" #define UNICODE_COMBINING_SQUARE_BELOW 0x033b #define UNITEXT_COMBINING_SQUARE_BELOW L"\u033b" #define UNICODE_COMBINING_SEAGULL_BELOW 0x033c #define UNITEXT_COMBINING_SEAGULL_BELOW L"\u033c" #define UNICODE_COMBINING_X_ABOVE 0x033d #define UNITEXT_COMBINING_X_ABOVE L"\u033d" #define UNICODE_COMBINING_VERTICAL_TILDE 0x033e #define UNITEXT_COMBINING_VERTICAL_TILDE L"\u033e" #define UNICODE_COMBINING_DOUBLE_OVERLINE 0x033f #define UNITEXT_COMBINING_DOUBLE_OVERLINE L"\u033f" #define UNICODE_COMBINING_GRAVE_TONE_MARK 0x0340 #define UNITEXT_COMBINING_GRAVE_TONE_MARK L"\u0340" #define UNICODE_COMBINING_ACUTE_TONE_MARK 0x0341 #define UNITEXT_COMBINING_ACUTE_TONE_MARK L"\u0341" #define UNICODE_COMBINING_GREEK_PERISPOMENI 0x0342 #define UNITEXT_COMBINING_GREEK_PERISPOMENI L"\u0342" #define UNICODE_COMBINING_GREEK_KORONIS 0x0343 #define UNITEXT_COMBINING_GREEK_KORONIS L"\u0343" #define UNICODE_COMBINING_GREEK_DIALYTIKA_TONOS 0x0344 #define UNITEXT_COMBINING_GREEK_DIALYTIKA_TONOS L"\u0344" #define UNICODE_COMBINING_GREEK_YPOGEGRAMMENI 0x0345 #define UNITEXT_COMBINING_GREEK_YPOGEGRAMMENI L"\u0345" #define UNICODE_COMBINING_BRIDGE_ABOVE 0x0346 #define UNITEXT_COMBINING_BRIDGE_ABOVE L"\u0346" #define UNICODE_COMBINING_EQUALS_SIGN_BELOW 0x0347 #define UNITEXT_COMBINING_EQUALS_SIGN_BELOW L"\u0347" #define UNICODE_COMBINING_DOUBLE_VERTICAL_LINE_BELOW 0x0348 #define UNITEXT_COMBINING_DOUBLE_VERTICAL_LINE_BELOW L"\u0348" #define UNICODE_COMBINING_LEFT_ANGLE_BELOW 0x0349 #define UNITEXT_COMBINING_LEFT_ANGLE_BELOW L"\u0349" #define UNICODE_COMBINING_NOT_TILDE_ABOVE 0x034a #define UNITEXT_COMBINING_NOT_TILDE_ABOVE L"\u034a" #define UNICODE_COMBINING_HOMOTHETIC_ABOVE 0x034b #define UNITEXT_COMBINING_HOMOTHETIC_ABOVE L"\u034b" #define UNICODE_COMBINING_ALMOST_EQUAL_TO_ABOVE 0x034c #define UNITEXT_COMBINING_ALMOST_EQUAL_TO_ABOVE L"\u034c" #define UNICODE_COMBINING_LEFT_RIGHT_ARROW_BELOW 0x034d #define UNITEXT_COMBINING_LEFT_RIGHT_ARROW_BELOW L"\u034d" #define UNICODE_COMBINING_UPWARDS_ARROW_BELOW 0x034e #define UNITEXT_COMBINING_UPWARDS_ARROW_BELOW L"\u034e" #define UNICODE_COMBINING_GRAPHEME_JOINER 0x034f #define UNITEXT_COMBINING_GRAPHEME_JOINER L"\u034f" #define UNICODE_COMBINING_RIGHT_ARROWHEAD_ABOVE 0x0350 #define UNITEXT_COMBINING_RIGHT_ARROWHEAD_ABOVE L"\u0350" #define UNICODE_COMBINING_LEFT_HALF_RING_ABOVE 0x0351 #define UNITEXT_COMBINING_LEFT_HALF_RING_ABOVE L"\u0351" #define UNICODE_COMBINING_FERMATA 0x0352 #define UNITEXT_COMBINING_FERMATA L"\u0352" #define UNICODE_COMBINING_X_BELOW 0x0353 #define UNITEXT_COMBINING_X_BELOW L"\u0353" #define UNICODE_COMBINING_LEFT_ARROWHEAD_BELOW 0x0354 #define UNITEXT_COMBINING_LEFT_ARROWHEAD_BELOW L"\u0354" #define UNICODE_COMBINING_RIGHT_ARROWHEAD_BELOW 0x0355 #define UNITEXT_COMBINING_RIGHT_ARROWHEAD_BELOW L"\u0355" #define UNICODE_COMBINING_RIGHT_ARROWHEAD_AND_UP_ARROWHEAD_BELOW 0x0356 #define UNITEXT_COMBINING_RIGHT_ARROWHEAD_AND_UP_ARROWHEAD_BELOW L"\u0356" #define UNICODE_COMBINING_RIGHT_HALF_RING_ABOVE 0x0357 #define UNITEXT_COMBINING_RIGHT_HALF_RING_ABOVE L"\u0357" #define UNICODE_COMBINING_DOT_ABOVE_RIGHT 0x0358 #define UNITEXT_COMBINING_DOT_ABOVE_RIGHT L"\u0358" #define UNICODE_COMBINING_ASTERISK_BELOW 0x0359 #define UNITEXT_COMBINING_ASTERISK_BELOW L"\u0359" #define UNICODE_COMBINING_DOUBLE_RING_BELOW 0x035a #define UNITEXT_COMBINING_DOUBLE_RING_BELOW L"\u035a" #define UNICODE_COMBINING_ZIGZAG_ABOVE 0x035b #define UNITEXT_COMBINING_ZIGZAG_ABOVE L"\u035b" #define UNICODE_COMBINING_DOUBLE_BREVE_BELOW 0x035c #define UNITEXT_COMBINING_DOUBLE_BREVE_BELOW L"\u035c" #define UNICODE_COMBINING_DOUBLE_BREVE 0x035d #define UNITEXT_COMBINING_DOUBLE_BREVE L"\u035d" #define UNICODE_COMBINING_DOUBLE_MACRON 0x035e #define UNITEXT_COMBINING_DOUBLE_MACRON L"\u035e" #define UNICODE_COMBINING_DOUBLE_MACRON_BELOW 0x035f #define UNITEXT_COMBINING_DOUBLE_MACRON_BELOW L"\u035f" #define UNICODE_COMBINING_DOUBLE_TILDE 0x0360 #define UNITEXT_COMBINING_DOUBLE_TILDE L"\u0360" #define UNICODE_COMBINING_DOUBLE_INVERTED_BREVE 0x0361 #define UNITEXT_COMBINING_DOUBLE_INVERTED_BREVE L"\u0361" #define UNICODE_COMBINING_DOUBLE_RIGHTWARDS_ARROW_BELOW 0x0362 #define UNITEXT_COMBINING_DOUBLE_RIGHTWARDS_ARROW_BELOW L"\u0362" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_A 0x0363 #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_A L"\u0363" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_E 0x0364 #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_E L"\u0364" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_I 0x0365 #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_I L"\u0365" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_O 0x0366 #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_O L"\u0366" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_U 0x0367 #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_U L"\u0367" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_C 0x0368 #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_C L"\u0368" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_D 0x0369 #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_D L"\u0369" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_H 0x036a #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_H L"\u036a" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_M 0x036b #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_M L"\u036b" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_R 0x036c #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_R L"\u036c" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_T 0x036d #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_T L"\u036d" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_V 0x036e #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_V L"\u036e" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_X 0x036f #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_X L"\u036f" #define UNICODE_GREEK_NUMERAL_SIGN 0x0374 #define UNITEXT_GREEK_NUMERAL_SIGN L"\u0374" #define UNICODE_GREEK_LOWER_NUMERAL_SIGN 0x0375 #define UNITEXT_GREEK_LOWER_NUMERAL_SIGN L"\u0375" #define UNICODE_GREEK_YPOGEGRAMMENI 0x037a #define UNITEXT_GREEK_YPOGEGRAMMENI L"\u037a" #define UNICODE_GREEK_SMALL_REVERSED_LUNATE_SIGMA_SYMBOL 0x037b #define UNITEXT_GREEK_SMALL_REVERSED_LUNATE_SIGMA_SYMBOL L"\u037b" #define UNICODE_GREEK_SMALL_DOTTED_LUNATE_SIGMA_SYMBOL 0x037c #define UNITEXT_GREEK_SMALL_DOTTED_LUNATE_SIGMA_SYMBOL L"\u037c" #define UNICODE_GREEK_SMALL_REVERSED_DOTTED_LUNATE_SIGMA_SYMBOL 0x037d #define UNITEXT_GREEK_SMALL_REVERSED_DOTTED_LUNATE_SIGMA_SYMBOL L"\u037d" #define UNICODE_GREEK_QUESTION_MARK 0x037e #define UNITEXT_GREEK_QUESTION_MARK L"\u037e" #define UNICODE_GREEK_TONOS 0x0384 #define UNITEXT_GREEK_TONOS L"\u0384" #define UNICODE_GREEK_DIALYTIKA_TONOS 0x0385 #define UNITEXT_GREEK_DIALYTIKA_TONOS L"\u0385" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_TONOS 0x0386 #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_TONOS L"\u0386" #define UNICODE_GREEK_ANO_TELEIA 0x0387 #define UNITEXT_GREEK_ANO_TELEIA L"\u0387" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON_WITH_TONOS 0x0388 #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON_WITH_TONOS L"\u0388" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_TONOS 0x0389 #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_TONOS L"\u0389" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_TONOS 0x038a #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_TONOS L"\u038a" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON_WITH_TONOS 0x038c #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON_WITH_TONOS L"\u038c" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_TONOS 0x038e #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_TONOS L"\u038e" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_TONOS 0x038f #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_TONOS L"\u038f" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA_AND_TONOS 0x0390 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA_AND_TONOS L"\u0390" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA 0x0391 #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA L"\u0391" #define UNICODE_GREEK_CAPITAL_LETTER_BETA 0x0392 #define UNITEXT_GREEK_CAPITAL_LETTER_BETA L"\u0392" #define UNICODE_GREEK_CAPITAL_LETTER_GAMMA 0x0393 #define UNITEXT_GREEK_CAPITAL_LETTER_GAMMA L"\u0393" #define UNICODE_GREEK_CAPITAL_LETTER_DELTA 0x0394 #define UNITEXT_GREEK_CAPITAL_LETTER_DELTA L"\u0394" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON 0x0395 #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON L"\u0395" #define UNICODE_GREEK_CAPITAL_LETTER_ZETA 0x0396 #define UNITEXT_GREEK_CAPITAL_LETTER_ZETA L"\u0396" #define UNICODE_GREEK_CAPITAL_LETTER_ETA 0x0397 #define UNITEXT_GREEK_CAPITAL_LETTER_ETA L"\u0397" #define UNICODE_GREEK_CAPITAL_LETTER_THETA 0x0398 #define UNITEXT_GREEK_CAPITAL_LETTER_THETA L"\u0398" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA 0x0399 #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA L"\u0399" #define UNICODE_GREEK_CAPITAL_LETTER_KAPPA 0x039a #define UNITEXT_GREEK_CAPITAL_LETTER_KAPPA L"\u039a" #define UNICODE_GREEK_CAPITAL_LETTER_LAMDA 0x039b #define UNITEXT_GREEK_CAPITAL_LETTER_LAMDA L"\u039b" #define UNICODE_GREEK_CAPITAL_LETTER_MU 0x039c #define UNITEXT_GREEK_CAPITAL_LETTER_MU L"\u039c" #define UNICODE_GREEK_CAPITAL_LETTER_NU 0x039d #define UNITEXT_GREEK_CAPITAL_LETTER_NU L"\u039d" #define UNICODE_GREEK_CAPITAL_LETTER_XI 0x039e #define UNITEXT_GREEK_CAPITAL_LETTER_XI L"\u039e" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON 0x039f #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON L"\u039f" #define UNICODE_GREEK_CAPITAL_LETTER_PI 0x03a0 #define UNITEXT_GREEK_CAPITAL_LETTER_PI L"\u03a0" #define UNICODE_GREEK_CAPITAL_LETTER_RHO 0x03a1 #define UNITEXT_GREEK_CAPITAL_LETTER_RHO L"\u03a1" #define UNICODE_GREEK_CAPITAL_LETTER_SIGMA 0x03a3 #define UNITEXT_GREEK_CAPITAL_LETTER_SIGMA L"\u03a3" #define UNICODE_GREEK_CAPITAL_LETTER_TAU 0x03a4 #define UNITEXT_GREEK_CAPITAL_LETTER_TAU L"\u03a4" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON 0x03a5 #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON L"\u03a5" #define UNICODE_GREEK_CAPITAL_LETTER_PHI 0x03a6 #define UNITEXT_GREEK_CAPITAL_LETTER_PHI L"\u03a6" #define UNICODE_GREEK_CAPITAL_LETTER_CHI 0x03a7 #define UNITEXT_GREEK_CAPITAL_LETTER_CHI L"\u03a7" #define UNICODE_GREEK_CAPITAL_LETTER_PSI 0x03a8 #define UNITEXT_GREEK_CAPITAL_LETTER_PSI L"\u03a8" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA 0x03a9 #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA L"\u03a9" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_DIALYTIKA 0x03aa #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_DIALYTIKA L"\u03aa" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_DIALYTIKA 0x03ab #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_DIALYTIKA L"\u03ab" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_TONOS 0x03ac #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_TONOS L"\u03ac" #define UNICODE_GREEK_SMALL_LETTER_EPSILON_WITH_TONOS 0x03ad #define UNITEXT_GREEK_SMALL_LETTER_EPSILON_WITH_TONOS L"\u03ad" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_TONOS 0x03ae #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_TONOS L"\u03ae" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_TONOS 0x03af #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_TONOS L"\u03af" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA_AND_TONOS 0x03b0 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA_AND_TONOS L"\u03b0" #define UNICODE_GREEK_SMALL_LETTER_ALPHA 0x03b1 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA L"\u03b1" #define UNICODE_GREEK_SMALL_LETTER_BETA 0x03b2 #define UNITEXT_GREEK_SMALL_LETTER_BETA L"\u03b2" #define UNICODE_GREEK_SMALL_LETTER_GAMMA 0x03b3 #define UNITEXT_GREEK_SMALL_LETTER_GAMMA L"\u03b3" #define UNICODE_GREEK_SMALL_LETTER_DELTA 0x03b4 #define UNITEXT_GREEK_SMALL_LETTER_DELTA L"\u03b4" #define UNICODE_GREEK_SMALL_LETTER_EPSILON 0x03b5 #define UNITEXT_GREEK_SMALL_LETTER_EPSILON L"\u03b5" #define UNICODE_GREEK_SMALL_LETTER_ZETA 0x03b6 #define UNITEXT_GREEK_SMALL_LETTER_ZETA L"\u03b6" #define UNICODE_GREEK_SMALL_LETTER_ETA 0x03b7 #define UNITEXT_GREEK_SMALL_LETTER_ETA L"\u03b7" #define UNICODE_GREEK_SMALL_LETTER_THETA 0x03b8 #define UNITEXT_GREEK_SMALL_LETTER_THETA L"\u03b8" #define UNICODE_GREEK_SMALL_LETTER_IOTA 0x03b9 #define UNITEXT_GREEK_SMALL_LETTER_IOTA L"\u03b9" #define UNICODE_GREEK_SMALL_LETTER_KAPPA 0x03ba #define UNITEXT_GREEK_SMALL_LETTER_KAPPA L"\u03ba" #define UNICODE_GREEK_SMALL_LETTER_LAMDA 0x03bb #define UNITEXT_GREEK_SMALL_LETTER_LAMDA L"\u03bb" #define UNICODE_GREEK_SMALL_LETTER_MU 0x03bc #define UNITEXT_GREEK_SMALL_LETTER_MU L"\u03bc" #define UNICODE_GREEK_SMALL_LETTER_NU 0x03bd #define UNITEXT_GREEK_SMALL_LETTER_NU L"\u03bd" #define UNICODE_GREEK_SMALL_LETTER_XI 0x03be #define UNITEXT_GREEK_SMALL_LETTER_XI L"\u03be" #define UNICODE_GREEK_SMALL_LETTER_OMICRON 0x03bf #define UNITEXT_GREEK_SMALL_LETTER_OMICRON L"\u03bf" #define UNICODE_GREEK_SMALL_LETTER_PI 0x03c0 #define UNITEXT_GREEK_SMALL_LETTER_PI L"\u03c0" #define UNICODE_GREEK_SMALL_LETTER_RHO 0x03c1 #define UNITEXT_GREEK_SMALL_LETTER_RHO L"\u03c1" #define UNICODE_GREEK_SMALL_LETTER_FINAL_SIGMA 0x03c2 #define UNITEXT_GREEK_SMALL_LETTER_FINAL_SIGMA L"\u03c2" #define UNICODE_GREEK_SMALL_LETTER_SIGMA 0x03c3 #define UNITEXT_GREEK_SMALL_LETTER_SIGMA L"\u03c3" #define UNICODE_GREEK_SMALL_LETTER_TAU 0x03c4 #define UNITEXT_GREEK_SMALL_LETTER_TAU L"\u03c4" #define UNICODE_GREEK_SMALL_LETTER_UPSILON 0x03c5 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON L"\u03c5" #define UNICODE_GREEK_SMALL_LETTER_PHI 0x03c6 #define UNITEXT_GREEK_SMALL_LETTER_PHI L"\u03c6" #define UNICODE_GREEK_SMALL_LETTER_CHI 0x03c7 #define UNITEXT_GREEK_SMALL_LETTER_CHI L"\u03c7" #define UNICODE_GREEK_SMALL_LETTER_PSI 0x03c8 #define UNITEXT_GREEK_SMALL_LETTER_PSI L"\u03c8" #define UNICODE_GREEK_SMALL_LETTER_OMEGA 0x03c9 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA L"\u03c9" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA 0x03ca #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA L"\u03ca" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA 0x03cb #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA L"\u03cb" #define UNICODE_GREEK_SMALL_LETTER_OMICRON_WITH_TONOS 0x03cc #define UNITEXT_GREEK_SMALL_LETTER_OMICRON_WITH_TONOS L"\u03cc" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_TONOS 0x03cd #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_TONOS L"\u03cd" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_TONOS 0x03ce #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_TONOS L"\u03ce" #define UNICODE_GREEK_BETA_SYMBOL 0x03d0 #define UNITEXT_GREEK_BETA_SYMBOL L"\u03d0" #define UNICODE_GREEK_THETA_SYMBOL 0x03d1 #define UNITEXT_GREEK_THETA_SYMBOL L"\u03d1" #define UNICODE_GREEK_UPSILON_WITH_HOOK_SYMBOL 0x03d2 #define UNITEXT_GREEK_UPSILON_WITH_HOOK_SYMBOL L"\u03d2" #define UNICODE_GREEK_UPSILON_WITH_ACUTE_AND_HOOK_SYMBOL 0x03d3 #define UNITEXT_GREEK_UPSILON_WITH_ACUTE_AND_HOOK_SYMBOL L"\u03d3" #define UNICODE_GREEK_UPSILON_WITH_DIAERESIS_AND_HOOK_SYMBOL 0x03d4 #define UNITEXT_GREEK_UPSILON_WITH_DIAERESIS_AND_HOOK_SYMBOL L"\u03d4" #define UNICODE_GREEK_PHI_SYMBOL 0x03d5 #define UNITEXT_GREEK_PHI_SYMBOL L"\u03d5" #define UNICODE_GREEK_PI_SYMBOL 0x03d6 #define UNITEXT_GREEK_PI_SYMBOL L"\u03d6" #define UNICODE_GREEK_KAI_SYMBOL 0x03d7 #define UNITEXT_GREEK_KAI_SYMBOL L"\u03d7" #define UNICODE_GREEK_LETTER_ARCHAIC_KOPPA 0x03d8 #define UNITEXT_GREEK_LETTER_ARCHAIC_KOPPA L"\u03d8" #define UNICODE_GREEK_SMALL_LETTER_ARCHAIC_KOPPA 0x03d9 #define UNITEXT_GREEK_SMALL_LETTER_ARCHAIC_KOPPA L"\u03d9" #define UNICODE_GREEK_LETTER_STIGMA 0x03da #define UNITEXT_GREEK_LETTER_STIGMA L"\u03da" #define UNICODE_GREEK_SMALL_LETTER_STIGMA 0x03db #define UNITEXT_GREEK_SMALL_LETTER_STIGMA L"\u03db" #define UNICODE_GREEK_LETTER_DIGAMMA 0x03dc #define UNITEXT_GREEK_LETTER_DIGAMMA L"\u03dc" #define UNICODE_GREEK_SMALL_LETTER_DIGAMMA 0x03dd #define UNITEXT_GREEK_SMALL_LETTER_DIGAMMA L"\u03dd" #define UNICODE_GREEK_LETTER_KOPPA 0x03de #define UNITEXT_GREEK_LETTER_KOPPA L"\u03de" #define UNICODE_GREEK_SMALL_LETTER_KOPPA 0x03df #define UNITEXT_GREEK_SMALL_LETTER_KOPPA L"\u03df" #define UNICODE_GREEK_LETTER_SAMPI 0x03e0 #define UNITEXT_GREEK_LETTER_SAMPI L"\u03e0" #define UNICODE_GREEK_SMALL_LETTER_SAMPI 0x03e1 #define UNITEXT_GREEK_SMALL_LETTER_SAMPI L"\u03e1" #define UNICODE_COPTIC_CAPITAL_LETTER_SHEI 0x03e2 #define UNITEXT_COPTIC_CAPITAL_LETTER_SHEI L"\u03e2" #define UNICODE_COPTIC_SMALL_LETTER_SHEI 0x03e3 #define UNITEXT_COPTIC_SMALL_LETTER_SHEI L"\u03e3" #define UNICODE_COPTIC_CAPITAL_LETTER_FEI 0x03e4 #define UNITEXT_COPTIC_CAPITAL_LETTER_FEI L"\u03e4" #define UNICODE_COPTIC_SMALL_LETTER_FEI 0x03e5 #define UNITEXT_COPTIC_SMALL_LETTER_FEI L"\u03e5" #define UNICODE_COPTIC_CAPITAL_LETTER_KHEI 0x03e6 #define UNITEXT_COPTIC_CAPITAL_LETTER_KHEI L"\u03e6" #define UNICODE_COPTIC_SMALL_LETTER_KHEI 0x03e7 #define UNITEXT_COPTIC_SMALL_LETTER_KHEI L"\u03e7" #define UNICODE_COPTIC_CAPITAL_LETTER_HORI 0x03e8 #define UNITEXT_COPTIC_CAPITAL_LETTER_HORI L"\u03e8" #define UNICODE_COPTIC_SMALL_LETTER_HORI 0x03e9 #define UNITEXT_COPTIC_SMALL_LETTER_HORI L"\u03e9" #define UNICODE_COPTIC_CAPITAL_LETTER_GANGIA 0x03ea #define UNITEXT_COPTIC_CAPITAL_LETTER_GANGIA L"\u03ea" #define UNICODE_COPTIC_SMALL_LETTER_GANGIA 0x03eb #define UNITEXT_COPTIC_SMALL_LETTER_GANGIA L"\u03eb" #define UNICODE_COPTIC_CAPITAL_LETTER_SHIMA 0x03ec #define UNITEXT_COPTIC_CAPITAL_LETTER_SHIMA L"\u03ec" #define UNICODE_COPTIC_SMALL_LETTER_SHIMA 0x03ed #define UNITEXT_COPTIC_SMALL_LETTER_SHIMA L"\u03ed" #define UNICODE_COPTIC_CAPITAL_LETTER_DEI 0x03ee #define UNITEXT_COPTIC_CAPITAL_LETTER_DEI L"\u03ee" #define UNICODE_COPTIC_SMALL_LETTER_DEI 0x03ef #define UNITEXT_COPTIC_SMALL_LETTER_DEI L"\u03ef" #define UNICODE_GREEK_KAPPA_SYMBOL 0x03f0 #define UNITEXT_GREEK_KAPPA_SYMBOL L"\u03f0" #define UNICODE_GREEK_RHO_SYMBOL 0x03f1 #define UNITEXT_GREEK_RHO_SYMBOL L"\u03f1" #define UNICODE_GREEK_LUNATE_SIGMA_SYMBOL 0x03f2 #define UNITEXT_GREEK_LUNATE_SIGMA_SYMBOL L"\u03f2" #define UNICODE_GREEK_LETTER_YOT 0x03f3 #define UNITEXT_GREEK_LETTER_YOT L"\u03f3" #define UNICODE_GREEK_CAPITAL_THETA_SYMBOL 0x03f4 #define UNITEXT_GREEK_CAPITAL_THETA_SYMBOL L"\u03f4" #define UNICODE_GREEK_LUNATE_EPSILON_SYMBOL 0x03f5 #define UNITEXT_GREEK_LUNATE_EPSILON_SYMBOL L"\u03f5" #define UNICODE_GREEK_REVERSED_LUNATE_EPSILON_SYMBOL 0x03f6 #define UNITEXT_GREEK_REVERSED_LUNATE_EPSILON_SYMBOL L"\u03f6" #define UNICODE_GREEK_CAPITAL_LETTER_SHO 0x03f7 #define UNITEXT_GREEK_CAPITAL_LETTER_SHO L"\u03f7" #define UNICODE_GREEK_SMALL_LETTER_SHO 0x03f8 #define UNITEXT_GREEK_SMALL_LETTER_SHO L"\u03f8" #define UNICODE_GREEK_CAPITAL_LUNATE_SIGMA_SYMBOL 0x03f9 #define UNITEXT_GREEK_CAPITAL_LUNATE_SIGMA_SYMBOL L"\u03f9" #define UNICODE_GREEK_CAPITAL_LETTER_SAN 0x03fa #define UNITEXT_GREEK_CAPITAL_LETTER_SAN L"\u03fa" #define UNICODE_GREEK_SMALL_LETTER_SAN 0x03fb #define UNITEXT_GREEK_SMALL_LETTER_SAN L"\u03fb" #define UNICODE_GREEK_RHO_WITH_STROKE_SYMBOL 0x03fc #define UNITEXT_GREEK_RHO_WITH_STROKE_SYMBOL L"\u03fc" #define UNICODE_GREEK_CAPITAL_REVERSED_LUNATE_SIGMA_SYMBOL 0x03fd #define UNITEXT_GREEK_CAPITAL_REVERSED_LUNATE_SIGMA_SYMBOL L"\u03fd" #define UNICODE_GREEK_CAPITAL_DOTTED_LUNATE_SIGMA_SYMBOL 0x03fe #define UNITEXT_GREEK_CAPITAL_DOTTED_LUNATE_SIGMA_SYMBOL L"\u03fe" #define UNICODE_GREEK_CAPITAL_REVERSED_DOTTED_LUNATE_SIGMA_SYMBOL 0x03ff #define UNITEXT_GREEK_CAPITAL_REVERSED_DOTTED_LUNATE_SIGMA_SYMBOL L"\u03ff" #define UNICODE_CYRILLIC_CAPITAL_LETTER_IE_WITH_GRAVE 0x0400 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_IE_WITH_GRAVE L"\u0400" #define UNICODE_CYRILLIC_CAPITAL_LETTER_IO 0x0401 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_IO L"\u0401" #define UNICODE_CYRILLIC_CAPITAL_LETTER_DJE 0x0402 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_DJE L"\u0402" #define UNICODE_CYRILLIC_CAPITAL_LETTER_GJE 0x0403 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_GJE L"\u0403" #define UNICODE_CYRILLIC_CAPITAL_LETTER_UKRAINIAN_IE 0x0404 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_UKRAINIAN_IE L"\u0404" #define UNICODE_CYRILLIC_CAPITAL_LETTER_DZE 0x0405 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_DZE L"\u0405" #define UNICODE_CYRILLIC_CAPITAL_LETTER_BYELORUSSIAN_UKRAINIAN_I 0x0406 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_BYELORUSSIAN_UKRAINIAN_I L"\u0406" #define UNICODE_CYRILLIC_CAPITAL_LETTER_YI 0x0407 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_YI L"\u0407" #define UNICODE_CYRILLIC_CAPITAL_LETTER_JE 0x0408 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_JE L"\u0408" #define UNICODE_CYRILLIC_CAPITAL_LETTER_LJE 0x0409 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_LJE L"\u0409" #define UNICODE_CYRILLIC_CAPITAL_LETTER_NJE 0x040a #define UNITEXT_CYRILLIC_CAPITAL_LETTER_NJE L"\u040a" #define UNICODE_CYRILLIC_CAPITAL_LETTER_TSHE 0x040b #define UNITEXT_CYRILLIC_CAPITAL_LETTER_TSHE L"\u040b" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KJE 0x040c #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KJE L"\u040c" #define UNICODE_CYRILLIC_CAPITAL_LETTER_I_WITH_GRAVE 0x040d #define UNITEXT_CYRILLIC_CAPITAL_LETTER_I_WITH_GRAVE L"\u040d" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SHORT_U 0x040e #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SHORT_U L"\u040e" #define UNICODE_CYRILLIC_CAPITAL_LETTER_DZHE 0x040f #define UNITEXT_CYRILLIC_CAPITAL_LETTER_DZHE L"\u040f" #define UNICODE_CYRILLIC_CAPITAL_LETTER_A 0x0410 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_A L"\u0410" #define UNICODE_CYRILLIC_CAPITAL_LETTER_BE 0x0411 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_BE L"\u0411" #define UNICODE_CYRILLIC_CAPITAL_LETTER_VE 0x0412 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_VE L"\u0412" #define UNICODE_CYRILLIC_CAPITAL_LETTER_GHE 0x0413 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_GHE L"\u0413" #define UNICODE_CYRILLIC_CAPITAL_LETTER_DE 0x0414 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_DE L"\u0414" #define UNICODE_CYRILLIC_CAPITAL_LETTER_IE 0x0415 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_IE L"\u0415" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ZHE 0x0416 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ZHE L"\u0416" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ZE 0x0417 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ZE L"\u0417" #define UNICODE_CYRILLIC_CAPITAL_LETTER_I 0x0418 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_I L"\u0418" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SHORT_I 0x0419 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SHORT_I L"\u0419" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KA 0x041a #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KA L"\u041a" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EL 0x041b #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EL L"\u041b" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EM 0x041c #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EM L"\u041c" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EN 0x041d #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EN L"\u041d" #define UNICODE_CYRILLIC_CAPITAL_LETTER_O 0x041e #define UNITEXT_CYRILLIC_CAPITAL_LETTER_O L"\u041e" #define UNICODE_CYRILLIC_CAPITAL_LETTER_PE 0x041f #define UNITEXT_CYRILLIC_CAPITAL_LETTER_PE L"\u041f" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ER 0x0420 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ER L"\u0420" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ES 0x0421 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ES L"\u0421" #define UNICODE_CYRILLIC_CAPITAL_LETTER_TE 0x0422 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_TE L"\u0422" #define UNICODE_CYRILLIC_CAPITAL_LETTER_U 0x0423 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_U L"\u0423" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EF 0x0424 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EF L"\u0424" #define UNICODE_CYRILLIC_CAPITAL_LETTER_HA 0x0425 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_HA L"\u0425" #define UNICODE_CYRILLIC_CAPITAL_LETTER_TSE 0x0426 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_TSE L"\u0426" #define UNICODE_CYRILLIC_CAPITAL_LETTER_CHE 0x0427 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_CHE L"\u0427" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SHA 0x0428 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SHA L"\u0428" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SHCHA 0x0429 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SHCHA L"\u0429" #define UNICODE_CYRILLIC_CAPITAL_LETTER_HARD_SIGN 0x042a #define UNITEXT_CYRILLIC_CAPITAL_LETTER_HARD_SIGN L"\u042a" #define UNICODE_CYRILLIC_CAPITAL_LETTER_YERU 0x042b #define UNITEXT_CYRILLIC_CAPITAL_LETTER_YERU L"\u042b" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SOFT_SIGN 0x042c #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SOFT_SIGN L"\u042c" #define UNICODE_CYRILLIC_CAPITAL_LETTER_E 0x042d #define UNITEXT_CYRILLIC_CAPITAL_LETTER_E L"\u042d" #define UNICODE_CYRILLIC_CAPITAL_LETTER_YU 0x042e #define UNITEXT_CYRILLIC_CAPITAL_LETTER_YU L"\u042e" #define UNICODE_CYRILLIC_CAPITAL_LETTER_YA 0x042f #define UNITEXT_CYRILLIC_CAPITAL_LETTER_YA L"\u042f" #define UNICODE_CYRILLIC_SMALL_LETTER_A 0x0430 #define UNITEXT_CYRILLIC_SMALL_LETTER_A L"\u0430" #define UNICODE_CYRILLIC_SMALL_LETTER_BE 0x0431 #define UNITEXT_CYRILLIC_SMALL_LETTER_BE L"\u0431" #define UNICODE_CYRILLIC_SMALL_LETTER_VE 0x0432 #define UNITEXT_CYRILLIC_SMALL_LETTER_VE L"\u0432" #define UNICODE_CYRILLIC_SMALL_LETTER_GHE 0x0433 #define UNITEXT_CYRILLIC_SMALL_LETTER_GHE L"\u0433" #define UNICODE_CYRILLIC_SMALL_LETTER_DE 0x0434 #define UNITEXT_CYRILLIC_SMALL_LETTER_DE L"\u0434" #define UNICODE_CYRILLIC_SMALL_LETTER_IE 0x0435 #define UNITEXT_CYRILLIC_SMALL_LETTER_IE L"\u0435" #define UNICODE_CYRILLIC_SMALL_LETTER_ZHE 0x0436 #define UNITEXT_CYRILLIC_SMALL_LETTER_ZHE L"\u0436" #define UNICODE_CYRILLIC_SMALL_LETTER_ZE 0x0437 #define UNITEXT_CYRILLIC_SMALL_LETTER_ZE L"\u0437" #define UNICODE_CYRILLIC_SMALL_LETTER_I 0x0438 #define UNITEXT_CYRILLIC_SMALL_LETTER_I L"\u0438" #define UNICODE_CYRILLIC_SMALL_LETTER_SHORT_I 0x0439 #define UNITEXT_CYRILLIC_SMALL_LETTER_SHORT_I L"\u0439" #define UNICODE_CYRILLIC_SMALL_LETTER_KA 0x043a #define UNITEXT_CYRILLIC_SMALL_LETTER_KA L"\u043a" #define UNICODE_CYRILLIC_SMALL_LETTER_EL 0x043b #define UNITEXT_CYRILLIC_SMALL_LETTER_EL L"\u043b" #define UNICODE_CYRILLIC_SMALL_LETTER_EM 0x043c #define UNITEXT_CYRILLIC_SMALL_LETTER_EM L"\u043c" #define UNICODE_CYRILLIC_SMALL_LETTER_EN 0x043d #define UNITEXT_CYRILLIC_SMALL_LETTER_EN L"\u043d" #define UNICODE_CYRILLIC_SMALL_LETTER_O 0x043e #define UNITEXT_CYRILLIC_SMALL_LETTER_O L"\u043e" #define UNICODE_CYRILLIC_SMALL_LETTER_PE 0x043f #define UNITEXT_CYRILLIC_SMALL_LETTER_PE L"\u043f" #define UNICODE_CYRILLIC_SMALL_LETTER_ER 0x0440 #define UNITEXT_CYRILLIC_SMALL_LETTER_ER L"\u0440" #define UNICODE_CYRILLIC_SMALL_LETTER_ES 0x0441 #define UNITEXT_CYRILLIC_SMALL_LETTER_ES L"\u0441" #define UNICODE_CYRILLIC_SMALL_LETTER_TE 0x0442 #define UNITEXT_CYRILLIC_SMALL_LETTER_TE L"\u0442" #define UNICODE_CYRILLIC_SMALL_LETTER_U 0x0443 #define UNITEXT_CYRILLIC_SMALL_LETTER_U L"\u0443" #define UNICODE_CYRILLIC_SMALL_LETTER_EF 0x0444 #define UNITEXT_CYRILLIC_SMALL_LETTER_EF L"\u0444" #define UNICODE_CYRILLIC_SMALL_LETTER_HA 0x0445 #define UNITEXT_CYRILLIC_SMALL_LETTER_HA L"\u0445" #define UNICODE_CYRILLIC_SMALL_LETTER_TSE 0x0446 #define UNITEXT_CYRILLIC_SMALL_LETTER_TSE L"\u0446" #define UNICODE_CYRILLIC_SMALL_LETTER_CHE 0x0447 #define UNITEXT_CYRILLIC_SMALL_LETTER_CHE L"\u0447" #define UNICODE_CYRILLIC_SMALL_LETTER_SHA 0x0448 #define UNITEXT_CYRILLIC_SMALL_LETTER_SHA L"\u0448" #define UNICODE_CYRILLIC_SMALL_LETTER_SHCHA 0x0449 #define UNITEXT_CYRILLIC_SMALL_LETTER_SHCHA L"\u0449" #define UNICODE_CYRILLIC_SMALL_LETTER_HARD_SIGN 0x044a #define UNITEXT_CYRILLIC_SMALL_LETTER_HARD_SIGN L"\u044a" #define UNICODE_CYRILLIC_SMALL_LETTER_YERU 0x044b #define UNITEXT_CYRILLIC_SMALL_LETTER_YERU L"\u044b" #define UNICODE_CYRILLIC_SMALL_LETTER_SOFT_SIGN 0x044c #define UNITEXT_CYRILLIC_SMALL_LETTER_SOFT_SIGN L"\u044c" #define UNICODE_CYRILLIC_SMALL_LETTER_E 0x044d #define UNITEXT_CYRILLIC_SMALL_LETTER_E L"\u044d" #define UNICODE_CYRILLIC_SMALL_LETTER_YU 0x044e #define UNITEXT_CYRILLIC_SMALL_LETTER_YU L"\u044e" #define UNICODE_CYRILLIC_SMALL_LETTER_YA 0x044f #define UNITEXT_CYRILLIC_SMALL_LETTER_YA L"\u044f" #define UNICODE_CYRILLIC_SMALL_LETTER_IE_WITH_GRAVE 0x0450 #define UNITEXT_CYRILLIC_SMALL_LETTER_IE_WITH_GRAVE L"\u0450" #define UNICODE_CYRILLIC_SMALL_LETTER_IO 0x0451 #define UNITEXT_CYRILLIC_SMALL_LETTER_IO L"\u0451" #define UNICODE_CYRILLIC_SMALL_LETTER_DJE 0x0452 #define UNITEXT_CYRILLIC_SMALL_LETTER_DJE L"\u0452" #define UNICODE_CYRILLIC_SMALL_LETTER_GJE 0x0453 #define UNITEXT_CYRILLIC_SMALL_LETTER_GJE L"\u0453" #define UNICODE_CYRILLIC_SMALL_LETTER_UKRAINIAN_IE 0x0454 #define UNITEXT_CYRILLIC_SMALL_LETTER_UKRAINIAN_IE L"\u0454" #define UNICODE_CYRILLIC_SMALL_LETTER_DZE 0x0455 #define UNITEXT_CYRILLIC_SMALL_LETTER_DZE L"\u0455" #define UNICODE_CYRILLIC_SMALL_LETTER_BYELORUSSIAN_UKRAINIAN_I 0x0456 #define UNITEXT_CYRILLIC_SMALL_LETTER_BYELORUSSIAN_UKRAINIAN_I L"\u0456" #define UNICODE_CYRILLIC_SMALL_LETTER_YI 0x0457 #define UNITEXT_CYRILLIC_SMALL_LETTER_YI L"\u0457" #define UNICODE_CYRILLIC_SMALL_LETTER_JE 0x0458 #define UNITEXT_CYRILLIC_SMALL_LETTER_JE L"\u0458" #define UNICODE_CYRILLIC_SMALL_LETTER_LJE 0x0459 #define UNITEXT_CYRILLIC_SMALL_LETTER_LJE L"\u0459" #define UNICODE_CYRILLIC_SMALL_LETTER_NJE 0x045a #define UNITEXT_CYRILLIC_SMALL_LETTER_NJE L"\u045a" #define UNICODE_CYRILLIC_SMALL_LETTER_TSHE 0x045b #define UNITEXT_CYRILLIC_SMALL_LETTER_TSHE L"\u045b" #define UNICODE_CYRILLIC_SMALL_LETTER_KJE 0x045c #define UNITEXT_CYRILLIC_SMALL_LETTER_KJE L"\u045c" #define UNICODE_CYRILLIC_SMALL_LETTER_I_WITH_GRAVE 0x045d #define UNITEXT_CYRILLIC_SMALL_LETTER_I_WITH_GRAVE L"\u045d" #define UNICODE_CYRILLIC_SMALL_LETTER_SHORT_U 0x045e #define UNITEXT_CYRILLIC_SMALL_LETTER_SHORT_U L"\u045e" #define UNICODE_CYRILLIC_SMALL_LETTER_DZHE 0x045f #define UNITEXT_CYRILLIC_SMALL_LETTER_DZHE L"\u045f" #define UNICODE_CYRILLIC_CAPITAL_LETTER_OMEGA 0x0460 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_OMEGA L"\u0460" #define UNICODE_CYRILLIC_SMALL_LETTER_OMEGA 0x0461 #define UNITEXT_CYRILLIC_SMALL_LETTER_OMEGA L"\u0461" #define UNICODE_CYRILLIC_CAPITAL_LETTER_YAT 0x0462 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_YAT L"\u0462" #define UNICODE_CYRILLIC_SMALL_LETTER_YAT 0x0463 #define UNITEXT_CYRILLIC_SMALL_LETTER_YAT L"\u0463" #define UNICODE_CYRILLIC_CAPITAL_LETTER_IOTIFIED_E 0x0464 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_IOTIFIED_E L"\u0464" #define UNICODE_CYRILLIC_SMALL_LETTER_IOTIFIED_E 0x0465 #define UNITEXT_CYRILLIC_SMALL_LETTER_IOTIFIED_E L"\u0465" #define UNICODE_CYRILLIC_CAPITAL_LETTER_LITTLE_YUS 0x0466 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_LITTLE_YUS L"\u0466" #define UNICODE_CYRILLIC_SMALL_LETTER_LITTLE_YUS 0x0467 #define UNITEXT_CYRILLIC_SMALL_LETTER_LITTLE_YUS L"\u0467" #define UNICODE_CYRILLIC_CAPITAL_LETTER_IOTIFIED_LITTLE_YUS 0x0468 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_IOTIFIED_LITTLE_YUS L"\u0468" #define UNICODE_CYRILLIC_SMALL_LETTER_IOTIFIED_LITTLE_YUS 0x0469 #define UNITEXT_CYRILLIC_SMALL_LETTER_IOTIFIED_LITTLE_YUS L"\u0469" #define UNICODE_CYRILLIC_CAPITAL_LETTER_BIG_YUS 0x046a #define UNITEXT_CYRILLIC_CAPITAL_LETTER_BIG_YUS L"\u046a" #define UNICODE_CYRILLIC_SMALL_LETTER_BIG_YUS 0x046b #define UNITEXT_CYRILLIC_SMALL_LETTER_BIG_YUS L"\u046b" #define UNICODE_CYRILLIC_CAPITAL_LETTER_IOTIFIED_BIG_YUS 0x046c #define UNITEXT_CYRILLIC_CAPITAL_LETTER_IOTIFIED_BIG_YUS L"\u046c" #define UNICODE_CYRILLIC_SMALL_LETTER_IOTIFIED_BIG_YUS 0x046d #define UNITEXT_CYRILLIC_SMALL_LETTER_IOTIFIED_BIG_YUS L"\u046d" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KSI 0x046e #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KSI L"\u046e" #define UNICODE_CYRILLIC_SMALL_LETTER_KSI 0x046f #define UNITEXT_CYRILLIC_SMALL_LETTER_KSI L"\u046f" #define UNICODE_CYRILLIC_CAPITAL_LETTER_PSI 0x0470 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_PSI L"\u0470" #define UNICODE_CYRILLIC_SMALL_LETTER_PSI 0x0471 #define UNITEXT_CYRILLIC_SMALL_LETTER_PSI L"\u0471" #define UNICODE_CYRILLIC_CAPITAL_LETTER_FITA 0x0472 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_FITA L"\u0472" #define UNICODE_CYRILLIC_SMALL_LETTER_FITA 0x0473 #define UNITEXT_CYRILLIC_SMALL_LETTER_FITA L"\u0473" #define UNICODE_CYRILLIC_CAPITAL_LETTER_IZHITSA 0x0474 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_IZHITSA L"\u0474" #define UNICODE_CYRILLIC_SMALL_LETTER_IZHITSA 0x0475 #define UNITEXT_CYRILLIC_SMALL_LETTER_IZHITSA L"\u0475" #define UNICODE_CYRILLIC_CAPITAL_LETTER_IZHITSA_WITH_DOUBLE_GRAVE_ACCENT 0x0476 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_IZHITSA_WITH_DOUBLE_GRAVE_ACCENT L"\u0476" #define UNICODE_CYRILLIC_SMALL_LETTER_IZHITSA_WITH_DOUBLE_GRAVE_ACCENT 0x0477 #define UNITEXT_CYRILLIC_SMALL_LETTER_IZHITSA_WITH_DOUBLE_GRAVE_ACCENT L"\u0477" #define UNICODE_CYRILLIC_CAPITAL_LETTER_UK 0x0478 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_UK L"\u0478" #define UNICODE_CYRILLIC_SMALL_LETTER_UK 0x0479 #define UNITEXT_CYRILLIC_SMALL_LETTER_UK L"\u0479" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ROUND_OMEGA 0x047a #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ROUND_OMEGA L"\u047a" #define UNICODE_CYRILLIC_SMALL_LETTER_ROUND_OMEGA 0x047b #define UNITEXT_CYRILLIC_SMALL_LETTER_ROUND_OMEGA L"\u047b" #define UNICODE_CYRILLIC_CAPITAL_LETTER_OMEGA_WITH_TITLO 0x047c #define UNITEXT_CYRILLIC_CAPITAL_LETTER_OMEGA_WITH_TITLO L"\u047c" #define UNICODE_CYRILLIC_SMALL_LETTER_OMEGA_WITH_TITLO 0x047d #define UNITEXT_CYRILLIC_SMALL_LETTER_OMEGA_WITH_TITLO L"\u047d" #define UNICODE_CYRILLIC_CAPITAL_LETTER_OT 0x047e #define UNITEXT_CYRILLIC_CAPITAL_LETTER_OT L"\u047e" #define UNICODE_CYRILLIC_SMALL_LETTER_OT 0x047f #define UNITEXT_CYRILLIC_SMALL_LETTER_OT L"\u047f" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KOPPA 0x0480 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KOPPA L"\u0480" #define UNICODE_CYRILLIC_SMALL_LETTER_KOPPA 0x0481 #define UNITEXT_CYRILLIC_SMALL_LETTER_KOPPA L"\u0481" #define UNICODE_CYRILLIC_THOUSANDS_SIGN 0x0482 #define UNITEXT_CYRILLIC_THOUSANDS_SIGN L"\u0482" #define UNICODE_COMBINING_CYRILLIC_TITLO 0x0483 #define UNITEXT_COMBINING_CYRILLIC_TITLO L"\u0483" #define UNICODE_COMBINING_CYRILLIC_PALATALIZATION 0x0484 #define UNITEXT_COMBINING_CYRILLIC_PALATALIZATION L"\u0484" #define UNICODE_COMBINING_CYRILLIC_DASIA_PNEUMATA 0x0485 #define UNITEXT_COMBINING_CYRILLIC_DASIA_PNEUMATA L"\u0485" #define UNICODE_COMBINING_CYRILLIC_PSILI_PNEUMATA 0x0486 #define UNITEXT_COMBINING_CYRILLIC_PSILI_PNEUMATA L"\u0486" #define UNICODE_COMBINING_CYRILLIC_HUNDRED_THOUSANDS_SIGN 0x0488 #define UNITEXT_COMBINING_CYRILLIC_HUNDRED_THOUSANDS_SIGN L"\u0488" #define UNICODE_COMBINING_CYRILLIC_MILLIONS_SIGN 0x0489 #define UNITEXT_COMBINING_CYRILLIC_MILLIONS_SIGN L"\u0489" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SHORT_I_WITH_TAIL 0x048a #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SHORT_I_WITH_TAIL L"\u048a" #define UNICODE_CYRILLIC_SMALL_LETTER_SHORT_I_WITH_TAIL 0x048b #define UNITEXT_CYRILLIC_SMALL_LETTER_SHORT_I_WITH_TAIL L"\u048b" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SEMISOFT_SIGN 0x048c #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SEMISOFT_SIGN L"\u048c" #define UNICODE_CYRILLIC_SMALL_LETTER_SEMISOFT_SIGN 0x048d #define UNITEXT_CYRILLIC_SMALL_LETTER_SEMISOFT_SIGN L"\u048d" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ER_WITH_TICK 0x048e #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ER_WITH_TICK L"\u048e" #define UNICODE_CYRILLIC_SMALL_LETTER_ER_WITH_TICK 0x048f #define UNITEXT_CYRILLIC_SMALL_LETTER_ER_WITH_TICK L"\u048f" #define UNICODE_CYRILLIC_CAPITAL_LETTER_GHE_WITH_UPTURN 0x0490 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_GHE_WITH_UPTURN L"\u0490" #define UNICODE_CYRILLIC_SMALL_LETTER_GHE_WITH_UPTURN 0x0491 #define UNITEXT_CYRILLIC_SMALL_LETTER_GHE_WITH_UPTURN L"\u0491" #define UNICODE_CYRILLIC_CAPITAL_LETTER_GHE_WITH_STROKE 0x0492 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_GHE_WITH_STROKE L"\u0492" #define UNICODE_CYRILLIC_SMALL_LETTER_GHE_WITH_STROKE 0x0493 #define UNITEXT_CYRILLIC_SMALL_LETTER_GHE_WITH_STROKE L"\u0493" #define UNICODE_CYRILLIC_CAPITAL_LETTER_GHE_WITH_MIDDLE_HOOK 0x0494 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_GHE_WITH_MIDDLE_HOOK L"\u0494" #define UNICODE_CYRILLIC_SMALL_LETTER_GHE_WITH_MIDDLE_HOOK 0x0495 #define UNITEXT_CYRILLIC_SMALL_LETTER_GHE_WITH_MIDDLE_HOOK L"\u0495" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ZHE_WITH_DESCENDER 0x0496 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ZHE_WITH_DESCENDER L"\u0496" #define UNICODE_CYRILLIC_SMALL_LETTER_ZHE_WITH_DESCENDER 0x0497 #define UNITEXT_CYRILLIC_SMALL_LETTER_ZHE_WITH_DESCENDER L"\u0497" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ZE_WITH_DESCENDER 0x0498 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ZE_WITH_DESCENDER L"\u0498" #define UNICODE_CYRILLIC_SMALL_LETTER_ZE_WITH_DESCENDER 0x0499 #define UNITEXT_CYRILLIC_SMALL_LETTER_ZE_WITH_DESCENDER L"\u0499" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KA_WITH_DESCENDER 0x049a #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KA_WITH_DESCENDER L"\u049a" #define UNICODE_CYRILLIC_SMALL_LETTER_KA_WITH_DESCENDER 0x049b #define UNITEXT_CYRILLIC_SMALL_LETTER_KA_WITH_DESCENDER L"\u049b" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KA_WITH_VERTICAL_STROKE 0x049c #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KA_WITH_VERTICAL_STROKE L"\u049c" #define UNICODE_CYRILLIC_SMALL_LETTER_KA_WITH_VERTICAL_STROKE 0x049d #define UNITEXT_CYRILLIC_SMALL_LETTER_KA_WITH_VERTICAL_STROKE L"\u049d" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KA_WITH_STROKE 0x049e #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KA_WITH_STROKE L"\u049e" #define UNICODE_CYRILLIC_SMALL_LETTER_KA_WITH_STROKE 0x049f #define UNITEXT_CYRILLIC_SMALL_LETTER_KA_WITH_STROKE L"\u049f" #define UNICODE_CYRILLIC_CAPITAL_LETTER_BASHKIR_KA 0x04a0 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_BASHKIR_KA L"\u04a0" #define UNICODE_CYRILLIC_SMALL_LETTER_BASHKIR_KA 0x04a1 #define UNITEXT_CYRILLIC_SMALL_LETTER_BASHKIR_KA L"\u04a1" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EN_WITH_DESCENDER 0x04a2 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EN_WITH_DESCENDER L"\u04a2" #define UNICODE_CYRILLIC_SMALL_LETTER_EN_WITH_DESCENDER 0x04a3 #define UNITEXT_CYRILLIC_SMALL_LETTER_EN_WITH_DESCENDER L"\u04a3" #define UNICODE_CYRILLIC_CAPITAL_LIGATURE_EN_GHE 0x04a4 #define UNITEXT_CYRILLIC_CAPITAL_LIGATURE_EN_GHE L"\u04a4" #define UNICODE_CYRILLIC_SMALL_LIGATURE_EN_GHE 0x04a5 #define UNITEXT_CYRILLIC_SMALL_LIGATURE_EN_GHE L"\u04a5" #define UNICODE_CYRILLIC_CAPITAL_LETTER_PE_WITH_MIDDLE_HOOK 0x04a6 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_PE_WITH_MIDDLE_HOOK L"\u04a6" #define UNICODE_CYRILLIC_SMALL_LETTER_PE_WITH_MIDDLE_HOOK 0x04a7 #define UNITEXT_CYRILLIC_SMALL_LETTER_PE_WITH_MIDDLE_HOOK L"\u04a7" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ABKHASIAN_HA 0x04a8 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ABKHASIAN_HA L"\u04a8" #define UNICODE_CYRILLIC_SMALL_LETTER_ABKHASIAN_HA 0x04a9 #define UNITEXT_CYRILLIC_SMALL_LETTER_ABKHASIAN_HA L"\u04a9" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ES_WITH_DESCENDER 0x04aa #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ES_WITH_DESCENDER L"\u04aa" #define UNICODE_CYRILLIC_SMALL_LETTER_ES_WITH_DESCENDER 0x04ab #define UNITEXT_CYRILLIC_SMALL_LETTER_ES_WITH_DESCENDER L"\u04ab" #define UNICODE_CYRILLIC_CAPITAL_LETTER_TE_WITH_DESCENDER 0x04ac #define UNITEXT_CYRILLIC_CAPITAL_LETTER_TE_WITH_DESCENDER L"\u04ac" #define UNICODE_CYRILLIC_SMALL_LETTER_TE_WITH_DESCENDER 0x04ad #define UNITEXT_CYRILLIC_SMALL_LETTER_TE_WITH_DESCENDER L"\u04ad" #define UNICODE_CYRILLIC_CAPITAL_LETTER_STRAIGHT_U 0x04ae #define UNITEXT_CYRILLIC_CAPITAL_LETTER_STRAIGHT_U L"\u04ae" #define UNICODE_CYRILLIC_SMALL_LETTER_STRAIGHT_U 0x04af #define UNITEXT_CYRILLIC_SMALL_LETTER_STRAIGHT_U L"\u04af" #define UNICODE_CYRILLIC_CAPITAL_LETTER_STRAIGHT_U_WITH_STROKE 0x04b0 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_STRAIGHT_U_WITH_STROKE L"\u04b0" #define UNICODE_CYRILLIC_SMALL_LETTER_STRAIGHT_U_WITH_STROKE 0x04b1 #define UNITEXT_CYRILLIC_SMALL_LETTER_STRAIGHT_U_WITH_STROKE L"\u04b1" #define UNICODE_CYRILLIC_CAPITAL_LETTER_HA_WITH_DESCENDER 0x04b2 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_HA_WITH_DESCENDER L"\u04b2" #define UNICODE_CYRILLIC_SMALL_LETTER_HA_WITH_DESCENDER 0x04b3 #define UNITEXT_CYRILLIC_SMALL_LETTER_HA_WITH_DESCENDER L"\u04b3" #define UNICODE_CYRILLIC_CAPITAL_LIGATURE_TE_TSE 0x04b4 #define UNITEXT_CYRILLIC_CAPITAL_LIGATURE_TE_TSE L"\u04b4" #define UNICODE_CYRILLIC_SMALL_LIGATURE_TE_TSE 0x04b5 #define UNITEXT_CYRILLIC_SMALL_LIGATURE_TE_TSE L"\u04b5" #define UNICODE_CYRILLIC_CAPITAL_LETTER_CHE_WITH_DESCENDER 0x04b6 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_CHE_WITH_DESCENDER L"\u04b6" #define UNICODE_CYRILLIC_SMALL_LETTER_CHE_WITH_DESCENDER 0x04b7 #define UNITEXT_CYRILLIC_SMALL_LETTER_CHE_WITH_DESCENDER L"\u04b7" #define UNICODE_CYRILLIC_CAPITAL_LETTER_CHE_WITH_VERTICAL_STROKE 0x04b8 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_CHE_WITH_VERTICAL_STROKE L"\u04b8" #define UNICODE_CYRILLIC_SMALL_LETTER_CHE_WITH_VERTICAL_STROKE 0x04b9 #define UNITEXT_CYRILLIC_SMALL_LETTER_CHE_WITH_VERTICAL_STROKE L"\u04b9" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SHHA 0x04ba #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SHHA L"\u04ba" #define UNICODE_CYRILLIC_SMALL_LETTER_SHHA 0x04bb #define UNITEXT_CYRILLIC_SMALL_LETTER_SHHA L"\u04bb" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ABKHASIAN_CHE 0x04bc #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ABKHASIAN_CHE L"\u04bc" #define UNICODE_CYRILLIC_SMALL_LETTER_ABKHASIAN_CHE 0x04bd #define UNITEXT_CYRILLIC_SMALL_LETTER_ABKHASIAN_CHE L"\u04bd" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ABKHASIAN_CHE_WITH_DESCENDER 0x04be #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ABKHASIAN_CHE_WITH_DESCENDER L"\u04be" #define UNICODE_CYRILLIC_SMALL_LETTER_ABKHASIAN_CHE_WITH_DESCENDER 0x04bf #define UNITEXT_CYRILLIC_SMALL_LETTER_ABKHASIAN_CHE_WITH_DESCENDER L"\u04bf" #define UNICODE_CYRILLIC_LETTER_PALOCHKA 0x04c0 #define UNITEXT_CYRILLIC_LETTER_PALOCHKA L"\u04c0" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ZHE_WITH_BREVE 0x04c1 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ZHE_WITH_BREVE L"\u04c1" #define UNICODE_CYRILLIC_SMALL_LETTER_ZHE_WITH_BREVE 0x04c2 #define UNITEXT_CYRILLIC_SMALL_LETTER_ZHE_WITH_BREVE L"\u04c2" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KA_WITH_HOOK 0x04c3 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KA_WITH_HOOK L"\u04c3" #define UNICODE_CYRILLIC_SMALL_LETTER_KA_WITH_HOOK 0x04c4 #define UNITEXT_CYRILLIC_SMALL_LETTER_KA_WITH_HOOK L"\u04c4" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EL_WITH_TAIL 0x04c5 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EL_WITH_TAIL L"\u04c5" #define UNICODE_CYRILLIC_SMALL_LETTER_EL_WITH_TAIL 0x04c6 #define UNITEXT_CYRILLIC_SMALL_LETTER_EL_WITH_TAIL L"\u04c6" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EN_WITH_HOOK 0x04c7 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EN_WITH_HOOK L"\u04c7" #define UNICODE_CYRILLIC_SMALL_LETTER_EN_WITH_HOOK 0x04c8 #define UNITEXT_CYRILLIC_SMALL_LETTER_EN_WITH_HOOK L"\u04c8" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EN_WITH_TAIL 0x04c9 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EN_WITH_TAIL L"\u04c9" #define UNICODE_CYRILLIC_SMALL_LETTER_EN_WITH_TAIL 0x04ca #define UNITEXT_CYRILLIC_SMALL_LETTER_EN_WITH_TAIL L"\u04ca" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KHAKASSIAN_CHE 0x04cb #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KHAKASSIAN_CHE L"\u04cb" #define UNICODE_CYRILLIC_SMALL_LETTER_KHAKASSIAN_CHE 0x04cc #define UNITEXT_CYRILLIC_SMALL_LETTER_KHAKASSIAN_CHE L"\u04cc" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EM_WITH_TAIL 0x04cd #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EM_WITH_TAIL L"\u04cd" #define UNICODE_CYRILLIC_SMALL_LETTER_EM_WITH_TAIL 0x04ce #define UNITEXT_CYRILLIC_SMALL_LETTER_EM_WITH_TAIL L"\u04ce" #define UNICODE_CYRILLIC_SMALL_LETTER_PALOCHKA 0x04cf #define UNITEXT_CYRILLIC_SMALL_LETTER_PALOCHKA L"\u04cf" #define UNICODE_CYRILLIC_CAPITAL_LETTER_A_WITH_BREVE 0x04d0 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_A_WITH_BREVE L"\u04d0" #define UNICODE_CYRILLIC_SMALL_LETTER_A_WITH_BREVE 0x04d1 #define UNITEXT_CYRILLIC_SMALL_LETTER_A_WITH_BREVE L"\u04d1" #define UNICODE_CYRILLIC_CAPITAL_LETTER_A_WITH_DIAERESIS 0x04d2 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_A_WITH_DIAERESIS L"\u04d2" #define UNICODE_CYRILLIC_SMALL_LETTER_A_WITH_DIAERESIS 0x04d3 #define UNITEXT_CYRILLIC_SMALL_LETTER_A_WITH_DIAERESIS L"\u04d3" #define UNICODE_CYRILLIC_CAPITAL_LIGATURE_A_IE 0x04d4 #define UNITEXT_CYRILLIC_CAPITAL_LIGATURE_A_IE L"\u04d4" #define UNICODE_CYRILLIC_SMALL_LIGATURE_A_IE 0x04d5 #define UNITEXT_CYRILLIC_SMALL_LIGATURE_A_IE L"\u04d5" #define UNICODE_CYRILLIC_CAPITAL_LETTER_IE_WITH_BREVE 0x04d6 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_IE_WITH_BREVE L"\u04d6" #define UNICODE_CYRILLIC_SMALL_LETTER_IE_WITH_BREVE 0x04d7 #define UNITEXT_CYRILLIC_SMALL_LETTER_IE_WITH_BREVE L"\u04d7" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SCHWA 0x04d8 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SCHWA L"\u04d8" #define UNICODE_CYRILLIC_SMALL_LETTER_SCHWA 0x04d9 #define UNITEXT_CYRILLIC_SMALL_LETTER_SCHWA L"\u04d9" #define UNICODE_CYRILLIC_CAPITAL_LETTER_SCHWA_WITH_DIAERESIS 0x04da #define UNITEXT_CYRILLIC_CAPITAL_LETTER_SCHWA_WITH_DIAERESIS L"\u04da" #define UNICODE_CYRILLIC_SMALL_LETTER_SCHWA_WITH_DIAERESIS 0x04db #define UNITEXT_CYRILLIC_SMALL_LETTER_SCHWA_WITH_DIAERESIS L"\u04db" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ZHE_WITH_DIAERESIS 0x04dc #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ZHE_WITH_DIAERESIS L"\u04dc" #define UNICODE_CYRILLIC_SMALL_LETTER_ZHE_WITH_DIAERESIS 0x04dd #define UNITEXT_CYRILLIC_SMALL_LETTER_ZHE_WITH_DIAERESIS L"\u04dd" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ZE_WITH_DIAERESIS 0x04de #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ZE_WITH_DIAERESIS L"\u04de" #define UNICODE_CYRILLIC_SMALL_LETTER_ZE_WITH_DIAERESIS 0x04df #define UNITEXT_CYRILLIC_SMALL_LETTER_ZE_WITH_DIAERESIS L"\u04df" #define UNICODE_CYRILLIC_CAPITAL_LETTER_ABKHASIAN_DZE 0x04e0 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_ABKHASIAN_DZE L"\u04e0" #define UNICODE_CYRILLIC_SMALL_LETTER_ABKHASIAN_DZE 0x04e1 #define UNITEXT_CYRILLIC_SMALL_LETTER_ABKHASIAN_DZE L"\u04e1" #define UNICODE_CYRILLIC_CAPITAL_LETTER_I_WITH_MACRON 0x04e2 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_I_WITH_MACRON L"\u04e2" #define UNICODE_CYRILLIC_SMALL_LETTER_I_WITH_MACRON 0x04e3 #define UNITEXT_CYRILLIC_SMALL_LETTER_I_WITH_MACRON L"\u04e3" #define UNICODE_CYRILLIC_CAPITAL_LETTER_I_WITH_DIAERESIS 0x04e4 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_I_WITH_DIAERESIS L"\u04e4" #define UNICODE_CYRILLIC_SMALL_LETTER_I_WITH_DIAERESIS 0x04e5 #define UNITEXT_CYRILLIC_SMALL_LETTER_I_WITH_DIAERESIS L"\u04e5" #define UNICODE_CYRILLIC_CAPITAL_LETTER_O_WITH_DIAERESIS 0x04e6 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_O_WITH_DIAERESIS L"\u04e6" #define UNICODE_CYRILLIC_SMALL_LETTER_O_WITH_DIAERESIS 0x04e7 #define UNITEXT_CYRILLIC_SMALL_LETTER_O_WITH_DIAERESIS L"\u04e7" #define UNICODE_CYRILLIC_CAPITAL_LETTER_BARRED_O 0x04e8 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_BARRED_O L"\u04e8" #define UNICODE_CYRILLIC_SMALL_LETTER_BARRED_O 0x04e9 #define UNITEXT_CYRILLIC_SMALL_LETTER_BARRED_O L"\u04e9" #define UNICODE_CYRILLIC_CAPITAL_LETTER_BARRED_O_WITH_DIAERESIS 0x04ea #define UNITEXT_CYRILLIC_CAPITAL_LETTER_BARRED_O_WITH_DIAERESIS L"\u04ea" #define UNICODE_CYRILLIC_SMALL_LETTER_BARRED_O_WITH_DIAERESIS 0x04eb #define UNITEXT_CYRILLIC_SMALL_LETTER_BARRED_O_WITH_DIAERESIS L"\u04eb" #define UNICODE_CYRILLIC_CAPITAL_LETTER_E_WITH_DIAERESIS 0x04ec #define UNITEXT_CYRILLIC_CAPITAL_LETTER_E_WITH_DIAERESIS L"\u04ec" #define UNICODE_CYRILLIC_SMALL_LETTER_E_WITH_DIAERESIS 0x04ed #define UNITEXT_CYRILLIC_SMALL_LETTER_E_WITH_DIAERESIS L"\u04ed" #define UNICODE_CYRILLIC_CAPITAL_LETTER_U_WITH_MACRON 0x04ee #define UNITEXT_CYRILLIC_CAPITAL_LETTER_U_WITH_MACRON L"\u04ee" #define UNICODE_CYRILLIC_SMALL_LETTER_U_WITH_MACRON 0x04ef #define UNITEXT_CYRILLIC_SMALL_LETTER_U_WITH_MACRON L"\u04ef" #define UNICODE_CYRILLIC_CAPITAL_LETTER_U_WITH_DIAERESIS 0x04f0 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_U_WITH_DIAERESIS L"\u04f0" #define UNICODE_CYRILLIC_SMALL_LETTER_U_WITH_DIAERESIS 0x04f1 #define UNITEXT_CYRILLIC_SMALL_LETTER_U_WITH_DIAERESIS L"\u04f1" #define UNICODE_CYRILLIC_CAPITAL_LETTER_U_WITH_DOUBLE_ACUTE 0x04f2 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_U_WITH_DOUBLE_ACUTE L"\u04f2" #define UNICODE_CYRILLIC_SMALL_LETTER_U_WITH_DOUBLE_ACUTE 0x04f3 #define UNITEXT_CYRILLIC_SMALL_LETTER_U_WITH_DOUBLE_ACUTE L"\u04f3" #define UNICODE_CYRILLIC_CAPITAL_LETTER_CHE_WITH_DIAERESIS 0x04f4 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_CHE_WITH_DIAERESIS L"\u04f4" #define UNICODE_CYRILLIC_SMALL_LETTER_CHE_WITH_DIAERESIS 0x04f5 #define UNITEXT_CYRILLIC_SMALL_LETTER_CHE_WITH_DIAERESIS L"\u04f5" #define UNICODE_CYRILLIC_CAPITAL_LETTER_GHE_WITH_DESCENDER 0x04f6 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_GHE_WITH_DESCENDER L"\u04f6" #define UNICODE_CYRILLIC_SMALL_LETTER_GHE_WITH_DESCENDER 0x04f7 #define UNITEXT_CYRILLIC_SMALL_LETTER_GHE_WITH_DESCENDER L"\u04f7" #define UNICODE_CYRILLIC_CAPITAL_LETTER_YERU_WITH_DIAERESIS 0x04f8 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_YERU_WITH_DIAERESIS L"\u04f8" #define UNICODE_CYRILLIC_SMALL_LETTER_YERU_WITH_DIAERESIS 0x04f9 #define UNITEXT_CYRILLIC_SMALL_LETTER_YERU_WITH_DIAERESIS L"\u04f9" #define UNICODE_CYRILLIC_CAPITAL_LETTER_GHE_WITH_STROKE_AND_HOOK 0x04fa #define UNITEXT_CYRILLIC_CAPITAL_LETTER_GHE_WITH_STROKE_AND_HOOK L"\u04fa" #define UNICODE_CYRILLIC_SMALL_LETTER_GHE_WITH_STROKE_AND_HOOK 0x04fb #define UNITEXT_CYRILLIC_SMALL_LETTER_GHE_WITH_STROKE_AND_HOOK L"\u04fb" #define UNICODE_CYRILLIC_CAPITAL_LETTER_HA_WITH_HOOK 0x04fc #define UNITEXT_CYRILLIC_CAPITAL_LETTER_HA_WITH_HOOK L"\u04fc" #define UNICODE_CYRILLIC_SMALL_LETTER_HA_WITH_HOOK 0x04fd #define UNITEXT_CYRILLIC_SMALL_LETTER_HA_WITH_HOOK L"\u04fd" #define UNICODE_CYRILLIC_CAPITAL_LETTER_HA_WITH_STROKE 0x04fe #define UNITEXT_CYRILLIC_CAPITAL_LETTER_HA_WITH_STROKE L"\u04fe" #define UNICODE_CYRILLIC_SMALL_LETTER_HA_WITH_STROKE 0x04ff #define UNITEXT_CYRILLIC_SMALL_LETTER_HA_WITH_STROKE L"\u04ff" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KOMI_DE 0x0500 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KOMI_DE L"\u0500" #define UNICODE_CYRILLIC_SMALL_LETTER_KOMI_DE 0x0501 #define UNITEXT_CYRILLIC_SMALL_LETTER_KOMI_DE L"\u0501" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KOMI_DJE 0x0502 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KOMI_DJE L"\u0502" #define UNICODE_CYRILLIC_SMALL_LETTER_KOMI_DJE 0x0503 #define UNITEXT_CYRILLIC_SMALL_LETTER_KOMI_DJE L"\u0503" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KOMI_ZJE 0x0504 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KOMI_ZJE L"\u0504" #define UNICODE_CYRILLIC_SMALL_LETTER_KOMI_ZJE 0x0505 #define UNITEXT_CYRILLIC_SMALL_LETTER_KOMI_ZJE L"\u0505" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KOMI_DZJE 0x0506 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KOMI_DZJE L"\u0506" #define UNICODE_CYRILLIC_SMALL_LETTER_KOMI_DZJE 0x0507 #define UNITEXT_CYRILLIC_SMALL_LETTER_KOMI_DZJE L"\u0507" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KOMI_LJE 0x0508 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KOMI_LJE L"\u0508" #define UNICODE_CYRILLIC_SMALL_LETTER_KOMI_LJE 0x0509 #define UNITEXT_CYRILLIC_SMALL_LETTER_KOMI_LJE L"\u0509" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KOMI_NJE 0x050a #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KOMI_NJE L"\u050a" #define UNICODE_CYRILLIC_SMALL_LETTER_KOMI_NJE 0x050b #define UNITEXT_CYRILLIC_SMALL_LETTER_KOMI_NJE L"\u050b" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KOMI_SJE 0x050c #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KOMI_SJE L"\u050c" #define UNICODE_CYRILLIC_SMALL_LETTER_KOMI_SJE 0x050d #define UNITEXT_CYRILLIC_SMALL_LETTER_KOMI_SJE L"\u050d" #define UNICODE_CYRILLIC_CAPITAL_LETTER_KOMI_TJE 0x050e #define UNITEXT_CYRILLIC_CAPITAL_LETTER_KOMI_TJE L"\u050e" #define UNICODE_CYRILLIC_SMALL_LETTER_KOMI_TJE 0x050f #define UNITEXT_CYRILLIC_SMALL_LETTER_KOMI_TJE L"\u050f" #define UNICODE_CYRILLIC_CAPITAL_LETTER_REVERSED_ZE 0x0510 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_REVERSED_ZE L"\u0510" #define UNICODE_CYRILLIC_SMALL_LETTER_REVERSED_ZE 0x0511 #define UNITEXT_CYRILLIC_SMALL_LETTER_REVERSED_ZE L"\u0511" #define UNICODE_CYRILLIC_CAPITAL_LETTER_EL_WITH_HOOK 0x0512 #define UNITEXT_CYRILLIC_CAPITAL_LETTER_EL_WITH_HOOK L"\u0512" #define UNICODE_CYRILLIC_SMALL_LETTER_EL_WITH_HOOK 0x0513 #define UNITEXT_CYRILLIC_SMALL_LETTER_EL_WITH_HOOK L"\u0513" #define UNICODE_ARMENIAN_CAPITAL_LETTER_AYB 0x0531 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_AYB L"\u0531" #define UNICODE_ARMENIAN_CAPITAL_LETTER_BEN 0x0532 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_BEN L"\u0532" #define UNICODE_ARMENIAN_CAPITAL_LETTER_GIM 0x0533 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_GIM L"\u0533" #define UNICODE_ARMENIAN_CAPITAL_LETTER_DA 0x0534 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_DA L"\u0534" #define UNICODE_ARMENIAN_CAPITAL_LETTER_ECH 0x0535 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_ECH L"\u0535" #define UNICODE_ARMENIAN_CAPITAL_LETTER_ZA 0x0536 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_ZA L"\u0536" #define UNICODE_ARMENIAN_CAPITAL_LETTER_EH 0x0537 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_EH L"\u0537" #define UNICODE_ARMENIAN_CAPITAL_LETTER_ET 0x0538 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_ET L"\u0538" #define UNICODE_ARMENIAN_CAPITAL_LETTER_TO 0x0539 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_TO L"\u0539" #define UNICODE_ARMENIAN_CAPITAL_LETTER_ZHE 0x053a #define UNITEXT_ARMENIAN_CAPITAL_LETTER_ZHE L"\u053a" #define UNICODE_ARMENIAN_CAPITAL_LETTER_INI 0x053b #define UNITEXT_ARMENIAN_CAPITAL_LETTER_INI L"\u053b" #define UNICODE_ARMENIAN_CAPITAL_LETTER_LIWN 0x053c #define UNITEXT_ARMENIAN_CAPITAL_LETTER_LIWN L"\u053c" #define UNICODE_ARMENIAN_CAPITAL_LETTER_XEH 0x053d #define UNITEXT_ARMENIAN_CAPITAL_LETTER_XEH L"\u053d" #define UNICODE_ARMENIAN_CAPITAL_LETTER_CA 0x053e #define UNITEXT_ARMENIAN_CAPITAL_LETTER_CA L"\u053e" #define UNICODE_ARMENIAN_CAPITAL_LETTER_KEN 0x053f #define UNITEXT_ARMENIAN_CAPITAL_LETTER_KEN L"\u053f" #define UNICODE_ARMENIAN_CAPITAL_LETTER_HO 0x0540 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_HO L"\u0540" #define UNICODE_ARMENIAN_CAPITAL_LETTER_JA 0x0541 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_JA L"\u0541" #define UNICODE_ARMENIAN_CAPITAL_LETTER_GHAD 0x0542 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_GHAD L"\u0542" #define UNICODE_ARMENIAN_CAPITAL_LETTER_CHEH 0x0543 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_CHEH L"\u0543" #define UNICODE_ARMENIAN_CAPITAL_LETTER_MEN 0x0544 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_MEN L"\u0544" #define UNICODE_ARMENIAN_CAPITAL_LETTER_YI 0x0545 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_YI L"\u0545" #define UNICODE_ARMENIAN_CAPITAL_LETTER_NOW 0x0546 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_NOW L"\u0546" #define UNICODE_ARMENIAN_CAPITAL_LETTER_SHA 0x0547 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_SHA L"\u0547" #define UNICODE_ARMENIAN_CAPITAL_LETTER_VO 0x0548 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_VO L"\u0548" #define UNICODE_ARMENIAN_CAPITAL_LETTER_CHA 0x0549 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_CHA L"\u0549" #define UNICODE_ARMENIAN_CAPITAL_LETTER_PEH 0x054a #define UNITEXT_ARMENIAN_CAPITAL_LETTER_PEH L"\u054a" #define UNICODE_ARMENIAN_CAPITAL_LETTER_JHEH 0x054b #define UNITEXT_ARMENIAN_CAPITAL_LETTER_JHEH L"\u054b" #define UNICODE_ARMENIAN_CAPITAL_LETTER_RA 0x054c #define UNITEXT_ARMENIAN_CAPITAL_LETTER_RA L"\u054c" #define UNICODE_ARMENIAN_CAPITAL_LETTER_SEH 0x054d #define UNITEXT_ARMENIAN_CAPITAL_LETTER_SEH L"\u054d" #define UNICODE_ARMENIAN_CAPITAL_LETTER_VEW 0x054e #define UNITEXT_ARMENIAN_CAPITAL_LETTER_VEW L"\u054e" #define UNICODE_ARMENIAN_CAPITAL_LETTER_TIWN 0x054f #define UNITEXT_ARMENIAN_CAPITAL_LETTER_TIWN L"\u054f" #define UNICODE_ARMENIAN_CAPITAL_LETTER_REH 0x0550 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_REH L"\u0550" #define UNICODE_ARMENIAN_CAPITAL_LETTER_CO 0x0551 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_CO L"\u0551" #define UNICODE_ARMENIAN_CAPITAL_LETTER_YIWN 0x0552 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_YIWN L"\u0552" #define UNICODE_ARMENIAN_CAPITAL_LETTER_PIWR 0x0553 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_PIWR L"\u0553" #define UNICODE_ARMENIAN_CAPITAL_LETTER_KEH 0x0554 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_KEH L"\u0554" #define UNICODE_ARMENIAN_CAPITAL_LETTER_OH 0x0555 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_OH L"\u0555" #define UNICODE_ARMENIAN_CAPITAL_LETTER_FEH 0x0556 #define UNITEXT_ARMENIAN_CAPITAL_LETTER_FEH L"\u0556" #define UNICODE_ARMENIAN_MODIFIER_LETTER_LEFT_HALF_RING 0x0559 #define UNITEXT_ARMENIAN_MODIFIER_LETTER_LEFT_HALF_RING L"\u0559" #define UNICODE_ARMENIAN_APOSTROPHE 0x055a #define UNITEXT_ARMENIAN_APOSTROPHE L"\u055a" #define UNICODE_ARMENIAN_EMPHASIS_MARK 0x055b #define UNITEXT_ARMENIAN_EMPHASIS_MARK L"\u055b" #define UNICODE_ARMENIAN_EXCLAMATION_MARK 0x055c #define UNITEXT_ARMENIAN_EXCLAMATION_MARK L"\u055c" #define UNICODE_ARMENIAN_COMMA 0x055d #define UNITEXT_ARMENIAN_COMMA L"\u055d" #define UNICODE_ARMENIAN_QUESTION_MARK 0x055e #define UNITEXT_ARMENIAN_QUESTION_MARK L"\u055e" #define UNICODE_ARMENIAN_ABBREVIATION_MARK 0x055f #define UNITEXT_ARMENIAN_ABBREVIATION_MARK L"\u055f" #define UNICODE_ARMENIAN_SMALL_LETTER_AYB 0x0561 #define UNITEXT_ARMENIAN_SMALL_LETTER_AYB L"\u0561" #define UNICODE_ARMENIAN_SMALL_LETTER_BEN 0x0562 #define UNITEXT_ARMENIAN_SMALL_LETTER_BEN L"\u0562" #define UNICODE_ARMENIAN_SMALL_LETTER_GIM 0x0563 #define UNITEXT_ARMENIAN_SMALL_LETTER_GIM L"\u0563" #define UNICODE_ARMENIAN_SMALL_LETTER_DA 0x0564 #define UNITEXT_ARMENIAN_SMALL_LETTER_DA L"\u0564" #define UNICODE_ARMENIAN_SMALL_LETTER_ECH 0x0565 #define UNITEXT_ARMENIAN_SMALL_LETTER_ECH L"\u0565" #define UNICODE_ARMENIAN_SMALL_LETTER_ZA 0x0566 #define UNITEXT_ARMENIAN_SMALL_LETTER_ZA L"\u0566" #define UNICODE_ARMENIAN_SMALL_LETTER_EH 0x0567 #define UNITEXT_ARMENIAN_SMALL_LETTER_EH L"\u0567" #define UNICODE_ARMENIAN_SMALL_LETTER_ET 0x0568 #define UNITEXT_ARMENIAN_SMALL_LETTER_ET L"\u0568" #define UNICODE_ARMENIAN_SMALL_LETTER_TO 0x0569 #define UNITEXT_ARMENIAN_SMALL_LETTER_TO L"\u0569" #define UNICODE_ARMENIAN_SMALL_LETTER_ZHE 0x056a #define UNITEXT_ARMENIAN_SMALL_LETTER_ZHE L"\u056a" #define UNICODE_ARMENIAN_SMALL_LETTER_INI 0x056b #define UNITEXT_ARMENIAN_SMALL_LETTER_INI L"\u056b" #define UNICODE_ARMENIAN_SMALL_LETTER_LIWN 0x056c #define UNITEXT_ARMENIAN_SMALL_LETTER_LIWN L"\u056c" #define UNICODE_ARMENIAN_SMALL_LETTER_XEH 0x056d #define UNITEXT_ARMENIAN_SMALL_LETTER_XEH L"\u056d" #define UNICODE_ARMENIAN_SMALL_LETTER_CA 0x056e #define UNITEXT_ARMENIAN_SMALL_LETTER_CA L"\u056e" #define UNICODE_ARMENIAN_SMALL_LETTER_KEN 0x056f #define UNITEXT_ARMENIAN_SMALL_LETTER_KEN L"\u056f" #define UNICODE_ARMENIAN_SMALL_LETTER_HO 0x0570 #define UNITEXT_ARMENIAN_SMALL_LETTER_HO L"\u0570" #define UNICODE_ARMENIAN_SMALL_LETTER_JA 0x0571 #define UNITEXT_ARMENIAN_SMALL_LETTER_JA L"\u0571" #define UNICODE_ARMENIAN_SMALL_LETTER_GHAD 0x0572 #define UNITEXT_ARMENIAN_SMALL_LETTER_GHAD L"\u0572" #define UNICODE_ARMENIAN_SMALL_LETTER_CHEH 0x0573 #define UNITEXT_ARMENIAN_SMALL_LETTER_CHEH L"\u0573" #define UNICODE_ARMENIAN_SMALL_LETTER_MEN 0x0574 #define UNITEXT_ARMENIAN_SMALL_LETTER_MEN L"\u0574" #define UNICODE_ARMENIAN_SMALL_LETTER_YI 0x0575 #define UNITEXT_ARMENIAN_SMALL_LETTER_YI L"\u0575" #define UNICODE_ARMENIAN_SMALL_LETTER_NOW 0x0576 #define UNITEXT_ARMENIAN_SMALL_LETTER_NOW L"\u0576" #define UNICODE_ARMENIAN_SMALL_LETTER_SHA 0x0577 #define UNITEXT_ARMENIAN_SMALL_LETTER_SHA L"\u0577" #define UNICODE_ARMENIAN_SMALL_LETTER_VO 0x0578 #define UNITEXT_ARMENIAN_SMALL_LETTER_VO L"\u0578" #define UNICODE_ARMENIAN_SMALL_LETTER_CHA 0x0579 #define UNITEXT_ARMENIAN_SMALL_LETTER_CHA L"\u0579" #define UNICODE_ARMENIAN_SMALL_LETTER_PEH 0x057a #define UNITEXT_ARMENIAN_SMALL_LETTER_PEH L"\u057a" #define UNICODE_ARMENIAN_SMALL_LETTER_JHEH 0x057b #define UNITEXT_ARMENIAN_SMALL_LETTER_JHEH L"\u057b" #define UNICODE_ARMENIAN_SMALL_LETTER_RA 0x057c #define UNITEXT_ARMENIAN_SMALL_LETTER_RA L"\u057c" #define UNICODE_ARMENIAN_SMALL_LETTER_SEH 0x057d #define UNITEXT_ARMENIAN_SMALL_LETTER_SEH L"\u057d" #define UNICODE_ARMENIAN_SMALL_LETTER_VEW 0x057e #define UNITEXT_ARMENIAN_SMALL_LETTER_VEW L"\u057e" #define UNICODE_ARMENIAN_SMALL_LETTER_TIWN 0x057f #define UNITEXT_ARMENIAN_SMALL_LETTER_TIWN L"\u057f" #define UNICODE_ARMENIAN_SMALL_LETTER_REH 0x0580 #define UNITEXT_ARMENIAN_SMALL_LETTER_REH L"\u0580" #define UNICODE_ARMENIAN_SMALL_LETTER_CO 0x0581 #define UNITEXT_ARMENIAN_SMALL_LETTER_CO L"\u0581" #define UNICODE_ARMENIAN_SMALL_LETTER_YIWN 0x0582 #define UNITEXT_ARMENIAN_SMALL_LETTER_YIWN L"\u0582" #define UNICODE_ARMENIAN_SMALL_LETTER_PIWR 0x0583 #define UNITEXT_ARMENIAN_SMALL_LETTER_PIWR L"\u0583" #define UNICODE_ARMENIAN_SMALL_LETTER_KEH 0x0584 #define UNITEXT_ARMENIAN_SMALL_LETTER_KEH L"\u0584" #define UNICODE_ARMENIAN_SMALL_LETTER_OH 0x0585 #define UNITEXT_ARMENIAN_SMALL_LETTER_OH L"\u0585" #define UNICODE_ARMENIAN_SMALL_LETTER_FEH 0x0586 #define UNITEXT_ARMENIAN_SMALL_LETTER_FEH L"\u0586" #define UNICODE_ARMENIAN_SMALL_LIGATURE_ECH_YIWN 0x0587 #define UNITEXT_ARMENIAN_SMALL_LIGATURE_ECH_YIWN L"\u0587" #define UNICODE_ARMENIAN_FULL_STOP 0x0589 #define UNITEXT_ARMENIAN_FULL_STOP L"\u0589" #define UNICODE_ARMENIAN_HYPHEN 0x058a #define UNITEXT_ARMENIAN_HYPHEN L"\u058a" #define UNICODE_HEBREW_ACCENT_ETNAHTA 0x0591 #define UNITEXT_HEBREW_ACCENT_ETNAHTA L"\u0591" #define UNICODE_HEBREW_ACCENT_SEGOL 0x0592 #define UNITEXT_HEBREW_ACCENT_SEGOL L"\u0592" #define UNICODE_HEBREW_ACCENT_SHALSHELET 0x0593 #define UNITEXT_HEBREW_ACCENT_SHALSHELET L"\u0593" #define UNICODE_HEBREW_ACCENT_ZAQEF_QATAN 0x0594 #define UNITEXT_HEBREW_ACCENT_ZAQEF_QATAN L"\u0594" #define UNICODE_HEBREW_ACCENT_ZAQEF_GADOL 0x0595 #define UNITEXT_HEBREW_ACCENT_ZAQEF_GADOL L"\u0595" #define UNICODE_HEBREW_ACCENT_TIPEHA 0x0596 #define UNITEXT_HEBREW_ACCENT_TIPEHA L"\u0596" #define UNICODE_HEBREW_ACCENT_REVIA 0x0597 #define UNITEXT_HEBREW_ACCENT_REVIA L"\u0597" #define UNICODE_HEBREW_ACCENT_ZARQA 0x0598 #define UNITEXT_HEBREW_ACCENT_ZARQA L"\u0598" #define UNICODE_HEBREW_ACCENT_PASHTA 0x0599 #define UNITEXT_HEBREW_ACCENT_PASHTA L"\u0599" #define UNICODE_HEBREW_ACCENT_YETIV 0x059a #define UNITEXT_HEBREW_ACCENT_YETIV L"\u059a" #define UNICODE_HEBREW_ACCENT_TEVIR 0x059b #define UNITEXT_HEBREW_ACCENT_TEVIR L"\u059b" #define UNICODE_HEBREW_ACCENT_GERESH 0x059c #define UNITEXT_HEBREW_ACCENT_GERESH L"\u059c" #define UNICODE_HEBREW_ACCENT_GERESH_MUQDAM 0x059d #define UNITEXT_HEBREW_ACCENT_GERESH_MUQDAM L"\u059d" #define UNICODE_HEBREW_ACCENT_GERSHAYIM 0x059e #define UNITEXT_HEBREW_ACCENT_GERSHAYIM L"\u059e" #define UNICODE_HEBREW_ACCENT_QARNEY_PARA 0x059f #define UNITEXT_HEBREW_ACCENT_QARNEY_PARA L"\u059f" #define UNICODE_HEBREW_ACCENT_TELISHA_GEDOLA 0x05a0 #define UNITEXT_HEBREW_ACCENT_TELISHA_GEDOLA L"\u05a0" #define UNICODE_HEBREW_ACCENT_PAZER 0x05a1 #define UNITEXT_HEBREW_ACCENT_PAZER L"\u05a1" #define UNICODE_HEBREW_ACCENT_ATNAH_HAFUKH 0x05a2 #define UNITEXT_HEBREW_ACCENT_ATNAH_HAFUKH L"\u05a2" #define UNICODE_HEBREW_ACCENT_MUNAH 0x05a3 #define UNITEXT_HEBREW_ACCENT_MUNAH L"\u05a3" #define UNICODE_HEBREW_ACCENT_MAHAPAKH 0x05a4 #define UNITEXT_HEBREW_ACCENT_MAHAPAKH L"\u05a4" #define UNICODE_HEBREW_ACCENT_MERKHA 0x05a5 #define UNITEXT_HEBREW_ACCENT_MERKHA L"\u05a5" #define UNICODE_HEBREW_ACCENT_MERKHA_KEFULA 0x05a6 #define UNITEXT_HEBREW_ACCENT_MERKHA_KEFULA L"\u05a6" #define UNICODE_HEBREW_ACCENT_DARGA 0x05a7 #define UNITEXT_HEBREW_ACCENT_DARGA L"\u05a7" #define UNICODE_HEBREW_ACCENT_QADMA 0x05a8 #define UNITEXT_HEBREW_ACCENT_QADMA L"\u05a8" #define UNICODE_HEBREW_ACCENT_TELISHA_QETANA 0x05a9 #define UNITEXT_HEBREW_ACCENT_TELISHA_QETANA L"\u05a9" #define UNICODE_HEBREW_ACCENT_YERAH_BEN_YOMO 0x05aa #define UNITEXT_HEBREW_ACCENT_YERAH_BEN_YOMO L"\u05aa" #define UNICODE_HEBREW_ACCENT_OLE 0x05ab #define UNITEXT_HEBREW_ACCENT_OLE L"\u05ab" #define UNICODE_HEBREW_ACCENT_ILUY 0x05ac #define UNITEXT_HEBREW_ACCENT_ILUY L"\u05ac" #define UNICODE_HEBREW_ACCENT_DEHI 0x05ad #define UNITEXT_HEBREW_ACCENT_DEHI L"\u05ad" #define UNICODE_HEBREW_ACCENT_ZINOR 0x05ae #define UNITEXT_HEBREW_ACCENT_ZINOR L"\u05ae" #define UNICODE_HEBREW_MARK_MASORA_CIRCLE 0x05af #define UNITEXT_HEBREW_MARK_MASORA_CIRCLE L"\u05af" #define UNICODE_HEBREW_POINT_SHEVA 0x05b0 #define UNITEXT_HEBREW_POINT_SHEVA L"\u05b0" #define UNICODE_HEBREW_POINT_HATAF_SEGOL 0x05b1 #define UNITEXT_HEBREW_POINT_HATAF_SEGOL L"\u05b1" #define UNICODE_HEBREW_POINT_HATAF_PATAH 0x05b2 #define UNITEXT_HEBREW_POINT_HATAF_PATAH L"\u05b2" #define UNICODE_HEBREW_POINT_HATAF_QAMATS 0x05b3 #define UNITEXT_HEBREW_POINT_HATAF_QAMATS L"\u05b3" #define UNICODE_HEBREW_POINT_HIRIQ 0x05b4 #define UNITEXT_HEBREW_POINT_HIRIQ L"\u05b4" #define UNICODE_HEBREW_POINT_TSERE 0x05b5 #define UNITEXT_HEBREW_POINT_TSERE L"\u05b5" #define UNICODE_HEBREW_POINT_SEGOL 0x05b6 #define UNITEXT_HEBREW_POINT_SEGOL L"\u05b6" #define UNICODE_HEBREW_POINT_PATAH 0x05b7 #define UNITEXT_HEBREW_POINT_PATAH L"\u05b7" #define UNICODE_HEBREW_POINT_QAMATS 0x05b8 #define UNITEXT_HEBREW_POINT_QAMATS L"\u05b8" #define UNICODE_HEBREW_POINT_HOLAM 0x05b9 #define UNITEXT_HEBREW_POINT_HOLAM L"\u05b9" #define UNICODE_HEBREW_POINT_HOLAM_HASER_FOR_VAV 0x05ba #define UNITEXT_HEBREW_POINT_HOLAM_HASER_FOR_VAV L"\u05ba" #define UNICODE_HEBREW_POINT_QUBUTS 0x05bb #define UNITEXT_HEBREW_POINT_QUBUTS L"\u05bb" #define UNICODE_HEBREW_POINT_DAGESH_OR_MAPIQ 0x05bc #define UNITEXT_HEBREW_POINT_DAGESH_OR_MAPIQ L"\u05bc" #define UNICODE_HEBREW_POINT_METEG 0x05bd #define UNITEXT_HEBREW_POINT_METEG L"\u05bd" #define UNICODE_HEBREW_PUNCTUATION_MAQAF 0x05be #define UNITEXT_HEBREW_PUNCTUATION_MAQAF L"\u05be" #define UNICODE_HEBREW_POINT_RAFE 0x05bf #define UNITEXT_HEBREW_POINT_RAFE L"\u05bf" #define UNICODE_HEBREW_PUNCTUATION_PASEQ 0x05c0 #define UNITEXT_HEBREW_PUNCTUATION_PASEQ L"\u05c0" #define UNICODE_HEBREW_POINT_SHIN_DOT 0x05c1 #define UNITEXT_HEBREW_POINT_SHIN_DOT L"\u05c1" #define UNICODE_HEBREW_POINT_SIN_DOT 0x05c2 #define UNITEXT_HEBREW_POINT_SIN_DOT L"\u05c2" #define UNICODE_HEBREW_PUNCTUATION_SOF_PASUQ 0x05c3 #define UNITEXT_HEBREW_PUNCTUATION_SOF_PASUQ L"\u05c3" #define UNICODE_HEBREW_MARK_UPPER_DOT 0x05c4 #define UNITEXT_HEBREW_MARK_UPPER_DOT L"\u05c4" #define UNICODE_HEBREW_MARK_LOWER_DOT 0x05c5 #define UNITEXT_HEBREW_MARK_LOWER_DOT L"\u05c5" #define UNICODE_HEBREW_PUNCTUATION_NUN_HAFUKHA 0x05c6 #define UNITEXT_HEBREW_PUNCTUATION_NUN_HAFUKHA L"\u05c6" #define UNICODE_HEBREW_POINT_QAMATS_QATAN 0x05c7 #define UNITEXT_HEBREW_POINT_QAMATS_QATAN L"\u05c7" #define UNICODE_HEBREW_LETTER_ALEF 0x05d0 #define UNITEXT_HEBREW_LETTER_ALEF L"\u05d0" #define UNICODE_HEBREW_LETTER_BET 0x05d1 #define UNITEXT_HEBREW_LETTER_BET L"\u05d1" #define UNICODE_HEBREW_LETTER_GIMEL 0x05d2 #define UNITEXT_HEBREW_LETTER_GIMEL L"\u05d2" #define UNICODE_HEBREW_LETTER_DALET 0x05d3 #define UNITEXT_HEBREW_LETTER_DALET L"\u05d3" #define UNICODE_HEBREW_LETTER_HE 0x05d4 #define UNITEXT_HEBREW_LETTER_HE L"\u05d4" #define UNICODE_HEBREW_LETTER_VAV 0x05d5 #define UNITEXT_HEBREW_LETTER_VAV L"\u05d5" #define UNICODE_HEBREW_LETTER_ZAYIN 0x05d6 #define UNITEXT_HEBREW_LETTER_ZAYIN L"\u05d6" #define UNICODE_HEBREW_LETTER_HET 0x05d7 #define UNITEXT_HEBREW_LETTER_HET L"\u05d7" #define UNICODE_HEBREW_LETTER_TET 0x05d8 #define UNITEXT_HEBREW_LETTER_TET L"\u05d8" #define UNICODE_HEBREW_LETTER_YOD 0x05d9 #define UNITEXT_HEBREW_LETTER_YOD L"\u05d9" #define UNICODE_HEBREW_LETTER_FINAL_KAF 0x05da #define UNITEXT_HEBREW_LETTER_FINAL_KAF L"\u05da" #define UNICODE_HEBREW_LETTER_KAF 0x05db #define UNITEXT_HEBREW_LETTER_KAF L"\u05db" #define UNICODE_HEBREW_LETTER_LAMED 0x05dc #define UNITEXT_HEBREW_LETTER_LAMED L"\u05dc" #define UNICODE_HEBREW_LETTER_FINAL_MEM 0x05dd #define UNITEXT_HEBREW_LETTER_FINAL_MEM L"\u05dd" #define UNICODE_HEBREW_LETTER_MEM 0x05de #define UNITEXT_HEBREW_LETTER_MEM L"\u05de" #define UNICODE_HEBREW_LETTER_FINAL_NUN 0x05df #define UNITEXT_HEBREW_LETTER_FINAL_NUN L"\u05df" #define UNICODE_HEBREW_LETTER_NUN 0x05e0 #define UNITEXT_HEBREW_LETTER_NUN L"\u05e0" #define UNICODE_HEBREW_LETTER_SAMEKH 0x05e1 #define UNITEXT_HEBREW_LETTER_SAMEKH L"\u05e1" #define UNICODE_HEBREW_LETTER_AYIN 0x05e2 #define UNITEXT_HEBREW_LETTER_AYIN L"\u05e2" #define UNICODE_HEBREW_LETTER_FINAL_PE 0x05e3 #define UNITEXT_HEBREW_LETTER_FINAL_PE L"\u05e3" #define UNICODE_HEBREW_LETTER_PE 0x05e4 #define UNITEXT_HEBREW_LETTER_PE L"\u05e4" #define UNICODE_HEBREW_LETTER_FINAL_TSADI 0x05e5 #define UNITEXT_HEBREW_LETTER_FINAL_TSADI L"\u05e5" #define UNICODE_HEBREW_LETTER_TSADI 0x05e6 #define UNITEXT_HEBREW_LETTER_TSADI L"\u05e6" #define UNICODE_HEBREW_LETTER_QOF 0x05e7 #define UNITEXT_HEBREW_LETTER_QOF L"\u05e7" #define UNICODE_HEBREW_LETTER_RESH 0x05e8 #define UNITEXT_HEBREW_LETTER_RESH L"\u05e8" #define UNICODE_HEBREW_LETTER_SHIN 0x05e9 #define UNITEXT_HEBREW_LETTER_SHIN L"\u05e9" #define UNICODE_HEBREW_LETTER_TAV 0x05ea #define UNITEXT_HEBREW_LETTER_TAV L"\u05ea" #define UNICODE_HEBREW_LIGATURE_YIDDISH_DOUBLE_VAV 0x05f0 #define UNITEXT_HEBREW_LIGATURE_YIDDISH_DOUBLE_VAV L"\u05f0" #define UNICODE_HEBREW_LIGATURE_YIDDISH_VAV_YOD 0x05f1 #define UNITEXT_HEBREW_LIGATURE_YIDDISH_VAV_YOD L"\u05f1" #define UNICODE_HEBREW_LIGATURE_YIDDISH_DOUBLE_YOD 0x05f2 #define UNITEXT_HEBREW_LIGATURE_YIDDISH_DOUBLE_YOD L"\u05f2" #define UNICODE_HEBREW_PUNCTUATION_GERESH 0x05f3 #define UNITEXT_HEBREW_PUNCTUATION_GERESH L"\u05f3" #define UNICODE_HEBREW_PUNCTUATION_GERSHAYIM 0x05f4 #define UNITEXT_HEBREW_PUNCTUATION_GERSHAYIM L"\u05f4" #define UNICODE_ARABIC_NUMBER_SIGN 0x0600 #define UNITEXT_ARABIC_NUMBER_SIGN L"\u0600" #define UNICODE_ARABIC_SIGN_SANAH 0x0601 #define UNITEXT_ARABIC_SIGN_SANAH L"\u0601" #define UNICODE_ARABIC_FOOTNOTE_MARKER 0x0602 #define UNITEXT_ARABIC_FOOTNOTE_MARKER L"\u0602" #define UNICODE_ARABIC_SIGN_SAFHA 0x0603 #define UNITEXT_ARABIC_SIGN_SAFHA L"\u0603" #define UNICODE_AFGHANI_SIGN 0x060b #define UNITEXT_AFGHANI_SIGN L"\u060b" #define UNICODE_ARABIC_COMMA 0x060c #define UNITEXT_ARABIC_COMMA L"\u060c" #define UNICODE_ARABIC_DATE_SEPARATOR 0x060d #define UNITEXT_ARABIC_DATE_SEPARATOR L"\u060d" #define UNICODE_ARABIC_POETIC_VERSE_SIGN 0x060e #define UNITEXT_ARABIC_POETIC_VERSE_SIGN L"\u060e" #define UNICODE_ARABIC_SIGN_MISRA 0x060f #define UNITEXT_ARABIC_SIGN_MISRA L"\u060f" #define UNICODE_ARABIC_SIGN_SALLALLAHOU_ALAYHE_WASSALLAM 0x0610 #define UNITEXT_ARABIC_SIGN_SALLALLAHOU_ALAYHE_WASSALLAM L"\u0610" #define UNICODE_ARABIC_SIGN_ALAYHE_ASSALLAM 0x0611 #define UNITEXT_ARABIC_SIGN_ALAYHE_ASSALLAM L"\u0611" #define UNICODE_ARABIC_SIGN_RAHMATULLAH_ALAYHE 0x0612 #define UNITEXT_ARABIC_SIGN_RAHMATULLAH_ALAYHE L"\u0612" #define UNICODE_ARABIC_SIGN_RADI_ALLAHOU_ANHU 0x0613 #define UNITEXT_ARABIC_SIGN_RADI_ALLAHOU_ANHU L"\u0613" #define UNICODE_ARABIC_SIGN_TAKHALLUS 0x0614 #define UNITEXT_ARABIC_SIGN_TAKHALLUS L"\u0614" #define UNICODE_ARABIC_SMALL_HIGH_TAH 0x0615 #define UNITEXT_ARABIC_SMALL_HIGH_TAH L"\u0615" #define UNICODE_ARABIC_SEMICOLON 0x061b #define UNITEXT_ARABIC_SEMICOLON L"\u061b" #define UNICODE_ARABIC_TRIPLE_DOT_PUNCTUATION_MARK 0x061e #define UNITEXT_ARABIC_TRIPLE_DOT_PUNCTUATION_MARK L"\u061e" #define UNICODE_ARABIC_QUESTION_MARK 0x061f #define UNITEXT_ARABIC_QUESTION_MARK L"\u061f" #define UNICODE_ARABIC_LETTER_HAMZA 0x0621 #define UNITEXT_ARABIC_LETTER_HAMZA L"\u0621" #define UNICODE_ARABIC_LETTER_ALEF_WITH_MADDA_ABOVE 0x0622 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_MADDA_ABOVE L"\u0622" #define UNICODE_ARABIC_LETTER_ALEF_WITH_HAMZA_ABOVE 0x0623 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_HAMZA_ABOVE L"\u0623" #define UNICODE_ARABIC_LETTER_WAW_WITH_HAMZA_ABOVE 0x0624 #define UNITEXT_ARABIC_LETTER_WAW_WITH_HAMZA_ABOVE L"\u0624" #define UNICODE_ARABIC_LETTER_ALEF_WITH_HAMZA_BELOW 0x0625 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_HAMZA_BELOW L"\u0625" #define UNICODE_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE 0x0626 #define UNITEXT_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE L"\u0626" #define UNICODE_ARABIC_LETTER_ALEF 0x0627 #define UNITEXT_ARABIC_LETTER_ALEF L"\u0627" #define UNICODE_ARABIC_LETTER_BEH 0x0628 #define UNITEXT_ARABIC_LETTER_BEH L"\u0628" #define UNICODE_ARABIC_LETTER_TEH_MARBUTA 0x0629 #define UNITEXT_ARABIC_LETTER_TEH_MARBUTA L"\u0629" #define UNICODE_ARABIC_LETTER_TEH 0x062a #define UNITEXT_ARABIC_LETTER_TEH L"\u062a" #define UNICODE_ARABIC_LETTER_THEH 0x062b #define UNITEXT_ARABIC_LETTER_THEH L"\u062b" #define UNICODE_ARABIC_LETTER_JEEM 0x062c #define UNITEXT_ARABIC_LETTER_JEEM L"\u062c" #define UNICODE_ARABIC_LETTER_HAH 0x062d #define UNITEXT_ARABIC_LETTER_HAH L"\u062d" #define UNICODE_ARABIC_LETTER_KHAH 0x062e #define UNITEXT_ARABIC_LETTER_KHAH L"\u062e" #define UNICODE_ARABIC_LETTER_DAL 0x062f #define UNITEXT_ARABIC_LETTER_DAL L"\u062f" #define UNICODE_ARABIC_LETTER_THAL 0x0630 #define UNITEXT_ARABIC_LETTER_THAL L"\u0630" #define UNICODE_ARABIC_LETTER_REH 0x0631 #define UNITEXT_ARABIC_LETTER_REH L"\u0631" #define UNICODE_ARABIC_LETTER_ZAIN 0x0632 #define UNITEXT_ARABIC_LETTER_ZAIN L"\u0632" #define UNICODE_ARABIC_LETTER_SEEN 0x0633 #define UNITEXT_ARABIC_LETTER_SEEN L"\u0633" #define UNICODE_ARABIC_LETTER_SHEEN 0x0634 #define UNITEXT_ARABIC_LETTER_SHEEN L"\u0634" #define UNICODE_ARABIC_LETTER_SAD 0x0635 #define UNITEXT_ARABIC_LETTER_SAD L"\u0635" #define UNICODE_ARABIC_LETTER_DAD 0x0636 #define UNITEXT_ARABIC_LETTER_DAD L"\u0636" #define UNICODE_ARABIC_LETTER_TAH 0x0637 #define UNITEXT_ARABIC_LETTER_TAH L"\u0637" #define UNICODE_ARABIC_LETTER_ZAH 0x0638 #define UNITEXT_ARABIC_LETTER_ZAH L"\u0638" #define UNICODE_ARABIC_LETTER_AIN 0x0639 #define UNITEXT_ARABIC_LETTER_AIN L"\u0639" #define UNICODE_ARABIC_LETTER_GHAIN 0x063a #define UNITEXT_ARABIC_LETTER_GHAIN L"\u063a" #define UNICODE_ARABIC_TATWEEL 0x0640 #define UNITEXT_ARABIC_TATWEEL L"\u0640" #define UNICODE_ARABIC_LETTER_FEH 0x0641 #define UNITEXT_ARABIC_LETTER_FEH L"\u0641" #define UNICODE_ARABIC_LETTER_QAF 0x0642 #define UNITEXT_ARABIC_LETTER_QAF L"\u0642" #define UNICODE_ARABIC_LETTER_KAF 0x0643 #define UNITEXT_ARABIC_LETTER_KAF L"\u0643" #define UNICODE_ARABIC_LETTER_LAM 0x0644 #define UNITEXT_ARABIC_LETTER_LAM L"\u0644" #define UNICODE_ARABIC_LETTER_MEEM 0x0645 #define UNITEXT_ARABIC_LETTER_MEEM L"\u0645" #define UNICODE_ARABIC_LETTER_NOON 0x0646 #define UNITEXT_ARABIC_LETTER_NOON L"\u0646" #define UNICODE_ARABIC_LETTER_HEH 0x0647 #define UNITEXT_ARABIC_LETTER_HEH L"\u0647" #define UNICODE_ARABIC_LETTER_WAW 0x0648 #define UNITEXT_ARABIC_LETTER_WAW L"\u0648" #define UNICODE_ARABIC_LETTER_ALEF_MAKSURA 0x0649 #define UNITEXT_ARABIC_LETTER_ALEF_MAKSURA L"\u0649" #define UNICODE_ARABIC_LETTER_YEH 0x064a #define UNITEXT_ARABIC_LETTER_YEH L"\u064a" #define UNICODE_ARABIC_FATHATAN 0x064b #define UNITEXT_ARABIC_FATHATAN L"\u064b" #define UNICODE_ARABIC_DAMMATAN 0x064c #define UNITEXT_ARABIC_DAMMATAN L"\u064c" #define UNICODE_ARABIC_KASRATAN 0x064d #define UNITEXT_ARABIC_KASRATAN L"\u064d" #define UNICODE_ARABIC_FATHA 0x064e #define UNITEXT_ARABIC_FATHA L"\u064e" #define UNICODE_ARABIC_DAMMA 0x064f #define UNITEXT_ARABIC_DAMMA L"\u064f" #define UNICODE_ARABIC_KASRA 0x0650 #define UNITEXT_ARABIC_KASRA L"\u0650" #define UNICODE_ARABIC_SHADDA 0x0651 #define UNITEXT_ARABIC_SHADDA L"\u0651" #define UNICODE_ARABIC_SUKUN 0x0652 #define UNITEXT_ARABIC_SUKUN L"\u0652" #define UNICODE_ARABIC_MADDAH_ABOVE 0x0653 #define UNITEXT_ARABIC_MADDAH_ABOVE L"\u0653" #define UNICODE_ARABIC_HAMZA_ABOVE 0x0654 #define UNITEXT_ARABIC_HAMZA_ABOVE L"\u0654" #define UNICODE_ARABIC_HAMZA_BELOW 0x0655 #define UNITEXT_ARABIC_HAMZA_BELOW L"\u0655" #define UNICODE_ARABIC_SUBSCRIPT_ALEF 0x0656 #define UNITEXT_ARABIC_SUBSCRIPT_ALEF L"\u0656" #define UNICODE_ARABIC_INVERTED_DAMMA 0x0657 #define UNITEXT_ARABIC_INVERTED_DAMMA L"\u0657" #define UNICODE_ARABIC_MARK_NOON_GHUNNA 0x0658 #define UNITEXT_ARABIC_MARK_NOON_GHUNNA L"\u0658" #define UNICODE_ARABIC_ZWARAKAY 0x0659 #define UNITEXT_ARABIC_ZWARAKAY L"\u0659" #define UNICODE_ARABIC_VOWEL_SIGN_SMALL_V_ABOVE 0x065a #define UNITEXT_ARABIC_VOWEL_SIGN_SMALL_V_ABOVE L"\u065a" #define UNICODE_ARABIC_VOWEL_SIGN_INVERTED_SMALL_V_ABOVE 0x065b #define UNITEXT_ARABIC_VOWEL_SIGN_INVERTED_SMALL_V_ABOVE L"\u065b" #define UNICODE_ARABIC_VOWEL_SIGN_DOT_BELOW 0x065c #define UNITEXT_ARABIC_VOWEL_SIGN_DOT_BELOW L"\u065c" #define UNICODE_ARABIC_REVERSED_DAMMA 0x065d #define UNITEXT_ARABIC_REVERSED_DAMMA L"\u065d" #define UNICODE_ARABIC_FATHA_WITH_TWO_DOTS 0x065e #define UNITEXT_ARABIC_FATHA_WITH_TWO_DOTS L"\u065e" #define UNICODE_ARABIC_INDIC_DIGIT_ZERO 0x0660 #define UNITEXT_ARABIC_INDIC_DIGIT_ZERO L"\u0660" #define UNICODE_ARABIC_INDIC_DIGIT_ONE 0x0661 #define UNITEXT_ARABIC_INDIC_DIGIT_ONE L"\u0661" #define UNICODE_ARABIC_INDIC_DIGIT_TWO 0x0662 #define UNITEXT_ARABIC_INDIC_DIGIT_TWO L"\u0662" #define UNICODE_ARABIC_INDIC_DIGIT_THREE 0x0663 #define UNITEXT_ARABIC_INDIC_DIGIT_THREE L"\u0663" #define UNICODE_ARABIC_INDIC_DIGIT_FOUR 0x0664 #define UNITEXT_ARABIC_INDIC_DIGIT_FOUR L"\u0664" #define UNICODE_ARABIC_INDIC_DIGIT_FIVE 0x0665 #define UNITEXT_ARABIC_INDIC_DIGIT_FIVE L"\u0665" #define UNICODE_ARABIC_INDIC_DIGIT_SIX 0x0666 #define UNITEXT_ARABIC_INDIC_DIGIT_SIX L"\u0666" #define UNICODE_ARABIC_INDIC_DIGIT_SEVEN 0x0667 #define UNITEXT_ARABIC_INDIC_DIGIT_SEVEN L"\u0667" #define UNICODE_ARABIC_INDIC_DIGIT_EIGHT 0x0668 #define UNITEXT_ARABIC_INDIC_DIGIT_EIGHT L"\u0668" #define UNICODE_ARABIC_INDIC_DIGIT_NINE 0x0669 #define UNITEXT_ARABIC_INDIC_DIGIT_NINE L"\u0669" #define UNICODE_ARABIC_PERCENT_SIGN 0x066a #define UNITEXT_ARABIC_PERCENT_SIGN L"\u066a" #define UNICODE_ARABIC_DECIMAL_SEPARATOR 0x066b #define UNITEXT_ARABIC_DECIMAL_SEPARATOR L"\u066b" #define UNICODE_ARABIC_THOUSANDS_SEPARATOR 0x066c #define UNITEXT_ARABIC_THOUSANDS_SEPARATOR L"\u066c" #define UNICODE_ARABIC_FIVE_POINTED_STAR 0x066d #define UNITEXT_ARABIC_FIVE_POINTED_STAR L"\u066d" #define UNICODE_ARABIC_LETTER_DOTLESS_BEH 0x066e #define UNITEXT_ARABIC_LETTER_DOTLESS_BEH L"\u066e" #define UNICODE_ARABIC_LETTER_DOTLESS_QAF 0x066f #define UNITEXT_ARABIC_LETTER_DOTLESS_QAF L"\u066f" #define UNICODE_ARABIC_LETTER_SUPERSCRIPT_ALEF 0x0670 #define UNITEXT_ARABIC_LETTER_SUPERSCRIPT_ALEF L"\u0670" #define UNICODE_ARABIC_LETTER_ALEF_WASLA 0x0671 #define UNITEXT_ARABIC_LETTER_ALEF_WASLA L"\u0671" #define UNICODE_ARABIC_LETTER_ALEF_WITH_WAVY_HAMZA_ABOVE 0x0672 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_WAVY_HAMZA_ABOVE L"\u0672" #define UNICODE_ARABIC_LETTER_ALEF_WITH_WAVY_HAMZA_BELOW 0x0673 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_WAVY_HAMZA_BELOW L"\u0673" #define UNICODE_ARABIC_LETTER_HIGH_HAMZA 0x0674 #define UNITEXT_ARABIC_LETTER_HIGH_HAMZA L"\u0674" #define UNICODE_ARABIC_LETTER_HIGH_HAMZA_ALEF 0x0675 #define UNITEXT_ARABIC_LETTER_HIGH_HAMZA_ALEF L"\u0675" #define UNICODE_ARABIC_LETTER_HIGH_HAMZA_WAW 0x0676 #define UNITEXT_ARABIC_LETTER_HIGH_HAMZA_WAW L"\u0676" #define UNICODE_ARABIC_LETTER_U_WITH_HAMZA_ABOVE 0x0677 #define UNITEXT_ARABIC_LETTER_U_WITH_HAMZA_ABOVE L"\u0677" #define UNICODE_ARABIC_LETTER_HIGH_HAMZA_YEH 0x0678 #define UNITEXT_ARABIC_LETTER_HIGH_HAMZA_YEH L"\u0678" #define UNICODE_ARABIC_LETTER_TTEH 0x0679 #define UNITEXT_ARABIC_LETTER_TTEH L"\u0679" #define UNICODE_ARABIC_LETTER_TTEHEH 0x067a #define UNITEXT_ARABIC_LETTER_TTEHEH L"\u067a" #define UNICODE_ARABIC_LETTER_BEEH 0x067b #define UNITEXT_ARABIC_LETTER_BEEH L"\u067b" #define UNICODE_ARABIC_LETTER_TEH_WITH_RING 0x067c #define UNITEXT_ARABIC_LETTER_TEH_WITH_RING L"\u067c" #define UNICODE_ARABIC_LETTER_TEH_WITH_THREE_DOTS_ABOVE_DOWNWARDS 0x067d #define UNITEXT_ARABIC_LETTER_TEH_WITH_THREE_DOTS_ABOVE_DOWNWARDS L"\u067d" #define UNICODE_ARABIC_LETTER_PEH 0x067e #define UNITEXT_ARABIC_LETTER_PEH L"\u067e" #define UNICODE_ARABIC_LETTER_TEHEH 0x067f #define UNITEXT_ARABIC_LETTER_TEHEH L"\u067f" #define UNICODE_ARABIC_LETTER_BEHEH 0x0680 #define UNITEXT_ARABIC_LETTER_BEHEH L"\u0680" #define UNICODE_ARABIC_LETTER_HAH_WITH_HAMZA_ABOVE 0x0681 #define UNITEXT_ARABIC_LETTER_HAH_WITH_HAMZA_ABOVE L"\u0681" #define UNICODE_ARABIC_LETTER_HAH_WITH_TWO_DOTS_VERTICAL_ABOVE 0x0682 #define UNITEXT_ARABIC_LETTER_HAH_WITH_TWO_DOTS_VERTICAL_ABOVE L"\u0682" #define UNICODE_ARABIC_LETTER_NYEH 0x0683 #define UNITEXT_ARABIC_LETTER_NYEH L"\u0683" #define UNICODE_ARABIC_LETTER_DYEH 0x0684 #define UNITEXT_ARABIC_LETTER_DYEH L"\u0684" #define UNICODE_ARABIC_LETTER_HAH_WITH_THREE_DOTS_ABOVE 0x0685 #define UNITEXT_ARABIC_LETTER_HAH_WITH_THREE_DOTS_ABOVE L"\u0685" #define UNICODE_ARABIC_LETTER_TCHEH 0x0686 #define UNITEXT_ARABIC_LETTER_TCHEH L"\u0686" #define UNICODE_ARABIC_LETTER_TCHEHEH 0x0687 #define UNITEXT_ARABIC_LETTER_TCHEHEH L"\u0687" #define UNICODE_ARABIC_LETTER_DDAL 0x0688 #define UNITEXT_ARABIC_LETTER_DDAL L"\u0688" #define UNICODE_ARABIC_LETTER_DAL_WITH_RING 0x0689 #define UNITEXT_ARABIC_LETTER_DAL_WITH_RING L"\u0689" #define UNICODE_ARABIC_LETTER_DAL_WITH_DOT_BELOW 0x068a #define UNITEXT_ARABIC_LETTER_DAL_WITH_DOT_BELOW L"\u068a" #define UNICODE_ARABIC_LETTER_DAL_WITH_DOT_BELOW_AND_SMALL_TAH 0x068b #define UNITEXT_ARABIC_LETTER_DAL_WITH_DOT_BELOW_AND_SMALL_TAH L"\u068b" #define UNICODE_ARABIC_LETTER_DAHAL 0x068c #define UNITEXT_ARABIC_LETTER_DAHAL L"\u068c" #define UNICODE_ARABIC_LETTER_DDAHAL 0x068d #define UNITEXT_ARABIC_LETTER_DDAHAL L"\u068d" #define UNICODE_ARABIC_LETTER_DUL 0x068e #define UNITEXT_ARABIC_LETTER_DUL L"\u068e" #define UNICODE_ARABIC_LETTER_DAL_WITH_THREE_DOTS_ABOVE_DOWNWARDS 0x068f #define UNITEXT_ARABIC_LETTER_DAL_WITH_THREE_DOTS_ABOVE_DOWNWARDS L"\u068f" #define UNICODE_ARABIC_LETTER_DAL_WITH_FOUR_DOTS_ABOVE 0x0690 #define UNITEXT_ARABIC_LETTER_DAL_WITH_FOUR_DOTS_ABOVE L"\u0690" #define UNICODE_ARABIC_LETTER_RREH 0x0691 #define UNITEXT_ARABIC_LETTER_RREH L"\u0691" #define UNICODE_ARABIC_LETTER_REH_WITH_SMALL_V 0x0692 #define UNITEXT_ARABIC_LETTER_REH_WITH_SMALL_V L"\u0692" #define UNICODE_ARABIC_LETTER_REH_WITH_RING 0x0693 #define UNITEXT_ARABIC_LETTER_REH_WITH_RING L"\u0693" #define UNICODE_ARABIC_LETTER_REH_WITH_DOT_BELOW 0x0694 #define UNITEXT_ARABIC_LETTER_REH_WITH_DOT_BELOW L"\u0694" #define UNICODE_ARABIC_LETTER_REH_WITH_SMALL_V_BELOW 0x0695 #define UNITEXT_ARABIC_LETTER_REH_WITH_SMALL_V_BELOW L"\u0695" #define UNICODE_ARABIC_LETTER_REH_WITH_DOT_BELOW_AND_DOT_ABOVE 0x0696 #define UNITEXT_ARABIC_LETTER_REH_WITH_DOT_BELOW_AND_DOT_ABOVE L"\u0696" #define UNICODE_ARABIC_LETTER_REH_WITH_TWO_DOTS_ABOVE 0x0697 #define UNITEXT_ARABIC_LETTER_REH_WITH_TWO_DOTS_ABOVE L"\u0697" #define UNICODE_ARABIC_LETTER_JEH 0x0698 #define UNITEXT_ARABIC_LETTER_JEH L"\u0698" #define UNICODE_ARABIC_LETTER_REH_WITH_FOUR_DOTS_ABOVE 0x0699 #define UNITEXT_ARABIC_LETTER_REH_WITH_FOUR_DOTS_ABOVE L"\u0699" #define UNICODE_ARABIC_LETTER_SEEN_WITH_DOT_BELOW_AND_DOT_ABOVE 0x069a #define UNITEXT_ARABIC_LETTER_SEEN_WITH_DOT_BELOW_AND_DOT_ABOVE L"\u069a" #define UNICODE_ARABIC_LETTER_SEEN_WITH_THREE_DOTS_BELOW 0x069b #define UNITEXT_ARABIC_LETTER_SEEN_WITH_THREE_DOTS_BELOW L"\u069b" #define UNICODE_ARABIC_LETTER_SEEN_WITH_THREE_DOTS_BELOW_AND_THREE_DOTS_ABOVE 0x069c #define UNITEXT_ARABIC_LETTER_SEEN_WITH_THREE_DOTS_BELOW_AND_THREE_DOTS_ABOVE L"\u069c" #define UNICODE_ARABIC_LETTER_SAD_WITH_TWO_DOTS_BELOW 0x069d #define UNITEXT_ARABIC_LETTER_SAD_WITH_TWO_DOTS_BELOW L"\u069d" #define UNICODE_ARABIC_LETTER_SAD_WITH_THREE_DOTS_ABOVE 0x069e #define UNITEXT_ARABIC_LETTER_SAD_WITH_THREE_DOTS_ABOVE L"\u069e" #define UNICODE_ARABIC_LETTER_TAH_WITH_THREE_DOTS_ABOVE 0x069f #define UNITEXT_ARABIC_LETTER_TAH_WITH_THREE_DOTS_ABOVE L"\u069f" #define UNICODE_ARABIC_LETTER_AIN_WITH_THREE_DOTS_ABOVE 0x06a0 #define UNITEXT_ARABIC_LETTER_AIN_WITH_THREE_DOTS_ABOVE L"\u06a0" #define UNICODE_ARABIC_LETTER_DOTLESS_FEH 0x06a1 #define UNITEXT_ARABIC_LETTER_DOTLESS_FEH L"\u06a1" #define UNICODE_ARABIC_LETTER_FEH_WITH_DOT_MOVED_BELOW 0x06a2 #define UNITEXT_ARABIC_LETTER_FEH_WITH_DOT_MOVED_BELOW L"\u06a2" #define UNICODE_ARABIC_LETTER_FEH_WITH_DOT_BELOW 0x06a3 #define UNITEXT_ARABIC_LETTER_FEH_WITH_DOT_BELOW L"\u06a3" #define UNICODE_ARABIC_LETTER_VEH 0x06a4 #define UNITEXT_ARABIC_LETTER_VEH L"\u06a4" #define UNICODE_ARABIC_LETTER_FEH_WITH_THREE_DOTS_BELOW 0x06a5 #define UNITEXT_ARABIC_LETTER_FEH_WITH_THREE_DOTS_BELOW L"\u06a5" #define UNICODE_ARABIC_LETTER_PEHEH 0x06a6 #define UNITEXT_ARABIC_LETTER_PEHEH L"\u06a6" #define UNICODE_ARABIC_LETTER_QAF_WITH_DOT_ABOVE 0x06a7 #define UNITEXT_ARABIC_LETTER_QAF_WITH_DOT_ABOVE L"\u06a7" #define UNICODE_ARABIC_LETTER_QAF_WITH_THREE_DOTS_ABOVE 0x06a8 #define UNITEXT_ARABIC_LETTER_QAF_WITH_THREE_DOTS_ABOVE L"\u06a8" #define UNICODE_ARABIC_LETTER_KEHEH 0x06a9 #define UNITEXT_ARABIC_LETTER_KEHEH L"\u06a9" #define UNICODE_ARABIC_LETTER_SWASH_KAF 0x06aa #define UNITEXT_ARABIC_LETTER_SWASH_KAF L"\u06aa" #define UNICODE_ARABIC_LETTER_KAF_WITH_RING 0x06ab #define UNITEXT_ARABIC_LETTER_KAF_WITH_RING L"\u06ab" #define UNICODE_ARABIC_LETTER_KAF_WITH_DOT_ABOVE 0x06ac #define UNITEXT_ARABIC_LETTER_KAF_WITH_DOT_ABOVE L"\u06ac" #define UNICODE_ARABIC_LETTER_NG 0x06ad #define UNITEXT_ARABIC_LETTER_NG L"\u06ad" #define UNICODE_ARABIC_LETTER_KAF_WITH_THREE_DOTS_BELOW 0x06ae #define UNITEXT_ARABIC_LETTER_KAF_WITH_THREE_DOTS_BELOW L"\u06ae" #define UNICODE_ARABIC_LETTER_GAF 0x06af #define UNITEXT_ARABIC_LETTER_GAF L"\u06af" #define UNICODE_ARABIC_LETTER_GAF_WITH_RING 0x06b0 #define UNITEXT_ARABIC_LETTER_GAF_WITH_RING L"\u06b0" #define UNICODE_ARABIC_LETTER_NGOEH 0x06b1 #define UNITEXT_ARABIC_LETTER_NGOEH L"\u06b1" #define UNICODE_ARABIC_LETTER_GAF_WITH_TWO_DOTS_BELOW 0x06b2 #define UNITEXT_ARABIC_LETTER_GAF_WITH_TWO_DOTS_BELOW L"\u06b2" #define UNICODE_ARABIC_LETTER_GUEH 0x06b3 #define UNITEXT_ARABIC_LETTER_GUEH L"\u06b3" #define UNICODE_ARABIC_LETTER_GAF_WITH_THREE_DOTS_ABOVE 0x06b4 #define UNITEXT_ARABIC_LETTER_GAF_WITH_THREE_DOTS_ABOVE L"\u06b4" #define UNICODE_ARABIC_LETTER_LAM_WITH_SMALL_V 0x06b5 #define UNITEXT_ARABIC_LETTER_LAM_WITH_SMALL_V L"\u06b5" #define UNICODE_ARABIC_LETTER_LAM_WITH_DOT_ABOVE 0x06b6 #define UNITEXT_ARABIC_LETTER_LAM_WITH_DOT_ABOVE L"\u06b6" #define UNICODE_ARABIC_LETTER_LAM_WITH_THREE_DOTS_ABOVE 0x06b7 #define UNITEXT_ARABIC_LETTER_LAM_WITH_THREE_DOTS_ABOVE L"\u06b7" #define UNICODE_ARABIC_LETTER_LAM_WITH_THREE_DOTS_BELOW 0x06b8 #define UNITEXT_ARABIC_LETTER_LAM_WITH_THREE_DOTS_BELOW L"\u06b8" #define UNICODE_ARABIC_LETTER_NOON_WITH_DOT_BELOW 0x06b9 #define UNITEXT_ARABIC_LETTER_NOON_WITH_DOT_BELOW L"\u06b9" #define UNICODE_ARABIC_LETTER_NOON_GHUNNA 0x06ba #define UNITEXT_ARABIC_LETTER_NOON_GHUNNA L"\u06ba" #define UNICODE_ARABIC_LETTER_RNOON 0x06bb #define UNITEXT_ARABIC_LETTER_RNOON L"\u06bb" #define UNICODE_ARABIC_LETTER_NOON_WITH_RING 0x06bc #define UNITEXT_ARABIC_LETTER_NOON_WITH_RING L"\u06bc" #define UNICODE_ARABIC_LETTER_NOON_WITH_THREE_DOTS_ABOVE 0x06bd #define UNITEXT_ARABIC_LETTER_NOON_WITH_THREE_DOTS_ABOVE L"\u06bd" #define UNICODE_ARABIC_LETTER_HEH_DOACHASHMEE 0x06be #define UNITEXT_ARABIC_LETTER_HEH_DOACHASHMEE L"\u06be" #define UNICODE_ARABIC_LETTER_TCHEH_WITH_DOT_ABOVE 0x06bf #define UNITEXT_ARABIC_LETTER_TCHEH_WITH_DOT_ABOVE L"\u06bf" #define UNICODE_ARABIC_LETTER_HEH_WITH_YEH_ABOVE 0x06c0 #define UNITEXT_ARABIC_LETTER_HEH_WITH_YEH_ABOVE L"\u06c0" #define UNICODE_ARABIC_LETTER_HEH_GOAL 0x06c1 #define UNITEXT_ARABIC_LETTER_HEH_GOAL L"\u06c1" #define UNICODE_ARABIC_LETTER_HEH_GOAL_WITH_HAMZA_ABOVE 0x06c2 #define UNITEXT_ARABIC_LETTER_HEH_GOAL_WITH_HAMZA_ABOVE L"\u06c2" #define UNICODE_ARABIC_LETTER_TEH_MARBUTA_GOAL 0x06c3 #define UNITEXT_ARABIC_LETTER_TEH_MARBUTA_GOAL L"\u06c3" #define UNICODE_ARABIC_LETTER_WAW_WITH_RING 0x06c4 #define UNITEXT_ARABIC_LETTER_WAW_WITH_RING L"\u06c4" #define UNICODE_ARABIC_LETTER_KIRGHIZ_OE 0x06c5 #define UNITEXT_ARABIC_LETTER_KIRGHIZ_OE L"\u06c5" #define UNICODE_ARABIC_LETTER_OE 0x06c6 #define UNITEXT_ARABIC_LETTER_OE L"\u06c6" #define UNICODE_ARABIC_LETTER_U 0x06c7 #define UNITEXT_ARABIC_LETTER_U L"\u06c7" #define UNICODE_ARABIC_LETTER_YU 0x06c8 #define UNITEXT_ARABIC_LETTER_YU L"\u06c8" #define UNICODE_ARABIC_LETTER_KIRGHIZ_YU 0x06c9 #define UNITEXT_ARABIC_LETTER_KIRGHIZ_YU L"\u06c9" #define UNICODE_ARABIC_LETTER_WAW_WITH_TWO_DOTS_ABOVE 0x06ca #define UNITEXT_ARABIC_LETTER_WAW_WITH_TWO_DOTS_ABOVE L"\u06ca" #define UNICODE_ARABIC_LETTER_VE 0x06cb #define UNITEXT_ARABIC_LETTER_VE L"\u06cb" #define UNICODE_ARABIC_LETTER_FARSI_YEH 0x06cc #define UNITEXT_ARABIC_LETTER_FARSI_YEH L"\u06cc" #define UNICODE_ARABIC_LETTER_YEH_WITH_TAIL 0x06cd #define UNITEXT_ARABIC_LETTER_YEH_WITH_TAIL L"\u06cd" #define UNICODE_ARABIC_LETTER_YEH_WITH_SMALL_V 0x06ce #define UNITEXT_ARABIC_LETTER_YEH_WITH_SMALL_V L"\u06ce" #define UNICODE_ARABIC_LETTER_WAW_WITH_DOT_ABOVE 0x06cf #define UNITEXT_ARABIC_LETTER_WAW_WITH_DOT_ABOVE L"\u06cf" #define UNICODE_ARABIC_LETTER_E 0x06d0 #define UNITEXT_ARABIC_LETTER_E L"\u06d0" #define UNICODE_ARABIC_LETTER_YEH_WITH_THREE_DOTS_BELOW 0x06d1 #define UNITEXT_ARABIC_LETTER_YEH_WITH_THREE_DOTS_BELOW L"\u06d1" #define UNICODE_ARABIC_LETTER_YEH_BARREE 0x06d2 #define UNITEXT_ARABIC_LETTER_YEH_BARREE L"\u06d2" #define UNICODE_ARABIC_LETTER_YEH_BARREE_WITH_HAMZA_ABOVE 0x06d3 #define UNITEXT_ARABIC_LETTER_YEH_BARREE_WITH_HAMZA_ABOVE L"\u06d3" #define UNICODE_ARABIC_FULL_STOP 0x06d4 #define UNITEXT_ARABIC_FULL_STOP L"\u06d4" #define UNICODE_ARABIC_LETTER_AE 0x06d5 #define UNITEXT_ARABIC_LETTER_AE L"\u06d5" #define UNICODE_ARABIC_SMALL_HIGH_LIGATURE_SAD_WITH_LAM_WITH_ALEF_MAKSURA 0x06d6 #define UNITEXT_ARABIC_SMALL_HIGH_LIGATURE_SAD_WITH_LAM_WITH_ALEF_MAKSURA L"\u06d6" #define UNICODE_ARABIC_SMALL_HIGH_LIGATURE_QAF_WITH_LAM_WITH_ALEF_MAKSURA 0x06d7 #define UNITEXT_ARABIC_SMALL_HIGH_LIGATURE_QAF_WITH_LAM_WITH_ALEF_MAKSURA L"\u06d7" #define UNICODE_ARABIC_SMALL_HIGH_MEEM_INITIAL_FORM 0x06d8 #define UNITEXT_ARABIC_SMALL_HIGH_MEEM_INITIAL_FORM L"\u06d8" #define UNICODE_ARABIC_SMALL_HIGH_LAM_ALEF 0x06d9 #define UNITEXT_ARABIC_SMALL_HIGH_LAM_ALEF L"\u06d9" #define UNICODE_ARABIC_SMALL_HIGH_JEEM 0x06da #define UNITEXT_ARABIC_SMALL_HIGH_JEEM L"\u06da" #define UNICODE_ARABIC_SMALL_HIGH_THREE_DOTS 0x06db #define UNITEXT_ARABIC_SMALL_HIGH_THREE_DOTS L"\u06db" #define UNICODE_ARABIC_SMALL_HIGH_SEEN 0x06dc #define UNITEXT_ARABIC_SMALL_HIGH_SEEN L"\u06dc" #define UNICODE_ARABIC_END_OF_AYAH 0x06dd #define UNITEXT_ARABIC_END_OF_AYAH L"\u06dd" #define UNICODE_ARABIC_START_OF_RUB_EL_HIZB 0x06de #define UNITEXT_ARABIC_START_OF_RUB_EL_HIZB L"\u06de" #define UNICODE_ARABIC_SMALL_HIGH_ROUNDED_ZERO 0x06df #define UNITEXT_ARABIC_SMALL_HIGH_ROUNDED_ZERO L"\u06df" #define UNICODE_ARABIC_SMALL_HIGH_UPRIGHT_RECTANGULAR_ZERO 0x06e0 #define UNITEXT_ARABIC_SMALL_HIGH_UPRIGHT_RECTANGULAR_ZERO L"\u06e0" #define UNICODE_ARABIC_SMALL_HIGH_DOTLESS_HEAD_OF_KHAH 0x06e1 #define UNITEXT_ARABIC_SMALL_HIGH_DOTLESS_HEAD_OF_KHAH L"\u06e1" #define UNICODE_ARABIC_SMALL_HIGH_MEEM_ISOLATED_FORM 0x06e2 #define UNITEXT_ARABIC_SMALL_HIGH_MEEM_ISOLATED_FORM L"\u06e2" #define UNICODE_ARABIC_SMALL_LOW_SEEN 0x06e3 #define UNITEXT_ARABIC_SMALL_LOW_SEEN L"\u06e3" #define UNICODE_ARABIC_SMALL_HIGH_MADDA 0x06e4 #define UNITEXT_ARABIC_SMALL_HIGH_MADDA L"\u06e4" #define UNICODE_ARABIC_SMALL_WAW 0x06e5 #define UNITEXT_ARABIC_SMALL_WAW L"\u06e5" #define UNICODE_ARABIC_SMALL_YEH 0x06e6 #define UNITEXT_ARABIC_SMALL_YEH L"\u06e6" #define UNICODE_ARABIC_SMALL_HIGH_YEH 0x06e7 #define UNITEXT_ARABIC_SMALL_HIGH_YEH L"\u06e7" #define UNICODE_ARABIC_SMALL_HIGH_NOON 0x06e8 #define UNITEXT_ARABIC_SMALL_HIGH_NOON L"\u06e8" #define UNICODE_ARABIC_PLACE_OF_SAJDAH 0x06e9 #define UNITEXT_ARABIC_PLACE_OF_SAJDAH L"\u06e9" #define UNICODE_ARABIC_EMPTY_CENTRE_LOW_STOP 0x06ea #define UNITEXT_ARABIC_EMPTY_CENTRE_LOW_STOP L"\u06ea" #define UNICODE_ARABIC_EMPTY_CENTRE_HIGH_STOP 0x06eb #define UNITEXT_ARABIC_EMPTY_CENTRE_HIGH_STOP L"\u06eb" #define UNICODE_ARABIC_ROUNDED_HIGH_STOP_WITH_FILLED_CENTRE 0x06ec #define UNITEXT_ARABIC_ROUNDED_HIGH_STOP_WITH_FILLED_CENTRE L"\u06ec" #define UNICODE_ARABIC_SMALL_LOW_MEEM 0x06ed #define UNITEXT_ARABIC_SMALL_LOW_MEEM L"\u06ed" #define UNICODE_ARABIC_LETTER_DAL_WITH_INVERTED_V 0x06ee #define UNITEXT_ARABIC_LETTER_DAL_WITH_INVERTED_V L"\u06ee" #define UNICODE_ARABIC_LETTER_REH_WITH_INVERTED_V 0x06ef #define UNITEXT_ARABIC_LETTER_REH_WITH_INVERTED_V L"\u06ef" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_ZERO 0x06f0 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_ZERO L"\u06f0" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_ONE 0x06f1 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_ONE L"\u06f1" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_TWO 0x06f2 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_TWO L"\u06f2" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_THREE 0x06f3 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_THREE L"\u06f3" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_FOUR 0x06f4 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_FOUR L"\u06f4" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_FIVE 0x06f5 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_FIVE L"\u06f5" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_SIX 0x06f6 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_SIX L"\u06f6" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_SEVEN 0x06f7 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_SEVEN L"\u06f7" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_EIGHT 0x06f8 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_EIGHT L"\u06f8" #define UNICODE_EXTENDED_ARABIC_INDIC_DIGIT_NINE 0x06f9 #define UNITEXT_EXTENDED_ARABIC_INDIC_DIGIT_NINE L"\u06f9" #define UNICODE_ARABIC_LETTER_SHEEN_WITH_DOT_BELOW 0x06fa #define UNITEXT_ARABIC_LETTER_SHEEN_WITH_DOT_BELOW L"\u06fa" #define UNICODE_ARABIC_LETTER_DAD_WITH_DOT_BELOW 0x06fb #define UNITEXT_ARABIC_LETTER_DAD_WITH_DOT_BELOW L"\u06fb" #define UNICODE_ARABIC_LETTER_GHAIN_WITH_DOT_BELOW 0x06fc #define UNITEXT_ARABIC_LETTER_GHAIN_WITH_DOT_BELOW L"\u06fc" #define UNICODE_ARABIC_SIGN_SINDHI_AMPERSAND 0x06fd #define UNITEXT_ARABIC_SIGN_SINDHI_AMPERSAND L"\u06fd" #define UNICODE_ARABIC_SIGN_SINDHI_POSTPOSITION_MEN 0x06fe #define UNITEXT_ARABIC_SIGN_SINDHI_POSTPOSITION_MEN L"\u06fe" #define UNICODE_ARABIC_LETTER_HEH_WITH_INVERTED_V 0x06ff #define UNITEXT_ARABIC_LETTER_HEH_WITH_INVERTED_V L"\u06ff" #define UNICODE_SYRIAC_END_OF_PARAGRAPH 0x0700 #define UNITEXT_SYRIAC_END_OF_PARAGRAPH L"\u0700" #define UNICODE_SYRIAC_SUPRALINEAR_FULL_STOP 0x0701 #define UNITEXT_SYRIAC_SUPRALINEAR_FULL_STOP L"\u0701" #define UNICODE_SYRIAC_SUBLINEAR_FULL_STOP 0x0702 #define UNITEXT_SYRIAC_SUBLINEAR_FULL_STOP L"\u0702" #define UNICODE_SYRIAC_SUPRALINEAR_COLON 0x0703 #define UNITEXT_SYRIAC_SUPRALINEAR_COLON L"\u0703" #define UNICODE_SYRIAC_SUBLINEAR_COLON 0x0704 #define UNITEXT_SYRIAC_SUBLINEAR_COLON L"\u0704" #define UNICODE_SYRIAC_HORIZONTAL_COLON 0x0705 #define UNITEXT_SYRIAC_HORIZONTAL_COLON L"\u0705" #define UNICODE_SYRIAC_COLON_SKEWED_LEFT 0x0706 #define UNITEXT_SYRIAC_COLON_SKEWED_LEFT L"\u0706" #define UNICODE_SYRIAC_COLON_SKEWED_RIGHT 0x0707 #define UNITEXT_SYRIAC_COLON_SKEWED_RIGHT L"\u0707" #define UNICODE_SYRIAC_SUPRALINEAR_COLON_SKEWED_LEFT 0x0708 #define UNITEXT_SYRIAC_SUPRALINEAR_COLON_SKEWED_LEFT L"\u0708" #define UNICODE_SYRIAC_SUBLINEAR_COLON_SKEWED_RIGHT 0x0709 #define UNITEXT_SYRIAC_SUBLINEAR_COLON_SKEWED_RIGHT L"\u0709" #define UNICODE_SYRIAC_CONTRACTION 0x070a #define UNITEXT_SYRIAC_CONTRACTION L"\u070a" #define UNICODE_SYRIAC_HARKLEAN_OBELUS 0x070b #define UNITEXT_SYRIAC_HARKLEAN_OBELUS L"\u070b" #define UNICODE_SYRIAC_HARKLEAN_METOBELUS 0x070c #define UNITEXT_SYRIAC_HARKLEAN_METOBELUS L"\u070c" #define UNICODE_SYRIAC_HARKLEAN_ASTERISCUS 0x070d #define UNITEXT_SYRIAC_HARKLEAN_ASTERISCUS L"\u070d" #define UNICODE_SYRIAC_ABBREVIATION_MARK 0x070f #define UNITEXT_SYRIAC_ABBREVIATION_MARK L"\u070f" #define UNICODE_SYRIAC_LETTER_ALAPH 0x0710 #define UNITEXT_SYRIAC_LETTER_ALAPH L"\u0710" #define UNICODE_SYRIAC_LETTER_SUPERSCRIPT_ALAPH 0x0711 #define UNITEXT_SYRIAC_LETTER_SUPERSCRIPT_ALAPH L"\u0711" #define UNICODE_SYRIAC_LETTER_BETH 0x0712 #define UNITEXT_SYRIAC_LETTER_BETH L"\u0712" #define UNICODE_SYRIAC_LETTER_GAMAL 0x0713 #define UNITEXT_SYRIAC_LETTER_GAMAL L"\u0713" #define UNICODE_SYRIAC_LETTER_GAMAL_GARSHUNI 0x0714 #define UNITEXT_SYRIAC_LETTER_GAMAL_GARSHUNI L"\u0714" #define UNICODE_SYRIAC_LETTER_DALATH 0x0715 #define UNITEXT_SYRIAC_LETTER_DALATH L"\u0715" #define UNICODE_SYRIAC_LETTER_DOTLESS_DALATH_RISH 0x0716 #define UNITEXT_SYRIAC_LETTER_DOTLESS_DALATH_RISH L"\u0716" #define UNICODE_SYRIAC_LETTER_HE 0x0717 #define UNITEXT_SYRIAC_LETTER_HE L"\u0717" #define UNICODE_SYRIAC_LETTER_WAW 0x0718 #define UNITEXT_SYRIAC_LETTER_WAW L"\u0718" #define UNICODE_SYRIAC_LETTER_ZAIN 0x0719 #define UNITEXT_SYRIAC_LETTER_ZAIN L"\u0719" #define UNICODE_SYRIAC_LETTER_HETH 0x071a #define UNITEXT_SYRIAC_LETTER_HETH L"\u071a" #define UNICODE_SYRIAC_LETTER_TETH 0x071b #define UNITEXT_SYRIAC_LETTER_TETH L"\u071b" #define UNICODE_SYRIAC_LETTER_TETH_GARSHUNI 0x071c #define UNITEXT_SYRIAC_LETTER_TETH_GARSHUNI L"\u071c" #define UNICODE_SYRIAC_LETTER_YUDH 0x071d #define UNITEXT_SYRIAC_LETTER_YUDH L"\u071d" #define UNICODE_SYRIAC_LETTER_YUDH_HE 0x071e #define UNITEXT_SYRIAC_LETTER_YUDH_HE L"\u071e" #define UNICODE_SYRIAC_LETTER_KAPH 0x071f #define UNITEXT_SYRIAC_LETTER_KAPH L"\u071f" #define UNICODE_SYRIAC_LETTER_LAMADH 0x0720 #define UNITEXT_SYRIAC_LETTER_LAMADH L"\u0720" #define UNICODE_SYRIAC_LETTER_MIM 0x0721 #define UNITEXT_SYRIAC_LETTER_MIM L"\u0721" #define UNICODE_SYRIAC_LETTER_NUN 0x0722 #define UNITEXT_SYRIAC_LETTER_NUN L"\u0722" #define UNICODE_SYRIAC_LETTER_SEMKATH 0x0723 #define UNITEXT_SYRIAC_LETTER_SEMKATH L"\u0723" #define UNICODE_SYRIAC_LETTER_FINAL_SEMKATH 0x0724 #define UNITEXT_SYRIAC_LETTER_FINAL_SEMKATH L"\u0724" #define UNICODE_SYRIAC_LETTER_E 0x0725 #define UNITEXT_SYRIAC_LETTER_E L"\u0725" #define UNICODE_SYRIAC_LETTER_PE 0x0726 #define UNITEXT_SYRIAC_LETTER_PE L"\u0726" #define UNICODE_SYRIAC_LETTER_REVERSED_PE 0x0727 #define UNITEXT_SYRIAC_LETTER_REVERSED_PE L"\u0727" #define UNICODE_SYRIAC_LETTER_SADHE 0x0728 #define UNITEXT_SYRIAC_LETTER_SADHE L"\u0728" #define UNICODE_SYRIAC_LETTER_QAPH 0x0729 #define UNITEXT_SYRIAC_LETTER_QAPH L"\u0729" #define UNICODE_SYRIAC_LETTER_RISH 0x072a #define UNITEXT_SYRIAC_LETTER_RISH L"\u072a" #define UNICODE_SYRIAC_LETTER_SHIN 0x072b #define UNITEXT_SYRIAC_LETTER_SHIN L"\u072b" #define UNICODE_SYRIAC_LETTER_TAW 0x072c #define UNITEXT_SYRIAC_LETTER_TAW L"\u072c" #define UNICODE_SYRIAC_LETTER_PERSIAN_BHETH 0x072d #define UNITEXT_SYRIAC_LETTER_PERSIAN_BHETH L"\u072d" #define UNICODE_SYRIAC_LETTER_PERSIAN_GHAMAL 0x072e #define UNITEXT_SYRIAC_LETTER_PERSIAN_GHAMAL L"\u072e" #define UNICODE_SYRIAC_LETTER_PERSIAN_DHALATH 0x072f #define UNITEXT_SYRIAC_LETTER_PERSIAN_DHALATH L"\u072f" #define UNICODE_SYRIAC_PTHAHA_ABOVE 0x0730 #define UNITEXT_SYRIAC_PTHAHA_ABOVE L"\u0730" #define UNICODE_SYRIAC_PTHAHA_BELOW 0x0731 #define UNITEXT_SYRIAC_PTHAHA_BELOW L"\u0731" #define UNICODE_SYRIAC_PTHAHA_DOTTED 0x0732 #define UNITEXT_SYRIAC_PTHAHA_DOTTED L"\u0732" #define UNICODE_SYRIAC_ZQAPHA_ABOVE 0x0733 #define UNITEXT_SYRIAC_ZQAPHA_ABOVE L"\u0733" #define UNICODE_SYRIAC_ZQAPHA_BELOW 0x0734 #define UNITEXT_SYRIAC_ZQAPHA_BELOW L"\u0734" #define UNICODE_SYRIAC_ZQAPHA_DOTTED 0x0735 #define UNITEXT_SYRIAC_ZQAPHA_DOTTED L"\u0735" #define UNICODE_SYRIAC_RBASA_ABOVE 0x0736 #define UNITEXT_SYRIAC_RBASA_ABOVE L"\u0736" #define UNICODE_SYRIAC_RBASA_BELOW 0x0737 #define UNITEXT_SYRIAC_RBASA_BELOW L"\u0737" #define UNICODE_SYRIAC_DOTTED_ZLAMA_HORIZONTAL 0x0738 #define UNITEXT_SYRIAC_DOTTED_ZLAMA_HORIZONTAL L"\u0738" #define UNICODE_SYRIAC_DOTTED_ZLAMA_ANGULAR 0x0739 #define UNITEXT_SYRIAC_DOTTED_ZLAMA_ANGULAR L"\u0739" #define UNICODE_SYRIAC_HBASA_ABOVE 0x073a #define UNITEXT_SYRIAC_HBASA_ABOVE L"\u073a" #define UNICODE_SYRIAC_HBASA_BELOW 0x073b #define UNITEXT_SYRIAC_HBASA_BELOW L"\u073b" #define UNICODE_SYRIAC_HBASA_ESASA_DOTTED 0x073c #define UNITEXT_SYRIAC_HBASA_ESASA_DOTTED L"\u073c" #define UNICODE_SYRIAC_ESASA_ABOVE 0x073d #define UNITEXT_SYRIAC_ESASA_ABOVE L"\u073d" #define UNICODE_SYRIAC_ESASA_BELOW 0x073e #define UNITEXT_SYRIAC_ESASA_BELOW L"\u073e" #define UNICODE_SYRIAC_RWAHA 0x073f #define UNITEXT_SYRIAC_RWAHA L"\u073f" #define UNICODE_SYRIAC_FEMININE_DOT 0x0740 #define UNITEXT_SYRIAC_FEMININE_DOT L"\u0740" #define UNICODE_SYRIAC_QUSHSHAYA 0x0741 #define UNITEXT_SYRIAC_QUSHSHAYA L"\u0741" #define UNICODE_SYRIAC_RUKKAKHA 0x0742 #define UNITEXT_SYRIAC_RUKKAKHA L"\u0742" #define UNICODE_SYRIAC_TWO_VERTICAL_DOTS_ABOVE 0x0743 #define UNITEXT_SYRIAC_TWO_VERTICAL_DOTS_ABOVE L"\u0743" #define UNICODE_SYRIAC_TWO_VERTICAL_DOTS_BELOW 0x0744 #define UNITEXT_SYRIAC_TWO_VERTICAL_DOTS_BELOW L"\u0744" #define UNICODE_SYRIAC_THREE_DOTS_ABOVE 0x0745 #define UNITEXT_SYRIAC_THREE_DOTS_ABOVE L"\u0745" #define UNICODE_SYRIAC_THREE_DOTS_BELOW 0x0746 #define UNITEXT_SYRIAC_THREE_DOTS_BELOW L"\u0746" #define UNICODE_SYRIAC_OBLIQUE_LINE_ABOVE 0x0747 #define UNITEXT_SYRIAC_OBLIQUE_LINE_ABOVE L"\u0747" #define UNICODE_SYRIAC_OBLIQUE_LINE_BELOW 0x0748 #define UNITEXT_SYRIAC_OBLIQUE_LINE_BELOW L"\u0748" #define UNICODE_SYRIAC_MUSIC 0x0749 #define UNITEXT_SYRIAC_MUSIC L"\u0749" #define UNICODE_SYRIAC_BARREKH 0x074a #define UNITEXT_SYRIAC_BARREKH L"\u074a" #define UNICODE_SYRIAC_LETTER_SOGDIAN_ZHAIN 0x074d #define UNITEXT_SYRIAC_LETTER_SOGDIAN_ZHAIN L"\u074d" #define UNICODE_SYRIAC_LETTER_SOGDIAN_KHAPH 0x074e #define UNITEXT_SYRIAC_LETTER_SOGDIAN_KHAPH L"\u074e" #define UNICODE_SYRIAC_LETTER_SOGDIAN_FE 0x074f #define UNITEXT_SYRIAC_LETTER_SOGDIAN_FE L"\u074f" #define UNICODE_ARABIC_LETTER_BEH_WITH_THREE_DOTS_HORIZONTALLY_BELOW 0x0750 #define UNITEXT_ARABIC_LETTER_BEH_WITH_THREE_DOTS_HORIZONTALLY_BELOW L"\u0750" #define UNICODE_ARABIC_LETTER_BEH_WITH_DOT_BELOW_AND_THREE_DOTS_ABOVE 0x0751 #define UNITEXT_ARABIC_LETTER_BEH_WITH_DOT_BELOW_AND_THREE_DOTS_ABOVE L"\u0751" #define UNICODE_ARABIC_LETTER_BEH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW 0x0752 #define UNITEXT_ARABIC_LETTER_BEH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW L"\u0752" #define UNICODE_ARABIC_LETTER_BEH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW_AND_TWO_DOTS_ABOVE 0x0753 #define UNITEXT_ARABIC_LETTER_BEH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW_AND_TWO_DOTS_ABOVE L"\u0753" #define UNICODE_ARABIC_LETTER_BEH_WITH_TWO_DOTS_BELOW_AND_DOT_ABOVE 0x0754 #define UNITEXT_ARABIC_LETTER_BEH_WITH_TWO_DOTS_BELOW_AND_DOT_ABOVE L"\u0754" #define UNICODE_ARABIC_LETTER_BEH_WITH_INVERTED_SMALL_V_BELOW 0x0755 #define UNITEXT_ARABIC_LETTER_BEH_WITH_INVERTED_SMALL_V_BELOW L"\u0755" #define UNICODE_ARABIC_LETTER_BEH_WITH_SMALL_V 0x0756 #define UNITEXT_ARABIC_LETTER_BEH_WITH_SMALL_V L"\u0756" #define UNICODE_ARABIC_LETTER_HAH_WITH_TWO_DOTS_ABOVE 0x0757 #define UNITEXT_ARABIC_LETTER_HAH_WITH_TWO_DOTS_ABOVE L"\u0757" #define UNICODE_ARABIC_LETTER_HAH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW 0x0758 #define UNITEXT_ARABIC_LETTER_HAH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW L"\u0758" #define UNICODE_ARABIC_LETTER_DAL_WITH_TWO_DOTS_VERTICALLY_BELOW_AND_SMALL_TAH 0x0759 #define UNITEXT_ARABIC_LETTER_DAL_WITH_TWO_DOTS_VERTICALLY_BELOW_AND_SMALL_TAH L"\u0759" #define UNICODE_ARABIC_LETTER_DAL_WITH_INVERTED_SMALL_V_BELOW 0x075a #define UNITEXT_ARABIC_LETTER_DAL_WITH_INVERTED_SMALL_V_BELOW L"\u075a" #define UNICODE_ARABIC_LETTER_REH_WITH_STROKE 0x075b #define UNITEXT_ARABIC_LETTER_REH_WITH_STROKE L"\u075b" #define UNICODE_ARABIC_LETTER_SEEN_WITH_FOUR_DOTS_ABOVE 0x075c #define UNITEXT_ARABIC_LETTER_SEEN_WITH_FOUR_DOTS_ABOVE L"\u075c" #define UNICODE_ARABIC_LETTER_AIN_WITH_TWO_DOTS_ABOVE 0x075d #define UNITEXT_ARABIC_LETTER_AIN_WITH_TWO_DOTS_ABOVE L"\u075d" #define UNICODE_ARABIC_LETTER_AIN_WITH_THREE_DOTS_POINTING_DOWNWARDS_ABOVE 0x075e #define UNITEXT_ARABIC_LETTER_AIN_WITH_THREE_DOTS_POINTING_DOWNWARDS_ABOVE L"\u075e" #define UNICODE_ARABIC_LETTER_AIN_WITH_TWO_DOTS_VERTICALLY_ABOVE 0x075f #define UNITEXT_ARABIC_LETTER_AIN_WITH_TWO_DOTS_VERTICALLY_ABOVE L"\u075f" #define UNICODE_ARABIC_LETTER_FEH_WITH_TWO_DOTS_BELOW 0x0760 #define UNITEXT_ARABIC_LETTER_FEH_WITH_TWO_DOTS_BELOW L"\u0760" #define UNICODE_ARABIC_LETTER_FEH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW 0x0761 #define UNITEXT_ARABIC_LETTER_FEH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW L"\u0761" #define UNICODE_ARABIC_LETTER_KEHEH_WITH_DOT_ABOVE 0x0762 #define UNITEXT_ARABIC_LETTER_KEHEH_WITH_DOT_ABOVE L"\u0762" #define UNICODE_ARABIC_LETTER_KEHEH_WITH_THREE_DOTS_ABOVE 0x0763 #define UNITEXT_ARABIC_LETTER_KEHEH_WITH_THREE_DOTS_ABOVE L"\u0763" #define UNICODE_ARABIC_LETTER_KEHEH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW 0x0764 #define UNITEXT_ARABIC_LETTER_KEHEH_WITH_THREE_DOTS_POINTING_UPWARDS_BELOW L"\u0764" #define UNICODE_ARABIC_LETTER_MEEM_WITH_DOT_ABOVE 0x0765 #define UNITEXT_ARABIC_LETTER_MEEM_WITH_DOT_ABOVE L"\u0765" #define UNICODE_ARABIC_LETTER_MEEM_WITH_DOT_BELOW 0x0766 #define UNITEXT_ARABIC_LETTER_MEEM_WITH_DOT_BELOW L"\u0766" #define UNICODE_ARABIC_LETTER_NOON_WITH_TWO_DOTS_BELOW 0x0767 #define UNITEXT_ARABIC_LETTER_NOON_WITH_TWO_DOTS_BELOW L"\u0767" #define UNICODE_ARABIC_LETTER_NOON_WITH_SMALL_TAH 0x0768 #define UNITEXT_ARABIC_LETTER_NOON_WITH_SMALL_TAH L"\u0768" #define UNICODE_ARABIC_LETTER_NOON_WITH_SMALL_V 0x0769 #define UNITEXT_ARABIC_LETTER_NOON_WITH_SMALL_V L"\u0769" #define UNICODE_ARABIC_LETTER_LAM_WITH_BAR 0x076a #define UNITEXT_ARABIC_LETTER_LAM_WITH_BAR L"\u076a" #define UNICODE_ARABIC_LETTER_REH_WITH_TWO_DOTS_VERTICALLY_ABOVE 0x076b #define UNITEXT_ARABIC_LETTER_REH_WITH_TWO_DOTS_VERTICALLY_ABOVE L"\u076b" #define UNICODE_ARABIC_LETTER_REH_WITH_HAMZA_ABOVE 0x076c #define UNITEXT_ARABIC_LETTER_REH_WITH_HAMZA_ABOVE L"\u076c" #define UNICODE_ARABIC_LETTER_SEEN_WITH_TWO_DOTS_VERTICALLY_ABOVE 0x076d #define UNITEXT_ARABIC_LETTER_SEEN_WITH_TWO_DOTS_VERTICALLY_ABOVE L"\u076d" #define UNICODE_THAANA_LETTER_HAA 0x0780 #define UNITEXT_THAANA_LETTER_HAA L"\u0780" #define UNICODE_THAANA_LETTER_SHAVIYANI 0x0781 #define UNITEXT_THAANA_LETTER_SHAVIYANI L"\u0781" #define UNICODE_THAANA_LETTER_NOONU 0x0782 #define UNITEXT_THAANA_LETTER_NOONU L"\u0782" #define UNICODE_THAANA_LETTER_RAA 0x0783 #define UNITEXT_THAANA_LETTER_RAA L"\u0783" #define UNICODE_THAANA_LETTER_BAA 0x0784 #define UNITEXT_THAANA_LETTER_BAA L"\u0784" #define UNICODE_THAANA_LETTER_LHAVIYANI 0x0785 #define UNITEXT_THAANA_LETTER_LHAVIYANI L"\u0785" #define UNICODE_THAANA_LETTER_KAAFU 0x0786 #define UNITEXT_THAANA_LETTER_KAAFU L"\u0786" #define UNICODE_THAANA_LETTER_ALIFU 0x0787 #define UNITEXT_THAANA_LETTER_ALIFU L"\u0787" #define UNICODE_THAANA_LETTER_VAAVU 0x0788 #define UNITEXT_THAANA_LETTER_VAAVU L"\u0788" #define UNICODE_THAANA_LETTER_MEEMU 0x0789 #define UNITEXT_THAANA_LETTER_MEEMU L"\u0789" #define UNICODE_THAANA_LETTER_FAAFU 0x078a #define UNITEXT_THAANA_LETTER_FAAFU L"\u078a" #define UNICODE_THAANA_LETTER_DHAALU 0x078b #define UNITEXT_THAANA_LETTER_DHAALU L"\u078b" #define UNICODE_THAANA_LETTER_THAA 0x078c #define UNITEXT_THAANA_LETTER_THAA L"\u078c" #define UNICODE_THAANA_LETTER_LAAMU 0x078d #define UNITEXT_THAANA_LETTER_LAAMU L"\u078d" #define UNICODE_THAANA_LETTER_GAAFU 0x078e #define UNITEXT_THAANA_LETTER_GAAFU L"\u078e" #define UNICODE_THAANA_LETTER_GNAVIYANI 0x078f #define UNITEXT_THAANA_LETTER_GNAVIYANI L"\u078f" #define UNICODE_THAANA_LETTER_SEENU 0x0790 #define UNITEXT_THAANA_LETTER_SEENU L"\u0790" #define UNICODE_THAANA_LETTER_DAVIYANI 0x0791 #define UNITEXT_THAANA_LETTER_DAVIYANI L"\u0791" #define UNICODE_THAANA_LETTER_ZAVIYANI 0x0792 #define UNITEXT_THAANA_LETTER_ZAVIYANI L"\u0792" #define UNICODE_THAANA_LETTER_TAVIYANI 0x0793 #define UNITEXT_THAANA_LETTER_TAVIYANI L"\u0793" #define UNICODE_THAANA_LETTER_YAA 0x0794 #define UNITEXT_THAANA_LETTER_YAA L"\u0794" #define UNICODE_THAANA_LETTER_PAVIYANI 0x0795 #define UNITEXT_THAANA_LETTER_PAVIYANI L"\u0795" #define UNICODE_THAANA_LETTER_JAVIYANI 0x0796 #define UNITEXT_THAANA_LETTER_JAVIYANI L"\u0796" #define UNICODE_THAANA_LETTER_CHAVIYANI 0x0797 #define UNITEXT_THAANA_LETTER_CHAVIYANI L"\u0797" #define UNICODE_THAANA_LETTER_TTAA 0x0798 #define UNITEXT_THAANA_LETTER_TTAA L"\u0798" #define UNICODE_THAANA_LETTER_HHAA 0x0799 #define UNITEXT_THAANA_LETTER_HHAA L"\u0799" #define UNICODE_THAANA_LETTER_KHAA 0x079a #define UNITEXT_THAANA_LETTER_KHAA L"\u079a" #define UNICODE_THAANA_LETTER_THAALU 0x079b #define UNITEXT_THAANA_LETTER_THAALU L"\u079b" #define UNICODE_THAANA_LETTER_ZAA 0x079c #define UNITEXT_THAANA_LETTER_ZAA L"\u079c" #define UNICODE_THAANA_LETTER_SHEENU 0x079d #define UNITEXT_THAANA_LETTER_SHEENU L"\u079d" #define UNICODE_THAANA_LETTER_SAADHU 0x079e #define UNITEXT_THAANA_LETTER_SAADHU L"\u079e" #define UNICODE_THAANA_LETTER_DAADHU 0x079f #define UNITEXT_THAANA_LETTER_DAADHU L"\u079f" #define UNICODE_THAANA_LETTER_TO 0x07a0 #define UNITEXT_THAANA_LETTER_TO L"\u07a0" #define UNICODE_THAANA_LETTER_ZO 0x07a1 #define UNITEXT_THAANA_LETTER_ZO L"\u07a1" #define UNICODE_THAANA_LETTER_AINU 0x07a2 #define UNITEXT_THAANA_LETTER_AINU L"\u07a2" #define UNICODE_THAANA_LETTER_GHAINU 0x07a3 #define UNITEXT_THAANA_LETTER_GHAINU L"\u07a3" #define UNICODE_THAANA_LETTER_QAAFU 0x07a4 #define UNITEXT_THAANA_LETTER_QAAFU L"\u07a4" #define UNICODE_THAANA_LETTER_WAAVU 0x07a5 #define UNITEXT_THAANA_LETTER_WAAVU L"\u07a5" #define UNICODE_THAANA_ABAFILI 0x07a6 #define UNITEXT_THAANA_ABAFILI L"\u07a6" #define UNICODE_THAANA_AABAAFILI 0x07a7 #define UNITEXT_THAANA_AABAAFILI L"\u07a7" #define UNICODE_THAANA_IBIFILI 0x07a8 #define UNITEXT_THAANA_IBIFILI L"\u07a8" #define UNICODE_THAANA_EEBEEFILI 0x07a9 #define UNITEXT_THAANA_EEBEEFILI L"\u07a9" #define UNICODE_THAANA_UBUFILI 0x07aa #define UNITEXT_THAANA_UBUFILI L"\u07aa" #define UNICODE_THAANA_OOBOOFILI 0x07ab #define UNITEXT_THAANA_OOBOOFILI L"\u07ab" #define UNICODE_THAANA_EBEFILI 0x07ac #define UNITEXT_THAANA_EBEFILI L"\u07ac" #define UNICODE_THAANA_EYBEYFILI 0x07ad #define UNITEXT_THAANA_EYBEYFILI L"\u07ad" #define UNICODE_THAANA_OBOFILI 0x07ae #define UNITEXT_THAANA_OBOFILI L"\u07ae" #define UNICODE_THAANA_OABOAFILI 0x07af #define UNITEXT_THAANA_OABOAFILI L"\u07af" #define UNICODE_THAANA_SUKUN 0x07b0 #define UNITEXT_THAANA_SUKUN L"\u07b0" #define UNICODE_THAANA_LETTER_NAA 0x07b1 #define UNITEXT_THAANA_LETTER_NAA L"\u07b1" #define UNICODE_NKO_DIGIT_ZERO 0x07c0 #define UNITEXT_NKO_DIGIT_ZERO L"\u07c0" #define UNICODE_NKO_DIGIT_ONE 0x07c1 #define UNITEXT_NKO_DIGIT_ONE L"\u07c1" #define UNICODE_NKO_DIGIT_TWO 0x07c2 #define UNITEXT_NKO_DIGIT_TWO L"\u07c2" #define UNICODE_NKO_DIGIT_THREE 0x07c3 #define UNITEXT_NKO_DIGIT_THREE L"\u07c3" #define UNICODE_NKO_DIGIT_FOUR 0x07c4 #define UNITEXT_NKO_DIGIT_FOUR L"\u07c4" #define UNICODE_NKO_DIGIT_FIVE 0x07c5 #define UNITEXT_NKO_DIGIT_FIVE L"\u07c5" #define UNICODE_NKO_DIGIT_SIX 0x07c6 #define UNITEXT_NKO_DIGIT_SIX L"\u07c6" #define UNICODE_NKO_DIGIT_SEVEN 0x07c7 #define UNITEXT_NKO_DIGIT_SEVEN L"\u07c7" #define UNICODE_NKO_DIGIT_EIGHT 0x07c8 #define UNITEXT_NKO_DIGIT_EIGHT L"\u07c8" #define UNICODE_NKO_DIGIT_NINE 0x07c9 #define UNITEXT_NKO_DIGIT_NINE L"\u07c9" #define UNICODE_NKO_LETTER_A 0x07ca #define UNITEXT_NKO_LETTER_A L"\u07ca" #define UNICODE_NKO_LETTER_EE 0x07cb #define UNITEXT_NKO_LETTER_EE L"\u07cb" #define UNICODE_NKO_LETTER_I 0x07cc #define UNITEXT_NKO_LETTER_I L"\u07cc" #define UNICODE_NKO_LETTER_E 0x07cd #define UNITEXT_NKO_LETTER_E L"\u07cd" #define UNICODE_NKO_LETTER_U 0x07ce #define UNITEXT_NKO_LETTER_U L"\u07ce" #define UNICODE_NKO_LETTER_OO 0x07cf #define UNITEXT_NKO_LETTER_OO L"\u07cf" #define UNICODE_NKO_LETTER_O 0x07d0 #define UNITEXT_NKO_LETTER_O L"\u07d0" #define UNICODE_NKO_LETTER_DAGBASINNA 0x07d1 #define UNITEXT_NKO_LETTER_DAGBASINNA L"\u07d1" #define UNICODE_NKO_LETTER_N 0x07d2 #define UNITEXT_NKO_LETTER_N L"\u07d2" #define UNICODE_NKO_LETTER_BA 0x07d3 #define UNITEXT_NKO_LETTER_BA L"\u07d3" #define UNICODE_NKO_LETTER_PA 0x07d4 #define UNITEXT_NKO_LETTER_PA L"\u07d4" #define UNICODE_NKO_LETTER_TA 0x07d5 #define UNITEXT_NKO_LETTER_TA L"\u07d5" #define UNICODE_NKO_LETTER_JA 0x07d6 #define UNITEXT_NKO_LETTER_JA L"\u07d6" #define UNICODE_NKO_LETTER_CHA 0x07d7 #define UNITEXT_NKO_LETTER_CHA L"\u07d7" #define UNICODE_NKO_LETTER_DA 0x07d8 #define UNITEXT_NKO_LETTER_DA L"\u07d8" #define UNICODE_NKO_LETTER_RA 0x07d9 #define UNITEXT_NKO_LETTER_RA L"\u07d9" #define UNICODE_NKO_LETTER_RRA 0x07da #define UNITEXT_NKO_LETTER_RRA L"\u07da" #define UNICODE_NKO_LETTER_SA 0x07db #define UNITEXT_NKO_LETTER_SA L"\u07db" #define UNICODE_NKO_LETTER_GBA 0x07dc #define UNITEXT_NKO_LETTER_GBA L"\u07dc" #define UNICODE_NKO_LETTER_FA 0x07dd #define UNITEXT_NKO_LETTER_FA L"\u07dd" #define UNICODE_NKO_LETTER_KA 0x07de #define UNITEXT_NKO_LETTER_KA L"\u07de" #define UNICODE_NKO_LETTER_LA 0x07df #define UNITEXT_NKO_LETTER_LA L"\u07df" #define UNICODE_NKO_LETTER_NA_WOLOSO 0x07e0 #define UNITEXT_NKO_LETTER_NA_WOLOSO L"\u07e0" #define UNICODE_NKO_LETTER_MA 0x07e1 #define UNITEXT_NKO_LETTER_MA L"\u07e1" #define UNICODE_NKO_LETTER_NYA 0x07e2 #define UNITEXT_NKO_LETTER_NYA L"\u07e2" #define UNICODE_NKO_LETTER_NA 0x07e3 #define UNITEXT_NKO_LETTER_NA L"\u07e3" #define UNICODE_NKO_LETTER_HA 0x07e4 #define UNITEXT_NKO_LETTER_HA L"\u07e4" #define UNICODE_NKO_LETTER_WA 0x07e5 #define UNITEXT_NKO_LETTER_WA L"\u07e5" #define UNICODE_NKO_LETTER_YA 0x07e6 #define UNITEXT_NKO_LETTER_YA L"\u07e6" #define UNICODE_NKO_LETTER_NYA_WOLOSO 0x07e7 #define UNITEXT_NKO_LETTER_NYA_WOLOSO L"\u07e7" #define UNICODE_NKO_LETTER_JONA_JA 0x07e8 #define UNITEXT_NKO_LETTER_JONA_JA L"\u07e8" #define UNICODE_NKO_LETTER_JONA_CHA 0x07e9 #define UNITEXT_NKO_LETTER_JONA_CHA L"\u07e9" #define UNICODE_NKO_LETTER_JONA_RA 0x07ea #define UNITEXT_NKO_LETTER_JONA_RA L"\u07ea" #define UNICODE_NKO_COMBINING_SHORT_HIGH_TONE 0x07eb #define UNITEXT_NKO_COMBINING_SHORT_HIGH_TONE L"\u07eb" #define UNICODE_NKO_COMBINING_SHORT_LOW_TONE 0x07ec #define UNITEXT_NKO_COMBINING_SHORT_LOW_TONE L"\u07ec" #define UNICODE_NKO_COMBINING_SHORT_RISING_TONE 0x07ed #define UNITEXT_NKO_COMBINING_SHORT_RISING_TONE L"\u07ed" #define UNICODE_NKO_COMBINING_LONG_DESCENDING_TONE 0x07ee #define UNITEXT_NKO_COMBINING_LONG_DESCENDING_TONE L"\u07ee" #define UNICODE_NKO_COMBINING_LONG_HIGH_TONE 0x07ef #define UNITEXT_NKO_COMBINING_LONG_HIGH_TONE L"\u07ef" #define UNICODE_NKO_COMBINING_LONG_LOW_TONE 0x07f0 #define UNITEXT_NKO_COMBINING_LONG_LOW_TONE L"\u07f0" #define UNICODE_NKO_COMBINING_LONG_RISING_TONE 0x07f1 #define UNITEXT_NKO_COMBINING_LONG_RISING_TONE L"\u07f1" #define UNICODE_NKO_COMBINING_NASALIZATION_MARK 0x07f2 #define UNITEXT_NKO_COMBINING_NASALIZATION_MARK L"\u07f2" #define UNICODE_NKO_COMBINING_DOUBLE_DOT_ABOVE 0x07f3 #define UNITEXT_NKO_COMBINING_DOUBLE_DOT_ABOVE L"\u07f3" #define UNICODE_NKO_HIGH_TONE_APOSTROPHE 0x07f4 #define UNITEXT_NKO_HIGH_TONE_APOSTROPHE L"\u07f4" #define UNICODE_NKO_LOW_TONE_APOSTROPHE 0x07f5 #define UNITEXT_NKO_LOW_TONE_APOSTROPHE L"\u07f5" #define UNICODE_NKO_SYMBOL_OO_DENNEN 0x07f6 #define UNITEXT_NKO_SYMBOL_OO_DENNEN L"\u07f6" #define UNICODE_NKO_SYMBOL_GBAKURUNEN 0x07f7 #define UNITEXT_NKO_SYMBOL_GBAKURUNEN L"\u07f7" #define UNICODE_NKO_COMMA 0x07f8 #define UNITEXT_NKO_COMMA L"\u07f8" #define UNICODE_NKO_EXCLAMATION_MARK 0x07f9 #define UNITEXT_NKO_EXCLAMATION_MARK L"\u07f9" #define UNICODE_NKO_LAJANYALAN 0x07fa #define UNITEXT_NKO_LAJANYALAN L"\u07fa" #define UNICODE_DEVANAGARI_SIGN_CANDRABINDU 0x0901 #define UNITEXT_DEVANAGARI_SIGN_CANDRABINDU L"\u0901" #define UNICODE_DEVANAGARI_SIGN_ANUSVARA 0x0902 #define UNITEXT_DEVANAGARI_SIGN_ANUSVARA L"\u0902" #define UNICODE_DEVANAGARI_SIGN_VISARGA 0x0903 #define UNITEXT_DEVANAGARI_SIGN_VISARGA L"\u0903" #define UNICODE_DEVANAGARI_LETTER_SHORT_A 0x0904 #define UNITEXT_DEVANAGARI_LETTER_SHORT_A L"\u0904" #define UNICODE_DEVANAGARI_LETTER_A 0x0905 #define UNITEXT_DEVANAGARI_LETTER_A L"\u0905" #define UNICODE_DEVANAGARI_LETTER_AA 0x0906 #define UNITEXT_DEVANAGARI_LETTER_AA L"\u0906" #define UNICODE_DEVANAGARI_LETTER_I 0x0907 #define UNITEXT_DEVANAGARI_LETTER_I L"\u0907" #define UNICODE_DEVANAGARI_LETTER_II 0x0908 #define UNITEXT_DEVANAGARI_LETTER_II L"\u0908" #define UNICODE_DEVANAGARI_LETTER_U 0x0909 #define UNITEXT_DEVANAGARI_LETTER_U L"\u0909" #define UNICODE_DEVANAGARI_LETTER_UU 0x090a #define UNITEXT_DEVANAGARI_LETTER_UU L"\u090a" #define UNICODE_DEVANAGARI_LETTER_VOCALIC_R 0x090b #define UNITEXT_DEVANAGARI_LETTER_VOCALIC_R L"\u090b" #define UNICODE_DEVANAGARI_LETTER_VOCALIC_L 0x090c #define UNITEXT_DEVANAGARI_LETTER_VOCALIC_L L"\u090c" #define UNICODE_DEVANAGARI_LETTER_CANDRA_E 0x090d #define UNITEXT_DEVANAGARI_LETTER_CANDRA_E L"\u090d" #define UNICODE_DEVANAGARI_LETTER_SHORT_E 0x090e #define UNITEXT_DEVANAGARI_LETTER_SHORT_E L"\u090e" #define UNICODE_DEVANAGARI_LETTER_E 0x090f #define UNITEXT_DEVANAGARI_LETTER_E L"\u090f" #define UNICODE_DEVANAGARI_LETTER_AI 0x0910 #define UNITEXT_DEVANAGARI_LETTER_AI L"\u0910" #define UNICODE_DEVANAGARI_LETTER_CANDRA_O 0x0911 #define UNITEXT_DEVANAGARI_LETTER_CANDRA_O L"\u0911" #define UNICODE_DEVANAGARI_LETTER_SHORT_O 0x0912 #define UNITEXT_DEVANAGARI_LETTER_SHORT_O L"\u0912" #define UNICODE_DEVANAGARI_LETTER_O 0x0913 #define UNITEXT_DEVANAGARI_LETTER_O L"\u0913" #define UNICODE_DEVANAGARI_LETTER_AU 0x0914 #define UNITEXT_DEVANAGARI_LETTER_AU L"\u0914" #define UNICODE_DEVANAGARI_LETTER_KA 0x0915 #define UNITEXT_DEVANAGARI_LETTER_KA L"\u0915" #define UNICODE_DEVANAGARI_LETTER_KHA 0x0916 #define UNITEXT_DEVANAGARI_LETTER_KHA L"\u0916" #define UNICODE_DEVANAGARI_LETTER_GA 0x0917 #define UNITEXT_DEVANAGARI_LETTER_GA L"\u0917" #define UNICODE_DEVANAGARI_LETTER_GHA 0x0918 #define UNITEXT_DEVANAGARI_LETTER_GHA L"\u0918" #define UNICODE_DEVANAGARI_LETTER_NGA 0x0919 #define UNITEXT_DEVANAGARI_LETTER_NGA L"\u0919" #define UNICODE_DEVANAGARI_LETTER_CA 0x091a #define UNITEXT_DEVANAGARI_LETTER_CA L"\u091a" #define UNICODE_DEVANAGARI_LETTER_CHA 0x091b #define UNITEXT_DEVANAGARI_LETTER_CHA L"\u091b" #define UNICODE_DEVANAGARI_LETTER_JA 0x091c #define UNITEXT_DEVANAGARI_LETTER_JA L"\u091c" #define UNICODE_DEVANAGARI_LETTER_JHA 0x091d #define UNITEXT_DEVANAGARI_LETTER_JHA L"\u091d" #define UNICODE_DEVANAGARI_LETTER_NYA 0x091e #define UNITEXT_DEVANAGARI_LETTER_NYA L"\u091e" #define UNICODE_DEVANAGARI_LETTER_TTA 0x091f #define UNITEXT_DEVANAGARI_LETTER_TTA L"\u091f" #define UNICODE_DEVANAGARI_LETTER_TTHA 0x0920 #define UNITEXT_DEVANAGARI_LETTER_TTHA L"\u0920" #define UNICODE_DEVANAGARI_LETTER_DDA 0x0921 #define UNITEXT_DEVANAGARI_LETTER_DDA L"\u0921" #define UNICODE_DEVANAGARI_LETTER_DDHA 0x0922 #define UNITEXT_DEVANAGARI_LETTER_DDHA L"\u0922" #define UNICODE_DEVANAGARI_LETTER_NNA 0x0923 #define UNITEXT_DEVANAGARI_LETTER_NNA L"\u0923" #define UNICODE_DEVANAGARI_LETTER_TA 0x0924 #define UNITEXT_DEVANAGARI_LETTER_TA L"\u0924" #define UNICODE_DEVANAGARI_LETTER_THA 0x0925 #define UNITEXT_DEVANAGARI_LETTER_THA L"\u0925" #define UNICODE_DEVANAGARI_LETTER_DA 0x0926 #define UNITEXT_DEVANAGARI_LETTER_DA L"\u0926" #define UNICODE_DEVANAGARI_LETTER_DHA 0x0927 #define UNITEXT_DEVANAGARI_LETTER_DHA L"\u0927" #define UNICODE_DEVANAGARI_LETTER_NA 0x0928 #define UNITEXT_DEVANAGARI_LETTER_NA L"\u0928" #define UNICODE_DEVANAGARI_LETTER_NNNA 0x0929 #define UNITEXT_DEVANAGARI_LETTER_NNNA L"\u0929" #define UNICODE_DEVANAGARI_LETTER_PA 0x092a #define UNITEXT_DEVANAGARI_LETTER_PA L"\u092a" #define UNICODE_DEVANAGARI_LETTER_PHA 0x092b #define UNITEXT_DEVANAGARI_LETTER_PHA L"\u092b" #define UNICODE_DEVANAGARI_LETTER_BA 0x092c #define UNITEXT_DEVANAGARI_LETTER_BA L"\u092c" #define UNICODE_DEVANAGARI_LETTER_BHA 0x092d #define UNITEXT_DEVANAGARI_LETTER_BHA L"\u092d" #define UNICODE_DEVANAGARI_LETTER_MA 0x092e #define UNITEXT_DEVANAGARI_LETTER_MA L"\u092e" #define UNICODE_DEVANAGARI_LETTER_YA 0x092f #define UNITEXT_DEVANAGARI_LETTER_YA L"\u092f" #define UNICODE_DEVANAGARI_LETTER_RA 0x0930 #define UNITEXT_DEVANAGARI_LETTER_RA L"\u0930" #define UNICODE_DEVANAGARI_LETTER_RRA 0x0931 #define UNITEXT_DEVANAGARI_LETTER_RRA L"\u0931" #define UNICODE_DEVANAGARI_LETTER_LA 0x0932 #define UNITEXT_DEVANAGARI_LETTER_LA L"\u0932" #define UNICODE_DEVANAGARI_LETTER_LLA 0x0933 #define UNITEXT_DEVANAGARI_LETTER_LLA L"\u0933" #define UNICODE_DEVANAGARI_LETTER_LLLA 0x0934 #define UNITEXT_DEVANAGARI_LETTER_LLLA L"\u0934" #define UNICODE_DEVANAGARI_LETTER_VA 0x0935 #define UNITEXT_DEVANAGARI_LETTER_VA L"\u0935" #define UNICODE_DEVANAGARI_LETTER_SHA 0x0936 #define UNITEXT_DEVANAGARI_LETTER_SHA L"\u0936" #define UNICODE_DEVANAGARI_LETTER_SSA 0x0937 #define UNITEXT_DEVANAGARI_LETTER_SSA L"\u0937" #define UNICODE_DEVANAGARI_LETTER_SA 0x0938 #define UNITEXT_DEVANAGARI_LETTER_SA L"\u0938" #define UNICODE_DEVANAGARI_LETTER_HA 0x0939 #define UNITEXT_DEVANAGARI_LETTER_HA L"\u0939" #define UNICODE_DEVANAGARI_SIGN_NUKTA 0x093c #define UNITEXT_DEVANAGARI_SIGN_NUKTA L"\u093c" #define UNICODE_DEVANAGARI_SIGN_AVAGRAHA 0x093d #define UNITEXT_DEVANAGARI_SIGN_AVAGRAHA L"\u093d" #define UNICODE_DEVANAGARI_VOWEL_SIGN_AA 0x093e #define UNITEXT_DEVANAGARI_VOWEL_SIGN_AA L"\u093e" #define UNICODE_DEVANAGARI_VOWEL_SIGN_I 0x093f #define UNITEXT_DEVANAGARI_VOWEL_SIGN_I L"\u093f" #define UNICODE_DEVANAGARI_VOWEL_SIGN_II 0x0940 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_II L"\u0940" #define UNICODE_DEVANAGARI_VOWEL_SIGN_U 0x0941 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_U L"\u0941" #define UNICODE_DEVANAGARI_VOWEL_SIGN_UU 0x0942 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_UU L"\u0942" #define UNICODE_DEVANAGARI_VOWEL_SIGN_VOCALIC_R 0x0943 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_VOCALIC_R L"\u0943" #define UNICODE_DEVANAGARI_VOWEL_SIGN_VOCALIC_RR 0x0944 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_VOCALIC_RR L"\u0944" #define UNICODE_DEVANAGARI_VOWEL_SIGN_CANDRA_E 0x0945 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_CANDRA_E L"\u0945" #define UNICODE_DEVANAGARI_VOWEL_SIGN_SHORT_E 0x0946 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_SHORT_E L"\u0946" #define UNICODE_DEVANAGARI_VOWEL_SIGN_E 0x0947 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_E L"\u0947" #define UNICODE_DEVANAGARI_VOWEL_SIGN_AI 0x0948 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_AI L"\u0948" #define UNICODE_DEVANAGARI_VOWEL_SIGN_CANDRA_O 0x0949 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_CANDRA_O L"\u0949" #define UNICODE_DEVANAGARI_VOWEL_SIGN_SHORT_O 0x094a #define UNITEXT_DEVANAGARI_VOWEL_SIGN_SHORT_O L"\u094a" #define UNICODE_DEVANAGARI_VOWEL_SIGN_O 0x094b #define UNITEXT_DEVANAGARI_VOWEL_SIGN_O L"\u094b" #define UNICODE_DEVANAGARI_VOWEL_SIGN_AU 0x094c #define UNITEXT_DEVANAGARI_VOWEL_SIGN_AU L"\u094c" #define UNICODE_DEVANAGARI_SIGN_VIRAMA 0x094d #define UNITEXT_DEVANAGARI_SIGN_VIRAMA L"\u094d" #define UNICODE_DEVANAGARI_OM 0x0950 #define UNITEXT_DEVANAGARI_OM L"\u0950" #define UNICODE_DEVANAGARI_STRESS_SIGN_UDATTA 0x0951 #define UNITEXT_DEVANAGARI_STRESS_SIGN_UDATTA L"\u0951" #define UNICODE_DEVANAGARI_STRESS_SIGN_ANUDATTA 0x0952 #define UNITEXT_DEVANAGARI_STRESS_SIGN_ANUDATTA L"\u0952" #define UNICODE_DEVANAGARI_GRAVE_ACCENT 0x0953 #define UNITEXT_DEVANAGARI_GRAVE_ACCENT L"\u0953" #define UNICODE_DEVANAGARI_ACUTE_ACCENT 0x0954 #define UNITEXT_DEVANAGARI_ACUTE_ACCENT L"\u0954" #define UNICODE_DEVANAGARI_LETTER_QA 0x0958 #define UNITEXT_DEVANAGARI_LETTER_QA L"\u0958" #define UNICODE_DEVANAGARI_LETTER_KHHA 0x0959 #define UNITEXT_DEVANAGARI_LETTER_KHHA L"\u0959" #define UNICODE_DEVANAGARI_LETTER_GHHA 0x095a #define UNITEXT_DEVANAGARI_LETTER_GHHA L"\u095a" #define UNICODE_DEVANAGARI_LETTER_ZA 0x095b #define UNITEXT_DEVANAGARI_LETTER_ZA L"\u095b" #define UNICODE_DEVANAGARI_LETTER_DDDHA 0x095c #define UNITEXT_DEVANAGARI_LETTER_DDDHA L"\u095c" #define UNICODE_DEVANAGARI_LETTER_RHA 0x095d #define UNITEXT_DEVANAGARI_LETTER_RHA L"\u095d" #define UNICODE_DEVANAGARI_LETTER_FA 0x095e #define UNITEXT_DEVANAGARI_LETTER_FA L"\u095e" #define UNICODE_DEVANAGARI_LETTER_YYA 0x095f #define UNITEXT_DEVANAGARI_LETTER_YYA L"\u095f" #define UNICODE_DEVANAGARI_LETTER_VOCALIC_RR 0x0960 #define UNITEXT_DEVANAGARI_LETTER_VOCALIC_RR L"\u0960" #define UNICODE_DEVANAGARI_LETTER_VOCALIC_LL 0x0961 #define UNITEXT_DEVANAGARI_LETTER_VOCALIC_LL L"\u0961" #define UNICODE_DEVANAGARI_VOWEL_SIGN_VOCALIC_L 0x0962 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_VOCALIC_L L"\u0962" #define UNICODE_DEVANAGARI_VOWEL_SIGN_VOCALIC_LL 0x0963 #define UNITEXT_DEVANAGARI_VOWEL_SIGN_VOCALIC_LL L"\u0963" #define UNICODE_DEVANAGARI_DANDA 0x0964 #define UNITEXT_DEVANAGARI_DANDA L"\u0964" #define UNICODE_DEVANAGARI_DOUBLE_DANDA 0x0965 #define UNITEXT_DEVANAGARI_DOUBLE_DANDA L"\u0965" #define UNICODE_DEVANAGARI_DIGIT_ZERO 0x0966 #define UNITEXT_DEVANAGARI_DIGIT_ZERO L"\u0966" #define UNICODE_DEVANAGARI_DIGIT_ONE 0x0967 #define UNITEXT_DEVANAGARI_DIGIT_ONE L"\u0967" #define UNICODE_DEVANAGARI_DIGIT_TWO 0x0968 #define UNITEXT_DEVANAGARI_DIGIT_TWO L"\u0968" #define UNICODE_DEVANAGARI_DIGIT_THREE 0x0969 #define UNITEXT_DEVANAGARI_DIGIT_THREE L"\u0969" #define UNICODE_DEVANAGARI_DIGIT_FOUR 0x096a #define UNITEXT_DEVANAGARI_DIGIT_FOUR L"\u096a" #define UNICODE_DEVANAGARI_DIGIT_FIVE 0x096b #define UNITEXT_DEVANAGARI_DIGIT_FIVE L"\u096b" #define UNICODE_DEVANAGARI_DIGIT_SIX 0x096c #define UNITEXT_DEVANAGARI_DIGIT_SIX L"\u096c" #define UNICODE_DEVANAGARI_DIGIT_SEVEN 0x096d #define UNITEXT_DEVANAGARI_DIGIT_SEVEN L"\u096d" #define UNICODE_DEVANAGARI_DIGIT_EIGHT 0x096e #define UNITEXT_DEVANAGARI_DIGIT_EIGHT L"\u096e" #define UNICODE_DEVANAGARI_DIGIT_NINE 0x096f #define UNITEXT_DEVANAGARI_DIGIT_NINE L"\u096f" #define UNICODE_DEVANAGARI_ABBREVIATION_SIGN 0x0970 #define UNITEXT_DEVANAGARI_ABBREVIATION_SIGN L"\u0970" #define UNICODE_DEVANAGARI_LETTER_GGA 0x097b #define UNITEXT_DEVANAGARI_LETTER_GGA L"\u097b" #define UNICODE_DEVANAGARI_LETTER_JJA 0x097c #define UNITEXT_DEVANAGARI_LETTER_JJA L"\u097c" #define UNICODE_DEVANAGARI_LETTER_GLOTTAL_STOP 0x097d #define UNITEXT_DEVANAGARI_LETTER_GLOTTAL_STOP L"\u097d" #define UNICODE_DEVANAGARI_LETTER_DDDA 0x097e #define UNITEXT_DEVANAGARI_LETTER_DDDA L"\u097e" #define UNICODE_DEVANAGARI_LETTER_BBA 0x097f #define UNITEXT_DEVANAGARI_LETTER_BBA L"\u097f" #define UNICODE_BENGALI_SIGN_CANDRABINDU 0x0981 #define UNITEXT_BENGALI_SIGN_CANDRABINDU L"\u0981" #define UNICODE_BENGALI_SIGN_ANUSVARA 0x0982 #define UNITEXT_BENGALI_SIGN_ANUSVARA L"\u0982" #define UNICODE_BENGALI_SIGN_VISARGA 0x0983 #define UNITEXT_BENGALI_SIGN_VISARGA L"\u0983" #define UNICODE_BENGALI_LETTER_A 0x0985 #define UNITEXT_BENGALI_LETTER_A L"\u0985" #define UNICODE_BENGALI_LETTER_AA 0x0986 #define UNITEXT_BENGALI_LETTER_AA L"\u0986" #define UNICODE_BENGALI_LETTER_I 0x0987 #define UNITEXT_BENGALI_LETTER_I L"\u0987" #define UNICODE_BENGALI_LETTER_II 0x0988 #define UNITEXT_BENGALI_LETTER_II L"\u0988" #define UNICODE_BENGALI_LETTER_U 0x0989 #define UNITEXT_BENGALI_LETTER_U L"\u0989" #define UNICODE_BENGALI_LETTER_UU 0x098a #define UNITEXT_BENGALI_LETTER_UU L"\u098a" #define UNICODE_BENGALI_LETTER_VOCALIC_R 0x098b #define UNITEXT_BENGALI_LETTER_VOCALIC_R L"\u098b" #define UNICODE_BENGALI_LETTER_VOCALIC_L 0x098c #define UNITEXT_BENGALI_LETTER_VOCALIC_L L"\u098c" #define UNICODE_BENGALI_LETTER_E 0x098f #define UNITEXT_BENGALI_LETTER_E L"\u098f" #define UNICODE_BENGALI_LETTER_AI 0x0990 #define UNITEXT_BENGALI_LETTER_AI L"\u0990" #define UNICODE_BENGALI_LETTER_O 0x0993 #define UNITEXT_BENGALI_LETTER_O L"\u0993" #define UNICODE_BENGALI_LETTER_AU 0x0994 #define UNITEXT_BENGALI_LETTER_AU L"\u0994" #define UNICODE_BENGALI_LETTER_KA 0x0995 #define UNITEXT_BENGALI_LETTER_KA L"\u0995" #define UNICODE_BENGALI_LETTER_KHA 0x0996 #define UNITEXT_BENGALI_LETTER_KHA L"\u0996" #define UNICODE_BENGALI_LETTER_GA 0x0997 #define UNITEXT_BENGALI_LETTER_GA L"\u0997" #define UNICODE_BENGALI_LETTER_GHA 0x0998 #define UNITEXT_BENGALI_LETTER_GHA L"\u0998" #define UNICODE_BENGALI_LETTER_NGA 0x0999 #define UNITEXT_BENGALI_LETTER_NGA L"\u0999" #define UNICODE_BENGALI_LETTER_CA 0x099a #define UNITEXT_BENGALI_LETTER_CA L"\u099a" #define UNICODE_BENGALI_LETTER_CHA 0x099b #define UNITEXT_BENGALI_LETTER_CHA L"\u099b" #define UNICODE_BENGALI_LETTER_JA 0x099c #define UNITEXT_BENGALI_LETTER_JA L"\u099c" #define UNICODE_BENGALI_LETTER_JHA 0x099d #define UNITEXT_BENGALI_LETTER_JHA L"\u099d" #define UNICODE_BENGALI_LETTER_NYA 0x099e #define UNITEXT_BENGALI_LETTER_NYA L"\u099e" #define UNICODE_BENGALI_LETTER_TTA 0x099f #define UNITEXT_BENGALI_LETTER_TTA L"\u099f" #define UNICODE_BENGALI_LETTER_TTHA 0x09a0 #define UNITEXT_BENGALI_LETTER_TTHA L"\u09a0" #define UNICODE_BENGALI_LETTER_DDA 0x09a1 #define UNITEXT_BENGALI_LETTER_DDA L"\u09a1" #define UNICODE_BENGALI_LETTER_DDHA 0x09a2 #define UNITEXT_BENGALI_LETTER_DDHA L"\u09a2" #define UNICODE_BENGALI_LETTER_NNA 0x09a3 #define UNITEXT_BENGALI_LETTER_NNA L"\u09a3" #define UNICODE_BENGALI_LETTER_TA 0x09a4 #define UNITEXT_BENGALI_LETTER_TA L"\u09a4" #define UNICODE_BENGALI_LETTER_THA 0x09a5 #define UNITEXT_BENGALI_LETTER_THA L"\u09a5" #define UNICODE_BENGALI_LETTER_DA 0x09a6 #define UNITEXT_BENGALI_LETTER_DA L"\u09a6" #define UNICODE_BENGALI_LETTER_DHA 0x09a7 #define UNITEXT_BENGALI_LETTER_DHA L"\u09a7" #define UNICODE_BENGALI_LETTER_NA 0x09a8 #define UNITEXT_BENGALI_LETTER_NA L"\u09a8" #define UNICODE_BENGALI_LETTER_PA 0x09aa #define UNITEXT_BENGALI_LETTER_PA L"\u09aa" #define UNICODE_BENGALI_LETTER_PHA 0x09ab #define UNITEXT_BENGALI_LETTER_PHA L"\u09ab" #define UNICODE_BENGALI_LETTER_BA 0x09ac #define UNITEXT_BENGALI_LETTER_BA L"\u09ac" #define UNICODE_BENGALI_LETTER_BHA 0x09ad #define UNITEXT_BENGALI_LETTER_BHA L"\u09ad" #define UNICODE_BENGALI_LETTER_MA 0x09ae #define UNITEXT_BENGALI_LETTER_MA L"\u09ae" #define UNICODE_BENGALI_LETTER_YA 0x09af #define UNITEXT_BENGALI_LETTER_YA L"\u09af" #define UNICODE_BENGALI_LETTER_RA 0x09b0 #define UNITEXT_BENGALI_LETTER_RA L"\u09b0" #define UNICODE_BENGALI_LETTER_LA 0x09b2 #define UNITEXT_BENGALI_LETTER_LA L"\u09b2" #define UNICODE_BENGALI_LETTER_SHA 0x09b6 #define UNITEXT_BENGALI_LETTER_SHA L"\u09b6" #define UNICODE_BENGALI_LETTER_SSA 0x09b7 #define UNITEXT_BENGALI_LETTER_SSA L"\u09b7" #define UNICODE_BENGALI_LETTER_SA 0x09b8 #define UNITEXT_BENGALI_LETTER_SA L"\u09b8" #define UNICODE_BENGALI_LETTER_HA 0x09b9 #define UNITEXT_BENGALI_LETTER_HA L"\u09b9" #define UNICODE_BENGALI_SIGN_NUKTA 0x09bc #define UNITEXT_BENGALI_SIGN_NUKTA L"\u09bc" #define UNICODE_BENGALI_SIGN_AVAGRAHA 0x09bd #define UNITEXT_BENGALI_SIGN_AVAGRAHA L"\u09bd" #define UNICODE_BENGALI_VOWEL_SIGN_AA 0x09be #define UNITEXT_BENGALI_VOWEL_SIGN_AA L"\u09be" #define UNICODE_BENGALI_VOWEL_SIGN_I 0x09bf #define UNITEXT_BENGALI_VOWEL_SIGN_I L"\u09bf" #define UNICODE_BENGALI_VOWEL_SIGN_II 0x09c0 #define UNITEXT_BENGALI_VOWEL_SIGN_II L"\u09c0" #define UNICODE_BENGALI_VOWEL_SIGN_U 0x09c1 #define UNITEXT_BENGALI_VOWEL_SIGN_U L"\u09c1" #define UNICODE_BENGALI_VOWEL_SIGN_UU 0x09c2 #define UNITEXT_BENGALI_VOWEL_SIGN_UU L"\u09c2" #define UNICODE_BENGALI_VOWEL_SIGN_VOCALIC_R 0x09c3 #define UNITEXT_BENGALI_VOWEL_SIGN_VOCALIC_R L"\u09c3" #define UNICODE_BENGALI_VOWEL_SIGN_VOCALIC_RR 0x09c4 #define UNITEXT_BENGALI_VOWEL_SIGN_VOCALIC_RR L"\u09c4" #define UNICODE_BENGALI_VOWEL_SIGN_E 0x09c7 #define UNITEXT_BENGALI_VOWEL_SIGN_E L"\u09c7" #define UNICODE_BENGALI_VOWEL_SIGN_AI 0x09c8 #define UNITEXT_BENGALI_VOWEL_SIGN_AI L"\u09c8" #define UNICODE_BENGALI_VOWEL_SIGN_O 0x09cb #define UNITEXT_BENGALI_VOWEL_SIGN_O L"\u09cb" #define UNICODE_BENGALI_VOWEL_SIGN_AU 0x09cc #define UNITEXT_BENGALI_VOWEL_SIGN_AU L"\u09cc" #define UNICODE_BENGALI_SIGN_VIRAMA 0x09cd #define UNITEXT_BENGALI_SIGN_VIRAMA L"\u09cd" #define UNICODE_BENGALI_LETTER_KHANDA_TA 0x09ce #define UNITEXT_BENGALI_LETTER_KHANDA_TA L"\u09ce" #define UNICODE_BENGALI_AU_LENGTH_MARK 0x09d7 #define UNITEXT_BENGALI_AU_LENGTH_MARK L"\u09d7" #define UNICODE_BENGALI_LETTER_RRA 0x09dc #define UNITEXT_BENGALI_LETTER_RRA L"\u09dc" #define UNICODE_BENGALI_LETTER_RHA 0x09dd #define UNITEXT_BENGALI_LETTER_RHA L"\u09dd" #define UNICODE_BENGALI_LETTER_YYA 0x09df #define UNITEXT_BENGALI_LETTER_YYA L"\u09df" #define UNICODE_BENGALI_LETTER_VOCALIC_RR 0x09e0 #define UNITEXT_BENGALI_LETTER_VOCALIC_RR L"\u09e0" #define UNICODE_BENGALI_LETTER_VOCALIC_LL 0x09e1 #define UNITEXT_BENGALI_LETTER_VOCALIC_LL L"\u09e1" #define UNICODE_BENGALI_VOWEL_SIGN_VOCALIC_L 0x09e2 #define UNITEXT_BENGALI_VOWEL_SIGN_VOCALIC_L L"\u09e2" #define UNICODE_BENGALI_VOWEL_SIGN_VOCALIC_LL 0x09e3 #define UNITEXT_BENGALI_VOWEL_SIGN_VOCALIC_LL L"\u09e3" #define UNICODE_BENGALI_DIGIT_ZERO 0x09e6 #define UNITEXT_BENGALI_DIGIT_ZERO L"\u09e6" #define UNICODE_BENGALI_DIGIT_ONE 0x09e7 #define UNITEXT_BENGALI_DIGIT_ONE L"\u09e7" #define UNICODE_BENGALI_DIGIT_TWO 0x09e8 #define UNITEXT_BENGALI_DIGIT_TWO L"\u09e8" #define UNICODE_BENGALI_DIGIT_THREE 0x09e9 #define UNITEXT_BENGALI_DIGIT_THREE L"\u09e9" #define UNICODE_BENGALI_DIGIT_FOUR 0x09ea #define UNITEXT_BENGALI_DIGIT_FOUR L"\u09ea" #define UNICODE_BENGALI_DIGIT_FIVE 0x09eb #define UNITEXT_BENGALI_DIGIT_FIVE L"\u09eb" #define UNICODE_BENGALI_DIGIT_SIX 0x09ec #define UNITEXT_BENGALI_DIGIT_SIX L"\u09ec" #define UNICODE_BENGALI_DIGIT_SEVEN 0x09ed #define UNITEXT_BENGALI_DIGIT_SEVEN L"\u09ed" #define UNICODE_BENGALI_DIGIT_EIGHT 0x09ee #define UNITEXT_BENGALI_DIGIT_EIGHT L"\u09ee" #define UNICODE_BENGALI_DIGIT_NINE 0x09ef #define UNITEXT_BENGALI_DIGIT_NINE L"\u09ef" #define UNICODE_BENGALI_LETTER_RA_WITH_MIDDLE_DIAGONAL 0x09f0 #define UNITEXT_BENGALI_LETTER_RA_WITH_MIDDLE_DIAGONAL L"\u09f0" #define UNICODE_BENGALI_LETTER_RA_WITH_LOWER_DIAGONAL 0x09f1 #define UNITEXT_BENGALI_LETTER_RA_WITH_LOWER_DIAGONAL L"\u09f1" #define UNICODE_BENGALI_RUPEE_MARK 0x09f2 #define UNITEXT_BENGALI_RUPEE_MARK L"\u09f2" #define UNICODE_BENGALI_RUPEE_SIGN 0x09f3 #define UNITEXT_BENGALI_RUPEE_SIGN L"\u09f3" #define UNICODE_BENGALI_CURRENCY_NUMERATOR_ONE 0x09f4 #define UNITEXT_BENGALI_CURRENCY_NUMERATOR_ONE L"\u09f4" #define UNICODE_BENGALI_CURRENCY_NUMERATOR_TWO 0x09f5 #define UNITEXT_BENGALI_CURRENCY_NUMERATOR_TWO L"\u09f5" #define UNICODE_BENGALI_CURRENCY_NUMERATOR_THREE 0x09f6 #define UNITEXT_BENGALI_CURRENCY_NUMERATOR_THREE L"\u09f6" #define UNICODE_BENGALI_CURRENCY_NUMERATOR_FOUR 0x09f7 #define UNITEXT_BENGALI_CURRENCY_NUMERATOR_FOUR L"\u09f7" #define UNICODE_BENGALI_CURRENCY_NUMERATOR_ONE_LESS_THAN_THE_DENOMINATOR 0x09f8 #define UNITEXT_BENGALI_CURRENCY_NUMERATOR_ONE_LESS_THAN_THE_DENOMINATOR L"\u09f8" #define UNICODE_BENGALI_CURRENCY_DENOMINATOR_SIXTEEN 0x09f9 #define UNITEXT_BENGALI_CURRENCY_DENOMINATOR_SIXTEEN L"\u09f9" #define UNICODE_BENGALI_ISSHAR 0x09fa #define UNITEXT_BENGALI_ISSHAR L"\u09fa" #define UNICODE_GURMUKHI_SIGN_ADAK_BINDI 0x0a01 #define UNITEXT_GURMUKHI_SIGN_ADAK_BINDI L"\u0a01" #define UNICODE_GURMUKHI_SIGN_BINDI 0x0a02 #define UNITEXT_GURMUKHI_SIGN_BINDI L"\u0a02" #define UNICODE_GURMUKHI_SIGN_VISARGA 0x0a03 #define UNITEXT_GURMUKHI_SIGN_VISARGA L"\u0a03" #define UNICODE_GURMUKHI_LETTER_A 0x0a05 #define UNITEXT_GURMUKHI_LETTER_A L"\u0a05" #define UNICODE_GURMUKHI_LETTER_AA 0x0a06 #define UNITEXT_GURMUKHI_LETTER_AA L"\u0a06" #define UNICODE_GURMUKHI_LETTER_I 0x0a07 #define UNITEXT_GURMUKHI_LETTER_I L"\u0a07" #define UNICODE_GURMUKHI_LETTER_II 0x0a08 #define UNITEXT_GURMUKHI_LETTER_II L"\u0a08" #define UNICODE_GURMUKHI_LETTER_U 0x0a09 #define UNITEXT_GURMUKHI_LETTER_U L"\u0a09" #define UNICODE_GURMUKHI_LETTER_UU 0x0a0a #define UNITEXT_GURMUKHI_LETTER_UU L"\u0a0a" #define UNICODE_GURMUKHI_LETTER_EE 0x0a0f #define UNITEXT_GURMUKHI_LETTER_EE L"\u0a0f" #define UNICODE_GURMUKHI_LETTER_AI 0x0a10 #define UNITEXT_GURMUKHI_LETTER_AI L"\u0a10" #define UNICODE_GURMUKHI_LETTER_OO 0x0a13 #define UNITEXT_GURMUKHI_LETTER_OO L"\u0a13" #define UNICODE_GURMUKHI_LETTER_AU 0x0a14 #define UNITEXT_GURMUKHI_LETTER_AU L"\u0a14" #define UNICODE_GURMUKHI_LETTER_KA 0x0a15 #define UNITEXT_GURMUKHI_LETTER_KA L"\u0a15" #define UNICODE_GURMUKHI_LETTER_KHA 0x0a16 #define UNITEXT_GURMUKHI_LETTER_KHA L"\u0a16" #define UNICODE_GURMUKHI_LETTER_GA 0x0a17 #define UNITEXT_GURMUKHI_LETTER_GA L"\u0a17" #define UNICODE_GURMUKHI_LETTER_GHA 0x0a18 #define UNITEXT_GURMUKHI_LETTER_GHA L"\u0a18" #define UNICODE_GURMUKHI_LETTER_NGA 0x0a19 #define UNITEXT_GURMUKHI_LETTER_NGA L"\u0a19" #define UNICODE_GURMUKHI_LETTER_CA 0x0a1a #define UNITEXT_GURMUKHI_LETTER_CA L"\u0a1a" #define UNICODE_GURMUKHI_LETTER_CHA 0x0a1b #define UNITEXT_GURMUKHI_LETTER_CHA L"\u0a1b" #define UNICODE_GURMUKHI_LETTER_JA 0x0a1c #define UNITEXT_GURMUKHI_LETTER_JA L"\u0a1c" #define UNICODE_GURMUKHI_LETTER_JHA 0x0a1d #define UNITEXT_GURMUKHI_LETTER_JHA L"\u0a1d" #define UNICODE_GURMUKHI_LETTER_NYA 0x0a1e #define UNITEXT_GURMUKHI_LETTER_NYA L"\u0a1e" #define UNICODE_GURMUKHI_LETTER_TTA 0x0a1f #define UNITEXT_GURMUKHI_LETTER_TTA L"\u0a1f" #define UNICODE_GURMUKHI_LETTER_TTHA 0x0a20 #define UNITEXT_GURMUKHI_LETTER_TTHA L"\u0a20" #define UNICODE_GURMUKHI_LETTER_DDA 0x0a21 #define UNITEXT_GURMUKHI_LETTER_DDA L"\u0a21" #define UNICODE_GURMUKHI_LETTER_DDHA 0x0a22 #define UNITEXT_GURMUKHI_LETTER_DDHA L"\u0a22" #define UNICODE_GURMUKHI_LETTER_NNA 0x0a23 #define UNITEXT_GURMUKHI_LETTER_NNA L"\u0a23" #define UNICODE_GURMUKHI_LETTER_TA 0x0a24 #define UNITEXT_GURMUKHI_LETTER_TA L"\u0a24" #define UNICODE_GURMUKHI_LETTER_THA 0x0a25 #define UNITEXT_GURMUKHI_LETTER_THA L"\u0a25" #define UNICODE_GURMUKHI_LETTER_DA 0x0a26 #define UNITEXT_GURMUKHI_LETTER_DA L"\u0a26" #define UNICODE_GURMUKHI_LETTER_DHA 0x0a27 #define UNITEXT_GURMUKHI_LETTER_DHA L"\u0a27" #define UNICODE_GURMUKHI_LETTER_NA 0x0a28 #define UNITEXT_GURMUKHI_LETTER_NA L"\u0a28" #define UNICODE_GURMUKHI_LETTER_PA 0x0a2a #define UNITEXT_GURMUKHI_LETTER_PA L"\u0a2a" #define UNICODE_GURMUKHI_LETTER_PHA 0x0a2b #define UNITEXT_GURMUKHI_LETTER_PHA L"\u0a2b" #define UNICODE_GURMUKHI_LETTER_BA 0x0a2c #define UNITEXT_GURMUKHI_LETTER_BA L"\u0a2c" #define UNICODE_GURMUKHI_LETTER_BHA 0x0a2d #define UNITEXT_GURMUKHI_LETTER_BHA L"\u0a2d" #define UNICODE_GURMUKHI_LETTER_MA 0x0a2e #define UNITEXT_GURMUKHI_LETTER_MA L"\u0a2e" #define UNICODE_GURMUKHI_LETTER_YA 0x0a2f #define UNITEXT_GURMUKHI_LETTER_YA L"\u0a2f" #define UNICODE_GURMUKHI_LETTER_RA 0x0a30 #define UNITEXT_GURMUKHI_LETTER_RA L"\u0a30" #define UNICODE_GURMUKHI_LETTER_LA 0x0a32 #define UNITEXT_GURMUKHI_LETTER_LA L"\u0a32" #define UNICODE_GURMUKHI_LETTER_LLA 0x0a33 #define UNITEXT_GURMUKHI_LETTER_LLA L"\u0a33" #define UNICODE_GURMUKHI_LETTER_VA 0x0a35 #define UNITEXT_GURMUKHI_LETTER_VA L"\u0a35" #define UNICODE_GURMUKHI_LETTER_SHA 0x0a36 #define UNITEXT_GURMUKHI_LETTER_SHA L"\u0a36" #define UNICODE_GURMUKHI_LETTER_SA 0x0a38 #define UNITEXT_GURMUKHI_LETTER_SA L"\u0a38" #define UNICODE_GURMUKHI_LETTER_HA 0x0a39 #define UNITEXT_GURMUKHI_LETTER_HA L"\u0a39" #define UNICODE_GURMUKHI_SIGN_NUKTA 0x0a3c #define UNITEXT_GURMUKHI_SIGN_NUKTA L"\u0a3c" #define UNICODE_GURMUKHI_VOWEL_SIGN_AA 0x0a3e #define UNITEXT_GURMUKHI_VOWEL_SIGN_AA L"\u0a3e" #define UNICODE_GURMUKHI_VOWEL_SIGN_I 0x0a3f #define UNITEXT_GURMUKHI_VOWEL_SIGN_I L"\u0a3f" #define UNICODE_GURMUKHI_VOWEL_SIGN_II 0x0a40 #define UNITEXT_GURMUKHI_VOWEL_SIGN_II L"\u0a40" #define UNICODE_GURMUKHI_VOWEL_SIGN_U 0x0a41 #define UNITEXT_GURMUKHI_VOWEL_SIGN_U L"\u0a41" #define UNICODE_GURMUKHI_VOWEL_SIGN_UU 0x0a42 #define UNITEXT_GURMUKHI_VOWEL_SIGN_UU L"\u0a42" #define UNICODE_GURMUKHI_VOWEL_SIGN_EE 0x0a47 #define UNITEXT_GURMUKHI_VOWEL_SIGN_EE L"\u0a47" #define UNICODE_GURMUKHI_VOWEL_SIGN_AI 0x0a48 #define UNITEXT_GURMUKHI_VOWEL_SIGN_AI L"\u0a48" #define UNICODE_GURMUKHI_VOWEL_SIGN_OO 0x0a4b #define UNITEXT_GURMUKHI_VOWEL_SIGN_OO L"\u0a4b" #define UNICODE_GURMUKHI_VOWEL_SIGN_AU 0x0a4c #define UNITEXT_GURMUKHI_VOWEL_SIGN_AU L"\u0a4c" #define UNICODE_GURMUKHI_SIGN_VIRAMA 0x0a4d #define UNITEXT_GURMUKHI_SIGN_VIRAMA L"\u0a4d" #define UNICODE_GURMUKHI_LETTER_KHHA 0x0a59 #define UNITEXT_GURMUKHI_LETTER_KHHA L"\u0a59" #define UNICODE_GURMUKHI_LETTER_GHHA 0x0a5a #define UNITEXT_GURMUKHI_LETTER_GHHA L"\u0a5a" #define UNICODE_GURMUKHI_LETTER_ZA 0x0a5b #define UNITEXT_GURMUKHI_LETTER_ZA L"\u0a5b" #define UNICODE_GURMUKHI_LETTER_RRA 0x0a5c #define UNITEXT_GURMUKHI_LETTER_RRA L"\u0a5c" #define UNICODE_GURMUKHI_LETTER_FA 0x0a5e #define UNITEXT_GURMUKHI_LETTER_FA L"\u0a5e" #define UNICODE_GURMUKHI_DIGIT_ZERO 0x0a66 #define UNITEXT_GURMUKHI_DIGIT_ZERO L"\u0a66" #define UNICODE_GURMUKHI_DIGIT_ONE 0x0a67 #define UNITEXT_GURMUKHI_DIGIT_ONE L"\u0a67" #define UNICODE_GURMUKHI_DIGIT_TWO 0x0a68 #define UNITEXT_GURMUKHI_DIGIT_TWO L"\u0a68" #define UNICODE_GURMUKHI_DIGIT_THREE 0x0a69 #define UNITEXT_GURMUKHI_DIGIT_THREE L"\u0a69" #define UNICODE_GURMUKHI_DIGIT_FOUR 0x0a6a #define UNITEXT_GURMUKHI_DIGIT_FOUR L"\u0a6a" #define UNICODE_GURMUKHI_DIGIT_FIVE 0x0a6b #define UNITEXT_GURMUKHI_DIGIT_FIVE L"\u0a6b" #define UNICODE_GURMUKHI_DIGIT_SIX 0x0a6c #define UNITEXT_GURMUKHI_DIGIT_SIX L"\u0a6c" #define UNICODE_GURMUKHI_DIGIT_SEVEN 0x0a6d #define UNITEXT_GURMUKHI_DIGIT_SEVEN L"\u0a6d" #define UNICODE_GURMUKHI_DIGIT_EIGHT 0x0a6e #define UNITEXT_GURMUKHI_DIGIT_EIGHT L"\u0a6e" #define UNICODE_GURMUKHI_DIGIT_NINE 0x0a6f #define UNITEXT_GURMUKHI_DIGIT_NINE L"\u0a6f" #define UNICODE_GURMUKHI_TIPPI 0x0a70 #define UNITEXT_GURMUKHI_TIPPI L"\u0a70" #define UNICODE_GURMUKHI_ADDAK 0x0a71 #define UNITEXT_GURMUKHI_ADDAK L"\u0a71" #define UNICODE_GURMUKHI_IRI 0x0a72 #define UNITEXT_GURMUKHI_IRI L"\u0a72" #define UNICODE_GURMUKHI_URA 0x0a73 #define UNITEXT_GURMUKHI_URA L"\u0a73" #define UNICODE_GURMUKHI_EK_ONKAR 0x0a74 #define UNITEXT_GURMUKHI_EK_ONKAR L"\u0a74" #define UNICODE_GUJARATI_SIGN_CANDRABINDU 0x0a81 #define UNITEXT_GUJARATI_SIGN_CANDRABINDU L"\u0a81" #define UNICODE_GUJARATI_SIGN_ANUSVARA 0x0a82 #define UNITEXT_GUJARATI_SIGN_ANUSVARA L"\u0a82" #define UNICODE_GUJARATI_SIGN_VISARGA 0x0a83 #define UNITEXT_GUJARATI_SIGN_VISARGA L"\u0a83" #define UNICODE_GUJARATI_LETTER_A 0x0a85 #define UNITEXT_GUJARATI_LETTER_A L"\u0a85" #define UNICODE_GUJARATI_LETTER_AA 0x0a86 #define UNITEXT_GUJARATI_LETTER_AA L"\u0a86" #define UNICODE_GUJARATI_LETTER_I 0x0a87 #define UNITEXT_GUJARATI_LETTER_I L"\u0a87" #define UNICODE_GUJARATI_LETTER_II 0x0a88 #define UNITEXT_GUJARATI_LETTER_II L"\u0a88" #define UNICODE_GUJARATI_LETTER_U 0x0a89 #define UNITEXT_GUJARATI_LETTER_U L"\u0a89" #define UNICODE_GUJARATI_LETTER_UU 0x0a8a #define UNITEXT_GUJARATI_LETTER_UU L"\u0a8a" #define UNICODE_GUJARATI_LETTER_VOCALIC_R 0x0a8b #define UNITEXT_GUJARATI_LETTER_VOCALIC_R L"\u0a8b" #define UNICODE_GUJARATI_LETTER_VOCALIC_L 0x0a8c #define UNITEXT_GUJARATI_LETTER_VOCALIC_L L"\u0a8c" #define UNICODE_GUJARATI_VOWEL_CANDRA_E 0x0a8d #define UNITEXT_GUJARATI_VOWEL_CANDRA_E L"\u0a8d" #define UNICODE_GUJARATI_LETTER_E 0x0a8f #define UNITEXT_GUJARATI_LETTER_E L"\u0a8f" #define UNICODE_GUJARATI_LETTER_AI 0x0a90 #define UNITEXT_GUJARATI_LETTER_AI L"\u0a90" #define UNICODE_GUJARATI_VOWEL_CANDRA_O 0x0a91 #define UNITEXT_GUJARATI_VOWEL_CANDRA_O L"\u0a91" #define UNICODE_GUJARATI_LETTER_O 0x0a93 #define UNITEXT_GUJARATI_LETTER_O L"\u0a93" #define UNICODE_GUJARATI_LETTER_AU 0x0a94 #define UNITEXT_GUJARATI_LETTER_AU L"\u0a94" #define UNICODE_GUJARATI_LETTER_KA 0x0a95 #define UNITEXT_GUJARATI_LETTER_KA L"\u0a95" #define UNICODE_GUJARATI_LETTER_KHA 0x0a96 #define UNITEXT_GUJARATI_LETTER_KHA L"\u0a96" #define UNICODE_GUJARATI_LETTER_GA 0x0a97 #define UNITEXT_GUJARATI_LETTER_GA L"\u0a97" #define UNICODE_GUJARATI_LETTER_GHA 0x0a98 #define UNITEXT_GUJARATI_LETTER_GHA L"\u0a98" #define UNICODE_GUJARATI_LETTER_NGA 0x0a99 #define UNITEXT_GUJARATI_LETTER_NGA L"\u0a99" #define UNICODE_GUJARATI_LETTER_CA 0x0a9a #define UNITEXT_GUJARATI_LETTER_CA L"\u0a9a" #define UNICODE_GUJARATI_LETTER_CHA 0x0a9b #define UNITEXT_GUJARATI_LETTER_CHA L"\u0a9b" #define UNICODE_GUJARATI_LETTER_JA 0x0a9c #define UNITEXT_GUJARATI_LETTER_JA L"\u0a9c" #define UNICODE_GUJARATI_LETTER_JHA 0x0a9d #define UNITEXT_GUJARATI_LETTER_JHA L"\u0a9d" #define UNICODE_GUJARATI_LETTER_NYA 0x0a9e #define UNITEXT_GUJARATI_LETTER_NYA L"\u0a9e" #define UNICODE_GUJARATI_LETTER_TTA 0x0a9f #define UNITEXT_GUJARATI_LETTER_TTA L"\u0a9f" #define UNICODE_GUJARATI_LETTER_TTHA 0x0aa0 #define UNITEXT_GUJARATI_LETTER_TTHA L"\u0aa0" #define UNICODE_GUJARATI_LETTER_DDA 0x0aa1 #define UNITEXT_GUJARATI_LETTER_DDA L"\u0aa1" #define UNICODE_GUJARATI_LETTER_DDHA 0x0aa2 #define UNITEXT_GUJARATI_LETTER_DDHA L"\u0aa2" #define UNICODE_GUJARATI_LETTER_NNA 0x0aa3 #define UNITEXT_GUJARATI_LETTER_NNA L"\u0aa3" #define UNICODE_GUJARATI_LETTER_TA 0x0aa4 #define UNITEXT_GUJARATI_LETTER_TA L"\u0aa4" #define UNICODE_GUJARATI_LETTER_THA 0x0aa5 #define UNITEXT_GUJARATI_LETTER_THA L"\u0aa5" #define UNICODE_GUJARATI_LETTER_DA 0x0aa6 #define UNITEXT_GUJARATI_LETTER_DA L"\u0aa6" #define UNICODE_GUJARATI_LETTER_DHA 0x0aa7 #define UNITEXT_GUJARATI_LETTER_DHA L"\u0aa7" #define UNICODE_GUJARATI_LETTER_NA 0x0aa8 #define UNITEXT_GUJARATI_LETTER_NA L"\u0aa8" #define UNICODE_GUJARATI_LETTER_PA 0x0aaa #define UNITEXT_GUJARATI_LETTER_PA L"\u0aaa" #define UNICODE_GUJARATI_LETTER_PHA 0x0aab #define UNITEXT_GUJARATI_LETTER_PHA L"\u0aab" #define UNICODE_GUJARATI_LETTER_BA 0x0aac #define UNITEXT_GUJARATI_LETTER_BA L"\u0aac" #define UNICODE_GUJARATI_LETTER_BHA 0x0aad #define UNITEXT_GUJARATI_LETTER_BHA L"\u0aad" #define UNICODE_GUJARATI_LETTER_MA 0x0aae #define UNITEXT_GUJARATI_LETTER_MA L"\u0aae" #define UNICODE_GUJARATI_LETTER_YA 0x0aaf #define UNITEXT_GUJARATI_LETTER_YA L"\u0aaf" #define UNICODE_GUJARATI_LETTER_RA 0x0ab0 #define UNITEXT_GUJARATI_LETTER_RA L"\u0ab0" #define UNICODE_GUJARATI_LETTER_LA 0x0ab2 #define UNITEXT_GUJARATI_LETTER_LA L"\u0ab2" #define UNICODE_GUJARATI_LETTER_LLA 0x0ab3 #define UNITEXT_GUJARATI_LETTER_LLA L"\u0ab3" #define UNICODE_GUJARATI_LETTER_VA 0x0ab5 #define UNITEXT_GUJARATI_LETTER_VA L"\u0ab5" #define UNICODE_GUJARATI_LETTER_SHA 0x0ab6 #define UNITEXT_GUJARATI_LETTER_SHA L"\u0ab6" #define UNICODE_GUJARATI_LETTER_SSA 0x0ab7 #define UNITEXT_GUJARATI_LETTER_SSA L"\u0ab7" #define UNICODE_GUJARATI_LETTER_SA 0x0ab8 #define UNITEXT_GUJARATI_LETTER_SA L"\u0ab8" #define UNICODE_GUJARATI_LETTER_HA 0x0ab9 #define UNITEXT_GUJARATI_LETTER_HA L"\u0ab9" #define UNICODE_GUJARATI_SIGN_NUKTA 0x0abc #define UNITEXT_GUJARATI_SIGN_NUKTA L"\u0abc" #define UNICODE_GUJARATI_SIGN_AVAGRAHA 0x0abd #define UNITEXT_GUJARATI_SIGN_AVAGRAHA L"\u0abd" #define UNICODE_GUJARATI_VOWEL_SIGN_AA 0x0abe #define UNITEXT_GUJARATI_VOWEL_SIGN_AA L"\u0abe" #define UNICODE_GUJARATI_VOWEL_SIGN_I 0x0abf #define UNITEXT_GUJARATI_VOWEL_SIGN_I L"\u0abf" #define UNICODE_GUJARATI_VOWEL_SIGN_II 0x0ac0 #define UNITEXT_GUJARATI_VOWEL_SIGN_II L"\u0ac0" #define UNICODE_GUJARATI_VOWEL_SIGN_U 0x0ac1 #define UNITEXT_GUJARATI_VOWEL_SIGN_U L"\u0ac1" #define UNICODE_GUJARATI_VOWEL_SIGN_UU 0x0ac2 #define UNITEXT_GUJARATI_VOWEL_SIGN_UU L"\u0ac2" #define UNICODE_GUJARATI_VOWEL_SIGN_VOCALIC_R 0x0ac3 #define UNITEXT_GUJARATI_VOWEL_SIGN_VOCALIC_R L"\u0ac3" #define UNICODE_GUJARATI_VOWEL_SIGN_VOCALIC_RR 0x0ac4 #define UNITEXT_GUJARATI_VOWEL_SIGN_VOCALIC_RR L"\u0ac4" #define UNICODE_GUJARATI_VOWEL_SIGN_CANDRA_E 0x0ac5 #define UNITEXT_GUJARATI_VOWEL_SIGN_CANDRA_E L"\u0ac5" #define UNICODE_GUJARATI_VOWEL_SIGN_E 0x0ac7 #define UNITEXT_GUJARATI_VOWEL_SIGN_E L"\u0ac7" #define UNICODE_GUJARATI_VOWEL_SIGN_AI 0x0ac8 #define UNITEXT_GUJARATI_VOWEL_SIGN_AI L"\u0ac8" #define UNICODE_GUJARATI_VOWEL_SIGN_CANDRA_O 0x0ac9 #define UNITEXT_GUJARATI_VOWEL_SIGN_CANDRA_O L"\u0ac9" #define UNICODE_GUJARATI_VOWEL_SIGN_O 0x0acb #define UNITEXT_GUJARATI_VOWEL_SIGN_O L"\u0acb" #define UNICODE_GUJARATI_VOWEL_SIGN_AU 0x0acc #define UNITEXT_GUJARATI_VOWEL_SIGN_AU L"\u0acc" #define UNICODE_GUJARATI_SIGN_VIRAMA 0x0acd #define UNITEXT_GUJARATI_SIGN_VIRAMA L"\u0acd" #define UNICODE_GUJARATI_OM 0x0ad0 #define UNITEXT_GUJARATI_OM L"\u0ad0" #define UNICODE_GUJARATI_LETTER_VOCALIC_RR 0x0ae0 #define UNITEXT_GUJARATI_LETTER_VOCALIC_RR L"\u0ae0" #define UNICODE_GUJARATI_LETTER_VOCALIC_LL 0x0ae1 #define UNITEXT_GUJARATI_LETTER_VOCALIC_LL L"\u0ae1" #define UNICODE_GUJARATI_VOWEL_SIGN_VOCALIC_L 0x0ae2 #define UNITEXT_GUJARATI_VOWEL_SIGN_VOCALIC_L L"\u0ae2" #define UNICODE_GUJARATI_VOWEL_SIGN_VOCALIC_LL 0x0ae3 #define UNITEXT_GUJARATI_VOWEL_SIGN_VOCALIC_LL L"\u0ae3" #define UNICODE_GUJARATI_DIGIT_ZERO 0x0ae6 #define UNITEXT_GUJARATI_DIGIT_ZERO L"\u0ae6" #define UNICODE_GUJARATI_DIGIT_ONE 0x0ae7 #define UNITEXT_GUJARATI_DIGIT_ONE L"\u0ae7" #define UNICODE_GUJARATI_DIGIT_TWO 0x0ae8 #define UNITEXT_GUJARATI_DIGIT_TWO L"\u0ae8" #define UNICODE_GUJARATI_DIGIT_THREE 0x0ae9 #define UNITEXT_GUJARATI_DIGIT_THREE L"\u0ae9" #define UNICODE_GUJARATI_DIGIT_FOUR 0x0aea #define UNITEXT_GUJARATI_DIGIT_FOUR L"\u0aea" #define UNICODE_GUJARATI_DIGIT_FIVE 0x0aeb #define UNITEXT_GUJARATI_DIGIT_FIVE L"\u0aeb" #define UNICODE_GUJARATI_DIGIT_SIX 0x0aec #define UNITEXT_GUJARATI_DIGIT_SIX L"\u0aec" #define UNICODE_GUJARATI_DIGIT_SEVEN 0x0aed #define UNITEXT_GUJARATI_DIGIT_SEVEN L"\u0aed" #define UNICODE_GUJARATI_DIGIT_EIGHT 0x0aee #define UNITEXT_GUJARATI_DIGIT_EIGHT L"\u0aee" #define UNICODE_GUJARATI_DIGIT_NINE 0x0aef #define UNITEXT_GUJARATI_DIGIT_NINE L"\u0aef" #define UNICODE_GUJARATI_RUPEE_SIGN 0x0af1 #define UNITEXT_GUJARATI_RUPEE_SIGN L"\u0af1" #define UNICODE_ORIYA_SIGN_CANDRABINDU 0x0b01 #define UNITEXT_ORIYA_SIGN_CANDRABINDU L"\u0b01" #define UNICODE_ORIYA_SIGN_ANUSVARA 0x0b02 #define UNITEXT_ORIYA_SIGN_ANUSVARA L"\u0b02" #define UNICODE_ORIYA_SIGN_VISARGA 0x0b03 #define UNITEXT_ORIYA_SIGN_VISARGA L"\u0b03" #define UNICODE_ORIYA_LETTER_A 0x0b05 #define UNITEXT_ORIYA_LETTER_A L"\u0b05" #define UNICODE_ORIYA_LETTER_AA 0x0b06 #define UNITEXT_ORIYA_LETTER_AA L"\u0b06" #define UNICODE_ORIYA_LETTER_I 0x0b07 #define UNITEXT_ORIYA_LETTER_I L"\u0b07" #define UNICODE_ORIYA_LETTER_II 0x0b08 #define UNITEXT_ORIYA_LETTER_II L"\u0b08" #define UNICODE_ORIYA_LETTER_U 0x0b09 #define UNITEXT_ORIYA_LETTER_U L"\u0b09" #define UNICODE_ORIYA_LETTER_UU 0x0b0a #define UNITEXT_ORIYA_LETTER_UU L"\u0b0a" #define UNICODE_ORIYA_LETTER_VOCALIC_R 0x0b0b #define UNITEXT_ORIYA_LETTER_VOCALIC_R L"\u0b0b" #define UNICODE_ORIYA_LETTER_VOCALIC_L 0x0b0c #define UNITEXT_ORIYA_LETTER_VOCALIC_L L"\u0b0c" #define UNICODE_ORIYA_LETTER_E 0x0b0f #define UNITEXT_ORIYA_LETTER_E L"\u0b0f" #define UNICODE_ORIYA_LETTER_AI 0x0b10 #define UNITEXT_ORIYA_LETTER_AI L"\u0b10" #define UNICODE_ORIYA_LETTER_O 0x0b13 #define UNITEXT_ORIYA_LETTER_O L"\u0b13" #define UNICODE_ORIYA_LETTER_AU 0x0b14 #define UNITEXT_ORIYA_LETTER_AU L"\u0b14" #define UNICODE_ORIYA_LETTER_KA 0x0b15 #define UNITEXT_ORIYA_LETTER_KA L"\u0b15" #define UNICODE_ORIYA_LETTER_KHA 0x0b16 #define UNITEXT_ORIYA_LETTER_KHA L"\u0b16" #define UNICODE_ORIYA_LETTER_GA 0x0b17 #define UNITEXT_ORIYA_LETTER_GA L"\u0b17" #define UNICODE_ORIYA_LETTER_GHA 0x0b18 #define UNITEXT_ORIYA_LETTER_GHA L"\u0b18" #define UNICODE_ORIYA_LETTER_NGA 0x0b19 #define UNITEXT_ORIYA_LETTER_NGA L"\u0b19" #define UNICODE_ORIYA_LETTER_CA 0x0b1a #define UNITEXT_ORIYA_LETTER_CA L"\u0b1a" #define UNICODE_ORIYA_LETTER_CHA 0x0b1b #define UNITEXT_ORIYA_LETTER_CHA L"\u0b1b" #define UNICODE_ORIYA_LETTER_JA 0x0b1c #define UNITEXT_ORIYA_LETTER_JA L"\u0b1c" #define UNICODE_ORIYA_LETTER_JHA 0x0b1d #define UNITEXT_ORIYA_LETTER_JHA L"\u0b1d" #define UNICODE_ORIYA_LETTER_NYA 0x0b1e #define UNITEXT_ORIYA_LETTER_NYA L"\u0b1e" #define UNICODE_ORIYA_LETTER_TTA 0x0b1f #define UNITEXT_ORIYA_LETTER_TTA L"\u0b1f" #define UNICODE_ORIYA_LETTER_TTHA 0x0b20 #define UNITEXT_ORIYA_LETTER_TTHA L"\u0b20" #define UNICODE_ORIYA_LETTER_DDA 0x0b21 #define UNITEXT_ORIYA_LETTER_DDA L"\u0b21" #define UNICODE_ORIYA_LETTER_DDHA 0x0b22 #define UNITEXT_ORIYA_LETTER_DDHA L"\u0b22" #define UNICODE_ORIYA_LETTER_NNA 0x0b23 #define UNITEXT_ORIYA_LETTER_NNA L"\u0b23" #define UNICODE_ORIYA_LETTER_TA 0x0b24 #define UNITEXT_ORIYA_LETTER_TA L"\u0b24" #define UNICODE_ORIYA_LETTER_THA 0x0b25 #define UNITEXT_ORIYA_LETTER_THA L"\u0b25" #define UNICODE_ORIYA_LETTER_DA 0x0b26 #define UNITEXT_ORIYA_LETTER_DA L"\u0b26" #define UNICODE_ORIYA_LETTER_DHA 0x0b27 #define UNITEXT_ORIYA_LETTER_DHA L"\u0b27" #define UNICODE_ORIYA_LETTER_NA 0x0b28 #define UNITEXT_ORIYA_LETTER_NA L"\u0b28" #define UNICODE_ORIYA_LETTER_PA 0x0b2a #define UNITEXT_ORIYA_LETTER_PA L"\u0b2a" #define UNICODE_ORIYA_LETTER_PHA 0x0b2b #define UNITEXT_ORIYA_LETTER_PHA L"\u0b2b" #define UNICODE_ORIYA_LETTER_BA 0x0b2c #define UNITEXT_ORIYA_LETTER_BA L"\u0b2c" #define UNICODE_ORIYA_LETTER_BHA 0x0b2d #define UNITEXT_ORIYA_LETTER_BHA L"\u0b2d" #define UNICODE_ORIYA_LETTER_MA 0x0b2e #define UNITEXT_ORIYA_LETTER_MA L"\u0b2e" #define UNICODE_ORIYA_LETTER_YA 0x0b2f #define UNITEXT_ORIYA_LETTER_YA L"\u0b2f" #define UNICODE_ORIYA_LETTER_RA 0x0b30 #define UNITEXT_ORIYA_LETTER_RA L"\u0b30" #define UNICODE_ORIYA_LETTER_LA 0x0b32 #define UNITEXT_ORIYA_LETTER_LA L"\u0b32" #define UNICODE_ORIYA_LETTER_LLA 0x0b33 #define UNITEXT_ORIYA_LETTER_LLA L"\u0b33" #define UNICODE_ORIYA_LETTER_VA 0x0b35 #define UNITEXT_ORIYA_LETTER_VA L"\u0b35" #define UNICODE_ORIYA_LETTER_SHA 0x0b36 #define UNITEXT_ORIYA_LETTER_SHA L"\u0b36" #define UNICODE_ORIYA_LETTER_SSA 0x0b37 #define UNITEXT_ORIYA_LETTER_SSA L"\u0b37" #define UNICODE_ORIYA_LETTER_SA 0x0b38 #define UNITEXT_ORIYA_LETTER_SA L"\u0b38" #define UNICODE_ORIYA_LETTER_HA 0x0b39 #define UNITEXT_ORIYA_LETTER_HA L"\u0b39" #define UNICODE_ORIYA_SIGN_NUKTA 0x0b3c #define UNITEXT_ORIYA_SIGN_NUKTA L"\u0b3c" #define UNICODE_ORIYA_SIGN_AVAGRAHA 0x0b3d #define UNITEXT_ORIYA_SIGN_AVAGRAHA L"\u0b3d" #define UNICODE_ORIYA_VOWEL_SIGN_AA 0x0b3e #define UNITEXT_ORIYA_VOWEL_SIGN_AA L"\u0b3e" #define UNICODE_ORIYA_VOWEL_SIGN_I 0x0b3f #define UNITEXT_ORIYA_VOWEL_SIGN_I L"\u0b3f" #define UNICODE_ORIYA_VOWEL_SIGN_II 0x0b40 #define UNITEXT_ORIYA_VOWEL_SIGN_II L"\u0b40" #define UNICODE_ORIYA_VOWEL_SIGN_U 0x0b41 #define UNITEXT_ORIYA_VOWEL_SIGN_U L"\u0b41" #define UNICODE_ORIYA_VOWEL_SIGN_UU 0x0b42 #define UNITEXT_ORIYA_VOWEL_SIGN_UU L"\u0b42" #define UNICODE_ORIYA_VOWEL_SIGN_VOCALIC_R 0x0b43 #define UNITEXT_ORIYA_VOWEL_SIGN_VOCALIC_R L"\u0b43" #define UNICODE_ORIYA_VOWEL_SIGN_E 0x0b47 #define UNITEXT_ORIYA_VOWEL_SIGN_E L"\u0b47" #define UNICODE_ORIYA_VOWEL_SIGN_AI 0x0b48 #define UNITEXT_ORIYA_VOWEL_SIGN_AI L"\u0b48" #define UNICODE_ORIYA_VOWEL_SIGN_O 0x0b4b #define UNITEXT_ORIYA_VOWEL_SIGN_O L"\u0b4b" #define UNICODE_ORIYA_VOWEL_SIGN_AU 0x0b4c #define UNITEXT_ORIYA_VOWEL_SIGN_AU L"\u0b4c" #define UNICODE_ORIYA_SIGN_VIRAMA 0x0b4d #define UNITEXT_ORIYA_SIGN_VIRAMA L"\u0b4d" #define UNICODE_ORIYA_AI_LENGTH_MARK 0x0b56 #define UNITEXT_ORIYA_AI_LENGTH_MARK L"\u0b56" #define UNICODE_ORIYA_AU_LENGTH_MARK 0x0b57 #define UNITEXT_ORIYA_AU_LENGTH_MARK L"\u0b57" #define UNICODE_ORIYA_LETTER_RRA 0x0b5c #define UNITEXT_ORIYA_LETTER_RRA L"\u0b5c" #define UNICODE_ORIYA_LETTER_RHA 0x0b5d #define UNITEXT_ORIYA_LETTER_RHA L"\u0b5d" #define UNICODE_ORIYA_LETTER_YYA 0x0b5f #define UNITEXT_ORIYA_LETTER_YYA L"\u0b5f" #define UNICODE_ORIYA_LETTER_VOCALIC_RR 0x0b60 #define UNITEXT_ORIYA_LETTER_VOCALIC_RR L"\u0b60" #define UNICODE_ORIYA_LETTER_VOCALIC_LL 0x0b61 #define UNITEXT_ORIYA_LETTER_VOCALIC_LL L"\u0b61" #define UNICODE_ORIYA_DIGIT_ZERO 0x0b66 #define UNITEXT_ORIYA_DIGIT_ZERO L"\u0b66" #define UNICODE_ORIYA_DIGIT_ONE 0x0b67 #define UNITEXT_ORIYA_DIGIT_ONE L"\u0b67" #define UNICODE_ORIYA_DIGIT_TWO 0x0b68 #define UNITEXT_ORIYA_DIGIT_TWO L"\u0b68" #define UNICODE_ORIYA_DIGIT_THREE 0x0b69 #define UNITEXT_ORIYA_DIGIT_THREE L"\u0b69" #define UNICODE_ORIYA_DIGIT_FOUR 0x0b6a #define UNITEXT_ORIYA_DIGIT_FOUR L"\u0b6a" #define UNICODE_ORIYA_DIGIT_FIVE 0x0b6b #define UNITEXT_ORIYA_DIGIT_FIVE L"\u0b6b" #define UNICODE_ORIYA_DIGIT_SIX 0x0b6c #define UNITEXT_ORIYA_DIGIT_SIX L"\u0b6c" #define UNICODE_ORIYA_DIGIT_SEVEN 0x0b6d #define UNITEXT_ORIYA_DIGIT_SEVEN L"\u0b6d" #define UNICODE_ORIYA_DIGIT_EIGHT 0x0b6e #define UNITEXT_ORIYA_DIGIT_EIGHT L"\u0b6e" #define UNICODE_ORIYA_DIGIT_NINE 0x0b6f #define UNITEXT_ORIYA_DIGIT_NINE L"\u0b6f" #define UNICODE_ORIYA_ISSHAR 0x0b70 #define UNITEXT_ORIYA_ISSHAR L"\u0b70" #define UNICODE_ORIYA_LETTER_WA 0x0b71 #define UNITEXT_ORIYA_LETTER_WA L"\u0b71" #define UNICODE_TAMIL_SIGN_ANUSVARA 0x0b82 #define UNITEXT_TAMIL_SIGN_ANUSVARA L"\u0b82" #define UNICODE_TAMIL_SIGN_VISARGA 0x0b83 #define UNITEXT_TAMIL_SIGN_VISARGA L"\u0b83" #define UNICODE_TAMIL_LETTER_A 0x0b85 #define UNITEXT_TAMIL_LETTER_A L"\u0b85" #define UNICODE_TAMIL_LETTER_AA 0x0b86 #define UNITEXT_TAMIL_LETTER_AA L"\u0b86" #define UNICODE_TAMIL_LETTER_I 0x0b87 #define UNITEXT_TAMIL_LETTER_I L"\u0b87" #define UNICODE_TAMIL_LETTER_II 0x0b88 #define UNITEXT_TAMIL_LETTER_II L"\u0b88" #define UNICODE_TAMIL_LETTER_U 0x0b89 #define UNITEXT_TAMIL_LETTER_U L"\u0b89" #define UNICODE_TAMIL_LETTER_UU 0x0b8a #define UNITEXT_TAMIL_LETTER_UU L"\u0b8a" #define UNICODE_TAMIL_LETTER_E 0x0b8e #define UNITEXT_TAMIL_LETTER_E L"\u0b8e" #define UNICODE_TAMIL_LETTER_EE 0x0b8f #define UNITEXT_TAMIL_LETTER_EE L"\u0b8f" #define UNICODE_TAMIL_LETTER_AI 0x0b90 #define UNITEXT_TAMIL_LETTER_AI L"\u0b90" #define UNICODE_TAMIL_LETTER_O 0x0b92 #define UNITEXT_TAMIL_LETTER_O L"\u0b92" #define UNICODE_TAMIL_LETTER_OO 0x0b93 #define UNITEXT_TAMIL_LETTER_OO L"\u0b93" #define UNICODE_TAMIL_LETTER_AU 0x0b94 #define UNITEXT_TAMIL_LETTER_AU L"\u0b94" #define UNICODE_TAMIL_LETTER_KA 0x0b95 #define UNITEXT_TAMIL_LETTER_KA L"\u0b95" #define UNICODE_TAMIL_LETTER_NGA 0x0b99 #define UNITEXT_TAMIL_LETTER_NGA L"\u0b99" #define UNICODE_TAMIL_LETTER_CA 0x0b9a #define UNITEXT_TAMIL_LETTER_CA L"\u0b9a" #define UNICODE_TAMIL_LETTER_JA 0x0b9c #define UNITEXT_TAMIL_LETTER_JA L"\u0b9c" #define UNICODE_TAMIL_LETTER_NYA 0x0b9e #define UNITEXT_TAMIL_LETTER_NYA L"\u0b9e" #define UNICODE_TAMIL_LETTER_TTA 0x0b9f #define UNITEXT_TAMIL_LETTER_TTA L"\u0b9f" #define UNICODE_TAMIL_LETTER_NNA 0x0ba3 #define UNITEXT_TAMIL_LETTER_NNA L"\u0ba3" #define UNICODE_TAMIL_LETTER_TA 0x0ba4 #define UNITEXT_TAMIL_LETTER_TA L"\u0ba4" #define UNICODE_TAMIL_LETTER_NA 0x0ba8 #define UNITEXT_TAMIL_LETTER_NA L"\u0ba8" #define UNICODE_TAMIL_LETTER_NNNA 0x0ba9 #define UNITEXT_TAMIL_LETTER_NNNA L"\u0ba9" #define UNICODE_TAMIL_LETTER_PA 0x0baa #define UNITEXT_TAMIL_LETTER_PA L"\u0baa" #define UNICODE_TAMIL_LETTER_MA 0x0bae #define UNITEXT_TAMIL_LETTER_MA L"\u0bae" #define UNICODE_TAMIL_LETTER_YA 0x0baf #define UNITEXT_TAMIL_LETTER_YA L"\u0baf" #define UNICODE_TAMIL_LETTER_RA 0x0bb0 #define UNITEXT_TAMIL_LETTER_RA L"\u0bb0" #define UNICODE_TAMIL_LETTER_RRA 0x0bb1 #define UNITEXT_TAMIL_LETTER_RRA L"\u0bb1" #define UNICODE_TAMIL_LETTER_LA 0x0bb2 #define UNITEXT_TAMIL_LETTER_LA L"\u0bb2" #define UNICODE_TAMIL_LETTER_LLA 0x0bb3 #define UNITEXT_TAMIL_LETTER_LLA L"\u0bb3" #define UNICODE_TAMIL_LETTER_LLLA 0x0bb4 #define UNITEXT_TAMIL_LETTER_LLLA L"\u0bb4" #define UNICODE_TAMIL_LETTER_VA 0x0bb5 #define UNITEXT_TAMIL_LETTER_VA L"\u0bb5" #define UNICODE_TAMIL_LETTER_SHA 0x0bb6 #define UNITEXT_TAMIL_LETTER_SHA L"\u0bb6" #define UNICODE_TAMIL_LETTER_SSA 0x0bb7 #define UNITEXT_TAMIL_LETTER_SSA L"\u0bb7" #define UNICODE_TAMIL_LETTER_SA 0x0bb8 #define UNITEXT_TAMIL_LETTER_SA L"\u0bb8" #define UNICODE_TAMIL_LETTER_HA 0x0bb9 #define UNITEXT_TAMIL_LETTER_HA L"\u0bb9" #define UNICODE_TAMIL_VOWEL_SIGN_AA 0x0bbe #define UNITEXT_TAMIL_VOWEL_SIGN_AA L"\u0bbe" #define UNICODE_TAMIL_VOWEL_SIGN_I 0x0bbf #define UNITEXT_TAMIL_VOWEL_SIGN_I L"\u0bbf" #define UNICODE_TAMIL_VOWEL_SIGN_II 0x0bc0 #define UNITEXT_TAMIL_VOWEL_SIGN_II L"\u0bc0" #define UNICODE_TAMIL_VOWEL_SIGN_U 0x0bc1 #define UNITEXT_TAMIL_VOWEL_SIGN_U L"\u0bc1" #define UNICODE_TAMIL_VOWEL_SIGN_UU 0x0bc2 #define UNITEXT_TAMIL_VOWEL_SIGN_UU L"\u0bc2" #define UNICODE_TAMIL_VOWEL_SIGN_E 0x0bc6 #define UNITEXT_TAMIL_VOWEL_SIGN_E L"\u0bc6" #define UNICODE_TAMIL_VOWEL_SIGN_EE 0x0bc7 #define UNITEXT_TAMIL_VOWEL_SIGN_EE L"\u0bc7" #define UNICODE_TAMIL_VOWEL_SIGN_AI 0x0bc8 #define UNITEXT_TAMIL_VOWEL_SIGN_AI L"\u0bc8" #define UNICODE_TAMIL_VOWEL_SIGN_O 0x0bca #define UNITEXT_TAMIL_VOWEL_SIGN_O L"\u0bca" #define UNICODE_TAMIL_VOWEL_SIGN_OO 0x0bcb #define UNITEXT_TAMIL_VOWEL_SIGN_OO L"\u0bcb" #define UNICODE_TAMIL_VOWEL_SIGN_AU 0x0bcc #define UNITEXT_TAMIL_VOWEL_SIGN_AU L"\u0bcc" #define UNICODE_TAMIL_SIGN_VIRAMA 0x0bcd #define UNITEXT_TAMIL_SIGN_VIRAMA L"\u0bcd" #define UNICODE_TAMIL_AU_LENGTH_MARK 0x0bd7 #define UNITEXT_TAMIL_AU_LENGTH_MARK L"\u0bd7" #define UNICODE_TAMIL_DIGIT_ZERO 0x0be6 #define UNITEXT_TAMIL_DIGIT_ZERO L"\u0be6" #define UNICODE_TAMIL_DIGIT_ONE 0x0be7 #define UNITEXT_TAMIL_DIGIT_ONE L"\u0be7" #define UNICODE_TAMIL_DIGIT_TWO 0x0be8 #define UNITEXT_TAMIL_DIGIT_TWO L"\u0be8" #define UNICODE_TAMIL_DIGIT_THREE 0x0be9 #define UNITEXT_TAMIL_DIGIT_THREE L"\u0be9" #define UNICODE_TAMIL_DIGIT_FOUR 0x0bea #define UNITEXT_TAMIL_DIGIT_FOUR L"\u0bea" #define UNICODE_TAMIL_DIGIT_FIVE 0x0beb #define UNITEXT_TAMIL_DIGIT_FIVE L"\u0beb" #define UNICODE_TAMIL_DIGIT_SIX 0x0bec #define UNITEXT_TAMIL_DIGIT_SIX L"\u0bec" #define UNICODE_TAMIL_DIGIT_SEVEN 0x0bed #define UNITEXT_TAMIL_DIGIT_SEVEN L"\u0bed" #define UNICODE_TAMIL_DIGIT_EIGHT 0x0bee #define UNITEXT_TAMIL_DIGIT_EIGHT L"\u0bee" #define UNICODE_TAMIL_DIGIT_NINE 0x0bef #define UNITEXT_TAMIL_DIGIT_NINE L"\u0bef" #define UNICODE_TAMIL_NUMBER_TEN 0x0bf0 #define UNITEXT_TAMIL_NUMBER_TEN L"\u0bf0" #define UNICODE_TAMIL_NUMBER_ONE_HUNDRED 0x0bf1 #define UNITEXT_TAMIL_NUMBER_ONE_HUNDRED L"\u0bf1" #define UNICODE_TAMIL_NUMBER_ONE_THOUSAND 0x0bf2 #define UNITEXT_TAMIL_NUMBER_ONE_THOUSAND L"\u0bf2" #define UNICODE_TAMIL_DAY_SIGN 0x0bf3 #define UNITEXT_TAMIL_DAY_SIGN L"\u0bf3" #define UNICODE_TAMIL_MONTH_SIGN 0x0bf4 #define UNITEXT_TAMIL_MONTH_SIGN L"\u0bf4" #define UNICODE_TAMIL_YEAR_SIGN 0x0bf5 #define UNITEXT_TAMIL_YEAR_SIGN L"\u0bf5" #define UNICODE_TAMIL_DEBIT_SIGN 0x0bf6 #define UNITEXT_TAMIL_DEBIT_SIGN L"\u0bf6" #define UNICODE_TAMIL_CREDIT_SIGN 0x0bf7 #define UNITEXT_TAMIL_CREDIT_SIGN L"\u0bf7" #define UNICODE_TAMIL_AS_ABOVE_SIGN 0x0bf8 #define UNITEXT_TAMIL_AS_ABOVE_SIGN L"\u0bf8" #define UNICODE_TAMIL_RUPEE_SIGN 0x0bf9 #define UNITEXT_TAMIL_RUPEE_SIGN L"\u0bf9" #define UNICODE_TAMIL_NUMBER_SIGN 0x0bfa #define UNITEXT_TAMIL_NUMBER_SIGN L"\u0bfa" #define UNICODE_TELUGU_SIGN_CANDRABINDU 0x0c01 #define UNITEXT_TELUGU_SIGN_CANDRABINDU L"\u0c01" #define UNICODE_TELUGU_SIGN_ANUSVARA 0x0c02 #define UNITEXT_TELUGU_SIGN_ANUSVARA L"\u0c02" #define UNICODE_TELUGU_SIGN_VISARGA 0x0c03 #define UNITEXT_TELUGU_SIGN_VISARGA L"\u0c03" #define UNICODE_TELUGU_LETTER_A 0x0c05 #define UNITEXT_TELUGU_LETTER_A L"\u0c05" #define UNICODE_TELUGU_LETTER_AA 0x0c06 #define UNITEXT_TELUGU_LETTER_AA L"\u0c06" #define UNICODE_TELUGU_LETTER_I 0x0c07 #define UNITEXT_TELUGU_LETTER_I L"\u0c07" #define UNICODE_TELUGU_LETTER_II 0x0c08 #define UNITEXT_TELUGU_LETTER_II L"\u0c08" #define UNICODE_TELUGU_LETTER_U 0x0c09 #define UNITEXT_TELUGU_LETTER_U L"\u0c09" #define UNICODE_TELUGU_LETTER_UU 0x0c0a #define UNITEXT_TELUGU_LETTER_UU L"\u0c0a" #define UNICODE_TELUGU_LETTER_VOCALIC_R 0x0c0b #define UNITEXT_TELUGU_LETTER_VOCALIC_R L"\u0c0b" #define UNICODE_TELUGU_LETTER_VOCALIC_L 0x0c0c #define UNITEXT_TELUGU_LETTER_VOCALIC_L L"\u0c0c" #define UNICODE_TELUGU_LETTER_E 0x0c0e #define UNITEXT_TELUGU_LETTER_E L"\u0c0e" #define UNICODE_TELUGU_LETTER_EE 0x0c0f #define UNITEXT_TELUGU_LETTER_EE L"\u0c0f" #define UNICODE_TELUGU_LETTER_AI 0x0c10 #define UNITEXT_TELUGU_LETTER_AI L"\u0c10" #define UNICODE_TELUGU_LETTER_O 0x0c12 #define UNITEXT_TELUGU_LETTER_O L"\u0c12" #define UNICODE_TELUGU_LETTER_OO 0x0c13 #define UNITEXT_TELUGU_LETTER_OO L"\u0c13" #define UNICODE_TELUGU_LETTER_AU 0x0c14 #define UNITEXT_TELUGU_LETTER_AU L"\u0c14" #define UNICODE_TELUGU_LETTER_KA 0x0c15 #define UNITEXT_TELUGU_LETTER_KA L"\u0c15" #define UNICODE_TELUGU_LETTER_KHA 0x0c16 #define UNITEXT_TELUGU_LETTER_KHA L"\u0c16" #define UNICODE_TELUGU_LETTER_GA 0x0c17 #define UNITEXT_TELUGU_LETTER_GA L"\u0c17" #define UNICODE_TELUGU_LETTER_GHA 0x0c18 #define UNITEXT_TELUGU_LETTER_GHA L"\u0c18" #define UNICODE_TELUGU_LETTER_NGA 0x0c19 #define UNITEXT_TELUGU_LETTER_NGA L"\u0c19" #define UNICODE_TELUGU_LETTER_CA 0x0c1a #define UNITEXT_TELUGU_LETTER_CA L"\u0c1a" #define UNICODE_TELUGU_LETTER_CHA 0x0c1b #define UNITEXT_TELUGU_LETTER_CHA L"\u0c1b" #define UNICODE_TELUGU_LETTER_JA 0x0c1c #define UNITEXT_TELUGU_LETTER_JA L"\u0c1c" #define UNICODE_TELUGU_LETTER_JHA 0x0c1d #define UNITEXT_TELUGU_LETTER_JHA L"\u0c1d" #define UNICODE_TELUGU_LETTER_NYA 0x0c1e #define UNITEXT_TELUGU_LETTER_NYA L"\u0c1e" #define UNICODE_TELUGU_LETTER_TTA 0x0c1f #define UNITEXT_TELUGU_LETTER_TTA L"\u0c1f" #define UNICODE_TELUGU_LETTER_TTHA 0x0c20 #define UNITEXT_TELUGU_LETTER_TTHA L"\u0c20" #define UNICODE_TELUGU_LETTER_DDA 0x0c21 #define UNITEXT_TELUGU_LETTER_DDA L"\u0c21" #define UNICODE_TELUGU_LETTER_DDHA 0x0c22 #define UNITEXT_TELUGU_LETTER_DDHA L"\u0c22" #define UNICODE_TELUGU_LETTER_NNA 0x0c23 #define UNITEXT_TELUGU_LETTER_NNA L"\u0c23" #define UNICODE_TELUGU_LETTER_TA 0x0c24 #define UNITEXT_TELUGU_LETTER_TA L"\u0c24" #define UNICODE_TELUGU_LETTER_THA 0x0c25 #define UNITEXT_TELUGU_LETTER_THA L"\u0c25" #define UNICODE_TELUGU_LETTER_DA 0x0c26 #define UNITEXT_TELUGU_LETTER_DA L"\u0c26" #define UNICODE_TELUGU_LETTER_DHA 0x0c27 #define UNITEXT_TELUGU_LETTER_DHA L"\u0c27" #define UNICODE_TELUGU_LETTER_NA 0x0c28 #define UNITEXT_TELUGU_LETTER_NA L"\u0c28" #define UNICODE_TELUGU_LETTER_PA 0x0c2a #define UNITEXT_TELUGU_LETTER_PA L"\u0c2a" #define UNICODE_TELUGU_LETTER_PHA 0x0c2b #define UNITEXT_TELUGU_LETTER_PHA L"\u0c2b" #define UNICODE_TELUGU_LETTER_BA 0x0c2c #define UNITEXT_TELUGU_LETTER_BA L"\u0c2c" #define UNICODE_TELUGU_LETTER_BHA 0x0c2d #define UNITEXT_TELUGU_LETTER_BHA L"\u0c2d" #define UNICODE_TELUGU_LETTER_MA 0x0c2e #define UNITEXT_TELUGU_LETTER_MA L"\u0c2e" #define UNICODE_TELUGU_LETTER_YA 0x0c2f #define UNITEXT_TELUGU_LETTER_YA L"\u0c2f" #define UNICODE_TELUGU_LETTER_RA 0x0c30 #define UNITEXT_TELUGU_LETTER_RA L"\u0c30" #define UNICODE_TELUGU_LETTER_RRA 0x0c31 #define UNITEXT_TELUGU_LETTER_RRA L"\u0c31" #define UNICODE_TELUGU_LETTER_LA 0x0c32 #define UNITEXT_TELUGU_LETTER_LA L"\u0c32" #define UNICODE_TELUGU_LETTER_LLA 0x0c33 #define UNITEXT_TELUGU_LETTER_LLA L"\u0c33" #define UNICODE_TELUGU_LETTER_VA 0x0c35 #define UNITEXT_TELUGU_LETTER_VA L"\u0c35" #define UNICODE_TELUGU_LETTER_SHA 0x0c36 #define UNITEXT_TELUGU_LETTER_SHA L"\u0c36" #define UNICODE_TELUGU_LETTER_SSA 0x0c37 #define UNITEXT_TELUGU_LETTER_SSA L"\u0c37" #define UNICODE_TELUGU_LETTER_SA 0x0c38 #define UNITEXT_TELUGU_LETTER_SA L"\u0c38" #define UNICODE_TELUGU_LETTER_HA 0x0c39 #define UNITEXT_TELUGU_LETTER_HA L"\u0c39" #define UNICODE_TELUGU_VOWEL_SIGN_AA 0x0c3e #define UNITEXT_TELUGU_VOWEL_SIGN_AA L"\u0c3e" #define UNICODE_TELUGU_VOWEL_SIGN_I 0x0c3f #define UNITEXT_TELUGU_VOWEL_SIGN_I L"\u0c3f" #define UNICODE_TELUGU_VOWEL_SIGN_II 0x0c40 #define UNITEXT_TELUGU_VOWEL_SIGN_II L"\u0c40" #define UNICODE_TELUGU_VOWEL_SIGN_U 0x0c41 #define UNITEXT_TELUGU_VOWEL_SIGN_U L"\u0c41" #define UNICODE_TELUGU_VOWEL_SIGN_UU 0x0c42 #define UNITEXT_TELUGU_VOWEL_SIGN_UU L"\u0c42" #define UNICODE_TELUGU_VOWEL_SIGN_VOCALIC_R 0x0c43 #define UNITEXT_TELUGU_VOWEL_SIGN_VOCALIC_R L"\u0c43" #define UNICODE_TELUGU_VOWEL_SIGN_VOCALIC_RR 0x0c44 #define UNITEXT_TELUGU_VOWEL_SIGN_VOCALIC_RR L"\u0c44" #define UNICODE_TELUGU_VOWEL_SIGN_E 0x0c46 #define UNITEXT_TELUGU_VOWEL_SIGN_E L"\u0c46" #define UNICODE_TELUGU_VOWEL_SIGN_EE 0x0c47 #define UNITEXT_TELUGU_VOWEL_SIGN_EE L"\u0c47" #define UNICODE_TELUGU_VOWEL_SIGN_AI 0x0c48 #define UNITEXT_TELUGU_VOWEL_SIGN_AI L"\u0c48" #define UNICODE_TELUGU_VOWEL_SIGN_O 0x0c4a #define UNITEXT_TELUGU_VOWEL_SIGN_O L"\u0c4a" #define UNICODE_TELUGU_VOWEL_SIGN_OO 0x0c4b #define UNITEXT_TELUGU_VOWEL_SIGN_OO L"\u0c4b" #define UNICODE_TELUGU_VOWEL_SIGN_AU 0x0c4c #define UNITEXT_TELUGU_VOWEL_SIGN_AU L"\u0c4c" #define UNICODE_TELUGU_SIGN_VIRAMA 0x0c4d #define UNITEXT_TELUGU_SIGN_VIRAMA L"\u0c4d" #define UNICODE_TELUGU_LENGTH_MARK 0x0c55 #define UNITEXT_TELUGU_LENGTH_MARK L"\u0c55" #define UNICODE_TELUGU_AI_LENGTH_MARK 0x0c56 #define UNITEXT_TELUGU_AI_LENGTH_MARK L"\u0c56" #define UNICODE_TELUGU_LETTER_VOCALIC_RR 0x0c60 #define UNITEXT_TELUGU_LETTER_VOCALIC_RR L"\u0c60" #define UNICODE_TELUGU_LETTER_VOCALIC_LL 0x0c61 #define UNITEXT_TELUGU_LETTER_VOCALIC_LL L"\u0c61" #define UNICODE_TELUGU_DIGIT_ZERO 0x0c66 #define UNITEXT_TELUGU_DIGIT_ZERO L"\u0c66" #define UNICODE_TELUGU_DIGIT_ONE 0x0c67 #define UNITEXT_TELUGU_DIGIT_ONE L"\u0c67" #define UNICODE_TELUGU_DIGIT_TWO 0x0c68 #define UNITEXT_TELUGU_DIGIT_TWO L"\u0c68" #define UNICODE_TELUGU_DIGIT_THREE 0x0c69 #define UNITEXT_TELUGU_DIGIT_THREE L"\u0c69" #define UNICODE_TELUGU_DIGIT_FOUR 0x0c6a #define UNITEXT_TELUGU_DIGIT_FOUR L"\u0c6a" #define UNICODE_TELUGU_DIGIT_FIVE 0x0c6b #define UNITEXT_TELUGU_DIGIT_FIVE L"\u0c6b" #define UNICODE_TELUGU_DIGIT_SIX 0x0c6c #define UNITEXT_TELUGU_DIGIT_SIX L"\u0c6c" #define UNICODE_TELUGU_DIGIT_SEVEN 0x0c6d #define UNITEXT_TELUGU_DIGIT_SEVEN L"\u0c6d" #define UNICODE_TELUGU_DIGIT_EIGHT 0x0c6e #define UNITEXT_TELUGU_DIGIT_EIGHT L"\u0c6e" #define UNICODE_TELUGU_DIGIT_NINE 0x0c6f #define UNITEXT_TELUGU_DIGIT_NINE L"\u0c6f" #define UNICODE_KANNADA_SIGN_ANUSVARA 0x0c82 #define UNITEXT_KANNADA_SIGN_ANUSVARA L"\u0c82" #define UNICODE_KANNADA_SIGN_VISARGA 0x0c83 #define UNITEXT_KANNADA_SIGN_VISARGA L"\u0c83" #define UNICODE_KANNADA_LETTER_A 0x0c85 #define UNITEXT_KANNADA_LETTER_A L"\u0c85" #define UNICODE_KANNADA_LETTER_AA 0x0c86 #define UNITEXT_KANNADA_LETTER_AA L"\u0c86" #define UNICODE_KANNADA_LETTER_I 0x0c87 #define UNITEXT_KANNADA_LETTER_I L"\u0c87" #define UNICODE_KANNADA_LETTER_II 0x0c88 #define UNITEXT_KANNADA_LETTER_II L"\u0c88" #define UNICODE_KANNADA_LETTER_U 0x0c89 #define UNITEXT_KANNADA_LETTER_U L"\u0c89" #define UNICODE_KANNADA_LETTER_UU 0x0c8a #define UNITEXT_KANNADA_LETTER_UU L"\u0c8a" #define UNICODE_KANNADA_LETTER_VOCALIC_R 0x0c8b #define UNITEXT_KANNADA_LETTER_VOCALIC_R L"\u0c8b" #define UNICODE_KANNADA_LETTER_VOCALIC_L 0x0c8c #define UNITEXT_KANNADA_LETTER_VOCALIC_L L"\u0c8c" #define UNICODE_KANNADA_LETTER_E 0x0c8e #define UNITEXT_KANNADA_LETTER_E L"\u0c8e" #define UNICODE_KANNADA_LETTER_EE 0x0c8f #define UNITEXT_KANNADA_LETTER_EE L"\u0c8f" #define UNICODE_KANNADA_LETTER_AI 0x0c90 #define UNITEXT_KANNADA_LETTER_AI L"\u0c90" #define UNICODE_KANNADA_LETTER_O 0x0c92 #define UNITEXT_KANNADA_LETTER_O L"\u0c92" #define UNICODE_KANNADA_LETTER_OO 0x0c93 #define UNITEXT_KANNADA_LETTER_OO L"\u0c93" #define UNICODE_KANNADA_LETTER_AU 0x0c94 #define UNITEXT_KANNADA_LETTER_AU L"\u0c94" #define UNICODE_KANNADA_LETTER_KA 0x0c95 #define UNITEXT_KANNADA_LETTER_KA L"\u0c95" #define UNICODE_KANNADA_LETTER_KHA 0x0c96 #define UNITEXT_KANNADA_LETTER_KHA L"\u0c96" #define UNICODE_KANNADA_LETTER_GA 0x0c97 #define UNITEXT_KANNADA_LETTER_GA L"\u0c97" #define UNICODE_KANNADA_LETTER_GHA 0x0c98 #define UNITEXT_KANNADA_LETTER_GHA L"\u0c98" #define UNICODE_KANNADA_LETTER_NGA 0x0c99 #define UNITEXT_KANNADA_LETTER_NGA L"\u0c99" #define UNICODE_KANNADA_LETTER_CA 0x0c9a #define UNITEXT_KANNADA_LETTER_CA L"\u0c9a" #define UNICODE_KANNADA_LETTER_CHA 0x0c9b #define UNITEXT_KANNADA_LETTER_CHA L"\u0c9b" #define UNICODE_KANNADA_LETTER_JA 0x0c9c #define UNITEXT_KANNADA_LETTER_JA L"\u0c9c" #define UNICODE_KANNADA_LETTER_JHA 0x0c9d #define UNITEXT_KANNADA_LETTER_JHA L"\u0c9d" #define UNICODE_KANNADA_LETTER_NYA 0x0c9e #define UNITEXT_KANNADA_LETTER_NYA L"\u0c9e" #define UNICODE_KANNADA_LETTER_TTA 0x0c9f #define UNITEXT_KANNADA_LETTER_TTA L"\u0c9f" #define UNICODE_KANNADA_LETTER_TTHA 0x0ca0 #define UNITEXT_KANNADA_LETTER_TTHA L"\u0ca0" #define UNICODE_KANNADA_LETTER_DDA 0x0ca1 #define UNITEXT_KANNADA_LETTER_DDA L"\u0ca1" #define UNICODE_KANNADA_LETTER_DDHA 0x0ca2 #define UNITEXT_KANNADA_LETTER_DDHA L"\u0ca2" #define UNICODE_KANNADA_LETTER_NNA 0x0ca3 #define UNITEXT_KANNADA_LETTER_NNA L"\u0ca3" #define UNICODE_KANNADA_LETTER_TA 0x0ca4 #define UNITEXT_KANNADA_LETTER_TA L"\u0ca4" #define UNICODE_KANNADA_LETTER_THA 0x0ca5 #define UNITEXT_KANNADA_LETTER_THA L"\u0ca5" #define UNICODE_KANNADA_LETTER_DA 0x0ca6 #define UNITEXT_KANNADA_LETTER_DA L"\u0ca6" #define UNICODE_KANNADA_LETTER_DHA 0x0ca7 #define UNITEXT_KANNADA_LETTER_DHA L"\u0ca7" #define UNICODE_KANNADA_LETTER_NA 0x0ca8 #define UNITEXT_KANNADA_LETTER_NA L"\u0ca8" #define UNICODE_KANNADA_LETTER_PA 0x0caa #define UNITEXT_KANNADA_LETTER_PA L"\u0caa" #define UNICODE_KANNADA_LETTER_PHA 0x0cab #define UNITEXT_KANNADA_LETTER_PHA L"\u0cab" #define UNICODE_KANNADA_LETTER_BA 0x0cac #define UNITEXT_KANNADA_LETTER_BA L"\u0cac" #define UNICODE_KANNADA_LETTER_BHA 0x0cad #define UNITEXT_KANNADA_LETTER_BHA L"\u0cad" #define UNICODE_KANNADA_LETTER_MA 0x0cae #define UNITEXT_KANNADA_LETTER_MA L"\u0cae" #define UNICODE_KANNADA_LETTER_YA 0x0caf #define UNITEXT_KANNADA_LETTER_YA L"\u0caf" #define UNICODE_KANNADA_LETTER_RA 0x0cb0 #define UNITEXT_KANNADA_LETTER_RA L"\u0cb0" #define UNICODE_KANNADA_LETTER_RRA 0x0cb1 #define UNITEXT_KANNADA_LETTER_RRA L"\u0cb1" #define UNICODE_KANNADA_LETTER_LA 0x0cb2 #define UNITEXT_KANNADA_LETTER_LA L"\u0cb2" #define UNICODE_KANNADA_LETTER_LLA 0x0cb3 #define UNITEXT_KANNADA_LETTER_LLA L"\u0cb3" #define UNICODE_KANNADA_LETTER_VA 0x0cb5 #define UNITEXT_KANNADA_LETTER_VA L"\u0cb5" #define UNICODE_KANNADA_LETTER_SHA 0x0cb6 #define UNITEXT_KANNADA_LETTER_SHA L"\u0cb6" #define UNICODE_KANNADA_LETTER_SSA 0x0cb7 #define UNITEXT_KANNADA_LETTER_SSA L"\u0cb7" #define UNICODE_KANNADA_LETTER_SA 0x0cb8 #define UNITEXT_KANNADA_LETTER_SA L"\u0cb8" #define UNICODE_KANNADA_LETTER_HA 0x0cb9 #define UNITEXT_KANNADA_LETTER_HA L"\u0cb9" #define UNICODE_KANNADA_SIGN_NUKTA 0x0cbc #define UNITEXT_KANNADA_SIGN_NUKTA L"\u0cbc" #define UNICODE_KANNADA_SIGN_AVAGRAHA 0x0cbd #define UNITEXT_KANNADA_SIGN_AVAGRAHA L"\u0cbd" #define UNICODE_KANNADA_VOWEL_SIGN_AA 0x0cbe #define UNITEXT_KANNADA_VOWEL_SIGN_AA L"\u0cbe" #define UNICODE_KANNADA_VOWEL_SIGN_I 0x0cbf #define UNITEXT_KANNADA_VOWEL_SIGN_I L"\u0cbf" #define UNICODE_KANNADA_VOWEL_SIGN_II 0x0cc0 #define UNITEXT_KANNADA_VOWEL_SIGN_II L"\u0cc0" #define UNICODE_KANNADA_VOWEL_SIGN_U 0x0cc1 #define UNITEXT_KANNADA_VOWEL_SIGN_U L"\u0cc1" #define UNICODE_KANNADA_VOWEL_SIGN_UU 0x0cc2 #define UNITEXT_KANNADA_VOWEL_SIGN_UU L"\u0cc2" #define UNICODE_KANNADA_VOWEL_SIGN_VOCALIC_R 0x0cc3 #define UNITEXT_KANNADA_VOWEL_SIGN_VOCALIC_R L"\u0cc3" #define UNICODE_KANNADA_VOWEL_SIGN_VOCALIC_RR 0x0cc4 #define UNITEXT_KANNADA_VOWEL_SIGN_VOCALIC_RR L"\u0cc4" #define UNICODE_KANNADA_VOWEL_SIGN_E 0x0cc6 #define UNITEXT_KANNADA_VOWEL_SIGN_E L"\u0cc6" #define UNICODE_KANNADA_VOWEL_SIGN_EE 0x0cc7 #define UNITEXT_KANNADA_VOWEL_SIGN_EE L"\u0cc7" #define UNICODE_KANNADA_VOWEL_SIGN_AI 0x0cc8 #define UNITEXT_KANNADA_VOWEL_SIGN_AI L"\u0cc8" #define UNICODE_KANNADA_VOWEL_SIGN_O 0x0cca #define UNITEXT_KANNADA_VOWEL_SIGN_O L"\u0cca" #define UNICODE_KANNADA_VOWEL_SIGN_OO 0x0ccb #define UNITEXT_KANNADA_VOWEL_SIGN_OO L"\u0ccb" #define UNICODE_KANNADA_VOWEL_SIGN_AU 0x0ccc #define UNITEXT_KANNADA_VOWEL_SIGN_AU L"\u0ccc" #define UNICODE_KANNADA_SIGN_VIRAMA 0x0ccd #define UNITEXT_KANNADA_SIGN_VIRAMA L"\u0ccd" #define UNICODE_KANNADA_LENGTH_MARK 0x0cd5 #define UNITEXT_KANNADA_LENGTH_MARK L"\u0cd5" #define UNICODE_KANNADA_AI_LENGTH_MARK 0x0cd6 #define UNITEXT_KANNADA_AI_LENGTH_MARK L"\u0cd6" #define UNICODE_KANNADA_LETTER_FA 0x0cde #define UNITEXT_KANNADA_LETTER_FA L"\u0cde" #define UNICODE_KANNADA_LETTER_VOCALIC_RR 0x0ce0 #define UNITEXT_KANNADA_LETTER_VOCALIC_RR L"\u0ce0" #define UNICODE_KANNADA_LETTER_VOCALIC_LL 0x0ce1 #define UNITEXT_KANNADA_LETTER_VOCALIC_LL L"\u0ce1" #define UNICODE_KANNADA_VOWEL_SIGN_VOCALIC_L 0x0ce2 #define UNITEXT_KANNADA_VOWEL_SIGN_VOCALIC_L L"\u0ce2" #define UNICODE_KANNADA_VOWEL_SIGN_VOCALIC_LL 0x0ce3 #define UNITEXT_KANNADA_VOWEL_SIGN_VOCALIC_LL L"\u0ce3" #define UNICODE_KANNADA_DIGIT_ZERO 0x0ce6 #define UNITEXT_KANNADA_DIGIT_ZERO L"\u0ce6" #define UNICODE_KANNADA_DIGIT_ONE 0x0ce7 #define UNITEXT_KANNADA_DIGIT_ONE L"\u0ce7" #define UNICODE_KANNADA_DIGIT_TWO 0x0ce8 #define UNITEXT_KANNADA_DIGIT_TWO L"\u0ce8" #define UNICODE_KANNADA_DIGIT_THREE 0x0ce9 #define UNITEXT_KANNADA_DIGIT_THREE L"\u0ce9" #define UNICODE_KANNADA_DIGIT_FOUR 0x0cea #define UNITEXT_KANNADA_DIGIT_FOUR L"\u0cea" #define UNICODE_KANNADA_DIGIT_FIVE 0x0ceb #define UNITEXT_KANNADA_DIGIT_FIVE L"\u0ceb" #define UNICODE_KANNADA_DIGIT_SIX 0x0cec #define UNITEXT_KANNADA_DIGIT_SIX L"\u0cec" #define UNICODE_KANNADA_DIGIT_SEVEN 0x0ced #define UNITEXT_KANNADA_DIGIT_SEVEN L"\u0ced" #define UNICODE_KANNADA_DIGIT_EIGHT 0x0cee #define UNITEXT_KANNADA_DIGIT_EIGHT L"\u0cee" #define UNICODE_KANNADA_DIGIT_NINE 0x0cef #define UNITEXT_KANNADA_DIGIT_NINE L"\u0cef" #define UNICODE_KANNADA_SIGN_JIHVAMULIYA 0x0cf1 #define UNITEXT_KANNADA_SIGN_JIHVAMULIYA L"\u0cf1" #define UNICODE_KANNADA_SIGN_UPADHMANIYA 0x0cf2 #define UNITEXT_KANNADA_SIGN_UPADHMANIYA L"\u0cf2" #define UNICODE_MALAYALAM_SIGN_ANUSVARA 0x0d02 #define UNITEXT_MALAYALAM_SIGN_ANUSVARA L"\u0d02" #define UNICODE_MALAYALAM_SIGN_VISARGA 0x0d03 #define UNITEXT_MALAYALAM_SIGN_VISARGA L"\u0d03" #define UNICODE_MALAYALAM_LETTER_A 0x0d05 #define UNITEXT_MALAYALAM_LETTER_A L"\u0d05" #define UNICODE_MALAYALAM_LETTER_AA 0x0d06 #define UNITEXT_MALAYALAM_LETTER_AA L"\u0d06" #define UNICODE_MALAYALAM_LETTER_I 0x0d07 #define UNITEXT_MALAYALAM_LETTER_I L"\u0d07" #define UNICODE_MALAYALAM_LETTER_II 0x0d08 #define UNITEXT_MALAYALAM_LETTER_II L"\u0d08" #define UNICODE_MALAYALAM_LETTER_U 0x0d09 #define UNITEXT_MALAYALAM_LETTER_U L"\u0d09" #define UNICODE_MALAYALAM_LETTER_UU 0x0d0a #define UNITEXT_MALAYALAM_LETTER_UU L"\u0d0a" #define UNICODE_MALAYALAM_LETTER_VOCALIC_R 0x0d0b #define UNITEXT_MALAYALAM_LETTER_VOCALIC_R L"\u0d0b" #define UNICODE_MALAYALAM_LETTER_VOCALIC_L 0x0d0c #define UNITEXT_MALAYALAM_LETTER_VOCALIC_L L"\u0d0c" #define UNICODE_MALAYALAM_LETTER_E 0x0d0e #define UNITEXT_MALAYALAM_LETTER_E L"\u0d0e" #define UNICODE_MALAYALAM_LETTER_EE 0x0d0f #define UNITEXT_MALAYALAM_LETTER_EE L"\u0d0f" #define UNICODE_MALAYALAM_LETTER_AI 0x0d10 #define UNITEXT_MALAYALAM_LETTER_AI L"\u0d10" #define UNICODE_MALAYALAM_LETTER_O 0x0d12 #define UNITEXT_MALAYALAM_LETTER_O L"\u0d12" #define UNICODE_MALAYALAM_LETTER_OO 0x0d13 #define UNITEXT_MALAYALAM_LETTER_OO L"\u0d13" #define UNICODE_MALAYALAM_LETTER_AU 0x0d14 #define UNITEXT_MALAYALAM_LETTER_AU L"\u0d14" #define UNICODE_MALAYALAM_LETTER_KA 0x0d15 #define UNITEXT_MALAYALAM_LETTER_KA L"\u0d15" #define UNICODE_MALAYALAM_LETTER_KHA 0x0d16 #define UNITEXT_MALAYALAM_LETTER_KHA L"\u0d16" #define UNICODE_MALAYALAM_LETTER_GA 0x0d17 #define UNITEXT_MALAYALAM_LETTER_GA L"\u0d17" #define UNICODE_MALAYALAM_LETTER_GHA 0x0d18 #define UNITEXT_MALAYALAM_LETTER_GHA L"\u0d18" #define UNICODE_MALAYALAM_LETTER_NGA 0x0d19 #define UNITEXT_MALAYALAM_LETTER_NGA L"\u0d19" #define UNICODE_MALAYALAM_LETTER_CA 0x0d1a #define UNITEXT_MALAYALAM_LETTER_CA L"\u0d1a" #define UNICODE_MALAYALAM_LETTER_CHA 0x0d1b #define UNITEXT_MALAYALAM_LETTER_CHA L"\u0d1b" #define UNICODE_MALAYALAM_LETTER_JA 0x0d1c #define UNITEXT_MALAYALAM_LETTER_JA L"\u0d1c" #define UNICODE_MALAYALAM_LETTER_JHA 0x0d1d #define UNITEXT_MALAYALAM_LETTER_JHA L"\u0d1d" #define UNICODE_MALAYALAM_LETTER_NYA 0x0d1e #define UNITEXT_MALAYALAM_LETTER_NYA L"\u0d1e" #define UNICODE_MALAYALAM_LETTER_TTA 0x0d1f #define UNITEXT_MALAYALAM_LETTER_TTA L"\u0d1f" #define UNICODE_MALAYALAM_LETTER_TTHA 0x0d20 #define UNITEXT_MALAYALAM_LETTER_TTHA L"\u0d20" #define UNICODE_MALAYALAM_LETTER_DDA 0x0d21 #define UNITEXT_MALAYALAM_LETTER_DDA L"\u0d21" #define UNICODE_MALAYALAM_LETTER_DDHA 0x0d22 #define UNITEXT_MALAYALAM_LETTER_DDHA L"\u0d22" #define UNICODE_MALAYALAM_LETTER_NNA 0x0d23 #define UNITEXT_MALAYALAM_LETTER_NNA L"\u0d23" #define UNICODE_MALAYALAM_LETTER_TA 0x0d24 #define UNITEXT_MALAYALAM_LETTER_TA L"\u0d24" #define UNICODE_MALAYALAM_LETTER_THA 0x0d25 #define UNITEXT_MALAYALAM_LETTER_THA L"\u0d25" #define UNICODE_MALAYALAM_LETTER_DA 0x0d26 #define UNITEXT_MALAYALAM_LETTER_DA L"\u0d26" #define UNICODE_MALAYALAM_LETTER_DHA 0x0d27 #define UNITEXT_MALAYALAM_LETTER_DHA L"\u0d27" #define UNICODE_MALAYALAM_LETTER_NA 0x0d28 #define UNITEXT_MALAYALAM_LETTER_NA L"\u0d28" #define UNICODE_MALAYALAM_LETTER_PA 0x0d2a #define UNITEXT_MALAYALAM_LETTER_PA L"\u0d2a" #define UNICODE_MALAYALAM_LETTER_PHA 0x0d2b #define UNITEXT_MALAYALAM_LETTER_PHA L"\u0d2b" #define UNICODE_MALAYALAM_LETTER_BA 0x0d2c #define UNITEXT_MALAYALAM_LETTER_BA L"\u0d2c" #define UNICODE_MALAYALAM_LETTER_BHA 0x0d2d #define UNITEXT_MALAYALAM_LETTER_BHA L"\u0d2d" #define UNICODE_MALAYALAM_LETTER_MA 0x0d2e #define UNITEXT_MALAYALAM_LETTER_MA L"\u0d2e" #define UNICODE_MALAYALAM_LETTER_YA 0x0d2f #define UNITEXT_MALAYALAM_LETTER_YA L"\u0d2f" #define UNICODE_MALAYALAM_LETTER_RA 0x0d30 #define UNITEXT_MALAYALAM_LETTER_RA L"\u0d30" #define UNICODE_MALAYALAM_LETTER_RRA 0x0d31 #define UNITEXT_MALAYALAM_LETTER_RRA L"\u0d31" #define UNICODE_MALAYALAM_LETTER_LA 0x0d32 #define UNITEXT_MALAYALAM_LETTER_LA L"\u0d32" #define UNICODE_MALAYALAM_LETTER_LLA 0x0d33 #define UNITEXT_MALAYALAM_LETTER_LLA L"\u0d33" #define UNICODE_MALAYALAM_LETTER_LLLA 0x0d34 #define UNITEXT_MALAYALAM_LETTER_LLLA L"\u0d34" #define UNICODE_MALAYALAM_LETTER_VA 0x0d35 #define UNITEXT_MALAYALAM_LETTER_VA L"\u0d35" #define UNICODE_MALAYALAM_LETTER_SHA 0x0d36 #define UNITEXT_MALAYALAM_LETTER_SHA L"\u0d36" #define UNICODE_MALAYALAM_LETTER_SSA 0x0d37 #define UNITEXT_MALAYALAM_LETTER_SSA L"\u0d37" #define UNICODE_MALAYALAM_LETTER_SA 0x0d38 #define UNITEXT_MALAYALAM_LETTER_SA L"\u0d38" #define UNICODE_MALAYALAM_LETTER_HA 0x0d39 #define UNITEXT_MALAYALAM_LETTER_HA L"\u0d39" #define UNICODE_MALAYALAM_VOWEL_SIGN_AA 0x0d3e #define UNITEXT_MALAYALAM_VOWEL_SIGN_AA L"\u0d3e" #define UNICODE_MALAYALAM_VOWEL_SIGN_I 0x0d3f #define UNITEXT_MALAYALAM_VOWEL_SIGN_I L"\u0d3f" #define UNICODE_MALAYALAM_VOWEL_SIGN_II 0x0d40 #define UNITEXT_MALAYALAM_VOWEL_SIGN_II L"\u0d40" #define UNICODE_MALAYALAM_VOWEL_SIGN_U 0x0d41 #define UNITEXT_MALAYALAM_VOWEL_SIGN_U L"\u0d41" #define UNICODE_MALAYALAM_VOWEL_SIGN_UU 0x0d42 #define UNITEXT_MALAYALAM_VOWEL_SIGN_UU L"\u0d42" #define UNICODE_MALAYALAM_VOWEL_SIGN_VOCALIC_R 0x0d43 #define UNITEXT_MALAYALAM_VOWEL_SIGN_VOCALIC_R L"\u0d43" #define UNICODE_MALAYALAM_VOWEL_SIGN_E 0x0d46 #define UNITEXT_MALAYALAM_VOWEL_SIGN_E L"\u0d46" #define UNICODE_MALAYALAM_VOWEL_SIGN_EE 0x0d47 #define UNITEXT_MALAYALAM_VOWEL_SIGN_EE L"\u0d47" #define UNICODE_MALAYALAM_VOWEL_SIGN_AI 0x0d48 #define UNITEXT_MALAYALAM_VOWEL_SIGN_AI L"\u0d48" #define UNICODE_MALAYALAM_VOWEL_SIGN_O 0x0d4a #define UNITEXT_MALAYALAM_VOWEL_SIGN_O L"\u0d4a" #define UNICODE_MALAYALAM_VOWEL_SIGN_OO 0x0d4b #define UNITEXT_MALAYALAM_VOWEL_SIGN_OO L"\u0d4b" #define UNICODE_MALAYALAM_VOWEL_SIGN_AU 0x0d4c #define UNITEXT_MALAYALAM_VOWEL_SIGN_AU L"\u0d4c" #define UNICODE_MALAYALAM_SIGN_VIRAMA 0x0d4d #define UNITEXT_MALAYALAM_SIGN_VIRAMA L"\u0d4d" #define UNICODE_MALAYALAM_AU_LENGTH_MARK 0x0d57 #define UNITEXT_MALAYALAM_AU_LENGTH_MARK L"\u0d57" #define UNICODE_MALAYALAM_LETTER_VOCALIC_RR 0x0d60 #define UNITEXT_MALAYALAM_LETTER_VOCALIC_RR L"\u0d60" #define UNICODE_MALAYALAM_LETTER_VOCALIC_LL 0x0d61 #define UNITEXT_MALAYALAM_LETTER_VOCALIC_LL L"\u0d61" #define UNICODE_MALAYALAM_DIGIT_ZERO 0x0d66 #define UNITEXT_MALAYALAM_DIGIT_ZERO L"\u0d66" #define UNICODE_MALAYALAM_DIGIT_ONE 0x0d67 #define UNITEXT_MALAYALAM_DIGIT_ONE L"\u0d67" #define UNICODE_MALAYALAM_DIGIT_TWO 0x0d68 #define UNITEXT_MALAYALAM_DIGIT_TWO L"\u0d68" #define UNICODE_MALAYALAM_DIGIT_THREE 0x0d69 #define UNITEXT_MALAYALAM_DIGIT_THREE L"\u0d69" #define UNICODE_MALAYALAM_DIGIT_FOUR 0x0d6a #define UNITEXT_MALAYALAM_DIGIT_FOUR L"\u0d6a" #define UNICODE_MALAYALAM_DIGIT_FIVE 0x0d6b #define UNITEXT_MALAYALAM_DIGIT_FIVE L"\u0d6b" #define UNICODE_MALAYALAM_DIGIT_SIX 0x0d6c #define UNITEXT_MALAYALAM_DIGIT_SIX L"\u0d6c" #define UNICODE_MALAYALAM_DIGIT_SEVEN 0x0d6d #define UNITEXT_MALAYALAM_DIGIT_SEVEN L"\u0d6d" #define UNICODE_MALAYALAM_DIGIT_EIGHT 0x0d6e #define UNITEXT_MALAYALAM_DIGIT_EIGHT L"\u0d6e" #define UNICODE_MALAYALAM_DIGIT_NINE 0x0d6f #define UNITEXT_MALAYALAM_DIGIT_NINE L"\u0d6f" #define UNICODE_SINHALA_SIGN_ANUSVARAYA 0x0d82 #define UNITEXT_SINHALA_SIGN_ANUSVARAYA L"\u0d82" #define UNICODE_SINHALA_SIGN_VISARGAYA 0x0d83 #define UNITEXT_SINHALA_SIGN_VISARGAYA L"\u0d83" #define UNICODE_SINHALA_LETTER_AYANNA 0x0d85 #define UNITEXT_SINHALA_LETTER_AYANNA L"\u0d85" #define UNICODE_SINHALA_LETTER_AAYANNA 0x0d86 #define UNITEXT_SINHALA_LETTER_AAYANNA L"\u0d86" #define UNICODE_SINHALA_LETTER_AEYANNA 0x0d87 #define UNITEXT_SINHALA_LETTER_AEYANNA L"\u0d87" #define UNICODE_SINHALA_LETTER_AEEYANNA 0x0d88 #define UNITEXT_SINHALA_LETTER_AEEYANNA L"\u0d88" #define UNICODE_SINHALA_LETTER_IYANNA 0x0d89 #define UNITEXT_SINHALA_LETTER_IYANNA L"\u0d89" #define UNICODE_SINHALA_LETTER_IIYANNA 0x0d8a #define UNITEXT_SINHALA_LETTER_IIYANNA L"\u0d8a" #define UNICODE_SINHALA_LETTER_UYANNA 0x0d8b #define UNITEXT_SINHALA_LETTER_UYANNA L"\u0d8b" #define UNICODE_SINHALA_LETTER_UUYANNA 0x0d8c #define UNITEXT_SINHALA_LETTER_UUYANNA L"\u0d8c" #define UNICODE_SINHALA_LETTER_IRUYANNA 0x0d8d #define UNITEXT_SINHALA_LETTER_IRUYANNA L"\u0d8d" #define UNICODE_SINHALA_LETTER_IRUUYANNA 0x0d8e #define UNITEXT_SINHALA_LETTER_IRUUYANNA L"\u0d8e" #define UNICODE_SINHALA_LETTER_ILUYANNA 0x0d8f #define UNITEXT_SINHALA_LETTER_ILUYANNA L"\u0d8f" #define UNICODE_SINHALA_LETTER_ILUUYANNA 0x0d90 #define UNITEXT_SINHALA_LETTER_ILUUYANNA L"\u0d90" #define UNICODE_SINHALA_LETTER_EYANNA 0x0d91 #define UNITEXT_SINHALA_LETTER_EYANNA L"\u0d91" #define UNICODE_SINHALA_LETTER_EEYANNA 0x0d92 #define UNITEXT_SINHALA_LETTER_EEYANNA L"\u0d92" #define UNICODE_SINHALA_LETTER_AIYANNA 0x0d93 #define UNITEXT_SINHALA_LETTER_AIYANNA L"\u0d93" #define UNICODE_SINHALA_LETTER_OYANNA 0x0d94 #define UNITEXT_SINHALA_LETTER_OYANNA L"\u0d94" #define UNICODE_SINHALA_LETTER_OOYANNA 0x0d95 #define UNITEXT_SINHALA_LETTER_OOYANNA L"\u0d95" #define UNICODE_SINHALA_LETTER_AUYANNA 0x0d96 #define UNITEXT_SINHALA_LETTER_AUYANNA L"\u0d96" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_KAYANNA 0x0d9a #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_KAYANNA L"\u0d9a" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_KAYANNA 0x0d9b #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_KAYANNA L"\u0d9b" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_GAYANNA 0x0d9c #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_GAYANNA L"\u0d9c" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_GAYANNA 0x0d9d #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_GAYANNA L"\u0d9d" #define UNICODE_SINHALA_LETTER_KANTAJA_NAASIKYAYA 0x0d9e #define UNITEXT_SINHALA_LETTER_KANTAJA_NAASIKYAYA L"\u0d9e" #define UNICODE_SINHALA_LETTER_SANYAKA_GAYANNA 0x0d9f #define UNITEXT_SINHALA_LETTER_SANYAKA_GAYANNA L"\u0d9f" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_CAYANNA 0x0da0 #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_CAYANNA L"\u0da0" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_CAYANNA 0x0da1 #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_CAYANNA L"\u0da1" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_JAYANNA 0x0da2 #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_JAYANNA L"\u0da2" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_JAYANNA 0x0da3 #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_JAYANNA L"\u0da3" #define UNICODE_SINHALA_LETTER_TAALUJA_NAASIKYAYA 0x0da4 #define UNITEXT_SINHALA_LETTER_TAALUJA_NAASIKYAYA L"\u0da4" #define UNICODE_SINHALA_LETTER_TAALUJA_SANYOOGA_NAAKSIKYAYA 0x0da5 #define UNITEXT_SINHALA_LETTER_TAALUJA_SANYOOGA_NAAKSIKYAYA L"\u0da5" #define UNICODE_SINHALA_LETTER_SANYAKA_JAYANNA 0x0da6 #define UNITEXT_SINHALA_LETTER_SANYAKA_JAYANNA L"\u0da6" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_TTAYANNA 0x0da7 #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_TTAYANNA L"\u0da7" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_TTAYANNA 0x0da8 #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_TTAYANNA L"\u0da8" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_DDAYANNA 0x0da9 #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_DDAYANNA L"\u0da9" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_DDAYANNA 0x0daa #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_DDAYANNA L"\u0daa" #define UNICODE_SINHALA_LETTER_MUURDHAJA_NAYANNA 0x0dab #define UNITEXT_SINHALA_LETTER_MUURDHAJA_NAYANNA L"\u0dab" #define UNICODE_SINHALA_LETTER_SANYAKA_DDAYANNA 0x0dac #define UNITEXT_SINHALA_LETTER_SANYAKA_DDAYANNA L"\u0dac" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_TAYANNA 0x0dad #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_TAYANNA L"\u0dad" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_TAYANNA 0x0dae #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_TAYANNA L"\u0dae" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_DAYANNA 0x0daf #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_DAYANNA L"\u0daf" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_DAYANNA 0x0db0 #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_DAYANNA L"\u0db0" #define UNICODE_SINHALA_LETTER_DANTAJA_NAYANNA 0x0db1 #define UNITEXT_SINHALA_LETTER_DANTAJA_NAYANNA L"\u0db1" #define UNICODE_SINHALA_LETTER_SANYAKA_DAYANNA 0x0db3 #define UNITEXT_SINHALA_LETTER_SANYAKA_DAYANNA L"\u0db3" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_PAYANNA 0x0db4 #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_PAYANNA L"\u0db4" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_PAYANNA 0x0db5 #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_PAYANNA L"\u0db5" #define UNICODE_SINHALA_LETTER_ALPAPRAANA_BAYANNA 0x0db6 #define UNITEXT_SINHALA_LETTER_ALPAPRAANA_BAYANNA L"\u0db6" #define UNICODE_SINHALA_LETTER_MAHAAPRAANA_BAYANNA 0x0db7 #define UNITEXT_SINHALA_LETTER_MAHAAPRAANA_BAYANNA L"\u0db7" #define UNICODE_SINHALA_LETTER_MAYANNA 0x0db8 #define UNITEXT_SINHALA_LETTER_MAYANNA L"\u0db8" #define UNICODE_SINHALA_LETTER_AMBA_BAYANNA 0x0db9 #define UNITEXT_SINHALA_LETTER_AMBA_BAYANNA L"\u0db9" #define UNICODE_SINHALA_LETTER_YAYANNA 0x0dba #define UNITEXT_SINHALA_LETTER_YAYANNA L"\u0dba" #define UNICODE_SINHALA_LETTER_RAYANNA 0x0dbb #define UNITEXT_SINHALA_LETTER_RAYANNA L"\u0dbb" #define UNICODE_SINHALA_LETTER_DANTAJA_LAYANNA 0x0dbd #define UNITEXT_SINHALA_LETTER_DANTAJA_LAYANNA L"\u0dbd" #define UNICODE_SINHALA_LETTER_VAYANNA 0x0dc0 #define UNITEXT_SINHALA_LETTER_VAYANNA L"\u0dc0" #define UNICODE_SINHALA_LETTER_TAALUJA_SAYANNA 0x0dc1 #define UNITEXT_SINHALA_LETTER_TAALUJA_SAYANNA L"\u0dc1" #define UNICODE_SINHALA_LETTER_MUURDHAJA_SAYANNA 0x0dc2 #define UNITEXT_SINHALA_LETTER_MUURDHAJA_SAYANNA L"\u0dc2" #define UNICODE_SINHALA_LETTER_DANTAJA_SAYANNA 0x0dc3 #define UNITEXT_SINHALA_LETTER_DANTAJA_SAYANNA L"\u0dc3" #define UNICODE_SINHALA_LETTER_HAYANNA 0x0dc4 #define UNITEXT_SINHALA_LETTER_HAYANNA L"\u0dc4" #define UNICODE_SINHALA_LETTER_MUURDHAJA_LAYANNA 0x0dc5 #define UNITEXT_SINHALA_LETTER_MUURDHAJA_LAYANNA L"\u0dc5" #define UNICODE_SINHALA_LETTER_FAYANNA 0x0dc6 #define UNITEXT_SINHALA_LETTER_FAYANNA L"\u0dc6" #define UNICODE_SINHALA_SIGN_AL_LAKUNA 0x0dca #define UNITEXT_SINHALA_SIGN_AL_LAKUNA L"\u0dca" #define UNICODE_SINHALA_VOWEL_SIGN_AELA_PILLA 0x0dcf #define UNITEXT_SINHALA_VOWEL_SIGN_AELA_PILLA L"\u0dcf" #define UNICODE_SINHALA_VOWEL_SIGN_KETTI_AEDA_PILLA 0x0dd0 #define UNITEXT_SINHALA_VOWEL_SIGN_KETTI_AEDA_PILLA L"\u0dd0" #define UNICODE_SINHALA_VOWEL_SIGN_DIGA_AEDA_PILLA 0x0dd1 #define UNITEXT_SINHALA_VOWEL_SIGN_DIGA_AEDA_PILLA L"\u0dd1" #define UNICODE_SINHALA_VOWEL_SIGN_KETTI_IS_PILLA 0x0dd2 #define UNITEXT_SINHALA_VOWEL_SIGN_KETTI_IS_PILLA L"\u0dd2" #define UNICODE_SINHALA_VOWEL_SIGN_DIGA_IS_PILLA 0x0dd3 #define UNITEXT_SINHALA_VOWEL_SIGN_DIGA_IS_PILLA L"\u0dd3" #define UNICODE_SINHALA_VOWEL_SIGN_KETTI_PAA_PILLA 0x0dd4 #define UNITEXT_SINHALA_VOWEL_SIGN_KETTI_PAA_PILLA L"\u0dd4" #define UNICODE_SINHALA_VOWEL_SIGN_DIGA_PAA_PILLA 0x0dd6 #define UNITEXT_SINHALA_VOWEL_SIGN_DIGA_PAA_PILLA L"\u0dd6" #define UNICODE_SINHALA_VOWEL_SIGN_GAETTA_PILLA 0x0dd8 #define UNITEXT_SINHALA_VOWEL_SIGN_GAETTA_PILLA L"\u0dd8" #define UNICODE_SINHALA_VOWEL_SIGN_KOMBUVA 0x0dd9 #define UNITEXT_SINHALA_VOWEL_SIGN_KOMBUVA L"\u0dd9" #define UNICODE_SINHALA_VOWEL_SIGN_DIGA_KOMBUVA 0x0dda #define UNITEXT_SINHALA_VOWEL_SIGN_DIGA_KOMBUVA L"\u0dda" #define UNICODE_SINHALA_VOWEL_SIGN_KOMBU_DEKA 0x0ddb #define UNITEXT_SINHALA_VOWEL_SIGN_KOMBU_DEKA L"\u0ddb" #define UNICODE_SINHALA_VOWEL_SIGN_KOMBUVA_HAA_AELA_PILLA 0x0ddc #define UNITEXT_SINHALA_VOWEL_SIGN_KOMBUVA_HAA_AELA_PILLA L"\u0ddc" #define UNICODE_SINHALA_VOWEL_SIGN_KOMBUVA_HAA_DIGA_AELA_PILLA 0x0ddd #define UNITEXT_SINHALA_VOWEL_SIGN_KOMBUVA_HAA_DIGA_AELA_PILLA L"\u0ddd" #define UNICODE_SINHALA_VOWEL_SIGN_KOMBUVA_HAA_GAYANUKITTA 0x0dde #define UNITEXT_SINHALA_VOWEL_SIGN_KOMBUVA_HAA_GAYANUKITTA L"\u0dde" #define UNICODE_SINHALA_VOWEL_SIGN_GAYANUKITTA 0x0ddf #define UNITEXT_SINHALA_VOWEL_SIGN_GAYANUKITTA L"\u0ddf" #define UNICODE_SINHALA_VOWEL_SIGN_DIGA_GAETTA_PILLA 0x0df2 #define UNITEXT_SINHALA_VOWEL_SIGN_DIGA_GAETTA_PILLA L"\u0df2" #define UNICODE_SINHALA_VOWEL_SIGN_DIGA_GAYANUKITTA 0x0df3 #define UNITEXT_SINHALA_VOWEL_SIGN_DIGA_GAYANUKITTA L"\u0df3" #define UNICODE_SINHALA_PUNCTUATION_KUNDDALIYA 0x0df4 #define UNITEXT_SINHALA_PUNCTUATION_KUNDDALIYA L"\u0df4" #define UNICODE_THAI_CHARACTER_KO_KAI 0x0e01 #define UNITEXT_THAI_CHARACTER_KO_KAI L"\u0e01" #define UNICODE_THAI_CHARACTER_KHO_KHAI 0x0e02 #define UNITEXT_THAI_CHARACTER_KHO_KHAI L"\u0e02" #define UNICODE_THAI_CHARACTER_KHO_KHUAT 0x0e03 #define UNITEXT_THAI_CHARACTER_KHO_KHUAT L"\u0e03" #define UNICODE_THAI_CHARACTER_KHO_KHWAI 0x0e04 #define UNITEXT_THAI_CHARACTER_KHO_KHWAI L"\u0e04" #define UNICODE_THAI_CHARACTER_KHO_KHON 0x0e05 #define UNITEXT_THAI_CHARACTER_KHO_KHON L"\u0e05" #define UNICODE_THAI_CHARACTER_KHO_RAKHANG 0x0e06 #define UNITEXT_THAI_CHARACTER_KHO_RAKHANG L"\u0e06" #define UNICODE_THAI_CHARACTER_NGO_NGU 0x0e07 #define UNITEXT_THAI_CHARACTER_NGO_NGU L"\u0e07" #define UNICODE_THAI_CHARACTER_CHO_CHAN 0x0e08 #define UNITEXT_THAI_CHARACTER_CHO_CHAN L"\u0e08" #define UNICODE_THAI_CHARACTER_CHO_CHING 0x0e09 #define UNITEXT_THAI_CHARACTER_CHO_CHING L"\u0e09" #define UNICODE_THAI_CHARACTER_CHO_CHANG 0x0e0a #define UNITEXT_THAI_CHARACTER_CHO_CHANG L"\u0e0a" #define UNICODE_THAI_CHARACTER_SO_SO 0x0e0b #define UNITEXT_THAI_CHARACTER_SO_SO L"\u0e0b" #define UNICODE_THAI_CHARACTER_CHO_CHOE 0x0e0c #define UNITEXT_THAI_CHARACTER_CHO_CHOE L"\u0e0c" #define UNICODE_THAI_CHARACTER_YO_YING 0x0e0d #define UNITEXT_THAI_CHARACTER_YO_YING L"\u0e0d" #define UNICODE_THAI_CHARACTER_DO_CHADA 0x0e0e #define UNITEXT_THAI_CHARACTER_DO_CHADA L"\u0e0e" #define UNICODE_THAI_CHARACTER_TO_PATAK 0x0e0f #define UNITEXT_THAI_CHARACTER_TO_PATAK L"\u0e0f" #define UNICODE_THAI_CHARACTER_THO_THAN 0x0e10 #define UNITEXT_THAI_CHARACTER_THO_THAN L"\u0e10" #define UNICODE_THAI_CHARACTER_THO_NANGMONTHO 0x0e11 #define UNITEXT_THAI_CHARACTER_THO_NANGMONTHO L"\u0e11" #define UNICODE_THAI_CHARACTER_THO_PHUTHAO 0x0e12 #define UNITEXT_THAI_CHARACTER_THO_PHUTHAO L"\u0e12" #define UNICODE_THAI_CHARACTER_NO_NEN 0x0e13 #define UNITEXT_THAI_CHARACTER_NO_NEN L"\u0e13" #define UNICODE_THAI_CHARACTER_DO_DEK 0x0e14 #define UNITEXT_THAI_CHARACTER_DO_DEK L"\u0e14" #define UNICODE_THAI_CHARACTER_TO_TAO 0x0e15 #define UNITEXT_THAI_CHARACTER_TO_TAO L"\u0e15" #define UNICODE_THAI_CHARACTER_THO_THUNG 0x0e16 #define UNITEXT_THAI_CHARACTER_THO_THUNG L"\u0e16" #define UNICODE_THAI_CHARACTER_THO_THAHAN 0x0e17 #define UNITEXT_THAI_CHARACTER_THO_THAHAN L"\u0e17" #define UNICODE_THAI_CHARACTER_THO_THONG 0x0e18 #define UNITEXT_THAI_CHARACTER_THO_THONG L"\u0e18" #define UNICODE_THAI_CHARACTER_NO_NU 0x0e19 #define UNITEXT_THAI_CHARACTER_NO_NU L"\u0e19" #define UNICODE_THAI_CHARACTER_BO_BAIMAI 0x0e1a #define UNITEXT_THAI_CHARACTER_BO_BAIMAI L"\u0e1a" #define UNICODE_THAI_CHARACTER_PO_PLA 0x0e1b #define UNITEXT_THAI_CHARACTER_PO_PLA L"\u0e1b" #define UNICODE_THAI_CHARACTER_PHO_PHUNG 0x0e1c #define UNITEXT_THAI_CHARACTER_PHO_PHUNG L"\u0e1c" #define UNICODE_THAI_CHARACTER_FO_FA 0x0e1d #define UNITEXT_THAI_CHARACTER_FO_FA L"\u0e1d" #define UNICODE_THAI_CHARACTER_PHO_PHAN 0x0e1e #define UNITEXT_THAI_CHARACTER_PHO_PHAN L"\u0e1e" #define UNICODE_THAI_CHARACTER_FO_FAN 0x0e1f #define UNITEXT_THAI_CHARACTER_FO_FAN L"\u0e1f" #define UNICODE_THAI_CHARACTER_PHO_SAMPHAO 0x0e20 #define UNITEXT_THAI_CHARACTER_PHO_SAMPHAO L"\u0e20" #define UNICODE_THAI_CHARACTER_MO_MA 0x0e21 #define UNITEXT_THAI_CHARACTER_MO_MA L"\u0e21" #define UNICODE_THAI_CHARACTER_YO_YAK 0x0e22 #define UNITEXT_THAI_CHARACTER_YO_YAK L"\u0e22" #define UNICODE_THAI_CHARACTER_RO_RUA 0x0e23 #define UNITEXT_THAI_CHARACTER_RO_RUA L"\u0e23" #define UNICODE_THAI_CHARACTER_RU 0x0e24 #define UNITEXT_THAI_CHARACTER_RU L"\u0e24" #define UNICODE_THAI_CHARACTER_LO_LING 0x0e25 #define UNITEXT_THAI_CHARACTER_LO_LING L"\u0e25" #define UNICODE_THAI_CHARACTER_LU 0x0e26 #define UNITEXT_THAI_CHARACTER_LU L"\u0e26" #define UNICODE_THAI_CHARACTER_WO_WAEN 0x0e27 #define UNITEXT_THAI_CHARACTER_WO_WAEN L"\u0e27" #define UNICODE_THAI_CHARACTER_SO_SALA 0x0e28 #define UNITEXT_THAI_CHARACTER_SO_SALA L"\u0e28" #define UNICODE_THAI_CHARACTER_SO_RUSI 0x0e29 #define UNITEXT_THAI_CHARACTER_SO_RUSI L"\u0e29" #define UNICODE_THAI_CHARACTER_SO_SUA 0x0e2a #define UNITEXT_THAI_CHARACTER_SO_SUA L"\u0e2a" #define UNICODE_THAI_CHARACTER_HO_HIP 0x0e2b #define UNITEXT_THAI_CHARACTER_HO_HIP L"\u0e2b" #define UNICODE_THAI_CHARACTER_LO_CHULA 0x0e2c #define UNITEXT_THAI_CHARACTER_LO_CHULA L"\u0e2c" #define UNICODE_THAI_CHARACTER_O_ANG 0x0e2d #define UNITEXT_THAI_CHARACTER_O_ANG L"\u0e2d" #define UNICODE_THAI_CHARACTER_HO_NOKHUK 0x0e2e #define UNITEXT_THAI_CHARACTER_HO_NOKHUK L"\u0e2e" #define UNICODE_THAI_CHARACTER_PAIYANNOI 0x0e2f #define UNITEXT_THAI_CHARACTER_PAIYANNOI L"\u0e2f" #define UNICODE_THAI_CHARACTER_SARA_A 0x0e30 #define UNITEXT_THAI_CHARACTER_SARA_A L"\u0e30" #define UNICODE_THAI_CHARACTER_MAI_HAN_AKAT 0x0e31 #define UNITEXT_THAI_CHARACTER_MAI_HAN_AKAT L"\u0e31" #define UNICODE_THAI_CHARACTER_SARA_AA 0x0e32 #define UNITEXT_THAI_CHARACTER_SARA_AA L"\u0e32" #define UNICODE_THAI_CHARACTER_SARA_AM 0x0e33 #define UNITEXT_THAI_CHARACTER_SARA_AM L"\u0e33" #define UNICODE_THAI_CHARACTER_SARA_I 0x0e34 #define UNITEXT_THAI_CHARACTER_SARA_I L"\u0e34" #define UNICODE_THAI_CHARACTER_SARA_II 0x0e35 #define UNITEXT_THAI_CHARACTER_SARA_II L"\u0e35" #define UNICODE_THAI_CHARACTER_SARA_UE 0x0e36 #define UNITEXT_THAI_CHARACTER_SARA_UE L"\u0e36" #define UNICODE_THAI_CHARACTER_SARA_UEE 0x0e37 #define UNITEXT_THAI_CHARACTER_SARA_UEE L"\u0e37" #define UNICODE_THAI_CHARACTER_SARA_U 0x0e38 #define UNITEXT_THAI_CHARACTER_SARA_U L"\u0e38" #define UNICODE_THAI_CHARACTER_SARA_UU 0x0e39 #define UNITEXT_THAI_CHARACTER_SARA_UU L"\u0e39" #define UNICODE_THAI_CHARACTER_PHINTHU 0x0e3a #define UNITEXT_THAI_CHARACTER_PHINTHU L"\u0e3a" #define UNICODE_THAI_CURRENCY_SYMBOL_BAHT 0x0e3f #define UNITEXT_THAI_CURRENCY_SYMBOL_BAHT L"\u0e3f" #define UNICODE_THAI_CHARACTER_SARA_E 0x0e40 #define UNITEXT_THAI_CHARACTER_SARA_E L"\u0e40" #define UNICODE_THAI_CHARACTER_SARA_AE 0x0e41 #define UNITEXT_THAI_CHARACTER_SARA_AE L"\u0e41" #define UNICODE_THAI_CHARACTER_SARA_O 0x0e42 #define UNITEXT_THAI_CHARACTER_SARA_O L"\u0e42" #define UNICODE_THAI_CHARACTER_SARA_AI_MAIMUAN 0x0e43 #define UNITEXT_THAI_CHARACTER_SARA_AI_MAIMUAN L"\u0e43" #define UNICODE_THAI_CHARACTER_SARA_AI_MAIMALAI 0x0e44 #define UNITEXT_THAI_CHARACTER_SARA_AI_MAIMALAI L"\u0e44" #define UNICODE_THAI_CHARACTER_LAKKHANGYAO 0x0e45 #define UNITEXT_THAI_CHARACTER_LAKKHANGYAO L"\u0e45" #define UNICODE_THAI_CHARACTER_MAIYAMOK 0x0e46 #define UNITEXT_THAI_CHARACTER_MAIYAMOK L"\u0e46" #define UNICODE_THAI_CHARACTER_MAITAIKHU 0x0e47 #define UNITEXT_THAI_CHARACTER_MAITAIKHU L"\u0e47" #define UNICODE_THAI_CHARACTER_MAI_EK 0x0e48 #define UNITEXT_THAI_CHARACTER_MAI_EK L"\u0e48" #define UNICODE_THAI_CHARACTER_MAI_THO 0x0e49 #define UNITEXT_THAI_CHARACTER_MAI_THO L"\u0e49" #define UNICODE_THAI_CHARACTER_MAI_TRI 0x0e4a #define UNITEXT_THAI_CHARACTER_MAI_TRI L"\u0e4a" #define UNICODE_THAI_CHARACTER_MAI_CHATTAWA 0x0e4b #define UNITEXT_THAI_CHARACTER_MAI_CHATTAWA L"\u0e4b" #define UNICODE_THAI_CHARACTER_THANTHAKHAT 0x0e4c #define UNITEXT_THAI_CHARACTER_THANTHAKHAT L"\u0e4c" #define UNICODE_THAI_CHARACTER_NIKHAHIT 0x0e4d #define UNITEXT_THAI_CHARACTER_NIKHAHIT L"\u0e4d" #define UNICODE_THAI_CHARACTER_YAMAKKAN 0x0e4e #define UNITEXT_THAI_CHARACTER_YAMAKKAN L"\u0e4e" #define UNICODE_THAI_CHARACTER_FONGMAN 0x0e4f #define UNITEXT_THAI_CHARACTER_FONGMAN L"\u0e4f" #define UNICODE_THAI_DIGIT_ZERO 0x0e50 #define UNITEXT_THAI_DIGIT_ZERO L"\u0e50" #define UNICODE_THAI_DIGIT_ONE 0x0e51 #define UNITEXT_THAI_DIGIT_ONE L"\u0e51" #define UNICODE_THAI_DIGIT_TWO 0x0e52 #define UNITEXT_THAI_DIGIT_TWO L"\u0e52" #define UNICODE_THAI_DIGIT_THREE 0x0e53 #define UNITEXT_THAI_DIGIT_THREE L"\u0e53" #define UNICODE_THAI_DIGIT_FOUR 0x0e54 #define UNITEXT_THAI_DIGIT_FOUR L"\u0e54" #define UNICODE_THAI_DIGIT_FIVE 0x0e55 #define UNITEXT_THAI_DIGIT_FIVE L"\u0e55" #define UNICODE_THAI_DIGIT_SIX 0x0e56 #define UNITEXT_THAI_DIGIT_SIX L"\u0e56" #define UNICODE_THAI_DIGIT_SEVEN 0x0e57 #define UNITEXT_THAI_DIGIT_SEVEN L"\u0e57" #define UNICODE_THAI_DIGIT_EIGHT 0x0e58 #define UNITEXT_THAI_DIGIT_EIGHT L"\u0e58" #define UNICODE_THAI_DIGIT_NINE 0x0e59 #define UNITEXT_THAI_DIGIT_NINE L"\u0e59" #define UNICODE_THAI_CHARACTER_ANGKHANKHU 0x0e5a #define UNITEXT_THAI_CHARACTER_ANGKHANKHU L"\u0e5a" #define UNICODE_THAI_CHARACTER_KHOMUT 0x0e5b #define UNITEXT_THAI_CHARACTER_KHOMUT L"\u0e5b" #define UNICODE_LAO_LETTER_KO 0x0e81 #define UNITEXT_LAO_LETTER_KO L"\u0e81" #define UNICODE_LAO_LETTER_KHO_SUNG 0x0e82 #define UNITEXT_LAO_LETTER_KHO_SUNG L"\u0e82" #define UNICODE_LAO_LETTER_KHO_TAM 0x0e84 #define UNITEXT_LAO_LETTER_KHO_TAM L"\u0e84" #define UNICODE_LAO_LETTER_NGO 0x0e87 #define UNITEXT_LAO_LETTER_NGO L"\u0e87" #define UNICODE_LAO_LETTER_CO 0x0e88 #define UNITEXT_LAO_LETTER_CO L"\u0e88" #define UNICODE_LAO_LETTER_SO_TAM 0x0e8a #define UNITEXT_LAO_LETTER_SO_TAM L"\u0e8a" #define UNICODE_LAO_LETTER_NYO 0x0e8d #define UNITEXT_LAO_LETTER_NYO L"\u0e8d" #define UNICODE_LAO_LETTER_DO 0x0e94 #define UNITEXT_LAO_LETTER_DO L"\u0e94" #define UNICODE_LAO_LETTER_TO 0x0e95 #define UNITEXT_LAO_LETTER_TO L"\u0e95" #define UNICODE_LAO_LETTER_THO_SUNG 0x0e96 #define UNITEXT_LAO_LETTER_THO_SUNG L"\u0e96" #define UNICODE_LAO_LETTER_THO_TAM 0x0e97 #define UNITEXT_LAO_LETTER_THO_TAM L"\u0e97" #define UNICODE_LAO_LETTER_NO 0x0e99 #define UNITEXT_LAO_LETTER_NO L"\u0e99" #define UNICODE_LAO_LETTER_BO 0x0e9a #define UNITEXT_LAO_LETTER_BO L"\u0e9a" #define UNICODE_LAO_LETTER_PO 0x0e9b #define UNITEXT_LAO_LETTER_PO L"\u0e9b" #define UNICODE_LAO_LETTER_PHO_SUNG 0x0e9c #define UNITEXT_LAO_LETTER_PHO_SUNG L"\u0e9c" #define UNICODE_LAO_LETTER_FO_TAM 0x0e9d #define UNITEXT_LAO_LETTER_FO_TAM L"\u0e9d" #define UNICODE_LAO_LETTER_PHO_TAM 0x0e9e #define UNITEXT_LAO_LETTER_PHO_TAM L"\u0e9e" #define UNICODE_LAO_LETTER_FO_SUNG 0x0e9f #define UNITEXT_LAO_LETTER_FO_SUNG L"\u0e9f" #define UNICODE_LAO_LETTER_MO 0x0ea1 #define UNITEXT_LAO_LETTER_MO L"\u0ea1" #define UNICODE_LAO_LETTER_YO 0x0ea2 #define UNITEXT_LAO_LETTER_YO L"\u0ea2" #define UNICODE_LAO_LETTER_LO_LING 0x0ea3 #define UNITEXT_LAO_LETTER_LO_LING L"\u0ea3" #define UNICODE_LAO_LETTER_LO_LOOT 0x0ea5 #define UNITEXT_LAO_LETTER_LO_LOOT L"\u0ea5" #define UNICODE_LAO_LETTER_WO 0x0ea7 #define UNITEXT_LAO_LETTER_WO L"\u0ea7" #define UNICODE_LAO_LETTER_SO_SUNG 0x0eaa #define UNITEXT_LAO_LETTER_SO_SUNG L"\u0eaa" #define UNICODE_LAO_LETTER_HO_SUNG 0x0eab #define UNITEXT_LAO_LETTER_HO_SUNG L"\u0eab" #define UNICODE_LAO_LETTER_O 0x0ead #define UNITEXT_LAO_LETTER_O L"\u0ead" #define UNICODE_LAO_LETTER_HO_TAM 0x0eae #define UNITEXT_LAO_LETTER_HO_TAM L"\u0eae" #define UNICODE_LAO_ELLIPSIS 0x0eaf #define UNITEXT_LAO_ELLIPSIS L"\u0eaf" #define UNICODE_LAO_VOWEL_SIGN_A 0x0eb0 #define UNITEXT_LAO_VOWEL_SIGN_A L"\u0eb0" #define UNICODE_LAO_VOWEL_SIGN_MAI_KAN 0x0eb1 #define UNITEXT_LAO_VOWEL_SIGN_MAI_KAN L"\u0eb1" #define UNICODE_LAO_VOWEL_SIGN_AA 0x0eb2 #define UNITEXT_LAO_VOWEL_SIGN_AA L"\u0eb2" #define UNICODE_LAO_VOWEL_SIGN_AM 0x0eb3 #define UNITEXT_LAO_VOWEL_SIGN_AM L"\u0eb3" #define UNICODE_LAO_VOWEL_SIGN_I 0x0eb4 #define UNITEXT_LAO_VOWEL_SIGN_I L"\u0eb4" #define UNICODE_LAO_VOWEL_SIGN_II 0x0eb5 #define UNITEXT_LAO_VOWEL_SIGN_II L"\u0eb5" #define UNICODE_LAO_VOWEL_SIGN_Y 0x0eb6 #define UNITEXT_LAO_VOWEL_SIGN_Y L"\u0eb6" #define UNICODE_LAO_VOWEL_SIGN_YY 0x0eb7 #define UNITEXT_LAO_VOWEL_SIGN_YY L"\u0eb7" #define UNICODE_LAO_VOWEL_SIGN_U 0x0eb8 #define UNITEXT_LAO_VOWEL_SIGN_U L"\u0eb8" #define UNICODE_LAO_VOWEL_SIGN_UU 0x0eb9 #define UNITEXT_LAO_VOWEL_SIGN_UU L"\u0eb9" #define UNICODE_LAO_VOWEL_SIGN_MAI_KON 0x0ebb #define UNITEXT_LAO_VOWEL_SIGN_MAI_KON L"\u0ebb" #define UNICODE_LAO_SEMIVOWEL_SIGN_LO 0x0ebc #define UNITEXT_LAO_SEMIVOWEL_SIGN_LO L"\u0ebc" #define UNICODE_LAO_SEMIVOWEL_SIGN_NYO 0x0ebd #define UNITEXT_LAO_SEMIVOWEL_SIGN_NYO L"\u0ebd" #define UNICODE_LAO_VOWEL_SIGN_E 0x0ec0 #define UNITEXT_LAO_VOWEL_SIGN_E L"\u0ec0" #define UNICODE_LAO_VOWEL_SIGN_EI 0x0ec1 #define UNITEXT_LAO_VOWEL_SIGN_EI L"\u0ec1" #define UNICODE_LAO_VOWEL_SIGN_O 0x0ec2 #define UNITEXT_LAO_VOWEL_SIGN_O L"\u0ec2" #define UNICODE_LAO_VOWEL_SIGN_AY 0x0ec3 #define UNITEXT_LAO_VOWEL_SIGN_AY L"\u0ec3" #define UNICODE_LAO_VOWEL_SIGN_AI 0x0ec4 #define UNITEXT_LAO_VOWEL_SIGN_AI L"\u0ec4" #define UNICODE_LAO_KO_LA 0x0ec6 #define UNITEXT_LAO_KO_LA L"\u0ec6" #define UNICODE_LAO_TONE_MAI_EK 0x0ec8 #define UNITEXT_LAO_TONE_MAI_EK L"\u0ec8" #define UNICODE_LAO_TONE_MAI_THO 0x0ec9 #define UNITEXT_LAO_TONE_MAI_THO L"\u0ec9" #define UNICODE_LAO_TONE_MAI_TI 0x0eca #define UNITEXT_LAO_TONE_MAI_TI L"\u0eca" #define UNICODE_LAO_TONE_MAI_CATAWA 0x0ecb #define UNITEXT_LAO_TONE_MAI_CATAWA L"\u0ecb" #define UNICODE_LAO_CANCELLATION_MARK 0x0ecc #define UNITEXT_LAO_CANCELLATION_MARK L"\u0ecc" #define UNICODE_LAO_NIGGAHITA 0x0ecd #define UNITEXT_LAO_NIGGAHITA L"\u0ecd" #define UNICODE_LAO_DIGIT_ZERO 0x0ed0 #define UNITEXT_LAO_DIGIT_ZERO L"\u0ed0" #define UNICODE_LAO_DIGIT_ONE 0x0ed1 #define UNITEXT_LAO_DIGIT_ONE L"\u0ed1" #define UNICODE_LAO_DIGIT_TWO 0x0ed2 #define UNITEXT_LAO_DIGIT_TWO L"\u0ed2" #define UNICODE_LAO_DIGIT_THREE 0x0ed3 #define UNITEXT_LAO_DIGIT_THREE L"\u0ed3" #define UNICODE_LAO_DIGIT_FOUR 0x0ed4 #define UNITEXT_LAO_DIGIT_FOUR L"\u0ed4" #define UNICODE_LAO_DIGIT_FIVE 0x0ed5 #define UNITEXT_LAO_DIGIT_FIVE L"\u0ed5" #define UNICODE_LAO_DIGIT_SIX 0x0ed6 #define UNITEXT_LAO_DIGIT_SIX L"\u0ed6" #define UNICODE_LAO_DIGIT_SEVEN 0x0ed7 #define UNITEXT_LAO_DIGIT_SEVEN L"\u0ed7" #define UNICODE_LAO_DIGIT_EIGHT 0x0ed8 #define UNITEXT_LAO_DIGIT_EIGHT L"\u0ed8" #define UNICODE_LAO_DIGIT_NINE 0x0ed9 #define UNITEXT_LAO_DIGIT_NINE L"\u0ed9" #define UNICODE_LAO_HO_NO 0x0edc #define UNITEXT_LAO_HO_NO L"\u0edc" #define UNICODE_LAO_HO_MO 0x0edd #define UNITEXT_LAO_HO_MO L"\u0edd" #define UNICODE_TIBETAN_SYLLABLE_OM 0x0f00 #define UNITEXT_TIBETAN_SYLLABLE_OM L"\u0f00" #define UNICODE_TIBETAN_MARK_GTER_YIG_MGO_TRUNCATED_A 0x0f01 #define UNITEXT_TIBETAN_MARK_GTER_YIG_MGO_TRUNCATED_A L"\u0f01" #define UNICODE_TIBETAN_MARK_GTER_YIG_MGO__UM_RNAM_BCAD_MA 0x0f02 #define UNITEXT_TIBETAN_MARK_GTER_YIG_MGO__UM_RNAM_BCAD_MA L"\u0f02" #define UNICODE_TIBETAN_MARK_GTER_YIG_MGO__UM_GTER_TSHEG_MA 0x0f03 #define UNITEXT_TIBETAN_MARK_GTER_YIG_MGO__UM_GTER_TSHEG_MA L"\u0f03" #define UNICODE_TIBETAN_MARK_INITIAL_YIG_MGO_MDUN_MA 0x0f04 #define UNITEXT_TIBETAN_MARK_INITIAL_YIG_MGO_MDUN_MA L"\u0f04" #define UNICODE_TIBETAN_MARK_CLOSING_YIG_MGO_SGAB_MA 0x0f05 #define UNITEXT_TIBETAN_MARK_CLOSING_YIG_MGO_SGAB_MA L"\u0f05" #define UNICODE_TIBETAN_MARK_CARET_YIG_MGO_PHUR_SHAD_MA 0x0f06 #define UNITEXT_TIBETAN_MARK_CARET_YIG_MGO_PHUR_SHAD_MA L"\u0f06" #define UNICODE_TIBETAN_MARK_YIG_MGO_TSHEG_SHAD_MA 0x0f07 #define UNITEXT_TIBETAN_MARK_YIG_MGO_TSHEG_SHAD_MA L"\u0f07" #define UNICODE_TIBETAN_MARK_SBRUL_SHAD 0x0f08 #define UNITEXT_TIBETAN_MARK_SBRUL_SHAD L"\u0f08" #define UNICODE_TIBETAN_MARK_BSKUR_YIG_MGO 0x0f09 #define UNITEXT_TIBETAN_MARK_BSKUR_YIG_MGO L"\u0f09" #define UNICODE_TIBETAN_MARK_BKA__SHOG_YIG_MGO 0x0f0a #define UNITEXT_TIBETAN_MARK_BKA__SHOG_YIG_MGO L"\u0f0a" #define UNICODE_TIBETAN_MARK_INTERSYLLABIC_TSHEG 0x0f0b #define UNITEXT_TIBETAN_MARK_INTERSYLLABIC_TSHEG L"\u0f0b" #define UNICODE_TIBETAN_MARK_DELIMITER_TSHEG_BSTAR 0x0f0c #define UNITEXT_TIBETAN_MARK_DELIMITER_TSHEG_BSTAR L"\u0f0c" #define UNICODE_TIBETAN_MARK_SHAD 0x0f0d #define UNITEXT_TIBETAN_MARK_SHAD L"\u0f0d" #define UNICODE_TIBETAN_MARK_NYIS_SHAD 0x0f0e #define UNITEXT_TIBETAN_MARK_NYIS_SHAD L"\u0f0e" #define UNICODE_TIBETAN_MARK_TSHEG_SHAD 0x0f0f #define UNITEXT_TIBETAN_MARK_TSHEG_SHAD L"\u0f0f" #define UNICODE_TIBETAN_MARK_NYIS_TSHEG_SHAD 0x0f10 #define UNITEXT_TIBETAN_MARK_NYIS_TSHEG_SHAD L"\u0f10" #define UNICODE_TIBETAN_MARK_RIN_CHEN_SPUNGS_SHAD 0x0f11 #define UNITEXT_TIBETAN_MARK_RIN_CHEN_SPUNGS_SHAD L"\u0f11" #define UNICODE_TIBETAN_MARK_RGYA_GRAM_SHAD 0x0f12 #define UNITEXT_TIBETAN_MARK_RGYA_GRAM_SHAD L"\u0f12" #define UNICODE_TIBETAN_MARK_CARET__DZUD_RTAGS_ME_LONG_CAN 0x0f13 #define UNITEXT_TIBETAN_MARK_CARET__DZUD_RTAGS_ME_LONG_CAN L"\u0f13" #define UNICODE_TIBETAN_MARK_GTER_TSHEG 0x0f14 #define UNITEXT_TIBETAN_MARK_GTER_TSHEG L"\u0f14" #define UNICODE_TIBETAN_LOGOTYPE_SIGN_CHAD_RTAGS 0x0f15 #define UNITEXT_TIBETAN_LOGOTYPE_SIGN_CHAD_RTAGS L"\u0f15" #define UNICODE_TIBETAN_LOGOTYPE_SIGN_LHAG_RTAGS 0x0f16 #define UNITEXT_TIBETAN_LOGOTYPE_SIGN_LHAG_RTAGS L"\u0f16" #define UNICODE_TIBETAN_ASTROLOGICAL_SIGN_SGRA_GCAN__CHAR_RTAGS 0x0f17 #define UNITEXT_TIBETAN_ASTROLOGICAL_SIGN_SGRA_GCAN__CHAR_RTAGS L"\u0f17" #define UNICODE_TIBETAN_ASTROLOGICAL_SIGN__KHYUD_PA 0x0f18 #define UNITEXT_TIBETAN_ASTROLOGICAL_SIGN__KHYUD_PA L"\u0f18" #define UNICODE_TIBETAN_ASTROLOGICAL_SIGN_SDONG_TSHUGS 0x0f19 #define UNITEXT_TIBETAN_ASTROLOGICAL_SIGN_SDONG_TSHUGS L"\u0f19" #define UNICODE_TIBETAN_SIGN_RDEL_DKAR_GCIG 0x0f1a #define UNITEXT_TIBETAN_SIGN_RDEL_DKAR_GCIG L"\u0f1a" #define UNICODE_TIBETAN_SIGN_RDEL_DKAR_GNYIS 0x0f1b #define UNITEXT_TIBETAN_SIGN_RDEL_DKAR_GNYIS L"\u0f1b" #define UNICODE_TIBETAN_SIGN_RDEL_DKAR_GSUM 0x0f1c #define UNITEXT_TIBETAN_SIGN_RDEL_DKAR_GSUM L"\u0f1c" #define UNICODE_TIBETAN_SIGN_RDEL_NAG_GCIG 0x0f1d #define UNITEXT_TIBETAN_SIGN_RDEL_NAG_GCIG L"\u0f1d" #define UNICODE_TIBETAN_SIGN_RDEL_NAG_GNYIS 0x0f1e #define UNITEXT_TIBETAN_SIGN_RDEL_NAG_GNYIS L"\u0f1e" #define UNICODE_TIBETAN_SIGN_RDEL_DKAR_RDEL_NAG 0x0f1f #define UNITEXT_TIBETAN_SIGN_RDEL_DKAR_RDEL_NAG L"\u0f1f" #define UNICODE_TIBETAN_DIGIT_ZERO 0x0f20 #define UNITEXT_TIBETAN_DIGIT_ZERO L"\u0f20" #define UNICODE_TIBETAN_DIGIT_ONE 0x0f21 #define UNITEXT_TIBETAN_DIGIT_ONE L"\u0f21" #define UNICODE_TIBETAN_DIGIT_TWO 0x0f22 #define UNITEXT_TIBETAN_DIGIT_TWO L"\u0f22" #define UNICODE_TIBETAN_DIGIT_THREE 0x0f23 #define UNITEXT_TIBETAN_DIGIT_THREE L"\u0f23" #define UNICODE_TIBETAN_DIGIT_FOUR 0x0f24 #define UNITEXT_TIBETAN_DIGIT_FOUR L"\u0f24" #define UNICODE_TIBETAN_DIGIT_FIVE 0x0f25 #define UNITEXT_TIBETAN_DIGIT_FIVE L"\u0f25" #define UNICODE_TIBETAN_DIGIT_SIX 0x0f26 #define UNITEXT_TIBETAN_DIGIT_SIX L"\u0f26" #define UNICODE_TIBETAN_DIGIT_SEVEN 0x0f27 #define UNITEXT_TIBETAN_DIGIT_SEVEN L"\u0f27" #define UNICODE_TIBETAN_DIGIT_EIGHT 0x0f28 #define UNITEXT_TIBETAN_DIGIT_EIGHT L"\u0f28" #define UNICODE_TIBETAN_DIGIT_NINE 0x0f29 #define UNITEXT_TIBETAN_DIGIT_NINE L"\u0f29" #define UNICODE_TIBETAN_DIGIT_HALF_ONE 0x0f2a #define UNITEXT_TIBETAN_DIGIT_HALF_ONE L"\u0f2a" #define UNICODE_TIBETAN_DIGIT_HALF_TWO 0x0f2b #define UNITEXT_TIBETAN_DIGIT_HALF_TWO L"\u0f2b" #define UNICODE_TIBETAN_DIGIT_HALF_THREE 0x0f2c #define UNITEXT_TIBETAN_DIGIT_HALF_THREE L"\u0f2c" #define UNICODE_TIBETAN_DIGIT_HALF_FOUR 0x0f2d #define UNITEXT_TIBETAN_DIGIT_HALF_FOUR L"\u0f2d" #define UNICODE_TIBETAN_DIGIT_HALF_FIVE 0x0f2e #define UNITEXT_TIBETAN_DIGIT_HALF_FIVE L"\u0f2e" #define UNICODE_TIBETAN_DIGIT_HALF_SIX 0x0f2f #define UNITEXT_TIBETAN_DIGIT_HALF_SIX L"\u0f2f" #define UNICODE_TIBETAN_DIGIT_HALF_SEVEN 0x0f30 #define UNITEXT_TIBETAN_DIGIT_HALF_SEVEN L"\u0f30" #define UNICODE_TIBETAN_DIGIT_HALF_EIGHT 0x0f31 #define UNITEXT_TIBETAN_DIGIT_HALF_EIGHT L"\u0f31" #define UNICODE_TIBETAN_DIGIT_HALF_NINE 0x0f32 #define UNITEXT_TIBETAN_DIGIT_HALF_NINE L"\u0f32" #define UNICODE_TIBETAN_DIGIT_HALF_ZERO 0x0f33 #define UNITEXT_TIBETAN_DIGIT_HALF_ZERO L"\u0f33" #define UNICODE_TIBETAN_MARK_BSDUS_RTAGS 0x0f34 #define UNITEXT_TIBETAN_MARK_BSDUS_RTAGS L"\u0f34" #define UNICODE_TIBETAN_MARK_NGAS_BZUNG_NYI_ZLA 0x0f35 #define UNITEXT_TIBETAN_MARK_NGAS_BZUNG_NYI_ZLA L"\u0f35" #define UNICODE_TIBETAN_MARK_CARET__DZUD_RTAGS_BZHI_MIG_CAN 0x0f36 #define UNITEXT_TIBETAN_MARK_CARET__DZUD_RTAGS_BZHI_MIG_CAN L"\u0f36" #define UNICODE_TIBETAN_MARK_NGAS_BZUNG_SGOR_RTAGS 0x0f37 #define UNITEXT_TIBETAN_MARK_NGAS_BZUNG_SGOR_RTAGS L"\u0f37" #define UNICODE_TIBETAN_MARK_CHE_MGO 0x0f38 #define UNITEXT_TIBETAN_MARK_CHE_MGO L"\u0f38" #define UNICODE_TIBETAN_MARK_TSA__PHRU 0x0f39 #define UNITEXT_TIBETAN_MARK_TSA__PHRU L"\u0f39" #define UNICODE_TIBETAN_MARK_GUG_RTAGS_GYON 0x0f3a #define UNITEXT_TIBETAN_MARK_GUG_RTAGS_GYON L"\u0f3a" #define UNICODE_TIBETAN_MARK_GUG_RTAGS_GYAS 0x0f3b #define UNITEXT_TIBETAN_MARK_GUG_RTAGS_GYAS L"\u0f3b" #define UNICODE_TIBETAN_MARK_ANG_KHANG_GYON 0x0f3c #define UNITEXT_TIBETAN_MARK_ANG_KHANG_GYON L"\u0f3c" #define UNICODE_TIBETAN_MARK_ANG_KHANG_GYAS 0x0f3d #define UNITEXT_TIBETAN_MARK_ANG_KHANG_GYAS L"\u0f3d" #define UNICODE_TIBETAN_SIGN_YAR_TSHES 0x0f3e #define UNITEXT_TIBETAN_SIGN_YAR_TSHES L"\u0f3e" #define UNICODE_TIBETAN_SIGN_MAR_TSHES 0x0f3f #define UNITEXT_TIBETAN_SIGN_MAR_TSHES L"\u0f3f" #define UNICODE_TIBETAN_LETTER_KA 0x0f40 #define UNITEXT_TIBETAN_LETTER_KA L"\u0f40" #define UNICODE_TIBETAN_LETTER_KHA 0x0f41 #define UNITEXT_TIBETAN_LETTER_KHA L"\u0f41" #define UNICODE_TIBETAN_LETTER_GA 0x0f42 #define UNITEXT_TIBETAN_LETTER_GA L"\u0f42" #define UNICODE_TIBETAN_LETTER_GHA 0x0f43 #define UNITEXT_TIBETAN_LETTER_GHA L"\u0f43" #define UNICODE_TIBETAN_LETTER_NGA 0x0f44 #define UNITEXT_TIBETAN_LETTER_NGA L"\u0f44" #define UNICODE_TIBETAN_LETTER_CA 0x0f45 #define UNITEXT_TIBETAN_LETTER_CA L"\u0f45" #define UNICODE_TIBETAN_LETTER_CHA 0x0f46 #define UNITEXT_TIBETAN_LETTER_CHA L"\u0f46" #define UNICODE_TIBETAN_LETTER_JA 0x0f47 #define UNITEXT_TIBETAN_LETTER_JA L"\u0f47" #define UNICODE_TIBETAN_LETTER_NYA 0x0f49 #define UNITEXT_TIBETAN_LETTER_NYA L"\u0f49" #define UNICODE_TIBETAN_LETTER_TTA 0x0f4a #define UNITEXT_TIBETAN_LETTER_TTA L"\u0f4a" #define UNICODE_TIBETAN_LETTER_TTHA 0x0f4b #define UNITEXT_TIBETAN_LETTER_TTHA L"\u0f4b" #define UNICODE_TIBETAN_LETTER_DDA 0x0f4c #define UNITEXT_TIBETAN_LETTER_DDA L"\u0f4c" #define UNICODE_TIBETAN_LETTER_DDHA 0x0f4d #define UNITEXT_TIBETAN_LETTER_DDHA L"\u0f4d" #define UNICODE_TIBETAN_LETTER_NNA 0x0f4e #define UNITEXT_TIBETAN_LETTER_NNA L"\u0f4e" #define UNICODE_TIBETAN_LETTER_TA 0x0f4f #define UNITEXT_TIBETAN_LETTER_TA L"\u0f4f" #define UNICODE_TIBETAN_LETTER_THA 0x0f50 #define UNITEXT_TIBETAN_LETTER_THA L"\u0f50" #define UNICODE_TIBETAN_LETTER_DA 0x0f51 #define UNITEXT_TIBETAN_LETTER_DA L"\u0f51" #define UNICODE_TIBETAN_LETTER_DHA 0x0f52 #define UNITEXT_TIBETAN_LETTER_DHA L"\u0f52" #define UNICODE_TIBETAN_LETTER_NA 0x0f53 #define UNITEXT_TIBETAN_LETTER_NA L"\u0f53" #define UNICODE_TIBETAN_LETTER_PA 0x0f54 #define UNITEXT_TIBETAN_LETTER_PA L"\u0f54" #define UNICODE_TIBETAN_LETTER_PHA 0x0f55 #define UNITEXT_TIBETAN_LETTER_PHA L"\u0f55" #define UNICODE_TIBETAN_LETTER_BA 0x0f56 #define UNITEXT_TIBETAN_LETTER_BA L"\u0f56" #define UNICODE_TIBETAN_LETTER_BHA 0x0f57 #define UNITEXT_TIBETAN_LETTER_BHA L"\u0f57" #define UNICODE_TIBETAN_LETTER_MA 0x0f58 #define UNITEXT_TIBETAN_LETTER_MA L"\u0f58" #define UNICODE_TIBETAN_LETTER_TSA 0x0f59 #define UNITEXT_TIBETAN_LETTER_TSA L"\u0f59" #define UNICODE_TIBETAN_LETTER_TSHA 0x0f5a #define UNITEXT_TIBETAN_LETTER_TSHA L"\u0f5a" #define UNICODE_TIBETAN_LETTER_DZA 0x0f5b #define UNITEXT_TIBETAN_LETTER_DZA L"\u0f5b" #define UNICODE_TIBETAN_LETTER_DZHA 0x0f5c #define UNITEXT_TIBETAN_LETTER_DZHA L"\u0f5c" #define UNICODE_TIBETAN_LETTER_WA 0x0f5d #define UNITEXT_TIBETAN_LETTER_WA L"\u0f5d" #define UNICODE_TIBETAN_LETTER_ZHA 0x0f5e #define UNITEXT_TIBETAN_LETTER_ZHA L"\u0f5e" #define UNICODE_TIBETAN_LETTER_ZA 0x0f5f #define UNITEXT_TIBETAN_LETTER_ZA L"\u0f5f" #define UNICODE_TIBETAN_LETTER__A 0x0f60 #define UNITEXT_TIBETAN_LETTER__A L"\u0f60" #define UNICODE_TIBETAN_LETTER_YA 0x0f61 #define UNITEXT_TIBETAN_LETTER_YA L"\u0f61" #define UNICODE_TIBETAN_LETTER_RA 0x0f62 #define UNITEXT_TIBETAN_LETTER_RA L"\u0f62" #define UNICODE_TIBETAN_LETTER_LA 0x0f63 #define UNITEXT_TIBETAN_LETTER_LA L"\u0f63" #define UNICODE_TIBETAN_LETTER_SHA 0x0f64 #define UNITEXT_TIBETAN_LETTER_SHA L"\u0f64" #define UNICODE_TIBETAN_LETTER_SSA 0x0f65 #define UNITEXT_TIBETAN_LETTER_SSA L"\u0f65" #define UNICODE_TIBETAN_LETTER_SA 0x0f66 #define UNITEXT_TIBETAN_LETTER_SA L"\u0f66" #define UNICODE_TIBETAN_LETTER_HA 0x0f67 #define UNITEXT_TIBETAN_LETTER_HA L"\u0f67" #define UNICODE_TIBETAN_LETTER_A 0x0f68 #define UNITEXT_TIBETAN_LETTER_A L"\u0f68" #define UNICODE_TIBETAN_LETTER_KSSA 0x0f69 #define UNITEXT_TIBETAN_LETTER_KSSA L"\u0f69" #define UNICODE_TIBETAN_LETTER_FIXED_FORM_RA 0x0f6a #define UNITEXT_TIBETAN_LETTER_FIXED_FORM_RA L"\u0f6a" #define UNICODE_TIBETAN_VOWEL_SIGN_AA 0x0f71 #define UNITEXT_TIBETAN_VOWEL_SIGN_AA L"\u0f71" #define UNICODE_TIBETAN_VOWEL_SIGN_I 0x0f72 #define UNITEXT_TIBETAN_VOWEL_SIGN_I L"\u0f72" #define UNICODE_TIBETAN_VOWEL_SIGN_II 0x0f73 #define UNITEXT_TIBETAN_VOWEL_SIGN_II L"\u0f73" #define UNICODE_TIBETAN_VOWEL_SIGN_U 0x0f74 #define UNITEXT_TIBETAN_VOWEL_SIGN_U L"\u0f74" #define UNICODE_TIBETAN_VOWEL_SIGN_UU 0x0f75 #define UNITEXT_TIBETAN_VOWEL_SIGN_UU L"\u0f75" #define UNICODE_TIBETAN_VOWEL_SIGN_VOCALIC_R 0x0f76 #define UNITEXT_TIBETAN_VOWEL_SIGN_VOCALIC_R L"\u0f76" #define UNICODE_TIBETAN_VOWEL_SIGN_VOCALIC_RR 0x0f77 #define UNITEXT_TIBETAN_VOWEL_SIGN_VOCALIC_RR L"\u0f77" #define UNICODE_TIBETAN_VOWEL_SIGN_VOCALIC_L 0x0f78 #define UNITEXT_TIBETAN_VOWEL_SIGN_VOCALIC_L L"\u0f78" #define UNICODE_TIBETAN_VOWEL_SIGN_VOCALIC_LL 0x0f79 #define UNITEXT_TIBETAN_VOWEL_SIGN_VOCALIC_LL L"\u0f79" #define UNICODE_TIBETAN_VOWEL_SIGN_E 0x0f7a #define UNITEXT_TIBETAN_VOWEL_SIGN_E L"\u0f7a" #define UNICODE_TIBETAN_VOWEL_SIGN_EE 0x0f7b #define UNITEXT_TIBETAN_VOWEL_SIGN_EE L"\u0f7b" #define UNICODE_TIBETAN_VOWEL_SIGN_O 0x0f7c #define UNITEXT_TIBETAN_VOWEL_SIGN_O L"\u0f7c" #define UNICODE_TIBETAN_VOWEL_SIGN_OO 0x0f7d #define UNITEXT_TIBETAN_VOWEL_SIGN_OO L"\u0f7d" #define UNICODE_TIBETAN_SIGN_RJES_SU_NGA_RO 0x0f7e #define UNITEXT_TIBETAN_SIGN_RJES_SU_NGA_RO L"\u0f7e" #define UNICODE_TIBETAN_SIGN_RNAM_BCAD 0x0f7f #define UNITEXT_TIBETAN_SIGN_RNAM_BCAD L"\u0f7f" #define UNICODE_TIBETAN_VOWEL_SIGN_REVERSED_I 0x0f80 #define UNITEXT_TIBETAN_VOWEL_SIGN_REVERSED_I L"\u0f80" #define UNICODE_TIBETAN_VOWEL_SIGN_REVERSED_II 0x0f81 #define UNITEXT_TIBETAN_VOWEL_SIGN_REVERSED_II L"\u0f81" #define UNICODE_TIBETAN_SIGN_NYI_ZLA_NAA_DA 0x0f82 #define UNITEXT_TIBETAN_SIGN_NYI_ZLA_NAA_DA L"\u0f82" #define UNICODE_TIBETAN_SIGN_SNA_LDAN 0x0f83 #define UNITEXT_TIBETAN_SIGN_SNA_LDAN L"\u0f83" #define UNICODE_TIBETAN_MARK_HALANTA 0x0f84 #define UNITEXT_TIBETAN_MARK_HALANTA L"\u0f84" #define UNICODE_TIBETAN_MARK_PALUTA 0x0f85 #define UNITEXT_TIBETAN_MARK_PALUTA L"\u0f85" #define UNICODE_TIBETAN_SIGN_LCI_RTAGS 0x0f86 #define UNITEXT_TIBETAN_SIGN_LCI_RTAGS L"\u0f86" #define UNICODE_TIBETAN_SIGN_YANG_RTAGS 0x0f87 #define UNITEXT_TIBETAN_SIGN_YANG_RTAGS L"\u0f87" #define UNICODE_TIBETAN_SIGN_LCE_TSA_CAN 0x0f88 #define UNITEXT_TIBETAN_SIGN_LCE_TSA_CAN L"\u0f88" #define UNICODE_TIBETAN_SIGN_MCHU_CAN 0x0f89 #define UNITEXT_TIBETAN_SIGN_MCHU_CAN L"\u0f89" #define UNICODE_TIBETAN_SIGN_GRU_CAN_RGYINGS 0x0f8a #define UNITEXT_TIBETAN_SIGN_GRU_CAN_RGYINGS L"\u0f8a" #define UNICODE_TIBETAN_SIGN_GRU_MED_RGYINGS 0x0f8b #define UNITEXT_TIBETAN_SIGN_GRU_MED_RGYINGS L"\u0f8b" #define UNICODE_TIBETAN_SUBJOINED_LETTER_KA 0x0f90 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_KA L"\u0f90" #define UNICODE_TIBETAN_SUBJOINED_LETTER_KHA 0x0f91 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_KHA L"\u0f91" #define UNICODE_TIBETAN_SUBJOINED_LETTER_GA 0x0f92 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_GA L"\u0f92" #define UNICODE_TIBETAN_SUBJOINED_LETTER_GHA 0x0f93 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_GHA L"\u0f93" #define UNICODE_TIBETAN_SUBJOINED_LETTER_NGA 0x0f94 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_NGA L"\u0f94" #define UNICODE_TIBETAN_SUBJOINED_LETTER_CA 0x0f95 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_CA L"\u0f95" #define UNICODE_TIBETAN_SUBJOINED_LETTER_CHA 0x0f96 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_CHA L"\u0f96" #define UNICODE_TIBETAN_SUBJOINED_LETTER_JA 0x0f97 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_JA L"\u0f97" #define UNICODE_TIBETAN_SUBJOINED_LETTER_NYA 0x0f99 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_NYA L"\u0f99" #define UNICODE_TIBETAN_SUBJOINED_LETTER_TTA 0x0f9a #define UNITEXT_TIBETAN_SUBJOINED_LETTER_TTA L"\u0f9a" #define UNICODE_TIBETAN_SUBJOINED_LETTER_TTHA 0x0f9b #define UNITEXT_TIBETAN_SUBJOINED_LETTER_TTHA L"\u0f9b" #define UNICODE_TIBETAN_SUBJOINED_LETTER_DDA 0x0f9c #define UNITEXT_TIBETAN_SUBJOINED_LETTER_DDA L"\u0f9c" #define UNICODE_TIBETAN_SUBJOINED_LETTER_DDHA 0x0f9d #define UNITEXT_TIBETAN_SUBJOINED_LETTER_DDHA L"\u0f9d" #define UNICODE_TIBETAN_SUBJOINED_LETTER_NNA 0x0f9e #define UNITEXT_TIBETAN_SUBJOINED_LETTER_NNA L"\u0f9e" #define UNICODE_TIBETAN_SUBJOINED_LETTER_TA 0x0f9f #define UNITEXT_TIBETAN_SUBJOINED_LETTER_TA L"\u0f9f" #define UNICODE_TIBETAN_SUBJOINED_LETTER_THA 0x0fa0 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_THA L"\u0fa0" #define UNICODE_TIBETAN_SUBJOINED_LETTER_DA 0x0fa1 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_DA L"\u0fa1" #define UNICODE_TIBETAN_SUBJOINED_LETTER_DHA 0x0fa2 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_DHA L"\u0fa2" #define UNICODE_TIBETAN_SUBJOINED_LETTER_NA 0x0fa3 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_NA L"\u0fa3" #define UNICODE_TIBETAN_SUBJOINED_LETTER_PA 0x0fa4 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_PA L"\u0fa4" #define UNICODE_TIBETAN_SUBJOINED_LETTER_PHA 0x0fa5 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_PHA L"\u0fa5" #define UNICODE_TIBETAN_SUBJOINED_LETTER_BA 0x0fa6 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_BA L"\u0fa6" #define UNICODE_TIBETAN_SUBJOINED_LETTER_BHA 0x0fa7 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_BHA L"\u0fa7" #define UNICODE_TIBETAN_SUBJOINED_LETTER_MA 0x0fa8 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_MA L"\u0fa8" #define UNICODE_TIBETAN_SUBJOINED_LETTER_TSA 0x0fa9 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_TSA L"\u0fa9" #define UNICODE_TIBETAN_SUBJOINED_LETTER_TSHA 0x0faa #define UNITEXT_TIBETAN_SUBJOINED_LETTER_TSHA L"\u0faa" #define UNICODE_TIBETAN_SUBJOINED_LETTER_DZA 0x0fab #define UNITEXT_TIBETAN_SUBJOINED_LETTER_DZA L"\u0fab" #define UNICODE_TIBETAN_SUBJOINED_LETTER_DZHA 0x0fac #define UNITEXT_TIBETAN_SUBJOINED_LETTER_DZHA L"\u0fac" #define UNICODE_TIBETAN_SUBJOINED_LETTER_WA 0x0fad #define UNITEXT_TIBETAN_SUBJOINED_LETTER_WA L"\u0fad" #define UNICODE_TIBETAN_SUBJOINED_LETTER_ZHA 0x0fae #define UNITEXT_TIBETAN_SUBJOINED_LETTER_ZHA L"\u0fae" #define UNICODE_TIBETAN_SUBJOINED_LETTER_ZA 0x0faf #define UNITEXT_TIBETAN_SUBJOINED_LETTER_ZA L"\u0faf" #define UNICODE_TIBETAN_SUBJOINED_LETTER__A 0x0fb0 #define UNITEXT_TIBETAN_SUBJOINED_LETTER__A L"\u0fb0" #define UNICODE_TIBETAN_SUBJOINED_LETTER_YA 0x0fb1 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_YA L"\u0fb1" #define UNICODE_TIBETAN_SUBJOINED_LETTER_RA 0x0fb2 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_RA L"\u0fb2" #define UNICODE_TIBETAN_SUBJOINED_LETTER_LA 0x0fb3 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_LA L"\u0fb3" #define UNICODE_TIBETAN_SUBJOINED_LETTER_SHA 0x0fb4 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_SHA L"\u0fb4" #define UNICODE_TIBETAN_SUBJOINED_LETTER_SSA 0x0fb5 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_SSA L"\u0fb5" #define UNICODE_TIBETAN_SUBJOINED_LETTER_SA 0x0fb6 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_SA L"\u0fb6" #define UNICODE_TIBETAN_SUBJOINED_LETTER_HA 0x0fb7 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_HA L"\u0fb7" #define UNICODE_TIBETAN_SUBJOINED_LETTER_A 0x0fb8 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_A L"\u0fb8" #define UNICODE_TIBETAN_SUBJOINED_LETTER_KSSA 0x0fb9 #define UNITEXT_TIBETAN_SUBJOINED_LETTER_KSSA L"\u0fb9" #define UNICODE_TIBETAN_SUBJOINED_LETTER_FIXED_FORM_WA 0x0fba #define UNITEXT_TIBETAN_SUBJOINED_LETTER_FIXED_FORM_WA L"\u0fba" #define UNICODE_TIBETAN_SUBJOINED_LETTER_FIXED_FORM_YA 0x0fbb #define UNITEXT_TIBETAN_SUBJOINED_LETTER_FIXED_FORM_YA L"\u0fbb" #define UNICODE_TIBETAN_SUBJOINED_LETTER_FIXED_FORM_RA 0x0fbc #define UNITEXT_TIBETAN_SUBJOINED_LETTER_FIXED_FORM_RA L"\u0fbc" #define UNICODE_TIBETAN_KU_RU_KHA 0x0fbe #define UNITEXT_TIBETAN_KU_RU_KHA L"\u0fbe" #define UNICODE_TIBETAN_KU_RU_KHA_BZHI_MIG_CAN 0x0fbf #define UNITEXT_TIBETAN_KU_RU_KHA_BZHI_MIG_CAN L"\u0fbf" #define UNICODE_TIBETAN_CANTILLATION_SIGN_HEAVY_BEAT 0x0fc0 #define UNITEXT_TIBETAN_CANTILLATION_SIGN_HEAVY_BEAT L"\u0fc0" #define UNICODE_TIBETAN_CANTILLATION_SIGN_LIGHT_BEAT 0x0fc1 #define UNITEXT_TIBETAN_CANTILLATION_SIGN_LIGHT_BEAT L"\u0fc1" #define UNICODE_TIBETAN_CANTILLATION_SIGN_CANG_TE_U 0x0fc2 #define UNITEXT_TIBETAN_CANTILLATION_SIGN_CANG_TE_U L"\u0fc2" #define UNICODE_TIBETAN_CANTILLATION_SIGN_SBUB__CHAL 0x0fc3 #define UNITEXT_TIBETAN_CANTILLATION_SIGN_SBUB__CHAL L"\u0fc3" #define UNICODE_TIBETAN_SYMBOL_DRIL_BU 0x0fc4 #define UNITEXT_TIBETAN_SYMBOL_DRIL_BU L"\u0fc4" #define UNICODE_TIBETAN_SYMBOL_RDO_RJE 0x0fc5 #define UNITEXT_TIBETAN_SYMBOL_RDO_RJE L"\u0fc5" #define UNICODE_TIBETAN_SYMBOL_PADMA_GDAN 0x0fc6 #define UNITEXT_TIBETAN_SYMBOL_PADMA_GDAN L"\u0fc6" #define UNICODE_TIBETAN_SYMBOL_RDO_RJE_RGYA_GRAM 0x0fc7 #define UNITEXT_TIBETAN_SYMBOL_RDO_RJE_RGYA_GRAM L"\u0fc7" #define UNICODE_TIBETAN_SYMBOL_PHUR_PA 0x0fc8 #define UNITEXT_TIBETAN_SYMBOL_PHUR_PA L"\u0fc8" #define UNICODE_TIBETAN_SYMBOL_NOR_BU 0x0fc9 #define UNITEXT_TIBETAN_SYMBOL_NOR_BU L"\u0fc9" #define UNICODE_TIBETAN_SYMBOL_NOR_BU_NYIS__KHYIL 0x0fca #define UNITEXT_TIBETAN_SYMBOL_NOR_BU_NYIS__KHYIL L"\u0fca" #define UNICODE_TIBETAN_SYMBOL_NOR_BU_GSUM__KHYIL 0x0fcb #define UNITEXT_TIBETAN_SYMBOL_NOR_BU_GSUM__KHYIL L"\u0fcb" #define UNICODE_TIBETAN_SYMBOL_NOR_BU_BZHI__KHYIL 0x0fcc #define UNITEXT_TIBETAN_SYMBOL_NOR_BU_BZHI__KHYIL L"\u0fcc" #define UNICODE_TIBETAN_SIGN_RDEL_NAG_GSUM 0x0fcf #define UNITEXT_TIBETAN_SIGN_RDEL_NAG_GSUM L"\u0fcf" #define UNICODE_TIBETAN_MARK_BSKA__SHOG_GI_MGO_RGYAN 0x0fd0 #define UNITEXT_TIBETAN_MARK_BSKA__SHOG_GI_MGO_RGYAN L"\u0fd0" #define UNICODE_TIBETAN_MARK_MNYAM_YIG_GI_MGO_RGYAN 0x0fd1 #define UNITEXT_TIBETAN_MARK_MNYAM_YIG_GI_MGO_RGYAN L"\u0fd1" #define UNICODE_MYANMAR_LETTER_KA 0x1000 #define UNITEXT_MYANMAR_LETTER_KA L"\u1000" #define UNICODE_MYANMAR_LETTER_KHA 0x1001 #define UNITEXT_MYANMAR_LETTER_KHA L"\u1001" #define UNICODE_MYANMAR_LETTER_GA 0x1002 #define UNITEXT_MYANMAR_LETTER_GA L"\u1002" #define UNICODE_MYANMAR_LETTER_GHA 0x1003 #define UNITEXT_MYANMAR_LETTER_GHA L"\u1003" #define UNICODE_MYANMAR_LETTER_NGA 0x1004 #define UNITEXT_MYANMAR_LETTER_NGA L"\u1004" #define UNICODE_MYANMAR_LETTER_CA 0x1005 #define UNITEXT_MYANMAR_LETTER_CA L"\u1005" #define UNICODE_MYANMAR_LETTER_CHA 0x1006 #define UNITEXT_MYANMAR_LETTER_CHA L"\u1006" #define UNICODE_MYANMAR_LETTER_JA 0x1007 #define UNITEXT_MYANMAR_LETTER_JA L"\u1007" #define UNICODE_MYANMAR_LETTER_JHA 0x1008 #define UNITEXT_MYANMAR_LETTER_JHA L"\u1008" #define UNICODE_MYANMAR_LETTER_NYA 0x1009 #define UNITEXT_MYANMAR_LETTER_NYA L"\u1009" #define UNICODE_MYANMAR_LETTER_NNYA 0x100a #define UNITEXT_MYANMAR_LETTER_NNYA L"\u100a" #define UNICODE_MYANMAR_LETTER_TTA 0x100b #define UNITEXT_MYANMAR_LETTER_TTA L"\u100b" #define UNICODE_MYANMAR_LETTER_TTHA 0x100c #define UNITEXT_MYANMAR_LETTER_TTHA L"\u100c" #define UNICODE_MYANMAR_LETTER_DDA 0x100d #define UNITEXT_MYANMAR_LETTER_DDA L"\u100d" #define UNICODE_MYANMAR_LETTER_DDHA 0x100e #define UNITEXT_MYANMAR_LETTER_DDHA L"\u100e" #define UNICODE_MYANMAR_LETTER_NNA 0x100f #define UNITEXT_MYANMAR_LETTER_NNA L"\u100f" #define UNICODE_MYANMAR_LETTER_TA 0x1010 #define UNITEXT_MYANMAR_LETTER_TA L"\u1010" #define UNICODE_MYANMAR_LETTER_THA 0x1011 #define UNITEXT_MYANMAR_LETTER_THA L"\u1011" #define UNICODE_MYANMAR_LETTER_DA 0x1012 #define UNITEXT_MYANMAR_LETTER_DA L"\u1012" #define UNICODE_MYANMAR_LETTER_DHA 0x1013 #define UNITEXT_MYANMAR_LETTER_DHA L"\u1013" #define UNICODE_MYANMAR_LETTER_NA 0x1014 #define UNITEXT_MYANMAR_LETTER_NA L"\u1014" #define UNICODE_MYANMAR_LETTER_PA 0x1015 #define UNITEXT_MYANMAR_LETTER_PA L"\u1015" #define UNICODE_MYANMAR_LETTER_PHA 0x1016 #define UNITEXT_MYANMAR_LETTER_PHA L"\u1016" #define UNICODE_MYANMAR_LETTER_BA 0x1017 #define UNITEXT_MYANMAR_LETTER_BA L"\u1017" #define UNICODE_MYANMAR_LETTER_BHA 0x1018 #define UNITEXT_MYANMAR_LETTER_BHA L"\u1018" #define UNICODE_MYANMAR_LETTER_MA 0x1019 #define UNITEXT_MYANMAR_LETTER_MA L"\u1019" #define UNICODE_MYANMAR_LETTER_YA 0x101a #define UNITEXT_MYANMAR_LETTER_YA L"\u101a" #define UNICODE_MYANMAR_LETTER_RA 0x101b #define UNITEXT_MYANMAR_LETTER_RA L"\u101b" #define UNICODE_MYANMAR_LETTER_LA 0x101c #define UNITEXT_MYANMAR_LETTER_LA L"\u101c" #define UNICODE_MYANMAR_LETTER_WA 0x101d #define UNITEXT_MYANMAR_LETTER_WA L"\u101d" #define UNICODE_MYANMAR_LETTER_SA 0x101e #define UNITEXT_MYANMAR_LETTER_SA L"\u101e" #define UNICODE_MYANMAR_LETTER_HA 0x101f #define UNITEXT_MYANMAR_LETTER_HA L"\u101f" #define UNICODE_MYANMAR_LETTER_LLA 0x1020 #define UNITEXT_MYANMAR_LETTER_LLA L"\u1020" #define UNICODE_MYANMAR_LETTER_A 0x1021 #define UNITEXT_MYANMAR_LETTER_A L"\u1021" #define UNICODE_MYANMAR_LETTER_I 0x1023 #define UNITEXT_MYANMAR_LETTER_I L"\u1023" #define UNICODE_MYANMAR_LETTER_II 0x1024 #define UNITEXT_MYANMAR_LETTER_II L"\u1024" #define UNICODE_MYANMAR_LETTER_U 0x1025 #define UNITEXT_MYANMAR_LETTER_U L"\u1025" #define UNICODE_MYANMAR_LETTER_UU 0x1026 #define UNITEXT_MYANMAR_LETTER_UU L"\u1026" #define UNICODE_MYANMAR_LETTER_E 0x1027 #define UNITEXT_MYANMAR_LETTER_E L"\u1027" #define UNICODE_MYANMAR_LETTER_O 0x1029 #define UNITEXT_MYANMAR_LETTER_O L"\u1029" #define UNICODE_MYANMAR_LETTER_AU 0x102a #define UNITEXT_MYANMAR_LETTER_AU L"\u102a" #define UNICODE_MYANMAR_VOWEL_SIGN_AA 0x102c #define UNITEXT_MYANMAR_VOWEL_SIGN_AA L"\u102c" #define UNICODE_MYANMAR_VOWEL_SIGN_I 0x102d #define UNITEXT_MYANMAR_VOWEL_SIGN_I L"\u102d" #define UNICODE_MYANMAR_VOWEL_SIGN_II 0x102e #define UNITEXT_MYANMAR_VOWEL_SIGN_II L"\u102e" #define UNICODE_MYANMAR_VOWEL_SIGN_U 0x102f #define UNITEXT_MYANMAR_VOWEL_SIGN_U L"\u102f" #define UNICODE_MYANMAR_VOWEL_SIGN_UU 0x1030 #define UNITEXT_MYANMAR_VOWEL_SIGN_UU L"\u1030" #define UNICODE_MYANMAR_VOWEL_SIGN_E 0x1031 #define UNITEXT_MYANMAR_VOWEL_SIGN_E L"\u1031" #define UNICODE_MYANMAR_VOWEL_SIGN_AI 0x1032 #define UNITEXT_MYANMAR_VOWEL_SIGN_AI L"\u1032" #define UNICODE_MYANMAR_SIGN_ANUSVARA 0x1036 #define UNITEXT_MYANMAR_SIGN_ANUSVARA L"\u1036" #define UNICODE_MYANMAR_SIGN_DOT_BELOW 0x1037 #define UNITEXT_MYANMAR_SIGN_DOT_BELOW L"\u1037" #define UNICODE_MYANMAR_SIGN_VISARGA 0x1038 #define UNITEXT_MYANMAR_SIGN_VISARGA L"\u1038" #define UNICODE_MYANMAR_SIGN_VIRAMA 0x1039 #define UNITEXT_MYANMAR_SIGN_VIRAMA L"\u1039" #define UNICODE_MYANMAR_DIGIT_ZERO 0x1040 #define UNITEXT_MYANMAR_DIGIT_ZERO L"\u1040" #define UNICODE_MYANMAR_DIGIT_ONE 0x1041 #define UNITEXT_MYANMAR_DIGIT_ONE L"\u1041" #define UNICODE_MYANMAR_DIGIT_TWO 0x1042 #define UNITEXT_MYANMAR_DIGIT_TWO L"\u1042" #define UNICODE_MYANMAR_DIGIT_THREE 0x1043 #define UNITEXT_MYANMAR_DIGIT_THREE L"\u1043" #define UNICODE_MYANMAR_DIGIT_FOUR 0x1044 #define UNITEXT_MYANMAR_DIGIT_FOUR L"\u1044" #define UNICODE_MYANMAR_DIGIT_FIVE 0x1045 #define UNITEXT_MYANMAR_DIGIT_FIVE L"\u1045" #define UNICODE_MYANMAR_DIGIT_SIX 0x1046 #define UNITEXT_MYANMAR_DIGIT_SIX L"\u1046" #define UNICODE_MYANMAR_DIGIT_SEVEN 0x1047 #define UNITEXT_MYANMAR_DIGIT_SEVEN L"\u1047" #define UNICODE_MYANMAR_DIGIT_EIGHT 0x1048 #define UNITEXT_MYANMAR_DIGIT_EIGHT L"\u1048" #define UNICODE_MYANMAR_DIGIT_NINE 0x1049 #define UNITEXT_MYANMAR_DIGIT_NINE L"\u1049" #define UNICODE_MYANMAR_SIGN_LITTLE_SECTION 0x104a #define UNITEXT_MYANMAR_SIGN_LITTLE_SECTION L"\u104a" #define UNICODE_MYANMAR_SIGN_SECTION 0x104b #define UNITEXT_MYANMAR_SIGN_SECTION L"\u104b" #define UNICODE_MYANMAR_SYMBOL_LOCATIVE 0x104c #define UNITEXT_MYANMAR_SYMBOL_LOCATIVE L"\u104c" #define UNICODE_MYANMAR_SYMBOL_COMPLETED 0x104d #define UNITEXT_MYANMAR_SYMBOL_COMPLETED L"\u104d" #define UNICODE_MYANMAR_SYMBOL_AFOREMENTIONED 0x104e #define UNITEXT_MYANMAR_SYMBOL_AFOREMENTIONED L"\u104e" #define UNICODE_MYANMAR_SYMBOL_GENITIVE 0x104f #define UNITEXT_MYANMAR_SYMBOL_GENITIVE L"\u104f" #define UNICODE_MYANMAR_LETTER_SHA 0x1050 #define UNITEXT_MYANMAR_LETTER_SHA L"\u1050" #define UNICODE_MYANMAR_LETTER_SSA 0x1051 #define UNITEXT_MYANMAR_LETTER_SSA L"\u1051" #define UNICODE_MYANMAR_LETTER_VOCALIC_R 0x1052 #define UNITEXT_MYANMAR_LETTER_VOCALIC_R L"\u1052" #define UNICODE_MYANMAR_LETTER_VOCALIC_RR 0x1053 #define UNITEXT_MYANMAR_LETTER_VOCALIC_RR L"\u1053" #define UNICODE_MYANMAR_LETTER_VOCALIC_L 0x1054 #define UNITEXT_MYANMAR_LETTER_VOCALIC_L L"\u1054" #define UNICODE_MYANMAR_LETTER_VOCALIC_LL 0x1055 #define UNITEXT_MYANMAR_LETTER_VOCALIC_LL L"\u1055" #define UNICODE_MYANMAR_VOWEL_SIGN_VOCALIC_R 0x1056 #define UNITEXT_MYANMAR_VOWEL_SIGN_VOCALIC_R L"\u1056" #define UNICODE_MYANMAR_VOWEL_SIGN_VOCALIC_RR 0x1057 #define UNITEXT_MYANMAR_VOWEL_SIGN_VOCALIC_RR L"\u1057" #define UNICODE_MYANMAR_VOWEL_SIGN_VOCALIC_L 0x1058 #define UNITEXT_MYANMAR_VOWEL_SIGN_VOCALIC_L L"\u1058" #define UNICODE_MYANMAR_VOWEL_SIGN_VOCALIC_LL 0x1059 #define UNITEXT_MYANMAR_VOWEL_SIGN_VOCALIC_LL L"\u1059" #define UNICODE_GEORGIAN_CAPITAL_LETTER_AN 0x10a0 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_AN L"\u10a0" #define UNICODE_GEORGIAN_CAPITAL_LETTER_BAN 0x10a1 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_BAN L"\u10a1" #define UNICODE_GEORGIAN_CAPITAL_LETTER_GAN 0x10a2 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_GAN L"\u10a2" #define UNICODE_GEORGIAN_CAPITAL_LETTER_DON 0x10a3 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_DON L"\u10a3" #define UNICODE_GEORGIAN_CAPITAL_LETTER_EN 0x10a4 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_EN L"\u10a4" #define UNICODE_GEORGIAN_CAPITAL_LETTER_VIN 0x10a5 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_VIN L"\u10a5" #define UNICODE_GEORGIAN_CAPITAL_LETTER_ZEN 0x10a6 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_ZEN L"\u10a6" #define UNICODE_GEORGIAN_CAPITAL_LETTER_TAN 0x10a7 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_TAN L"\u10a7" #define UNICODE_GEORGIAN_CAPITAL_LETTER_IN 0x10a8 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_IN L"\u10a8" #define UNICODE_GEORGIAN_CAPITAL_LETTER_KAN 0x10a9 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_KAN L"\u10a9" #define UNICODE_GEORGIAN_CAPITAL_LETTER_LAS 0x10aa #define UNITEXT_GEORGIAN_CAPITAL_LETTER_LAS L"\u10aa" #define UNICODE_GEORGIAN_CAPITAL_LETTER_MAN 0x10ab #define UNITEXT_GEORGIAN_CAPITAL_LETTER_MAN L"\u10ab" #define UNICODE_GEORGIAN_CAPITAL_LETTER_NAR 0x10ac #define UNITEXT_GEORGIAN_CAPITAL_LETTER_NAR L"\u10ac" #define UNICODE_GEORGIAN_CAPITAL_LETTER_ON 0x10ad #define UNITEXT_GEORGIAN_CAPITAL_LETTER_ON L"\u10ad" #define UNICODE_GEORGIAN_CAPITAL_LETTER_PAR 0x10ae #define UNITEXT_GEORGIAN_CAPITAL_LETTER_PAR L"\u10ae" #define UNICODE_GEORGIAN_CAPITAL_LETTER_ZHAR 0x10af #define UNITEXT_GEORGIAN_CAPITAL_LETTER_ZHAR L"\u10af" #define UNICODE_GEORGIAN_CAPITAL_LETTER_RAE 0x10b0 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_RAE L"\u10b0" #define UNICODE_GEORGIAN_CAPITAL_LETTER_SAN 0x10b1 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_SAN L"\u10b1" #define UNICODE_GEORGIAN_CAPITAL_LETTER_TAR 0x10b2 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_TAR L"\u10b2" #define UNICODE_GEORGIAN_CAPITAL_LETTER_UN 0x10b3 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_UN L"\u10b3" #define UNICODE_GEORGIAN_CAPITAL_LETTER_PHAR 0x10b4 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_PHAR L"\u10b4" #define UNICODE_GEORGIAN_CAPITAL_LETTER_KHAR 0x10b5 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_KHAR L"\u10b5" #define UNICODE_GEORGIAN_CAPITAL_LETTER_GHAN 0x10b6 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_GHAN L"\u10b6" #define UNICODE_GEORGIAN_CAPITAL_LETTER_QAR 0x10b7 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_QAR L"\u10b7" #define UNICODE_GEORGIAN_CAPITAL_LETTER_SHIN 0x10b8 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_SHIN L"\u10b8" #define UNICODE_GEORGIAN_CAPITAL_LETTER_CHIN 0x10b9 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_CHIN L"\u10b9" #define UNICODE_GEORGIAN_CAPITAL_LETTER_CAN 0x10ba #define UNITEXT_GEORGIAN_CAPITAL_LETTER_CAN L"\u10ba" #define UNICODE_GEORGIAN_CAPITAL_LETTER_JIL 0x10bb #define UNITEXT_GEORGIAN_CAPITAL_LETTER_JIL L"\u10bb" #define UNICODE_GEORGIAN_CAPITAL_LETTER_CIL 0x10bc #define UNITEXT_GEORGIAN_CAPITAL_LETTER_CIL L"\u10bc" #define UNICODE_GEORGIAN_CAPITAL_LETTER_CHAR 0x10bd #define UNITEXT_GEORGIAN_CAPITAL_LETTER_CHAR L"\u10bd" #define UNICODE_GEORGIAN_CAPITAL_LETTER_XAN 0x10be #define UNITEXT_GEORGIAN_CAPITAL_LETTER_XAN L"\u10be" #define UNICODE_GEORGIAN_CAPITAL_LETTER_JHAN 0x10bf #define UNITEXT_GEORGIAN_CAPITAL_LETTER_JHAN L"\u10bf" #define UNICODE_GEORGIAN_CAPITAL_LETTER_HAE 0x10c0 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_HAE L"\u10c0" #define UNICODE_GEORGIAN_CAPITAL_LETTER_HE 0x10c1 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_HE L"\u10c1" #define UNICODE_GEORGIAN_CAPITAL_LETTER_HIE 0x10c2 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_HIE L"\u10c2" #define UNICODE_GEORGIAN_CAPITAL_LETTER_WE 0x10c3 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_WE L"\u10c3" #define UNICODE_GEORGIAN_CAPITAL_LETTER_HAR 0x10c4 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_HAR L"\u10c4" #define UNICODE_GEORGIAN_CAPITAL_LETTER_HOE 0x10c5 #define UNITEXT_GEORGIAN_CAPITAL_LETTER_HOE L"\u10c5" #define UNICODE_GEORGIAN_LETTER_AN 0x10d0 #define UNITEXT_GEORGIAN_LETTER_AN L"\u10d0" #define UNICODE_GEORGIAN_LETTER_BAN 0x10d1 #define UNITEXT_GEORGIAN_LETTER_BAN L"\u10d1" #define UNICODE_GEORGIAN_LETTER_GAN 0x10d2 #define UNITEXT_GEORGIAN_LETTER_GAN L"\u10d2" #define UNICODE_GEORGIAN_LETTER_DON 0x10d3 #define UNITEXT_GEORGIAN_LETTER_DON L"\u10d3" #define UNICODE_GEORGIAN_LETTER_EN 0x10d4 #define UNITEXT_GEORGIAN_LETTER_EN L"\u10d4" #define UNICODE_GEORGIAN_LETTER_VIN 0x10d5 #define UNITEXT_GEORGIAN_LETTER_VIN L"\u10d5" #define UNICODE_GEORGIAN_LETTER_ZEN 0x10d6 #define UNITEXT_GEORGIAN_LETTER_ZEN L"\u10d6" #define UNICODE_GEORGIAN_LETTER_TAN 0x10d7 #define UNITEXT_GEORGIAN_LETTER_TAN L"\u10d7" #define UNICODE_GEORGIAN_LETTER_IN 0x10d8 #define UNITEXT_GEORGIAN_LETTER_IN L"\u10d8" #define UNICODE_GEORGIAN_LETTER_KAN 0x10d9 #define UNITEXT_GEORGIAN_LETTER_KAN L"\u10d9" #define UNICODE_GEORGIAN_LETTER_LAS 0x10da #define UNITEXT_GEORGIAN_LETTER_LAS L"\u10da" #define UNICODE_GEORGIAN_LETTER_MAN 0x10db #define UNITEXT_GEORGIAN_LETTER_MAN L"\u10db" #define UNICODE_GEORGIAN_LETTER_NAR 0x10dc #define UNITEXT_GEORGIAN_LETTER_NAR L"\u10dc" #define UNICODE_GEORGIAN_LETTER_ON 0x10dd #define UNITEXT_GEORGIAN_LETTER_ON L"\u10dd" #define UNICODE_GEORGIAN_LETTER_PAR 0x10de #define UNITEXT_GEORGIAN_LETTER_PAR L"\u10de" #define UNICODE_GEORGIAN_LETTER_ZHAR 0x10df #define UNITEXT_GEORGIAN_LETTER_ZHAR L"\u10df" #define UNICODE_GEORGIAN_LETTER_RAE 0x10e0 #define UNITEXT_GEORGIAN_LETTER_RAE L"\u10e0" #define UNICODE_GEORGIAN_LETTER_SAN 0x10e1 #define UNITEXT_GEORGIAN_LETTER_SAN L"\u10e1" #define UNICODE_GEORGIAN_LETTER_TAR 0x10e2 #define UNITEXT_GEORGIAN_LETTER_TAR L"\u10e2" #define UNICODE_GEORGIAN_LETTER_UN 0x10e3 #define UNITEXT_GEORGIAN_LETTER_UN L"\u10e3" #define UNICODE_GEORGIAN_LETTER_PHAR 0x10e4 #define UNITEXT_GEORGIAN_LETTER_PHAR L"\u10e4" #define UNICODE_GEORGIAN_LETTER_KHAR 0x10e5 #define UNITEXT_GEORGIAN_LETTER_KHAR L"\u10e5" #define UNICODE_GEORGIAN_LETTER_GHAN 0x10e6 #define UNITEXT_GEORGIAN_LETTER_GHAN L"\u10e6" #define UNICODE_GEORGIAN_LETTER_QAR 0x10e7 #define UNITEXT_GEORGIAN_LETTER_QAR L"\u10e7" #define UNICODE_GEORGIAN_LETTER_SHIN 0x10e8 #define UNITEXT_GEORGIAN_LETTER_SHIN L"\u10e8" #define UNICODE_GEORGIAN_LETTER_CHIN 0x10e9 #define UNITEXT_GEORGIAN_LETTER_CHIN L"\u10e9" #define UNICODE_GEORGIAN_LETTER_CAN 0x10ea #define UNITEXT_GEORGIAN_LETTER_CAN L"\u10ea" #define UNICODE_GEORGIAN_LETTER_JIL 0x10eb #define UNITEXT_GEORGIAN_LETTER_JIL L"\u10eb" #define UNICODE_GEORGIAN_LETTER_CIL 0x10ec #define UNITEXT_GEORGIAN_LETTER_CIL L"\u10ec" #define UNICODE_GEORGIAN_LETTER_CHAR 0x10ed #define UNITEXT_GEORGIAN_LETTER_CHAR L"\u10ed" #define UNICODE_GEORGIAN_LETTER_XAN 0x10ee #define UNITEXT_GEORGIAN_LETTER_XAN L"\u10ee" #define UNICODE_GEORGIAN_LETTER_JHAN 0x10ef #define UNITEXT_GEORGIAN_LETTER_JHAN L"\u10ef" #define UNICODE_GEORGIAN_LETTER_HAE 0x10f0 #define UNITEXT_GEORGIAN_LETTER_HAE L"\u10f0" #define UNICODE_GEORGIAN_LETTER_HE 0x10f1 #define UNITEXT_GEORGIAN_LETTER_HE L"\u10f1" #define UNICODE_GEORGIAN_LETTER_HIE 0x10f2 #define UNITEXT_GEORGIAN_LETTER_HIE L"\u10f2" #define UNICODE_GEORGIAN_LETTER_WE 0x10f3 #define UNITEXT_GEORGIAN_LETTER_WE L"\u10f3" #define UNICODE_GEORGIAN_LETTER_HAR 0x10f4 #define UNITEXT_GEORGIAN_LETTER_HAR L"\u10f4" #define UNICODE_GEORGIAN_LETTER_HOE 0x10f5 #define UNITEXT_GEORGIAN_LETTER_HOE L"\u10f5" #define UNICODE_GEORGIAN_LETTER_FI 0x10f6 #define UNITEXT_GEORGIAN_LETTER_FI L"\u10f6" #define UNICODE_GEORGIAN_LETTER_YN 0x10f7 #define UNITEXT_GEORGIAN_LETTER_YN L"\u10f7" #define UNICODE_GEORGIAN_LETTER_ELIFI 0x10f8 #define UNITEXT_GEORGIAN_LETTER_ELIFI L"\u10f8" #define UNICODE_GEORGIAN_LETTER_TURNED_GAN 0x10f9 #define UNITEXT_GEORGIAN_LETTER_TURNED_GAN L"\u10f9" #define UNICODE_GEORGIAN_LETTER_AIN 0x10fa #define UNITEXT_GEORGIAN_LETTER_AIN L"\u10fa" #define UNICODE_GEORGIAN_PARAGRAPH_SEPARATOR 0x10fb #define UNITEXT_GEORGIAN_PARAGRAPH_SEPARATOR L"\u10fb" #define UNICODE_MODIFIER_LETTER_GEORGIAN_NAR 0x10fc #define UNITEXT_MODIFIER_LETTER_GEORGIAN_NAR L"\u10fc" #define UNICODE_HANGUL_CHOSEONG_KIYEOK 0x1100 #define UNITEXT_HANGUL_CHOSEONG_KIYEOK L"\u1100" #define UNICODE_HANGUL_CHOSEONG_SSANGKIYEOK 0x1101 #define UNITEXT_HANGUL_CHOSEONG_SSANGKIYEOK L"\u1101" #define UNICODE_HANGUL_CHOSEONG_NIEUN 0x1102 #define UNITEXT_HANGUL_CHOSEONG_NIEUN L"\u1102" #define UNICODE_HANGUL_CHOSEONG_TIKEUT 0x1103 #define UNITEXT_HANGUL_CHOSEONG_TIKEUT L"\u1103" #define UNICODE_HANGUL_CHOSEONG_SSANGTIKEUT 0x1104 #define UNITEXT_HANGUL_CHOSEONG_SSANGTIKEUT L"\u1104" #define UNICODE_HANGUL_CHOSEONG_RIEUL 0x1105 #define UNITEXT_HANGUL_CHOSEONG_RIEUL L"\u1105" #define UNICODE_HANGUL_CHOSEONG_MIEUM 0x1106 #define UNITEXT_HANGUL_CHOSEONG_MIEUM L"\u1106" #define UNICODE_HANGUL_CHOSEONG_PIEUP 0x1107 #define UNITEXT_HANGUL_CHOSEONG_PIEUP L"\u1107" #define UNICODE_HANGUL_CHOSEONG_SSANGPIEUP 0x1108 #define UNITEXT_HANGUL_CHOSEONG_SSANGPIEUP L"\u1108" #define UNICODE_HANGUL_CHOSEONG_SIOS 0x1109 #define UNITEXT_HANGUL_CHOSEONG_SIOS L"\u1109" #define UNICODE_HANGUL_CHOSEONG_SSANGSIOS 0x110a #define UNITEXT_HANGUL_CHOSEONG_SSANGSIOS L"\u110a" #define UNICODE_HANGUL_CHOSEONG_IEUNG 0x110b #define UNITEXT_HANGUL_CHOSEONG_IEUNG L"\u110b" #define UNICODE_HANGUL_CHOSEONG_CIEUC 0x110c #define UNITEXT_HANGUL_CHOSEONG_CIEUC L"\u110c" #define UNICODE_HANGUL_CHOSEONG_SSANGCIEUC 0x110d #define UNITEXT_HANGUL_CHOSEONG_SSANGCIEUC L"\u110d" #define UNICODE_HANGUL_CHOSEONG_CHIEUCH 0x110e #define UNITEXT_HANGUL_CHOSEONG_CHIEUCH L"\u110e" #define UNICODE_HANGUL_CHOSEONG_KHIEUKH 0x110f #define UNITEXT_HANGUL_CHOSEONG_KHIEUKH L"\u110f" #define UNICODE_HANGUL_CHOSEONG_THIEUTH 0x1110 #define UNITEXT_HANGUL_CHOSEONG_THIEUTH L"\u1110" #define UNICODE_HANGUL_CHOSEONG_PHIEUPH 0x1111 #define UNITEXT_HANGUL_CHOSEONG_PHIEUPH L"\u1111" #define UNICODE_HANGUL_CHOSEONG_HIEUH 0x1112 #define UNITEXT_HANGUL_CHOSEONG_HIEUH L"\u1112" #define UNICODE_HANGUL_CHOSEONG_NIEUN_KIYEOK 0x1113 #define UNITEXT_HANGUL_CHOSEONG_NIEUN_KIYEOK L"\u1113" #define UNICODE_HANGUL_CHOSEONG_SSANGNIEUN 0x1114 #define UNITEXT_HANGUL_CHOSEONG_SSANGNIEUN L"\u1114" #define UNICODE_HANGUL_CHOSEONG_NIEUN_TIKEUT 0x1115 #define UNITEXT_HANGUL_CHOSEONG_NIEUN_TIKEUT L"\u1115" #define UNICODE_HANGUL_CHOSEONG_NIEUN_PIEUP 0x1116 #define UNITEXT_HANGUL_CHOSEONG_NIEUN_PIEUP L"\u1116" #define UNICODE_HANGUL_CHOSEONG_TIKEUT_KIYEOK 0x1117 #define UNITEXT_HANGUL_CHOSEONG_TIKEUT_KIYEOK L"\u1117" #define UNICODE_HANGUL_CHOSEONG_RIEUL_NIEUN 0x1118 #define UNITEXT_HANGUL_CHOSEONG_RIEUL_NIEUN L"\u1118" #define UNICODE_HANGUL_CHOSEONG_SSANGRIEUL 0x1119 #define UNITEXT_HANGUL_CHOSEONG_SSANGRIEUL L"\u1119" #define UNICODE_HANGUL_CHOSEONG_RIEUL_HIEUH 0x111a #define UNITEXT_HANGUL_CHOSEONG_RIEUL_HIEUH L"\u111a" #define UNICODE_HANGUL_CHOSEONG_KAPYEOUNRIEUL 0x111b #define UNITEXT_HANGUL_CHOSEONG_KAPYEOUNRIEUL L"\u111b" #define UNICODE_HANGUL_CHOSEONG_MIEUM_PIEUP 0x111c #define UNITEXT_HANGUL_CHOSEONG_MIEUM_PIEUP L"\u111c" #define UNICODE_HANGUL_CHOSEONG_KAPYEOUNMIEUM 0x111d #define UNITEXT_HANGUL_CHOSEONG_KAPYEOUNMIEUM L"\u111d" #define UNICODE_HANGUL_CHOSEONG_PIEUP_KIYEOK 0x111e #define UNITEXT_HANGUL_CHOSEONG_PIEUP_KIYEOK L"\u111e" #define UNICODE_HANGUL_CHOSEONG_PIEUP_NIEUN 0x111f #define UNITEXT_HANGUL_CHOSEONG_PIEUP_NIEUN L"\u111f" #define UNICODE_HANGUL_CHOSEONG_PIEUP_TIKEUT 0x1120 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_TIKEUT L"\u1120" #define UNICODE_HANGUL_CHOSEONG_PIEUP_SIOS 0x1121 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_SIOS L"\u1121" #define UNICODE_HANGUL_CHOSEONG_PIEUP_SIOS_KIYEOK 0x1122 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_SIOS_KIYEOK L"\u1122" #define UNICODE_HANGUL_CHOSEONG_PIEUP_SIOS_TIKEUT 0x1123 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_SIOS_TIKEUT L"\u1123" #define UNICODE_HANGUL_CHOSEONG_PIEUP_SIOS_PIEUP 0x1124 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_SIOS_PIEUP L"\u1124" #define UNICODE_HANGUL_CHOSEONG_PIEUP_SSANGSIOS 0x1125 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_SSANGSIOS L"\u1125" #define UNICODE_HANGUL_CHOSEONG_PIEUP_SIOS_CIEUC 0x1126 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_SIOS_CIEUC L"\u1126" #define UNICODE_HANGUL_CHOSEONG_PIEUP_CIEUC 0x1127 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_CIEUC L"\u1127" #define UNICODE_HANGUL_CHOSEONG_PIEUP_CHIEUCH 0x1128 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_CHIEUCH L"\u1128" #define UNICODE_HANGUL_CHOSEONG_PIEUP_THIEUTH 0x1129 #define UNITEXT_HANGUL_CHOSEONG_PIEUP_THIEUTH L"\u1129" #define UNICODE_HANGUL_CHOSEONG_PIEUP_PHIEUPH 0x112a #define UNITEXT_HANGUL_CHOSEONG_PIEUP_PHIEUPH L"\u112a" #define UNICODE_HANGUL_CHOSEONG_KAPYEOUNPIEUP 0x112b #define UNITEXT_HANGUL_CHOSEONG_KAPYEOUNPIEUP L"\u112b" #define UNICODE_HANGUL_CHOSEONG_KAPYEOUNSSANGPIEUP 0x112c #define UNITEXT_HANGUL_CHOSEONG_KAPYEOUNSSANGPIEUP L"\u112c" #define UNICODE_HANGUL_CHOSEONG_SIOS_KIYEOK 0x112d #define UNITEXT_HANGUL_CHOSEONG_SIOS_KIYEOK L"\u112d" #define UNICODE_HANGUL_CHOSEONG_SIOS_NIEUN 0x112e #define UNITEXT_HANGUL_CHOSEONG_SIOS_NIEUN L"\u112e" #define UNICODE_HANGUL_CHOSEONG_SIOS_TIKEUT 0x112f #define UNITEXT_HANGUL_CHOSEONG_SIOS_TIKEUT L"\u112f" #define UNICODE_HANGUL_CHOSEONG_SIOS_RIEUL 0x1130 #define UNITEXT_HANGUL_CHOSEONG_SIOS_RIEUL L"\u1130" #define UNICODE_HANGUL_CHOSEONG_SIOS_MIEUM 0x1131 #define UNITEXT_HANGUL_CHOSEONG_SIOS_MIEUM L"\u1131" #define UNICODE_HANGUL_CHOSEONG_SIOS_PIEUP 0x1132 #define UNITEXT_HANGUL_CHOSEONG_SIOS_PIEUP L"\u1132" #define UNICODE_HANGUL_CHOSEONG_SIOS_PIEUP_KIYEOK 0x1133 #define UNITEXT_HANGUL_CHOSEONG_SIOS_PIEUP_KIYEOK L"\u1133" #define UNICODE_HANGUL_CHOSEONG_SIOS_SSANGSIOS 0x1134 #define UNITEXT_HANGUL_CHOSEONG_SIOS_SSANGSIOS L"\u1134" #define UNICODE_HANGUL_CHOSEONG_SIOS_IEUNG 0x1135 #define UNITEXT_HANGUL_CHOSEONG_SIOS_IEUNG L"\u1135" #define UNICODE_HANGUL_CHOSEONG_SIOS_CIEUC 0x1136 #define UNITEXT_HANGUL_CHOSEONG_SIOS_CIEUC L"\u1136" #define UNICODE_HANGUL_CHOSEONG_SIOS_CHIEUCH 0x1137 #define UNITEXT_HANGUL_CHOSEONG_SIOS_CHIEUCH L"\u1137" #define UNICODE_HANGUL_CHOSEONG_SIOS_KHIEUKH 0x1138 #define UNITEXT_HANGUL_CHOSEONG_SIOS_KHIEUKH L"\u1138" #define UNICODE_HANGUL_CHOSEONG_SIOS_THIEUTH 0x1139 #define UNITEXT_HANGUL_CHOSEONG_SIOS_THIEUTH L"\u1139" #define UNICODE_HANGUL_CHOSEONG_SIOS_PHIEUPH 0x113a #define UNITEXT_HANGUL_CHOSEONG_SIOS_PHIEUPH L"\u113a" #define UNICODE_HANGUL_CHOSEONG_SIOS_HIEUH 0x113b #define UNITEXT_HANGUL_CHOSEONG_SIOS_HIEUH L"\u113b" #define UNICODE_HANGUL_CHOSEONG_CHITUEUMSIOS 0x113c #define UNITEXT_HANGUL_CHOSEONG_CHITUEUMSIOS L"\u113c" #define UNICODE_HANGUL_CHOSEONG_CHITUEUMSSANGSIOS 0x113d #define UNITEXT_HANGUL_CHOSEONG_CHITUEUMSSANGSIOS L"\u113d" #define UNICODE_HANGUL_CHOSEONG_CEONGCHIEUMSIOS 0x113e #define UNITEXT_HANGUL_CHOSEONG_CEONGCHIEUMSIOS L"\u113e" #define UNICODE_HANGUL_CHOSEONG_CEONGCHIEUMSSANGSIOS 0x113f #define UNITEXT_HANGUL_CHOSEONG_CEONGCHIEUMSSANGSIOS L"\u113f" #define UNICODE_HANGUL_CHOSEONG_PANSIOS 0x1140 #define UNITEXT_HANGUL_CHOSEONG_PANSIOS L"\u1140" #define UNICODE_HANGUL_CHOSEONG_IEUNG_KIYEOK 0x1141 #define UNITEXT_HANGUL_CHOSEONG_IEUNG_KIYEOK L"\u1141" #define UNICODE_HANGUL_CHOSEONG_IEUNG_TIKEUT 0x1142 #define UNITEXT_HANGUL_CHOSEONG_IEUNG_TIKEUT L"\u1142" #define UNICODE_HANGUL_CHOSEONG_IEUNG_MIEUM 0x1143 #define UNITEXT_HANGUL_CHOSEONG_IEUNG_MIEUM L"\u1143" #define UNICODE_HANGUL_CHOSEONG_IEUNG_PIEUP 0x1144 #define UNITEXT_HANGUL_CHOSEONG_IEUNG_PIEUP L"\u1144" #define UNICODE_HANGUL_CHOSEONG_IEUNG_SIOS 0x1145 #define UNITEXT_HANGUL_CHOSEONG_IEUNG_SIOS L"\u1145" #define UNICODE_HANGUL_CHOSEONG_IEUNG_PANSIOS 0x1146 #define UNITEXT_HANGUL_CHOSEONG_IEUNG_PANSIOS L"\u1146" #define UNICODE_HANGUL_CHOSEONG_SSANGIEUNG 0x1147 #define UNITEXT_HANGUL_CHOSEONG_SSANGIEUNG L"\u1147" #define UNICODE_HANGUL_CHOSEONG_IEUNG_CIEUC 0x1148 #define UNITEXT_HANGUL_CHOSEONG_IEUNG_CIEUC L"\u1148" #define UNICODE_HANGUL_CHOSEONG_IEUNG_CHIEUCH 0x1149 #define UNITEXT_HANGUL_CHOSEONG_IEUNG_CHIEUCH L"\u1149" #define UNICODE_HANGUL_CHOSEONG_IEUNG_THIEUTH 0x114a #define UNITEXT_HANGUL_CHOSEONG_IEUNG_THIEUTH L"\u114a" #define UNICODE_HANGUL_CHOSEONG_IEUNG_PHIEUPH 0x114b #define UNITEXT_HANGUL_CHOSEONG_IEUNG_PHIEUPH L"\u114b" #define UNICODE_HANGUL_CHOSEONG_YESIEUNG 0x114c #define UNITEXT_HANGUL_CHOSEONG_YESIEUNG L"\u114c" #define UNICODE_HANGUL_CHOSEONG_CIEUC_IEUNG 0x114d #define UNITEXT_HANGUL_CHOSEONG_CIEUC_IEUNG L"\u114d" #define UNICODE_HANGUL_CHOSEONG_CHITUEUMCIEUC 0x114e #define UNITEXT_HANGUL_CHOSEONG_CHITUEUMCIEUC L"\u114e" #define UNICODE_HANGUL_CHOSEONG_CHITUEUMSSANGCIEUC 0x114f #define UNITEXT_HANGUL_CHOSEONG_CHITUEUMSSANGCIEUC L"\u114f" #define UNICODE_HANGUL_CHOSEONG_CEONGCHIEUMCIEUC 0x1150 #define UNITEXT_HANGUL_CHOSEONG_CEONGCHIEUMCIEUC L"\u1150" #define UNICODE_HANGUL_CHOSEONG_CEONGCHIEUMSSANGCIEUC 0x1151 #define UNITEXT_HANGUL_CHOSEONG_CEONGCHIEUMSSANGCIEUC L"\u1151" #define UNICODE_HANGUL_CHOSEONG_CHIEUCH_KHIEUKH 0x1152 #define UNITEXT_HANGUL_CHOSEONG_CHIEUCH_KHIEUKH L"\u1152" #define UNICODE_HANGUL_CHOSEONG_CHIEUCH_HIEUH 0x1153 #define UNITEXT_HANGUL_CHOSEONG_CHIEUCH_HIEUH L"\u1153" #define UNICODE_HANGUL_CHOSEONG_CHITUEUMCHIEUCH 0x1154 #define UNITEXT_HANGUL_CHOSEONG_CHITUEUMCHIEUCH L"\u1154" #define UNICODE_HANGUL_CHOSEONG_CEONGCHIEUMCHIEUCH 0x1155 #define UNITEXT_HANGUL_CHOSEONG_CEONGCHIEUMCHIEUCH L"\u1155" #define UNICODE_HANGUL_CHOSEONG_PHIEUPH_PIEUP 0x1156 #define UNITEXT_HANGUL_CHOSEONG_PHIEUPH_PIEUP L"\u1156" #define UNICODE_HANGUL_CHOSEONG_KAPYEOUNPHIEUPH 0x1157 #define UNITEXT_HANGUL_CHOSEONG_KAPYEOUNPHIEUPH L"\u1157" #define UNICODE_HANGUL_CHOSEONG_SSANGHIEUH 0x1158 #define UNITEXT_HANGUL_CHOSEONG_SSANGHIEUH L"\u1158" #define UNICODE_HANGUL_CHOSEONG_YEORINHIEUH 0x1159 #define UNITEXT_HANGUL_CHOSEONG_YEORINHIEUH L"\u1159" #define UNICODE_HANGUL_CHOSEONG_FILLER 0x115f #define UNITEXT_HANGUL_CHOSEONG_FILLER L"\u115f" #define UNICODE_HANGUL_JUNGSEONG_FILLER 0x1160 #define UNITEXT_HANGUL_JUNGSEONG_FILLER L"\u1160" #define UNICODE_HANGUL_JUNGSEONG_A 0x1161 #define UNITEXT_HANGUL_JUNGSEONG_A L"\u1161" #define UNICODE_HANGUL_JUNGSEONG_AE 0x1162 #define UNITEXT_HANGUL_JUNGSEONG_AE L"\u1162" #define UNICODE_HANGUL_JUNGSEONG_YA 0x1163 #define UNITEXT_HANGUL_JUNGSEONG_YA L"\u1163" #define UNICODE_HANGUL_JUNGSEONG_YAE 0x1164 #define UNITEXT_HANGUL_JUNGSEONG_YAE L"\u1164" #define UNICODE_HANGUL_JUNGSEONG_EO 0x1165 #define UNITEXT_HANGUL_JUNGSEONG_EO L"\u1165" #define UNICODE_HANGUL_JUNGSEONG_E 0x1166 #define UNITEXT_HANGUL_JUNGSEONG_E L"\u1166" #define UNICODE_HANGUL_JUNGSEONG_YEO 0x1167 #define UNITEXT_HANGUL_JUNGSEONG_YEO L"\u1167" #define UNICODE_HANGUL_JUNGSEONG_YE 0x1168 #define UNITEXT_HANGUL_JUNGSEONG_YE L"\u1168" #define UNICODE_HANGUL_JUNGSEONG_O 0x1169 #define UNITEXT_HANGUL_JUNGSEONG_O L"\u1169" #define UNICODE_HANGUL_JUNGSEONG_WA 0x116a #define UNITEXT_HANGUL_JUNGSEONG_WA L"\u116a" #define UNICODE_HANGUL_JUNGSEONG_WAE 0x116b #define UNITEXT_HANGUL_JUNGSEONG_WAE L"\u116b" #define UNICODE_HANGUL_JUNGSEONG_OE 0x116c #define UNITEXT_HANGUL_JUNGSEONG_OE L"\u116c" #define UNICODE_HANGUL_JUNGSEONG_YO 0x116d #define UNITEXT_HANGUL_JUNGSEONG_YO L"\u116d" #define UNICODE_HANGUL_JUNGSEONG_U 0x116e #define UNITEXT_HANGUL_JUNGSEONG_U L"\u116e" #define UNICODE_HANGUL_JUNGSEONG_WEO 0x116f #define UNITEXT_HANGUL_JUNGSEONG_WEO L"\u116f" #define UNICODE_HANGUL_JUNGSEONG_WE 0x1170 #define UNITEXT_HANGUL_JUNGSEONG_WE L"\u1170" #define UNICODE_HANGUL_JUNGSEONG_WI 0x1171 #define UNITEXT_HANGUL_JUNGSEONG_WI L"\u1171" #define UNICODE_HANGUL_JUNGSEONG_YU 0x1172 #define UNITEXT_HANGUL_JUNGSEONG_YU L"\u1172" #define UNICODE_HANGUL_JUNGSEONG_EU 0x1173 #define UNITEXT_HANGUL_JUNGSEONG_EU L"\u1173" #define UNICODE_HANGUL_JUNGSEONG_YI 0x1174 #define UNITEXT_HANGUL_JUNGSEONG_YI L"\u1174" #define UNICODE_HANGUL_JUNGSEONG_I 0x1175 #define UNITEXT_HANGUL_JUNGSEONG_I L"\u1175" #define UNICODE_HANGUL_JUNGSEONG_A_O 0x1176 #define UNITEXT_HANGUL_JUNGSEONG_A_O L"\u1176" #define UNICODE_HANGUL_JUNGSEONG_A_U 0x1177 #define UNITEXT_HANGUL_JUNGSEONG_A_U L"\u1177" #define UNICODE_HANGUL_JUNGSEONG_YA_O 0x1178 #define UNITEXT_HANGUL_JUNGSEONG_YA_O L"\u1178" #define UNICODE_HANGUL_JUNGSEONG_YA_YO 0x1179 #define UNITEXT_HANGUL_JUNGSEONG_YA_YO L"\u1179" #define UNICODE_HANGUL_JUNGSEONG_EO_O 0x117a #define UNITEXT_HANGUL_JUNGSEONG_EO_O L"\u117a" #define UNICODE_HANGUL_JUNGSEONG_EO_U 0x117b #define UNITEXT_HANGUL_JUNGSEONG_EO_U L"\u117b" #define UNICODE_HANGUL_JUNGSEONG_EO_EU 0x117c #define UNITEXT_HANGUL_JUNGSEONG_EO_EU L"\u117c" #define UNICODE_HANGUL_JUNGSEONG_YEO_O 0x117d #define UNITEXT_HANGUL_JUNGSEONG_YEO_O L"\u117d" #define UNICODE_HANGUL_JUNGSEONG_YEO_U 0x117e #define UNITEXT_HANGUL_JUNGSEONG_YEO_U L"\u117e" #define UNICODE_HANGUL_JUNGSEONG_O_EO 0x117f #define UNITEXT_HANGUL_JUNGSEONG_O_EO L"\u117f" #define UNICODE_HANGUL_JUNGSEONG_O_E 0x1180 #define UNITEXT_HANGUL_JUNGSEONG_O_E L"\u1180" #define UNICODE_HANGUL_JUNGSEONG_O_YE 0x1181 #define UNITEXT_HANGUL_JUNGSEONG_O_YE L"\u1181" #define UNICODE_HANGUL_JUNGSEONG_O_O 0x1182 #define UNITEXT_HANGUL_JUNGSEONG_O_O L"\u1182" #define UNICODE_HANGUL_JUNGSEONG_O_U 0x1183 #define UNITEXT_HANGUL_JUNGSEONG_O_U L"\u1183" #define UNICODE_HANGUL_JUNGSEONG_YO_YA 0x1184 #define UNITEXT_HANGUL_JUNGSEONG_YO_YA L"\u1184" #define UNICODE_HANGUL_JUNGSEONG_YO_YAE 0x1185 #define UNITEXT_HANGUL_JUNGSEONG_YO_YAE L"\u1185" #define UNICODE_HANGUL_JUNGSEONG_YO_YEO 0x1186 #define UNITEXT_HANGUL_JUNGSEONG_YO_YEO L"\u1186" #define UNICODE_HANGUL_JUNGSEONG_YO_O 0x1187 #define UNITEXT_HANGUL_JUNGSEONG_YO_O L"\u1187" #define UNICODE_HANGUL_JUNGSEONG_YO_I 0x1188 #define UNITEXT_HANGUL_JUNGSEONG_YO_I L"\u1188" #define UNICODE_HANGUL_JUNGSEONG_U_A 0x1189 #define UNITEXT_HANGUL_JUNGSEONG_U_A L"\u1189" #define UNICODE_HANGUL_JUNGSEONG_U_AE 0x118a #define UNITEXT_HANGUL_JUNGSEONG_U_AE L"\u118a" #define UNICODE_HANGUL_JUNGSEONG_U_EO_EU 0x118b #define UNITEXT_HANGUL_JUNGSEONG_U_EO_EU L"\u118b" #define UNICODE_HANGUL_JUNGSEONG_U_YE 0x118c #define UNITEXT_HANGUL_JUNGSEONG_U_YE L"\u118c" #define UNICODE_HANGUL_JUNGSEONG_U_U 0x118d #define UNITEXT_HANGUL_JUNGSEONG_U_U L"\u118d" #define UNICODE_HANGUL_JUNGSEONG_YU_A 0x118e #define UNITEXT_HANGUL_JUNGSEONG_YU_A L"\u118e" #define UNICODE_HANGUL_JUNGSEONG_YU_EO 0x118f #define UNITEXT_HANGUL_JUNGSEONG_YU_EO L"\u118f" #define UNICODE_HANGUL_JUNGSEONG_YU_E 0x1190 #define UNITEXT_HANGUL_JUNGSEONG_YU_E L"\u1190" #define UNICODE_HANGUL_JUNGSEONG_YU_YEO 0x1191 #define UNITEXT_HANGUL_JUNGSEONG_YU_YEO L"\u1191" #define UNICODE_HANGUL_JUNGSEONG_YU_YE 0x1192 #define UNITEXT_HANGUL_JUNGSEONG_YU_YE L"\u1192" #define UNICODE_HANGUL_JUNGSEONG_YU_U 0x1193 #define UNITEXT_HANGUL_JUNGSEONG_YU_U L"\u1193" #define UNICODE_HANGUL_JUNGSEONG_YU_I 0x1194 #define UNITEXT_HANGUL_JUNGSEONG_YU_I L"\u1194" #define UNICODE_HANGUL_JUNGSEONG_EU_U 0x1195 #define UNITEXT_HANGUL_JUNGSEONG_EU_U L"\u1195" #define UNICODE_HANGUL_JUNGSEONG_EU_EU 0x1196 #define UNITEXT_HANGUL_JUNGSEONG_EU_EU L"\u1196" #define UNICODE_HANGUL_JUNGSEONG_YI_U 0x1197 #define UNITEXT_HANGUL_JUNGSEONG_YI_U L"\u1197" #define UNICODE_HANGUL_JUNGSEONG_I_A 0x1198 #define UNITEXT_HANGUL_JUNGSEONG_I_A L"\u1198" #define UNICODE_HANGUL_JUNGSEONG_I_YA 0x1199 #define UNITEXT_HANGUL_JUNGSEONG_I_YA L"\u1199" #define UNICODE_HANGUL_JUNGSEONG_I_O 0x119a #define UNITEXT_HANGUL_JUNGSEONG_I_O L"\u119a" #define UNICODE_HANGUL_JUNGSEONG_I_U 0x119b #define UNITEXT_HANGUL_JUNGSEONG_I_U L"\u119b" #define UNICODE_HANGUL_JUNGSEONG_I_EU 0x119c #define UNITEXT_HANGUL_JUNGSEONG_I_EU L"\u119c" #define UNICODE_HANGUL_JUNGSEONG_I_ARAEA 0x119d #define UNITEXT_HANGUL_JUNGSEONG_I_ARAEA L"\u119d" #define UNICODE_HANGUL_JUNGSEONG_ARAEA 0x119e #define UNITEXT_HANGUL_JUNGSEONG_ARAEA L"\u119e" #define UNICODE_HANGUL_JUNGSEONG_ARAEA_EO 0x119f #define UNITEXT_HANGUL_JUNGSEONG_ARAEA_EO L"\u119f" #define UNICODE_HANGUL_JUNGSEONG_ARAEA_U 0x11a0 #define UNITEXT_HANGUL_JUNGSEONG_ARAEA_U L"\u11a0" #define UNICODE_HANGUL_JUNGSEONG_ARAEA_I 0x11a1 #define UNITEXT_HANGUL_JUNGSEONG_ARAEA_I L"\u11a1" #define UNICODE_HANGUL_JUNGSEONG_SSANGARAEA 0x11a2 #define UNITEXT_HANGUL_JUNGSEONG_SSANGARAEA L"\u11a2" #define UNICODE_HANGUL_JONGSEONG_KIYEOK 0x11a8 #define UNITEXT_HANGUL_JONGSEONG_KIYEOK L"\u11a8" #define UNICODE_HANGUL_JONGSEONG_SSANGKIYEOK 0x11a9 #define UNITEXT_HANGUL_JONGSEONG_SSANGKIYEOK L"\u11a9" #define UNICODE_HANGUL_JONGSEONG_KIYEOK_SIOS 0x11aa #define UNITEXT_HANGUL_JONGSEONG_KIYEOK_SIOS L"\u11aa" #define UNICODE_HANGUL_JONGSEONG_NIEUN 0x11ab #define UNITEXT_HANGUL_JONGSEONG_NIEUN L"\u11ab" #define UNICODE_HANGUL_JONGSEONG_NIEUN_CIEUC 0x11ac #define UNITEXT_HANGUL_JONGSEONG_NIEUN_CIEUC L"\u11ac" #define UNICODE_HANGUL_JONGSEONG_NIEUN_HIEUH 0x11ad #define UNITEXT_HANGUL_JONGSEONG_NIEUN_HIEUH L"\u11ad" #define UNICODE_HANGUL_JONGSEONG_TIKEUT 0x11ae #define UNITEXT_HANGUL_JONGSEONG_TIKEUT L"\u11ae" #define UNICODE_HANGUL_JONGSEONG_RIEUL 0x11af #define UNITEXT_HANGUL_JONGSEONG_RIEUL L"\u11af" #define UNICODE_HANGUL_JONGSEONG_RIEUL_KIYEOK 0x11b0 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_KIYEOK L"\u11b0" #define UNICODE_HANGUL_JONGSEONG_RIEUL_MIEUM 0x11b1 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_MIEUM L"\u11b1" #define UNICODE_HANGUL_JONGSEONG_RIEUL_PIEUP 0x11b2 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_PIEUP L"\u11b2" #define UNICODE_HANGUL_JONGSEONG_RIEUL_SIOS 0x11b3 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_SIOS L"\u11b3" #define UNICODE_HANGUL_JONGSEONG_RIEUL_THIEUTH 0x11b4 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_THIEUTH L"\u11b4" #define UNICODE_HANGUL_JONGSEONG_RIEUL_PHIEUPH 0x11b5 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_PHIEUPH L"\u11b5" #define UNICODE_HANGUL_JONGSEONG_RIEUL_HIEUH 0x11b6 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_HIEUH L"\u11b6" #define UNICODE_HANGUL_JONGSEONG_MIEUM 0x11b7 #define UNITEXT_HANGUL_JONGSEONG_MIEUM L"\u11b7" #define UNICODE_HANGUL_JONGSEONG_PIEUP 0x11b8 #define UNITEXT_HANGUL_JONGSEONG_PIEUP L"\u11b8" #define UNICODE_HANGUL_JONGSEONG_PIEUP_SIOS 0x11b9 #define UNITEXT_HANGUL_JONGSEONG_PIEUP_SIOS L"\u11b9" #define UNICODE_HANGUL_JONGSEONG_SIOS 0x11ba #define UNITEXT_HANGUL_JONGSEONG_SIOS L"\u11ba" #define UNICODE_HANGUL_JONGSEONG_SSANGSIOS 0x11bb #define UNITEXT_HANGUL_JONGSEONG_SSANGSIOS L"\u11bb" #define UNICODE_HANGUL_JONGSEONG_IEUNG 0x11bc #define UNITEXT_HANGUL_JONGSEONG_IEUNG L"\u11bc" #define UNICODE_HANGUL_JONGSEONG_CIEUC 0x11bd #define UNITEXT_HANGUL_JONGSEONG_CIEUC L"\u11bd" #define UNICODE_HANGUL_JONGSEONG_CHIEUCH 0x11be #define UNITEXT_HANGUL_JONGSEONG_CHIEUCH L"\u11be" #define UNICODE_HANGUL_JONGSEONG_KHIEUKH 0x11bf #define UNITEXT_HANGUL_JONGSEONG_KHIEUKH L"\u11bf" #define UNICODE_HANGUL_JONGSEONG_THIEUTH 0x11c0 #define UNITEXT_HANGUL_JONGSEONG_THIEUTH L"\u11c0" #define UNICODE_HANGUL_JONGSEONG_PHIEUPH 0x11c1 #define UNITEXT_HANGUL_JONGSEONG_PHIEUPH L"\u11c1" #define UNICODE_HANGUL_JONGSEONG_HIEUH 0x11c2 #define UNITEXT_HANGUL_JONGSEONG_HIEUH L"\u11c2" #define UNICODE_HANGUL_JONGSEONG_KIYEOK_RIEUL 0x11c3 #define UNITEXT_HANGUL_JONGSEONG_KIYEOK_RIEUL L"\u11c3" #define UNICODE_HANGUL_JONGSEONG_KIYEOK_SIOS_KIYEOK 0x11c4 #define UNITEXT_HANGUL_JONGSEONG_KIYEOK_SIOS_KIYEOK L"\u11c4" #define UNICODE_HANGUL_JONGSEONG_NIEUN_KIYEOK 0x11c5 #define UNITEXT_HANGUL_JONGSEONG_NIEUN_KIYEOK L"\u11c5" #define UNICODE_HANGUL_JONGSEONG_NIEUN_TIKEUT 0x11c6 #define UNITEXT_HANGUL_JONGSEONG_NIEUN_TIKEUT L"\u11c6" #define UNICODE_HANGUL_JONGSEONG_NIEUN_SIOS 0x11c7 #define UNITEXT_HANGUL_JONGSEONG_NIEUN_SIOS L"\u11c7" #define UNICODE_HANGUL_JONGSEONG_NIEUN_PANSIOS 0x11c8 #define UNITEXT_HANGUL_JONGSEONG_NIEUN_PANSIOS L"\u11c8" #define UNICODE_HANGUL_JONGSEONG_NIEUN_THIEUTH 0x11c9 #define UNITEXT_HANGUL_JONGSEONG_NIEUN_THIEUTH L"\u11c9" #define UNICODE_HANGUL_JONGSEONG_TIKEUT_KIYEOK 0x11ca #define UNITEXT_HANGUL_JONGSEONG_TIKEUT_KIYEOK L"\u11ca" #define UNICODE_HANGUL_JONGSEONG_TIKEUT_RIEUL 0x11cb #define UNITEXT_HANGUL_JONGSEONG_TIKEUT_RIEUL L"\u11cb" #define UNICODE_HANGUL_JONGSEONG_RIEUL_KIYEOK_SIOS 0x11cc #define UNITEXT_HANGUL_JONGSEONG_RIEUL_KIYEOK_SIOS L"\u11cc" #define UNICODE_HANGUL_JONGSEONG_RIEUL_NIEUN 0x11cd #define UNITEXT_HANGUL_JONGSEONG_RIEUL_NIEUN L"\u11cd" #define UNICODE_HANGUL_JONGSEONG_RIEUL_TIKEUT 0x11ce #define UNITEXT_HANGUL_JONGSEONG_RIEUL_TIKEUT L"\u11ce" #define UNICODE_HANGUL_JONGSEONG_RIEUL_TIKEUT_HIEUH 0x11cf #define UNITEXT_HANGUL_JONGSEONG_RIEUL_TIKEUT_HIEUH L"\u11cf" #define UNICODE_HANGUL_JONGSEONG_SSANGRIEUL 0x11d0 #define UNITEXT_HANGUL_JONGSEONG_SSANGRIEUL L"\u11d0" #define UNICODE_HANGUL_JONGSEONG_RIEUL_MIEUM_KIYEOK 0x11d1 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_MIEUM_KIYEOK L"\u11d1" #define UNICODE_HANGUL_JONGSEONG_RIEUL_MIEUM_SIOS 0x11d2 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_MIEUM_SIOS L"\u11d2" #define UNICODE_HANGUL_JONGSEONG_RIEUL_PIEUP_SIOS 0x11d3 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_PIEUP_SIOS L"\u11d3" #define UNICODE_HANGUL_JONGSEONG_RIEUL_PIEUP_HIEUH 0x11d4 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_PIEUP_HIEUH L"\u11d4" #define UNICODE_HANGUL_JONGSEONG_RIEUL_KAPYEOUNPIEUP 0x11d5 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_KAPYEOUNPIEUP L"\u11d5" #define UNICODE_HANGUL_JONGSEONG_RIEUL_SSANGSIOS 0x11d6 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_SSANGSIOS L"\u11d6" #define UNICODE_HANGUL_JONGSEONG_RIEUL_PANSIOS 0x11d7 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_PANSIOS L"\u11d7" #define UNICODE_HANGUL_JONGSEONG_RIEUL_KHIEUKH 0x11d8 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_KHIEUKH L"\u11d8" #define UNICODE_HANGUL_JONGSEONG_RIEUL_YEORINHIEUH 0x11d9 #define UNITEXT_HANGUL_JONGSEONG_RIEUL_YEORINHIEUH L"\u11d9" #define UNICODE_HANGUL_JONGSEONG_MIEUM_KIYEOK 0x11da #define UNITEXT_HANGUL_JONGSEONG_MIEUM_KIYEOK L"\u11da" #define UNICODE_HANGUL_JONGSEONG_MIEUM_RIEUL 0x11db #define UNITEXT_HANGUL_JONGSEONG_MIEUM_RIEUL L"\u11db" #define UNICODE_HANGUL_JONGSEONG_MIEUM_PIEUP 0x11dc #define UNITEXT_HANGUL_JONGSEONG_MIEUM_PIEUP L"\u11dc" #define UNICODE_HANGUL_JONGSEONG_MIEUM_SIOS 0x11dd #define UNITEXT_HANGUL_JONGSEONG_MIEUM_SIOS L"\u11dd" #define UNICODE_HANGUL_JONGSEONG_MIEUM_SSANGSIOS 0x11de #define UNITEXT_HANGUL_JONGSEONG_MIEUM_SSANGSIOS L"\u11de" #define UNICODE_HANGUL_JONGSEONG_MIEUM_PANSIOS 0x11df #define UNITEXT_HANGUL_JONGSEONG_MIEUM_PANSIOS L"\u11df" #define UNICODE_HANGUL_JONGSEONG_MIEUM_CHIEUCH 0x11e0 #define UNITEXT_HANGUL_JONGSEONG_MIEUM_CHIEUCH L"\u11e0" #define UNICODE_HANGUL_JONGSEONG_MIEUM_HIEUH 0x11e1 #define UNITEXT_HANGUL_JONGSEONG_MIEUM_HIEUH L"\u11e1" #define UNICODE_HANGUL_JONGSEONG_KAPYEOUNMIEUM 0x11e2 #define UNITEXT_HANGUL_JONGSEONG_KAPYEOUNMIEUM L"\u11e2" #define UNICODE_HANGUL_JONGSEONG_PIEUP_RIEUL 0x11e3 #define UNITEXT_HANGUL_JONGSEONG_PIEUP_RIEUL L"\u11e3" #define UNICODE_HANGUL_JONGSEONG_PIEUP_PHIEUPH 0x11e4 #define UNITEXT_HANGUL_JONGSEONG_PIEUP_PHIEUPH L"\u11e4" #define UNICODE_HANGUL_JONGSEONG_PIEUP_HIEUH 0x11e5 #define UNITEXT_HANGUL_JONGSEONG_PIEUP_HIEUH L"\u11e5" #define UNICODE_HANGUL_JONGSEONG_KAPYEOUNPIEUP 0x11e6 #define UNITEXT_HANGUL_JONGSEONG_KAPYEOUNPIEUP L"\u11e6" #define UNICODE_HANGUL_JONGSEONG_SIOS_KIYEOK 0x11e7 #define UNITEXT_HANGUL_JONGSEONG_SIOS_KIYEOK L"\u11e7" #define UNICODE_HANGUL_JONGSEONG_SIOS_TIKEUT 0x11e8 #define UNITEXT_HANGUL_JONGSEONG_SIOS_TIKEUT L"\u11e8" #define UNICODE_HANGUL_JONGSEONG_SIOS_RIEUL 0x11e9 #define UNITEXT_HANGUL_JONGSEONG_SIOS_RIEUL L"\u11e9" #define UNICODE_HANGUL_JONGSEONG_SIOS_PIEUP 0x11ea #define UNITEXT_HANGUL_JONGSEONG_SIOS_PIEUP L"\u11ea" #define UNICODE_HANGUL_JONGSEONG_PANSIOS 0x11eb #define UNITEXT_HANGUL_JONGSEONG_PANSIOS L"\u11eb" #define UNICODE_HANGUL_JONGSEONG_IEUNG_KIYEOK 0x11ec #define UNITEXT_HANGUL_JONGSEONG_IEUNG_KIYEOK L"\u11ec" #define UNICODE_HANGUL_JONGSEONG_IEUNG_SSANGKIYEOK 0x11ed #define UNITEXT_HANGUL_JONGSEONG_IEUNG_SSANGKIYEOK L"\u11ed" #define UNICODE_HANGUL_JONGSEONG_SSANGIEUNG 0x11ee #define UNITEXT_HANGUL_JONGSEONG_SSANGIEUNG L"\u11ee" #define UNICODE_HANGUL_JONGSEONG_IEUNG_KHIEUKH 0x11ef #define UNITEXT_HANGUL_JONGSEONG_IEUNG_KHIEUKH L"\u11ef" #define UNICODE_HANGUL_JONGSEONG_YESIEUNG 0x11f0 #define UNITEXT_HANGUL_JONGSEONG_YESIEUNG L"\u11f0" #define UNICODE_HANGUL_JONGSEONG_YESIEUNG_SIOS 0x11f1 #define UNITEXT_HANGUL_JONGSEONG_YESIEUNG_SIOS L"\u11f1" #define UNICODE_HANGUL_JONGSEONG_YESIEUNG_PANSIOS 0x11f2 #define UNITEXT_HANGUL_JONGSEONG_YESIEUNG_PANSIOS L"\u11f2" #define UNICODE_HANGUL_JONGSEONG_PHIEUPH_PIEUP 0x11f3 #define UNITEXT_HANGUL_JONGSEONG_PHIEUPH_PIEUP L"\u11f3" #define UNICODE_HANGUL_JONGSEONG_KAPYEOUNPHIEUPH 0x11f4 #define UNITEXT_HANGUL_JONGSEONG_KAPYEOUNPHIEUPH L"\u11f4" #define UNICODE_HANGUL_JONGSEONG_HIEUH_NIEUN 0x11f5 #define UNITEXT_HANGUL_JONGSEONG_HIEUH_NIEUN L"\u11f5" #define UNICODE_HANGUL_JONGSEONG_HIEUH_RIEUL 0x11f6 #define UNITEXT_HANGUL_JONGSEONG_HIEUH_RIEUL L"\u11f6" #define UNICODE_HANGUL_JONGSEONG_HIEUH_MIEUM 0x11f7 #define UNITEXT_HANGUL_JONGSEONG_HIEUH_MIEUM L"\u11f7" #define UNICODE_HANGUL_JONGSEONG_HIEUH_PIEUP 0x11f8 #define UNITEXT_HANGUL_JONGSEONG_HIEUH_PIEUP L"\u11f8" #define UNICODE_HANGUL_JONGSEONG_YEORINHIEUH 0x11f9 #define UNITEXT_HANGUL_JONGSEONG_YEORINHIEUH L"\u11f9" #define UNICODE_ETHIOPIC_SYLLABLE_HA 0x1200 #define UNITEXT_ETHIOPIC_SYLLABLE_HA L"\u1200" #define UNICODE_ETHIOPIC_SYLLABLE_HU 0x1201 #define UNITEXT_ETHIOPIC_SYLLABLE_HU L"\u1201" #define UNICODE_ETHIOPIC_SYLLABLE_HI 0x1202 #define UNITEXT_ETHIOPIC_SYLLABLE_HI L"\u1202" #define UNICODE_ETHIOPIC_SYLLABLE_HAA 0x1203 #define UNITEXT_ETHIOPIC_SYLLABLE_HAA L"\u1203" #define UNICODE_ETHIOPIC_SYLLABLE_HEE 0x1204 #define UNITEXT_ETHIOPIC_SYLLABLE_HEE L"\u1204" #define UNICODE_ETHIOPIC_SYLLABLE_HE 0x1205 #define UNITEXT_ETHIOPIC_SYLLABLE_HE L"\u1205" #define UNICODE_ETHIOPIC_SYLLABLE_HO 0x1206 #define UNITEXT_ETHIOPIC_SYLLABLE_HO L"\u1206" #define UNICODE_ETHIOPIC_SYLLABLE_HOA 0x1207 #define UNITEXT_ETHIOPIC_SYLLABLE_HOA L"\u1207" #define UNICODE_ETHIOPIC_SYLLABLE_LA 0x1208 #define UNITEXT_ETHIOPIC_SYLLABLE_LA L"\u1208" #define UNICODE_ETHIOPIC_SYLLABLE_LU 0x1209 #define UNITEXT_ETHIOPIC_SYLLABLE_LU L"\u1209" #define UNICODE_ETHIOPIC_SYLLABLE_LI 0x120a #define UNITEXT_ETHIOPIC_SYLLABLE_LI L"\u120a" #define UNICODE_ETHIOPIC_SYLLABLE_LAA 0x120b #define UNITEXT_ETHIOPIC_SYLLABLE_LAA L"\u120b" #define UNICODE_ETHIOPIC_SYLLABLE_LEE 0x120c #define UNITEXT_ETHIOPIC_SYLLABLE_LEE L"\u120c" #define UNICODE_ETHIOPIC_SYLLABLE_LE 0x120d #define UNITEXT_ETHIOPIC_SYLLABLE_LE L"\u120d" #define UNICODE_ETHIOPIC_SYLLABLE_LO 0x120e #define UNITEXT_ETHIOPIC_SYLLABLE_LO L"\u120e" #define UNICODE_ETHIOPIC_SYLLABLE_LWA 0x120f #define UNITEXT_ETHIOPIC_SYLLABLE_LWA L"\u120f" #define UNICODE_ETHIOPIC_SYLLABLE_HHA 0x1210 #define UNITEXT_ETHIOPIC_SYLLABLE_HHA L"\u1210" #define UNICODE_ETHIOPIC_SYLLABLE_HHU 0x1211 #define UNITEXT_ETHIOPIC_SYLLABLE_HHU L"\u1211" #define UNICODE_ETHIOPIC_SYLLABLE_HHI 0x1212 #define UNITEXT_ETHIOPIC_SYLLABLE_HHI L"\u1212" #define UNICODE_ETHIOPIC_SYLLABLE_HHAA 0x1213 #define UNITEXT_ETHIOPIC_SYLLABLE_HHAA L"\u1213" #define UNICODE_ETHIOPIC_SYLLABLE_HHEE 0x1214 #define UNITEXT_ETHIOPIC_SYLLABLE_HHEE L"\u1214" #define UNICODE_ETHIOPIC_SYLLABLE_HHE 0x1215 #define UNITEXT_ETHIOPIC_SYLLABLE_HHE L"\u1215" #define UNICODE_ETHIOPIC_SYLLABLE_HHO 0x1216 #define UNITEXT_ETHIOPIC_SYLLABLE_HHO L"\u1216" #define UNICODE_ETHIOPIC_SYLLABLE_HHWA 0x1217 #define UNITEXT_ETHIOPIC_SYLLABLE_HHWA L"\u1217" #define UNICODE_ETHIOPIC_SYLLABLE_MA 0x1218 #define UNITEXT_ETHIOPIC_SYLLABLE_MA L"\u1218" #define UNICODE_ETHIOPIC_SYLLABLE_MU 0x1219 #define UNITEXT_ETHIOPIC_SYLLABLE_MU L"\u1219" #define UNICODE_ETHIOPIC_SYLLABLE_MI 0x121a #define UNITEXT_ETHIOPIC_SYLLABLE_MI L"\u121a" #define UNICODE_ETHIOPIC_SYLLABLE_MAA 0x121b #define UNITEXT_ETHIOPIC_SYLLABLE_MAA L"\u121b" #define UNICODE_ETHIOPIC_SYLLABLE_MEE 0x121c #define UNITEXT_ETHIOPIC_SYLLABLE_MEE L"\u121c" #define UNICODE_ETHIOPIC_SYLLABLE_ME 0x121d #define UNITEXT_ETHIOPIC_SYLLABLE_ME L"\u121d" #define UNICODE_ETHIOPIC_SYLLABLE_MO 0x121e #define UNITEXT_ETHIOPIC_SYLLABLE_MO L"\u121e" #define UNICODE_ETHIOPIC_SYLLABLE_MWA 0x121f #define UNITEXT_ETHIOPIC_SYLLABLE_MWA L"\u121f" #define UNICODE_ETHIOPIC_SYLLABLE_SZA 0x1220 #define UNITEXT_ETHIOPIC_SYLLABLE_SZA L"\u1220" #define UNICODE_ETHIOPIC_SYLLABLE_SZU 0x1221 #define UNITEXT_ETHIOPIC_SYLLABLE_SZU L"\u1221" #define UNICODE_ETHIOPIC_SYLLABLE_SZI 0x1222 #define UNITEXT_ETHIOPIC_SYLLABLE_SZI L"\u1222" #define UNICODE_ETHIOPIC_SYLLABLE_SZAA 0x1223 #define UNITEXT_ETHIOPIC_SYLLABLE_SZAA L"\u1223" #define UNICODE_ETHIOPIC_SYLLABLE_SZEE 0x1224 #define UNITEXT_ETHIOPIC_SYLLABLE_SZEE L"\u1224" #define UNICODE_ETHIOPIC_SYLLABLE_SZE 0x1225 #define UNITEXT_ETHIOPIC_SYLLABLE_SZE L"\u1225" #define UNICODE_ETHIOPIC_SYLLABLE_SZO 0x1226 #define UNITEXT_ETHIOPIC_SYLLABLE_SZO L"\u1226" #define UNICODE_ETHIOPIC_SYLLABLE_SZWA 0x1227 #define UNITEXT_ETHIOPIC_SYLLABLE_SZWA L"\u1227" #define UNICODE_ETHIOPIC_SYLLABLE_RA 0x1228 #define UNITEXT_ETHIOPIC_SYLLABLE_RA L"\u1228" #define UNICODE_ETHIOPIC_SYLLABLE_RU 0x1229 #define UNITEXT_ETHIOPIC_SYLLABLE_RU L"\u1229" #define UNICODE_ETHIOPIC_SYLLABLE_RI 0x122a #define UNITEXT_ETHIOPIC_SYLLABLE_RI L"\u122a" #define UNICODE_ETHIOPIC_SYLLABLE_RAA 0x122b #define UNITEXT_ETHIOPIC_SYLLABLE_RAA L"\u122b" #define UNICODE_ETHIOPIC_SYLLABLE_REE 0x122c #define UNITEXT_ETHIOPIC_SYLLABLE_REE L"\u122c" #define UNICODE_ETHIOPIC_SYLLABLE_RE 0x122d #define UNITEXT_ETHIOPIC_SYLLABLE_RE L"\u122d" #define UNICODE_ETHIOPIC_SYLLABLE_RO 0x122e #define UNITEXT_ETHIOPIC_SYLLABLE_RO L"\u122e" #define UNICODE_ETHIOPIC_SYLLABLE_RWA 0x122f #define UNITEXT_ETHIOPIC_SYLLABLE_RWA L"\u122f" #define UNICODE_ETHIOPIC_SYLLABLE_SA 0x1230 #define UNITEXT_ETHIOPIC_SYLLABLE_SA L"\u1230" #define UNICODE_ETHIOPIC_SYLLABLE_SU 0x1231 #define UNITEXT_ETHIOPIC_SYLLABLE_SU L"\u1231" #define UNICODE_ETHIOPIC_SYLLABLE_SI 0x1232 #define UNITEXT_ETHIOPIC_SYLLABLE_SI L"\u1232" #define UNICODE_ETHIOPIC_SYLLABLE_SAA 0x1233 #define UNITEXT_ETHIOPIC_SYLLABLE_SAA L"\u1233" #define UNICODE_ETHIOPIC_SYLLABLE_SEE 0x1234 #define UNITEXT_ETHIOPIC_SYLLABLE_SEE L"\u1234" #define UNICODE_ETHIOPIC_SYLLABLE_SE 0x1235 #define UNITEXT_ETHIOPIC_SYLLABLE_SE L"\u1235" #define UNICODE_ETHIOPIC_SYLLABLE_SO 0x1236 #define UNITEXT_ETHIOPIC_SYLLABLE_SO L"\u1236" #define UNICODE_ETHIOPIC_SYLLABLE_SWA 0x1237 #define UNITEXT_ETHIOPIC_SYLLABLE_SWA L"\u1237" #define UNICODE_ETHIOPIC_SYLLABLE_SHA 0x1238 #define UNITEXT_ETHIOPIC_SYLLABLE_SHA L"\u1238" #define UNICODE_ETHIOPIC_SYLLABLE_SHU 0x1239 #define UNITEXT_ETHIOPIC_SYLLABLE_SHU L"\u1239" #define UNICODE_ETHIOPIC_SYLLABLE_SHI 0x123a #define UNITEXT_ETHIOPIC_SYLLABLE_SHI L"\u123a" #define UNICODE_ETHIOPIC_SYLLABLE_SHAA 0x123b #define UNITEXT_ETHIOPIC_SYLLABLE_SHAA L"\u123b" #define UNICODE_ETHIOPIC_SYLLABLE_SHEE 0x123c #define UNITEXT_ETHIOPIC_SYLLABLE_SHEE L"\u123c" #define UNICODE_ETHIOPIC_SYLLABLE_SHE 0x123d #define UNITEXT_ETHIOPIC_SYLLABLE_SHE L"\u123d" #define UNICODE_ETHIOPIC_SYLLABLE_SHO 0x123e #define UNITEXT_ETHIOPIC_SYLLABLE_SHO L"\u123e" #define UNICODE_ETHIOPIC_SYLLABLE_SHWA 0x123f #define UNITEXT_ETHIOPIC_SYLLABLE_SHWA L"\u123f" #define UNICODE_ETHIOPIC_SYLLABLE_QA 0x1240 #define UNITEXT_ETHIOPIC_SYLLABLE_QA L"\u1240" #define UNICODE_ETHIOPIC_SYLLABLE_QU 0x1241 #define UNITEXT_ETHIOPIC_SYLLABLE_QU L"\u1241" #define UNICODE_ETHIOPIC_SYLLABLE_QI 0x1242 #define UNITEXT_ETHIOPIC_SYLLABLE_QI L"\u1242" #define UNICODE_ETHIOPIC_SYLLABLE_QAA 0x1243 #define UNITEXT_ETHIOPIC_SYLLABLE_QAA L"\u1243" #define UNICODE_ETHIOPIC_SYLLABLE_QEE 0x1244 #define UNITEXT_ETHIOPIC_SYLLABLE_QEE L"\u1244" #define UNICODE_ETHIOPIC_SYLLABLE_QE 0x1245 #define UNITEXT_ETHIOPIC_SYLLABLE_QE L"\u1245" #define UNICODE_ETHIOPIC_SYLLABLE_QO 0x1246 #define UNITEXT_ETHIOPIC_SYLLABLE_QO L"\u1246" #define UNICODE_ETHIOPIC_SYLLABLE_QOA 0x1247 #define UNITEXT_ETHIOPIC_SYLLABLE_QOA L"\u1247" #define UNICODE_ETHIOPIC_SYLLABLE_QWA 0x1248 #define UNITEXT_ETHIOPIC_SYLLABLE_QWA L"\u1248" #define UNICODE_ETHIOPIC_SYLLABLE_QWI 0x124a #define UNITEXT_ETHIOPIC_SYLLABLE_QWI L"\u124a" #define UNICODE_ETHIOPIC_SYLLABLE_QWAA 0x124b #define UNITEXT_ETHIOPIC_SYLLABLE_QWAA L"\u124b" #define UNICODE_ETHIOPIC_SYLLABLE_QWEE 0x124c #define UNITEXT_ETHIOPIC_SYLLABLE_QWEE L"\u124c" #define UNICODE_ETHIOPIC_SYLLABLE_QWE 0x124d #define UNITEXT_ETHIOPIC_SYLLABLE_QWE L"\u124d" #define UNICODE_ETHIOPIC_SYLLABLE_QHA 0x1250 #define UNITEXT_ETHIOPIC_SYLLABLE_QHA L"\u1250" #define UNICODE_ETHIOPIC_SYLLABLE_QHU 0x1251 #define UNITEXT_ETHIOPIC_SYLLABLE_QHU L"\u1251" #define UNICODE_ETHIOPIC_SYLLABLE_QHI 0x1252 #define UNITEXT_ETHIOPIC_SYLLABLE_QHI L"\u1252" #define UNICODE_ETHIOPIC_SYLLABLE_QHAA 0x1253 #define UNITEXT_ETHIOPIC_SYLLABLE_QHAA L"\u1253" #define UNICODE_ETHIOPIC_SYLLABLE_QHEE 0x1254 #define UNITEXT_ETHIOPIC_SYLLABLE_QHEE L"\u1254" #define UNICODE_ETHIOPIC_SYLLABLE_QHE 0x1255 #define UNITEXT_ETHIOPIC_SYLLABLE_QHE L"\u1255" #define UNICODE_ETHIOPIC_SYLLABLE_QHO 0x1256 #define UNITEXT_ETHIOPIC_SYLLABLE_QHO L"\u1256" #define UNICODE_ETHIOPIC_SYLLABLE_QHWA 0x1258 #define UNITEXT_ETHIOPIC_SYLLABLE_QHWA L"\u1258" #define UNICODE_ETHIOPIC_SYLLABLE_QHWI 0x125a #define UNITEXT_ETHIOPIC_SYLLABLE_QHWI L"\u125a" #define UNICODE_ETHIOPIC_SYLLABLE_QHWAA 0x125b #define UNITEXT_ETHIOPIC_SYLLABLE_QHWAA L"\u125b" #define UNICODE_ETHIOPIC_SYLLABLE_QHWEE 0x125c #define UNITEXT_ETHIOPIC_SYLLABLE_QHWEE L"\u125c" #define UNICODE_ETHIOPIC_SYLLABLE_QHWE 0x125d #define UNITEXT_ETHIOPIC_SYLLABLE_QHWE L"\u125d" #define UNICODE_ETHIOPIC_SYLLABLE_BA 0x1260 #define UNITEXT_ETHIOPIC_SYLLABLE_BA L"\u1260" #define UNICODE_ETHIOPIC_SYLLABLE_BU 0x1261 #define UNITEXT_ETHIOPIC_SYLLABLE_BU L"\u1261" #define UNICODE_ETHIOPIC_SYLLABLE_BI 0x1262 #define UNITEXT_ETHIOPIC_SYLLABLE_BI L"\u1262" #define UNICODE_ETHIOPIC_SYLLABLE_BAA 0x1263 #define UNITEXT_ETHIOPIC_SYLLABLE_BAA L"\u1263" #define UNICODE_ETHIOPIC_SYLLABLE_BEE 0x1264 #define UNITEXT_ETHIOPIC_SYLLABLE_BEE L"\u1264" #define UNICODE_ETHIOPIC_SYLLABLE_BE 0x1265 #define UNITEXT_ETHIOPIC_SYLLABLE_BE L"\u1265" #define UNICODE_ETHIOPIC_SYLLABLE_BO 0x1266 #define UNITEXT_ETHIOPIC_SYLLABLE_BO L"\u1266" #define UNICODE_ETHIOPIC_SYLLABLE_BWA 0x1267 #define UNITEXT_ETHIOPIC_SYLLABLE_BWA L"\u1267" #define UNICODE_ETHIOPIC_SYLLABLE_VA 0x1268 #define UNITEXT_ETHIOPIC_SYLLABLE_VA L"\u1268" #define UNICODE_ETHIOPIC_SYLLABLE_VU 0x1269 #define UNITEXT_ETHIOPIC_SYLLABLE_VU L"\u1269" #define UNICODE_ETHIOPIC_SYLLABLE_VI 0x126a #define UNITEXT_ETHIOPIC_SYLLABLE_VI L"\u126a" #define UNICODE_ETHIOPIC_SYLLABLE_VAA 0x126b #define UNITEXT_ETHIOPIC_SYLLABLE_VAA L"\u126b" #define UNICODE_ETHIOPIC_SYLLABLE_VEE 0x126c #define UNITEXT_ETHIOPIC_SYLLABLE_VEE L"\u126c" #define UNICODE_ETHIOPIC_SYLLABLE_VE 0x126d #define UNITEXT_ETHIOPIC_SYLLABLE_VE L"\u126d" #define UNICODE_ETHIOPIC_SYLLABLE_VO 0x126e #define UNITEXT_ETHIOPIC_SYLLABLE_VO L"\u126e" #define UNICODE_ETHIOPIC_SYLLABLE_VWA 0x126f #define UNITEXT_ETHIOPIC_SYLLABLE_VWA L"\u126f" #define UNICODE_ETHIOPIC_SYLLABLE_TA 0x1270 #define UNITEXT_ETHIOPIC_SYLLABLE_TA L"\u1270" #define UNICODE_ETHIOPIC_SYLLABLE_TU 0x1271 #define UNITEXT_ETHIOPIC_SYLLABLE_TU L"\u1271" #define UNICODE_ETHIOPIC_SYLLABLE_TI 0x1272 #define UNITEXT_ETHIOPIC_SYLLABLE_TI L"\u1272" #define UNICODE_ETHIOPIC_SYLLABLE_TAA 0x1273 #define UNITEXT_ETHIOPIC_SYLLABLE_TAA L"\u1273" #define UNICODE_ETHIOPIC_SYLLABLE_TEE 0x1274 #define UNITEXT_ETHIOPIC_SYLLABLE_TEE L"\u1274" #define UNICODE_ETHIOPIC_SYLLABLE_TE 0x1275 #define UNITEXT_ETHIOPIC_SYLLABLE_TE L"\u1275" #define UNICODE_ETHIOPIC_SYLLABLE_TO 0x1276 #define UNITEXT_ETHIOPIC_SYLLABLE_TO L"\u1276" #define UNICODE_ETHIOPIC_SYLLABLE_TWA 0x1277 #define UNITEXT_ETHIOPIC_SYLLABLE_TWA L"\u1277" #define UNICODE_ETHIOPIC_SYLLABLE_CA 0x1278 #define UNITEXT_ETHIOPIC_SYLLABLE_CA L"\u1278" #define UNICODE_ETHIOPIC_SYLLABLE_CU 0x1279 #define UNITEXT_ETHIOPIC_SYLLABLE_CU L"\u1279" #define UNICODE_ETHIOPIC_SYLLABLE_CI 0x127a #define UNITEXT_ETHIOPIC_SYLLABLE_CI L"\u127a" #define UNICODE_ETHIOPIC_SYLLABLE_CAA 0x127b #define UNITEXT_ETHIOPIC_SYLLABLE_CAA L"\u127b" #define UNICODE_ETHIOPIC_SYLLABLE_CEE 0x127c #define UNITEXT_ETHIOPIC_SYLLABLE_CEE L"\u127c" #define UNICODE_ETHIOPIC_SYLLABLE_CE 0x127d #define UNITEXT_ETHIOPIC_SYLLABLE_CE L"\u127d" #define UNICODE_ETHIOPIC_SYLLABLE_CO 0x127e #define UNITEXT_ETHIOPIC_SYLLABLE_CO L"\u127e" #define UNICODE_ETHIOPIC_SYLLABLE_CWA 0x127f #define UNITEXT_ETHIOPIC_SYLLABLE_CWA L"\u127f" #define UNICODE_ETHIOPIC_SYLLABLE_XA 0x1280 #define UNITEXT_ETHIOPIC_SYLLABLE_XA L"\u1280" #define UNICODE_ETHIOPIC_SYLLABLE_XU 0x1281 #define UNITEXT_ETHIOPIC_SYLLABLE_XU L"\u1281" #define UNICODE_ETHIOPIC_SYLLABLE_XI 0x1282 #define UNITEXT_ETHIOPIC_SYLLABLE_XI L"\u1282" #define UNICODE_ETHIOPIC_SYLLABLE_XAA 0x1283 #define UNITEXT_ETHIOPIC_SYLLABLE_XAA L"\u1283" #define UNICODE_ETHIOPIC_SYLLABLE_XEE 0x1284 #define UNITEXT_ETHIOPIC_SYLLABLE_XEE L"\u1284" #define UNICODE_ETHIOPIC_SYLLABLE_XE 0x1285 #define UNITEXT_ETHIOPIC_SYLLABLE_XE L"\u1285" #define UNICODE_ETHIOPIC_SYLLABLE_XO 0x1286 #define UNITEXT_ETHIOPIC_SYLLABLE_XO L"\u1286" #define UNICODE_ETHIOPIC_SYLLABLE_XOA 0x1287 #define UNITEXT_ETHIOPIC_SYLLABLE_XOA L"\u1287" #define UNICODE_ETHIOPIC_SYLLABLE_XWA 0x1288 #define UNITEXT_ETHIOPIC_SYLLABLE_XWA L"\u1288" #define UNICODE_ETHIOPIC_SYLLABLE_XWI 0x128a #define UNITEXT_ETHIOPIC_SYLLABLE_XWI L"\u128a" #define UNICODE_ETHIOPIC_SYLLABLE_XWAA 0x128b #define UNITEXT_ETHIOPIC_SYLLABLE_XWAA L"\u128b" #define UNICODE_ETHIOPIC_SYLLABLE_XWEE 0x128c #define UNITEXT_ETHIOPIC_SYLLABLE_XWEE L"\u128c" #define UNICODE_ETHIOPIC_SYLLABLE_XWE 0x128d #define UNITEXT_ETHIOPIC_SYLLABLE_XWE L"\u128d" #define UNICODE_ETHIOPIC_SYLLABLE_NA 0x1290 #define UNITEXT_ETHIOPIC_SYLLABLE_NA L"\u1290" #define UNICODE_ETHIOPIC_SYLLABLE_NU 0x1291 #define UNITEXT_ETHIOPIC_SYLLABLE_NU L"\u1291" #define UNICODE_ETHIOPIC_SYLLABLE_NI 0x1292 #define UNITEXT_ETHIOPIC_SYLLABLE_NI L"\u1292" #define UNICODE_ETHIOPIC_SYLLABLE_NAA 0x1293 #define UNITEXT_ETHIOPIC_SYLLABLE_NAA L"\u1293" #define UNICODE_ETHIOPIC_SYLLABLE_NEE 0x1294 #define UNITEXT_ETHIOPIC_SYLLABLE_NEE L"\u1294" #define UNICODE_ETHIOPIC_SYLLABLE_NE 0x1295 #define UNITEXT_ETHIOPIC_SYLLABLE_NE L"\u1295" #define UNICODE_ETHIOPIC_SYLLABLE_NO 0x1296 #define UNITEXT_ETHIOPIC_SYLLABLE_NO L"\u1296" #define UNICODE_ETHIOPIC_SYLLABLE_NWA 0x1297 #define UNITEXT_ETHIOPIC_SYLLABLE_NWA L"\u1297" #define UNICODE_ETHIOPIC_SYLLABLE_NYA 0x1298 #define UNITEXT_ETHIOPIC_SYLLABLE_NYA L"\u1298" #define UNICODE_ETHIOPIC_SYLLABLE_NYU 0x1299 #define UNITEXT_ETHIOPIC_SYLLABLE_NYU L"\u1299" #define UNICODE_ETHIOPIC_SYLLABLE_NYI 0x129a #define UNITEXT_ETHIOPIC_SYLLABLE_NYI L"\u129a" #define UNICODE_ETHIOPIC_SYLLABLE_NYAA 0x129b #define UNITEXT_ETHIOPIC_SYLLABLE_NYAA L"\u129b" #define UNICODE_ETHIOPIC_SYLLABLE_NYEE 0x129c #define UNITEXT_ETHIOPIC_SYLLABLE_NYEE L"\u129c" #define UNICODE_ETHIOPIC_SYLLABLE_NYE 0x129d #define UNITEXT_ETHIOPIC_SYLLABLE_NYE L"\u129d" #define UNICODE_ETHIOPIC_SYLLABLE_NYO 0x129e #define UNITEXT_ETHIOPIC_SYLLABLE_NYO L"\u129e" #define UNICODE_ETHIOPIC_SYLLABLE_NYWA 0x129f #define UNITEXT_ETHIOPIC_SYLLABLE_NYWA L"\u129f" #define UNICODE_ETHIOPIC_SYLLABLE_GLOTTAL_A 0x12a0 #define UNITEXT_ETHIOPIC_SYLLABLE_GLOTTAL_A L"\u12a0" #define UNICODE_ETHIOPIC_SYLLABLE_GLOTTAL_U 0x12a1 #define UNITEXT_ETHIOPIC_SYLLABLE_GLOTTAL_U L"\u12a1" #define UNICODE_ETHIOPIC_SYLLABLE_GLOTTAL_I 0x12a2 #define UNITEXT_ETHIOPIC_SYLLABLE_GLOTTAL_I L"\u12a2" #define UNICODE_ETHIOPIC_SYLLABLE_GLOTTAL_AA 0x12a3 #define UNITEXT_ETHIOPIC_SYLLABLE_GLOTTAL_AA L"\u12a3" #define UNICODE_ETHIOPIC_SYLLABLE_GLOTTAL_EE 0x12a4 #define UNITEXT_ETHIOPIC_SYLLABLE_GLOTTAL_EE L"\u12a4" #define UNICODE_ETHIOPIC_SYLLABLE_GLOTTAL_E 0x12a5 #define UNITEXT_ETHIOPIC_SYLLABLE_GLOTTAL_E L"\u12a5" #define UNICODE_ETHIOPIC_SYLLABLE_GLOTTAL_O 0x12a6 #define UNITEXT_ETHIOPIC_SYLLABLE_GLOTTAL_O L"\u12a6" #define UNICODE_ETHIOPIC_SYLLABLE_GLOTTAL_WA 0x12a7 #define UNITEXT_ETHIOPIC_SYLLABLE_GLOTTAL_WA L"\u12a7" #define UNICODE_ETHIOPIC_SYLLABLE_KA 0x12a8 #define UNITEXT_ETHIOPIC_SYLLABLE_KA L"\u12a8" #define UNICODE_ETHIOPIC_SYLLABLE_KU 0x12a9 #define UNITEXT_ETHIOPIC_SYLLABLE_KU L"\u12a9" #define UNICODE_ETHIOPIC_SYLLABLE_KI 0x12aa #define UNITEXT_ETHIOPIC_SYLLABLE_KI L"\u12aa" #define UNICODE_ETHIOPIC_SYLLABLE_KAA 0x12ab #define UNITEXT_ETHIOPIC_SYLLABLE_KAA L"\u12ab" #define UNICODE_ETHIOPIC_SYLLABLE_KEE 0x12ac #define UNITEXT_ETHIOPIC_SYLLABLE_KEE L"\u12ac" #define UNICODE_ETHIOPIC_SYLLABLE_KE 0x12ad #define UNITEXT_ETHIOPIC_SYLLABLE_KE L"\u12ad" #define UNICODE_ETHIOPIC_SYLLABLE_KO 0x12ae #define UNITEXT_ETHIOPIC_SYLLABLE_KO L"\u12ae" #define UNICODE_ETHIOPIC_SYLLABLE_KOA 0x12af #define UNITEXT_ETHIOPIC_SYLLABLE_KOA L"\u12af" #define UNICODE_ETHIOPIC_SYLLABLE_KWA 0x12b0 #define UNITEXT_ETHIOPIC_SYLLABLE_KWA L"\u12b0" #define UNICODE_ETHIOPIC_SYLLABLE_KWI 0x12b2 #define UNITEXT_ETHIOPIC_SYLLABLE_KWI L"\u12b2" #define UNICODE_ETHIOPIC_SYLLABLE_KWAA 0x12b3 #define UNITEXT_ETHIOPIC_SYLLABLE_KWAA L"\u12b3" #define UNICODE_ETHIOPIC_SYLLABLE_KWEE 0x12b4 #define UNITEXT_ETHIOPIC_SYLLABLE_KWEE L"\u12b4" #define UNICODE_ETHIOPIC_SYLLABLE_KWE 0x12b5 #define UNITEXT_ETHIOPIC_SYLLABLE_KWE L"\u12b5" #define UNICODE_ETHIOPIC_SYLLABLE_KXA 0x12b8 #define UNITEXT_ETHIOPIC_SYLLABLE_KXA L"\u12b8" #define UNICODE_ETHIOPIC_SYLLABLE_KXU 0x12b9 #define UNITEXT_ETHIOPIC_SYLLABLE_KXU L"\u12b9" #define UNICODE_ETHIOPIC_SYLLABLE_KXI 0x12ba #define UNITEXT_ETHIOPIC_SYLLABLE_KXI L"\u12ba" #define UNICODE_ETHIOPIC_SYLLABLE_KXAA 0x12bb #define UNITEXT_ETHIOPIC_SYLLABLE_KXAA L"\u12bb" #define UNICODE_ETHIOPIC_SYLLABLE_KXEE 0x12bc #define UNITEXT_ETHIOPIC_SYLLABLE_KXEE L"\u12bc" #define UNICODE_ETHIOPIC_SYLLABLE_KXE 0x12bd #define UNITEXT_ETHIOPIC_SYLLABLE_KXE L"\u12bd" #define UNICODE_ETHIOPIC_SYLLABLE_KXO 0x12be #define UNITEXT_ETHIOPIC_SYLLABLE_KXO L"\u12be" #define UNICODE_ETHIOPIC_SYLLABLE_KXWA 0x12c0 #define UNITEXT_ETHIOPIC_SYLLABLE_KXWA L"\u12c0" #define UNICODE_ETHIOPIC_SYLLABLE_KXWI 0x12c2 #define UNITEXT_ETHIOPIC_SYLLABLE_KXWI L"\u12c2" #define UNICODE_ETHIOPIC_SYLLABLE_KXWAA 0x12c3 #define UNITEXT_ETHIOPIC_SYLLABLE_KXWAA L"\u12c3" #define UNICODE_ETHIOPIC_SYLLABLE_KXWEE 0x12c4 #define UNITEXT_ETHIOPIC_SYLLABLE_KXWEE L"\u12c4" #define UNICODE_ETHIOPIC_SYLLABLE_KXWE 0x12c5 #define UNITEXT_ETHIOPIC_SYLLABLE_KXWE L"\u12c5" #define UNICODE_ETHIOPIC_SYLLABLE_WA 0x12c8 #define UNITEXT_ETHIOPIC_SYLLABLE_WA L"\u12c8" #define UNICODE_ETHIOPIC_SYLLABLE_WU 0x12c9 #define UNITEXT_ETHIOPIC_SYLLABLE_WU L"\u12c9" #define UNICODE_ETHIOPIC_SYLLABLE_WI 0x12ca #define UNITEXT_ETHIOPIC_SYLLABLE_WI L"\u12ca" #define UNICODE_ETHIOPIC_SYLLABLE_WAA 0x12cb #define UNITEXT_ETHIOPIC_SYLLABLE_WAA L"\u12cb" #define UNICODE_ETHIOPIC_SYLLABLE_WEE 0x12cc #define UNITEXT_ETHIOPIC_SYLLABLE_WEE L"\u12cc" #define UNICODE_ETHIOPIC_SYLLABLE_WE 0x12cd #define UNITEXT_ETHIOPIC_SYLLABLE_WE L"\u12cd" #define UNICODE_ETHIOPIC_SYLLABLE_WO 0x12ce #define UNITEXT_ETHIOPIC_SYLLABLE_WO L"\u12ce" #define UNICODE_ETHIOPIC_SYLLABLE_WOA 0x12cf #define UNITEXT_ETHIOPIC_SYLLABLE_WOA L"\u12cf" #define UNICODE_ETHIOPIC_SYLLABLE_PHARYNGEAL_A 0x12d0 #define UNITEXT_ETHIOPIC_SYLLABLE_PHARYNGEAL_A L"\u12d0" #define UNICODE_ETHIOPIC_SYLLABLE_PHARYNGEAL_U 0x12d1 #define UNITEXT_ETHIOPIC_SYLLABLE_PHARYNGEAL_U L"\u12d1" #define UNICODE_ETHIOPIC_SYLLABLE_PHARYNGEAL_I 0x12d2 #define UNITEXT_ETHIOPIC_SYLLABLE_PHARYNGEAL_I L"\u12d2" #define UNICODE_ETHIOPIC_SYLLABLE_PHARYNGEAL_AA 0x12d3 #define UNITEXT_ETHIOPIC_SYLLABLE_PHARYNGEAL_AA L"\u12d3" #define UNICODE_ETHIOPIC_SYLLABLE_PHARYNGEAL_EE 0x12d4 #define UNITEXT_ETHIOPIC_SYLLABLE_PHARYNGEAL_EE L"\u12d4" #define UNICODE_ETHIOPIC_SYLLABLE_PHARYNGEAL_E 0x12d5 #define UNITEXT_ETHIOPIC_SYLLABLE_PHARYNGEAL_E L"\u12d5" #define UNICODE_ETHIOPIC_SYLLABLE_PHARYNGEAL_O 0x12d6 #define UNITEXT_ETHIOPIC_SYLLABLE_PHARYNGEAL_O L"\u12d6" #define UNICODE_ETHIOPIC_SYLLABLE_ZA 0x12d8 #define UNITEXT_ETHIOPIC_SYLLABLE_ZA L"\u12d8" #define UNICODE_ETHIOPIC_SYLLABLE_ZU 0x12d9 #define UNITEXT_ETHIOPIC_SYLLABLE_ZU L"\u12d9" #define UNICODE_ETHIOPIC_SYLLABLE_ZI 0x12da #define UNITEXT_ETHIOPIC_SYLLABLE_ZI L"\u12da" #define UNICODE_ETHIOPIC_SYLLABLE_ZAA 0x12db #define UNITEXT_ETHIOPIC_SYLLABLE_ZAA L"\u12db" #define UNICODE_ETHIOPIC_SYLLABLE_ZEE 0x12dc #define UNITEXT_ETHIOPIC_SYLLABLE_ZEE L"\u12dc" #define UNICODE_ETHIOPIC_SYLLABLE_ZE 0x12dd #define UNITEXT_ETHIOPIC_SYLLABLE_ZE L"\u12dd" #define UNICODE_ETHIOPIC_SYLLABLE_ZO 0x12de #define UNITEXT_ETHIOPIC_SYLLABLE_ZO L"\u12de" #define UNICODE_ETHIOPIC_SYLLABLE_ZWA 0x12df #define UNITEXT_ETHIOPIC_SYLLABLE_ZWA L"\u12df" #define UNICODE_ETHIOPIC_SYLLABLE_ZHA 0x12e0 #define UNITEXT_ETHIOPIC_SYLLABLE_ZHA L"\u12e0" #define UNICODE_ETHIOPIC_SYLLABLE_ZHU 0x12e1 #define UNITEXT_ETHIOPIC_SYLLABLE_ZHU L"\u12e1" #define UNICODE_ETHIOPIC_SYLLABLE_ZHI 0x12e2 #define UNITEXT_ETHIOPIC_SYLLABLE_ZHI L"\u12e2" #define UNICODE_ETHIOPIC_SYLLABLE_ZHAA 0x12e3 #define UNITEXT_ETHIOPIC_SYLLABLE_ZHAA L"\u12e3" #define UNICODE_ETHIOPIC_SYLLABLE_ZHEE 0x12e4 #define UNITEXT_ETHIOPIC_SYLLABLE_ZHEE L"\u12e4" #define UNICODE_ETHIOPIC_SYLLABLE_ZHE 0x12e5 #define UNITEXT_ETHIOPIC_SYLLABLE_ZHE L"\u12e5" #define UNICODE_ETHIOPIC_SYLLABLE_ZHO 0x12e6 #define UNITEXT_ETHIOPIC_SYLLABLE_ZHO L"\u12e6" #define UNICODE_ETHIOPIC_SYLLABLE_ZHWA 0x12e7 #define UNITEXT_ETHIOPIC_SYLLABLE_ZHWA L"\u12e7" #define UNICODE_ETHIOPIC_SYLLABLE_YA 0x12e8 #define UNITEXT_ETHIOPIC_SYLLABLE_YA L"\u12e8" #define UNICODE_ETHIOPIC_SYLLABLE_YU 0x12e9 #define UNITEXT_ETHIOPIC_SYLLABLE_YU L"\u12e9" #define UNICODE_ETHIOPIC_SYLLABLE_YI 0x12ea #define UNITEXT_ETHIOPIC_SYLLABLE_YI L"\u12ea" #define UNICODE_ETHIOPIC_SYLLABLE_YAA 0x12eb #define UNITEXT_ETHIOPIC_SYLLABLE_YAA L"\u12eb" #define UNICODE_ETHIOPIC_SYLLABLE_YEE 0x12ec #define UNITEXT_ETHIOPIC_SYLLABLE_YEE L"\u12ec" #define UNICODE_ETHIOPIC_SYLLABLE_YE 0x12ed #define UNITEXT_ETHIOPIC_SYLLABLE_YE L"\u12ed" #define UNICODE_ETHIOPIC_SYLLABLE_YO 0x12ee #define UNITEXT_ETHIOPIC_SYLLABLE_YO L"\u12ee" #define UNICODE_ETHIOPIC_SYLLABLE_YOA 0x12ef #define UNITEXT_ETHIOPIC_SYLLABLE_YOA L"\u12ef" #define UNICODE_ETHIOPIC_SYLLABLE_DA 0x12f0 #define UNITEXT_ETHIOPIC_SYLLABLE_DA L"\u12f0" #define UNICODE_ETHIOPIC_SYLLABLE_DU 0x12f1 #define UNITEXT_ETHIOPIC_SYLLABLE_DU L"\u12f1" #define UNICODE_ETHIOPIC_SYLLABLE_DI 0x12f2 #define UNITEXT_ETHIOPIC_SYLLABLE_DI L"\u12f2" #define UNICODE_ETHIOPIC_SYLLABLE_DAA 0x12f3 #define UNITEXT_ETHIOPIC_SYLLABLE_DAA L"\u12f3" #define UNICODE_ETHIOPIC_SYLLABLE_DEE 0x12f4 #define UNITEXT_ETHIOPIC_SYLLABLE_DEE L"\u12f4" #define UNICODE_ETHIOPIC_SYLLABLE_DE 0x12f5 #define UNITEXT_ETHIOPIC_SYLLABLE_DE L"\u12f5" #define UNICODE_ETHIOPIC_SYLLABLE_DO 0x12f6 #define UNITEXT_ETHIOPIC_SYLLABLE_DO L"\u12f6" #define UNICODE_ETHIOPIC_SYLLABLE_DWA 0x12f7 #define UNITEXT_ETHIOPIC_SYLLABLE_DWA L"\u12f7" #define UNICODE_ETHIOPIC_SYLLABLE_DDA 0x12f8 #define UNITEXT_ETHIOPIC_SYLLABLE_DDA L"\u12f8" #define UNICODE_ETHIOPIC_SYLLABLE_DDU 0x12f9 #define UNITEXT_ETHIOPIC_SYLLABLE_DDU L"\u12f9" #define UNICODE_ETHIOPIC_SYLLABLE_DDI 0x12fa #define UNITEXT_ETHIOPIC_SYLLABLE_DDI L"\u12fa" #define UNICODE_ETHIOPIC_SYLLABLE_DDAA 0x12fb #define UNITEXT_ETHIOPIC_SYLLABLE_DDAA L"\u12fb" #define UNICODE_ETHIOPIC_SYLLABLE_DDEE 0x12fc #define UNITEXT_ETHIOPIC_SYLLABLE_DDEE L"\u12fc" #define UNICODE_ETHIOPIC_SYLLABLE_DDE 0x12fd #define UNITEXT_ETHIOPIC_SYLLABLE_DDE L"\u12fd" #define UNICODE_ETHIOPIC_SYLLABLE_DDO 0x12fe #define UNITEXT_ETHIOPIC_SYLLABLE_DDO L"\u12fe" #define UNICODE_ETHIOPIC_SYLLABLE_DDWA 0x12ff #define UNITEXT_ETHIOPIC_SYLLABLE_DDWA L"\u12ff" #define UNICODE_ETHIOPIC_SYLLABLE_JA 0x1300 #define UNITEXT_ETHIOPIC_SYLLABLE_JA L"\u1300" #define UNICODE_ETHIOPIC_SYLLABLE_JU 0x1301 #define UNITEXT_ETHIOPIC_SYLLABLE_JU L"\u1301" #define UNICODE_ETHIOPIC_SYLLABLE_JI 0x1302 #define UNITEXT_ETHIOPIC_SYLLABLE_JI L"\u1302" #define UNICODE_ETHIOPIC_SYLLABLE_JAA 0x1303 #define UNITEXT_ETHIOPIC_SYLLABLE_JAA L"\u1303" #define UNICODE_ETHIOPIC_SYLLABLE_JEE 0x1304 #define UNITEXT_ETHIOPIC_SYLLABLE_JEE L"\u1304" #define UNICODE_ETHIOPIC_SYLLABLE_JE 0x1305 #define UNITEXT_ETHIOPIC_SYLLABLE_JE L"\u1305" #define UNICODE_ETHIOPIC_SYLLABLE_JO 0x1306 #define UNITEXT_ETHIOPIC_SYLLABLE_JO L"\u1306" #define UNICODE_ETHIOPIC_SYLLABLE_JWA 0x1307 #define UNITEXT_ETHIOPIC_SYLLABLE_JWA L"\u1307" #define UNICODE_ETHIOPIC_SYLLABLE_GA 0x1308 #define UNITEXT_ETHIOPIC_SYLLABLE_GA L"\u1308" #define UNICODE_ETHIOPIC_SYLLABLE_GU 0x1309 #define UNITEXT_ETHIOPIC_SYLLABLE_GU L"\u1309" #define UNICODE_ETHIOPIC_SYLLABLE_GI 0x130a #define UNITEXT_ETHIOPIC_SYLLABLE_GI L"\u130a" #define UNICODE_ETHIOPIC_SYLLABLE_GAA 0x130b #define UNITEXT_ETHIOPIC_SYLLABLE_GAA L"\u130b" #define UNICODE_ETHIOPIC_SYLLABLE_GEE 0x130c #define UNITEXT_ETHIOPIC_SYLLABLE_GEE L"\u130c" #define UNICODE_ETHIOPIC_SYLLABLE_GE 0x130d #define UNITEXT_ETHIOPIC_SYLLABLE_GE L"\u130d" #define UNICODE_ETHIOPIC_SYLLABLE_GO 0x130e #define UNITEXT_ETHIOPIC_SYLLABLE_GO L"\u130e" #define UNICODE_ETHIOPIC_SYLLABLE_GOA 0x130f #define UNITEXT_ETHIOPIC_SYLLABLE_GOA L"\u130f" #define UNICODE_ETHIOPIC_SYLLABLE_GWA 0x1310 #define UNITEXT_ETHIOPIC_SYLLABLE_GWA L"\u1310" #define UNICODE_ETHIOPIC_SYLLABLE_GWI 0x1312 #define UNITEXT_ETHIOPIC_SYLLABLE_GWI L"\u1312" #define UNICODE_ETHIOPIC_SYLLABLE_GWAA 0x1313 #define UNITEXT_ETHIOPIC_SYLLABLE_GWAA L"\u1313" #define UNICODE_ETHIOPIC_SYLLABLE_GWEE 0x1314 #define UNITEXT_ETHIOPIC_SYLLABLE_GWEE L"\u1314" #define UNICODE_ETHIOPIC_SYLLABLE_GWE 0x1315 #define UNITEXT_ETHIOPIC_SYLLABLE_GWE L"\u1315" #define UNICODE_ETHIOPIC_SYLLABLE_GGA 0x1318 #define UNITEXT_ETHIOPIC_SYLLABLE_GGA L"\u1318" #define UNICODE_ETHIOPIC_SYLLABLE_GGU 0x1319 #define UNITEXT_ETHIOPIC_SYLLABLE_GGU L"\u1319" #define UNICODE_ETHIOPIC_SYLLABLE_GGI 0x131a #define UNITEXT_ETHIOPIC_SYLLABLE_GGI L"\u131a" #define UNICODE_ETHIOPIC_SYLLABLE_GGAA 0x131b #define UNITEXT_ETHIOPIC_SYLLABLE_GGAA L"\u131b" #define UNICODE_ETHIOPIC_SYLLABLE_GGEE 0x131c #define UNITEXT_ETHIOPIC_SYLLABLE_GGEE L"\u131c" #define UNICODE_ETHIOPIC_SYLLABLE_GGE 0x131d #define UNITEXT_ETHIOPIC_SYLLABLE_GGE L"\u131d" #define UNICODE_ETHIOPIC_SYLLABLE_GGO 0x131e #define UNITEXT_ETHIOPIC_SYLLABLE_GGO L"\u131e" #define UNICODE_ETHIOPIC_SYLLABLE_GGWAA 0x131f #define UNITEXT_ETHIOPIC_SYLLABLE_GGWAA L"\u131f" #define UNICODE_ETHIOPIC_SYLLABLE_THA 0x1320 #define UNITEXT_ETHIOPIC_SYLLABLE_THA L"\u1320" #define UNICODE_ETHIOPIC_SYLLABLE_THU 0x1321 #define UNITEXT_ETHIOPIC_SYLLABLE_THU L"\u1321" #define UNICODE_ETHIOPIC_SYLLABLE_THI 0x1322 #define UNITEXT_ETHIOPIC_SYLLABLE_THI L"\u1322" #define UNICODE_ETHIOPIC_SYLLABLE_THAA 0x1323 #define UNITEXT_ETHIOPIC_SYLLABLE_THAA L"\u1323" #define UNICODE_ETHIOPIC_SYLLABLE_THEE 0x1324 #define UNITEXT_ETHIOPIC_SYLLABLE_THEE L"\u1324" #define UNICODE_ETHIOPIC_SYLLABLE_THE 0x1325 #define UNITEXT_ETHIOPIC_SYLLABLE_THE L"\u1325" #define UNICODE_ETHIOPIC_SYLLABLE_THO 0x1326 #define UNITEXT_ETHIOPIC_SYLLABLE_THO L"\u1326" #define UNICODE_ETHIOPIC_SYLLABLE_THWA 0x1327 #define UNITEXT_ETHIOPIC_SYLLABLE_THWA L"\u1327" #define UNICODE_ETHIOPIC_SYLLABLE_CHA 0x1328 #define UNITEXT_ETHIOPIC_SYLLABLE_CHA L"\u1328" #define UNICODE_ETHIOPIC_SYLLABLE_CHU 0x1329 #define UNITEXT_ETHIOPIC_SYLLABLE_CHU L"\u1329" #define UNICODE_ETHIOPIC_SYLLABLE_CHI 0x132a #define UNITEXT_ETHIOPIC_SYLLABLE_CHI L"\u132a" #define UNICODE_ETHIOPIC_SYLLABLE_CHAA 0x132b #define UNITEXT_ETHIOPIC_SYLLABLE_CHAA L"\u132b" #define UNICODE_ETHIOPIC_SYLLABLE_CHEE 0x132c #define UNITEXT_ETHIOPIC_SYLLABLE_CHEE L"\u132c" #define UNICODE_ETHIOPIC_SYLLABLE_CHE 0x132d #define UNITEXT_ETHIOPIC_SYLLABLE_CHE L"\u132d" #define UNICODE_ETHIOPIC_SYLLABLE_CHO 0x132e #define UNITEXT_ETHIOPIC_SYLLABLE_CHO L"\u132e" #define UNICODE_ETHIOPIC_SYLLABLE_CHWA 0x132f #define UNITEXT_ETHIOPIC_SYLLABLE_CHWA L"\u132f" #define UNICODE_ETHIOPIC_SYLLABLE_PHA 0x1330 #define UNITEXT_ETHIOPIC_SYLLABLE_PHA L"\u1330" #define UNICODE_ETHIOPIC_SYLLABLE_PHU 0x1331 #define UNITEXT_ETHIOPIC_SYLLABLE_PHU L"\u1331" #define UNICODE_ETHIOPIC_SYLLABLE_PHI 0x1332 #define UNITEXT_ETHIOPIC_SYLLABLE_PHI L"\u1332" #define UNICODE_ETHIOPIC_SYLLABLE_PHAA 0x1333 #define UNITEXT_ETHIOPIC_SYLLABLE_PHAA L"\u1333" #define UNICODE_ETHIOPIC_SYLLABLE_PHEE 0x1334 #define UNITEXT_ETHIOPIC_SYLLABLE_PHEE L"\u1334" #define UNICODE_ETHIOPIC_SYLLABLE_PHE 0x1335 #define UNITEXT_ETHIOPIC_SYLLABLE_PHE L"\u1335" #define UNICODE_ETHIOPIC_SYLLABLE_PHO 0x1336 #define UNITEXT_ETHIOPIC_SYLLABLE_PHO L"\u1336" #define UNICODE_ETHIOPIC_SYLLABLE_PHWA 0x1337 #define UNITEXT_ETHIOPIC_SYLLABLE_PHWA L"\u1337" #define UNICODE_ETHIOPIC_SYLLABLE_TSA 0x1338 #define UNITEXT_ETHIOPIC_SYLLABLE_TSA L"\u1338" #define UNICODE_ETHIOPIC_SYLLABLE_TSU 0x1339 #define UNITEXT_ETHIOPIC_SYLLABLE_TSU L"\u1339" #define UNICODE_ETHIOPIC_SYLLABLE_TSI 0x133a #define UNITEXT_ETHIOPIC_SYLLABLE_TSI L"\u133a" #define UNICODE_ETHIOPIC_SYLLABLE_TSAA 0x133b #define UNITEXT_ETHIOPIC_SYLLABLE_TSAA L"\u133b" #define UNICODE_ETHIOPIC_SYLLABLE_TSEE 0x133c #define UNITEXT_ETHIOPIC_SYLLABLE_TSEE L"\u133c" #define UNICODE_ETHIOPIC_SYLLABLE_TSE 0x133d #define UNITEXT_ETHIOPIC_SYLLABLE_TSE L"\u133d" #define UNICODE_ETHIOPIC_SYLLABLE_TSO 0x133e #define UNITEXT_ETHIOPIC_SYLLABLE_TSO L"\u133e" #define UNICODE_ETHIOPIC_SYLLABLE_TSWA 0x133f #define UNITEXT_ETHIOPIC_SYLLABLE_TSWA L"\u133f" #define UNICODE_ETHIOPIC_SYLLABLE_TZA 0x1340 #define UNITEXT_ETHIOPIC_SYLLABLE_TZA L"\u1340" #define UNICODE_ETHIOPIC_SYLLABLE_TZU 0x1341 #define UNITEXT_ETHIOPIC_SYLLABLE_TZU L"\u1341" #define UNICODE_ETHIOPIC_SYLLABLE_TZI 0x1342 #define UNITEXT_ETHIOPIC_SYLLABLE_TZI L"\u1342" #define UNICODE_ETHIOPIC_SYLLABLE_TZAA 0x1343 #define UNITEXT_ETHIOPIC_SYLLABLE_TZAA L"\u1343" #define UNICODE_ETHIOPIC_SYLLABLE_TZEE 0x1344 #define UNITEXT_ETHIOPIC_SYLLABLE_TZEE L"\u1344" #define UNICODE_ETHIOPIC_SYLLABLE_TZE 0x1345 #define UNITEXT_ETHIOPIC_SYLLABLE_TZE L"\u1345" #define UNICODE_ETHIOPIC_SYLLABLE_TZO 0x1346 #define UNITEXT_ETHIOPIC_SYLLABLE_TZO L"\u1346" #define UNICODE_ETHIOPIC_SYLLABLE_TZOA 0x1347 #define UNITEXT_ETHIOPIC_SYLLABLE_TZOA L"\u1347" #define UNICODE_ETHIOPIC_SYLLABLE_FA 0x1348 #define UNITEXT_ETHIOPIC_SYLLABLE_FA L"\u1348" #define UNICODE_ETHIOPIC_SYLLABLE_FU 0x1349 #define UNITEXT_ETHIOPIC_SYLLABLE_FU L"\u1349" #define UNICODE_ETHIOPIC_SYLLABLE_FI 0x134a #define UNITEXT_ETHIOPIC_SYLLABLE_FI L"\u134a" #define UNICODE_ETHIOPIC_SYLLABLE_FAA 0x134b #define UNITEXT_ETHIOPIC_SYLLABLE_FAA L"\u134b" #define UNICODE_ETHIOPIC_SYLLABLE_FEE 0x134c #define UNITEXT_ETHIOPIC_SYLLABLE_FEE L"\u134c" #define UNICODE_ETHIOPIC_SYLLABLE_FE 0x134d #define UNITEXT_ETHIOPIC_SYLLABLE_FE L"\u134d" #define UNICODE_ETHIOPIC_SYLLABLE_FO 0x134e #define UNITEXT_ETHIOPIC_SYLLABLE_FO L"\u134e" #define UNICODE_ETHIOPIC_SYLLABLE_FWA 0x134f #define UNITEXT_ETHIOPIC_SYLLABLE_FWA L"\u134f" #define UNICODE_ETHIOPIC_SYLLABLE_PA 0x1350 #define UNITEXT_ETHIOPIC_SYLLABLE_PA L"\u1350" #define UNICODE_ETHIOPIC_SYLLABLE_PU 0x1351 #define UNITEXT_ETHIOPIC_SYLLABLE_PU L"\u1351" #define UNICODE_ETHIOPIC_SYLLABLE_PI 0x1352 #define UNITEXT_ETHIOPIC_SYLLABLE_PI L"\u1352" #define UNICODE_ETHIOPIC_SYLLABLE_PAA 0x1353 #define UNITEXT_ETHIOPIC_SYLLABLE_PAA L"\u1353" #define UNICODE_ETHIOPIC_SYLLABLE_PEE 0x1354 #define UNITEXT_ETHIOPIC_SYLLABLE_PEE L"\u1354" #define UNICODE_ETHIOPIC_SYLLABLE_PE 0x1355 #define UNITEXT_ETHIOPIC_SYLLABLE_PE L"\u1355" #define UNICODE_ETHIOPIC_SYLLABLE_PO 0x1356 #define UNITEXT_ETHIOPIC_SYLLABLE_PO L"\u1356" #define UNICODE_ETHIOPIC_SYLLABLE_PWA 0x1357 #define UNITEXT_ETHIOPIC_SYLLABLE_PWA L"\u1357" #define UNICODE_ETHIOPIC_SYLLABLE_RYA 0x1358 #define UNITEXT_ETHIOPIC_SYLLABLE_RYA L"\u1358" #define UNICODE_ETHIOPIC_SYLLABLE_MYA 0x1359 #define UNITEXT_ETHIOPIC_SYLLABLE_MYA L"\u1359" #define UNICODE_ETHIOPIC_SYLLABLE_FYA 0x135a #define UNITEXT_ETHIOPIC_SYLLABLE_FYA L"\u135a" #define UNICODE_ETHIOPIC_COMBINING_GEMINATION_MARK 0x135f #define UNITEXT_ETHIOPIC_COMBINING_GEMINATION_MARK L"\u135f" #define UNICODE_ETHIOPIC_SECTION_MARK 0x1360 #define UNITEXT_ETHIOPIC_SECTION_MARK L"\u1360" #define UNICODE_ETHIOPIC_WORDSPACE 0x1361 #define UNITEXT_ETHIOPIC_WORDSPACE L"\u1361" #define UNICODE_ETHIOPIC_FULL_STOP 0x1362 #define UNITEXT_ETHIOPIC_FULL_STOP L"\u1362" #define UNICODE_ETHIOPIC_COMMA 0x1363 #define UNITEXT_ETHIOPIC_COMMA L"\u1363" #define UNICODE_ETHIOPIC_SEMICOLON 0x1364 #define UNITEXT_ETHIOPIC_SEMICOLON L"\u1364" #define UNICODE_ETHIOPIC_COLON 0x1365 #define UNITEXT_ETHIOPIC_COLON L"\u1365" #define UNICODE_ETHIOPIC_PREFACE_COLON 0x1366 #define UNITEXT_ETHIOPIC_PREFACE_COLON L"\u1366" #define UNICODE_ETHIOPIC_QUESTION_MARK 0x1367 #define UNITEXT_ETHIOPIC_QUESTION_MARK L"\u1367" #define UNICODE_ETHIOPIC_PARAGRAPH_SEPARATOR 0x1368 #define UNITEXT_ETHIOPIC_PARAGRAPH_SEPARATOR L"\u1368" #define UNICODE_ETHIOPIC_DIGIT_ONE 0x1369 #define UNITEXT_ETHIOPIC_DIGIT_ONE L"\u1369" #define UNICODE_ETHIOPIC_DIGIT_TWO 0x136a #define UNITEXT_ETHIOPIC_DIGIT_TWO L"\u136a" #define UNICODE_ETHIOPIC_DIGIT_THREE 0x136b #define UNITEXT_ETHIOPIC_DIGIT_THREE L"\u136b" #define UNICODE_ETHIOPIC_DIGIT_FOUR 0x136c #define UNITEXT_ETHIOPIC_DIGIT_FOUR L"\u136c" #define UNICODE_ETHIOPIC_DIGIT_FIVE 0x136d #define UNITEXT_ETHIOPIC_DIGIT_FIVE L"\u136d" #define UNICODE_ETHIOPIC_DIGIT_SIX 0x136e #define UNITEXT_ETHIOPIC_DIGIT_SIX L"\u136e" #define UNICODE_ETHIOPIC_DIGIT_SEVEN 0x136f #define UNITEXT_ETHIOPIC_DIGIT_SEVEN L"\u136f" #define UNICODE_ETHIOPIC_DIGIT_EIGHT 0x1370 #define UNITEXT_ETHIOPIC_DIGIT_EIGHT L"\u1370" #define UNICODE_ETHIOPIC_DIGIT_NINE 0x1371 #define UNITEXT_ETHIOPIC_DIGIT_NINE L"\u1371" #define UNICODE_ETHIOPIC_NUMBER_TEN 0x1372 #define UNITEXT_ETHIOPIC_NUMBER_TEN L"\u1372" #define UNICODE_ETHIOPIC_NUMBER_TWENTY 0x1373 #define UNITEXT_ETHIOPIC_NUMBER_TWENTY L"\u1373" #define UNICODE_ETHIOPIC_NUMBER_THIRTY 0x1374 #define UNITEXT_ETHIOPIC_NUMBER_THIRTY L"\u1374" #define UNICODE_ETHIOPIC_NUMBER_FORTY 0x1375 #define UNITEXT_ETHIOPIC_NUMBER_FORTY L"\u1375" #define UNICODE_ETHIOPIC_NUMBER_FIFTY 0x1376 #define UNITEXT_ETHIOPIC_NUMBER_FIFTY L"\u1376" #define UNICODE_ETHIOPIC_NUMBER_SIXTY 0x1377 #define UNITEXT_ETHIOPIC_NUMBER_SIXTY L"\u1377" #define UNICODE_ETHIOPIC_NUMBER_SEVENTY 0x1378 #define UNITEXT_ETHIOPIC_NUMBER_SEVENTY L"\u1378" #define UNICODE_ETHIOPIC_NUMBER_EIGHTY 0x1379 #define UNITEXT_ETHIOPIC_NUMBER_EIGHTY L"\u1379" #define UNICODE_ETHIOPIC_NUMBER_NINETY 0x137a #define UNITEXT_ETHIOPIC_NUMBER_NINETY L"\u137a" #define UNICODE_ETHIOPIC_NUMBER_HUNDRED 0x137b #define UNITEXT_ETHIOPIC_NUMBER_HUNDRED L"\u137b" #define UNICODE_ETHIOPIC_NUMBER_TEN_THOUSAND 0x137c #define UNITEXT_ETHIOPIC_NUMBER_TEN_THOUSAND L"\u137c" #define UNICODE_ETHIOPIC_SYLLABLE_SEBATBEIT_MWA 0x1380 #define UNITEXT_ETHIOPIC_SYLLABLE_SEBATBEIT_MWA L"\u1380" #define UNICODE_ETHIOPIC_SYLLABLE_MWI 0x1381 #define UNITEXT_ETHIOPIC_SYLLABLE_MWI L"\u1381" #define UNICODE_ETHIOPIC_SYLLABLE_MWEE 0x1382 #define UNITEXT_ETHIOPIC_SYLLABLE_MWEE L"\u1382" #define UNICODE_ETHIOPIC_SYLLABLE_MWE 0x1383 #define UNITEXT_ETHIOPIC_SYLLABLE_MWE L"\u1383" #define UNICODE_ETHIOPIC_SYLLABLE_SEBATBEIT_BWA 0x1384 #define UNITEXT_ETHIOPIC_SYLLABLE_SEBATBEIT_BWA L"\u1384" #define UNICODE_ETHIOPIC_SYLLABLE_BWI 0x1385 #define UNITEXT_ETHIOPIC_SYLLABLE_BWI L"\u1385" #define UNICODE_ETHIOPIC_SYLLABLE_BWEE 0x1386 #define UNITEXT_ETHIOPIC_SYLLABLE_BWEE L"\u1386" #define UNICODE_ETHIOPIC_SYLLABLE_BWE 0x1387 #define UNITEXT_ETHIOPIC_SYLLABLE_BWE L"\u1387" #define UNICODE_ETHIOPIC_SYLLABLE_SEBATBEIT_FWA 0x1388 #define UNITEXT_ETHIOPIC_SYLLABLE_SEBATBEIT_FWA L"\u1388" #define UNICODE_ETHIOPIC_SYLLABLE_FWI 0x1389 #define UNITEXT_ETHIOPIC_SYLLABLE_FWI L"\u1389" #define UNICODE_ETHIOPIC_SYLLABLE_FWEE 0x138a #define UNITEXT_ETHIOPIC_SYLLABLE_FWEE L"\u138a" #define UNICODE_ETHIOPIC_SYLLABLE_FWE 0x138b #define UNITEXT_ETHIOPIC_SYLLABLE_FWE L"\u138b" #define UNICODE_ETHIOPIC_SYLLABLE_SEBATBEIT_PWA 0x138c #define UNITEXT_ETHIOPIC_SYLLABLE_SEBATBEIT_PWA L"\u138c" #define UNICODE_ETHIOPIC_SYLLABLE_PWI 0x138d #define UNITEXT_ETHIOPIC_SYLLABLE_PWI L"\u138d" #define UNICODE_ETHIOPIC_SYLLABLE_PWEE 0x138e #define UNITEXT_ETHIOPIC_SYLLABLE_PWEE L"\u138e" #define UNICODE_ETHIOPIC_SYLLABLE_PWE 0x138f #define UNITEXT_ETHIOPIC_SYLLABLE_PWE L"\u138f" #define UNICODE_ETHIOPIC_TONAL_MARK_YIZET 0x1390 #define UNITEXT_ETHIOPIC_TONAL_MARK_YIZET L"\u1390" #define UNICODE_ETHIOPIC_TONAL_MARK_DERET 0x1391 #define UNITEXT_ETHIOPIC_TONAL_MARK_DERET L"\u1391" #define UNICODE_ETHIOPIC_TONAL_MARK_RIKRIK 0x1392 #define UNITEXT_ETHIOPIC_TONAL_MARK_RIKRIK L"\u1392" #define UNICODE_ETHIOPIC_TONAL_MARK_SHORT_RIKRIK 0x1393 #define UNITEXT_ETHIOPIC_TONAL_MARK_SHORT_RIKRIK L"\u1393" #define UNICODE_ETHIOPIC_TONAL_MARK_DIFAT 0x1394 #define UNITEXT_ETHIOPIC_TONAL_MARK_DIFAT L"\u1394" #define UNICODE_ETHIOPIC_TONAL_MARK_KENAT 0x1395 #define UNITEXT_ETHIOPIC_TONAL_MARK_KENAT L"\u1395" #define UNICODE_ETHIOPIC_TONAL_MARK_CHIRET 0x1396 #define UNITEXT_ETHIOPIC_TONAL_MARK_CHIRET L"\u1396" #define UNICODE_ETHIOPIC_TONAL_MARK_HIDET 0x1397 #define UNITEXT_ETHIOPIC_TONAL_MARK_HIDET L"\u1397" #define UNICODE_ETHIOPIC_TONAL_MARK_DERET_HIDET 0x1398 #define UNITEXT_ETHIOPIC_TONAL_MARK_DERET_HIDET L"\u1398" #define UNICODE_ETHIOPIC_TONAL_MARK_KURT 0x1399 #define UNITEXT_ETHIOPIC_TONAL_MARK_KURT L"\u1399" #define UNICODE_CHEROKEE_LETTER_A 0x13a0 #define UNITEXT_CHEROKEE_LETTER_A L"\u13a0" #define UNICODE_CHEROKEE_LETTER_E 0x13a1 #define UNITEXT_CHEROKEE_LETTER_E L"\u13a1" #define UNICODE_CHEROKEE_LETTER_I 0x13a2 #define UNITEXT_CHEROKEE_LETTER_I L"\u13a2" #define UNICODE_CHEROKEE_LETTER_O 0x13a3 #define UNITEXT_CHEROKEE_LETTER_O L"\u13a3" #define UNICODE_CHEROKEE_LETTER_U 0x13a4 #define UNITEXT_CHEROKEE_LETTER_U L"\u13a4" #define UNICODE_CHEROKEE_LETTER_V 0x13a5 #define UNITEXT_CHEROKEE_LETTER_V L"\u13a5" #define UNICODE_CHEROKEE_LETTER_GA 0x13a6 #define UNITEXT_CHEROKEE_LETTER_GA L"\u13a6" #define UNICODE_CHEROKEE_LETTER_KA 0x13a7 #define UNITEXT_CHEROKEE_LETTER_KA L"\u13a7" #define UNICODE_CHEROKEE_LETTER_GE 0x13a8 #define UNITEXT_CHEROKEE_LETTER_GE L"\u13a8" #define UNICODE_CHEROKEE_LETTER_GI 0x13a9 #define UNITEXT_CHEROKEE_LETTER_GI L"\u13a9" #define UNICODE_CHEROKEE_LETTER_GO 0x13aa #define UNITEXT_CHEROKEE_LETTER_GO L"\u13aa" #define UNICODE_CHEROKEE_LETTER_GU 0x13ab #define UNITEXT_CHEROKEE_LETTER_GU L"\u13ab" #define UNICODE_CHEROKEE_LETTER_GV 0x13ac #define UNITEXT_CHEROKEE_LETTER_GV L"\u13ac" #define UNICODE_CHEROKEE_LETTER_HA 0x13ad #define UNITEXT_CHEROKEE_LETTER_HA L"\u13ad" #define UNICODE_CHEROKEE_LETTER_HE 0x13ae #define UNITEXT_CHEROKEE_LETTER_HE L"\u13ae" #define UNICODE_CHEROKEE_LETTER_HI 0x13af #define UNITEXT_CHEROKEE_LETTER_HI L"\u13af" #define UNICODE_CHEROKEE_LETTER_HO 0x13b0 #define UNITEXT_CHEROKEE_LETTER_HO L"\u13b0" #define UNICODE_CHEROKEE_LETTER_HU 0x13b1 #define UNITEXT_CHEROKEE_LETTER_HU L"\u13b1" #define UNICODE_CHEROKEE_LETTER_HV 0x13b2 #define UNITEXT_CHEROKEE_LETTER_HV L"\u13b2" #define UNICODE_CHEROKEE_LETTER_LA 0x13b3 #define UNITEXT_CHEROKEE_LETTER_LA L"\u13b3" #define UNICODE_CHEROKEE_LETTER_LE 0x13b4 #define UNITEXT_CHEROKEE_LETTER_LE L"\u13b4" #define UNICODE_CHEROKEE_LETTER_LI 0x13b5 #define UNITEXT_CHEROKEE_LETTER_LI L"\u13b5" #define UNICODE_CHEROKEE_LETTER_LO 0x13b6 #define UNITEXT_CHEROKEE_LETTER_LO L"\u13b6" #define UNICODE_CHEROKEE_LETTER_LU 0x13b7 #define UNITEXT_CHEROKEE_LETTER_LU L"\u13b7" #define UNICODE_CHEROKEE_LETTER_LV 0x13b8 #define UNITEXT_CHEROKEE_LETTER_LV L"\u13b8" #define UNICODE_CHEROKEE_LETTER_MA 0x13b9 #define UNITEXT_CHEROKEE_LETTER_MA L"\u13b9" #define UNICODE_CHEROKEE_LETTER_ME 0x13ba #define UNITEXT_CHEROKEE_LETTER_ME L"\u13ba" #define UNICODE_CHEROKEE_LETTER_MI 0x13bb #define UNITEXT_CHEROKEE_LETTER_MI L"\u13bb" #define UNICODE_CHEROKEE_LETTER_MO 0x13bc #define UNITEXT_CHEROKEE_LETTER_MO L"\u13bc" #define UNICODE_CHEROKEE_LETTER_MU 0x13bd #define UNITEXT_CHEROKEE_LETTER_MU L"\u13bd" #define UNICODE_CHEROKEE_LETTER_NA 0x13be #define UNITEXT_CHEROKEE_LETTER_NA L"\u13be" #define UNICODE_CHEROKEE_LETTER_HNA 0x13bf #define UNITEXT_CHEROKEE_LETTER_HNA L"\u13bf" #define UNICODE_CHEROKEE_LETTER_NAH 0x13c0 #define UNITEXT_CHEROKEE_LETTER_NAH L"\u13c0" #define UNICODE_CHEROKEE_LETTER_NE 0x13c1 #define UNITEXT_CHEROKEE_LETTER_NE L"\u13c1" #define UNICODE_CHEROKEE_LETTER_NI 0x13c2 #define UNITEXT_CHEROKEE_LETTER_NI L"\u13c2" #define UNICODE_CHEROKEE_LETTER_NO 0x13c3 #define UNITEXT_CHEROKEE_LETTER_NO L"\u13c3" #define UNICODE_CHEROKEE_LETTER_NU 0x13c4 #define UNITEXT_CHEROKEE_LETTER_NU L"\u13c4" #define UNICODE_CHEROKEE_LETTER_NV 0x13c5 #define UNITEXT_CHEROKEE_LETTER_NV L"\u13c5" #define UNICODE_CHEROKEE_LETTER_QUA 0x13c6 #define UNITEXT_CHEROKEE_LETTER_QUA L"\u13c6" #define UNICODE_CHEROKEE_LETTER_QUE 0x13c7 #define UNITEXT_CHEROKEE_LETTER_QUE L"\u13c7" #define UNICODE_CHEROKEE_LETTER_QUI 0x13c8 #define UNITEXT_CHEROKEE_LETTER_QUI L"\u13c8" #define UNICODE_CHEROKEE_LETTER_QUO 0x13c9 #define UNITEXT_CHEROKEE_LETTER_QUO L"\u13c9" #define UNICODE_CHEROKEE_LETTER_QUU 0x13ca #define UNITEXT_CHEROKEE_LETTER_QUU L"\u13ca" #define UNICODE_CHEROKEE_LETTER_QUV 0x13cb #define UNITEXT_CHEROKEE_LETTER_QUV L"\u13cb" #define UNICODE_CHEROKEE_LETTER_SA 0x13cc #define UNITEXT_CHEROKEE_LETTER_SA L"\u13cc" #define UNICODE_CHEROKEE_LETTER_S 0x13cd #define UNITEXT_CHEROKEE_LETTER_S L"\u13cd" #define UNICODE_CHEROKEE_LETTER_SE 0x13ce #define UNITEXT_CHEROKEE_LETTER_SE L"\u13ce" #define UNICODE_CHEROKEE_LETTER_SI 0x13cf #define UNITEXT_CHEROKEE_LETTER_SI L"\u13cf" #define UNICODE_CHEROKEE_LETTER_SO 0x13d0 #define UNITEXT_CHEROKEE_LETTER_SO L"\u13d0" #define UNICODE_CHEROKEE_LETTER_SU 0x13d1 #define UNITEXT_CHEROKEE_LETTER_SU L"\u13d1" #define UNICODE_CHEROKEE_LETTER_SV 0x13d2 #define UNITEXT_CHEROKEE_LETTER_SV L"\u13d2" #define UNICODE_CHEROKEE_LETTER_DA 0x13d3 #define UNITEXT_CHEROKEE_LETTER_DA L"\u13d3" #define UNICODE_CHEROKEE_LETTER_TA 0x13d4 #define UNITEXT_CHEROKEE_LETTER_TA L"\u13d4" #define UNICODE_CHEROKEE_LETTER_DE 0x13d5 #define UNITEXT_CHEROKEE_LETTER_DE L"\u13d5" #define UNICODE_CHEROKEE_LETTER_TE 0x13d6 #define UNITEXT_CHEROKEE_LETTER_TE L"\u13d6" #define UNICODE_CHEROKEE_LETTER_DI 0x13d7 #define UNITEXT_CHEROKEE_LETTER_DI L"\u13d7" #define UNICODE_CHEROKEE_LETTER_TI 0x13d8 #define UNITEXT_CHEROKEE_LETTER_TI L"\u13d8" #define UNICODE_CHEROKEE_LETTER_DO 0x13d9 #define UNITEXT_CHEROKEE_LETTER_DO L"\u13d9" #define UNICODE_CHEROKEE_LETTER_DU 0x13da #define UNITEXT_CHEROKEE_LETTER_DU L"\u13da" #define UNICODE_CHEROKEE_LETTER_DV 0x13db #define UNITEXT_CHEROKEE_LETTER_DV L"\u13db" #define UNICODE_CHEROKEE_LETTER_DLA 0x13dc #define UNITEXT_CHEROKEE_LETTER_DLA L"\u13dc" #define UNICODE_CHEROKEE_LETTER_TLA 0x13dd #define UNITEXT_CHEROKEE_LETTER_TLA L"\u13dd" #define UNICODE_CHEROKEE_LETTER_TLE 0x13de #define UNITEXT_CHEROKEE_LETTER_TLE L"\u13de" #define UNICODE_CHEROKEE_LETTER_TLI 0x13df #define UNITEXT_CHEROKEE_LETTER_TLI L"\u13df" #define UNICODE_CHEROKEE_LETTER_TLO 0x13e0 #define UNITEXT_CHEROKEE_LETTER_TLO L"\u13e0" #define UNICODE_CHEROKEE_LETTER_TLU 0x13e1 #define UNITEXT_CHEROKEE_LETTER_TLU L"\u13e1" #define UNICODE_CHEROKEE_LETTER_TLV 0x13e2 #define UNITEXT_CHEROKEE_LETTER_TLV L"\u13e2" #define UNICODE_CHEROKEE_LETTER_TSA 0x13e3 #define UNITEXT_CHEROKEE_LETTER_TSA L"\u13e3" #define UNICODE_CHEROKEE_LETTER_TSE 0x13e4 #define UNITEXT_CHEROKEE_LETTER_TSE L"\u13e4" #define UNICODE_CHEROKEE_LETTER_TSI 0x13e5 #define UNITEXT_CHEROKEE_LETTER_TSI L"\u13e5" #define UNICODE_CHEROKEE_LETTER_TSO 0x13e6 #define UNITEXT_CHEROKEE_LETTER_TSO L"\u13e6" #define UNICODE_CHEROKEE_LETTER_TSU 0x13e7 #define UNITEXT_CHEROKEE_LETTER_TSU L"\u13e7" #define UNICODE_CHEROKEE_LETTER_TSV 0x13e8 #define UNITEXT_CHEROKEE_LETTER_TSV L"\u13e8" #define UNICODE_CHEROKEE_LETTER_WA 0x13e9 #define UNITEXT_CHEROKEE_LETTER_WA L"\u13e9" #define UNICODE_CHEROKEE_LETTER_WE 0x13ea #define UNITEXT_CHEROKEE_LETTER_WE L"\u13ea" #define UNICODE_CHEROKEE_LETTER_WI 0x13eb #define UNITEXT_CHEROKEE_LETTER_WI L"\u13eb" #define UNICODE_CHEROKEE_LETTER_WO 0x13ec #define UNITEXT_CHEROKEE_LETTER_WO L"\u13ec" #define UNICODE_CHEROKEE_LETTER_WU 0x13ed #define UNITEXT_CHEROKEE_LETTER_WU L"\u13ed" #define UNICODE_CHEROKEE_LETTER_WV 0x13ee #define UNITEXT_CHEROKEE_LETTER_WV L"\u13ee" #define UNICODE_CHEROKEE_LETTER_YA 0x13ef #define UNITEXT_CHEROKEE_LETTER_YA L"\u13ef" #define UNICODE_CHEROKEE_LETTER_YE 0x13f0 #define UNITEXT_CHEROKEE_LETTER_YE L"\u13f0" #define UNICODE_CHEROKEE_LETTER_YI 0x13f1 #define UNITEXT_CHEROKEE_LETTER_YI L"\u13f1" #define UNICODE_CHEROKEE_LETTER_YO 0x13f2 #define UNITEXT_CHEROKEE_LETTER_YO L"\u13f2" #define UNICODE_CHEROKEE_LETTER_YU 0x13f3 #define UNITEXT_CHEROKEE_LETTER_YU L"\u13f3" #define UNICODE_CHEROKEE_LETTER_YV 0x13f4 #define UNITEXT_CHEROKEE_LETTER_YV L"\u13f4" #define UNICODE_CANADIAN_SYLLABICS_E 0x1401 #define UNITEXT_CANADIAN_SYLLABICS_E L"\u1401" #define UNICODE_CANADIAN_SYLLABICS_AAI 0x1402 #define UNITEXT_CANADIAN_SYLLABICS_AAI L"\u1402" #define UNICODE_CANADIAN_SYLLABICS_I 0x1403 #define UNITEXT_CANADIAN_SYLLABICS_I L"\u1403" #define UNICODE_CANADIAN_SYLLABICS_II 0x1404 #define UNITEXT_CANADIAN_SYLLABICS_II L"\u1404" #define UNICODE_CANADIAN_SYLLABICS_O 0x1405 #define UNITEXT_CANADIAN_SYLLABICS_O L"\u1405" #define UNICODE_CANADIAN_SYLLABICS_OO 0x1406 #define UNITEXT_CANADIAN_SYLLABICS_OO L"\u1406" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_OO 0x1407 #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_OO L"\u1407" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_EE 0x1408 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_EE L"\u1408" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_I 0x1409 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_I L"\u1409" #define UNICODE_CANADIAN_SYLLABICS_A 0x140a #define UNITEXT_CANADIAN_SYLLABICS_A L"\u140a" #define UNICODE_CANADIAN_SYLLABICS_AA 0x140b #define UNITEXT_CANADIAN_SYLLABICS_AA L"\u140b" #define UNICODE_CANADIAN_SYLLABICS_WE 0x140c #define UNITEXT_CANADIAN_SYLLABICS_WE L"\u140c" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_WE 0x140d #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_WE L"\u140d" #define UNICODE_CANADIAN_SYLLABICS_WI 0x140e #define UNITEXT_CANADIAN_SYLLABICS_WI L"\u140e" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_WI 0x140f #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_WI L"\u140f" #define UNICODE_CANADIAN_SYLLABICS_WII 0x1410 #define UNITEXT_CANADIAN_SYLLABICS_WII L"\u1410" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_WII 0x1411 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_WII L"\u1411" #define UNICODE_CANADIAN_SYLLABICS_WO 0x1412 #define UNITEXT_CANADIAN_SYLLABICS_WO L"\u1412" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_WO 0x1413 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_WO L"\u1413" #define UNICODE_CANADIAN_SYLLABICS_WOO 0x1414 #define UNITEXT_CANADIAN_SYLLABICS_WOO L"\u1414" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_WOO 0x1415 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_WOO L"\u1415" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_WOO 0x1416 #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_WOO L"\u1416" #define UNICODE_CANADIAN_SYLLABICS_WA 0x1417 #define UNITEXT_CANADIAN_SYLLABICS_WA L"\u1417" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_WA 0x1418 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_WA L"\u1418" #define UNICODE_CANADIAN_SYLLABICS_WAA 0x1419 #define UNITEXT_CANADIAN_SYLLABICS_WAA L"\u1419" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_WAA 0x141a #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_WAA L"\u141a" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_WAA 0x141b #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_WAA L"\u141b" #define UNICODE_CANADIAN_SYLLABICS_AI 0x141c #define UNITEXT_CANADIAN_SYLLABICS_AI L"\u141c" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_W 0x141d #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_W L"\u141d" #define UNICODE_CANADIAN_SYLLABICS_GLOTTAL_STOP 0x141e #define UNITEXT_CANADIAN_SYLLABICS_GLOTTAL_STOP L"\u141e" #define UNICODE_CANADIAN_SYLLABICS_FINAL_ACUTE 0x141f #define UNITEXT_CANADIAN_SYLLABICS_FINAL_ACUTE L"\u141f" #define UNICODE_CANADIAN_SYLLABICS_FINAL_GRAVE 0x1420 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_GRAVE L"\u1420" #define UNICODE_CANADIAN_SYLLABICS_FINAL_BOTTOM_HALF_RING 0x1421 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_BOTTOM_HALF_RING L"\u1421" #define UNICODE_CANADIAN_SYLLABICS_FINAL_TOP_HALF_RING 0x1422 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_TOP_HALF_RING L"\u1422" #define UNICODE_CANADIAN_SYLLABICS_FINAL_RIGHT_HALF_RING 0x1423 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_RIGHT_HALF_RING L"\u1423" #define UNICODE_CANADIAN_SYLLABICS_FINAL_RING 0x1424 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_RING L"\u1424" #define UNICODE_CANADIAN_SYLLABICS_FINAL_DOUBLE_ACUTE 0x1425 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_DOUBLE_ACUTE L"\u1425" #define UNICODE_CANADIAN_SYLLABICS_FINAL_DOUBLE_SHORT_VERTICAL_STROKES 0x1426 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_DOUBLE_SHORT_VERTICAL_STROKES L"\u1426" #define UNICODE_CANADIAN_SYLLABICS_FINAL_MIDDLE_DOT 0x1427 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_MIDDLE_DOT L"\u1427" #define UNICODE_CANADIAN_SYLLABICS_FINAL_SHORT_HORIZONTAL_STROKE 0x1428 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_SHORT_HORIZONTAL_STROKE L"\u1428" #define UNICODE_CANADIAN_SYLLABICS_FINAL_PLUS 0x1429 #define UNITEXT_CANADIAN_SYLLABICS_FINAL_PLUS L"\u1429" #define UNICODE_CANADIAN_SYLLABICS_FINAL_DOWN_TACK 0x142a #define UNITEXT_CANADIAN_SYLLABICS_FINAL_DOWN_TACK L"\u142a" #define UNICODE_CANADIAN_SYLLABICS_EN 0x142b #define UNITEXT_CANADIAN_SYLLABICS_EN L"\u142b" #define UNICODE_CANADIAN_SYLLABICS_IN 0x142c #define UNITEXT_CANADIAN_SYLLABICS_IN L"\u142c" #define UNICODE_CANADIAN_SYLLABICS_ON 0x142d #define UNITEXT_CANADIAN_SYLLABICS_ON L"\u142d" #define UNICODE_CANADIAN_SYLLABICS_AN 0x142e #define UNITEXT_CANADIAN_SYLLABICS_AN L"\u142e" #define UNICODE_CANADIAN_SYLLABICS_PE 0x142f #define UNITEXT_CANADIAN_SYLLABICS_PE L"\u142f" #define UNICODE_CANADIAN_SYLLABICS_PAAI 0x1430 #define UNITEXT_CANADIAN_SYLLABICS_PAAI L"\u1430" #define UNICODE_CANADIAN_SYLLABICS_PI 0x1431 #define UNITEXT_CANADIAN_SYLLABICS_PI L"\u1431" #define UNICODE_CANADIAN_SYLLABICS_PII 0x1432 #define UNITEXT_CANADIAN_SYLLABICS_PII L"\u1432" #define UNICODE_CANADIAN_SYLLABICS_PO 0x1433 #define UNITEXT_CANADIAN_SYLLABICS_PO L"\u1433" #define UNICODE_CANADIAN_SYLLABICS_POO 0x1434 #define UNITEXT_CANADIAN_SYLLABICS_POO L"\u1434" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_POO 0x1435 #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_POO L"\u1435" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_HEE 0x1436 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_HEE L"\u1436" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_HI 0x1437 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_HI L"\u1437" #define UNICODE_CANADIAN_SYLLABICS_PA 0x1438 #define UNITEXT_CANADIAN_SYLLABICS_PA L"\u1438" #define UNICODE_CANADIAN_SYLLABICS_PAA 0x1439 #define UNITEXT_CANADIAN_SYLLABICS_PAA L"\u1439" #define UNICODE_CANADIAN_SYLLABICS_PWE 0x143a #define UNITEXT_CANADIAN_SYLLABICS_PWE L"\u143a" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_PWE 0x143b #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_PWE L"\u143b" #define UNICODE_CANADIAN_SYLLABICS_PWI 0x143c #define UNITEXT_CANADIAN_SYLLABICS_PWI L"\u143c" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_PWI 0x143d #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_PWI L"\u143d" #define UNICODE_CANADIAN_SYLLABICS_PWII 0x143e #define UNITEXT_CANADIAN_SYLLABICS_PWII L"\u143e" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_PWII 0x143f #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_PWII L"\u143f" #define UNICODE_CANADIAN_SYLLABICS_PWO 0x1440 #define UNITEXT_CANADIAN_SYLLABICS_PWO L"\u1440" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_PWO 0x1441 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_PWO L"\u1441" #define UNICODE_CANADIAN_SYLLABICS_PWOO 0x1442 #define UNITEXT_CANADIAN_SYLLABICS_PWOO L"\u1442" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_PWOO 0x1443 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_PWOO L"\u1443" #define UNICODE_CANADIAN_SYLLABICS_PWA 0x1444 #define UNITEXT_CANADIAN_SYLLABICS_PWA L"\u1444" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_PWA 0x1445 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_PWA L"\u1445" #define UNICODE_CANADIAN_SYLLABICS_PWAA 0x1446 #define UNITEXT_CANADIAN_SYLLABICS_PWAA L"\u1446" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_PWAA 0x1447 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_PWAA L"\u1447" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_PWAA 0x1448 #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_PWAA L"\u1448" #define UNICODE_CANADIAN_SYLLABICS_P 0x1449 #define UNITEXT_CANADIAN_SYLLABICS_P L"\u1449" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_P 0x144a #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_P L"\u144a" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_H 0x144b #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_H L"\u144b" #define UNICODE_CANADIAN_SYLLABICS_TE 0x144c #define UNITEXT_CANADIAN_SYLLABICS_TE L"\u144c" #define UNICODE_CANADIAN_SYLLABICS_TAAI 0x144d #define UNITEXT_CANADIAN_SYLLABICS_TAAI L"\u144d" #define UNICODE_CANADIAN_SYLLABICS_TI 0x144e #define UNITEXT_CANADIAN_SYLLABICS_TI L"\u144e" #define UNICODE_CANADIAN_SYLLABICS_TII 0x144f #define UNITEXT_CANADIAN_SYLLABICS_TII L"\u144f" #define UNICODE_CANADIAN_SYLLABICS_TO 0x1450 #define UNITEXT_CANADIAN_SYLLABICS_TO L"\u1450" #define UNICODE_CANADIAN_SYLLABICS_TOO 0x1451 #define UNITEXT_CANADIAN_SYLLABICS_TOO L"\u1451" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_TOO 0x1452 #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_TOO L"\u1452" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DEE 0x1453 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DEE L"\u1453" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DI 0x1454 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DI L"\u1454" #define UNICODE_CANADIAN_SYLLABICS_TA 0x1455 #define UNITEXT_CANADIAN_SYLLABICS_TA L"\u1455" #define UNICODE_CANADIAN_SYLLABICS_TAA 0x1456 #define UNITEXT_CANADIAN_SYLLABICS_TAA L"\u1456" #define UNICODE_CANADIAN_SYLLABICS_TWE 0x1457 #define UNITEXT_CANADIAN_SYLLABICS_TWE L"\u1457" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_TWE 0x1458 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_TWE L"\u1458" #define UNICODE_CANADIAN_SYLLABICS_TWI 0x1459 #define UNITEXT_CANADIAN_SYLLABICS_TWI L"\u1459" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_TWI 0x145a #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_TWI L"\u145a" #define UNICODE_CANADIAN_SYLLABICS_TWII 0x145b #define UNITEXT_CANADIAN_SYLLABICS_TWII L"\u145b" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_TWII 0x145c #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_TWII L"\u145c" #define UNICODE_CANADIAN_SYLLABICS_TWO 0x145d #define UNITEXT_CANADIAN_SYLLABICS_TWO L"\u145d" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_TWO 0x145e #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_TWO L"\u145e" #define UNICODE_CANADIAN_SYLLABICS_TWOO 0x145f #define UNITEXT_CANADIAN_SYLLABICS_TWOO L"\u145f" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_TWOO 0x1460 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_TWOO L"\u1460" #define UNICODE_CANADIAN_SYLLABICS_TWA 0x1461 #define UNITEXT_CANADIAN_SYLLABICS_TWA L"\u1461" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_TWA 0x1462 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_TWA L"\u1462" #define UNICODE_CANADIAN_SYLLABICS_TWAA 0x1463 #define UNITEXT_CANADIAN_SYLLABICS_TWAA L"\u1463" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_TWAA 0x1464 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_TWAA L"\u1464" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_TWAA 0x1465 #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_TWAA L"\u1465" #define UNICODE_CANADIAN_SYLLABICS_T 0x1466 #define UNITEXT_CANADIAN_SYLLABICS_T L"\u1466" #define UNICODE_CANADIAN_SYLLABICS_TTE 0x1467 #define UNITEXT_CANADIAN_SYLLABICS_TTE L"\u1467" #define UNICODE_CANADIAN_SYLLABICS_TTI 0x1468 #define UNITEXT_CANADIAN_SYLLABICS_TTI L"\u1468" #define UNICODE_CANADIAN_SYLLABICS_TTO 0x1469 #define UNITEXT_CANADIAN_SYLLABICS_TTO L"\u1469" #define UNICODE_CANADIAN_SYLLABICS_TTA 0x146a #define UNITEXT_CANADIAN_SYLLABICS_TTA L"\u146a" #define UNICODE_CANADIAN_SYLLABICS_KE 0x146b #define UNITEXT_CANADIAN_SYLLABICS_KE L"\u146b" #define UNICODE_CANADIAN_SYLLABICS_KAAI 0x146c #define UNITEXT_CANADIAN_SYLLABICS_KAAI L"\u146c" #define UNICODE_CANADIAN_SYLLABICS_KI 0x146d #define UNITEXT_CANADIAN_SYLLABICS_KI L"\u146d" #define UNICODE_CANADIAN_SYLLABICS_KII 0x146e #define UNITEXT_CANADIAN_SYLLABICS_KII L"\u146e" #define UNICODE_CANADIAN_SYLLABICS_KO 0x146f #define UNITEXT_CANADIAN_SYLLABICS_KO L"\u146f" #define UNICODE_CANADIAN_SYLLABICS_KOO 0x1470 #define UNITEXT_CANADIAN_SYLLABICS_KOO L"\u1470" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_KOO 0x1471 #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_KOO L"\u1471" #define UNICODE_CANADIAN_SYLLABICS_KA 0x1472 #define UNITEXT_CANADIAN_SYLLABICS_KA L"\u1472" #define UNICODE_CANADIAN_SYLLABICS_KAA 0x1473 #define UNITEXT_CANADIAN_SYLLABICS_KAA L"\u1473" #define UNICODE_CANADIAN_SYLLABICS_KWE 0x1474 #define UNITEXT_CANADIAN_SYLLABICS_KWE L"\u1474" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_KWE 0x1475 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_KWE L"\u1475" #define UNICODE_CANADIAN_SYLLABICS_KWI 0x1476 #define UNITEXT_CANADIAN_SYLLABICS_KWI L"\u1476" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_KWI 0x1477 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_KWI L"\u1477" #define UNICODE_CANADIAN_SYLLABICS_KWII 0x1478 #define UNITEXT_CANADIAN_SYLLABICS_KWII L"\u1478" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_KWII 0x1479 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_KWII L"\u1479" #define UNICODE_CANADIAN_SYLLABICS_KWO 0x147a #define UNITEXT_CANADIAN_SYLLABICS_KWO L"\u147a" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_KWO 0x147b #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_KWO L"\u147b" #define UNICODE_CANADIAN_SYLLABICS_KWOO 0x147c #define UNITEXT_CANADIAN_SYLLABICS_KWOO L"\u147c" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_KWOO 0x147d #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_KWOO L"\u147d" #define UNICODE_CANADIAN_SYLLABICS_KWA 0x147e #define UNITEXT_CANADIAN_SYLLABICS_KWA L"\u147e" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_KWA 0x147f #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_KWA L"\u147f" #define UNICODE_CANADIAN_SYLLABICS_KWAA 0x1480 #define UNITEXT_CANADIAN_SYLLABICS_KWAA L"\u1480" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_KWAA 0x1481 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_KWAA L"\u1481" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_KWAA 0x1482 #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_KWAA L"\u1482" #define UNICODE_CANADIAN_SYLLABICS_K 0x1483 #define UNITEXT_CANADIAN_SYLLABICS_K L"\u1483" #define UNICODE_CANADIAN_SYLLABICS_KW 0x1484 #define UNITEXT_CANADIAN_SYLLABICS_KW L"\u1484" #define UNICODE_CANADIAN_SYLLABICS_SOUTH_SLAVEY_KEH 0x1485 #define UNITEXT_CANADIAN_SYLLABICS_SOUTH_SLAVEY_KEH L"\u1485" #define UNICODE_CANADIAN_SYLLABICS_SOUTH_SLAVEY_KIH 0x1486 #define UNITEXT_CANADIAN_SYLLABICS_SOUTH_SLAVEY_KIH L"\u1486" #define UNICODE_CANADIAN_SYLLABICS_SOUTH_SLAVEY_KOH 0x1487 #define UNITEXT_CANADIAN_SYLLABICS_SOUTH_SLAVEY_KOH L"\u1487" #define UNICODE_CANADIAN_SYLLABICS_SOUTH_SLAVEY_KAH 0x1488 #define UNITEXT_CANADIAN_SYLLABICS_SOUTH_SLAVEY_KAH L"\u1488" #define UNICODE_CANADIAN_SYLLABICS_CE 0x1489 #define UNITEXT_CANADIAN_SYLLABICS_CE L"\u1489" #define UNICODE_CANADIAN_SYLLABICS_CAAI 0x148a #define UNITEXT_CANADIAN_SYLLABICS_CAAI L"\u148a" #define UNICODE_CANADIAN_SYLLABICS_CI 0x148b #define UNITEXT_CANADIAN_SYLLABICS_CI L"\u148b" #define UNICODE_CANADIAN_SYLLABICS_CII 0x148c #define UNITEXT_CANADIAN_SYLLABICS_CII L"\u148c" #define UNICODE_CANADIAN_SYLLABICS_CO 0x148d #define UNITEXT_CANADIAN_SYLLABICS_CO L"\u148d" #define UNICODE_CANADIAN_SYLLABICS_COO 0x148e #define UNITEXT_CANADIAN_SYLLABICS_COO L"\u148e" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_COO 0x148f #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_COO L"\u148f" #define UNICODE_CANADIAN_SYLLABICS_CA 0x1490 #define UNITEXT_CANADIAN_SYLLABICS_CA L"\u1490" #define UNICODE_CANADIAN_SYLLABICS_CAA 0x1491 #define UNITEXT_CANADIAN_SYLLABICS_CAA L"\u1491" #define UNICODE_CANADIAN_SYLLABICS_CWE 0x1492 #define UNITEXT_CANADIAN_SYLLABICS_CWE L"\u1492" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_CWE 0x1493 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_CWE L"\u1493" #define UNICODE_CANADIAN_SYLLABICS_CWI 0x1494 #define UNITEXT_CANADIAN_SYLLABICS_CWI L"\u1494" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_CWI 0x1495 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_CWI L"\u1495" #define UNICODE_CANADIAN_SYLLABICS_CWII 0x1496 #define UNITEXT_CANADIAN_SYLLABICS_CWII L"\u1496" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_CWII 0x1497 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_CWII L"\u1497" #define UNICODE_CANADIAN_SYLLABICS_CWO 0x1498 #define UNITEXT_CANADIAN_SYLLABICS_CWO L"\u1498" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_CWO 0x1499 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_CWO L"\u1499" #define UNICODE_CANADIAN_SYLLABICS_CWOO 0x149a #define UNITEXT_CANADIAN_SYLLABICS_CWOO L"\u149a" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_CWOO 0x149b #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_CWOO L"\u149b" #define UNICODE_CANADIAN_SYLLABICS_CWA 0x149c #define UNITEXT_CANADIAN_SYLLABICS_CWA L"\u149c" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_CWA 0x149d #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_CWA L"\u149d" #define UNICODE_CANADIAN_SYLLABICS_CWAA 0x149e #define UNITEXT_CANADIAN_SYLLABICS_CWAA L"\u149e" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_CWAA 0x149f #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_CWAA L"\u149f" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_CWAA 0x14a0 #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_CWAA L"\u14a0" #define UNICODE_CANADIAN_SYLLABICS_C 0x14a1 #define UNITEXT_CANADIAN_SYLLABICS_C L"\u14a1" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_TH 0x14a2 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_TH L"\u14a2" #define UNICODE_CANADIAN_SYLLABICS_ME 0x14a3 #define UNITEXT_CANADIAN_SYLLABICS_ME L"\u14a3" #define UNICODE_CANADIAN_SYLLABICS_MAAI 0x14a4 #define UNITEXT_CANADIAN_SYLLABICS_MAAI L"\u14a4" #define UNICODE_CANADIAN_SYLLABICS_MI 0x14a5 #define UNITEXT_CANADIAN_SYLLABICS_MI L"\u14a5" #define UNICODE_CANADIAN_SYLLABICS_MII 0x14a6 #define UNITEXT_CANADIAN_SYLLABICS_MII L"\u14a6" #define UNICODE_CANADIAN_SYLLABICS_MO 0x14a7 #define UNITEXT_CANADIAN_SYLLABICS_MO L"\u14a7" #define UNICODE_CANADIAN_SYLLABICS_MOO 0x14a8 #define UNITEXT_CANADIAN_SYLLABICS_MOO L"\u14a8" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_MOO 0x14a9 #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_MOO L"\u14a9" #define UNICODE_CANADIAN_SYLLABICS_MA 0x14aa #define UNITEXT_CANADIAN_SYLLABICS_MA L"\u14aa" #define UNICODE_CANADIAN_SYLLABICS_MAA 0x14ab #define UNITEXT_CANADIAN_SYLLABICS_MAA L"\u14ab" #define UNICODE_CANADIAN_SYLLABICS_MWE 0x14ac #define UNITEXT_CANADIAN_SYLLABICS_MWE L"\u14ac" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_MWE 0x14ad #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_MWE L"\u14ad" #define UNICODE_CANADIAN_SYLLABICS_MWI 0x14ae #define UNITEXT_CANADIAN_SYLLABICS_MWI L"\u14ae" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_MWI 0x14af #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_MWI L"\u14af" #define UNICODE_CANADIAN_SYLLABICS_MWII 0x14b0 #define UNITEXT_CANADIAN_SYLLABICS_MWII L"\u14b0" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_MWII 0x14b1 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_MWII L"\u14b1" #define UNICODE_CANADIAN_SYLLABICS_MWO 0x14b2 #define UNITEXT_CANADIAN_SYLLABICS_MWO L"\u14b2" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_MWO 0x14b3 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_MWO L"\u14b3" #define UNICODE_CANADIAN_SYLLABICS_MWOO 0x14b4 #define UNITEXT_CANADIAN_SYLLABICS_MWOO L"\u14b4" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_MWOO 0x14b5 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_MWOO L"\u14b5" #define UNICODE_CANADIAN_SYLLABICS_MWA 0x14b6 #define UNITEXT_CANADIAN_SYLLABICS_MWA L"\u14b6" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_MWA 0x14b7 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_MWA L"\u14b7" #define UNICODE_CANADIAN_SYLLABICS_MWAA 0x14b8 #define UNITEXT_CANADIAN_SYLLABICS_MWAA L"\u14b8" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_MWAA 0x14b9 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_MWAA L"\u14b9" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_MWAA 0x14ba #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_MWAA L"\u14ba" #define UNICODE_CANADIAN_SYLLABICS_M 0x14bb #define UNITEXT_CANADIAN_SYLLABICS_M L"\u14bb" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_M 0x14bc #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_M L"\u14bc" #define UNICODE_CANADIAN_SYLLABICS_MH 0x14bd #define UNITEXT_CANADIAN_SYLLABICS_MH L"\u14bd" #define UNICODE_CANADIAN_SYLLABICS_ATHAPASCAN_M 0x14be #define UNITEXT_CANADIAN_SYLLABICS_ATHAPASCAN_M L"\u14be" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_M 0x14bf #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_M L"\u14bf" #define UNICODE_CANADIAN_SYLLABICS_NE 0x14c0 #define UNITEXT_CANADIAN_SYLLABICS_NE L"\u14c0" #define UNICODE_CANADIAN_SYLLABICS_NAAI 0x14c1 #define UNITEXT_CANADIAN_SYLLABICS_NAAI L"\u14c1" #define UNICODE_CANADIAN_SYLLABICS_NI 0x14c2 #define UNITEXT_CANADIAN_SYLLABICS_NI L"\u14c2" #define UNICODE_CANADIAN_SYLLABICS_NII 0x14c3 #define UNITEXT_CANADIAN_SYLLABICS_NII L"\u14c3" #define UNICODE_CANADIAN_SYLLABICS_NO 0x14c4 #define UNITEXT_CANADIAN_SYLLABICS_NO L"\u14c4" #define UNICODE_CANADIAN_SYLLABICS_NOO 0x14c5 #define UNITEXT_CANADIAN_SYLLABICS_NOO L"\u14c5" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_NOO 0x14c6 #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_NOO L"\u14c6" #define UNICODE_CANADIAN_SYLLABICS_NA 0x14c7 #define UNITEXT_CANADIAN_SYLLABICS_NA L"\u14c7" #define UNICODE_CANADIAN_SYLLABICS_NAA 0x14c8 #define UNITEXT_CANADIAN_SYLLABICS_NAA L"\u14c8" #define UNICODE_CANADIAN_SYLLABICS_NWE 0x14c9 #define UNITEXT_CANADIAN_SYLLABICS_NWE L"\u14c9" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_NWE 0x14ca #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_NWE L"\u14ca" #define UNICODE_CANADIAN_SYLLABICS_NWA 0x14cb #define UNITEXT_CANADIAN_SYLLABICS_NWA L"\u14cb" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_NWA 0x14cc #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_NWA L"\u14cc" #define UNICODE_CANADIAN_SYLLABICS_NWAA 0x14cd #define UNITEXT_CANADIAN_SYLLABICS_NWAA L"\u14cd" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_NWAA 0x14ce #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_NWAA L"\u14ce" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_NWAA 0x14cf #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_NWAA L"\u14cf" #define UNICODE_CANADIAN_SYLLABICS_N 0x14d0 #define UNITEXT_CANADIAN_SYLLABICS_N L"\u14d0" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_NG 0x14d1 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_NG L"\u14d1" #define UNICODE_CANADIAN_SYLLABICS_NH 0x14d2 #define UNITEXT_CANADIAN_SYLLABICS_NH L"\u14d2" #define UNICODE_CANADIAN_SYLLABICS_LE 0x14d3 #define UNITEXT_CANADIAN_SYLLABICS_LE L"\u14d3" #define UNICODE_CANADIAN_SYLLABICS_LAAI 0x14d4 #define UNITEXT_CANADIAN_SYLLABICS_LAAI L"\u14d4" #define UNICODE_CANADIAN_SYLLABICS_LI 0x14d5 #define UNITEXT_CANADIAN_SYLLABICS_LI L"\u14d5" #define UNICODE_CANADIAN_SYLLABICS_LII 0x14d6 #define UNITEXT_CANADIAN_SYLLABICS_LII L"\u14d6" #define UNICODE_CANADIAN_SYLLABICS_LO 0x14d7 #define UNITEXT_CANADIAN_SYLLABICS_LO L"\u14d7" #define UNICODE_CANADIAN_SYLLABICS_LOO 0x14d8 #define UNITEXT_CANADIAN_SYLLABICS_LOO L"\u14d8" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_LOO 0x14d9 #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_LOO L"\u14d9" #define UNICODE_CANADIAN_SYLLABICS_LA 0x14da #define UNITEXT_CANADIAN_SYLLABICS_LA L"\u14da" #define UNICODE_CANADIAN_SYLLABICS_LAA 0x14db #define UNITEXT_CANADIAN_SYLLABICS_LAA L"\u14db" #define UNICODE_CANADIAN_SYLLABICS_LWE 0x14dc #define UNITEXT_CANADIAN_SYLLABICS_LWE L"\u14dc" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LWE 0x14dd #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LWE L"\u14dd" #define UNICODE_CANADIAN_SYLLABICS_LWI 0x14de #define UNITEXT_CANADIAN_SYLLABICS_LWI L"\u14de" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LWI 0x14df #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LWI L"\u14df" #define UNICODE_CANADIAN_SYLLABICS_LWII 0x14e0 #define UNITEXT_CANADIAN_SYLLABICS_LWII L"\u14e0" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LWII 0x14e1 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LWII L"\u14e1" #define UNICODE_CANADIAN_SYLLABICS_LWO 0x14e2 #define UNITEXT_CANADIAN_SYLLABICS_LWO L"\u14e2" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LWO 0x14e3 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LWO L"\u14e3" #define UNICODE_CANADIAN_SYLLABICS_LWOO 0x14e4 #define UNITEXT_CANADIAN_SYLLABICS_LWOO L"\u14e4" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LWOO 0x14e5 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LWOO L"\u14e5" #define UNICODE_CANADIAN_SYLLABICS_LWA 0x14e6 #define UNITEXT_CANADIAN_SYLLABICS_LWA L"\u14e6" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LWA 0x14e7 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LWA L"\u14e7" #define UNICODE_CANADIAN_SYLLABICS_LWAA 0x14e8 #define UNITEXT_CANADIAN_SYLLABICS_LWAA L"\u14e8" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LWAA 0x14e9 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LWAA L"\u14e9" #define UNICODE_CANADIAN_SYLLABICS_L 0x14ea #define UNITEXT_CANADIAN_SYLLABICS_L L"\u14ea" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_L 0x14eb #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_L L"\u14eb" #define UNICODE_CANADIAN_SYLLABICS_MEDIAL_L 0x14ec #define UNITEXT_CANADIAN_SYLLABICS_MEDIAL_L L"\u14ec" #define UNICODE_CANADIAN_SYLLABICS_SE 0x14ed #define UNITEXT_CANADIAN_SYLLABICS_SE L"\u14ed" #define UNICODE_CANADIAN_SYLLABICS_SAAI 0x14ee #define UNITEXT_CANADIAN_SYLLABICS_SAAI L"\u14ee" #define UNICODE_CANADIAN_SYLLABICS_SI 0x14ef #define UNITEXT_CANADIAN_SYLLABICS_SI L"\u14ef" #define UNICODE_CANADIAN_SYLLABICS_SII 0x14f0 #define UNITEXT_CANADIAN_SYLLABICS_SII L"\u14f0" #define UNICODE_CANADIAN_SYLLABICS_SO 0x14f1 #define UNITEXT_CANADIAN_SYLLABICS_SO L"\u14f1" #define UNICODE_CANADIAN_SYLLABICS_SOO 0x14f2 #define UNITEXT_CANADIAN_SYLLABICS_SOO L"\u14f2" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_SOO 0x14f3 #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_SOO L"\u14f3" #define UNICODE_CANADIAN_SYLLABICS_SA 0x14f4 #define UNITEXT_CANADIAN_SYLLABICS_SA L"\u14f4" #define UNICODE_CANADIAN_SYLLABICS_SAA 0x14f5 #define UNITEXT_CANADIAN_SYLLABICS_SAA L"\u14f5" #define UNICODE_CANADIAN_SYLLABICS_SWE 0x14f6 #define UNITEXT_CANADIAN_SYLLABICS_SWE L"\u14f6" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SWE 0x14f7 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SWE L"\u14f7" #define UNICODE_CANADIAN_SYLLABICS_SWI 0x14f8 #define UNITEXT_CANADIAN_SYLLABICS_SWI L"\u14f8" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SWI 0x14f9 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SWI L"\u14f9" #define UNICODE_CANADIAN_SYLLABICS_SWII 0x14fa #define UNITEXT_CANADIAN_SYLLABICS_SWII L"\u14fa" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SWII 0x14fb #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SWII L"\u14fb" #define UNICODE_CANADIAN_SYLLABICS_SWO 0x14fc #define UNITEXT_CANADIAN_SYLLABICS_SWO L"\u14fc" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SWO 0x14fd #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SWO L"\u14fd" #define UNICODE_CANADIAN_SYLLABICS_SWOO 0x14fe #define UNITEXT_CANADIAN_SYLLABICS_SWOO L"\u14fe" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SWOO 0x14ff #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SWOO L"\u14ff" #define UNICODE_CANADIAN_SYLLABICS_SWA 0x1500 #define UNITEXT_CANADIAN_SYLLABICS_SWA L"\u1500" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SWA 0x1501 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SWA L"\u1501" #define UNICODE_CANADIAN_SYLLABICS_SWAA 0x1502 #define UNITEXT_CANADIAN_SYLLABICS_SWAA L"\u1502" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SWAA 0x1503 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SWAA L"\u1503" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_SWAA 0x1504 #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_SWAA L"\u1504" #define UNICODE_CANADIAN_SYLLABICS_S 0x1505 #define UNITEXT_CANADIAN_SYLLABICS_S L"\u1505" #define UNICODE_CANADIAN_SYLLABICS_ATHAPASCAN_S 0x1506 #define UNITEXT_CANADIAN_SYLLABICS_ATHAPASCAN_S L"\u1506" #define UNICODE_CANADIAN_SYLLABICS_SW 0x1507 #define UNITEXT_CANADIAN_SYLLABICS_SW L"\u1507" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_S 0x1508 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_S L"\u1508" #define UNICODE_CANADIAN_SYLLABICS_MOOSE_CREE_SK 0x1509 #define UNITEXT_CANADIAN_SYLLABICS_MOOSE_CREE_SK L"\u1509" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_SKW 0x150a #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_SKW L"\u150a" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_S_W 0x150b #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_S_W L"\u150b" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_SPWA 0x150c #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_SPWA L"\u150c" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_STWA 0x150d #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_STWA L"\u150d" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_SKWA 0x150e #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_SKWA L"\u150e" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_SCWA 0x150f #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_SCWA L"\u150f" #define UNICODE_CANADIAN_SYLLABICS_SHE 0x1510 #define UNITEXT_CANADIAN_SYLLABICS_SHE L"\u1510" #define UNICODE_CANADIAN_SYLLABICS_SHI 0x1511 #define UNITEXT_CANADIAN_SYLLABICS_SHI L"\u1511" #define UNICODE_CANADIAN_SYLLABICS_SHII 0x1512 #define UNITEXT_CANADIAN_SYLLABICS_SHII L"\u1512" #define UNICODE_CANADIAN_SYLLABICS_SHO 0x1513 #define UNITEXT_CANADIAN_SYLLABICS_SHO L"\u1513" #define UNICODE_CANADIAN_SYLLABICS_SHOO 0x1514 #define UNITEXT_CANADIAN_SYLLABICS_SHOO L"\u1514" #define UNICODE_CANADIAN_SYLLABICS_SHA 0x1515 #define UNITEXT_CANADIAN_SYLLABICS_SHA L"\u1515" #define UNICODE_CANADIAN_SYLLABICS_SHAA 0x1516 #define UNITEXT_CANADIAN_SYLLABICS_SHAA L"\u1516" #define UNICODE_CANADIAN_SYLLABICS_SHWE 0x1517 #define UNITEXT_CANADIAN_SYLLABICS_SHWE L"\u1517" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SHWE 0x1518 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SHWE L"\u1518" #define UNICODE_CANADIAN_SYLLABICS_SHWI 0x1519 #define UNITEXT_CANADIAN_SYLLABICS_SHWI L"\u1519" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SHWI 0x151a #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SHWI L"\u151a" #define UNICODE_CANADIAN_SYLLABICS_SHWII 0x151b #define UNITEXT_CANADIAN_SYLLABICS_SHWII L"\u151b" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SHWII 0x151c #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SHWII L"\u151c" #define UNICODE_CANADIAN_SYLLABICS_SHWO 0x151d #define UNITEXT_CANADIAN_SYLLABICS_SHWO L"\u151d" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SHWO 0x151e #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SHWO L"\u151e" #define UNICODE_CANADIAN_SYLLABICS_SHWOO 0x151f #define UNITEXT_CANADIAN_SYLLABICS_SHWOO L"\u151f" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SHWOO 0x1520 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SHWOO L"\u1520" #define UNICODE_CANADIAN_SYLLABICS_SHWA 0x1521 #define UNITEXT_CANADIAN_SYLLABICS_SHWA L"\u1521" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SHWA 0x1522 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SHWA L"\u1522" #define UNICODE_CANADIAN_SYLLABICS_SHWAA 0x1523 #define UNITEXT_CANADIAN_SYLLABICS_SHWAA L"\u1523" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_SHWAA 0x1524 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_SHWAA L"\u1524" #define UNICODE_CANADIAN_SYLLABICS_SH 0x1525 #define UNITEXT_CANADIAN_SYLLABICS_SH L"\u1525" #define UNICODE_CANADIAN_SYLLABICS_YE 0x1526 #define UNITEXT_CANADIAN_SYLLABICS_YE L"\u1526" #define UNICODE_CANADIAN_SYLLABICS_YAAI 0x1527 #define UNITEXT_CANADIAN_SYLLABICS_YAAI L"\u1527" #define UNICODE_CANADIAN_SYLLABICS_YI 0x1528 #define UNITEXT_CANADIAN_SYLLABICS_YI L"\u1528" #define UNICODE_CANADIAN_SYLLABICS_YII 0x1529 #define UNITEXT_CANADIAN_SYLLABICS_YII L"\u1529" #define UNICODE_CANADIAN_SYLLABICS_YO 0x152a #define UNITEXT_CANADIAN_SYLLABICS_YO L"\u152a" #define UNICODE_CANADIAN_SYLLABICS_YOO 0x152b #define UNITEXT_CANADIAN_SYLLABICS_YOO L"\u152b" #define UNICODE_CANADIAN_SYLLABICS_Y_CREE_YOO 0x152c #define UNITEXT_CANADIAN_SYLLABICS_Y_CREE_YOO L"\u152c" #define UNICODE_CANADIAN_SYLLABICS_YA 0x152d #define UNITEXT_CANADIAN_SYLLABICS_YA L"\u152d" #define UNICODE_CANADIAN_SYLLABICS_YAA 0x152e #define UNITEXT_CANADIAN_SYLLABICS_YAA L"\u152e" #define UNICODE_CANADIAN_SYLLABICS_YWE 0x152f #define UNITEXT_CANADIAN_SYLLABICS_YWE L"\u152f" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_YWE 0x1530 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_YWE L"\u1530" #define UNICODE_CANADIAN_SYLLABICS_YWI 0x1531 #define UNITEXT_CANADIAN_SYLLABICS_YWI L"\u1531" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_YWI 0x1532 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_YWI L"\u1532" #define UNICODE_CANADIAN_SYLLABICS_YWII 0x1533 #define UNITEXT_CANADIAN_SYLLABICS_YWII L"\u1533" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_YWII 0x1534 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_YWII L"\u1534" #define UNICODE_CANADIAN_SYLLABICS_YWO 0x1535 #define UNITEXT_CANADIAN_SYLLABICS_YWO L"\u1535" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_YWO 0x1536 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_YWO L"\u1536" #define UNICODE_CANADIAN_SYLLABICS_YWOO 0x1537 #define UNITEXT_CANADIAN_SYLLABICS_YWOO L"\u1537" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_YWOO 0x1538 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_YWOO L"\u1538" #define UNICODE_CANADIAN_SYLLABICS_YWA 0x1539 #define UNITEXT_CANADIAN_SYLLABICS_YWA L"\u1539" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_YWA 0x153a #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_YWA L"\u153a" #define UNICODE_CANADIAN_SYLLABICS_YWAA 0x153b #define UNITEXT_CANADIAN_SYLLABICS_YWAA L"\u153b" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_YWAA 0x153c #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_YWAA L"\u153c" #define UNICODE_CANADIAN_SYLLABICS_NASKAPI_YWAA 0x153d #define UNITEXT_CANADIAN_SYLLABICS_NASKAPI_YWAA L"\u153d" #define UNICODE_CANADIAN_SYLLABICS_Y 0x153e #define UNITEXT_CANADIAN_SYLLABICS_Y L"\u153e" #define UNICODE_CANADIAN_SYLLABICS_BIBLE_CREE_Y 0x153f #define UNITEXT_CANADIAN_SYLLABICS_BIBLE_CREE_Y L"\u153f" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_Y 0x1540 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_Y L"\u1540" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_YI 0x1541 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_YI L"\u1541" #define UNICODE_CANADIAN_SYLLABICS_RE 0x1542 #define UNITEXT_CANADIAN_SYLLABICS_RE L"\u1542" #define UNICODE_CANADIAN_SYLLABICS_R_CREE_RE 0x1543 #define UNITEXT_CANADIAN_SYLLABICS_R_CREE_RE L"\u1543" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LE 0x1544 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LE L"\u1544" #define UNICODE_CANADIAN_SYLLABICS_RAAI 0x1545 #define UNITEXT_CANADIAN_SYLLABICS_RAAI L"\u1545" #define UNICODE_CANADIAN_SYLLABICS_RI 0x1546 #define UNITEXT_CANADIAN_SYLLABICS_RI L"\u1546" #define UNICODE_CANADIAN_SYLLABICS_RII 0x1547 #define UNITEXT_CANADIAN_SYLLABICS_RII L"\u1547" #define UNICODE_CANADIAN_SYLLABICS_RO 0x1548 #define UNITEXT_CANADIAN_SYLLABICS_RO L"\u1548" #define UNICODE_CANADIAN_SYLLABICS_ROO 0x1549 #define UNITEXT_CANADIAN_SYLLABICS_ROO L"\u1549" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LO 0x154a #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LO L"\u154a" #define UNICODE_CANADIAN_SYLLABICS_RA 0x154b #define UNITEXT_CANADIAN_SYLLABICS_RA L"\u154b" #define UNICODE_CANADIAN_SYLLABICS_RAA 0x154c #define UNITEXT_CANADIAN_SYLLABICS_RAA L"\u154c" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_LA 0x154d #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_LA L"\u154d" #define UNICODE_CANADIAN_SYLLABICS_RWAA 0x154e #define UNITEXT_CANADIAN_SYLLABICS_RWAA L"\u154e" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_RWAA 0x154f #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_RWAA L"\u154f" #define UNICODE_CANADIAN_SYLLABICS_R 0x1550 #define UNITEXT_CANADIAN_SYLLABICS_R L"\u1550" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_R 0x1551 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_R L"\u1551" #define UNICODE_CANADIAN_SYLLABICS_MEDIAL_R 0x1552 #define UNITEXT_CANADIAN_SYLLABICS_MEDIAL_R L"\u1552" #define UNICODE_CANADIAN_SYLLABICS_FE 0x1553 #define UNITEXT_CANADIAN_SYLLABICS_FE L"\u1553" #define UNICODE_CANADIAN_SYLLABICS_FAAI 0x1554 #define UNITEXT_CANADIAN_SYLLABICS_FAAI L"\u1554" #define UNICODE_CANADIAN_SYLLABICS_FI 0x1555 #define UNITEXT_CANADIAN_SYLLABICS_FI L"\u1555" #define UNICODE_CANADIAN_SYLLABICS_FII 0x1556 #define UNITEXT_CANADIAN_SYLLABICS_FII L"\u1556" #define UNICODE_CANADIAN_SYLLABICS_FO 0x1557 #define UNITEXT_CANADIAN_SYLLABICS_FO L"\u1557" #define UNICODE_CANADIAN_SYLLABICS_FOO 0x1558 #define UNITEXT_CANADIAN_SYLLABICS_FOO L"\u1558" #define UNICODE_CANADIAN_SYLLABICS_FA 0x1559 #define UNITEXT_CANADIAN_SYLLABICS_FA L"\u1559" #define UNICODE_CANADIAN_SYLLABICS_FAA 0x155a #define UNITEXT_CANADIAN_SYLLABICS_FAA L"\u155a" #define UNICODE_CANADIAN_SYLLABICS_FWAA 0x155b #define UNITEXT_CANADIAN_SYLLABICS_FWAA L"\u155b" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_FWAA 0x155c #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_FWAA L"\u155c" #define UNICODE_CANADIAN_SYLLABICS_F 0x155d #define UNITEXT_CANADIAN_SYLLABICS_F L"\u155d" #define UNICODE_CANADIAN_SYLLABICS_THE 0x155e #define UNITEXT_CANADIAN_SYLLABICS_THE L"\u155e" #define UNICODE_CANADIAN_SYLLABICS_N_CREE_THE 0x155f #define UNITEXT_CANADIAN_SYLLABICS_N_CREE_THE L"\u155f" #define UNICODE_CANADIAN_SYLLABICS_THI 0x1560 #define UNITEXT_CANADIAN_SYLLABICS_THI L"\u1560" #define UNICODE_CANADIAN_SYLLABICS_N_CREE_THI 0x1561 #define UNITEXT_CANADIAN_SYLLABICS_N_CREE_THI L"\u1561" #define UNICODE_CANADIAN_SYLLABICS_THII 0x1562 #define UNITEXT_CANADIAN_SYLLABICS_THII L"\u1562" #define UNICODE_CANADIAN_SYLLABICS_N_CREE_THII 0x1563 #define UNITEXT_CANADIAN_SYLLABICS_N_CREE_THII L"\u1563" #define UNICODE_CANADIAN_SYLLABICS_THO 0x1564 #define UNITEXT_CANADIAN_SYLLABICS_THO L"\u1564" #define UNICODE_CANADIAN_SYLLABICS_THOO 0x1565 #define UNITEXT_CANADIAN_SYLLABICS_THOO L"\u1565" #define UNICODE_CANADIAN_SYLLABICS_THA 0x1566 #define UNITEXT_CANADIAN_SYLLABICS_THA L"\u1566" #define UNICODE_CANADIAN_SYLLABICS_THAA 0x1567 #define UNITEXT_CANADIAN_SYLLABICS_THAA L"\u1567" #define UNICODE_CANADIAN_SYLLABICS_THWAA 0x1568 #define UNITEXT_CANADIAN_SYLLABICS_THWAA L"\u1568" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_THWAA 0x1569 #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_THWAA L"\u1569" #define UNICODE_CANADIAN_SYLLABICS_TH 0x156a #define UNITEXT_CANADIAN_SYLLABICS_TH L"\u156a" #define UNICODE_CANADIAN_SYLLABICS_TTHE 0x156b #define UNITEXT_CANADIAN_SYLLABICS_TTHE L"\u156b" #define UNICODE_CANADIAN_SYLLABICS_TTHI 0x156c #define UNITEXT_CANADIAN_SYLLABICS_TTHI L"\u156c" #define UNICODE_CANADIAN_SYLLABICS_TTHO 0x156d #define UNITEXT_CANADIAN_SYLLABICS_TTHO L"\u156d" #define UNICODE_CANADIAN_SYLLABICS_TTHA 0x156e #define UNITEXT_CANADIAN_SYLLABICS_TTHA L"\u156e" #define UNICODE_CANADIAN_SYLLABICS_TTH 0x156f #define UNITEXT_CANADIAN_SYLLABICS_TTH L"\u156f" #define UNICODE_CANADIAN_SYLLABICS_TYE 0x1570 #define UNITEXT_CANADIAN_SYLLABICS_TYE L"\u1570" #define UNICODE_CANADIAN_SYLLABICS_TYI 0x1571 #define UNITEXT_CANADIAN_SYLLABICS_TYI L"\u1571" #define UNICODE_CANADIAN_SYLLABICS_TYO 0x1572 #define UNITEXT_CANADIAN_SYLLABICS_TYO L"\u1572" #define UNICODE_CANADIAN_SYLLABICS_TYA 0x1573 #define UNITEXT_CANADIAN_SYLLABICS_TYA L"\u1573" #define UNICODE_CANADIAN_SYLLABICS_NUNAVIK_HE 0x1574 #define UNITEXT_CANADIAN_SYLLABICS_NUNAVIK_HE L"\u1574" #define UNICODE_CANADIAN_SYLLABICS_NUNAVIK_HI 0x1575 #define UNITEXT_CANADIAN_SYLLABICS_NUNAVIK_HI L"\u1575" #define UNICODE_CANADIAN_SYLLABICS_NUNAVIK_HII 0x1576 #define UNITEXT_CANADIAN_SYLLABICS_NUNAVIK_HII L"\u1576" #define UNICODE_CANADIAN_SYLLABICS_NUNAVIK_HO 0x1577 #define UNITEXT_CANADIAN_SYLLABICS_NUNAVIK_HO L"\u1577" #define UNICODE_CANADIAN_SYLLABICS_NUNAVIK_HOO 0x1578 #define UNITEXT_CANADIAN_SYLLABICS_NUNAVIK_HOO L"\u1578" #define UNICODE_CANADIAN_SYLLABICS_NUNAVIK_HA 0x1579 #define UNITEXT_CANADIAN_SYLLABICS_NUNAVIK_HA L"\u1579" #define UNICODE_CANADIAN_SYLLABICS_NUNAVIK_HAA 0x157a #define UNITEXT_CANADIAN_SYLLABICS_NUNAVIK_HAA L"\u157a" #define UNICODE_CANADIAN_SYLLABICS_NUNAVIK_H 0x157b #define UNITEXT_CANADIAN_SYLLABICS_NUNAVIK_H L"\u157b" #define UNICODE_CANADIAN_SYLLABICS_NUNAVUT_H 0x157c #define UNITEXT_CANADIAN_SYLLABICS_NUNAVUT_H L"\u157c" #define UNICODE_CANADIAN_SYLLABICS_HK 0x157d #define UNITEXT_CANADIAN_SYLLABICS_HK L"\u157d" #define UNICODE_CANADIAN_SYLLABICS_QAAI 0x157e #define UNITEXT_CANADIAN_SYLLABICS_QAAI L"\u157e" #define UNICODE_CANADIAN_SYLLABICS_QI 0x157f #define UNITEXT_CANADIAN_SYLLABICS_QI L"\u157f" #define UNICODE_CANADIAN_SYLLABICS_QII 0x1580 #define UNITEXT_CANADIAN_SYLLABICS_QII L"\u1580" #define UNICODE_CANADIAN_SYLLABICS_QO 0x1581 #define UNITEXT_CANADIAN_SYLLABICS_QO L"\u1581" #define UNICODE_CANADIAN_SYLLABICS_QOO 0x1582 #define UNITEXT_CANADIAN_SYLLABICS_QOO L"\u1582" #define UNICODE_CANADIAN_SYLLABICS_QA 0x1583 #define UNITEXT_CANADIAN_SYLLABICS_QA L"\u1583" #define UNICODE_CANADIAN_SYLLABICS_QAA 0x1584 #define UNITEXT_CANADIAN_SYLLABICS_QAA L"\u1584" #define UNICODE_CANADIAN_SYLLABICS_Q 0x1585 #define UNITEXT_CANADIAN_SYLLABICS_Q L"\u1585" #define UNICODE_CANADIAN_SYLLABICS_TLHE 0x1586 #define UNITEXT_CANADIAN_SYLLABICS_TLHE L"\u1586" #define UNICODE_CANADIAN_SYLLABICS_TLHI 0x1587 #define UNITEXT_CANADIAN_SYLLABICS_TLHI L"\u1587" #define UNICODE_CANADIAN_SYLLABICS_TLHO 0x1588 #define UNITEXT_CANADIAN_SYLLABICS_TLHO L"\u1588" #define UNICODE_CANADIAN_SYLLABICS_TLHA 0x1589 #define UNITEXT_CANADIAN_SYLLABICS_TLHA L"\u1589" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_RE 0x158a #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_RE L"\u158a" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_RI 0x158b #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_RI L"\u158b" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_RO 0x158c #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_RO L"\u158c" #define UNICODE_CANADIAN_SYLLABICS_WEST_CREE_RA 0x158d #define UNITEXT_CANADIAN_SYLLABICS_WEST_CREE_RA L"\u158d" #define UNICODE_CANADIAN_SYLLABICS_NGAAI 0x158e #define UNITEXT_CANADIAN_SYLLABICS_NGAAI L"\u158e" #define UNICODE_CANADIAN_SYLLABICS_NGI 0x158f #define UNITEXT_CANADIAN_SYLLABICS_NGI L"\u158f" #define UNICODE_CANADIAN_SYLLABICS_NGII 0x1590 #define UNITEXT_CANADIAN_SYLLABICS_NGII L"\u1590" #define UNICODE_CANADIAN_SYLLABICS_NGO 0x1591 #define UNITEXT_CANADIAN_SYLLABICS_NGO L"\u1591" #define UNICODE_CANADIAN_SYLLABICS_NGOO 0x1592 #define UNITEXT_CANADIAN_SYLLABICS_NGOO L"\u1592" #define UNICODE_CANADIAN_SYLLABICS_NGA 0x1593 #define UNITEXT_CANADIAN_SYLLABICS_NGA L"\u1593" #define UNICODE_CANADIAN_SYLLABICS_NGAA 0x1594 #define UNITEXT_CANADIAN_SYLLABICS_NGAA L"\u1594" #define UNICODE_CANADIAN_SYLLABICS_NG 0x1595 #define UNITEXT_CANADIAN_SYLLABICS_NG L"\u1595" #define UNICODE_CANADIAN_SYLLABICS_NNG 0x1596 #define UNITEXT_CANADIAN_SYLLABICS_NNG L"\u1596" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_SHE 0x1597 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_SHE L"\u1597" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_SHI 0x1598 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_SHI L"\u1598" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_SHO 0x1599 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_SHO L"\u1599" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_SHA 0x159a #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_SHA L"\u159a" #define UNICODE_CANADIAN_SYLLABICS_WOODS_CREE_THE 0x159b #define UNITEXT_CANADIAN_SYLLABICS_WOODS_CREE_THE L"\u159b" #define UNICODE_CANADIAN_SYLLABICS_WOODS_CREE_THI 0x159c #define UNITEXT_CANADIAN_SYLLABICS_WOODS_CREE_THI L"\u159c" #define UNICODE_CANADIAN_SYLLABICS_WOODS_CREE_THO 0x159d #define UNITEXT_CANADIAN_SYLLABICS_WOODS_CREE_THO L"\u159d" #define UNICODE_CANADIAN_SYLLABICS_WOODS_CREE_THA 0x159e #define UNITEXT_CANADIAN_SYLLABICS_WOODS_CREE_THA L"\u159e" #define UNICODE_CANADIAN_SYLLABICS_WOODS_CREE_TH 0x159f #define UNITEXT_CANADIAN_SYLLABICS_WOODS_CREE_TH L"\u159f" #define UNICODE_CANADIAN_SYLLABICS_LHI 0x15a0 #define UNITEXT_CANADIAN_SYLLABICS_LHI L"\u15a0" #define UNICODE_CANADIAN_SYLLABICS_LHII 0x15a1 #define UNITEXT_CANADIAN_SYLLABICS_LHII L"\u15a1" #define UNICODE_CANADIAN_SYLLABICS_LHO 0x15a2 #define UNITEXT_CANADIAN_SYLLABICS_LHO L"\u15a2" #define UNICODE_CANADIAN_SYLLABICS_LHOO 0x15a3 #define UNITEXT_CANADIAN_SYLLABICS_LHOO L"\u15a3" #define UNICODE_CANADIAN_SYLLABICS_LHA 0x15a4 #define UNITEXT_CANADIAN_SYLLABICS_LHA L"\u15a4" #define UNICODE_CANADIAN_SYLLABICS_LHAA 0x15a5 #define UNITEXT_CANADIAN_SYLLABICS_LHAA L"\u15a5" #define UNICODE_CANADIAN_SYLLABICS_LH 0x15a6 #define UNITEXT_CANADIAN_SYLLABICS_LH L"\u15a6" #define UNICODE_CANADIAN_SYLLABICS_TH_CREE_THE 0x15a7 #define UNITEXT_CANADIAN_SYLLABICS_TH_CREE_THE L"\u15a7" #define UNICODE_CANADIAN_SYLLABICS_TH_CREE_THI 0x15a8 #define UNITEXT_CANADIAN_SYLLABICS_TH_CREE_THI L"\u15a8" #define UNICODE_CANADIAN_SYLLABICS_TH_CREE_THII 0x15a9 #define UNITEXT_CANADIAN_SYLLABICS_TH_CREE_THII L"\u15a9" #define UNICODE_CANADIAN_SYLLABICS_TH_CREE_THO 0x15aa #define UNITEXT_CANADIAN_SYLLABICS_TH_CREE_THO L"\u15aa" #define UNICODE_CANADIAN_SYLLABICS_TH_CREE_THOO 0x15ab #define UNITEXT_CANADIAN_SYLLABICS_TH_CREE_THOO L"\u15ab" #define UNICODE_CANADIAN_SYLLABICS_TH_CREE_THA 0x15ac #define UNITEXT_CANADIAN_SYLLABICS_TH_CREE_THA L"\u15ac" #define UNICODE_CANADIAN_SYLLABICS_TH_CREE_THAA 0x15ad #define UNITEXT_CANADIAN_SYLLABICS_TH_CREE_THAA L"\u15ad" #define UNICODE_CANADIAN_SYLLABICS_TH_CREE_TH 0x15ae #define UNITEXT_CANADIAN_SYLLABICS_TH_CREE_TH L"\u15ae" #define UNICODE_CANADIAN_SYLLABICS_AIVILIK_B 0x15af #define UNITEXT_CANADIAN_SYLLABICS_AIVILIK_B L"\u15af" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_E 0x15b0 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_E L"\u15b0" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_I 0x15b1 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_I L"\u15b1" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_O 0x15b2 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_O L"\u15b2" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_A 0x15b3 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_A L"\u15b3" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_WE 0x15b4 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_WE L"\u15b4" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_WI 0x15b5 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_WI L"\u15b5" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_WO 0x15b6 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_WO L"\u15b6" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_WA 0x15b7 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_WA L"\u15b7" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_NE 0x15b8 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_NE L"\u15b8" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_NI 0x15b9 #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_NI L"\u15b9" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_NO 0x15ba #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_NO L"\u15ba" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_NA 0x15bb #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_NA L"\u15bb" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_KE 0x15bc #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_KE L"\u15bc" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_KI 0x15bd #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_KI L"\u15bd" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_KO 0x15be #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_KO L"\u15be" #define UNICODE_CANADIAN_SYLLABICS_BLACKFOOT_KA 0x15bf #define UNITEXT_CANADIAN_SYLLABICS_BLACKFOOT_KA L"\u15bf" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_HE 0x15c0 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_HE L"\u15c0" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_HI 0x15c1 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_HI L"\u15c1" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_HO 0x15c2 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_HO L"\u15c2" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_HA 0x15c3 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_HA L"\u15c3" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GHU 0x15c4 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GHU L"\u15c4" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GHO 0x15c5 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GHO L"\u15c5" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GHE 0x15c6 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GHE L"\u15c6" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GHEE 0x15c7 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GHEE L"\u15c7" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GHI 0x15c8 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GHI L"\u15c8" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GHA 0x15c9 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GHA L"\u15c9" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_RU 0x15ca #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_RU L"\u15ca" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_RO 0x15cb #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_RO L"\u15cb" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_RE 0x15cc #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_RE L"\u15cc" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_REE 0x15cd #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_REE L"\u15cd" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_RI 0x15ce #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_RI L"\u15ce" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_RA 0x15cf #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_RA L"\u15cf" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_WU 0x15d0 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_WU L"\u15d0" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_WO 0x15d1 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_WO L"\u15d1" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_WE 0x15d2 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_WE L"\u15d2" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_WEE 0x15d3 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_WEE L"\u15d3" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_WI 0x15d4 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_WI L"\u15d4" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_WA 0x15d5 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_WA L"\u15d5" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_HWU 0x15d6 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_HWU L"\u15d6" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_HWO 0x15d7 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_HWO L"\u15d7" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_HWE 0x15d8 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_HWE L"\u15d8" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_HWEE 0x15d9 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_HWEE L"\u15d9" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_HWI 0x15da #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_HWI L"\u15da" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_HWA 0x15db #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_HWA L"\u15db" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_THU 0x15dc #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_THU L"\u15dc" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_THO 0x15dd #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_THO L"\u15dd" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_THE 0x15de #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_THE L"\u15de" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_THEE 0x15df #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_THEE L"\u15df" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_THI 0x15e0 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_THI L"\u15e0" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_THA 0x15e1 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_THA L"\u15e1" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTU 0x15e2 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTU L"\u15e2" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTO 0x15e3 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTO L"\u15e3" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTE 0x15e4 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTE L"\u15e4" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTEE 0x15e5 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTEE L"\u15e5" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTI 0x15e6 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTI L"\u15e6" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTA 0x15e7 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTA L"\u15e7" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_PU 0x15e8 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_PU L"\u15e8" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_PO 0x15e9 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_PO L"\u15e9" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_PE 0x15ea #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_PE L"\u15ea" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_PEE 0x15eb #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_PEE L"\u15eb" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_PI 0x15ec #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_PI L"\u15ec" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_PA 0x15ed #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_PA L"\u15ed" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_P 0x15ee #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_P L"\u15ee" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GU 0x15ef #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GU L"\u15ef" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GO 0x15f0 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GO L"\u15f0" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GE 0x15f1 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GE L"\u15f1" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GEE 0x15f2 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GEE L"\u15f2" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GI 0x15f3 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GI L"\u15f3" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_GA 0x15f4 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_GA L"\u15f4" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KHU 0x15f5 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KHU L"\u15f5" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KHO 0x15f6 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KHO L"\u15f6" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KHE 0x15f7 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KHE L"\u15f7" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KHEE 0x15f8 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KHEE L"\u15f8" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KHI 0x15f9 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KHI L"\u15f9" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KHA 0x15fa #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KHA L"\u15fa" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KKU 0x15fb #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KKU L"\u15fb" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KKO 0x15fc #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KKO L"\u15fc" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KKE 0x15fd #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KKE L"\u15fd" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KKEE 0x15fe #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KKEE L"\u15fe" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KKI 0x15ff #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KKI L"\u15ff" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KKA 0x1600 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KKA L"\u1600" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_KK 0x1601 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_KK L"\u1601" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_NU 0x1602 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_NU L"\u1602" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_NO 0x1603 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_NO L"\u1603" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_NE 0x1604 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_NE L"\u1604" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_NEE 0x1605 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_NEE L"\u1605" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_NI 0x1606 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_NI L"\u1606" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_NA 0x1607 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_NA L"\u1607" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_MU 0x1608 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_MU L"\u1608" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_MO 0x1609 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_MO L"\u1609" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_ME 0x160a #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_ME L"\u160a" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_MEE 0x160b #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_MEE L"\u160b" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_MI 0x160c #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_MI L"\u160c" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_MA 0x160d #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_MA L"\u160d" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_YU 0x160e #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_YU L"\u160e" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_YO 0x160f #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_YO L"\u160f" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_YE 0x1610 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_YE L"\u1610" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_YEE 0x1611 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_YEE L"\u1611" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_YI 0x1612 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_YI L"\u1612" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_YA 0x1613 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_YA L"\u1613" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JU 0x1614 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JU L"\u1614" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_JU 0x1615 #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_JU L"\u1615" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JO 0x1616 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JO L"\u1616" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JE 0x1617 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JE L"\u1617" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JEE 0x1618 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JEE L"\u1618" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JI 0x1619 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JI L"\u1619" #define UNICODE_CANADIAN_SYLLABICS_SAYISI_JI 0x161a #define UNITEXT_CANADIAN_SYLLABICS_SAYISI_JI L"\u161a" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JA 0x161b #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JA L"\u161b" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JJU 0x161c #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JJU L"\u161c" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JJO 0x161d #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JJO L"\u161d" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JJE 0x161e #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JJE L"\u161e" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JJEE 0x161f #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JJEE L"\u161f" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JJI 0x1620 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JJI L"\u1620" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_JJA 0x1621 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_JJA L"\u1621" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LU 0x1622 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LU L"\u1622" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LO 0x1623 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LO L"\u1623" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LE 0x1624 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LE L"\u1624" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LEE 0x1625 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LEE L"\u1625" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LI 0x1626 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LI L"\u1626" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LA 0x1627 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LA L"\u1627" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DLU 0x1628 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DLU L"\u1628" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DLO 0x1629 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DLO L"\u1629" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DLE 0x162a #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DLE L"\u162a" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DLEE 0x162b #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DLEE L"\u162b" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DLI 0x162c #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DLI L"\u162c" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DLA 0x162d #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DLA L"\u162d" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LHU 0x162e #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LHU L"\u162e" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LHO 0x162f #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LHO L"\u162f" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LHE 0x1630 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LHE L"\u1630" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LHEE 0x1631 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LHEE L"\u1631" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LHI 0x1632 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LHI L"\u1632" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_LHA 0x1633 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_LHA L"\u1633" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLHU 0x1634 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLHU L"\u1634" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLHO 0x1635 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLHO L"\u1635" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLHE 0x1636 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLHE L"\u1636" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLHEE 0x1637 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLHEE L"\u1637" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLHI 0x1638 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLHI L"\u1638" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLHA 0x1639 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLHA L"\u1639" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLU 0x163a #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLU L"\u163a" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLO 0x163b #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLO L"\u163b" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLE 0x163c #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLE L"\u163c" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLEE 0x163d #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLEE L"\u163d" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLI 0x163e #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLI L"\u163e" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TLA 0x163f #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TLA L"\u163f" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_ZU 0x1640 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_ZU L"\u1640" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_ZO 0x1641 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_ZO L"\u1641" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_ZE 0x1642 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_ZE L"\u1642" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_ZEE 0x1643 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_ZEE L"\u1643" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_ZI 0x1644 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_ZI L"\u1644" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_ZA 0x1645 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_ZA L"\u1645" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_Z 0x1646 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_Z L"\u1646" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_INITIAL_Z 0x1647 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_INITIAL_Z L"\u1647" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DZU 0x1648 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DZU L"\u1648" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DZO 0x1649 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DZO L"\u1649" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DZE 0x164a #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DZE L"\u164a" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DZEE 0x164b #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DZEE L"\u164b" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DZI 0x164c #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DZI L"\u164c" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_DZA 0x164d #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_DZA L"\u164d" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SU 0x164e #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SU L"\u164e" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SO 0x164f #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SO L"\u164f" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SE 0x1650 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SE L"\u1650" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SEE 0x1651 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SEE L"\u1651" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SI 0x1652 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SI L"\u1652" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SA 0x1653 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SA L"\u1653" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SHU 0x1654 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SHU L"\u1654" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SHO 0x1655 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SHO L"\u1655" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SHE 0x1656 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SHE L"\u1656" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SHEE 0x1657 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SHEE L"\u1657" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SHI 0x1658 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SHI L"\u1658" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SHA 0x1659 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SHA L"\u1659" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_SH 0x165a #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_SH L"\u165a" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TSU 0x165b #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TSU L"\u165b" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TSO 0x165c #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TSO L"\u165c" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TSE 0x165d #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TSE L"\u165d" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TSEE 0x165e #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TSEE L"\u165e" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TSI 0x165f #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TSI L"\u165f" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TSA 0x1660 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TSA L"\u1660" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_CHU 0x1661 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_CHU L"\u1661" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_CHO 0x1662 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_CHO L"\u1662" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_CHE 0x1663 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_CHE L"\u1663" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_CHEE 0x1664 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_CHEE L"\u1664" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_CHI 0x1665 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_CHI L"\u1665" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_CHA 0x1666 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_CHA L"\u1666" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTSU 0x1667 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTSU L"\u1667" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTSO 0x1668 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTSO L"\u1668" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTSE 0x1669 #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTSE L"\u1669" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTSEE 0x166a #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTSEE L"\u166a" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTSI 0x166b #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTSI L"\u166b" #define UNICODE_CANADIAN_SYLLABICS_CARRIER_TTSA 0x166c #define UNITEXT_CANADIAN_SYLLABICS_CARRIER_TTSA L"\u166c" #define UNICODE_CANADIAN_SYLLABICS_CHI_SIGN 0x166d #define UNITEXT_CANADIAN_SYLLABICS_CHI_SIGN L"\u166d" #define UNICODE_CANADIAN_SYLLABICS_FULL_STOP 0x166e #define UNITEXT_CANADIAN_SYLLABICS_FULL_STOP L"\u166e" #define UNICODE_CANADIAN_SYLLABICS_QAI 0x166f #define UNITEXT_CANADIAN_SYLLABICS_QAI L"\u166f" #define UNICODE_CANADIAN_SYLLABICS_NGAI 0x1670 #define UNITEXT_CANADIAN_SYLLABICS_NGAI L"\u1670" #define UNICODE_CANADIAN_SYLLABICS_NNGI 0x1671 #define UNITEXT_CANADIAN_SYLLABICS_NNGI L"\u1671" #define UNICODE_CANADIAN_SYLLABICS_NNGII 0x1672 #define UNITEXT_CANADIAN_SYLLABICS_NNGII L"\u1672" #define UNICODE_CANADIAN_SYLLABICS_NNGO 0x1673 #define UNITEXT_CANADIAN_SYLLABICS_NNGO L"\u1673" #define UNICODE_CANADIAN_SYLLABICS_NNGOO 0x1674 #define UNITEXT_CANADIAN_SYLLABICS_NNGOO L"\u1674" #define UNICODE_CANADIAN_SYLLABICS_NNGA 0x1675 #define UNITEXT_CANADIAN_SYLLABICS_NNGA L"\u1675" #define UNICODE_CANADIAN_SYLLABICS_NNGAA 0x1676 #define UNITEXT_CANADIAN_SYLLABICS_NNGAA L"\u1676" #define UNICODE_OGHAM_SPACE_MARK 0x1680 #define UNITEXT_OGHAM_SPACE_MARK L"\u1680" #define UNICODE_OGHAM_LETTER_BEITH 0x1681 #define UNITEXT_OGHAM_LETTER_BEITH L"\u1681" #define UNICODE_OGHAM_LETTER_LUIS 0x1682 #define UNITEXT_OGHAM_LETTER_LUIS L"\u1682" #define UNICODE_OGHAM_LETTER_FEARN 0x1683 #define UNITEXT_OGHAM_LETTER_FEARN L"\u1683" #define UNICODE_OGHAM_LETTER_SAIL 0x1684 #define UNITEXT_OGHAM_LETTER_SAIL L"\u1684" #define UNICODE_OGHAM_LETTER_NION 0x1685 #define UNITEXT_OGHAM_LETTER_NION L"\u1685" #define UNICODE_OGHAM_LETTER_UATH 0x1686 #define UNITEXT_OGHAM_LETTER_UATH L"\u1686" #define UNICODE_OGHAM_LETTER_DAIR 0x1687 #define UNITEXT_OGHAM_LETTER_DAIR L"\u1687" #define UNICODE_OGHAM_LETTER_TINNE 0x1688 #define UNITEXT_OGHAM_LETTER_TINNE L"\u1688" #define UNICODE_OGHAM_LETTER_COLL 0x1689 #define UNITEXT_OGHAM_LETTER_COLL L"\u1689" #define UNICODE_OGHAM_LETTER_CEIRT 0x168a #define UNITEXT_OGHAM_LETTER_CEIRT L"\u168a" #define UNICODE_OGHAM_LETTER_MUIN 0x168b #define UNITEXT_OGHAM_LETTER_MUIN L"\u168b" #define UNICODE_OGHAM_LETTER_GORT 0x168c #define UNITEXT_OGHAM_LETTER_GORT L"\u168c" #define UNICODE_OGHAM_LETTER_NGEADAL 0x168d #define UNITEXT_OGHAM_LETTER_NGEADAL L"\u168d" #define UNICODE_OGHAM_LETTER_STRAIF 0x168e #define UNITEXT_OGHAM_LETTER_STRAIF L"\u168e" #define UNICODE_OGHAM_LETTER_RUIS 0x168f #define UNITEXT_OGHAM_LETTER_RUIS L"\u168f" #define UNICODE_OGHAM_LETTER_AILM 0x1690 #define UNITEXT_OGHAM_LETTER_AILM L"\u1690" #define UNICODE_OGHAM_LETTER_ONN 0x1691 #define UNITEXT_OGHAM_LETTER_ONN L"\u1691" #define UNICODE_OGHAM_LETTER_UR 0x1692 #define UNITEXT_OGHAM_LETTER_UR L"\u1692" #define UNICODE_OGHAM_LETTER_EADHADH 0x1693 #define UNITEXT_OGHAM_LETTER_EADHADH L"\u1693" #define UNICODE_OGHAM_LETTER_IODHADH 0x1694 #define UNITEXT_OGHAM_LETTER_IODHADH L"\u1694" #define UNICODE_OGHAM_LETTER_EABHADH 0x1695 #define UNITEXT_OGHAM_LETTER_EABHADH L"\u1695" #define UNICODE_OGHAM_LETTER_OR 0x1696 #define UNITEXT_OGHAM_LETTER_OR L"\u1696" #define UNICODE_OGHAM_LETTER_UILLEANN 0x1697 #define UNITEXT_OGHAM_LETTER_UILLEANN L"\u1697" #define UNICODE_OGHAM_LETTER_IFIN 0x1698 #define UNITEXT_OGHAM_LETTER_IFIN L"\u1698" #define UNICODE_OGHAM_LETTER_EAMHANCHOLL 0x1699 #define UNITEXT_OGHAM_LETTER_EAMHANCHOLL L"\u1699" #define UNICODE_OGHAM_LETTER_PEITH 0x169a #define UNITEXT_OGHAM_LETTER_PEITH L"\u169a" #define UNICODE_OGHAM_FEATHER_MARK 0x169b #define UNITEXT_OGHAM_FEATHER_MARK L"\u169b" #define UNICODE_OGHAM_REVERSED_FEATHER_MARK 0x169c #define UNITEXT_OGHAM_REVERSED_FEATHER_MARK L"\u169c" #define UNICODE_RUNIC_LETTER_FEHU_FEOH_FE_F 0x16a0 #define UNITEXT_RUNIC_LETTER_FEHU_FEOH_FE_F L"\u16a0" #define UNICODE_RUNIC_LETTER_V 0x16a1 #define UNITEXT_RUNIC_LETTER_V L"\u16a1" #define UNICODE_RUNIC_LETTER_URUZ_UR_U 0x16a2 #define UNITEXT_RUNIC_LETTER_URUZ_UR_U L"\u16a2" #define UNICODE_RUNIC_LETTER_YR 0x16a3 #define UNITEXT_RUNIC_LETTER_YR L"\u16a3" #define UNICODE_RUNIC_LETTER_Y 0x16a4 #define UNITEXT_RUNIC_LETTER_Y L"\u16a4" #define UNICODE_RUNIC_LETTER_W 0x16a5 #define UNITEXT_RUNIC_LETTER_W L"\u16a5" #define UNICODE_RUNIC_LETTER_THURISAZ_THURS_THORN 0x16a6 #define UNITEXT_RUNIC_LETTER_THURISAZ_THURS_THORN L"\u16a6" #define UNICODE_RUNIC_LETTER_ETH 0x16a7 #define UNITEXT_RUNIC_LETTER_ETH L"\u16a7" #define UNICODE_RUNIC_LETTER_ANSUZ_A 0x16a8 #define UNITEXT_RUNIC_LETTER_ANSUZ_A L"\u16a8" #define UNICODE_RUNIC_LETTER_OS_O 0x16a9 #define UNITEXT_RUNIC_LETTER_OS_O L"\u16a9" #define UNICODE_RUNIC_LETTER_AC_A 0x16aa #define UNITEXT_RUNIC_LETTER_AC_A L"\u16aa" #define UNICODE_RUNIC_LETTER_AESC 0x16ab #define UNITEXT_RUNIC_LETTER_AESC L"\u16ab" #define UNICODE_RUNIC_LETTER_LONG_BRANCH_OSS_O 0x16ac #define UNITEXT_RUNIC_LETTER_LONG_BRANCH_OSS_O L"\u16ac" #define UNICODE_RUNIC_LETTER_SHORT_TWIG_OSS_O 0x16ad #define UNITEXT_RUNIC_LETTER_SHORT_TWIG_OSS_O L"\u16ad" #define UNICODE_RUNIC_LETTER_O 0x16ae #define UNITEXT_RUNIC_LETTER_O L"\u16ae" #define UNICODE_RUNIC_LETTER_OE 0x16af #define UNITEXT_RUNIC_LETTER_OE L"\u16af" #define UNICODE_RUNIC_LETTER_ON 0x16b0 #define UNITEXT_RUNIC_LETTER_ON L"\u16b0" #define UNICODE_RUNIC_LETTER_RAIDO_RAD_REID_R 0x16b1 #define UNITEXT_RUNIC_LETTER_RAIDO_RAD_REID_R L"\u16b1" #define UNICODE_RUNIC_LETTER_KAUNA 0x16b2 #define UNITEXT_RUNIC_LETTER_KAUNA L"\u16b2" #define UNICODE_RUNIC_LETTER_CEN 0x16b3 #define UNITEXT_RUNIC_LETTER_CEN L"\u16b3" #define UNICODE_RUNIC_LETTER_KAUN_K 0x16b4 #define UNITEXT_RUNIC_LETTER_KAUN_K L"\u16b4" #define UNICODE_RUNIC_LETTER_G 0x16b5 #define UNITEXT_RUNIC_LETTER_G L"\u16b5" #define UNICODE_RUNIC_LETTER_ENG 0x16b6 #define UNITEXT_RUNIC_LETTER_ENG L"\u16b6" #define UNICODE_RUNIC_LETTER_GEBO_GYFU_G 0x16b7 #define UNITEXT_RUNIC_LETTER_GEBO_GYFU_G L"\u16b7" #define UNICODE_RUNIC_LETTER_GAR 0x16b8 #define UNITEXT_RUNIC_LETTER_GAR L"\u16b8" #define UNICODE_RUNIC_LETTER_WUNJO_WYNN_W 0x16b9 #define UNITEXT_RUNIC_LETTER_WUNJO_WYNN_W L"\u16b9" #define UNICODE_RUNIC_LETTER_HAGLAZ_H 0x16ba #define UNITEXT_RUNIC_LETTER_HAGLAZ_H L"\u16ba" #define UNICODE_RUNIC_LETTER_HAEGL_H 0x16bb #define UNITEXT_RUNIC_LETTER_HAEGL_H L"\u16bb" #define UNICODE_RUNIC_LETTER_LONG_BRANCH_HAGALL_H 0x16bc #define UNITEXT_RUNIC_LETTER_LONG_BRANCH_HAGALL_H L"\u16bc" #define UNICODE_RUNIC_LETTER_SHORT_TWIG_HAGALL_H 0x16bd #define UNITEXT_RUNIC_LETTER_SHORT_TWIG_HAGALL_H L"\u16bd" #define UNICODE_RUNIC_LETTER_NAUDIZ_NYD_NAUD_N 0x16be #define UNITEXT_RUNIC_LETTER_NAUDIZ_NYD_NAUD_N L"\u16be" #define UNICODE_RUNIC_LETTER_SHORT_TWIG_NAUD_N 0x16bf #define UNITEXT_RUNIC_LETTER_SHORT_TWIG_NAUD_N L"\u16bf" #define UNICODE_RUNIC_LETTER_DOTTED_N 0x16c0 #define UNITEXT_RUNIC_LETTER_DOTTED_N L"\u16c0" #define UNICODE_RUNIC_LETTER_ISAZ_IS_ISS_I 0x16c1 #define UNITEXT_RUNIC_LETTER_ISAZ_IS_ISS_I L"\u16c1" #define UNICODE_RUNIC_LETTER_E 0x16c2 #define UNITEXT_RUNIC_LETTER_E L"\u16c2" #define UNICODE_RUNIC_LETTER_JERAN_J 0x16c3 #define UNITEXT_RUNIC_LETTER_JERAN_J L"\u16c3" #define UNICODE_RUNIC_LETTER_GER 0x16c4 #define UNITEXT_RUNIC_LETTER_GER L"\u16c4" #define UNICODE_RUNIC_LETTER_LONG_BRANCH_AR_AE 0x16c5 #define UNITEXT_RUNIC_LETTER_LONG_BRANCH_AR_AE L"\u16c5" #define UNICODE_RUNIC_LETTER_SHORT_TWIG_AR_A 0x16c6 #define UNITEXT_RUNIC_LETTER_SHORT_TWIG_AR_A L"\u16c6" #define UNICODE_RUNIC_LETTER_IWAZ_EOH 0x16c7 #define UNITEXT_RUNIC_LETTER_IWAZ_EOH L"\u16c7" #define UNICODE_RUNIC_LETTER_PERTHO_PEORTH_P 0x16c8 #define UNITEXT_RUNIC_LETTER_PERTHO_PEORTH_P L"\u16c8" #define UNICODE_RUNIC_LETTER_ALGIZ_EOLHX 0x16c9 #define UNITEXT_RUNIC_LETTER_ALGIZ_EOLHX L"\u16c9" #define UNICODE_RUNIC_LETTER_SOWILO_S 0x16ca #define UNITEXT_RUNIC_LETTER_SOWILO_S L"\u16ca" #define UNICODE_RUNIC_LETTER_SIGEL_LONG_BRANCH_SOL_S 0x16cb #define UNITEXT_RUNIC_LETTER_SIGEL_LONG_BRANCH_SOL_S L"\u16cb" #define UNICODE_RUNIC_LETTER_SHORT_TWIG_SOL_S 0x16cc #define UNITEXT_RUNIC_LETTER_SHORT_TWIG_SOL_S L"\u16cc" #define UNICODE_RUNIC_LETTER_C 0x16cd #define UNITEXT_RUNIC_LETTER_C L"\u16cd" #define UNICODE_RUNIC_LETTER_Z 0x16ce #define UNITEXT_RUNIC_LETTER_Z L"\u16ce" #define UNICODE_RUNIC_LETTER_TIWAZ_TIR_TYR_T 0x16cf #define UNITEXT_RUNIC_LETTER_TIWAZ_TIR_TYR_T L"\u16cf" #define UNICODE_RUNIC_LETTER_SHORT_TWIG_TYR_T 0x16d0 #define UNITEXT_RUNIC_LETTER_SHORT_TWIG_TYR_T L"\u16d0" #define UNICODE_RUNIC_LETTER_D 0x16d1 #define UNITEXT_RUNIC_LETTER_D L"\u16d1" #define UNICODE_RUNIC_LETTER_BERKANAN_BEORC_BJARKAN_B 0x16d2 #define UNITEXT_RUNIC_LETTER_BERKANAN_BEORC_BJARKAN_B L"\u16d2" #define UNICODE_RUNIC_LETTER_SHORT_TWIG_BJARKAN_B 0x16d3 #define UNITEXT_RUNIC_LETTER_SHORT_TWIG_BJARKAN_B L"\u16d3" #define UNICODE_RUNIC_LETTER_DOTTED_P 0x16d4 #define UNITEXT_RUNIC_LETTER_DOTTED_P L"\u16d4" #define UNICODE_RUNIC_LETTER_OPEN_P 0x16d5 #define UNITEXT_RUNIC_LETTER_OPEN_P L"\u16d5" #define UNICODE_RUNIC_LETTER_EHWAZ_EH_E 0x16d6 #define UNITEXT_RUNIC_LETTER_EHWAZ_EH_E L"\u16d6" #define UNICODE_RUNIC_LETTER_MANNAZ_MAN_M 0x16d7 #define UNITEXT_RUNIC_LETTER_MANNAZ_MAN_M L"\u16d7" #define UNICODE_RUNIC_LETTER_LONG_BRANCH_MADR_M 0x16d8 #define UNITEXT_RUNIC_LETTER_LONG_BRANCH_MADR_M L"\u16d8" #define UNICODE_RUNIC_LETTER_SHORT_TWIG_MADR_M 0x16d9 #define UNITEXT_RUNIC_LETTER_SHORT_TWIG_MADR_M L"\u16d9" #define UNICODE_RUNIC_LETTER_LAUKAZ_LAGU_LOGR_L 0x16da #define UNITEXT_RUNIC_LETTER_LAUKAZ_LAGU_LOGR_L L"\u16da" #define UNICODE_RUNIC_LETTER_DOTTED_L 0x16db #define UNITEXT_RUNIC_LETTER_DOTTED_L L"\u16db" #define UNICODE_RUNIC_LETTER_INGWAZ 0x16dc #define UNITEXT_RUNIC_LETTER_INGWAZ L"\u16dc" #define UNICODE_RUNIC_LETTER_ING 0x16dd #define UNITEXT_RUNIC_LETTER_ING L"\u16dd" #define UNICODE_RUNIC_LETTER_DAGAZ_DAEG_D 0x16de #define UNITEXT_RUNIC_LETTER_DAGAZ_DAEG_D L"\u16de" #define UNICODE_RUNIC_LETTER_OTHALAN_ETHEL_O 0x16df #define UNITEXT_RUNIC_LETTER_OTHALAN_ETHEL_O L"\u16df" #define UNICODE_RUNIC_LETTER_EAR 0x16e0 #define UNITEXT_RUNIC_LETTER_EAR L"\u16e0" #define UNICODE_RUNIC_LETTER_IOR 0x16e1 #define UNITEXT_RUNIC_LETTER_IOR L"\u16e1" #define UNICODE_RUNIC_LETTER_CWEORTH 0x16e2 #define UNITEXT_RUNIC_LETTER_CWEORTH L"\u16e2" #define UNICODE_RUNIC_LETTER_CALC 0x16e3 #define UNITEXT_RUNIC_LETTER_CALC L"\u16e3" #define UNICODE_RUNIC_LETTER_CEALC 0x16e4 #define UNITEXT_RUNIC_LETTER_CEALC L"\u16e4" #define UNICODE_RUNIC_LETTER_STAN 0x16e5 #define UNITEXT_RUNIC_LETTER_STAN L"\u16e5" #define UNICODE_RUNIC_LETTER_LONG_BRANCH_YR 0x16e6 #define UNITEXT_RUNIC_LETTER_LONG_BRANCH_YR L"\u16e6" #define UNICODE_RUNIC_LETTER_SHORT_TWIG_YR 0x16e7 #define UNITEXT_RUNIC_LETTER_SHORT_TWIG_YR L"\u16e7" #define UNICODE_RUNIC_LETTER_ICELANDIC_YR 0x16e8 #define UNITEXT_RUNIC_LETTER_ICELANDIC_YR L"\u16e8" #define UNICODE_RUNIC_LETTER_Q 0x16e9 #define UNITEXT_RUNIC_LETTER_Q L"\u16e9" #define UNICODE_RUNIC_LETTER_X 0x16ea #define UNITEXT_RUNIC_LETTER_X L"\u16ea" #define UNICODE_RUNIC_SINGLE_PUNCTUATION 0x16eb #define UNITEXT_RUNIC_SINGLE_PUNCTUATION L"\u16eb" #define UNICODE_RUNIC_MULTIPLE_PUNCTUATION 0x16ec #define UNITEXT_RUNIC_MULTIPLE_PUNCTUATION L"\u16ec" #define UNICODE_RUNIC_CROSS_PUNCTUATION 0x16ed #define UNITEXT_RUNIC_CROSS_PUNCTUATION L"\u16ed" #define UNICODE_RUNIC_ARLAUG_SYMBOL 0x16ee #define UNITEXT_RUNIC_ARLAUG_SYMBOL L"\u16ee" #define UNICODE_RUNIC_TVIMADUR_SYMBOL 0x16ef #define UNITEXT_RUNIC_TVIMADUR_SYMBOL L"\u16ef" #define UNICODE_RUNIC_BELGTHOR_SYMBOL 0x16f0 #define UNITEXT_RUNIC_BELGTHOR_SYMBOL L"\u16f0" #define UNICODE_TAGALOG_LETTER_A 0x1700 #define UNITEXT_TAGALOG_LETTER_A L"\u1700" #define UNICODE_TAGALOG_LETTER_I 0x1701 #define UNITEXT_TAGALOG_LETTER_I L"\u1701" #define UNICODE_TAGALOG_LETTER_U 0x1702 #define UNITEXT_TAGALOG_LETTER_U L"\u1702" #define UNICODE_TAGALOG_LETTER_KA 0x1703 #define UNITEXT_TAGALOG_LETTER_KA L"\u1703" #define UNICODE_TAGALOG_LETTER_GA 0x1704 #define UNITEXT_TAGALOG_LETTER_GA L"\u1704" #define UNICODE_TAGALOG_LETTER_NGA 0x1705 #define UNITEXT_TAGALOG_LETTER_NGA L"\u1705" #define UNICODE_TAGALOG_LETTER_TA 0x1706 #define UNITEXT_TAGALOG_LETTER_TA L"\u1706" #define UNICODE_TAGALOG_LETTER_DA 0x1707 #define UNITEXT_TAGALOG_LETTER_DA L"\u1707" #define UNICODE_TAGALOG_LETTER_NA 0x1708 #define UNITEXT_TAGALOG_LETTER_NA L"\u1708" #define UNICODE_TAGALOG_LETTER_PA 0x1709 #define UNITEXT_TAGALOG_LETTER_PA L"\u1709" #define UNICODE_TAGALOG_LETTER_BA 0x170a #define UNITEXT_TAGALOG_LETTER_BA L"\u170a" #define UNICODE_TAGALOG_LETTER_MA 0x170b #define UNITEXT_TAGALOG_LETTER_MA L"\u170b" #define UNICODE_TAGALOG_LETTER_YA 0x170c #define UNITEXT_TAGALOG_LETTER_YA L"\u170c" #define UNICODE_TAGALOG_LETTER_LA 0x170e #define UNITEXT_TAGALOG_LETTER_LA L"\u170e" #define UNICODE_TAGALOG_LETTER_WA 0x170f #define UNITEXT_TAGALOG_LETTER_WA L"\u170f" #define UNICODE_TAGALOG_LETTER_SA 0x1710 #define UNITEXT_TAGALOG_LETTER_SA L"\u1710" #define UNICODE_TAGALOG_LETTER_HA 0x1711 #define UNITEXT_TAGALOG_LETTER_HA L"\u1711" #define UNICODE_TAGALOG_VOWEL_SIGN_I 0x1712 #define UNITEXT_TAGALOG_VOWEL_SIGN_I L"\u1712" #define UNICODE_TAGALOG_VOWEL_SIGN_U 0x1713 #define UNITEXT_TAGALOG_VOWEL_SIGN_U L"\u1713" #define UNICODE_TAGALOG_SIGN_VIRAMA 0x1714 #define UNITEXT_TAGALOG_SIGN_VIRAMA L"\u1714" #define UNICODE_HANUNOO_LETTER_A 0x1720 #define UNITEXT_HANUNOO_LETTER_A L"\u1720" #define UNICODE_HANUNOO_LETTER_I 0x1721 #define UNITEXT_HANUNOO_LETTER_I L"\u1721" #define UNICODE_HANUNOO_LETTER_U 0x1722 #define UNITEXT_HANUNOO_LETTER_U L"\u1722" #define UNICODE_HANUNOO_LETTER_KA 0x1723 #define UNITEXT_HANUNOO_LETTER_KA L"\u1723" #define UNICODE_HANUNOO_LETTER_GA 0x1724 #define UNITEXT_HANUNOO_LETTER_GA L"\u1724" #define UNICODE_HANUNOO_LETTER_NGA 0x1725 #define UNITEXT_HANUNOO_LETTER_NGA L"\u1725" #define UNICODE_HANUNOO_LETTER_TA 0x1726 #define UNITEXT_HANUNOO_LETTER_TA L"\u1726" #define UNICODE_HANUNOO_LETTER_DA 0x1727 #define UNITEXT_HANUNOO_LETTER_DA L"\u1727" #define UNICODE_HANUNOO_LETTER_NA 0x1728 #define UNITEXT_HANUNOO_LETTER_NA L"\u1728" #define UNICODE_HANUNOO_LETTER_PA 0x1729 #define UNITEXT_HANUNOO_LETTER_PA L"\u1729" #define UNICODE_HANUNOO_LETTER_BA 0x172a #define UNITEXT_HANUNOO_LETTER_BA L"\u172a" #define UNICODE_HANUNOO_LETTER_MA 0x172b #define UNITEXT_HANUNOO_LETTER_MA L"\u172b" #define UNICODE_HANUNOO_LETTER_YA 0x172c #define UNITEXT_HANUNOO_LETTER_YA L"\u172c" #define UNICODE_HANUNOO_LETTER_RA 0x172d #define UNITEXT_HANUNOO_LETTER_RA L"\u172d" #define UNICODE_HANUNOO_LETTER_LA 0x172e #define UNITEXT_HANUNOO_LETTER_LA L"\u172e" #define UNICODE_HANUNOO_LETTER_WA 0x172f #define UNITEXT_HANUNOO_LETTER_WA L"\u172f" #define UNICODE_HANUNOO_LETTER_SA 0x1730 #define UNITEXT_HANUNOO_LETTER_SA L"\u1730" #define UNICODE_HANUNOO_LETTER_HA 0x1731 #define UNITEXT_HANUNOO_LETTER_HA L"\u1731" #define UNICODE_HANUNOO_VOWEL_SIGN_I 0x1732 #define UNITEXT_HANUNOO_VOWEL_SIGN_I L"\u1732" #define UNICODE_HANUNOO_VOWEL_SIGN_U 0x1733 #define UNITEXT_HANUNOO_VOWEL_SIGN_U L"\u1733" #define UNICODE_HANUNOO_SIGN_PAMUDPOD 0x1734 #define UNITEXT_HANUNOO_SIGN_PAMUDPOD L"\u1734" #define UNICODE_PHILIPPINE_SINGLE_PUNCTUATION 0x1735 #define UNITEXT_PHILIPPINE_SINGLE_PUNCTUATION L"\u1735" #define UNICODE_PHILIPPINE_DOUBLE_PUNCTUATION 0x1736 #define UNITEXT_PHILIPPINE_DOUBLE_PUNCTUATION L"\u1736" #define UNICODE_BUHID_LETTER_A 0x1740 #define UNITEXT_BUHID_LETTER_A L"\u1740" #define UNICODE_BUHID_LETTER_I 0x1741 #define UNITEXT_BUHID_LETTER_I L"\u1741" #define UNICODE_BUHID_LETTER_U 0x1742 #define UNITEXT_BUHID_LETTER_U L"\u1742" #define UNICODE_BUHID_LETTER_KA 0x1743 #define UNITEXT_BUHID_LETTER_KA L"\u1743" #define UNICODE_BUHID_LETTER_GA 0x1744 #define UNITEXT_BUHID_LETTER_GA L"\u1744" #define UNICODE_BUHID_LETTER_NGA 0x1745 #define UNITEXT_BUHID_LETTER_NGA L"\u1745" #define UNICODE_BUHID_LETTER_TA 0x1746 #define UNITEXT_BUHID_LETTER_TA L"\u1746" #define UNICODE_BUHID_LETTER_DA 0x1747 #define UNITEXT_BUHID_LETTER_DA L"\u1747" #define UNICODE_BUHID_LETTER_NA 0x1748 #define UNITEXT_BUHID_LETTER_NA L"\u1748" #define UNICODE_BUHID_LETTER_PA 0x1749 #define UNITEXT_BUHID_LETTER_PA L"\u1749" #define UNICODE_BUHID_LETTER_BA 0x174a #define UNITEXT_BUHID_LETTER_BA L"\u174a" #define UNICODE_BUHID_LETTER_MA 0x174b #define UNITEXT_BUHID_LETTER_MA L"\u174b" #define UNICODE_BUHID_LETTER_YA 0x174c #define UNITEXT_BUHID_LETTER_YA L"\u174c" #define UNICODE_BUHID_LETTER_RA 0x174d #define UNITEXT_BUHID_LETTER_RA L"\u174d" #define UNICODE_BUHID_LETTER_LA 0x174e #define UNITEXT_BUHID_LETTER_LA L"\u174e" #define UNICODE_BUHID_LETTER_WA 0x174f #define UNITEXT_BUHID_LETTER_WA L"\u174f" #define UNICODE_BUHID_LETTER_SA 0x1750 #define UNITEXT_BUHID_LETTER_SA L"\u1750" #define UNICODE_BUHID_LETTER_HA 0x1751 #define UNITEXT_BUHID_LETTER_HA L"\u1751" #define UNICODE_BUHID_VOWEL_SIGN_I 0x1752 #define UNITEXT_BUHID_VOWEL_SIGN_I L"\u1752" #define UNICODE_BUHID_VOWEL_SIGN_U 0x1753 #define UNITEXT_BUHID_VOWEL_SIGN_U L"\u1753" #define UNICODE_TAGBANWA_LETTER_A 0x1760 #define UNITEXT_TAGBANWA_LETTER_A L"\u1760" #define UNICODE_TAGBANWA_LETTER_I 0x1761 #define UNITEXT_TAGBANWA_LETTER_I L"\u1761" #define UNICODE_TAGBANWA_LETTER_U 0x1762 #define UNITEXT_TAGBANWA_LETTER_U L"\u1762" #define UNICODE_TAGBANWA_LETTER_KA 0x1763 #define UNITEXT_TAGBANWA_LETTER_KA L"\u1763" #define UNICODE_TAGBANWA_LETTER_GA 0x1764 #define UNITEXT_TAGBANWA_LETTER_GA L"\u1764" #define UNICODE_TAGBANWA_LETTER_NGA 0x1765 #define UNITEXT_TAGBANWA_LETTER_NGA L"\u1765" #define UNICODE_TAGBANWA_LETTER_TA 0x1766 #define UNITEXT_TAGBANWA_LETTER_TA L"\u1766" #define UNICODE_TAGBANWA_LETTER_DA 0x1767 #define UNITEXT_TAGBANWA_LETTER_DA L"\u1767" #define UNICODE_TAGBANWA_LETTER_NA 0x1768 #define UNITEXT_TAGBANWA_LETTER_NA L"\u1768" #define UNICODE_TAGBANWA_LETTER_PA 0x1769 #define UNITEXT_TAGBANWA_LETTER_PA L"\u1769" #define UNICODE_TAGBANWA_LETTER_BA 0x176a #define UNITEXT_TAGBANWA_LETTER_BA L"\u176a" #define UNICODE_TAGBANWA_LETTER_MA 0x176b #define UNITEXT_TAGBANWA_LETTER_MA L"\u176b" #define UNICODE_TAGBANWA_LETTER_YA 0x176c #define UNITEXT_TAGBANWA_LETTER_YA L"\u176c" #define UNICODE_TAGBANWA_LETTER_LA 0x176e #define UNITEXT_TAGBANWA_LETTER_LA L"\u176e" #define UNICODE_TAGBANWA_LETTER_WA 0x176f #define UNITEXT_TAGBANWA_LETTER_WA L"\u176f" #define UNICODE_TAGBANWA_LETTER_SA 0x1770 #define UNITEXT_TAGBANWA_LETTER_SA L"\u1770" #define UNICODE_TAGBANWA_VOWEL_SIGN_I 0x1772 #define UNITEXT_TAGBANWA_VOWEL_SIGN_I L"\u1772" #define UNICODE_TAGBANWA_VOWEL_SIGN_U 0x1773 #define UNITEXT_TAGBANWA_VOWEL_SIGN_U L"\u1773" #define UNICODE_KHMER_LETTER_KA 0x1780 #define UNITEXT_KHMER_LETTER_KA L"\u1780" #define UNICODE_KHMER_LETTER_KHA 0x1781 #define UNITEXT_KHMER_LETTER_KHA L"\u1781" #define UNICODE_KHMER_LETTER_KO 0x1782 #define UNITEXT_KHMER_LETTER_KO L"\u1782" #define UNICODE_KHMER_LETTER_KHO 0x1783 #define UNITEXT_KHMER_LETTER_KHO L"\u1783" #define UNICODE_KHMER_LETTER_NGO 0x1784 #define UNITEXT_KHMER_LETTER_NGO L"\u1784" #define UNICODE_KHMER_LETTER_CA 0x1785 #define UNITEXT_KHMER_LETTER_CA L"\u1785" #define UNICODE_KHMER_LETTER_CHA 0x1786 #define UNITEXT_KHMER_LETTER_CHA L"\u1786" #define UNICODE_KHMER_LETTER_CO 0x1787 #define UNITEXT_KHMER_LETTER_CO L"\u1787" #define UNICODE_KHMER_LETTER_CHO 0x1788 #define UNITEXT_KHMER_LETTER_CHO L"\u1788" #define UNICODE_KHMER_LETTER_NYO 0x1789 #define UNITEXT_KHMER_LETTER_NYO L"\u1789" #define UNICODE_KHMER_LETTER_DA 0x178a #define UNITEXT_KHMER_LETTER_DA L"\u178a" #define UNICODE_KHMER_LETTER_TTHA 0x178b #define UNITEXT_KHMER_LETTER_TTHA L"\u178b" #define UNICODE_KHMER_LETTER_DO 0x178c #define UNITEXT_KHMER_LETTER_DO L"\u178c" #define UNICODE_KHMER_LETTER_TTHO 0x178d #define UNITEXT_KHMER_LETTER_TTHO L"\u178d" #define UNICODE_KHMER_LETTER_NNO 0x178e #define UNITEXT_KHMER_LETTER_NNO L"\u178e" #define UNICODE_KHMER_LETTER_TA 0x178f #define UNITEXT_KHMER_LETTER_TA L"\u178f" #define UNICODE_KHMER_LETTER_THA 0x1790 #define UNITEXT_KHMER_LETTER_THA L"\u1790" #define UNICODE_KHMER_LETTER_TO 0x1791 #define UNITEXT_KHMER_LETTER_TO L"\u1791" #define UNICODE_KHMER_LETTER_THO 0x1792 #define UNITEXT_KHMER_LETTER_THO L"\u1792" #define UNICODE_KHMER_LETTER_NO 0x1793 #define UNITEXT_KHMER_LETTER_NO L"\u1793" #define UNICODE_KHMER_LETTER_BA 0x1794 #define UNITEXT_KHMER_LETTER_BA L"\u1794" #define UNICODE_KHMER_LETTER_PHA 0x1795 #define UNITEXT_KHMER_LETTER_PHA L"\u1795" #define UNICODE_KHMER_LETTER_PO 0x1796 #define UNITEXT_KHMER_LETTER_PO L"\u1796" #define UNICODE_KHMER_LETTER_PHO 0x1797 #define UNITEXT_KHMER_LETTER_PHO L"\u1797" #define UNICODE_KHMER_LETTER_MO 0x1798 #define UNITEXT_KHMER_LETTER_MO L"\u1798" #define UNICODE_KHMER_LETTER_YO 0x1799 #define UNITEXT_KHMER_LETTER_YO L"\u1799" #define UNICODE_KHMER_LETTER_RO 0x179a #define UNITEXT_KHMER_LETTER_RO L"\u179a" #define UNICODE_KHMER_LETTER_LO 0x179b #define UNITEXT_KHMER_LETTER_LO L"\u179b" #define UNICODE_KHMER_LETTER_VO 0x179c #define UNITEXT_KHMER_LETTER_VO L"\u179c" #define UNICODE_KHMER_LETTER_SHA 0x179d #define UNITEXT_KHMER_LETTER_SHA L"\u179d" #define UNICODE_KHMER_LETTER_SSO 0x179e #define UNITEXT_KHMER_LETTER_SSO L"\u179e" #define UNICODE_KHMER_LETTER_SA 0x179f #define UNITEXT_KHMER_LETTER_SA L"\u179f" #define UNICODE_KHMER_LETTER_HA 0x17a0 #define UNITEXT_KHMER_LETTER_HA L"\u17a0" #define UNICODE_KHMER_LETTER_LA 0x17a1 #define UNITEXT_KHMER_LETTER_LA L"\u17a1" #define UNICODE_KHMER_LETTER_QA 0x17a2 #define UNITEXT_KHMER_LETTER_QA L"\u17a2" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QAQ 0x17a3 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QAQ L"\u17a3" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QAA 0x17a4 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QAA L"\u17a4" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QI 0x17a5 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QI L"\u17a5" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QII 0x17a6 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QII L"\u17a6" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QU 0x17a7 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QU L"\u17a7" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QUK 0x17a8 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QUK L"\u17a8" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QUU 0x17a9 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QUU L"\u17a9" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QUUV 0x17aa #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QUUV L"\u17aa" #define UNICODE_KHMER_INDEPENDENT_VOWEL_RY 0x17ab #define UNITEXT_KHMER_INDEPENDENT_VOWEL_RY L"\u17ab" #define UNICODE_KHMER_INDEPENDENT_VOWEL_RYY 0x17ac #define UNITEXT_KHMER_INDEPENDENT_VOWEL_RYY L"\u17ac" #define UNICODE_KHMER_INDEPENDENT_VOWEL_LY 0x17ad #define UNITEXT_KHMER_INDEPENDENT_VOWEL_LY L"\u17ad" #define UNICODE_KHMER_INDEPENDENT_VOWEL_LYY 0x17ae #define UNITEXT_KHMER_INDEPENDENT_VOWEL_LYY L"\u17ae" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QE 0x17af #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QE L"\u17af" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QAI 0x17b0 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QAI L"\u17b0" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QOO_TYPE_ONE 0x17b1 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QOO_TYPE_ONE L"\u17b1" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QOO_TYPE_TWO 0x17b2 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QOO_TYPE_TWO L"\u17b2" #define UNICODE_KHMER_INDEPENDENT_VOWEL_QAU 0x17b3 #define UNITEXT_KHMER_INDEPENDENT_VOWEL_QAU L"\u17b3" #define UNICODE_KHMER_VOWEL_INHERENT_AQ 0x17b4 #define UNITEXT_KHMER_VOWEL_INHERENT_AQ L"\u17b4" #define UNICODE_KHMER_VOWEL_INHERENT_AA 0x17b5 #define UNITEXT_KHMER_VOWEL_INHERENT_AA L"\u17b5" #define UNICODE_KHMER_VOWEL_SIGN_AA 0x17b6 #define UNITEXT_KHMER_VOWEL_SIGN_AA L"\u17b6" #define UNICODE_KHMER_VOWEL_SIGN_I 0x17b7 #define UNITEXT_KHMER_VOWEL_SIGN_I L"\u17b7" #define UNICODE_KHMER_VOWEL_SIGN_II 0x17b8 #define UNITEXT_KHMER_VOWEL_SIGN_II L"\u17b8" #define UNICODE_KHMER_VOWEL_SIGN_Y 0x17b9 #define UNITEXT_KHMER_VOWEL_SIGN_Y L"\u17b9" #define UNICODE_KHMER_VOWEL_SIGN_YY 0x17ba #define UNITEXT_KHMER_VOWEL_SIGN_YY L"\u17ba" #define UNICODE_KHMER_VOWEL_SIGN_U 0x17bb #define UNITEXT_KHMER_VOWEL_SIGN_U L"\u17bb" #define UNICODE_KHMER_VOWEL_SIGN_UU 0x17bc #define UNITEXT_KHMER_VOWEL_SIGN_UU L"\u17bc" #define UNICODE_KHMER_VOWEL_SIGN_UA 0x17bd #define UNITEXT_KHMER_VOWEL_SIGN_UA L"\u17bd" #define UNICODE_KHMER_VOWEL_SIGN_OE 0x17be #define UNITEXT_KHMER_VOWEL_SIGN_OE L"\u17be" #define UNICODE_KHMER_VOWEL_SIGN_YA 0x17bf #define UNITEXT_KHMER_VOWEL_SIGN_YA L"\u17bf" #define UNICODE_KHMER_VOWEL_SIGN_IE 0x17c0 #define UNITEXT_KHMER_VOWEL_SIGN_IE L"\u17c0" #define UNICODE_KHMER_VOWEL_SIGN_E 0x17c1 #define UNITEXT_KHMER_VOWEL_SIGN_E L"\u17c1" #define UNICODE_KHMER_VOWEL_SIGN_AE 0x17c2 #define UNITEXT_KHMER_VOWEL_SIGN_AE L"\u17c2" #define UNICODE_KHMER_VOWEL_SIGN_AI 0x17c3 #define UNITEXT_KHMER_VOWEL_SIGN_AI L"\u17c3" #define UNICODE_KHMER_VOWEL_SIGN_OO 0x17c4 #define UNITEXT_KHMER_VOWEL_SIGN_OO L"\u17c4" #define UNICODE_KHMER_VOWEL_SIGN_AU 0x17c5 #define UNITEXT_KHMER_VOWEL_SIGN_AU L"\u17c5" #define UNICODE_KHMER_SIGN_NIKAHIT 0x17c6 #define UNITEXT_KHMER_SIGN_NIKAHIT L"\u17c6" #define UNICODE_KHMER_SIGN_REAHMUK 0x17c7 #define UNITEXT_KHMER_SIGN_REAHMUK L"\u17c7" #define UNICODE_KHMER_SIGN_YUUKALEAPINTU 0x17c8 #define UNITEXT_KHMER_SIGN_YUUKALEAPINTU L"\u17c8" #define UNICODE_KHMER_SIGN_MUUSIKATOAN 0x17c9 #define UNITEXT_KHMER_SIGN_MUUSIKATOAN L"\u17c9" #define UNICODE_KHMER_SIGN_TRIISAP 0x17ca #define UNITEXT_KHMER_SIGN_TRIISAP L"\u17ca" #define UNICODE_KHMER_SIGN_BANTOC 0x17cb #define UNITEXT_KHMER_SIGN_BANTOC L"\u17cb" #define UNICODE_KHMER_SIGN_ROBAT 0x17cc #define UNITEXT_KHMER_SIGN_ROBAT L"\u17cc" #define UNICODE_KHMER_SIGN_TOANDAKHIAT 0x17cd #define UNITEXT_KHMER_SIGN_TOANDAKHIAT L"\u17cd" #define UNICODE_KHMER_SIGN_KAKABAT 0x17ce #define UNITEXT_KHMER_SIGN_KAKABAT L"\u17ce" #define UNICODE_KHMER_SIGN_AHSDA 0x17cf #define UNITEXT_KHMER_SIGN_AHSDA L"\u17cf" #define UNICODE_KHMER_SIGN_SAMYOK_SANNYA 0x17d0 #define UNITEXT_KHMER_SIGN_SAMYOK_SANNYA L"\u17d0" #define UNICODE_KHMER_SIGN_VIRIAM 0x17d1 #define UNITEXT_KHMER_SIGN_VIRIAM L"\u17d1" #define UNICODE_KHMER_SIGN_COENG 0x17d2 #define UNITEXT_KHMER_SIGN_COENG L"\u17d2" #define UNICODE_KHMER_SIGN_BATHAMASAT 0x17d3 #define UNITEXT_KHMER_SIGN_BATHAMASAT L"\u17d3" #define UNICODE_KHMER_SIGN_KHAN 0x17d4 #define UNITEXT_KHMER_SIGN_KHAN L"\u17d4" #define UNICODE_KHMER_SIGN_BARIYOOSAN 0x17d5 #define UNITEXT_KHMER_SIGN_BARIYOOSAN L"\u17d5" #define UNICODE_KHMER_SIGN_CAMNUC_PII_KUUH 0x17d6 #define UNITEXT_KHMER_SIGN_CAMNUC_PII_KUUH L"\u17d6" #define UNICODE_KHMER_SIGN_LEK_TOO 0x17d7 #define UNITEXT_KHMER_SIGN_LEK_TOO L"\u17d7" #define UNICODE_KHMER_SIGN_BEYYAL 0x17d8 #define UNITEXT_KHMER_SIGN_BEYYAL L"\u17d8" #define UNICODE_KHMER_SIGN_PHNAEK_MUAN 0x17d9 #define UNITEXT_KHMER_SIGN_PHNAEK_MUAN L"\u17d9" #define UNICODE_KHMER_SIGN_KOOMUUT 0x17da #define UNITEXT_KHMER_SIGN_KOOMUUT L"\u17da" #define UNICODE_KHMER_CURRENCY_SYMBOL_RIEL 0x17db #define UNITEXT_KHMER_CURRENCY_SYMBOL_RIEL L"\u17db" #define UNICODE_KHMER_SIGN_AVAKRAHASANYA 0x17dc #define UNITEXT_KHMER_SIGN_AVAKRAHASANYA L"\u17dc" #define UNICODE_KHMER_SIGN_ATTHACAN 0x17dd #define UNITEXT_KHMER_SIGN_ATTHACAN L"\u17dd" #define UNICODE_KHMER_DIGIT_ZERO 0x17e0 #define UNITEXT_KHMER_DIGIT_ZERO L"\u17e0" #define UNICODE_KHMER_DIGIT_ONE 0x17e1 #define UNITEXT_KHMER_DIGIT_ONE L"\u17e1" #define UNICODE_KHMER_DIGIT_TWO 0x17e2 #define UNITEXT_KHMER_DIGIT_TWO L"\u17e2" #define UNICODE_KHMER_DIGIT_THREE 0x17e3 #define UNITEXT_KHMER_DIGIT_THREE L"\u17e3" #define UNICODE_KHMER_DIGIT_FOUR 0x17e4 #define UNITEXT_KHMER_DIGIT_FOUR L"\u17e4" #define UNICODE_KHMER_DIGIT_FIVE 0x17e5 #define UNITEXT_KHMER_DIGIT_FIVE L"\u17e5" #define UNICODE_KHMER_DIGIT_SIX 0x17e6 #define UNITEXT_KHMER_DIGIT_SIX L"\u17e6" #define UNICODE_KHMER_DIGIT_SEVEN 0x17e7 #define UNITEXT_KHMER_DIGIT_SEVEN L"\u17e7" #define UNICODE_KHMER_DIGIT_EIGHT 0x17e8 #define UNITEXT_KHMER_DIGIT_EIGHT L"\u17e8" #define UNICODE_KHMER_DIGIT_NINE 0x17e9 #define UNITEXT_KHMER_DIGIT_NINE L"\u17e9" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_SON 0x17f0 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_SON L"\u17f0" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_MUOY 0x17f1 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_MUOY L"\u17f1" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_PII 0x17f2 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_PII L"\u17f2" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_BEI 0x17f3 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_BEI L"\u17f3" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_BUON 0x17f4 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_BUON L"\u17f4" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_PRAM 0x17f5 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_PRAM L"\u17f5" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_PRAM_MUOY 0x17f6 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_PRAM_MUOY L"\u17f6" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_PRAM_PII 0x17f7 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_PRAM_PII L"\u17f7" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_PRAM_BEI 0x17f8 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_PRAM_BEI L"\u17f8" #define UNICODE_KHMER_SYMBOL_LEK_ATTAK_PRAM_BUON 0x17f9 #define UNITEXT_KHMER_SYMBOL_LEK_ATTAK_PRAM_BUON L"\u17f9" #define UNICODE_MONGOLIAN_BIRGA 0x1800 #define UNITEXT_MONGOLIAN_BIRGA L"\u1800" #define UNICODE_MONGOLIAN_ELLIPSIS 0x1801 #define UNITEXT_MONGOLIAN_ELLIPSIS L"\u1801" #define UNICODE_MONGOLIAN_COMMA 0x1802 #define UNITEXT_MONGOLIAN_COMMA L"\u1802" #define UNICODE_MONGOLIAN_FULL_STOP 0x1803 #define UNITEXT_MONGOLIAN_FULL_STOP L"\u1803" #define UNICODE_MONGOLIAN_COLON 0x1804 #define UNITEXT_MONGOLIAN_COLON L"\u1804" #define UNICODE_MONGOLIAN_FOUR_DOTS 0x1805 #define UNITEXT_MONGOLIAN_FOUR_DOTS L"\u1805" #define UNICODE_MONGOLIAN_TODO_SOFT_HYPHEN 0x1806 #define UNITEXT_MONGOLIAN_TODO_SOFT_HYPHEN L"\u1806" #define UNICODE_MONGOLIAN_SIBE_SYLLABLE_BOUNDARY_MARKER 0x1807 #define UNITEXT_MONGOLIAN_SIBE_SYLLABLE_BOUNDARY_MARKER L"\u1807" #define UNICODE_MONGOLIAN_MANCHU_COMMA 0x1808 #define UNITEXT_MONGOLIAN_MANCHU_COMMA L"\u1808" #define UNICODE_MONGOLIAN_MANCHU_FULL_STOP 0x1809 #define UNITEXT_MONGOLIAN_MANCHU_FULL_STOP L"\u1809" #define UNICODE_MONGOLIAN_NIRUGU 0x180a #define UNITEXT_MONGOLIAN_NIRUGU L"\u180a" #define UNICODE_MONGOLIAN_FREE_VARIATION_SELECTOR_ONE 0x180b #define UNITEXT_MONGOLIAN_FREE_VARIATION_SELECTOR_ONE L"\u180b" #define UNICODE_MONGOLIAN_FREE_VARIATION_SELECTOR_TWO 0x180c #define UNITEXT_MONGOLIAN_FREE_VARIATION_SELECTOR_TWO L"\u180c" #define UNICODE_MONGOLIAN_FREE_VARIATION_SELECTOR_THREE 0x180d #define UNITEXT_MONGOLIAN_FREE_VARIATION_SELECTOR_THREE L"\u180d" #define UNICODE_MONGOLIAN_VOWEL_SEPARATOR 0x180e #define UNITEXT_MONGOLIAN_VOWEL_SEPARATOR L"\u180e" #define UNICODE_MONGOLIAN_DIGIT_ZERO 0x1810 #define UNITEXT_MONGOLIAN_DIGIT_ZERO L"\u1810" #define UNICODE_MONGOLIAN_DIGIT_ONE 0x1811 #define UNITEXT_MONGOLIAN_DIGIT_ONE L"\u1811" #define UNICODE_MONGOLIAN_DIGIT_TWO 0x1812 #define UNITEXT_MONGOLIAN_DIGIT_TWO L"\u1812" #define UNICODE_MONGOLIAN_DIGIT_THREE 0x1813 #define UNITEXT_MONGOLIAN_DIGIT_THREE L"\u1813" #define UNICODE_MONGOLIAN_DIGIT_FOUR 0x1814 #define UNITEXT_MONGOLIAN_DIGIT_FOUR L"\u1814" #define UNICODE_MONGOLIAN_DIGIT_FIVE 0x1815 #define UNITEXT_MONGOLIAN_DIGIT_FIVE L"\u1815" #define UNICODE_MONGOLIAN_DIGIT_SIX 0x1816 #define UNITEXT_MONGOLIAN_DIGIT_SIX L"\u1816" #define UNICODE_MONGOLIAN_DIGIT_SEVEN 0x1817 #define UNITEXT_MONGOLIAN_DIGIT_SEVEN L"\u1817" #define UNICODE_MONGOLIAN_DIGIT_EIGHT 0x1818 #define UNITEXT_MONGOLIAN_DIGIT_EIGHT L"\u1818" #define UNICODE_MONGOLIAN_DIGIT_NINE 0x1819 #define UNITEXT_MONGOLIAN_DIGIT_NINE L"\u1819" #define UNICODE_MONGOLIAN_LETTER_A 0x1820 #define UNITEXT_MONGOLIAN_LETTER_A L"\u1820" #define UNICODE_MONGOLIAN_LETTER_E 0x1821 #define UNITEXT_MONGOLIAN_LETTER_E L"\u1821" #define UNICODE_MONGOLIAN_LETTER_I 0x1822 #define UNITEXT_MONGOLIAN_LETTER_I L"\u1822" #define UNICODE_MONGOLIAN_LETTER_O 0x1823 #define UNITEXT_MONGOLIAN_LETTER_O L"\u1823" #define UNICODE_MONGOLIAN_LETTER_U 0x1824 #define UNITEXT_MONGOLIAN_LETTER_U L"\u1824" #define UNICODE_MONGOLIAN_LETTER_OE 0x1825 #define UNITEXT_MONGOLIAN_LETTER_OE L"\u1825" #define UNICODE_MONGOLIAN_LETTER_UE 0x1826 #define UNITEXT_MONGOLIAN_LETTER_UE L"\u1826" #define UNICODE_MONGOLIAN_LETTER_EE 0x1827 #define UNITEXT_MONGOLIAN_LETTER_EE L"\u1827" #define UNICODE_MONGOLIAN_LETTER_NA 0x1828 #define UNITEXT_MONGOLIAN_LETTER_NA L"\u1828" #define UNICODE_MONGOLIAN_LETTER_ANG 0x1829 #define UNITEXT_MONGOLIAN_LETTER_ANG L"\u1829" #define UNICODE_MONGOLIAN_LETTER_BA 0x182a #define UNITEXT_MONGOLIAN_LETTER_BA L"\u182a" #define UNICODE_MONGOLIAN_LETTER_PA 0x182b #define UNITEXT_MONGOLIAN_LETTER_PA L"\u182b" #define UNICODE_MONGOLIAN_LETTER_QA 0x182c #define UNITEXT_MONGOLIAN_LETTER_QA L"\u182c" #define UNICODE_MONGOLIAN_LETTER_GA 0x182d #define UNITEXT_MONGOLIAN_LETTER_GA L"\u182d" #define UNICODE_MONGOLIAN_LETTER_MA 0x182e #define UNITEXT_MONGOLIAN_LETTER_MA L"\u182e" #define UNICODE_MONGOLIAN_LETTER_LA 0x182f #define UNITEXT_MONGOLIAN_LETTER_LA L"\u182f" #define UNICODE_MONGOLIAN_LETTER_SA 0x1830 #define UNITEXT_MONGOLIAN_LETTER_SA L"\u1830" #define UNICODE_MONGOLIAN_LETTER_SHA 0x1831 #define UNITEXT_MONGOLIAN_LETTER_SHA L"\u1831" #define UNICODE_MONGOLIAN_LETTER_TA 0x1832 #define UNITEXT_MONGOLIAN_LETTER_TA L"\u1832" #define UNICODE_MONGOLIAN_LETTER_DA 0x1833 #define UNITEXT_MONGOLIAN_LETTER_DA L"\u1833" #define UNICODE_MONGOLIAN_LETTER_CHA 0x1834 #define UNITEXT_MONGOLIAN_LETTER_CHA L"\u1834" #define UNICODE_MONGOLIAN_LETTER_JA 0x1835 #define UNITEXT_MONGOLIAN_LETTER_JA L"\u1835" #define UNICODE_MONGOLIAN_LETTER_YA 0x1836 #define UNITEXT_MONGOLIAN_LETTER_YA L"\u1836" #define UNICODE_MONGOLIAN_LETTER_RA 0x1837 #define UNITEXT_MONGOLIAN_LETTER_RA L"\u1837" #define UNICODE_MONGOLIAN_LETTER_WA 0x1838 #define UNITEXT_MONGOLIAN_LETTER_WA L"\u1838" #define UNICODE_MONGOLIAN_LETTER_FA 0x1839 #define UNITEXT_MONGOLIAN_LETTER_FA L"\u1839" #define UNICODE_MONGOLIAN_LETTER_KA 0x183a #define UNITEXT_MONGOLIAN_LETTER_KA L"\u183a" #define UNICODE_MONGOLIAN_LETTER_KHA 0x183b #define UNITEXT_MONGOLIAN_LETTER_KHA L"\u183b" #define UNICODE_MONGOLIAN_LETTER_TSA 0x183c #define UNITEXT_MONGOLIAN_LETTER_TSA L"\u183c" #define UNICODE_MONGOLIAN_LETTER_ZA 0x183d #define UNITEXT_MONGOLIAN_LETTER_ZA L"\u183d" #define UNICODE_MONGOLIAN_LETTER_HAA 0x183e #define UNITEXT_MONGOLIAN_LETTER_HAA L"\u183e" #define UNICODE_MONGOLIAN_LETTER_ZRA 0x183f #define UNITEXT_MONGOLIAN_LETTER_ZRA L"\u183f" #define UNICODE_MONGOLIAN_LETTER_LHA 0x1840 #define UNITEXT_MONGOLIAN_LETTER_LHA L"\u1840" #define UNICODE_MONGOLIAN_LETTER_ZHI 0x1841 #define UNITEXT_MONGOLIAN_LETTER_ZHI L"\u1841" #define UNICODE_MONGOLIAN_LETTER_CHI 0x1842 #define UNITEXT_MONGOLIAN_LETTER_CHI L"\u1842" #define UNICODE_MONGOLIAN_LETTER_TODO_LONG_VOWEL_SIGN 0x1843 #define UNITEXT_MONGOLIAN_LETTER_TODO_LONG_VOWEL_SIGN L"\u1843" #define UNICODE_MONGOLIAN_LETTER_TODO_E 0x1844 #define UNITEXT_MONGOLIAN_LETTER_TODO_E L"\u1844" #define UNICODE_MONGOLIAN_LETTER_TODO_I 0x1845 #define UNITEXT_MONGOLIAN_LETTER_TODO_I L"\u1845" #define UNICODE_MONGOLIAN_LETTER_TODO_O 0x1846 #define UNITEXT_MONGOLIAN_LETTER_TODO_O L"\u1846" #define UNICODE_MONGOLIAN_LETTER_TODO_U 0x1847 #define UNITEXT_MONGOLIAN_LETTER_TODO_U L"\u1847" #define UNICODE_MONGOLIAN_LETTER_TODO_OE 0x1848 #define UNITEXT_MONGOLIAN_LETTER_TODO_OE L"\u1848" #define UNICODE_MONGOLIAN_LETTER_TODO_UE 0x1849 #define UNITEXT_MONGOLIAN_LETTER_TODO_UE L"\u1849" #define UNICODE_MONGOLIAN_LETTER_TODO_ANG 0x184a #define UNITEXT_MONGOLIAN_LETTER_TODO_ANG L"\u184a" #define UNICODE_MONGOLIAN_LETTER_TODO_BA 0x184b #define UNITEXT_MONGOLIAN_LETTER_TODO_BA L"\u184b" #define UNICODE_MONGOLIAN_LETTER_TODO_PA 0x184c #define UNITEXT_MONGOLIAN_LETTER_TODO_PA L"\u184c" #define UNICODE_MONGOLIAN_LETTER_TODO_QA 0x184d #define UNITEXT_MONGOLIAN_LETTER_TODO_QA L"\u184d" #define UNICODE_MONGOLIAN_LETTER_TODO_GA 0x184e #define UNITEXT_MONGOLIAN_LETTER_TODO_GA L"\u184e" #define UNICODE_MONGOLIAN_LETTER_TODO_MA 0x184f #define UNITEXT_MONGOLIAN_LETTER_TODO_MA L"\u184f" #define UNICODE_MONGOLIAN_LETTER_TODO_TA 0x1850 #define UNITEXT_MONGOLIAN_LETTER_TODO_TA L"\u1850" #define UNICODE_MONGOLIAN_LETTER_TODO_DA 0x1851 #define UNITEXT_MONGOLIAN_LETTER_TODO_DA L"\u1851" #define UNICODE_MONGOLIAN_LETTER_TODO_CHA 0x1852 #define UNITEXT_MONGOLIAN_LETTER_TODO_CHA L"\u1852" #define UNICODE_MONGOLIAN_LETTER_TODO_JA 0x1853 #define UNITEXT_MONGOLIAN_LETTER_TODO_JA L"\u1853" #define UNICODE_MONGOLIAN_LETTER_TODO_TSA 0x1854 #define UNITEXT_MONGOLIAN_LETTER_TODO_TSA L"\u1854" #define UNICODE_MONGOLIAN_LETTER_TODO_YA 0x1855 #define UNITEXT_MONGOLIAN_LETTER_TODO_YA L"\u1855" #define UNICODE_MONGOLIAN_LETTER_TODO_WA 0x1856 #define UNITEXT_MONGOLIAN_LETTER_TODO_WA L"\u1856" #define UNICODE_MONGOLIAN_LETTER_TODO_KA 0x1857 #define UNITEXT_MONGOLIAN_LETTER_TODO_KA L"\u1857" #define UNICODE_MONGOLIAN_LETTER_TODO_GAA 0x1858 #define UNITEXT_MONGOLIAN_LETTER_TODO_GAA L"\u1858" #define UNICODE_MONGOLIAN_LETTER_TODO_HAA 0x1859 #define UNITEXT_MONGOLIAN_LETTER_TODO_HAA L"\u1859" #define UNICODE_MONGOLIAN_LETTER_TODO_JIA 0x185a #define UNITEXT_MONGOLIAN_LETTER_TODO_JIA L"\u185a" #define UNICODE_MONGOLIAN_LETTER_TODO_NIA 0x185b #define UNITEXT_MONGOLIAN_LETTER_TODO_NIA L"\u185b" #define UNICODE_MONGOLIAN_LETTER_TODO_DZA 0x185c #define UNITEXT_MONGOLIAN_LETTER_TODO_DZA L"\u185c" #define UNICODE_MONGOLIAN_LETTER_SIBE_E 0x185d #define UNITEXT_MONGOLIAN_LETTER_SIBE_E L"\u185d" #define UNICODE_MONGOLIAN_LETTER_SIBE_I 0x185e #define UNITEXT_MONGOLIAN_LETTER_SIBE_I L"\u185e" #define UNICODE_MONGOLIAN_LETTER_SIBE_IY 0x185f #define UNITEXT_MONGOLIAN_LETTER_SIBE_IY L"\u185f" #define UNICODE_MONGOLIAN_LETTER_SIBE_UE 0x1860 #define UNITEXT_MONGOLIAN_LETTER_SIBE_UE L"\u1860" #define UNICODE_MONGOLIAN_LETTER_SIBE_U 0x1861 #define UNITEXT_MONGOLIAN_LETTER_SIBE_U L"\u1861" #define UNICODE_MONGOLIAN_LETTER_SIBE_ANG 0x1862 #define UNITEXT_MONGOLIAN_LETTER_SIBE_ANG L"\u1862" #define UNICODE_MONGOLIAN_LETTER_SIBE_KA 0x1863 #define UNITEXT_MONGOLIAN_LETTER_SIBE_KA L"\u1863" #define UNICODE_MONGOLIAN_LETTER_SIBE_GA 0x1864 #define UNITEXT_MONGOLIAN_LETTER_SIBE_GA L"\u1864" #define UNICODE_MONGOLIAN_LETTER_SIBE_HA 0x1865 #define UNITEXT_MONGOLIAN_LETTER_SIBE_HA L"\u1865" #define UNICODE_MONGOLIAN_LETTER_SIBE_PA 0x1866 #define UNITEXT_MONGOLIAN_LETTER_SIBE_PA L"\u1866" #define UNICODE_MONGOLIAN_LETTER_SIBE_SHA 0x1867 #define UNITEXT_MONGOLIAN_LETTER_SIBE_SHA L"\u1867" #define UNICODE_MONGOLIAN_LETTER_SIBE_TA 0x1868 #define UNITEXT_MONGOLIAN_LETTER_SIBE_TA L"\u1868" #define UNICODE_MONGOLIAN_LETTER_SIBE_DA 0x1869 #define UNITEXT_MONGOLIAN_LETTER_SIBE_DA L"\u1869" #define UNICODE_MONGOLIAN_LETTER_SIBE_JA 0x186a #define UNITEXT_MONGOLIAN_LETTER_SIBE_JA L"\u186a" #define UNICODE_MONGOLIAN_LETTER_SIBE_FA 0x186b #define UNITEXT_MONGOLIAN_LETTER_SIBE_FA L"\u186b" #define UNICODE_MONGOLIAN_LETTER_SIBE_GAA 0x186c #define UNITEXT_MONGOLIAN_LETTER_SIBE_GAA L"\u186c" #define UNICODE_MONGOLIAN_LETTER_SIBE_HAA 0x186d #define UNITEXT_MONGOLIAN_LETTER_SIBE_HAA L"\u186d" #define UNICODE_MONGOLIAN_LETTER_SIBE_TSA 0x186e #define UNITEXT_MONGOLIAN_LETTER_SIBE_TSA L"\u186e" #define UNICODE_MONGOLIAN_LETTER_SIBE_ZA 0x186f #define UNITEXT_MONGOLIAN_LETTER_SIBE_ZA L"\u186f" #define UNICODE_MONGOLIAN_LETTER_SIBE_RAA 0x1870 #define UNITEXT_MONGOLIAN_LETTER_SIBE_RAA L"\u1870" #define UNICODE_MONGOLIAN_LETTER_SIBE_CHA 0x1871 #define UNITEXT_MONGOLIAN_LETTER_SIBE_CHA L"\u1871" #define UNICODE_MONGOLIAN_LETTER_SIBE_ZHA 0x1872 #define UNITEXT_MONGOLIAN_LETTER_SIBE_ZHA L"\u1872" #define UNICODE_MONGOLIAN_LETTER_MANCHU_I 0x1873 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_I L"\u1873" #define UNICODE_MONGOLIAN_LETTER_MANCHU_KA 0x1874 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_KA L"\u1874" #define UNICODE_MONGOLIAN_LETTER_MANCHU_RA 0x1875 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_RA L"\u1875" #define UNICODE_MONGOLIAN_LETTER_MANCHU_FA 0x1876 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_FA L"\u1876" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ZHA 0x1877 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ZHA L"\u1877" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_ANUSVARA_ONE 0x1880 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_ANUSVARA_ONE L"\u1880" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_VISARGA_ONE 0x1881 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_VISARGA_ONE L"\u1881" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_DAMARU 0x1882 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_DAMARU L"\u1882" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_UBADAMA 0x1883 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_UBADAMA L"\u1883" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_INVERTED_UBADAMA 0x1884 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_INVERTED_UBADAMA L"\u1884" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_BALUDA 0x1885 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_BALUDA L"\u1885" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_THREE_BALUDA 0x1886 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_THREE_BALUDA L"\u1886" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_A 0x1887 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_A L"\u1887" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_I 0x1888 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_I L"\u1888" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_KA 0x1889 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_KA L"\u1889" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_NGA 0x188a #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_NGA L"\u188a" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_CA 0x188b #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_CA L"\u188b" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_TTA 0x188c #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_TTA L"\u188c" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_TTHA 0x188d #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_TTHA L"\u188d" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_DDA 0x188e #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_DDA L"\u188e" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_NNA 0x188f #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_NNA L"\u188f" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_TA 0x1890 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_TA L"\u1890" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_DA 0x1891 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_DA L"\u1891" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_PA 0x1892 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_PA L"\u1892" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_PHA 0x1893 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_PHA L"\u1893" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_SSA 0x1894 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_SSA L"\u1894" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_ZHA 0x1895 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_ZHA L"\u1895" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_ZA 0x1896 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_ZA L"\u1896" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_AH 0x1897 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_AH L"\u1897" #define UNICODE_MONGOLIAN_LETTER_TODO_ALI_GALI_TA 0x1898 #define UNITEXT_MONGOLIAN_LETTER_TODO_ALI_GALI_TA L"\u1898" #define UNICODE_MONGOLIAN_LETTER_TODO_ALI_GALI_ZHA 0x1899 #define UNITEXT_MONGOLIAN_LETTER_TODO_ALI_GALI_ZHA L"\u1899" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_GHA 0x189a #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_GHA L"\u189a" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_NGA 0x189b #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_NGA L"\u189b" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_CA 0x189c #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_CA L"\u189c" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_JHA 0x189d #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_JHA L"\u189d" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_TTA 0x189e #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_TTA L"\u189e" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_DDHA 0x189f #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_DDHA L"\u189f" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_TA 0x18a0 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_TA L"\u18a0" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_DHA 0x18a1 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_DHA L"\u18a1" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_SSA 0x18a2 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_SSA L"\u18a2" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_CYA 0x18a3 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_CYA L"\u18a3" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_ZHA 0x18a4 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_ZHA L"\u18a4" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_ZA 0x18a5 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_ZA L"\u18a5" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_HALF_U 0x18a6 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_HALF_U L"\u18a6" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_HALF_YA 0x18a7 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_HALF_YA L"\u18a7" #define UNICODE_MONGOLIAN_LETTER_MANCHU_ALI_GALI_BHA 0x18a8 #define UNITEXT_MONGOLIAN_LETTER_MANCHU_ALI_GALI_BHA L"\u18a8" #define UNICODE_MONGOLIAN_LETTER_ALI_GALI_DAGALGA 0x18a9 #define UNITEXT_MONGOLIAN_LETTER_ALI_GALI_DAGALGA L"\u18a9" #define UNICODE_LIMBU_VOWEL_CARRIER_LETTER 0x1900 #define UNITEXT_LIMBU_VOWEL_CARRIER_LETTER L"\u1900" #define UNICODE_LIMBU_LETTER_KA 0x1901 #define UNITEXT_LIMBU_LETTER_KA L"\u1901" #define UNICODE_LIMBU_LETTER_KHA 0x1902 #define UNITEXT_LIMBU_LETTER_KHA L"\u1902" #define UNICODE_LIMBU_LETTER_GA 0x1903 #define UNITEXT_LIMBU_LETTER_GA L"\u1903" #define UNICODE_LIMBU_LETTER_GHA 0x1904 #define UNITEXT_LIMBU_LETTER_GHA L"\u1904" #define UNICODE_LIMBU_LETTER_NGA 0x1905 #define UNITEXT_LIMBU_LETTER_NGA L"\u1905" #define UNICODE_LIMBU_LETTER_CA 0x1906 #define UNITEXT_LIMBU_LETTER_CA L"\u1906" #define UNICODE_LIMBU_LETTER_CHA 0x1907 #define UNITEXT_LIMBU_LETTER_CHA L"\u1907" #define UNICODE_LIMBU_LETTER_JA 0x1908 #define UNITEXT_LIMBU_LETTER_JA L"\u1908" #define UNICODE_LIMBU_LETTER_JHA 0x1909 #define UNITEXT_LIMBU_LETTER_JHA L"\u1909" #define UNICODE_LIMBU_LETTER_YAN 0x190a #define UNITEXT_LIMBU_LETTER_YAN L"\u190a" #define UNICODE_LIMBU_LETTER_TA 0x190b #define UNITEXT_LIMBU_LETTER_TA L"\u190b" #define UNICODE_LIMBU_LETTER_THA 0x190c #define UNITEXT_LIMBU_LETTER_THA L"\u190c" #define UNICODE_LIMBU_LETTER_DA 0x190d #define UNITEXT_LIMBU_LETTER_DA L"\u190d" #define UNICODE_LIMBU_LETTER_DHA 0x190e #define UNITEXT_LIMBU_LETTER_DHA L"\u190e" #define UNICODE_LIMBU_LETTER_NA 0x190f #define UNITEXT_LIMBU_LETTER_NA L"\u190f" #define UNICODE_LIMBU_LETTER_PA 0x1910 #define UNITEXT_LIMBU_LETTER_PA L"\u1910" #define UNICODE_LIMBU_LETTER_PHA 0x1911 #define UNITEXT_LIMBU_LETTER_PHA L"\u1911" #define UNICODE_LIMBU_LETTER_BA 0x1912 #define UNITEXT_LIMBU_LETTER_BA L"\u1912" #define UNICODE_LIMBU_LETTER_BHA 0x1913 #define UNITEXT_LIMBU_LETTER_BHA L"\u1913" #define UNICODE_LIMBU_LETTER_MA 0x1914 #define UNITEXT_LIMBU_LETTER_MA L"\u1914" #define UNICODE_LIMBU_LETTER_YA 0x1915 #define UNITEXT_LIMBU_LETTER_YA L"\u1915" #define UNICODE_LIMBU_LETTER_RA 0x1916 #define UNITEXT_LIMBU_LETTER_RA L"\u1916" #define UNICODE_LIMBU_LETTER_LA 0x1917 #define UNITEXT_LIMBU_LETTER_LA L"\u1917" #define UNICODE_LIMBU_LETTER_WA 0x1918 #define UNITEXT_LIMBU_LETTER_WA L"\u1918" #define UNICODE_LIMBU_LETTER_SHA 0x1919 #define UNITEXT_LIMBU_LETTER_SHA L"\u1919" #define UNICODE_LIMBU_LETTER_SSA 0x191a #define UNITEXT_LIMBU_LETTER_SSA L"\u191a" #define UNICODE_LIMBU_LETTER_SA 0x191b #define UNITEXT_LIMBU_LETTER_SA L"\u191b" #define UNICODE_LIMBU_LETTER_HA 0x191c #define UNITEXT_LIMBU_LETTER_HA L"\u191c" #define UNICODE_LIMBU_VOWEL_SIGN_A 0x1920 #define UNITEXT_LIMBU_VOWEL_SIGN_A L"\u1920" #define UNICODE_LIMBU_VOWEL_SIGN_I 0x1921 #define UNITEXT_LIMBU_VOWEL_SIGN_I L"\u1921" #define UNICODE_LIMBU_VOWEL_SIGN_U 0x1922 #define UNITEXT_LIMBU_VOWEL_SIGN_U L"\u1922" #define UNICODE_LIMBU_VOWEL_SIGN_EE 0x1923 #define UNITEXT_LIMBU_VOWEL_SIGN_EE L"\u1923" #define UNICODE_LIMBU_VOWEL_SIGN_AI 0x1924 #define UNITEXT_LIMBU_VOWEL_SIGN_AI L"\u1924" #define UNICODE_LIMBU_VOWEL_SIGN_OO 0x1925 #define UNITEXT_LIMBU_VOWEL_SIGN_OO L"\u1925" #define UNICODE_LIMBU_VOWEL_SIGN_AU 0x1926 #define UNITEXT_LIMBU_VOWEL_SIGN_AU L"\u1926" #define UNICODE_LIMBU_VOWEL_SIGN_E 0x1927 #define UNITEXT_LIMBU_VOWEL_SIGN_E L"\u1927" #define UNICODE_LIMBU_VOWEL_SIGN_O 0x1928 #define UNITEXT_LIMBU_VOWEL_SIGN_O L"\u1928" #define UNICODE_LIMBU_SUBJOINED_LETTER_YA 0x1929 #define UNITEXT_LIMBU_SUBJOINED_LETTER_YA L"\u1929" #define UNICODE_LIMBU_SUBJOINED_LETTER_RA 0x192a #define UNITEXT_LIMBU_SUBJOINED_LETTER_RA L"\u192a" #define UNICODE_LIMBU_SUBJOINED_LETTER_WA 0x192b #define UNITEXT_LIMBU_SUBJOINED_LETTER_WA L"\u192b" #define UNICODE_LIMBU_SMALL_LETTER_KA 0x1930 #define UNITEXT_LIMBU_SMALL_LETTER_KA L"\u1930" #define UNICODE_LIMBU_SMALL_LETTER_NGA 0x1931 #define UNITEXT_LIMBU_SMALL_LETTER_NGA L"\u1931" #define UNICODE_LIMBU_SMALL_LETTER_ANUSVARA 0x1932 #define UNITEXT_LIMBU_SMALL_LETTER_ANUSVARA L"\u1932" #define UNICODE_LIMBU_SMALL_LETTER_TA 0x1933 #define UNITEXT_LIMBU_SMALL_LETTER_TA L"\u1933" #define UNICODE_LIMBU_SMALL_LETTER_NA 0x1934 #define UNITEXT_LIMBU_SMALL_LETTER_NA L"\u1934" #define UNICODE_LIMBU_SMALL_LETTER_PA 0x1935 #define UNITEXT_LIMBU_SMALL_LETTER_PA L"\u1935" #define UNICODE_LIMBU_SMALL_LETTER_MA 0x1936 #define UNITEXT_LIMBU_SMALL_LETTER_MA L"\u1936" #define UNICODE_LIMBU_SMALL_LETTER_RA 0x1937 #define UNITEXT_LIMBU_SMALL_LETTER_RA L"\u1937" #define UNICODE_LIMBU_SMALL_LETTER_LA 0x1938 #define UNITEXT_LIMBU_SMALL_LETTER_LA L"\u1938" #define UNICODE_LIMBU_SIGN_MUKPHRENG 0x1939 #define UNITEXT_LIMBU_SIGN_MUKPHRENG L"\u1939" #define UNICODE_LIMBU_SIGN_KEMPHRENG 0x193a #define UNITEXT_LIMBU_SIGN_KEMPHRENG L"\u193a" #define UNICODE_LIMBU_SIGN_SA_I 0x193b #define UNITEXT_LIMBU_SIGN_SA_I L"\u193b" #define UNICODE_LIMBU_SIGN_LOO 0x1940 #define UNITEXT_LIMBU_SIGN_LOO L"\u1940" #define UNICODE_LIMBU_EXCLAMATION_MARK 0x1944 #define UNITEXT_LIMBU_EXCLAMATION_MARK L"\u1944" #define UNICODE_LIMBU_QUESTION_MARK 0x1945 #define UNITEXT_LIMBU_QUESTION_MARK L"\u1945" #define UNICODE_LIMBU_DIGIT_ZERO 0x1946 #define UNITEXT_LIMBU_DIGIT_ZERO L"\u1946" #define UNICODE_LIMBU_DIGIT_ONE 0x1947 #define UNITEXT_LIMBU_DIGIT_ONE L"\u1947" #define UNICODE_LIMBU_DIGIT_TWO 0x1948 #define UNITEXT_LIMBU_DIGIT_TWO L"\u1948" #define UNICODE_LIMBU_DIGIT_THREE 0x1949 #define UNITEXT_LIMBU_DIGIT_THREE L"\u1949" #define UNICODE_LIMBU_DIGIT_FOUR 0x194a #define UNITEXT_LIMBU_DIGIT_FOUR L"\u194a" #define UNICODE_LIMBU_DIGIT_FIVE 0x194b #define UNITEXT_LIMBU_DIGIT_FIVE L"\u194b" #define UNICODE_LIMBU_DIGIT_SIX 0x194c #define UNITEXT_LIMBU_DIGIT_SIX L"\u194c" #define UNICODE_LIMBU_DIGIT_SEVEN 0x194d #define UNITEXT_LIMBU_DIGIT_SEVEN L"\u194d" #define UNICODE_LIMBU_DIGIT_EIGHT 0x194e #define UNITEXT_LIMBU_DIGIT_EIGHT L"\u194e" #define UNICODE_LIMBU_DIGIT_NINE 0x194f #define UNITEXT_LIMBU_DIGIT_NINE L"\u194f" #define UNICODE_TAI_LE_LETTER_KA 0x1950 #define UNITEXT_TAI_LE_LETTER_KA L"\u1950" #define UNICODE_TAI_LE_LETTER_XA 0x1951 #define UNITEXT_TAI_LE_LETTER_XA L"\u1951" #define UNICODE_TAI_LE_LETTER_NGA 0x1952 #define UNITEXT_TAI_LE_LETTER_NGA L"\u1952" #define UNICODE_TAI_LE_LETTER_TSA 0x1953 #define UNITEXT_TAI_LE_LETTER_TSA L"\u1953" #define UNICODE_TAI_LE_LETTER_SA 0x1954 #define UNITEXT_TAI_LE_LETTER_SA L"\u1954" #define UNICODE_TAI_LE_LETTER_YA 0x1955 #define UNITEXT_TAI_LE_LETTER_YA L"\u1955" #define UNICODE_TAI_LE_LETTER_TA 0x1956 #define UNITEXT_TAI_LE_LETTER_TA L"\u1956" #define UNICODE_TAI_LE_LETTER_THA 0x1957 #define UNITEXT_TAI_LE_LETTER_THA L"\u1957" #define UNICODE_TAI_LE_LETTER_LA 0x1958 #define UNITEXT_TAI_LE_LETTER_LA L"\u1958" #define UNICODE_TAI_LE_LETTER_PA 0x1959 #define UNITEXT_TAI_LE_LETTER_PA L"\u1959" #define UNICODE_TAI_LE_LETTER_PHA 0x195a #define UNITEXT_TAI_LE_LETTER_PHA L"\u195a" #define UNICODE_TAI_LE_LETTER_MA 0x195b #define UNITEXT_TAI_LE_LETTER_MA L"\u195b" #define UNICODE_TAI_LE_LETTER_FA 0x195c #define UNITEXT_TAI_LE_LETTER_FA L"\u195c" #define UNICODE_TAI_LE_LETTER_VA 0x195d #define UNITEXT_TAI_LE_LETTER_VA L"\u195d" #define UNICODE_TAI_LE_LETTER_HA 0x195e #define UNITEXT_TAI_LE_LETTER_HA L"\u195e" #define UNICODE_TAI_LE_LETTER_QA 0x195f #define UNITEXT_TAI_LE_LETTER_QA L"\u195f" #define UNICODE_TAI_LE_LETTER_KHA 0x1960 #define UNITEXT_TAI_LE_LETTER_KHA L"\u1960" #define UNICODE_TAI_LE_LETTER_TSHA 0x1961 #define UNITEXT_TAI_LE_LETTER_TSHA L"\u1961" #define UNICODE_TAI_LE_LETTER_NA 0x1962 #define UNITEXT_TAI_LE_LETTER_NA L"\u1962" #define UNICODE_TAI_LE_LETTER_A 0x1963 #define UNITEXT_TAI_LE_LETTER_A L"\u1963" #define UNICODE_TAI_LE_LETTER_I 0x1964 #define UNITEXT_TAI_LE_LETTER_I L"\u1964" #define UNICODE_TAI_LE_LETTER_EE 0x1965 #define UNITEXT_TAI_LE_LETTER_EE L"\u1965" #define UNICODE_TAI_LE_LETTER_EH 0x1966 #define UNITEXT_TAI_LE_LETTER_EH L"\u1966" #define UNICODE_TAI_LE_LETTER_U 0x1967 #define UNITEXT_TAI_LE_LETTER_U L"\u1967" #define UNICODE_TAI_LE_LETTER_OO 0x1968 #define UNITEXT_TAI_LE_LETTER_OO L"\u1968" #define UNICODE_TAI_LE_LETTER_O 0x1969 #define UNITEXT_TAI_LE_LETTER_O L"\u1969" #define UNICODE_TAI_LE_LETTER_UE 0x196a #define UNITEXT_TAI_LE_LETTER_UE L"\u196a" #define UNICODE_TAI_LE_LETTER_E 0x196b #define UNITEXT_TAI_LE_LETTER_E L"\u196b" #define UNICODE_TAI_LE_LETTER_AUE 0x196c #define UNITEXT_TAI_LE_LETTER_AUE L"\u196c" #define UNICODE_TAI_LE_LETTER_AI 0x196d #define UNITEXT_TAI_LE_LETTER_AI L"\u196d" #define UNICODE_TAI_LE_LETTER_TONE_2 0x1970 #define UNITEXT_TAI_LE_LETTER_TONE_2 L"\u1970" #define UNICODE_TAI_LE_LETTER_TONE_3 0x1971 #define UNITEXT_TAI_LE_LETTER_TONE_3 L"\u1971" #define UNICODE_TAI_LE_LETTER_TONE_4 0x1972 #define UNITEXT_TAI_LE_LETTER_TONE_4 L"\u1972" #define UNICODE_TAI_LE_LETTER_TONE_5 0x1973 #define UNITEXT_TAI_LE_LETTER_TONE_5 L"\u1973" #define UNICODE_TAI_LE_LETTER_TONE_6 0x1974 #define UNITEXT_TAI_LE_LETTER_TONE_6 L"\u1974" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_QA 0x1980 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_QA L"\u1980" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_QA 0x1981 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_QA L"\u1981" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_KA 0x1982 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_KA L"\u1982" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_XA 0x1983 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_XA L"\u1983" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_NGA 0x1984 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_NGA L"\u1984" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_KA 0x1985 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_KA L"\u1985" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_XA 0x1986 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_XA L"\u1986" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_NGA 0x1987 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_NGA L"\u1987" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_TSA 0x1988 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_TSA L"\u1988" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_SA 0x1989 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_SA L"\u1989" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_YA 0x198a #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_YA L"\u198a" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_TSA 0x198b #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_TSA L"\u198b" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_SA 0x198c #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_SA L"\u198c" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_YA 0x198d #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_YA L"\u198d" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_TA 0x198e #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_TA L"\u198e" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_THA 0x198f #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_THA L"\u198f" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_NA 0x1990 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_NA L"\u1990" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_TA 0x1991 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_TA L"\u1991" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_THA 0x1992 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_THA L"\u1992" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_NA 0x1993 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_NA L"\u1993" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_PA 0x1994 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_PA L"\u1994" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_PHA 0x1995 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_PHA L"\u1995" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_MA 0x1996 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_MA L"\u1996" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_PA 0x1997 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_PA L"\u1997" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_PHA 0x1998 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_PHA L"\u1998" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_MA 0x1999 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_MA L"\u1999" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_FA 0x199a #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_FA L"\u199a" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_VA 0x199b #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_VA L"\u199b" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_LA 0x199c #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_LA L"\u199c" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_FA 0x199d #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_FA L"\u199d" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_VA 0x199e #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_VA L"\u199e" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_LA 0x199f #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_LA L"\u199f" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_HA 0x19a0 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_HA L"\u19a0" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_DA 0x19a1 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_DA L"\u19a1" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_BA 0x19a2 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_BA L"\u19a2" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_HA 0x19a3 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_HA L"\u19a3" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_DA 0x19a4 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_DA L"\u19a4" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_BA 0x19a5 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_BA L"\u19a5" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_KVA 0x19a6 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_KVA L"\u19a6" #define UNICODE_NEW_TAI_LUE_LETTER_HIGH_XVA 0x19a7 #define UNITEXT_NEW_TAI_LUE_LETTER_HIGH_XVA L"\u19a7" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_KVA 0x19a8 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_KVA L"\u19a8" #define UNICODE_NEW_TAI_LUE_LETTER_LOW_XVA 0x19a9 #define UNITEXT_NEW_TAI_LUE_LETTER_LOW_XVA L"\u19a9" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_VOWEL_SHORTENER 0x19b0 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_VOWEL_SHORTENER L"\u19b0" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_AA 0x19b1 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_AA L"\u19b1" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_II 0x19b2 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_II L"\u19b2" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_U 0x19b3 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_U L"\u19b3" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_UU 0x19b4 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_UU L"\u19b4" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_E 0x19b5 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_E L"\u19b5" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_AE 0x19b6 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_AE L"\u19b6" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_O 0x19b7 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_O L"\u19b7" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_OA 0x19b8 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_OA L"\u19b8" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_UE 0x19b9 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_UE L"\u19b9" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_AY 0x19ba #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_AY L"\u19ba" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_AAY 0x19bb #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_AAY L"\u19bb" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_UY 0x19bc #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_UY L"\u19bc" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_OY 0x19bd #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_OY L"\u19bd" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_OAY 0x19be #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_OAY L"\u19be" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_UEY 0x19bf #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_UEY L"\u19bf" #define UNICODE_NEW_TAI_LUE_VOWEL_SIGN_IY 0x19c0 #define UNITEXT_NEW_TAI_LUE_VOWEL_SIGN_IY L"\u19c0" #define UNICODE_NEW_TAI_LUE_LETTER_FINAL_V 0x19c1 #define UNITEXT_NEW_TAI_LUE_LETTER_FINAL_V L"\u19c1" #define UNICODE_NEW_TAI_LUE_LETTER_FINAL_NG 0x19c2 #define UNITEXT_NEW_TAI_LUE_LETTER_FINAL_NG L"\u19c2" #define UNICODE_NEW_TAI_LUE_LETTER_FINAL_N 0x19c3 #define UNITEXT_NEW_TAI_LUE_LETTER_FINAL_N L"\u19c3" #define UNICODE_NEW_TAI_LUE_LETTER_FINAL_M 0x19c4 #define UNITEXT_NEW_TAI_LUE_LETTER_FINAL_M L"\u19c4" #define UNICODE_NEW_TAI_LUE_LETTER_FINAL_K 0x19c5 #define UNITEXT_NEW_TAI_LUE_LETTER_FINAL_K L"\u19c5" #define UNICODE_NEW_TAI_LUE_LETTER_FINAL_D 0x19c6 #define UNITEXT_NEW_TAI_LUE_LETTER_FINAL_D L"\u19c6" #define UNICODE_NEW_TAI_LUE_LETTER_FINAL_B 0x19c7 #define UNITEXT_NEW_TAI_LUE_LETTER_FINAL_B L"\u19c7" #define UNICODE_NEW_TAI_LUE_TONE_MARK_1 0x19c8 #define UNITEXT_NEW_TAI_LUE_TONE_MARK_1 L"\u19c8" #define UNICODE_NEW_TAI_LUE_TONE_MARK_2 0x19c9 #define UNITEXT_NEW_TAI_LUE_TONE_MARK_2 L"\u19c9" #define UNICODE_NEW_TAI_LUE_DIGIT_ZERO 0x19d0 #define UNITEXT_NEW_TAI_LUE_DIGIT_ZERO L"\u19d0" #define UNICODE_NEW_TAI_LUE_DIGIT_ONE 0x19d1 #define UNITEXT_NEW_TAI_LUE_DIGIT_ONE L"\u19d1" #define UNICODE_NEW_TAI_LUE_DIGIT_TWO 0x19d2 #define UNITEXT_NEW_TAI_LUE_DIGIT_TWO L"\u19d2" #define UNICODE_NEW_TAI_LUE_DIGIT_THREE 0x19d3 #define UNITEXT_NEW_TAI_LUE_DIGIT_THREE L"\u19d3" #define UNICODE_NEW_TAI_LUE_DIGIT_FOUR 0x19d4 #define UNITEXT_NEW_TAI_LUE_DIGIT_FOUR L"\u19d4" #define UNICODE_NEW_TAI_LUE_DIGIT_FIVE 0x19d5 #define UNITEXT_NEW_TAI_LUE_DIGIT_FIVE L"\u19d5" #define UNICODE_NEW_TAI_LUE_DIGIT_SIX 0x19d6 #define UNITEXT_NEW_TAI_LUE_DIGIT_SIX L"\u19d6" #define UNICODE_NEW_TAI_LUE_DIGIT_SEVEN 0x19d7 #define UNITEXT_NEW_TAI_LUE_DIGIT_SEVEN L"\u19d7" #define UNICODE_NEW_TAI_LUE_DIGIT_EIGHT 0x19d8 #define UNITEXT_NEW_TAI_LUE_DIGIT_EIGHT L"\u19d8" #define UNICODE_NEW_TAI_LUE_DIGIT_NINE 0x19d9 #define UNITEXT_NEW_TAI_LUE_DIGIT_NINE L"\u19d9" #define UNICODE_NEW_TAI_LUE_SIGN_LAE 0x19de #define UNITEXT_NEW_TAI_LUE_SIGN_LAE L"\u19de" #define UNICODE_NEW_TAI_LUE_SIGN_LAEV 0x19df #define UNITEXT_NEW_TAI_LUE_SIGN_LAEV L"\u19df" #define UNICODE_KHMER_SYMBOL_PATHAMASAT 0x19e0 #define UNITEXT_KHMER_SYMBOL_PATHAMASAT L"\u19e0" #define UNICODE_KHMER_SYMBOL_MUOY_KOET 0x19e1 #define UNITEXT_KHMER_SYMBOL_MUOY_KOET L"\u19e1" #define UNICODE_KHMER_SYMBOL_PII_KOET 0x19e2 #define UNITEXT_KHMER_SYMBOL_PII_KOET L"\u19e2" #define UNICODE_KHMER_SYMBOL_BEI_KOET 0x19e3 #define UNITEXT_KHMER_SYMBOL_BEI_KOET L"\u19e3" #define UNICODE_KHMER_SYMBOL_BUON_KOET 0x19e4 #define UNITEXT_KHMER_SYMBOL_BUON_KOET L"\u19e4" #define UNICODE_KHMER_SYMBOL_PRAM_KOET 0x19e5 #define UNITEXT_KHMER_SYMBOL_PRAM_KOET L"\u19e5" #define UNICODE_KHMER_SYMBOL_PRAM_MUOY_KOET 0x19e6 #define UNITEXT_KHMER_SYMBOL_PRAM_MUOY_KOET L"\u19e6" #define UNICODE_KHMER_SYMBOL_PRAM_PII_KOET 0x19e7 #define UNITEXT_KHMER_SYMBOL_PRAM_PII_KOET L"\u19e7" #define UNICODE_KHMER_SYMBOL_PRAM_BEI_KOET 0x19e8 #define UNITEXT_KHMER_SYMBOL_PRAM_BEI_KOET L"\u19e8" #define UNICODE_KHMER_SYMBOL_PRAM_BUON_KOET 0x19e9 #define UNITEXT_KHMER_SYMBOL_PRAM_BUON_KOET L"\u19e9" #define UNICODE_KHMER_SYMBOL_DAP_KOET 0x19ea #define UNITEXT_KHMER_SYMBOL_DAP_KOET L"\u19ea" #define UNICODE_KHMER_SYMBOL_DAP_MUOY_KOET 0x19eb #define UNITEXT_KHMER_SYMBOL_DAP_MUOY_KOET L"\u19eb" #define UNICODE_KHMER_SYMBOL_DAP_PII_KOET 0x19ec #define UNITEXT_KHMER_SYMBOL_DAP_PII_KOET L"\u19ec" #define UNICODE_KHMER_SYMBOL_DAP_BEI_KOET 0x19ed #define UNITEXT_KHMER_SYMBOL_DAP_BEI_KOET L"\u19ed" #define UNICODE_KHMER_SYMBOL_DAP_BUON_KOET 0x19ee #define UNITEXT_KHMER_SYMBOL_DAP_BUON_KOET L"\u19ee" #define UNICODE_KHMER_SYMBOL_DAP_PRAM_KOET 0x19ef #define UNITEXT_KHMER_SYMBOL_DAP_PRAM_KOET L"\u19ef" #define UNICODE_KHMER_SYMBOL_TUTEYASAT 0x19f0 #define UNITEXT_KHMER_SYMBOL_TUTEYASAT L"\u19f0" #define UNICODE_KHMER_SYMBOL_MUOY_ROC 0x19f1 #define UNITEXT_KHMER_SYMBOL_MUOY_ROC L"\u19f1" #define UNICODE_KHMER_SYMBOL_PII_ROC 0x19f2 #define UNITEXT_KHMER_SYMBOL_PII_ROC L"\u19f2" #define UNICODE_KHMER_SYMBOL_BEI_ROC 0x19f3 #define UNITEXT_KHMER_SYMBOL_BEI_ROC L"\u19f3" #define UNICODE_KHMER_SYMBOL_BUON_ROC 0x19f4 #define UNITEXT_KHMER_SYMBOL_BUON_ROC L"\u19f4" #define UNICODE_KHMER_SYMBOL_PRAM_ROC 0x19f5 #define UNITEXT_KHMER_SYMBOL_PRAM_ROC L"\u19f5" #define UNICODE_KHMER_SYMBOL_PRAM_MUOY_ROC 0x19f6 #define UNITEXT_KHMER_SYMBOL_PRAM_MUOY_ROC L"\u19f6" #define UNICODE_KHMER_SYMBOL_PRAM_PII_ROC 0x19f7 #define UNITEXT_KHMER_SYMBOL_PRAM_PII_ROC L"\u19f7" #define UNICODE_KHMER_SYMBOL_PRAM_BEI_ROC 0x19f8 #define UNITEXT_KHMER_SYMBOL_PRAM_BEI_ROC L"\u19f8" #define UNICODE_KHMER_SYMBOL_PRAM_BUON_ROC 0x19f9 #define UNITEXT_KHMER_SYMBOL_PRAM_BUON_ROC L"\u19f9" #define UNICODE_KHMER_SYMBOL_DAP_ROC 0x19fa #define UNITEXT_KHMER_SYMBOL_DAP_ROC L"\u19fa" #define UNICODE_KHMER_SYMBOL_DAP_MUOY_ROC 0x19fb #define UNITEXT_KHMER_SYMBOL_DAP_MUOY_ROC L"\u19fb" #define UNICODE_KHMER_SYMBOL_DAP_PII_ROC 0x19fc #define UNITEXT_KHMER_SYMBOL_DAP_PII_ROC L"\u19fc" #define UNICODE_KHMER_SYMBOL_DAP_BEI_ROC 0x19fd #define UNITEXT_KHMER_SYMBOL_DAP_BEI_ROC L"\u19fd" #define UNICODE_KHMER_SYMBOL_DAP_BUON_ROC 0x19fe #define UNITEXT_KHMER_SYMBOL_DAP_BUON_ROC L"\u19fe" #define UNICODE_KHMER_SYMBOL_DAP_PRAM_ROC 0x19ff #define UNITEXT_KHMER_SYMBOL_DAP_PRAM_ROC L"\u19ff" #define UNICODE_BUGINESE_LETTER_KA 0x1a00 #define UNITEXT_BUGINESE_LETTER_KA L"\u1a00" #define UNICODE_BUGINESE_LETTER_GA 0x1a01 #define UNITEXT_BUGINESE_LETTER_GA L"\u1a01" #define UNICODE_BUGINESE_LETTER_NGA 0x1a02 #define UNITEXT_BUGINESE_LETTER_NGA L"\u1a02" #define UNICODE_BUGINESE_LETTER_NGKA 0x1a03 #define UNITEXT_BUGINESE_LETTER_NGKA L"\u1a03" #define UNICODE_BUGINESE_LETTER_PA 0x1a04 #define UNITEXT_BUGINESE_LETTER_PA L"\u1a04" #define UNICODE_BUGINESE_LETTER_BA 0x1a05 #define UNITEXT_BUGINESE_LETTER_BA L"\u1a05" #define UNICODE_BUGINESE_LETTER_MA 0x1a06 #define UNITEXT_BUGINESE_LETTER_MA L"\u1a06" #define UNICODE_BUGINESE_LETTER_MPA 0x1a07 #define UNITEXT_BUGINESE_LETTER_MPA L"\u1a07" #define UNICODE_BUGINESE_LETTER_TA 0x1a08 #define UNITEXT_BUGINESE_LETTER_TA L"\u1a08" #define UNICODE_BUGINESE_LETTER_DA 0x1a09 #define UNITEXT_BUGINESE_LETTER_DA L"\u1a09" #define UNICODE_BUGINESE_LETTER_NA 0x1a0a #define UNITEXT_BUGINESE_LETTER_NA L"\u1a0a" #define UNICODE_BUGINESE_LETTER_NRA 0x1a0b #define UNITEXT_BUGINESE_LETTER_NRA L"\u1a0b" #define UNICODE_BUGINESE_LETTER_CA 0x1a0c #define UNITEXT_BUGINESE_LETTER_CA L"\u1a0c" #define UNICODE_BUGINESE_LETTER_JA 0x1a0d #define UNITEXT_BUGINESE_LETTER_JA L"\u1a0d" #define UNICODE_BUGINESE_LETTER_NYA 0x1a0e #define UNITEXT_BUGINESE_LETTER_NYA L"\u1a0e" #define UNICODE_BUGINESE_LETTER_NYCA 0x1a0f #define UNITEXT_BUGINESE_LETTER_NYCA L"\u1a0f" #define UNICODE_BUGINESE_LETTER_YA 0x1a10 #define UNITEXT_BUGINESE_LETTER_YA L"\u1a10" #define UNICODE_BUGINESE_LETTER_RA 0x1a11 #define UNITEXT_BUGINESE_LETTER_RA L"\u1a11" #define UNICODE_BUGINESE_LETTER_LA 0x1a12 #define UNITEXT_BUGINESE_LETTER_LA L"\u1a12" #define UNICODE_BUGINESE_LETTER_VA 0x1a13 #define UNITEXT_BUGINESE_LETTER_VA L"\u1a13" #define UNICODE_BUGINESE_LETTER_SA 0x1a14 #define UNITEXT_BUGINESE_LETTER_SA L"\u1a14" #define UNICODE_BUGINESE_LETTER_A 0x1a15 #define UNITEXT_BUGINESE_LETTER_A L"\u1a15" #define UNICODE_BUGINESE_LETTER_HA 0x1a16 #define UNITEXT_BUGINESE_LETTER_HA L"\u1a16" #define UNICODE_BUGINESE_VOWEL_SIGN_I 0x1a17 #define UNITEXT_BUGINESE_VOWEL_SIGN_I L"\u1a17" #define UNICODE_BUGINESE_VOWEL_SIGN_U 0x1a18 #define UNITEXT_BUGINESE_VOWEL_SIGN_U L"\u1a18" #define UNICODE_BUGINESE_VOWEL_SIGN_E 0x1a19 #define UNITEXT_BUGINESE_VOWEL_SIGN_E L"\u1a19" #define UNICODE_BUGINESE_VOWEL_SIGN_O 0x1a1a #define UNITEXT_BUGINESE_VOWEL_SIGN_O L"\u1a1a" #define UNICODE_BUGINESE_VOWEL_SIGN_AE 0x1a1b #define UNITEXT_BUGINESE_VOWEL_SIGN_AE L"\u1a1b" #define UNICODE_BUGINESE_PALLAWA 0x1a1e #define UNITEXT_BUGINESE_PALLAWA L"\u1a1e" #define UNICODE_BUGINESE_END_OF_SECTION 0x1a1f #define UNITEXT_BUGINESE_END_OF_SECTION L"\u1a1f" #define UNICODE_BALINESE_SIGN_ULU_RICEM 0x1b00 #define UNITEXT_BALINESE_SIGN_ULU_RICEM L"\u1b00" #define UNICODE_BALINESE_SIGN_ULU_CANDRA 0x1b01 #define UNITEXT_BALINESE_SIGN_ULU_CANDRA L"\u1b01" #define UNICODE_BALINESE_SIGN_CECEK 0x1b02 #define UNITEXT_BALINESE_SIGN_CECEK L"\u1b02" #define UNICODE_BALINESE_SIGN_SURANG 0x1b03 #define UNITEXT_BALINESE_SIGN_SURANG L"\u1b03" #define UNICODE_BALINESE_SIGN_BISAH 0x1b04 #define UNITEXT_BALINESE_SIGN_BISAH L"\u1b04" #define UNICODE_BALINESE_LETTER_AKARA 0x1b05 #define UNITEXT_BALINESE_LETTER_AKARA L"\u1b05" #define UNICODE_BALINESE_LETTER_AKARA_TEDUNG 0x1b06 #define UNITEXT_BALINESE_LETTER_AKARA_TEDUNG L"\u1b06" #define UNICODE_BALINESE_LETTER_IKARA 0x1b07 #define UNITEXT_BALINESE_LETTER_IKARA L"\u1b07" #define UNICODE_BALINESE_LETTER_IKARA_TEDUNG 0x1b08 #define UNITEXT_BALINESE_LETTER_IKARA_TEDUNG L"\u1b08" #define UNICODE_BALINESE_LETTER_UKARA 0x1b09 #define UNITEXT_BALINESE_LETTER_UKARA L"\u1b09" #define UNICODE_BALINESE_LETTER_UKARA_TEDUNG 0x1b0a #define UNITEXT_BALINESE_LETTER_UKARA_TEDUNG L"\u1b0a" #define UNICODE_BALINESE_LETTER_RA_REPA 0x1b0b #define UNITEXT_BALINESE_LETTER_RA_REPA L"\u1b0b" #define UNICODE_BALINESE_LETTER_RA_REPA_TEDUNG 0x1b0c #define UNITEXT_BALINESE_LETTER_RA_REPA_TEDUNG L"\u1b0c" #define UNICODE_BALINESE_LETTER_LA_LENGA 0x1b0d #define UNITEXT_BALINESE_LETTER_LA_LENGA L"\u1b0d" #define UNICODE_BALINESE_LETTER_LA_LENGA_TEDUNG 0x1b0e #define UNITEXT_BALINESE_LETTER_LA_LENGA_TEDUNG L"\u1b0e" #define UNICODE_BALINESE_LETTER_EKARA 0x1b0f #define UNITEXT_BALINESE_LETTER_EKARA L"\u1b0f" #define UNICODE_BALINESE_LETTER_AIKARA 0x1b10 #define UNITEXT_BALINESE_LETTER_AIKARA L"\u1b10" #define UNICODE_BALINESE_LETTER_OKARA 0x1b11 #define UNITEXT_BALINESE_LETTER_OKARA L"\u1b11" #define UNICODE_BALINESE_LETTER_OKARA_TEDUNG 0x1b12 #define UNITEXT_BALINESE_LETTER_OKARA_TEDUNG L"\u1b12" #define UNICODE_BALINESE_LETTER_KA 0x1b13 #define UNITEXT_BALINESE_LETTER_KA L"\u1b13" #define UNICODE_BALINESE_LETTER_KA_MAHAPRANA 0x1b14 #define UNITEXT_BALINESE_LETTER_KA_MAHAPRANA L"\u1b14" #define UNICODE_BALINESE_LETTER_GA 0x1b15 #define UNITEXT_BALINESE_LETTER_GA L"\u1b15" #define UNICODE_BALINESE_LETTER_GA_GORA 0x1b16 #define UNITEXT_BALINESE_LETTER_GA_GORA L"\u1b16" #define UNICODE_BALINESE_LETTER_NGA 0x1b17 #define UNITEXT_BALINESE_LETTER_NGA L"\u1b17" #define UNICODE_BALINESE_LETTER_CA 0x1b18 #define UNITEXT_BALINESE_LETTER_CA L"\u1b18" #define UNICODE_BALINESE_LETTER_CA_LACA 0x1b19 #define UNITEXT_BALINESE_LETTER_CA_LACA L"\u1b19" #define UNICODE_BALINESE_LETTER_JA 0x1b1a #define UNITEXT_BALINESE_LETTER_JA L"\u1b1a" #define UNICODE_BALINESE_LETTER_JA_JERA 0x1b1b #define UNITEXT_BALINESE_LETTER_JA_JERA L"\u1b1b" #define UNICODE_BALINESE_LETTER_NYA 0x1b1c #define UNITEXT_BALINESE_LETTER_NYA L"\u1b1c" #define UNICODE_BALINESE_LETTER_TA_LATIK 0x1b1d #define UNITEXT_BALINESE_LETTER_TA_LATIK L"\u1b1d" #define UNICODE_BALINESE_LETTER_TA_MURDA_MAHAPRANA 0x1b1e #define UNITEXT_BALINESE_LETTER_TA_MURDA_MAHAPRANA L"\u1b1e" #define UNICODE_BALINESE_LETTER_DA_MURDA_ALPAPRANA 0x1b1f #define UNITEXT_BALINESE_LETTER_DA_MURDA_ALPAPRANA L"\u1b1f" #define UNICODE_BALINESE_LETTER_DA_MURDA_MAHAPRANA 0x1b20 #define UNITEXT_BALINESE_LETTER_DA_MURDA_MAHAPRANA L"\u1b20" #define UNICODE_BALINESE_LETTER_NA_RAMBAT 0x1b21 #define UNITEXT_BALINESE_LETTER_NA_RAMBAT L"\u1b21" #define UNICODE_BALINESE_LETTER_TA 0x1b22 #define UNITEXT_BALINESE_LETTER_TA L"\u1b22" #define UNICODE_BALINESE_LETTER_TA_TAWA 0x1b23 #define UNITEXT_BALINESE_LETTER_TA_TAWA L"\u1b23" #define UNICODE_BALINESE_LETTER_DA 0x1b24 #define UNITEXT_BALINESE_LETTER_DA L"\u1b24" #define UNICODE_BALINESE_LETTER_DA_MADU 0x1b25 #define UNITEXT_BALINESE_LETTER_DA_MADU L"\u1b25" #define UNICODE_BALINESE_LETTER_NA 0x1b26 #define UNITEXT_BALINESE_LETTER_NA L"\u1b26" #define UNICODE_BALINESE_LETTER_PA 0x1b27 #define UNITEXT_BALINESE_LETTER_PA L"\u1b27" #define UNICODE_BALINESE_LETTER_PA_KAPAL 0x1b28 #define UNITEXT_BALINESE_LETTER_PA_KAPAL L"\u1b28" #define UNICODE_BALINESE_LETTER_BA 0x1b29 #define UNITEXT_BALINESE_LETTER_BA L"\u1b29" #define UNICODE_BALINESE_LETTER_BA_KEMBANG 0x1b2a #define UNITEXT_BALINESE_LETTER_BA_KEMBANG L"\u1b2a" #define UNICODE_BALINESE_LETTER_MA 0x1b2b #define UNITEXT_BALINESE_LETTER_MA L"\u1b2b" #define UNICODE_BALINESE_LETTER_YA 0x1b2c #define UNITEXT_BALINESE_LETTER_YA L"\u1b2c" #define UNICODE_BALINESE_LETTER_RA 0x1b2d #define UNITEXT_BALINESE_LETTER_RA L"\u1b2d" #define UNICODE_BALINESE_LETTER_LA 0x1b2e #define UNITEXT_BALINESE_LETTER_LA L"\u1b2e" #define UNICODE_BALINESE_LETTER_WA 0x1b2f #define UNITEXT_BALINESE_LETTER_WA L"\u1b2f" #define UNICODE_BALINESE_LETTER_SA_SAGA 0x1b30 #define UNITEXT_BALINESE_LETTER_SA_SAGA L"\u1b30" #define UNICODE_BALINESE_LETTER_SA_SAPA 0x1b31 #define UNITEXT_BALINESE_LETTER_SA_SAPA L"\u1b31" #define UNICODE_BALINESE_LETTER_SA 0x1b32 #define UNITEXT_BALINESE_LETTER_SA L"\u1b32" #define UNICODE_BALINESE_LETTER_HA 0x1b33 #define UNITEXT_BALINESE_LETTER_HA L"\u1b33" #define UNICODE_BALINESE_SIGN_REREKAN 0x1b34 #define UNITEXT_BALINESE_SIGN_REREKAN L"\u1b34" #define UNICODE_BALINESE_VOWEL_SIGN_TEDUNG 0x1b35 #define UNITEXT_BALINESE_VOWEL_SIGN_TEDUNG L"\u1b35" #define UNICODE_BALINESE_VOWEL_SIGN_ULU 0x1b36 #define UNITEXT_BALINESE_VOWEL_SIGN_ULU L"\u1b36" #define UNICODE_BALINESE_VOWEL_SIGN_ULU_SARI 0x1b37 #define UNITEXT_BALINESE_VOWEL_SIGN_ULU_SARI L"\u1b37" #define UNICODE_BALINESE_VOWEL_SIGN_SUKU 0x1b38 #define UNITEXT_BALINESE_VOWEL_SIGN_SUKU L"\u1b38" #define UNICODE_BALINESE_VOWEL_SIGN_SUKU_ILUT 0x1b39 #define UNITEXT_BALINESE_VOWEL_SIGN_SUKU_ILUT L"\u1b39" #define UNICODE_BALINESE_VOWEL_SIGN_RA_REPA 0x1b3a #define UNITEXT_BALINESE_VOWEL_SIGN_RA_REPA L"\u1b3a" #define UNICODE_BALINESE_VOWEL_SIGN_RA_REPA_TEDUNG 0x1b3b #define UNITEXT_BALINESE_VOWEL_SIGN_RA_REPA_TEDUNG L"\u1b3b" #define UNICODE_BALINESE_VOWEL_SIGN_LA_LENGA 0x1b3c #define UNITEXT_BALINESE_VOWEL_SIGN_LA_LENGA L"\u1b3c" #define UNICODE_BALINESE_VOWEL_SIGN_LA_LENGA_TEDUNG 0x1b3d #define UNITEXT_BALINESE_VOWEL_SIGN_LA_LENGA_TEDUNG L"\u1b3d" #define UNICODE_BALINESE_VOWEL_SIGN_TALING 0x1b3e #define UNITEXT_BALINESE_VOWEL_SIGN_TALING L"\u1b3e" #define UNICODE_BALINESE_VOWEL_SIGN_TALING_REPA 0x1b3f #define UNITEXT_BALINESE_VOWEL_SIGN_TALING_REPA L"\u1b3f" #define UNICODE_BALINESE_VOWEL_SIGN_TALING_TEDUNG 0x1b40 #define UNITEXT_BALINESE_VOWEL_SIGN_TALING_TEDUNG L"\u1b40" #define UNICODE_BALINESE_VOWEL_SIGN_TALING_REPA_TEDUNG 0x1b41 #define UNITEXT_BALINESE_VOWEL_SIGN_TALING_REPA_TEDUNG L"\u1b41" #define UNICODE_BALINESE_VOWEL_SIGN_PEPET 0x1b42 #define UNITEXT_BALINESE_VOWEL_SIGN_PEPET L"\u1b42" #define UNICODE_BALINESE_VOWEL_SIGN_PEPET_TEDUNG 0x1b43 #define UNITEXT_BALINESE_VOWEL_SIGN_PEPET_TEDUNG L"\u1b43" #define UNICODE_BALINESE_ADEG_ADEG 0x1b44 #define UNITEXT_BALINESE_ADEG_ADEG L"\u1b44" #define UNICODE_BALINESE_LETTER_KAF_SASAK 0x1b45 #define UNITEXT_BALINESE_LETTER_KAF_SASAK L"\u1b45" #define UNICODE_BALINESE_LETTER_KHOT_SASAK 0x1b46 #define UNITEXT_BALINESE_LETTER_KHOT_SASAK L"\u1b46" #define UNICODE_BALINESE_LETTER_TZIR_SASAK 0x1b47 #define UNITEXT_BALINESE_LETTER_TZIR_SASAK L"\u1b47" #define UNICODE_BALINESE_LETTER_EF_SASAK 0x1b48 #define UNITEXT_BALINESE_LETTER_EF_SASAK L"\u1b48" #define UNICODE_BALINESE_LETTER_VE_SASAK 0x1b49 #define UNITEXT_BALINESE_LETTER_VE_SASAK L"\u1b49" #define UNICODE_BALINESE_LETTER_ZAL_SASAK 0x1b4a #define UNITEXT_BALINESE_LETTER_ZAL_SASAK L"\u1b4a" #define UNICODE_BALINESE_LETTER_ASYURA_SASAK 0x1b4b #define UNITEXT_BALINESE_LETTER_ASYURA_SASAK L"\u1b4b" #define UNICODE_BALINESE_DIGIT_ZERO 0x1b50 #define UNITEXT_BALINESE_DIGIT_ZERO L"\u1b50" #define UNICODE_BALINESE_DIGIT_ONE 0x1b51 #define UNITEXT_BALINESE_DIGIT_ONE L"\u1b51" #define UNICODE_BALINESE_DIGIT_TWO 0x1b52 #define UNITEXT_BALINESE_DIGIT_TWO L"\u1b52" #define UNICODE_BALINESE_DIGIT_THREE 0x1b53 #define UNITEXT_BALINESE_DIGIT_THREE L"\u1b53" #define UNICODE_BALINESE_DIGIT_FOUR 0x1b54 #define UNITEXT_BALINESE_DIGIT_FOUR L"\u1b54" #define UNICODE_BALINESE_DIGIT_FIVE 0x1b55 #define UNITEXT_BALINESE_DIGIT_FIVE L"\u1b55" #define UNICODE_BALINESE_DIGIT_SIX 0x1b56 #define UNITEXT_BALINESE_DIGIT_SIX L"\u1b56" #define UNICODE_BALINESE_DIGIT_SEVEN 0x1b57 #define UNITEXT_BALINESE_DIGIT_SEVEN L"\u1b57" #define UNICODE_BALINESE_DIGIT_EIGHT 0x1b58 #define UNITEXT_BALINESE_DIGIT_EIGHT L"\u1b58" #define UNICODE_BALINESE_DIGIT_NINE 0x1b59 #define UNITEXT_BALINESE_DIGIT_NINE L"\u1b59" #define UNICODE_BALINESE_PANTI 0x1b5a #define UNITEXT_BALINESE_PANTI L"\u1b5a" #define UNICODE_BALINESE_PAMADA 0x1b5b #define UNITEXT_BALINESE_PAMADA L"\u1b5b" #define UNICODE_BALINESE_WINDU 0x1b5c #define UNITEXT_BALINESE_WINDU L"\u1b5c" #define UNICODE_BALINESE_CARIK_PAMUNGKAH 0x1b5d #define UNITEXT_BALINESE_CARIK_PAMUNGKAH L"\u1b5d" #define UNICODE_BALINESE_CARIK_SIKI 0x1b5e #define UNITEXT_BALINESE_CARIK_SIKI L"\u1b5e" #define UNICODE_BALINESE_CARIK_PAREREN 0x1b5f #define UNITEXT_BALINESE_CARIK_PAREREN L"\u1b5f" #define UNICODE_BALINESE_PAMENENG 0x1b60 #define UNITEXT_BALINESE_PAMENENG L"\u1b60" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DONG 0x1b61 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DONG L"\u1b61" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DENG 0x1b62 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DENG L"\u1b62" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DUNG 0x1b63 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DUNG L"\u1b63" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DANG 0x1b64 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DANG L"\u1b64" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DANG_SURANG 0x1b65 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DANG_SURANG L"\u1b65" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DING 0x1b66 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DING L"\u1b66" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DAENG 0x1b67 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DAENG L"\u1b67" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DEUNG 0x1b68 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DEUNG L"\u1b68" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DAING 0x1b69 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DAING L"\u1b69" #define UNICODE_BALINESE_MUSICAL_SYMBOL_DANG_GEDE 0x1b6a #define UNITEXT_BALINESE_MUSICAL_SYMBOL_DANG_GEDE L"\u1b6a" #define UNICODE_BALINESE_MUSICAL_SYMBOL_COMBINING_TEGEH 0x1b6b #define UNITEXT_BALINESE_MUSICAL_SYMBOL_COMBINING_TEGEH L"\u1b6b" #define UNICODE_BALINESE_MUSICAL_SYMBOL_COMBINING_ENDEP 0x1b6c #define UNITEXT_BALINESE_MUSICAL_SYMBOL_COMBINING_ENDEP L"\u1b6c" #define UNICODE_BALINESE_MUSICAL_SYMBOL_COMBINING_KEMPUL 0x1b6d #define UNITEXT_BALINESE_MUSICAL_SYMBOL_COMBINING_KEMPUL L"\u1b6d" #define UNICODE_BALINESE_MUSICAL_SYMBOL_COMBINING_KEMPLI 0x1b6e #define UNITEXT_BALINESE_MUSICAL_SYMBOL_COMBINING_KEMPLI L"\u1b6e" #define UNICODE_BALINESE_MUSICAL_SYMBOL_COMBINING_JEGOGAN 0x1b6f #define UNITEXT_BALINESE_MUSICAL_SYMBOL_COMBINING_JEGOGAN L"\u1b6f" #define UNICODE_BALINESE_MUSICAL_SYMBOL_COMBINING_KEMPUL_WITH_JEGOGAN 0x1b70 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_COMBINING_KEMPUL_WITH_JEGOGAN L"\u1b70" #define UNICODE_BALINESE_MUSICAL_SYMBOL_COMBINING_KEMPLI_WITH_JEGOGAN 0x1b71 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_COMBINING_KEMPLI_WITH_JEGOGAN L"\u1b71" #define UNICODE_BALINESE_MUSICAL_SYMBOL_COMBINING_BENDE 0x1b72 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_COMBINING_BENDE L"\u1b72" #define UNICODE_BALINESE_MUSICAL_SYMBOL_COMBINING_GONG 0x1b73 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_COMBINING_GONG L"\u1b73" #define UNICODE_BALINESE_MUSICAL_SYMBOL_RIGHT_HAND_OPEN_DUG 0x1b74 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_RIGHT_HAND_OPEN_DUG L"\u1b74" #define UNICODE_BALINESE_MUSICAL_SYMBOL_RIGHT_HAND_OPEN_DAG 0x1b75 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_RIGHT_HAND_OPEN_DAG L"\u1b75" #define UNICODE_BALINESE_MUSICAL_SYMBOL_RIGHT_HAND_CLOSED_TUK 0x1b76 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_RIGHT_HAND_CLOSED_TUK L"\u1b76" #define UNICODE_BALINESE_MUSICAL_SYMBOL_RIGHT_HAND_CLOSED_TAK 0x1b77 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_RIGHT_HAND_CLOSED_TAK L"\u1b77" #define UNICODE_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_OPEN_PANG 0x1b78 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_OPEN_PANG L"\u1b78" #define UNICODE_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_OPEN_PUNG 0x1b79 #define UNITEXT_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_OPEN_PUNG L"\u1b79" #define UNICODE_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_CLOSED_PLAK 0x1b7a #define UNITEXT_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_CLOSED_PLAK L"\u1b7a" #define UNICODE_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_CLOSED_PLUK 0x1b7b #define UNITEXT_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_CLOSED_PLUK L"\u1b7b" #define UNICODE_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_OPEN_PING 0x1b7c #define UNITEXT_BALINESE_MUSICAL_SYMBOL_LEFT_HAND_OPEN_PING L"\u1b7c" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_A 0x1d00 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_A L"\u1d00" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_AE 0x1d01 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_AE L"\u1d01" #define UNICODE_LATIN_SMALL_LETTER_TURNED_AE 0x1d02 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_AE L"\u1d02" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_BARRED_B 0x1d03 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_BARRED_B L"\u1d03" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_C 0x1d04 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_C L"\u1d04" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_D 0x1d05 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_D L"\u1d05" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_ETH 0x1d06 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_ETH L"\u1d06" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_E 0x1d07 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_E L"\u1d07" #define UNICODE_LATIN_SMALL_LETTER_TURNED_OPEN_E 0x1d08 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_OPEN_E L"\u1d08" #define UNICODE_LATIN_SMALL_LETTER_TURNED_I 0x1d09 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_I L"\u1d09" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_J 0x1d0a #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_J L"\u1d0a" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_K 0x1d0b #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_K L"\u1d0b" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_L_WITH_STROKE 0x1d0c #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_L_WITH_STROKE L"\u1d0c" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_M 0x1d0d #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_M L"\u1d0d" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_REVERSED_N 0x1d0e #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_REVERSED_N L"\u1d0e" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_O 0x1d0f #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_O L"\u1d0f" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_OPEN_O 0x1d10 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_OPEN_O L"\u1d10" #define UNICODE_LATIN_SMALL_LETTER_SIDEWAYS_O 0x1d11 #define UNITEXT_LATIN_SMALL_LETTER_SIDEWAYS_O L"\u1d11" #define UNICODE_LATIN_SMALL_LETTER_SIDEWAYS_OPEN_O 0x1d12 #define UNITEXT_LATIN_SMALL_LETTER_SIDEWAYS_OPEN_O L"\u1d12" #define UNICODE_LATIN_SMALL_LETTER_SIDEWAYS_O_WITH_STROKE 0x1d13 #define UNITEXT_LATIN_SMALL_LETTER_SIDEWAYS_O_WITH_STROKE L"\u1d13" #define UNICODE_LATIN_SMALL_LETTER_TURNED_OE 0x1d14 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_OE L"\u1d14" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_OU 0x1d15 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_OU L"\u1d15" #define UNICODE_LATIN_SMALL_LETTER_TOP_HALF_O 0x1d16 #define UNITEXT_LATIN_SMALL_LETTER_TOP_HALF_O L"\u1d16" #define UNICODE_LATIN_SMALL_LETTER_BOTTOM_HALF_O 0x1d17 #define UNITEXT_LATIN_SMALL_LETTER_BOTTOM_HALF_O L"\u1d17" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_P 0x1d18 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_P L"\u1d18" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_REVERSED_R 0x1d19 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_REVERSED_R L"\u1d19" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_TURNED_R 0x1d1a #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_TURNED_R L"\u1d1a" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_T 0x1d1b #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_T L"\u1d1b" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_U 0x1d1c #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_U L"\u1d1c" #define UNICODE_LATIN_SMALL_LETTER_SIDEWAYS_U 0x1d1d #define UNITEXT_LATIN_SMALL_LETTER_SIDEWAYS_U L"\u1d1d" #define UNICODE_LATIN_SMALL_LETTER_SIDEWAYS_DIAERESIZED_U 0x1d1e #define UNITEXT_LATIN_SMALL_LETTER_SIDEWAYS_DIAERESIZED_U L"\u1d1e" #define UNICODE_LATIN_SMALL_LETTER_SIDEWAYS_TURNED_M 0x1d1f #define UNITEXT_LATIN_SMALL_LETTER_SIDEWAYS_TURNED_M L"\u1d1f" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_V 0x1d20 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_V L"\u1d20" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_W 0x1d21 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_W L"\u1d21" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_Z 0x1d22 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_Z L"\u1d22" #define UNICODE_LATIN_LETTER_SMALL_CAPITAL_EZH 0x1d23 #define UNITEXT_LATIN_LETTER_SMALL_CAPITAL_EZH L"\u1d23" #define UNICODE_LATIN_LETTER_VOICED_LARYNGEAL_SPIRANT 0x1d24 #define UNITEXT_LATIN_LETTER_VOICED_LARYNGEAL_SPIRANT L"\u1d24" #define UNICODE_LATIN_LETTER_AIN 0x1d25 #define UNITEXT_LATIN_LETTER_AIN L"\u1d25" #define UNICODE_GREEK_LETTER_SMALL_CAPITAL_GAMMA 0x1d26 #define UNITEXT_GREEK_LETTER_SMALL_CAPITAL_GAMMA L"\u1d26" #define UNICODE_GREEK_LETTER_SMALL_CAPITAL_LAMDA 0x1d27 #define UNITEXT_GREEK_LETTER_SMALL_CAPITAL_LAMDA L"\u1d27" #define UNICODE_GREEK_LETTER_SMALL_CAPITAL_PI 0x1d28 #define UNITEXT_GREEK_LETTER_SMALL_CAPITAL_PI L"\u1d28" #define UNICODE_GREEK_LETTER_SMALL_CAPITAL_RHO 0x1d29 #define UNITEXT_GREEK_LETTER_SMALL_CAPITAL_RHO L"\u1d29" #define UNICODE_GREEK_LETTER_SMALL_CAPITAL_PSI 0x1d2a #define UNITEXT_GREEK_LETTER_SMALL_CAPITAL_PSI L"\u1d2a" #define UNICODE_CYRILLIC_LETTER_SMALL_CAPITAL_EL 0x1d2b #define UNITEXT_CYRILLIC_LETTER_SMALL_CAPITAL_EL L"\u1d2b" #define UNICODE_MODIFIER_LETTER_CAPITAL_A 0x1d2c #define UNITEXT_MODIFIER_LETTER_CAPITAL_A L"\u1d2c" #define UNICODE_MODIFIER_LETTER_CAPITAL_AE 0x1d2d #define UNITEXT_MODIFIER_LETTER_CAPITAL_AE L"\u1d2d" #define UNICODE_MODIFIER_LETTER_CAPITAL_B 0x1d2e #define UNITEXT_MODIFIER_LETTER_CAPITAL_B L"\u1d2e" #define UNICODE_MODIFIER_LETTER_CAPITAL_BARRED_B 0x1d2f #define UNITEXT_MODIFIER_LETTER_CAPITAL_BARRED_B L"\u1d2f" #define UNICODE_MODIFIER_LETTER_CAPITAL_D 0x1d30 #define UNITEXT_MODIFIER_LETTER_CAPITAL_D L"\u1d30" #define UNICODE_MODIFIER_LETTER_CAPITAL_E 0x1d31 #define UNITEXT_MODIFIER_LETTER_CAPITAL_E L"\u1d31" #define UNICODE_MODIFIER_LETTER_CAPITAL_REVERSED_E 0x1d32 #define UNITEXT_MODIFIER_LETTER_CAPITAL_REVERSED_E L"\u1d32" #define UNICODE_MODIFIER_LETTER_CAPITAL_G 0x1d33 #define UNITEXT_MODIFIER_LETTER_CAPITAL_G L"\u1d33" #define UNICODE_MODIFIER_LETTER_CAPITAL_H 0x1d34 #define UNITEXT_MODIFIER_LETTER_CAPITAL_H L"\u1d34" #define UNICODE_MODIFIER_LETTER_CAPITAL_I 0x1d35 #define UNITEXT_MODIFIER_LETTER_CAPITAL_I L"\u1d35" #define UNICODE_MODIFIER_LETTER_CAPITAL_J 0x1d36 #define UNITEXT_MODIFIER_LETTER_CAPITAL_J L"\u1d36" #define UNICODE_MODIFIER_LETTER_CAPITAL_K 0x1d37 #define UNITEXT_MODIFIER_LETTER_CAPITAL_K L"\u1d37" #define UNICODE_MODIFIER_LETTER_CAPITAL_L 0x1d38 #define UNITEXT_MODIFIER_LETTER_CAPITAL_L L"\u1d38" #define UNICODE_MODIFIER_LETTER_CAPITAL_M 0x1d39 #define UNITEXT_MODIFIER_LETTER_CAPITAL_M L"\u1d39" #define UNICODE_MODIFIER_LETTER_CAPITAL_N 0x1d3a #define UNITEXT_MODIFIER_LETTER_CAPITAL_N L"\u1d3a" #define UNICODE_MODIFIER_LETTER_CAPITAL_REVERSED_N 0x1d3b #define UNITEXT_MODIFIER_LETTER_CAPITAL_REVERSED_N L"\u1d3b" #define UNICODE_MODIFIER_LETTER_CAPITAL_O 0x1d3c #define UNITEXT_MODIFIER_LETTER_CAPITAL_O L"\u1d3c" #define UNICODE_MODIFIER_LETTER_CAPITAL_OU 0x1d3d #define UNITEXT_MODIFIER_LETTER_CAPITAL_OU L"\u1d3d" #define UNICODE_MODIFIER_LETTER_CAPITAL_P 0x1d3e #define UNITEXT_MODIFIER_LETTER_CAPITAL_P L"\u1d3e" #define UNICODE_MODIFIER_LETTER_CAPITAL_R 0x1d3f #define UNITEXT_MODIFIER_LETTER_CAPITAL_R L"\u1d3f" #define UNICODE_MODIFIER_LETTER_CAPITAL_T 0x1d40 #define UNITEXT_MODIFIER_LETTER_CAPITAL_T L"\u1d40" #define UNICODE_MODIFIER_LETTER_CAPITAL_U 0x1d41 #define UNITEXT_MODIFIER_LETTER_CAPITAL_U L"\u1d41" #define UNICODE_MODIFIER_LETTER_CAPITAL_W 0x1d42 #define UNITEXT_MODIFIER_LETTER_CAPITAL_W L"\u1d42" #define UNICODE_MODIFIER_LETTER_SMALL_A 0x1d43 #define UNITEXT_MODIFIER_LETTER_SMALL_A L"\u1d43" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_A 0x1d44 #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_A L"\u1d44" #define UNICODE_MODIFIER_LETTER_SMALL_ALPHA 0x1d45 #define UNITEXT_MODIFIER_LETTER_SMALL_ALPHA L"\u1d45" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_AE 0x1d46 #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_AE L"\u1d46" #define UNICODE_MODIFIER_LETTER_SMALL_B 0x1d47 #define UNITEXT_MODIFIER_LETTER_SMALL_B L"\u1d47" #define UNICODE_MODIFIER_LETTER_SMALL_D 0x1d48 #define UNITEXT_MODIFIER_LETTER_SMALL_D L"\u1d48" #define UNICODE_MODIFIER_LETTER_SMALL_E 0x1d49 #define UNITEXT_MODIFIER_LETTER_SMALL_E L"\u1d49" #define UNICODE_MODIFIER_LETTER_SMALL_SCHWA 0x1d4a #define UNITEXT_MODIFIER_LETTER_SMALL_SCHWA L"\u1d4a" #define UNICODE_MODIFIER_LETTER_SMALL_OPEN_E 0x1d4b #define UNITEXT_MODIFIER_LETTER_SMALL_OPEN_E L"\u1d4b" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_OPEN_E 0x1d4c #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_OPEN_E L"\u1d4c" #define UNICODE_MODIFIER_LETTER_SMALL_G 0x1d4d #define UNITEXT_MODIFIER_LETTER_SMALL_G L"\u1d4d" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_I 0x1d4e #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_I L"\u1d4e" #define UNICODE_MODIFIER_LETTER_SMALL_K 0x1d4f #define UNITEXT_MODIFIER_LETTER_SMALL_K L"\u1d4f" #define UNICODE_MODIFIER_LETTER_SMALL_M 0x1d50 #define UNITEXT_MODIFIER_LETTER_SMALL_M L"\u1d50" #define UNICODE_MODIFIER_LETTER_SMALL_ENG 0x1d51 #define UNITEXT_MODIFIER_LETTER_SMALL_ENG L"\u1d51" #define UNICODE_MODIFIER_LETTER_SMALL_O 0x1d52 #define UNITEXT_MODIFIER_LETTER_SMALL_O L"\u1d52" #define UNICODE_MODIFIER_LETTER_SMALL_OPEN_O 0x1d53 #define UNITEXT_MODIFIER_LETTER_SMALL_OPEN_O L"\u1d53" #define UNICODE_MODIFIER_LETTER_SMALL_TOP_HALF_O 0x1d54 #define UNITEXT_MODIFIER_LETTER_SMALL_TOP_HALF_O L"\u1d54" #define UNICODE_MODIFIER_LETTER_SMALL_BOTTOM_HALF_O 0x1d55 #define UNITEXT_MODIFIER_LETTER_SMALL_BOTTOM_HALF_O L"\u1d55" #define UNICODE_MODIFIER_LETTER_SMALL_P 0x1d56 #define UNITEXT_MODIFIER_LETTER_SMALL_P L"\u1d56" #define UNICODE_MODIFIER_LETTER_SMALL_T 0x1d57 #define UNITEXT_MODIFIER_LETTER_SMALL_T L"\u1d57" #define UNICODE_MODIFIER_LETTER_SMALL_U 0x1d58 #define UNITEXT_MODIFIER_LETTER_SMALL_U L"\u1d58" #define UNICODE_MODIFIER_LETTER_SMALL_SIDEWAYS_U 0x1d59 #define UNITEXT_MODIFIER_LETTER_SMALL_SIDEWAYS_U L"\u1d59" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_M 0x1d5a #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_M L"\u1d5a" #define UNICODE_MODIFIER_LETTER_SMALL_V 0x1d5b #define UNITEXT_MODIFIER_LETTER_SMALL_V L"\u1d5b" #define UNICODE_MODIFIER_LETTER_SMALL_AIN 0x1d5c #define UNITEXT_MODIFIER_LETTER_SMALL_AIN L"\u1d5c" #define UNICODE_MODIFIER_LETTER_SMALL_BETA 0x1d5d #define UNITEXT_MODIFIER_LETTER_SMALL_BETA L"\u1d5d" #define UNICODE_MODIFIER_LETTER_SMALL_GREEK_GAMMA 0x1d5e #define UNITEXT_MODIFIER_LETTER_SMALL_GREEK_GAMMA L"\u1d5e" #define UNICODE_MODIFIER_LETTER_SMALL_DELTA 0x1d5f #define UNITEXT_MODIFIER_LETTER_SMALL_DELTA L"\u1d5f" #define UNICODE_MODIFIER_LETTER_SMALL_GREEK_PHI 0x1d60 #define UNITEXT_MODIFIER_LETTER_SMALL_GREEK_PHI L"\u1d60" #define UNICODE_MODIFIER_LETTER_SMALL_CHI 0x1d61 #define UNITEXT_MODIFIER_LETTER_SMALL_CHI L"\u1d61" #define UNICODE_LATIN_SUBSCRIPT_SMALL_LETTER_I 0x1d62 #define UNITEXT_LATIN_SUBSCRIPT_SMALL_LETTER_I L"\u1d62" #define UNICODE_LATIN_SUBSCRIPT_SMALL_LETTER_R 0x1d63 #define UNITEXT_LATIN_SUBSCRIPT_SMALL_LETTER_R L"\u1d63" #define UNICODE_LATIN_SUBSCRIPT_SMALL_LETTER_U 0x1d64 #define UNITEXT_LATIN_SUBSCRIPT_SMALL_LETTER_U L"\u1d64" #define UNICODE_LATIN_SUBSCRIPT_SMALL_LETTER_V 0x1d65 #define UNITEXT_LATIN_SUBSCRIPT_SMALL_LETTER_V L"\u1d65" #define UNICODE_GREEK_SUBSCRIPT_SMALL_LETTER_BETA 0x1d66 #define UNITEXT_GREEK_SUBSCRIPT_SMALL_LETTER_BETA L"\u1d66" #define UNICODE_GREEK_SUBSCRIPT_SMALL_LETTER_GAMMA 0x1d67 #define UNITEXT_GREEK_SUBSCRIPT_SMALL_LETTER_GAMMA L"\u1d67" #define UNICODE_GREEK_SUBSCRIPT_SMALL_LETTER_RHO 0x1d68 #define UNITEXT_GREEK_SUBSCRIPT_SMALL_LETTER_RHO L"\u1d68" #define UNICODE_GREEK_SUBSCRIPT_SMALL_LETTER_PHI 0x1d69 #define UNITEXT_GREEK_SUBSCRIPT_SMALL_LETTER_PHI L"\u1d69" #define UNICODE_GREEK_SUBSCRIPT_SMALL_LETTER_CHI 0x1d6a #define UNITEXT_GREEK_SUBSCRIPT_SMALL_LETTER_CHI L"\u1d6a" #define UNICODE_LATIN_SMALL_LETTER_UE 0x1d6b #define UNITEXT_LATIN_SMALL_LETTER_UE L"\u1d6b" #define UNICODE_LATIN_SMALL_LETTER_B_WITH_MIDDLE_TILDE 0x1d6c #define UNITEXT_LATIN_SMALL_LETTER_B_WITH_MIDDLE_TILDE L"\u1d6c" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_MIDDLE_TILDE 0x1d6d #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_MIDDLE_TILDE L"\u1d6d" #define UNICODE_LATIN_SMALL_LETTER_F_WITH_MIDDLE_TILDE 0x1d6e #define UNITEXT_LATIN_SMALL_LETTER_F_WITH_MIDDLE_TILDE L"\u1d6e" #define UNICODE_LATIN_SMALL_LETTER_M_WITH_MIDDLE_TILDE 0x1d6f #define UNITEXT_LATIN_SMALL_LETTER_M_WITH_MIDDLE_TILDE L"\u1d6f" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_MIDDLE_TILDE 0x1d70 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_MIDDLE_TILDE L"\u1d70" #define UNICODE_LATIN_SMALL_LETTER_P_WITH_MIDDLE_TILDE 0x1d71 #define UNITEXT_LATIN_SMALL_LETTER_P_WITH_MIDDLE_TILDE L"\u1d71" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_MIDDLE_TILDE 0x1d72 #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_MIDDLE_TILDE L"\u1d72" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_FISHHOOK_AND_MIDDLE_TILDE 0x1d73 #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_FISHHOOK_AND_MIDDLE_TILDE L"\u1d73" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_MIDDLE_TILDE 0x1d74 #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_MIDDLE_TILDE L"\u1d74" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_MIDDLE_TILDE 0x1d75 #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_MIDDLE_TILDE L"\u1d75" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_MIDDLE_TILDE 0x1d76 #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_MIDDLE_TILDE L"\u1d76" #define UNICODE_LATIN_SMALL_LETTER_TURNED_G 0x1d77 #define UNITEXT_LATIN_SMALL_LETTER_TURNED_G L"\u1d77" #define UNICODE_MODIFIER_LETTER_CYRILLIC_EN 0x1d78 #define UNITEXT_MODIFIER_LETTER_CYRILLIC_EN L"\u1d78" #define UNICODE_LATIN_SMALL_LETTER_INSULAR_G 0x1d79 #define UNITEXT_LATIN_SMALL_LETTER_INSULAR_G L"\u1d79" #define UNICODE_LATIN_SMALL_LETTER_TH_WITH_STRIKETHROUGH 0x1d7a #define UNITEXT_LATIN_SMALL_LETTER_TH_WITH_STRIKETHROUGH L"\u1d7a" #define UNICODE_LATIN_SMALL_CAPITAL_LETTER_I_WITH_STROKE 0x1d7b #define UNITEXT_LATIN_SMALL_CAPITAL_LETTER_I_WITH_STROKE L"\u1d7b" #define UNICODE_LATIN_SMALL_LETTER_IOTA_WITH_STROKE 0x1d7c #define UNITEXT_LATIN_SMALL_LETTER_IOTA_WITH_STROKE L"\u1d7c" #define UNICODE_LATIN_SMALL_LETTER_P_WITH_STROKE 0x1d7d #define UNITEXT_LATIN_SMALL_LETTER_P_WITH_STROKE L"\u1d7d" #define UNICODE_LATIN_SMALL_CAPITAL_LETTER_U_WITH_STROKE 0x1d7e #define UNITEXT_LATIN_SMALL_CAPITAL_LETTER_U_WITH_STROKE L"\u1d7e" #define UNICODE_LATIN_SMALL_LETTER_UPSILON_WITH_STROKE 0x1d7f #define UNITEXT_LATIN_SMALL_LETTER_UPSILON_WITH_STROKE L"\u1d7f" #define UNICODE_LATIN_SMALL_LETTER_B_WITH_PALATAL_HOOK 0x1d80 #define UNITEXT_LATIN_SMALL_LETTER_B_WITH_PALATAL_HOOK L"\u1d80" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_PALATAL_HOOK 0x1d81 #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_PALATAL_HOOK L"\u1d81" #define UNICODE_LATIN_SMALL_LETTER_F_WITH_PALATAL_HOOK 0x1d82 #define UNITEXT_LATIN_SMALL_LETTER_F_WITH_PALATAL_HOOK L"\u1d82" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_PALATAL_HOOK 0x1d83 #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_PALATAL_HOOK L"\u1d83" #define UNICODE_LATIN_SMALL_LETTER_K_WITH_PALATAL_HOOK 0x1d84 #define UNITEXT_LATIN_SMALL_LETTER_K_WITH_PALATAL_HOOK L"\u1d84" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_PALATAL_HOOK 0x1d85 #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_PALATAL_HOOK L"\u1d85" #define UNICODE_LATIN_SMALL_LETTER_M_WITH_PALATAL_HOOK 0x1d86 #define UNITEXT_LATIN_SMALL_LETTER_M_WITH_PALATAL_HOOK L"\u1d86" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_PALATAL_HOOK 0x1d87 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_PALATAL_HOOK L"\u1d87" #define UNICODE_LATIN_SMALL_LETTER_P_WITH_PALATAL_HOOK 0x1d88 #define UNITEXT_LATIN_SMALL_LETTER_P_WITH_PALATAL_HOOK L"\u1d88" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_PALATAL_HOOK 0x1d89 #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_PALATAL_HOOK L"\u1d89" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_PALATAL_HOOK 0x1d8a #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_PALATAL_HOOK L"\u1d8a" #define UNICODE_LATIN_SMALL_LETTER_ESH_WITH_PALATAL_HOOK 0x1d8b #define UNITEXT_LATIN_SMALL_LETTER_ESH_WITH_PALATAL_HOOK L"\u1d8b" #define UNICODE_LATIN_SMALL_LETTER_V_WITH_PALATAL_HOOK 0x1d8c #define UNITEXT_LATIN_SMALL_LETTER_V_WITH_PALATAL_HOOK L"\u1d8c" #define UNICODE_LATIN_SMALL_LETTER_X_WITH_PALATAL_HOOK 0x1d8d #define UNITEXT_LATIN_SMALL_LETTER_X_WITH_PALATAL_HOOK L"\u1d8d" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_PALATAL_HOOK 0x1d8e #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_PALATAL_HOOK L"\u1d8e" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_RETROFLEX_HOOK 0x1d8f #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_RETROFLEX_HOOK L"\u1d8f" #define UNICODE_LATIN_SMALL_LETTER_ALPHA_WITH_RETROFLEX_HOOK 0x1d90 #define UNITEXT_LATIN_SMALL_LETTER_ALPHA_WITH_RETROFLEX_HOOK L"\u1d90" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_HOOK_AND_TAIL 0x1d91 #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_HOOK_AND_TAIL L"\u1d91" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_RETROFLEX_HOOK 0x1d92 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_RETROFLEX_HOOK L"\u1d92" #define UNICODE_LATIN_SMALL_LETTER_OPEN_E_WITH_RETROFLEX_HOOK 0x1d93 #define UNITEXT_LATIN_SMALL_LETTER_OPEN_E_WITH_RETROFLEX_HOOK L"\u1d93" #define UNICODE_LATIN_SMALL_LETTER_REVERSED_OPEN_E_WITH_RETROFLEX_HOOK 0x1d94 #define UNITEXT_LATIN_SMALL_LETTER_REVERSED_OPEN_E_WITH_RETROFLEX_HOOK L"\u1d94" #define UNICODE_LATIN_SMALL_LETTER_SCHWA_WITH_RETROFLEX_HOOK 0x1d95 #define UNITEXT_LATIN_SMALL_LETTER_SCHWA_WITH_RETROFLEX_HOOK L"\u1d95" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_RETROFLEX_HOOK 0x1d96 #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_RETROFLEX_HOOK L"\u1d96" #define UNICODE_LATIN_SMALL_LETTER_OPEN_O_WITH_RETROFLEX_HOOK 0x1d97 #define UNITEXT_LATIN_SMALL_LETTER_OPEN_O_WITH_RETROFLEX_HOOK L"\u1d97" #define UNICODE_LATIN_SMALL_LETTER_ESH_WITH_RETROFLEX_HOOK 0x1d98 #define UNITEXT_LATIN_SMALL_LETTER_ESH_WITH_RETROFLEX_HOOK L"\u1d98" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_RETROFLEX_HOOK 0x1d99 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_RETROFLEX_HOOK L"\u1d99" #define UNICODE_LATIN_SMALL_LETTER_EZH_WITH_RETROFLEX_HOOK 0x1d9a #define UNITEXT_LATIN_SMALL_LETTER_EZH_WITH_RETROFLEX_HOOK L"\u1d9a" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_ALPHA 0x1d9b #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_ALPHA L"\u1d9b" #define UNICODE_MODIFIER_LETTER_SMALL_C 0x1d9c #define UNITEXT_MODIFIER_LETTER_SMALL_C L"\u1d9c" #define UNICODE_MODIFIER_LETTER_SMALL_C_WITH_CURL 0x1d9d #define UNITEXT_MODIFIER_LETTER_SMALL_C_WITH_CURL L"\u1d9d" #define UNICODE_MODIFIER_LETTER_SMALL_ETH 0x1d9e #define UNITEXT_MODIFIER_LETTER_SMALL_ETH L"\u1d9e" #define UNICODE_MODIFIER_LETTER_SMALL_REVERSED_OPEN_E 0x1d9f #define UNITEXT_MODIFIER_LETTER_SMALL_REVERSED_OPEN_E L"\u1d9f" #define UNICODE_MODIFIER_LETTER_SMALL_F 0x1da0 #define UNITEXT_MODIFIER_LETTER_SMALL_F L"\u1da0" #define UNICODE_MODIFIER_LETTER_SMALL_DOTLESS_J_WITH_STROKE 0x1da1 #define UNITEXT_MODIFIER_LETTER_SMALL_DOTLESS_J_WITH_STROKE L"\u1da1" #define UNICODE_MODIFIER_LETTER_SMALL_SCRIPT_G 0x1da2 #define UNITEXT_MODIFIER_LETTER_SMALL_SCRIPT_G L"\u1da2" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_H 0x1da3 #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_H L"\u1da3" #define UNICODE_MODIFIER_LETTER_SMALL_I_WITH_STROKE 0x1da4 #define UNITEXT_MODIFIER_LETTER_SMALL_I_WITH_STROKE L"\u1da4" #define UNICODE_MODIFIER_LETTER_SMALL_IOTA 0x1da5 #define UNITEXT_MODIFIER_LETTER_SMALL_IOTA L"\u1da5" #define UNICODE_MODIFIER_LETTER_SMALL_CAPITAL_I 0x1da6 #define UNITEXT_MODIFIER_LETTER_SMALL_CAPITAL_I L"\u1da6" #define UNICODE_MODIFIER_LETTER_SMALL_CAPITAL_I_WITH_STROKE 0x1da7 #define UNITEXT_MODIFIER_LETTER_SMALL_CAPITAL_I_WITH_STROKE L"\u1da7" #define UNICODE_MODIFIER_LETTER_SMALL_J_WITH_CROSSED_TAIL 0x1da8 #define UNITEXT_MODIFIER_LETTER_SMALL_J_WITH_CROSSED_TAIL L"\u1da8" #define UNICODE_MODIFIER_LETTER_SMALL_L_WITH_RETROFLEX_HOOK 0x1da9 #define UNITEXT_MODIFIER_LETTER_SMALL_L_WITH_RETROFLEX_HOOK L"\u1da9" #define UNICODE_MODIFIER_LETTER_SMALL_L_WITH_PALATAL_HOOK 0x1daa #define UNITEXT_MODIFIER_LETTER_SMALL_L_WITH_PALATAL_HOOK L"\u1daa" #define UNICODE_MODIFIER_LETTER_SMALL_CAPITAL_L 0x1dab #define UNITEXT_MODIFIER_LETTER_SMALL_CAPITAL_L L"\u1dab" #define UNICODE_MODIFIER_LETTER_SMALL_M_WITH_HOOK 0x1dac #define UNITEXT_MODIFIER_LETTER_SMALL_M_WITH_HOOK L"\u1dac" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_M_WITH_LONG_LEG 0x1dad #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_M_WITH_LONG_LEG L"\u1dad" #define UNICODE_MODIFIER_LETTER_SMALL_N_WITH_LEFT_HOOK 0x1dae #define UNITEXT_MODIFIER_LETTER_SMALL_N_WITH_LEFT_HOOK L"\u1dae" #define UNICODE_MODIFIER_LETTER_SMALL_N_WITH_RETROFLEX_HOOK 0x1daf #define UNITEXT_MODIFIER_LETTER_SMALL_N_WITH_RETROFLEX_HOOK L"\u1daf" #define UNICODE_MODIFIER_LETTER_SMALL_CAPITAL_N 0x1db0 #define UNITEXT_MODIFIER_LETTER_SMALL_CAPITAL_N L"\u1db0" #define UNICODE_MODIFIER_LETTER_SMALL_BARRED_O 0x1db1 #define UNITEXT_MODIFIER_LETTER_SMALL_BARRED_O L"\u1db1" #define UNICODE_MODIFIER_LETTER_SMALL_PHI 0x1db2 #define UNITEXT_MODIFIER_LETTER_SMALL_PHI L"\u1db2" #define UNICODE_MODIFIER_LETTER_SMALL_S_WITH_HOOK 0x1db3 #define UNITEXT_MODIFIER_LETTER_SMALL_S_WITH_HOOK L"\u1db3" #define UNICODE_MODIFIER_LETTER_SMALL_ESH 0x1db4 #define UNITEXT_MODIFIER_LETTER_SMALL_ESH L"\u1db4" #define UNICODE_MODIFIER_LETTER_SMALL_T_WITH_PALATAL_HOOK 0x1db5 #define UNITEXT_MODIFIER_LETTER_SMALL_T_WITH_PALATAL_HOOK L"\u1db5" #define UNICODE_MODIFIER_LETTER_SMALL_U_BAR 0x1db6 #define UNITEXT_MODIFIER_LETTER_SMALL_U_BAR L"\u1db6" #define UNICODE_MODIFIER_LETTER_SMALL_UPSILON 0x1db7 #define UNITEXT_MODIFIER_LETTER_SMALL_UPSILON L"\u1db7" #define UNICODE_MODIFIER_LETTER_SMALL_CAPITAL_U 0x1db8 #define UNITEXT_MODIFIER_LETTER_SMALL_CAPITAL_U L"\u1db8" #define UNICODE_MODIFIER_LETTER_SMALL_V_WITH_HOOK 0x1db9 #define UNITEXT_MODIFIER_LETTER_SMALL_V_WITH_HOOK L"\u1db9" #define UNICODE_MODIFIER_LETTER_SMALL_TURNED_V 0x1dba #define UNITEXT_MODIFIER_LETTER_SMALL_TURNED_V L"\u1dba" #define UNICODE_MODIFIER_LETTER_SMALL_Z 0x1dbb #define UNITEXT_MODIFIER_LETTER_SMALL_Z L"\u1dbb" #define UNICODE_MODIFIER_LETTER_SMALL_Z_WITH_RETROFLEX_HOOK 0x1dbc #define UNITEXT_MODIFIER_LETTER_SMALL_Z_WITH_RETROFLEX_HOOK L"\u1dbc" #define UNICODE_MODIFIER_LETTER_SMALL_Z_WITH_CURL 0x1dbd #define UNITEXT_MODIFIER_LETTER_SMALL_Z_WITH_CURL L"\u1dbd" #define UNICODE_MODIFIER_LETTER_SMALL_EZH 0x1dbe #define UNITEXT_MODIFIER_LETTER_SMALL_EZH L"\u1dbe" #define UNICODE_MODIFIER_LETTER_SMALL_THETA 0x1dbf #define UNITEXT_MODIFIER_LETTER_SMALL_THETA L"\u1dbf" #define UNICODE_COMBINING_DOTTED_GRAVE_ACCENT 0x1dc0 #define UNITEXT_COMBINING_DOTTED_GRAVE_ACCENT L"\u1dc0" #define UNICODE_COMBINING_DOTTED_ACUTE_ACCENT 0x1dc1 #define UNITEXT_COMBINING_DOTTED_ACUTE_ACCENT L"\u1dc1" #define UNICODE_COMBINING_SNAKE_BELOW 0x1dc2 #define UNITEXT_COMBINING_SNAKE_BELOW L"\u1dc2" #define UNICODE_COMBINING_SUSPENSION_MARK 0x1dc3 #define UNITEXT_COMBINING_SUSPENSION_MARK L"\u1dc3" #define UNICODE_COMBINING_MACRON_ACUTE 0x1dc4 #define UNITEXT_COMBINING_MACRON_ACUTE L"\u1dc4" #define UNICODE_COMBINING_GRAVE_MACRON 0x1dc5 #define UNITEXT_COMBINING_GRAVE_MACRON L"\u1dc5" #define UNICODE_COMBINING_MACRON_GRAVE 0x1dc6 #define UNITEXT_COMBINING_MACRON_GRAVE L"\u1dc6" #define UNICODE_COMBINING_ACUTE_MACRON 0x1dc7 #define UNITEXT_COMBINING_ACUTE_MACRON L"\u1dc7" #define UNICODE_COMBINING_GRAVE_ACUTE_GRAVE 0x1dc8 #define UNITEXT_COMBINING_GRAVE_ACUTE_GRAVE L"\u1dc8" #define UNICODE_COMBINING_ACUTE_GRAVE_ACUTE 0x1dc9 #define UNITEXT_COMBINING_ACUTE_GRAVE_ACUTE L"\u1dc9" #define UNICODE_COMBINING_LATIN_SMALL_LETTER_R_BELOW 0x1dca #define UNITEXT_COMBINING_LATIN_SMALL_LETTER_R_BELOW L"\u1dca" #define UNICODE_COMBINING_LEFT_ARROWHEAD_ABOVE 0x1dfe #define UNITEXT_COMBINING_LEFT_ARROWHEAD_ABOVE L"\u1dfe" #define UNICODE_COMBINING_RIGHT_ARROWHEAD_AND_DOWN_ARROWHEAD_BELOW 0x1dff #define UNITEXT_COMBINING_RIGHT_ARROWHEAD_AND_DOWN_ARROWHEAD_BELOW L"\u1dff" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_RING_BELOW 0x1e00 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_RING_BELOW L"\u1e00" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_RING_BELOW 0x1e01 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_RING_BELOW L"\u1e01" #define UNICODE_LATIN_CAPITAL_LETTER_B_WITH_DOT_ABOVE 0x1e02 #define UNITEXT_LATIN_CAPITAL_LETTER_B_WITH_DOT_ABOVE L"\u1e02" #define UNICODE_LATIN_SMALL_LETTER_B_WITH_DOT_ABOVE 0x1e03 #define UNITEXT_LATIN_SMALL_LETTER_B_WITH_DOT_ABOVE L"\u1e03" #define UNICODE_LATIN_CAPITAL_LETTER_B_WITH_DOT_BELOW 0x1e04 #define UNITEXT_LATIN_CAPITAL_LETTER_B_WITH_DOT_BELOW L"\u1e04" #define UNICODE_LATIN_SMALL_LETTER_B_WITH_DOT_BELOW 0x1e05 #define UNITEXT_LATIN_SMALL_LETTER_B_WITH_DOT_BELOW L"\u1e05" #define UNICODE_LATIN_CAPITAL_LETTER_B_WITH_LINE_BELOW 0x1e06 #define UNITEXT_LATIN_CAPITAL_LETTER_B_WITH_LINE_BELOW L"\u1e06" #define UNICODE_LATIN_SMALL_LETTER_B_WITH_LINE_BELOW 0x1e07 #define UNITEXT_LATIN_SMALL_LETTER_B_WITH_LINE_BELOW L"\u1e07" #define UNICODE_LATIN_CAPITAL_LETTER_C_WITH_CEDILLA_AND_ACUTE 0x1e08 #define UNITEXT_LATIN_CAPITAL_LETTER_C_WITH_CEDILLA_AND_ACUTE L"\u1e08" #define UNICODE_LATIN_SMALL_LETTER_C_WITH_CEDILLA_AND_ACUTE 0x1e09 #define UNITEXT_LATIN_SMALL_LETTER_C_WITH_CEDILLA_AND_ACUTE L"\u1e09" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_DOT_ABOVE 0x1e0a #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_DOT_ABOVE L"\u1e0a" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_DOT_ABOVE 0x1e0b #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_DOT_ABOVE L"\u1e0b" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_DOT_BELOW 0x1e0c #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_DOT_BELOW L"\u1e0c" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_DOT_BELOW 0x1e0d #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_DOT_BELOW L"\u1e0d" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_LINE_BELOW 0x1e0e #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_LINE_BELOW L"\u1e0e" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_LINE_BELOW 0x1e0f #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_LINE_BELOW L"\u1e0f" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_CEDILLA 0x1e10 #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_CEDILLA L"\u1e10" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_CEDILLA 0x1e11 #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_CEDILLA L"\u1e11" #define UNICODE_LATIN_CAPITAL_LETTER_D_WITH_CIRCUMFLEX_BELOW 0x1e12 #define UNITEXT_LATIN_CAPITAL_LETTER_D_WITH_CIRCUMFLEX_BELOW L"\u1e12" #define UNICODE_LATIN_SMALL_LETTER_D_WITH_CIRCUMFLEX_BELOW 0x1e13 #define UNITEXT_LATIN_SMALL_LETTER_D_WITH_CIRCUMFLEX_BELOW L"\u1e13" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_MACRON_AND_GRAVE 0x1e14 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_MACRON_AND_GRAVE L"\u1e14" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_MACRON_AND_GRAVE 0x1e15 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_MACRON_AND_GRAVE L"\u1e15" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_MACRON_AND_ACUTE 0x1e16 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_MACRON_AND_ACUTE L"\u1e16" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_MACRON_AND_ACUTE 0x1e17 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_MACRON_AND_ACUTE L"\u1e17" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_BELOW 0x1e18 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_BELOW L"\u1e18" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_BELOW 0x1e19 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_BELOW L"\u1e19" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_TILDE_BELOW 0x1e1a #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_TILDE_BELOW L"\u1e1a" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_TILDE_BELOW 0x1e1b #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_TILDE_BELOW L"\u1e1b" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CEDILLA_AND_BREVE 0x1e1c #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CEDILLA_AND_BREVE L"\u1e1c" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CEDILLA_AND_BREVE 0x1e1d #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CEDILLA_AND_BREVE L"\u1e1d" #define UNICODE_LATIN_CAPITAL_LETTER_F_WITH_DOT_ABOVE 0x1e1e #define UNITEXT_LATIN_CAPITAL_LETTER_F_WITH_DOT_ABOVE L"\u1e1e" #define UNICODE_LATIN_SMALL_LETTER_F_WITH_DOT_ABOVE 0x1e1f #define UNITEXT_LATIN_SMALL_LETTER_F_WITH_DOT_ABOVE L"\u1e1f" #define UNICODE_LATIN_CAPITAL_LETTER_G_WITH_MACRON 0x1e20 #define UNITEXT_LATIN_CAPITAL_LETTER_G_WITH_MACRON L"\u1e20" #define UNICODE_LATIN_SMALL_LETTER_G_WITH_MACRON 0x1e21 #define UNITEXT_LATIN_SMALL_LETTER_G_WITH_MACRON L"\u1e21" #define UNICODE_LATIN_CAPITAL_LETTER_H_WITH_DOT_ABOVE 0x1e22 #define UNITEXT_LATIN_CAPITAL_LETTER_H_WITH_DOT_ABOVE L"\u1e22" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_DOT_ABOVE 0x1e23 #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_DOT_ABOVE L"\u1e23" #define UNICODE_LATIN_CAPITAL_LETTER_H_WITH_DOT_BELOW 0x1e24 #define UNITEXT_LATIN_CAPITAL_LETTER_H_WITH_DOT_BELOW L"\u1e24" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_DOT_BELOW 0x1e25 #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_DOT_BELOW L"\u1e25" #define UNICODE_LATIN_CAPITAL_LETTER_H_WITH_DIAERESIS 0x1e26 #define UNITEXT_LATIN_CAPITAL_LETTER_H_WITH_DIAERESIS L"\u1e26" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_DIAERESIS 0x1e27 #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_DIAERESIS L"\u1e27" #define UNICODE_LATIN_CAPITAL_LETTER_H_WITH_CEDILLA 0x1e28 #define UNITEXT_LATIN_CAPITAL_LETTER_H_WITH_CEDILLA L"\u1e28" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_CEDILLA 0x1e29 #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_CEDILLA L"\u1e29" #define UNICODE_LATIN_CAPITAL_LETTER_H_WITH_BREVE_BELOW 0x1e2a #define UNITEXT_LATIN_CAPITAL_LETTER_H_WITH_BREVE_BELOW L"\u1e2a" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_BREVE_BELOW 0x1e2b #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_BREVE_BELOW L"\u1e2b" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_TILDE_BELOW 0x1e2c #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_TILDE_BELOW L"\u1e2c" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_TILDE_BELOW 0x1e2d #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_TILDE_BELOW L"\u1e2d" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_DIAERESIS_AND_ACUTE 0x1e2e #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_DIAERESIS_AND_ACUTE L"\u1e2e" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_DIAERESIS_AND_ACUTE 0x1e2f #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_DIAERESIS_AND_ACUTE L"\u1e2f" #define UNICODE_LATIN_CAPITAL_LETTER_K_WITH_ACUTE 0x1e30 #define UNITEXT_LATIN_CAPITAL_LETTER_K_WITH_ACUTE L"\u1e30" #define UNICODE_LATIN_SMALL_LETTER_K_WITH_ACUTE 0x1e31 #define UNITEXT_LATIN_SMALL_LETTER_K_WITH_ACUTE L"\u1e31" #define UNICODE_LATIN_CAPITAL_LETTER_K_WITH_DOT_BELOW 0x1e32 #define UNITEXT_LATIN_CAPITAL_LETTER_K_WITH_DOT_BELOW L"\u1e32" #define UNICODE_LATIN_SMALL_LETTER_K_WITH_DOT_BELOW 0x1e33 #define UNITEXT_LATIN_SMALL_LETTER_K_WITH_DOT_BELOW L"\u1e33" #define UNICODE_LATIN_CAPITAL_LETTER_K_WITH_LINE_BELOW 0x1e34 #define UNITEXT_LATIN_CAPITAL_LETTER_K_WITH_LINE_BELOW L"\u1e34" #define UNICODE_LATIN_SMALL_LETTER_K_WITH_LINE_BELOW 0x1e35 #define UNITEXT_LATIN_SMALL_LETTER_K_WITH_LINE_BELOW L"\u1e35" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_DOT_BELOW 0x1e36 #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_DOT_BELOW L"\u1e36" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_DOT_BELOW 0x1e37 #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_DOT_BELOW L"\u1e37" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_DOT_BELOW_AND_MACRON 0x1e38 #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_DOT_BELOW_AND_MACRON L"\u1e38" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_DOT_BELOW_AND_MACRON 0x1e39 #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_DOT_BELOW_AND_MACRON L"\u1e39" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_LINE_BELOW 0x1e3a #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_LINE_BELOW L"\u1e3a" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_LINE_BELOW 0x1e3b #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_LINE_BELOW L"\u1e3b" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_CIRCUMFLEX_BELOW 0x1e3c #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_CIRCUMFLEX_BELOW L"\u1e3c" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_CIRCUMFLEX_BELOW 0x1e3d #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_CIRCUMFLEX_BELOW L"\u1e3d" #define UNICODE_LATIN_CAPITAL_LETTER_M_WITH_ACUTE 0x1e3e #define UNITEXT_LATIN_CAPITAL_LETTER_M_WITH_ACUTE L"\u1e3e" #define UNICODE_LATIN_SMALL_LETTER_M_WITH_ACUTE 0x1e3f #define UNITEXT_LATIN_SMALL_LETTER_M_WITH_ACUTE L"\u1e3f" #define UNICODE_LATIN_CAPITAL_LETTER_M_WITH_DOT_ABOVE 0x1e40 #define UNITEXT_LATIN_CAPITAL_LETTER_M_WITH_DOT_ABOVE L"\u1e40" #define UNICODE_LATIN_SMALL_LETTER_M_WITH_DOT_ABOVE 0x1e41 #define UNITEXT_LATIN_SMALL_LETTER_M_WITH_DOT_ABOVE L"\u1e41" #define UNICODE_LATIN_CAPITAL_LETTER_M_WITH_DOT_BELOW 0x1e42 #define UNITEXT_LATIN_CAPITAL_LETTER_M_WITH_DOT_BELOW L"\u1e42" #define UNICODE_LATIN_SMALL_LETTER_M_WITH_DOT_BELOW 0x1e43 #define UNITEXT_LATIN_SMALL_LETTER_M_WITH_DOT_BELOW L"\u1e43" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_DOT_ABOVE 0x1e44 #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_DOT_ABOVE L"\u1e44" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_DOT_ABOVE 0x1e45 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_DOT_ABOVE L"\u1e45" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_DOT_BELOW 0x1e46 #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_DOT_BELOW L"\u1e46" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_DOT_BELOW 0x1e47 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_DOT_BELOW L"\u1e47" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_LINE_BELOW 0x1e48 #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_LINE_BELOW L"\u1e48" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_LINE_BELOW 0x1e49 #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_LINE_BELOW L"\u1e49" #define UNICODE_LATIN_CAPITAL_LETTER_N_WITH_CIRCUMFLEX_BELOW 0x1e4a #define UNITEXT_LATIN_CAPITAL_LETTER_N_WITH_CIRCUMFLEX_BELOW L"\u1e4a" #define UNICODE_LATIN_SMALL_LETTER_N_WITH_CIRCUMFLEX_BELOW 0x1e4b #define UNITEXT_LATIN_SMALL_LETTER_N_WITH_CIRCUMFLEX_BELOW L"\u1e4b" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_TILDE_AND_ACUTE 0x1e4c #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_TILDE_AND_ACUTE L"\u1e4c" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_TILDE_AND_ACUTE 0x1e4d #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_TILDE_AND_ACUTE L"\u1e4d" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_TILDE_AND_DIAERESIS 0x1e4e #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_TILDE_AND_DIAERESIS L"\u1e4e" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_TILDE_AND_DIAERESIS 0x1e4f #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_TILDE_AND_DIAERESIS L"\u1e4f" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_MACRON_AND_GRAVE 0x1e50 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_MACRON_AND_GRAVE L"\u1e50" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_MACRON_AND_GRAVE 0x1e51 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_MACRON_AND_GRAVE L"\u1e51" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_MACRON_AND_ACUTE 0x1e52 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_MACRON_AND_ACUTE L"\u1e52" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_MACRON_AND_ACUTE 0x1e53 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_MACRON_AND_ACUTE L"\u1e53" #define UNICODE_LATIN_CAPITAL_LETTER_P_WITH_ACUTE 0x1e54 #define UNITEXT_LATIN_CAPITAL_LETTER_P_WITH_ACUTE L"\u1e54" #define UNICODE_LATIN_SMALL_LETTER_P_WITH_ACUTE 0x1e55 #define UNITEXT_LATIN_SMALL_LETTER_P_WITH_ACUTE L"\u1e55" #define UNICODE_LATIN_CAPITAL_LETTER_P_WITH_DOT_ABOVE 0x1e56 #define UNITEXT_LATIN_CAPITAL_LETTER_P_WITH_DOT_ABOVE L"\u1e56" #define UNICODE_LATIN_SMALL_LETTER_P_WITH_DOT_ABOVE 0x1e57 #define UNITEXT_LATIN_SMALL_LETTER_P_WITH_DOT_ABOVE L"\u1e57" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_DOT_ABOVE 0x1e58 #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_DOT_ABOVE L"\u1e58" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_DOT_ABOVE 0x1e59 #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_DOT_ABOVE L"\u1e59" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_DOT_BELOW 0x1e5a #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_DOT_BELOW L"\u1e5a" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_DOT_BELOW 0x1e5b #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_DOT_BELOW L"\u1e5b" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_DOT_BELOW_AND_MACRON 0x1e5c #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_DOT_BELOW_AND_MACRON L"\u1e5c" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_DOT_BELOW_AND_MACRON 0x1e5d #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_DOT_BELOW_AND_MACRON L"\u1e5d" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_LINE_BELOW 0x1e5e #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_LINE_BELOW L"\u1e5e" #define UNICODE_LATIN_SMALL_LETTER_R_WITH_LINE_BELOW 0x1e5f #define UNITEXT_LATIN_SMALL_LETTER_R_WITH_LINE_BELOW L"\u1e5f" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_DOT_ABOVE 0x1e60 #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_DOT_ABOVE L"\u1e60" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_DOT_ABOVE 0x1e61 #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_DOT_ABOVE L"\u1e61" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_DOT_BELOW 0x1e62 #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_DOT_BELOW L"\u1e62" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_DOT_BELOW 0x1e63 #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_DOT_BELOW L"\u1e63" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_ACUTE_AND_DOT_ABOVE 0x1e64 #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_ACUTE_AND_DOT_ABOVE L"\u1e64" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_ACUTE_AND_DOT_ABOVE 0x1e65 #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_ACUTE_AND_DOT_ABOVE L"\u1e65" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_CARON_AND_DOT_ABOVE 0x1e66 #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_CARON_AND_DOT_ABOVE L"\u1e66" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_CARON_AND_DOT_ABOVE 0x1e67 #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_CARON_AND_DOT_ABOVE L"\u1e67" #define UNICODE_LATIN_CAPITAL_LETTER_S_WITH_DOT_BELOW_AND_DOT_ABOVE 0x1e68 #define UNITEXT_LATIN_CAPITAL_LETTER_S_WITH_DOT_BELOW_AND_DOT_ABOVE L"\u1e68" #define UNICODE_LATIN_SMALL_LETTER_S_WITH_DOT_BELOW_AND_DOT_ABOVE 0x1e69 #define UNITEXT_LATIN_SMALL_LETTER_S_WITH_DOT_BELOW_AND_DOT_ABOVE L"\u1e69" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_DOT_ABOVE 0x1e6a #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_DOT_ABOVE L"\u1e6a" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_DOT_ABOVE 0x1e6b #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_DOT_ABOVE L"\u1e6b" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_DOT_BELOW 0x1e6c #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_DOT_BELOW L"\u1e6c" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_DOT_BELOW 0x1e6d #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_DOT_BELOW L"\u1e6d" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_LINE_BELOW 0x1e6e #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_LINE_BELOW L"\u1e6e" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_LINE_BELOW 0x1e6f #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_LINE_BELOW L"\u1e6f" #define UNICODE_LATIN_CAPITAL_LETTER_T_WITH_CIRCUMFLEX_BELOW 0x1e70 #define UNITEXT_LATIN_CAPITAL_LETTER_T_WITH_CIRCUMFLEX_BELOW L"\u1e70" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_CIRCUMFLEX_BELOW 0x1e71 #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_CIRCUMFLEX_BELOW L"\u1e71" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_BELOW 0x1e72 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS_BELOW L"\u1e72" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_BELOW 0x1e73 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_DIAERESIS_BELOW L"\u1e73" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_TILDE_BELOW 0x1e74 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_TILDE_BELOW L"\u1e74" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_TILDE_BELOW 0x1e75 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_TILDE_BELOW L"\u1e75" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_CIRCUMFLEX_BELOW 0x1e76 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_CIRCUMFLEX_BELOW L"\u1e76" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_CIRCUMFLEX_BELOW 0x1e77 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_CIRCUMFLEX_BELOW L"\u1e77" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_TILDE_AND_ACUTE 0x1e78 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_TILDE_AND_ACUTE L"\u1e78" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_TILDE_AND_ACUTE 0x1e79 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_TILDE_AND_ACUTE L"\u1e79" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_MACRON_AND_DIAERESIS 0x1e7a #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_MACRON_AND_DIAERESIS L"\u1e7a" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_MACRON_AND_DIAERESIS 0x1e7b #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_MACRON_AND_DIAERESIS L"\u1e7b" #define UNICODE_LATIN_CAPITAL_LETTER_V_WITH_TILDE 0x1e7c #define UNITEXT_LATIN_CAPITAL_LETTER_V_WITH_TILDE L"\u1e7c" #define UNICODE_LATIN_SMALL_LETTER_V_WITH_TILDE 0x1e7d #define UNITEXT_LATIN_SMALL_LETTER_V_WITH_TILDE L"\u1e7d" #define UNICODE_LATIN_CAPITAL_LETTER_V_WITH_DOT_BELOW 0x1e7e #define UNITEXT_LATIN_CAPITAL_LETTER_V_WITH_DOT_BELOW L"\u1e7e" #define UNICODE_LATIN_SMALL_LETTER_V_WITH_DOT_BELOW 0x1e7f #define UNITEXT_LATIN_SMALL_LETTER_V_WITH_DOT_BELOW L"\u1e7f" #define UNICODE_LATIN_CAPITAL_LETTER_W_WITH_GRAVE 0x1e80 #define UNITEXT_LATIN_CAPITAL_LETTER_W_WITH_GRAVE L"\u1e80" #define UNICODE_LATIN_SMALL_LETTER_W_WITH_GRAVE 0x1e81 #define UNITEXT_LATIN_SMALL_LETTER_W_WITH_GRAVE L"\u1e81" #define UNICODE_LATIN_CAPITAL_LETTER_W_WITH_ACUTE 0x1e82 #define UNITEXT_LATIN_CAPITAL_LETTER_W_WITH_ACUTE L"\u1e82" #define UNICODE_LATIN_SMALL_LETTER_W_WITH_ACUTE 0x1e83 #define UNITEXT_LATIN_SMALL_LETTER_W_WITH_ACUTE L"\u1e83" #define UNICODE_LATIN_CAPITAL_LETTER_W_WITH_DIAERESIS 0x1e84 #define UNITEXT_LATIN_CAPITAL_LETTER_W_WITH_DIAERESIS L"\u1e84" #define UNICODE_LATIN_SMALL_LETTER_W_WITH_DIAERESIS 0x1e85 #define UNITEXT_LATIN_SMALL_LETTER_W_WITH_DIAERESIS L"\u1e85" #define UNICODE_LATIN_CAPITAL_LETTER_W_WITH_DOT_ABOVE 0x1e86 #define UNITEXT_LATIN_CAPITAL_LETTER_W_WITH_DOT_ABOVE L"\u1e86" #define UNICODE_LATIN_SMALL_LETTER_W_WITH_DOT_ABOVE 0x1e87 #define UNITEXT_LATIN_SMALL_LETTER_W_WITH_DOT_ABOVE L"\u1e87" #define UNICODE_LATIN_CAPITAL_LETTER_W_WITH_DOT_BELOW 0x1e88 #define UNITEXT_LATIN_CAPITAL_LETTER_W_WITH_DOT_BELOW L"\u1e88" #define UNICODE_LATIN_SMALL_LETTER_W_WITH_DOT_BELOW 0x1e89 #define UNITEXT_LATIN_SMALL_LETTER_W_WITH_DOT_BELOW L"\u1e89" #define UNICODE_LATIN_CAPITAL_LETTER_X_WITH_DOT_ABOVE 0x1e8a #define UNITEXT_LATIN_CAPITAL_LETTER_X_WITH_DOT_ABOVE L"\u1e8a" #define UNICODE_LATIN_SMALL_LETTER_X_WITH_DOT_ABOVE 0x1e8b #define UNITEXT_LATIN_SMALL_LETTER_X_WITH_DOT_ABOVE L"\u1e8b" #define UNICODE_LATIN_CAPITAL_LETTER_X_WITH_DIAERESIS 0x1e8c #define UNITEXT_LATIN_CAPITAL_LETTER_X_WITH_DIAERESIS L"\u1e8c" #define UNICODE_LATIN_SMALL_LETTER_X_WITH_DIAERESIS 0x1e8d #define UNITEXT_LATIN_SMALL_LETTER_X_WITH_DIAERESIS L"\u1e8d" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_DOT_ABOVE 0x1e8e #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_DOT_ABOVE L"\u1e8e" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_DOT_ABOVE 0x1e8f #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_DOT_ABOVE L"\u1e8f" #define UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_CIRCUMFLEX 0x1e90 #define UNITEXT_LATIN_CAPITAL_LETTER_Z_WITH_CIRCUMFLEX L"\u1e90" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_CIRCUMFLEX 0x1e91 #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_CIRCUMFLEX L"\u1e91" #define UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_DOT_BELOW 0x1e92 #define UNITEXT_LATIN_CAPITAL_LETTER_Z_WITH_DOT_BELOW L"\u1e92" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_DOT_BELOW 0x1e93 #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_DOT_BELOW L"\u1e93" #define UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_LINE_BELOW 0x1e94 #define UNITEXT_LATIN_CAPITAL_LETTER_Z_WITH_LINE_BELOW L"\u1e94" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_LINE_BELOW 0x1e95 #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_LINE_BELOW L"\u1e95" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_LINE_BELOW 0x1e96 #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_LINE_BELOW L"\u1e96" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_DIAERESIS 0x1e97 #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_DIAERESIS L"\u1e97" #define UNICODE_LATIN_SMALL_LETTER_W_WITH_RING_ABOVE 0x1e98 #define UNITEXT_LATIN_SMALL_LETTER_W_WITH_RING_ABOVE L"\u1e98" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_RING_ABOVE 0x1e99 #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_RING_ABOVE L"\u1e99" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_RIGHT_HALF_RING 0x1e9a #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_RIGHT_HALF_RING L"\u1e9a" #define UNICODE_LATIN_SMALL_LETTER_LONG_S_WITH_DOT_ABOVE 0x1e9b #define UNITEXT_LATIN_SMALL_LETTER_LONG_S_WITH_DOT_ABOVE L"\u1e9b" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_DOT_BELOW 0x1ea0 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_DOT_BELOW L"\u1ea0" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_DOT_BELOW 0x1ea1 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_DOT_BELOW L"\u1ea1" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_HOOK_ABOVE 0x1ea2 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_HOOK_ABOVE L"\u1ea2" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_HOOK_ABOVE 0x1ea3 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_HOOK_ABOVE L"\u1ea3" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_ACUTE 0x1ea4 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_ACUTE L"\u1ea4" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_ACUTE 0x1ea5 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_ACUTE L"\u1ea5" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_GRAVE 0x1ea6 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_GRAVE L"\u1ea6" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_GRAVE 0x1ea7 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_GRAVE L"\u1ea7" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_HOOK_ABOVE 0x1ea8 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_HOOK_ABOVE L"\u1ea8" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_HOOK_ABOVE 0x1ea9 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_HOOK_ABOVE L"\u1ea9" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_TILDE 0x1eaa #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_TILDE L"\u1eaa" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_TILDE 0x1eab #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_TILDE L"\u1eab" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_DOT_BELOW 0x1eac #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX_AND_DOT_BELOW L"\u1eac" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_DOT_BELOW 0x1ead #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX_AND_DOT_BELOW L"\u1ead" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_ACUTE 0x1eae #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_ACUTE L"\u1eae" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_ACUTE 0x1eaf #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_ACUTE L"\u1eaf" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_GRAVE 0x1eb0 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_GRAVE L"\u1eb0" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_GRAVE 0x1eb1 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_GRAVE L"\u1eb1" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_HOOK_ABOVE 0x1eb2 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_HOOK_ABOVE L"\u1eb2" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_HOOK_ABOVE 0x1eb3 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_HOOK_ABOVE L"\u1eb3" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_TILDE 0x1eb4 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_TILDE L"\u1eb4" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_TILDE 0x1eb5 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_TILDE L"\u1eb5" #define UNICODE_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_DOT_BELOW 0x1eb6 #define UNITEXT_LATIN_CAPITAL_LETTER_A_WITH_BREVE_AND_DOT_BELOW L"\u1eb6" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_DOT_BELOW 0x1eb7 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_BREVE_AND_DOT_BELOW L"\u1eb7" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_DOT_BELOW 0x1eb8 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_DOT_BELOW L"\u1eb8" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_DOT_BELOW 0x1eb9 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_DOT_BELOW L"\u1eb9" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_HOOK_ABOVE 0x1eba #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_HOOK_ABOVE L"\u1eba" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_HOOK_ABOVE 0x1ebb #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_HOOK_ABOVE L"\u1ebb" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_TILDE 0x1ebc #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_TILDE L"\u1ebc" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_TILDE 0x1ebd #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_TILDE L"\u1ebd" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_ACUTE 0x1ebe #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_ACUTE L"\u1ebe" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_ACUTE 0x1ebf #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_ACUTE L"\u1ebf" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_GRAVE 0x1ec0 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_GRAVE L"\u1ec0" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_GRAVE 0x1ec1 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_GRAVE L"\u1ec1" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_HOOK_ABOVE 0x1ec2 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_HOOK_ABOVE L"\u1ec2" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_HOOK_ABOVE 0x1ec3 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_HOOK_ABOVE L"\u1ec3" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_TILDE 0x1ec4 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_TILDE L"\u1ec4" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_TILDE 0x1ec5 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_TILDE L"\u1ec5" #define UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_DOT_BELOW 0x1ec6 #define UNITEXT_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX_AND_DOT_BELOW L"\u1ec6" #define UNICODE_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_DOT_BELOW 0x1ec7 #define UNITEXT_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX_AND_DOT_BELOW L"\u1ec7" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_HOOK_ABOVE 0x1ec8 #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_HOOK_ABOVE L"\u1ec8" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_HOOK_ABOVE 0x1ec9 #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_HOOK_ABOVE L"\u1ec9" #define UNICODE_LATIN_CAPITAL_LETTER_I_WITH_DOT_BELOW 0x1eca #define UNITEXT_LATIN_CAPITAL_LETTER_I_WITH_DOT_BELOW L"\u1eca" #define UNICODE_LATIN_SMALL_LETTER_I_WITH_DOT_BELOW 0x1ecb #define UNITEXT_LATIN_SMALL_LETTER_I_WITH_DOT_BELOW L"\u1ecb" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DOT_BELOW 0x1ecc #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_DOT_BELOW L"\u1ecc" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_DOT_BELOW 0x1ecd #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_DOT_BELOW L"\u1ecd" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_HOOK_ABOVE 0x1ece #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_HOOK_ABOVE L"\u1ece" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_HOOK_ABOVE 0x1ecf #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_HOOK_ABOVE L"\u1ecf" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_ACUTE 0x1ed0 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_ACUTE L"\u1ed0" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_ACUTE 0x1ed1 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_ACUTE L"\u1ed1" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_GRAVE 0x1ed2 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_GRAVE L"\u1ed2" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_GRAVE 0x1ed3 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_GRAVE L"\u1ed3" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_HOOK_ABOVE 0x1ed4 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_HOOK_ABOVE L"\u1ed4" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_HOOK_ABOVE 0x1ed5 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_HOOK_ABOVE L"\u1ed5" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_TILDE 0x1ed6 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_TILDE L"\u1ed6" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_TILDE 0x1ed7 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_TILDE L"\u1ed7" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_DOT_BELOW 0x1ed8 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX_AND_DOT_BELOW L"\u1ed8" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_DOT_BELOW 0x1ed9 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX_AND_DOT_BELOW L"\u1ed9" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_ACUTE 0x1eda #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_ACUTE L"\u1eda" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_HORN_AND_ACUTE 0x1edb #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_HORN_AND_ACUTE L"\u1edb" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_GRAVE 0x1edc #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_GRAVE L"\u1edc" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_HORN_AND_GRAVE 0x1edd #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_HORN_AND_GRAVE L"\u1edd" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_HOOK_ABOVE 0x1ede #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_HOOK_ABOVE L"\u1ede" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_HORN_AND_HOOK_ABOVE 0x1edf #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_HORN_AND_HOOK_ABOVE L"\u1edf" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_TILDE 0x1ee0 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_TILDE L"\u1ee0" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_HORN_AND_TILDE 0x1ee1 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_HORN_AND_TILDE L"\u1ee1" #define UNICODE_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_DOT_BELOW 0x1ee2 #define UNITEXT_LATIN_CAPITAL_LETTER_O_WITH_HORN_AND_DOT_BELOW L"\u1ee2" #define UNICODE_LATIN_SMALL_LETTER_O_WITH_HORN_AND_DOT_BELOW 0x1ee3 #define UNITEXT_LATIN_SMALL_LETTER_O_WITH_HORN_AND_DOT_BELOW L"\u1ee3" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DOT_BELOW 0x1ee4 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_DOT_BELOW L"\u1ee4" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_DOT_BELOW 0x1ee5 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_DOT_BELOW L"\u1ee5" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_HOOK_ABOVE 0x1ee6 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_HOOK_ABOVE L"\u1ee6" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_HOOK_ABOVE 0x1ee7 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_HOOK_ABOVE L"\u1ee7" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_ACUTE 0x1ee8 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_ACUTE L"\u1ee8" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_HORN_AND_ACUTE 0x1ee9 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_HORN_AND_ACUTE L"\u1ee9" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_GRAVE 0x1eea #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_GRAVE L"\u1eea" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_HORN_AND_GRAVE 0x1eeb #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_HORN_AND_GRAVE L"\u1eeb" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_HOOK_ABOVE 0x1eec #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_HOOK_ABOVE L"\u1eec" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_HORN_AND_HOOK_ABOVE 0x1eed #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_HORN_AND_HOOK_ABOVE L"\u1eed" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_TILDE 0x1eee #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_TILDE L"\u1eee" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_HORN_AND_TILDE 0x1eef #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_HORN_AND_TILDE L"\u1eef" #define UNICODE_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_DOT_BELOW 0x1ef0 #define UNITEXT_LATIN_CAPITAL_LETTER_U_WITH_HORN_AND_DOT_BELOW L"\u1ef0" #define UNICODE_LATIN_SMALL_LETTER_U_WITH_HORN_AND_DOT_BELOW 0x1ef1 #define UNITEXT_LATIN_SMALL_LETTER_U_WITH_HORN_AND_DOT_BELOW L"\u1ef1" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_GRAVE 0x1ef2 #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_GRAVE L"\u1ef2" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_GRAVE 0x1ef3 #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_GRAVE L"\u1ef3" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_DOT_BELOW 0x1ef4 #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_DOT_BELOW L"\u1ef4" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_DOT_BELOW 0x1ef5 #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_DOT_BELOW L"\u1ef5" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_HOOK_ABOVE 0x1ef6 #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_HOOK_ABOVE L"\u1ef6" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_HOOK_ABOVE 0x1ef7 #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_HOOK_ABOVE L"\u1ef7" #define UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_TILDE 0x1ef8 #define UNITEXT_LATIN_CAPITAL_LETTER_Y_WITH_TILDE L"\u1ef8" #define UNICODE_LATIN_SMALL_LETTER_Y_WITH_TILDE 0x1ef9 #define UNITEXT_LATIN_SMALL_LETTER_Y_WITH_TILDE L"\u1ef9" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI 0x1f00 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI L"\u1f00" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA 0x1f01 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA L"\u1f01" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_VARIA 0x1f02 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_VARIA L"\u1f02" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_VARIA 0x1f03 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_VARIA L"\u1f03" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_OXIA 0x1f04 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_OXIA L"\u1f04" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_OXIA 0x1f05 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_OXIA L"\u1f05" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_PERISPOMENI 0x1f06 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_PERISPOMENI L"\u1f06" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_PERISPOMENI 0x1f07 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_PERISPOMENI L"\u1f07" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI 0x1f08 #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI L"\u1f08" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA 0x1f09 #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA L"\u1f09" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_VARIA 0x1f0a #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_VARIA L"\u1f0a" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_VARIA 0x1f0b #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_VARIA L"\u1f0b" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_OXIA 0x1f0c #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_OXIA L"\u1f0c" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_OXIA 0x1f0d #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_OXIA L"\u1f0d" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_PERISPOMENI 0x1f0e #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_PERISPOMENI L"\u1f0e" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_PERISPOMENI 0x1f0f #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_PERISPOMENI L"\u1f0f" #define UNICODE_GREEK_SMALL_LETTER_EPSILON_WITH_PSILI 0x1f10 #define UNITEXT_GREEK_SMALL_LETTER_EPSILON_WITH_PSILI L"\u1f10" #define UNICODE_GREEK_SMALL_LETTER_EPSILON_WITH_DASIA 0x1f11 #define UNITEXT_GREEK_SMALL_LETTER_EPSILON_WITH_DASIA L"\u1f11" #define UNICODE_GREEK_SMALL_LETTER_EPSILON_WITH_PSILI_AND_VARIA 0x1f12 #define UNITEXT_GREEK_SMALL_LETTER_EPSILON_WITH_PSILI_AND_VARIA L"\u1f12" #define UNICODE_GREEK_SMALL_LETTER_EPSILON_WITH_DASIA_AND_VARIA 0x1f13 #define UNITEXT_GREEK_SMALL_LETTER_EPSILON_WITH_DASIA_AND_VARIA L"\u1f13" #define UNICODE_GREEK_SMALL_LETTER_EPSILON_WITH_PSILI_AND_OXIA 0x1f14 #define UNITEXT_GREEK_SMALL_LETTER_EPSILON_WITH_PSILI_AND_OXIA L"\u1f14" #define UNICODE_GREEK_SMALL_LETTER_EPSILON_WITH_DASIA_AND_OXIA 0x1f15 #define UNITEXT_GREEK_SMALL_LETTER_EPSILON_WITH_DASIA_AND_OXIA L"\u1f15" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON_WITH_PSILI 0x1f18 #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON_WITH_PSILI L"\u1f18" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON_WITH_DASIA 0x1f19 #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON_WITH_DASIA L"\u1f19" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON_WITH_PSILI_AND_VARIA 0x1f1a #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON_WITH_PSILI_AND_VARIA L"\u1f1a" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON_WITH_DASIA_AND_VARIA 0x1f1b #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON_WITH_DASIA_AND_VARIA L"\u1f1b" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON_WITH_PSILI_AND_OXIA 0x1f1c #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON_WITH_PSILI_AND_OXIA L"\u1f1c" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON_WITH_DASIA_AND_OXIA 0x1f1d #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON_WITH_DASIA_AND_OXIA L"\u1f1d" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PSILI 0x1f20 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PSILI L"\u1f20" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_DASIA 0x1f21 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_DASIA L"\u1f21" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_VARIA 0x1f22 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_VARIA L"\u1f22" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_VARIA 0x1f23 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_VARIA L"\u1f23" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_OXIA 0x1f24 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_OXIA L"\u1f24" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_OXIA 0x1f25 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_OXIA L"\u1f25" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_PERISPOMENI 0x1f26 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_PERISPOMENI L"\u1f26" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_PERISPOMENI 0x1f27 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_PERISPOMENI L"\u1f27" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI 0x1f28 #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI L"\u1f28" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA 0x1f29 #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA L"\u1f29" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_VARIA 0x1f2a #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_VARIA L"\u1f2a" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_VARIA 0x1f2b #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_VARIA L"\u1f2b" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_OXIA 0x1f2c #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_OXIA L"\u1f2c" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_OXIA 0x1f2d #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_OXIA L"\u1f2d" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_PERISPOMENI 0x1f2e #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_PERISPOMENI L"\u1f2e" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_PERISPOMENI 0x1f2f #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_PERISPOMENI L"\u1f2f" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_PSILI 0x1f30 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_PSILI L"\u1f30" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_DASIA 0x1f31 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_DASIA L"\u1f31" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_PSILI_AND_VARIA 0x1f32 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_PSILI_AND_VARIA L"\u1f32" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_DASIA_AND_VARIA 0x1f33 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_DASIA_AND_VARIA L"\u1f33" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_PSILI_AND_OXIA 0x1f34 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_PSILI_AND_OXIA L"\u1f34" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_DASIA_AND_OXIA 0x1f35 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_DASIA_AND_OXIA L"\u1f35" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_PSILI_AND_PERISPOMENI 0x1f36 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_PSILI_AND_PERISPOMENI L"\u1f36" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_DASIA_AND_PERISPOMENI 0x1f37 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_DASIA_AND_PERISPOMENI L"\u1f37" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_PSILI 0x1f38 #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_PSILI L"\u1f38" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_DASIA 0x1f39 #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_DASIA L"\u1f39" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_PSILI_AND_VARIA 0x1f3a #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_PSILI_AND_VARIA L"\u1f3a" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_DASIA_AND_VARIA 0x1f3b #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_DASIA_AND_VARIA L"\u1f3b" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_PSILI_AND_OXIA 0x1f3c #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_PSILI_AND_OXIA L"\u1f3c" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_DASIA_AND_OXIA 0x1f3d #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_DASIA_AND_OXIA L"\u1f3d" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_PSILI_AND_PERISPOMENI 0x1f3e #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_PSILI_AND_PERISPOMENI L"\u1f3e" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_DASIA_AND_PERISPOMENI 0x1f3f #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_DASIA_AND_PERISPOMENI L"\u1f3f" #define UNICODE_GREEK_SMALL_LETTER_OMICRON_WITH_PSILI 0x1f40 #define UNITEXT_GREEK_SMALL_LETTER_OMICRON_WITH_PSILI L"\u1f40" #define UNICODE_GREEK_SMALL_LETTER_OMICRON_WITH_DASIA 0x1f41 #define UNITEXT_GREEK_SMALL_LETTER_OMICRON_WITH_DASIA L"\u1f41" #define UNICODE_GREEK_SMALL_LETTER_OMICRON_WITH_PSILI_AND_VARIA 0x1f42 #define UNITEXT_GREEK_SMALL_LETTER_OMICRON_WITH_PSILI_AND_VARIA L"\u1f42" #define UNICODE_GREEK_SMALL_LETTER_OMICRON_WITH_DASIA_AND_VARIA 0x1f43 #define UNITEXT_GREEK_SMALL_LETTER_OMICRON_WITH_DASIA_AND_VARIA L"\u1f43" #define UNICODE_GREEK_SMALL_LETTER_OMICRON_WITH_PSILI_AND_OXIA 0x1f44 #define UNITEXT_GREEK_SMALL_LETTER_OMICRON_WITH_PSILI_AND_OXIA L"\u1f44" #define UNICODE_GREEK_SMALL_LETTER_OMICRON_WITH_DASIA_AND_OXIA 0x1f45 #define UNITEXT_GREEK_SMALL_LETTER_OMICRON_WITH_DASIA_AND_OXIA L"\u1f45" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON_WITH_PSILI 0x1f48 #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON_WITH_PSILI L"\u1f48" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON_WITH_DASIA 0x1f49 #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON_WITH_DASIA L"\u1f49" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON_WITH_PSILI_AND_VARIA 0x1f4a #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON_WITH_PSILI_AND_VARIA L"\u1f4a" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON_WITH_DASIA_AND_VARIA 0x1f4b #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON_WITH_DASIA_AND_VARIA L"\u1f4b" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON_WITH_PSILI_AND_OXIA 0x1f4c #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON_WITH_PSILI_AND_OXIA L"\u1f4c" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON_WITH_DASIA_AND_OXIA 0x1f4d #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON_WITH_DASIA_AND_OXIA L"\u1f4d" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_PSILI 0x1f50 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_PSILI L"\u1f50" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_DASIA 0x1f51 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_DASIA L"\u1f51" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_PSILI_AND_VARIA 0x1f52 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_PSILI_AND_VARIA L"\u1f52" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_DASIA_AND_VARIA 0x1f53 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_DASIA_AND_VARIA L"\u1f53" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_PSILI_AND_OXIA 0x1f54 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_PSILI_AND_OXIA L"\u1f54" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_DASIA_AND_OXIA 0x1f55 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_DASIA_AND_OXIA L"\u1f55" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_PSILI_AND_PERISPOMENI 0x1f56 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_PSILI_AND_PERISPOMENI L"\u1f56" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_DASIA_AND_PERISPOMENI 0x1f57 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_DASIA_AND_PERISPOMENI L"\u1f57" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_DASIA 0x1f59 #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_DASIA L"\u1f59" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_DASIA_AND_VARIA 0x1f5b #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_DASIA_AND_VARIA L"\u1f5b" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_DASIA_AND_OXIA 0x1f5d #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_DASIA_AND_OXIA L"\u1f5d" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_DASIA_AND_PERISPOMENI 0x1f5f #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_DASIA_AND_PERISPOMENI L"\u1f5f" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI 0x1f60 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI L"\u1f60" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA 0x1f61 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA L"\u1f61" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_VARIA 0x1f62 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_VARIA L"\u1f62" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_VARIA 0x1f63 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_VARIA L"\u1f63" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_OXIA 0x1f64 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_OXIA L"\u1f64" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_OXIA 0x1f65 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_OXIA L"\u1f65" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_PERISPOMENI 0x1f66 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_PERISPOMENI L"\u1f66" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_PERISPOMENI 0x1f67 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_PERISPOMENI L"\u1f67" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI 0x1f68 #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI L"\u1f68" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA 0x1f69 #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA L"\u1f69" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_VARIA 0x1f6a #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_VARIA L"\u1f6a" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_VARIA 0x1f6b #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_VARIA L"\u1f6b" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_OXIA 0x1f6c #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_OXIA L"\u1f6c" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_OXIA 0x1f6d #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_OXIA L"\u1f6d" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_PERISPOMENI 0x1f6e #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_PERISPOMENI L"\u1f6e" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_PERISPOMENI 0x1f6f #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_PERISPOMENI L"\u1f6f" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_VARIA 0x1f70 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_VARIA L"\u1f70" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_OXIA 0x1f71 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_OXIA L"\u1f71" #define UNICODE_GREEK_SMALL_LETTER_EPSILON_WITH_VARIA 0x1f72 #define UNITEXT_GREEK_SMALL_LETTER_EPSILON_WITH_VARIA L"\u1f72" #define UNICODE_GREEK_SMALL_LETTER_EPSILON_WITH_OXIA 0x1f73 #define UNITEXT_GREEK_SMALL_LETTER_EPSILON_WITH_OXIA L"\u1f73" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_VARIA 0x1f74 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_VARIA L"\u1f74" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_OXIA 0x1f75 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_OXIA L"\u1f75" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_VARIA 0x1f76 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_VARIA L"\u1f76" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_OXIA 0x1f77 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_OXIA L"\u1f77" #define UNICODE_GREEK_SMALL_LETTER_OMICRON_WITH_VARIA 0x1f78 #define UNITEXT_GREEK_SMALL_LETTER_OMICRON_WITH_VARIA L"\u1f78" #define UNICODE_GREEK_SMALL_LETTER_OMICRON_WITH_OXIA 0x1f79 #define UNITEXT_GREEK_SMALL_LETTER_OMICRON_WITH_OXIA L"\u1f79" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_VARIA 0x1f7a #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_VARIA L"\u1f7a" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_OXIA 0x1f7b #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_OXIA L"\u1f7b" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_VARIA 0x1f7c #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_VARIA L"\u1f7c" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_OXIA 0x1f7d #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_OXIA L"\u1f7d" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_YPOGEGRAMMENI 0x1f80 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_YPOGEGRAMMENI L"\u1f80" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_YPOGEGRAMMENI 0x1f81 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_YPOGEGRAMMENI L"\u1f81" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_VARIA_AND_YPOGEGRAMMENI 0x1f82 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_VARIA_AND_YPOGEGRAMMENI L"\u1f82" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_VARIA_AND_YPOGEGRAMMENI 0x1f83 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_VARIA_AND_YPOGEGRAMMENI L"\u1f83" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_OXIA_AND_YPOGEGRAMMENI 0x1f84 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_OXIA_AND_YPOGEGRAMMENI L"\u1f84" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_OXIA_AND_YPOGEGRAMMENI 0x1f85 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_OXIA_AND_YPOGEGRAMMENI L"\u1f85" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_PERISPOMENI_AND_YPOGEGRAMMENI 0x1f86 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PSILI_AND_PERISPOMENI_AND_YPOGEGRAMMENI L"\u1f86" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_PERISPOMENI_AND_YPOGEGRAMMENI 0x1f87 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_DASIA_AND_PERISPOMENI_AND_YPOGEGRAMMENI L"\u1f87" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_PROSGEGRAMMENI 0x1f88 #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_PROSGEGRAMMENI L"\u1f88" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_PROSGEGRAMMENI 0x1f89 #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_PROSGEGRAMMENI L"\u1f89" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_VARIA_AND_PROSGEGRAMMENI 0x1f8a #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_VARIA_AND_PROSGEGRAMMENI L"\u1f8a" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_VARIA_AND_PROSGEGRAMMENI 0x1f8b #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_VARIA_AND_PROSGEGRAMMENI L"\u1f8b" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_OXIA_AND_PROSGEGRAMMENI 0x1f8c #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_OXIA_AND_PROSGEGRAMMENI L"\u1f8c" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_OXIA_AND_PROSGEGRAMMENI 0x1f8d #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_OXIA_AND_PROSGEGRAMMENI L"\u1f8d" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_PERISPOMENI_AND_PROSGEGRAMMENI 0x1f8e #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_PSILI_AND_PERISPOMENI_AND_PROSGEGRAMMENI L"\u1f8e" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_PERISPOMENI_AND_PROSGEGRAMMENI 0x1f8f #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_DASIA_AND_PERISPOMENI_AND_PROSGEGRAMMENI L"\u1f8f" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_YPOGEGRAMMENI 0x1f90 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_YPOGEGRAMMENI L"\u1f90" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_YPOGEGRAMMENI 0x1f91 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_YPOGEGRAMMENI L"\u1f91" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_VARIA_AND_YPOGEGRAMMENI 0x1f92 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_VARIA_AND_YPOGEGRAMMENI L"\u1f92" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_VARIA_AND_YPOGEGRAMMENI 0x1f93 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_VARIA_AND_YPOGEGRAMMENI L"\u1f93" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_OXIA_AND_YPOGEGRAMMENI 0x1f94 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_OXIA_AND_YPOGEGRAMMENI L"\u1f94" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_OXIA_AND_YPOGEGRAMMENI 0x1f95 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_OXIA_AND_YPOGEGRAMMENI L"\u1f95" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_PERISPOMENI_AND_YPOGEGRAMMENI 0x1f96 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PSILI_AND_PERISPOMENI_AND_YPOGEGRAMMENI L"\u1f96" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_PERISPOMENI_AND_YPOGEGRAMMENI 0x1f97 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_DASIA_AND_PERISPOMENI_AND_YPOGEGRAMMENI L"\u1f97" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_PROSGEGRAMMENI 0x1f98 #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_PROSGEGRAMMENI L"\u1f98" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_PROSGEGRAMMENI 0x1f99 #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_PROSGEGRAMMENI L"\u1f99" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_VARIA_AND_PROSGEGRAMMENI 0x1f9a #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_VARIA_AND_PROSGEGRAMMENI L"\u1f9a" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_VARIA_AND_PROSGEGRAMMENI 0x1f9b #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_VARIA_AND_PROSGEGRAMMENI L"\u1f9b" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_OXIA_AND_PROSGEGRAMMENI 0x1f9c #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_OXIA_AND_PROSGEGRAMMENI L"\u1f9c" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_OXIA_AND_PROSGEGRAMMENI 0x1f9d #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_OXIA_AND_PROSGEGRAMMENI L"\u1f9d" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_PERISPOMENI_AND_PROSGEGRAMMENI 0x1f9e #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_PSILI_AND_PERISPOMENI_AND_PROSGEGRAMMENI L"\u1f9e" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_PERISPOMENI_AND_PROSGEGRAMMENI 0x1f9f #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_DASIA_AND_PERISPOMENI_AND_PROSGEGRAMMENI L"\u1f9f" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_YPOGEGRAMMENI 0x1fa0 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_YPOGEGRAMMENI L"\u1fa0" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_YPOGEGRAMMENI 0x1fa1 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_YPOGEGRAMMENI L"\u1fa1" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_VARIA_AND_YPOGEGRAMMENI 0x1fa2 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_VARIA_AND_YPOGEGRAMMENI L"\u1fa2" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_VARIA_AND_YPOGEGRAMMENI 0x1fa3 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_VARIA_AND_YPOGEGRAMMENI L"\u1fa3" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_OXIA_AND_YPOGEGRAMMENI 0x1fa4 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_OXIA_AND_YPOGEGRAMMENI L"\u1fa4" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_OXIA_AND_YPOGEGRAMMENI 0x1fa5 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_OXIA_AND_YPOGEGRAMMENI L"\u1fa5" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_PERISPOMENI_AND_YPOGEGRAMMENI 0x1fa6 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PSILI_AND_PERISPOMENI_AND_YPOGEGRAMMENI L"\u1fa6" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_PERISPOMENI_AND_YPOGEGRAMMENI 0x1fa7 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_DASIA_AND_PERISPOMENI_AND_YPOGEGRAMMENI L"\u1fa7" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_PROSGEGRAMMENI 0x1fa8 #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_PROSGEGRAMMENI L"\u1fa8" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_PROSGEGRAMMENI 0x1fa9 #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_PROSGEGRAMMENI L"\u1fa9" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_VARIA_AND_PROSGEGRAMMENI 0x1faa #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_VARIA_AND_PROSGEGRAMMENI L"\u1faa" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_VARIA_AND_PROSGEGRAMMENI 0x1fab #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_VARIA_AND_PROSGEGRAMMENI L"\u1fab" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_OXIA_AND_PROSGEGRAMMENI 0x1fac #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_OXIA_AND_PROSGEGRAMMENI L"\u1fac" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_OXIA_AND_PROSGEGRAMMENI 0x1fad #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_OXIA_AND_PROSGEGRAMMENI L"\u1fad" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_PERISPOMENI_AND_PROSGEGRAMMENI 0x1fae #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_PSILI_AND_PERISPOMENI_AND_PROSGEGRAMMENI L"\u1fae" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_PERISPOMENI_AND_PROSGEGRAMMENI 0x1faf #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_DASIA_AND_PERISPOMENI_AND_PROSGEGRAMMENI L"\u1faf" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_VRACHY 0x1fb0 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_VRACHY L"\u1fb0" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_MACRON 0x1fb1 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_MACRON L"\u1fb1" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_VARIA_AND_YPOGEGRAMMENI 0x1fb2 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_VARIA_AND_YPOGEGRAMMENI L"\u1fb2" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_YPOGEGRAMMENI 0x1fb3 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_YPOGEGRAMMENI L"\u1fb3" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_OXIA_AND_YPOGEGRAMMENI 0x1fb4 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_OXIA_AND_YPOGEGRAMMENI L"\u1fb4" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PERISPOMENI 0x1fb6 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PERISPOMENI L"\u1fb6" #define UNICODE_GREEK_SMALL_LETTER_ALPHA_WITH_PERISPOMENI_AND_YPOGEGRAMMENI 0x1fb7 #define UNITEXT_GREEK_SMALL_LETTER_ALPHA_WITH_PERISPOMENI_AND_YPOGEGRAMMENI L"\u1fb7" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_VRACHY 0x1fb8 #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_VRACHY L"\u1fb8" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_MACRON 0x1fb9 #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_MACRON L"\u1fb9" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_VARIA 0x1fba #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_VARIA L"\u1fba" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_OXIA 0x1fbb #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_OXIA L"\u1fbb" #define UNICODE_GREEK_CAPITAL_LETTER_ALPHA_WITH_PROSGEGRAMMENI 0x1fbc #define UNITEXT_GREEK_CAPITAL_LETTER_ALPHA_WITH_PROSGEGRAMMENI L"\u1fbc" #define UNICODE_GREEK_KORONIS 0x1fbd #define UNITEXT_GREEK_KORONIS L"\u1fbd" #define UNICODE_GREEK_PROSGEGRAMMENI 0x1fbe #define UNITEXT_GREEK_PROSGEGRAMMENI L"\u1fbe" #define UNICODE_GREEK_PSILI 0x1fbf #define UNITEXT_GREEK_PSILI L"\u1fbf" #define UNICODE_GREEK_PERISPOMENI 0x1fc0 #define UNITEXT_GREEK_PERISPOMENI L"\u1fc0" #define UNICODE_GREEK_DIALYTIKA_AND_PERISPOMENI 0x1fc1 #define UNITEXT_GREEK_DIALYTIKA_AND_PERISPOMENI L"\u1fc1" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_VARIA_AND_YPOGEGRAMMENI 0x1fc2 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_VARIA_AND_YPOGEGRAMMENI L"\u1fc2" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_YPOGEGRAMMENI 0x1fc3 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_YPOGEGRAMMENI L"\u1fc3" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_OXIA_AND_YPOGEGRAMMENI 0x1fc4 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_OXIA_AND_YPOGEGRAMMENI L"\u1fc4" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PERISPOMENI 0x1fc6 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PERISPOMENI L"\u1fc6" #define UNICODE_GREEK_SMALL_LETTER_ETA_WITH_PERISPOMENI_AND_YPOGEGRAMMENI 0x1fc7 #define UNITEXT_GREEK_SMALL_LETTER_ETA_WITH_PERISPOMENI_AND_YPOGEGRAMMENI L"\u1fc7" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON_WITH_VARIA 0x1fc8 #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON_WITH_VARIA L"\u1fc8" #define UNICODE_GREEK_CAPITAL_LETTER_EPSILON_WITH_OXIA 0x1fc9 #define UNITEXT_GREEK_CAPITAL_LETTER_EPSILON_WITH_OXIA L"\u1fc9" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_VARIA 0x1fca #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_VARIA L"\u1fca" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_OXIA 0x1fcb #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_OXIA L"\u1fcb" #define UNICODE_GREEK_CAPITAL_LETTER_ETA_WITH_PROSGEGRAMMENI 0x1fcc #define UNITEXT_GREEK_CAPITAL_LETTER_ETA_WITH_PROSGEGRAMMENI L"\u1fcc" #define UNICODE_GREEK_PSILI_AND_VARIA 0x1fcd #define UNITEXT_GREEK_PSILI_AND_VARIA L"\u1fcd" #define UNICODE_GREEK_PSILI_AND_OXIA 0x1fce #define UNITEXT_GREEK_PSILI_AND_OXIA L"\u1fce" #define UNICODE_GREEK_PSILI_AND_PERISPOMENI 0x1fcf #define UNITEXT_GREEK_PSILI_AND_PERISPOMENI L"\u1fcf" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_VRACHY 0x1fd0 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_VRACHY L"\u1fd0" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_MACRON 0x1fd1 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_MACRON L"\u1fd1" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA_AND_VARIA 0x1fd2 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA_AND_VARIA L"\u1fd2" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA_AND_OXIA 0x1fd3 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA_AND_OXIA L"\u1fd3" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_PERISPOMENI 0x1fd6 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_PERISPOMENI L"\u1fd6" #define UNICODE_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA_AND_PERISPOMENI 0x1fd7 #define UNITEXT_GREEK_SMALL_LETTER_IOTA_WITH_DIALYTIKA_AND_PERISPOMENI L"\u1fd7" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_VRACHY 0x1fd8 #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_VRACHY L"\u1fd8" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_MACRON 0x1fd9 #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_MACRON L"\u1fd9" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_VARIA 0x1fda #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_VARIA L"\u1fda" #define UNICODE_GREEK_CAPITAL_LETTER_IOTA_WITH_OXIA 0x1fdb #define UNITEXT_GREEK_CAPITAL_LETTER_IOTA_WITH_OXIA L"\u1fdb" #define UNICODE_GREEK_DASIA_AND_VARIA 0x1fdd #define UNITEXT_GREEK_DASIA_AND_VARIA L"\u1fdd" #define UNICODE_GREEK_DASIA_AND_OXIA 0x1fde #define UNITEXT_GREEK_DASIA_AND_OXIA L"\u1fde" #define UNICODE_GREEK_DASIA_AND_PERISPOMENI 0x1fdf #define UNITEXT_GREEK_DASIA_AND_PERISPOMENI L"\u1fdf" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_VRACHY 0x1fe0 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_VRACHY L"\u1fe0" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_MACRON 0x1fe1 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_MACRON L"\u1fe1" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA_AND_VARIA 0x1fe2 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA_AND_VARIA L"\u1fe2" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA_AND_OXIA 0x1fe3 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA_AND_OXIA L"\u1fe3" #define UNICODE_GREEK_SMALL_LETTER_RHO_WITH_PSILI 0x1fe4 #define UNITEXT_GREEK_SMALL_LETTER_RHO_WITH_PSILI L"\u1fe4" #define UNICODE_GREEK_SMALL_LETTER_RHO_WITH_DASIA 0x1fe5 #define UNITEXT_GREEK_SMALL_LETTER_RHO_WITH_DASIA L"\u1fe5" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_PERISPOMENI 0x1fe6 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_PERISPOMENI L"\u1fe6" #define UNICODE_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA_AND_PERISPOMENI 0x1fe7 #define UNITEXT_GREEK_SMALL_LETTER_UPSILON_WITH_DIALYTIKA_AND_PERISPOMENI L"\u1fe7" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_VRACHY 0x1fe8 #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_VRACHY L"\u1fe8" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_MACRON 0x1fe9 #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_MACRON L"\u1fe9" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_VARIA 0x1fea #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_VARIA L"\u1fea" #define UNICODE_GREEK_CAPITAL_LETTER_UPSILON_WITH_OXIA 0x1feb #define UNITEXT_GREEK_CAPITAL_LETTER_UPSILON_WITH_OXIA L"\u1feb" #define UNICODE_GREEK_CAPITAL_LETTER_RHO_WITH_DASIA 0x1fec #define UNITEXT_GREEK_CAPITAL_LETTER_RHO_WITH_DASIA L"\u1fec" #define UNICODE_GREEK_DIALYTIKA_AND_VARIA 0x1fed #define UNITEXT_GREEK_DIALYTIKA_AND_VARIA L"\u1fed" #define UNICODE_GREEK_DIALYTIKA_AND_OXIA 0x1fee #define UNITEXT_GREEK_DIALYTIKA_AND_OXIA L"\u1fee" #define UNICODE_GREEK_VARIA 0x1fef #define UNITEXT_GREEK_VARIA L"\u1fef" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_VARIA_AND_YPOGEGRAMMENI 0x1ff2 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_VARIA_AND_YPOGEGRAMMENI L"\u1ff2" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_YPOGEGRAMMENI 0x1ff3 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_YPOGEGRAMMENI L"\u1ff3" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_OXIA_AND_YPOGEGRAMMENI 0x1ff4 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_OXIA_AND_YPOGEGRAMMENI L"\u1ff4" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PERISPOMENI 0x1ff6 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PERISPOMENI L"\u1ff6" #define UNICODE_GREEK_SMALL_LETTER_OMEGA_WITH_PERISPOMENI_AND_YPOGEGRAMMENI 0x1ff7 #define UNITEXT_GREEK_SMALL_LETTER_OMEGA_WITH_PERISPOMENI_AND_YPOGEGRAMMENI L"\u1ff7" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON_WITH_VARIA 0x1ff8 #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON_WITH_VARIA L"\u1ff8" #define UNICODE_GREEK_CAPITAL_LETTER_OMICRON_WITH_OXIA 0x1ff9 #define UNITEXT_GREEK_CAPITAL_LETTER_OMICRON_WITH_OXIA L"\u1ff9" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_VARIA 0x1ffa #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_VARIA L"\u1ffa" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_OXIA 0x1ffb #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_OXIA L"\u1ffb" #define UNICODE_GREEK_CAPITAL_LETTER_OMEGA_WITH_PROSGEGRAMMENI 0x1ffc #define UNITEXT_GREEK_CAPITAL_LETTER_OMEGA_WITH_PROSGEGRAMMENI L"\u1ffc" #define UNICODE_GREEK_OXIA 0x1ffd #define UNITEXT_GREEK_OXIA L"\u1ffd" #define UNICODE_GREEK_DASIA 0x1ffe #define UNITEXT_GREEK_DASIA L"\u1ffe" #define UNICODE_EN_QUAD 0x2000 #define UNITEXT_EN_QUAD L"\u2000" #define UNICODE_EM_QUAD 0x2001 #define UNITEXT_EM_QUAD L"\u2001" #define UNICODE_EN_SPACE 0x2002 #define UNITEXT_EN_SPACE L"\u2002" #define UNICODE_EM_SPACE 0x2003 #define UNITEXT_EM_SPACE L"\u2003" #define UNICODE_THREE_PER_EM_SPACE 0x2004 #define UNITEXT_THREE_PER_EM_SPACE L"\u2004" #define UNICODE_FOUR_PER_EM_SPACE 0x2005 #define UNITEXT_FOUR_PER_EM_SPACE L"\u2005" #define UNICODE_SIX_PER_EM_SPACE 0x2006 #define UNITEXT_SIX_PER_EM_SPACE L"\u2006" #define UNICODE_FIGURE_SPACE 0x2007 #define UNITEXT_FIGURE_SPACE L"\u2007" #define UNICODE_PUNCTUATION_SPACE 0x2008 #define UNITEXT_PUNCTUATION_SPACE L"\u2008" #define UNICODE_THIN_SPACE 0x2009 #define UNITEXT_THIN_SPACE L"\u2009" #define UNICODE_HAIR_SPACE 0x200a #define UNITEXT_HAIR_SPACE L"\u200a" #define UNICODE_ZERO_WIDTH_SPACE 0x200b #define UNITEXT_ZERO_WIDTH_SPACE L"\u200b" #define UNICODE_ZERO_WIDTH_NON_JOINER 0x200c #define UNITEXT_ZERO_WIDTH_NON_JOINER L"\u200c" #define UNICODE_ZERO_WIDTH_JOINER 0x200d #define UNITEXT_ZERO_WIDTH_JOINER L"\u200d" #define UNICODE_LEFT_TO_RIGHT_MARK 0x200e #define UNITEXT_LEFT_TO_RIGHT_MARK L"\u200e" #define UNICODE_RIGHT_TO_LEFT_MARK 0x200f #define UNITEXT_RIGHT_TO_LEFT_MARK L"\u200f" #define UNICODE_HYPHEN 0x2010 #define UNITEXT_HYPHEN L"\u2010" #define UNICODE_NON_BREAKING_HYPHEN 0x2011 #define UNITEXT_NON_BREAKING_HYPHEN L"\u2011" #define UNICODE_FIGURE_DASH 0x2012 #define UNITEXT_FIGURE_DASH L"\u2012" #define UNICODE_EN_DASH 0x2013 #define UNITEXT_EN_DASH L"\u2013" #define UNICODE_EM_DASH 0x2014 #define UNITEXT_EM_DASH L"\u2014" #define UNICODE_HORIZONTAL_BAR 0x2015 #define UNITEXT_HORIZONTAL_BAR L"\u2015" #define UNICODE_DOUBLE_VERTICAL_LINE 0x2016 #define UNITEXT_DOUBLE_VERTICAL_LINE L"\u2016" #define UNICODE_DOUBLE_LOW_LINE 0x2017 #define UNITEXT_DOUBLE_LOW_LINE L"\u2017" #define UNICODE_LEFT_SINGLE_QUOTATION_MARK 0x2018 #define UNITEXT_LEFT_SINGLE_QUOTATION_MARK L"\u2018" #define UNICODE_RIGHT_SINGLE_QUOTATION_MARK 0x2019 #define UNITEXT_RIGHT_SINGLE_QUOTATION_MARK L"\u2019" #define UNICODE_SINGLE_LOW_9_QUOTATION_MARK 0x201a #define UNITEXT_SINGLE_LOW_9_QUOTATION_MARK L"\u201a" #define UNICODE_SINGLE_HIGH_REVERSED_9_QUOTATION_MARK 0x201b #define UNITEXT_SINGLE_HIGH_REVERSED_9_QUOTATION_MARK L"\u201b" #define UNICODE_LEFT_DOUBLE_QUOTATION_MARK 0x201c #define UNITEXT_LEFT_DOUBLE_QUOTATION_MARK L"\u201c" #define UNICODE_RIGHT_DOUBLE_QUOTATION_MARK 0x201d #define UNITEXT_RIGHT_DOUBLE_QUOTATION_MARK L"\u201d" #define UNICODE_DOUBLE_LOW_9_QUOTATION_MARK 0x201e #define UNITEXT_DOUBLE_LOW_9_QUOTATION_MARK L"\u201e" #define UNICODE_DOUBLE_HIGH_REVERSED_9_QUOTATION_MARK 0x201f #define UNITEXT_DOUBLE_HIGH_REVERSED_9_QUOTATION_MARK L"\u201f" #define UNICODE_DAGGER 0x2020 #define UNITEXT_DAGGER L"\u2020" #define UNICODE_DOUBLE_DAGGER 0x2021 #define UNITEXT_DOUBLE_DAGGER L"\u2021" #define UNICODE_BULLET 0x2022 #define UNITEXT_BULLET L"\u2022" #define UNICODE_TRIANGULAR_BULLET 0x2023 #define UNITEXT_TRIANGULAR_BULLET L"\u2023" #define UNICODE_ONE_DOT_LEADER 0x2024 #define UNITEXT_ONE_DOT_LEADER L"\u2024" #define UNICODE_TWO_DOT_LEADER 0x2025 #define UNITEXT_TWO_DOT_LEADER L"\u2025" #define UNICODE_HORIZONTAL_ELLIPSIS 0x2026 #define UNITEXT_HORIZONTAL_ELLIPSIS L"\u2026" #define UNICODE_HYPHENATION_POINT 0x2027 #define UNITEXT_HYPHENATION_POINT L"\u2027" #define UNICODE_LINE_SEPARATOR 0x2028 #define UNITEXT_LINE_SEPARATOR L"\u2028" #define UNICODE_PARAGRAPH_SEPARATOR 0x2029 #define UNITEXT_PARAGRAPH_SEPARATOR L"\u2029" #define UNICODE_LEFT_TO_RIGHT_EMBEDDING 0x202a #define UNITEXT_LEFT_TO_RIGHT_EMBEDDING L"\u202a" #define UNICODE_RIGHT_TO_LEFT_EMBEDDING 0x202b #define UNITEXT_RIGHT_TO_LEFT_EMBEDDING L"\u202b" #define UNICODE_POP_DIRECTIONAL_FORMATTING 0x202c #define UNITEXT_POP_DIRECTIONAL_FORMATTING L"\u202c" #define UNICODE_LEFT_TO_RIGHT_OVERRIDE 0x202d #define UNITEXT_LEFT_TO_RIGHT_OVERRIDE L"\u202d" #define UNICODE_RIGHT_TO_LEFT_OVERRIDE 0x202e #define UNITEXT_RIGHT_TO_LEFT_OVERRIDE L"\u202e" #define UNICODE_NARROW_NO_BREAK_SPACE 0x202f #define UNITEXT_NARROW_NO_BREAK_SPACE L"\u202f" #define UNICODE_PER_MILLE_SIGN 0x2030 #define UNITEXT_PER_MILLE_SIGN L"\u2030" #define UNICODE_PER_TEN_THOUSAND_SIGN 0x2031 #define UNITEXT_PER_TEN_THOUSAND_SIGN L"\u2031" #define UNICODE_PRIME 0x2032 #define UNITEXT_PRIME L"\u2032" #define UNICODE_DOUBLE_PRIME 0x2033 #define UNITEXT_DOUBLE_PRIME L"\u2033" #define UNICODE_TRIPLE_PRIME 0x2034 #define UNITEXT_TRIPLE_PRIME L"\u2034" #define UNICODE_REVERSED_PRIME 0x2035 #define UNITEXT_REVERSED_PRIME L"\u2035" #define UNICODE_REVERSED_DOUBLE_PRIME 0x2036 #define UNITEXT_REVERSED_DOUBLE_PRIME L"\u2036" #define UNICODE_REVERSED_TRIPLE_PRIME 0x2037 #define UNITEXT_REVERSED_TRIPLE_PRIME L"\u2037" #define UNICODE_CARET 0x2038 #define UNITEXT_CARET L"\u2038" #define UNICODE_SINGLE_LEFT_POINTING_ANGLE_QUOTATION_MARK 0x2039 #define UNITEXT_SINGLE_LEFT_POINTING_ANGLE_QUOTATION_MARK L"\u2039" #define UNICODE_SINGLE_RIGHT_POINTING_ANGLE_QUOTATION_MARK 0x203a #define UNITEXT_SINGLE_RIGHT_POINTING_ANGLE_QUOTATION_MARK L"\u203a" #define UNICODE_REFERENCE_MARK 0x203b #define UNITEXT_REFERENCE_MARK L"\u203b" #define UNICODE_DOUBLE_EXCLAMATION_MARK 0x203c #define UNITEXT_DOUBLE_EXCLAMATION_MARK L"\u203c" #define UNICODE_INTERROBANG 0x203d #define UNITEXT_INTERROBANG L"\u203d" #define UNICODE_OVERLINE 0x203e #define UNITEXT_OVERLINE L"\u203e" #define UNICODE_UNDERTIE 0x203f #define UNITEXT_UNDERTIE L"\u203f" #define UNICODE_CHARACTER_TIE 0x2040 #define UNITEXT_CHARACTER_TIE L"\u2040" #define UNICODE_CARET_INSERTION_POINT 0x2041 #define UNITEXT_CARET_INSERTION_POINT L"\u2041" #define UNICODE_ASTERISM 0x2042 #define UNITEXT_ASTERISM L"\u2042" #define UNICODE_HYPHEN_BULLET 0x2043 #define UNITEXT_HYPHEN_BULLET L"\u2043" #define UNICODE_FRACTION_SLASH 0x2044 #define UNITEXT_FRACTION_SLASH L"\u2044" #define UNICODE_LEFT_SQUARE_BRACKET_WITH_QUILL 0x2045 #define UNITEXT_LEFT_SQUARE_BRACKET_WITH_QUILL L"\u2045" #define UNICODE_RIGHT_SQUARE_BRACKET_WITH_QUILL 0x2046 #define UNITEXT_RIGHT_SQUARE_BRACKET_WITH_QUILL L"\u2046" #define UNICODE_DOUBLE_QUESTION_MARK 0x2047 #define UNITEXT_DOUBLE_QUESTION_MARK L"\u2047" #define UNICODE_QUESTION_EXCLAMATION_MARK 0x2048 #define UNITEXT_QUESTION_EXCLAMATION_MARK L"\u2048" #define UNICODE_EXCLAMATION_QUESTION_MARK 0x2049 #define UNITEXT_EXCLAMATION_QUESTION_MARK L"\u2049" #define UNICODE_TIRONIAN_SIGN_ET 0x204a #define UNITEXT_TIRONIAN_SIGN_ET L"\u204a" #define UNICODE_REVERSED_PILCROW_SIGN 0x204b #define UNITEXT_REVERSED_PILCROW_SIGN L"\u204b" #define UNICODE_BLACK_LEFTWARDS_BULLET 0x204c #define UNITEXT_BLACK_LEFTWARDS_BULLET L"\u204c" #define UNICODE_BLACK_RIGHTWARDS_BULLET 0x204d #define UNITEXT_BLACK_RIGHTWARDS_BULLET L"\u204d" #define UNICODE_LOW_ASTERISK 0x204e #define UNITEXT_LOW_ASTERISK L"\u204e" #define UNICODE_REVERSED_SEMICOLON 0x204f #define UNITEXT_REVERSED_SEMICOLON L"\u204f" #define UNICODE_CLOSE_UP 0x2050 #define UNITEXT_CLOSE_UP L"\u2050" #define UNICODE_TWO_ASTERISKS_ALIGNED_VERTICALLY 0x2051 #define UNITEXT_TWO_ASTERISKS_ALIGNED_VERTICALLY L"\u2051" #define UNICODE_COMMERCIAL_MINUS_SIGN 0x2052 #define UNITEXT_COMMERCIAL_MINUS_SIGN L"\u2052" #define UNICODE_SWUNG_DASH 0x2053 #define UNITEXT_SWUNG_DASH L"\u2053" #define UNICODE_INVERTED_UNDERTIE 0x2054 #define UNITEXT_INVERTED_UNDERTIE L"\u2054" #define UNICODE_FLOWER_PUNCTUATION_MARK 0x2055 #define UNITEXT_FLOWER_PUNCTUATION_MARK L"\u2055" #define UNICODE_THREE_DOT_PUNCTUATION 0x2056 #define UNITEXT_THREE_DOT_PUNCTUATION L"\u2056" #define UNICODE_QUADRUPLE_PRIME 0x2057 #define UNITEXT_QUADRUPLE_PRIME L"\u2057" #define UNICODE_FOUR_DOT_PUNCTUATION 0x2058 #define UNITEXT_FOUR_DOT_PUNCTUATION L"\u2058" #define UNICODE_FIVE_DOT_PUNCTUATION 0x2059 #define UNITEXT_FIVE_DOT_PUNCTUATION L"\u2059" #define UNICODE_TWO_DOT_PUNCTUATION 0x205a #define UNITEXT_TWO_DOT_PUNCTUATION L"\u205a" #define UNICODE_FOUR_DOT_MARK 0x205b #define UNITEXT_FOUR_DOT_MARK L"\u205b" #define UNICODE_DOTTED_CROSS 0x205c #define UNITEXT_DOTTED_CROSS L"\u205c" #define UNICODE_TRICOLON 0x205d #define UNITEXT_TRICOLON L"\u205d" #define UNICODE_VERTICAL_FOUR_DOTS 0x205e #define UNITEXT_VERTICAL_FOUR_DOTS L"\u205e" #define UNICODE_MEDIUM_MATHEMATICAL_SPACE 0x205f #define UNITEXT_MEDIUM_MATHEMATICAL_SPACE L"\u205f" #define UNICODE_WORD_JOINER 0x2060 #define UNITEXT_WORD_JOINER L"\u2060" #define UNICODE_FUNCTION_APPLICATION 0x2061 #define UNITEXT_FUNCTION_APPLICATION L"\u2061" #define UNICODE_INVISIBLE_TIMES 0x2062 #define UNITEXT_INVISIBLE_TIMES L"\u2062" #define UNICODE_INVISIBLE_SEPARATOR 0x2063 #define UNITEXT_INVISIBLE_SEPARATOR L"\u2063" #define UNICODE_INHIBIT_SYMMETRIC_SWAPPING 0x206a #define UNITEXT_INHIBIT_SYMMETRIC_SWAPPING L"\u206a" #define UNICODE_ACTIVATE_SYMMETRIC_SWAPPING 0x206b #define UNITEXT_ACTIVATE_SYMMETRIC_SWAPPING L"\u206b" #define UNICODE_INHIBIT_ARABIC_FORM_SHAPING 0x206c #define UNITEXT_INHIBIT_ARABIC_FORM_SHAPING L"\u206c" #define UNICODE_ACTIVATE_ARABIC_FORM_SHAPING 0x206d #define UNITEXT_ACTIVATE_ARABIC_FORM_SHAPING L"\u206d" #define UNICODE_NATIONAL_DIGIT_SHAPES 0x206e #define UNITEXT_NATIONAL_DIGIT_SHAPES L"\u206e" #define UNICODE_NOMINAL_DIGIT_SHAPES 0x206f #define UNITEXT_NOMINAL_DIGIT_SHAPES L"\u206f" #define UNICODE_SUPERSCRIPT_ZERO 0x2070 #define UNITEXT_SUPERSCRIPT_ZERO L"\u2070" #define UNICODE_SUPERSCRIPT_LATIN_SMALL_LETTER_I 0x2071 #define UNITEXT_SUPERSCRIPT_LATIN_SMALL_LETTER_I L"\u2071" #define UNICODE_SUPERSCRIPT_FOUR 0x2074 #define UNITEXT_SUPERSCRIPT_FOUR L"\u2074" #define UNICODE_SUPERSCRIPT_FIVE 0x2075 #define UNITEXT_SUPERSCRIPT_FIVE L"\u2075" #define UNICODE_SUPERSCRIPT_SIX 0x2076 #define UNITEXT_SUPERSCRIPT_SIX L"\u2076" #define UNICODE_SUPERSCRIPT_SEVEN 0x2077 #define UNITEXT_SUPERSCRIPT_SEVEN L"\u2077" #define UNICODE_SUPERSCRIPT_EIGHT 0x2078 #define UNITEXT_SUPERSCRIPT_EIGHT L"\u2078" #define UNICODE_SUPERSCRIPT_NINE 0x2079 #define UNITEXT_SUPERSCRIPT_NINE L"\u2079" #define UNICODE_SUPERSCRIPT_PLUS_SIGN 0x207a #define UNITEXT_SUPERSCRIPT_PLUS_SIGN L"\u207a" #define UNICODE_SUPERSCRIPT_MINUS 0x207b #define UNITEXT_SUPERSCRIPT_MINUS L"\u207b" #define UNICODE_SUPERSCRIPT_EQUALS_SIGN 0x207c #define UNITEXT_SUPERSCRIPT_EQUALS_SIGN L"\u207c" #define UNICODE_SUPERSCRIPT_LEFT_PARENTHESIS 0x207d #define UNITEXT_SUPERSCRIPT_LEFT_PARENTHESIS L"\u207d" #define UNICODE_SUPERSCRIPT_RIGHT_PARENTHESIS 0x207e #define UNITEXT_SUPERSCRIPT_RIGHT_PARENTHESIS L"\u207e" #define UNICODE_SUPERSCRIPT_LATIN_SMALL_LETTER_N 0x207f #define UNITEXT_SUPERSCRIPT_LATIN_SMALL_LETTER_N L"\u207f" #define UNICODE_SUBSCRIPT_ZERO 0x2080 #define UNITEXT_SUBSCRIPT_ZERO L"\u2080" #define UNICODE_SUBSCRIPT_ONE 0x2081 #define UNITEXT_SUBSCRIPT_ONE L"\u2081" #define UNICODE_SUBSCRIPT_TWO 0x2082 #define UNITEXT_SUBSCRIPT_TWO L"\u2082" #define UNICODE_SUBSCRIPT_THREE 0x2083 #define UNITEXT_SUBSCRIPT_THREE L"\u2083" #define UNICODE_SUBSCRIPT_FOUR 0x2084 #define UNITEXT_SUBSCRIPT_FOUR L"\u2084" #define UNICODE_SUBSCRIPT_FIVE 0x2085 #define UNITEXT_SUBSCRIPT_FIVE L"\u2085" #define UNICODE_SUBSCRIPT_SIX 0x2086 #define UNITEXT_SUBSCRIPT_SIX L"\u2086" #define UNICODE_SUBSCRIPT_SEVEN 0x2087 #define UNITEXT_SUBSCRIPT_SEVEN L"\u2087" #define UNICODE_SUBSCRIPT_EIGHT 0x2088 #define UNITEXT_SUBSCRIPT_EIGHT L"\u2088" #define UNICODE_SUBSCRIPT_NINE 0x2089 #define UNITEXT_SUBSCRIPT_NINE L"\u2089" #define UNICODE_SUBSCRIPT_PLUS_SIGN 0x208a #define UNITEXT_SUBSCRIPT_PLUS_SIGN L"\u208a" #define UNICODE_SUBSCRIPT_MINUS 0x208b #define UNITEXT_SUBSCRIPT_MINUS L"\u208b" #define UNICODE_SUBSCRIPT_EQUALS_SIGN 0x208c #define UNITEXT_SUBSCRIPT_EQUALS_SIGN L"\u208c" #define UNICODE_SUBSCRIPT_LEFT_PARENTHESIS 0x208d #define UNITEXT_SUBSCRIPT_LEFT_PARENTHESIS L"\u208d" #define UNICODE_SUBSCRIPT_RIGHT_PARENTHESIS 0x208e #define UNITEXT_SUBSCRIPT_RIGHT_PARENTHESIS L"\u208e" #define UNICODE_LATIN_SUBSCRIPT_SMALL_LETTER_A 0x2090 #define UNITEXT_LATIN_SUBSCRIPT_SMALL_LETTER_A L"\u2090" #define UNICODE_LATIN_SUBSCRIPT_SMALL_LETTER_E 0x2091 #define UNITEXT_LATIN_SUBSCRIPT_SMALL_LETTER_E L"\u2091" #define UNICODE_LATIN_SUBSCRIPT_SMALL_LETTER_O 0x2092 #define UNITEXT_LATIN_SUBSCRIPT_SMALL_LETTER_O L"\u2092" #define UNICODE_LATIN_SUBSCRIPT_SMALL_LETTER_X 0x2093 #define UNITEXT_LATIN_SUBSCRIPT_SMALL_LETTER_X L"\u2093" #define UNICODE_LATIN_SUBSCRIPT_SMALL_LETTER_SCHWA 0x2094 #define UNITEXT_LATIN_SUBSCRIPT_SMALL_LETTER_SCHWA L"\u2094" #define UNICODE_EURO_CURRENCY_SIGN 0x20a0 #define UNITEXT_EURO_CURRENCY_SIGN L"\u20a0" #define UNICODE_COLON_SIGN 0x20a1 #define UNITEXT_COLON_SIGN L"\u20a1" #define UNICODE_CRUZEIRO_SIGN 0x20a2 #define UNITEXT_CRUZEIRO_SIGN L"\u20a2" #define UNICODE_FRENCH_FRANC_SIGN 0x20a3 #define UNITEXT_FRENCH_FRANC_SIGN L"\u20a3" #define UNICODE_LIRA_SIGN 0x20a4 #define UNITEXT_LIRA_SIGN L"\u20a4" #define UNICODE_MILL_SIGN 0x20a5 #define UNITEXT_MILL_SIGN L"\u20a5" #define UNICODE_NAIRA_SIGN 0x20a6 #define UNITEXT_NAIRA_SIGN L"\u20a6" #define UNICODE_PESETA_SIGN 0x20a7 #define UNITEXT_PESETA_SIGN L"\u20a7" #define UNICODE_RUPEE_SIGN 0x20a8 #define UNITEXT_RUPEE_SIGN L"\u20a8" #define UNICODE_WON_SIGN 0x20a9 #define UNITEXT_WON_SIGN L"\u20a9" #define UNICODE_NEW_SHEQEL_SIGN 0x20aa #define UNITEXT_NEW_SHEQEL_SIGN L"\u20aa" #define UNICODE_DONG_SIGN 0x20ab #define UNITEXT_DONG_SIGN L"\u20ab" #define UNICODE_EURO_SIGN 0x20ac #define UNITEXT_EURO_SIGN L"\u20ac" #define UNICODE_KIP_SIGN 0x20ad #define UNITEXT_KIP_SIGN L"\u20ad" #define UNICODE_TUGRIK_SIGN 0x20ae #define UNITEXT_TUGRIK_SIGN L"\u20ae" #define UNICODE_DRACHMA_SIGN 0x20af #define UNITEXT_DRACHMA_SIGN L"\u20af" #define UNICODE_GERMAN_PENNY_SIGN 0x20b0 #define UNITEXT_GERMAN_PENNY_SIGN L"\u20b0" #define UNICODE_PESO_SIGN 0x20b1 #define UNITEXT_PESO_SIGN L"\u20b1" #define UNICODE_GUARANI_SIGN 0x20b2 #define UNITEXT_GUARANI_SIGN L"\u20b2" #define UNICODE_AUSTRAL_SIGN 0x20b3 #define UNITEXT_AUSTRAL_SIGN L"\u20b3" #define UNICODE_HRYVNIA_SIGN 0x20b4 #define UNITEXT_HRYVNIA_SIGN L"\u20b4" #define UNICODE_CEDI_SIGN 0x20b5 #define UNITEXT_CEDI_SIGN L"\u20b5" #define UNICODE_COMBINING_LEFT_HARPOON_ABOVE 0x20d0 #define UNITEXT_COMBINING_LEFT_HARPOON_ABOVE L"\u20d0" #define UNICODE_COMBINING_RIGHT_HARPOON_ABOVE 0x20d1 #define UNITEXT_COMBINING_RIGHT_HARPOON_ABOVE L"\u20d1" #define UNICODE_COMBINING_LONG_VERTICAL_LINE_OVERLAY 0x20d2 #define UNITEXT_COMBINING_LONG_VERTICAL_LINE_OVERLAY L"\u20d2" #define UNICODE_COMBINING_SHORT_VERTICAL_LINE_OVERLAY 0x20d3 #define UNITEXT_COMBINING_SHORT_VERTICAL_LINE_OVERLAY L"\u20d3" #define UNICODE_COMBINING_ANTICLOCKWISE_ARROW_ABOVE 0x20d4 #define UNITEXT_COMBINING_ANTICLOCKWISE_ARROW_ABOVE L"\u20d4" #define UNICODE_COMBINING_CLOCKWISE_ARROW_ABOVE 0x20d5 #define UNITEXT_COMBINING_CLOCKWISE_ARROW_ABOVE L"\u20d5" #define UNICODE_COMBINING_LEFT_ARROW_ABOVE 0x20d6 #define UNITEXT_COMBINING_LEFT_ARROW_ABOVE L"\u20d6" #define UNICODE_COMBINING_RIGHT_ARROW_ABOVE 0x20d7 #define UNITEXT_COMBINING_RIGHT_ARROW_ABOVE L"\u20d7" #define UNICODE_COMBINING_RING_OVERLAY 0x20d8 #define UNITEXT_COMBINING_RING_OVERLAY L"\u20d8" #define UNICODE_COMBINING_CLOCKWISE_RING_OVERLAY 0x20d9 #define UNITEXT_COMBINING_CLOCKWISE_RING_OVERLAY L"\u20d9" #define UNICODE_COMBINING_ANTICLOCKWISE_RING_OVERLAY 0x20da #define UNITEXT_COMBINING_ANTICLOCKWISE_RING_OVERLAY L"\u20da" #define UNICODE_COMBINING_THREE_DOTS_ABOVE 0x20db #define UNITEXT_COMBINING_THREE_DOTS_ABOVE L"\u20db" #define UNICODE_COMBINING_FOUR_DOTS_ABOVE 0x20dc #define UNITEXT_COMBINING_FOUR_DOTS_ABOVE L"\u20dc" #define UNICODE_COMBINING_ENCLOSING_CIRCLE 0x20dd #define UNITEXT_COMBINING_ENCLOSING_CIRCLE L"\u20dd" #define UNICODE_COMBINING_ENCLOSING_SQUARE 0x20de #define UNITEXT_COMBINING_ENCLOSING_SQUARE L"\u20de" #define UNICODE_COMBINING_ENCLOSING_DIAMOND 0x20df #define UNITEXT_COMBINING_ENCLOSING_DIAMOND L"\u20df" #define UNICODE_COMBINING_ENCLOSING_CIRCLE_BACKSLASH 0x20e0 #define UNITEXT_COMBINING_ENCLOSING_CIRCLE_BACKSLASH L"\u20e0" #define UNICODE_COMBINING_LEFT_RIGHT_ARROW_ABOVE 0x20e1 #define UNITEXT_COMBINING_LEFT_RIGHT_ARROW_ABOVE L"\u20e1" #define UNICODE_COMBINING_ENCLOSING_SCREEN 0x20e2 #define UNITEXT_COMBINING_ENCLOSING_SCREEN L"\u20e2" #define UNICODE_COMBINING_ENCLOSING_KEYCAP 0x20e3 #define UNITEXT_COMBINING_ENCLOSING_KEYCAP L"\u20e3" #define UNICODE_COMBINING_ENCLOSING_UPWARD_POINTING_TRIANGLE 0x20e4 #define UNITEXT_COMBINING_ENCLOSING_UPWARD_POINTING_TRIANGLE L"\u20e4" #define UNICODE_COMBINING_REVERSE_SOLIDUS_OVERLAY 0x20e5 #define UNITEXT_COMBINING_REVERSE_SOLIDUS_OVERLAY L"\u20e5" #define UNICODE_COMBINING_DOUBLE_VERTICAL_STROKE_OVERLAY 0x20e6 #define UNITEXT_COMBINING_DOUBLE_VERTICAL_STROKE_OVERLAY L"\u20e6" #define UNICODE_COMBINING_ANNUITY_SYMBOL 0x20e7 #define UNITEXT_COMBINING_ANNUITY_SYMBOL L"\u20e7" #define UNICODE_COMBINING_TRIPLE_UNDERDOT 0x20e8 #define UNITEXT_COMBINING_TRIPLE_UNDERDOT L"\u20e8" #define UNICODE_COMBINING_WIDE_BRIDGE_ABOVE 0x20e9 #define UNITEXT_COMBINING_WIDE_BRIDGE_ABOVE L"\u20e9" #define UNICODE_COMBINING_LEFTWARDS_ARROW_OVERLAY 0x20ea #define UNITEXT_COMBINING_LEFTWARDS_ARROW_OVERLAY L"\u20ea" #define UNICODE_COMBINING_LONG_DOUBLE_SOLIDUS_OVERLAY 0x20eb #define UNITEXT_COMBINING_LONG_DOUBLE_SOLIDUS_OVERLAY L"\u20eb" #define UNICODE_COMBINING_RIGHTWARDS_HARPOON_WITH_BARB_DOWNWARDS 0x20ec #define UNITEXT_COMBINING_RIGHTWARDS_HARPOON_WITH_BARB_DOWNWARDS L"\u20ec" #define UNICODE_COMBINING_LEFTWARDS_HARPOON_WITH_BARB_DOWNWARDS 0x20ed #define UNITEXT_COMBINING_LEFTWARDS_HARPOON_WITH_BARB_DOWNWARDS L"\u20ed" #define UNICODE_COMBINING_LEFT_ARROW_BELOW 0x20ee #define UNITEXT_COMBINING_LEFT_ARROW_BELOW L"\u20ee" #define UNICODE_COMBINING_RIGHT_ARROW_BELOW 0x20ef #define UNITEXT_COMBINING_RIGHT_ARROW_BELOW L"\u20ef" #define UNICODE_ACCOUNT_OF 0x2100 #define UNITEXT_ACCOUNT_OF L"\u2100" #define UNICODE_ADDRESSED_TO_THE_SUBJECT 0x2101 #define UNITEXT_ADDRESSED_TO_THE_SUBJECT L"\u2101" #define UNICODE_DOUBLE_STRUCK_CAPITAL_C 0x2102 #define UNITEXT_DOUBLE_STRUCK_CAPITAL_C L"\u2102" #define UNICODE_DEGREE_CELSIUS 0x2103 #define UNITEXT_DEGREE_CELSIUS L"\u2103" #define UNICODE_CENTRE_LINE_SYMBOL 0x2104 #define UNITEXT_CENTRE_LINE_SYMBOL L"\u2104" #define UNICODE_CARE_OF 0x2105 #define UNITEXT_CARE_OF L"\u2105" #define UNICODE_CADA_UNA 0x2106 #define UNITEXT_CADA_UNA L"\u2106" #define UNICODE_EULER_CONSTANT 0x2107 #define UNITEXT_EULER_CONSTANT L"\u2107" #define UNICODE_SCRUPLE 0x2108 #define UNITEXT_SCRUPLE L"\u2108" #define UNICODE_DEGREE_FAHRENHEIT 0x2109 #define UNITEXT_DEGREE_FAHRENHEIT L"\u2109" #define UNICODE_SCRIPT_SMALL_G 0x210a #define UNITEXT_SCRIPT_SMALL_G L"\u210a" #define UNICODE_SCRIPT_CAPITAL_H 0x210b #define UNITEXT_SCRIPT_CAPITAL_H L"\u210b" #define UNICODE_BLACK_LETTER_CAPITAL_H 0x210c #define UNITEXT_BLACK_LETTER_CAPITAL_H L"\u210c" #define UNICODE_DOUBLE_STRUCK_CAPITAL_H 0x210d #define UNITEXT_DOUBLE_STRUCK_CAPITAL_H L"\u210d" #define UNICODE_PLANCK_CONSTANT 0x210e #define UNITEXT_PLANCK_CONSTANT L"\u210e" #define UNICODE_PLANCK_CONSTANT_OVER_TWO_PI 0x210f #define UNITEXT_PLANCK_CONSTANT_OVER_TWO_PI L"\u210f" #define UNICODE_SCRIPT_CAPITAL_I 0x2110 #define UNITEXT_SCRIPT_CAPITAL_I L"\u2110" #define UNICODE_BLACK_LETTER_CAPITAL_I 0x2111 #define UNITEXT_BLACK_LETTER_CAPITAL_I L"\u2111" #define UNICODE_SCRIPT_CAPITAL_L 0x2112 #define UNITEXT_SCRIPT_CAPITAL_L L"\u2112" #define UNICODE_SCRIPT_SMALL_L 0x2113 #define UNITEXT_SCRIPT_SMALL_L L"\u2113" #define UNICODE_L_B_BAR_SYMBOL 0x2114 #define UNITEXT_L_B_BAR_SYMBOL L"\u2114" #define UNICODE_DOUBLE_STRUCK_CAPITAL_N 0x2115 #define UNITEXT_DOUBLE_STRUCK_CAPITAL_N L"\u2115" #define UNICODE_NUMERO_SIGN 0x2116 #define UNITEXT_NUMERO_SIGN L"\u2116" #define UNICODE_SOUND_RECORDING_COPYRIGHT 0x2117 #define UNITEXT_SOUND_RECORDING_COPYRIGHT L"\u2117" #define UNICODE_SCRIPT_CAPITAL_P 0x2118 #define UNITEXT_SCRIPT_CAPITAL_P L"\u2118" #define UNICODE_DOUBLE_STRUCK_CAPITAL_P 0x2119 #define UNITEXT_DOUBLE_STRUCK_CAPITAL_P L"\u2119" #define UNICODE_DOUBLE_STRUCK_CAPITAL_Q 0x211a #define UNITEXT_DOUBLE_STRUCK_CAPITAL_Q L"\u211a" #define UNICODE_SCRIPT_CAPITAL_R 0x211b #define UNITEXT_SCRIPT_CAPITAL_R L"\u211b" #define UNICODE_BLACK_LETTER_CAPITAL_R 0x211c #define UNITEXT_BLACK_LETTER_CAPITAL_R L"\u211c" #define UNICODE_DOUBLE_STRUCK_CAPITAL_R 0x211d #define UNITEXT_DOUBLE_STRUCK_CAPITAL_R L"\u211d" #define UNICODE_PRESCRIPTION_TAKE 0x211e #define UNITEXT_PRESCRIPTION_TAKE L"\u211e" #define UNICODE_RESPONSE 0x211f #define UNITEXT_RESPONSE L"\u211f" #define UNICODE_SERVICE_MARK 0x2120 #define UNITEXT_SERVICE_MARK L"\u2120" #define UNICODE_TELEPHONE_SIGN 0x2121 #define UNITEXT_TELEPHONE_SIGN L"\u2121" #define UNICODE_TRADE_MARK_SIGN 0x2122 #define UNITEXT_TRADE_MARK_SIGN L"\u2122" #define UNICODE_VERSICLE 0x2123 #define UNITEXT_VERSICLE L"\u2123" #define UNICODE_DOUBLE_STRUCK_CAPITAL_Z 0x2124 #define UNITEXT_DOUBLE_STRUCK_CAPITAL_Z L"\u2124" #define UNICODE_OUNCE_SIGN 0x2125 #define UNITEXT_OUNCE_SIGN L"\u2125" #define UNICODE_OHM_SIGN 0x2126 #define UNITEXT_OHM_SIGN L"\u2126" #define UNICODE_INVERTED_OHM_SIGN 0x2127 #define UNITEXT_INVERTED_OHM_SIGN L"\u2127" #define UNICODE_BLACK_LETTER_CAPITAL_Z 0x2128 #define UNITEXT_BLACK_LETTER_CAPITAL_Z L"\u2128" #define UNICODE_TURNED_GREEK_SMALL_LETTER_IOTA 0x2129 #define UNITEXT_TURNED_GREEK_SMALL_LETTER_IOTA L"\u2129" #define UNICODE_KELVIN_SIGN 0x212a #define UNITEXT_KELVIN_SIGN L"\u212a" #define UNICODE_ANGSTROM_SIGN 0x212b #define UNITEXT_ANGSTROM_SIGN L"\u212b" #define UNICODE_SCRIPT_CAPITAL_B 0x212c #define UNITEXT_SCRIPT_CAPITAL_B L"\u212c" #define UNICODE_BLACK_LETTER_CAPITAL_C 0x212d #define UNITEXT_BLACK_LETTER_CAPITAL_C L"\u212d" #define UNICODE_ESTIMATED_SYMBOL 0x212e #define UNITEXT_ESTIMATED_SYMBOL L"\u212e" #define UNICODE_SCRIPT_SMALL_E 0x212f #define UNITEXT_SCRIPT_SMALL_E L"\u212f" #define UNICODE_SCRIPT_CAPITAL_E 0x2130 #define UNITEXT_SCRIPT_CAPITAL_E L"\u2130" #define UNICODE_SCRIPT_CAPITAL_F 0x2131 #define UNITEXT_SCRIPT_CAPITAL_F L"\u2131" #define UNICODE_TURNED_CAPITAL_F 0x2132 #define UNITEXT_TURNED_CAPITAL_F L"\u2132" #define UNICODE_SCRIPT_CAPITAL_M 0x2133 #define UNITEXT_SCRIPT_CAPITAL_M L"\u2133" #define UNICODE_SCRIPT_SMALL_O 0x2134 #define UNITEXT_SCRIPT_SMALL_O L"\u2134" #define UNICODE_ALEF_SYMBOL 0x2135 #define UNITEXT_ALEF_SYMBOL L"\u2135" #define UNICODE_BET_SYMBOL 0x2136 #define UNITEXT_BET_SYMBOL L"\u2136" #define UNICODE_GIMEL_SYMBOL 0x2137 #define UNITEXT_GIMEL_SYMBOL L"\u2137" #define UNICODE_DALET_SYMBOL 0x2138 #define UNITEXT_DALET_SYMBOL L"\u2138" #define UNICODE_INFORMATION_SOURCE 0x2139 #define UNITEXT_INFORMATION_SOURCE L"\u2139" #define UNICODE_ROTATED_CAPITAL_Q 0x213a #define UNITEXT_ROTATED_CAPITAL_Q L"\u213a" #define UNICODE_FACSIMILE_SIGN 0x213b #define UNITEXT_FACSIMILE_SIGN L"\u213b" #define UNICODE_DOUBLE_STRUCK_SMALL_PI 0x213c #define UNITEXT_DOUBLE_STRUCK_SMALL_PI L"\u213c" #define UNICODE_DOUBLE_STRUCK_SMALL_GAMMA 0x213d #define UNITEXT_DOUBLE_STRUCK_SMALL_GAMMA L"\u213d" #define UNICODE_DOUBLE_STRUCK_CAPITAL_GAMMA 0x213e #define UNITEXT_DOUBLE_STRUCK_CAPITAL_GAMMA L"\u213e" #define UNICODE_DOUBLE_STRUCK_CAPITAL_PI 0x213f #define UNITEXT_DOUBLE_STRUCK_CAPITAL_PI L"\u213f" #define UNICODE_DOUBLE_STRUCK_N_ARY_SUMMATION 0x2140 #define UNITEXT_DOUBLE_STRUCK_N_ARY_SUMMATION L"\u2140" #define UNICODE_TURNED_SANS_SERIF_CAPITAL_G 0x2141 #define UNITEXT_TURNED_SANS_SERIF_CAPITAL_G L"\u2141" #define UNICODE_TURNED_SANS_SERIF_CAPITAL_L 0x2142 #define UNITEXT_TURNED_SANS_SERIF_CAPITAL_L L"\u2142" #define UNICODE_REVERSED_SANS_SERIF_CAPITAL_L 0x2143 #define UNITEXT_REVERSED_SANS_SERIF_CAPITAL_L L"\u2143" #define UNICODE_TURNED_SANS_SERIF_CAPITAL_Y 0x2144 #define UNITEXT_TURNED_SANS_SERIF_CAPITAL_Y L"\u2144" #define UNICODE_DOUBLE_STRUCK_ITALIC_CAPITAL_D 0x2145 #define UNITEXT_DOUBLE_STRUCK_ITALIC_CAPITAL_D L"\u2145" #define UNICODE_DOUBLE_STRUCK_ITALIC_SMALL_D 0x2146 #define UNITEXT_DOUBLE_STRUCK_ITALIC_SMALL_D L"\u2146" #define UNICODE_DOUBLE_STRUCK_ITALIC_SMALL_E 0x2147 #define UNITEXT_DOUBLE_STRUCK_ITALIC_SMALL_E L"\u2147" #define UNICODE_DOUBLE_STRUCK_ITALIC_SMALL_I 0x2148 #define UNITEXT_DOUBLE_STRUCK_ITALIC_SMALL_I L"\u2148" #define UNICODE_DOUBLE_STRUCK_ITALIC_SMALL_J 0x2149 #define UNITEXT_DOUBLE_STRUCK_ITALIC_SMALL_J L"\u2149" #define UNICODE_PROPERTY_LINE 0x214a #define UNITEXT_PROPERTY_LINE L"\u214a" #define UNICODE_TURNED_AMPERSAND 0x214b #define UNITEXT_TURNED_AMPERSAND L"\u214b" #define UNICODE_PER_SIGN 0x214c #define UNITEXT_PER_SIGN L"\u214c" #define UNICODE_AKTIESELSKAB 0x214d #define UNITEXT_AKTIESELSKAB L"\u214d" #define UNICODE_TURNED_SMALL_F 0x214e #define UNITEXT_TURNED_SMALL_F L"\u214e" #define UNICODE_VULGAR_FRACTION_ONE_THIRD 0x2153 #define UNITEXT_VULGAR_FRACTION_ONE_THIRD L"\u2153" #define UNICODE_VULGAR_FRACTION_TWO_THIRDS 0x2154 #define UNITEXT_VULGAR_FRACTION_TWO_THIRDS L"\u2154" #define UNICODE_VULGAR_FRACTION_ONE_FIFTH 0x2155 #define UNITEXT_VULGAR_FRACTION_ONE_FIFTH L"\u2155" #define UNICODE_VULGAR_FRACTION_TWO_FIFTHS 0x2156 #define UNITEXT_VULGAR_FRACTION_TWO_FIFTHS L"\u2156" #define UNICODE_VULGAR_FRACTION_THREE_FIFTHS 0x2157 #define UNITEXT_VULGAR_FRACTION_THREE_FIFTHS L"\u2157" #define UNICODE_VULGAR_FRACTION_FOUR_FIFTHS 0x2158 #define UNITEXT_VULGAR_FRACTION_FOUR_FIFTHS L"\u2158" #define UNICODE_VULGAR_FRACTION_ONE_SIXTH 0x2159 #define UNITEXT_VULGAR_FRACTION_ONE_SIXTH L"\u2159" #define UNICODE_VULGAR_FRACTION_FIVE_SIXTHS 0x215a #define UNITEXT_VULGAR_FRACTION_FIVE_SIXTHS L"\u215a" #define UNICODE_VULGAR_FRACTION_ONE_EIGHTH 0x215b #define UNITEXT_VULGAR_FRACTION_ONE_EIGHTH L"\u215b" #define UNICODE_VULGAR_FRACTION_THREE_EIGHTHS 0x215c #define UNITEXT_VULGAR_FRACTION_THREE_EIGHTHS L"\u215c" #define UNICODE_VULGAR_FRACTION_FIVE_EIGHTHS 0x215d #define UNITEXT_VULGAR_FRACTION_FIVE_EIGHTHS L"\u215d" #define UNICODE_VULGAR_FRACTION_SEVEN_EIGHTHS 0x215e #define UNITEXT_VULGAR_FRACTION_SEVEN_EIGHTHS L"\u215e" #define UNICODE_FRACTION_NUMERATOR_ONE 0x215f #define UNITEXT_FRACTION_NUMERATOR_ONE L"\u215f" #define UNICODE_ROMAN_NUMERAL_ONE 0x2160 #define UNITEXT_ROMAN_NUMERAL_ONE L"\u2160" #define UNICODE_ROMAN_NUMERAL_TWO 0x2161 #define UNITEXT_ROMAN_NUMERAL_TWO L"\u2161" #define UNICODE_ROMAN_NUMERAL_THREE 0x2162 #define UNITEXT_ROMAN_NUMERAL_THREE L"\u2162" #define UNICODE_ROMAN_NUMERAL_FOUR 0x2163 #define UNITEXT_ROMAN_NUMERAL_FOUR L"\u2163" #define UNICODE_ROMAN_NUMERAL_FIVE 0x2164 #define UNITEXT_ROMAN_NUMERAL_FIVE L"\u2164" #define UNICODE_ROMAN_NUMERAL_SIX 0x2165 #define UNITEXT_ROMAN_NUMERAL_SIX L"\u2165" #define UNICODE_ROMAN_NUMERAL_SEVEN 0x2166 #define UNITEXT_ROMAN_NUMERAL_SEVEN L"\u2166" #define UNICODE_ROMAN_NUMERAL_EIGHT 0x2167 #define UNITEXT_ROMAN_NUMERAL_EIGHT L"\u2167" #define UNICODE_ROMAN_NUMERAL_NINE 0x2168 #define UNITEXT_ROMAN_NUMERAL_NINE L"\u2168" #define UNICODE_ROMAN_NUMERAL_TEN 0x2169 #define UNITEXT_ROMAN_NUMERAL_TEN L"\u2169" #define UNICODE_ROMAN_NUMERAL_ELEVEN 0x216a #define UNITEXT_ROMAN_NUMERAL_ELEVEN L"\u216a" #define UNICODE_ROMAN_NUMERAL_TWELVE 0x216b #define UNITEXT_ROMAN_NUMERAL_TWELVE L"\u216b" #define UNICODE_ROMAN_NUMERAL_FIFTY 0x216c #define UNITEXT_ROMAN_NUMERAL_FIFTY L"\u216c" #define UNICODE_ROMAN_NUMERAL_ONE_HUNDRED 0x216d #define UNITEXT_ROMAN_NUMERAL_ONE_HUNDRED L"\u216d" #define UNICODE_ROMAN_NUMERAL_FIVE_HUNDRED 0x216e #define UNITEXT_ROMAN_NUMERAL_FIVE_HUNDRED L"\u216e" #define UNICODE_ROMAN_NUMERAL_ONE_THOUSAND 0x216f #define UNITEXT_ROMAN_NUMERAL_ONE_THOUSAND L"\u216f" #define UNICODE_SMALL_ROMAN_NUMERAL_ONE 0x2170 #define UNITEXT_SMALL_ROMAN_NUMERAL_ONE L"\u2170" #define UNICODE_SMALL_ROMAN_NUMERAL_TWO 0x2171 #define UNITEXT_SMALL_ROMAN_NUMERAL_TWO L"\u2171" #define UNICODE_SMALL_ROMAN_NUMERAL_THREE 0x2172 #define UNITEXT_SMALL_ROMAN_NUMERAL_THREE L"\u2172" #define UNICODE_SMALL_ROMAN_NUMERAL_FOUR 0x2173 #define UNITEXT_SMALL_ROMAN_NUMERAL_FOUR L"\u2173" #define UNICODE_SMALL_ROMAN_NUMERAL_FIVE 0x2174 #define UNITEXT_SMALL_ROMAN_NUMERAL_FIVE L"\u2174" #define UNICODE_SMALL_ROMAN_NUMERAL_SIX 0x2175 #define UNITEXT_SMALL_ROMAN_NUMERAL_SIX L"\u2175" #define UNICODE_SMALL_ROMAN_NUMERAL_SEVEN 0x2176 #define UNITEXT_SMALL_ROMAN_NUMERAL_SEVEN L"\u2176" #define UNICODE_SMALL_ROMAN_NUMERAL_EIGHT 0x2177 #define UNITEXT_SMALL_ROMAN_NUMERAL_EIGHT L"\u2177" #define UNICODE_SMALL_ROMAN_NUMERAL_NINE 0x2178 #define UNITEXT_SMALL_ROMAN_NUMERAL_NINE L"\u2178" #define UNICODE_SMALL_ROMAN_NUMERAL_TEN 0x2179 #define UNITEXT_SMALL_ROMAN_NUMERAL_TEN L"\u2179" #define UNICODE_SMALL_ROMAN_NUMERAL_ELEVEN 0x217a #define UNITEXT_SMALL_ROMAN_NUMERAL_ELEVEN L"\u217a" #define UNICODE_SMALL_ROMAN_NUMERAL_TWELVE 0x217b #define UNITEXT_SMALL_ROMAN_NUMERAL_TWELVE L"\u217b" #define UNICODE_SMALL_ROMAN_NUMERAL_FIFTY 0x217c #define UNITEXT_SMALL_ROMAN_NUMERAL_FIFTY L"\u217c" #define UNICODE_SMALL_ROMAN_NUMERAL_ONE_HUNDRED 0x217d #define UNITEXT_SMALL_ROMAN_NUMERAL_ONE_HUNDRED L"\u217d" #define UNICODE_SMALL_ROMAN_NUMERAL_FIVE_HUNDRED 0x217e #define UNITEXT_SMALL_ROMAN_NUMERAL_FIVE_HUNDRED L"\u217e" #define UNICODE_SMALL_ROMAN_NUMERAL_ONE_THOUSAND 0x217f #define UNITEXT_SMALL_ROMAN_NUMERAL_ONE_THOUSAND L"\u217f" #define UNICODE_ROMAN_NUMERAL_ONE_THOUSAND_C_D 0x2180 #define UNITEXT_ROMAN_NUMERAL_ONE_THOUSAND_C_D L"\u2180" #define UNICODE_ROMAN_NUMERAL_FIVE_THOUSAND 0x2181 #define UNITEXT_ROMAN_NUMERAL_FIVE_THOUSAND L"\u2181" #define UNICODE_ROMAN_NUMERAL_TEN_THOUSAND 0x2182 #define UNITEXT_ROMAN_NUMERAL_TEN_THOUSAND L"\u2182" #define UNICODE_ROMAN_NUMERAL_REVERSED_ONE_HUNDRED 0x2183 #define UNITEXT_ROMAN_NUMERAL_REVERSED_ONE_HUNDRED L"\u2183" #define UNICODE_LATIN_SMALL_LETTER_REVERSED_C 0x2184 #define UNITEXT_LATIN_SMALL_LETTER_REVERSED_C L"\u2184" #define UNICODE_LEFTWARDS_ARROW 0x2190 #define UNITEXT_LEFTWARDS_ARROW L"\u2190" #define UNICODE_UPWARDS_ARROW 0x2191 #define UNITEXT_UPWARDS_ARROW L"\u2191" #define UNICODE_RIGHTWARDS_ARROW 0x2192 #define UNITEXT_RIGHTWARDS_ARROW L"\u2192" #define UNICODE_DOWNWARDS_ARROW 0x2193 #define UNITEXT_DOWNWARDS_ARROW L"\u2193" #define UNICODE_LEFT_RIGHT_ARROW 0x2194 #define UNITEXT_LEFT_RIGHT_ARROW L"\u2194" #define UNICODE_UP_DOWN_ARROW 0x2195 #define UNITEXT_UP_DOWN_ARROW L"\u2195" #define UNICODE_NORTH_WEST_ARROW 0x2196 #define UNITEXT_NORTH_WEST_ARROW L"\u2196" #define UNICODE_NORTH_EAST_ARROW 0x2197 #define UNITEXT_NORTH_EAST_ARROW L"\u2197" #define UNICODE_SOUTH_EAST_ARROW 0x2198 #define UNITEXT_SOUTH_EAST_ARROW L"\u2198" #define UNICODE_SOUTH_WEST_ARROW 0x2199 #define UNITEXT_SOUTH_WEST_ARROW L"\u2199" #define UNICODE_LEFTWARDS_ARROW_WITH_STROKE 0x219a #define UNITEXT_LEFTWARDS_ARROW_WITH_STROKE L"\u219a" #define UNICODE_RIGHTWARDS_ARROW_WITH_STROKE 0x219b #define UNITEXT_RIGHTWARDS_ARROW_WITH_STROKE L"\u219b" #define UNICODE_LEFTWARDS_WAVE_ARROW 0x219c #define UNITEXT_LEFTWARDS_WAVE_ARROW L"\u219c" #define UNICODE_RIGHTWARDS_WAVE_ARROW 0x219d #define UNITEXT_RIGHTWARDS_WAVE_ARROW L"\u219d" #define UNICODE_LEFTWARDS_TWO_HEADED_ARROW 0x219e #define UNITEXT_LEFTWARDS_TWO_HEADED_ARROW L"\u219e" #define UNICODE_UPWARDS_TWO_HEADED_ARROW 0x219f #define UNITEXT_UPWARDS_TWO_HEADED_ARROW L"\u219f" #define UNICODE_RIGHTWARDS_TWO_HEADED_ARROW 0x21a0 #define UNITEXT_RIGHTWARDS_TWO_HEADED_ARROW L"\u21a0" #define UNICODE_DOWNWARDS_TWO_HEADED_ARROW 0x21a1 #define UNITEXT_DOWNWARDS_TWO_HEADED_ARROW L"\u21a1" #define UNICODE_LEFTWARDS_ARROW_WITH_TAIL 0x21a2 #define UNITEXT_LEFTWARDS_ARROW_WITH_TAIL L"\u21a2" #define UNICODE_RIGHTWARDS_ARROW_WITH_TAIL 0x21a3 #define UNITEXT_RIGHTWARDS_ARROW_WITH_TAIL L"\u21a3" #define UNICODE_LEFTWARDS_ARROW_FROM_BAR 0x21a4 #define UNITEXT_LEFTWARDS_ARROW_FROM_BAR L"\u21a4" #define UNICODE_UPWARDS_ARROW_FROM_BAR 0x21a5 #define UNITEXT_UPWARDS_ARROW_FROM_BAR L"\u21a5" #define UNICODE_RIGHTWARDS_ARROW_FROM_BAR 0x21a6 #define UNITEXT_RIGHTWARDS_ARROW_FROM_BAR L"\u21a6" #define UNICODE_DOWNWARDS_ARROW_FROM_BAR 0x21a7 #define UNITEXT_DOWNWARDS_ARROW_FROM_BAR L"\u21a7" #define UNICODE_UP_DOWN_ARROW_WITH_BASE 0x21a8 #define UNITEXT_UP_DOWN_ARROW_WITH_BASE L"\u21a8" #define UNICODE_LEFTWARDS_ARROW_WITH_HOOK 0x21a9 #define UNITEXT_LEFTWARDS_ARROW_WITH_HOOK L"\u21a9" #define UNICODE_RIGHTWARDS_ARROW_WITH_HOOK 0x21aa #define UNITEXT_RIGHTWARDS_ARROW_WITH_HOOK L"\u21aa" #define UNICODE_LEFTWARDS_ARROW_WITH_LOOP 0x21ab #define UNITEXT_LEFTWARDS_ARROW_WITH_LOOP L"\u21ab" #define UNICODE_RIGHTWARDS_ARROW_WITH_LOOP 0x21ac #define UNITEXT_RIGHTWARDS_ARROW_WITH_LOOP L"\u21ac" #define UNICODE_LEFT_RIGHT_WAVE_ARROW 0x21ad #define UNITEXT_LEFT_RIGHT_WAVE_ARROW L"\u21ad" #define UNICODE_LEFT_RIGHT_ARROW_WITH_STROKE 0x21ae #define UNITEXT_LEFT_RIGHT_ARROW_WITH_STROKE L"\u21ae" #define UNICODE_DOWNWARDS_ZIGZAG_ARROW 0x21af #define UNITEXT_DOWNWARDS_ZIGZAG_ARROW L"\u21af" #define UNICODE_UPWARDS_ARROW_WITH_TIP_LEFTWARDS 0x21b0 #define UNITEXT_UPWARDS_ARROW_WITH_TIP_LEFTWARDS L"\u21b0" #define UNICODE_UPWARDS_ARROW_WITH_TIP_RIGHTWARDS 0x21b1 #define UNITEXT_UPWARDS_ARROW_WITH_TIP_RIGHTWARDS L"\u21b1" #define UNICODE_DOWNWARDS_ARROW_WITH_TIP_LEFTWARDS 0x21b2 #define UNITEXT_DOWNWARDS_ARROW_WITH_TIP_LEFTWARDS L"\u21b2" #define UNICODE_DOWNWARDS_ARROW_WITH_TIP_RIGHTWARDS 0x21b3 #define UNITEXT_DOWNWARDS_ARROW_WITH_TIP_RIGHTWARDS L"\u21b3" #define UNICODE_RIGHTWARDS_ARROW_WITH_CORNER_DOWNWARDS 0x21b4 #define UNITEXT_RIGHTWARDS_ARROW_WITH_CORNER_DOWNWARDS L"\u21b4" #define UNICODE_DOWNWARDS_ARROW_WITH_CORNER_LEFTWARDS 0x21b5 #define UNITEXT_DOWNWARDS_ARROW_WITH_CORNER_LEFTWARDS L"\u21b5" #define UNICODE_ANTICLOCKWISE_TOP_SEMICIRCLE_ARROW 0x21b6 #define UNITEXT_ANTICLOCKWISE_TOP_SEMICIRCLE_ARROW L"\u21b6" #define UNICODE_CLOCKWISE_TOP_SEMICIRCLE_ARROW 0x21b7 #define UNITEXT_CLOCKWISE_TOP_SEMICIRCLE_ARROW L"\u21b7" #define UNICODE_NORTH_WEST_ARROW_TO_LONG_BAR 0x21b8 #define UNITEXT_NORTH_WEST_ARROW_TO_LONG_BAR L"\u21b8" #define UNICODE_LEFTWARDS_ARROW_TO_BAR_OVER_RIGHTWARDS_ARROW_TO_BAR 0x21b9 #define UNITEXT_LEFTWARDS_ARROW_TO_BAR_OVER_RIGHTWARDS_ARROW_TO_BAR L"\u21b9" #define UNICODE_ANTICLOCKWISE_OPEN_CIRCLE_ARROW 0x21ba #define UNITEXT_ANTICLOCKWISE_OPEN_CIRCLE_ARROW L"\u21ba" #define UNICODE_CLOCKWISE_OPEN_CIRCLE_ARROW 0x21bb #define UNITEXT_CLOCKWISE_OPEN_CIRCLE_ARROW L"\u21bb" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_UPWARDS 0x21bc #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_UPWARDS L"\u21bc" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_DOWNWARDS 0x21bd #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_DOWNWARDS L"\u21bd" #define UNICODE_UPWARDS_HARPOON_WITH_BARB_RIGHTWARDS 0x21be #define UNITEXT_UPWARDS_HARPOON_WITH_BARB_RIGHTWARDS L"\u21be" #define UNICODE_UPWARDS_HARPOON_WITH_BARB_LEFTWARDS 0x21bf #define UNITEXT_UPWARDS_HARPOON_WITH_BARB_LEFTWARDS L"\u21bf" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_UPWARDS 0x21c0 #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_UPWARDS L"\u21c0" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_DOWNWARDS 0x21c1 #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_DOWNWARDS L"\u21c1" #define UNICODE_DOWNWARDS_HARPOON_WITH_BARB_RIGHTWARDS 0x21c2 #define UNITEXT_DOWNWARDS_HARPOON_WITH_BARB_RIGHTWARDS L"\u21c2" #define UNICODE_DOWNWARDS_HARPOON_WITH_BARB_LEFTWARDS 0x21c3 #define UNITEXT_DOWNWARDS_HARPOON_WITH_BARB_LEFTWARDS L"\u21c3" #define UNICODE_RIGHTWARDS_ARROW_OVER_LEFTWARDS_ARROW 0x21c4 #define UNITEXT_RIGHTWARDS_ARROW_OVER_LEFTWARDS_ARROW L"\u21c4" #define UNICODE_UPWARDS_ARROW_LEFTWARDS_OF_DOWNWARDS_ARROW 0x21c5 #define UNITEXT_UPWARDS_ARROW_LEFTWARDS_OF_DOWNWARDS_ARROW L"\u21c5" #define UNICODE_LEFTWARDS_ARROW_OVER_RIGHTWARDS_ARROW 0x21c6 #define UNITEXT_LEFTWARDS_ARROW_OVER_RIGHTWARDS_ARROW L"\u21c6" #define UNICODE_LEFTWARDS_PAIRED_ARROWS 0x21c7 #define UNITEXT_LEFTWARDS_PAIRED_ARROWS L"\u21c7" #define UNICODE_UPWARDS_PAIRED_ARROWS 0x21c8 #define UNITEXT_UPWARDS_PAIRED_ARROWS L"\u21c8" #define UNICODE_RIGHTWARDS_PAIRED_ARROWS 0x21c9 #define UNITEXT_RIGHTWARDS_PAIRED_ARROWS L"\u21c9" #define UNICODE_DOWNWARDS_PAIRED_ARROWS 0x21ca #define UNITEXT_DOWNWARDS_PAIRED_ARROWS L"\u21ca" #define UNICODE_LEFTWARDS_HARPOON_OVER_RIGHTWARDS_HARPOON 0x21cb #define UNITEXT_LEFTWARDS_HARPOON_OVER_RIGHTWARDS_HARPOON L"\u21cb" #define UNICODE_RIGHTWARDS_HARPOON_OVER_LEFTWARDS_HARPOON 0x21cc #define UNITEXT_RIGHTWARDS_HARPOON_OVER_LEFTWARDS_HARPOON L"\u21cc" #define UNICODE_LEFTWARDS_DOUBLE_ARROW_WITH_STROKE 0x21cd #define UNITEXT_LEFTWARDS_DOUBLE_ARROW_WITH_STROKE L"\u21cd" #define UNICODE_LEFT_RIGHT_DOUBLE_ARROW_WITH_STROKE 0x21ce #define UNITEXT_LEFT_RIGHT_DOUBLE_ARROW_WITH_STROKE L"\u21ce" #define UNICODE_RIGHTWARDS_DOUBLE_ARROW_WITH_STROKE 0x21cf #define UNITEXT_RIGHTWARDS_DOUBLE_ARROW_WITH_STROKE L"\u21cf" #define UNICODE_LEFTWARDS_DOUBLE_ARROW 0x21d0 #define UNITEXT_LEFTWARDS_DOUBLE_ARROW L"\u21d0" #define UNICODE_UPWARDS_DOUBLE_ARROW 0x21d1 #define UNITEXT_UPWARDS_DOUBLE_ARROW L"\u21d1" #define UNICODE_RIGHTWARDS_DOUBLE_ARROW 0x21d2 #define UNITEXT_RIGHTWARDS_DOUBLE_ARROW L"\u21d2" #define UNICODE_DOWNWARDS_DOUBLE_ARROW 0x21d3 #define UNITEXT_DOWNWARDS_DOUBLE_ARROW L"\u21d3" #define UNICODE_LEFT_RIGHT_DOUBLE_ARROW 0x21d4 #define UNITEXT_LEFT_RIGHT_DOUBLE_ARROW L"\u21d4" #define UNICODE_UP_DOWN_DOUBLE_ARROW 0x21d5 #define UNITEXT_UP_DOWN_DOUBLE_ARROW L"\u21d5" #define UNICODE_NORTH_WEST_DOUBLE_ARROW 0x21d6 #define UNITEXT_NORTH_WEST_DOUBLE_ARROW L"\u21d6" #define UNICODE_NORTH_EAST_DOUBLE_ARROW 0x21d7 #define UNITEXT_NORTH_EAST_DOUBLE_ARROW L"\u21d7" #define UNICODE_SOUTH_EAST_DOUBLE_ARROW 0x21d8 #define UNITEXT_SOUTH_EAST_DOUBLE_ARROW L"\u21d8" #define UNICODE_SOUTH_WEST_DOUBLE_ARROW 0x21d9 #define UNITEXT_SOUTH_WEST_DOUBLE_ARROW L"\u21d9" #define UNICODE_LEFTWARDS_TRIPLE_ARROW 0x21da #define UNITEXT_LEFTWARDS_TRIPLE_ARROW L"\u21da" #define UNICODE_RIGHTWARDS_TRIPLE_ARROW 0x21db #define UNITEXT_RIGHTWARDS_TRIPLE_ARROW L"\u21db" #define UNICODE_LEFTWARDS_SQUIGGLE_ARROW 0x21dc #define UNITEXT_LEFTWARDS_SQUIGGLE_ARROW L"\u21dc" #define UNICODE_RIGHTWARDS_SQUIGGLE_ARROW 0x21dd #define UNITEXT_RIGHTWARDS_SQUIGGLE_ARROW L"\u21dd" #define UNICODE_UPWARDS_ARROW_WITH_DOUBLE_STROKE 0x21de #define UNITEXT_UPWARDS_ARROW_WITH_DOUBLE_STROKE L"\u21de" #define UNICODE_DOWNWARDS_ARROW_WITH_DOUBLE_STROKE 0x21df #define UNITEXT_DOWNWARDS_ARROW_WITH_DOUBLE_STROKE L"\u21df" #define UNICODE_LEFTWARDS_DASHED_ARROW 0x21e0 #define UNITEXT_LEFTWARDS_DASHED_ARROW L"\u21e0" #define UNICODE_UPWARDS_DASHED_ARROW 0x21e1 #define UNITEXT_UPWARDS_DASHED_ARROW L"\u21e1" #define UNICODE_RIGHTWARDS_DASHED_ARROW 0x21e2 #define UNITEXT_RIGHTWARDS_DASHED_ARROW L"\u21e2" #define UNICODE_DOWNWARDS_DASHED_ARROW 0x21e3 #define UNITEXT_DOWNWARDS_DASHED_ARROW L"\u21e3" #define UNICODE_LEFTWARDS_ARROW_TO_BAR 0x21e4 #define UNITEXT_LEFTWARDS_ARROW_TO_BAR L"\u21e4" #define UNICODE_RIGHTWARDS_ARROW_TO_BAR 0x21e5 #define UNITEXT_RIGHTWARDS_ARROW_TO_BAR L"\u21e5" #define UNICODE_LEFTWARDS_WHITE_ARROW 0x21e6 #define UNITEXT_LEFTWARDS_WHITE_ARROW L"\u21e6" #define UNICODE_UPWARDS_WHITE_ARROW 0x21e7 #define UNITEXT_UPWARDS_WHITE_ARROW L"\u21e7" #define UNICODE_RIGHTWARDS_WHITE_ARROW 0x21e8 #define UNITEXT_RIGHTWARDS_WHITE_ARROW L"\u21e8" #define UNICODE_DOWNWARDS_WHITE_ARROW 0x21e9 #define UNITEXT_DOWNWARDS_WHITE_ARROW L"\u21e9" #define UNICODE_UPWARDS_WHITE_ARROW_FROM_BAR 0x21ea #define UNITEXT_UPWARDS_WHITE_ARROW_FROM_BAR L"\u21ea" #define UNICODE_UPWARDS_WHITE_ARROW_ON_PEDESTAL 0x21eb #define UNITEXT_UPWARDS_WHITE_ARROW_ON_PEDESTAL L"\u21eb" #define UNICODE_UPWARDS_WHITE_ARROW_ON_PEDESTAL_WITH_HORIZONTAL_BAR 0x21ec #define UNITEXT_UPWARDS_WHITE_ARROW_ON_PEDESTAL_WITH_HORIZONTAL_BAR L"\u21ec" #define UNICODE_UPWARDS_WHITE_ARROW_ON_PEDESTAL_WITH_VERTICAL_BAR 0x21ed #define UNITEXT_UPWARDS_WHITE_ARROW_ON_PEDESTAL_WITH_VERTICAL_BAR L"\u21ed" #define UNICODE_UPWARDS_WHITE_DOUBLE_ARROW 0x21ee #define UNITEXT_UPWARDS_WHITE_DOUBLE_ARROW L"\u21ee" #define UNICODE_UPWARDS_WHITE_DOUBLE_ARROW_ON_PEDESTAL 0x21ef #define UNITEXT_UPWARDS_WHITE_DOUBLE_ARROW_ON_PEDESTAL L"\u21ef" #define UNICODE_RIGHTWARDS_WHITE_ARROW_FROM_WALL 0x21f0 #define UNITEXT_RIGHTWARDS_WHITE_ARROW_FROM_WALL L"\u21f0" #define UNICODE_NORTH_WEST_ARROW_TO_CORNER 0x21f1 #define UNITEXT_NORTH_WEST_ARROW_TO_CORNER L"\u21f1" #define UNICODE_SOUTH_EAST_ARROW_TO_CORNER 0x21f2 #define UNITEXT_SOUTH_EAST_ARROW_TO_CORNER L"\u21f2" #define UNICODE_UP_DOWN_WHITE_ARROW 0x21f3 #define UNITEXT_UP_DOWN_WHITE_ARROW L"\u21f3" #define UNICODE_RIGHT_ARROW_WITH_SMALL_CIRCLE 0x21f4 #define UNITEXT_RIGHT_ARROW_WITH_SMALL_CIRCLE L"\u21f4" #define UNICODE_DOWNWARDS_ARROW_LEFTWARDS_OF_UPWARDS_ARROW 0x21f5 #define UNITEXT_DOWNWARDS_ARROW_LEFTWARDS_OF_UPWARDS_ARROW L"\u21f5" #define UNICODE_THREE_RIGHTWARDS_ARROWS 0x21f6 #define UNITEXT_THREE_RIGHTWARDS_ARROWS L"\u21f6" #define UNICODE_LEFTWARDS_ARROW_WITH_VERTICAL_STROKE 0x21f7 #define UNITEXT_LEFTWARDS_ARROW_WITH_VERTICAL_STROKE L"\u21f7" #define UNICODE_RIGHTWARDS_ARROW_WITH_VERTICAL_STROKE 0x21f8 #define UNITEXT_RIGHTWARDS_ARROW_WITH_VERTICAL_STROKE L"\u21f8" #define UNICODE_LEFT_RIGHT_ARROW_WITH_VERTICAL_STROKE 0x21f9 #define UNITEXT_LEFT_RIGHT_ARROW_WITH_VERTICAL_STROKE L"\u21f9" #define UNICODE_LEFTWARDS_ARROW_WITH_DOUBLE_VERTICAL_STROKE 0x21fa #define UNITEXT_LEFTWARDS_ARROW_WITH_DOUBLE_VERTICAL_STROKE L"\u21fa" #define UNICODE_RIGHTWARDS_ARROW_WITH_DOUBLE_VERTICAL_STROKE 0x21fb #define UNITEXT_RIGHTWARDS_ARROW_WITH_DOUBLE_VERTICAL_STROKE L"\u21fb" #define UNICODE_LEFT_RIGHT_ARROW_WITH_DOUBLE_VERTICAL_STROKE 0x21fc #define UNITEXT_LEFT_RIGHT_ARROW_WITH_DOUBLE_VERTICAL_STROKE L"\u21fc" #define UNICODE_LEFTWARDS_OPEN_HEADED_ARROW 0x21fd #define UNITEXT_LEFTWARDS_OPEN_HEADED_ARROW L"\u21fd" #define UNICODE_RIGHTWARDS_OPEN_HEADED_ARROW 0x21fe #define UNITEXT_RIGHTWARDS_OPEN_HEADED_ARROW L"\u21fe" #define UNICODE_LEFT_RIGHT_OPEN_HEADED_ARROW 0x21ff #define UNITEXT_LEFT_RIGHT_OPEN_HEADED_ARROW L"\u21ff" #define UNICODE_FOR_ALL 0x2200 #define UNITEXT_FOR_ALL L"\u2200" #define UNICODE_COMPLEMENT 0x2201 #define UNITEXT_COMPLEMENT L"\u2201" #define UNICODE_PARTIAL_DIFFERENTIAL 0x2202 #define UNITEXT_PARTIAL_DIFFERENTIAL L"\u2202" #define UNICODE_THERE_EXISTS 0x2203 #define UNITEXT_THERE_EXISTS L"\u2203" #define UNICODE_THERE_DOES_NOT_EXIST 0x2204 #define UNITEXT_THERE_DOES_NOT_EXIST L"\u2204" #define UNICODE_EMPTY_SET 0x2205 #define UNITEXT_EMPTY_SET L"\u2205" #define UNICODE_INCREMENT 0x2206 #define UNITEXT_INCREMENT L"\u2206" #define UNICODE_NABLA 0x2207 #define UNITEXT_NABLA L"\u2207" #define UNICODE_ELEMENT_OF 0x2208 #define UNITEXT_ELEMENT_OF L"\u2208" #define UNICODE_NOT_AN_ELEMENT_OF 0x2209 #define UNITEXT_NOT_AN_ELEMENT_OF L"\u2209" #define UNICODE_SMALL_ELEMENT_OF 0x220a #define UNITEXT_SMALL_ELEMENT_OF L"\u220a" #define UNICODE_CONTAINS_AS_MEMBER 0x220b #define UNITEXT_CONTAINS_AS_MEMBER L"\u220b" #define UNICODE_DOES_NOT_CONTAIN_AS_MEMBER 0x220c #define UNITEXT_DOES_NOT_CONTAIN_AS_MEMBER L"\u220c" #define UNICODE_SMALL_CONTAINS_AS_MEMBER 0x220d #define UNITEXT_SMALL_CONTAINS_AS_MEMBER L"\u220d" #define UNICODE_END_OF_PROOF 0x220e #define UNITEXT_END_OF_PROOF L"\u220e" #define UNICODE_N_ARY_PRODUCT 0x220f #define UNITEXT_N_ARY_PRODUCT L"\u220f" #define UNICODE_N_ARY_COPRODUCT 0x2210 #define UNITEXT_N_ARY_COPRODUCT L"\u2210" #define UNICODE_N_ARY_SUMMATION 0x2211 #define UNITEXT_N_ARY_SUMMATION L"\u2211" #define UNICODE_MINUS_SIGN 0x2212 #define UNITEXT_MINUS_SIGN L"\u2212" #define UNICODE_MINUS_OR_PLUS_SIGN 0x2213 #define UNITEXT_MINUS_OR_PLUS_SIGN L"\u2213" #define UNICODE_DOT_PLUS 0x2214 #define UNITEXT_DOT_PLUS L"\u2214" #define UNICODE_DIVISION_SLASH 0x2215 #define UNITEXT_DIVISION_SLASH L"\u2215" #define UNICODE_SET_MINUS 0x2216 #define UNITEXT_SET_MINUS L"\u2216" #define UNICODE_ASTERISK_OPERATOR 0x2217 #define UNITEXT_ASTERISK_OPERATOR L"\u2217" #define UNICODE_RING_OPERATOR 0x2218 #define UNITEXT_RING_OPERATOR L"\u2218" #define UNICODE_BULLET_OPERATOR 0x2219 #define UNITEXT_BULLET_OPERATOR L"\u2219" #define UNICODE_SQUARE_ROOT 0x221a #define UNITEXT_SQUARE_ROOT L"\u221a" #define UNICODE_CUBE_ROOT 0x221b #define UNITEXT_CUBE_ROOT L"\u221b" #define UNICODE_FOURTH_ROOT 0x221c #define UNITEXT_FOURTH_ROOT L"\u221c" #define UNICODE_PROPORTIONAL_TO 0x221d #define UNITEXT_PROPORTIONAL_TO L"\u221d" #define UNICODE_INFINITY 0x221e #define UNITEXT_INFINITY L"\u221e" #define UNICODE_RIGHT_ANGLE 0x221f #define UNITEXT_RIGHT_ANGLE L"\u221f" #define UNICODE_ANGLE 0x2220 #define UNITEXT_ANGLE L"\u2220" #define UNICODE_MEASURED_ANGLE 0x2221 #define UNITEXT_MEASURED_ANGLE L"\u2221" #define UNICODE_SPHERICAL_ANGLE 0x2222 #define UNITEXT_SPHERICAL_ANGLE L"\u2222" #define UNICODE_DIVIDES 0x2223 #define UNITEXT_DIVIDES L"\u2223" #define UNICODE_DOES_NOT_DIVIDE 0x2224 #define UNITEXT_DOES_NOT_DIVIDE L"\u2224" #define UNICODE_PARALLEL_TO 0x2225 #define UNITEXT_PARALLEL_TO L"\u2225" #define UNICODE_NOT_PARALLEL_TO 0x2226 #define UNITEXT_NOT_PARALLEL_TO L"\u2226" #define UNICODE_LOGICAL_AND 0x2227 #define UNITEXT_LOGICAL_AND L"\u2227" #define UNICODE_LOGICAL_OR 0x2228 #define UNITEXT_LOGICAL_OR L"\u2228" #define UNICODE_INTERSECTION 0x2229 #define UNITEXT_INTERSECTION L"\u2229" #define UNICODE_UNION 0x222a #define UNITEXT_UNION L"\u222a" #define UNICODE_INTEGRAL 0x222b #define UNITEXT_INTEGRAL L"\u222b" #define UNICODE_DOUBLE_INTEGRAL 0x222c #define UNITEXT_DOUBLE_INTEGRAL L"\u222c" #define UNICODE_TRIPLE_INTEGRAL 0x222d #define UNITEXT_TRIPLE_INTEGRAL L"\u222d" #define UNICODE_CONTOUR_INTEGRAL 0x222e #define UNITEXT_CONTOUR_INTEGRAL L"\u222e" #define UNICODE_SURFACE_INTEGRAL 0x222f #define UNITEXT_SURFACE_INTEGRAL L"\u222f" #define UNICODE_VOLUME_INTEGRAL 0x2230 #define UNITEXT_VOLUME_INTEGRAL L"\u2230" #define UNICODE_CLOCKWISE_INTEGRAL 0x2231 #define UNITEXT_CLOCKWISE_INTEGRAL L"\u2231" #define UNICODE_CLOCKWISE_CONTOUR_INTEGRAL 0x2232 #define UNITEXT_CLOCKWISE_CONTOUR_INTEGRAL L"\u2232" #define UNICODE_ANTICLOCKWISE_CONTOUR_INTEGRAL 0x2233 #define UNITEXT_ANTICLOCKWISE_CONTOUR_INTEGRAL L"\u2233" #define UNICODE_THEREFORE 0x2234 #define UNITEXT_THEREFORE L"\u2234" #define UNICODE_BECAUSE 0x2235 #define UNITEXT_BECAUSE L"\u2235" #define UNICODE_RATIO 0x2236 #define UNITEXT_RATIO L"\u2236" #define UNICODE_PROPORTION 0x2237 #define UNITEXT_PROPORTION L"\u2237" #define UNICODE_DOT_MINUS 0x2238 #define UNITEXT_DOT_MINUS L"\u2238" #define UNICODE_EXCESS 0x2239 #define UNITEXT_EXCESS L"\u2239" #define UNICODE_GEOMETRIC_PROPORTION 0x223a #define UNITEXT_GEOMETRIC_PROPORTION L"\u223a" #define UNICODE_HOMOTHETIC 0x223b #define UNITEXT_HOMOTHETIC L"\u223b" #define UNICODE_TILDE_OPERATOR 0x223c #define UNITEXT_TILDE_OPERATOR L"\u223c" #define UNICODE_REVERSED_TILDE 0x223d #define UNITEXT_REVERSED_TILDE L"\u223d" #define UNICODE_INVERTED_LAZY_S 0x223e #define UNITEXT_INVERTED_LAZY_S L"\u223e" #define UNICODE_SINE_WAVE 0x223f #define UNITEXT_SINE_WAVE L"\u223f" #define UNICODE_WREATH_PRODUCT 0x2240 #define UNITEXT_WREATH_PRODUCT L"\u2240" #define UNICODE_NOT_TILDE 0x2241 #define UNITEXT_NOT_TILDE L"\u2241" #define UNICODE_MINUS_TILDE 0x2242 #define UNITEXT_MINUS_TILDE L"\u2242" #define UNICODE_ASYMPTOTICALLY_EQUAL_TO 0x2243 #define UNITEXT_ASYMPTOTICALLY_EQUAL_TO L"\u2243" #define UNICODE_NOT_ASYMPTOTICALLY_EQUAL_TO 0x2244 #define UNITEXT_NOT_ASYMPTOTICALLY_EQUAL_TO L"\u2244" #define UNICODE_APPROXIMATELY_EQUAL_TO 0x2245 #define UNITEXT_APPROXIMATELY_EQUAL_TO L"\u2245" #define UNICODE_APPROXIMATELY_BUT_NOT_ACTUALLY_EQUAL_TO 0x2246 #define UNITEXT_APPROXIMATELY_BUT_NOT_ACTUALLY_EQUAL_TO L"\u2246" #define UNICODE_NEITHER_APPROXIMATELY_NOR_ACTUALLY_EQUAL_TO 0x2247 #define UNITEXT_NEITHER_APPROXIMATELY_NOR_ACTUALLY_EQUAL_TO L"\u2247" #define UNICODE_ALMOST_EQUAL_TO 0x2248 #define UNITEXT_ALMOST_EQUAL_TO L"\u2248" #define UNICODE_NOT_ALMOST_EQUAL_TO 0x2249 #define UNITEXT_NOT_ALMOST_EQUAL_TO L"\u2249" #define UNICODE_ALMOST_EQUAL_OR_EQUAL_TO 0x224a #define UNITEXT_ALMOST_EQUAL_OR_EQUAL_TO L"\u224a" #define UNICODE_TRIPLE_TILDE 0x224b #define UNITEXT_TRIPLE_TILDE L"\u224b" #define UNICODE_ALL_EQUAL_TO 0x224c #define UNITEXT_ALL_EQUAL_TO L"\u224c" #define UNICODE_EQUIVALENT_TO 0x224d #define UNITEXT_EQUIVALENT_TO L"\u224d" #define UNICODE_GEOMETRICALLY_EQUIVALENT_TO 0x224e #define UNITEXT_GEOMETRICALLY_EQUIVALENT_TO L"\u224e" #define UNICODE_DIFFERENCE_BETWEEN 0x224f #define UNITEXT_DIFFERENCE_BETWEEN L"\u224f" #define UNICODE_APPROACHES_THE_LIMIT 0x2250 #define UNITEXT_APPROACHES_THE_LIMIT L"\u2250" #define UNICODE_GEOMETRICALLY_EQUAL_TO 0x2251 #define UNITEXT_GEOMETRICALLY_EQUAL_TO L"\u2251" #define UNICODE_APPROXIMATELY_EQUAL_TO_OR_THE_IMAGE_OF 0x2252 #define UNITEXT_APPROXIMATELY_EQUAL_TO_OR_THE_IMAGE_OF L"\u2252" #define UNICODE_IMAGE_OF_OR_APPROXIMATELY_EQUAL_TO 0x2253 #define UNITEXT_IMAGE_OF_OR_APPROXIMATELY_EQUAL_TO L"\u2253" #define UNICODE_COLON_EQUALS 0x2254 #define UNITEXT_COLON_EQUALS L"\u2254" #define UNICODE_EQUALS_COLON 0x2255 #define UNITEXT_EQUALS_COLON L"\u2255" #define UNICODE_RING_IN_EQUAL_TO 0x2256 #define UNITEXT_RING_IN_EQUAL_TO L"\u2256" #define UNICODE_RING_EQUAL_TO 0x2257 #define UNITEXT_RING_EQUAL_TO L"\u2257" #define UNICODE_CORRESPONDS_TO 0x2258 #define UNITEXT_CORRESPONDS_TO L"\u2258" #define UNICODE_ESTIMATES 0x2259 #define UNITEXT_ESTIMATES L"\u2259" #define UNICODE_EQUIANGULAR_TO 0x225a #define UNITEXT_EQUIANGULAR_TO L"\u225a" #define UNICODE_STAR_EQUALS 0x225b #define UNITEXT_STAR_EQUALS L"\u225b" #define UNICODE_DELTA_EQUAL_TO 0x225c #define UNITEXT_DELTA_EQUAL_TO L"\u225c" #define UNICODE_EQUAL_TO_BY_DEFINITION 0x225d #define UNITEXT_EQUAL_TO_BY_DEFINITION L"\u225d" #define UNICODE_MEASURED_BY 0x225e #define UNITEXT_MEASURED_BY L"\u225e" #define UNICODE_QUESTIONED_EQUAL_TO 0x225f #define UNITEXT_QUESTIONED_EQUAL_TO L"\u225f" #define UNICODE_NOT_EQUAL_TO 0x2260 #define UNITEXT_NOT_EQUAL_TO L"\u2260" #define UNICODE_IDENTICAL_TO 0x2261 #define UNITEXT_IDENTICAL_TO L"\u2261" #define UNICODE_NOT_IDENTICAL_TO 0x2262 #define UNITEXT_NOT_IDENTICAL_TO L"\u2262" #define UNICODE_STRICTLY_EQUIVALENT_TO 0x2263 #define UNITEXT_STRICTLY_EQUIVALENT_TO L"\u2263" #define UNICODE_LESS_THAN_OR_EQUAL_TO 0x2264 #define UNITEXT_LESS_THAN_OR_EQUAL_TO L"\u2264" #define UNICODE_GREATER_THAN_OR_EQUAL_TO 0x2265 #define UNITEXT_GREATER_THAN_OR_EQUAL_TO L"\u2265" #define UNICODE_LESS_THAN_OVER_EQUAL_TO 0x2266 #define UNITEXT_LESS_THAN_OVER_EQUAL_TO L"\u2266" #define UNICODE_GREATER_THAN_OVER_EQUAL_TO 0x2267 #define UNITEXT_GREATER_THAN_OVER_EQUAL_TO L"\u2267" #define UNICODE_LESS_THAN_BUT_NOT_EQUAL_TO 0x2268 #define UNITEXT_LESS_THAN_BUT_NOT_EQUAL_TO L"\u2268" #define UNICODE_GREATER_THAN_BUT_NOT_EQUAL_TO 0x2269 #define UNITEXT_GREATER_THAN_BUT_NOT_EQUAL_TO L"\u2269" #define UNICODE_MUCH_LESS_THAN 0x226a #define UNITEXT_MUCH_LESS_THAN L"\u226a" #define UNICODE_MUCH_GREATER_THAN 0x226b #define UNITEXT_MUCH_GREATER_THAN L"\u226b" #define UNICODE_BETWEEN 0x226c #define UNITEXT_BETWEEN L"\u226c" #define UNICODE_NOT_EQUIVALENT_TO 0x226d #define UNITEXT_NOT_EQUIVALENT_TO L"\u226d" #define UNICODE_NOT_LESS_THAN 0x226e #define UNITEXT_NOT_LESS_THAN L"\u226e" #define UNICODE_NOT_GREATER_THAN 0x226f #define UNITEXT_NOT_GREATER_THAN L"\u226f" #define UNICODE_NEITHER_LESS_THAN_NOR_EQUAL_TO 0x2270 #define UNITEXT_NEITHER_LESS_THAN_NOR_EQUAL_TO L"\u2270" #define UNICODE_NEITHER_GREATER_THAN_NOR_EQUAL_TO 0x2271 #define UNITEXT_NEITHER_GREATER_THAN_NOR_EQUAL_TO L"\u2271" #define UNICODE_LESS_THAN_OR_EQUIVALENT_TO 0x2272 #define UNITEXT_LESS_THAN_OR_EQUIVALENT_TO L"\u2272" #define UNICODE_GREATER_THAN_OR_EQUIVALENT_TO 0x2273 #define UNITEXT_GREATER_THAN_OR_EQUIVALENT_TO L"\u2273" #define UNICODE_NEITHER_LESS_THAN_NOR_EQUIVALENT_TO 0x2274 #define UNITEXT_NEITHER_LESS_THAN_NOR_EQUIVALENT_TO L"\u2274" #define UNICODE_NEITHER_GREATER_THAN_NOR_EQUIVALENT_TO 0x2275 #define UNITEXT_NEITHER_GREATER_THAN_NOR_EQUIVALENT_TO L"\u2275" #define UNICODE_LESS_THAN_OR_GREATER_THAN 0x2276 #define UNITEXT_LESS_THAN_OR_GREATER_THAN L"\u2276" #define UNICODE_GREATER_THAN_OR_LESS_THAN 0x2277 #define UNITEXT_GREATER_THAN_OR_LESS_THAN L"\u2277" #define UNICODE_NEITHER_LESS_THAN_NOR_GREATER_THAN 0x2278 #define UNITEXT_NEITHER_LESS_THAN_NOR_GREATER_THAN L"\u2278" #define UNICODE_NEITHER_GREATER_THAN_NOR_LESS_THAN 0x2279 #define UNITEXT_NEITHER_GREATER_THAN_NOR_LESS_THAN L"\u2279" #define UNICODE_PRECEDES 0x227a #define UNITEXT_PRECEDES L"\u227a" #define UNICODE_SUCCEEDS 0x227b #define UNITEXT_SUCCEEDS L"\u227b" #define UNICODE_PRECEDES_OR_EQUAL_TO 0x227c #define UNITEXT_PRECEDES_OR_EQUAL_TO L"\u227c" #define UNICODE_SUCCEEDS_OR_EQUAL_TO 0x227d #define UNITEXT_SUCCEEDS_OR_EQUAL_TO L"\u227d" #define UNICODE_PRECEDES_OR_EQUIVALENT_TO 0x227e #define UNITEXT_PRECEDES_OR_EQUIVALENT_TO L"\u227e" #define UNICODE_SUCCEEDS_OR_EQUIVALENT_TO 0x227f #define UNITEXT_SUCCEEDS_OR_EQUIVALENT_TO L"\u227f" #define UNICODE_DOES_NOT_PRECEDE 0x2280 #define UNITEXT_DOES_NOT_PRECEDE L"\u2280" #define UNICODE_DOES_NOT_SUCCEED 0x2281 #define UNITEXT_DOES_NOT_SUCCEED L"\u2281" #define UNICODE_SUBSET_OF 0x2282 #define UNITEXT_SUBSET_OF L"\u2282" #define UNICODE_SUPERSET_OF 0x2283 #define UNITEXT_SUPERSET_OF L"\u2283" #define UNICODE_NOT_A_SUBSET_OF 0x2284 #define UNITEXT_NOT_A_SUBSET_OF L"\u2284" #define UNICODE_NOT_A_SUPERSET_OF 0x2285 #define UNITEXT_NOT_A_SUPERSET_OF L"\u2285" #define UNICODE_SUBSET_OF_OR_EQUAL_TO 0x2286 #define UNITEXT_SUBSET_OF_OR_EQUAL_TO L"\u2286" #define UNICODE_SUPERSET_OF_OR_EQUAL_TO 0x2287 #define UNITEXT_SUPERSET_OF_OR_EQUAL_TO L"\u2287" #define UNICODE_NEITHER_A_SUBSET_OF_NOR_EQUAL_TO 0x2288 #define UNITEXT_NEITHER_A_SUBSET_OF_NOR_EQUAL_TO L"\u2288" #define UNICODE_NEITHER_A_SUPERSET_OF_NOR_EQUAL_TO 0x2289 #define UNITEXT_NEITHER_A_SUPERSET_OF_NOR_EQUAL_TO L"\u2289" #define UNICODE_SUBSET_OF_WITH_NOT_EQUAL_TO 0x228a #define UNITEXT_SUBSET_OF_WITH_NOT_EQUAL_TO L"\u228a" #define UNICODE_SUPERSET_OF_WITH_NOT_EQUAL_TO 0x228b #define UNITEXT_SUPERSET_OF_WITH_NOT_EQUAL_TO L"\u228b" #define UNICODE_MULTISET 0x228c #define UNITEXT_MULTISET L"\u228c" #define UNICODE_MULTISET_MULTIPLICATION 0x228d #define UNITEXT_MULTISET_MULTIPLICATION L"\u228d" #define UNICODE_MULTISET_UNION 0x228e #define UNITEXT_MULTISET_UNION L"\u228e" #define UNICODE_SQUARE_IMAGE_OF 0x228f #define UNITEXT_SQUARE_IMAGE_OF L"\u228f" #define UNICODE_SQUARE_ORIGINAL_OF 0x2290 #define UNITEXT_SQUARE_ORIGINAL_OF L"\u2290" #define UNICODE_SQUARE_IMAGE_OF_OR_EQUAL_TO 0x2291 #define UNITEXT_SQUARE_IMAGE_OF_OR_EQUAL_TO L"\u2291" #define UNICODE_SQUARE_ORIGINAL_OF_OR_EQUAL_TO 0x2292 #define UNITEXT_SQUARE_ORIGINAL_OF_OR_EQUAL_TO L"\u2292" #define UNICODE_SQUARE_CAP 0x2293 #define UNITEXT_SQUARE_CAP L"\u2293" #define UNICODE_SQUARE_CUP 0x2294 #define UNITEXT_SQUARE_CUP L"\u2294" #define UNICODE_CIRCLED_PLUS 0x2295 #define UNITEXT_CIRCLED_PLUS L"\u2295" #define UNICODE_CIRCLED_MINUS 0x2296 #define UNITEXT_CIRCLED_MINUS L"\u2296" #define UNICODE_CIRCLED_TIMES 0x2297 #define UNITEXT_CIRCLED_TIMES L"\u2297" #define UNICODE_CIRCLED_DIVISION_SLASH 0x2298 #define UNITEXT_CIRCLED_DIVISION_SLASH L"\u2298" #define UNICODE_CIRCLED_DOT_OPERATOR 0x2299 #define UNITEXT_CIRCLED_DOT_OPERATOR L"\u2299" #define UNICODE_CIRCLED_RING_OPERATOR 0x229a #define UNITEXT_CIRCLED_RING_OPERATOR L"\u229a" #define UNICODE_CIRCLED_ASTERISK_OPERATOR 0x229b #define UNITEXT_CIRCLED_ASTERISK_OPERATOR L"\u229b" #define UNICODE_CIRCLED_EQUALS 0x229c #define UNITEXT_CIRCLED_EQUALS L"\u229c" #define UNICODE_CIRCLED_DASH 0x229d #define UNITEXT_CIRCLED_DASH L"\u229d" #define UNICODE_SQUARED_PLUS 0x229e #define UNITEXT_SQUARED_PLUS L"\u229e" #define UNICODE_SQUARED_MINUS 0x229f #define UNITEXT_SQUARED_MINUS L"\u229f" #define UNICODE_SQUARED_TIMES 0x22a0 #define UNITEXT_SQUARED_TIMES L"\u22a0" #define UNICODE_SQUARED_DOT_OPERATOR 0x22a1 #define UNITEXT_SQUARED_DOT_OPERATOR L"\u22a1" #define UNICODE_RIGHT_TACK 0x22a2 #define UNITEXT_RIGHT_TACK L"\u22a2" #define UNICODE_LEFT_TACK 0x22a3 #define UNITEXT_LEFT_TACK L"\u22a3" #define UNICODE_DOWN_TACK 0x22a4 #define UNITEXT_DOWN_TACK L"\u22a4" #define UNICODE_UP_TACK 0x22a5 #define UNITEXT_UP_TACK L"\u22a5" #define UNICODE_ASSERTION 0x22a6 #define UNITEXT_ASSERTION L"\u22a6" #define UNICODE_MODELS 0x22a7 #define UNITEXT_MODELS L"\u22a7" #define UNICODE_TRUE 0x22a8 #define UNITEXT_TRUE L"\u22a8" #define UNICODE_FORCES 0x22a9 #define UNITEXT_FORCES L"\u22a9" #define UNICODE_TRIPLE_VERTICAL_BAR_RIGHT_TURNSTILE 0x22aa #define UNITEXT_TRIPLE_VERTICAL_BAR_RIGHT_TURNSTILE L"\u22aa" #define UNICODE_DOUBLE_VERTICAL_BAR_DOUBLE_RIGHT_TURNSTILE 0x22ab #define UNITEXT_DOUBLE_VERTICAL_BAR_DOUBLE_RIGHT_TURNSTILE L"\u22ab" #define UNICODE_DOES_NOT_PROVE 0x22ac #define UNITEXT_DOES_NOT_PROVE L"\u22ac" #define UNICODE_NOT_TRUE 0x22ad #define UNITEXT_NOT_TRUE L"\u22ad" #define UNICODE_DOES_NOT_FORCE 0x22ae #define UNITEXT_DOES_NOT_FORCE L"\u22ae" #define UNICODE_NEGATED_DOUBLE_VERTICAL_BAR_DOUBLE_RIGHT_TURNSTILE 0x22af #define UNITEXT_NEGATED_DOUBLE_VERTICAL_BAR_DOUBLE_RIGHT_TURNSTILE L"\u22af" #define UNICODE_PRECEDES_UNDER_RELATION 0x22b0 #define UNITEXT_PRECEDES_UNDER_RELATION L"\u22b0" #define UNICODE_SUCCEEDS_UNDER_RELATION 0x22b1 #define UNITEXT_SUCCEEDS_UNDER_RELATION L"\u22b1" #define UNICODE_NORMAL_SUBGROUP_OF 0x22b2 #define UNITEXT_NORMAL_SUBGROUP_OF L"\u22b2" #define UNICODE_CONTAINS_AS_NORMAL_SUBGROUP 0x22b3 #define UNITEXT_CONTAINS_AS_NORMAL_SUBGROUP L"\u22b3" #define UNICODE_NORMAL_SUBGROUP_OF_OR_EQUAL_TO 0x22b4 #define UNITEXT_NORMAL_SUBGROUP_OF_OR_EQUAL_TO L"\u22b4" #define UNICODE_CONTAINS_AS_NORMAL_SUBGROUP_OR_EQUAL_TO 0x22b5 #define UNITEXT_CONTAINS_AS_NORMAL_SUBGROUP_OR_EQUAL_TO L"\u22b5" #define UNICODE_ORIGINAL_OF 0x22b6 #define UNITEXT_ORIGINAL_OF L"\u22b6" #define UNICODE_IMAGE_OF 0x22b7 #define UNITEXT_IMAGE_OF L"\u22b7" #define UNICODE_MULTIMAP 0x22b8 #define UNITEXT_MULTIMAP L"\u22b8" #define UNICODE_HERMITIAN_CONJUGATE_MATRIX 0x22b9 #define UNITEXT_HERMITIAN_CONJUGATE_MATRIX L"\u22b9" #define UNICODE_INTERCALATE 0x22ba #define UNITEXT_INTERCALATE L"\u22ba" #define UNICODE_XOR 0x22bb #define UNITEXT_XOR L"\u22bb" #define UNICODE_NAND 0x22bc #define UNITEXT_NAND L"\u22bc" #define UNICODE_NOR 0x22bd #define UNITEXT_NOR L"\u22bd" #define UNICODE_RIGHT_ANGLE_WITH_ARC 0x22be #define UNITEXT_RIGHT_ANGLE_WITH_ARC L"\u22be" #define UNICODE_RIGHT_TRIANGLE 0x22bf #define UNITEXT_RIGHT_TRIANGLE L"\u22bf" #define UNICODE_N_ARY_LOGICAL_AND 0x22c0 #define UNITEXT_N_ARY_LOGICAL_AND L"\u22c0" #define UNICODE_N_ARY_LOGICAL_OR 0x22c1 #define UNITEXT_N_ARY_LOGICAL_OR L"\u22c1" #define UNICODE_N_ARY_INTERSECTION 0x22c2 #define UNITEXT_N_ARY_INTERSECTION L"\u22c2" #define UNICODE_N_ARY_UNION 0x22c3 #define UNITEXT_N_ARY_UNION L"\u22c3" #define UNICODE_DIAMOND_OPERATOR 0x22c4 #define UNITEXT_DIAMOND_OPERATOR L"\u22c4" #define UNICODE_DOT_OPERATOR 0x22c5 #define UNITEXT_DOT_OPERATOR L"\u22c5" #define UNICODE_STAR_OPERATOR 0x22c6 #define UNITEXT_STAR_OPERATOR L"\u22c6" #define UNICODE_DIVISION_TIMES 0x22c7 #define UNITEXT_DIVISION_TIMES L"\u22c7" #define UNICODE_BOWTIE 0x22c8 #define UNITEXT_BOWTIE L"\u22c8" #define UNICODE_LEFT_NORMAL_FACTOR_SEMIDIRECT_PRODUCT 0x22c9 #define UNITEXT_LEFT_NORMAL_FACTOR_SEMIDIRECT_PRODUCT L"\u22c9" #define UNICODE_RIGHT_NORMAL_FACTOR_SEMIDIRECT_PRODUCT 0x22ca #define UNITEXT_RIGHT_NORMAL_FACTOR_SEMIDIRECT_PRODUCT L"\u22ca" #define UNICODE_LEFT_SEMIDIRECT_PRODUCT 0x22cb #define UNITEXT_LEFT_SEMIDIRECT_PRODUCT L"\u22cb" #define UNICODE_RIGHT_SEMIDIRECT_PRODUCT 0x22cc #define UNITEXT_RIGHT_SEMIDIRECT_PRODUCT L"\u22cc" #define UNICODE_REVERSED_TILDE_EQUALS 0x22cd #define UNITEXT_REVERSED_TILDE_EQUALS L"\u22cd" #define UNICODE_CURLY_LOGICAL_OR 0x22ce #define UNITEXT_CURLY_LOGICAL_OR L"\u22ce" #define UNICODE_CURLY_LOGICAL_AND 0x22cf #define UNITEXT_CURLY_LOGICAL_AND L"\u22cf" #define UNICODE_DOUBLE_SUBSET 0x22d0 #define UNITEXT_DOUBLE_SUBSET L"\u22d0" #define UNICODE_DOUBLE_SUPERSET 0x22d1 #define UNITEXT_DOUBLE_SUPERSET L"\u22d1" #define UNICODE_DOUBLE_INTERSECTION 0x22d2 #define UNITEXT_DOUBLE_INTERSECTION L"\u22d2" #define UNICODE_DOUBLE_UNION 0x22d3 #define UNITEXT_DOUBLE_UNION L"\u22d3" #define UNICODE_PITCHFORK 0x22d4 #define UNITEXT_PITCHFORK L"\u22d4" #define UNICODE_EQUAL_AND_PARALLEL_TO 0x22d5 #define UNITEXT_EQUAL_AND_PARALLEL_TO L"\u22d5" #define UNICODE_LESS_THAN_WITH_DOT 0x22d6 #define UNITEXT_LESS_THAN_WITH_DOT L"\u22d6" #define UNICODE_GREATER_THAN_WITH_DOT 0x22d7 #define UNITEXT_GREATER_THAN_WITH_DOT L"\u22d7" #define UNICODE_VERY_MUCH_LESS_THAN 0x22d8 #define UNITEXT_VERY_MUCH_LESS_THAN L"\u22d8" #define UNICODE_VERY_MUCH_GREATER_THAN 0x22d9 #define UNITEXT_VERY_MUCH_GREATER_THAN L"\u22d9" #define UNICODE_LESS_THAN_EQUAL_TO_OR_GREATER_THAN 0x22da #define UNITEXT_LESS_THAN_EQUAL_TO_OR_GREATER_THAN L"\u22da" #define UNICODE_GREATER_THAN_EQUAL_TO_OR_LESS_THAN 0x22db #define UNITEXT_GREATER_THAN_EQUAL_TO_OR_LESS_THAN L"\u22db" #define UNICODE_EQUAL_TO_OR_LESS_THAN 0x22dc #define UNITEXT_EQUAL_TO_OR_LESS_THAN L"\u22dc" #define UNICODE_EQUAL_TO_OR_GREATER_THAN 0x22dd #define UNITEXT_EQUAL_TO_OR_GREATER_THAN L"\u22dd" #define UNICODE_EQUAL_TO_OR_PRECEDES 0x22de #define UNITEXT_EQUAL_TO_OR_PRECEDES L"\u22de" #define UNICODE_EQUAL_TO_OR_SUCCEEDS 0x22df #define UNITEXT_EQUAL_TO_OR_SUCCEEDS L"\u22df" #define UNICODE_DOES_NOT_PRECEDE_OR_EQUAL 0x22e0 #define UNITEXT_DOES_NOT_PRECEDE_OR_EQUAL L"\u22e0" #define UNICODE_DOES_NOT_SUCCEED_OR_EQUAL 0x22e1 #define UNITEXT_DOES_NOT_SUCCEED_OR_EQUAL L"\u22e1" #define UNICODE_NOT_SQUARE_IMAGE_OF_OR_EQUAL_TO 0x22e2 #define UNITEXT_NOT_SQUARE_IMAGE_OF_OR_EQUAL_TO L"\u22e2" #define UNICODE_NOT_SQUARE_ORIGINAL_OF_OR_EQUAL_TO 0x22e3 #define UNITEXT_NOT_SQUARE_ORIGINAL_OF_OR_EQUAL_TO L"\u22e3" #define UNICODE_SQUARE_IMAGE_OF_OR_NOT_EQUAL_TO 0x22e4 #define UNITEXT_SQUARE_IMAGE_OF_OR_NOT_EQUAL_TO L"\u22e4" #define UNICODE_SQUARE_ORIGINAL_OF_OR_NOT_EQUAL_TO 0x22e5 #define UNITEXT_SQUARE_ORIGINAL_OF_OR_NOT_EQUAL_TO L"\u22e5" #define UNICODE_LESS_THAN_BUT_NOT_EQUIVALENT_TO 0x22e6 #define UNITEXT_LESS_THAN_BUT_NOT_EQUIVALENT_TO L"\u22e6" #define UNICODE_GREATER_THAN_BUT_NOT_EQUIVALENT_TO 0x22e7 #define UNITEXT_GREATER_THAN_BUT_NOT_EQUIVALENT_TO L"\u22e7" #define UNICODE_PRECEDES_BUT_NOT_EQUIVALENT_TO 0x22e8 #define UNITEXT_PRECEDES_BUT_NOT_EQUIVALENT_TO L"\u22e8" #define UNICODE_SUCCEEDS_BUT_NOT_EQUIVALENT_TO 0x22e9 #define UNITEXT_SUCCEEDS_BUT_NOT_EQUIVALENT_TO L"\u22e9" #define UNICODE_NOT_NORMAL_SUBGROUP_OF 0x22ea #define UNITEXT_NOT_NORMAL_SUBGROUP_OF L"\u22ea" #define UNICODE_DOES_NOT_CONTAIN_AS_NORMAL_SUBGROUP 0x22eb #define UNITEXT_DOES_NOT_CONTAIN_AS_NORMAL_SUBGROUP L"\u22eb" #define UNICODE_NOT_NORMAL_SUBGROUP_OF_OR_EQUAL_TO 0x22ec #define UNITEXT_NOT_NORMAL_SUBGROUP_OF_OR_EQUAL_TO L"\u22ec" #define UNICODE_DOES_NOT_CONTAIN_AS_NORMAL_SUBGROUP_OR_EQUAL 0x22ed #define UNITEXT_DOES_NOT_CONTAIN_AS_NORMAL_SUBGROUP_OR_EQUAL L"\u22ed" #define UNICODE_VERTICAL_ELLIPSIS 0x22ee #define UNITEXT_VERTICAL_ELLIPSIS L"\u22ee" #define UNICODE_MIDLINE_HORIZONTAL_ELLIPSIS 0x22ef #define UNITEXT_MIDLINE_HORIZONTAL_ELLIPSIS L"\u22ef" #define UNICODE_UP_RIGHT_DIAGONAL_ELLIPSIS 0x22f0 #define UNITEXT_UP_RIGHT_DIAGONAL_ELLIPSIS L"\u22f0" #define UNICODE_DOWN_RIGHT_DIAGONAL_ELLIPSIS 0x22f1 #define UNITEXT_DOWN_RIGHT_DIAGONAL_ELLIPSIS L"\u22f1" #define UNICODE_ELEMENT_OF_WITH_LONG_HORIZONTAL_STROKE 0x22f2 #define UNITEXT_ELEMENT_OF_WITH_LONG_HORIZONTAL_STROKE L"\u22f2" #define UNICODE_ELEMENT_OF_WITH_VERTICAL_BAR_AT_END_OF_HORIZONTAL_STROKE 0x22f3 #define UNITEXT_ELEMENT_OF_WITH_VERTICAL_BAR_AT_END_OF_HORIZONTAL_STROKE L"\u22f3" #define UNICODE_SMALL_ELEMENT_OF_WITH_VERTICAL_BAR_AT_END_OF_HORIZONTAL_STROKE 0x22f4 #define UNITEXT_SMALL_ELEMENT_OF_WITH_VERTICAL_BAR_AT_END_OF_HORIZONTAL_STROKE L"\u22f4" #define UNICODE_ELEMENT_OF_WITH_DOT_ABOVE 0x22f5 #define UNITEXT_ELEMENT_OF_WITH_DOT_ABOVE L"\u22f5" #define UNICODE_ELEMENT_OF_WITH_OVERBAR 0x22f6 #define UNITEXT_ELEMENT_OF_WITH_OVERBAR L"\u22f6" #define UNICODE_SMALL_ELEMENT_OF_WITH_OVERBAR 0x22f7 #define UNITEXT_SMALL_ELEMENT_OF_WITH_OVERBAR L"\u22f7" #define UNICODE_ELEMENT_OF_WITH_UNDERBAR 0x22f8 #define UNITEXT_ELEMENT_OF_WITH_UNDERBAR L"\u22f8" #define UNICODE_ELEMENT_OF_WITH_TWO_HORIZONTAL_STROKES 0x22f9 #define UNITEXT_ELEMENT_OF_WITH_TWO_HORIZONTAL_STROKES L"\u22f9" #define UNICODE_CONTAINS_WITH_LONG_HORIZONTAL_STROKE 0x22fa #define UNITEXT_CONTAINS_WITH_LONG_HORIZONTAL_STROKE L"\u22fa" #define UNICODE_CONTAINS_WITH_VERTICAL_BAR_AT_END_OF_HORIZONTAL_STROKE 0x22fb #define UNITEXT_CONTAINS_WITH_VERTICAL_BAR_AT_END_OF_HORIZONTAL_STROKE L"\u22fb" #define UNICODE_SMALL_CONTAINS_WITH_VERTICAL_BAR_AT_END_OF_HORIZONTAL_STROKE 0x22fc #define UNITEXT_SMALL_CONTAINS_WITH_VERTICAL_BAR_AT_END_OF_HORIZONTAL_STROKE L"\u22fc" #define UNICODE_CONTAINS_WITH_OVERBAR 0x22fd #define UNITEXT_CONTAINS_WITH_OVERBAR L"\u22fd" #define UNICODE_SMALL_CONTAINS_WITH_OVERBAR 0x22fe #define UNITEXT_SMALL_CONTAINS_WITH_OVERBAR L"\u22fe" #define UNICODE_Z_NOTATION_BAG_MEMBERSHIP 0x22ff #define UNITEXT_Z_NOTATION_BAG_MEMBERSHIP L"\u22ff" #define UNICODE_DIAMETER_SIGN 0x2300 #define UNITEXT_DIAMETER_SIGN L"\u2300" #define UNICODE_ELECTRIC_ARROW 0x2301 #define UNITEXT_ELECTRIC_ARROW L"\u2301" #define UNICODE_HOUSE 0x2302 #define UNITEXT_HOUSE L"\u2302" #define UNICODE_UP_ARROWHEAD 0x2303 #define UNITEXT_UP_ARROWHEAD L"\u2303" #define UNICODE_DOWN_ARROWHEAD 0x2304 #define UNITEXT_DOWN_ARROWHEAD L"\u2304" #define UNICODE_PROJECTIVE 0x2305 #define UNITEXT_PROJECTIVE L"\u2305" #define UNICODE_PERSPECTIVE 0x2306 #define UNITEXT_PERSPECTIVE L"\u2306" #define UNICODE_WAVY_LINE 0x2307 #define UNITEXT_WAVY_LINE L"\u2307" #define UNICODE_LEFT_CEILING 0x2308 #define UNITEXT_LEFT_CEILING L"\u2308" #define UNICODE_RIGHT_CEILING 0x2309 #define UNITEXT_RIGHT_CEILING L"\u2309" #define UNICODE_LEFT_FLOOR 0x230a #define UNITEXT_LEFT_FLOOR L"\u230a" #define UNICODE_RIGHT_FLOOR 0x230b #define UNITEXT_RIGHT_FLOOR L"\u230b" #define UNICODE_BOTTOM_RIGHT_CROP 0x230c #define UNITEXT_BOTTOM_RIGHT_CROP L"\u230c" #define UNICODE_BOTTOM_LEFT_CROP 0x230d #define UNITEXT_BOTTOM_LEFT_CROP L"\u230d" #define UNICODE_TOP_RIGHT_CROP 0x230e #define UNITEXT_TOP_RIGHT_CROP L"\u230e" #define UNICODE_TOP_LEFT_CROP 0x230f #define UNITEXT_TOP_LEFT_CROP L"\u230f" #define UNICODE_REVERSED_NOT_SIGN 0x2310 #define UNITEXT_REVERSED_NOT_SIGN L"\u2310" #define UNICODE_SQUARE_LOZENGE 0x2311 #define UNITEXT_SQUARE_LOZENGE L"\u2311" #define UNICODE_ARC 0x2312 #define UNITEXT_ARC L"\u2312" #define UNICODE_SEGMENT 0x2313 #define UNITEXT_SEGMENT L"\u2313" #define UNICODE_SECTOR 0x2314 #define UNITEXT_SECTOR L"\u2314" #define UNICODE_TELEPHONE_RECORDER 0x2315 #define UNITEXT_TELEPHONE_RECORDER L"\u2315" #define UNICODE_POSITION_INDICATOR 0x2316 #define UNITEXT_POSITION_INDICATOR L"\u2316" #define UNICODE_VIEWDATA_SQUARE 0x2317 #define UNITEXT_VIEWDATA_SQUARE L"\u2317" #define UNICODE_PLACE_OF_INTEREST_SIGN 0x2318 #define UNITEXT_PLACE_OF_INTEREST_SIGN L"\u2318" #define UNICODE_TURNED_NOT_SIGN 0x2319 #define UNITEXT_TURNED_NOT_SIGN L"\u2319" #define UNICODE_WATCH 0x231a #define UNITEXT_WATCH L"\u231a" #define UNICODE_HOURGLASS 0x231b #define UNITEXT_HOURGLASS L"\u231b" #define UNICODE_TOP_LEFT_CORNER 0x231c #define UNITEXT_TOP_LEFT_CORNER L"\u231c" #define UNICODE_TOP_RIGHT_CORNER 0x231d #define UNITEXT_TOP_RIGHT_CORNER L"\u231d" #define UNICODE_BOTTOM_LEFT_CORNER 0x231e #define UNITEXT_BOTTOM_LEFT_CORNER L"\u231e" #define UNICODE_BOTTOM_RIGHT_CORNER 0x231f #define UNITEXT_BOTTOM_RIGHT_CORNER L"\u231f" #define UNICODE_TOP_HALF_INTEGRAL 0x2320 #define UNITEXT_TOP_HALF_INTEGRAL L"\u2320" #define UNICODE_BOTTOM_HALF_INTEGRAL 0x2321 #define UNITEXT_BOTTOM_HALF_INTEGRAL L"\u2321" #define UNICODE_FROWN 0x2322 #define UNITEXT_FROWN L"\u2322" #define UNICODE_SMILE 0x2323 #define UNITEXT_SMILE L"\u2323" #define UNICODE_UP_ARROWHEAD_BETWEEN_TWO_HORIZONTAL_BARS 0x2324 #define UNITEXT_UP_ARROWHEAD_BETWEEN_TWO_HORIZONTAL_BARS L"\u2324" #define UNICODE_OPTION_KEY 0x2325 #define UNITEXT_OPTION_KEY L"\u2325" #define UNICODE_ERASE_TO_THE_RIGHT 0x2326 #define UNITEXT_ERASE_TO_THE_RIGHT L"\u2326" #define UNICODE_X_IN_A_RECTANGLE_BOX 0x2327 #define UNITEXT_X_IN_A_RECTANGLE_BOX L"\u2327" #define UNICODE_KEYBOARD 0x2328 #define UNITEXT_KEYBOARD L"\u2328" #define UNICODE_LEFT_POINTING_ANGLE_BRACKET 0x2329 #define UNITEXT_LEFT_POINTING_ANGLE_BRACKET L"\u2329" #define UNICODE_RIGHT_POINTING_ANGLE_BRACKET 0x232a #define UNITEXT_RIGHT_POINTING_ANGLE_BRACKET L"\u232a" #define UNICODE_ERASE_TO_THE_LEFT 0x232b #define UNITEXT_ERASE_TO_THE_LEFT L"\u232b" #define UNICODE_BENZENE_RING 0x232c #define UNITEXT_BENZENE_RING L"\u232c" #define UNICODE_CYLINDRICITY 0x232d #define UNITEXT_CYLINDRICITY L"\u232d" #define UNICODE_ALL_AROUND_PROFILE 0x232e #define UNITEXT_ALL_AROUND_PROFILE L"\u232e" #define UNICODE_SYMMETRY 0x232f #define UNITEXT_SYMMETRY L"\u232f" #define UNICODE_TOTAL_RUNOUT 0x2330 #define UNITEXT_TOTAL_RUNOUT L"\u2330" #define UNICODE_DIMENSION_ORIGIN 0x2331 #define UNITEXT_DIMENSION_ORIGIN L"\u2331" #define UNICODE_CONICAL_TAPER 0x2332 #define UNITEXT_CONICAL_TAPER L"\u2332" #define UNICODE_SLOPE 0x2333 #define UNITEXT_SLOPE L"\u2333" #define UNICODE_COUNTERBORE 0x2334 #define UNITEXT_COUNTERBORE L"\u2334" #define UNICODE_COUNTERSINK 0x2335 #define UNITEXT_COUNTERSINK L"\u2335" #define UNICODE_APL_FUNCTIONAL_SYMBOL_I_BEAM 0x2336 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_I_BEAM L"\u2336" #define UNICODE_APL_FUNCTIONAL_SYMBOL_SQUISH_QUAD 0x2337 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_SQUISH_QUAD L"\u2337" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_EQUAL 0x2338 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_EQUAL L"\u2338" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_DIVIDE 0x2339 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_DIVIDE L"\u2339" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_DIAMOND 0x233a #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_DIAMOND L"\u233a" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_JOT 0x233b #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_JOT L"\u233b" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_CIRCLE 0x233c #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_CIRCLE L"\u233c" #define UNICODE_APL_FUNCTIONAL_SYMBOL_CIRCLE_STILE 0x233d #define UNITEXT_APL_FUNCTIONAL_SYMBOL_CIRCLE_STILE L"\u233d" #define UNICODE_APL_FUNCTIONAL_SYMBOL_CIRCLE_JOT 0x233e #define UNITEXT_APL_FUNCTIONAL_SYMBOL_CIRCLE_JOT L"\u233e" #define UNICODE_APL_FUNCTIONAL_SYMBOL_SLASH_BAR 0x233f #define UNITEXT_APL_FUNCTIONAL_SYMBOL_SLASH_BAR L"\u233f" #define UNICODE_APL_FUNCTIONAL_SYMBOL_BACKSLASH_BAR 0x2340 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_BACKSLASH_BAR L"\u2340" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_SLASH 0x2341 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_SLASH L"\u2341" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_BACKSLASH 0x2342 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_BACKSLASH L"\u2342" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_LESS_THAN 0x2343 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_LESS_THAN L"\u2343" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_GREATER_THAN 0x2344 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_GREATER_THAN L"\u2344" #define UNICODE_APL_FUNCTIONAL_SYMBOL_LEFTWARDS_VANE 0x2345 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_LEFTWARDS_VANE L"\u2345" #define UNICODE_APL_FUNCTIONAL_SYMBOL_RIGHTWARDS_VANE 0x2346 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_RIGHTWARDS_VANE L"\u2346" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_LEFTWARDS_ARROW 0x2347 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_LEFTWARDS_ARROW L"\u2347" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_RIGHTWARDS_ARROW 0x2348 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_RIGHTWARDS_ARROW L"\u2348" #define UNICODE_APL_FUNCTIONAL_SYMBOL_CIRCLE_BACKSLASH 0x2349 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_CIRCLE_BACKSLASH L"\u2349" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DOWN_TACK_UNDERBAR 0x234a #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DOWN_TACK_UNDERBAR L"\u234a" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DELTA_STILE 0x234b #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DELTA_STILE L"\u234b" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_DOWN_CARET 0x234c #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_DOWN_CARET L"\u234c" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_DELTA 0x234d #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_DELTA L"\u234d" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DOWN_TACK_JOT 0x234e #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DOWN_TACK_JOT L"\u234e" #define UNICODE_APL_FUNCTIONAL_SYMBOL_UPWARDS_VANE 0x234f #define UNITEXT_APL_FUNCTIONAL_SYMBOL_UPWARDS_VANE L"\u234f" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_UPWARDS_ARROW 0x2350 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_UPWARDS_ARROW L"\u2350" #define UNICODE_APL_FUNCTIONAL_SYMBOL_UP_TACK_OVERBAR 0x2351 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_UP_TACK_OVERBAR L"\u2351" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DEL_STILE 0x2352 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DEL_STILE L"\u2352" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_UP_CARET 0x2353 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_UP_CARET L"\u2353" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_DEL 0x2354 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_DEL L"\u2354" #define UNICODE_APL_FUNCTIONAL_SYMBOL_UP_TACK_JOT 0x2355 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_UP_TACK_JOT L"\u2355" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DOWNWARDS_VANE 0x2356 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DOWNWARDS_VANE L"\u2356" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_DOWNWARDS_ARROW 0x2357 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_DOWNWARDS_ARROW L"\u2357" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUOTE_UNDERBAR 0x2358 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUOTE_UNDERBAR L"\u2358" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DELTA_UNDERBAR 0x2359 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DELTA_UNDERBAR L"\u2359" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DIAMOND_UNDERBAR 0x235a #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DIAMOND_UNDERBAR L"\u235a" #define UNICODE_APL_FUNCTIONAL_SYMBOL_JOT_UNDERBAR 0x235b #define UNITEXT_APL_FUNCTIONAL_SYMBOL_JOT_UNDERBAR L"\u235b" #define UNICODE_APL_FUNCTIONAL_SYMBOL_CIRCLE_UNDERBAR 0x235c #define UNITEXT_APL_FUNCTIONAL_SYMBOL_CIRCLE_UNDERBAR L"\u235c" #define UNICODE_APL_FUNCTIONAL_SYMBOL_UP_SHOE_JOT 0x235d #define UNITEXT_APL_FUNCTIONAL_SYMBOL_UP_SHOE_JOT L"\u235d" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUOTE_QUAD 0x235e #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUOTE_QUAD L"\u235e" #define UNICODE_APL_FUNCTIONAL_SYMBOL_CIRCLE_STAR 0x235f #define UNITEXT_APL_FUNCTIONAL_SYMBOL_CIRCLE_STAR L"\u235f" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_COLON 0x2360 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_COLON L"\u2360" #define UNICODE_APL_FUNCTIONAL_SYMBOL_UP_TACK_DIAERESIS 0x2361 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_UP_TACK_DIAERESIS L"\u2361" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DEL_DIAERESIS 0x2362 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DEL_DIAERESIS L"\u2362" #define UNICODE_APL_FUNCTIONAL_SYMBOL_STAR_DIAERESIS 0x2363 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_STAR_DIAERESIS L"\u2363" #define UNICODE_APL_FUNCTIONAL_SYMBOL_JOT_DIAERESIS 0x2364 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_JOT_DIAERESIS L"\u2364" #define UNICODE_APL_FUNCTIONAL_SYMBOL_CIRCLE_DIAERESIS 0x2365 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_CIRCLE_DIAERESIS L"\u2365" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DOWN_SHOE_STILE 0x2366 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DOWN_SHOE_STILE L"\u2366" #define UNICODE_APL_FUNCTIONAL_SYMBOL_LEFT_SHOE_STILE 0x2367 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_LEFT_SHOE_STILE L"\u2367" #define UNICODE_APL_FUNCTIONAL_SYMBOL_TILDE_DIAERESIS 0x2368 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_TILDE_DIAERESIS L"\u2368" #define UNICODE_APL_FUNCTIONAL_SYMBOL_GREATER_THAN_DIAERESIS 0x2369 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_GREATER_THAN_DIAERESIS L"\u2369" #define UNICODE_APL_FUNCTIONAL_SYMBOL_COMMA_BAR 0x236a #define UNITEXT_APL_FUNCTIONAL_SYMBOL_COMMA_BAR L"\u236a" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DEL_TILDE 0x236b #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DEL_TILDE L"\u236b" #define UNICODE_APL_FUNCTIONAL_SYMBOL_ZILDE 0x236c #define UNITEXT_APL_FUNCTIONAL_SYMBOL_ZILDE L"\u236c" #define UNICODE_APL_FUNCTIONAL_SYMBOL_STILE_TILDE 0x236d #define UNITEXT_APL_FUNCTIONAL_SYMBOL_STILE_TILDE L"\u236d" #define UNICODE_APL_FUNCTIONAL_SYMBOL_SEMICOLON_UNDERBAR 0x236e #define UNITEXT_APL_FUNCTIONAL_SYMBOL_SEMICOLON_UNDERBAR L"\u236e" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_NOT_EQUAL 0x236f #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_NOT_EQUAL L"\u236f" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD_QUESTION 0x2370 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD_QUESTION L"\u2370" #define UNICODE_APL_FUNCTIONAL_SYMBOL_DOWN_CARET_TILDE 0x2371 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_DOWN_CARET_TILDE L"\u2371" #define UNICODE_APL_FUNCTIONAL_SYMBOL_UP_CARET_TILDE 0x2372 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_UP_CARET_TILDE L"\u2372" #define UNICODE_APL_FUNCTIONAL_SYMBOL_IOTA 0x2373 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_IOTA L"\u2373" #define UNICODE_APL_FUNCTIONAL_SYMBOL_RHO 0x2374 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_RHO L"\u2374" #define UNICODE_APL_FUNCTIONAL_SYMBOL_OMEGA 0x2375 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_OMEGA L"\u2375" #define UNICODE_APL_FUNCTIONAL_SYMBOL_ALPHA_UNDERBAR 0x2376 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_ALPHA_UNDERBAR L"\u2376" #define UNICODE_APL_FUNCTIONAL_SYMBOL_EPSILON_UNDERBAR 0x2377 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_EPSILON_UNDERBAR L"\u2377" #define UNICODE_APL_FUNCTIONAL_SYMBOL_IOTA_UNDERBAR 0x2378 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_IOTA_UNDERBAR L"\u2378" #define UNICODE_APL_FUNCTIONAL_SYMBOL_OMEGA_UNDERBAR 0x2379 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_OMEGA_UNDERBAR L"\u2379" #define UNICODE_APL_FUNCTIONAL_SYMBOL_ALPHA 0x237a #define UNITEXT_APL_FUNCTIONAL_SYMBOL_ALPHA L"\u237a" #define UNICODE_NOT_CHECK_MARK 0x237b #define UNITEXT_NOT_CHECK_MARK L"\u237b" #define UNICODE_RIGHT_ANGLE_WITH_DOWNWARDS_ZIGZAG_ARROW 0x237c #define UNITEXT_RIGHT_ANGLE_WITH_DOWNWARDS_ZIGZAG_ARROW L"\u237c" #define UNICODE_SHOULDERED_OPEN_BOX 0x237d #define UNITEXT_SHOULDERED_OPEN_BOX L"\u237d" #define UNICODE_BELL_SYMBOL 0x237e #define UNITEXT_BELL_SYMBOL L"\u237e" #define UNICODE_VERTICAL_LINE_WITH_MIDDLE_DOT 0x237f #define UNITEXT_VERTICAL_LINE_WITH_MIDDLE_DOT L"\u237f" #define UNICODE_INSERTION_SYMBOL 0x2380 #define UNITEXT_INSERTION_SYMBOL L"\u2380" #define UNICODE_CONTINUOUS_UNDERLINE_SYMBOL 0x2381 #define UNITEXT_CONTINUOUS_UNDERLINE_SYMBOL L"\u2381" #define UNICODE_DISCONTINUOUS_UNDERLINE_SYMBOL 0x2382 #define UNITEXT_DISCONTINUOUS_UNDERLINE_SYMBOL L"\u2382" #define UNICODE_EMPHASIS_SYMBOL 0x2383 #define UNITEXT_EMPHASIS_SYMBOL L"\u2383" #define UNICODE_COMPOSITION_SYMBOL 0x2384 #define UNITEXT_COMPOSITION_SYMBOL L"\u2384" #define UNICODE_WHITE_SQUARE_WITH_CENTRE_VERTICAL_LINE 0x2385 #define UNITEXT_WHITE_SQUARE_WITH_CENTRE_VERTICAL_LINE L"\u2385" #define UNICODE_ENTER_SYMBOL 0x2386 #define UNITEXT_ENTER_SYMBOL L"\u2386" #define UNICODE_ALTERNATIVE_KEY_SYMBOL 0x2387 #define UNITEXT_ALTERNATIVE_KEY_SYMBOL L"\u2387" #define UNICODE_HELM_SYMBOL 0x2388 #define UNITEXT_HELM_SYMBOL L"\u2388" #define UNICODE_CIRCLED_HORIZONTAL_BAR_WITH_NOTCH 0x2389 #define UNITEXT_CIRCLED_HORIZONTAL_BAR_WITH_NOTCH L"\u2389" #define UNICODE_CIRCLED_TRIANGLE_DOWN 0x238a #define UNITEXT_CIRCLED_TRIANGLE_DOWN L"\u238a" #define UNICODE_BROKEN_CIRCLE_WITH_NORTHWEST_ARROW 0x238b #define UNITEXT_BROKEN_CIRCLE_WITH_NORTHWEST_ARROW L"\u238b" #define UNICODE_UNDO_SYMBOL 0x238c #define UNITEXT_UNDO_SYMBOL L"\u238c" #define UNICODE_MONOSTABLE_SYMBOL 0x238d #define UNITEXT_MONOSTABLE_SYMBOL L"\u238d" #define UNICODE_HYSTERESIS_SYMBOL 0x238e #define UNITEXT_HYSTERESIS_SYMBOL L"\u238e" #define UNICODE_OPEN_CIRCUIT_OUTPUT_H_TYPE_SYMBOL 0x238f #define UNITEXT_OPEN_CIRCUIT_OUTPUT_H_TYPE_SYMBOL L"\u238f" #define UNICODE_OPEN_CIRCUIT_OUTPUT_L_TYPE_SYMBOL 0x2390 #define UNITEXT_OPEN_CIRCUIT_OUTPUT_L_TYPE_SYMBOL L"\u2390" #define UNICODE_PASSIVE_PULL_DOWN_OUTPUT_SYMBOL 0x2391 #define UNITEXT_PASSIVE_PULL_DOWN_OUTPUT_SYMBOL L"\u2391" #define UNICODE_PASSIVE_PULL_UP_OUTPUT_SYMBOL 0x2392 #define UNITEXT_PASSIVE_PULL_UP_OUTPUT_SYMBOL L"\u2392" #define UNICODE_DIRECT_CURRENT_SYMBOL_FORM_TWO 0x2393 #define UNITEXT_DIRECT_CURRENT_SYMBOL_FORM_TWO L"\u2393" #define UNICODE_SOFTWARE_FUNCTION_SYMBOL 0x2394 #define UNITEXT_SOFTWARE_FUNCTION_SYMBOL L"\u2394" #define UNICODE_APL_FUNCTIONAL_SYMBOL_QUAD 0x2395 #define UNITEXT_APL_FUNCTIONAL_SYMBOL_QUAD L"\u2395" #define UNICODE_DECIMAL_SEPARATOR_KEY_SYMBOL 0x2396 #define UNITEXT_DECIMAL_SEPARATOR_KEY_SYMBOL L"\u2396" #define UNICODE_PREVIOUS_PAGE 0x2397 #define UNITEXT_PREVIOUS_PAGE L"\u2397" #define UNICODE_NEXT_PAGE 0x2398 #define UNITEXT_NEXT_PAGE L"\u2398" #define UNICODE_PRINT_SCREEN_SYMBOL 0x2399 #define UNITEXT_PRINT_SCREEN_SYMBOL L"\u2399" #define UNICODE_CLEAR_SCREEN_SYMBOL 0x239a #define UNITEXT_CLEAR_SCREEN_SYMBOL L"\u239a" #define UNICODE_LEFT_PARENTHESIS_UPPER_HOOK 0x239b #define UNITEXT_LEFT_PARENTHESIS_UPPER_HOOK L"\u239b" #define UNICODE_LEFT_PARENTHESIS_EXTENSION 0x239c #define UNITEXT_LEFT_PARENTHESIS_EXTENSION L"\u239c" #define UNICODE_LEFT_PARENTHESIS_LOWER_HOOK 0x239d #define UNITEXT_LEFT_PARENTHESIS_LOWER_HOOK L"\u239d" #define UNICODE_RIGHT_PARENTHESIS_UPPER_HOOK 0x239e #define UNITEXT_RIGHT_PARENTHESIS_UPPER_HOOK L"\u239e" #define UNICODE_RIGHT_PARENTHESIS_EXTENSION 0x239f #define UNITEXT_RIGHT_PARENTHESIS_EXTENSION L"\u239f" #define UNICODE_RIGHT_PARENTHESIS_LOWER_HOOK 0x23a0 #define UNITEXT_RIGHT_PARENTHESIS_LOWER_HOOK L"\u23a0" #define UNICODE_LEFT_SQUARE_BRACKET_UPPER_CORNER 0x23a1 #define UNITEXT_LEFT_SQUARE_BRACKET_UPPER_CORNER L"\u23a1" #define UNICODE_LEFT_SQUARE_BRACKET_EXTENSION 0x23a2 #define UNITEXT_LEFT_SQUARE_BRACKET_EXTENSION L"\u23a2" #define UNICODE_LEFT_SQUARE_BRACKET_LOWER_CORNER 0x23a3 #define UNITEXT_LEFT_SQUARE_BRACKET_LOWER_CORNER L"\u23a3" #define UNICODE_RIGHT_SQUARE_BRACKET_UPPER_CORNER 0x23a4 #define UNITEXT_RIGHT_SQUARE_BRACKET_UPPER_CORNER L"\u23a4" #define UNICODE_RIGHT_SQUARE_BRACKET_EXTENSION 0x23a5 #define UNITEXT_RIGHT_SQUARE_BRACKET_EXTENSION L"\u23a5" #define UNICODE_RIGHT_SQUARE_BRACKET_LOWER_CORNER 0x23a6 #define UNITEXT_RIGHT_SQUARE_BRACKET_LOWER_CORNER L"\u23a6" #define UNICODE_LEFT_CURLY_BRACKET_UPPER_HOOK 0x23a7 #define UNITEXT_LEFT_CURLY_BRACKET_UPPER_HOOK L"\u23a7" #define UNICODE_LEFT_CURLY_BRACKET_MIDDLE_PIECE 0x23a8 #define UNITEXT_LEFT_CURLY_BRACKET_MIDDLE_PIECE L"\u23a8" #define UNICODE_LEFT_CURLY_BRACKET_LOWER_HOOK 0x23a9 #define UNITEXT_LEFT_CURLY_BRACKET_LOWER_HOOK L"\u23a9" #define UNICODE_CURLY_BRACKET_EXTENSION 0x23aa #define UNITEXT_CURLY_BRACKET_EXTENSION L"\u23aa" #define UNICODE_RIGHT_CURLY_BRACKET_UPPER_HOOK 0x23ab #define UNITEXT_RIGHT_CURLY_BRACKET_UPPER_HOOK L"\u23ab" #define UNICODE_RIGHT_CURLY_BRACKET_MIDDLE_PIECE 0x23ac #define UNITEXT_RIGHT_CURLY_BRACKET_MIDDLE_PIECE L"\u23ac" #define UNICODE_RIGHT_CURLY_BRACKET_LOWER_HOOK 0x23ad #define UNITEXT_RIGHT_CURLY_BRACKET_LOWER_HOOK L"\u23ad" #define UNICODE_INTEGRAL_EXTENSION 0x23ae #define UNITEXT_INTEGRAL_EXTENSION L"\u23ae" #define UNICODE_HORIZONTAL_LINE_EXTENSION 0x23af #define UNITEXT_HORIZONTAL_LINE_EXTENSION L"\u23af" #define UNICODE_UPPER_LEFT_OR_LOWER_RIGHT_CURLY_BRACKET_SECTION 0x23b0 #define UNITEXT_UPPER_LEFT_OR_LOWER_RIGHT_CURLY_BRACKET_SECTION L"\u23b0" #define UNICODE_UPPER_RIGHT_OR_LOWER_LEFT_CURLY_BRACKET_SECTION 0x23b1 #define UNITEXT_UPPER_RIGHT_OR_LOWER_LEFT_CURLY_BRACKET_SECTION L"\u23b1" #define UNICODE_SUMMATION_TOP 0x23b2 #define UNITEXT_SUMMATION_TOP L"\u23b2" #define UNICODE_SUMMATION_BOTTOM 0x23b3 #define UNITEXT_SUMMATION_BOTTOM L"\u23b3" #define UNICODE_TOP_SQUARE_BRACKET 0x23b4 #define UNITEXT_TOP_SQUARE_BRACKET L"\u23b4" #define UNICODE_BOTTOM_SQUARE_BRACKET 0x23b5 #define UNITEXT_BOTTOM_SQUARE_BRACKET L"\u23b5" #define UNICODE_BOTTOM_SQUARE_BRACKET_OVER_TOP_SQUARE_BRACKET 0x23b6 #define UNITEXT_BOTTOM_SQUARE_BRACKET_OVER_TOP_SQUARE_BRACKET L"\u23b6" #define UNICODE_RADICAL_SYMBOL_BOTTOM 0x23b7 #define UNITEXT_RADICAL_SYMBOL_BOTTOM L"\u23b7" #define UNICODE_LEFT_VERTICAL_BOX_LINE 0x23b8 #define UNITEXT_LEFT_VERTICAL_BOX_LINE L"\u23b8" #define UNICODE_RIGHT_VERTICAL_BOX_LINE 0x23b9 #define UNITEXT_RIGHT_VERTICAL_BOX_LINE L"\u23b9" #define UNICODE_HORIZONTAL_SCAN_LINE_1 0x23ba #define UNITEXT_HORIZONTAL_SCAN_LINE_1 L"\u23ba" #define UNICODE_HORIZONTAL_SCAN_LINE_3 0x23bb #define UNITEXT_HORIZONTAL_SCAN_LINE_3 L"\u23bb" #define UNICODE_HORIZONTAL_SCAN_LINE_7 0x23bc #define UNITEXT_HORIZONTAL_SCAN_LINE_7 L"\u23bc" #define UNICODE_HORIZONTAL_SCAN_LINE_9 0x23bd #define UNITEXT_HORIZONTAL_SCAN_LINE_9 L"\u23bd" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_TOP_RIGHT 0x23be #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_TOP_RIGHT L"\u23be" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_BOTTOM_RIGHT 0x23bf #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_BOTTOM_RIGHT L"\u23bf" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_VERTICAL_WITH_CIRCLE 0x23c0 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_VERTICAL_WITH_CIRCLE L"\u23c0" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_DOWN_AND_HORIZONTAL_WITH_CIRCLE 0x23c1 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_DOWN_AND_HORIZONTAL_WITH_CIRCLE L"\u23c1" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_UP_AND_HORIZONTAL_WITH_CIRCLE 0x23c2 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_UP_AND_HORIZONTAL_WITH_CIRCLE L"\u23c2" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_VERTICAL_WITH_TRIANGLE 0x23c3 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_VERTICAL_WITH_TRIANGLE L"\u23c3" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_DOWN_AND_HORIZONTAL_WITH_TRIANGLE 0x23c4 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_DOWN_AND_HORIZONTAL_WITH_TRIANGLE L"\u23c4" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_UP_AND_HORIZONTAL_WITH_TRIANGLE 0x23c5 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_UP_AND_HORIZONTAL_WITH_TRIANGLE L"\u23c5" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_WAVE 0x23c6 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_WAVE L"\u23c6" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_DOWN_AND_HORIZONTAL_WITH_WAVE 0x23c7 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_DOWN_AND_HORIZONTAL_WITH_WAVE L"\u23c7" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_UP_AND_HORIZONTAL_WITH_WAVE 0x23c8 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_UP_AND_HORIZONTAL_WITH_WAVE L"\u23c8" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_DOWN_AND_HORIZONTAL 0x23c9 #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_DOWN_AND_HORIZONTAL L"\u23c9" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_UP_AND_HORIZONTAL 0x23ca #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_UP_AND_HORIZONTAL L"\u23ca" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_TOP_LEFT 0x23cb #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_TOP_LEFT L"\u23cb" #define UNICODE_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_BOTTOM_LEFT 0x23cc #define UNITEXT_DENTISTRY_SYMBOL_LIGHT_VERTICAL_AND_BOTTOM_LEFT L"\u23cc" #define UNICODE_SQUARE_FOOT 0x23cd #define UNITEXT_SQUARE_FOOT L"\u23cd" #define UNICODE_RETURN_SYMBOL 0x23ce #define UNITEXT_RETURN_SYMBOL L"\u23ce" #define UNICODE_EJECT_SYMBOL 0x23cf #define UNITEXT_EJECT_SYMBOL L"\u23cf" #define UNICODE_VERTICAL_LINE_EXTENSION 0x23d0 #define UNITEXT_VERTICAL_LINE_EXTENSION L"\u23d0" #define UNICODE_METRICAL_BREVE 0x23d1 #define UNITEXT_METRICAL_BREVE L"\u23d1" #define UNICODE_METRICAL_LONG_OVER_SHORT 0x23d2 #define UNITEXT_METRICAL_LONG_OVER_SHORT L"\u23d2" #define UNICODE_METRICAL_SHORT_OVER_LONG 0x23d3 #define UNITEXT_METRICAL_SHORT_OVER_LONG L"\u23d3" #define UNICODE_METRICAL_LONG_OVER_TWO_SHORTS 0x23d4 #define UNITEXT_METRICAL_LONG_OVER_TWO_SHORTS L"\u23d4" #define UNICODE_METRICAL_TWO_SHORTS_OVER_LONG 0x23d5 #define UNITEXT_METRICAL_TWO_SHORTS_OVER_LONG L"\u23d5" #define UNICODE_METRICAL_TWO_SHORTS_JOINED 0x23d6 #define UNITEXT_METRICAL_TWO_SHORTS_JOINED L"\u23d6" #define UNICODE_METRICAL_TRISEME 0x23d7 #define UNITEXT_METRICAL_TRISEME L"\u23d7" #define UNICODE_METRICAL_TETRASEME 0x23d8 #define UNITEXT_METRICAL_TETRASEME L"\u23d8" #define UNICODE_METRICAL_PENTASEME 0x23d9 #define UNITEXT_METRICAL_PENTASEME L"\u23d9" #define UNICODE_EARTH_GROUND 0x23da #define UNITEXT_EARTH_GROUND L"\u23da" #define UNICODE_FUSE 0x23db #define UNITEXT_FUSE L"\u23db" #define UNICODE_TOP_PARENTHESIS 0x23dc #define UNITEXT_TOP_PARENTHESIS L"\u23dc" #define UNICODE_BOTTOM_PARENTHESIS 0x23dd #define UNITEXT_BOTTOM_PARENTHESIS L"\u23dd" #define UNICODE_TOP_CURLY_BRACKET 0x23de #define UNITEXT_TOP_CURLY_BRACKET L"\u23de" #define UNICODE_BOTTOM_CURLY_BRACKET 0x23df #define UNITEXT_BOTTOM_CURLY_BRACKET L"\u23df" #define UNICODE_TOP_TORTOISE_SHELL_BRACKET 0x23e0 #define UNITEXT_TOP_TORTOISE_SHELL_BRACKET L"\u23e0" #define UNICODE_BOTTOM_TORTOISE_SHELL_BRACKET 0x23e1 #define UNITEXT_BOTTOM_TORTOISE_SHELL_BRACKET L"\u23e1" #define UNICODE_WHITE_TRAPEZIUM 0x23e2 #define UNITEXT_WHITE_TRAPEZIUM L"\u23e2" #define UNICODE_BENZENE_RING_WITH_CIRCLE 0x23e3 #define UNITEXT_BENZENE_RING_WITH_CIRCLE L"\u23e3" #define UNICODE_STRAIGHTNESS 0x23e4 #define UNITEXT_STRAIGHTNESS L"\u23e4" #define UNICODE_FLATNESS 0x23e5 #define UNITEXT_FLATNESS L"\u23e5" #define UNICODE_AC_CURRENT 0x23e6 #define UNITEXT_AC_CURRENT L"\u23e6" #define UNICODE_ELECTRICAL_INTERSECTION 0x23e7 #define UNITEXT_ELECTRICAL_INTERSECTION L"\u23e7" #define UNICODE_SYMBOL_FOR_NULL 0x2400 #define UNITEXT_SYMBOL_FOR_NULL L"\u2400" #define UNICODE_SYMBOL_FOR_START_OF_HEADING 0x2401 #define UNITEXT_SYMBOL_FOR_START_OF_HEADING L"\u2401" #define UNICODE_SYMBOL_FOR_START_OF_TEXT 0x2402 #define UNITEXT_SYMBOL_FOR_START_OF_TEXT L"\u2402" #define UNICODE_SYMBOL_FOR_END_OF_TEXT 0x2403 #define UNITEXT_SYMBOL_FOR_END_OF_TEXT L"\u2403" #define UNICODE_SYMBOL_FOR_END_OF_TRANSMISSION 0x2404 #define UNITEXT_SYMBOL_FOR_END_OF_TRANSMISSION L"\u2404" #define UNICODE_SYMBOL_FOR_ENQUIRY 0x2405 #define UNITEXT_SYMBOL_FOR_ENQUIRY L"\u2405" #define UNICODE_SYMBOL_FOR_ACKNOWLEDGE 0x2406 #define UNITEXT_SYMBOL_FOR_ACKNOWLEDGE L"\u2406" #define UNICODE_SYMBOL_FOR_BELL 0x2407 #define UNITEXT_SYMBOL_FOR_BELL L"\u2407" #define UNICODE_SYMBOL_FOR_BACKSPACE 0x2408 #define UNITEXT_SYMBOL_FOR_BACKSPACE L"\u2408" #define UNICODE_SYMBOL_FOR_HORIZONTAL_TABULATION 0x2409 #define UNITEXT_SYMBOL_FOR_HORIZONTAL_TABULATION L"\u2409" #define UNICODE_SYMBOL_FOR_LINE_FEED 0x240a #define UNITEXT_SYMBOL_FOR_LINE_FEED L"\u240a" #define UNICODE_SYMBOL_FOR_VERTICAL_TABULATION 0x240b #define UNITEXT_SYMBOL_FOR_VERTICAL_TABULATION L"\u240b" #define UNICODE_SYMBOL_FOR_FORM_FEED 0x240c #define UNITEXT_SYMBOL_FOR_FORM_FEED L"\u240c" #define UNICODE_SYMBOL_FOR_CARRIAGE_RETURN 0x240d #define UNITEXT_SYMBOL_FOR_CARRIAGE_RETURN L"\u240d" #define UNICODE_SYMBOL_FOR_SHIFT_OUT 0x240e #define UNITEXT_SYMBOL_FOR_SHIFT_OUT L"\u240e" #define UNICODE_SYMBOL_FOR_SHIFT_IN 0x240f #define UNITEXT_SYMBOL_FOR_SHIFT_IN L"\u240f" #define UNICODE_SYMBOL_FOR_DATA_LINK_ESCAPE 0x2410 #define UNITEXT_SYMBOL_FOR_DATA_LINK_ESCAPE L"\u2410" #define UNICODE_SYMBOL_FOR_DEVICE_CONTROL_ONE 0x2411 #define UNITEXT_SYMBOL_FOR_DEVICE_CONTROL_ONE L"\u2411" #define UNICODE_SYMBOL_FOR_DEVICE_CONTROL_TWO 0x2412 #define UNITEXT_SYMBOL_FOR_DEVICE_CONTROL_TWO L"\u2412" #define UNICODE_SYMBOL_FOR_DEVICE_CONTROL_THREE 0x2413 #define UNITEXT_SYMBOL_FOR_DEVICE_CONTROL_THREE L"\u2413" #define UNICODE_SYMBOL_FOR_DEVICE_CONTROL_FOUR 0x2414 #define UNITEXT_SYMBOL_FOR_DEVICE_CONTROL_FOUR L"\u2414" #define UNICODE_SYMBOL_FOR_NEGATIVE_ACKNOWLEDGE 0x2415 #define UNITEXT_SYMBOL_FOR_NEGATIVE_ACKNOWLEDGE L"\u2415" #define UNICODE_SYMBOL_FOR_SYNCHRONOUS_IDLE 0x2416 #define UNITEXT_SYMBOL_FOR_SYNCHRONOUS_IDLE L"\u2416" #define UNICODE_SYMBOL_FOR_END_OF_TRANSMISSION_BLOCK 0x2417 #define UNITEXT_SYMBOL_FOR_END_OF_TRANSMISSION_BLOCK L"\u2417" #define UNICODE_SYMBOL_FOR_CANCEL 0x2418 #define UNITEXT_SYMBOL_FOR_CANCEL L"\u2418" #define UNICODE_SYMBOL_FOR_END_OF_MEDIUM 0x2419 #define UNITEXT_SYMBOL_FOR_END_OF_MEDIUM L"\u2419" #define UNICODE_SYMBOL_FOR_SUBSTITUTE 0x241a #define UNITEXT_SYMBOL_FOR_SUBSTITUTE L"\u241a" #define UNICODE_SYMBOL_FOR_ESCAPE 0x241b #define UNITEXT_SYMBOL_FOR_ESCAPE L"\u241b" #define UNICODE_SYMBOL_FOR_FILE_SEPARATOR 0x241c #define UNITEXT_SYMBOL_FOR_FILE_SEPARATOR L"\u241c" #define UNICODE_SYMBOL_FOR_GROUP_SEPARATOR 0x241d #define UNITEXT_SYMBOL_FOR_GROUP_SEPARATOR L"\u241d" #define UNICODE_SYMBOL_FOR_RECORD_SEPARATOR 0x241e #define UNITEXT_SYMBOL_FOR_RECORD_SEPARATOR L"\u241e" #define UNICODE_SYMBOL_FOR_UNIT_SEPARATOR 0x241f #define UNITEXT_SYMBOL_FOR_UNIT_SEPARATOR L"\u241f" #define UNICODE_SYMBOL_FOR_SPACE 0x2420 #define UNITEXT_SYMBOL_FOR_SPACE L"\u2420" #define UNICODE_SYMBOL_FOR_DELETE 0x2421 #define UNITEXT_SYMBOL_FOR_DELETE L"\u2421" #define UNICODE_BLANK_SYMBOL 0x2422 #define UNITEXT_BLANK_SYMBOL L"\u2422" #define UNICODE_OPEN_BOX 0x2423 #define UNITEXT_OPEN_BOX L"\u2423" #define UNICODE_SYMBOL_FOR_NEWLINE 0x2424 #define UNITEXT_SYMBOL_FOR_NEWLINE L"\u2424" #define UNICODE_SYMBOL_FOR_DELETE_FORM_TWO 0x2425 #define UNITEXT_SYMBOL_FOR_DELETE_FORM_TWO L"\u2425" #define UNICODE_SYMBOL_FOR_SUBSTITUTE_FORM_TWO 0x2426 #define UNITEXT_SYMBOL_FOR_SUBSTITUTE_FORM_TWO L"\u2426" #define UNICODE_OCR_HOOK 0x2440 #define UNITEXT_OCR_HOOK L"\u2440" #define UNICODE_OCR_CHAIR 0x2441 #define UNITEXT_OCR_CHAIR L"\u2441" #define UNICODE_OCR_FORK 0x2442 #define UNITEXT_OCR_FORK L"\u2442" #define UNICODE_OCR_INVERTED_FORK 0x2443 #define UNITEXT_OCR_INVERTED_FORK L"\u2443" #define UNICODE_OCR_BELT_BUCKLE 0x2444 #define UNITEXT_OCR_BELT_BUCKLE L"\u2444" #define UNICODE_OCR_BOW_TIE 0x2445 #define UNITEXT_OCR_BOW_TIE L"\u2445" #define UNICODE_OCR_BRANCH_BANK_IDENTIFICATION 0x2446 #define UNITEXT_OCR_BRANCH_BANK_IDENTIFICATION L"\u2446" #define UNICODE_OCR_AMOUNT_OF_CHECK 0x2447 #define UNITEXT_OCR_AMOUNT_OF_CHECK L"\u2447" #define UNICODE_OCR_DASH 0x2448 #define UNITEXT_OCR_DASH L"\u2448" #define UNICODE_OCR_CUSTOMER_ACCOUNT_NUMBER 0x2449 #define UNITEXT_OCR_CUSTOMER_ACCOUNT_NUMBER L"\u2449" #define UNICODE_OCR_DOUBLE_BACKSLASH 0x244a #define UNITEXT_OCR_DOUBLE_BACKSLASH L"\u244a" #define UNICODE_CIRCLED_DIGIT_ONE 0x2460 #define UNITEXT_CIRCLED_DIGIT_ONE L"\u2460" #define UNICODE_CIRCLED_DIGIT_TWO 0x2461 #define UNITEXT_CIRCLED_DIGIT_TWO L"\u2461" #define UNICODE_CIRCLED_DIGIT_THREE 0x2462 #define UNITEXT_CIRCLED_DIGIT_THREE L"\u2462" #define UNICODE_CIRCLED_DIGIT_FOUR 0x2463 #define UNITEXT_CIRCLED_DIGIT_FOUR L"\u2463" #define UNICODE_CIRCLED_DIGIT_FIVE 0x2464 #define UNITEXT_CIRCLED_DIGIT_FIVE L"\u2464" #define UNICODE_CIRCLED_DIGIT_SIX 0x2465 #define UNITEXT_CIRCLED_DIGIT_SIX L"\u2465" #define UNICODE_CIRCLED_DIGIT_SEVEN 0x2466 #define UNITEXT_CIRCLED_DIGIT_SEVEN L"\u2466" #define UNICODE_CIRCLED_DIGIT_EIGHT 0x2467 #define UNITEXT_CIRCLED_DIGIT_EIGHT L"\u2467" #define UNICODE_CIRCLED_DIGIT_NINE 0x2468 #define UNITEXT_CIRCLED_DIGIT_NINE L"\u2468" #define UNICODE_CIRCLED_NUMBER_TEN 0x2469 #define UNITEXT_CIRCLED_NUMBER_TEN L"\u2469" #define UNICODE_CIRCLED_NUMBER_ELEVEN 0x246a #define UNITEXT_CIRCLED_NUMBER_ELEVEN L"\u246a" #define UNICODE_CIRCLED_NUMBER_TWELVE 0x246b #define UNITEXT_CIRCLED_NUMBER_TWELVE L"\u246b" #define UNICODE_CIRCLED_NUMBER_THIRTEEN 0x246c #define UNITEXT_CIRCLED_NUMBER_THIRTEEN L"\u246c" #define UNICODE_CIRCLED_NUMBER_FOURTEEN 0x246d #define UNITEXT_CIRCLED_NUMBER_FOURTEEN L"\u246d" #define UNICODE_CIRCLED_NUMBER_FIFTEEN 0x246e #define UNITEXT_CIRCLED_NUMBER_FIFTEEN L"\u246e" #define UNICODE_CIRCLED_NUMBER_SIXTEEN 0x246f #define UNITEXT_CIRCLED_NUMBER_SIXTEEN L"\u246f" #define UNICODE_CIRCLED_NUMBER_SEVENTEEN 0x2470 #define UNITEXT_CIRCLED_NUMBER_SEVENTEEN L"\u2470" #define UNICODE_CIRCLED_NUMBER_EIGHTEEN 0x2471 #define UNITEXT_CIRCLED_NUMBER_EIGHTEEN L"\u2471" #define UNICODE_CIRCLED_NUMBER_NINETEEN 0x2472 #define UNITEXT_CIRCLED_NUMBER_NINETEEN L"\u2472" #define UNICODE_CIRCLED_NUMBER_TWENTY 0x2473 #define UNITEXT_CIRCLED_NUMBER_TWENTY L"\u2473" #define UNICODE_PARENTHESIZED_DIGIT_ONE 0x2474 #define UNITEXT_PARENTHESIZED_DIGIT_ONE L"\u2474" #define UNICODE_PARENTHESIZED_DIGIT_TWO 0x2475 #define UNITEXT_PARENTHESIZED_DIGIT_TWO L"\u2475" #define UNICODE_PARENTHESIZED_DIGIT_THREE 0x2476 #define UNITEXT_PARENTHESIZED_DIGIT_THREE L"\u2476" #define UNICODE_PARENTHESIZED_DIGIT_FOUR 0x2477 #define UNITEXT_PARENTHESIZED_DIGIT_FOUR L"\u2477" #define UNICODE_PARENTHESIZED_DIGIT_FIVE 0x2478 #define UNITEXT_PARENTHESIZED_DIGIT_FIVE L"\u2478" #define UNICODE_PARENTHESIZED_DIGIT_SIX 0x2479 #define UNITEXT_PARENTHESIZED_DIGIT_SIX L"\u2479" #define UNICODE_PARENTHESIZED_DIGIT_SEVEN 0x247a #define UNITEXT_PARENTHESIZED_DIGIT_SEVEN L"\u247a" #define UNICODE_PARENTHESIZED_DIGIT_EIGHT 0x247b #define UNITEXT_PARENTHESIZED_DIGIT_EIGHT L"\u247b" #define UNICODE_PARENTHESIZED_DIGIT_NINE 0x247c #define UNITEXT_PARENTHESIZED_DIGIT_NINE L"\u247c" #define UNICODE_PARENTHESIZED_NUMBER_TEN 0x247d #define UNITEXT_PARENTHESIZED_NUMBER_TEN L"\u247d" #define UNICODE_PARENTHESIZED_NUMBER_ELEVEN 0x247e #define UNITEXT_PARENTHESIZED_NUMBER_ELEVEN L"\u247e" #define UNICODE_PARENTHESIZED_NUMBER_TWELVE 0x247f #define UNITEXT_PARENTHESIZED_NUMBER_TWELVE L"\u247f" #define UNICODE_PARENTHESIZED_NUMBER_THIRTEEN 0x2480 #define UNITEXT_PARENTHESIZED_NUMBER_THIRTEEN L"\u2480" #define UNICODE_PARENTHESIZED_NUMBER_FOURTEEN 0x2481 #define UNITEXT_PARENTHESIZED_NUMBER_FOURTEEN L"\u2481" #define UNICODE_PARENTHESIZED_NUMBER_FIFTEEN 0x2482 #define UNITEXT_PARENTHESIZED_NUMBER_FIFTEEN L"\u2482" #define UNICODE_PARENTHESIZED_NUMBER_SIXTEEN 0x2483 #define UNITEXT_PARENTHESIZED_NUMBER_SIXTEEN L"\u2483" #define UNICODE_PARENTHESIZED_NUMBER_SEVENTEEN 0x2484 #define UNITEXT_PARENTHESIZED_NUMBER_SEVENTEEN L"\u2484" #define UNICODE_PARENTHESIZED_NUMBER_EIGHTEEN 0x2485 #define UNITEXT_PARENTHESIZED_NUMBER_EIGHTEEN L"\u2485" #define UNICODE_PARENTHESIZED_NUMBER_NINETEEN 0x2486 #define UNITEXT_PARENTHESIZED_NUMBER_NINETEEN L"\u2486" #define UNICODE_PARENTHESIZED_NUMBER_TWENTY 0x2487 #define UNITEXT_PARENTHESIZED_NUMBER_TWENTY L"\u2487" #define UNICODE_DIGIT_ONE_FULL_STOP 0x2488 #define UNITEXT_DIGIT_ONE_FULL_STOP L"\u2488" #define UNICODE_DIGIT_TWO_FULL_STOP 0x2489 #define UNITEXT_DIGIT_TWO_FULL_STOP L"\u2489" #define UNICODE_DIGIT_THREE_FULL_STOP 0x248a #define UNITEXT_DIGIT_THREE_FULL_STOP L"\u248a" #define UNICODE_DIGIT_FOUR_FULL_STOP 0x248b #define UNITEXT_DIGIT_FOUR_FULL_STOP L"\u248b" #define UNICODE_DIGIT_FIVE_FULL_STOP 0x248c #define UNITEXT_DIGIT_FIVE_FULL_STOP L"\u248c" #define UNICODE_DIGIT_SIX_FULL_STOP 0x248d #define UNITEXT_DIGIT_SIX_FULL_STOP L"\u248d" #define UNICODE_DIGIT_SEVEN_FULL_STOP 0x248e #define UNITEXT_DIGIT_SEVEN_FULL_STOP L"\u248e" #define UNICODE_DIGIT_EIGHT_FULL_STOP 0x248f #define UNITEXT_DIGIT_EIGHT_FULL_STOP L"\u248f" #define UNICODE_DIGIT_NINE_FULL_STOP 0x2490 #define UNITEXT_DIGIT_NINE_FULL_STOP L"\u2490" #define UNICODE_NUMBER_TEN_FULL_STOP 0x2491 #define UNITEXT_NUMBER_TEN_FULL_STOP L"\u2491" #define UNICODE_NUMBER_ELEVEN_FULL_STOP 0x2492 #define UNITEXT_NUMBER_ELEVEN_FULL_STOP L"\u2492" #define UNICODE_NUMBER_TWELVE_FULL_STOP 0x2493 #define UNITEXT_NUMBER_TWELVE_FULL_STOP L"\u2493" #define UNICODE_NUMBER_THIRTEEN_FULL_STOP 0x2494 #define UNITEXT_NUMBER_THIRTEEN_FULL_STOP L"\u2494" #define UNICODE_NUMBER_FOURTEEN_FULL_STOP 0x2495 #define UNITEXT_NUMBER_FOURTEEN_FULL_STOP L"\u2495" #define UNICODE_NUMBER_FIFTEEN_FULL_STOP 0x2496 #define UNITEXT_NUMBER_FIFTEEN_FULL_STOP L"\u2496" #define UNICODE_NUMBER_SIXTEEN_FULL_STOP 0x2497 #define UNITEXT_NUMBER_SIXTEEN_FULL_STOP L"\u2497" #define UNICODE_NUMBER_SEVENTEEN_FULL_STOP 0x2498 #define UNITEXT_NUMBER_SEVENTEEN_FULL_STOP L"\u2498" #define UNICODE_NUMBER_EIGHTEEN_FULL_STOP 0x2499 #define UNITEXT_NUMBER_EIGHTEEN_FULL_STOP L"\u2499" #define UNICODE_NUMBER_NINETEEN_FULL_STOP 0x249a #define UNITEXT_NUMBER_NINETEEN_FULL_STOP L"\u249a" #define UNICODE_NUMBER_TWENTY_FULL_STOP 0x249b #define UNITEXT_NUMBER_TWENTY_FULL_STOP L"\u249b" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_A 0x249c #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_A L"\u249c" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_B 0x249d #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_B L"\u249d" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_C 0x249e #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_C L"\u249e" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_D 0x249f #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_D L"\u249f" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_E 0x24a0 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_E L"\u24a0" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_F 0x24a1 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_F L"\u24a1" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_G 0x24a2 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_G L"\u24a2" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_H 0x24a3 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_H L"\u24a3" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_I 0x24a4 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_I L"\u24a4" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_J 0x24a5 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_J L"\u24a5" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_K 0x24a6 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_K L"\u24a6" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_L 0x24a7 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_L L"\u24a7" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_M 0x24a8 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_M L"\u24a8" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_N 0x24a9 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_N L"\u24a9" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_O 0x24aa #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_O L"\u24aa" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_P 0x24ab #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_P L"\u24ab" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_Q 0x24ac #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_Q L"\u24ac" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_R 0x24ad #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_R L"\u24ad" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_S 0x24ae #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_S L"\u24ae" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_T 0x24af #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_T L"\u24af" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_U 0x24b0 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_U L"\u24b0" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_V 0x24b1 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_V L"\u24b1" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_W 0x24b2 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_W L"\u24b2" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_X 0x24b3 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_X L"\u24b3" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_Y 0x24b4 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_Y L"\u24b4" #define UNICODE_PARENTHESIZED_LATIN_SMALL_LETTER_Z 0x24b5 #define UNITEXT_PARENTHESIZED_LATIN_SMALL_LETTER_Z L"\u24b5" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_A 0x24b6 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_A L"\u24b6" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_B 0x24b7 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_B L"\u24b7" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_C 0x24b8 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_C L"\u24b8" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_D 0x24b9 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_D L"\u24b9" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_E 0x24ba #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_E L"\u24ba" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_F 0x24bb #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_F L"\u24bb" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_G 0x24bc #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_G L"\u24bc" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_H 0x24bd #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_H L"\u24bd" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_I 0x24be #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_I L"\u24be" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_J 0x24bf #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_J L"\u24bf" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_K 0x24c0 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_K L"\u24c0" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_L 0x24c1 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_L L"\u24c1" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_M 0x24c2 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_M L"\u24c2" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_N 0x24c3 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_N L"\u24c3" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_O 0x24c4 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_O L"\u24c4" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_P 0x24c5 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_P L"\u24c5" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_Q 0x24c6 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_Q L"\u24c6" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_R 0x24c7 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_R L"\u24c7" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_S 0x24c8 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_S L"\u24c8" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_T 0x24c9 #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_T L"\u24c9" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_U 0x24ca #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_U L"\u24ca" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_V 0x24cb #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_V L"\u24cb" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_W 0x24cc #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_W L"\u24cc" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_X 0x24cd #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_X L"\u24cd" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_Y 0x24ce #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_Y L"\u24ce" #define UNICODE_CIRCLED_LATIN_CAPITAL_LETTER_Z 0x24cf #define UNITEXT_CIRCLED_LATIN_CAPITAL_LETTER_Z L"\u24cf" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_A 0x24d0 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_A L"\u24d0" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_B 0x24d1 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_B L"\u24d1" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_C 0x24d2 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_C L"\u24d2" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_D 0x24d3 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_D L"\u24d3" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_E 0x24d4 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_E L"\u24d4" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_F 0x24d5 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_F L"\u24d5" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_G 0x24d6 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_G L"\u24d6" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_H 0x24d7 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_H L"\u24d7" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_I 0x24d8 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_I L"\u24d8" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_J 0x24d9 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_J L"\u24d9" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_K 0x24da #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_K L"\u24da" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_L 0x24db #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_L L"\u24db" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_M 0x24dc #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_M L"\u24dc" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_N 0x24dd #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_N L"\u24dd" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_O 0x24de #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_O L"\u24de" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_P 0x24df #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_P L"\u24df" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_Q 0x24e0 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_Q L"\u24e0" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_R 0x24e1 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_R L"\u24e1" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_S 0x24e2 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_S L"\u24e2" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_T 0x24e3 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_T L"\u24e3" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_U 0x24e4 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_U L"\u24e4" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_V 0x24e5 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_V L"\u24e5" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_W 0x24e6 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_W L"\u24e6" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_X 0x24e7 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_X L"\u24e7" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_Y 0x24e8 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_Y L"\u24e8" #define UNICODE_CIRCLED_LATIN_SMALL_LETTER_Z 0x24e9 #define UNITEXT_CIRCLED_LATIN_SMALL_LETTER_Z L"\u24e9" #define UNICODE_CIRCLED_DIGIT_ZERO 0x24ea #define UNITEXT_CIRCLED_DIGIT_ZERO L"\u24ea" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_ELEVEN 0x24eb #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_ELEVEN L"\u24eb" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_TWELVE 0x24ec #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_TWELVE L"\u24ec" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_THIRTEEN 0x24ed #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_THIRTEEN L"\u24ed" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_FOURTEEN 0x24ee #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_FOURTEEN L"\u24ee" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_FIFTEEN 0x24ef #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_FIFTEEN L"\u24ef" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_SIXTEEN 0x24f0 #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_SIXTEEN L"\u24f0" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_SEVENTEEN 0x24f1 #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_SEVENTEEN L"\u24f1" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_EIGHTEEN 0x24f2 #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_EIGHTEEN L"\u24f2" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_NINETEEN 0x24f3 #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_NINETEEN L"\u24f3" #define UNICODE_NEGATIVE_CIRCLED_NUMBER_TWENTY 0x24f4 #define UNITEXT_NEGATIVE_CIRCLED_NUMBER_TWENTY L"\u24f4" #define UNICODE_DOUBLE_CIRCLED_DIGIT_ONE 0x24f5 #define UNITEXT_DOUBLE_CIRCLED_DIGIT_ONE L"\u24f5" #define UNICODE_DOUBLE_CIRCLED_DIGIT_TWO 0x24f6 #define UNITEXT_DOUBLE_CIRCLED_DIGIT_TWO L"\u24f6" #define UNICODE_DOUBLE_CIRCLED_DIGIT_THREE 0x24f7 #define UNITEXT_DOUBLE_CIRCLED_DIGIT_THREE L"\u24f7" #define UNICODE_DOUBLE_CIRCLED_DIGIT_FOUR 0x24f8 #define UNITEXT_DOUBLE_CIRCLED_DIGIT_FOUR L"\u24f8" #define UNICODE_DOUBLE_CIRCLED_DIGIT_FIVE 0x24f9 #define UNITEXT_DOUBLE_CIRCLED_DIGIT_FIVE L"\u24f9" #define UNICODE_DOUBLE_CIRCLED_DIGIT_SIX 0x24fa #define UNITEXT_DOUBLE_CIRCLED_DIGIT_SIX L"\u24fa" #define UNICODE_DOUBLE_CIRCLED_DIGIT_SEVEN 0x24fb #define UNITEXT_DOUBLE_CIRCLED_DIGIT_SEVEN L"\u24fb" #define UNICODE_DOUBLE_CIRCLED_DIGIT_EIGHT 0x24fc #define UNITEXT_DOUBLE_CIRCLED_DIGIT_EIGHT L"\u24fc" #define UNICODE_DOUBLE_CIRCLED_DIGIT_NINE 0x24fd #define UNITEXT_DOUBLE_CIRCLED_DIGIT_NINE L"\u24fd" #define UNICODE_DOUBLE_CIRCLED_NUMBER_TEN 0x24fe #define UNITEXT_DOUBLE_CIRCLED_NUMBER_TEN L"\u24fe" #define UNICODE_NEGATIVE_CIRCLED_DIGIT_ZERO 0x24ff #define UNITEXT_NEGATIVE_CIRCLED_DIGIT_ZERO L"\u24ff" #define UNICODE_BOX_DRAWINGS_LIGHT_HORIZONTAL 0x2500 #define UNITEXT_BOX_DRAWINGS_LIGHT_HORIZONTAL L"\u2500" #define UNICODE_BOX_DRAWINGS_HEAVY_HORIZONTAL 0x2501 #define UNITEXT_BOX_DRAWINGS_HEAVY_HORIZONTAL L"\u2501" #define UNICODE_BOX_DRAWINGS_LIGHT_VERTICAL 0x2502 #define UNITEXT_BOX_DRAWINGS_LIGHT_VERTICAL L"\u2502" #define UNICODE_BOX_DRAWINGS_HEAVY_VERTICAL 0x2503 #define UNITEXT_BOX_DRAWINGS_HEAVY_VERTICAL L"\u2503" #define UNICODE_BOX_DRAWINGS_LIGHT_TRIPLE_DASH_HORIZONTAL 0x2504 #define UNITEXT_BOX_DRAWINGS_LIGHT_TRIPLE_DASH_HORIZONTAL L"\u2504" #define UNICODE_BOX_DRAWINGS_HEAVY_TRIPLE_DASH_HORIZONTAL 0x2505 #define UNITEXT_BOX_DRAWINGS_HEAVY_TRIPLE_DASH_HORIZONTAL L"\u2505" #define UNICODE_BOX_DRAWINGS_LIGHT_TRIPLE_DASH_VERTICAL 0x2506 #define UNITEXT_BOX_DRAWINGS_LIGHT_TRIPLE_DASH_VERTICAL L"\u2506" #define UNICODE_BOX_DRAWINGS_HEAVY_TRIPLE_DASH_VERTICAL 0x2507 #define UNITEXT_BOX_DRAWINGS_HEAVY_TRIPLE_DASH_VERTICAL L"\u2507" #define UNICODE_BOX_DRAWINGS_LIGHT_QUADRUPLE_DASH_HORIZONTAL 0x2508 #define UNITEXT_BOX_DRAWINGS_LIGHT_QUADRUPLE_DASH_HORIZONTAL L"\u2508" #define UNICODE_BOX_DRAWINGS_HEAVY_QUADRUPLE_DASH_HORIZONTAL 0x2509 #define UNITEXT_BOX_DRAWINGS_HEAVY_QUADRUPLE_DASH_HORIZONTAL L"\u2509" #define UNICODE_BOX_DRAWINGS_LIGHT_QUADRUPLE_DASH_VERTICAL 0x250a #define UNITEXT_BOX_DRAWINGS_LIGHT_QUADRUPLE_DASH_VERTICAL L"\u250a" #define UNICODE_BOX_DRAWINGS_HEAVY_QUADRUPLE_DASH_VERTICAL 0x250b #define UNITEXT_BOX_DRAWINGS_HEAVY_QUADRUPLE_DASH_VERTICAL L"\u250b" #define UNICODE_BOX_DRAWINGS_LIGHT_DOWN_AND_RIGHT 0x250c #define UNITEXT_BOX_DRAWINGS_LIGHT_DOWN_AND_RIGHT L"\u250c" #define UNICODE_BOX_DRAWINGS_DOWN_LIGHT_AND_RIGHT_HEAVY 0x250d #define UNITEXT_BOX_DRAWINGS_DOWN_LIGHT_AND_RIGHT_HEAVY L"\u250d" #define UNICODE_BOX_DRAWINGS_DOWN_HEAVY_AND_RIGHT_LIGHT 0x250e #define UNITEXT_BOX_DRAWINGS_DOWN_HEAVY_AND_RIGHT_LIGHT L"\u250e" #define UNICODE_BOX_DRAWINGS_HEAVY_DOWN_AND_RIGHT 0x250f #define UNITEXT_BOX_DRAWINGS_HEAVY_DOWN_AND_RIGHT L"\u250f" #define UNICODE_BOX_DRAWINGS_LIGHT_DOWN_AND_LEFT 0x2510 #define UNITEXT_BOX_DRAWINGS_LIGHT_DOWN_AND_LEFT L"\u2510" #define UNICODE_BOX_DRAWINGS_DOWN_LIGHT_AND_LEFT_HEAVY 0x2511 #define UNITEXT_BOX_DRAWINGS_DOWN_LIGHT_AND_LEFT_HEAVY L"\u2511" #define UNICODE_BOX_DRAWINGS_DOWN_HEAVY_AND_LEFT_LIGHT 0x2512 #define UNITEXT_BOX_DRAWINGS_DOWN_HEAVY_AND_LEFT_LIGHT L"\u2512" #define UNICODE_BOX_DRAWINGS_HEAVY_DOWN_AND_LEFT 0x2513 #define UNITEXT_BOX_DRAWINGS_HEAVY_DOWN_AND_LEFT L"\u2513" #define UNICODE_BOX_DRAWINGS_LIGHT_UP_AND_RIGHT 0x2514 #define UNITEXT_BOX_DRAWINGS_LIGHT_UP_AND_RIGHT L"\u2514" #define UNICODE_BOX_DRAWINGS_UP_LIGHT_AND_RIGHT_HEAVY 0x2515 #define UNITEXT_BOX_DRAWINGS_UP_LIGHT_AND_RIGHT_HEAVY L"\u2515" #define UNICODE_BOX_DRAWINGS_UP_HEAVY_AND_RIGHT_LIGHT 0x2516 #define UNITEXT_BOX_DRAWINGS_UP_HEAVY_AND_RIGHT_LIGHT L"\u2516" #define UNICODE_BOX_DRAWINGS_HEAVY_UP_AND_RIGHT 0x2517 #define UNITEXT_BOX_DRAWINGS_HEAVY_UP_AND_RIGHT L"\u2517" #define UNICODE_BOX_DRAWINGS_LIGHT_UP_AND_LEFT 0x2518 #define UNITEXT_BOX_DRAWINGS_LIGHT_UP_AND_LEFT L"\u2518" #define UNICODE_BOX_DRAWINGS_UP_LIGHT_AND_LEFT_HEAVY 0x2519 #define UNITEXT_BOX_DRAWINGS_UP_LIGHT_AND_LEFT_HEAVY L"\u2519" #define UNICODE_BOX_DRAWINGS_UP_HEAVY_AND_LEFT_LIGHT 0x251a #define UNITEXT_BOX_DRAWINGS_UP_HEAVY_AND_LEFT_LIGHT L"\u251a" #define UNICODE_BOX_DRAWINGS_HEAVY_UP_AND_LEFT 0x251b #define UNITEXT_BOX_DRAWINGS_HEAVY_UP_AND_LEFT L"\u251b" #define UNICODE_BOX_DRAWINGS_LIGHT_VERTICAL_AND_RIGHT 0x251c #define UNITEXT_BOX_DRAWINGS_LIGHT_VERTICAL_AND_RIGHT L"\u251c" #define UNICODE_BOX_DRAWINGS_VERTICAL_LIGHT_AND_RIGHT_HEAVY 0x251d #define UNITEXT_BOX_DRAWINGS_VERTICAL_LIGHT_AND_RIGHT_HEAVY L"\u251d" #define UNICODE_BOX_DRAWINGS_UP_HEAVY_AND_RIGHT_DOWN_LIGHT 0x251e #define UNITEXT_BOX_DRAWINGS_UP_HEAVY_AND_RIGHT_DOWN_LIGHT L"\u251e" #define UNICODE_BOX_DRAWINGS_DOWN_HEAVY_AND_RIGHT_UP_LIGHT 0x251f #define UNITEXT_BOX_DRAWINGS_DOWN_HEAVY_AND_RIGHT_UP_LIGHT L"\u251f" #define UNICODE_BOX_DRAWINGS_VERTICAL_HEAVY_AND_RIGHT_LIGHT 0x2520 #define UNITEXT_BOX_DRAWINGS_VERTICAL_HEAVY_AND_RIGHT_LIGHT L"\u2520" #define UNICODE_BOX_DRAWINGS_DOWN_LIGHT_AND_RIGHT_UP_HEAVY 0x2521 #define UNITEXT_BOX_DRAWINGS_DOWN_LIGHT_AND_RIGHT_UP_HEAVY L"\u2521" #define UNICODE_BOX_DRAWINGS_UP_LIGHT_AND_RIGHT_DOWN_HEAVY 0x2522 #define UNITEXT_BOX_DRAWINGS_UP_LIGHT_AND_RIGHT_DOWN_HEAVY L"\u2522" #define UNICODE_BOX_DRAWINGS_HEAVY_VERTICAL_AND_RIGHT 0x2523 #define UNITEXT_BOX_DRAWINGS_HEAVY_VERTICAL_AND_RIGHT L"\u2523" #define UNICODE_BOX_DRAWINGS_LIGHT_VERTICAL_AND_LEFT 0x2524 #define UNITEXT_BOX_DRAWINGS_LIGHT_VERTICAL_AND_LEFT L"\u2524" #define UNICODE_BOX_DRAWINGS_VERTICAL_LIGHT_AND_LEFT_HEAVY 0x2525 #define UNITEXT_BOX_DRAWINGS_VERTICAL_LIGHT_AND_LEFT_HEAVY L"\u2525" #define UNICODE_BOX_DRAWINGS_UP_HEAVY_AND_LEFT_DOWN_LIGHT 0x2526 #define UNITEXT_BOX_DRAWINGS_UP_HEAVY_AND_LEFT_DOWN_LIGHT L"\u2526" #define UNICODE_BOX_DRAWINGS_DOWN_HEAVY_AND_LEFT_UP_LIGHT 0x2527 #define UNITEXT_BOX_DRAWINGS_DOWN_HEAVY_AND_LEFT_UP_LIGHT L"\u2527" #define UNICODE_BOX_DRAWINGS_VERTICAL_HEAVY_AND_LEFT_LIGHT 0x2528 #define UNITEXT_BOX_DRAWINGS_VERTICAL_HEAVY_AND_LEFT_LIGHT L"\u2528" #define UNICODE_BOX_DRAWINGS_DOWN_LIGHT_AND_LEFT_UP_HEAVY 0x2529 #define UNITEXT_BOX_DRAWINGS_DOWN_LIGHT_AND_LEFT_UP_HEAVY L"\u2529" #define UNICODE_BOX_DRAWINGS_UP_LIGHT_AND_LEFT_DOWN_HEAVY 0x252a #define UNITEXT_BOX_DRAWINGS_UP_LIGHT_AND_LEFT_DOWN_HEAVY L"\u252a" #define UNICODE_BOX_DRAWINGS_HEAVY_VERTICAL_AND_LEFT 0x252b #define UNITEXT_BOX_DRAWINGS_HEAVY_VERTICAL_AND_LEFT L"\u252b" #define UNICODE_BOX_DRAWINGS_LIGHT_DOWN_AND_HORIZONTAL 0x252c #define UNITEXT_BOX_DRAWINGS_LIGHT_DOWN_AND_HORIZONTAL L"\u252c" #define UNICODE_BOX_DRAWINGS_LEFT_HEAVY_AND_RIGHT_DOWN_LIGHT 0x252d #define UNITEXT_BOX_DRAWINGS_LEFT_HEAVY_AND_RIGHT_DOWN_LIGHT L"\u252d" #define UNICODE_BOX_DRAWINGS_RIGHT_HEAVY_AND_LEFT_DOWN_LIGHT 0x252e #define UNITEXT_BOX_DRAWINGS_RIGHT_HEAVY_AND_LEFT_DOWN_LIGHT L"\u252e" #define UNICODE_BOX_DRAWINGS_DOWN_LIGHT_AND_HORIZONTAL_HEAVY 0x252f #define UNITEXT_BOX_DRAWINGS_DOWN_LIGHT_AND_HORIZONTAL_HEAVY L"\u252f" #define UNICODE_BOX_DRAWINGS_DOWN_HEAVY_AND_HORIZONTAL_LIGHT 0x2530 #define UNITEXT_BOX_DRAWINGS_DOWN_HEAVY_AND_HORIZONTAL_LIGHT L"\u2530" #define UNICODE_BOX_DRAWINGS_RIGHT_LIGHT_AND_LEFT_DOWN_HEAVY 0x2531 #define UNITEXT_BOX_DRAWINGS_RIGHT_LIGHT_AND_LEFT_DOWN_HEAVY L"\u2531" #define UNICODE_BOX_DRAWINGS_LEFT_LIGHT_AND_RIGHT_DOWN_HEAVY 0x2532 #define UNITEXT_BOX_DRAWINGS_LEFT_LIGHT_AND_RIGHT_DOWN_HEAVY L"\u2532" #define UNICODE_BOX_DRAWINGS_HEAVY_DOWN_AND_HORIZONTAL 0x2533 #define UNITEXT_BOX_DRAWINGS_HEAVY_DOWN_AND_HORIZONTAL L"\u2533" #define UNICODE_BOX_DRAWINGS_LIGHT_UP_AND_HORIZONTAL 0x2534 #define UNITEXT_BOX_DRAWINGS_LIGHT_UP_AND_HORIZONTAL L"\u2534" #define UNICODE_BOX_DRAWINGS_LEFT_HEAVY_AND_RIGHT_UP_LIGHT 0x2535 #define UNITEXT_BOX_DRAWINGS_LEFT_HEAVY_AND_RIGHT_UP_LIGHT L"\u2535" #define UNICODE_BOX_DRAWINGS_RIGHT_HEAVY_AND_LEFT_UP_LIGHT 0x2536 #define UNITEXT_BOX_DRAWINGS_RIGHT_HEAVY_AND_LEFT_UP_LIGHT L"\u2536" #define UNICODE_BOX_DRAWINGS_UP_LIGHT_AND_HORIZONTAL_HEAVY 0x2537 #define UNITEXT_BOX_DRAWINGS_UP_LIGHT_AND_HORIZONTAL_HEAVY L"\u2537" #define UNICODE_BOX_DRAWINGS_UP_HEAVY_AND_HORIZONTAL_LIGHT 0x2538 #define UNITEXT_BOX_DRAWINGS_UP_HEAVY_AND_HORIZONTAL_LIGHT L"\u2538" #define UNICODE_BOX_DRAWINGS_RIGHT_LIGHT_AND_LEFT_UP_HEAVY 0x2539 #define UNITEXT_BOX_DRAWINGS_RIGHT_LIGHT_AND_LEFT_UP_HEAVY L"\u2539" #define UNICODE_BOX_DRAWINGS_LEFT_LIGHT_AND_RIGHT_UP_HEAVY 0x253a #define UNITEXT_BOX_DRAWINGS_LEFT_LIGHT_AND_RIGHT_UP_HEAVY L"\u253a" #define UNICODE_BOX_DRAWINGS_HEAVY_UP_AND_HORIZONTAL 0x253b #define UNITEXT_BOX_DRAWINGS_HEAVY_UP_AND_HORIZONTAL L"\u253b" #define UNICODE_BOX_DRAWINGS_LIGHT_VERTICAL_AND_HORIZONTAL 0x253c #define UNITEXT_BOX_DRAWINGS_LIGHT_VERTICAL_AND_HORIZONTAL L"\u253c" #define UNICODE_BOX_DRAWINGS_LEFT_HEAVY_AND_RIGHT_VERTICAL_LIGHT 0x253d #define UNITEXT_BOX_DRAWINGS_LEFT_HEAVY_AND_RIGHT_VERTICAL_LIGHT L"\u253d" #define UNICODE_BOX_DRAWINGS_RIGHT_HEAVY_AND_LEFT_VERTICAL_LIGHT 0x253e #define UNITEXT_BOX_DRAWINGS_RIGHT_HEAVY_AND_LEFT_VERTICAL_LIGHT L"\u253e" #define UNICODE_BOX_DRAWINGS_VERTICAL_LIGHT_AND_HORIZONTAL_HEAVY 0x253f #define UNITEXT_BOX_DRAWINGS_VERTICAL_LIGHT_AND_HORIZONTAL_HEAVY L"\u253f" #define UNICODE_BOX_DRAWINGS_UP_HEAVY_AND_DOWN_HORIZONTAL_LIGHT 0x2540 #define UNITEXT_BOX_DRAWINGS_UP_HEAVY_AND_DOWN_HORIZONTAL_LIGHT L"\u2540" #define UNICODE_BOX_DRAWINGS_DOWN_HEAVY_AND_UP_HORIZONTAL_LIGHT 0x2541 #define UNITEXT_BOX_DRAWINGS_DOWN_HEAVY_AND_UP_HORIZONTAL_LIGHT L"\u2541" #define UNICODE_BOX_DRAWINGS_VERTICAL_HEAVY_AND_HORIZONTAL_LIGHT 0x2542 #define UNITEXT_BOX_DRAWINGS_VERTICAL_HEAVY_AND_HORIZONTAL_LIGHT L"\u2542" #define UNICODE_BOX_DRAWINGS_LEFT_UP_HEAVY_AND_RIGHT_DOWN_LIGHT 0x2543 #define UNITEXT_BOX_DRAWINGS_LEFT_UP_HEAVY_AND_RIGHT_DOWN_LIGHT L"\u2543" #define UNICODE_BOX_DRAWINGS_RIGHT_UP_HEAVY_AND_LEFT_DOWN_LIGHT 0x2544 #define UNITEXT_BOX_DRAWINGS_RIGHT_UP_HEAVY_AND_LEFT_DOWN_LIGHT L"\u2544" #define UNICODE_BOX_DRAWINGS_LEFT_DOWN_HEAVY_AND_RIGHT_UP_LIGHT 0x2545 #define UNITEXT_BOX_DRAWINGS_LEFT_DOWN_HEAVY_AND_RIGHT_UP_LIGHT L"\u2545" #define UNICODE_BOX_DRAWINGS_RIGHT_DOWN_HEAVY_AND_LEFT_UP_LIGHT 0x2546 #define UNITEXT_BOX_DRAWINGS_RIGHT_DOWN_HEAVY_AND_LEFT_UP_LIGHT L"\u2546" #define UNICODE_BOX_DRAWINGS_DOWN_LIGHT_AND_UP_HORIZONTAL_HEAVY 0x2547 #define UNITEXT_BOX_DRAWINGS_DOWN_LIGHT_AND_UP_HORIZONTAL_HEAVY L"\u2547" #define UNICODE_BOX_DRAWINGS_UP_LIGHT_AND_DOWN_HORIZONTAL_HEAVY 0x2548 #define UNITEXT_BOX_DRAWINGS_UP_LIGHT_AND_DOWN_HORIZONTAL_HEAVY L"\u2548" #define UNICODE_BOX_DRAWINGS_RIGHT_LIGHT_AND_LEFT_VERTICAL_HEAVY 0x2549 #define UNITEXT_BOX_DRAWINGS_RIGHT_LIGHT_AND_LEFT_VERTICAL_HEAVY L"\u2549" #define UNICODE_BOX_DRAWINGS_LEFT_LIGHT_AND_RIGHT_VERTICAL_HEAVY 0x254a #define UNITEXT_BOX_DRAWINGS_LEFT_LIGHT_AND_RIGHT_VERTICAL_HEAVY L"\u254a" #define UNICODE_BOX_DRAWINGS_HEAVY_VERTICAL_AND_HORIZONTAL 0x254b #define UNITEXT_BOX_DRAWINGS_HEAVY_VERTICAL_AND_HORIZONTAL L"\u254b" #define UNICODE_BOX_DRAWINGS_LIGHT_DOUBLE_DASH_HORIZONTAL 0x254c #define UNITEXT_BOX_DRAWINGS_LIGHT_DOUBLE_DASH_HORIZONTAL L"\u254c" #define UNICODE_BOX_DRAWINGS_HEAVY_DOUBLE_DASH_HORIZONTAL 0x254d #define UNITEXT_BOX_DRAWINGS_HEAVY_DOUBLE_DASH_HORIZONTAL L"\u254d" #define UNICODE_BOX_DRAWINGS_LIGHT_DOUBLE_DASH_VERTICAL 0x254e #define UNITEXT_BOX_DRAWINGS_LIGHT_DOUBLE_DASH_VERTICAL L"\u254e" #define UNICODE_BOX_DRAWINGS_HEAVY_DOUBLE_DASH_VERTICAL 0x254f #define UNITEXT_BOX_DRAWINGS_HEAVY_DOUBLE_DASH_VERTICAL L"\u254f" #define UNICODE_BOX_DRAWINGS_DOUBLE_HORIZONTAL 0x2550 #define UNITEXT_BOX_DRAWINGS_DOUBLE_HORIZONTAL L"\u2550" #define UNICODE_BOX_DRAWINGS_DOUBLE_VERTICAL 0x2551 #define UNITEXT_BOX_DRAWINGS_DOUBLE_VERTICAL L"\u2551" #define UNICODE_BOX_DRAWINGS_DOWN_SINGLE_AND_RIGHT_DOUBLE 0x2552 #define UNITEXT_BOX_DRAWINGS_DOWN_SINGLE_AND_RIGHT_DOUBLE L"\u2552" #define UNICODE_BOX_DRAWINGS_DOWN_DOUBLE_AND_RIGHT_SINGLE 0x2553 #define UNITEXT_BOX_DRAWINGS_DOWN_DOUBLE_AND_RIGHT_SINGLE L"\u2553" #define UNICODE_BOX_DRAWINGS_DOUBLE_DOWN_AND_RIGHT 0x2554 #define UNITEXT_BOX_DRAWINGS_DOUBLE_DOWN_AND_RIGHT L"\u2554" #define UNICODE_BOX_DRAWINGS_DOWN_SINGLE_AND_LEFT_DOUBLE 0x2555 #define UNITEXT_BOX_DRAWINGS_DOWN_SINGLE_AND_LEFT_DOUBLE L"\u2555" #define UNICODE_BOX_DRAWINGS_DOWN_DOUBLE_AND_LEFT_SINGLE 0x2556 #define UNITEXT_BOX_DRAWINGS_DOWN_DOUBLE_AND_LEFT_SINGLE L"\u2556" #define UNICODE_BOX_DRAWINGS_DOUBLE_DOWN_AND_LEFT 0x2557 #define UNITEXT_BOX_DRAWINGS_DOUBLE_DOWN_AND_LEFT L"\u2557" #define UNICODE_BOX_DRAWINGS_UP_SINGLE_AND_RIGHT_DOUBLE 0x2558 #define UNITEXT_BOX_DRAWINGS_UP_SINGLE_AND_RIGHT_DOUBLE L"\u2558" #define UNICODE_BOX_DRAWINGS_UP_DOUBLE_AND_RIGHT_SINGLE 0x2559 #define UNITEXT_BOX_DRAWINGS_UP_DOUBLE_AND_RIGHT_SINGLE L"\u2559" #define UNICODE_BOX_DRAWINGS_DOUBLE_UP_AND_RIGHT 0x255a #define UNITEXT_BOX_DRAWINGS_DOUBLE_UP_AND_RIGHT L"\u255a" #define UNICODE_BOX_DRAWINGS_UP_SINGLE_AND_LEFT_DOUBLE 0x255b #define UNITEXT_BOX_DRAWINGS_UP_SINGLE_AND_LEFT_DOUBLE L"\u255b" #define UNICODE_BOX_DRAWINGS_UP_DOUBLE_AND_LEFT_SINGLE 0x255c #define UNITEXT_BOX_DRAWINGS_UP_DOUBLE_AND_LEFT_SINGLE L"\u255c" #define UNICODE_BOX_DRAWINGS_DOUBLE_UP_AND_LEFT 0x255d #define UNITEXT_BOX_DRAWINGS_DOUBLE_UP_AND_LEFT L"\u255d" #define UNICODE_BOX_DRAWINGS_VERTICAL_SINGLE_AND_RIGHT_DOUBLE 0x255e #define UNITEXT_BOX_DRAWINGS_VERTICAL_SINGLE_AND_RIGHT_DOUBLE L"\u255e" #define UNICODE_BOX_DRAWINGS_VERTICAL_DOUBLE_AND_RIGHT_SINGLE 0x255f #define UNITEXT_BOX_DRAWINGS_VERTICAL_DOUBLE_AND_RIGHT_SINGLE L"\u255f" #define UNICODE_BOX_DRAWINGS_DOUBLE_VERTICAL_AND_RIGHT 0x2560 #define UNITEXT_BOX_DRAWINGS_DOUBLE_VERTICAL_AND_RIGHT L"\u2560" #define UNICODE_BOX_DRAWINGS_VERTICAL_SINGLE_AND_LEFT_DOUBLE 0x2561 #define UNITEXT_BOX_DRAWINGS_VERTICAL_SINGLE_AND_LEFT_DOUBLE L"\u2561" #define UNICODE_BOX_DRAWINGS_VERTICAL_DOUBLE_AND_LEFT_SINGLE 0x2562 #define UNITEXT_BOX_DRAWINGS_VERTICAL_DOUBLE_AND_LEFT_SINGLE L"\u2562" #define UNICODE_BOX_DRAWINGS_DOUBLE_VERTICAL_AND_LEFT 0x2563 #define UNITEXT_BOX_DRAWINGS_DOUBLE_VERTICAL_AND_LEFT L"\u2563" #define UNICODE_BOX_DRAWINGS_DOWN_SINGLE_AND_HORIZONTAL_DOUBLE 0x2564 #define UNITEXT_BOX_DRAWINGS_DOWN_SINGLE_AND_HORIZONTAL_DOUBLE L"\u2564" #define UNICODE_BOX_DRAWINGS_DOWN_DOUBLE_AND_HORIZONTAL_SINGLE 0x2565 #define UNITEXT_BOX_DRAWINGS_DOWN_DOUBLE_AND_HORIZONTAL_SINGLE L"\u2565" #define UNICODE_BOX_DRAWINGS_DOUBLE_DOWN_AND_HORIZONTAL 0x2566 #define UNITEXT_BOX_DRAWINGS_DOUBLE_DOWN_AND_HORIZONTAL L"\u2566" #define UNICODE_BOX_DRAWINGS_UP_SINGLE_AND_HORIZONTAL_DOUBLE 0x2567 #define UNITEXT_BOX_DRAWINGS_UP_SINGLE_AND_HORIZONTAL_DOUBLE L"\u2567" #define UNICODE_BOX_DRAWINGS_UP_DOUBLE_AND_HORIZONTAL_SINGLE 0x2568 #define UNITEXT_BOX_DRAWINGS_UP_DOUBLE_AND_HORIZONTAL_SINGLE L"\u2568" #define UNICODE_BOX_DRAWINGS_DOUBLE_UP_AND_HORIZONTAL 0x2569 #define UNITEXT_BOX_DRAWINGS_DOUBLE_UP_AND_HORIZONTAL L"\u2569" #define UNICODE_BOX_DRAWINGS_VERTICAL_SINGLE_AND_HORIZONTAL_DOUBLE 0x256a #define UNITEXT_BOX_DRAWINGS_VERTICAL_SINGLE_AND_HORIZONTAL_DOUBLE L"\u256a" #define UNICODE_BOX_DRAWINGS_VERTICAL_DOUBLE_AND_HORIZONTAL_SINGLE 0x256b #define UNITEXT_BOX_DRAWINGS_VERTICAL_DOUBLE_AND_HORIZONTAL_SINGLE L"\u256b" #define UNICODE_BOX_DRAWINGS_DOUBLE_VERTICAL_AND_HORIZONTAL 0x256c #define UNITEXT_BOX_DRAWINGS_DOUBLE_VERTICAL_AND_HORIZONTAL L"\u256c" #define UNICODE_BOX_DRAWINGS_LIGHT_ARC_DOWN_AND_RIGHT 0x256d #define UNITEXT_BOX_DRAWINGS_LIGHT_ARC_DOWN_AND_RIGHT L"\u256d" #define UNICODE_BOX_DRAWINGS_LIGHT_ARC_DOWN_AND_LEFT 0x256e #define UNITEXT_BOX_DRAWINGS_LIGHT_ARC_DOWN_AND_LEFT L"\u256e" #define UNICODE_BOX_DRAWINGS_LIGHT_ARC_UP_AND_LEFT 0x256f #define UNITEXT_BOX_DRAWINGS_LIGHT_ARC_UP_AND_LEFT L"\u256f" #define UNICODE_BOX_DRAWINGS_LIGHT_ARC_UP_AND_RIGHT 0x2570 #define UNITEXT_BOX_DRAWINGS_LIGHT_ARC_UP_AND_RIGHT L"\u2570" #define UNICODE_BOX_DRAWINGS_LIGHT_DIAGONAL_UPPER_RIGHT_TO_LOWER_LEFT 0x2571 #define UNITEXT_BOX_DRAWINGS_LIGHT_DIAGONAL_UPPER_RIGHT_TO_LOWER_LEFT L"\u2571" #define UNICODE_BOX_DRAWINGS_LIGHT_DIAGONAL_UPPER_LEFT_TO_LOWER_RIGHT 0x2572 #define UNITEXT_BOX_DRAWINGS_LIGHT_DIAGONAL_UPPER_LEFT_TO_LOWER_RIGHT L"\u2572" #define UNICODE_BOX_DRAWINGS_LIGHT_DIAGONAL_CROSS 0x2573 #define UNITEXT_BOX_DRAWINGS_LIGHT_DIAGONAL_CROSS L"\u2573" #define UNICODE_BOX_DRAWINGS_LIGHT_LEFT 0x2574 #define UNITEXT_BOX_DRAWINGS_LIGHT_LEFT L"\u2574" #define UNICODE_BOX_DRAWINGS_LIGHT_UP 0x2575 #define UNITEXT_BOX_DRAWINGS_LIGHT_UP L"\u2575" #define UNICODE_BOX_DRAWINGS_LIGHT_RIGHT 0x2576 #define UNITEXT_BOX_DRAWINGS_LIGHT_RIGHT L"\u2576" #define UNICODE_BOX_DRAWINGS_LIGHT_DOWN 0x2577 #define UNITEXT_BOX_DRAWINGS_LIGHT_DOWN L"\u2577" #define UNICODE_BOX_DRAWINGS_HEAVY_LEFT 0x2578 #define UNITEXT_BOX_DRAWINGS_HEAVY_LEFT L"\u2578" #define UNICODE_BOX_DRAWINGS_HEAVY_UP 0x2579 #define UNITEXT_BOX_DRAWINGS_HEAVY_UP L"\u2579" #define UNICODE_BOX_DRAWINGS_HEAVY_RIGHT 0x257a #define UNITEXT_BOX_DRAWINGS_HEAVY_RIGHT L"\u257a" #define UNICODE_BOX_DRAWINGS_HEAVY_DOWN 0x257b #define UNITEXT_BOX_DRAWINGS_HEAVY_DOWN L"\u257b" #define UNICODE_BOX_DRAWINGS_LIGHT_LEFT_AND_HEAVY_RIGHT 0x257c #define UNITEXT_BOX_DRAWINGS_LIGHT_LEFT_AND_HEAVY_RIGHT L"\u257c" #define UNICODE_BOX_DRAWINGS_LIGHT_UP_AND_HEAVY_DOWN 0x257d #define UNITEXT_BOX_DRAWINGS_LIGHT_UP_AND_HEAVY_DOWN L"\u257d" #define UNICODE_BOX_DRAWINGS_HEAVY_LEFT_AND_LIGHT_RIGHT 0x257e #define UNITEXT_BOX_DRAWINGS_HEAVY_LEFT_AND_LIGHT_RIGHT L"\u257e" #define UNICODE_BOX_DRAWINGS_HEAVY_UP_AND_LIGHT_DOWN 0x257f #define UNITEXT_BOX_DRAWINGS_HEAVY_UP_AND_LIGHT_DOWN L"\u257f" #define UNICODE_UPPER_HALF_BLOCK 0x2580 #define UNITEXT_UPPER_HALF_BLOCK L"\u2580" #define UNICODE_LOWER_ONE_EIGHTH_BLOCK 0x2581 #define UNITEXT_LOWER_ONE_EIGHTH_BLOCK L"\u2581" #define UNICODE_LOWER_ONE_QUARTER_BLOCK 0x2582 #define UNITEXT_LOWER_ONE_QUARTER_BLOCK L"\u2582" #define UNICODE_LOWER_THREE_EIGHTHS_BLOCK 0x2583 #define UNITEXT_LOWER_THREE_EIGHTHS_BLOCK L"\u2583" #define UNICODE_LOWER_HALF_BLOCK 0x2584 #define UNITEXT_LOWER_HALF_BLOCK L"\u2584" #define UNICODE_LOWER_FIVE_EIGHTHS_BLOCK 0x2585 #define UNITEXT_LOWER_FIVE_EIGHTHS_BLOCK L"\u2585" #define UNICODE_LOWER_THREE_QUARTERS_BLOCK 0x2586 #define UNITEXT_LOWER_THREE_QUARTERS_BLOCK L"\u2586" #define UNICODE_LOWER_SEVEN_EIGHTHS_BLOCK 0x2587 #define UNITEXT_LOWER_SEVEN_EIGHTHS_BLOCK L"\u2587" #define UNICODE_FULL_BLOCK 0x2588 #define UNITEXT_FULL_BLOCK L"\u2588" #define UNICODE_LEFT_SEVEN_EIGHTHS_BLOCK 0x2589 #define UNITEXT_LEFT_SEVEN_EIGHTHS_BLOCK L"\u2589" #define UNICODE_LEFT_THREE_QUARTERS_BLOCK 0x258a #define UNITEXT_LEFT_THREE_QUARTERS_BLOCK L"\u258a" #define UNICODE_LEFT_FIVE_EIGHTHS_BLOCK 0x258b #define UNITEXT_LEFT_FIVE_EIGHTHS_BLOCK L"\u258b" #define UNICODE_LEFT_HALF_BLOCK 0x258c #define UNITEXT_LEFT_HALF_BLOCK L"\u258c" #define UNICODE_LEFT_THREE_EIGHTHS_BLOCK 0x258d #define UNITEXT_LEFT_THREE_EIGHTHS_BLOCK L"\u258d" #define UNICODE_LEFT_ONE_QUARTER_BLOCK 0x258e #define UNITEXT_LEFT_ONE_QUARTER_BLOCK L"\u258e" #define UNICODE_LEFT_ONE_EIGHTH_BLOCK 0x258f #define UNITEXT_LEFT_ONE_EIGHTH_BLOCK L"\u258f" #define UNICODE_RIGHT_HALF_BLOCK 0x2590 #define UNITEXT_RIGHT_HALF_BLOCK L"\u2590" #define UNICODE_LIGHT_SHADE 0x2591 #define UNITEXT_LIGHT_SHADE L"\u2591" #define UNICODE_MEDIUM_SHADE 0x2592 #define UNITEXT_MEDIUM_SHADE L"\u2592" #define UNICODE_DARK_SHADE 0x2593 #define UNITEXT_DARK_SHADE L"\u2593" #define UNICODE_UPPER_ONE_EIGHTH_BLOCK 0x2594 #define UNITEXT_UPPER_ONE_EIGHTH_BLOCK L"\u2594" #define UNICODE_RIGHT_ONE_EIGHTH_BLOCK 0x2595 #define UNITEXT_RIGHT_ONE_EIGHTH_BLOCK L"\u2595" #define UNICODE_QUADRANT_LOWER_LEFT 0x2596 #define UNITEXT_QUADRANT_LOWER_LEFT L"\u2596" #define UNICODE_QUADRANT_LOWER_RIGHT 0x2597 #define UNITEXT_QUADRANT_LOWER_RIGHT L"\u2597" #define UNICODE_QUADRANT_UPPER_LEFT 0x2598 #define UNITEXT_QUADRANT_UPPER_LEFT L"\u2598" #define UNICODE_QUADRANT_UPPER_LEFT_AND_LOWER_LEFT_AND_LOWER_RIGHT 0x2599 #define UNITEXT_QUADRANT_UPPER_LEFT_AND_LOWER_LEFT_AND_LOWER_RIGHT L"\u2599" #define UNICODE_QUADRANT_UPPER_LEFT_AND_LOWER_RIGHT 0x259a #define UNITEXT_QUADRANT_UPPER_LEFT_AND_LOWER_RIGHT L"\u259a" #define UNICODE_QUADRANT_UPPER_LEFT_AND_UPPER_RIGHT_AND_LOWER_LEFT 0x259b #define UNITEXT_QUADRANT_UPPER_LEFT_AND_UPPER_RIGHT_AND_LOWER_LEFT L"\u259b" #define UNICODE_QUADRANT_UPPER_LEFT_AND_UPPER_RIGHT_AND_LOWER_RIGHT 0x259c #define UNITEXT_QUADRANT_UPPER_LEFT_AND_UPPER_RIGHT_AND_LOWER_RIGHT L"\u259c" #define UNICODE_QUADRANT_UPPER_RIGHT 0x259d #define UNITEXT_QUADRANT_UPPER_RIGHT L"\u259d" #define UNICODE_QUADRANT_UPPER_RIGHT_AND_LOWER_LEFT 0x259e #define UNITEXT_QUADRANT_UPPER_RIGHT_AND_LOWER_LEFT L"\u259e" #define UNICODE_QUADRANT_UPPER_RIGHT_AND_LOWER_LEFT_AND_LOWER_RIGHT 0x259f #define UNITEXT_QUADRANT_UPPER_RIGHT_AND_LOWER_LEFT_AND_LOWER_RIGHT L"\u259f" #define UNICODE_BLACK_SQUARE 0x25a0 #define UNITEXT_BLACK_SQUARE L"\u25a0" #define UNICODE_WHITE_SQUARE 0x25a1 #define UNITEXT_WHITE_SQUARE L"\u25a1" #define UNICODE_WHITE_SQUARE_WITH_ROUNDED_CORNERS 0x25a2 #define UNITEXT_WHITE_SQUARE_WITH_ROUNDED_CORNERS L"\u25a2" #define UNICODE_WHITE_SQUARE_CONTAINING_BLACK_SMALL_SQUARE 0x25a3 #define UNITEXT_WHITE_SQUARE_CONTAINING_BLACK_SMALL_SQUARE L"\u25a3" #define UNICODE_SQUARE_WITH_HORIZONTAL_FILL 0x25a4 #define UNITEXT_SQUARE_WITH_HORIZONTAL_FILL L"\u25a4" #define UNICODE_SQUARE_WITH_VERTICAL_FILL 0x25a5 #define UNITEXT_SQUARE_WITH_VERTICAL_FILL L"\u25a5" #define UNICODE_SQUARE_WITH_ORTHOGONAL_CROSSHATCH_FILL 0x25a6 #define UNITEXT_SQUARE_WITH_ORTHOGONAL_CROSSHATCH_FILL L"\u25a6" #define UNICODE_SQUARE_WITH_UPPER_LEFT_TO_LOWER_RIGHT_FILL 0x25a7 #define UNITEXT_SQUARE_WITH_UPPER_LEFT_TO_LOWER_RIGHT_FILL L"\u25a7" #define UNICODE_SQUARE_WITH_UPPER_RIGHT_TO_LOWER_LEFT_FILL 0x25a8 #define UNITEXT_SQUARE_WITH_UPPER_RIGHT_TO_LOWER_LEFT_FILL L"\u25a8" #define UNICODE_SQUARE_WITH_DIAGONAL_CROSSHATCH_FILL 0x25a9 #define UNITEXT_SQUARE_WITH_DIAGONAL_CROSSHATCH_FILL L"\u25a9" #define UNICODE_BLACK_SMALL_SQUARE 0x25aa #define UNITEXT_BLACK_SMALL_SQUARE L"\u25aa" #define UNICODE_WHITE_SMALL_SQUARE 0x25ab #define UNITEXT_WHITE_SMALL_SQUARE L"\u25ab" #define UNICODE_BLACK_RECTANGLE 0x25ac #define UNITEXT_BLACK_RECTANGLE L"\u25ac" #define UNICODE_WHITE_RECTANGLE 0x25ad #define UNITEXT_WHITE_RECTANGLE L"\u25ad" #define UNICODE_BLACK_VERTICAL_RECTANGLE 0x25ae #define UNITEXT_BLACK_VERTICAL_RECTANGLE L"\u25ae" #define UNICODE_WHITE_VERTICAL_RECTANGLE 0x25af #define UNITEXT_WHITE_VERTICAL_RECTANGLE L"\u25af" #define UNICODE_BLACK_PARALLELOGRAM 0x25b0 #define UNITEXT_BLACK_PARALLELOGRAM L"\u25b0" #define UNICODE_WHITE_PARALLELOGRAM 0x25b1 #define UNITEXT_WHITE_PARALLELOGRAM L"\u25b1" #define UNICODE_BLACK_UP_POINTING_TRIANGLE 0x25b2 #define UNITEXT_BLACK_UP_POINTING_TRIANGLE L"\u25b2" #define UNICODE_WHITE_UP_POINTING_TRIANGLE 0x25b3 #define UNITEXT_WHITE_UP_POINTING_TRIANGLE L"\u25b3" #define UNICODE_BLACK_UP_POINTING_SMALL_TRIANGLE 0x25b4 #define UNITEXT_BLACK_UP_POINTING_SMALL_TRIANGLE L"\u25b4" #define UNICODE_WHITE_UP_POINTING_SMALL_TRIANGLE 0x25b5 #define UNITEXT_WHITE_UP_POINTING_SMALL_TRIANGLE L"\u25b5" #define UNICODE_BLACK_RIGHT_POINTING_TRIANGLE 0x25b6 #define UNITEXT_BLACK_RIGHT_POINTING_TRIANGLE L"\u25b6" #define UNICODE_WHITE_RIGHT_POINTING_TRIANGLE 0x25b7 #define UNITEXT_WHITE_RIGHT_POINTING_TRIANGLE L"\u25b7" #define UNICODE_BLACK_RIGHT_POINTING_SMALL_TRIANGLE 0x25b8 #define UNITEXT_BLACK_RIGHT_POINTING_SMALL_TRIANGLE L"\u25b8" #define UNICODE_WHITE_RIGHT_POINTING_SMALL_TRIANGLE 0x25b9 #define UNITEXT_WHITE_RIGHT_POINTING_SMALL_TRIANGLE L"\u25b9" #define UNICODE_BLACK_RIGHT_POINTING_POINTER 0x25ba #define UNITEXT_BLACK_RIGHT_POINTING_POINTER L"\u25ba" #define UNICODE_WHITE_RIGHT_POINTING_POINTER 0x25bb #define UNITEXT_WHITE_RIGHT_POINTING_POINTER L"\u25bb" #define UNICODE_BLACK_DOWN_POINTING_TRIANGLE 0x25bc #define UNITEXT_BLACK_DOWN_POINTING_TRIANGLE L"\u25bc" #define UNICODE_WHITE_DOWN_POINTING_TRIANGLE 0x25bd #define UNITEXT_WHITE_DOWN_POINTING_TRIANGLE L"\u25bd" #define UNICODE_BLACK_DOWN_POINTING_SMALL_TRIANGLE 0x25be #define UNITEXT_BLACK_DOWN_POINTING_SMALL_TRIANGLE L"\u25be" #define UNICODE_WHITE_DOWN_POINTING_SMALL_TRIANGLE 0x25bf #define UNITEXT_WHITE_DOWN_POINTING_SMALL_TRIANGLE L"\u25bf" #define UNICODE_BLACK_LEFT_POINTING_TRIANGLE 0x25c0 #define UNITEXT_BLACK_LEFT_POINTING_TRIANGLE L"\u25c0" #define UNICODE_WHITE_LEFT_POINTING_TRIANGLE 0x25c1 #define UNITEXT_WHITE_LEFT_POINTING_TRIANGLE L"\u25c1" #define UNICODE_BLACK_LEFT_POINTING_SMALL_TRIANGLE 0x25c2 #define UNITEXT_BLACK_LEFT_POINTING_SMALL_TRIANGLE L"\u25c2" #define UNICODE_WHITE_LEFT_POINTING_SMALL_TRIANGLE 0x25c3 #define UNITEXT_WHITE_LEFT_POINTING_SMALL_TRIANGLE L"\u25c3" #define UNICODE_BLACK_LEFT_POINTING_POINTER 0x25c4 #define UNITEXT_BLACK_LEFT_POINTING_POINTER L"\u25c4" #define UNICODE_WHITE_LEFT_POINTING_POINTER 0x25c5 #define UNITEXT_WHITE_LEFT_POINTING_POINTER L"\u25c5" #define UNICODE_BLACK_DIAMOND 0x25c6 #define UNITEXT_BLACK_DIAMOND L"\u25c6" #define UNICODE_WHITE_DIAMOND 0x25c7 #define UNITEXT_WHITE_DIAMOND L"\u25c7" #define UNICODE_WHITE_DIAMOND_CONTAINING_BLACK_SMALL_DIAMOND 0x25c8 #define UNITEXT_WHITE_DIAMOND_CONTAINING_BLACK_SMALL_DIAMOND L"\u25c8" #define UNICODE_FISHEYE 0x25c9 #define UNITEXT_FISHEYE L"\u25c9" #define UNICODE_LOZENGE 0x25ca #define UNITEXT_LOZENGE L"\u25ca" #define UNICODE_WHITE_CIRCLE 0x25cb #define UNITEXT_WHITE_CIRCLE L"\u25cb" #define UNICODE_DOTTED_CIRCLE 0x25cc #define UNITEXT_DOTTED_CIRCLE L"\u25cc" #define UNICODE_CIRCLE_WITH_VERTICAL_FILL 0x25cd #define UNITEXT_CIRCLE_WITH_VERTICAL_FILL L"\u25cd" #define UNICODE_BULLSEYE 0x25ce #define UNITEXT_BULLSEYE L"\u25ce" #define UNICODE_BLACK_CIRCLE 0x25cf #define UNITEXT_BLACK_CIRCLE L"\u25cf" #define UNICODE_CIRCLE_WITH_LEFT_HALF_BLACK 0x25d0 #define UNITEXT_CIRCLE_WITH_LEFT_HALF_BLACK L"\u25d0" #define UNICODE_CIRCLE_WITH_RIGHT_HALF_BLACK 0x25d1 #define UNITEXT_CIRCLE_WITH_RIGHT_HALF_BLACK L"\u25d1" #define UNICODE_CIRCLE_WITH_LOWER_HALF_BLACK 0x25d2 #define UNITEXT_CIRCLE_WITH_LOWER_HALF_BLACK L"\u25d2" #define UNICODE_CIRCLE_WITH_UPPER_HALF_BLACK 0x25d3 #define UNITEXT_CIRCLE_WITH_UPPER_HALF_BLACK L"\u25d3" #define UNICODE_CIRCLE_WITH_UPPER_RIGHT_QUADRANT_BLACK 0x25d4 #define UNITEXT_CIRCLE_WITH_UPPER_RIGHT_QUADRANT_BLACK L"\u25d4" #define UNICODE_CIRCLE_WITH_ALL_BUT_UPPER_LEFT_QUADRANT_BLACK 0x25d5 #define UNITEXT_CIRCLE_WITH_ALL_BUT_UPPER_LEFT_QUADRANT_BLACK L"\u25d5" #define UNICODE_LEFT_HALF_BLACK_CIRCLE 0x25d6 #define UNITEXT_LEFT_HALF_BLACK_CIRCLE L"\u25d6" #define UNICODE_RIGHT_HALF_BLACK_CIRCLE 0x25d7 #define UNITEXT_RIGHT_HALF_BLACK_CIRCLE L"\u25d7" #define UNICODE_INVERSE_BULLET 0x25d8 #define UNITEXT_INVERSE_BULLET L"\u25d8" #define UNICODE_INVERSE_WHITE_CIRCLE 0x25d9 #define UNITEXT_INVERSE_WHITE_CIRCLE L"\u25d9" #define UNICODE_UPPER_HALF_INVERSE_WHITE_CIRCLE 0x25da #define UNITEXT_UPPER_HALF_INVERSE_WHITE_CIRCLE L"\u25da" #define UNICODE_LOWER_HALF_INVERSE_WHITE_CIRCLE 0x25db #define UNITEXT_LOWER_HALF_INVERSE_WHITE_CIRCLE L"\u25db" #define UNICODE_UPPER_LEFT_QUADRANT_CIRCULAR_ARC 0x25dc #define UNITEXT_UPPER_LEFT_QUADRANT_CIRCULAR_ARC L"\u25dc" #define UNICODE_UPPER_RIGHT_QUADRANT_CIRCULAR_ARC 0x25dd #define UNITEXT_UPPER_RIGHT_QUADRANT_CIRCULAR_ARC L"\u25dd" #define UNICODE_LOWER_RIGHT_QUADRANT_CIRCULAR_ARC 0x25de #define UNITEXT_LOWER_RIGHT_QUADRANT_CIRCULAR_ARC L"\u25de" #define UNICODE_LOWER_LEFT_QUADRANT_CIRCULAR_ARC 0x25df #define UNITEXT_LOWER_LEFT_QUADRANT_CIRCULAR_ARC L"\u25df" #define UNICODE_UPPER_HALF_CIRCLE 0x25e0 #define UNITEXT_UPPER_HALF_CIRCLE L"\u25e0" #define UNICODE_LOWER_HALF_CIRCLE 0x25e1 #define UNITEXT_LOWER_HALF_CIRCLE L"\u25e1" #define UNICODE_BLACK_LOWER_RIGHT_TRIANGLE 0x25e2 #define UNITEXT_BLACK_LOWER_RIGHT_TRIANGLE L"\u25e2" #define UNICODE_BLACK_LOWER_LEFT_TRIANGLE 0x25e3 #define UNITEXT_BLACK_LOWER_LEFT_TRIANGLE L"\u25e3" #define UNICODE_BLACK_UPPER_LEFT_TRIANGLE 0x25e4 #define UNITEXT_BLACK_UPPER_LEFT_TRIANGLE L"\u25e4" #define UNICODE_BLACK_UPPER_RIGHT_TRIANGLE 0x25e5 #define UNITEXT_BLACK_UPPER_RIGHT_TRIANGLE L"\u25e5" #define UNICODE_WHITE_BULLET 0x25e6 #define UNITEXT_WHITE_BULLET L"\u25e6" #define UNICODE_SQUARE_WITH_LEFT_HALF_BLACK 0x25e7 #define UNITEXT_SQUARE_WITH_LEFT_HALF_BLACK L"\u25e7" #define UNICODE_SQUARE_WITH_RIGHT_HALF_BLACK 0x25e8 #define UNITEXT_SQUARE_WITH_RIGHT_HALF_BLACK L"\u25e8" #define UNICODE_SQUARE_WITH_UPPER_LEFT_DIAGONAL_HALF_BLACK 0x25e9 #define UNITEXT_SQUARE_WITH_UPPER_LEFT_DIAGONAL_HALF_BLACK L"\u25e9" #define UNICODE_SQUARE_WITH_LOWER_RIGHT_DIAGONAL_HALF_BLACK 0x25ea #define UNITEXT_SQUARE_WITH_LOWER_RIGHT_DIAGONAL_HALF_BLACK L"\u25ea" #define UNICODE_WHITE_SQUARE_WITH_VERTICAL_BISECTING_LINE 0x25eb #define UNITEXT_WHITE_SQUARE_WITH_VERTICAL_BISECTING_LINE L"\u25eb" #define UNICODE_WHITE_UP_POINTING_TRIANGLE_WITH_DOT 0x25ec #define UNITEXT_WHITE_UP_POINTING_TRIANGLE_WITH_DOT L"\u25ec" #define UNICODE_UP_POINTING_TRIANGLE_WITH_LEFT_HALF_BLACK 0x25ed #define UNITEXT_UP_POINTING_TRIANGLE_WITH_LEFT_HALF_BLACK L"\u25ed" #define UNICODE_UP_POINTING_TRIANGLE_WITH_RIGHT_HALF_BLACK 0x25ee #define UNITEXT_UP_POINTING_TRIANGLE_WITH_RIGHT_HALF_BLACK L"\u25ee" #define UNICODE_LARGE_CIRCLE 0x25ef #define UNITEXT_LARGE_CIRCLE L"\u25ef" #define UNICODE_WHITE_SQUARE_WITH_UPPER_LEFT_QUADRANT 0x25f0 #define UNITEXT_WHITE_SQUARE_WITH_UPPER_LEFT_QUADRANT L"\u25f0" #define UNICODE_WHITE_SQUARE_WITH_LOWER_LEFT_QUADRANT 0x25f1 #define UNITEXT_WHITE_SQUARE_WITH_LOWER_LEFT_QUADRANT L"\u25f1" #define UNICODE_WHITE_SQUARE_WITH_LOWER_RIGHT_QUADRANT 0x25f2 #define UNITEXT_WHITE_SQUARE_WITH_LOWER_RIGHT_QUADRANT L"\u25f2" #define UNICODE_WHITE_SQUARE_WITH_UPPER_RIGHT_QUADRANT 0x25f3 #define UNITEXT_WHITE_SQUARE_WITH_UPPER_RIGHT_QUADRANT L"\u25f3" #define UNICODE_WHITE_CIRCLE_WITH_UPPER_LEFT_QUADRANT 0x25f4 #define UNITEXT_WHITE_CIRCLE_WITH_UPPER_LEFT_QUADRANT L"\u25f4" #define UNICODE_WHITE_CIRCLE_WITH_LOWER_LEFT_QUADRANT 0x25f5 #define UNITEXT_WHITE_CIRCLE_WITH_LOWER_LEFT_QUADRANT L"\u25f5" #define UNICODE_WHITE_CIRCLE_WITH_LOWER_RIGHT_QUADRANT 0x25f6 #define UNITEXT_WHITE_CIRCLE_WITH_LOWER_RIGHT_QUADRANT L"\u25f6" #define UNICODE_WHITE_CIRCLE_WITH_UPPER_RIGHT_QUADRANT 0x25f7 #define UNITEXT_WHITE_CIRCLE_WITH_UPPER_RIGHT_QUADRANT L"\u25f7" #define UNICODE_UPPER_LEFT_TRIANGLE 0x25f8 #define UNITEXT_UPPER_LEFT_TRIANGLE L"\u25f8" #define UNICODE_UPPER_RIGHT_TRIANGLE 0x25f9 #define UNITEXT_UPPER_RIGHT_TRIANGLE L"\u25f9" #define UNICODE_LOWER_LEFT_TRIANGLE 0x25fa #define UNITEXT_LOWER_LEFT_TRIANGLE L"\u25fa" #define UNICODE_WHITE_MEDIUM_SQUARE 0x25fb #define UNITEXT_WHITE_MEDIUM_SQUARE L"\u25fb" #define UNICODE_BLACK_MEDIUM_SQUARE 0x25fc #define UNITEXT_BLACK_MEDIUM_SQUARE L"\u25fc" #define UNICODE_WHITE_MEDIUM_SMALL_SQUARE 0x25fd #define UNITEXT_WHITE_MEDIUM_SMALL_SQUARE L"\u25fd" #define UNICODE_BLACK_MEDIUM_SMALL_SQUARE 0x25fe #define UNITEXT_BLACK_MEDIUM_SMALL_SQUARE L"\u25fe" #define UNICODE_LOWER_RIGHT_TRIANGLE 0x25ff #define UNITEXT_LOWER_RIGHT_TRIANGLE L"\u25ff" #define UNICODE_BLACK_SUN_WITH_RAYS 0x2600 #define UNITEXT_BLACK_SUN_WITH_RAYS L"\u2600" #define UNICODE_CLOUD 0x2601 #define UNITEXT_CLOUD L"\u2601" #define UNICODE_UMBRELLA 0x2602 #define UNITEXT_UMBRELLA L"\u2602" #define UNICODE_SNOWMAN 0x2603 #define UNITEXT_SNOWMAN L"\u2603" #define UNICODE_COMET 0x2604 #define UNITEXT_COMET L"\u2604" #define UNICODE_BLACK_STAR 0x2605 #define UNITEXT_BLACK_STAR L"\u2605" #define UNICODE_WHITE_STAR 0x2606 #define UNITEXT_WHITE_STAR L"\u2606" #define UNICODE_LIGHTNING 0x2607 #define UNITEXT_LIGHTNING L"\u2607" #define UNICODE_THUNDERSTORM 0x2608 #define UNITEXT_THUNDERSTORM L"\u2608" #define UNICODE_SUN 0x2609 #define UNITEXT_SUN L"\u2609" #define UNICODE_ASCENDING_NODE 0x260a #define UNITEXT_ASCENDING_NODE L"\u260a" #define UNICODE_DESCENDING_NODE 0x260b #define UNITEXT_DESCENDING_NODE L"\u260b" #define UNICODE_CONJUNCTION 0x260c #define UNITEXT_CONJUNCTION L"\u260c" #define UNICODE_OPPOSITION 0x260d #define UNITEXT_OPPOSITION L"\u260d" #define UNICODE_BLACK_TELEPHONE 0x260e #define UNITEXT_BLACK_TELEPHONE L"\u260e" #define UNICODE_WHITE_TELEPHONE 0x260f #define UNITEXT_WHITE_TELEPHONE L"\u260f" #define UNICODE_BALLOT_BOX 0x2610 #define UNITEXT_BALLOT_BOX L"\u2610" #define UNICODE_BALLOT_BOX_WITH_CHECK 0x2611 #define UNITEXT_BALLOT_BOX_WITH_CHECK L"\u2611" #define UNICODE_BALLOT_BOX_WITH_X 0x2612 #define UNITEXT_BALLOT_BOX_WITH_X L"\u2612" #define UNICODE_SALTIRE 0x2613 #define UNITEXT_SALTIRE L"\u2613" #define UNICODE_UMBRELLA_WITH_RAIN_DROPS 0x2614 #define UNITEXT_UMBRELLA_WITH_RAIN_DROPS L"\u2614" #define UNICODE_HOT_BEVERAGE 0x2615 #define UNITEXT_HOT_BEVERAGE L"\u2615" #define UNICODE_WHITE_SHOGI_PIECE 0x2616 #define UNITEXT_WHITE_SHOGI_PIECE L"\u2616" #define UNICODE_BLACK_SHOGI_PIECE 0x2617 #define UNITEXT_BLACK_SHOGI_PIECE L"\u2617" #define UNICODE_SHAMROCK 0x2618 #define UNITEXT_SHAMROCK L"\u2618" #define UNICODE_REVERSED_ROTATED_FLORAL_HEART_BULLET 0x2619 #define UNITEXT_REVERSED_ROTATED_FLORAL_HEART_BULLET L"\u2619" #define UNICODE_BLACK_LEFT_POINTING_INDEX 0x261a #define UNITEXT_BLACK_LEFT_POINTING_INDEX L"\u261a" #define UNICODE_BLACK_RIGHT_POINTING_INDEX 0x261b #define UNITEXT_BLACK_RIGHT_POINTING_INDEX L"\u261b" #define UNICODE_WHITE_LEFT_POINTING_INDEX 0x261c #define UNITEXT_WHITE_LEFT_POINTING_INDEX L"\u261c" #define UNICODE_WHITE_UP_POINTING_INDEX 0x261d #define UNITEXT_WHITE_UP_POINTING_INDEX L"\u261d" #define UNICODE_WHITE_RIGHT_POINTING_INDEX 0x261e #define UNITEXT_WHITE_RIGHT_POINTING_INDEX L"\u261e" #define UNICODE_WHITE_DOWN_POINTING_INDEX 0x261f #define UNITEXT_WHITE_DOWN_POINTING_INDEX L"\u261f" #define UNICODE_SKULL_AND_CROSSBONES 0x2620 #define UNITEXT_SKULL_AND_CROSSBONES L"\u2620" #define UNICODE_CAUTION_SIGN 0x2621 #define UNITEXT_CAUTION_SIGN L"\u2621" #define UNICODE_RADIOACTIVE_SIGN 0x2622 #define UNITEXT_RADIOACTIVE_SIGN L"\u2622" #define UNICODE_BIOHAZARD_SIGN 0x2623 #define UNITEXT_BIOHAZARD_SIGN L"\u2623" #define UNICODE_CADUCEUS 0x2624 #define UNITEXT_CADUCEUS L"\u2624" #define UNICODE_ANKH 0x2625 #define UNITEXT_ANKH L"\u2625" #define UNICODE_ORTHODOX_CROSS 0x2626 #define UNITEXT_ORTHODOX_CROSS L"\u2626" #define UNICODE_CHI_RHO 0x2627 #define UNITEXT_CHI_RHO L"\u2627" #define UNICODE_CROSS_OF_LORRAINE 0x2628 #define UNITEXT_CROSS_OF_LORRAINE L"\u2628" #define UNICODE_CROSS_OF_JERUSALEM 0x2629 #define UNITEXT_CROSS_OF_JERUSALEM L"\u2629" #define UNICODE_STAR_AND_CRESCENT 0x262a #define UNITEXT_STAR_AND_CRESCENT L"\u262a" #define UNICODE_FARSI_SYMBOL 0x262b #define UNITEXT_FARSI_SYMBOL L"\u262b" #define UNICODE_ADI_SHAKTI 0x262c #define UNITEXT_ADI_SHAKTI L"\u262c" #define UNICODE_HAMMER_AND_SICKLE 0x262d #define UNITEXT_HAMMER_AND_SICKLE L"\u262d" #define UNICODE_PEACE_SYMBOL 0x262e #define UNITEXT_PEACE_SYMBOL L"\u262e" #define UNICODE_YIN_YANG 0x262f #define UNITEXT_YIN_YANG L"\u262f" #define UNICODE_TRIGRAM_FOR_HEAVEN 0x2630 #define UNITEXT_TRIGRAM_FOR_HEAVEN L"\u2630" #define UNICODE_TRIGRAM_FOR_LAKE 0x2631 #define UNITEXT_TRIGRAM_FOR_LAKE L"\u2631" #define UNICODE_TRIGRAM_FOR_FIRE 0x2632 #define UNITEXT_TRIGRAM_FOR_FIRE L"\u2632" #define UNICODE_TRIGRAM_FOR_THUNDER 0x2633 #define UNITEXT_TRIGRAM_FOR_THUNDER L"\u2633" #define UNICODE_TRIGRAM_FOR_WIND 0x2634 #define UNITEXT_TRIGRAM_FOR_WIND L"\u2634" #define UNICODE_TRIGRAM_FOR_WATER 0x2635 #define UNITEXT_TRIGRAM_FOR_WATER L"\u2635" #define UNICODE_TRIGRAM_FOR_MOUNTAIN 0x2636 #define UNITEXT_TRIGRAM_FOR_MOUNTAIN L"\u2636" #define UNICODE_TRIGRAM_FOR_EARTH 0x2637 #define UNITEXT_TRIGRAM_FOR_EARTH L"\u2637" #define UNICODE_WHEEL_OF_DHARMA 0x2638 #define UNITEXT_WHEEL_OF_DHARMA L"\u2638" #define UNICODE_WHITE_FROWNING_FACE 0x2639 #define UNITEXT_WHITE_FROWNING_FACE L"\u2639" #define UNICODE_WHITE_SMILING_FACE 0x263a #define UNITEXT_WHITE_SMILING_FACE L"\u263a" #define UNICODE_BLACK_SMILING_FACE 0x263b #define UNITEXT_BLACK_SMILING_FACE L"\u263b" #define UNICODE_WHITE_SUN_WITH_RAYS 0x263c #define UNITEXT_WHITE_SUN_WITH_RAYS L"\u263c" #define UNICODE_FIRST_QUARTER_MOON 0x263d #define UNITEXT_FIRST_QUARTER_MOON L"\u263d" #define UNICODE_LAST_QUARTER_MOON 0x263e #define UNITEXT_LAST_QUARTER_MOON L"\u263e" #define UNICODE_MERCURY 0x263f #define UNITEXT_MERCURY L"\u263f" #define UNICODE_FEMALE_SIGN 0x2640 #define UNITEXT_FEMALE_SIGN L"\u2640" #define UNICODE_EARTH 0x2641 #define UNITEXT_EARTH L"\u2641" #define UNICODE_MALE_SIGN 0x2642 #define UNITEXT_MALE_SIGN L"\u2642" #define UNICODE_JUPITER 0x2643 #define UNITEXT_JUPITER L"\u2643" #define UNICODE_SATURN 0x2644 #define UNITEXT_SATURN L"\u2644" #define UNICODE_URANUS 0x2645 #define UNITEXT_URANUS L"\u2645" #define UNICODE_NEPTUNE 0x2646 #define UNITEXT_NEPTUNE L"\u2646" #define UNICODE_PLUTO 0x2647 #define UNITEXT_PLUTO L"\u2647" #define UNICODE_ARIES 0x2648 #define UNITEXT_ARIES L"\u2648" #define UNICODE_TAURUS 0x2649 #define UNITEXT_TAURUS L"\u2649" #define UNICODE_GEMINI 0x264a #define UNITEXT_GEMINI L"\u264a" #define UNICODE_CANCER 0x264b #define UNITEXT_CANCER L"\u264b" #define UNICODE_LEO 0x264c #define UNITEXT_LEO L"\u264c" #define UNICODE_VIRGO 0x264d #define UNITEXT_VIRGO L"\u264d" #define UNICODE_LIBRA 0x264e #define UNITEXT_LIBRA L"\u264e" #define UNICODE_SCORPIUS 0x264f #define UNITEXT_SCORPIUS L"\u264f" #define UNICODE_SAGITTARIUS 0x2650 #define UNITEXT_SAGITTARIUS L"\u2650" #define UNICODE_CAPRICORN 0x2651 #define UNITEXT_CAPRICORN L"\u2651" #define UNICODE_AQUARIUS 0x2652 #define UNITEXT_AQUARIUS L"\u2652" #define UNICODE_PISCES 0x2653 #define UNITEXT_PISCES L"\u2653" #define UNICODE_WHITE_CHESS_KING 0x2654 #define UNITEXT_WHITE_CHESS_KING L"\u2654" #define UNICODE_WHITE_CHESS_QUEEN 0x2655 #define UNITEXT_WHITE_CHESS_QUEEN L"\u2655" #define UNICODE_WHITE_CHESS_ROOK 0x2656 #define UNITEXT_WHITE_CHESS_ROOK L"\u2656" #define UNICODE_WHITE_CHESS_BISHOP 0x2657 #define UNITEXT_WHITE_CHESS_BISHOP L"\u2657" #define UNICODE_WHITE_CHESS_KNIGHT 0x2658 #define UNITEXT_WHITE_CHESS_KNIGHT L"\u2658" #define UNICODE_WHITE_CHESS_PAWN 0x2659 #define UNITEXT_WHITE_CHESS_PAWN L"\u2659" #define UNICODE_BLACK_CHESS_KING 0x265a #define UNITEXT_BLACK_CHESS_KING L"\u265a" #define UNICODE_BLACK_CHESS_QUEEN 0x265b #define UNITEXT_BLACK_CHESS_QUEEN L"\u265b" #define UNICODE_BLACK_CHESS_ROOK 0x265c #define UNITEXT_BLACK_CHESS_ROOK L"\u265c" #define UNICODE_BLACK_CHESS_BISHOP 0x265d #define UNITEXT_BLACK_CHESS_BISHOP L"\u265d" #define UNICODE_BLACK_CHESS_KNIGHT 0x265e #define UNITEXT_BLACK_CHESS_KNIGHT L"\u265e" #define UNICODE_BLACK_CHESS_PAWN 0x265f #define UNITEXT_BLACK_CHESS_PAWN L"\u265f" #define UNICODE_BLACK_SPADE_SUIT 0x2660 #define UNITEXT_BLACK_SPADE_SUIT L"\u2660" #define UNICODE_WHITE_HEART_SUIT 0x2661 #define UNITEXT_WHITE_HEART_SUIT L"\u2661" #define UNICODE_WHITE_DIAMOND_SUIT 0x2662 #define UNITEXT_WHITE_DIAMOND_SUIT L"\u2662" #define UNICODE_BLACK_CLUB_SUIT 0x2663 #define UNITEXT_BLACK_CLUB_SUIT L"\u2663" #define UNICODE_WHITE_SPADE_SUIT 0x2664 #define UNITEXT_WHITE_SPADE_SUIT L"\u2664" #define UNICODE_BLACK_HEART_SUIT 0x2665 #define UNITEXT_BLACK_HEART_SUIT L"\u2665" #define UNICODE_BLACK_DIAMOND_SUIT 0x2666 #define UNITEXT_BLACK_DIAMOND_SUIT L"\u2666" #define UNICODE_WHITE_CLUB_SUIT 0x2667 #define UNITEXT_WHITE_CLUB_SUIT L"\u2667" #define UNICODE_HOT_SPRINGS 0x2668 #define UNITEXT_HOT_SPRINGS L"\u2668" #define UNICODE_QUARTER_NOTE 0x2669 #define UNITEXT_QUARTER_NOTE L"\u2669" #define UNICODE_EIGHTH_NOTE 0x266a #define UNITEXT_EIGHTH_NOTE L"\u266a" #define UNICODE_BEAMED_EIGHTH_NOTES 0x266b #define UNITEXT_BEAMED_EIGHTH_NOTES L"\u266b" #define UNICODE_BEAMED_SIXTEENTH_NOTES 0x266c #define UNITEXT_BEAMED_SIXTEENTH_NOTES L"\u266c" #define UNICODE_MUSIC_FLAT_SIGN 0x266d #define UNITEXT_MUSIC_FLAT_SIGN L"\u266d" #define UNICODE_MUSIC_NATURAL_SIGN 0x266e #define UNITEXT_MUSIC_NATURAL_SIGN L"\u266e" #define UNICODE_MUSIC_SHARP_SIGN 0x266f #define UNITEXT_MUSIC_SHARP_SIGN L"\u266f" #define UNICODE_WEST_SYRIAC_CROSS 0x2670 #define UNITEXT_WEST_SYRIAC_CROSS L"\u2670" #define UNICODE_EAST_SYRIAC_CROSS 0x2671 #define UNITEXT_EAST_SYRIAC_CROSS L"\u2671" #define UNICODE_UNIVERSAL_RECYCLING_SYMBOL 0x2672 #define UNITEXT_UNIVERSAL_RECYCLING_SYMBOL L"\u2672" #define UNICODE_RECYCLING_SYMBOL_FOR_TYPE_1_PLASTICS 0x2673 #define UNITEXT_RECYCLING_SYMBOL_FOR_TYPE_1_PLASTICS L"\u2673" #define UNICODE_RECYCLING_SYMBOL_FOR_TYPE_2_PLASTICS 0x2674 #define UNITEXT_RECYCLING_SYMBOL_FOR_TYPE_2_PLASTICS L"\u2674" #define UNICODE_RECYCLING_SYMBOL_FOR_TYPE_3_PLASTICS 0x2675 #define UNITEXT_RECYCLING_SYMBOL_FOR_TYPE_3_PLASTICS L"\u2675" #define UNICODE_RECYCLING_SYMBOL_FOR_TYPE_4_PLASTICS 0x2676 #define UNITEXT_RECYCLING_SYMBOL_FOR_TYPE_4_PLASTICS L"\u2676" #define UNICODE_RECYCLING_SYMBOL_FOR_TYPE_5_PLASTICS 0x2677 #define UNITEXT_RECYCLING_SYMBOL_FOR_TYPE_5_PLASTICS L"\u2677" #define UNICODE_RECYCLING_SYMBOL_FOR_TYPE_6_PLASTICS 0x2678 #define UNITEXT_RECYCLING_SYMBOL_FOR_TYPE_6_PLASTICS L"\u2678" #define UNICODE_RECYCLING_SYMBOL_FOR_TYPE_7_PLASTICS 0x2679 #define UNITEXT_RECYCLING_SYMBOL_FOR_TYPE_7_PLASTICS L"\u2679" #define UNICODE_RECYCLING_SYMBOL_FOR_GENERIC_MATERIALS 0x267a #define UNITEXT_RECYCLING_SYMBOL_FOR_GENERIC_MATERIALS L"\u267a" #define UNICODE_BLACK_UNIVERSAL_RECYCLING_SYMBOL 0x267b #define UNITEXT_BLACK_UNIVERSAL_RECYCLING_SYMBOL L"\u267b" #define UNICODE_RECYCLED_PAPER_SYMBOL 0x267c #define UNITEXT_RECYCLED_PAPER_SYMBOL L"\u267c" #define UNICODE_PARTIALLY_RECYCLED_PAPER_SYMBOL 0x267d #define UNITEXT_PARTIALLY_RECYCLED_PAPER_SYMBOL L"\u267d" #define UNICODE_PERMANENT_PAPER_SIGN 0x267e #define UNITEXT_PERMANENT_PAPER_SIGN L"\u267e" #define UNICODE_WHEELCHAIR_SYMBOL 0x267f #define UNITEXT_WHEELCHAIR_SYMBOL L"\u267f" #define UNICODE_DIE_FACE_1 0x2680 #define UNITEXT_DIE_FACE_1 L"\u2680" #define UNICODE_DIE_FACE_2 0x2681 #define UNITEXT_DIE_FACE_2 L"\u2681" #define UNICODE_DIE_FACE_3 0x2682 #define UNITEXT_DIE_FACE_3 L"\u2682" #define UNICODE_DIE_FACE_4 0x2683 #define UNITEXT_DIE_FACE_4 L"\u2683" #define UNICODE_DIE_FACE_5 0x2684 #define UNITEXT_DIE_FACE_5 L"\u2684" #define UNICODE_DIE_FACE_6 0x2685 #define UNITEXT_DIE_FACE_6 L"\u2685" #define UNICODE_WHITE_CIRCLE_WITH_DOT_RIGHT 0x2686 #define UNITEXT_WHITE_CIRCLE_WITH_DOT_RIGHT L"\u2686" #define UNICODE_WHITE_CIRCLE_WITH_TWO_DOTS 0x2687 #define UNITEXT_WHITE_CIRCLE_WITH_TWO_DOTS L"\u2687" #define UNICODE_BLACK_CIRCLE_WITH_WHITE_DOT_RIGHT 0x2688 #define UNITEXT_BLACK_CIRCLE_WITH_WHITE_DOT_RIGHT L"\u2688" #define UNICODE_BLACK_CIRCLE_WITH_TWO_WHITE_DOTS 0x2689 #define UNITEXT_BLACK_CIRCLE_WITH_TWO_WHITE_DOTS L"\u2689" #define UNICODE_MONOGRAM_FOR_YANG 0x268a #define UNITEXT_MONOGRAM_FOR_YANG L"\u268a" #define UNICODE_MONOGRAM_FOR_YIN 0x268b #define UNITEXT_MONOGRAM_FOR_YIN L"\u268b" #define UNICODE_DIGRAM_FOR_GREATER_YANG 0x268c #define UNITEXT_DIGRAM_FOR_GREATER_YANG L"\u268c" #define UNICODE_DIGRAM_FOR_LESSER_YIN 0x268d #define UNITEXT_DIGRAM_FOR_LESSER_YIN L"\u268d" #define UNICODE_DIGRAM_FOR_LESSER_YANG 0x268e #define UNITEXT_DIGRAM_FOR_LESSER_YANG L"\u268e" #define UNICODE_DIGRAM_FOR_GREATER_YIN 0x268f #define UNITEXT_DIGRAM_FOR_GREATER_YIN L"\u268f" #define UNICODE_WHITE_FLAG 0x2690 #define UNITEXT_WHITE_FLAG L"\u2690" #define UNICODE_BLACK_FLAG 0x2691 #define UNITEXT_BLACK_FLAG L"\u2691" #define UNICODE_HAMMER_AND_PICK 0x2692 #define UNITEXT_HAMMER_AND_PICK L"\u2692" #define UNICODE_ANCHOR 0x2693 #define UNITEXT_ANCHOR L"\u2693" #define UNICODE_CROSSED_SWORDS 0x2694 #define UNITEXT_CROSSED_SWORDS L"\u2694" #define UNICODE_STAFF_OF_AESCULAPIUS 0x2695 #define UNITEXT_STAFF_OF_AESCULAPIUS L"\u2695" #define UNICODE_SCALES 0x2696 #define UNITEXT_SCALES L"\u2696" #define UNICODE_ALEMBIC 0x2697 #define UNITEXT_ALEMBIC L"\u2697" #define UNICODE_FLOWER 0x2698 #define UNITEXT_FLOWER L"\u2698" #define UNICODE_GEAR 0x2699 #define UNITEXT_GEAR L"\u2699" #define UNICODE_STAFF_OF_HERMES 0x269a #define UNITEXT_STAFF_OF_HERMES L"\u269a" #define UNICODE_ATOM_SYMBOL 0x269b #define UNITEXT_ATOM_SYMBOL L"\u269b" #define UNICODE_FLEUR_DE_LIS 0x269c #define UNITEXT_FLEUR_DE_LIS L"\u269c" #define UNICODE_WARNING_SIGN 0x26a0 #define UNITEXT_WARNING_SIGN L"\u26a0" #define UNICODE_HIGH_VOLTAGE_SIGN 0x26a1 #define UNITEXT_HIGH_VOLTAGE_SIGN L"\u26a1" #define UNICODE_DOUBLED_FEMALE_SIGN 0x26a2 #define UNITEXT_DOUBLED_FEMALE_SIGN L"\u26a2" #define UNICODE_DOUBLED_MALE_SIGN 0x26a3 #define UNITEXT_DOUBLED_MALE_SIGN L"\u26a3" #define UNICODE_INTERLOCKED_FEMALE_AND_MALE_SIGN 0x26a4 #define UNITEXT_INTERLOCKED_FEMALE_AND_MALE_SIGN L"\u26a4" #define UNICODE_MALE_AND_FEMALE_SIGN 0x26a5 #define UNITEXT_MALE_AND_FEMALE_SIGN L"\u26a5" #define UNICODE_MALE_WITH_STROKE_SIGN 0x26a6 #define UNITEXT_MALE_WITH_STROKE_SIGN L"\u26a6" #define UNICODE_MALE_WITH_STROKE_AND_MALE_AND_FEMALE_SIGN 0x26a7 #define UNITEXT_MALE_WITH_STROKE_AND_MALE_AND_FEMALE_SIGN L"\u26a7" #define UNICODE_VERTICAL_MALE_WITH_STROKE_SIGN 0x26a8 #define UNITEXT_VERTICAL_MALE_WITH_STROKE_SIGN L"\u26a8" #define UNICODE_HORIZONTAL_MALE_WITH_STROKE_SIGN 0x26a9 #define UNITEXT_HORIZONTAL_MALE_WITH_STROKE_SIGN L"\u26a9" #define UNICODE_MEDIUM_WHITE_CIRCLE 0x26aa #define UNITEXT_MEDIUM_WHITE_CIRCLE L"\u26aa" #define UNICODE_MEDIUM_BLACK_CIRCLE 0x26ab #define UNITEXT_MEDIUM_BLACK_CIRCLE L"\u26ab" #define UNICODE_MEDIUM_SMALL_WHITE_CIRCLE 0x26ac #define UNITEXT_MEDIUM_SMALL_WHITE_CIRCLE L"\u26ac" #define UNICODE_MARRIAGE_SYMBOL 0x26ad #define UNITEXT_MARRIAGE_SYMBOL L"\u26ad" #define UNICODE_DIVORCE_SYMBOL 0x26ae #define UNITEXT_DIVORCE_SYMBOL L"\u26ae" #define UNICODE_UNMARRIED_PARTNERSHIP_SYMBOL 0x26af #define UNITEXT_UNMARRIED_PARTNERSHIP_SYMBOL L"\u26af" #define UNICODE_COFFIN 0x26b0 #define UNITEXT_COFFIN L"\u26b0" #define UNICODE_FUNERAL_URN 0x26b1 #define UNITEXT_FUNERAL_URN L"\u26b1" #define UNICODE_NEUTER 0x26b2 #define UNITEXT_NEUTER L"\u26b2" #define UNICODE_UPPER_BLADE_SCISSORS 0x2701 #define UNITEXT_UPPER_BLADE_SCISSORS L"\u2701" #define UNICODE_BLACK_SCISSORS 0x2702 #define UNITEXT_BLACK_SCISSORS L"\u2702" #define UNICODE_LOWER_BLADE_SCISSORS 0x2703 #define UNITEXT_LOWER_BLADE_SCISSORS L"\u2703" #define UNICODE_WHITE_SCISSORS 0x2704 #define UNITEXT_WHITE_SCISSORS L"\u2704" #define UNICODE_TELEPHONE_LOCATION_SIGN 0x2706 #define UNITEXT_TELEPHONE_LOCATION_SIGN L"\u2706" #define UNICODE_TAPE_DRIVE 0x2707 #define UNITEXT_TAPE_DRIVE L"\u2707" #define UNICODE_AIRPLANE 0x2708 #define UNITEXT_AIRPLANE L"\u2708" #define UNICODE_ENVELOPE 0x2709 #define UNITEXT_ENVELOPE L"\u2709" #define UNICODE_VICTORY_HAND 0x270c #define UNITEXT_VICTORY_HAND L"\u270c" #define UNICODE_WRITING_HAND 0x270d #define UNITEXT_WRITING_HAND L"\u270d" #define UNICODE_LOWER_RIGHT_PENCIL 0x270e #define UNITEXT_LOWER_RIGHT_PENCIL L"\u270e" #define UNICODE_PENCIL 0x270f #define UNITEXT_PENCIL L"\u270f" #define UNICODE_UPPER_RIGHT_PENCIL 0x2710 #define UNITEXT_UPPER_RIGHT_PENCIL L"\u2710" #define UNICODE_WHITE_NIB 0x2711 #define UNITEXT_WHITE_NIB L"\u2711" #define UNICODE_BLACK_NIB 0x2712 #define UNITEXT_BLACK_NIB L"\u2712" #define UNICODE_CHECK_MARK 0x2713 #define UNITEXT_CHECK_MARK L"\u2713" #define UNICODE_HEAVY_CHECK_MARK 0x2714 #define UNITEXT_HEAVY_CHECK_MARK L"\u2714" #define UNICODE_MULTIPLICATION_X 0x2715 #define UNITEXT_MULTIPLICATION_X L"\u2715" #define UNICODE_HEAVY_MULTIPLICATION_X 0x2716 #define UNITEXT_HEAVY_MULTIPLICATION_X L"\u2716" #define UNICODE_BALLOT_X 0x2717 #define UNITEXT_BALLOT_X L"\u2717" #define UNICODE_HEAVY_BALLOT_X 0x2718 #define UNITEXT_HEAVY_BALLOT_X L"\u2718" #define UNICODE_OUTLINED_GREEK_CROSS 0x2719 #define UNITEXT_OUTLINED_GREEK_CROSS L"\u2719" #define UNICODE_HEAVY_GREEK_CROSS 0x271a #define UNITEXT_HEAVY_GREEK_CROSS L"\u271a" #define UNICODE_OPEN_CENTRE_CROSS 0x271b #define UNITEXT_OPEN_CENTRE_CROSS L"\u271b" #define UNICODE_HEAVY_OPEN_CENTRE_CROSS 0x271c #define UNITEXT_HEAVY_OPEN_CENTRE_CROSS L"\u271c" #define UNICODE_LATIN_CROSS 0x271d #define UNITEXT_LATIN_CROSS L"\u271d" #define UNICODE_SHADOWED_WHITE_LATIN_CROSS 0x271e #define UNITEXT_SHADOWED_WHITE_LATIN_CROSS L"\u271e" #define UNICODE_OUTLINED_LATIN_CROSS 0x271f #define UNITEXT_OUTLINED_LATIN_CROSS L"\u271f" #define UNICODE_MALTESE_CROSS 0x2720 #define UNITEXT_MALTESE_CROSS L"\u2720" #define UNICODE_STAR_OF_DAVID 0x2721 #define UNITEXT_STAR_OF_DAVID L"\u2721" #define UNICODE_FOUR_TEARDROP_SPOKED_ASTERISK 0x2722 #define UNITEXT_FOUR_TEARDROP_SPOKED_ASTERISK L"\u2722" #define UNICODE_FOUR_BALLOON_SPOKED_ASTERISK 0x2723 #define UNITEXT_FOUR_BALLOON_SPOKED_ASTERISK L"\u2723" #define UNICODE_HEAVY_FOUR_BALLOON_SPOKED_ASTERISK 0x2724 #define UNITEXT_HEAVY_FOUR_BALLOON_SPOKED_ASTERISK L"\u2724" #define UNICODE_FOUR_CLUB_SPOKED_ASTERISK 0x2725 #define UNITEXT_FOUR_CLUB_SPOKED_ASTERISK L"\u2725" #define UNICODE_BLACK_FOUR_POINTED_STAR 0x2726 #define UNITEXT_BLACK_FOUR_POINTED_STAR L"\u2726" #define UNICODE_WHITE_FOUR_POINTED_STAR 0x2727 #define UNITEXT_WHITE_FOUR_POINTED_STAR L"\u2727" #define UNICODE_STRESS_OUTLINED_WHITE_STAR 0x2729 #define UNITEXT_STRESS_OUTLINED_WHITE_STAR L"\u2729" #define UNICODE_CIRCLED_WHITE_STAR 0x272a #define UNITEXT_CIRCLED_WHITE_STAR L"\u272a" #define UNICODE_OPEN_CENTRE_BLACK_STAR 0x272b #define UNITEXT_OPEN_CENTRE_BLACK_STAR L"\u272b" #define UNICODE_BLACK_CENTRE_WHITE_STAR 0x272c #define UNITEXT_BLACK_CENTRE_WHITE_STAR L"\u272c" #define UNICODE_OUTLINED_BLACK_STAR 0x272d #define UNITEXT_OUTLINED_BLACK_STAR L"\u272d" #define UNICODE_HEAVY_OUTLINED_BLACK_STAR 0x272e #define UNITEXT_HEAVY_OUTLINED_BLACK_STAR L"\u272e" #define UNICODE_PINWHEEL_STAR 0x272f #define UNITEXT_PINWHEEL_STAR L"\u272f" #define UNICODE_SHADOWED_WHITE_STAR 0x2730 #define UNITEXT_SHADOWED_WHITE_STAR L"\u2730" #define UNICODE_HEAVY_ASTERISK 0x2731 #define UNITEXT_HEAVY_ASTERISK L"\u2731" #define UNICODE_OPEN_CENTRE_ASTERISK 0x2732 #define UNITEXT_OPEN_CENTRE_ASTERISK L"\u2732" #define UNICODE_EIGHT_SPOKED_ASTERISK 0x2733 #define UNITEXT_EIGHT_SPOKED_ASTERISK L"\u2733" #define UNICODE_EIGHT_POINTED_BLACK_STAR 0x2734 #define UNITEXT_EIGHT_POINTED_BLACK_STAR L"\u2734" #define UNICODE_EIGHT_POINTED_PINWHEEL_STAR 0x2735 #define UNITEXT_EIGHT_POINTED_PINWHEEL_STAR L"\u2735" #define UNICODE_SIX_POINTED_BLACK_STAR 0x2736 #define UNITEXT_SIX_POINTED_BLACK_STAR L"\u2736" #define UNICODE_EIGHT_POINTED_RECTILINEAR_BLACK_STAR 0x2737 #define UNITEXT_EIGHT_POINTED_RECTILINEAR_BLACK_STAR L"\u2737" #define UNICODE_HEAVY_EIGHT_POINTED_RECTILINEAR_BLACK_STAR 0x2738 #define UNITEXT_HEAVY_EIGHT_POINTED_RECTILINEAR_BLACK_STAR L"\u2738" #define UNICODE_TWELVE_POINTED_BLACK_STAR 0x2739 #define UNITEXT_TWELVE_POINTED_BLACK_STAR L"\u2739" #define UNICODE_SIXTEEN_POINTED_ASTERISK 0x273a #define UNITEXT_SIXTEEN_POINTED_ASTERISK L"\u273a" #define UNICODE_TEARDROP_SPOKED_ASTERISK 0x273b #define UNITEXT_TEARDROP_SPOKED_ASTERISK L"\u273b" #define UNICODE_OPEN_CENTRE_TEARDROP_SPOKED_ASTERISK 0x273c #define UNITEXT_OPEN_CENTRE_TEARDROP_SPOKED_ASTERISK L"\u273c" #define UNICODE_HEAVY_TEARDROP_SPOKED_ASTERISK 0x273d #define UNITEXT_HEAVY_TEARDROP_SPOKED_ASTERISK L"\u273d" #define UNICODE_SIX_PETALLED_BLACK_AND_WHITE_FLORETTE 0x273e #define UNITEXT_SIX_PETALLED_BLACK_AND_WHITE_FLORETTE L"\u273e" #define UNICODE_BLACK_FLORETTE 0x273f #define UNITEXT_BLACK_FLORETTE L"\u273f" #define UNICODE_WHITE_FLORETTE 0x2740 #define UNITEXT_WHITE_FLORETTE L"\u2740" #define UNICODE_EIGHT_PETALLED_OUTLINED_BLACK_FLORETTE 0x2741 #define UNITEXT_EIGHT_PETALLED_OUTLINED_BLACK_FLORETTE L"\u2741" #define UNICODE_CIRCLED_OPEN_CENTRE_EIGHT_POINTED_STAR 0x2742 #define UNITEXT_CIRCLED_OPEN_CENTRE_EIGHT_POINTED_STAR L"\u2742" #define UNICODE_HEAVY_TEARDROP_SPOKED_PINWHEEL_ASTERISK 0x2743 #define UNITEXT_HEAVY_TEARDROP_SPOKED_PINWHEEL_ASTERISK L"\u2743" #define UNICODE_SNOWFLAKE 0x2744 #define UNITEXT_SNOWFLAKE L"\u2744" #define UNICODE_TIGHT_TRIFOLIATE_SNOWFLAKE 0x2745 #define UNITEXT_TIGHT_TRIFOLIATE_SNOWFLAKE L"\u2745" #define UNICODE_HEAVY_CHEVRON_SNOWFLAKE 0x2746 #define UNITEXT_HEAVY_CHEVRON_SNOWFLAKE L"\u2746" #define UNICODE_SPARKLE 0x2747 #define UNITEXT_SPARKLE L"\u2747" #define UNICODE_HEAVY_SPARKLE 0x2748 #define UNITEXT_HEAVY_SPARKLE L"\u2748" #define UNICODE_BALLOON_SPOKED_ASTERISK 0x2749 #define UNITEXT_BALLOON_SPOKED_ASTERISK L"\u2749" #define UNICODE_EIGHT_TEARDROP_SPOKED_PROPELLER_ASTERISK 0x274a #define UNITEXT_EIGHT_TEARDROP_SPOKED_PROPELLER_ASTERISK L"\u274a" #define UNICODE_HEAVY_EIGHT_TEARDROP_SPOKED_PROPELLER_ASTERISK 0x274b #define UNITEXT_HEAVY_EIGHT_TEARDROP_SPOKED_PROPELLER_ASTERISK L"\u274b" #define UNICODE_SHADOWED_WHITE_CIRCLE 0x274d #define UNITEXT_SHADOWED_WHITE_CIRCLE L"\u274d" #define UNICODE_LOWER_RIGHT_DROP_SHADOWED_WHITE_SQUARE 0x274f #define UNITEXT_LOWER_RIGHT_DROP_SHADOWED_WHITE_SQUARE L"\u274f" #define UNICODE_UPPER_RIGHT_DROP_SHADOWED_WHITE_SQUARE 0x2750 #define UNITEXT_UPPER_RIGHT_DROP_SHADOWED_WHITE_SQUARE L"\u2750" #define UNICODE_LOWER_RIGHT_SHADOWED_WHITE_SQUARE 0x2751 #define UNITEXT_LOWER_RIGHT_SHADOWED_WHITE_SQUARE L"\u2751" #define UNICODE_UPPER_RIGHT_SHADOWED_WHITE_SQUARE 0x2752 #define UNITEXT_UPPER_RIGHT_SHADOWED_WHITE_SQUARE L"\u2752" #define UNICODE_BLACK_DIAMOND_MINUS_WHITE_X 0x2756 #define UNITEXT_BLACK_DIAMOND_MINUS_WHITE_X L"\u2756" #define UNICODE_LIGHT_VERTICAL_BAR 0x2758 #define UNITEXT_LIGHT_VERTICAL_BAR L"\u2758" #define UNICODE_MEDIUM_VERTICAL_BAR 0x2759 #define UNITEXT_MEDIUM_VERTICAL_BAR L"\u2759" #define UNICODE_HEAVY_VERTICAL_BAR 0x275a #define UNITEXT_HEAVY_VERTICAL_BAR L"\u275a" #define UNICODE_HEAVY_SINGLE_TURNED_COMMA_QUOTATION_MARK_ORNAMENT 0x275b #define UNITEXT_HEAVY_SINGLE_TURNED_COMMA_QUOTATION_MARK_ORNAMENT L"\u275b" #define UNICODE_HEAVY_SINGLE_COMMA_QUOTATION_MARK_ORNAMENT 0x275c #define UNITEXT_HEAVY_SINGLE_COMMA_QUOTATION_MARK_ORNAMENT L"\u275c" #define UNICODE_HEAVY_DOUBLE_TURNED_COMMA_QUOTATION_MARK_ORNAMENT 0x275d #define UNITEXT_HEAVY_DOUBLE_TURNED_COMMA_QUOTATION_MARK_ORNAMENT L"\u275d" #define UNICODE_HEAVY_DOUBLE_COMMA_QUOTATION_MARK_ORNAMENT 0x275e #define UNITEXT_HEAVY_DOUBLE_COMMA_QUOTATION_MARK_ORNAMENT L"\u275e" #define UNICODE_CURVED_STEM_PARAGRAPH_SIGN_ORNAMENT 0x2761 #define UNITEXT_CURVED_STEM_PARAGRAPH_SIGN_ORNAMENT L"\u2761" #define UNICODE_HEAVY_EXCLAMATION_MARK_ORNAMENT 0x2762 #define UNITEXT_HEAVY_EXCLAMATION_MARK_ORNAMENT L"\u2762" #define UNICODE_HEAVY_HEART_EXCLAMATION_MARK_ORNAMENT 0x2763 #define UNITEXT_HEAVY_HEART_EXCLAMATION_MARK_ORNAMENT L"\u2763" #define UNICODE_HEAVY_BLACK_HEART 0x2764 #define UNITEXT_HEAVY_BLACK_HEART L"\u2764" #define UNICODE_ROTATED_HEAVY_BLACK_HEART_BULLET 0x2765 #define UNITEXT_ROTATED_HEAVY_BLACK_HEART_BULLET L"\u2765" #define UNICODE_FLORAL_HEART 0x2766 #define UNITEXT_FLORAL_HEART L"\u2766" #define UNICODE_ROTATED_FLORAL_HEART_BULLET 0x2767 #define UNITEXT_ROTATED_FLORAL_HEART_BULLET L"\u2767" #define UNICODE_MEDIUM_LEFT_PARENTHESIS_ORNAMENT 0x2768 #define UNITEXT_MEDIUM_LEFT_PARENTHESIS_ORNAMENT L"\u2768" #define UNICODE_MEDIUM_RIGHT_PARENTHESIS_ORNAMENT 0x2769 #define UNITEXT_MEDIUM_RIGHT_PARENTHESIS_ORNAMENT L"\u2769" #define UNICODE_MEDIUM_FLATTENED_LEFT_PARENTHESIS_ORNAMENT 0x276a #define UNITEXT_MEDIUM_FLATTENED_LEFT_PARENTHESIS_ORNAMENT L"\u276a" #define UNICODE_MEDIUM_FLATTENED_RIGHT_PARENTHESIS_ORNAMENT 0x276b #define UNITEXT_MEDIUM_FLATTENED_RIGHT_PARENTHESIS_ORNAMENT L"\u276b" #define UNICODE_MEDIUM_LEFT_POINTING_ANGLE_BRACKET_ORNAMENT 0x276c #define UNITEXT_MEDIUM_LEFT_POINTING_ANGLE_BRACKET_ORNAMENT L"\u276c" #define UNICODE_MEDIUM_RIGHT_POINTING_ANGLE_BRACKET_ORNAMENT 0x276d #define UNITEXT_MEDIUM_RIGHT_POINTING_ANGLE_BRACKET_ORNAMENT L"\u276d" #define UNICODE_HEAVY_LEFT_POINTING_ANGLE_QUOTATION_MARK_ORNAMENT 0x276e #define UNITEXT_HEAVY_LEFT_POINTING_ANGLE_QUOTATION_MARK_ORNAMENT L"\u276e" #define UNICODE_HEAVY_RIGHT_POINTING_ANGLE_QUOTATION_MARK_ORNAMENT 0x276f #define UNITEXT_HEAVY_RIGHT_POINTING_ANGLE_QUOTATION_MARK_ORNAMENT L"\u276f" #define UNICODE_HEAVY_LEFT_POINTING_ANGLE_BRACKET_ORNAMENT 0x2770 #define UNITEXT_HEAVY_LEFT_POINTING_ANGLE_BRACKET_ORNAMENT L"\u2770" #define UNICODE_HEAVY_RIGHT_POINTING_ANGLE_BRACKET_ORNAMENT 0x2771 #define UNITEXT_HEAVY_RIGHT_POINTING_ANGLE_BRACKET_ORNAMENT L"\u2771" #define UNICODE_LIGHT_LEFT_TORTOISE_SHELL_BRACKET_ORNAMENT 0x2772 #define UNITEXT_LIGHT_LEFT_TORTOISE_SHELL_BRACKET_ORNAMENT L"\u2772" #define UNICODE_LIGHT_RIGHT_TORTOISE_SHELL_BRACKET_ORNAMENT 0x2773 #define UNITEXT_LIGHT_RIGHT_TORTOISE_SHELL_BRACKET_ORNAMENT L"\u2773" #define UNICODE_MEDIUM_LEFT_CURLY_BRACKET_ORNAMENT 0x2774 #define UNITEXT_MEDIUM_LEFT_CURLY_BRACKET_ORNAMENT L"\u2774" #define UNICODE_MEDIUM_RIGHT_CURLY_BRACKET_ORNAMENT 0x2775 #define UNITEXT_MEDIUM_RIGHT_CURLY_BRACKET_ORNAMENT L"\u2775" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_DIGIT_ONE 0x2776 #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_DIGIT_ONE L"\u2776" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_DIGIT_TWO 0x2777 #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_DIGIT_TWO L"\u2777" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_DIGIT_THREE 0x2778 #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_DIGIT_THREE L"\u2778" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_DIGIT_FOUR 0x2779 #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_DIGIT_FOUR L"\u2779" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_DIGIT_FIVE 0x277a #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_DIGIT_FIVE L"\u277a" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_DIGIT_SIX 0x277b #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_DIGIT_SIX L"\u277b" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_DIGIT_SEVEN 0x277c #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_DIGIT_SEVEN L"\u277c" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_DIGIT_EIGHT 0x277d #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_DIGIT_EIGHT L"\u277d" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_DIGIT_NINE 0x277e #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_DIGIT_NINE L"\u277e" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_NUMBER_TEN 0x277f #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_NUMBER_TEN L"\u277f" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_ONE 0x2780 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_ONE L"\u2780" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_TWO 0x2781 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_TWO L"\u2781" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_THREE 0x2782 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_THREE L"\u2782" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_FOUR 0x2783 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_FOUR L"\u2783" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_FIVE 0x2784 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_FIVE L"\u2784" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_SIX 0x2785 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_SIX L"\u2785" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_SEVEN 0x2786 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_SEVEN L"\u2786" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_EIGHT 0x2787 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_EIGHT L"\u2787" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_NINE 0x2788 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_DIGIT_NINE L"\u2788" #define UNICODE_DINGBAT_CIRCLED_SANS_SERIF_NUMBER_TEN 0x2789 #define UNITEXT_DINGBAT_CIRCLED_SANS_SERIF_NUMBER_TEN L"\u2789" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_ONE 0x278a #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_ONE L"\u278a" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_TWO 0x278b #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_TWO L"\u278b" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_THREE 0x278c #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_THREE L"\u278c" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_FOUR 0x278d #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_FOUR L"\u278d" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_FIVE 0x278e #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_FIVE L"\u278e" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_SIX 0x278f #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_SIX L"\u278f" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_SEVEN 0x2790 #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_SEVEN L"\u2790" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_EIGHT 0x2791 #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_EIGHT L"\u2791" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_NINE 0x2792 #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_DIGIT_NINE L"\u2792" #define UNICODE_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_NUMBER_TEN 0x2793 #define UNITEXT_DINGBAT_NEGATIVE_CIRCLED_SANS_SERIF_NUMBER_TEN L"\u2793" #define UNICODE_HEAVY_WIDE_HEADED_RIGHTWARDS_ARROW 0x2794 #define UNITEXT_HEAVY_WIDE_HEADED_RIGHTWARDS_ARROW L"\u2794" #define UNICODE_HEAVY_SOUTH_EAST_ARROW 0x2798 #define UNITEXT_HEAVY_SOUTH_EAST_ARROW L"\u2798" #define UNICODE_HEAVY_RIGHTWARDS_ARROW 0x2799 #define UNITEXT_HEAVY_RIGHTWARDS_ARROW L"\u2799" #define UNICODE_HEAVY_NORTH_EAST_ARROW 0x279a #define UNITEXT_HEAVY_NORTH_EAST_ARROW L"\u279a" #define UNICODE_DRAFTING_POINT_RIGHTWARDS_ARROW 0x279b #define UNITEXT_DRAFTING_POINT_RIGHTWARDS_ARROW L"\u279b" #define UNICODE_HEAVY_ROUND_TIPPED_RIGHTWARDS_ARROW 0x279c #define UNITEXT_HEAVY_ROUND_TIPPED_RIGHTWARDS_ARROW L"\u279c" #define UNICODE_TRIANGLE_HEADED_RIGHTWARDS_ARROW 0x279d #define UNITEXT_TRIANGLE_HEADED_RIGHTWARDS_ARROW L"\u279d" #define UNICODE_HEAVY_TRIANGLE_HEADED_RIGHTWARDS_ARROW 0x279e #define UNITEXT_HEAVY_TRIANGLE_HEADED_RIGHTWARDS_ARROW L"\u279e" #define UNICODE_DASHED_TRIANGLE_HEADED_RIGHTWARDS_ARROW 0x279f #define UNITEXT_DASHED_TRIANGLE_HEADED_RIGHTWARDS_ARROW L"\u279f" #define UNICODE_HEAVY_DASHED_TRIANGLE_HEADED_RIGHTWARDS_ARROW 0x27a0 #define UNITEXT_HEAVY_DASHED_TRIANGLE_HEADED_RIGHTWARDS_ARROW L"\u27a0" #define UNICODE_BLACK_RIGHTWARDS_ARROW 0x27a1 #define UNITEXT_BLACK_RIGHTWARDS_ARROW L"\u27a1" #define UNICODE_THREE_D_TOP_LIGHTED_RIGHTWARDS_ARROWHEAD 0x27a2 #define UNITEXT_THREE_D_TOP_LIGHTED_RIGHTWARDS_ARROWHEAD L"\u27a2" #define UNICODE_THREE_D_BOTTOM_LIGHTED_RIGHTWARDS_ARROWHEAD 0x27a3 #define UNITEXT_THREE_D_BOTTOM_LIGHTED_RIGHTWARDS_ARROWHEAD L"\u27a3" #define UNICODE_BLACK_RIGHTWARDS_ARROWHEAD 0x27a4 #define UNITEXT_BLACK_RIGHTWARDS_ARROWHEAD L"\u27a4" #define UNICODE_HEAVY_BLACK_CURVED_DOWNWARDS_AND_RIGHTWARDS_ARROW 0x27a5 #define UNITEXT_HEAVY_BLACK_CURVED_DOWNWARDS_AND_RIGHTWARDS_ARROW L"\u27a5" #define UNICODE_HEAVY_BLACK_CURVED_UPWARDS_AND_RIGHTWARDS_ARROW 0x27a6 #define UNITEXT_HEAVY_BLACK_CURVED_UPWARDS_AND_RIGHTWARDS_ARROW L"\u27a6" #define UNICODE_SQUAT_BLACK_RIGHTWARDS_ARROW 0x27a7 #define UNITEXT_SQUAT_BLACK_RIGHTWARDS_ARROW L"\u27a7" #define UNICODE_HEAVY_CONCAVE_POINTED_BLACK_RIGHTWARDS_ARROW 0x27a8 #define UNITEXT_HEAVY_CONCAVE_POINTED_BLACK_RIGHTWARDS_ARROW L"\u27a8" #define UNICODE_RIGHT_SHADED_WHITE_RIGHTWARDS_ARROW 0x27a9 #define UNITEXT_RIGHT_SHADED_WHITE_RIGHTWARDS_ARROW L"\u27a9" #define UNICODE_LEFT_SHADED_WHITE_RIGHTWARDS_ARROW 0x27aa #define UNITEXT_LEFT_SHADED_WHITE_RIGHTWARDS_ARROW L"\u27aa" #define UNICODE_BACK_TILTED_SHADOWED_WHITE_RIGHTWARDS_ARROW 0x27ab #define UNITEXT_BACK_TILTED_SHADOWED_WHITE_RIGHTWARDS_ARROW L"\u27ab" #define UNICODE_FRONT_TILTED_SHADOWED_WHITE_RIGHTWARDS_ARROW 0x27ac #define UNITEXT_FRONT_TILTED_SHADOWED_WHITE_RIGHTWARDS_ARROW L"\u27ac" #define UNICODE_HEAVY_LOWER_RIGHT_SHADOWED_WHITE_RIGHTWARDS_ARROW 0x27ad #define UNITEXT_HEAVY_LOWER_RIGHT_SHADOWED_WHITE_RIGHTWARDS_ARROW L"\u27ad" #define UNICODE_HEAVY_UPPER_RIGHT_SHADOWED_WHITE_RIGHTWARDS_ARROW 0x27ae #define UNITEXT_HEAVY_UPPER_RIGHT_SHADOWED_WHITE_RIGHTWARDS_ARROW L"\u27ae" #define UNICODE_NOTCHED_LOWER_RIGHT_SHADOWED_WHITE_RIGHTWARDS_ARROW 0x27af #define UNITEXT_NOTCHED_LOWER_RIGHT_SHADOWED_WHITE_RIGHTWARDS_ARROW L"\u27af" #define UNICODE_NOTCHED_UPPER_RIGHT_SHADOWED_WHITE_RIGHTWARDS_ARROW 0x27b1 #define UNITEXT_NOTCHED_UPPER_RIGHT_SHADOWED_WHITE_RIGHTWARDS_ARROW L"\u27b1" #define UNICODE_CIRCLED_HEAVY_WHITE_RIGHTWARDS_ARROW 0x27b2 #define UNITEXT_CIRCLED_HEAVY_WHITE_RIGHTWARDS_ARROW L"\u27b2" #define UNICODE_WHITE_FEATHERED_RIGHTWARDS_ARROW 0x27b3 #define UNITEXT_WHITE_FEATHERED_RIGHTWARDS_ARROW L"\u27b3" #define UNICODE_BLACK_FEATHERED_SOUTH_EAST_ARROW 0x27b4 #define UNITEXT_BLACK_FEATHERED_SOUTH_EAST_ARROW L"\u27b4" #define UNICODE_BLACK_FEATHERED_RIGHTWARDS_ARROW 0x27b5 #define UNITEXT_BLACK_FEATHERED_RIGHTWARDS_ARROW L"\u27b5" #define UNICODE_BLACK_FEATHERED_NORTH_EAST_ARROW 0x27b6 #define UNITEXT_BLACK_FEATHERED_NORTH_EAST_ARROW L"\u27b6" #define UNICODE_HEAVY_BLACK_FEATHERED_SOUTH_EAST_ARROW 0x27b7 #define UNITEXT_HEAVY_BLACK_FEATHERED_SOUTH_EAST_ARROW L"\u27b7" #define UNICODE_HEAVY_BLACK_FEATHERED_RIGHTWARDS_ARROW 0x27b8 #define UNITEXT_HEAVY_BLACK_FEATHERED_RIGHTWARDS_ARROW L"\u27b8" #define UNICODE_HEAVY_BLACK_FEATHERED_NORTH_EAST_ARROW 0x27b9 #define UNITEXT_HEAVY_BLACK_FEATHERED_NORTH_EAST_ARROW L"\u27b9" #define UNICODE_TEARDROP_BARBED_RIGHTWARDS_ARROW 0x27ba #define UNITEXT_TEARDROP_BARBED_RIGHTWARDS_ARROW L"\u27ba" #define UNICODE_HEAVY_TEARDROP_SHANKED_RIGHTWARDS_ARROW 0x27bb #define UNITEXT_HEAVY_TEARDROP_SHANKED_RIGHTWARDS_ARROW L"\u27bb" #define UNICODE_WEDGE_TAILED_RIGHTWARDS_ARROW 0x27bc #define UNITEXT_WEDGE_TAILED_RIGHTWARDS_ARROW L"\u27bc" #define UNICODE_HEAVY_WEDGE_TAILED_RIGHTWARDS_ARROW 0x27bd #define UNITEXT_HEAVY_WEDGE_TAILED_RIGHTWARDS_ARROW L"\u27bd" #define UNICODE_OPEN_OUTLINED_RIGHTWARDS_ARROW 0x27be #define UNITEXT_OPEN_OUTLINED_RIGHTWARDS_ARROW L"\u27be" #define UNICODE_THREE_DIMENSIONAL_ANGLE 0x27c0 #define UNITEXT_THREE_DIMENSIONAL_ANGLE L"\u27c0" #define UNICODE_WHITE_TRIANGLE_CONTAINING_SMALL_WHITE_TRIANGLE 0x27c1 #define UNITEXT_WHITE_TRIANGLE_CONTAINING_SMALL_WHITE_TRIANGLE L"\u27c1" #define UNICODE_PERPENDICULAR 0x27c2 #define UNITEXT_PERPENDICULAR L"\u27c2" #define UNICODE_OPEN_SUBSET 0x27c3 #define UNITEXT_OPEN_SUBSET L"\u27c3" #define UNICODE_OPEN_SUPERSET 0x27c4 #define UNITEXT_OPEN_SUPERSET L"\u27c4" #define UNICODE_LEFT_S_SHAPED_BAG_DELIMITER 0x27c5 #define UNITEXT_LEFT_S_SHAPED_BAG_DELIMITER L"\u27c5" #define UNICODE_RIGHT_S_SHAPED_BAG_DELIMITER 0x27c6 #define UNITEXT_RIGHT_S_SHAPED_BAG_DELIMITER L"\u27c6" #define UNICODE_OR_WITH_DOT_INSIDE 0x27c7 #define UNITEXT_OR_WITH_DOT_INSIDE L"\u27c7" #define UNICODE_REVERSE_SOLIDUS_PRECEDING_SUBSET 0x27c8 #define UNITEXT_REVERSE_SOLIDUS_PRECEDING_SUBSET L"\u27c8" #define UNICODE_SUPERSET_PRECEDING_SOLIDUS 0x27c9 #define UNITEXT_SUPERSET_PRECEDING_SOLIDUS L"\u27c9" #define UNICODE_VERTICAL_BAR_WITH_HORIZONTAL_STROKE 0x27ca #define UNITEXT_VERTICAL_BAR_WITH_HORIZONTAL_STROKE L"\u27ca" #define UNICODE_WHITE_DIAMOND_WITH_CENTRED_DOT 0x27d0 #define UNITEXT_WHITE_DIAMOND_WITH_CENTRED_DOT L"\u27d0" #define UNICODE_AND_WITH_DOT 0x27d1 #define UNITEXT_AND_WITH_DOT L"\u27d1" #define UNICODE_ELEMENT_OF_OPENING_UPWARDS 0x27d2 #define UNITEXT_ELEMENT_OF_OPENING_UPWARDS L"\u27d2" #define UNICODE_LOWER_RIGHT_CORNER_WITH_DOT 0x27d3 #define UNITEXT_LOWER_RIGHT_CORNER_WITH_DOT L"\u27d3" #define UNICODE_UPPER_LEFT_CORNER_WITH_DOT 0x27d4 #define UNITEXT_UPPER_LEFT_CORNER_WITH_DOT L"\u27d4" #define UNICODE_LEFT_OUTER_JOIN 0x27d5 #define UNITEXT_LEFT_OUTER_JOIN L"\u27d5" #define UNICODE_RIGHT_OUTER_JOIN 0x27d6 #define UNITEXT_RIGHT_OUTER_JOIN L"\u27d6" #define UNICODE_FULL_OUTER_JOIN 0x27d7 #define UNITEXT_FULL_OUTER_JOIN L"\u27d7" #define UNICODE_LARGE_UP_TACK 0x27d8 #define UNITEXT_LARGE_UP_TACK L"\u27d8" #define UNICODE_LARGE_DOWN_TACK 0x27d9 #define UNITEXT_LARGE_DOWN_TACK L"\u27d9" #define UNICODE_LEFT_AND_RIGHT_DOUBLE_TURNSTILE 0x27da #define UNITEXT_LEFT_AND_RIGHT_DOUBLE_TURNSTILE L"\u27da" #define UNICODE_LEFT_AND_RIGHT_TACK 0x27db #define UNITEXT_LEFT_AND_RIGHT_TACK L"\u27db" #define UNICODE_LEFT_MULTIMAP 0x27dc #define UNITEXT_LEFT_MULTIMAP L"\u27dc" #define UNICODE_LONG_RIGHT_TACK 0x27dd #define UNITEXT_LONG_RIGHT_TACK L"\u27dd" #define UNICODE_LONG_LEFT_TACK 0x27de #define UNITEXT_LONG_LEFT_TACK L"\u27de" #define UNICODE_UP_TACK_WITH_CIRCLE_ABOVE 0x27df #define UNITEXT_UP_TACK_WITH_CIRCLE_ABOVE L"\u27df" #define UNICODE_LOZENGE_DIVIDED_BY_HORIZONTAL_RULE 0x27e0 #define UNITEXT_LOZENGE_DIVIDED_BY_HORIZONTAL_RULE L"\u27e0" #define UNICODE_WHITE_CONCAVE_SIDED_DIAMOND 0x27e1 #define UNITEXT_WHITE_CONCAVE_SIDED_DIAMOND L"\u27e1" #define UNICODE_WHITE_CONCAVE_SIDED_DIAMOND_WITH_LEFTWARDS_TICK 0x27e2 #define UNITEXT_WHITE_CONCAVE_SIDED_DIAMOND_WITH_LEFTWARDS_TICK L"\u27e2" #define UNICODE_WHITE_CONCAVE_SIDED_DIAMOND_WITH_RIGHTWARDS_TICK 0x27e3 #define UNITEXT_WHITE_CONCAVE_SIDED_DIAMOND_WITH_RIGHTWARDS_TICK L"\u27e3" #define UNICODE_WHITE_SQUARE_WITH_LEFTWARDS_TICK 0x27e4 #define UNITEXT_WHITE_SQUARE_WITH_LEFTWARDS_TICK L"\u27e4" #define UNICODE_WHITE_SQUARE_WITH_RIGHTWARDS_TICK 0x27e5 #define UNITEXT_WHITE_SQUARE_WITH_RIGHTWARDS_TICK L"\u27e5" #define UNICODE_MATHEMATICAL_LEFT_WHITE_SQUARE_BRACKET 0x27e6 #define UNITEXT_MATHEMATICAL_LEFT_WHITE_SQUARE_BRACKET L"\u27e6" #define UNICODE_MATHEMATICAL_RIGHT_WHITE_SQUARE_BRACKET 0x27e7 #define UNITEXT_MATHEMATICAL_RIGHT_WHITE_SQUARE_BRACKET L"\u27e7" #define UNICODE_MATHEMATICAL_LEFT_ANGLE_BRACKET 0x27e8 #define UNITEXT_MATHEMATICAL_LEFT_ANGLE_BRACKET L"\u27e8" #define UNICODE_MATHEMATICAL_RIGHT_ANGLE_BRACKET 0x27e9 #define UNITEXT_MATHEMATICAL_RIGHT_ANGLE_BRACKET L"\u27e9" #define UNICODE_MATHEMATICAL_LEFT_DOUBLE_ANGLE_BRACKET 0x27ea #define UNITEXT_MATHEMATICAL_LEFT_DOUBLE_ANGLE_BRACKET L"\u27ea" #define UNICODE_MATHEMATICAL_RIGHT_DOUBLE_ANGLE_BRACKET 0x27eb #define UNITEXT_MATHEMATICAL_RIGHT_DOUBLE_ANGLE_BRACKET L"\u27eb" #define UNICODE_UPWARDS_QUADRUPLE_ARROW 0x27f0 #define UNITEXT_UPWARDS_QUADRUPLE_ARROW L"\u27f0" #define UNICODE_DOWNWARDS_QUADRUPLE_ARROW 0x27f1 #define UNITEXT_DOWNWARDS_QUADRUPLE_ARROW L"\u27f1" #define UNICODE_ANTICLOCKWISE_GAPPED_CIRCLE_ARROW 0x27f2 #define UNITEXT_ANTICLOCKWISE_GAPPED_CIRCLE_ARROW L"\u27f2" #define UNICODE_CLOCKWISE_GAPPED_CIRCLE_ARROW 0x27f3 #define UNITEXT_CLOCKWISE_GAPPED_CIRCLE_ARROW L"\u27f3" #define UNICODE_RIGHT_ARROW_WITH_CIRCLED_PLUS 0x27f4 #define UNITEXT_RIGHT_ARROW_WITH_CIRCLED_PLUS L"\u27f4" #define UNICODE_LONG_LEFTWARDS_ARROW 0x27f5 #define UNITEXT_LONG_LEFTWARDS_ARROW L"\u27f5" #define UNICODE_LONG_RIGHTWARDS_ARROW 0x27f6 #define UNITEXT_LONG_RIGHTWARDS_ARROW L"\u27f6" #define UNICODE_LONG_LEFT_RIGHT_ARROW 0x27f7 #define UNITEXT_LONG_LEFT_RIGHT_ARROW L"\u27f7" #define UNICODE_LONG_LEFTWARDS_DOUBLE_ARROW 0x27f8 #define UNITEXT_LONG_LEFTWARDS_DOUBLE_ARROW L"\u27f8" #define UNICODE_LONG_RIGHTWARDS_DOUBLE_ARROW 0x27f9 #define UNITEXT_LONG_RIGHTWARDS_DOUBLE_ARROW L"\u27f9" #define UNICODE_LONG_LEFT_RIGHT_DOUBLE_ARROW 0x27fa #define UNITEXT_LONG_LEFT_RIGHT_DOUBLE_ARROW L"\u27fa" #define UNICODE_LONG_LEFTWARDS_ARROW_FROM_BAR 0x27fb #define UNITEXT_LONG_LEFTWARDS_ARROW_FROM_BAR L"\u27fb" #define UNICODE_LONG_RIGHTWARDS_ARROW_FROM_BAR 0x27fc #define UNITEXT_LONG_RIGHTWARDS_ARROW_FROM_BAR L"\u27fc" #define UNICODE_LONG_LEFTWARDS_DOUBLE_ARROW_FROM_BAR 0x27fd #define UNITEXT_LONG_LEFTWARDS_DOUBLE_ARROW_FROM_BAR L"\u27fd" #define UNICODE_LONG_RIGHTWARDS_DOUBLE_ARROW_FROM_BAR 0x27fe #define UNITEXT_LONG_RIGHTWARDS_DOUBLE_ARROW_FROM_BAR L"\u27fe" #define UNICODE_LONG_RIGHTWARDS_SQUIGGLE_ARROW 0x27ff #define UNITEXT_LONG_RIGHTWARDS_SQUIGGLE_ARROW L"\u27ff" #define UNICODE_BRAILLE_PATTERN_BLANK 0x2800 #define UNITEXT_BRAILLE_PATTERN_BLANK L"\u2800" #define UNICODE_BRAILLE_PATTERN_DOTS_1 0x2801 #define UNITEXT_BRAILLE_PATTERN_DOTS_1 L"\u2801" #define UNICODE_BRAILLE_PATTERN_DOTS_2 0x2802 #define UNITEXT_BRAILLE_PATTERN_DOTS_2 L"\u2802" #define UNICODE_BRAILLE_PATTERN_DOTS_12 0x2803 #define UNITEXT_BRAILLE_PATTERN_DOTS_12 L"\u2803" #define UNICODE_BRAILLE_PATTERN_DOTS_3 0x2804 #define UNITEXT_BRAILLE_PATTERN_DOTS_3 L"\u2804" #define UNICODE_BRAILLE_PATTERN_DOTS_13 0x2805 #define UNITEXT_BRAILLE_PATTERN_DOTS_13 L"\u2805" #define UNICODE_BRAILLE_PATTERN_DOTS_23 0x2806 #define UNITEXT_BRAILLE_PATTERN_DOTS_23 L"\u2806" #define UNICODE_BRAILLE_PATTERN_DOTS_123 0x2807 #define UNITEXT_BRAILLE_PATTERN_DOTS_123 L"\u2807" #define UNICODE_BRAILLE_PATTERN_DOTS_4 0x2808 #define UNITEXT_BRAILLE_PATTERN_DOTS_4 L"\u2808" #define UNICODE_BRAILLE_PATTERN_DOTS_14 0x2809 #define UNITEXT_BRAILLE_PATTERN_DOTS_14 L"\u2809" #define UNICODE_BRAILLE_PATTERN_DOTS_24 0x280a #define UNITEXT_BRAILLE_PATTERN_DOTS_24 L"\u280a" #define UNICODE_BRAILLE_PATTERN_DOTS_124 0x280b #define UNITEXT_BRAILLE_PATTERN_DOTS_124 L"\u280b" #define UNICODE_BRAILLE_PATTERN_DOTS_34 0x280c #define UNITEXT_BRAILLE_PATTERN_DOTS_34 L"\u280c" #define UNICODE_BRAILLE_PATTERN_DOTS_134 0x280d #define UNITEXT_BRAILLE_PATTERN_DOTS_134 L"\u280d" #define UNICODE_BRAILLE_PATTERN_DOTS_234 0x280e #define UNITEXT_BRAILLE_PATTERN_DOTS_234 L"\u280e" #define UNICODE_BRAILLE_PATTERN_DOTS_1234 0x280f #define UNITEXT_BRAILLE_PATTERN_DOTS_1234 L"\u280f" #define UNICODE_BRAILLE_PATTERN_DOTS_5 0x2810 #define UNITEXT_BRAILLE_PATTERN_DOTS_5 L"\u2810" #define UNICODE_BRAILLE_PATTERN_DOTS_15 0x2811 #define UNITEXT_BRAILLE_PATTERN_DOTS_15 L"\u2811" #define UNICODE_BRAILLE_PATTERN_DOTS_25 0x2812 #define UNITEXT_BRAILLE_PATTERN_DOTS_25 L"\u2812" #define UNICODE_BRAILLE_PATTERN_DOTS_125 0x2813 #define UNITEXT_BRAILLE_PATTERN_DOTS_125 L"\u2813" #define UNICODE_BRAILLE_PATTERN_DOTS_35 0x2814 #define UNITEXT_BRAILLE_PATTERN_DOTS_35 L"\u2814" #define UNICODE_BRAILLE_PATTERN_DOTS_135 0x2815 #define UNITEXT_BRAILLE_PATTERN_DOTS_135 L"\u2815" #define UNICODE_BRAILLE_PATTERN_DOTS_235 0x2816 #define UNITEXT_BRAILLE_PATTERN_DOTS_235 L"\u2816" #define UNICODE_BRAILLE_PATTERN_DOTS_1235 0x2817 #define UNITEXT_BRAILLE_PATTERN_DOTS_1235 L"\u2817" #define UNICODE_BRAILLE_PATTERN_DOTS_45 0x2818 #define UNITEXT_BRAILLE_PATTERN_DOTS_45 L"\u2818" #define UNICODE_BRAILLE_PATTERN_DOTS_145 0x2819 #define UNITEXT_BRAILLE_PATTERN_DOTS_145 L"\u2819" #define UNICODE_BRAILLE_PATTERN_DOTS_245 0x281a #define UNITEXT_BRAILLE_PATTERN_DOTS_245 L"\u281a" #define UNICODE_BRAILLE_PATTERN_DOTS_1245 0x281b #define UNITEXT_BRAILLE_PATTERN_DOTS_1245 L"\u281b" #define UNICODE_BRAILLE_PATTERN_DOTS_345 0x281c #define UNITEXT_BRAILLE_PATTERN_DOTS_345 L"\u281c" #define UNICODE_BRAILLE_PATTERN_DOTS_1345 0x281d #define UNITEXT_BRAILLE_PATTERN_DOTS_1345 L"\u281d" #define UNICODE_BRAILLE_PATTERN_DOTS_2345 0x281e #define UNITEXT_BRAILLE_PATTERN_DOTS_2345 L"\u281e" #define UNICODE_BRAILLE_PATTERN_DOTS_12345 0x281f #define UNITEXT_BRAILLE_PATTERN_DOTS_12345 L"\u281f" #define UNICODE_BRAILLE_PATTERN_DOTS_6 0x2820 #define UNITEXT_BRAILLE_PATTERN_DOTS_6 L"\u2820" #define UNICODE_BRAILLE_PATTERN_DOTS_16 0x2821 #define UNITEXT_BRAILLE_PATTERN_DOTS_16 L"\u2821" #define UNICODE_BRAILLE_PATTERN_DOTS_26 0x2822 #define UNITEXT_BRAILLE_PATTERN_DOTS_26 L"\u2822" #define UNICODE_BRAILLE_PATTERN_DOTS_126 0x2823 #define UNITEXT_BRAILLE_PATTERN_DOTS_126 L"\u2823" #define UNICODE_BRAILLE_PATTERN_DOTS_36 0x2824 #define UNITEXT_BRAILLE_PATTERN_DOTS_36 L"\u2824" #define UNICODE_BRAILLE_PATTERN_DOTS_136 0x2825 #define UNITEXT_BRAILLE_PATTERN_DOTS_136 L"\u2825" #define UNICODE_BRAILLE_PATTERN_DOTS_236 0x2826 #define UNITEXT_BRAILLE_PATTERN_DOTS_236 L"\u2826" #define UNICODE_BRAILLE_PATTERN_DOTS_1236 0x2827 #define UNITEXT_BRAILLE_PATTERN_DOTS_1236 L"\u2827" #define UNICODE_BRAILLE_PATTERN_DOTS_46 0x2828 #define UNITEXT_BRAILLE_PATTERN_DOTS_46 L"\u2828" #define UNICODE_BRAILLE_PATTERN_DOTS_146 0x2829 #define UNITEXT_BRAILLE_PATTERN_DOTS_146 L"\u2829" #define UNICODE_BRAILLE_PATTERN_DOTS_246 0x282a #define UNITEXT_BRAILLE_PATTERN_DOTS_246 L"\u282a" #define UNICODE_BRAILLE_PATTERN_DOTS_1246 0x282b #define UNITEXT_BRAILLE_PATTERN_DOTS_1246 L"\u282b" #define UNICODE_BRAILLE_PATTERN_DOTS_346 0x282c #define UNITEXT_BRAILLE_PATTERN_DOTS_346 L"\u282c" #define UNICODE_BRAILLE_PATTERN_DOTS_1346 0x282d #define UNITEXT_BRAILLE_PATTERN_DOTS_1346 L"\u282d" #define UNICODE_BRAILLE_PATTERN_DOTS_2346 0x282e #define UNITEXT_BRAILLE_PATTERN_DOTS_2346 L"\u282e" #define UNICODE_BRAILLE_PATTERN_DOTS_12346 0x282f #define UNITEXT_BRAILLE_PATTERN_DOTS_12346 L"\u282f" #define UNICODE_BRAILLE_PATTERN_DOTS_56 0x2830 #define UNITEXT_BRAILLE_PATTERN_DOTS_56 L"\u2830" #define UNICODE_BRAILLE_PATTERN_DOTS_156 0x2831 #define UNITEXT_BRAILLE_PATTERN_DOTS_156 L"\u2831" #define UNICODE_BRAILLE_PATTERN_DOTS_256 0x2832 #define UNITEXT_BRAILLE_PATTERN_DOTS_256 L"\u2832" #define UNICODE_BRAILLE_PATTERN_DOTS_1256 0x2833 #define UNITEXT_BRAILLE_PATTERN_DOTS_1256 L"\u2833" #define UNICODE_BRAILLE_PATTERN_DOTS_356 0x2834 #define UNITEXT_BRAILLE_PATTERN_DOTS_356 L"\u2834" #define UNICODE_BRAILLE_PATTERN_DOTS_1356 0x2835 #define UNITEXT_BRAILLE_PATTERN_DOTS_1356 L"\u2835" #define UNICODE_BRAILLE_PATTERN_DOTS_2356 0x2836 #define UNITEXT_BRAILLE_PATTERN_DOTS_2356 L"\u2836" #define UNICODE_BRAILLE_PATTERN_DOTS_12356 0x2837 #define UNITEXT_BRAILLE_PATTERN_DOTS_12356 L"\u2837" #define UNICODE_BRAILLE_PATTERN_DOTS_456 0x2838 #define UNITEXT_BRAILLE_PATTERN_DOTS_456 L"\u2838" #define UNICODE_BRAILLE_PATTERN_DOTS_1456 0x2839 #define UNITEXT_BRAILLE_PATTERN_DOTS_1456 L"\u2839" #define UNICODE_BRAILLE_PATTERN_DOTS_2456 0x283a #define UNITEXT_BRAILLE_PATTERN_DOTS_2456 L"\u283a" #define UNICODE_BRAILLE_PATTERN_DOTS_12456 0x283b #define UNITEXT_BRAILLE_PATTERN_DOTS_12456 L"\u283b" #define UNICODE_BRAILLE_PATTERN_DOTS_3456 0x283c #define UNITEXT_BRAILLE_PATTERN_DOTS_3456 L"\u283c" #define UNICODE_BRAILLE_PATTERN_DOTS_13456 0x283d #define UNITEXT_BRAILLE_PATTERN_DOTS_13456 L"\u283d" #define UNICODE_BRAILLE_PATTERN_DOTS_23456 0x283e #define UNITEXT_BRAILLE_PATTERN_DOTS_23456 L"\u283e" #define UNICODE_BRAILLE_PATTERN_DOTS_123456 0x283f #define UNITEXT_BRAILLE_PATTERN_DOTS_123456 L"\u283f" #define UNICODE_BRAILLE_PATTERN_DOTS_7 0x2840 #define UNITEXT_BRAILLE_PATTERN_DOTS_7 L"\u2840" #define UNICODE_BRAILLE_PATTERN_DOTS_17 0x2841 #define UNITEXT_BRAILLE_PATTERN_DOTS_17 L"\u2841" #define UNICODE_BRAILLE_PATTERN_DOTS_27 0x2842 #define UNITEXT_BRAILLE_PATTERN_DOTS_27 L"\u2842" #define UNICODE_BRAILLE_PATTERN_DOTS_127 0x2843 #define UNITEXT_BRAILLE_PATTERN_DOTS_127 L"\u2843" #define UNICODE_BRAILLE_PATTERN_DOTS_37 0x2844 #define UNITEXT_BRAILLE_PATTERN_DOTS_37 L"\u2844" #define UNICODE_BRAILLE_PATTERN_DOTS_137 0x2845 #define UNITEXT_BRAILLE_PATTERN_DOTS_137 L"\u2845" #define UNICODE_BRAILLE_PATTERN_DOTS_237 0x2846 #define UNITEXT_BRAILLE_PATTERN_DOTS_237 L"\u2846" #define UNICODE_BRAILLE_PATTERN_DOTS_1237 0x2847 #define UNITEXT_BRAILLE_PATTERN_DOTS_1237 L"\u2847" #define UNICODE_BRAILLE_PATTERN_DOTS_47 0x2848 #define UNITEXT_BRAILLE_PATTERN_DOTS_47 L"\u2848" #define UNICODE_BRAILLE_PATTERN_DOTS_147 0x2849 #define UNITEXT_BRAILLE_PATTERN_DOTS_147 L"\u2849" #define UNICODE_BRAILLE_PATTERN_DOTS_247 0x284a #define UNITEXT_BRAILLE_PATTERN_DOTS_247 L"\u284a" #define UNICODE_BRAILLE_PATTERN_DOTS_1247 0x284b #define UNITEXT_BRAILLE_PATTERN_DOTS_1247 L"\u284b" #define UNICODE_BRAILLE_PATTERN_DOTS_347 0x284c #define UNITEXT_BRAILLE_PATTERN_DOTS_347 L"\u284c" #define UNICODE_BRAILLE_PATTERN_DOTS_1347 0x284d #define UNITEXT_BRAILLE_PATTERN_DOTS_1347 L"\u284d" #define UNICODE_BRAILLE_PATTERN_DOTS_2347 0x284e #define UNITEXT_BRAILLE_PATTERN_DOTS_2347 L"\u284e" #define UNICODE_BRAILLE_PATTERN_DOTS_12347 0x284f #define UNITEXT_BRAILLE_PATTERN_DOTS_12347 L"\u284f" #define UNICODE_BRAILLE_PATTERN_DOTS_57 0x2850 #define UNITEXT_BRAILLE_PATTERN_DOTS_57 L"\u2850" #define UNICODE_BRAILLE_PATTERN_DOTS_157 0x2851 #define UNITEXT_BRAILLE_PATTERN_DOTS_157 L"\u2851" #define UNICODE_BRAILLE_PATTERN_DOTS_257 0x2852 #define UNITEXT_BRAILLE_PATTERN_DOTS_257 L"\u2852" #define UNICODE_BRAILLE_PATTERN_DOTS_1257 0x2853 #define UNITEXT_BRAILLE_PATTERN_DOTS_1257 L"\u2853" #define UNICODE_BRAILLE_PATTERN_DOTS_357 0x2854 #define UNITEXT_BRAILLE_PATTERN_DOTS_357 L"\u2854" #define UNICODE_BRAILLE_PATTERN_DOTS_1357 0x2855 #define UNITEXT_BRAILLE_PATTERN_DOTS_1357 L"\u2855" #define UNICODE_BRAILLE_PATTERN_DOTS_2357 0x2856 #define UNITEXT_BRAILLE_PATTERN_DOTS_2357 L"\u2856" #define UNICODE_BRAILLE_PATTERN_DOTS_12357 0x2857 #define UNITEXT_BRAILLE_PATTERN_DOTS_12357 L"\u2857" #define UNICODE_BRAILLE_PATTERN_DOTS_457 0x2858 #define UNITEXT_BRAILLE_PATTERN_DOTS_457 L"\u2858" #define UNICODE_BRAILLE_PATTERN_DOTS_1457 0x2859 #define UNITEXT_BRAILLE_PATTERN_DOTS_1457 L"\u2859" #define UNICODE_BRAILLE_PATTERN_DOTS_2457 0x285a #define UNITEXT_BRAILLE_PATTERN_DOTS_2457 L"\u285a" #define UNICODE_BRAILLE_PATTERN_DOTS_12457 0x285b #define UNITEXT_BRAILLE_PATTERN_DOTS_12457 L"\u285b" #define UNICODE_BRAILLE_PATTERN_DOTS_3457 0x285c #define UNITEXT_BRAILLE_PATTERN_DOTS_3457 L"\u285c" #define UNICODE_BRAILLE_PATTERN_DOTS_13457 0x285d #define UNITEXT_BRAILLE_PATTERN_DOTS_13457 L"\u285d" #define UNICODE_BRAILLE_PATTERN_DOTS_23457 0x285e #define UNITEXT_BRAILLE_PATTERN_DOTS_23457 L"\u285e" #define UNICODE_BRAILLE_PATTERN_DOTS_123457 0x285f #define UNITEXT_BRAILLE_PATTERN_DOTS_123457 L"\u285f" #define UNICODE_BRAILLE_PATTERN_DOTS_67 0x2860 #define UNITEXT_BRAILLE_PATTERN_DOTS_67 L"\u2860" #define UNICODE_BRAILLE_PATTERN_DOTS_167 0x2861 #define UNITEXT_BRAILLE_PATTERN_DOTS_167 L"\u2861" #define UNICODE_BRAILLE_PATTERN_DOTS_267 0x2862 #define UNITEXT_BRAILLE_PATTERN_DOTS_267 L"\u2862" #define UNICODE_BRAILLE_PATTERN_DOTS_1267 0x2863 #define UNITEXT_BRAILLE_PATTERN_DOTS_1267 L"\u2863" #define UNICODE_BRAILLE_PATTERN_DOTS_367 0x2864 #define UNITEXT_BRAILLE_PATTERN_DOTS_367 L"\u2864" #define UNICODE_BRAILLE_PATTERN_DOTS_1367 0x2865 #define UNITEXT_BRAILLE_PATTERN_DOTS_1367 L"\u2865" #define UNICODE_BRAILLE_PATTERN_DOTS_2367 0x2866 #define UNITEXT_BRAILLE_PATTERN_DOTS_2367 L"\u2866" #define UNICODE_BRAILLE_PATTERN_DOTS_12367 0x2867 #define UNITEXT_BRAILLE_PATTERN_DOTS_12367 L"\u2867" #define UNICODE_BRAILLE_PATTERN_DOTS_467 0x2868 #define UNITEXT_BRAILLE_PATTERN_DOTS_467 L"\u2868" #define UNICODE_BRAILLE_PATTERN_DOTS_1467 0x2869 #define UNITEXT_BRAILLE_PATTERN_DOTS_1467 L"\u2869" #define UNICODE_BRAILLE_PATTERN_DOTS_2467 0x286a #define UNITEXT_BRAILLE_PATTERN_DOTS_2467 L"\u286a" #define UNICODE_BRAILLE_PATTERN_DOTS_12467 0x286b #define UNITEXT_BRAILLE_PATTERN_DOTS_12467 L"\u286b" #define UNICODE_BRAILLE_PATTERN_DOTS_3467 0x286c #define UNITEXT_BRAILLE_PATTERN_DOTS_3467 L"\u286c" #define UNICODE_BRAILLE_PATTERN_DOTS_13467 0x286d #define UNITEXT_BRAILLE_PATTERN_DOTS_13467 L"\u286d" #define UNICODE_BRAILLE_PATTERN_DOTS_23467 0x286e #define UNITEXT_BRAILLE_PATTERN_DOTS_23467 L"\u286e" #define UNICODE_BRAILLE_PATTERN_DOTS_123467 0x286f #define UNITEXT_BRAILLE_PATTERN_DOTS_123467 L"\u286f" #define UNICODE_BRAILLE_PATTERN_DOTS_567 0x2870 #define UNITEXT_BRAILLE_PATTERN_DOTS_567 L"\u2870" #define UNICODE_BRAILLE_PATTERN_DOTS_1567 0x2871 #define UNITEXT_BRAILLE_PATTERN_DOTS_1567 L"\u2871" #define UNICODE_BRAILLE_PATTERN_DOTS_2567 0x2872 #define UNITEXT_BRAILLE_PATTERN_DOTS_2567 L"\u2872" #define UNICODE_BRAILLE_PATTERN_DOTS_12567 0x2873 #define UNITEXT_BRAILLE_PATTERN_DOTS_12567 L"\u2873" #define UNICODE_BRAILLE_PATTERN_DOTS_3567 0x2874 #define UNITEXT_BRAILLE_PATTERN_DOTS_3567 L"\u2874" #define UNICODE_BRAILLE_PATTERN_DOTS_13567 0x2875 #define UNITEXT_BRAILLE_PATTERN_DOTS_13567 L"\u2875" #define UNICODE_BRAILLE_PATTERN_DOTS_23567 0x2876 #define UNITEXT_BRAILLE_PATTERN_DOTS_23567 L"\u2876" #define UNICODE_BRAILLE_PATTERN_DOTS_123567 0x2877 #define UNITEXT_BRAILLE_PATTERN_DOTS_123567 L"\u2877" #define UNICODE_BRAILLE_PATTERN_DOTS_4567 0x2878 #define UNITEXT_BRAILLE_PATTERN_DOTS_4567 L"\u2878" #define UNICODE_BRAILLE_PATTERN_DOTS_14567 0x2879 #define UNITEXT_BRAILLE_PATTERN_DOTS_14567 L"\u2879" #define UNICODE_BRAILLE_PATTERN_DOTS_24567 0x287a #define UNITEXT_BRAILLE_PATTERN_DOTS_24567 L"\u287a" #define UNICODE_BRAILLE_PATTERN_DOTS_124567 0x287b #define UNITEXT_BRAILLE_PATTERN_DOTS_124567 L"\u287b" #define UNICODE_BRAILLE_PATTERN_DOTS_34567 0x287c #define UNITEXT_BRAILLE_PATTERN_DOTS_34567 L"\u287c" #define UNICODE_BRAILLE_PATTERN_DOTS_134567 0x287d #define UNITEXT_BRAILLE_PATTERN_DOTS_134567 L"\u287d" #define UNICODE_BRAILLE_PATTERN_DOTS_234567 0x287e #define UNITEXT_BRAILLE_PATTERN_DOTS_234567 L"\u287e" #define UNICODE_BRAILLE_PATTERN_DOTS_1234567 0x287f #define UNITEXT_BRAILLE_PATTERN_DOTS_1234567 L"\u287f" #define UNICODE_BRAILLE_PATTERN_DOTS_8 0x2880 #define UNITEXT_BRAILLE_PATTERN_DOTS_8 L"\u2880" #define UNICODE_BRAILLE_PATTERN_DOTS_18 0x2881 #define UNITEXT_BRAILLE_PATTERN_DOTS_18 L"\u2881" #define UNICODE_BRAILLE_PATTERN_DOTS_28 0x2882 #define UNITEXT_BRAILLE_PATTERN_DOTS_28 L"\u2882" #define UNICODE_BRAILLE_PATTERN_DOTS_128 0x2883 #define UNITEXT_BRAILLE_PATTERN_DOTS_128 L"\u2883" #define UNICODE_BRAILLE_PATTERN_DOTS_38 0x2884 #define UNITEXT_BRAILLE_PATTERN_DOTS_38 L"\u2884" #define UNICODE_BRAILLE_PATTERN_DOTS_138 0x2885 #define UNITEXT_BRAILLE_PATTERN_DOTS_138 L"\u2885" #define UNICODE_BRAILLE_PATTERN_DOTS_238 0x2886 #define UNITEXT_BRAILLE_PATTERN_DOTS_238 L"\u2886" #define UNICODE_BRAILLE_PATTERN_DOTS_1238 0x2887 #define UNITEXT_BRAILLE_PATTERN_DOTS_1238 L"\u2887" #define UNICODE_BRAILLE_PATTERN_DOTS_48 0x2888 #define UNITEXT_BRAILLE_PATTERN_DOTS_48 L"\u2888" #define UNICODE_BRAILLE_PATTERN_DOTS_148 0x2889 #define UNITEXT_BRAILLE_PATTERN_DOTS_148 L"\u2889" #define UNICODE_BRAILLE_PATTERN_DOTS_248 0x288a #define UNITEXT_BRAILLE_PATTERN_DOTS_248 L"\u288a" #define UNICODE_BRAILLE_PATTERN_DOTS_1248 0x288b #define UNITEXT_BRAILLE_PATTERN_DOTS_1248 L"\u288b" #define UNICODE_BRAILLE_PATTERN_DOTS_348 0x288c #define UNITEXT_BRAILLE_PATTERN_DOTS_348 L"\u288c" #define UNICODE_BRAILLE_PATTERN_DOTS_1348 0x288d #define UNITEXT_BRAILLE_PATTERN_DOTS_1348 L"\u288d" #define UNICODE_BRAILLE_PATTERN_DOTS_2348 0x288e #define UNITEXT_BRAILLE_PATTERN_DOTS_2348 L"\u288e" #define UNICODE_BRAILLE_PATTERN_DOTS_12348 0x288f #define UNITEXT_BRAILLE_PATTERN_DOTS_12348 L"\u288f" #define UNICODE_BRAILLE_PATTERN_DOTS_58 0x2890 #define UNITEXT_BRAILLE_PATTERN_DOTS_58 L"\u2890" #define UNICODE_BRAILLE_PATTERN_DOTS_158 0x2891 #define UNITEXT_BRAILLE_PATTERN_DOTS_158 L"\u2891" #define UNICODE_BRAILLE_PATTERN_DOTS_258 0x2892 #define UNITEXT_BRAILLE_PATTERN_DOTS_258 L"\u2892" #define UNICODE_BRAILLE_PATTERN_DOTS_1258 0x2893 #define UNITEXT_BRAILLE_PATTERN_DOTS_1258 L"\u2893" #define UNICODE_BRAILLE_PATTERN_DOTS_358 0x2894 #define UNITEXT_BRAILLE_PATTERN_DOTS_358 L"\u2894" #define UNICODE_BRAILLE_PATTERN_DOTS_1358 0x2895 #define UNITEXT_BRAILLE_PATTERN_DOTS_1358 L"\u2895" #define UNICODE_BRAILLE_PATTERN_DOTS_2358 0x2896 #define UNITEXT_BRAILLE_PATTERN_DOTS_2358 L"\u2896" #define UNICODE_BRAILLE_PATTERN_DOTS_12358 0x2897 #define UNITEXT_BRAILLE_PATTERN_DOTS_12358 L"\u2897" #define UNICODE_BRAILLE_PATTERN_DOTS_458 0x2898 #define UNITEXT_BRAILLE_PATTERN_DOTS_458 L"\u2898" #define UNICODE_BRAILLE_PATTERN_DOTS_1458 0x2899 #define UNITEXT_BRAILLE_PATTERN_DOTS_1458 L"\u2899" #define UNICODE_BRAILLE_PATTERN_DOTS_2458 0x289a #define UNITEXT_BRAILLE_PATTERN_DOTS_2458 L"\u289a" #define UNICODE_BRAILLE_PATTERN_DOTS_12458 0x289b #define UNITEXT_BRAILLE_PATTERN_DOTS_12458 L"\u289b" #define UNICODE_BRAILLE_PATTERN_DOTS_3458 0x289c #define UNITEXT_BRAILLE_PATTERN_DOTS_3458 L"\u289c" #define UNICODE_BRAILLE_PATTERN_DOTS_13458 0x289d #define UNITEXT_BRAILLE_PATTERN_DOTS_13458 L"\u289d" #define UNICODE_BRAILLE_PATTERN_DOTS_23458 0x289e #define UNITEXT_BRAILLE_PATTERN_DOTS_23458 L"\u289e" #define UNICODE_BRAILLE_PATTERN_DOTS_123458 0x289f #define UNITEXT_BRAILLE_PATTERN_DOTS_123458 L"\u289f" #define UNICODE_BRAILLE_PATTERN_DOTS_68 0x28a0 #define UNITEXT_BRAILLE_PATTERN_DOTS_68 L"\u28a0" #define UNICODE_BRAILLE_PATTERN_DOTS_168 0x28a1 #define UNITEXT_BRAILLE_PATTERN_DOTS_168 L"\u28a1" #define UNICODE_BRAILLE_PATTERN_DOTS_268 0x28a2 #define UNITEXT_BRAILLE_PATTERN_DOTS_268 L"\u28a2" #define UNICODE_BRAILLE_PATTERN_DOTS_1268 0x28a3 #define UNITEXT_BRAILLE_PATTERN_DOTS_1268 L"\u28a3" #define UNICODE_BRAILLE_PATTERN_DOTS_368 0x28a4 #define UNITEXT_BRAILLE_PATTERN_DOTS_368 L"\u28a4" #define UNICODE_BRAILLE_PATTERN_DOTS_1368 0x28a5 #define UNITEXT_BRAILLE_PATTERN_DOTS_1368 L"\u28a5" #define UNICODE_BRAILLE_PATTERN_DOTS_2368 0x28a6 #define UNITEXT_BRAILLE_PATTERN_DOTS_2368 L"\u28a6" #define UNICODE_BRAILLE_PATTERN_DOTS_12368 0x28a7 #define UNITEXT_BRAILLE_PATTERN_DOTS_12368 L"\u28a7" #define UNICODE_BRAILLE_PATTERN_DOTS_468 0x28a8 #define UNITEXT_BRAILLE_PATTERN_DOTS_468 L"\u28a8" #define UNICODE_BRAILLE_PATTERN_DOTS_1468 0x28a9 #define UNITEXT_BRAILLE_PATTERN_DOTS_1468 L"\u28a9" #define UNICODE_BRAILLE_PATTERN_DOTS_2468 0x28aa #define UNITEXT_BRAILLE_PATTERN_DOTS_2468 L"\u28aa" #define UNICODE_BRAILLE_PATTERN_DOTS_12468 0x28ab #define UNITEXT_BRAILLE_PATTERN_DOTS_12468 L"\u28ab" #define UNICODE_BRAILLE_PATTERN_DOTS_3468 0x28ac #define UNITEXT_BRAILLE_PATTERN_DOTS_3468 L"\u28ac" #define UNICODE_BRAILLE_PATTERN_DOTS_13468 0x28ad #define UNITEXT_BRAILLE_PATTERN_DOTS_13468 L"\u28ad" #define UNICODE_BRAILLE_PATTERN_DOTS_23468 0x28ae #define UNITEXT_BRAILLE_PATTERN_DOTS_23468 L"\u28ae" #define UNICODE_BRAILLE_PATTERN_DOTS_123468 0x28af #define UNITEXT_BRAILLE_PATTERN_DOTS_123468 L"\u28af" #define UNICODE_BRAILLE_PATTERN_DOTS_568 0x28b0 #define UNITEXT_BRAILLE_PATTERN_DOTS_568 L"\u28b0" #define UNICODE_BRAILLE_PATTERN_DOTS_1568 0x28b1 #define UNITEXT_BRAILLE_PATTERN_DOTS_1568 L"\u28b1" #define UNICODE_BRAILLE_PATTERN_DOTS_2568 0x28b2 #define UNITEXT_BRAILLE_PATTERN_DOTS_2568 L"\u28b2" #define UNICODE_BRAILLE_PATTERN_DOTS_12568 0x28b3 #define UNITEXT_BRAILLE_PATTERN_DOTS_12568 L"\u28b3" #define UNICODE_BRAILLE_PATTERN_DOTS_3568 0x28b4 #define UNITEXT_BRAILLE_PATTERN_DOTS_3568 L"\u28b4" #define UNICODE_BRAILLE_PATTERN_DOTS_13568 0x28b5 #define UNITEXT_BRAILLE_PATTERN_DOTS_13568 L"\u28b5" #define UNICODE_BRAILLE_PATTERN_DOTS_23568 0x28b6 #define UNITEXT_BRAILLE_PATTERN_DOTS_23568 L"\u28b6" #define UNICODE_BRAILLE_PATTERN_DOTS_123568 0x28b7 #define UNITEXT_BRAILLE_PATTERN_DOTS_123568 L"\u28b7" #define UNICODE_BRAILLE_PATTERN_DOTS_4568 0x28b8 #define UNITEXT_BRAILLE_PATTERN_DOTS_4568 L"\u28b8" #define UNICODE_BRAILLE_PATTERN_DOTS_14568 0x28b9 #define UNITEXT_BRAILLE_PATTERN_DOTS_14568 L"\u28b9" #define UNICODE_BRAILLE_PATTERN_DOTS_24568 0x28ba #define UNITEXT_BRAILLE_PATTERN_DOTS_24568 L"\u28ba" #define UNICODE_BRAILLE_PATTERN_DOTS_124568 0x28bb #define UNITEXT_BRAILLE_PATTERN_DOTS_124568 L"\u28bb" #define UNICODE_BRAILLE_PATTERN_DOTS_34568 0x28bc #define UNITEXT_BRAILLE_PATTERN_DOTS_34568 L"\u28bc" #define UNICODE_BRAILLE_PATTERN_DOTS_134568 0x28bd #define UNITEXT_BRAILLE_PATTERN_DOTS_134568 L"\u28bd" #define UNICODE_BRAILLE_PATTERN_DOTS_234568 0x28be #define UNITEXT_BRAILLE_PATTERN_DOTS_234568 L"\u28be" #define UNICODE_BRAILLE_PATTERN_DOTS_1234568 0x28bf #define UNITEXT_BRAILLE_PATTERN_DOTS_1234568 L"\u28bf" #define UNICODE_BRAILLE_PATTERN_DOTS_78 0x28c0 #define UNITEXT_BRAILLE_PATTERN_DOTS_78 L"\u28c0" #define UNICODE_BRAILLE_PATTERN_DOTS_178 0x28c1 #define UNITEXT_BRAILLE_PATTERN_DOTS_178 L"\u28c1" #define UNICODE_BRAILLE_PATTERN_DOTS_278 0x28c2 #define UNITEXT_BRAILLE_PATTERN_DOTS_278 L"\u28c2" #define UNICODE_BRAILLE_PATTERN_DOTS_1278 0x28c3 #define UNITEXT_BRAILLE_PATTERN_DOTS_1278 L"\u28c3" #define UNICODE_BRAILLE_PATTERN_DOTS_378 0x28c4 #define UNITEXT_BRAILLE_PATTERN_DOTS_378 L"\u28c4" #define UNICODE_BRAILLE_PATTERN_DOTS_1378 0x28c5 #define UNITEXT_BRAILLE_PATTERN_DOTS_1378 L"\u28c5" #define UNICODE_BRAILLE_PATTERN_DOTS_2378 0x28c6 #define UNITEXT_BRAILLE_PATTERN_DOTS_2378 L"\u28c6" #define UNICODE_BRAILLE_PATTERN_DOTS_12378 0x28c7 #define UNITEXT_BRAILLE_PATTERN_DOTS_12378 L"\u28c7" #define UNICODE_BRAILLE_PATTERN_DOTS_478 0x28c8 #define UNITEXT_BRAILLE_PATTERN_DOTS_478 L"\u28c8" #define UNICODE_BRAILLE_PATTERN_DOTS_1478 0x28c9 #define UNITEXT_BRAILLE_PATTERN_DOTS_1478 L"\u28c9" #define UNICODE_BRAILLE_PATTERN_DOTS_2478 0x28ca #define UNITEXT_BRAILLE_PATTERN_DOTS_2478 L"\u28ca" #define UNICODE_BRAILLE_PATTERN_DOTS_12478 0x28cb #define UNITEXT_BRAILLE_PATTERN_DOTS_12478 L"\u28cb" #define UNICODE_BRAILLE_PATTERN_DOTS_3478 0x28cc #define UNITEXT_BRAILLE_PATTERN_DOTS_3478 L"\u28cc" #define UNICODE_BRAILLE_PATTERN_DOTS_13478 0x28cd #define UNITEXT_BRAILLE_PATTERN_DOTS_13478 L"\u28cd" #define UNICODE_BRAILLE_PATTERN_DOTS_23478 0x28ce #define UNITEXT_BRAILLE_PATTERN_DOTS_23478 L"\u28ce" #define UNICODE_BRAILLE_PATTERN_DOTS_123478 0x28cf #define UNITEXT_BRAILLE_PATTERN_DOTS_123478 L"\u28cf" #define UNICODE_BRAILLE_PATTERN_DOTS_578 0x28d0 #define UNITEXT_BRAILLE_PATTERN_DOTS_578 L"\u28d0" #define UNICODE_BRAILLE_PATTERN_DOTS_1578 0x28d1 #define UNITEXT_BRAILLE_PATTERN_DOTS_1578 L"\u28d1" #define UNICODE_BRAILLE_PATTERN_DOTS_2578 0x28d2 #define UNITEXT_BRAILLE_PATTERN_DOTS_2578 L"\u28d2" #define UNICODE_BRAILLE_PATTERN_DOTS_12578 0x28d3 #define UNITEXT_BRAILLE_PATTERN_DOTS_12578 L"\u28d3" #define UNICODE_BRAILLE_PATTERN_DOTS_3578 0x28d4 #define UNITEXT_BRAILLE_PATTERN_DOTS_3578 L"\u28d4" #define UNICODE_BRAILLE_PATTERN_DOTS_13578 0x28d5 #define UNITEXT_BRAILLE_PATTERN_DOTS_13578 L"\u28d5" #define UNICODE_BRAILLE_PATTERN_DOTS_23578 0x28d6 #define UNITEXT_BRAILLE_PATTERN_DOTS_23578 L"\u28d6" #define UNICODE_BRAILLE_PATTERN_DOTS_123578 0x28d7 #define UNITEXT_BRAILLE_PATTERN_DOTS_123578 L"\u28d7" #define UNICODE_BRAILLE_PATTERN_DOTS_4578 0x28d8 #define UNITEXT_BRAILLE_PATTERN_DOTS_4578 L"\u28d8" #define UNICODE_BRAILLE_PATTERN_DOTS_14578 0x28d9 #define UNITEXT_BRAILLE_PATTERN_DOTS_14578 L"\u28d9" #define UNICODE_BRAILLE_PATTERN_DOTS_24578 0x28da #define UNITEXT_BRAILLE_PATTERN_DOTS_24578 L"\u28da" #define UNICODE_BRAILLE_PATTERN_DOTS_124578 0x28db #define UNITEXT_BRAILLE_PATTERN_DOTS_124578 L"\u28db" #define UNICODE_BRAILLE_PATTERN_DOTS_34578 0x28dc #define UNITEXT_BRAILLE_PATTERN_DOTS_34578 L"\u28dc" #define UNICODE_BRAILLE_PATTERN_DOTS_134578 0x28dd #define UNITEXT_BRAILLE_PATTERN_DOTS_134578 L"\u28dd" #define UNICODE_BRAILLE_PATTERN_DOTS_234578 0x28de #define UNITEXT_BRAILLE_PATTERN_DOTS_234578 L"\u28de" #define UNICODE_BRAILLE_PATTERN_DOTS_1234578 0x28df #define UNITEXT_BRAILLE_PATTERN_DOTS_1234578 L"\u28df" #define UNICODE_BRAILLE_PATTERN_DOTS_678 0x28e0 #define UNITEXT_BRAILLE_PATTERN_DOTS_678 L"\u28e0" #define UNICODE_BRAILLE_PATTERN_DOTS_1678 0x28e1 #define UNITEXT_BRAILLE_PATTERN_DOTS_1678 L"\u28e1" #define UNICODE_BRAILLE_PATTERN_DOTS_2678 0x28e2 #define UNITEXT_BRAILLE_PATTERN_DOTS_2678 L"\u28e2" #define UNICODE_BRAILLE_PATTERN_DOTS_12678 0x28e3 #define UNITEXT_BRAILLE_PATTERN_DOTS_12678 L"\u28e3" #define UNICODE_BRAILLE_PATTERN_DOTS_3678 0x28e4 #define UNITEXT_BRAILLE_PATTERN_DOTS_3678 L"\u28e4" #define UNICODE_BRAILLE_PATTERN_DOTS_13678 0x28e5 #define UNITEXT_BRAILLE_PATTERN_DOTS_13678 L"\u28e5" #define UNICODE_BRAILLE_PATTERN_DOTS_23678 0x28e6 #define UNITEXT_BRAILLE_PATTERN_DOTS_23678 L"\u28e6" #define UNICODE_BRAILLE_PATTERN_DOTS_123678 0x28e7 #define UNITEXT_BRAILLE_PATTERN_DOTS_123678 L"\u28e7" #define UNICODE_BRAILLE_PATTERN_DOTS_4678 0x28e8 #define UNITEXT_BRAILLE_PATTERN_DOTS_4678 L"\u28e8" #define UNICODE_BRAILLE_PATTERN_DOTS_14678 0x28e9 #define UNITEXT_BRAILLE_PATTERN_DOTS_14678 L"\u28e9" #define UNICODE_BRAILLE_PATTERN_DOTS_24678 0x28ea #define UNITEXT_BRAILLE_PATTERN_DOTS_24678 L"\u28ea" #define UNICODE_BRAILLE_PATTERN_DOTS_124678 0x28eb #define UNITEXT_BRAILLE_PATTERN_DOTS_124678 L"\u28eb" #define UNICODE_BRAILLE_PATTERN_DOTS_34678 0x28ec #define UNITEXT_BRAILLE_PATTERN_DOTS_34678 L"\u28ec" #define UNICODE_BRAILLE_PATTERN_DOTS_134678 0x28ed #define UNITEXT_BRAILLE_PATTERN_DOTS_134678 L"\u28ed" #define UNICODE_BRAILLE_PATTERN_DOTS_234678 0x28ee #define UNITEXT_BRAILLE_PATTERN_DOTS_234678 L"\u28ee" #define UNICODE_BRAILLE_PATTERN_DOTS_1234678 0x28ef #define UNITEXT_BRAILLE_PATTERN_DOTS_1234678 L"\u28ef" #define UNICODE_BRAILLE_PATTERN_DOTS_5678 0x28f0 #define UNITEXT_BRAILLE_PATTERN_DOTS_5678 L"\u28f0" #define UNICODE_BRAILLE_PATTERN_DOTS_15678 0x28f1 #define UNITEXT_BRAILLE_PATTERN_DOTS_15678 L"\u28f1" #define UNICODE_BRAILLE_PATTERN_DOTS_25678 0x28f2 #define UNITEXT_BRAILLE_PATTERN_DOTS_25678 L"\u28f2" #define UNICODE_BRAILLE_PATTERN_DOTS_125678 0x28f3 #define UNITEXT_BRAILLE_PATTERN_DOTS_125678 L"\u28f3" #define UNICODE_BRAILLE_PATTERN_DOTS_35678 0x28f4 #define UNITEXT_BRAILLE_PATTERN_DOTS_35678 L"\u28f4" #define UNICODE_BRAILLE_PATTERN_DOTS_135678 0x28f5 #define UNITEXT_BRAILLE_PATTERN_DOTS_135678 L"\u28f5" #define UNICODE_BRAILLE_PATTERN_DOTS_235678 0x28f6 #define UNITEXT_BRAILLE_PATTERN_DOTS_235678 L"\u28f6" #define UNICODE_BRAILLE_PATTERN_DOTS_1235678 0x28f7 #define UNITEXT_BRAILLE_PATTERN_DOTS_1235678 L"\u28f7" #define UNICODE_BRAILLE_PATTERN_DOTS_45678 0x28f8 #define UNITEXT_BRAILLE_PATTERN_DOTS_45678 L"\u28f8" #define UNICODE_BRAILLE_PATTERN_DOTS_145678 0x28f9 #define UNITEXT_BRAILLE_PATTERN_DOTS_145678 L"\u28f9" #define UNICODE_BRAILLE_PATTERN_DOTS_245678 0x28fa #define UNITEXT_BRAILLE_PATTERN_DOTS_245678 L"\u28fa" #define UNICODE_BRAILLE_PATTERN_DOTS_1245678 0x28fb #define UNITEXT_BRAILLE_PATTERN_DOTS_1245678 L"\u28fb" #define UNICODE_BRAILLE_PATTERN_DOTS_345678 0x28fc #define UNITEXT_BRAILLE_PATTERN_DOTS_345678 L"\u28fc" #define UNICODE_BRAILLE_PATTERN_DOTS_1345678 0x28fd #define UNITEXT_BRAILLE_PATTERN_DOTS_1345678 L"\u28fd" #define UNICODE_BRAILLE_PATTERN_DOTS_2345678 0x28fe #define UNITEXT_BRAILLE_PATTERN_DOTS_2345678 L"\u28fe" #define UNICODE_BRAILLE_PATTERN_DOTS_12345678 0x28ff #define UNITEXT_BRAILLE_PATTERN_DOTS_12345678 L"\u28ff" #define UNICODE_RIGHTWARDS_TWO_HEADED_ARROW_WITH_VERTICAL_STROKE 0x2900 #define UNITEXT_RIGHTWARDS_TWO_HEADED_ARROW_WITH_VERTICAL_STROKE L"\u2900" #define UNICODE_RIGHTWARDS_TWO_HEADED_ARROW_WITH_DOUBLE_VERTICAL_STROKE 0x2901 #define UNITEXT_RIGHTWARDS_TWO_HEADED_ARROW_WITH_DOUBLE_VERTICAL_STROKE L"\u2901" #define UNICODE_LEFTWARDS_DOUBLE_ARROW_WITH_VERTICAL_STROKE 0x2902 #define UNITEXT_LEFTWARDS_DOUBLE_ARROW_WITH_VERTICAL_STROKE L"\u2902" #define UNICODE_RIGHTWARDS_DOUBLE_ARROW_WITH_VERTICAL_STROKE 0x2903 #define UNITEXT_RIGHTWARDS_DOUBLE_ARROW_WITH_VERTICAL_STROKE L"\u2903" #define UNICODE_LEFT_RIGHT_DOUBLE_ARROW_WITH_VERTICAL_STROKE 0x2904 #define UNITEXT_LEFT_RIGHT_DOUBLE_ARROW_WITH_VERTICAL_STROKE L"\u2904" #define UNICODE_RIGHTWARDS_TWO_HEADED_ARROW_FROM_BAR 0x2905 #define UNITEXT_RIGHTWARDS_TWO_HEADED_ARROW_FROM_BAR L"\u2905" #define UNICODE_LEFTWARDS_DOUBLE_ARROW_FROM_BAR 0x2906 #define UNITEXT_LEFTWARDS_DOUBLE_ARROW_FROM_BAR L"\u2906" #define UNICODE_RIGHTWARDS_DOUBLE_ARROW_FROM_BAR 0x2907 #define UNITEXT_RIGHTWARDS_DOUBLE_ARROW_FROM_BAR L"\u2907" #define UNICODE_DOWNWARDS_ARROW_WITH_HORIZONTAL_STROKE 0x2908 #define UNITEXT_DOWNWARDS_ARROW_WITH_HORIZONTAL_STROKE L"\u2908" #define UNICODE_UPWARDS_ARROW_WITH_HORIZONTAL_STROKE 0x2909 #define UNITEXT_UPWARDS_ARROW_WITH_HORIZONTAL_STROKE L"\u2909" #define UNICODE_UPWARDS_TRIPLE_ARROW 0x290a #define UNITEXT_UPWARDS_TRIPLE_ARROW L"\u290a" #define UNICODE_DOWNWARDS_TRIPLE_ARROW 0x290b #define UNITEXT_DOWNWARDS_TRIPLE_ARROW L"\u290b" #define UNICODE_LEFTWARDS_DOUBLE_DASH_ARROW 0x290c #define UNITEXT_LEFTWARDS_DOUBLE_DASH_ARROW L"\u290c" #define UNICODE_RIGHTWARDS_DOUBLE_DASH_ARROW 0x290d #define UNITEXT_RIGHTWARDS_DOUBLE_DASH_ARROW L"\u290d" #define UNICODE_LEFTWARDS_TRIPLE_DASH_ARROW 0x290e #define UNITEXT_LEFTWARDS_TRIPLE_DASH_ARROW L"\u290e" #define UNICODE_RIGHTWARDS_TRIPLE_DASH_ARROW 0x290f #define UNITEXT_RIGHTWARDS_TRIPLE_DASH_ARROW L"\u290f" #define UNICODE_RIGHTWARDS_TWO_HEADED_TRIPLE_DASH_ARROW 0x2910 #define UNITEXT_RIGHTWARDS_TWO_HEADED_TRIPLE_DASH_ARROW L"\u2910" #define UNICODE_RIGHTWARDS_ARROW_WITH_DOTTED_STEM 0x2911 #define UNITEXT_RIGHTWARDS_ARROW_WITH_DOTTED_STEM L"\u2911" #define UNICODE_UPWARDS_ARROW_TO_BAR 0x2912 #define UNITEXT_UPWARDS_ARROW_TO_BAR L"\u2912" #define UNICODE_DOWNWARDS_ARROW_TO_BAR 0x2913 #define UNITEXT_DOWNWARDS_ARROW_TO_BAR L"\u2913" #define UNICODE_RIGHTWARDS_ARROW_WITH_TAIL_WITH_VERTICAL_STROKE 0x2914 #define UNITEXT_RIGHTWARDS_ARROW_WITH_TAIL_WITH_VERTICAL_STROKE L"\u2914" #define UNICODE_RIGHTWARDS_ARROW_WITH_TAIL_WITH_DOUBLE_VERTICAL_STROKE 0x2915 #define UNITEXT_RIGHTWARDS_ARROW_WITH_TAIL_WITH_DOUBLE_VERTICAL_STROKE L"\u2915" #define UNICODE_RIGHTWARDS_TWO_HEADED_ARROW_WITH_TAIL 0x2916 #define UNITEXT_RIGHTWARDS_TWO_HEADED_ARROW_WITH_TAIL L"\u2916" #define UNICODE_RIGHTWARDS_TWO_HEADED_ARROW_WITH_TAIL_WITH_VERTICAL_STROKE 0x2917 #define UNITEXT_RIGHTWARDS_TWO_HEADED_ARROW_WITH_TAIL_WITH_VERTICAL_STROKE L"\u2917" #define UNICODE_RIGHTWARDS_TWO_HEADED_ARROW_WITH_TAIL_WITH_DOUBLE_VERTICAL_STROKE 0x2918 #define UNITEXT_RIGHTWARDS_TWO_HEADED_ARROW_WITH_TAIL_WITH_DOUBLE_VERTICAL_STROKE L"\u2918" #define UNICODE_LEFTWARDS_ARROW_TAIL 0x2919 #define UNITEXT_LEFTWARDS_ARROW_TAIL L"\u2919" #define UNICODE_RIGHTWARDS_ARROW_TAIL 0x291a #define UNITEXT_RIGHTWARDS_ARROW_TAIL L"\u291a" #define UNICODE_LEFTWARDS_DOUBLE_ARROW_TAIL 0x291b #define UNITEXT_LEFTWARDS_DOUBLE_ARROW_TAIL L"\u291b" #define UNICODE_RIGHTWARDS_DOUBLE_ARROW_TAIL 0x291c #define UNITEXT_RIGHTWARDS_DOUBLE_ARROW_TAIL L"\u291c" #define UNICODE_LEFTWARDS_ARROW_TO_BLACK_DIAMOND 0x291d #define UNITEXT_LEFTWARDS_ARROW_TO_BLACK_DIAMOND L"\u291d" #define UNICODE_RIGHTWARDS_ARROW_TO_BLACK_DIAMOND 0x291e #define UNITEXT_RIGHTWARDS_ARROW_TO_BLACK_DIAMOND L"\u291e" #define UNICODE_LEFTWARDS_ARROW_FROM_BAR_TO_BLACK_DIAMOND 0x291f #define UNITEXT_LEFTWARDS_ARROW_FROM_BAR_TO_BLACK_DIAMOND L"\u291f" #define UNICODE_RIGHTWARDS_ARROW_FROM_BAR_TO_BLACK_DIAMOND 0x2920 #define UNITEXT_RIGHTWARDS_ARROW_FROM_BAR_TO_BLACK_DIAMOND L"\u2920" #define UNICODE_NORTH_WEST_AND_SOUTH_EAST_ARROW 0x2921 #define UNITEXT_NORTH_WEST_AND_SOUTH_EAST_ARROW L"\u2921" #define UNICODE_NORTH_EAST_AND_SOUTH_WEST_ARROW 0x2922 #define UNITEXT_NORTH_EAST_AND_SOUTH_WEST_ARROW L"\u2922" #define UNICODE_NORTH_WEST_ARROW_WITH_HOOK 0x2923 #define UNITEXT_NORTH_WEST_ARROW_WITH_HOOK L"\u2923" #define UNICODE_NORTH_EAST_ARROW_WITH_HOOK 0x2924 #define UNITEXT_NORTH_EAST_ARROW_WITH_HOOK L"\u2924" #define UNICODE_SOUTH_EAST_ARROW_WITH_HOOK 0x2925 #define UNITEXT_SOUTH_EAST_ARROW_WITH_HOOK L"\u2925" #define UNICODE_SOUTH_WEST_ARROW_WITH_HOOK 0x2926 #define UNITEXT_SOUTH_WEST_ARROW_WITH_HOOK L"\u2926" #define UNICODE_NORTH_WEST_ARROW_AND_NORTH_EAST_ARROW 0x2927 #define UNITEXT_NORTH_WEST_ARROW_AND_NORTH_EAST_ARROW L"\u2927" #define UNICODE_NORTH_EAST_ARROW_AND_SOUTH_EAST_ARROW 0x2928 #define UNITEXT_NORTH_EAST_ARROW_AND_SOUTH_EAST_ARROW L"\u2928" #define UNICODE_SOUTH_EAST_ARROW_AND_SOUTH_WEST_ARROW 0x2929 #define UNITEXT_SOUTH_EAST_ARROW_AND_SOUTH_WEST_ARROW L"\u2929" #define UNICODE_SOUTH_WEST_ARROW_AND_NORTH_WEST_ARROW 0x292a #define UNITEXT_SOUTH_WEST_ARROW_AND_NORTH_WEST_ARROW L"\u292a" #define UNICODE_RISING_DIAGONAL_CROSSING_FALLING_DIAGONAL 0x292b #define UNITEXT_RISING_DIAGONAL_CROSSING_FALLING_DIAGONAL L"\u292b" #define UNICODE_FALLING_DIAGONAL_CROSSING_RISING_DIAGONAL 0x292c #define UNITEXT_FALLING_DIAGONAL_CROSSING_RISING_DIAGONAL L"\u292c" #define UNICODE_SOUTH_EAST_ARROW_CROSSING_NORTH_EAST_ARROW 0x292d #define UNITEXT_SOUTH_EAST_ARROW_CROSSING_NORTH_EAST_ARROW L"\u292d" #define UNICODE_NORTH_EAST_ARROW_CROSSING_SOUTH_EAST_ARROW 0x292e #define UNITEXT_NORTH_EAST_ARROW_CROSSING_SOUTH_EAST_ARROW L"\u292e" #define UNICODE_FALLING_DIAGONAL_CROSSING_NORTH_EAST_ARROW 0x292f #define UNITEXT_FALLING_DIAGONAL_CROSSING_NORTH_EAST_ARROW L"\u292f" #define UNICODE_RISING_DIAGONAL_CROSSING_SOUTH_EAST_ARROW 0x2930 #define UNITEXT_RISING_DIAGONAL_CROSSING_SOUTH_EAST_ARROW L"\u2930" #define UNICODE_NORTH_EAST_ARROW_CROSSING_NORTH_WEST_ARROW 0x2931 #define UNITEXT_NORTH_EAST_ARROW_CROSSING_NORTH_WEST_ARROW L"\u2931" #define UNICODE_NORTH_WEST_ARROW_CROSSING_NORTH_EAST_ARROW 0x2932 #define UNITEXT_NORTH_WEST_ARROW_CROSSING_NORTH_EAST_ARROW L"\u2932" #define UNICODE_WAVE_ARROW_POINTING_DIRECTLY_RIGHT 0x2933 #define UNITEXT_WAVE_ARROW_POINTING_DIRECTLY_RIGHT L"\u2933" #define UNICODE_ARROW_POINTING_RIGHTWARDS_THEN_CURVING_UPWARDS 0x2934 #define UNITEXT_ARROW_POINTING_RIGHTWARDS_THEN_CURVING_UPWARDS L"\u2934" #define UNICODE_ARROW_POINTING_RIGHTWARDS_THEN_CURVING_DOWNWARDS 0x2935 #define UNITEXT_ARROW_POINTING_RIGHTWARDS_THEN_CURVING_DOWNWARDS L"\u2935" #define UNICODE_ARROW_POINTING_DOWNWARDS_THEN_CURVING_LEFTWARDS 0x2936 #define UNITEXT_ARROW_POINTING_DOWNWARDS_THEN_CURVING_LEFTWARDS L"\u2936" #define UNICODE_ARROW_POINTING_DOWNWARDS_THEN_CURVING_RIGHTWARDS 0x2937 #define UNITEXT_ARROW_POINTING_DOWNWARDS_THEN_CURVING_RIGHTWARDS L"\u2937" #define UNICODE_RIGHT_SIDE_ARC_CLOCKWISE_ARROW 0x2938 #define UNITEXT_RIGHT_SIDE_ARC_CLOCKWISE_ARROW L"\u2938" #define UNICODE_LEFT_SIDE_ARC_ANTICLOCKWISE_ARROW 0x2939 #define UNITEXT_LEFT_SIDE_ARC_ANTICLOCKWISE_ARROW L"\u2939" #define UNICODE_TOP_ARC_ANTICLOCKWISE_ARROW 0x293a #define UNITEXT_TOP_ARC_ANTICLOCKWISE_ARROW L"\u293a" #define UNICODE_BOTTOM_ARC_ANTICLOCKWISE_ARROW 0x293b #define UNITEXT_BOTTOM_ARC_ANTICLOCKWISE_ARROW L"\u293b" #define UNICODE_TOP_ARC_CLOCKWISE_ARROW_WITH_MINUS 0x293c #define UNITEXT_TOP_ARC_CLOCKWISE_ARROW_WITH_MINUS L"\u293c" #define UNICODE_TOP_ARC_ANTICLOCKWISE_ARROW_WITH_PLUS 0x293d #define UNITEXT_TOP_ARC_ANTICLOCKWISE_ARROW_WITH_PLUS L"\u293d" #define UNICODE_LOWER_RIGHT_SEMICIRCULAR_CLOCKWISE_ARROW 0x293e #define UNITEXT_LOWER_RIGHT_SEMICIRCULAR_CLOCKWISE_ARROW L"\u293e" #define UNICODE_LOWER_LEFT_SEMICIRCULAR_ANTICLOCKWISE_ARROW 0x293f #define UNITEXT_LOWER_LEFT_SEMICIRCULAR_ANTICLOCKWISE_ARROW L"\u293f" #define UNICODE_ANTICLOCKWISE_CLOSED_CIRCLE_ARROW 0x2940 #define UNITEXT_ANTICLOCKWISE_CLOSED_CIRCLE_ARROW L"\u2940" #define UNICODE_CLOCKWISE_CLOSED_CIRCLE_ARROW 0x2941 #define UNITEXT_CLOCKWISE_CLOSED_CIRCLE_ARROW L"\u2941" #define UNICODE_RIGHTWARDS_ARROW_ABOVE_SHORT_LEFTWARDS_ARROW 0x2942 #define UNITEXT_RIGHTWARDS_ARROW_ABOVE_SHORT_LEFTWARDS_ARROW L"\u2942" #define UNICODE_LEFTWARDS_ARROW_ABOVE_SHORT_RIGHTWARDS_ARROW 0x2943 #define UNITEXT_LEFTWARDS_ARROW_ABOVE_SHORT_RIGHTWARDS_ARROW L"\u2943" #define UNICODE_SHORT_RIGHTWARDS_ARROW_ABOVE_LEFTWARDS_ARROW 0x2944 #define UNITEXT_SHORT_RIGHTWARDS_ARROW_ABOVE_LEFTWARDS_ARROW L"\u2944" #define UNICODE_RIGHTWARDS_ARROW_WITH_PLUS_BELOW 0x2945 #define UNITEXT_RIGHTWARDS_ARROW_WITH_PLUS_BELOW L"\u2945" #define UNICODE_LEFTWARDS_ARROW_WITH_PLUS_BELOW 0x2946 #define UNITEXT_LEFTWARDS_ARROW_WITH_PLUS_BELOW L"\u2946" #define UNICODE_RIGHTWARDS_ARROW_THROUGH_X 0x2947 #define UNITEXT_RIGHTWARDS_ARROW_THROUGH_X L"\u2947" #define UNICODE_LEFT_RIGHT_ARROW_THROUGH_SMALL_CIRCLE 0x2948 #define UNITEXT_LEFT_RIGHT_ARROW_THROUGH_SMALL_CIRCLE L"\u2948" #define UNICODE_UPWARDS_TWO_HEADED_ARROW_FROM_SMALL_CIRCLE 0x2949 #define UNITEXT_UPWARDS_TWO_HEADED_ARROW_FROM_SMALL_CIRCLE L"\u2949" #define UNICODE_LEFT_BARB_UP_RIGHT_BARB_DOWN_HARPOON 0x294a #define UNITEXT_LEFT_BARB_UP_RIGHT_BARB_DOWN_HARPOON L"\u294a" #define UNICODE_LEFT_BARB_DOWN_RIGHT_BARB_UP_HARPOON 0x294b #define UNITEXT_LEFT_BARB_DOWN_RIGHT_BARB_UP_HARPOON L"\u294b" #define UNICODE_UP_BARB_RIGHT_DOWN_BARB_LEFT_HARPOON 0x294c #define UNITEXT_UP_BARB_RIGHT_DOWN_BARB_LEFT_HARPOON L"\u294c" #define UNICODE_UP_BARB_LEFT_DOWN_BARB_RIGHT_HARPOON 0x294d #define UNITEXT_UP_BARB_LEFT_DOWN_BARB_RIGHT_HARPOON L"\u294d" #define UNICODE_LEFT_BARB_UP_RIGHT_BARB_UP_HARPOON 0x294e #define UNITEXT_LEFT_BARB_UP_RIGHT_BARB_UP_HARPOON L"\u294e" #define UNICODE_UP_BARB_RIGHT_DOWN_BARB_RIGHT_HARPOON 0x294f #define UNITEXT_UP_BARB_RIGHT_DOWN_BARB_RIGHT_HARPOON L"\u294f" #define UNICODE_LEFT_BARB_DOWN_RIGHT_BARB_DOWN_HARPOON 0x2950 #define UNITEXT_LEFT_BARB_DOWN_RIGHT_BARB_DOWN_HARPOON L"\u2950" #define UNICODE_UP_BARB_LEFT_DOWN_BARB_LEFT_HARPOON 0x2951 #define UNITEXT_UP_BARB_LEFT_DOWN_BARB_LEFT_HARPOON L"\u2951" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_UP_TO_BAR 0x2952 #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_UP_TO_BAR L"\u2952" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_UP_TO_BAR 0x2953 #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_UP_TO_BAR L"\u2953" #define UNICODE_UPWARDS_HARPOON_WITH_BARB_RIGHT_TO_BAR 0x2954 #define UNITEXT_UPWARDS_HARPOON_WITH_BARB_RIGHT_TO_BAR L"\u2954" #define UNICODE_DOWNWARDS_HARPOON_WITH_BARB_RIGHT_TO_BAR 0x2955 #define UNITEXT_DOWNWARDS_HARPOON_WITH_BARB_RIGHT_TO_BAR L"\u2955" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_DOWN_TO_BAR 0x2956 #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_DOWN_TO_BAR L"\u2956" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_DOWN_TO_BAR 0x2957 #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_DOWN_TO_BAR L"\u2957" #define UNICODE_UPWARDS_HARPOON_WITH_BARB_LEFT_TO_BAR 0x2958 #define UNITEXT_UPWARDS_HARPOON_WITH_BARB_LEFT_TO_BAR L"\u2958" #define UNICODE_DOWNWARDS_HARPOON_WITH_BARB_LEFT_TO_BAR 0x2959 #define UNITEXT_DOWNWARDS_HARPOON_WITH_BARB_LEFT_TO_BAR L"\u2959" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_UP_FROM_BAR 0x295a #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_UP_FROM_BAR L"\u295a" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_UP_FROM_BAR 0x295b #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_UP_FROM_BAR L"\u295b" #define UNICODE_UPWARDS_HARPOON_WITH_BARB_RIGHT_FROM_BAR 0x295c #define UNITEXT_UPWARDS_HARPOON_WITH_BARB_RIGHT_FROM_BAR L"\u295c" #define UNICODE_DOWNWARDS_HARPOON_WITH_BARB_RIGHT_FROM_BAR 0x295d #define UNITEXT_DOWNWARDS_HARPOON_WITH_BARB_RIGHT_FROM_BAR L"\u295d" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_DOWN_FROM_BAR 0x295e #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_DOWN_FROM_BAR L"\u295e" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_DOWN_FROM_BAR 0x295f #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_DOWN_FROM_BAR L"\u295f" #define UNICODE_UPWARDS_HARPOON_WITH_BARB_LEFT_FROM_BAR 0x2960 #define UNITEXT_UPWARDS_HARPOON_WITH_BARB_LEFT_FROM_BAR L"\u2960" #define UNICODE_DOWNWARDS_HARPOON_WITH_BARB_LEFT_FROM_BAR 0x2961 #define UNITEXT_DOWNWARDS_HARPOON_WITH_BARB_LEFT_FROM_BAR L"\u2961" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_UP_ABOVE_LEFTWARDS_HARPOON_WITH_BARB_DOWN 0x2962 #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_UP_ABOVE_LEFTWARDS_HARPOON_WITH_BARB_DOWN L"\u2962" #define UNICODE_UPWARDS_HARPOON_WITH_BARB_LEFT_BESIDE_UPWARDS_HARPOON_WITH_BARB_RIGHT 0x2963 #define UNITEXT_UPWARDS_HARPOON_WITH_BARB_LEFT_BESIDE_UPWARDS_HARPOON_WITH_BARB_RIGHT L"\u2963" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_UP_ABOVE_RIGHTWARDS_HARPOON_WITH_BARB_DOWN 0x2964 #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_UP_ABOVE_RIGHTWARDS_HARPOON_WITH_BARB_DOWN L"\u2964" #define UNICODE_DOWNWARDS_HARPOON_WITH_BARB_LEFT_BESIDE_DOWNWARDS_HARPOON_WITH_BARB_RIGHT 0x2965 #define UNITEXT_DOWNWARDS_HARPOON_WITH_BARB_LEFT_BESIDE_DOWNWARDS_HARPOON_WITH_BARB_RIGHT L"\u2965" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_UP_ABOVE_RIGHTWARDS_HARPOON_WITH_BARB_UP 0x2966 #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_UP_ABOVE_RIGHTWARDS_HARPOON_WITH_BARB_UP L"\u2966" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_DOWN_ABOVE_RIGHTWARDS_HARPOON_WITH_BARB_DOWN 0x2967 #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_DOWN_ABOVE_RIGHTWARDS_HARPOON_WITH_BARB_DOWN L"\u2967" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_UP_ABOVE_LEFTWARDS_HARPOON_WITH_BARB_UP 0x2968 #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_UP_ABOVE_LEFTWARDS_HARPOON_WITH_BARB_UP L"\u2968" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_DOWN_ABOVE_LEFTWARDS_HARPOON_WITH_BARB_DOWN 0x2969 #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_DOWN_ABOVE_LEFTWARDS_HARPOON_WITH_BARB_DOWN L"\u2969" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_UP_ABOVE_LONG_DASH 0x296a #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_UP_ABOVE_LONG_DASH L"\u296a" #define UNICODE_LEFTWARDS_HARPOON_WITH_BARB_DOWN_BELOW_LONG_DASH 0x296b #define UNITEXT_LEFTWARDS_HARPOON_WITH_BARB_DOWN_BELOW_LONG_DASH L"\u296b" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_UP_ABOVE_LONG_DASH 0x296c #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_UP_ABOVE_LONG_DASH L"\u296c" #define UNICODE_RIGHTWARDS_HARPOON_WITH_BARB_DOWN_BELOW_LONG_DASH 0x296d #define UNITEXT_RIGHTWARDS_HARPOON_WITH_BARB_DOWN_BELOW_LONG_DASH L"\u296d" #define UNICODE_UPWARDS_HARPOON_WITH_BARB_LEFT_BESIDE_DOWNWARDS_HARPOON_WITH_BARB_RIGHT 0x296e #define UNITEXT_UPWARDS_HARPOON_WITH_BARB_LEFT_BESIDE_DOWNWARDS_HARPOON_WITH_BARB_RIGHT L"\u296e" #define UNICODE_DOWNWARDS_HARPOON_WITH_BARB_LEFT_BESIDE_UPWARDS_HARPOON_WITH_BARB_RIGHT 0x296f #define UNITEXT_DOWNWARDS_HARPOON_WITH_BARB_LEFT_BESIDE_UPWARDS_HARPOON_WITH_BARB_RIGHT L"\u296f" #define UNICODE_RIGHT_DOUBLE_ARROW_WITH_ROUNDED_HEAD 0x2970 #define UNITEXT_RIGHT_DOUBLE_ARROW_WITH_ROUNDED_HEAD L"\u2970" #define UNICODE_EQUALS_SIGN_ABOVE_RIGHTWARDS_ARROW 0x2971 #define UNITEXT_EQUALS_SIGN_ABOVE_RIGHTWARDS_ARROW L"\u2971" #define UNICODE_TILDE_OPERATOR_ABOVE_RIGHTWARDS_ARROW 0x2972 #define UNITEXT_TILDE_OPERATOR_ABOVE_RIGHTWARDS_ARROW L"\u2972" #define UNICODE_LEFTWARDS_ARROW_ABOVE_TILDE_OPERATOR 0x2973 #define UNITEXT_LEFTWARDS_ARROW_ABOVE_TILDE_OPERATOR L"\u2973" #define UNICODE_RIGHTWARDS_ARROW_ABOVE_TILDE_OPERATOR 0x2974 #define UNITEXT_RIGHTWARDS_ARROW_ABOVE_TILDE_OPERATOR L"\u2974" #define UNICODE_RIGHTWARDS_ARROW_ABOVE_ALMOST_EQUAL_TO 0x2975 #define UNITEXT_RIGHTWARDS_ARROW_ABOVE_ALMOST_EQUAL_TO L"\u2975" #define UNICODE_LESS_THAN_ABOVE_LEFTWARDS_ARROW 0x2976 #define UNITEXT_LESS_THAN_ABOVE_LEFTWARDS_ARROW L"\u2976" #define UNICODE_LEFTWARDS_ARROW_THROUGH_LESS_THAN 0x2977 #define UNITEXT_LEFTWARDS_ARROW_THROUGH_LESS_THAN L"\u2977" #define UNICODE_GREATER_THAN_ABOVE_RIGHTWARDS_ARROW 0x2978 #define UNITEXT_GREATER_THAN_ABOVE_RIGHTWARDS_ARROW L"\u2978" #define UNICODE_SUBSET_ABOVE_RIGHTWARDS_ARROW 0x2979 #define UNITEXT_SUBSET_ABOVE_RIGHTWARDS_ARROW L"\u2979" #define UNICODE_LEFTWARDS_ARROW_THROUGH_SUBSET 0x297a #define UNITEXT_LEFTWARDS_ARROW_THROUGH_SUBSET L"\u297a" #define UNICODE_SUPERSET_ABOVE_LEFTWARDS_ARROW 0x297b #define UNITEXT_SUPERSET_ABOVE_LEFTWARDS_ARROW L"\u297b" #define UNICODE_LEFT_FISH_TAIL 0x297c #define UNITEXT_LEFT_FISH_TAIL L"\u297c" #define UNICODE_RIGHT_FISH_TAIL 0x297d #define UNITEXT_RIGHT_FISH_TAIL L"\u297d" #define UNICODE_UP_FISH_TAIL 0x297e #define UNITEXT_UP_FISH_TAIL L"\u297e" #define UNICODE_DOWN_FISH_TAIL 0x297f #define UNITEXT_DOWN_FISH_TAIL L"\u297f" #define UNICODE_TRIPLE_VERTICAL_BAR_DELIMITER 0x2980 #define UNITEXT_TRIPLE_VERTICAL_BAR_DELIMITER L"\u2980" #define UNICODE_Z_NOTATION_SPOT 0x2981 #define UNITEXT_Z_NOTATION_SPOT L"\u2981" #define UNICODE_Z_NOTATION_TYPE_COLON 0x2982 #define UNITEXT_Z_NOTATION_TYPE_COLON L"\u2982" #define UNICODE_LEFT_WHITE_CURLY_BRACKET 0x2983 #define UNITEXT_LEFT_WHITE_CURLY_BRACKET L"\u2983" #define UNICODE_RIGHT_WHITE_CURLY_BRACKET 0x2984 #define UNITEXT_RIGHT_WHITE_CURLY_BRACKET L"\u2984" #define UNICODE_LEFT_WHITE_PARENTHESIS 0x2985 #define UNITEXT_LEFT_WHITE_PARENTHESIS L"\u2985" #define UNICODE_RIGHT_WHITE_PARENTHESIS 0x2986 #define UNITEXT_RIGHT_WHITE_PARENTHESIS L"\u2986" #define UNICODE_Z_NOTATION_LEFT_IMAGE_BRACKET 0x2987 #define UNITEXT_Z_NOTATION_LEFT_IMAGE_BRACKET L"\u2987" #define UNICODE_Z_NOTATION_RIGHT_IMAGE_BRACKET 0x2988 #define UNITEXT_Z_NOTATION_RIGHT_IMAGE_BRACKET L"\u2988" #define UNICODE_Z_NOTATION_LEFT_BINDING_BRACKET 0x2989 #define UNITEXT_Z_NOTATION_LEFT_BINDING_BRACKET L"\u2989" #define UNICODE_Z_NOTATION_RIGHT_BINDING_BRACKET 0x298a #define UNITEXT_Z_NOTATION_RIGHT_BINDING_BRACKET L"\u298a" #define UNICODE_LEFT_SQUARE_BRACKET_WITH_UNDERBAR 0x298b #define UNITEXT_LEFT_SQUARE_BRACKET_WITH_UNDERBAR L"\u298b" #define UNICODE_RIGHT_SQUARE_BRACKET_WITH_UNDERBAR 0x298c #define UNITEXT_RIGHT_SQUARE_BRACKET_WITH_UNDERBAR L"\u298c" #define UNICODE_LEFT_SQUARE_BRACKET_WITH_TICK_IN_TOP_CORNER 0x298d #define UNITEXT_LEFT_SQUARE_BRACKET_WITH_TICK_IN_TOP_CORNER L"\u298d" #define UNICODE_RIGHT_SQUARE_BRACKET_WITH_TICK_IN_BOTTOM_CORNER 0x298e #define UNITEXT_RIGHT_SQUARE_BRACKET_WITH_TICK_IN_BOTTOM_CORNER L"\u298e" #define UNICODE_LEFT_SQUARE_BRACKET_WITH_TICK_IN_BOTTOM_CORNER 0x298f #define UNITEXT_LEFT_SQUARE_BRACKET_WITH_TICK_IN_BOTTOM_CORNER L"\u298f" #define UNICODE_RIGHT_SQUARE_BRACKET_WITH_TICK_IN_TOP_CORNER 0x2990 #define UNITEXT_RIGHT_SQUARE_BRACKET_WITH_TICK_IN_TOP_CORNER L"\u2990" #define UNICODE_LEFT_ANGLE_BRACKET_WITH_DOT 0x2991 #define UNITEXT_LEFT_ANGLE_BRACKET_WITH_DOT L"\u2991" #define UNICODE_RIGHT_ANGLE_BRACKET_WITH_DOT 0x2992 #define UNITEXT_RIGHT_ANGLE_BRACKET_WITH_DOT L"\u2992" #define UNICODE_LEFT_ARC_LESS_THAN_BRACKET 0x2993 #define UNITEXT_LEFT_ARC_LESS_THAN_BRACKET L"\u2993" #define UNICODE_RIGHT_ARC_GREATER_THAN_BRACKET 0x2994 #define UNITEXT_RIGHT_ARC_GREATER_THAN_BRACKET L"\u2994" #define UNICODE_DOUBLE_LEFT_ARC_GREATER_THAN_BRACKET 0x2995 #define UNITEXT_DOUBLE_LEFT_ARC_GREATER_THAN_BRACKET L"\u2995" #define UNICODE_DOUBLE_RIGHT_ARC_LESS_THAN_BRACKET 0x2996 #define UNITEXT_DOUBLE_RIGHT_ARC_LESS_THAN_BRACKET L"\u2996" #define UNICODE_LEFT_BLACK_TORTOISE_SHELL_BRACKET 0x2997 #define UNITEXT_LEFT_BLACK_TORTOISE_SHELL_BRACKET L"\u2997" #define UNICODE_RIGHT_BLACK_TORTOISE_SHELL_BRACKET 0x2998 #define UNITEXT_RIGHT_BLACK_TORTOISE_SHELL_BRACKET L"\u2998" #define UNICODE_DOTTED_FENCE 0x2999 #define UNITEXT_DOTTED_FENCE L"\u2999" #define UNICODE_VERTICAL_ZIGZAG_LINE 0x299a #define UNITEXT_VERTICAL_ZIGZAG_LINE L"\u299a" #define UNICODE_MEASURED_ANGLE_OPENING_LEFT 0x299b #define UNITEXT_MEASURED_ANGLE_OPENING_LEFT L"\u299b" #define UNICODE_RIGHT_ANGLE_VARIANT_WITH_SQUARE 0x299c #define UNITEXT_RIGHT_ANGLE_VARIANT_WITH_SQUARE L"\u299c" #define UNICODE_MEASURED_RIGHT_ANGLE_WITH_DOT 0x299d #define UNITEXT_MEASURED_RIGHT_ANGLE_WITH_DOT L"\u299d" #define UNICODE_ANGLE_WITH_S_INSIDE 0x299e #define UNITEXT_ANGLE_WITH_S_INSIDE L"\u299e" #define UNICODE_ACUTE_ANGLE 0x299f #define UNITEXT_ACUTE_ANGLE L"\u299f" #define UNICODE_SPHERICAL_ANGLE_OPENING_LEFT 0x29a0 #define UNITEXT_SPHERICAL_ANGLE_OPENING_LEFT L"\u29a0" #define UNICODE_SPHERICAL_ANGLE_OPENING_UP 0x29a1 #define UNITEXT_SPHERICAL_ANGLE_OPENING_UP L"\u29a1" #define UNICODE_TURNED_ANGLE 0x29a2 #define UNITEXT_TURNED_ANGLE L"\u29a2" #define UNICODE_REVERSED_ANGLE 0x29a3 #define UNITEXT_REVERSED_ANGLE L"\u29a3" #define UNICODE_ANGLE_WITH_UNDERBAR 0x29a4 #define UNITEXT_ANGLE_WITH_UNDERBAR L"\u29a4" #define UNICODE_REVERSED_ANGLE_WITH_UNDERBAR 0x29a5 #define UNITEXT_REVERSED_ANGLE_WITH_UNDERBAR L"\u29a5" #define UNICODE_OBLIQUE_ANGLE_OPENING_UP 0x29a6 #define UNITEXT_OBLIQUE_ANGLE_OPENING_UP L"\u29a6" #define UNICODE_OBLIQUE_ANGLE_OPENING_DOWN 0x29a7 #define UNITEXT_OBLIQUE_ANGLE_OPENING_DOWN L"\u29a7" #define UNICODE_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_UP_AND_RIGHT 0x29a8 #define UNITEXT_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_UP_AND_RIGHT L"\u29a8" #define UNICODE_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_UP_AND_LEFT 0x29a9 #define UNITEXT_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_UP_AND_LEFT L"\u29a9" #define UNICODE_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_DOWN_AND_RIGHT 0x29aa #define UNITEXT_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_DOWN_AND_RIGHT L"\u29aa" #define UNICODE_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_DOWN_AND_LEFT 0x29ab #define UNITEXT_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_DOWN_AND_LEFT L"\u29ab" #define UNICODE_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_RIGHT_AND_UP 0x29ac #define UNITEXT_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_RIGHT_AND_UP L"\u29ac" #define UNICODE_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_LEFT_AND_UP 0x29ad #define UNITEXT_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_LEFT_AND_UP L"\u29ad" #define UNICODE_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_RIGHT_AND_DOWN 0x29ae #define UNITEXT_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_RIGHT_AND_DOWN L"\u29ae" #define UNICODE_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_LEFT_AND_DOWN 0x29af #define UNITEXT_MEASURED_ANGLE_WITH_OPEN_ARM_ENDING_IN_ARROW_POINTING_LEFT_AND_DOWN L"\u29af" #define UNICODE_REVERSED_EMPTY_SET 0x29b0 #define UNITEXT_REVERSED_EMPTY_SET L"\u29b0" #define UNICODE_EMPTY_SET_WITH_OVERBAR 0x29b1 #define UNITEXT_EMPTY_SET_WITH_OVERBAR L"\u29b1" #define UNICODE_EMPTY_SET_WITH_SMALL_CIRCLE_ABOVE 0x29b2 #define UNITEXT_EMPTY_SET_WITH_SMALL_CIRCLE_ABOVE L"\u29b2" #define UNICODE_EMPTY_SET_WITH_RIGHT_ARROW_ABOVE 0x29b3 #define UNITEXT_EMPTY_SET_WITH_RIGHT_ARROW_ABOVE L"\u29b3" #define UNICODE_EMPTY_SET_WITH_LEFT_ARROW_ABOVE 0x29b4 #define UNITEXT_EMPTY_SET_WITH_LEFT_ARROW_ABOVE L"\u29b4" #define UNICODE_CIRCLE_WITH_HORIZONTAL_BAR 0x29b5 #define UNITEXT_CIRCLE_WITH_HORIZONTAL_BAR L"\u29b5" #define UNICODE_CIRCLED_VERTICAL_BAR 0x29b6 #define UNITEXT_CIRCLED_VERTICAL_BAR L"\u29b6" #define UNICODE_CIRCLED_PARALLEL 0x29b7 #define UNITEXT_CIRCLED_PARALLEL L"\u29b7" #define UNICODE_CIRCLED_REVERSE_SOLIDUS 0x29b8 #define UNITEXT_CIRCLED_REVERSE_SOLIDUS L"\u29b8" #define UNICODE_CIRCLED_PERPENDICULAR 0x29b9 #define UNITEXT_CIRCLED_PERPENDICULAR L"\u29b9" #define UNICODE_CIRCLE_DIVIDED_BY_HORIZONTAL_BAR_AND_TOP_HALF_DIVIDED_BY_VERTICAL_BAR 0x29ba #define UNITEXT_CIRCLE_DIVIDED_BY_HORIZONTAL_BAR_AND_TOP_HALF_DIVIDED_BY_VERTICAL_BAR L"\u29ba" #define UNICODE_CIRCLE_WITH_SUPERIMPOSED_X 0x29bb #define UNITEXT_CIRCLE_WITH_SUPERIMPOSED_X L"\u29bb" #define UNICODE_CIRCLED_ANTICLOCKWISE_ROTATED_DIVISION_SIGN 0x29bc #define UNITEXT_CIRCLED_ANTICLOCKWISE_ROTATED_DIVISION_SIGN L"\u29bc" #define UNICODE_UP_ARROW_THROUGH_CIRCLE 0x29bd #define UNITEXT_UP_ARROW_THROUGH_CIRCLE L"\u29bd" #define UNICODE_CIRCLED_WHITE_BULLET 0x29be #define UNITEXT_CIRCLED_WHITE_BULLET L"\u29be" #define UNICODE_CIRCLED_BULLET 0x29bf #define UNITEXT_CIRCLED_BULLET L"\u29bf" #define UNICODE_CIRCLED_LESS_THAN 0x29c0 #define UNITEXT_CIRCLED_LESS_THAN L"\u29c0" #define UNICODE_CIRCLED_GREATER_THAN 0x29c1 #define UNITEXT_CIRCLED_GREATER_THAN L"\u29c1" #define UNICODE_CIRCLE_WITH_SMALL_CIRCLE_TO_THE_RIGHT 0x29c2 #define UNITEXT_CIRCLE_WITH_SMALL_CIRCLE_TO_THE_RIGHT L"\u29c2" #define UNICODE_CIRCLE_WITH_TWO_HORIZONTAL_STROKES_TO_THE_RIGHT 0x29c3 #define UNITEXT_CIRCLE_WITH_TWO_HORIZONTAL_STROKES_TO_THE_RIGHT L"\u29c3" #define UNICODE_SQUARED_RISING_DIAGONAL_SLASH 0x29c4 #define UNITEXT_SQUARED_RISING_DIAGONAL_SLASH L"\u29c4" #define UNICODE_SQUARED_FALLING_DIAGONAL_SLASH 0x29c5 #define UNITEXT_SQUARED_FALLING_DIAGONAL_SLASH L"\u29c5" #define UNICODE_SQUARED_ASTERISK 0x29c6 #define UNITEXT_SQUARED_ASTERISK L"\u29c6" #define UNICODE_SQUARED_SMALL_CIRCLE 0x29c7 #define UNITEXT_SQUARED_SMALL_CIRCLE L"\u29c7" #define UNICODE_SQUARED_SQUARE 0x29c8 #define UNITEXT_SQUARED_SQUARE L"\u29c8" #define UNICODE_TWO_JOINED_SQUARES 0x29c9 #define UNITEXT_TWO_JOINED_SQUARES L"\u29c9" #define UNICODE_TRIANGLE_WITH_DOT_ABOVE 0x29ca #define UNITEXT_TRIANGLE_WITH_DOT_ABOVE L"\u29ca" #define UNICODE_TRIANGLE_WITH_UNDERBAR 0x29cb #define UNITEXT_TRIANGLE_WITH_UNDERBAR L"\u29cb" #define UNICODE_S_IN_TRIANGLE 0x29cc #define UNITEXT_S_IN_TRIANGLE L"\u29cc" #define UNICODE_TRIANGLE_WITH_SERIFS_AT_BOTTOM 0x29cd #define UNITEXT_TRIANGLE_WITH_SERIFS_AT_BOTTOM L"\u29cd" #define UNICODE_RIGHT_TRIANGLE_ABOVE_LEFT_TRIANGLE 0x29ce #define UNITEXT_RIGHT_TRIANGLE_ABOVE_LEFT_TRIANGLE L"\u29ce" #define UNICODE_LEFT_TRIANGLE_BESIDE_VERTICAL_BAR 0x29cf #define UNITEXT_LEFT_TRIANGLE_BESIDE_VERTICAL_BAR L"\u29cf" #define UNICODE_VERTICAL_BAR_BESIDE_RIGHT_TRIANGLE 0x29d0 #define UNITEXT_VERTICAL_BAR_BESIDE_RIGHT_TRIANGLE L"\u29d0" #define UNICODE_BOWTIE_WITH_LEFT_HALF_BLACK 0x29d1 #define UNITEXT_BOWTIE_WITH_LEFT_HALF_BLACK L"\u29d1" #define UNICODE_BOWTIE_WITH_RIGHT_HALF_BLACK 0x29d2 #define UNITEXT_BOWTIE_WITH_RIGHT_HALF_BLACK L"\u29d2" #define UNICODE_BLACK_BOWTIE 0x29d3 #define UNITEXT_BLACK_BOWTIE L"\u29d3" #define UNICODE_TIMES_WITH_LEFT_HALF_BLACK 0x29d4 #define UNITEXT_TIMES_WITH_LEFT_HALF_BLACK L"\u29d4" #define UNICODE_TIMES_WITH_RIGHT_HALF_BLACK 0x29d5 #define UNITEXT_TIMES_WITH_RIGHT_HALF_BLACK L"\u29d5" #define UNICODE_WHITE_HOURGLASS 0x29d6 #define UNITEXT_WHITE_HOURGLASS L"\u29d6" #define UNICODE_BLACK_HOURGLASS 0x29d7 #define UNITEXT_BLACK_HOURGLASS L"\u29d7" #define UNICODE_LEFT_WIGGLY_FENCE 0x29d8 #define UNITEXT_LEFT_WIGGLY_FENCE L"\u29d8" #define UNICODE_RIGHT_WIGGLY_FENCE 0x29d9 #define UNITEXT_RIGHT_WIGGLY_FENCE L"\u29d9" #define UNICODE_LEFT_DOUBLE_WIGGLY_FENCE 0x29da #define UNITEXT_LEFT_DOUBLE_WIGGLY_FENCE L"\u29da" #define UNICODE_RIGHT_DOUBLE_WIGGLY_FENCE 0x29db #define UNITEXT_RIGHT_DOUBLE_WIGGLY_FENCE L"\u29db" #define UNICODE_INCOMPLETE_INFINITY 0x29dc #define UNITEXT_INCOMPLETE_INFINITY L"\u29dc" #define UNICODE_TIE_OVER_INFINITY 0x29dd #define UNITEXT_TIE_OVER_INFINITY L"\u29dd" #define UNICODE_INFINITY_NEGATED_WITH_VERTICAL_BAR 0x29de #define UNITEXT_INFINITY_NEGATED_WITH_VERTICAL_BAR L"\u29de" #define UNICODE_DOUBLE_ENDED_MULTIMAP 0x29df #define UNITEXT_DOUBLE_ENDED_MULTIMAP L"\u29df" #define UNICODE_SQUARE_WITH_CONTOURED_OUTLINE 0x29e0 #define UNITEXT_SQUARE_WITH_CONTOURED_OUTLINE L"\u29e0" #define UNICODE_INCREASES_AS 0x29e1 #define UNITEXT_INCREASES_AS L"\u29e1" #define UNICODE_SHUFFLE_PRODUCT 0x29e2 #define UNITEXT_SHUFFLE_PRODUCT L"\u29e2" #define UNICODE_EQUALS_SIGN_AND_SLANTED_PARALLEL 0x29e3 #define UNITEXT_EQUALS_SIGN_AND_SLANTED_PARALLEL L"\u29e3" #define UNICODE_EQUALS_SIGN_AND_SLANTED_PARALLEL_WITH_TILDE_ABOVE 0x29e4 #define UNITEXT_EQUALS_SIGN_AND_SLANTED_PARALLEL_WITH_TILDE_ABOVE L"\u29e4" #define UNICODE_IDENTICAL_TO_AND_SLANTED_PARALLEL 0x29e5 #define UNITEXT_IDENTICAL_TO_AND_SLANTED_PARALLEL L"\u29e5" #define UNICODE_GLEICH_STARK 0x29e6 #define UNITEXT_GLEICH_STARK L"\u29e6" #define UNICODE_THERMODYNAMIC 0x29e7 #define UNITEXT_THERMODYNAMIC L"\u29e7" #define UNICODE_DOWN_POINTING_TRIANGLE_WITH_LEFT_HALF_BLACK 0x29e8 #define UNITEXT_DOWN_POINTING_TRIANGLE_WITH_LEFT_HALF_BLACK L"\u29e8" #define UNICODE_DOWN_POINTING_TRIANGLE_WITH_RIGHT_HALF_BLACK 0x29e9 #define UNITEXT_DOWN_POINTING_TRIANGLE_WITH_RIGHT_HALF_BLACK L"\u29e9" #define UNICODE_BLACK_DIAMOND_WITH_DOWN_ARROW 0x29ea #define UNITEXT_BLACK_DIAMOND_WITH_DOWN_ARROW L"\u29ea" #define UNICODE_BLACK_LOZENGE 0x29eb #define UNITEXT_BLACK_LOZENGE L"\u29eb" #define UNICODE_WHITE_CIRCLE_WITH_DOWN_ARROW 0x29ec #define UNITEXT_WHITE_CIRCLE_WITH_DOWN_ARROW L"\u29ec" #define UNICODE_BLACK_CIRCLE_WITH_DOWN_ARROW 0x29ed #define UNITEXT_BLACK_CIRCLE_WITH_DOWN_ARROW L"\u29ed" #define UNICODE_ERROR_BARRED_WHITE_SQUARE 0x29ee #define UNITEXT_ERROR_BARRED_WHITE_SQUARE L"\u29ee" #define UNICODE_ERROR_BARRED_BLACK_SQUARE 0x29ef #define UNITEXT_ERROR_BARRED_BLACK_SQUARE L"\u29ef" #define UNICODE_ERROR_BARRED_WHITE_DIAMOND 0x29f0 #define UNITEXT_ERROR_BARRED_WHITE_DIAMOND L"\u29f0" #define UNICODE_ERROR_BARRED_BLACK_DIAMOND 0x29f1 #define UNITEXT_ERROR_BARRED_BLACK_DIAMOND L"\u29f1" #define UNICODE_ERROR_BARRED_WHITE_CIRCLE 0x29f2 #define UNITEXT_ERROR_BARRED_WHITE_CIRCLE L"\u29f2" #define UNICODE_ERROR_BARRED_BLACK_CIRCLE 0x29f3 #define UNITEXT_ERROR_BARRED_BLACK_CIRCLE L"\u29f3" #define UNICODE_RULE_DELAYED 0x29f4 #define UNITEXT_RULE_DELAYED L"\u29f4" #define UNICODE_REVERSE_SOLIDUS_OPERATOR 0x29f5 #define UNITEXT_REVERSE_SOLIDUS_OPERATOR L"\u29f5" #define UNICODE_SOLIDUS_WITH_OVERBAR 0x29f6 #define UNITEXT_SOLIDUS_WITH_OVERBAR L"\u29f6" #define UNICODE_REVERSE_SOLIDUS_WITH_HORIZONTAL_STROKE 0x29f7 #define UNITEXT_REVERSE_SOLIDUS_WITH_HORIZONTAL_STROKE L"\u29f7" #define UNICODE_BIG_SOLIDUS 0x29f8 #define UNITEXT_BIG_SOLIDUS L"\u29f8" #define UNICODE_BIG_REVERSE_SOLIDUS 0x29f9 #define UNITEXT_BIG_REVERSE_SOLIDUS L"\u29f9" #define UNICODE_DOUBLE_PLUS 0x29fa #define UNITEXT_DOUBLE_PLUS L"\u29fa" #define UNICODE_TRIPLE_PLUS 0x29fb #define UNITEXT_TRIPLE_PLUS L"\u29fb" #define UNICODE_LEFT_POINTING_CURVED_ANGLE_BRACKET 0x29fc #define UNITEXT_LEFT_POINTING_CURVED_ANGLE_BRACKET L"\u29fc" #define UNICODE_RIGHT_POINTING_CURVED_ANGLE_BRACKET 0x29fd #define UNITEXT_RIGHT_POINTING_CURVED_ANGLE_BRACKET L"\u29fd" #define UNICODE_TINY 0x29fe #define UNITEXT_TINY L"\u29fe" #define UNICODE_MINY 0x29ff #define UNITEXT_MINY L"\u29ff" #define UNICODE_N_ARY_CIRCLED_DOT_OPERATOR 0x2a00 #define UNITEXT_N_ARY_CIRCLED_DOT_OPERATOR L"\u2a00" #define UNICODE_N_ARY_CIRCLED_PLUS_OPERATOR 0x2a01 #define UNITEXT_N_ARY_CIRCLED_PLUS_OPERATOR L"\u2a01" #define UNICODE_N_ARY_CIRCLED_TIMES_OPERATOR 0x2a02 #define UNITEXT_N_ARY_CIRCLED_TIMES_OPERATOR L"\u2a02" #define UNICODE_N_ARY_UNION_OPERATOR_WITH_DOT 0x2a03 #define UNITEXT_N_ARY_UNION_OPERATOR_WITH_DOT L"\u2a03" #define UNICODE_N_ARY_UNION_OPERATOR_WITH_PLUS 0x2a04 #define UNITEXT_N_ARY_UNION_OPERATOR_WITH_PLUS L"\u2a04" #define UNICODE_N_ARY_SQUARE_INTERSECTION_OPERATOR 0x2a05 #define UNITEXT_N_ARY_SQUARE_INTERSECTION_OPERATOR L"\u2a05" #define UNICODE_N_ARY_SQUARE_UNION_OPERATOR 0x2a06 #define UNITEXT_N_ARY_SQUARE_UNION_OPERATOR L"\u2a06" #define UNICODE_TWO_LOGICAL_AND_OPERATOR 0x2a07 #define UNITEXT_TWO_LOGICAL_AND_OPERATOR L"\u2a07" #define UNICODE_TWO_LOGICAL_OR_OPERATOR 0x2a08 #define UNITEXT_TWO_LOGICAL_OR_OPERATOR L"\u2a08" #define UNICODE_N_ARY_TIMES_OPERATOR 0x2a09 #define UNITEXT_N_ARY_TIMES_OPERATOR L"\u2a09" #define UNICODE_MODULO_TWO_SUM 0x2a0a #define UNITEXT_MODULO_TWO_SUM L"\u2a0a" #define UNICODE_SUMMATION_WITH_INTEGRAL 0x2a0b #define UNITEXT_SUMMATION_WITH_INTEGRAL L"\u2a0b" #define UNICODE_QUADRUPLE_INTEGRAL_OPERATOR 0x2a0c #define UNITEXT_QUADRUPLE_INTEGRAL_OPERATOR L"\u2a0c" #define UNICODE_FINITE_PART_INTEGRAL 0x2a0d #define UNITEXT_FINITE_PART_INTEGRAL L"\u2a0d" #define UNICODE_INTEGRAL_WITH_DOUBLE_STROKE 0x2a0e #define UNITEXT_INTEGRAL_WITH_DOUBLE_STROKE L"\u2a0e" #define UNICODE_INTEGRAL_AVERAGE_WITH_SLASH 0x2a0f #define UNITEXT_INTEGRAL_AVERAGE_WITH_SLASH L"\u2a0f" #define UNICODE_CIRCULATION_FUNCTION 0x2a10 #define UNITEXT_CIRCULATION_FUNCTION L"\u2a10" #define UNICODE_ANTICLOCKWISE_INTEGRATION 0x2a11 #define UNITEXT_ANTICLOCKWISE_INTEGRATION L"\u2a11" #define UNICODE_LINE_INTEGRATION_WITH_RECTANGULAR_PATH_AROUND_POLE 0x2a12 #define UNITEXT_LINE_INTEGRATION_WITH_RECTANGULAR_PATH_AROUND_POLE L"\u2a12" #define UNICODE_LINE_INTEGRATION_WITH_SEMICIRCULAR_PATH_AROUND_POLE 0x2a13 #define UNITEXT_LINE_INTEGRATION_WITH_SEMICIRCULAR_PATH_AROUND_POLE L"\u2a13" #define UNICODE_LINE_INTEGRATION_NOT_INCLUDING_THE_POLE 0x2a14 #define UNITEXT_LINE_INTEGRATION_NOT_INCLUDING_THE_POLE L"\u2a14" #define UNICODE_INTEGRAL_AROUND_A_POINT_OPERATOR 0x2a15 #define UNITEXT_INTEGRAL_AROUND_A_POINT_OPERATOR L"\u2a15" #define UNICODE_QUATERNION_INTEGRAL_OPERATOR 0x2a16 #define UNITEXT_QUATERNION_INTEGRAL_OPERATOR L"\u2a16" #define UNICODE_INTEGRAL_WITH_LEFTWARDS_ARROW_WITH_HOOK 0x2a17 #define UNITEXT_INTEGRAL_WITH_LEFTWARDS_ARROW_WITH_HOOK L"\u2a17" #define UNICODE_INTEGRAL_WITH_TIMES_SIGN 0x2a18 #define UNITEXT_INTEGRAL_WITH_TIMES_SIGN L"\u2a18" #define UNICODE_INTEGRAL_WITH_INTERSECTION 0x2a19 #define UNITEXT_INTEGRAL_WITH_INTERSECTION L"\u2a19" #define UNICODE_INTEGRAL_WITH_UNION 0x2a1a #define UNITEXT_INTEGRAL_WITH_UNION L"\u2a1a" #define UNICODE_INTEGRAL_WITH_OVERBAR 0x2a1b #define UNITEXT_INTEGRAL_WITH_OVERBAR L"\u2a1b" #define UNICODE_INTEGRAL_WITH_UNDERBAR 0x2a1c #define UNITEXT_INTEGRAL_WITH_UNDERBAR L"\u2a1c" #define UNICODE_JOIN 0x2a1d #define UNITEXT_JOIN L"\u2a1d" #define UNICODE_LARGE_LEFT_TRIANGLE_OPERATOR 0x2a1e #define UNITEXT_LARGE_LEFT_TRIANGLE_OPERATOR L"\u2a1e" #define UNICODE_Z_NOTATION_SCHEMA_COMPOSITION 0x2a1f #define UNITEXT_Z_NOTATION_SCHEMA_COMPOSITION L"\u2a1f" #define UNICODE_Z_NOTATION_SCHEMA_PIPING 0x2a20 #define UNITEXT_Z_NOTATION_SCHEMA_PIPING L"\u2a20" #define UNICODE_Z_NOTATION_SCHEMA_PROJECTION 0x2a21 #define UNITEXT_Z_NOTATION_SCHEMA_PROJECTION L"\u2a21" #define UNICODE_PLUS_SIGN_WITH_SMALL_CIRCLE_ABOVE 0x2a22 #define UNITEXT_PLUS_SIGN_WITH_SMALL_CIRCLE_ABOVE L"\u2a22" #define UNICODE_PLUS_SIGN_WITH_CIRCUMFLEX_ACCENT_ABOVE 0x2a23 #define UNITEXT_PLUS_SIGN_WITH_CIRCUMFLEX_ACCENT_ABOVE L"\u2a23" #define UNICODE_PLUS_SIGN_WITH_TILDE_ABOVE 0x2a24 #define UNITEXT_PLUS_SIGN_WITH_TILDE_ABOVE L"\u2a24" #define UNICODE_PLUS_SIGN_WITH_DOT_BELOW 0x2a25 #define UNITEXT_PLUS_SIGN_WITH_DOT_BELOW L"\u2a25" #define UNICODE_PLUS_SIGN_WITH_TILDE_BELOW 0x2a26 #define UNITEXT_PLUS_SIGN_WITH_TILDE_BELOW L"\u2a26" #define UNICODE_PLUS_SIGN_WITH_SUBSCRIPT_TWO 0x2a27 #define UNITEXT_PLUS_SIGN_WITH_SUBSCRIPT_TWO L"\u2a27" #define UNICODE_PLUS_SIGN_WITH_BLACK_TRIANGLE 0x2a28 #define UNITEXT_PLUS_SIGN_WITH_BLACK_TRIANGLE L"\u2a28" #define UNICODE_MINUS_SIGN_WITH_COMMA_ABOVE 0x2a29 #define UNITEXT_MINUS_SIGN_WITH_COMMA_ABOVE L"\u2a29" #define UNICODE_MINUS_SIGN_WITH_DOT_BELOW 0x2a2a #define UNITEXT_MINUS_SIGN_WITH_DOT_BELOW L"\u2a2a" #define UNICODE_MINUS_SIGN_WITH_FALLING_DOTS 0x2a2b #define UNITEXT_MINUS_SIGN_WITH_FALLING_DOTS L"\u2a2b" #define UNICODE_MINUS_SIGN_WITH_RISING_DOTS 0x2a2c #define UNITEXT_MINUS_SIGN_WITH_RISING_DOTS L"\u2a2c" #define UNICODE_PLUS_SIGN_IN_LEFT_HALF_CIRCLE 0x2a2d #define UNITEXT_PLUS_SIGN_IN_LEFT_HALF_CIRCLE L"\u2a2d" #define UNICODE_PLUS_SIGN_IN_RIGHT_HALF_CIRCLE 0x2a2e #define UNITEXT_PLUS_SIGN_IN_RIGHT_HALF_CIRCLE L"\u2a2e" #define UNICODE_VECTOR_OR_CROSS_PRODUCT 0x2a2f #define UNITEXT_VECTOR_OR_CROSS_PRODUCT L"\u2a2f" #define UNICODE_MULTIPLICATION_SIGN_WITH_DOT_ABOVE 0x2a30 #define UNITEXT_MULTIPLICATION_SIGN_WITH_DOT_ABOVE L"\u2a30" #define UNICODE_MULTIPLICATION_SIGN_WITH_UNDERBAR 0x2a31 #define UNITEXT_MULTIPLICATION_SIGN_WITH_UNDERBAR L"\u2a31" #define UNICODE_SEMIDIRECT_PRODUCT_WITH_BOTTOM_CLOSED 0x2a32 #define UNITEXT_SEMIDIRECT_PRODUCT_WITH_BOTTOM_CLOSED L"\u2a32" #define UNICODE_SMASH_PRODUCT 0x2a33 #define UNITEXT_SMASH_PRODUCT L"\u2a33" #define UNICODE_MULTIPLICATION_SIGN_IN_LEFT_HALF_CIRCLE 0x2a34 #define UNITEXT_MULTIPLICATION_SIGN_IN_LEFT_HALF_CIRCLE L"\u2a34" #define UNICODE_MULTIPLICATION_SIGN_IN_RIGHT_HALF_CIRCLE 0x2a35 #define UNITEXT_MULTIPLICATION_SIGN_IN_RIGHT_HALF_CIRCLE L"\u2a35" #define UNICODE_CIRCLED_MULTIPLICATION_SIGN_WITH_CIRCUMFLEX_ACCENT 0x2a36 #define UNITEXT_CIRCLED_MULTIPLICATION_SIGN_WITH_CIRCUMFLEX_ACCENT L"\u2a36" #define UNICODE_MULTIPLICATION_SIGN_IN_DOUBLE_CIRCLE 0x2a37 #define UNITEXT_MULTIPLICATION_SIGN_IN_DOUBLE_CIRCLE L"\u2a37" #define UNICODE_CIRCLED_DIVISION_SIGN 0x2a38 #define UNITEXT_CIRCLED_DIVISION_SIGN L"\u2a38" #define UNICODE_PLUS_SIGN_IN_TRIANGLE 0x2a39 #define UNITEXT_PLUS_SIGN_IN_TRIANGLE L"\u2a39" #define UNICODE_MINUS_SIGN_IN_TRIANGLE 0x2a3a #define UNITEXT_MINUS_SIGN_IN_TRIANGLE L"\u2a3a" #define UNICODE_MULTIPLICATION_SIGN_IN_TRIANGLE 0x2a3b #define UNITEXT_MULTIPLICATION_SIGN_IN_TRIANGLE L"\u2a3b" #define UNICODE_INTERIOR_PRODUCT 0x2a3c #define UNITEXT_INTERIOR_PRODUCT L"\u2a3c" #define UNICODE_RIGHTHAND_INTERIOR_PRODUCT 0x2a3d #define UNITEXT_RIGHTHAND_INTERIOR_PRODUCT L"\u2a3d" #define UNICODE_Z_NOTATION_RELATIONAL_COMPOSITION 0x2a3e #define UNITEXT_Z_NOTATION_RELATIONAL_COMPOSITION L"\u2a3e" #define UNICODE_AMALGAMATION_OR_COPRODUCT 0x2a3f #define UNITEXT_AMALGAMATION_OR_COPRODUCT L"\u2a3f" #define UNICODE_INTERSECTION_WITH_DOT 0x2a40 #define UNITEXT_INTERSECTION_WITH_DOT L"\u2a40" #define UNICODE_UNION_WITH_MINUS_SIGN 0x2a41 #define UNITEXT_UNION_WITH_MINUS_SIGN L"\u2a41" #define UNICODE_UNION_WITH_OVERBAR 0x2a42 #define UNITEXT_UNION_WITH_OVERBAR L"\u2a42" #define UNICODE_INTERSECTION_WITH_OVERBAR 0x2a43 #define UNITEXT_INTERSECTION_WITH_OVERBAR L"\u2a43" #define UNICODE_INTERSECTION_WITH_LOGICAL_AND 0x2a44 #define UNITEXT_INTERSECTION_WITH_LOGICAL_AND L"\u2a44" #define UNICODE_UNION_WITH_LOGICAL_OR 0x2a45 #define UNITEXT_UNION_WITH_LOGICAL_OR L"\u2a45" #define UNICODE_UNION_ABOVE_INTERSECTION 0x2a46 #define UNITEXT_UNION_ABOVE_INTERSECTION L"\u2a46" #define UNICODE_INTERSECTION_ABOVE_UNION 0x2a47 #define UNITEXT_INTERSECTION_ABOVE_UNION L"\u2a47" #define UNICODE_UNION_ABOVE_BAR_ABOVE_INTERSECTION 0x2a48 #define UNITEXT_UNION_ABOVE_BAR_ABOVE_INTERSECTION L"\u2a48" #define UNICODE_INTERSECTION_ABOVE_BAR_ABOVE_UNION 0x2a49 #define UNITEXT_INTERSECTION_ABOVE_BAR_ABOVE_UNION L"\u2a49" #define UNICODE_UNION_BESIDE_AND_JOINED_WITH_UNION 0x2a4a #define UNITEXT_UNION_BESIDE_AND_JOINED_WITH_UNION L"\u2a4a" #define UNICODE_INTERSECTION_BESIDE_AND_JOINED_WITH_INTERSECTION 0x2a4b #define UNITEXT_INTERSECTION_BESIDE_AND_JOINED_WITH_INTERSECTION L"\u2a4b" #define UNICODE_CLOSED_UNION_WITH_SERIFS 0x2a4c #define UNITEXT_CLOSED_UNION_WITH_SERIFS L"\u2a4c" #define UNICODE_CLOSED_INTERSECTION_WITH_SERIFS 0x2a4d #define UNITEXT_CLOSED_INTERSECTION_WITH_SERIFS L"\u2a4d" #define UNICODE_DOUBLE_SQUARE_INTERSECTION 0x2a4e #define UNITEXT_DOUBLE_SQUARE_INTERSECTION L"\u2a4e" #define UNICODE_DOUBLE_SQUARE_UNION 0x2a4f #define UNITEXT_DOUBLE_SQUARE_UNION L"\u2a4f" #define UNICODE_CLOSED_UNION_WITH_SERIFS_AND_SMASH_PRODUCT 0x2a50 #define UNITEXT_CLOSED_UNION_WITH_SERIFS_AND_SMASH_PRODUCT L"\u2a50" #define UNICODE_LOGICAL_AND_WITH_DOT_ABOVE 0x2a51 #define UNITEXT_LOGICAL_AND_WITH_DOT_ABOVE L"\u2a51" #define UNICODE_LOGICAL_OR_WITH_DOT_ABOVE 0x2a52 #define UNITEXT_LOGICAL_OR_WITH_DOT_ABOVE L"\u2a52" #define UNICODE_DOUBLE_LOGICAL_AND 0x2a53 #define UNITEXT_DOUBLE_LOGICAL_AND L"\u2a53" #define UNICODE_DOUBLE_LOGICAL_OR 0x2a54 #define UNITEXT_DOUBLE_LOGICAL_OR L"\u2a54" #define UNICODE_TWO_INTERSECTING_LOGICAL_AND 0x2a55 #define UNITEXT_TWO_INTERSECTING_LOGICAL_AND L"\u2a55" #define UNICODE_TWO_INTERSECTING_LOGICAL_OR 0x2a56 #define UNITEXT_TWO_INTERSECTING_LOGICAL_OR L"\u2a56" #define UNICODE_SLOPING_LARGE_OR 0x2a57 #define UNITEXT_SLOPING_LARGE_OR L"\u2a57" #define UNICODE_SLOPING_LARGE_AND 0x2a58 #define UNITEXT_SLOPING_LARGE_AND L"\u2a58" #define UNICODE_LOGICAL_OR_OVERLAPPING_LOGICAL_AND 0x2a59 #define UNITEXT_LOGICAL_OR_OVERLAPPING_LOGICAL_AND L"\u2a59" #define UNICODE_LOGICAL_AND_WITH_MIDDLE_STEM 0x2a5a #define UNITEXT_LOGICAL_AND_WITH_MIDDLE_STEM L"\u2a5a" #define UNICODE_LOGICAL_OR_WITH_MIDDLE_STEM 0x2a5b #define UNITEXT_LOGICAL_OR_WITH_MIDDLE_STEM L"\u2a5b" #define UNICODE_LOGICAL_AND_WITH_HORIZONTAL_DASH 0x2a5c #define UNITEXT_LOGICAL_AND_WITH_HORIZONTAL_DASH L"\u2a5c" #define UNICODE_LOGICAL_OR_WITH_HORIZONTAL_DASH 0x2a5d #define UNITEXT_LOGICAL_OR_WITH_HORIZONTAL_DASH L"\u2a5d" #define UNICODE_LOGICAL_AND_WITH_DOUBLE_OVERBAR 0x2a5e #define UNITEXT_LOGICAL_AND_WITH_DOUBLE_OVERBAR L"\u2a5e" #define UNICODE_LOGICAL_AND_WITH_UNDERBAR 0x2a5f #define UNITEXT_LOGICAL_AND_WITH_UNDERBAR L"\u2a5f" #define UNICODE_LOGICAL_AND_WITH_DOUBLE_UNDERBAR 0x2a60 #define UNITEXT_LOGICAL_AND_WITH_DOUBLE_UNDERBAR L"\u2a60" #define UNICODE_SMALL_VEE_WITH_UNDERBAR 0x2a61 #define UNITEXT_SMALL_VEE_WITH_UNDERBAR L"\u2a61" #define UNICODE_LOGICAL_OR_WITH_DOUBLE_OVERBAR 0x2a62 #define UNITEXT_LOGICAL_OR_WITH_DOUBLE_OVERBAR L"\u2a62" #define UNICODE_LOGICAL_OR_WITH_DOUBLE_UNDERBAR 0x2a63 #define UNITEXT_LOGICAL_OR_WITH_DOUBLE_UNDERBAR L"\u2a63" #define UNICODE_Z_NOTATION_DOMAIN_ANTIRESTRICTION 0x2a64 #define UNITEXT_Z_NOTATION_DOMAIN_ANTIRESTRICTION L"\u2a64" #define UNICODE_Z_NOTATION_RANGE_ANTIRESTRICTION 0x2a65 #define UNITEXT_Z_NOTATION_RANGE_ANTIRESTRICTION L"\u2a65" #define UNICODE_EQUALS_SIGN_WITH_DOT_BELOW 0x2a66 #define UNITEXT_EQUALS_SIGN_WITH_DOT_BELOW L"\u2a66" #define UNICODE_IDENTICAL_WITH_DOT_ABOVE 0x2a67 #define UNITEXT_IDENTICAL_WITH_DOT_ABOVE L"\u2a67" #define UNICODE_TRIPLE_HORIZONTAL_BAR_WITH_DOUBLE_VERTICAL_STROKE 0x2a68 #define UNITEXT_TRIPLE_HORIZONTAL_BAR_WITH_DOUBLE_VERTICAL_STROKE L"\u2a68" #define UNICODE_TRIPLE_HORIZONTAL_BAR_WITH_TRIPLE_VERTICAL_STROKE 0x2a69 #define UNITEXT_TRIPLE_HORIZONTAL_BAR_WITH_TRIPLE_VERTICAL_STROKE L"\u2a69" #define UNICODE_TILDE_OPERATOR_WITH_DOT_ABOVE 0x2a6a #define UNITEXT_TILDE_OPERATOR_WITH_DOT_ABOVE L"\u2a6a" #define UNICODE_TILDE_OPERATOR_WITH_RISING_DOTS 0x2a6b #define UNITEXT_TILDE_OPERATOR_WITH_RISING_DOTS L"\u2a6b" #define UNICODE_SIMILAR_MINUS_SIMILAR 0x2a6c #define UNITEXT_SIMILAR_MINUS_SIMILAR L"\u2a6c" #define UNICODE_CONGRUENT_WITH_DOT_ABOVE 0x2a6d #define UNITEXT_CONGRUENT_WITH_DOT_ABOVE L"\u2a6d" #define UNICODE_EQUALS_WITH_ASTERISK 0x2a6e #define UNITEXT_EQUALS_WITH_ASTERISK L"\u2a6e" #define UNICODE_ALMOST_EQUAL_TO_WITH_CIRCUMFLEX_ACCENT 0x2a6f #define UNITEXT_ALMOST_EQUAL_TO_WITH_CIRCUMFLEX_ACCENT L"\u2a6f" #define UNICODE_APPROXIMATELY_EQUAL_OR_EQUAL_TO 0x2a70 #define UNITEXT_APPROXIMATELY_EQUAL_OR_EQUAL_TO L"\u2a70" #define UNICODE_EQUALS_SIGN_ABOVE_PLUS_SIGN 0x2a71 #define UNITEXT_EQUALS_SIGN_ABOVE_PLUS_SIGN L"\u2a71" #define UNICODE_PLUS_SIGN_ABOVE_EQUALS_SIGN 0x2a72 #define UNITEXT_PLUS_SIGN_ABOVE_EQUALS_SIGN L"\u2a72" #define UNICODE_EQUALS_SIGN_ABOVE_TILDE_OPERATOR 0x2a73 #define UNITEXT_EQUALS_SIGN_ABOVE_TILDE_OPERATOR L"\u2a73" #define UNICODE_DOUBLE_COLON_EQUAL 0x2a74 #define UNITEXT_DOUBLE_COLON_EQUAL L"\u2a74" #define UNICODE_TWO_CONSECUTIVE_EQUALS_SIGNS 0x2a75 #define UNITEXT_TWO_CONSECUTIVE_EQUALS_SIGNS L"\u2a75" #define UNICODE_THREE_CONSECUTIVE_EQUALS_SIGNS 0x2a76 #define UNITEXT_THREE_CONSECUTIVE_EQUALS_SIGNS L"\u2a76" #define UNICODE_EQUALS_SIGN_WITH_TWO_DOTS_ABOVE_AND_TWO_DOTS_BELOW 0x2a77 #define UNITEXT_EQUALS_SIGN_WITH_TWO_DOTS_ABOVE_AND_TWO_DOTS_BELOW L"\u2a77" #define UNICODE_EQUIVALENT_WITH_FOUR_DOTS_ABOVE 0x2a78 #define UNITEXT_EQUIVALENT_WITH_FOUR_DOTS_ABOVE L"\u2a78" #define UNICODE_LESS_THAN_WITH_CIRCLE_INSIDE 0x2a79 #define UNITEXT_LESS_THAN_WITH_CIRCLE_INSIDE L"\u2a79" #define UNICODE_GREATER_THAN_WITH_CIRCLE_INSIDE 0x2a7a #define UNITEXT_GREATER_THAN_WITH_CIRCLE_INSIDE L"\u2a7a" #define UNICODE_LESS_THAN_WITH_QUESTION_MARK_ABOVE 0x2a7b #define UNITEXT_LESS_THAN_WITH_QUESTION_MARK_ABOVE L"\u2a7b" #define UNICODE_GREATER_THAN_WITH_QUESTION_MARK_ABOVE 0x2a7c #define UNITEXT_GREATER_THAN_WITH_QUESTION_MARK_ABOVE L"\u2a7c" #define UNICODE_LESS_THAN_OR_SLANTED_EQUAL_TO 0x2a7d #define UNITEXT_LESS_THAN_OR_SLANTED_EQUAL_TO L"\u2a7d" #define UNICODE_GREATER_THAN_OR_SLANTED_EQUAL_TO 0x2a7e #define UNITEXT_GREATER_THAN_OR_SLANTED_EQUAL_TO L"\u2a7e" #define UNICODE_LESS_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_INSIDE 0x2a7f #define UNITEXT_LESS_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_INSIDE L"\u2a7f" #define UNICODE_GREATER_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_INSIDE 0x2a80 #define UNITEXT_GREATER_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_INSIDE L"\u2a80" #define UNICODE_LESS_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_ABOVE 0x2a81 #define UNITEXT_LESS_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_ABOVE L"\u2a81" #define UNICODE_GREATER_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_ABOVE 0x2a82 #define UNITEXT_GREATER_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_ABOVE L"\u2a82" #define UNICODE_LESS_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_ABOVE_RIGHT 0x2a83 #define UNITEXT_LESS_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_ABOVE_RIGHT L"\u2a83" #define UNICODE_GREATER_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_ABOVE_LEFT 0x2a84 #define UNITEXT_GREATER_THAN_OR_SLANTED_EQUAL_TO_WITH_DOT_ABOVE_LEFT L"\u2a84" #define UNICODE_LESS_THAN_OR_APPROXIMATE 0x2a85 #define UNITEXT_LESS_THAN_OR_APPROXIMATE L"\u2a85" #define UNICODE_GREATER_THAN_OR_APPROXIMATE 0x2a86 #define UNITEXT_GREATER_THAN_OR_APPROXIMATE L"\u2a86" #define UNICODE_LESS_THAN_AND_SINGLE_LINE_NOT_EQUAL_TO 0x2a87 #define UNITEXT_LESS_THAN_AND_SINGLE_LINE_NOT_EQUAL_TO L"\u2a87" #define UNICODE_GREATER_THAN_AND_SINGLE_LINE_NOT_EQUAL_TO 0x2a88 #define UNITEXT_GREATER_THAN_AND_SINGLE_LINE_NOT_EQUAL_TO L"\u2a88" #define UNICODE_LESS_THAN_AND_NOT_APPROXIMATE 0x2a89 #define UNITEXT_LESS_THAN_AND_NOT_APPROXIMATE L"\u2a89" #define UNICODE_GREATER_THAN_AND_NOT_APPROXIMATE 0x2a8a #define UNITEXT_GREATER_THAN_AND_NOT_APPROXIMATE L"\u2a8a" #define UNICODE_LESS_THAN_ABOVE_DOUBLE_LINE_EQUAL_ABOVE_GREATER_THAN 0x2a8b #define UNITEXT_LESS_THAN_ABOVE_DOUBLE_LINE_EQUAL_ABOVE_GREATER_THAN L"\u2a8b" #define UNICODE_GREATER_THAN_ABOVE_DOUBLE_LINE_EQUAL_ABOVE_LESS_THAN 0x2a8c #define UNITEXT_GREATER_THAN_ABOVE_DOUBLE_LINE_EQUAL_ABOVE_LESS_THAN L"\u2a8c" #define UNICODE_LESS_THAN_ABOVE_SIMILAR_OR_EQUAL 0x2a8d #define UNITEXT_LESS_THAN_ABOVE_SIMILAR_OR_EQUAL L"\u2a8d" #define UNICODE_GREATER_THAN_ABOVE_SIMILAR_OR_EQUAL 0x2a8e #define UNITEXT_GREATER_THAN_ABOVE_SIMILAR_OR_EQUAL L"\u2a8e" #define UNICODE_LESS_THAN_ABOVE_SIMILAR_ABOVE_GREATER_THAN 0x2a8f #define UNITEXT_LESS_THAN_ABOVE_SIMILAR_ABOVE_GREATER_THAN L"\u2a8f" #define UNICODE_GREATER_THAN_ABOVE_SIMILAR_ABOVE_LESS_THAN 0x2a90 #define UNITEXT_GREATER_THAN_ABOVE_SIMILAR_ABOVE_LESS_THAN L"\u2a90" #define UNICODE_LESS_THAN_ABOVE_GREATER_THAN_ABOVE_DOUBLE_LINE_EQUAL 0x2a91 #define UNITEXT_LESS_THAN_ABOVE_GREATER_THAN_ABOVE_DOUBLE_LINE_EQUAL L"\u2a91" #define UNICODE_GREATER_THAN_ABOVE_LESS_THAN_ABOVE_DOUBLE_LINE_EQUAL 0x2a92 #define UNITEXT_GREATER_THAN_ABOVE_LESS_THAN_ABOVE_DOUBLE_LINE_EQUAL L"\u2a92" #define UNICODE_LESS_THAN_ABOVE_SLANTED_EQUAL_ABOVE_GREATER_THAN_ABOVE_SLANTED_EQUAL 0x2a93 #define UNITEXT_LESS_THAN_ABOVE_SLANTED_EQUAL_ABOVE_GREATER_THAN_ABOVE_SLANTED_EQUAL L"\u2a93" #define UNICODE_GREATER_THAN_ABOVE_SLANTED_EQUAL_ABOVE_LESS_THAN_ABOVE_SLANTED_EQUAL 0x2a94 #define UNITEXT_GREATER_THAN_ABOVE_SLANTED_EQUAL_ABOVE_LESS_THAN_ABOVE_SLANTED_EQUAL L"\u2a94" #define UNICODE_SLANTED_EQUAL_TO_OR_LESS_THAN 0x2a95 #define UNITEXT_SLANTED_EQUAL_TO_OR_LESS_THAN L"\u2a95" #define UNICODE_SLANTED_EQUAL_TO_OR_GREATER_THAN 0x2a96 #define UNITEXT_SLANTED_EQUAL_TO_OR_GREATER_THAN L"\u2a96" #define UNICODE_SLANTED_EQUAL_TO_OR_LESS_THAN_WITH_DOT_INSIDE 0x2a97 #define UNITEXT_SLANTED_EQUAL_TO_OR_LESS_THAN_WITH_DOT_INSIDE L"\u2a97" #define UNICODE_SLANTED_EQUAL_TO_OR_GREATER_THAN_WITH_DOT_INSIDE 0x2a98 #define UNITEXT_SLANTED_EQUAL_TO_OR_GREATER_THAN_WITH_DOT_INSIDE L"\u2a98" #define UNICODE_DOUBLE_LINE_EQUAL_TO_OR_LESS_THAN 0x2a99 #define UNITEXT_DOUBLE_LINE_EQUAL_TO_OR_LESS_THAN L"\u2a99" #define UNICODE_DOUBLE_LINE_EQUAL_TO_OR_GREATER_THAN 0x2a9a #define UNITEXT_DOUBLE_LINE_EQUAL_TO_OR_GREATER_THAN L"\u2a9a" #define UNICODE_DOUBLE_LINE_SLANTED_EQUAL_TO_OR_LESS_THAN 0x2a9b #define UNITEXT_DOUBLE_LINE_SLANTED_EQUAL_TO_OR_LESS_THAN L"\u2a9b" #define UNICODE_DOUBLE_LINE_SLANTED_EQUAL_TO_OR_GREATER_THAN 0x2a9c #define UNITEXT_DOUBLE_LINE_SLANTED_EQUAL_TO_OR_GREATER_THAN L"\u2a9c" #define UNICODE_SIMILAR_OR_LESS_THAN 0x2a9d #define UNITEXT_SIMILAR_OR_LESS_THAN L"\u2a9d" #define UNICODE_SIMILAR_OR_GREATER_THAN 0x2a9e #define UNITEXT_SIMILAR_OR_GREATER_THAN L"\u2a9e" #define UNICODE_SIMILAR_ABOVE_LESS_THAN_ABOVE_EQUALS_SIGN 0x2a9f #define UNITEXT_SIMILAR_ABOVE_LESS_THAN_ABOVE_EQUALS_SIGN L"\u2a9f" #define UNICODE_SIMILAR_ABOVE_GREATER_THAN_ABOVE_EQUALS_SIGN 0x2aa0 #define UNITEXT_SIMILAR_ABOVE_GREATER_THAN_ABOVE_EQUALS_SIGN L"\u2aa0" #define UNICODE_DOUBLE_NESTED_LESS_THAN 0x2aa1 #define UNITEXT_DOUBLE_NESTED_LESS_THAN L"\u2aa1" #define UNICODE_DOUBLE_NESTED_GREATER_THAN 0x2aa2 #define UNITEXT_DOUBLE_NESTED_GREATER_THAN L"\u2aa2" #define UNICODE_DOUBLE_NESTED_LESS_THAN_WITH_UNDERBAR 0x2aa3 #define UNITEXT_DOUBLE_NESTED_LESS_THAN_WITH_UNDERBAR L"\u2aa3" #define UNICODE_GREATER_THAN_OVERLAPPING_LESS_THAN 0x2aa4 #define UNITEXT_GREATER_THAN_OVERLAPPING_LESS_THAN L"\u2aa4" #define UNICODE_GREATER_THAN_BESIDE_LESS_THAN 0x2aa5 #define UNITEXT_GREATER_THAN_BESIDE_LESS_THAN L"\u2aa5" #define UNICODE_LESS_THAN_CLOSED_BY_CURVE 0x2aa6 #define UNITEXT_LESS_THAN_CLOSED_BY_CURVE L"\u2aa6" #define UNICODE_GREATER_THAN_CLOSED_BY_CURVE 0x2aa7 #define UNITEXT_GREATER_THAN_CLOSED_BY_CURVE L"\u2aa7" #define UNICODE_LESS_THAN_CLOSED_BY_CURVE_ABOVE_SLANTED_EQUAL 0x2aa8 #define UNITEXT_LESS_THAN_CLOSED_BY_CURVE_ABOVE_SLANTED_EQUAL L"\u2aa8" #define UNICODE_GREATER_THAN_CLOSED_BY_CURVE_ABOVE_SLANTED_EQUAL 0x2aa9 #define UNITEXT_GREATER_THAN_CLOSED_BY_CURVE_ABOVE_SLANTED_EQUAL L"\u2aa9" #define UNICODE_SMALLER_THAN 0x2aaa #define UNITEXT_SMALLER_THAN L"\u2aaa" #define UNICODE_LARGER_THAN 0x2aab #define UNITEXT_LARGER_THAN L"\u2aab" #define UNICODE_SMALLER_THAN_OR_EQUAL_TO 0x2aac #define UNITEXT_SMALLER_THAN_OR_EQUAL_TO L"\u2aac" #define UNICODE_LARGER_THAN_OR_EQUAL_TO 0x2aad #define UNITEXT_LARGER_THAN_OR_EQUAL_TO L"\u2aad" #define UNICODE_EQUALS_SIGN_WITH_BUMPY_ABOVE 0x2aae #define UNITEXT_EQUALS_SIGN_WITH_BUMPY_ABOVE L"\u2aae" #define UNICODE_PRECEDES_ABOVE_SINGLE_LINE_EQUALS_SIGN 0x2aaf #define UNITEXT_PRECEDES_ABOVE_SINGLE_LINE_EQUALS_SIGN L"\u2aaf" #define UNICODE_SUCCEEDS_ABOVE_SINGLE_LINE_EQUALS_SIGN 0x2ab0 #define UNITEXT_SUCCEEDS_ABOVE_SINGLE_LINE_EQUALS_SIGN L"\u2ab0" #define UNICODE_PRECEDES_ABOVE_SINGLE_LINE_NOT_EQUAL_TO 0x2ab1 #define UNITEXT_PRECEDES_ABOVE_SINGLE_LINE_NOT_EQUAL_TO L"\u2ab1" #define UNICODE_SUCCEEDS_ABOVE_SINGLE_LINE_NOT_EQUAL_TO 0x2ab2 #define UNITEXT_SUCCEEDS_ABOVE_SINGLE_LINE_NOT_EQUAL_TO L"\u2ab2" #define UNICODE_PRECEDES_ABOVE_EQUALS_SIGN 0x2ab3 #define UNITEXT_PRECEDES_ABOVE_EQUALS_SIGN L"\u2ab3" #define UNICODE_SUCCEEDS_ABOVE_EQUALS_SIGN 0x2ab4 #define UNITEXT_SUCCEEDS_ABOVE_EQUALS_SIGN L"\u2ab4" #define UNICODE_PRECEDES_ABOVE_NOT_EQUAL_TO 0x2ab5 #define UNITEXT_PRECEDES_ABOVE_NOT_EQUAL_TO L"\u2ab5" #define UNICODE_SUCCEEDS_ABOVE_NOT_EQUAL_TO 0x2ab6 #define UNITEXT_SUCCEEDS_ABOVE_NOT_EQUAL_TO L"\u2ab6" #define UNICODE_PRECEDES_ABOVE_ALMOST_EQUAL_TO 0x2ab7 #define UNITEXT_PRECEDES_ABOVE_ALMOST_EQUAL_TO L"\u2ab7" #define UNICODE_SUCCEEDS_ABOVE_ALMOST_EQUAL_TO 0x2ab8 #define UNITEXT_SUCCEEDS_ABOVE_ALMOST_EQUAL_TO L"\u2ab8" #define UNICODE_PRECEDES_ABOVE_NOT_ALMOST_EQUAL_TO 0x2ab9 #define UNITEXT_PRECEDES_ABOVE_NOT_ALMOST_EQUAL_TO L"\u2ab9" #define UNICODE_SUCCEEDS_ABOVE_NOT_ALMOST_EQUAL_TO 0x2aba #define UNITEXT_SUCCEEDS_ABOVE_NOT_ALMOST_EQUAL_TO L"\u2aba" #define UNICODE_DOUBLE_PRECEDES 0x2abb #define UNITEXT_DOUBLE_PRECEDES L"\u2abb" #define UNICODE_DOUBLE_SUCCEEDS 0x2abc #define UNITEXT_DOUBLE_SUCCEEDS L"\u2abc" #define UNICODE_SUBSET_WITH_DOT 0x2abd #define UNITEXT_SUBSET_WITH_DOT L"\u2abd" #define UNICODE_SUPERSET_WITH_DOT 0x2abe #define UNITEXT_SUPERSET_WITH_DOT L"\u2abe" #define UNICODE_SUBSET_WITH_PLUS_SIGN_BELOW 0x2abf #define UNITEXT_SUBSET_WITH_PLUS_SIGN_BELOW L"\u2abf" #define UNICODE_SUPERSET_WITH_PLUS_SIGN_BELOW 0x2ac0 #define UNITEXT_SUPERSET_WITH_PLUS_SIGN_BELOW L"\u2ac0" #define UNICODE_SUBSET_WITH_MULTIPLICATION_SIGN_BELOW 0x2ac1 #define UNITEXT_SUBSET_WITH_MULTIPLICATION_SIGN_BELOW L"\u2ac1" #define UNICODE_SUPERSET_WITH_MULTIPLICATION_SIGN_BELOW 0x2ac2 #define UNITEXT_SUPERSET_WITH_MULTIPLICATION_SIGN_BELOW L"\u2ac2" #define UNICODE_SUBSET_OF_OR_EQUAL_TO_WITH_DOT_ABOVE 0x2ac3 #define UNITEXT_SUBSET_OF_OR_EQUAL_TO_WITH_DOT_ABOVE L"\u2ac3" #define UNICODE_SUPERSET_OF_OR_EQUAL_TO_WITH_DOT_ABOVE 0x2ac4 #define UNITEXT_SUPERSET_OF_OR_EQUAL_TO_WITH_DOT_ABOVE L"\u2ac4" #define UNICODE_SUBSET_OF_ABOVE_EQUALS_SIGN 0x2ac5 #define UNITEXT_SUBSET_OF_ABOVE_EQUALS_SIGN L"\u2ac5" #define UNICODE_SUPERSET_OF_ABOVE_EQUALS_SIGN 0x2ac6 #define UNITEXT_SUPERSET_OF_ABOVE_EQUALS_SIGN L"\u2ac6" #define UNICODE_SUBSET_OF_ABOVE_TILDE_OPERATOR 0x2ac7 #define UNITEXT_SUBSET_OF_ABOVE_TILDE_OPERATOR L"\u2ac7" #define UNICODE_SUPERSET_OF_ABOVE_TILDE_OPERATOR 0x2ac8 #define UNITEXT_SUPERSET_OF_ABOVE_TILDE_OPERATOR L"\u2ac8" #define UNICODE_SUBSET_OF_ABOVE_ALMOST_EQUAL_TO 0x2ac9 #define UNITEXT_SUBSET_OF_ABOVE_ALMOST_EQUAL_TO L"\u2ac9" #define UNICODE_SUPERSET_OF_ABOVE_ALMOST_EQUAL_TO 0x2aca #define UNITEXT_SUPERSET_OF_ABOVE_ALMOST_EQUAL_TO L"\u2aca" #define UNICODE_SUBSET_OF_ABOVE_NOT_EQUAL_TO 0x2acb #define UNITEXT_SUBSET_OF_ABOVE_NOT_EQUAL_TO L"\u2acb" #define UNICODE_SUPERSET_OF_ABOVE_NOT_EQUAL_TO 0x2acc #define UNITEXT_SUPERSET_OF_ABOVE_NOT_EQUAL_TO L"\u2acc" #define UNICODE_SQUARE_LEFT_OPEN_BOX_OPERATOR 0x2acd #define UNITEXT_SQUARE_LEFT_OPEN_BOX_OPERATOR L"\u2acd" #define UNICODE_SQUARE_RIGHT_OPEN_BOX_OPERATOR 0x2ace #define UNITEXT_SQUARE_RIGHT_OPEN_BOX_OPERATOR L"\u2ace" #define UNICODE_CLOSED_SUBSET 0x2acf #define UNITEXT_CLOSED_SUBSET L"\u2acf" #define UNICODE_CLOSED_SUPERSET 0x2ad0 #define UNITEXT_CLOSED_SUPERSET L"\u2ad0" #define UNICODE_CLOSED_SUBSET_OR_EQUAL_TO 0x2ad1 #define UNITEXT_CLOSED_SUBSET_OR_EQUAL_TO L"\u2ad1" #define UNICODE_CLOSED_SUPERSET_OR_EQUAL_TO 0x2ad2 #define UNITEXT_CLOSED_SUPERSET_OR_EQUAL_TO L"\u2ad2" #define UNICODE_SUBSET_ABOVE_SUPERSET 0x2ad3 #define UNITEXT_SUBSET_ABOVE_SUPERSET L"\u2ad3" #define UNICODE_SUPERSET_ABOVE_SUBSET 0x2ad4 #define UNITEXT_SUPERSET_ABOVE_SUBSET L"\u2ad4" #define UNICODE_SUBSET_ABOVE_SUBSET 0x2ad5 #define UNITEXT_SUBSET_ABOVE_SUBSET L"\u2ad5" #define UNICODE_SUPERSET_ABOVE_SUPERSET 0x2ad6 #define UNITEXT_SUPERSET_ABOVE_SUPERSET L"\u2ad6" #define UNICODE_SUPERSET_BESIDE_SUBSET 0x2ad7 #define UNITEXT_SUPERSET_BESIDE_SUBSET L"\u2ad7" #define UNICODE_SUPERSET_BESIDE_AND_JOINED_BY_DASH_WITH_SUBSET 0x2ad8 #define UNITEXT_SUPERSET_BESIDE_AND_JOINED_BY_DASH_WITH_SUBSET L"\u2ad8" #define UNICODE_ELEMENT_OF_OPENING_DOWNWARDS 0x2ad9 #define UNITEXT_ELEMENT_OF_OPENING_DOWNWARDS L"\u2ad9" #define UNICODE_PITCHFORK_WITH_TEE_TOP 0x2ada #define UNITEXT_PITCHFORK_WITH_TEE_TOP L"\u2ada" #define UNICODE_TRANSVERSAL_INTERSECTION 0x2adb #define UNITEXT_TRANSVERSAL_INTERSECTION L"\u2adb" #define UNICODE_FORKING 0x2adc #define UNITEXT_FORKING L"\u2adc" #define UNICODE_NONFORKING 0x2add #define UNITEXT_NONFORKING L"\u2add" #define UNICODE_SHORT_LEFT_TACK 0x2ade #define UNITEXT_SHORT_LEFT_TACK L"\u2ade" #define UNICODE_SHORT_DOWN_TACK 0x2adf #define UNITEXT_SHORT_DOWN_TACK L"\u2adf" #define UNICODE_SHORT_UP_TACK 0x2ae0 #define UNITEXT_SHORT_UP_TACK L"\u2ae0" #define UNICODE_PERPENDICULAR_WITH_S 0x2ae1 #define UNITEXT_PERPENDICULAR_WITH_S L"\u2ae1" #define UNICODE_VERTICAL_BAR_TRIPLE_RIGHT_TURNSTILE 0x2ae2 #define UNITEXT_VERTICAL_BAR_TRIPLE_RIGHT_TURNSTILE L"\u2ae2" #define UNICODE_DOUBLE_VERTICAL_BAR_LEFT_TURNSTILE 0x2ae3 #define UNITEXT_DOUBLE_VERTICAL_BAR_LEFT_TURNSTILE L"\u2ae3" #define UNICODE_VERTICAL_BAR_DOUBLE_LEFT_TURNSTILE 0x2ae4 #define UNITEXT_VERTICAL_BAR_DOUBLE_LEFT_TURNSTILE L"\u2ae4" #define UNICODE_DOUBLE_VERTICAL_BAR_DOUBLE_LEFT_TURNSTILE 0x2ae5 #define UNITEXT_DOUBLE_VERTICAL_BAR_DOUBLE_LEFT_TURNSTILE L"\u2ae5" #define UNICODE_LONG_DASH_FROM_LEFT_MEMBER_OF_DOUBLE_VERTICAL 0x2ae6 #define UNITEXT_LONG_DASH_FROM_LEFT_MEMBER_OF_DOUBLE_VERTICAL L"\u2ae6" #define UNICODE_SHORT_DOWN_TACK_WITH_OVERBAR 0x2ae7 #define UNITEXT_SHORT_DOWN_TACK_WITH_OVERBAR L"\u2ae7" #define UNICODE_SHORT_UP_TACK_WITH_UNDERBAR 0x2ae8 #define UNITEXT_SHORT_UP_TACK_WITH_UNDERBAR L"\u2ae8" #define UNICODE_SHORT_UP_TACK_ABOVE_SHORT_DOWN_TACK 0x2ae9 #define UNITEXT_SHORT_UP_TACK_ABOVE_SHORT_DOWN_TACK L"\u2ae9" #define UNICODE_DOUBLE_DOWN_TACK 0x2aea #define UNITEXT_DOUBLE_DOWN_TACK L"\u2aea" #define UNICODE_DOUBLE_UP_TACK 0x2aeb #define UNITEXT_DOUBLE_UP_TACK L"\u2aeb" #define UNICODE_DOUBLE_STROKE_NOT_SIGN 0x2aec #define UNITEXT_DOUBLE_STROKE_NOT_SIGN L"\u2aec" #define UNICODE_REVERSED_DOUBLE_STROKE_NOT_SIGN 0x2aed #define UNITEXT_REVERSED_DOUBLE_STROKE_NOT_SIGN L"\u2aed" #define UNICODE_DOES_NOT_DIVIDE_WITH_REVERSED_NEGATION_SLASH 0x2aee #define UNITEXT_DOES_NOT_DIVIDE_WITH_REVERSED_NEGATION_SLASH L"\u2aee" #define UNICODE_VERTICAL_LINE_WITH_CIRCLE_ABOVE 0x2aef #define UNITEXT_VERTICAL_LINE_WITH_CIRCLE_ABOVE L"\u2aef" #define UNICODE_VERTICAL_LINE_WITH_CIRCLE_BELOW 0x2af0 #define UNITEXT_VERTICAL_LINE_WITH_CIRCLE_BELOW L"\u2af0" #define UNICODE_DOWN_TACK_WITH_CIRCLE_BELOW 0x2af1 #define UNITEXT_DOWN_TACK_WITH_CIRCLE_BELOW L"\u2af1" #define UNICODE_PARALLEL_WITH_HORIZONTAL_STROKE 0x2af2 #define UNITEXT_PARALLEL_WITH_HORIZONTAL_STROKE L"\u2af2" #define UNICODE_PARALLEL_WITH_TILDE_OPERATOR 0x2af3 #define UNITEXT_PARALLEL_WITH_TILDE_OPERATOR L"\u2af3" #define UNICODE_TRIPLE_VERTICAL_BAR_BINARY_RELATION 0x2af4 #define UNITEXT_TRIPLE_VERTICAL_BAR_BINARY_RELATION L"\u2af4" #define UNICODE_TRIPLE_VERTICAL_BAR_WITH_HORIZONTAL_STROKE 0x2af5 #define UNITEXT_TRIPLE_VERTICAL_BAR_WITH_HORIZONTAL_STROKE L"\u2af5" #define UNICODE_TRIPLE_COLON_OPERATOR 0x2af6 #define UNITEXT_TRIPLE_COLON_OPERATOR L"\u2af6" #define UNICODE_TRIPLE_NESTED_LESS_THAN 0x2af7 #define UNITEXT_TRIPLE_NESTED_LESS_THAN L"\u2af7" #define UNICODE_TRIPLE_NESTED_GREATER_THAN 0x2af8 #define UNITEXT_TRIPLE_NESTED_GREATER_THAN L"\u2af8" #define UNICODE_DOUBLE_LINE_SLANTED_LESS_THAN_OR_EQUAL_TO 0x2af9 #define UNITEXT_DOUBLE_LINE_SLANTED_LESS_THAN_OR_EQUAL_TO L"\u2af9" #define UNICODE_DOUBLE_LINE_SLANTED_GREATER_THAN_OR_EQUAL_TO 0x2afa #define UNITEXT_DOUBLE_LINE_SLANTED_GREATER_THAN_OR_EQUAL_TO L"\u2afa" #define UNICODE_TRIPLE_SOLIDUS_BINARY_RELATION 0x2afb #define UNITEXT_TRIPLE_SOLIDUS_BINARY_RELATION L"\u2afb" #define UNICODE_LARGE_TRIPLE_VERTICAL_BAR_OPERATOR 0x2afc #define UNITEXT_LARGE_TRIPLE_VERTICAL_BAR_OPERATOR L"\u2afc" #define UNICODE_DOUBLE_SOLIDUS_OPERATOR 0x2afd #define UNITEXT_DOUBLE_SOLIDUS_OPERATOR L"\u2afd" #define UNICODE_WHITE_VERTICAL_BAR 0x2afe #define UNITEXT_WHITE_VERTICAL_BAR L"\u2afe" #define UNICODE_N_ARY_WHITE_VERTICAL_BAR 0x2aff #define UNITEXT_N_ARY_WHITE_VERTICAL_BAR L"\u2aff" #define UNICODE_NORTH_EAST_WHITE_ARROW 0x2b00 #define UNITEXT_NORTH_EAST_WHITE_ARROW L"\u2b00" #define UNICODE_NORTH_WEST_WHITE_ARROW 0x2b01 #define UNITEXT_NORTH_WEST_WHITE_ARROW L"\u2b01" #define UNICODE_SOUTH_EAST_WHITE_ARROW 0x2b02 #define UNITEXT_SOUTH_EAST_WHITE_ARROW L"\u2b02" #define UNICODE_SOUTH_WEST_WHITE_ARROW 0x2b03 #define UNITEXT_SOUTH_WEST_WHITE_ARROW L"\u2b03" #define UNICODE_LEFT_RIGHT_WHITE_ARROW 0x2b04 #define UNITEXT_LEFT_RIGHT_WHITE_ARROW L"\u2b04" #define UNICODE_LEFTWARDS_BLACK_ARROW 0x2b05 #define UNITEXT_LEFTWARDS_BLACK_ARROW L"\u2b05" #define UNICODE_UPWARDS_BLACK_ARROW 0x2b06 #define UNITEXT_UPWARDS_BLACK_ARROW L"\u2b06" #define UNICODE_DOWNWARDS_BLACK_ARROW 0x2b07 #define UNITEXT_DOWNWARDS_BLACK_ARROW L"\u2b07" #define UNICODE_NORTH_EAST_BLACK_ARROW 0x2b08 #define UNITEXT_NORTH_EAST_BLACK_ARROW L"\u2b08" #define UNICODE_NORTH_WEST_BLACK_ARROW 0x2b09 #define UNITEXT_NORTH_WEST_BLACK_ARROW L"\u2b09" #define UNICODE_SOUTH_EAST_BLACK_ARROW 0x2b0a #define UNITEXT_SOUTH_EAST_BLACK_ARROW L"\u2b0a" #define UNICODE_SOUTH_WEST_BLACK_ARROW 0x2b0b #define UNITEXT_SOUTH_WEST_BLACK_ARROW L"\u2b0b" #define UNICODE_LEFT_RIGHT_BLACK_ARROW 0x2b0c #define UNITEXT_LEFT_RIGHT_BLACK_ARROW L"\u2b0c" #define UNICODE_UP_DOWN_BLACK_ARROW 0x2b0d #define UNITEXT_UP_DOWN_BLACK_ARROW L"\u2b0d" #define UNICODE_RIGHTWARDS_ARROW_WITH_TIP_DOWNWARDS 0x2b0e #define UNITEXT_RIGHTWARDS_ARROW_WITH_TIP_DOWNWARDS L"\u2b0e" #define UNICODE_RIGHTWARDS_ARROW_WITH_TIP_UPWARDS 0x2b0f #define UNITEXT_RIGHTWARDS_ARROW_WITH_TIP_UPWARDS L"\u2b0f" #define UNICODE_LEFTWARDS_ARROW_WITH_TIP_DOWNWARDS 0x2b10 #define UNITEXT_LEFTWARDS_ARROW_WITH_TIP_DOWNWARDS L"\u2b10" #define UNICODE_LEFTWARDS_ARROW_WITH_TIP_UPWARDS 0x2b11 #define UNITEXT_LEFTWARDS_ARROW_WITH_TIP_UPWARDS L"\u2b11" #define UNICODE_SQUARE_WITH_TOP_HALF_BLACK 0x2b12 #define UNITEXT_SQUARE_WITH_TOP_HALF_BLACK L"\u2b12" #define UNICODE_SQUARE_WITH_BOTTOM_HALF_BLACK 0x2b13 #define UNITEXT_SQUARE_WITH_BOTTOM_HALF_BLACK L"\u2b13" #define UNICODE_SQUARE_WITH_UPPER_RIGHT_DIAGONAL_HALF_BLACK 0x2b14 #define UNITEXT_SQUARE_WITH_UPPER_RIGHT_DIAGONAL_HALF_BLACK L"\u2b14" #define UNICODE_SQUARE_WITH_LOWER_LEFT_DIAGONAL_HALF_BLACK 0x2b15 #define UNITEXT_SQUARE_WITH_LOWER_LEFT_DIAGONAL_HALF_BLACK L"\u2b15" #define UNICODE_DIAMOND_WITH_LEFT_HALF_BLACK 0x2b16 #define UNITEXT_DIAMOND_WITH_LEFT_HALF_BLACK L"\u2b16" #define UNICODE_DIAMOND_WITH_RIGHT_HALF_BLACK 0x2b17 #define UNITEXT_DIAMOND_WITH_RIGHT_HALF_BLACK L"\u2b17" #define UNICODE_DIAMOND_WITH_TOP_HALF_BLACK 0x2b18 #define UNITEXT_DIAMOND_WITH_TOP_HALF_BLACK L"\u2b18" #define UNICODE_DIAMOND_WITH_BOTTOM_HALF_BLACK 0x2b19 #define UNITEXT_DIAMOND_WITH_BOTTOM_HALF_BLACK L"\u2b19" #define UNICODE_DOTTED_SQUARE 0x2b1a #define UNITEXT_DOTTED_SQUARE L"\u2b1a" #define UNICODE_WHITE_PENTAGON 0x2b20 #define UNITEXT_WHITE_PENTAGON L"\u2b20" #define UNICODE_WHITE_HEXAGON 0x2b21 #define UNITEXT_WHITE_HEXAGON L"\u2b21" #define UNICODE_BLACK_HEXAGON 0x2b22 #define UNITEXT_BLACK_HEXAGON L"\u2b22" #define UNICODE_HORIZONTAL_BLACK_HEXAGON 0x2b23 #define UNITEXT_HORIZONTAL_BLACK_HEXAGON L"\u2b23" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_AZU 0x2c00 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_AZU L"\u2c00" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_BUKY 0x2c01 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_BUKY L"\u2c01" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_VEDE 0x2c02 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_VEDE L"\u2c02" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_GLAGOLI 0x2c03 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_GLAGOLI L"\u2c03" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_DOBRO 0x2c04 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_DOBRO L"\u2c04" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_YESTU 0x2c05 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_YESTU L"\u2c05" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_ZHIVETE 0x2c06 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_ZHIVETE L"\u2c06" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_DZELO 0x2c07 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_DZELO L"\u2c07" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_ZEMLJA 0x2c08 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_ZEMLJA L"\u2c08" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_IZHE 0x2c09 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_IZHE L"\u2c09" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_INITIAL_IZHE 0x2c0a #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_INITIAL_IZHE L"\u2c0a" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_I 0x2c0b #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_I L"\u2c0b" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_DJERVI 0x2c0c #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_DJERVI L"\u2c0c" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_KAKO 0x2c0d #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_KAKO L"\u2c0d" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_LJUDIJE 0x2c0e #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_LJUDIJE L"\u2c0e" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_MYSLITE 0x2c0f #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_MYSLITE L"\u2c0f" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_NASHI 0x2c10 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_NASHI L"\u2c10" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_ONU 0x2c11 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_ONU L"\u2c11" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_POKOJI 0x2c12 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_POKOJI L"\u2c12" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_RITSI 0x2c13 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_RITSI L"\u2c13" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_SLOVO 0x2c14 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_SLOVO L"\u2c14" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_TVRIDO 0x2c15 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_TVRIDO L"\u2c15" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_UKU 0x2c16 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_UKU L"\u2c16" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_FRITU 0x2c17 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_FRITU L"\u2c17" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_HERU 0x2c18 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_HERU L"\u2c18" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_OTU 0x2c19 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_OTU L"\u2c19" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_PE 0x2c1a #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_PE L"\u2c1a" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_SHTA 0x2c1b #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_SHTA L"\u2c1b" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_TSI 0x2c1c #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_TSI L"\u2c1c" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_CHRIVI 0x2c1d #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_CHRIVI L"\u2c1d" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_SHA 0x2c1e #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_SHA L"\u2c1e" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_YERU 0x2c1f #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_YERU L"\u2c1f" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_YERI 0x2c20 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_YERI L"\u2c20" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_YATI 0x2c21 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_YATI L"\u2c21" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_SPIDERY_HA 0x2c22 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_SPIDERY_HA L"\u2c22" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_YU 0x2c23 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_YU L"\u2c23" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_SMALL_YUS 0x2c24 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_SMALL_YUS L"\u2c24" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_SMALL_YUS_WITH_TAIL 0x2c25 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_SMALL_YUS_WITH_TAIL L"\u2c25" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_YO 0x2c26 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_YO L"\u2c26" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_IOTATED_SMALL_YUS 0x2c27 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_IOTATED_SMALL_YUS L"\u2c27" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_BIG_YUS 0x2c28 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_BIG_YUS L"\u2c28" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_IOTATED_BIG_YUS 0x2c29 #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_IOTATED_BIG_YUS L"\u2c29" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_FITA 0x2c2a #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_FITA L"\u2c2a" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_IZHITSA 0x2c2b #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_IZHITSA L"\u2c2b" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_SHTAPIC 0x2c2c #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_SHTAPIC L"\u2c2c" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_TROKUTASTI_A 0x2c2d #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_TROKUTASTI_A L"\u2c2d" #define UNICODE_GLAGOLITIC_CAPITAL_LETTER_LATINATE_MYSLITE 0x2c2e #define UNITEXT_GLAGOLITIC_CAPITAL_LETTER_LATINATE_MYSLITE L"\u2c2e" #define UNICODE_GLAGOLITIC_SMALL_LETTER_AZU 0x2c30 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_AZU L"\u2c30" #define UNICODE_GLAGOLITIC_SMALL_LETTER_BUKY 0x2c31 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_BUKY L"\u2c31" #define UNICODE_GLAGOLITIC_SMALL_LETTER_VEDE 0x2c32 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_VEDE L"\u2c32" #define UNICODE_GLAGOLITIC_SMALL_LETTER_GLAGOLI 0x2c33 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_GLAGOLI L"\u2c33" #define UNICODE_GLAGOLITIC_SMALL_LETTER_DOBRO 0x2c34 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_DOBRO L"\u2c34" #define UNICODE_GLAGOLITIC_SMALL_LETTER_YESTU 0x2c35 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_YESTU L"\u2c35" #define UNICODE_GLAGOLITIC_SMALL_LETTER_ZHIVETE 0x2c36 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_ZHIVETE L"\u2c36" #define UNICODE_GLAGOLITIC_SMALL_LETTER_DZELO 0x2c37 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_DZELO L"\u2c37" #define UNICODE_GLAGOLITIC_SMALL_LETTER_ZEMLJA 0x2c38 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_ZEMLJA L"\u2c38" #define UNICODE_GLAGOLITIC_SMALL_LETTER_IZHE 0x2c39 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_IZHE L"\u2c39" #define UNICODE_GLAGOLITIC_SMALL_LETTER_INITIAL_IZHE 0x2c3a #define UNITEXT_GLAGOLITIC_SMALL_LETTER_INITIAL_IZHE L"\u2c3a" #define UNICODE_GLAGOLITIC_SMALL_LETTER_I 0x2c3b #define UNITEXT_GLAGOLITIC_SMALL_LETTER_I L"\u2c3b" #define UNICODE_GLAGOLITIC_SMALL_LETTER_DJERVI 0x2c3c #define UNITEXT_GLAGOLITIC_SMALL_LETTER_DJERVI L"\u2c3c" #define UNICODE_GLAGOLITIC_SMALL_LETTER_KAKO 0x2c3d #define UNITEXT_GLAGOLITIC_SMALL_LETTER_KAKO L"\u2c3d" #define UNICODE_GLAGOLITIC_SMALL_LETTER_LJUDIJE 0x2c3e #define UNITEXT_GLAGOLITIC_SMALL_LETTER_LJUDIJE L"\u2c3e" #define UNICODE_GLAGOLITIC_SMALL_LETTER_MYSLITE 0x2c3f #define UNITEXT_GLAGOLITIC_SMALL_LETTER_MYSLITE L"\u2c3f" #define UNICODE_GLAGOLITIC_SMALL_LETTER_NASHI 0x2c40 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_NASHI L"\u2c40" #define UNICODE_GLAGOLITIC_SMALL_LETTER_ONU 0x2c41 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_ONU L"\u2c41" #define UNICODE_GLAGOLITIC_SMALL_LETTER_POKOJI 0x2c42 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_POKOJI L"\u2c42" #define UNICODE_GLAGOLITIC_SMALL_LETTER_RITSI 0x2c43 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_RITSI L"\u2c43" #define UNICODE_GLAGOLITIC_SMALL_LETTER_SLOVO 0x2c44 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_SLOVO L"\u2c44" #define UNICODE_GLAGOLITIC_SMALL_LETTER_TVRIDO 0x2c45 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_TVRIDO L"\u2c45" #define UNICODE_GLAGOLITIC_SMALL_LETTER_UKU 0x2c46 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_UKU L"\u2c46" #define UNICODE_GLAGOLITIC_SMALL_LETTER_FRITU 0x2c47 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_FRITU L"\u2c47" #define UNICODE_GLAGOLITIC_SMALL_LETTER_HERU 0x2c48 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_HERU L"\u2c48" #define UNICODE_GLAGOLITIC_SMALL_LETTER_OTU 0x2c49 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_OTU L"\u2c49" #define UNICODE_GLAGOLITIC_SMALL_LETTER_PE 0x2c4a #define UNITEXT_GLAGOLITIC_SMALL_LETTER_PE L"\u2c4a" #define UNICODE_GLAGOLITIC_SMALL_LETTER_SHTA 0x2c4b #define UNITEXT_GLAGOLITIC_SMALL_LETTER_SHTA L"\u2c4b" #define UNICODE_GLAGOLITIC_SMALL_LETTER_TSI 0x2c4c #define UNITEXT_GLAGOLITIC_SMALL_LETTER_TSI L"\u2c4c" #define UNICODE_GLAGOLITIC_SMALL_LETTER_CHRIVI 0x2c4d #define UNITEXT_GLAGOLITIC_SMALL_LETTER_CHRIVI L"\u2c4d" #define UNICODE_GLAGOLITIC_SMALL_LETTER_SHA 0x2c4e #define UNITEXT_GLAGOLITIC_SMALL_LETTER_SHA L"\u2c4e" #define UNICODE_GLAGOLITIC_SMALL_LETTER_YERU 0x2c4f #define UNITEXT_GLAGOLITIC_SMALL_LETTER_YERU L"\u2c4f" #define UNICODE_GLAGOLITIC_SMALL_LETTER_YERI 0x2c50 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_YERI L"\u2c50" #define UNICODE_GLAGOLITIC_SMALL_LETTER_YATI 0x2c51 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_YATI L"\u2c51" #define UNICODE_GLAGOLITIC_SMALL_LETTER_SPIDERY_HA 0x2c52 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_SPIDERY_HA L"\u2c52" #define UNICODE_GLAGOLITIC_SMALL_LETTER_YU 0x2c53 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_YU L"\u2c53" #define UNICODE_GLAGOLITIC_SMALL_LETTER_SMALL_YUS 0x2c54 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_SMALL_YUS L"\u2c54" #define UNICODE_GLAGOLITIC_SMALL_LETTER_SMALL_YUS_WITH_TAIL 0x2c55 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_SMALL_YUS_WITH_TAIL L"\u2c55" #define UNICODE_GLAGOLITIC_SMALL_LETTER_YO 0x2c56 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_YO L"\u2c56" #define UNICODE_GLAGOLITIC_SMALL_LETTER_IOTATED_SMALL_YUS 0x2c57 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_IOTATED_SMALL_YUS L"\u2c57" #define UNICODE_GLAGOLITIC_SMALL_LETTER_BIG_YUS 0x2c58 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_BIG_YUS L"\u2c58" #define UNICODE_GLAGOLITIC_SMALL_LETTER_IOTATED_BIG_YUS 0x2c59 #define UNITEXT_GLAGOLITIC_SMALL_LETTER_IOTATED_BIG_YUS L"\u2c59" #define UNICODE_GLAGOLITIC_SMALL_LETTER_FITA 0x2c5a #define UNITEXT_GLAGOLITIC_SMALL_LETTER_FITA L"\u2c5a" #define UNICODE_GLAGOLITIC_SMALL_LETTER_IZHITSA 0x2c5b #define UNITEXT_GLAGOLITIC_SMALL_LETTER_IZHITSA L"\u2c5b" #define UNICODE_GLAGOLITIC_SMALL_LETTER_SHTAPIC 0x2c5c #define UNITEXT_GLAGOLITIC_SMALL_LETTER_SHTAPIC L"\u2c5c" #define UNICODE_GLAGOLITIC_SMALL_LETTER_TROKUTASTI_A 0x2c5d #define UNITEXT_GLAGOLITIC_SMALL_LETTER_TROKUTASTI_A L"\u2c5d" #define UNICODE_GLAGOLITIC_SMALL_LETTER_LATINATE_MYSLITE 0x2c5e #define UNITEXT_GLAGOLITIC_SMALL_LETTER_LATINATE_MYSLITE L"\u2c5e" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_DOUBLE_BAR 0x2c60 #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_DOUBLE_BAR L"\u2c60" #define UNICODE_LATIN_SMALL_LETTER_L_WITH_DOUBLE_BAR 0x2c61 #define UNITEXT_LATIN_SMALL_LETTER_L_WITH_DOUBLE_BAR L"\u2c61" #define UNICODE_LATIN_CAPITAL_LETTER_L_WITH_MIDDLE_TILDE 0x2c62 #define UNITEXT_LATIN_CAPITAL_LETTER_L_WITH_MIDDLE_TILDE L"\u2c62" #define UNICODE_LATIN_CAPITAL_LETTER_P_WITH_STROKE 0x2c63 #define UNITEXT_LATIN_CAPITAL_LETTER_P_WITH_STROKE L"\u2c63" #define UNICODE_LATIN_CAPITAL_LETTER_R_WITH_TAIL 0x2c64 #define UNITEXT_LATIN_CAPITAL_LETTER_R_WITH_TAIL L"\u2c64" #define UNICODE_LATIN_SMALL_LETTER_A_WITH_STROKE 0x2c65 #define UNITEXT_LATIN_SMALL_LETTER_A_WITH_STROKE L"\u2c65" #define UNICODE_LATIN_SMALL_LETTER_T_WITH_DIAGONAL_STROKE 0x2c66 #define UNITEXT_LATIN_SMALL_LETTER_T_WITH_DIAGONAL_STROKE L"\u2c66" #define UNICODE_LATIN_CAPITAL_LETTER_H_WITH_DESCENDER 0x2c67 #define UNITEXT_LATIN_CAPITAL_LETTER_H_WITH_DESCENDER L"\u2c67" #define UNICODE_LATIN_SMALL_LETTER_H_WITH_DESCENDER 0x2c68 #define UNITEXT_LATIN_SMALL_LETTER_H_WITH_DESCENDER L"\u2c68" #define UNICODE_LATIN_CAPITAL_LETTER_K_WITH_DESCENDER 0x2c69 #define UNITEXT_LATIN_CAPITAL_LETTER_K_WITH_DESCENDER L"\u2c69" #define UNICODE_LATIN_SMALL_LETTER_K_WITH_DESCENDER 0x2c6a #define UNITEXT_LATIN_SMALL_LETTER_K_WITH_DESCENDER L"\u2c6a" #define UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_DESCENDER 0x2c6b #define UNITEXT_LATIN_CAPITAL_LETTER_Z_WITH_DESCENDER L"\u2c6b" #define UNICODE_LATIN_SMALL_LETTER_Z_WITH_DESCENDER 0x2c6c #define UNITEXT_LATIN_SMALL_LETTER_Z_WITH_DESCENDER L"\u2c6c" #define UNICODE_LATIN_SMALL_LETTER_V_WITH_CURL 0x2c74 #define UNITEXT_LATIN_SMALL_LETTER_V_WITH_CURL L"\u2c74" #define UNICODE_LATIN_CAPITAL_LETTER_HALF_H 0x2c75 #define UNITEXT_LATIN_CAPITAL_LETTER_HALF_H L"\u2c75" #define UNICODE_LATIN_SMALL_LETTER_HALF_H 0x2c76 #define UNITEXT_LATIN_SMALL_LETTER_HALF_H L"\u2c76" #define UNICODE_LATIN_SMALL_LETTER_TAILLESS_PHI 0x2c77 #define UNITEXT_LATIN_SMALL_LETTER_TAILLESS_PHI L"\u2c77" #define UNICODE_COPTIC_CAPITAL_LETTER_ALFA 0x2c80 #define UNITEXT_COPTIC_CAPITAL_LETTER_ALFA L"\u2c80" #define UNICODE_COPTIC_SMALL_LETTER_ALFA 0x2c81 #define UNITEXT_COPTIC_SMALL_LETTER_ALFA L"\u2c81" #define UNICODE_COPTIC_CAPITAL_LETTER_VIDA 0x2c82 #define UNITEXT_COPTIC_CAPITAL_LETTER_VIDA L"\u2c82" #define UNICODE_COPTIC_SMALL_LETTER_VIDA 0x2c83 #define UNITEXT_COPTIC_SMALL_LETTER_VIDA L"\u2c83" #define UNICODE_COPTIC_CAPITAL_LETTER_GAMMA 0x2c84 #define UNITEXT_COPTIC_CAPITAL_LETTER_GAMMA L"\u2c84" #define UNICODE_COPTIC_SMALL_LETTER_GAMMA 0x2c85 #define UNITEXT_COPTIC_SMALL_LETTER_GAMMA L"\u2c85" #define UNICODE_COPTIC_CAPITAL_LETTER_DALDA 0x2c86 #define UNITEXT_COPTIC_CAPITAL_LETTER_DALDA L"\u2c86" #define UNICODE_COPTIC_SMALL_LETTER_DALDA 0x2c87 #define UNITEXT_COPTIC_SMALL_LETTER_DALDA L"\u2c87" #define UNICODE_COPTIC_CAPITAL_LETTER_EIE 0x2c88 #define UNITEXT_COPTIC_CAPITAL_LETTER_EIE L"\u2c88" #define UNICODE_COPTIC_SMALL_LETTER_EIE 0x2c89 #define UNITEXT_COPTIC_SMALL_LETTER_EIE L"\u2c89" #define UNICODE_COPTIC_CAPITAL_LETTER_SOU 0x2c8a #define UNITEXT_COPTIC_CAPITAL_LETTER_SOU L"\u2c8a" #define UNICODE_COPTIC_SMALL_LETTER_SOU 0x2c8b #define UNITEXT_COPTIC_SMALL_LETTER_SOU L"\u2c8b" #define UNICODE_COPTIC_CAPITAL_LETTER_ZATA 0x2c8c #define UNITEXT_COPTIC_CAPITAL_LETTER_ZATA L"\u2c8c" #define UNICODE_COPTIC_SMALL_LETTER_ZATA 0x2c8d #define UNITEXT_COPTIC_SMALL_LETTER_ZATA L"\u2c8d" #define UNICODE_COPTIC_CAPITAL_LETTER_HATE 0x2c8e #define UNITEXT_COPTIC_CAPITAL_LETTER_HATE L"\u2c8e" #define UNICODE_COPTIC_SMALL_LETTER_HATE 0x2c8f #define UNITEXT_COPTIC_SMALL_LETTER_HATE L"\u2c8f" #define UNICODE_COPTIC_CAPITAL_LETTER_THETHE 0x2c90 #define UNITEXT_COPTIC_CAPITAL_LETTER_THETHE L"\u2c90" #define UNICODE_COPTIC_SMALL_LETTER_THETHE 0x2c91 #define UNITEXT_COPTIC_SMALL_LETTER_THETHE L"\u2c91" #define UNICODE_COPTIC_CAPITAL_LETTER_IAUDA 0x2c92 #define UNITEXT_COPTIC_CAPITAL_LETTER_IAUDA L"\u2c92" #define UNICODE_COPTIC_SMALL_LETTER_IAUDA 0x2c93 #define UNITEXT_COPTIC_SMALL_LETTER_IAUDA L"\u2c93" #define UNICODE_COPTIC_CAPITAL_LETTER_KAPA 0x2c94 #define UNITEXT_COPTIC_CAPITAL_LETTER_KAPA L"\u2c94" #define UNICODE_COPTIC_SMALL_LETTER_KAPA 0x2c95 #define UNITEXT_COPTIC_SMALL_LETTER_KAPA L"\u2c95" #define UNICODE_COPTIC_CAPITAL_LETTER_LAULA 0x2c96 #define UNITEXT_COPTIC_CAPITAL_LETTER_LAULA L"\u2c96" #define UNICODE_COPTIC_SMALL_LETTER_LAULA 0x2c97 #define UNITEXT_COPTIC_SMALL_LETTER_LAULA L"\u2c97" #define UNICODE_COPTIC_CAPITAL_LETTER_MI 0x2c98 #define UNITEXT_COPTIC_CAPITAL_LETTER_MI L"\u2c98" #define UNICODE_COPTIC_SMALL_LETTER_MI 0x2c99 #define UNITEXT_COPTIC_SMALL_LETTER_MI L"\u2c99" #define UNICODE_COPTIC_CAPITAL_LETTER_NI 0x2c9a #define UNITEXT_COPTIC_CAPITAL_LETTER_NI L"\u2c9a" #define UNICODE_COPTIC_SMALL_LETTER_NI 0x2c9b #define UNITEXT_COPTIC_SMALL_LETTER_NI L"\u2c9b" #define UNICODE_COPTIC_CAPITAL_LETTER_KSI 0x2c9c #define UNITEXT_COPTIC_CAPITAL_LETTER_KSI L"\u2c9c" #define UNICODE_COPTIC_SMALL_LETTER_KSI 0x2c9d #define UNITEXT_COPTIC_SMALL_LETTER_KSI L"\u2c9d" #define UNICODE_COPTIC_CAPITAL_LETTER_O 0x2c9e #define UNITEXT_COPTIC_CAPITAL_LETTER_O L"\u2c9e" #define UNICODE_COPTIC_SMALL_LETTER_O 0x2c9f #define UNITEXT_COPTIC_SMALL_LETTER_O L"\u2c9f" #define UNICODE_COPTIC_CAPITAL_LETTER_PI 0x2ca0 #define UNITEXT_COPTIC_CAPITAL_LETTER_PI L"\u2ca0" #define UNICODE_COPTIC_SMALL_LETTER_PI 0x2ca1 #define UNITEXT_COPTIC_SMALL_LETTER_PI L"\u2ca1" #define UNICODE_COPTIC_CAPITAL_LETTER_RO 0x2ca2 #define UNITEXT_COPTIC_CAPITAL_LETTER_RO L"\u2ca2" #define UNICODE_COPTIC_SMALL_LETTER_RO 0x2ca3 #define UNITEXT_COPTIC_SMALL_LETTER_RO L"\u2ca3" #define UNICODE_COPTIC_CAPITAL_LETTER_SIMA 0x2ca4 #define UNITEXT_COPTIC_CAPITAL_LETTER_SIMA L"\u2ca4" #define UNICODE_COPTIC_SMALL_LETTER_SIMA 0x2ca5 #define UNITEXT_COPTIC_SMALL_LETTER_SIMA L"\u2ca5" #define UNICODE_COPTIC_CAPITAL_LETTER_TAU 0x2ca6 #define UNITEXT_COPTIC_CAPITAL_LETTER_TAU L"\u2ca6" #define UNICODE_COPTIC_SMALL_LETTER_TAU 0x2ca7 #define UNITEXT_COPTIC_SMALL_LETTER_TAU L"\u2ca7" #define UNICODE_COPTIC_CAPITAL_LETTER_UA 0x2ca8 #define UNITEXT_COPTIC_CAPITAL_LETTER_UA L"\u2ca8" #define UNICODE_COPTIC_SMALL_LETTER_UA 0x2ca9 #define UNITEXT_COPTIC_SMALL_LETTER_UA L"\u2ca9" #define UNICODE_COPTIC_CAPITAL_LETTER_FI 0x2caa #define UNITEXT_COPTIC_CAPITAL_LETTER_FI L"\u2caa" #define UNICODE_COPTIC_SMALL_LETTER_FI 0x2cab #define UNITEXT_COPTIC_SMALL_LETTER_FI L"\u2cab" #define UNICODE_COPTIC_CAPITAL_LETTER_KHI 0x2cac #define UNITEXT_COPTIC_CAPITAL_LETTER_KHI L"\u2cac" #define UNICODE_COPTIC_SMALL_LETTER_KHI 0x2cad #define UNITEXT_COPTIC_SMALL_LETTER_KHI L"\u2cad" #define UNICODE_COPTIC_CAPITAL_LETTER_PSI 0x2cae #define UNITEXT_COPTIC_CAPITAL_LETTER_PSI L"\u2cae" #define UNICODE_COPTIC_SMALL_LETTER_PSI 0x2caf #define UNITEXT_COPTIC_SMALL_LETTER_PSI L"\u2caf" #define UNICODE_COPTIC_CAPITAL_LETTER_OOU 0x2cb0 #define UNITEXT_COPTIC_CAPITAL_LETTER_OOU L"\u2cb0" #define UNICODE_COPTIC_SMALL_LETTER_OOU 0x2cb1 #define UNITEXT_COPTIC_SMALL_LETTER_OOU L"\u2cb1" #define UNICODE_COPTIC_CAPITAL_LETTER_DIALECT_P_ALEF 0x2cb2 #define UNITEXT_COPTIC_CAPITAL_LETTER_DIALECT_P_ALEF L"\u2cb2" #define UNICODE_COPTIC_SMALL_LETTER_DIALECT_P_ALEF 0x2cb3 #define UNITEXT_COPTIC_SMALL_LETTER_DIALECT_P_ALEF L"\u2cb3" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_AIN 0x2cb4 #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_AIN L"\u2cb4" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_AIN 0x2cb5 #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_AIN L"\u2cb5" #define UNICODE_COPTIC_CAPITAL_LETTER_CRYPTOGRAMMIC_EIE 0x2cb6 #define UNITEXT_COPTIC_CAPITAL_LETTER_CRYPTOGRAMMIC_EIE L"\u2cb6" #define UNICODE_COPTIC_SMALL_LETTER_CRYPTOGRAMMIC_EIE 0x2cb7 #define UNITEXT_COPTIC_SMALL_LETTER_CRYPTOGRAMMIC_EIE L"\u2cb7" #define UNICODE_COPTIC_CAPITAL_LETTER_DIALECT_P_KAPA 0x2cb8 #define UNITEXT_COPTIC_CAPITAL_LETTER_DIALECT_P_KAPA L"\u2cb8" #define UNICODE_COPTIC_SMALL_LETTER_DIALECT_P_KAPA 0x2cb9 #define UNITEXT_COPTIC_SMALL_LETTER_DIALECT_P_KAPA L"\u2cb9" #define UNICODE_COPTIC_CAPITAL_LETTER_DIALECT_P_NI 0x2cba #define UNITEXT_COPTIC_CAPITAL_LETTER_DIALECT_P_NI L"\u2cba" #define UNICODE_COPTIC_SMALL_LETTER_DIALECT_P_NI 0x2cbb #define UNITEXT_COPTIC_SMALL_LETTER_DIALECT_P_NI L"\u2cbb" #define UNICODE_COPTIC_CAPITAL_LETTER_CRYPTOGRAMMIC_NI 0x2cbc #define UNITEXT_COPTIC_CAPITAL_LETTER_CRYPTOGRAMMIC_NI L"\u2cbc" #define UNICODE_COPTIC_SMALL_LETTER_CRYPTOGRAMMIC_NI 0x2cbd #define UNITEXT_COPTIC_SMALL_LETTER_CRYPTOGRAMMIC_NI L"\u2cbd" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_OOU 0x2cbe #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_OOU L"\u2cbe" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_OOU 0x2cbf #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_OOU L"\u2cbf" #define UNICODE_COPTIC_CAPITAL_LETTER_SAMPI 0x2cc0 #define UNITEXT_COPTIC_CAPITAL_LETTER_SAMPI L"\u2cc0" #define UNICODE_COPTIC_SMALL_LETTER_SAMPI 0x2cc1 #define UNITEXT_COPTIC_SMALL_LETTER_SAMPI L"\u2cc1" #define UNICODE_COPTIC_CAPITAL_LETTER_CROSSED_SHEI 0x2cc2 #define UNITEXT_COPTIC_CAPITAL_LETTER_CROSSED_SHEI L"\u2cc2" #define UNICODE_COPTIC_SMALL_LETTER_CROSSED_SHEI 0x2cc3 #define UNITEXT_COPTIC_SMALL_LETTER_CROSSED_SHEI L"\u2cc3" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_SHEI 0x2cc4 #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_SHEI L"\u2cc4" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_SHEI 0x2cc5 #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_SHEI L"\u2cc5" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_ESH 0x2cc6 #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_ESH L"\u2cc6" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_ESH 0x2cc7 #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_ESH L"\u2cc7" #define UNICODE_COPTIC_CAPITAL_LETTER_AKHMIMIC_KHEI 0x2cc8 #define UNITEXT_COPTIC_CAPITAL_LETTER_AKHMIMIC_KHEI L"\u2cc8" #define UNICODE_COPTIC_SMALL_LETTER_AKHMIMIC_KHEI 0x2cc9 #define UNITEXT_COPTIC_SMALL_LETTER_AKHMIMIC_KHEI L"\u2cc9" #define UNICODE_COPTIC_CAPITAL_LETTER_DIALECT_P_HORI 0x2cca #define UNITEXT_COPTIC_CAPITAL_LETTER_DIALECT_P_HORI L"\u2cca" #define UNICODE_COPTIC_SMALL_LETTER_DIALECT_P_HORI 0x2ccb #define UNITEXT_COPTIC_SMALL_LETTER_DIALECT_P_HORI L"\u2ccb" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_HORI 0x2ccc #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_HORI L"\u2ccc" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_HORI 0x2ccd #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_HORI L"\u2ccd" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_HA 0x2cce #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_HA L"\u2cce" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_HA 0x2ccf #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_HA L"\u2ccf" #define UNICODE_COPTIC_CAPITAL_LETTER_L_SHAPED_HA 0x2cd0 #define UNITEXT_COPTIC_CAPITAL_LETTER_L_SHAPED_HA L"\u2cd0" #define UNICODE_COPTIC_SMALL_LETTER_L_SHAPED_HA 0x2cd1 #define UNITEXT_COPTIC_SMALL_LETTER_L_SHAPED_HA L"\u2cd1" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_HEI 0x2cd2 #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_HEI L"\u2cd2" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_HEI 0x2cd3 #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_HEI L"\u2cd3" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_HAT 0x2cd4 #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_HAT L"\u2cd4" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_HAT 0x2cd5 #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_HAT L"\u2cd5" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_GANGIA 0x2cd6 #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_GANGIA L"\u2cd6" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_GANGIA 0x2cd7 #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_GANGIA L"\u2cd7" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_DJA 0x2cd8 #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_DJA L"\u2cd8" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_DJA 0x2cd9 #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_DJA L"\u2cd9" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_COPTIC_SHIMA 0x2cda #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_COPTIC_SHIMA L"\u2cda" #define UNICODE_COPTIC_SMALL_LETTER_OLD_COPTIC_SHIMA 0x2cdb #define UNITEXT_COPTIC_SMALL_LETTER_OLD_COPTIC_SHIMA L"\u2cdb" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_NUBIAN_SHIMA 0x2cdc #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_NUBIAN_SHIMA L"\u2cdc" #define UNICODE_COPTIC_SMALL_LETTER_OLD_NUBIAN_SHIMA 0x2cdd #define UNITEXT_COPTIC_SMALL_LETTER_OLD_NUBIAN_SHIMA L"\u2cdd" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_NUBIAN_NGI 0x2cde #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_NUBIAN_NGI L"\u2cde" #define UNICODE_COPTIC_SMALL_LETTER_OLD_NUBIAN_NGI 0x2cdf #define UNITEXT_COPTIC_SMALL_LETTER_OLD_NUBIAN_NGI L"\u2cdf" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_NUBIAN_NYI 0x2ce0 #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_NUBIAN_NYI L"\u2ce0" #define UNICODE_COPTIC_SMALL_LETTER_OLD_NUBIAN_NYI 0x2ce1 #define UNITEXT_COPTIC_SMALL_LETTER_OLD_NUBIAN_NYI L"\u2ce1" #define UNICODE_COPTIC_CAPITAL_LETTER_OLD_NUBIAN_WAU 0x2ce2 #define UNITEXT_COPTIC_CAPITAL_LETTER_OLD_NUBIAN_WAU L"\u2ce2" #define UNICODE_COPTIC_SMALL_LETTER_OLD_NUBIAN_WAU 0x2ce3 #define UNITEXT_COPTIC_SMALL_LETTER_OLD_NUBIAN_WAU L"\u2ce3" #define UNICODE_COPTIC_SYMBOL_KAI 0x2ce4 #define UNITEXT_COPTIC_SYMBOL_KAI L"\u2ce4" #define UNICODE_COPTIC_SYMBOL_MI_RO 0x2ce5 #define UNITEXT_COPTIC_SYMBOL_MI_RO L"\u2ce5" #define UNICODE_COPTIC_SYMBOL_PI_RO 0x2ce6 #define UNITEXT_COPTIC_SYMBOL_PI_RO L"\u2ce6" #define UNICODE_COPTIC_SYMBOL_STAUROS 0x2ce7 #define UNITEXT_COPTIC_SYMBOL_STAUROS L"\u2ce7" #define UNICODE_COPTIC_SYMBOL_TAU_RO 0x2ce8 #define UNITEXT_COPTIC_SYMBOL_TAU_RO L"\u2ce8" #define UNICODE_COPTIC_SYMBOL_KHI_RO 0x2ce9 #define UNITEXT_COPTIC_SYMBOL_KHI_RO L"\u2ce9" #define UNICODE_COPTIC_SYMBOL_SHIMA_SIMA 0x2cea #define UNITEXT_COPTIC_SYMBOL_SHIMA_SIMA L"\u2cea" #define UNICODE_COPTIC_OLD_NUBIAN_FULL_STOP 0x2cf9 #define UNITEXT_COPTIC_OLD_NUBIAN_FULL_STOP L"\u2cf9" #define UNICODE_COPTIC_OLD_NUBIAN_DIRECT_QUESTION_MARK 0x2cfa #define UNITEXT_COPTIC_OLD_NUBIAN_DIRECT_QUESTION_MARK L"\u2cfa" #define UNICODE_COPTIC_OLD_NUBIAN_INDIRECT_QUESTION_MARK 0x2cfb #define UNITEXT_COPTIC_OLD_NUBIAN_INDIRECT_QUESTION_MARK L"\u2cfb" #define UNICODE_COPTIC_OLD_NUBIAN_VERSE_DIVIDER 0x2cfc #define UNITEXT_COPTIC_OLD_NUBIAN_VERSE_DIVIDER L"\u2cfc" #define UNICODE_COPTIC_FRACTION_ONE_HALF 0x2cfd #define UNITEXT_COPTIC_FRACTION_ONE_HALF L"\u2cfd" #define UNICODE_COPTIC_FULL_STOP 0x2cfe #define UNITEXT_COPTIC_FULL_STOP L"\u2cfe" #define UNICODE_COPTIC_MORPHOLOGICAL_DIVIDER 0x2cff #define UNITEXT_COPTIC_MORPHOLOGICAL_DIVIDER L"\u2cff" #define UNICODE_GEORGIAN_SMALL_LETTER_AN 0x2d00 #define UNITEXT_GEORGIAN_SMALL_LETTER_AN L"\u2d00" #define UNICODE_GEORGIAN_SMALL_LETTER_BAN 0x2d01 #define UNITEXT_GEORGIAN_SMALL_LETTER_BAN L"\u2d01" #define UNICODE_GEORGIAN_SMALL_LETTER_GAN 0x2d02 #define UNITEXT_GEORGIAN_SMALL_LETTER_GAN L"\u2d02" #define UNICODE_GEORGIAN_SMALL_LETTER_DON 0x2d03 #define UNITEXT_GEORGIAN_SMALL_LETTER_DON L"\u2d03" #define UNICODE_GEORGIAN_SMALL_LETTER_EN 0x2d04 #define UNITEXT_GEORGIAN_SMALL_LETTER_EN L"\u2d04" #define UNICODE_GEORGIAN_SMALL_LETTER_VIN 0x2d05 #define UNITEXT_GEORGIAN_SMALL_LETTER_VIN L"\u2d05" #define UNICODE_GEORGIAN_SMALL_LETTER_ZEN 0x2d06 #define UNITEXT_GEORGIAN_SMALL_LETTER_ZEN L"\u2d06" #define UNICODE_GEORGIAN_SMALL_LETTER_TAN 0x2d07 #define UNITEXT_GEORGIAN_SMALL_LETTER_TAN L"\u2d07" #define UNICODE_GEORGIAN_SMALL_LETTER_IN 0x2d08 #define UNITEXT_GEORGIAN_SMALL_LETTER_IN L"\u2d08" #define UNICODE_GEORGIAN_SMALL_LETTER_KAN 0x2d09 #define UNITEXT_GEORGIAN_SMALL_LETTER_KAN L"\u2d09" #define UNICODE_GEORGIAN_SMALL_LETTER_LAS 0x2d0a #define UNITEXT_GEORGIAN_SMALL_LETTER_LAS L"\u2d0a" #define UNICODE_GEORGIAN_SMALL_LETTER_MAN 0x2d0b #define UNITEXT_GEORGIAN_SMALL_LETTER_MAN L"\u2d0b" #define UNICODE_GEORGIAN_SMALL_LETTER_NAR 0x2d0c #define UNITEXT_GEORGIAN_SMALL_LETTER_NAR L"\u2d0c" #define UNICODE_GEORGIAN_SMALL_LETTER_ON 0x2d0d #define UNITEXT_GEORGIAN_SMALL_LETTER_ON L"\u2d0d" #define UNICODE_GEORGIAN_SMALL_LETTER_PAR 0x2d0e #define UNITEXT_GEORGIAN_SMALL_LETTER_PAR L"\u2d0e" #define UNICODE_GEORGIAN_SMALL_LETTER_ZHAR 0x2d0f #define UNITEXT_GEORGIAN_SMALL_LETTER_ZHAR L"\u2d0f" #define UNICODE_GEORGIAN_SMALL_LETTER_RAE 0x2d10 #define UNITEXT_GEORGIAN_SMALL_LETTER_RAE L"\u2d10" #define UNICODE_GEORGIAN_SMALL_LETTER_SAN 0x2d11 #define UNITEXT_GEORGIAN_SMALL_LETTER_SAN L"\u2d11" #define UNICODE_GEORGIAN_SMALL_LETTER_TAR 0x2d12 #define UNITEXT_GEORGIAN_SMALL_LETTER_TAR L"\u2d12" #define UNICODE_GEORGIAN_SMALL_LETTER_UN 0x2d13 #define UNITEXT_GEORGIAN_SMALL_LETTER_UN L"\u2d13" #define UNICODE_GEORGIAN_SMALL_LETTER_PHAR 0x2d14 #define UNITEXT_GEORGIAN_SMALL_LETTER_PHAR L"\u2d14" #define UNICODE_GEORGIAN_SMALL_LETTER_KHAR 0x2d15 #define UNITEXT_GEORGIAN_SMALL_LETTER_KHAR L"\u2d15" #define UNICODE_GEORGIAN_SMALL_LETTER_GHAN 0x2d16 #define UNITEXT_GEORGIAN_SMALL_LETTER_GHAN L"\u2d16" #define UNICODE_GEORGIAN_SMALL_LETTER_QAR 0x2d17 #define UNITEXT_GEORGIAN_SMALL_LETTER_QAR L"\u2d17" #define UNICODE_GEORGIAN_SMALL_LETTER_SHIN 0x2d18 #define UNITEXT_GEORGIAN_SMALL_LETTER_SHIN L"\u2d18" #define UNICODE_GEORGIAN_SMALL_LETTER_CHIN 0x2d19 #define UNITEXT_GEORGIAN_SMALL_LETTER_CHIN L"\u2d19" #define UNICODE_GEORGIAN_SMALL_LETTER_CAN 0x2d1a #define UNITEXT_GEORGIAN_SMALL_LETTER_CAN L"\u2d1a" #define UNICODE_GEORGIAN_SMALL_LETTER_JIL 0x2d1b #define UNITEXT_GEORGIAN_SMALL_LETTER_JIL L"\u2d1b" #define UNICODE_GEORGIAN_SMALL_LETTER_CIL 0x2d1c #define UNITEXT_GEORGIAN_SMALL_LETTER_CIL L"\u2d1c" #define UNICODE_GEORGIAN_SMALL_LETTER_CHAR 0x2d1d #define UNITEXT_GEORGIAN_SMALL_LETTER_CHAR L"\u2d1d" #define UNICODE_GEORGIAN_SMALL_LETTER_XAN 0x2d1e #define UNITEXT_GEORGIAN_SMALL_LETTER_XAN L"\u2d1e" #define UNICODE_GEORGIAN_SMALL_LETTER_JHAN 0x2d1f #define UNITEXT_GEORGIAN_SMALL_LETTER_JHAN L"\u2d1f" #define UNICODE_GEORGIAN_SMALL_LETTER_HAE 0x2d20 #define UNITEXT_GEORGIAN_SMALL_LETTER_HAE L"\u2d20" #define UNICODE_GEORGIAN_SMALL_LETTER_HE 0x2d21 #define UNITEXT_GEORGIAN_SMALL_LETTER_HE L"\u2d21" #define UNICODE_GEORGIAN_SMALL_LETTER_HIE 0x2d22 #define UNITEXT_GEORGIAN_SMALL_LETTER_HIE L"\u2d22" #define UNICODE_GEORGIAN_SMALL_LETTER_WE 0x2d23 #define UNITEXT_GEORGIAN_SMALL_LETTER_WE L"\u2d23" #define UNICODE_GEORGIAN_SMALL_LETTER_HAR 0x2d24 #define UNITEXT_GEORGIAN_SMALL_LETTER_HAR L"\u2d24" #define UNICODE_GEORGIAN_SMALL_LETTER_HOE 0x2d25 #define UNITEXT_GEORGIAN_SMALL_LETTER_HOE L"\u2d25" #define UNICODE_TIFINAGH_LETTER_YA 0x2d30 #define UNITEXT_TIFINAGH_LETTER_YA L"\u2d30" #define UNICODE_TIFINAGH_LETTER_YAB 0x2d31 #define UNITEXT_TIFINAGH_LETTER_YAB L"\u2d31" #define UNICODE_TIFINAGH_LETTER_YABH 0x2d32 #define UNITEXT_TIFINAGH_LETTER_YABH L"\u2d32" #define UNICODE_TIFINAGH_LETTER_YAG 0x2d33 #define UNITEXT_TIFINAGH_LETTER_YAG L"\u2d33" #define UNICODE_TIFINAGH_LETTER_YAGHH 0x2d34 #define UNITEXT_TIFINAGH_LETTER_YAGHH L"\u2d34" #define UNICODE_TIFINAGH_LETTER_BERBER_ACADEMY_YAJ 0x2d35 #define UNITEXT_TIFINAGH_LETTER_BERBER_ACADEMY_YAJ L"\u2d35" #define UNICODE_TIFINAGH_LETTER_YAJ 0x2d36 #define UNITEXT_TIFINAGH_LETTER_YAJ L"\u2d36" #define UNICODE_TIFINAGH_LETTER_YAD 0x2d37 #define UNITEXT_TIFINAGH_LETTER_YAD L"\u2d37" #define UNICODE_TIFINAGH_LETTER_YADH 0x2d38 #define UNITEXT_TIFINAGH_LETTER_YADH L"\u2d38" #define UNICODE_TIFINAGH_LETTER_YADD 0x2d39 #define UNITEXT_TIFINAGH_LETTER_YADD L"\u2d39" #define UNICODE_TIFINAGH_LETTER_YADDH 0x2d3a #define UNITEXT_TIFINAGH_LETTER_YADDH L"\u2d3a" #define UNICODE_TIFINAGH_LETTER_YEY 0x2d3b #define UNITEXT_TIFINAGH_LETTER_YEY L"\u2d3b" #define UNICODE_TIFINAGH_LETTER_YAF 0x2d3c #define UNITEXT_TIFINAGH_LETTER_YAF L"\u2d3c" #define UNICODE_TIFINAGH_LETTER_YAK 0x2d3d #define UNITEXT_TIFINAGH_LETTER_YAK L"\u2d3d" #define UNICODE_TIFINAGH_LETTER_TUAREG_YAK 0x2d3e #define UNITEXT_TIFINAGH_LETTER_TUAREG_YAK L"\u2d3e" #define UNICODE_TIFINAGH_LETTER_YAKHH 0x2d3f #define UNITEXT_TIFINAGH_LETTER_YAKHH L"\u2d3f" #define UNICODE_TIFINAGH_LETTER_YAH 0x2d40 #define UNITEXT_TIFINAGH_LETTER_YAH L"\u2d40" #define UNICODE_TIFINAGH_LETTER_BERBER_ACADEMY_YAH 0x2d41 #define UNITEXT_TIFINAGH_LETTER_BERBER_ACADEMY_YAH L"\u2d41" #define UNICODE_TIFINAGH_LETTER_TUAREG_YAH 0x2d42 #define UNITEXT_TIFINAGH_LETTER_TUAREG_YAH L"\u2d42" #define UNICODE_TIFINAGH_LETTER_YAHH 0x2d43 #define UNITEXT_TIFINAGH_LETTER_YAHH L"\u2d43" #define UNICODE_TIFINAGH_LETTER_YAA 0x2d44 #define UNITEXT_TIFINAGH_LETTER_YAA L"\u2d44" #define UNICODE_TIFINAGH_LETTER_YAKH 0x2d45 #define UNITEXT_TIFINAGH_LETTER_YAKH L"\u2d45" #define UNICODE_TIFINAGH_LETTER_TUAREG_YAKH 0x2d46 #define UNITEXT_TIFINAGH_LETTER_TUAREG_YAKH L"\u2d46" #define UNICODE_TIFINAGH_LETTER_YAQ 0x2d47 #define UNITEXT_TIFINAGH_LETTER_YAQ L"\u2d47" #define UNICODE_TIFINAGH_LETTER_TUAREG_YAQ 0x2d48 #define UNITEXT_TIFINAGH_LETTER_TUAREG_YAQ L"\u2d48" #define UNICODE_TIFINAGH_LETTER_YI 0x2d49 #define UNITEXT_TIFINAGH_LETTER_YI L"\u2d49" #define UNICODE_TIFINAGH_LETTER_YAZH 0x2d4a #define UNITEXT_TIFINAGH_LETTER_YAZH L"\u2d4a" #define UNICODE_TIFINAGH_LETTER_AHAGGAR_YAZH 0x2d4b #define UNITEXT_TIFINAGH_LETTER_AHAGGAR_YAZH L"\u2d4b" #define UNICODE_TIFINAGH_LETTER_TUAREG_YAZH 0x2d4c #define UNITEXT_TIFINAGH_LETTER_TUAREG_YAZH L"\u2d4c" #define UNICODE_TIFINAGH_LETTER_YAL 0x2d4d #define UNITEXT_TIFINAGH_LETTER_YAL L"\u2d4d" #define UNICODE_TIFINAGH_LETTER_YAM 0x2d4e #define UNITEXT_TIFINAGH_LETTER_YAM L"\u2d4e" #define UNICODE_TIFINAGH_LETTER_YAN 0x2d4f #define UNITEXT_TIFINAGH_LETTER_YAN L"\u2d4f" #define UNICODE_TIFINAGH_LETTER_TUAREG_YAGN 0x2d50 #define UNITEXT_TIFINAGH_LETTER_TUAREG_YAGN L"\u2d50" #define UNICODE_TIFINAGH_LETTER_TUAREG_YANG 0x2d51 #define UNITEXT_TIFINAGH_LETTER_TUAREG_YANG L"\u2d51" #define UNICODE_TIFINAGH_LETTER_YAP 0x2d52 #define UNITEXT_TIFINAGH_LETTER_YAP L"\u2d52" #define UNICODE_TIFINAGH_LETTER_YU 0x2d53 #define UNITEXT_TIFINAGH_LETTER_YU L"\u2d53" #define UNICODE_TIFINAGH_LETTER_YAR 0x2d54 #define UNITEXT_TIFINAGH_LETTER_YAR L"\u2d54" #define UNICODE_TIFINAGH_LETTER_YARR 0x2d55 #define UNITEXT_TIFINAGH_LETTER_YARR L"\u2d55" #define UNICODE_TIFINAGH_LETTER_YAGH 0x2d56 #define UNITEXT_TIFINAGH_LETTER_YAGH L"\u2d56" #define UNICODE_TIFINAGH_LETTER_TUAREG_YAGH 0x2d57 #define UNITEXT_TIFINAGH_LETTER_TUAREG_YAGH L"\u2d57" #define UNICODE_TIFINAGH_LETTER_AYER_YAGH 0x2d58 #define UNITEXT_TIFINAGH_LETTER_AYER_YAGH L"\u2d58" #define UNICODE_TIFINAGH_LETTER_YAS 0x2d59 #define UNITEXT_TIFINAGH_LETTER_YAS L"\u2d59" #define UNICODE_TIFINAGH_LETTER_YASS 0x2d5a #define UNITEXT_TIFINAGH_LETTER_YASS L"\u2d5a" #define UNICODE_TIFINAGH_LETTER_YASH 0x2d5b #define UNITEXT_TIFINAGH_LETTER_YASH L"\u2d5b" #define UNICODE_TIFINAGH_LETTER_YAT 0x2d5c #define UNITEXT_TIFINAGH_LETTER_YAT L"\u2d5c" #define UNICODE_TIFINAGH_LETTER_YATH 0x2d5d #define UNITEXT_TIFINAGH_LETTER_YATH L"\u2d5d" #define UNICODE_TIFINAGH_LETTER_YACH 0x2d5e #define UNITEXT_TIFINAGH_LETTER_YACH L"\u2d5e" #define UNICODE_TIFINAGH_LETTER_YATT 0x2d5f #define UNITEXT_TIFINAGH_LETTER_YATT L"\u2d5f" #define UNICODE_TIFINAGH_LETTER_YAV 0x2d60 #define UNITEXT_TIFINAGH_LETTER_YAV L"\u2d60" #define UNICODE_TIFINAGH_LETTER_YAW 0x2d61 #define UNITEXT_TIFINAGH_LETTER_YAW L"\u2d61" #define UNICODE_TIFINAGH_LETTER_YAY 0x2d62 #define UNITEXT_TIFINAGH_LETTER_YAY L"\u2d62" #define UNICODE_TIFINAGH_LETTER_YAZ 0x2d63 #define UNITEXT_TIFINAGH_LETTER_YAZ L"\u2d63" #define UNICODE_TIFINAGH_LETTER_TAWELLEMET_YAZ 0x2d64 #define UNITEXT_TIFINAGH_LETTER_TAWELLEMET_YAZ L"\u2d64" #define UNICODE_TIFINAGH_LETTER_YAZZ 0x2d65 #define UNITEXT_TIFINAGH_LETTER_YAZZ L"\u2d65" #define UNICODE_TIFINAGH_MODIFIER_LETTER_LABIALIZATION_MARK 0x2d6f #define UNITEXT_TIFINAGH_MODIFIER_LETTER_LABIALIZATION_MARK L"\u2d6f" #define UNICODE_ETHIOPIC_SYLLABLE_LOA 0x2d80 #define UNITEXT_ETHIOPIC_SYLLABLE_LOA L"\u2d80" #define UNICODE_ETHIOPIC_SYLLABLE_MOA 0x2d81 #define UNITEXT_ETHIOPIC_SYLLABLE_MOA L"\u2d81" #define UNICODE_ETHIOPIC_SYLLABLE_ROA 0x2d82 #define UNITEXT_ETHIOPIC_SYLLABLE_ROA L"\u2d82" #define UNICODE_ETHIOPIC_SYLLABLE_SOA 0x2d83 #define UNITEXT_ETHIOPIC_SYLLABLE_SOA L"\u2d83" #define UNICODE_ETHIOPIC_SYLLABLE_SHOA 0x2d84 #define UNITEXT_ETHIOPIC_SYLLABLE_SHOA L"\u2d84" #define UNICODE_ETHIOPIC_SYLLABLE_BOA 0x2d85 #define UNITEXT_ETHIOPIC_SYLLABLE_BOA L"\u2d85" #define UNICODE_ETHIOPIC_SYLLABLE_TOA 0x2d86 #define UNITEXT_ETHIOPIC_SYLLABLE_TOA L"\u2d86" #define UNICODE_ETHIOPIC_SYLLABLE_COA 0x2d87 #define UNITEXT_ETHIOPIC_SYLLABLE_COA L"\u2d87" #define UNICODE_ETHIOPIC_SYLLABLE_NOA 0x2d88 #define UNITEXT_ETHIOPIC_SYLLABLE_NOA L"\u2d88" #define UNICODE_ETHIOPIC_SYLLABLE_NYOA 0x2d89 #define UNITEXT_ETHIOPIC_SYLLABLE_NYOA L"\u2d89" #define UNICODE_ETHIOPIC_SYLLABLE_GLOTTAL_OA 0x2d8a #define UNITEXT_ETHIOPIC_SYLLABLE_GLOTTAL_OA L"\u2d8a" #define UNICODE_ETHIOPIC_SYLLABLE_ZOA 0x2d8b #define UNITEXT_ETHIOPIC_SYLLABLE_ZOA L"\u2d8b" #define UNICODE_ETHIOPIC_SYLLABLE_DOA 0x2d8c #define UNITEXT_ETHIOPIC_SYLLABLE_DOA L"\u2d8c" #define UNICODE_ETHIOPIC_SYLLABLE_DDOA 0x2d8d #define UNITEXT_ETHIOPIC_SYLLABLE_DDOA L"\u2d8d" #define UNICODE_ETHIOPIC_SYLLABLE_JOA 0x2d8e #define UNITEXT_ETHIOPIC_SYLLABLE_JOA L"\u2d8e" #define UNICODE_ETHIOPIC_SYLLABLE_THOA 0x2d8f #define UNITEXT_ETHIOPIC_SYLLABLE_THOA L"\u2d8f" #define UNICODE_ETHIOPIC_SYLLABLE_CHOA 0x2d90 #define UNITEXT_ETHIOPIC_SYLLABLE_CHOA L"\u2d90" #define UNICODE_ETHIOPIC_SYLLABLE_PHOA 0x2d91 #define UNITEXT_ETHIOPIC_SYLLABLE_PHOA L"\u2d91" #define UNICODE_ETHIOPIC_SYLLABLE_POA 0x2d92 #define UNITEXT_ETHIOPIC_SYLLABLE_POA L"\u2d92" #define UNICODE_ETHIOPIC_SYLLABLE_GGWA 0x2d93 #define UNITEXT_ETHIOPIC_SYLLABLE_GGWA L"\u2d93" #define UNICODE_ETHIOPIC_SYLLABLE_GGWI 0x2d94 #define UNITEXT_ETHIOPIC_SYLLABLE_GGWI L"\u2d94" #define UNICODE_ETHIOPIC_SYLLABLE_GGWEE 0x2d95 #define UNITEXT_ETHIOPIC_SYLLABLE_GGWEE L"\u2d95" #define UNICODE_ETHIOPIC_SYLLABLE_GGWE 0x2d96 #define UNITEXT_ETHIOPIC_SYLLABLE_GGWE L"\u2d96" #define UNICODE_ETHIOPIC_SYLLABLE_SSA 0x2da0 #define UNITEXT_ETHIOPIC_SYLLABLE_SSA L"\u2da0" #define UNICODE_ETHIOPIC_SYLLABLE_SSU 0x2da1 #define UNITEXT_ETHIOPIC_SYLLABLE_SSU L"\u2da1" #define UNICODE_ETHIOPIC_SYLLABLE_SSI 0x2da2 #define UNITEXT_ETHIOPIC_SYLLABLE_SSI L"\u2da2" #define UNICODE_ETHIOPIC_SYLLABLE_SSAA 0x2da3 #define UNITEXT_ETHIOPIC_SYLLABLE_SSAA L"\u2da3" #define UNICODE_ETHIOPIC_SYLLABLE_SSEE 0x2da4 #define UNITEXT_ETHIOPIC_SYLLABLE_SSEE L"\u2da4" #define UNICODE_ETHIOPIC_SYLLABLE_SSE 0x2da5 #define UNITEXT_ETHIOPIC_SYLLABLE_SSE L"\u2da5" #define UNICODE_ETHIOPIC_SYLLABLE_SSO 0x2da6 #define UNITEXT_ETHIOPIC_SYLLABLE_SSO L"\u2da6" #define UNICODE_ETHIOPIC_SYLLABLE_CCA 0x2da8 #define UNITEXT_ETHIOPIC_SYLLABLE_CCA L"\u2da8" #define UNICODE_ETHIOPIC_SYLLABLE_CCU 0x2da9 #define UNITEXT_ETHIOPIC_SYLLABLE_CCU L"\u2da9" #define UNICODE_ETHIOPIC_SYLLABLE_CCI 0x2daa #define UNITEXT_ETHIOPIC_SYLLABLE_CCI L"\u2daa" #define UNICODE_ETHIOPIC_SYLLABLE_CCAA 0x2dab #define UNITEXT_ETHIOPIC_SYLLABLE_CCAA L"\u2dab" #define UNICODE_ETHIOPIC_SYLLABLE_CCEE 0x2dac #define UNITEXT_ETHIOPIC_SYLLABLE_CCEE L"\u2dac" #define UNICODE_ETHIOPIC_SYLLABLE_CCE 0x2dad #define UNITEXT_ETHIOPIC_SYLLABLE_CCE L"\u2dad" #define UNICODE_ETHIOPIC_SYLLABLE_CCO 0x2dae #define UNITEXT_ETHIOPIC_SYLLABLE_CCO L"\u2dae" #define UNICODE_ETHIOPIC_SYLLABLE_ZZA 0x2db0 #define UNITEXT_ETHIOPIC_SYLLABLE_ZZA L"\u2db0" #define UNICODE_ETHIOPIC_SYLLABLE_ZZU 0x2db1 #define UNITEXT_ETHIOPIC_SYLLABLE_ZZU L"\u2db1" #define UNICODE_ETHIOPIC_SYLLABLE_ZZI 0x2db2 #define UNITEXT_ETHIOPIC_SYLLABLE_ZZI L"\u2db2" #define UNICODE_ETHIOPIC_SYLLABLE_ZZAA 0x2db3 #define UNITEXT_ETHIOPIC_SYLLABLE_ZZAA L"\u2db3" #define UNICODE_ETHIOPIC_SYLLABLE_ZZEE 0x2db4 #define UNITEXT_ETHIOPIC_SYLLABLE_ZZEE L"\u2db4" #define UNICODE_ETHIOPIC_SYLLABLE_ZZE 0x2db5 #define UNITEXT_ETHIOPIC_SYLLABLE_ZZE L"\u2db5" #define UNICODE_ETHIOPIC_SYLLABLE_ZZO 0x2db6 #define UNITEXT_ETHIOPIC_SYLLABLE_ZZO L"\u2db6" #define UNICODE_ETHIOPIC_SYLLABLE_CCHA 0x2db8 #define UNITEXT_ETHIOPIC_SYLLABLE_CCHA L"\u2db8" #define UNICODE_ETHIOPIC_SYLLABLE_CCHU 0x2db9 #define UNITEXT_ETHIOPIC_SYLLABLE_CCHU L"\u2db9" #define UNICODE_ETHIOPIC_SYLLABLE_CCHI 0x2dba #define UNITEXT_ETHIOPIC_SYLLABLE_CCHI L"\u2dba" #define UNICODE_ETHIOPIC_SYLLABLE_CCHAA 0x2dbb #define UNITEXT_ETHIOPIC_SYLLABLE_CCHAA L"\u2dbb" #define UNICODE_ETHIOPIC_SYLLABLE_CCHEE 0x2dbc #define UNITEXT_ETHIOPIC_SYLLABLE_CCHEE L"\u2dbc" #define UNICODE_ETHIOPIC_SYLLABLE_CCHE 0x2dbd #define UNITEXT_ETHIOPIC_SYLLABLE_CCHE L"\u2dbd" #define UNICODE_ETHIOPIC_SYLLABLE_CCHO 0x2dbe #define UNITEXT_ETHIOPIC_SYLLABLE_CCHO L"\u2dbe" #define UNICODE_ETHIOPIC_SYLLABLE_QYA 0x2dc0 #define UNITEXT_ETHIOPIC_SYLLABLE_QYA L"\u2dc0" #define UNICODE_ETHIOPIC_SYLLABLE_QYU 0x2dc1 #define UNITEXT_ETHIOPIC_SYLLABLE_QYU L"\u2dc1" #define UNICODE_ETHIOPIC_SYLLABLE_QYI 0x2dc2 #define UNITEXT_ETHIOPIC_SYLLABLE_QYI L"\u2dc2" #define UNICODE_ETHIOPIC_SYLLABLE_QYAA 0x2dc3 #define UNITEXT_ETHIOPIC_SYLLABLE_QYAA L"\u2dc3" #define UNICODE_ETHIOPIC_SYLLABLE_QYEE 0x2dc4 #define UNITEXT_ETHIOPIC_SYLLABLE_QYEE L"\u2dc4" #define UNICODE_ETHIOPIC_SYLLABLE_QYE 0x2dc5 #define UNITEXT_ETHIOPIC_SYLLABLE_QYE L"\u2dc5" #define UNICODE_ETHIOPIC_SYLLABLE_QYO 0x2dc6 #define UNITEXT_ETHIOPIC_SYLLABLE_QYO L"\u2dc6" #define UNICODE_ETHIOPIC_SYLLABLE_KYA 0x2dc8 #define UNITEXT_ETHIOPIC_SYLLABLE_KYA L"\u2dc8" #define UNICODE_ETHIOPIC_SYLLABLE_KYU 0x2dc9 #define UNITEXT_ETHIOPIC_SYLLABLE_KYU L"\u2dc9" #define UNICODE_ETHIOPIC_SYLLABLE_KYI 0x2dca #define UNITEXT_ETHIOPIC_SYLLABLE_KYI L"\u2dca" #define UNICODE_ETHIOPIC_SYLLABLE_KYAA 0x2dcb #define UNITEXT_ETHIOPIC_SYLLABLE_KYAA L"\u2dcb" #define UNICODE_ETHIOPIC_SYLLABLE_KYEE 0x2dcc #define UNITEXT_ETHIOPIC_SYLLABLE_KYEE L"\u2dcc" #define UNICODE_ETHIOPIC_SYLLABLE_KYE 0x2dcd #define UNITEXT_ETHIOPIC_SYLLABLE_KYE L"\u2dcd" #define UNICODE_ETHIOPIC_SYLLABLE_KYO 0x2dce #define UNITEXT_ETHIOPIC_SYLLABLE_KYO L"\u2dce" #define UNICODE_ETHIOPIC_SYLLABLE_XYA 0x2dd0 #define UNITEXT_ETHIOPIC_SYLLABLE_XYA L"\u2dd0" #define UNICODE_ETHIOPIC_SYLLABLE_XYU 0x2dd1 #define UNITEXT_ETHIOPIC_SYLLABLE_XYU L"\u2dd1" #define UNICODE_ETHIOPIC_SYLLABLE_XYI 0x2dd2 #define UNITEXT_ETHIOPIC_SYLLABLE_XYI L"\u2dd2" #define UNICODE_ETHIOPIC_SYLLABLE_XYAA 0x2dd3 #define UNITEXT_ETHIOPIC_SYLLABLE_XYAA L"\u2dd3" #define UNICODE_ETHIOPIC_SYLLABLE_XYEE 0x2dd4 #define UNITEXT_ETHIOPIC_SYLLABLE_XYEE L"\u2dd4" #define UNICODE_ETHIOPIC_SYLLABLE_XYE 0x2dd5 #define UNITEXT_ETHIOPIC_SYLLABLE_XYE L"\u2dd5" #define UNICODE_ETHIOPIC_SYLLABLE_XYO 0x2dd6 #define UNITEXT_ETHIOPIC_SYLLABLE_XYO L"\u2dd6" #define UNICODE_ETHIOPIC_SYLLABLE_GYA 0x2dd8 #define UNITEXT_ETHIOPIC_SYLLABLE_GYA L"\u2dd8" #define UNICODE_ETHIOPIC_SYLLABLE_GYU 0x2dd9 #define UNITEXT_ETHIOPIC_SYLLABLE_GYU L"\u2dd9" #define UNICODE_ETHIOPIC_SYLLABLE_GYI 0x2dda #define UNITEXT_ETHIOPIC_SYLLABLE_GYI L"\u2dda" #define UNICODE_ETHIOPIC_SYLLABLE_GYAA 0x2ddb #define UNITEXT_ETHIOPIC_SYLLABLE_GYAA L"\u2ddb" #define UNICODE_ETHIOPIC_SYLLABLE_GYEE 0x2ddc #define UNITEXT_ETHIOPIC_SYLLABLE_GYEE L"\u2ddc" #define UNICODE_ETHIOPIC_SYLLABLE_GYE 0x2ddd #define UNITEXT_ETHIOPIC_SYLLABLE_GYE L"\u2ddd" #define UNICODE_ETHIOPIC_SYLLABLE_GYO 0x2dde #define UNITEXT_ETHIOPIC_SYLLABLE_GYO L"\u2dde" #define UNICODE_RIGHT_ANGLE_SUBSTITUTION_MARKER 0x2e00 #define UNITEXT_RIGHT_ANGLE_SUBSTITUTION_MARKER L"\u2e00" #define UNICODE_RIGHT_ANGLE_DOTTED_SUBSTITUTION_MARKER 0x2e01 #define UNITEXT_RIGHT_ANGLE_DOTTED_SUBSTITUTION_MARKER L"\u2e01" #define UNICODE_LEFT_SUBSTITUTION_BRACKET 0x2e02 #define UNITEXT_LEFT_SUBSTITUTION_BRACKET L"\u2e02" #define UNICODE_RIGHT_SUBSTITUTION_BRACKET 0x2e03 #define UNITEXT_RIGHT_SUBSTITUTION_BRACKET L"\u2e03" #define UNICODE_LEFT_DOTTED_SUBSTITUTION_BRACKET 0x2e04 #define UNITEXT_LEFT_DOTTED_SUBSTITUTION_BRACKET L"\u2e04" #define UNICODE_RIGHT_DOTTED_SUBSTITUTION_BRACKET 0x2e05 #define UNITEXT_RIGHT_DOTTED_SUBSTITUTION_BRACKET L"\u2e05" #define UNICODE_RAISED_INTERPOLATION_MARKER 0x2e06 #define UNITEXT_RAISED_INTERPOLATION_MARKER L"\u2e06" #define UNICODE_RAISED_DOTTED_INTERPOLATION_MARKER 0x2e07 #define UNITEXT_RAISED_DOTTED_INTERPOLATION_MARKER L"\u2e07" #define UNICODE_DOTTED_TRANSPOSITION_MARKER 0x2e08 #define UNITEXT_DOTTED_TRANSPOSITION_MARKER L"\u2e08" #define UNICODE_LEFT_TRANSPOSITION_BRACKET 0x2e09 #define UNITEXT_LEFT_TRANSPOSITION_BRACKET L"\u2e09" #define UNICODE_RIGHT_TRANSPOSITION_BRACKET 0x2e0a #define UNITEXT_RIGHT_TRANSPOSITION_BRACKET L"\u2e0a" #define UNICODE_RAISED_SQUARE 0x2e0b #define UNITEXT_RAISED_SQUARE L"\u2e0b" #define UNICODE_LEFT_RAISED_OMISSION_BRACKET 0x2e0c #define UNITEXT_LEFT_RAISED_OMISSION_BRACKET L"\u2e0c" #define UNICODE_RIGHT_RAISED_OMISSION_BRACKET 0x2e0d #define UNITEXT_RIGHT_RAISED_OMISSION_BRACKET L"\u2e0d" #define UNICODE_EDITORIAL_CORONIS 0x2e0e #define UNITEXT_EDITORIAL_CORONIS L"\u2e0e" #define UNICODE_PARAGRAPHOS 0x2e0f #define UNITEXT_PARAGRAPHOS L"\u2e0f" #define UNICODE_FORKED_PARAGRAPHOS 0x2e10 #define UNITEXT_FORKED_PARAGRAPHOS L"\u2e10" #define UNICODE_REVERSED_FORKED_PARAGRAPHOS 0x2e11 #define UNITEXT_REVERSED_FORKED_PARAGRAPHOS L"\u2e11" #define UNICODE_HYPODIASTOLE 0x2e12 #define UNITEXT_HYPODIASTOLE L"\u2e12" #define UNICODE_DOTTED_OBELOS 0x2e13 #define UNITEXT_DOTTED_OBELOS L"\u2e13" #define UNICODE_DOWNWARDS_ANCORA 0x2e14 #define UNITEXT_DOWNWARDS_ANCORA L"\u2e14" #define UNICODE_UPWARDS_ANCORA 0x2e15 #define UNITEXT_UPWARDS_ANCORA L"\u2e15" #define UNICODE_DOTTED_RIGHT_POINTING_ANGLE 0x2e16 #define UNITEXT_DOTTED_RIGHT_POINTING_ANGLE L"\u2e16" #define UNICODE_DOUBLE_OBLIQUE_HYPHEN 0x2e17 #define UNITEXT_DOUBLE_OBLIQUE_HYPHEN L"\u2e17" #define UNICODE_LEFT_LOW_PARAPHRASE_BRACKET 0x2e1c #define UNITEXT_LEFT_LOW_PARAPHRASE_BRACKET L"\u2e1c" #define UNICODE_RIGHT_LOW_PARAPHRASE_BRACKET 0x2e1d #define UNITEXT_RIGHT_LOW_PARAPHRASE_BRACKET L"\u2e1d" #define UNICODE_CJK_RADICAL_REPEAT 0x2e80 #define UNITEXT_CJK_RADICAL_REPEAT L"\u2e80" #define UNICODE_CJK_RADICAL_CLIFF 0x2e81 #define UNITEXT_CJK_RADICAL_CLIFF L"\u2e81" #define UNICODE_CJK_RADICAL_SECOND_ONE 0x2e82 #define UNITEXT_CJK_RADICAL_SECOND_ONE L"\u2e82" #define UNICODE_CJK_RADICAL_SECOND_TWO 0x2e83 #define UNITEXT_CJK_RADICAL_SECOND_TWO L"\u2e83" #define UNICODE_CJK_RADICAL_SECOND_THREE 0x2e84 #define UNITEXT_CJK_RADICAL_SECOND_THREE L"\u2e84" #define UNICODE_CJK_RADICAL_PERSON 0x2e85 #define UNITEXT_CJK_RADICAL_PERSON L"\u2e85" #define UNICODE_CJK_RADICAL_BOX 0x2e86 #define UNITEXT_CJK_RADICAL_BOX L"\u2e86" #define UNICODE_CJK_RADICAL_TABLE 0x2e87 #define UNITEXT_CJK_RADICAL_TABLE L"\u2e87" #define UNICODE_CJK_RADICAL_KNIFE_ONE 0x2e88 #define UNITEXT_CJK_RADICAL_KNIFE_ONE L"\u2e88" #define UNICODE_CJK_RADICAL_KNIFE_TWO 0x2e89 #define UNITEXT_CJK_RADICAL_KNIFE_TWO L"\u2e89" #define UNICODE_CJK_RADICAL_DIVINATION 0x2e8a #define UNITEXT_CJK_RADICAL_DIVINATION L"\u2e8a" #define UNICODE_CJK_RADICAL_SEAL 0x2e8b #define UNITEXT_CJK_RADICAL_SEAL L"\u2e8b" #define UNICODE_CJK_RADICAL_SMALL_ONE 0x2e8c #define UNITEXT_CJK_RADICAL_SMALL_ONE L"\u2e8c" #define UNICODE_CJK_RADICAL_SMALL_TWO 0x2e8d #define UNITEXT_CJK_RADICAL_SMALL_TWO L"\u2e8d" #define UNICODE_CJK_RADICAL_LAME_ONE 0x2e8e #define UNITEXT_CJK_RADICAL_LAME_ONE L"\u2e8e" #define UNICODE_CJK_RADICAL_LAME_TWO 0x2e8f #define UNITEXT_CJK_RADICAL_LAME_TWO L"\u2e8f" #define UNICODE_CJK_RADICAL_LAME_THREE 0x2e90 #define UNITEXT_CJK_RADICAL_LAME_THREE L"\u2e90" #define UNICODE_CJK_RADICAL_LAME_FOUR 0x2e91 #define UNITEXT_CJK_RADICAL_LAME_FOUR L"\u2e91" #define UNICODE_CJK_RADICAL_SNAKE 0x2e92 #define UNITEXT_CJK_RADICAL_SNAKE L"\u2e92" #define UNICODE_CJK_RADICAL_THREAD 0x2e93 #define UNITEXT_CJK_RADICAL_THREAD L"\u2e93" #define UNICODE_CJK_RADICAL_SNOUT_ONE 0x2e94 #define UNITEXT_CJK_RADICAL_SNOUT_ONE L"\u2e94" #define UNICODE_CJK_RADICAL_SNOUT_TWO 0x2e95 #define UNITEXT_CJK_RADICAL_SNOUT_TWO L"\u2e95" #define UNICODE_CJK_RADICAL_HEART_ONE 0x2e96 #define UNITEXT_CJK_RADICAL_HEART_ONE L"\u2e96" #define UNICODE_CJK_RADICAL_HEART_TWO 0x2e97 #define UNITEXT_CJK_RADICAL_HEART_TWO L"\u2e97" #define UNICODE_CJK_RADICAL_HAND 0x2e98 #define UNITEXT_CJK_RADICAL_HAND L"\u2e98" #define UNICODE_CJK_RADICAL_RAP 0x2e99 #define UNITEXT_CJK_RADICAL_RAP L"\u2e99" #define UNICODE_CJK_RADICAL_CHOKE 0x2e9b #define UNITEXT_CJK_RADICAL_CHOKE L"\u2e9b" #define UNICODE_CJK_RADICAL_SUN 0x2e9c #define UNITEXT_CJK_RADICAL_SUN L"\u2e9c" #define UNICODE_CJK_RADICAL_MOON 0x2e9d #define UNITEXT_CJK_RADICAL_MOON L"\u2e9d" #define UNICODE_CJK_RADICAL_DEATH 0x2e9e #define UNITEXT_CJK_RADICAL_DEATH L"\u2e9e" #define UNICODE_CJK_RADICAL_MOTHER 0x2e9f #define UNITEXT_CJK_RADICAL_MOTHER L"\u2e9f" #define UNICODE_CJK_RADICAL_CIVILIAN 0x2ea0 #define UNITEXT_CJK_RADICAL_CIVILIAN L"\u2ea0" #define UNICODE_CJK_RADICAL_WATER_ONE 0x2ea1 #define UNITEXT_CJK_RADICAL_WATER_ONE L"\u2ea1" #define UNICODE_CJK_RADICAL_WATER_TWO 0x2ea2 #define UNITEXT_CJK_RADICAL_WATER_TWO L"\u2ea2" #define UNICODE_CJK_RADICAL_FIRE 0x2ea3 #define UNITEXT_CJK_RADICAL_FIRE L"\u2ea3" #define UNICODE_CJK_RADICAL_PAW_ONE 0x2ea4 #define UNITEXT_CJK_RADICAL_PAW_ONE L"\u2ea4" #define UNICODE_CJK_RADICAL_PAW_TWO 0x2ea5 #define UNITEXT_CJK_RADICAL_PAW_TWO L"\u2ea5" #define UNICODE_CJK_RADICAL_SIMPLIFIED_HALF_TREE_TRUNK 0x2ea6 #define UNITEXT_CJK_RADICAL_SIMPLIFIED_HALF_TREE_TRUNK L"\u2ea6" #define UNICODE_CJK_RADICAL_COW 0x2ea7 #define UNITEXT_CJK_RADICAL_COW L"\u2ea7" #define UNICODE_CJK_RADICAL_DOG 0x2ea8 #define UNITEXT_CJK_RADICAL_DOG L"\u2ea8" #define UNICODE_CJK_RADICAL_JADE 0x2ea9 #define UNITEXT_CJK_RADICAL_JADE L"\u2ea9" #define UNICODE_CJK_RADICAL_BOLT_OF_CLOTH 0x2eaa #define UNITEXT_CJK_RADICAL_BOLT_OF_CLOTH L"\u2eaa" #define UNICODE_CJK_RADICAL_EYE 0x2eab #define UNITEXT_CJK_RADICAL_EYE L"\u2eab" #define UNICODE_CJK_RADICAL_SPIRIT_ONE 0x2eac #define UNITEXT_CJK_RADICAL_SPIRIT_ONE L"\u2eac" #define UNICODE_CJK_RADICAL_SPIRIT_TWO 0x2ead #define UNITEXT_CJK_RADICAL_SPIRIT_TWO L"\u2ead" #define UNICODE_CJK_RADICAL_BAMBOO 0x2eae #define UNITEXT_CJK_RADICAL_BAMBOO L"\u2eae" #define UNICODE_CJK_RADICAL_SILK 0x2eaf #define UNITEXT_CJK_RADICAL_SILK L"\u2eaf" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_SILK 0x2eb0 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_SILK L"\u2eb0" #define UNICODE_CJK_RADICAL_NET_ONE 0x2eb1 #define UNITEXT_CJK_RADICAL_NET_ONE L"\u2eb1" #define UNICODE_CJK_RADICAL_NET_TWO 0x2eb2 #define UNITEXT_CJK_RADICAL_NET_TWO L"\u2eb2" #define UNICODE_CJK_RADICAL_NET_THREE 0x2eb3 #define UNITEXT_CJK_RADICAL_NET_THREE L"\u2eb3" #define UNICODE_CJK_RADICAL_NET_FOUR 0x2eb4 #define UNITEXT_CJK_RADICAL_NET_FOUR L"\u2eb4" #define UNICODE_CJK_RADICAL_MESH 0x2eb5 #define UNITEXT_CJK_RADICAL_MESH L"\u2eb5" #define UNICODE_CJK_RADICAL_SHEEP 0x2eb6 #define UNITEXT_CJK_RADICAL_SHEEP L"\u2eb6" #define UNICODE_CJK_RADICAL_RAM 0x2eb7 #define UNITEXT_CJK_RADICAL_RAM L"\u2eb7" #define UNICODE_CJK_RADICAL_EWE 0x2eb8 #define UNITEXT_CJK_RADICAL_EWE L"\u2eb8" #define UNICODE_CJK_RADICAL_OLD 0x2eb9 #define UNITEXT_CJK_RADICAL_OLD L"\u2eb9" #define UNICODE_CJK_RADICAL_BRUSH_ONE 0x2eba #define UNITEXT_CJK_RADICAL_BRUSH_ONE L"\u2eba" #define UNICODE_CJK_RADICAL_BRUSH_TWO 0x2ebb #define UNITEXT_CJK_RADICAL_BRUSH_TWO L"\u2ebb" #define UNICODE_CJK_RADICAL_MEAT 0x2ebc #define UNITEXT_CJK_RADICAL_MEAT L"\u2ebc" #define UNICODE_CJK_RADICAL_MORTAR 0x2ebd #define UNITEXT_CJK_RADICAL_MORTAR L"\u2ebd" #define UNICODE_CJK_RADICAL_GRASS_ONE 0x2ebe #define UNITEXT_CJK_RADICAL_GRASS_ONE L"\u2ebe" #define UNICODE_CJK_RADICAL_GRASS_TWO 0x2ebf #define UNITEXT_CJK_RADICAL_GRASS_TWO L"\u2ebf" #define UNICODE_CJK_RADICAL_GRASS_THREE 0x2ec0 #define UNITEXT_CJK_RADICAL_GRASS_THREE L"\u2ec0" #define UNICODE_CJK_RADICAL_TIGER 0x2ec1 #define UNITEXT_CJK_RADICAL_TIGER L"\u2ec1" #define UNICODE_CJK_RADICAL_CLOTHES 0x2ec2 #define UNITEXT_CJK_RADICAL_CLOTHES L"\u2ec2" #define UNICODE_CJK_RADICAL_WEST_ONE 0x2ec3 #define UNITEXT_CJK_RADICAL_WEST_ONE L"\u2ec3" #define UNICODE_CJK_RADICAL_WEST_TWO 0x2ec4 #define UNITEXT_CJK_RADICAL_WEST_TWO L"\u2ec4" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_SEE 0x2ec5 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_SEE L"\u2ec5" #define UNICODE_CJK_RADICAL_SIMPLIFIED_HORN 0x2ec6 #define UNITEXT_CJK_RADICAL_SIMPLIFIED_HORN L"\u2ec6" #define UNICODE_CJK_RADICAL_HORN 0x2ec7 #define UNITEXT_CJK_RADICAL_HORN L"\u2ec7" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_SPEECH 0x2ec8 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_SPEECH L"\u2ec8" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_SHELL 0x2ec9 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_SHELL L"\u2ec9" #define UNICODE_CJK_RADICAL_FOOT 0x2eca #define UNITEXT_CJK_RADICAL_FOOT L"\u2eca" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_CART 0x2ecb #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_CART L"\u2ecb" #define UNICODE_CJK_RADICAL_SIMPLIFIED_WALK 0x2ecc #define UNITEXT_CJK_RADICAL_SIMPLIFIED_WALK L"\u2ecc" #define UNICODE_CJK_RADICAL_WALK_ONE 0x2ecd #define UNITEXT_CJK_RADICAL_WALK_ONE L"\u2ecd" #define UNICODE_CJK_RADICAL_WALK_TWO 0x2ece #define UNITEXT_CJK_RADICAL_WALK_TWO L"\u2ece" #define UNICODE_CJK_RADICAL_CITY 0x2ecf #define UNITEXT_CJK_RADICAL_CITY L"\u2ecf" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_GOLD 0x2ed0 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_GOLD L"\u2ed0" #define UNICODE_CJK_RADICAL_LONG_ONE 0x2ed1 #define UNITEXT_CJK_RADICAL_LONG_ONE L"\u2ed1" #define UNICODE_CJK_RADICAL_LONG_TWO 0x2ed2 #define UNITEXT_CJK_RADICAL_LONG_TWO L"\u2ed2" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_LONG 0x2ed3 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_LONG L"\u2ed3" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_GATE 0x2ed4 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_GATE L"\u2ed4" #define UNICODE_CJK_RADICAL_MOUND_ONE 0x2ed5 #define UNITEXT_CJK_RADICAL_MOUND_ONE L"\u2ed5" #define UNICODE_CJK_RADICAL_MOUND_TWO 0x2ed6 #define UNITEXT_CJK_RADICAL_MOUND_TWO L"\u2ed6" #define UNICODE_CJK_RADICAL_RAIN 0x2ed7 #define UNITEXT_CJK_RADICAL_RAIN L"\u2ed7" #define UNICODE_CJK_RADICAL_BLUE 0x2ed8 #define UNITEXT_CJK_RADICAL_BLUE L"\u2ed8" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_TANNED_LEATHER 0x2ed9 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_TANNED_LEATHER L"\u2ed9" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_LEAF 0x2eda #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_LEAF L"\u2eda" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_WIND 0x2edb #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_WIND L"\u2edb" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_FLY 0x2edc #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_FLY L"\u2edc" #define UNICODE_CJK_RADICAL_EAT_ONE 0x2edd #define UNITEXT_CJK_RADICAL_EAT_ONE L"\u2edd" #define UNICODE_CJK_RADICAL_EAT_TWO 0x2ede #define UNITEXT_CJK_RADICAL_EAT_TWO L"\u2ede" #define UNICODE_CJK_RADICAL_EAT_THREE 0x2edf #define UNITEXT_CJK_RADICAL_EAT_THREE L"\u2edf" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_EAT 0x2ee0 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_EAT L"\u2ee0" #define UNICODE_CJK_RADICAL_HEAD 0x2ee1 #define UNITEXT_CJK_RADICAL_HEAD L"\u2ee1" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_HORSE 0x2ee2 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_HORSE L"\u2ee2" #define UNICODE_CJK_RADICAL_BONE 0x2ee3 #define UNITEXT_CJK_RADICAL_BONE L"\u2ee3" #define UNICODE_CJK_RADICAL_GHOST 0x2ee4 #define UNITEXT_CJK_RADICAL_GHOST L"\u2ee4" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_FISH 0x2ee5 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_FISH L"\u2ee5" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_BIRD 0x2ee6 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_BIRD L"\u2ee6" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_SALT 0x2ee7 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_SALT L"\u2ee7" #define UNICODE_CJK_RADICAL_SIMPLIFIED_WHEAT 0x2ee8 #define UNITEXT_CJK_RADICAL_SIMPLIFIED_WHEAT L"\u2ee8" #define UNICODE_CJK_RADICAL_SIMPLIFIED_YELLOW 0x2ee9 #define UNITEXT_CJK_RADICAL_SIMPLIFIED_YELLOW L"\u2ee9" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_FROG 0x2eea #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_FROG L"\u2eea" #define UNICODE_CJK_RADICAL_J_SIMPLIFIED_EVEN 0x2eeb #define UNITEXT_CJK_RADICAL_J_SIMPLIFIED_EVEN L"\u2eeb" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_EVEN 0x2eec #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_EVEN L"\u2eec" #define UNICODE_CJK_RADICAL_J_SIMPLIFIED_TOOTH 0x2eed #define UNITEXT_CJK_RADICAL_J_SIMPLIFIED_TOOTH L"\u2eed" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_TOOTH 0x2eee #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_TOOTH L"\u2eee" #define UNICODE_CJK_RADICAL_J_SIMPLIFIED_DRAGON 0x2eef #define UNITEXT_CJK_RADICAL_J_SIMPLIFIED_DRAGON L"\u2eef" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_DRAGON 0x2ef0 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_DRAGON L"\u2ef0" #define UNICODE_CJK_RADICAL_TURTLE 0x2ef1 #define UNITEXT_CJK_RADICAL_TURTLE L"\u2ef1" #define UNICODE_CJK_RADICAL_J_SIMPLIFIED_TURTLE 0x2ef2 #define UNITEXT_CJK_RADICAL_J_SIMPLIFIED_TURTLE L"\u2ef2" #define UNICODE_CJK_RADICAL_C_SIMPLIFIED_TURTLE 0x2ef3 #define UNITEXT_CJK_RADICAL_C_SIMPLIFIED_TURTLE L"\u2ef3" #define UNICODE_KANGXI_RADICAL_ONE 0x2f00 #define UNITEXT_KANGXI_RADICAL_ONE L"\u2f00" #define UNICODE_KANGXI_RADICAL_LINE 0x2f01 #define UNITEXT_KANGXI_RADICAL_LINE L"\u2f01" #define UNICODE_KANGXI_RADICAL_DOT 0x2f02 #define UNITEXT_KANGXI_RADICAL_DOT L"\u2f02" #define UNICODE_KANGXI_RADICAL_SLASH 0x2f03 #define UNITEXT_KANGXI_RADICAL_SLASH L"\u2f03" #define UNICODE_KANGXI_RADICAL_SECOND 0x2f04 #define UNITEXT_KANGXI_RADICAL_SECOND L"\u2f04" #define UNICODE_KANGXI_RADICAL_HOOK 0x2f05 #define UNITEXT_KANGXI_RADICAL_HOOK L"\u2f05" #define UNICODE_KANGXI_RADICAL_TWO 0x2f06 #define UNITEXT_KANGXI_RADICAL_TWO L"\u2f06" #define UNICODE_KANGXI_RADICAL_LID 0x2f07 #define UNITEXT_KANGXI_RADICAL_LID L"\u2f07" #define UNICODE_KANGXI_RADICAL_MAN 0x2f08 #define UNITEXT_KANGXI_RADICAL_MAN L"\u2f08" #define UNICODE_KANGXI_RADICAL_LEGS 0x2f09 #define UNITEXT_KANGXI_RADICAL_LEGS L"\u2f09" #define UNICODE_KANGXI_RADICAL_ENTER 0x2f0a #define UNITEXT_KANGXI_RADICAL_ENTER L"\u2f0a" #define UNICODE_KANGXI_RADICAL_EIGHT 0x2f0b #define UNITEXT_KANGXI_RADICAL_EIGHT L"\u2f0b" #define UNICODE_KANGXI_RADICAL_DOWN_BOX 0x2f0c #define UNITEXT_KANGXI_RADICAL_DOWN_BOX L"\u2f0c" #define UNICODE_KANGXI_RADICAL_COVER 0x2f0d #define UNITEXT_KANGXI_RADICAL_COVER L"\u2f0d" #define UNICODE_KANGXI_RADICAL_ICE 0x2f0e #define UNITEXT_KANGXI_RADICAL_ICE L"\u2f0e" #define UNICODE_KANGXI_RADICAL_TABLE 0x2f0f #define UNITEXT_KANGXI_RADICAL_TABLE L"\u2f0f" #define UNICODE_KANGXI_RADICAL_OPEN_BOX 0x2f10 #define UNITEXT_KANGXI_RADICAL_OPEN_BOX L"\u2f10" #define UNICODE_KANGXI_RADICAL_KNIFE 0x2f11 #define UNITEXT_KANGXI_RADICAL_KNIFE L"\u2f11" #define UNICODE_KANGXI_RADICAL_POWER 0x2f12 #define UNITEXT_KANGXI_RADICAL_POWER L"\u2f12" #define UNICODE_KANGXI_RADICAL_WRAP 0x2f13 #define UNITEXT_KANGXI_RADICAL_WRAP L"\u2f13" #define UNICODE_KANGXI_RADICAL_SPOON 0x2f14 #define UNITEXT_KANGXI_RADICAL_SPOON L"\u2f14" #define UNICODE_KANGXI_RADICAL_RIGHT_OPEN_BOX 0x2f15 #define UNITEXT_KANGXI_RADICAL_RIGHT_OPEN_BOX L"\u2f15" #define UNICODE_KANGXI_RADICAL_HIDING_ENCLOSURE 0x2f16 #define UNITEXT_KANGXI_RADICAL_HIDING_ENCLOSURE L"\u2f16" #define UNICODE_KANGXI_RADICAL_TEN 0x2f17 #define UNITEXT_KANGXI_RADICAL_TEN L"\u2f17" #define UNICODE_KANGXI_RADICAL_DIVINATION 0x2f18 #define UNITEXT_KANGXI_RADICAL_DIVINATION L"\u2f18" #define UNICODE_KANGXI_RADICAL_SEAL 0x2f19 #define UNITEXT_KANGXI_RADICAL_SEAL L"\u2f19" #define UNICODE_KANGXI_RADICAL_CLIFF 0x2f1a #define UNITEXT_KANGXI_RADICAL_CLIFF L"\u2f1a" #define UNICODE_KANGXI_RADICAL_PRIVATE 0x2f1b #define UNITEXT_KANGXI_RADICAL_PRIVATE L"\u2f1b" #define UNICODE_KANGXI_RADICAL_AGAIN 0x2f1c #define UNITEXT_KANGXI_RADICAL_AGAIN L"\u2f1c" #define UNICODE_KANGXI_RADICAL_MOUTH 0x2f1d #define UNITEXT_KANGXI_RADICAL_MOUTH L"\u2f1d" #define UNICODE_KANGXI_RADICAL_ENCLOSURE 0x2f1e #define UNITEXT_KANGXI_RADICAL_ENCLOSURE L"\u2f1e" #define UNICODE_KANGXI_RADICAL_EARTH 0x2f1f #define UNITEXT_KANGXI_RADICAL_EARTH L"\u2f1f" #define UNICODE_KANGXI_RADICAL_SCHOLAR 0x2f20 #define UNITEXT_KANGXI_RADICAL_SCHOLAR L"\u2f20" #define UNICODE_KANGXI_RADICAL_GO 0x2f21 #define UNITEXT_KANGXI_RADICAL_GO L"\u2f21" #define UNICODE_KANGXI_RADICAL_GO_SLOWLY 0x2f22 #define UNITEXT_KANGXI_RADICAL_GO_SLOWLY L"\u2f22" #define UNICODE_KANGXI_RADICAL_EVENING 0x2f23 #define UNITEXT_KANGXI_RADICAL_EVENING L"\u2f23" #define UNICODE_KANGXI_RADICAL_BIG 0x2f24 #define UNITEXT_KANGXI_RADICAL_BIG L"\u2f24" #define UNICODE_KANGXI_RADICAL_WOMAN 0x2f25 #define UNITEXT_KANGXI_RADICAL_WOMAN L"\u2f25" #define UNICODE_KANGXI_RADICAL_CHILD 0x2f26 #define UNITEXT_KANGXI_RADICAL_CHILD L"\u2f26" #define UNICODE_KANGXI_RADICAL_ROOF 0x2f27 #define UNITEXT_KANGXI_RADICAL_ROOF L"\u2f27" #define UNICODE_KANGXI_RADICAL_INCH 0x2f28 #define UNITEXT_KANGXI_RADICAL_INCH L"\u2f28" #define UNICODE_KANGXI_RADICAL_SMALL 0x2f29 #define UNITEXT_KANGXI_RADICAL_SMALL L"\u2f29" #define UNICODE_KANGXI_RADICAL_LAME 0x2f2a #define UNITEXT_KANGXI_RADICAL_LAME L"\u2f2a" #define UNICODE_KANGXI_RADICAL_CORPSE 0x2f2b #define UNITEXT_KANGXI_RADICAL_CORPSE L"\u2f2b" #define UNICODE_KANGXI_RADICAL_SPROUT 0x2f2c #define UNITEXT_KANGXI_RADICAL_SPROUT L"\u2f2c" #define UNICODE_KANGXI_RADICAL_MOUNTAIN 0x2f2d #define UNITEXT_KANGXI_RADICAL_MOUNTAIN L"\u2f2d" #define UNICODE_KANGXI_RADICAL_RIVER 0x2f2e #define UNITEXT_KANGXI_RADICAL_RIVER L"\u2f2e" #define UNICODE_KANGXI_RADICAL_WORK 0x2f2f #define UNITEXT_KANGXI_RADICAL_WORK L"\u2f2f" #define UNICODE_KANGXI_RADICAL_ONESELF 0x2f30 #define UNITEXT_KANGXI_RADICAL_ONESELF L"\u2f30" #define UNICODE_KANGXI_RADICAL_TURBAN 0x2f31 #define UNITEXT_KANGXI_RADICAL_TURBAN L"\u2f31" #define UNICODE_KANGXI_RADICAL_DRY 0x2f32 #define UNITEXT_KANGXI_RADICAL_DRY L"\u2f32" #define UNICODE_KANGXI_RADICAL_SHORT_THREAD 0x2f33 #define UNITEXT_KANGXI_RADICAL_SHORT_THREAD L"\u2f33" #define UNICODE_KANGXI_RADICAL_DOTTED_CLIFF 0x2f34 #define UNITEXT_KANGXI_RADICAL_DOTTED_CLIFF L"\u2f34" #define UNICODE_KANGXI_RADICAL_LONG_STRIDE 0x2f35 #define UNITEXT_KANGXI_RADICAL_LONG_STRIDE L"\u2f35" #define UNICODE_KANGXI_RADICAL_TWO_HANDS 0x2f36 #define UNITEXT_KANGXI_RADICAL_TWO_HANDS L"\u2f36" #define UNICODE_KANGXI_RADICAL_SHOOT 0x2f37 #define UNITEXT_KANGXI_RADICAL_SHOOT L"\u2f37" #define UNICODE_KANGXI_RADICAL_BOW 0x2f38 #define UNITEXT_KANGXI_RADICAL_BOW L"\u2f38" #define UNICODE_KANGXI_RADICAL_SNOUT 0x2f39 #define UNITEXT_KANGXI_RADICAL_SNOUT L"\u2f39" #define UNICODE_KANGXI_RADICAL_BRISTLE 0x2f3a #define UNITEXT_KANGXI_RADICAL_BRISTLE L"\u2f3a" #define UNICODE_KANGXI_RADICAL_STEP 0x2f3b #define UNITEXT_KANGXI_RADICAL_STEP L"\u2f3b" #define UNICODE_KANGXI_RADICAL_HEART 0x2f3c #define UNITEXT_KANGXI_RADICAL_HEART L"\u2f3c" #define UNICODE_KANGXI_RADICAL_HALBERD 0x2f3d #define UNITEXT_KANGXI_RADICAL_HALBERD L"\u2f3d" #define UNICODE_KANGXI_RADICAL_DOOR 0x2f3e #define UNITEXT_KANGXI_RADICAL_DOOR L"\u2f3e" #define UNICODE_KANGXI_RADICAL_HAND 0x2f3f #define UNITEXT_KANGXI_RADICAL_HAND L"\u2f3f" #define UNICODE_KANGXI_RADICAL_BRANCH 0x2f40 #define UNITEXT_KANGXI_RADICAL_BRANCH L"\u2f40" #define UNICODE_KANGXI_RADICAL_RAP 0x2f41 #define UNITEXT_KANGXI_RADICAL_RAP L"\u2f41" #define UNICODE_KANGXI_RADICAL_SCRIPT 0x2f42 #define UNITEXT_KANGXI_RADICAL_SCRIPT L"\u2f42" #define UNICODE_KANGXI_RADICAL_DIPPER 0x2f43 #define UNITEXT_KANGXI_RADICAL_DIPPER L"\u2f43" #define UNICODE_KANGXI_RADICAL_AXE 0x2f44 #define UNITEXT_KANGXI_RADICAL_AXE L"\u2f44" #define UNICODE_KANGXI_RADICAL_SQUARE 0x2f45 #define UNITEXT_KANGXI_RADICAL_SQUARE L"\u2f45" #define UNICODE_KANGXI_RADICAL_NOT 0x2f46 #define UNITEXT_KANGXI_RADICAL_NOT L"\u2f46" #define UNICODE_KANGXI_RADICAL_SUN 0x2f47 #define UNITEXT_KANGXI_RADICAL_SUN L"\u2f47" #define UNICODE_KANGXI_RADICAL_SAY 0x2f48 #define UNITEXT_KANGXI_RADICAL_SAY L"\u2f48" #define UNICODE_KANGXI_RADICAL_MOON 0x2f49 #define UNITEXT_KANGXI_RADICAL_MOON L"\u2f49" #define UNICODE_KANGXI_RADICAL_TREE 0x2f4a #define UNITEXT_KANGXI_RADICAL_TREE L"\u2f4a" #define UNICODE_KANGXI_RADICAL_LACK 0x2f4b #define UNITEXT_KANGXI_RADICAL_LACK L"\u2f4b" #define UNICODE_KANGXI_RADICAL_STOP 0x2f4c #define UNITEXT_KANGXI_RADICAL_STOP L"\u2f4c" #define UNICODE_KANGXI_RADICAL_DEATH 0x2f4d #define UNITEXT_KANGXI_RADICAL_DEATH L"\u2f4d" #define UNICODE_KANGXI_RADICAL_WEAPON 0x2f4e #define UNITEXT_KANGXI_RADICAL_WEAPON L"\u2f4e" #define UNICODE_KANGXI_RADICAL_DO_NOT 0x2f4f #define UNITEXT_KANGXI_RADICAL_DO_NOT L"\u2f4f" #define UNICODE_KANGXI_RADICAL_COMPARE 0x2f50 #define UNITEXT_KANGXI_RADICAL_COMPARE L"\u2f50" #define UNICODE_KANGXI_RADICAL_FUR 0x2f51 #define UNITEXT_KANGXI_RADICAL_FUR L"\u2f51" #define UNICODE_KANGXI_RADICAL_CLAN 0x2f52 #define UNITEXT_KANGXI_RADICAL_CLAN L"\u2f52" #define UNICODE_KANGXI_RADICAL_STEAM 0x2f53 #define UNITEXT_KANGXI_RADICAL_STEAM L"\u2f53" #define UNICODE_KANGXI_RADICAL_WATER 0x2f54 #define UNITEXT_KANGXI_RADICAL_WATER L"\u2f54" #define UNICODE_KANGXI_RADICAL_FIRE 0x2f55 #define UNITEXT_KANGXI_RADICAL_FIRE L"\u2f55" #define UNICODE_KANGXI_RADICAL_CLAW 0x2f56 #define UNITEXT_KANGXI_RADICAL_CLAW L"\u2f56" #define UNICODE_KANGXI_RADICAL_FATHER 0x2f57 #define UNITEXT_KANGXI_RADICAL_FATHER L"\u2f57" #define UNICODE_KANGXI_RADICAL_DOUBLE_X 0x2f58 #define UNITEXT_KANGXI_RADICAL_DOUBLE_X L"\u2f58" #define UNICODE_KANGXI_RADICAL_HALF_TREE_TRUNK 0x2f59 #define UNITEXT_KANGXI_RADICAL_HALF_TREE_TRUNK L"\u2f59" #define UNICODE_KANGXI_RADICAL_SLICE 0x2f5a #define UNITEXT_KANGXI_RADICAL_SLICE L"\u2f5a" #define UNICODE_KANGXI_RADICAL_FANG 0x2f5b #define UNITEXT_KANGXI_RADICAL_FANG L"\u2f5b" #define UNICODE_KANGXI_RADICAL_COW 0x2f5c #define UNITEXT_KANGXI_RADICAL_COW L"\u2f5c" #define UNICODE_KANGXI_RADICAL_DOG 0x2f5d #define UNITEXT_KANGXI_RADICAL_DOG L"\u2f5d" #define UNICODE_KANGXI_RADICAL_PROFOUND 0x2f5e #define UNITEXT_KANGXI_RADICAL_PROFOUND L"\u2f5e" #define UNICODE_KANGXI_RADICAL_JADE 0x2f5f #define UNITEXT_KANGXI_RADICAL_JADE L"\u2f5f" #define UNICODE_KANGXI_RADICAL_MELON 0x2f60 #define UNITEXT_KANGXI_RADICAL_MELON L"\u2f60" #define UNICODE_KANGXI_RADICAL_TILE 0x2f61 #define UNITEXT_KANGXI_RADICAL_TILE L"\u2f61" #define UNICODE_KANGXI_RADICAL_SWEET 0x2f62 #define UNITEXT_KANGXI_RADICAL_SWEET L"\u2f62" #define UNICODE_KANGXI_RADICAL_LIFE 0x2f63 #define UNITEXT_KANGXI_RADICAL_LIFE L"\u2f63" #define UNICODE_KANGXI_RADICAL_USE 0x2f64 #define UNITEXT_KANGXI_RADICAL_USE L"\u2f64" #define UNICODE_KANGXI_RADICAL_FIELD 0x2f65 #define UNITEXT_KANGXI_RADICAL_FIELD L"\u2f65" #define UNICODE_KANGXI_RADICAL_BOLT_OF_CLOTH 0x2f66 #define UNITEXT_KANGXI_RADICAL_BOLT_OF_CLOTH L"\u2f66" #define UNICODE_KANGXI_RADICAL_SICKNESS 0x2f67 #define UNITEXT_KANGXI_RADICAL_SICKNESS L"\u2f67" #define UNICODE_KANGXI_RADICAL_DOTTED_TENT 0x2f68 #define UNITEXT_KANGXI_RADICAL_DOTTED_TENT L"\u2f68" #define UNICODE_KANGXI_RADICAL_WHITE 0x2f69 #define UNITEXT_KANGXI_RADICAL_WHITE L"\u2f69" #define UNICODE_KANGXI_RADICAL_SKIN 0x2f6a #define UNITEXT_KANGXI_RADICAL_SKIN L"\u2f6a" #define UNICODE_KANGXI_RADICAL_DISH 0x2f6b #define UNITEXT_KANGXI_RADICAL_DISH L"\u2f6b" #define UNICODE_KANGXI_RADICAL_EYE 0x2f6c #define UNITEXT_KANGXI_RADICAL_EYE L"\u2f6c" #define UNICODE_KANGXI_RADICAL_SPEAR 0x2f6d #define UNITEXT_KANGXI_RADICAL_SPEAR L"\u2f6d" #define UNICODE_KANGXI_RADICAL_ARROW 0x2f6e #define UNITEXT_KANGXI_RADICAL_ARROW L"\u2f6e" #define UNICODE_KANGXI_RADICAL_STONE 0x2f6f #define UNITEXT_KANGXI_RADICAL_STONE L"\u2f6f" #define UNICODE_KANGXI_RADICAL_SPIRIT 0x2f70 #define UNITEXT_KANGXI_RADICAL_SPIRIT L"\u2f70" #define UNICODE_KANGXI_RADICAL_TRACK 0x2f71 #define UNITEXT_KANGXI_RADICAL_TRACK L"\u2f71" #define UNICODE_KANGXI_RADICAL_GRAIN 0x2f72 #define UNITEXT_KANGXI_RADICAL_GRAIN L"\u2f72" #define UNICODE_KANGXI_RADICAL_CAVE 0x2f73 #define UNITEXT_KANGXI_RADICAL_CAVE L"\u2f73" #define UNICODE_KANGXI_RADICAL_STAND 0x2f74 #define UNITEXT_KANGXI_RADICAL_STAND L"\u2f74" #define UNICODE_KANGXI_RADICAL_BAMBOO 0x2f75 #define UNITEXT_KANGXI_RADICAL_BAMBOO L"\u2f75" #define UNICODE_KANGXI_RADICAL_RICE 0x2f76 #define UNITEXT_KANGXI_RADICAL_RICE L"\u2f76" #define UNICODE_KANGXI_RADICAL_SILK 0x2f77 #define UNITEXT_KANGXI_RADICAL_SILK L"\u2f77" #define UNICODE_KANGXI_RADICAL_JAR 0x2f78 #define UNITEXT_KANGXI_RADICAL_JAR L"\u2f78" #define UNICODE_KANGXI_RADICAL_NET 0x2f79 #define UNITEXT_KANGXI_RADICAL_NET L"\u2f79" #define UNICODE_KANGXI_RADICAL_SHEEP 0x2f7a #define UNITEXT_KANGXI_RADICAL_SHEEP L"\u2f7a" #define UNICODE_KANGXI_RADICAL_FEATHER 0x2f7b #define UNITEXT_KANGXI_RADICAL_FEATHER L"\u2f7b" #define UNICODE_KANGXI_RADICAL_OLD 0x2f7c #define UNITEXT_KANGXI_RADICAL_OLD L"\u2f7c" #define UNICODE_KANGXI_RADICAL_AND 0x2f7d #define UNITEXT_KANGXI_RADICAL_AND L"\u2f7d" #define UNICODE_KANGXI_RADICAL_PLOW 0x2f7e #define UNITEXT_KANGXI_RADICAL_PLOW L"\u2f7e" #define UNICODE_KANGXI_RADICAL_EAR 0x2f7f #define UNITEXT_KANGXI_RADICAL_EAR L"\u2f7f" #define UNICODE_KANGXI_RADICAL_BRUSH 0x2f80 #define UNITEXT_KANGXI_RADICAL_BRUSH L"\u2f80" #define UNICODE_KANGXI_RADICAL_MEAT 0x2f81 #define UNITEXT_KANGXI_RADICAL_MEAT L"\u2f81" #define UNICODE_KANGXI_RADICAL_MINISTER 0x2f82 #define UNITEXT_KANGXI_RADICAL_MINISTER L"\u2f82" #define UNICODE_KANGXI_RADICAL_SELF 0x2f83 #define UNITEXT_KANGXI_RADICAL_SELF L"\u2f83" #define UNICODE_KANGXI_RADICAL_ARRIVE 0x2f84 #define UNITEXT_KANGXI_RADICAL_ARRIVE L"\u2f84" #define UNICODE_KANGXI_RADICAL_MORTAR 0x2f85 #define UNITEXT_KANGXI_RADICAL_MORTAR L"\u2f85" #define UNICODE_KANGXI_RADICAL_TONGUE 0x2f86 #define UNITEXT_KANGXI_RADICAL_TONGUE L"\u2f86" #define UNICODE_KANGXI_RADICAL_OPPOSE 0x2f87 #define UNITEXT_KANGXI_RADICAL_OPPOSE L"\u2f87" #define UNICODE_KANGXI_RADICAL_BOAT 0x2f88 #define UNITEXT_KANGXI_RADICAL_BOAT L"\u2f88" #define UNICODE_KANGXI_RADICAL_STOPPING 0x2f89 #define UNITEXT_KANGXI_RADICAL_STOPPING L"\u2f89" #define UNICODE_KANGXI_RADICAL_COLOR 0x2f8a #define UNITEXT_KANGXI_RADICAL_COLOR L"\u2f8a" #define UNICODE_KANGXI_RADICAL_GRASS 0x2f8b #define UNITEXT_KANGXI_RADICAL_GRASS L"\u2f8b" #define UNICODE_KANGXI_RADICAL_TIGER 0x2f8c #define UNITEXT_KANGXI_RADICAL_TIGER L"\u2f8c" #define UNICODE_KANGXI_RADICAL_INSECT 0x2f8d #define UNITEXT_KANGXI_RADICAL_INSECT L"\u2f8d" #define UNICODE_KANGXI_RADICAL_BLOOD 0x2f8e #define UNITEXT_KANGXI_RADICAL_BLOOD L"\u2f8e" #define UNICODE_KANGXI_RADICAL_WALK_ENCLOSURE 0x2f8f #define UNITEXT_KANGXI_RADICAL_WALK_ENCLOSURE L"\u2f8f" #define UNICODE_KANGXI_RADICAL_CLOTHES 0x2f90 #define UNITEXT_KANGXI_RADICAL_CLOTHES L"\u2f90" #define UNICODE_KANGXI_RADICAL_WEST 0x2f91 #define UNITEXT_KANGXI_RADICAL_WEST L"\u2f91" #define UNICODE_KANGXI_RADICAL_SEE 0x2f92 #define UNITEXT_KANGXI_RADICAL_SEE L"\u2f92" #define UNICODE_KANGXI_RADICAL_HORN 0x2f93 #define UNITEXT_KANGXI_RADICAL_HORN L"\u2f93" #define UNICODE_KANGXI_RADICAL_SPEECH 0x2f94 #define UNITEXT_KANGXI_RADICAL_SPEECH L"\u2f94" #define UNICODE_KANGXI_RADICAL_VALLEY 0x2f95 #define UNITEXT_KANGXI_RADICAL_VALLEY L"\u2f95" #define UNICODE_KANGXI_RADICAL_BEAN 0x2f96 #define UNITEXT_KANGXI_RADICAL_BEAN L"\u2f96" #define UNICODE_KANGXI_RADICAL_PIG 0x2f97 #define UNITEXT_KANGXI_RADICAL_PIG L"\u2f97" #define UNICODE_KANGXI_RADICAL_BADGER 0x2f98 #define UNITEXT_KANGXI_RADICAL_BADGER L"\u2f98" #define UNICODE_KANGXI_RADICAL_SHELL 0x2f99 #define UNITEXT_KANGXI_RADICAL_SHELL L"\u2f99" #define UNICODE_KANGXI_RADICAL_RED 0x2f9a #define UNITEXT_KANGXI_RADICAL_RED L"\u2f9a" #define UNICODE_KANGXI_RADICAL_RUN 0x2f9b #define UNITEXT_KANGXI_RADICAL_RUN L"\u2f9b" #define UNICODE_KANGXI_RADICAL_FOOT 0x2f9c #define UNITEXT_KANGXI_RADICAL_FOOT L"\u2f9c" #define UNICODE_KANGXI_RADICAL_BODY 0x2f9d #define UNITEXT_KANGXI_RADICAL_BODY L"\u2f9d" #define UNICODE_KANGXI_RADICAL_CART 0x2f9e #define UNITEXT_KANGXI_RADICAL_CART L"\u2f9e" #define UNICODE_KANGXI_RADICAL_BITTER 0x2f9f #define UNITEXT_KANGXI_RADICAL_BITTER L"\u2f9f" #define UNICODE_KANGXI_RADICAL_MORNING 0x2fa0 #define UNITEXT_KANGXI_RADICAL_MORNING L"\u2fa0" #define UNICODE_KANGXI_RADICAL_WALK 0x2fa1 #define UNITEXT_KANGXI_RADICAL_WALK L"\u2fa1" #define UNICODE_KANGXI_RADICAL_CITY 0x2fa2 #define UNITEXT_KANGXI_RADICAL_CITY L"\u2fa2" #define UNICODE_KANGXI_RADICAL_WINE 0x2fa3 #define UNITEXT_KANGXI_RADICAL_WINE L"\u2fa3" #define UNICODE_KANGXI_RADICAL_DISTINGUISH 0x2fa4 #define UNITEXT_KANGXI_RADICAL_DISTINGUISH L"\u2fa4" #define UNICODE_KANGXI_RADICAL_VILLAGE 0x2fa5 #define UNITEXT_KANGXI_RADICAL_VILLAGE L"\u2fa5" #define UNICODE_KANGXI_RADICAL_GOLD 0x2fa6 #define UNITEXT_KANGXI_RADICAL_GOLD L"\u2fa6" #define UNICODE_KANGXI_RADICAL_LONG 0x2fa7 #define UNITEXT_KANGXI_RADICAL_LONG L"\u2fa7" #define UNICODE_KANGXI_RADICAL_GATE 0x2fa8 #define UNITEXT_KANGXI_RADICAL_GATE L"\u2fa8" #define UNICODE_KANGXI_RADICAL_MOUND 0x2fa9 #define UNITEXT_KANGXI_RADICAL_MOUND L"\u2fa9" #define UNICODE_KANGXI_RADICAL_SLAVE 0x2faa #define UNITEXT_KANGXI_RADICAL_SLAVE L"\u2faa" #define UNICODE_KANGXI_RADICAL_SHORT_TAILED_BIRD 0x2fab #define UNITEXT_KANGXI_RADICAL_SHORT_TAILED_BIRD L"\u2fab" #define UNICODE_KANGXI_RADICAL_RAIN 0x2fac #define UNITEXT_KANGXI_RADICAL_RAIN L"\u2fac" #define UNICODE_KANGXI_RADICAL_BLUE 0x2fad #define UNITEXT_KANGXI_RADICAL_BLUE L"\u2fad" #define UNICODE_KANGXI_RADICAL_WRONG 0x2fae #define UNITEXT_KANGXI_RADICAL_WRONG L"\u2fae" #define UNICODE_KANGXI_RADICAL_FACE 0x2faf #define UNITEXT_KANGXI_RADICAL_FACE L"\u2faf" #define UNICODE_KANGXI_RADICAL_LEATHER 0x2fb0 #define UNITEXT_KANGXI_RADICAL_LEATHER L"\u2fb0" #define UNICODE_KANGXI_RADICAL_TANNED_LEATHER 0x2fb1 #define UNITEXT_KANGXI_RADICAL_TANNED_LEATHER L"\u2fb1" #define UNICODE_KANGXI_RADICAL_LEEK 0x2fb2 #define UNITEXT_KANGXI_RADICAL_LEEK L"\u2fb2" #define UNICODE_KANGXI_RADICAL_SOUND 0x2fb3 #define UNITEXT_KANGXI_RADICAL_SOUND L"\u2fb3" #define UNICODE_KANGXI_RADICAL_LEAF 0x2fb4 #define UNITEXT_KANGXI_RADICAL_LEAF L"\u2fb4" #define UNICODE_KANGXI_RADICAL_WIND 0x2fb5 #define UNITEXT_KANGXI_RADICAL_WIND L"\u2fb5" #define UNICODE_KANGXI_RADICAL_FLY 0x2fb6 #define UNITEXT_KANGXI_RADICAL_FLY L"\u2fb6" #define UNICODE_KANGXI_RADICAL_EAT 0x2fb7 #define UNITEXT_KANGXI_RADICAL_EAT L"\u2fb7" #define UNICODE_KANGXI_RADICAL_HEAD 0x2fb8 #define UNITEXT_KANGXI_RADICAL_HEAD L"\u2fb8" #define UNICODE_KANGXI_RADICAL_FRAGRANT 0x2fb9 #define UNITEXT_KANGXI_RADICAL_FRAGRANT L"\u2fb9" #define UNICODE_KANGXI_RADICAL_HORSE 0x2fba #define UNITEXT_KANGXI_RADICAL_HORSE L"\u2fba" #define UNICODE_KANGXI_RADICAL_BONE 0x2fbb #define UNITEXT_KANGXI_RADICAL_BONE L"\u2fbb" #define UNICODE_KANGXI_RADICAL_TALL 0x2fbc #define UNITEXT_KANGXI_RADICAL_TALL L"\u2fbc" #define UNICODE_KANGXI_RADICAL_HAIR 0x2fbd #define UNITEXT_KANGXI_RADICAL_HAIR L"\u2fbd" #define UNICODE_KANGXI_RADICAL_FIGHT 0x2fbe #define UNITEXT_KANGXI_RADICAL_FIGHT L"\u2fbe" #define UNICODE_KANGXI_RADICAL_SACRIFICIAL_WINE 0x2fbf #define UNITEXT_KANGXI_RADICAL_SACRIFICIAL_WINE L"\u2fbf" #define UNICODE_KANGXI_RADICAL_CAULDRON 0x2fc0 #define UNITEXT_KANGXI_RADICAL_CAULDRON L"\u2fc0" #define UNICODE_KANGXI_RADICAL_GHOST 0x2fc1 #define UNITEXT_KANGXI_RADICAL_GHOST L"\u2fc1" #define UNICODE_KANGXI_RADICAL_FISH 0x2fc2 #define UNITEXT_KANGXI_RADICAL_FISH L"\u2fc2" #define UNICODE_KANGXI_RADICAL_BIRD 0x2fc3 #define UNITEXT_KANGXI_RADICAL_BIRD L"\u2fc3" #define UNICODE_KANGXI_RADICAL_SALT 0x2fc4 #define UNITEXT_KANGXI_RADICAL_SALT L"\u2fc4" #define UNICODE_KANGXI_RADICAL_DEER 0x2fc5 #define UNITEXT_KANGXI_RADICAL_DEER L"\u2fc5" #define UNICODE_KANGXI_RADICAL_WHEAT 0x2fc6 #define UNITEXT_KANGXI_RADICAL_WHEAT L"\u2fc6" #define UNICODE_KANGXI_RADICAL_HEMP 0x2fc7 #define UNITEXT_KANGXI_RADICAL_HEMP L"\u2fc7" #define UNICODE_KANGXI_RADICAL_YELLOW 0x2fc8 #define UNITEXT_KANGXI_RADICAL_YELLOW L"\u2fc8" #define UNICODE_KANGXI_RADICAL_MILLET 0x2fc9 #define UNITEXT_KANGXI_RADICAL_MILLET L"\u2fc9" #define UNICODE_KANGXI_RADICAL_BLACK 0x2fca #define UNITEXT_KANGXI_RADICAL_BLACK L"\u2fca" #define UNICODE_KANGXI_RADICAL_EMBROIDERY 0x2fcb #define UNITEXT_KANGXI_RADICAL_EMBROIDERY L"\u2fcb" #define UNICODE_KANGXI_RADICAL_FROG 0x2fcc #define UNITEXT_KANGXI_RADICAL_FROG L"\u2fcc" #define UNICODE_KANGXI_RADICAL_TRIPOD 0x2fcd #define UNITEXT_KANGXI_RADICAL_TRIPOD L"\u2fcd" #define UNICODE_KANGXI_RADICAL_DRUM 0x2fce #define UNITEXT_KANGXI_RADICAL_DRUM L"\u2fce" #define UNICODE_KANGXI_RADICAL_RAT 0x2fcf #define UNITEXT_KANGXI_RADICAL_RAT L"\u2fcf" #define UNICODE_KANGXI_RADICAL_NOSE 0x2fd0 #define UNITEXT_KANGXI_RADICAL_NOSE L"\u2fd0" #define UNICODE_KANGXI_RADICAL_EVEN 0x2fd1 #define UNITEXT_KANGXI_RADICAL_EVEN L"\u2fd1" #define UNICODE_KANGXI_RADICAL_TOOTH 0x2fd2 #define UNITEXT_KANGXI_RADICAL_TOOTH L"\u2fd2" #define UNICODE_KANGXI_RADICAL_DRAGON 0x2fd3 #define UNITEXT_KANGXI_RADICAL_DRAGON L"\u2fd3" #define UNICODE_KANGXI_RADICAL_TURTLE 0x2fd4 #define UNITEXT_KANGXI_RADICAL_TURTLE L"\u2fd4" #define UNICODE_KANGXI_RADICAL_FLUTE 0x2fd5 #define UNITEXT_KANGXI_RADICAL_FLUTE L"\u2fd5" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_LEFT_TO_RIGHT 0x2ff0 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_LEFT_TO_RIGHT L"\u2ff0" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_ABOVE_TO_BELOW 0x2ff1 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_ABOVE_TO_BELOW L"\u2ff1" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_LEFT_TO_MIDDLE_AND_RIGHT 0x2ff2 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_LEFT_TO_MIDDLE_AND_RIGHT L"\u2ff2" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_ABOVE_TO_MIDDLE_AND_BELOW 0x2ff3 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_ABOVE_TO_MIDDLE_AND_BELOW L"\u2ff3" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_FULL_SURROUND 0x2ff4 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_FULL_SURROUND L"\u2ff4" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_ABOVE 0x2ff5 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_ABOVE L"\u2ff5" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_BELOW 0x2ff6 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_BELOW L"\u2ff6" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_LEFT 0x2ff7 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_LEFT L"\u2ff7" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_UPPER_LEFT 0x2ff8 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_UPPER_LEFT L"\u2ff8" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_UPPER_RIGHT 0x2ff9 #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_UPPER_RIGHT L"\u2ff9" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_LOWER_LEFT 0x2ffa #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_SURROUND_FROM_LOWER_LEFT L"\u2ffa" #define UNICODE_IDEOGRAPHIC_DESCRIPTION_CHARACTER_OVERLAID 0x2ffb #define UNITEXT_IDEOGRAPHIC_DESCRIPTION_CHARACTER_OVERLAID L"\u2ffb" #define UNICODE_IDEOGRAPHIC_SPACE 0x3000 #define UNITEXT_IDEOGRAPHIC_SPACE L"\u3000" #define UNICODE_IDEOGRAPHIC_COMMA 0x3001 #define UNITEXT_IDEOGRAPHIC_COMMA L"\u3001" #define UNICODE_IDEOGRAPHIC_FULL_STOP 0x3002 #define UNITEXT_IDEOGRAPHIC_FULL_STOP L"\u3002" #define UNICODE_DITTO_MARK 0x3003 #define UNITEXT_DITTO_MARK L"\u3003" #define UNICODE_JAPANESE_INDUSTRIAL_STANDARD_SYMBOL 0x3004 #define UNITEXT_JAPANESE_INDUSTRIAL_STANDARD_SYMBOL L"\u3004" #define UNICODE_IDEOGRAPHIC_ITERATION_MARK 0x3005 #define UNITEXT_IDEOGRAPHIC_ITERATION_MARK L"\u3005" #define UNICODE_IDEOGRAPHIC_CLOSING_MARK 0x3006 #define UNITEXT_IDEOGRAPHIC_CLOSING_MARK L"\u3006" #define UNICODE_IDEOGRAPHIC_NUMBER_ZERO 0x3007 #define UNITEXT_IDEOGRAPHIC_NUMBER_ZERO L"\u3007" #define UNICODE_LEFT_ANGLE_BRACKET 0x3008 #define UNITEXT_LEFT_ANGLE_BRACKET L"\u3008" #define UNICODE_RIGHT_ANGLE_BRACKET 0x3009 #define UNITEXT_RIGHT_ANGLE_BRACKET L"\u3009" #define UNICODE_LEFT_DOUBLE_ANGLE_BRACKET 0x300a #define UNITEXT_LEFT_DOUBLE_ANGLE_BRACKET L"\u300a" #define UNICODE_RIGHT_DOUBLE_ANGLE_BRACKET 0x300b #define UNITEXT_RIGHT_DOUBLE_ANGLE_BRACKET L"\u300b" #define UNICODE_LEFT_CORNER_BRACKET 0x300c #define UNITEXT_LEFT_CORNER_BRACKET L"\u300c" #define UNICODE_RIGHT_CORNER_BRACKET 0x300d #define UNITEXT_RIGHT_CORNER_BRACKET L"\u300d" #define UNICODE_LEFT_WHITE_CORNER_BRACKET 0x300e #define UNITEXT_LEFT_WHITE_CORNER_BRACKET L"\u300e" #define UNICODE_RIGHT_WHITE_CORNER_BRACKET 0x300f #define UNITEXT_RIGHT_WHITE_CORNER_BRACKET L"\u300f" #define UNICODE_LEFT_BLACK_LENTICULAR_BRACKET 0x3010 #define UNITEXT_LEFT_BLACK_LENTICULAR_BRACKET L"\u3010" #define UNICODE_RIGHT_BLACK_LENTICULAR_BRACKET 0x3011 #define UNITEXT_RIGHT_BLACK_LENTICULAR_BRACKET L"\u3011" #define UNICODE_POSTAL_MARK 0x3012 #define UNITEXT_POSTAL_MARK L"\u3012" #define UNICODE_GETA_MARK 0x3013 #define UNITEXT_GETA_MARK L"\u3013" #define UNICODE_LEFT_TORTOISE_SHELL_BRACKET 0x3014 #define UNITEXT_LEFT_TORTOISE_SHELL_BRACKET L"\u3014" #define UNICODE_RIGHT_TORTOISE_SHELL_BRACKET 0x3015 #define UNITEXT_RIGHT_TORTOISE_SHELL_BRACKET L"\u3015" #define UNICODE_LEFT_WHITE_LENTICULAR_BRACKET 0x3016 #define UNITEXT_LEFT_WHITE_LENTICULAR_BRACKET L"\u3016" #define UNICODE_RIGHT_WHITE_LENTICULAR_BRACKET 0x3017 #define UNITEXT_RIGHT_WHITE_LENTICULAR_BRACKET L"\u3017" #define UNICODE_LEFT_WHITE_TORTOISE_SHELL_BRACKET 0x3018 #define UNITEXT_LEFT_WHITE_TORTOISE_SHELL_BRACKET L"\u3018" #define UNICODE_RIGHT_WHITE_TORTOISE_SHELL_BRACKET 0x3019 #define UNITEXT_RIGHT_WHITE_TORTOISE_SHELL_BRACKET L"\u3019" #define UNICODE_LEFT_WHITE_SQUARE_BRACKET 0x301a #define UNITEXT_LEFT_WHITE_SQUARE_BRACKET L"\u301a" #define UNICODE_RIGHT_WHITE_SQUARE_BRACKET 0x301b #define UNITEXT_RIGHT_WHITE_SQUARE_BRACKET L"\u301b" #define UNICODE_WAVE_DASH 0x301c #define UNITEXT_WAVE_DASH L"\u301c" #define UNICODE_REVERSED_DOUBLE_PRIME_QUOTATION_MARK 0x301d #define UNITEXT_REVERSED_DOUBLE_PRIME_QUOTATION_MARK L"\u301d" #define UNICODE_DOUBLE_PRIME_QUOTATION_MARK 0x301e #define UNITEXT_DOUBLE_PRIME_QUOTATION_MARK L"\u301e" #define UNICODE_LOW_DOUBLE_PRIME_QUOTATION_MARK 0x301f #define UNITEXT_LOW_DOUBLE_PRIME_QUOTATION_MARK L"\u301f" #define UNICODE_POSTAL_MARK_FACE 0x3020 #define UNITEXT_POSTAL_MARK_FACE L"\u3020" #define UNICODE_HANGZHOU_NUMERAL_ONE 0x3021 #define UNITEXT_HANGZHOU_NUMERAL_ONE L"\u3021" #define UNICODE_HANGZHOU_NUMERAL_TWO 0x3022 #define UNITEXT_HANGZHOU_NUMERAL_TWO L"\u3022" #define UNICODE_HANGZHOU_NUMERAL_THREE 0x3023 #define UNITEXT_HANGZHOU_NUMERAL_THREE L"\u3023" #define UNICODE_HANGZHOU_NUMERAL_FOUR 0x3024 #define UNITEXT_HANGZHOU_NUMERAL_FOUR L"\u3024" #define UNICODE_HANGZHOU_NUMERAL_FIVE 0x3025 #define UNITEXT_HANGZHOU_NUMERAL_FIVE L"\u3025" #define UNICODE_HANGZHOU_NUMERAL_SIX 0x3026 #define UNITEXT_HANGZHOU_NUMERAL_SIX L"\u3026" #define UNICODE_HANGZHOU_NUMERAL_SEVEN 0x3027 #define UNITEXT_HANGZHOU_NUMERAL_SEVEN L"\u3027" #define UNICODE_HANGZHOU_NUMERAL_EIGHT 0x3028 #define UNITEXT_HANGZHOU_NUMERAL_EIGHT L"\u3028" #define UNICODE_HANGZHOU_NUMERAL_NINE 0x3029 #define UNITEXT_HANGZHOU_NUMERAL_NINE L"\u3029" #define UNICODE_IDEOGRAPHIC_LEVEL_TONE_MARK 0x302a #define UNITEXT_IDEOGRAPHIC_LEVEL_TONE_MARK L"\u302a" #define UNICODE_IDEOGRAPHIC_RISING_TONE_MARK 0x302b #define UNITEXT_IDEOGRAPHIC_RISING_TONE_MARK L"\u302b" #define UNICODE_IDEOGRAPHIC_DEPARTING_TONE_MARK 0x302c #define UNITEXT_IDEOGRAPHIC_DEPARTING_TONE_MARK L"\u302c" #define UNICODE_IDEOGRAPHIC_ENTERING_TONE_MARK 0x302d #define UNITEXT_IDEOGRAPHIC_ENTERING_TONE_MARK L"\u302d" #define UNICODE_HANGUL_SINGLE_DOT_TONE_MARK 0x302e #define UNITEXT_HANGUL_SINGLE_DOT_TONE_MARK L"\u302e" #define UNICODE_HANGUL_DOUBLE_DOT_TONE_MARK 0x302f #define UNITEXT_HANGUL_DOUBLE_DOT_TONE_MARK L"\u302f" #define UNICODE_WAVY_DASH 0x3030 #define UNITEXT_WAVY_DASH L"\u3030" #define UNICODE_VERTICAL_KANA_REPEAT_MARK 0x3031 #define UNITEXT_VERTICAL_KANA_REPEAT_MARK L"\u3031" #define UNICODE_VERTICAL_KANA_REPEAT_WITH_VOICED_SOUND_MARK 0x3032 #define UNITEXT_VERTICAL_KANA_REPEAT_WITH_VOICED_SOUND_MARK L"\u3032" #define UNICODE_VERTICAL_KANA_REPEAT_MARK_UPPER_HALF 0x3033 #define UNITEXT_VERTICAL_KANA_REPEAT_MARK_UPPER_HALF L"\u3033" #define UNICODE_VERTICAL_KANA_REPEAT_WITH_VOICED_SOUND_MARK_UPPER_HALF 0x3034 #define UNITEXT_VERTICAL_KANA_REPEAT_WITH_VOICED_SOUND_MARK_UPPER_HALF L"\u3034" #define UNICODE_VERTICAL_KANA_REPEAT_MARK_LOWER_HALF 0x3035 #define UNITEXT_VERTICAL_KANA_REPEAT_MARK_LOWER_HALF L"\u3035" #define UNICODE_CIRCLED_POSTAL_MARK 0x3036 #define UNITEXT_CIRCLED_POSTAL_MARK L"\u3036" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_LINE_FEED_SEPARATOR_SYMBOL 0x3037 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_LINE_FEED_SEPARATOR_SYMBOL L"\u3037" #define UNICODE_HANGZHOU_NUMERAL_TEN 0x3038 #define UNITEXT_HANGZHOU_NUMERAL_TEN L"\u3038" #define UNICODE_HANGZHOU_NUMERAL_TWENTY 0x3039 #define UNITEXT_HANGZHOU_NUMERAL_TWENTY L"\u3039" #define UNICODE_HANGZHOU_NUMERAL_THIRTY 0x303a #define UNITEXT_HANGZHOU_NUMERAL_THIRTY L"\u303a" #define UNICODE_VERTICAL_IDEOGRAPHIC_ITERATION_MARK 0x303b #define UNITEXT_VERTICAL_IDEOGRAPHIC_ITERATION_MARK L"\u303b" #define UNICODE_MASU_MARK 0x303c #define UNITEXT_MASU_MARK L"\u303c" #define UNICODE_PART_ALTERNATION_MARK 0x303d #define UNITEXT_PART_ALTERNATION_MARK L"\u303d" #define UNICODE_IDEOGRAPHIC_VARIATION_INDICATOR 0x303e #define UNITEXT_IDEOGRAPHIC_VARIATION_INDICATOR L"\u303e" #define UNICODE_IDEOGRAPHIC_HALF_FILL_SPACE 0x303f #define UNITEXT_IDEOGRAPHIC_HALF_FILL_SPACE L"\u303f" #define UNICODE_HIRAGANA_LETTER_SMALL_A 0x3041 #define UNITEXT_HIRAGANA_LETTER_SMALL_A L"\u3041" #define UNICODE_HIRAGANA_LETTER_A 0x3042 #define UNITEXT_HIRAGANA_LETTER_A L"\u3042" #define UNICODE_HIRAGANA_LETTER_SMALL_I 0x3043 #define UNITEXT_HIRAGANA_LETTER_SMALL_I L"\u3043" #define UNICODE_HIRAGANA_LETTER_I 0x3044 #define UNITEXT_HIRAGANA_LETTER_I L"\u3044" #define UNICODE_HIRAGANA_LETTER_SMALL_U 0x3045 #define UNITEXT_HIRAGANA_LETTER_SMALL_U L"\u3045" #define UNICODE_HIRAGANA_LETTER_U 0x3046 #define UNITEXT_HIRAGANA_LETTER_U L"\u3046" #define UNICODE_HIRAGANA_LETTER_SMALL_E 0x3047 #define UNITEXT_HIRAGANA_LETTER_SMALL_E L"\u3047" #define UNICODE_HIRAGANA_LETTER_E 0x3048 #define UNITEXT_HIRAGANA_LETTER_E L"\u3048" #define UNICODE_HIRAGANA_LETTER_SMALL_O 0x3049 #define UNITEXT_HIRAGANA_LETTER_SMALL_O L"\u3049" #define UNICODE_HIRAGANA_LETTER_O 0x304a #define UNITEXT_HIRAGANA_LETTER_O L"\u304a" #define UNICODE_HIRAGANA_LETTER_KA 0x304b #define UNITEXT_HIRAGANA_LETTER_KA L"\u304b" #define UNICODE_HIRAGANA_LETTER_GA 0x304c #define UNITEXT_HIRAGANA_LETTER_GA L"\u304c" #define UNICODE_HIRAGANA_LETTER_KI 0x304d #define UNITEXT_HIRAGANA_LETTER_KI L"\u304d" #define UNICODE_HIRAGANA_LETTER_GI 0x304e #define UNITEXT_HIRAGANA_LETTER_GI L"\u304e" #define UNICODE_HIRAGANA_LETTER_KU 0x304f #define UNITEXT_HIRAGANA_LETTER_KU L"\u304f" #define UNICODE_HIRAGANA_LETTER_GU 0x3050 #define UNITEXT_HIRAGANA_LETTER_GU L"\u3050" #define UNICODE_HIRAGANA_LETTER_KE 0x3051 #define UNITEXT_HIRAGANA_LETTER_KE L"\u3051" #define UNICODE_HIRAGANA_LETTER_GE 0x3052 #define UNITEXT_HIRAGANA_LETTER_GE L"\u3052" #define UNICODE_HIRAGANA_LETTER_KO 0x3053 #define UNITEXT_HIRAGANA_LETTER_KO L"\u3053" #define UNICODE_HIRAGANA_LETTER_GO 0x3054 #define UNITEXT_HIRAGANA_LETTER_GO L"\u3054" #define UNICODE_HIRAGANA_LETTER_SA 0x3055 #define UNITEXT_HIRAGANA_LETTER_SA L"\u3055" #define UNICODE_HIRAGANA_LETTER_ZA 0x3056 #define UNITEXT_HIRAGANA_LETTER_ZA L"\u3056" #define UNICODE_HIRAGANA_LETTER_SI 0x3057 #define UNITEXT_HIRAGANA_LETTER_SI L"\u3057" #define UNICODE_HIRAGANA_LETTER_ZI 0x3058 #define UNITEXT_HIRAGANA_LETTER_ZI L"\u3058" #define UNICODE_HIRAGANA_LETTER_SU 0x3059 #define UNITEXT_HIRAGANA_LETTER_SU L"\u3059" #define UNICODE_HIRAGANA_LETTER_ZU 0x305a #define UNITEXT_HIRAGANA_LETTER_ZU L"\u305a" #define UNICODE_HIRAGANA_LETTER_SE 0x305b #define UNITEXT_HIRAGANA_LETTER_SE L"\u305b" #define UNICODE_HIRAGANA_LETTER_ZE 0x305c #define UNITEXT_HIRAGANA_LETTER_ZE L"\u305c" #define UNICODE_HIRAGANA_LETTER_SO 0x305d #define UNITEXT_HIRAGANA_LETTER_SO L"\u305d" #define UNICODE_HIRAGANA_LETTER_ZO 0x305e #define UNITEXT_HIRAGANA_LETTER_ZO L"\u305e" #define UNICODE_HIRAGANA_LETTER_TA 0x305f #define UNITEXT_HIRAGANA_LETTER_TA L"\u305f" #define UNICODE_HIRAGANA_LETTER_DA 0x3060 #define UNITEXT_HIRAGANA_LETTER_DA L"\u3060" #define UNICODE_HIRAGANA_LETTER_TI 0x3061 #define UNITEXT_HIRAGANA_LETTER_TI L"\u3061" #define UNICODE_HIRAGANA_LETTER_DI 0x3062 #define UNITEXT_HIRAGANA_LETTER_DI L"\u3062" #define UNICODE_HIRAGANA_LETTER_SMALL_TU 0x3063 #define UNITEXT_HIRAGANA_LETTER_SMALL_TU L"\u3063" #define UNICODE_HIRAGANA_LETTER_TU 0x3064 #define UNITEXT_HIRAGANA_LETTER_TU L"\u3064" #define UNICODE_HIRAGANA_LETTER_DU 0x3065 #define UNITEXT_HIRAGANA_LETTER_DU L"\u3065" #define UNICODE_HIRAGANA_LETTER_TE 0x3066 #define UNITEXT_HIRAGANA_LETTER_TE L"\u3066" #define UNICODE_HIRAGANA_LETTER_DE 0x3067 #define UNITEXT_HIRAGANA_LETTER_DE L"\u3067" #define UNICODE_HIRAGANA_LETTER_TO 0x3068 #define UNITEXT_HIRAGANA_LETTER_TO L"\u3068" #define UNICODE_HIRAGANA_LETTER_DO 0x3069 #define UNITEXT_HIRAGANA_LETTER_DO L"\u3069" #define UNICODE_HIRAGANA_LETTER_NA 0x306a #define UNITEXT_HIRAGANA_LETTER_NA L"\u306a" #define UNICODE_HIRAGANA_LETTER_NI 0x306b #define UNITEXT_HIRAGANA_LETTER_NI L"\u306b" #define UNICODE_HIRAGANA_LETTER_NU 0x306c #define UNITEXT_HIRAGANA_LETTER_NU L"\u306c" #define UNICODE_HIRAGANA_LETTER_NE 0x306d #define UNITEXT_HIRAGANA_LETTER_NE L"\u306d" #define UNICODE_HIRAGANA_LETTER_NO 0x306e #define UNITEXT_HIRAGANA_LETTER_NO L"\u306e" #define UNICODE_HIRAGANA_LETTER_HA 0x306f #define UNITEXT_HIRAGANA_LETTER_HA L"\u306f" #define UNICODE_HIRAGANA_LETTER_BA 0x3070 #define UNITEXT_HIRAGANA_LETTER_BA L"\u3070" #define UNICODE_HIRAGANA_LETTER_PA 0x3071 #define UNITEXT_HIRAGANA_LETTER_PA L"\u3071" #define UNICODE_HIRAGANA_LETTER_HI 0x3072 #define UNITEXT_HIRAGANA_LETTER_HI L"\u3072" #define UNICODE_HIRAGANA_LETTER_BI 0x3073 #define UNITEXT_HIRAGANA_LETTER_BI L"\u3073" #define UNICODE_HIRAGANA_LETTER_PI 0x3074 #define UNITEXT_HIRAGANA_LETTER_PI L"\u3074" #define UNICODE_HIRAGANA_LETTER_HU 0x3075 #define UNITEXT_HIRAGANA_LETTER_HU L"\u3075" #define UNICODE_HIRAGANA_LETTER_BU 0x3076 #define UNITEXT_HIRAGANA_LETTER_BU L"\u3076" #define UNICODE_HIRAGANA_LETTER_PU 0x3077 #define UNITEXT_HIRAGANA_LETTER_PU L"\u3077" #define UNICODE_HIRAGANA_LETTER_HE 0x3078 #define UNITEXT_HIRAGANA_LETTER_HE L"\u3078" #define UNICODE_HIRAGANA_LETTER_BE 0x3079 #define UNITEXT_HIRAGANA_LETTER_BE L"\u3079" #define UNICODE_HIRAGANA_LETTER_PE 0x307a #define UNITEXT_HIRAGANA_LETTER_PE L"\u307a" #define UNICODE_HIRAGANA_LETTER_HO 0x307b #define UNITEXT_HIRAGANA_LETTER_HO L"\u307b" #define UNICODE_HIRAGANA_LETTER_BO 0x307c #define UNITEXT_HIRAGANA_LETTER_BO L"\u307c" #define UNICODE_HIRAGANA_LETTER_PO 0x307d #define UNITEXT_HIRAGANA_LETTER_PO L"\u307d" #define UNICODE_HIRAGANA_LETTER_MA 0x307e #define UNITEXT_HIRAGANA_LETTER_MA L"\u307e" #define UNICODE_HIRAGANA_LETTER_MI 0x307f #define UNITEXT_HIRAGANA_LETTER_MI L"\u307f" #define UNICODE_HIRAGANA_LETTER_MU 0x3080 #define UNITEXT_HIRAGANA_LETTER_MU L"\u3080" #define UNICODE_HIRAGANA_LETTER_ME 0x3081 #define UNITEXT_HIRAGANA_LETTER_ME L"\u3081" #define UNICODE_HIRAGANA_LETTER_MO 0x3082 #define UNITEXT_HIRAGANA_LETTER_MO L"\u3082" #define UNICODE_HIRAGANA_LETTER_SMALL_YA 0x3083 #define UNITEXT_HIRAGANA_LETTER_SMALL_YA L"\u3083" #define UNICODE_HIRAGANA_LETTER_YA 0x3084 #define UNITEXT_HIRAGANA_LETTER_YA L"\u3084" #define UNICODE_HIRAGANA_LETTER_SMALL_YU 0x3085 #define UNITEXT_HIRAGANA_LETTER_SMALL_YU L"\u3085" #define UNICODE_HIRAGANA_LETTER_YU 0x3086 #define UNITEXT_HIRAGANA_LETTER_YU L"\u3086" #define UNICODE_HIRAGANA_LETTER_SMALL_YO 0x3087 #define UNITEXT_HIRAGANA_LETTER_SMALL_YO L"\u3087" #define UNICODE_HIRAGANA_LETTER_YO 0x3088 #define UNITEXT_HIRAGANA_LETTER_YO L"\u3088" #define UNICODE_HIRAGANA_LETTER_RA 0x3089 #define UNITEXT_HIRAGANA_LETTER_RA L"\u3089" #define UNICODE_HIRAGANA_LETTER_RI 0x308a #define UNITEXT_HIRAGANA_LETTER_RI L"\u308a" #define UNICODE_HIRAGANA_LETTER_RU 0x308b #define UNITEXT_HIRAGANA_LETTER_RU L"\u308b" #define UNICODE_HIRAGANA_LETTER_RE 0x308c #define UNITEXT_HIRAGANA_LETTER_RE L"\u308c" #define UNICODE_HIRAGANA_LETTER_RO 0x308d #define UNITEXT_HIRAGANA_LETTER_RO L"\u308d" #define UNICODE_HIRAGANA_LETTER_SMALL_WA 0x308e #define UNITEXT_HIRAGANA_LETTER_SMALL_WA L"\u308e" #define UNICODE_HIRAGANA_LETTER_WA 0x308f #define UNITEXT_HIRAGANA_LETTER_WA L"\u308f" #define UNICODE_HIRAGANA_LETTER_WI 0x3090 #define UNITEXT_HIRAGANA_LETTER_WI L"\u3090" #define UNICODE_HIRAGANA_LETTER_WE 0x3091 #define UNITEXT_HIRAGANA_LETTER_WE L"\u3091" #define UNICODE_HIRAGANA_LETTER_WO 0x3092 #define UNITEXT_HIRAGANA_LETTER_WO L"\u3092" #define UNICODE_HIRAGANA_LETTER_N 0x3093 #define UNITEXT_HIRAGANA_LETTER_N L"\u3093" #define UNICODE_HIRAGANA_LETTER_VU 0x3094 #define UNITEXT_HIRAGANA_LETTER_VU L"\u3094" #define UNICODE_HIRAGANA_LETTER_SMALL_KA 0x3095 #define UNITEXT_HIRAGANA_LETTER_SMALL_KA L"\u3095" #define UNICODE_HIRAGANA_LETTER_SMALL_KE 0x3096 #define UNITEXT_HIRAGANA_LETTER_SMALL_KE L"\u3096" #define UNICODE_COMBINING_KATAKANA_HIRAGANA_VOICED_SOUND_MARK 0x3099 #define UNITEXT_COMBINING_KATAKANA_HIRAGANA_VOICED_SOUND_MARK L"\u3099" #define UNICODE_COMBINING_KATAKANA_HIRAGANA_SEMI_VOICED_SOUND_MARK 0x309a #define UNITEXT_COMBINING_KATAKANA_HIRAGANA_SEMI_VOICED_SOUND_MARK L"\u309a" #define UNICODE_KATAKANA_HIRAGANA_VOICED_SOUND_MARK 0x309b #define UNITEXT_KATAKANA_HIRAGANA_VOICED_SOUND_MARK L"\u309b" #define UNICODE_KATAKANA_HIRAGANA_SEMI_VOICED_SOUND_MARK 0x309c #define UNITEXT_KATAKANA_HIRAGANA_SEMI_VOICED_SOUND_MARK L"\u309c" #define UNICODE_HIRAGANA_ITERATION_MARK 0x309d #define UNITEXT_HIRAGANA_ITERATION_MARK L"\u309d" #define UNICODE_HIRAGANA_VOICED_ITERATION_MARK 0x309e #define UNITEXT_HIRAGANA_VOICED_ITERATION_MARK L"\u309e" #define UNICODE_HIRAGANA_DIGRAPH_YORI 0x309f #define UNITEXT_HIRAGANA_DIGRAPH_YORI L"\u309f" #define UNICODE_KATAKANA_HIRAGANA_DOUBLE_HYPHEN 0x30a0 #define UNITEXT_KATAKANA_HIRAGANA_DOUBLE_HYPHEN L"\u30a0" #define UNICODE_KATAKANA_LETTER_SMALL_A 0x30a1 #define UNITEXT_KATAKANA_LETTER_SMALL_A L"\u30a1" #define UNICODE_KATAKANA_LETTER_A 0x30a2 #define UNITEXT_KATAKANA_LETTER_A L"\u30a2" #define UNICODE_KATAKANA_LETTER_SMALL_I 0x30a3 #define UNITEXT_KATAKANA_LETTER_SMALL_I L"\u30a3" #define UNICODE_KATAKANA_LETTER_I 0x30a4 #define UNITEXT_KATAKANA_LETTER_I L"\u30a4" #define UNICODE_KATAKANA_LETTER_SMALL_U 0x30a5 #define UNITEXT_KATAKANA_LETTER_SMALL_U L"\u30a5" #define UNICODE_KATAKANA_LETTER_U 0x30a6 #define UNITEXT_KATAKANA_LETTER_U L"\u30a6" #define UNICODE_KATAKANA_LETTER_SMALL_E 0x30a7 #define UNITEXT_KATAKANA_LETTER_SMALL_E L"\u30a7" #define UNICODE_KATAKANA_LETTER_E 0x30a8 #define UNITEXT_KATAKANA_LETTER_E L"\u30a8" #define UNICODE_KATAKANA_LETTER_SMALL_O 0x30a9 #define UNITEXT_KATAKANA_LETTER_SMALL_O L"\u30a9" #define UNICODE_KATAKANA_LETTER_O 0x30aa #define UNITEXT_KATAKANA_LETTER_O L"\u30aa" #define UNICODE_KATAKANA_LETTER_KA 0x30ab #define UNITEXT_KATAKANA_LETTER_KA L"\u30ab" #define UNICODE_KATAKANA_LETTER_GA 0x30ac #define UNITEXT_KATAKANA_LETTER_GA L"\u30ac" #define UNICODE_KATAKANA_LETTER_KI 0x30ad #define UNITEXT_KATAKANA_LETTER_KI L"\u30ad" #define UNICODE_KATAKANA_LETTER_GI 0x30ae #define UNITEXT_KATAKANA_LETTER_GI L"\u30ae" #define UNICODE_KATAKANA_LETTER_KU 0x30af #define UNITEXT_KATAKANA_LETTER_KU L"\u30af" #define UNICODE_KATAKANA_LETTER_GU 0x30b0 #define UNITEXT_KATAKANA_LETTER_GU L"\u30b0" #define UNICODE_KATAKANA_LETTER_KE 0x30b1 #define UNITEXT_KATAKANA_LETTER_KE L"\u30b1" #define UNICODE_KATAKANA_LETTER_GE 0x30b2 #define UNITEXT_KATAKANA_LETTER_GE L"\u30b2" #define UNICODE_KATAKANA_LETTER_KO 0x30b3 #define UNITEXT_KATAKANA_LETTER_KO L"\u30b3" #define UNICODE_KATAKANA_LETTER_GO 0x30b4 #define UNITEXT_KATAKANA_LETTER_GO L"\u30b4" #define UNICODE_KATAKANA_LETTER_SA 0x30b5 #define UNITEXT_KATAKANA_LETTER_SA L"\u30b5" #define UNICODE_KATAKANA_LETTER_ZA 0x30b6 #define UNITEXT_KATAKANA_LETTER_ZA L"\u30b6" #define UNICODE_KATAKANA_LETTER_SI 0x30b7 #define UNITEXT_KATAKANA_LETTER_SI L"\u30b7" #define UNICODE_KATAKANA_LETTER_ZI 0x30b8 #define UNITEXT_KATAKANA_LETTER_ZI L"\u30b8" #define UNICODE_KATAKANA_LETTER_SU 0x30b9 #define UNITEXT_KATAKANA_LETTER_SU L"\u30b9" #define UNICODE_KATAKANA_LETTER_ZU 0x30ba #define UNITEXT_KATAKANA_LETTER_ZU L"\u30ba" #define UNICODE_KATAKANA_LETTER_SE 0x30bb #define UNITEXT_KATAKANA_LETTER_SE L"\u30bb" #define UNICODE_KATAKANA_LETTER_ZE 0x30bc #define UNITEXT_KATAKANA_LETTER_ZE L"\u30bc" #define UNICODE_KATAKANA_LETTER_SO 0x30bd #define UNITEXT_KATAKANA_LETTER_SO L"\u30bd" #define UNICODE_KATAKANA_LETTER_ZO 0x30be #define UNITEXT_KATAKANA_LETTER_ZO L"\u30be" #define UNICODE_KATAKANA_LETTER_TA 0x30bf #define UNITEXT_KATAKANA_LETTER_TA L"\u30bf" #define UNICODE_KATAKANA_LETTER_DA 0x30c0 #define UNITEXT_KATAKANA_LETTER_DA L"\u30c0" #define UNICODE_KATAKANA_LETTER_TI 0x30c1 #define UNITEXT_KATAKANA_LETTER_TI L"\u30c1" #define UNICODE_KATAKANA_LETTER_DI 0x30c2 #define UNITEXT_KATAKANA_LETTER_DI L"\u30c2" #define UNICODE_KATAKANA_LETTER_SMALL_TU 0x30c3 #define UNITEXT_KATAKANA_LETTER_SMALL_TU L"\u30c3" #define UNICODE_KATAKANA_LETTER_TU 0x30c4 #define UNITEXT_KATAKANA_LETTER_TU L"\u30c4" #define UNICODE_KATAKANA_LETTER_DU 0x30c5 #define UNITEXT_KATAKANA_LETTER_DU L"\u30c5" #define UNICODE_KATAKANA_LETTER_TE 0x30c6 #define UNITEXT_KATAKANA_LETTER_TE L"\u30c6" #define UNICODE_KATAKANA_LETTER_DE 0x30c7 #define UNITEXT_KATAKANA_LETTER_DE L"\u30c7" #define UNICODE_KATAKANA_LETTER_TO 0x30c8 #define UNITEXT_KATAKANA_LETTER_TO L"\u30c8" #define UNICODE_KATAKANA_LETTER_DO 0x30c9 #define UNITEXT_KATAKANA_LETTER_DO L"\u30c9" #define UNICODE_KATAKANA_LETTER_NA 0x30ca #define UNITEXT_KATAKANA_LETTER_NA L"\u30ca" #define UNICODE_KATAKANA_LETTER_NI 0x30cb #define UNITEXT_KATAKANA_LETTER_NI L"\u30cb" #define UNICODE_KATAKANA_LETTER_NU 0x30cc #define UNITEXT_KATAKANA_LETTER_NU L"\u30cc" #define UNICODE_KATAKANA_LETTER_NE 0x30cd #define UNITEXT_KATAKANA_LETTER_NE L"\u30cd" #define UNICODE_KATAKANA_LETTER_NO 0x30ce #define UNITEXT_KATAKANA_LETTER_NO L"\u30ce" #define UNICODE_KATAKANA_LETTER_HA 0x30cf #define UNITEXT_KATAKANA_LETTER_HA L"\u30cf" #define UNICODE_KATAKANA_LETTER_BA 0x30d0 #define UNITEXT_KATAKANA_LETTER_BA L"\u30d0" #define UNICODE_KATAKANA_LETTER_PA 0x30d1 #define UNITEXT_KATAKANA_LETTER_PA L"\u30d1" #define UNICODE_KATAKANA_LETTER_HI 0x30d2 #define UNITEXT_KATAKANA_LETTER_HI L"\u30d2" #define UNICODE_KATAKANA_LETTER_BI 0x30d3 #define UNITEXT_KATAKANA_LETTER_BI L"\u30d3" #define UNICODE_KATAKANA_LETTER_PI 0x30d4 #define UNITEXT_KATAKANA_LETTER_PI L"\u30d4" #define UNICODE_KATAKANA_LETTER_HU 0x30d5 #define UNITEXT_KATAKANA_LETTER_HU L"\u30d5" #define UNICODE_KATAKANA_LETTER_BU 0x30d6 #define UNITEXT_KATAKANA_LETTER_BU L"\u30d6" #define UNICODE_KATAKANA_LETTER_PU 0x30d7 #define UNITEXT_KATAKANA_LETTER_PU L"\u30d7" #define UNICODE_KATAKANA_LETTER_HE 0x30d8 #define UNITEXT_KATAKANA_LETTER_HE L"\u30d8" #define UNICODE_KATAKANA_LETTER_BE 0x30d9 #define UNITEXT_KATAKANA_LETTER_BE L"\u30d9" #define UNICODE_KATAKANA_LETTER_PE 0x30da #define UNITEXT_KATAKANA_LETTER_PE L"\u30da" #define UNICODE_KATAKANA_LETTER_HO 0x30db #define UNITEXT_KATAKANA_LETTER_HO L"\u30db" #define UNICODE_KATAKANA_LETTER_BO 0x30dc #define UNITEXT_KATAKANA_LETTER_BO L"\u30dc" #define UNICODE_KATAKANA_LETTER_PO 0x30dd #define UNITEXT_KATAKANA_LETTER_PO L"\u30dd" #define UNICODE_KATAKANA_LETTER_MA 0x30de #define UNITEXT_KATAKANA_LETTER_MA L"\u30de" #define UNICODE_KATAKANA_LETTER_MI 0x30df #define UNITEXT_KATAKANA_LETTER_MI L"\u30df" #define UNICODE_KATAKANA_LETTER_MU 0x30e0 #define UNITEXT_KATAKANA_LETTER_MU L"\u30e0" #define UNICODE_KATAKANA_LETTER_ME 0x30e1 #define UNITEXT_KATAKANA_LETTER_ME L"\u30e1" #define UNICODE_KATAKANA_LETTER_MO 0x30e2 #define UNITEXT_KATAKANA_LETTER_MO L"\u30e2" #define UNICODE_KATAKANA_LETTER_SMALL_YA 0x30e3 #define UNITEXT_KATAKANA_LETTER_SMALL_YA L"\u30e3" #define UNICODE_KATAKANA_LETTER_YA 0x30e4 #define UNITEXT_KATAKANA_LETTER_YA L"\u30e4" #define UNICODE_KATAKANA_LETTER_SMALL_YU 0x30e5 #define UNITEXT_KATAKANA_LETTER_SMALL_YU L"\u30e5" #define UNICODE_KATAKANA_LETTER_YU 0x30e6 #define UNITEXT_KATAKANA_LETTER_YU L"\u30e6" #define UNICODE_KATAKANA_LETTER_SMALL_YO 0x30e7 #define UNITEXT_KATAKANA_LETTER_SMALL_YO L"\u30e7" #define UNICODE_KATAKANA_LETTER_YO 0x30e8 #define UNITEXT_KATAKANA_LETTER_YO L"\u30e8" #define UNICODE_KATAKANA_LETTER_RA 0x30e9 #define UNITEXT_KATAKANA_LETTER_RA L"\u30e9" #define UNICODE_KATAKANA_LETTER_RI 0x30ea #define UNITEXT_KATAKANA_LETTER_RI L"\u30ea" #define UNICODE_KATAKANA_LETTER_RU 0x30eb #define UNITEXT_KATAKANA_LETTER_RU L"\u30eb" #define UNICODE_KATAKANA_LETTER_RE 0x30ec #define UNITEXT_KATAKANA_LETTER_RE L"\u30ec" #define UNICODE_KATAKANA_LETTER_RO 0x30ed #define UNITEXT_KATAKANA_LETTER_RO L"\u30ed" #define UNICODE_KATAKANA_LETTER_SMALL_WA 0x30ee #define UNITEXT_KATAKANA_LETTER_SMALL_WA L"\u30ee" #define UNICODE_KATAKANA_LETTER_WA 0x30ef #define UNITEXT_KATAKANA_LETTER_WA L"\u30ef" #define UNICODE_KATAKANA_LETTER_WI 0x30f0 #define UNITEXT_KATAKANA_LETTER_WI L"\u30f0" #define UNICODE_KATAKANA_LETTER_WE 0x30f1 #define UNITEXT_KATAKANA_LETTER_WE L"\u30f1" #define UNICODE_KATAKANA_LETTER_WO 0x30f2 #define UNITEXT_KATAKANA_LETTER_WO L"\u30f2" #define UNICODE_KATAKANA_LETTER_N 0x30f3 #define UNITEXT_KATAKANA_LETTER_N L"\u30f3" #define UNICODE_KATAKANA_LETTER_VU 0x30f4 #define UNITEXT_KATAKANA_LETTER_VU L"\u30f4" #define UNICODE_KATAKANA_LETTER_SMALL_KA 0x30f5 #define UNITEXT_KATAKANA_LETTER_SMALL_KA L"\u30f5" #define UNICODE_KATAKANA_LETTER_SMALL_KE 0x30f6 #define UNITEXT_KATAKANA_LETTER_SMALL_KE L"\u30f6" #define UNICODE_KATAKANA_LETTER_VA 0x30f7 #define UNITEXT_KATAKANA_LETTER_VA L"\u30f7" #define UNICODE_KATAKANA_LETTER_VI 0x30f8 #define UNITEXT_KATAKANA_LETTER_VI L"\u30f8" #define UNICODE_KATAKANA_LETTER_VE 0x30f9 #define UNITEXT_KATAKANA_LETTER_VE L"\u30f9" #define UNICODE_KATAKANA_LETTER_VO 0x30fa #define UNITEXT_KATAKANA_LETTER_VO L"\u30fa" #define UNICODE_KATAKANA_MIDDLE_DOT 0x30fb #define UNITEXT_KATAKANA_MIDDLE_DOT L"\u30fb" #define UNICODE_KATAKANA_HIRAGANA_PROLONGED_SOUND_MARK 0x30fc #define UNITEXT_KATAKANA_HIRAGANA_PROLONGED_SOUND_MARK L"\u30fc" #define UNICODE_KATAKANA_ITERATION_MARK 0x30fd #define UNITEXT_KATAKANA_ITERATION_MARK L"\u30fd" #define UNICODE_KATAKANA_VOICED_ITERATION_MARK 0x30fe #define UNITEXT_KATAKANA_VOICED_ITERATION_MARK L"\u30fe" #define UNICODE_KATAKANA_DIGRAPH_KOTO 0x30ff #define UNITEXT_KATAKANA_DIGRAPH_KOTO L"\u30ff" #define UNICODE_BOPOMOFO_LETTER_B 0x3105 #define UNITEXT_BOPOMOFO_LETTER_B L"\u3105" #define UNICODE_BOPOMOFO_LETTER_P 0x3106 #define UNITEXT_BOPOMOFO_LETTER_P L"\u3106" #define UNICODE_BOPOMOFO_LETTER_M 0x3107 #define UNITEXT_BOPOMOFO_LETTER_M L"\u3107" #define UNICODE_BOPOMOFO_LETTER_F 0x3108 #define UNITEXT_BOPOMOFO_LETTER_F L"\u3108" #define UNICODE_BOPOMOFO_LETTER_D 0x3109 #define UNITEXT_BOPOMOFO_LETTER_D L"\u3109" #define UNICODE_BOPOMOFO_LETTER_T 0x310a #define UNITEXT_BOPOMOFO_LETTER_T L"\u310a" #define UNICODE_BOPOMOFO_LETTER_N 0x310b #define UNITEXT_BOPOMOFO_LETTER_N L"\u310b" #define UNICODE_BOPOMOFO_LETTER_L 0x310c #define UNITEXT_BOPOMOFO_LETTER_L L"\u310c" #define UNICODE_BOPOMOFO_LETTER_G 0x310d #define UNITEXT_BOPOMOFO_LETTER_G L"\u310d" #define UNICODE_BOPOMOFO_LETTER_K 0x310e #define UNITEXT_BOPOMOFO_LETTER_K L"\u310e" #define UNICODE_BOPOMOFO_LETTER_H 0x310f #define UNITEXT_BOPOMOFO_LETTER_H L"\u310f" #define UNICODE_BOPOMOFO_LETTER_J 0x3110 #define UNITEXT_BOPOMOFO_LETTER_J L"\u3110" #define UNICODE_BOPOMOFO_LETTER_Q 0x3111 #define UNITEXT_BOPOMOFO_LETTER_Q L"\u3111" #define UNICODE_BOPOMOFO_LETTER_X 0x3112 #define UNITEXT_BOPOMOFO_LETTER_X L"\u3112" #define UNICODE_BOPOMOFO_LETTER_ZH 0x3113 #define UNITEXT_BOPOMOFO_LETTER_ZH L"\u3113" #define UNICODE_BOPOMOFO_LETTER_CH 0x3114 #define UNITEXT_BOPOMOFO_LETTER_CH L"\u3114" #define UNICODE_BOPOMOFO_LETTER_SH 0x3115 #define UNITEXT_BOPOMOFO_LETTER_SH L"\u3115" #define UNICODE_BOPOMOFO_LETTER_R 0x3116 #define UNITEXT_BOPOMOFO_LETTER_R L"\u3116" #define UNICODE_BOPOMOFO_LETTER_Z 0x3117 #define UNITEXT_BOPOMOFO_LETTER_Z L"\u3117" #define UNICODE_BOPOMOFO_LETTER_C 0x3118 #define UNITEXT_BOPOMOFO_LETTER_C L"\u3118" #define UNICODE_BOPOMOFO_LETTER_S 0x3119 #define UNITEXT_BOPOMOFO_LETTER_S L"\u3119" #define UNICODE_BOPOMOFO_LETTER_A 0x311a #define UNITEXT_BOPOMOFO_LETTER_A L"\u311a" #define UNICODE_BOPOMOFO_LETTER_O 0x311b #define UNITEXT_BOPOMOFO_LETTER_O L"\u311b" #define UNICODE_BOPOMOFO_LETTER_E 0x311c #define UNITEXT_BOPOMOFO_LETTER_E L"\u311c" #define UNICODE_BOPOMOFO_LETTER_EH 0x311d #define UNITEXT_BOPOMOFO_LETTER_EH L"\u311d" #define UNICODE_BOPOMOFO_LETTER_AI 0x311e #define UNITEXT_BOPOMOFO_LETTER_AI L"\u311e" #define UNICODE_BOPOMOFO_LETTER_EI 0x311f #define UNITEXT_BOPOMOFO_LETTER_EI L"\u311f" #define UNICODE_BOPOMOFO_LETTER_AU 0x3120 #define UNITEXT_BOPOMOFO_LETTER_AU L"\u3120" #define UNICODE_BOPOMOFO_LETTER_OU 0x3121 #define UNITEXT_BOPOMOFO_LETTER_OU L"\u3121" #define UNICODE_BOPOMOFO_LETTER_AN 0x3122 #define UNITEXT_BOPOMOFO_LETTER_AN L"\u3122" #define UNICODE_BOPOMOFO_LETTER_EN 0x3123 #define UNITEXT_BOPOMOFO_LETTER_EN L"\u3123" #define UNICODE_BOPOMOFO_LETTER_ANG 0x3124 #define UNITEXT_BOPOMOFO_LETTER_ANG L"\u3124" #define UNICODE_BOPOMOFO_LETTER_ENG 0x3125 #define UNITEXT_BOPOMOFO_LETTER_ENG L"\u3125" #define UNICODE_BOPOMOFO_LETTER_ER 0x3126 #define UNITEXT_BOPOMOFO_LETTER_ER L"\u3126" #define UNICODE_BOPOMOFO_LETTER_I 0x3127 #define UNITEXT_BOPOMOFO_LETTER_I L"\u3127" #define UNICODE_BOPOMOFO_LETTER_U 0x3128 #define UNITEXT_BOPOMOFO_LETTER_U L"\u3128" #define UNICODE_BOPOMOFO_LETTER_IU 0x3129 #define UNITEXT_BOPOMOFO_LETTER_IU L"\u3129" #define UNICODE_BOPOMOFO_LETTER_V 0x312a #define UNITEXT_BOPOMOFO_LETTER_V L"\u312a" #define UNICODE_BOPOMOFO_LETTER_NG 0x312b #define UNITEXT_BOPOMOFO_LETTER_NG L"\u312b" #define UNICODE_BOPOMOFO_LETTER_GN 0x312c #define UNITEXT_BOPOMOFO_LETTER_GN L"\u312c" #define UNICODE_HANGUL_LETTER_KIYEOK 0x3131 #define UNITEXT_HANGUL_LETTER_KIYEOK L"\u3131" #define UNICODE_HANGUL_LETTER_SSANGKIYEOK 0x3132 #define UNITEXT_HANGUL_LETTER_SSANGKIYEOK L"\u3132" #define UNICODE_HANGUL_LETTER_KIYEOK_SIOS 0x3133 #define UNITEXT_HANGUL_LETTER_KIYEOK_SIOS L"\u3133" #define UNICODE_HANGUL_LETTER_NIEUN 0x3134 #define UNITEXT_HANGUL_LETTER_NIEUN L"\u3134" #define UNICODE_HANGUL_LETTER_NIEUN_CIEUC 0x3135 #define UNITEXT_HANGUL_LETTER_NIEUN_CIEUC L"\u3135" #define UNICODE_HANGUL_LETTER_NIEUN_HIEUH 0x3136 #define UNITEXT_HANGUL_LETTER_NIEUN_HIEUH L"\u3136" #define UNICODE_HANGUL_LETTER_TIKEUT 0x3137 #define UNITEXT_HANGUL_LETTER_TIKEUT L"\u3137" #define UNICODE_HANGUL_LETTER_SSANGTIKEUT 0x3138 #define UNITEXT_HANGUL_LETTER_SSANGTIKEUT L"\u3138" #define UNICODE_HANGUL_LETTER_RIEUL 0x3139 #define UNITEXT_HANGUL_LETTER_RIEUL L"\u3139" #define UNICODE_HANGUL_LETTER_RIEUL_KIYEOK 0x313a #define UNITEXT_HANGUL_LETTER_RIEUL_KIYEOK L"\u313a" #define UNICODE_HANGUL_LETTER_RIEUL_MIEUM 0x313b #define UNITEXT_HANGUL_LETTER_RIEUL_MIEUM L"\u313b" #define UNICODE_HANGUL_LETTER_RIEUL_PIEUP 0x313c #define UNITEXT_HANGUL_LETTER_RIEUL_PIEUP L"\u313c" #define UNICODE_HANGUL_LETTER_RIEUL_SIOS 0x313d #define UNITEXT_HANGUL_LETTER_RIEUL_SIOS L"\u313d" #define UNICODE_HANGUL_LETTER_RIEUL_THIEUTH 0x313e #define UNITEXT_HANGUL_LETTER_RIEUL_THIEUTH L"\u313e" #define UNICODE_HANGUL_LETTER_RIEUL_PHIEUPH 0x313f #define UNITEXT_HANGUL_LETTER_RIEUL_PHIEUPH L"\u313f" #define UNICODE_HANGUL_LETTER_RIEUL_HIEUH 0x3140 #define UNITEXT_HANGUL_LETTER_RIEUL_HIEUH L"\u3140" #define UNICODE_HANGUL_LETTER_MIEUM 0x3141 #define UNITEXT_HANGUL_LETTER_MIEUM L"\u3141" #define UNICODE_HANGUL_LETTER_PIEUP 0x3142 #define UNITEXT_HANGUL_LETTER_PIEUP L"\u3142" #define UNICODE_HANGUL_LETTER_SSANGPIEUP 0x3143 #define UNITEXT_HANGUL_LETTER_SSANGPIEUP L"\u3143" #define UNICODE_HANGUL_LETTER_PIEUP_SIOS 0x3144 #define UNITEXT_HANGUL_LETTER_PIEUP_SIOS L"\u3144" #define UNICODE_HANGUL_LETTER_SIOS 0x3145 #define UNITEXT_HANGUL_LETTER_SIOS L"\u3145" #define UNICODE_HANGUL_LETTER_SSANGSIOS 0x3146 #define UNITEXT_HANGUL_LETTER_SSANGSIOS L"\u3146" #define UNICODE_HANGUL_LETTER_IEUNG 0x3147 #define UNITEXT_HANGUL_LETTER_IEUNG L"\u3147" #define UNICODE_HANGUL_LETTER_CIEUC 0x3148 #define UNITEXT_HANGUL_LETTER_CIEUC L"\u3148" #define UNICODE_HANGUL_LETTER_SSANGCIEUC 0x3149 #define UNITEXT_HANGUL_LETTER_SSANGCIEUC L"\u3149" #define UNICODE_HANGUL_LETTER_CHIEUCH 0x314a #define UNITEXT_HANGUL_LETTER_CHIEUCH L"\u314a" #define UNICODE_HANGUL_LETTER_KHIEUKH 0x314b #define UNITEXT_HANGUL_LETTER_KHIEUKH L"\u314b" #define UNICODE_HANGUL_LETTER_THIEUTH 0x314c #define UNITEXT_HANGUL_LETTER_THIEUTH L"\u314c" #define UNICODE_HANGUL_LETTER_PHIEUPH 0x314d #define UNITEXT_HANGUL_LETTER_PHIEUPH L"\u314d" #define UNICODE_HANGUL_LETTER_HIEUH 0x314e #define UNITEXT_HANGUL_LETTER_HIEUH L"\u314e" #define UNICODE_HANGUL_LETTER_A 0x314f #define UNITEXT_HANGUL_LETTER_A L"\u314f" #define UNICODE_HANGUL_LETTER_AE 0x3150 #define UNITEXT_HANGUL_LETTER_AE L"\u3150" #define UNICODE_HANGUL_LETTER_YA 0x3151 #define UNITEXT_HANGUL_LETTER_YA L"\u3151" #define UNICODE_HANGUL_LETTER_YAE 0x3152 #define UNITEXT_HANGUL_LETTER_YAE L"\u3152" #define UNICODE_HANGUL_LETTER_EO 0x3153 #define UNITEXT_HANGUL_LETTER_EO L"\u3153" #define UNICODE_HANGUL_LETTER_E 0x3154 #define UNITEXT_HANGUL_LETTER_E L"\u3154" #define UNICODE_HANGUL_LETTER_YEO 0x3155 #define UNITEXT_HANGUL_LETTER_YEO L"\u3155" #define UNICODE_HANGUL_LETTER_YE 0x3156 #define UNITEXT_HANGUL_LETTER_YE L"\u3156" #define UNICODE_HANGUL_LETTER_O 0x3157 #define UNITEXT_HANGUL_LETTER_O L"\u3157" #define UNICODE_HANGUL_LETTER_WA 0x3158 #define UNITEXT_HANGUL_LETTER_WA L"\u3158" #define UNICODE_HANGUL_LETTER_WAE 0x3159 #define UNITEXT_HANGUL_LETTER_WAE L"\u3159" #define UNICODE_HANGUL_LETTER_OE 0x315a #define UNITEXT_HANGUL_LETTER_OE L"\u315a" #define UNICODE_HANGUL_LETTER_YO 0x315b #define UNITEXT_HANGUL_LETTER_YO L"\u315b" #define UNICODE_HANGUL_LETTER_U 0x315c #define UNITEXT_HANGUL_LETTER_U L"\u315c" #define UNICODE_HANGUL_LETTER_WEO 0x315d #define UNITEXT_HANGUL_LETTER_WEO L"\u315d" #define UNICODE_HANGUL_LETTER_WE 0x315e #define UNITEXT_HANGUL_LETTER_WE L"\u315e" #define UNICODE_HANGUL_LETTER_WI 0x315f #define UNITEXT_HANGUL_LETTER_WI L"\u315f" #define UNICODE_HANGUL_LETTER_YU 0x3160 #define UNITEXT_HANGUL_LETTER_YU L"\u3160" #define UNICODE_HANGUL_LETTER_EU 0x3161 #define UNITEXT_HANGUL_LETTER_EU L"\u3161" #define UNICODE_HANGUL_LETTER_YI 0x3162 #define UNITEXT_HANGUL_LETTER_YI L"\u3162" #define UNICODE_HANGUL_LETTER_I 0x3163 #define UNITEXT_HANGUL_LETTER_I L"\u3163" #define UNICODE_HANGUL_FILLER 0x3164 #define UNITEXT_HANGUL_FILLER L"\u3164" #define UNICODE_HANGUL_LETTER_SSANGNIEUN 0x3165 #define UNITEXT_HANGUL_LETTER_SSANGNIEUN L"\u3165" #define UNICODE_HANGUL_LETTER_NIEUN_TIKEUT 0x3166 #define UNITEXT_HANGUL_LETTER_NIEUN_TIKEUT L"\u3166" #define UNICODE_HANGUL_LETTER_NIEUN_SIOS 0x3167 #define UNITEXT_HANGUL_LETTER_NIEUN_SIOS L"\u3167" #define UNICODE_HANGUL_LETTER_NIEUN_PANSIOS 0x3168 #define UNITEXT_HANGUL_LETTER_NIEUN_PANSIOS L"\u3168" #define UNICODE_HANGUL_LETTER_RIEUL_KIYEOK_SIOS 0x3169 #define UNITEXT_HANGUL_LETTER_RIEUL_KIYEOK_SIOS L"\u3169" #define UNICODE_HANGUL_LETTER_RIEUL_TIKEUT 0x316a #define UNITEXT_HANGUL_LETTER_RIEUL_TIKEUT L"\u316a" #define UNICODE_HANGUL_LETTER_RIEUL_PIEUP_SIOS 0x316b #define UNITEXT_HANGUL_LETTER_RIEUL_PIEUP_SIOS L"\u316b" #define UNICODE_HANGUL_LETTER_RIEUL_PANSIOS 0x316c #define UNITEXT_HANGUL_LETTER_RIEUL_PANSIOS L"\u316c" #define UNICODE_HANGUL_LETTER_RIEUL_YEORINHIEUH 0x316d #define UNITEXT_HANGUL_LETTER_RIEUL_YEORINHIEUH L"\u316d" #define UNICODE_HANGUL_LETTER_MIEUM_PIEUP 0x316e #define UNITEXT_HANGUL_LETTER_MIEUM_PIEUP L"\u316e" #define UNICODE_HANGUL_LETTER_MIEUM_SIOS 0x316f #define UNITEXT_HANGUL_LETTER_MIEUM_SIOS L"\u316f" #define UNICODE_HANGUL_LETTER_MIEUM_PANSIOS 0x3170 #define UNITEXT_HANGUL_LETTER_MIEUM_PANSIOS L"\u3170" #define UNICODE_HANGUL_LETTER_KAPYEOUNMIEUM 0x3171 #define UNITEXT_HANGUL_LETTER_KAPYEOUNMIEUM L"\u3171" #define UNICODE_HANGUL_LETTER_PIEUP_KIYEOK 0x3172 #define UNITEXT_HANGUL_LETTER_PIEUP_KIYEOK L"\u3172" #define UNICODE_HANGUL_LETTER_PIEUP_TIKEUT 0x3173 #define UNITEXT_HANGUL_LETTER_PIEUP_TIKEUT L"\u3173" #define UNICODE_HANGUL_LETTER_PIEUP_SIOS_KIYEOK 0x3174 #define UNITEXT_HANGUL_LETTER_PIEUP_SIOS_KIYEOK L"\u3174" #define UNICODE_HANGUL_LETTER_PIEUP_SIOS_TIKEUT 0x3175 #define UNITEXT_HANGUL_LETTER_PIEUP_SIOS_TIKEUT L"\u3175" #define UNICODE_HANGUL_LETTER_PIEUP_CIEUC 0x3176 #define UNITEXT_HANGUL_LETTER_PIEUP_CIEUC L"\u3176" #define UNICODE_HANGUL_LETTER_PIEUP_THIEUTH 0x3177 #define UNITEXT_HANGUL_LETTER_PIEUP_THIEUTH L"\u3177" #define UNICODE_HANGUL_LETTER_KAPYEOUNPIEUP 0x3178 #define UNITEXT_HANGUL_LETTER_KAPYEOUNPIEUP L"\u3178" #define UNICODE_HANGUL_LETTER_KAPYEOUNSSANGPIEUP 0x3179 #define UNITEXT_HANGUL_LETTER_KAPYEOUNSSANGPIEUP L"\u3179" #define UNICODE_HANGUL_LETTER_SIOS_KIYEOK 0x317a #define UNITEXT_HANGUL_LETTER_SIOS_KIYEOK L"\u317a" #define UNICODE_HANGUL_LETTER_SIOS_NIEUN 0x317b #define UNITEXT_HANGUL_LETTER_SIOS_NIEUN L"\u317b" #define UNICODE_HANGUL_LETTER_SIOS_TIKEUT 0x317c #define UNITEXT_HANGUL_LETTER_SIOS_TIKEUT L"\u317c" #define UNICODE_HANGUL_LETTER_SIOS_PIEUP 0x317d #define UNITEXT_HANGUL_LETTER_SIOS_PIEUP L"\u317d" #define UNICODE_HANGUL_LETTER_SIOS_CIEUC 0x317e #define UNITEXT_HANGUL_LETTER_SIOS_CIEUC L"\u317e" #define UNICODE_HANGUL_LETTER_PANSIOS 0x317f #define UNITEXT_HANGUL_LETTER_PANSIOS L"\u317f" #define UNICODE_HANGUL_LETTER_SSANGIEUNG 0x3180 #define UNITEXT_HANGUL_LETTER_SSANGIEUNG L"\u3180" #define UNICODE_HANGUL_LETTER_YESIEUNG 0x3181 #define UNITEXT_HANGUL_LETTER_YESIEUNG L"\u3181" #define UNICODE_HANGUL_LETTER_YESIEUNG_SIOS 0x3182 #define UNITEXT_HANGUL_LETTER_YESIEUNG_SIOS L"\u3182" #define UNICODE_HANGUL_LETTER_YESIEUNG_PANSIOS 0x3183 #define UNITEXT_HANGUL_LETTER_YESIEUNG_PANSIOS L"\u3183" #define UNICODE_HANGUL_LETTER_KAPYEOUNPHIEUPH 0x3184 #define UNITEXT_HANGUL_LETTER_KAPYEOUNPHIEUPH L"\u3184" #define UNICODE_HANGUL_LETTER_SSANGHIEUH 0x3185 #define UNITEXT_HANGUL_LETTER_SSANGHIEUH L"\u3185" #define UNICODE_HANGUL_LETTER_YEORINHIEUH 0x3186 #define UNITEXT_HANGUL_LETTER_YEORINHIEUH L"\u3186" #define UNICODE_HANGUL_LETTER_YO_YA 0x3187 #define UNITEXT_HANGUL_LETTER_YO_YA L"\u3187" #define UNICODE_HANGUL_LETTER_YO_YAE 0x3188 #define UNITEXT_HANGUL_LETTER_YO_YAE L"\u3188" #define UNICODE_HANGUL_LETTER_YO_I 0x3189 #define UNITEXT_HANGUL_LETTER_YO_I L"\u3189" #define UNICODE_HANGUL_LETTER_YU_YEO 0x318a #define UNITEXT_HANGUL_LETTER_YU_YEO L"\u318a" #define UNICODE_HANGUL_LETTER_YU_YE 0x318b #define UNITEXT_HANGUL_LETTER_YU_YE L"\u318b" #define UNICODE_HANGUL_LETTER_YU_I 0x318c #define UNITEXT_HANGUL_LETTER_YU_I L"\u318c" #define UNICODE_HANGUL_LETTER_ARAEA 0x318d #define UNITEXT_HANGUL_LETTER_ARAEA L"\u318d" #define UNICODE_HANGUL_LETTER_ARAEAE 0x318e #define UNITEXT_HANGUL_LETTER_ARAEAE L"\u318e" #define UNICODE_IDEOGRAPHIC_ANNOTATION_LINKING_MARK 0x3190 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_LINKING_MARK L"\u3190" #define UNICODE_IDEOGRAPHIC_ANNOTATION_REVERSE_MARK 0x3191 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_REVERSE_MARK L"\u3191" #define UNICODE_IDEOGRAPHIC_ANNOTATION_ONE_MARK 0x3192 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_ONE_MARK L"\u3192" #define UNICODE_IDEOGRAPHIC_ANNOTATION_TWO_MARK 0x3193 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_TWO_MARK L"\u3193" #define UNICODE_IDEOGRAPHIC_ANNOTATION_THREE_MARK 0x3194 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_THREE_MARK L"\u3194" #define UNICODE_IDEOGRAPHIC_ANNOTATION_FOUR_MARK 0x3195 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_FOUR_MARK L"\u3195" #define UNICODE_IDEOGRAPHIC_ANNOTATION_TOP_MARK 0x3196 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_TOP_MARK L"\u3196" #define UNICODE_IDEOGRAPHIC_ANNOTATION_MIDDLE_MARK 0x3197 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_MIDDLE_MARK L"\u3197" #define UNICODE_IDEOGRAPHIC_ANNOTATION_BOTTOM_MARK 0x3198 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_BOTTOM_MARK L"\u3198" #define UNICODE_IDEOGRAPHIC_ANNOTATION_FIRST_MARK 0x3199 #define UNITEXT_IDEOGRAPHIC_ANNOTATION_FIRST_MARK L"\u3199" #define UNICODE_IDEOGRAPHIC_ANNOTATION_SECOND_MARK 0x319a #define UNITEXT_IDEOGRAPHIC_ANNOTATION_SECOND_MARK L"\u319a" #define UNICODE_IDEOGRAPHIC_ANNOTATION_THIRD_MARK 0x319b #define UNITEXT_IDEOGRAPHIC_ANNOTATION_THIRD_MARK L"\u319b" #define UNICODE_IDEOGRAPHIC_ANNOTATION_FOURTH_MARK 0x319c #define UNITEXT_IDEOGRAPHIC_ANNOTATION_FOURTH_MARK L"\u319c" #define UNICODE_IDEOGRAPHIC_ANNOTATION_HEAVEN_MARK 0x319d #define UNITEXT_IDEOGRAPHIC_ANNOTATION_HEAVEN_MARK L"\u319d" #define UNICODE_IDEOGRAPHIC_ANNOTATION_EARTH_MARK 0x319e #define UNITEXT_IDEOGRAPHIC_ANNOTATION_EARTH_MARK L"\u319e" #define UNICODE_IDEOGRAPHIC_ANNOTATION_MAN_MARK 0x319f #define UNITEXT_IDEOGRAPHIC_ANNOTATION_MAN_MARK L"\u319f" #define UNICODE_BOPOMOFO_LETTER_BU 0x31a0 #define UNITEXT_BOPOMOFO_LETTER_BU L"\u31a0" #define UNICODE_BOPOMOFO_LETTER_ZI 0x31a1 #define UNITEXT_BOPOMOFO_LETTER_ZI L"\u31a1" #define UNICODE_BOPOMOFO_LETTER_JI 0x31a2 #define UNITEXT_BOPOMOFO_LETTER_JI L"\u31a2" #define UNICODE_BOPOMOFO_LETTER_GU 0x31a3 #define UNITEXT_BOPOMOFO_LETTER_GU L"\u31a3" #define UNICODE_BOPOMOFO_LETTER_EE 0x31a4 #define UNITEXT_BOPOMOFO_LETTER_EE L"\u31a4" #define UNICODE_BOPOMOFO_LETTER_ENN 0x31a5 #define UNITEXT_BOPOMOFO_LETTER_ENN L"\u31a5" #define UNICODE_BOPOMOFO_LETTER_OO 0x31a6 #define UNITEXT_BOPOMOFO_LETTER_OO L"\u31a6" #define UNICODE_BOPOMOFO_LETTER_ONN 0x31a7 #define UNITEXT_BOPOMOFO_LETTER_ONN L"\u31a7" #define UNICODE_BOPOMOFO_LETTER_IR 0x31a8 #define UNITEXT_BOPOMOFO_LETTER_IR L"\u31a8" #define UNICODE_BOPOMOFO_LETTER_ANN 0x31a9 #define UNITEXT_BOPOMOFO_LETTER_ANN L"\u31a9" #define UNICODE_BOPOMOFO_LETTER_INN 0x31aa #define UNITEXT_BOPOMOFO_LETTER_INN L"\u31aa" #define UNICODE_BOPOMOFO_LETTER_UNN 0x31ab #define UNITEXT_BOPOMOFO_LETTER_UNN L"\u31ab" #define UNICODE_BOPOMOFO_LETTER_IM 0x31ac #define UNITEXT_BOPOMOFO_LETTER_IM L"\u31ac" #define UNICODE_BOPOMOFO_LETTER_NGG 0x31ad #define UNITEXT_BOPOMOFO_LETTER_NGG L"\u31ad" #define UNICODE_BOPOMOFO_LETTER_AINN 0x31ae #define UNITEXT_BOPOMOFO_LETTER_AINN L"\u31ae" #define UNICODE_BOPOMOFO_LETTER_AUNN 0x31af #define UNITEXT_BOPOMOFO_LETTER_AUNN L"\u31af" #define UNICODE_BOPOMOFO_LETTER_AM 0x31b0 #define UNITEXT_BOPOMOFO_LETTER_AM L"\u31b0" #define UNICODE_BOPOMOFO_LETTER_OM 0x31b1 #define UNITEXT_BOPOMOFO_LETTER_OM L"\u31b1" #define UNICODE_BOPOMOFO_LETTER_ONG 0x31b2 #define UNITEXT_BOPOMOFO_LETTER_ONG L"\u31b2" #define UNICODE_BOPOMOFO_LETTER_INNN 0x31b3 #define UNITEXT_BOPOMOFO_LETTER_INNN L"\u31b3" #define UNICODE_BOPOMOFO_FINAL_LETTER_P 0x31b4 #define UNITEXT_BOPOMOFO_FINAL_LETTER_P L"\u31b4" #define UNICODE_BOPOMOFO_FINAL_LETTER_T 0x31b5 #define UNITEXT_BOPOMOFO_FINAL_LETTER_T L"\u31b5" #define UNICODE_BOPOMOFO_FINAL_LETTER_K 0x31b6 #define UNITEXT_BOPOMOFO_FINAL_LETTER_K L"\u31b6" #define UNICODE_BOPOMOFO_FINAL_LETTER_H 0x31b7 #define UNITEXT_BOPOMOFO_FINAL_LETTER_H L"\u31b7" #define UNICODE_CJK_STROKE_T 0x31c0 #define UNITEXT_CJK_STROKE_T L"\u31c0" #define UNICODE_CJK_STROKE_WG 0x31c1 #define UNITEXT_CJK_STROKE_WG L"\u31c1" #define UNICODE_CJK_STROKE_XG 0x31c2 #define UNITEXT_CJK_STROKE_XG L"\u31c2" #define UNICODE_CJK_STROKE_BXG 0x31c3 #define UNITEXT_CJK_STROKE_BXG L"\u31c3" #define UNICODE_CJK_STROKE_SW 0x31c4 #define UNITEXT_CJK_STROKE_SW L"\u31c4" #define UNICODE_CJK_STROKE_HZZ 0x31c5 #define UNITEXT_CJK_STROKE_HZZ L"\u31c5" #define UNICODE_CJK_STROKE_HZG 0x31c6 #define UNITEXT_CJK_STROKE_HZG L"\u31c6" #define UNICODE_CJK_STROKE_HP 0x31c7 #define UNITEXT_CJK_STROKE_HP L"\u31c7" #define UNICODE_CJK_STROKE_HZWG 0x31c8 #define UNITEXT_CJK_STROKE_HZWG L"\u31c8" #define UNICODE_CJK_STROKE_SZWG 0x31c9 #define UNITEXT_CJK_STROKE_SZWG L"\u31c9" #define UNICODE_CJK_STROKE_HZT 0x31ca #define UNITEXT_CJK_STROKE_HZT L"\u31ca" #define UNICODE_CJK_STROKE_HZZP 0x31cb #define UNITEXT_CJK_STROKE_HZZP L"\u31cb" #define UNICODE_CJK_STROKE_HPWG 0x31cc #define UNITEXT_CJK_STROKE_HPWG L"\u31cc" #define UNICODE_CJK_STROKE_HZW 0x31cd #define UNITEXT_CJK_STROKE_HZW L"\u31cd" #define UNICODE_CJK_STROKE_HZZZ 0x31ce #define UNITEXT_CJK_STROKE_HZZZ L"\u31ce" #define UNICODE_CJK_STROKE_N 0x31cf #define UNITEXT_CJK_STROKE_N L"\u31cf" #define UNICODE_KATAKANA_LETTER_SMALL_KU 0x31f0 #define UNITEXT_KATAKANA_LETTER_SMALL_KU L"\u31f0" #define UNICODE_KATAKANA_LETTER_SMALL_SI 0x31f1 #define UNITEXT_KATAKANA_LETTER_SMALL_SI L"\u31f1" #define UNICODE_KATAKANA_LETTER_SMALL_SU 0x31f2 #define UNITEXT_KATAKANA_LETTER_SMALL_SU L"\u31f2" #define UNICODE_KATAKANA_LETTER_SMALL_TO 0x31f3 #define UNITEXT_KATAKANA_LETTER_SMALL_TO L"\u31f3" #define UNICODE_KATAKANA_LETTER_SMALL_NU 0x31f4 #define UNITEXT_KATAKANA_LETTER_SMALL_NU L"\u31f4" #define UNICODE_KATAKANA_LETTER_SMALL_HA 0x31f5 #define UNITEXT_KATAKANA_LETTER_SMALL_HA L"\u31f5" #define UNICODE_KATAKANA_LETTER_SMALL_HI 0x31f6 #define UNITEXT_KATAKANA_LETTER_SMALL_HI L"\u31f6" #define UNICODE_KATAKANA_LETTER_SMALL_HU 0x31f7 #define UNITEXT_KATAKANA_LETTER_SMALL_HU L"\u31f7" #define UNICODE_KATAKANA_LETTER_SMALL_HE 0x31f8 #define UNITEXT_KATAKANA_LETTER_SMALL_HE L"\u31f8" #define UNICODE_KATAKANA_LETTER_SMALL_HO 0x31f9 #define UNITEXT_KATAKANA_LETTER_SMALL_HO L"\u31f9" #define UNICODE_KATAKANA_LETTER_SMALL_MU 0x31fa #define UNITEXT_KATAKANA_LETTER_SMALL_MU L"\u31fa" #define UNICODE_KATAKANA_LETTER_SMALL_RA 0x31fb #define UNITEXT_KATAKANA_LETTER_SMALL_RA L"\u31fb" #define UNICODE_KATAKANA_LETTER_SMALL_RI 0x31fc #define UNITEXT_KATAKANA_LETTER_SMALL_RI L"\u31fc" #define UNICODE_KATAKANA_LETTER_SMALL_RU 0x31fd #define UNITEXT_KATAKANA_LETTER_SMALL_RU L"\u31fd" #define UNICODE_KATAKANA_LETTER_SMALL_RE 0x31fe #define UNITEXT_KATAKANA_LETTER_SMALL_RE L"\u31fe" #define UNICODE_KATAKANA_LETTER_SMALL_RO 0x31ff #define UNITEXT_KATAKANA_LETTER_SMALL_RO L"\u31ff" #define UNICODE_PARENTHESIZED_HANGUL_KIYEOK 0x3200 #define UNITEXT_PARENTHESIZED_HANGUL_KIYEOK L"\u3200" #define UNICODE_PARENTHESIZED_HANGUL_NIEUN 0x3201 #define UNITEXT_PARENTHESIZED_HANGUL_NIEUN L"\u3201" #define UNICODE_PARENTHESIZED_HANGUL_TIKEUT 0x3202 #define UNITEXT_PARENTHESIZED_HANGUL_TIKEUT L"\u3202" #define UNICODE_PARENTHESIZED_HANGUL_RIEUL 0x3203 #define UNITEXT_PARENTHESIZED_HANGUL_RIEUL L"\u3203" #define UNICODE_PARENTHESIZED_HANGUL_MIEUM 0x3204 #define UNITEXT_PARENTHESIZED_HANGUL_MIEUM L"\u3204" #define UNICODE_PARENTHESIZED_HANGUL_PIEUP 0x3205 #define UNITEXT_PARENTHESIZED_HANGUL_PIEUP L"\u3205" #define UNICODE_PARENTHESIZED_HANGUL_SIOS 0x3206 #define UNITEXT_PARENTHESIZED_HANGUL_SIOS L"\u3206" #define UNICODE_PARENTHESIZED_HANGUL_IEUNG 0x3207 #define UNITEXT_PARENTHESIZED_HANGUL_IEUNG L"\u3207" #define UNICODE_PARENTHESIZED_HANGUL_CIEUC 0x3208 #define UNITEXT_PARENTHESIZED_HANGUL_CIEUC L"\u3208" #define UNICODE_PARENTHESIZED_HANGUL_CHIEUCH 0x3209 #define UNITEXT_PARENTHESIZED_HANGUL_CHIEUCH L"\u3209" #define UNICODE_PARENTHESIZED_HANGUL_KHIEUKH 0x320a #define UNITEXT_PARENTHESIZED_HANGUL_KHIEUKH L"\u320a" #define UNICODE_PARENTHESIZED_HANGUL_THIEUTH 0x320b #define UNITEXT_PARENTHESIZED_HANGUL_THIEUTH L"\u320b" #define UNICODE_PARENTHESIZED_HANGUL_PHIEUPH 0x320c #define UNITEXT_PARENTHESIZED_HANGUL_PHIEUPH L"\u320c" #define UNICODE_PARENTHESIZED_HANGUL_HIEUH 0x320d #define UNITEXT_PARENTHESIZED_HANGUL_HIEUH L"\u320d" #define UNICODE_PARENTHESIZED_HANGUL_KIYEOK_A 0x320e #define UNITEXT_PARENTHESIZED_HANGUL_KIYEOK_A L"\u320e" #define UNICODE_PARENTHESIZED_HANGUL_NIEUN_A 0x320f #define UNITEXT_PARENTHESIZED_HANGUL_NIEUN_A L"\u320f" #define UNICODE_PARENTHESIZED_HANGUL_TIKEUT_A 0x3210 #define UNITEXT_PARENTHESIZED_HANGUL_TIKEUT_A L"\u3210" #define UNICODE_PARENTHESIZED_HANGUL_RIEUL_A 0x3211 #define UNITEXT_PARENTHESIZED_HANGUL_RIEUL_A L"\u3211" #define UNICODE_PARENTHESIZED_HANGUL_MIEUM_A 0x3212 #define UNITEXT_PARENTHESIZED_HANGUL_MIEUM_A L"\u3212" #define UNICODE_PARENTHESIZED_HANGUL_PIEUP_A 0x3213 #define UNITEXT_PARENTHESIZED_HANGUL_PIEUP_A L"\u3213" #define UNICODE_PARENTHESIZED_HANGUL_SIOS_A 0x3214 #define UNITEXT_PARENTHESIZED_HANGUL_SIOS_A L"\u3214" #define UNICODE_PARENTHESIZED_HANGUL_IEUNG_A 0x3215 #define UNITEXT_PARENTHESIZED_HANGUL_IEUNG_A L"\u3215" #define UNICODE_PARENTHESIZED_HANGUL_CIEUC_A 0x3216 #define UNITEXT_PARENTHESIZED_HANGUL_CIEUC_A L"\u3216" #define UNICODE_PARENTHESIZED_HANGUL_CHIEUCH_A 0x3217 #define UNITEXT_PARENTHESIZED_HANGUL_CHIEUCH_A L"\u3217" #define UNICODE_PARENTHESIZED_HANGUL_KHIEUKH_A 0x3218 #define UNITEXT_PARENTHESIZED_HANGUL_KHIEUKH_A L"\u3218" #define UNICODE_PARENTHESIZED_HANGUL_THIEUTH_A 0x3219 #define UNITEXT_PARENTHESIZED_HANGUL_THIEUTH_A L"\u3219" #define UNICODE_PARENTHESIZED_HANGUL_PHIEUPH_A 0x321a #define UNITEXT_PARENTHESIZED_HANGUL_PHIEUPH_A L"\u321a" #define UNICODE_PARENTHESIZED_HANGUL_HIEUH_A 0x321b #define UNITEXT_PARENTHESIZED_HANGUL_HIEUH_A L"\u321b" #define UNICODE_PARENTHESIZED_HANGUL_CIEUC_U 0x321c #define UNITEXT_PARENTHESIZED_HANGUL_CIEUC_U L"\u321c" #define UNICODE_PARENTHESIZED_KOREAN_CHARACTER_OJEON 0x321d #define UNITEXT_PARENTHESIZED_KOREAN_CHARACTER_OJEON L"\u321d" #define UNICODE_PARENTHESIZED_KOREAN_CHARACTER_O_HU 0x321e #define UNITEXT_PARENTHESIZED_KOREAN_CHARACTER_O_HU L"\u321e" #define UNICODE_PARENTHESIZED_IDEOGRAPH_ONE 0x3220 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_ONE L"\u3220" #define UNICODE_PARENTHESIZED_IDEOGRAPH_TWO 0x3221 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_TWO L"\u3221" #define UNICODE_PARENTHESIZED_IDEOGRAPH_THREE 0x3222 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_THREE L"\u3222" #define UNICODE_PARENTHESIZED_IDEOGRAPH_FOUR 0x3223 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_FOUR L"\u3223" #define UNICODE_PARENTHESIZED_IDEOGRAPH_FIVE 0x3224 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_FIVE L"\u3224" #define UNICODE_PARENTHESIZED_IDEOGRAPH_SIX 0x3225 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_SIX L"\u3225" #define UNICODE_PARENTHESIZED_IDEOGRAPH_SEVEN 0x3226 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_SEVEN L"\u3226" #define UNICODE_PARENTHESIZED_IDEOGRAPH_EIGHT 0x3227 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_EIGHT L"\u3227" #define UNICODE_PARENTHESIZED_IDEOGRAPH_NINE 0x3228 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_NINE L"\u3228" #define UNICODE_PARENTHESIZED_IDEOGRAPH_TEN 0x3229 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_TEN L"\u3229" #define UNICODE_PARENTHESIZED_IDEOGRAPH_MOON 0x322a #define UNITEXT_PARENTHESIZED_IDEOGRAPH_MOON L"\u322a" #define UNICODE_PARENTHESIZED_IDEOGRAPH_FIRE 0x322b #define UNITEXT_PARENTHESIZED_IDEOGRAPH_FIRE L"\u322b" #define UNICODE_PARENTHESIZED_IDEOGRAPH_WATER 0x322c #define UNITEXT_PARENTHESIZED_IDEOGRAPH_WATER L"\u322c" #define UNICODE_PARENTHESIZED_IDEOGRAPH_WOOD 0x322d #define UNITEXT_PARENTHESIZED_IDEOGRAPH_WOOD L"\u322d" #define UNICODE_PARENTHESIZED_IDEOGRAPH_METAL 0x322e #define UNITEXT_PARENTHESIZED_IDEOGRAPH_METAL L"\u322e" #define UNICODE_PARENTHESIZED_IDEOGRAPH_EARTH 0x322f #define UNITEXT_PARENTHESIZED_IDEOGRAPH_EARTH L"\u322f" #define UNICODE_PARENTHESIZED_IDEOGRAPH_SUN 0x3230 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_SUN L"\u3230" #define UNICODE_PARENTHESIZED_IDEOGRAPH_STOCK 0x3231 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_STOCK L"\u3231" #define UNICODE_PARENTHESIZED_IDEOGRAPH_HAVE 0x3232 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_HAVE L"\u3232" #define UNICODE_PARENTHESIZED_IDEOGRAPH_SOCIETY 0x3233 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_SOCIETY L"\u3233" #define UNICODE_PARENTHESIZED_IDEOGRAPH_NAME 0x3234 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_NAME L"\u3234" #define UNICODE_PARENTHESIZED_IDEOGRAPH_SPECIAL 0x3235 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_SPECIAL L"\u3235" #define UNICODE_PARENTHESIZED_IDEOGRAPH_FINANCIAL 0x3236 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_FINANCIAL L"\u3236" #define UNICODE_PARENTHESIZED_IDEOGRAPH_CONGRATULATION 0x3237 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_CONGRATULATION L"\u3237" #define UNICODE_PARENTHESIZED_IDEOGRAPH_LABOR 0x3238 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_LABOR L"\u3238" #define UNICODE_PARENTHESIZED_IDEOGRAPH_REPRESENT 0x3239 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_REPRESENT L"\u3239" #define UNICODE_PARENTHESIZED_IDEOGRAPH_CALL 0x323a #define UNITEXT_PARENTHESIZED_IDEOGRAPH_CALL L"\u323a" #define UNICODE_PARENTHESIZED_IDEOGRAPH_STUDY 0x323b #define UNITEXT_PARENTHESIZED_IDEOGRAPH_STUDY L"\u323b" #define UNICODE_PARENTHESIZED_IDEOGRAPH_SUPERVISE 0x323c #define UNITEXT_PARENTHESIZED_IDEOGRAPH_SUPERVISE L"\u323c" #define UNICODE_PARENTHESIZED_IDEOGRAPH_ENTERPRISE 0x323d #define UNITEXT_PARENTHESIZED_IDEOGRAPH_ENTERPRISE L"\u323d" #define UNICODE_PARENTHESIZED_IDEOGRAPH_RESOURCE 0x323e #define UNITEXT_PARENTHESIZED_IDEOGRAPH_RESOURCE L"\u323e" #define UNICODE_PARENTHESIZED_IDEOGRAPH_ALLIANCE 0x323f #define UNITEXT_PARENTHESIZED_IDEOGRAPH_ALLIANCE L"\u323f" #define UNICODE_PARENTHESIZED_IDEOGRAPH_FESTIVAL 0x3240 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_FESTIVAL L"\u3240" #define UNICODE_PARENTHESIZED_IDEOGRAPH_REST 0x3241 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_REST L"\u3241" #define UNICODE_PARENTHESIZED_IDEOGRAPH_SELF 0x3242 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_SELF L"\u3242" #define UNICODE_PARENTHESIZED_IDEOGRAPH_REACH 0x3243 #define UNITEXT_PARENTHESIZED_IDEOGRAPH_REACH L"\u3243" #define UNICODE_PARTNERSHIP_SIGN 0x3250 #define UNITEXT_PARTNERSHIP_SIGN L"\u3250" #define UNICODE_CIRCLED_NUMBER_TWENTY_ONE 0x3251 #define UNITEXT_CIRCLED_NUMBER_TWENTY_ONE L"\u3251" #define UNICODE_CIRCLED_NUMBER_TWENTY_TWO 0x3252 #define UNITEXT_CIRCLED_NUMBER_TWENTY_TWO L"\u3252" #define UNICODE_CIRCLED_NUMBER_TWENTY_THREE 0x3253 #define UNITEXT_CIRCLED_NUMBER_TWENTY_THREE L"\u3253" #define UNICODE_CIRCLED_NUMBER_TWENTY_FOUR 0x3254 #define UNITEXT_CIRCLED_NUMBER_TWENTY_FOUR L"\u3254" #define UNICODE_CIRCLED_NUMBER_TWENTY_FIVE 0x3255 #define UNITEXT_CIRCLED_NUMBER_TWENTY_FIVE L"\u3255" #define UNICODE_CIRCLED_NUMBER_TWENTY_SIX 0x3256 #define UNITEXT_CIRCLED_NUMBER_TWENTY_SIX L"\u3256" #define UNICODE_CIRCLED_NUMBER_TWENTY_SEVEN 0x3257 #define UNITEXT_CIRCLED_NUMBER_TWENTY_SEVEN L"\u3257" #define UNICODE_CIRCLED_NUMBER_TWENTY_EIGHT 0x3258 #define UNITEXT_CIRCLED_NUMBER_TWENTY_EIGHT L"\u3258" #define UNICODE_CIRCLED_NUMBER_TWENTY_NINE 0x3259 #define UNITEXT_CIRCLED_NUMBER_TWENTY_NINE L"\u3259" #define UNICODE_CIRCLED_NUMBER_THIRTY 0x325a #define UNITEXT_CIRCLED_NUMBER_THIRTY L"\u325a" #define UNICODE_CIRCLED_NUMBER_THIRTY_ONE 0x325b #define UNITEXT_CIRCLED_NUMBER_THIRTY_ONE L"\u325b" #define UNICODE_CIRCLED_NUMBER_THIRTY_TWO 0x325c #define UNITEXT_CIRCLED_NUMBER_THIRTY_TWO L"\u325c" #define UNICODE_CIRCLED_NUMBER_THIRTY_THREE 0x325d #define UNITEXT_CIRCLED_NUMBER_THIRTY_THREE L"\u325d" #define UNICODE_CIRCLED_NUMBER_THIRTY_FOUR 0x325e #define UNITEXT_CIRCLED_NUMBER_THIRTY_FOUR L"\u325e" #define UNICODE_CIRCLED_NUMBER_THIRTY_FIVE 0x325f #define UNITEXT_CIRCLED_NUMBER_THIRTY_FIVE L"\u325f" #define UNICODE_CIRCLED_HANGUL_KIYEOK 0x3260 #define UNITEXT_CIRCLED_HANGUL_KIYEOK L"\u3260" #define UNICODE_CIRCLED_HANGUL_NIEUN 0x3261 #define UNITEXT_CIRCLED_HANGUL_NIEUN L"\u3261" #define UNICODE_CIRCLED_HANGUL_TIKEUT 0x3262 #define UNITEXT_CIRCLED_HANGUL_TIKEUT L"\u3262" #define UNICODE_CIRCLED_HANGUL_RIEUL 0x3263 #define UNITEXT_CIRCLED_HANGUL_RIEUL L"\u3263" #define UNICODE_CIRCLED_HANGUL_MIEUM 0x3264 #define UNITEXT_CIRCLED_HANGUL_MIEUM L"\u3264" #define UNICODE_CIRCLED_HANGUL_PIEUP 0x3265 #define UNITEXT_CIRCLED_HANGUL_PIEUP L"\u3265" #define UNICODE_CIRCLED_HANGUL_SIOS 0x3266 #define UNITEXT_CIRCLED_HANGUL_SIOS L"\u3266" #define UNICODE_CIRCLED_HANGUL_IEUNG 0x3267 #define UNITEXT_CIRCLED_HANGUL_IEUNG L"\u3267" #define UNICODE_CIRCLED_HANGUL_CIEUC 0x3268 #define UNITEXT_CIRCLED_HANGUL_CIEUC L"\u3268" #define UNICODE_CIRCLED_HANGUL_CHIEUCH 0x3269 #define UNITEXT_CIRCLED_HANGUL_CHIEUCH L"\u3269" #define UNICODE_CIRCLED_HANGUL_KHIEUKH 0x326a #define UNITEXT_CIRCLED_HANGUL_KHIEUKH L"\u326a" #define UNICODE_CIRCLED_HANGUL_THIEUTH 0x326b #define UNITEXT_CIRCLED_HANGUL_THIEUTH L"\u326b" #define UNICODE_CIRCLED_HANGUL_PHIEUPH 0x326c #define UNITEXT_CIRCLED_HANGUL_PHIEUPH L"\u326c" #define UNICODE_CIRCLED_HANGUL_HIEUH 0x326d #define UNITEXT_CIRCLED_HANGUL_HIEUH L"\u326d" #define UNICODE_CIRCLED_HANGUL_KIYEOK_A 0x326e #define UNITEXT_CIRCLED_HANGUL_KIYEOK_A L"\u326e" #define UNICODE_CIRCLED_HANGUL_NIEUN_A 0x326f #define UNITEXT_CIRCLED_HANGUL_NIEUN_A L"\u326f" #define UNICODE_CIRCLED_HANGUL_TIKEUT_A 0x3270 #define UNITEXT_CIRCLED_HANGUL_TIKEUT_A L"\u3270" #define UNICODE_CIRCLED_HANGUL_RIEUL_A 0x3271 #define UNITEXT_CIRCLED_HANGUL_RIEUL_A L"\u3271" #define UNICODE_CIRCLED_HANGUL_MIEUM_A 0x3272 #define UNITEXT_CIRCLED_HANGUL_MIEUM_A L"\u3272" #define UNICODE_CIRCLED_HANGUL_PIEUP_A 0x3273 #define UNITEXT_CIRCLED_HANGUL_PIEUP_A L"\u3273" #define UNICODE_CIRCLED_HANGUL_SIOS_A 0x3274 #define UNITEXT_CIRCLED_HANGUL_SIOS_A L"\u3274" #define UNICODE_CIRCLED_HANGUL_IEUNG_A 0x3275 #define UNITEXT_CIRCLED_HANGUL_IEUNG_A L"\u3275" #define UNICODE_CIRCLED_HANGUL_CIEUC_A 0x3276 #define UNITEXT_CIRCLED_HANGUL_CIEUC_A L"\u3276" #define UNICODE_CIRCLED_HANGUL_CHIEUCH_A 0x3277 #define UNITEXT_CIRCLED_HANGUL_CHIEUCH_A L"\u3277" #define UNICODE_CIRCLED_HANGUL_KHIEUKH_A 0x3278 #define UNITEXT_CIRCLED_HANGUL_KHIEUKH_A L"\u3278" #define UNICODE_CIRCLED_HANGUL_THIEUTH_A 0x3279 #define UNITEXT_CIRCLED_HANGUL_THIEUTH_A L"\u3279" #define UNICODE_CIRCLED_HANGUL_PHIEUPH_A 0x327a #define UNITEXT_CIRCLED_HANGUL_PHIEUPH_A L"\u327a" #define UNICODE_CIRCLED_HANGUL_HIEUH_A 0x327b #define UNITEXT_CIRCLED_HANGUL_HIEUH_A L"\u327b" #define UNICODE_CIRCLED_KOREAN_CHARACTER_CHAMKO 0x327c #define UNITEXT_CIRCLED_KOREAN_CHARACTER_CHAMKO L"\u327c" #define UNICODE_CIRCLED_KOREAN_CHARACTER_JUEUI 0x327d #define UNITEXT_CIRCLED_KOREAN_CHARACTER_JUEUI L"\u327d" #define UNICODE_CIRCLED_HANGUL_IEUNG_U 0x327e #define UNITEXT_CIRCLED_HANGUL_IEUNG_U L"\u327e" #define UNICODE_KOREAN_STANDARD_SYMBOL 0x327f #define UNITEXT_KOREAN_STANDARD_SYMBOL L"\u327f" #define UNICODE_CIRCLED_IDEOGRAPH_ONE 0x3280 #define UNITEXT_CIRCLED_IDEOGRAPH_ONE L"\u3280" #define UNICODE_CIRCLED_IDEOGRAPH_TWO 0x3281 #define UNITEXT_CIRCLED_IDEOGRAPH_TWO L"\u3281" #define UNICODE_CIRCLED_IDEOGRAPH_THREE 0x3282 #define UNITEXT_CIRCLED_IDEOGRAPH_THREE L"\u3282" #define UNICODE_CIRCLED_IDEOGRAPH_FOUR 0x3283 #define UNITEXT_CIRCLED_IDEOGRAPH_FOUR L"\u3283" #define UNICODE_CIRCLED_IDEOGRAPH_FIVE 0x3284 #define UNITEXT_CIRCLED_IDEOGRAPH_FIVE L"\u3284" #define UNICODE_CIRCLED_IDEOGRAPH_SIX 0x3285 #define UNITEXT_CIRCLED_IDEOGRAPH_SIX L"\u3285" #define UNICODE_CIRCLED_IDEOGRAPH_SEVEN 0x3286 #define UNITEXT_CIRCLED_IDEOGRAPH_SEVEN L"\u3286" #define UNICODE_CIRCLED_IDEOGRAPH_EIGHT 0x3287 #define UNITEXT_CIRCLED_IDEOGRAPH_EIGHT L"\u3287" #define UNICODE_CIRCLED_IDEOGRAPH_NINE 0x3288 #define UNITEXT_CIRCLED_IDEOGRAPH_NINE L"\u3288" #define UNICODE_CIRCLED_IDEOGRAPH_TEN 0x3289 #define UNITEXT_CIRCLED_IDEOGRAPH_TEN L"\u3289" #define UNICODE_CIRCLED_IDEOGRAPH_MOON 0x328a #define UNITEXT_CIRCLED_IDEOGRAPH_MOON L"\u328a" #define UNICODE_CIRCLED_IDEOGRAPH_FIRE 0x328b #define UNITEXT_CIRCLED_IDEOGRAPH_FIRE L"\u328b" #define UNICODE_CIRCLED_IDEOGRAPH_WATER 0x328c #define UNITEXT_CIRCLED_IDEOGRAPH_WATER L"\u328c" #define UNICODE_CIRCLED_IDEOGRAPH_WOOD 0x328d #define UNITEXT_CIRCLED_IDEOGRAPH_WOOD L"\u328d" #define UNICODE_CIRCLED_IDEOGRAPH_METAL 0x328e #define UNITEXT_CIRCLED_IDEOGRAPH_METAL L"\u328e" #define UNICODE_CIRCLED_IDEOGRAPH_EARTH 0x328f #define UNITEXT_CIRCLED_IDEOGRAPH_EARTH L"\u328f" #define UNICODE_CIRCLED_IDEOGRAPH_SUN 0x3290 #define UNITEXT_CIRCLED_IDEOGRAPH_SUN L"\u3290" #define UNICODE_CIRCLED_IDEOGRAPH_STOCK 0x3291 #define UNITEXT_CIRCLED_IDEOGRAPH_STOCK L"\u3291" #define UNICODE_CIRCLED_IDEOGRAPH_HAVE 0x3292 #define UNITEXT_CIRCLED_IDEOGRAPH_HAVE L"\u3292" #define UNICODE_CIRCLED_IDEOGRAPH_SOCIETY 0x3293 #define UNITEXT_CIRCLED_IDEOGRAPH_SOCIETY L"\u3293" #define UNICODE_CIRCLED_IDEOGRAPH_NAME 0x3294 #define UNITEXT_CIRCLED_IDEOGRAPH_NAME L"\u3294" #define UNICODE_CIRCLED_IDEOGRAPH_SPECIAL 0x3295 #define UNITEXT_CIRCLED_IDEOGRAPH_SPECIAL L"\u3295" #define UNICODE_CIRCLED_IDEOGRAPH_FINANCIAL 0x3296 #define UNITEXT_CIRCLED_IDEOGRAPH_FINANCIAL L"\u3296" #define UNICODE_CIRCLED_IDEOGRAPH_CONGRATULATION 0x3297 #define UNITEXT_CIRCLED_IDEOGRAPH_CONGRATULATION L"\u3297" #define UNICODE_CIRCLED_IDEOGRAPH_LABOR 0x3298 #define UNITEXT_CIRCLED_IDEOGRAPH_LABOR L"\u3298" #define UNICODE_CIRCLED_IDEOGRAPH_SECRET 0x3299 #define UNITEXT_CIRCLED_IDEOGRAPH_SECRET L"\u3299" #define UNICODE_CIRCLED_IDEOGRAPH_MALE 0x329a #define UNITEXT_CIRCLED_IDEOGRAPH_MALE L"\u329a" #define UNICODE_CIRCLED_IDEOGRAPH_FEMALE 0x329b #define UNITEXT_CIRCLED_IDEOGRAPH_FEMALE L"\u329b" #define UNICODE_CIRCLED_IDEOGRAPH_SUITABLE 0x329c #define UNITEXT_CIRCLED_IDEOGRAPH_SUITABLE L"\u329c" #define UNICODE_CIRCLED_IDEOGRAPH_EXCELLENT 0x329d #define UNITEXT_CIRCLED_IDEOGRAPH_EXCELLENT L"\u329d" #define UNICODE_CIRCLED_IDEOGRAPH_PRINT 0x329e #define UNITEXT_CIRCLED_IDEOGRAPH_PRINT L"\u329e" #define UNICODE_CIRCLED_IDEOGRAPH_ATTENTION 0x329f #define UNITEXT_CIRCLED_IDEOGRAPH_ATTENTION L"\u329f" #define UNICODE_CIRCLED_IDEOGRAPH_ITEM 0x32a0 #define UNITEXT_CIRCLED_IDEOGRAPH_ITEM L"\u32a0" #define UNICODE_CIRCLED_IDEOGRAPH_REST 0x32a1 #define UNITEXT_CIRCLED_IDEOGRAPH_REST L"\u32a1" #define UNICODE_CIRCLED_IDEOGRAPH_COPY 0x32a2 #define UNITEXT_CIRCLED_IDEOGRAPH_COPY L"\u32a2" #define UNICODE_CIRCLED_IDEOGRAPH_CORRECT 0x32a3 #define UNITEXT_CIRCLED_IDEOGRAPH_CORRECT L"\u32a3" #define UNICODE_CIRCLED_IDEOGRAPH_HIGH 0x32a4 #define UNITEXT_CIRCLED_IDEOGRAPH_HIGH L"\u32a4" #define UNICODE_CIRCLED_IDEOGRAPH_CENTRE 0x32a5 #define UNITEXT_CIRCLED_IDEOGRAPH_CENTRE L"\u32a5" #define UNICODE_CIRCLED_IDEOGRAPH_LOW 0x32a6 #define UNITEXT_CIRCLED_IDEOGRAPH_LOW L"\u32a6" #define UNICODE_CIRCLED_IDEOGRAPH_LEFT 0x32a7 #define UNITEXT_CIRCLED_IDEOGRAPH_LEFT L"\u32a7" #define UNICODE_CIRCLED_IDEOGRAPH_RIGHT 0x32a8 #define UNITEXT_CIRCLED_IDEOGRAPH_RIGHT L"\u32a8" #define UNICODE_CIRCLED_IDEOGRAPH_MEDICINE 0x32a9 #define UNITEXT_CIRCLED_IDEOGRAPH_MEDICINE L"\u32a9" #define UNICODE_CIRCLED_IDEOGRAPH_RELIGION 0x32aa #define UNITEXT_CIRCLED_IDEOGRAPH_RELIGION L"\u32aa" #define UNICODE_CIRCLED_IDEOGRAPH_STUDY 0x32ab #define UNITEXT_CIRCLED_IDEOGRAPH_STUDY L"\u32ab" #define UNICODE_CIRCLED_IDEOGRAPH_SUPERVISE 0x32ac #define UNITEXT_CIRCLED_IDEOGRAPH_SUPERVISE L"\u32ac" #define UNICODE_CIRCLED_IDEOGRAPH_ENTERPRISE 0x32ad #define UNITEXT_CIRCLED_IDEOGRAPH_ENTERPRISE L"\u32ad" #define UNICODE_CIRCLED_IDEOGRAPH_RESOURCE 0x32ae #define UNITEXT_CIRCLED_IDEOGRAPH_RESOURCE L"\u32ae" #define UNICODE_CIRCLED_IDEOGRAPH_ALLIANCE 0x32af #define UNITEXT_CIRCLED_IDEOGRAPH_ALLIANCE L"\u32af" #define UNICODE_CIRCLED_IDEOGRAPH_NIGHT 0x32b0 #define UNITEXT_CIRCLED_IDEOGRAPH_NIGHT L"\u32b0" #define UNICODE_CIRCLED_NUMBER_THIRTY_SIX 0x32b1 #define UNITEXT_CIRCLED_NUMBER_THIRTY_SIX L"\u32b1" #define UNICODE_CIRCLED_NUMBER_THIRTY_SEVEN 0x32b2 #define UNITEXT_CIRCLED_NUMBER_THIRTY_SEVEN L"\u32b2" #define UNICODE_CIRCLED_NUMBER_THIRTY_EIGHT 0x32b3 #define UNITEXT_CIRCLED_NUMBER_THIRTY_EIGHT L"\u32b3" #define UNICODE_CIRCLED_NUMBER_THIRTY_NINE 0x32b4 #define UNITEXT_CIRCLED_NUMBER_THIRTY_NINE L"\u32b4" #define UNICODE_CIRCLED_NUMBER_FORTY 0x32b5 #define UNITEXT_CIRCLED_NUMBER_FORTY L"\u32b5" #define UNICODE_CIRCLED_NUMBER_FORTY_ONE 0x32b6 #define UNITEXT_CIRCLED_NUMBER_FORTY_ONE L"\u32b6" #define UNICODE_CIRCLED_NUMBER_FORTY_TWO 0x32b7 #define UNITEXT_CIRCLED_NUMBER_FORTY_TWO L"\u32b7" #define UNICODE_CIRCLED_NUMBER_FORTY_THREE 0x32b8 #define UNITEXT_CIRCLED_NUMBER_FORTY_THREE L"\u32b8" #define UNICODE_CIRCLED_NUMBER_FORTY_FOUR 0x32b9 #define UNITEXT_CIRCLED_NUMBER_FORTY_FOUR L"\u32b9" #define UNICODE_CIRCLED_NUMBER_FORTY_FIVE 0x32ba #define UNITEXT_CIRCLED_NUMBER_FORTY_FIVE L"\u32ba" #define UNICODE_CIRCLED_NUMBER_FORTY_SIX 0x32bb #define UNITEXT_CIRCLED_NUMBER_FORTY_SIX L"\u32bb" #define UNICODE_CIRCLED_NUMBER_FORTY_SEVEN 0x32bc #define UNITEXT_CIRCLED_NUMBER_FORTY_SEVEN L"\u32bc" #define UNICODE_CIRCLED_NUMBER_FORTY_EIGHT 0x32bd #define UNITEXT_CIRCLED_NUMBER_FORTY_EIGHT L"\u32bd" #define UNICODE_CIRCLED_NUMBER_FORTY_NINE 0x32be #define UNITEXT_CIRCLED_NUMBER_FORTY_NINE L"\u32be" #define UNICODE_CIRCLED_NUMBER_FIFTY 0x32bf #define UNITEXT_CIRCLED_NUMBER_FIFTY L"\u32bf" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_JANUARY 0x32c0 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_JANUARY L"\u32c0" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_FEBRUARY 0x32c1 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_FEBRUARY L"\u32c1" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_MARCH 0x32c2 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_MARCH L"\u32c2" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_APRIL 0x32c3 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_APRIL L"\u32c3" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_MAY 0x32c4 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_MAY L"\u32c4" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_JUNE 0x32c5 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_JUNE L"\u32c5" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_JULY 0x32c6 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_JULY L"\u32c6" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_AUGUST 0x32c7 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_AUGUST L"\u32c7" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_SEPTEMBER 0x32c8 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_SEPTEMBER L"\u32c8" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_OCTOBER 0x32c9 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_OCTOBER L"\u32c9" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_NOVEMBER 0x32ca #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_NOVEMBER L"\u32ca" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DECEMBER 0x32cb #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DECEMBER L"\u32cb" #define UNICODE_SQUARE_HG 0x32cc #define UNITEXT_SQUARE_HG L"\u32cc" #define UNICODE_SQUARE_ERG 0x32cd #define UNITEXT_SQUARE_ERG L"\u32cd" #define UNICODE_SQUARE_EV 0x32ce #define UNITEXT_SQUARE_EV L"\u32ce" #define UNICODE_LIMITED_LIABILITY_SIGN 0x32cf #define UNITEXT_LIMITED_LIABILITY_SIGN L"\u32cf" #define UNICODE_CIRCLED_KATAKANA_A 0x32d0 #define UNITEXT_CIRCLED_KATAKANA_A L"\u32d0" #define UNICODE_CIRCLED_KATAKANA_I 0x32d1 #define UNITEXT_CIRCLED_KATAKANA_I L"\u32d1" #define UNICODE_CIRCLED_KATAKANA_U 0x32d2 #define UNITEXT_CIRCLED_KATAKANA_U L"\u32d2" #define UNICODE_CIRCLED_KATAKANA_E 0x32d3 #define UNITEXT_CIRCLED_KATAKANA_E L"\u32d3" #define UNICODE_CIRCLED_KATAKANA_O 0x32d4 #define UNITEXT_CIRCLED_KATAKANA_O L"\u32d4" #define UNICODE_CIRCLED_KATAKANA_KA 0x32d5 #define UNITEXT_CIRCLED_KATAKANA_KA L"\u32d5" #define UNICODE_CIRCLED_KATAKANA_KI 0x32d6 #define UNITEXT_CIRCLED_KATAKANA_KI L"\u32d6" #define UNICODE_CIRCLED_KATAKANA_KU 0x32d7 #define UNITEXT_CIRCLED_KATAKANA_KU L"\u32d7" #define UNICODE_CIRCLED_KATAKANA_KE 0x32d8 #define UNITEXT_CIRCLED_KATAKANA_KE L"\u32d8" #define UNICODE_CIRCLED_KATAKANA_KO 0x32d9 #define UNITEXT_CIRCLED_KATAKANA_KO L"\u32d9" #define UNICODE_CIRCLED_KATAKANA_SA 0x32da #define UNITEXT_CIRCLED_KATAKANA_SA L"\u32da" #define UNICODE_CIRCLED_KATAKANA_SI 0x32db #define UNITEXT_CIRCLED_KATAKANA_SI L"\u32db" #define UNICODE_CIRCLED_KATAKANA_SU 0x32dc #define UNITEXT_CIRCLED_KATAKANA_SU L"\u32dc" #define UNICODE_CIRCLED_KATAKANA_SE 0x32dd #define UNITEXT_CIRCLED_KATAKANA_SE L"\u32dd" #define UNICODE_CIRCLED_KATAKANA_SO 0x32de #define UNITEXT_CIRCLED_KATAKANA_SO L"\u32de" #define UNICODE_CIRCLED_KATAKANA_TA 0x32df #define UNITEXT_CIRCLED_KATAKANA_TA L"\u32df" #define UNICODE_CIRCLED_KATAKANA_TI 0x32e0 #define UNITEXT_CIRCLED_KATAKANA_TI L"\u32e0" #define UNICODE_CIRCLED_KATAKANA_TU 0x32e1 #define UNITEXT_CIRCLED_KATAKANA_TU L"\u32e1" #define UNICODE_CIRCLED_KATAKANA_TE 0x32e2 #define UNITEXT_CIRCLED_KATAKANA_TE L"\u32e2" #define UNICODE_CIRCLED_KATAKANA_TO 0x32e3 #define UNITEXT_CIRCLED_KATAKANA_TO L"\u32e3" #define UNICODE_CIRCLED_KATAKANA_NA 0x32e4 #define UNITEXT_CIRCLED_KATAKANA_NA L"\u32e4" #define UNICODE_CIRCLED_KATAKANA_NI 0x32e5 #define UNITEXT_CIRCLED_KATAKANA_NI L"\u32e5" #define UNICODE_CIRCLED_KATAKANA_NU 0x32e6 #define UNITEXT_CIRCLED_KATAKANA_NU L"\u32e6" #define UNICODE_CIRCLED_KATAKANA_NE 0x32e7 #define UNITEXT_CIRCLED_KATAKANA_NE L"\u32e7" #define UNICODE_CIRCLED_KATAKANA_NO 0x32e8 #define UNITEXT_CIRCLED_KATAKANA_NO L"\u32e8" #define UNICODE_CIRCLED_KATAKANA_HA 0x32e9 #define UNITEXT_CIRCLED_KATAKANA_HA L"\u32e9" #define UNICODE_CIRCLED_KATAKANA_HI 0x32ea #define UNITEXT_CIRCLED_KATAKANA_HI L"\u32ea" #define UNICODE_CIRCLED_KATAKANA_HU 0x32eb #define UNITEXT_CIRCLED_KATAKANA_HU L"\u32eb" #define UNICODE_CIRCLED_KATAKANA_HE 0x32ec #define UNITEXT_CIRCLED_KATAKANA_HE L"\u32ec" #define UNICODE_CIRCLED_KATAKANA_HO 0x32ed #define UNITEXT_CIRCLED_KATAKANA_HO L"\u32ed" #define UNICODE_CIRCLED_KATAKANA_MA 0x32ee #define UNITEXT_CIRCLED_KATAKANA_MA L"\u32ee" #define UNICODE_CIRCLED_KATAKANA_MI 0x32ef #define UNITEXT_CIRCLED_KATAKANA_MI L"\u32ef" #define UNICODE_CIRCLED_KATAKANA_MU 0x32f0 #define UNITEXT_CIRCLED_KATAKANA_MU L"\u32f0" #define UNICODE_CIRCLED_KATAKANA_ME 0x32f1 #define UNITEXT_CIRCLED_KATAKANA_ME L"\u32f1" #define UNICODE_CIRCLED_KATAKANA_MO 0x32f2 #define UNITEXT_CIRCLED_KATAKANA_MO L"\u32f2" #define UNICODE_CIRCLED_KATAKANA_YA 0x32f3 #define UNITEXT_CIRCLED_KATAKANA_YA L"\u32f3" #define UNICODE_CIRCLED_KATAKANA_YU 0x32f4 #define UNITEXT_CIRCLED_KATAKANA_YU L"\u32f4" #define UNICODE_CIRCLED_KATAKANA_YO 0x32f5 #define UNITEXT_CIRCLED_KATAKANA_YO L"\u32f5" #define UNICODE_CIRCLED_KATAKANA_RA 0x32f6 #define UNITEXT_CIRCLED_KATAKANA_RA L"\u32f6" #define UNICODE_CIRCLED_KATAKANA_RI 0x32f7 #define UNITEXT_CIRCLED_KATAKANA_RI L"\u32f7" #define UNICODE_CIRCLED_KATAKANA_RU 0x32f8 #define UNITEXT_CIRCLED_KATAKANA_RU L"\u32f8" #define UNICODE_CIRCLED_KATAKANA_RE 0x32f9 #define UNITEXT_CIRCLED_KATAKANA_RE L"\u32f9" #define UNICODE_CIRCLED_KATAKANA_RO 0x32fa #define UNITEXT_CIRCLED_KATAKANA_RO L"\u32fa" #define UNICODE_CIRCLED_KATAKANA_WA 0x32fb #define UNITEXT_CIRCLED_KATAKANA_WA L"\u32fb" #define UNICODE_CIRCLED_KATAKANA_WI 0x32fc #define UNITEXT_CIRCLED_KATAKANA_WI L"\u32fc" #define UNICODE_CIRCLED_KATAKANA_WE 0x32fd #define UNITEXT_CIRCLED_KATAKANA_WE L"\u32fd" #define UNICODE_CIRCLED_KATAKANA_WO 0x32fe #define UNITEXT_CIRCLED_KATAKANA_WO L"\u32fe" #define UNICODE_SQUARE_APAATO 0x3300 #define UNITEXT_SQUARE_APAATO L"\u3300" #define UNICODE_SQUARE_ARUHUA 0x3301 #define UNITEXT_SQUARE_ARUHUA L"\u3301" #define UNICODE_SQUARE_ANPEA 0x3302 #define UNITEXT_SQUARE_ANPEA L"\u3302" #define UNICODE_SQUARE_AARU 0x3303 #define UNITEXT_SQUARE_AARU L"\u3303" #define UNICODE_SQUARE_ININGU 0x3304 #define UNITEXT_SQUARE_ININGU L"\u3304" #define UNICODE_SQUARE_INTI 0x3305 #define UNITEXT_SQUARE_INTI L"\u3305" #define UNICODE_SQUARE_UON 0x3306 #define UNITEXT_SQUARE_UON L"\u3306" #define UNICODE_SQUARE_ESUKUUDO 0x3307 #define UNITEXT_SQUARE_ESUKUUDO L"\u3307" #define UNICODE_SQUARE_EEKAA 0x3308 #define UNITEXT_SQUARE_EEKAA L"\u3308" #define UNICODE_SQUARE_ONSU 0x3309 #define UNITEXT_SQUARE_ONSU L"\u3309" #define UNICODE_SQUARE_OOMU 0x330a #define UNITEXT_SQUARE_OOMU L"\u330a" #define UNICODE_SQUARE_KAIRI 0x330b #define UNITEXT_SQUARE_KAIRI L"\u330b" #define UNICODE_SQUARE_KARATTO 0x330c #define UNITEXT_SQUARE_KARATTO L"\u330c" #define UNICODE_SQUARE_KARORII 0x330d #define UNITEXT_SQUARE_KARORII L"\u330d" #define UNICODE_SQUARE_GARON 0x330e #define UNITEXT_SQUARE_GARON L"\u330e" #define UNICODE_SQUARE_GANMA 0x330f #define UNITEXT_SQUARE_GANMA L"\u330f" #define UNICODE_SQUARE_GIGA 0x3310 #define UNITEXT_SQUARE_GIGA L"\u3310" #define UNICODE_SQUARE_GINII 0x3311 #define UNITEXT_SQUARE_GINII L"\u3311" #define UNICODE_SQUARE_KYURII 0x3312 #define UNITEXT_SQUARE_KYURII L"\u3312" #define UNICODE_SQUARE_GIRUDAA 0x3313 #define UNITEXT_SQUARE_GIRUDAA L"\u3313" #define UNICODE_SQUARE_KIRO 0x3314 #define UNITEXT_SQUARE_KIRO L"\u3314" #define UNICODE_SQUARE_KIROGURAMU 0x3315 #define UNITEXT_SQUARE_KIROGURAMU L"\u3315" #define UNICODE_SQUARE_KIROMEETORU 0x3316 #define UNITEXT_SQUARE_KIROMEETORU L"\u3316" #define UNICODE_SQUARE_KIROWATTO 0x3317 #define UNITEXT_SQUARE_KIROWATTO L"\u3317" #define UNICODE_SQUARE_GURAMU 0x3318 #define UNITEXT_SQUARE_GURAMU L"\u3318" #define UNICODE_SQUARE_GURAMUTON 0x3319 #define UNITEXT_SQUARE_GURAMUTON L"\u3319" #define UNICODE_SQUARE_KURUZEIRO 0x331a #define UNITEXT_SQUARE_KURUZEIRO L"\u331a" #define UNICODE_SQUARE_KUROONE 0x331b #define UNITEXT_SQUARE_KUROONE L"\u331b" #define UNICODE_SQUARE_KEESU 0x331c #define UNITEXT_SQUARE_KEESU L"\u331c" #define UNICODE_SQUARE_KORUNA 0x331d #define UNITEXT_SQUARE_KORUNA L"\u331d" #define UNICODE_SQUARE_KOOPO 0x331e #define UNITEXT_SQUARE_KOOPO L"\u331e" #define UNICODE_SQUARE_SAIKURU 0x331f #define UNITEXT_SQUARE_SAIKURU L"\u331f" #define UNICODE_SQUARE_SANTIIMU 0x3320 #define UNITEXT_SQUARE_SANTIIMU L"\u3320" #define UNICODE_SQUARE_SIRINGU 0x3321 #define UNITEXT_SQUARE_SIRINGU L"\u3321" #define UNICODE_SQUARE_SENTI 0x3322 #define UNITEXT_SQUARE_SENTI L"\u3322" #define UNICODE_SQUARE_SENTO 0x3323 #define UNITEXT_SQUARE_SENTO L"\u3323" #define UNICODE_SQUARE_DAASU 0x3324 #define UNITEXT_SQUARE_DAASU L"\u3324" #define UNICODE_SQUARE_DESI 0x3325 #define UNITEXT_SQUARE_DESI L"\u3325" #define UNICODE_SQUARE_DORU 0x3326 #define UNITEXT_SQUARE_DORU L"\u3326" #define UNICODE_SQUARE_TON 0x3327 #define UNITEXT_SQUARE_TON L"\u3327" #define UNICODE_SQUARE_NANO 0x3328 #define UNITEXT_SQUARE_NANO L"\u3328" #define UNICODE_SQUARE_NOTTO 0x3329 #define UNITEXT_SQUARE_NOTTO L"\u3329" #define UNICODE_SQUARE_HAITU 0x332a #define UNITEXT_SQUARE_HAITU L"\u332a" #define UNICODE_SQUARE_PAASENTO 0x332b #define UNITEXT_SQUARE_PAASENTO L"\u332b" #define UNICODE_SQUARE_PAATU 0x332c #define UNITEXT_SQUARE_PAATU L"\u332c" #define UNICODE_SQUARE_BAARERU 0x332d #define UNITEXT_SQUARE_BAARERU L"\u332d" #define UNICODE_SQUARE_PIASUTORU 0x332e #define UNITEXT_SQUARE_PIASUTORU L"\u332e" #define UNICODE_SQUARE_PIKURU 0x332f #define UNITEXT_SQUARE_PIKURU L"\u332f" #define UNICODE_SQUARE_PIKO 0x3330 #define UNITEXT_SQUARE_PIKO L"\u3330" #define UNICODE_SQUARE_BIRU 0x3331 #define UNITEXT_SQUARE_BIRU L"\u3331" #define UNICODE_SQUARE_HUARADDO 0x3332 #define UNITEXT_SQUARE_HUARADDO L"\u3332" #define UNICODE_SQUARE_HUIITO 0x3333 #define UNITEXT_SQUARE_HUIITO L"\u3333" #define UNICODE_SQUARE_BUSSYERU 0x3334 #define UNITEXT_SQUARE_BUSSYERU L"\u3334" #define UNICODE_SQUARE_HURAN 0x3335 #define UNITEXT_SQUARE_HURAN L"\u3335" #define UNICODE_SQUARE_HEKUTAARU 0x3336 #define UNITEXT_SQUARE_HEKUTAARU L"\u3336" #define UNICODE_SQUARE_PESO 0x3337 #define UNITEXT_SQUARE_PESO L"\u3337" #define UNICODE_SQUARE_PENIHI 0x3338 #define UNITEXT_SQUARE_PENIHI L"\u3338" #define UNICODE_SQUARE_HERUTU 0x3339 #define UNITEXT_SQUARE_HERUTU L"\u3339" #define UNICODE_SQUARE_PENSU 0x333a #define UNITEXT_SQUARE_PENSU L"\u333a" #define UNICODE_SQUARE_PEEZI 0x333b #define UNITEXT_SQUARE_PEEZI L"\u333b" #define UNICODE_SQUARE_BEETA 0x333c #define UNITEXT_SQUARE_BEETA L"\u333c" #define UNICODE_SQUARE_POINTO 0x333d #define UNITEXT_SQUARE_POINTO L"\u333d" #define UNICODE_SQUARE_BORUTO 0x333e #define UNITEXT_SQUARE_BORUTO L"\u333e" #define UNICODE_SQUARE_HON 0x333f #define UNITEXT_SQUARE_HON L"\u333f" #define UNICODE_SQUARE_PONDO 0x3340 #define UNITEXT_SQUARE_PONDO L"\u3340" #define UNICODE_SQUARE_HOORU 0x3341 #define UNITEXT_SQUARE_HOORU L"\u3341" #define UNICODE_SQUARE_HOON 0x3342 #define UNITEXT_SQUARE_HOON L"\u3342" #define UNICODE_SQUARE_MAIKURO 0x3343 #define UNITEXT_SQUARE_MAIKURO L"\u3343" #define UNICODE_SQUARE_MAIRU 0x3344 #define UNITEXT_SQUARE_MAIRU L"\u3344" #define UNICODE_SQUARE_MAHHA 0x3345 #define UNITEXT_SQUARE_MAHHA L"\u3345" #define UNICODE_SQUARE_MARUKU 0x3346 #define UNITEXT_SQUARE_MARUKU L"\u3346" #define UNICODE_SQUARE_MANSYON 0x3347 #define UNITEXT_SQUARE_MANSYON L"\u3347" #define UNICODE_SQUARE_MIKURON 0x3348 #define UNITEXT_SQUARE_MIKURON L"\u3348" #define UNICODE_SQUARE_MIRI 0x3349 #define UNITEXT_SQUARE_MIRI L"\u3349" #define UNICODE_SQUARE_MIRIBAARU 0x334a #define UNITEXT_SQUARE_MIRIBAARU L"\u334a" #define UNICODE_SQUARE_MEGA 0x334b #define UNITEXT_SQUARE_MEGA L"\u334b" #define UNICODE_SQUARE_MEGATON 0x334c #define UNITEXT_SQUARE_MEGATON L"\u334c" #define UNICODE_SQUARE_MEETORU 0x334d #define UNITEXT_SQUARE_MEETORU L"\u334d" #define UNICODE_SQUARE_YAADO 0x334e #define UNITEXT_SQUARE_YAADO L"\u334e" #define UNICODE_SQUARE_YAARU 0x334f #define UNITEXT_SQUARE_YAARU L"\u334f" #define UNICODE_SQUARE_YUAN 0x3350 #define UNITEXT_SQUARE_YUAN L"\u3350" #define UNICODE_SQUARE_RITTORU 0x3351 #define UNITEXT_SQUARE_RITTORU L"\u3351" #define UNICODE_SQUARE_RIRA 0x3352 #define UNITEXT_SQUARE_RIRA L"\u3352" #define UNICODE_SQUARE_RUPII 0x3353 #define UNITEXT_SQUARE_RUPII L"\u3353" #define UNICODE_SQUARE_RUUBURU 0x3354 #define UNITEXT_SQUARE_RUUBURU L"\u3354" #define UNICODE_SQUARE_REMU 0x3355 #define UNITEXT_SQUARE_REMU L"\u3355" #define UNICODE_SQUARE_RENTOGEN 0x3356 #define UNITEXT_SQUARE_RENTOGEN L"\u3356" #define UNICODE_SQUARE_WATTO 0x3357 #define UNITEXT_SQUARE_WATTO L"\u3357" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_ZERO 0x3358 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_ZERO L"\u3358" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_ONE 0x3359 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_ONE L"\u3359" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWO 0x335a #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWO L"\u335a" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_THREE 0x335b #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_THREE L"\u335b" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_FOUR 0x335c #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_FOUR L"\u335c" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_FIVE 0x335d #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_FIVE L"\u335d" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_SIX 0x335e #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_SIX L"\u335e" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_SEVEN 0x335f #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_SEVEN L"\u335f" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_EIGHT 0x3360 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_EIGHT L"\u3360" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_NINE 0x3361 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_NINE L"\u3361" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TEN 0x3362 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TEN L"\u3362" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_ELEVEN 0x3363 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_ELEVEN L"\u3363" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWELVE 0x3364 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWELVE L"\u3364" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_THIRTEEN 0x3365 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_THIRTEEN L"\u3365" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_FOURTEEN 0x3366 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_FOURTEEN L"\u3366" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_FIFTEEN 0x3367 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_FIFTEEN L"\u3367" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_SIXTEEN 0x3368 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_SIXTEEN L"\u3368" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_SEVENTEEN 0x3369 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_SEVENTEEN L"\u3369" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_EIGHTEEN 0x336a #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_EIGHTEEN L"\u336a" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_NINETEEN 0x336b #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_NINETEEN L"\u336b" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY 0x336c #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY L"\u336c" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY_ONE 0x336d #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY_ONE L"\u336d" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY_TWO 0x336e #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY_TWO L"\u336e" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY_THREE 0x336f #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY_THREE L"\u336f" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY_FOUR 0x3370 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_HOUR_TWENTY_FOUR L"\u3370" #define UNICODE_SQUARE_HPA 0x3371 #define UNITEXT_SQUARE_HPA L"\u3371" #define UNICODE_SQUARE_DA 0x3372 #define UNITEXT_SQUARE_DA L"\u3372" #define UNICODE_SQUARE_AU 0x3373 #define UNITEXT_SQUARE_AU L"\u3373" #define UNICODE_SQUARE_BAR 0x3374 #define UNITEXT_SQUARE_BAR L"\u3374" #define UNICODE_SQUARE_OV 0x3375 #define UNITEXT_SQUARE_OV L"\u3375" #define UNICODE_SQUARE_PC 0x3376 #define UNITEXT_SQUARE_PC L"\u3376" #define UNICODE_SQUARE_DM 0x3377 #define UNITEXT_SQUARE_DM L"\u3377" #define UNICODE_SQUARE_DM_SQUARED 0x3378 #define UNITEXT_SQUARE_DM_SQUARED L"\u3378" #define UNICODE_SQUARE_DM_CUBED 0x3379 #define UNITEXT_SQUARE_DM_CUBED L"\u3379" #define UNICODE_SQUARE_IU 0x337a #define UNITEXT_SQUARE_IU L"\u337a" #define UNICODE_SQUARE_ERA_NAME_HEISEI 0x337b #define UNITEXT_SQUARE_ERA_NAME_HEISEI L"\u337b" #define UNICODE_SQUARE_ERA_NAME_SYOUWA 0x337c #define UNITEXT_SQUARE_ERA_NAME_SYOUWA L"\u337c" #define UNICODE_SQUARE_ERA_NAME_TAISYOU 0x337d #define UNITEXT_SQUARE_ERA_NAME_TAISYOU L"\u337d" #define UNICODE_SQUARE_ERA_NAME_MEIZI 0x337e #define UNITEXT_SQUARE_ERA_NAME_MEIZI L"\u337e" #define UNICODE_SQUARE_CORPORATION 0x337f #define UNITEXT_SQUARE_CORPORATION L"\u337f" #define UNICODE_SQUARE_PA_AMPS 0x3380 #define UNITEXT_SQUARE_PA_AMPS L"\u3380" #define UNICODE_SQUARE_NA 0x3381 #define UNITEXT_SQUARE_NA L"\u3381" #define UNICODE_SQUARE_MU_A 0x3382 #define UNITEXT_SQUARE_MU_A L"\u3382" #define UNICODE_SQUARE_MA 0x3383 #define UNITEXT_SQUARE_MA L"\u3383" #define UNICODE_SQUARE_KA 0x3384 #define UNITEXT_SQUARE_KA L"\u3384" #define UNICODE_SQUARE_KB 0x3385 #define UNITEXT_SQUARE_KB L"\u3385" #define UNICODE_SQUARE_MB 0x3386 #define UNITEXT_SQUARE_MB L"\u3386" #define UNICODE_SQUARE_GB 0x3387 #define UNITEXT_SQUARE_GB L"\u3387" #define UNICODE_SQUARE_CAL 0x3388 #define UNITEXT_SQUARE_CAL L"\u3388" #define UNICODE_SQUARE_KCAL 0x3389 #define UNITEXT_SQUARE_KCAL L"\u3389" #define UNICODE_SQUARE_PF 0x338a #define UNITEXT_SQUARE_PF L"\u338a" #define UNICODE_SQUARE_NF 0x338b #define UNITEXT_SQUARE_NF L"\u338b" #define UNICODE_SQUARE_MU_F 0x338c #define UNITEXT_SQUARE_MU_F L"\u338c" #define UNICODE_SQUARE_MU_G 0x338d #define UNITEXT_SQUARE_MU_G L"\u338d" #define UNICODE_SQUARE_MG 0x338e #define UNITEXT_SQUARE_MG L"\u338e" #define UNICODE_SQUARE_KG 0x338f #define UNITEXT_SQUARE_KG L"\u338f" #define UNICODE_SQUARE_HZ 0x3390 #define UNITEXT_SQUARE_HZ L"\u3390" #define UNICODE_SQUARE_KHZ 0x3391 #define UNITEXT_SQUARE_KHZ L"\u3391" #define UNICODE_SQUARE_MHZ 0x3392 #define UNITEXT_SQUARE_MHZ L"\u3392" #define UNICODE_SQUARE_GHZ 0x3393 #define UNITEXT_SQUARE_GHZ L"\u3393" #define UNICODE_SQUARE_THZ 0x3394 #define UNITEXT_SQUARE_THZ L"\u3394" #define UNICODE_SQUARE_MU_L 0x3395 #define UNITEXT_SQUARE_MU_L L"\u3395" #define UNICODE_SQUARE_ML 0x3396 #define UNITEXT_SQUARE_ML L"\u3396" #define UNICODE_SQUARE_DL 0x3397 #define UNITEXT_SQUARE_DL L"\u3397" #define UNICODE_SQUARE_KL 0x3398 #define UNITEXT_SQUARE_KL L"\u3398" #define UNICODE_SQUARE_FM 0x3399 #define UNITEXT_SQUARE_FM L"\u3399" #define UNICODE_SQUARE_NM 0x339a #define UNITEXT_SQUARE_NM L"\u339a" #define UNICODE_SQUARE_MU_M 0x339b #define UNITEXT_SQUARE_MU_M L"\u339b" #define UNICODE_SQUARE_MM 0x339c #define UNITEXT_SQUARE_MM L"\u339c" #define UNICODE_SQUARE_CM 0x339d #define UNITEXT_SQUARE_CM L"\u339d" #define UNICODE_SQUARE_KM 0x339e #define UNITEXT_SQUARE_KM L"\u339e" #define UNICODE_SQUARE_MM_SQUARED 0x339f #define UNITEXT_SQUARE_MM_SQUARED L"\u339f" #define UNICODE_SQUARE_CM_SQUARED 0x33a0 #define UNITEXT_SQUARE_CM_SQUARED L"\u33a0" #define UNICODE_SQUARE_M_SQUARED 0x33a1 #define UNITEXT_SQUARE_M_SQUARED L"\u33a1" #define UNICODE_SQUARE_KM_SQUARED 0x33a2 #define UNITEXT_SQUARE_KM_SQUARED L"\u33a2" #define UNICODE_SQUARE_MM_CUBED 0x33a3 #define UNITEXT_SQUARE_MM_CUBED L"\u33a3" #define UNICODE_SQUARE_CM_CUBED 0x33a4 #define UNITEXT_SQUARE_CM_CUBED L"\u33a4" #define UNICODE_SQUARE_M_CUBED 0x33a5 #define UNITEXT_SQUARE_M_CUBED L"\u33a5" #define UNICODE_SQUARE_KM_CUBED 0x33a6 #define UNITEXT_SQUARE_KM_CUBED L"\u33a6" #define UNICODE_SQUARE_M_OVER_S 0x33a7 #define UNITEXT_SQUARE_M_OVER_S L"\u33a7" #define UNICODE_SQUARE_M_OVER_S_SQUARED 0x33a8 #define UNITEXT_SQUARE_M_OVER_S_SQUARED L"\u33a8" #define UNICODE_SQUARE_PA 0x33a9 #define UNITEXT_SQUARE_PA L"\u33a9" #define UNICODE_SQUARE_KPA 0x33aa #define UNITEXT_SQUARE_KPA L"\u33aa" #define UNICODE_SQUARE_MPA 0x33ab #define UNITEXT_SQUARE_MPA L"\u33ab" #define UNICODE_SQUARE_GPA 0x33ac #define UNITEXT_SQUARE_GPA L"\u33ac" #define UNICODE_SQUARE_RAD 0x33ad #define UNITEXT_SQUARE_RAD L"\u33ad" #define UNICODE_SQUARE_RAD_OVER_S 0x33ae #define UNITEXT_SQUARE_RAD_OVER_S L"\u33ae" #define UNICODE_SQUARE_RAD_OVER_S_SQUARED 0x33af #define UNITEXT_SQUARE_RAD_OVER_S_SQUARED L"\u33af" #define UNICODE_SQUARE_PS 0x33b0 #define UNITEXT_SQUARE_PS L"\u33b0" #define UNICODE_SQUARE_NS 0x33b1 #define UNITEXT_SQUARE_NS L"\u33b1" #define UNICODE_SQUARE_MU_S 0x33b2 #define UNITEXT_SQUARE_MU_S L"\u33b2" #define UNICODE_SQUARE_MS 0x33b3 #define UNITEXT_SQUARE_MS L"\u33b3" #define UNICODE_SQUARE_PV 0x33b4 #define UNITEXT_SQUARE_PV L"\u33b4" #define UNICODE_SQUARE_NV 0x33b5 #define UNITEXT_SQUARE_NV L"\u33b5" #define UNICODE_SQUARE_MU_V 0x33b6 #define UNITEXT_SQUARE_MU_V L"\u33b6" #define UNICODE_SQUARE_MV 0x33b7 #define UNITEXT_SQUARE_MV L"\u33b7" #define UNICODE_SQUARE_KV 0x33b8 #define UNITEXT_SQUARE_KV L"\u33b8" #define UNICODE_SQUARE_MV_MEGA 0x33b9 #define UNITEXT_SQUARE_MV_MEGA L"\u33b9" #define UNICODE_SQUARE_PW 0x33ba #define UNITEXT_SQUARE_PW L"\u33ba" #define UNICODE_SQUARE_NW 0x33bb #define UNITEXT_SQUARE_NW L"\u33bb" #define UNICODE_SQUARE_MU_W 0x33bc #define UNITEXT_SQUARE_MU_W L"\u33bc" #define UNICODE_SQUARE_MW 0x33bd #define UNITEXT_SQUARE_MW L"\u33bd" #define UNICODE_SQUARE_KW 0x33be #define UNITEXT_SQUARE_KW L"\u33be" #define UNICODE_SQUARE_MW_MEGA 0x33bf #define UNITEXT_SQUARE_MW_MEGA L"\u33bf" #define UNICODE_SQUARE_K_OHM 0x33c0 #define UNITEXT_SQUARE_K_OHM L"\u33c0" #define UNICODE_SQUARE_M_OHM 0x33c1 #define UNITEXT_SQUARE_M_OHM L"\u33c1" #define UNICODE_SQUARE_AM 0x33c2 #define UNITEXT_SQUARE_AM L"\u33c2" #define UNICODE_SQUARE_BQ 0x33c3 #define UNITEXT_SQUARE_BQ L"\u33c3" #define UNICODE_SQUARE_CC 0x33c4 #define UNITEXT_SQUARE_CC L"\u33c4" #define UNICODE_SQUARE_CD 0x33c5 #define UNITEXT_SQUARE_CD L"\u33c5" #define UNICODE_SQUARE_C_OVER_KG 0x33c6 #define UNITEXT_SQUARE_C_OVER_KG L"\u33c6" #define UNICODE_SQUARE_CO 0x33c7 #define UNITEXT_SQUARE_CO L"\u33c7" #define UNICODE_SQUARE_DB 0x33c8 #define UNITEXT_SQUARE_DB L"\u33c8" #define UNICODE_SQUARE_GY 0x33c9 #define UNITEXT_SQUARE_GY L"\u33c9" #define UNICODE_SQUARE_HA 0x33ca #define UNITEXT_SQUARE_HA L"\u33ca" #define UNICODE_SQUARE_HP 0x33cb #define UNITEXT_SQUARE_HP L"\u33cb" #define UNICODE_SQUARE_IN 0x33cc #define UNITEXT_SQUARE_IN L"\u33cc" #define UNICODE_SQUARE_KK 0x33cd #define UNITEXT_SQUARE_KK L"\u33cd" #define UNICODE_SQUARE_KM_CAPITAL 0x33ce #define UNITEXT_SQUARE_KM_CAPITAL L"\u33ce" #define UNICODE_SQUARE_KT 0x33cf #define UNITEXT_SQUARE_KT L"\u33cf" #define UNICODE_SQUARE_LM 0x33d0 #define UNITEXT_SQUARE_LM L"\u33d0" #define UNICODE_SQUARE_LN 0x33d1 #define UNITEXT_SQUARE_LN L"\u33d1" #define UNICODE_SQUARE_LOG 0x33d2 #define UNITEXT_SQUARE_LOG L"\u33d2" #define UNICODE_SQUARE_LX 0x33d3 #define UNITEXT_SQUARE_LX L"\u33d3" #define UNICODE_SQUARE_MB_SMALL 0x33d4 #define UNITEXT_SQUARE_MB_SMALL L"\u33d4" #define UNICODE_SQUARE_MIL 0x33d5 #define UNITEXT_SQUARE_MIL L"\u33d5" #define UNICODE_SQUARE_MOL 0x33d6 #define UNITEXT_SQUARE_MOL L"\u33d6" #define UNICODE_SQUARE_PH 0x33d7 #define UNITEXT_SQUARE_PH L"\u33d7" #define UNICODE_SQUARE_PM 0x33d8 #define UNITEXT_SQUARE_PM L"\u33d8" #define UNICODE_SQUARE_PPM 0x33d9 #define UNITEXT_SQUARE_PPM L"\u33d9" #define UNICODE_SQUARE_PR 0x33da #define UNITEXT_SQUARE_PR L"\u33da" #define UNICODE_SQUARE_SR 0x33db #define UNITEXT_SQUARE_SR L"\u33db" #define UNICODE_SQUARE_SV 0x33dc #define UNITEXT_SQUARE_SV L"\u33dc" #define UNICODE_SQUARE_WB 0x33dd #define UNITEXT_SQUARE_WB L"\u33dd" #define UNICODE_SQUARE_V_OVER_M 0x33de #define UNITEXT_SQUARE_V_OVER_M L"\u33de" #define UNICODE_SQUARE_A_OVER_M 0x33df #define UNITEXT_SQUARE_A_OVER_M L"\u33df" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_ONE 0x33e0 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_ONE L"\u33e0" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWO 0x33e1 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWO L"\u33e1" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_THREE 0x33e2 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_THREE L"\u33e2" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_FOUR 0x33e3 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_FOUR L"\u33e3" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_FIVE 0x33e4 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_FIVE L"\u33e4" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_SIX 0x33e5 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_SIX L"\u33e5" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_SEVEN 0x33e6 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_SEVEN L"\u33e6" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_EIGHT 0x33e7 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_EIGHT L"\u33e7" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_NINE 0x33e8 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_NINE L"\u33e8" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TEN 0x33e9 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TEN L"\u33e9" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_ELEVEN 0x33ea #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_ELEVEN L"\u33ea" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWELVE 0x33eb #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWELVE L"\u33eb" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_THIRTEEN 0x33ec #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_THIRTEEN L"\u33ec" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_FOURTEEN 0x33ed #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_FOURTEEN L"\u33ed" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_FIFTEEN 0x33ee #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_FIFTEEN L"\u33ee" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_SIXTEEN 0x33ef #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_SIXTEEN L"\u33ef" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_SEVENTEEN 0x33f0 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_SEVENTEEN L"\u33f0" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_EIGHTEEN 0x33f1 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_EIGHTEEN L"\u33f1" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_NINETEEN 0x33f2 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_NINETEEN L"\u33f2" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY 0x33f3 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY L"\u33f3" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_ONE 0x33f4 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_ONE L"\u33f4" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_TWO 0x33f5 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_TWO L"\u33f5" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_THREE 0x33f6 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_THREE L"\u33f6" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_FOUR 0x33f7 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_FOUR L"\u33f7" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_FIVE 0x33f8 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_FIVE L"\u33f8" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_SIX 0x33f9 #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_SIX L"\u33f9" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_SEVEN 0x33fa #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_SEVEN L"\u33fa" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_EIGHT 0x33fb #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_EIGHT L"\u33fb" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_NINE 0x33fc #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_TWENTY_NINE L"\u33fc" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_THIRTY 0x33fd #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_THIRTY L"\u33fd" #define UNICODE_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_THIRTY_ONE 0x33fe #define UNITEXT_IDEOGRAPHIC_TELEGRAPH_SYMBOL_FOR_DAY_THIRTY_ONE L"\u33fe" #define UNICODE_SQUARE_GAL 0x33ff #define UNITEXT_SQUARE_GAL L"\u33ff" #define UNICODE_HEXAGRAM_FOR_THE_CREATIVE_HEAVEN 0x4dc0 #define UNITEXT_HEXAGRAM_FOR_THE_CREATIVE_HEAVEN L"\u4dc0" #define UNICODE_HEXAGRAM_FOR_THE_RECEPTIVE_EARTH 0x4dc1 #define UNITEXT_HEXAGRAM_FOR_THE_RECEPTIVE_EARTH L"\u4dc1" #define UNICODE_HEXAGRAM_FOR_DIFFICULTY_AT_THE_BEGINNING 0x4dc2 #define UNITEXT_HEXAGRAM_FOR_DIFFICULTY_AT_THE_BEGINNING L"\u4dc2" #define UNICODE_HEXAGRAM_FOR_YOUTHFUL_FOLLY 0x4dc3 #define UNITEXT_HEXAGRAM_FOR_YOUTHFUL_FOLLY L"\u4dc3" #define UNICODE_HEXAGRAM_FOR_WAITING 0x4dc4 #define UNITEXT_HEXAGRAM_FOR_WAITING L"\u4dc4" #define UNICODE_HEXAGRAM_FOR_CONFLICT 0x4dc5 #define UNITEXT_HEXAGRAM_FOR_CONFLICT L"\u4dc5" #define UNICODE_HEXAGRAM_FOR_THE_ARMY 0x4dc6 #define UNITEXT_HEXAGRAM_FOR_THE_ARMY L"\u4dc6" #define UNICODE_HEXAGRAM_FOR_HOLDING_TOGETHER 0x4dc7 #define UNITEXT_HEXAGRAM_FOR_HOLDING_TOGETHER L"\u4dc7" #define UNICODE_HEXAGRAM_FOR_SMALL_TAMING 0x4dc8 #define UNITEXT_HEXAGRAM_FOR_SMALL_TAMING L"\u4dc8" #define UNICODE_HEXAGRAM_FOR_TREADING 0x4dc9 #define UNITEXT_HEXAGRAM_FOR_TREADING L"\u4dc9" #define UNICODE_HEXAGRAM_FOR_PEACE 0x4dca #define UNITEXT_HEXAGRAM_FOR_PEACE L"\u4dca" #define UNICODE_HEXAGRAM_FOR_STANDSTILL 0x4dcb #define UNITEXT_HEXAGRAM_FOR_STANDSTILL L"\u4dcb" #define UNICODE_HEXAGRAM_FOR_FELLOWSHIP 0x4dcc #define UNITEXT_HEXAGRAM_FOR_FELLOWSHIP L"\u4dcc" #define UNICODE_HEXAGRAM_FOR_GREAT_POSSESSION 0x4dcd #define UNITEXT_HEXAGRAM_FOR_GREAT_POSSESSION L"\u4dcd" #define UNICODE_HEXAGRAM_FOR_MODESTY 0x4dce #define UNITEXT_HEXAGRAM_FOR_MODESTY L"\u4dce" #define UNICODE_HEXAGRAM_FOR_ENTHUSIASM 0x4dcf #define UNITEXT_HEXAGRAM_FOR_ENTHUSIASM L"\u4dcf" #define UNICODE_HEXAGRAM_FOR_FOLLOWING 0x4dd0 #define UNITEXT_HEXAGRAM_FOR_FOLLOWING L"\u4dd0" #define UNICODE_HEXAGRAM_FOR_WORK_ON_THE_DECAYED 0x4dd1 #define UNITEXT_HEXAGRAM_FOR_WORK_ON_THE_DECAYED L"\u4dd1" #define UNICODE_HEXAGRAM_FOR_APPROACH 0x4dd2 #define UNITEXT_HEXAGRAM_FOR_APPROACH L"\u4dd2" #define UNICODE_HEXAGRAM_FOR_CONTEMPLATION 0x4dd3 #define UNITEXT_HEXAGRAM_FOR_CONTEMPLATION L"\u4dd3" #define UNICODE_HEXAGRAM_FOR_BITING_THROUGH 0x4dd4 #define UNITEXT_HEXAGRAM_FOR_BITING_THROUGH L"\u4dd4" #define UNICODE_HEXAGRAM_FOR_GRACE 0x4dd5 #define UNITEXT_HEXAGRAM_FOR_GRACE L"\u4dd5" #define UNICODE_HEXAGRAM_FOR_SPLITTING_APART 0x4dd6 #define UNITEXT_HEXAGRAM_FOR_SPLITTING_APART L"\u4dd6" #define UNICODE_HEXAGRAM_FOR_RETURN 0x4dd7 #define UNITEXT_HEXAGRAM_FOR_RETURN L"\u4dd7" #define UNICODE_HEXAGRAM_FOR_INNOCENCE 0x4dd8 #define UNITEXT_HEXAGRAM_FOR_INNOCENCE L"\u4dd8" #define UNICODE_HEXAGRAM_FOR_GREAT_TAMING 0x4dd9 #define UNITEXT_HEXAGRAM_FOR_GREAT_TAMING L"\u4dd9" #define UNICODE_HEXAGRAM_FOR_MOUTH_CORNERS 0x4dda #define UNITEXT_HEXAGRAM_FOR_MOUTH_CORNERS L"\u4dda" #define UNICODE_HEXAGRAM_FOR_GREAT_PREPONDERANCE 0x4ddb #define UNITEXT_HEXAGRAM_FOR_GREAT_PREPONDERANCE L"\u4ddb" #define UNICODE_HEXAGRAM_FOR_THE_ABYSMAL_WATER 0x4ddc #define UNITEXT_HEXAGRAM_FOR_THE_ABYSMAL_WATER L"\u4ddc" #define UNICODE_HEXAGRAM_FOR_THE_CLINGING_FIRE 0x4ddd #define UNITEXT_HEXAGRAM_FOR_THE_CLINGING_FIRE L"\u4ddd" #define UNICODE_HEXAGRAM_FOR_INFLUENCE 0x4dde #define UNITEXT_HEXAGRAM_FOR_INFLUENCE L"\u4dde" #define UNICODE_HEXAGRAM_FOR_DURATION 0x4ddf #define UNITEXT_HEXAGRAM_FOR_DURATION L"\u4ddf" #define UNICODE_HEXAGRAM_FOR_RETREAT 0x4de0 #define UNITEXT_HEXAGRAM_FOR_RETREAT L"\u4de0" #define UNICODE_HEXAGRAM_FOR_GREAT_POWER 0x4de1 #define UNITEXT_HEXAGRAM_FOR_GREAT_POWER L"\u4de1" #define UNICODE_HEXAGRAM_FOR_PROGRESS 0x4de2 #define UNITEXT_HEXAGRAM_FOR_PROGRESS L"\u4de2" #define UNICODE_HEXAGRAM_FOR_DARKENING_OF_THE_LIGHT 0x4de3 #define UNITEXT_HEXAGRAM_FOR_DARKENING_OF_THE_LIGHT L"\u4de3" #define UNICODE_HEXAGRAM_FOR_THE_FAMILY 0x4de4 #define UNITEXT_HEXAGRAM_FOR_THE_FAMILY L"\u4de4" #define UNICODE_HEXAGRAM_FOR_OPPOSITION 0x4de5 #define UNITEXT_HEXAGRAM_FOR_OPPOSITION L"\u4de5" #define UNICODE_HEXAGRAM_FOR_OBSTRUCTION 0x4de6 #define UNITEXT_HEXAGRAM_FOR_OBSTRUCTION L"\u4de6" #define UNICODE_HEXAGRAM_FOR_DELIVERANCE 0x4de7 #define UNITEXT_HEXAGRAM_FOR_DELIVERANCE L"\u4de7" #define UNICODE_HEXAGRAM_FOR_DECREASE 0x4de8 #define UNITEXT_HEXAGRAM_FOR_DECREASE L"\u4de8" #define UNICODE_HEXAGRAM_FOR_INCREASE 0x4de9 #define UNITEXT_HEXAGRAM_FOR_INCREASE L"\u4de9" #define UNICODE_HEXAGRAM_FOR_BREAKTHROUGH 0x4dea #define UNITEXT_HEXAGRAM_FOR_BREAKTHROUGH L"\u4dea" #define UNICODE_HEXAGRAM_FOR_COMING_TO_MEET 0x4deb #define UNITEXT_HEXAGRAM_FOR_COMING_TO_MEET L"\u4deb" #define UNICODE_HEXAGRAM_FOR_GATHERING_TOGETHER 0x4dec #define UNITEXT_HEXAGRAM_FOR_GATHERING_TOGETHER L"\u4dec" #define UNICODE_HEXAGRAM_FOR_PUSHING_UPWARD 0x4ded #define UNITEXT_HEXAGRAM_FOR_PUSHING_UPWARD L"\u4ded" #define UNICODE_HEXAGRAM_FOR_OPPRESSION 0x4dee #define UNITEXT_HEXAGRAM_FOR_OPPRESSION L"\u4dee" #define UNICODE_HEXAGRAM_FOR_THE_WELL 0x4def #define UNITEXT_HEXAGRAM_FOR_THE_WELL L"\u4def" #define UNICODE_HEXAGRAM_FOR_REVOLUTION 0x4df0 #define UNITEXT_HEXAGRAM_FOR_REVOLUTION L"\u4df0" #define UNICODE_HEXAGRAM_FOR_THE_CAULDRON 0x4df1 #define UNITEXT_HEXAGRAM_FOR_THE_CAULDRON L"\u4df1" #define UNICODE_HEXAGRAM_FOR_THE_AROUSING_THUNDER 0x4df2 #define UNITEXT_HEXAGRAM_FOR_THE_AROUSING_THUNDER L"\u4df2" #define UNICODE_HEXAGRAM_FOR_THE_KEEPING_STILL_MOUNTAIN 0x4df3 #define UNITEXT_HEXAGRAM_FOR_THE_KEEPING_STILL_MOUNTAIN L"\u4df3" #define UNICODE_HEXAGRAM_FOR_DEVELOPMENT 0x4df4 #define UNITEXT_HEXAGRAM_FOR_DEVELOPMENT L"\u4df4" #define UNICODE_HEXAGRAM_FOR_THE_MARRYING_MAIDEN 0x4df5 #define UNITEXT_HEXAGRAM_FOR_THE_MARRYING_MAIDEN L"\u4df5" #define UNICODE_HEXAGRAM_FOR_ABUNDANCE 0x4df6 #define UNITEXT_HEXAGRAM_FOR_ABUNDANCE L"\u4df6" #define UNICODE_HEXAGRAM_FOR_THE_WANDERER 0x4df7 #define UNITEXT_HEXAGRAM_FOR_THE_WANDERER L"\u4df7" #define UNICODE_HEXAGRAM_FOR_THE_GENTLE_WIND 0x4df8 #define UNITEXT_HEXAGRAM_FOR_THE_GENTLE_WIND L"\u4df8" #define UNICODE_HEXAGRAM_FOR_THE_JOYOUS_LAKE 0x4df9 #define UNITEXT_HEXAGRAM_FOR_THE_JOYOUS_LAKE L"\u4df9" #define UNICODE_HEXAGRAM_FOR_DISPERSION 0x4dfa #define UNITEXT_HEXAGRAM_FOR_DISPERSION L"\u4dfa" #define UNICODE_HEXAGRAM_FOR_LIMITATION 0x4dfb #define UNITEXT_HEXAGRAM_FOR_LIMITATION L"\u4dfb" #define UNICODE_HEXAGRAM_FOR_INNER_TRUTH 0x4dfc #define UNITEXT_HEXAGRAM_FOR_INNER_TRUTH L"\u4dfc" #define UNICODE_HEXAGRAM_FOR_SMALL_PREPONDERANCE 0x4dfd #define UNITEXT_HEXAGRAM_FOR_SMALL_PREPONDERANCE L"\u4dfd" #define UNICODE_HEXAGRAM_FOR_AFTER_COMPLETION 0x4dfe #define UNITEXT_HEXAGRAM_FOR_AFTER_COMPLETION L"\u4dfe" #define UNICODE_HEXAGRAM_FOR_BEFORE_COMPLETION 0x4dff #define UNITEXT_HEXAGRAM_FOR_BEFORE_COMPLETION L"\u4dff" #define UNICODE_YI_SYLLABLE_IT 0xa000 #define UNITEXT_YI_SYLLABLE_IT L"\ua000" #define UNICODE_YI_SYLLABLE_IX 0xa001 #define UNITEXT_YI_SYLLABLE_IX L"\ua001" #define UNICODE_YI_SYLLABLE_I 0xa002 #define UNITEXT_YI_SYLLABLE_I L"\ua002" #define UNICODE_YI_SYLLABLE_IP 0xa003 #define UNITEXT_YI_SYLLABLE_IP L"\ua003" #define UNICODE_YI_SYLLABLE_IET 0xa004 #define UNITEXT_YI_SYLLABLE_IET L"\ua004" #define UNICODE_YI_SYLLABLE_IEX 0xa005 #define UNITEXT_YI_SYLLABLE_IEX L"\ua005" #define UNICODE_YI_SYLLABLE_IE 0xa006 #define UNITEXT_YI_SYLLABLE_IE L"\ua006" #define UNICODE_YI_SYLLABLE_IEP 0xa007 #define UNITEXT_YI_SYLLABLE_IEP L"\ua007" #define UNICODE_YI_SYLLABLE_AT 0xa008 #define UNITEXT_YI_SYLLABLE_AT L"\ua008" #define UNICODE_YI_SYLLABLE_AX 0xa009 #define UNITEXT_YI_SYLLABLE_AX L"\ua009" #define UNICODE_YI_SYLLABLE_A 0xa00a #define UNITEXT_YI_SYLLABLE_A L"\ua00a" #define UNICODE_YI_SYLLABLE_AP 0xa00b #define UNITEXT_YI_SYLLABLE_AP L"\ua00b" #define UNICODE_YI_SYLLABLE_UOX 0xa00c #define UNITEXT_YI_SYLLABLE_UOX L"\ua00c" #define UNICODE_YI_SYLLABLE_UO 0xa00d #define UNITEXT_YI_SYLLABLE_UO L"\ua00d" #define UNICODE_YI_SYLLABLE_UOP 0xa00e #define UNITEXT_YI_SYLLABLE_UOP L"\ua00e" #define UNICODE_YI_SYLLABLE_OT 0xa00f #define UNITEXT_YI_SYLLABLE_OT L"\ua00f" #define UNICODE_YI_SYLLABLE_OX 0xa010 #define UNITEXT_YI_SYLLABLE_OX L"\ua010" #define UNICODE_YI_SYLLABLE_O 0xa011 #define UNITEXT_YI_SYLLABLE_O L"\ua011" #define UNICODE_YI_SYLLABLE_OP 0xa012 #define UNITEXT_YI_SYLLABLE_OP L"\ua012" #define UNICODE_YI_SYLLABLE_EX 0xa013 #define UNITEXT_YI_SYLLABLE_EX L"\ua013" #define UNICODE_YI_SYLLABLE_E 0xa014 #define UNITEXT_YI_SYLLABLE_E L"\ua014" #define UNICODE_YI_SYLLABLE_WU 0xa015 #define UNITEXT_YI_SYLLABLE_WU L"\ua015" #define UNICODE_YI_SYLLABLE_BIT 0xa016 #define UNITEXT_YI_SYLLABLE_BIT L"\ua016" #define UNICODE_YI_SYLLABLE_BIX 0xa017 #define UNITEXT_YI_SYLLABLE_BIX L"\ua017" #define UNICODE_YI_SYLLABLE_BI 0xa018 #define UNITEXT_YI_SYLLABLE_BI L"\ua018" #define UNICODE_YI_SYLLABLE_BIP 0xa019 #define UNITEXT_YI_SYLLABLE_BIP L"\ua019" #define UNICODE_YI_SYLLABLE_BIET 0xa01a #define UNITEXT_YI_SYLLABLE_BIET L"\ua01a" #define UNICODE_YI_SYLLABLE_BIEX 0xa01b #define UNITEXT_YI_SYLLABLE_BIEX L"\ua01b" #define UNICODE_YI_SYLLABLE_BIE 0xa01c #define UNITEXT_YI_SYLLABLE_BIE L"\ua01c" #define UNICODE_YI_SYLLABLE_BIEP 0xa01d #define UNITEXT_YI_SYLLABLE_BIEP L"\ua01d" #define UNICODE_YI_SYLLABLE_BAT 0xa01e #define UNITEXT_YI_SYLLABLE_BAT L"\ua01e" #define UNICODE_YI_SYLLABLE_BAX 0xa01f #define UNITEXT_YI_SYLLABLE_BAX L"\ua01f" #define UNICODE_YI_SYLLABLE_BA 0xa020 #define UNITEXT_YI_SYLLABLE_BA L"\ua020" #define UNICODE_YI_SYLLABLE_BAP 0xa021 #define UNITEXT_YI_SYLLABLE_BAP L"\ua021" #define UNICODE_YI_SYLLABLE_BUOX 0xa022 #define UNITEXT_YI_SYLLABLE_BUOX L"\ua022" #define UNICODE_YI_SYLLABLE_BUO 0xa023 #define UNITEXT_YI_SYLLABLE_BUO L"\ua023" #define UNICODE_YI_SYLLABLE_BUOP 0xa024 #define UNITEXT_YI_SYLLABLE_BUOP L"\ua024" #define UNICODE_YI_SYLLABLE_BOT 0xa025 #define UNITEXT_YI_SYLLABLE_BOT L"\ua025" #define UNICODE_YI_SYLLABLE_BOX 0xa026 #define UNITEXT_YI_SYLLABLE_BOX L"\ua026" #define UNICODE_YI_SYLLABLE_BO 0xa027 #define UNITEXT_YI_SYLLABLE_BO L"\ua027" #define UNICODE_YI_SYLLABLE_BOP 0xa028 #define UNITEXT_YI_SYLLABLE_BOP L"\ua028" #define UNICODE_YI_SYLLABLE_BEX 0xa029 #define UNITEXT_YI_SYLLABLE_BEX L"\ua029" #define UNICODE_YI_SYLLABLE_BE 0xa02a #define UNITEXT_YI_SYLLABLE_BE L"\ua02a" #define UNICODE_YI_SYLLABLE_BEP 0xa02b #define UNITEXT_YI_SYLLABLE_BEP L"\ua02b" #define UNICODE_YI_SYLLABLE_BUT 0xa02c #define UNITEXT_YI_SYLLABLE_BUT L"\ua02c" #define UNICODE_YI_SYLLABLE_BUX 0xa02d #define UNITEXT_YI_SYLLABLE_BUX L"\ua02d" #define UNICODE_YI_SYLLABLE_BU 0xa02e #define UNITEXT_YI_SYLLABLE_BU L"\ua02e" #define UNICODE_YI_SYLLABLE_BUP 0xa02f #define UNITEXT_YI_SYLLABLE_BUP L"\ua02f" #define UNICODE_YI_SYLLABLE_BURX 0xa030 #define UNITEXT_YI_SYLLABLE_BURX L"\ua030" #define UNICODE_YI_SYLLABLE_BUR 0xa031 #define UNITEXT_YI_SYLLABLE_BUR L"\ua031" #define UNICODE_YI_SYLLABLE_BYT 0xa032 #define UNITEXT_YI_SYLLABLE_BYT L"\ua032" #define UNICODE_YI_SYLLABLE_BYX 0xa033 #define UNITEXT_YI_SYLLABLE_BYX L"\ua033" #define UNICODE_YI_SYLLABLE_BY 0xa034 #define UNITEXT_YI_SYLLABLE_BY L"\ua034" #define UNICODE_YI_SYLLABLE_BYP 0xa035 #define UNITEXT_YI_SYLLABLE_BYP L"\ua035" #define UNICODE_YI_SYLLABLE_BYRX 0xa036 #define UNITEXT_YI_SYLLABLE_BYRX L"\ua036" #define UNICODE_YI_SYLLABLE_BYR 0xa037 #define UNITEXT_YI_SYLLABLE_BYR L"\ua037" #define UNICODE_YI_SYLLABLE_PIT 0xa038 #define UNITEXT_YI_SYLLABLE_PIT L"\ua038" #define UNICODE_YI_SYLLABLE_PIX 0xa039 #define UNITEXT_YI_SYLLABLE_PIX L"\ua039" #define UNICODE_YI_SYLLABLE_PI 0xa03a #define UNITEXT_YI_SYLLABLE_PI L"\ua03a" #define UNICODE_YI_SYLLABLE_PIP 0xa03b #define UNITEXT_YI_SYLLABLE_PIP L"\ua03b" #define UNICODE_YI_SYLLABLE_PIEX 0xa03c #define UNITEXT_YI_SYLLABLE_PIEX L"\ua03c" #define UNICODE_YI_SYLLABLE_PIE 0xa03d #define UNITEXT_YI_SYLLABLE_PIE L"\ua03d" #define UNICODE_YI_SYLLABLE_PIEP 0xa03e #define UNITEXT_YI_SYLLABLE_PIEP L"\ua03e" #define UNICODE_YI_SYLLABLE_PAT 0xa03f #define UNITEXT_YI_SYLLABLE_PAT L"\ua03f" #define UNICODE_YI_SYLLABLE_PAX 0xa040 #define UNITEXT_YI_SYLLABLE_PAX L"\ua040" #define UNICODE_YI_SYLLABLE_PA 0xa041 #define UNITEXT_YI_SYLLABLE_PA L"\ua041" #define UNICODE_YI_SYLLABLE_PAP 0xa042 #define UNITEXT_YI_SYLLABLE_PAP L"\ua042" #define UNICODE_YI_SYLLABLE_PUOX 0xa043 #define UNITEXT_YI_SYLLABLE_PUOX L"\ua043" #define UNICODE_YI_SYLLABLE_PUO 0xa044 #define UNITEXT_YI_SYLLABLE_PUO L"\ua044" #define UNICODE_YI_SYLLABLE_PUOP 0xa045 #define UNITEXT_YI_SYLLABLE_PUOP L"\ua045" #define UNICODE_YI_SYLLABLE_POT 0xa046 #define UNITEXT_YI_SYLLABLE_POT L"\ua046" #define UNICODE_YI_SYLLABLE_POX 0xa047 #define UNITEXT_YI_SYLLABLE_POX L"\ua047" #define UNICODE_YI_SYLLABLE_PO 0xa048 #define UNITEXT_YI_SYLLABLE_PO L"\ua048" #define UNICODE_YI_SYLLABLE_POP 0xa049 #define UNITEXT_YI_SYLLABLE_POP L"\ua049" #define UNICODE_YI_SYLLABLE_PUT 0xa04a #define UNITEXT_YI_SYLLABLE_PUT L"\ua04a" #define UNICODE_YI_SYLLABLE_PUX 0xa04b #define UNITEXT_YI_SYLLABLE_PUX L"\ua04b" #define UNICODE_YI_SYLLABLE_PU 0xa04c #define UNITEXT_YI_SYLLABLE_PU L"\ua04c" #define UNICODE_YI_SYLLABLE_PUP 0xa04d #define UNITEXT_YI_SYLLABLE_PUP L"\ua04d" #define UNICODE_YI_SYLLABLE_PURX 0xa04e #define UNITEXT_YI_SYLLABLE_PURX L"\ua04e" #define UNICODE_YI_SYLLABLE_PUR 0xa04f #define UNITEXT_YI_SYLLABLE_PUR L"\ua04f" #define UNICODE_YI_SYLLABLE_PYT 0xa050 #define UNITEXT_YI_SYLLABLE_PYT L"\ua050" #define UNICODE_YI_SYLLABLE_PYX 0xa051 #define UNITEXT_YI_SYLLABLE_PYX L"\ua051" #define UNICODE_YI_SYLLABLE_PY 0xa052 #define UNITEXT_YI_SYLLABLE_PY L"\ua052" #define UNICODE_YI_SYLLABLE_PYP 0xa053 #define UNITEXT_YI_SYLLABLE_PYP L"\ua053" #define UNICODE_YI_SYLLABLE_PYRX 0xa054 #define UNITEXT_YI_SYLLABLE_PYRX L"\ua054" #define UNICODE_YI_SYLLABLE_PYR 0xa055 #define UNITEXT_YI_SYLLABLE_PYR L"\ua055" #define UNICODE_YI_SYLLABLE_BBIT 0xa056 #define UNITEXT_YI_SYLLABLE_BBIT L"\ua056" #define UNICODE_YI_SYLLABLE_BBIX 0xa057 #define UNITEXT_YI_SYLLABLE_BBIX L"\ua057" #define UNICODE_YI_SYLLABLE_BBI 0xa058 #define UNITEXT_YI_SYLLABLE_BBI L"\ua058" #define UNICODE_YI_SYLLABLE_BBIP 0xa059 #define UNITEXT_YI_SYLLABLE_BBIP L"\ua059" #define UNICODE_YI_SYLLABLE_BBIET 0xa05a #define UNITEXT_YI_SYLLABLE_BBIET L"\ua05a" #define UNICODE_YI_SYLLABLE_BBIEX 0xa05b #define UNITEXT_YI_SYLLABLE_BBIEX L"\ua05b" #define UNICODE_YI_SYLLABLE_BBIE 0xa05c #define UNITEXT_YI_SYLLABLE_BBIE L"\ua05c" #define UNICODE_YI_SYLLABLE_BBIEP 0xa05d #define UNITEXT_YI_SYLLABLE_BBIEP L"\ua05d" #define UNICODE_YI_SYLLABLE_BBAT 0xa05e #define UNITEXT_YI_SYLLABLE_BBAT L"\ua05e" #define UNICODE_YI_SYLLABLE_BBAX 0xa05f #define UNITEXT_YI_SYLLABLE_BBAX L"\ua05f" #define UNICODE_YI_SYLLABLE_BBA 0xa060 #define UNITEXT_YI_SYLLABLE_BBA L"\ua060" #define UNICODE_YI_SYLLABLE_BBAP 0xa061 #define UNITEXT_YI_SYLLABLE_BBAP L"\ua061" #define UNICODE_YI_SYLLABLE_BBUOX 0xa062 #define UNITEXT_YI_SYLLABLE_BBUOX L"\ua062" #define UNICODE_YI_SYLLABLE_BBUO 0xa063 #define UNITEXT_YI_SYLLABLE_BBUO L"\ua063" #define UNICODE_YI_SYLLABLE_BBUOP 0xa064 #define UNITEXT_YI_SYLLABLE_BBUOP L"\ua064" #define UNICODE_YI_SYLLABLE_BBOT 0xa065 #define UNITEXT_YI_SYLLABLE_BBOT L"\ua065" #define UNICODE_YI_SYLLABLE_BBOX 0xa066 #define UNITEXT_YI_SYLLABLE_BBOX L"\ua066" #define UNICODE_YI_SYLLABLE_BBO 0xa067 #define UNITEXT_YI_SYLLABLE_BBO L"\ua067" #define UNICODE_YI_SYLLABLE_BBOP 0xa068 #define UNITEXT_YI_SYLLABLE_BBOP L"\ua068" #define UNICODE_YI_SYLLABLE_BBEX 0xa069 #define UNITEXT_YI_SYLLABLE_BBEX L"\ua069" #define UNICODE_YI_SYLLABLE_BBE 0xa06a #define UNITEXT_YI_SYLLABLE_BBE L"\ua06a" #define UNICODE_YI_SYLLABLE_BBEP 0xa06b #define UNITEXT_YI_SYLLABLE_BBEP L"\ua06b" #define UNICODE_YI_SYLLABLE_BBUT 0xa06c #define UNITEXT_YI_SYLLABLE_BBUT L"\ua06c" #define UNICODE_YI_SYLLABLE_BBUX 0xa06d #define UNITEXT_YI_SYLLABLE_BBUX L"\ua06d" #define UNICODE_YI_SYLLABLE_BBU 0xa06e #define UNITEXT_YI_SYLLABLE_BBU L"\ua06e" #define UNICODE_YI_SYLLABLE_BBUP 0xa06f #define UNITEXT_YI_SYLLABLE_BBUP L"\ua06f" #define UNICODE_YI_SYLLABLE_BBURX 0xa070 #define UNITEXT_YI_SYLLABLE_BBURX L"\ua070" #define UNICODE_YI_SYLLABLE_BBUR 0xa071 #define UNITEXT_YI_SYLLABLE_BBUR L"\ua071" #define UNICODE_YI_SYLLABLE_BBYT 0xa072 #define UNITEXT_YI_SYLLABLE_BBYT L"\ua072" #define UNICODE_YI_SYLLABLE_BBYX 0xa073 #define UNITEXT_YI_SYLLABLE_BBYX L"\ua073" #define UNICODE_YI_SYLLABLE_BBY 0xa074 #define UNITEXT_YI_SYLLABLE_BBY L"\ua074" #define UNICODE_YI_SYLLABLE_BBYP 0xa075 #define UNITEXT_YI_SYLLABLE_BBYP L"\ua075" #define UNICODE_YI_SYLLABLE_NBIT 0xa076 #define UNITEXT_YI_SYLLABLE_NBIT L"\ua076" #define UNICODE_YI_SYLLABLE_NBIX 0xa077 #define UNITEXT_YI_SYLLABLE_NBIX L"\ua077" #define UNICODE_YI_SYLLABLE_NBI 0xa078 #define UNITEXT_YI_SYLLABLE_NBI L"\ua078" #define UNICODE_YI_SYLLABLE_NBIP 0xa079 #define UNITEXT_YI_SYLLABLE_NBIP L"\ua079" #define UNICODE_YI_SYLLABLE_NBIEX 0xa07a #define UNITEXT_YI_SYLLABLE_NBIEX L"\ua07a" #define UNICODE_YI_SYLLABLE_NBIE 0xa07b #define UNITEXT_YI_SYLLABLE_NBIE L"\ua07b" #define UNICODE_YI_SYLLABLE_NBIEP 0xa07c #define UNITEXT_YI_SYLLABLE_NBIEP L"\ua07c" #define UNICODE_YI_SYLLABLE_NBAT 0xa07d #define UNITEXT_YI_SYLLABLE_NBAT L"\ua07d" #define UNICODE_YI_SYLLABLE_NBAX 0xa07e #define UNITEXT_YI_SYLLABLE_NBAX L"\ua07e" #define UNICODE_YI_SYLLABLE_NBA 0xa07f #define UNITEXT_YI_SYLLABLE_NBA L"\ua07f" #define UNICODE_YI_SYLLABLE_NBAP 0xa080 #define UNITEXT_YI_SYLLABLE_NBAP L"\ua080" #define UNICODE_YI_SYLLABLE_NBOT 0xa081 #define UNITEXT_YI_SYLLABLE_NBOT L"\ua081" #define UNICODE_YI_SYLLABLE_NBOX 0xa082 #define UNITEXT_YI_SYLLABLE_NBOX L"\ua082" #define UNICODE_YI_SYLLABLE_NBO 0xa083 #define UNITEXT_YI_SYLLABLE_NBO L"\ua083" #define UNICODE_YI_SYLLABLE_NBOP 0xa084 #define UNITEXT_YI_SYLLABLE_NBOP L"\ua084" #define UNICODE_YI_SYLLABLE_NBUT 0xa085 #define UNITEXT_YI_SYLLABLE_NBUT L"\ua085" #define UNICODE_YI_SYLLABLE_NBUX 0xa086 #define UNITEXT_YI_SYLLABLE_NBUX L"\ua086" #define UNICODE_YI_SYLLABLE_NBU 0xa087 #define UNITEXT_YI_SYLLABLE_NBU L"\ua087" #define UNICODE_YI_SYLLABLE_NBUP 0xa088 #define UNITEXT_YI_SYLLABLE_NBUP L"\ua088" #define UNICODE_YI_SYLLABLE_NBURX 0xa089 #define UNITEXT_YI_SYLLABLE_NBURX L"\ua089" #define UNICODE_YI_SYLLABLE_NBUR 0xa08a #define UNITEXT_YI_SYLLABLE_NBUR L"\ua08a" #define UNICODE_YI_SYLLABLE_NBYT 0xa08b #define UNITEXT_YI_SYLLABLE_NBYT L"\ua08b" #define UNICODE_YI_SYLLABLE_NBYX 0xa08c #define UNITEXT_YI_SYLLABLE_NBYX L"\ua08c" #define UNICODE_YI_SYLLABLE_NBY 0xa08d #define UNITEXT_YI_SYLLABLE_NBY L"\ua08d" #define UNICODE_YI_SYLLABLE_NBYP 0xa08e #define UNITEXT_YI_SYLLABLE_NBYP L"\ua08e" #define UNICODE_YI_SYLLABLE_NBYRX 0xa08f #define UNITEXT_YI_SYLLABLE_NBYRX L"\ua08f" #define UNICODE_YI_SYLLABLE_NBYR 0xa090 #define UNITEXT_YI_SYLLABLE_NBYR L"\ua090" #define UNICODE_YI_SYLLABLE_HMIT 0xa091 #define UNITEXT_YI_SYLLABLE_HMIT L"\ua091" #define UNICODE_YI_SYLLABLE_HMIX 0xa092 #define UNITEXT_YI_SYLLABLE_HMIX L"\ua092" #define UNICODE_YI_SYLLABLE_HMI 0xa093 #define UNITEXT_YI_SYLLABLE_HMI L"\ua093" #define UNICODE_YI_SYLLABLE_HMIP 0xa094 #define UNITEXT_YI_SYLLABLE_HMIP L"\ua094" #define UNICODE_YI_SYLLABLE_HMIEX 0xa095 #define UNITEXT_YI_SYLLABLE_HMIEX L"\ua095" #define UNICODE_YI_SYLLABLE_HMIE 0xa096 #define UNITEXT_YI_SYLLABLE_HMIE L"\ua096" #define UNICODE_YI_SYLLABLE_HMIEP 0xa097 #define UNITEXT_YI_SYLLABLE_HMIEP L"\ua097" #define UNICODE_YI_SYLLABLE_HMAT 0xa098 #define UNITEXT_YI_SYLLABLE_HMAT L"\ua098" #define UNICODE_YI_SYLLABLE_HMAX 0xa099 #define UNITEXT_YI_SYLLABLE_HMAX L"\ua099" #define UNICODE_YI_SYLLABLE_HMA 0xa09a #define UNITEXT_YI_SYLLABLE_HMA L"\ua09a" #define UNICODE_YI_SYLLABLE_HMAP 0xa09b #define UNITEXT_YI_SYLLABLE_HMAP L"\ua09b" #define UNICODE_YI_SYLLABLE_HMUOX 0xa09c #define UNITEXT_YI_SYLLABLE_HMUOX L"\ua09c" #define UNICODE_YI_SYLLABLE_HMUO 0xa09d #define UNITEXT_YI_SYLLABLE_HMUO L"\ua09d" #define UNICODE_YI_SYLLABLE_HMUOP 0xa09e #define UNITEXT_YI_SYLLABLE_HMUOP L"\ua09e" #define UNICODE_YI_SYLLABLE_HMOT 0xa09f #define UNITEXT_YI_SYLLABLE_HMOT L"\ua09f" #define UNICODE_YI_SYLLABLE_HMOX 0xa0a0 #define UNITEXT_YI_SYLLABLE_HMOX L"\ua0a0" #define UNICODE_YI_SYLLABLE_HMO 0xa0a1 #define UNITEXT_YI_SYLLABLE_HMO L"\ua0a1" #define UNICODE_YI_SYLLABLE_HMOP 0xa0a2 #define UNITEXT_YI_SYLLABLE_HMOP L"\ua0a2" #define UNICODE_YI_SYLLABLE_HMUT 0xa0a3 #define UNITEXT_YI_SYLLABLE_HMUT L"\ua0a3" #define UNICODE_YI_SYLLABLE_HMUX 0xa0a4 #define UNITEXT_YI_SYLLABLE_HMUX L"\ua0a4" #define UNICODE_YI_SYLLABLE_HMU 0xa0a5 #define UNITEXT_YI_SYLLABLE_HMU L"\ua0a5" #define UNICODE_YI_SYLLABLE_HMUP 0xa0a6 #define UNITEXT_YI_SYLLABLE_HMUP L"\ua0a6" #define UNICODE_YI_SYLLABLE_HMURX 0xa0a7 #define UNITEXT_YI_SYLLABLE_HMURX L"\ua0a7" #define UNICODE_YI_SYLLABLE_HMUR 0xa0a8 #define UNITEXT_YI_SYLLABLE_HMUR L"\ua0a8" #define UNICODE_YI_SYLLABLE_HMYX 0xa0a9 #define UNITEXT_YI_SYLLABLE_HMYX L"\ua0a9" #define UNICODE_YI_SYLLABLE_HMY 0xa0aa #define UNITEXT_YI_SYLLABLE_HMY L"\ua0aa" #define UNICODE_YI_SYLLABLE_HMYP 0xa0ab #define UNITEXT_YI_SYLLABLE_HMYP L"\ua0ab" #define UNICODE_YI_SYLLABLE_HMYRX 0xa0ac #define UNITEXT_YI_SYLLABLE_HMYRX L"\ua0ac" #define UNICODE_YI_SYLLABLE_HMYR 0xa0ad #define UNITEXT_YI_SYLLABLE_HMYR L"\ua0ad" #define UNICODE_YI_SYLLABLE_MIT 0xa0ae #define UNITEXT_YI_SYLLABLE_MIT L"\ua0ae" #define UNICODE_YI_SYLLABLE_MIX 0xa0af #define UNITEXT_YI_SYLLABLE_MIX L"\ua0af" #define UNICODE_YI_SYLLABLE_MI 0xa0b0 #define UNITEXT_YI_SYLLABLE_MI L"\ua0b0" #define UNICODE_YI_SYLLABLE_MIP 0xa0b1 #define UNITEXT_YI_SYLLABLE_MIP L"\ua0b1" #define UNICODE_YI_SYLLABLE_MIEX 0xa0b2 #define UNITEXT_YI_SYLLABLE_MIEX L"\ua0b2" #define UNICODE_YI_SYLLABLE_MIE 0xa0b3 #define UNITEXT_YI_SYLLABLE_MIE L"\ua0b3" #define UNICODE_YI_SYLLABLE_MIEP 0xa0b4 #define UNITEXT_YI_SYLLABLE_MIEP L"\ua0b4" #define UNICODE_YI_SYLLABLE_MAT 0xa0b5 #define UNITEXT_YI_SYLLABLE_MAT L"\ua0b5" #define UNICODE_YI_SYLLABLE_MAX 0xa0b6 #define UNITEXT_YI_SYLLABLE_MAX L"\ua0b6" #define UNICODE_YI_SYLLABLE_MA 0xa0b7 #define UNITEXT_YI_SYLLABLE_MA L"\ua0b7" #define UNICODE_YI_SYLLABLE_MAP 0xa0b8 #define UNITEXT_YI_SYLLABLE_MAP L"\ua0b8" #define UNICODE_YI_SYLLABLE_MUOT 0xa0b9 #define UNITEXT_YI_SYLLABLE_MUOT L"\ua0b9" #define UNICODE_YI_SYLLABLE_MUOX 0xa0ba #define UNITEXT_YI_SYLLABLE_MUOX L"\ua0ba" #define UNICODE_YI_SYLLABLE_MUO 0xa0bb #define UNITEXT_YI_SYLLABLE_MUO L"\ua0bb" #define UNICODE_YI_SYLLABLE_MUOP 0xa0bc #define UNITEXT_YI_SYLLABLE_MUOP L"\ua0bc" #define UNICODE_YI_SYLLABLE_MOT 0xa0bd #define UNITEXT_YI_SYLLABLE_MOT L"\ua0bd" #define UNICODE_YI_SYLLABLE_MOX 0xa0be #define UNITEXT_YI_SYLLABLE_MOX L"\ua0be" #define UNICODE_YI_SYLLABLE_MO 0xa0bf #define UNITEXT_YI_SYLLABLE_MO L"\ua0bf" #define UNICODE_YI_SYLLABLE_MOP 0xa0c0 #define UNITEXT_YI_SYLLABLE_MOP L"\ua0c0" #define UNICODE_YI_SYLLABLE_MEX 0xa0c1 #define UNITEXT_YI_SYLLABLE_MEX L"\ua0c1" #define UNICODE_YI_SYLLABLE_ME 0xa0c2 #define UNITEXT_YI_SYLLABLE_ME L"\ua0c2" #define UNICODE_YI_SYLLABLE_MUT 0xa0c3 #define UNITEXT_YI_SYLLABLE_MUT L"\ua0c3" #define UNICODE_YI_SYLLABLE_MUX 0xa0c4 #define UNITEXT_YI_SYLLABLE_MUX L"\ua0c4" #define UNICODE_YI_SYLLABLE_MU 0xa0c5 #define UNITEXT_YI_SYLLABLE_MU L"\ua0c5" #define UNICODE_YI_SYLLABLE_MUP 0xa0c6 #define UNITEXT_YI_SYLLABLE_MUP L"\ua0c6" #define UNICODE_YI_SYLLABLE_MURX 0xa0c7 #define UNITEXT_YI_SYLLABLE_MURX L"\ua0c7" #define UNICODE_YI_SYLLABLE_MUR 0xa0c8 #define UNITEXT_YI_SYLLABLE_MUR L"\ua0c8" #define UNICODE_YI_SYLLABLE_MYT 0xa0c9 #define UNITEXT_YI_SYLLABLE_MYT L"\ua0c9" #define UNICODE_YI_SYLLABLE_MYX 0xa0ca #define UNITEXT_YI_SYLLABLE_MYX L"\ua0ca" #define UNICODE_YI_SYLLABLE_MY 0xa0cb #define UNITEXT_YI_SYLLABLE_MY L"\ua0cb" #define UNICODE_YI_SYLLABLE_MYP 0xa0cc #define UNITEXT_YI_SYLLABLE_MYP L"\ua0cc" #define UNICODE_YI_SYLLABLE_FIT 0xa0cd #define UNITEXT_YI_SYLLABLE_FIT L"\ua0cd" #define UNICODE_YI_SYLLABLE_FIX 0xa0ce #define UNITEXT_YI_SYLLABLE_FIX L"\ua0ce" #define UNICODE_YI_SYLLABLE_FI 0xa0cf #define UNITEXT_YI_SYLLABLE_FI L"\ua0cf" #define UNICODE_YI_SYLLABLE_FIP 0xa0d0 #define UNITEXT_YI_SYLLABLE_FIP L"\ua0d0" #define UNICODE_YI_SYLLABLE_FAT 0xa0d1 #define UNITEXT_YI_SYLLABLE_FAT L"\ua0d1" #define UNICODE_YI_SYLLABLE_FAX 0xa0d2 #define UNITEXT_YI_SYLLABLE_FAX L"\ua0d2" #define UNICODE_YI_SYLLABLE_FA 0xa0d3 #define UNITEXT_YI_SYLLABLE_FA L"\ua0d3" #define UNICODE_YI_SYLLABLE_FAP 0xa0d4 #define UNITEXT_YI_SYLLABLE_FAP L"\ua0d4" #define UNICODE_YI_SYLLABLE_FOX 0xa0d5 #define UNITEXT_YI_SYLLABLE_FOX L"\ua0d5" #define UNICODE_YI_SYLLABLE_FO 0xa0d6 #define UNITEXT_YI_SYLLABLE_FO L"\ua0d6" #define UNICODE_YI_SYLLABLE_FOP 0xa0d7 #define UNITEXT_YI_SYLLABLE_FOP L"\ua0d7" #define UNICODE_YI_SYLLABLE_FUT 0xa0d8 #define UNITEXT_YI_SYLLABLE_FUT L"\ua0d8" #define UNICODE_YI_SYLLABLE_FUX 0xa0d9 #define UNITEXT_YI_SYLLABLE_FUX L"\ua0d9" #define UNICODE_YI_SYLLABLE_FU 0xa0da #define UNITEXT_YI_SYLLABLE_FU L"\ua0da" #define UNICODE_YI_SYLLABLE_FUP 0xa0db #define UNITEXT_YI_SYLLABLE_FUP L"\ua0db" #define UNICODE_YI_SYLLABLE_FURX 0xa0dc #define UNITEXT_YI_SYLLABLE_FURX L"\ua0dc" #define UNICODE_YI_SYLLABLE_FUR 0xa0dd #define UNITEXT_YI_SYLLABLE_FUR L"\ua0dd" #define UNICODE_YI_SYLLABLE_FYT 0xa0de #define UNITEXT_YI_SYLLABLE_FYT L"\ua0de" #define UNICODE_YI_SYLLABLE_FYX 0xa0df #define UNITEXT_YI_SYLLABLE_FYX L"\ua0df" #define UNICODE_YI_SYLLABLE_FY 0xa0e0 #define UNITEXT_YI_SYLLABLE_FY L"\ua0e0" #define UNICODE_YI_SYLLABLE_FYP 0xa0e1 #define UNITEXT_YI_SYLLABLE_FYP L"\ua0e1" #define UNICODE_YI_SYLLABLE_VIT 0xa0e2 #define UNITEXT_YI_SYLLABLE_VIT L"\ua0e2" #define UNICODE_YI_SYLLABLE_VIX 0xa0e3 #define UNITEXT_YI_SYLLABLE_VIX L"\ua0e3" #define UNICODE_YI_SYLLABLE_VI 0xa0e4 #define UNITEXT_YI_SYLLABLE_VI L"\ua0e4" #define UNICODE_YI_SYLLABLE_VIP 0xa0e5 #define UNITEXT_YI_SYLLABLE_VIP L"\ua0e5" #define UNICODE_YI_SYLLABLE_VIET 0xa0e6 #define UNITEXT_YI_SYLLABLE_VIET L"\ua0e6" #define UNICODE_YI_SYLLABLE_VIEX 0xa0e7 #define UNITEXT_YI_SYLLABLE_VIEX L"\ua0e7" #define UNICODE_YI_SYLLABLE_VIE 0xa0e8 #define UNITEXT_YI_SYLLABLE_VIE L"\ua0e8" #define UNICODE_YI_SYLLABLE_VIEP 0xa0e9 #define UNITEXT_YI_SYLLABLE_VIEP L"\ua0e9" #define UNICODE_YI_SYLLABLE_VAT 0xa0ea #define UNITEXT_YI_SYLLABLE_VAT L"\ua0ea" #define UNICODE_YI_SYLLABLE_VAX 0xa0eb #define UNITEXT_YI_SYLLABLE_VAX L"\ua0eb" #define UNICODE_YI_SYLLABLE_VA 0xa0ec #define UNITEXT_YI_SYLLABLE_VA L"\ua0ec" #define UNICODE_YI_SYLLABLE_VAP 0xa0ed #define UNITEXT_YI_SYLLABLE_VAP L"\ua0ed" #define UNICODE_YI_SYLLABLE_VOT 0xa0ee #define UNITEXT_YI_SYLLABLE_VOT L"\ua0ee" #define UNICODE_YI_SYLLABLE_VOX 0xa0ef #define UNITEXT_YI_SYLLABLE_VOX L"\ua0ef" #define UNICODE_YI_SYLLABLE_VO 0xa0f0 #define UNITEXT_YI_SYLLABLE_VO L"\ua0f0" #define UNICODE_YI_SYLLABLE_VOP 0xa0f1 #define UNITEXT_YI_SYLLABLE_VOP L"\ua0f1" #define UNICODE_YI_SYLLABLE_VEX 0xa0f2 #define UNITEXT_YI_SYLLABLE_VEX L"\ua0f2" #define UNICODE_YI_SYLLABLE_VEP 0xa0f3 #define UNITEXT_YI_SYLLABLE_VEP L"\ua0f3" #define UNICODE_YI_SYLLABLE_VUT 0xa0f4 #define UNITEXT_YI_SYLLABLE_VUT L"\ua0f4" #define UNICODE_YI_SYLLABLE_VUX 0xa0f5 #define UNITEXT_YI_SYLLABLE_VUX L"\ua0f5" #define UNICODE_YI_SYLLABLE_VU 0xa0f6 #define UNITEXT_YI_SYLLABLE_VU L"\ua0f6" #define UNICODE_YI_SYLLABLE_VUP 0xa0f7 #define UNITEXT_YI_SYLLABLE_VUP L"\ua0f7" #define UNICODE_YI_SYLLABLE_VURX 0xa0f8 #define UNITEXT_YI_SYLLABLE_VURX L"\ua0f8" #define UNICODE_YI_SYLLABLE_VUR 0xa0f9 #define UNITEXT_YI_SYLLABLE_VUR L"\ua0f9" #define UNICODE_YI_SYLLABLE_VYT 0xa0fa #define UNITEXT_YI_SYLLABLE_VYT L"\ua0fa" #define UNICODE_YI_SYLLABLE_VYX 0xa0fb #define UNITEXT_YI_SYLLABLE_VYX L"\ua0fb" #define UNICODE_YI_SYLLABLE_VY 0xa0fc #define UNITEXT_YI_SYLLABLE_VY L"\ua0fc" #define UNICODE_YI_SYLLABLE_VYP 0xa0fd #define UNITEXT_YI_SYLLABLE_VYP L"\ua0fd" #define UNICODE_YI_SYLLABLE_VYRX 0xa0fe #define UNITEXT_YI_SYLLABLE_VYRX L"\ua0fe" #define UNICODE_YI_SYLLABLE_VYR 0xa0ff #define UNITEXT_YI_SYLLABLE_VYR L"\ua0ff" #define UNICODE_YI_SYLLABLE_DIT 0xa100 #define UNITEXT_YI_SYLLABLE_DIT L"\ua100" #define UNICODE_YI_SYLLABLE_DIX 0xa101 #define UNITEXT_YI_SYLLABLE_DIX L"\ua101" #define UNICODE_YI_SYLLABLE_DI 0xa102 #define UNITEXT_YI_SYLLABLE_DI L"\ua102" #define UNICODE_YI_SYLLABLE_DIP 0xa103 #define UNITEXT_YI_SYLLABLE_DIP L"\ua103" #define UNICODE_YI_SYLLABLE_DIEX 0xa104 #define UNITEXT_YI_SYLLABLE_DIEX L"\ua104" #define UNICODE_YI_SYLLABLE_DIE 0xa105 #define UNITEXT_YI_SYLLABLE_DIE L"\ua105" #define UNICODE_YI_SYLLABLE_DIEP 0xa106 #define UNITEXT_YI_SYLLABLE_DIEP L"\ua106" #define UNICODE_YI_SYLLABLE_DAT 0xa107 #define UNITEXT_YI_SYLLABLE_DAT L"\ua107" #define UNICODE_YI_SYLLABLE_DAX 0xa108 #define UNITEXT_YI_SYLLABLE_DAX L"\ua108" #define UNICODE_YI_SYLLABLE_DA 0xa109 #define UNITEXT_YI_SYLLABLE_DA L"\ua109" #define UNICODE_YI_SYLLABLE_DAP 0xa10a #define UNITEXT_YI_SYLLABLE_DAP L"\ua10a" #define UNICODE_YI_SYLLABLE_DUOX 0xa10b #define UNITEXT_YI_SYLLABLE_DUOX L"\ua10b" #define UNICODE_YI_SYLLABLE_DUO 0xa10c #define UNITEXT_YI_SYLLABLE_DUO L"\ua10c" #define UNICODE_YI_SYLLABLE_DOT 0xa10d #define UNITEXT_YI_SYLLABLE_DOT L"\ua10d" #define UNICODE_YI_SYLLABLE_DOX 0xa10e #define UNITEXT_YI_SYLLABLE_DOX L"\ua10e" #define UNICODE_YI_SYLLABLE_DO 0xa10f #define UNITEXT_YI_SYLLABLE_DO L"\ua10f" #define UNICODE_YI_SYLLABLE_DOP 0xa110 #define UNITEXT_YI_SYLLABLE_DOP L"\ua110" #define UNICODE_YI_SYLLABLE_DEX 0xa111 #define UNITEXT_YI_SYLLABLE_DEX L"\ua111" #define UNICODE_YI_SYLLABLE_DE 0xa112 #define UNITEXT_YI_SYLLABLE_DE L"\ua112" #define UNICODE_YI_SYLLABLE_DEP 0xa113 #define UNITEXT_YI_SYLLABLE_DEP L"\ua113" #define UNICODE_YI_SYLLABLE_DUT 0xa114 #define UNITEXT_YI_SYLLABLE_DUT L"\ua114" #define UNICODE_YI_SYLLABLE_DUX 0xa115 #define UNITEXT_YI_SYLLABLE_DUX L"\ua115" #define UNICODE_YI_SYLLABLE_DU 0xa116 #define UNITEXT_YI_SYLLABLE_DU L"\ua116" #define UNICODE_YI_SYLLABLE_DUP 0xa117 #define UNITEXT_YI_SYLLABLE_DUP L"\ua117" #define UNICODE_YI_SYLLABLE_DURX 0xa118 #define UNITEXT_YI_SYLLABLE_DURX L"\ua118" #define UNICODE_YI_SYLLABLE_DUR 0xa119 #define UNITEXT_YI_SYLLABLE_DUR L"\ua119" #define UNICODE_YI_SYLLABLE_TIT 0xa11a #define UNITEXT_YI_SYLLABLE_TIT L"\ua11a" #define UNICODE_YI_SYLLABLE_TIX 0xa11b #define UNITEXT_YI_SYLLABLE_TIX L"\ua11b" #define UNICODE_YI_SYLLABLE_TI 0xa11c #define UNITEXT_YI_SYLLABLE_TI L"\ua11c" #define UNICODE_YI_SYLLABLE_TIP 0xa11d #define UNITEXT_YI_SYLLABLE_TIP L"\ua11d" #define UNICODE_YI_SYLLABLE_TIEX 0xa11e #define UNITEXT_YI_SYLLABLE_TIEX L"\ua11e" #define UNICODE_YI_SYLLABLE_TIE 0xa11f #define UNITEXT_YI_SYLLABLE_TIE L"\ua11f" #define UNICODE_YI_SYLLABLE_TIEP 0xa120 #define UNITEXT_YI_SYLLABLE_TIEP L"\ua120" #define UNICODE_YI_SYLLABLE_TAT 0xa121 #define UNITEXT_YI_SYLLABLE_TAT L"\ua121" #define UNICODE_YI_SYLLABLE_TAX 0xa122 #define UNITEXT_YI_SYLLABLE_TAX L"\ua122" #define UNICODE_YI_SYLLABLE_TA 0xa123 #define UNITEXT_YI_SYLLABLE_TA L"\ua123" #define UNICODE_YI_SYLLABLE_TAP 0xa124 #define UNITEXT_YI_SYLLABLE_TAP L"\ua124" #define UNICODE_YI_SYLLABLE_TUOT 0xa125 #define UNITEXT_YI_SYLLABLE_TUOT L"\ua125" #define UNICODE_YI_SYLLABLE_TUOX 0xa126 #define UNITEXT_YI_SYLLABLE_TUOX L"\ua126" #define UNICODE_YI_SYLLABLE_TUO 0xa127 #define UNITEXT_YI_SYLLABLE_TUO L"\ua127" #define UNICODE_YI_SYLLABLE_TUOP 0xa128 #define UNITEXT_YI_SYLLABLE_TUOP L"\ua128" #define UNICODE_YI_SYLLABLE_TOT 0xa129 #define UNITEXT_YI_SYLLABLE_TOT L"\ua129" #define UNICODE_YI_SYLLABLE_TOX 0xa12a #define UNITEXT_YI_SYLLABLE_TOX L"\ua12a" #define UNICODE_YI_SYLLABLE_TO 0xa12b #define UNITEXT_YI_SYLLABLE_TO L"\ua12b" #define UNICODE_YI_SYLLABLE_TOP 0xa12c #define UNITEXT_YI_SYLLABLE_TOP L"\ua12c" #define UNICODE_YI_SYLLABLE_TEX 0xa12d #define UNITEXT_YI_SYLLABLE_TEX L"\ua12d" #define UNICODE_YI_SYLLABLE_TE 0xa12e #define UNITEXT_YI_SYLLABLE_TE L"\ua12e" #define UNICODE_YI_SYLLABLE_TEP 0xa12f #define UNITEXT_YI_SYLLABLE_TEP L"\ua12f" #define UNICODE_YI_SYLLABLE_TUT 0xa130 #define UNITEXT_YI_SYLLABLE_TUT L"\ua130" #define UNICODE_YI_SYLLABLE_TUX 0xa131 #define UNITEXT_YI_SYLLABLE_TUX L"\ua131" #define UNICODE_YI_SYLLABLE_TU 0xa132 #define UNITEXT_YI_SYLLABLE_TU L"\ua132" #define UNICODE_YI_SYLLABLE_TUP 0xa133 #define UNITEXT_YI_SYLLABLE_TUP L"\ua133" #define UNICODE_YI_SYLLABLE_TURX 0xa134 #define UNITEXT_YI_SYLLABLE_TURX L"\ua134" #define UNICODE_YI_SYLLABLE_TUR 0xa135 #define UNITEXT_YI_SYLLABLE_TUR L"\ua135" #define UNICODE_YI_SYLLABLE_DDIT 0xa136 #define UNITEXT_YI_SYLLABLE_DDIT L"\ua136" #define UNICODE_YI_SYLLABLE_DDIX 0xa137 #define UNITEXT_YI_SYLLABLE_DDIX L"\ua137" #define UNICODE_YI_SYLLABLE_DDI 0xa138 #define UNITEXT_YI_SYLLABLE_DDI L"\ua138" #define UNICODE_YI_SYLLABLE_DDIP 0xa139 #define UNITEXT_YI_SYLLABLE_DDIP L"\ua139" #define UNICODE_YI_SYLLABLE_DDIEX 0xa13a #define UNITEXT_YI_SYLLABLE_DDIEX L"\ua13a" #define UNICODE_YI_SYLLABLE_DDIE 0xa13b #define UNITEXT_YI_SYLLABLE_DDIE L"\ua13b" #define UNICODE_YI_SYLLABLE_DDIEP 0xa13c #define UNITEXT_YI_SYLLABLE_DDIEP L"\ua13c" #define UNICODE_YI_SYLLABLE_DDAT 0xa13d #define UNITEXT_YI_SYLLABLE_DDAT L"\ua13d" #define UNICODE_YI_SYLLABLE_DDAX 0xa13e #define UNITEXT_YI_SYLLABLE_DDAX L"\ua13e" #define UNICODE_YI_SYLLABLE_DDA 0xa13f #define UNITEXT_YI_SYLLABLE_DDA L"\ua13f" #define UNICODE_YI_SYLLABLE_DDAP 0xa140 #define UNITEXT_YI_SYLLABLE_DDAP L"\ua140" #define UNICODE_YI_SYLLABLE_DDUOX 0xa141 #define UNITEXT_YI_SYLLABLE_DDUOX L"\ua141" #define UNICODE_YI_SYLLABLE_DDUO 0xa142 #define UNITEXT_YI_SYLLABLE_DDUO L"\ua142" #define UNICODE_YI_SYLLABLE_DDUOP 0xa143 #define UNITEXT_YI_SYLLABLE_DDUOP L"\ua143" #define UNICODE_YI_SYLLABLE_DDOT 0xa144 #define UNITEXT_YI_SYLLABLE_DDOT L"\ua144" #define UNICODE_YI_SYLLABLE_DDOX 0xa145 #define UNITEXT_YI_SYLLABLE_DDOX L"\ua145" #define UNICODE_YI_SYLLABLE_DDO 0xa146 #define UNITEXT_YI_SYLLABLE_DDO L"\ua146" #define UNICODE_YI_SYLLABLE_DDOP 0xa147 #define UNITEXT_YI_SYLLABLE_DDOP L"\ua147" #define UNICODE_YI_SYLLABLE_DDEX 0xa148 #define UNITEXT_YI_SYLLABLE_DDEX L"\ua148" #define UNICODE_YI_SYLLABLE_DDE 0xa149 #define UNITEXT_YI_SYLLABLE_DDE L"\ua149" #define UNICODE_YI_SYLLABLE_DDEP 0xa14a #define UNITEXT_YI_SYLLABLE_DDEP L"\ua14a" #define UNICODE_YI_SYLLABLE_DDUT 0xa14b #define UNITEXT_YI_SYLLABLE_DDUT L"\ua14b" #define UNICODE_YI_SYLLABLE_DDUX 0xa14c #define UNITEXT_YI_SYLLABLE_DDUX L"\ua14c" #define UNICODE_YI_SYLLABLE_DDU 0xa14d #define UNITEXT_YI_SYLLABLE_DDU L"\ua14d" #define UNICODE_YI_SYLLABLE_DDUP 0xa14e #define UNITEXT_YI_SYLLABLE_DDUP L"\ua14e" #define UNICODE_YI_SYLLABLE_DDURX 0xa14f #define UNITEXT_YI_SYLLABLE_DDURX L"\ua14f" #define UNICODE_YI_SYLLABLE_DDUR 0xa150 #define UNITEXT_YI_SYLLABLE_DDUR L"\ua150" #define UNICODE_YI_SYLLABLE_NDIT 0xa151 #define UNITEXT_YI_SYLLABLE_NDIT L"\ua151" #define UNICODE_YI_SYLLABLE_NDIX 0xa152 #define UNITEXT_YI_SYLLABLE_NDIX L"\ua152" #define UNICODE_YI_SYLLABLE_NDI 0xa153 #define UNITEXT_YI_SYLLABLE_NDI L"\ua153" #define UNICODE_YI_SYLLABLE_NDIP 0xa154 #define UNITEXT_YI_SYLLABLE_NDIP L"\ua154" #define UNICODE_YI_SYLLABLE_NDIEX 0xa155 #define UNITEXT_YI_SYLLABLE_NDIEX L"\ua155" #define UNICODE_YI_SYLLABLE_NDIE 0xa156 #define UNITEXT_YI_SYLLABLE_NDIE L"\ua156" #define UNICODE_YI_SYLLABLE_NDAT 0xa157 #define UNITEXT_YI_SYLLABLE_NDAT L"\ua157" #define UNICODE_YI_SYLLABLE_NDAX 0xa158 #define UNITEXT_YI_SYLLABLE_NDAX L"\ua158" #define UNICODE_YI_SYLLABLE_NDA 0xa159 #define UNITEXT_YI_SYLLABLE_NDA L"\ua159" #define UNICODE_YI_SYLLABLE_NDAP 0xa15a #define UNITEXT_YI_SYLLABLE_NDAP L"\ua15a" #define UNICODE_YI_SYLLABLE_NDOT 0xa15b #define UNITEXT_YI_SYLLABLE_NDOT L"\ua15b" #define UNICODE_YI_SYLLABLE_NDOX 0xa15c #define UNITEXT_YI_SYLLABLE_NDOX L"\ua15c" #define UNICODE_YI_SYLLABLE_NDO 0xa15d #define UNITEXT_YI_SYLLABLE_NDO L"\ua15d" #define UNICODE_YI_SYLLABLE_NDOP 0xa15e #define UNITEXT_YI_SYLLABLE_NDOP L"\ua15e" #define UNICODE_YI_SYLLABLE_NDEX 0xa15f #define UNITEXT_YI_SYLLABLE_NDEX L"\ua15f" #define UNICODE_YI_SYLLABLE_NDE 0xa160 #define UNITEXT_YI_SYLLABLE_NDE L"\ua160" #define UNICODE_YI_SYLLABLE_NDEP 0xa161 #define UNITEXT_YI_SYLLABLE_NDEP L"\ua161" #define UNICODE_YI_SYLLABLE_NDUT 0xa162 #define UNITEXT_YI_SYLLABLE_NDUT L"\ua162" #define UNICODE_YI_SYLLABLE_NDUX 0xa163 #define UNITEXT_YI_SYLLABLE_NDUX L"\ua163" #define UNICODE_YI_SYLLABLE_NDU 0xa164 #define UNITEXT_YI_SYLLABLE_NDU L"\ua164" #define UNICODE_YI_SYLLABLE_NDUP 0xa165 #define UNITEXT_YI_SYLLABLE_NDUP L"\ua165" #define UNICODE_YI_SYLLABLE_NDURX 0xa166 #define UNITEXT_YI_SYLLABLE_NDURX L"\ua166" #define UNICODE_YI_SYLLABLE_NDUR 0xa167 #define UNITEXT_YI_SYLLABLE_NDUR L"\ua167" #define UNICODE_YI_SYLLABLE_HNIT 0xa168 #define UNITEXT_YI_SYLLABLE_HNIT L"\ua168" #define UNICODE_YI_SYLLABLE_HNIX 0xa169 #define UNITEXT_YI_SYLLABLE_HNIX L"\ua169" #define UNICODE_YI_SYLLABLE_HNI 0xa16a #define UNITEXT_YI_SYLLABLE_HNI L"\ua16a" #define UNICODE_YI_SYLLABLE_HNIP 0xa16b #define UNITEXT_YI_SYLLABLE_HNIP L"\ua16b" #define UNICODE_YI_SYLLABLE_HNIET 0xa16c #define UNITEXT_YI_SYLLABLE_HNIET L"\ua16c" #define UNICODE_YI_SYLLABLE_HNIEX 0xa16d #define UNITEXT_YI_SYLLABLE_HNIEX L"\ua16d" #define UNICODE_YI_SYLLABLE_HNIE 0xa16e #define UNITEXT_YI_SYLLABLE_HNIE L"\ua16e" #define UNICODE_YI_SYLLABLE_HNIEP 0xa16f #define UNITEXT_YI_SYLLABLE_HNIEP L"\ua16f" #define UNICODE_YI_SYLLABLE_HNAT 0xa170 #define UNITEXT_YI_SYLLABLE_HNAT L"\ua170" #define UNICODE_YI_SYLLABLE_HNAX 0xa171 #define UNITEXT_YI_SYLLABLE_HNAX L"\ua171" #define UNICODE_YI_SYLLABLE_HNA 0xa172 #define UNITEXT_YI_SYLLABLE_HNA L"\ua172" #define UNICODE_YI_SYLLABLE_HNAP 0xa173 #define UNITEXT_YI_SYLLABLE_HNAP L"\ua173" #define UNICODE_YI_SYLLABLE_HNUOX 0xa174 #define UNITEXT_YI_SYLLABLE_HNUOX L"\ua174" #define UNICODE_YI_SYLLABLE_HNUO 0xa175 #define UNITEXT_YI_SYLLABLE_HNUO L"\ua175" #define UNICODE_YI_SYLLABLE_HNOT 0xa176 #define UNITEXT_YI_SYLLABLE_HNOT L"\ua176" #define UNICODE_YI_SYLLABLE_HNOX 0xa177 #define UNITEXT_YI_SYLLABLE_HNOX L"\ua177" #define UNICODE_YI_SYLLABLE_HNOP 0xa178 #define UNITEXT_YI_SYLLABLE_HNOP L"\ua178" #define UNICODE_YI_SYLLABLE_HNEX 0xa179 #define UNITEXT_YI_SYLLABLE_HNEX L"\ua179" #define UNICODE_YI_SYLLABLE_HNE 0xa17a #define UNITEXT_YI_SYLLABLE_HNE L"\ua17a" #define UNICODE_YI_SYLLABLE_HNEP 0xa17b #define UNITEXT_YI_SYLLABLE_HNEP L"\ua17b" #define UNICODE_YI_SYLLABLE_HNUT 0xa17c #define UNITEXT_YI_SYLLABLE_HNUT L"\ua17c" #define UNICODE_YI_SYLLABLE_NIT 0xa17d #define UNITEXT_YI_SYLLABLE_NIT L"\ua17d" #define UNICODE_YI_SYLLABLE_NIX 0xa17e #define UNITEXT_YI_SYLLABLE_NIX L"\ua17e" #define UNICODE_YI_SYLLABLE_NI 0xa17f #define UNITEXT_YI_SYLLABLE_NI L"\ua17f" #define UNICODE_YI_SYLLABLE_NIP 0xa180 #define UNITEXT_YI_SYLLABLE_NIP L"\ua180" #define UNICODE_YI_SYLLABLE_NIEX 0xa181 #define UNITEXT_YI_SYLLABLE_NIEX L"\ua181" #define UNICODE_YI_SYLLABLE_NIE 0xa182 #define UNITEXT_YI_SYLLABLE_NIE L"\ua182" #define UNICODE_YI_SYLLABLE_NIEP 0xa183 #define UNITEXT_YI_SYLLABLE_NIEP L"\ua183" #define UNICODE_YI_SYLLABLE_NAX 0xa184 #define UNITEXT_YI_SYLLABLE_NAX L"\ua184" #define UNICODE_YI_SYLLABLE_NA 0xa185 #define UNITEXT_YI_SYLLABLE_NA L"\ua185" #define UNICODE_YI_SYLLABLE_NAP 0xa186 #define UNITEXT_YI_SYLLABLE_NAP L"\ua186" #define UNICODE_YI_SYLLABLE_NUOX 0xa187 #define UNITEXT_YI_SYLLABLE_NUOX L"\ua187" #define UNICODE_YI_SYLLABLE_NUO 0xa188 #define UNITEXT_YI_SYLLABLE_NUO L"\ua188" #define UNICODE_YI_SYLLABLE_NUOP 0xa189 #define UNITEXT_YI_SYLLABLE_NUOP L"\ua189" #define UNICODE_YI_SYLLABLE_NOT 0xa18a #define UNITEXT_YI_SYLLABLE_NOT L"\ua18a" #define UNICODE_YI_SYLLABLE_NOX 0xa18b #define UNITEXT_YI_SYLLABLE_NOX L"\ua18b" #define UNICODE_YI_SYLLABLE_NO 0xa18c #define UNITEXT_YI_SYLLABLE_NO L"\ua18c" #define UNICODE_YI_SYLLABLE_NOP 0xa18d #define UNITEXT_YI_SYLLABLE_NOP L"\ua18d" #define UNICODE_YI_SYLLABLE_NEX 0xa18e #define UNITEXT_YI_SYLLABLE_NEX L"\ua18e" #define UNICODE_YI_SYLLABLE_NE 0xa18f #define UNITEXT_YI_SYLLABLE_NE L"\ua18f" #define UNICODE_YI_SYLLABLE_NEP 0xa190 #define UNITEXT_YI_SYLLABLE_NEP L"\ua190" #define UNICODE_YI_SYLLABLE_NUT 0xa191 #define UNITEXT_YI_SYLLABLE_NUT L"\ua191" #define UNICODE_YI_SYLLABLE_NUX 0xa192 #define UNITEXT_YI_SYLLABLE_NUX L"\ua192" #define UNICODE_YI_SYLLABLE_NU 0xa193 #define UNITEXT_YI_SYLLABLE_NU L"\ua193" #define UNICODE_YI_SYLLABLE_NUP 0xa194 #define UNITEXT_YI_SYLLABLE_NUP L"\ua194" #define UNICODE_YI_SYLLABLE_NURX 0xa195 #define UNITEXT_YI_SYLLABLE_NURX L"\ua195" #define UNICODE_YI_SYLLABLE_NUR 0xa196 #define UNITEXT_YI_SYLLABLE_NUR L"\ua196" #define UNICODE_YI_SYLLABLE_HLIT 0xa197 #define UNITEXT_YI_SYLLABLE_HLIT L"\ua197" #define UNICODE_YI_SYLLABLE_HLIX 0xa198 #define UNITEXT_YI_SYLLABLE_HLIX L"\ua198" #define UNICODE_YI_SYLLABLE_HLI 0xa199 #define UNITEXT_YI_SYLLABLE_HLI L"\ua199" #define UNICODE_YI_SYLLABLE_HLIP 0xa19a #define UNITEXT_YI_SYLLABLE_HLIP L"\ua19a" #define UNICODE_YI_SYLLABLE_HLIEX 0xa19b #define UNITEXT_YI_SYLLABLE_HLIEX L"\ua19b" #define UNICODE_YI_SYLLABLE_HLIE 0xa19c #define UNITEXT_YI_SYLLABLE_HLIE L"\ua19c" #define UNICODE_YI_SYLLABLE_HLIEP 0xa19d #define UNITEXT_YI_SYLLABLE_HLIEP L"\ua19d" #define UNICODE_YI_SYLLABLE_HLAT 0xa19e #define UNITEXT_YI_SYLLABLE_HLAT L"\ua19e" #define UNICODE_YI_SYLLABLE_HLAX 0xa19f #define UNITEXT_YI_SYLLABLE_HLAX L"\ua19f" #define UNICODE_YI_SYLLABLE_HLA 0xa1a0 #define UNITEXT_YI_SYLLABLE_HLA L"\ua1a0" #define UNICODE_YI_SYLLABLE_HLAP 0xa1a1 #define UNITEXT_YI_SYLLABLE_HLAP L"\ua1a1" #define UNICODE_YI_SYLLABLE_HLUOX 0xa1a2 #define UNITEXT_YI_SYLLABLE_HLUOX L"\ua1a2" #define UNICODE_YI_SYLLABLE_HLUO 0xa1a3 #define UNITEXT_YI_SYLLABLE_HLUO L"\ua1a3" #define UNICODE_YI_SYLLABLE_HLUOP 0xa1a4 #define UNITEXT_YI_SYLLABLE_HLUOP L"\ua1a4" #define UNICODE_YI_SYLLABLE_HLOX 0xa1a5 #define UNITEXT_YI_SYLLABLE_HLOX L"\ua1a5" #define UNICODE_YI_SYLLABLE_HLO 0xa1a6 #define UNITEXT_YI_SYLLABLE_HLO L"\ua1a6" #define UNICODE_YI_SYLLABLE_HLOP 0xa1a7 #define UNITEXT_YI_SYLLABLE_HLOP L"\ua1a7" #define UNICODE_YI_SYLLABLE_HLEX 0xa1a8 #define UNITEXT_YI_SYLLABLE_HLEX L"\ua1a8" #define UNICODE_YI_SYLLABLE_HLE 0xa1a9 #define UNITEXT_YI_SYLLABLE_HLE L"\ua1a9" #define UNICODE_YI_SYLLABLE_HLEP 0xa1aa #define UNITEXT_YI_SYLLABLE_HLEP L"\ua1aa" #define UNICODE_YI_SYLLABLE_HLUT 0xa1ab #define UNITEXT_YI_SYLLABLE_HLUT L"\ua1ab" #define UNICODE_YI_SYLLABLE_HLUX 0xa1ac #define UNITEXT_YI_SYLLABLE_HLUX L"\ua1ac" #define UNICODE_YI_SYLLABLE_HLU 0xa1ad #define UNITEXT_YI_SYLLABLE_HLU L"\ua1ad" #define UNICODE_YI_SYLLABLE_HLUP 0xa1ae #define UNITEXT_YI_SYLLABLE_HLUP L"\ua1ae" #define UNICODE_YI_SYLLABLE_HLURX 0xa1af #define UNITEXT_YI_SYLLABLE_HLURX L"\ua1af" #define UNICODE_YI_SYLLABLE_HLUR 0xa1b0 #define UNITEXT_YI_SYLLABLE_HLUR L"\ua1b0" #define UNICODE_YI_SYLLABLE_HLYT 0xa1b1 #define UNITEXT_YI_SYLLABLE_HLYT L"\ua1b1" #define UNICODE_YI_SYLLABLE_HLYX 0xa1b2 #define UNITEXT_YI_SYLLABLE_HLYX L"\ua1b2" #define UNICODE_YI_SYLLABLE_HLY 0xa1b3 #define UNITEXT_YI_SYLLABLE_HLY L"\ua1b3" #define UNICODE_YI_SYLLABLE_HLYP 0xa1b4 #define UNITEXT_YI_SYLLABLE_HLYP L"\ua1b4" #define UNICODE_YI_SYLLABLE_HLYRX 0xa1b5 #define UNITEXT_YI_SYLLABLE_HLYRX L"\ua1b5" #define UNICODE_YI_SYLLABLE_HLYR 0xa1b6 #define UNITEXT_YI_SYLLABLE_HLYR L"\ua1b6" #define UNICODE_YI_SYLLABLE_LIT 0xa1b7 #define UNITEXT_YI_SYLLABLE_LIT L"\ua1b7" #define UNICODE_YI_SYLLABLE_LIX 0xa1b8 #define UNITEXT_YI_SYLLABLE_LIX L"\ua1b8" #define UNICODE_YI_SYLLABLE_LI 0xa1b9 #define UNITEXT_YI_SYLLABLE_LI L"\ua1b9" #define UNICODE_YI_SYLLABLE_LIP 0xa1ba #define UNITEXT_YI_SYLLABLE_LIP L"\ua1ba" #define UNICODE_YI_SYLLABLE_LIET 0xa1bb #define UNITEXT_YI_SYLLABLE_LIET L"\ua1bb" #define UNICODE_YI_SYLLABLE_LIEX 0xa1bc #define UNITEXT_YI_SYLLABLE_LIEX L"\ua1bc" #define UNICODE_YI_SYLLABLE_LIE 0xa1bd #define UNITEXT_YI_SYLLABLE_LIE L"\ua1bd" #define UNICODE_YI_SYLLABLE_LIEP 0xa1be #define UNITEXT_YI_SYLLABLE_LIEP L"\ua1be" #define UNICODE_YI_SYLLABLE_LAT 0xa1bf #define UNITEXT_YI_SYLLABLE_LAT L"\ua1bf" #define UNICODE_YI_SYLLABLE_LAX 0xa1c0 #define UNITEXT_YI_SYLLABLE_LAX L"\ua1c0" #define UNICODE_YI_SYLLABLE_LA 0xa1c1 #define UNITEXT_YI_SYLLABLE_LA L"\ua1c1" #define UNICODE_YI_SYLLABLE_LAP 0xa1c2 #define UNITEXT_YI_SYLLABLE_LAP L"\ua1c2" #define UNICODE_YI_SYLLABLE_LUOT 0xa1c3 #define UNITEXT_YI_SYLLABLE_LUOT L"\ua1c3" #define UNICODE_YI_SYLLABLE_LUOX 0xa1c4 #define UNITEXT_YI_SYLLABLE_LUOX L"\ua1c4" #define UNICODE_YI_SYLLABLE_LUO 0xa1c5 #define UNITEXT_YI_SYLLABLE_LUO L"\ua1c5" #define UNICODE_YI_SYLLABLE_LUOP 0xa1c6 #define UNITEXT_YI_SYLLABLE_LUOP L"\ua1c6" #define UNICODE_YI_SYLLABLE_LOT 0xa1c7 #define UNITEXT_YI_SYLLABLE_LOT L"\ua1c7" #define UNICODE_YI_SYLLABLE_LOX 0xa1c8 #define UNITEXT_YI_SYLLABLE_LOX L"\ua1c8" #define UNICODE_YI_SYLLABLE_LO 0xa1c9 #define UNITEXT_YI_SYLLABLE_LO L"\ua1c9" #define UNICODE_YI_SYLLABLE_LOP 0xa1ca #define UNITEXT_YI_SYLLABLE_LOP L"\ua1ca" #define UNICODE_YI_SYLLABLE_LEX 0xa1cb #define UNITEXT_YI_SYLLABLE_LEX L"\ua1cb" #define UNICODE_YI_SYLLABLE_LE 0xa1cc #define UNITEXT_YI_SYLLABLE_LE L"\ua1cc" #define UNICODE_YI_SYLLABLE_LEP 0xa1cd #define UNITEXT_YI_SYLLABLE_LEP L"\ua1cd" #define UNICODE_YI_SYLLABLE_LUT 0xa1ce #define UNITEXT_YI_SYLLABLE_LUT L"\ua1ce" #define UNICODE_YI_SYLLABLE_LUX 0xa1cf #define UNITEXT_YI_SYLLABLE_LUX L"\ua1cf" #define UNICODE_YI_SYLLABLE_LU 0xa1d0 #define UNITEXT_YI_SYLLABLE_LU L"\ua1d0" #define UNICODE_YI_SYLLABLE_LUP 0xa1d1 #define UNITEXT_YI_SYLLABLE_LUP L"\ua1d1" #define UNICODE_YI_SYLLABLE_LURX 0xa1d2 #define UNITEXT_YI_SYLLABLE_LURX L"\ua1d2" #define UNICODE_YI_SYLLABLE_LUR 0xa1d3 #define UNITEXT_YI_SYLLABLE_LUR L"\ua1d3" #define UNICODE_YI_SYLLABLE_LYT 0xa1d4 #define UNITEXT_YI_SYLLABLE_LYT L"\ua1d4" #define UNICODE_YI_SYLLABLE_LYX 0xa1d5 #define UNITEXT_YI_SYLLABLE_LYX L"\ua1d5" #define UNICODE_YI_SYLLABLE_LY 0xa1d6 #define UNITEXT_YI_SYLLABLE_LY L"\ua1d6" #define UNICODE_YI_SYLLABLE_LYP 0xa1d7 #define UNITEXT_YI_SYLLABLE_LYP L"\ua1d7" #define UNICODE_YI_SYLLABLE_LYRX 0xa1d8 #define UNITEXT_YI_SYLLABLE_LYRX L"\ua1d8" #define UNICODE_YI_SYLLABLE_LYR 0xa1d9 #define UNITEXT_YI_SYLLABLE_LYR L"\ua1d9" #define UNICODE_YI_SYLLABLE_GIT 0xa1da #define UNITEXT_YI_SYLLABLE_GIT L"\ua1da" #define UNICODE_YI_SYLLABLE_GIX 0xa1db #define UNITEXT_YI_SYLLABLE_GIX L"\ua1db" #define UNICODE_YI_SYLLABLE_GI 0xa1dc #define UNITEXT_YI_SYLLABLE_GI L"\ua1dc" #define UNICODE_YI_SYLLABLE_GIP 0xa1dd #define UNITEXT_YI_SYLLABLE_GIP L"\ua1dd" #define UNICODE_YI_SYLLABLE_GIET 0xa1de #define UNITEXT_YI_SYLLABLE_GIET L"\ua1de" #define UNICODE_YI_SYLLABLE_GIEX 0xa1df #define UNITEXT_YI_SYLLABLE_GIEX L"\ua1df" #define UNICODE_YI_SYLLABLE_GIE 0xa1e0 #define UNITEXT_YI_SYLLABLE_GIE L"\ua1e0" #define UNICODE_YI_SYLLABLE_GIEP 0xa1e1 #define UNITEXT_YI_SYLLABLE_GIEP L"\ua1e1" #define UNICODE_YI_SYLLABLE_GAT 0xa1e2 #define UNITEXT_YI_SYLLABLE_GAT L"\ua1e2" #define UNICODE_YI_SYLLABLE_GAX 0xa1e3 #define UNITEXT_YI_SYLLABLE_GAX L"\ua1e3" #define UNICODE_YI_SYLLABLE_GA 0xa1e4 #define UNITEXT_YI_SYLLABLE_GA L"\ua1e4" #define UNICODE_YI_SYLLABLE_GAP 0xa1e5 #define UNITEXT_YI_SYLLABLE_GAP L"\ua1e5" #define UNICODE_YI_SYLLABLE_GUOT 0xa1e6 #define UNITEXT_YI_SYLLABLE_GUOT L"\ua1e6" #define UNICODE_YI_SYLLABLE_GUOX 0xa1e7 #define UNITEXT_YI_SYLLABLE_GUOX L"\ua1e7" #define UNICODE_YI_SYLLABLE_GUO 0xa1e8 #define UNITEXT_YI_SYLLABLE_GUO L"\ua1e8" #define UNICODE_YI_SYLLABLE_GUOP 0xa1e9 #define UNITEXT_YI_SYLLABLE_GUOP L"\ua1e9" #define UNICODE_YI_SYLLABLE_GOT 0xa1ea #define UNITEXT_YI_SYLLABLE_GOT L"\ua1ea" #define UNICODE_YI_SYLLABLE_GOX 0xa1eb #define UNITEXT_YI_SYLLABLE_GOX L"\ua1eb" #define UNICODE_YI_SYLLABLE_GO 0xa1ec #define UNITEXT_YI_SYLLABLE_GO L"\ua1ec" #define UNICODE_YI_SYLLABLE_GOP 0xa1ed #define UNITEXT_YI_SYLLABLE_GOP L"\ua1ed" #define UNICODE_YI_SYLLABLE_GET 0xa1ee #define UNITEXT_YI_SYLLABLE_GET L"\ua1ee" #define UNICODE_YI_SYLLABLE_GEX 0xa1ef #define UNITEXT_YI_SYLLABLE_GEX L"\ua1ef" #define UNICODE_YI_SYLLABLE_GE 0xa1f0 #define UNITEXT_YI_SYLLABLE_GE L"\ua1f0" #define UNICODE_YI_SYLLABLE_GEP 0xa1f1 #define UNITEXT_YI_SYLLABLE_GEP L"\ua1f1" #define UNICODE_YI_SYLLABLE_GUT 0xa1f2 #define UNITEXT_YI_SYLLABLE_GUT L"\ua1f2" #define UNICODE_YI_SYLLABLE_GUX 0xa1f3 #define UNITEXT_YI_SYLLABLE_GUX L"\ua1f3" #define UNICODE_YI_SYLLABLE_GU 0xa1f4 #define UNITEXT_YI_SYLLABLE_GU L"\ua1f4" #define UNICODE_YI_SYLLABLE_GUP 0xa1f5 #define UNITEXT_YI_SYLLABLE_GUP L"\ua1f5" #define UNICODE_YI_SYLLABLE_GURX 0xa1f6 #define UNITEXT_YI_SYLLABLE_GURX L"\ua1f6" #define UNICODE_YI_SYLLABLE_GUR 0xa1f7 #define UNITEXT_YI_SYLLABLE_GUR L"\ua1f7" #define UNICODE_YI_SYLLABLE_KIT 0xa1f8 #define UNITEXT_YI_SYLLABLE_KIT L"\ua1f8" #define UNICODE_YI_SYLLABLE_KIX 0xa1f9 #define UNITEXT_YI_SYLLABLE_KIX L"\ua1f9" #define UNICODE_YI_SYLLABLE_KI 0xa1fa #define UNITEXT_YI_SYLLABLE_KI L"\ua1fa" #define UNICODE_YI_SYLLABLE_KIP 0xa1fb #define UNITEXT_YI_SYLLABLE_KIP L"\ua1fb" #define UNICODE_YI_SYLLABLE_KIEX 0xa1fc #define UNITEXT_YI_SYLLABLE_KIEX L"\ua1fc" #define UNICODE_YI_SYLLABLE_KIE 0xa1fd #define UNITEXT_YI_SYLLABLE_KIE L"\ua1fd" #define UNICODE_YI_SYLLABLE_KIEP 0xa1fe #define UNITEXT_YI_SYLLABLE_KIEP L"\ua1fe" #define UNICODE_YI_SYLLABLE_KAT 0xa1ff #define UNITEXT_YI_SYLLABLE_KAT L"\ua1ff" #define UNICODE_YI_SYLLABLE_KAX 0xa200 #define UNITEXT_YI_SYLLABLE_KAX L"\ua200" #define UNICODE_YI_SYLLABLE_KA 0xa201 #define UNITEXT_YI_SYLLABLE_KA L"\ua201" #define UNICODE_YI_SYLLABLE_KAP 0xa202 #define UNITEXT_YI_SYLLABLE_KAP L"\ua202" #define UNICODE_YI_SYLLABLE_KUOX 0xa203 #define UNITEXT_YI_SYLLABLE_KUOX L"\ua203" #define UNICODE_YI_SYLLABLE_KUO 0xa204 #define UNITEXT_YI_SYLLABLE_KUO L"\ua204" #define UNICODE_YI_SYLLABLE_KUOP 0xa205 #define UNITEXT_YI_SYLLABLE_KUOP L"\ua205" #define UNICODE_YI_SYLLABLE_KOT 0xa206 #define UNITEXT_YI_SYLLABLE_KOT L"\ua206" #define UNICODE_YI_SYLLABLE_KOX 0xa207 #define UNITEXT_YI_SYLLABLE_KOX L"\ua207" #define UNICODE_YI_SYLLABLE_KO 0xa208 #define UNITEXT_YI_SYLLABLE_KO L"\ua208" #define UNICODE_YI_SYLLABLE_KOP 0xa209 #define UNITEXT_YI_SYLLABLE_KOP L"\ua209" #define UNICODE_YI_SYLLABLE_KET 0xa20a #define UNITEXT_YI_SYLLABLE_KET L"\ua20a" #define UNICODE_YI_SYLLABLE_KEX 0xa20b #define UNITEXT_YI_SYLLABLE_KEX L"\ua20b" #define UNICODE_YI_SYLLABLE_KE 0xa20c #define UNITEXT_YI_SYLLABLE_KE L"\ua20c" #define UNICODE_YI_SYLLABLE_KEP 0xa20d #define UNITEXT_YI_SYLLABLE_KEP L"\ua20d" #define UNICODE_YI_SYLLABLE_KUT 0xa20e #define UNITEXT_YI_SYLLABLE_KUT L"\ua20e" #define UNICODE_YI_SYLLABLE_KUX 0xa20f #define UNITEXT_YI_SYLLABLE_KUX L"\ua20f" #define UNICODE_YI_SYLLABLE_KU 0xa210 #define UNITEXT_YI_SYLLABLE_KU L"\ua210" #define UNICODE_YI_SYLLABLE_KUP 0xa211 #define UNITEXT_YI_SYLLABLE_KUP L"\ua211" #define UNICODE_YI_SYLLABLE_KURX 0xa212 #define UNITEXT_YI_SYLLABLE_KURX L"\ua212" #define UNICODE_YI_SYLLABLE_KUR 0xa213 #define UNITEXT_YI_SYLLABLE_KUR L"\ua213" #define UNICODE_YI_SYLLABLE_GGIT 0xa214 #define UNITEXT_YI_SYLLABLE_GGIT L"\ua214" #define UNICODE_YI_SYLLABLE_GGIX 0xa215 #define UNITEXT_YI_SYLLABLE_GGIX L"\ua215" #define UNICODE_YI_SYLLABLE_GGI 0xa216 #define UNITEXT_YI_SYLLABLE_GGI L"\ua216" #define UNICODE_YI_SYLLABLE_GGIEX 0xa217 #define UNITEXT_YI_SYLLABLE_GGIEX L"\ua217" #define UNICODE_YI_SYLLABLE_GGIE 0xa218 #define UNITEXT_YI_SYLLABLE_GGIE L"\ua218" #define UNICODE_YI_SYLLABLE_GGIEP 0xa219 #define UNITEXT_YI_SYLLABLE_GGIEP L"\ua219" #define UNICODE_YI_SYLLABLE_GGAT 0xa21a #define UNITEXT_YI_SYLLABLE_GGAT L"\ua21a" #define UNICODE_YI_SYLLABLE_GGAX 0xa21b #define UNITEXT_YI_SYLLABLE_GGAX L"\ua21b" #define UNICODE_YI_SYLLABLE_GGA 0xa21c #define UNITEXT_YI_SYLLABLE_GGA L"\ua21c" #define UNICODE_YI_SYLLABLE_GGAP 0xa21d #define UNITEXT_YI_SYLLABLE_GGAP L"\ua21d" #define UNICODE_YI_SYLLABLE_GGUOT 0xa21e #define UNITEXT_YI_SYLLABLE_GGUOT L"\ua21e" #define UNICODE_YI_SYLLABLE_GGUOX 0xa21f #define UNITEXT_YI_SYLLABLE_GGUOX L"\ua21f" #define UNICODE_YI_SYLLABLE_GGUO 0xa220 #define UNITEXT_YI_SYLLABLE_GGUO L"\ua220" #define UNICODE_YI_SYLLABLE_GGUOP 0xa221 #define UNITEXT_YI_SYLLABLE_GGUOP L"\ua221" #define UNICODE_YI_SYLLABLE_GGOT 0xa222 #define UNITEXT_YI_SYLLABLE_GGOT L"\ua222" #define UNICODE_YI_SYLLABLE_GGOX 0xa223 #define UNITEXT_YI_SYLLABLE_GGOX L"\ua223" #define UNICODE_YI_SYLLABLE_GGO 0xa224 #define UNITEXT_YI_SYLLABLE_GGO L"\ua224" #define UNICODE_YI_SYLLABLE_GGOP 0xa225 #define UNITEXT_YI_SYLLABLE_GGOP L"\ua225" #define UNICODE_YI_SYLLABLE_GGET 0xa226 #define UNITEXT_YI_SYLLABLE_GGET L"\ua226" #define UNICODE_YI_SYLLABLE_GGEX 0xa227 #define UNITEXT_YI_SYLLABLE_GGEX L"\ua227" #define UNICODE_YI_SYLLABLE_GGE 0xa228 #define UNITEXT_YI_SYLLABLE_GGE L"\ua228" #define UNICODE_YI_SYLLABLE_GGEP 0xa229 #define UNITEXT_YI_SYLLABLE_GGEP L"\ua229" #define UNICODE_YI_SYLLABLE_GGUT 0xa22a #define UNITEXT_YI_SYLLABLE_GGUT L"\ua22a" #define UNICODE_YI_SYLLABLE_GGUX 0xa22b #define UNITEXT_YI_SYLLABLE_GGUX L"\ua22b" #define UNICODE_YI_SYLLABLE_GGU 0xa22c #define UNITEXT_YI_SYLLABLE_GGU L"\ua22c" #define UNICODE_YI_SYLLABLE_GGUP 0xa22d #define UNITEXT_YI_SYLLABLE_GGUP L"\ua22d" #define UNICODE_YI_SYLLABLE_GGURX 0xa22e #define UNITEXT_YI_SYLLABLE_GGURX L"\ua22e" #define UNICODE_YI_SYLLABLE_GGUR 0xa22f #define UNITEXT_YI_SYLLABLE_GGUR L"\ua22f" #define UNICODE_YI_SYLLABLE_MGIEX 0xa230 #define UNITEXT_YI_SYLLABLE_MGIEX L"\ua230" #define UNICODE_YI_SYLLABLE_MGIE 0xa231 #define UNITEXT_YI_SYLLABLE_MGIE L"\ua231" #define UNICODE_YI_SYLLABLE_MGAT 0xa232 #define UNITEXT_YI_SYLLABLE_MGAT L"\ua232" #define UNICODE_YI_SYLLABLE_MGAX 0xa233 #define UNITEXT_YI_SYLLABLE_MGAX L"\ua233" #define UNICODE_YI_SYLLABLE_MGA 0xa234 #define UNITEXT_YI_SYLLABLE_MGA L"\ua234" #define UNICODE_YI_SYLLABLE_MGAP 0xa235 #define UNITEXT_YI_SYLLABLE_MGAP L"\ua235" #define UNICODE_YI_SYLLABLE_MGUOX 0xa236 #define UNITEXT_YI_SYLLABLE_MGUOX L"\ua236" #define UNICODE_YI_SYLLABLE_MGUO 0xa237 #define UNITEXT_YI_SYLLABLE_MGUO L"\ua237" #define UNICODE_YI_SYLLABLE_MGUOP 0xa238 #define UNITEXT_YI_SYLLABLE_MGUOP L"\ua238" #define UNICODE_YI_SYLLABLE_MGOT 0xa239 #define UNITEXT_YI_SYLLABLE_MGOT L"\ua239" #define UNICODE_YI_SYLLABLE_MGOX 0xa23a #define UNITEXT_YI_SYLLABLE_MGOX L"\ua23a" #define UNICODE_YI_SYLLABLE_MGO 0xa23b #define UNITEXT_YI_SYLLABLE_MGO L"\ua23b" #define UNICODE_YI_SYLLABLE_MGOP 0xa23c #define UNITEXT_YI_SYLLABLE_MGOP L"\ua23c" #define UNICODE_YI_SYLLABLE_MGEX 0xa23d #define UNITEXT_YI_SYLLABLE_MGEX L"\ua23d" #define UNICODE_YI_SYLLABLE_MGE 0xa23e #define UNITEXT_YI_SYLLABLE_MGE L"\ua23e" #define UNICODE_YI_SYLLABLE_MGEP 0xa23f #define UNITEXT_YI_SYLLABLE_MGEP L"\ua23f" #define UNICODE_YI_SYLLABLE_MGUT 0xa240 #define UNITEXT_YI_SYLLABLE_MGUT L"\ua240" #define UNICODE_YI_SYLLABLE_MGUX 0xa241 #define UNITEXT_YI_SYLLABLE_MGUX L"\ua241" #define UNICODE_YI_SYLLABLE_MGU 0xa242 #define UNITEXT_YI_SYLLABLE_MGU L"\ua242" #define UNICODE_YI_SYLLABLE_MGUP 0xa243 #define UNITEXT_YI_SYLLABLE_MGUP L"\ua243" #define UNICODE_YI_SYLLABLE_MGURX 0xa244 #define UNITEXT_YI_SYLLABLE_MGURX L"\ua244" #define UNICODE_YI_SYLLABLE_MGUR 0xa245 #define UNITEXT_YI_SYLLABLE_MGUR L"\ua245" #define UNICODE_YI_SYLLABLE_HXIT 0xa246 #define UNITEXT_YI_SYLLABLE_HXIT L"\ua246" #define UNICODE_YI_SYLLABLE_HXIX 0xa247 #define UNITEXT_YI_SYLLABLE_HXIX L"\ua247" #define UNICODE_YI_SYLLABLE_HXI 0xa248 #define UNITEXT_YI_SYLLABLE_HXI L"\ua248" #define UNICODE_YI_SYLLABLE_HXIP 0xa249 #define UNITEXT_YI_SYLLABLE_HXIP L"\ua249" #define UNICODE_YI_SYLLABLE_HXIET 0xa24a #define UNITEXT_YI_SYLLABLE_HXIET L"\ua24a" #define UNICODE_YI_SYLLABLE_HXIEX 0xa24b #define UNITEXT_YI_SYLLABLE_HXIEX L"\ua24b" #define UNICODE_YI_SYLLABLE_HXIE 0xa24c #define UNITEXT_YI_SYLLABLE_HXIE L"\ua24c" #define UNICODE_YI_SYLLABLE_HXIEP 0xa24d #define UNITEXT_YI_SYLLABLE_HXIEP L"\ua24d" #define UNICODE_YI_SYLLABLE_HXAT 0xa24e #define UNITEXT_YI_SYLLABLE_HXAT L"\ua24e" #define UNICODE_YI_SYLLABLE_HXAX 0xa24f #define UNITEXT_YI_SYLLABLE_HXAX L"\ua24f" #define UNICODE_YI_SYLLABLE_HXA 0xa250 #define UNITEXT_YI_SYLLABLE_HXA L"\ua250" #define UNICODE_YI_SYLLABLE_HXAP 0xa251 #define UNITEXT_YI_SYLLABLE_HXAP L"\ua251" #define UNICODE_YI_SYLLABLE_HXUOT 0xa252 #define UNITEXT_YI_SYLLABLE_HXUOT L"\ua252" #define UNICODE_YI_SYLLABLE_HXUOX 0xa253 #define UNITEXT_YI_SYLLABLE_HXUOX L"\ua253" #define UNICODE_YI_SYLLABLE_HXUO 0xa254 #define UNITEXT_YI_SYLLABLE_HXUO L"\ua254" #define UNICODE_YI_SYLLABLE_HXUOP 0xa255 #define UNITEXT_YI_SYLLABLE_HXUOP L"\ua255" #define UNICODE_YI_SYLLABLE_HXOT 0xa256 #define UNITEXT_YI_SYLLABLE_HXOT L"\ua256" #define UNICODE_YI_SYLLABLE_HXOX 0xa257 #define UNITEXT_YI_SYLLABLE_HXOX L"\ua257" #define UNICODE_YI_SYLLABLE_HXO 0xa258 #define UNITEXT_YI_SYLLABLE_HXO L"\ua258" #define UNICODE_YI_SYLLABLE_HXOP 0xa259 #define UNITEXT_YI_SYLLABLE_HXOP L"\ua259" #define UNICODE_YI_SYLLABLE_HXEX 0xa25a #define UNITEXT_YI_SYLLABLE_HXEX L"\ua25a" #define UNICODE_YI_SYLLABLE_HXE 0xa25b #define UNITEXT_YI_SYLLABLE_HXE L"\ua25b" #define UNICODE_YI_SYLLABLE_HXEP 0xa25c #define UNITEXT_YI_SYLLABLE_HXEP L"\ua25c" #define UNICODE_YI_SYLLABLE_NGIEX 0xa25d #define UNITEXT_YI_SYLLABLE_NGIEX L"\ua25d" #define UNICODE_YI_SYLLABLE_NGIE 0xa25e #define UNITEXT_YI_SYLLABLE_NGIE L"\ua25e" #define UNICODE_YI_SYLLABLE_NGIEP 0xa25f #define UNITEXT_YI_SYLLABLE_NGIEP L"\ua25f" #define UNICODE_YI_SYLLABLE_NGAT 0xa260 #define UNITEXT_YI_SYLLABLE_NGAT L"\ua260" #define UNICODE_YI_SYLLABLE_NGAX 0xa261 #define UNITEXT_YI_SYLLABLE_NGAX L"\ua261" #define UNICODE_YI_SYLLABLE_NGA 0xa262 #define UNITEXT_YI_SYLLABLE_NGA L"\ua262" #define UNICODE_YI_SYLLABLE_NGAP 0xa263 #define UNITEXT_YI_SYLLABLE_NGAP L"\ua263" #define UNICODE_YI_SYLLABLE_NGUOT 0xa264 #define UNITEXT_YI_SYLLABLE_NGUOT L"\ua264" #define UNICODE_YI_SYLLABLE_NGUOX 0xa265 #define UNITEXT_YI_SYLLABLE_NGUOX L"\ua265" #define UNICODE_YI_SYLLABLE_NGUO 0xa266 #define UNITEXT_YI_SYLLABLE_NGUO L"\ua266" #define UNICODE_YI_SYLLABLE_NGOT 0xa267 #define UNITEXT_YI_SYLLABLE_NGOT L"\ua267" #define UNICODE_YI_SYLLABLE_NGOX 0xa268 #define UNITEXT_YI_SYLLABLE_NGOX L"\ua268" #define UNICODE_YI_SYLLABLE_NGO 0xa269 #define UNITEXT_YI_SYLLABLE_NGO L"\ua269" #define UNICODE_YI_SYLLABLE_NGOP 0xa26a #define UNITEXT_YI_SYLLABLE_NGOP L"\ua26a" #define UNICODE_YI_SYLLABLE_NGEX 0xa26b #define UNITEXT_YI_SYLLABLE_NGEX L"\ua26b" #define UNICODE_YI_SYLLABLE_NGE 0xa26c #define UNITEXT_YI_SYLLABLE_NGE L"\ua26c" #define UNICODE_YI_SYLLABLE_NGEP 0xa26d #define UNITEXT_YI_SYLLABLE_NGEP L"\ua26d" #define UNICODE_YI_SYLLABLE_HIT 0xa26e #define UNITEXT_YI_SYLLABLE_HIT L"\ua26e" #define UNICODE_YI_SYLLABLE_HIEX 0xa26f #define UNITEXT_YI_SYLLABLE_HIEX L"\ua26f" #define UNICODE_YI_SYLLABLE_HIE 0xa270 #define UNITEXT_YI_SYLLABLE_HIE L"\ua270" #define UNICODE_YI_SYLLABLE_HAT 0xa271 #define UNITEXT_YI_SYLLABLE_HAT L"\ua271" #define UNICODE_YI_SYLLABLE_HAX 0xa272 #define UNITEXT_YI_SYLLABLE_HAX L"\ua272" #define UNICODE_YI_SYLLABLE_HA 0xa273 #define UNITEXT_YI_SYLLABLE_HA L"\ua273" #define UNICODE_YI_SYLLABLE_HAP 0xa274 #define UNITEXT_YI_SYLLABLE_HAP L"\ua274" #define UNICODE_YI_SYLLABLE_HUOT 0xa275 #define UNITEXT_YI_SYLLABLE_HUOT L"\ua275" #define UNICODE_YI_SYLLABLE_HUOX 0xa276 #define UNITEXT_YI_SYLLABLE_HUOX L"\ua276" #define UNICODE_YI_SYLLABLE_HUO 0xa277 #define UNITEXT_YI_SYLLABLE_HUO L"\ua277" #define UNICODE_YI_SYLLABLE_HUOP 0xa278 #define UNITEXT_YI_SYLLABLE_HUOP L"\ua278" #define UNICODE_YI_SYLLABLE_HOT 0xa279 #define UNITEXT_YI_SYLLABLE_HOT L"\ua279" #define UNICODE_YI_SYLLABLE_HOX 0xa27a #define UNITEXT_YI_SYLLABLE_HOX L"\ua27a" #define UNICODE_YI_SYLLABLE_HO 0xa27b #define UNITEXT_YI_SYLLABLE_HO L"\ua27b" #define UNICODE_YI_SYLLABLE_HOP 0xa27c #define UNITEXT_YI_SYLLABLE_HOP L"\ua27c" #define UNICODE_YI_SYLLABLE_HEX 0xa27d #define UNITEXT_YI_SYLLABLE_HEX L"\ua27d" #define UNICODE_YI_SYLLABLE_HE 0xa27e #define UNITEXT_YI_SYLLABLE_HE L"\ua27e" #define UNICODE_YI_SYLLABLE_HEP 0xa27f #define UNITEXT_YI_SYLLABLE_HEP L"\ua27f" #define UNICODE_YI_SYLLABLE_WAT 0xa280 #define UNITEXT_YI_SYLLABLE_WAT L"\ua280" #define UNICODE_YI_SYLLABLE_WAX 0xa281 #define UNITEXT_YI_SYLLABLE_WAX L"\ua281" #define UNICODE_YI_SYLLABLE_WA 0xa282 #define UNITEXT_YI_SYLLABLE_WA L"\ua282" #define UNICODE_YI_SYLLABLE_WAP 0xa283 #define UNITEXT_YI_SYLLABLE_WAP L"\ua283" #define UNICODE_YI_SYLLABLE_WUOX 0xa284 #define UNITEXT_YI_SYLLABLE_WUOX L"\ua284" #define UNICODE_YI_SYLLABLE_WUO 0xa285 #define UNITEXT_YI_SYLLABLE_WUO L"\ua285" #define UNICODE_YI_SYLLABLE_WUOP 0xa286 #define UNITEXT_YI_SYLLABLE_WUOP L"\ua286" #define UNICODE_YI_SYLLABLE_WOX 0xa287 #define UNITEXT_YI_SYLLABLE_WOX L"\ua287" #define UNICODE_YI_SYLLABLE_WO 0xa288 #define UNITEXT_YI_SYLLABLE_WO L"\ua288" #define UNICODE_YI_SYLLABLE_WOP 0xa289 #define UNITEXT_YI_SYLLABLE_WOP L"\ua289" #define UNICODE_YI_SYLLABLE_WEX 0xa28a #define UNITEXT_YI_SYLLABLE_WEX L"\ua28a" #define UNICODE_YI_SYLLABLE_WE 0xa28b #define UNITEXT_YI_SYLLABLE_WE L"\ua28b" #define UNICODE_YI_SYLLABLE_WEP 0xa28c #define UNITEXT_YI_SYLLABLE_WEP L"\ua28c" #define UNICODE_YI_SYLLABLE_ZIT 0xa28d #define UNITEXT_YI_SYLLABLE_ZIT L"\ua28d" #define UNICODE_YI_SYLLABLE_ZIX 0xa28e #define UNITEXT_YI_SYLLABLE_ZIX L"\ua28e" #define UNICODE_YI_SYLLABLE_ZI 0xa28f #define UNITEXT_YI_SYLLABLE_ZI L"\ua28f" #define UNICODE_YI_SYLLABLE_ZIP 0xa290 #define UNITEXT_YI_SYLLABLE_ZIP L"\ua290" #define UNICODE_YI_SYLLABLE_ZIEX 0xa291 #define UNITEXT_YI_SYLLABLE_ZIEX L"\ua291" #define UNICODE_YI_SYLLABLE_ZIE 0xa292 #define UNITEXT_YI_SYLLABLE_ZIE L"\ua292" #define UNICODE_YI_SYLLABLE_ZIEP 0xa293 #define UNITEXT_YI_SYLLABLE_ZIEP L"\ua293" #define UNICODE_YI_SYLLABLE_ZAT 0xa294 #define UNITEXT_YI_SYLLABLE_ZAT L"\ua294" #define UNICODE_YI_SYLLABLE_ZAX 0xa295 #define UNITEXT_YI_SYLLABLE_ZAX L"\ua295" #define UNICODE_YI_SYLLABLE_ZA 0xa296 #define UNITEXT_YI_SYLLABLE_ZA L"\ua296" #define UNICODE_YI_SYLLABLE_ZAP 0xa297 #define UNITEXT_YI_SYLLABLE_ZAP L"\ua297" #define UNICODE_YI_SYLLABLE_ZUOX 0xa298 #define UNITEXT_YI_SYLLABLE_ZUOX L"\ua298" #define UNICODE_YI_SYLLABLE_ZUO 0xa299 #define UNITEXT_YI_SYLLABLE_ZUO L"\ua299" #define UNICODE_YI_SYLLABLE_ZUOP 0xa29a #define UNITEXT_YI_SYLLABLE_ZUOP L"\ua29a" #define UNICODE_YI_SYLLABLE_ZOT 0xa29b #define UNITEXT_YI_SYLLABLE_ZOT L"\ua29b" #define UNICODE_YI_SYLLABLE_ZOX 0xa29c #define UNITEXT_YI_SYLLABLE_ZOX L"\ua29c" #define UNICODE_YI_SYLLABLE_ZO 0xa29d #define UNITEXT_YI_SYLLABLE_ZO L"\ua29d" #define UNICODE_YI_SYLLABLE_ZOP 0xa29e #define UNITEXT_YI_SYLLABLE_ZOP L"\ua29e" #define UNICODE_YI_SYLLABLE_ZEX 0xa29f #define UNITEXT_YI_SYLLABLE_ZEX L"\ua29f" #define UNICODE_YI_SYLLABLE_ZE 0xa2a0 #define UNITEXT_YI_SYLLABLE_ZE L"\ua2a0" #define UNICODE_YI_SYLLABLE_ZEP 0xa2a1 #define UNITEXT_YI_SYLLABLE_ZEP L"\ua2a1" #define UNICODE_YI_SYLLABLE_ZUT 0xa2a2 #define UNITEXT_YI_SYLLABLE_ZUT L"\ua2a2" #define UNICODE_YI_SYLLABLE_ZUX 0xa2a3 #define UNITEXT_YI_SYLLABLE_ZUX L"\ua2a3" #define UNICODE_YI_SYLLABLE_ZU 0xa2a4 #define UNITEXT_YI_SYLLABLE_ZU L"\ua2a4" #define UNICODE_YI_SYLLABLE_ZUP 0xa2a5 #define UNITEXT_YI_SYLLABLE_ZUP L"\ua2a5" #define UNICODE_YI_SYLLABLE_ZURX 0xa2a6 #define UNITEXT_YI_SYLLABLE_ZURX L"\ua2a6" #define UNICODE_YI_SYLLABLE_ZUR 0xa2a7 #define UNITEXT_YI_SYLLABLE_ZUR L"\ua2a7" #define UNICODE_YI_SYLLABLE_ZYT 0xa2a8 #define UNITEXT_YI_SYLLABLE_ZYT L"\ua2a8" #define UNICODE_YI_SYLLABLE_ZYX 0xa2a9 #define UNITEXT_YI_SYLLABLE_ZYX L"\ua2a9" #define UNICODE_YI_SYLLABLE_ZY 0xa2aa #define UNITEXT_YI_SYLLABLE_ZY L"\ua2aa" #define UNICODE_YI_SYLLABLE_ZYP 0xa2ab #define UNITEXT_YI_SYLLABLE_ZYP L"\ua2ab" #define UNICODE_YI_SYLLABLE_ZYRX 0xa2ac #define UNITEXT_YI_SYLLABLE_ZYRX L"\ua2ac" #define UNICODE_YI_SYLLABLE_ZYR 0xa2ad #define UNITEXT_YI_SYLLABLE_ZYR L"\ua2ad" #define UNICODE_YI_SYLLABLE_CIT 0xa2ae #define UNITEXT_YI_SYLLABLE_CIT L"\ua2ae" #define UNICODE_YI_SYLLABLE_CIX 0xa2af #define UNITEXT_YI_SYLLABLE_CIX L"\ua2af" #define UNICODE_YI_SYLLABLE_CI 0xa2b0 #define UNITEXT_YI_SYLLABLE_CI L"\ua2b0" #define UNICODE_YI_SYLLABLE_CIP 0xa2b1 #define UNITEXT_YI_SYLLABLE_CIP L"\ua2b1" #define UNICODE_YI_SYLLABLE_CIET 0xa2b2 #define UNITEXT_YI_SYLLABLE_CIET L"\ua2b2" #define UNICODE_YI_SYLLABLE_CIEX 0xa2b3 #define UNITEXT_YI_SYLLABLE_CIEX L"\ua2b3" #define UNICODE_YI_SYLLABLE_CIE 0xa2b4 #define UNITEXT_YI_SYLLABLE_CIE L"\ua2b4" #define UNICODE_YI_SYLLABLE_CIEP 0xa2b5 #define UNITEXT_YI_SYLLABLE_CIEP L"\ua2b5" #define UNICODE_YI_SYLLABLE_CAT 0xa2b6 #define UNITEXT_YI_SYLLABLE_CAT L"\ua2b6" #define UNICODE_YI_SYLLABLE_CAX 0xa2b7 #define UNITEXT_YI_SYLLABLE_CAX L"\ua2b7" #define UNICODE_YI_SYLLABLE_CA 0xa2b8 #define UNITEXT_YI_SYLLABLE_CA L"\ua2b8" #define UNICODE_YI_SYLLABLE_CAP 0xa2b9 #define UNITEXT_YI_SYLLABLE_CAP L"\ua2b9" #define UNICODE_YI_SYLLABLE_CUOX 0xa2ba #define UNITEXT_YI_SYLLABLE_CUOX L"\ua2ba" #define UNICODE_YI_SYLLABLE_CUO 0xa2bb #define UNITEXT_YI_SYLLABLE_CUO L"\ua2bb" #define UNICODE_YI_SYLLABLE_CUOP 0xa2bc #define UNITEXT_YI_SYLLABLE_CUOP L"\ua2bc" #define UNICODE_YI_SYLLABLE_COT 0xa2bd #define UNITEXT_YI_SYLLABLE_COT L"\ua2bd" #define UNICODE_YI_SYLLABLE_COX 0xa2be #define UNITEXT_YI_SYLLABLE_COX L"\ua2be" #define UNICODE_YI_SYLLABLE_CO 0xa2bf #define UNITEXT_YI_SYLLABLE_CO L"\ua2bf" #define UNICODE_YI_SYLLABLE_COP 0xa2c0 #define UNITEXT_YI_SYLLABLE_COP L"\ua2c0" #define UNICODE_YI_SYLLABLE_CEX 0xa2c1 #define UNITEXT_YI_SYLLABLE_CEX L"\ua2c1" #define UNICODE_YI_SYLLABLE_CE 0xa2c2 #define UNITEXT_YI_SYLLABLE_CE L"\ua2c2" #define UNICODE_YI_SYLLABLE_CEP 0xa2c3 #define UNITEXT_YI_SYLLABLE_CEP L"\ua2c3" #define UNICODE_YI_SYLLABLE_CUT 0xa2c4 #define UNITEXT_YI_SYLLABLE_CUT L"\ua2c4" #define UNICODE_YI_SYLLABLE_CUX 0xa2c5 #define UNITEXT_YI_SYLLABLE_CUX L"\ua2c5" #define UNICODE_YI_SYLLABLE_CU 0xa2c6 #define UNITEXT_YI_SYLLABLE_CU L"\ua2c6" #define UNICODE_YI_SYLLABLE_CUP 0xa2c7 #define UNITEXT_YI_SYLLABLE_CUP L"\ua2c7" #define UNICODE_YI_SYLLABLE_CURX 0xa2c8 #define UNITEXT_YI_SYLLABLE_CURX L"\ua2c8" #define UNICODE_YI_SYLLABLE_CUR 0xa2c9 #define UNITEXT_YI_SYLLABLE_CUR L"\ua2c9" #define UNICODE_YI_SYLLABLE_CYT 0xa2ca #define UNITEXT_YI_SYLLABLE_CYT L"\ua2ca" #define UNICODE_YI_SYLLABLE_CYX 0xa2cb #define UNITEXT_YI_SYLLABLE_CYX L"\ua2cb" #define UNICODE_YI_SYLLABLE_CY 0xa2cc #define UNITEXT_YI_SYLLABLE_CY L"\ua2cc" #define UNICODE_YI_SYLLABLE_CYP 0xa2cd #define UNITEXT_YI_SYLLABLE_CYP L"\ua2cd" #define UNICODE_YI_SYLLABLE_CYRX 0xa2ce #define UNITEXT_YI_SYLLABLE_CYRX L"\ua2ce" #define UNICODE_YI_SYLLABLE_CYR 0xa2cf #define UNITEXT_YI_SYLLABLE_CYR L"\ua2cf" #define UNICODE_YI_SYLLABLE_ZZIT 0xa2d0 #define UNITEXT_YI_SYLLABLE_ZZIT L"\ua2d0" #define UNICODE_YI_SYLLABLE_ZZIX 0xa2d1 #define UNITEXT_YI_SYLLABLE_ZZIX L"\ua2d1" #define UNICODE_YI_SYLLABLE_ZZI 0xa2d2 #define UNITEXT_YI_SYLLABLE_ZZI L"\ua2d2" #define UNICODE_YI_SYLLABLE_ZZIP 0xa2d3 #define UNITEXT_YI_SYLLABLE_ZZIP L"\ua2d3" #define UNICODE_YI_SYLLABLE_ZZIET 0xa2d4 #define UNITEXT_YI_SYLLABLE_ZZIET L"\ua2d4" #define UNICODE_YI_SYLLABLE_ZZIEX 0xa2d5 #define UNITEXT_YI_SYLLABLE_ZZIEX L"\ua2d5" #define UNICODE_YI_SYLLABLE_ZZIE 0xa2d6 #define UNITEXT_YI_SYLLABLE_ZZIE L"\ua2d6" #define UNICODE_YI_SYLLABLE_ZZIEP 0xa2d7 #define UNITEXT_YI_SYLLABLE_ZZIEP L"\ua2d7" #define UNICODE_YI_SYLLABLE_ZZAT 0xa2d8 #define UNITEXT_YI_SYLLABLE_ZZAT L"\ua2d8" #define UNICODE_YI_SYLLABLE_ZZAX 0xa2d9 #define UNITEXT_YI_SYLLABLE_ZZAX L"\ua2d9" #define UNICODE_YI_SYLLABLE_ZZA 0xa2da #define UNITEXT_YI_SYLLABLE_ZZA L"\ua2da" #define UNICODE_YI_SYLLABLE_ZZAP 0xa2db #define UNITEXT_YI_SYLLABLE_ZZAP L"\ua2db" #define UNICODE_YI_SYLLABLE_ZZOX 0xa2dc #define UNITEXT_YI_SYLLABLE_ZZOX L"\ua2dc" #define UNICODE_YI_SYLLABLE_ZZO 0xa2dd #define UNITEXT_YI_SYLLABLE_ZZO L"\ua2dd" #define UNICODE_YI_SYLLABLE_ZZOP 0xa2de #define UNITEXT_YI_SYLLABLE_ZZOP L"\ua2de" #define UNICODE_YI_SYLLABLE_ZZEX 0xa2df #define UNITEXT_YI_SYLLABLE_ZZEX L"\ua2df" #define UNICODE_YI_SYLLABLE_ZZE 0xa2e0 #define UNITEXT_YI_SYLLABLE_ZZE L"\ua2e0" #define UNICODE_YI_SYLLABLE_ZZEP 0xa2e1 #define UNITEXT_YI_SYLLABLE_ZZEP L"\ua2e1" #define UNICODE_YI_SYLLABLE_ZZUX 0xa2e2 #define UNITEXT_YI_SYLLABLE_ZZUX L"\ua2e2" #define UNICODE_YI_SYLLABLE_ZZU 0xa2e3 #define UNITEXT_YI_SYLLABLE_ZZU L"\ua2e3" #define UNICODE_YI_SYLLABLE_ZZUP 0xa2e4 #define UNITEXT_YI_SYLLABLE_ZZUP L"\ua2e4" #define UNICODE_YI_SYLLABLE_ZZURX 0xa2e5 #define UNITEXT_YI_SYLLABLE_ZZURX L"\ua2e5" #define UNICODE_YI_SYLLABLE_ZZUR 0xa2e6 #define UNITEXT_YI_SYLLABLE_ZZUR L"\ua2e6" #define UNICODE_YI_SYLLABLE_ZZYT 0xa2e7 #define UNITEXT_YI_SYLLABLE_ZZYT L"\ua2e7" #define UNICODE_YI_SYLLABLE_ZZYX 0xa2e8 #define UNITEXT_YI_SYLLABLE_ZZYX L"\ua2e8" #define UNICODE_YI_SYLLABLE_ZZY 0xa2e9 #define UNITEXT_YI_SYLLABLE_ZZY L"\ua2e9" #define UNICODE_YI_SYLLABLE_ZZYP 0xa2ea #define UNITEXT_YI_SYLLABLE_ZZYP L"\ua2ea" #define UNICODE_YI_SYLLABLE_ZZYRX 0xa2eb #define UNITEXT_YI_SYLLABLE_ZZYRX L"\ua2eb" #define UNICODE_YI_SYLLABLE_ZZYR 0xa2ec #define UNITEXT_YI_SYLLABLE_ZZYR L"\ua2ec" #define UNICODE_YI_SYLLABLE_NZIT 0xa2ed #define UNITEXT_YI_SYLLABLE_NZIT L"\ua2ed" #define UNICODE_YI_SYLLABLE_NZIX 0xa2ee #define UNITEXT_YI_SYLLABLE_NZIX L"\ua2ee" #define UNICODE_YI_SYLLABLE_NZI 0xa2ef #define UNITEXT_YI_SYLLABLE_NZI L"\ua2ef" #define UNICODE_YI_SYLLABLE_NZIP 0xa2f0 #define UNITEXT_YI_SYLLABLE_NZIP L"\ua2f0" #define UNICODE_YI_SYLLABLE_NZIEX 0xa2f1 #define UNITEXT_YI_SYLLABLE_NZIEX L"\ua2f1" #define UNICODE_YI_SYLLABLE_NZIE 0xa2f2 #define UNITEXT_YI_SYLLABLE_NZIE L"\ua2f2" #define UNICODE_YI_SYLLABLE_NZIEP 0xa2f3 #define UNITEXT_YI_SYLLABLE_NZIEP L"\ua2f3" #define UNICODE_YI_SYLLABLE_NZAT 0xa2f4 #define UNITEXT_YI_SYLLABLE_NZAT L"\ua2f4" #define UNICODE_YI_SYLLABLE_NZAX 0xa2f5 #define UNITEXT_YI_SYLLABLE_NZAX L"\ua2f5" #define UNICODE_YI_SYLLABLE_NZA 0xa2f6 #define UNITEXT_YI_SYLLABLE_NZA L"\ua2f6" #define UNICODE_YI_SYLLABLE_NZAP 0xa2f7 #define UNITEXT_YI_SYLLABLE_NZAP L"\ua2f7" #define UNICODE_YI_SYLLABLE_NZUOX 0xa2f8 #define UNITEXT_YI_SYLLABLE_NZUOX L"\ua2f8" #define UNICODE_YI_SYLLABLE_NZUO 0xa2f9 #define UNITEXT_YI_SYLLABLE_NZUO L"\ua2f9" #define UNICODE_YI_SYLLABLE_NZOX 0xa2fa #define UNITEXT_YI_SYLLABLE_NZOX L"\ua2fa" #define UNICODE_YI_SYLLABLE_NZOP 0xa2fb #define UNITEXT_YI_SYLLABLE_NZOP L"\ua2fb" #define UNICODE_YI_SYLLABLE_NZEX 0xa2fc #define UNITEXT_YI_SYLLABLE_NZEX L"\ua2fc" #define UNICODE_YI_SYLLABLE_NZE 0xa2fd #define UNITEXT_YI_SYLLABLE_NZE L"\ua2fd" #define UNICODE_YI_SYLLABLE_NZUX 0xa2fe #define UNITEXT_YI_SYLLABLE_NZUX L"\ua2fe" #define UNICODE_YI_SYLLABLE_NZU 0xa2ff #define UNITEXT_YI_SYLLABLE_NZU L"\ua2ff" #define UNICODE_YI_SYLLABLE_NZUP 0xa300 #define UNITEXT_YI_SYLLABLE_NZUP L"\ua300" #define UNICODE_YI_SYLLABLE_NZURX 0xa301 #define UNITEXT_YI_SYLLABLE_NZURX L"\ua301" #define UNICODE_YI_SYLLABLE_NZUR 0xa302 #define UNITEXT_YI_SYLLABLE_NZUR L"\ua302" #define UNICODE_YI_SYLLABLE_NZYT 0xa303 #define UNITEXT_YI_SYLLABLE_NZYT L"\ua303" #define UNICODE_YI_SYLLABLE_NZYX 0xa304 #define UNITEXT_YI_SYLLABLE_NZYX L"\ua304" #define UNICODE_YI_SYLLABLE_NZY 0xa305 #define UNITEXT_YI_SYLLABLE_NZY L"\ua305" #define UNICODE_YI_SYLLABLE_NZYP 0xa306 #define UNITEXT_YI_SYLLABLE_NZYP L"\ua306" #define UNICODE_YI_SYLLABLE_NZYRX 0xa307 #define UNITEXT_YI_SYLLABLE_NZYRX L"\ua307" #define UNICODE_YI_SYLLABLE_NZYR 0xa308 #define UNITEXT_YI_SYLLABLE_NZYR L"\ua308" #define UNICODE_YI_SYLLABLE_SIT 0xa309 #define UNITEXT_YI_SYLLABLE_SIT L"\ua309" #define UNICODE_YI_SYLLABLE_SIX 0xa30a #define UNITEXT_YI_SYLLABLE_SIX L"\ua30a" #define UNICODE_YI_SYLLABLE_SI 0xa30b #define UNITEXT_YI_SYLLABLE_SI L"\ua30b" #define UNICODE_YI_SYLLABLE_SIP 0xa30c #define UNITEXT_YI_SYLLABLE_SIP L"\ua30c" #define UNICODE_YI_SYLLABLE_SIEX 0xa30d #define UNITEXT_YI_SYLLABLE_SIEX L"\ua30d" #define UNICODE_YI_SYLLABLE_SIE 0xa30e #define UNITEXT_YI_SYLLABLE_SIE L"\ua30e" #define UNICODE_YI_SYLLABLE_SIEP 0xa30f #define UNITEXT_YI_SYLLABLE_SIEP L"\ua30f" #define UNICODE_YI_SYLLABLE_SAT 0xa310 #define UNITEXT_YI_SYLLABLE_SAT L"\ua310" #define UNICODE_YI_SYLLABLE_SAX 0xa311 #define UNITEXT_YI_SYLLABLE_SAX L"\ua311" #define UNICODE_YI_SYLLABLE_SA 0xa312 #define UNITEXT_YI_SYLLABLE_SA L"\ua312" #define UNICODE_YI_SYLLABLE_SAP 0xa313 #define UNITEXT_YI_SYLLABLE_SAP L"\ua313" #define UNICODE_YI_SYLLABLE_SUOX 0xa314 #define UNITEXT_YI_SYLLABLE_SUOX L"\ua314" #define UNICODE_YI_SYLLABLE_SUO 0xa315 #define UNITEXT_YI_SYLLABLE_SUO L"\ua315" #define UNICODE_YI_SYLLABLE_SUOP 0xa316 #define UNITEXT_YI_SYLLABLE_SUOP L"\ua316" #define UNICODE_YI_SYLLABLE_SOT 0xa317 #define UNITEXT_YI_SYLLABLE_SOT L"\ua317" #define UNICODE_YI_SYLLABLE_SOX 0xa318 #define UNITEXT_YI_SYLLABLE_SOX L"\ua318" #define UNICODE_YI_SYLLABLE_SO 0xa319 #define UNITEXT_YI_SYLLABLE_SO L"\ua319" #define UNICODE_YI_SYLLABLE_SOP 0xa31a #define UNITEXT_YI_SYLLABLE_SOP L"\ua31a" #define UNICODE_YI_SYLLABLE_SEX 0xa31b #define UNITEXT_YI_SYLLABLE_SEX L"\ua31b" #define UNICODE_YI_SYLLABLE_SE 0xa31c #define UNITEXT_YI_SYLLABLE_SE L"\ua31c" #define UNICODE_YI_SYLLABLE_SEP 0xa31d #define UNITEXT_YI_SYLLABLE_SEP L"\ua31d" #define UNICODE_YI_SYLLABLE_SUT 0xa31e #define UNITEXT_YI_SYLLABLE_SUT L"\ua31e" #define UNICODE_YI_SYLLABLE_SUX 0xa31f #define UNITEXT_YI_SYLLABLE_SUX L"\ua31f" #define UNICODE_YI_SYLLABLE_SU 0xa320 #define UNITEXT_YI_SYLLABLE_SU L"\ua320" #define UNICODE_YI_SYLLABLE_SUP 0xa321 #define UNITEXT_YI_SYLLABLE_SUP L"\ua321" #define UNICODE_YI_SYLLABLE_SURX 0xa322 #define UNITEXT_YI_SYLLABLE_SURX L"\ua322" #define UNICODE_YI_SYLLABLE_SUR 0xa323 #define UNITEXT_YI_SYLLABLE_SUR L"\ua323" #define UNICODE_YI_SYLLABLE_SYT 0xa324 #define UNITEXT_YI_SYLLABLE_SYT L"\ua324" #define UNICODE_YI_SYLLABLE_SYX 0xa325 #define UNITEXT_YI_SYLLABLE_SYX L"\ua325" #define UNICODE_YI_SYLLABLE_SY 0xa326 #define UNITEXT_YI_SYLLABLE_SY L"\ua326" #define UNICODE_YI_SYLLABLE_SYP 0xa327 #define UNITEXT_YI_SYLLABLE_SYP L"\ua327" #define UNICODE_YI_SYLLABLE_SYRX 0xa328 #define UNITEXT_YI_SYLLABLE_SYRX L"\ua328" #define UNICODE_YI_SYLLABLE_SYR 0xa329 #define UNITEXT_YI_SYLLABLE_SYR L"\ua329" #define UNICODE_YI_SYLLABLE_SSIT 0xa32a #define UNITEXT_YI_SYLLABLE_SSIT L"\ua32a" #define UNICODE_YI_SYLLABLE_SSIX 0xa32b #define UNITEXT_YI_SYLLABLE_SSIX L"\ua32b" #define UNICODE_YI_SYLLABLE_SSI 0xa32c #define UNITEXT_YI_SYLLABLE_SSI L"\ua32c" #define UNICODE_YI_SYLLABLE_SSIP 0xa32d #define UNITEXT_YI_SYLLABLE_SSIP L"\ua32d" #define UNICODE_YI_SYLLABLE_SSIEX 0xa32e #define UNITEXT_YI_SYLLABLE_SSIEX L"\ua32e" #define UNICODE_YI_SYLLABLE_SSIE 0xa32f #define UNITEXT_YI_SYLLABLE_SSIE L"\ua32f" #define UNICODE_YI_SYLLABLE_SSIEP 0xa330 #define UNITEXT_YI_SYLLABLE_SSIEP L"\ua330" #define UNICODE_YI_SYLLABLE_SSAT 0xa331 #define UNITEXT_YI_SYLLABLE_SSAT L"\ua331" #define UNICODE_YI_SYLLABLE_SSAX 0xa332 #define UNITEXT_YI_SYLLABLE_SSAX L"\ua332" #define UNICODE_YI_SYLLABLE_SSA 0xa333 #define UNITEXT_YI_SYLLABLE_SSA L"\ua333" #define UNICODE_YI_SYLLABLE_SSAP 0xa334 #define UNITEXT_YI_SYLLABLE_SSAP L"\ua334" #define UNICODE_YI_SYLLABLE_SSOT 0xa335 #define UNITEXT_YI_SYLLABLE_SSOT L"\ua335" #define UNICODE_YI_SYLLABLE_SSOX 0xa336 #define UNITEXT_YI_SYLLABLE_SSOX L"\ua336" #define UNICODE_YI_SYLLABLE_SSO 0xa337 #define UNITEXT_YI_SYLLABLE_SSO L"\ua337" #define UNICODE_YI_SYLLABLE_SSOP 0xa338 #define UNITEXT_YI_SYLLABLE_SSOP L"\ua338" #define UNICODE_YI_SYLLABLE_SSEX 0xa339 #define UNITEXT_YI_SYLLABLE_SSEX L"\ua339" #define UNICODE_YI_SYLLABLE_SSE 0xa33a #define UNITEXT_YI_SYLLABLE_SSE L"\ua33a" #define UNICODE_YI_SYLLABLE_SSEP 0xa33b #define UNITEXT_YI_SYLLABLE_SSEP L"\ua33b" #define UNICODE_YI_SYLLABLE_SSUT 0xa33c #define UNITEXT_YI_SYLLABLE_SSUT L"\ua33c" #define UNICODE_YI_SYLLABLE_SSUX 0xa33d #define UNITEXT_YI_SYLLABLE_SSUX L"\ua33d" #define UNICODE_YI_SYLLABLE_SSU 0xa33e #define UNITEXT_YI_SYLLABLE_SSU L"\ua33e" #define UNICODE_YI_SYLLABLE_SSUP 0xa33f #define UNITEXT_YI_SYLLABLE_SSUP L"\ua33f" #define UNICODE_YI_SYLLABLE_SSYT 0xa340 #define UNITEXT_YI_SYLLABLE_SSYT L"\ua340" #define UNICODE_YI_SYLLABLE_SSYX 0xa341 #define UNITEXT_YI_SYLLABLE_SSYX L"\ua341" #define UNICODE_YI_SYLLABLE_SSY 0xa342 #define UNITEXT_YI_SYLLABLE_SSY L"\ua342" #define UNICODE_YI_SYLLABLE_SSYP 0xa343 #define UNITEXT_YI_SYLLABLE_SSYP L"\ua343" #define UNICODE_YI_SYLLABLE_SSYRX 0xa344 #define UNITEXT_YI_SYLLABLE_SSYRX L"\ua344" #define UNICODE_YI_SYLLABLE_SSYR 0xa345 #define UNITEXT_YI_SYLLABLE_SSYR L"\ua345" #define UNICODE_YI_SYLLABLE_ZHAT 0xa346 #define UNITEXT_YI_SYLLABLE_ZHAT L"\ua346" #define UNICODE_YI_SYLLABLE_ZHAX 0xa347 #define UNITEXT_YI_SYLLABLE_ZHAX L"\ua347" #define UNICODE_YI_SYLLABLE_ZHA 0xa348 #define UNITEXT_YI_SYLLABLE_ZHA L"\ua348" #define UNICODE_YI_SYLLABLE_ZHAP 0xa349 #define UNITEXT_YI_SYLLABLE_ZHAP L"\ua349" #define UNICODE_YI_SYLLABLE_ZHUOX 0xa34a #define UNITEXT_YI_SYLLABLE_ZHUOX L"\ua34a" #define UNICODE_YI_SYLLABLE_ZHUO 0xa34b #define UNITEXT_YI_SYLLABLE_ZHUO L"\ua34b" #define UNICODE_YI_SYLLABLE_ZHUOP 0xa34c #define UNITEXT_YI_SYLLABLE_ZHUOP L"\ua34c" #define UNICODE_YI_SYLLABLE_ZHOT 0xa34d #define UNITEXT_YI_SYLLABLE_ZHOT L"\ua34d" #define UNICODE_YI_SYLLABLE_ZHOX 0xa34e #define UNITEXT_YI_SYLLABLE_ZHOX L"\ua34e" #define UNICODE_YI_SYLLABLE_ZHO 0xa34f #define UNITEXT_YI_SYLLABLE_ZHO L"\ua34f" #define UNICODE_YI_SYLLABLE_ZHOP 0xa350 #define UNITEXT_YI_SYLLABLE_ZHOP L"\ua350" #define UNICODE_YI_SYLLABLE_ZHET 0xa351 #define UNITEXT_YI_SYLLABLE_ZHET L"\ua351" #define UNICODE_YI_SYLLABLE_ZHEX 0xa352 #define UNITEXT_YI_SYLLABLE_ZHEX L"\ua352" #define UNICODE_YI_SYLLABLE_ZHE 0xa353 #define UNITEXT_YI_SYLLABLE_ZHE L"\ua353" #define UNICODE_YI_SYLLABLE_ZHEP 0xa354 #define UNITEXT_YI_SYLLABLE_ZHEP L"\ua354" #define UNICODE_YI_SYLLABLE_ZHUT 0xa355 #define UNITEXT_YI_SYLLABLE_ZHUT L"\ua355" #define UNICODE_YI_SYLLABLE_ZHUX 0xa356 #define UNITEXT_YI_SYLLABLE_ZHUX L"\ua356" #define UNICODE_YI_SYLLABLE_ZHU 0xa357 #define UNITEXT_YI_SYLLABLE_ZHU L"\ua357" #define UNICODE_YI_SYLLABLE_ZHUP 0xa358 #define UNITEXT_YI_SYLLABLE_ZHUP L"\ua358" #define UNICODE_YI_SYLLABLE_ZHURX 0xa359 #define UNITEXT_YI_SYLLABLE_ZHURX L"\ua359" #define UNICODE_YI_SYLLABLE_ZHUR 0xa35a #define UNITEXT_YI_SYLLABLE_ZHUR L"\ua35a" #define UNICODE_YI_SYLLABLE_ZHYT 0xa35b #define UNITEXT_YI_SYLLABLE_ZHYT L"\ua35b" #define UNICODE_YI_SYLLABLE_ZHYX 0xa35c #define UNITEXT_YI_SYLLABLE_ZHYX L"\ua35c" #define UNICODE_YI_SYLLABLE_ZHY 0xa35d #define UNITEXT_YI_SYLLABLE_ZHY L"\ua35d" #define UNICODE_YI_SYLLABLE_ZHYP 0xa35e #define UNITEXT_YI_SYLLABLE_ZHYP L"\ua35e" #define UNICODE_YI_SYLLABLE_ZHYRX 0xa35f #define UNITEXT_YI_SYLLABLE_ZHYRX L"\ua35f" #define UNICODE_YI_SYLLABLE_ZHYR 0xa360 #define UNITEXT_YI_SYLLABLE_ZHYR L"\ua360" #define UNICODE_YI_SYLLABLE_CHAT 0xa361 #define UNITEXT_YI_SYLLABLE_CHAT L"\ua361" #define UNICODE_YI_SYLLABLE_CHAX 0xa362 #define UNITEXT_YI_SYLLABLE_CHAX L"\ua362" #define UNICODE_YI_SYLLABLE_CHA 0xa363 #define UNITEXT_YI_SYLLABLE_CHA L"\ua363" #define UNICODE_YI_SYLLABLE_CHAP 0xa364 #define UNITEXT_YI_SYLLABLE_CHAP L"\ua364" #define UNICODE_YI_SYLLABLE_CHUOT 0xa365 #define UNITEXT_YI_SYLLABLE_CHUOT L"\ua365" #define UNICODE_YI_SYLLABLE_CHUOX 0xa366 #define UNITEXT_YI_SYLLABLE_CHUOX L"\ua366" #define UNICODE_YI_SYLLABLE_CHUO 0xa367 #define UNITEXT_YI_SYLLABLE_CHUO L"\ua367" #define UNICODE_YI_SYLLABLE_CHUOP 0xa368 #define UNITEXT_YI_SYLLABLE_CHUOP L"\ua368" #define UNICODE_YI_SYLLABLE_CHOT 0xa369 #define UNITEXT_YI_SYLLABLE_CHOT L"\ua369" #define UNICODE_YI_SYLLABLE_CHOX 0xa36a #define UNITEXT_YI_SYLLABLE_CHOX L"\ua36a" #define UNICODE_YI_SYLLABLE_CHO 0xa36b #define UNITEXT_YI_SYLLABLE_CHO L"\ua36b" #define UNICODE_YI_SYLLABLE_CHOP 0xa36c #define UNITEXT_YI_SYLLABLE_CHOP L"\ua36c" #define UNICODE_YI_SYLLABLE_CHET 0xa36d #define UNITEXT_YI_SYLLABLE_CHET L"\ua36d" #define UNICODE_YI_SYLLABLE_CHEX 0xa36e #define UNITEXT_YI_SYLLABLE_CHEX L"\ua36e" #define UNICODE_YI_SYLLABLE_CHE 0xa36f #define UNITEXT_YI_SYLLABLE_CHE L"\ua36f" #define UNICODE_YI_SYLLABLE_CHEP 0xa370 #define UNITEXT_YI_SYLLABLE_CHEP L"\ua370" #define UNICODE_YI_SYLLABLE_CHUX 0xa371 #define UNITEXT_YI_SYLLABLE_CHUX L"\ua371" #define UNICODE_YI_SYLLABLE_CHU 0xa372 #define UNITEXT_YI_SYLLABLE_CHU L"\ua372" #define UNICODE_YI_SYLLABLE_CHUP 0xa373 #define UNITEXT_YI_SYLLABLE_CHUP L"\ua373" #define UNICODE_YI_SYLLABLE_CHURX 0xa374 #define UNITEXT_YI_SYLLABLE_CHURX L"\ua374" #define UNICODE_YI_SYLLABLE_CHUR 0xa375 #define UNITEXT_YI_SYLLABLE_CHUR L"\ua375" #define UNICODE_YI_SYLLABLE_CHYT 0xa376 #define UNITEXT_YI_SYLLABLE_CHYT L"\ua376" #define UNICODE_YI_SYLLABLE_CHYX 0xa377 #define UNITEXT_YI_SYLLABLE_CHYX L"\ua377" #define UNICODE_YI_SYLLABLE_CHY 0xa378 #define UNITEXT_YI_SYLLABLE_CHY L"\ua378" #define UNICODE_YI_SYLLABLE_CHYP 0xa379 #define UNITEXT_YI_SYLLABLE_CHYP L"\ua379" #define UNICODE_YI_SYLLABLE_CHYRX 0xa37a #define UNITEXT_YI_SYLLABLE_CHYRX L"\ua37a" #define UNICODE_YI_SYLLABLE_CHYR 0xa37b #define UNITEXT_YI_SYLLABLE_CHYR L"\ua37b" #define UNICODE_YI_SYLLABLE_RRAX 0xa37c #define UNITEXT_YI_SYLLABLE_RRAX L"\ua37c" #define UNICODE_YI_SYLLABLE_RRA 0xa37d #define UNITEXT_YI_SYLLABLE_RRA L"\ua37d" #define UNICODE_YI_SYLLABLE_RRUOX 0xa37e #define UNITEXT_YI_SYLLABLE_RRUOX L"\ua37e" #define UNICODE_YI_SYLLABLE_RRUO 0xa37f #define UNITEXT_YI_SYLLABLE_RRUO L"\ua37f" #define UNICODE_YI_SYLLABLE_RROT 0xa380 #define UNITEXT_YI_SYLLABLE_RROT L"\ua380" #define UNICODE_YI_SYLLABLE_RROX 0xa381 #define UNITEXT_YI_SYLLABLE_RROX L"\ua381" #define UNICODE_YI_SYLLABLE_RRO 0xa382 #define UNITEXT_YI_SYLLABLE_RRO L"\ua382" #define UNICODE_YI_SYLLABLE_RROP 0xa383 #define UNITEXT_YI_SYLLABLE_RROP L"\ua383" #define UNICODE_YI_SYLLABLE_RRET 0xa384 #define UNITEXT_YI_SYLLABLE_RRET L"\ua384" #define UNICODE_YI_SYLLABLE_RREX 0xa385 #define UNITEXT_YI_SYLLABLE_RREX L"\ua385" #define UNICODE_YI_SYLLABLE_RRE 0xa386 #define UNITEXT_YI_SYLLABLE_RRE L"\ua386" #define UNICODE_YI_SYLLABLE_RREP 0xa387 #define UNITEXT_YI_SYLLABLE_RREP L"\ua387" #define UNICODE_YI_SYLLABLE_RRUT 0xa388 #define UNITEXT_YI_SYLLABLE_RRUT L"\ua388" #define UNICODE_YI_SYLLABLE_RRUX 0xa389 #define UNITEXT_YI_SYLLABLE_RRUX L"\ua389" #define UNICODE_YI_SYLLABLE_RRU 0xa38a #define UNITEXT_YI_SYLLABLE_RRU L"\ua38a" #define UNICODE_YI_SYLLABLE_RRUP 0xa38b #define UNITEXT_YI_SYLLABLE_RRUP L"\ua38b" #define UNICODE_YI_SYLLABLE_RRURX 0xa38c #define UNITEXT_YI_SYLLABLE_RRURX L"\ua38c" #define UNICODE_YI_SYLLABLE_RRUR 0xa38d #define UNITEXT_YI_SYLLABLE_RRUR L"\ua38d" #define UNICODE_YI_SYLLABLE_RRYT 0xa38e #define UNITEXT_YI_SYLLABLE_RRYT L"\ua38e" #define UNICODE_YI_SYLLABLE_RRYX 0xa38f #define UNITEXT_YI_SYLLABLE_RRYX L"\ua38f" #define UNICODE_YI_SYLLABLE_RRY 0xa390 #define UNITEXT_YI_SYLLABLE_RRY L"\ua390" #define UNICODE_YI_SYLLABLE_RRYP 0xa391 #define UNITEXT_YI_SYLLABLE_RRYP L"\ua391" #define UNICODE_YI_SYLLABLE_RRYRX 0xa392 #define UNITEXT_YI_SYLLABLE_RRYRX L"\ua392" #define UNICODE_YI_SYLLABLE_RRYR 0xa393 #define UNITEXT_YI_SYLLABLE_RRYR L"\ua393" #define UNICODE_YI_SYLLABLE_NRAT 0xa394 #define UNITEXT_YI_SYLLABLE_NRAT L"\ua394" #define UNICODE_YI_SYLLABLE_NRAX 0xa395 #define UNITEXT_YI_SYLLABLE_NRAX L"\ua395" #define UNICODE_YI_SYLLABLE_NRA 0xa396 #define UNITEXT_YI_SYLLABLE_NRA L"\ua396" #define UNICODE_YI_SYLLABLE_NRAP 0xa397 #define UNITEXT_YI_SYLLABLE_NRAP L"\ua397" #define UNICODE_YI_SYLLABLE_NROX 0xa398 #define UNITEXT_YI_SYLLABLE_NROX L"\ua398" #define UNICODE_YI_SYLLABLE_NRO 0xa399 #define UNITEXT_YI_SYLLABLE_NRO L"\ua399" #define UNICODE_YI_SYLLABLE_NROP 0xa39a #define UNITEXT_YI_SYLLABLE_NROP L"\ua39a" #define UNICODE_YI_SYLLABLE_NRET 0xa39b #define UNITEXT_YI_SYLLABLE_NRET L"\ua39b" #define UNICODE_YI_SYLLABLE_NREX 0xa39c #define UNITEXT_YI_SYLLABLE_NREX L"\ua39c" #define UNICODE_YI_SYLLABLE_NRE 0xa39d #define UNITEXT_YI_SYLLABLE_NRE L"\ua39d" #define UNICODE_YI_SYLLABLE_NREP 0xa39e #define UNITEXT_YI_SYLLABLE_NREP L"\ua39e" #define UNICODE_YI_SYLLABLE_NRUT 0xa39f #define UNITEXT_YI_SYLLABLE_NRUT L"\ua39f" #define UNICODE_YI_SYLLABLE_NRUX 0xa3a0 #define UNITEXT_YI_SYLLABLE_NRUX L"\ua3a0" #define UNICODE_YI_SYLLABLE_NRU 0xa3a1 #define UNITEXT_YI_SYLLABLE_NRU L"\ua3a1" #define UNICODE_YI_SYLLABLE_NRUP 0xa3a2 #define UNITEXT_YI_SYLLABLE_NRUP L"\ua3a2" #define UNICODE_YI_SYLLABLE_NRURX 0xa3a3 #define UNITEXT_YI_SYLLABLE_NRURX L"\ua3a3" #define UNICODE_YI_SYLLABLE_NRUR 0xa3a4 #define UNITEXT_YI_SYLLABLE_NRUR L"\ua3a4" #define UNICODE_YI_SYLLABLE_NRYT 0xa3a5 #define UNITEXT_YI_SYLLABLE_NRYT L"\ua3a5" #define UNICODE_YI_SYLLABLE_NRYX 0xa3a6 #define UNITEXT_YI_SYLLABLE_NRYX L"\ua3a6" #define UNICODE_YI_SYLLABLE_NRY 0xa3a7 #define UNITEXT_YI_SYLLABLE_NRY L"\ua3a7" #define UNICODE_YI_SYLLABLE_NRYP 0xa3a8 #define UNITEXT_YI_SYLLABLE_NRYP L"\ua3a8" #define UNICODE_YI_SYLLABLE_NRYRX 0xa3a9 #define UNITEXT_YI_SYLLABLE_NRYRX L"\ua3a9" #define UNICODE_YI_SYLLABLE_NRYR 0xa3aa #define UNITEXT_YI_SYLLABLE_NRYR L"\ua3aa" #define UNICODE_YI_SYLLABLE_SHAT 0xa3ab #define UNITEXT_YI_SYLLABLE_SHAT L"\ua3ab" #define UNICODE_YI_SYLLABLE_SHAX 0xa3ac #define UNITEXT_YI_SYLLABLE_SHAX L"\ua3ac" #define UNICODE_YI_SYLLABLE_SHA 0xa3ad #define UNITEXT_YI_SYLLABLE_SHA L"\ua3ad" #define UNICODE_YI_SYLLABLE_SHAP 0xa3ae #define UNITEXT_YI_SYLLABLE_SHAP L"\ua3ae" #define UNICODE_YI_SYLLABLE_SHUOX 0xa3af #define UNITEXT_YI_SYLLABLE_SHUOX L"\ua3af" #define UNICODE_YI_SYLLABLE_SHUO 0xa3b0 #define UNITEXT_YI_SYLLABLE_SHUO L"\ua3b0" #define UNICODE_YI_SYLLABLE_SHUOP 0xa3b1 #define UNITEXT_YI_SYLLABLE_SHUOP L"\ua3b1" #define UNICODE_YI_SYLLABLE_SHOT 0xa3b2 #define UNITEXT_YI_SYLLABLE_SHOT L"\ua3b2" #define UNICODE_YI_SYLLABLE_SHOX 0xa3b3 #define UNITEXT_YI_SYLLABLE_SHOX L"\ua3b3" #define UNICODE_YI_SYLLABLE_SHO 0xa3b4 #define UNITEXT_YI_SYLLABLE_SHO L"\ua3b4" #define UNICODE_YI_SYLLABLE_SHOP 0xa3b5 #define UNITEXT_YI_SYLLABLE_SHOP L"\ua3b5" #define UNICODE_YI_SYLLABLE_SHET 0xa3b6 #define UNITEXT_YI_SYLLABLE_SHET L"\ua3b6" #define UNICODE_YI_SYLLABLE_SHEX 0xa3b7 #define UNITEXT_YI_SYLLABLE_SHEX L"\ua3b7" #define UNICODE_YI_SYLLABLE_SHE 0xa3b8 #define UNITEXT_YI_SYLLABLE_SHE L"\ua3b8" #define UNICODE_YI_SYLLABLE_SHEP 0xa3b9 #define UNITEXT_YI_SYLLABLE_SHEP L"\ua3b9" #define UNICODE_YI_SYLLABLE_SHUT 0xa3ba #define UNITEXT_YI_SYLLABLE_SHUT L"\ua3ba" #define UNICODE_YI_SYLLABLE_SHUX 0xa3bb #define UNITEXT_YI_SYLLABLE_SHUX L"\ua3bb" #define UNICODE_YI_SYLLABLE_SHU 0xa3bc #define UNITEXT_YI_SYLLABLE_SHU L"\ua3bc" #define UNICODE_YI_SYLLABLE_SHUP 0xa3bd #define UNITEXT_YI_SYLLABLE_SHUP L"\ua3bd" #define UNICODE_YI_SYLLABLE_SHURX 0xa3be #define UNITEXT_YI_SYLLABLE_SHURX L"\ua3be" #define UNICODE_YI_SYLLABLE_SHUR 0xa3bf #define UNITEXT_YI_SYLLABLE_SHUR L"\ua3bf" #define UNICODE_YI_SYLLABLE_SHYT 0xa3c0 #define UNITEXT_YI_SYLLABLE_SHYT L"\ua3c0" #define UNICODE_YI_SYLLABLE_SHYX 0xa3c1 #define UNITEXT_YI_SYLLABLE_SHYX L"\ua3c1" #define UNICODE_YI_SYLLABLE_SHY 0xa3c2 #define UNITEXT_YI_SYLLABLE_SHY L"\ua3c2" #define UNICODE_YI_SYLLABLE_SHYP 0xa3c3 #define UNITEXT_YI_SYLLABLE_SHYP L"\ua3c3" #define UNICODE_YI_SYLLABLE_SHYRX 0xa3c4 #define UNITEXT_YI_SYLLABLE_SHYRX L"\ua3c4" #define UNICODE_YI_SYLLABLE_SHYR 0xa3c5 #define UNITEXT_YI_SYLLABLE_SHYR L"\ua3c5" #define UNICODE_YI_SYLLABLE_RAT 0xa3c6 #define UNITEXT_YI_SYLLABLE_RAT L"\ua3c6" #define UNICODE_YI_SYLLABLE_RAX 0xa3c7 #define UNITEXT_YI_SYLLABLE_RAX L"\ua3c7" #define UNICODE_YI_SYLLABLE_RA 0xa3c8 #define UNITEXT_YI_SYLLABLE_RA L"\ua3c8" #define UNICODE_YI_SYLLABLE_RAP 0xa3c9 #define UNITEXT_YI_SYLLABLE_RAP L"\ua3c9" #define UNICODE_YI_SYLLABLE_RUOX 0xa3ca #define UNITEXT_YI_SYLLABLE_RUOX L"\ua3ca" #define UNICODE_YI_SYLLABLE_RUO 0xa3cb #define UNITEXT_YI_SYLLABLE_RUO L"\ua3cb" #define UNICODE_YI_SYLLABLE_RUOP 0xa3cc #define UNITEXT_YI_SYLLABLE_RUOP L"\ua3cc" #define UNICODE_YI_SYLLABLE_ROT 0xa3cd #define UNITEXT_YI_SYLLABLE_ROT L"\ua3cd" #define UNICODE_YI_SYLLABLE_ROX 0xa3ce #define UNITEXT_YI_SYLLABLE_ROX L"\ua3ce" #define UNICODE_YI_SYLLABLE_RO 0xa3cf #define UNITEXT_YI_SYLLABLE_RO L"\ua3cf" #define UNICODE_YI_SYLLABLE_ROP 0xa3d0 #define UNITEXT_YI_SYLLABLE_ROP L"\ua3d0" #define UNICODE_YI_SYLLABLE_REX 0xa3d1 #define UNITEXT_YI_SYLLABLE_REX L"\ua3d1" #define UNICODE_YI_SYLLABLE_RE 0xa3d2 #define UNITEXT_YI_SYLLABLE_RE L"\ua3d2" #define UNICODE_YI_SYLLABLE_REP 0xa3d3 #define UNITEXT_YI_SYLLABLE_REP L"\ua3d3" #define UNICODE_YI_SYLLABLE_RUT 0xa3d4 #define UNITEXT_YI_SYLLABLE_RUT L"\ua3d4" #define UNICODE_YI_SYLLABLE_RUX 0xa3d5 #define UNITEXT_YI_SYLLABLE_RUX L"\ua3d5" #define UNICODE_YI_SYLLABLE_RU 0xa3d6 #define UNITEXT_YI_SYLLABLE_RU L"\ua3d6" #define UNICODE_YI_SYLLABLE_RUP 0xa3d7 #define UNITEXT_YI_SYLLABLE_RUP L"\ua3d7" #define UNICODE_YI_SYLLABLE_RURX 0xa3d8 #define UNITEXT_YI_SYLLABLE_RURX L"\ua3d8" #define UNICODE_YI_SYLLABLE_RUR 0xa3d9 #define UNITEXT_YI_SYLLABLE_RUR L"\ua3d9" #define UNICODE_YI_SYLLABLE_RYT 0xa3da #define UNITEXT_YI_SYLLABLE_RYT L"\ua3da" #define UNICODE_YI_SYLLABLE_RYX 0xa3db #define UNITEXT_YI_SYLLABLE_RYX L"\ua3db" #define UNICODE_YI_SYLLABLE_RY 0xa3dc #define UNITEXT_YI_SYLLABLE_RY L"\ua3dc" #define UNICODE_YI_SYLLABLE_RYP 0xa3dd #define UNITEXT_YI_SYLLABLE_RYP L"\ua3dd" #define UNICODE_YI_SYLLABLE_RYRX 0xa3de #define UNITEXT_YI_SYLLABLE_RYRX L"\ua3de" #define UNICODE_YI_SYLLABLE_RYR 0xa3df #define UNITEXT_YI_SYLLABLE_RYR L"\ua3df" #define UNICODE_YI_SYLLABLE_JIT 0xa3e0 #define UNITEXT_YI_SYLLABLE_JIT L"\ua3e0" #define UNICODE_YI_SYLLABLE_JIX 0xa3e1 #define UNITEXT_YI_SYLLABLE_JIX L"\ua3e1" #define UNICODE_YI_SYLLABLE_JI 0xa3e2 #define UNITEXT_YI_SYLLABLE_JI L"\ua3e2" #define UNICODE_YI_SYLLABLE_JIP 0xa3e3 #define UNITEXT_YI_SYLLABLE_JIP L"\ua3e3" #define UNICODE_YI_SYLLABLE_JIET 0xa3e4 #define UNITEXT_YI_SYLLABLE_JIET L"\ua3e4" #define UNICODE_YI_SYLLABLE_JIEX 0xa3e5 #define UNITEXT_YI_SYLLABLE_JIEX L"\ua3e5" #define UNICODE_YI_SYLLABLE_JIE 0xa3e6 #define UNITEXT_YI_SYLLABLE_JIE L"\ua3e6" #define UNICODE_YI_SYLLABLE_JIEP 0xa3e7 #define UNITEXT_YI_SYLLABLE_JIEP L"\ua3e7" #define UNICODE_YI_SYLLABLE_JUOT 0xa3e8 #define UNITEXT_YI_SYLLABLE_JUOT L"\ua3e8" #define UNICODE_YI_SYLLABLE_JUOX 0xa3e9 #define UNITEXT_YI_SYLLABLE_JUOX L"\ua3e9" #define UNICODE_YI_SYLLABLE_JUO 0xa3ea #define UNITEXT_YI_SYLLABLE_JUO L"\ua3ea" #define UNICODE_YI_SYLLABLE_JUOP 0xa3eb #define UNITEXT_YI_SYLLABLE_JUOP L"\ua3eb" #define UNICODE_YI_SYLLABLE_JOT 0xa3ec #define UNITEXT_YI_SYLLABLE_JOT L"\ua3ec" #define UNICODE_YI_SYLLABLE_JOX 0xa3ed #define UNITEXT_YI_SYLLABLE_JOX L"\ua3ed" #define UNICODE_YI_SYLLABLE_JO 0xa3ee #define UNITEXT_YI_SYLLABLE_JO L"\ua3ee" #define UNICODE_YI_SYLLABLE_JOP 0xa3ef #define UNITEXT_YI_SYLLABLE_JOP L"\ua3ef" #define UNICODE_YI_SYLLABLE_JUT 0xa3f0 #define UNITEXT_YI_SYLLABLE_JUT L"\ua3f0" #define UNICODE_YI_SYLLABLE_JUX 0xa3f1 #define UNITEXT_YI_SYLLABLE_JUX L"\ua3f1" #define UNICODE_YI_SYLLABLE_JU 0xa3f2 #define UNITEXT_YI_SYLLABLE_JU L"\ua3f2" #define UNICODE_YI_SYLLABLE_JUP 0xa3f3 #define UNITEXT_YI_SYLLABLE_JUP L"\ua3f3" #define UNICODE_YI_SYLLABLE_JURX 0xa3f4 #define UNITEXT_YI_SYLLABLE_JURX L"\ua3f4" #define UNICODE_YI_SYLLABLE_JUR 0xa3f5 #define UNITEXT_YI_SYLLABLE_JUR L"\ua3f5" #define UNICODE_YI_SYLLABLE_JYT 0xa3f6 #define UNITEXT_YI_SYLLABLE_JYT L"\ua3f6" #define UNICODE_YI_SYLLABLE_JYX 0xa3f7 #define UNITEXT_YI_SYLLABLE_JYX L"\ua3f7" #define UNICODE_YI_SYLLABLE_JY 0xa3f8 #define UNITEXT_YI_SYLLABLE_JY L"\ua3f8" #define UNICODE_YI_SYLLABLE_JYP 0xa3f9 #define UNITEXT_YI_SYLLABLE_JYP L"\ua3f9" #define UNICODE_YI_SYLLABLE_JYRX 0xa3fa #define UNITEXT_YI_SYLLABLE_JYRX L"\ua3fa" #define UNICODE_YI_SYLLABLE_JYR 0xa3fb #define UNITEXT_YI_SYLLABLE_JYR L"\ua3fb" #define UNICODE_YI_SYLLABLE_QIT 0xa3fc #define UNITEXT_YI_SYLLABLE_QIT L"\ua3fc" #define UNICODE_YI_SYLLABLE_QIX 0xa3fd #define UNITEXT_YI_SYLLABLE_QIX L"\ua3fd" #define UNICODE_YI_SYLLABLE_QI 0xa3fe #define UNITEXT_YI_SYLLABLE_QI L"\ua3fe" #define UNICODE_YI_SYLLABLE_QIP 0xa3ff #define UNITEXT_YI_SYLLABLE_QIP L"\ua3ff" #define UNICODE_YI_SYLLABLE_QIET 0xa400 #define UNITEXT_YI_SYLLABLE_QIET L"\ua400" #define UNICODE_YI_SYLLABLE_QIEX 0xa401 #define UNITEXT_YI_SYLLABLE_QIEX L"\ua401" #define UNICODE_YI_SYLLABLE_QIE 0xa402 #define UNITEXT_YI_SYLLABLE_QIE L"\ua402" #define UNICODE_YI_SYLLABLE_QIEP 0xa403 #define UNITEXT_YI_SYLLABLE_QIEP L"\ua403" #define UNICODE_YI_SYLLABLE_QUOT 0xa404 #define UNITEXT_YI_SYLLABLE_QUOT L"\ua404" #define UNICODE_YI_SYLLABLE_QUOX 0xa405 #define UNITEXT_YI_SYLLABLE_QUOX L"\ua405" #define UNICODE_YI_SYLLABLE_QUO 0xa406 #define UNITEXT_YI_SYLLABLE_QUO L"\ua406" #define UNICODE_YI_SYLLABLE_QUOP 0xa407 #define UNITEXT_YI_SYLLABLE_QUOP L"\ua407" #define UNICODE_YI_SYLLABLE_QOT 0xa408 #define UNITEXT_YI_SYLLABLE_QOT L"\ua408" #define UNICODE_YI_SYLLABLE_QOX 0xa409 #define UNITEXT_YI_SYLLABLE_QOX L"\ua409" #define UNICODE_YI_SYLLABLE_QO 0xa40a #define UNITEXT_YI_SYLLABLE_QO L"\ua40a" #define UNICODE_YI_SYLLABLE_QOP 0xa40b #define UNITEXT_YI_SYLLABLE_QOP L"\ua40b" #define UNICODE_YI_SYLLABLE_QUT 0xa40c #define UNITEXT_YI_SYLLABLE_QUT L"\ua40c" #define UNICODE_YI_SYLLABLE_QUX 0xa40d #define UNITEXT_YI_SYLLABLE_QUX L"\ua40d" #define UNICODE_YI_SYLLABLE_QU 0xa40e #define UNITEXT_YI_SYLLABLE_QU L"\ua40e" #define UNICODE_YI_SYLLABLE_QUP 0xa40f #define UNITEXT_YI_SYLLABLE_QUP L"\ua40f" #define UNICODE_YI_SYLLABLE_QURX 0xa410 #define UNITEXT_YI_SYLLABLE_QURX L"\ua410" #define UNICODE_YI_SYLLABLE_QUR 0xa411 #define UNITEXT_YI_SYLLABLE_QUR L"\ua411" #define UNICODE_YI_SYLLABLE_QYT 0xa412 #define UNITEXT_YI_SYLLABLE_QYT L"\ua412" #define UNICODE_YI_SYLLABLE_QYX 0xa413 #define UNITEXT_YI_SYLLABLE_QYX L"\ua413" #define UNICODE_YI_SYLLABLE_QY 0xa414 #define UNITEXT_YI_SYLLABLE_QY L"\ua414" #define UNICODE_YI_SYLLABLE_QYP 0xa415 #define UNITEXT_YI_SYLLABLE_QYP L"\ua415" #define UNICODE_YI_SYLLABLE_QYRX 0xa416 #define UNITEXT_YI_SYLLABLE_QYRX L"\ua416" #define UNICODE_YI_SYLLABLE_QYR 0xa417 #define UNITEXT_YI_SYLLABLE_QYR L"\ua417" #define UNICODE_YI_SYLLABLE_JJIT 0xa418 #define UNITEXT_YI_SYLLABLE_JJIT L"\ua418" #define UNICODE_YI_SYLLABLE_JJIX 0xa419 #define UNITEXT_YI_SYLLABLE_JJIX L"\ua419" #define UNICODE_YI_SYLLABLE_JJI 0xa41a #define UNITEXT_YI_SYLLABLE_JJI L"\ua41a" #define UNICODE_YI_SYLLABLE_JJIP 0xa41b #define UNITEXT_YI_SYLLABLE_JJIP L"\ua41b" #define UNICODE_YI_SYLLABLE_JJIET 0xa41c #define UNITEXT_YI_SYLLABLE_JJIET L"\ua41c" #define UNICODE_YI_SYLLABLE_JJIEX 0xa41d #define UNITEXT_YI_SYLLABLE_JJIEX L"\ua41d" #define UNICODE_YI_SYLLABLE_JJIE 0xa41e #define UNITEXT_YI_SYLLABLE_JJIE L"\ua41e" #define UNICODE_YI_SYLLABLE_JJIEP 0xa41f #define UNITEXT_YI_SYLLABLE_JJIEP L"\ua41f" #define UNICODE_YI_SYLLABLE_JJUOX 0xa420 #define UNITEXT_YI_SYLLABLE_JJUOX L"\ua420" #define UNICODE_YI_SYLLABLE_JJUO 0xa421 #define UNITEXT_YI_SYLLABLE_JJUO L"\ua421" #define UNICODE_YI_SYLLABLE_JJUOP 0xa422 #define UNITEXT_YI_SYLLABLE_JJUOP L"\ua422" #define UNICODE_YI_SYLLABLE_JJOT 0xa423 #define UNITEXT_YI_SYLLABLE_JJOT L"\ua423" #define UNICODE_YI_SYLLABLE_JJOX 0xa424 #define UNITEXT_YI_SYLLABLE_JJOX L"\ua424" #define UNICODE_YI_SYLLABLE_JJO 0xa425 #define UNITEXT_YI_SYLLABLE_JJO L"\ua425" #define UNICODE_YI_SYLLABLE_JJOP 0xa426 #define UNITEXT_YI_SYLLABLE_JJOP L"\ua426" #define UNICODE_YI_SYLLABLE_JJUT 0xa427 #define UNITEXT_YI_SYLLABLE_JJUT L"\ua427" #define UNICODE_YI_SYLLABLE_JJUX 0xa428 #define UNITEXT_YI_SYLLABLE_JJUX L"\ua428" #define UNICODE_YI_SYLLABLE_JJU 0xa429 #define UNITEXT_YI_SYLLABLE_JJU L"\ua429" #define UNICODE_YI_SYLLABLE_JJUP 0xa42a #define UNITEXT_YI_SYLLABLE_JJUP L"\ua42a" #define UNICODE_YI_SYLLABLE_JJURX 0xa42b #define UNITEXT_YI_SYLLABLE_JJURX L"\ua42b" #define UNICODE_YI_SYLLABLE_JJUR 0xa42c #define UNITEXT_YI_SYLLABLE_JJUR L"\ua42c" #define UNICODE_YI_SYLLABLE_JJYT 0xa42d #define UNITEXT_YI_SYLLABLE_JJYT L"\ua42d" #define UNICODE_YI_SYLLABLE_JJYX 0xa42e #define UNITEXT_YI_SYLLABLE_JJYX L"\ua42e" #define UNICODE_YI_SYLLABLE_JJY 0xa42f #define UNITEXT_YI_SYLLABLE_JJY L"\ua42f" #define UNICODE_YI_SYLLABLE_JJYP 0xa430 #define UNITEXT_YI_SYLLABLE_JJYP L"\ua430" #define UNICODE_YI_SYLLABLE_NJIT 0xa431 #define UNITEXT_YI_SYLLABLE_NJIT L"\ua431" #define UNICODE_YI_SYLLABLE_NJIX 0xa432 #define UNITEXT_YI_SYLLABLE_NJIX L"\ua432" #define UNICODE_YI_SYLLABLE_NJI 0xa433 #define UNITEXT_YI_SYLLABLE_NJI L"\ua433" #define UNICODE_YI_SYLLABLE_NJIP 0xa434 #define UNITEXT_YI_SYLLABLE_NJIP L"\ua434" #define UNICODE_YI_SYLLABLE_NJIET 0xa435 #define UNITEXT_YI_SYLLABLE_NJIET L"\ua435" #define UNICODE_YI_SYLLABLE_NJIEX 0xa436 #define UNITEXT_YI_SYLLABLE_NJIEX L"\ua436" #define UNICODE_YI_SYLLABLE_NJIE 0xa437 #define UNITEXT_YI_SYLLABLE_NJIE L"\ua437" #define UNICODE_YI_SYLLABLE_NJIEP 0xa438 #define UNITEXT_YI_SYLLABLE_NJIEP L"\ua438" #define UNICODE_YI_SYLLABLE_NJUOX 0xa439 #define UNITEXT_YI_SYLLABLE_NJUOX L"\ua439" #define UNICODE_YI_SYLLABLE_NJUO 0xa43a #define UNITEXT_YI_SYLLABLE_NJUO L"\ua43a" #define UNICODE_YI_SYLLABLE_NJOT 0xa43b #define UNITEXT_YI_SYLLABLE_NJOT L"\ua43b" #define UNICODE_YI_SYLLABLE_NJOX 0xa43c #define UNITEXT_YI_SYLLABLE_NJOX L"\ua43c" #define UNICODE_YI_SYLLABLE_NJO 0xa43d #define UNITEXT_YI_SYLLABLE_NJO L"\ua43d" #define UNICODE_YI_SYLLABLE_NJOP 0xa43e #define UNITEXT_YI_SYLLABLE_NJOP L"\ua43e" #define UNICODE_YI_SYLLABLE_NJUX 0xa43f #define UNITEXT_YI_SYLLABLE_NJUX L"\ua43f" #define UNICODE_YI_SYLLABLE_NJU 0xa440 #define UNITEXT_YI_SYLLABLE_NJU L"\ua440" #define UNICODE_YI_SYLLABLE_NJUP 0xa441 #define UNITEXT_YI_SYLLABLE_NJUP L"\ua441" #define UNICODE_YI_SYLLABLE_NJURX 0xa442 #define UNITEXT_YI_SYLLABLE_NJURX L"\ua442" #define UNICODE_YI_SYLLABLE_NJUR 0xa443 #define UNITEXT_YI_SYLLABLE_NJUR L"\ua443" #define UNICODE_YI_SYLLABLE_NJYT 0xa444 #define UNITEXT_YI_SYLLABLE_NJYT L"\ua444" #define UNICODE_YI_SYLLABLE_NJYX 0xa445 #define UNITEXT_YI_SYLLABLE_NJYX L"\ua445" #define UNICODE_YI_SYLLABLE_NJY 0xa446 #define UNITEXT_YI_SYLLABLE_NJY L"\ua446" #define UNICODE_YI_SYLLABLE_NJYP 0xa447 #define UNITEXT_YI_SYLLABLE_NJYP L"\ua447" #define UNICODE_YI_SYLLABLE_NJYRX 0xa448 #define UNITEXT_YI_SYLLABLE_NJYRX L"\ua448" #define UNICODE_YI_SYLLABLE_NJYR 0xa449 #define UNITEXT_YI_SYLLABLE_NJYR L"\ua449" #define UNICODE_YI_SYLLABLE_NYIT 0xa44a #define UNITEXT_YI_SYLLABLE_NYIT L"\ua44a" #define UNICODE_YI_SYLLABLE_NYIX 0xa44b #define UNITEXT_YI_SYLLABLE_NYIX L"\ua44b" #define UNICODE_YI_SYLLABLE_NYI 0xa44c #define UNITEXT_YI_SYLLABLE_NYI L"\ua44c" #define UNICODE_YI_SYLLABLE_NYIP 0xa44d #define UNITEXT_YI_SYLLABLE_NYIP L"\ua44d" #define UNICODE_YI_SYLLABLE_NYIET 0xa44e #define UNITEXT_YI_SYLLABLE_NYIET L"\ua44e" #define UNICODE_YI_SYLLABLE_NYIEX 0xa44f #define UNITEXT_YI_SYLLABLE_NYIEX L"\ua44f" #define UNICODE_YI_SYLLABLE_NYIE 0xa450 #define UNITEXT_YI_SYLLABLE_NYIE L"\ua450" #define UNICODE_YI_SYLLABLE_NYIEP 0xa451 #define UNITEXT_YI_SYLLABLE_NYIEP L"\ua451" #define UNICODE_YI_SYLLABLE_NYUOX 0xa452 #define UNITEXT_YI_SYLLABLE_NYUOX L"\ua452" #define UNICODE_YI_SYLLABLE_NYUO 0xa453 #define UNITEXT_YI_SYLLABLE_NYUO L"\ua453" #define UNICODE_YI_SYLLABLE_NYUOP 0xa454 #define UNITEXT_YI_SYLLABLE_NYUOP L"\ua454" #define UNICODE_YI_SYLLABLE_NYOT 0xa455 #define UNITEXT_YI_SYLLABLE_NYOT L"\ua455" #define UNICODE_YI_SYLLABLE_NYOX 0xa456 #define UNITEXT_YI_SYLLABLE_NYOX L"\ua456" #define UNICODE_YI_SYLLABLE_NYO 0xa457 #define UNITEXT_YI_SYLLABLE_NYO L"\ua457" #define UNICODE_YI_SYLLABLE_NYOP 0xa458 #define UNITEXT_YI_SYLLABLE_NYOP L"\ua458" #define UNICODE_YI_SYLLABLE_NYUT 0xa459 #define UNITEXT_YI_SYLLABLE_NYUT L"\ua459" #define UNICODE_YI_SYLLABLE_NYUX 0xa45a #define UNITEXT_YI_SYLLABLE_NYUX L"\ua45a" #define UNICODE_YI_SYLLABLE_NYU 0xa45b #define UNITEXT_YI_SYLLABLE_NYU L"\ua45b" #define UNICODE_YI_SYLLABLE_NYUP 0xa45c #define UNITEXT_YI_SYLLABLE_NYUP L"\ua45c" #define UNICODE_YI_SYLLABLE_XIT 0xa45d #define UNITEXT_YI_SYLLABLE_XIT L"\ua45d" #define UNICODE_YI_SYLLABLE_XIX 0xa45e #define UNITEXT_YI_SYLLABLE_XIX L"\ua45e" #define UNICODE_YI_SYLLABLE_XI 0xa45f #define UNITEXT_YI_SYLLABLE_XI L"\ua45f" #define UNICODE_YI_SYLLABLE_XIP 0xa460 #define UNITEXT_YI_SYLLABLE_XIP L"\ua460" #define UNICODE_YI_SYLLABLE_XIET 0xa461 #define UNITEXT_YI_SYLLABLE_XIET L"\ua461" #define UNICODE_YI_SYLLABLE_XIEX 0xa462 #define UNITEXT_YI_SYLLABLE_XIEX L"\ua462" #define UNICODE_YI_SYLLABLE_XIE 0xa463 #define UNITEXT_YI_SYLLABLE_XIE L"\ua463" #define UNICODE_YI_SYLLABLE_XIEP 0xa464 #define UNITEXT_YI_SYLLABLE_XIEP L"\ua464" #define UNICODE_YI_SYLLABLE_XUOX 0xa465 #define UNITEXT_YI_SYLLABLE_XUOX L"\ua465" #define UNICODE_YI_SYLLABLE_XUO 0xa466 #define UNITEXT_YI_SYLLABLE_XUO L"\ua466" #define UNICODE_YI_SYLLABLE_XOT 0xa467 #define UNITEXT_YI_SYLLABLE_XOT L"\ua467" #define UNICODE_YI_SYLLABLE_XOX 0xa468 #define UNITEXT_YI_SYLLABLE_XOX L"\ua468" #define UNICODE_YI_SYLLABLE_XO 0xa469 #define UNITEXT_YI_SYLLABLE_XO L"\ua469" #define UNICODE_YI_SYLLABLE_XOP 0xa46a #define UNITEXT_YI_SYLLABLE_XOP L"\ua46a" #define UNICODE_YI_SYLLABLE_XYT 0xa46b #define UNITEXT_YI_SYLLABLE_XYT L"\ua46b" #define UNICODE_YI_SYLLABLE_XYX 0xa46c #define UNITEXT_YI_SYLLABLE_XYX L"\ua46c" #define UNICODE_YI_SYLLABLE_XY 0xa46d #define UNITEXT_YI_SYLLABLE_XY L"\ua46d" #define UNICODE_YI_SYLLABLE_XYP 0xa46e #define UNITEXT_YI_SYLLABLE_XYP L"\ua46e" #define UNICODE_YI_SYLLABLE_XYRX 0xa46f #define UNITEXT_YI_SYLLABLE_XYRX L"\ua46f" #define UNICODE_YI_SYLLABLE_XYR 0xa470 #define UNITEXT_YI_SYLLABLE_XYR L"\ua470" #define UNICODE_YI_SYLLABLE_YIT 0xa471 #define UNITEXT_YI_SYLLABLE_YIT L"\ua471" #define UNICODE_YI_SYLLABLE_YIX 0xa472 #define UNITEXT_YI_SYLLABLE_YIX L"\ua472" #define UNICODE_YI_SYLLABLE_YI 0xa473 #define UNITEXT_YI_SYLLABLE_YI L"\ua473" #define UNICODE_YI_SYLLABLE_YIP 0xa474 #define UNITEXT_YI_SYLLABLE_YIP L"\ua474" #define UNICODE_YI_SYLLABLE_YIET 0xa475 #define UNITEXT_YI_SYLLABLE_YIET L"\ua475" #define UNICODE_YI_SYLLABLE_YIEX 0xa476 #define UNITEXT_YI_SYLLABLE_YIEX L"\ua476" #define UNICODE_YI_SYLLABLE_YIE 0xa477 #define UNITEXT_YI_SYLLABLE_YIE L"\ua477" #define UNICODE_YI_SYLLABLE_YIEP 0xa478 #define UNITEXT_YI_SYLLABLE_YIEP L"\ua478" #define UNICODE_YI_SYLLABLE_YUOT 0xa479 #define UNITEXT_YI_SYLLABLE_YUOT L"\ua479" #define UNICODE_YI_SYLLABLE_YUOX 0xa47a #define UNITEXT_YI_SYLLABLE_YUOX L"\ua47a" #define UNICODE_YI_SYLLABLE_YUO 0xa47b #define UNITEXT_YI_SYLLABLE_YUO L"\ua47b" #define UNICODE_YI_SYLLABLE_YUOP 0xa47c #define UNITEXT_YI_SYLLABLE_YUOP L"\ua47c" #define UNICODE_YI_SYLLABLE_YOT 0xa47d #define UNITEXT_YI_SYLLABLE_YOT L"\ua47d" #define UNICODE_YI_SYLLABLE_YOX 0xa47e #define UNITEXT_YI_SYLLABLE_YOX L"\ua47e" #define UNICODE_YI_SYLLABLE_YO 0xa47f #define UNITEXT_YI_SYLLABLE_YO L"\ua47f" #define UNICODE_YI_SYLLABLE_YOP 0xa480 #define UNITEXT_YI_SYLLABLE_YOP L"\ua480" #define UNICODE_YI_SYLLABLE_YUT 0xa481 #define UNITEXT_YI_SYLLABLE_YUT L"\ua481" #define UNICODE_YI_SYLLABLE_YUX 0xa482 #define UNITEXT_YI_SYLLABLE_YUX L"\ua482" #define UNICODE_YI_SYLLABLE_YU 0xa483 #define UNITEXT_YI_SYLLABLE_YU L"\ua483" #define UNICODE_YI_SYLLABLE_YUP 0xa484 #define UNITEXT_YI_SYLLABLE_YUP L"\ua484" #define UNICODE_YI_SYLLABLE_YURX 0xa485 #define UNITEXT_YI_SYLLABLE_YURX L"\ua485" #define UNICODE_YI_SYLLABLE_YUR 0xa486 #define UNITEXT_YI_SYLLABLE_YUR L"\ua486" #define UNICODE_YI_SYLLABLE_YYT 0xa487 #define UNITEXT_YI_SYLLABLE_YYT L"\ua487" #define UNICODE_YI_SYLLABLE_YYX 0xa488 #define UNITEXT_YI_SYLLABLE_YYX L"\ua488" #define UNICODE_YI_SYLLABLE_YY 0xa489 #define UNITEXT_YI_SYLLABLE_YY L"\ua489" #define UNICODE_YI_SYLLABLE_YYP 0xa48a #define UNITEXT_YI_SYLLABLE_YYP L"\ua48a" #define UNICODE_YI_SYLLABLE_YYRX 0xa48b #define UNITEXT_YI_SYLLABLE_YYRX L"\ua48b" #define UNICODE_YI_SYLLABLE_YYR 0xa48c #define UNITEXT_YI_SYLLABLE_YYR L"\ua48c" #define UNICODE_YI_RADICAL_QOT 0xa490 #define UNITEXT_YI_RADICAL_QOT L"\ua490" #define UNICODE_YI_RADICAL_LI 0xa491 #define UNITEXT_YI_RADICAL_LI L"\ua491" #define UNICODE_YI_RADICAL_KIT 0xa492 #define UNITEXT_YI_RADICAL_KIT L"\ua492" #define UNICODE_YI_RADICAL_NYIP 0xa493 #define UNITEXT_YI_RADICAL_NYIP L"\ua493" #define UNICODE_YI_RADICAL_CYP 0xa494 #define UNITEXT_YI_RADICAL_CYP L"\ua494" #define UNICODE_YI_RADICAL_SSI 0xa495 #define UNITEXT_YI_RADICAL_SSI L"\ua495" #define UNICODE_YI_RADICAL_GGOP 0xa496 #define UNITEXT_YI_RADICAL_GGOP L"\ua496" #define UNICODE_YI_RADICAL_GEP 0xa497 #define UNITEXT_YI_RADICAL_GEP L"\ua497" #define UNICODE_YI_RADICAL_MI 0xa498 #define UNITEXT_YI_RADICAL_MI L"\ua498" #define UNICODE_YI_RADICAL_HXIT 0xa499 #define UNITEXT_YI_RADICAL_HXIT L"\ua499" #define UNICODE_YI_RADICAL_LYR 0xa49a #define UNITEXT_YI_RADICAL_LYR L"\ua49a" #define UNICODE_YI_RADICAL_BBUT 0xa49b #define UNITEXT_YI_RADICAL_BBUT L"\ua49b" #define UNICODE_YI_RADICAL_MOP 0xa49c #define UNITEXT_YI_RADICAL_MOP L"\ua49c" #define UNICODE_YI_RADICAL_YO 0xa49d #define UNITEXT_YI_RADICAL_YO L"\ua49d" #define UNICODE_YI_RADICAL_PUT 0xa49e #define UNITEXT_YI_RADICAL_PUT L"\ua49e" #define UNICODE_YI_RADICAL_HXUO 0xa49f #define UNITEXT_YI_RADICAL_HXUO L"\ua49f" #define UNICODE_YI_RADICAL_TAT 0xa4a0 #define UNITEXT_YI_RADICAL_TAT L"\ua4a0" #define UNICODE_YI_RADICAL_GA 0xa4a1 #define UNITEXT_YI_RADICAL_GA L"\ua4a1" #define UNICODE_YI_RADICAL_ZUP 0xa4a2 #define UNITEXT_YI_RADICAL_ZUP L"\ua4a2" #define UNICODE_YI_RADICAL_CYT 0xa4a3 #define UNITEXT_YI_RADICAL_CYT L"\ua4a3" #define UNICODE_YI_RADICAL_DDUR 0xa4a4 #define UNITEXT_YI_RADICAL_DDUR L"\ua4a4" #define UNICODE_YI_RADICAL_BUR 0xa4a5 #define UNITEXT_YI_RADICAL_BUR L"\ua4a5" #define UNICODE_YI_RADICAL_GGUO 0xa4a6 #define UNITEXT_YI_RADICAL_GGUO L"\ua4a6" #define UNICODE_YI_RADICAL_NYOP 0xa4a7 #define UNITEXT_YI_RADICAL_NYOP L"\ua4a7" #define UNICODE_YI_RADICAL_TU 0xa4a8 #define UNITEXT_YI_RADICAL_TU L"\ua4a8" #define UNICODE_YI_RADICAL_OP 0xa4a9 #define UNITEXT_YI_RADICAL_OP L"\ua4a9" #define UNICODE_YI_RADICAL_JJUT 0xa4aa #define UNITEXT_YI_RADICAL_JJUT L"\ua4aa" #define UNICODE_YI_RADICAL_ZOT 0xa4ab #define UNITEXT_YI_RADICAL_ZOT L"\ua4ab" #define UNICODE_YI_RADICAL_PYT 0xa4ac #define UNITEXT_YI_RADICAL_PYT L"\ua4ac" #define UNICODE_YI_RADICAL_HMO 0xa4ad #define UNITEXT_YI_RADICAL_HMO L"\ua4ad" #define UNICODE_YI_RADICAL_YIT 0xa4ae #define UNITEXT_YI_RADICAL_YIT L"\ua4ae" #define UNICODE_YI_RADICAL_VUR 0xa4af #define UNITEXT_YI_RADICAL_VUR L"\ua4af" #define UNICODE_YI_RADICAL_SHY 0xa4b0 #define UNITEXT_YI_RADICAL_SHY L"\ua4b0" #define UNICODE_YI_RADICAL_VEP 0xa4b1 #define UNITEXT_YI_RADICAL_VEP L"\ua4b1" #define UNICODE_YI_RADICAL_ZA 0xa4b2 #define UNITEXT_YI_RADICAL_ZA L"\ua4b2" #define UNICODE_YI_RADICAL_JO 0xa4b3 #define UNITEXT_YI_RADICAL_JO L"\ua4b3" #define UNICODE_YI_RADICAL_NZUP 0xa4b4 #define UNITEXT_YI_RADICAL_NZUP L"\ua4b4" #define UNICODE_YI_RADICAL_JJY 0xa4b5 #define UNITEXT_YI_RADICAL_JJY L"\ua4b5" #define UNICODE_YI_RADICAL_GOT 0xa4b6 #define UNITEXT_YI_RADICAL_GOT L"\ua4b6" #define UNICODE_YI_RADICAL_JJIE 0xa4b7 #define UNITEXT_YI_RADICAL_JJIE L"\ua4b7" #define UNICODE_YI_RADICAL_WO 0xa4b8 #define UNITEXT_YI_RADICAL_WO L"\ua4b8" #define UNICODE_YI_RADICAL_DU 0xa4b9 #define UNITEXT_YI_RADICAL_DU L"\ua4b9" #define UNICODE_YI_RADICAL_SHUR 0xa4ba #define UNITEXT_YI_RADICAL_SHUR L"\ua4ba" #define UNICODE_YI_RADICAL_LIE 0xa4bb #define UNITEXT_YI_RADICAL_LIE L"\ua4bb" #define UNICODE_YI_RADICAL_CY 0xa4bc #define UNITEXT_YI_RADICAL_CY L"\ua4bc" #define UNICODE_YI_RADICAL_CUOP 0xa4bd #define UNITEXT_YI_RADICAL_CUOP L"\ua4bd" #define UNICODE_YI_RADICAL_CIP 0xa4be #define UNITEXT_YI_RADICAL_CIP L"\ua4be" #define UNICODE_YI_RADICAL_HXOP 0xa4bf #define UNITEXT_YI_RADICAL_HXOP L"\ua4bf" #define UNICODE_YI_RADICAL_SHAT 0xa4c0 #define UNITEXT_YI_RADICAL_SHAT L"\ua4c0" #define UNICODE_YI_RADICAL_ZUR 0xa4c1 #define UNITEXT_YI_RADICAL_ZUR L"\ua4c1" #define UNICODE_YI_RADICAL_SHOP 0xa4c2 #define UNITEXT_YI_RADICAL_SHOP L"\ua4c2" #define UNICODE_YI_RADICAL_CHE 0xa4c3 #define UNITEXT_YI_RADICAL_CHE L"\ua4c3" #define UNICODE_YI_RADICAL_ZZIET 0xa4c4 #define UNITEXT_YI_RADICAL_ZZIET L"\ua4c4" #define UNICODE_YI_RADICAL_NBIE 0xa4c5 #define UNITEXT_YI_RADICAL_NBIE L"\ua4c5" #define UNICODE_YI_RADICAL_KE 0xa4c6 #define UNITEXT_YI_RADICAL_KE L"\ua4c6" #define UNICODE_MODIFIER_LETTER_CHINESE_TONE_YIN_PING 0xa700 #define UNITEXT_MODIFIER_LETTER_CHINESE_TONE_YIN_PING L"\ua700" #define UNICODE_MODIFIER_LETTER_CHINESE_TONE_YANG_PING 0xa701 #define UNITEXT_MODIFIER_LETTER_CHINESE_TONE_YANG_PING L"\ua701" #define UNICODE_MODIFIER_LETTER_CHINESE_TONE_YIN_SHANG 0xa702 #define UNITEXT_MODIFIER_LETTER_CHINESE_TONE_YIN_SHANG L"\ua702" #define UNICODE_MODIFIER_LETTER_CHINESE_TONE_YANG_SHANG 0xa703 #define UNITEXT_MODIFIER_LETTER_CHINESE_TONE_YANG_SHANG L"\ua703" #define UNICODE_MODIFIER_LETTER_CHINESE_TONE_YIN_QU 0xa704 #define UNITEXT_MODIFIER_LETTER_CHINESE_TONE_YIN_QU L"\ua704" #define UNICODE_MODIFIER_LETTER_CHINESE_TONE_YANG_QU 0xa705 #define UNITEXT_MODIFIER_LETTER_CHINESE_TONE_YANG_QU L"\ua705" #define UNICODE_MODIFIER_LETTER_CHINESE_TONE_YIN_RU 0xa706 #define UNITEXT_MODIFIER_LETTER_CHINESE_TONE_YIN_RU L"\ua706" #define UNICODE_MODIFIER_LETTER_CHINESE_TONE_YANG_RU 0xa707 #define UNITEXT_MODIFIER_LETTER_CHINESE_TONE_YANG_RU L"\ua707" #define UNICODE_MODIFIER_LETTER_EXTRA_HIGH_DOTTED_TONE_BAR 0xa708 #define UNITEXT_MODIFIER_LETTER_EXTRA_HIGH_DOTTED_TONE_BAR L"\ua708" #define UNICODE_MODIFIER_LETTER_HIGH_DOTTED_TONE_BAR 0xa709 #define UNITEXT_MODIFIER_LETTER_HIGH_DOTTED_TONE_BAR L"\ua709" #define UNICODE_MODIFIER_LETTER_MID_DOTTED_TONE_BAR 0xa70a #define UNITEXT_MODIFIER_LETTER_MID_DOTTED_TONE_BAR L"\ua70a" #define UNICODE_MODIFIER_LETTER_LOW_DOTTED_TONE_BAR 0xa70b #define UNITEXT_MODIFIER_LETTER_LOW_DOTTED_TONE_BAR L"\ua70b" #define UNICODE_MODIFIER_LETTER_EXTRA_LOW_DOTTED_TONE_BAR 0xa70c #define UNITEXT_MODIFIER_LETTER_EXTRA_LOW_DOTTED_TONE_BAR L"\ua70c" #define UNICODE_MODIFIER_LETTER_EXTRA_HIGH_DOTTED_LEFT_STEM_TONE_BAR 0xa70d #define UNITEXT_MODIFIER_LETTER_EXTRA_HIGH_DOTTED_LEFT_STEM_TONE_BAR L"\ua70d" #define UNICODE_MODIFIER_LETTER_HIGH_DOTTED_LEFT_STEM_TONE_BAR 0xa70e #define UNITEXT_MODIFIER_LETTER_HIGH_DOTTED_LEFT_STEM_TONE_BAR L"\ua70e" #define UNICODE_MODIFIER_LETTER_MID_DOTTED_LEFT_STEM_TONE_BAR 0xa70f #define UNITEXT_MODIFIER_LETTER_MID_DOTTED_LEFT_STEM_TONE_BAR L"\ua70f" #define UNICODE_MODIFIER_LETTER_LOW_DOTTED_LEFT_STEM_TONE_BAR 0xa710 #define UNITEXT_MODIFIER_LETTER_LOW_DOTTED_LEFT_STEM_TONE_BAR L"\ua710" #define UNICODE_MODIFIER_LETTER_EXTRA_LOW_DOTTED_LEFT_STEM_TONE_BAR 0xa711 #define UNITEXT_MODIFIER_LETTER_EXTRA_LOW_DOTTED_LEFT_STEM_TONE_BAR L"\ua711" #define UNICODE_MODIFIER_LETTER_EXTRA_HIGH_LEFT_STEM_TONE_BAR 0xa712 #define UNITEXT_MODIFIER_LETTER_EXTRA_HIGH_LEFT_STEM_TONE_BAR L"\ua712" #define UNICODE_MODIFIER_LETTER_HIGH_LEFT_STEM_TONE_BAR 0xa713 #define UNITEXT_MODIFIER_LETTER_HIGH_LEFT_STEM_TONE_BAR L"\ua713" #define UNICODE_MODIFIER_LETTER_MID_LEFT_STEM_TONE_BAR 0xa714 #define UNITEXT_MODIFIER_LETTER_MID_LEFT_STEM_TONE_BAR L"\ua714" #define UNICODE_MODIFIER_LETTER_LOW_LEFT_STEM_TONE_BAR 0xa715 #define UNITEXT_MODIFIER_LETTER_LOW_LEFT_STEM_TONE_BAR L"\ua715" #define UNICODE_MODIFIER_LETTER_EXTRA_LOW_LEFT_STEM_TONE_BAR 0xa716 #define UNITEXT_MODIFIER_LETTER_EXTRA_LOW_LEFT_STEM_TONE_BAR L"\ua716" #define UNICODE_MODIFIER_LETTER_DOT_VERTICAL_BAR 0xa717 #define UNITEXT_MODIFIER_LETTER_DOT_VERTICAL_BAR L"\ua717" #define UNICODE_MODIFIER_LETTER_DOT_SLASH 0xa718 #define UNITEXT_MODIFIER_LETTER_DOT_SLASH L"\ua718" #define UNICODE_MODIFIER_LETTER_DOT_HORIZONTAL_BAR 0xa719 #define UNITEXT_MODIFIER_LETTER_DOT_HORIZONTAL_BAR L"\ua719" #define UNICODE_MODIFIER_LETTER_LOWER_RIGHT_CORNER_ANGLE 0xa71a #define UNITEXT_MODIFIER_LETTER_LOWER_RIGHT_CORNER_ANGLE L"\ua71a" #define UNICODE_MODIFIER_LETTER_STRESS_AND_HIGH_TONE 0xa720 #define UNITEXT_MODIFIER_LETTER_STRESS_AND_HIGH_TONE L"\ua720" #define UNICODE_MODIFIER_LETTER_STRESS_AND_LOW_TONE 0xa721 #define UNITEXT_MODIFIER_LETTER_STRESS_AND_LOW_TONE L"\ua721" #define UNICODE_SYLOTI_NAGRI_LETTER_A 0xa800 #define UNITEXT_SYLOTI_NAGRI_LETTER_A L"\ua800" #define UNICODE_SYLOTI_NAGRI_LETTER_I 0xa801 #define UNITEXT_SYLOTI_NAGRI_LETTER_I L"\ua801" #define UNICODE_SYLOTI_NAGRI_SIGN_DVISVARA 0xa802 #define UNITEXT_SYLOTI_NAGRI_SIGN_DVISVARA L"\ua802" #define UNICODE_SYLOTI_NAGRI_LETTER_U 0xa803 #define UNITEXT_SYLOTI_NAGRI_LETTER_U L"\ua803" #define UNICODE_SYLOTI_NAGRI_LETTER_E 0xa804 #define UNITEXT_SYLOTI_NAGRI_LETTER_E L"\ua804" #define UNICODE_SYLOTI_NAGRI_LETTER_O 0xa805 #define UNITEXT_SYLOTI_NAGRI_LETTER_O L"\ua805" #define UNICODE_SYLOTI_NAGRI_SIGN_HASANTA 0xa806 #define UNITEXT_SYLOTI_NAGRI_SIGN_HASANTA L"\ua806" #define UNICODE_SYLOTI_NAGRI_LETTER_KO 0xa807 #define UNITEXT_SYLOTI_NAGRI_LETTER_KO L"\ua807" #define UNICODE_SYLOTI_NAGRI_LETTER_KHO 0xa808 #define UNITEXT_SYLOTI_NAGRI_LETTER_KHO L"\ua808" #define UNICODE_SYLOTI_NAGRI_LETTER_GO 0xa809 #define UNITEXT_SYLOTI_NAGRI_LETTER_GO L"\ua809" #define UNICODE_SYLOTI_NAGRI_LETTER_GHO 0xa80a #define UNITEXT_SYLOTI_NAGRI_LETTER_GHO L"\ua80a" #define UNICODE_SYLOTI_NAGRI_SIGN_ANUSVARA 0xa80b #define UNITEXT_SYLOTI_NAGRI_SIGN_ANUSVARA L"\ua80b" #define UNICODE_SYLOTI_NAGRI_LETTER_CO 0xa80c #define UNITEXT_SYLOTI_NAGRI_LETTER_CO L"\ua80c" #define UNICODE_SYLOTI_NAGRI_LETTER_CHO 0xa80d #define UNITEXT_SYLOTI_NAGRI_LETTER_CHO L"\ua80d" #define UNICODE_SYLOTI_NAGRI_LETTER_JO 0xa80e #define UNITEXT_SYLOTI_NAGRI_LETTER_JO L"\ua80e" #define UNICODE_SYLOTI_NAGRI_LETTER_JHO 0xa80f #define UNITEXT_SYLOTI_NAGRI_LETTER_JHO L"\ua80f" #define UNICODE_SYLOTI_NAGRI_LETTER_TTO 0xa810 #define UNITEXT_SYLOTI_NAGRI_LETTER_TTO L"\ua810" #define UNICODE_SYLOTI_NAGRI_LETTER_TTHO 0xa811 #define UNITEXT_SYLOTI_NAGRI_LETTER_TTHO L"\ua811" #define UNICODE_SYLOTI_NAGRI_LETTER_DDO 0xa812 #define UNITEXT_SYLOTI_NAGRI_LETTER_DDO L"\ua812" #define UNICODE_SYLOTI_NAGRI_LETTER_DDHO 0xa813 #define UNITEXT_SYLOTI_NAGRI_LETTER_DDHO L"\ua813" #define UNICODE_SYLOTI_NAGRI_LETTER_TO 0xa814 #define UNITEXT_SYLOTI_NAGRI_LETTER_TO L"\ua814" #define UNICODE_SYLOTI_NAGRI_LETTER_THO 0xa815 #define UNITEXT_SYLOTI_NAGRI_LETTER_THO L"\ua815" #define UNICODE_SYLOTI_NAGRI_LETTER_DO 0xa816 #define UNITEXT_SYLOTI_NAGRI_LETTER_DO L"\ua816" #define UNICODE_SYLOTI_NAGRI_LETTER_DHO 0xa817 #define UNITEXT_SYLOTI_NAGRI_LETTER_DHO L"\ua817" #define UNICODE_SYLOTI_NAGRI_LETTER_NO 0xa818 #define UNITEXT_SYLOTI_NAGRI_LETTER_NO L"\ua818" #define UNICODE_SYLOTI_NAGRI_LETTER_PO 0xa819 #define UNITEXT_SYLOTI_NAGRI_LETTER_PO L"\ua819" #define UNICODE_SYLOTI_NAGRI_LETTER_PHO 0xa81a #define UNITEXT_SYLOTI_NAGRI_LETTER_PHO L"\ua81a" #define UNICODE_SYLOTI_NAGRI_LETTER_BO 0xa81b #define UNITEXT_SYLOTI_NAGRI_LETTER_BO L"\ua81b" #define UNICODE_SYLOTI_NAGRI_LETTER_BHO 0xa81c #define UNITEXT_SYLOTI_NAGRI_LETTER_BHO L"\ua81c" #define UNICODE_SYLOTI_NAGRI_LETTER_MO 0xa81d #define UNITEXT_SYLOTI_NAGRI_LETTER_MO L"\ua81d" #define UNICODE_SYLOTI_NAGRI_LETTER_RO 0xa81e #define UNITEXT_SYLOTI_NAGRI_LETTER_RO L"\ua81e" #define UNICODE_SYLOTI_NAGRI_LETTER_LO 0xa81f #define UNITEXT_SYLOTI_NAGRI_LETTER_LO L"\ua81f" #define UNICODE_SYLOTI_NAGRI_LETTER_RRO 0xa820 #define UNITEXT_SYLOTI_NAGRI_LETTER_RRO L"\ua820" #define UNICODE_SYLOTI_NAGRI_LETTER_SO 0xa821 #define UNITEXT_SYLOTI_NAGRI_LETTER_SO L"\ua821" #define UNICODE_SYLOTI_NAGRI_LETTER_HO 0xa822 #define UNITEXT_SYLOTI_NAGRI_LETTER_HO L"\ua822" #define UNICODE_SYLOTI_NAGRI_VOWEL_SIGN_A 0xa823 #define UNITEXT_SYLOTI_NAGRI_VOWEL_SIGN_A L"\ua823" #define UNICODE_SYLOTI_NAGRI_VOWEL_SIGN_I 0xa824 #define UNITEXT_SYLOTI_NAGRI_VOWEL_SIGN_I L"\ua824" #define UNICODE_SYLOTI_NAGRI_VOWEL_SIGN_U 0xa825 #define UNITEXT_SYLOTI_NAGRI_VOWEL_SIGN_U L"\ua825" #define UNICODE_SYLOTI_NAGRI_VOWEL_SIGN_E 0xa826 #define UNITEXT_SYLOTI_NAGRI_VOWEL_SIGN_E L"\ua826" #define UNICODE_SYLOTI_NAGRI_VOWEL_SIGN_OO 0xa827 #define UNITEXT_SYLOTI_NAGRI_VOWEL_SIGN_OO L"\ua827" #define UNICODE_SYLOTI_NAGRI_POETRY_MARK_1 0xa828 #define UNITEXT_SYLOTI_NAGRI_POETRY_MARK_1 L"\ua828" #define UNICODE_SYLOTI_NAGRI_POETRY_MARK_2 0xa829 #define UNITEXT_SYLOTI_NAGRI_POETRY_MARK_2 L"\ua829" #define UNICODE_SYLOTI_NAGRI_POETRY_MARK_3 0xa82a #define UNITEXT_SYLOTI_NAGRI_POETRY_MARK_3 L"\ua82a" #define UNICODE_SYLOTI_NAGRI_POETRY_MARK_4 0xa82b #define UNITEXT_SYLOTI_NAGRI_POETRY_MARK_4 L"\ua82b" #define UNICODE_PHAGS_PA_LETTER_KA 0xa840 #define UNITEXT_PHAGS_PA_LETTER_KA L"\ua840" #define UNICODE_PHAGS_PA_LETTER_KHA 0xa841 #define UNITEXT_PHAGS_PA_LETTER_KHA L"\ua841" #define UNICODE_PHAGS_PA_LETTER_GA 0xa842 #define UNITEXT_PHAGS_PA_LETTER_GA L"\ua842" #define UNICODE_PHAGS_PA_LETTER_NGA 0xa843 #define UNITEXT_PHAGS_PA_LETTER_NGA L"\ua843" #define UNICODE_PHAGS_PA_LETTER_CA 0xa844 #define UNITEXT_PHAGS_PA_LETTER_CA L"\ua844" #define UNICODE_PHAGS_PA_LETTER_CHA 0xa845 #define UNITEXT_PHAGS_PA_LETTER_CHA L"\ua845" #define UNICODE_PHAGS_PA_LETTER_JA 0xa846 #define UNITEXT_PHAGS_PA_LETTER_JA L"\ua846" #define UNICODE_PHAGS_PA_LETTER_NYA 0xa847 #define UNITEXT_PHAGS_PA_LETTER_NYA L"\ua847" #define UNICODE_PHAGS_PA_LETTER_TA 0xa848 #define UNITEXT_PHAGS_PA_LETTER_TA L"\ua848" #define UNICODE_PHAGS_PA_LETTER_THA 0xa849 #define UNITEXT_PHAGS_PA_LETTER_THA L"\ua849" #define UNICODE_PHAGS_PA_LETTER_DA 0xa84a #define UNITEXT_PHAGS_PA_LETTER_DA L"\ua84a" #define UNICODE_PHAGS_PA_LETTER_NA 0xa84b #define UNITEXT_PHAGS_PA_LETTER_NA L"\ua84b" #define UNICODE_PHAGS_PA_LETTER_PA 0xa84c #define UNITEXT_PHAGS_PA_LETTER_PA L"\ua84c" #define UNICODE_PHAGS_PA_LETTER_PHA 0xa84d #define UNITEXT_PHAGS_PA_LETTER_PHA L"\ua84d" #define UNICODE_PHAGS_PA_LETTER_BA 0xa84e #define UNITEXT_PHAGS_PA_LETTER_BA L"\ua84e" #define UNICODE_PHAGS_PA_LETTER_MA 0xa84f #define UNITEXT_PHAGS_PA_LETTER_MA L"\ua84f" #define UNICODE_PHAGS_PA_LETTER_TSA 0xa850 #define UNITEXT_PHAGS_PA_LETTER_TSA L"\ua850" #define UNICODE_PHAGS_PA_LETTER_TSHA 0xa851 #define UNITEXT_PHAGS_PA_LETTER_TSHA L"\ua851" #define UNICODE_PHAGS_PA_LETTER_DZA 0xa852 #define UNITEXT_PHAGS_PA_LETTER_DZA L"\ua852" #define UNICODE_PHAGS_PA_LETTER_WA 0xa853 #define UNITEXT_PHAGS_PA_LETTER_WA L"\ua853" #define UNICODE_PHAGS_PA_LETTER_ZHA 0xa854 #define UNITEXT_PHAGS_PA_LETTER_ZHA L"\ua854" #define UNICODE_PHAGS_PA_LETTER_ZA 0xa855 #define UNITEXT_PHAGS_PA_LETTER_ZA L"\ua855" #define UNICODE_PHAGS_PA_LETTER_SMALL_A 0xa856 #define UNITEXT_PHAGS_PA_LETTER_SMALL_A L"\ua856" #define UNICODE_PHAGS_PA_LETTER_YA 0xa857 #define UNITEXT_PHAGS_PA_LETTER_YA L"\ua857" #define UNICODE_PHAGS_PA_LETTER_RA 0xa858 #define UNITEXT_PHAGS_PA_LETTER_RA L"\ua858" #define UNICODE_PHAGS_PA_LETTER_LA 0xa859 #define UNITEXT_PHAGS_PA_LETTER_LA L"\ua859" #define UNICODE_PHAGS_PA_LETTER_SHA 0xa85a #define UNITEXT_PHAGS_PA_LETTER_SHA L"\ua85a" #define UNICODE_PHAGS_PA_LETTER_SA 0xa85b #define UNITEXT_PHAGS_PA_LETTER_SA L"\ua85b" #define UNICODE_PHAGS_PA_LETTER_HA 0xa85c #define UNITEXT_PHAGS_PA_LETTER_HA L"\ua85c" #define UNICODE_PHAGS_PA_LETTER_A 0xa85d #define UNITEXT_PHAGS_PA_LETTER_A L"\ua85d" #define UNICODE_PHAGS_PA_LETTER_I 0xa85e #define UNITEXT_PHAGS_PA_LETTER_I L"\ua85e" #define UNICODE_PHAGS_PA_LETTER_U 0xa85f #define UNITEXT_PHAGS_PA_LETTER_U L"\ua85f" #define UNICODE_PHAGS_PA_LETTER_E 0xa860 #define UNITEXT_PHAGS_PA_LETTER_E L"\ua860" #define UNICODE_PHAGS_PA_LETTER_O 0xa861 #define UNITEXT_PHAGS_PA_LETTER_O L"\ua861" #define UNICODE_PHAGS_PA_LETTER_QA 0xa862 #define UNITEXT_PHAGS_PA_LETTER_QA L"\ua862" #define UNICODE_PHAGS_PA_LETTER_XA 0xa863 #define UNITEXT_PHAGS_PA_LETTER_XA L"\ua863" #define UNICODE_PHAGS_PA_LETTER_FA 0xa864 #define UNITEXT_PHAGS_PA_LETTER_FA L"\ua864" #define UNICODE_PHAGS_PA_LETTER_GGA 0xa865 #define UNITEXT_PHAGS_PA_LETTER_GGA L"\ua865" #define UNICODE_PHAGS_PA_LETTER_EE 0xa866 #define UNITEXT_PHAGS_PA_LETTER_EE L"\ua866" #define UNICODE_PHAGS_PA_SUBJOINED_LETTER_WA 0xa867 #define UNITEXT_PHAGS_PA_SUBJOINED_LETTER_WA L"\ua867" #define UNICODE_PHAGS_PA_SUBJOINED_LETTER_YA 0xa868 #define UNITEXT_PHAGS_PA_SUBJOINED_LETTER_YA L"\ua868" #define UNICODE_PHAGS_PA_LETTER_TTA 0xa869 #define UNITEXT_PHAGS_PA_LETTER_TTA L"\ua869" #define UNICODE_PHAGS_PA_LETTER_TTHA 0xa86a #define UNITEXT_PHAGS_PA_LETTER_TTHA L"\ua86a" #define UNICODE_PHAGS_PA_LETTER_DDA 0xa86b #define UNITEXT_PHAGS_PA_LETTER_DDA L"\ua86b" #define UNICODE_PHAGS_PA_LETTER_NNA 0xa86c #define UNITEXT_PHAGS_PA_LETTER_NNA L"\ua86c" #define UNICODE_PHAGS_PA_LETTER_ALTERNATE_YA 0xa86d #define UNITEXT_PHAGS_PA_LETTER_ALTERNATE_YA L"\ua86d" #define UNICODE_PHAGS_PA_LETTER_VOICELESS_SHA 0xa86e #define UNITEXT_PHAGS_PA_LETTER_VOICELESS_SHA L"\ua86e" #define UNICODE_PHAGS_PA_LETTER_VOICED_HA 0xa86f #define UNITEXT_PHAGS_PA_LETTER_VOICED_HA L"\ua86f" #define UNICODE_PHAGS_PA_LETTER_ASPIRATED_FA 0xa870 #define UNITEXT_PHAGS_PA_LETTER_ASPIRATED_FA L"\ua870" #define UNICODE_PHAGS_PA_SUBJOINED_LETTER_RA 0xa871 #define UNITEXT_PHAGS_PA_SUBJOINED_LETTER_RA L"\ua871" #define UNICODE_PHAGS_PA_SUPERFIXED_LETTER_RA 0xa872 #define UNITEXT_PHAGS_PA_SUPERFIXED_LETTER_RA L"\ua872" #define UNICODE_PHAGS_PA_LETTER_CANDRABINDU 0xa873 #define UNITEXT_PHAGS_PA_LETTER_CANDRABINDU L"\ua873" #define UNICODE_PHAGS_PA_SINGLE_HEAD_MARK 0xa874 #define UNITEXT_PHAGS_PA_SINGLE_HEAD_MARK L"\ua874" #define UNICODE_PHAGS_PA_DOUBLE_HEAD_MARK 0xa875 #define UNITEXT_PHAGS_PA_DOUBLE_HEAD_MARK L"\ua875" #define UNICODE_PHAGS_PA_MARK_SHAD 0xa876 #define UNITEXT_PHAGS_PA_MARK_SHAD L"\ua876" #define UNICODE_PHAGS_PA_MARK_DOUBLE_SHAD 0xa877 #define UNITEXT_PHAGS_PA_MARK_DOUBLE_SHAD L"\ua877" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F900 0xf900 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F900 L"\uf900" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F901 0xf901 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F901 L"\uf901" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F902 0xf902 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F902 L"\uf902" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F903 0xf903 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F903 L"\uf903" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F904 0xf904 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F904 L"\uf904" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F905 0xf905 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F905 L"\uf905" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F906 0xf906 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F906 L"\uf906" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F907 0xf907 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F907 L"\uf907" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F908 0xf908 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F908 L"\uf908" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F909 0xf909 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F909 L"\uf909" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F90A 0xf90a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F90A L"\uf90a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F90B 0xf90b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F90B L"\uf90b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F90C 0xf90c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F90C L"\uf90c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F90D 0xf90d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F90D L"\uf90d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F90E 0xf90e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F90E L"\uf90e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F90F 0xf90f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F90F L"\uf90f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F910 0xf910 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F910 L"\uf910" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F911 0xf911 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F911 L"\uf911" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F912 0xf912 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F912 L"\uf912" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F913 0xf913 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F913 L"\uf913" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F914 0xf914 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F914 L"\uf914" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F915 0xf915 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F915 L"\uf915" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F916 0xf916 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F916 L"\uf916" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F917 0xf917 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F917 L"\uf917" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F918 0xf918 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F918 L"\uf918" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F919 0xf919 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F919 L"\uf919" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F91A 0xf91a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F91A L"\uf91a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F91B 0xf91b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F91B L"\uf91b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F91C 0xf91c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F91C L"\uf91c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F91D 0xf91d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F91D L"\uf91d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F91E 0xf91e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F91E L"\uf91e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F91F 0xf91f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F91F L"\uf91f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F920 0xf920 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F920 L"\uf920" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F921 0xf921 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F921 L"\uf921" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F922 0xf922 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F922 L"\uf922" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F923 0xf923 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F923 L"\uf923" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F924 0xf924 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F924 L"\uf924" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F925 0xf925 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F925 L"\uf925" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F926 0xf926 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F926 L"\uf926" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F927 0xf927 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F927 L"\uf927" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F928 0xf928 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F928 L"\uf928" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F929 0xf929 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F929 L"\uf929" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F92A 0xf92a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F92A L"\uf92a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F92B 0xf92b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F92B L"\uf92b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F92C 0xf92c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F92C L"\uf92c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F92D 0xf92d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F92D L"\uf92d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F92E 0xf92e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F92E L"\uf92e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F92F 0xf92f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F92F L"\uf92f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F930 0xf930 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F930 L"\uf930" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F931 0xf931 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F931 L"\uf931" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F932 0xf932 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F932 L"\uf932" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F933 0xf933 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F933 L"\uf933" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F934 0xf934 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F934 L"\uf934" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F935 0xf935 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F935 L"\uf935" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F936 0xf936 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F936 L"\uf936" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F937 0xf937 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F937 L"\uf937" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F938 0xf938 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F938 L"\uf938" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F939 0xf939 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F939 L"\uf939" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F93A 0xf93a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F93A L"\uf93a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F93B 0xf93b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F93B L"\uf93b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F93C 0xf93c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F93C L"\uf93c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F93D 0xf93d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F93D L"\uf93d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F93E 0xf93e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F93E L"\uf93e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F93F 0xf93f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F93F L"\uf93f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F940 0xf940 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F940 L"\uf940" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F941 0xf941 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F941 L"\uf941" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F942 0xf942 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F942 L"\uf942" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F943 0xf943 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F943 L"\uf943" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F944 0xf944 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F944 L"\uf944" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F945 0xf945 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F945 L"\uf945" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F946 0xf946 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F946 L"\uf946" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F947 0xf947 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F947 L"\uf947" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F948 0xf948 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F948 L"\uf948" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F949 0xf949 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F949 L"\uf949" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F94A 0xf94a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F94A L"\uf94a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F94B 0xf94b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F94B L"\uf94b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F94C 0xf94c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F94C L"\uf94c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F94D 0xf94d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F94D L"\uf94d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F94E 0xf94e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F94E L"\uf94e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F94F 0xf94f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F94F L"\uf94f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F950 0xf950 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F950 L"\uf950" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F951 0xf951 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F951 L"\uf951" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F952 0xf952 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F952 L"\uf952" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F953 0xf953 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F953 L"\uf953" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F954 0xf954 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F954 L"\uf954" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F955 0xf955 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F955 L"\uf955" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F956 0xf956 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F956 L"\uf956" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F957 0xf957 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F957 L"\uf957" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F958 0xf958 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F958 L"\uf958" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F959 0xf959 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F959 L"\uf959" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F95A 0xf95a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F95A L"\uf95a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F95B 0xf95b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F95B L"\uf95b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F95C 0xf95c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F95C L"\uf95c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F95D 0xf95d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F95D L"\uf95d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F95E 0xf95e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F95E L"\uf95e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F95F 0xf95f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F95F L"\uf95f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F960 0xf960 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F960 L"\uf960" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F961 0xf961 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F961 L"\uf961" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F962 0xf962 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F962 L"\uf962" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F963 0xf963 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F963 L"\uf963" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F964 0xf964 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F964 L"\uf964" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F965 0xf965 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F965 L"\uf965" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F966 0xf966 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F966 L"\uf966" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F967 0xf967 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F967 L"\uf967" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F968 0xf968 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F968 L"\uf968" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F969 0xf969 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F969 L"\uf969" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F96A 0xf96a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F96A L"\uf96a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F96B 0xf96b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F96B L"\uf96b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F96C 0xf96c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F96C L"\uf96c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F96D 0xf96d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F96D L"\uf96d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F96E 0xf96e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F96E L"\uf96e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F96F 0xf96f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F96F L"\uf96f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F970 0xf970 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F970 L"\uf970" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F971 0xf971 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F971 L"\uf971" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F972 0xf972 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F972 L"\uf972" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F973 0xf973 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F973 L"\uf973" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F974 0xf974 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F974 L"\uf974" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F975 0xf975 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F975 L"\uf975" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F976 0xf976 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F976 L"\uf976" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F977 0xf977 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F977 L"\uf977" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F978 0xf978 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F978 L"\uf978" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F979 0xf979 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F979 L"\uf979" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F97A 0xf97a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F97A L"\uf97a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F97B 0xf97b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F97B L"\uf97b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F97C 0xf97c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F97C L"\uf97c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F97D 0xf97d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F97D L"\uf97d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F97E 0xf97e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F97E L"\uf97e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F97F 0xf97f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F97F L"\uf97f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F980 0xf980 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F980 L"\uf980" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F981 0xf981 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F981 L"\uf981" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F982 0xf982 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F982 L"\uf982" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F983 0xf983 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F983 L"\uf983" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F984 0xf984 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F984 L"\uf984" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F985 0xf985 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F985 L"\uf985" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F986 0xf986 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F986 L"\uf986" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F987 0xf987 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F987 L"\uf987" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F988 0xf988 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F988 L"\uf988" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F989 0xf989 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F989 L"\uf989" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F98A 0xf98a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F98A L"\uf98a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F98B 0xf98b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F98B L"\uf98b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F98C 0xf98c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F98C L"\uf98c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F98D 0xf98d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F98D L"\uf98d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F98E 0xf98e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F98E L"\uf98e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F98F 0xf98f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F98F L"\uf98f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F990 0xf990 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F990 L"\uf990" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F991 0xf991 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F991 L"\uf991" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F992 0xf992 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F992 L"\uf992" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F993 0xf993 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F993 L"\uf993" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F994 0xf994 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F994 L"\uf994" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F995 0xf995 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F995 L"\uf995" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F996 0xf996 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F996 L"\uf996" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F997 0xf997 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F997 L"\uf997" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F998 0xf998 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F998 L"\uf998" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F999 0xf999 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F999 L"\uf999" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F99A 0xf99a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F99A L"\uf99a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F99B 0xf99b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F99B L"\uf99b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F99C 0xf99c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F99C L"\uf99c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F99D 0xf99d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F99D L"\uf99d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F99E 0xf99e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F99E L"\uf99e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F99F 0xf99f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F99F L"\uf99f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A0 0xf9a0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A0 L"\uf9a0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A1 0xf9a1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A1 L"\uf9a1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A2 0xf9a2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A2 L"\uf9a2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A3 0xf9a3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A3 L"\uf9a3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A4 0xf9a4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A4 L"\uf9a4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A5 0xf9a5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A5 L"\uf9a5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A6 0xf9a6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A6 L"\uf9a6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A7 0xf9a7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A7 L"\uf9a7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A8 0xf9a8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A8 L"\uf9a8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9A9 0xf9a9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9A9 L"\uf9a9" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9AA 0xf9aa #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9AA L"\uf9aa" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9AB 0xf9ab #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9AB L"\uf9ab" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9AC 0xf9ac #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9AC L"\uf9ac" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9AD 0xf9ad #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9AD L"\uf9ad" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9AE 0xf9ae #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9AE L"\uf9ae" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9AF 0xf9af #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9AF L"\uf9af" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B0 0xf9b0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B0 L"\uf9b0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B1 0xf9b1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B1 L"\uf9b1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B2 0xf9b2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B2 L"\uf9b2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B3 0xf9b3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B3 L"\uf9b3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B4 0xf9b4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B4 L"\uf9b4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B5 0xf9b5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B5 L"\uf9b5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B6 0xf9b6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B6 L"\uf9b6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B7 0xf9b7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B7 L"\uf9b7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B8 0xf9b8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B8 L"\uf9b8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9B9 0xf9b9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9B9 L"\uf9b9" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9BA 0xf9ba #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9BA L"\uf9ba" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9BB 0xf9bb #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9BB L"\uf9bb" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9BC 0xf9bc #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9BC L"\uf9bc" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9BD 0xf9bd #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9BD L"\uf9bd" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9BE 0xf9be #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9BE L"\uf9be" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9BF 0xf9bf #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9BF L"\uf9bf" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C0 0xf9c0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C0 L"\uf9c0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C1 0xf9c1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C1 L"\uf9c1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C2 0xf9c2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C2 L"\uf9c2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C3 0xf9c3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C3 L"\uf9c3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C4 0xf9c4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C4 L"\uf9c4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C5 0xf9c5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C5 L"\uf9c5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C6 0xf9c6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C6 L"\uf9c6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C7 0xf9c7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C7 L"\uf9c7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C8 0xf9c8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C8 L"\uf9c8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9C9 0xf9c9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9C9 L"\uf9c9" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9CA 0xf9ca #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9CA L"\uf9ca" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9CB 0xf9cb #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9CB L"\uf9cb" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9CC 0xf9cc #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9CC L"\uf9cc" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9CD 0xf9cd #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9CD L"\uf9cd" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9CE 0xf9ce #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9CE L"\uf9ce" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9CF 0xf9cf #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9CF L"\uf9cf" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D0 0xf9d0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D0 L"\uf9d0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D1 0xf9d1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D1 L"\uf9d1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D2 0xf9d2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D2 L"\uf9d2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D3 0xf9d3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D3 L"\uf9d3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D4 0xf9d4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D4 L"\uf9d4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D5 0xf9d5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D5 L"\uf9d5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D6 0xf9d6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D6 L"\uf9d6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D7 0xf9d7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D7 L"\uf9d7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D8 0xf9d8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D8 L"\uf9d8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9D9 0xf9d9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9D9 L"\uf9d9" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9DA 0xf9da #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9DA L"\uf9da" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9DB 0xf9db #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9DB L"\uf9db" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9DC 0xf9dc #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9DC L"\uf9dc" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9DD 0xf9dd #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9DD L"\uf9dd" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9DE 0xf9de #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9DE L"\uf9de" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9DF 0xf9df #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9DF L"\uf9df" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E0 0xf9e0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E0 L"\uf9e0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E1 0xf9e1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E1 L"\uf9e1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E2 0xf9e2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E2 L"\uf9e2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E3 0xf9e3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E3 L"\uf9e3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E4 0xf9e4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E4 L"\uf9e4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E5 0xf9e5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E5 L"\uf9e5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E6 0xf9e6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E6 L"\uf9e6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E7 0xf9e7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E7 L"\uf9e7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E8 0xf9e8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E8 L"\uf9e8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9E9 0xf9e9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9E9 L"\uf9e9" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9EA 0xf9ea #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9EA L"\uf9ea" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9EB 0xf9eb #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9EB L"\uf9eb" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9EC 0xf9ec #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9EC L"\uf9ec" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9ED 0xf9ed #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9ED L"\uf9ed" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9EE 0xf9ee #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9EE L"\uf9ee" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9EF 0xf9ef #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9EF L"\uf9ef" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F0 0xf9f0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F0 L"\uf9f0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F1 0xf9f1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F1 L"\uf9f1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F2 0xf9f2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F2 L"\uf9f2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F3 0xf9f3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F3 L"\uf9f3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F4 0xf9f4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F4 L"\uf9f4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F5 0xf9f5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F5 L"\uf9f5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F6 0xf9f6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F6 L"\uf9f6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F7 0xf9f7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F7 L"\uf9f7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F8 0xf9f8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F8 L"\uf9f8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9F9 0xf9f9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9F9 L"\uf9f9" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9FA 0xf9fa #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9FA L"\uf9fa" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9FB 0xf9fb #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9FB L"\uf9fb" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9FC 0xf9fc #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9FC L"\uf9fc" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9FD 0xf9fd #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9FD L"\uf9fd" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9FE 0xf9fe #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9FE L"\uf9fe" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_F9FF 0xf9ff #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_F9FF L"\uf9ff" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA00 0xfa00 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA00 L"\ufa00" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA01 0xfa01 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA01 L"\ufa01" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA02 0xfa02 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA02 L"\ufa02" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA03 0xfa03 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA03 L"\ufa03" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA04 0xfa04 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA04 L"\ufa04" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA05 0xfa05 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA05 L"\ufa05" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA06 0xfa06 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA06 L"\ufa06" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA07 0xfa07 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA07 L"\ufa07" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA08 0xfa08 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA08 L"\ufa08" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA09 0xfa09 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA09 L"\ufa09" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA0A 0xfa0a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA0A L"\ufa0a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA0B 0xfa0b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA0B L"\ufa0b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA0C 0xfa0c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA0C L"\ufa0c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA0D 0xfa0d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA0D L"\ufa0d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA0E 0xfa0e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA0E L"\ufa0e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA0F 0xfa0f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA0F L"\ufa0f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA10 0xfa10 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA10 L"\ufa10" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA11 0xfa11 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA11 L"\ufa11" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA12 0xfa12 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA12 L"\ufa12" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA13 0xfa13 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA13 L"\ufa13" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA14 0xfa14 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA14 L"\ufa14" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA15 0xfa15 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA15 L"\ufa15" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA16 0xfa16 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA16 L"\ufa16" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA17 0xfa17 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA17 L"\ufa17" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA18 0xfa18 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA18 L"\ufa18" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA19 0xfa19 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA19 L"\ufa19" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA1A 0xfa1a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA1A L"\ufa1a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA1B 0xfa1b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA1B L"\ufa1b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA1C 0xfa1c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA1C L"\ufa1c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA1D 0xfa1d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA1D L"\ufa1d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA1E 0xfa1e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA1E L"\ufa1e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA1F 0xfa1f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA1F L"\ufa1f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA20 0xfa20 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA20 L"\ufa20" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA21 0xfa21 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA21 L"\ufa21" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA22 0xfa22 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA22 L"\ufa22" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA23 0xfa23 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA23 L"\ufa23" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA24 0xfa24 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA24 L"\ufa24" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA25 0xfa25 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA25 L"\ufa25" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA26 0xfa26 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA26 L"\ufa26" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA27 0xfa27 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA27 L"\ufa27" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA28 0xfa28 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA28 L"\ufa28" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA29 0xfa29 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA29 L"\ufa29" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA2A 0xfa2a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA2A L"\ufa2a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA2B 0xfa2b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA2B L"\ufa2b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA2C 0xfa2c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA2C L"\ufa2c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA2D 0xfa2d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA2D L"\ufa2d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA30 0xfa30 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA30 L"\ufa30" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA31 0xfa31 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA31 L"\ufa31" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA32 0xfa32 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA32 L"\ufa32" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA33 0xfa33 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA33 L"\ufa33" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA34 0xfa34 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA34 L"\ufa34" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA35 0xfa35 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA35 L"\ufa35" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA36 0xfa36 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA36 L"\ufa36" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA37 0xfa37 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA37 L"\ufa37" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA38 0xfa38 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA38 L"\ufa38" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA39 0xfa39 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA39 L"\ufa39" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA3A 0xfa3a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA3A L"\ufa3a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA3B 0xfa3b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA3B L"\ufa3b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA3C 0xfa3c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA3C L"\ufa3c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA3D 0xfa3d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA3D L"\ufa3d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA3E 0xfa3e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA3E L"\ufa3e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA3F 0xfa3f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA3F L"\ufa3f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA40 0xfa40 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA40 L"\ufa40" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA41 0xfa41 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA41 L"\ufa41" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA42 0xfa42 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA42 L"\ufa42" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA43 0xfa43 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA43 L"\ufa43" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA44 0xfa44 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA44 L"\ufa44" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA45 0xfa45 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA45 L"\ufa45" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA46 0xfa46 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA46 L"\ufa46" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA47 0xfa47 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA47 L"\ufa47" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA48 0xfa48 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA48 L"\ufa48" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA49 0xfa49 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA49 L"\ufa49" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA4A 0xfa4a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA4A L"\ufa4a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA4B 0xfa4b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA4B L"\ufa4b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA4C 0xfa4c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA4C L"\ufa4c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA4D 0xfa4d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA4D L"\ufa4d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA4E 0xfa4e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA4E L"\ufa4e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA4F 0xfa4f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA4F L"\ufa4f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA50 0xfa50 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA50 L"\ufa50" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA51 0xfa51 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA51 L"\ufa51" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA52 0xfa52 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA52 L"\ufa52" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA53 0xfa53 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA53 L"\ufa53" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA54 0xfa54 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA54 L"\ufa54" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA55 0xfa55 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA55 L"\ufa55" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA56 0xfa56 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA56 L"\ufa56" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA57 0xfa57 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA57 L"\ufa57" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA58 0xfa58 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA58 L"\ufa58" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA59 0xfa59 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA59 L"\ufa59" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA5A 0xfa5a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA5A L"\ufa5a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA5B 0xfa5b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA5B L"\ufa5b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA5C 0xfa5c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA5C L"\ufa5c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA5D 0xfa5d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA5D L"\ufa5d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA5E 0xfa5e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA5E L"\ufa5e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA5F 0xfa5f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA5F L"\ufa5f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA60 0xfa60 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA60 L"\ufa60" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA61 0xfa61 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA61 L"\ufa61" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA62 0xfa62 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA62 L"\ufa62" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA63 0xfa63 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA63 L"\ufa63" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA64 0xfa64 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA64 L"\ufa64" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA65 0xfa65 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA65 L"\ufa65" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA66 0xfa66 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA66 L"\ufa66" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA67 0xfa67 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA67 L"\ufa67" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA68 0xfa68 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA68 L"\ufa68" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA69 0xfa69 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA69 L"\ufa69" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA6A 0xfa6a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA6A L"\ufa6a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA70 0xfa70 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA70 L"\ufa70" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA71 0xfa71 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA71 L"\ufa71" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA72 0xfa72 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA72 L"\ufa72" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA73 0xfa73 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA73 L"\ufa73" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA74 0xfa74 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA74 L"\ufa74" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA75 0xfa75 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA75 L"\ufa75" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA76 0xfa76 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA76 L"\ufa76" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA77 0xfa77 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA77 L"\ufa77" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA78 0xfa78 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA78 L"\ufa78" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA79 0xfa79 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA79 L"\ufa79" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA7A 0xfa7a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA7A L"\ufa7a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA7B 0xfa7b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA7B L"\ufa7b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA7C 0xfa7c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA7C L"\ufa7c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA7D 0xfa7d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA7D L"\ufa7d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA7E 0xfa7e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA7E L"\ufa7e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA7F 0xfa7f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA7F L"\ufa7f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA80 0xfa80 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA80 L"\ufa80" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA81 0xfa81 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA81 L"\ufa81" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA82 0xfa82 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA82 L"\ufa82" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA83 0xfa83 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA83 L"\ufa83" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA84 0xfa84 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA84 L"\ufa84" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA85 0xfa85 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA85 L"\ufa85" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA86 0xfa86 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA86 L"\ufa86" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA87 0xfa87 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA87 L"\ufa87" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA88 0xfa88 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA88 L"\ufa88" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA89 0xfa89 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA89 L"\ufa89" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA8A 0xfa8a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA8A L"\ufa8a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA8B 0xfa8b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA8B L"\ufa8b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA8C 0xfa8c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA8C L"\ufa8c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA8D 0xfa8d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA8D L"\ufa8d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA8E 0xfa8e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA8E L"\ufa8e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA8F 0xfa8f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA8F L"\ufa8f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA90 0xfa90 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA90 L"\ufa90" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA91 0xfa91 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA91 L"\ufa91" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA92 0xfa92 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA92 L"\ufa92" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA93 0xfa93 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA93 L"\ufa93" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA94 0xfa94 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA94 L"\ufa94" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA95 0xfa95 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA95 L"\ufa95" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA96 0xfa96 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA96 L"\ufa96" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA97 0xfa97 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA97 L"\ufa97" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA98 0xfa98 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA98 L"\ufa98" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA99 0xfa99 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA99 L"\ufa99" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA9A 0xfa9a #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA9A L"\ufa9a" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA9B 0xfa9b #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA9B L"\ufa9b" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA9C 0xfa9c #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA9C L"\ufa9c" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA9D 0xfa9d #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA9D L"\ufa9d" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA9E 0xfa9e #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA9E L"\ufa9e" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FA9F 0xfa9f #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FA9F L"\ufa9f" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA0 0xfaa0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA0 L"\ufaa0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA1 0xfaa1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA1 L"\ufaa1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA2 0xfaa2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA2 L"\ufaa2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA3 0xfaa3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA3 L"\ufaa3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA4 0xfaa4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA4 L"\ufaa4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA5 0xfaa5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA5 L"\ufaa5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA6 0xfaa6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA6 L"\ufaa6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA7 0xfaa7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA7 L"\ufaa7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA8 0xfaa8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA8 L"\ufaa8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAA9 0xfaa9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAA9 L"\ufaa9" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAAA 0xfaaa #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAAA L"\ufaaa" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAAB 0xfaab #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAAB L"\ufaab" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAAC 0xfaac #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAAC L"\ufaac" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAAD 0xfaad #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAAD L"\ufaad" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAAE 0xfaae #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAAE L"\ufaae" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAAF 0xfaaf #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAAF L"\ufaaf" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB0 0xfab0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB0 L"\ufab0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB1 0xfab1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB1 L"\ufab1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB2 0xfab2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB2 L"\ufab2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB3 0xfab3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB3 L"\ufab3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB4 0xfab4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB4 L"\ufab4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB5 0xfab5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB5 L"\ufab5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB6 0xfab6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB6 L"\ufab6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB7 0xfab7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB7 L"\ufab7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB8 0xfab8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB8 L"\ufab8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAB9 0xfab9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAB9 L"\ufab9" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FABA 0xfaba #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FABA L"\ufaba" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FABB 0xfabb #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FABB L"\ufabb" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FABC 0xfabc #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FABC L"\ufabc" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FABD 0xfabd #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FABD L"\ufabd" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FABE 0xfabe #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FABE L"\ufabe" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FABF 0xfabf #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FABF L"\ufabf" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC0 0xfac0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC0 L"\ufac0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC1 0xfac1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC1 L"\ufac1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC2 0xfac2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC2 L"\ufac2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC3 0xfac3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC3 L"\ufac3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC4 0xfac4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC4 L"\ufac4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC5 0xfac5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC5 L"\ufac5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC6 0xfac6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC6 L"\ufac6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC7 0xfac7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC7 L"\ufac7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC8 0xfac8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC8 L"\ufac8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAC9 0xfac9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAC9 L"\ufac9" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FACA 0xfaca #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FACA L"\ufaca" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FACB 0xfacb #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FACB L"\ufacb" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FACC 0xfacc #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FACC L"\ufacc" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FACD 0xfacd #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FACD L"\ufacd" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FACE 0xface #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FACE L"\uface" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FACF 0xfacf #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FACF L"\ufacf" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD0 0xfad0 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD0 L"\ufad0" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD1 0xfad1 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD1 L"\ufad1" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD2 0xfad2 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD2 L"\ufad2" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD3 0xfad3 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD3 L"\ufad3" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD4 0xfad4 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD4 L"\ufad4" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD5 0xfad5 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD5 L"\ufad5" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD6 0xfad6 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD6 L"\ufad6" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD7 0xfad7 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD7 L"\ufad7" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD8 0xfad8 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD8 L"\ufad8" #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_FAD9 0xfad9 #define UNITEXT_CJK_COMPATIBILITY_IDEOGRAPH_FAD9 L"\ufad9" #define UNICODE_LATIN_SMALL_LIGATURE_FF 0xfb00 #define UNITEXT_LATIN_SMALL_LIGATURE_FF L"\ufb00" #define UNICODE_LATIN_SMALL_LIGATURE_FI 0xfb01 #define UNITEXT_LATIN_SMALL_LIGATURE_FI L"\ufb01" #define UNICODE_LATIN_SMALL_LIGATURE_FL 0xfb02 #define UNITEXT_LATIN_SMALL_LIGATURE_FL L"\ufb02" #define UNICODE_LATIN_SMALL_LIGATURE_FFI 0xfb03 #define UNITEXT_LATIN_SMALL_LIGATURE_FFI L"\ufb03" #define UNICODE_LATIN_SMALL_LIGATURE_FFL 0xfb04 #define UNITEXT_LATIN_SMALL_LIGATURE_FFL L"\ufb04" #define UNICODE_LATIN_SMALL_LIGATURE_LONG_S_T 0xfb05 #define UNITEXT_LATIN_SMALL_LIGATURE_LONG_S_T L"\ufb05" #define UNICODE_LATIN_SMALL_LIGATURE_ST 0xfb06 #define UNITEXT_LATIN_SMALL_LIGATURE_ST L"\ufb06" #define UNICODE_ARMENIAN_SMALL_LIGATURE_MEN_NOW 0xfb13 #define UNITEXT_ARMENIAN_SMALL_LIGATURE_MEN_NOW L"\ufb13" #define UNICODE_ARMENIAN_SMALL_LIGATURE_MEN_ECH 0xfb14 #define UNITEXT_ARMENIAN_SMALL_LIGATURE_MEN_ECH L"\ufb14" #define UNICODE_ARMENIAN_SMALL_LIGATURE_MEN_INI 0xfb15 #define UNITEXT_ARMENIAN_SMALL_LIGATURE_MEN_INI L"\ufb15" #define UNICODE_ARMENIAN_SMALL_LIGATURE_VEW_NOW 0xfb16 #define UNITEXT_ARMENIAN_SMALL_LIGATURE_VEW_NOW L"\ufb16" #define UNICODE_ARMENIAN_SMALL_LIGATURE_MEN_XEH 0xfb17 #define UNITEXT_ARMENIAN_SMALL_LIGATURE_MEN_XEH L"\ufb17" #define UNICODE_HEBREW_LETTER_YOD_WITH_HIRIQ 0xfb1d #define UNITEXT_HEBREW_LETTER_YOD_WITH_HIRIQ L"\ufb1d" #define UNICODE_HEBREW_POINT_JUDEO_SPANISH_VARIKA 0xfb1e #define UNITEXT_HEBREW_POINT_JUDEO_SPANISH_VARIKA L"\ufb1e" #define UNICODE_HEBREW_LIGATURE_YIDDISH_YOD_YOD_PATAH 0xfb1f #define UNITEXT_HEBREW_LIGATURE_YIDDISH_YOD_YOD_PATAH L"\ufb1f" #define UNICODE_HEBREW_LETTER_ALTERNATIVE_AYIN 0xfb20 #define UNITEXT_HEBREW_LETTER_ALTERNATIVE_AYIN L"\ufb20" #define UNICODE_HEBREW_LETTER_WIDE_ALEF 0xfb21 #define UNITEXT_HEBREW_LETTER_WIDE_ALEF L"\ufb21" #define UNICODE_HEBREW_LETTER_WIDE_DALET 0xfb22 #define UNITEXT_HEBREW_LETTER_WIDE_DALET L"\ufb22" #define UNICODE_HEBREW_LETTER_WIDE_HE 0xfb23 #define UNITEXT_HEBREW_LETTER_WIDE_HE L"\ufb23" #define UNICODE_HEBREW_LETTER_WIDE_KAF 0xfb24 #define UNITEXT_HEBREW_LETTER_WIDE_KAF L"\ufb24" #define UNICODE_HEBREW_LETTER_WIDE_LAMED 0xfb25 #define UNITEXT_HEBREW_LETTER_WIDE_LAMED L"\ufb25" #define UNICODE_HEBREW_LETTER_WIDE_FINAL_MEM 0xfb26 #define UNITEXT_HEBREW_LETTER_WIDE_FINAL_MEM L"\ufb26" #define UNICODE_HEBREW_LETTER_WIDE_RESH 0xfb27 #define UNITEXT_HEBREW_LETTER_WIDE_RESH L"\ufb27" #define UNICODE_HEBREW_LETTER_WIDE_TAV 0xfb28 #define UNITEXT_HEBREW_LETTER_WIDE_TAV L"\ufb28" #define UNICODE_HEBREW_LETTER_ALTERNATIVE_PLUS_SIGN 0xfb29 #define UNITEXT_HEBREW_LETTER_ALTERNATIVE_PLUS_SIGN L"\ufb29" #define UNICODE_HEBREW_LETTER_SHIN_WITH_SHIN_DOT 0xfb2a #define UNITEXT_HEBREW_LETTER_SHIN_WITH_SHIN_DOT L"\ufb2a" #define UNICODE_HEBREW_LETTER_SHIN_WITH_SIN_DOT 0xfb2b #define UNITEXT_HEBREW_LETTER_SHIN_WITH_SIN_DOT L"\ufb2b" #define UNICODE_HEBREW_LETTER_SHIN_WITH_DAGESH_AND_SHIN_DOT 0xfb2c #define UNITEXT_HEBREW_LETTER_SHIN_WITH_DAGESH_AND_SHIN_DOT L"\ufb2c" #define UNICODE_HEBREW_LETTER_SHIN_WITH_DAGESH_AND_SIN_DOT 0xfb2d #define UNITEXT_HEBREW_LETTER_SHIN_WITH_DAGESH_AND_SIN_DOT L"\ufb2d" #define UNICODE_HEBREW_LETTER_ALEF_WITH_PATAH 0xfb2e #define UNITEXT_HEBREW_LETTER_ALEF_WITH_PATAH L"\ufb2e" #define UNICODE_HEBREW_LETTER_ALEF_WITH_QAMATS 0xfb2f #define UNITEXT_HEBREW_LETTER_ALEF_WITH_QAMATS L"\ufb2f" #define UNICODE_HEBREW_LETTER_ALEF_WITH_MAPIQ 0xfb30 #define UNITEXT_HEBREW_LETTER_ALEF_WITH_MAPIQ L"\ufb30" #define UNICODE_HEBREW_LETTER_BET_WITH_DAGESH 0xfb31 #define UNITEXT_HEBREW_LETTER_BET_WITH_DAGESH L"\ufb31" #define UNICODE_HEBREW_LETTER_GIMEL_WITH_DAGESH 0xfb32 #define UNITEXT_HEBREW_LETTER_GIMEL_WITH_DAGESH L"\ufb32" #define UNICODE_HEBREW_LETTER_DALET_WITH_DAGESH 0xfb33 #define UNITEXT_HEBREW_LETTER_DALET_WITH_DAGESH L"\ufb33" #define UNICODE_HEBREW_LETTER_HE_WITH_MAPIQ 0xfb34 #define UNITEXT_HEBREW_LETTER_HE_WITH_MAPIQ L"\ufb34" #define UNICODE_HEBREW_LETTER_VAV_WITH_DAGESH 0xfb35 #define UNITEXT_HEBREW_LETTER_VAV_WITH_DAGESH L"\ufb35" #define UNICODE_HEBREW_LETTER_ZAYIN_WITH_DAGESH 0xfb36 #define UNITEXT_HEBREW_LETTER_ZAYIN_WITH_DAGESH L"\ufb36" #define UNICODE_HEBREW_LETTER_TET_WITH_DAGESH 0xfb38 #define UNITEXT_HEBREW_LETTER_TET_WITH_DAGESH L"\ufb38" #define UNICODE_HEBREW_LETTER_YOD_WITH_DAGESH 0xfb39 #define UNITEXT_HEBREW_LETTER_YOD_WITH_DAGESH L"\ufb39" #define UNICODE_HEBREW_LETTER_FINAL_KAF_WITH_DAGESH 0xfb3a #define UNITEXT_HEBREW_LETTER_FINAL_KAF_WITH_DAGESH L"\ufb3a" #define UNICODE_HEBREW_LETTER_KAF_WITH_DAGESH 0xfb3b #define UNITEXT_HEBREW_LETTER_KAF_WITH_DAGESH L"\ufb3b" #define UNICODE_HEBREW_LETTER_LAMED_WITH_DAGESH 0xfb3c #define UNITEXT_HEBREW_LETTER_LAMED_WITH_DAGESH L"\ufb3c" #define UNICODE_HEBREW_LETTER_MEM_WITH_DAGESH 0xfb3e #define UNITEXT_HEBREW_LETTER_MEM_WITH_DAGESH L"\ufb3e" #define UNICODE_HEBREW_LETTER_NUN_WITH_DAGESH 0xfb40 #define UNITEXT_HEBREW_LETTER_NUN_WITH_DAGESH L"\ufb40" #define UNICODE_HEBREW_LETTER_SAMEKH_WITH_DAGESH 0xfb41 #define UNITEXT_HEBREW_LETTER_SAMEKH_WITH_DAGESH L"\ufb41" #define UNICODE_HEBREW_LETTER_FINAL_PE_WITH_DAGESH 0xfb43 #define UNITEXT_HEBREW_LETTER_FINAL_PE_WITH_DAGESH L"\ufb43" #define UNICODE_HEBREW_LETTER_PE_WITH_DAGESH 0xfb44 #define UNITEXT_HEBREW_LETTER_PE_WITH_DAGESH L"\ufb44" #define UNICODE_HEBREW_LETTER_TSADI_WITH_DAGESH 0xfb46 #define UNITEXT_HEBREW_LETTER_TSADI_WITH_DAGESH L"\ufb46" #define UNICODE_HEBREW_LETTER_QOF_WITH_DAGESH 0xfb47 #define UNITEXT_HEBREW_LETTER_QOF_WITH_DAGESH L"\ufb47" #define UNICODE_HEBREW_LETTER_RESH_WITH_DAGESH 0xfb48 #define UNITEXT_HEBREW_LETTER_RESH_WITH_DAGESH L"\ufb48" #define UNICODE_HEBREW_LETTER_SHIN_WITH_DAGESH 0xfb49 #define UNITEXT_HEBREW_LETTER_SHIN_WITH_DAGESH L"\ufb49" #define UNICODE_HEBREW_LETTER_TAV_WITH_DAGESH 0xfb4a #define UNITEXT_HEBREW_LETTER_TAV_WITH_DAGESH L"\ufb4a" #define UNICODE_HEBREW_LETTER_VAV_WITH_HOLAM 0xfb4b #define UNITEXT_HEBREW_LETTER_VAV_WITH_HOLAM L"\ufb4b" #define UNICODE_HEBREW_LETTER_BET_WITH_RAFE 0xfb4c #define UNITEXT_HEBREW_LETTER_BET_WITH_RAFE L"\ufb4c" #define UNICODE_HEBREW_LETTER_KAF_WITH_RAFE 0xfb4d #define UNITEXT_HEBREW_LETTER_KAF_WITH_RAFE L"\ufb4d" #define UNICODE_HEBREW_LETTER_PE_WITH_RAFE 0xfb4e #define UNITEXT_HEBREW_LETTER_PE_WITH_RAFE L"\ufb4e" #define UNICODE_HEBREW_LIGATURE_ALEF_LAMED 0xfb4f #define UNITEXT_HEBREW_LIGATURE_ALEF_LAMED L"\ufb4f" #define UNICODE_ARABIC_LETTER_ALEF_WASLA_ISOLATED_FORM 0xfb50 #define UNITEXT_ARABIC_LETTER_ALEF_WASLA_ISOLATED_FORM L"\ufb50" #define UNICODE_ARABIC_LETTER_ALEF_WASLA_FINAL_FORM 0xfb51 #define UNITEXT_ARABIC_LETTER_ALEF_WASLA_FINAL_FORM L"\ufb51" #define UNICODE_ARABIC_LETTER_BEEH_ISOLATED_FORM 0xfb52 #define UNITEXT_ARABIC_LETTER_BEEH_ISOLATED_FORM L"\ufb52" #define UNICODE_ARABIC_LETTER_BEEH_FINAL_FORM 0xfb53 #define UNITEXT_ARABIC_LETTER_BEEH_FINAL_FORM L"\ufb53" #define UNICODE_ARABIC_LETTER_BEEH_INITIAL_FORM 0xfb54 #define UNITEXT_ARABIC_LETTER_BEEH_INITIAL_FORM L"\ufb54" #define UNICODE_ARABIC_LETTER_BEEH_MEDIAL_FORM 0xfb55 #define UNITEXT_ARABIC_LETTER_BEEH_MEDIAL_FORM L"\ufb55" #define UNICODE_ARABIC_LETTER_PEH_ISOLATED_FORM 0xfb56 #define UNITEXT_ARABIC_LETTER_PEH_ISOLATED_FORM L"\ufb56" #define UNICODE_ARABIC_LETTER_PEH_FINAL_FORM 0xfb57 #define UNITEXT_ARABIC_LETTER_PEH_FINAL_FORM L"\ufb57" #define UNICODE_ARABIC_LETTER_PEH_INITIAL_FORM 0xfb58 #define UNITEXT_ARABIC_LETTER_PEH_INITIAL_FORM L"\ufb58" #define UNICODE_ARABIC_LETTER_PEH_MEDIAL_FORM 0xfb59 #define UNITEXT_ARABIC_LETTER_PEH_MEDIAL_FORM L"\ufb59" #define UNICODE_ARABIC_LETTER_BEHEH_ISOLATED_FORM 0xfb5a #define UNITEXT_ARABIC_LETTER_BEHEH_ISOLATED_FORM L"\ufb5a" #define UNICODE_ARABIC_LETTER_BEHEH_FINAL_FORM 0xfb5b #define UNITEXT_ARABIC_LETTER_BEHEH_FINAL_FORM L"\ufb5b" #define UNICODE_ARABIC_LETTER_BEHEH_INITIAL_FORM 0xfb5c #define UNITEXT_ARABIC_LETTER_BEHEH_INITIAL_FORM L"\ufb5c" #define UNICODE_ARABIC_LETTER_BEHEH_MEDIAL_FORM 0xfb5d #define UNITEXT_ARABIC_LETTER_BEHEH_MEDIAL_FORM L"\ufb5d" #define UNICODE_ARABIC_LETTER_TTEHEH_ISOLATED_FORM 0xfb5e #define UNITEXT_ARABIC_LETTER_TTEHEH_ISOLATED_FORM L"\ufb5e" #define UNICODE_ARABIC_LETTER_TTEHEH_FINAL_FORM 0xfb5f #define UNITEXT_ARABIC_LETTER_TTEHEH_FINAL_FORM L"\ufb5f" #define UNICODE_ARABIC_LETTER_TTEHEH_INITIAL_FORM 0xfb60 #define UNITEXT_ARABIC_LETTER_TTEHEH_INITIAL_FORM L"\ufb60" #define UNICODE_ARABIC_LETTER_TTEHEH_MEDIAL_FORM 0xfb61 #define UNITEXT_ARABIC_LETTER_TTEHEH_MEDIAL_FORM L"\ufb61" #define UNICODE_ARABIC_LETTER_TEHEH_ISOLATED_FORM 0xfb62 #define UNITEXT_ARABIC_LETTER_TEHEH_ISOLATED_FORM L"\ufb62" #define UNICODE_ARABIC_LETTER_TEHEH_FINAL_FORM 0xfb63 #define UNITEXT_ARABIC_LETTER_TEHEH_FINAL_FORM L"\ufb63" #define UNICODE_ARABIC_LETTER_TEHEH_INITIAL_FORM 0xfb64 #define UNITEXT_ARABIC_LETTER_TEHEH_INITIAL_FORM L"\ufb64" #define UNICODE_ARABIC_LETTER_TEHEH_MEDIAL_FORM 0xfb65 #define UNITEXT_ARABIC_LETTER_TEHEH_MEDIAL_FORM L"\ufb65" #define UNICODE_ARABIC_LETTER_TTEH_ISOLATED_FORM 0xfb66 #define UNITEXT_ARABIC_LETTER_TTEH_ISOLATED_FORM L"\ufb66" #define UNICODE_ARABIC_LETTER_TTEH_FINAL_FORM 0xfb67 #define UNITEXT_ARABIC_LETTER_TTEH_FINAL_FORM L"\ufb67" #define UNICODE_ARABIC_LETTER_TTEH_INITIAL_FORM 0xfb68 #define UNITEXT_ARABIC_LETTER_TTEH_INITIAL_FORM L"\ufb68" #define UNICODE_ARABIC_LETTER_TTEH_MEDIAL_FORM 0xfb69 #define UNITEXT_ARABIC_LETTER_TTEH_MEDIAL_FORM L"\ufb69" #define UNICODE_ARABIC_LETTER_VEH_ISOLATED_FORM 0xfb6a #define UNITEXT_ARABIC_LETTER_VEH_ISOLATED_FORM L"\ufb6a" #define UNICODE_ARABIC_LETTER_VEH_FINAL_FORM 0xfb6b #define UNITEXT_ARABIC_LETTER_VEH_FINAL_FORM L"\ufb6b" #define UNICODE_ARABIC_LETTER_VEH_INITIAL_FORM 0xfb6c #define UNITEXT_ARABIC_LETTER_VEH_INITIAL_FORM L"\ufb6c" #define UNICODE_ARABIC_LETTER_VEH_MEDIAL_FORM 0xfb6d #define UNITEXT_ARABIC_LETTER_VEH_MEDIAL_FORM L"\ufb6d" #define UNICODE_ARABIC_LETTER_PEHEH_ISOLATED_FORM 0xfb6e #define UNITEXT_ARABIC_LETTER_PEHEH_ISOLATED_FORM L"\ufb6e" #define UNICODE_ARABIC_LETTER_PEHEH_FINAL_FORM 0xfb6f #define UNITEXT_ARABIC_LETTER_PEHEH_FINAL_FORM L"\ufb6f" #define UNICODE_ARABIC_LETTER_PEHEH_INITIAL_FORM 0xfb70 #define UNITEXT_ARABIC_LETTER_PEHEH_INITIAL_FORM L"\ufb70" #define UNICODE_ARABIC_LETTER_PEHEH_MEDIAL_FORM 0xfb71 #define UNITEXT_ARABIC_LETTER_PEHEH_MEDIAL_FORM L"\ufb71" #define UNICODE_ARABIC_LETTER_DYEH_ISOLATED_FORM 0xfb72 #define UNITEXT_ARABIC_LETTER_DYEH_ISOLATED_FORM L"\ufb72" #define UNICODE_ARABIC_LETTER_DYEH_FINAL_FORM 0xfb73 #define UNITEXT_ARABIC_LETTER_DYEH_FINAL_FORM L"\ufb73" #define UNICODE_ARABIC_LETTER_DYEH_INITIAL_FORM 0xfb74 #define UNITEXT_ARABIC_LETTER_DYEH_INITIAL_FORM L"\ufb74" #define UNICODE_ARABIC_LETTER_DYEH_MEDIAL_FORM 0xfb75 #define UNITEXT_ARABIC_LETTER_DYEH_MEDIAL_FORM L"\ufb75" #define UNICODE_ARABIC_LETTER_NYEH_ISOLATED_FORM 0xfb76 #define UNITEXT_ARABIC_LETTER_NYEH_ISOLATED_FORM L"\ufb76" #define UNICODE_ARABIC_LETTER_NYEH_FINAL_FORM 0xfb77 #define UNITEXT_ARABIC_LETTER_NYEH_FINAL_FORM L"\ufb77" #define UNICODE_ARABIC_LETTER_NYEH_INITIAL_FORM 0xfb78 #define UNITEXT_ARABIC_LETTER_NYEH_INITIAL_FORM L"\ufb78" #define UNICODE_ARABIC_LETTER_NYEH_MEDIAL_FORM 0xfb79 #define UNITEXT_ARABIC_LETTER_NYEH_MEDIAL_FORM L"\ufb79" #define UNICODE_ARABIC_LETTER_TCHEH_ISOLATED_FORM 0xfb7a #define UNITEXT_ARABIC_LETTER_TCHEH_ISOLATED_FORM L"\ufb7a" #define UNICODE_ARABIC_LETTER_TCHEH_FINAL_FORM 0xfb7b #define UNITEXT_ARABIC_LETTER_TCHEH_FINAL_FORM L"\ufb7b" #define UNICODE_ARABIC_LETTER_TCHEH_INITIAL_FORM 0xfb7c #define UNITEXT_ARABIC_LETTER_TCHEH_INITIAL_FORM L"\ufb7c" #define UNICODE_ARABIC_LETTER_TCHEH_MEDIAL_FORM 0xfb7d #define UNITEXT_ARABIC_LETTER_TCHEH_MEDIAL_FORM L"\ufb7d" #define UNICODE_ARABIC_LETTER_TCHEHEH_ISOLATED_FORM 0xfb7e #define UNITEXT_ARABIC_LETTER_TCHEHEH_ISOLATED_FORM L"\ufb7e" #define UNICODE_ARABIC_LETTER_TCHEHEH_FINAL_FORM 0xfb7f #define UNITEXT_ARABIC_LETTER_TCHEHEH_FINAL_FORM L"\ufb7f" #define UNICODE_ARABIC_LETTER_TCHEHEH_INITIAL_FORM 0xfb80 #define UNITEXT_ARABIC_LETTER_TCHEHEH_INITIAL_FORM L"\ufb80" #define UNICODE_ARABIC_LETTER_TCHEHEH_MEDIAL_FORM 0xfb81 #define UNITEXT_ARABIC_LETTER_TCHEHEH_MEDIAL_FORM L"\ufb81" #define UNICODE_ARABIC_LETTER_DDAHAL_ISOLATED_FORM 0xfb82 #define UNITEXT_ARABIC_LETTER_DDAHAL_ISOLATED_FORM L"\ufb82" #define UNICODE_ARABIC_LETTER_DDAHAL_FINAL_FORM 0xfb83 #define UNITEXT_ARABIC_LETTER_DDAHAL_FINAL_FORM L"\ufb83" #define UNICODE_ARABIC_LETTER_DAHAL_ISOLATED_FORM 0xfb84 #define UNITEXT_ARABIC_LETTER_DAHAL_ISOLATED_FORM L"\ufb84" #define UNICODE_ARABIC_LETTER_DAHAL_FINAL_FORM 0xfb85 #define UNITEXT_ARABIC_LETTER_DAHAL_FINAL_FORM L"\ufb85" #define UNICODE_ARABIC_LETTER_DUL_ISOLATED_FORM 0xfb86 #define UNITEXT_ARABIC_LETTER_DUL_ISOLATED_FORM L"\ufb86" #define UNICODE_ARABIC_LETTER_DUL_FINAL_FORM 0xfb87 #define UNITEXT_ARABIC_LETTER_DUL_FINAL_FORM L"\ufb87" #define UNICODE_ARABIC_LETTER_DDAL_ISOLATED_FORM 0xfb88 #define UNITEXT_ARABIC_LETTER_DDAL_ISOLATED_FORM L"\ufb88" #define UNICODE_ARABIC_LETTER_DDAL_FINAL_FORM 0xfb89 #define UNITEXT_ARABIC_LETTER_DDAL_FINAL_FORM L"\ufb89" #define UNICODE_ARABIC_LETTER_JEH_ISOLATED_FORM 0xfb8a #define UNITEXT_ARABIC_LETTER_JEH_ISOLATED_FORM L"\ufb8a" #define UNICODE_ARABIC_LETTER_JEH_FINAL_FORM 0xfb8b #define UNITEXT_ARABIC_LETTER_JEH_FINAL_FORM L"\ufb8b" #define UNICODE_ARABIC_LETTER_RREH_ISOLATED_FORM 0xfb8c #define UNITEXT_ARABIC_LETTER_RREH_ISOLATED_FORM L"\ufb8c" #define UNICODE_ARABIC_LETTER_RREH_FINAL_FORM 0xfb8d #define UNITEXT_ARABIC_LETTER_RREH_FINAL_FORM L"\ufb8d" #define UNICODE_ARABIC_LETTER_KEHEH_ISOLATED_FORM 0xfb8e #define UNITEXT_ARABIC_LETTER_KEHEH_ISOLATED_FORM L"\ufb8e" #define UNICODE_ARABIC_LETTER_KEHEH_FINAL_FORM 0xfb8f #define UNITEXT_ARABIC_LETTER_KEHEH_FINAL_FORM L"\ufb8f" #define UNICODE_ARABIC_LETTER_KEHEH_INITIAL_FORM 0xfb90 #define UNITEXT_ARABIC_LETTER_KEHEH_INITIAL_FORM L"\ufb90" #define UNICODE_ARABIC_LETTER_KEHEH_MEDIAL_FORM 0xfb91 #define UNITEXT_ARABIC_LETTER_KEHEH_MEDIAL_FORM L"\ufb91" #define UNICODE_ARABIC_LETTER_GAF_ISOLATED_FORM 0xfb92 #define UNITEXT_ARABIC_LETTER_GAF_ISOLATED_FORM L"\ufb92" #define UNICODE_ARABIC_LETTER_GAF_FINAL_FORM 0xfb93 #define UNITEXT_ARABIC_LETTER_GAF_FINAL_FORM L"\ufb93" #define UNICODE_ARABIC_LETTER_GAF_INITIAL_FORM 0xfb94 #define UNITEXT_ARABIC_LETTER_GAF_INITIAL_FORM L"\ufb94" #define UNICODE_ARABIC_LETTER_GAF_MEDIAL_FORM 0xfb95 #define UNITEXT_ARABIC_LETTER_GAF_MEDIAL_FORM L"\ufb95" #define UNICODE_ARABIC_LETTER_GUEH_ISOLATED_FORM 0xfb96 #define UNITEXT_ARABIC_LETTER_GUEH_ISOLATED_FORM L"\ufb96" #define UNICODE_ARABIC_LETTER_GUEH_FINAL_FORM 0xfb97 #define UNITEXT_ARABIC_LETTER_GUEH_FINAL_FORM L"\ufb97" #define UNICODE_ARABIC_LETTER_GUEH_INITIAL_FORM 0xfb98 #define UNITEXT_ARABIC_LETTER_GUEH_INITIAL_FORM L"\ufb98" #define UNICODE_ARABIC_LETTER_GUEH_MEDIAL_FORM 0xfb99 #define UNITEXT_ARABIC_LETTER_GUEH_MEDIAL_FORM L"\ufb99" #define UNICODE_ARABIC_LETTER_NGOEH_ISOLATED_FORM 0xfb9a #define UNITEXT_ARABIC_LETTER_NGOEH_ISOLATED_FORM L"\ufb9a" #define UNICODE_ARABIC_LETTER_NGOEH_FINAL_FORM 0xfb9b #define UNITEXT_ARABIC_LETTER_NGOEH_FINAL_FORM L"\ufb9b" #define UNICODE_ARABIC_LETTER_NGOEH_INITIAL_FORM 0xfb9c #define UNITEXT_ARABIC_LETTER_NGOEH_INITIAL_FORM L"\ufb9c" #define UNICODE_ARABIC_LETTER_NGOEH_MEDIAL_FORM 0xfb9d #define UNITEXT_ARABIC_LETTER_NGOEH_MEDIAL_FORM L"\ufb9d" #define UNICODE_ARABIC_LETTER_NOON_GHUNNA_ISOLATED_FORM 0xfb9e #define UNITEXT_ARABIC_LETTER_NOON_GHUNNA_ISOLATED_FORM L"\ufb9e" #define UNICODE_ARABIC_LETTER_NOON_GHUNNA_FINAL_FORM 0xfb9f #define UNITEXT_ARABIC_LETTER_NOON_GHUNNA_FINAL_FORM L"\ufb9f" #define UNICODE_ARABIC_LETTER_RNOON_ISOLATED_FORM 0xfba0 #define UNITEXT_ARABIC_LETTER_RNOON_ISOLATED_FORM L"\ufba0" #define UNICODE_ARABIC_LETTER_RNOON_FINAL_FORM 0xfba1 #define UNITEXT_ARABIC_LETTER_RNOON_FINAL_FORM L"\ufba1" #define UNICODE_ARABIC_LETTER_RNOON_INITIAL_FORM 0xfba2 #define UNITEXT_ARABIC_LETTER_RNOON_INITIAL_FORM L"\ufba2" #define UNICODE_ARABIC_LETTER_RNOON_MEDIAL_FORM 0xfba3 #define UNITEXT_ARABIC_LETTER_RNOON_MEDIAL_FORM L"\ufba3" #define UNICODE_ARABIC_LETTER_HEH_WITH_YEH_ABOVE_ISOLATED_FORM 0xfba4 #define UNITEXT_ARABIC_LETTER_HEH_WITH_YEH_ABOVE_ISOLATED_FORM L"\ufba4" #define UNICODE_ARABIC_LETTER_HEH_WITH_YEH_ABOVE_FINAL_FORM 0xfba5 #define UNITEXT_ARABIC_LETTER_HEH_WITH_YEH_ABOVE_FINAL_FORM L"\ufba5" #define UNICODE_ARABIC_LETTER_HEH_GOAL_ISOLATED_FORM 0xfba6 #define UNITEXT_ARABIC_LETTER_HEH_GOAL_ISOLATED_FORM L"\ufba6" #define UNICODE_ARABIC_LETTER_HEH_GOAL_FINAL_FORM 0xfba7 #define UNITEXT_ARABIC_LETTER_HEH_GOAL_FINAL_FORM L"\ufba7" #define UNICODE_ARABIC_LETTER_HEH_GOAL_INITIAL_FORM 0xfba8 #define UNITEXT_ARABIC_LETTER_HEH_GOAL_INITIAL_FORM L"\ufba8" #define UNICODE_ARABIC_LETTER_HEH_GOAL_MEDIAL_FORM 0xfba9 #define UNITEXT_ARABIC_LETTER_HEH_GOAL_MEDIAL_FORM L"\ufba9" #define UNICODE_ARABIC_LETTER_HEH_DOACHASHMEE_ISOLATED_FORM 0xfbaa #define UNITEXT_ARABIC_LETTER_HEH_DOACHASHMEE_ISOLATED_FORM L"\ufbaa" #define UNICODE_ARABIC_LETTER_HEH_DOACHASHMEE_FINAL_FORM 0xfbab #define UNITEXT_ARABIC_LETTER_HEH_DOACHASHMEE_FINAL_FORM L"\ufbab" #define UNICODE_ARABIC_LETTER_HEH_DOACHASHMEE_INITIAL_FORM 0xfbac #define UNITEXT_ARABIC_LETTER_HEH_DOACHASHMEE_INITIAL_FORM L"\ufbac" #define UNICODE_ARABIC_LETTER_HEH_DOACHASHMEE_MEDIAL_FORM 0xfbad #define UNITEXT_ARABIC_LETTER_HEH_DOACHASHMEE_MEDIAL_FORM L"\ufbad" #define UNICODE_ARABIC_LETTER_YEH_BARREE_ISOLATED_FORM 0xfbae #define UNITEXT_ARABIC_LETTER_YEH_BARREE_ISOLATED_FORM L"\ufbae" #define UNICODE_ARABIC_LETTER_YEH_BARREE_FINAL_FORM 0xfbaf #define UNITEXT_ARABIC_LETTER_YEH_BARREE_FINAL_FORM L"\ufbaf" #define UNICODE_ARABIC_LETTER_YEH_BARREE_WITH_HAMZA_ABOVE_ISOLATED_FORM 0xfbb0 #define UNITEXT_ARABIC_LETTER_YEH_BARREE_WITH_HAMZA_ABOVE_ISOLATED_FORM L"\ufbb0" #define UNICODE_ARABIC_LETTER_YEH_BARREE_WITH_HAMZA_ABOVE_FINAL_FORM 0xfbb1 #define UNITEXT_ARABIC_LETTER_YEH_BARREE_WITH_HAMZA_ABOVE_FINAL_FORM L"\ufbb1" #define UNICODE_ARABIC_LETTER_NG_ISOLATED_FORM 0xfbd3 #define UNITEXT_ARABIC_LETTER_NG_ISOLATED_FORM L"\ufbd3" #define UNICODE_ARABIC_LETTER_NG_FINAL_FORM 0xfbd4 #define UNITEXT_ARABIC_LETTER_NG_FINAL_FORM L"\ufbd4" #define UNICODE_ARABIC_LETTER_NG_INITIAL_FORM 0xfbd5 #define UNITEXT_ARABIC_LETTER_NG_INITIAL_FORM L"\ufbd5" #define UNICODE_ARABIC_LETTER_NG_MEDIAL_FORM 0xfbd6 #define UNITEXT_ARABIC_LETTER_NG_MEDIAL_FORM L"\ufbd6" #define UNICODE_ARABIC_LETTER_U_ISOLATED_FORM 0xfbd7 #define UNITEXT_ARABIC_LETTER_U_ISOLATED_FORM L"\ufbd7" #define UNICODE_ARABIC_LETTER_U_FINAL_FORM 0xfbd8 #define UNITEXT_ARABIC_LETTER_U_FINAL_FORM L"\ufbd8" #define UNICODE_ARABIC_LETTER_OE_ISOLATED_FORM 0xfbd9 #define UNITEXT_ARABIC_LETTER_OE_ISOLATED_FORM L"\ufbd9" #define UNICODE_ARABIC_LETTER_OE_FINAL_FORM 0xfbda #define UNITEXT_ARABIC_LETTER_OE_FINAL_FORM L"\ufbda" #define UNICODE_ARABIC_LETTER_YU_ISOLATED_FORM 0xfbdb #define UNITEXT_ARABIC_LETTER_YU_ISOLATED_FORM L"\ufbdb" #define UNICODE_ARABIC_LETTER_YU_FINAL_FORM 0xfbdc #define UNITEXT_ARABIC_LETTER_YU_FINAL_FORM L"\ufbdc" #define UNICODE_ARABIC_LETTER_U_WITH_HAMZA_ABOVE_ISOLATED_FORM 0xfbdd #define UNITEXT_ARABIC_LETTER_U_WITH_HAMZA_ABOVE_ISOLATED_FORM L"\ufbdd" #define UNICODE_ARABIC_LETTER_VE_ISOLATED_FORM 0xfbde #define UNITEXT_ARABIC_LETTER_VE_ISOLATED_FORM L"\ufbde" #define UNICODE_ARABIC_LETTER_VE_FINAL_FORM 0xfbdf #define UNITEXT_ARABIC_LETTER_VE_FINAL_FORM L"\ufbdf" #define UNICODE_ARABIC_LETTER_KIRGHIZ_OE_ISOLATED_FORM 0xfbe0 #define UNITEXT_ARABIC_LETTER_KIRGHIZ_OE_ISOLATED_FORM L"\ufbe0" #define UNICODE_ARABIC_LETTER_KIRGHIZ_OE_FINAL_FORM 0xfbe1 #define UNITEXT_ARABIC_LETTER_KIRGHIZ_OE_FINAL_FORM L"\ufbe1" #define UNICODE_ARABIC_LETTER_KIRGHIZ_YU_ISOLATED_FORM 0xfbe2 #define UNITEXT_ARABIC_LETTER_KIRGHIZ_YU_ISOLATED_FORM L"\ufbe2" #define UNICODE_ARABIC_LETTER_KIRGHIZ_YU_FINAL_FORM 0xfbe3 #define UNITEXT_ARABIC_LETTER_KIRGHIZ_YU_FINAL_FORM L"\ufbe3" #define UNICODE_ARABIC_LETTER_E_ISOLATED_FORM 0xfbe4 #define UNITEXT_ARABIC_LETTER_E_ISOLATED_FORM L"\ufbe4" #define UNICODE_ARABIC_LETTER_E_FINAL_FORM 0xfbe5 #define UNITEXT_ARABIC_LETTER_E_FINAL_FORM L"\ufbe5" #define UNICODE_ARABIC_LETTER_E_INITIAL_FORM 0xfbe6 #define UNITEXT_ARABIC_LETTER_E_INITIAL_FORM L"\ufbe6" #define UNICODE_ARABIC_LETTER_E_MEDIAL_FORM 0xfbe7 #define UNITEXT_ARABIC_LETTER_E_MEDIAL_FORM L"\ufbe7" #define UNICODE_ARABIC_LETTER_UIGHUR_KAZAKH_KIRGHIZ_ALEF_MAKSURA_INITIAL_FORM 0xfbe8 #define UNITEXT_ARABIC_LETTER_UIGHUR_KAZAKH_KIRGHIZ_ALEF_MAKSURA_INITIAL_FORM L"\ufbe8" #define UNICODE_ARABIC_LETTER_UIGHUR_KAZAKH_KIRGHIZ_ALEF_MAKSURA_MEDIAL_FORM 0xfbe9 #define UNITEXT_ARABIC_LETTER_UIGHUR_KAZAKH_KIRGHIZ_ALEF_MAKSURA_MEDIAL_FORM L"\ufbe9" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_ISOLATED_FORM 0xfbea #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_ISOLATED_FORM L"\ufbea" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_FINAL_FORM 0xfbeb #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_FINAL_FORM L"\ufbeb" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_AE_ISOLATED_FORM 0xfbec #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_AE_ISOLATED_FORM L"\ufbec" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_AE_FINAL_FORM 0xfbed #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_AE_FINAL_FORM L"\ufbed" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_WAW_ISOLATED_FORM 0xfbee #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_WAW_ISOLATED_FORM L"\ufbee" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_WAW_FINAL_FORM 0xfbef #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_WAW_FINAL_FORM L"\ufbef" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_U_ISOLATED_FORM 0xfbf0 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_U_ISOLATED_FORM L"\ufbf0" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_U_FINAL_FORM 0xfbf1 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_U_FINAL_FORM L"\ufbf1" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_OE_ISOLATED_FORM 0xfbf2 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_OE_ISOLATED_FORM L"\ufbf2" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_OE_FINAL_FORM 0xfbf3 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_OE_FINAL_FORM L"\ufbf3" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_YU_ISOLATED_FORM 0xfbf4 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_YU_ISOLATED_FORM L"\ufbf4" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_YU_FINAL_FORM 0xfbf5 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_YU_FINAL_FORM L"\ufbf5" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_E_ISOLATED_FORM 0xfbf6 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_E_ISOLATED_FORM L"\ufbf6" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_E_FINAL_FORM 0xfbf7 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_E_FINAL_FORM L"\ufbf7" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_E_INITIAL_FORM 0xfbf8 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_E_INITIAL_FORM L"\ufbf8" #define UNICODE_ARABIC_LIGATURE_UIGHUR_KIRGHIZ_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfbf9 #define UNITEXT_ARABIC_LIGATURE_UIGHUR_KIRGHIZ_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufbf9" #define UNICODE_ARABIC_LIGATURE_UIGHUR_KIRGHIZ_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_FINAL_FORM 0xfbfa #define UNITEXT_ARABIC_LIGATURE_UIGHUR_KIRGHIZ_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufbfa" #define UNICODE_ARABIC_LIGATURE_UIGHUR_KIRGHIZ_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_INITIAL_FORM 0xfbfb #define UNITEXT_ARABIC_LIGATURE_UIGHUR_KIRGHIZ_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_INITIAL_FORM L"\ufbfb" #define UNICODE_ARABIC_LETTER_FARSI_YEH_ISOLATED_FORM 0xfbfc #define UNITEXT_ARABIC_LETTER_FARSI_YEH_ISOLATED_FORM L"\ufbfc" #define UNICODE_ARABIC_LETTER_FARSI_YEH_FINAL_FORM 0xfbfd #define UNITEXT_ARABIC_LETTER_FARSI_YEH_FINAL_FORM L"\ufbfd" #define UNICODE_ARABIC_LETTER_FARSI_YEH_INITIAL_FORM 0xfbfe #define UNITEXT_ARABIC_LETTER_FARSI_YEH_INITIAL_FORM L"\ufbfe" #define UNICODE_ARABIC_LETTER_FARSI_YEH_MEDIAL_FORM 0xfbff #define UNITEXT_ARABIC_LETTER_FARSI_YEH_MEDIAL_FORM L"\ufbff" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_JEEM_ISOLATED_FORM 0xfc00 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_JEEM_ISOLATED_FORM L"\ufc00" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_HAH_ISOLATED_FORM 0xfc01 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_HAH_ISOLATED_FORM L"\ufc01" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_MEEM_ISOLATED_FORM 0xfc02 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_MEEM_ISOLATED_FORM L"\ufc02" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc03 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc03" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_YEH_ISOLATED_FORM 0xfc04 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_YEH_ISOLATED_FORM L"\ufc04" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_JEEM_ISOLATED_FORM 0xfc05 #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_JEEM_ISOLATED_FORM L"\ufc05" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_HAH_ISOLATED_FORM 0xfc06 #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_HAH_ISOLATED_FORM L"\ufc06" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_KHAH_ISOLATED_FORM 0xfc07 #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_KHAH_ISOLATED_FORM L"\ufc07" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_MEEM_ISOLATED_FORM 0xfc08 #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_MEEM_ISOLATED_FORM L"\ufc08" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc09 #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc09" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_YEH_ISOLATED_FORM 0xfc0a #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_YEH_ISOLATED_FORM L"\ufc0a" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_JEEM_ISOLATED_FORM 0xfc0b #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_JEEM_ISOLATED_FORM L"\ufc0b" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_HAH_ISOLATED_FORM 0xfc0c #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_HAH_ISOLATED_FORM L"\ufc0c" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_KHAH_ISOLATED_FORM 0xfc0d #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_KHAH_ISOLATED_FORM L"\ufc0d" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_MEEM_ISOLATED_FORM 0xfc0e #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_MEEM_ISOLATED_FORM L"\ufc0e" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc0f #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc0f" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_YEH_ISOLATED_FORM 0xfc10 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_YEH_ISOLATED_FORM L"\ufc10" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_JEEM_ISOLATED_FORM 0xfc11 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_JEEM_ISOLATED_FORM L"\ufc11" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_MEEM_ISOLATED_FORM 0xfc12 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_MEEM_ISOLATED_FORM L"\ufc12" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc13 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc13" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_YEH_ISOLATED_FORM 0xfc14 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_YEH_ISOLATED_FORM L"\ufc14" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_HAH_ISOLATED_FORM 0xfc15 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_HAH_ISOLATED_FORM L"\ufc15" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_MEEM_ISOLATED_FORM 0xfc16 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_MEEM_ISOLATED_FORM L"\ufc16" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_JEEM_ISOLATED_FORM 0xfc17 #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_JEEM_ISOLATED_FORM L"\ufc17" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_MEEM_ISOLATED_FORM 0xfc18 #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_MEEM_ISOLATED_FORM L"\ufc18" #define UNICODE_ARABIC_LIGATURE_KHAH_WITH_JEEM_ISOLATED_FORM 0xfc19 #define UNITEXT_ARABIC_LIGATURE_KHAH_WITH_JEEM_ISOLATED_FORM L"\ufc19" #define UNICODE_ARABIC_LIGATURE_KHAH_WITH_HAH_ISOLATED_FORM 0xfc1a #define UNITEXT_ARABIC_LIGATURE_KHAH_WITH_HAH_ISOLATED_FORM L"\ufc1a" #define UNICODE_ARABIC_LIGATURE_KHAH_WITH_MEEM_ISOLATED_FORM 0xfc1b #define UNITEXT_ARABIC_LIGATURE_KHAH_WITH_MEEM_ISOLATED_FORM L"\ufc1b" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_JEEM_ISOLATED_FORM 0xfc1c #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_JEEM_ISOLATED_FORM L"\ufc1c" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_HAH_ISOLATED_FORM 0xfc1d #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_HAH_ISOLATED_FORM L"\ufc1d" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_KHAH_ISOLATED_FORM 0xfc1e #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_KHAH_ISOLATED_FORM L"\ufc1e" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_MEEM_ISOLATED_FORM 0xfc1f #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_MEEM_ISOLATED_FORM L"\ufc1f" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_HAH_ISOLATED_FORM 0xfc20 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_HAH_ISOLATED_FORM L"\ufc20" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_MEEM_ISOLATED_FORM 0xfc21 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_MEEM_ISOLATED_FORM L"\ufc21" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_JEEM_ISOLATED_FORM 0xfc22 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_JEEM_ISOLATED_FORM L"\ufc22" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_HAH_ISOLATED_FORM 0xfc23 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_HAH_ISOLATED_FORM L"\ufc23" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_KHAH_ISOLATED_FORM 0xfc24 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_KHAH_ISOLATED_FORM L"\ufc24" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_MEEM_ISOLATED_FORM 0xfc25 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_MEEM_ISOLATED_FORM L"\ufc25" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_HAH_ISOLATED_FORM 0xfc26 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_HAH_ISOLATED_FORM L"\ufc26" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_MEEM_ISOLATED_FORM 0xfc27 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_MEEM_ISOLATED_FORM L"\ufc27" #define UNICODE_ARABIC_LIGATURE_ZAH_WITH_MEEM_ISOLATED_FORM 0xfc28 #define UNITEXT_ARABIC_LIGATURE_ZAH_WITH_MEEM_ISOLATED_FORM L"\ufc28" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_JEEM_ISOLATED_FORM 0xfc29 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_JEEM_ISOLATED_FORM L"\ufc29" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_MEEM_ISOLATED_FORM 0xfc2a #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_MEEM_ISOLATED_FORM L"\ufc2a" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_JEEM_ISOLATED_FORM 0xfc2b #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_JEEM_ISOLATED_FORM L"\ufc2b" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_MEEM_ISOLATED_FORM 0xfc2c #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_MEEM_ISOLATED_FORM L"\ufc2c" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_JEEM_ISOLATED_FORM 0xfc2d #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_JEEM_ISOLATED_FORM L"\ufc2d" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_HAH_ISOLATED_FORM 0xfc2e #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_HAH_ISOLATED_FORM L"\ufc2e" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_KHAH_ISOLATED_FORM 0xfc2f #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_KHAH_ISOLATED_FORM L"\ufc2f" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_MEEM_ISOLATED_FORM 0xfc30 #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_MEEM_ISOLATED_FORM L"\ufc30" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc31 #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc31" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_YEH_ISOLATED_FORM 0xfc32 #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_YEH_ISOLATED_FORM L"\ufc32" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_HAH_ISOLATED_FORM 0xfc33 #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_HAH_ISOLATED_FORM L"\ufc33" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_MEEM_ISOLATED_FORM 0xfc34 #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_MEEM_ISOLATED_FORM L"\ufc34" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc35 #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc35" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_YEH_ISOLATED_FORM 0xfc36 #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_YEH_ISOLATED_FORM L"\ufc36" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_ALEF_ISOLATED_FORM 0xfc37 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_ALEF_ISOLATED_FORM L"\ufc37" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_JEEM_ISOLATED_FORM 0xfc38 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_JEEM_ISOLATED_FORM L"\ufc38" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_HAH_ISOLATED_FORM 0xfc39 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_HAH_ISOLATED_FORM L"\ufc39" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_KHAH_ISOLATED_FORM 0xfc3a #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_KHAH_ISOLATED_FORM L"\ufc3a" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_LAM_ISOLATED_FORM 0xfc3b #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_LAM_ISOLATED_FORM L"\ufc3b" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_MEEM_ISOLATED_FORM 0xfc3c #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_MEEM_ISOLATED_FORM L"\ufc3c" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc3d #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc3d" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_YEH_ISOLATED_FORM 0xfc3e #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_YEH_ISOLATED_FORM L"\ufc3e" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_JEEM_ISOLATED_FORM 0xfc3f #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_JEEM_ISOLATED_FORM L"\ufc3f" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_HAH_ISOLATED_FORM 0xfc40 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_HAH_ISOLATED_FORM L"\ufc40" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_KHAH_ISOLATED_FORM 0xfc41 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_KHAH_ISOLATED_FORM L"\ufc41" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_MEEM_ISOLATED_FORM 0xfc42 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_MEEM_ISOLATED_FORM L"\ufc42" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc43 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc43" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_YEH_ISOLATED_FORM 0xfc44 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_YEH_ISOLATED_FORM L"\ufc44" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_JEEM_ISOLATED_FORM 0xfc45 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_JEEM_ISOLATED_FORM L"\ufc45" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_HAH_ISOLATED_FORM 0xfc46 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_HAH_ISOLATED_FORM L"\ufc46" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_KHAH_ISOLATED_FORM 0xfc47 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_KHAH_ISOLATED_FORM L"\ufc47" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_MEEM_ISOLATED_FORM 0xfc48 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_MEEM_ISOLATED_FORM L"\ufc48" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc49 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc49" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_YEH_ISOLATED_FORM 0xfc4a #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_YEH_ISOLATED_FORM L"\ufc4a" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_JEEM_ISOLATED_FORM 0xfc4b #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_JEEM_ISOLATED_FORM L"\ufc4b" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_HAH_ISOLATED_FORM 0xfc4c #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_HAH_ISOLATED_FORM L"\ufc4c" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_KHAH_ISOLATED_FORM 0xfc4d #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_KHAH_ISOLATED_FORM L"\ufc4d" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_MEEM_ISOLATED_FORM 0xfc4e #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_MEEM_ISOLATED_FORM L"\ufc4e" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc4f #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc4f" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_YEH_ISOLATED_FORM 0xfc50 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_YEH_ISOLATED_FORM L"\ufc50" #define UNICODE_ARABIC_LIGATURE_HEH_WITH_JEEM_ISOLATED_FORM 0xfc51 #define UNITEXT_ARABIC_LIGATURE_HEH_WITH_JEEM_ISOLATED_FORM L"\ufc51" #define UNICODE_ARABIC_LIGATURE_HEH_WITH_MEEM_ISOLATED_FORM 0xfc52 #define UNITEXT_ARABIC_LIGATURE_HEH_WITH_MEEM_ISOLATED_FORM L"\ufc52" #define UNICODE_ARABIC_LIGATURE_HEH_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc53 #define UNITEXT_ARABIC_LIGATURE_HEH_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc53" #define UNICODE_ARABIC_LIGATURE_HEH_WITH_YEH_ISOLATED_FORM 0xfc54 #define UNITEXT_ARABIC_LIGATURE_HEH_WITH_YEH_ISOLATED_FORM L"\ufc54" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_JEEM_ISOLATED_FORM 0xfc55 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_JEEM_ISOLATED_FORM L"\ufc55" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAH_ISOLATED_FORM 0xfc56 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAH_ISOLATED_FORM L"\ufc56" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_KHAH_ISOLATED_FORM 0xfc57 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_KHAH_ISOLATED_FORM L"\ufc57" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_MEEM_ISOLATED_FORM 0xfc58 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_MEEM_ISOLATED_FORM L"\ufc58" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfc59 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufc59" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_YEH_ISOLATED_FORM 0xfc5a #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_YEH_ISOLATED_FORM L"\ufc5a" #define UNICODE_ARABIC_LIGATURE_THAL_WITH_SUPERSCRIPT_ALEF_ISOLATED_FORM 0xfc5b #define UNITEXT_ARABIC_LIGATURE_THAL_WITH_SUPERSCRIPT_ALEF_ISOLATED_FORM L"\ufc5b" #define UNICODE_ARABIC_LIGATURE_REH_WITH_SUPERSCRIPT_ALEF_ISOLATED_FORM 0xfc5c #define UNITEXT_ARABIC_LIGATURE_REH_WITH_SUPERSCRIPT_ALEF_ISOLATED_FORM L"\ufc5c" #define UNICODE_ARABIC_LIGATURE_ALEF_MAKSURA_WITH_SUPERSCRIPT_ALEF_ISOLATED_FORM 0xfc5d #define UNITEXT_ARABIC_LIGATURE_ALEF_MAKSURA_WITH_SUPERSCRIPT_ALEF_ISOLATED_FORM L"\ufc5d" #define UNICODE_ARABIC_LIGATURE_SHADDA_WITH_DAMMATAN_ISOLATED_FORM 0xfc5e #define UNITEXT_ARABIC_LIGATURE_SHADDA_WITH_DAMMATAN_ISOLATED_FORM L"\ufc5e" #define UNICODE_ARABIC_LIGATURE_SHADDA_WITH_KASRATAN_ISOLATED_FORM 0xfc5f #define UNITEXT_ARABIC_LIGATURE_SHADDA_WITH_KASRATAN_ISOLATED_FORM L"\ufc5f" #define UNICODE_ARABIC_LIGATURE_SHADDA_WITH_FATHA_ISOLATED_FORM 0xfc60 #define UNITEXT_ARABIC_LIGATURE_SHADDA_WITH_FATHA_ISOLATED_FORM L"\ufc60" #define UNICODE_ARABIC_LIGATURE_SHADDA_WITH_DAMMA_ISOLATED_FORM 0xfc61 #define UNITEXT_ARABIC_LIGATURE_SHADDA_WITH_DAMMA_ISOLATED_FORM L"\ufc61" #define UNICODE_ARABIC_LIGATURE_SHADDA_WITH_KASRA_ISOLATED_FORM 0xfc62 #define UNITEXT_ARABIC_LIGATURE_SHADDA_WITH_KASRA_ISOLATED_FORM L"\ufc62" #define UNICODE_ARABIC_LIGATURE_SHADDA_WITH_SUPERSCRIPT_ALEF_ISOLATED_FORM 0xfc63 #define UNITEXT_ARABIC_LIGATURE_SHADDA_WITH_SUPERSCRIPT_ALEF_ISOLATED_FORM L"\ufc63" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_REH_FINAL_FORM 0xfc64 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_REH_FINAL_FORM L"\ufc64" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ZAIN_FINAL_FORM 0xfc65 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ZAIN_FINAL_FORM L"\ufc65" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_MEEM_FINAL_FORM 0xfc66 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_MEEM_FINAL_FORM L"\ufc66" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_NOON_FINAL_FORM 0xfc67 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_NOON_FINAL_FORM L"\ufc67" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc68 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc68" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_YEH_FINAL_FORM 0xfc69 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_YEH_FINAL_FORM L"\ufc69" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_REH_FINAL_FORM 0xfc6a #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_REH_FINAL_FORM L"\ufc6a" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_ZAIN_FINAL_FORM 0xfc6b #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_ZAIN_FINAL_FORM L"\ufc6b" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_MEEM_FINAL_FORM 0xfc6c #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_MEEM_FINAL_FORM L"\ufc6c" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_NOON_FINAL_FORM 0xfc6d #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_NOON_FINAL_FORM L"\ufc6d" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc6e #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc6e" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_YEH_FINAL_FORM 0xfc6f #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_YEH_FINAL_FORM L"\ufc6f" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_REH_FINAL_FORM 0xfc70 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_REH_FINAL_FORM L"\ufc70" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_ZAIN_FINAL_FORM 0xfc71 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_ZAIN_FINAL_FORM L"\ufc71" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_MEEM_FINAL_FORM 0xfc72 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_MEEM_FINAL_FORM L"\ufc72" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_NOON_FINAL_FORM 0xfc73 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_NOON_FINAL_FORM L"\ufc73" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc74 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc74" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_YEH_FINAL_FORM 0xfc75 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_YEH_FINAL_FORM L"\ufc75" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_REH_FINAL_FORM 0xfc76 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_REH_FINAL_FORM L"\ufc76" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_ZAIN_FINAL_FORM 0xfc77 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_ZAIN_FINAL_FORM L"\ufc77" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_MEEM_FINAL_FORM 0xfc78 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_MEEM_FINAL_FORM L"\ufc78" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_NOON_FINAL_FORM 0xfc79 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_NOON_FINAL_FORM L"\ufc79" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc7a #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc7a" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_YEH_FINAL_FORM 0xfc7b #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_YEH_FINAL_FORM L"\ufc7b" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc7c #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc7c" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_YEH_FINAL_FORM 0xfc7d #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_YEH_FINAL_FORM L"\ufc7d" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc7e #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc7e" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_YEH_FINAL_FORM 0xfc7f #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_YEH_FINAL_FORM L"\ufc7f" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_ALEF_FINAL_FORM 0xfc80 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_ALEF_FINAL_FORM L"\ufc80" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_LAM_FINAL_FORM 0xfc81 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_LAM_FINAL_FORM L"\ufc81" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_MEEM_FINAL_FORM 0xfc82 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_MEEM_FINAL_FORM L"\ufc82" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc83 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc83" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_YEH_FINAL_FORM 0xfc84 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_YEH_FINAL_FORM L"\ufc84" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_MEEM_FINAL_FORM 0xfc85 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_MEEM_FINAL_FORM L"\ufc85" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc86 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc86" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_YEH_FINAL_FORM 0xfc87 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_YEH_FINAL_FORM L"\ufc87" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_ALEF_FINAL_FORM 0xfc88 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_ALEF_FINAL_FORM L"\ufc88" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_MEEM_FINAL_FORM 0xfc89 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_MEEM_FINAL_FORM L"\ufc89" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_REH_FINAL_FORM 0xfc8a #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_REH_FINAL_FORM L"\ufc8a" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_ZAIN_FINAL_FORM 0xfc8b #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_ZAIN_FINAL_FORM L"\ufc8b" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_MEEM_FINAL_FORM 0xfc8c #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_MEEM_FINAL_FORM L"\ufc8c" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_NOON_FINAL_FORM 0xfc8d #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_NOON_FINAL_FORM L"\ufc8d" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc8e #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc8e" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_YEH_FINAL_FORM 0xfc8f #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_YEH_FINAL_FORM L"\ufc8f" #define UNICODE_ARABIC_LIGATURE_ALEF_MAKSURA_WITH_SUPERSCRIPT_ALEF_FINAL_FORM 0xfc90 #define UNITEXT_ARABIC_LIGATURE_ALEF_MAKSURA_WITH_SUPERSCRIPT_ALEF_FINAL_FORM L"\ufc90" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_REH_FINAL_FORM 0xfc91 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_REH_FINAL_FORM L"\ufc91" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_ZAIN_FINAL_FORM 0xfc92 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_ZAIN_FINAL_FORM L"\ufc92" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_MEEM_FINAL_FORM 0xfc93 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_MEEM_FINAL_FORM L"\ufc93" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_NOON_FINAL_FORM 0xfc94 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_NOON_FINAL_FORM L"\ufc94" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfc95 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufc95" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_YEH_FINAL_FORM 0xfc96 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_YEH_FINAL_FORM L"\ufc96" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_JEEM_INITIAL_FORM 0xfc97 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_JEEM_INITIAL_FORM L"\ufc97" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_HAH_INITIAL_FORM 0xfc98 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_HAH_INITIAL_FORM L"\ufc98" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_KHAH_INITIAL_FORM 0xfc99 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_KHAH_INITIAL_FORM L"\ufc99" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_MEEM_INITIAL_FORM 0xfc9a #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_MEEM_INITIAL_FORM L"\ufc9a" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_HEH_INITIAL_FORM 0xfc9b #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_HEH_INITIAL_FORM L"\ufc9b" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_JEEM_INITIAL_FORM 0xfc9c #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_JEEM_INITIAL_FORM L"\ufc9c" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_HAH_INITIAL_FORM 0xfc9d #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_HAH_INITIAL_FORM L"\ufc9d" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_KHAH_INITIAL_FORM 0xfc9e #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_KHAH_INITIAL_FORM L"\ufc9e" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_MEEM_INITIAL_FORM 0xfc9f #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_MEEM_INITIAL_FORM L"\ufc9f" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_HEH_INITIAL_FORM 0xfca0 #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_HEH_INITIAL_FORM L"\ufca0" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_JEEM_INITIAL_FORM 0xfca1 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_JEEM_INITIAL_FORM L"\ufca1" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_HAH_INITIAL_FORM 0xfca2 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_HAH_INITIAL_FORM L"\ufca2" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_KHAH_INITIAL_FORM 0xfca3 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_KHAH_INITIAL_FORM L"\ufca3" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_MEEM_INITIAL_FORM 0xfca4 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_MEEM_INITIAL_FORM L"\ufca4" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_HEH_INITIAL_FORM 0xfca5 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_HEH_INITIAL_FORM L"\ufca5" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_MEEM_INITIAL_FORM 0xfca6 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_MEEM_INITIAL_FORM L"\ufca6" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_HAH_INITIAL_FORM 0xfca7 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_HAH_INITIAL_FORM L"\ufca7" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_MEEM_INITIAL_FORM 0xfca8 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_MEEM_INITIAL_FORM L"\ufca8" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_JEEM_INITIAL_FORM 0xfca9 #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_JEEM_INITIAL_FORM L"\ufca9" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_MEEM_INITIAL_FORM 0xfcaa #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_MEEM_INITIAL_FORM L"\ufcaa" #define UNICODE_ARABIC_LIGATURE_KHAH_WITH_JEEM_INITIAL_FORM 0xfcab #define UNITEXT_ARABIC_LIGATURE_KHAH_WITH_JEEM_INITIAL_FORM L"\ufcab" #define UNICODE_ARABIC_LIGATURE_KHAH_WITH_MEEM_INITIAL_FORM 0xfcac #define UNITEXT_ARABIC_LIGATURE_KHAH_WITH_MEEM_INITIAL_FORM L"\ufcac" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_JEEM_INITIAL_FORM 0xfcad #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_JEEM_INITIAL_FORM L"\ufcad" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_HAH_INITIAL_FORM 0xfcae #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_HAH_INITIAL_FORM L"\ufcae" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_KHAH_INITIAL_FORM 0xfcaf #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_KHAH_INITIAL_FORM L"\ufcaf" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_MEEM_INITIAL_FORM 0xfcb0 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_MEEM_INITIAL_FORM L"\ufcb0" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_HAH_INITIAL_FORM 0xfcb1 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_HAH_INITIAL_FORM L"\ufcb1" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_KHAH_INITIAL_FORM 0xfcb2 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_KHAH_INITIAL_FORM L"\ufcb2" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_MEEM_INITIAL_FORM 0xfcb3 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_MEEM_INITIAL_FORM L"\ufcb3" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_JEEM_INITIAL_FORM 0xfcb4 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_JEEM_INITIAL_FORM L"\ufcb4" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_HAH_INITIAL_FORM 0xfcb5 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_HAH_INITIAL_FORM L"\ufcb5" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_KHAH_INITIAL_FORM 0xfcb6 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_KHAH_INITIAL_FORM L"\ufcb6" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_MEEM_INITIAL_FORM 0xfcb7 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_MEEM_INITIAL_FORM L"\ufcb7" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_HAH_INITIAL_FORM 0xfcb8 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_HAH_INITIAL_FORM L"\ufcb8" #define UNICODE_ARABIC_LIGATURE_ZAH_WITH_MEEM_INITIAL_FORM 0xfcb9 #define UNITEXT_ARABIC_LIGATURE_ZAH_WITH_MEEM_INITIAL_FORM L"\ufcb9" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_JEEM_INITIAL_FORM 0xfcba #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_JEEM_INITIAL_FORM L"\ufcba" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_MEEM_INITIAL_FORM 0xfcbb #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_MEEM_INITIAL_FORM L"\ufcbb" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_JEEM_INITIAL_FORM 0xfcbc #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_JEEM_INITIAL_FORM L"\ufcbc" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_MEEM_INITIAL_FORM 0xfcbd #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_MEEM_INITIAL_FORM L"\ufcbd" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_JEEM_INITIAL_FORM 0xfcbe #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_JEEM_INITIAL_FORM L"\ufcbe" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_HAH_INITIAL_FORM 0xfcbf #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_HAH_INITIAL_FORM L"\ufcbf" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_KHAH_INITIAL_FORM 0xfcc0 #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_KHAH_INITIAL_FORM L"\ufcc0" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_MEEM_INITIAL_FORM 0xfcc1 #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_MEEM_INITIAL_FORM L"\ufcc1" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_HAH_INITIAL_FORM 0xfcc2 #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_HAH_INITIAL_FORM L"\ufcc2" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_MEEM_INITIAL_FORM 0xfcc3 #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_MEEM_INITIAL_FORM L"\ufcc3" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_JEEM_INITIAL_FORM 0xfcc4 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_JEEM_INITIAL_FORM L"\ufcc4" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_HAH_INITIAL_FORM 0xfcc5 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_HAH_INITIAL_FORM L"\ufcc5" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_KHAH_INITIAL_FORM 0xfcc6 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_KHAH_INITIAL_FORM L"\ufcc6" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_LAM_INITIAL_FORM 0xfcc7 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_LAM_INITIAL_FORM L"\ufcc7" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_MEEM_INITIAL_FORM 0xfcc8 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_MEEM_INITIAL_FORM L"\ufcc8" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_JEEM_INITIAL_FORM 0xfcc9 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_JEEM_INITIAL_FORM L"\ufcc9" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_HAH_INITIAL_FORM 0xfcca #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_HAH_INITIAL_FORM L"\ufcca" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_KHAH_INITIAL_FORM 0xfccb #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_KHAH_INITIAL_FORM L"\ufccb" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_MEEM_INITIAL_FORM 0xfccc #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_MEEM_INITIAL_FORM L"\ufccc" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_HEH_INITIAL_FORM 0xfccd #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_HEH_INITIAL_FORM L"\ufccd" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_JEEM_INITIAL_FORM 0xfcce #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_JEEM_INITIAL_FORM L"\ufcce" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_HAH_INITIAL_FORM 0xfccf #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_HAH_INITIAL_FORM L"\ufccf" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_KHAH_INITIAL_FORM 0xfcd0 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_KHAH_INITIAL_FORM L"\ufcd0" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_MEEM_INITIAL_FORM 0xfcd1 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_MEEM_INITIAL_FORM L"\ufcd1" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_JEEM_INITIAL_FORM 0xfcd2 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_JEEM_INITIAL_FORM L"\ufcd2" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_HAH_INITIAL_FORM 0xfcd3 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_HAH_INITIAL_FORM L"\ufcd3" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_KHAH_INITIAL_FORM 0xfcd4 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_KHAH_INITIAL_FORM L"\ufcd4" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_MEEM_INITIAL_FORM 0xfcd5 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_MEEM_INITIAL_FORM L"\ufcd5" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_HEH_INITIAL_FORM 0xfcd6 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_HEH_INITIAL_FORM L"\ufcd6" #define UNICODE_ARABIC_LIGATURE_HEH_WITH_JEEM_INITIAL_FORM 0xfcd7 #define UNITEXT_ARABIC_LIGATURE_HEH_WITH_JEEM_INITIAL_FORM L"\ufcd7" #define UNICODE_ARABIC_LIGATURE_HEH_WITH_MEEM_INITIAL_FORM 0xfcd8 #define UNITEXT_ARABIC_LIGATURE_HEH_WITH_MEEM_INITIAL_FORM L"\ufcd8" #define UNICODE_ARABIC_LIGATURE_HEH_WITH_SUPERSCRIPT_ALEF_INITIAL_FORM 0xfcd9 #define UNITEXT_ARABIC_LIGATURE_HEH_WITH_SUPERSCRIPT_ALEF_INITIAL_FORM L"\ufcd9" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_JEEM_INITIAL_FORM 0xfcda #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_JEEM_INITIAL_FORM L"\ufcda" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAH_INITIAL_FORM 0xfcdb #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAH_INITIAL_FORM L"\ufcdb" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_KHAH_INITIAL_FORM 0xfcdc #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_KHAH_INITIAL_FORM L"\ufcdc" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_MEEM_INITIAL_FORM 0xfcdd #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_MEEM_INITIAL_FORM L"\ufcdd" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HEH_INITIAL_FORM 0xfcde #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HEH_INITIAL_FORM L"\ufcde" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_MEEM_MEDIAL_FORM 0xfcdf #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_MEEM_MEDIAL_FORM L"\ufcdf" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_HEH_MEDIAL_FORM 0xfce0 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAMZA_ABOVE_WITH_HEH_MEDIAL_FORM L"\ufce0" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_MEEM_MEDIAL_FORM 0xfce1 #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_MEEM_MEDIAL_FORM L"\ufce1" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_HEH_MEDIAL_FORM 0xfce2 #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_HEH_MEDIAL_FORM L"\ufce2" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_MEEM_MEDIAL_FORM 0xfce3 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_MEEM_MEDIAL_FORM L"\ufce3" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_HEH_MEDIAL_FORM 0xfce4 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_HEH_MEDIAL_FORM L"\ufce4" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_MEEM_MEDIAL_FORM 0xfce5 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_MEEM_MEDIAL_FORM L"\ufce5" #define UNICODE_ARABIC_LIGATURE_THEH_WITH_HEH_MEDIAL_FORM 0xfce6 #define UNITEXT_ARABIC_LIGATURE_THEH_WITH_HEH_MEDIAL_FORM L"\ufce6" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_MEEM_MEDIAL_FORM 0xfce7 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_MEEM_MEDIAL_FORM L"\ufce7" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_HEH_MEDIAL_FORM 0xfce8 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_HEH_MEDIAL_FORM L"\ufce8" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_MEEM_MEDIAL_FORM 0xfce9 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_MEEM_MEDIAL_FORM L"\ufce9" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_HEH_MEDIAL_FORM 0xfcea #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_HEH_MEDIAL_FORM L"\ufcea" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_LAM_MEDIAL_FORM 0xfceb #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_LAM_MEDIAL_FORM L"\ufceb" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_MEEM_MEDIAL_FORM 0xfcec #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_MEEM_MEDIAL_FORM L"\ufcec" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_MEEM_MEDIAL_FORM 0xfced #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_MEEM_MEDIAL_FORM L"\ufced" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_MEEM_MEDIAL_FORM 0xfcee #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_MEEM_MEDIAL_FORM L"\ufcee" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_HEH_MEDIAL_FORM 0xfcef #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_HEH_MEDIAL_FORM L"\ufcef" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_MEEM_MEDIAL_FORM 0xfcf0 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_MEEM_MEDIAL_FORM L"\ufcf0" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HEH_MEDIAL_FORM 0xfcf1 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HEH_MEDIAL_FORM L"\ufcf1" #define UNICODE_ARABIC_LIGATURE_SHADDA_WITH_FATHA_MEDIAL_FORM 0xfcf2 #define UNITEXT_ARABIC_LIGATURE_SHADDA_WITH_FATHA_MEDIAL_FORM L"\ufcf2" #define UNICODE_ARABIC_LIGATURE_SHADDA_WITH_DAMMA_MEDIAL_FORM 0xfcf3 #define UNITEXT_ARABIC_LIGATURE_SHADDA_WITH_DAMMA_MEDIAL_FORM L"\ufcf3" #define UNICODE_ARABIC_LIGATURE_SHADDA_WITH_KASRA_MEDIAL_FORM 0xfcf4 #define UNITEXT_ARABIC_LIGATURE_SHADDA_WITH_KASRA_MEDIAL_FORM L"\ufcf4" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfcf5 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufcf5" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_YEH_ISOLATED_FORM 0xfcf6 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_YEH_ISOLATED_FORM L"\ufcf6" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfcf7 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufcf7" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_YEH_ISOLATED_FORM 0xfcf8 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_YEH_ISOLATED_FORM L"\ufcf8" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfcf9 #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufcf9" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_YEH_ISOLATED_FORM 0xfcfa #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_YEH_ISOLATED_FORM L"\ufcfa" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfcfb #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufcfb" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_YEH_ISOLATED_FORM 0xfcfc #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_YEH_ISOLATED_FORM L"\ufcfc" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfcfd #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufcfd" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_YEH_ISOLATED_FORM 0xfcfe #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_YEH_ISOLATED_FORM L"\ufcfe" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfcff #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufcff" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_YEH_ISOLATED_FORM 0xfd00 #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_YEH_ISOLATED_FORM L"\ufd00" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfd01 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufd01" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_YEH_ISOLATED_FORM 0xfd02 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_YEH_ISOLATED_FORM L"\ufd02" #define UNICODE_ARABIC_LIGATURE_KHAH_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfd03 #define UNITEXT_ARABIC_LIGATURE_KHAH_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufd03" #define UNICODE_ARABIC_LIGATURE_KHAH_WITH_YEH_ISOLATED_FORM 0xfd04 #define UNITEXT_ARABIC_LIGATURE_KHAH_WITH_YEH_ISOLATED_FORM L"\ufd04" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfd05 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufd05" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_YEH_ISOLATED_FORM 0xfd06 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_YEH_ISOLATED_FORM L"\ufd06" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_ALEF_MAKSURA_ISOLATED_FORM 0xfd07 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_ALEF_MAKSURA_ISOLATED_FORM L"\ufd07" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_YEH_ISOLATED_FORM 0xfd08 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_YEH_ISOLATED_FORM L"\ufd08" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_JEEM_ISOLATED_FORM 0xfd09 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_JEEM_ISOLATED_FORM L"\ufd09" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_HAH_ISOLATED_FORM 0xfd0a #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_HAH_ISOLATED_FORM L"\ufd0a" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_KHAH_ISOLATED_FORM 0xfd0b #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_KHAH_ISOLATED_FORM L"\ufd0b" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_MEEM_ISOLATED_FORM 0xfd0c #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_MEEM_ISOLATED_FORM L"\ufd0c" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_REH_ISOLATED_FORM 0xfd0d #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_REH_ISOLATED_FORM L"\ufd0d" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_REH_ISOLATED_FORM 0xfd0e #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_REH_ISOLATED_FORM L"\ufd0e" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_REH_ISOLATED_FORM 0xfd0f #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_REH_ISOLATED_FORM L"\ufd0f" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_REH_ISOLATED_FORM 0xfd10 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_REH_ISOLATED_FORM L"\ufd10" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd11 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd11" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_YEH_FINAL_FORM 0xfd12 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_YEH_FINAL_FORM L"\ufd12" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd13 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd13" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_YEH_FINAL_FORM 0xfd14 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_YEH_FINAL_FORM L"\ufd14" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd15 #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd15" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_YEH_FINAL_FORM 0xfd16 #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_YEH_FINAL_FORM L"\ufd16" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd17 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd17" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_YEH_FINAL_FORM 0xfd18 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_YEH_FINAL_FORM L"\ufd18" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd19 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd19" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_YEH_FINAL_FORM 0xfd1a #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_YEH_FINAL_FORM L"\ufd1a" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd1b #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd1b" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_YEH_FINAL_FORM 0xfd1c #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_YEH_FINAL_FORM L"\ufd1c" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd1d #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd1d" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_YEH_FINAL_FORM 0xfd1e #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_YEH_FINAL_FORM L"\ufd1e" #define UNICODE_ARABIC_LIGATURE_KHAH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd1f #define UNITEXT_ARABIC_LIGATURE_KHAH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd1f" #define UNICODE_ARABIC_LIGATURE_KHAH_WITH_YEH_FINAL_FORM 0xfd20 #define UNITEXT_ARABIC_LIGATURE_KHAH_WITH_YEH_FINAL_FORM L"\ufd20" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd21 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd21" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_YEH_FINAL_FORM 0xfd22 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_YEH_FINAL_FORM L"\ufd22" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd23 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd23" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_YEH_FINAL_FORM 0xfd24 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_YEH_FINAL_FORM L"\ufd24" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_JEEM_FINAL_FORM 0xfd25 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_JEEM_FINAL_FORM L"\ufd25" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_HAH_FINAL_FORM 0xfd26 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_HAH_FINAL_FORM L"\ufd26" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_KHAH_FINAL_FORM 0xfd27 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_KHAH_FINAL_FORM L"\ufd27" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_MEEM_FINAL_FORM 0xfd28 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_MEEM_FINAL_FORM L"\ufd28" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_REH_FINAL_FORM 0xfd29 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_REH_FINAL_FORM L"\ufd29" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_REH_FINAL_FORM 0xfd2a #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_REH_FINAL_FORM L"\ufd2a" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_REH_FINAL_FORM 0xfd2b #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_REH_FINAL_FORM L"\ufd2b" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_REH_FINAL_FORM 0xfd2c #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_REH_FINAL_FORM L"\ufd2c" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_JEEM_INITIAL_FORM 0xfd2d #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_JEEM_INITIAL_FORM L"\ufd2d" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_HAH_INITIAL_FORM 0xfd2e #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_HAH_INITIAL_FORM L"\ufd2e" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_KHAH_INITIAL_FORM 0xfd2f #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_KHAH_INITIAL_FORM L"\ufd2f" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_MEEM_INITIAL_FORM 0xfd30 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_MEEM_INITIAL_FORM L"\ufd30" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_HEH_INITIAL_FORM 0xfd31 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_HEH_INITIAL_FORM L"\ufd31" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_HEH_INITIAL_FORM 0xfd32 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_HEH_INITIAL_FORM L"\ufd32" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_MEEM_INITIAL_FORM 0xfd33 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_MEEM_INITIAL_FORM L"\ufd33" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_JEEM_MEDIAL_FORM 0xfd34 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_JEEM_MEDIAL_FORM L"\ufd34" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_HAH_MEDIAL_FORM 0xfd35 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_HAH_MEDIAL_FORM L"\ufd35" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_KHAH_MEDIAL_FORM 0xfd36 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_KHAH_MEDIAL_FORM L"\ufd36" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_JEEM_MEDIAL_FORM 0xfd37 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_JEEM_MEDIAL_FORM L"\ufd37" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_HAH_MEDIAL_FORM 0xfd38 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_HAH_MEDIAL_FORM L"\ufd38" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_KHAH_MEDIAL_FORM 0xfd39 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_KHAH_MEDIAL_FORM L"\ufd39" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_MEEM_MEDIAL_FORM 0xfd3a #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_MEEM_MEDIAL_FORM L"\ufd3a" #define UNICODE_ARABIC_LIGATURE_ZAH_WITH_MEEM_MEDIAL_FORM 0xfd3b #define UNITEXT_ARABIC_LIGATURE_ZAH_WITH_MEEM_MEDIAL_FORM L"\ufd3b" #define UNICODE_ARABIC_LIGATURE_ALEF_WITH_FATHATAN_FINAL_FORM 0xfd3c #define UNITEXT_ARABIC_LIGATURE_ALEF_WITH_FATHATAN_FINAL_FORM L"\ufd3c" #define UNICODE_ARABIC_LIGATURE_ALEF_WITH_FATHATAN_ISOLATED_FORM 0xfd3d #define UNITEXT_ARABIC_LIGATURE_ALEF_WITH_FATHATAN_ISOLATED_FORM L"\ufd3d" #define UNICODE_ORNATE_LEFT_PARENTHESIS 0xfd3e #define UNITEXT_ORNATE_LEFT_PARENTHESIS L"\ufd3e" #define UNICODE_ORNATE_RIGHT_PARENTHESIS 0xfd3f #define UNITEXT_ORNATE_RIGHT_PARENTHESIS L"\ufd3f" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_JEEM_WITH_MEEM_INITIAL_FORM 0xfd50 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_JEEM_WITH_MEEM_INITIAL_FORM L"\ufd50" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_HAH_WITH_JEEM_FINAL_FORM 0xfd51 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_HAH_WITH_JEEM_FINAL_FORM L"\ufd51" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_HAH_WITH_JEEM_INITIAL_FORM 0xfd52 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_HAH_WITH_JEEM_INITIAL_FORM L"\ufd52" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_HAH_WITH_MEEM_INITIAL_FORM 0xfd53 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_HAH_WITH_MEEM_INITIAL_FORM L"\ufd53" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_KHAH_WITH_MEEM_INITIAL_FORM 0xfd54 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_KHAH_WITH_MEEM_INITIAL_FORM L"\ufd54" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_JEEM_INITIAL_FORM 0xfd55 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_JEEM_INITIAL_FORM L"\ufd55" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_HAH_INITIAL_FORM 0xfd56 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_HAH_INITIAL_FORM L"\ufd56" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_KHAH_INITIAL_FORM 0xfd57 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_KHAH_INITIAL_FORM L"\ufd57" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_MEEM_WITH_HAH_FINAL_FORM 0xfd58 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_MEEM_WITH_HAH_FINAL_FORM L"\ufd58" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_MEEM_WITH_HAH_INITIAL_FORM 0xfd59 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_MEEM_WITH_HAH_INITIAL_FORM L"\ufd59" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfd5a #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufd5a" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd5b #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd5b" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_HAH_WITH_JEEM_INITIAL_FORM 0xfd5c #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_HAH_WITH_JEEM_INITIAL_FORM L"\ufd5c" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_JEEM_WITH_HAH_INITIAL_FORM 0xfd5d #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_JEEM_WITH_HAH_INITIAL_FORM L"\ufd5d" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_JEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd5e #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_JEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd5e" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_HAH_FINAL_FORM 0xfd5f #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_HAH_FINAL_FORM L"\ufd5f" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_HAH_INITIAL_FORM 0xfd60 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_HAH_INITIAL_FORM L"\ufd60" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_JEEM_INITIAL_FORM 0xfd61 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_JEEM_INITIAL_FORM L"\ufd61" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_MEEM_FINAL_FORM 0xfd62 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_MEEM_FINAL_FORM L"\ufd62" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_MEEM_INITIAL_FORM 0xfd63 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_MEEM_WITH_MEEM_INITIAL_FORM L"\ufd63" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_HAH_WITH_HAH_FINAL_FORM 0xfd64 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_HAH_WITH_HAH_FINAL_FORM L"\ufd64" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_HAH_WITH_HAH_INITIAL_FORM 0xfd65 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_HAH_WITH_HAH_INITIAL_FORM L"\ufd65" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_MEEM_WITH_MEEM_FINAL_FORM 0xfd66 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_MEEM_WITH_MEEM_FINAL_FORM L"\ufd66" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_HAH_WITH_MEEM_FINAL_FORM 0xfd67 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_HAH_WITH_MEEM_FINAL_FORM L"\ufd67" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_HAH_WITH_MEEM_INITIAL_FORM 0xfd68 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_HAH_WITH_MEEM_INITIAL_FORM L"\ufd68" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_JEEM_WITH_YEH_FINAL_FORM 0xfd69 #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_JEEM_WITH_YEH_FINAL_FORM L"\ufd69" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_MEEM_WITH_KHAH_FINAL_FORM 0xfd6a #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_MEEM_WITH_KHAH_FINAL_FORM L"\ufd6a" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_MEEM_WITH_KHAH_INITIAL_FORM 0xfd6b #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_MEEM_WITH_KHAH_INITIAL_FORM L"\ufd6b" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_MEEM_WITH_MEEM_FINAL_FORM 0xfd6c #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_MEEM_WITH_MEEM_FINAL_FORM L"\ufd6c" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_MEEM_WITH_MEEM_INITIAL_FORM 0xfd6d #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_MEEM_WITH_MEEM_INITIAL_FORM L"\ufd6d" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_HAH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd6e #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_HAH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd6e" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_KHAH_WITH_MEEM_FINAL_FORM 0xfd6f #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_KHAH_WITH_MEEM_FINAL_FORM L"\ufd6f" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_KHAH_WITH_MEEM_INITIAL_FORM 0xfd70 #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_KHAH_WITH_MEEM_INITIAL_FORM L"\ufd70" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_MEEM_WITH_HAH_FINAL_FORM 0xfd71 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_MEEM_WITH_HAH_FINAL_FORM L"\ufd71" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_MEEM_WITH_HAH_INITIAL_FORM 0xfd72 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_MEEM_WITH_HAH_INITIAL_FORM L"\ufd72" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_MEEM_WITH_MEEM_INITIAL_FORM 0xfd73 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_MEEM_WITH_MEEM_INITIAL_FORM L"\ufd73" #define UNICODE_ARABIC_LIGATURE_TAH_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfd74 #define UNITEXT_ARABIC_LIGATURE_TAH_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufd74" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_JEEM_WITH_MEEM_FINAL_FORM 0xfd75 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_JEEM_WITH_MEEM_FINAL_FORM L"\ufd75" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_MEEM_WITH_MEEM_FINAL_FORM 0xfd76 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_MEEM_WITH_MEEM_FINAL_FORM L"\ufd76" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_MEEM_WITH_MEEM_INITIAL_FORM 0xfd77 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_MEEM_WITH_MEEM_INITIAL_FORM L"\ufd77" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd78 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd78" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_MEEM_WITH_MEEM_FINAL_FORM 0xfd79 #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_MEEM_WITH_MEEM_FINAL_FORM L"\ufd79" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfd7a #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufd7a" #define UNICODE_ARABIC_LIGATURE_GHAIN_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd7b #define UNITEXT_ARABIC_LIGATURE_GHAIN_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd7b" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_KHAH_WITH_MEEM_FINAL_FORM 0xfd7c #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_KHAH_WITH_MEEM_FINAL_FORM L"\ufd7c" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_KHAH_WITH_MEEM_INITIAL_FORM 0xfd7d #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_KHAH_WITH_MEEM_INITIAL_FORM L"\ufd7d" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_MEEM_WITH_HAH_FINAL_FORM 0xfd7e #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_MEEM_WITH_HAH_FINAL_FORM L"\ufd7e" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_MEEM_WITH_MEEM_FINAL_FORM 0xfd7f #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_MEEM_WITH_MEEM_FINAL_FORM L"\ufd7f" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_HAH_WITH_MEEM_FINAL_FORM 0xfd80 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_HAH_WITH_MEEM_FINAL_FORM L"\ufd80" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_HAH_WITH_YEH_FINAL_FORM 0xfd81 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_HAH_WITH_YEH_FINAL_FORM L"\ufd81" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_HAH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd82 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_HAH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd82" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_JEEM_INITIAL_FORM 0xfd83 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_JEEM_INITIAL_FORM L"\ufd83" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_JEEM_FINAL_FORM 0xfd84 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_JEEM_FINAL_FORM L"\ufd84" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_KHAH_WITH_MEEM_FINAL_FORM 0xfd85 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_KHAH_WITH_MEEM_FINAL_FORM L"\ufd85" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_KHAH_WITH_MEEM_INITIAL_FORM 0xfd86 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_KHAH_WITH_MEEM_INITIAL_FORM L"\ufd86" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_MEEM_WITH_HAH_FINAL_FORM 0xfd87 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_MEEM_WITH_HAH_FINAL_FORM L"\ufd87" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_MEEM_WITH_HAH_INITIAL_FORM 0xfd88 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_MEEM_WITH_HAH_INITIAL_FORM L"\ufd88" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_HAH_WITH_JEEM_INITIAL_FORM 0xfd89 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_HAH_WITH_JEEM_INITIAL_FORM L"\ufd89" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_HAH_WITH_MEEM_INITIAL_FORM 0xfd8a #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_HAH_WITH_MEEM_INITIAL_FORM L"\ufd8a" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_HAH_WITH_YEH_FINAL_FORM 0xfd8b #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_HAH_WITH_YEH_FINAL_FORM L"\ufd8b" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_JEEM_WITH_HAH_INITIAL_FORM 0xfd8c #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_JEEM_WITH_HAH_INITIAL_FORM L"\ufd8c" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_JEEM_WITH_MEEM_INITIAL_FORM 0xfd8d #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_JEEM_WITH_MEEM_INITIAL_FORM L"\ufd8d" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_KHAH_WITH_JEEM_INITIAL_FORM 0xfd8e #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_KHAH_WITH_JEEM_INITIAL_FORM L"\ufd8e" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_KHAH_WITH_MEEM_INITIAL_FORM 0xfd8f #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_KHAH_WITH_MEEM_INITIAL_FORM L"\ufd8f" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_JEEM_WITH_KHAH_INITIAL_FORM 0xfd92 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_JEEM_WITH_KHAH_INITIAL_FORM L"\ufd92" #define UNICODE_ARABIC_LIGATURE_HEH_WITH_MEEM_WITH_JEEM_INITIAL_FORM 0xfd93 #define UNITEXT_ARABIC_LIGATURE_HEH_WITH_MEEM_WITH_JEEM_INITIAL_FORM L"\ufd93" #define UNICODE_ARABIC_LIGATURE_HEH_WITH_MEEM_WITH_MEEM_INITIAL_FORM 0xfd94 #define UNITEXT_ARABIC_LIGATURE_HEH_WITH_MEEM_WITH_MEEM_INITIAL_FORM L"\ufd94" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_HAH_WITH_MEEM_INITIAL_FORM 0xfd95 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_HAH_WITH_MEEM_INITIAL_FORM L"\ufd95" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_HAH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd96 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_HAH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd96" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_MEEM_FINAL_FORM 0xfd97 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_MEEM_FINAL_FORM L"\ufd97" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_MEEM_INITIAL_FORM 0xfd98 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_MEEM_INITIAL_FORM L"\ufd98" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd99 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd99" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfd9a #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufd9a" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfd9b #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufd9b" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_MEEM_WITH_MEEM_FINAL_FORM 0xfd9c #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_MEEM_WITH_MEEM_FINAL_FORM L"\ufd9c" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_MEEM_WITH_MEEM_INITIAL_FORM 0xfd9d #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_MEEM_WITH_MEEM_INITIAL_FORM L"\ufd9d" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_KHAH_WITH_YEH_FINAL_FORM 0xfd9e #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_KHAH_WITH_YEH_FINAL_FORM L"\ufd9e" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_JEEM_WITH_YEH_FINAL_FORM 0xfd9f #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_JEEM_WITH_YEH_FINAL_FORM L"\ufd9f" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_JEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfda0 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_JEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufda0" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_KHAH_WITH_YEH_FINAL_FORM 0xfda1 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_KHAH_WITH_YEH_FINAL_FORM L"\ufda1" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_KHAH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfda2 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_KHAH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufda2" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfda3 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufda3" #define UNICODE_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfda4 #define UNITEXT_ARABIC_LIGATURE_TEH_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufda4" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfda5 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufda5" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_HAH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfda6 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_HAH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufda6" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM 0xfda7 #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_MEEM_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufda7" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_KHAH_WITH_ALEF_MAKSURA_FINAL_FORM 0xfda8 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_KHAH_WITH_ALEF_MAKSURA_FINAL_FORM L"\ufda8" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_HAH_WITH_YEH_FINAL_FORM 0xfda9 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_HAH_WITH_YEH_FINAL_FORM L"\ufda9" #define UNICODE_ARABIC_LIGATURE_SHEEN_WITH_HAH_WITH_YEH_FINAL_FORM 0xfdaa #define UNITEXT_ARABIC_LIGATURE_SHEEN_WITH_HAH_WITH_YEH_FINAL_FORM L"\ufdaa" #define UNICODE_ARABIC_LIGATURE_DAD_WITH_HAH_WITH_YEH_FINAL_FORM 0xfdab #define UNITEXT_ARABIC_LIGATURE_DAD_WITH_HAH_WITH_YEH_FINAL_FORM L"\ufdab" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_YEH_FINAL_FORM 0xfdac #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_YEH_FINAL_FORM L"\ufdac" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfdad #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufdad" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_HAH_WITH_YEH_FINAL_FORM 0xfdae #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_HAH_WITH_YEH_FINAL_FORM L"\ufdae" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_JEEM_WITH_YEH_FINAL_FORM 0xfdaf #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_JEEM_WITH_YEH_FINAL_FORM L"\ufdaf" #define UNICODE_ARABIC_LIGATURE_YEH_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfdb0 #define UNITEXT_ARABIC_LIGATURE_YEH_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufdb0" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfdb1 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufdb1" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfdb2 #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufdb2" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_HAH_WITH_YEH_FINAL_FORM 0xfdb3 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_HAH_WITH_YEH_FINAL_FORM L"\ufdb3" #define UNICODE_ARABIC_LIGATURE_QAF_WITH_MEEM_WITH_HAH_INITIAL_FORM 0xfdb4 #define UNITEXT_ARABIC_LIGATURE_QAF_WITH_MEEM_WITH_HAH_INITIAL_FORM L"\ufdb4" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_HAH_WITH_MEEM_INITIAL_FORM 0xfdb5 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_HAH_WITH_MEEM_INITIAL_FORM L"\ufdb5" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfdb6 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufdb6" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfdb7 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufdb7" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_HAH_INITIAL_FORM 0xfdb8 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_HAH_INITIAL_FORM L"\ufdb8" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_KHAH_WITH_YEH_FINAL_FORM 0xfdb9 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_KHAH_WITH_YEH_FINAL_FORM L"\ufdb9" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_MEEM_INITIAL_FORM 0xfdba #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_MEEM_INITIAL_FORM L"\ufdba" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_MEEM_WITH_MEEM_FINAL_FORM 0xfdbb #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_MEEM_WITH_MEEM_FINAL_FORM L"\ufdbb" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_MEEM_FINAL_FORM 0xfdbc #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_JEEM_WITH_MEEM_FINAL_FORM L"\ufdbc" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_HAH_FINAL_FORM 0xfdbd #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_HAH_FINAL_FORM L"\ufdbd" #define UNICODE_ARABIC_LIGATURE_JEEM_WITH_HAH_WITH_YEH_FINAL_FORM 0xfdbe #define UNITEXT_ARABIC_LIGATURE_JEEM_WITH_HAH_WITH_YEH_FINAL_FORM L"\ufdbe" #define UNICODE_ARABIC_LIGATURE_HAH_WITH_JEEM_WITH_YEH_FINAL_FORM 0xfdbf #define UNITEXT_ARABIC_LIGATURE_HAH_WITH_JEEM_WITH_YEH_FINAL_FORM L"\ufdbf" #define UNICODE_ARABIC_LIGATURE_MEEM_WITH_JEEM_WITH_YEH_FINAL_FORM 0xfdc0 #define UNITEXT_ARABIC_LIGATURE_MEEM_WITH_JEEM_WITH_YEH_FINAL_FORM L"\ufdc0" #define UNICODE_ARABIC_LIGATURE_FEH_WITH_MEEM_WITH_YEH_FINAL_FORM 0xfdc1 #define UNITEXT_ARABIC_LIGATURE_FEH_WITH_MEEM_WITH_YEH_FINAL_FORM L"\ufdc1" #define UNICODE_ARABIC_LIGATURE_BEH_WITH_HAH_WITH_YEH_FINAL_FORM 0xfdc2 #define UNITEXT_ARABIC_LIGATURE_BEH_WITH_HAH_WITH_YEH_FINAL_FORM L"\ufdc2" #define UNICODE_ARABIC_LIGATURE_KAF_WITH_MEEM_WITH_MEEM_INITIAL_FORM 0xfdc3 #define UNITEXT_ARABIC_LIGATURE_KAF_WITH_MEEM_WITH_MEEM_INITIAL_FORM L"\ufdc3" #define UNICODE_ARABIC_LIGATURE_AIN_WITH_JEEM_WITH_MEEM_INITIAL_FORM 0xfdc4 #define UNITEXT_ARABIC_LIGATURE_AIN_WITH_JEEM_WITH_MEEM_INITIAL_FORM L"\ufdc4" #define UNICODE_ARABIC_LIGATURE_SAD_WITH_MEEM_WITH_MEEM_INITIAL_FORM 0xfdc5 #define UNITEXT_ARABIC_LIGATURE_SAD_WITH_MEEM_WITH_MEEM_INITIAL_FORM L"\ufdc5" #define UNICODE_ARABIC_LIGATURE_SEEN_WITH_KHAH_WITH_YEH_FINAL_FORM 0xfdc6 #define UNITEXT_ARABIC_LIGATURE_SEEN_WITH_KHAH_WITH_YEH_FINAL_FORM L"\ufdc6" #define UNICODE_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_YEH_FINAL_FORM 0xfdc7 #define UNITEXT_ARABIC_LIGATURE_NOON_WITH_JEEM_WITH_YEH_FINAL_FORM L"\ufdc7" #define UNICODE_ARABIC_LIGATURE_SALLA_USED_AS_KORANIC_STOP_SIGN_ISOLATED_FORM 0xfdf0 #define UNITEXT_ARABIC_LIGATURE_SALLA_USED_AS_KORANIC_STOP_SIGN_ISOLATED_FORM L"\ufdf0" #define UNICODE_ARABIC_LIGATURE_QALA_USED_AS_KORANIC_STOP_SIGN_ISOLATED_FORM 0xfdf1 #define UNITEXT_ARABIC_LIGATURE_QALA_USED_AS_KORANIC_STOP_SIGN_ISOLATED_FORM L"\ufdf1" #define UNICODE_ARABIC_LIGATURE_ALLAH_ISOLATED_FORM 0xfdf2 #define UNITEXT_ARABIC_LIGATURE_ALLAH_ISOLATED_FORM L"\ufdf2" #define UNICODE_ARABIC_LIGATURE_AKBAR_ISOLATED_FORM 0xfdf3 #define UNITEXT_ARABIC_LIGATURE_AKBAR_ISOLATED_FORM L"\ufdf3" #define UNICODE_ARABIC_LIGATURE_MOHAMMAD_ISOLATED_FORM 0xfdf4 #define UNITEXT_ARABIC_LIGATURE_MOHAMMAD_ISOLATED_FORM L"\ufdf4" #define UNICODE_ARABIC_LIGATURE_SALAM_ISOLATED_FORM 0xfdf5 #define UNITEXT_ARABIC_LIGATURE_SALAM_ISOLATED_FORM L"\ufdf5" #define UNICODE_ARABIC_LIGATURE_RASOUL_ISOLATED_FORM 0xfdf6 #define UNITEXT_ARABIC_LIGATURE_RASOUL_ISOLATED_FORM L"\ufdf6" #define UNICODE_ARABIC_LIGATURE_ALAYHE_ISOLATED_FORM 0xfdf7 #define UNITEXT_ARABIC_LIGATURE_ALAYHE_ISOLATED_FORM L"\ufdf7" #define UNICODE_ARABIC_LIGATURE_WASALLAM_ISOLATED_FORM 0xfdf8 #define UNITEXT_ARABIC_LIGATURE_WASALLAM_ISOLATED_FORM L"\ufdf8" #define UNICODE_ARABIC_LIGATURE_SALLA_ISOLATED_FORM 0xfdf9 #define UNITEXT_ARABIC_LIGATURE_SALLA_ISOLATED_FORM L"\ufdf9" #define UNICODE_ARABIC_LIGATURE_SALLALLAHOU_ALAYHE_WASALLAM 0xfdfa #define UNITEXT_ARABIC_LIGATURE_SALLALLAHOU_ALAYHE_WASALLAM L"\ufdfa" #define UNICODE_ARABIC_LIGATURE_JALLAJALALOUHOU 0xfdfb #define UNITEXT_ARABIC_LIGATURE_JALLAJALALOUHOU L"\ufdfb" #define UNICODE_RIAL_SIGN 0xfdfc #define UNITEXT_RIAL_SIGN L"\ufdfc" #define UNICODE_ARABIC_LIGATURE_BISMILLAH_AR_RAHMAN_AR_RAHEEM 0xfdfd #define UNITEXT_ARABIC_LIGATURE_BISMILLAH_AR_RAHMAN_AR_RAHEEM L"\ufdfd" #define UNICODE_VARIATION_SELECTOR_1 0xfe00 #define UNITEXT_VARIATION_SELECTOR_1 L"\ufe00" #define UNICODE_VARIATION_SELECTOR_2 0xfe01 #define UNITEXT_VARIATION_SELECTOR_2 L"\ufe01" #define UNICODE_VARIATION_SELECTOR_3 0xfe02 #define UNITEXT_VARIATION_SELECTOR_3 L"\ufe02" #define UNICODE_VARIATION_SELECTOR_4 0xfe03 #define UNITEXT_VARIATION_SELECTOR_4 L"\ufe03" #define UNICODE_VARIATION_SELECTOR_5 0xfe04 #define UNITEXT_VARIATION_SELECTOR_5 L"\ufe04" #define UNICODE_VARIATION_SELECTOR_6 0xfe05 #define UNITEXT_VARIATION_SELECTOR_6 L"\ufe05" #define UNICODE_VARIATION_SELECTOR_7 0xfe06 #define UNITEXT_VARIATION_SELECTOR_7 L"\ufe06" #define UNICODE_VARIATION_SELECTOR_8 0xfe07 #define UNITEXT_VARIATION_SELECTOR_8 L"\ufe07" #define UNICODE_VARIATION_SELECTOR_9 0xfe08 #define UNITEXT_VARIATION_SELECTOR_9 L"\ufe08" #define UNICODE_VARIATION_SELECTOR_10 0xfe09 #define UNITEXT_VARIATION_SELECTOR_10 L"\ufe09" #define UNICODE_VARIATION_SELECTOR_11 0xfe0a #define UNITEXT_VARIATION_SELECTOR_11 L"\ufe0a" #define UNICODE_VARIATION_SELECTOR_12 0xfe0b #define UNITEXT_VARIATION_SELECTOR_12 L"\ufe0b" #define UNICODE_VARIATION_SELECTOR_13 0xfe0c #define UNITEXT_VARIATION_SELECTOR_13 L"\ufe0c" #define UNICODE_VARIATION_SELECTOR_14 0xfe0d #define UNITEXT_VARIATION_SELECTOR_14 L"\ufe0d" #define UNICODE_VARIATION_SELECTOR_15 0xfe0e #define UNITEXT_VARIATION_SELECTOR_15 L"\ufe0e" #define UNICODE_VARIATION_SELECTOR_16 0xfe0f #define UNITEXT_VARIATION_SELECTOR_16 L"\ufe0f" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_COMMA 0xfe10 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_COMMA L"\ufe10" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_IDEOGRAPHIC_COMMA 0xfe11 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_IDEOGRAPHIC_COMMA L"\ufe11" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_IDEOGRAPHIC_FULL_STOP 0xfe12 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_IDEOGRAPHIC_FULL_STOP L"\ufe12" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_COLON 0xfe13 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_COLON L"\ufe13" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_SEMICOLON 0xfe14 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_SEMICOLON L"\ufe14" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_EXCLAMATION_MARK 0xfe15 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_EXCLAMATION_MARK L"\ufe15" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_QUESTION_MARK 0xfe16 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_QUESTION_MARK L"\ufe16" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_WHITE_LENTICULAR_BRACKET 0xfe17 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_WHITE_LENTICULAR_BRACKET L"\ufe17" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_WHITE_LENTICULAR_BRAKCET 0xfe18 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_WHITE_LENTICULAR_BRAKCET L"\ufe18" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_HORIZONTAL_ELLIPSIS 0xfe19 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_HORIZONTAL_ELLIPSIS L"\ufe19" #define UNICODE_COMBINING_LIGATURE_LEFT_HALF 0xfe20 #define UNITEXT_COMBINING_LIGATURE_LEFT_HALF L"\ufe20" #define UNICODE_COMBINING_LIGATURE_RIGHT_HALF 0xfe21 #define UNITEXT_COMBINING_LIGATURE_RIGHT_HALF L"\ufe21" #define UNICODE_COMBINING_DOUBLE_TILDE_LEFT_HALF 0xfe22 #define UNITEXT_COMBINING_DOUBLE_TILDE_LEFT_HALF L"\ufe22" #define UNICODE_COMBINING_DOUBLE_TILDE_RIGHT_HALF 0xfe23 #define UNITEXT_COMBINING_DOUBLE_TILDE_RIGHT_HALF L"\ufe23" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_TWO_DOT_LEADER 0xfe30 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_TWO_DOT_LEADER L"\ufe30" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_EM_DASH 0xfe31 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_EM_DASH L"\ufe31" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_EN_DASH 0xfe32 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_EN_DASH L"\ufe32" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LOW_LINE 0xfe33 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LOW_LINE L"\ufe33" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_WAVY_LOW_LINE 0xfe34 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_WAVY_LOW_LINE L"\ufe34" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_PARENTHESIS 0xfe35 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_PARENTHESIS L"\ufe35" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_PARENTHESIS 0xfe36 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_PARENTHESIS L"\ufe36" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_CURLY_BRACKET 0xfe37 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_CURLY_BRACKET L"\ufe37" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_CURLY_BRACKET 0xfe38 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_CURLY_BRACKET L"\ufe38" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_TORTOISE_SHELL_BRACKET 0xfe39 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_TORTOISE_SHELL_BRACKET L"\ufe39" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_TORTOISE_SHELL_BRACKET 0xfe3a #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_TORTOISE_SHELL_BRACKET L"\ufe3a" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_BLACK_LENTICULAR_BRACKET 0xfe3b #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_BLACK_LENTICULAR_BRACKET L"\ufe3b" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_BLACK_LENTICULAR_BRACKET 0xfe3c #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_BLACK_LENTICULAR_BRACKET L"\ufe3c" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_DOUBLE_ANGLE_BRACKET 0xfe3d #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_DOUBLE_ANGLE_BRACKET L"\ufe3d" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_DOUBLE_ANGLE_BRACKET 0xfe3e #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_DOUBLE_ANGLE_BRACKET L"\ufe3e" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_ANGLE_BRACKET 0xfe3f #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_ANGLE_BRACKET L"\ufe3f" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_ANGLE_BRACKET 0xfe40 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_ANGLE_BRACKET L"\ufe40" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_CORNER_BRACKET 0xfe41 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_CORNER_BRACKET L"\ufe41" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_CORNER_BRACKET 0xfe42 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_CORNER_BRACKET L"\ufe42" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_WHITE_CORNER_BRACKET 0xfe43 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_WHITE_CORNER_BRACKET L"\ufe43" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_WHITE_CORNER_BRACKET 0xfe44 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_WHITE_CORNER_BRACKET L"\ufe44" #define UNICODE_SESAME_DOT 0xfe45 #define UNITEXT_SESAME_DOT L"\ufe45" #define UNICODE_WHITE_SESAME_DOT 0xfe46 #define UNITEXT_WHITE_SESAME_DOT L"\ufe46" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_LEFT_SQUARE_BRACKET 0xfe47 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_LEFT_SQUARE_BRACKET L"\ufe47" #define UNICODE_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_SQUARE_BRACKET 0xfe48 #define UNITEXT_PRESENTATION_FORM_FOR_VERTICAL_RIGHT_SQUARE_BRACKET L"\ufe48" #define UNICODE_DASHED_OVERLINE 0xfe49 #define UNITEXT_DASHED_OVERLINE L"\ufe49" #define UNICODE_CENTRELINE_OVERLINE 0xfe4a #define UNITEXT_CENTRELINE_OVERLINE L"\ufe4a" #define UNICODE_WAVY_OVERLINE 0xfe4b #define UNITEXT_WAVY_OVERLINE L"\ufe4b" #define UNICODE_DOUBLE_WAVY_OVERLINE 0xfe4c #define UNITEXT_DOUBLE_WAVY_OVERLINE L"\ufe4c" #define UNICODE_DASHED_LOW_LINE 0xfe4d #define UNITEXT_DASHED_LOW_LINE L"\ufe4d" #define UNICODE_CENTRELINE_LOW_LINE 0xfe4e #define UNITEXT_CENTRELINE_LOW_LINE L"\ufe4e" #define UNICODE_WAVY_LOW_LINE 0xfe4f #define UNITEXT_WAVY_LOW_LINE L"\ufe4f" #define UNICODE_SMALL_COMMA 0xfe50 #define UNITEXT_SMALL_COMMA L"\ufe50" #define UNICODE_SMALL_IDEOGRAPHIC_COMMA 0xfe51 #define UNITEXT_SMALL_IDEOGRAPHIC_COMMA L"\ufe51" #define UNICODE_SMALL_FULL_STOP 0xfe52 #define UNITEXT_SMALL_FULL_STOP L"\ufe52" #define UNICODE_SMALL_SEMICOLON 0xfe54 #define UNITEXT_SMALL_SEMICOLON L"\ufe54" #define UNICODE_SMALL_COLON 0xfe55 #define UNITEXT_SMALL_COLON L"\ufe55" #define UNICODE_SMALL_QUESTION_MARK 0xfe56 #define UNITEXT_SMALL_QUESTION_MARK L"\ufe56" #define UNICODE_SMALL_EXCLAMATION_MARK 0xfe57 #define UNITEXT_SMALL_EXCLAMATION_MARK L"\ufe57" #define UNICODE_SMALL_EM_DASH 0xfe58 #define UNITEXT_SMALL_EM_DASH L"\ufe58" #define UNICODE_SMALL_LEFT_PARENTHESIS 0xfe59 #define UNITEXT_SMALL_LEFT_PARENTHESIS L"\ufe59" #define UNICODE_SMALL_RIGHT_PARENTHESIS 0xfe5a #define UNITEXT_SMALL_RIGHT_PARENTHESIS L"\ufe5a" #define UNICODE_SMALL_LEFT_CURLY_BRACKET 0xfe5b #define UNITEXT_SMALL_LEFT_CURLY_BRACKET L"\ufe5b" #define UNICODE_SMALL_RIGHT_CURLY_BRACKET 0xfe5c #define UNITEXT_SMALL_RIGHT_CURLY_BRACKET L"\ufe5c" #define UNICODE_SMALL_LEFT_TORTOISE_SHELL_BRACKET 0xfe5d #define UNITEXT_SMALL_LEFT_TORTOISE_SHELL_BRACKET L"\ufe5d" #define UNICODE_SMALL_RIGHT_TORTOISE_SHELL_BRACKET 0xfe5e #define UNITEXT_SMALL_RIGHT_TORTOISE_SHELL_BRACKET L"\ufe5e" #define UNICODE_SMALL_NUMBER_SIGN 0xfe5f #define UNITEXT_SMALL_NUMBER_SIGN L"\ufe5f" #define UNICODE_SMALL_AMPERSAND 0xfe60 #define UNITEXT_SMALL_AMPERSAND L"\ufe60" #define UNICODE_SMALL_ASTERISK 0xfe61 #define UNITEXT_SMALL_ASTERISK L"\ufe61" #define UNICODE_SMALL_PLUS_SIGN 0xfe62 #define UNITEXT_SMALL_PLUS_SIGN L"\ufe62" #define UNICODE_SMALL_HYPHEN_MINUS 0xfe63 #define UNITEXT_SMALL_HYPHEN_MINUS L"\ufe63" #define UNICODE_SMALL_LESS_THAN_SIGN 0xfe64 #define UNITEXT_SMALL_LESS_THAN_SIGN L"\ufe64" #define UNICODE_SMALL_GREATER_THAN_SIGN 0xfe65 #define UNITEXT_SMALL_GREATER_THAN_SIGN L"\ufe65" #define UNICODE_SMALL_EQUALS_SIGN 0xfe66 #define UNITEXT_SMALL_EQUALS_SIGN L"\ufe66" #define UNICODE_SMALL_REVERSE_SOLIDUS 0xfe68 #define UNITEXT_SMALL_REVERSE_SOLIDUS L"\ufe68" #define UNICODE_SMALL_DOLLAR_SIGN 0xfe69 #define UNITEXT_SMALL_DOLLAR_SIGN L"\ufe69" #define UNICODE_SMALL_PERCENT_SIGN 0xfe6a #define UNITEXT_SMALL_PERCENT_SIGN L"\ufe6a" #define UNICODE_SMALL_COMMERCIAL_AT 0xfe6b #define UNITEXT_SMALL_COMMERCIAL_AT L"\ufe6b" #define UNICODE_ARABIC_FATHATAN_ISOLATED_FORM 0xfe70 #define UNITEXT_ARABIC_FATHATAN_ISOLATED_FORM L"\ufe70" #define UNICODE_ARABIC_TATWEEL_WITH_FATHATAN_ABOVE 0xfe71 #define UNITEXT_ARABIC_TATWEEL_WITH_FATHATAN_ABOVE L"\ufe71" #define UNICODE_ARABIC_DAMMATAN_ISOLATED_FORM 0xfe72 #define UNITEXT_ARABIC_DAMMATAN_ISOLATED_FORM L"\ufe72" #define UNICODE_ARABIC_TAIL_FRAGMENT 0xfe73 #define UNITEXT_ARABIC_TAIL_FRAGMENT L"\ufe73" #define UNICODE_ARABIC_KASRATAN_ISOLATED_FORM 0xfe74 #define UNITEXT_ARABIC_KASRATAN_ISOLATED_FORM L"\ufe74" #define UNICODE_ARABIC_FATHA_ISOLATED_FORM 0xfe76 #define UNITEXT_ARABIC_FATHA_ISOLATED_FORM L"\ufe76" #define UNICODE_ARABIC_FATHA_MEDIAL_FORM 0xfe77 #define UNITEXT_ARABIC_FATHA_MEDIAL_FORM L"\ufe77" #define UNICODE_ARABIC_DAMMA_ISOLATED_FORM 0xfe78 #define UNITEXT_ARABIC_DAMMA_ISOLATED_FORM L"\ufe78" #define UNICODE_ARABIC_DAMMA_MEDIAL_FORM 0xfe79 #define UNITEXT_ARABIC_DAMMA_MEDIAL_FORM L"\ufe79" #define UNICODE_ARABIC_KASRA_ISOLATED_FORM 0xfe7a #define UNITEXT_ARABIC_KASRA_ISOLATED_FORM L"\ufe7a" #define UNICODE_ARABIC_KASRA_MEDIAL_FORM 0xfe7b #define UNITEXT_ARABIC_KASRA_MEDIAL_FORM L"\ufe7b" #define UNICODE_ARABIC_SHADDA_ISOLATED_FORM 0xfe7c #define UNITEXT_ARABIC_SHADDA_ISOLATED_FORM L"\ufe7c" #define UNICODE_ARABIC_SHADDA_MEDIAL_FORM 0xfe7d #define UNITEXT_ARABIC_SHADDA_MEDIAL_FORM L"\ufe7d" #define UNICODE_ARABIC_SUKUN_ISOLATED_FORM 0xfe7e #define UNITEXT_ARABIC_SUKUN_ISOLATED_FORM L"\ufe7e" #define UNICODE_ARABIC_SUKUN_MEDIAL_FORM 0xfe7f #define UNITEXT_ARABIC_SUKUN_MEDIAL_FORM L"\ufe7f" #define UNICODE_ARABIC_LETTER_HAMZA_ISOLATED_FORM 0xfe80 #define UNITEXT_ARABIC_LETTER_HAMZA_ISOLATED_FORM L"\ufe80" #define UNICODE_ARABIC_LETTER_ALEF_WITH_MADDA_ABOVE_ISOLATED_FORM 0xfe81 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_MADDA_ABOVE_ISOLATED_FORM L"\ufe81" #define UNICODE_ARABIC_LETTER_ALEF_WITH_MADDA_ABOVE_FINAL_FORM 0xfe82 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_MADDA_ABOVE_FINAL_FORM L"\ufe82" #define UNICODE_ARABIC_LETTER_ALEF_WITH_HAMZA_ABOVE_ISOLATED_FORM 0xfe83 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_HAMZA_ABOVE_ISOLATED_FORM L"\ufe83" #define UNICODE_ARABIC_LETTER_ALEF_WITH_HAMZA_ABOVE_FINAL_FORM 0xfe84 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_HAMZA_ABOVE_FINAL_FORM L"\ufe84" #define UNICODE_ARABIC_LETTER_WAW_WITH_HAMZA_ABOVE_ISOLATED_FORM 0xfe85 #define UNITEXT_ARABIC_LETTER_WAW_WITH_HAMZA_ABOVE_ISOLATED_FORM L"\ufe85" #define UNICODE_ARABIC_LETTER_WAW_WITH_HAMZA_ABOVE_FINAL_FORM 0xfe86 #define UNITEXT_ARABIC_LETTER_WAW_WITH_HAMZA_ABOVE_FINAL_FORM L"\ufe86" #define UNICODE_ARABIC_LETTER_ALEF_WITH_HAMZA_BELOW_ISOLATED_FORM 0xfe87 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_HAMZA_BELOW_ISOLATED_FORM L"\ufe87" #define UNICODE_ARABIC_LETTER_ALEF_WITH_HAMZA_BELOW_FINAL_FORM 0xfe88 #define UNITEXT_ARABIC_LETTER_ALEF_WITH_HAMZA_BELOW_FINAL_FORM L"\ufe88" #define UNICODE_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE_ISOLATED_FORM 0xfe89 #define UNITEXT_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE_ISOLATED_FORM L"\ufe89" #define UNICODE_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE_FINAL_FORM 0xfe8a #define UNITEXT_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE_FINAL_FORM L"\ufe8a" #define UNICODE_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE_INITIAL_FORM 0xfe8b #define UNITEXT_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE_INITIAL_FORM L"\ufe8b" #define UNICODE_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE_MEDIAL_FORM 0xfe8c #define UNITEXT_ARABIC_LETTER_YEH_WITH_HAMZA_ABOVE_MEDIAL_FORM L"\ufe8c" #define UNICODE_ARABIC_LETTER_ALEF_ISOLATED_FORM 0xfe8d #define UNITEXT_ARABIC_LETTER_ALEF_ISOLATED_FORM L"\ufe8d" #define UNICODE_ARABIC_LETTER_ALEF_FINAL_FORM 0xfe8e #define UNITEXT_ARABIC_LETTER_ALEF_FINAL_FORM L"\ufe8e" #define UNICODE_ARABIC_LETTER_BEH_ISOLATED_FORM 0xfe8f #define UNITEXT_ARABIC_LETTER_BEH_ISOLATED_FORM L"\ufe8f" #define UNICODE_ARABIC_LETTER_BEH_FINAL_FORM 0xfe90 #define UNITEXT_ARABIC_LETTER_BEH_FINAL_FORM L"\ufe90" #define UNICODE_ARABIC_LETTER_BEH_INITIAL_FORM 0xfe91 #define UNITEXT_ARABIC_LETTER_BEH_INITIAL_FORM L"\ufe91" #define UNICODE_ARABIC_LETTER_BEH_MEDIAL_FORM 0xfe92 #define UNITEXT_ARABIC_LETTER_BEH_MEDIAL_FORM L"\ufe92" #define UNICODE_ARABIC_LETTER_TEH_MARBUTA_ISOLATED_FORM 0xfe93 #define UNITEXT_ARABIC_LETTER_TEH_MARBUTA_ISOLATED_FORM L"\ufe93" #define UNICODE_ARABIC_LETTER_TEH_MARBUTA_FINAL_FORM 0xfe94 #define UNITEXT_ARABIC_LETTER_TEH_MARBUTA_FINAL_FORM L"\ufe94" #define UNICODE_ARABIC_LETTER_TEH_ISOLATED_FORM 0xfe95 #define UNITEXT_ARABIC_LETTER_TEH_ISOLATED_FORM L"\ufe95" #define UNICODE_ARABIC_LETTER_TEH_FINAL_FORM 0xfe96 #define UNITEXT_ARABIC_LETTER_TEH_FINAL_FORM L"\ufe96" #define UNICODE_ARABIC_LETTER_TEH_INITIAL_FORM 0xfe97 #define UNITEXT_ARABIC_LETTER_TEH_INITIAL_FORM L"\ufe97" #define UNICODE_ARABIC_LETTER_TEH_MEDIAL_FORM 0xfe98 #define UNITEXT_ARABIC_LETTER_TEH_MEDIAL_FORM L"\ufe98" #define UNICODE_ARABIC_LETTER_THEH_ISOLATED_FORM 0xfe99 #define UNITEXT_ARABIC_LETTER_THEH_ISOLATED_FORM L"\ufe99" #define UNICODE_ARABIC_LETTER_THEH_FINAL_FORM 0xfe9a #define UNITEXT_ARABIC_LETTER_THEH_FINAL_FORM L"\ufe9a" #define UNICODE_ARABIC_LETTER_THEH_INITIAL_FORM 0xfe9b #define UNITEXT_ARABIC_LETTER_THEH_INITIAL_FORM L"\ufe9b" #define UNICODE_ARABIC_LETTER_THEH_MEDIAL_FORM 0xfe9c #define UNITEXT_ARABIC_LETTER_THEH_MEDIAL_FORM L"\ufe9c" #define UNICODE_ARABIC_LETTER_JEEM_ISOLATED_FORM 0xfe9d #define UNITEXT_ARABIC_LETTER_JEEM_ISOLATED_FORM L"\ufe9d" #define UNICODE_ARABIC_LETTER_JEEM_FINAL_FORM 0xfe9e #define UNITEXT_ARABIC_LETTER_JEEM_FINAL_FORM L"\ufe9e" #define UNICODE_ARABIC_LETTER_JEEM_INITIAL_FORM 0xfe9f #define UNITEXT_ARABIC_LETTER_JEEM_INITIAL_FORM L"\ufe9f" #define UNICODE_ARABIC_LETTER_JEEM_MEDIAL_FORM 0xfea0 #define UNITEXT_ARABIC_LETTER_JEEM_MEDIAL_FORM L"\ufea0" #define UNICODE_ARABIC_LETTER_HAH_ISOLATED_FORM 0xfea1 #define UNITEXT_ARABIC_LETTER_HAH_ISOLATED_FORM L"\ufea1" #define UNICODE_ARABIC_LETTER_HAH_FINAL_FORM 0xfea2 #define UNITEXT_ARABIC_LETTER_HAH_FINAL_FORM L"\ufea2" #define UNICODE_ARABIC_LETTER_HAH_INITIAL_FORM 0xfea3 #define UNITEXT_ARABIC_LETTER_HAH_INITIAL_FORM L"\ufea3" #define UNICODE_ARABIC_LETTER_HAH_MEDIAL_FORM 0xfea4 #define UNITEXT_ARABIC_LETTER_HAH_MEDIAL_FORM L"\ufea4" #define UNICODE_ARABIC_LETTER_KHAH_ISOLATED_FORM 0xfea5 #define UNITEXT_ARABIC_LETTER_KHAH_ISOLATED_FORM L"\ufea5" #define UNICODE_ARABIC_LETTER_KHAH_FINAL_FORM 0xfea6 #define UNITEXT_ARABIC_LETTER_KHAH_FINAL_FORM L"\ufea6" #define UNICODE_ARABIC_LETTER_KHAH_INITIAL_FORM 0xfea7 #define UNITEXT_ARABIC_LETTER_KHAH_INITIAL_FORM L"\ufea7" #define UNICODE_ARABIC_LETTER_KHAH_MEDIAL_FORM 0xfea8 #define UNITEXT_ARABIC_LETTER_KHAH_MEDIAL_FORM L"\ufea8" #define UNICODE_ARABIC_LETTER_DAL_ISOLATED_FORM 0xfea9 #define UNITEXT_ARABIC_LETTER_DAL_ISOLATED_FORM L"\ufea9" #define UNICODE_ARABIC_LETTER_DAL_FINAL_FORM 0xfeaa #define UNITEXT_ARABIC_LETTER_DAL_FINAL_FORM L"\ufeaa" #define UNICODE_ARABIC_LETTER_THAL_ISOLATED_FORM 0xfeab #define UNITEXT_ARABIC_LETTER_THAL_ISOLATED_FORM L"\ufeab" #define UNICODE_ARABIC_LETTER_THAL_FINAL_FORM 0xfeac #define UNITEXT_ARABIC_LETTER_THAL_FINAL_FORM L"\ufeac" #define UNICODE_ARABIC_LETTER_REH_ISOLATED_FORM 0xfead #define UNITEXT_ARABIC_LETTER_REH_ISOLATED_FORM L"\ufead" #define UNICODE_ARABIC_LETTER_REH_FINAL_FORM 0xfeae #define UNITEXT_ARABIC_LETTER_REH_FINAL_FORM L"\ufeae" #define UNICODE_ARABIC_LETTER_ZAIN_ISOLATED_FORM 0xfeaf #define UNITEXT_ARABIC_LETTER_ZAIN_ISOLATED_FORM L"\ufeaf" #define UNICODE_ARABIC_LETTER_ZAIN_FINAL_FORM 0xfeb0 #define UNITEXT_ARABIC_LETTER_ZAIN_FINAL_FORM L"\ufeb0" #define UNICODE_ARABIC_LETTER_SEEN_ISOLATED_FORM 0xfeb1 #define UNITEXT_ARABIC_LETTER_SEEN_ISOLATED_FORM L"\ufeb1" #define UNICODE_ARABIC_LETTER_SEEN_FINAL_FORM 0xfeb2 #define UNITEXT_ARABIC_LETTER_SEEN_FINAL_FORM L"\ufeb2" #define UNICODE_ARABIC_LETTER_SEEN_INITIAL_FORM 0xfeb3 #define UNITEXT_ARABIC_LETTER_SEEN_INITIAL_FORM L"\ufeb3" #define UNICODE_ARABIC_LETTER_SEEN_MEDIAL_FORM 0xfeb4 #define UNITEXT_ARABIC_LETTER_SEEN_MEDIAL_FORM L"\ufeb4" #define UNICODE_ARABIC_LETTER_SHEEN_ISOLATED_FORM 0xfeb5 #define UNITEXT_ARABIC_LETTER_SHEEN_ISOLATED_FORM L"\ufeb5" #define UNICODE_ARABIC_LETTER_SHEEN_FINAL_FORM 0xfeb6 #define UNITEXT_ARABIC_LETTER_SHEEN_FINAL_FORM L"\ufeb6" #define UNICODE_ARABIC_LETTER_SHEEN_INITIAL_FORM 0xfeb7 #define UNITEXT_ARABIC_LETTER_SHEEN_INITIAL_FORM L"\ufeb7" #define UNICODE_ARABIC_LETTER_SHEEN_MEDIAL_FORM 0xfeb8 #define UNITEXT_ARABIC_LETTER_SHEEN_MEDIAL_FORM L"\ufeb8" #define UNICODE_ARABIC_LETTER_SAD_ISOLATED_FORM 0xfeb9 #define UNITEXT_ARABIC_LETTER_SAD_ISOLATED_FORM L"\ufeb9" #define UNICODE_ARABIC_LETTER_SAD_FINAL_FORM 0xfeba #define UNITEXT_ARABIC_LETTER_SAD_FINAL_FORM L"\ufeba" #define UNICODE_ARABIC_LETTER_SAD_INITIAL_FORM 0xfebb #define UNITEXT_ARABIC_LETTER_SAD_INITIAL_FORM L"\ufebb" #define UNICODE_ARABIC_LETTER_SAD_MEDIAL_FORM 0xfebc #define UNITEXT_ARABIC_LETTER_SAD_MEDIAL_FORM L"\ufebc" #define UNICODE_ARABIC_LETTER_DAD_ISOLATED_FORM 0xfebd #define UNITEXT_ARABIC_LETTER_DAD_ISOLATED_FORM L"\ufebd" #define UNICODE_ARABIC_LETTER_DAD_FINAL_FORM 0xfebe #define UNITEXT_ARABIC_LETTER_DAD_FINAL_FORM L"\ufebe" #define UNICODE_ARABIC_LETTER_DAD_INITIAL_FORM 0xfebf #define UNITEXT_ARABIC_LETTER_DAD_INITIAL_FORM L"\ufebf" #define UNICODE_ARABIC_LETTER_DAD_MEDIAL_FORM 0xfec0 #define UNITEXT_ARABIC_LETTER_DAD_MEDIAL_FORM L"\ufec0" #define UNICODE_ARABIC_LETTER_TAH_ISOLATED_FORM 0xfec1 #define UNITEXT_ARABIC_LETTER_TAH_ISOLATED_FORM L"\ufec1" #define UNICODE_ARABIC_LETTER_TAH_FINAL_FORM 0xfec2 #define UNITEXT_ARABIC_LETTER_TAH_FINAL_FORM L"\ufec2" #define UNICODE_ARABIC_LETTER_TAH_INITIAL_FORM 0xfec3 #define UNITEXT_ARABIC_LETTER_TAH_INITIAL_FORM L"\ufec3" #define UNICODE_ARABIC_LETTER_TAH_MEDIAL_FORM 0xfec4 #define UNITEXT_ARABIC_LETTER_TAH_MEDIAL_FORM L"\ufec4" #define UNICODE_ARABIC_LETTER_ZAH_ISOLATED_FORM 0xfec5 #define UNITEXT_ARABIC_LETTER_ZAH_ISOLATED_FORM L"\ufec5" #define UNICODE_ARABIC_LETTER_ZAH_FINAL_FORM 0xfec6 #define UNITEXT_ARABIC_LETTER_ZAH_FINAL_FORM L"\ufec6" #define UNICODE_ARABIC_LETTER_ZAH_INITIAL_FORM 0xfec7 #define UNITEXT_ARABIC_LETTER_ZAH_INITIAL_FORM L"\ufec7" #define UNICODE_ARABIC_LETTER_ZAH_MEDIAL_FORM 0xfec8 #define UNITEXT_ARABIC_LETTER_ZAH_MEDIAL_FORM L"\ufec8" #define UNICODE_ARABIC_LETTER_AIN_ISOLATED_FORM 0xfec9 #define UNITEXT_ARABIC_LETTER_AIN_ISOLATED_FORM L"\ufec9" #define UNICODE_ARABIC_LETTER_AIN_FINAL_FORM 0xfeca #define UNITEXT_ARABIC_LETTER_AIN_FINAL_FORM L"\ufeca" #define UNICODE_ARABIC_LETTER_AIN_INITIAL_FORM 0xfecb #define UNITEXT_ARABIC_LETTER_AIN_INITIAL_FORM L"\ufecb" #define UNICODE_ARABIC_LETTER_AIN_MEDIAL_FORM 0xfecc #define UNITEXT_ARABIC_LETTER_AIN_MEDIAL_FORM L"\ufecc" #define UNICODE_ARABIC_LETTER_GHAIN_ISOLATED_FORM 0xfecd #define UNITEXT_ARABIC_LETTER_GHAIN_ISOLATED_FORM L"\ufecd" #define UNICODE_ARABIC_LETTER_GHAIN_FINAL_FORM 0xfece #define UNITEXT_ARABIC_LETTER_GHAIN_FINAL_FORM L"\ufece" #define UNICODE_ARABIC_LETTER_GHAIN_INITIAL_FORM 0xfecf #define UNITEXT_ARABIC_LETTER_GHAIN_INITIAL_FORM L"\ufecf" #define UNICODE_ARABIC_LETTER_GHAIN_MEDIAL_FORM 0xfed0 #define UNITEXT_ARABIC_LETTER_GHAIN_MEDIAL_FORM L"\ufed0" #define UNICODE_ARABIC_LETTER_FEH_ISOLATED_FORM 0xfed1 #define UNITEXT_ARABIC_LETTER_FEH_ISOLATED_FORM L"\ufed1" #define UNICODE_ARABIC_LETTER_FEH_FINAL_FORM 0xfed2 #define UNITEXT_ARABIC_LETTER_FEH_FINAL_FORM L"\ufed2" #define UNICODE_ARABIC_LETTER_FEH_INITIAL_FORM 0xfed3 #define UNITEXT_ARABIC_LETTER_FEH_INITIAL_FORM L"\ufed3" #define UNICODE_ARABIC_LETTER_FEH_MEDIAL_FORM 0xfed4 #define UNITEXT_ARABIC_LETTER_FEH_MEDIAL_FORM L"\ufed4" #define UNICODE_ARABIC_LETTER_QAF_ISOLATED_FORM 0xfed5 #define UNITEXT_ARABIC_LETTER_QAF_ISOLATED_FORM L"\ufed5" #define UNICODE_ARABIC_LETTER_QAF_FINAL_FORM 0xfed6 #define UNITEXT_ARABIC_LETTER_QAF_FINAL_FORM L"\ufed6" #define UNICODE_ARABIC_LETTER_QAF_INITIAL_FORM 0xfed7 #define UNITEXT_ARABIC_LETTER_QAF_INITIAL_FORM L"\ufed7" #define UNICODE_ARABIC_LETTER_QAF_MEDIAL_FORM 0xfed8 #define UNITEXT_ARABIC_LETTER_QAF_MEDIAL_FORM L"\ufed8" #define UNICODE_ARABIC_LETTER_KAF_ISOLATED_FORM 0xfed9 #define UNITEXT_ARABIC_LETTER_KAF_ISOLATED_FORM L"\ufed9" #define UNICODE_ARABIC_LETTER_KAF_FINAL_FORM 0xfeda #define UNITEXT_ARABIC_LETTER_KAF_FINAL_FORM L"\ufeda" #define UNICODE_ARABIC_LETTER_KAF_INITIAL_FORM 0xfedb #define UNITEXT_ARABIC_LETTER_KAF_INITIAL_FORM L"\ufedb" #define UNICODE_ARABIC_LETTER_KAF_MEDIAL_FORM 0xfedc #define UNITEXT_ARABIC_LETTER_KAF_MEDIAL_FORM L"\ufedc" #define UNICODE_ARABIC_LETTER_LAM_ISOLATED_FORM 0xfedd #define UNITEXT_ARABIC_LETTER_LAM_ISOLATED_FORM L"\ufedd" #define UNICODE_ARABIC_LETTER_LAM_FINAL_FORM 0xfede #define UNITEXT_ARABIC_LETTER_LAM_FINAL_FORM L"\ufede" #define UNICODE_ARABIC_LETTER_LAM_INITIAL_FORM 0xfedf #define UNITEXT_ARABIC_LETTER_LAM_INITIAL_FORM L"\ufedf" #define UNICODE_ARABIC_LETTER_LAM_MEDIAL_FORM 0xfee0 #define UNITEXT_ARABIC_LETTER_LAM_MEDIAL_FORM L"\ufee0" #define UNICODE_ARABIC_LETTER_MEEM_ISOLATED_FORM 0xfee1 #define UNITEXT_ARABIC_LETTER_MEEM_ISOLATED_FORM L"\ufee1" #define UNICODE_ARABIC_LETTER_MEEM_FINAL_FORM 0xfee2 #define UNITEXT_ARABIC_LETTER_MEEM_FINAL_FORM L"\ufee2" #define UNICODE_ARABIC_LETTER_MEEM_INITIAL_FORM 0xfee3 #define UNITEXT_ARABIC_LETTER_MEEM_INITIAL_FORM L"\ufee3" #define UNICODE_ARABIC_LETTER_MEEM_MEDIAL_FORM 0xfee4 #define UNITEXT_ARABIC_LETTER_MEEM_MEDIAL_FORM L"\ufee4" #define UNICODE_ARABIC_LETTER_NOON_ISOLATED_FORM 0xfee5 #define UNITEXT_ARABIC_LETTER_NOON_ISOLATED_FORM L"\ufee5" #define UNICODE_ARABIC_LETTER_NOON_FINAL_FORM 0xfee6 #define UNITEXT_ARABIC_LETTER_NOON_FINAL_FORM L"\ufee6" #define UNICODE_ARABIC_LETTER_NOON_INITIAL_FORM 0xfee7 #define UNITEXT_ARABIC_LETTER_NOON_INITIAL_FORM L"\ufee7" #define UNICODE_ARABIC_LETTER_NOON_MEDIAL_FORM 0xfee8 #define UNITEXT_ARABIC_LETTER_NOON_MEDIAL_FORM L"\ufee8" #define UNICODE_ARABIC_LETTER_HEH_ISOLATED_FORM 0xfee9 #define UNITEXT_ARABIC_LETTER_HEH_ISOLATED_FORM L"\ufee9" #define UNICODE_ARABIC_LETTER_HEH_FINAL_FORM 0xfeea #define UNITEXT_ARABIC_LETTER_HEH_FINAL_FORM L"\ufeea" #define UNICODE_ARABIC_LETTER_HEH_INITIAL_FORM 0xfeeb #define UNITEXT_ARABIC_LETTER_HEH_INITIAL_FORM L"\ufeeb" #define UNICODE_ARABIC_LETTER_HEH_MEDIAL_FORM 0xfeec #define UNITEXT_ARABIC_LETTER_HEH_MEDIAL_FORM L"\ufeec" #define UNICODE_ARABIC_LETTER_WAW_ISOLATED_FORM 0xfeed #define UNITEXT_ARABIC_LETTER_WAW_ISOLATED_FORM L"\ufeed" #define UNICODE_ARABIC_LETTER_WAW_FINAL_FORM 0xfeee #define UNITEXT_ARABIC_LETTER_WAW_FINAL_FORM L"\ufeee" #define UNICODE_ARABIC_LETTER_ALEF_MAKSURA_ISOLATED_FORM 0xfeef #define UNITEXT_ARABIC_LETTER_ALEF_MAKSURA_ISOLATED_FORM L"\ufeef" #define UNICODE_ARABIC_LETTER_ALEF_MAKSURA_FINAL_FORM 0xfef0 #define UNITEXT_ARABIC_LETTER_ALEF_MAKSURA_FINAL_FORM L"\ufef0" #define UNICODE_ARABIC_LETTER_YEH_ISOLATED_FORM 0xfef1 #define UNITEXT_ARABIC_LETTER_YEH_ISOLATED_FORM L"\ufef1" #define UNICODE_ARABIC_LETTER_YEH_FINAL_FORM 0xfef2 #define UNITEXT_ARABIC_LETTER_YEH_FINAL_FORM L"\ufef2" #define UNICODE_ARABIC_LETTER_YEH_INITIAL_FORM 0xfef3 #define UNITEXT_ARABIC_LETTER_YEH_INITIAL_FORM L"\ufef3" #define UNICODE_ARABIC_LETTER_YEH_MEDIAL_FORM 0xfef4 #define UNITEXT_ARABIC_LETTER_YEH_MEDIAL_FORM L"\ufef4" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_MADDA_ABOVE_ISOLATED_FORM 0xfef5 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_MADDA_ABOVE_ISOLATED_FORM L"\ufef5" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_MADDA_ABOVE_FINAL_FORM 0xfef6 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_MADDA_ABOVE_FINAL_FORM L"\ufef6" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_HAMZA_ABOVE_ISOLATED_FORM 0xfef7 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_HAMZA_ABOVE_ISOLATED_FORM L"\ufef7" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_HAMZA_ABOVE_FINAL_FORM 0xfef8 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_HAMZA_ABOVE_FINAL_FORM L"\ufef8" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_HAMZA_BELOW_ISOLATED_FORM 0xfef9 #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_HAMZA_BELOW_ISOLATED_FORM L"\ufef9" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_HAMZA_BELOW_FINAL_FORM 0xfefa #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_WITH_HAMZA_BELOW_FINAL_FORM L"\ufefa" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_ISOLATED_FORM 0xfefb #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_ISOLATED_FORM L"\ufefb" #define UNICODE_ARABIC_LIGATURE_LAM_WITH_ALEF_FINAL_FORM 0xfefc #define UNITEXT_ARABIC_LIGATURE_LAM_WITH_ALEF_FINAL_FORM L"\ufefc" #define UNICODE_ZERO_WIDTH_NO_BREAK_SPACE 0xfeff #define UNITEXT_ZERO_WIDTH_NO_BREAK_SPACE L"\ufeff" #define UNICODE_FULLWIDTH_EXCLAMATION_MARK 0xff01 #define UNITEXT_FULLWIDTH_EXCLAMATION_MARK L"\uff01" #define UNICODE_FULLWIDTH_QUOTATION_MARK 0xff02 #define UNITEXT_FULLWIDTH_QUOTATION_MARK L"\uff02" #define UNICODE_FULLWIDTH_NUMBER_SIGN 0xff03 #define UNITEXT_FULLWIDTH_NUMBER_SIGN L"\uff03" #define UNICODE_FULLWIDTH_DOLLAR_SIGN 0xff04 #define UNITEXT_FULLWIDTH_DOLLAR_SIGN L"\uff04" #define UNICODE_FULLWIDTH_PERCENT_SIGN 0xff05 #define UNITEXT_FULLWIDTH_PERCENT_SIGN L"\uff05" #define UNICODE_FULLWIDTH_AMPERSAND 0xff06 #define UNITEXT_FULLWIDTH_AMPERSAND L"\uff06" #define UNICODE_FULLWIDTH_APOSTROPHE 0xff07 #define UNITEXT_FULLWIDTH_APOSTROPHE L"\uff07" #define UNICODE_FULLWIDTH_LEFT_PARENTHESIS 0xff08 #define UNITEXT_FULLWIDTH_LEFT_PARENTHESIS L"\uff08" #define UNICODE_FULLWIDTH_RIGHT_PARENTHESIS 0xff09 #define UNITEXT_FULLWIDTH_RIGHT_PARENTHESIS L"\uff09" #define UNICODE_FULLWIDTH_ASTERISK 0xff0a #define UNITEXT_FULLWIDTH_ASTERISK L"\uff0a" #define UNICODE_FULLWIDTH_PLUS_SIGN 0xff0b #define UNITEXT_FULLWIDTH_PLUS_SIGN L"\uff0b" #define UNICODE_FULLWIDTH_COMMA 0xff0c #define UNITEXT_FULLWIDTH_COMMA L"\uff0c" #define UNICODE_FULLWIDTH_HYPHEN_MINUS 0xff0d #define UNITEXT_FULLWIDTH_HYPHEN_MINUS L"\uff0d" #define UNICODE_FULLWIDTH_FULL_STOP 0xff0e #define UNITEXT_FULLWIDTH_FULL_STOP L"\uff0e" #define UNICODE_FULLWIDTH_SOLIDUS 0xff0f #define UNITEXT_FULLWIDTH_SOLIDUS L"\uff0f" #define UNICODE_FULLWIDTH_DIGIT_ZERO 0xff10 #define UNITEXT_FULLWIDTH_DIGIT_ZERO L"\uff10" #define UNICODE_FULLWIDTH_DIGIT_ONE 0xff11 #define UNITEXT_FULLWIDTH_DIGIT_ONE L"\uff11" #define UNICODE_FULLWIDTH_DIGIT_TWO 0xff12 #define UNITEXT_FULLWIDTH_DIGIT_TWO L"\uff12" #define UNICODE_FULLWIDTH_DIGIT_THREE 0xff13 #define UNITEXT_FULLWIDTH_DIGIT_THREE L"\uff13" #define UNICODE_FULLWIDTH_DIGIT_FOUR 0xff14 #define UNITEXT_FULLWIDTH_DIGIT_FOUR L"\uff14" #define UNICODE_FULLWIDTH_DIGIT_FIVE 0xff15 #define UNITEXT_FULLWIDTH_DIGIT_FIVE L"\uff15" #define UNICODE_FULLWIDTH_DIGIT_SIX 0xff16 #define UNITEXT_FULLWIDTH_DIGIT_SIX L"\uff16" #define UNICODE_FULLWIDTH_DIGIT_SEVEN 0xff17 #define UNITEXT_FULLWIDTH_DIGIT_SEVEN L"\uff17" #define UNICODE_FULLWIDTH_DIGIT_EIGHT 0xff18 #define UNITEXT_FULLWIDTH_DIGIT_EIGHT L"\uff18" #define UNICODE_FULLWIDTH_DIGIT_NINE 0xff19 #define UNITEXT_FULLWIDTH_DIGIT_NINE L"\uff19" #define UNICODE_FULLWIDTH_COLON 0xff1a #define UNITEXT_FULLWIDTH_COLON L"\uff1a" #define UNICODE_FULLWIDTH_SEMICOLON 0xff1b #define UNITEXT_FULLWIDTH_SEMICOLON L"\uff1b" #define UNICODE_FULLWIDTH_LESS_THAN_SIGN 0xff1c #define UNITEXT_FULLWIDTH_LESS_THAN_SIGN L"\uff1c" #define UNICODE_FULLWIDTH_EQUALS_SIGN 0xff1d #define UNITEXT_FULLWIDTH_EQUALS_SIGN L"\uff1d" #define UNICODE_FULLWIDTH_GREATER_THAN_SIGN 0xff1e #define UNITEXT_FULLWIDTH_GREATER_THAN_SIGN L"\uff1e" #define UNICODE_FULLWIDTH_QUESTION_MARK 0xff1f #define UNITEXT_FULLWIDTH_QUESTION_MARK L"\uff1f" #define UNICODE_FULLWIDTH_COMMERCIAL_AT 0xff20 #define UNITEXT_FULLWIDTH_COMMERCIAL_AT L"\uff20" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_A 0xff21 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_A L"\uff21" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_B 0xff22 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_B L"\uff22" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_C 0xff23 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_C L"\uff23" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_D 0xff24 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_D L"\uff24" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_E 0xff25 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_E L"\uff25" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_F 0xff26 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_F L"\uff26" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_G 0xff27 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_G L"\uff27" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_H 0xff28 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_H L"\uff28" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_I 0xff29 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_I L"\uff29" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_J 0xff2a #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_J L"\uff2a" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_K 0xff2b #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_K L"\uff2b" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_L 0xff2c #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_L L"\uff2c" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_M 0xff2d #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_M L"\uff2d" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_N 0xff2e #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_N L"\uff2e" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_O 0xff2f #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_O L"\uff2f" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_P 0xff30 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_P L"\uff30" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_Q 0xff31 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_Q L"\uff31" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_R 0xff32 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_R L"\uff32" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_S 0xff33 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_S L"\uff33" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_T 0xff34 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_T L"\uff34" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_U 0xff35 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_U L"\uff35" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_V 0xff36 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_V L"\uff36" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_W 0xff37 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_W L"\uff37" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_X 0xff38 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_X L"\uff38" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_Y 0xff39 #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_Y L"\uff39" #define UNICODE_FULLWIDTH_LATIN_CAPITAL_LETTER_Z 0xff3a #define UNITEXT_FULLWIDTH_LATIN_CAPITAL_LETTER_Z L"\uff3a" #define UNICODE_FULLWIDTH_LEFT_SQUARE_BRACKET 0xff3b #define UNITEXT_FULLWIDTH_LEFT_SQUARE_BRACKET L"\uff3b" #define UNICODE_FULLWIDTH_REVERSE_SOLIDUS 0xff3c #define UNITEXT_FULLWIDTH_REVERSE_SOLIDUS L"\uff3c" #define UNICODE_FULLWIDTH_RIGHT_SQUARE_BRACKET 0xff3d #define UNITEXT_FULLWIDTH_RIGHT_SQUARE_BRACKET L"\uff3d" #define UNICODE_FULLWIDTH_CIRCUMFLEX_ACCENT 0xff3e #define UNITEXT_FULLWIDTH_CIRCUMFLEX_ACCENT L"\uff3e" #define UNICODE_FULLWIDTH_LOW_LINE 0xff3f #define UNITEXT_FULLWIDTH_LOW_LINE L"\uff3f" #define UNICODE_FULLWIDTH_GRAVE_ACCENT 0xff40 #define UNITEXT_FULLWIDTH_GRAVE_ACCENT L"\uff40" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_A 0xff41 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_A L"\uff41" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_B 0xff42 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_B L"\uff42" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_C 0xff43 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_C L"\uff43" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_D 0xff44 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_D L"\uff44" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_E 0xff45 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_E L"\uff45" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_F 0xff46 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_F L"\uff46" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_G 0xff47 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_G L"\uff47" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_H 0xff48 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_H L"\uff48" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_I 0xff49 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_I L"\uff49" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_J 0xff4a #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_J L"\uff4a" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_K 0xff4b #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_K L"\uff4b" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_L 0xff4c #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_L L"\uff4c" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_M 0xff4d #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_M L"\uff4d" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_N 0xff4e #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_N L"\uff4e" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_O 0xff4f #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_O L"\uff4f" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_P 0xff50 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_P L"\uff50" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_Q 0xff51 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_Q L"\uff51" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_R 0xff52 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_R L"\uff52" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_S 0xff53 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_S L"\uff53" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_T 0xff54 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_T L"\uff54" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_U 0xff55 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_U L"\uff55" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_V 0xff56 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_V L"\uff56" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_W 0xff57 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_W L"\uff57" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_X 0xff58 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_X L"\uff58" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_Y 0xff59 #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_Y L"\uff59" #define UNICODE_FULLWIDTH_LATIN_SMALL_LETTER_Z 0xff5a #define UNITEXT_FULLWIDTH_LATIN_SMALL_LETTER_Z L"\uff5a" #define UNICODE_FULLWIDTH_LEFT_CURLY_BRACKET 0xff5b #define UNITEXT_FULLWIDTH_LEFT_CURLY_BRACKET L"\uff5b" #define UNICODE_FULLWIDTH_VERTICAL_LINE 0xff5c #define UNITEXT_FULLWIDTH_VERTICAL_LINE L"\uff5c" #define UNICODE_FULLWIDTH_RIGHT_CURLY_BRACKET 0xff5d #define UNITEXT_FULLWIDTH_RIGHT_CURLY_BRACKET L"\uff5d" #define UNICODE_FULLWIDTH_TILDE 0xff5e #define UNITEXT_FULLWIDTH_TILDE L"\uff5e" #define UNICODE_FULLWIDTH_LEFT_WHITE_PARENTHESIS 0xff5f #define UNITEXT_FULLWIDTH_LEFT_WHITE_PARENTHESIS L"\uff5f" #define UNICODE_FULLWIDTH_RIGHT_WHITE_PARENTHESIS 0xff60 #define UNITEXT_FULLWIDTH_RIGHT_WHITE_PARENTHESIS L"\uff60" #define UNICODE_HALFWIDTH_IDEOGRAPHIC_FULL_STOP 0xff61 #define UNITEXT_HALFWIDTH_IDEOGRAPHIC_FULL_STOP L"\uff61" #define UNICODE_HALFWIDTH_LEFT_CORNER_BRACKET 0xff62 #define UNITEXT_HALFWIDTH_LEFT_CORNER_BRACKET L"\uff62" #define UNICODE_HALFWIDTH_RIGHT_CORNER_BRACKET 0xff63 #define UNITEXT_HALFWIDTH_RIGHT_CORNER_BRACKET L"\uff63" #define UNICODE_HALFWIDTH_IDEOGRAPHIC_COMMA 0xff64 #define UNITEXT_HALFWIDTH_IDEOGRAPHIC_COMMA L"\uff64" #define UNICODE_HALFWIDTH_KATAKANA_MIDDLE_DOT 0xff65 #define UNITEXT_HALFWIDTH_KATAKANA_MIDDLE_DOT L"\uff65" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_WO 0xff66 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_WO L"\uff66" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SMALL_A 0xff67 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SMALL_A L"\uff67" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SMALL_I 0xff68 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SMALL_I L"\uff68" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SMALL_U 0xff69 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SMALL_U L"\uff69" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SMALL_E 0xff6a #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SMALL_E L"\uff6a" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SMALL_O 0xff6b #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SMALL_O L"\uff6b" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SMALL_YA 0xff6c #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SMALL_YA L"\uff6c" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SMALL_YU 0xff6d #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SMALL_YU L"\uff6d" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SMALL_YO 0xff6e #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SMALL_YO L"\uff6e" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SMALL_TU 0xff6f #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SMALL_TU L"\uff6f" #define UNICODE_HALFWIDTH_KATAKANA_HIRAGANA_PROLONGED_SOUND_MARK 0xff70 #define UNITEXT_HALFWIDTH_KATAKANA_HIRAGANA_PROLONGED_SOUND_MARK L"\uff70" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_A 0xff71 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_A L"\uff71" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_I 0xff72 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_I L"\uff72" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_U 0xff73 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_U L"\uff73" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_E 0xff74 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_E L"\uff74" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_O 0xff75 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_O L"\uff75" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_KA 0xff76 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_KA L"\uff76" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_KI 0xff77 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_KI L"\uff77" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_KU 0xff78 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_KU L"\uff78" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_KE 0xff79 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_KE L"\uff79" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_KO 0xff7a #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_KO L"\uff7a" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SA 0xff7b #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SA L"\uff7b" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SI 0xff7c #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SI L"\uff7c" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SU 0xff7d #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SU L"\uff7d" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SE 0xff7e #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SE L"\uff7e" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_SO 0xff7f #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_SO L"\uff7f" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_TA 0xff80 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_TA L"\uff80" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_TI 0xff81 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_TI L"\uff81" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_TU 0xff82 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_TU L"\uff82" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_TE 0xff83 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_TE L"\uff83" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_TO 0xff84 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_TO L"\uff84" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_NA 0xff85 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_NA L"\uff85" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_NI 0xff86 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_NI L"\uff86" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_NU 0xff87 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_NU L"\uff87" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_NE 0xff88 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_NE L"\uff88" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_NO 0xff89 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_NO L"\uff89" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_HA 0xff8a #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_HA L"\uff8a" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_HI 0xff8b #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_HI L"\uff8b" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_HU 0xff8c #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_HU L"\uff8c" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_HE 0xff8d #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_HE L"\uff8d" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_HO 0xff8e #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_HO L"\uff8e" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_MA 0xff8f #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_MA L"\uff8f" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_MI 0xff90 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_MI L"\uff90" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_MU 0xff91 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_MU L"\uff91" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_ME 0xff92 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_ME L"\uff92" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_MO 0xff93 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_MO L"\uff93" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_YA 0xff94 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_YA L"\uff94" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_YU 0xff95 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_YU L"\uff95" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_YO 0xff96 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_YO L"\uff96" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_RA 0xff97 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_RA L"\uff97" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_RI 0xff98 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_RI L"\uff98" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_RU 0xff99 #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_RU L"\uff99" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_RE 0xff9a #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_RE L"\uff9a" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_RO 0xff9b #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_RO L"\uff9b" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_WA 0xff9c #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_WA L"\uff9c" #define UNICODE_HALFWIDTH_KATAKANA_LETTER_N 0xff9d #define UNITEXT_HALFWIDTH_KATAKANA_LETTER_N L"\uff9d" #define UNICODE_HALFWIDTH_KATAKANA_VOICED_SOUND_MARK 0xff9e #define UNITEXT_HALFWIDTH_KATAKANA_VOICED_SOUND_MARK L"\uff9e" #define UNICODE_HALFWIDTH_KATAKANA_SEMI_VOICED_SOUND_MARK 0xff9f #define UNITEXT_HALFWIDTH_KATAKANA_SEMI_VOICED_SOUND_MARK L"\uff9f" #define UNICODE_HALFWIDTH_HANGUL_FILLER 0xffa0 #define UNITEXT_HALFWIDTH_HANGUL_FILLER L"\uffa0" #define UNICODE_HALFWIDTH_HANGUL_LETTER_KIYEOK 0xffa1 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_KIYEOK L"\uffa1" #define UNICODE_HALFWIDTH_HANGUL_LETTER_SSANGKIYEOK 0xffa2 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_SSANGKIYEOK L"\uffa2" #define UNICODE_HALFWIDTH_HANGUL_LETTER_KIYEOK_SIOS 0xffa3 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_KIYEOK_SIOS L"\uffa3" #define UNICODE_HALFWIDTH_HANGUL_LETTER_NIEUN 0xffa4 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_NIEUN L"\uffa4" #define UNICODE_HALFWIDTH_HANGUL_LETTER_NIEUN_CIEUC 0xffa5 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_NIEUN_CIEUC L"\uffa5" #define UNICODE_HALFWIDTH_HANGUL_LETTER_NIEUN_HIEUH 0xffa6 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_NIEUN_HIEUH L"\uffa6" #define UNICODE_HALFWIDTH_HANGUL_LETTER_TIKEUT 0xffa7 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_TIKEUT L"\uffa7" #define UNICODE_HALFWIDTH_HANGUL_LETTER_SSANGTIKEUT 0xffa8 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_SSANGTIKEUT L"\uffa8" #define UNICODE_HALFWIDTH_HANGUL_LETTER_RIEUL 0xffa9 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_RIEUL L"\uffa9" #define UNICODE_HALFWIDTH_HANGUL_LETTER_RIEUL_KIYEOK 0xffaa #define UNITEXT_HALFWIDTH_HANGUL_LETTER_RIEUL_KIYEOK L"\uffaa" #define UNICODE_HALFWIDTH_HANGUL_LETTER_RIEUL_MIEUM 0xffab #define UNITEXT_HALFWIDTH_HANGUL_LETTER_RIEUL_MIEUM L"\uffab" #define UNICODE_HALFWIDTH_HANGUL_LETTER_RIEUL_PIEUP 0xffac #define UNITEXT_HALFWIDTH_HANGUL_LETTER_RIEUL_PIEUP L"\uffac" #define UNICODE_HALFWIDTH_HANGUL_LETTER_RIEUL_SIOS 0xffad #define UNITEXT_HALFWIDTH_HANGUL_LETTER_RIEUL_SIOS L"\uffad" #define UNICODE_HALFWIDTH_HANGUL_LETTER_RIEUL_THIEUTH 0xffae #define UNITEXT_HALFWIDTH_HANGUL_LETTER_RIEUL_THIEUTH L"\uffae" #define UNICODE_HALFWIDTH_HANGUL_LETTER_RIEUL_PHIEUPH 0xffaf #define UNITEXT_HALFWIDTH_HANGUL_LETTER_RIEUL_PHIEUPH L"\uffaf" #define UNICODE_HALFWIDTH_HANGUL_LETTER_RIEUL_HIEUH 0xffb0 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_RIEUL_HIEUH L"\uffb0" #define UNICODE_HALFWIDTH_HANGUL_LETTER_MIEUM 0xffb1 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_MIEUM L"\uffb1" #define UNICODE_HALFWIDTH_HANGUL_LETTER_PIEUP 0xffb2 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_PIEUP L"\uffb2" #define UNICODE_HALFWIDTH_HANGUL_LETTER_SSANGPIEUP 0xffb3 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_SSANGPIEUP L"\uffb3" #define UNICODE_HALFWIDTH_HANGUL_LETTER_PIEUP_SIOS 0xffb4 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_PIEUP_SIOS L"\uffb4" #define UNICODE_HALFWIDTH_HANGUL_LETTER_SIOS 0xffb5 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_SIOS L"\uffb5" #define UNICODE_HALFWIDTH_HANGUL_LETTER_SSANGSIOS 0xffb6 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_SSANGSIOS L"\uffb6" #define UNICODE_HALFWIDTH_HANGUL_LETTER_IEUNG 0xffb7 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_IEUNG L"\uffb7" #define UNICODE_HALFWIDTH_HANGUL_LETTER_CIEUC 0xffb8 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_CIEUC L"\uffb8" #define UNICODE_HALFWIDTH_HANGUL_LETTER_SSANGCIEUC 0xffb9 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_SSANGCIEUC L"\uffb9" #define UNICODE_HALFWIDTH_HANGUL_LETTER_CHIEUCH 0xffba #define UNITEXT_HALFWIDTH_HANGUL_LETTER_CHIEUCH L"\uffba" #define UNICODE_HALFWIDTH_HANGUL_LETTER_KHIEUKH 0xffbb #define UNITEXT_HALFWIDTH_HANGUL_LETTER_KHIEUKH L"\uffbb" #define UNICODE_HALFWIDTH_HANGUL_LETTER_THIEUTH 0xffbc #define UNITEXT_HALFWIDTH_HANGUL_LETTER_THIEUTH L"\uffbc" #define UNICODE_HALFWIDTH_HANGUL_LETTER_PHIEUPH 0xffbd #define UNITEXT_HALFWIDTH_HANGUL_LETTER_PHIEUPH L"\uffbd" #define UNICODE_HALFWIDTH_HANGUL_LETTER_HIEUH 0xffbe #define UNITEXT_HALFWIDTH_HANGUL_LETTER_HIEUH L"\uffbe" #define UNICODE_HALFWIDTH_HANGUL_LETTER_A 0xffc2 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_A L"\uffc2" #define UNICODE_HALFWIDTH_HANGUL_LETTER_AE 0xffc3 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_AE L"\uffc3" #define UNICODE_HALFWIDTH_HANGUL_LETTER_YA 0xffc4 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_YA L"\uffc4" #define UNICODE_HALFWIDTH_HANGUL_LETTER_YAE 0xffc5 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_YAE L"\uffc5" #define UNICODE_HALFWIDTH_HANGUL_LETTER_EO 0xffc6 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_EO L"\uffc6" #define UNICODE_HALFWIDTH_HANGUL_LETTER_E 0xffc7 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_E L"\uffc7" #define UNICODE_HALFWIDTH_HANGUL_LETTER_YEO 0xffca #define UNITEXT_HALFWIDTH_HANGUL_LETTER_YEO L"\uffca" #define UNICODE_HALFWIDTH_HANGUL_LETTER_YE 0xffcb #define UNITEXT_HALFWIDTH_HANGUL_LETTER_YE L"\uffcb" #define UNICODE_HALFWIDTH_HANGUL_LETTER_O 0xffcc #define UNITEXT_HALFWIDTH_HANGUL_LETTER_O L"\uffcc" #define UNICODE_HALFWIDTH_HANGUL_LETTER_WA 0xffcd #define UNITEXT_HALFWIDTH_HANGUL_LETTER_WA L"\uffcd" #define UNICODE_HALFWIDTH_HANGUL_LETTER_WAE 0xffce #define UNITEXT_HALFWIDTH_HANGUL_LETTER_WAE L"\uffce" #define UNICODE_HALFWIDTH_HANGUL_LETTER_OE 0xffcf #define UNITEXT_HALFWIDTH_HANGUL_LETTER_OE L"\uffcf" #define UNICODE_HALFWIDTH_HANGUL_LETTER_YO 0xffd2 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_YO L"\uffd2" #define UNICODE_HALFWIDTH_HANGUL_LETTER_U 0xffd3 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_U L"\uffd3" #define UNICODE_HALFWIDTH_HANGUL_LETTER_WEO 0xffd4 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_WEO L"\uffd4" #define UNICODE_HALFWIDTH_HANGUL_LETTER_WE 0xffd5 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_WE L"\uffd5" #define UNICODE_HALFWIDTH_HANGUL_LETTER_WI 0xffd6 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_WI L"\uffd6" #define UNICODE_HALFWIDTH_HANGUL_LETTER_YU 0xffd7 #define UNITEXT_HALFWIDTH_HANGUL_LETTER_YU L"\uffd7" #define UNICODE_HALFWIDTH_HANGUL_LETTER_EU 0xffda #define UNITEXT_HALFWIDTH_HANGUL_LETTER_EU L"\uffda" #define UNICODE_HALFWIDTH_HANGUL_LETTER_YI 0xffdb #define UNITEXT_HALFWIDTH_HANGUL_LETTER_YI L"\uffdb" #define UNICODE_HALFWIDTH_HANGUL_LETTER_I 0xffdc #define UNITEXT_HALFWIDTH_HANGUL_LETTER_I L"\uffdc" #define UNICODE_FULLWIDTH_CENT_SIGN 0xffe0 #define UNITEXT_FULLWIDTH_CENT_SIGN L"\uffe0" #define UNICODE_FULLWIDTH_POUND_SIGN 0xffe1 #define UNITEXT_FULLWIDTH_POUND_SIGN L"\uffe1" #define UNICODE_FULLWIDTH_NOT_SIGN 0xffe2 #define UNITEXT_FULLWIDTH_NOT_SIGN L"\uffe2" #define UNICODE_FULLWIDTH_MACRON 0xffe3 #define UNITEXT_FULLWIDTH_MACRON L"\uffe3" #define UNICODE_FULLWIDTH_BROKEN_BAR 0xffe4 #define UNITEXT_FULLWIDTH_BROKEN_BAR L"\uffe4" #define UNICODE_FULLWIDTH_YEN_SIGN 0xffe5 #define UNITEXT_FULLWIDTH_YEN_SIGN L"\uffe5" #define UNICODE_FULLWIDTH_WON_SIGN 0xffe6 #define UNITEXT_FULLWIDTH_WON_SIGN L"\uffe6" #define UNICODE_HALFWIDTH_FORMS_LIGHT_VERTICAL 0xffe8 #define UNITEXT_HALFWIDTH_FORMS_LIGHT_VERTICAL L"\uffe8" #define UNICODE_HALFWIDTH_LEFTWARDS_ARROW 0xffe9 #define UNITEXT_HALFWIDTH_LEFTWARDS_ARROW L"\uffe9" #define UNICODE_HALFWIDTH_UPWARDS_ARROW 0xffea #define UNITEXT_HALFWIDTH_UPWARDS_ARROW L"\uffea" #define UNICODE_HALFWIDTH_RIGHTWARDS_ARROW 0xffeb #define UNITEXT_HALFWIDTH_RIGHTWARDS_ARROW L"\uffeb" #define UNICODE_HALFWIDTH_DOWNWARDS_ARROW 0xffec #define UNITEXT_HALFWIDTH_DOWNWARDS_ARROW L"\uffec" #define UNICODE_HALFWIDTH_BLACK_SQUARE 0xffed #define UNITEXT_HALFWIDTH_BLACK_SQUARE L"\uffed" #define UNICODE_HALFWIDTH_WHITE_CIRCLE 0xffee #define UNITEXT_HALFWIDTH_WHITE_CIRCLE L"\uffee" #define UNICODE_INTERLINEAR_ANNOTATION_ANCHOR 0xfff9 #define UNITEXT_INTERLINEAR_ANNOTATION_ANCHOR L"\ufff9" #define UNICODE_INTERLINEAR_ANNOTATION_SEPARATOR 0xfffa #define UNITEXT_INTERLINEAR_ANNOTATION_SEPARATOR L"\ufffa" #define UNICODE_INTERLINEAR_ANNOTATION_TERMINATOR 0xfffb #define UNITEXT_INTERLINEAR_ANNOTATION_TERMINATOR L"\ufffb" #define UNICODE_OBJECT_REPLACEMENT_CHARACTER 0xfffc #define UNITEXT_OBJECT_REPLACEMENT_CHARACTER L"\ufffc" #define UNICODE_REPLACEMENT_CHARACTER 0xfffd #define UNITEXT_REPLACEMENT_CHARACTER L"\ufffd" #define UNICODE_LINEAR_B_SYLLABLE_B008_A 0x10000 #define UNICODE_LINEAR_B_SYLLABLE_B038_E 0x10001 #define UNICODE_LINEAR_B_SYLLABLE_B028_I 0x10002 #define UNICODE_LINEAR_B_SYLLABLE_B061_O 0x10003 #define UNICODE_LINEAR_B_SYLLABLE_B010_U 0x10004 #define UNICODE_LINEAR_B_SYLLABLE_B001_DA 0x10005 #define UNICODE_LINEAR_B_SYLLABLE_B045_DE 0x10006 #define UNICODE_LINEAR_B_SYLLABLE_B007_DI 0x10007 #define UNICODE_LINEAR_B_SYLLABLE_B014_DO 0x10008 #define UNICODE_LINEAR_B_SYLLABLE_B051_DU 0x10009 #define UNICODE_LINEAR_B_SYLLABLE_B057_JA 0x1000a #define UNICODE_LINEAR_B_SYLLABLE_B046_JE 0x1000b #define UNICODE_LINEAR_B_SYLLABLE_B036_JO 0x1000d #define UNICODE_LINEAR_B_SYLLABLE_B065_JU 0x1000e #define UNICODE_LINEAR_B_SYLLABLE_B077_KA 0x1000f #define UNICODE_LINEAR_B_SYLLABLE_B044_KE 0x10010 #define UNICODE_LINEAR_B_SYLLABLE_B067_KI 0x10011 #define UNICODE_LINEAR_B_SYLLABLE_B070_KO 0x10012 #define UNICODE_LINEAR_B_SYLLABLE_B081_KU 0x10013 #define UNICODE_LINEAR_B_SYLLABLE_B080_MA 0x10014 #define UNICODE_LINEAR_B_SYLLABLE_B013_ME 0x10015 #define UNICODE_LINEAR_B_SYLLABLE_B073_MI 0x10016 #define UNICODE_LINEAR_B_SYLLABLE_B015_MO 0x10017 #define UNICODE_LINEAR_B_SYLLABLE_B023_MU 0x10018 #define UNICODE_LINEAR_B_SYLLABLE_B006_NA 0x10019 #define UNICODE_LINEAR_B_SYLLABLE_B024_NE 0x1001a #define UNICODE_LINEAR_B_SYLLABLE_B030_NI 0x1001b #define UNICODE_LINEAR_B_SYLLABLE_B052_NO 0x1001c #define UNICODE_LINEAR_B_SYLLABLE_B055_NU 0x1001d #define UNICODE_LINEAR_B_SYLLABLE_B003_PA 0x1001e #define UNICODE_LINEAR_B_SYLLABLE_B072_PE 0x1001f #define UNICODE_LINEAR_B_SYLLABLE_B039_PI 0x10020 #define UNICODE_LINEAR_B_SYLLABLE_B011_PO 0x10021 #define UNICODE_LINEAR_B_SYLLABLE_B050_PU 0x10022 #define UNICODE_LINEAR_B_SYLLABLE_B016_QA 0x10023 #define UNICODE_LINEAR_B_SYLLABLE_B078_QE 0x10024 #define UNICODE_LINEAR_B_SYLLABLE_B021_QI 0x10025 #define UNICODE_LINEAR_B_SYLLABLE_B032_QO 0x10026 #define UNICODE_LINEAR_B_SYLLABLE_B060_RA 0x10028 #define UNICODE_LINEAR_B_SYLLABLE_B027_RE 0x10029 #define UNICODE_LINEAR_B_SYLLABLE_B053_RI 0x1002a #define UNICODE_LINEAR_B_SYLLABLE_B002_RO 0x1002b #define UNICODE_LINEAR_B_SYLLABLE_B026_RU 0x1002c #define UNICODE_LINEAR_B_SYLLABLE_B031_SA 0x1002d #define UNICODE_LINEAR_B_SYLLABLE_B009_SE 0x1002e #define UNICODE_LINEAR_B_SYLLABLE_B041_SI 0x1002f #define UNICODE_LINEAR_B_SYLLABLE_B012_SO 0x10030 #define UNICODE_LINEAR_B_SYLLABLE_B058_SU 0x10031 #define UNICODE_LINEAR_B_SYLLABLE_B059_TA 0x10032 #define UNICODE_LINEAR_B_SYLLABLE_B004_TE 0x10033 #define UNICODE_LINEAR_B_SYLLABLE_B037_TI 0x10034 #define UNICODE_LINEAR_B_SYLLABLE_B005_TO 0x10035 #define UNICODE_LINEAR_B_SYLLABLE_B069_TU 0x10036 #define UNICODE_LINEAR_B_SYLLABLE_B054_WA 0x10037 #define UNICODE_LINEAR_B_SYLLABLE_B075_WE 0x10038 #define UNICODE_LINEAR_B_SYLLABLE_B040_WI 0x10039 #define UNICODE_LINEAR_B_SYLLABLE_B042_WO 0x1003a #define UNICODE_LINEAR_B_SYLLABLE_B017_ZA 0x1003c #define UNICODE_LINEAR_B_SYLLABLE_B074_ZE 0x1003d #define UNICODE_LINEAR_B_SYLLABLE_B020_ZO 0x1003f #define UNICODE_LINEAR_B_SYLLABLE_B025_A2 0x10040 #define UNICODE_LINEAR_B_SYLLABLE_B043_A3 0x10041 #define UNICODE_LINEAR_B_SYLLABLE_B085_AU 0x10042 #define UNICODE_LINEAR_B_SYLLABLE_B071_DWE 0x10043 #define UNICODE_LINEAR_B_SYLLABLE_B090_DWO 0x10044 #define UNICODE_LINEAR_B_SYLLABLE_B048_NWA 0x10045 #define UNICODE_LINEAR_B_SYLLABLE_B029_PU2 0x10046 #define UNICODE_LINEAR_B_SYLLABLE_B062_PTE 0x10047 #define UNICODE_LINEAR_B_SYLLABLE_B076_RA2 0x10048 #define UNICODE_LINEAR_B_SYLLABLE_B033_RA3 0x10049 #define UNICODE_LINEAR_B_SYLLABLE_B068_RO2 0x1004a #define UNICODE_LINEAR_B_SYLLABLE_B066_TA2 0x1004b #define UNICODE_LINEAR_B_SYLLABLE_B087_TWE 0x1004c #define UNICODE_LINEAR_B_SYLLABLE_B091_TWO 0x1004d #define UNICODE_LINEAR_B_SYMBOL_B018 0x10050 #define UNICODE_LINEAR_B_SYMBOL_B019 0x10051 #define UNICODE_LINEAR_B_SYMBOL_B022 0x10052 #define UNICODE_LINEAR_B_SYMBOL_B034 0x10053 #define UNICODE_LINEAR_B_SYMBOL_B047 0x10054 #define UNICODE_LINEAR_B_SYMBOL_B049 0x10055 #define UNICODE_LINEAR_B_SYMBOL_B056 0x10056 #define UNICODE_LINEAR_B_SYMBOL_B063 0x10057 #define UNICODE_LINEAR_B_SYMBOL_B064 0x10058 #define UNICODE_LINEAR_B_SYMBOL_B079 0x10059 #define UNICODE_LINEAR_B_SYMBOL_B082 0x1005a #define UNICODE_LINEAR_B_SYMBOL_B083 0x1005b #define UNICODE_LINEAR_B_SYMBOL_B086 0x1005c #define UNICODE_LINEAR_B_SYMBOL_B089 0x1005d #define UNICODE_LINEAR_B_IDEOGRAM_B100_MAN 0x10080 #define UNICODE_LINEAR_B_IDEOGRAM_B102_WOMAN 0x10081 #define UNICODE_LINEAR_B_IDEOGRAM_B104_DEER 0x10082 #define UNICODE_LINEAR_B_IDEOGRAM_B105_EQUID 0x10083 #define UNICODE_LINEAR_B_IDEOGRAM_B105F_MARE 0x10084 #define UNICODE_LINEAR_B_IDEOGRAM_B105M_STALLION 0x10085 #define UNICODE_LINEAR_B_IDEOGRAM_B106F_EWE 0x10086 #define UNICODE_LINEAR_B_IDEOGRAM_B106M_RAM 0x10087 #define UNICODE_LINEAR_B_IDEOGRAM_B107F_SHE_GOAT 0x10088 #define UNICODE_LINEAR_B_IDEOGRAM_B107M_HE_GOAT 0x10089 #define UNICODE_LINEAR_B_IDEOGRAM_B108F_SOW 0x1008a #define UNICODE_LINEAR_B_IDEOGRAM_B108M_BOAR 0x1008b #define UNICODE_LINEAR_B_IDEOGRAM_B109F_COW 0x1008c #define UNICODE_LINEAR_B_IDEOGRAM_B109M_BULL 0x1008d #define UNICODE_LINEAR_B_IDEOGRAM_B120_WHEAT 0x1008e #define UNICODE_LINEAR_B_IDEOGRAM_B121_BARLEY 0x1008f #define UNICODE_LINEAR_B_IDEOGRAM_B122_OLIVE 0x10090 #define UNICODE_LINEAR_B_IDEOGRAM_B123_SPICE 0x10091 #define UNICODE_LINEAR_B_IDEOGRAM_B125_CYPERUS 0x10092 #define UNICODE_LINEAR_B_MONOGRAM_B127_KAPO 0x10093 #define UNICODE_LINEAR_B_MONOGRAM_B128_KANAKO 0x10094 #define UNICODE_LINEAR_B_IDEOGRAM_B130_OIL 0x10095 #define UNICODE_LINEAR_B_IDEOGRAM_B131_WINE 0x10096 #define UNICODE_LINEAR_B_IDEOGRAM_B132 0x10097 #define UNICODE_LINEAR_B_MONOGRAM_B133_AREPA 0x10098 #define UNICODE_LINEAR_B_MONOGRAM_B135_MERI 0x10099 #define UNICODE_LINEAR_B_IDEOGRAM_B140_BRONZE 0x1009a #define UNICODE_LINEAR_B_IDEOGRAM_B141_GOLD 0x1009b #define UNICODE_LINEAR_B_IDEOGRAM_B142 0x1009c #define UNICODE_LINEAR_B_IDEOGRAM_B145_WOOL 0x1009d #define UNICODE_LINEAR_B_IDEOGRAM_B146 0x1009e #define UNICODE_LINEAR_B_IDEOGRAM_B150 0x1009f #define UNICODE_LINEAR_B_IDEOGRAM_B151_HORN 0x100a0 #define UNICODE_LINEAR_B_IDEOGRAM_B152 0x100a1 #define UNICODE_LINEAR_B_IDEOGRAM_B153 0x100a2 #define UNICODE_LINEAR_B_IDEOGRAM_B154 0x100a3 #define UNICODE_LINEAR_B_MONOGRAM_B156_TURO2 0x100a4 #define UNICODE_LINEAR_B_IDEOGRAM_B157 0x100a5 #define UNICODE_LINEAR_B_IDEOGRAM_B158 0x100a6 #define UNICODE_LINEAR_B_IDEOGRAM_B159_CLOTH 0x100a7 #define UNICODE_LINEAR_B_IDEOGRAM_B160 0x100a8 #define UNICODE_LINEAR_B_IDEOGRAM_B161 0x100a9 #define UNICODE_LINEAR_B_IDEOGRAM_B162_GARMENT 0x100aa #define UNICODE_LINEAR_B_IDEOGRAM_B163_ARMOUR 0x100ab #define UNICODE_LINEAR_B_IDEOGRAM_B164 0x100ac #define UNICODE_LINEAR_B_IDEOGRAM_B165 0x100ad #define UNICODE_LINEAR_B_IDEOGRAM_B166 0x100ae #define UNICODE_LINEAR_B_IDEOGRAM_B167 0x100af #define UNICODE_LINEAR_B_IDEOGRAM_B168 0x100b0 #define UNICODE_LINEAR_B_IDEOGRAM_B169 0x100b1 #define UNICODE_LINEAR_B_IDEOGRAM_B170 0x100b2 #define UNICODE_LINEAR_B_IDEOGRAM_B171 0x100b3 #define UNICODE_LINEAR_B_IDEOGRAM_B172 0x100b4 #define UNICODE_LINEAR_B_IDEOGRAM_B173_MONTH 0x100b5 #define UNICODE_LINEAR_B_IDEOGRAM_B174 0x100b6 #define UNICODE_LINEAR_B_IDEOGRAM_B176_TREE 0x100b7 #define UNICODE_LINEAR_B_IDEOGRAM_B177 0x100b8 #define UNICODE_LINEAR_B_IDEOGRAM_B178 0x100b9 #define UNICODE_LINEAR_B_IDEOGRAM_B179 0x100ba #define UNICODE_LINEAR_B_IDEOGRAM_B180 0x100bb #define UNICODE_LINEAR_B_IDEOGRAM_B181 0x100bc #define UNICODE_LINEAR_B_IDEOGRAM_B182 0x100bd #define UNICODE_LINEAR_B_IDEOGRAM_B183 0x100be #define UNICODE_LINEAR_B_IDEOGRAM_B184 0x100bf #define UNICODE_LINEAR_B_IDEOGRAM_B185 0x100c0 #define UNICODE_LINEAR_B_IDEOGRAM_B189 0x100c1 #define UNICODE_LINEAR_B_IDEOGRAM_B190 0x100c2 #define UNICODE_LINEAR_B_IDEOGRAM_B191_HELMET 0x100c3 #define UNICODE_LINEAR_B_IDEOGRAM_B220_FOOTSTOOL 0x100c4 #define UNICODE_LINEAR_B_IDEOGRAM_B225_BATHTUB 0x100c5 #define UNICODE_LINEAR_B_IDEOGRAM_B230_SPEAR 0x100c6 #define UNICODE_LINEAR_B_IDEOGRAM_B231_ARROW 0x100c7 #define UNICODE_LINEAR_B_IDEOGRAM_B232 0x100c8 #define UNICODE_LINEAR_B_IDEOGRAM_B233_SWORD 0x100c9 #define UNICODE_LINEAR_B_IDEOGRAM_B234 0x100ca #define UNICODE_LINEAR_B_IDEOGRAM_B236 0x100cb #define UNICODE_LINEAR_B_IDEOGRAM_B240_WHEELED_CHARIOT 0x100cc #define UNICODE_LINEAR_B_IDEOGRAM_B241_CHARIOT 0x100cd #define UNICODE_LINEAR_B_IDEOGRAM_B242_CHARIOT_FRAME 0x100ce #define UNICODE_LINEAR_B_IDEOGRAM_B243_WHEEL 0x100cf #define UNICODE_LINEAR_B_IDEOGRAM_B245 0x100d0 #define UNICODE_LINEAR_B_IDEOGRAM_B246 0x100d1 #define UNICODE_LINEAR_B_MONOGRAM_B247_DIPTE 0x100d2 #define UNICODE_LINEAR_B_IDEOGRAM_B248 0x100d3 #define UNICODE_LINEAR_B_IDEOGRAM_B249 0x100d4 #define UNICODE_LINEAR_B_IDEOGRAM_B251 0x100d5 #define UNICODE_LINEAR_B_IDEOGRAM_B252 0x100d6 #define UNICODE_LINEAR_B_IDEOGRAM_B253 0x100d7 #define UNICODE_LINEAR_B_IDEOGRAM_B254_DART 0x100d8 #define UNICODE_LINEAR_B_IDEOGRAM_B255 0x100d9 #define UNICODE_LINEAR_B_IDEOGRAM_B256 0x100da #define UNICODE_LINEAR_B_IDEOGRAM_B257 0x100db #define UNICODE_LINEAR_B_IDEOGRAM_B258 0x100dc #define UNICODE_LINEAR_B_IDEOGRAM_B259 0x100dd #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B155 0x100de #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B200 0x100df #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B201 0x100e0 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B202 0x100e1 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B203 0x100e2 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B204 0x100e3 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B205 0x100e4 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B206 0x100e5 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B207 0x100e6 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B208 0x100e7 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B209 0x100e8 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B210 0x100e9 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B211 0x100ea #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B212 0x100eb #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B213 0x100ec #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B214 0x100ed #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B215 0x100ee #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B216 0x100ef #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B217 0x100f0 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B218 0x100f1 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B219 0x100f2 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B221 0x100f3 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B222 0x100f4 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B226 0x100f5 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B227 0x100f6 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B228 0x100f7 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B229 0x100f8 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B250 0x100f9 #define UNICODE_LINEAR_B_IDEOGRAM_VESSEL_B305 0x100fa #define UNICODE_AEGEAN_WORD_SEPARATOR_LINE 0x10100 #define UNICODE_AEGEAN_WORD_SEPARATOR_DOT 0x10101 #define UNICODE_AEGEAN_CHECK_MARK 0x10102 #define UNICODE_AEGEAN_NUMBER_ONE 0x10107 #define UNICODE_AEGEAN_NUMBER_TWO 0x10108 #define UNICODE_AEGEAN_NUMBER_THREE 0x10109 #define UNICODE_AEGEAN_NUMBER_FOUR 0x1010a #define UNICODE_AEGEAN_NUMBER_FIVE 0x1010b #define UNICODE_AEGEAN_NUMBER_SIX 0x1010c #define UNICODE_AEGEAN_NUMBER_SEVEN 0x1010d #define UNICODE_AEGEAN_NUMBER_EIGHT 0x1010e #define UNICODE_AEGEAN_NUMBER_NINE 0x1010f #define UNICODE_AEGEAN_NUMBER_TEN 0x10110 #define UNICODE_AEGEAN_NUMBER_TWENTY 0x10111 #define UNICODE_AEGEAN_NUMBER_THIRTY 0x10112 #define UNICODE_AEGEAN_NUMBER_FORTY 0x10113 #define UNICODE_AEGEAN_NUMBER_FIFTY 0x10114 #define UNICODE_AEGEAN_NUMBER_SIXTY 0x10115 #define UNICODE_AEGEAN_NUMBER_SEVENTY 0x10116 #define UNICODE_AEGEAN_NUMBER_EIGHTY 0x10117 #define UNICODE_AEGEAN_NUMBER_NINETY 0x10118 #define UNICODE_AEGEAN_NUMBER_ONE_HUNDRED 0x10119 #define UNICODE_AEGEAN_NUMBER_TWO_HUNDRED 0x1011a #define UNICODE_AEGEAN_NUMBER_THREE_HUNDRED 0x1011b #define UNICODE_AEGEAN_NUMBER_FOUR_HUNDRED 0x1011c #define UNICODE_AEGEAN_NUMBER_FIVE_HUNDRED 0x1011d #define UNICODE_AEGEAN_NUMBER_SIX_HUNDRED 0x1011e #define UNICODE_AEGEAN_NUMBER_SEVEN_HUNDRED 0x1011f #define UNICODE_AEGEAN_NUMBER_EIGHT_HUNDRED 0x10120 #define UNICODE_AEGEAN_NUMBER_NINE_HUNDRED 0x10121 #define UNICODE_AEGEAN_NUMBER_ONE_THOUSAND 0x10122 #define UNICODE_AEGEAN_NUMBER_TWO_THOUSAND 0x10123 #define UNICODE_AEGEAN_NUMBER_THREE_THOUSAND 0x10124 #define UNICODE_AEGEAN_NUMBER_FOUR_THOUSAND 0x10125 #define UNICODE_AEGEAN_NUMBER_FIVE_THOUSAND 0x10126 #define UNICODE_AEGEAN_NUMBER_SIX_THOUSAND 0x10127 #define UNICODE_AEGEAN_NUMBER_SEVEN_THOUSAND 0x10128 #define UNICODE_AEGEAN_NUMBER_EIGHT_THOUSAND 0x10129 #define UNICODE_AEGEAN_NUMBER_NINE_THOUSAND 0x1012a #define UNICODE_AEGEAN_NUMBER_TEN_THOUSAND 0x1012b #define UNICODE_AEGEAN_NUMBER_TWENTY_THOUSAND 0x1012c #define UNICODE_AEGEAN_NUMBER_THIRTY_THOUSAND 0x1012d #define UNICODE_AEGEAN_NUMBER_FORTY_THOUSAND 0x1012e #define UNICODE_AEGEAN_NUMBER_FIFTY_THOUSAND 0x1012f #define UNICODE_AEGEAN_NUMBER_SIXTY_THOUSAND 0x10130 #define UNICODE_AEGEAN_NUMBER_SEVENTY_THOUSAND 0x10131 #define UNICODE_AEGEAN_NUMBER_EIGHTY_THOUSAND 0x10132 #define UNICODE_AEGEAN_NUMBER_NINETY_THOUSAND 0x10133 #define UNICODE_AEGEAN_WEIGHT_BASE_UNIT 0x10137 #define UNICODE_AEGEAN_WEIGHT_FIRST_SUBUNIT 0x10138 #define UNICODE_AEGEAN_WEIGHT_SECOND_SUBUNIT 0x10139 #define UNICODE_AEGEAN_WEIGHT_THIRD_SUBUNIT 0x1013a #define UNICODE_AEGEAN_WEIGHT_FOURTH_SUBUNIT 0x1013b #define UNICODE_AEGEAN_DRY_MEASURE_FIRST_SUBUNIT 0x1013c #define UNICODE_AEGEAN_LIQUID_MEASURE_FIRST_SUBUNIT 0x1013d #define UNICODE_AEGEAN_MEASURE_SECOND_SUBUNIT 0x1013e #define UNICODE_AEGEAN_MEASURE_THIRD_SUBUNIT 0x1013f #define UNICODE_GREEK_ACROPHONIC_ATTIC_ONE_QUARTER 0x10140 #define UNICODE_GREEK_ACROPHONIC_ATTIC_ONE_HALF 0x10141 #define UNICODE_GREEK_ACROPHONIC_ATTIC_ONE_DRACHMA 0x10142 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIVE 0x10143 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIFTY 0x10144 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIVE_HUNDRED 0x10145 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIVE_THOUSAND 0x10146 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIFTY_THOUSAND 0x10147 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIVE_TALENTS 0x10148 #define UNICODE_GREEK_ACROPHONIC_ATTIC_TEN_TALENTS 0x10149 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIFTY_TALENTS 0x1014a #define UNICODE_GREEK_ACROPHONIC_ATTIC_ONE_HUNDRED_TALENTS 0x1014b #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIVE_HUNDRED_TALENTS 0x1014c #define UNICODE_GREEK_ACROPHONIC_ATTIC_ONE_THOUSAND_TALENTS 0x1014d #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIVE_THOUSAND_TALENTS 0x1014e #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIVE_STATERS 0x1014f #define UNICODE_GREEK_ACROPHONIC_ATTIC_TEN_STATERS 0x10150 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIFTY_STATERS 0x10151 #define UNICODE_GREEK_ACROPHONIC_ATTIC_ONE_HUNDRED_STATERS 0x10152 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIVE_HUNDRED_STATERS 0x10153 #define UNICODE_GREEK_ACROPHONIC_ATTIC_ONE_THOUSAND_STATERS 0x10154 #define UNICODE_GREEK_ACROPHONIC_ATTIC_TEN_THOUSAND_STATERS 0x10155 #define UNICODE_GREEK_ACROPHONIC_ATTIC_FIFTY_THOUSAND_STATERS 0x10156 #define UNICODE_GREEK_ACROPHONIC_ATTIC_TEN_MNAS 0x10157 #define UNICODE_GREEK_ACROPHONIC_HERAEUM_ONE_PLETHRON 0x10158 #define UNICODE_GREEK_ACROPHONIC_THESPIAN_ONE 0x10159 #define UNICODE_GREEK_ACROPHONIC_HERMIONIAN_ONE 0x1015a #define UNICODE_GREEK_ACROPHONIC_EPIDAUREAN_TWO 0x1015b #define UNICODE_GREEK_ACROPHONIC_THESPIAN_TWO 0x1015c #define UNICODE_GREEK_ACROPHONIC_CYRENAIC_TWO_DRACHMAS 0x1015d #define UNICODE_GREEK_ACROPHONIC_EPIDAUREAN_TWO_DRACHMAS 0x1015e #define UNICODE_GREEK_ACROPHONIC_TROEZENIAN_FIVE 0x1015f #define UNICODE_GREEK_ACROPHONIC_TROEZENIAN_TEN 0x10160 #define UNICODE_GREEK_ACROPHONIC_TROEZENIAN_TEN_ALTERNATE_FORM 0x10161 #define UNICODE_GREEK_ACROPHONIC_HERMIONIAN_TEN 0x10162 #define UNICODE_GREEK_ACROPHONIC_MESSENIAN_TEN 0x10163 #define UNICODE_GREEK_ACROPHONIC_THESPIAN_TEN 0x10164 #define UNICODE_GREEK_ACROPHONIC_THESPIAN_THIRTY 0x10165 #define UNICODE_GREEK_ACROPHONIC_TROEZENIAN_FIFTY 0x10166 #define UNICODE_GREEK_ACROPHONIC_TROEZENIAN_FIFTY_ALTERNATE_FORM 0x10167 #define UNICODE_GREEK_ACROPHONIC_HERMIONIAN_FIFTY 0x10168 #define UNICODE_GREEK_ACROPHONIC_THESPIAN_FIFTY 0x10169 #define UNICODE_GREEK_ACROPHONIC_THESPIAN_ONE_HUNDRED 0x1016a #define UNICODE_GREEK_ACROPHONIC_THESPIAN_THREE_HUNDRED 0x1016b #define UNICODE_GREEK_ACROPHONIC_EPIDAUREAN_FIVE_HUNDRED 0x1016c #define UNICODE_GREEK_ACROPHONIC_TROEZENIAN_FIVE_HUNDRED 0x1016d #define UNICODE_GREEK_ACROPHONIC_THESPIAN_FIVE_HUNDRED 0x1016e #define UNICODE_GREEK_ACROPHONIC_CARYSTIAN_FIVE_HUNDRED 0x1016f #define UNICODE_GREEK_ACROPHONIC_NAXIAN_FIVE_HUNDRED 0x10170 #define UNICODE_GREEK_ACROPHONIC_THESPIAN_ONE_THOUSAND 0x10171 #define UNICODE_GREEK_ACROPHONIC_THESPIAN_FIVE_THOUSAND 0x10172 #define UNICODE_GREEK_ACROPHONIC_DELPHIC_FIVE_MNAS 0x10173 #define UNICODE_GREEK_ACROPHONIC_STRATIAN_FIFTY_MNAS 0x10174 #define UNICODE_GREEK_ONE_HALF_SIGN 0x10175 #define UNICODE_GREEK_ONE_HALF_SIGN_ALTERNATE_FORM 0x10176 #define UNICODE_GREEK_TWO_THIRDS_SIGN 0x10177 #define UNICODE_GREEK_THREE_QUARTERS_SIGN 0x10178 #define UNICODE_GREEK_YEAR_SIGN 0x10179 #define UNICODE_GREEK_TALENT_SIGN 0x1017a #define UNICODE_GREEK_DRACHMA_SIGN 0x1017b #define UNICODE_GREEK_OBOL_SIGN 0x1017c #define UNICODE_GREEK_TWO_OBOLS_SIGN 0x1017d #define UNICODE_GREEK_THREE_OBOLS_SIGN 0x1017e #define UNICODE_GREEK_FOUR_OBOLS_SIGN 0x1017f #define UNICODE_GREEK_FIVE_OBOLS_SIGN 0x10180 #define UNICODE_GREEK_METRETES_SIGN 0x10181 #define UNICODE_GREEK_KYATHOS_BASE_SIGN 0x10182 #define UNICODE_GREEK_LITRA_SIGN 0x10183 #define UNICODE_GREEK_OUNKIA_SIGN 0x10184 #define UNICODE_GREEK_XESTES_SIGN 0x10185 #define UNICODE_GREEK_ARTABE_SIGN 0x10186 #define UNICODE_GREEK_AROURA_SIGN 0x10187 #define UNICODE_GREEK_GRAMMA_SIGN 0x10188 #define UNICODE_GREEK_TRYBLION_BASE_SIGN 0x10189 #define UNICODE_GREEK_ZERO_SIGN 0x1018a #define UNICODE_OLD_ITALIC_LETTER_A 0x10300 #define UNICODE_OLD_ITALIC_LETTER_BE 0x10301 #define UNICODE_OLD_ITALIC_LETTER_KE 0x10302 #define UNICODE_OLD_ITALIC_LETTER_DE 0x10303 #define UNICODE_OLD_ITALIC_LETTER_E 0x10304 #define UNICODE_OLD_ITALIC_LETTER_VE 0x10305 #define UNICODE_OLD_ITALIC_LETTER_ZE 0x10306 #define UNICODE_OLD_ITALIC_LETTER_HE 0x10307 #define UNICODE_OLD_ITALIC_LETTER_THE 0x10308 #define UNICODE_OLD_ITALIC_LETTER_I 0x10309 #define UNICODE_OLD_ITALIC_LETTER_KA 0x1030a #define UNICODE_OLD_ITALIC_LETTER_EL 0x1030b #define UNICODE_OLD_ITALIC_LETTER_EM 0x1030c #define UNICODE_OLD_ITALIC_LETTER_EN 0x1030d #define UNICODE_OLD_ITALIC_LETTER_ESH 0x1030e #define UNICODE_OLD_ITALIC_LETTER_O 0x1030f #define UNICODE_OLD_ITALIC_LETTER_PE 0x10310 #define UNICODE_OLD_ITALIC_LETTER_SHE 0x10311 #define UNICODE_OLD_ITALIC_LETTER_KU 0x10312 #define UNICODE_OLD_ITALIC_LETTER_ER 0x10313 #define UNICODE_OLD_ITALIC_LETTER_ES 0x10314 #define UNICODE_OLD_ITALIC_LETTER_TE 0x10315 #define UNICODE_OLD_ITALIC_LETTER_U 0x10316 #define UNICODE_OLD_ITALIC_LETTER_EKS 0x10317 #define UNICODE_OLD_ITALIC_LETTER_PHE 0x10318 #define UNICODE_OLD_ITALIC_LETTER_KHE 0x10319 #define UNICODE_OLD_ITALIC_LETTER_EF 0x1031a #define UNICODE_OLD_ITALIC_LETTER_ERS 0x1031b #define UNICODE_OLD_ITALIC_LETTER_CHE 0x1031c #define UNICODE_OLD_ITALIC_LETTER_II 0x1031d #define UNICODE_OLD_ITALIC_LETTER_UU 0x1031e #define UNICODE_OLD_ITALIC_NUMERAL_ONE 0x10320 #define UNICODE_OLD_ITALIC_NUMERAL_FIVE 0x10321 #define UNICODE_OLD_ITALIC_NUMERAL_TEN 0x10322 #define UNICODE_OLD_ITALIC_NUMERAL_FIFTY 0x10323 #define UNICODE_GOTHIC_LETTER_AHSA 0x10330 #define UNICODE_GOTHIC_LETTER_BAIRKAN 0x10331 #define UNICODE_GOTHIC_LETTER_GIBA 0x10332 #define UNICODE_GOTHIC_LETTER_DAGS 0x10333 #define UNICODE_GOTHIC_LETTER_AIHVUS 0x10334 #define UNICODE_GOTHIC_LETTER_QAIRTHRA 0x10335 #define UNICODE_GOTHIC_LETTER_IUJA 0x10336 #define UNICODE_GOTHIC_LETTER_HAGL 0x10337 #define UNICODE_GOTHIC_LETTER_THIUTH 0x10338 #define UNICODE_GOTHIC_LETTER_EIS 0x10339 #define UNICODE_GOTHIC_LETTER_KUSMA 0x1033a #define UNICODE_GOTHIC_LETTER_LAGUS 0x1033b #define UNICODE_GOTHIC_LETTER_MANNA 0x1033c #define UNICODE_GOTHIC_LETTER_NAUTHS 0x1033d #define UNICODE_GOTHIC_LETTER_JER 0x1033e #define UNICODE_GOTHIC_LETTER_URUS 0x1033f #define UNICODE_GOTHIC_LETTER_PAIRTHRA 0x10340 #define UNICODE_GOTHIC_LETTER_NINETY 0x10341 #define UNICODE_GOTHIC_LETTER_RAIDA 0x10342 #define UNICODE_GOTHIC_LETTER_SAUIL 0x10343 #define UNICODE_GOTHIC_LETTER_TEIWS 0x10344 #define UNICODE_GOTHIC_LETTER_WINJA 0x10345 #define UNICODE_GOTHIC_LETTER_FAIHU 0x10346 #define UNICODE_GOTHIC_LETTER_IGGWS 0x10347 #define UNICODE_GOTHIC_LETTER_HWAIR 0x10348 #define UNICODE_GOTHIC_LETTER_OTHAL 0x10349 #define UNICODE_GOTHIC_LETTER_NINE_HUNDRED 0x1034a #define UNICODE_UGARITIC_LETTER_ALPA 0x10380 #define UNICODE_UGARITIC_LETTER_BETA 0x10381 #define UNICODE_UGARITIC_LETTER_GAMLA 0x10382 #define UNICODE_UGARITIC_LETTER_KHA 0x10383 #define UNICODE_UGARITIC_LETTER_DELTA 0x10384 #define UNICODE_UGARITIC_LETTER_HO 0x10385 #define UNICODE_UGARITIC_LETTER_WO 0x10386 #define UNICODE_UGARITIC_LETTER_ZETA 0x10387 #define UNICODE_UGARITIC_LETTER_HOTA 0x10388 #define UNICODE_UGARITIC_LETTER_TET 0x10389 #define UNICODE_UGARITIC_LETTER_YOD 0x1038a #define UNICODE_UGARITIC_LETTER_KAF 0x1038b #define UNICODE_UGARITIC_LETTER_SHIN 0x1038c #define UNICODE_UGARITIC_LETTER_LAMDA 0x1038d #define UNICODE_UGARITIC_LETTER_MEM 0x1038e #define UNICODE_UGARITIC_LETTER_DHAL 0x1038f #define UNICODE_UGARITIC_LETTER_NUN 0x10390 #define UNICODE_UGARITIC_LETTER_ZU 0x10391 #define UNICODE_UGARITIC_LETTER_SAMKA 0x10392 #define UNICODE_UGARITIC_LETTER_AIN 0x10393 #define UNICODE_UGARITIC_LETTER_PU 0x10394 #define UNICODE_UGARITIC_LETTER_SADE 0x10395 #define UNICODE_UGARITIC_LETTER_QOPA 0x10396 #define UNICODE_UGARITIC_LETTER_RASHA 0x10397 #define UNICODE_UGARITIC_LETTER_THANNA 0x10398 #define UNICODE_UGARITIC_LETTER_GHAIN 0x10399 #define UNICODE_UGARITIC_LETTER_TO 0x1039a #define UNICODE_UGARITIC_LETTER_I 0x1039b #define UNICODE_UGARITIC_LETTER_U 0x1039c #define UNICODE_UGARITIC_LETTER_SSU 0x1039d #define UNICODE_UGARITIC_WORD_DIVIDER 0x1039f #define UNICODE_OLD_PERSIAN_SIGN_A 0x103a0 #define UNICODE_OLD_PERSIAN_SIGN_I 0x103a1 #define UNICODE_OLD_PERSIAN_SIGN_U 0x103a2 #define UNICODE_OLD_PERSIAN_SIGN_KA 0x103a3 #define UNICODE_OLD_PERSIAN_SIGN_KU 0x103a4 #define UNICODE_OLD_PERSIAN_SIGN_GA 0x103a5 #define UNICODE_OLD_PERSIAN_SIGN_GU 0x103a6 #define UNICODE_OLD_PERSIAN_SIGN_XA 0x103a7 #define UNICODE_OLD_PERSIAN_SIGN_CA 0x103a8 #define UNICODE_OLD_PERSIAN_SIGN_JA 0x103a9 #define UNICODE_OLD_PERSIAN_SIGN_JI 0x103aa #define UNICODE_OLD_PERSIAN_SIGN_TA 0x103ab #define UNICODE_OLD_PERSIAN_SIGN_TU 0x103ac #define UNICODE_OLD_PERSIAN_SIGN_DA 0x103ad #define UNICODE_OLD_PERSIAN_SIGN_DI 0x103ae #define UNICODE_OLD_PERSIAN_SIGN_DU 0x103af #define UNICODE_OLD_PERSIAN_SIGN_THA 0x103b0 #define UNICODE_OLD_PERSIAN_SIGN_PA 0x103b1 #define UNICODE_OLD_PERSIAN_SIGN_BA 0x103b2 #define UNICODE_OLD_PERSIAN_SIGN_FA 0x103b3 #define UNICODE_OLD_PERSIAN_SIGN_NA 0x103b4 #define UNICODE_OLD_PERSIAN_SIGN_NU 0x103b5 #define UNICODE_OLD_PERSIAN_SIGN_MA 0x103b6 #define UNICODE_OLD_PERSIAN_SIGN_MI 0x103b7 #define UNICODE_OLD_PERSIAN_SIGN_MU 0x103b8 #define UNICODE_OLD_PERSIAN_SIGN_YA 0x103b9 #define UNICODE_OLD_PERSIAN_SIGN_VA 0x103ba #define UNICODE_OLD_PERSIAN_SIGN_VI 0x103bb #define UNICODE_OLD_PERSIAN_SIGN_RA 0x103bc #define UNICODE_OLD_PERSIAN_SIGN_RU 0x103bd #define UNICODE_OLD_PERSIAN_SIGN_LA 0x103be #define UNICODE_OLD_PERSIAN_SIGN_SA 0x103bf #define UNICODE_OLD_PERSIAN_SIGN_ZA 0x103c0 #define UNICODE_OLD_PERSIAN_SIGN_SHA 0x103c1 #define UNICODE_OLD_PERSIAN_SIGN_SSA 0x103c2 #define UNICODE_OLD_PERSIAN_SIGN_HA 0x103c3 #define UNICODE_OLD_PERSIAN_SIGN_AURAMAZDAA 0x103c8 #define UNICODE_OLD_PERSIAN_SIGN_AURAMAZDAA_2 0x103c9 #define UNICODE_OLD_PERSIAN_SIGN_AURAMAZDAAHA 0x103ca #define UNICODE_OLD_PERSIAN_SIGN_XSHAAYATHIYA 0x103cb #define UNICODE_OLD_PERSIAN_SIGN_DAHYAAUSH 0x103cc #define UNICODE_OLD_PERSIAN_SIGN_DAHYAAUSH_2 0x103cd #define UNICODE_OLD_PERSIAN_SIGN_BAGA 0x103ce #define UNICODE_OLD_PERSIAN_SIGN_BUUMISH 0x103cf #define UNICODE_OLD_PERSIAN_WORD_DIVIDER 0x103d0 #define UNICODE_OLD_PERSIAN_NUMBER_ONE 0x103d1 #define UNICODE_OLD_PERSIAN_NUMBER_TWO 0x103d2 #define UNICODE_OLD_PERSIAN_NUMBER_TEN 0x103d3 #define UNICODE_OLD_PERSIAN_NUMBER_TWENTY 0x103d4 #define UNICODE_OLD_PERSIAN_NUMBER_HUNDRED 0x103d5 #define UNICODE_DESERET_CAPITAL_LETTER_LONG_I 0x10400 #define UNICODE_DESERET_CAPITAL_LETTER_LONG_E 0x10401 #define UNICODE_DESERET_CAPITAL_LETTER_LONG_A 0x10402 #define UNICODE_DESERET_CAPITAL_LETTER_LONG_AH 0x10403 #define UNICODE_DESERET_CAPITAL_LETTER_LONG_O 0x10404 #define UNICODE_DESERET_CAPITAL_LETTER_LONG_OO 0x10405 #define UNICODE_DESERET_CAPITAL_LETTER_SHORT_I 0x10406 #define UNICODE_DESERET_CAPITAL_LETTER_SHORT_E 0x10407 #define UNICODE_DESERET_CAPITAL_LETTER_SHORT_A 0x10408 #define UNICODE_DESERET_CAPITAL_LETTER_SHORT_AH 0x10409 #define UNICODE_DESERET_CAPITAL_LETTER_SHORT_O 0x1040a #define UNICODE_DESERET_CAPITAL_LETTER_SHORT_OO 0x1040b #define UNICODE_DESERET_CAPITAL_LETTER_AY 0x1040c #define UNICODE_DESERET_CAPITAL_LETTER_OW 0x1040d #define UNICODE_DESERET_CAPITAL_LETTER_WU 0x1040e #define UNICODE_DESERET_CAPITAL_LETTER_YEE 0x1040f #define UNICODE_DESERET_CAPITAL_LETTER_H 0x10410 #define UNICODE_DESERET_CAPITAL_LETTER_PEE 0x10411 #define UNICODE_DESERET_CAPITAL_LETTER_BEE 0x10412 #define UNICODE_DESERET_CAPITAL_LETTER_TEE 0x10413 #define UNICODE_DESERET_CAPITAL_LETTER_DEE 0x10414 #define UNICODE_DESERET_CAPITAL_LETTER_CHEE 0x10415 #define UNICODE_DESERET_CAPITAL_LETTER_JEE 0x10416 #define UNICODE_DESERET_CAPITAL_LETTER_KAY 0x10417 #define UNICODE_DESERET_CAPITAL_LETTER_GAY 0x10418 #define UNICODE_DESERET_CAPITAL_LETTER_EF 0x10419 #define UNICODE_DESERET_CAPITAL_LETTER_VEE 0x1041a #define UNICODE_DESERET_CAPITAL_LETTER_ETH 0x1041b #define UNICODE_DESERET_CAPITAL_LETTER_THEE 0x1041c #define UNICODE_DESERET_CAPITAL_LETTER_ES 0x1041d #define UNICODE_DESERET_CAPITAL_LETTER_ZEE 0x1041e #define UNICODE_DESERET_CAPITAL_LETTER_ESH 0x1041f #define UNICODE_DESERET_CAPITAL_LETTER_ZHEE 0x10420 #define UNICODE_DESERET_CAPITAL_LETTER_ER 0x10421 #define UNICODE_DESERET_CAPITAL_LETTER_EL 0x10422 #define UNICODE_DESERET_CAPITAL_LETTER_EM 0x10423 #define UNICODE_DESERET_CAPITAL_LETTER_EN 0x10424 #define UNICODE_DESERET_CAPITAL_LETTER_ENG 0x10425 #define UNICODE_DESERET_CAPITAL_LETTER_OI 0x10426 #define UNICODE_DESERET_CAPITAL_LETTER_EW 0x10427 #define UNICODE_DESERET_SMALL_LETTER_LONG_I 0x10428 #define UNICODE_DESERET_SMALL_LETTER_LONG_E 0x10429 #define UNICODE_DESERET_SMALL_LETTER_LONG_A 0x1042a #define UNICODE_DESERET_SMALL_LETTER_LONG_AH 0x1042b #define UNICODE_DESERET_SMALL_LETTER_LONG_O 0x1042c #define UNICODE_DESERET_SMALL_LETTER_LONG_OO 0x1042d #define UNICODE_DESERET_SMALL_LETTER_SHORT_I 0x1042e #define UNICODE_DESERET_SMALL_LETTER_SHORT_E 0x1042f #define UNICODE_DESERET_SMALL_LETTER_SHORT_A 0x10430 #define UNICODE_DESERET_SMALL_LETTER_SHORT_AH 0x10431 #define UNICODE_DESERET_SMALL_LETTER_SHORT_O 0x10432 #define UNICODE_DESERET_SMALL_LETTER_SHORT_OO 0x10433 #define UNICODE_DESERET_SMALL_LETTER_AY 0x10434 #define UNICODE_DESERET_SMALL_LETTER_OW 0x10435 #define UNICODE_DESERET_SMALL_LETTER_WU 0x10436 #define UNICODE_DESERET_SMALL_LETTER_YEE 0x10437 #define UNICODE_DESERET_SMALL_LETTER_H 0x10438 #define UNICODE_DESERET_SMALL_LETTER_PEE 0x10439 #define UNICODE_DESERET_SMALL_LETTER_BEE 0x1043a #define UNICODE_DESERET_SMALL_LETTER_TEE 0x1043b #define UNICODE_DESERET_SMALL_LETTER_DEE 0x1043c #define UNICODE_DESERET_SMALL_LETTER_CHEE 0x1043d #define UNICODE_DESERET_SMALL_LETTER_JEE 0x1043e #define UNICODE_DESERET_SMALL_LETTER_KAY 0x1043f #define UNICODE_DESERET_SMALL_LETTER_GAY 0x10440 #define UNICODE_DESERET_SMALL_LETTER_EF 0x10441 #define UNICODE_DESERET_SMALL_LETTER_VEE 0x10442 #define UNICODE_DESERET_SMALL_LETTER_ETH 0x10443 #define UNICODE_DESERET_SMALL_LETTER_THEE 0x10444 #define UNICODE_DESERET_SMALL_LETTER_ES 0x10445 #define UNICODE_DESERET_SMALL_LETTER_ZEE 0x10446 #define UNICODE_DESERET_SMALL_LETTER_ESH 0x10447 #define UNICODE_DESERET_SMALL_LETTER_ZHEE 0x10448 #define UNICODE_DESERET_SMALL_LETTER_ER 0x10449 #define UNICODE_DESERET_SMALL_LETTER_EL 0x1044a #define UNICODE_DESERET_SMALL_LETTER_EM 0x1044b #define UNICODE_DESERET_SMALL_LETTER_EN 0x1044c #define UNICODE_DESERET_SMALL_LETTER_ENG 0x1044d #define UNICODE_DESERET_SMALL_LETTER_OI 0x1044e #define UNICODE_DESERET_SMALL_LETTER_EW 0x1044f #define UNICODE_SHAVIAN_LETTER_PEEP 0x10450 #define UNICODE_SHAVIAN_LETTER_TOT 0x10451 #define UNICODE_SHAVIAN_LETTER_KICK 0x10452 #define UNICODE_SHAVIAN_LETTER_FEE 0x10453 #define UNICODE_SHAVIAN_LETTER_THIGH 0x10454 #define UNICODE_SHAVIAN_LETTER_SO 0x10455 #define UNICODE_SHAVIAN_LETTER_SURE 0x10456 #define UNICODE_SHAVIAN_LETTER_CHURCH 0x10457 #define UNICODE_SHAVIAN_LETTER_YEA 0x10458 #define UNICODE_SHAVIAN_LETTER_HUNG 0x10459 #define UNICODE_SHAVIAN_LETTER_BIB 0x1045a #define UNICODE_SHAVIAN_LETTER_DEAD 0x1045b #define UNICODE_SHAVIAN_LETTER_GAG 0x1045c #define UNICODE_SHAVIAN_LETTER_VOW 0x1045d #define UNICODE_SHAVIAN_LETTER_THEY 0x1045e #define UNICODE_SHAVIAN_LETTER_ZOO 0x1045f #define UNICODE_SHAVIAN_LETTER_MEASURE 0x10460 #define UNICODE_SHAVIAN_LETTER_JUDGE 0x10461 #define UNICODE_SHAVIAN_LETTER_WOE 0x10462 #define UNICODE_SHAVIAN_LETTER_HA_HA 0x10463 #define UNICODE_SHAVIAN_LETTER_LOLL 0x10464 #define UNICODE_SHAVIAN_LETTER_MIME 0x10465 #define UNICODE_SHAVIAN_LETTER_IF 0x10466 #define UNICODE_SHAVIAN_LETTER_EGG 0x10467 #define UNICODE_SHAVIAN_LETTER_ASH 0x10468 #define UNICODE_SHAVIAN_LETTER_ADO 0x10469 #define UNICODE_SHAVIAN_LETTER_ON 0x1046a #define UNICODE_SHAVIAN_LETTER_WOOL 0x1046b #define UNICODE_SHAVIAN_LETTER_OUT 0x1046c #define UNICODE_SHAVIAN_LETTER_AH 0x1046d #define UNICODE_SHAVIAN_LETTER_ROAR 0x1046e #define UNICODE_SHAVIAN_LETTER_NUN 0x1046f #define UNICODE_SHAVIAN_LETTER_EAT 0x10470 #define UNICODE_SHAVIAN_LETTER_AGE 0x10471 #define UNICODE_SHAVIAN_LETTER_ICE 0x10472 #define UNICODE_SHAVIAN_LETTER_UP 0x10473 #define UNICODE_SHAVIAN_LETTER_OAK 0x10474 #define UNICODE_SHAVIAN_LETTER_OOZE 0x10475 #define UNICODE_SHAVIAN_LETTER_OIL 0x10476 #define UNICODE_SHAVIAN_LETTER_AWE 0x10477 #define UNICODE_SHAVIAN_LETTER_ARE 0x10478 #define UNICODE_SHAVIAN_LETTER_OR 0x10479 #define UNICODE_SHAVIAN_LETTER_AIR 0x1047a #define UNICODE_SHAVIAN_LETTER_ERR 0x1047b #define UNICODE_SHAVIAN_LETTER_ARRAY 0x1047c #define UNICODE_SHAVIAN_LETTER_EAR 0x1047d #define UNICODE_SHAVIAN_LETTER_IAN 0x1047e #define UNICODE_SHAVIAN_LETTER_YEW 0x1047f #define UNICODE_OSMANYA_LETTER_ALEF 0x10480 #define UNICODE_OSMANYA_LETTER_BA 0x10481 #define UNICODE_OSMANYA_LETTER_TA 0x10482 #define UNICODE_OSMANYA_LETTER_JA 0x10483 #define UNICODE_OSMANYA_LETTER_XA 0x10484 #define UNICODE_OSMANYA_LETTER_KHA 0x10485 #define UNICODE_OSMANYA_LETTER_DEEL 0x10486 #define UNICODE_OSMANYA_LETTER_RA 0x10487 #define UNICODE_OSMANYA_LETTER_SA 0x10488 #define UNICODE_OSMANYA_LETTER_SHIIN 0x10489 #define UNICODE_OSMANYA_LETTER_DHA 0x1048a #define UNICODE_OSMANYA_LETTER_CAYN 0x1048b #define UNICODE_OSMANYA_LETTER_GA 0x1048c #define UNICODE_OSMANYA_LETTER_FA 0x1048d #define UNICODE_OSMANYA_LETTER_QAAF 0x1048e #define UNICODE_OSMANYA_LETTER_KAAF 0x1048f #define UNICODE_OSMANYA_LETTER_LAAN 0x10490 #define UNICODE_OSMANYA_LETTER_MIIN 0x10491 #define UNICODE_OSMANYA_LETTER_NUUN 0x10492 #define UNICODE_OSMANYA_LETTER_WAW 0x10493 #define UNICODE_OSMANYA_LETTER_HA 0x10494 #define UNICODE_OSMANYA_LETTER_YA 0x10495 #define UNICODE_OSMANYA_LETTER_A 0x10496 #define UNICODE_OSMANYA_LETTER_E 0x10497 #define UNICODE_OSMANYA_LETTER_I 0x10498 #define UNICODE_OSMANYA_LETTER_O 0x10499 #define UNICODE_OSMANYA_LETTER_U 0x1049a #define UNICODE_OSMANYA_LETTER_AA 0x1049b #define UNICODE_OSMANYA_LETTER_EE 0x1049c #define UNICODE_OSMANYA_LETTER_OO 0x1049d #define UNICODE_OSMANYA_DIGIT_ZERO 0x104a0 #define UNICODE_OSMANYA_DIGIT_ONE 0x104a1 #define UNICODE_OSMANYA_DIGIT_TWO 0x104a2 #define UNICODE_OSMANYA_DIGIT_THREE 0x104a3 #define UNICODE_OSMANYA_DIGIT_FOUR 0x104a4 #define UNICODE_OSMANYA_DIGIT_FIVE 0x104a5 #define UNICODE_OSMANYA_DIGIT_SIX 0x104a6 #define UNICODE_OSMANYA_DIGIT_SEVEN 0x104a7 #define UNICODE_OSMANYA_DIGIT_EIGHT 0x104a8 #define UNICODE_OSMANYA_DIGIT_NINE 0x104a9 #define UNICODE_CYPRIOT_SYLLABLE_A 0x10800 #define UNICODE_CYPRIOT_SYLLABLE_E 0x10801 #define UNICODE_CYPRIOT_SYLLABLE_I 0x10802 #define UNICODE_CYPRIOT_SYLLABLE_O 0x10803 #define UNICODE_CYPRIOT_SYLLABLE_U 0x10804 #define UNICODE_CYPRIOT_SYLLABLE_JA 0x10805 #define UNICODE_CYPRIOT_SYLLABLE_JO 0x10808 #define UNICODE_CYPRIOT_SYLLABLE_KA 0x1080a #define UNICODE_CYPRIOT_SYLLABLE_KE 0x1080b #define UNICODE_CYPRIOT_SYLLABLE_KI 0x1080c #define UNICODE_CYPRIOT_SYLLABLE_KO 0x1080d #define UNICODE_CYPRIOT_SYLLABLE_KU 0x1080e #define UNICODE_CYPRIOT_SYLLABLE_LA 0x1080f #define UNICODE_CYPRIOT_SYLLABLE_LE 0x10810 #define UNICODE_CYPRIOT_SYLLABLE_LI 0x10811 #define UNICODE_CYPRIOT_SYLLABLE_LO 0x10812 #define UNICODE_CYPRIOT_SYLLABLE_LU 0x10813 #define UNICODE_CYPRIOT_SYLLABLE_MA 0x10814 #define UNICODE_CYPRIOT_SYLLABLE_ME 0x10815 #define UNICODE_CYPRIOT_SYLLABLE_MI 0x10816 #define UNICODE_CYPRIOT_SYLLABLE_MO 0x10817 #define UNICODE_CYPRIOT_SYLLABLE_MU 0x10818 #define UNICODE_CYPRIOT_SYLLABLE_NA 0x10819 #define UNICODE_CYPRIOT_SYLLABLE_NE 0x1081a #define UNICODE_CYPRIOT_SYLLABLE_NI 0x1081b #define UNICODE_CYPRIOT_SYLLABLE_NO 0x1081c #define UNICODE_CYPRIOT_SYLLABLE_NU 0x1081d #define UNICODE_CYPRIOT_SYLLABLE_PA 0x1081e #define UNICODE_CYPRIOT_SYLLABLE_PE 0x1081f #define UNICODE_CYPRIOT_SYLLABLE_PI 0x10820 #define UNICODE_CYPRIOT_SYLLABLE_PO 0x10821 #define UNICODE_CYPRIOT_SYLLABLE_PU 0x10822 #define UNICODE_CYPRIOT_SYLLABLE_RA 0x10823 #define UNICODE_CYPRIOT_SYLLABLE_RE 0x10824 #define UNICODE_CYPRIOT_SYLLABLE_RI 0x10825 #define UNICODE_CYPRIOT_SYLLABLE_RO 0x10826 #define UNICODE_CYPRIOT_SYLLABLE_RU 0x10827 #define UNICODE_CYPRIOT_SYLLABLE_SA 0x10828 #define UNICODE_CYPRIOT_SYLLABLE_SE 0x10829 #define UNICODE_CYPRIOT_SYLLABLE_SI 0x1082a #define UNICODE_CYPRIOT_SYLLABLE_SO 0x1082b #define UNICODE_CYPRIOT_SYLLABLE_SU 0x1082c #define UNICODE_CYPRIOT_SYLLABLE_TA 0x1082d #define UNICODE_CYPRIOT_SYLLABLE_TE 0x1082e #define UNICODE_CYPRIOT_SYLLABLE_TI 0x1082f #define UNICODE_CYPRIOT_SYLLABLE_TO 0x10830 #define UNICODE_CYPRIOT_SYLLABLE_TU 0x10831 #define UNICODE_CYPRIOT_SYLLABLE_WA 0x10832 #define UNICODE_CYPRIOT_SYLLABLE_WE 0x10833 #define UNICODE_CYPRIOT_SYLLABLE_WI 0x10834 #define UNICODE_CYPRIOT_SYLLABLE_WO 0x10835 #define UNICODE_CYPRIOT_SYLLABLE_XA 0x10837 #define UNICODE_CYPRIOT_SYLLABLE_XE 0x10838 #define UNICODE_CYPRIOT_SYLLABLE_ZA 0x1083c #define UNICODE_CYPRIOT_SYLLABLE_ZO 0x1083f #define UNICODE_PHOENICIAN_LETTER_ALF 0x10900 #define UNICODE_PHOENICIAN_LETTER_BET 0x10901 #define UNICODE_PHOENICIAN_LETTER_GAML 0x10902 #define UNICODE_PHOENICIAN_LETTER_DELT 0x10903 #define UNICODE_PHOENICIAN_LETTER_HE 0x10904 #define UNICODE_PHOENICIAN_LETTER_WAU 0x10905 #define UNICODE_PHOENICIAN_LETTER_ZAI 0x10906 #define UNICODE_PHOENICIAN_LETTER_HET 0x10907 #define UNICODE_PHOENICIAN_LETTER_TET 0x10908 #define UNICODE_PHOENICIAN_LETTER_YOD 0x10909 #define UNICODE_PHOENICIAN_LETTER_KAF 0x1090a #define UNICODE_PHOENICIAN_LETTER_LAMD 0x1090b #define UNICODE_PHOENICIAN_LETTER_MEM 0x1090c #define UNICODE_PHOENICIAN_LETTER_NUN 0x1090d #define UNICODE_PHOENICIAN_LETTER_SEMK 0x1090e #define UNICODE_PHOENICIAN_LETTER_AIN 0x1090f #define UNICODE_PHOENICIAN_LETTER_PE 0x10910 #define UNICODE_PHOENICIAN_LETTER_SADE 0x10911 #define UNICODE_PHOENICIAN_LETTER_QOF 0x10912 #define UNICODE_PHOENICIAN_LETTER_ROSH 0x10913 #define UNICODE_PHOENICIAN_LETTER_SHIN 0x10914 #define UNICODE_PHOENICIAN_LETTER_TAU 0x10915 #define UNICODE_PHOENICIAN_NUMBER_ONE 0x10916 #define UNICODE_PHOENICIAN_NUMBER_TEN 0x10917 #define UNICODE_PHOENICIAN_NUMBER_TWENTY 0x10918 #define UNICODE_PHOENICIAN_NUMBER_ONE_HUNDRED 0x10919 #define UNICODE_PHOENICIAN_WORD_SEPARATOR 0x1091f #define UNICODE_KHAROSHTHI_LETTER_A 0x10a00 #define UNICODE_KHAROSHTHI_VOWEL_SIGN_I 0x10a01 #define UNICODE_KHAROSHTHI_VOWEL_SIGN_U 0x10a02 #define UNICODE_KHAROSHTHI_VOWEL_SIGN_VOCALIC_R 0x10a03 #define UNICODE_KHAROSHTHI_VOWEL_SIGN_E 0x10a05 #define UNICODE_KHAROSHTHI_VOWEL_SIGN_O 0x10a06 #define UNICODE_KHAROSHTHI_VOWEL_LENGTH_MARK 0x10a0c #define UNICODE_KHAROSHTHI_SIGN_DOUBLE_RING_BELOW 0x10a0d #define UNICODE_KHAROSHTHI_SIGN_ANUSVARA 0x10a0e #define UNICODE_KHAROSHTHI_SIGN_VISARGA 0x10a0f #define UNICODE_KHAROSHTHI_LETTER_KA 0x10a10 #define UNICODE_KHAROSHTHI_LETTER_KHA 0x10a11 #define UNICODE_KHAROSHTHI_LETTER_GA 0x10a12 #define UNICODE_KHAROSHTHI_LETTER_GHA 0x10a13 #define UNICODE_KHAROSHTHI_LETTER_CA 0x10a15 #define UNICODE_KHAROSHTHI_LETTER_CHA 0x10a16 #define UNICODE_KHAROSHTHI_LETTER_JA 0x10a17 #define UNICODE_KHAROSHTHI_LETTER_NYA 0x10a19 #define UNICODE_KHAROSHTHI_LETTER_TTA 0x10a1a #define UNICODE_KHAROSHTHI_LETTER_TTHA 0x10a1b #define UNICODE_KHAROSHTHI_LETTER_DDA 0x10a1c #define UNICODE_KHAROSHTHI_LETTER_DDHA 0x10a1d #define UNICODE_KHAROSHTHI_LETTER_NNA 0x10a1e #define UNICODE_KHAROSHTHI_LETTER_TA 0x10a1f #define UNICODE_KHAROSHTHI_LETTER_THA 0x10a20 #define UNICODE_KHAROSHTHI_LETTER_DA 0x10a21 #define UNICODE_KHAROSHTHI_LETTER_DHA 0x10a22 #define UNICODE_KHAROSHTHI_LETTER_NA 0x10a23 #define UNICODE_KHAROSHTHI_LETTER_PA 0x10a24 #define UNICODE_KHAROSHTHI_LETTER_PHA 0x10a25 #define UNICODE_KHAROSHTHI_LETTER_BA 0x10a26 #define UNICODE_KHAROSHTHI_LETTER_BHA 0x10a27 #define UNICODE_KHAROSHTHI_LETTER_MA 0x10a28 #define UNICODE_KHAROSHTHI_LETTER_YA 0x10a29 #define UNICODE_KHAROSHTHI_LETTER_RA 0x10a2a #define UNICODE_KHAROSHTHI_LETTER_LA 0x10a2b #define UNICODE_KHAROSHTHI_LETTER_VA 0x10a2c #define UNICODE_KHAROSHTHI_LETTER_SHA 0x10a2d #define UNICODE_KHAROSHTHI_LETTER_SSA 0x10a2e #define UNICODE_KHAROSHTHI_LETTER_SA 0x10a2f #define UNICODE_KHAROSHTHI_LETTER_ZA 0x10a30 #define UNICODE_KHAROSHTHI_LETTER_HA 0x10a31 #define UNICODE_KHAROSHTHI_LETTER_KKA 0x10a32 #define UNICODE_KHAROSHTHI_LETTER_TTTHA 0x10a33 #define UNICODE_KHAROSHTHI_SIGN_BAR_ABOVE 0x10a38 #define UNICODE_KHAROSHTHI_SIGN_CAUDA 0x10a39 #define UNICODE_KHAROSHTHI_SIGN_DOT_BELOW 0x10a3a #define UNICODE_KHAROSHTHI_VIRAMA 0x10a3f #define UNICODE_KHAROSHTHI_DIGIT_ONE 0x10a40 #define UNICODE_KHAROSHTHI_DIGIT_TWO 0x10a41 #define UNICODE_KHAROSHTHI_DIGIT_THREE 0x10a42 #define UNICODE_KHAROSHTHI_DIGIT_FOUR 0x10a43 #define UNICODE_KHAROSHTHI_NUMBER_TEN 0x10a44 #define UNICODE_KHAROSHTHI_NUMBER_TWENTY 0x10a45 #define UNICODE_KHAROSHTHI_NUMBER_ONE_HUNDRED 0x10a46 #define UNICODE_KHAROSHTHI_NUMBER_ONE_THOUSAND 0x10a47 #define UNICODE_KHAROSHTHI_PUNCTUATION_DOT 0x10a50 #define UNICODE_KHAROSHTHI_PUNCTUATION_SMALL_CIRCLE 0x10a51 #define UNICODE_KHAROSHTHI_PUNCTUATION_CIRCLE 0x10a52 #define UNICODE_KHAROSHTHI_PUNCTUATION_CRESCENT_BAR 0x10a53 #define UNICODE_KHAROSHTHI_PUNCTUATION_MANGALAM 0x10a54 #define UNICODE_KHAROSHTHI_PUNCTUATION_LOTUS 0x10a55 #define UNICODE_KHAROSHTHI_PUNCTUATION_DANDA 0x10a56 #define UNICODE_KHAROSHTHI_PUNCTUATION_DOUBLE_DANDA 0x10a57 #define UNICODE_KHAROSHTHI_PUNCTUATION_LINES 0x10a58 #define UNICODE_CUNEIFORM_SIGN_A 0x12000 #define UNICODE_CUNEIFORM_SIGN_A_TIMES_A 0x12001 #define UNICODE_CUNEIFORM_SIGN_A_TIMES_BAD 0x12002 #define UNICODE_CUNEIFORM_SIGN_A_TIMES_GAN2_TENU 0x12003 #define UNICODE_CUNEIFORM_SIGN_A_TIMES_HA 0x12004 #define UNICODE_CUNEIFORM_SIGN_A_TIMES_IGI 0x12005 #define UNICODE_CUNEIFORM_SIGN_A_TIMES_LAGAR_GUNU 0x12006 #define UNICODE_CUNEIFORM_SIGN_A_TIMES_MUSH 0x12007 #define UNICODE_CUNEIFORM_SIGN_A_TIMES_SAG 0x12008 #define UNICODE_CUNEIFORM_SIGN_A2 0x12009 #define UNICODE_CUNEIFORM_SIGN_AB 0x1200a #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_ASH2 0x1200b #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_DUN3_GUNU 0x1200c #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_GAL 0x1200d #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_GAN2_TENU 0x1200e #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_HA 0x1200f #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_IGI_GUNU 0x12010 #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_IMIN 0x12011 #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_LAGAB 0x12012 #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_SHESH 0x12013 #define UNICODE_CUNEIFORM_SIGN_AB_TIMES_U_PLUS_U_PLUS_U 0x12014 #define UNICODE_CUNEIFORM_SIGN_AB_GUNU 0x12015 #define UNICODE_CUNEIFORM_SIGN_AB2 0x12016 #define UNICODE_CUNEIFORM_SIGN_AB2_TIMES_BALAG 0x12017 #define UNICODE_CUNEIFORM_SIGN_AB2_TIMES_GAN2_TENU 0x12018 #define UNICODE_CUNEIFORM_SIGN_AB2_TIMES_ME_PLUS_EN 0x12019 #define UNICODE_CUNEIFORM_SIGN_AB2_TIMES_SHA3 0x1201a #define UNICODE_CUNEIFORM_SIGN_AB2_TIMES_TAK4 0x1201b #define UNICODE_CUNEIFORM_SIGN_AD 0x1201c #define UNICODE_CUNEIFORM_SIGN_AK 0x1201d #define UNICODE_CUNEIFORM_SIGN_AK_TIMES_ERIN2 0x1201e #define UNICODE_CUNEIFORM_SIGN_AK_TIMES_SHITA_PLUS_GISH 0x1201f #define UNICODE_CUNEIFORM_SIGN_AL 0x12020 #define UNICODE_CUNEIFORM_SIGN_AL_TIMES_AL 0x12021 #define UNICODE_CUNEIFORM_SIGN_AL_TIMES_DIM2 0x12022 #define UNICODE_CUNEIFORM_SIGN_AL_TIMES_GISH 0x12023 #define UNICODE_CUNEIFORM_SIGN_AL_TIMES_HA 0x12024 #define UNICODE_CUNEIFORM_SIGN_AL_TIMES_KAD3 0x12025 #define UNICODE_CUNEIFORM_SIGN_AL_TIMES_KI 0x12026 #define UNICODE_CUNEIFORM_SIGN_AL_TIMES_SHE 0x12027 #define UNICODE_CUNEIFORM_SIGN_AL_TIMES_USH 0x12028 #define UNICODE_CUNEIFORM_SIGN_ALAN 0x12029 #define UNICODE_CUNEIFORM_SIGN_ALEPH 0x1202a #define UNICODE_CUNEIFORM_SIGN_AMAR 0x1202b #define UNICODE_CUNEIFORM_SIGN_AMAR_TIMES_SHE 0x1202c #define UNICODE_CUNEIFORM_SIGN_AN 0x1202d #define UNICODE_CUNEIFORM_SIGN_AN_OVER_AN 0x1202e #define UNICODE_CUNEIFORM_SIGN_AN_THREE_TIMES 0x1202f #define UNICODE_CUNEIFORM_SIGN_AN_PLUS_NAGA_OPPOSING_AN_PLUS_NAGA 0x12030 #define UNICODE_CUNEIFORM_SIGN_AN_PLUS_NAGA_SQUARED 0x12031 #define UNICODE_CUNEIFORM_SIGN_ANSHE 0x12032 #define UNICODE_CUNEIFORM_SIGN_APIN 0x12033 #define UNICODE_CUNEIFORM_SIGN_ARAD 0x12034 #define UNICODE_CUNEIFORM_SIGN_ARAD_TIMES_KUR 0x12035 #define UNICODE_CUNEIFORM_SIGN_ARKAB 0x12036 #define UNICODE_CUNEIFORM_SIGN_ASAL2 0x12037 #define UNICODE_CUNEIFORM_SIGN_ASH 0x12038 #define UNICODE_CUNEIFORM_SIGN_ASH_ZIDA_TENU 0x12039 #define UNICODE_CUNEIFORM_SIGN_ASH_KABA_TENU 0x1203a #define UNICODE_CUNEIFORM_SIGN_ASH_OVER_ASH_TUG2_OVER_TUG2_TUG2_OVER_TUG2_PAP 0x1203b #define UNICODE_CUNEIFORM_SIGN_ASH_OVER_ASH_OVER_ASH 0x1203c #define UNICODE_CUNEIFORM_SIGN_ASH_OVER_ASH_OVER_ASH_CROSSING_ASH_OVER_ASH_OVER_ASH 0x1203d #define UNICODE_CUNEIFORM_SIGN_ASH2 0x1203e #define UNICODE_CUNEIFORM_SIGN_ASHGAB 0x1203f #define UNICODE_CUNEIFORM_SIGN_BA 0x12040 #define UNICODE_CUNEIFORM_SIGN_BAD 0x12041 #define UNICODE_CUNEIFORM_SIGN_BAG3 0x12042 #define UNICODE_CUNEIFORM_SIGN_BAHAR2 0x12043 #define UNICODE_CUNEIFORM_SIGN_BAL 0x12044 #define UNICODE_CUNEIFORM_SIGN_BAL_OVER_BAL 0x12045 #define UNICODE_CUNEIFORM_SIGN_BALAG 0x12046 #define UNICODE_CUNEIFORM_SIGN_BAR 0x12047 #define UNICODE_CUNEIFORM_SIGN_BARA2 0x12048 #define UNICODE_CUNEIFORM_SIGN_BI 0x12049 #define UNICODE_CUNEIFORM_SIGN_BI_TIMES_A 0x1204a #define UNICODE_CUNEIFORM_SIGN_BI_TIMES_GAR 0x1204b #define UNICODE_CUNEIFORM_SIGN_BI_TIMES_IGI_GUNU 0x1204c #define UNICODE_CUNEIFORM_SIGN_BU 0x1204d #define UNICODE_CUNEIFORM_SIGN_BU_OVER_BU_AB 0x1204e #define UNICODE_CUNEIFORM_SIGN_BU_OVER_BU_UN 0x1204f #define UNICODE_CUNEIFORM_SIGN_BU_CROSSING_BU 0x12050 #define UNICODE_CUNEIFORM_SIGN_BULUG 0x12051 #define UNICODE_CUNEIFORM_SIGN_BULUG_OVER_BULUG 0x12052 #define UNICODE_CUNEIFORM_SIGN_BUR 0x12053 #define UNICODE_CUNEIFORM_SIGN_BUR2 0x12054 #define UNICODE_CUNEIFORM_SIGN_DA 0x12055 #define UNICODE_CUNEIFORM_SIGN_DAG 0x12056 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_A_PLUS_MASH 0x12057 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_AMAR 0x12058 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_BALAG 0x12059 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_BI 0x1205a #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_GA 0x1205b #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_GA_PLUS_MASH 0x1205c #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_GI 0x1205d #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_GIR2 0x1205e #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_GUD 0x1205f #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_HA 0x12060 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_IR 0x12061 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_IR_PLUS_LU 0x12062 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_KAK 0x12063 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_LA 0x12064 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_LU 0x12065 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_LU_PLUS_MASH2 0x12066 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_LUM 0x12067 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_NE 0x12068 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_PAP_PLUS_PAP 0x12069 #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_SI 0x1206a #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_TAK4 0x1206b #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_U2_PLUS_GIR2 0x1206c #define UNICODE_CUNEIFORM_SIGN_DAG_KISIM5_TIMES_USH 0x1206d #define UNICODE_CUNEIFORM_SIGN_DAM 0x1206e #define UNICODE_CUNEIFORM_SIGN_DAR 0x1206f #define UNICODE_CUNEIFORM_SIGN_DARA3 0x12070 #define UNICODE_CUNEIFORM_SIGN_DARA4 0x12071 #define UNICODE_CUNEIFORM_SIGN_DI 0x12072 #define UNICODE_CUNEIFORM_SIGN_DIB 0x12073 #define UNICODE_CUNEIFORM_SIGN_DIM 0x12074 #define UNICODE_CUNEIFORM_SIGN_DIM_TIMES_SHE 0x12075 #define UNICODE_CUNEIFORM_SIGN_DIM2 0x12076 #define UNICODE_CUNEIFORM_SIGN_DIN 0x12077 #define UNICODE_CUNEIFORM_SIGN_DIN_KASKAL_U_GUNU_DISH 0x12078 #define UNICODE_CUNEIFORM_SIGN_DISH 0x12079 #define UNICODE_CUNEIFORM_SIGN_DU 0x1207a #define UNICODE_CUNEIFORM_SIGN_DU_OVER_DU 0x1207b #define UNICODE_CUNEIFORM_SIGN_DU_GUNU 0x1207c #define UNICODE_CUNEIFORM_SIGN_DU_SHESHIG 0x1207d #define UNICODE_CUNEIFORM_SIGN_DUB 0x1207e #define UNICODE_CUNEIFORM_SIGN_DUB_TIMES_ESH2 0x1207f #define UNICODE_CUNEIFORM_SIGN_DUB2 0x12080 #define UNICODE_CUNEIFORM_SIGN_DUG 0x12081 #define UNICODE_CUNEIFORM_SIGN_DUGUD 0x12082 #define UNICODE_CUNEIFORM_SIGN_DUH 0x12083 #define UNICODE_CUNEIFORM_SIGN_DUN 0x12084 #define UNICODE_CUNEIFORM_SIGN_DUN3 0x12085 #define UNICODE_CUNEIFORM_SIGN_DUN3_GUNU 0x12086 #define UNICODE_CUNEIFORM_SIGN_DUN3_GUNU_GUNU 0x12087 #define UNICODE_CUNEIFORM_SIGN_DUN4 0x12088 #define UNICODE_CUNEIFORM_SIGN_DUR2 0x12089 #define UNICODE_CUNEIFORM_SIGN_E 0x1208a #define UNICODE_CUNEIFORM_SIGN_E_TIMES_PAP 0x1208b #define UNICODE_CUNEIFORM_SIGN_E_OVER_E_NUN_OVER_NUN 0x1208c #define UNICODE_CUNEIFORM_SIGN_E2 0x1208d #define UNICODE_CUNEIFORM_SIGN_E2_TIMES_A_PLUS_HA_PLUS_DA 0x1208e #define UNICODE_CUNEIFORM_SIGN_E2_TIMES_GAR 0x1208f #define UNICODE_CUNEIFORM_SIGN_E2_TIMES_MI 0x12090 #define UNICODE_CUNEIFORM_SIGN_E2_TIMES_SAL 0x12091 #define UNICODE_CUNEIFORM_SIGN_E2_TIMES_SHE 0x12092 #define UNICODE_CUNEIFORM_SIGN_E2_TIMES_U 0x12093 #define UNICODE_CUNEIFORM_SIGN_EDIN 0x12094 #define UNICODE_CUNEIFORM_SIGN_EGIR 0x12095 #define UNICODE_CUNEIFORM_SIGN_EL 0x12096 #define UNICODE_CUNEIFORM_SIGN_EN 0x12097 #define UNICODE_CUNEIFORM_SIGN_EN_TIMES_GAN2 0x12098 #define UNICODE_CUNEIFORM_SIGN_EN_TIMES_GAN2_TENU 0x12099 #define UNICODE_CUNEIFORM_SIGN_EN_TIMES_ME 0x1209a #define UNICODE_CUNEIFORM_SIGN_EN_CROSSING_EN 0x1209b #define UNICODE_CUNEIFORM_SIGN_EN_OPPOSING_EN 0x1209c #define UNICODE_CUNEIFORM_SIGN_EN_SQUARED 0x1209d #define UNICODE_CUNEIFORM_SIGN_EREN 0x1209e #define UNICODE_CUNEIFORM_SIGN_ERIN2 0x1209f #define UNICODE_CUNEIFORM_SIGN_ESH2 0x120a0 #define UNICODE_CUNEIFORM_SIGN_EZEN 0x120a1 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_A 0x120a2 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_A_PLUS_LAL 0x120a3 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_A_PLUS_LAL_TIMES_LAL 0x120a4 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_AN 0x120a5 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_BAD 0x120a6 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_DUN3_GUNU 0x120a7 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_DUN3_GUNU_GUNU 0x120a8 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_HA 0x120a9 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_HA_GUNU 0x120aa #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_IGI_GUNU 0x120ab #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_KASKAL 0x120ac #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_KASKAL_SQUARED 0x120ad #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_KU3 0x120ae #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_LA 0x120af #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_LAL_TIMES_LAL 0x120b0 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_LI 0x120b1 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_LU 0x120b2 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_U2 0x120b3 #define UNICODE_CUNEIFORM_SIGN_EZEN_TIMES_UD 0x120b4 #define UNICODE_CUNEIFORM_SIGN_GA 0x120b5 #define UNICODE_CUNEIFORM_SIGN_GA_GUNU 0x120b6 #define UNICODE_CUNEIFORM_SIGN_GA2 0x120b7 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_A_PLUS_DA_PLUS_HA 0x120b8 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_A_PLUS_HA 0x120b9 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_A_PLUS_IGI 0x120ba #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_AB2_TENU_PLUS_TAB 0x120bb #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_AN 0x120bc #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_ASH 0x120bd #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_ASH2_PLUS_GAL 0x120be #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_BAD 0x120bf #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_BAR_PLUS_RA 0x120c0 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_BUR 0x120c1 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_BUR_PLUS_RA 0x120c2 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_DA 0x120c3 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_DI 0x120c4 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_DIM_TIMES_SHE 0x120c5 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_DUB 0x120c6 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_EL 0x120c7 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_EL_PLUS_LA 0x120c8 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_EN 0x120c9 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_EN_TIMES_GAN2_TENU 0x120ca #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_GAN2_TENU 0x120cb #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_GAR 0x120cc #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_GI 0x120cd #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_GI4 0x120ce #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_GI4_PLUS_A 0x120cf #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_GIR2_PLUS_SU 0x120d0 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_HA_PLUS_LU_PLUS_ESH2 0x120d1 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_HAL 0x120d2 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_HAL_PLUS_LA 0x120d3 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_HI_PLUS_LI 0x120d4 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_HUB2 0x120d5 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_IGI_GUNU 0x120d6 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_ISH_PLUS_HU_PLUS_ASH 0x120d7 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_KAK 0x120d8 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_KASKAL 0x120d9 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_KID 0x120da #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_KID_PLUS_LAL 0x120db #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_KU3_PLUS_AN 0x120dc #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_LA 0x120dd #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_ME_PLUS_EN 0x120de #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_MI 0x120df #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_NUN 0x120e0 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_NUN_OVER_NUN 0x120e1 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_PA 0x120e2 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_SAL 0x120e3 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_SAR 0x120e4 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_SHE 0x120e5 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_SHE_PLUS_TUR 0x120e6 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_SHID 0x120e7 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_SUM 0x120e8 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_TAK4 0x120e9 #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_U 0x120ea #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_UD 0x120eb #define UNICODE_CUNEIFORM_SIGN_GA2_TIMES_UD_PLUS_DU 0x120ec #define UNICODE_CUNEIFORM_SIGN_GA2_OVER_GA2 0x120ed #define UNICODE_CUNEIFORM_SIGN_GABA 0x120ee #define UNICODE_CUNEIFORM_SIGN_GABA_CROSSING_GABA 0x120ef #define UNICODE_CUNEIFORM_SIGN_GAD 0x120f0 #define UNICODE_CUNEIFORM_SIGN_GAD_OVER_GAD_GAR_OVER_GAR 0x120f1 #define UNICODE_CUNEIFORM_SIGN_GAL 0x120f2 #define UNICODE_CUNEIFORM_SIGN_GAL_GAD_OVER_GAD_GAR_OVER_GAR 0x120f3 #define UNICODE_CUNEIFORM_SIGN_GALAM 0x120f4 #define UNICODE_CUNEIFORM_SIGN_GAM 0x120f5 #define UNICODE_CUNEIFORM_SIGN_GAN 0x120f6 #define UNICODE_CUNEIFORM_SIGN_GAN2 0x120f7 #define UNICODE_CUNEIFORM_SIGN_GAN2_TENU 0x120f8 #define UNICODE_CUNEIFORM_SIGN_GAN2_OVER_GAN2 0x120f9 #define UNICODE_CUNEIFORM_SIGN_GAN2_CROSSING_GAN2 0x120fa #define UNICODE_CUNEIFORM_SIGN_GAR 0x120fb #define UNICODE_CUNEIFORM_SIGN_GAR3 0x120fc #define UNICODE_CUNEIFORM_SIGN_GASHAN 0x120fd #define UNICODE_CUNEIFORM_SIGN_GESHTIN 0x120fe #define UNICODE_CUNEIFORM_SIGN_GESHTIN_TIMES_KUR 0x120ff #define UNICODE_CUNEIFORM_SIGN_GI 0x12100 #define UNICODE_CUNEIFORM_SIGN_GI_TIMES_E 0x12101 #define UNICODE_CUNEIFORM_SIGN_GI_TIMES_U 0x12102 #define UNICODE_CUNEIFORM_SIGN_GI_CROSSING_GI 0x12103 #define UNICODE_CUNEIFORM_SIGN_GI4 0x12104 #define UNICODE_CUNEIFORM_SIGN_GI4_OVER_GI4 0x12105 #define UNICODE_CUNEIFORM_SIGN_GI4_CROSSING_GI4 0x12106 #define UNICODE_CUNEIFORM_SIGN_GIDIM 0x12107 #define UNICODE_CUNEIFORM_SIGN_GIR2 0x12108 #define UNICODE_CUNEIFORM_SIGN_GIR2_GUNU 0x12109 #define UNICODE_CUNEIFORM_SIGN_GIR3 0x1210a #define UNICODE_CUNEIFORM_SIGN_GIR3_TIMES_A_PLUS_IGI 0x1210b #define UNICODE_CUNEIFORM_SIGN_GIR3_TIMES_GAN2_TENU 0x1210c #define UNICODE_CUNEIFORM_SIGN_GIR3_TIMES_IGI 0x1210d #define UNICODE_CUNEIFORM_SIGN_GIR3_TIMES_LU_PLUS_IGI 0x1210e #define UNICODE_CUNEIFORM_SIGN_GIR3_TIMES_PA 0x1210f #define UNICODE_CUNEIFORM_SIGN_GISAL 0x12110 #define UNICODE_CUNEIFORM_SIGN_GISH 0x12111 #define UNICODE_CUNEIFORM_SIGN_GISH_CROSSING_GISH 0x12112 #define UNICODE_CUNEIFORM_SIGN_GISH_TIMES_BAD 0x12113 #define UNICODE_CUNEIFORM_SIGN_GISH_TIMES_TAK4 0x12114 #define UNICODE_CUNEIFORM_SIGN_GISH_TENU 0x12115 #define UNICODE_CUNEIFORM_SIGN_GU 0x12116 #define UNICODE_CUNEIFORM_SIGN_GU_CROSSING_GU 0x12117 #define UNICODE_CUNEIFORM_SIGN_GU2 0x12118 #define UNICODE_CUNEIFORM_SIGN_GU2_TIMES_KAK 0x12119 #define UNICODE_CUNEIFORM_SIGN_GU2_TIMES_KAK_TIMES_IGI_GUNU 0x1211a #define UNICODE_CUNEIFORM_SIGN_GU2_TIMES_NUN 0x1211b #define UNICODE_CUNEIFORM_SIGN_GU2_TIMES_SAL_PLUS_TUG2 0x1211c #define UNICODE_CUNEIFORM_SIGN_GU2_GUNU 0x1211d #define UNICODE_CUNEIFORM_SIGN_GUD 0x1211e #define UNICODE_CUNEIFORM_SIGN_GUD_TIMES_A_PLUS_KUR 0x1211f #define UNICODE_CUNEIFORM_SIGN_GUD_TIMES_KUR 0x12120 #define UNICODE_CUNEIFORM_SIGN_GUD_OVER_GUD_LUGAL 0x12121 #define UNICODE_CUNEIFORM_SIGN_GUL 0x12122 #define UNICODE_CUNEIFORM_SIGN_GUM 0x12123 #define UNICODE_CUNEIFORM_SIGN_GUM_TIMES_SHE 0x12124 #define UNICODE_CUNEIFORM_SIGN_GUR 0x12125 #define UNICODE_CUNEIFORM_SIGN_GUR7 0x12126 #define UNICODE_CUNEIFORM_SIGN_GURUN 0x12127 #define UNICODE_CUNEIFORM_SIGN_GURUSH 0x12128 #define UNICODE_CUNEIFORM_SIGN_HA 0x12129 #define UNICODE_CUNEIFORM_SIGN_HA_TENU 0x1212a #define UNICODE_CUNEIFORM_SIGN_HA_GUNU 0x1212b #define UNICODE_CUNEIFORM_SIGN_HAL 0x1212c #define UNICODE_CUNEIFORM_SIGN_HI 0x1212d #define UNICODE_CUNEIFORM_SIGN_HI_TIMES_ASH 0x1212e #define UNICODE_CUNEIFORM_SIGN_HI_TIMES_ASH2 0x1212f #define UNICODE_CUNEIFORM_SIGN_HI_TIMES_BAD 0x12130 #define UNICODE_CUNEIFORM_SIGN_HI_TIMES_DISH 0x12131 #define UNICODE_CUNEIFORM_SIGN_HI_TIMES_GAD 0x12132 #define UNICODE_CUNEIFORM_SIGN_HI_TIMES_KIN 0x12133 #define UNICODE_CUNEIFORM_SIGN_HI_TIMES_NUN 0x12134 #define UNICODE_CUNEIFORM_SIGN_HI_TIMES_SHE 0x12135 #define UNICODE_CUNEIFORM_SIGN_HI_TIMES_U 0x12136 #define UNICODE_CUNEIFORM_SIGN_HU 0x12137 #define UNICODE_CUNEIFORM_SIGN_HUB2 0x12138 #define UNICODE_CUNEIFORM_SIGN_HUB2_TIMES_AN 0x12139 #define UNICODE_CUNEIFORM_SIGN_HUB2_TIMES_HAL 0x1213a #define UNICODE_CUNEIFORM_SIGN_HUB2_TIMES_KASKAL 0x1213b #define UNICODE_CUNEIFORM_SIGN_HUB2_TIMES_LISH 0x1213c #define UNICODE_CUNEIFORM_SIGN_HUB2_TIMES_UD 0x1213d #define UNICODE_CUNEIFORM_SIGN_HUL2 0x1213e #define UNICODE_CUNEIFORM_SIGN_I 0x1213f #define UNICODE_CUNEIFORM_SIGN_I_A 0x12140 #define UNICODE_CUNEIFORM_SIGN_IB 0x12141 #define UNICODE_CUNEIFORM_SIGN_IDIM 0x12142 #define UNICODE_CUNEIFORM_SIGN_IDIM_OVER_IDIM_BUR 0x12143 #define UNICODE_CUNEIFORM_SIGN_IDIM_OVER_IDIM_SQUARED 0x12144 #define UNICODE_CUNEIFORM_SIGN_IG 0x12145 #define UNICODE_CUNEIFORM_SIGN_IGI 0x12146 #define UNICODE_CUNEIFORM_SIGN_IGI_DIB 0x12147 #define UNICODE_CUNEIFORM_SIGN_IGI_RI 0x12148 #define UNICODE_CUNEIFORM_SIGN_IGI_OVER_IGI_SHIR_OVER_SHIR_UD_OVER_UD 0x12149 #define UNICODE_CUNEIFORM_SIGN_IGI_GUNU 0x1214a #define UNICODE_CUNEIFORM_SIGN_IL 0x1214b #define UNICODE_CUNEIFORM_SIGN_IL_TIMES_GAN2_TENU 0x1214c #define UNICODE_CUNEIFORM_SIGN_IL2 0x1214d #define UNICODE_CUNEIFORM_SIGN_IM 0x1214e #define UNICODE_CUNEIFORM_SIGN_IM_TIMES_TAK4 0x1214f #define UNICODE_CUNEIFORM_SIGN_IM_CROSSING_IM 0x12150 #define UNICODE_CUNEIFORM_SIGN_IM_OPPOSING_IM 0x12151 #define UNICODE_CUNEIFORM_SIGN_IM_SQUARED 0x12152 #define UNICODE_CUNEIFORM_SIGN_IMIN 0x12153 #define UNICODE_CUNEIFORM_SIGN_IN 0x12154 #define UNICODE_CUNEIFORM_SIGN_IR 0x12155 #define UNICODE_CUNEIFORM_SIGN_ISH 0x12156 #define UNICODE_CUNEIFORM_SIGN_KA 0x12157 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_A 0x12158 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_AD 0x12159 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_AD_PLUS_KU3 0x1215a #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_ASH2 0x1215b #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_BAD 0x1215c #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_BALAG 0x1215d #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_BAR 0x1215e #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_BI 0x1215f #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_ERIN2 0x12160 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_ESH2 0x12161 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GA 0x12162 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GAL 0x12163 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GAN2_TENU 0x12164 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GAR 0x12165 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GAR_PLUS_SHA3_PLUS_A 0x12166 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GI 0x12167 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GIR2 0x12168 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GISH_PLUS_SAR 0x12169 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GISH_CROSSING_GISH 0x1216a #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GU 0x1216b #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_GUR7 0x1216c #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_IGI 0x1216d #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_IM 0x1216e #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_KAK 0x1216f #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_KI 0x12170 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_KID 0x12171 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_LI 0x12172 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_LU 0x12173 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_ME 0x12174 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_ME_PLUS_DU 0x12175 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_ME_PLUS_GI 0x12176 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_ME_PLUS_TE 0x12177 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_MI 0x12178 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_MI_PLUS_NUNUZ 0x12179 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_NE 0x1217a #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_NUN 0x1217b #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_PI 0x1217c #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_RU 0x1217d #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_SA 0x1217e #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_SAR 0x1217f #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_SHA 0x12180 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_SHE 0x12181 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_SHID 0x12182 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_SHU 0x12183 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_SIG 0x12184 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_SUHUR 0x12185 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_TAR 0x12186 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_U 0x12187 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_U2 0x12188 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_UD 0x12189 #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_UMUM_TIMES_PA 0x1218a #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_USH 0x1218b #define UNICODE_CUNEIFORM_SIGN_KA_TIMES_ZI 0x1218c #define UNICODE_CUNEIFORM_SIGN_KA2 0x1218d #define UNICODE_CUNEIFORM_SIGN_KA2_CROSSING_KA2 0x1218e #define UNICODE_CUNEIFORM_SIGN_KAB 0x1218f #define UNICODE_CUNEIFORM_SIGN_KAD2 0x12190 #define UNICODE_CUNEIFORM_SIGN_KAD3 0x12191 #define UNICODE_CUNEIFORM_SIGN_KAD4 0x12192 #define UNICODE_CUNEIFORM_SIGN_KAD5 0x12193 #define UNICODE_CUNEIFORM_SIGN_KAD5_OVER_KAD5 0x12194 #define UNICODE_CUNEIFORM_SIGN_KAK 0x12195 #define UNICODE_CUNEIFORM_SIGN_KAK_TIMES_IGI_GUNU 0x12196 #define UNICODE_CUNEIFORM_SIGN_KAL 0x12197 #define UNICODE_CUNEIFORM_SIGN_KAL_TIMES_BAD 0x12198 #define UNICODE_CUNEIFORM_SIGN_KAL_CROSSING_KAL 0x12199 #define UNICODE_CUNEIFORM_SIGN_KAM2 0x1219a #define UNICODE_CUNEIFORM_SIGN_KAM4 0x1219b #define UNICODE_CUNEIFORM_SIGN_KASKAL 0x1219c #define UNICODE_CUNEIFORM_SIGN_KASKAL_LAGAB_TIMES_U_OVER_LAGAB_TIMES_U 0x1219d #define UNICODE_CUNEIFORM_SIGN_KASKAL_OVER_KASKAL_LAGAB_TIMES_U_OVER_LAGAB_TIMES_U 0x1219e #define UNICODE_CUNEIFORM_SIGN_KESH2 0x1219f #define UNICODE_CUNEIFORM_SIGN_KI 0x121a0 #define UNICODE_CUNEIFORM_SIGN_KI_TIMES_BAD 0x121a1 #define UNICODE_CUNEIFORM_SIGN_KI_TIMES_U 0x121a2 #define UNICODE_CUNEIFORM_SIGN_KI_TIMES_UD 0x121a3 #define UNICODE_CUNEIFORM_SIGN_KID 0x121a4 #define UNICODE_CUNEIFORM_SIGN_KIN 0x121a5 #define UNICODE_CUNEIFORM_SIGN_KISAL 0x121a6 #define UNICODE_CUNEIFORM_SIGN_KISH 0x121a7 #define UNICODE_CUNEIFORM_SIGN_KISIM5 0x121a8 #define UNICODE_CUNEIFORM_SIGN_KISIM5_OVER_KISIM5 0x121a9 #define UNICODE_CUNEIFORM_SIGN_KU 0x121aa #define UNICODE_CUNEIFORM_SIGN_KU_OVER_HI_TIMES_ASH2_KU_OVER_HI_TIMES_ASH2 0x121ab #define UNICODE_CUNEIFORM_SIGN_KU3 0x121ac #define UNICODE_CUNEIFORM_SIGN_KU4 0x121ad #define UNICODE_CUNEIFORM_SIGN_KU4_VARIANT_FORM 0x121ae #define UNICODE_CUNEIFORM_SIGN_KU7 0x121af #define UNICODE_CUNEIFORM_SIGN_KUL 0x121b0 #define UNICODE_CUNEIFORM_SIGN_KUL_GUNU 0x121b1 #define UNICODE_CUNEIFORM_SIGN_KUN 0x121b2 #define UNICODE_CUNEIFORM_SIGN_KUR 0x121b3 #define UNICODE_CUNEIFORM_SIGN_KUR_OPPOSING_KUR 0x121b4 #define UNICODE_CUNEIFORM_SIGN_KUSHU2 0x121b5 #define UNICODE_CUNEIFORM_SIGN_KWU318 0x121b6 #define UNICODE_CUNEIFORM_SIGN_LA 0x121b7 #define UNICODE_CUNEIFORM_SIGN_LAGAB 0x121b8 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_A 0x121b9 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_A_PLUS_DA_PLUS_HA 0x121ba #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_A_PLUS_GAR 0x121bb #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_A_PLUS_LAL 0x121bc #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_AL 0x121bd #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_AN 0x121be #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_ASH_ZIDA_TENU 0x121bf #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_BAD 0x121c0 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_BI 0x121c1 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_DAR 0x121c2 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_EN 0x121c3 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_GA 0x121c4 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_GAR 0x121c5 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_GUD 0x121c6 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_GUD_PLUS_GUD 0x121c7 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_HA 0x121c8 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_HAL 0x121c9 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_HI_TIMES_NUN 0x121ca #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_IGI_GUNU 0x121cb #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_IM 0x121cc #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_IM_PLUS_HA 0x121cd #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_IM_PLUS_LU 0x121ce #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_KI 0x121cf #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_KIN 0x121d0 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_KU3 0x121d1 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_KUL 0x121d2 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_KUL_PLUS_HI_PLUS_A 0x121d3 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_LAGAB 0x121d4 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_LISH 0x121d5 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_LU 0x121d6 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_LUL 0x121d7 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_ME 0x121d8 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_ME_PLUS_EN 0x121d9 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_MUSH 0x121da #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_NE 0x121db #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_SHE_PLUS_SUM 0x121dc #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_SHITA_PLUS_GISH_PLUS_ERIN2 0x121dd #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_SHITA_PLUS_GISH_TENU 0x121de #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_SHU2 0x121df #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_SHU2_PLUS_SHU2 0x121e0 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_SUM 0x121e1 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_TAG 0x121e2 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_TAK4 0x121e3 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_TE_PLUS_A_PLUS_SU_PLUS_NA 0x121e4 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_U 0x121e5 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_U_PLUS_A 0x121e6 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_U_PLUS_U_PLUS_U 0x121e7 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_U2_PLUS_ASH 0x121e8 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_UD 0x121e9 #define UNICODE_CUNEIFORM_SIGN_LAGAB_TIMES_USH 0x121ea #define UNICODE_CUNEIFORM_SIGN_LAGAB_SQUARED 0x121eb #define UNICODE_CUNEIFORM_SIGN_LAGAR 0x121ec #define UNICODE_CUNEIFORM_SIGN_LAGAR_TIMES_SHE 0x121ed #define UNICODE_CUNEIFORM_SIGN_LAGAR_TIMES_SHE_PLUS_SUM 0x121ee #define UNICODE_CUNEIFORM_SIGN_LAGAR_GUNU 0x121ef #define UNICODE_CUNEIFORM_SIGN_LAGAR_GUNU_OVER_LAGAR_GUNU_SHE 0x121f0 #define UNICODE_CUNEIFORM_SIGN_LAHSHU 0x121f1 #define UNICODE_CUNEIFORM_SIGN_LAL 0x121f2 #define UNICODE_CUNEIFORM_SIGN_LAL_TIMES_LAL 0x121f3 #define UNICODE_CUNEIFORM_SIGN_LAM 0x121f4 #define UNICODE_CUNEIFORM_SIGN_LAM_TIMES_KUR 0x121f5 #define UNICODE_CUNEIFORM_SIGN_LAM_TIMES_KUR_PLUS_RU 0x121f6 #define UNICODE_CUNEIFORM_SIGN_LI 0x121f7 #define UNICODE_CUNEIFORM_SIGN_LIL 0x121f8 #define UNICODE_CUNEIFORM_SIGN_LIMMU2 0x121f9 #define UNICODE_CUNEIFORM_SIGN_LISH 0x121fa #define UNICODE_CUNEIFORM_SIGN_LU 0x121fb #define UNICODE_CUNEIFORM_SIGN_LU_TIMES_BAD 0x121fc #define UNICODE_CUNEIFORM_SIGN_LU2 0x121fd #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_AL 0x121fe #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_BAD 0x121ff #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_ESH2 0x12200 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_ESH2_TENU 0x12201 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_GAN2_TENU 0x12202 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_HI_TIMES_BAD 0x12203 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_IM 0x12204 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_KAD2 0x12205 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_KAD3 0x12206 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_KAD3_PLUS_ASH 0x12207 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_KI 0x12208 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_LA_PLUS_ASH 0x12209 #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_LAGAB 0x1220a #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_ME_PLUS_EN 0x1220b #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_NE 0x1220c #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_NU 0x1220d #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_SI_PLUS_ASH 0x1220e #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_SIK2_PLUS_BU 0x1220f #define UNICODE_CUNEIFORM_SIGN_LU2_TIMES_TUG2 0x12210 #define UNICODE_CUNEIFORM_SIGN_LU2_TENU 0x12211 #define UNICODE_CUNEIFORM_SIGN_LU2_CROSSING_LU2 0x12212 #define UNICODE_CUNEIFORM_SIGN_LU2_OPPOSING_LU2 0x12213 #define UNICODE_CUNEIFORM_SIGN_LU2_SQUARED 0x12214 #define UNICODE_CUNEIFORM_SIGN_LU2_SHESHIG 0x12215 #define UNICODE_CUNEIFORM_SIGN_LU3 0x12216 #define UNICODE_CUNEIFORM_SIGN_LUGAL 0x12217 #define UNICODE_CUNEIFORM_SIGN_LUGAL_OVER_LUGAL 0x12218 #define UNICODE_CUNEIFORM_SIGN_LUGAL_OPPOSING_LUGAL 0x12219 #define UNICODE_CUNEIFORM_SIGN_LUGAL_SHESHIG 0x1221a #define UNICODE_CUNEIFORM_SIGN_LUH 0x1221b #define UNICODE_CUNEIFORM_SIGN_LUL 0x1221c #define UNICODE_CUNEIFORM_SIGN_LUM 0x1221d #define UNICODE_CUNEIFORM_SIGN_LUM_OVER_LUM 0x1221e #define UNICODE_CUNEIFORM_SIGN_LUM_OVER_LUM_GAR_OVER_GAR 0x1221f #define UNICODE_CUNEIFORM_SIGN_MA 0x12220 #define UNICODE_CUNEIFORM_SIGN_MA_TIMES_TAK4 0x12221 #define UNICODE_CUNEIFORM_SIGN_MA_GUNU 0x12222 #define UNICODE_CUNEIFORM_SIGN_MA2 0x12223 #define UNICODE_CUNEIFORM_SIGN_MAH 0x12224 #define UNICODE_CUNEIFORM_SIGN_MAR 0x12225 #define UNICODE_CUNEIFORM_SIGN_MASH 0x12226 #define UNICODE_CUNEIFORM_SIGN_MASH2 0x12227 #define UNICODE_CUNEIFORM_SIGN_ME 0x12228 #define UNICODE_CUNEIFORM_SIGN_MES 0x12229 #define UNICODE_CUNEIFORM_SIGN_MI 0x1222a #define UNICODE_CUNEIFORM_SIGN_MIN 0x1222b #define UNICODE_CUNEIFORM_SIGN_MU 0x1222c #define UNICODE_CUNEIFORM_SIGN_MU_OVER_MU 0x1222d #define UNICODE_CUNEIFORM_SIGN_MUG 0x1222e #define UNICODE_CUNEIFORM_SIGN_MUG_GUNU 0x1222f #define UNICODE_CUNEIFORM_SIGN_MUNSUB 0x12230 #define UNICODE_CUNEIFORM_SIGN_MURGU2 0x12231 #define UNICODE_CUNEIFORM_SIGN_MUSH 0x12232 #define UNICODE_CUNEIFORM_SIGN_MUSH_TIMES_A 0x12233 #define UNICODE_CUNEIFORM_SIGN_MUSH_TIMES_KUR 0x12234 #define UNICODE_CUNEIFORM_SIGN_MUSH_TIMES_ZA 0x12235 #define UNICODE_CUNEIFORM_SIGN_MUSH_OVER_MUSH 0x12236 #define UNICODE_CUNEIFORM_SIGN_MUSH_OVER_MUSH_TIMES_A_PLUS_NA 0x12237 #define UNICODE_CUNEIFORM_SIGN_MUSH_CROSSING_MUSH 0x12238 #define UNICODE_CUNEIFORM_SIGN_MUSH3 0x12239 #define UNICODE_CUNEIFORM_SIGN_MUSH3_TIMES_A 0x1223a #define UNICODE_CUNEIFORM_SIGN_MUSH3_TIMES_A_PLUS_DI 0x1223b #define UNICODE_CUNEIFORM_SIGN_MUSH3_TIMES_DI 0x1223c #define UNICODE_CUNEIFORM_SIGN_MUSH3_GUNU 0x1223d #define UNICODE_CUNEIFORM_SIGN_NA 0x1223e #define UNICODE_CUNEIFORM_SIGN_NA2 0x1223f #define UNICODE_CUNEIFORM_SIGN_NAGA 0x12240 #define UNICODE_CUNEIFORM_SIGN_NAGA_INVERTED 0x12241 #define UNICODE_CUNEIFORM_SIGN_NAGA_TIMES_SHU_TENU 0x12242 #define UNICODE_CUNEIFORM_SIGN_NAGA_OPPOSING_NAGA 0x12243 #define UNICODE_CUNEIFORM_SIGN_NAGAR 0x12244 #define UNICODE_CUNEIFORM_SIGN_NAM_NUTILLU 0x12245 #define UNICODE_CUNEIFORM_SIGN_NAM 0x12246 #define UNICODE_CUNEIFORM_SIGN_NAM2 0x12247 #define UNICODE_CUNEIFORM_SIGN_NE 0x12248 #define UNICODE_CUNEIFORM_SIGN_NE_TIMES_A 0x12249 #define UNICODE_CUNEIFORM_SIGN_NE_TIMES_UD 0x1224a #define UNICODE_CUNEIFORM_SIGN_NE_SHESHIG 0x1224b #define UNICODE_CUNEIFORM_SIGN_NI 0x1224c #define UNICODE_CUNEIFORM_SIGN_NI_TIMES_E 0x1224d #define UNICODE_CUNEIFORM_SIGN_NI2 0x1224e #define UNICODE_CUNEIFORM_SIGN_NIM 0x1224f #define UNICODE_CUNEIFORM_SIGN_NIM_TIMES_GAN2_TENU 0x12250 #define UNICODE_CUNEIFORM_SIGN_NIM_TIMES_GAR_PLUS_GAN2_TENU 0x12251 #define UNICODE_CUNEIFORM_SIGN_NINDA2 0x12252 #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_AN 0x12253 #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_ASH 0x12254 #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_ASH_PLUS_ASH 0x12255 #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_GUD 0x12256 #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_ME_PLUS_GAN2_TENU 0x12257 #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_NE 0x12258 #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_NUN 0x12259 #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_SHE 0x1225a #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_SHE_PLUS_A_AN 0x1225b #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_SHE_PLUS_ASH 0x1225c #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_SHE_PLUS_ASH_PLUS_ASH 0x1225d #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_U2_PLUS_ASH 0x1225e #define UNICODE_CUNEIFORM_SIGN_NINDA2_TIMES_USH 0x1225f #define UNICODE_CUNEIFORM_SIGN_NISAG 0x12260 #define UNICODE_CUNEIFORM_SIGN_NU 0x12261 #define UNICODE_CUNEIFORM_SIGN_NU11 0x12262 #define UNICODE_CUNEIFORM_SIGN_NUN 0x12263 #define UNICODE_CUNEIFORM_SIGN_NUN_LAGAR_TIMES_GAR 0x12264 #define UNICODE_CUNEIFORM_SIGN_NUN_LAGAR_TIMES_MASH 0x12265 #define UNICODE_CUNEIFORM_SIGN_NUN_LAGAR_TIMES_SAL 0x12266 #define UNICODE_CUNEIFORM_SIGN_NUN_LAGAR_TIMES_SAL_OVER_NUN_LAGAR_TIMES_SAL 0x12267 #define UNICODE_CUNEIFORM_SIGN_NUN_LAGAR_TIMES_USH 0x12268 #define UNICODE_CUNEIFORM_SIGN_NUN_TENU 0x12269 #define UNICODE_CUNEIFORM_SIGN_NUN_OVER_NUN 0x1226a #define UNICODE_CUNEIFORM_SIGN_NUN_CROSSING_NUN 0x1226b #define UNICODE_CUNEIFORM_SIGN_NUN_CROSSING_NUN_LAGAR_OVER_LAGAR 0x1226c #define UNICODE_CUNEIFORM_SIGN_NUNUZ 0x1226d #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_ASHGAB 0x1226e #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_BI 0x1226f #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_DUG 0x12270 #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_GUD 0x12271 #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_IGI_GUNU 0x12272 #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_KAD3 0x12273 #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_LA 0x12274 #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_NE 0x12275 #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_SILA3 0x12276 #define UNICODE_CUNEIFORM_SIGN_NUNUZ_AB2_TIMES_U2 0x12277 #define UNICODE_CUNEIFORM_SIGN_NUNUZ_KISIM5_TIMES_BI 0x12278 #define UNICODE_CUNEIFORM_SIGN_NUNUZ_KISIM5_TIMES_BI_U 0x12279 #define UNICODE_CUNEIFORM_SIGN_PA 0x1227a #define UNICODE_CUNEIFORM_SIGN_PAD 0x1227b #define UNICODE_CUNEIFORM_SIGN_PAN 0x1227c #define UNICODE_CUNEIFORM_SIGN_PAP 0x1227d #define UNICODE_CUNEIFORM_SIGN_PESH2 0x1227e #define UNICODE_CUNEIFORM_SIGN_PI 0x1227f #define UNICODE_CUNEIFORM_SIGN_PI_TIMES_A 0x12280 #define UNICODE_CUNEIFORM_SIGN_PI_TIMES_AB 0x12281 #define UNICODE_CUNEIFORM_SIGN_PI_TIMES_BI 0x12282 #define UNICODE_CUNEIFORM_SIGN_PI_TIMES_BU 0x12283 #define UNICODE_CUNEIFORM_SIGN_PI_TIMES_E 0x12284 #define UNICODE_CUNEIFORM_SIGN_PI_TIMES_I 0x12285 #define UNICODE_CUNEIFORM_SIGN_PI_TIMES_IB 0x12286 #define UNICODE_CUNEIFORM_SIGN_PI_TIMES_U 0x12287 #define UNICODE_CUNEIFORM_SIGN_PI_TIMES_U2 0x12288 #define UNICODE_CUNEIFORM_SIGN_PI_CROSSING_PI 0x12289 #define UNICODE_CUNEIFORM_SIGN_PIRIG 0x1228a #define UNICODE_CUNEIFORM_SIGN_PIRIG_TIMES_KAL 0x1228b #define UNICODE_CUNEIFORM_SIGN_PIRIG_TIMES_UD 0x1228c #define UNICODE_CUNEIFORM_SIGN_PIRIG_TIMES_ZA 0x1228d #define UNICODE_CUNEIFORM_SIGN_PIRIG_OPPOSING_PIRIG 0x1228e #define UNICODE_CUNEIFORM_SIGN_RA 0x1228f #define UNICODE_CUNEIFORM_SIGN_RAB 0x12290 #define UNICODE_CUNEIFORM_SIGN_RI 0x12291 #define UNICODE_CUNEIFORM_SIGN_RU 0x12292 #define UNICODE_CUNEIFORM_SIGN_SA 0x12293 #define UNICODE_CUNEIFORM_SIGN_SAG_NUTILLU 0x12294 #define UNICODE_CUNEIFORM_SIGN_SAG 0x12295 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_A 0x12296 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_DU 0x12297 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_DUB 0x12298 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_HA 0x12299 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_KAK 0x1229a #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_KUR 0x1229b #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_LUM 0x1229c #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_MI 0x1229d #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_NUN 0x1229e #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_SAL 0x1229f #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_SHID 0x122a0 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_TAB 0x122a1 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_U2 0x122a2 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_UB 0x122a3 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_UM 0x122a4 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_UR 0x122a5 #define UNICODE_CUNEIFORM_SIGN_SAG_TIMES_USH 0x122a6 #define UNICODE_CUNEIFORM_SIGN_SAG_OVER_SAG 0x122a7 #define UNICODE_CUNEIFORM_SIGN_SAG_GUNU 0x122a8 #define UNICODE_CUNEIFORM_SIGN_SAL 0x122a9 #define UNICODE_CUNEIFORM_SIGN_SAL_LAGAB_TIMES_ASH2 0x122aa #define UNICODE_CUNEIFORM_SIGN_SANGA2 0x122ab #define UNICODE_CUNEIFORM_SIGN_SAR 0x122ac #define UNICODE_CUNEIFORM_SIGN_SHA 0x122ad #define UNICODE_CUNEIFORM_SIGN_SHA3 0x122ae #define UNICODE_CUNEIFORM_SIGN_SHA3_TIMES_A 0x122af #define UNICODE_CUNEIFORM_SIGN_SHA3_TIMES_BAD 0x122b0 #define UNICODE_CUNEIFORM_SIGN_SHA3_TIMES_GISH 0x122b1 #define UNICODE_CUNEIFORM_SIGN_SHA3_TIMES_NE 0x122b2 #define UNICODE_CUNEIFORM_SIGN_SHA3_TIMES_SHU2 0x122b3 #define UNICODE_CUNEIFORM_SIGN_SHA3_TIMES_TUR 0x122b4 #define UNICODE_CUNEIFORM_SIGN_SHA3_TIMES_U 0x122b5 #define UNICODE_CUNEIFORM_SIGN_SHA3_TIMES_U_PLUS_A 0x122b6 #define UNICODE_CUNEIFORM_SIGN_SHA6 0x122b7 #define UNICODE_CUNEIFORM_SIGN_SHAB6 0x122b8 #define UNICODE_CUNEIFORM_SIGN_SHAR2 0x122b9 #define UNICODE_CUNEIFORM_SIGN_SHE 0x122ba #define UNICODE_CUNEIFORM_SIGN_SHE_HU 0x122bb #define UNICODE_CUNEIFORM_SIGN_SHE_OVER_SHE_GAD_OVER_GAD_GAR_OVER_GAR 0x122bc #define UNICODE_CUNEIFORM_SIGN_SHE_OVER_SHE_TAB_OVER_TAB_GAR_OVER_GAR 0x122bd #define UNICODE_CUNEIFORM_SIGN_SHEG9 0x122be #define UNICODE_CUNEIFORM_SIGN_SHEN 0x122bf #define UNICODE_CUNEIFORM_SIGN_SHESH 0x122c0 #define UNICODE_CUNEIFORM_SIGN_SHESH2 0x122c1 #define UNICODE_CUNEIFORM_SIGN_SHESHLAM 0x122c2 #define UNICODE_CUNEIFORM_SIGN_SHID 0x122c3 #define UNICODE_CUNEIFORM_SIGN_SHID_TIMES_A 0x122c4 #define UNICODE_CUNEIFORM_SIGN_SHID_TIMES_IM 0x122c5 #define UNICODE_CUNEIFORM_SIGN_SHIM 0x122c6 #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_A 0x122c7 #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_BAL 0x122c8 #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_BULUG 0x122c9 #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_DIN 0x122ca #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_GAR 0x122cb #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_IGI 0x122cc #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_IGI_GUNU 0x122cd #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_KUSHU2 0x122ce #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_LUL 0x122cf #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_MUG 0x122d0 #define UNICODE_CUNEIFORM_SIGN_SHIM_TIMES_SAL 0x122d1 #define UNICODE_CUNEIFORM_SIGN_SHINIG 0x122d2 #define UNICODE_CUNEIFORM_SIGN_SHIR 0x122d3 #define UNICODE_CUNEIFORM_SIGN_SHIR_TENU 0x122d4 #define UNICODE_CUNEIFORM_SIGN_SHIR_OVER_SHIR_BUR_OVER_BUR 0x122d5 #define UNICODE_CUNEIFORM_SIGN_SHITA 0x122d6 #define UNICODE_CUNEIFORM_SIGN_SHU 0x122d7 #define UNICODE_CUNEIFORM_SIGN_SHU_OVER_INVERTED_SHU 0x122d8 #define UNICODE_CUNEIFORM_SIGN_SHU2 0x122d9 #define UNICODE_CUNEIFORM_SIGN_SHUBUR 0x122da #define UNICODE_CUNEIFORM_SIGN_SI 0x122db #define UNICODE_CUNEIFORM_SIGN_SI_GUNU 0x122dc #define UNICODE_CUNEIFORM_SIGN_SIG 0x122dd #define UNICODE_CUNEIFORM_SIGN_SIG4 0x122de #define UNICODE_CUNEIFORM_SIGN_SIG4_OVER_SIG4_SHU2 0x122df #define UNICODE_CUNEIFORM_SIGN_SIK2 0x122e0 #define UNICODE_CUNEIFORM_SIGN_SILA3 0x122e1 #define UNICODE_CUNEIFORM_SIGN_SU 0x122e2 #define UNICODE_CUNEIFORM_SIGN_SU_OVER_SU 0x122e3 #define UNICODE_CUNEIFORM_SIGN_SUD 0x122e4 #define UNICODE_CUNEIFORM_SIGN_SUD2 0x122e5 #define UNICODE_CUNEIFORM_SIGN_SUHUR 0x122e6 #define UNICODE_CUNEIFORM_SIGN_SUM 0x122e7 #define UNICODE_CUNEIFORM_SIGN_SUMASH 0x122e8 #define UNICODE_CUNEIFORM_SIGN_SUR 0x122e9 #define UNICODE_CUNEIFORM_SIGN_SUR9 0x122ea #define UNICODE_CUNEIFORM_SIGN_TA 0x122eb #define UNICODE_CUNEIFORM_SIGN_TA_ASTERISK 0x122ec #define UNICODE_CUNEIFORM_SIGN_TA_TIMES_HI 0x122ed #define UNICODE_CUNEIFORM_SIGN_TA_TIMES_MI 0x122ee #define UNICODE_CUNEIFORM_SIGN_TA_GUNU 0x122ef #define UNICODE_CUNEIFORM_SIGN_TAB 0x122f0 #define UNICODE_CUNEIFORM_SIGN_TAB_OVER_TAB_NI_OVER_NI_DISH_OVER_DISH 0x122f1 #define UNICODE_CUNEIFORM_SIGN_TAB_SQUARED 0x122f2 #define UNICODE_CUNEIFORM_SIGN_TAG 0x122f3 #define UNICODE_CUNEIFORM_SIGN_TAG_TIMES_BI 0x122f4 #define UNICODE_CUNEIFORM_SIGN_TAG_TIMES_GUD 0x122f5 #define UNICODE_CUNEIFORM_SIGN_TAG_TIMES_SHE 0x122f6 #define UNICODE_CUNEIFORM_SIGN_TAG_TIMES_SHU 0x122f7 #define UNICODE_CUNEIFORM_SIGN_TAG_TIMES_TUG2 0x122f8 #define UNICODE_CUNEIFORM_SIGN_TAG_TIMES_UD 0x122f9 #define UNICODE_CUNEIFORM_SIGN_TAK4 0x122fa #define UNICODE_CUNEIFORM_SIGN_TAR 0x122fb #define UNICODE_CUNEIFORM_SIGN_TE 0x122fc #define UNICODE_CUNEIFORM_SIGN_TE_GUNU 0x122fd #define UNICODE_CUNEIFORM_SIGN_TI 0x122fe #define UNICODE_CUNEIFORM_SIGN_TI_TENU 0x122ff #define UNICODE_CUNEIFORM_SIGN_TIL 0x12300 #define UNICODE_CUNEIFORM_SIGN_TIR 0x12301 #define UNICODE_CUNEIFORM_SIGN_TIR_TIMES_TAK4 0x12302 #define UNICODE_CUNEIFORM_SIGN_TIR_OVER_TIR 0x12303 #define UNICODE_CUNEIFORM_SIGN_TIR_OVER_TIR_GAD_OVER_GAD_GAR_OVER_GAR 0x12304 #define UNICODE_CUNEIFORM_SIGN_TU 0x12305 #define UNICODE_CUNEIFORM_SIGN_TUG2 0x12306 #define UNICODE_CUNEIFORM_SIGN_TUK 0x12307 #define UNICODE_CUNEIFORM_SIGN_TUM 0x12308 #define UNICODE_CUNEIFORM_SIGN_TUR 0x12309 #define UNICODE_CUNEIFORM_SIGN_TUR_OVER_TUR_ZA_OVER_ZA 0x1230a #define UNICODE_CUNEIFORM_SIGN_U 0x1230b #define UNICODE_CUNEIFORM_SIGN_U_GUD 0x1230c #define UNICODE_CUNEIFORM_SIGN_U_U_U 0x1230d #define UNICODE_CUNEIFORM_SIGN_U_OVER_U_PA_OVER_PA_GAR_OVER_GAR 0x1230e #define UNICODE_CUNEIFORM_SIGN_U_OVER_U_SUR_OVER_SUR 0x1230f #define UNICODE_CUNEIFORM_SIGN_U_OVER_U_U_REVERSED_OVER_U_REVERSED 0x12310 #define UNICODE_CUNEIFORM_SIGN_U2 0x12311 #define UNICODE_CUNEIFORM_SIGN_UB 0x12312 #define UNICODE_CUNEIFORM_SIGN_UD 0x12313 #define UNICODE_CUNEIFORM_SIGN_UD_KUSHU2 0x12314 #define UNICODE_CUNEIFORM_SIGN_UD_TIMES_BAD 0x12315 #define UNICODE_CUNEIFORM_SIGN_UD_TIMES_MI 0x12316 #define UNICODE_CUNEIFORM_SIGN_UD_TIMES_U_PLUS_U_PLUS_U 0x12317 #define UNICODE_CUNEIFORM_SIGN_UD_TIMES_U_PLUS_U_PLUS_U_GUNU 0x12318 #define UNICODE_CUNEIFORM_SIGN_UD_GUNU 0x12319 #define UNICODE_CUNEIFORM_SIGN_UD_SHESHIG 0x1231a #define UNICODE_CUNEIFORM_SIGN_UD_SHESHIG_TIMES_BAD 0x1231b #define UNICODE_CUNEIFORM_SIGN_UDUG 0x1231c #define UNICODE_CUNEIFORM_SIGN_UM 0x1231d #define UNICODE_CUNEIFORM_SIGN_UM_TIMES_LAGAB 0x1231e #define UNICODE_CUNEIFORM_SIGN_UM_TIMES_ME_PLUS_DA 0x1231f #define UNICODE_CUNEIFORM_SIGN_UM_TIMES_SHA3 0x12320 #define UNICODE_CUNEIFORM_SIGN_UM_TIMES_U 0x12321 #define UNICODE_CUNEIFORM_SIGN_UMBIN 0x12322 #define UNICODE_CUNEIFORM_SIGN_UMUM 0x12323 #define UNICODE_CUNEIFORM_SIGN_UMUM_TIMES_KASKAL 0x12324 #define UNICODE_CUNEIFORM_SIGN_UMUM_TIMES_PA 0x12325 #define UNICODE_CUNEIFORM_SIGN_UN 0x12326 #define UNICODE_CUNEIFORM_SIGN_UN_GUNU 0x12327 #define UNICODE_CUNEIFORM_SIGN_UR 0x12328 #define UNICODE_CUNEIFORM_SIGN_UR_CROSSING_UR 0x12329 #define UNICODE_CUNEIFORM_SIGN_UR_SHESHIG 0x1232a #define UNICODE_CUNEIFORM_SIGN_UR2 0x1232b #define UNICODE_CUNEIFORM_SIGN_UR2_TIMES_A_PLUS_HA 0x1232c #define UNICODE_CUNEIFORM_SIGN_UR2_TIMES_A_PLUS_NA 0x1232d #define UNICODE_CUNEIFORM_SIGN_UR2_TIMES_AL 0x1232e #define UNICODE_CUNEIFORM_SIGN_UR2_TIMES_HA 0x1232f #define UNICODE_CUNEIFORM_SIGN_UR2_TIMES_NUN 0x12330 #define UNICODE_CUNEIFORM_SIGN_UR2_TIMES_U2 0x12331 #define UNICODE_CUNEIFORM_SIGN_UR2_TIMES_U2_PLUS_ASH 0x12332 #define UNICODE_CUNEIFORM_SIGN_UR2_TIMES_U2_PLUS_BI 0x12333 #define UNICODE_CUNEIFORM_SIGN_UR4 0x12334 #define UNICODE_CUNEIFORM_SIGN_URI 0x12335 #define UNICODE_CUNEIFORM_SIGN_URI3 0x12336 #define UNICODE_CUNEIFORM_SIGN_URU 0x12337 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_A 0x12338 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_ASHGAB 0x12339 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_BAR 0x1233a #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_DUN 0x1233b #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_GA 0x1233c #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_GAL 0x1233d #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_GAN2_TENU 0x1233e #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_GAR 0x1233f #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_GU 0x12340 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_HA 0x12341 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_IGI 0x12342 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_IM 0x12343 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_ISH 0x12344 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_KI 0x12345 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_LUM 0x12346 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_MIN 0x12347 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_PA 0x12348 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_SHE 0x12349 #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_SIG4 0x1234a #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_TU 0x1234b #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_U_PLUS_GUD 0x1234c #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_UD 0x1234d #define UNICODE_CUNEIFORM_SIGN_URU_TIMES_URUDA 0x1234e #define UNICODE_CUNEIFORM_SIGN_URUDA 0x1234f #define UNICODE_CUNEIFORM_SIGN_URUDA_TIMES_U 0x12350 #define UNICODE_CUNEIFORM_SIGN_USH 0x12351 #define UNICODE_CUNEIFORM_SIGN_USH_TIMES_A 0x12352 #define UNICODE_CUNEIFORM_SIGN_USH_TIMES_KU 0x12353 #define UNICODE_CUNEIFORM_SIGN_USH_TIMES_KUR 0x12354 #define UNICODE_CUNEIFORM_SIGN_USH_TIMES_TAK4 0x12355 #define UNICODE_CUNEIFORM_SIGN_USHX 0x12356 #define UNICODE_CUNEIFORM_SIGN_USH2 0x12357 #define UNICODE_CUNEIFORM_SIGN_USHUMX 0x12358 #define UNICODE_CUNEIFORM_SIGN_UTUKI 0x12359 #define UNICODE_CUNEIFORM_SIGN_UZ3 0x1235a #define UNICODE_CUNEIFORM_SIGN_UZ3_TIMES_KASKAL 0x1235b #define UNICODE_CUNEIFORM_SIGN_UZU 0x1235c #define UNICODE_CUNEIFORM_SIGN_ZA 0x1235d #define UNICODE_CUNEIFORM_SIGN_ZA_TENU 0x1235e #define UNICODE_CUNEIFORM_SIGN_ZA_SQUARED_TIMES_KUR 0x1235f #define UNICODE_CUNEIFORM_SIGN_ZAG 0x12360 #define UNICODE_CUNEIFORM_SIGN_ZAMX 0x12361 #define UNICODE_CUNEIFORM_SIGN_ZE2 0x12362 #define UNICODE_CUNEIFORM_SIGN_ZI 0x12363 #define UNICODE_CUNEIFORM_SIGN_ZI_OVER_ZI 0x12364 #define UNICODE_CUNEIFORM_SIGN_ZI3 0x12365 #define UNICODE_CUNEIFORM_SIGN_ZIB 0x12366 #define UNICODE_CUNEIFORM_SIGN_ZIB_KABA_TENU 0x12367 #define UNICODE_CUNEIFORM_SIGN_ZIG 0x12368 #define UNICODE_CUNEIFORM_SIGN_ZIZ2 0x12369 #define UNICODE_CUNEIFORM_SIGN_ZU 0x1236a #define UNICODE_CUNEIFORM_SIGN_ZU5 0x1236b #define UNICODE_CUNEIFORM_SIGN_ZU5_TIMES_A 0x1236c #define UNICODE_CUNEIFORM_SIGN_ZUBUR 0x1236d #define UNICODE_CUNEIFORM_SIGN_ZUM 0x1236e #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_ASH 0x12400 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_ASH 0x12401 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_ASH 0x12402 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_ASH 0x12403 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SIX_ASH 0x12404 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SEVEN_ASH 0x12405 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_EIGHT_ASH 0x12406 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NINE_ASH 0x12407 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_DISH 0x12408 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_DISH 0x12409 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_DISH 0x1240a #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SIX_DISH 0x1240b #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SEVEN_DISH 0x1240c #define UNICODE_CUNEIFORM_NUMERIC_SIGN_EIGHT_DISH 0x1240d #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NINE_DISH 0x1240e #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_U 0x1240f #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_U 0x12410 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SIX_U 0x12411 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SEVEN_U 0x12412 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_EIGHT_U 0x12413 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NINE_U 0x12414 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_GESH2 0x12415 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_GESH2 0x12416 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_GESH2 0x12417 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_GESH2 0x12418 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_GESH2 0x12419 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SIX_GESH2 0x1241a #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SEVEN_GESH2 0x1241b #define UNICODE_CUNEIFORM_NUMERIC_SIGN_EIGHT_GESH2 0x1241c #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NINE_GESH2 0x1241d #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_GESHU 0x1241e #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_GESHU 0x1241f #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_GESHU 0x12420 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_GESHU 0x12421 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_GESHU 0x12422 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_SHAR2 0x12423 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_SHAR2 0x12424 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_SHAR2_VARIANT_FORM 0x12425 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_SHAR2 0x12426 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_SHAR2 0x12427 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SIX_SHAR2 0x12428 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SEVEN_SHAR2 0x12429 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_EIGHT_SHAR2 0x1242a #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NINE_SHAR2 0x1242b #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_SHARU 0x1242c #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_SHARU 0x1242d #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_SHARU 0x1242e #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_SHARU_VARIANT_FORM 0x1242f #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_SHARU 0x12430 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_SHARU 0x12431 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SHAR2_TIMES_GAL_PLUS_DISH 0x12432 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SHAR2_TIMES_GAL_PLUS_MIN 0x12433 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_BURU 0x12434 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_BURU 0x12435 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_BURU 0x12436 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_BURU_VARIANT_FORM 0x12437 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_BURU 0x12438 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_BURU 0x12439 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_VARIANT_FORM_ESH16 0x1243a #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_VARIANT_FORM_ESH21 0x1243b #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_VARIANT_FORM_LIMMU 0x1243c #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_VARIANT_FORM_LIMMU4 0x1243d #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_VARIANT_FORM_LIMMU_A 0x1243e #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_VARIANT_FORM_LIMMU_B 0x1243f #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SIX_VARIANT_FORM_ASH9 0x12440 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SEVEN_VARIANT_FORM_IMIN3 0x12441 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SEVEN_VARIANT_FORM_IMIN_A 0x12442 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SEVEN_VARIANT_FORM_IMIN_B 0x12443 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_EIGHT_VARIANT_FORM_USSU 0x12444 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_EIGHT_VARIANT_FORM_USSU3 0x12445 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NINE_VARIANT_FORM_ILIMMU 0x12446 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NINE_VARIANT_FORM_ILIMMU3 0x12447 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NINE_VARIANT_FORM_ILIMMU4 0x12448 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NINE_VARIANT_FORM_ILIMMU_A 0x12449 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_ASH_TENU 0x1244a #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_ASH_TENU 0x1244b #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_ASH_TENU 0x1244c #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_ASH_TENU 0x1244d #define UNICODE_CUNEIFORM_NUMERIC_SIGN_SIX_ASH_TENU 0x1244e #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_BAN2 0x1244f #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_BAN2 0x12450 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_THREE_BAN2 0x12451 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_BAN2 0x12452 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FOUR_BAN2_VARIANT_FORM 0x12453 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_BAN2 0x12454 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_BAN2_VARIANT_FORM 0x12455 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NIGIDAMIN 0x12456 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_NIGIDAESH 0x12457 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_ESHE3 0x12458 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_ESHE3 0x12459 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_THIRD_DISH 0x1245a #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_THIRDS_DISH 0x1245b #define UNICODE_CUNEIFORM_NUMERIC_SIGN_FIVE_SIXTHS_DISH 0x1245c #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_THIRD_VARIANT_FORM_A 0x1245d #define UNICODE_CUNEIFORM_NUMERIC_SIGN_TWO_THIRDS_VARIANT_FORM_A 0x1245e #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_EIGHTH_ASH 0x1245f #define UNICODE_CUNEIFORM_NUMERIC_SIGN_ONE_QUARTER_ASH 0x12460 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_OLD_ASSYRIAN_ONE_SIXTH 0x12461 #define UNICODE_CUNEIFORM_NUMERIC_SIGN_OLD_ASSYRIAN_ONE_QUARTER 0x12462 #define UNICODE_CUNEIFORM_PUNCTUATION_SIGN_OLD_ASSYRIAN_WORD_DIVIDER 0x12470 #define UNICODE_CUNEIFORM_PUNCTUATION_SIGN_VERTICAL_COLON 0x12471 #define UNICODE_CUNEIFORM_PUNCTUATION_SIGN_DIAGONAL_COLON 0x12472 #define UNICODE_CUNEIFORM_PUNCTUATION_SIGN_DIAGONAL_TRICOLON 0x12473 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PSILI 0x1d000 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DASEIA 0x1d001 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PERISPOMENI 0x1d002 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_OXEIA_EKFONITIKON 0x1d003 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_OXEIA_DIPLI 0x1d004 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_VAREIA_EKFONITIKON 0x1d005 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_VAREIA_DIPLI 0x1d006 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KATHISTI 0x1d007 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SYRMATIKI 0x1d008 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PARAKLITIKI 0x1d009 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YPOKRISIS 0x1d00a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YPOKRISIS_DIPLI 0x1d00b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KREMASTI 0x1d00c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APESO_EKFONITIKON 0x1d00d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_EXO_EKFONITIKON 0x1d00e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TELEIA 0x1d00f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KENTIMATA 0x1d010 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APOSTROFOS 0x1d011 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APOSTROFOS_DIPLI 0x1d012 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SYNEVMA 0x1d013 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_THITA 0x1d014 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_OLIGON_ARCHAION 0x1d015 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GORGON_ARCHAION 0x1d016 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PSILON 0x1d017 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_CHAMILON 0x1d018 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_VATHY 0x1d019 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ISON_ARCHAION 0x1d01a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KENTIMA_ARCHAION 0x1d01b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KENTIMATA_ARCHAION 0x1d01c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SAXIMATA 0x1d01d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PARICHON 0x1d01e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_STAVROS_APODEXIA 0x1d01f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_OXEIAI_ARCHAION 0x1d020 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_VAREIAI_ARCHAION 0x1d021 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APODERMA_ARCHAION 0x1d022 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APOTHEMA 0x1d023 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KLASMA 0x1d024 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_REVMA 0x1d025 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PIASMA_ARCHAION 0x1d026 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TINAGMA 0x1d027 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ANATRICHISMA 0x1d028 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SEISMA 0x1d029 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SYNAGMA_ARCHAION 0x1d02a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SYNAGMA_META_STAVROU 0x1d02b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_OYRANISMA_ARCHAION 0x1d02c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_THEMA 0x1d02d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_LEMOI 0x1d02e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DYO 0x1d02f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TRIA 0x1d030 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TESSERA 0x1d031 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KRATIMATA 0x1d032 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APESO_EXO_NEO 0x1d033 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_ARCHAION 0x1d034 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_IMIFTHORA 0x1d035 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TROMIKON_ARCHAION 0x1d036 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KATAVA_TROMIKON 0x1d037 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PELASTON 0x1d038 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PSIFISTON 0x1d039 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KONTEVMA 0x1d03a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_CHOREVMA_ARCHAION 0x1d03b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_RAPISMA 0x1d03c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PARAKALESMA_ARCHAION 0x1d03d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PARAKLITIKI_ARCHAION 0x1d03e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ICHADIN 0x1d03f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_NANA 0x1d040 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PETASMA 0x1d041 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KONTEVMA_ALLO 0x1d042 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TROMIKON_ALLO 0x1d043 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_STRAGGISMATA 0x1d044 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GRONTHISMATA 0x1d045 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ISON_NEO 0x1d046 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_OLIGON_NEO 0x1d047 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_OXEIA_NEO 0x1d048 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PETASTI 0x1d049 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KOUFISMA 0x1d04a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PETASTOKOUFISMA 0x1d04b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KRATIMOKOUFISMA 0x1d04c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PELASTON_NEO 0x1d04d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KENTIMATA_NEO_ANO 0x1d04e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KENTIMA_NEO_ANO 0x1d04f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YPSILI 0x1d050 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APOSTROFOS_NEO 0x1d051 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APOSTROFOI_SYNDESMOS_NEO 0x1d052 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YPORROI 0x1d053 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KRATIMOYPORROON 0x1d054 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ELAFRON 0x1d055 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_CHAMILI 0x1d056 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MIKRON_ISON 0x1d057 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_VAREIA_NEO 0x1d058 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PIASMA_NEO 0x1d059 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PSIFISTON_NEO 0x1d05a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_OMALON 0x1d05b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ANTIKENOMA 0x1d05c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_LYGISMA 0x1d05d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PARAKLITIKI_NEO 0x1d05e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PARAKALESMA_NEO 0x1d05f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ETERON_PARAKALESMA 0x1d060 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KYLISMA 0x1d061 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ANTIKENOKYLISMA 0x1d062 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TROMIKON_NEO 0x1d063 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_EKSTREPTON 0x1d064 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SYNAGMA_NEO 0x1d065 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SYRMA 0x1d066 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_CHOREVMA_NEO 0x1d067 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_EPEGERMA 0x1d068 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SEISMA_NEO 0x1d069 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_XIRON_KLASMA 0x1d06a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TROMIKOPSIFISTON 0x1d06b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PSIFISTOLYGISMA 0x1d06c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TROMIKOLYGISMA 0x1d06d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TROMIKOPARAKALESMA 0x1d06e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PSIFISTOPARAKALESMA 0x1d06f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TROMIKOSYNAGMA 0x1d070 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_PSIFISTOSYNAGMA 0x1d071 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GORGOSYNTHETON 0x1d072 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ARGOSYNTHETON 0x1d073 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ETERON_ARGOSYNTHETON 0x1d074 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_OYRANISMA_NEO 0x1d075 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_THEMATISMOS_ESO 0x1d076 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_THEMATISMOS_EXO 0x1d077 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_THEMA_APLOUN 0x1d078 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_THES_KAI_APOTHES 0x1d079 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KATAVASMA 0x1d07a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ENDOFONON 0x1d07b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YFEN_KATO 0x1d07c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YFEN_ANO 0x1d07d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_STAVROS 0x1d07e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KLASMA_ANO 0x1d07f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIPLI_ARCHAION 0x1d080 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KRATIMA_ARCHAION 0x1d081 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KRATIMA_ALLO 0x1d082 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KRATIMA_NEO 0x1d083 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APODERMA_NEO 0x1d084 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APLI 0x1d085 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIPLI 0x1d086 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TRIPLI 0x1d087 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TETRAPLI 0x1d088 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KORONIS 0x1d089 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_LEIMMA_ENOS_CHRONOU 0x1d08a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_LEIMMA_DYO_CHRONON 0x1d08b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_LEIMMA_TRION_CHRONON 0x1d08c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_LEIMMA_TESSARON_CHRONON 0x1d08d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_LEIMMA_IMISEOS_CHRONOU 0x1d08e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GORGON_NEO_ANO 0x1d08f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GORGON_PARESTIGMENON_ARISTERA 0x1d090 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GORGON_PARESTIGMENON_DEXIA 0x1d091 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIGORGON 0x1d092 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIGORGON_PARESTIGMENON_ARISTERA_KATO 0x1d093 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIGORGON_PARESTIGMENON_ARISTERA_ANO 0x1d094 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIGORGON_PARESTIGMENON_DEXIA 0x1d095 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_TRIGORGON 0x1d096 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ARGON 0x1d097 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_IMIDIARGON 0x1d098 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIARGON 0x1d099 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_AGOGI_POLI_ARGI 0x1d09a #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_AGOGI_ARGOTERI 0x1d09b #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_AGOGI_ARGI 0x1d09c #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_AGOGI_METRIA 0x1d09d #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_AGOGI_MESI 0x1d09e #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_AGOGI_GORGI 0x1d09f #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_AGOGI_GORGOTERI 0x1d0a0 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_AGOGI_POLI_GORGI 0x1d0a1 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_PROTOS_ICHOS 0x1d0a2 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_ALLI_PROTOS_ICHOS 0x1d0a3 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_DEYTEROS_ICHOS 0x1d0a4 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_ALLI_DEYTEROS_ICHOS 0x1d0a5 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_TRITOS_ICHOS 0x1d0a6 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_TRIFONIAS 0x1d0a7 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_TETARTOS_ICHOS 0x1d0a8 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_TETARTOS_LEGETOS_ICHOS 0x1d0a9 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_LEGETOS_ICHOS 0x1d0aa #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_PLAGIOS_ICHOS 0x1d0ab #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ISAKIA_TELOUS_ICHIMATOS 0x1d0ac #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_APOSTROFOI_TELOUS_ICHIMATOS 0x1d0ad #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FANEROSIS_TETRAFONIAS 0x1d0ae #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FANEROSIS_MONOFONIAS 0x1d0af #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FANEROSIS_DIFONIAS 0x1d0b0 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_VARYS_ICHOS 0x1d0b1 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_PROTOVARYS_ICHOS 0x1d0b2 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_MARTYRIA_PLAGIOS_TETARTOS_ICHOS 0x1d0b3 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GORTHMIKON_N_APLOUN 0x1d0b4 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GORTHMIKON_N_DIPLOUN 0x1d0b5 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ENARXIS_KAI_FTHORA_VOU 0x1d0b6 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_IMIFONON 0x1d0b7 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_IMIFTHORON 0x1d0b8 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_ARCHAION_DEYTEROU_ICHOU 0x1d0b9 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_DIATONIKI_PA 0x1d0ba #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_DIATONIKI_NANA 0x1d0bb #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_NAOS_ICHOS 0x1d0bc #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_DIATONIKI_DI 0x1d0bd #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_SKLIRON_DIATONON_DI 0x1d0be #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_DIATONIKI_KE 0x1d0bf #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_DIATONIKI_ZO 0x1d0c0 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_DIATONIKI_NI_KATO 0x1d0c1 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_DIATONIKI_NI_ANO 0x1d0c2 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_MALAKON_CHROMA_DIFONIAS 0x1d0c3 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_MALAKON_CHROMA_MONOFONIAS 0x1d0c4 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FHTORA_SKLIRON_CHROMA_VASIS 0x1d0c5 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_SKLIRON_CHROMA_SYNAFI 0x1d0c6 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_NENANO 0x1d0c7 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_CHROA_ZYGOS 0x1d0c8 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_CHROA_KLITON 0x1d0c9 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_CHROA_SPATHI 0x1d0ca #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_I_YFESIS_TETARTIMORION 0x1d0cb #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_FTHORA_ENARMONIOS_ANTIFONIA 0x1d0cc #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YFESIS_TRITIMORION 0x1d0cd #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIESIS_TRITIMORION 0x1d0ce #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIESIS_TETARTIMORION 0x1d0cf #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIESIS_APLI_DYO_DODEKATA 0x1d0d0 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIESIS_MONOGRAMMOS_TESSERA_DODEKATA 0x1d0d1 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIESIS_DIGRAMMOS_EX_DODEKATA 0x1d0d2 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIESIS_TRIGRAMMOS_OKTO_DODEKATA 0x1d0d3 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YFESIS_APLI_DYO_DODEKATA 0x1d0d4 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YFESIS_MONOGRAMMOS_TESSERA_DODEKATA 0x1d0d5 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YFESIS_DIGRAMMOS_EX_DODEKATA 0x1d0d6 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_YFESIS_TRIGRAMMOS_OKTO_DODEKATA 0x1d0d7 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GENIKI_DIESIS 0x1d0d8 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GENIKI_YFESIS 0x1d0d9 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIASTOLI_APLI_MIKRI 0x1d0da #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIASTOLI_APLI_MEGALI 0x1d0db #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIASTOLI_DIPLI 0x1d0dc #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIASTOLI_THESEOS 0x1d0dd #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SIMANSIS_THESEOS 0x1d0de #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SIMANSIS_THESEOS_DISIMOU 0x1d0df #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SIMANSIS_THESEOS_TRISIMOU 0x1d0e0 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SIMANSIS_THESEOS_TETRASIMOU 0x1d0e1 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SIMANSIS_ARSEOS 0x1d0e2 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SIMANSIS_ARSEOS_DISIMOU 0x1d0e3 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SIMANSIS_ARSEOS_TRISIMOU 0x1d0e4 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_SIMANSIS_ARSEOS_TETRASIMOU 0x1d0e5 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIGRAMMA_GG 0x1d0e6 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_DIFTOGGOS_OU 0x1d0e7 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_STIGMA 0x1d0e8 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ARKTIKO_PA 0x1d0e9 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ARKTIKO_VOU 0x1d0ea #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ARKTIKO_GA 0x1d0eb #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ARKTIKO_DI 0x1d0ec #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ARKTIKO_KE 0x1d0ed #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ARKTIKO_ZO 0x1d0ee #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_ARKTIKO_NI 0x1d0ef #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KENTIMATA_NEO_MESO 0x1d0f0 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KENTIMA_NEO_MESO 0x1d0f1 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KENTIMATA_NEO_KATO 0x1d0f2 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KENTIMA_NEO_KATO 0x1d0f3 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_KLASMA_KATO 0x1d0f4 #define UNICODE_BYZANTINE_MUSICAL_SYMBOL_GORGON_NEO_KATO 0x1d0f5 #define UNICODE_MUSICAL_SYMBOL_SINGLE_BARLINE 0x1d100 #define UNICODE_MUSICAL_SYMBOL_DOUBLE_BARLINE 0x1d101 #define UNICODE_MUSICAL_SYMBOL_FINAL_BARLINE 0x1d102 #define UNICODE_MUSICAL_SYMBOL_REVERSE_FINAL_BARLINE 0x1d103 #define UNICODE_MUSICAL_SYMBOL_DASHED_BARLINE 0x1d104 #define UNICODE_MUSICAL_SYMBOL_SHORT_BARLINE 0x1d105 #define UNICODE_MUSICAL_SYMBOL_LEFT_REPEAT_SIGN 0x1d106 #define UNICODE_MUSICAL_SYMBOL_RIGHT_REPEAT_SIGN 0x1d107 #define UNICODE_MUSICAL_SYMBOL_REPEAT_DOTS 0x1d108 #define UNICODE_MUSICAL_SYMBOL_DAL_SEGNO 0x1d109 #define UNICODE_MUSICAL_SYMBOL_DA_CAPO 0x1d10a #define UNICODE_MUSICAL_SYMBOL_SEGNO 0x1d10b #define UNICODE_MUSICAL_SYMBOL_CODA 0x1d10c #define UNICODE_MUSICAL_SYMBOL_REPEATED_FIGURE_1 0x1d10d #define UNICODE_MUSICAL_SYMBOL_REPEATED_FIGURE_2 0x1d10e #define UNICODE_MUSICAL_SYMBOL_REPEATED_FIGURE_3 0x1d10f #define UNICODE_MUSICAL_SYMBOL_FERMATA 0x1d110 #define UNICODE_MUSICAL_SYMBOL_FERMATA_BELOW 0x1d111 #define UNICODE_MUSICAL_SYMBOL_BREATH_MARK 0x1d112 #define UNICODE_MUSICAL_SYMBOL_CAESURA 0x1d113 #define UNICODE_MUSICAL_SYMBOL_BRACE 0x1d114 #define UNICODE_MUSICAL_SYMBOL_BRACKET 0x1d115 #define UNICODE_MUSICAL_SYMBOL_ONE_LINE_STAFF 0x1d116 #define UNICODE_MUSICAL_SYMBOL_TWO_LINE_STAFF 0x1d117 #define UNICODE_MUSICAL_SYMBOL_THREE_LINE_STAFF 0x1d118 #define UNICODE_MUSICAL_SYMBOL_FOUR_LINE_STAFF 0x1d119 #define UNICODE_MUSICAL_SYMBOL_FIVE_LINE_STAFF 0x1d11a #define UNICODE_MUSICAL_SYMBOL_SIX_LINE_STAFF 0x1d11b #define UNICODE_MUSICAL_SYMBOL_SIX_STRING_FRETBOARD 0x1d11c #define UNICODE_MUSICAL_SYMBOL_FOUR_STRING_FRETBOARD 0x1d11d #define UNICODE_MUSICAL_SYMBOL_G_CLEF 0x1d11e #define UNICODE_MUSICAL_SYMBOL_G_CLEF_OTTAVA_ALTA 0x1d11f #define UNICODE_MUSICAL_SYMBOL_G_CLEF_OTTAVA_BASSA 0x1d120 #define UNICODE_MUSICAL_SYMBOL_C_CLEF 0x1d121 #define UNICODE_MUSICAL_SYMBOL_F_CLEF 0x1d122 #define UNICODE_MUSICAL_SYMBOL_F_CLEF_OTTAVA_ALTA 0x1d123 #define UNICODE_MUSICAL_SYMBOL_F_CLEF_OTTAVA_BASSA 0x1d124 #define UNICODE_MUSICAL_SYMBOL_DRUM_CLEF_1 0x1d125 #define UNICODE_MUSICAL_SYMBOL_DRUM_CLEF_2 0x1d126 #define UNICODE_MUSICAL_SYMBOL_DOUBLE_SHARP 0x1d12a #define UNICODE_MUSICAL_SYMBOL_DOUBLE_FLAT 0x1d12b #define UNICODE_MUSICAL_SYMBOL_FLAT_UP 0x1d12c #define UNICODE_MUSICAL_SYMBOL_FLAT_DOWN 0x1d12d #define UNICODE_MUSICAL_SYMBOL_NATURAL_UP 0x1d12e #define UNICODE_MUSICAL_SYMBOL_NATURAL_DOWN 0x1d12f #define UNICODE_MUSICAL_SYMBOL_SHARP_UP 0x1d130 #define UNICODE_MUSICAL_SYMBOL_SHARP_DOWN 0x1d131 #define UNICODE_MUSICAL_SYMBOL_QUARTER_TONE_SHARP 0x1d132 #define UNICODE_MUSICAL_SYMBOL_QUARTER_TONE_FLAT 0x1d133 #define UNICODE_MUSICAL_SYMBOL_COMMON_TIME 0x1d134 #define UNICODE_MUSICAL_SYMBOL_CUT_TIME 0x1d135 #define UNICODE_MUSICAL_SYMBOL_OTTAVA_ALTA 0x1d136 #define UNICODE_MUSICAL_SYMBOL_OTTAVA_BASSA 0x1d137 #define UNICODE_MUSICAL_SYMBOL_QUINDICESIMA_ALTA 0x1d138 #define UNICODE_MUSICAL_SYMBOL_QUINDICESIMA_BASSA 0x1d139 #define UNICODE_MUSICAL_SYMBOL_MULTI_REST 0x1d13a #define UNICODE_MUSICAL_SYMBOL_WHOLE_REST 0x1d13b #define UNICODE_MUSICAL_SYMBOL_HALF_REST 0x1d13c #define UNICODE_MUSICAL_SYMBOL_QUARTER_REST 0x1d13d #define UNICODE_MUSICAL_SYMBOL_EIGHTH_REST 0x1d13e #define UNICODE_MUSICAL_SYMBOL_SIXTEENTH_REST 0x1d13f #define UNICODE_MUSICAL_SYMBOL_THIRTY_SECOND_REST 0x1d140 #define UNICODE_MUSICAL_SYMBOL_SIXTY_FOURTH_REST 0x1d141 #define UNICODE_MUSICAL_SYMBOL_ONE_HUNDRED_TWENTY_EIGHTH_REST 0x1d142 #define UNICODE_MUSICAL_SYMBOL_X_NOTEHEAD 0x1d143 #define UNICODE_MUSICAL_SYMBOL_PLUS_NOTEHEAD 0x1d144 #define UNICODE_MUSICAL_SYMBOL_CIRCLE_X_NOTEHEAD 0x1d145 #define UNICODE_MUSICAL_SYMBOL_SQUARE_NOTEHEAD_WHITE 0x1d146 #define UNICODE_MUSICAL_SYMBOL_SQUARE_NOTEHEAD_BLACK 0x1d147 #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_UP_WHITE 0x1d148 #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_UP_BLACK 0x1d149 #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_LEFT_WHITE 0x1d14a #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_LEFT_BLACK 0x1d14b #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_RIGHT_WHITE 0x1d14c #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_RIGHT_BLACK 0x1d14d #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_DOWN_WHITE 0x1d14e #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_DOWN_BLACK 0x1d14f #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_UP_RIGHT_WHITE 0x1d150 #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_NOTEHEAD_UP_RIGHT_BLACK 0x1d151 #define UNICODE_MUSICAL_SYMBOL_MOON_NOTEHEAD_WHITE 0x1d152 #define UNICODE_MUSICAL_SYMBOL_MOON_NOTEHEAD_BLACK 0x1d153 #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_ROUND_NOTEHEAD_DOWN_WHITE 0x1d154 #define UNICODE_MUSICAL_SYMBOL_TRIANGLE_ROUND_NOTEHEAD_DOWN_BLACK 0x1d155 #define UNICODE_MUSICAL_SYMBOL_PARENTHESIS_NOTEHEAD 0x1d156 #define UNICODE_MUSICAL_SYMBOL_VOID_NOTEHEAD 0x1d157 #define UNICODE_MUSICAL_SYMBOL_NOTEHEAD_BLACK 0x1d158 #define UNICODE_MUSICAL_SYMBOL_NULL_NOTEHEAD 0x1d159 #define UNICODE_MUSICAL_SYMBOL_CLUSTER_NOTEHEAD_WHITE 0x1d15a #define UNICODE_MUSICAL_SYMBOL_CLUSTER_NOTEHEAD_BLACK 0x1d15b #define UNICODE_MUSICAL_SYMBOL_BREVE 0x1d15c #define UNICODE_MUSICAL_SYMBOL_WHOLE_NOTE 0x1d15d #define UNICODE_MUSICAL_SYMBOL_HALF_NOTE 0x1d15e #define UNICODE_MUSICAL_SYMBOL_QUARTER_NOTE 0x1d15f #define UNICODE_MUSICAL_SYMBOL_EIGHTH_NOTE 0x1d160 #define UNICODE_MUSICAL_SYMBOL_SIXTEENTH_NOTE 0x1d161 #define UNICODE_MUSICAL_SYMBOL_THIRTY_SECOND_NOTE 0x1d162 #define UNICODE_MUSICAL_SYMBOL_SIXTY_FOURTH_NOTE 0x1d163 #define UNICODE_MUSICAL_SYMBOL_ONE_HUNDRED_TWENTY_EIGHTH_NOTE 0x1d164 #define UNICODE_MUSICAL_SYMBOL_COMBINING_STEM 0x1d165 #define UNICODE_MUSICAL_SYMBOL_COMBINING_SPRECHGESANG_STEM 0x1d166 #define UNICODE_MUSICAL_SYMBOL_COMBINING_TREMOLO_1 0x1d167 #define UNICODE_MUSICAL_SYMBOL_COMBINING_TREMOLO_2 0x1d168 #define UNICODE_MUSICAL_SYMBOL_COMBINING_TREMOLO_3 0x1d169 #define UNICODE_MUSICAL_SYMBOL_FINGERED_TREMOLO_1 0x1d16a #define UNICODE_MUSICAL_SYMBOL_FINGERED_TREMOLO_2 0x1d16b #define UNICODE_MUSICAL_SYMBOL_FINGERED_TREMOLO_3 0x1d16c #define UNICODE_MUSICAL_SYMBOL_COMBINING_AUGMENTATION_DOT 0x1d16d #define UNICODE_MUSICAL_SYMBOL_COMBINING_FLAG_1 0x1d16e #define UNICODE_MUSICAL_SYMBOL_COMBINING_FLAG_2 0x1d16f #define UNICODE_MUSICAL_SYMBOL_COMBINING_FLAG_3 0x1d170 #define UNICODE_MUSICAL_SYMBOL_COMBINING_FLAG_4 0x1d171 #define UNICODE_MUSICAL_SYMBOL_COMBINING_FLAG_5 0x1d172 #define UNICODE_MUSICAL_SYMBOL_BEGIN_BEAM 0x1d173 #define UNICODE_MUSICAL_SYMBOL_END_BEAM 0x1d174 #define UNICODE_MUSICAL_SYMBOL_BEGIN_TIE 0x1d175 #define UNICODE_MUSICAL_SYMBOL_END_TIE 0x1d176 #define UNICODE_MUSICAL_SYMBOL_BEGIN_SLUR 0x1d177 #define UNICODE_MUSICAL_SYMBOL_END_SLUR 0x1d178 #define UNICODE_MUSICAL_SYMBOL_BEGIN_PHRASE 0x1d179 #define UNICODE_MUSICAL_SYMBOL_END_PHRASE 0x1d17a #define UNICODE_MUSICAL_SYMBOL_COMBINING_ACCENT 0x1d17b #define UNICODE_MUSICAL_SYMBOL_COMBINING_STACCATO 0x1d17c #define UNICODE_MUSICAL_SYMBOL_COMBINING_TENUTO 0x1d17d #define UNICODE_MUSICAL_SYMBOL_COMBINING_STACCATISSIMO 0x1d17e #define UNICODE_MUSICAL_SYMBOL_COMBINING_MARCATO 0x1d17f #define UNICODE_MUSICAL_SYMBOL_COMBINING_MARCATO_STACCATO 0x1d180 #define UNICODE_MUSICAL_SYMBOL_COMBINING_ACCENT_STACCATO 0x1d181 #define UNICODE_MUSICAL_SYMBOL_COMBINING_LOURE 0x1d182 #define UNICODE_MUSICAL_SYMBOL_ARPEGGIATO_UP 0x1d183 #define UNICODE_MUSICAL_SYMBOL_ARPEGGIATO_DOWN 0x1d184 #define UNICODE_MUSICAL_SYMBOL_COMBINING_DOIT 0x1d185 #define UNICODE_MUSICAL_SYMBOL_COMBINING_RIP 0x1d186 #define UNICODE_MUSICAL_SYMBOL_COMBINING_FLIP 0x1d187 #define UNICODE_MUSICAL_SYMBOL_COMBINING_SMEAR 0x1d188 #define UNICODE_MUSICAL_SYMBOL_COMBINING_BEND 0x1d189 #define UNICODE_MUSICAL_SYMBOL_COMBINING_DOUBLE_TONGUE 0x1d18a #define UNICODE_MUSICAL_SYMBOL_COMBINING_TRIPLE_TONGUE 0x1d18b #define UNICODE_MUSICAL_SYMBOL_RINFORZANDO 0x1d18c #define UNICODE_MUSICAL_SYMBOL_SUBITO 0x1d18d #define UNICODE_MUSICAL_SYMBOL_Z 0x1d18e #define UNICODE_MUSICAL_SYMBOL_PIANO 0x1d18f #define UNICODE_MUSICAL_SYMBOL_MEZZO 0x1d190 #define UNICODE_MUSICAL_SYMBOL_FORTE 0x1d191 #define UNICODE_MUSICAL_SYMBOL_CRESCENDO 0x1d192 #define UNICODE_MUSICAL_SYMBOL_DECRESCENDO 0x1d193 #define UNICODE_MUSICAL_SYMBOL_GRACE_NOTE_SLASH 0x1d194 #define UNICODE_MUSICAL_SYMBOL_GRACE_NOTE_NO_SLASH 0x1d195 #define UNICODE_MUSICAL_SYMBOL_TR 0x1d196 #define UNICODE_MUSICAL_SYMBOL_TURN 0x1d197 #define UNICODE_MUSICAL_SYMBOL_INVERTED_TURN 0x1d198 #define UNICODE_MUSICAL_SYMBOL_TURN_SLASH 0x1d199 #define UNICODE_MUSICAL_SYMBOL_TURN_UP 0x1d19a #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_1 0x1d19b #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_2 0x1d19c #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_3 0x1d19d #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_4 0x1d19e #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_5 0x1d19f #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_6 0x1d1a0 #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_7 0x1d1a1 #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_8 0x1d1a2 #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_9 0x1d1a3 #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_10 0x1d1a4 #define UNICODE_MUSICAL_SYMBOL_ORNAMENT_STROKE_11 0x1d1a5 #define UNICODE_MUSICAL_SYMBOL_HAUPTSTIMME 0x1d1a6 #define UNICODE_MUSICAL_SYMBOL_NEBENSTIMME 0x1d1a7 #define UNICODE_MUSICAL_SYMBOL_END_OF_STIMME 0x1d1a8 #define UNICODE_MUSICAL_SYMBOL_DEGREE_SLASH 0x1d1a9 #define UNICODE_MUSICAL_SYMBOL_COMBINING_DOWN_BOW 0x1d1aa #define UNICODE_MUSICAL_SYMBOL_COMBINING_UP_BOW 0x1d1ab #define UNICODE_MUSICAL_SYMBOL_COMBINING_HARMONIC 0x1d1ac #define UNICODE_MUSICAL_SYMBOL_COMBINING_SNAP_PIZZICATO 0x1d1ad #define UNICODE_MUSICAL_SYMBOL_PEDAL_MARK 0x1d1ae #define UNICODE_MUSICAL_SYMBOL_PEDAL_UP_MARK 0x1d1af #define UNICODE_MUSICAL_SYMBOL_HALF_PEDAL_MARK 0x1d1b0 #define UNICODE_MUSICAL_SYMBOL_GLISSANDO_UP 0x1d1b1 #define UNICODE_MUSICAL_SYMBOL_GLISSANDO_DOWN 0x1d1b2 #define UNICODE_MUSICAL_SYMBOL_WITH_FINGERNAILS 0x1d1b3 #define UNICODE_MUSICAL_SYMBOL_DAMP 0x1d1b4 #define UNICODE_MUSICAL_SYMBOL_DAMP_ALL 0x1d1b5 #define UNICODE_MUSICAL_SYMBOL_MAXIMA 0x1d1b6 #define UNICODE_MUSICAL_SYMBOL_LONGA 0x1d1b7 #define UNICODE_MUSICAL_SYMBOL_BREVIS 0x1d1b8 #define UNICODE_MUSICAL_SYMBOL_SEMIBREVIS_WHITE 0x1d1b9 #define UNICODE_MUSICAL_SYMBOL_SEMIBREVIS_BLACK 0x1d1ba #define UNICODE_MUSICAL_SYMBOL_MINIMA 0x1d1bb #define UNICODE_MUSICAL_SYMBOL_MINIMA_BLACK 0x1d1bc #define UNICODE_MUSICAL_SYMBOL_SEMIMINIMA_WHITE 0x1d1bd #define UNICODE_MUSICAL_SYMBOL_SEMIMINIMA_BLACK 0x1d1be #define UNICODE_MUSICAL_SYMBOL_FUSA_WHITE 0x1d1bf #define UNICODE_MUSICAL_SYMBOL_FUSA_BLACK 0x1d1c0 #define UNICODE_MUSICAL_SYMBOL_LONGA_PERFECTA_REST 0x1d1c1 #define UNICODE_MUSICAL_SYMBOL_LONGA_IMPERFECTA_REST 0x1d1c2 #define UNICODE_MUSICAL_SYMBOL_BREVIS_REST 0x1d1c3 #define UNICODE_MUSICAL_SYMBOL_SEMIBREVIS_REST 0x1d1c4 #define UNICODE_MUSICAL_SYMBOL_MINIMA_REST 0x1d1c5 #define UNICODE_MUSICAL_SYMBOL_SEMIMINIMA_REST 0x1d1c6 #define UNICODE_MUSICAL_SYMBOL_TEMPUS_PERFECTUM_CUM_PROLATIONE_PERFECTA 0x1d1c7 #define UNICODE_MUSICAL_SYMBOL_TEMPUS_PERFECTUM_CUM_PROLATIONE_IMPERFECTA 0x1d1c8 #define UNICODE_MUSICAL_SYMBOL_TEMPUS_PERFECTUM_CUM_PROLATIONE_PERFECTA_DIMINUTION_1 0x1d1c9 #define UNICODE_MUSICAL_SYMBOL_TEMPUS_IMPERFECTUM_CUM_PROLATIONE_PERFECTA 0x1d1ca #define UNICODE_MUSICAL_SYMBOL_TEMPUS_IMPERFECTUM_CUM_PROLATIONE_IMPERFECTA 0x1d1cb #define UNICODE_MUSICAL_SYMBOL_TEMPUS_IMPERFECTUM_CUM_PROLATIONE_IMPERFECTA_DIMINUTION_1 0x1d1cc #define UNICODE_MUSICAL_SYMBOL_TEMPUS_IMPERFECTUM_CUM_PROLATIONE_IMPERFECTA_DIMINUTION_2 0x1d1cd #define UNICODE_MUSICAL_SYMBOL_TEMPUS_IMPERFECTUM_CUM_PROLATIONE_IMPERFECTA_DIMINUTION_3 0x1d1ce #define UNICODE_MUSICAL_SYMBOL_CROIX 0x1d1cf #define UNICODE_MUSICAL_SYMBOL_GREGORIAN_C_CLEF 0x1d1d0 #define UNICODE_MUSICAL_SYMBOL_GREGORIAN_F_CLEF 0x1d1d1 #define UNICODE_MUSICAL_SYMBOL_SQUARE_B 0x1d1d2 #define UNICODE_MUSICAL_SYMBOL_VIRGA 0x1d1d3 #define UNICODE_MUSICAL_SYMBOL_PODATUS 0x1d1d4 #define UNICODE_MUSICAL_SYMBOL_CLIVIS 0x1d1d5 #define UNICODE_MUSICAL_SYMBOL_SCANDICUS 0x1d1d6 #define UNICODE_MUSICAL_SYMBOL_CLIMACUS 0x1d1d7 #define UNICODE_MUSICAL_SYMBOL_TORCULUS 0x1d1d8 #define UNICODE_MUSICAL_SYMBOL_PORRECTUS 0x1d1d9 #define UNICODE_MUSICAL_SYMBOL_PORRECTUS_FLEXUS 0x1d1da #define UNICODE_MUSICAL_SYMBOL_SCANDICUS_FLEXUS 0x1d1db #define UNICODE_MUSICAL_SYMBOL_TORCULUS_RESUPINUS 0x1d1dc #define UNICODE_MUSICAL_SYMBOL_PES_SUBPUNCTIS 0x1d1dd #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_1 0x1d200 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_2 0x1d201 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_3 0x1d202 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_4 0x1d203 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_5 0x1d204 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_6 0x1d205 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_7 0x1d206 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_8 0x1d207 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_9 0x1d208 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_10 0x1d209 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_11 0x1d20a #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_12 0x1d20b #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_13 0x1d20c #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_14 0x1d20d #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_15 0x1d20e #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_16 0x1d20f #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_17 0x1d210 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_18 0x1d211 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_19 0x1d212 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_20 0x1d213 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_21 0x1d214 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_22 0x1d215 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_23 0x1d216 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_24 0x1d217 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_50 0x1d218 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_51 0x1d219 #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_52 0x1d21a #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_53 0x1d21b #define UNICODE_GREEK_VOCAL_NOTATION_SYMBOL_54 0x1d21c #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_1 0x1d21d #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_2 0x1d21e #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_4 0x1d21f #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_5 0x1d220 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_7 0x1d221 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_8 0x1d222 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_11 0x1d223 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_12 0x1d224 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_13 0x1d225 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_14 0x1d226 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_17 0x1d227 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_18 0x1d228 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_19 0x1d229 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_23 0x1d22a #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_24 0x1d22b #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_25 0x1d22c #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_26 0x1d22d #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_27 0x1d22e #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_29 0x1d22f #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_30 0x1d230 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_32 0x1d231 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_36 0x1d232 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_37 0x1d233 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_38 0x1d234 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_39 0x1d235 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_40 0x1d236 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_42 0x1d237 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_43 0x1d238 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_45 0x1d239 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_47 0x1d23a #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_48 0x1d23b #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_49 0x1d23c #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_50 0x1d23d #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_51 0x1d23e #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_52 0x1d23f #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_53 0x1d240 #define UNICODE_GREEK_INSTRUMENTAL_NOTATION_SYMBOL_54 0x1d241 #define UNICODE_COMBINING_GREEK_MUSICAL_TRISEME 0x1d242 #define UNICODE_COMBINING_GREEK_MUSICAL_TETRASEME 0x1d243 #define UNICODE_COMBINING_GREEK_MUSICAL_PENTASEME 0x1d244 #define UNICODE_GREEK_MUSICAL_LEIMMA 0x1d245 #define UNICODE_MONOGRAM_FOR_EARTH 0x1d300 #define UNICODE_DIGRAM_FOR_HEAVENLY_EARTH 0x1d301 #define UNICODE_DIGRAM_FOR_HUMAN_EARTH 0x1d302 #define UNICODE_DIGRAM_FOR_EARTHLY_HEAVEN 0x1d303 #define UNICODE_DIGRAM_FOR_EARTHLY_HUMAN 0x1d304 #define UNICODE_DIGRAM_FOR_EARTH 0x1d305 #define UNICODE_TETRAGRAM_FOR_CENTRE 0x1d306 #define UNICODE_TETRAGRAM_FOR_FULL_CIRCLE 0x1d307 #define UNICODE_TETRAGRAM_FOR_MIRED 0x1d308 #define UNICODE_TETRAGRAM_FOR_BARRIER 0x1d309 #define UNICODE_TETRAGRAM_FOR_KEEPING_SMALL 0x1d30a #define UNICODE_TETRAGRAM_FOR_CONTRARIETY 0x1d30b #define UNICODE_TETRAGRAM_FOR_ASCENT 0x1d30c #define UNICODE_TETRAGRAM_FOR_OPPOSITION 0x1d30d #define UNICODE_TETRAGRAM_FOR_BRANCHING_OUT 0x1d30e #define UNICODE_TETRAGRAM_FOR_DEFECTIVENESS_OR_DISTORTION 0x1d30f #define UNICODE_TETRAGRAM_FOR_DIVERGENCE 0x1d310 #define UNICODE_TETRAGRAM_FOR_YOUTHFULNESS 0x1d311 #define UNICODE_TETRAGRAM_FOR_INCREASE 0x1d312 #define UNICODE_TETRAGRAM_FOR_PENETRATION 0x1d313 #define UNICODE_TETRAGRAM_FOR_REACH 0x1d314 #define UNICODE_TETRAGRAM_FOR_CONTACT 0x1d315 #define UNICODE_TETRAGRAM_FOR_HOLDING_BACK 0x1d316 #define UNICODE_TETRAGRAM_FOR_WAITING 0x1d317 #define UNICODE_TETRAGRAM_FOR_FOLLOWING 0x1d318 #define UNICODE_TETRAGRAM_FOR_ADVANCE 0x1d319 #define UNICODE_TETRAGRAM_FOR_RELEASE 0x1d31a #define UNICODE_TETRAGRAM_FOR_RESISTANCE 0x1d31b #define UNICODE_TETRAGRAM_FOR_EASE 0x1d31c #define UNICODE_TETRAGRAM_FOR_JOY 0x1d31d #define UNICODE_TETRAGRAM_FOR_CONTENTION 0x1d31e #define UNICODE_TETRAGRAM_FOR_ENDEAVOUR 0x1d31f #define UNICODE_TETRAGRAM_FOR_DUTIES 0x1d320 #define UNICODE_TETRAGRAM_FOR_CHANGE 0x1d321 #define UNICODE_TETRAGRAM_FOR_DECISIVENESS 0x1d322 #define UNICODE_TETRAGRAM_FOR_BOLD_RESOLUTION 0x1d323 #define UNICODE_TETRAGRAM_FOR_PACKING 0x1d324 #define UNICODE_TETRAGRAM_FOR_LEGION 0x1d325 #define UNICODE_TETRAGRAM_FOR_CLOSENESS 0x1d326 #define UNICODE_TETRAGRAM_FOR_KINSHIP 0x1d327 #define UNICODE_TETRAGRAM_FOR_GATHERING 0x1d328 #define UNICODE_TETRAGRAM_FOR_STRENGTH 0x1d329 #define UNICODE_TETRAGRAM_FOR_PURITY 0x1d32a #define UNICODE_TETRAGRAM_FOR_FULLNESS 0x1d32b #define UNICODE_TETRAGRAM_FOR_RESIDENCE 0x1d32c #define UNICODE_TETRAGRAM_FOR_LAW_OR_MODEL 0x1d32d #define UNICODE_TETRAGRAM_FOR_RESPONSE 0x1d32e #define UNICODE_TETRAGRAM_FOR_GOING_TO_MEET 0x1d32f #define UNICODE_TETRAGRAM_FOR_ENCOUNTERS 0x1d330 #define UNICODE_TETRAGRAM_FOR_STOVE 0x1d331 #define UNICODE_TETRAGRAM_FOR_GREATNESS 0x1d332 #define UNICODE_TETRAGRAM_FOR_ENLARGEMENT 0x1d333 #define UNICODE_TETRAGRAM_FOR_PATTERN 0x1d334 #define UNICODE_TETRAGRAM_FOR_RITUAL 0x1d335 #define UNICODE_TETRAGRAM_FOR_FLIGHT 0x1d336 #define UNICODE_TETRAGRAM_FOR_VASTNESS_OR_WASTING 0x1d337 #define UNICODE_TETRAGRAM_FOR_CONSTANCY 0x1d338 #define UNICODE_TETRAGRAM_FOR_MEASURE 0x1d339 #define UNICODE_TETRAGRAM_FOR_ETERNITY 0x1d33a #define UNICODE_TETRAGRAM_FOR_UNITY 0x1d33b #define UNICODE_TETRAGRAM_FOR_DIMINISHMENT 0x1d33c #define UNICODE_TETRAGRAM_FOR_CLOSED_MOUTH 0x1d33d #define UNICODE_TETRAGRAM_FOR_GUARDEDNESS 0x1d33e #define UNICODE_TETRAGRAM_FOR_GATHERING_IN 0x1d33f #define UNICODE_TETRAGRAM_FOR_MASSING 0x1d340 #define UNICODE_TETRAGRAM_FOR_ACCUMULATION 0x1d341 #define UNICODE_TETRAGRAM_FOR_EMBELLISHMENT 0x1d342 #define UNICODE_TETRAGRAM_FOR_DOUBT 0x1d343 #define UNICODE_TETRAGRAM_FOR_WATCH 0x1d344 #define UNICODE_TETRAGRAM_FOR_SINKING 0x1d345 #define UNICODE_TETRAGRAM_FOR_INNER 0x1d346 #define UNICODE_TETRAGRAM_FOR_DEPARTURE 0x1d347 #define UNICODE_TETRAGRAM_FOR_DARKENING 0x1d348 #define UNICODE_TETRAGRAM_FOR_DIMMING 0x1d349 #define UNICODE_TETRAGRAM_FOR_EXHAUSTION 0x1d34a #define UNICODE_TETRAGRAM_FOR_SEVERANCE 0x1d34b #define UNICODE_TETRAGRAM_FOR_STOPPAGE 0x1d34c #define UNICODE_TETRAGRAM_FOR_HARDNESS 0x1d34d #define UNICODE_TETRAGRAM_FOR_COMPLETION 0x1d34e #define UNICODE_TETRAGRAM_FOR_CLOSURE 0x1d34f #define UNICODE_TETRAGRAM_FOR_FAILURE 0x1d350 #define UNICODE_TETRAGRAM_FOR_AGGRAVATION 0x1d351 #define UNICODE_TETRAGRAM_FOR_COMPLIANCE 0x1d352 #define UNICODE_TETRAGRAM_FOR_ON_THE_VERGE 0x1d353 #define UNICODE_TETRAGRAM_FOR_DIFFICULTIES 0x1d354 #define UNICODE_TETRAGRAM_FOR_LABOURING 0x1d355 #define UNICODE_TETRAGRAM_FOR_FOSTERING 0x1d356 #define UNICODE_COUNTING_ROD_UNIT_DIGIT_ONE 0x1d360 #define UNICODE_COUNTING_ROD_UNIT_DIGIT_TWO 0x1d361 #define UNICODE_COUNTING_ROD_UNIT_DIGIT_THREE 0x1d362 #define UNICODE_COUNTING_ROD_UNIT_DIGIT_FOUR 0x1d363 #define UNICODE_COUNTING_ROD_UNIT_DIGIT_FIVE 0x1d364 #define UNICODE_COUNTING_ROD_UNIT_DIGIT_SIX 0x1d365 #define UNICODE_COUNTING_ROD_UNIT_DIGIT_SEVEN 0x1d366 #define UNICODE_COUNTING_ROD_UNIT_DIGIT_EIGHT 0x1d367 #define UNICODE_COUNTING_ROD_UNIT_DIGIT_NINE 0x1d368 #define UNICODE_COUNTING_ROD_TENS_DIGIT_ONE 0x1d369 #define UNICODE_COUNTING_ROD_TENS_DIGIT_TWO 0x1d36a #define UNICODE_COUNTING_ROD_TENS_DIGIT_THREE 0x1d36b #define UNICODE_COUNTING_ROD_TENS_DIGIT_FOUR 0x1d36c #define UNICODE_COUNTING_ROD_TENS_DIGIT_FIVE 0x1d36d #define UNICODE_COUNTING_ROD_TENS_DIGIT_SIX 0x1d36e #define UNICODE_COUNTING_ROD_TENS_DIGIT_SEVEN 0x1d36f #define UNICODE_COUNTING_ROD_TENS_DIGIT_EIGHT 0x1d370 #define UNICODE_COUNTING_ROD_TENS_DIGIT_NINE 0x1d371 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_A 0x1d400 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_B 0x1d401 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_C 0x1d402 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_D 0x1d403 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_E 0x1d404 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_F 0x1d405 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_G 0x1d406 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_H 0x1d407 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_I 0x1d408 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_J 0x1d409 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_K 0x1d40a #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_L 0x1d40b #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_M 0x1d40c #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_N 0x1d40d #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_O 0x1d40e #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_P 0x1d40f #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_Q 0x1d410 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_R 0x1d411 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_S 0x1d412 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_T 0x1d413 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_U 0x1d414 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_V 0x1d415 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_W 0x1d416 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_X 0x1d417 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_Y 0x1d418 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_Z 0x1d419 #define UNICODE_MATHEMATICAL_BOLD_SMALL_A 0x1d41a #define UNICODE_MATHEMATICAL_BOLD_SMALL_B 0x1d41b #define UNICODE_MATHEMATICAL_BOLD_SMALL_C 0x1d41c #define UNICODE_MATHEMATICAL_BOLD_SMALL_D 0x1d41d #define UNICODE_MATHEMATICAL_BOLD_SMALL_E 0x1d41e #define UNICODE_MATHEMATICAL_BOLD_SMALL_F 0x1d41f #define UNICODE_MATHEMATICAL_BOLD_SMALL_G 0x1d420 #define UNICODE_MATHEMATICAL_BOLD_SMALL_H 0x1d421 #define UNICODE_MATHEMATICAL_BOLD_SMALL_I 0x1d422 #define UNICODE_MATHEMATICAL_BOLD_SMALL_J 0x1d423 #define UNICODE_MATHEMATICAL_BOLD_SMALL_K 0x1d424 #define UNICODE_MATHEMATICAL_BOLD_SMALL_L 0x1d425 #define UNICODE_MATHEMATICAL_BOLD_SMALL_M 0x1d426 #define UNICODE_MATHEMATICAL_BOLD_SMALL_N 0x1d427 #define UNICODE_MATHEMATICAL_BOLD_SMALL_O 0x1d428 #define UNICODE_MATHEMATICAL_BOLD_SMALL_P 0x1d429 #define UNICODE_MATHEMATICAL_BOLD_SMALL_Q 0x1d42a #define UNICODE_MATHEMATICAL_BOLD_SMALL_R 0x1d42b #define UNICODE_MATHEMATICAL_BOLD_SMALL_S 0x1d42c #define UNICODE_MATHEMATICAL_BOLD_SMALL_T 0x1d42d #define UNICODE_MATHEMATICAL_BOLD_SMALL_U 0x1d42e #define UNICODE_MATHEMATICAL_BOLD_SMALL_V 0x1d42f #define UNICODE_MATHEMATICAL_BOLD_SMALL_W 0x1d430 #define UNICODE_MATHEMATICAL_BOLD_SMALL_X 0x1d431 #define UNICODE_MATHEMATICAL_BOLD_SMALL_Y 0x1d432 #define UNICODE_MATHEMATICAL_BOLD_SMALL_Z 0x1d433 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_A 0x1d434 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_B 0x1d435 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_C 0x1d436 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_D 0x1d437 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_E 0x1d438 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_F 0x1d439 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_G 0x1d43a #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_H 0x1d43b #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_I 0x1d43c #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_J 0x1d43d #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_K 0x1d43e #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_L 0x1d43f #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_M 0x1d440 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_N 0x1d441 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_O 0x1d442 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_P 0x1d443 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_Q 0x1d444 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_R 0x1d445 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_S 0x1d446 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_T 0x1d447 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_U 0x1d448 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_V 0x1d449 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_W 0x1d44a #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_X 0x1d44b #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_Y 0x1d44c #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_Z 0x1d44d #define UNICODE_MATHEMATICAL_ITALIC_SMALL_A 0x1d44e #define UNICODE_MATHEMATICAL_ITALIC_SMALL_B 0x1d44f #define UNICODE_MATHEMATICAL_ITALIC_SMALL_C 0x1d450 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_D 0x1d451 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_E 0x1d452 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_F 0x1d453 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_G 0x1d454 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_I 0x1d456 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_J 0x1d457 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_K 0x1d458 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_L 0x1d459 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_M 0x1d45a #define UNICODE_MATHEMATICAL_ITALIC_SMALL_N 0x1d45b #define UNICODE_MATHEMATICAL_ITALIC_SMALL_O 0x1d45c #define UNICODE_MATHEMATICAL_ITALIC_SMALL_P 0x1d45d #define UNICODE_MATHEMATICAL_ITALIC_SMALL_Q 0x1d45e #define UNICODE_MATHEMATICAL_ITALIC_SMALL_R 0x1d45f #define UNICODE_MATHEMATICAL_ITALIC_SMALL_S 0x1d460 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_T 0x1d461 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_U 0x1d462 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_V 0x1d463 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_W 0x1d464 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_X 0x1d465 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_Y 0x1d466 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_Z 0x1d467 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_A 0x1d468 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_B 0x1d469 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_C 0x1d46a #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_D 0x1d46b #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_E 0x1d46c #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_F 0x1d46d #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_G 0x1d46e #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_H 0x1d46f #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_I 0x1d470 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_J 0x1d471 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_K 0x1d472 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_L 0x1d473 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_M 0x1d474 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_N 0x1d475 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_O 0x1d476 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_P 0x1d477 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_Q 0x1d478 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_R 0x1d479 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_S 0x1d47a #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_T 0x1d47b #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_U 0x1d47c #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_V 0x1d47d #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_W 0x1d47e #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_X 0x1d47f #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_Y 0x1d480 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_Z 0x1d481 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_A 0x1d482 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_B 0x1d483 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_C 0x1d484 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_D 0x1d485 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_E 0x1d486 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_F 0x1d487 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_G 0x1d488 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_H 0x1d489 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_I 0x1d48a #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_J 0x1d48b #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_K 0x1d48c #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_L 0x1d48d #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_M 0x1d48e #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_N 0x1d48f #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_O 0x1d490 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_P 0x1d491 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_Q 0x1d492 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_R 0x1d493 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_S 0x1d494 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_T 0x1d495 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_U 0x1d496 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_V 0x1d497 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_W 0x1d498 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_X 0x1d499 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_Y 0x1d49a #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_Z 0x1d49b #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_A 0x1d49c #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_C 0x1d49e #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_D 0x1d49f #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_G 0x1d4a2 #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_J 0x1d4a5 #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_K 0x1d4a6 #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_N 0x1d4a9 #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_O 0x1d4aa #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_P 0x1d4ab #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_Q 0x1d4ac #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_S 0x1d4ae #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_T 0x1d4af #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_U 0x1d4b0 #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_V 0x1d4b1 #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_W 0x1d4b2 #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_X 0x1d4b3 #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_Y 0x1d4b4 #define UNICODE_MATHEMATICAL_SCRIPT_CAPITAL_Z 0x1d4b5 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_A 0x1d4b6 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_B 0x1d4b7 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_C 0x1d4b8 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_D 0x1d4b9 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_F 0x1d4bb #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_H 0x1d4bd #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_I 0x1d4be #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_J 0x1d4bf #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_K 0x1d4c0 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_L 0x1d4c1 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_M 0x1d4c2 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_N 0x1d4c3 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_P 0x1d4c5 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_Q 0x1d4c6 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_R 0x1d4c7 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_S 0x1d4c8 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_T 0x1d4c9 #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_U 0x1d4ca #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_V 0x1d4cb #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_W 0x1d4cc #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_X 0x1d4cd #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_Y 0x1d4ce #define UNICODE_MATHEMATICAL_SCRIPT_SMALL_Z 0x1d4cf #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_A 0x1d4d0 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_B 0x1d4d1 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_C 0x1d4d2 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_D 0x1d4d3 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_E 0x1d4d4 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_F 0x1d4d5 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_G 0x1d4d6 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_H 0x1d4d7 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_I 0x1d4d8 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_J 0x1d4d9 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_K 0x1d4da #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_L 0x1d4db #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_M 0x1d4dc #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_N 0x1d4dd #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_O 0x1d4de #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_P 0x1d4df #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_Q 0x1d4e0 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_R 0x1d4e1 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_S 0x1d4e2 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_T 0x1d4e3 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_U 0x1d4e4 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_V 0x1d4e5 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_W 0x1d4e6 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_X 0x1d4e7 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_Y 0x1d4e8 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_CAPITAL_Z 0x1d4e9 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_A 0x1d4ea #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_B 0x1d4eb #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_C 0x1d4ec #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_D 0x1d4ed #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_E 0x1d4ee #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_F 0x1d4ef #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_G 0x1d4f0 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_H 0x1d4f1 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_I 0x1d4f2 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_J 0x1d4f3 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_K 0x1d4f4 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_L 0x1d4f5 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_M 0x1d4f6 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_N 0x1d4f7 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_O 0x1d4f8 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_P 0x1d4f9 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_Q 0x1d4fa #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_R 0x1d4fb #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_S 0x1d4fc #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_T 0x1d4fd #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_U 0x1d4fe #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_V 0x1d4ff #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_W 0x1d500 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_X 0x1d501 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_Y 0x1d502 #define UNICODE_MATHEMATICAL_BOLD_SCRIPT_SMALL_Z 0x1d503 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_A 0x1d504 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_B 0x1d505 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_D 0x1d507 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_E 0x1d508 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_F 0x1d509 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_G 0x1d50a #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_J 0x1d50d #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_K 0x1d50e #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_L 0x1d50f #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_M 0x1d510 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_N 0x1d511 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_O 0x1d512 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_P 0x1d513 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_Q 0x1d514 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_S 0x1d516 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_T 0x1d517 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_U 0x1d518 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_V 0x1d519 #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_W 0x1d51a #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_X 0x1d51b #define UNICODE_MATHEMATICAL_FRAKTUR_CAPITAL_Y 0x1d51c #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_A 0x1d51e #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_B 0x1d51f #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_C 0x1d520 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_D 0x1d521 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_E 0x1d522 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_F 0x1d523 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_G 0x1d524 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_H 0x1d525 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_I 0x1d526 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_J 0x1d527 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_K 0x1d528 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_L 0x1d529 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_M 0x1d52a #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_N 0x1d52b #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_O 0x1d52c #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_P 0x1d52d #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_Q 0x1d52e #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_R 0x1d52f #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_S 0x1d530 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_T 0x1d531 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_U 0x1d532 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_V 0x1d533 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_W 0x1d534 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_X 0x1d535 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_Y 0x1d536 #define UNICODE_MATHEMATICAL_FRAKTUR_SMALL_Z 0x1d537 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_A 0x1d538 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_B 0x1d539 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_D 0x1d53b #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_E 0x1d53c #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_F 0x1d53d #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_G 0x1d53e #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_I 0x1d540 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_J 0x1d541 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_K 0x1d542 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_L 0x1d543 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_M 0x1d544 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_O 0x1d546 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_S 0x1d54a #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_T 0x1d54b #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_U 0x1d54c #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_V 0x1d54d #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_W 0x1d54e #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_X 0x1d54f #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_CAPITAL_Y 0x1d550 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_A 0x1d552 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_B 0x1d553 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_C 0x1d554 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_D 0x1d555 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_E 0x1d556 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_F 0x1d557 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_G 0x1d558 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_H 0x1d559 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_I 0x1d55a #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_J 0x1d55b #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_K 0x1d55c #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_L 0x1d55d #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_M 0x1d55e #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_N 0x1d55f #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_O 0x1d560 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_P 0x1d561 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_Q 0x1d562 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_R 0x1d563 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_S 0x1d564 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_T 0x1d565 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_U 0x1d566 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_V 0x1d567 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_W 0x1d568 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_X 0x1d569 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_Y 0x1d56a #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_SMALL_Z 0x1d56b #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_A 0x1d56c #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_B 0x1d56d #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_C 0x1d56e #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_D 0x1d56f #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_E 0x1d570 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_F 0x1d571 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_G 0x1d572 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_H 0x1d573 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_I 0x1d574 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_J 0x1d575 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_K 0x1d576 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_L 0x1d577 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_M 0x1d578 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_N 0x1d579 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_O 0x1d57a #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_P 0x1d57b #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_Q 0x1d57c #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_R 0x1d57d #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_S 0x1d57e #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_T 0x1d57f #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_U 0x1d580 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_V 0x1d581 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_W 0x1d582 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_X 0x1d583 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_Y 0x1d584 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_CAPITAL_Z 0x1d585 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_A 0x1d586 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_B 0x1d587 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_C 0x1d588 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_D 0x1d589 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_E 0x1d58a #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_F 0x1d58b #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_G 0x1d58c #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_H 0x1d58d #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_I 0x1d58e #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_J 0x1d58f #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_K 0x1d590 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_L 0x1d591 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_M 0x1d592 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_N 0x1d593 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_O 0x1d594 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_P 0x1d595 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_Q 0x1d596 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_R 0x1d597 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_S 0x1d598 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_T 0x1d599 #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_U 0x1d59a #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_V 0x1d59b #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_W 0x1d59c #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_X 0x1d59d #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_Y 0x1d59e #define UNICODE_MATHEMATICAL_BOLD_FRAKTUR_SMALL_Z 0x1d59f #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_A 0x1d5a0 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_B 0x1d5a1 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_C 0x1d5a2 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_D 0x1d5a3 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_E 0x1d5a4 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_F 0x1d5a5 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_G 0x1d5a6 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_H 0x1d5a7 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_I 0x1d5a8 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_J 0x1d5a9 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_K 0x1d5aa #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_L 0x1d5ab #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_M 0x1d5ac #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_N 0x1d5ad #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_O 0x1d5ae #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_P 0x1d5af #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_Q 0x1d5b0 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_R 0x1d5b1 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_S 0x1d5b2 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_T 0x1d5b3 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_U 0x1d5b4 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_V 0x1d5b5 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_W 0x1d5b6 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_X 0x1d5b7 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_Y 0x1d5b8 #define UNICODE_MATHEMATICAL_SANS_SERIF_CAPITAL_Z 0x1d5b9 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_A 0x1d5ba #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_B 0x1d5bb #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_C 0x1d5bc #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_D 0x1d5bd #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_E 0x1d5be #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_F 0x1d5bf #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_G 0x1d5c0 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_H 0x1d5c1 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_I 0x1d5c2 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_J 0x1d5c3 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_K 0x1d5c4 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_L 0x1d5c5 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_M 0x1d5c6 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_N 0x1d5c7 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_O 0x1d5c8 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_P 0x1d5c9 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_Q 0x1d5ca #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_R 0x1d5cb #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_S 0x1d5cc #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_T 0x1d5cd #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_U 0x1d5ce #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_V 0x1d5cf #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_W 0x1d5d0 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_X 0x1d5d1 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_Y 0x1d5d2 #define UNICODE_MATHEMATICAL_SANS_SERIF_SMALL_Z 0x1d5d3 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_A 0x1d5d4 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_B 0x1d5d5 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_C 0x1d5d6 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_D 0x1d5d7 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_E 0x1d5d8 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_F 0x1d5d9 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_G 0x1d5da #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_H 0x1d5db #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_I 0x1d5dc #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_J 0x1d5dd #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_K 0x1d5de #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_L 0x1d5df #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_M 0x1d5e0 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_N 0x1d5e1 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_O 0x1d5e2 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_P 0x1d5e3 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_Q 0x1d5e4 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_R 0x1d5e5 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_S 0x1d5e6 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_T 0x1d5e7 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_U 0x1d5e8 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_V 0x1d5e9 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_W 0x1d5ea #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_X 0x1d5eb #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_Y 0x1d5ec #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_Z 0x1d5ed #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_A 0x1d5ee #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_B 0x1d5ef #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_C 0x1d5f0 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_D 0x1d5f1 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_E 0x1d5f2 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_F 0x1d5f3 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_G 0x1d5f4 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_H 0x1d5f5 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_I 0x1d5f6 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_J 0x1d5f7 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_K 0x1d5f8 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_L 0x1d5f9 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_M 0x1d5fa #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_N 0x1d5fb #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_O 0x1d5fc #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_P 0x1d5fd #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_Q 0x1d5fe #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_R 0x1d5ff #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_S 0x1d600 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_T 0x1d601 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_U 0x1d602 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_V 0x1d603 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_W 0x1d604 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_X 0x1d605 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_Y 0x1d606 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_Z 0x1d607 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_A 0x1d608 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_B 0x1d609 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_C 0x1d60a #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_D 0x1d60b #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_E 0x1d60c #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_F 0x1d60d #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_G 0x1d60e #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_H 0x1d60f #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_I 0x1d610 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_J 0x1d611 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_K 0x1d612 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_L 0x1d613 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_M 0x1d614 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_N 0x1d615 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_O 0x1d616 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_P 0x1d617 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_Q 0x1d618 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_R 0x1d619 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_S 0x1d61a #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_T 0x1d61b #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_U 0x1d61c #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_V 0x1d61d #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_W 0x1d61e #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_X 0x1d61f #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_Y 0x1d620 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_CAPITAL_Z 0x1d621 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_A 0x1d622 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_B 0x1d623 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_C 0x1d624 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_D 0x1d625 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_E 0x1d626 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_F 0x1d627 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_G 0x1d628 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_H 0x1d629 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_I 0x1d62a #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_J 0x1d62b #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_K 0x1d62c #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_L 0x1d62d #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_M 0x1d62e #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_N 0x1d62f #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_O 0x1d630 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_P 0x1d631 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_Q 0x1d632 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_R 0x1d633 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_S 0x1d634 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_T 0x1d635 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_U 0x1d636 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_V 0x1d637 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_W 0x1d638 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_X 0x1d639 #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_Y 0x1d63a #define UNICODE_MATHEMATICAL_SANS_SERIF_ITALIC_SMALL_Z 0x1d63b #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_A 0x1d63c #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_B 0x1d63d #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_C 0x1d63e #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_D 0x1d63f #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_E 0x1d640 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_F 0x1d641 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_G 0x1d642 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_H 0x1d643 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_I 0x1d644 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_J 0x1d645 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_K 0x1d646 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_L 0x1d647 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_M 0x1d648 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_N 0x1d649 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_O 0x1d64a #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_P 0x1d64b #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_Q 0x1d64c #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_R 0x1d64d #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_S 0x1d64e #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_T 0x1d64f #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_U 0x1d650 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_V 0x1d651 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_W 0x1d652 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_X 0x1d653 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_Y 0x1d654 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_Z 0x1d655 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_A 0x1d656 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_B 0x1d657 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_C 0x1d658 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_D 0x1d659 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_E 0x1d65a #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_F 0x1d65b #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_G 0x1d65c #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_H 0x1d65d #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_I 0x1d65e #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_J 0x1d65f #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_K 0x1d660 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_L 0x1d661 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_M 0x1d662 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_N 0x1d663 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_O 0x1d664 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_P 0x1d665 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_Q 0x1d666 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_R 0x1d667 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_S 0x1d668 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_T 0x1d669 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_U 0x1d66a #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_V 0x1d66b #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_W 0x1d66c #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_X 0x1d66d #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_Y 0x1d66e #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_Z 0x1d66f #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_A 0x1d670 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_B 0x1d671 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_C 0x1d672 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_D 0x1d673 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_E 0x1d674 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_F 0x1d675 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_G 0x1d676 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_H 0x1d677 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_I 0x1d678 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_J 0x1d679 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_K 0x1d67a #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_L 0x1d67b #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_M 0x1d67c #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_N 0x1d67d #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_O 0x1d67e #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_P 0x1d67f #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_Q 0x1d680 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_R 0x1d681 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_S 0x1d682 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_T 0x1d683 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_U 0x1d684 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_V 0x1d685 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_W 0x1d686 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_X 0x1d687 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_Y 0x1d688 #define UNICODE_MATHEMATICAL_MONOSPACE_CAPITAL_Z 0x1d689 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_A 0x1d68a #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_B 0x1d68b #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_C 0x1d68c #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_D 0x1d68d #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_E 0x1d68e #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_F 0x1d68f #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_G 0x1d690 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_H 0x1d691 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_I 0x1d692 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_J 0x1d693 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_K 0x1d694 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_L 0x1d695 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_M 0x1d696 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_N 0x1d697 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_O 0x1d698 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_P 0x1d699 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_Q 0x1d69a #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_R 0x1d69b #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_S 0x1d69c #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_T 0x1d69d #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_U 0x1d69e #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_V 0x1d69f #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_W 0x1d6a0 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_X 0x1d6a1 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_Y 0x1d6a2 #define UNICODE_MATHEMATICAL_MONOSPACE_SMALL_Z 0x1d6a3 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_DOTLESS_I 0x1d6a4 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_DOTLESS_J 0x1d6a5 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_ALPHA 0x1d6a8 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_BETA 0x1d6a9 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_GAMMA 0x1d6aa #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_DELTA 0x1d6ab #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_EPSILON 0x1d6ac #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_ZETA 0x1d6ad #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_ETA 0x1d6ae #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_THETA 0x1d6af #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_IOTA 0x1d6b0 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_KAPPA 0x1d6b1 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_LAMDA 0x1d6b2 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_MU 0x1d6b3 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_NU 0x1d6b4 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_XI 0x1d6b5 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_OMICRON 0x1d6b6 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_PI 0x1d6b7 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_RHO 0x1d6b8 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_THETA_SYMBOL 0x1d6b9 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_SIGMA 0x1d6ba #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_TAU 0x1d6bb #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_UPSILON 0x1d6bc #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_PHI 0x1d6bd #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_CHI 0x1d6be #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_PSI 0x1d6bf #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_OMEGA 0x1d6c0 #define UNICODE_MATHEMATICAL_BOLD_NABLA 0x1d6c1 #define UNICODE_MATHEMATICAL_BOLD_SMALL_ALPHA 0x1d6c2 #define UNICODE_MATHEMATICAL_BOLD_SMALL_BETA 0x1d6c3 #define UNICODE_MATHEMATICAL_BOLD_SMALL_GAMMA 0x1d6c4 #define UNICODE_MATHEMATICAL_BOLD_SMALL_DELTA 0x1d6c5 #define UNICODE_MATHEMATICAL_BOLD_SMALL_EPSILON 0x1d6c6 #define UNICODE_MATHEMATICAL_BOLD_SMALL_ZETA 0x1d6c7 #define UNICODE_MATHEMATICAL_BOLD_SMALL_ETA 0x1d6c8 #define UNICODE_MATHEMATICAL_BOLD_SMALL_THETA 0x1d6c9 #define UNICODE_MATHEMATICAL_BOLD_SMALL_IOTA 0x1d6ca #define UNICODE_MATHEMATICAL_BOLD_SMALL_KAPPA 0x1d6cb #define UNICODE_MATHEMATICAL_BOLD_SMALL_LAMDA 0x1d6cc #define UNICODE_MATHEMATICAL_BOLD_SMALL_MU 0x1d6cd #define UNICODE_MATHEMATICAL_BOLD_SMALL_NU 0x1d6ce #define UNICODE_MATHEMATICAL_BOLD_SMALL_XI 0x1d6cf #define UNICODE_MATHEMATICAL_BOLD_SMALL_OMICRON 0x1d6d0 #define UNICODE_MATHEMATICAL_BOLD_SMALL_PI 0x1d6d1 #define UNICODE_MATHEMATICAL_BOLD_SMALL_RHO 0x1d6d2 #define UNICODE_MATHEMATICAL_BOLD_SMALL_FINAL_SIGMA 0x1d6d3 #define UNICODE_MATHEMATICAL_BOLD_SMALL_SIGMA 0x1d6d4 #define UNICODE_MATHEMATICAL_BOLD_SMALL_TAU 0x1d6d5 #define UNICODE_MATHEMATICAL_BOLD_SMALL_UPSILON 0x1d6d6 #define UNICODE_MATHEMATICAL_BOLD_SMALL_PHI 0x1d6d7 #define UNICODE_MATHEMATICAL_BOLD_SMALL_CHI 0x1d6d8 #define UNICODE_MATHEMATICAL_BOLD_SMALL_PSI 0x1d6d9 #define UNICODE_MATHEMATICAL_BOLD_SMALL_OMEGA 0x1d6da #define UNICODE_MATHEMATICAL_BOLD_PARTIAL_DIFFERENTIAL 0x1d6db #define UNICODE_MATHEMATICAL_BOLD_EPSILON_SYMBOL 0x1d6dc #define UNICODE_MATHEMATICAL_BOLD_THETA_SYMBOL 0x1d6dd #define UNICODE_MATHEMATICAL_BOLD_KAPPA_SYMBOL 0x1d6de #define UNICODE_MATHEMATICAL_BOLD_PHI_SYMBOL 0x1d6df #define UNICODE_MATHEMATICAL_BOLD_RHO_SYMBOL 0x1d6e0 #define UNICODE_MATHEMATICAL_BOLD_PI_SYMBOL 0x1d6e1 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_ALPHA 0x1d6e2 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_BETA 0x1d6e3 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_GAMMA 0x1d6e4 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_DELTA 0x1d6e5 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_EPSILON 0x1d6e6 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_ZETA 0x1d6e7 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_ETA 0x1d6e8 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_THETA 0x1d6e9 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_IOTA 0x1d6ea #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_KAPPA 0x1d6eb #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_LAMDA 0x1d6ec #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_MU 0x1d6ed #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_NU 0x1d6ee #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_XI 0x1d6ef #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_OMICRON 0x1d6f0 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_PI 0x1d6f1 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_RHO 0x1d6f2 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_THETA_SYMBOL 0x1d6f3 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_SIGMA 0x1d6f4 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_TAU 0x1d6f5 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_UPSILON 0x1d6f6 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_PHI 0x1d6f7 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_CHI 0x1d6f8 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_PSI 0x1d6f9 #define UNICODE_MATHEMATICAL_ITALIC_CAPITAL_OMEGA 0x1d6fa #define UNICODE_MATHEMATICAL_ITALIC_NABLA 0x1d6fb #define UNICODE_MATHEMATICAL_ITALIC_SMALL_ALPHA 0x1d6fc #define UNICODE_MATHEMATICAL_ITALIC_SMALL_BETA 0x1d6fd #define UNICODE_MATHEMATICAL_ITALIC_SMALL_GAMMA 0x1d6fe #define UNICODE_MATHEMATICAL_ITALIC_SMALL_DELTA 0x1d6ff #define UNICODE_MATHEMATICAL_ITALIC_SMALL_EPSILON 0x1d700 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_ZETA 0x1d701 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_ETA 0x1d702 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_THETA 0x1d703 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_IOTA 0x1d704 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_KAPPA 0x1d705 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_LAMDA 0x1d706 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_MU 0x1d707 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_NU 0x1d708 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_XI 0x1d709 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_OMICRON 0x1d70a #define UNICODE_MATHEMATICAL_ITALIC_SMALL_PI 0x1d70b #define UNICODE_MATHEMATICAL_ITALIC_SMALL_RHO 0x1d70c #define UNICODE_MATHEMATICAL_ITALIC_SMALL_FINAL_SIGMA 0x1d70d #define UNICODE_MATHEMATICAL_ITALIC_SMALL_SIGMA 0x1d70e #define UNICODE_MATHEMATICAL_ITALIC_SMALL_TAU 0x1d70f #define UNICODE_MATHEMATICAL_ITALIC_SMALL_UPSILON 0x1d710 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_PHI 0x1d711 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_CHI 0x1d712 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_PSI 0x1d713 #define UNICODE_MATHEMATICAL_ITALIC_SMALL_OMEGA 0x1d714 #define UNICODE_MATHEMATICAL_ITALIC_PARTIAL_DIFFERENTIAL 0x1d715 #define UNICODE_MATHEMATICAL_ITALIC_EPSILON_SYMBOL 0x1d716 #define UNICODE_MATHEMATICAL_ITALIC_THETA_SYMBOL 0x1d717 #define UNICODE_MATHEMATICAL_ITALIC_KAPPA_SYMBOL 0x1d718 #define UNICODE_MATHEMATICAL_ITALIC_PHI_SYMBOL 0x1d719 #define UNICODE_MATHEMATICAL_ITALIC_RHO_SYMBOL 0x1d71a #define UNICODE_MATHEMATICAL_ITALIC_PI_SYMBOL 0x1d71b #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_ALPHA 0x1d71c #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_BETA 0x1d71d #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_GAMMA 0x1d71e #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_DELTA 0x1d71f #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_EPSILON 0x1d720 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_ZETA 0x1d721 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_ETA 0x1d722 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_THETA 0x1d723 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_IOTA 0x1d724 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_KAPPA 0x1d725 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_LAMDA 0x1d726 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_MU 0x1d727 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_NU 0x1d728 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_XI 0x1d729 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_OMICRON 0x1d72a #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_PI 0x1d72b #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_RHO 0x1d72c #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_THETA_SYMBOL 0x1d72d #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_SIGMA 0x1d72e #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_TAU 0x1d72f #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_UPSILON 0x1d730 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_PHI 0x1d731 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_CHI 0x1d732 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_PSI 0x1d733 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_CAPITAL_OMEGA 0x1d734 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_NABLA 0x1d735 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_ALPHA 0x1d736 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_BETA 0x1d737 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_GAMMA 0x1d738 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_DELTA 0x1d739 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_EPSILON 0x1d73a #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_ZETA 0x1d73b #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_ETA 0x1d73c #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_THETA 0x1d73d #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_IOTA 0x1d73e #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_KAPPA 0x1d73f #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_LAMDA 0x1d740 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_MU 0x1d741 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_NU 0x1d742 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_XI 0x1d743 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_OMICRON 0x1d744 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_PI 0x1d745 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_RHO 0x1d746 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_FINAL_SIGMA 0x1d747 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_SIGMA 0x1d748 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_TAU 0x1d749 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_UPSILON 0x1d74a #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_PHI 0x1d74b #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_CHI 0x1d74c #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_PSI 0x1d74d #define UNICODE_MATHEMATICAL_BOLD_ITALIC_SMALL_OMEGA 0x1d74e #define UNICODE_MATHEMATICAL_BOLD_ITALIC_PARTIAL_DIFFERENTIAL 0x1d74f #define UNICODE_MATHEMATICAL_BOLD_ITALIC_EPSILON_SYMBOL 0x1d750 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_THETA_SYMBOL 0x1d751 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_KAPPA_SYMBOL 0x1d752 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_PHI_SYMBOL 0x1d753 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_RHO_SYMBOL 0x1d754 #define UNICODE_MATHEMATICAL_BOLD_ITALIC_PI_SYMBOL 0x1d755 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_ALPHA 0x1d756 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_BETA 0x1d757 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_GAMMA 0x1d758 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_DELTA 0x1d759 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_EPSILON 0x1d75a #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_ZETA 0x1d75b #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_ETA 0x1d75c #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_THETA 0x1d75d #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_IOTA 0x1d75e #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_KAPPA 0x1d75f #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_LAMDA 0x1d760 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_MU 0x1d761 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_NU 0x1d762 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_XI 0x1d763 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_OMICRON 0x1d764 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_PI 0x1d765 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_RHO 0x1d766 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_THETA_SYMBOL 0x1d767 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_SIGMA 0x1d768 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_TAU 0x1d769 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_UPSILON 0x1d76a #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_PHI 0x1d76b #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_CHI 0x1d76c #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_PSI 0x1d76d #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_CAPITAL_OMEGA 0x1d76e #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_NABLA 0x1d76f #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_ALPHA 0x1d770 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_BETA 0x1d771 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_GAMMA 0x1d772 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_DELTA 0x1d773 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_EPSILON 0x1d774 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_ZETA 0x1d775 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_ETA 0x1d776 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_THETA 0x1d777 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_IOTA 0x1d778 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_KAPPA 0x1d779 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_LAMDA 0x1d77a #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_MU 0x1d77b #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_NU 0x1d77c #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_XI 0x1d77d #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_OMICRON 0x1d77e #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_PI 0x1d77f #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_RHO 0x1d780 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_FINAL_SIGMA 0x1d781 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_SIGMA 0x1d782 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_TAU 0x1d783 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_UPSILON 0x1d784 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_PHI 0x1d785 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_CHI 0x1d786 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_PSI 0x1d787 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_SMALL_OMEGA 0x1d788 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_PARTIAL_DIFFERENTIAL 0x1d789 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_EPSILON_SYMBOL 0x1d78a #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_THETA_SYMBOL 0x1d78b #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_KAPPA_SYMBOL 0x1d78c #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_PHI_SYMBOL 0x1d78d #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_RHO_SYMBOL 0x1d78e #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_PI_SYMBOL 0x1d78f #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_ALPHA 0x1d790 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_BETA 0x1d791 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_GAMMA 0x1d792 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_DELTA 0x1d793 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_EPSILON 0x1d794 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_ZETA 0x1d795 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_ETA 0x1d796 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_THETA 0x1d797 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_IOTA 0x1d798 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_KAPPA 0x1d799 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_LAMDA 0x1d79a #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_MU 0x1d79b #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_NU 0x1d79c #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_XI 0x1d79d #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_OMICRON 0x1d79e #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_PI 0x1d79f #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_RHO 0x1d7a0 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_THETA_SYMBOL 0x1d7a1 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_SIGMA 0x1d7a2 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_TAU 0x1d7a3 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_UPSILON 0x1d7a4 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_PHI 0x1d7a5 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_CHI 0x1d7a6 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_PSI 0x1d7a7 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_CAPITAL_OMEGA 0x1d7a8 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_NABLA 0x1d7a9 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_ALPHA 0x1d7aa #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_BETA 0x1d7ab #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_GAMMA 0x1d7ac #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_DELTA 0x1d7ad #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_EPSILON 0x1d7ae #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_ZETA 0x1d7af #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_ETA 0x1d7b0 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_THETA 0x1d7b1 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_IOTA 0x1d7b2 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_KAPPA 0x1d7b3 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_LAMDA 0x1d7b4 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_MU 0x1d7b5 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_NU 0x1d7b6 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_XI 0x1d7b7 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_OMICRON 0x1d7b8 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_PI 0x1d7b9 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_RHO 0x1d7ba #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_FINAL_SIGMA 0x1d7bb #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_SIGMA 0x1d7bc #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_TAU 0x1d7bd #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_UPSILON 0x1d7be #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_PHI 0x1d7bf #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_CHI 0x1d7c0 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_PSI 0x1d7c1 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_SMALL_OMEGA 0x1d7c2 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_PARTIAL_DIFFERENTIAL 0x1d7c3 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_EPSILON_SYMBOL 0x1d7c4 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_THETA_SYMBOL 0x1d7c5 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_KAPPA_SYMBOL 0x1d7c6 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_PHI_SYMBOL 0x1d7c7 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_RHO_SYMBOL 0x1d7c8 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_ITALIC_PI_SYMBOL 0x1d7c9 #define UNICODE_MATHEMATICAL_BOLD_CAPITAL_DIGAMMA 0x1d7ca #define UNICODE_MATHEMATICAL_BOLD_SMALL_DIGAMMA 0x1d7cb #define UNICODE_MATHEMATICAL_BOLD_DIGIT_ZERO 0x1d7ce #define UNICODE_MATHEMATICAL_BOLD_DIGIT_ONE 0x1d7cf #define UNICODE_MATHEMATICAL_BOLD_DIGIT_TWO 0x1d7d0 #define UNICODE_MATHEMATICAL_BOLD_DIGIT_THREE 0x1d7d1 #define UNICODE_MATHEMATICAL_BOLD_DIGIT_FOUR 0x1d7d2 #define UNICODE_MATHEMATICAL_BOLD_DIGIT_FIVE 0x1d7d3 #define UNICODE_MATHEMATICAL_BOLD_DIGIT_SIX 0x1d7d4 #define UNICODE_MATHEMATICAL_BOLD_DIGIT_SEVEN 0x1d7d5 #define UNICODE_MATHEMATICAL_BOLD_DIGIT_EIGHT 0x1d7d6 #define UNICODE_MATHEMATICAL_BOLD_DIGIT_NINE 0x1d7d7 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_ZERO 0x1d7d8 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_ONE 0x1d7d9 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_TWO 0x1d7da #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_THREE 0x1d7db #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_FOUR 0x1d7dc #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_FIVE 0x1d7dd #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_SIX 0x1d7de #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_SEVEN 0x1d7df #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_EIGHT 0x1d7e0 #define UNICODE_MATHEMATICAL_DOUBLE_STRUCK_DIGIT_NINE 0x1d7e1 #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_ZERO 0x1d7e2 #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_ONE 0x1d7e3 #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_TWO 0x1d7e4 #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_THREE 0x1d7e5 #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_FOUR 0x1d7e6 #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_FIVE 0x1d7e7 #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_SIX 0x1d7e8 #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_SEVEN 0x1d7e9 #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_EIGHT 0x1d7ea #define UNICODE_MATHEMATICAL_SANS_SERIF_DIGIT_NINE 0x1d7eb #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_ZERO 0x1d7ec #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_ONE 0x1d7ed #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_TWO 0x1d7ee #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_THREE 0x1d7ef #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_FOUR 0x1d7f0 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_FIVE 0x1d7f1 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_SIX 0x1d7f2 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_SEVEN 0x1d7f3 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_EIGHT 0x1d7f4 #define UNICODE_MATHEMATICAL_SANS_SERIF_BOLD_DIGIT_NINE 0x1d7f5 #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_ZERO 0x1d7f6 #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_ONE 0x1d7f7 #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_TWO 0x1d7f8 #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_THREE 0x1d7f9 #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_FOUR 0x1d7fa #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_FIVE 0x1d7fb #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_SIX 0x1d7fc #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_SEVEN 0x1d7fd #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_EIGHT 0x1d7fe #define UNICODE_MATHEMATICAL_MONOSPACE_DIGIT_NINE 0x1d7ff #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F800 0x2f800 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F801 0x2f801 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F802 0x2f802 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F803 0x2f803 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F804 0x2f804 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F805 0x2f805 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F806 0x2f806 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F807 0x2f807 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F808 0x2f808 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F809 0x2f809 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F80A 0x2f80a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F80B 0x2f80b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F80C 0x2f80c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F80D 0x2f80d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F80E 0x2f80e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F80F 0x2f80f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F810 0x2f810 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F811 0x2f811 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F812 0x2f812 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F813 0x2f813 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F814 0x2f814 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F815 0x2f815 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F816 0x2f816 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F817 0x2f817 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F818 0x2f818 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F819 0x2f819 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F81A 0x2f81a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F81B 0x2f81b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F81C 0x2f81c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F81D 0x2f81d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F81E 0x2f81e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F81F 0x2f81f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F820 0x2f820 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F821 0x2f821 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F822 0x2f822 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F823 0x2f823 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F824 0x2f824 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F825 0x2f825 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F826 0x2f826 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F827 0x2f827 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F828 0x2f828 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F829 0x2f829 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F82A 0x2f82a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F82B 0x2f82b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F82C 0x2f82c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F82D 0x2f82d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F82E 0x2f82e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F82F 0x2f82f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F830 0x2f830 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F831 0x2f831 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F832 0x2f832 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F833 0x2f833 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F834 0x2f834 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F835 0x2f835 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F836 0x2f836 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F837 0x2f837 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F838 0x2f838 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F839 0x2f839 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F83A 0x2f83a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F83B 0x2f83b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F83C 0x2f83c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F83D 0x2f83d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F83E 0x2f83e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F83F 0x2f83f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F840 0x2f840 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F841 0x2f841 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F842 0x2f842 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F843 0x2f843 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F844 0x2f844 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F845 0x2f845 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F846 0x2f846 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F847 0x2f847 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F848 0x2f848 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F849 0x2f849 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F84A 0x2f84a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F84B 0x2f84b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F84C 0x2f84c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F84D 0x2f84d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F84E 0x2f84e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F84F 0x2f84f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F850 0x2f850 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F851 0x2f851 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F852 0x2f852 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F853 0x2f853 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F854 0x2f854 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F855 0x2f855 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F856 0x2f856 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F857 0x2f857 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F858 0x2f858 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F859 0x2f859 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F85A 0x2f85a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F85B 0x2f85b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F85C 0x2f85c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F85D 0x2f85d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F85E 0x2f85e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F85F 0x2f85f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F860 0x2f860 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F861 0x2f861 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F862 0x2f862 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F863 0x2f863 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F864 0x2f864 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F865 0x2f865 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F866 0x2f866 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F867 0x2f867 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F868 0x2f868 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F869 0x2f869 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F86A 0x2f86a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F86B 0x2f86b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F86C 0x2f86c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F86D 0x2f86d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F86E 0x2f86e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F86F 0x2f86f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F870 0x2f870 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F871 0x2f871 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F872 0x2f872 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F873 0x2f873 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F874 0x2f874 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F875 0x2f875 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F876 0x2f876 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F877 0x2f877 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F878 0x2f878 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F879 0x2f879 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F87A 0x2f87a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F87B 0x2f87b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F87C 0x2f87c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F87D 0x2f87d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F87E 0x2f87e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F87F 0x2f87f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F880 0x2f880 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F881 0x2f881 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F882 0x2f882 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F883 0x2f883 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F884 0x2f884 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F885 0x2f885 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F886 0x2f886 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F887 0x2f887 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F888 0x2f888 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F889 0x2f889 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F88A 0x2f88a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F88B 0x2f88b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F88C 0x2f88c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F88D 0x2f88d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F88E 0x2f88e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F88F 0x2f88f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F890 0x2f890 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F891 0x2f891 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F892 0x2f892 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F893 0x2f893 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F894 0x2f894 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F895 0x2f895 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F896 0x2f896 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F897 0x2f897 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F898 0x2f898 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F899 0x2f899 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F89A 0x2f89a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F89B 0x2f89b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F89C 0x2f89c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F89D 0x2f89d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F89E 0x2f89e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F89F 0x2f89f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A0 0x2f8a0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A1 0x2f8a1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A2 0x2f8a2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A3 0x2f8a3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A4 0x2f8a4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A5 0x2f8a5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A6 0x2f8a6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A7 0x2f8a7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A8 0x2f8a8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8A9 0x2f8a9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8AA 0x2f8aa #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8AB 0x2f8ab #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8AC 0x2f8ac #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8AD 0x2f8ad #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8AE 0x2f8ae #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8AF 0x2f8af #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B0 0x2f8b0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B1 0x2f8b1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B2 0x2f8b2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B3 0x2f8b3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B4 0x2f8b4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B5 0x2f8b5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B6 0x2f8b6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B7 0x2f8b7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B8 0x2f8b8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8B9 0x2f8b9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8BA 0x2f8ba #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8BB 0x2f8bb #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8BC 0x2f8bc #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8BD 0x2f8bd #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8BE 0x2f8be #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8BF 0x2f8bf #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C0 0x2f8c0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C1 0x2f8c1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C2 0x2f8c2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C3 0x2f8c3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C4 0x2f8c4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C5 0x2f8c5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C6 0x2f8c6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C7 0x2f8c7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C8 0x2f8c8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8C9 0x2f8c9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8CA 0x2f8ca #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8CB 0x2f8cb #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8CC 0x2f8cc #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8CD 0x2f8cd #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8CE 0x2f8ce #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8CF 0x2f8cf #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D0 0x2f8d0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D1 0x2f8d1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D2 0x2f8d2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D3 0x2f8d3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D4 0x2f8d4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D5 0x2f8d5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D6 0x2f8d6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D7 0x2f8d7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D8 0x2f8d8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8D9 0x2f8d9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8DA 0x2f8da #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8DB 0x2f8db #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8DC 0x2f8dc #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8DD 0x2f8dd #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8DE 0x2f8de #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8DF 0x2f8df #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E0 0x2f8e0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E1 0x2f8e1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E2 0x2f8e2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E3 0x2f8e3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E4 0x2f8e4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E5 0x2f8e5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E6 0x2f8e6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E7 0x2f8e7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E8 0x2f8e8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8E9 0x2f8e9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8EA 0x2f8ea #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8EB 0x2f8eb #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8EC 0x2f8ec #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8ED 0x2f8ed #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8EE 0x2f8ee #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8EF 0x2f8ef #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F0 0x2f8f0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F1 0x2f8f1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F2 0x2f8f2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F3 0x2f8f3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F4 0x2f8f4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F5 0x2f8f5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F6 0x2f8f6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F7 0x2f8f7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F8 0x2f8f8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8F9 0x2f8f9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8FA 0x2f8fa #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8FB 0x2f8fb #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8FC 0x2f8fc #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8FD 0x2f8fd #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8FE 0x2f8fe #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F8FF 0x2f8ff #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F900 0x2f900 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F901 0x2f901 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F902 0x2f902 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F903 0x2f903 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F904 0x2f904 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F905 0x2f905 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F906 0x2f906 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F907 0x2f907 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F908 0x2f908 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F909 0x2f909 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F90A 0x2f90a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F90B 0x2f90b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F90C 0x2f90c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F90D 0x2f90d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F90E 0x2f90e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F90F 0x2f90f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F910 0x2f910 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F911 0x2f911 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F912 0x2f912 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F913 0x2f913 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F914 0x2f914 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F915 0x2f915 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F916 0x2f916 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F917 0x2f917 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F918 0x2f918 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F919 0x2f919 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F91A 0x2f91a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F91B 0x2f91b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F91C 0x2f91c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F91D 0x2f91d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F91E 0x2f91e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F91F 0x2f91f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F920 0x2f920 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F921 0x2f921 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F922 0x2f922 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F923 0x2f923 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F924 0x2f924 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F925 0x2f925 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F926 0x2f926 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F927 0x2f927 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F928 0x2f928 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F929 0x2f929 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F92A 0x2f92a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F92B 0x2f92b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F92C 0x2f92c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F92D 0x2f92d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F92E 0x2f92e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F92F 0x2f92f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F930 0x2f930 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F931 0x2f931 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F932 0x2f932 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F933 0x2f933 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F934 0x2f934 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F935 0x2f935 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F936 0x2f936 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F937 0x2f937 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F938 0x2f938 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F939 0x2f939 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F93A 0x2f93a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F93B 0x2f93b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F93C 0x2f93c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F93D 0x2f93d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F93E 0x2f93e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F93F 0x2f93f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F940 0x2f940 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F941 0x2f941 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F942 0x2f942 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F943 0x2f943 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F944 0x2f944 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F945 0x2f945 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F946 0x2f946 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F947 0x2f947 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F948 0x2f948 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F949 0x2f949 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F94A 0x2f94a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F94B 0x2f94b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F94C 0x2f94c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F94D 0x2f94d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F94E 0x2f94e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F94F 0x2f94f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F950 0x2f950 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F951 0x2f951 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F952 0x2f952 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F953 0x2f953 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F954 0x2f954 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F955 0x2f955 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F956 0x2f956 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F957 0x2f957 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F958 0x2f958 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F959 0x2f959 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F95A 0x2f95a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F95B 0x2f95b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F95C 0x2f95c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F95D 0x2f95d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F95E 0x2f95e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F95F 0x2f95f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F960 0x2f960 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F961 0x2f961 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F962 0x2f962 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F963 0x2f963 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F964 0x2f964 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F965 0x2f965 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F966 0x2f966 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F967 0x2f967 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F968 0x2f968 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F969 0x2f969 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F96A 0x2f96a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F96B 0x2f96b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F96C 0x2f96c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F96D 0x2f96d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F96E 0x2f96e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F96F 0x2f96f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F970 0x2f970 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F971 0x2f971 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F972 0x2f972 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F973 0x2f973 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F974 0x2f974 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F975 0x2f975 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F976 0x2f976 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F977 0x2f977 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F978 0x2f978 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F979 0x2f979 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F97A 0x2f97a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F97B 0x2f97b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F97C 0x2f97c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F97D 0x2f97d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F97E 0x2f97e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F97F 0x2f97f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F980 0x2f980 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F981 0x2f981 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F982 0x2f982 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F983 0x2f983 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F984 0x2f984 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F985 0x2f985 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F986 0x2f986 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F987 0x2f987 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F988 0x2f988 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F989 0x2f989 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F98A 0x2f98a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F98B 0x2f98b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F98C 0x2f98c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F98D 0x2f98d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F98E 0x2f98e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F98F 0x2f98f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F990 0x2f990 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F991 0x2f991 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F992 0x2f992 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F993 0x2f993 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F994 0x2f994 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F995 0x2f995 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F996 0x2f996 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F997 0x2f997 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F998 0x2f998 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F999 0x2f999 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F99A 0x2f99a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F99B 0x2f99b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F99C 0x2f99c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F99D 0x2f99d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F99E 0x2f99e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F99F 0x2f99f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A0 0x2f9a0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A1 0x2f9a1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A2 0x2f9a2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A3 0x2f9a3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A4 0x2f9a4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A5 0x2f9a5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A6 0x2f9a6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A7 0x2f9a7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A8 0x2f9a8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9A9 0x2f9a9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9AA 0x2f9aa #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9AB 0x2f9ab #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9AC 0x2f9ac #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9AD 0x2f9ad #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9AE 0x2f9ae #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9AF 0x2f9af #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B0 0x2f9b0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B1 0x2f9b1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B2 0x2f9b2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B3 0x2f9b3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B4 0x2f9b4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B5 0x2f9b5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B6 0x2f9b6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B7 0x2f9b7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B8 0x2f9b8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9B9 0x2f9b9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9BA 0x2f9ba #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9BB 0x2f9bb #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9BC 0x2f9bc #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9BD 0x2f9bd #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9BE 0x2f9be #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9BF 0x2f9bf #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C0 0x2f9c0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C1 0x2f9c1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C2 0x2f9c2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C3 0x2f9c3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C4 0x2f9c4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C5 0x2f9c5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C6 0x2f9c6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C7 0x2f9c7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C8 0x2f9c8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9C9 0x2f9c9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9CA 0x2f9ca #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9CB 0x2f9cb #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9CC 0x2f9cc #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9CD 0x2f9cd #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9CE 0x2f9ce #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9CF 0x2f9cf #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D0 0x2f9d0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D1 0x2f9d1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D2 0x2f9d2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D3 0x2f9d3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D4 0x2f9d4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D5 0x2f9d5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D6 0x2f9d6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D7 0x2f9d7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D8 0x2f9d8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9D9 0x2f9d9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9DA 0x2f9da #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9DB 0x2f9db #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9DC 0x2f9dc #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9DD 0x2f9dd #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9DE 0x2f9de #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9DF 0x2f9df #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E0 0x2f9e0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E1 0x2f9e1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E2 0x2f9e2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E3 0x2f9e3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E4 0x2f9e4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E5 0x2f9e5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E6 0x2f9e6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E7 0x2f9e7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E8 0x2f9e8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9E9 0x2f9e9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9EA 0x2f9ea #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9EB 0x2f9eb #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9EC 0x2f9ec #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9ED 0x2f9ed #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9EE 0x2f9ee #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9EF 0x2f9ef #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F0 0x2f9f0 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F1 0x2f9f1 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F2 0x2f9f2 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F3 0x2f9f3 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F4 0x2f9f4 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F5 0x2f9f5 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F6 0x2f9f6 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F7 0x2f9f7 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F8 0x2f9f8 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9F9 0x2f9f9 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9FA 0x2f9fa #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9FB 0x2f9fb #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9FC 0x2f9fc #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9FD 0x2f9fd #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9FE 0x2f9fe #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2F9FF 0x2f9ff #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA00 0x2fa00 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA01 0x2fa01 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA02 0x2fa02 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA03 0x2fa03 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA04 0x2fa04 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA05 0x2fa05 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA06 0x2fa06 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA07 0x2fa07 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA08 0x2fa08 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA09 0x2fa09 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA0A 0x2fa0a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA0B 0x2fa0b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA0C 0x2fa0c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA0D 0x2fa0d #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA0E 0x2fa0e #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA0F 0x2fa0f #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA10 0x2fa10 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA11 0x2fa11 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA12 0x2fa12 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA13 0x2fa13 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA14 0x2fa14 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA15 0x2fa15 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA16 0x2fa16 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA17 0x2fa17 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA18 0x2fa18 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA19 0x2fa19 #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA1A 0x2fa1a #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA1B 0x2fa1b #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA1C 0x2fa1c #define UNICODE_CJK_COMPATIBILITY_IDEOGRAPH_2FA1D 0x2fa1d #define UNICODE_LANGUAGE_TAG 0xe0001 #define UNICODE_TAG_SPACE 0xe0020 #define UNICODE_TAG_EXCLAMATION_MARK 0xe0021 #define UNICODE_TAG_QUOTATION_MARK 0xe0022 #define UNICODE_TAG_NUMBER_SIGN 0xe0023 #define UNICODE_TAG_DOLLAR_SIGN 0xe0024 #define UNICODE_TAG_PERCENT_SIGN 0xe0025 #define UNICODE_TAG_AMPERSAND 0xe0026 #define UNICODE_TAG_APOSTROPHE 0xe0027 #define UNICODE_TAG_LEFT_PARENTHESIS 0xe0028 #define UNICODE_TAG_RIGHT_PARENTHESIS 0xe0029 #define UNICODE_TAG_ASTERISK 0xe002a #define UNICODE_TAG_PLUS_SIGN 0xe002b #define UNICODE_TAG_COMMA 0xe002c #define UNICODE_TAG_HYPHEN_MINUS 0xe002d #define UNICODE_TAG_FULL_STOP 0xe002e #define UNICODE_TAG_SOLIDUS 0xe002f #define UNICODE_TAG_DIGIT_ZERO 0xe0030 #define UNICODE_TAG_DIGIT_ONE 0xe0031 #define UNICODE_TAG_DIGIT_TWO 0xe0032 #define UNICODE_TAG_DIGIT_THREE 0xe0033 #define UNICODE_TAG_DIGIT_FOUR 0xe0034 #define UNICODE_TAG_DIGIT_FIVE 0xe0035 #define UNICODE_TAG_DIGIT_SIX 0xe0036 #define UNICODE_TAG_DIGIT_SEVEN 0xe0037 #define UNICODE_TAG_DIGIT_EIGHT 0xe0038 #define UNICODE_TAG_DIGIT_NINE 0xe0039 #define UNICODE_TAG_COLON 0xe003a #define UNICODE_TAG_SEMICOLON 0xe003b #define UNICODE_TAG_LESS_THAN_SIGN 0xe003c #define UNICODE_TAG_EQUALS_SIGN 0xe003d #define UNICODE_TAG_GREATER_THAN_SIGN 0xe003e #define UNICODE_TAG_QUESTION_MARK 0xe003f #define UNICODE_TAG_COMMERCIAL_AT 0xe0040 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_A 0xe0041 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_B 0xe0042 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_C 0xe0043 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_D 0xe0044 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_E 0xe0045 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_F 0xe0046 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_G 0xe0047 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_H 0xe0048 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_I 0xe0049 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_J 0xe004a #define UNICODE_TAG_LATIN_CAPITAL_LETTER_K 0xe004b #define UNICODE_TAG_LATIN_CAPITAL_LETTER_L 0xe004c #define UNICODE_TAG_LATIN_CAPITAL_LETTER_M 0xe004d #define UNICODE_TAG_LATIN_CAPITAL_LETTER_N 0xe004e #define UNICODE_TAG_LATIN_CAPITAL_LETTER_O 0xe004f #define UNICODE_TAG_LATIN_CAPITAL_LETTER_P 0xe0050 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_Q 0xe0051 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_R 0xe0052 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_S 0xe0053 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_T 0xe0054 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_U 0xe0055 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_V 0xe0056 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_W 0xe0057 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_X 0xe0058 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_Y 0xe0059 #define UNICODE_TAG_LATIN_CAPITAL_LETTER_Z 0xe005a #define UNICODE_TAG_LEFT_SQUARE_BRACKET 0xe005b #define UNICODE_TAG_REVERSE_SOLIDUS 0xe005c #define UNICODE_TAG_RIGHT_SQUARE_BRACKET 0xe005d #define UNICODE_TAG_CIRCUMFLEX_ACCENT 0xe005e #define UNICODE_TAG_LOW_LINE 0xe005f #define UNICODE_TAG_GRAVE_ACCENT 0xe0060 #define UNICODE_TAG_LATIN_SMALL_LETTER_A 0xe0061 #define UNICODE_TAG_LATIN_SMALL_LETTER_B 0xe0062 #define UNICODE_TAG_LATIN_SMALL_LETTER_C 0xe0063 #define UNICODE_TAG_LATIN_SMALL_LETTER_D 0xe0064 #define UNICODE_TAG_LATIN_SMALL_LETTER_E 0xe0065 #define UNICODE_TAG_LATIN_SMALL_LETTER_F 0xe0066 #define UNICODE_TAG_LATIN_SMALL_LETTER_G 0xe0067 #define UNICODE_TAG_LATIN_SMALL_LETTER_H 0xe0068 #define UNICODE_TAG_LATIN_SMALL_LETTER_I 0xe0069 #define UNICODE_TAG_LATIN_SMALL_LETTER_J 0xe006a #define UNICODE_TAG_LATIN_SMALL_LETTER_K 0xe006b #define UNICODE_TAG_LATIN_SMALL_LETTER_L 0xe006c #define UNICODE_TAG_LATIN_SMALL_LETTER_M 0xe006d #define UNICODE_TAG_LATIN_SMALL_LETTER_N 0xe006e #define UNICODE_TAG_LATIN_SMALL_LETTER_O 0xe006f #define UNICODE_TAG_LATIN_SMALL_LETTER_P 0xe0070 #define UNICODE_TAG_LATIN_SMALL_LETTER_Q 0xe0071 #define UNICODE_TAG_LATIN_SMALL_LETTER_R 0xe0072 #define UNICODE_TAG_LATIN_SMALL_LETTER_S 0xe0073 #define UNICODE_TAG_LATIN_SMALL_LETTER_T 0xe0074 #define UNICODE_TAG_LATIN_SMALL_LETTER_U 0xe0075 #define UNICODE_TAG_LATIN_SMALL_LETTER_V 0xe0076 #define UNICODE_TAG_LATIN_SMALL_LETTER_W 0xe0077 #define UNICODE_TAG_LATIN_SMALL_LETTER_X 0xe0078 #define UNICODE_TAG_LATIN_SMALL_LETTER_Y 0xe0079 #define UNICODE_TAG_LATIN_SMALL_LETTER_Z 0xe007a #define UNICODE_TAG_LEFT_CURLY_BRACKET 0xe007b #define UNICODE_TAG_VERTICAL_LINE 0xe007c #define UNICODE_TAG_RIGHT_CURLY_BRACKET 0xe007d #define UNICODE_TAG_TILDE 0xe007e #define UNICODE_CANCEL_TAG 0xe007f #define UNICODE_VARIATION_SELECTOR_17 0xe0100 #define UNICODE_VARIATION_SELECTOR_18 0xe0101 #define UNICODE_VARIATION_SELECTOR_19 0xe0102 #define UNICODE_VARIATION_SELECTOR_20 0xe0103 #define UNICODE_VARIATION_SELECTOR_21 0xe0104 #define UNICODE_VARIATION_SELECTOR_22 0xe0105 #define UNICODE_VARIATION_SELECTOR_23 0xe0106 #define UNICODE_VARIATION_SELECTOR_24 0xe0107 #define UNICODE_VARIATION_SELECTOR_25 0xe0108 #define UNICODE_VARIATION_SELECTOR_26 0xe0109 #define UNICODE_VARIATION_SELECTOR_27 0xe010a #define UNICODE_VARIATION_SELECTOR_28 0xe010b #define UNICODE_VARIATION_SELECTOR_29 0xe010c #define UNICODE_VARIATION_SELECTOR_30 0xe010d #define UNICODE_VARIATION_SELECTOR_31 0xe010e #define UNICODE_VARIATION_SELECTOR_32 0xe010f #define UNICODE_VARIATION_SELECTOR_33 0xe0110 #define UNICODE_VARIATION_SELECTOR_34 0xe0111 #define UNICODE_VARIATION_SELECTOR_35 0xe0112 #define UNICODE_VARIATION_SELECTOR_36 0xe0113 #define UNICODE_VARIATION_SELECTOR_37 0xe0114 #define UNICODE_VARIATION_SELECTOR_38 0xe0115 #define UNICODE_VARIATION_SELECTOR_39 0xe0116 #define UNICODE_VARIATION_SELECTOR_40 0xe0117 #define UNICODE_VARIATION_SELECTOR_41 0xe0118 #define UNICODE_VARIATION_SELECTOR_42 0xe0119 #define UNICODE_VARIATION_SELECTOR_43 0xe011a #define UNICODE_VARIATION_SELECTOR_44 0xe011b #define UNICODE_VARIATION_SELECTOR_45 0xe011c #define UNICODE_VARIATION_SELECTOR_46 0xe011d #define UNICODE_VARIATION_SELECTOR_47 0xe011e #define UNICODE_VARIATION_SELECTOR_48 0xe011f #define UNICODE_VARIATION_SELECTOR_49 0xe0120 #define UNICODE_VARIATION_SELECTOR_50 0xe0121 #define UNICODE_VARIATION_SELECTOR_51 0xe0122 #define UNICODE_VARIATION_SELECTOR_52 0xe0123 #define UNICODE_VARIATION_SELECTOR_53 0xe0124 #define UNICODE_VARIATION_SELECTOR_54 0xe0125 #define UNICODE_VARIATION_SELECTOR_55 0xe0126 #define UNICODE_VARIATION_SELECTOR_56 0xe0127 #define UNICODE_VARIATION_SELECTOR_57 0xe0128 #define UNICODE_VARIATION_SELECTOR_58 0xe0129 #define UNICODE_VARIATION_SELECTOR_59 0xe012a #define UNICODE_VARIATION_SELECTOR_60 0xe012b #define UNICODE_VARIATION_SELECTOR_61 0xe012c #define UNICODE_VARIATION_SELECTOR_62 0xe012d #define UNICODE_VARIATION_SELECTOR_63 0xe012e #define UNICODE_VARIATION_SELECTOR_64 0xe012f #define UNICODE_VARIATION_SELECTOR_65 0xe0130 #define UNICODE_VARIATION_SELECTOR_66 0xe0131 #define UNICODE_VARIATION_SELECTOR_67 0xe0132 #define UNICODE_VARIATION_SELECTOR_68 0xe0133 #define UNICODE_VARIATION_SELECTOR_69 0xe0134 #define UNICODE_VARIATION_SELECTOR_70 0xe0135 #define UNICODE_VARIATION_SELECTOR_71 0xe0136 #define UNICODE_VARIATION_SELECTOR_72 0xe0137 #define UNICODE_VARIATION_SELECTOR_73 0xe0138 #define UNICODE_VARIATION_SELECTOR_74 0xe0139 #define UNICODE_VARIATION_SELECTOR_75 0xe013a #define UNICODE_VARIATION_SELECTOR_76 0xe013b #define UNICODE_VARIATION_SELECTOR_77 0xe013c #define UNICODE_VARIATION_SELECTOR_78 0xe013d #define UNICODE_VARIATION_SELECTOR_79 0xe013e #define UNICODE_VARIATION_SELECTOR_80 0xe013f #define UNICODE_VARIATION_SELECTOR_81 0xe0140 #define UNICODE_VARIATION_SELECTOR_82 0xe0141 #define UNICODE_VARIATION_SELECTOR_83 0xe0142 #define UNICODE_VARIATION_SELECTOR_84 0xe0143 #define UNICODE_VARIATION_SELECTOR_85 0xe0144 #define UNICODE_VARIATION_SELECTOR_86 0xe0145 #define UNICODE_VARIATION_SELECTOR_87 0xe0146 #define UNICODE_VARIATION_SELECTOR_88 0xe0147 #define UNICODE_VARIATION_SELECTOR_89 0xe0148 #define UNICODE_VARIATION_SELECTOR_90 0xe0149 #define UNICODE_VARIATION_SELECTOR_91 0xe014a #define UNICODE_VARIATION_SELECTOR_92 0xe014b #define UNICODE_VARIATION_SELECTOR_93 0xe014c #define UNICODE_VARIATION_SELECTOR_94 0xe014d #define UNICODE_VARIATION_SELECTOR_95 0xe014e #define UNICODE_VARIATION_SELECTOR_96 0xe014f #define UNICODE_VARIATION_SELECTOR_97 0xe0150 #define UNICODE_VARIATION_SELECTOR_98 0xe0151 #define UNICODE_VARIATION_SELECTOR_99 0xe0152 #define UNICODE_VARIATION_SELECTOR_100 0xe0153 #define UNICODE_VARIATION_SELECTOR_101 0xe0154 #define UNICODE_VARIATION_SELECTOR_102 0xe0155 #define UNICODE_VARIATION_SELECTOR_103 0xe0156 #define UNICODE_VARIATION_SELECTOR_104 0xe0157 #define UNICODE_VARIATION_SELECTOR_105 0xe0158 #define UNICODE_VARIATION_SELECTOR_106 0xe0159 #define UNICODE_VARIATION_SELECTOR_107 0xe015a #define UNICODE_VARIATION_SELECTOR_108 0xe015b #define UNICODE_VARIATION_SELECTOR_109 0xe015c #define UNICODE_VARIATION_SELECTOR_110 0xe015d #define UNICODE_VARIATION_SELECTOR_111 0xe015e #define UNICODE_VARIATION_SELECTOR_112 0xe015f #define UNICODE_VARIATION_SELECTOR_113 0xe0160 #define UNICODE_VARIATION_SELECTOR_114 0xe0161 #define UNICODE_VARIATION_SELECTOR_115 0xe0162 #define UNICODE_VARIATION_SELECTOR_116 0xe0163 #define UNICODE_VARIATION_SELECTOR_117 0xe0164 #define UNICODE_VARIATION_SELECTOR_118 0xe0165 #define UNICODE_VARIATION_SELECTOR_119 0xe0166 #define UNICODE_VARIATION_SELECTOR_120 0xe0167 #define UNICODE_VARIATION_SELECTOR_121 0xe0168 #define UNICODE_VARIATION_SELECTOR_122 0xe0169 #define UNICODE_VARIATION_SELECTOR_123 0xe016a #define UNICODE_VARIATION_SELECTOR_124 0xe016b #define UNICODE_VARIATION_SELECTOR_125 0xe016c #define UNICODE_VARIATION_SELECTOR_126 0xe016d #define UNICODE_VARIATION_SELECTOR_127 0xe016e #define UNICODE_VARIATION_SELECTOR_128 0xe016f #define UNICODE_VARIATION_SELECTOR_129 0xe0170 #define UNICODE_VARIATION_SELECTOR_130 0xe0171 #define UNICODE_VARIATION_SELECTOR_131 0xe0172 #define UNICODE_VARIATION_SELECTOR_132 0xe0173 #define UNICODE_VARIATION_SELECTOR_133 0xe0174 #define UNICODE_VARIATION_SELECTOR_134 0xe0175 #define UNICODE_VARIATION_SELECTOR_135 0xe0176 #define UNICODE_VARIATION_SELECTOR_136 0xe0177 #define UNICODE_VARIATION_SELECTOR_137 0xe0178 #define UNICODE_VARIATION_SELECTOR_138 0xe0179 #define UNICODE_VARIATION_SELECTOR_139 0xe017a #define UNICODE_VARIATION_SELECTOR_140 0xe017b #define UNICODE_VARIATION_SELECTOR_141 0xe017c #define UNICODE_VARIATION_SELECTOR_142 0xe017d #define UNICODE_VARIATION_SELECTOR_143 0xe017e #define UNICODE_VARIATION_SELECTOR_144 0xe017f #define UNICODE_VARIATION_SELECTOR_145 0xe0180 #define UNICODE_VARIATION_SELECTOR_146 0xe0181 #define UNICODE_VARIATION_SELECTOR_147 0xe0182 #define UNICODE_VARIATION_SELECTOR_148 0xe0183 #define UNICODE_VARIATION_SELECTOR_149 0xe0184 #define UNICODE_VARIATION_SELECTOR_150 0xe0185 #define UNICODE_VARIATION_SELECTOR_151 0xe0186 #define UNICODE_VARIATION_SELECTOR_152 0xe0187 #define UNICODE_VARIATION_SELECTOR_153 0xe0188 #define UNICODE_VARIATION_SELECTOR_154 0xe0189 #define UNICODE_VARIATION_SELECTOR_155 0xe018a #define UNICODE_VARIATION_SELECTOR_156 0xe018b #define UNICODE_VARIATION_SELECTOR_157 0xe018c #define UNICODE_VARIATION_SELECTOR_158 0xe018d #define UNICODE_VARIATION_SELECTOR_159 0xe018e #define UNICODE_VARIATION_SELECTOR_160 0xe018f #define UNICODE_VARIATION_SELECTOR_161 0xe0190 #define UNICODE_VARIATION_SELECTOR_162 0xe0191 #define UNICODE_VARIATION_SELECTOR_163 0xe0192 #define UNICODE_VARIATION_SELECTOR_164 0xe0193 #define UNICODE_VARIATION_SELECTOR_165 0xe0194 #define UNICODE_VARIATION_SELECTOR_166 0xe0195 #define UNICODE_VARIATION_SELECTOR_167 0xe0196 #define UNICODE_VARIATION_SELECTOR_168 0xe0197 #define UNICODE_VARIATION_SELECTOR_169 0xe0198 #define UNICODE_VARIATION_SELECTOR_170 0xe0199 #define UNICODE_VARIATION_SELECTOR_171 0xe019a #define UNICODE_VARIATION_SELECTOR_172 0xe019b #define UNICODE_VARIATION_SELECTOR_173 0xe019c #define UNICODE_VARIATION_SELECTOR_174 0xe019d #define UNICODE_VARIATION_SELECTOR_175 0xe019e #define UNICODE_VARIATION_SELECTOR_176 0xe019f #define UNICODE_VARIATION_SELECTOR_177 0xe01a0 #define UNICODE_VARIATION_SELECTOR_178 0xe01a1 #define UNICODE_VARIATION_SELECTOR_179 0xe01a2 #define UNICODE_VARIATION_SELECTOR_180 0xe01a3 #define UNICODE_VARIATION_SELECTOR_181 0xe01a4 #define UNICODE_VARIATION_SELECTOR_182 0xe01a5 #define UNICODE_VARIATION_SELECTOR_183 0xe01a6 #define UNICODE_VARIATION_SELECTOR_184 0xe01a7 #define UNICODE_VARIATION_SELECTOR_185 0xe01a8 #define UNICODE_VARIATION_SELECTOR_186 0xe01a9 #define UNICODE_VARIATION_SELECTOR_187 0xe01aa #define UNICODE_VARIATION_SELECTOR_188 0xe01ab #define UNICODE_VARIATION_SELECTOR_189 0xe01ac #define UNICODE_VARIATION_SELECTOR_190 0xe01ad #define UNICODE_VARIATION_SELECTOR_191 0xe01ae #define UNICODE_VARIATION_SELECTOR_192 0xe01af #define UNICODE_VARIATION_SELECTOR_193 0xe01b0 #define UNICODE_VARIATION_SELECTOR_194 0xe01b1 #define UNICODE_VARIATION_SELECTOR_195 0xe01b2 #define UNICODE_VARIATION_SELECTOR_196 0xe01b3 #define UNICODE_VARIATION_SELECTOR_197 0xe01b4 #define UNICODE_VARIATION_SELECTOR_198 0xe01b5 #define UNICODE_VARIATION_SELECTOR_199 0xe01b6 #define UNICODE_VARIATION_SELECTOR_200 0xe01b7 #define UNICODE_VARIATION_SELECTOR_201 0xe01b8 #define UNICODE_VARIATION_SELECTOR_202 0xe01b9 #define UNICODE_VARIATION_SELECTOR_203 0xe01ba #define UNICODE_VARIATION_SELECTOR_204 0xe01bb #define UNICODE_VARIATION_SELECTOR_205 0xe01bc #define UNICODE_VARIATION_SELECTOR_206 0xe01bd #define UNICODE_VARIATION_SELECTOR_207 0xe01be #define UNICODE_VARIATION_SELECTOR_208 0xe01bf #define UNICODE_VARIATION_SELECTOR_209 0xe01c0 #define UNICODE_VARIATION_SELECTOR_210 0xe01c1 #define UNICODE_VARIATION_SELECTOR_211 0xe01c2 #define UNICODE_VARIATION_SELECTOR_212 0xe01c3 #define UNICODE_VARIATION_SELECTOR_213 0xe01c4 #define UNICODE_VARIATION_SELECTOR_214 0xe01c5 #define UNICODE_VARIATION_SELECTOR_215 0xe01c6 #define UNICODE_VARIATION_SELECTOR_216 0xe01c7 #define UNICODE_VARIATION_SELECTOR_217 0xe01c8 #define UNICODE_VARIATION_SELECTOR_218 0xe01c9 #define UNICODE_VARIATION_SELECTOR_219 0xe01ca #define UNICODE_VARIATION_SELECTOR_220 0xe01cb #define UNICODE_VARIATION_SELECTOR_221 0xe01cc #define UNICODE_VARIATION_SELECTOR_222 0xe01cd #define UNICODE_VARIATION_SELECTOR_223 0xe01ce #define UNICODE_VARIATION_SELECTOR_224 0xe01cf #define UNICODE_VARIATION_SELECTOR_225 0xe01d0 #define UNICODE_VARIATION_SELECTOR_226 0xe01d1 #define UNICODE_VARIATION_SELECTOR_227 0xe01d2 #define UNICODE_VARIATION_SELECTOR_228 0xe01d3 #define UNICODE_VARIATION_SELECTOR_229 0xe01d4 #define UNICODE_VARIATION_SELECTOR_230 0xe01d5 #define UNICODE_VARIATION_SELECTOR_231 0xe01d6 #define UNICODE_VARIATION_SELECTOR_232 0xe01d7 #define UNICODE_VARIATION_SELECTOR_233 0xe01d8 #define UNICODE_VARIATION_SELECTOR_234 0xe01d9 #define UNICODE_VARIATION_SELECTOR_235 0xe01da #define UNICODE_VARIATION_SELECTOR_236 0xe01db #define UNICODE_VARIATION_SELECTOR_237 0xe01dc #define UNICODE_VARIATION_SELECTOR_238 0xe01dd #define UNICODE_VARIATION_SELECTOR_239 0xe01de #define UNICODE_VARIATION_SELECTOR_240 0xe01df #define UNICODE_VARIATION_SELECTOR_241 0xe01e0 #define UNICODE_VARIATION_SELECTOR_242 0xe01e1 #define UNICODE_VARIATION_SELECTOR_243 0xe01e2 #define UNICODE_VARIATION_SELECTOR_244 0xe01e3 #define UNICODE_VARIATION_SELECTOR_245 0xe01e4 #define UNICODE_VARIATION_SELECTOR_246 0xe01e5 #define UNICODE_VARIATION_SELECTOR_247 0xe01e6 #define UNICODE_VARIATION_SELECTOR_248 0xe01e7 #define UNICODE_VARIATION_SELECTOR_249 0xe01e8 #define UNICODE_VARIATION_SELECTOR_250 0xe01e9 #define UNICODE_VARIATION_SELECTOR_251 0xe01ea #define UNICODE_VARIATION_SELECTOR_252 0xe01eb #define UNICODE_VARIATION_SELECTOR_253 0xe01ec #define UNICODE_VARIATION_SELECTOR_254 0xe01ed #define UNICODE_VARIATION_SELECTOR_255 0xe01ee #define UNICODE_VARIATION_SELECTOR_256 0xe01ef sources_5316/kar/longchar.cpp0000644000176700017670000024161011647316236015016 0ustar paulpaul/* longchar.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/11/17 removed bug that genericized to non-Roman glyphs (thanks Mietta Lennes) * pb 2003/08/20 added five phonetic Greek characters * pb 2004/12/01 added many bitmaps * pb 2004/12/02 support for TIPA font (xwin column); unfortunately, several characters are missing (ringunder, diaeresisunder, tildeunder) * pb 2005/02/04 the IPA widths become those of the PostScript font TeX-xipa10-Praat-Regular * pb 2005/02/04 erev and kidneybean * pb 2005/03/08 ps encoding; SILIPA93 encoding for Windows and Mac * pb 2005/09/18 SILIPA93 widths for fontless EPS files, including bold * pb 2006/11/17 Unicode * pb 2006/12/05 first wchar support * pb 2006/12/15 stress marks * pb 2007/08/08 Longchar_genericizeW * pb 2008/02/27 \d- and \D- * pb 2009/03/24 removed bug that caused Longchar_getInfoFromNative to be able to work with uninitialized table * pb 2011/04/06 C++ */ #include "longchar.h" #include /* For error message. */ #include "UnicodeData.h" static struct structLongchar_Info Longchar_database [] = { /* Space. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { ' ', ' ', 0, { "/space", 250, 250, 250, 250, 278, 278, 250, 250, 250, 250 }, 32, 32, 32, 32, UNICODE_SPACE }, /* Letters. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { 'a', ' ', 0, { "/a", 444, 500, 500, 500, 556, 556, 500, 500, 444, 556 }, 97, 97, 97, 97, UNICODE_LATIN_SMALL_LETTER_A }, { 'b', ' ', 0, { "/b", 500, 556, 500, 500, 556, 611, 553, 611, 463, 537 }, 98, 98, 98, 98, UNICODE_LATIN_SMALL_LETTER_B }, { 'c', ' ', 0, { "/c", 444, 444, 444, 444, 500, 556, 444, 444, 407, 444 }, 99, 99, 99, 99, UNICODE_LATIN_SMALL_LETTER_C }, { 'd', ' ', 0, { "/d", 500, 556, 500, 500, 556, 611, 611, 611, 500, 556 }, 100, 100, 100, 100, UNICODE_LATIN_SMALL_LETTER_D }, { 'e', ' ', 0, { "/e", 444, 444, 444, 444, 556, 556, 479, 500, 389, 444 }, 101, 101, 101, 101, UNICODE_LATIN_SMALL_LETTER_E }, { 'f', ' ', 0, { "/f", 333, 333, 278, 333, 278, 333, 333, 389, 278, 333 }, 102, 102, 102, 102, UNICODE_LATIN_SMALL_LETTER_F }, { 'g', ' ', 0, { "/g", 500, 500, 500, 500, 556, 611, 556, 556, 500, 500 }, 103, 103, 103, 103, UNICODE_LATIN_SMALL_LETTER_G }, { 'h', ' ', 0, { "/h", 500, 556, 500, 556, 556, 611, 582, 611, 500, 556 }, 104, 104, 104, 104, UNICODE_LATIN_SMALL_LETTER_H }, { 'i', ' ', 0, { "/i", 278, 278, 278, 278, 222, 278, 291, 333, 278, 333 }, 105, 105, 105, 105, UNICODE_LATIN_SMALL_LETTER_I }, { 'j', ' ', 0, { "/j", 278, 333, 278, 278, 222, 278, 234, 333, 278, 333 }, 106, 106, 106, 106, UNICODE_LATIN_SMALL_LETTER_J }, { 'k', ' ', 0, { "/k", 500, 556, 444, 500, 500, 556, 556, 611, 444, 556 }, 107, 107, 107, 107, UNICODE_LATIN_SMALL_LETTER_K }, { 'l', ' ', 0, { "/l", 278, 278, 278, 278, 222, 278, 291, 333, 278, 333 }, 108, 108, 108, 108, UNICODE_LATIN_SMALL_LETTER_L }, { 'm', ' ', 0, { "/m", 778, 833, 722, 778, 833, 889, 883, 889, 778, 833 }, 109, 109, 109, 109, UNICODE_LATIN_SMALL_LETTER_M }, { 'n', ' ', 0, { "/n", 500, 556, 500, 556, 556, 611, 582, 611, 556, 556 }, 110, 110, 110, 110, UNICODE_LATIN_SMALL_LETTER_N }, { 'o', ' ', 0, { "/o", 500, 500, 500, 500, 556, 611, 546, 556, 444, 556 }, 111, 111, 111, 111, UNICODE_LATIN_SMALL_LETTER_O }, { 'p', ' ', 0, { "/p", 500, 556, 500, 500, 556, 611, 601, 611, 500, 556 }, 112, 112, 112, 112, UNICODE_LATIN_SMALL_LETTER_P }, { 'q', ' ', 0, { "/q", 500, 556, 500, 500, 556, 611, 560, 611, 463, 537 }, 113, 113, 113, 113, UNICODE_LATIN_SMALL_LETTER_Q }, { 'r', ' ', 0, { "/r", 333, 444, 389, 389, 333, 389, 395, 389, 389, 389 }, 114, 114, 114, 114, UNICODE_LATIN_SMALL_LETTER_R }, { 's', ' ', 0, { "/s", 389, 389, 389, 389, 500, 556, 424, 444, 389, 444 }, 115, 115, 115, 115, UNICODE_LATIN_SMALL_LETTER_S }, { 't', ' ', 0, { "/t", 278, 333, 278, 278, 278, 333, 326, 333, 333, 389 }, 116, 116, 116, 116, UNICODE_LATIN_SMALL_LETTER_T }, { 'u', ' ', 0, { "/u", 500, 556, 500, 556, 556, 611, 603, 611, 556, 556 }, 117, 117, 117, 117, UNICODE_LATIN_SMALL_LETTER_U }, { 'v', ' ', 0, { "/v", 500, 500, 444, 444, 500, 556, 565, 556, 500, 556 }, 118, 118, 118, 118, UNICODE_LATIN_SMALL_LETTER_V }, { 'w', ' ', 0, { "/w", 722, 722, 667, 667, 722, 778, 834, 833, 722, 833 }, 119, 119, 119, 119, UNICODE_LATIN_SMALL_LETTER_W }, { 'x', ' ', 0, { "/x", 500, 500, 444, 500, 500, 556, 516, 500, 500, 500 }, 120, 120, 120, 120, UNICODE_LATIN_SMALL_LETTER_X }, { 'y', ' ', 0, { "/y", 500, 500, 444, 444, 500, 556, 556, 556, 500, 556 }, 121, 121, 121, 121, UNICODE_LATIN_SMALL_LETTER_Y }, { 'z', ' ', 0, { "/z", 444, 444, 389, 389, 500, 500, 500, 500, 444, 500 }, 122, 122, 122, 122, UNICODE_LATIN_SMALL_LETTER_Z }, /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { 'A', ' ', 0, { "/A", 722, 722, 611, 667, 667, 722, 778, 778, 722, 722 }, 65, 65, 65, 65, UNICODE_LATIN_CAPITAL_LETTER_A }, { 'B', ' ', 0, { "/B", 667, 667, 611, 667, 667, 722, 611, 667, 611, 667 }, 66, 66, 66, 66, UNICODE_LATIN_CAPITAL_LETTER_B }, { 'C', ' ', 0, { "/C", 667, 722, 667, 667, 722, 722, 709, 722, 667, 685 }, 67, 67, 67, 67, UNICODE_LATIN_CAPITAL_LETTER_C }, { 'D', ' ', 0, { "/D", 722, 722, 722, 722, 722, 722, 774, 833, 778, 778 }, 68, 68, 68, 68, UNICODE_LATIN_CAPITAL_LETTER_D }, { 'E', ' ', 0, { "/E", 611, 667, 611, 667, 667, 667, 611, 611, 611, 611 }, 69, 69, 69, 69, UNICODE_LATIN_CAPITAL_LETTER_E }, { 'F', ' ', 0, { "/F", 556, 611, 611, 667, 611, 611, 556, 556, 556, 556 }, 70, 70, 70, 70, UNICODE_LATIN_CAPITAL_LETTER_F }, { 'G', ' ', 0, { "/G", 722, 778, 722, 722, 778, 778, 763, 833, 722, 778 }, 71, 71, 71, 71, UNICODE_LATIN_CAPITAL_LETTER_G }, { 'H', ' ', 0, { "/H", 722, 778, 722, 778, 722, 722, 832, 833, 778, 778 }, 72, 72, 72, 72, UNICODE_LATIN_CAPITAL_LETTER_H }, { 'I', ' ', 0, { "/I", 333, 389, 333, 389, 278, 278, 337, 389, 333, 389 }, 73, 73, 73, 73, UNICODE_LATIN_CAPITAL_LETTER_I }, { 'J', ' ', 0, { "/J", 389, 500, 444, 500, 500, 556, 333, 389, 333, 389 }, 74, 74, 74, 74, UNICODE_LATIN_CAPITAL_LETTER_J }, { 'K', ' ', 0, { "/K", 722, 778, 667, 667, 667, 722, 726, 778, 667, 722 }, 75, 75, 75, 75, UNICODE_LATIN_CAPITAL_LETTER_K }, { 'L', ' ', 0, { "/L", 611, 667, 556, 611, 556, 611, 611, 611, 556, 611 }, 76, 76, 76, 76, UNICODE_LATIN_CAPITAL_LETTER_L }, { 'M', ' ', 0, { "/M", 889, 944, 833, 889, 833, 833, 946,1000, 944, 944 }, 77, 77, 77, 77, UNICODE_LATIN_CAPITAL_LETTER_M }, { 'N', ' ', 0, { "/N", 722, 722, 667, 722, 722, 722, 831, 833, 778, 778 }, 78, 78, 78, 78, UNICODE_LATIN_CAPITAL_LETTER_N }, { 'O', ' ', 0, { "/O", 722, 778, 722, 722, 778, 778, 786, 833, 778, 833 }, 79, 79, 79, 79, UNICODE_LATIN_CAPITAL_LETTER_O }, { 'P', ' ', 0, { "/P", 556, 611, 611, 611, 667, 667, 604, 611, 611, 667 }, 80, 80, 80, 80, UNICODE_LATIN_CAPITAL_LETTER_P }, { 'Q', ' ', 0, { "/Q", 722, 778, 722, 722, 778, 778, 786, 833, 778, 833 }, 81, 81, 81, 81, UNICODE_LATIN_CAPITAL_LETTER_Q }, { 'R', ' ', 0, { "/R", 667, 722, 611, 667, 722, 722, 668, 722, 667, 722 }, 82, 82, 82, 82, UNICODE_LATIN_CAPITAL_LETTER_R }, { 'S', ' ', 0, { "/S", 556, 556, 500, 556, 667, 667, 525, 611, 556, 556 }, 83, 83, 83, 83, UNICODE_LATIN_CAPITAL_LETTER_S }, { 'T', ' ', 0, { "/T", 611, 667, 556, 611, 611, 611, 613, 667, 611, 611 }, 84, 84, 84, 84, UNICODE_LATIN_CAPITAL_LETTER_T }, { 'U', ' ', 0, { "/U", 722, 722, 722, 722, 722, 722, 778, 778, 778, 778 }, 85, 85, 85, 85, UNICODE_LATIN_CAPITAL_LETTER_U }, { 'V', ' ', 0, { "/V", 722, 722, 611, 667, 667, 667, 722, 778, 722, 778 }, 86, 86, 86, 86, UNICODE_LATIN_CAPITAL_LETTER_V }, { 'W', ' ', 0, { "/W", 944,1000, 833, 889, 944, 944, 1000,1000, 944,1000 }, 87, 87, 87, 87, UNICODE_LATIN_CAPITAL_LETTER_W }, { 'X', ' ', 0, { "/X", 722, 722, 611, 667, 667, 667, 667, 667, 722, 722 }, 88, 88, 88, 88, UNICODE_LATIN_CAPITAL_LETTER_X }, { 'Y', ' ', 0, { "/Y", 722, 722, 556, 611, 667, 667, 667, 667, 667, 611 }, 89, 89, 89, 89, UNICODE_LATIN_CAPITAL_LETTER_Y }, { 'Z', ' ', 0, { "/Z", 611, 667, 556, 611, 611, 611, 667, 667, 667, 667 }, 90, 90, 90, 90, UNICODE_LATIN_CAPITAL_LETTER_Z }, /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { '.', ' ', 0, { "/period", 250, 250, 250, 250, 278, 278, 250, 250, 250, 250 }, 46, 46, 46, 46, UNICODE_FULL_STOP }, { ',', ' ', 0, { "/comma", 250, 250, 250, 250, 278, 278, 250, 250, 250, 250 }, 44, 44, 44, 44, UNICODE_COMMA }, { ':', ' ', 0, { "/colon", 278, 333, 333, 333, 278, 333, 250, 250, 250, 250 }, 58, 58, 58, 58, UNICODE_COLON }, { ';', ' ', 0, { "/semicolon", 278, 333, 333, 333, 278, 333, 250, 250, 250, 250 }, 59, 59, 59, 59, UNICODE_SEMICOLON }, { '!', ' ', 0, { "/exclam", 333, 333, 333, 389, 278, 333, 278, 278, 333, 333 }, 33, 33, 33, 33, UNICODE_EXCLAMATION_MARK }, { '!', 'd', 0, { "/exclamdown", 333, 333, 389, 389, 333, 333, 278, 278, 333, 333 }, 161, 161, 193, 193, UNICODE_INVERTED_EXCLAMATION_MARK }, { '?', ' ', 0, { "/question", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, 63, 63, 63, 63, UNICODE_QUESTION_MARK }, { '?', 'd', 0, { "/questiondown", 444, 500, 500, 500, 611, 611, 444, 444, 500, 444 }, 191, 191, 192, 192, UNICODE_INVERTED_QUESTION_MARK }, /* Numbers. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { '0', ' ', 0, { "/zero", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 48, 48, 48, 48, UNICODE_DIGIT_ZERO }, { '1', ' ', 0, { "/one", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 49, 49, 49, 49, UNICODE_DIGIT_ONE }, { '2', ' ', 0, { "/two", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 50, 50, 50, 50, UNICODE_DIGIT_TWO }, { '3', ' ', 0, { "/three", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 51, 51, 51, 51, UNICODE_DIGIT_THREE }, { '4', ' ', 0, { "/four", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 52, 52, 52, 52, UNICODE_DIGIT_FOUR }, { '5', ' ', 0, { "/five", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 53, 53, 53, 53, UNICODE_DIGIT_FIVE }, { '6', ' ', 0, { "/six", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 54, 54, 54, 54, UNICODE_DIGIT_SIX }, { '7', ' ', 0, { "/seven", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 55, 55, 55, 55, UNICODE_DIGIT_SEVEN }, { '8', ' ', 0, { "/eight", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 56, 56, 56, 56, UNICODE_DIGIT_EIGHT }, { '9', ' ', 0, { "/nine", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 57, 57, 57, 57, UNICODE_DIGIT_NINE }, /* Parentheses, brackets, braces. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { '(', ' ', 0, { "/parenleft", 333, 333, 333, 333, 333, 333, 333, 333, 333, 333 }, 40, 40, 40, 40, UNICODE_LEFT_PARENTHESIS }, { ')', ' ', 0, { "/parenright", 333, 333, 333, 333, 333, 333, 333, 333, 333, 333 }, 41, 41, 41, 41, UNICODE_RIGHT_PARENTHESIS }, { '[', ' ', 0, { "/bracketleft", 333, 333, 389, 333, 278, 333, 333, 333, 333, 333 }, 91, 91, 91, 91, UNICODE_LEFT_SQUARE_BRACKET }, { ']', ' ', 0, { "/bracketright", 333, 333, 389, 333, 278, 333, 333, 333, 333, 333 }, 93, 93, 93, 93, UNICODE_RIGHT_SQUARE_BRACKET }, { '{', ' ', 0, { "/braceleft", 480, 394, 400, 348, 334, 389, 333, 310, 333, 333 }, 123, 123, 123, 123, UNICODE_LEFT_CURLY_BRACKET }, { '}', ' ', 0, { "/braceright", 480, 394, 400, 348, 334, 389, 333, 310, 333, 333 }, 125, 125, 125, 125, UNICODE_RIGHT_CURLY_BRACKET }, { '+', ' ', 0, { "/plus", 564, 570, 675, 570, 584, 584, 606, 606, 606, 606 }, 43, 43, 43, 43, UNICODE_PLUS_SIGN }, //{ '-', ' ', 0, { "/minus", 564, 570, 675, 606, 584, 584, 606, 606, 606, 606 }, 45, 45, 208, 45, UNICODE_HYPHEN_MINUS }, /* Add minus to ps */ { '-', ' ', 0, { "/hyphen", 333, 333, 333, 333, 333, 333, 333, 333, 333, 389 }, 173, 173, 45, 45, UNICODE_HYPHEN_MINUS }, /* Add minus to ps */ { '-', 'h', 0, { "/hyphen", 333, 333, 333, 333, 333, 333, 333, 333, 333, 389 }, 173, 173, 45, 45, UNICODE_SOFT_HYPHEN }, { '-', '-', 0, { "/endash", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 45, 45, 208, 208, UNICODE_EN_DASH }, { '+', '-', 0, { "/plusminus", 564, 570, 675, 570, 584, 584, 606, 606, 606, 606 }, 177, 177, 177, 177, UNICODE_PLUS_MINUS_SIGN }, { '*', ' ', 0, { "/asterisk", 500, 500, 500, 500, 389, 389, 389, 444, 389, 444 }, 42, 42, 42, 42, UNICODE_ASTERISK }, { '/', ' ', 0, { "/slash", 278, 278, 278, 278, 278, 278, 606, 296, 296, 315 }, 47, 47, 47, 47, UNICODE_SOLIDUS }, /* Comparison. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { '<', ' ', 0, { "/less", 564, 570, 675, 570, 584, 584, 606, 606, 606, 606 }, 60, 60, 60, 60, UNICODE_LESS_THAN_SIGN }, { '=', ' ', 0, { "/equal", 564, 570, 675, 570, 584, 584, 606, 606, 606, 606 }, 61, 61, 61, 61, UNICODE_EQUALS_SIGN }, { '>', ' ', 0, { "/greater", 564, 570, 675, 570, 584, 584, 606, 606, 606, 606 }, 62, 62, 62, 62, UNICODE_GREATER_THAN_SIGN }, /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { '#', ' ', 0, { "/numbersign", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 35, 35, 35, 35, UNICODE_NUMBER_SIGN }, { '$', ' ', 0, { "/dollar", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 36, 36, 36, 36, UNICODE_DOLLAR_SIGN }, { '%', ' ', 0, { "/percent", 833,1000, 833, 833, 889, 889, 840, 889, 889, 889 }, 37, 37, 37, 37, UNICODE_PERCENT_SIGN }, { '&', ' ', 0, { "/ampersand", 778, 833, 778, 778, 667, 722, 778, 833, 778, 833 }, 38, 38, 38, 38, UNICODE_AMPERSAND }, { '@', ' ', 0, { "/at", 921, 930, 920, 832, 1015, 975, 747, 747, 747, 833 }, 64, 64, 64, 64, UNICODE_COMMERCIAL_AT }, { 'b', 's', 0, { "/backslash", 278, 278, 278, 278, 278, 278, 606, 606, 606, 606 }, 92, 92, 92, 92, UNICODE_REVERSE_SOLIDUS }, { '_', ' ', 0, { "/underscore", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 95, 95, 95, 95, UNICODE_LOW_LINE }, { '^', ' ', 0, { "/asciicircum", 469, 581, 422, 570, 469, 584, 606, 606, 606, 606 }, 94, 94, 94, 94, UNICODE_CIRCUMFLEX_ACCENT }, { '|', ' ', 0, { "/bar", 200, 220, 275, 220, 260, 280, 606, 606, 606, 606 }, 124, 124, 124, 124, UNICODE_VERTICAL_LINE }, { '~', ' ', 0, { "/asciitilde", 541, 520, 541, 570, 584, 584, 606, 606, 606, 606 }, 126, 126, 126, 126, UNICODE_TILDE }, /* Quotes: conversion. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { '`', ' ', 0, { "/quotesinglleft", 333, 333, 333, 333, 222, 278, 278, 278, 278, 278 }, 96, 96, 212, 212, UNICODE_LEFT_SINGLE_QUOTATION_MARK }, {'\'', ' ', 0, { "/quotesinglright",333, 333, 333, 333, 222, 278, 278, 278, 278, 278 }, 39, 39, 213, 213, UNICODE_RIGHT_SINGLE_QUOTATION_MARK }, {'\'', 'a', 0, { "/apostrophe", 333, 333, 333, 333, 222, 278, 278, 278, 278, 278 }, 39, 39, 39, 39, UNICODE_APOSTROPHE }, {'\"', 'l', 0, { "/quotedblleft", 444, 500, 556, 500, 333, 500, 500, 500, 500, 500 }, 34, 34, 210, 210, UNICODE_LEFT_DOUBLE_QUOTATION_MARK }, {'\"', 'r', 0, { "/quotedblright", 444, 500, 556, 500, 333, 500, 500, 500, 500, 500 }, 34, 34, 211, 211, UNICODE_RIGHT_DOUBLE_QUOTATION_MARK }, {'\"', ' ', 0, { "/quotedbl", 408, 555, 420, 555, 355, 474, 371, 402, 500, 500 }, 34, 34, 34, 34, UNICODE_QUOTATION_MARK }, { '<', '<', 0, { "/guillemotleft", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 171, 171, 199, 199, UNICODE_LEFT_POINTING_DOUBLE_ANGLE_QUOTATION_MARK }, { '>', '>', 0, { "/guillemotright", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 187, 187, 200, 200, UNICODE_RIGHT_POINTING_DOUBLE_ANGLE_QUOTATION_MARK }, /* Accented letters. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { 'a', '`', 0, { "/agrave", 444, 500, 500, 500, 556, 556, 500, 500, 444, 556 }, 224, 224, 136, 136, UNICODE_LATIN_SMALL_LETTER_A_WITH_GRAVE }, { 'a','\'', 0, { "/aacute", 444, 500, 500, 500, 556, 556, 500, 500, 444, 556 }, 225, 225, 135, 135, UNICODE_LATIN_SMALL_LETTER_A_WITH_ACUTE }, { 'a', '^', 0, { "/acircumflex", 444, 500, 500, 500, 556, 556, 500, 500, 444, 556 }, 226, 226, 137, 137, UNICODE_LATIN_SMALL_LETTER_A_WITH_CIRCUMFLEX }, { 'a', '~', 0, { "/atilde", 444, 500, 500, 500, 556, 556, 500, 500, 444, 556 }, 227, 227, 139, 139, UNICODE_LATIN_SMALL_LETTER_A_WITH_TILDE }, { 'a','\"', 0, { "/adieresis", 444, 500, 500, 500, 556, 556, 500, 500, 444, 556 }, 228, 228, 138, 138, UNICODE_LATIN_SMALL_LETTER_A_WITH_DIAERESIS }, { 'a', 'o', 0, { "/aring", 444, 500, 500, 500, 556, 556, 500, 500, 444, 556 }, 229, 229, 140, 140, UNICODE_LATIN_SMALL_LETTER_A_WITH_RING_ABOVE }, { 'a', ';', 0, { "/aogonek", 444, 500, 500, 500, 556, 556, 500, 500, 444, 556 }, 0, 0, 0, 2, UNICODE_LATIN_SMALL_LETTER_A_WITH_OGONEK }, { 'c','\'', 0, { "/cacute", 444, 444, 444, 444, 500, 556, 444, 444, 407, 444 }, 0, 0, 0, 4, UNICODE_LATIN_SMALL_LETTER_C_WITH_ACUTE }, { 'c', '<', 0, { "/ccaron", 444, 444, 444, 444, 500, 556, 444, 444, 407, 444 }, 0, 0, 0, 6, UNICODE_LATIN_SMALL_LETTER_C_WITH_CARON }, { 'd', '<', 0, { "/dcaron", 500, 556, 500, 500, 556, 611, 611, 611, 500, 556 }, 0, 0, 0, 8, UNICODE_LATIN_SMALL_LETTER_D_WITH_CARON }, { 'd', '-', 0, { "/dbar", 500, 556, 500, 500, 556, 611, 611, 611, 500, 556 }, 0, 0, 0, 10, UNICODE_LATIN_SMALL_LETTER_D_WITH_STROKE }, { 'e', '`', 0, { "/egrave", 444, 444, 444, 444, 556, 556, 479, 500, 389, 444 }, 232, 232, 143, 143, UNICODE_LATIN_SMALL_LETTER_E_WITH_GRAVE }, { 'e','\'', 0, { "/eacute", 444, 444, 444, 444, 556, 556, 479, 500, 389, 444 }, 233, 233, 142, 142, UNICODE_LATIN_SMALL_LETTER_E_WITH_ACUTE }, { 'e', '^', 0, { "/ecircumflex", 444, 444, 444, 444, 556, 556, 479, 500, 389, 444 }, 234, 234, 144, 144, UNICODE_LATIN_SMALL_LETTER_E_WITH_CIRCUMFLEX }, { 'e','\"', 0, { "/edieresis", 444, 444, 444, 444, 556, 556, 479, 500, 389, 444 }, 235, 235, 145, 145, UNICODE_LATIN_SMALL_LETTER_E_WITH_DIAERESIS }, { 'e', '<', 0, { "/ecaron", 444, 444, 444, 444, 556, 556, 479, 500, 389, 444 }, 0, 0, 0, 12, UNICODE_LATIN_SMALL_LETTER_E_WITH_CARON }, { 'e', ';', 0, { "/eogonek", 444, 444, 444, 444, 556, 556, 479, 500, 389, 444 }, 0, 0, 0, 14, UNICODE_LATIN_SMALL_LETTER_E_WITH_OGONEK }, { 'g', '<', 0, { "/gcaron", 500, 500, 500, 500, 556, 611, 556, 556, 500, 500 }, 0, 0, 0, 16, UNICODE_LATIN_SMALL_LETTER_G_WITH_CARON }, { 'i', '`', 0, { "/igrave", 278, 278, 278, 278, 222, 278, 287, 333, 278, 333 }, 236, 236, 147, 147, UNICODE_LATIN_SMALL_LETTER_I_WITH_GRAVE }, { 'i','\'', 0, { "/iacute", 278, 278, 278, 278, 222, 278, 287, 333, 278, 333 }, 237, 237, 146, 146, UNICODE_LATIN_SMALL_LETTER_I_WITH_ACUTE }, { 'i', '^', 0, { "/icircumflex", 278, 278, 278, 278, 222, 278, 287, 333, 278, 333 }, 238, 238, 148, 148, UNICODE_LATIN_SMALL_LETTER_I_WITH_CIRCUMFLEX }, { 'i','\"', 0, { "/idieresis", 278, 278, 278, 278, 222, 278, 287, 333, 278, 333 }, 239, 239, 149, 149, UNICODE_LATIN_SMALL_LETTER_I_WITH_DIAERESIS }, { 'l', '/', 0, { "/lslash", 278, 278, 278, 278, 222, 278, 291, 333, 278, 333 }, 0, 0, 0, 18, UNICODE_LATIN_SMALL_LETTER_L_WITH_STROKE }, { 'n','\'', 0, { "/nacute", 500, 556, 500, 556, 556, 611, 582, 611, 556, 556 }, 0, 0, 0, 20, UNICODE_LATIN_SMALL_LETTER_N_WITH_ACUTE }, { 'n', '~', 0, { "/ntilde", 500, 556, 500, 556, 556, 611, 582, 611, 556, 556 }, 241, 241, 150, 150, UNICODE_LATIN_SMALL_LETTER_N_WITH_TILDE }, { 'n', '<', 0, { "/ncaron", 500, 556, 500, 556, 556, 611, 582, 611, 556, 556 }, 0, 0, 0, 22, UNICODE_LATIN_SMALL_LETTER_N_WITH_CARON }, { 'o', '`', 0, { "/ograve", 500, 500, 500, 500, 556, 611, 546, 556, 444, 556 }, 242, 242, 152, 152, UNICODE_LATIN_SMALL_LETTER_O_WITH_GRAVE }, { 'o','\'', 0, { "/oacute", 500, 500, 500, 500, 556, 611, 546, 556, 444, 556 }, 243, 243, 151, 151, UNICODE_LATIN_SMALL_LETTER_O_WITH_ACUTE }, { 'o', '^', 0, { "/ocircumflex", 500, 500, 500, 500, 556, 611, 546, 556, 444, 556 }, 244, 244, 153, 153, UNICODE_LATIN_SMALL_LETTER_O_WITH_CIRCUMFLEX }, { 'o', '~', 0, { "/otilde", 444, 500, 500, 500, 556, 611, 546, 556, 444, 556 }, 245, 245, 155, 155, UNICODE_LATIN_SMALL_LETTER_O_WITH_TILDE }, { 'o','\"', 0, { "/odieresis", 500, 500, 500, 500, 556, 611, 546, 556, 444, 556 }, 246, 246, 154, 154, UNICODE_LATIN_SMALL_LETTER_O_WITH_DIAERESIS }, { 'o', ':', 0, { "/ohungarumlaut", 500, 500, 500, 500, 556, 611, 546, 556, 444, 556 }, 0, 0, 0, 24, UNICODE_LATIN_SMALL_LETTER_O_WITH_DOUBLE_ACUTE }, { 'r', '<', 0, { "/rcaron", 333, 444, 389, 389, 333, 389, 395, 389, 389, 389 }, 0, 0, 0, 26, UNICODE_LATIN_SMALL_LETTER_R_WITH_CARON }, { 's','\'', 0, { "/sacute", 389, 389, 389, 389, 500, 556, 424, 444, 389, 444 }, 0, 0, 0, 28, UNICODE_LATIN_SMALL_LETTER_S_WITH_ACUTE }, { 's', '<', 0, { "/scaron", 389, 389, 389, 389, 500, 556, 424, 444, 389, 444 }, 0, 0, 0, 30, UNICODE_LATIN_SMALL_LETTER_S_WITH_CARON }, { 't', '<', 0, { "/tcaron", 278, 333, 278, 278, 278, 333, 326, 333, 333, 389 }, 0, 0, 0, 245, UNICODE_LATIN_SMALL_LETTER_T_WITH_CARON }, { 'u', '`', 0, { "/ugrave", 500, 556, 500, 556, 556, 611, 603, 611, 556, 556 }, 249, 249, 157, 157, UNICODE_LATIN_SMALL_LETTER_U_WITH_GRAVE }, { 'u','\'', 0, { "/uacute", 500, 556, 500, 556, 556, 611, 603, 611, 556, 556 }, 250, 250, 156, 156, UNICODE_LATIN_SMALL_LETTER_U_WITH_ACUTE }, { 'u', '^', 0, { "/ucircumflex", 500, 556, 500, 556, 556, 611, 603, 611, 556, 556 }, 251, 251, 158, 158, UNICODE_LATIN_SMALL_LETTER_U_WITH_CIRCUMFLEX }, { 'u','\"', 0, { "/udieresis", 500, 556, 500, 556, 556, 611, 603, 611, 556, 556 }, 252, 252, 159, 159, UNICODE_LATIN_SMALL_LETTER_U_WITH_DIAERESIS }, { 'u', ':', 0, { "/uhungarumlaut", 500, 556, 500, 556, 556, 611, 603, 611, 556, 556 }, 0, 0, 0, 247, UNICODE_LATIN_SMALL_LETTER_U_WITH_DOUBLE_ACUTE }, { 'u', 'o', 0, { "/uring", 500, 556, 500, 556, 556, 611, 603, 611, 556, 556 }, 0, 0, 0, 249, UNICODE_LATIN_SMALL_LETTER_U_WITH_RING_ABOVE }, { 'y','\'', 0, { "/yacute", 500, 500, 444, 444, 500, 556, 556, 556, 500, 556 }, 253, 253, 0, 251, UNICODE_LATIN_SMALL_LETTER_Y_WITH_ACUTE }, { 'y','\"', 0, { "/ydieresis", 500, 500, 444, 444, 500, 556, 556, 556, 500, 556 }, 255, 255, 216, 216, UNICODE_LATIN_SMALL_LETTER_Y_WITH_DIAERESIS }, { 'z','\'', 0, { "/zacute", 444, 444, 389, 389, 500, 500, 500, 500, 444, 500 }, 0, 0, 0, 253, UNICODE_LATIN_SMALL_LETTER_Z_WITH_ACUTE }, { 'z', '<', 0, { "/zcaron", 444, 444, 389, 389, 500, 500, 500, 500, 444, 500 }, 0, 0, 0, 255, UNICODE_LATIN_SMALL_LETTER_Z_WITH_CARON }, { 'z', '!', 0, { "/zdot", 444, 444, 389, 389, 500, 500, 500, 500, 444, 500 }, 0, 0, 0, 202, UNICODE_LATIN_SMALL_LETTER_Z_WITH_DOT_ABOVE }, /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { 'A', '`', 0, { "/Agrave", 722, 722, 611, 667, 667, 722, 778, 778, 722, 722 }, 192, 192, 203, 203, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_GRAVE }, { 'A','\'', 0, { "/Aacute", 722, 722, 611, 667, 667, 722, 778, 778, 722, 722 }, 193, 193, 231, 231, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_ACUTE }, { 'A', '^', 0, { "/Acircumflex", 722, 722, 611, 667, 667, 722, 778, 778, 722, 722 }, 194, 194, 229, 229, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_CIRCUMFLEX }, { 'A', '~', 0, { "/Atilde", 722, 722, 611, 667, 667, 722, 778, 778, 722, 722 }, 195, 195, 204, 204, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_TILDE }, { 'A','\"', 0, { "/Adieresis", 722, 722, 611, 667, 667, 722, 778, 778, 722, 722 }, 196, 196, 128, 128, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_DIAERESIS }, { 'A', 'o', 0, { "/Aring", 722, 722, 611, 667, 667, 722, 778, 778, 722, 722 }, 197, 197, 129, 129, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_RING_ABOVE }, { 'A', ';', 0, { "/Aogonek", 722, 722, 611, 667, 667, 722, 778, 778, 722, 722 }, 0, 0, 0, 1, UNICODE_LATIN_CAPITAL_LETTER_A_WITH_OGONEK }, { 'C','\'', 0, { "/Cacute", 667, 722, 667, 667, 722, 722, 709, 722, 667, 685 }, 0, 0, 0, 3, UNICODE_LATIN_CAPITAL_LETTER_C_WITH_ACUTE }, { 'C', '<', 0, { "/Ccaron", 667, 722, 667, 667, 722, 722, 709, 722, 667, 685 }, 0, 0, 0, 5, UNICODE_LATIN_CAPITAL_LETTER_C_WITH_CARON }, { 'D', '<', 0, { "/Dcaron", 722, 722, 722, 722, 722, 722, 774, 833, 778, 778 }, 0, 0, 0, 7, UNICODE_LATIN_CAPITAL_LETTER_D_WITH_CARON }, { 'D', '-', 0, { "/Dbar", 722, 722, 722, 722, 722, 722, 774, 833, 778, 778 }, 0, 0, 0, 9, UNICODE_LATIN_CAPITAL_LETTER_D_WITH_STROKE }, { 'E', '`', 0, { "/Egrave", 611, 667, 611, 667, 667, 667, 611, 611, 611, 611 }, 200, 200, 233, 233, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_GRAVE }, { 'E','\'', 0, { "/Eacute", 611, 667, 611, 667, 667, 667, 611, 611, 611, 611 }, 201, 201, 131, 131, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_ACUTE }, { 'E', '^', 0, { "/Ecircumflex", 611, 667, 611, 667, 667, 667, 611, 611, 611, 611 }, 202, 202, 230, 230, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CIRCUMFLEX }, { 'E','\"', 0, { "/Edieresis", 611, 667, 611, 667, 667, 667, 611, 611, 611, 611 }, 203, 203, 232, 232, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_DIAERESIS }, { 'E', '<', 0, { "/Ecaron", 611, 667, 611, 667, 667, 667, 611, 611, 611, 611 }, 0, 0, 0, 11, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_CARON }, { 'E', ';', 0, { "/Eogonek", 611, 667, 611, 667, 667, 667, 611, 611, 611, 611 }, 0, 0, 0, 13, UNICODE_LATIN_CAPITAL_LETTER_E_WITH_OGONEK }, { 'G', '<', 0, { "/Gcaron", 722, 778, 722, 722, 778, 778, 763, 833, 722, 778 }, 0, 0, 0, 15, UNICODE_LATIN_CAPITAL_LETTER_G_WITH_CARON }, { 'I', '`', 0, { "/Igrave", 333, 389, 333, 389, 278, 278, 337, 389, 333, 389 }, 204, 204, 237, 237, UNICODE_LATIN_CAPITAL_LETTER_I_WITH_GRAVE }, { 'I','\'', 0, { "/Iacute", 333, 389, 333, 389, 278, 278, 337, 389, 333, 389 }, 205, 205, 234, 234, UNICODE_LATIN_CAPITAL_LETTER_I_WITH_ACUTE }, { 'I', '^', 0, { "/Icircumflex", 333, 389, 333, 389, 278, 278, 337, 389, 333, 389 }, 206, 206, 235, 235, UNICODE_LATIN_CAPITAL_LETTER_I_WITH_CIRCUMFLEX }, { 'I','\"', 0, { "/Idieresis", 333, 389, 333, 389, 278, 278, 337, 389, 333, 389 }, 207, 207, 236, 236, UNICODE_LATIN_CAPITAL_LETTER_I_WITH_DIAERESIS }, { 'L', '/', 0, { "/Lslash", 611, 667, 556, 611, 556, 611, 611, 611, 556, 611 }, 0, 0, 0, 17, UNICODE_LATIN_CAPITAL_LETTER_L_WITH_STROKE }, { 'N','\'', 0, { "/Nacute", 722, 722, 667, 722, 722, 722, 831, 833, 778, 778 }, 0, 0, 0, 19, UNICODE_LATIN_CAPITAL_LETTER_N_WITH_ACUTE }, { 'N', '~', 0, { "/Ntilde", 722, 722, 667, 722, 722, 722, 831, 833, 778, 778 }, 209, 209, 132, 132, UNICODE_LATIN_CAPITAL_LETTER_N_WITH_TILDE }, { 'N', '<', 0, { "/Ncaron", 722, 722, 667, 722, 722, 722, 831, 833, 778, 778 }, 0, 0, 0, 21, UNICODE_LATIN_CAPITAL_LETTER_N_WITH_CARON }, { 'O', '`', 0, { "/Ograve", 722, 778, 722, 722, 778, 778, 786, 833, 778, 833 }, 210, 210, 241, 241, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_GRAVE }, { 'O','\'', 0, { "/Oacute", 722, 778, 722, 722, 778, 778, 786, 833, 778, 833 }, 211, 211, 238, 238, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_ACUTE }, { 'O', '^', 0, { "/Ocircumflex", 722, 778, 722, 722, 778, 778, 786, 833, 778, 833 }, 212, 212, 239, 239, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_CIRCUMFLEX }, { 'O', '~', 0, { "/Otilde", 722, 778, 722, 722, 778, 778, 786, 833, 778, 833 }, 213, 213, 205, 205, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_TILDE }, { 'O','\"', 0, { "/Odieresis", 722, 778, 722, 722, 778, 778, 786, 833, 778, 833 }, 214, 214, 133, 133, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DIAERESIS }, { 'O', ':', 0, { "/Ohungarumlaut", 722, 778, 722, 722, 778, 778, 786, 833, 778, 833 }, 0, 0, 0, 23, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_DOUBLE_ACUTE }, { 'R', '<', 0, { "/Rcaron", 667, 722, 611, 667, 722, 722, 668, 722, 667, 722 }, 0, 0, 0, 25, UNICODE_LATIN_CAPITAL_LETTER_R_WITH_CARON }, { 'S','\'', 0, { "/Sacute", 556, 556, 500, 556, 667, 667, 525, 611, 556, 556 }, 0, 0, 0, 27, UNICODE_LATIN_CAPITAL_LETTER_S_WITH_ACUTE }, { 'S', '<', 0, { "/Scaron", 556, 556, 500, 556, 667, 667, 525, 611, 556, 556 }, 0, 0, 0, 29, UNICODE_LATIN_CAPITAL_LETTER_S_WITH_CARON }, { 'T', '<', 0, { "/Tcaron", 611, 667, 556, 611, 611, 611, 613, 667, 611, 611 }, 0, 0, 0, 31, UNICODE_LATIN_CAPITAL_LETTER_T_WITH_CARON }, { 'U', '`', 0, { "/Ugrave", 722, 722, 722, 722, 722, 722, 778, 778, 778, 778 }, 217, 217, 244, 244, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_GRAVE }, { 'U','\'', 0, { "/Uacute", 722, 722, 722, 722, 722, 722, 778, 778, 778, 778 }, 218, 218, 242, 242, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_ACUTE }, { 'U', '^', 0, { "/Ucircumflex", 722, 722, 722, 722, 722, 722, 778, 778, 778, 778 }, 219, 219, 243, 243, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_CIRCUMFLEX }, { 'U','\"', 0, { "/Udieresis", 722, 722, 722, 722, 722, 722, 778, 778, 778, 778 }, 220, 220, 134, 134, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DIAERESIS }, { 'U', ':', 0, { "/Uhungarumlaut", 722, 722, 722, 722, 722, 722, 778, 778, 778, 778 }, 0, 0, 0, 246, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_DOUBLE_ACUTE }, { 'U', 'o', 0, { "/Uring", 722, 722, 722, 722, 722, 722, 778, 778, 778, 778 }, 0, 0, 0, 248, UNICODE_LATIN_CAPITAL_LETTER_U_WITH_RING_ABOVE }, { 'Y','\'', 0, { "/Yacute", 722, 722, 556, 611, 667, 667, 667, 667, 667, 611 }, 221, 221, 0, 250, UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_ACUTE }, { 'Y','\"', 0, { "/Ydieresis", 722, 722, 556, 611, 667, 667, 667, 667, 667, 611 }, 0, 0, 217, 217, UNICODE_LATIN_CAPITAL_LETTER_Y_WITH_DIAERESIS }, { 'Z','\'', 0, { "/Zacute", 611, 667, 556, 611, 611, 611, 667, 667, 667, 667 }, 0, 0, 0, 252, UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_ACUTE }, { 'Z', '<', 0, { "/Zcaron", 611, 667, 556, 611, 611, 611, 667, 667, 667, 667 }, 0, 0, 0, 254, UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_CARON }, { 'Z', '!', 0, { "/Zdot", 611, 667, 556, 611, 611, 611, 667, 667, 667, 667 }, 0, 0, 0, 129, UNICODE_LATIN_CAPITAL_LETTER_Z_WITH_DOT_ABOVE }, /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { 's', 's', 0, { "/germandbls", 500, 556, 500, 500, 611, 611, 556, 611, 500, 556 }, 223, 223, 167, 167, UNICODE_LATIN_SMALL_LETTER_SHARP_S }, /* Ringel-s. */ { 'a', 'e', 0, { "/ae", 667, 722, 667, 722, 889, 889, 758, 778, 638, 738 }, 230, 230, 190, 190, UNICODE_LATIN_SMALL_LETTER_AE }, /* ash */ { 'c', ',', 0, { "/ccedilla", 444, 444, 444, 444, 500, 556, 444, 444, 407, 444 }, 231, 231, 141, 141, UNICODE_LATIN_SMALL_LETTER_C_WITH_CEDILLA }, { 'o', '/', 0, { "/oslash", 500, 500, 500, 500, 611, 611, 556, 556, 444, 556 }, 248, 248, 191, 191, UNICODE_LATIN_SMALL_LETTER_O_WITH_STROKE }, { 't', 'h', 0, { "/thorn", 500, 556, 500, 500, 556, 611, 601, 611, 500, 556 }, 254, 254, 0, 0, UNICODE_LATIN_SMALL_LETTER_THORN }, { 'A', 'e', 0, { "/AE", 722,1000, 889, 944, 1000,1000, 944,1000, 941, 944 }, 198, 198, 174, 174, UNICODE_LATIN_CAPITAL_LETTER_AE }, /* Ash */ { 'C', ',', 0, { "/Ccedilla", 667, 722, 667, 667, 722, 722, 709, 722, 667, 685 }, 199, 199, 130, 130, UNICODE_LATIN_CAPITAL_LETTER_C_WITH_CEDILLA }, { 'O', '/', 0, { "/Oslash", 722, 778, 722, 722, 778, 778, 833, 833, 778, 833 }, 216, 216, 175, 175, UNICODE_LATIN_CAPITAL_LETTER_O_WITH_STROKE }, { 'T', 'h', 0, { "/Thorn", 556, 611, 611, 611, 667, 667, 604, 611, 611, 667 }, 222, 222, 0, 0, UNICODE_LATIN_CAPITAL_LETTER_THORN }, /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { '.', 'c', 0, { "/periodcentered", 250, 250, 250, 250, 278, 278, 250, 250, 250, 250 }, 183, 183, 225, 225, UNICODE_MIDDLE_DOT }, { 'd', 'g', 0, { "/degree", 400, 400, 400, 400, 400, 400, 400, 400, 400, 400 }, 176, 176, 161, 161, UNICODE_DEGREE_SIGN }, { 'c', '/', 0, { "/cent", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 162, 162, 162, 162, UNICODE_CENT_SIGN }, { 'L', 'p', 0, { "/sterling", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 163, 163, 163, 163, UNICODE_POUND_SIGN }, { 'c', 'u', 0, { "/currency", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 164, 164, 219, 219, UNICODE_CURRENCY_SIGN }, { 'e', 'u', 0, { "/euro", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 164, 164, 219, 219, UNICODE_EURO_SIGN }, // = currency? { 'Y', '=', 0, { "/yen", 500, 500, 500, 500, 556, 556, 500, 500, 500, 500 }, 165, 165, 180, 180, UNICODE_YEN_SIGN }, { 'S', 'S', 0, { "/section", 500, 500, 500, 500, 556, 556, 500, 500, 500, 556 }, 167, 167, 164, 164, UNICODE_SECTION_SIGN }, { '|', '|', 0, { "/paragraph", 453, 540, 523, 500, 537, 556, 628, 641, 500, 556 }, 182, 182, 166, 166, UNICODE_PILCROW_SIGN }, { 'c', 'o', 0, { "/copyright", 760, 747, 760, 747, 737, 737, 747, 747, 747, 747 }, 169, 169, 169, 169, UNICODE_COPYRIGHT_SIGN }, { 'r', 'e', 0, { "/registered", 760, 747, 760, 747, 737, 737, 747, 747, 747, 747 }, 174, 174, 168, 168, UNICODE_REGISTERED_SIGN }, { 'a', '_', 0, { "/ordfeminine", 276, 300, 276, 266, 370, 370, 333, 438, 333, 333 }, 170, 170, 187, 187, UNICODE_FEMININE_ORDINAL_INDICATOR }, { 'o', '_', 0, { "/ordmasculine", 310, 330, 310, 300, 365, 365, 333, 488, 333, 333 }, 186, 186, 188, 188, UNICODE_MASCULINE_ORDINAL_INDICATOR }, { 'F', 'I', 0, { "/fi", 556, 556, 500, 556, 500, 611, 605, 611, 528, 611 }, 0, 0, 222, 222, UNICODE_LATIN_SMALL_LIGATURE_FI }, { 'F', 'L', 0, { "/fl", 556, 556, 500, 556, 500, 611, 608, 611, 545, 611 }, 0, 0, 223, 223, UNICODE_LATIN_SMALL_LIGATURE_FL }, /* Greek. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { 'a', 'l', 1, { "/alpha", 631, 0, 0, 0, 631, 0, 631, 0, 0, 0 }, 97, 97, 97, 97, UNICODE_GREEK_SMALL_LETTER_ALPHA }, { 'b', 'e', 1, { "/beta", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 98, 98, 98, 98, UNICODE_GREEK_SMALL_LETTER_BETA }, { 'g', 'a', 1, { "/gamma", 411, 0, 0, 0, 411, 0, 411, 0, 0, 0 }, 103, 103, 103, 103, UNICODE_GREEK_SMALL_LETTER_GAMMA }, { 'd', 'e', 1, { "/delta", 494, 0, 0, 0, 494, 0, 494, 0, 0, 0 }, 100, 100, 100, 100, UNICODE_GREEK_SMALL_LETTER_DELTA }, { 'e', 'p', 1, { "/epsilon", 439, 0, 0, 0, 439, 0, 439, 0, 0, 0 }, 101, 101, 101, 101, UNICODE_GREEK_SMALL_LETTER_EPSILON }, { 'z', 'e', 1, { "/zeta", 494, 0, 0, 0, 494, 0, 494, 0, 0, 0 }, 122, 122, 122, 122, UNICODE_GREEK_SMALL_LETTER_ZETA }, { 'e', 't', 1, { "/eta", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 104, 104, 104, 104, UNICODE_GREEK_SMALL_LETTER_ETA }, { 't', 'e', 1, { "/theta", 521, 0, 0, 0, 521, 0, 521, 0, 0, 0 }, 113, 113, 113, 113, UNICODE_GREEK_SMALL_LETTER_THETA }, /* like obar */ { 't', '2', 1, { "/theta1", 631, 0, 0, 0, 631, 0, 631, 0, 0, 0 }, 74, 74, 74, 74, UNICODE_GREEK_THETA_SYMBOL }, // curly { 'i', 'o', 1, { "/iota", 329, 0, 0, 0, 329, 0, 329, 0, 0, 0 }, 105, 105, 105, 105, UNICODE_GREEK_SMALL_LETTER_IOTA }, { 'k', 'a', 1, { "/kappa", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 107, 107, 107, 107, UNICODE_GREEK_SMALL_LETTER_KAPPA }, { 'l', 'a', 1, { "/lambda", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 108, 108, 108, 108, UNICODE_GREEK_SMALL_LETTER_LAMDA }, { 'm', 'u', 1, { "/mu", 576, 0, 0, 0, 576, 0, 576, 0, 0, 0 }, 109, 109, 109, 109, UNICODE_GREEK_SMALL_LETTER_MU }, { 'n', 'u', 1, { "/nu", 521, 0, 0, 0, 521, 0, 521, 0, 0, 0 }, 110, 110, 110, 110, UNICODE_GREEK_SMALL_LETTER_NU }, { 'x', 'i', 1, { "/xi", 493, 0, 0, 0, 493, 0, 493, 0, 0, 0 }, 120, 120, 120, 120, UNICODE_GREEK_SMALL_LETTER_XI }, { 'o', 'n', 1, { "/omicron", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 111, 111, 111, 111, UNICODE_GREEK_SMALL_LETTER_OMICRON }, { 'p', 'i', 1, { "/pi", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 112, 112, 112, 112, UNICODE_GREEK_SMALL_LETTER_PI }, { 'r', 'o', 1, { "/rho", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 114, 114, 114, 114, UNICODE_GREEK_SMALL_LETTER_RHO }, { 's', 'i', 1, { "/sigma", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 115, 115, 115, 115, UNICODE_GREEK_SMALL_LETTER_SIGMA }, { 's', '2', 1, { "/sigma1", 439, 0, 0, 0, 439, 0, 439, 0, 0, 0 }, 86, 86, 86, 86, UNICODE_GREEK_SMALL_LETTER_FINAL_SIGMA }, { 't', 'a', 1, { "/tau", 439, 0, 0, 0, 439, 0, 439, 0, 0, 0 }, 116, 116, 116, 116, UNICODE_GREEK_SMALL_LETTER_TAU }, { 'u', 'p', 1, { "/upsilon", 576, 0, 0, 0, 576, 0, 576, 0, 0, 0 }, 117, 117, 117, 117, UNICODE_GREEK_SMALL_LETTER_UPSILON }, { 'f', 'i', 1, { "/phi", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 106, 106, 106, 106, UNICODE_GREEK_SMALL_LETTER_PHI }, // curly { 'f', '2', 1, { "/phi1", 521, 0, 0, 0, 521, 0, 521, 0, 0, 0 }, 102, 102, 102, 102, UNICODE_GREEK_PHI_SYMBOL }, /* like oslash */ { 'c', 'i', 1, { "/chi", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 99, 99, 99, 99, UNICODE_GREEK_SMALL_LETTER_CHI }, { 'p', 's', 1, { "/psi", 686, 0, 0, 0, 686, 0, 686, 0, 0, 0 }, 121, 121, 121, 121, UNICODE_GREEK_SMALL_LETTER_PSI }, { 'o', 'm', 1, { "/omega", 686, 0, 0, 0, 686, 0, 686, 0, 0, 0 }, 119, 119, 119, 119, UNICODE_GREEK_SMALL_LETTER_OMEGA }, { 'o', '2', 1, { "/omega1", 713, 0, 0, 0, 713, 0, 713, 0, 0, 0 }, 118, 118, 118, 118, UNICODE_GREEK_PI_SYMBOL }, /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { 'A', 'l', 1, { "/Alpha", 722, 0, 0, 0, 722, 0, 722, 0, 0, 0 }, 65, 65, 65, 65, UNICODE_GREEK_CAPITAL_LETTER_ALPHA }, { 'B', 'e', 1, { "/Beta", 667, 0, 0, 0, 667, 0, 667, 0, 0, 0 }, 66, 66, 66, 66, UNICODE_GREEK_CAPITAL_LETTER_BETA }, { 'G', 'a', 1, { "/Gamma", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 71, 71, 71, 71, UNICODE_GREEK_CAPITAL_LETTER_GAMMA }, { 'D', 'e', 1, { "/Delta", 612, 0, 0, 0, 612, 0, 612, 0, 0, 0 }, 68, 68, 68, 68, UNICODE_GREEK_CAPITAL_LETTER_DELTA }, { 'E', 'p', 1, { "/Epsilon", 611, 0, 0, 0, 611, 0, 611, 0, 0, 0 }, 69, 69, 69, 69, UNICODE_GREEK_CAPITAL_LETTER_EPSILON }, { 'Z', 'e', 1, { "/Zeta", 611, 0, 0, 0, 611, 0, 611, 0, 0, 0 }, 90, 90, 90, 90, UNICODE_GREEK_CAPITAL_LETTER_ZETA }, { 'E', 't', 1, { "/Eta", 722, 0, 0, 0, 722, 0, 722, 0, 0, 0 }, 72, 72, 72, 72, UNICODE_GREEK_CAPITAL_LETTER_ETA }, { 'T', 'e', 1, { "/Theta", 741, 0, 0, 0, 741, 0, 741, 0, 0, 0 }, 81, 81, 81, 81, UNICODE_GREEK_CAPITAL_LETTER_THETA }, { 'I', 'o', 1, { "/Iota", 333, 0, 0, 0, 333, 0, 333, 0, 0, 0 }, 73, 73, 73, 73, UNICODE_GREEK_CAPITAL_LETTER_IOTA }, { 'K', 'a', 1, { "/Kappa", 722, 0, 0, 0, 722, 0, 722, 0, 0, 0 }, 75, 75, 75, 75, UNICODE_GREEK_CAPITAL_LETTER_KAPPA }, { 'L', 'a', 1, { "/Lambda", 686, 0, 0, 0, 686, 0, 686, 0, 0, 0 }, 76, 76, 76, 76, UNICODE_GREEK_CAPITAL_LETTER_LAMDA }, { 'M', 'u', 1, { "/Mu", 889, 0, 0, 0, 889, 0, 889, 0, 0, 0 }, 77, 77, 77, 77, UNICODE_GREEK_CAPITAL_LETTER_MU }, { 'N', 'u', 1, { "/Nu", 722, 0, 0, 0, 722, 0, 722, 0, 0, 0 }, 78, 78, 78, 78, UNICODE_GREEK_CAPITAL_LETTER_NU }, { 'X', 'i', 1, { "/Xi", 645, 0, 0, 0, 645, 0, 645, 0, 0, 0 }, 88, 88, 88, 88, UNICODE_GREEK_CAPITAL_LETTER_XI }, { 'O', 'n', 1, { "/Omicron", 722, 0, 0, 0, 722, 0, 722, 0, 0, 0 }, 79, 79, 79, 79, UNICODE_GREEK_CAPITAL_LETTER_OMICRON }, { 'P', 'i', 1, { "/Pi", 768, 0, 0, 0, 768, 0, 768, 0, 0, 0 }, 80, 80, 80, 80, UNICODE_GREEK_CAPITAL_LETTER_PI }, { 'R', 'o', 1, { "/Rho", 556, 0, 0, 0, 556, 0, 556, 0, 0, 0 }, 82, 82, 82, 82, UNICODE_GREEK_CAPITAL_LETTER_RHO }, { 'S', 'i', 1, { "/Sigma", 592, 0, 0, 0, 592, 0, 592, 0, 0, 0 }, 83, 83, 83, 83, UNICODE_GREEK_CAPITAL_LETTER_SIGMA }, { 'T', 'a', 1, { "/Tau", 611, 0, 0, 0, 611, 0, 611, 0, 0, 0 }, 84, 84, 84, 84, UNICODE_GREEK_CAPITAL_LETTER_TAU }, { 'U', 'p', 1, { "/Upsilon", 690, 0, 0, 0, 690, 0, 690, 0, 0, 0 }, 85, 85, 85, 85, UNICODE_GREEK_CAPITAL_LETTER_UPSILON }, { 'F', 'i', 1, { "/Phi", 763, 0, 0, 0, 763, 0, 763, 0, 0, 0 }, 70, 70, 70, 70, UNICODE_GREEK_CAPITAL_LETTER_PHI }, { 'C', 'i', 1, { "/Chi", 722, 0, 0, 0, 722, 0, 722, 0, 0, 0 }, 67, 67, 67, 67, UNICODE_GREEK_CAPITAL_LETTER_CHI }, { 'P', 's', 1, { "/Psi", 795, 0, 0, 0, 795, 0, 795, 0, 0, 0 }, 89, 89, 89, 89, UNICODE_GREEK_CAPITAL_LETTER_PSI }, { 'O', 'm', 1, { "/Omega", 768, 0, 0, 0, 768, 0, 768, 0, 0, 0 }, 87, 87, 87, 87, UNICODE_GREEK_CAPITAL_LETTER_OMEGA }, /* Hebrew. */ { '?', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_ALEF }, { 'B', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_BET }, { 'G', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_GIMEL }, { 'D', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_DALET }, { 'H', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_HE }, { 'V', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_VAV }, { 'Z', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_ZAYIN }, { 'X', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_HET }, { 'Y', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_TET }, { 'J', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_YOD }, { 'K', '%', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_FINAL_KAF }, { 'K', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_KAF }, { 'L', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_LAMED }, { 'M', '%', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_FINAL_MEM }, { 'M', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_MEM }, { 'N', '%', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_FINAL_NUN }, { 'N', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_NUN }, { 'S', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_SAMEKH }, { '9', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_AYIN }, { 'P', '%', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_FINAL_PE }, { 'P', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_PE }, { 'C', '%', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_FINAL_TSADI }, { 'C', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_TSADI }, { 'Q', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_QOF }, { 'R', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_RESH }, { 'W', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_SHIN }, { 'T', '+', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_TAV }, { 'h', 'I', 4, { "", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 0, 0, 0, UNICODE_HEBREW_POINT_HIRIQ }, { 's', 'E', 4, { "", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 0, 0, 0, UNICODE_HEBREW_POINT_SEGOL }, { 'c', 'E', 4, { "", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 0, 0, 0, UNICODE_HEBREW_POINT_TSERE }, { 'q', 'A', 4, { "", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 0, 0, 0, UNICODE_HEBREW_POINT_QAMATS }, { 'p', 'A', 4, { "", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 0, 0, 0, UNICODE_HEBREW_POINT_PATAH }, { 'h', 'O', 4, { "", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 0, 0, 0, UNICODE_HEBREW_POINT_HOLAM }, { 'v', 'O', 4, { "", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_VAV_WITH_HOLAM }, { 'q', 'U', 4, { "", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 0, 0, 0, UNICODE_HEBREW_POINT_QUBUTS }, { 'd', 'q', 4, { "", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 0, 0, 0, UNICODE_HEBREW_POINT_DAGESH_OR_MAPIQ }, { 's', 'U', 4, { "/shuruq", 500, 500, 500, 500, 500, 500, 500, 500, 500, 500 }, 0, 0, 0, 0, UNICODE_HEBREW_LETTER_VAV_WITH_DAGESH }, /* Symbol. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { 't', 'm', 1, { "/trademarkserif", 890, 0, 0, 0, 890, 0, 890, 0, 0, 0 }, 212, 212, 212, 212, UNICODE_TRADE_MARK_SIGN }, { 'T', 'M', 1, { "/trademarksans", 786, 0, 0, 0, 786, 0, 786, 0, 0, 0 }, 228, 228, 228, 228, UNICODE_TRADE_MARK_SIGN }, { 'n', 'o', 1, { "/logicalnot", 713, 0, 0, 0, 713, 0, 713, 0, 0, 0 }, 216, 216, 216, 215, UNICODE_NOT_SIGN }, { 'x', 'x', 1, { "/multiply", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 180, 180, 180, 180, UNICODE_MULTIPLICATION_SIGN }, { ':', '-', 1, { "/divide", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 184, 184, 184, 184, UNICODE_DIVISION_SIGN }, { 'f', 'd', 1, { "/florin", 500, 0, 0, 0, 500, 0, 500, 0, 0, 0 }, 166, 166, 166, 166, UNICODE_LATIN_SMALL_LETTER_F_WITH_HOOK }, { 'b', 'u', 1, { "/bullet", 460, 0, 0, 0, 460, 0, 460, 0, 0, 0 }, 183, 183, 183, 183, UNICODE_BULLET }, {'\'', 'p', 1, { "/minute", 247, 0, 0, 0, 247, 0, 247, 0, 0, 0 }, 162, 162, 162, 162, UNICODE_PRIME }, {'\"', 'p', 1, { "/second", 411, 0, 0, 0, 411, 0, 411, 0, 0, 0 }, 178, 178, 178, 178, UNICODE_DOUBLE_PRIME }, { 'A', 't', 1, { "/universal", 713, 0, 0, 0, 713, 0, 713, 0, 0, 0 }, 34, 34, 34, 34, UNICODE_FOR_ALL }, { 'd', 'd', 1, { "/partialdiff", 494, 0, 0, 0, 494, 0, 494, 0, 0, 0 }, 182, 182, 182, 182, UNICODE_PARTIAL_DIFFERENTIAL }, { 'E', 'r', 1, { "/existential", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 36, 36, 36, 36, UNICODE_THERE_EXISTS }, { 'O', '|', 1, { "/emptyset", 823, 0, 0, 0, 823, 0, 823, 0, 0, 0 }, 198, 198, 198, 198, UNICODE_EMPTY_SET }, { 'e', '=', 1, { "/element", 713, 0, 0, 0, 713, 0, 713, 0, 0, 0 }, 206, 206, 206, 206, UNICODE_ELEMENT_OF }, { 's', 'u', 1, { "/summation", 713, 0, 0, 0, 713, 0, 713, 0, 0, 0 }, 229, 229, 229, 229, UNICODE_N_ARY_SUMMATION }, { '-', 'm', 1, { "/minus", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 45, 45, 45, 45, UNICODE_MINUS_SIGN }, { '/', 'd', 1, { "/fraction", 167, 0, 0, 0, 167, 0, 167, 0, 0, 0 }, 164, 164, 164, 164, UNICODE_DIVISION_SLASH }, { 'V', 'r', 1, { "/radical", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 214, 214, 214, 214, UNICODE_SQUARE_ROOT }, { 'o', 'c', 1, { "/proportional", 713, 0, 0, 0, 713, 0, 713, 0, 0, 0 }, 181, 181, 181, 181, UNICODE_PROPORTIONAL_TO }, { 'o', 'o', 1, { "/infinity", 713, 0, 0, 0, 713, 0, 713, 0, 0, 0 }, 165, 165, 165, 165, UNICODE_INFINITY }, { 'a', 'n', 1, { "/logicaland", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 217, 217, 217, 217, UNICODE_LOGICAL_AND }, { 'o', 'r', 1, { "/logicalor", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 218, 218, 218, 218, UNICODE_LOGICAL_OR }, { 'n', 'i', 1, { "/intersection", 768, 0, 0, 0, 768, 0, 768, 0, 0, 0 }, 199, 199, 199, 199, UNICODE_INTERSECTION }, { 'u', 'u', 1, { "/union", 768, 0, 0, 0, 768, 0, 768, 0, 0, 0 }, 200, 200, 200, 200, UNICODE_UNION }, { 'i', 'n', 1, { "/integral", 274, 0, 0, 0, 274, 0, 274, 0, 0, 0 }, 242, 242, 242, 242, UNICODE_INTEGRAL }, { '.', '3', 1, { "/therefore", 863, 0, 0, 0, 863, 0, 863, 0, 0, 0 }, 92, 92, 92, 92, UNICODE_THEREFORE }, { '=', '~', 1, { "/congruent", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 64, 64, 64, 64, UNICODE_APPROXIMATELY_EQUAL_TO }, { '~', '~', 1, { "/approxequal", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 187, 187, 187, 187, UNICODE_ALMOST_EQUAL_TO }, { 'u', 'n', 1, { "/underscore", 500, 0, 0, 0, 500, 0, 500, 0, 0, 0 }, 95, 95, 95, 95 }, { 'o', 'v', 1, { "/radicalex", 500, 0, 0, 0, 500, 0, 500, 0, 0, 0 }, 96, 96, 96, 96 }, { '=', '/', 1, { "/notequal", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 185, 185, 185, 185, UNICODE_NOT_EQUAL_TO }, { '=', '3', 1, { "/equivalence", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 186, 186, 186, 186, UNICODE_IDENTICAL_TO }, /* defined as */ { '<', '_', 1, { "/lessequal", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 163, 163, 163, 163, UNICODE_LESS_THAN_OR_EQUAL_TO }, { '>', '_', 1, { "/greaterequal", 549, 0, 0, 0, 549, 0, 549, 0, 0, 0 }, 179, 179, 179, 179, UNICODE_GREATER_THAN_OR_EQUAL_TO }, { 'c', '=', 1, { "/propersubset", 713, 0, 0, 0, 713, 0, 713, 0, 0, 0 }, 204, 204, 204, 204, UNICODE_SUBSET_OF }, { 'o', '+', 1, { "/circleplus", 768, 0, 0, 0, 768, 0, 768, 0, 0, 0 }, 197, 197, 197, 197, UNICODE_CIRCLED_PLUS }, { 'o', 'x', 1, { "/circlemultiply", 768, 0, 0, 0, 768, 0, 768, 0, 0, 0 }, 196, 196, 196, 196, UNICODE_CIRCLED_TIMES }, { 'T', 't', 1, { "/perpendicular", 658, 0, 0, 0, 658, 0, 658, 0, 0, 0 }, 94, 94, 94, 94, UNICODE_UP_TACK }, { '.', '.', 1, { "/ellipsis", 1000, 0, 0, 0, 1000, 0, 1000, 0, 0, 0 }, 188, 188, 188, 188, UNICODE_MIDLINE_HORIZONTAL_ELLIPSIS }, { 'c', 'l', 1, { "/club", 753, 0, 0, 0, 753, 0, 753, 0, 0, 0 }, 167, 167, 167, 167, UNICODE_BLACK_CLUB_SUIT }, { 'd', 'i', 1, { "/diamond", 753, 0, 0, 0, 753, 0, 753, 0, 0, 0 }, 168, 168, 168, 168, UNICODE_BLACK_DIAMOND_SUIT }, { 'h', 'e', 1, { "/heart", 753, 0, 0, 0, 753, 0, 753, 0, 0, 0 }, 169, 169, 169, 169, UNICODE_BLACK_HEART_SUIT }, { 's', 'p', 1, { "/spade", 753, 0, 0, 0, 753, 0, 753, 0, 0, 0 }, 170, 170, 170, 170, UNICODE_BLACK_SPADE_SUIT }, { '<', '-', 1, { "/arrowleft", 987, 0, 0, 0, 987, 0, 987, 0, 0, 0 }, 172, 172, 172, 172, UNICODE_LEFTWARDS_ARROW }, { '^', '|', 1, { "/arrowup", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 173, 173, 173, 173, UNICODE_UPWARDS_ARROW }, { '-', '>', 1, { "/arrowright", 987, 0, 0, 0, 987, 0, 987, 0, 0, 0 }, 174, 174, 174, 174, UNICODE_RIGHTWARDS_ARROW }, { '_', '|', 1, { "/arrowdown", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 175, 175, 175, 175, UNICODE_DOWNWARDS_ARROW }, { '<', '>', 1, { "/arrowboth", 1042, 0, 0, 0, 1042, 0, 1042, 0, 0, 0 }, 171, 171, 171, 171, UNICODE_LEFT_RIGHT_ARROW }, { '<', '=', 1, { "/arrowdblleft", 987, 0, 0, 0, 987, 0, 987, 0, 0, 0 }, 220, 220, 220, 220, UNICODE_LEFTWARDS_DOUBLE_ARROW }, /* follows from */ { '^', '#', 1, { "/arrowdblup", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 221, 221, 221, 221, UNICODE_UPWARDS_DOUBLE_ARROW }, { '=', '>', 1, { "/arrowdblright", 987, 0, 0, 0, 987, 0, 987, 0, 0, 0 }, 222, 222, 222, 222, UNICODE_RIGHTWARDS_DOUBLE_ARROW }, /* implies */ { '_', '#', 1, { "/arrowdbldown", 603, 0, 0, 0, 603, 0, 603, 0, 0, 0 }, 223, 223, 223, 223, UNICODE_DOWNWARDS_DOUBLE_ARROW }, { 'e', 'q', 1, { "/arrowdblboth", 1042, 0, 0, 0, 1042, 0, 1042, 0, 0, 0 }, 219, 219, 219, 219, UNICODE_LEFT_RIGHT_DOUBLE_ARROW }, /* equivalence */ /* Phonetic. i89+ i93 i93 i89+ */ /*fir sec al ps xipa b ipa93 b xipa b xipa b i bi xwin win mac ps unicode decomp */ { 'd', 'h', 2, { "/eth", 500, 0, 510, 532, 500, 0, 500, 0, 0, 0 }, 68, 68, 68, 68, UNICODE_LATIN_SMALL_LETTER_ETH }, { 'h', '-', 2, { "/hbar", 525, 0, 520, 578, 525, 0, 525, 0, 0, 0 }, 240, 240, 240, 240, UNICODE_LATIN_SMALL_LETTER_H_WITH_STROKE }, { 'o', 'e', 2, { "/oe", 700, 0, 751, 769, 700, 0, 700, 0, 0, 0 }, 191, 191, 191, 191, UNICODE_LATIN_SMALL_LIGATURE_OE }, { 'a', 't', 2, { "/aturn", 444, 0, 462, 520, 444, 0, 444, 0, 0, 0 }, 140, 140, 140, 140, UNICODE_LATIN_SMALL_LETTER_TURNED_A }, { 'a', 's', 2, { "/ascript", 500, 0, 520, 578, 500, 0, 500, 0, 0, 0 }, 65, 65, 65, 65, UNICODE_LATIN_SMALL_LETTER_ALPHA }, { 'a', 'b', 2, { "/ascriptturn", 500, 0, 520, 578, 500, 0, 500, 0, 0, 0 }, 129, 129, 129, 129, UNICODE_LATIN_SMALL_LETTER_TURNED_ALPHA }, // Am. pot { 'a', 'y', 2, { "/ascriptturn", 500, 0, 520, 578, 500, 0, 500, 0, 0, 0 }, 129, 129, 129, 129, UNICODE_LATIN_SMALL_LETTER_TURNED_ALPHA }, // Am. pot { 'b', '^', 2, { "/bhooktop", 475, 0, 510, 580, 475, 0, 475, 0, 0, 0 }, 186, 186, 186, 186, UNICODE_LATIN_SMALL_LETTER_B_WITH_HOOK }, { '[', 'f', 2, { "/bracketleft", 333, 0, 346, 356, 333, 0, 333, 0, 0, 0 }, 91, 91, 91, 91, UNICODE_LEFT_SQUARE_BRACKET }, // second version { ']', 'f', 2, { "/bracketright", 333, 0, 346, 356, 333, 0, 333, 0, 0, 0 }, 93, 93, 93, 93, UNICODE_RIGHT_SQUARE_BRACKET }, // second version { 'b', 'c', 2, { "/bcap", 513, 0, 539, 572, 513, 0, 513, 0, 0, 0 }, 245, 245, 245, 245, UNICODE_LATIN_LETTER_SMALL_CAPITAL_B }, // bilabial trill { 'c', 't', 2, { "/cturn", 444, 0, 452, 462, 444, 0, 444, 0, 0, 0 }, 141, 141, 141, 141, UNICODE_LATIN_SMALL_LETTER_OPEN_O }, { 'c', 'c', 2, { "/ccurl", 444, 0, 462, 462, 444, 0, 444, 0, 0, 0 }, 254, 254, 254, 254, UNICODE_LATIN_SMALL_LETTER_C_WITH_CURL }, { 'd', '.', 2, { "/drighttail", 500, 0, 520, 578, 500, 0, 500, 0, 0, 0 }, 234, 234, 234, 234, UNICODE_LATIN_SMALL_LETTER_D_WITH_TAIL }, { 'd', '^', 2, { "/dhooktop", 500, 0, 523, 578, 500, 0, 500, 0, 0, 0 }, 235, 235, 235, 235, UNICODE_LATIN_SMALL_LETTER_D_WITH_HOOK }, { 'e', '-', 2, { "/erev", 444, 0, 462, 462, 444, 0, 444, 0, 0, 0 }, 251, 130, 130, 251, UNICODE_LATIN_SMALL_LETTER_REVERSED_E }, // 1993 addition { 's', 'w', 2, { "/schwa", 444, 0, 462, 462, 444, 0, 444, 0, 0, 0 }, 171, 171, 171, 171, UNICODE_LATIN_SMALL_LETTER_SCHWA }, { 's', 'r', 2, { "/schwarighthook", 600, 0, 600.0,600.0, 600, 0, 600, 0, 0, 0 }, 212, 0, 0, 212, UNICODE_LATIN_SMALL_LETTER_SCHWA_WITH_HOOK }, // Am. bird { 'e', 'f', 2, { "/epsilonphonetic",444, 0, 441, 471, 444, 0, 444, 0, 0, 0 }, 69, 69, 69, 69, UNICODE_LATIN_SMALL_LETTER_OPEN_E }, { 'e', 'r', 2, { "/epsilonrev", 444, 0, 441, 471, 444, 0, 444, 0, 0, 0 }, 206, 206, 206, 206, UNICODE_LATIN_SMALL_LETTER_REVERSED_OPEN_E }, { 'k', 'b', 2, { "/kidneybean", 500, 0, 471, 514, 500, 0, 500, 0, 0, 0 }, 185, 207, 207, 185, UNICODE_LATIN_SMALL_LETTER_CLOSED_REVERSED_OPEN_E }, // 1993 addition, 1996 correction { 'j', '-', 2, { "/jdotlessbar", 333, 0, 289, 340, 333, 0, 333, 0, 0, 0 }, 239, 239, 239, 239, UNICODE_LATIN_SMALL_LETTER_DOTLESS_J_WITH_STROKE }, { 'g', '^', 2, { "/ghooktop", 500, 0, 520, 572, 500, 0, 500, 0, 0, 0 }, 169, 169, 169, 169, UNICODE_LATIN_SMALL_LETTER_G_WITH_HOOK }, { 'g', 's', 2, { "/gscript", 475, 0, 500, 555, 475, 0, 475, 0, 0, 0 }, 103, 103, 103, 103, UNICODE_LATIN_SMALL_LETTER_SCRIPT_G }, { 'g', 'c', 2, { "/gcap", 565, 0, 605, 659, 565, 0, 565, 0, 0, 0 }, 71, 71, 71, 71, UNICODE_LATIN_LETTER_SMALL_CAPITAL_G }, { 'g', 'f', 2, { "/gammaphonetic", 500, 0, 520, 578, 500, 0, 500, 0, 0, 0 }, 196, 196, 196, 196, UNICODE_LATIN_SMALL_LETTER_GAMMA }, { 'r', 'h', 2, { "/ramshorn", 500, 0, 573, 603, 500, 0, 500, 0, 0, 0 }, 70, 70, 70, 70, UNICODE_LATIN_SMALL_LETTER_RAMS_HORN }, // formerly a baby gamma { 'G', '^', 2, { "/gcaphooktop", 584, 0, 638, 662, 584, 0, 584, 0, 0, 0 }, 253, 253, 253, 253, UNICODE_LATIN_LETTER_SMALL_CAPITAL_G_WITH_HOOK }, { 'h', 't', 2, { "/hturn", 500, 0, 520, 578, 500, 0, 500, 0, 0, 0 }, 231, 231, 231, 231, UNICODE_LATIN_SMALL_LETTER_TURNED_H }, { 'h', '^', 2, { "/hhooktop", 500, 0, 520, 578, 500, 0, 500, 0, 0, 0 }, 250, 250, 250, 250, UNICODE_LATIN_SMALL_LETTER_H_WITH_HOOK }, { 'h', 'j', 2, { "/henghooktop", 475, 0, 520, 578, 475, 0, 475, 0, 0, 0 }, 238, 238, 238, 238, UNICODE_LATIN_SMALL_LETTER_HENG_WITH_HOOK }, // Swedish fricative sj { 'h', 'c', 2, { "/hcap", 547, 0, 605, 659, 547, 0, 547, 0, 0, 0 }, 75, 75, 75, 75, UNICODE_LATIN_LETTER_SMALL_CAPITAL_H }, { 'i', '-', 2, { "/ibar", 308, 0, 289, 289, 308, 0, 308, 0, 0, 0 }, 246, 246, 246, 246, UNICODE_LATIN_SMALL_LETTER_I_WITH_STROKE }, { 'i', 'c', 2, { "/icap", 280, 0, 289, 300, 280, 0, 280, 0, 0, 0 }, 73, 73, 73, 73, UNICODE_LATIN_LETTER_SMALL_CAPITAL_I }, { 'j', 'c', 2, { "/jcurl", 318, 0, 289, 371, 318, 0, 318, 0, 0, 0 }, 198, 198, 198, 198, UNICODE_LATIN_SMALL_LETTER_J_WITH_CROSSED_TAIL }, { 'l', '~', 2, { "/ltilde", 380, 0, 0, 0, 380, 0, 380, 0, 0, 0 }, 201, 0, 0, 201, UNICODE_LATIN_SMALL_LETTER_L_WITH_MIDDLE_TILDE }, { 'l', '-', 2, { "/lbelt", 350, 0, 337, 371, 350, 0, 350, 0, 0, 0 }, 194, 194, 194, 194, UNICODE_LATIN_SMALL_LETTER_L_WITH_BELT }, // Welsh ll { 'l', '.', 2, { "/lrighttail", 278, 0, 289, 298, 278, 0, 278, 0, 0, 0 }, 241, 241, 241, 241, UNICODE_LATIN_SMALL_LETTER_L_WITH_RETROFLEX_HOOK }, { 'l', 'z', 2, { "/lyogh", 506, 0, 604, 641, 506, 0, 506, 0, 0, 0 }, 76, 76, 76, 76, UNICODE_LATIN_SMALL_LETTER_LEZH }, { 'l', 'c', 2, { "/lcap", 455, 0, 502, 559, 455, 0, 455, 0, 0, 0 }, 59, 59, 59, 59, UNICODE_LATIN_LETTER_SMALL_CAPITAL_L }, { 'm', 't', 2, { "/mturn", 778, 0, 809, 866, 778, 0, 778, 0, 0, 0 }, 181, 181, 181, 181, UNICODE_LATIN_SMALL_LETTER_TURNED_M }, { 'm', 'l', 2, { "/mturnleg", 778, 0, 809, 866, 778, 0, 778, 0, 0, 0 }, 229, 229, 229, 229, UNICODE_LATIN_SMALL_LETTER_TURNED_M_WITH_LONG_LEG }, { 'm', 'j', 2, { "/mlefttail", 753, 0, 795, 866, 753, 0, 753, 0, 0, 0 }, 77, 77, 77, 77, UNICODE_LATIN_SMALL_LETTER_M_WITH_HOOK }, // labiodental nasal { 'n', 'g', 2, { "/eng", 475, 0, 506, 578, 475, 0, 475, 0, 0, 0 }, 78, 78, 78, 78, UNICODE_LATIN_SMALL_LETTER_ENG }, /* velar nasal */ { 'n', 'j', 2, { "/nlefttail", 500, 0, 520, 578, 500, 0, 500, 0, 0, 0 }, 248, 248, 248, 248, UNICODE_LATIN_SMALL_LETTER_N_WITH_LEFT_HOOK }, // palatal nasal { 'n', '.', 2, { "/nrighttail", 500, 0, 506, 578, 500, 0, 500, 0, 0, 0 }, 247, 247, 247, 247, UNICODE_LATIN_SMALL_LETTER_N_WITH_RETROFLEX_HOOK }, { 'n', 'c', 2, { "/ncap", 547, 0, 595, 614, 547, 0, 547, 0, 0, 0 }, 178, 178, 178, 178, UNICODE_LATIN_LETTER_SMALL_CAPITAL_N }, // uvular nasal { 'o', '-', 2, { "/obar", 500, 0, 520, 520, 500, 0, 500, 0, 0, 0 }, 80, 80, 80, 80, UNICODE_LATIN_SMALL_LETTER_BARRED_O }, // Swedish short u { 'O', 'e', 2, { "/oecap", 727, 0, 745, 845, 727, 0, 727, 0, 0, 0 }, 175, 175, 175, 175, UNICODE_LATIN_LETTER_SMALL_CAPITAL_OE }, { '|', '1', 2, { "/pipe", 278, 0, 221, 221, 278, 0, 278, 0, 0, 0 }, 142, 142, 142, 142, UNICODE_LATIN_LETTER_DENTAL_CLICK }, { '|', '2', 2, { "/pipedouble", 444, 0, 221, 221, 444, 0, 444, 0, 0, 0 }, 146, 146, 146, 146, UNICODE_LATIN_LETTER_LATERAL_CLICK }, { '|', '-', 2, { "/pipedoublebar", 500, 0, 435, 435, 500, 0, 500, 0, 0, 0 }, 156, 156, 156, 156, UNICODE_LATIN_LETTER_ALVEOLAR_CLICK }, { '|', 'f', 2, { "/stroke", 278, 0, 208, 229, 278, 0, 278, 0, 0, 0 }, 150, 150, 150, 150, UNICODE_VERTICAL_LINE }, // second version { 'f', 'f', 2, { "/phiphonetic", 550, 0, 549, 616, 550, 0, 550, 0, 0, 0 }, 184, 184, 184, 184, UNICODE_LATIN_SMALL_LETTER_PHI }, { 'r', 't', 2, { "/rturn", 333, 0, 356, 462, 333, 0, 333, 0, 0, 0 }, 168, 168, 168, 168, UNICODE_LATIN_SMALL_LETTER_TURNED_R }, { 'r', 'l', 2, { "/rturnleg", 333, 0, 356, 462, 333, 0, 333, 0, 0, 0 }, 228, 228, 228, 228, UNICODE_LATIN_SMALL_LETTER_TURNED_R_WITH_LONG_LEG }, { 'r', '.', 2, { "/rturnrighttail", 333, 0, 362, 457, 333, 0, 333, 0, 0, 0 }, 211, 211, 211, 211, UNICODE_LATIN_SMALL_LETTER_TURNED_R_WITH_HOOK }, { 'f', '.', 2, { "/rrighttail", 333, 0, 356, 462, 333, 0, 333, 0, 0, 0 }, 125, 125, 125, 125, UNICODE_LATIN_SMALL_LETTER_R_WITH_TAIL }, { 'f', 'h', 2, { "/fishhook", 333, 0, 380, 433, 333, 0, 333, 0, 0, 0 }, 82, 82, 82, 82, UNICODE_LATIN_SMALL_LETTER_R_WITH_FISHHOOK }, // tap { 'r', 'c', 2, { "/rcap", 541, 0, 559, 614, 541, 0, 541, 0, 0, 0 }, 123, 123, 123, 123, UNICODE_LATIN_LETTER_SMALL_CAPITAL_R }, { 'r', 'i', 2, { "/rcapinv", 541, 0, 559, 613, 541, 0, 541, 0, 0, 0 }, 210, 210, 210, 210, UNICODE_LATIN_LETTER_SMALL_CAPITAL_INVERTED_R }, { 's', '.', 2, { "/srighttail", 389, 0, 405, 405, 389, 0, 389, 0, 0, 0 }, 167, 167, 167, 167, UNICODE_LATIN_SMALL_LETTER_S_WITH_HOOK }, { 's', 'h', 2, { "/esh", 328, 0, 351, 361, 328, 0, 328, 0, 0, 0 }, 83, 83, 83, 83, UNICODE_LATIN_SMALL_LETTER_ESH }, { 'j', '^', 2, { "/jbarhooktop", 300, 0, 289, 360, 300, 0, 300, 0, 0, 0 }, 215, 215, 215, 215, UNICODE_LATIN_SMALL_LETTER_DOTLESS_J_WITH_STROKE_AND_HOOK }, { 't', '.', 2, { "/trighttail", 325, 0, 289, 345, 325, 0, 325, 0, 0, 0 }, 255, 255, 255, 255, UNICODE_LATIN_SMALL_LETTER_T_WITH_RETROFLEX_HOOK }, { 'u', '-', 2, { "/ubar", 500, 0, 520, 578, 500, 0, 500, 0, 0, 0 }, 172, 172, 172, 172, UNICODE_LATIN_SMALL_LETTER_U_BAR }, // Swedish long u { 'h', 's', 2, { "/horseshoe", 550, 0, 520, 549, 550, 0, 550, 0, 0, 0 }, 85, 85, 85, 85, UNICODE_LATIN_SMALL_LETTER_UPSILON }, // omegaturn, "upsilon" { 'v', 's', 2, { "/vscript", 461, 0, 488, 533, 461, 0, 461, 0, 0, 0 }, 86, 86, 86, 86, UNICODE_LATIN_SMALL_LETTER_V_WITH_HOOK }, // Dutch w { 'v', 't', 2, { "/vturn", 500, 0, 520, 520, 500, 0, 500, 0, 0, 0 }, 195, 195, 195, 195, UNICODE_LATIN_SMALL_LETTER_TURNED_V }, // wedge { 'w', 't', 2, { "/wturn", 722, 0, 751, 751, 722, 0, 722, 0, 0, 0 }, 227, 227, 227, 227, UNICODE_LATIN_SMALL_LETTER_TURNED_W }, { 'y', 't', 2, { "/yturn", 500, 0, 520, 520, 500, 0, 500, 0, 0, 0 }, 180, 180, 180, 180, UNICODE_LATIN_SMALL_LETTER_TURNED_Y }, { 'y', 'c', 2, { "/ycap", 547, 0, 605, 612, 547, 0, 547, 0, 0, 0 }, 89, 89, 89, 89, UNICODE_LATIN_LETTER_SMALL_CAPITAL_Y }, { 'z', '.', 2, { "/zrighttail", 444, 0, 462, 462, 444, 0, 444, 0, 0, 0 }, 189, 189, 189, 189, UNICODE_LATIN_SMALL_LETTER_Z_WITH_RETROFLEX_HOOK }, { 'z', 'c', 2, { "/zcurl", 494, 0, 482, 521, 494, 0, 494, 0, 0, 0 }, 252, 252, 252, 252, UNICODE_LATIN_SMALL_LETTER_Z_WITH_CURL }, { 'z', 'h', 2, { "/yogh", 444, 0, 459, 521, 444, 0, 444, 0, 0, 0 }, 90, 90, 90, 90, UNICODE_LATIN_SMALL_LETTER_EZH }, { '?', 'g', 2, { "/glottalstop", 500, 0, 440, 477, 500, 0, 500, 0, 0, 0 }, 47, 63, 63, 47, UNICODE_LATIN_LETTER_GLOTTAL_STOP }, { '9', 'e', 2, { "/glotrev", 500, 0, 440, 477, 500, 0, 500, 0, 0, 0 }, 214, 192, 192, 214, UNICODE_LATIN_LETTER_PHARYNGEAL_VOICED_FRICATIVE }, { 'O', '.', 2, { "/bullseye", 722, 0, 799, 818, 722, 0, 722, 0, 0, 0 }, 135, 135, 135, 135, UNICODE_LATIN_LETTER_BILABIAL_CLICK }, { '?', '-', 2, { "/glotbar", 500, 0, 440, 477, 500, 0, 500, 0, 0, 0 }, 63, 251, 251, 63, UNICODE_LATIN_LETTER_GLOTTAL_STOP_WITH_STROKE }, // epiglottal plosive { '9', '-', 2, { "/glotrevbar", 500, 0, 440, 477, 500, 0, 500, 0, 0, 0 }, 192, 185, 185, 192, UNICODE_LATIN_LETTER_REVERSED_GLOTTAL_STOP_WITH_STROKE }, // epiglottal fricative { ':', 'f', 2, { "/lengthsign", 250, 0, 217, 235, 250, 0, 250, 0, 0, 0 }, 249, 249, 249, 249, UNICODE_MODIFIER_LETTER_TRIANGULAR_COLON }, { '.', 'f', 2, { "/halflength", 250, 0, 217, 235, 250, 0, 250, 0, 0, 0 }, 62, 62, 62, 62, UNICODE_MODIFIER_LETTER_HALF_TRIANGULAR_COLON }, { 'h', 'r', 2, { "/righthook", 300, 0, 250, 265, 300, 0, 300, 0, 0, 0 }, 213, 213, 213, 213, UNICODE_MODIFIER_LETTER_RHOTIC_HOOK }, // or rturnsuper { '`', '^', 2, { "/graveover", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 36, 36, 36, 36, UNICODE_COMBINING_GRAVE_ACCENT }, { '\'','^', 2, { "/acuteover", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 64, 64, 64, 64, UNICODE_COMBINING_ACUTE_ACCENT }, { '^', '^', 2, { "/circumover", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 94, 94, 94, 94, UNICODE_COMBINING_CIRCUMFLEX_ACCENT }, { '~', '^', 2, { "/tildeover", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 41, 41, 41, 41, UNICODE_COMBINING_TILDE }, // nasalized { '-', '^', 2, { "/minusover", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 35, 35, 35, 35, UNICODE_COMBINING_MACRON }, // mid tone or so { ':', '^', 2, { "/diaeresisover", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 95, 95, 95, 95, UNICODE_COMBINING_DIAERESIS }, // centralized { '0', '^', 2, { "/ringover", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 42, 42, 42, 42, UNICODE_COMBINING_RING_ABOVE }, // voiceless { 'v', '^', 2, { "/caronover", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 38, 38, 38, 38, UNICODE_COMBINING_CARON }, // hacek { 'N', '^', 2, { "/breveover", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 40, 40, 40, 40, UNICODE_COMBINING_BREVE }, // nonsyllabic { 'c', 'n', 2, { "/corner", 260, 0, 299, 299, 260, 0, 260, 0, 0, 0 }, 124, 124, 124, 124, UNICODE_COMBINING_LEFT_ANGLE_ABOVE }, // ? unreleased { 'c', 'v', 2, { "/halfringleft", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 55, 55, 55, 55, UNICODE_COMBINING_LEFT_HALF_RING_BELOW }, // unrounded { 'T', '^', 2, { "/raising", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 51, 51, 51, 51, UNICODE_COMBINING_UP_TACK_BELOW }, { 'T', 'v', 2, { "/lowering", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 52, 52, 52, 52, UNICODE_COMBINING_DOWN_TACK_BELOW }, { 'T', '(', 2, { "/atr", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 49, 49, 49, 49, UNICODE_COMBINING_LEFT_TACK_BELOW }, { 'T', ')', 2, { "/rtr", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 50, 50, 50, 50, UNICODE_COMBINING_RIGHT_TACK_BELOW }, { '+', 'v', 2, { "/plusunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 43, 43, 43, 43, UNICODE_COMBINING_PLUS_SIGN_BELOW }, // fronted { ':', 'v', 2, { "/diaeresisunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 45, 45, 45, 45, UNICODE_COMBINING_DIAERESIS_BELOW }, // breathy voiced { '0', 'v', 2, { "/ringunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 56, 56, 56, 56, UNICODE_COMBINING_RING_BELOW }, // voiceless { '|', 'v', 2, { "/strokeunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 96, 96, 96, 96, UNICODE_COMBINING_VERTICAL_LINE_BELOW }, // syllabicity mark { 'N', 'v', 2, { "/bridgeunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 53, 53, 53, 53, UNICODE_COMBINING_BRIDGE_BELOW }, // dental { 'U', 'v', 2, { "/shelfunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 176, 176, 176, 176, UNICODE_COMBINING_INVERTED_BRIDGE_BELOW }, // apical { 'D', 'v', 2, { "/squareunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 54, 54, 54, 54, UNICODE_COMBINING_SQUARE_BELOW }, // laminal { 'n', 'v', 2, { "/archunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 57, 57, 57, 57, UNICODE_COMBINING_INVERTED_BREVE_BELOW }, // nonsyllabic { '~', 'v', 2, { "/tildeunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 48, 48, 48, 48, UNICODE_COMBINING_TILDE_BELOW }, // creaky voiced { '-', 'v', 2, { "/minusunder", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 61, 61, 61, 61, UNICODE_COMBINING_MINUS_SIGN_BELOW }, // backed { '~', '<', 2, { "/tildethrough", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 242, 242, 0, UNICODE_COMBINING_TILDE_OVERLAY }, // velarized l { '3', 'v', 2, { "/halfringright", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 166, 166, 166, 166, UNICODE_COMBINING_RIGHT_HALF_RING_BELOW }, // rounded { 'l', 'i', 2, { "/ligature", 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 131, 131, 131, 131, UNICODE_COMBINING_DOUBLE_INVERTED_BREVE }, { 'b', 'f', 2, { "/betaphonetic", 500, 0, 520, 597, 500, 0, 500, 0, 0, 0 }, 66, 66, 66, 66, UNICODE_GREEK_SMALL_LETTER_BETA }, // second version { 't', 'f', 2, { "/thetaphonetic", 444, 0, 520, 585, 444, 0, 444, 0, 0, 0 }, 84, 84, 84, 84, UNICODE_GREEK_SMALL_LETTER_THETA }, // second version { 'c', 'f', 2, { "/chiphonetic", 500, 0, 572, 610, 500, 0, 500, 0, 0, 0 }, 88, 88, 88, 88, UNICODE_GREEK_SMALL_LETTER_CHI }, // second version { '\'','1', 2, { "/stress1", 200, 0, 222, 222, 200, 0, 200, 0, 0, 0 }, 200, 200, 200, 200, UNICODE_MODIFIER_LETTER_VERTICAL_LINE }, { '\'','2', 2, { "/stress2", 200, 0, 222, 222, 200, 0, 200, 0, 0, 0 }, 199, 199, 199, 199, UNICODE_MODIFIER_LETTER_LOW_VERTICAL_LINE }, { '^', 'h', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_H }, { '^', 'H', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_H_WITH_HOOK }, { '^', 'j', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_J }, { '^', 'w', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_W }, { '^', 'Y', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_TURNED_H }, { '^', 'y', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_Y }, { '^', '?', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_GLOTTAL_STOP }, { '^', '9', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_REVERSED_GLOTTAL_STOP }, { '^', 'l', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_L }, { '^', 's', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_S }, { '^', 'g', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_GAMMA }, { '^', 'M', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_TURNED_M }, { '^', 'G', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_TURNED_M_WITH_LONG_LEG }, { '^', 'x', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_X }, { '^', 'f', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_F }, { '^', 'n', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_SUPERSCRIPT_LATIN_SMALL_LETTER_N }, { '^', 'm', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_M }, { '^', 'N', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_MODIFIER_LETTER_SMALL_ENG }, { 'i', 'd', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_LATIN_SMALL_LETTER_REVERSED_R_WITH_FISHHOOK }, { 'i', 'r', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_LATIN_SMALL_LETTER_SQUAT_REVERSED_ESH }, { '_', 'u', 2, { "", 444, 500, 500, 500, 556, 611, 444, 444, 500, 444 }, '?', '?', '?', '?', UNICODE_UNDERTIE }, /* Dingbats. */ /*fir sec al ps tim b i bi hel b pal b i bi xwin win mac ps unicode decomp */ { 'p', 'f', 3, { "/fingerright", 1000, 0, 0, 0, 1000, 0, 1000, 0, 0, 0 }, 43, 70, 43, 43, UNICODE_WHITE_RIGHT_POINTING_INDEX }, /* pointing finger */ /* Not yet bitmapped or measured. */ { 'f', '5', 3, { "/flower5", 800, 0, 0, 0, 800, 0, 800, 0, 0, 0 }, 96, 96, 96, 96, UNICODE_WHITE_FLORETTE }, /* sympathy flower */ {'\0','\0', 0, { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, 0, 0, 0, 0 } /* Closing. */ }; static short where [95] [95]; static short inited = 0; #define UNICODE_TOP_GENERICIZABLE 65000 static struct { char first, second; } genericDigraph [1+UNICODE_TOP_GENERICIZABLE]; static void init (void) { Longchar_Info data; int i; for (i = 0, data = & Longchar_database [0]; data -> first != '\0'; i ++, data ++) { short *location = & where [data -> first - 32] [data -> second - 32]; if (*location) { /* Doubly defined symbol; an error! */ /* We may not be able to use Melder_error yet, so just write a warning to stderr. */ fprintf (stderr, "Longchar init: symbol \"%c%c\" doubly defined.\n", data -> first, data -> second); } *location = i; if (data -> unicode <= UNICODE_TOP_GENERICIZABLE) { genericDigraph [data -> unicode]. first = data -> first; genericDigraph [data -> unicode]. second = data -> second; } } inited = 1; } wchar_t * Longchar_nativizeW (const wchar_t *generic, wchar_t *native, int educateQuotes) { long nquote = 0; wchar_t kar, kar1, kar2; if (! inited) init (); while ((kar = *generic++) != L'\0') { if (educateQuotes) { if (kar == L'\"') { *native++ = ++nquote & 1 ? UNICODE_LEFT_DOUBLE_QUOTATION_MARK : UNICODE_RIGHT_DOUBLE_QUOTATION_MARK; continue; } else if (kar == L'`') { /* Grave. */ *native++ = UNICODE_LEFT_SINGLE_QUOTATION_MARK; continue; } else if (kar == L'\'') { /* Straight apostrophe. */ *native++ = UNICODE_RIGHT_SINGLE_QUOTATION_MARK; /* Right single quote. */ continue; } } if (kar == '\\' && (kar1 = generic [0]) >= 32 && kar1 <= 126 && (kar2 = generic [1]) >= 32 && kar2 <= 126) { long location = where [kar1 - 32] [kar2 - 32]; if (location == 0) { *native++ = kar; *native++ = kar1; /* Even if this is a backslash itself... */ *native++ = kar2; /* Even if this is a backslash itself... */ /* These "evens" are here to ensure that Longchar_nativize does nothing on an already nativized string. */ } else { *native++ = Longchar_database [location]. unicode ? Longchar_database [location]. unicode : UNICODE_INVERTED_QUESTION_MARK; } generic += 2; } else { *native++ = kar; } } *native++ = '\0'; return native; } char *Longchar_genericize (const char *native, char *g) { unsigned char kar; if (! inited) init (); while ((kar = *native++) != '\0') { if (kar >= 32 && kar <= 126) { *g++ = kar; } else { *g++ = '\\'; *g++ = genericDigraph [kar]. first; *g++ = genericDigraph [kar]. second; } } *g++ = '\0'; return g; } wchar_t *Longchar_genericizeW (const wchar_t *native, wchar_t *g) { wchar_t kar; if (! inited) init (); while ((kar = *native++) != '\0') { if (kar > 128 && kar <= UNICODE_TOP_GENERICIZABLE && genericDigraph [kar]. first != '\0') { *g++ = '\\'; *g++ = genericDigraph [kar]. first; *g++ = genericDigraph [kar]. second; } else { *g++ = kar; } } *g++ = '\0'; return g; } Longchar_Info Longchar_getInfo (char kar1, char kar2) { if (! inited) init (); short position = kar1 < 32 || kar1 > 126 || kar2 < 32 || kar2 > 126 ? 0 : /* Return the 'space' character. */ where [kar1 - 32] [kar2 - 32]; return & Longchar_database [position]; } Longchar_Info Longchar_getInfoFromNative (wchar_t kar) { if (! inited) init (); return kar > UNICODE_TOP_GENERICIZABLE ? Longchar_getInfo (' ', ' ') : Longchar_getInfo (genericDigraph [kar]. first, genericDigraph [kar]. second); } /* End of file longchar.cpp */ sources_5316/kar/ipaSerifRegular24.cpp0000644000176700017670000024612111547114174016451 0ustar paulpaul/* ipaSerifRegular24.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2006/12/15 * pb 2011/04/06 C++ */ const char *ipaSerifRegular24 [1 + 255-33+1 + 1] [24 + 1] = { { 0 }, /* 33 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 34 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 35 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 36 graveover 8 24 over*/ { "oooooooo", "##oooooo", "o##ooooo", "oo##oooo", "ooo##ooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", 0 }, /* 37 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 38 caronover 10 24 over*/ { "oooooooo", "##oooo##", "o##oo##o", "oo####oo", "ooo##ooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", 0 }, /* 39 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 40 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 41 tildeover 12 24 over*/ { "oooooooooo", "oooooooooo", "oo##oooo##", "o##o##o##o", "##oooo##oo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 42 ringover 6 24 over*/ { "oooooo", "oo##oo", "o#oo#o", "o#oo#o", "oo##oo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", 0 }, /* 43 plusunder 6 24 over*/ { "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oo##oo", "oo##oo", "######", "######", "oo##oo", "oo##oo", 0 }, /* 44 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 45 diaresisunder 6 24 over*/ { "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "##oo##", "##oo##", "oooooo", "oooooo", 0 }, /* 46 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 47 glot 11 24 */ { "...........", "..#####....", ".###...##..", ".##.....#..", "........##.", "........##.", "........##.", ".......###.", "....#####..", "....####...", "....##.....", "....##.....", "....##.....", "....##.....", "....##.....", "....##.....", "....##.....", "...####....", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 48 tildeunder 12 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oo##oooo##", "o##o##o##o", "##oooo##oo", "oooooooooo", "oooooooooo", 0 }, /* 49 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 50 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 51 raising 6 24 over*/ { "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oo##oo", "oo##oo", "oo##oo", "######", "######", 0 }, /* 52 lowering 6 24 over*/ { "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "######", "######", "oo##oo", "oo##oo", "oo##oo", 0 }, /* 53 bridgeunder 6 24 over*/ { "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "######", "#oooo#", "#oooo#", "#oooo#", 0 }, /* 54 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 55 halfringleft 6 24 over*/ { "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oo##oo", "o#oooo", "o#oooo", "oo##oo", "oooooo", 0 }, /* 56 ringunder 6 24 over*/ { "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oo##oo", "o#oo#o", "o#oo#o", "oo##oo", "oooooo", 0 }, /* 57 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 58 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 59 lcap 12 24 */ { "............", "............", "............", "............", "............", "............", ".###........", "..##........", "..##........", "..##........", "..##........", "..##........", "..##........", "..##........", "..##........", "..##......#.", "..##.....##.", ".##########.", "............", "............", "............", "............", "............", "............", 0 }, /* 60 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 61 minusunder 6 24 over*/ { "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "######", "oooooo", "oooooo", "oooooo", 0 }, /* 62 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 63 glotbar 11 24 */ { "...........", "..#####....", ".###...##..", ".##.....#..", "........##.", "........##.", "........##.", ".......###.", "....#####..", "....####...", "....##.....", ".########..", ".########..", "....##.....", "....##.....", "....##.....", "....##.....", "...####....", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 64 acuteover 8 24 */ { "oooooooo", "oooooo##", "ooooo##o", "oooo##oo", "ooo##ooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", 0 }, /* 65 ascript 12 24 */ { "............", "............", "............", "............", "............", "............", "....###.##..", "..###.####..", "..##...###..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", "..##...###..", "..###.#####.", "....###..##.", "............", "............", "............", "............", "............", "............", 0 }, /* 66 betaphonetic 12 24 */ { "............", ".....###....", "...###.##...", "...##...##..", "..##....##..", "..##....##..", "..##....##..", "..##...##...", "..##.###....", "..##...###..", "..##....##..", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..####..##..", "..##.#####..", ".####.##....", "............", "............", "............", "............", "............", "............", 0 }, /* 67 ccedilla 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "....#####..", "..##...###.", "..#.....##.", ".##........", ".##........", ".##........", ".##........", ".##........", ".###.......", "..###....#.", "..#######..", "....####...", ".....#.....", "....##.....", "....####...", "......##...", "..##..##...", "...####....", 0 }, /* 68 eth 12 24 */ { "##..#.......", ".####.......", "..##........", ".####.......", ".#..##......", ".....##.....", "....####....", "..###..###..", "..##....##..", ".##......##.", ".##......##.", ".##......##.", ".##......##.", ".##......##.", ".##......##.", "..##....##..", "..###..###..", "....####....", "............", "............", "............", "............", "............", "............", 0 }, /* 69 epsilon 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", "...#####..", "..##...##.", ".##.....#.", ".##.......", ".###......", "..#####...", "..##......", ".##.......", ".##.......", ".###....#.", "..#######.", "...#####..", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 70 ramshorn 12 24 */ { "............", "............", "............", "............", "............", "............", "..##....##..", ".####..####.", ".#.##..##.#.", "....#..#....", "....####....", ".....##.....", "....####....", "...######...", "..##.....#..", "..##....##..", "..########..", "....####....", "............", "............", "............", "............", "............", "............", 0 }, /* 71 gcap 12 24 */ { "............", "............", "............", "............", "............", "............", "....####....", "..###..###..", "..##....##..", ".##......#..", ".##.........", ".##.........", ".##..######.", ".##......##.", ".##......##.", "..##....##..", "..###..###..", "....####....", "............", "............", "............", "............", "............", "............", 0 }, /* 72 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 73 icap 8 24 */ { "........", "........", "........", "........", "........", "........", ".######.", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", ".######.", "........", "........", "........", "........", "........", "........", 0 }, /* 74 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 75 hcap 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".###.....###.", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..#########..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", ".###.....###.", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 76 lyogh 12 24 */ { "............", ".###........", "..##........", "..##........", "..##........", "..##........", "..#########.", "..##.....##.", "..##....##..", "..##...###..", "..##..###...", "..##..##....", "..##.###....", "..##.####...", "..##...###..", "..##....###.", "..##.....##.", ".####....##.", ".........##.", "....##..##..", ".....####...", "............", "............", "............", 0 }, /* 77 mrighttail 20 24 */ { "....................", "....................", "....................", "....................", "....................", "....................", ".###..###....###....", "..##.#####..#####...", "..###...####...###..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", ".####...####....##..", "................##..", "................##..", "................##..", "...............###..", "............#####...", "............####....", 0 }, /* 78 eng 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".###..###....", "..##.#####...", "..###...###..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", ".####....##..", ".........##..", ".........##..", ".........##..", "........###..", ".....#####...", ".....####....", 0 }, /* 79 oslash 12 24 */ { "............", "............", "............", "............", "...........#", "..........#.", "....####.#..", "..###..###..", "..##....##..", ".##....####.", ".##....#.##.", ".##...#..##.", ".##..#...##.", ".##.#....##.", ".##.#....##.", "..##....##..", "..###..###..", ".#..####....", "#...........", "............", "............", "............", "............", "............", 0 }, /* 80 obar 12 24 */ { "............", "............", "............", "............", "............", "............", "....####....", "..###..###..", "..##....##..", ".##......##.", ".##......##.", ".##########.", ".##########.", ".##......##.", ".##......##.", "..##....##..", "..###..###..", "....####....", "............", "............", "............", "............", "............", "............", 0 }, /* 81 ash 17 24 */ { ".................", ".................", ".................", ".................", ".................", ".................", "....####...###...", "...##..####..##..", "...##...##....##.", "........##....##.", "......##########.", "....###.##.......", "...##...##.......", "..##....##.......", "..##....##.......", "..##...####....#.", "..#####..######..", "...###.....###...", ".................", ".................", ".................", ".................", ".................", ".................", 0 }, /* 82 fishhook 8 24 */ { "........", "........", "........", "........", "........", "........", ".....###", "...#####", "...##.##", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", ".####...", "........", "........", "........", "........", "........", "........", 0 }, /* 83 esh 8 24 */ { "........", ".....###", "....#.##", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "##.#....", "###.....", "........", 0 }, /* 84 thetaphonetic 12 24 */ { "............", "............", "....####....", "..###..###..", "..##....##..", ".##......##.", ".##......##.", ".##......##.", ".##......##.", ".##########.", ".##########.", ".##......##.", ".##......##.", ".##......##.", ".##......##.", "..##....##..", "..###..###..", "....####....", "............", "............", "............", "............", "............", "............", 0 }, /* 85 horseshoe 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".####...####.", "...##...##...", "...##...##...", "...##...##...", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..###...###..", "...#######...", "....#####....", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 86 vscript 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "###....##..", ".##....##..", ".##....##..", ".##.....##.", ".##......#.", ".##......#.", ".##......#.", ".##......#.", ".##.....#..", "..##...##..", "..######...", "....##.....", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 87 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 88 chi 12 24 */ { "............", "............", "............", "............", "............", "............", ".###......#.", "##.##....##.", "...##....#..", "...##...#...", "....##..#...", "....##.#....", "....##.#....", ".....##.....", ".....##.....", "....###.....", "....#.##....", "...#..##....", "...#..##....", "..#....##...", ".##....##.##", ".#......###.", "............", "............", 0 }, /* 89 ycap 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "####..####.", ".##....##..", ".##....##..", "..##..##...", "..##..##...", "...####....", "....##.....", "....##.....", "....##.....", "....##.....", "....##.....", "...####....", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 90 yogh 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...####...", ".....###..", "......###.", ".......##.", ".#.....##.", ".##....##.", "..##..##..", "...####...", "..........", "..........", "..........", 0 }, /* 91 bracketleft 10 24 */ { "..........", ".#########", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".##.......", ".#########", "..........", 0 }, /* 92 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 93 bracketright 10 24 */ { "..........", "#########.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", ".......##.", "#########.", "..........", 0 }, /* 94 circumover 8 24 over*/ { "oooooooo", "ooo##ooo", "oo####oo", "o##oo##o", "##oooo##", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", "oooooooo", 0 }, /* 95 diaresisover 6 24 over*/ { "oooooo", "oooooo", "##oo##", "##oo##", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", 0 }, /* 96 strokeunder 12 24 over*/ { "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "oooooooooooo", "ooooo##ooooo", "ooooo##ooooo", "ooooo##ooooo", "ooooo##ooooo", 0 }, /* 97 a 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "...#####...", "..##..###..", "..##...##..", ".......##..", ".....####..", "...###.##..", "..##...##..", ".##....##..", ".##....##..", ".##...###..", ".#####.##..", "..###...##.", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 98 b 12 24 */ { "............", ".###........", "..##........", "..##........", "..##........", "..##........", "..##.###....", "..###..###..", "..##....##..", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##....##..", "..###..###..", "..#.####....", "............", "............", "............", "............", "............", "............", 0 }, /* 99 c 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "....#####..", "..##...###.", "..#.....##.", ".##........", ".##........", ".##........", ".##........", ".##........", ".###.......", "..###....#.", "..#######..", "....####...", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 100 d 12 24 */ { "............", ".......###..", "........##..", "........##..", "........##..", "........##..", "....###.##..", "..###..###..", "..##....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", "..##....##..", "..###..###..", "....####.##.", "............", "............", "............", "............", "............", "............", 0 }, /* 101 e 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "....####...", "..##...##..", "..#.....##.", ".##.....##.", ".#########.", ".##........", ".##........", ".##........", ".###.......", "..###....#.", "..#######..", "....####...", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 102 f 7 24 */ { ".......", "....###", "...#.##", "..##...", "..##...", "..##...", "#######", "..##...", "..##...", "..##...", "..##...", "..##...", "..##...", "..##...", "..##...", "..##...", "..##...", ".####..", ".......", ".......", ".......", ".......", ".......", ".......", 0 }, /* 103 gscript 12 24 */ { "............", "............", "............", "............", "............", "............", "....###.###.", "..###..###..", "..##....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", "..##....##..", "..###..###..", "....######..", "........##..", "........##..", ".##.....##..", ".###...##...", "..#######...", "....###.....", 0 }, /* 104 h 13 24 */ { ".............", ".###.........", "..##.........", "..##.........", "..##.........", "..##.........", "..##..###....", "..##.#####...", "..###...###..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", ".####...####.", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 105 i 6 24 */ { "......", "..##..", "..##..", "......", "......", "......", ".###..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", ".####.", "......", "......", "......", "......", "......", "......", 0 }, /* 106 j 6 24 */ { "......", "..##..", "..##..", "......", "......", "......", ".###..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "###...", "##....", "......", 0 }, /* 107 k 12 24 */ { "............", ".###........", "..##........", "..##........", "..##........", "..##........", "..##..#####.", "..##...##...", "..##..##....", "..##..#.....", "..##.#......", "..####......", "..##.##.....", "..##.###....", "..##..###...", "..##...###..", "..##....###.", ".####..#####", "............", "............", "............", "............", "............", "............", 0 }, /* 108 l 6 24 */ { "......", ".###..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", ".####.", "......", "......", "......", "......", "......", "......", 0 }, /* 109 m 20 24 */ { "....................", "....................", "....................", "....................", "....................", "....................", ".###..###....###....", "..##.#####..#####...", "..###...####...###..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", ".####...####...####.", "....................", "....................", "....................", "....................", "....................", "....................", 0 }, /* 110 n 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".###..###....", "..##.#####...", "..###...###..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", ".####...####.", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 111 o 12 24 */ { "............", "............", "............", "............", "............", "............", "....####....", "..###..###..", "..##....##..", ".##......##.", ".##......##.", ".##......##.", ".##......##.", ".##......##.", ".##......##.", "..##....##..", "..###..###..", "....####....", "............", "............", "............", "............", "............", "............", 0 }, /* 112 p 12 24 */ { "............", "............", "............", "............", "............", "............", ".###.###....", "..###..###..", "..##....##..", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##....##..", "..###..###..", "..##.###....", "..##........", "..##........", "..##........", "..##........", ".####.......", "............", 0 }, /* 113 q 12 24 */ { "............", "............", "............", "............", "............", "............", "....###.##..", "..###..###..", "..##....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", ".##.....##..", "..##....##..", "..###..###..", "....###.##..", "........##..", "........##..", "........##..", "........##..", ".......####.", "............", 0 }, /* 114 r 9 24 */ { ".........", ".........", ".........", ".........", ".........", ".........", ".###..##.", "..##.###.", "..###.##.", "..##.....", "..##.....", "..##.....", "..##.....", "..##.....", "..##.....", "..##.....", "..##.....", ".####....", ".........", ".........", ".........", ".........", ".........", ".........", 0 }, /* 115 s 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", "...#####..", "..##..##..", ".##....#..", ".###......", "..###.....", "..#####...", "....####..", "......###.", ".......##.", ".#.....##.", ".##...##..", ".#####....", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 116 t 7 24 */ { ".......", ".......", ".......", "...#...", "..##...", ".###...", "#######", "..##...", "..##...", "..##...", "..##...", "..##...", "..##...", "..##...", "..##...", "..##...", "..##..#", "...###.", ".......", ".......", ".......", ".......", ".......", ".......", 0 }, /* 117 u 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".###....###..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..###...###..", "...#####.##..", "....###..###.", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 118 v 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "####...####", ".##.....##.", ".##.....#..", "..##....#..", "..##....#..", "..##...#...", "...##..#...", "...##..#...", "...##.#....", "....###....", "....###....", ".....#.....", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 119 w 17 24 */ { ".................", ".................", ".................", ".................", ".................", ".................", "####...####..####", ".##.....##....##.", ".##.....##....#..", "..##....##....#..", "..##....##....#..", "..##...#.##..#...", "...##..#.##..#...", "...##.#..##..#...", "...##.#...#.#....", "....###...###....", "....###...###....", ".....#.....#.....", ".................", ".................", ".................", ".................", ".................", ".................", 0 }, /* 120 x 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".####...####.", "..##.....##..", "...##...##...", "...###..#....", "....##.#.....", ".....##......", ".....###.....", "....##.##....", "...##..###...", "...#....##...", "..##.....##..", ".####...####.", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 121 y 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "####...####", ".##.....##.", ".##.....#..", "..##....#..", "..##....#..", "..##...#...", "...##..#...", "...##..#...", "...##.#....", "....###....", "....###....", ".....#.....", "....##.....", "....#......", "...##......", "####.......", "###........", "...........", 0 }, /* 122 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 123 rcap 12 24 */ { "............", "............", "............", "............", "............", "............", ".###.###....", "..###..###..", "..##....##..", "..##....##..", "..##...###..", "..######....", "..####......", "..##.##.....", "..##..##....", "..##...##...", "..##....##..", ".####..####.", "............", "............", "............", "............", "............", "............", 0 }, /* 124 corner 12 24 */ { "#######.....", "#######.....", ".....##.....", ".....##.....", ".....##.....", ".....##.....", ".....##.....", ".....##.....", "............", "............", "............", "............", "............", "............", "............", "............", "............", "............", "............", "............", "............", "............", "............", "............", 0 }, /* 125 rrighttail 8 24 */ { "........", "........", "........", "........", "........", "........", ".###..##", "..##.###", "..###.##", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "...##..#", "...#####", ".....##.", "........", 0 }, /* 126 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 127 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 128 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 129 ascriptturn 12 24 */ { "............", "............", "............", "............", "............", "............", ".##..###....", ".#####.###..", "..###...##..", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..###...##..", "..####.###..", "..##.###....", "............", "............", "............", "............", "............", "............", 0 }, /* 130 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 131 ligature 20 24 over*/ { "ooooooo#####oooooooo", "oooo###########ooooo", "o#####ooooooo#####oo", "##ooooooooooooooo##o", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", "oooooooooooooooooooo", 0 }, /* 132 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 133 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 134 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 135 bullseye 14 24 */ { "..............", "..............", "..............", "..............", "..............", ".....####.....", "...########...", "..###....###..", "..##......##..", ".##........##.", ".##...##...##.", ".##...##...##.", ".##...##...##.", ".##........##.", "..##......##..", "..###....###..", "...########...", ".....####.....", "..............", "..............", "..............", "..............", "..............", "..............", 0 }, /* 136 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 137 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 138 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 139 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 140 aturn 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", ".##...###..", "..##.#####.", "..###...##.", "..##....##.", "..##....##.", "..##...##..", "..##.###...", "..####.....", "..##.......", "..##...##..", "..###..##..", "...#####...", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 141 cturn 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "...####....", "..#######..", ".#....###..", ".......###.", "........##.", "........##.", "........##.", "........##.", "........##.", ".##.....#..", ".###...##..", "..#####....", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 142 pipe 6 24 */ { "......", "......", "......", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "......", "......", "......", "......", "......", 0 }, /* 143 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 144 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 145 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 146 pipedouble 10 24 */ { "..........", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..##..##..", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 147 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 148 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 149 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 150 stroke 6 24 */ { "......", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "..##..", "......", 0 }, /* 151 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 152 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 153 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 154 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 155 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 156 pipedoublebar 10 24 */ { "..........", "....##....", "....##....", "....##....", "....##....", "....##....", ".########.", ".########.", "....##....", "....##....", "....##....", ".########.", ".########.", "....##....", "....##....", "....##....", "....##....", "....##....", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 157 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 158 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 159 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 160 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 161 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 162 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 163 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 164 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 165 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 166 halfringright 6 24 over*/ { "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oooooo", "oo##oo", "oooo#o", "oooo#o", "oo##oo", "oooooo", 0 }, /* 167 srighttail 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", "...#####..", "..##..##..", ".##....#..", ".###......", "..###.....", "..#####...", "....####..", "......###.", ".......##.", ".#.....##.", ".##...##..", ".#####....", ".#........", ".#...#....", ".#####....", "..###.....", "..........", "..........", 0 }, /* 168 rturn 8 24 */ { "........", "........", "........", "........", "........", "........", "....####", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".##.###.", ".###.##.", ".##..###", "........", "........", "........", "........", "........", "........", 0 }, /* 169 ghooktop 14 24 */ { "..............", "..............", ".........###..", "........##.##.", "........##..#.", "........##....", "....###.##....", "..###..###....", "..##....##....", ".##.....##....", ".##.....##....", ".##.....##....", ".##.....##....", ".##.....##....", ".##.....##....", "..##....##....", "..###..###....", "....###.##....", "........##....", ".#......##....", ".##.....##....", "..#######.....", "...#####......", "..............", 0 }, /* 170 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 171 schwa 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "...####....", "..#######..", ".#....###..", ".......###.", "........##.", "........##.", "........##.", ".#########.", ".##.....##.", ".##.....#..", "..##...##..", "...####....", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 172 ubar 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".###....###..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "#############", "#############", "..##.....##..", "..##.....##..", "..###...###..", "...#####.##..", "....###..###.", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 173 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 174 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 175 oecap 17 24 */ { ".................", ".................", ".................", ".................", ".................", ".................", "....###.########.", "..###.####....##.", "..##...###.....#.", ".##.....##.......", ".##.....##.......", ".##.....######...", ".##.....##.......", ".##.....##.......", ".##.....##.......", "..##...###.....#.", "..###.####....##.", "....###.########.", ".................", ".................", ".................", ".................", ".................", ".................", 0 }, /* 176 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 177 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 178 ncap 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".###.....###.", "..##.....##..", "..###....##..", "..####...##..", "..##.#...##..", "..##.##..##..", "..##..##.##..", "..##...#.##..", "..##...####..", "..##....###..", "..##.....##..", ".####....###.", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 179 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 180 yturn 11 24 */ { "...........", "........###", ".......####", "......##...", "......#....", ".....##....", ".....#.....", "....###....", "....###....", "....#.##...", "...#..##...", "...#..##...", "...#...##..", "..#....##..", "..#....##..", "..#.....##.", ".##.....##.", "####...####", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 181 mturn 20 24 */ { "....................", "....................", "....................", "....................", "....................", "....................", ".####...####...####.", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..###...####...###..", "...#####..#####.##..", "....###....###..###.", "....................", "....................", "....................", "....................", "....................", "....................", 0 }, /* 182 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 183 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 184 phiphonetic 12 24 */ { "............", "............", "....####....", ".....##.....", ".....##.....", ".....##.....", "....####....", "..########..", "..##.##.##..", ".##..##..##.", ".##..##..##.", ".##..##..##.", ".##..##..##.", ".##..##..##.", ".##..##..##.", "..##.##.##..", "..########..", "....####....", ".....##.....", ".....##.....", ".....##.....", "....####....", "............", "............", 0 }, /* 185 kidneybean 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "....####...", "..###..##..", "..##....##.", ".##.....##.", ".##....###.", ".##.#####..", ".##....##..", ".##.....##.", ".##.....##.", "..##...###.", "..#######..", "....####...", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 186 bhooktop 12 24 */ { "....#####...", "...##...##..", "..##.....#..", "..##........", "..##........", "..##........", "..##.###....", "..###..###..", "..##....##..", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##.....##.", "..##....##..", "..###..###..", "..#.####....", "............", "............", "............", "............", "............", "............", 0 }, /* 187 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 188 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 189 zrighttail 12 24 */ { "............", "............", "............", "............", "............", "............", ".########...", ".##....##...", ".#....##....", ".....###....", "....###.....", "....##......", "...###......", "...##.......", "..###.......", "..##....#...", ".##.....#...", ".########...", ".......#....", ".......#...#", ".......#####", "........###.", "............", "............", 0 }, /* 190 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 191 oe 17 24 */ { ".................", ".................", ".................", ".................", ".................", ".................", "....###....###...", "..###.##.##..##..", "..##...###....##.", ".##.....##....##.", ".##.....########.", ".##.....##.......", ".##.....##.......", ".##.....##.......", ".##.....##.......", "..##...####....#.", "..###.##.######..", "....###....###...", ".................", ".................", ".................", ".................", ".................", ".................", 0 }, /* 192 glotrevbar 11 24 */ { "...........", "....#####..", "..##...###.", "..#.....##.", ".##........", ".##........", ".##........", ".###.......", "..#####....", "...####....", ".....##....", "..########.", "..########.", ".....##....", ".....##....", ".....##....", ".....##....", "....####...", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 193 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 194 lbelt 8 24 */ { "........", "..###...", "...##...", "...##...", "...##...", "...##...", "...##...", "..###...", ".#.##...", ".#.##...", "..#####.", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "..####..", "........", "........", "........", "........", "........", "........", 0 }, /* 195 vturn 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", ".....#.....", "....###....", "....###....", "....#.##...", "...#..##...", "...#..##...", "...#...##..", "..#....##..", "..#....##..", "..#.....##.", ".##.....##.", "####...####", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 196 gammaphonetic 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "####...####", ".##.....##.", ".##.....#..", "..##....#..", "..##....#..", "..##...#...", "...##..#...", "...##..#...", "...##.#....", "....#.#....", "....##.....", "....###....", "...#.##....", "...#..#....", "...#..#....", "...##.#....", "....##.....", "...........", 0 }, /* 197 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 198 jcurl 7 24 */ { ".......", "...##..", "...##..", ".......", ".......", ".......", "..###..", "...##..", "...##..", "...##..", "...##..", "...##..", "...##..", "...##..", "...##..", "...##..", "...##..", "...##..", ".######", "#..##..", "#..##..", "####...", ".##....", ".......", 0 }, /* 199 stress2 5 24 */ { ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", "..##.", "..##.", "..##.", "..##.", "..##.", "..##.", "..##.", 0 }, /* 200 stress1 5 24 */ { "..##.", "..##.", "..##.", "..##.", "..##.", "..##.", "..##.", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", ".....", 0 }, /* 201 ltilde 8 24 */ { "........", "..###...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", ".####..#", "#..####.", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "..####..", "........", "........", "........", "........", "........", "........", 0 }, /* 202 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 203 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 204 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 205 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 206 epsilonrev 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", "..#####...", ".##...##..", ".#.....##.", ".......##.", "......###.", "...#####..", "......##..", ".......##.", ".......##.", ".#....###.", ".#######..", "..#####...", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 207 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 208 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 209 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 210 rcapinv 12 24 */ { "............", "............", "............", "............", "............", "............", ".####..####.", "..##....##..", "..##...##...", "..##..##....", "..##.##.....", "..####......", "..######....", "..##...###..", "..##....##..", "..##....##..", "..###..###..", ".###.###....", "............", "............", "............", "............", "............", "............", 0 }, /* 211 rturnrighttail 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "....####...", ".....##....", ".....##....", ".....##....", ".....##....", ".....##....", ".....##....", ".....##....", ".....##....", ".##.###....", ".###.##....", ".##..##....", ".....##....", ".....##....", "......##..#", "......#####", "........##.", "...........", 0 }, /* 212 schwarighthook 18 24 */ { "..................", "..................", "..................", "..................", "..................", "..................", "...####...........", "..#######...##....", ".#....###..###....", ".......####.##....", "........##..##..#.", "........##..#####.", "........##...###..", ".#########........", ".##.....##........", ".##.....#.........", "..##...##.........", "...####...........", "..................", "..................", "..................", "..................", "..................", "..................", 0 }, /* 213 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 214 glotrev 11 24 */ { "...........", "....#####..", "..##...###.", "..#.....##.", ".##........", ".##........", ".##........", ".###.......", "..#####....", "...####....", ".....##....", ".....##....", ".....##....", ".....##....", ".....##....", ".....##....", ".....##....", "....####...", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 215 jbarhooktop 9 24 */ { ".........", ".........", ".........", "....###..", "...##..#.", "...##..#.", "...##....", "...##....", "...##....", "...##....", "...##....", "...##....", "...##....", "...##....", "...##....", "...##....", "...##....", "#######..", "...##....", "...##....", "...##....", "##.#.....", "###......", ".........", 0 }, /* 216 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 217 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 218 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 219 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 220 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 221 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 222 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 223 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 224 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 225 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 226 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 227 wturn 17 24 */ { ".................", ".................", ".................", ".................", ".................", ".................", ".....#.....#.....", "....###...###....", "....###...###....", "....#.#...#.##...", "...#..##..#.##...", "...#..##.#..##...", "...#..##.#...##..", "..#....##....##..", "..#....##....##..", "..#....##.....##.", ".##....##.....##.", "####..####...####", ".................", ".................", ".................", ".................", ".................", ".................", 0 }, /* 228 rturnleg 8 24 */ { "........", "....####", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".....##.", ".##.###.", ".###.##.", ".##..###", "........", "........", "........", "........", "........", "........", 0 }, /* 229 mturnleg 20 24 */ { "....................", "....................", "....................", "....................", "....................", "....................", ".####...####...####.", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..##.....##.....##..", "..###...####...###..", "...#####..#####.##..", "....###....###..##..", "................##..", "................##..", "................##..", "................##..", "................###.", "....................", 0 }, /* 230 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 231 hturn 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".####...####.", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..###...###..", "...#####.##..", "....###..##..", ".........##..", ".........##..", ".........##..", ".........##..", ".........###.", ".............", 0 }, /* 232 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 233 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 234 drighttail 14 24 */ { "..............", ".......###....", "........##....", "........##....", "........##....", "........##....", "....###.##....", "..###..###....", "..##....##....", ".##.....##....", ".##.....##....", ".##.....##....", ".##.....##....", ".##.....##....", ".##.....##....", "..##....##....", "..###..###....", "....######....", "........##....", "........##....", ".........##..#", ".........#####", "...........##.", "..............", 0 }, /* 235 dhooktop 14 24 */ { ".........###..", "........##..#.", "........##..#.", "........##....", "........##....", "........##....", "....###.##....", "..###..###....", "..##....##....", ".##.....##....", ".##.....##....", ".##.....##....", ".##.....##....", ".##.....##....", ".##.....##....", "..##....##....", "..###..###....", "....####.##...", "..............", "..............", "..............", "..............", "..............", "..............", 0 }, /* 236 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 237 z 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.....", "..##....#.", ".##....##.", ".########.", "..........", "..........", "..........", "..........", "..........", "..........", 0 }, /* 238 henghooktop 13 24 */ { ".............", "....####.....", "...##...#....", "..##.........", "..##.........", "..##.........", "..##..###....", "..##.#####...", "..###...###..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", ".####....##..", ".........##..", ".........##..", ".........##..", "........###..", ".....#####...", ".....####....", 0 }, /* 239 jdotlessbar 8 24 */ { "........", "........", "........", "........", "........", "........", "..####..", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "...##...", "#######.", "...##...", "...##...", "...##...", "##.#....", "###.....", "........", 0 }, /* 240 hbar 13 24 */ { ".###.........", "..##.........", "..##.........", "#######......", "#######......", "..##.........", "..##..###....", "..##.#####...", "..###...###..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", ".####...####.", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 241 lrighttail 8 24 */ { "........", ".###....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "...##..#", "...#####", ".....##.", "........", 0 }, /* 242 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 243 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 244 z 10 24 over*/ { "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "o########o", "o##oooo##o", "o#oooo##oo", "ooooo###oo", "oooo###ooo", "oooo##oooo", "ooo###oooo", "ooo##ooooo", "oo###ooooo", "oo##oooo#o", "o##oooo##o", "o########o", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", "oooooooooo", 0 }, /* 245 bcap 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", ".###.###...", "..###..##..", "..##....##.", "..##....##.", "..##...##..", "..######...", "..##...##..", "..##....##.", "..##.....#.", "..##....##.", "..###..##..", ".###.###...", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 246 ibar 8 24 */ { "........", "...##...", "...##...", "........", "........", "........", "..###...", "...##...", "...##...", "...##...", ".######.", ".######.", "...##...", "...##...", "...##...", "...##...", "...##...", "..####..", "........", "........", "........", "........", "........", "........", 0 }, /* 247 nrighttail 15 24 */ { "...............", "...............", "...............", "...............", "...............", "...............", ".###..###......", "..##.#####.....", "..###...###....", "..##.....##....", "..##.....##....", "..##.....##....", "..##.....##....", "..##.....##....", "..##.....##....", "..##.....##....", "..##.....##....", ".####....##....", ".........##....", ".........##....", "..........##..#", "..........#####", "............##.", "...............", 0 }, /* 248 nlefttail 13 24 */ { ".............", ".............", ".............", ".............", ".............", ".............", ".###..###....", "..##.#####...", "..###...###..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##....####.", "..##.........", "..##.........", "..##.........", "###..........", "##...........", ".............", 0 }, /* 249 length 6 24 */ { "......", "......", "......", "......", "......", "......", ".####.", "..##..", "..##..", "......", "......", "......", "......", "......", "......", "..##..", "..##..", ".####.", "......", "......", "......", "......", "......", "......", 0 }, /* 250 hhooktop 13 24 */ { "....#####....", "...##...##...", "..##.....#...", "..##.........", "..##.........", "..##.........", "..##..###....", "..##.#####...", "..###...###..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", "..##.....##..", ".####...####.", ".............", ".............", ".............", ".............", ".............", ".............", 0 }, /* 251 erev 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "...####....", "..##...##..", ".##.....#..", ".##.....##.", ".#########.", "........##.", "........##.", "........##.", ".......###.", ".#....###..", "..#######..", "...####....", "...........", "...........", "...........", "...........", "...........", "...........", 0 }, /* 252 zcurl 10 24 */ { "..........", "..........", "..........", "..........", "..........", "..........", ".########.", ".##....##.", ".#....##..", ".....###..", "....###...", "....##....", "...###....", "...##.....", "..###.##..", "..##..#.#.", ".##...#.#.", ".#######..", ".....#....", ".....#....", "..........", "..........", "..........", "..........", 0 }, /* 253 gcaphooktop 14 24 */ { "..............", "..............", "..............", "..............", "..........##..", ".........####.", "....####.#..#.", "..###..###....", "..##....##....", ".##......#....", ".##...........", ".##...........", ".##..######...", ".##......##...", ".##......##...", "..##....##....", "..###..###....", "....####......", "..............", "..............", "..............", "..............", "..............", "..............", 0 }, /* 254 ccurl 11 24 */ { "...........", "...........", "...........", "...........", "...........", "...........", "....#####..", "..##...###.", "..#.....##.", ".##........", ".##........", ".##........", ".##........", ".##........", ".##....##..", "..##..#..#.", "..###.#.#..", "....####...", ".....#.....", ".....#.....", "...........", "...........", "...........", "...........", 0 }, /* 255 trighttail 8 24 */ { "........", "........", "........", "...#....", "..##....", ".###....", "#######.", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "..##....", "...##..#", "...#####", ".....##.", "........", 0 }, { 0 } }; /* End of file ipaSerifRegular24.cpp */ sources_5316/kar/ipaSerifRegularPS.cpp0000644000176700017670000042451411547114240016544 0ustar paulpaul/* ipaSerifRegularPS.cpp * * Copyright (C) 2005 Rafael Laboissiere * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ /* This file was converted by R.L. from a PFA file generated from TIPA, * a system for processing IPA symbols in LaTeX written by Fukui Rei * (see ftp://ftp.tex.ac.uk/tex-archive/fonts/tipa). * * The encoding of the resulting file was modified by R.L. in order to * match the SILIPA 1989 encoding, and again modified to include * the reversed e and reversed closed epsilon characters * as required by the 1996 version of the International Phonetic Alphabet. * * The horizontal positions of the diacritics were modified by R.L. in such a way * that they overstrike the preceding character (as in the SIL IPA fonts) * rather than the following character (as in the original TIPA fonts). * * The vertical positions of the diacritics were modified by R.L. in such a way * that subscript diacritics end up below the baseline (as in the SIL IPA fonts) * rather than above it (as in the original TIPA fonts). * * These three changes were needed to smoothly integrate the font into Praat 4.3.01. */ /* * pb & rl 20061228 corrected width of secondary stress symbol * pb 2011/04/06 C++ */ const char * ipaSerifRegularPS [] = { "% %!PS-AdobeFont-1.0: TeX-xipa10 001.001\n", "% % Filtered by type1fix.pl 0.06\n", "% %%EndComments\n", "13 dict dup begin\n", "/FontInfo 16 dict dup begin\n", "/Copyright (see-copyright-of-original-TeX-font) def\n", "/FamilyName (TeX-xipa10) def\n", "/FullName (TeX-xipa10-Praat-Regular) def\n", "/ItalicAngle 0 def\n", "/Notice (converted-after-April-2001) def\n", "/UnderlinePosition -100 def\n", "/UnderlineThickness 50 def\n", "/Weight (Regular) def\n", "/isFixedPitch false def\n", "/version (001.001) def\n", "end readonly def\n", "/FontName /TeX-xipa10-Praat-Regular def\n", "/PaintType 0 def\n", "/FontType 1 def\n", "/FontMatrix [0.001 0 0 0.001 0 0] readonly def\n", "/Encoding 256 array\n", "0 1 255 {1 index exch /.notdef put} for\n", "dup 0 /grave put\n", "dup 1 /acute put\n", "dup 2 /circumflex put\n", "dup 3 /tilde put\n", "dup 4 /dieresis put\n", "dup 5 /hungarumlaut put\n", "dup 6 /ring put\n", "dup 7 /caron put\n", "dup 8 /breve put\n", "dup 9 /macron put\n", "dup 10 /dotaccent put\n", "dup 11 /cedilla put\n", "dup 12 /ogonek put\n", "dup 13 /quotesinglbase put\n", "dup 14 /guilsinglleft put\n", "dup 15 /guilsinglright put\n", "dup 16 /quotedblleft put\n", "dup 17 /quotedblright put\n", "dup 18 /quotedblbase put\n", "dup 19 /guillemotleft put\n", "dup 20 /guillemotright put\n", "dup 21 /endash put\n", "dup 22 /emdash put\n", "dup 23 /cwm put\n", "dup 24 /perthousand put\n", "dup 25 /dotlessi put\n", "dup 26 /dotlessj put\n", "dup 27 /ff put\n", "dup 28 /fi put\n", "dup 29 /fl put\n", "dup 30 /ffi put\n", "dup 31 /ffl put\n", "dup 32 /space put\n", "dup 33 /hungarumlaut put\n", "dup 34 /dotlessi put\n", "dup 35 /macron put\n", "dup 36 /grave put\n", "dup 37 /quotesinglbase put\n", "dup 38 /caron put\n", "dup 39 /quoteright put\n", "dup 40 /breve put\n", "dup 41 /tilde put\n", "dup 42 /ring put\n", "dup 43 /ff put\n", "dup 44 /comma put\n", "dup 45 /dieresisunder put\n", "dup 46 /period put\n", "dup 47 /P put\n", "dup 48 /tildeunder put\n", "dup 49 /ffi put\n", "dup 50 /ffl put\n", "dup 51 /fi put\n", "dup 52 /fl put\n", "dup 53 /quotedblright put\n", "dup 54 /guillemotright put\n", "dup 55 /endash put\n", "dup 56 /ringunder put\n", "dup 57 /quotedblleft put\n", "dup 58 /l put\n", "dup 59 /Idieresis put\n", "dup 60 /n put\n", "dup 61 /Lcaron put\n", "dup 62 /semicolon put\n", "dup 63 /Udieresis put\n", "dup 64 /acute put\n", "dup 65 /A put\n", "dup 66 /B put\n", "dup 67 /ccedilla put\n", "dup 68 /D put\n", "dup 69 /E put\n", "dup 70 /seven put\n", "dup 71 /aring put\n", "dup 72 /h put\n", "dup 73 /I put\n", "dup 74 /j put\n", "dup 75 /Edieresis put\n", "dup 76 /eng put\n", "dup 77 /M put\n", "dup 78 /N put\n", "dup 79 /oslash put\n", "dup 80 /eight put\n", "dup 81 /ae put\n", "dup 82 /R put\n", "dup 83 /S put\n", "dup 84 /T put\n", "dup 85 /U put\n", "dup 86 /V put\n", "dup 87 /w put\n", "dup 88 /X put\n", "dup 89 /Y put\n", "dup 90 /Z put\n", "dup 91 /bracketleft put\n", "dup 92 /Dcaron put\n", "dup 93 /bracketright put\n", "dup 94 /circumflex put\n", "dup 95 /dieresis put\n", "dup 96 /sfthyphen put\n", "dup 97 /a put\n", "dup 98 /b put\n", "dup 99 /c put\n", "dup 100 /d put\n", "dup 101 /e put\n", "dup 102 /f put\n", "dup 103 /g put\n", "dup 104 /h put\n", "dup 105 /i put\n", "dup 106 /j put\n", "dup 107 /k put\n", "dup 108 /l put\n", "dup 109 /m put\n", "dup 110 /n put\n", "dup 111 /o put\n", "dup 112 /p put\n", "dup 113 /q put\n", "dup 114 /r put\n", "dup 115 /s put\n", "dup 116 /t put\n", "dup 117 /u put\n", "dup 118 /v put\n", "dup 119 /w put\n", "dup 120 /x put\n", "dup 121 /y put\n", "dup 122 /z put\n", "dup 123 /odieresis put\n", "dup 124 /asciicircum put\n", "dup 125 /oacute put\n", "dup 126 /perthousand put\n", "dup 127 /sfthyphen put\n", "dup 128 /Abreve put\n", "dup 129 /six put\n", "dup 130 /Aacute put\n", "dup 131 /greater put\n", "dup 132 /Scedilla put\n", "dup 133 /Ecaron put\n", "dup 134 /Eogonek put\n", "dup 135 /ograve put\n", "dup 136 /hungarumlaut put\n", "dup 137 /hungarumlaut put\n", "dup 138 /Lslash put\n", "dup 139 /Tcedilla put\n", "dup 140 /five put\n", "dup 141 /O put\n", "dup 142 /bar put\n", "dup 143 /space put\n", "dup 144 /space put\n", "dup 145 /Sacute put\n", "dup 146 /braceleft put\n", "dup 147 /macron put\n", "dup 148 /macron put\n", "dup 149 /Tcedilla put\n", "dup 150 /Scaron put\n", "dup 151 /exclam put\n", "dup 152 /grave put\n", "dup 153 /grave put\n", "dup 154 /Zcaron put\n", "dup 155 /Tcaron put\n", "dup 156 /braceright put\n", "dup 157 /quotesinglbase put\n", "dup 158 /quotesinglbase put\n", "dup 159 /section put\n", "dup 160 /Odieresis put\n", "dup 161 /ring put\n", "dup 162 /fl put\n", "dup 163 /fi put\n", "dup 164 /dcaron put\n", "dup 165 /ecaron put\n", "dup 166 /guillemotright put\n", "dup 167 /ugrave put\n", "dup 168 /ocircumflex put\n", "dup 169 /adieresis put\n", "dup 170 /ffl put\n", "dup 171 /at put\n", "dup 172 /zero put\n", "dup 173 /Lcaron put\n", "dup 174 /one put\n", "dup 175 /OE put\n", "dup 176 /quotedblbase put\n", "dup 177 /ff put\n", "dup 178 /eth put\n", "dup 179 /Q put\n", "dup 180 /L put\n", "dup 181 /W put\n", "dup 182 /uhungarumlaut put\n", "dup 183 /uring put\n", "dup 184 /F put\n", "dup 185 /AE put\n", "dup 186 /aacute put\n", "dup 187 /zdotaccent put\n", "dup 188 /ij put\n", "dup 189 /udieresis put\n", "dup 190 /dotlessj put\n", "dup 191 /oe put\n", "dup 192 /Yacute put\n", "dup 193 /ffi put\n", "dup 194 /igrave put\n", "dup 195 /two put\n", "dup 196 /G put\n", "dup 197 /Aring put\n", "dup 198 /J put\n", "dup 199 /sfthyphen put\n", "dup 200 /quotedbl put\n", "dup 201 /edieresis put\n", "dup 202 /Ecircumflex put\n", "dup 203 /ff put\n", "dup 204 /Uhungarumlaut put\n", "dup 205 /Uring put\n", "dup 206 /three put\n", "dup 207 /Oacute put\n", "dup 208 /dieresisunder put\n", "dup 209 /Ntilde put\n", "dup 210 /K put\n", "dup 211 /otilde put\n", "dup 212 /Adieresis put\n", "dup 213 /asciitilde put\n", "dup 214 /Q put\n", "dup 215 /ecircumflex put\n", "dup 216 /Oslash put\n", "dup 217 /Ugrave put\n", "dup 218 /hungarumlaut put\n", "dup 219 /space put\n", "dup 220 /macron put\n", "dup 221 /grave put\n", "dup 222 /quotesinglbase put\n", "dup 223 /circumflex put\n", "dup 224 /caron put\n", "dup 225 /breve put\n", "dup 226 /tilde put\n", "dup 227 /ucircumflex put\n", "dup 228 /Otilde put\n", "dup 229 /icircumflex put\n", "dup 230 /circumflex put\n", "dup 231 /four put\n", "dup 232 /egrave put\n", "dup 233 /circumflex put\n", "dup 234 /atilde put\n", "dup 235 /acircumflex put\n", "dup 236 /G put\n", "dup 237 /iacute put\n", "dup 238 /Ecircumflex put\n", "dup 239 /Iacute put\n", "dup 240 /egrave put\n", "dup 241 /iacute put\n", "dup 242 /ograve put\n", "dup 243 /oacute put\n", "dup 244 /ocircumflex put\n", "dup 245 /agrave put\n", "dup 246 /one put\n", "dup 247 /idieresis put\n", "dup 248 /ntilde put\n", "dup 249 /colon put\n", "dup 250 /H put\n", "dup 251 /nine put\n", "dup 252 /yacute put\n", "dup 253 /Eacute put\n", "dup 254 /C put\n", "dup 255 /uacute put\n", "% % endarray\n", " readonly def\n", "/FontBBox {-72 -331 778 762} readonly def\n", "/UniqueID 4500055 def\n", "currentdict end\n", "currentfile eexec\n", "d9d66f633b846a97b686a97e45a3d0aa06da87fc7163a5a2a756a598fab07633\n", "89de8bae4f093966cd2192ce95eb0f323a6babfdaccfcf27d91f7869a0e46ca5\n", "9aaf6905783e8ac1f3f9875a76f97187738432f8d14e61574cb292ffb9740871\n", "66839799d8caf6e0dfe00012ee6d46a2b3655f29705be37fd5eda1c765aa2cf5\n", "c5ad37207ed1ee9db82ff31a33307ffa16911406557336af92f50b603c7bd336\n", "73ec060f68318378a6f599ddada5a21504cadba1e1f4b1a22962ba1bb39adc7b\n", "e8cc92f196549457877c9636a8a7efac1c3745644c0fd151c70b9fad69b02c1f\n", "fe5ed071ca1cf3d4a70909b6a39e1d447a7483fd8051be7aa167d87e638721fe\n", "fcb084bca27f055024228a75335fde2cf0336a5d4c1cbdf9ad181f51557a3aee\n", "2541b62e5ac7bf366dd962d8277bdd2e825d37b25bbda4856f1b90356c4e6a7e\n", "be19bab3a6278de0ca3791a7f36a92611c635d2430c8eb8e8a5ee8a72a6f75ae\n", "67b7e141bcc77de48975d117dd1031bf1c3f64ab2b093d9d2f19a1ecc9f029fc\n", "2026a326f26f7c374fa935b6540905373dcf1c057f87e64a02890fec2d98d926\n", "f8b6f0422f33405cd72cee9e9a862fc6839b28a8083319473a3092e15fe1f2ac\n", "b28e17df42ec60aa8b0209c7727648c46fe6de11c32d67f5ddb715a86df87431\n", "48afbfa2cd48ff4453a2d2db9857ff89c01a4d1b06a9c32d450c294b49286f59\n", "4bb6bd224f9e5531c607cc1a8be81c24a8f4ef67e1bf355daa4cae0221e2c18d\n", "38ef6916b12d05f7c85426a539c5791b3fdb67efd1a1e314922005a8f9c861a9\n", "8b6627732ed14f9fa0808cd8e6abe7372d6a12f20b5e1e7bd758e684b1618988\n", "bf15b134270e00a918fb7a4412d5c033a9dfa40346bfc161f40ea8d5715487d9\n", "64872f9e15288047620bee5378c9c9e478102854e0f1edddf2ced8d0fa9919a7\n", "10d5183e8ab3d4f835ebb01b769940dbd1b66c4e3eb807bacc2fb733c2a3036d\n", "655f5f46c62553bf047e1dc2aac6ee79bc19d156ce259c8db3ac9893e019b88d\n", "f6772b46d4a3440ddb8f491eeb060f4d0a2d5c8fcddc3ed41cd32dae1b459659\n", "63836ef4d0198691408d29875d7f0ba23ed37480b88cbe7dbba109a9839ed04e\n", "b3ea3184662173087679e7c717eb334f3699548992c65226e750321672115bba\n", "d75bcbfd615cecfad52b39ac3a30a290f6c974e8d7edc0db69a1ba58d85e0dd0\n", "ec62093f53463e0a53d7a178be754e94cfc1b8d45e546ef4499d25ca7aafa4fb\n", "f3f7f49dec8baa6d4ba58f0f770fe7da707e418458d53c2bdf17da67d09c96d6\n", "e8cb1852fc091c87c8e0510d8057a840a820e3d3085ef76f47acadd771f7a929\n", "1933bdda7ee03293e86ea3b8bc0ad1befe32da75bed1f11f091d6232bf6c2634\n", "81ec5ae35bf51a3fc5fb4f1082f75ffedd7d9cf0ee84d812cb1bc382f4b21636\n", "6218b5ae6843170811139f14308dddd55b739960b45ac2514ed9d97d726e8565\n", "2488f1a70c12480480c522107ecff83446cef3a76cc880e423908e29cd5d26ed\n", "cad17a83882087227f8b274b84bb526f685bad59f7846384feef8c821d010527\n", "f2f9d109a7b9a89557998c031b74cc2045f9aaf50bdb0feb0028df1946853615\n", "42a24cc7e02c9a45947fa3a347b935bdad8428e1271b8fa971fb3e054bd47b67\n", "47d64e8097fc3deca15ec91033cf24a8f969fdb637070df8f7398e397547e5c5\n", "41d7566028ee88eb0224f00a3d1399b736e7f3c3060d713f3998a977fc3e41d0\n", "30324b35913d889575b6e1dc44380fcbb1d66f52824f28b22ef6802b77c8d263\n", "166da13933b9af756383043257e2b654df6d165d44138e9be03a1f2d16dc3b2f\n", "9937f07310ed73352c2ebe6ad4f1d5a91c4c358ce669ac353738e3cee8170e3e\n", "2a43e75925e7b525784c25d26f41bd28b72a8c96a0485a6727325b235539be1c\n", "678cd68fce492ac86f05ace7c89b533eebe45610f6ce36522d659f4b1dcce327\n", "bc171c4e8118141c30dda2e1ba6ae3d89f44145473e116dd640aab59dad696c7\n", "8ed9e42d16ca10c304baca6f282e5ac1f5e2eb6ad60a95df32a4547bd6e5c7d3\n", "7b45174c2b11992fd27fc0f993778155c581eaa7f3bdd59c3ed3205cbaec40e5\n", "c2fca284a4146afedf643ec8c90a080238c513e9dfed2f9c738eb97d46d0fe79\n", "9ba59abc2f8528eec1799dea805a25a614afc52e6a57e50847569e65e4c97e0f\n", "50db687b45baed499e3e5bbc5945ca8b308d11c03a97dc30dac8176edeab5091\n", "a988d665bf867e684dc5535ccc5735cde1b4da684e06acb1fdda9179bc2c2e37\n", "347b100e0f44c7dabffa5785fa27969e6115ed65ff5098507d3993044f163da6\n", "46ce6ad9b24c6f13d9f95b317e7363ad4ac5d9b29c7f0d8c84a0f7ffdebf05e1\n", "2b86ac276c82871e86f91bd193a3bc7b6ec649164c034eb875f8555802a82819\n", "c9c704c6133d4466c6d1a2560e032029946e7b14587aa22113db0dd80406ba05\n", "bb39e1997b13323e8f997e100bbedb06ad304fa0849020e794c92168d2dc61f9\n", "f0e3c332dab30a0cf6b6c7731d6fc56c6cf34de11d78b7b42d91b0ebf712c0fc\n", "bb4ad1f741293a505a7417339b8d843181cbb7806058bd88c27d4f9b56418166\n", "08b457181408d7847d97e8b0c386642030723ef0bd8f6d4ca0cb8b9780317975\n", "b7e9bc15f92880be5172e55332191c84d991cf519cbe90f2ea7f1812d670b5e3\n", "853219655aa651fe2ebc21665fe4ee903ed1574bf183246b1a6503aa9eec05f6\n", "ef2553617f2b5ba01017a489f7614804e0f6cae8e444770ac6232e74009b5631\n", "ef1456cfcdeccb6d4dd5dd20fe6f8066858ddefd42127b639dbc6278af601bb4\n", "4f665f39b6d0c02cdd42a8803bdf1787c489f0609c8ba5f6f9909d6eb39cead7\n", "a3cfb33b0d42bfd8da49507f97796c0cef8c078fdbc85f6fba031e33037ef51a\n", "cde3aa53e99897adc94103fc4c4eb3b505572b7bb4f0210dbc6f240fd6e5bc67\n", "6dd7ca9e004c3bba28e2ac047898e3569029a835ebe9f2986dfde29666f7e8f3\n", "cb5ea9d57fbe736bb0b543e48bad658b2ff692dba3fa3c6a094c90df77e0df61\n", "6a24759236b9645d78d1030f3a6e0d3ce60d66665f53eb7bb81db52e5e7e1260\n", "57a2e7a19d7d7c4e2bae6478202d4007132735686ba34908ae1ac98b1c88f500\n", "15ce641260c507de9421852112019bb002eafd33c8fd6fc0b7a27c3b1032d2de\n", "686cf225d4f0d3f7b321ca807f620254491813faff856ae39cb95cd9ff7282a4\n", "4a6c08c35bef1ae6e5613d8c62195d1fb866e38e9e69466efa57a280c9e6f45d\n", "010acc031b33421f450c9049799322edc651636a57513b04b0c64813c07ab4c7\n", "ab3fa5810963f89aa8bbcc11fcb061bbe88d6c7f7f957242150f10aa2b1040d9\n", "b81ea7af9d4fa6a63c8c73ad6a6ac731a6dd695863be61a18e9fc97aad20baf7\n", "0a1bc186fc9d7a4012b338d2d24905f76bb79c53b0f0c91f62b941c6bef2a310\n", "6abd88b00469201930be8001a44328ada3b17ef25f0d1926b243c54d95296393\n", "e80425d31fd752c99c8e57abe7da8765a38597431ec0ee7d8e6844f1889d9337\n", "e3aa0ea08955c284d71b6885cf589861cfd8094732f90028552ad8d09d130dcb\n", "262943513458b9d2e731ba3caedae14f9a60553eb409c11f0ac60ff2d783fd82\n", "82b3863db9c3a7881cc26e5e04db975e789f505dce7ce7f2fa955adfe89efbbc\n", "7b870dcecd7202be053915eb0b9e9d5f5d12fa1f4b31246e4c1f3ed2eb2c40bf\n", "c11ba4fd43583b36d229937ad445538c4326cc4d1d5cdf4ab74ff3d537c6e257\n", "3f8734c1c71803f86d83d76fdcafc43a7227f6bb3a528dfdc0410ce655197745\n", "79b269e345dcc917bd720851dd4f4575b57973b97257cd51050da082009ad499\n", "04f5b3823fa6abb6db63f6e104e81e16932bdb9c4c9fa815604a4ccc9c61757e\n", "5cfcdaa0ea0beea6d7212f33b818ef098a3f47db51b03578bfd6d52e3e1916e1\n", "e5419fb734e072654abab653c74a5df8bb2ebd62d6ae9ee33aedaae0eec033f1\n", "06f4b0f8c8f9e22a700980565ac7beda5938b536da99fc69b9bf383b3cbe5bf0\n", "18382d9987169b45b1c1b9ca2769d05188491e1fbe204206ef16c2669aa12d76\n", "766b8d5063b403ce2894b6a5f13aba7d0d416cd25ec4579971466218ff619ebd\n", "752554ce0aa538704d73c71902bf71e903e8e679cd782694c487b44d3c7f13ee\n", "c61a9eed943519d124ba81d3e7735d575196b61a182db2a93ccf97769af56648\n", "801bbb53c23fe5ab5be21fc1293404f90abd57f09dfc393f4a410d4506a947e5\n", "aef1dfb497ec7a7c65fda56e4125688e9a1baf3dda6536a527f9844a32b15daa\n", "57a756bbfeeb1f1ae5bae4fffd965f2e1acbb983712abf968f79e5ed5df2a8b0\n", "d7828a0d77dca48b54dd590bbd435170e90a7365d93d3e12babdeca9db35515b\n", "a1805637115bcadd67766371d431e9febf860eca25739d629af2309bf229b0d6\n", "563122fe42b9d7b7c46d6a91833965a2f024cd241b87e5508a03126cbd855531\n", "6a2fa770a81511497602d69411264218589b29a322453f21602c9bdc326fb44e\n", "b81c6924811f2b16d4e28d4b20714262f1033cd55936e439c7427b4062f156c1\n", "1a73b4127335a6ee7951ea10c00aba4b0025eb958e3040e6548a49eccc5011dd\n", "fe158b72b5f4b9c7b9cd1fc0d123b9432da2ef34d1e9957677de7c42c82eeeec\n", "efa99fce0c91db767b8c343ba0ef8da61c1be4f059fc8e1a214124d4afd805c7\n", "cbedb1cb4be9235565393675475326f61ea7a16c8ba779e157815528abd6291f\n", "3ad08d8aa79855dfe4df281f66ac8359421ef14625968fb653e59a41b7a21b72\n", "14d559769cd82391ac7ba4779fa9cfac160419b1094ac7f522214b7b003868e9\n", "dfe4533d8cbfbe8e10d2988f7b84c8c773f8dcbfa22f783647fcc15b2bd4169e\n", "3ab899aead19438e61db153445ab2f12335c844037be3691a3ce9624496acf29\n", "ccc3886027ecb04270243183579d4336db08b64a7195624052570402f130769d\n", "b631d5a496748fa633e1368a0555ae1ad0546d36db38e4735ec693882ecceced\n", "b2ffa7eee812fdebbd9940df26d95c1903bbbb02bf171967acb1641a581393cb\n", "20d1f6a9f3d8573b69a0ece68f5d85e632a1d7be142462b7081a244dd303303a\n", "e9661490e44a7ef8a58756fcb8cd812ebffc547e07727ac20435f0e2a5c689dd\n", "cfbf475843d009fa76d1159bf66e24b93ea686e8f310e75ce44e7a447e798cea\n", "77331980c3f0d17c487454fc893f10887689f53ff4250b2bbeca3d3400052f25\n", "73b8c08a6772e07a05dbd88953052baa0bd04293699f3ef6626d7da132a7c559\n", "f47b051d5a29f8972eb73ab8adb1def9d69886049574d0438cf07c89f959c8d8\n", "b13569413b9c4143ba156859c7f2cf61f0ce50d9fecb4a2849c6a275f34794e6\n", "a096111176dc32a0b53d64a4ccd0381b51aac88c42577c7a0c8912f5c10209a9\n", "b839aff3edf230d9b6e1ac0b42621e941078d8f36669d931e6d8aab3fdbdd8a4\n", "c9087ec9e9b3c194572bb69e235b8fc0d5f139f51445c007885c296d2e826054\n", "32fdba41db0f7364f29f5b50c05eef5c1d76a7f5d279556b938be81c241a2f31\n", "46f38b89f58d4ae39e649e6d34c0f1f7a64c07fe6fc2a9f68ddcf9d866c77ae3\n", "38d52c761e22a716a84184470ed10fc4558d00c59742ebd9c147547db2160581\n", "2a84067b6eb6698dccb7412bd53fdbe9c43eb96e9d528e5f9e93ff2be50346ff\n", "c76e0baf58c6e7eee2925a0a576667cfe28f7067dc6d9755eed24e384ab3ddb5\n", "0656499db9a97505cc7e4c21750d736597a6bbfe95feb567dfea1fe42ad10141\n", "ea709c1c52030f3ec9143c96b34bc471d78602869ef06b541d6905ac8905a581\n", "23132d1c41d9fcc6b421163fa4ca0058028af9285b8100fe19c2b64962dfcd5e\n", "9c5e1027bd515faecdeec78ae8dcb21ee4d1f1d3077afe348629356edaaef122\n", "8174ce44529307bafe1bce23234d6109154f7fb85026a5023eaef7e148d39975\n", "5d89b3293a3907a5be7aad1a1e2555e61ca76a05ab92661e150a33b425e620bf\n", "92fe2d6a655ed2a786c78194730c2cfbe56ed9bf719a96e5b29ebadf26223f65\n", "461a1ba72f946ad96f38e74f3bc67ca1f8d8baf325b2c0971623eb55722349c3\n", "0a0a75726672455da158c5e98de41dac5a08f49c2ffc16f40a3c564806a5ed5b\n", "a75aa36487f027108ad768c4dfdc9827610cf1404e3e60190c42264c04c87c28\n", "e3cff73e353f0e13705cc09159ff8b454a4898705ab9e3e16f6cd9efed87114d\n", "6a23134d19a160e50df033f5931874c6f4fb4a473805ce276ef1cd2e84191791\n", "1cc6e16eb84621fda15e57876d1b46e2fa61926c3895fa3fcfe57ccb9a28d3be\n", "e1f48d9d21f4c2166e42246934dd006f5256c7fb571cb564b59704e13f85cf18\n", "3f4dacc58a7447da32fddd265c6462aec64a31642a996d532ddc62b4316ade4e\n", "2c4c860d238619cfad61326faa89d52997ce16a1e4a2b8744b26564bf7fc89eb\n", "3bfd65526b65186e6f6d790008bc9d3ba57405354b7dd889aa997d6ce09dfa5e\n", "fe9851fa71811556740882be19c2b3b7f3f8013bc21a35fc987ff7890f5cc1b9\n", "cfe98b982990f7ae3d04ba7b6e08b9c21d7f93e13fe515bbb6659571f7063508\n", "327a540b15cf977e4a8bb6d7f8017a35295eccb218b3be98647bfad995b422dc\n", "d6831d316f3cdb47a7f78919029c1ec42426d69d9599849a80e801dbff81a701\n", "dd4fc0fbc4637f6d77438b1b0fd3189dbe6e38a88257cf7ec3b3b2053039f3b3\n", "3e5f88e812dd24297b3cc72389df6c7f0af9c395dd925bce5d6a58fd5c71b6c6\n", "e301f1cbb06cc52013c980c0fa5f0efc94434d99312927af7d7e8fb0cfbbdae1\n", "ed3e9936c7e668a17f5c62ad9ca9239a77f35150e80bf415891d690a06db777b\n", "e2e58ea5e8f932a74d383152bbe177400ced7eb0a1803880c96d18c971d2497f\n", "da86f80453f8f43120cd48b7452a588ba0d1e6a6d7c7eaf9b632ad08790200da\n", "7e5e033d855c53af74b392a9bcb655aac2996427438dc4a33ab66843c88c4b45\n", "1a43766c89651f3b769dc9b889c7660587ee237c6258fee5122f25bc76929aaf\n", "dafe8263dbbb2a7a856c7dbedc80c19fb62a98490ae3d1a5677ab2432a85d922\n", "9fa29f97e30d482a7410c9a4739296fd4d6fc38a68707476d1a18f31d7706135\n", "2d1b8e490e90aa1d1d77210cdc8a8eb1025b6f318d30ab8fc7df5abee0ff44e5\n", "571aa0f3b55b0871da946d43f8ecce42470a988ce031e32e9002ec3bcf9ee0dc\n", "63b354f4fe929d239868aa79f37d15263f886b8d36c19b132253d36662cee778\n", "ab3407c2d226987b30efde2bd67f23b797eca327f81ba16a844aad1496c7f4d0\n", "3305a78d7f3a6dfb21b799bccb3df17326b67a88f073b34681a35762f640f411\n", "2d13cb57ab4a44ea455509ac085a8d8dcdd075d6e72f2967b3c0135f8bfaced9\n", "08717fe7958ca89f6cc2074bb38d0816c2e409b02354ff0785cfedc8470e945e\n", "7fa95d5b17ced77381594ce2ce464f786e0d33bd329ab2ad3d92f960235d0864\n", "de054e0e9197a8b78f2b1d1ca8da9d1a822f4fd7b9c5f5ac13fe1090ac620f6c\n", "63a510ee0dd20f7d5942dcd0c7af5f4ae245df8192a33a2b4397b26381cfc0af\n", "1915995b466b2886e0e11bf2e8e91abb03b98936e5cbce09632822947ccb5620\n", "5330c4cc56504d5d8ffef977939521088b3f9dbb6d379ff8673f0ef63b7ec637\n", "67a518e31d3e17806612b384f49aa456179059c7cbb1cea025d17b004fb63410\n", "8368ab16b9977dc658583f0d0d43a7276fe5878b69e8740215e71d99a401987c\n", "f72e63fc94ddbcb158afb014f47b516bde14c57a4ea418c9ff499013efcebaa3\n", "ac1bd5b883d3532563f6aaeea6f4c0326abb9aed3306c3cbb9b363f5ca022a46\n", "386a83425c66d7ca98264a765d5d00f61b8670d8bc74c473bfd6879e7eaeab4f\n", "6378a52ab60816fe0b643c6e1363c89f3070635f2173d585a726dc228054c48b\n", "ec8be2e633f6880f3c807cdc9f4317f01cb96ff771fef8b13fdbd8ea92a9e36f\n", "f1eb04bb78e7bb4a197c9163d1cdaf8a1cdd66e5ceb49ea65207504a72f23e48\n", "dee1d754b7b1170bb4bda36581ece1f10d79379447536f0afc53a7ee6f445538\n", "069705f4d171f944390bb39f49684475666fc7f59066f21bf82d52431611c84c\n", "5f8ac7c1d040aba35e226709ff78b7af1dce1f290c822304aa497ec8d4a0254e\n", "2b2636658abf79c1144fc7cef4d319a01eb2bc44ac1709c3a0fef96ad6fc2132\n", "aabf623222feb79a2637174b424f071ed62b7eca13065c8c1e03bd8d1b09eb83\n", "3f98dc6393f0ae1f2ffb7c75953c8541bfb9f17d4e10d1e925a9c18c65e175dc\n", "7b1133f482b748b58fd8519e5515c529f30545db441e04ca74d1395864dc6607\n", "962dd27bdbd3e8374064e692b9276c8c484f1d92dfab036a7c768545e86c3497\n", "626013b77caa9a2e9d7037e03ca7b856085ca8aed4524e207088565ceaa516bf\n", "2bae59b9e83d2f120f5147eb70d57b2688cbe68f48f1ea17853caf4f768cabe9\n", "5876a5e2b547b44e3e90ff854b7ab80d48360d225d8bf5cd9075a8259c803357\n", "13b0d590be5e93913f1bba612560318c1f8c2ee0cfee99616b1cb20c1ec0bf04\n", "848141ea66fa5d5e92195cdc9ab692edb7130014d52197623ad5685bedad9006\n", "23adb77b4dcc44a055da9c53dbafd20303622a1626c2eed2648c7f48f9f2ea96\n", "4d6bc27ec9c0af7f0ff2a4dd9ad740e860fe97efbf276bf3d20ed3348fd063fd\n", "fc1ec90601e2fb2ca62b2e3aad74c3443291aa48913a1c33713e443837c9b09a\n", "97c344327f9bf1b551da29bbc61445958093cfb93e0865469d30a5069d5f6f89\n", "e7b0107b40359517d664ad65fcc0b79351ba4517c8c28ec32eb8bcb9ec45fdf0\n", "2b5bfb328aeb3b20c522594c59366a53ea314eddfb9f822de7794240dd1266b2\n", "631608b4f801f3c1eb37594d8eefee7c692d8973db75d452f255eceb9e8301a2\n", "cdbc13c067b4c77d5c4c4a99779b570220e8ccd9fddd8572c17274851d7c4064\n", "5c301d5306dc51fee298a3f7fadd7a5fdf9de3a7897e446009dcad1b7f11aed4\n", "9b0f1512df1c45a51c5f570e64fe5ac95d3165354be28ca5899f271f3618fc5e\n", "3c94d931051425943af651cb046ac3ea3298b3def8bea4b12647d86966e20516\n", "6429c0a528613ef468183548090030ed9bd7f0c2b47b75d442d7275a2c403f19\n", "616816f4ea0045cf89ef4bb5f12895350cfca008aefb74f9e5fd8d4f6691fc8c\n", "3f986b6ab1a77e9d5be3d9389c5aa18aa17263de0ab917d1350673751f1601df\n", "b394318a2e7a7d471ae7479ee858f3f2bcaba04fd64d621384d6643d13d9a26d\n", "b5d219eb3a867c914ec23f584070eccd49ed4cbc5dfeb2135da075172d8fb9d9\n", "126d6ca79283395945195eec0b7e53655022469ab81dc62f68299d09afcdd282\n", "ae2e0f6643e5a54cbe3735fa1b46178b6800bebb7d4ea51a8cfcfc04f122ccb5\n", "7fc86b03baeee96ecd74186531f9e1c73e20916c9f4cc37428e0fa3f5ba9608d\n", "41d98c621c0fad646c9a406df6aa0e95527462f8c8b2db60d0939f5985eaacdd\n", "8d0f663d09218495317fd63c81cdbd8a5c56608ef399833e57c48fc37f2069d0\n", "df528d3f95bcf62c0e5f5f18d6b886681ffc594673198c49a32a6edad081df1d\n", "f5f58acd4c1097008e1f8bf608f772da2f2f933c431debad8c7e969ab83e131e\n", "16e112de80813b00c764c02bee8b54fc76c4aef9d75056b84005bee3b5a7923b\n", "0224c63911a7bd454c91cb1f8e065c44fa3616c799624c4a2ccec612d08449fc\n", "489509ddc77c0d21d7533c0f3bc62d2363adf3552240a286c684fe4a8d43a892\n", "fb36ccb11c6fd951e0f8ae34c9e9a5ea4ac018ef04677a1ea96d9d2b73248dbe\n", "fbe0e0f580fb2b899afa2ff4588d96540147f53b8f132c04c8f3f2427cb5d68c\n", "46b2842b3104bc74d637a5d3a12fd6973658b9214bb9070165ec1a173132639e\n", "8d65514f8051740b3c463679578e256aac66eefe65bcd260774f5885aad0f139\n", "c02d0cd6de46236e6f8187c44a900bef79ecdf53c13c2f00a3f6f3696811cb14\n", "43057d99e096d70aa0715c5009c033683aff419d5d477a9b18cb203415d4697b\n", "567a959e2579056430e6859c5fde92654a1f8fc762fba27b63621ae271f023db\n", "9159f7b5175065eacf227f4dc69cb9ebc1b0dce07b7841435aadcf20b36705be\n", "9818ca657b7e173420f5a86861fe787124ea68e53eed9168688435c679434bb5\n", "b0adecc5a145cdc7b9d85a32ae4d867e76a9b8f6314ed198a2390f6d0c7e7df3\n", "23d4c2c9b587c66fa45e50f26eedc042e818c5556c9794d7dff146ff9983c6bd\n", "a8a27d50e18fd0b612dee5ecfe25765630de787693d02a03ebe76ab0d9a6312e\n", "850957a9fa40f303bfcfe8463b145e1191730e2cf11fab365ce744109d43e259\n", "3c75342780cc14113064bafff6f772345519c4dc535c94c008854c0c23f39780\n", "071e72892274c46794ef1f8fa31f859b021901b433259225b37663f793620ba1\n", "abafe92b6cf2b9e242476dfc67bad7c3cb9411200cf5ff0a57bfdb4adcaf126f\n", "2238ddfdb9fd3d08fb3fdce84485a0ba42da878df5b42ed330d35115a8e008fc\n", "ccade4ed446017c0412bbc0fe848944664e99ac79ed9b8bf8ec5fafe6f14c7d0\n", "3b82378b01d44cf5f9e8e95e8c69179c9b13330866806a63785fa5144af0deb5\n", "3491acdfca8e492079f427409e1826e0f8467acd6c4cc90e3a5a6ea56f71252a\n", "9221e8986eb5b2b72092373494e0bddddfb4a3e51b873ea74bec88ea093e0800\n", "2fab03d3faa85d18aa036b9027b86a6dbc2aac31f562c806b3c872a578f78906\n", "56f238a32f2739f6074b0fea300a4a5872b9ca5a72c33b1764c7e9cc99ff5880\n", "a1554188b392974e1529025edf0ffc73c311b19ccec92c719a27ecbac33e8aaf\n", "6a0bb464ceb9438f8e92281adb3d0c83773282d04be6d07ea2e21e9aac69bdda\n", "6eaa08404e21744621f024e30c1cf08ea0ef46b1f8cc7951df2506367914baa3\n", "07207b5396244a4a7465427b7b9cc0cc5a7a47b649771014dc49ac75f1c07b1d\n", "cbe65704f2d539bdc5001127ad988a869b472347156dc65e9793cc69973f2138\n", "547c05ef5e9b50816bd32b281cf3c3b8f3fd6fe897f33910a304cb5a6e3ffe95\n", "d53307eac38b03106c2f4da173884df388153b3d34f815d6042aec014534b9e4\n", "8bcced82eab1c7a76c94693f3f96282e6a6f5bc0cb7b2b9dddaa9dc72c12e2b2\n", "ac85aca1c59522922b8b3830dcfa9d3c4a95fab0b2f2dcf7c745e2ca101e25c6\n", "88f619859e369ee31bff41b30e115dfa9824b25d72ee56ecfa9b0580e35c6397\n", "bb432801eaceb1d597e57b85d56da207c999b9059a3bc61eec025a23c1f20e31\n", "960c03970c14f753d046eeb9bab9f9f4a91f0ef44480953e5c3fc75ee2336da5\n", "9895401412a910d1af711023e3df3ed4fe2a09b26febbf167d588913001a222e\n", "8e2639deebb416ece476fa7595ca93c65be755c4eafe63c897778e702bfc301d\n", "5ff90d1793f98d7eaec837f4d65267835acb861294c32538f381a61327c3c1b1\n", "0d2fd5ba3bcb6c2aec500ae41e56bb60329d38f871ecc193e682325ceaf4c8db\n", "3a136308149a18a1d3f1a2d6710b362312b9b8719f437579f79857a5c4fcdccf\n", "94f973c061793197e5c7874cf8af0c0f92032c4f429990c7826622e457d72bda\n", "4b4be962614560bbba67f3e525be9d6a247e87e9914dca0f1c1bd7659c05296b\n", "982e1f814cedd02a7a3b71848b5ff581ad6b810c19e19fa228a780c0ba43f421\n", "ed6140f66e9cea33adb9ba6c3273e297c815114b84a404b37357c40f503f5d63\n", "9c83878f651e74f89d552226ebc53c2f1352cf5bc26a946118a24665423250b2\n", "a593c4e724b022d6a3a795356d069e0c24d02332c3fbbd27b7daf982ca03ded0\n", "756f093d9f56315975a449feecd9da123a6fa9c78090257a4b96ef0508c10382\n", "1a6f58d953ffe23be0f5718f826a84c54e923e6fd9733b03fc8f041f30621279\n", "8a68c2806adcd4a07b4f6b2056997f2d35c3d4573159120bb226552372ccbdc9\n", "dfc5cd4260bf4108984e86d55387ed8f733ff8f8ae5eee1e2f21dc3b01bd401d\n", "5bd99161cc2b21e11b05cb0df95677ef5de4112ebea7bb64aef78fdac16bfa2c\n", "f127ecde4f7187f8704c42cfad8b58da69b87461d47ec936479b8ffc0d9fe194\n", "7fb4fcabec2d33011d2ff6c0f686f0c089c199ae4d2b07e613c4798b2b4eb5a3\n", "ecf21636a56593ddeaf1cab07fb0fe1d1461e75fc16dee43d53e58d9028bfe33\n", "ff310309d1c6eb2349bfc7af8e3de43ff6efd2995cde8a038f108505802a44b8\n", "5f16c05354d18730fcd42c4bdb28124772576aaf63fe6230d1657421dec5edf6\n", "96bf4ee4f36918d401975819931c00a93168b7ed72a7ca60cf4fa9d004b1bbb7\n", "67d6e46765c82a873d8256d90b2f61ff0bc952451e89b17fa0ca2feb489f8d1b\n", "3e0b13104e93c9cfb0ac7010be88502393b16ee9b1c68b44cd3f82480e87c615\n", "9b1b7dd5d15ded1f4bcd6633517db4d0dee2a81efa44f7499f8626090fd783f4\n", "f14a597f3fdce037326eb48e409dff6322bc10bb99702a9a1f4ed57025a28951\n", "61c732beefcafc4a335653be5560b7c907136f657ccdbe14221443508ab2091e\n", "fe9263d106aea8ad60994b5fccea3385982a35f6a27459f115741bf4fa71c5f5\n", "36c3d4aa44a094187c983b4f32463f9526df7f198a7c683b07f201f57f90736b\n", "4ad242c94e59c15f9782d1219c9ad919b40dafea709dea21bf4df90c6841ec5c\n", "2c84cc1b5c6bbdd8c9b706e99425d58eab4d8cd6101f6d0ce41ac0528316d467\n", "a7638a5963e89f34814fde752d77c19469430feef6097a0a76b08a94fb71baa3\n", "ef4f0aca861845c558f6a72ae9ef51a357f52d7482c46bfbb3019cd1917262e0\n", "0e9db5621ec7e318ac51ac0f101f2da6edbf98195f9ca63d5387efd8c7f2854c\n", "e02db33850c9753827d95ca6d98c3589cf846adc9e26142e9e5ff02c7383e7cd\n", "dcf6016f3c352c396505014115648721303c34b3fbd83c3c1c56b441e2cf1b75\n", "05fbb34bb1061dbd6d2420a11d7d24db201abbae6e96e2877968d6cfab66d0f0\n", "f61e4fc77c1642ebe7f8e518d0194206d04382a59db4645642a8cddaed0902aa\n", "fd2b6018dd062d05ae0f3cb08d4c46e2c6c659b285cd7a6aa89cedebc196a39f\n", "b9aaf34f7c36f42598a141c3d50d140d2700bf1dfc65fb41292e00a98a78a9e1\n", "fcc29eb16b210bf4d6ad641a9838fb3abb2cf848be9c83b0d6053f77efa51eab\n", "ced6d83419d8327cc8e1e42576f3f3f7a46aec41e54f9422881d72cfb86dff82\n", "0465432fb20d6874013ae805cf4edb3a51c69de79e37cc81219c520718756016\n", "336b06114249b1fd063eb70962ec80288cd26e5b9ef345bf5c06fff55161de0b\n", "1b163b212c0cc0107b3786de9ca03dd86a179d65516b1c8990fa75d484257347\n", "9949be1534f24adcea98880ade4cae8fa2a1a545a21ffc782b982297f1509625\n", "47ccd45a9d7dffe162cfa9add438fe1660f7c8fac061191580565edb474c2c9c\n", "881926bdc46692493e570e0423b67cbc1243c9ba7fc59f1413285ff315aa16e3\n", "75053c08fda311a4aeae6b9e1aff44ae11d0ac02f5e0bac542055e8ce19d830b\n", "74678dd27051b04f4927a1f2a674f70f42129cc60aa359eeba27b8b94beb06aa\n", "a0068640b7647666bf88811e22df4e6edde7cbc421a5600a78ba7e46beeb9bce\n", "93eaa8798870280c854ead571f7ba9dacfe04274ab246262211f18ce873e1a04\n", "da627ab1831148112a3ac6fb844af9842e604b416c11a9ae6619735f0b7883fa\n", "15fcd0913760745948c406b68186024cd1af6c631060ee690c9a8735ab5f0f09\n", "2a95444a88a9c8b985155b988a3750dbbcc2e44c13112f82038d7f9133c0c0ab\n", "ccf8fc631c4fdcadb6bd43709b276d7c946dfb079a95c7b06e164b1be62925e3\n", "82c53fbdef44dfe74f57c451fbb7f4667199da36ea49ce1c746b57074071aecd\n", "c515d72c2fe8b851f355013958dc08c7fab33ca021c30c49c00616fe7e47ddc5\n", "1d31fcd1f1d5e0645c8c45cf0091c8d07e7a597d6c5173ff11f271fbb4b6efd7\n", "1111ec8a22dc6259a13b5210f1e409a21065161ae45ce3d8d227b9e2d0a90a2f\n", "c41e34b4e77ed3ade44fdb044934ce8b77aea01d1a3a9c2f3ce22264ce91b502\n", "ed502663ad1c31be1b713e11ffffccb3d464fddf466d4958766d327ba26e8ae8\n", "a95f3a8bccaa811fdb6b48c0f77c139d5f26181e5e57c0413ef5820d16d9c90d\n", "5b039cc3f30f35bd27d93a38bec458314c0c59cd1445bcf281aa4f4799b9224d\n", "c727d60caef0a308c18ae6b5185b50e36f6a72fcff9537dba318ffdfc875fa5a\n", "9e4941d4e69b03b5dbc3752134c02535d32ad052ce5f6a94ad7d2da5cabb7e4d\n", "b8201e1f0ee2ecae0535b13164688dd60096835e7ab36f10c8dd60d4fb56275d\n", "116be90b0732a774d5afb4828c42911a7f7b2c684cebe4ab4f0897fec6eab945\n", "67023242dd301b18ff9a540d1effa54c0cb950689607ffe9af0d8c0d6d1f60f6\n", "7c7e4c4e1fb3fcee75d4c7acbe8e05a899250744ec7b15db0b032205670f59d6\n", "2205786720056ea41eba5ac9731162a6a645b5686d4f67ec9f1b27e6b53184c9\n", "3ccd3671ec51bb5a3a4759482ea2ae81d3c2206db0f297d793c1135dccc31bdc\n", "52a30372abfbf875d495f52c7ec8ed642f1f096eb3864bf5f0e28f4d3ca2530e\n", "0294e4f44794f79a77a6779007be3a6ec1d9cecfb1702d086e67b5a3b805619c\n", "2179b73a87c6b06fb6440bcf2893cb93b32dde0ceddc04059756b54fb5c535b8\n", "ca7ea7031c214d334660ecb2fbcecb15372b0e0a92dbdda5b07c28c258abaa85\n", "04dfd185142f79a45db06fa65e782f4b8321312266df9a31fa62d36cad12a6de\n", "7b56d132ba62c23694d8207b56216b72a18958ed3f2622fc66ce5bf2624a7b3b\n", "fc2e088602a27e986c130d17e653787d17ca32b01e09adf3e95509c2795ed897\n", "0aefb61732fcbe47b9bf4a2626f4d0d135e914d55ab277217c4ce0798e159139\n", "feb8070272f4419e31ee5c9069ca53cc662429738e31fdd96390f2fdd7d42145\n", "73f6dc570fe238193281e49de434f7ae39fd888fd18fed5ba735012b4030939a\n", "30ec00d71dac994c99be4f47fec164d1134b43a142c41758267dee35fceccc68\n", "9926a5bd124b511a1c229ef8c5655bc42d34e332ab34893a2f08355e5d32d925\n", "fd14f18f9fc4d7221032676336cacb9f307c1c260c9a61cba65d02488ec45f18\n", "0415e29d9a8ad44c14e720315170e1c2d8cf6cecadc81428141b61c547f13dd5\n", "683114e3bc55a18e4cac6fed9afa03be06a01923db7d4e8d63c8ecdac2a459b1\n", "e2c5cf63ceaa7dd5841b8b0186f071557b2abe23bf7acdd814924695a5fcd513\n", "5e52630c6dcd4c1031bd50f6631da374e4a620170a44094e10607a9dc973319c\n", "4730e541e6599c08a8dc59b5cd0e3b38b9525a9d4e6337382bfc572c41a75e38\n", "7ebb920aff710a7511e0f1eeedb9977b97a39333a0f2ccd5706ee91f836954b2\n", "df0dbe7d099e8fe67da2cbc3f55dfc6bb6733db98185e3fdf6bbdacb17940016\n", "ce245180ffba7efd3a9ba28126d79c301c40b52c6df5b7a8f1dccd97f73407cc\n", "dfe924ce95c1d6b3ac8dc609fd0c43046ebc3366daf6973353c3357fb3f20a2c\n", "f3d797648700d4e9d8a7cb7ae61241471fae7d3e65722571a5d941e39c919b83\n", "299d2c15722aef799b0b234ffcb062ede9034042d33e90d2faf6805a7a9ff4f7\n", "f4ee486230bf087b5909fd87f3b74cc6aebf3eb420c6fdf82f6ea04810a95a95\n", "cce0cc4856378e2220bd8dfa7f87c4d6895761a159a1d4b3f23f261fb413b0d9\n", "cf4e402cb44a27c44e131e45e40e3b85177b10ba4d40b3ca8141aa180aa32c7f\n", "83e19f1016c785ddf497aa18e05ccd1e76fa227815fedeb98bcf6067467c1f53\n", "9384a743c42e0ce71bf6402450165ef8369a1d1ba76191a291120cb22694145a\n", "16376f56944da8ab84e5114ddb3cd5301c9133222eb3811fdbb6b3b268a1f861\n", "a9436c8831ab05d869985411a4a78c078e157638ea467b62f8d8f397bc3218a4\n", "a3155caa04493cd3977db7bc07ac92abfb4645cd2b4c7e627dfe9eb535367d96\n", "42a395f0a0a525320aa412a309234349ae86c943d90157d797b162a91b93e5f1\n", "6fb302e91d4ff42f8c67d06733399ba5d63e8be4455ba8390a20a55548fce81b\n", "90641bdd7f48167cf93ba482e55deab32f9c5ad99310fb45567fef8efe11dc44\n", "0783a6803ba9db566c5c243fc9d6f1acfe7e5139dd56dd1ba2f957c0a486105a\n", "67ed50389fd3f4710df9d85fba74479bbeae25615a2d2ed7f5d0586eefc4889f\n", "16aaa531202ed50b3ec7d2790e5335ad0a453b7181156bd1cb057ee25cb4123c\n", "a2b2954031778459db475444cef4e32cdf3ad0a19c27be95758d5b6e2e64f5e9\n", "c8d2f5955bd1b2f1604f70b45e1ab7f6704782274a4c89b9df5e5872bce3b226\n", "bdc61f6cc818795248c0cea460ee17011b589dacdf856f194f2a852e484bc8ea\n", "e291a21dccd3c4b0c6900069d0a86dc23b8b4669f56922ed17b3bbf26d184237\n", "bad5fa783edf1f04f413c8886f55990a9d73c5e12708cb79a18ef4468579b828\n", "2f76ce7304b635a23e4c5eb9b52bfe6b1f6d8f43a7264fe57e2a387b4cc0c200\n", "29cdc8e54c3e48c10cce9e0f647e4e744209b22debbe348898f57e4ee5393e5f\n", "7a59bf4747f91640d138a26d3c22b057d443f6b4fb730ce35f2b2602fd9d5435\n", "1645360b7e2a5bb81f97d5799c82921f781019afca158894ec42a266a855780b\n", "f9d59a2848109dc23451027036ad445e8eb19cb03a09ca990f2517981c37f3ec\n", "663715cefc6dac906dd26ffb8db2608f1902115b6eb94fbafbda040690d75a3e\n", "5bc57ea87d39b1de596d9eb18cb7531160254d1521f92890fb133301f59090f0\n", "b800688c4731fb1b98f7e5de07bd75bc4ec8493a791c4a45c42114af87d1ed69\n", "133b8800e5d9734b8bc19e96c3a852a06c93f72053c9f19da42532fab192a84f\n", "00d52fa59d8155f8df753c7c8796c7b11ddb80d295e08399d4e1db29473d3e37\n", "3ca7e07b950e1c58a051e439f5a8666c3c4388fd1587634b6d2775ed9f42654b\n", "ba7777a6360ac0993a399ebacedbc725105ddf418b7b684e78e3e989a56295a1\n", "afa7d679c0fd097dfcb3908c938036d632c4a9024fe758887a1029ae435ca230\n", "64a166e4331afb3c932bc9c6decbca79dc250ee4b97a0efa901e91070192a4ab\n", "bc921fe4ae41899e2de0d8ab2101645a8f7bc20580596c4dfa3c5d09fd8d7dec\n", "6965527eb421efc7aaaaf00c2a6f580921f44339ef5d26e4a61be65286cb5a7c\n", "ca916650cc092e348c90a159183122c8461218a22cd9d7f1a6e0f20a7b9b94e9\n", "e9c37f70724cfcabc2e75c7739b1bf2c17773ed6d425461d7c8c7653c4468d21\n", "94ca6709ee19c115bb9e37cb76c9ea8e01027ed0e0d4fcacf24ffd85a916cfc7\n", "e2198f859c37aaabe5f4d0c7dd953f827f8af232457a75ef12bddace5f83c96a\n", "19b948412f8b770ca8bca343283257de650b4e114fd988e48b5c8ee8513cb962\n", "6e0fc166c2435f092cdd10d1fa9ef782a2ba12dbee7184cd333eadbebddd2c2a\n", "8915d195d1c48d8890293e9ff5635ec6c69000ea3f6d1f85178f1af159a19bad\n", "463e33910391988ea543799970a449a73e227962e00d57f5ac6aad260c866fcf\n", "2b9d47f80dd2d585e823cfd1a18a2d90dc1d987f2d630141eb86c033fcb6e0e9\n", "391516f87c9feb98fc2d7c6f7723bc04860ea5d6adc28209c856c6d6f8fd8915\n", "90e6dabd189cbc31a9c4e3ebdf6bea431849a5c8a998c3be295d6831881e548c\n", "cd64cc6f54da82dda2af5f9a123acf057d0011211de57aff12eb42f75e05222f\n", "0b9e876ec399471da25c86cb21061c62b0b0936ba7bb1de5d0463d8d59e6b09c\n", "df9fd16cafa81881223056b91687d63e399dc6788c590c5a0f393f4fa4ed71bc\n", "daaf780f5e70fd49e0c24dd45af179443a1ea85319f96d3436d8b17689919c9b\n", "266308394cd2deabec1234bcc08a5ac42945a9f5a0d5031aa79b91c32fb5be5d\n", "1b88e84dc69fa17352b9d168ac200a12b2c75f879fa2c083520da722c89b59f0\n", "43a48c76f3b6ebe136276acad45a9f42105c0da64680868fa86582424299b155\n", "e002bc76dc13fe5d1548d137ea0a4552c94e95ed2480d8f8a621e62a32ca90fd\n", "3fe0b92d1297daadba653e40734ef27966978c6b38079487ff677cf53886e49c\n", "0bebf99e54cc5bb9492da91981f9ba3f5b0c5413ee3fc3bcf46c4663b56479e5\n", "978bf774c7bc1187da380c705b1d8347131a5493374b3357efbc087d61d72402\n", "283c56321737b4d9d89524bdc2894eaa480467ae45fc640c10367a842cdd2a8c\n", "0d44405c3b8a44118b3aff5d37fef1d861787be8fcfaa4f2c9df01b111994799\n", "bc1cad8f519f5c5e898a08654898961efabec26513bc18ded991a0a86d311886\n", "7f4113c6dd3b700f78d00d46ecb3e80b399695c1671f7f2ce75ebf56932e1280\n", "58e81d6664fdc1dea14cbd05df4aa3abe39f75f35100df5b7590bcb089937ae7\n", "d3c7e40ef541235b05dafbc7829231fa827c898616c1415578cd9e866e763304\n", "e644f3b7bfe68e7bfc1bfdeff39f8a285ac173ae8c1a37b6ade07bae4796e6c4\n", "e231e62bb91f991a6438e935b84e92d008fd0e5f76cd0f6ff56f7884dc54ec50\n", "a9a13a33e5ef32c9c423cda289f65b337b969c853bb719f29d1cf6e6df6318b9\n", "972d25fed3bd77ff2669087994cb57f5d5a8046dbf396050ae31d1e9a0492095\n", "e147d546fc9498f8ace9162fd67cb2c95871636fbc3fddc13e317802617a6fab\n", "835748692c49510365a8f2cdb6e3bc3cd7ae739360f98f2f117a3ad688f2bbdb\n", "2b2f90549766a280f65e7ba13d2003e545697dae998c924fa62b8e9627d07bbc\n", "9960c10fb5a78a2f586f8061d12ceadbaee8928920fe2fee9e669d6b1e199aa4\n", "acb75341760eb99856b9d72f24459119e0261a2369c1f6ab5ec494f8202f5f14\n", "1358454339ab86632ef47188c8063822ddbd71c60beb8b5879b4bb79e2c58030\n", "338ea003af837428df1776b2960c37c04350b2d34acbc7cc2f9e22fb9f870174\n", "f4d1bf46bda6415fb1f13685a72cebd59441ade4272ef3599d893c8a1570972e\n", "8ee289f32b1817faa07d2de20bd8f440e7a6939262229318d465b5264dd0122e\n", "5cf84145b7305bdc2f1d1ad2974a7363843ae7a1a06c9cade2689a3650be9e5f\n", "f449b366da6a7324014be3e2ce56630cc75a6c6226f17e5e56a56d70eac06a9f\n", "4b4ca007fc9432731a57b9479c52cc0b35d3329e4e19eeb3b62309d1b5015b4f\n", "8315a15249ad9666f828fb74f5a2c52d3c92ce421ccfb2bcf0479f2610301fa4\n", "98773a52751020efaea4b6425f3f20210f54fa91e1a178f448d10b4fc865f824\n", "227706a116dbcae3796e5548e21b634eb3836356bb8d6812344e2b4ffab3dc20\n", "4d9c1d35f37ce0e749fc8192ab11b08b63ca3179126426daa238f7f264ae3167\n", "a3a42eab3e15bb61ebd2d0c503fab2234596c4e854065ec4169a533a8343726c\n", "a302e1f324d9a09477e1ccac048567b0fc5e290bef8384417e751aa68efa6d4b\n", "ffb0f0cfbd29f39fa8a075fa907236d602e20cd438818ffd0403673e5c628fe6\n", "d2f966368b1a20dbd6b6c7c4b45e50907e227a2e9530738e50b16100bf90f050\n", "2bf089384c40b806113a7f3ffa1e978647eb10b11512db4c5a53a9815e244b43\n", "5157f8e6a0d797d5d843c75b264d5f4911eaba3330cdbb2e164e6ae38f369a3e\n", "b163160ec04de3533070309c0c908734cc58bbd998199c2fa39361375ba1a201\n", "4b5c0eb80cf0216e999dcb2bb10851a2ea4ea2a9417b257d76278ff4f2ade036\n", "1a07663666b781027650945a5fd5cdf562c5b34a31f18e2a0556e34dbdfaecf3\n", "ac7a5a94efcb81424576339ae99037a63481f1c77eb74ad8005cfb364f9fb5c0\n", "45a3048d58805d34d5f472d8a824fec60a3de77c3c8381660adbcd1efd80d18f\n", "eb39d1d15317493d0796df581f1bad405127bb8546c9c43a98a6483a5fd23a43\n", "275108c045e0bf89c07f58b4f63ae3542cd12e27e40bf2d3023bc30d24c7a88b\n", "868a8123066c60c74f6476d3afe4b1c46dc0d5edeb661e365e3489429c533fb0\n", "e6960300e4a46e55cd22ef10e388157cf9573f1c85f7de2976983ab38ab91033\n", "8ce5fa0dfc1624714ca75d3bce6da14a0c3a818b1d0c2581f54cddda291cccd6\n", "b437637f6823c06f5e4d93864096192e1a05bcd9e873051c738a7a1f52c04f0d\n", "c665064643009ae6d9c93911ee95ae567fdb8d9aa62190930b36c0995fba8c1a\n", "2c749553ed7f382cd15406b4d228bf20c89c4565a8cd98018ac6a2471378c027\n", "4d764c4b767fa9b0d59956eb0a20456dbb5413c622a0d0f46ae1a70006b36cde\n", "dbf4702cc9980df7cc2c559e3c065788fb0f270052c35c3668a8d4a5a895691a\n", "e8e9e69c057ba828bcf8428b5e5fa6a29dd34d8c04091fb466fc353c3e1d0600\n", "462058add371e36ed1e6d406fd9aca6b288908c3e36e46c557297fb8b503620e\n", "9276cd908547bab0bff8122fd3704857d21ae3bb4b87626dad4dc191d50bd144\n", "6b1e2d9a4a280d92a31c5b7be718cb240a1df24147ec27095d41d06c1bcbd1c8\n", "143430932560543b77bcd038a9725024f56af1809be51e99d5cad3c33f4f608a\n", "45fbdc6db805bc3907f431b151638edaa245ef0a10c2e714575e14615951b099\n", "a65844e8ae6126102c333d8114151a6d6eb8dd92a1e7e97811617857f4e3dca2\n", "801fdc61533e6c0e5a62b81c7ea9f2f6bb0506daebc840ffb62ddc9aaab2f5b4\n", "57940968b29b437d2ceab8e987ebe36965f640e1bccdc1548234ed7b60dcd583\n", "1badb14aa15069989afab1b0c0bf7554f26e8be11546d448b0cbb8b1420916d5\n", "135369e41146167fefeeb03f3613beceec475f5f370bfa5fe2ffaf12b5258e04\n", "f36eef02c55e84f975c73314b85772d99ac27852488ac064106eb55b6ec70a00\n", "742ba777a307164bfe1f7b2abc320f3348b1da354f4415693fb15406ed7d22d7\n", "5fa6c065bf1fcd1e19b6e856586006695fb9f84e519a46bbbce3fc7d9220d93e\n", "b20262dc4b175b752b55439919462c3bf12e246337c3d9f1e73a460e28c690af\n", "23be0667174440a4824a337c3f04037eabcf044e18271d88c742bff152a76e27\n", "f601f9a7628cde28d48eb8c9c40005ae200a69c406b73ceb429e1ff4e71c7c11\n", "107e5b2805aa092d802e4c24fd063f2cac9e96ba809e188bc9b0ad5e3773de16\n", "f2013145abb2a6bef0debd8bdb438ea91a557eac289357304e2ef859878a805a\n", "96c5f1287f7f2a373725c3bf704ab94d0319bd81eb31831de3089a9add28d015\n", "ac4e98433154ac3e0dda979a55317366f73f00501952b6d38bf6c00f8f450a3c\n", "95fd8d2fbcc971eb6c18a844e29003a47b4d77571ffa45542046ee2a87a255a6\n", "15715186d3098cf8b3748ba05523181daf865b6e28b6e842122f6671da4ff34e\n", "f98418569f67c865e2448752957812c71e53a950946e613d71cc0831ec35a656\n", "a6c8f7e684a11063fe81cb62f10f34cda44025bff6e36a7227576b4711563d42\n", "7a30ced91db71dc11f079c70745464ea522bdeddac1e0fb992948fd1961a12e0\n", "a8315a2fbec40f01d3e18e5fcfd6fe638f8c21ad1d13d18275cdadd8a05e9510\n", "f4a2cf161c6054ef3c9b3e7581c25b6b93322163c97feb70d6624cb0e6303413\n", "14785ddfc745ad7d114afc709b00561992ea91dc03af31a10bc139a709303707\n", "adce975283960dda722f7d6a214b96e5425db3ad9229d1f9170339df3a8b44b4\n", "b67d99122de293949eb2eedb5f8d97bf572c5a2cf2cb7046772c7fa05c6bb316\n", "0f1f1c372f08fefe8a3f18f9d6356fb8e4309a386ee4d2fbe05fa39846a74155\n", "b29982a87f10873a6d8c41069330a280b693449f3dccdeca248265ee8d26cb1f\n", "772ddfdc643d5175e7918bcbba4040c29700808f9d2095e72a8b344612c76707\n", "ff41449b6ae8c71213b4cc2b8138a09c786b1915effd6b1de6ce8e5d38a5d16a\n", "52c586a82d02d0be6df62e8f4a610373303d080da0f428d4ee62bf7ada52eaa2\n", "b0a75036ac75dcc4846ce1c4c63929c4ed62762413f9d259b27bd664c30d35b1\n", "03d731d9b37e90c259dbbec56258eac9860da921a5e50b1d59578c8df70143b4\n", "51bd17db570ab9ac28a45b0629a83de51ff65f94c01c1d50514226c4ba2e9403\n", "1055da8975b6910cca9a55e94b4c2178c60d281ee86947a509f9f4a007d5b3ea\n", "1ae0e1f93a1008543751a71d23f1dfd6434612e74fd7dfc2d6afae2e51211d28\n", "c850a56e177c5725fe72d9b6aaff0e41c6bc88d1d31b1f1d4971255eaed3f859\n", "7bf1900cbc4f87144e84564b18244ee14a5bb35460ea3e87b9b66cea93186b78\n", "947de89e4e47894831916d8e8166e34d320d73abbe97b8a3ffaf34e707c1c614\n", "a033a9b2a9981b906b6410d43ce7172ba4b44f0e7721ecebefcff276b2ded2e3\n", "8b16ea80f4a289e255eb822846c0efda56793efd9ddf3b9d7ac8c84c1f9f6c7d\n", "cd2130dfd26c9de74bde8caea15f91c911a2d48500573ba759e5cb69036e93e7\n", "83119e2a8b6e0d0821a5ceb1e914ed1126a3704efafef8fcda2ae819504be4ca\n", "fb84aeca8c8e1cd4e186e7351bae8e6837663e77b42a7d67fa517204d51f4db2\n", "b356cf730c4256eff22fe8168a97e387dd83dbed95f86b6be0fd9c2c8377dc19\n", "5c7afc4684708d84a6cfb0024f263378621ba930d2f11e23941a8cfdc3b77477\n", "7c1ac52a708ebfe5a20eaf1c705b0d9e96ee7cd8e40e201908aa70da2c68dede\n", "1c3e0c441b6df4ee11297db11dbb18352b346a182a492c8f332870103aa666eb\n", "52f7d35182f6a7808105f9c21b6c36663577e13387d187b1cb657105aa90301a\n", "28ba4d14e7069227f4eb71230f7190e13b45168b6252a2ff57d916fdeaca4940\n", "c57b4c5d06444c3b9eec1beffd803eee4827d633febad49e2d9eb50d710f9730\n", "c63f93ee8dc67f79a9767b3dc34d06b2361d31e6197c7589e2c22483d3c74c8c\n", "91b84c1755cb96c711febfba560ba8e026485139cf23158118fbdb834836d8ec\n", "6f930255a4801e921c878f6322558b463e08dbaab2b8c39fbc2dc4fbfab06fd0\n", "60799f0ddf88679b1752cbe97eca18f4e95de9f9e12bea03849e2f0bdaef0757\n", "270023d40260fde7c5ef00824dd7ba13f0e4162d02fe7711b714f026f21458b0\n", "6c107d6075eb037275c763cdf9cf3556c48914c80c79dc71acb99e11a3075655\n", "37a47bd775c61921e02925fe3059370247abb7d258453f5776d764f878bf0d39\n", "4d8ffd5956d9e225bee7532972571dabf8f5a02528158fa3aca4d43f4289fbec\n", "01a13c4e2a2c53e00956e5dd45b380efd6e6480c4724de9398c36ab3aff12245\n", "0b2546070b9f672dd8e6e45bf0d1ac2766589767d012b98d25d680f32ae50185\n", "442376a89ae94325ad18e66ccc28a9fdf6f5b834a138b79956875d69cad7008c\n", "9e5cdad5d23e48fbdb6a045ef39d2c7c8890636cdefd30ebc6ea07ebf76a41e8\n", "bbf6aac0a5d162a1308e88a0e42ae729527724565d9f4e2114cbe3d31a96f776\n", "f6eb03431abc3dcbf547f475345d7383918f3dce3210d62b888917bf673fe250\n", "fe69da55f914bf46fb641eb269387be3efde450732aeb7d89c89f9b87d0b402d\n", "6d8ac5bedcc182b35d2bed8cb1810dfe89f90aeb62808b7b06ea480f777a6918\n", "89620278ffae7e2857dd76eed74c11124a3b409d5d3d8245457b994b0bb846eb\n", "0d86f99e8d6ebf66746cda135dfe977194b12d82e52775c6892dbda258c129aa\n", "82e107e907922de0f5892337900ae3691d04754a144c65e7942c97ef4db623d7\n", "d0ea4538779bb1aea0fc9a86b3aec30536e0a3161bf8abbe89a90030f017c8b1\n", "cd9ecd63b79c79d378b3987d98d11cff3030d48634cf41aadbcb0c856d7e4d24\n", "71d9df922dd88b9a515c1eb63b27a681fec6da4e4e03fae19752becef8126f17\n", "547a92ae482f58808aa83a8a9cd5cfe7c719c9a3d50b1f634881642551441e87\n", "8af01c705803764593d9e025a069274acaa7537461ca495b69d904911d9995c0\n", "71f43b063192f48741c796c883abc9f4c21872ab162286de4905ce696e3f52ae\n", "f2641dfc0eb9289b8a52dfa880cf26327571ab3b45c91a9f926888d3bc4a8896\n", "364d8d2ce1d0fe4365bd54cc35841aa321dca363b2d6d530d463492822054313\n", "0b47f53437331ec8a9e0fb7128bf39407097c4b8c76bdefdc4512f48cf58a6e6\n", "112f30e9053c11f9f057efd8b25ff09f131fe3f26b71519b87d64bb94c53ecbf\n", "9ef065275a4132395b6f3c07a9e09bc951f5d11ee7f235c8a579ee1266a5bf1b\n", "acb3e80b514367fcf5aad087331284ddb90b93c45e8b50a930fcd0e9dfe1ae07\n", "b71fc47e5c28ac801479e9199c785578c1eeaf9bec1769cb3996d7ca51514291\n", "988ccc7fa9183e4f2265b231aa370abb1da4de8522b87c0aafd081d1096d8024\n", "f28b0a32ba68f1f6f43011bf6385f068d8fc22b8e0a861a800cce8f6cfb629a5\n", "bcbaed0aaf26eb8e37a22690f04f34114816d7f1daae0eb37162430ddc93f21c\n", "aa495f9a99c0b942d8d00c4395b0670fdf40c706a58391f221242af4127aa87f\n", "66e933a13118d4e69bd32cd57d19f5d7e1680be583831820e3a9f926ed151150\n", "378294b798a1153485996da3ad533e693c37800066259f7b600504224d98cbdb\n", "a9bae7a3ded8b62184c0ff8029c0d85a5f4699ebc1fee4e1b217464d080c31a3\n", "c88abdaae87d3bcc4770d770ffd07a88553e5de0389c490d60f82142b70c28e2\n", "b237746bdd80f1f7eff054231a5e49b8d209a84a6572cd67d5823e0d05ed39cc\n", "39dcf4c534cbd9c0ec754e4e9f5b3d16d5113fe06f3e8a35cfb5bc873f61103b\n", "45e1c35326ea4a93a878ae84aebbbf0e88f6b9bf8469da503dea1ebec6e779d3\n", "cc4c6b30291fed1f29be0a8b35c55838d580b03a72a620c896799649a430357c\n", "965578b3447c84907c8cd2b73a9a13fe89adac25f17933255989b66aacee0ce6\n", "461a39632da3f0a7a9fdcabc620e6d574f61fb7a816646dc4b4c2d2021ed9831\n", "ab0b6bc52c4d87a50aadc8094a8f2439781d53ddaa2ada0eba52ab6d785d7cbf\n", "2f96a505377362acde325412c70c4e830bf1aafc7228df3fd280db25906c81b8\n", "6edeaccabe94460770099d1236405c115c782700d4e450c0e3330fbac10c41e5\n", "7db436a457424f068376bad82c6aec4740e89ddd59dccfc194ec1dbffda2ecf4\n", "ab706904952a910e1a086253c8a8b6fcbe0eab356bf9a7817c791b80c4b5b4c2\n", "a64fada3553a68e7639a35c5fe413e2d05a7bc9df3b09b01d751f270f693de19\n", "f31ab54d013674ee56c96e6ba844600744ec1c04141a028a660fe76ca6dab8ba\n", "856c93f2443a4265fb475a3d8e58eecfc8b744830d04a85ba64b49d7cfab66ac\n", "050741449eb1258420d870a2551355f31736bcea795d8d14bce0d074a833c970\n", "898bc38f21cb2ba3ebd94f03a20098636c791bb96429b88a914eb955d03d7742\n", "b48af4ecced0f171166bf5323017f99b59ec4da3df04f3582b5b4e4b19338764\n", "06c56b049863690adb8310e585065764d8fd1f97a84952f710cedfb3edd1c625\n", "302acac463655c3b40d87d5546ba82419b553b75eaa089245fe55a83b915b98a\n", "e5fbb08a01317d212f6287fdeee3a4f0a96a550eec8ee7db3c3073d019ff98fc\n", "e0ba5947609d2bb10ecae62488a03ba31faa75d5d3ae11894f5d274495f8f453\n", "fbfb5023b5c1e9dbe6dd13c9fcdd82c29d6a5cf9411e740941819505ca8cb670\n", "4d9d75bddc7c65ce8d1aae105d9baf8f54d12de79739fde2d7b7e2e14a722eb0\n", "fe54cff50c95d2fb0e5d2c94f17a6a213666f7fe7c200e876646e0f01ff39701\n", "9776c09033d9bf478c22297909c99318c04c391a1e0c98c434fcf1cf4cab1c64\n", "b04fea5094417674ebfbc62db02247fac5cc8725d0abc1e83855c796458ae459\n", "db560c58a19c899f2f68d128139a617d859cc96ba4ed2c9d4fc8df40979a0bd2\n", "8783ae9e0b4f51de894f2686ec934172d708de3acc58130ad0e782a672ca6c27\n", "e0577d488b175ed4278a0450873ebfd015be9e862535a76f92e0d899418012eb\n", "e1e31504b4ae37c3187b5dbb7207fc495af7888d91b77359b79474daa7562a85\n", "36b9b6a433bf52ec2d128251683c800a1537158b16cf89d9b2930afbd813bae4\n", "3893159e7b69252e1180b6939390cc8571b977f1dbe4b95e6c98fef8785f563f\n", "fab2b18e85a870a93b416751db73458bda9f31f188631b33933217a5bb2fec56\n", "15793f1ddc4dce8bf3583820fb85043e8cf6eee2252f8b21a2c1afac3ed78473\n", "74a66b8959e9da461f5ea8f964a886a453d90855df6b769e2e6ca79f33ad31de\n", "21d20f1943df35ca5b047dc4c429913cd5ec45378bdc8f0ad7ec755d4665224f\n", "cad030770c7b763e8134c3cb3d48285ac4edeca95de12ca6eb6acb5d90ef5ee5\n", "fe97307b34cd8018b8b4fa9829ec4d6d976beade5ed877db48a3a4282181ee7f\n", "29a790bf9133bea6e5a594b0f9a5b286d66ae5f9578d36a2805abc3bdd397f8b\n", "cb74bda8dc0af877e43d62701450742e1fc3bb40998a7ce0420fcfeb48f436cd\n", "98d001c49bf88841f5b38723b027670cd8a8160ed36101df4469e1b8a152055a\n", "ba244f27ae3ec6c6bfb1b645b79d502edf4ad646d426419fcaa445f7ab7525b0\n", "a008d00d3cf7a1997cb081fd0574185e2ace04363a14817a64b000e9e5e0cbb9\n", "3c2da910a8a2438e2de168897a4940bb5a46af7a4eca6cef2ce50cb0e0a6ef6b\n", "a34f20d0e43883a713b52a0c11053ce40c86e77237853f1c81272983b1c32432\n", "485155f9b3d2db7312b58316ae0f329e5dc6b8078c7e554edbf7b0ce487cf055\n", "5ef2e9aeb725640978dc9e0746f3ac52ec5ded5a1d406cc2d60835081d9b7546\n", "04bc937a607c1b442450e37ece5e9114597c3c4053db1e519ac33d9a4c0de25e\n", "72620a01596f08d997b90f06e9429b0564123bec0b83c4656234e6b639523e34\n", "e17145a7acf24e5afdcbc27b8b27a7e450276960a34dfaa7aac905d28c1b75ac\n", "6032b625d05b341b1ea9a386369bd863bc3b1f975907a71fb455abff85660021\n", "33ef95d889dde30c7cd7e5857235f1862560b753cd978ca4cf80b61524827f38\n", "70934b2357ace391b3a0d93f7e76a2f4e6f6290c61256d786393a8d7b3aea484\n", "1f7d5c0cbfe24b6cb5bfd36b89ef760a83fdb1ccf5fa6554de9d73b327f4117c\n", "d35efd0676787576a31eb4974b7cba423c694cefea54d6d0361c454f7c9e5936\n", "1920856827c327e707b4814ad661b114aef7f13895b746371647274d20f73922\n", "693a29f2a4eee66ff74015599f745f998b61e726af6fe46cce2955c18a0f875a\n", "c73f90a19661b35c8e9cb823b4a2c80e9ae27bd60002cf64812b79a73d8b71b9\n", "67c1b92ef0551fced78113ca0dda991fca8ff395c4f4e739ccb4642107e3a0f3\n", "51e06b3460063caab67ac26582fe3b1259754ef223a5d38a70200ea144a39f1e\n", "229311a782ada7e626acf46540c54b47899a3a7b8b75d6a16a71ec21016d9816\n", "496ef0d9cee0a5455ff0df0880b524c8fefcca42f2e8c06d06f3443788fc887e\n", "8345f3e04c95e8df857601b57c1c9b985a68ab96f7ceda8d428aa33376f5268f\n", "1ed291fecc096db116ac5017d603ccead105f5d9a32c6ea0423909aa31442db1\n", "0c626a06ff2a7d0b44fbfeb1c18d6f95d70df184e6783456bfc41cca820d57b4\n", "4ffb4fb647f4e6c5d566fef67033ff764934625ea86d7ecb22bb879a3e421466\n", "9b70c5dd546880e7d056abd49d209b9fcd63480afc7105e97fd8c9561e79a157\n", "feae19899a28195dfcc833b99b57ff3d403641cab6fe1e13358ec8f02ae6d1ca\n", "4cdb3690b7de4d3f8c34550375e5b09bc45c6c4a7e2db2c873abbe2079b7ee5f\n", "305d1bccc8ab4770fa9c09ee7317a87721eace2ac157a42087e554255a22e87e\n", "00182718f5bb97f9bf3a2c3cb494f8576648fefe3c1f445b031a75550d634b22\n", "c7c1f5ee46d41c2b50c6da1be324a9a1365c3294b340f60201ef71e136d515a2\n", "5ad1837bf26a361bfae8209345314d476eb476af436b039365cfdbefff9c71e4\n", "3e4c98f5bc400ed5713e5356ae7127fef389e288394771f134251962bf09f06d\n", "d58d2d264540804074dbc2e2e6d4a88529ae3aaa1a55def75c9c83c43bcdc136\n", "e694f768e84047899eae31032018c4fae85a7f5961db811d83d64718884657c1\n", "b9c91a5ce9733e70eb5aaf93f85609e63202e63f04edb2ce6f56c7f6dc51888c\n", "3b652188416dfd79a5c54c799506a0cc7467bc09892add94d3619d8545149c0b\n", "4ff7b9b4796af26777a1f2676225a2290dbabea3da6215563b85ba406ec04b00\n", "1b30a761ada1801a5dc667682243d5739e8b5089066210a9a13b24078db5af1e\n", "38441fd8b52e6a9ec9355d61c2c15d11f063115b3f351c78c72890149e84ccd3\n", "485b5b8e1de09a0bdc73d393173ef54a637b3902ab60cee32f30741323165c9b\n", "482c1b746f2849fcfc948bc4f73452926408b9e394e555727e1ce9d8b6a9caf3\n", "b4289a76f2ac7b470c2f72a65afcf8e351d308d241a8f4cd210802563744b91c\n", "5a42596cc645aa39f56ec37e8464ece0798a335a89d90247479aa7bfc147a68c\n", "a993b325befe6befce55ff27b1c72c6091ffaee0a382e18f0bac6e0a52baf178\n", "7694aa62eb8060a81e14ee32303682af8d8475792f9fdcdf7432fb02fa72f2b2\n", "c9cb197445ca75a0fa68fe74b80bcbb749fd1a12d1e9c98fa188dfa44021022a\n", "3dd4aa202cf03ff379a63cdb3a74d4ee2098e075280c1b9b987180a31f9eeb1b\n", "3a5c26205c0251c089b3a3a53c816c66f4d7f42d77ff284272dd903f81c91a6e\n", "85f6b34fb87ad0ebe2737fed055a2cd8df97b855113f155adca4cafac24ac6d7\n", "465183140bcf98326e9297b2a8dd5afd5db599805a75c3ae55295d33cf46f9f3\n", "b7633c1d023684b91665825c42dbf8233b4e599c1f7ec89cc02c5bdd8284b127\n", "338e4e03c68acacd81394ff501e44334043c30c1cbe466bede2110506d25f4ed\n", "d3023e9ef0f224c368c23ea84be4d363b7ae4b4d98233dafd9e8ec2e6b9c100f\n", "f2655275d1fd158d629d42ff1daa2bfd89eefd4db4b9b2e9c8e442fd984c164d\n", "826565e01226742907df75247a88e8ec54db6088f0563146ce8b541f7926abdc\n", "bcaec41679469cff5ccec6f41bda15b723e53112e2cce03093a99b2f94a661a3\n", "3b7912ba8f1616fab0280ac95823d89c133d3c92699061bcaf2fb23869272c58\n", "9ce17e78eae4b51cd7acfaf572d35611d90d27d3663c29539fb7f8e165964404\n", "9356415fd00a84fed300fe561261f9cf46869107f1253e87c88ed878e40eea94\n", "b8cd6d6c2edaab2f239779928d19ba4b761dcff2e8fc4ce2d3dc4c3a100f0a05\n", "7d89604263604d8fca288b787e3a26627a2f1715d904a2cd79458a33083c244c\n", "373d89ccc9061ff1b46805cc877d58b269599f535ed9a08736a9bc7253bfdba8\n", "90d464738764e28c378fe4e996f550c1e224039e3bedac7ced377db9d21da533\n", "943e16e1ac9dc28ba43c1923b152ac53ea1f870e36d35e06b97b55b43adda005\n", "2a33b9d89c52055aee2caddde7dbf42ea297e245187120727371366cb7dcd509\n", "f78e9159da841bd815c4a6ceb4e140ed3bd34f5d84f03bbf3b8437a680a28f61\n", "02f23713d1c6aefbbc9ce6df31151bba55f7dcda14114fad3b75077f8e1f7631\n", "2c8caaef2292e7f8938ef4d22877eea098a23b8e47ac2ccf57ad745f7fa1b944\n", "1d47c47906619d60703a1f6387658f33e5ee05184b1601e8223752b834f66100\n", "ccb7ff88c26d323dfecaafbc4ad164100202894d50656702b38138c21c2f54d5\n", "6f6cab98f5e1d813cc9cb3b653c45eff7e860ea10b7d8d6859540cf5f2e8813d\n", "c242d96b1549e3f5fad92aea82d51bf9669189aa830fcf65c63d6c427c93fc65\n", "c3ef892af93cf6d05828750deffdc2746fe8b4963984b88c63959120f5e815bd\n", "be2eac311e4df89d27a15f3faa7dc446b7403ad3a6912bee68a912d23d6798d0\n", "76ffb308c24411ca894666212a3ff161a85d4daccad683342f6681cabb8ae017\n", "a74523a9a4c0c7f20e4746153d2e7e7bf46bced8c97976accc6bc644fc23b29b\n", "fa8902a59bfd6ee9af820ab5028a78207a3cc29a3fb7996bd37cffe1d39ff79c\n", "b74bc0d7dcfdebbcf9539bccd30d7971b689c68fea223741d6c6e0354947ac6d\n", "1a15cf1d1a8e1cf5391903db63669e377a5ecd2f1c0d1fdf53a575da4335c75e\n", "e754884714249315b7f0ae1492c1ee48a329230ee727a239e310707e73d1320c\n", "86b6c2600bc72b83a68d70db21f018f583aae5ffcfa548120512a27db7851315\n", "caa54e113d0703b8cbedc0413a93a4ad3e31a0aa87c2eaa93c404a8267f1ae3b\n", "52b799f825e1d4e4dae80f776daf1a64f824c6a5ad0a564a0dc044b4cca313e0\n", "a1823268c067f15f9a8bad1fae74366b7bf513de95975221f350036d043ce262\n", "6a9965ee1a9983ef7b364809128da86e0e095be1c6b13d72cca9de5088ce0732\n", "816184c86965567c22f19c0eabb9cdaaf314f2a2e6d2e9b8bb1fcc8c21c5e8dd\n", "fe8de4fa426dbe347ba86ab162b0ac48f25c1704bc0a32d971a1264a0427ce78\n", "23c4f2d522fd43dae269197aa97b92d6f5143fec2051dceb0a3308b9aa063e05\n", "564bf80ada8fb6327bd06ad35490e56f36797a137fd9c6cdfa6402838e80ec25\n", "ba9c25cb334e81de80d6453946b88c0fa4e9ae4fef0a936e6936728b2e073f3c\n", "f6a4df5b55824c33e408899e8f10c6ef0a05a5df7adbbf647d6e475b65855ee7\n", "9810df6dec24467425035e1f6a08ae48d946c24490d12f4b4dab8a5d4af91c56\n", "19331b151fe166942d12f05686156f1e7afebd8e324c6900a375b6e151d3fdc2\n", "f1873f2176c07fcc35f5919e5271b8432c8260f9edf6e85868da4e816b78b9ee\n", "7341d2a26811d26d858f7bb0dba295fb7ca92146b4fe056077489b13411bb88c\n", "081d72c9bfc0a1e5632640fe738a341aabb451e681043ebca94511728a89f71e\n", "f845fb95876154b85d09d42db84012d4579ffd4cb83dbea2eebc9b1cb4622b1a\n", "5a75fe7998746a6c67fe462091017eb23e61e6b326dd95aefaa04b6785136b6d\n", "bc81ee7564c58194f9bb71f678161dfac6286fef300a897e88a43430277e69af\n", "8f1f57688fefc2dcb0dd5c5778fa4c7555a9997dc332c076b69595e9f9640d03\n", "f8ebd0354536ca3f2710d65217af6564fe4de644563116e7a759f9cc8e7a452d\n", "38a6ad18b2ca4506d39edfe4bdb96cf39fe72d7db033c7c7f5d1a86d8c38f437\n", "4ac304f5b139dd9638bd2ef5ea9f0db5af8ffbf32508210a6dfd42b91a2f1580\n", "43beb6a68205edd57b2d4eaedd54c5417aa9d6df8beb10386f6d5296adbf09cf\n", "0792cc4938b4c656d7c30425c611f60dcad421dcd586d4bf8901720eef3732b3\n", "793f46bc5250e232ecb1581678a0ebaa61f5c0de9a7eb6313b6affcdaa161971\n", "88bd1926ab3812068757c9b92e553ff3cd5d25454cc909e2ade6da18ae1f33a5\n", "21e3d30f38ff11924ab3a3b4e153ffb26eb5d78c810481e46d187b56643b967e\n", "1463df4e55612608a5dced1f52335c5bbb1149c392077ee2c3e0c267cd2dc690\n", "4e5c53d6d10bd66f49729f1d0e230859c019eff1b9273902bb8f344a564a0155\n", "e00d9f55e05c8545c47393ad9e3b94285adf144e2c5019d99cae6b1e9c4e9d1c\n", "f809d73b1d3530f0735e05291332c31375dd83396ff370ef680a81c33e301917\n", "3e1580183766aea781ced8911a9cfa3de441d3cfd3f5396b7266c58af6e45f35\n", "ec8188be668449dae5ea86a8ae241e9ce6b0794e488fb83ab0e89fd0337d2edf\n", "044be50a907e4d541824e1e3aef74eaa69c513201ecb16e4c43274185e22ec3c\n", "a1209d5a2a9c565decc525f2c179aba68ad18edf952819a470723a9e423e5130\n", "acba52311437bc5770a7551d626da9cb3181dd80d81fdb46914213540ff0d1f6\n", "0334fc2b9247955f6391aade0914c223802e2f94566ad76cbc184a680e7a1529\n", "c947f70f24b044aa3358e860b0fec96f7472311d0ae89df55d69ab676dae2fde\n", "fdc9a3f1681f05ca3c418061b022f490b20a224084fc0fea99a6f5b41423ac6a\n", "4163ee202dd9f1afa1dc64556e1e807d72f8686381824d55de59f576e8eca457\n", "445ce2ffd5539f05e0b0c646f6f973db22af107b62912c16afad4d8b07cbe024\n", "1a82fc06b23a133b1d79807d126e7c544219f694460ca886cf7c9901eb572650\n", "2bf7b6cc91e487168f026d3766fe0a5a100b7ca04d0676d13b3f4180a70dca4d\n", "c6e087a471866f398e26e872d39804b060c6ac65d5ec68f2fa2196cf611f108c\n", "e81ca0995c2966b0037d83570abbf346f0d5f0cb909696dec7ad1230772d7b3a\n", "405b614f3ba93ccfc9521e62831d8e917ef812a39407848f44344a8afb868cd2\n", "438a85710d3d66890c4c29324b1daef416dc2a668f6fb8bb59ad8a5492ea07f8\n", "82ff3600ebaee36395859920006a8f68b6b6532d00989d1debc7b64381a21a4d\n", "690fe5846d9b3a5707c93a4cf20ea23b792dab6d53eeca331d0da1423a128940\n", "77e6de0fd9995d44db2ef1e5955bb927d692597a1d9cc04b3bf7f84ee69809a0\n", "7c3335dbb1414cc11d60af06056da695d9388f565d7cee3ab524bf3be627971c\n", "18ffe513fa69bf40ba23fca4db739c51d357fe4e43872d335ec4ae9b9e0a3df4\n", "99953950d190f9d40356a98f3497ec409d4bd999815fa4650feda8acfa0a0055\n", "33f95732d090e37c9bff473c88877883620b2902ceeb2233f1d544671c587f59\n", "f0848420356c0c6f817c5fda48ed337f29bb8b77da090abdf36e53098fb3ac31\n", "b811395be09a03ac59217c62d68ef1254acdb304de4d2ec26bcf3cf60bdc1db0\n", "367d5ac633fcfd08c22bd8db66475d6a32188e37c7575181d191e37b37b880cf\n", "d4026aa278d5ecfeaa7cded39938d91c5da031e0322be915a84a8ace206b9207\n", "887f55cc3869562653af9fbb854565decee5f8a1a54857e4f9e6cf3a3bfd661b\n", "10d844efc8f192ed8a4b05d0adc3512a6529128d87dc494c2ef9c4cd0eab620e\n", "d5e540ae0d36498da245b13422c7abd87b5fca0d757613ed719201006ad39035\n", "253beab12865c9296f0f32c21994612213abe7b45a859dd141ea63ae3f4db7db\n", "bf7709080ac90ebbc709a54b9fc23c25bd02fcacba968ef1486f620b56449491\n", "fe6177dd8cd01efc62096d5edf289002042010d50b6607a69d24d37b1f4616d2\n", "a1f6cfc862f5b21c4faf02a81dd79bad9fb992be509306b74a4962574f8c9ee4\n", "0d4a7fabf8fad26a03fe6a131e261be1ba946169e4955287ac0953dd4cdd67c7\n", "b82d72e8524ede76eef003f09afa8a31a603c300208404f7a50bd5b15e2f83d1\n", "f1f649f8023c07148794fb90a68c99020d20b598d1ab782c8aa31d14170a24b9\n", "2aa8264bb59516bfda9de60fdbb8569a10161e3d2383d93b2254704b13af05e1\n", "6757fd706be3ca8ce134647bc746060587d2bc50f0f3866ee303c23d88856954\n", "207f2473eb216b28d8ad76d91320d9ebb6f80e442e7c01c6040768360b684011\n", "a18fc6f53835c992519ec7f41f6ebf821b2fbef312a847d949b8c2856b0b79f6\n", "bad83865e234dfae64a7fd26de9b3703bf5059112d7c2aa56a73d51df9ee1c18\n", "071518bb4e6318f4e87eff5fe2357d9de794d5e8ea1ae5a35c0ba11fbd36b967\n", "1048420e581eeb2a9f760e2189e6e6ab9e3c650ca1523217f74641aaf37a97a7\n", "6604d340dcdf9b3691e59e832221a01f8f586e9558cb34de9a583a291cc2ee6d\n", "1380f61a66030fef9d66c9cf88752c530ac6ee327bb7fee107031bac6b138142\n", "c358b198c70cf41b6694ff9d788615399c5d8c706be164afcbf8f5e885175e45\n", "6b66deedad74502e983a8d59f3873639e0348fb944a4d814a40455daa226fa85\n", "b811b505529b5da350c4a36a5f7ffbcff0e5881206c295d2b25444d8acc8bed3\n", "f0fb404836220298cd6931465949394707a4ffb7d889e07162f0f3c9d183e97b\n", "3d85895b9649141bbe1047372e5c2af9ee59fcd5acfcdb1fdbcec3c482023142\n", "1d13b52789a75d2427b1499e7acd203e563d6b40951674dc190e30cccba62d4c\n", "8605d766b697c7c2fcadbab57588df71ee486c9090fa4a105d2ae95f32148348\n", "92fd9af101b395600fdc800a65d17805acaf3274e9f0514d58edbca44b9c738d\n", "348e60730adb674c492b1b1132b5ca3c397e222b8e49b5536b63c883d150d83e\n", "aa9e77d3f9cde20930cf9c5a476052a8b9b976cbdf686bea30caf98948707583\n", "79f310b9c66fb0db4ef919352aee89d4e0c0fba83d9e4a58de6f1b92a1e357a9\n", "ec0914bb621e8b36e475d29b2da128f764cd88d57b3a3f5a50b19af0f4a0863d\n", "a86d870e74c602eeb904ec05e6aa173a495e7655374543c0d50c0c33f36e93d7\n", "ff3d3d34f2670f2f53d50aa40264a52f9b5f27cad9549d688087137fd7cbb1bd\n", "a0cb356cfb7e3e3861d5ffdaa788c18d237d5c7c6ace6ebb269f3ba80ebd5dec\n", "99b9e20adcbb3785d0f30f06715c913c25ab9a2cff78fd23a48c6b55fe6e9d0b\n", "8ee8acbf39ef97cb03379a170bf09681e2f4adb85c2dc50ace161fc6430b86ad\n", "c41bc02f53ef1cc56b315b361ea9d4eae173725d3071d8248d5ec2aa4d84e6da\n", "ec01402f1b692f4f2c8f67646eacc70e25847139215aa12c81c4289199c75e10\n", "50669b249f0f5fceb68c1483af256bf1616c7647c7adf5bc2a6abae10674e67a\n", "b25c58ce4625201f5c69c6a264afa2d37cf228b86c0cfec3e61f62d6636244ae\n", "4e9c5f2839e873e290305b309bcecd3d276118b39638f8705fe0b86d82937fe5\n", "29f428d171d566407717cd45da70ec7218386cd840ae21a85139d8c69d495e29\n", "487a90b832f71f3d883eee5d0d3ee5f27241bbee442332eee80aa07d921e3e10\n", "9c610ef2d81f78a800803f8d029ac00cb20195f13c1b50ecc70f0d6c7042ddff\n", "33a95443a83345385ddf277e2005a6558fd46f9ad70d2840e29b88bc0fbdb41e\n", "f2cde3b7ae10538a928b4c89dbc272be513d0f892bdba12690d8db0b41963eb7\n", "7e3ada0a4c60a9172d9aead3d8c033cf3fa1e7ee80c720becfc6b1ea82448844\n", "b52f7294f7ff39cd36105a824bb79e54571caa841028dcd2acdfa1718d9506c6\n", "baddefe9a27d47be0655eda900a95c7f0f26a233fddcb22947d9abda92a63ee6\n", "640f505e85067da0412bfd61b1ea93e6aea854d1dbc924bc70de98961e5287bc\n", "807c42aac0dda517942e9f83554376ee4c21b608bdad27e26c5cd0c861292598\n", "264f8e1c499cf32939aef805f7ee2273401fb0a248deaa00c74eec835e97001d\n", "b3b04290ed98c7850ba210ed992ce99ed0148c624e7daf5eb8738f44448a3a22\n", "342a489d0bbd75b0feac00ebe6a8901e353c4d0854e6ccb17bd7a0bf82ba735f\n", "6efe8b6368f7e6da3ad25ab3bacd6982c46eb87d5d37e0b8ec6abfae3212f3b8\n", "88f35028f80acde7ba8ce615b67e6bab3529ca8b888e494309bfdecfe36c2d2b\n", "3124d4864cb218367e160b95a5e78484bacb4a8578f367994f1e5babb1dc89a5\n", "b16987bdd9231712ab0d2777432477ac02b7717861a9143bc657271af9496873\n", "c934e48dda28937be044f0934dfd6e31b1317e5c12633a0e270150dc883c2a81\n", "0c47372277e5d6173fe97a0c004f1330cddd907caed550844aa7e8da8903f79b\n", "4f919be5e3df612287fed452588aaee455ff16b5d2b5b1d7d543661353cdf621\n", "f6b79d08ac7375e93ea388c2e356ee52962240bb469d235d55f241c8e808a3ab\n", "403718b811ced47636224e003aaef59d3b337647f9cf287ce984c681d7bfc9af\n", "77b9bf050e361ddf566e2238dd5ee10279d1db7d3c2ffe6aa3d8d4516e45266d\n", "7a98083c92e731acd4158aa8faf60ed8045bf2cf32bf0a5b489ec84b1e625ac1\n", "5aec4d83eb002ec067bd0e72b2ff5c92cec93ed4d4652f954973863134f28318\n", "e0a16daf1652f219c992e8ad0dafcb38a1835db5b8fe6e5d941b346efc30ede1\n", "78126219c80b6e17a4305ca3c4033109ef8ead26923d9b8d74b31584d865fe96\n", "9d5765ac99e5e4861dfd00b7ec4a3dbebccc34418a6bfb28c5f99d6250497e31\n", "4929b97cf974d959be5590df0a09242519d5d2fa92f9065bd821fab38944c077\n", "0be7f59da083ce929a1130bca1ffbd6c722403eadffcec3dfae058f86bf271b3\n", "adb724455c0a7234b233c7a51fe16a66f44a1490b365dc0a1de3a47551b5e0bc\n", "3f6e089502354dacbcdae045d798b39d11cafe40fef994ca0ff46e419a30ad4b\n", "69a648a5d8f2cb028fad6cdf680ad4d4c2c7c3a9213a6b189126e376ef05c066\n", "98858d35152ce25d6e731989b3da8fbcf95422a3bfb5ba37f003e76a7b1c2687\n", "1ccc29db6592cf15e9b166d4ae15ca7a9cfe3ccc330f5844df22c8730a6b54c5\n", "e030d204ec5ee743b78edda0d182482ca1161d120d045c4a47261cc9e3722d97\n", "ff3f677848ee64f1be06f5c516afcd856777b6f8af2693bc6c70e9f1a1106c2b\n", "7bb95ba8b349278ddd55e5ff0c4818c22ffcc58c11667f15f2941f96d7576510\n", "a7ef96c16d45b42746c7efea8c492f7d1d64fa163f5d28fed234c54d6d82f73d\n", "808b0ab615aef3dd4f5baaf652e122c6e46d04541b6a2b07cd917c31b4c2baed\n", "d33682b53a7fc62bb740ebe7e74ab05123712b05ddfd062e5ef12337156c367d\n", "3093e45a1c8c68940ae0869bcf556863d259cd2c4f697735d1a25bb6587bc6bb\n", "1b33ae7ce15111e66d213a18b1503f4daa81344589c97ab2a6a7fae9ddbb7c08\n", "523fe1dd7728f14ab6b7493a1306accb336ede1095fe15cde0a15114161b6038\n", "666c949b055663c22334950ca1cd20a795090c78e8d71408d9df07a7b1c6d767\n", "8045a985f9793f25343d2bdb30e0f210c752169b2c6b22ea1a39ee99d267ce62\n", "f33f0c59263f65355f0a440287d931b47be8e6fcc9af5477c85c9e830c8ae749\n", "943a913e879b62d6439a08956b2c33685d369c3cdaa84605602ee04f69a0b664\n", "c4e505fcf90310a366629d180f111720e2916147fef8c69b3d7bc1021017cc84\n", "bfe47bdbd19021e015e95531b250c3f3524a34e223aaf4fb0acc42d0a3c4a33a\n", "84bc5e5d7d794ee0cf8769db13eca07640610cc9be1c0b31b65ee791d8ec520e\n", "8db0f3639b26cde5d3d290a52de7c3015073b7136d7758720f2bfe2629b9629a\n", "c40d62d5c3590040366a7f976580ac298f042b19731b454e0d00be16616c5177\n", "e1f975e2c7c77481125166ba36e2a6fa87b9c09fee3b8c878e76dd46c712306b\n", "e238ea39833a97c79d84dfba73d224ed495d43415a572ac4cce8753252364152\n", "561976c8b7c9e8192d57b73e1039b7630d5c13476dfd5d2126dd50a64f97d48e\n", "f407680c103e4b04d5f84f8edb92350f770dd1aa2c6f5891566430e1d6c3a965\n", "4070a995cba775526e9ba5513f84857a7ac717995155e1d98a0782cbb878af03\n", "39b91559a8aa38e93904f28b24dbd10168607c5b3c95228047ebb00ab394e38d\n", "17b90effc761a4933b41e7edbfe22bddfe8cbe2d2baea347e54b6e3494c1ef38\n", "0068ff024e5284302a67238157d749efca6b301187c7bbaa8fb3e61a8e7c1139\n", "8635b2c49d8ca32c6e410d94c50095dfe315aea11cc4f0cce5c8b526c85a1851\n", "8e01c0c0af9e59e9110da2d8968154e09d65840960d1180b856b77abb3462527\n", "2de19277da5b4f75be7b5c0df22311f65b01774a3a6b3ec685385cb58f8dd2c0\n", "299512a3a8e6d4cb26e485110c907de3c430106bbaef6df03e481dc534a7faa4\n", "a501ff84f857d948710a877ed85e13b6f19aabcbe13bf15c1efcbc3b6230b06c\n", "b726ba603324065e2d60231beb7e226fa7b0bb4181a9aaa60ea56c6d001e875f\n", "e2013a5b1c0e3981e6f73bca86d2a1f5cc850fb14c89f2e2ab745571d56a0b3e\n", "fe4728c1550661f36aa80f331d93e1c1061def980cdbda049dc6021cb62ad147\n", "0aceb98c757c3ba30499026bf1412f42d4837893d2bfc80d62ee7fbd4e67165f\n", "8caac9142e182a5ec9c4cc3636638ced70ee649b09e212590cec33f2e478a536\n", "0bd6ff8dd9d7f92e0135c5b57cb9f1f70e5237abea5f7c265c91ed6474e5ac2c\n", "b7c2f7b92346b4c22ea8a14bb4a68398b81392b54cf9055434056b534f6e96e9\n", "7520ee266ec80a2910806a29b49e17ae3d6afe6337d7524dd72f4a6987845af1\n", "58cb82579a50167a70dfa6592373c58b4bd730bb2fa88e925f2197aea61ad785\n", "0409a088574aefb48501c62d64e38a727c568c476805db09d57ff3a19c621ec5\n", "afd73a2cd7638afc6c537aa03ab6fd0d5b5686201978a9f2e05fe68c9dc03fd5\n", "6713bf893d5e64a745ec50fb8f3d816e106b7f6b8eb8d2a75874406f40207530\n", "48eb71bb1da269346093f8d9024b3d6a634a0d3dd7cd50598453c1b50e8db49d\n", "74d99b2e98fd571d6a667a4da35d2c5adf75dfbf3936bfaa6abeca3aeaa320ea\n", "7a7dd15f1a64b05e0ad547639b0dc747f4f2ccc8a68bee1e1ea18a89a9df4ffe\n", "9e9742ff16953a5dc5b21ab0f1b62a99dd9c642bd1951735f859951ec039db20\n", "e985f5944198c78cc44d2c957bfe0c844f027ca12e98c93dcbec8c63b306c66a\n", "d7bb7324efe08e9adc87c79468f117aa7a623f22233c12a0b3aec9b361ee32d3\n", "213b8a30ac2cf4fa8ec7dcf9a2e780798bc3800e2b42781cb8071badd935fc9d\n", "83ec351422a5dfa0b6e042489f9a5fba07844625d3891e0380702ce1929cd7aa\n", "a21f06f211327fcb9974f5ab701413f1cf9da5d32b6818fdbe2dce32c4a043ac\n", "22545bd9cd717a85ce93b709b6f8e5d59dd27d0d7bc103a91b276f5c85ffb98f\n", "9f2abf2d12caac55d99a982229d0e8221556f8484a3c363966d7eef4f1419a45\n", "acc756304fdda15e447c56f5e89ab35b4179f891944307a7d2cf6ca72870421e\n", "2fdc04e32a8f6060510d048ad29c5f4edf17b618788fb8ba9abe32adb6faeeb8\n", "386cfe4a2392bfaa6432aa700b133cb6be6fc1313cbeac9ccf825682349f4d79\n", "877a52e16c5fabbe0d90d29855bae393b94e054214f623b19a9949399e357a91\n", "6b82becf66642baf44faa130106627aec9dc8040e3653f120b4a9390388f5b8d\n", "80b9aabb47ef2f1f38c785d23a81a35b920780fe4e7dbd647b4032d66845ed03\n", "c05c7e58ad53656e64187d8b0c66f4328a49875aa990fc13c45ef2718ff430dc\n", "54f4efa64f20b82d7401fcf52821abf39914db1db669de812da0d25440d1d369\n", "f9a317842d17889a326b96d7a662120b01f622d2cb1cb52fb8a4c0853c866d74\n", "2318977f08bd6a6bdd8bb4ddb6efe5fbc7b7d2c7a961c3e256e2d1ad36bea00b\n", "e83cb280266aeaeb1aadac1d1b782bb90fbef1e8957945a8be6a43357028e580\n", "e40a94c7a934995d9fe12ef4145911d92473ec1dce01ba0551efce47678abb11\n", "9eec9d4fb1bdca73966492f202e60709a5be08ad45f1cf092ea057749cf75191\n", "b1c49e1884501942202a3dbd7de516aa117c9fc7224c3d8bba0df3ef2b786f06\n", "57300bd55ae80581b297cd7dccb333bfb48e8211c0baaa6953f15cf835234a0f\n", "3ca64f566629c0e530a6231e1c6410c80e3bfaf7fc3f4ac769aac7193daab8c7\n", "4006468cfee8aaa099102144d7468b9b0c9f01c0d847fdc4705171fd2125cad5\n", "b64d1454b67677c864fe1042e221c873627c085e9aec83c57e17df7e138a3736\n", "d2f89b154c1dbe693bb61b1902c0e66231fc42049d7a6d5804034465d1e727d7\n", "6e75cb0226b0fa22382016795fe7e9d1eded41d2f95fd97e8e6a8748694e5c89\n", "1fdd0edd07c3c1b1fccd1790a7c2f86c1da3cef1bfb8a6835bf1bac489a3f4c6\n", "a95816b932bf60ec256542b128a3a42ec1fdf11ec899de554e3f8e4460246375\n", "f08108cae36c00ab953a1d661b3b416ea9d6cf5d950f09cd0bbb3a8160fb8f8c\n", "4e9bbfaa44388d7a2ffe4745f5be62451d7aa8e764af8d112a09c1a975677a14\n", "2697541364012c0c63acbe5e14484ae6b3eee760fbd08a6caa4441a588df5931\n", "38f9f376f918b20b98bd00c40a133ab4a5b3a1d079b6142e4970e94c5257cbfb\n", "876a68cd1d9c2eb622cf06468617ab85eea3e4804669ad59bab2bf4e4658c38d\n", "f78d4f91e57191f72f391fe61c17c404e6a9e65239dd9df20c3798da177ee38c\n", "d41872bc8dc8f1aa6e802970bf435f1923590898b65a3adfd49d57748055c4a4\n", "4d8515fff770c657562bb3dddecdb9696eb9a3515a8c44dd6292b4a5650decee\n", "4159fd0477b51308529212f8a07fd747b155b3413dd13f9b3b3ee249a509ece4\n", "12045a6eabbde3f1f72869e084474661ccc67cbdf422bc83b4b51de757d05b98\n", "c881cdc38bf41e3632671788bcb87291d77ad249e9b9384ae9bd6ff793fb9006\n", "c5d1dc6a877f27d378bb8979c3edf835dcd250c92575acd50ca075e98858a18d\n", "02374619bfb2aabbb4e73b08fe55b6b8d1c00f05ae9a78f138ef20fd5bc2d997\n", "f3e3c9d29edd0311170fb6192b28c3baa76cf9db29d3ace233bc060b2a22afce\n", "761b74ac8a6dccb7be03601b17b1928749bb9286b1baaff34af97d90cccefcb9\n", "c97f1894b5ead417715cf66792393822643299e74e33da7125d97687ce3598ea\n", "c9200e653782aab082c7b938f02c5964cbd7a3dc5e46aa8d348fbeda80405d1d\n", "053b92cfc3451cea7506ff3d04bbffa8efc1c72d56d2ab5429bf76e1a7657377\n", "8ed597ca704f60859250ed6222ab6a7654fe79a9b5d9dddb1a1218e704041b20\n", "95c4fac472870dbe3ffd66f52458a91637ebba373acb8e4904a328651b5811f8\n", "27c7dd801c41904e62602bf6eea6054bec9309569b44b7bb5761dc50918207c3\n", "f12dcbf262b11c0ea370667a40b4f121d912b2172d77a404b560e860e824b1c6\n", "ebc145154c444fd0f4cedcc7d00d3686807ffec86eb67d416395cbdd4a0be50b\n", "ecfa54ede8339c8687d1dc59412e4e6e72c128beb077b4c7ac28f21999337a57\n", "a673021d3778ffae7683617377a82800630b7db509e239c4dd88eea70df230e7\n", "64f5504ba20b75251c435a18d19c1da352a927b5eae81843cced36822abdc828\n", "e4ed8efc7bdc31ce1121e201e52ac3203786b232d946b12461d514765f990ddd\n", "d9855a3bf960ec5031bc48c7468973b2ce4fa307dd4a9b9044e0d5ff0c0c5ca3\n", "0073e05c9f30160bd27519cb3d39fd43c51071c15664457a0a76431af4690392\n", "3e8173f3b3dae3ad88aba2acca73a9342e672a3e4556b3106c710524e9a2c086\n", "12e294bb4f0e86f7ca0e6ca3f58a04174e0ab45c9d8c30a6fa522f7352cb0546\n", "a927a24eac569b9a8c3475f57b6fbecd79bfabd6178eda7ecfd495975d1c8ea4\n", "bf7dd5337dbb021c7af94220b5454f2e2b2d4bc4d5599d09a9aefd75b129d71c\n", "4a633fa1bc39eb7bb3ef27ea837edaf9dbbfdc5e137b21743a542b9c007fdd3c\n", "bca75e08e408bcb7175842149bafe912502b6e5a8ba0bdc99edb5df14ba70818\n", "935fad45feb8c83788e1c52cbd476cdf90bfaa302e89ae79c94bbf1badf4498b\n", "654c98bf1e18e4968311f4868722e7f243f07a0ffcb777731c67dbbc165d0052\n", "8af63ee02f9adb8c2b4df77efd78ec69f5716fd5ab28ecf87fb528bc8548c784\n", "bda156094daad01c1586604af1fa73fab684f100f09adea4f757db1f036f426f\n", "056656d30274fe7ad94b0b4c036815b46327e592de8c42448ccad11d18dcab5f\n", "547a5477647136e9fa285ac2213b6faeb72ea3046af182d466973618d60829fc\n", "6533e84a94c8674523d2e28cfd8f9add10ec6e72af4cb64a311075df081a3f9c\n", "8e2e1506133ecc9695a77009e86548c3aa0cbaf8911925c116cdcf7801d0dc3b\n", "62dcf2476015e90dadb3c87ce33fae55fa992b89f9eb0d581027cb02c51b0a36\n", "44c6f988d471b4aecef66607a46de7decb17e7e5c56e392cfb502b3b233a7c35\n", "6ae3a73d225209bfdfde60912636490da68db524b8d757cffea5245a4da7d4a0\n", "31085c3157f4861d5ee2fca090a44d64dd960696e483be6881c4af57069981f5\n", "d9158a592f1a40f17c7308ba5bb13acaa15afbdb0e124858bcdba2a10d693d23\n", "725f156d82655668b04b176f6de35d881c921e4f2df12e7a30b4324ba603c0af\n", "0a95b83cd449a928867ec2621bf93e7a14c2b98599a6c00d4b774c046355974c\n", "ec34002273151c098b8ed5e47be799e8cf8a8c573ef5917ced91f62af78e1f27\n", "4c575807bda35f2647bcb2ddbb0d8452f4d244baa126d4f05732e7cd0b7f1277\n", "f244a036f9a8c95bdbfb1cd347088bdc2171a4066a4cd28f2dd2c621728fc33d\n", "1fefd279e77195f4bd197f0ac6e4bcc9255e2cf08daa23b2fb7eebb9355e4731\n", "b315f5a077b3ca5c0b848266804a361e416cb2a8257817bed2adf99cbbea9303\n", "ff25d459117772729583a5e57eca5e8081793f4d6b7ded0aeeae8c0675fcd751\n", "593b84f3fb7dc90816f58369b21dc03e0263c0889609a7a20d9d0c849370961b\n", "a64945ba9692e8a1f2d9685b4bc10a2e2f3979284f155a078f97f72aa68886a1\n", "2e4a6bfe676be3c8b21ecd6d54ab8266443a8b5553420f9d80b05bf5b75e5fee\n", "dd491fac2d0bb6b351c1a6273be1a9533435895984d82c7e8e80024ac81a249b\n", "bc25f06788f9e27133b3c217a36cf33e5804970c158d2629ab910853c598ce78\n", "e8c06145ac436c4b99bbd2105dca21becc2e285fd99b6cc9807dea4b3964ccfd\n", "ba3f412c43d50f0f6a89b0e9c9844050a211754ff7affbcdd3471cd3aea7dc5a\n", "2c9bc70458226ffa5bb18b3e27a95e4c925136299ff1b49b233792fbe764a5d6\n", "f1040d96d9bfa5028b2452474c3e9d9efd9d7e7ddfcb86243def20798d807138\n", "cf36c6701863cda9c92e6d23dea6dcee113bb2a266d362e0f90cee5b9616a030\n", "95b41c0955cb699757945c25657703608c3d6f509c53b284886cdaf9d2426087\n", "914ec7f7ff0d39a519528401013bce36dceb8530e30783a7034c93fb5b8ff89c\n", "6ddc66ae17dc7207654bfdfd1bb367d638cb7d594f10f0d6524b28bcdbb639f9\n", "26bb62be98519e245259192063ede6b84acb50a2337cb13e71a7ffe30a55fbbd\n", "1bd2cc399b0d86d607b03d8e07d4c028abe76ba426f49d47e4aef5aea1f2e5b1\n", "7b50a416becf7ca2d66946d1ced1dbc81a1d35f0a3c830e9b252f377ba717580\n", "6043a2c982104bc3ca70b47732de557b0af828fd6bdcb5b583b42a083305205c\n", "e753ba074224f34d3fea0e42d3183030733b6175e00d6236f1b3de3b104a0ad3\n", "dd17b5d3fdc277ca053e71cebc79652caa52a1e8eadf650529bb1d7488a27af8\n", "0014c6de449fa93222921868024d92b6f0808ffaff3471d5c90cab654303b62c\n", "e67867cb82f0bf4974f6cfd76cbc16ae879526f25da641d0339a613eeffb16f2\n", "d949337d8e6b1094bde6b2dd42fc491afa29e70304738285c8af5812c42557d1\n", "c775721600c955eb8c2e4326c818c18af91e4edf1db4f2ec7ae156c004f93ef1\n", "f396c4f0a4a4a1203b4bbb3de4c8d92b6d0e74a12502b6166a14a3a304101904\n", "5be33d96a0054703351c9831f5f9d0f62c57a7971797842e5af4eea950595c0b\n", "7592e7a7316df46488b25b5de54a7d486cc412f26f5604263a84c4f0013acbea\n", "9107940b587a5d753740dbb7e8a8db689afbf8a1bc8a5270f7e7356d4bf9a1fb\n", "7d44fcb548ee81cdfccb383ec60900d5f2e7cbfcd41d8c4ae8e368fd81654af2\n", "bff3d3335c454184c25ed8259e157d1eb12534b3bb9b2b0167a75b32dda5ffda\n", "87c72e94013c376c778c59bee79dac6438c70257c40b097c06c69ec4426d19e3\n", "d24950539f6c17264e525c37c011cedbc988322eef459986debe5bf38e2f8ef0\n", "f3f3769d6028ddc54b86dabcacbf98141480c240696ee29c3555f57b0eafbdd1\n", "71840eadce59f1c8f2895f108ebb7ec7ae7c2b34718972b15eb43cf79d124864\n", "04c06a21ae1065adeb514755e1fa1cfed8155661c90a403d92af3a2d0580a593\n", "d3ab7c56b17dc4f27dd574421dbc0b7b526260a96e29e089a4ddbfaf011fbc68\n", "9e1598e1da3f1e06ff0dd6154cdcf2bd42172851c58bdadd9be0ee93b3a8b708\n", "2f5efbb49a5bd80fdc3a9f5ece9c2183c0906a6b71ca13e7e9ffe71023524d8f\n", "1679a984a68a8350c6dda5982098d9f53781deaf0346916352c9f40052e80577\n", "222e71fab787de21d076a8c0be4c2d9808a09566296c25bf08a781d90d611f2f\n", "134427e5bd18514a0d484aa981075cfac8a281dd43923331c77feeb1aa475894\n", "e7abc18bccbb3146fea0dc1793ccc40e175124d35cff11dbd170cf95dec20ff5\n", "6c18b1556891e0f0ef4851e6388c3f9c7cc40c64201c994b586e5505abb74bc9\n", "a85c37fb7a8d92bd7f2546b22288a57024ddb814f5b2776b358401a924c2a49d\n", "e2027ecd9aefd282860c3ada613384bfb9874b6b33309da70de806a4b693a4fe\n", "81be4c407d4995f2f5e7db374e16b043fc5492f31d4aa2ceeb391d2d31b119f4\n", "b532425d8161c145d35e2d730b655f51ce82d9d9b2c482b23d4a33e0a8dedef0\n", "e37d22e5f29ebe7942bbf8b4da0c00eabd65f0a9c43cd0f71469fcc7efa56e17\n", "077d82efd8f0055f641225978de13c35dc05e127f308ac92b375dace7409e895\n", "44fece68e2508ac9a7325e70c1e795763d130dd97d52bc96949d549cc048abaa\n", "e6b2e7518f4fa4a3f2e9895f1e2e8afd94664757f2618095eecc5a3bc9fa53f4\n", "dc804fd980fdae5e357fb8a53ce221fdfafb01c2d4f0cc2f2aaf1c0936e77816\n", "f823b1283275a05157c151857fc8ee2aa403db42c56b45afde2724daffdc7386\n", "9733d7e240c259d35e105453c9b94e2e8ee26a96e0583100fe57b9c84baf61b6\n", "e1ab5837e246ae16460ddd546093e58e76b21c83de9dcbad460e4c5d8b4c92da\n", "cba8c8d0f65b2d22d8cc5445091af04dd3045eb1fae481522126ccd663102da2\n", "b7cc629b630692e38503568450bc0a22e9d0bb2677b5536cd485a15dcfa28600\n", "7aa0fc496aec73e69ac3a38be63f3adce5378b7611a23c63f6caa9dc83a9e493\n", "f98f15e6fa6ba593956190126c24e6fb0be70e61b723ed133e2dbbff33c20d5c\n", "8bfa1044ecc2c019ec3dfe93e33d364a44617dda1f823ab3872202b14e1cdbb5\n", "9c1f601c94be282ce2c2690e113e853e1f98f627f0aa52a1ed1654d830e29d6e\n", "2a9901965ef71c341938164e90a64039bce4105bcd901fc997136671692ffc4e\n", "1a06b7a515869d1dbb21fd66688edea33f04aecaa6ca17169dbdee581b0557f0\n", "e0a12ec463f8d3c3963e791b59df88816eb3f1ccb8774d0e0c1235cb3687e98a\n", "43702a68e97a416cc36b96b5e68b9516c4c99f5d396be49ac9544c0e1b9a91e1\n", "772d582f307d652d12c8339d30db48cf5a336305c6f381aca6dbfc93b12bda3b\n", "e13fcba26d917cf662b432704740e56bb83c5ae5dd42eccc7b196b3b150cfe43\n", "62220984833a1f62a7755c9ef6e417c8ec99a5bced51d90ed207867947151a11\n", "91254ce4807dfc6b11ed0a911f52b7fc8088c894a41701313b7816316ecb28c8\n", "8b7ef48c7fccb66b7b64af4001005435ece6af7d5e3b66c15a776b3078626270\n", "2d7894b697545e92f34fe91110bba5e4fe20cdeb0a0f3fee008bedb3325f425b\n", "2180336504e06a82a194536f9f1fbad393aa00f8528287ab0eb13a7ac4d70230\n", "e28f5c11e856e1bdf01f9adc1ecec39cd73dd722dd44398fd7bc7c8fdd356378\n", "81a3e4638615ccbfc4726f1c0358f90411bda1d96408042d83906dc258b57dfb\n", "4038447ce86d3f2036bd234f422db22999520033aef567f2621951acd09b7afa\n", "ab6f2ee03a64e1b6c7b9c5d0b976f9a600f72115292d48e64de2f30672bf1440\n", "9f0ed43e5962833672288797921c06219d76f361ed0613e721fa4333956f65b5\n", "193b03f84ded4552af188ad3d440293f2779816b5239af7c3a63142f2e50e4e0\n", "07e3636ab0bef2d295c4a070d6b89f9dfea4ca1b03a9d8bdff766d283a619076\n", "4fe384728d01ac87c428e4e0d857c1c81f9cebb5a53e8447c7448d6ee7666314\n", "8fbd3e00ed5fa7072f7debfd711137b36696143f77854c9cba3b943ae29987b9\n", "b2a9854e21498414e1edb255568d2f422c4c544f441ad84a1a0df7a44c4d9cf0\n", "cde6da578934ef64108bf8e23b91b33a8253f1f14fbc066283160ef719838cbf\n", "28237fbd24ab9fb221ca8f9f98e7d2541dc1b56b41819114b1d413680015a265\n", "c553d7b9a9789e96e3a079c0cab87e752462d89f1f2e3c0c3daacdde4299faab\n", "77cdbb3a7488ce9b9dc80d905fc109f73ad538bf485423388bc3c3d9a2ad49a5\n", "bbc5ea179fbf008cd09b5590d4fcc3b8ac01bb329631444bbce9eb77a9f9e090\n", "49b7d75d774374c89da9e31c1be5451a0bf7476fb60cfa491b29d5154b44712d\n", "c9c527f01fa5581584c6306b8d97429e22d4b1bfb469886d1d4d19163ef3047f\n", "5849a2a6db88932058416082ecea539f2e684e672ce6dac11bc6044fd0388cb1\n", "fee2071ff42d2f3ee3d67db41fe14c4c04f5626a8fd317d0675d391508f1f340\n", "abb7c6929a1f31954fa598bd3ff468db124cf2cb9c8f5acfd8357f0940ceb136\n", "7c236080f6d6aceef1b48365671c8a8a9931f2d8ba2cb6c85c856f471d01efd2\n", "8c81bfd61f7c35cfdd96d522d8778ae17f360dcb0e0d97dbfc09438db2b286f4\n", "2573f56d23e6542f5f8584cffb8ce5ba1ab235e119fb66d6a608deecc89ecb9e\n", "faf5e8e755c303283f9840d98c18eba17b38c552515ece59e5cc4c58bb08b786\n", "4b9eed4630690856ff4c4d395bca6acb70892026450ee264f6b9aafed3e737ed\n", "ecaf03bbca50272c219bc8f0d511323e8e7542cc910361a96d9949345c8bbc0a\n", "878608407b92fbd44fb987b9f769793099491c1acfa3666d4702f71ee55570e0\n", "2467e6766f5e4b1ccdbffed72e372be7be533962f898cde95173416f43478a70\n", "354224ac5c7e4f30f5424b47326ff531d801c1630e014d47a1e4ace899caa2f5\n", "b64ca6d9934d78ee7f9ec8be5548ad07661ae73b65e2a64b9ac59074a3995820\n", "6e4de4299cc8919ef939c8b6fccbb32cb29ab730b59fa86145210ec36a542c9a\n", "91a253656a7d4bac0f8239f9362eb9881fedf4a1d9f5b810a793e97d9cab27fc\n", "1a4d4b5a874e73c3afad4151043b7ef1398e873f19ac294a6bdf8fcbc19c8413\n", "1d6474f2aeeca4ef3a57b8d28f5c13b4e9af017b5b7a5605906eb6e39262ffa7\n", "d5cd484bc7cc87a738d6f780589b742e8838c9f8adf55520e124a6ac92fb151b\n", "90820c2dbaf6dc96fb2d4e1e7751de3cf068ffdee025099ac779996847b0eaae\n", "ad39dd9da86a1de7558611faccc5332f8ca1b70944de787a2155fa29a0a441b4\n", "8d07adaa30c458bdcd861aa5f8080b53c1619943e7baba33cbd54a25ff97efbf\n", "8d46bbd667cd5a6280a9fe9253f13512cb737733ff517676a5657b7b3838c95a\n", "ca93822cc654a10bc8faaacaccf2e1963fb5c0800a62688806efa0983cd5f7ac\n", "f007e5f458319fd5529dc44ad94192858b20becd565e7789999375ab48a9b0ad\n", "8cc9717518c3146e0e0d1bee1cc0dd7e7514a57c607c97b4f679aa5539dd193a\n", "61820f2b52a4399eb6fc8585ffabd42cdcd33d0a2145065d7540b5cc2a47b701\n", "38ecbd7fa32e20005eb85b3ef2e1dd1c2f7785b3e835ba7bc99a61a937410150\n", "3c55ea8ef0fe851663092807478c8147d2bfa0c3e03ebf685740422078db3e88\n", "e91c84ec8c8dff1d93f93cafbc4e4256caa8c45b2765eeb19d6f6e9535072d3f\n", "329065c62ee5b6a6bb353a49a829652a9f3e02ce0f64a5ab4ed28daa66e32164\n", "b18aa4f69764946e2922e9c332ec5bd37af720528185df17e98ddff4203ad36a\n", "90b34b90b0ca430cf1db9754adb03819b2da02ec4d8a693d573b2c5fcc8f0eac\n", "a2a601d33fe720b9fa32b554a4d76af4dcc5a0054d691a0d8fc93fcdaabe787f\n", "1594f539b31efd2954618885a486cd6f472fd84b7e2bdccd8b3aba4a96aea7a6\n", "8bf9a9b686660bfacbf0ce76e8260f8e0dba9c76bfb987adcfdf4ea766350ee9\n", "244ba57ef723e0c2b4507537452dc6bbe7703fd451c7b6918aac4858ef063cf0\n", "c8c481d03ee22e1ec4b8d996ef585c9ecbb89ad0cccdbf6fb90f2b5658e6d9e6\n", "dc80073652e1a9831a5adbfe526ae4ebebb75905c829c3b7fdb88ed2a9f5fde7\n", "5086fa4d9b64b3790c9d8a6aec903edab4a363c64aadbb2c7c57942bb547e3bc\n", "29584ef22bae524dcfcb2b4c69d0345bfdd1417ce63ac278c44d64311679446f\n", "05300314ea6de0ebc4d38ae3300439ebf168d846c807a056da94689e8357ee75\n", "5253a06137e55d9009ea9e483a5e4f62e5a81d47804ff9c2baaa22c07295e471\n", "60019055b439b367aa127b0835c2377d9bff8ddcb24190a07e11edf511aaf896\n", "fee60deca140fa776373173f3be3754744424aedbacf9bbc9c0f1f69e7248d28\n", "97cdfcb4a667b0a1b334153c7ea1443e31f6b661fb4e492937513bc0fcbe6548\n", "410923aa4c1eeb35d57162d1d450c9e560a74b36b2fcff0c0887ebb2099d6387\n", "0a311fddcc7a0bafa616febfa9f11685063eb4b08029bf68683889f9194d6ada\n", "0dc91c194fe0b3ec2d72bbd32c7518da17d5ff98f48c0342af55a888df013698\n", "a1c509d1415bb92d5c79abb73714a995da237c193cb1ec6ea56e9c54570cd260\n", "dfc9cce2aa5ab52d6fd153940d442349752b3665d0ce91312488b7b1786424e3\n", "e8ec6466e774e55f480c4760c0e1780b58e4af87c44d7f6b9386edb0dab2dfc2\n", "225c571df024aea1b8d43d813d09d4086f2ba1cb871821cc12816546ed8b9d98\n", "5e3ab24d001b3e7f718344c3b0a11ff1300a9e46934e0b545cfed93d219dfc96\n", "df95b85e39fa8a50298b7aed68660aaac972f9e362b10f55b6f2d3510c2fbae7\n", "2585e9bcd36ea68eb5c838525e80f3e27260cba03c41a90af4dae08143a2ed63\n", "27f3843d4327628d7b135232e652c7bc4a2617da15be415e027a6b9745566f70\n", "cdf69cf6c2180aef033234f6bd0b4a1df058d3cf5a728f0c75c70a228556e2e6\n", "1db7074c4bd5f6cf70bd5f82b2d90bc501dfcb4c764b3140a4cabd83a86f715c\n", "50dc8f474495ecb8dee665bf4c8d8a25a71d85732b389369e533612b299ebb61\n", "62da478a213a1b7435a52772d3ed57e1e4d1bfcd55eba80036a60976fe6e2940\n", "ec202499a5f73d427d5df7083889792e12f30dbc4030ad7b5c7d3f4876278b6c\n", "9251393308c37dcf78d661cbfb18d6f3585db1e75d0d248e6abc3d7159493641\n", "5a035b09f78d92f78d4fbdf4dd0b686bca9d0c699676b99257ca4fdb2edb2ba5\n", "37e26b24f0577f70d43493d68362a4120314ca2fa35e9e09117d798555b5cc3b\n", "ff2067529eba84eb382be3a349fed6841fe19cb111c69a884657e36286c97686\n", "25ab5ebf0537d68fcf3412990c986e49a73daacd1d1bfc7da37d3d5df84e1697\n", "c1c6cdf618e32a153d98fddf2d3286d35087ac0fcbba9b09b4ca8000fa65da0c\n", "3832ea606c9a17bc556a3895235048d516f8e4b0a0cf787a2291699cb04fc376\n", "a03e6b8a8f99f89e973c3b209df99220294addf4f802338d14deb12360c9dcd0\n", "0121f02195c88b48a27649e0f29c7e5c0a7633d35cb9be26a671cd15a934ccf0\n", "7e7743fa0449a08f4f80684f7a00008397b64c2879f711eaf42af41cfdc583da\n", "9fb974ac89e7575c2eddc1bbb1a9cfae60e111ef363bfa50c01b6dca24efe8af\n", "8f905637010a738def4572f2d56a09c3b1625f3a935d85b55d3897add082aeae\n", "ece135b4a221bcafd40d08c60fcc8c89025834dfe546e42d910a816263c9f69b\n", "f505c780c223336335e4982ab96c5f1483748840398c395b2d638cced1deb070\n", "c9b6f8e792b09bebf7af5569263f008d5dc6b27d0b97de3edb8dfb875b7785e1\n", "223d60a8cb3d3b94323c26c7099f483d6650d728f81d65dc880b2335f9c7cb23\n", "91d3a2ba2563eb779404a92eab8e069b318ae6bd8481ee8e0167256e7e2dfe68\n", "88325468788e33de70225bfd141db59b12169caa3abaf0169ef82d3d69e1e6df\n", "49c92eb6c711126518eb6eaadcab1cea3c81188895016d9dc87a06b493ea405c\n", "a46b0cb03d2e9f4c2751abc8e3ee96e0f2df03db2232cd8d6f1fb4794be2ab3a\n", "4a9d82f67169a77e42131734e6ad6b29c94466106ff072c7175ad6ac7ff5742f\n", "4fd702017461dd0196577c76daa9c49cb085ec98234d59c74ed76525205d6628\n", "50959d15c47429745871f2fd18aae01d62c7f2902bfef11aaf4d7e9c4292c8e3\n", "2f2e947b621933dd4bb3a75546e11c580d869c413f562c25105a250d2d670bc2\n", "08388acaa8b5e0055513b022fafff1699665ef76af6df25ca43f49e0349d86a0\n", "435bbf514450196ffd82bbc83dfcefaa1a4e6f1aa3d01fd5018996ced687ec3d\n", "b13bd83b37b072261f903f5c12ccf865099e9f986731170ced3ccd5263aafe2a\n", "480425ff37594d0ee4c744472098144a52a53023f5029eced278eb30cf8737ec\n", "576ec34dd872086607d31f91d9b3f62225119932fef70ef32f85436648eb379f\n", "c7ff72889d84242a8f8bff78c5019822571a0ca3417f51f25cbd86fc9aa055ef\n", "2c6443523f3b9fb3ed84be1102da40c00010063cb18d951e5c8693ae3461d7fb\n", "2b5320f2c4adb6d89b87bd5ac577bc1c2c74fd25e8628f6d44a319d9cbb29e51\n", "4659d4f99de859286c519c716ef54135dc2d2180f1b61504683db6e1e35fa9ea\n", "4bec430cac105f3e3344f67bb09ef4c652dcebb84b7c093e8cf212a7b8920ec1\n", "b4b4bfc3affca11f0dde8567bdfc48102e171c04893a746ade1ab59ac62e7dfd\n", "72afb282ce1ecc67111d79b464cf14087fa35a4cfa3538ed58d38e79dc6e1702\n", "db3d456a111f6606072fb9dd6f04cd7f42a629c5333c95359ca3a3866e7ff8cb\n", "d9168be00f425cd72bbe1cab55b378c94b86d0429a44e171f9ce3482809e5566\n", "5439af295c02baf984fb8c7bda6c1a077500e5e4ab712f7161e2a002378000bc\n", "d86ca018c3cc9d02eae605a21535e2936d179f75cee21c85489867c3a012c4c2\n", "1d71d40ec913c5524a476c68b35d32e0c8fc44eab24ac17d23dd1b8e14e68113\n", "93c2ab100f7af3c61be5a7104577baa4ec4fc2e0a360373e7bcaa98ced8e196c\n", "a40561dac88f1ff6141b1b5779a44cc0777a21c6a0a0086dfab3c90b45a131d7\n", "c41942cd26470a7cdec8c39ffaa9a92015e0ec310344e0d23c95a13baaf6016b\n", "7fd55500a40a4b4e0ca87f32c3dacfc1f31b80d728e3b9f60e468962227fbe10\n", "684372e6db4778628ce73a0ff954fab0be80d0bdf6210b0ce3ed5f7721b17c03\n", "440c90296177cb0cfc0cff5e42dce7c3be168fa36db686697710a03c007f0831\n", "a3f92d5f18668cd8c398c76bf1248c6197c3792e25462a2bea6bb696d670003f\n", "8782cfb4c315e83050c48fdb78b39ffc8368bf1d703725dcd7cd82e157106a98\n", "ace8450dcbf620e7170e299f4ea0d93883c761bc067c290a48e65d18b80cf7a1\n", "0aa11a0a28cd5d588faab8d02227816c69acd4208bbe631bab43df3666408096\n", "1bdba3b595f6e69a32adb70d6d0acaec0a46c8bacae50cad94cf6156342e10b7\n", "017181db61cd3c7051af674d204aa9a8bf4d7f39a1008a795db99861ec51955d\n", "cc401701d4cfb363591c0aeb1351386d7430b18bc2fbf34e67d34267786624a8\n", "72ce347c949538bba3bfea5af357d0054b36838fb7f28dffa8eb072578810e48\n", "88a558f52f6f16c5b5555cef738c2994a59c75fb7bd3806dcaaf37ba08c7e2ba\n", "7e4cbf4f3cf3cfd60659aba629e98a6ebd42935480065995a57038f289403849\n", "fbeeaf4c534e74ca76fe35265ae6fdddbeec9bfb02d243123c6bb63158d4ad11\n", "24341dbc775e242ab45b097581de39047c46618f3c4b9dcfb79594926ed78ff1\n", "3662e97158d344fb7a57fa35af88ef663ebd64c314fde70b7c52962b5049d46e\n", "0c4707504f89f12d1f5f8c036d16b43f3849a033016ed4549c0ccad808ddeff4\n", "9b732b50328279e572c2da003ed3bbc942a025e3748dc0f5e0689388371bc9e3\n", "c23a79a3986e741fa55be95500ef0ca96a01d1b8dc0a6836f54284d6db464a06\n", "c3c197cf906aac43ee372b13bdd9b2e2a00c5c4ec39a977e8874f212345d34bb\n", "a67b72179a947236d1e2078940e4fd138006792488cc4fe30669a48cd4dc4288\n", "924680944a12171f3cbfb3ed2e4518320fb30ba516f168fed8994304dca4fecf\n", "e8e5b8e46c265ac9425add47e5e8ba609ad863df666ade32a1a4a4a05521466a\n", "8f3f10a00732b73b3826a9dc1370f581bfa79544b1a2f7b33f77fcbf78b41212\n", "8a0ed830e911f884e94a0fef514e137dc1b4730d15d16bab2171fba51a013a82\n", "69ac46e53ea8caff2c6cdcfec1c5e74c135f2d9c82f0da7eaa6d42711f3e4010\n", "0e6261ae50014cb4e2bb32cd6267ccbf3384d52285ab4d89dfbc9446da1bb218\n", "849fc1fd556acd7d8de5eb615cba398fd36c00e47ce13cd2b296d91fad48b8be\n", "9985d2c9bb70563239283a01cb76e9af47692b0ab0bcdb8022d307d7435e8a43\n", "c0be7b8dccf2062cd8631989047c0f256d33aee98155ac3c7904567b3117fcbd\n", "1f6e8b8c4f003420115dc932a1aacbc5a84a7f7f3e57b894f2c4f61aa9af7760\n", "a150fee3310f19f6156a67fe5c399f62da3476cce84832bd5d341f6edb043c83\n", "03dd992aeb48b39c820ac300b8f1dc34a310f23cb91fadd5c97a9cc2f19f8d49\n", "debaa2fbf5b772e0f860a7c12264b4297a88ec570c0dd531e05630012eaf1dcc\n", "be132577f8f382f820b52a6ea2ae50453665b87e59928b2d28d780d919705472\n", "7ba1bb405d588f99882479d6d5fe50c7d954197d09ae4567cab8fa656e45c95f\n", "afd321f3e78d94ab3a161c13816f34e8eb128a1f43e8e056d5769a30d226cc34\n", "968521420bc8c3dff091fe294d21f2ebd3b6a087dc4f2d92a806eb2f90ab0be4\n", "d842538ef86e1a8ffd7194ab07fdf2f75676396a6fe757d23bf0c7e070b35655\n", "29571b69111fad790eaef17787be92f31c107ebf910eb5ede20818eaeac836ca\n", "9e8bda5f7b1dd76026ad9dd0b8b324aae754b77ffcd4396265d3e92da8e0e4df\n", "d63303871c49e84b63007b452e90486e4a795a556ecb2e35a5ccd5173db25fab\n", "22f138cecc76a48ee9495a1cfaf07f20a3cdff238cf8c102d6397d1f74dd1463\n", "baba044a8fd785259b96c9a61629d6a9a24b6faa0ea5818821d3fbf9c9e30e07\n", "5ff3927fb540d6521e8b362ecf978da0f9c76f6f331a5d3c7d6c838c25c54704\n", "201cb7a7025af3281ba38ba676622f3c95d072d4ef9d201196585894465563ac\n", "507837eeab4520a19501b8922c464ffc74200b56d5aa1add9ab41098ea4dbdda\n", "6d7cecd9422c475288f8170d87365fb167b6af8c4829cffe382defee9d1d6bf6\n", "aef0bae88bae71e99e14c6caed65a0f71244a0a07dc6c428bf83fa7ddd10320e\n", "658fc04cc40baefbf5287155fa5fbd5c3466f448a2411ed9d0dbd46b904298e3\n", "c495d47a4d986ddef63ce3c292ac54813004a4f5bef35ed5384b0eff742af968\n", "a5cde0df630e200e0dceb5b693a5ce8696d4b9850f63dec9250c603439d9c152\n", "37dedff91d8a80c65e3cee35a53bcb0791c43f17aa5fb9d02fd0adbaf79c8e66\n", "a6f2debe69ad1436d95ac5b63c86427c051772b7b806e4ec00ffa7c487bb76e7\n", "7c6a87b7755efcfba0aa196344ff3d944d86286365ed7746ff149b78b3364a8e\n", "05a78e7668f1415eb6bb65ba4be41ca2a7a5084cee2927ce854bef64871a28e5\n", "a7205773cbc7abc1edaf31c5e33a8298cd0fc6ef203732f7018e199f38d21ad1\n", "582e8f833472a06f30c80f999151f3a6a243b6c3f9f4ff03276f5cc90b8e72d4\n", "0dfc95b3a29d4199efde567fab985c400c0d81346feee7f14a987600dd4d04cc\n", "52e7ae30e9570b787f1b94bcf96318fcd33ff92493c39aef6710a4a8a539fef6\n", "c55b09bb56c6faab981c0039cc232f41d14fef54e756f0a9f0bbc7cc068cddb4\n", "d0eb455c29744bb5a773dd52d1d0f3be2f358682096c21c4b3c0f77c0f9a3e01\n", "ded93758fd0115d8672f750640391f14b540754af7c6d94dd0ebec0f044e55df\n", "b29f1d13195301115021eb4430c49ea220bbb97b1a07be3bff0015ab1cc04276\n", "092e4da37675226a90c3a74e59b57f5f0e40c59962718f5b6228d881935fd3fa\n", "9deb375fd857431b05ac400c594bdc6c5af666557efbe7720291249979a755f1\n", "bb6e5639298454cccb4e87153bfbd26b70350922db323bcee5372a6843c218a7\n", "5bafcae3f69b30b50ba8d1c3c89e46eea803c3e387d3bf1b17b888de58202fc9\n", "ba817d39f104b8d5845a92f8b666a02a1feccb356b78dfd581a8a89dab04e3b1\n", "c247b0836bdd15bd4572254d925a5b55b916a6578eeef53e14a7d70538fb2c12\n", "0fc3866ecf7a72ae8e29a7277ec2775457ecc2542b75dd92a9464f231f817750\n", "639063d780a373b776800debc7100b4b0f82be2edbdfc6f52d73f1ac0db55289\n", "5f0b170c51c0e4c49d8c0dfa29f02063e46235c81879d2fb553e36d66526eebc\n", "acfaa93ee4e5ee84f1069d6bb39f00455d9c3413d9a6299c2b0176167858a989\n", "1993182bccc44e22912921a578cdd5e7b4f37b584a92772be638e8e036e44398\n", "015e34a53e10f46154499970a65e135fc931d610fc4932e47736e0882fd4a966\n", "6ef60c77e0ca7e6f5a35c505c7073c1f84620eab6e15c2e43af7fe1bdf08b669\n", "4488634a696dd63aba34288407bcf8e04e65521903e92ceeb6d810de8f576258\n", "19457d1dbc8dc94351c149622bdcd19c97f60f20c50f6ed0f47c6e3f9f88a9e8\n", "a7d931164387fce8fce5909c8c5074c93b436e80461960ec8848bf878a0936eb\n", "7527d0ea32556a2998d9489d0ef1277315cfe2ebdddd63fb36c645e0db31f940\n", "54aaac78ded4ad0860bfddc45843bb51027715ab41811adb7df179ac3148f21a\n", "966edc443a2cc99dba4d94c5b5edcd58aaa9ce3fe6ee73dae97f79b84d67e2a8\n", "154c9d0283593591df10c7ded61866ed5ca7541b83036b1c6d94d0586bb742a7\n", "8e026073f070b32bce9af397e3f064f242a26172a683af17ac7f4e1e665c6240\n", "5ce2bfd0d9123f5eefe2b824251303a2db16322e85086c4a5eef7aeb10117e0c\n", "e7ac2c0e557acd994efe6421d37c721d1f59ef1600382f2f180ef45705db4fe4\n", "000e7d29dab964378959fe31ece7af0e88e856c71d10405c55f6ef17456ddc4b\n", "f3656a02e411e0b50c01d6aa4c1a35587afce8d0ec28bf24cb6075f58d0f3dfc\n", "d0183fee6e6951c41e4856405f4c30ed1b6c435d96e1e185a87e17aa369fd6ff\n", "58df405da333f2aa34487ad75385ebd3c1c9ad0ce745c9f0715b1b072f28b6ee\n", "ccf237c572a2c6659188b35fce5093b07da219d00bd4150e53bb9f8f10a0b5c9\n", "e04cbc60e2083d559223c165ddba3d8f5bca0e045698a0d7313f7273b71dd49e\n", "73d210d8e1da9e2564768b9f432c9700fc67979d7b8a053dca3876f0c558e4c9\n", "a24ee852550562c2d8f1a39bb2ea201e5fb16d2cdee5c65ee599d577dda0e02e\n", "0537c6908ff13aca0c01f737dce787556f0923d4911ec2661d9cd84014d92463\n", "2e258f474b327b9176688bce45994e060a5474d9479992a1e07cc005cb9218d0\n", "d797a6cb50f309082ce66a8ef80b6801dabfbce21b120edea48535d391716129\n", "e62d54b10730bf24b322c5e1cdf64cd355a9a2177cfc4e318d5c088303ba36f4\n", "3aeddda027fcaca01f331813e67c57256ca90ad5d7d4853f081a8ad2924796e7\n", "38f872e148a7cddaa6a3f4c7cae37b731f8cfa0037e3808c5cbabe152d394f86\n", "fb425748ff8b919aa7517dabc26eef0e03dcf5f23c208b02c36d9379aa1d21d9\n", "e50b608ff4b27cf4d09dca5ccda000911f3d15f7b6d9410a204b362a55556001\n", "517300f10a9d3dea394dd010a2469dae7da50f452c15f2eca9a6705dedd8a793\n", "931aa07a05c73837e38c79dbbc14e00506acb7ca1a0dfa3e6608b033b4c0a382\n", "0cf15e6820e2d6ca3e9560784ad42a147953422b646ec8731bfd33ad7129b556\n", "8a03b1c92e0f51454fd8cc95e52d144a7539c17029d95d6f5c58f9224ef2908f\n", "840fe5bba93756cceb3c59f1cfbc3c8b252eb48146e6054906ebeef4721ddada\n", "5eee6345e456a7cb9896989ed9a440a5706569f7248bf7490379eccf0e403f97\n", "34b2303ab453aa618f1061f122f3f3c2f479fa651f016d48b7fb04a59cd40b99\n", "a57320bb8c3257508223afed3cc9917c3ed791016b0f16e60d66e9c42cfce1cf\n", "0dbe4819ba34dadb210fa97f8ed12ee007fe8ccd1e3b06342e557891d60bfdd0\n", "b73efdd7ad1ce81f275351a80d0f1aff406169d32317cf648a6f387492f37d4b\n", "7884c0624da830f215ebb056f765c6f2e051b957098a30d049e8e96e77c5676d\n", "2005bc8727b6d325f43f7bd56fce2bfad8f3a76c93334d669d4ed13764f222ea\n", "85f90cebd3b700ba15bf29b8126a5d82324b3a5124cdcd728bf3f04cd5559c6b\n", "8c80b367a5fdf226c56729fffdba4038ea0d58c16a16c55ee6020a76a8c5c81f\n", "a6865a9b9fe9e00a6f5c38037f3ab2e9d5a9d0115e65a46ec27709405870eec5\n", "a9484ae4bb69bc304b288bf944446cc298540c144147dadef6218a8972afa132\n", "1962222af4b147d2955429fa9644b7e1ec57c8584e0425114594c09417eabb89\n", "1e5d283a23b8aa20ff8d4413291a7ce1fc733ef25f9928ee408ba4e71cdfc9f5\n", "b7e7f6159ccc45c8aa62ea589971be34f8c88986c888ad20e7a3b0b1efaab850\n", "1a832b5e6e9a70e431769d899fc74390daeb1b0a1725bc94b04470b625a5cf03\n", "1b14cc31600244a52d56c763dec05c43f057b93d16bc54efaa8004b774ef070c\n", "651d0f165ffe9901ef1f53e7a27ff2c954db5102552e544ab821b8a5ef5a6c25\n", "06913d78f59320960acd2fd51071e5c813cdec55742054067b360a56a79c1f19\n", "fc8e2cd578ac1220583137b2f23eace3e7127208b3373574e562e0cc5cc1d9b6\n", "c19b62ad5f19087cccacf67e6300ac1d85c49c18edf989c7a364621bdceba992\n", "d805318d305a0b885159e142d8f7c98ff736c9b8bd4941a09b37a69b58e3d219\n", "98a488d7cac59b1f1d4f14a357b61d785d33afee0b9ac1acc2e3eaee12b20d1c\n", "a275fd801feacc0a85fb6a97ae9319e4599e924893aaa8f6ea6869103df7caf1\n", "8978d5b57833c7c09be13689ef8117a981a6d5f4d3b81d25feff41f790bb29ab\n", "1d744c263c98423e68c4e0c183537975ade586b4b2078757b1f318566fce73d9\n", "8653790ab3c35bf6db3c88a0e0e1a051cc54d5eb33e5a8ecbf961ba5610614c2\n", "0a403a95288a5e1d137047f31aec14e03eccdc2647aa6c1b67182d72148a8f66\n", "3df68ac3b228e266ab6ee46644be6479acc290f321ca1e4cd2ae24ad3f4ab7ad\n", "595e1d699c601fb4ce53dcaa101daa6be7054a9ac65f311f9c0bcca78985014e\n", "34d0f05d1c2ab0c2d96b493d0aba5304d2a984906b39932ec22c6daf6514c104\n", "382c74565e0bd7051569a36108fd03bd17e83e15663d805b1f95b868b71ec3b1\n", "401600780b054c82e07c57623761b6a8494112376ebc6206a3631a28f2505fef\n", "ddbf86bcfde2187d3a8df11e86fe0024d82764d8bb57f79554ad8bda8499ac7a\n", "af7c91b987edcb2033c7cc6359504604d4320f8372dd1f110446b8542c4a1a10\n", "59fada7999095c6f59f303c4b4de1a12e755813483f974ed063705d9699632b2\n", "bd938288a628fdb3a8a20dcfa0de2ba0e6f2a511fd9f12d5782de4edee5fea60\n", "bad18f937401212091c22a4cc3d6e37ddc860c4b510efe8d1270052d53db9e77\n", "612d3fb0be35bce2c3bea5baabe66b7502ebbcbbee2ad706f72aa481e8122a02\n", "faddc676c0aba29c8cc5598f1f2830b28f87d6adf80c755bb8fb0d057e2bd969\n", "fd4e024e1404bab866e24b8fc0c6c86eed58c67921b7b7d564e24f792e0e0706\n", "f5f5e5de8c1eb3404084c2a6d7d97b0db6d65616d1912281bc524ec07bce3cf6\n", "3933f433b7793d09773ffdb5922823b2db1984355e091547b9128e751df24b48\n", "ff3d1cb4c8662a659516bc9e63a447dca1475c79edb816cdf75634ec0338e2dd\n", "a88f6a5b0951ee117ac1994c377ea6ab971031bfd875c56a66a9499be841d1f0\n", "3eee68507af00410fccf21d6baf26f70bd11b407f19252e86c2838118435809f\n", "97c8d881bfe67e83f46d7993a0412be1fe6e0adb0a04c9581760edb053106ca0\n", "2f3d30c735b55e4558407112f8d63f27028b7caaad3028fa92381f2767cce0da\n", "19e1169e48b33cfc049c55e81afebe2cf9cd8b38caa4f63b12edf79af9f8138e\n", "8330b2ffb72d7c1137f6d8518153201834f596c2f6e4d193b9b5084535507f41\n", "9175b25e7654ed9daec139e68729bdb16ab4c07c618435c2011005f41a540563\n", "c221ca92611c9160a0097ee363dcd26d9a9c288ea69fbb27231a50a222045224\n", "cd1fb71f629be046923ea888e46720f031d464b1a523faa66f2bc66b57b70dc1\n", "000f56df8a6566cb91770ec765219970fb0c241b19211965a0630bfdbd868ccc\n", "b81f198c9e80226622eafd3f4e6db5fd8ace42728b8c6e170d4354a09f431b37\n", "156e65a0f0e9df888062f9237e4f1ad8409c42310fd90e713da73b16ed31f6ed\n", "d278653d3ddfc6abf10485d8f3052bb487b4e9fd75aa3608407ca0725962b507\n", "351e4f699c3ba8687f49a4c845c5e6002635527230a320599210c56687504c04\n", "69ee3bd471466827e707aa11a99d4789fd4a4c01031d77131e3e41ad68ec6105\n", "df72a2c05600c936ac9748bdd614177b1aa843bb70f1859d2c23f7a73f16c184\n", "181b48485f87b0443d20c68b18645ceb388687338c3f9ffa1b5a8c8011b59e65\n", "36be136c02d15d673d6ee26b8a96ae05509458dff3b0b4a8874cb16a94026b0d\n", "58c91bc5230cb24ea3488aaf0485c5220ae6d70e8ec9e53a53e13e11f7bf50ee\n", "d167c907d5a49210715c72a131d1e4bc01b748465b5ac64bbb41ae15414d8253\n", "5ae126087416907562fb2d92d30a1a4367857f46f0178d1c27ff00c0c5efffef\n", "a83b02f2727c5099275fc161d38114136c5753261d2b159b14e12fdf6f9a5f13\n", "47bbd4bbba812b45a78dc42abc2c186db36e7fd18588c9c5c3cd72cf2857c5b7\n", "73e36a7f40a94273e4c4303a4b2273b7e6c79066fff6ddd16a1f71e57517dbf0\n", "a195515aac00a5856a94d4ceee53a49ff2befb25baa229b2974772d5766fb53a\n", "8b073736ee1458c85e7979c8b5ae91dccaabf42d1cbed0590388388c6a8ac047\n", "7e1b4d91a81d1f17a21937c5003d652162b4737007daee552aa3341ea9e760bf\n", "4e77248c91a7f128910927074d6d03995c0994f77c15b5d8df47c67e36f852c2\n", "1b934c89d65ad951668d91272436f821f62ec8984023e331f889f7688ecf8064\n", "2639ed601456e21adfb872c953a0ae9ed2ee09040a2675e4012e1fa9ad6a86bd\n", "36a8555ba14263dd226679fb6aa9ecea1540502c4002b7d55bc9de3b7165a8aa\n", "dc4b911a3cc3c81a49851d6aee637bac00b61cfbfb556ca29c01aef4e96256f9\n", "2ac56865cfa86192c5bf1b6b9db9aae6d7fb2dfd0e7e59089641f9b9376fb9ad\n", "66b686040e10f8bf2ca00921b8986bdc8402d94e04a00964f55e0f99524357c8\n", "d18c51fc4467391d03d82b218a7ad11ed4d486a33ead012124e4bddde760b053\n", "e6944ddc8903a78882c1cc3280026b61a13a6f651904ad0f6574852b22107682\n", "6a661762fc735bb75e8ae37e0e68ce59dda2ae82443320fa330f5bba3ffff571\n", "12b77c6e6dd4a597625da34e5cee020763f17bf3e0e2dba393d72485b5d3a4ec\n", "6af59958075f4489f14eef7bb6de7d67a6988dbb24e9de43bb93c36141d2da1d\n", "81ad77253cb6aadc8e20aef708d2d9a57299e7dc13800c0d80697e8dcd264955\n", "96d7eb2f12795a74a2593038f6657789179aafba2f3efc3df5f9c35ba27f92e0\n", "6824a87fc141065d2f9a1f5cc33b6db585983a25a286822f0d57a8578d129f44\n", "c6792e58f5a3e1a537d89ba36aa94b8b0a7d217f77090ea93ebe494d1f3aa6ff\n", "38a92b562f9669198c1339545f3d670b4ed53cf0806a12e696561820db18bd58\n", "f64c14c791d21d68f795d7f99a84fe8b42b458cee1bfd6a8da6048dc43dbcfb7\n", "1b0c4c055d2e700d85bd20284d917a132cd0aa6b1cebe3a1451afdb5141c0735\n", "32d8d2082a63229787cb5561c3b4d7f2770a337a67d35f77e0242658d5e9a570\n", "79bb2baee055be42f8852f4f4079129242b19551bffd10c13644233f8d45ee42\n", "54d8a868cd6a6f260c43165aabeee9b63f0891a53e8980c7c6dced448d725b89\n", "68d93f52cb6d92df510b8a9d620790c265d04952aa161ccefabde40442d97bc6\n", "9f4138de2ee40a3f30d1a3b1ea4c8c784fb9e2015821aa9d90f42a2401e40ab1\n", "46ee8cec9c4d924485e357484113cab16e0ca069aa3cc2363936c1b83edfd8e9\n", "f35d8b0de74249f38258019a9f7bbb2da91d70a1fa0debb2729113ecf9f4f8c8\n", "56e4512b98237653b53c92fd05c45e992418225d3a765361a269efb15bafcf10\n", "95b46e7a09098e885ae895d94bf27722c684979e5a2cb74cdd1a39368b1f7af8\n", "f963fd60921f1a9a3304e8e5d1e02db2d3ff3cb4a8682f8c44edb7f85b48d92e\n", "f893aef55ad49774552360cc420567c26d95ca4f6220409d19111d51dfede9e4\n", "1471a8e0ecad2f7ddb3c3e9116d647a9c72a11c9acdca79ab768bb9fd12bc341\n", "5be85594a6a105f96b2cb651f78f6a17feabfa74b91525f3c5f06783c46659fa\n", "77312e3607d7c4e535815f958562b0ca0c5cc3b98c0cfbf617a5239217233c7b\n", "9db71e90d1a072ac06de2370f56bcaa4e4cda3607710e19830f1581dc6e05184\n", "529a6a4f1e9e51238110bddd4d1c85791f01a4981e69f507a80117212c1f1ffe\n", "2a386d3311312130cc17cf8d635f13fc77c6622757ddb14c16eae8236617472a\n", "5172eb0cd990373c053b3df8bf4306af12baea8200c93be92e848687cef64937\n", "bb1ac8993be95a67f05d69edb6672ae57ff12ccc99e4040ecda031e9df93371f\n", "be1c62158d3feefd0d259bc33a919ea95bb2d514e21c893d7f5cbc33d96daffc\n", "941b30a945334478d87a49fa380108aef48f3ea7923c185c94530734d0c4ff12\n", "524267d7e1fa7a58ea2e8195de02c5527165708931dc9b8912e909012bf51b65\n", "9c060ddb61dc4962657105103b83fb3579742de02f724fb9f7ad74f5216fbce3\n", "7b09e0aa1c51baf3374fe05de4a4240e0bf42374c33fc7e8c32e44f06bb67bd0\n", "49909fc2f8637ac9f5ab189bbebc48639f324efe3748214deb2b1d538a39a16f\n", "0730e6d845861171053f78f15aff27c90dff055f08ac007e9f30b926d9c7a93f\n", "a6f1ac83025ac9a6ba2722cfec19ef189f74f8ef10add5f1619c2bfc9027a996\n", "61b9e6f7323fde0792bdfb672e6f2ace33f817a106ef649112fbfbe6bf668754\n", "aba37aa0833ccd7cca4d5cf142f8c2a16886a2a2395451aa0a847b8cfa62f59f\n", "4789a5eb2aec21bfc5efe32fc10175519cf9d4f12b189422d9b90f1133a98ddc\n", "890b0b01f24440444d55d32dd89f0fb22522d276b5e2100bc3e57ae498ebef7e\n", "390b4306b56db00292be40e6da6e6dc32a52f6c309543187c67137bb5ec1e00f\n", "adbecc8b841c2ef9bd7efd27c7e427e6dab930b98e0fa631fecc3246e8f5dbc5\n", "80bcf8f4282d04cc42d9b3bc175408cbb56858d93256d2467fd8c8b7d447e14a\n", "0f3694fe26daab14c9d1ae9980c6e436600b487207d38477b5bd03cf8406204f\n", "0ce4200443d78bde66b650b1b6900445d0e5b465a8b3b22875fdac086d034533\n", "9693e512eaa8a1ccfa253768ee320401608fd1b94166c474b4ca73349bef8f6f\n", "943abf7d1b2b3ccf52106337a9277fff05d10f27c142ca69e7d49ac8e6199778\n", "336617fe2c2a163a2390342022427c5085cf8ac1f7d725bcfe2c26e63fa916bd\n", "c005939f8d8fa5dc416ae1472c87abc346c48d2a401604e973930d22faa02f79\n", "d7ae9d4252f776a1cff7259cc1e5aad3f429b1bcf56ff6911a3e591485467968\n", "0fce7afae359b9ee2a2be55d9ff476f75e98f1d4f5860e0e56761164effd0244\n", "cc85f76247afd47a37e603786b0f3c1b4e3ae268d37d0ceca4ce381efd415857\n", "004ad74a456d01e3a57b1adedb46a7afc952b796f3d3a66c3b6c493c8bd4a721\n", "f7ac142a3c2dff5189e53a7b7589c8ba38a1d5802540f323309b5e433d372327\n", "4d91b5888a94591f5d671a08344939249b0d002b94b834f9cac5e3d57524fbe5\n", "f8ba8f28a6e121597eff0b879b48cc93d3546878c53f22c430535ba081da8172\n", "6fd98ed91a3e65043fb2e260b2677aacba3d8bb131fc55cd6de836ca98406e0c\n", "c0dc978561bb2719bc561c83ec18937302a3b79c01a126e27379d2a20032a1f8\n", "868e765955b6672cb83b9df137fbe67703b057d3d0c020f6291e8c26abe758a5\n", "51704ed723adc5849a150235f782d7b5695918c2b3c3f9c7e1c5df208d0d826c\n", "8240b0e26d094f2c3efc901f9e781ab86b87fb432407841e9cc03372334e286b\n", "83a378a4c8d03a4163fa75c3d60d4271e0e178423b066c4c5b5f5dcbd0176b3d\n", "9e1e7f00db9662bef14db8e2e87a1217e5846c3da7ea7dcbe5b209fcd27d185c\n", "693afa866260246e5d395bc7c1d90a7ae50d46634de6519efed3c08bb2905f97\n", "e4301540d22763348bf378e65fb7c583285e50563c0ab6cca218a50e0e788dc7\n", "80b3deac8fa33277bc005e11b5e84b22b279b595dd3ce054a5daab125d30f5c9\n", "7db74e9c7c36f1013213f3e83c9976d381a3df41e82c7cc434e79c674c4ecde6\n", "cff20a6ec22cfbd0c0f7bce3b134471dc0a6bf3c9383581b1e7a69ba1cb3a5f8\n", "c6670814f495e634b78ba860831cf877ee7cfa90f26050d90af03c723c275ec7\n", "67d7fefebcf60b8b13fe2969f711aaccaeec070831891ab32850bf22cf0a15c9\n", "28e0faa30a36d2b23157cd5710c5969a5474bd28216a2306a421f9e1d250d13e\n", "3ebf599f6ed52ccd70670c392ded24b9d2ad32d6593bec0facbe0cc7992a1e72\n", "44d8fa2a9414a86ac30cd7912e20802e13e895af1473e14c4d2ffb85feed2db0\n", "2481b0d5a27e1649c2c3b53b53108a4d6747125c549a07bb02856e4b51d8a109\n", "b359257c8be0cc3cdb654dedf82dc43e816f8c1d6fd66d5ffa6709a125a78b4f\n", "9eda11522295d576d60d317aa16556daa4073d8f845cbc347d7c90d283a5dd48\n", "30e615948320bc99e6b6e00cd3d1fd7504178cfc6f6495e0c6f3fe6b8720f5ac\n", "674c549172b67f797f9eb5b4a5c00355c7ebb66f265c13b5ca1a68765ed67e72\n", "b175f4ee6c5a72512b366fb6164de768d0df264f58223af004224f824cd720b9\n", "9b23a0a316f5a3b34ea61fe4032dbb6ee172695471bb19ba19aeb3b13af30a1d\n", "2543c04a0f966d73faadb66948123ac6441a5326656b74bebc4fbb585a6c1f76\n", "ef7e3ea0c855922f54cf2f74c27c44748ec18aca5126e59bc3c8bcf466abbe87\n", "204aaab72303db7cf5c5616f05a1387ee2ed7a46822726be07465377d59f7995\n", "12fcf4020ef54010a49cca02df8fcbcbc57f71adeba98f240d9747bd3828cfc4\n", "024b7ff99af775a19e2d1f87d55bf4feb439e79badbb8ddd3519c7ca0a6a96e3\n", "82941cf098c79b1f54694a71bc78b49e5abff786c9322644dc714ee43d1afd25\n", "d6855140dfc2a8211820e3fbc2202f30e4f2ac7bc9a051b10d5e125d2f764775\n", "e96489c33e6b04d178829ceb27af2e4ffdc6f9a2bc8b8feead0d6be322e7fd6a\n", "72d4f9e0ecd981617aaef7ef3d824aefe6ee551edd84a282728979bcb73146f3\n", "15ec76d6d7e75dd04598e77aec3926daf1d2b8a93de3e15d39a0cb03d1888f84\n", "ad912fa8e33959b464b2559ff07beec56a45c8ac3fee51012c6892dda21676a4\n", "aa1d2c4263e40b748a5752dcd14dc0ce70c200ab2c0f543a33d70b7c9ff04917\n", "7c02d05ec4526e1f5a3f35dfd82ccd384f4c3775952e4349d4ccfdfae75aa4bb\n", "24274ac0e25e4bc175cc1f5f37765017416a443ce0629fb5589a4e0a0d1880b5\n", "5a43a033e19dffc3072fe240ed960ecd3b1a14c076b2d33ba888e91b6a56b9a3\n", "4a7b695541f7645f37f210fda1ef10be3dfd19fc0948fcb40e3b2484a4f1cfe0\n", "45964f6af0a94abc5d120ef0a635be85e5de23c90e30bd3b9ebb32a8f19f2c8a\n", "8fe828b7dec1223f20792fa3a8cdd42ae9a34a3504c4295660ea397d84270d80\n", "2554e51eb3313e50bc19c65ef4889650cf15a83a63a903e85643cf11e07ac9c9\n", "a7a54f1d595c5a7d3ed1cdfd0230b049b80233bd33443feed6e1a9fc2bbaed69\n", "e620666a8b6db2ef1815003582d25f6e0ba3397c9ca1a504d70bcea0cfbfdc50\n", "e88932e2eb92f6a1d11f6b89e22b2cd03fe02882d029ffe601940d6480fbb2b7\n", "d92d499af19530c3e5c18e34a32e3ac68bd46ed333b630f6f89d1b62aef2e389\n", "4baf2c7cfdc046794297de61baa8abfef4659054be894ac7b28896a3a79fbb6d\n", "b6b8a4a3212b997e602d4767a11269cf583a8fb5d5df3563c3242883939798c4\n", "bec5fbe7a86d382c93e7ee4d517292a3fe4ccee399b20755e3f010c01a4c222e\n", "bd320c94bbc51437f23229ec4b6aeb121c99aa9723bfc91b7bd5f65e415eaca2\n", "cbd3dd808475240c8f77f70b14471ccdb024cfd9d5fc635975eef174fdedb772\n", "024d986f9482a9805d190aec285f85ad9f52059b0ca67845cf809c6bad407ce4\n", "58d3bc4e5def6baa8332cf2c191d695739469150e569fc86b8e6e8369df597d2\n", "fd2139931a698c4391989653de4f3f11611346f635be93a4134e04e2f0e5f596\n", "ed34e97611704af6e9e7a9b121790cdafbc5f43a46494bb160b15445a0793879\n", "9ca6a1d513917ff074e12c7e8b1eb3b2243b37c32d9a496362a7eec1707deed4\n", "3d087f104c9ec066d760074cf139ec3291cb2c54a78e126ebf3f87e64357e303\n", "0af01c4e8d95b36ca41ae5a1bba87f4cfb31f7f01bc8bb05af2ae6a73eb828e3\n", "70bc7c795811583ccddd03753e6499d8d4e660bd19f4c760edbed0b0018b10e7\n", "04f3542f3be2edb6ecbaf19e1373fc2e84da4976abadf3fc2d32560bba09bbdc\n", "25400d6b558e4dce7237208aabe52d9ecbf210bcadba2950c16c7ada4b3a9326\n", "16d997a8da7cf7e8ae5c02a99898d26fef57207a4a3b4417f4cbd20256ed9c98\n", "3ca7af94d3bca41d0a37a77040556165a969e1857a0abef150f1436ff2d976b3\n", "7aa0dc93e07c6aca1f672162e95fd17ded537cd43116182ee757adb04efd7411\n", "89d5fe4af7f6ae6a6793512f22daae9c622e43c027d501ce06dd74de4c73e35c\n", "ad4ebc8cae524cc38e0171df9395ab54a30be360ead3b78fec9c4ba73c169254\n", "c479f0c6d19bdb090e44aa5e2671e86115f1523ce9ac002a48c8116394d0da5b\n", "c78408f9a7dd6802297b9d6711336174e7619c96c7ffb4c210557723319f9430\n", "5a00910bb2b512013d7b5d78e047cb3a64b724e9eb193dabb29f13e95531b250\n", "c3f3522cef6043d1ab83beb75d261e7d48b9b5dfba0e531169f9af0b44591c11\n", "457586b4ced60f3e3d93566e2fd9225324969ac36e673cf930a5a180f1d37042\n", "82226f549655f49c3cd52443f08ccaed10c65bfba219989ece4d321a938bb2a1\n", "2690b9e9bb615e770a38ee45d6f2f094a168dcea22b776df1a046e0d26404aa2\n", "0d2832a57f5d3ade05f34090edf7e95bfebba6d2d84b2886db8b3778e772f819\n", "559b089b96c996374255aa7fe79944ff9462f49cb18fc124f8444ef49120e21b\n", "4e5d64e2bdee847b85adeab60f74be97aaee088cedc0e1ee107f6a3494d11770\n", "cb6b4025545231ad9e1b9774c8eda28ff05a872de2df6b143b2a19854577203a\n", "99b86c48e6de9d3f2912f05abb60b52a58eb7bc47b2d4b40c0b964b38ed8965b\n", "e9ccd565f073a441cff75fba92abd47a5e2b249bb449bae6ff9c3beddf9e3740\n", "914ca7af63bd416025ece997dd44ed39ecd64246e2babb422c24f9cd5fdcc6c8\n", "101c9836513f516cf7f30fd703a6582f24a2f434f508fedab1ed47fbe42fee9c\n", "14f491c1f2fedcf6be39f67deeec7a2ff6828e8ac57edb79c67839d5bca0d3e0\n", "716b6997d61085282f8a348ac3ba081054585de2fa3a69ecd72bba2061076d59\n", "049f5787c1ba4195c080823fe63fd495f3947bc776b0628dd66ede91dd435788\n", "e5c49eed82d3013f557ab24bf107a69ce5e879b86adc48feb605b1729c168ea4\n", "8551893c6f2a6edac580e4b48ca83301c856ee8c6e745c1c28cdf502ecd92a11\n", "356d144121f60d80645c176488ac44844a86407d8e416fa25340f99e01bbd4fa\n", "025aff0455ddd353a8a76acb171f87424cd75f32fe7a01b53fea924d5477c46e\n", "ca72a4d8d9e24acd4be49284a2ef8ccae1564f2d79dbed8bfb497a16cc440c46\n", "4b6a2db590de21ae7f4d3c142637308d056c2d956ca9b6affb9205c120827cdb\n", "26ce76da6c92704d46aefd381172e921a436f1eca400fcad6f5d8bc3fe630ac4\n", "dedb3ca31e72ae6ead5be6d7b9664b37f490030553f31b9b0ad3a76a5639b67a\n", "e8ae15be33e4a8ad1de8f766c82d19664a054baa2972da6b10246a5f57151c71\n", "2bf70fb2f2cb853d2dbcc0d3da60c454993f76ffd567f1e233366570c3b63184\n", "a066f5a54630a4fbe138d989947397dda8050a0a78193bdb2c1e985cc6c7d3b6\n", "367abc9cf422451c36d1c6492d94be9a55dd5e5320b2fcc6ca510d16737d4ed7\n", "9b08ecf0b0833566a4b1591b2ba306915c52c5bd6544d6fa63e5212833832113\n", "ff65d1857988df776586517484580ad90aaf96d78e1e2d8ba4e2c7abf9681425\n", "459ffd1dc8868dc753077a46fcbb5f133291fb1e0d951b18f715e7e3472cfb02\n", "320a67d25f66ac7a4badb887d78bc3d35c5d4ae225481f7f8b50f6ac0e14a492\n", "737360de8b521a0f8135ad797cc7b704590f97090733d560a8c66c7b36226bf4\n", "5e58c7ef201204f0cac046d21f9c687ac710b96afacdcdede21d1c97cf842f2c\n", "cd410465a031573805346a4f75418a7f5769b1d1345dc22dd96f70ef9d330f66\n", "a232a8c92dabe6bbec9acbb028e114b0db31bac58e68b0d46216a83330515a39\n", "c7862d3fdfb60c6c03ea396216388f1117a74610048edd66126d93f1cde20a44\n", "7f89656f0ba8682f9bbafe06593badb859bfcce6f4b969f1fb19016dc039b224\n", "681581fd68530ddeb2971447baee970320d9b265501bed0b3a67cbad18f82dba\n", "dfebd47cfa92ff341135404c97b636ca2bdb0c12cb23883a1b390b0c5acc9a3e\n", "bce7dfc1939442dda51896bb74200b17e050a0021fd3865047d3f3f814c65849\n", "d0e7e766d9d8a3113a55c0eaa921852aa391297ab66ebbb20f7ad79d28d45800\n", "f8cda23a7c69be637f2c3b5ff4db1a29d0bb8c997d445f44ac93513d67314b66\n", "e44dc7d80196b3a2230a658a8efde2c9ed135c068683914f36b9c20c587ada11\n", "5ab058af915442421cb73c4971693fc479072c244450e18ec81859ca414a1208\n", "dc7dd2b61677daeacc086e00494b8a1026a333582cea686e20a9e2c39b4cc558\n", "20bf618f9062813da16ea1d4611c179932acf43fb2ec83fb42110cdf21d9a4f2\n", "dded4357745292250d3b11c4718c61d20ee1610f3ed1e7d71b6c25737d3dc6dd\n", "657fd41fe9c42c425f4365fa74a058bc7eeb585edf26c857998f57b489ba6501\n", "020aa6ef6e6c296af4b8e72b0f42484d96fc799fe6a2c7f6bbaac281fdae8431\n", "46a8d71b7d790a4177bd297c3a47dd48cbe8d6242a5e0dca5b18c5c9ef51f5c3\n", "6087207c744c8963b578e8a8e5c096d4bca5e5cc39c97bcba0e70a94622a6ed9\n", "be2b61144ab7ef181e801bfa0c18db03623250707ba92725ccef8fefc2a52ef8\n", "3ddf33a28d638adc431bf8bba39cd07f421b000b43d4b5c10ebaefadd81e53c1\n", "54aa18d64791d42ff0e148deab897ca3b37d219a0bc719ab2119404c1f8fab06\n", "bd47fccfc26039e53fccffce8bf542658d41154f53703a8504ec50401070c618\n", "8fa3afb0eb0cb4e9a8900b43210c4b90c61b443abd668e88b60de8057c2aa2d5\n", "0b55276078a0be4e40ba8e5c0a6d51430b374018729b3a6e9f3ada8e05099313\n", "fed295a6b500215bb884c9014790c4a0c814243ad579881491779b863f677144\n", "f68c7a21d5de474fdafc5517fea56fb6b0e0ef3ee3dbd7dc05136e143d83e4d7\n", "351ecadfd64a72ba0e8d4f7b61a94c3c242d54a47590a8008b753c0cb4a97b5a\n", "3cfc303a5d7e892fce86de6a6859ce882f52f05a00ada41738964e4e0a39c993\n", "2118258468530dfef88666a922ee491423fe45deb165b896b7dab4e0ab194901\n", "02d418f7fb9941c3e85d747d4238f3c6ece30cd4353667dc679619a349888acf\n", "94b74aa520e2db84129404500fd721db9ecfa63d7d1deb36951ba722e2f1e3c0\n", "186ccb2a6c5fbf880038d5583c892d349f78614175440dd1f70e52362457ea58\n", "e5f48a4d164605816e3a92e2ff0d76fbf074759a2450a738a75fe234a53938fe\n", "94c3811b7f6d4e43fe4cfd8eb86ff37656da50cbe5d656b1ca35c30c01469d2e\n", "1dd58e6ac4c4d288af128c1c3f1443a9187bae610ded49bb91c8ae21e1cff20f\n", "cb37db7a3229888b786239b330dd6d89537cdf7e7eecf4f632860ea8817294ef\n", "f9c89a5ed439c1de51390cf1706a07a627a30653b655101b94fb3e8666af164a\n", "a847425a431fed08dcfa5126729869571ce947a39f8d949999ff1a73bdd603f7\n", "953f8417a388cc75c8fa3ba562320a11c907d45ab2d28e5e1bf1199249954f6d\n", "33bc90bb3c21654d0ed1fcead38a33b811ab123e9e560d4fee47724b66957e5d\n", "b27003530180ab10f9304604c16e6b83519854e5154d39e722a0a2cfcb01cb47\n", "52776786de33a9a349ba35108926fe59591ab3fe4116490e808bf4d6a589c8a2\n", "630261e2750e624a1cc4920a762b89b744e14a9a6bea301886d1a38e3c1a14c3\n", "c5ebe769d89ed32df700115f08af6bad5e631d4636b2687b40fdb9fcf21baf8b\n", "cd0d5bd4d6a9331714dfeaefb84ab4664954c2346599224b63020b3479ef2ca0\n", "0752dc4f01474847ddddfd4139c05042d4deaaa67f70b0e3d56229d4db8dee69\n", "35a382b46c3a1fc651aec7373fecf223794500ffec32e5da4581ba0f2b7013bb\n", "4fbe9741c4df40d44c0cc7a8c8f790f43a9fbdd478f8787cb9e90aaaeccf46ab\n", "1b1981c150d3b839b3a9b4073889b618cd379c80603e296a04cb55324511c454\n", "ae5b35d58438747e899fa58368d1fc0e1a06521f637b0e8fd572de3e039718b9\n", "83a0bbefa8d8db90c9a7f7740e573141da27480a3282f4fbb942265142a0b331\n", "816a8e7999e6bb5d13c9586a0aea3db0c4fa66bdcc30f0bf1a235ce955b98053\n", "3c18b1f0e815ff78bc8dbba99b34c671a97cd0b166d7af4cf756c5a15c2911e6\n", "baf2070c96b314cb70bcc2f2f9ee01397bb5bc86246274583fcc6e9e36a324f8\n", "01dabbf104c2977b79bb488aae164b1c6d4b27e5ab4788638533a69a289a241f\n", "cfe8f707d7dcb1fef0cc6f780cc2ddc488a1bb87169a016de4632d0e1e43c487\n", "7094b444a8b8d7881d453c39dcabb87f7fbc0d79663c126ef0d8611be3fc1769\n", "de2f49e484600500ab8ea91566ed96aabbac1434e30942f2d089af646c6815e1\n", "a6afdd667f69198942a93d41dc7777fe8f1524bcd9b55d29e63ec59ea5065b19\n", "590fcac5192d723df08ebec99e388f367ce41a95c9277b901af5e1162720d3a5\n", "187a37d8348cf9a037e4a47b771f887ad942772d84a7b225f587ca6e477780e7\n", "25c9416a369d386c5514b344ce69ee2e76d58806d7850286c4962b3d16ba5f1b\n", "259097447da51c33eb8088cbff3d528dc0388af1d1a0e478db5a9679e624392d\n", "610b3f106204f34ab8acb12b419f03367845b48d8f01b1dcf19ac92e835a83c1\n", "3af4bd4a947a05c8e5285c998f01b7d15e7f623e73ef60ea64b9792ace7bb73a\n", "d0e38745641b67ef2777569cacec4f3036c3c35fe4e8a31e545b3324c6c174c9\n", "b64f91cdb2b2e487ca07c3a2b73dbb3054bd909dcd226b7b5634d7c61a2572ba\n", "fd4dbd9d96e6b72a8b6b5b7b0367631f73c2829f0ae2b98e054df417331c9a6b\n", "ad6253b411f2f7055674581fc3064df02bb91865edd0bc634d01ce73cbcc009e\n", "39c47df41f2bcfe7e02fcfeaefbae99d52e8b327feb443c1e5446a4ad4eb013f\n", "3cc177cbd13d10089502dd6f97ffbde686a490d4c510ba76e09a0f13ebc92911\n", "48c1c54076c2a034879eaf2674f0fc127611a64f95b11b0bb6c76bd2e2117493\n", "84f325b67691a96001269b0b98280278d3fb2612b41f764559adcc8422ba04a4\n", "6b62071774ca4bd6583f3f4f574fda13b47c3eccfc7ebcef03b224feeadf7d81\n", "5eb00c952dee1f6ce60f6639d3d432f0dc83bd6de14b3189fd8d7c15153e7039\n", "b43f9b252a74ec26957d1e06af29c27d3e4232c0644b93fb427e209df795e613\n", "3ba306945c59c53be1ea2ab9d224bd7aa3644992521b24cedee070f44bdd888a\n", "ce141f5f35140eea9e0f67723ba7fffd9d1ca588e29f952f1d7e86b97862677c\n", "23a4815355b879e1d8f95bd01bada688e55de8c0e09872243e7ad01b5c7c3d5a\n", "1cbdbc3d2f9f595a6d1312498acf8073d7f6f1446141f552608bf830be57ee51\n", "75d164e3a163c5306bea351bdbebbf25074faab1807d90b1816b847ca47d9404\n", "487e8dff34d492b22d7094c9371d16b7c35766af366379edd344e87f6ef53160\n", "eb3c6d2015a01e63679748be3042c02c9965d859020ed1b1bfb48bf590ee31f7\n", "3d1060c85959701d6b23d0ee0b370947b3692119f57fecdb68fe4fcf66ead476\n", "397d3c0ebd6a1893f27715600c8ccb71d24d424e6f289031f3ad8162e7ede66b\n", "11c3f8a6830a42ec474b8723bba37b03d742bd4c78265a32d05f2b1d95a2a688\n", "68f072a0b0e356bead8b17ed704a8bb6c296c482a09749d34bc7c14e7d3a0e00\n", "7e35a2494092b28a77783d7d89b6bf79246dd496e17aac17533663d1f6afac81\n", "91039c8921dc2df0e00e5bd5ca9a06bba71324e527f520298690992eec68d822\n", "f2094370a28d43ed5ac1031b625136b1fb81aa6277eebcecefb6161844ff5614\n", "3ac03a0fd180621574019fb8cd12ebe739c8572b509480733b64121c7526434f\n", "926b54be68a3522383ab7b83e0090c719a125017200f00590125ab7d2659caad\n", "06d825d48e3f3af01e109b781a39d12f02965415cbc6486b787a33090729199a\n", "a5bde09ec4cd2f8a110e11dacb51b768da332a2834521bb663612fecf5fc5a65\n", "c424ccf864987700366cab29ef57b0b4840743c421c29c2b486c44e9ac7231ba\n", "a719b92724cd773fa851abb9018ca318910335728759958fc8418b4039e9e546\n", "32184c5ffb88305f34050b10e7e8517c46dc9b944256d53351e90c8018ab0c3b\n", "bd461c7f21d81598662e4b43ed0d5887fc438e13d752af84897be778ef86414f\n", "95233133e6f56068122f2c477e003b60dd41517214053fee7df66e4e6f360d12\n", "30ae3ef517ccd10477a0f1adb4890bb112aea31bb07be7b043900382e16dea4a\n", "be7fe4a0081eaf963206184805d4e06cc85b0b2a75262891ade3939e414181dc\n", "306f6451e0daa47128e1b0ec3e632e3005369668beeec3939d503d243167870a\n", "d81117a440db41330969c3b8b1d6287116fb17fb691584864d64e651b9f75732\n", "ebd2c1ab988de7ed5ff46b42d6f6e623c0c6dcdf73da64397a8721916c8aa1c2\n", "d49d08cc956b6b038aa7496330b0824c688079d1575311f5facc5fa1d1700905\n", "030fe7c47247f45882b21b8938ff0443e7c4822bce6433aba08a8eaade59975e\n", "2ba463f3a55b3f6521ad16f51e011fa0ee0f382cc293d48a6b09e0b5bb8ba0bd\n", "44ed912c9c3caf10fa32721586dc8e0dfbe0b78caa8c52aa8863e285cb28f4b4\n", "a2db8c32fea7a5fb7f900d7ccbf6a5983dd7f20dda4dc126ca86210e1212943b\n", "006daa9df302a9eeb779fa29bff8eaf6072507f2ea030dd3ad37d8eecb187800\n", "47467c609351f97008de8f0d2a8d7907818fcbb9a6a1386aa0cb7424b0c8fdcc\n", "a7d0b526fbb9face01e64f47f68411dd948aac53d4dbfe53cc767ad097cde1a1\n", "f5b5e00e714c7f7314f9294184f7dcbcbf41fe2da73fb4fc925a087763b06daf\n", "828bd811e88c5368f87c00f267c913dab0db3c85a43c8dd74042be8a731b8035\n", "cdc776f69f1e57105eb6fa86c33773fb3f7a482cb265aa8dc304d52e57e25515\n", "0542f73ff087cf44a94a2f4346b671e530a12f9aea4e0604d3a3442ed935f285\n", "80333db261b89bf009b5efb3d55fc5d0fcf3add7844ae4c71ba34b5ccd9c89f6\n", "ab2ae075715365a5f95cea63cffa73b6b9061f974e0fdc67746f4459f18f8614\n", "afb0328f816dd7821b3567ccd2fc712cc478aed78089bfdfe4bd3d6d8b1fa27d\n", "7bf1a9a6d16342a480437ef4cc16a2311351cc89c3883b1cb1d12d93e8163133\n", "9f2fca493a00600b6d71aa7c7877cb019d78a3986834e9668082b8c9de76d58c\n", "fcb2d62e4a626e174b332934350285e9e5170a11dbd840121c0301f977371049\n", "21e143053dacec2a8437c1456d2b01027b098f7288309ac96c2bf85dd1217860\n", "4d35643d82af188c9ef788c9bd68dbb109355ef690f3b316a8d7d391f8e13b10\n", "b566c0b9ec8713281849fea9601a1b4db3db74f965051ebcf867221278412b64\n", "e7958969d1681a9da572f926ef3819ff692670c09480f64a6b5a007f72691c75\n", "22e2175ac6da8e03a8d8797bc5ee4e9f0f42b0dae7b358b438feaa725c0b10e6\n", "473e7bb1be4d0b649f5542b528a83d5cb1bdf5c8f684a45c6f08875bd707bace\n", "064bf239a2c86ee740680b530548821796b9e58f9212ad600b4a21ab0e98cf39\n", "fcf87c4da51e726b7b5d6afa4df26d4e8be7a1881a6e34454d161b5704a6d214\n", "3d95faf2702365f03ab77fb02c52bb91bd38a66ff91034d9a4952b1a41e4536d\n", "93726ef82ff68d1c46d5088049eb12be055ed794bb5beb0cdd90ae299d308be7\n", "29911358e0327a3c5ac28e48dbb7e12d57b52aba3076ae4b9a6f697355ea8c28\n", "bc52dff627c8332a5696ab13d6f6b1d0483cb4b18e1254704788915d77cbb2c6\n", "e0580b96a080d9195524d9285c4ddca527f05f435411006879774ec147395e4c\n", "1da1b2bb8283396d551b5b8ceac6fb2ab44d8ac599c446c660aa44b1832dc40f\n", "06c53141b0390f68542e0226732661222bd6c36d78587b365f4dd094a7bce60c\n", "55e6d57b309bb698b9d3d25ada38f02d1d7a9d0d3a68b2f91b575daa5f2d755a\n", "685aabb3cf070125674c3c75eeb62758bc4b5e167ccb89614097fb686de324bf\n", "d2245586d34ee1f2e2cac1e22fe155b8dd469542b57c4231b95237a4517c98da\n", "dffcf5ac5080f94ac3fe7a11aabffb5e935ffb14a5af33e16d4529afd8f585a5\n", "f1853165e0a2df472fdfbc2009370df3d25978da3d0e55f40d9b5dbee1ca1dc9\n", "6a72c881e60110e70825a2b7e9567d699b1435c75d296a441f0806379da0d5c1\n", "d3a126610da3d0797efcdd123f5b5060724699813a1d08e0c3c9c52353e7a85b\n", "01e16a951ebf2688eef77beb0f4189aabdbeaa7824252f3ce642e46595d094b3\n", "fcba52d98d52b817a6f829c723c612b96c9bdf24caf13315114a043203c0e7a3\n", "c01aab159c2e08a0b383bb51233e29846ac57e912638547a1b9c30d614356d79\n", "6a6678d86958f56322b1d765df5e8305d410cba0b7df858b39705dcb569f606c\n", "eac8c91f59baa0075e9c257fe2cce32c07ff18f5b5115219bfcb69bb19eafddb\n", "3db8d39e9c8c4069420cc0008b1ff5058da92231a71cd49289ee5a5fcae9ecca\n", "2216f4325f1ea6b613e2b431a4674024c1532bf0ffa412a2bdb58354aae26aa0\n", "292ef132b70049041e99e5e4da522d8dc30f1ca074ab7b60a2314756ba337b82\n", "18c206bbce8b6873e92914763543d679662b9e499d86688cd0facc7802a25df3\n", "bed7996fe82c284c81be8a73b49a4d0f95b1b5e7860ee15a7dff939b357dd076\n", "0fb1e7adb9eaa56d8d9ab8af9199a998babb3e5236e108cf0b64477aec780b4a\n", "858c701424d2c174326be8122dceda6be405ffcd1349304b2f9ec44f53c11406\n", "639b417ddfb9b8102ae2d764c4f890deab51811b8fdfd5c0d7ce809c8f6409db\n", "4c08bc857d1a4e3f312d8c42c353e7369139b1d8ae163cec476c757a2e0f3081\n", "b520f80ea358225e0ea8da90b252adf1b1f4ba06d59b011201552b9624302223\n", "5f5d330c63bc7b676f5ee339419c93f787a1523423e46764447b7e870699fdaa\n", "6c183b7487aa8962c4ed6bc8eb2f00e6ebdb5ad303b234b0bc675d436a99353b\n", "bf3051209534704183889d80f1b7617ab9da849d11ec1e84e99b485cca506269\n", "43df0ae79cb862e448ca1de1cd0d6f4596aa444809a6833215670af67ca90476\n", "d925090700edcf32747ea77d36efbf9dc5d83ab273ee9898d5bfc3a7586a653b\n", "f597c2732a457ea02aa31e96bac9b73087caf19b6723da0f1d0ca6d2620f6209\n", "54a1c638456a95aa399869ad7d0cba7f8fafe86039050f636d2f21a16387f60d\n", "a5ef0412d7c036dc8e0762b673a6edb819c89355752fff698bbba41b9b85b6e1\n", "470708ea118bfa41215ef4b03018a4f0e9e35a39761d3cf194eda329e474dc62\n", "1a5ec28a99746a6e7831ad8a24836faa01d50cbb9baad9384ea3bf565fe6d311\n", "034e903269bf0dfa51d4d351577a92602637bed8d754e217a1f9fc7ed131d9c9\n", "8ebe8dc989fd49b790ff05bbbf4f3a54687a0db4c257ea231acdd8cdc78948fc\n", "542f8fbde9c957a6c1f9fa454fb8466858d66baf41f402dc2070e1fc80ad0975\n", "329109c6a52cb1b82f7528cfb352fcfae57d7b1760f06a63e6605ca36d0c0b95\n", "7ae61dc286163a82e0c8e2503ef9ecd8b4503a0f5f00a62549b86c0071a19343\n", "5bc009d9b23ec917fa133ea7602622bb261f7166528423e145c6b2dd38f4bd4c\n", "abd74a01aed23520e47564ce77bf893a49c58e163a128174b88e8bdee56fecc7\n", "5f2f645d437c42bcf13757e8efe21bb0051e9e449957df09b3b786e59d22c735\n", "248d944be1521fd9637c24217e0d5ad48eb6809085d69e14d4bd23005d21d39a\n", "a559d2a17f08500fee8f474ec95b2eef48f3618d0a8d5947bb5596e3bd742cbc\n", "76764d8883c3e0f53691d8da84222cba0a270f9117493c6d26742e16dc235758\n", "5cd3de4b80e3648230cbc9734799d7b34fb1c0a9cd82120bcbcdcf254f169f12\n", "8410acc52b18dc7d9eee1c30087186e7aec59f415090555a99691c26e7336039\n", "b096da077a20c6df93f987d00c4060a34639516b428c1e804e95a99a235e0b6f\n", "836a978f1309b2e4a4c0fd513944727a965700442ca5df5fb0cb10bff848ac93\n", "d96b92d642b43cf3618a2c7f95f4279cb50596d2e3c8bffaf6329311c48548ef\n", "f404f62c6854770257440b5e2d01c43938fec6930096b20f2f199cf4b9e90487\n", "fd05109f8d5bf0421961de925bcbbac1d7026fdee5e0aafb909faecc271e7016\n", "dfc647334eb6196830139ce8d2f85eee42128c9a5d1800ef823bdd4d49231275\n", "67191341991e0c83de41198d23cb6ae38f6c93b95d3f2fe67b0782d9913df00b\n", "e48c470b0d8670a45566cf34848ae264c3e06302794d111e7eb9bba1192c9aad\n", "71f84c9fa287b9a539472c38a9ecb93c2ef950f4eb0a8fda9a5cf1941db8a8a5\n", "95e2bcb4f1a882c49744bc04e795d477aac6c2d8268c4311adb0f5e8ce0f3225\n", "f601dd5052628edb69e3f81624db6e5d58eadcc2697cc7ba2091aae71d1955c5\n", "18b869e987f441a4522e44c6a7790b4fb8e4cc972d9e499a5a36b0059efd126d\n", "f8037875e3b32d84d183eaa26505e2e8a8fc261998286fb5179ce7ec68bd4881\n", "5b284771d6a80e44079575155891bb9e8bc8ebb7de56de2550e17fc07b04abed\n", "dd38fdbb107301d93d35d85a7b33ff12928c646e585ec775f1969c2ed7837860\n", "0b00c83f7642e757e195d86e20542f8de860d3a5a18077b423926303db2cc779\n", "34ae83598ff72a3df7bed36efb4030fad02564178c2ec48803395cbfb6a942cd\n", "5546083d6d0db1f31e0fd0eed2550b13306422e1b112a1804e87c9e754164bda\n", "ec77e0778298a2918277f6ee607c91e36521c3618ca5b8a2ec7db346a0a9d4d3\n", "6de4839e75dc801fde5f7ba8605486d4d077f175e0d50d6f0dea0165581d9998\n", "bac67010d5e44f536757c94effc29ad35e005f330cd5c80cf0badeca03c5994d\n", "ddae62595a4501a36ad5639c3cb8848ad8dc7da5107de63b8d9059370ed303e9\n", "ff1438d1ef8a7276362e8165249d8fdb3db136cbf3e81706d35595ed5d248516\n", "7e31e84cffbe854d5b0415e8376f695e837a508113dd554629e888da436b25c8\n", "b033e0fd6194ec34b4dd633e2927cec2b16f1085f6b5d62e02671aab55c202ea\n", "d9d5723d75a469d11ade6d7e6e23edcaaccde7b350c04b5fe82f6b5cc60bd95a\n", "756bca4b906844953bd5f4688028999f709d11d846914d964ea869624f1bd9bb\n", "768d3aec74662198704a190cad9722a7adf729f45d54df922a92f39cd769c22e\n", "c57ac209035c966d6cfe74ff83bcf771888684736bd9acb84d084a997aaf38bf\n", "c071b722dcb62dee14dc70d9dc885a1eb752954c40fde428f60fb12a65b24cb8\n", "2c0d14e3e95a13b9ebdfa1963ba37bf8a7e2e912b992fd663e6ee26214c32f57\n", "0a630ee744bf23f5ecdbb8f3a808eb8d87f28f8640a3e1f3b943528d511f5c65\n", "3757520c3bbb857f23b92c539199bee208da518379da054949b234bc3a055d33\n", "b3c5c6b7a0a984f124b6678024260fced1b91ea820b0c3126d6686e1374df9e1\n", "d6079c18f11a43f91990853bcafc71b26a0c239dc2b2a7cafc5280102935364c\n", "b5a1adf0a2f51e55d4e2dc9f5e06b61469117511a6464103d51d79a25f48f334\n", "1cb892bc98d8ffa201ac371e50022d13665de776b86ea3ae064001b8bf435957\n", "afa36ed9f7a8e5d9495b09f19afeaa9cf96c6a1038b9d38e341c3f4d7170cd47\n", "853e0e33d92587584492ec464749ffbce234cbbaf5104038ccd9ce079d468dae\n", "4cd27efc1d26f19002571d6be8fe7a25b89c02d2379b34b3709a22cfecdd684b\n", "2a96c9fab8b01bb3960c8543d1dcd4ea9a203ee61e38cf704ea53fcbe67f1885\n", "a417f5a936e9476fbed5f99093c5cf8345d924f78ff2e363dc1b1b5e57940c9d\n", "bdd7df3ab60c4d7eeee6090d78696bbd3d0f53ef92e3efba50d1126c10540a00\n", "e71d2fdfe175a70da38988e1a832b2dc630fb1c45ff8641c32f612b7d69b9d43\n", "27854725b42e9d0c1851670f92510aca7afde6e3c9f18954f1d8526a108745ae\n", "9298ec722aef1061c84612b51a92ce93db41cac39c2112f71a1194928f4b59c8\n", "886bbeebaf33e037ed536ff741456069534bbbe0e97b91fd1a9b365d487908d1\n", "210c2a2d366acad416920d2e05889190e47fc328b9c92986cef22a6666b1d303\n", "323a9a8ce7530259c1c4521dd86c073ece8fb703eaba7ac5b2a0eecc21c16ca5\n", "de0163ed51ddb1b720b6222b252d83859a4373acf80be115737ae7a65715951a\n", "1dcb488bebda7d9edfa15eacd18b245f79e06660b2e5c8f149be3407e5f63a71\n", "729a13d30e6d012861c9f4ff6fac795cc36ca5e5cc21778fb209c29def558ce4\n", "f92539e7da8965c6563463351b265fa7a267597b021e52d7c69563ca38298571\n", "e2b4cbb67686afa7e27c245a7dfe7522887ba84057a068c9492fb0033673bffe\n", "9e314f5fd4f02e1c826bcadc31c9eef0bc0ea503f2b05bb186147b2a34d9df5d\n", "10f824f5700b5badd275b8cb18f9dc04b4852c183426beb4b82e389135abe5f0\n", "8b77d439e3986cf13c59b867fa6d52a7948c2c701ae12cc9efdaab284c02a1ff\n", "6e35b657952bb94ff9406357f69caaa37cedf28e1a6e65850e09c2f0467e61e5\n", "10171d5395499be46779ace5e308ef47b8ab42f5c3279d7d6ecec5b2148c5f08\n", "56c2c5fd23aa9adf76ce63b87e91f380f8e9702ec21392e89b8089633329c27d\n", "b691e379db21f9d6b067f83519ff84b3514b1803763b5fb4ddcfb92cab06273d\n", "6d6060b2e67a20f9d8f049cda5e52134498145f9fbcb03d9b57a72de73d4952c\n", "6c1c1b234ba18f5c9c5d00dfa333a84ef517c5b8ed2494c0170e5436b6a8fc4b\n", "92f6449213b5520cdd0fa1a08958815539ea288356fc2cb43ffcde4427964095\n", "999a4388e631b435ceb2a9da68cf04cae56720a88d78ae25abeba3692b1a153c\n", "c668c6d20e73332568c30e8c00a21c38ea8ab6ebe6ca21938ead472a11e7155c\n", "7c2da1f8cadf6f406ec36f2d0d1080d16a436ad89e20844bf5593d2bf9174a4d\n", "97049a72a70a409e1d374190dd242040bc65b707184b5572a2123d1126698336\n", "12cb6e4008da02557943e21b9619a03b9317b91c3a9dc48dad5ca705cb410103\n", "20a856ae09fe2a43eed1bc29a8677a55a174b56d0ad2a0fb7960a826ae43826e\n", "bf416a36ab4f30ec35566dac8e918e56fb65da988e072aab5d886e6f0a714d91\n", "0973af747098c4854b60fd075ccb3f0aaca1814a24e549b9f2e99b86f75e967b\n", "359f7ad68c14b3e01ea304ee3d3275a60eb71d312dc34e46781d4958ee524401\n", "b2b9014fc61d0ba6196d12b5ac7b5d0f3ee643eb25fe57dd13d2dd787fb64adb\n", "d538186ea610c1ff62dfaa3b1632e116f51b46cff66c9ae61a0b8f3aba01c7e9\n", "02a5817d8f283aaa7304efe555ba7232077b4219519ce88ef35a3f6c34470794\n", "8cac26f4a85b244a50dd52d0d9c61310c11aaa56efeea25ba328ba5cf1607bab\n", "3884dd7d5ddc62b38aa98371e9d1dc4b0fa7f8fc4f27cfaee838e8d79f70a548\n", "cdfd426bab35d7257937815092172e90fb117c41bfb366c7573a433c4fe52089\n", "0d6ec0a27919170e66b010d55e037c7c39f242e97cc36b98ecdbe091d4349358\n", "a5cd66e3814adb28887d66b88a19402cba7fa749b9543984e2a610f1cda58a01\n", "41b456a3a086ea02009563d90fbbe9409dbc7f22f537201c271c28466adfa452\n", "1c9455ff9a3a2454e75d2150d8e4e53561a2a92b2606ee209133e9f688798125\n", "7f06ef68ce2d99a0e8b699246c5c2ef5c9298318b9957f0abc5bae2b334cff4e\n", "502f6a30fbb1bca2937fdbf7e2c74cab7eb5329fde270bb888fc954e5972e967\n", "a0923be18cb8535aa5c2bad5e39f39ce4acf0e48a2d47cffab154245f531fab7\n", "b3e7f9ec7b787b258a3a31dfdbaabbe4fc7a32c5f3d993420183b1694aa85ea2\n", "230eee5ac938e562fc9c53b419746019b609edaf33f2ee6516287f2f86735570\n", "22e4978936924c219f22b5fb55bff9b6b05ff830d32e3136ea83cd5f74de67c5\n", "09e1f5e35bd20c1dd0e0d6f05e6df0d783045928ff124c277be0173448394232\n", "9d2727b3e8df2598bd9e8af641cade412de2d1aac4a106988709c8bf5e9ad56d\n", "3012d564df1c978deac737e751317d5a234ee93c05902b83da953675a0597adb\n", "7e222231b0306ed55deec42da0e44ccc9d8f2a714d7b22b05b7ae9b1708cae05\n", "a8c57b82f06cd34422e19c94b6f0167e33199f53b4f463e50d2eb3e281797288\n", "0f654ff5fb292d3fdf0fff12ef3566f4c0e1f621c89035e3cf956e476297129d\n", "b2f91abbcb8c67e86ce93d18f6b44a4b06638dde93fe403f326bc35abd7c19f3\n", "3d29e35373da43d52e9b08367b9dfd0fe82b9f981780b1dac5bdfa8fafbe7048\n", "1142c2f2d1ae5f4634f73cab268b5e2925de7e38debda5fa30f0230443b5465c\n", "f950469ef739738bee199390ab2f5a489707ef7c63bfc37ee128a44405d18b2a\n", "07389d32f983fee7318abace1c972fb23f73b3ac152dbaa20766bcbefbf51c83\n", "db2335876105aa2b7bf56e0b0ca3de288f575d0d69f2210637aeb38932af0595\n", "c9dd2d48e0adc3710b9bffac12ccd610e8281305103171626eb647efc2fddc00\n", "158435cff52aef56bf1bf114ddc3ebc5d2def37b45acffeba6786e6ed9b88d01\n", "145a41c05f4c81ab1207567831bf58c13696a56227a18a3e196d5ebdb74a8ac7\n", "820bbcb1542b91f8e726ebc34af750ce77ca783216c9d1ee2ca287867ae4f260\n", "42c918b2c907e731002aee340e39e60a2f57f358c3f475202297bc0adecf9875\n", "f3239124740223af3b0c937acde56d65df74d1a6257db63ec732b7cd4b463bb8\n", "92ae5f006ee8fcd3b65fade9940218ba7c20adcb6fc0a86a7f3b0476dbc37c41\n", "d43097ea3553b506afa44b405de433467b672bb63fd55bc764cc9876acd6f56a\n", "085c0ef1bbd133f387fbc4ee3b7aba04d5918dc12cba2efc1fd3a889b724afb6\n", "6f399e51d35cb24e8a2a79160fe592ba853e5f64e2e09bad81ec8fb63138162b\n", "14a0af927ea5f74e02b3c7efcf951c2ff7c188d711b9c830dd6302bacc6f3ec2\n", "b57ee30ea0b3e594556acb21d389432a6fd07b0cb06187689255ecbf5aae5858\n", "dff320c0c569f025842b0f91f6e4975c1c710915c2502636a07590c9cf190e27\n", "c5bd0f8eb57e7ea4b0ea233ca00f30817326ca9332e85a9a5521d3be3f2a2dfe\n", "dfcb949f360891389747eee63cdc0beda4dcc121c6a0d03ee391be9ee2dd01c0\n", "6bb76c6a62048e6ab1b7696b7f51e15ba7ef6066bef69a672138ebc429fe6082\n", "5da0bf315f354118b78adafa777d09011c89d14f949557608f713651a036680e\n", "774c79564240ede0800584f65c106ed855968af6b9c3bf3558cb8921f0a9fbcb\n", "9cea0edcf960bd3240a55630fcb33612e30301254492ab77927a418889d02c7f\n", "ca340352165bab3b3a0f29b31e4ce179ba7528d3e3827a3e59a067de2aa0b147\n", "5e4268cd9c159c7caf2d5e24497c8d0b79e764d74249a805b40db3971a91a014\n", "3d3bc2a7e702364149c08dbb879a523e5d5e1b2cc00c21ad35ecca8b850c2397\n", "e1ab27c893f6b8cf2347165360c71bb3a796b7cdacfadacd1c9f056b1e5e093f\n", "7a7f3c53d32f8826e4dcec59c9dcb66b53b20297d4f236ecd265dd9024443cc9\n", "fc9c52673694b9f36b2be4e602ebae90336bfce45f11c68f1dc89524b241fb6f\n", "65c1f36e3502293f3436c10f2473146548ef02da2613da87d21411d3270cca1a\n", "2802784e0569f8263d29c0eb8aaa922e35fbb951c8250173cc95d6ec12c05fe9\n", "87e20fc7412b4a4a15d08b2611161e0e317f1c6532bca92b1272e35eccda2b0d\n", "063226dc5a4734e4fd8f1830956a7131f5b27998cb5a2c33b99c8447587d441e\n", "36505e2cbcbb2de5661f0713ecfcf0f25ede788795cb80a661db2d788eba3554\n", "009242f6ce96d52f9d4dd7aa317a5e2581408114d47ff5ab72b34b13236cbcc7\n", "8a8f935b9f3dcd2956f602a26270145613a9f75605b7c389dea717c236990681\n", "e3ecd91e4b271dc6829ede4940644d071ecfc9e656512152eff8df0c9c48d0f0\n", "2852a527a07a39e4e4841eb69fd7d9fd1528a82514e98a3c3f1c728654ddf4b6\n", "1202e1148f70794e697954fb6216e19cb6c018df67ca77a09ef66909d13e4a22\n", "c0d92d5b9f9510221a38d6305972cbf6cec547106afd69b131b12f7f4ee21fcb\n", "22b3b46072dc0be6978771f52b3442fd9b9c0cc7ababc26ec0f26d759ae6360e\n", "24a8e226dd2880393c6d1b01abb2df04ac946a46c381b6d96b34dd537edd86f1\n", "35cf1c9eb5245e0b364c18cbd498eb3e0a81ff8f01cb4c4f47730b586776ac78\n", "9265edce6651bd523ab5b0c97a353578acf58db6fac66813ba2bb7470837f726\n", "7da1540080817f8136e7960dec2d666f9c2ab1e613272f2e6a4e9a8254f8ed5c\n", "a583ad8eeada3cd8d34b408c827b1a97697fa68bd634ee1b36d8e67ac85c01a2\n", "2c8042698ed1535faaabca84e043ef7c2e794b2290e3634bdc04d68130ed34ee\n", "25e6b41305285ae29364c13a32340a354fa50452d6865f4dfdb9e10812b97994\n", "1fa4791fdca662a314bbd5afd636bfb2399b925ecd25cbbbcf0ce67a74498cfb\n", "f72b7f6d22fdd426cdd835e6e547862bb7cd461c213804023a834698e60a7bfe\n", "c8f092d3f3274b83ea2a7b13e282074c6a970d3ade9bf49b504e9f5405c3157c\n", "a59710dcb5f5a5b89d5a5731d75a7706d4bd88b1963b9b18015d9874ffe3e91f\n", "1535f7b239d730f83270a380b7ca9306e91292c015ed04f2889bd717e65dd091\n", "56f8f74efc04e56fcb43e26fd59c0f0ab19bdf916ac78343c0dcc8511e8eb131\n", "3a22db79964df1091f8d12f03c5fc42f185420e2d88d2354da998de2b3af9140\n", "512625f8ab120fafb6ed302977e6e6bf00119eddac35daa95486c4a787c679fe\n", "bb0fe94aecb4ce77c93f4c42cbfacb93e0cc6295739d9f88d4f391437046d792\n", "503112b63aa7841549326de9a7bf4a8d3ad2e5b05822eb8360391539a6f212f4\n", "8acd2fb49598fc45a108b56693ea317484aed61a080edd9982d75b05c22d1066\n", "28e6a5fcd070ff84012d6ea77d71f85d7c367af0b32317dba771db6059adf0ce\n", "98a7e71ab6c8ef0ee3160af60ae81cff1f512d34ff57f970abb617fa6b03dc33\n", "70ff54bca3ef1b4f22d8cbc9627b921bcbc0a3bf19455322a7bdd07fbae0caa8\n", "e2e7a9fd1261a3885da5f1bc5519fbd25a1d8a0a224701ba8d86bc7b9f175110\n", "1ea905814f87ae88dcecea6b9950501ca4d5ef6316a6da5782e7ab5e70a6ca0a\n", "604a9f4dce7b6407db411ba68ae3cb6382226c92b9537d571d24f452443cc183\n", "4e3c4e6f106b62b32996c9dab72b105e362c71878d4c1ac519ccedb72ef03fec\n", "f1ceae8eea4a0328c1fc21a25db6e7155cb266d3621438c13f90a48e521be6f8\n", "d82131e95b769d2e86abf77f4b8fd47eef1a988902c0388c1b2e6d8c2bb935e9\n", "3f7b37104b23c3a34b2548659fb205398f330143c73dc79f5e08243534f08912\n", "2478c1bf8e7e1d2a0d3941af8a19524145927cb7062c84211f1dfcb716f49171\n", "fe8fa01df19a18f8ce32602142c4b7c3669f0cc630010170a038a64fc266b1bc\n", "866cb59235096c4b53b27ca8c82abb9a510a1d4b3265d42964856e2a1fb3c1f8\n", "9dc497cd5c4ff74857df2213f8acaf5b7edfb9e5e6834c3acfd4252e1500d36e\n", "32f8482bf6bb0580103d88fb3e8bdcf673489ec54912a0e988244ec91e143dca\n", "ee1796c398593aa6a1e11af1da39fb1ff2a57a2d1dacb6bceed9171cd8aca37e\n", "b84f6cc339d30187a00a731267e43b7194852bdbbc2408faa3dd3f218e23807b\n", "fbd89355c7d54c92ca26dbd0df2a838b46a9d0697deb72a6edabdf15b1073bd8\n", "e9fbe37406e4353054ec1024a9c8e005e7ef379292161beec83d65ddcec6832f\n", "21ade9a7c85c20cebbdbdce3cde01ac9ac4a5f57604d214ce7cff26c2693a171\n", "3efbd00eb60166df480813a98d754f052bf597ea4444d92dff9575809a4bdbe6\n", "f2a8cbbd484ff298374c0c5d32159c74cfd03aef4c423afb72993e24eec96301\n", "aded3fbd3aede7ce975d97cb04d6ba51e29ba43a77824c001fb3e9f9ae791764\n", "b84f4dd5e1defddd4418fb6929e42235e7c1d2b8ae2020b8f287a14a3e02a0b8\n", "fca97ecb07717d2253538651f376b2a7398d1da8ed0a2414905315d80d5dc30d\n", "99038b2adfa36b55b68b058a8f4bbbc18f7c69319b96d41d9f54d3ca1d9625ea\n", "a608b9441fc98af880dca9f5f7794e101f21d479e6968fa7ff8373bd161edaa2\n", "3f538fb5782a6f7f881d110b784d4399c945534a9e43a04c47be1524af2562d5\n", "1dadd3e44f2743b317335707b62789465e02de60c3abe8df63bf39d4b82d5a54\n", "6e134b559a08f997f921da80148f54c7feb82736ca32d7751d4582af06b5d391\n", "429115306d056ef416c28c127a64cd69042fe4bce45f6b44e2e5fda767cc5b07\n", "5bcfb1eaec3dc0eb6153d60052a05a7c032fb95c729797196c52ab07c15c09ef\n", "727044cf1f15e6ebf605217013f85805e57f10817d66c64492d9519e1dca9793\n", "e3194a450fe3d29204848fcae2bfc36deb2c62d19bc1ee860c2c637b4e8c4977\n", "ad8136cf9812ffaa4aea8848302f6bfb4d5290e6df4302ad800d7a8c3e66579f\n", "879919e398551ecb7580e0f9fcdb3425f33b2f74640277e8dc353a2f86860217\n", "8bfd5c7d7f035d4e751607b5529c3e3cd6b708eb50695089a7f7595da32e54ff\n", "6a5e1da44140fba9acc6eb173c3ef1923a65d8d57e7deb4ecf3e667a6cc11284\n", "827c2ace5ed2e8e538b32684098c5df39f8bb8768b8492ec62d90325f769ee8a\n", "45bfa945d0ec3f5032c0dff0624a7488ffbea2405fdbdbffbca4fbcaf73b3531\n", "31160c98765edf9166eb843382f73958bd696ab0cf6686026b93fc6f987b0608\n", "b21c1755ab817469668359a7eff4525c33f36df82098a188f0b51622d68c17fc\n", "900608f1814f41413fd0790ad2f9d3ffcb5add846035ce108c3b4b5226a10c1c\n", "b2f0c10d5734899c99bbfee818574b927c06205d77b6deec670a51040bff6cc8\n", "f3c3863808d537bce1befcc56ac0377d9ac947bc875cdbdbbb54440501372303\n", "9016039adb5e06abd1e764afca6591f176c039aa40af35d5dbdb6cb8967cf023\n", "6a4d92b8c06f3f629dc6d2f0a3218e431fe4c69fc54d6c58845e9efe0bddc935\n", "d0561a188343d687979b4452f89607a7f11ee1342ef4b0a3c45c42b3d62ca268\n", "aa907f8d201f3508d531641ca193ead53c9012f171060a6a9f5fbc7334f2f72f\n", "29695ff01bb157a405999838c1980a8f8a791245e642e0dafe12248100c2a131\n", "7217033ed094bfbf22080f614678a9f9dacdca5d5d423f847ae93ad7983d200e\n", "2484ef89f1dbedc30199a84c36fed4a83c8b41922a1dd52a2845afb0ddd5f5bf\n", "ff7b577c4af200cb88b55e50c2113df5d58c8a7e46510640d58a96eb9d0cc8a5\n", "bf64e8fd2d92b24c2bc64a0ae606a0fcc2392e850aa0ddb34105f782e16c00e8\n", "93ec6ea5b0adeb70adaa20649e874cc209bc858e842b5c9fe5c393814714df6d\n", "ba9c132e70498b21e77c7f3282f2ead9d466bbeb5d90dbcea690110bd2f1c816\n", "2d631b909487ce68eef190c05ab9aebeff49d478d0278d3b86b1e01f249e8409\n", "7d9e0beb0436db65199023cfc29831fe9719371a333eadc74f01d962f841420e\n", "40f399e09d4ed56a73327f8927997246dfc9d8bbd1750f3c920e4626db5f249c\n", "bb03ce062e6f9ea2d2d24bb31f70f115ed19058e6cce8898933e1df48168edee\n", "f27b86c1b3b248583de2bd992a8cb2f67ad500ed022ca4516ddf1a57240495db\n", "5f5cf91aea1c79ef010174a90453bccdaaa841fb3337581996476ff553e28912\n", "d3d70ef87c4a80855d7e783d0fdb4d8565f2fe26e1091c887c92d75ae148ad3a\n", "95274cbfdf1f6bb0247bcef958ee9ae5fd9e32d7b7eb347cf52e7798beb07545\n", "0472d6d6773de6be62a8d3d5ea266dd45aaadbe25b8051f45ed3060fff9834fb\n", "2cb2da7e34ded8320551d916626b1932fa483d77d9bcfb0619507c61492c8ad8\n", "d4810987b047025dfded8379ce409f4dabcfebf7e439a1260f3e301525d327b2\n", "79496d725437923e3d5cda4e1e9b0f5ce62ef1576d8da005db8afd885e4794b4\n", "f067e14488dc4784a1420cf91f2792ca2d097421ad30b81f2a58a7769383a949\n", "57\n", "0000000000000000000000000000000000000000000000000000000000000000\n", "0000000000000000000000000000000000000000000000000000000000000000\n", "0000000000000000000000000000000000000000000000000000000000000000\n", "0000000000000000000000000000000000000000000000000000000000000000\n", "0000000000000000000000000000000000000000000000000000000000000000\n", "0000000000000000000000000000000000000000000000000000000000000000\n", "0000000000000000000000000000000000000000000000000000000000000000\n", "0000000000000000000000000000000000000000000000000000000000000000\n", "cleartomark\n", "\n", 0 }; /* End of file ipaSerifRegularPS.cpp */ sources_5316/artsynth/0000755000176700017670000000000011753755326013615 5ustar paulpaulsources_5316/artsynth/Speaker_def.h0000644000176700017670000000702311620746025016165 0ustar paulpaul/* Speaker_def.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Speaker_CordDimensions oo_DEFINE_STRUCT (Speaker_CordDimensions) oo_INT (numberOfMasses) oo_DOUBLE (length) oo_END_STRUCT (Speaker_CordDimensions) #undef ooSTRUCT #define ooSTRUCT Speaker_CordSpring oo_DEFINE_STRUCT (Speaker_CordSpring) oo_DOUBLE (thickness) oo_DOUBLE (mass) oo_DOUBLE (k1) oo_END_STRUCT (Speaker_CordSpring) #undef ooSTRUCT #define ooSTRUCT Speaker_GlottalShunt oo_DEFINE_STRUCT (Speaker_GlottalShunt) oo_DOUBLE (Dx) oo_DOUBLE (Dy) oo_DOUBLE (Dz) oo_END_STRUCT (Speaker_GlottalShunt) #undef ooSTRUCT #define ooSTRUCT Speaker_Velum oo_DEFINE_STRUCT (Speaker_Velum) /* V */ oo_DOUBLE (x) oo_DOUBLE (y) oo_DOUBLE (a) oo_END_STRUCT (Speaker_Velum) #undef ooSTRUCT #define ooSTRUCT Speaker_Palate oo_DEFINE_STRUCT (Speaker_Palate) /* OM */ oo_DOUBLE (radius) oo_END_STRUCT (Speaker_Palate) #undef ooSTRUCT #define ooSTRUCT Speaker_Tip oo_DEFINE_STRUCT (Speaker_Tip) oo_DOUBLE (length) oo_END_STRUCT (Speaker_Tip) #undef ooSTRUCT #define ooSTRUCT Speaker_Alveoli oo_DEFINE_STRUCT (Speaker_Alveoli) oo_DOUBLE (x) oo_DOUBLE (y) oo_DOUBLE (a) oo_END_STRUCT (Speaker_Alveoli) #undef ooSTRUCT #define ooSTRUCT Speaker_TeethCavity oo_DEFINE_STRUCT (Speaker_TeethCavity) oo_DOUBLE (dx1) oo_DOUBLE (dx2) oo_DOUBLE (dy) oo_END_STRUCT (Speaker_TeethCavity) #undef ooSTRUCT #define ooSTRUCT Speaker_LowerTeeth oo_DEFINE_STRUCT (Speaker_LowerTeeth) /* rest position of J */ oo_DOUBLE (r) oo_DOUBLE (a) oo_END_STRUCT (Speaker_LowerTeeth) #undef ooSTRUCT #define ooSTRUCT Speaker_UpperTeeth oo_DEFINE_STRUCT (Speaker_UpperTeeth) /* U */ oo_DOUBLE (x) oo_DOUBLE (y) oo_END_STRUCT (Speaker_UpperTeeth) #undef ooSTRUCT #define ooSTRUCT Speaker_Lip oo_DEFINE_STRUCT (Speaker_Lip) oo_DOUBLE (dx) oo_DOUBLE (dy) oo_END_STRUCT (Speaker_Lip) #undef ooSTRUCT #define ooSTRUCT Speaker_Nose oo_DEFINE_STRUCT (Speaker_Nose) oo_DOUBLE (Dx) oo_DOUBLE (Dz) oo_DOUBLE_ARRAY (weq, 14, 14) oo_END_STRUCT (Speaker_Nose) #undef ooSTRUCT #define ooSTRUCT Speaker oo_DEFINE_CLASS (Speaker, Data) oo_DOUBLE (relativeSize) /* Different for female, male, child. */ /* In the larynx. */ oo_STRUCT (Speaker_CordDimensions, cord) oo_STRUCT (Speaker_CordSpring, lowerCord) oo_STRUCT (Speaker_CordSpring, upperCord) oo_STRUCT (Speaker_GlottalShunt, shunt) /* Above the larynx. */ oo_STRUCT (Speaker_Velum, velum) oo_STRUCT (Speaker_Palate, palate) oo_STRUCT (Speaker_Tip, tip) oo_DOUBLE (neutralBodyDistance) oo_STRUCT (Speaker_Alveoli, alveoli) oo_STRUCT (Speaker_TeethCavity, teethCavity) oo_STRUCT (Speaker_LowerTeeth, lowerTeeth) oo_STRUCT (Speaker_UpperTeeth, upperTeeth) oo_STRUCT (Speaker_Lip, lowerLip) oo_STRUCT (Speaker_Lip, upperLip) /* In the nasal cavity. */ oo_STRUCT (Speaker_Nose, nose) oo_END_CLASS (Speaker) #undef ooSTRUCT /* End of file Speaker_def.h */ sources_5316/artsynth/Artword_Speaker_Sound.h0000644000176700017670000000172511611107117020215 0ustar paulpaul/* Artword_Speaker_Sound.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Artword.h" #include "Speaker.h" #include "Sound.h" void Artword_Speaker_Sound_movie (Artword artword, Speaker speaker, Sound sound, Graphics graphics); /* End of file Artword_Speaker_Sound.h */ sources_5316/artsynth/praat_Artsynth.cpp0000644000176700017670000003520011633766375017327 0ustar paulpaul/* praat_Artsynth.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2011/07/12 */ #include "Art_Speaker.h" #include "Artword_Speaker.h" #include "Art_Speaker_to_VocalTract.h" #include "Artword_Speaker_Sound.h" #include "Artword_Speaker_to_Sound.h" #include "Artword_to_Art.h" #include "ArtwordEditor.h" #include "VocalTract_to_Spectrum.h" #include "praat.h" extern "C" Graphics Movie_create (const wchar *title, int width, int height); #undef iam #define iam iam_LOOP /***** ART *****/ FORM (Art_create, L"Create a default Articulation", L"Articulatory synthesis") WORD (L"Name", L"articulation") OK DO praat_new1 (Art_create (), GET_STRING (L"Name")); END FORM (Art_edit, L"View & Edit Articulation", 0) for (int i = 1; i <= kArt_muscle_MAX; i ++) REAL (kArt_muscle_getText (i), L"0.0") OK { Art object = (Art) ONLY_OBJECT; for (int i = 1; i <= kArt_muscle_MAX; i ++) SET_REAL (kArt_muscle_getText (i), object -> art [i]); } DO Art object = (Art) ONLY_OBJECT; if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot edit an Art from batch."); for (int i = 1; i <= kArt_muscle_MAX; i ++) object -> art [i] = GET_REAL (kArt_muscle_getText (i)); END /***** ARTWORD *****/ FORM (Artword_create, L"Create an empty Artword", L"Create Artword...") WORD (L"Name", L"hallo") POSITIVE (L"Duration (seconds)", L"1.0") OK DO praat_new1 (Artword_create (GET_REAL (L"Duration")), GET_STRING (L"Name")); END FORM (Artword_draw, L"Draw one Artword tier", NULL) OPTIONMENU (L"Muscle", kArt_muscle_LUNGS) for (int ienum = 1; ienum <= kArt_muscle_MAX; ienum ++) OPTION (kArt_muscle_getText (ienum)) BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (Artword); Artword_draw (me, GRAPHICS, GET_INTEGER (L"Muscle"), GET_INTEGER (L"Garnish")); } END DIRECT (Artword_edit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot view or edit an Artword from batch."); WHERE (SELECTED) { iam_LOOP (Artword); autoArtwordEditor editor = ArtwordEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); praat_installEditor (editor.transfer(), IOBJECT); therror } END FORM (Artword_getTarget, L"Get one Artword target", 0) REAL (L"Time (seconds)", L"0.0") OPTIONMENU (L"Muscle", kArt_muscle_LUNGS) for (int ienum = 1; ienum <= kArt_muscle_MAX; ienum ++) OPTION (kArt_muscle_getText (ienum)) OK DO LOOP { iam (Artword); double target = Artword_getTarget (me, GET_INTEGER (L"Muscle"), GET_REAL (L"Time")); Melder_information (Melder_double (target)); } END DIRECT (Artword_help) Melder_help (L"Artword"); END FORM (Artword_setTarget, L"Set one Artword target", 0) REAL (L"Time (seconds)", L"0.0") REAL (L"Target value (0-1)", L"0.0") OPTIONMENU (L"Muscle", kArt_muscle_LUNGS) for (int ienum = 1; ienum <= kArt_muscle_MAX; ienum ++) OPTION (kArt_muscle_getText (ienum)) OK DO double time = GET_REAL (L"Time"); if (time < 0.0) Melder_throw ("Specified time should not be less than 0."); LOOP { iam (Artword); Artword_setTarget (me, GET_INTEGER (L"Muscle"), time, GET_REAL (L"Target value")); therror praat_dataChanged (me); } END FORM (Artword_to_Art, L"From Artword to Art", 0) REAL (L"Time (seconds)", L"0.0") OK DO LOOP { iam (Artword); autoArt thee = Artword_to_Art (me, GET_REAL (L"Time")); praat_new (thee.transfer(), my name); } END /***** ART & SPEAKER *****/ DIRECT (Art_Speaker_draw) autoPraatPicture picture; iam_ONLY (Art); thouart_ONLY (Speaker); Art_Speaker_draw (me, thee, GRAPHICS); END DIRECT (Art_Speaker_fillInnerContour) autoPraatPicture picture; iam_ONLY (Art); thouart_ONLY (Speaker); Art_Speaker_fillInnerContour (me, thee, GRAPHICS); END DIRECT (Art_Speaker_drawMesh) autoPraatPicture picture; iam_ONLY (Art); thouart_ONLY (Speaker); Art_Speaker_drawMesh (me, thee, GRAPHICS); END DIRECT (Art_Speaker_to_VocalTract) iam_ONLY (Art); thouart_ONLY (Speaker); autoVocalTract him = Art_Speaker_to_VocalTract (me, thee); praat_new (him.transfer(), my name, L"_", thy name); END /***** ARTWORD & SPEAKER *****/ FORM (Artword_Speaker_draw, L"Draw Artword & Speaker", 0) NATURAL (L"Number of steps", L"5") OK DO autoPraatPicture picture; iam_ONLY (Artword); thouart_ONLY (Speaker); Artword_Speaker_draw (me, thee, GRAPHICS, GET_INTEGER (L"Number of steps")); END FORM (Artword_Speaker_to_Sound, L"Articulatory synthesizer", L"Artword & Speaker: To Sound...") POSITIVE (L"Sampling frequency (Hz)", L"22050") NATURAL (L"Oversampling factor", L"25") INTEGER (L"Width 1", L"0") INTEGER (L"Width 2", L"0") INTEGER (L"Width 3", L"0") INTEGER (L"Pressure 1", L"0") INTEGER (L"Pressure 2", L"0") INTEGER (L"Pressure 3", L"0") INTEGER (L"Velocity 1", L"0") INTEGER (L"Velocity 2", L"0") INTEGER (L"Velocity 3", L"0") OK DO Sound w1, w2, w3, p1, p2, p3, v1, v2, v3; int iw1 = GET_INTEGER (L"Width 1"); int iw2 = GET_INTEGER (L"Width 2"); int iw3 = GET_INTEGER (L"Width 3"); int ip1 = GET_INTEGER (L"Pressure 1"); int ip2 = GET_INTEGER (L"Pressure 2"); int ip3 = GET_INTEGER (L"Pressure 3"); int iv1 = GET_INTEGER (L"Velocity 1"); int iv2 = GET_INTEGER (L"Velocity 2"); int iv3 = GET_INTEGER (L"Velocity 3"); iam_ONLY (Artword); thouart_ONLY (Speaker); autoSound him = Artword_Speaker_to_Sound (me, thee, GET_REAL (L"Sampling frequency"), GET_INTEGER (L"Oversampling factor"), & w1, iw1, & w2, iw2, & w3, iw3, & p1, ip1, & p2, ip2, & p3, ip3, & v1, iv1, & v2, iv2, & v3, iv3); praat_new (him.transfer(), my name, L"_", thy name); if (iw1) praat_new (w1, L"width", Melder_integer (iw1)); if (iw2) praat_new (w2, L"width", Melder_integer (iw2)); if (iw3) praat_new (w3, L"width", Melder_integer (iw3)); if (ip1) praat_new (p1, L"pressure", Melder_integer (ip1)); if (ip2) praat_new (p2, L"pressure", Melder_integer (ip2)); if (ip3) praat_new (p3, L"pressure", Melder_integer (ip3)); if (iv1) praat_new (v1, L"velocity", Melder_integer (iv1)); if (iv2) praat_new (v2, L"velocity", Melder_integer (iv2)); if (iv3) praat_new (v3, L"velocity", Melder_integer (iv3)); END /***** ARTWORD & SPEAKER [ & SOUND ] *****/ DIRECT (Artword_Speaker_movie) Graphics g = Movie_create (L"Artword & Speaker movie", 300, 300); iam_ONLY (Artword); thouart_ONLY (Speaker); heis_ONLY (Sound); // can be null Artword_Speaker_Sound_movie (me, thee, him, g); END /***** SPEAKER *****/ FORM (Speaker_create, L"Create a Speaker", L"Create Speaker...") WORD (L"Name", L"speaker") OPTIONMENU (L"Kind of speaker", 1) OPTION (L"Female") OPTION (L"Male") OPTION (L"Child") OPTIONMENU (L"Number of tubes in glottis", 2) OPTION (L"1") OPTION (L"2") OPTION (L"10") OK DO autoSpeaker me = Speaker_create (GET_STRING (L"Kind of speaker"), wcstol (GET_STRING (L"Number of tubes in glottis"), NULL, 10)); praat_new1 (me.transfer(), GET_STRING (L"Name")); END DIRECT (Speaker_help) Melder_help (L"Speaker"); END /***** VOCAL TRACT *****/ FORM (VocalTract_createFromPhone, L"Create Vocal Tract from phone", L"Create Vocal Tract from phone...") OPTIONMENU (L"Phone", 1) OPTION (L"a") OPTION (L"e") OPTION (L"i") OPTION (L"o") OPTION (L"u") OPTION (L"y1") OPTION (L"y2") OPTION (L"y3") OPTION (L"jery") OPTION (L"p") OPTION (L"t") OPTION (L"k") OPTION (L"x") OPTION (L"pa") OPTION (L"ta") OPTION (L"ka") OPTION (L"pi") OPTION (L"ti") OPTION (L"ki") OPTION (L"pu") OPTION (L"tu") OPTION (L"ku") OK DO autoVocalTract me = VocalTract_createFromPhone (GET_STRING (L"Phone")); praat_new1 (me.transfer(), GET_STRING (L"Phone")); END DIRECT (VocalTract_draw) autoPraatPicture picture; WHERE (SELECTED) { iam_LOOP (VocalTract); VocalTract_draw (me, GRAPHICS); } END FORM (VocalTract_formula, L"VocalTract Formula", L"Matrix: Formula...") LABEL (L"label", L"`x' is the distance form the glottis in metres, `col' is the section number, `self' is in m\u00B2") LABEL (L"label", L"x := x1; for col := 1 to ncol do { self [col] := `formula' ; x := x + dx }") TEXTFIELD (L"formula", L"0") OK DO LOOP { iam (VocalTract); try { Matrix_formula (me, GET_STRING (L"formula"), interpreter, NULL); therror praat_dataChanged (me); } catch (MelderError) { praat_dataChanged (me); throw; } } END DIRECT (VocalTract_help) Melder_help (L"VocalTract"); END DIRECT (VocalTract_to_Matrix) WHERE (SELECTED) { iam_LOOP (VocalTract); autoMatrix thee = VocalTract_to_Matrix (me); praat_new (thee.transfer(), my name); } END FORM (VocalTract_to_Spectrum, L"From Vocal Tract to Spectrum", 0) LABEL (L"", L"Compute transfer function") NATURAL (L"Number of frequencies", L"4097") POSITIVE (L"Maximum frequency (Hz)", L"5000") REAL (L"Glottal damping", L"0.1") BOOLEAN (L"Radiation damping", 1) BOOLEAN (L"Internal damping", 1) OK DO LOOP { iam (VocalTract); autoSpectrum thee = VocalTract_to_Spectrum (me, GET_INTEGER (L"Number of frequencies"), GET_REAL (L"Maximum frequency"), GET_REAL (L"Glottal damping"), GET_INTEGER (L"Radiation damping"), GET_INTEGER (L"Internal damping")); praat_new (thee.transfer(), my name); } END DIRECT (ArticulatorySynthesisTutorial) Melder_help (L"Articulatory synthesis"); END void manual_Artsynth_init (ManPages me); void praat_uvafon_Artsynth_init (void); void praat_uvafon_Artsynth_init (void) { Thing_recognizeClassesByName (classArt, classArtword, classSpeaker, NULL); praat_addMenuCommand (L"Objects", L"New", L"Articulatory synthesis", 0, 0, 0); praat_addMenuCommand (L"Objects", L"New", L"Articulatory synthesis tutorial", 0, 1, DO_ArticulatorySynthesisTutorial); praat_addMenuCommand (L"Objects", L"New", L"-- new articulatory synthesis -- ", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Create Articulation...", 0, 1, DO_Art_create); praat_addMenuCommand (L"Objects", L"New", L"Create Speaker...", 0, 1, DO_Speaker_create); praat_addMenuCommand (L"Objects", L"New", L"Create Artword...", 0, 1, DO_Artword_create); /*praat_addMenuCommand (L"Objects", L"New", L"-- figures --", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Figures", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 4.1: many tubes", 0, 2, DO_Fig_manyTubes); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 4.4: tube connections", 0, 2, DO_Fig_tubeConnections); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 4.7: vocal-tract construction", 0, 2, DO_Fig_vocalTractConstruction); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 5.2: pumping and sucking", 0, 2, DO_Fig_pumpingAndSucking); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 5.8: closed boundary", 0, 2, DO_Fig_closedBoundary); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 5.9: open boundary", 0, 2, DO_Fig_openBoundary); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 5.10: two-way boundary", 0, 2, DO_Fig_twoWayBoundary); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 5.11: three-way boundary", 0, 2, DO_Fig_threeWayBoundary); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 6.3: smoothing errors", 0, 2, DO_Fig_smoothingErrors); praat_addMenuCommand (L"Objects", L"New", L"PB Fig. 6.8: HNR window ripples", 0, 2, DO_Fig_hnrWindowRipples);*/ praat_addMenuCommand (L"Objects", L"New", L"-- new vocal tract --", 0, 1, 0); praat_addMenuCommand (L"Objects", L"New", L"Create Vocal Tract from phone...", 0, 1, DO_VocalTract_createFromPhone); praat_addAction1 (classArt, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_Art_edit); praat_addAction1 (classArt, 1, L"Edit", 0, praat_HIDDEN, DO_Art_edit); praat_addAction1 (classArtword, 0, L"Artword help", 0, 0, DO_Artword_help); praat_addAction1 (classArtword, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_Artword_edit); praat_addAction1 (classArtword, 1, L"Edit", 0, praat_HIDDEN, DO_Artword_edit); praat_addAction1 (classArtword, 0, L"Info", 0, 0, 0); praat_addAction1 (classArtword, 1, L"Get target...", 0, 0, DO_Artword_getTarget); praat_addAction1 (classArtword, 0, L"Draw", 0, 0, 0); praat_addAction1 (classArtword, 0, L"Draw...", 0, 0, DO_Artword_draw); praat_addAction1 (classArtword, 0, L"Modify", 0, 0, 0); praat_addAction1 (classArtword, 1, L"Set target...", 0, 0, DO_Artword_setTarget); praat_addAction1 (classArtword, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classArtword, 0, L"To Art (slice)...", 0, 0, DO_Artword_to_Art); praat_addAction2 (classArt, 1, classSpeaker, 1, L"Draw", 0, 0, 0); praat_addAction2 (classArt, 1, classSpeaker, 1, L"Draw", 0, 0, DO_Art_Speaker_draw); praat_addAction2 (classArt, 1, classSpeaker, 1, L"Fill inner contour", 0, 0, DO_Art_Speaker_fillInnerContour); praat_addAction2 (classArt, 1, classSpeaker, 1, L"Draw mesh", 0, 0, DO_Art_Speaker_drawMesh); praat_addAction2 (classArt, 1, classSpeaker, 1, L"Synthesize", 0, 0, 0); praat_addAction2 (classArt, 1, classSpeaker, 1, L"To VocalTract", 0, 0, DO_Art_Speaker_to_VocalTract); praat_addAction2 (classArtword, 1, classSpeaker, 1, L"Movie", 0, 0, DO_Artword_Speaker_movie); praat_addAction2 (classArtword, 1, classSpeaker, 1, L"Draw", 0, 0, 0); praat_addAction2 (classArtword, 1, classSpeaker, 1, L"Draw...", 0, 0, DO_Artword_Speaker_draw); praat_addAction2 (classArtword, 1, classSpeaker, 1, L"Synthesize", 0, 0, 0); praat_addAction2 (classArtword, 1, classSpeaker, 1, L"To Sound...", 0, 0, DO_Artword_Speaker_to_Sound); praat_addAction3 (classArtword, 1, classSpeaker, 1, classSound, 1, L"Movie", 0, 0, DO_Artword_Speaker_movie); praat_addAction1 (classSpeaker, 0, L"Speaker help", 0, 0, DO_Speaker_help); praat_addAction1 (classVocalTract, 0, L"VocalTract help", 0, 0, DO_VocalTract_help); praat_addAction1 (classVocalTract, 0, L"Draw", 0, 0, 0); praat_addAction1 (classVocalTract, 0, L"Draw", 0, 0, DO_VocalTract_draw); praat_addAction1 (classVocalTract, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classVocalTract, 0, L"To Spectrum...", 0, 0, DO_VocalTract_to_Spectrum); praat_addAction1 (classVocalTract, 0, L"Modify", 0, 0, 0); praat_addAction1 (classVocalTract, 0, L"Formula...", 0, 0, DO_VocalTract_formula); praat_addAction1 (classVocalTract, 0, L"Hack", 0, 0, 0); praat_addAction1 (classVocalTract, 0, L"To Matrix", 0, 0, DO_VocalTract_to_Matrix); manual_Artsynth_init (theCurrentPraatApplication -> manPages); } /* End of file praat_Artsynth.cpp */ sources_5316/artsynth/Delta.cpp0000644000176700017670000000260611753716310015344 0ustar paulpaul/* Delta.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Delta.h" Thing_implement (Delta, Thing, 0); void structDelta :: v_destroy () { NUMvector_free (this -> tube, 1); Delta_Parent :: v_destroy (); } void structDelta :: init (int a_numberOfTubes) { Melder_assert (a_numberOfTubes >= 1); this -> numberOfTubes = a_numberOfTubes; this -> tube = NUMvector (1, a_numberOfTubes); for (int itube = 1; itube <= a_numberOfTubes; itube ++) { Delta_Tube t = this -> tube + itube; t -> parallel = 1; } } Delta Delta_create (int a_numberOfTubes) { autoDelta me = Thing_new (Delta); my init (a_numberOfTubes); return me.transfer(); } /* End of file Delta.cpp */ sources_5316/artsynth/Art_Speaker.h0000644000176700017670000000356311611107117016153 0ustar paulpaul/* Art_Speaker.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Articulation.h" #include "Speaker.h" #include "Graphics.h" void Art_Speaker_toVocalTract (Art art, Speaker speaker, double intX [], double intY [], double extX [], double extY [], double *bodyX, double *bodyY); /* Function: compute key places of the supralaryngeal vocal tract. Preconditions: index intX [1..13]; index intY [1..13]; index extX [1..9]; index extY [1..9]; Postconditions: int [1..6] is anterior larynx, hyoid, and tongue root. int [6..7] is the arc of the tongue body. int [7..13] is tongue blade, lower teeth, and lower lip. ext [1..5] is posterior larynx, back pharynx wall, and velic. ext [5..6] is the arc of the velum and palate. ext [6..9] is the gums, upper teeth and upper lip. */ void Art_Speaker_draw (Art art, Speaker speaker, Graphics g); void Art_Speaker_fillInnerContour (Art art, Speaker speaker, Graphics g); void Art_Speaker_meshVocalTract (Art art, Speaker speaker, double xi [], double yi [], double xe [], double ye [], double xmm [], double ymm [], int closed []); void Art_Speaker_drawMesh (Art art, Speaker speaker, Graphics g); /* End of file Art_Speaker.h */ sources_5316/artsynth/Makefile0000644000176700017670000000132311631437106015240 0ustar paulpaul# Makefile of the library "artsynth" # Paul Boersma, 6 September 2011 include ../makefile.defs CPPFLAGS = -I ../num -I ../sys -I ../fon -I ../stat OBJECTS = Speaker.o Articulation.o Artword.o \ Art_Speaker.o Art_Speaker_to_VocalTract.o Artword_Speaker.o Artword_Speaker_Sound.o \ Artword_Speaker_to_Sound.o Artword_to_Art.o \ Delta.o Speaker_to_Delta.o Art_Speaker_Delta.o \ ArtwordEditor.o praat_Artsynth.o manual_Artsynth.o .PHONY: all clean all: libartsynth.a clean: $(RM) $(OBJECTS) $(RM) libartsynth.a libartsynth.a: $(OBJECTS) touch libartsynth.a rm libartsynth.a ar cq libartsynth.a $(OBJECTS) $(RANLIB) libartsynth.a $(OBJECTS): *.h ../num/NUM.h ../sys/*.h ../fon/*.h ../stat/*.h sources_5316/artsynth/Speaker.h0000644000176700017670000000221411625721240015341 0ustar paulpaul#ifndef _Speaker_h_ #define _Speaker_h_ /* Speaker.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" #include "Speaker_def.h" oo_CLASS_CREATE (Speaker, Data); Speaker Speaker_create (wchar *kindOfSpeaker, int numberOfVocalCordMasses); /* Preconditions: */ /* 1 <= numberOfVocalCordMasses <= 2; */ /* Failures: */ /* Kind of speaker is not one of "Female", "Male", or "Child". */ /* End of file Speaker.h */ #endif sources_5316/artsynth/ArtwordEditor.h0000644000176700017670000000243411621124713016542 0ustar paulpaul#ifndef _ArtwordEditor_h_ #define _ArtwordEditor_h_ /* ArtwordEditor.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Editor.h" #include "Artword.h" Thing_define (ArtwordEditor, Editor) { // new data: public: Graphics graphics; int feature; GuiObject list, drawingArea, radio, time, value; GuiObject button [1 + kArt_muscle_MAX]; // overridden methods: virtual void v_destroy (); virtual void v_createChildren (); virtual void v_dataChanged (); }; ArtwordEditor ArtwordEditor_create (GuiObject parent, const wchar *title, Artword data); /* End of file ArtwordEditor.h */ #endif sources_5316/artsynth/Articulation.h0000644000176700017670000000250011625721237016411 0ustar paulpaul#ifndef _Articulation_h_ #define _Articulation_h_ /* Articulation.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Art = Articulation */ /* Members represent muscle activities for speech production. */ /* All members have values from 0 (no activity) to 1 (maximum activity). */ #include "Data.h" #include "Articulation_enums.h" #include "Articulation_def.h" oo_CLASS_CREATE (Art, Data); Art Art_create (void); /* Return value: an array of double, with indices from enum Art. Postconditions: result -> art [kArt_muscle_LUNGS] == 0.0; ... result -> art [kArt_muscle_BUCCINATOR] = 0.0; */ /* End of file Articulation.h */ #endif sources_5316/artsynth/Art_Speaker.cpp0000644000176700017670000003717411614541130016513 0ustar paulpaul/* Art_Speaker.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Art_Speaker.h" #define DLIP 5e-3 void Art_Speaker_toVocalTract (Art _art, Speaker speaker, double intX [], double intY [], double extX [], double extY [], double *bodyX, double *bodyY) { double *art = _art -> art; double f = speaker -> relativeSize * 1e-3; struct { double x, y, da; } jaw; struct { double dx, dy; } hyoid; struct { double x, y, r, radius; } body; struct { double x, y, r, a; } teeth; struct { double a; } blade; struct { double x, y, a; } tip; struct { double dx, dy; } lowerLip, upperLip; double HBody_x, HBody_y, HC, Sp, p, a, b; /* Determine the position of the hyoid bone (Mermelstein's H). */ /* The rest position is a characteristic of the speaker. */ /* The stylohyoid muscle pulls the hyoid bone up. */ /* The sternohyoid muscle pulls the hyoid bone down. */ /* The sphincter muscle pulls the hyoid bone backwards. */ hyoid.dx = -5 * f * art [kArt_muscle_SPHINCTER]; hyoid.dy = 20 * f * (art [kArt_muscle_STYLOHYOID] - art [kArt_muscle_STERNOHYOID]); /* The larynx moves up and down with the hyoid bone. */ /* Only the lowest point (Mermelstein's K) */ /* does not follow completely the horizontal movements. */ /* Anterior larynx. */ intX [1] = -14 * f + 0.5 * hyoid.dx; intY [1] = -53 * f + hyoid.dy; /* Top of larynx. */ intX [2] = -20 * f + hyoid.dx; intY [2] = -33 * f + hyoid.dy; /* Epiglottis. */ intX [3] = -20 * f + hyoid.dx; intY [3] = -26 * f + hyoid.dy; /* Hyoid bone. */ intX [4] = -16 * f + hyoid.dx; intY [4] = -26 * f + hyoid.dy; /* Posterior larynx. */ extX [1] = -22 * f + hyoid.dx; extY [1] = -53 * f + hyoid.dy; /* Esophagus. */ extX [2] = -26 * f + hyoid.dx; extY [2] = -40 * f + hyoid.dy; /* The lower pharynx moves up and down with the hyoid bone. */ /* The lower constrictor muscle pulls the rear pharyngeal wall forwards. */ extX [3] = -34 * f + art [kArt_muscle_SPHINCTER] * 5 * f; extY [3] = extY [2]; /* The upper pharynx is fixed at the height of the velum. */ /* The upper constrictor muscle pulls the rear pharyngeal wall forwards. */ extX [5] = -34 * f + art [kArt_muscle_SPHINCTER] * 5 * f; extY [5] = speaker -> velum.y; /* The height of the middle pharynx is in between the lower and upper pharynx. */ /* The middle constrictor muscle pulls the rear pharyngeal wall forwards. */ extX [4] = -34 * f + art [kArt_muscle_SPHINCTER] * 5 * f; extY [4] = 0.5 * (extY [3] + extY [5]); /* Tongue root. */ jaw.x = -75 * f, jaw.y = 53 * f; /* Position of the condyle. */ jaw.da = art [kArt_muscle_MASSETER] * 0.15 - art [kArt_muscle_MYLOHYOID] * 0.20; body.x = jaw.x + 81 * f * cos (-0.60 + jaw.da) - art [kArt_muscle_STYLOGLOSSUS] * 10 * f + art [kArt_muscle_GENIOGLOSSUS] * 10 * f; body.y = jaw.y + 81 * f * sin (-0.60 + jaw.da) - art [kArt_muscle_HYOGLOSSUS] * 10 * f + art [kArt_muscle_STYLOGLOSSUS] * 5 * f; *bodyX = body.x; *bodyY = body.y; body.r = sqrt ((jaw.x - body.x) * (jaw.x - body.x) + (jaw.y - body.y) * (jaw.y - body.y)); body.radius = 20 * f; HBody_x = body.x - intX [4]; HBody_y = body.y - intY [4]; HC = sqrt (HBody_x * HBody_x + HBody_y * HBody_y); if (HC <= body.radius) { HC = body.radius; Sp = 0.0; /* 19980228 PowerPC processor BUG... Needed with the 603e at least: 00000344: CBC100B0 lfd fp30,176(SP) HC := body.radius 00000348: C94100B0 lfd fp10,176(SP) fp10 := body.radius 0000034C: C96100B0 lfd fp11,176(SP) fp11 := body.radius 00000350: FD4A02F2 fmul fp10,fp10,fp11 fp10 := body.radius ^ 2 00000354: FC3E57B8 fmsub fp1,fp30,fp30,fp10 fp1 := HC * HC - fp10 (should be zero) 00000358: 48000001 bl .sqrt gives NAN(001) !!! */ } else { Sp = sqrt (HC * HC - body.radius * body.radius); } a = atan2 (HBody_y, HBody_x); b = asin (body.radius / HC); p = 0.57 * (34.8 * f - Sp); intX [5] = intX [4] + 0.5 * Sp * cos (a + b) - p * sin (a + b); intY [5] = intY [4] + 0.5 * Sp * sin (a + b) + p * cos (a + b); HBody_x = body.x - intX [5]; HBody_y = body.y - intY [5]; HC = sqrt (HBody_x * HBody_x + HBody_y * HBody_y); if (HC <= body.radius) { HC = body.radius; Sp = 0.0; } else Sp = sqrt (HC * HC - body.radius * body.radius); a = atan2 (HBody_y, HBody_x); b = asin (body.radius / HC); intX [6] = intX [5] + Sp * cos (a + b); intY [6] = intY [5] + Sp * sin (a + b); /* Posterior blade. */ teeth.a = speaker -> lowerTeeth.a + jaw.da; intX [7] = body.x + body.radius * cos (1.73 + teeth.a); intY [7] = body.y + body.radius * sin (1.73 + teeth.a); /* Tip. */ tip.a = (art [kArt_muscle_UPPER_TONGUE] - art [kArt_muscle_LOWER_TONGUE]) * 1.0; blade.a = teeth.a + 0.004 * (body.r - speaker -> neutralBodyDistance) + tip.a; intX [8] = intX [7] + speaker -> tip.length * cos (blade.a); intY [8] = intY [7] + speaker -> tip.length * sin (blade.a); /* Jaw. */ teeth.r = speaker -> lowerTeeth.r; teeth.x = jaw.x + teeth.r * cos (teeth.a); teeth.y = jaw.y + teeth.r * sin (teeth.a); intX [9] = teeth.x + speaker -> teethCavity.dx1; intY [9] = teeth.y + speaker -> teethCavity.dy; intX [10] = teeth.x + speaker -> teethCavity.dx2; intY [10] = intY [9]; intX [11] = teeth.x; intY [11] = teeth.y; /* Lower lip. */ lowerLip.dx = speaker -> lowerLip.dx + art [kArt_muscle_ORBICULARIS_ORIS] * 0.02 - 5e-3; lowerLip.dy = speaker -> lowerLip.dy + art [kArt_muscle_ORBICULARIS_ORIS] * 0.01; intX [12] = teeth.x; intY [12] = teeth.y + lowerLip.dy; intX [13] = teeth.x + lowerLip.dx; intY [13] = intY [12]; /* Velum. */ extX [6] = speaker -> velum.x; extY [6] = speaker -> velum.y; /* Palate. */ extX [7] = speaker -> alveoli.x; extY [7] = speaker -> alveoli.y; extX [8] = speaker -> upperTeeth.x; extY [8] = speaker -> upperTeeth.y; /* Upper lip. */ upperLip.dx = speaker -> upperLip.dx + art [kArt_muscle_ORBICULARIS_ORIS] * 0.02 - 5e-3; upperLip.dy = speaker -> upperLip.dy - art [kArt_muscle_ORBICULARIS_ORIS] * 0.01; extX [9] = extX [8]; extY [9] = extY [8] + upperLip.dy; extX [10] = extX [9] + upperLip.dx; extY [10] = extY [9]; extX [11] = extX [10] + 5e-3; extY [11] = extY [10] + DLIP; /* Chin. */ intX [14] = intX [13] + 5e-3; intY [14] = intY [13] - DLIP; intX [15] = intX [11] + 0.5e-2; intY [15] = intY [11] - 3.0e-2; intX [16] = intX [1]; intY [16] = intY [1]; } void Art_Speaker_draw (Art art, Speaker speaker, Graphics g) { double f = speaker -> relativeSize * 1e-3; double intX [1 + 16], intY [1 + 16], extX [1 + 11], extY [1 + 11]; double bodyX, bodyY; int i; Graphics_Viewport previous; Art_Speaker_toVocalTract (art, speaker, intX, intY, extX, extY, & bodyX, & bodyY); previous = Graphics_insetViewport (g, 0.1, 0.9, 0.1, 0.9); Graphics_setWindow (g, -0.05, 0.05, -0.05, 0.05); /* Draw inner contour. */ for (i = 1; i <= 5; i ++) Graphics_line (g, intX [i], intY [i], intX [i + 1], intY [i + 1]); Graphics_arc (g, bodyX, bodyY, 20 * f, atan2 (intY [7] - bodyY, intX [7] - bodyX) * 180 / NUMpi, atan2 (intY [6] - bodyY, intX [6] - bodyX) * 180 / NUMpi); for (i = 7; i <= 15; i ++) Graphics_line (g, intX [i], intY [i], intX [i + 1], intY [i + 1]); /* Draw outer contour. */ for (i = 1; i <= 5; i ++) Graphics_line (g, extX [i], extY [i], extX [i + 1], extY [i + 1]); Graphics_arc (g, 0, 0, speaker -> palate.radius, speaker -> alveoli.a * 180 / NUMpi, speaker -> velum.a * 180 / NUMpi); for (i = 7; i <= 10; i ++) Graphics_line (g, extX [i], extY [i], extX [i + 1], extY [i + 1]); Graphics_resetViewport (g, previous); } void Art_Speaker_fillInnerContour (Art art, Speaker speaker, Graphics g) { double f = speaker -> relativeSize * 1e-3; double intX [1 + 16], intY [1 + 16], extX [1 + 11], extY [1 + 11]; double x [1 + 16], y [1 + 16]; double bodyX, bodyY; int i; Graphics_Viewport previous; Art_Speaker_toVocalTract (art, speaker, intX, intY, extX, extY, & bodyX, & bodyY); previous = Graphics_insetViewport (g, 0.1, 0.9, 0.1, 0.9); Graphics_setWindow (g, -0.05, 0.05, -0.05, 0.05); for (i = 1; i <= 16; i ++) { x [i] = intX [i]; y [i] = intY [i]; } Graphics_setGrey (g, 0.8); Graphics_fillArea (g, 16, & x [1], & y [1]); Graphics_fillCircle (g, bodyX, bodyY, 20 * f); Graphics_setGrey (g, 0.0); Graphics_resetViewport (g, previous); } static double arcLength (double from, double to) { double result = to - from; while (result > 0.0) result -= 2 * NUMpi; while (result < 0.0) result += 2 * NUMpi; return result; } static int Art_Speaker_meshCount = 27; static double bodyX, bodyY, bodyRadius; static double toLine (double x, double y, const double intX [], const double intY [], int i) { int nearby; if (i == 6) { double a7 = atan2 (intY [7] - bodyY, intX [7] - bodyX); double a6 = atan2 (intY [6] - bodyY, intX [6] - bodyX); double a = atan2 (y - bodyY, x - bodyX); double da6 = arcLength (a7, a6); double da = arcLength (a7, a); if (da <= da6) return fabs (sqrt ((bodyX - x) * (bodyX - x) + (bodyY - y) * (bodyY - y)) - bodyRadius); else nearby = arcLength (a7 + 0.5 * da6, a) < NUMpi ? 6 : 7; } else if ((x - intX [i]) * (intX [i + 1] - intX [i]) + (y - intY [i]) * (intY [i + 1] - intY [i]) < 0) { nearby = i; } else if ((x - intX [i + 1]) * (intX [i] - intX [i + 1]) + (y - intY [i + 1]) * (intY [i] - intY [i + 1]) < 0) { nearby = i + 1; } else { double boundaryDistance = sqrt ((intX [i + 1] - intX [i]) * (intX [i + 1] - intX [i]) + (intY [i + 1] - intY [i]) * (intY [i + 1] - intY [i])); double outerProduct = (intX [i] - x) * (intY [i + 1] - intY [i]) - (intY [i] - y) * (intX [i + 1] - intX [i]); return fabs (outerProduct) / boundaryDistance; } return sqrt ((intX [nearby] - x) * (intX [nearby] - x) + (intY [nearby] - y) * (intY [nearby] - y)); } static int inside (double x, double y, const double intX [], const double intY []) { int i, up = 0; for (i = 1; i <= 16 - 1; i ++) if ((y > intY [i]) != (y > intY [i + 1])) { double slope = (intX [i + 1] - intX [i]) / (intY [i + 1] - intY [i]); if (x > intX [i] + (y - intY [i]) * slope) up += ( y > intY [i] ? 1 : -1 ); } return up != 0 || bodyRadius * bodyRadius > (x - bodyX) * (x - bodyX) + (y - bodyY) * (y - bodyY); } void Art_Speaker_meshVocalTract (Art art, Speaker speaker, double xi [], double yi [], double xe [], double ye [], double xmm [], double ymm [], int closed []) { double f = speaker -> relativeSize * 1e-3; double intX [1 + 16], intY [1 + 16], extX [1 + 11], extY [1 + 11], d_angle; double xm [40], ym [40]; int i; Art_Speaker_toVocalTract (art, speaker, intX, intY, extX, extY, & bodyX, & bodyY); bodyRadius = 20 * f; xe [1] = extX [1]; /* Eq. 5.45 */ ye [1] = extY [1]; xe [2] = 0.2 * extX [2] + 0.8 * extX [1]; ye [2] = 0.2 * extY [2] + 0.8 * extY [1]; xe [3] = 0.6 * extX [2] + 0.4 * extX [1]; ye [3] = 0.6 * extY [2] + 0.4 * extY [1]; xe [4] = 0.9 * extX [3] + 0.1 * extX [4]; /* Eq. 5.46 */ ye [4] = 0.9 * extY [3] + 0.1 * extY [4]; xe [5] = 0.7 * extX [3] + 0.3 * extX [4]; ye [5] = 0.7 * extY [3] + 0.3 * extY [4]; xe [6] = 0.5 * extX [3] + 0.5 * extX [4]; ye [6] = 0.5 * extY [3] + 0.5 * extY [4]; xe [7] = 0.3 * extX [3] + 0.7 * extX [4]; ye [7] = 0.3 * extY [3] + 0.7 * extY [4]; xe [8] = 0.1 * extX [3] + 0.9 * extX [4]; ye [8] = 0.1 * extY [3] + 0.9 * extY [4]; xe [9] = 0.9 * extX [4] + 0.1 * extX [5]; ye [9] = 0.9 * extY [4] + 0.1 * extY [5]; xe [10] = 0.7 * extX [4] + 0.3 * extX [5]; ye [10] = 0.7 * extY [4] + 0.3 * extY [5]; xe [11] = 0.5 * extX [4] + 0.5 * extX [5]; ye [11] = 0.5 * extY [4] + 0.5 * extY [5]; xe [12] = 0.3 * extX [4] + 0.7 * extX [5]; ye [12] = 0.3 * extY [4] + 0.7 * extY [5]; xe [13] = 0.1 * extX [4] + 0.9 * extX [5]; ye [13] = 0.1 * extY [4] + 0.9 * extY [5]; d_angle = (atan2 (ye [13], xe [13]) - 0.5 * NUMpi) / 6; /* Eq. 5.47 */ for (i = 14; i <= 18; i ++) { double a = 0.5 * NUMpi + (19 - i) * d_angle; xe [i] = speaker -> palate.radius * cos (a); ye [i] = speaker -> palate.radius * sin (a); } xe [19] = 0; ye [19] = speaker -> palate.radius; xe [20] = 0.25 * extX [7]; xe [21] = 0.50 * extX [7]; xe [22] = 0.75 * extX [7]; for (i = 20; i <= 22; i ++) { ye [i] = speaker -> palate.radius * sqrt (1.0 - xe [i] * xe [i] / (speaker -> palate.radius * speaker -> palate.radius)); } xe [23] = extX [7]; ye [23] = extY [7]; xe [24] = 0.5 * (extX [7] + extX [8]); ye [24] = 0.5 * (extY [7] + extY [8]); xe [25] = extX [8]; ye [25] = extY [8]; xe [26] = 0.25 * extX [11] + 0.75 * extX [9]; xe [27] = 0.75 * extX [11] + 0.25 * extX [9]; ye [26] = extY [10]; ye [27] = 0.5 * (extY [10] + extY [11]); for (i = 1; i <= 27; i ++) { /* Every mesh point. */ double minimum = 100000; int j; for (j = 1; j <= 15 - 1; j ++) { /* Every internal segment. */ double d = toLine (xe [i], ye [i], intX, intY, j); if (d < minimum) minimum = d; } if ((closed [i] = inside (xe [i], ye [i], intX, intY)) != 0) minimum = - minimum; if (xe [i] >= 0.0) { /* Vertical line pieces. */ xi [i] = xe [i]; yi [i] = ye [i] - minimum; } else if (ye [i] <= 0.0) { /* Horizontal line pieces. */ xi [i] = xe [i] + minimum; yi [i] = ye [i]; } else { /* Radial line pieces, centre = centre of palate arc. */ double angle = atan2 (ye [i], xe [i]); xi [i] = xe [i] - minimum * cos (angle); yi [i] = ye [i] - minimum * sin (angle); } } for (i = 1; i <= Art_Speaker_meshCount; i ++) { xm [i] = 0.5 * (xe [i] + xi [i]); ym [i] = 0.5 * (ye [i] + yi [i]); } for (i = 2; i <= Art_Speaker_meshCount; i ++) { xmm [i] = 0.5 * (xm [i - 1] + xm [i]); ymm [i] = 0.5 * (ym [i - 1] + ym [i]); } xmm [1] = 2 * xm [1] - xmm [2]; ymm [1] = 2 * ym [1] - ymm [2]; xmm [Art_Speaker_meshCount + 1] = 2 * xm [Art_Speaker_meshCount] - xmm [Art_Speaker_meshCount]; ymm [Art_Speaker_meshCount + 1] = 2 * ym [Art_Speaker_meshCount] - ymm [Art_Speaker_meshCount]; } void Art_Speaker_drawMesh (Art art, Speaker speaker, Graphics graphics) { double xi [40], yi [40], xe [40], ye [40], xmm [40], ymm [40]; int closed [40]; int i; Graphics_Viewport previous; int oldLineType = Graphics_inqLineType (graphics); Art_Speaker_meshVocalTract (art, speaker, xi, yi, xe, ye, xmm, ymm, closed); previous = Graphics_insetViewport (graphics, 0.1, 0.9, 0.1, 0.9); /* Must be square. */ Graphics_setWindow (graphics, -0.05, 0.05, -0.05, 0.05); /* Mesh lines. */ for (i = 1; i <= Art_Speaker_meshCount; i ++) Graphics_line (graphics, xi [i], yi [i], xe [i], ye [i]); /* Radii. */ Graphics_setLineType (graphics, Graphics_DOTTED); for (i = 1; i <= Art_Speaker_meshCount; i ++) if (xe [i] <= 0.0 && ye [i] >= 0.0) Graphics_line (graphics, 0.0, 0.0, 0.9 * xi [i], 0.9 * yi [i]); Graphics_setLineType (graphics, oldLineType); /* Lengths. */ for (i = 1; i <= Art_Speaker_meshCount; i ++) Graphics_line (graphics, xmm [i], ymm [i], xmm [i + 1], ymm [i + 1]); for (i = 1; i <= Art_Speaker_meshCount + 1; i ++) Graphics_fillCircle_mm (graphics, xmm [i], ymm [i], 1.0); Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_HALF); Graphics_text (graphics, 0.0, 0.0, L"O"); /* Origin. */ Graphics_resetViewport (graphics, previous); } /* End of file Art_Speaker.cpp */ sources_5316/artsynth/Artword.cpp0000644000176700017670000001172711621176125015737 0ustar paulpaul/* Artword.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Artword.h" #include "oo_DESTROY.h" #include "Artword_def.h" #include "oo_COPY.h" #include "Artword_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Artword_def.h" #include "oo_EQUAL.h" #include "Artword_def.h" #include "oo_WRITE_TEXT.h" #include "Artword_def.h" #include "oo_READ_TEXT.h" #include "Artword_def.h" #include "oo_WRITE_BINARY.h" #include "Artword_def.h" #include "oo_READ_BINARY.h" #include "Artword_def.h" #include "oo_DESCRIPTION.h" #include "Artword_def.h" Thing_implement (Artword, Data, 0); Artword Artword_create (double totalTime) { Artword me = Thing_new (Artword); if (! me) return NULL; my totalTime = totalTime; for (int i = 1; i <= kArt_muscle_MAX; i ++) Artword_setDefault (me, i); return me; } void Artword_setDefault (Artword me, int feature) { ArtwordData f = & my data [feature]; NUMvector_free (f -> times, 1); NUMvector_free (f -> targets, 1); f -> times = NUMvector (1, 2); f -> targets = NUMvector (1, 2); f -> numberOfTargets = 2; f -> times [1] = 0.0; f -> targets [1] = 0.0; f -> times [2] = my totalTime; f -> targets [2] = 0.0; f -> _iTarget = 1; } void Artword_setTarget (Artword me, int feature, double time, double target) { try { Melder_assert (feature >= 1); Melder_assert (feature <= kArt_muscle_MAX); ArtwordData f = & my data [feature]; Melder_assert (f -> numberOfTargets >= 2); int insert = 1; if (time < 0.0) time = 0.0; if (time > my totalTime) time = my totalTime; while (insert <= f -> numberOfTargets && f -> times [insert] < time) insert ++; Melder_assert (insert <= f -> numberOfTargets); // can never insert past totalTime if (f -> times [insert] != time) { long numberOfTargets = f -> numberOfTargets; NUMvector_insert (& f -> times, 1, & numberOfTargets, insert); numberOfTargets = f -> numberOfTargets; NUMvector_insert (& f -> targets, 1, & numberOfTargets, insert); f -> numberOfTargets ++; } f -> targets [insert] = target; f -> times [insert] = time; } catch (MelderError) { Melder_throw (me, ": target not set."); } } double Artword_getTarget (Artword me, int feature, double time) { ArtwordData f = & my data [feature]; double *times = f -> times, *targets = f -> targets; int iTarget = f -> _iTarget; if (! iTarget) iTarget = 1; while (time > times [iTarget + 1] && iTarget < f -> numberOfTargets - 1) iTarget ++; while (time < times [iTarget] && iTarget > 1) iTarget --; f -> _iTarget = iTarget; Melder_assert (iTarget > 0 && iTarget < f -> numberOfTargets); return targets [iTarget] + (time - times [iTarget]) * (targets [iTarget + 1] - targets [iTarget]) / (times [iTarget + 1] - times [iTarget]); } void Artword_removeTarget (Artword me, int feature, int iTarget) { ArtwordData f = & my data [feature]; Melder_assert (iTarget >= 1); Melder_assert (iTarget <= f -> numberOfTargets); if (iTarget == 1) f -> targets [iTarget] = 0.0; else if (iTarget == f -> numberOfTargets) f -> targets [f -> numberOfTargets] = 0.0; else { int i; for (i = iTarget; i < f -> numberOfTargets; i ++) { f -> times [i] = f -> times [i + 1]; f -> targets [i] = f -> targets [i + 1]; } f -> numberOfTargets --; } f -> _iTarget = 1; } void Artword_intoArt (Artword me, Art art, double time) { for (int feature = 1; feature <= kArt_muscle_MAX; feature ++) { art -> art [feature] = Artword_getTarget (me, feature, time); } } void Artword_draw (Artword me, Graphics g, int feature, int garnish) { long numberOfTargets = my data [feature]. numberOfTargets; if (numberOfTargets > 0) { autoNUMvector x (1, numberOfTargets); autoNUMvector y (1, numberOfTargets); Graphics_setInner (g); Graphics_setWindow (g, 0, my totalTime, -1, 1); for (int i = 1; i <= numberOfTargets; i ++) { x [i] = my data [feature]. times [i]; y [i] = my data [feature]. targets [i]; } Graphics_polyline (g, numberOfTargets, & x [1], & y [1]); Graphics_unsetInner (g); } if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, TRUE, TRUE, FALSE); Graphics_marksLeft (g, 3, TRUE, TRUE, TRUE); Graphics_textTop (g, FALSE, kArt_muscle_getText (feature)); Graphics_textBottom (g, TRUE, L"Time (s)"); } } /* End of file Artword.cpp */ sources_5316/artsynth/Speaker_to_Delta.h0000644000176700017670000000156511611107117017160 0ustar paulpaul/* Speaker_to_Delta.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Speaker.h" #include "Delta.h" Delta Speaker_to_Delta (Speaker me); /* End of file Speaker_to_Delta.h */ sources_5316/artsynth/Artword_to_Art.h0000644000176700017670000000164111614541351016705 0ustar paulpaul/* Artword_to_Art.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Artword.h" Art Artword_to_Art (Artword me, double time); /* Function: linear interpolation between targets. */ /* End of file Artword_to_Art.h */ sources_5316/artsynth/Art_Speaker_Delta.h0000644000176700017670000000166011611107117017260 0ustar paulpaul/* Art_Speaker_Delta.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Articulation.h" #include "Speaker.h" #include "Delta.h" void Art_Speaker_intoDelta (Art art, Speaker speaker, Delta delta); /* End of file Art_Speaker_Delta.h */ sources_5316/artsynth/Artword_Speaker_to_Sound.h0000644000176700017670000000224411611107117020714 0ustar paulpaul/* Artword_Speaker_to_Sound.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Artword.h" #include "Speaker.h" #include "Sound.h" Sound Artword_Speaker_to_Sound (Artword artword, Speaker speaker, double samplingFrequency, int oversampling, Sound *w1, int iw1, Sound *w2, int iw2, Sound *w3, int iw3, Sound *p1, int ip1, Sound *p2, int ip2, Sound *p3, int ip3, Sound *v1, int iv1, Sound *v2, int iv2, Sound *v3, int iv3); /* End of file Artword_Speaker_to_Sound.h */ sources_5316/artsynth/ArtwordEditor.cpp0000644000176700017670000001470611753755326017122 0ustar paulpaul/* ArtwordEditor.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ArtwordEditor.h" #include "machine.h" Thing_implement (ArtwordEditor, Editor, 0); void structArtwordEditor :: v_destroy () { forget (graphics); ArtwordEditor_Parent :: v_destroy (); } static void updateList (ArtwordEditor me) { Artword artword = (Artword) my data; ArtwordData a = & artword -> data [my feature]; GuiList_deleteAllItems (my list); for (int i = 1; i <= a -> numberOfTargets; i ++) { static MelderString itemText = { 0 }; MelderString_empty (& itemText); MelderString_append (& itemText, Melder_single (a -> times [i]), L" ", Melder_single (a -> targets [i])); GuiList_insertItem (my list, itemText.string, i); } Graphics_updateWs (my graphics); } static void gui_button_cb_removeTarget (I, GuiButtonEvent event) { (void) event; iam (ArtwordEditor); Artword artword = (Artword) my data; long numberOfSelectedPositions, *selectedPositions = GuiList_getSelectedPositions (my list, & numberOfSelectedPositions); // BUG memory if (selectedPositions != NULL) { for (long ipos = numberOfSelectedPositions; ipos > 0; ipos --) Artword_removeTarget (artword, my feature, selectedPositions [ipos]); } NUMvector_free (selectedPositions, 1); updateList (me); my broadcastDataChanged (); } static void gui_button_cb_addTarget (I, GuiButtonEvent event) { (void) event; iam (ArtwordEditor); Artword artword = (Artword) my data; wchar *timeText = GuiText_getString (my time); double tim = Melder_atof (timeText); wchar *valueText = GuiText_getString (my value); double value = Melder_atof (valueText); ArtwordData a = & artword -> data [my feature]; int i = 1, oldCount = a -> numberOfTargets; Melder_free (timeText); Melder_free (valueText); Artword_setTarget (artword, my feature, tim, value); /* Optimization instead of "updateList (me)". */ if (tim < 0) tim = 0; if (tim > artword -> totalTime) tim = artword -> totalTime; while (tim != a -> times [i]) { i ++; Melder_assert (i <= a -> numberOfTargets); // can fail if tim is in an extended precision register } static MelderString itemText = { 0 }; MelderString_empty (& itemText); MelderString_append (& itemText, Melder_single (tim), L" ", Melder_single (value)); if (a -> numberOfTargets == oldCount) { GuiList_replaceItem (my list, itemText.string, i); } else { GuiList_insertItem (my list, itemText.string, i); } Graphics_updateWs (my graphics); my broadcastDataChanged (); } static void gui_radiobutton_cb_toggle (I, GuiRadioButtonEvent event) { iam (ArtwordEditor); int i = 0; while (event -> toggle != my button [i]) { i ++; Melder_assert (i <= kArt_muscle_MAX); } my feature = i; Melder_assert (my feature > 0); Melder_assert (my feature <= kArt_muscle_MAX); updateList (me); } static void gui_drawingarea_cb_expose (I, GuiDrawingAreaExposeEvent event) { iam (ArtwordEditor); (void) event; if (my graphics == NULL) return; Artword artword = (Artword) my data; Graphics_clearWs (my graphics); Artword_draw (artword, my graphics, my feature, TRUE); } static void gui_drawingarea_cb_click (I, GuiDrawingAreaClickEvent event) { iam (ArtwordEditor); if (my graphics == NULL) return; if (gtk && event -> type != BUTTON_PRESS) return; Artword artword = (Artword) my data; Graphics_setWindow (my graphics, 0, artword -> totalTime, -1.0, 1.0); Graphics_setInner (my graphics); double xWC, yWC; Graphics_DCtoWC (my graphics, event -> x, event -> y, & xWC, & yWC); Graphics_unsetInner (my graphics); GuiText_setString (my time, Melder_fixed (xWC, 6)); GuiText_setString (my value, Melder_fixed (yWC, 6)); } void structArtwordEditor :: v_dataChanged () { updateList (this); Graphics_updateWs (graphics); } void structArtwordEditor :: v_createChildren () { int dy = Machine_getMenuBarHeight (); GuiLabel_createShown (d_windowForm, 40, 100, dy + 3, Gui_AUTOMATIC, L"Targets:", 0); GuiLabel_createShown (d_windowForm, 5, 65, dy + 20, Gui_AUTOMATIC, L"Times:", 0); GuiLabel_createShown (d_windowForm, 80, 140, dy + 20, Gui_AUTOMATIC, L"Values:", 0); list = GuiList_createShown (d_windowForm, 0, 140, dy + 40, dy + 340, true, NULL); GuiButton_createShown (d_windowForm, 10, 130, dy + 410, Gui_AUTOMATIC, L"Remove target", gui_button_cb_removeTarget, this, 0); drawingArea = GuiDrawingArea_createShown (d_windowForm, 170, 470, dy + 10, dy + 310, gui_drawingarea_cb_expose, gui_drawingarea_cb_click, NULL, NULL, this, 0); GuiLabel_createShown (d_windowForm, 220, 270, dy + 340, Gui_AUTOMATIC, L"Time:", 0); time = GuiText_createShown (d_windowForm, 270, 370, dy + 340, Gui_AUTOMATIC, 0); GuiLabel_createShown (d_windowForm, 220, 270, dy + 370, Gui_AUTOMATIC, L"Value:", 0); value = GuiText_createShown (d_windowForm, 270, 370, dy + 370, Gui_AUTOMATIC, 0); GuiButton_createShown (d_windowForm, 240, 360, dy + 410, Gui_AUTOMATIC, L"Add target", gui_button_cb_addTarget, this, GuiButton_DEFAULT); #if gtk radio = d_windowForm; #elif motif radio = XtVaCreateManagedWidget ("radioBox", xmRowColumnWidgetClass, d_windowForm, XmNradioBehavior, True, XmNx, 470, XmNy, dy, NULL); #endif for (int i = 1; i <= kArt_muscle_MAX; i ++) { button [i] = GuiRadioButton_createShown (radio, 0, 160, Gui_AUTOMATIC, Gui_AUTOMATIC, kArt_muscle_getText (i), gui_radiobutton_cb_toggle, this, 0); } feature = 1; GuiRadioButton_setValue (button [1], true); } ArtwordEditor ArtwordEditor_create (GuiObject parent, const wchar *title, Artword data) { try { autoArtwordEditor me = Thing_new (ArtwordEditor); Editor_init (me.peek(), parent, 20, 40, 650, 600, title, data); //XtUnmanageChild (my menuBar); my graphics = Graphics_create_xmdrawingarea (my drawingArea); updateList (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("Artword window not created."); } } /* End of file ArtwordEditor.cpp */ sources_5316/artsynth/Artword_Speaker_Sound.cpp0000644000176700017670000000351311614541130020545 0ustar paulpaul/* Artword_Speaker_Sound.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Artword_Speaker_Sound.h" #include "Artword_Speaker.h" #include "Art_Speaker.h" struct playInfo { Artword artword; Speaker speaker; Graphics graphics; }; static int playCallback (void *playClosure, int phase, double tmin, double tmax, double t) { struct playInfo *me = (struct playInfo *) playClosure; static Art art; (void) phase; (void) tmin; (void) tmax; if (! art) art = Art_create (); Artword_intoArt (my artword, art, t); Graphics_clearWs (my graphics); Art_Speaker_draw (art, my speaker, my graphics); return 1; } void Artword_Speaker_Sound_movie (Artword artword, Speaker speaker, Sound sound, Graphics graphics) { try { static struct playInfo info; // must be static!!! info. artword = artword; info. speaker = speaker; info. graphics = graphics; autoSound mySound = sound ? NULL : Sound_createSimple (1, artword -> totalTime, 44100); Sound_play (sound ? sound : mySound.peek(), playCallback, & info); } catch (MelderError) { Melder_throw (artword, " & ", speaker, ": movie not played."); } } /* End of file Artword_Speaker_Sound.cpp */ sources_5316/artsynth/Speaker_to_Delta.cpp0000644000176700017670000003236511620521221017511 0ustar paulpaul/* Speaker_to_Delta.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Art_Speaker.h" #include "Speaker_to_Delta.h" #define SMOOTH_LUNGS TRUE #define FIRST_TUBE 7 Delta Speaker_to_Delta (Speaker me) { double f = my relativeSize * 1e-3; /* We shall use millimetres and grams. */ double xe [30], ye [30], xi [30], yi [30], xmm [30], ymm [30], dx, dy; int closed [40]; int itube; autoDelta thee = Delta_create (89); Melder_assert (my cord.numberOfMasses == 1 || my cord.numberOfMasses == 2 || my cord.numberOfMasses == 10); /* Lungs: tubes 1..23. */ for (itube = 1; itube <= 23; itube ++) { Delta_Tube t = thy tube + itube; t -> Dx = t -> Dxeq = 10 * f; t -> Dy = t -> Dyeq = 100 * f; t -> Dz = t -> Dzeq = 230 * f; t -> mass = 10 * my relativeSize * t -> Dx * t -> Dz; /* 80 * f; 35 * Dx * Dz */ t -> k1 = 200; /* 90000 * Dx * Dz; Newtons per metre */ t -> k3 = 0.0; t -> Brel = 0.8; t -> parallel = 1000; } /* Bronchi: tubes 24..29. */ for (itube = 24; itube <= 29; itube ++) { Delta_Tube t = thy tube + itube; t -> Dx = t -> Dxeq = 10 * f; t -> Dy = t -> Dyeq = 15 * f; t -> Dz = t -> Dzeq = 30 * f; t -> mass = 10 * f; t -> k1 = 40; /* 125000 * Dx * Dz; Newtons per metre */ t -> k3 = 0.0; t -> Brel = 0.8; } /* Trachea: tubes 30..35; four of these may be replaced by conus elasticus (see below). */ for (itube = 30; itube <= 35; itube ++) { Delta_Tube t = thy tube + itube; t -> Dx = t -> Dxeq = 10 * f; t -> Dy = t -> Dyeq = 15 * f; t -> Dz = t -> Dzeq = 16 * f; t -> mass = 5 * f; t -> k1 = 160; /* 100000 * Dx * Dz; Newtons per metre */ t -> k3 = 0.0; t -> Brel = 0.8; } if (SMOOTH_LUNGS) { struct { int itube; double Dy, Dz, parallel; } data [] = { { 7, 120, 240, 5000 }, { 8, 120, 240, 5000 }, { 9, 120, 240, 5000 }, { 10, 120, 240, 5000 }, { 11, 120, 240, 5000 }, { 12, 120, 240, 5000 }, { 13, 120, 240, 2500 }, { 14, 120, 240, 1250 }, { 15, 120, 240, 640 }, { 16, 120, 240, 320 }, { 17, 120, 240, 160 }, { 18, 120, 140, 80 }, { 19, 70, 70, 40 }, { 20, 35, 35, 20 }, { 21, 18, 18, 10 }, { 22, 12, 12, 5 }, { 23, 12, 12, 3 }, { 24, 18, 9, 2 }, { 25, 18, 19, 2 }, { 0 } }; int i; for (i = 0; data [i]. itube; i ++) { Delta_Tube t = thy tube + data [i]. itube; t -> Dy = t -> Dyeq = data [i]. Dy * f; t -> Dz = t -> Dzeq = data [i]. Dz * f; t -> parallel = data [i]. parallel; } for (itube = 26; itube <= 35; itube ++) { Delta_Tube t = thy tube + itube; t -> Dy = t -> Dyeq = 11 * f; t -> Dz = t -> Dzeq = 14 * f; t -> parallel = 1; } for (itube = FIRST_TUBE; itube <= 18; itube ++) { Delta_Tube t = thy tube + itube; t -> Dx = t -> Dxeq = 10 * f; t -> mass = 10 * my relativeSize * t -> Dx * t -> Dz; /* 10 mm */ t -> k1 = 1e5 * t -> Dx * t -> Dz; /* elastic tissue: 1 mbar/mm */ t -> k3 = 0.0; t -> Brel = 1; } for (itube = 19; itube <= 35; itube ++) { Delta_Tube t = thy tube + itube; t -> Dx = t -> Dxeq = 10 * f; t -> mass = 3 * my relativeSize * t -> Dx * t -> Dz; /* 3 mm */ t -> k1 = 10e5 * t -> Dx * t -> Dz; /* cartilage: 10 mbar/mm */ t -> k3 = 0.0; t -> Brel = 1; } } /* Glottis: tubes 36 and 37; the last one may be disconnected (see below). */ { Delta_Tube t = thy tube + 36; t -> Dx = t -> Dxeq = my lowerCord.thickness; t -> Dy = t -> Dyeq = 0.0; t -> Dz = t -> Dzeq = my cord.length; t -> mass = my lowerCord.mass; t -> k1 = my lowerCord.k1; t -> k3 = t -> k1 * (20 / t -> Dz) * (20 / t -> Dz); t -> Brel = 0.2; } /* * Fill in the values for the upper part of the glottis (tube 37) only if there is no one-mass model. */ if (my cord.numberOfMasses >= 2) { Delta_Tube t = thy tube + 37; t -> Dx = t -> Dxeq = my upperCord.thickness; t -> Dy = t -> Dyeq = 0.0; t -> Dz = t -> Dzeq = my cord.length; t -> mass = my upperCord.mass; t -> k1 = my upperCord.k1; t -> k3 = t -> k1 * (20 / t -> Dz) * (20 / t -> Dz); t -> Brel = 0.2; /* Couple spring with lower cord. */ t -> k1left1 = thy tube [36]. k1right1 = 1.0; } /* * Fill in the values for the conus elasticus (tubes 79..86) only if we want to model it. */ if (my cord.numberOfMasses == 10) { thy tube [79]. Dx = thy tube [79]. Dxeq = 8 * f; thy tube [80]. Dx = thy tube [80]. Dxeq = 7 * f; thy tube [81]. Dx = thy tube [81]. Dxeq = 6 * f; thy tube [82]. Dx = thy tube [82]. Dxeq = 5 * f; thy tube [83]. Dx = thy tube [83]. Dxeq = 4 * f; thy tube [84]. Dx = thy tube [84]. Dxeq = 0.75 * 4 * f + 0.25 * my lowerCord.thickness; thy tube [85]. Dx = thy tube [85]. Dxeq = 0.50 * 4 * f + 0.50 * my lowerCord.thickness; thy tube [86]. Dx = thy tube [86]. Dxeq = 0.25 * 4 * f + 0.75 * my lowerCord.thickness; thy tube [79]. Dy = thy tube [79]. Dyeq = 11 * f; thy tube [80]. Dy = thy tube [80]. Dyeq = 7 * f; thy tube [81]. Dy = thy tube [81]. Dyeq = 4 * f; thy tube [82]. Dy = thy tube [82]. Dyeq = 2 * f; thy tube [83]. Dy = thy tube [83]. Dyeq = 1 * f; thy tube [84]. Dy = thy tube [84]. Dyeq = 0.75 * f; thy tube [85]. Dy = thy tube [85]. Dyeq = 0.50 * f; thy tube [86]. Dy = thy tube [86]. Dyeq = 0.25 * f; thy tube [79]. Dz = thy tube [79]. Dzeq = 16 * f; thy tube [80]. Dz = thy tube [80]. Dzeq = 16 * f; thy tube [81]. Dz = thy tube [81]. Dzeq = 16 * f; thy tube [82]. Dz = thy tube [82]. Dzeq = 16 * f; thy tube [83]. Dz = thy tube [83]. Dzeq = 16 * f; thy tube [84]. Dz = thy tube [84]. Dzeq = 0.75 * 16 * f + 0.25 * my cord.length; thy tube [85]. Dz = thy tube [85]. Dzeq = 0.50 * 16 * f + 0.50 * my cord.length; thy tube [86]. Dz = thy tube [86]. Dzeq = 0.25 * 16 * f + 0.75 * my cord.length; thy tube [79]. k1 = 160; thy tube [80]. k1 = 160; thy tube [81]. k1 = 160; thy tube [82]. k1 = 160; thy tube [83]. k1 = 160; thy tube [84]. k1 = 0.75 * 160 * f + 0.25 * my lowerCord.k1; thy tube [85]. k1 = 0.50 * 160 * f + 0.50 * my lowerCord.k1; thy tube [86]. k1 = 0.25 * 160 * f + 0.75 * my lowerCord.k1; thy tube [79]. Brel = 0.7; thy tube [80]. Brel = 0.6; thy tube [81]. Brel = 0.5; thy tube [82]. Brel = 0.4; thy tube [83]. Brel = 0.3; thy tube [84]. Brel = 0.2; thy tube [85]. Brel = 0.2; thy tube [86]. Brel = 0.2; for (itube = 79; itube <= 86; itube ++) { Delta_Tube t = thy tube + itube; t -> mass = t -> Dx * t -> Dz / (30 * f); t -> k3 = t -> k1 * (20 / t -> Dz) * (20 / t -> Dz); t -> k1left1 = t -> k1right1 = 1.0; } thy tube [79]. k1left1 = 0.0; thy tube [36]. k1left1 = 1.0; /* The essence: couple spring with lower vocal cords. */ } /* * Fill in the values of the glottal shunt only if we want to model it. */ if (my shunt.Dx != 0.0) { for (itube = 87; itube <= 89; itube ++) { Delta_Tube t = thy tube + itube; t -> Dx = t -> Dxeq = my shunt.Dx; t -> Dy = t -> Dyeq = my shunt.Dy; t -> Dz = t -> Dzeq = my shunt.Dz; t -> mass = 3 * my upperCord.mass; /* Heavy... */ t -> k1 = 3 * my upperCord.k1; /* ...and stiff... */ t -> k3 = t -> k1 * (20 / t -> Dz) * (20 / t -> Dz); t -> Brel = 3.0; /* ...and inelastic, so that the walls will not vibrate. */ } } /* Vocal tract from neutral articulation. */ { autoArt art = Art_create (); Art_Speaker_meshVocalTract (art.peek(), me, xi, yi, xe, ye, xmm, ymm, closed); } /* Pharynx and mouth: tubes 38..64. */ for (itube = 38; itube <= 64; itube ++) { Delta_Tube t = thy tube + itube; int i = itube - 37; t -> Dx = t -> Dxeq = sqrt (( dx = xmm [i] - xmm [i + 1], dx * dx ) + ( dy = ymm [i] - ymm [i + 1], dy * dy )); t -> Dyeq = sqrt (( dx = xe [i] - xi [i], dx * dx ) + ( dy = ye [i] - yi [i], dy * dy )); if (closed [i]) t -> Dyeq = - t -> Dyeq; t -> Dy = t -> Dyeq; t -> Dz = t -> Dzeq = 0.015; t -> mass = 0.006; t -> k1 = 30; t -> k3 = 0.0; t -> Brel = 1.0; } /* For tongue-tip vibration [r]: thy tube [60]. Brel = 0.1; thy tube [60]. k1 = 3; */ /* Nose: tubes 65..78. */ for (itube = 65; itube <= 78; itube ++) { Delta_Tube t = thy tube + itube; t -> Dx = t -> Dxeq = my nose.Dx; t -> Dy = t -> Dyeq = my nose.weq [itube - 65]; t -> Dz = t -> Dzeq = my nose.Dz; t -> mass = 0.006; t -> k1 = 100; t -> k3 = 0.0; t -> Brel = 1.0; } thy tube [65]. Dy = thy tube [65]. Dyeq = 0.0; /* Override: nasopharyngeal port closed. */ /* The default structure: * every tube is connected on the left to the previous tube (index one lower). * This corresponds to a two-mass model of the vocal cords without shunt. */ for (itube = SMOOTH_LUNGS ? FIRST_TUBE : 1; itube <= thy numberOfTubes; itube ++) { Delta_Tube t = thy tube + itube; t -> s1 = 5e6 * t -> Dx * t -> Dz; t -> s3 = t -> s1 / (0.9e-3 * 0.9e-3); t -> dy = 1e-5; t -> left1 = t - 1; /* Connect to the previous tube on the left. */ t -> right1 = t + 1; /* Connect to the next tube on the right. */ } /***** Connections: boundaries and interfaces. *****/ /* The leftmost boundary: the diaphragm (tube 1). * Disconnect on the left. */ thy tube [SMOOTH_LUNGS ? FIRST_TUBE : 1]. left1 = NULL; /* Closed at diaphragm. */ /* Optional one-mass model of the vocal cords. * Short-circuit over tube 37 (upper glottis). */ if (my cord.numberOfMasses == 1) { /* Connect the right side of tube 36 to the left side of tube 38. */ thy tube [36]. right1 = thy tube + 38; thy tube [38]. left1 = thy tube + 36; /* Disconnect tube 37 on both sides. */ thy tube [37]. left1 = thy tube [37]. right1 = NULL; } /* Optionally couple vocal cords with conus elasticus. * Replace tubes 32..35 (upper trachea) by tubes 79..86 (conus elasticus). */ if (my cord.numberOfMasses == 10) { /* Connect the right side of tube 31 to the left side of tube 79. */ thy tube [31]. right1 = thy tube + 79; thy tube [79]. left1 = thy tube + 31; /* Connect the right side of tube 86 to the left side of tube 36. */ thy tube [86]. right1 = thy tube + 36; thy tube [36]. left1 = thy tube + 86; /* Disconnect tubes 32..35 on both sides. */ thy tube [32]. left1 = thy tube [32]. right1 = NULL; thy tube [33]. left1 = thy tube [33]. right1 = NULL; thy tube [34]. left1 = thy tube [34]. right1 = NULL; thy tube [35]. left1 = thy tube [35]. right1 = NULL; } else { /* Disconnect tubes 79..86 on both sides. */ for (itube = 79; itube <= 86; itube ++) thy tube [itube]. left1 = thy tube [itube]. right1 = NULL; } /* Optionally add a shunt parallel to the glottis. * Create a side branch from tube 34/35 (or 85/86) to tube 38/39 with tubes 87..89. */ if (my shunt.Dx != 0.0) { int topOfTrachea = my cord.numberOfMasses == 10 ? 86 : 35; /* Create a three-way interface below the shunt. * Connect lowest shunt tube (87) with top of trachea (34/35 or 85/86). */ thy tube [topOfTrachea - 1]. right2 = thy tube + 87; /* Trachea to shunt. */ thy tube [87]. left1 = thy tube + topOfTrachea - 1; /* Shunt to trachea. */ thy tube [87]. Dxeq = thy tube [topOfTrachea - 1]. Dxeq = thy tube [topOfTrachea]. Dxeq; /* Equal length. */ thy tube [87]. Dx = thy tube [topOfTrachea - 1]. Dx = thy tube [topOfTrachea]. Dx; /* Create a three-way interface above the shunt. * Connect highest shunt tube (89) with bottom of pharynx (38/39). */ thy tube [89]. right1 = thy tube + 39; /* Shunt to pharynx. */ thy tube [39]. left2 = thy tube + 89; /* Pharynx to shunt. */ thy tube [89]. Dxeq = thy tube [39]. Dxeq = thy tube [38]. Dxeq; /* All three of equal length. */ thy tube [89]. Dx = thy tube [39]. Dx = thy tube [38]. Dx; } else { /* Disconnect tubes 87..89 on both sides. */ for (itube = 87; itube <= 89; itube ++) thy tube [itube]. left1 = thy tube [itube]. right1 = NULL; } /* Create a three-way interface at the nasopharyngeal port. * Connect tubes 50 (pharynx), 51 (mouth), and 65 (nose). */ thy tube [50]. right2 = thy tube + 65; /* Pharynx to nose. */ thy tube [65]. left1 = thy tube + 50; /* Nose to pharynx. */ thy tube [65]. Dxeq = thy tube [51]. Dxeq = thy tube [50]. Dxeq; /* All three must be of equal length. */ thy tube [65]. Dx = thy tube [51]. Dx = thy tube [50]. Dx; /* The rightmost boundaries: the lips (tube 64) and the nostrils (tube 78). * Disconnect on the right. */ thy tube [64]. right1 = NULL; /* Radiation at the lips. */ thy tube [78]. right1 = NULL; /* Radiation at the nostrils. */ for (itube = 1; itube <= thy numberOfTubes; itube ++) { Delta_Tube t = thy tube + itube; Melder_assert (! t->left1 || t->left1->right1 == t || t->left1->right2 == t); Melder_assert (! t->left2 || t->left2->right1 == t); Melder_assert (! t->right1 || t->right1->left1 == t || t->right1->left2 == t); Melder_assert (! t->right2 || t->right2->left1 == t); } return thee.transfer(); } /* End of file Speaker_to_Delta.cpp */ sources_5316/artsynth/Art_Speaker_Delta.cpp0000644000176700017670000000662111614541130017615 0ustar paulpaul/* Art_Speaker_Delta.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Art_Speaker_Delta.h" #include "Art_Speaker.h" void Art_Speaker_intoDelta (Art art, Speaker speaker, Delta delta) { double f = speaker -> relativeSize * 1e-3; double xe [30], ye [30], xi [30], yi [30], xmm [30], ymm [30], dx, dy; int closed [40]; int itube; /* Lungs. */ for (itube = 7; itube <= 18; itube ++) delta -> tube [itube]. Dyeq = 120 * f * (1 + art -> art [kArt_muscle_LUNGS]); /* Glottis. */ { Delta_Tube t = delta -> tube + 36; t -> Dyeq = f * (5 - 10 * art -> art [kArt_muscle_INTERARYTENOID] + 3 * art -> art [kArt_muscle_POSTERIOR_CRICOARYTENOID] - 3 * art -> art [kArt_muscle_LATERAL_CRICOARYTENOID]); /* 4.38 */ t -> k1 = speaker -> lowerCord.k1 * (1 + art -> art [kArt_muscle_CRICOTHYROID]); t -> k3 = t -> k1 * (20 / t -> Dz) * (20 / t -> Dz); } if (speaker -> cord.numberOfMasses >= 2) { Delta_Tube t = delta -> tube + 37; t -> Dyeq = delta -> tube [36]. Dyeq; t -> k1 = speaker -> upperCord.k1 * (1 + art -> art [kArt_muscle_CRICOTHYROID]); t -> k3 = t -> k1 * (20 / t -> Dz) * (20 / t -> Dz); } if (speaker -> cord.numberOfMasses >= 10) { delta -> tube [84]. Dyeq = 0.75 * 1 * f + 0.25 * delta -> tube [36]. Dyeq; delta -> tube [85]. Dyeq = 0.50 * 1 * f + 0.50 * delta -> tube [36]. Dyeq; delta -> tube [86]. Dyeq = 0.25 * 1 * f + 0.75 * delta -> tube [36]. Dyeq; delta -> tube [84]. k1 = 0.75 * 160 + 0.25 * delta -> tube [36]. k1; delta -> tube [85]. k1 = 0.50 * 160 + 0.50 * delta -> tube [36]. k1; delta -> tube [86]. k1 = 0.25 * 160 + 0.75 * delta -> tube [36]. k1; for (itube = 84; itube <= 86; itube ++) delta -> tube [itube]. k3 = delta -> tube [itube]. k1 * (20 / delta -> tube [itube]. Dz) * (20 / delta -> tube [itube]. Dz); } /* Vocal tract. */ Art_Speaker_meshVocalTract (art, speaker, xi, yi, xe, ye, xmm, ymm, closed); for (itube = 38; itube <= 64; itube ++) { Delta_Tube t = delta -> tube + itube; int i = itube - 37; t -> Dxeq = sqrt (( dx = xmm [i] - xmm [i + 1], dx * dx ) + ( dy = ymm [i] - ymm [i + 1], dy * dy )); t -> Dyeq = sqrt (( dx = xe [i] - xi [i], dx * dx ) + ( dy = ye [i] - yi [i], dy * dy )); if (closed [i]) t -> Dyeq = - t -> Dyeq; } delta -> tube [65]. Dxeq = delta -> tube [51]. Dxeq = delta -> tube [50]. Dxeq; /* Voor [r]: thy tube [60]. Brel = 0.1; thy tube [60]. k1 = 3; */ /* Nasopharyngeal port. */ delta -> tube [65]. Dyeq = f * (18 - 25 * art -> art [kArt_muscle_LEVATOR_PALATINI]); /* 4.40 */ for (itube = 1; itube <= delta -> numberOfTubes; itube ++) { Delta_Tube t = delta -> tube + itube; t -> s1 = 5e6 * t -> Dxeq * t -> Dzeq; t -> s3 = t -> s1 / (0.9e-3 * 0.9e-3); } } /* End of file Art_Speaker_Delta.cpp */ sources_5316/artsynth/Artword_Speaker.h0000644000176700017670000000201711611107117017040 0ustar paulpaul/* Artword_Speaker.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Artword.h" #include "Speaker.h" #include "Graphics.h" void Artword_Speaker_draw (Artword artword, Speaker speaker, Graphics g, int numberOfSteps); void Artword_Speaker_movie (Artword artword, Speaker speaker, Graphics g); /* End of file Artword_Speaker.h */ sources_5316/artsynth/Artword_Speaker_to_Sound.cpp0000644000176700017670000004576211633703572021276 0ustar paulpaul/* Artword_Speaker_to_Sound.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Speaker_to_Delta.h" #include "Art_Speaker_Delta.h" #include "Artword_Speaker_to_Sound.h" #define Dymin 0.00001 #define criticalVelocity 10.0 #define noiseFactor 0.1 #define MONITOR_SAMPLES 11 /* While debugging, some of these can be 1; otherwise, they are all 0: */ #define EQUAL_TUBE_WIDTHS 0 #define CONSTANT_TUBE_LENGTHS 1 #define NO_MOVING_WALLS 0 #define NO_TURBULENCE 0 #define NO_RADIATION_DAMPING 0 #define NO_BERNOULLI_EFFECT 0 #define MASS_LEAPFROG 0 #define B91 0 Sound Artword_Speaker_to_Sound (Artword artword, Speaker speaker, double fsamp, int oversampling, Sound *out_w1, int iw1, Sound *out_w2, int iw2, Sound *out_w3, int iw3, Sound *out_p1, int ip1, Sound *out_p2, int ip2, Sound *out_p3, int ip3, Sound *out_v1, int iv1, Sound *out_v2, int iv2, Sound *out_v3, int iv3) { try { autoSound result = Sound_createSimple (1, artword -> totalTime, fsamp); long numberOfSamples = result -> nx; double minTract [1+78], maxTract [1+78]; /* For drawing. */ double Dt = 1 / fsamp / oversampling, rho0 = 1.14, c = 353, onebyc2 = 1.0 / (c * c), rho0c2 = rho0 * c * c, halfDt = 0.5 * Dt, twoDt = 2 * Dt, halfc2Dt = 0.5 * c * c * Dt, twoc2Dt = 2 * c * c * Dt, onebytworho0 = 1.0 / (2.0 * rho0), Dtbytworho0 = Dt / (2.0 * rho0); double tension, rrad, onebygrad, totalVolume; autoArt art = Art_create (); long sample; int n, m, M; autoDelta delta = Speaker_to_Delta (speaker); autoMelderMonitor monitor (L"Articulatory synthesis"); Artword_intoArt (artword, art.peek(), 0.0); Art_Speaker_intoDelta (art.peek(), speaker, delta.peek()); M = delta -> numberOfTubes; autoSound w1, w2, w3, p1, p2, p3, v1, v2, v3; if (iw1 > 0 && iw1 <= M) w1.reset (Sound_createSimple (1, artword -> totalTime, fsamp)); else iw1 = 0; if (iw2 > 0 && iw2 <= M) w2.reset (Sound_createSimple (1, artword -> totalTime, fsamp)); else iw2 = 0; if (iw3 > 0 && iw3 <= M) w3.reset (Sound_createSimple (1, artword -> totalTime, fsamp)); else iw3 = 0; if (ip1 > 0 && ip1 <= M) p1.reset (Sound_createSimple (1, artword -> totalTime, fsamp)); else ip1 = 0; if (ip2 > 0 && ip2 <= M) p2.reset (Sound_createSimple (1, artword -> totalTime, fsamp)); else ip2 = 0; if (ip3 > 0 && ip3 <= M) p3.reset (Sound_createSimple (1, artword -> totalTime, fsamp)); else ip3 = 0; if (iv1 > 0 && iv1 <= M) v1.reset (Sound_createSimple (1, artword -> totalTime, fsamp)); else iv1 = 0; if (iv2 > 0 && iv2 <= M) v2.reset (Sound_createSimple (1, artword -> totalTime, fsamp)); else iv2 = 0; if (iv3 > 0 && iv3 <= M) v3.reset (Sound_createSimple (1, artword -> totalTime, fsamp)); else iv3 = 0; /* Initialize drawing. */ { int i; for (i = 1; i <= 78; i ++) { minTract [i] = 100; maxTract [i] = -100; } } totalVolume = 0.0; for (m = 1; m <= M; m ++) { Delta_Tube t = delta->tube + m; if (! t -> left1 && ! t -> right1) continue; t->Dx = t->Dxeq; t->dDxdt = 0; /* 5.113 */ t->Dy = t->Dyeq; t->dDydt = 0; /* 5.113 */ t->Dz = t->Dzeq; /* 5.113 */ t->A = t->Dz * ( t->Dy >= t->dy ? t->Dy + Dymin : t->Dy <= - t->dy ? Dymin : (t->dy + t->Dy) * (t->dy + t->Dy) / (4 * t->dy) + Dymin ); /* 4.4, 4.5 */ #if EQUAL_TUBE_WIDTHS t->A = 0.0001; #endif t->Jleft = t->Jright = 0; /* 5.113 */ t->Qleft = t->Qright = rho0c2; /* 5.113 */ t->pleft = t->pright = 0; /* 5.114 */ t->Kleft = t->Kright = 0; /* 5.114 */ t->V = t->A * t->Dx; /* 5.114 */ totalVolume += t->V; } //Melder_casual ("Starting volume: %.10g litres.", totalVolume * 1000); for (sample = 1; sample <= numberOfSamples; sample ++) { double time = (sample - 1) / fsamp; Artword_intoArt (artword, art.peek(), time); Art_Speaker_intoDelta (art.peek(), speaker, delta.peek()); if (sample % MONITOR_SAMPLES == 0 && monitor.graphics()) { // because we can be in batch Graphics graphics = monitor.graphics(); double area [1+78]; Graphics_Viewport vp; for (int i = 1; i <= 78; i ++) { area [i] = delta -> tube [i]. A; if (area [i] < minTract [i]) minTract [i] = area [i]; if (area [i] > maxTract [i]) maxTract [i] = area [i]; } Graphics_clearWs (graphics); vp = Graphics_insetViewport (monitor.graphics(), 0, 0.5, 0.5, 1); Graphics_setWindow (graphics, 0, 1, 0, 0.05); Graphics_setColour (graphics, Graphics_RED); Graphics_function (graphics, minTract, 1, 35, 0, 0.9); Graphics_function (graphics, maxTract, 1, 35, 0, 0.9); Graphics_setColour (graphics, Graphics_BLACK); Graphics_function (graphics, area, 1, 35, 0, 0.9); Graphics_setLineType (graphics, Graphics_DOTTED); Graphics_line (graphics, 0, 0, 1, 0); Graphics_setLineType (graphics, Graphics_DRAWN); Graphics_resetViewport (graphics, vp); vp = Graphics_insetViewport (graphics, 0, 0.5, 0, 0.5); Graphics_setWindow (graphics, 0, 1, -0.000003, 0.00001); Graphics_setColour (graphics, Graphics_RED); Graphics_function (graphics, minTract, 36, 37, 0.2, 0.8); Graphics_function (graphics, maxTract, 36, 37, 0.2, 0.8); Graphics_setColour (graphics, Graphics_BLACK); Graphics_function (graphics, area, 36, 37, 0.2, 0.8); Graphics_setLineType (graphics, Graphics_DOTTED); Graphics_line (graphics, 0, 0, 1, 0); Graphics_setLineType (graphics, Graphics_DRAWN); Graphics_resetViewport (graphics, vp); vp = Graphics_insetViewport (graphics, 0.5, 1, 0.5, 1); Graphics_setWindow (graphics, 0, 1, 0, 0.001); Graphics_setColour (graphics, Graphics_RED); Graphics_function (graphics, minTract, 38, 64, 0, 1); Graphics_function (graphics, maxTract, 38, 64, 0, 1); Graphics_setColour (graphics, Graphics_BLACK); Graphics_function (graphics, area, 38, 64, 0, 1); Graphics_setLineType (graphics, Graphics_DOTTED); Graphics_line (graphics, 0, 0, 1, 0); Graphics_setLineType (graphics, Graphics_DRAWN); Graphics_resetViewport (graphics, vp); vp = Graphics_insetViewport (graphics, 0.5, 1, 0, 0.5); Graphics_setWindow (graphics, 0, 1, 0.001, 0); Graphics_setColour (graphics, Graphics_RED); Graphics_function (graphics, minTract, 65, 78, 0.5, 1); Graphics_function (graphics, maxTract, 65, 78, 0.5, 1); Graphics_setColour (graphics, Graphics_BLACK); Graphics_function (graphics, area, 65, 78, 0.5, 1); Graphics_setLineType (graphics, Graphics_DRAWN); Graphics_resetViewport (graphics, vp); Melder_monitor ((double) sample / numberOfSamples, L"Articulatory synthesis: ", Melder_half (time), L" seconds"); therror } for (n = 1; n <= oversampling; n ++) { for (m = 1; m <= M; m ++) { Delta_Tube t = delta -> tube + m; if (! t -> left1 && ! t -> right1) continue; /* New geometry. */ #if CONSTANT_TUBE_LENGTHS t->Dxnew = t->Dx; #else t->dDxdtnew = (t->dDxdt + Dt * 10000 * (t->Dxeq - t->Dx)) / (1 + 200 * Dt); /* Critical damping, 10 ms. */ t->Dxnew = t->Dx + t->dDxdtnew * Dt; #endif /* 3-way: equal lengths. */ /* This requires left tubes to be processed before right tubes. */ if (t->left1 && t->left1->right2) t->Dxnew = t->left1->Dxnew; t->Dz = t->Dzeq; /* immediate... */ t->eleft = (t->Qleft - t->Kleft) * t->V; /* 5.115 */ t->eright = (t->Qright - t->Kright) * t->V; /* 5.115 */ t->e = 0.5 * (t->eleft + t->eright); /* 5.116 */ t->p = 0.5 * (t->pleft + t->pright); /* 5.116 */ t->DeltaP = t->e / t->V - rho0c2; /* 5.117 */ t->v = t->p / (rho0 + onebyc2 * t->DeltaP); /* 5.118 */ { double dDy = t->Dyeq - t->Dy; double cubic = t->k3 * dDy * dDy; Delta_Tube l1 = t->left1, l2 = t->left2, r1 = t->right1, r2 = t->right2; tension = dDy * (t->k1 + cubic); t->B = 2 * t->Brel * sqrt (t->mass * (t->k1 + 3 * cubic)); if (t->k1left1 && l1) tension += t->k1left1 * t->k1 * (dDy - (l1->Dyeq - l1->Dy)); if (t->k1left2 && l2) tension += t->k1left2 * t->k1 * (dDy - (l2->Dyeq - l2->Dy)); if (t->k1right1 && r1) tension += t->k1right1 * t->k1 * (dDy - (r1->Dyeq - r1->Dy)); if (t->k1right2 && r2) tension += t->k1right2 * t->k1 * (dDy - (r2->Dyeq - r2->Dy)); } if (t->Dy < t->dy) { if (t->Dy >= - t->dy) { double dDy = t->dy - t->Dy, dDy2 = dDy * dDy; tension += dDy2 / (4 * t->dy) * (t->s1 + 0.5 * t->s3 * dDy2); t->B += 2 * dDy / (2 * t->dy) * sqrt (t->mass * (t->s1 + t->s3 * dDy2)); } else { tension -= t->Dy * (t->s1 + t->s3 * (t->Dy * t->Dy + t->dy * t->dy)); t->B += 2 * sqrt (t->mass * (t->s1 + t->s3 * (3 * t->Dy * t->Dy + t->dy * t->dy))); } } t->dDydtnew = (t->dDydt + Dt / t->mass * (tension + 2 * t->DeltaP * t->Dz * t->Dx)) / (1 + t->B * Dt / t->mass); /* 5.119 */ t->Dynew = t->Dy + t->dDydtnew * Dt; /* 5.119 */ #if NO_MOVING_WALLS t->Dynew = t->Dy; #endif t->Anew = t->Dz * ( t->Dynew >= t->dy ? t->Dynew + Dymin : t->Dynew <= - t->dy ? Dymin : (t->dy + t->Dynew) * (t->dy + t->Dynew) / (4 * t->dy) + Dymin ); /* 4.4, 4.5 */ #if EQUAL_TUBE_WIDTHS t->Anew = 0.0001; #endif t->Ahalf = 0.5 * (t->A + t->Anew); /* 5.120 */ t->Dxhalf = 0.5 * (t->Dxnew + t->Dx); /* 5.121 */ t->Vnew = t->Anew * t->Dxnew; /* 5.128 */ { double oneByDyav = t->Dz / t->A; /*t->R = 12 * 1.86e-5 * t->parallel * t->parallel * oneByDyav * oneByDyav;*/ if (t->Dy < 0) t->R = 12 * 1.86e-5 / (Dymin * Dymin + t->dy * t->dy); else t->R = 12 * 1.86e-5 * t->parallel * t->parallel / ((t->Dy + Dymin) * (t->Dy + Dymin) + t->dy * t->dy); t->R += 0.3 * t->parallel * oneByDyav; /* 5.23 */ } t->r = (1 + t->R * Dt / rho0) * t->Dxhalf / t->Anew; /* 5.122 */ t->ehalf = t->e + halfc2Dt * (t->Jleft - t->Jright); /* 5.123 */ t->phalf = (t->p + halfDt * (t->Qleft - t->Qright) / t->Dx) / (1 + Dtbytworho0 * t->R); /* 5.123 */ #if MASS_LEAPFROG t->ehalf = t->ehalfold + 2 * halfc2Dt * (t->Jleft - t->Jright); #endif t->Jhalf = t->phalf * t->Ahalf; /* 5.124 */ t->Qhalf = t->ehalf / (t->Ahalf * t->Dxhalf) + onebytworho0 * t->phalf * t->phalf; /* 5.124 */ #if NO_BERNOULLI_EFFECT t->Qhalf = t->ehalf / (t->Ahalf * t->Dxhalf); #endif } for (m = 1; m <= M; m ++) { /* Compute Jleftnew and Qleftnew. */ Delta_Tube l = delta->tube + m, r1 = l -> right1, r2 = l -> right2, r = r1; Delta_Tube l1 = l, l2 = r ? r -> left2 : NULL; if (l->left1 == NULL) { /* Closed boundary at the left side (diaphragm)? */ if (r == NULL) continue; /* Tube not connected at all. */ l->Jleftnew = 0; /* 5.132. */ l->Qleftnew = (l->eleft - twoc2Dt * l->Jhalf) / l->Vnew; /* 5.132. */ } else /* Left boundary open to another tube will be handled... */ (void) 0; /* ...together with the right boundary of the tube to the left. */ if (r == NULL) { /* Open boundary at the right side (lips, nostrils)? */ rrad = 1 - c * Dt / 0.02; /* Radiation resistance, 5.135. */ onebygrad = 1 / (1 + c * Dt / 0.02); /* Radiation conductance, 5.135. */ #if NO_RADIATION_DAMPING rrad = 0; onebygrad = 0; #endif l->prightnew = ((l->Dxhalf / Dt + c * onebygrad) * l->pright + 2 * ((l->Qhalf - rho0c2) - (l->Qright - rho0c2) * onebygrad)) / (l->r * l->Anew / Dt + c * onebygrad); /* 5.136 */ l->Jrightnew = l->prightnew * l->Anew; /* 5.136 */ l->Qrightnew = (rrad * (l->Qright - rho0c2) + c * (l->prightnew - l->pright)) * onebygrad + rho0c2; /* 5.136 */ } else if (l2 == NULL && r2 == NULL) { /* Two-way boundary. */ if (l->v > criticalVelocity && l->A < r->A) { l->Pturbrightnew = -0.5 * rho0 * (l->v - criticalVelocity) * (1 - l->A / r->A) * (1 - l->A / r->A) * l->v; if (l->Pturbrightnew != 0.0) l->Pturbrightnew *= 1 + NUMrandomGauss (0, noiseFactor) /* * l->A */; } if (r->v < - criticalVelocity && r->A < l->A) { l->Pturbrightnew = 0.5 * rho0 * (r->v + criticalVelocity) * (1 - r->A / l->A) * (1 - r->A / l->A) * r->v; if (l->Pturbrightnew != 0.0) l->Pturbrightnew *= 1 + NUMrandomGauss (0, noiseFactor) /* * r->A */; } #if NO_TURBULENCE l->Pturbrightnew = 0; #endif l->Jrightnew = r->Jleftnew = (l->Dxhalf * l->pright + r->Dxhalf * r->pleft + twoDt * (l->Qhalf - r->Qhalf + l->Pturbright)) / (l->r + r->r); /* 5.127 */ #if B91 l->Jrightnew = r->Jleftnew = (l->pright + r->pleft + 2 * twoDt * (l->Qhalf - r->Qhalf + l->Pturbright) / (l->Dxhalf + r->Dxhalf)) / (l->r / l->Dxhalf + r->r / r->Dxhalf); #endif l->prightnew = l->Jrightnew / l->Anew; /* 5.128 */ r->pleftnew = r->Jleftnew / r->Anew; /* 5.128 */ l->Krightnew = onebytworho0 * l->prightnew * l->prightnew; /* 5.128 */ r->Kleftnew = onebytworho0 * r->pleftnew * r->pleftnew; /* 5.128 */ #if NO_BERNOULLI_EFFECT l->Krightnew = r->Kleftnew = 0; #endif l->Qrightnew = (l->eright + r->eleft + twoc2Dt * (l->Jhalf - r->Jhalf) + l->Krightnew * l->Vnew + (r->Kleftnew - l->Pturbrightnew) * r->Vnew) / (l->Vnew + r->Vnew); /* 5.131 */ r->Qleftnew = l->Qrightnew + l->Pturbrightnew; /* 5.131 */ } else if (r2) { /* Two adjacent tubes at the right side (velic). */ r1->Jleftnew = (r1->Jleft * r1->Dxhalf * (1 / (l->A + r2->A) + 1 / r1->A) + twoDt * ((l->Ahalf * l->Qhalf + r2->Ahalf * r2->Qhalf ) / (l->Ahalf + r2->Ahalf) - r1->Qhalf)) / (1 / (1 / l->r + 1 / r2->r) + r1->r); /* 5.138 */ r2->Jleftnew = (r2->Jleft * r2->Dxhalf * (1 / (l->A + r1->A) + 1 / r2->A) + twoDt * ((l->Ahalf * l->Qhalf + r1->Ahalf * r1->Qhalf ) / (l->Ahalf + r1->Ahalf) - r2->Qhalf)) / (1 / (1 / l->r + 1 / r1->r) + r2->r); /* 5.138 */ l->Jrightnew = r1->Jleftnew + r2->Jleftnew; /* 5.139 */ l->prightnew = l->Jrightnew / l->Anew; /* 5.128 */ r1->pleftnew = r1->Jleftnew / r1->Anew; /* 5.128 */ r2->pleftnew = r2->Jleftnew / r2->Anew; /* 5.128 */ l->Krightnew = onebytworho0 * l->prightnew * l->prightnew; /* 5.128 */ r1->Kleftnew = onebytworho0 * r1->pleftnew * r1->pleftnew; /* 5.128 */ r2->Kleftnew = onebytworho0 * r2->pleftnew * r2->pleftnew; /* 5.128 */ #if NO_BERNOULLI_EFFECT l->Krightnew = r1->Kleftnew = r2->Kleftnew = 0; #endif l->Qrightnew = r1->Qleftnew = r2->Qleftnew = (l->eright + r1->eleft + r2->eleft + twoc2Dt * (l->Jhalf - r1->Jhalf - r2->Jhalf) + l->Krightnew * l->Vnew + r1->Kleftnew * r1->Vnew + r2->Kleftnew * r2->Vnew) / (l->Vnew + r1->Vnew + r2->Vnew); /* 5.137 */ } else { Melder_assert (l2 != NULL); l1->Jrightnew = (l1->Jright * l1->Dxhalf * (1 / (r->A + l2->A) + 1 / l1->A) - twoDt * ((r->Ahalf * r->Qhalf + l2->Ahalf * l2->Qhalf ) / (r->Ahalf + l2->Ahalf) - l1->Qhalf)) / (1 / (1 / r->r + 1 / l2->r) + l1->r); /* 5.138 */ l2->Jrightnew = (l2->Jright * l2->Dxhalf * (1 / (r->A + l1->A) + 1 / l2->A) - twoDt * ((r->Ahalf * r->Qhalf + l1->Ahalf * l1->Qhalf ) / (r->Ahalf + l1->Ahalf) - l2->Qhalf)) / (1 / (1 / r->r + 1 / l1->r) + l2->r); /* 5.138 */ r->Jleftnew = l1->Jrightnew + l2->Jrightnew; /* 5.139 */ r->pleftnew = r->Jleftnew / r->Anew; /* 5.128 */ l1->prightnew = l1->Jrightnew / l1->Anew; /* 5.128 */ l2->prightnew = l2->Jrightnew / l2->Anew; /* 5.128 */ r->Kleftnew = onebytworho0 * r->pleftnew * r->pleftnew; /* 5.128 */ l1->Krightnew = onebytworho0 * l1->prightnew * l1->prightnew; /* 5.128 */ l2->Krightnew = onebytworho0 * l2->prightnew * l2->prightnew; /* 5.128 */ #if NO_BERNOULLI_EFFECT r->Kleftnew = l1->Krightnew = l2->Krightnew = 0; #endif r->Qleftnew = l1->Qrightnew = l2->Qrightnew = (r->eleft + l1->eright + l2->eright + twoc2Dt * (l1->Jhalf + l2->Jhalf - r->Jhalf) + r->Kleftnew * r->Vnew + l1->Krightnew * l1->Vnew + l2->Krightnew * l2->Vnew) / (r->Vnew + l1->Vnew + l2->Vnew); /* 5.137 */ } } /* Save some results. */ if (n == (oversampling + 1) / 2) { double out = 0.0; for (m = 1; m <= M; m ++) { Delta_Tube t = delta->tube + m; out += rho0 * t->Dx * t->Dz * t->dDydt * Dt * 1000; /* Radiation of wall movement, 5.140. */ if (t->right1 == NULL) out += t->Jrightnew - t->Jright; /* Radiation of open tube end. */ } result -> z [1] [sample] = out /= 4 * NUMpi * 0.4 * Dt; /* At 0.4 metres. */ if (iw1) w1 -> z [1] [sample] = delta->tube[iw1].Dy; if (iw2) w2 -> z [1] [sample] = delta->tube[iw2].Dy; if (iw3) w3 -> z [1] [sample] = delta->tube[iw3].Dy; if (ip1) p1 -> z [1] [sample] = delta->tube[ip1].DeltaP; if (ip2) p2 -> z [1] [sample] = delta->tube[ip2].DeltaP; if (ip3) p3 -> z [1] [sample] = delta->tube[ip3].DeltaP; if (iv1) v1 -> z [1] [sample] = delta->tube[iv1].v; if (iv2) v2 -> z [1] [sample] = delta->tube[iv2].v; if (iv3) v3 -> z [1] [sample] = delta->tube[iv3].v; } for (m = 1; m <= M; m ++) { Delta_Tube t = delta->tube + m; t->Jleft = t->Jleftnew; t->Jright = t->Jrightnew; t->Qleft = t->Qleftnew; t->Qright = t->Qrightnew; t->Dy = t->Dynew; t->dDydt = t->dDydtnew; t->A = t->Anew; t->Dx = t->Dxnew; t->dDxdt = t->dDxdtnew; t->eleft = t->eleftnew; t->eright = t->erightnew; #if MASS_LEAPFROG t->ehalfold = t->ehalf; #endif t->pleft = t->pleftnew; t->pright = t->prightnew; t->Kleft = t->Kleftnew; t->Kright = t->Krightnew; t->V = t->Vnew; t->Pturbright = t->Pturbrightnew; } } } totalVolume = 0.0; for (m = 1; m <= M; m ++) totalVolume += delta->tube [m]. V; //Melder_casual ("Ending volume: %.10g litres.", totalVolume * 1000); if (out_w1) *out_w1 = w1.transfer(); if (out_w2) *out_w2 = w2.transfer(); if (out_w3) *out_w3 = w3.transfer(); if (out_p1) *out_p1 = p1.transfer(); if (out_p2) *out_p2 = p2.transfer(); if (out_p3) *out_p3 = p3.transfer(); if (out_v1) *out_v1 = v1.transfer(); if (out_v2) *out_v2 = v2.transfer(); if (out_v3) *out_v3 = v3.transfer(); return result.transfer(); } catch (MelderError) { Melder_throw (artword, " & ", speaker, ": articulatory synthesis not performed."); } } /* End of file Artword_Speaker_to_Sound.cpp */ sources_5316/artsynth/Articulation.cpp0000644000176700017670000000301411621176073016743 0ustar paulpaul/* Articulation.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Articulation.h" #include "oo_DESTROY.h" #include "Articulation_def.h" #include "oo_COPY.h" #include "Articulation_def.h" #include "oo_EQUAL.h" #include "Articulation_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Articulation_def.h" #include "oo_WRITE_TEXT.h" #include "Articulation_def.h" #include "oo_WRITE_BINARY.h" #include "Articulation_def.h" #include "oo_READ_TEXT.h" #include "Articulation_def.h" #include "oo_READ_BINARY.h" #include "Articulation_def.h" #include "oo_DESCRIPTION.h" #include "Articulation_def.h" #include "enums_getText.h" #include "Articulation_enums.h" #include "enums_getValue.h" #include "Articulation_enums.h" Thing_implement (Art, Data, 0); Art Art_create (void) { return Thing_new (Art); } /* End of file Articulation.cpp */ sources_5316/artsynth/Artword_to_Art.cpp0000644000176700017670000000206411614541000017227 0ustar paulpaul/* Artword_to_Art.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Artword_to_Art.h" Art Artword_to_Art (Artword me, double tim) { try { autoArt thee = Art_create (); Artword_intoArt (me, thee.peek(), tim); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Articulation."); } } /* End of file Artword_to_Art.cpp */ sources_5316/artsynth/manual_Artsynth.cpp0000644000176700017670000002477611627222747017506 0ustar paulpaul/* manual_Artsynth.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" void manual_Artsynth_init (ManPages me); void manual_Artsynth_init (ManPages me) { MAN_BEGIN (L"Articulatory synthesis", L"ppgb", 201101028) INTRO (L"This is a description of the articulatory synthesis package in Praat. " "For a detailed description of the physics and mathematics behind the model, " "see @@Boersma (1998)@, chapters 2 and 3. " "For examples of how to synthesize utterances, consult http://www.fon.hum.uva.nl/paul/diss/ch5/.") ENTRY (L"How to start (after reading the @Intro)") NORMAL (L"We are going to have the synthesizer say [\\swp\\sw]. We need a @Speaker and an @Artword object.") NORMAL (L"1. Create a speaker with @@Create Speaker...@ from the @@New menu@.") NORMAL (L"2. Create an articulation word of 0.5 seconds with @@Create Artword...@.") NORMAL (L"3. Edit the Artword by selecting it and clicking ##View & Edit#.") NORMAL (L"4. To set the glottis to a position suitable for phonation, use the ArtwordEditor to " "set the %Interarytenoid activity to 0.5 throughout the utterance. You set two targets: " "0.5 at a time of 0 seconds, and 0.5 at a time of 0.5 seconds.") NORMAL (L"5. To prevent air escaping from the nose, close the nasopharyngeal port " "by setting the %LevatorPalatini activity to 1.0 throughout the utterance.") NORMAL (L"6. To generate the lung pressure needed for phonation, you set the %Lungs activity at 0 seconds to 0.2, " "and at 0.1 seconds to 0.") NORMAL (L"7. To force a jaw movement that closes the lips, set the %Masseter activity at 0.25 seconds to 0.7, " "and the %OrbicularisOris activity at 0.25 seconds to 0.2.") NORMAL (L"8. Select the Speaker and the Artword and click #Movie; " "you will see a closing-and-opening gesture of the mouth.") NORMAL (L"9. Select the Speaker and the Artword and click ##To Sound...# " "(see @@Artword & Speaker: To Sound...@).") NORMAL (L"10. Just click #OK; the synthesis starts.") NORMAL (L"11. If you are sitting at a 1997 computer, this will last for 5 minutes or so; at a 2010 computer, 6 seconds. " "If this is too slow for you, click #Interrupt. " "Otherwise, you can watch the vibrating vocal cords " "and the changing vocal-tract shape.") NORMAL (L"12. You can play, view, and analyse the resulting @Sound as you would any other. " "You can see and hear a sound movie if you select the Speaker, " "the Artword, and the Sound, and click #Play.") MAN_END MAN_BEGIN (L"Artword", L"ppgb", 20030316) INTRO (L"One of the @@types of objects@ in Praat. See @@Articulatory synthesis@.") NORMAL (L"An object of class Artword object represents the activities of several speech muscles as functions of time.") ENTRY (L"Artword commands") LIST_ITEM (L"\\bu @@Create Artword...@: creates an Artword with relaxed muscles") LIST_ITEM (L"\\bu @@Artword & Speaker: To Sound...@: articulatory synthesis") MAN_END MAN_BEGIN (L"Artword & Speaker: To Sound...", L"ppgb", 20040331) INTRO (L"A command to synthesize a @Sound object from the selected @Speaker and the selected @Artword.") NORMAL (L"This is the command that performs the actual articulatory synthesis. " "See @@Articulatory synthesis@.") ENTRY (L"Settings") TAG (L"##Sampling frequency (Hz)") DEFINITION (L"the number of times per second that the equilibrium widths and lengths and the tensions of the muscles " "are recomputed from the Artword. This will also be the sampling frequency of the resulting sound and " "of the optional resulting tube widths, air pressures, and air velocities. The standard value is 22050 Hz.") TAG (L"##Oversampling") DEFINITION (L"the number of times that the aerodynamic quantities and the state of the tube walls " "will be recomputed during each sample period. The standard value is 25.") TAG (L"##Width 1#, ##Width 2#, ##Width 3#") DEFINITION (L"the numbers (see below) of the tubes whose widths you want to monitor. " "E.g., if ##Width 1# is 36, the synthesizer will create a Sound object named $$width36$, " "which contains the width of tube 36 (the lower glottis) as a function of time, expressed in metres. " "To prevent the creation of a $$width$ object, specify $$0$ (the standard value).") TAG (L"##Pressure 1#, ##Pressure 2#, ##Pressure 3#") DEFINITION (L"the numbers (see below) of the tubes whose air pressures you want to monitor. " "E.g., if ##Pressure 3# is 37, the synthesizer will create a Sound object named $$pressure37$, " "which contains the air pressure of tube 37 (the upper glottis) as a function of time, expressed in Pascal. " "To prevent the creation of a $$pressure$ object, specify $$0$ (the standard value).") TAG (L"##Velocity 1#, ##Velocity 2#, ##Velocity 3") DEFINITION (L"the numbers (see below) of the tubes whose air velocities you want to monitor. " "E.g., if ##Velocity 1# is 60, the synthesizer will create a Sound object named $velocity60, " "which contains the air velocity of tube 60 (in the mouth) as a function of time, expressed in metres per second. " "To prevent the creation of a $velocity object, specify $0 (the standard value).") ENTRY (L"Stability") NORMAL (L"The internal sampling frequency for the aerodynamics is the specified ##Sampling frequency#, " "multiplied by the specified #Oversampling. With the standard settings, this is 22050 times 25 = 550750 Hz.") NORMAL (L"To ensure the stability of the synthesis, this internal sampling frequency should not be less than the " "velocity of sound (353 m/s) divided by the length of the shortest tube. For the standard #Female, " "#Male, and #Child speakers, the shortest tube is the upper glottis, which has a length " "of 0.7, 1.0, and 0.3 millimetres, respectively. The minimum internal sampling frequencies, therefore, " "are 504286, 353000, and 1176667 hertz, respectively.") ENTRY (L"Time resolution") NORMAL (L"To capture the microscopic pressure changes in the glottis, you will want maximum time resolution. " "For a female speaker, you could set ##Sampling frequency# to 550750 Hz, and #Oversampling to 1.") ENTRY (L"Tube numbers") NORMAL (L"Here are the tube numbers that you can use for the #Width, #Pressure, and #Velocity settings:") LIST_ITEM (L"1..23: lungs (from bottom to top)") LIST_ITEM (L"24..29: bronchi (from bottom to top)") LIST_ITEM (L"30..35: trachea (from bottom to top)") LIST_ITEM (L"36: lower glottis") LIST_ITEM (L"37: upper glottis (not for a one-mass model)") LIST_ITEM (L"38..49: pharynx (from bottom to top)") LIST_ITEM (L"50..51: nasopharyngeal branching") LIST_ITEM (L"52..64: mouth (from back to front)") LIST_ITEM (L"65..78: nose (from back to front)") LIST_ITEM (L"79..86: conus elasticus (only for a 10-mass model)") LIST_ITEM (L"87..89: glottal shunt between the arytenoids (from bottom to top)") NORMAL (L"Some structural properties:") LIST_ITEM (L"\\bu Tube 1 is closed at the bottom.") LIST_ITEM (L"\\bu Tubes 64 (lips) and 78 (nostrils) radiate into the air.") LIST_ITEM (L"\\bu The nasopharyngeal branch is at tubes 50, 51, and 65. They are constrained to have equal lengths.") LIST_ITEM (L"\\bu For a one-mass model of the vocal cords, tube 36 is connected to 38.") LIST_ITEM (L"\\bu For a 10-mass model, tubes 32..35 are replaced with 79..86, so that " "tube 31 is connected to 79, and 86 is connected to 36.") LIST_ITEM (L"\\bu A glottal shunt will be implemented if the speaker's $$shunt.Dx$ attribute is not zero. " "A branch is then made from tubes 34 and 35 (or 85 and 86) to 87, " "and from tube 89 to 38 and 39.") MAN_END MAN_BEGIN (L"Create Artword...", L"ppgb", 20101212) INTRO (L"A command to create an @Artword object with all muscle activities set to zero. " "See @@Articulatory synthesis@.") ENTRY (L"Settings") TAG (L"##Name") DEFINITION (L"the name that you give to the created object. The standard name is $$hallo$, " "but you should give it a more sensible name, possibly something that represents the utterance " "that it is supposed to generate.") TAG (L"##Duration (seconds)") DEFINITION (L"the duration of the resulting Artword. Should be as long as the utterance that " "you want to generate with it. The standard value is 1 second.") MAN_END MAN_BEGIN (L"Create Speaker...", L"ppgb", 20101212) INTRO (L"A command to create a @Speaker object. See @@Articulatory synthesis@.") ENTRY (L"Settings") TAG (L"##Name") DEFINITION (L"the name that you give to the created object. The standard name is \"speaker\", " "but if you work with multiple Speaker objects, give them sensible names to reduce confusion.") TAG (L"##Kind of speaker") DEFINITION (L"Choose from #Female, #Male, or #Child. The only difference is a relative size.") TAG (L"##Number of tubes in glottis") DEFINITION (L"Choose from #1, #2, or #10. See @@Artword & Speaker: To Sound...@ for details.") MAN_END MAN_BEGIN (L"Create Vocal Tract from phone...", L"ppgb", 19960908) INTRO (L"A way to create a @VocalTract object.") ENTRY (L"Purpose") NORMAL (L"to translate a phone symbol like [a], [u], etc., into a vocal-tract area function.") ENTRY (L"Behaviour") NORMAL (L"The resulting VocalTract will appear in the list of objects, " "with the same name as the phone.") ENTRY (L"Algorithm") NORMAL (L"The area function of the resulting VocalTract is taken from the Russian speaker from @@Fant (1960)@.") MAN_END MAN_BEGIN (L"Speaker", L"ppgb", 19980201) INTRO (L"One of the @@types of objects@ in Praat. See @@Articulatory synthesis@.") ENTRY (L"Speaker commands") LIST_ITEM (L"\\bu @@Create Speaker...") LIST_ITEM (L"\\bu @@Artword & Speaker: To Sound...@: articulatory synthesis") MAN_END MAN_BEGIN (L"VocalTract", L"ppgb", 20030316) INTRO (L"One of the @@types of objects@ in Praat.") NORMAL (L"A VocalTract object represents the area function of the vocal tract, expressed in m^2, " "running from the glottis to the lips.") MAN_END MAN_BEGIN (L"VocalTract: Formula...", L"ppgb", 20021206) INTRO (L"A command for changing the data in all selected @VocalTract objects.") NORMAL (L"See the @Formulas tutorial for examples and explanations.") MAN_END } /* End of file manual_Artsynth.cpp */ sources_5316/artsynth/Art_Speaker_to_VocalTract.cpp0000644000176700017670000000355411614541130021332 0ustar paulpaul/* Art_Speaker_to_VocalTract.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Delta.h" #include "Speaker_to_Delta.h" #include "Art_Speaker_Delta.h" #include "Art_Speaker_to_VocalTract.h" VocalTract Art_Speaker_to_VocalTract (Art art, Speaker speaker) { VocalTract thee = NULL; long isection; double area [300]; int numberOfSections; double sectionLength = 0.001; /* One millimetre. */ Delta delta = NULL; delta = Speaker_to_Delta (speaker); if (! delta) goto end; Art_Speaker_intoDelta (art, speaker, delta); numberOfSections = 0; for (isection = 1; isection <= 27; isection ++) { Delta_Tube tube = delta -> tube + 37 + isection; int numberOfConstantSections = floor (tube -> Dxeq / sectionLength + 0.5); double constantArea = tube -> Dyeq * tube -> Dzeq; int jsection; for (jsection = 1; jsection <= numberOfConstantSections; jsection ++) area [++ numberOfSections] = constantArea; } thee = VocalTract_create (numberOfSections, sectionLength); if (! thee) goto end; for (isection = 1; isection <= numberOfSections; isection ++) thy z [1] [isection] = area [isection]; end: forget (delta); return thee; } /* End of file Art_Speaker_to_VocalTract.cpp */ sources_5316/artsynth/Artword.h0000644000176700017670000000527211625721237015406 0ustar paulpaul#ifndef _Artword_h_ #define _Artword_h_ /* Artword.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Articulation.h" #include "Graphics.h" #include "Artword_def.h" oo_CLASS_CREATE (Artword, Data); Artword Artword_create (double totalTime); void Artword_setDefault (Artword me, int feature); /* Postconditions: my data [feature]. numberOfTargets == 2; my data [feature]. times [1] == 0.0; my data [feature]. times [2] == self -> totalTime; my data [feature]. targets [1] == 0.0; my data [feature]. targets [2] == 0.0; rest unchanged; */ void Artword_setTarget (Artword me, int feature, double tim, double value); double Artword_getTarget (Artword me, int feature, double tim); void Artword_removeTarget (Artword me, int feature, int iTarget); /* Function: remove one target from the target list of "feature". If "iTarget" is the first or the last target in the list, only set the target to zero (begin and end targets remain). Preconditions: self != NULL; feature in enum Art_MUSCLE; iTarget >= 1; iTarget <= self -> data [feature]. numberOfTargets; Postconditions: if (iTarget == 1) self -> data [feature]. targets [1] == 0.0; else if (iTarget == self -> data [feature]. numberOfTargets) self -> data [feature]. targets [iTarget] == 0.0; else self -> data [feature]. numberOfTargets == old self -> data [feature]. numberOfTargets - 1; for (i == iTarget..self -> data [feature]. numberOfTargets) self -> data [feature]. times [i] == old self -> data [feature]. times [i + 1]; self -> data [feature]. targets [i] == old self -> data [feature]. targets [i + 1]; */ /* Implemented methods: int Artword::writeText (I, FILE *f) writes an Artword as text to the stream f. */ void Artword_intoArt (Artword me, Art art, double tim); /* Function: Linear interpolation between targets, into an existing Art. Preconditions: me != NULL; art != NULL; */ void Artword_draw (Artword me, Graphics graphics, int feature, int garnish); /* End of file Artword.h */ #endif sources_5316/artsynth/Art_Speaker_to_VocalTract.h0000644000176700017670000000170211611107117020770 0ustar paulpaul/* Art_Speaker_to_VocalTract.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Articulation.h" #include "Speaker.h" #include "VocalTract.h" VocalTract Art_Speaker_to_VocalTract (Art art, Speaker speaker); /* End of file Art_Speaker_to_VocalTract.h */ sources_5316/artsynth/Speaker.cpp0000644000176700017670000001101611621176037015700 0ustar paulpaul/* Speaker.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Speaker.h" #include "oo_DESTROY.h" #include "Speaker_def.h" #include "oo_COPY.h" #include "Speaker_def.h" #include "oo_EQUAL.h" #include "Speaker_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Speaker_def.h" #include "oo_WRITE_TEXT.h" #include "Speaker_def.h" #include "oo_READ_TEXT.h" #include "Speaker_def.h" #include "oo_WRITE_BINARY.h" #include "Speaker_def.h" #include "oo_READ_BINARY.h" #include "Speaker_def.h" #include "oo_DESCRIPTION.h" #include "Speaker_def.h" Thing_implement (Speaker, Data, 0); Speaker Speaker_create (wchar *kindOfSpeaker, int numberOfVocalCordMasses) { Speaker me = Thing_new (Speaker); /* Supralaryngeal dimensions are taken from P. Mermelstein (1973): */ /* "Articulatory model for the study of speech production", */ /* Journal of the Acoustical Society of America 53,1070 - 1082. */ /* That was a male speaker, so we need scaling for other speakers: */ double scaling; if (! me) return NULL; if (wcsequ (kindOfSpeaker, L"Male")) my relativeSize = 1.1; else if (wcsequ (kindOfSpeaker, L"Child")) my relativeSize = 0.7; else my relativeSize = 1.0; scaling = my relativeSize; /* Laryngeal system. Data for male speaker from Ishizaka and Flanagan. */ if (wcsequ (kindOfSpeaker, L"Female")) { my lowerCord.thickness = 1.4e-3; /* dx, in metres */ my upperCord.thickness = 0.7e-3; my cord.length = 10e-3; my lowerCord.mass = 0.02e-3; /* kilograms */ my upperCord.mass = 0.01e-3; my lowerCord.k1 = 10; /* Newtons per metre */ my upperCord.k1 = 4; } else if (wcsequ (kindOfSpeaker, L"Male")) { my lowerCord.thickness = 2.0e-3; /* dx, in metres */ my upperCord.thickness = 1.0e-3; my cord.length = 18e-3; my lowerCord.mass = 0.1e-3; /* kilograms */ my upperCord.mass = 0.05e-3; my lowerCord.k1 = 12; /* Newtons per metre */ my upperCord.k1 = 4; } else /* "Child" */ { my lowerCord.thickness = 0.7e-3; /* dx, in metres */ my upperCord.thickness = 0.3e-3; my cord.length = 6e-3; my lowerCord.mass = 0.003e-3; /* kilograms */ my upperCord.mass = 0.002e-3; my lowerCord.k1 = 6; /* Newtons per metre */ my upperCord.k1 = 2; } my cord.numberOfMasses = numberOfVocalCordMasses; if (numberOfVocalCordMasses == 1) { my lowerCord.thickness += my upperCord.thickness; my lowerCord.mass += my upperCord.mass; my lowerCord.k1 += my upperCord.k1; } /* Supralaryngeal system. Data from Mermelstein. */ my velum.x = -0.031 * scaling; my velum.y = 0.023 * scaling; my velum.a = atan2 (my velum.y, my velum.x); my palate.radius = sqrt (my velum.x * my velum.x + my velum.y * my velum.y); my tip.length = 0.034 * scaling; my neutralBodyDistance = 0.086 * scaling; my alveoli.x = 0.024 * scaling; my alveoli.y = 0.0302 * scaling; my alveoli.a = atan2 (my alveoli.y, my alveoli.x); my teethCavity.dx1 = -0.009 * scaling; my teethCavity.dx2 = -0.004 * scaling; my teethCavity.dy = -0.011 * scaling; my lowerTeeth.a = -0.30; /* radians */ my lowerTeeth.r = 0.113 * scaling; /* metres */ my upperTeeth.x = 0.036 * scaling; my upperTeeth.y = 0.026 * scaling; my lowerLip.dx = 0.010 * scaling; my lowerLip.dy = -0.004 * scaling; my upperLip.dx = 0.010 * scaling; my upperLip.dy = 0.004 * scaling; my nose.Dx = 0.007 * scaling; my nose.Dz = 0.014 * scaling; my nose.weq [0] = 0.018 * scaling; my nose.weq [1] = 0.016 * scaling; my nose.weq [2] = 0.014 * scaling; my nose.weq [3] = 0.020 * scaling; my nose.weq [4] = 0.023 * scaling; my nose.weq [5] = 0.020 * scaling; my nose.weq [6] = 0.035 * scaling; my nose.weq [7] = 0.035 * scaling; my nose.weq [8] = 0.030 * scaling; my nose.weq [9] = 0.022 * scaling; my nose.weq [10] = 0.016 * scaling; my nose.weq [11] = 0.010 * scaling; my nose.weq [12] = 0.012 * scaling; my nose.weq [13] = 0.013 * scaling; return me; } /* End of file Speaker.cpp */ sources_5316/artsynth/Artword_def.h0000644000176700017670000000232411621131500016177 0ustar paulpaul/* Artword_def.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT ArtwordData oo_DEFINE_STRUCT (ArtwordData) oo_INT (numberOfTargets) oo_DOUBLE_VECTOR (targets, numberOfTargets) oo_DOUBLE_VECTOR (times, numberOfTargets) #if oo_DECLARING oo_INT (_iTarget) #endif oo_END_STRUCT (ArtwordData) #undef ooSTRUCT #define ooSTRUCT Artword oo_DEFINE_CLASS (Artword, Data) oo_DOUBLE (totalTime) oo_STRUCT_SET (ArtwordData, data, kArt_muscle) oo_END_CLASS (Artword) #undef ooSTRUCT /* End of file Artword_def.h */ sources_5316/artsynth/Articulation_enums.h0000644000176700017670000000672111161310376017622 0ustar paulpaul/* Articulation_enums.h * * Copyright (C) 1992-2009 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 1996/06/11 * pb 2002/07/16 GPL * pb 2009/03/21 modern enums */ enums_begin (kArt_muscle, 0) enums_add (kArt_muscle, 0, _, L"_") enums_add (kArt_muscle, 1, LUNGS, L"Lungs") enums_add (kArt_muscle, 2, INTERARYTENOID, L"Interarytenoid") // constriction of larynx; 0 = breathing, 1 = constricted glottis enums_add (kArt_muscle, 3, CRICOTHYROID, L"Cricothyroid") // vocal-cord tension enums_add (kArt_muscle, 4, VOCALIS, L"Vocalis") // vocal-cord tension enums_add (kArt_muscle, 5, THYROARYTENOID, L"Thyroarytenoid") enums_add (kArt_muscle, 6, POSTERIOR_CRICOARYTENOID, L"PosteriorCricoarytenoid") // opening of glottis enums_add (kArt_muscle, 7, LATERAL_CRICOARYTENOID, L"LateralCricoarytenoid") // opening of glottis enums_add (kArt_muscle, 8, STYLOHYOID, L"Stylohyoid") // up movement of hyoid bone enums_add (kArt_muscle, 9, STERNOHYOID, L"Sternohyoid") // down movement of hyoid bone enums_add (kArt_muscle, 10, THYROPHARYNGEUS, L"Thyropharyngeus") // constriction of ventricular folds enums_add (kArt_muscle, 11, LOWER_CONSTRICTOR, L"LowerConstrictor") enums_add (kArt_muscle, 12, MIDDLE_CONSTRICTOR, L"MiddleConstrictor") enums_add (kArt_muscle, 13, UPPER_CONSTRICTOR, L"UpperConstrictor") enums_add (kArt_muscle, 14, SPHINCTER, L"Sphincter") // constriction of pharynx enums_add (kArt_muscle, 15, HYOGLOSSUS, L"Hyoglossus") // down movement of tongue body enums_add (kArt_muscle, 16, STYLOGLOSSUS, L"Styloglossus") // up movement of tongue body enums_add (kArt_muscle, 17, GENIOGLOSSUS, L"Genioglossus") // forward movement of tongue body enums_add (kArt_muscle, 18, UPPER_TONGUE, L"UpperTongue") // up curling of the tongue tip enums_add (kArt_muscle, 19, LOWER_TONGUE, L"LowerTongue") // down curling of the tongue enums_add (kArt_muscle, 20, TRANSVERSE_TONGUE, L"TransverseTongue") // thickening of tongue enums_add (kArt_muscle, 21, VERTICAL_TONGUE, L"VerticalTongue") // thinning of tongue enums_add (kArt_muscle, 22, RISORIUS, L"Risorius") // spreading of lips enums_add (kArt_muscle, 23, ORBICULARIS_ORIS, L"OrbicularisOris") // rounding of lips enums_add (kArt_muscle, 24, LEVATOR_PALATINI, L"LevatorPalatini") // closing of velo-pharyngeal port; 0 = open ("nasal"), 1 = closed ("oral") enums_add (kArt_muscle, 25, TENSOR_PALATINI, L"TensorPalatini") enums_add (kArt_muscle, 26, MASSETER, L"Masseter") // closing of jaw; 0 = open, 1 = closed enums_add (kArt_muscle, 27, MYLOHYOID, L"Mylohyoid") // opening of jaw enums_add (kArt_muscle, 28, LATERAL_PTERYGOID, L"LateralPterygoid") // horizontal jaw position enums_add (kArt_muscle, 29, BUCCINATOR, L"Buccinator") // oral wall tension enums_end (kArt_muscle, 29, LUNGS) /* End of file Articulation.enums */ sources_5316/artsynth/Artword_Speaker.cpp0000644000176700017670000000325111614541130017374 0ustar paulpaul/* Artword_Speaker.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Art_Speaker.h" #include "Artword_Speaker.h" void Artword_Speaker_draw (Artword artword, Speaker speaker, Graphics g, int numberOfSteps) { double oldLineWidth = Graphics_inqLineWidth (g); Art art = Art_create (); for (int i = 0; i <= numberOfSteps; i ++) { Artword_intoArt (artword, art, i * artword -> totalTime / numberOfSteps); Graphics_setLineWidth (g, 2 + i + i); Art_Speaker_draw (art, speaker, g); } forget (art); Graphics_setLineWidth (g, oldLineWidth); } void Artword_Speaker_movie (Artword artword, Speaker speaker, Graphics g) { double timeStep = 0.00001; Art art = Art_create (); for (double tim = 0.0; tim < artword -> totalTime; tim += timeStep) { Artword_intoArt (artword, art, tim); Graphics_setViewport (g, 0, 1, 0, 1); Graphics_clearWs (g); Art_Speaker_draw (art, speaker, g); Graphics_flushWs (g); // TODO: we should pause here a bit } } /* End of file Artword_Speaker.cpp */ sources_5316/artsynth/Articulation_def.h0000644000176700017670000000164111620745777017246 0ustar paulpaul/* Articulation_def.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Art oo_DEFINE_CLASS (Art, Data) oo_DOUBLE_SET (art, kArt_muscle) oo_END_CLASS (Art) #undef ooSTRUCT /* End of file Articulation_def.h */ sources_5316/artsynth/Delta.h0000644000176700017670000000474011621127261015005 0ustar paulpaul#ifndef _Delta_h_ #define _Delta_h_ /* Delta.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Thing.h" typedef struct structDelta_Tube *Delta_Tube; struct structDelta_Tube { /* Structure: static. */ Delta_Tube left1; /* If NULL: closed at left edge. */ Delta_Tube left2; /* If not NULL: two merging streams. */ Delta_Tube right1; /* If NULL: radiation at right edge. */ Delta_Tube right2; /* If not NULL: a stream splitting into two. */ long parallel; /* Parallel subdivision. */ /* Controlled by articulation: quasistatic. */ double Dxeq, Dyeq, Dzeq; double mass, k1, k3, Brel, s1, s3, dy; double k1left1, k1left2, k1right1, k1right2; /* Linear coupling factors. */ double k3left1, k3left2, k3right1, k3right2; /* Cubic coupling factors. */ /* Dynamic. */ double Jhalf, Jleft, Jleftnew, Jright, Jrightnew; double Qhalf, Qleft, Qleftnew, Qright, Qrightnew; double Dx, Dxnew, dDxdt, dDxdtnew, Dxhalf; double Dy, Dynew, dDydt, dDydtnew; double Dz; double A, Ahalf, Anew, V, Vnew; double e, ehalf, eleft, eleftnew, eright, erightnew, ehalfold; double p, phalf, pleft, pleftnew, pright, prightnew; double Kleft, Kleftnew, Kright, Krightnew, Pturbright, Pturbrightnew; double B, r, R, DeltaP, v; }; Thing_define (Delta, Thing) { // functions: public: void init (int numberOfTubes); // new data: public: int numberOfTubes; // >= 1 struct structDelta_Tube *tube; // tube [1..numberOfTubes] // overridden methods: virtual void v_destroy (); }; Delta Delta_create (int numberOfTubes); /* Function: return a new Delta. Preconditions: numberOfTubes >= 1; Postconditions: result -> numberOfTubes = numberOfTubes; all members of result -> tube [1..numberOfTubes] are zero or NULL, except 'parallel', which is 1. */ /* End of file Delta.h */ #endif sources_5316/fon/0000755000176700017670000000000011757244463012522 5ustar paulpaulsources_5316/fon/Pitch_def.h0000644000176700017670000000656711724660617014573 0ustar paulpaul/* Pitch_def.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Attributes: xmin // Start time (seconds). xmax > xmin // End time (seconds). nx >= 1 // Number of time slices. dx > 0.0 // Time step (seconds). x1 // Centre of first time slice (seconds). ceiling // Candidates with a higher frequency are unvoiced. maxnCandidates >= 1 // Maximum number of candidates per time slice. frame[1..nx].nCandidates // Number of candidates in each time slice, including the unvoiced candidate. frame[1..nx].candidate[1..nCandidates].frequency // The frequency of each candidate (Hz), 0 means aperiodic or silent. // candidate[1].frequency is the frequency of the currently best candidate. frame[1..nx].candidate[1..nCandidates].strength // The strength of each candidate, a real number between 0 and 1: // 0 means not periodic at all, 1 means perfectly periodic; // if the frequency of the candidate is 0, its strength is a real number // that represents the maximum periodicity that // can still be considered to be due to noise (e.g., 0.4). // candidate[1].strength is the strength of the currently best candidate. frame[1..nx].intensity // The relative intensity of each frame, a real number between 0 and 1. */ #define ooSTRUCT Pitch_Candidate oo_DEFINE_STRUCT (Pitch_Candidate) oo_DOUBLE (frequency) oo_DOUBLE (strength) oo_END_STRUCT (Pitch_Candidate) #undef ooSTRUCT #define ooSTRUCT Pitch_Frame oo_DEFINE_STRUCT (Pitch_Frame) #if oo_READING_BINARY if (localVersion < 0) { oo_INT (nCandidates) oo_FLOAT (intensity) } else if (localVersion == 0) { oo_FLOAT (intensity) oo_LONG (nCandidates) } else { oo_DOUBLE (intensity) oo_LONG (nCandidates) } #else oo_DOUBLE (intensity) oo_LONG (nCandidates) #endif oo_STRUCT_VECTOR (Pitch_Candidate, candidate, nCandidates) oo_END_STRUCT (Pitch_Frame) #undef ooSTRUCT #define ooSTRUCT Pitch oo_DEFINE_CLASS (Pitch, Sampled) oo_DOUBLE (ceiling) oo_INT (maxnCandidates) oo_STRUCT_VECTOR (Pitch_Frame, frame, nx) #if oo_DECLARING // overridden methods: virtual void v_info (); virtual int v_domainQuantity () { return MelderQuantity_TIME_SECONDS; } virtual int v_getMinimumUnit (long ilevel); virtual int v_getMaximumUnit (long ilevel); virtual const wchar * v_getUnitText (long ilevel, int unit, unsigned long flags); virtual bool v_isUnitLogarithmic (long ilevel, int unit); virtual double v_convertStandardToSpecialUnit (double value, long ilevel, int unit); virtual double v_convertSpecialToStandardUnit (double value, long ilevel, int unit); virtual double v_getValueAtSample (long isamp, long ilevel, int unit); #endif oo_END_CLASS (Pitch) #undef ooSTRUCT /* End of file Pitch_def.h */ sources_5316/fon/Intensity.cpp0000644000176700017670000001074411621636071015210 0ustar paulpaul/* Intensity.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Intensity.h" Thing_implement (Intensity, Vector, 2); void structIntensity :: v_info () { structData :: v_info (); MelderInfo_writeLine1 (L"Time domain:"); MelderInfo_writeLine3 (L" Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine3 (L" End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine3 (L" Total duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine1 (L"Time sampling:"); MelderInfo_writeLine2 (L" Number of frames: ", Melder_integer (nx)); MelderInfo_writeLine3 (L" Time step: ", Melder_double (dx), L" seconds"); MelderInfo_writeLine3 (L" First frame centred at: ", Melder_double (x1), L" seconds"); } double structIntensity :: v_convertStandardToSpecialUnit (double value, long ilevel, int unit) { (void) ilevel; if (unit == 1) { return pow (10.0, 0.1 * value); // energy } else if (unit == 2) { return pow (2.0, 0.1 * value); // sones } return value; // default, especially if units == 0 (as in Vector_getMean) or units == 3 (averaging_DB) } double structIntensity :: v_convertSpecialToStandardUnit (double value, long ilevel, int unit) { (void) ilevel; return unit == 1 ? 10.0 * log10 (value) : // value = energy unit == 2 ? 10.0 * NUMlog2 (value) : // value = sones value; // value = dB } void Intensity_init (Intensity me, double tmin, double tmax, long nt, double dt, double t1) { Matrix_init (me, tmin, tmax, nt, dt, t1, 1.0, 1.0, 1, 1.0, 1.0); } Intensity Intensity_create (double tmin, double tmax, long nt, double dt, double t1) { try { autoIntensity me = Thing_new (Intensity); Intensity_init (me.peek(), tmin, tmax, nt, dt, t1); return me.transfer(); } catch (MelderError) { Melder_throw ("Intensity not created."); } } Matrix Intensity_to_Matrix (Intensity me) { try { autoMatrix thee = Thing_new (Matrix); my structMatrix :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Intensity."); } } Intensity Matrix_to_Intensity (Matrix me) { try { autoIntensity thee = Thing_new (Intensity); my structMatrix :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Matrix."); } } void Intensity_drawInside (Intensity me, Graphics g, double tmin, double tmax, double minimum, double maximum) { if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } // autowindow long itmin, itmax; Matrix_getWindowSamplesX (me, tmin, tmax, & itmin, & itmax); if (maximum <= minimum) Matrix_getWindowExtrema (me, itmin, itmax, 1, 1, & minimum, & maximum); // autoscale if (maximum <= minimum) { minimum -= 10; maximum += 10; } Graphics_setWindow (g, tmin, tmax, minimum, maximum); Graphics_function (g, my z [1], itmin, itmax, Matrix_columnToX (me, itmin), Matrix_columnToX (me, itmax)); } void Intensity_draw (Intensity me, Graphics g, double tmin, double tmax, double minimum, double maximum, int garnish) { Graphics_setInner (g); Intensity_drawInside (me, g, tmin, tmax, minimum, maximum); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Time (s)"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_textLeft (g, 1, L"Intensity (dB)"); } } double Intensity_getQuantile (Intensity me, double tmin, double tmax, double quantile) { return Sampled_getQuantile (me, tmin, tmax, quantile, 0, Intensity_units_DB); } double Intensity_getAverage (Intensity me, double tmin, double tmax, int averagingMethod) { return averagingMethod == Intensity_averaging_MEDIAN ? Intensity_getQuantile (me, tmin, tmax, 0.50) : Sampled_getMean_standardUnit (me, tmin, tmax, 0, averagingMethod, TRUE); } /* End of file Intensity.cpp */ sources_5316/fon/Cochleagram.h0000644000176700017670000000527411621633706015100 0ustar paulpaul#ifndef _Cochleagram_h_ #define _Cochleagram_h_ /* Cochleagram.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Matrix.h" Thing_define (Cochleagram, Matrix) { // overridden methods: protected: virtual int v_domainQuantity () { return MelderQuantity_TIME_SECONDS; } }; /* Normally, the attributes will meet the following: xmin; // Start time (seconds). xmax; // End time (seconds). nx; // Number of time slices. dx; // Time step (seconds). x1; // Centre of first time sample (seconds). ymin = 0; // Minimum frequency (Bark). ymax = 25.6; // Maximum frequency (Bark). ny; // Number of frequencies. dy = 25.6 / ny; // Frequency step (Bark). y1 = 0.5 * dy; // Centre of first frequency band (Bark). z; // Basilar filter output (milliVolt), or firing rate (Hz), or intensity (phon). */ Cochleagram Cochleagram_create (double tmin, double tmax, long nt, double dt, double t1, double df, long nf); /* Function: return a new instance of Cochleagram, or NULL if out of memory. Preconditions: dt > 0.0; df > 0.0; nt >= 1; nf >= 1; Postconditions: result -> xmin == tmin; result -> ymin == 0.0; result -> xmax == tmax; result -> ymax == 25.6; result -> nx == nt; result -> ny == nf; result -> dx == dt; result -> dy == df; result -> x1 == t1; result -> y1 == 0.5 * df; result -> z [1..nf] [1..nt] == 0.0; */ void Cochleagram_paint (Cochleagram me, Graphics g, double tmin, double tmax, int garnish); double Cochleagram_difference (Cochleagram me, Cochleagram thee, double tmin, double tmax); Cochleagram Matrix_to_Cochleagram (Matrix me); /* Function: create a Cochleagram from a Matrix, with deep copy of all its attributes, except class information and methods. Return NULL if out of memory. */ Matrix Cochleagram_to_Matrix (Cochleagram me); /* Function: create a Matrix from a Cochleagram, with deep copy of all its attributes, except class information and methods. Return NULL if out of memory. */ /* End of file Cochleagram.h */ #endif sources_5316/fon/FunctionEditor.h0000644000176700017670000002510211702525426015616 0ustar paulpaul#ifndef _FunctionEditor_h_ #define _FunctionEditor_h_ /* FunctionEditor.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Editor.h" #include "Graphics.h" #include "Function.h" struct FunctionEditor_picture { /* KEEP IN SYNC WITH PREFS. */ bool garnish; }; Thing_define (FunctionEditor, Editor) { // new data: public: /* Subclass may change the following attributes, */ /* but has to respect the invariants, */ /* and has to call FunctionEditor_marksChanged () */ /* immediately after making the changes. */ double tmin, tmax, startWindow, endWindow; double startSelection, endSelection; // markers /* These attributes are all expressed in seconds. Invariants: */ /* tmin <= startWindow < endWindow <= tmax; */ /* tmin <= (startSelection, endSelection) <= tmax; */ double arrowScrollStep; Graphics graphics; // used in the 'draw' method short functionViewerLeft, functionViewerRight; // size of drawing areas in pixels short selectionViewerLeft, selectionViewerRight; // size of drawing areas in pixels short height; // size of drawing areas in pixels GuiObject text; // optional text at top int shiftKeyPressed; // information for the 'play' method. bool playingCursor, playingSelection; // information for end of play struct FunctionEditor_picture picture; /* Private: */ GuiObject drawingArea, scrollBar, groupButton, bottomArea; bool group, enableUpdates, d_hasSelectionViewer; int nrect; struct { double left, right, bottom, top; } rect [8]; double marker [1 + 3], playCursor, startZoomHistory, endZoomHistory; int numberOfMarkers; // overridden methods: virtual void v_destroy (); virtual void v_info (); virtual void v_createMenus (); virtual void v_createMenuItems_file (EditorMenu menu); virtual void v_createMenuItems_query (EditorMenu menu); virtual void v_createChildren (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_dataChanged (); // new methods: virtual void v_draw () { } /* * Message: "draw your part of the data between startWindow and endWindow." */ virtual void v_drawSelectionViewer () { } virtual void v_prepareDraw () { } // for less flashing virtual const wchar * v_format_domain () { return L"Time domain:"; } virtual const wchar * v_format_short () { return L"%.3f"; } virtual const wchar * v_format_long () { return L"%f"; } virtual const wchar * v_format_units () { return L"seconds"; } virtual const wchar * v_format_totalDuration () { return L"Total duration %f seconds"; } virtual const wchar * v_format_window () { return L"Visible part %f seconds"; } virtual const wchar * v_format_selection () { return L"%f (%.3f / s)"; } virtual int v_fixedPrecision_long () { return 6; } virtual bool v_hasText () { return false; } virtual void v_play (double a_tmin, double a_tmax) { (void) a_tmin; (void) a_tmax; } /* * Message: "the user clicked in one of the rectangles above or below the data window." */ virtual int v_click (double xWC, double yWC, bool shiftKeyPressed); /* * Message: "the user clicked in data window with the left mouse button." * 'xWC' is the time; * 'yWC' is a value between 0.0 (bottom) and 1.0 (top); * 'shiftKeyPressed' flags if the Shift key was held down during the click. * Constraints: * Return FunctionEditor_UPDATE_NEEDED if you want a window update, i.e., * if your 'click' moves the cursor or otherwise changes the appearance of the data. * Return FunctionEditor_NO_UPDATE_NEEDED if you do not want a window update, e.g., * if your 'click' method just 'plays' something or puts a dialog on the screen. * In the latter case, the 'ok' callback of the dialog should * call FunctionEditor_marksChanged if necessary. * Behaviour of FunctionEditor::click (): * moves the cursor to 'xWC', drags to create a selection, or extends the selection. */ virtual int v_clickB (double xWC, double yWC); virtual int v_clickE (double xWC, double yWC); virtual void v_key (unsigned char key) { (void) key; } virtual int v_playCallback (int phase, double tmin, double tmax, double t); virtual void v_updateText () { } virtual void v_prefs_addFields (EditorCommand cmd) { (void) cmd; } virtual void v_prefs_setValues (EditorCommand cmd) { (void) cmd; } virtual void v_prefs_getValues (EditorCommand cmd) { (void) cmd; } virtual void v_createMenuItems_file_draw (EditorMenu menu) { (void) menu; } virtual void v_createMenuItems_file_extract (EditorMenu menu) { (void) menu; } virtual void v_createMenuItems_file_write (EditorMenu menu) { (void) menu; } virtual void v_createMenuItems_view (EditorMenu menu); virtual void v_createMenuItems_view_timeDomain (EditorMenu menu); virtual void v_createMenuItems_view_audio (EditorMenu menu); virtual void v_highlightSelection (double left, double right, double bottom, double top); virtual void v_unhighlightSelection (double left, double right, double bottom, double top); virtual double v_getBottomOfSoundArea () { return 0.0; } virtual double v_getBottomOfSoundAndAnalysisArea () { return 0.0; } virtual void v_form_pictureSelection (EditorCommand cmd); virtual void v_ok_pictureSelection (EditorCommand cmd); virtual void v_do_pictureSelection (EditorCommand cmd); }; int theFunctionEditor_playCallback (void *void_me, int phase, double tmin, double tmax, double t); /* Attributes: data: must be a Function. int clickB (I, double xWC, double yWC); "user clicked in data window with the middle mouse button (Mac: control- or option-click)." 'xWC' is the time; 'yWC' is a value between 0.0 (bottom) and 1.0 (top). For the return value, see the 'click' method. FunctionEditor::clickB simply moves the start of the selection (B) to 'xWC', with the sole statement 'my startSelection = xWC'. int clickE (I, double xWC, double yWC); "user clicked in data window with the right mouse button (Mac: command-click)." 'xWC' is the time; 'yWC' is a value between 0.0 (bottom) and 1.0 (top). For the return value, see the 'click' method. FunctionEditor::clickB simply moves the end of the selection (E) to 'xWC', with the sole statement 'my endSelection = xWC'. void key (I, unsigned char key); "user typed a key to the data window." FunctionEditor::key ignores this message. */ #define FunctionEditor_UPDATE_NEEDED 1 #define FunctionEditor_NO_UPDATE_NEEDED 0 void FunctionEditor_init (FunctionEditor me, GuiObject parent, const wchar *title, Function data); /* Function: creates an Editor with a drawing area, a scroll bar and some buttons. Preconditions: parent != NULL; Postconditions: my drawingArea is attached to the form at all sides, my scrollBar only to the bottom, left and right sides. */ void FunctionEditor_marksChanged (FunctionEditor me); /* Function: update optional text field, the scroll bar, the drawing area and the buttons, from the current total time, window, cursor, and selection, and redraw the contents. This will be done for all the editors in the group. Usage: call this after a change in any of the markers or in the duration of the data. */ void FunctionEditor_shift (FunctionEditor me, double shift); /* Function: shift (scroll) the window through time, keeping the window length constant. Usage: call this after a search. */ void FunctionEditor_updateText (FunctionEditor me); /* Function: update the optional text widget. Usage: call this after moving the cursor, if that would have to change the text. The generic FunctionEditor also calls this if one of the other marks have changed. Behaviour: we just call the updateText method, which the inheritor will have to modify, since FunctionEditor::updateText does nothing. */ void FunctionEditor_redraw (FunctionEditor me); /* Function: update the drawing area of a single editor. Usage: calls this after she changes a view option (font, scaling, hide/show xx) or after any of the data have changed. In the latter case, also call Editor_broadcastChange. Behaviour: we just call Graphics_updateWs (my graphics). */ void FunctionEditor_enableUpdates (FunctionEditor me, bool enable); /* Function: temporarily disable update event to cause 'draw' messages. Usage: If you call from your 'draw' method routines that may trigger expose events, you should bracket those routines between FunctionEditor_enableUpdates (me, false); and FunctionEditor_enableUpdates (me, true); This may happen if you call an analysis routine which calls Melder_progress. */ void FunctionEditor_ungroup (FunctionEditor me); /* Function: force me out of the group. Usage: Start cut or paste methods by calling this routine, as the grouped editors will not be synchronized after either of those actions. Worse, the selection may get outside the common interval of the editors. */ void FunctionEditor_prefs (void); /* Some routines to enforce common look to all function editors. */ /* The x axis of the window is supposed to have been set to [my startWindow, my endWindow]. */ /* Preconditions: default line type, default line width. */ /* Postconditions: default line type, default line width, undefined colour, undefined text alignment. */ void FunctionEditor_drawRangeMark (FunctionEditor me, double yWC, const wchar_t *yWC_string, const wchar_t *units, int verticalAlignment); void FunctionEditor_drawCursorFunctionValue (FunctionEditor me, double yWC, const wchar_t *yWC_string, const wchar_t *units); void FunctionEditor_insertCursorFunctionValue (FunctionEditor me, double yWC, const wchar_t *yWC_string, const wchar_t *units, double minimum, double maximum); void FunctionEditor_drawHorizontalHair (FunctionEditor me, double yWC, const wchar_t *yWC_string, const wchar_t *units); void FunctionEditor_drawGridLine (FunctionEditor me, double yWC); void FunctionEditor_insetViewport (FunctionEditor me); void FunctionEditor_garnish (FunctionEditor me); // Optionally selection times and selection hairs. /* End of file FunctionEditor.h */ #endif sources_5316/fon/Ltas_to_SpectrumTier.h0000644000176700017670000000161711614424561017002 0ustar paulpaul/* Ltas_to_SpectrumTier.h * * Copyright (C) 2007-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Ltas.h" #include "SpectrumTier.h" SpectrumTier Ltas_to_SpectrumTier_peaks (Ltas me); /* End of file Ltas_to_SpectrumTier.h */ sources_5316/fon/Pitch_AnyTier_to_PitchTier.cpp0000644000176700017670000000577711606670120020407 0ustar paulpaul/* Pitch_AnyTier_to_PitchTier.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2005/06/16 units * pb 2011/06/04 C++ */ #include "Pitch_AnyTier_to_PitchTier.h" #include "Pitch_to_PitchTier.h" PitchTier PitchTier_AnyTier_to_PitchTier (PitchTier pitch, AnyTier tier) { try { SortedSetOfDouble points = tier -> points; if (pitch -> points -> size == 0) Melder_throw ("No pitch points."); /* * Result's domain is a union of both domains. */ autoPitchTier thee = PitchTier_create ( pitch -> xmin < tier -> xmin ? pitch -> xmin : tier -> xmin, pitch -> xmax > tier -> xmax ? pitch -> xmax : tier -> xmax); /* * Copy pitch's frequencies at tier's points to the resulting PitchTier. */ for (long ipoint = 1; ipoint <= points -> size; ipoint ++) { AnyPoint point = (AnyPoint) points -> item [ipoint]; double time = point -> number; double frequency = RealTier_getValueAtTime (pitch, time); RealTier_addPoint (thee.peek(), time, frequency); } return thee.peek(); } catch (MelderError) { Melder_throw (pitch, " & ", tier, ": not converted to PitchTier."); } } PitchTier Pitch_AnyTier_to_PitchTier (Pitch pitch, AnyTier tier, int checkMethod) { try { SortedSetOfDouble points = tier -> points; if (checkMethod == 2) { autoPitchTier temp = Pitch_to_PitchTier (pitch); autoPitchTier thee = PitchTier_AnyTier_to_PitchTier (temp.peek(), tier); return thee.transfer(); } /* * Result's domain is a union of both domains. */ autoPitchTier thee = PitchTier_create ( pitch -> xmin < tier -> xmin ? pitch -> xmin : tier -> xmin, pitch -> xmax > tier -> xmax ? pitch -> xmax : tier -> xmax); /* * Copy pitch's frequencies at tier's points to the resulting PitchTier. */ for (long ipoint = 1; ipoint <= points -> size; ipoint ++) { AnyPoint point = (AnyPoint) points -> item [ipoint]; double time = point -> number; double frequency = Pitch_getValueAtTime (pitch, time, kPitch_unit_HERTZ, Pitch_LINEAR); if (frequency == NUMundefined && checkMethod) Melder_throw ("No periodicity at time ", time, " seconds."); RealTier_addPoint (thee.peek(), time, frequency); } return thee.transfer(); } catch (MelderError) { Melder_throw (pitch, " & ", tier, ": not converted to PitchTier."); } } /* End of file Pitch_AnyTier_to_PitchTier.cpp */ sources_5316/fon/Pitch_Intensity.h0000644000176700017670000000176711614424561016012 0ustar paulpaul/* Pitch_Intensity.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Pitch.h" #include "Intensity.h" #include "Graphics.h" void Pitch_Intensity_draw (Pitch pitch, Intensity intensity, Graphics g, double f1, double f2, double s1, double s2, int garnish, int connect); /* End of file Pitch_Intensity.h */ sources_5316/fon/Ltas_to_SpectrumTier.cpp0000644000176700017670000000207211622365037017332 0ustar paulpaul/* Ltas_to_SpectrumTier.cpp * * Copyright (C) 2007-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Ltas_to_SpectrumTier.h" SpectrumTier Ltas_to_SpectrumTier_peaks (Ltas me) { try { return (SpectrumTier) Vector_to_RealTier_peaks (me, 1, classSpectrumTier); } catch (MelderError) { Melder_throw (me, ": peaks not analyzed as SpectrumTier."); } } /* End of file Ltas_to_SpectrumTier.cpp */ sources_5316/fon/AmplitudeTier.h0000644000176700017670000000563511622364000015431 0ustar paulpaul#ifndef _AmplitudeTier_h_ #define _AmplitudeTier_h_ /* AmplitudeTier.h * * Copyright (C) 2003-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "IntensityTier.h" #include "TableOfReal.h" #include "Sound.h" /********** class AmplitudeTier **********/ Thing_define (AmplitudeTier, RealTier) { // overridden methods: protected: virtual int v_domainQuantity () { return MelderQuantity_TIME_SECONDS; } }; AmplitudeTier AmplitudeTier_create (double tmin, double tmax); void AmplitudeTier_draw (AmplitudeTier me, Graphics g, double tmin, double tmax, double ymin, double ymax, const wchar *method, int garnish); AmplitudeTier PointProcess_upto_AmplitudeTier (PointProcess me, double soundPressure); AmplitudeTier IntensityTier_to_AmplitudeTier (IntensityTier me); IntensityTier AmplitudeTier_to_IntensityTier (AmplitudeTier me, double threshold_dB); TableOfReal AmplitudeTier_downto_TableOfReal (AmplitudeTier me); void Sound_AmplitudeTier_multiply_inline (Sound me, AmplitudeTier intensity); Sound Sound_AmplitudeTier_multiply (Sound me, AmplitudeTier intensity); AmplitudeTier PointProcess_Sound_to_AmplitudeTier_point (PointProcess me, Sound thee); AmplitudeTier PointProcess_Sound_to_AmplitudeTier_period (PointProcess me, Sound thee, double tmin, double tmax, double shortestPeriod, double longestPeriod, double maximumPeriodFactor); double AmplitudeTier_getShimmer_local (AmplitudeTier me, double shortestPeriod, double longestPeriod, double maximumAmplitudeFactor); double AmplitudeTier_getShimmer_local_dB (AmplitudeTier me, double shortestPeriod, double longestPeriod, double maximumAmplitudeFactor); double AmplitudeTier_getShimmer_apq3 (AmplitudeTier me, double shortestPeriod, double longestPeriod, double maximumAmplitudeFactor); double AmplitudeTier_getShimmer_apq5 (AmplitudeTier me, double shortestPeriod, double longestPeriod, double maximumAmplitudeFactor); double AmplitudeTier_getShimmer_apq11 (AmplitudeTier me, double shortestPeriod, double longestPeriod, double maximumAmplitudeFactor); double AmplitudeTier_getShimmer_dda (AmplitudeTier me, double shortestPeriod, double longestPeriod, double maximumAmplitudeFactor); Sound AmplitudeTier_to_Sound (AmplitudeTier me, double samplingFrequency, long interpolationDepth); /* End of file AmplitudeTier.h */ #endif sources_5316/fon/Cochleagram_and_Excitation.h0000644000176700017670000000165611614422227020105 0ustar paulpaul/* Cochleagram_and_Excitation.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Cochleagram.h" #include "Excitation.h" Excitation Cochleagram_to_Excitation (Cochleagram me, double t); /* End of file Cochleagram_and_Excitation.h */ sources_5316/fon/ExperimentMFC.cpp0000644000176700017670000004704611643514745015704 0ustar paulpaul/* ExperimentMFC.cpp * * Copyright (C) 2001-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2002/10/31 NUMlog2 * pb 2003/03/08 inter-stimulus interval; version 2 * pb 2003/09/14 MelderDir_relativePathToFile * pb 2004/06/22 added response keys; version 3 * pb 2004/08/12 removed a bug (something said carrierBefore instead of carrierAfter) * that caused Praat to crash if the carrier before was longer than the carrier after * pb 2005/11/21 added replay button; version 4 * pb 2005/12/02 response sounds are read * pb 2006/10/28 erased MacOS 9 stuff * pb 2006/12/20 stereo * pb 2007/08/12 wchar_t * pb 2007/09/26 added font size; version 5 * pb 2007/10/01 can write as encoding * pb 2008/04/08 in ExtractResults, check that a resonse was given * pb 2008/10/20 except nonstandard sound files * pb 2009/03/18 removed a bug introduced by the previous change (an error check got hidden) * pb 2011/03/03 added reaction times; version 2 of ResultsMFC * pb 2011/03/15 allowed result extraction from incomplete experiments * pb 2011/03/23 C++ * pb 2011/07/06 C++ */ #include "ExperimentMFC.h" #include "oo_DESTROY.h" #include "ExperimentMFC_def.h" #include "oo_COPY.h" #include "ExperimentMFC_def.h" #include "oo_EQUAL.h" #include "ExperimentMFC_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "ExperimentMFC_def.h" #include "oo_READ_TEXT.h" #include "ExperimentMFC_def.h" #include "oo_WRITE_TEXT.h" #include "ExperimentMFC_def.h" #include "oo_READ_BINARY.h" #include "ExperimentMFC_def.h" #include "oo_WRITE_BINARY.h" #include "ExperimentMFC_def.h" #include "oo_DESCRIPTION.h" #include "ExperimentMFC_def.h" Thing_implement (ExperimentMFC, Data, 5); #include "enums_getText.h" #include "Experiment_enums.h" #include "enums_getValue.h" #include "Experiment_enums.h" static void readSound (ExperimentMFC me, const wchar *fileNameHead, const wchar *fileNameTail, double medialSilenceDuration, wchar **name, Sound *sound) { wchar fileNameBuffer [256], pathName [256], *fileNames = & fileNameBuffer [0]; structMelderFile file = { 0 }; wcscpy (fileNameBuffer, *name); /* * The following conversion is needed when fileNameHead is an absolute path, * and the stimulus names contain slashes for relative paths. * An ugly case, but allowed. */ #if defined (_WIN32) for (;;) { wchar *slash = wcschr (fileNames, '/'); if (! slash) break; *slash = '\\'; } #endif forget (*sound); /* * 'fileNames' can contain commas, which separate partial file names. * The separate files should be concatenated. */ for (;;) { /* * Determine partial file name. */ wchar *comma = wcschr (fileNames, ','); if (comma) *comma = '\0'; /* * Determine complete (relative) file name. */ swprintf (pathName, 256, L"%ls%ls%ls", fileNameHead, fileNames, fileNameTail); /* * Make sure we are in the correct directory. */ if (MelderDir_isNull (& my rootDirectory)) { /* * Absolute file name. */ Melder_pathToFile (pathName, & file); } else { /* * Relative or absolute file name. */ MelderDir_relativePathToFile (& my rootDirectory, pathName, & file); if (Melder_debug == 32) { MelderInfo_open (); MelderInfo_writeLine3 (L"Path name <", pathName, L">"); MelderInfo_writeLine3 (L"Root directory <", my rootDirectory.path, L">"); MelderInfo_writeLine3 (L"Full path name <", file.path, L">"); MelderInfo_close (); } } /* * Read the substimulus. */ autoSound substimulus = (Sound) Data_readFromFile (& file); // Sound_readFromSoundFile (& file); if (substimulus -> classInfo != classSound) Melder_throw ("File ", & file, " contains a ", Thing_className (substimulus.peek()), " instead of a sound."); /* * Check whether all sounds have the same number of channels. */ if (my numberOfChannels == 0) { my numberOfChannels = substimulus -> ny; } else if (substimulus -> ny != my numberOfChannels) { Melder_throw ("The sound in file ", & file, " has a different number of channels than some other sound."); } /* * Check whether all sounds have the same sampling frequency. */ if (my samplePeriod == 0.0) { my samplePeriod = substimulus -> dx; /* This must be the first sound read. */ } else if (substimulus -> dx != my samplePeriod) { Melder_throw ("The sound in file ", & file, " has a different sampling frequency than some other sound."); } /* * Append the substimuli, perhaps with silent intervals. */ if (*sound == NULL) { *sound = substimulus.transfer(); } else { autoSound newStimulus = Sounds_append (*sound, medialSilenceDuration, substimulus.peek()); Melder_assert (sound == & (*sound)); forget (*sound); *sound = newStimulus.transfer(); } /* * Cycle. */ if (comma == NULL) break; fileNames = & comma [1]; } } static void permuteRandomly (ExperimentMFC me, long first, long last) { for (long itrial = first; itrial < last; itrial ++) { long jtrial = NUMrandomInteger (itrial, last); long dummy = my stimuli [jtrial]; my stimuli [jtrial] = my stimuli [itrial]; my stimuli [itrial] = dummy; } } void ExperimentMFC_start (ExperimentMFC me) { try { long maximumStimulusPlaySamples, maximumResponsePlaySamples, maximumPlaySamples; long stimulusCarrierBeforeSamples = 0, stimulusCarrierAfterSamples = 0, maximumStimulusSamples = 0; long responseCarrierBeforeSamples = 0, responseCarrierAfterSamples = 0, maximumResponseSamples = 0; Melder_warningOff (); my trial = 0; NUMvector_free (my stimuli, 1); NUMvector_free (my responses, 1); NUMvector_free (my goodnesses, 1); NUMvector_free (my reactionTimes, 1); forget (my playBuffer); my pausing = FALSE; my numberOfTrials = my numberOfDifferentStimuli * my numberOfReplicationsPerStimulus; my stimuli = NUMvector (1, my numberOfTrials); my responses = NUMvector (1, my numberOfTrials); my goodnesses = NUMvector (1, my numberOfTrials); my reactionTimes = NUMvector (1, my numberOfTrials); /* * Read all the sounds. They must all have the same sampling frequency and number of channels. */ my samplePeriod = 0.0; my numberOfChannels = 0; if (my stimuliAreSounds) { if (my stimulusCarrierBefore. name && my stimulusCarrierBefore. name [0]) { readSound (me, my stimulusFileNameHead, my stimulusFileNameTail, my stimulusMedialSilenceDuration, & my stimulusCarrierBefore. name, & my stimulusCarrierBefore. sound); stimulusCarrierBeforeSamples = my stimulusCarrierBefore. sound -> nx; } if (my stimulusCarrierAfter. name && my stimulusCarrierAfter. name [0]) { readSound (me, my stimulusFileNameHead, my stimulusFileNameTail, my stimulusMedialSilenceDuration, & my stimulusCarrierAfter. name, & my stimulusCarrierAfter. sound); stimulusCarrierAfterSamples = my stimulusCarrierAfter. sound -> nx; } for (long istim = 1; istim <= my numberOfDifferentStimuli; istim ++) { readSound (me, my stimulusFileNameHead, my stimulusFileNameTail, my stimulusMedialSilenceDuration, & my stimulus [istim]. name, & my stimulus [istim]. sound); if (my stimulus [istim]. sound -> nx > maximumStimulusSamples) maximumStimulusSamples = my stimulus [istim]. sound -> nx; } } if (my responsesAreSounds) { if (my responseCarrierBefore. name && my responseCarrierBefore. name [0]) { readSound (me, my responseFileNameHead, my responseFileNameTail, my responseMedialSilenceDuration, & my responseCarrierBefore. name, & my responseCarrierBefore. sound); responseCarrierBeforeSamples = my responseCarrierBefore. sound -> nx; } if (my responseCarrierAfter. name && my responseCarrierAfter. name [0]) { readSound (me, my responseFileNameHead, my responseFileNameTail, my responseMedialSilenceDuration, & my responseCarrierAfter. name, & my responseCarrierAfter. sound); responseCarrierAfterSamples = my responseCarrierAfter. sound -> nx; } for (long iresp = 1; iresp <= my numberOfDifferentResponses; iresp ++) { readSound (me, my responseFileNameHead, my responseFileNameTail, my responseMedialSilenceDuration, & my response [iresp]. name, & my response [iresp]. sound); if (my response [iresp]. sound -> nx > maximumResponseSamples) maximumResponseSamples = my response [iresp]. sound -> nx; } } /* * Create the play buffer. */ maximumStimulusPlaySamples = floor (my stimulusInitialSilenceDuration / my samplePeriod + 0.5) + stimulusCarrierBeforeSamples + maximumStimulusSamples + stimulusCarrierAfterSamples + 1; maximumResponsePlaySamples = floor (my responseInitialSilenceDuration / my samplePeriod + 0.5) + responseCarrierBeforeSamples + maximumResponseSamples + responseCarrierAfterSamples + 1; maximumPlaySamples = maximumStimulusPlaySamples > maximumResponsePlaySamples ? maximumStimulusPlaySamples : maximumResponsePlaySamples; my playBuffer = Sound_create (my numberOfChannels, 0.0, maximumPlaySamples * my samplePeriod, maximumPlaySamples, my samplePeriod, 0.5 * my samplePeriod); therror /* * Determine the order in which the stimuli will be presented to the subject. */ if (my randomize == kExperiment_randomize_CYCLIC_NON_RANDOM) { for (long itrial = 1; itrial <= my numberOfTrials; itrial ++) my stimuli [itrial] = (itrial - 1) % my numberOfDifferentStimuli + 1; } else if (my randomize == kExperiment_randomize_PERMUTE_ALL) { for (long itrial = 1; itrial <= my numberOfTrials; itrial ++) my stimuli [itrial] = (itrial - 1) % my numberOfDifferentStimuli + 1; permuteRandomly (me, 1, my numberOfTrials); } else if (my randomize == kExperiment_randomize_PERMUTE_BALANCED) { for (long ireplica = 1; ireplica <= my numberOfReplicationsPerStimulus; ireplica ++) { long offset = (ireplica - 1) * my numberOfDifferentStimuli; for (long istim = 1; istim <= my numberOfDifferentStimuli; istim ++) my stimuli [offset + istim] = istim; permuteRandomly (me, offset + 1, offset + my numberOfDifferentStimuli); } } else if (my randomize == kExperiment_randomize_PERMUTE_BALANCED_NO_DOUBLETS) { for (long ireplica = 1; ireplica <= my numberOfReplicationsPerStimulus; ireplica ++) { long offset = (ireplica - 1) * my numberOfDifferentStimuli; for (long istim = 1; istim <= my numberOfDifferentStimuli; istim ++) my stimuli [offset + istim] = istim; do { permuteRandomly (me, offset + 1, offset + my numberOfDifferentStimuli); } while (ireplica != 1 && my stimuli [offset + 1] == my stimuli [offset] && my numberOfDifferentStimuli > 1); } } else if (my randomize == kExperiment_randomize_WITH_REPLACEMENT) { for (long itrial = 1; itrial <= my numberOfTrials; itrial ++) my stimuli [itrial] = NUMrandomInteger (1, my numberOfDifferentStimuli); } Melder_warningOn (); } catch (MelderError) { Melder_warningOn (); my numberOfTrials = 0; NUMvector_free (my stimuli, 1); my stimuli = NULL; Melder_throw (me, ": not started."); } } static void playSound (ExperimentMFC me, Sound sound, Sound carrierBefore, Sound carrierAfter, double initialSilenceDuration) { long initialSilenceSamples = floor (initialSilenceDuration / my samplePeriod + 0.5); long carrierBeforeSamples = carrierBefore ? carrierBefore -> nx : 0; long soundSamples = sound ? sound -> nx : 0; long carrierAfterSamples = carrierAfter ? carrierAfter -> nx : 0; for (long channel = 1; channel <= my numberOfChannels; channel ++) { for (long i = 1; i <= initialSilenceSamples; i ++) { my playBuffer -> z [channel] [i] = 0.0; } } if (carrierBefore) { for (long channel = 1; channel <= my numberOfChannels; channel ++) { NUMvector_copyElements (carrierBefore -> z [channel], my playBuffer -> z [channel] + initialSilenceSamples, 1, carrierBeforeSamples); } } if (sound) { for (long channel = 1; channel <= my numberOfChannels; channel ++) { NUMvector_copyElements (sound -> z [channel], my playBuffer -> z [channel] + initialSilenceSamples + carrierBeforeSamples, 1, soundSamples); } } if (carrierAfter) { for (long channel = 1; channel <= my numberOfChannels; channel ++) { NUMvector_copyElements (carrierAfter -> z [channel], my playBuffer -> z [channel] + initialSilenceSamples + carrierBeforeSamples + soundSamples, 1, carrierAfterSamples); } } my startingTime = Melder_clock (); Sound_playPart (my playBuffer, 0.0, (initialSilenceSamples + carrierBeforeSamples + soundSamples + carrierAfterSamples) * my samplePeriod, 0, NULL); } void ExperimentMFC_playStimulus (ExperimentMFC me, long istim) { playSound (me, my stimulus [istim]. sound, my stimulusCarrierBefore. sound, my stimulusCarrierAfter. sound, my stimulusInitialSilenceDuration); } void ExperimentMFC_playResponse (ExperimentMFC me, long iresp) { playSound (me, my response [iresp]. sound, my responseCarrierBefore. sound, my responseCarrierAfter. sound, my responseInitialSilenceDuration); } Thing_implement (ResultsMFC, Data, 2); ResultsMFC ResultsMFC_create (long numberOfTrials) { try { autoResultsMFC me = Thing_new (ResultsMFC); my numberOfTrials = numberOfTrials; my result = NUMvector (1, my numberOfTrials); return me.transfer(); } catch (MelderError) { Melder_throw ("ResultsMFC not created."); } } ResultsMFC ExperimentMFC_extractResults (ExperimentMFC me) { try { if (my trial == 0 || my trial <= my numberOfTrials) Melder_warning ("The experiment was not finished. Only the first ", my trial - 1, " responses are valid."); autoResultsMFC thee = ResultsMFC_create (my numberOfTrials); for (long trial = 1; trial <= my numberOfTrials; trial ++) { wchar_t *pipe = my stimulus [my stimuli [trial]]. visibleText ? wcschr (my stimulus [my stimuli [trial]]. visibleText, '|') : NULL; if (pipe) { long nameLength = wcslen (my stimulus [my stimuli [trial]]. name); long buttonTextLength = wcslen (pipe); thy result [trial]. stimulus = Melder_calloc (wchar_t, nameLength + buttonTextLength + 1); wcscpy (thy result [trial]. stimulus, my stimulus [my stimuli [trial]]. name); wcscat (thy result [trial]. stimulus, pipe); } else { thy result [trial]. stimulus = Melder_wcsdup (my stimulus [my stimuli [trial]]. name); } //if (my responses [trial] < 1) Melder_throw ("No response for trial ", trial, ".") thy result [trial]. response = Melder_wcsdup (my responses [trial] ? my response [my responses [trial]]. name : L""); thy result [trial]. goodness = my goodnesses [trial]; thy result [trial]. reactionTime = my reactionTimes [trial]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": results not extracted."); } } ResultsMFC ResultsMFC_removeUnsharedStimuli (ResultsMFC me, ResultsMFC thee) { try { autoResultsMFC him = ResultsMFC_create (thy numberOfTrials); his numberOfTrials = 0; for (long i = 1; i <= thy numberOfTrials; i ++) { bool present = false; for (long j = 1; j <= my numberOfTrials; j ++) { if (wcsequ (thy result [i]. stimulus, my result [j]. stimulus)) { present = true; break; } } if (present) { his numberOfTrials ++; his result [his numberOfTrials]. stimulus = Melder_wcsdup (thy result [i]. stimulus); his result [his numberOfTrials]. response = Melder_wcsdup (thy result [i]. response); } } if (his numberOfTrials == 0) Melder_throw ("No shared stimuli."); return him.transfer(); } catch (MelderError) { Melder_throw (me, " & ", thee, ": unshared stimuli not removed."); } } Table ResultsMFCs_to_Table (Collection me) { try { long irow = 0; bool hasGoodnesses = false, hasReactionTimes = false; for (long iresults = 1; iresults <= my size; iresults ++) { ResultsMFC results = (ResultsMFC) my item [iresults]; for (long itrial = 1; itrial <= results -> numberOfTrials; itrial ++) { irow ++; if (results -> result [itrial]. goodness != 0) hasGoodnesses = true; if (results -> result [itrial]. reactionTime != 0.0) hasReactionTimes = true; } } autoTable thee = Table_create (irow, 3 + hasGoodnesses + hasReactionTimes); Table_setColumnLabel (thee.peek(), 1, L"subject"); therror Table_setColumnLabel (thee.peek(), 2, L"stimulus"); therror Table_setColumnLabel (thee.peek(), 3, L"response"); therror if (hasGoodnesses) { Table_setColumnLabel (thee.peek(), 4, L"goodness"); therror } if (hasReactionTimes) { Table_setColumnLabel (thee.peek(), 4 + hasGoodnesses, L"reactionTime"); therror } irow = 0; for (long iresults = 1; iresults <= my size; iresults ++) { ResultsMFC results = (ResultsMFC) my item [iresults]; for (long itrial = 1; itrial <= results -> numberOfTrials; itrial ++) { irow ++; Table_setStringValue (thee.peek(), irow, 1, results -> name); therror Table_setStringValue (thee.peek(), irow, 2, results -> result [itrial]. stimulus); therror Table_setStringValue (thee.peek(), irow, 3, results -> result [itrial]. response); therror if (hasGoodnesses) { Table_setNumericValue (thee.peek(), irow, 4, results -> result [itrial]. goodness); therror } if (hasReactionTimes) { Table_setNumericValue (thee.peek(), irow, 4 + hasGoodnesses, results -> result [itrial]. reactionTime); therror } } } return thee.transfer(); } catch (MelderError) { Melder_throw ("ResultsMFC objects not collected to Table."); } } Categories ResultsMFC_to_Categories_stimuli (ResultsMFC me) { try { autoCategories thee = Categories_create (); for (long trial = 1; trial <= my numberOfTrials; trial ++) { autoSimpleString category = SimpleString_create (my result [trial]. stimulus); Collection_addItem (thee.peek(), category.transfer()); therror } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": stimuli not converted to Categories."); } } Categories ResultsMFC_to_Categories_responses (ResultsMFC me) { try { autoCategories thee = Categories_create (); for (long trial = 1; trial <= my numberOfTrials; trial ++) { autoSimpleString category = SimpleString_create (my result [trial]. response); Collection_addItem (thee.peek(), category.transfer()); therror } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": responses not converted to Categories."); } } static int compare (SimpleString me, SimpleString thee) { return wcscmp (my string, thy string); } void Categories_sort (Categories me) { NUMsort_p (my size, my item, (int (*) (const void *, const void *)) compare); } double Categories_getEntropy (Categories me) { long numberOfTokens = 0; wchar_t *previousString = NULL; double entropy = 0.0; autoCategories thee = Data_copy (me); Categories_sort (thee.peek()); for (long i = 1; i <= thy size; i ++) { SimpleString s = (SimpleString) thy item [i]; wchar_t *string = s -> string; if (previousString != NULL && ! wcsequ (string, previousString)) { double p = (double) numberOfTokens / thy size; entropy -= p * NUMlog2 (p); numberOfTokens = 1; } else { numberOfTokens ++; } previousString = string; } if (numberOfTokens) { double p = (double) numberOfTokens / thy size; entropy -= p * NUMlog2 (p); } return entropy; } /* End of file ExperimentMFC.cpp */ sources_5316/fon/manual_soundFiles.cpp0000644000176700017670000005716411627220774016706 0ustar paulpaul/* manual_soundFiles.cpp * * Copyright (C) 1992-2008 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" void manual_soundFiles_init (ManPages me); void manual_soundFiles_init (ManPages me) { MAN_BEGIN (L"Sound files", L"ppgb", 20070602) INTRO (L"This tutorial describes the sound files that you can read " "and write with Praat. It assumes you are familiar with the @Intro.") NORMAL (L"You can read this tutorial sequentially with the help of the \"< 1\" and \"1 >\" buttons.") LIST_ITEM (L"1. @@Sound files 1. General structure|General structure@") LIST_ITEM1 (L"1.1. @@Sound files 1.1. Sampling|Sampling@ (sampling frequency)") LIST_ITEM1 (L"1.2. @@Sound files 1.2. Quantization|Quantization@ (linear, endian, \\mu-law, A-law)") LIST_ITEM1 (L"1.3. @@Sound files 1.3. Channels|Channels@ (mono, stereo)") LIST_ITEM1 (L"1.4. @@Sound files 1.4. The header|The header@") LIST_ITEM1 (L"1.5. @@Sound files 1.5. Size|Size@") LIST_ITEM1 (L"1.6. @@Sound files 1.6. Compression|Compression@") LIST_ITEM (L"2. @@Sound files 2. File types|File types@") LIST_ITEM1 (L"2.1. @@Sound files 2.1. WAV files|WAV files@") LIST_ITEM1 (L"2.2. @@Sound files 2.2. AIFF files|AIFF files@") LIST_ITEM1 (L"2.3. @@Sound files 2.3. AIFC files|AIFC files@") LIST_ITEM1 (L"2.4. @@Sound files 2.4. NeXT/Sun (.au) files|NeXT/Sun (.au) files@") LIST_ITEM1 (L"2.5. @@Sound files 2.5. NIST files|NIST files@") LIST_ITEM1 (L"2.6. @@Sound files 2.6. FLAC files|FLAC files@") LIST_ITEM1 (L"2.7. @@Sound files 2.7. MP3 files|MP3 files@") LIST_ITEM (L"3. @@Sound files 3. Files that Praat can read|Files that Praat can read@") LIST_ITEM (L"4. @@Sound files 4. Files that Praat can write|Files that Praat can write@") MAN_END MAN_BEGIN (L"Sound files 1. General structure", L"ppgb", 20000123) INTRO (L"This is chapter 1 of the @@Sound files@ tutorial. " "It describes the general structure of the headers and data parts of sound files.") LIST_ITEM (L"1.1. @@Sound files 1.1. Sampling|Sampling@ (sampling frequency)") LIST_ITEM (L"1.2. @@Sound files 1.2. Quantization|Quantization@ (linear, \\mu-law, A-law)") LIST_ITEM (L"1.3. @@Sound files 1.3. Channels|Channels@ (mono, stereo)") LIST_ITEM (L"1.4. @@Sound files 1.4. The header|The header@") LIST_ITEM (L"1.5. @@Sound files 1.5. Size|Size@") LIST_ITEM (L"1.6. @@Sound files 1.6. Compression|Compression@") MAN_END MAN_BEGIN (L"Sound files 1.1. Sampling", L"ppgb", 20040330) NORMAL (L"When a sound signal from a microphone or on a tape needs to be read into a computer, " "it is %digitized, which means that it is %sampled and %quantized.") NORMAL (L"Sampling is the discretization of the time domain of the signal: " "each second of the signal is divided up into 11025, 22050, or 44100 " "slices (or any other suitable number), and a %%sample value% is associated with " "each slice. For instance, a continuous 377-Hz sine wave is expressed by") FORMULA (L"%x(%t) = sin (2%\\pi 377 %t)") NORMAL (L"If the %%sampling frequency% (or %%sample rate%) is 44100 Hz, this sine wave will be sampled at " "points spaced \\De%t = 1/44100 second apart, and the sample values will be") FORMULA (L"%x__%i_ = sin (2%\\pi 377 (%t__0_ + %i \\De%t))") NORMAL (L"where %t__0_ is the time after which sampling begins. " "\\De%t is called the %%sample period%.") NORMAL (L"Quantization is handled in the next section (@@Sound files 1.2. Quantization|\\SS1.2@).") MAN_END MAN_BEGIN (L"Sound files 1.2. Quantization", L"ppgb", 20000126) NORMAL (L"Apart from sampling (@@Sound files 1.1. Sampling|\\SS1.1@), " "digitization also involves quantization, which is the conversion of a sample value " "into a number that fits into 8 or 16 bits.") MAN_END MAN_BEGIN (L"Sound files 1.3. Channels", L"ppgb", 20000126) NORMAL (L"For most file types, Praat supports sounds with one channel (mono) and two channels (stereo).") MAN_END MAN_BEGIN (L"Sound files 1.4. The header", L"ppgb", 20040223) NORMAL (L"The bulk of most sound files is formed by the samples. " "The sample part is usually preceded by a header, which contains " "information about:") LIST_ITEM (L"1. The type of file (WAV, AIFF, AIFC, NeXT/Sun, NIST, Kay, FLAC...).") LIST_ITEM (L"2. The sampling frequency (@@Sound files 1.1. Sampling|\\SS1.1@).") LIST_ITEM (L"3. The encoding (linear, 8 or 16 bit, byte order, \\mu-law, A-law, see @@Sound files 1.2. Quantization|\\SS1.2@).") LIST_ITEM (L"4. The number of channels (mono, stereo, see @@Sound files 1.3. Channels|\\SS1.3@).") LIST_ITEM (L"5. The duration (usually the number of samples).") MAN_END MAN_BEGIN (L"Sound files 1.5. Size", L"ppgb", 20000126) NORMAL (L"The size of a sound file is equal to the size of the header " "plus the product of the number of samples, the quantization size, " "and the number of channels.") NORMAL (L"For instance, a stereo sound with a duration of 3 seconds, sampled at 44100 Hz, " "would, when written into a 16-bit NeXT/Sun file, take up a disk space of") FORMULA (L"28 + 2 * 3.0 * 44100 * 2 = 529228 bytes") NORMAL (L"whereas the same sound, when averaged to mono, downsampled to 8000 Hz, " "and written into a \\mu-law NeXT/Sun file, take up only a disk space of") FORMULA (L"28 + 1 * 3.0 * 8000 * 1 = 24028 bytes") NORMAL (L"The first example is typical of CD quality, the second of telephone speech.") MAN_END MAN_BEGIN (L"Sound files 1.6. Compression", L"ppgb", 20040602) NORMAL (L"Praat used to be able to read some compressed sound file formats (shortened NIST, Polyphone), " "but because of licensing problems (Praat went open source, Shorten did not), " "you now need to use other (freely available) programs to do the conversion before reading them into Praat. " "Praat can decode (but not create) MP3 files. " "Praat fully supports FLAC compressed files.") MAN_END MAN_BEGIN (L"Sound files 2. File types", L"ppgb", 20070602) LIST_ITEM (L"2.1. @@Sound files 2.1. WAV files|WAV files@") LIST_ITEM (L"2.2. @@Sound files 2.2. AIFF files|AIFF files@") LIST_ITEM (L"2.3. @@Sound files 2.3. AIFC files|AIFC files@") LIST_ITEM (L"2.4. @@Sound files 2.4. NeXT/Sun (.au) files|NeXT/Sun (.au) files@") LIST_ITEM (L"2.5. @@Sound files 2.5. NIST files|NIST files@") LIST_ITEM (L"2.6. @@Sound files 2.6. FLAC files|FLAC files@") LIST_ITEM (L"2.7. @@Sound files 2.7. MP3 files|MP3 files@") MAN_END MAN_BEGIN (L"Sound files 2.1. WAV files", L"ppgb", 20040223) NORMAL (L"The audio file type most commonly used on Windows computers, also very common on the Internet.") MAN_END MAN_BEGIN (L"Sound files 2.2. AIFF files", L"ppgb", 20040223) NORMAL (L"AIFF stands for: Audio Interchange File Format.") NORMAL (L"This standard format for sound files was defined by Apple. " "It is also the format of the sound files on the Iris Indigo, " "where each sample is quantized into 16 bits.") MAN_END MAN_BEGIN (L"Sound files 2.3. AIFC files", L"ppgb", 20040223) NORMAL (L"AIFC is short for AIFF(C) or AIFF-C, i.e. the Audio Interchange File Format " "(@@Sound files 2.2. AIFF files|\\SS2.2@) with optional compression.") NORMAL (L"Praat reads and write uncompressed AIFC files, but does not support compressed AIFC files.") MAN_END MAN_BEGIN (L"Sound files 2.4. NeXT/Sun (.au) files", L"ppgb", 20110131) NORMAL (L"This is the format of the sound files on the Sun.") ENTRY (L"Reading") NORMAL (L"To read a #Sound from a Sun audio file on disk, use @@Read from file...@." "Praat then asks you for a file name. " "After you click OK, Praat determines the encoding of the file. " "If the encoding is 16-bit linear, the 16-bit sample values are divided by 32768 so that the amplitude " "of the resulting Sound is between -1.0 and +1.0. " "If the encoding is 8-bit %\\mu-law, the 16-bit sample value is determined by table look-up first.") NORMAL (L"The resulting Sound will appear in the list of objects; " "its name will be equal to the file name, without extension.") ENTRY (L"Saving") NORMAL (L"Use @@Save as NeXT/Sun file...@. The samples of the Sound are multiplied by 32768 " "and quantized between -32768 and 32767; " "the result is written to the file in 16-bit mono Sun audio format.") NORMAL (L"To avoid clipping, keep the absolute amplitude below 1.000. " "If the maximum sound pressure level is 91 dB (top = 32767), " "the quantization threshold is (top = 1/2) -5 dB.") MAN_END MAN_BEGIN (L"Sound files 2.5. NIST files", L"ppgb", 20040223) NORMAL (L"An audio file type used by speech researchers. Used, for instance, in the TIMIT database. " "Praat reads several kinds of NIST files: big-endian, little-endian, \\mu-law, A-law, Polyphone. " "NIST files compressed with #shorten are no longer supported " "(see @@Sound files 1.6. Compression|\\SS1.6@)") MAN_END MAN_BEGIN (L"Sound files 2.6. FLAC files", L"Erez Volk", 20070514) NORMAL (L"A lossless compressed audio format (see ##http://flac.sourceforge.net##). " "Praat reads FLAC files in all bitrate/frequency settings " "(see also @@Sound files 1.6. Compression|\\SS1.6@)") MAN_END MAN_BEGIN (L"Sound files 3. Files that Praat can read", L"ppgb", 20070602) INTRO (L"Praat can read five types of standard sound files in several formats, " "and a number of proprietary types of sound files as well.") ENTRY (L"Standard sound files") NORMAL (L"The @@Open menu@ contains two commands for opening sound files:") LIST_ITEM (L"\\bu With @@Read from file...@, you read the entire file into memory. " "A @Sound object will appear in the list. " "This is appropriate if your sound is not too long to fit into memory. " "The advantage of having a @Sound object is that you can perform analysis " "on it directly.") LIST_ITEM (L"\\bu With @@Open long sound file...@, you open a sound file that is too long " "to read into memory completely. A @LongSound object will appear in the list. " "You will typically choose #View to view the contents of this sound and analyse it. " "Praat will only read so much of the file into memory as is needed to play or display " "parts of it.") NORMAL (L"Both commands understand the following five standard audio file formats:") LIST_ITEM (L"\\bu WAV:") LIST_ITEM1 (L"\\bu linear 16-bit little-endian") LIST_ITEM1 (L"\\bu 8-bit \\mu-law") LIST_ITEM1 (L"\\bu 8-bit A-law") LIST_ITEM1 (L"\\bu linear 8-bit unsigned") LIST_ITEM (L"\\bu AIFF or AIFC:") LIST_ITEM1 (L"\\bu linear 16-bit big-endian") LIST_ITEM1 (L"\\bu linear 8-bit signed") LIST_ITEM (L"\\bu NeXT/Sun (.au):") LIST_ITEM1 (L"\\bu linear 16-bit big-endian") LIST_ITEM1 (L"\\bu 8-bit \\mu-law") LIST_ITEM1 (L"\\bu 8-bit A-law") LIST_ITEM1 (L"\\bu linear 8-bit signed") LIST_ITEM (L"\\bu NIST:") LIST_ITEM1 (L"\\bu linear 16-bit little-endian") LIST_ITEM1 (L"\\bu linear 16-bit big-endian") LIST_ITEM1 (L"\\bu 8-bit \\mu-law") LIST_ITEM1 (L"\\bu 8-bit A-law") LIST_ITEM1 (L"\\bu linear 8-bit signed") LIST_ITEM (L"\\bu FLAC:") LIST_ITEM1 (L"\\bu 8-bit, 16-bit, 24-bit or 32-bit") LIST_ITEM1 (L"\\bu all sampling frequencies") LIST_ITEM (L"\\bu MP3:") LIST_ITEM1 (L"\\bu all constant or variable bitrates") MAN_END MAN_BEGIN (L"Sound files 4. Files that Praat can write", L"ppgb", 20110129) INTRO (L"Praat can write five types of standard sound files in an appropriate linear 16-bit formats, " "and a number of proprietary types of sound files as well:") LIST_ITEM (L"\\bu @@Save as WAV file...@ (16-bit little-endian)") LIST_ITEM (L"\\bu @@Save as AIFF file...@ (16-bit big-endian)") LIST_ITEM (L"\\bu @@Save as AIFC file...@ (16-bit big-endian)") LIST_ITEM (L"\\bu @@Save as NeXT/Sun file...@ (16-bit big-endian)") LIST_ITEM (L"\\bu @@Save as NIST file...@ (16-bit little-endian)") LIST_ITEM (L"\\bu @@Save as FLAC file...@ (16-bit)") MAN_END MAN_BEGIN (L"AIFF and AIFC files", L"ppgb", 20110131) INTRO (L"Ways for storing a @Sound object on disk.") ENTRY (L"File format") ENTRY (L"Reading") NORMAL (L"@@Read from file...@ recognizes AIFF and AIFC files with 8-bit and 16-bit encoding, " "but not compressed AIFC files. It recognizes any sampling frequency. The two channels of stereo files " "are averaged. ##Read two Sounds from AIFF file...# reads both channels separately and names " "them %left and %right.") NORMAL (L"The sample values are divided by 2^^(%numberOfBitsPerSample \\-- 1)^, " "so that the amplitude of the resulting Sound is between \\--1.0 and +1.0; " "the maximum sound pressure level for a sine wave is therefore: " "20 \\.c ^^10^log (\\Vr2 / 2\\.c10^^\\--5^) = 91 dB.") NORMAL (L"The resulting Sound will appear in the List of Objects; " "its name will be equal to the file name, without extension.") ENTRY (L"Saving") NORMAL (L"With @@Save as AIFF file...@.") NORMAL (L"The samples of the Sound are multiplied by 32768 " "and quantized between \\--32768 and 32767.") NORMAL (L"To avoid clipping, keep the absolute amplitude below 1.000. " "If the maximum sound pressure level is 91 dB (top = 32767), " "the quantization threshold is (top = 1/2) \\--5 dB.") MAN_END MAN_BEGIN (L"Save as WAV file...", L"ppgb", 20110129) INTRO (L"With this command, you save one or more selected @Sound and/or @LongSound objects " "as a single 16-bit little-endian WAV file on disk. See the @@Sound files@ tutorial for more information.") MAN_END MAN_BEGIN (L"Save as AIFF file...", L"ppgb", 20110129) INTRO (L"With this command, you save one or more selected @Sound and/or @LongSound objects " "as a single 16-bit big-endian AIFF file on disk. See the @@Sound files@ tutorial for more information.") /*ENTRY (L"AIFF file format for writing") NORMAL (L"Although")*/ MAN_END MAN_BEGIN (L"Save as AIFC file...", L"ppgb", 20110129) INTRO (L"With this command, you save one or more selected @Sound and/or @LongSound objects " "as a single 16-bit big-endian AIFC file on disk. See the @@Sound files@ tutorial for more information.") MAN_END MAN_BEGIN (L"Save as NeXT/Sun file...", L"ppgb", 20110129) INTRO (L"With this command, you save one or more selected @Sound and/or @LongSound objects " "as a single 16-bit big-endian NeXT/Sun (.au) file on disk. See the @@Sound files@ tutorial for more information.") MAN_END MAN_BEGIN (L"Save as NIST file...", L"ppgb", 20110129) INTRO (L"With this command, you save one or more selected @Sound and/or @LongSound objects " "as a single 16-bit little-endian NIST audio file on disk. See the @@Sound files@ tutorial for more information.") MAN_END MAN_BEGIN (L"Save as FLAC file...", L"ppgb", 20110129) INTRO (L"With this command, you save one or more selected @Sound and/or @LongSound objects " "as a single 16-bit FLAC audio file on disk. See the @@Sound files@ tutorial for more information.") MAN_END MAN_BEGIN (L"Sound files 2.7. MP3 files", L"Erez Volk", 20070601) NORMAL (L"A ubiquitous lossy audio compression format. " "Praat supports MP3 decoding through the MPEG Audio Decoder library " "##http://www.underbit.com/products/mad/##. " "(see also @@Sound files 1.6. Compression|\\SS1.6@)") MAN_END MAN_BEGIN (L"NIST files", L"Erez Volk", 20110131) INTRO (L"A way for storing a @Sound object on disk.") ENTRY (L"File format") NORMAL (L"The compressed sound files of the Timit database, and the Groningen speech corpus.") ENTRY (L"Reading") NORMAL (L"With @@Read from file...@.") ENTRY (L"Saving") NORMAL (L"With ##Save as NIST audio file...#.") MAN_END MAN_BEGIN (L"FLAC files", L"Erez Volk", 20110131) INTRO (L"A way for storing a @Sound object on disk.") ENTRY (L"File format") NORMAL (L"A lossless compressed audio file format.") ENTRY (L"Reading") NORMAL (L"With @@Read from file...@.") ENTRY (L"Saving") NORMAL (L"With ##Save as FLAC audio file...#.") MAN_END MAN_BEGIN (L"How to concatenate sound files", L"ppgb", 20110131) INTRO (L"You can concatenate any combination of AIFF, AIFC, WAV, NeXT/Sun, NIST " "and FLAC audio files, and other files that you have read into memory.") NORMAL (L"For instance, if you want to concatenate a 30-minute AIFF file, " "a 4-minute Kay sound file, and a 60-minute Next/Sun file, " "by saving them into a 94-minute WAV file, " "you do the following:") LIST_ITEM (L"1. Open the AIFF file with @@Open long sound file...@ from the @@Open menu@. " "A @LongSound object will appear in the list.") LIST_ITEM (L"2. Read the Kay sound file into memory with @@Read from file...@. " "A @Sound object will appear in the list.") LIST_ITEM (L"3. Open the AIFF file with @@Open long sound file...@ from the @@Open menu@. " "A second @LongSound object will appear in the list.") LIST_ITEM (L"4. Select the three objects and choose @@Save as WAV file...@ " "from the @@Save menu@.") NORMAL (L"This only works if all the sounds have the same sampling frequency " "and the same number of channels.") ENTRY (L"Available formats") NORMAL (L"The format of the original sound files may be 16-bit linear " "(with big-endian or little-endian byte order), 8-bit linear (signed or unsigned), " "8-bit \\mu-law, or 8-bit A-law. The format of the resulting sound file is always " "16-bit linear, with an appropriate default byte order. The following commands " "are available in the @@Save menu@ of you select any combination of @LongSound " "and/or @Sound objects:") LIST_ITEM (L"\\bu @@Save as WAV file...@ (little-endian)") LIST_ITEM (L"\\bu @@Save as AIFF file...@ (big-endian)") LIST_ITEM (L"\\bu @@Save as AIFC file...@ (big-endian)") LIST_ITEM (L"\\bu @@Save as NeXT/Sun file...@ (big-endian)") LIST_ITEM (L"\\bu @@Save as NIST file...@ (little-endian)") LIST_ITEM (L"\\bu @@Save as FLAC file...@") MAN_END MAN_BEGIN (L"LongSound", L"ppgb", 20110131) INTRO (L"One of the @@types of objects@ in Praat. See the @@Sound files@ tutorial.") NORMAL (L"A LongSound object gives you the ability to view and label " "a sound file that resides on disk. You will want to use it for sounds " "that are too long to read into memory as a @Sound object (typically, a few minutes).") ENTRY (L"How to create a LongSound object") NORMAL (L"You create a LongSound object with @@Open long sound file...@ from the @@Open menu@.") ENTRY (L"What you can do with a LongSound object") NORMAL (L"You can save a LongSound object to a new sound file, " "perhaps in a different format (AIFF, AIFC, WAV, NeXT/Sun, NIST, FLAC) " "with the commands in the Save menu. You can also concatenate several " "LongSound objects in this way. See @@How to concatenate sound files@.") ENTRY (L"How to view and edit a LongSound object") NORMAL (L"You can view a LongSound object in a @LongSoundEditor by choosing @@LongSound: View@. " "This also allows you to extract parts of the LongSound as @Sound objects, " "or save these parts as a sound file. " "There are currently no ways to actually change the data in the file.") ENTRY (L"How to annotate a LongSound object") NORMAL (L"You can label and segment a LongSound object after the following steps:") LIST_ITEM (L"1. Select the LongSound object.") LIST_ITEM (L"2. Choose @@LongSound: To TextGrid...@ and specify your tiers.") LIST_ITEM (L"3. Select the resulting @TextGrid object together with the LongSound object, and click ##View & Edit#.") NORMAL (L"A @TextGridEditor will appear on the screen, with a copy of the LongSound object in it.") ENTRY (L"Limitations") NORMAL (L"The length of the sound file is limited to 2 gigabytes, which is 3 hours of CD-quality stereo, " "or 12 hours 16-bit mono sampled at 22050 Hz.") MAN_END MAN_BEGIN (L"LongSound: To TextGrid...", L"ppgb", 19980730) INTRO (L"A command to create a @TextGrid without any labels, copying the time domain from the selected @LongSound.") NORMAL (L"See @@Sound: To TextGrid...@ for the settings.") MAN_END MAN_BEGIN (L"LongSound: View", L"ppgb", 19980730) INTRO (L"A command to view the selected @LongSound object in a @LongSoundEditor.") MAN_END MAN_BEGIN (L"LongSoundEditor", L"ppgb", 20041124) INTRO (L"One of the @Editors in Praat, for viewing a @LongSound object.") NORMAL (L"This viewer allows you:") LIST_ITEM (L"\\bu to view and hear parts of the sound as it is on disk;") LIST_ITEM (L"\\bu to copy a selected part as a @Sound object to the list of objects, so that you " "can perform analyses on it or save it to a smaller sound file;") LIST_ITEM (L"\\bu to copy a selected part as a @Sound object to the @Sound clipboard, " "so that you can paste it into another Sound object that you are viewing in a @SoundEditor.") NORMAL (L"To label and segment the LongSound object, use the @TextGridEditor instead (see @LongSound).") NORMAL (L"The display and playback of the samples is restricted to 60 seconds at a time, for reasons of speed " "(although you can change this number with ##LongSound prefs# from the main #Preferences menu; " "the sound file itself can contain several hours of sound.") MAN_END MAN_BEGIN (L"Macintosh sound files", L"ppgb", 20110131) INTRO (L"A way for storing a @Sound object on disk.") ENTRY (L"File format") NORMAL (L"The double-clickable sound file of the Macintosh (8 bits per sample). " "Cannot be ported to other machines, because the sound is in the @@resource fork@.") ENTRY (L"Reading") NORMAL (L"With @@Read from file...@.") NORMAL (L"To read a Sound from a Macintosh sound file on disk, use @@Read from file...@ (Macintosh only).") NORMAL (L"The 8-bit sample values are divided by 128 so that the amplitude " "of the resulting Sound is between \\--1.0 and +1.0.") NORMAL (L"The resulting Sound will appear in the list of objects; " "its name will be equal to the file name, without extension.") ENTRY (L"Saving") NORMAL (L"With ##Save as Mac sound file...#. Praat asks you for a file name. " "After you click OK, 0.5 is added to the samples of the Sound, " "they are multiplied by 128 and quantized between 0 and 255; " "the result is written to the file in 8-bit linear Macintosh sound-file format.") NORMAL (L"To avoid clipping, keep the absolute amplitude below 1.000. " "If the maximum sound pressure level is 91 dB (top = 127), " "the quantization threshold for a sine wave is (top = 1/2) 43 dB.") MAN_END MAN_BEGIN (L"Open long sound file...", L"ppgb", 19980730) INTRO (L"A command in the @@Open menu@ that creates a @LongSound object.") NORMAL (L"The file will be opened for reading only. The file stays open until you remove the LongSound object.") MAN_END MAN_BEGIN (L"Sesam/LVS files", L"ppgb", 20110131) INTRO (L"A way for storing a @Sound object on disk.") ENTRY (L"File format") NORMAL (L"The sound files used by the SESAM and LVS programs. Each sample is normally quantized into 12 bits.") ENTRY (L"Reading") NORMAL (L"To read a #Sound from a Sesam file on disk, use @@Read from file...@. " "The file name is expected to end in \".sdf\" or \".SDF\".") NORMAL (L"The 12-bit sample values are divided by 2048 so that the amplitude " "of the resulting Sound is between -1.0 and +1.0.") NORMAL (L"The resulting #Sound will appear in the List of Objects; " "its name will be equal to the file name, without extension.") NORMAL (L"If the sound was encoded in 16 bits per sample, you should divide by 16 after reading " "(with $$Formula... self/16$)") ENTRY (L"Saving") NORMAL (L"With ##Save as Sesam file...#. Praat then asks you for a file name. " "After you click OK, the samples of the Sound are multiplied by 2048 " "and quantized between -2048 and 2047; " "the result is written to the file in 12-bit LVS and Sesam format.") NORMAL (L"To avoid clipping, keep the absolute amplitude below 1.000. " "If the maximum sound pressure level is 91 dB (top = 2047), " "the quantization threshold is (top = 1/2) 19 dB.") NORMAL (L"If you prefer 16-bit encoding, you should multiply by 16 before saving " "(with $$Formula... self*16$)") MAN_END } /* End of file manual_soundFiles.cpp */ sources_5316/fon/Sampled_def.h0000644000176700017670000000311411621511216015054 0ustar paulpaul/* Sampled_def.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Sampled oo_DEFINE_CLASS (Sampled, Function) oo_LONG (nx) oo_DOUBLE (dx) oo_DOUBLE (x1) #if oo_DECLARING // overridden methods: virtual bool v_hasGetNx () { return true; } virtual double v_getNx () { return nx; } virtual bool v_hasGetDx () { return true; } virtual double v_getDx () { return dx; } virtual bool v_hasGetX () { return true; } virtual double v_getX (long ix) { return x1 + (ix - 1) * dx; } virtual void v_shiftX (double xfrom, double xto); virtual void v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto); // new methods: virtual double v_getValueAtSample (long isamp, long ilevel, int unit) { (void) isamp; (void) ilevel; (void) unit; return NUMundefined; } #endif oo_END_CLASS (Sampled) #undef ooSTRUCT /* End of file Sampled_def.h */ sources_5316/fon/ManipulationEditor.h0000644000176700017670000000430311623752044016471 0ustar paulpaul#ifndef _ManipulationEditor_h_ #define _ManipulationEditor_h_ /* ManipulationEditor.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "FunctionEditor.h" #include "Manipulation.h" #include "ManipulationEditor_enums.h" Thing_define (ManipulationEditor, FunctionEditor) { // new data: public: PointProcess previousPulses; PitchTier previousPitch; DurationTier previousDuration; double soundmin, soundmax; int synthesisMethod; GuiObject synthPulsesButton, synthPulsesHumButton; GuiObject synthPulsesLpcButton; GuiObject synthPitchButton, synthPitchHumButton; GuiObject synthPulsesPitchButton, synthPulsesPitchHumButton; GuiObject synthOverlapAddNodurButton, synthOverlapAddButton; GuiObject synthPitchLpcButton; struct { enum kManipulationEditor_pitchUnits units; enum kManipulationEditor_draggingStrategy draggingStrategy; double minimum, minPeriodic, maximum, cursor; } pitchTier; struct { double minimum, maximum, cursor; } duration; Graphics_Viewport inset; // overridden methods: virtual void v_destroy (); virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_saveData (); virtual void v_restoreData (); virtual void v_draw (); virtual int v_click (double xWC, double yWC, bool shiftKeyPressed); virtual void v_play (double tmin, double tmax); }; ManipulationEditor ManipulationEditor_create (GuiObject parent, const wchar *title, Manipulation ana); void ManipulationEditor_prefs (void); /* End of file ManipulationEditor.h */ #endif sources_5316/fon/PointProcess_def.h0000644000176700017670000000277411621654541016143 0ustar paulpaul/* PointProcess_def.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT PointProcess oo_DEFINE_CLASS (PointProcess, Function) #if oo_DECLARING || oo_COPYING oo_LONG (maxnt) #endif oo_LONG (nt) #if oo_COPYING oo_DOUBLE_VECTOR (t, maxnt) #elif oo_READING if (nt) { maxnt = nt; oo_DOUBLE_VECTOR (t, nt) } else { maxnt = 1; t = NUMvector (1, 1); } #else oo_DOUBLE_VECTOR (t, nt) #endif #if oo_DECLARING // overridden methods: public: virtual void v_info (); virtual int v_domainQuantity () { return MelderQuantity_TIME_SECONDS; } virtual void v_shiftX (double xfrom, double xto); virtual void v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto); #endif oo_END_CLASS (PointProcess) #undef ooSTRUCT /* End of file PointProcess_def.h */ sources_5316/fon/Formant.cpp0000644000176700017670000005215411634625546014642 0ustar paulpaul/* Formant.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2004/10/05 allow reverse axes in scatter plot (and remove special routine for those) * pb 2005/12/08 Formant_getQuantileOfBandwidth * pb 2007/03/17 domain quantity * pb 2007/10/01 can write as encoding * pb 2008/01/19 version 2 * pb 2008/01/19 don't draw undefined lines * pb 2008/06/01 Formant_downto_Table, Formant_list * pb 2009/01/18 Interpreter argument to formula * pb 2011/05/24 C++ */ #include "Formant.h" #include "oo_DESTROY.h" #include "Formant_def.h" #include "oo_COPY.h" #include "Formant_def.h" #include "oo_EQUAL.h" #include "Formant_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "Formant_def.h" #include "oo_READ_TEXT.h" #include "Formant_def.h" #include "oo_WRITE_TEXT.h" #include "Formant_def.h" #include "oo_READ_BINARY.h" #include "Formant_def.h" #include "oo_WRITE_BINARY.h" #include "Formant_def.h" #include "oo_DESCRIPTION.h" #include "Formant_def.h" Thing_implement (Formant, Sampled, 2); // version 1 = with intensity, 2 = double void structFormant :: v_info () { structData :: v_info (); MelderInfo_writeLine1 (L"Time domain:"); MelderInfo_writeLine3 (L" Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine3 (L" End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine3 (L" Total duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine1 (L"Time sampling:"); MelderInfo_writeLine2 (L" Number of frames: ", Melder_integer (nx)); MelderInfo_writeLine3 (L" Time step: ", Melder_double (dx), L" seconds"); MelderInfo_writeLine3 (L" First frame centred at: ", Melder_double (x1), L" seconds"); } double structFormant :: v_getValueAtSample (long iframe, long which, int units) { Formant_Frame frame = & d_frames [iframe]; long iformant = which >> 1; if (iformant < 1 || iformant > frame -> nFormants) return NUMundefined; double frequency = frame -> formant [iformant]. frequency; if ((which & 1) == 0) { return units ? NUMhertzToBark (frequency) : frequency; } else { double bandwidth = frame -> formant [iformant]. bandwidth; if (units) { double fleft = frequency - 0.5 * bandwidth, fright = frequency + 0.5 * bandwidth; fleft = fleft <= 0 ? 0 : NUMhertzToBark (fleft); // prevent NUMundefined fright = NUMhertzToBark (fright); return fright - fleft; } return bandwidth; } return NUMundefined; } Formant Formant_create (double tmin, double tmax, long nt, double dt, double t1, int maxnFormants) { try { autoFormant me = Thing_new (Formant); Sampled_init (me.peek(), tmin, tmax, nt, dt, t1); therror my d_frames = NUMvector (1, nt); my maxnFormants = maxnFormants; return me.transfer(); } catch (MelderError) { Melder_throw ("Formant object not created."); } } long Formant_getMinNumFormants (Formant me) { long minNumFormants = 100000000; for (long iframe = 1; iframe <= my nx; iframe ++) if (my d_frames [iframe]. nFormants < minNumFormants) minNumFormants = my d_frames [iframe]. nFormants; return minNumFormants; } long Formant_getMaxNumFormants (Formant me) { long maxNumFormants = 0; for (long iframe = 1; iframe <= my nx; iframe ++) if (my d_frames [iframe]. nFormants > maxNumFormants) maxNumFormants = my d_frames [iframe]. nFormants; return maxNumFormants; } void Formant_drawTracks (Formant me, Graphics g, double tmin, double tmax, double fmax, int garnish) { long itmin, itmax, ntrack = Formant_getMinNumFormants (me); if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } if (! Sampled_getWindowSamples (me, tmin, tmax, & itmin, & itmax)) return; Graphics_setInner (g); Graphics_setWindow (g, tmin, tmax, 0.0, fmax); for (long itrack = 1; itrack <= ntrack; itrack ++) { for (long iframe = itmin; iframe < itmax; iframe ++) { Formant_Frame curFrame = & my d_frames [iframe], nextFrame = & my d_frames [iframe + 1]; double x1 = Sampled_indexToX (me, iframe), x2 = Sampled_indexToX (me, iframe + 1); double f1 = curFrame -> formant [itrack]. frequency; double f2 = nextFrame -> formant [itrack]. frequency; if (NUMdefined (x1) && NUMdefined (f1) && NUMdefined (x2) && NUMdefined (f2)) Graphics_line (g, x1, f1, x2, f2); } } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Time (s)"); Graphics_textLeft (g, 1, L"Formant frequency (Hz)"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeftEvery (g, 1.0, 1000.0, 1, 1, 1); } } void Formant_drawSpeckles_inside (Formant me, Graphics g, double tmin, double tmax, double fmin, double fmax, double suppress_dB, double dotSize) { long itmin, itmax; double maximumIntensity = 0.0, minimumIntensity; if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } if (! Sampled_getWindowSamples (me, tmin, tmax, & itmin, & itmax)) return; Graphics_setWindow (g, tmin, tmax, fmin, fmax); for (long iframe = itmin; iframe <= itmax; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; if (frame -> intensity > maximumIntensity) maximumIntensity = frame -> intensity; } if (maximumIntensity == 0.0 || suppress_dB <= 0.0) minimumIntensity = 0.0; /* Ignore. */ else minimumIntensity = maximumIntensity / pow (10.0, suppress_dB / 10.0); for (long iframe = itmin; iframe <= itmax; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; double x = Sampled_indexToX (me, iframe); if (frame -> intensity < minimumIntensity) continue; for (long iformant = 1; iformant <= frame -> nFormants; iformant ++) { double frequency = frame -> formant [iformant]. frequency; if (frequency >= fmin && frequency <= fmax) Graphics_fillCircle_mm (g, x, frequency, dotSize); } } } void Formant_drawSpeckles (Formant me, Graphics g, double tmin, double tmax, double fmax, double suppress_dB, int garnish) { Graphics_setInner (g); Formant_drawSpeckles_inside (me, g, tmin, tmax, 0.0, fmax, suppress_dB, 1.0); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Time (s)"); Graphics_textLeft (g, 1, L"Formant frequency (Hz)"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeftEvery (g, 1.0, 1000.0, 1, 1, 1); } } void Formant_formula_bandwidths (Formant me, const wchar *formula, Interpreter interpreter) { try { long nrow = Formant_getMaxNumFormants (me); if (nrow < 1) Melder_throw (L"No formants available."); autoMatrix mat = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 0.5, nrow + 0.5, nrow, 1, 1); for (long iframe = 1; iframe <= my nx; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; for (long iformant = 1; iformant <= frame -> nFormants; iformant ++) mat -> z [iformant] [iframe] = frame -> formant [iformant]. bandwidth; } Matrix_formula (mat.peek(), formula, interpreter, NULL); therror for (long iframe = 1; iframe <= my nx; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; for (long iformant = 1; iformant <= frame -> nFormants; iformant ++) frame -> formant [iformant]. bandwidth = mat -> z [iformant] [iframe]; } } catch (MelderError) { Melder_throw (me, ": bandwidth formula not executed."); } } void Formant_formula_frequencies (Formant me, const wchar *formula, Interpreter interpreter) { try { long nrow = Formant_getMaxNumFormants (me); if (nrow < 1) Melder_throw ("No formants available."); autoMatrix mat = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 0.5, nrow + 0.5, nrow, 1, 1); for (long iframe = 1; iframe <= my nx; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; for (long iformant = 1; iformant <= frame -> nFormants; iformant ++) mat -> z [iformant] [iframe] = frame -> formant [iformant]. frequency; } Matrix_formula (mat.peek(), formula, interpreter, NULL); therror for (long iframe = 1; iframe <= my nx; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; for (long iformant = 1; iformant <= frame -> nFormants; iformant ++) frame -> formant [iformant]. frequency = mat -> z [iformant] [iframe]; } } catch (MelderError) { Melder_throw (me, ": frequency formula not executed."); } } void Formant_getExtrema (Formant me, int iformant, double tmin, double tmax, double *fmin, double *fmax) { long itmin, itmax, iframe; if (fmin) *fmin = 0.0; if (fmax) *fmax = 0.0; if (iformant < 1) return; if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } if (! Sampled_getWindowSamples (me, tmin, tmax, & itmin, & itmax)) return; for (iframe = itmin; iframe <= itmax; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; double f; if (iformant > frame -> nFormants) continue; f = frame -> formant [iformant]. frequency; if (! f) continue; if (fmin) if (f < *fmin || *fmin == 0.0) *fmin = f; if (fmax) if (f > *fmax) *fmax = f; } } void Formant_getMinimumAndTime (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate, double *return_minimum, double *return_timeOfMinimum) { Sampled_getMinimumAndX (me, tmin, tmax, iformant << 1, bark, interpolate, return_minimum, return_timeOfMinimum); if (return_minimum && *return_minimum <= 0.0) *return_minimum = NUMundefined; } double Formant_getMinimum (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate) { double minimum; Formant_getMinimumAndTime (me, iformant, tmin, tmax, bark, interpolate, & minimum, NULL); return minimum; } double Formant_getTimeOfMinimum (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate) { double time; Formant_getMinimumAndTime (me, iformant, tmin, tmax, bark, interpolate, NULL, & time); return time; } void Formant_getMaximumAndTime (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate, double *return_maximum, double *return_timeOfMaximum) { Sampled_getMaximumAndX (me, tmin, tmax, iformant << 1, bark, interpolate, return_maximum, return_timeOfMaximum); if (return_maximum && *return_maximum <= 0.0) *return_maximum = NUMundefined; /* Unlikely. */ } double Formant_getMaximum (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate) { double maximum; Formant_getMaximumAndTime (me, iformant, tmin, tmax, bark, interpolate, & maximum, NULL); return maximum; } double Formant_getTimeOfMaximum (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate) { double time; Formant_getMaximumAndTime (me, iformant, tmin, tmax, bark, interpolate, NULL, & time); return time; } double Formant_getQuantile (Formant me, int iformant, double quantile, double tmin, double tmax, int bark) { return Sampled_getQuantile (me, tmin, tmax, quantile, iformant << 1, bark); } double Formant_getMean (Formant me, int iformant, double tmin, double tmax, int bark) { return Sampled_getMean (me, tmin, tmax, iformant << 1, bark, TRUE); } double Formant_getStandardDeviation (Formant me, int iformant, double tmin, double tmax, int bark) { if (iformant < 1 || tmin == NUMundefined || tmax == NUMundefined) return NUMundefined; if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } long itmin, itmax; if (! Sampled_getWindowSamples (me, tmin, tmax, & itmin, & itmax)) return NUMundefined; double mean = Formant_getMean (me, iformant, tmin, tmax, bark); double sum = 0.0; long n = 0; for (long iframe = itmin; iframe <= itmax; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; if (iformant > frame -> nFormants) continue; double f = frame -> formant [iformant]. frequency; if (! f) continue; if (bark) f = NUMhertzToBark (f); n += 1; sum += (f - mean) * (f - mean); } if (n > 1) return sqrt (sum / (n - 1)); return NUMundefined; } double Formant_getValueAtTime (Formant me, int iformant, double time, int bark) { return Sampled_getValueAtX (me, time, iformant << 1, bark, TRUE); } double Formant_getBandwidthAtTime (Formant me, int iformant, double time, int bark) { return Sampled_getValueAtX (me, time, (iformant << 1) + 1, bark, TRUE); } double Formant_getQuantileOfBandwidth (Formant me, int iformant, double quantile, double tmin, double tmax, int bark) { return Sampled_getQuantile (me, tmin, tmax, quantile, (iformant << 1) + 1, bark); } void Formant_scatterPlot (Formant me, Graphics g, double tmin, double tmax, int iformant1, double fmin1, double fmax1, int iformant2, double fmin2, double fmax2, double size_mm, const wchar *mark, int garnish) { if (iformant1 < 1 || iformant2 < 1) return; if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } long itmin, itmax; if (! Sampled_getWindowSamples (me, tmin, tmax, & itmin, & itmax)) return; if (fmax1 == fmin1) Formant_getExtrema (me, iformant1, tmin, tmax, & fmin1, & fmax1); if (fmax1 == fmin1) return; if (fmax2 == fmin2) Formant_getExtrema (me, iformant2, tmin, tmax, & fmin2, & fmax2); if (fmax2 == fmin2) return; Graphics_setInner (g); Graphics_setWindow (g, fmin1, fmax1, fmin2, fmax2); for (long iframe = itmin; iframe <= itmax; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; if (iformant1 > frame -> nFormants || iformant2 > frame -> nFormants) continue; double x = frame -> formant [iformant1]. frequency; double y = frame -> formant [iformant2]. frequency; if (x == 0.0 || y == 0.0) continue; Graphics_mark (g, x, y, size_mm, mark); } Graphics_unsetInner (g); if (garnish) { wchar text [100]; Graphics_drawInnerBox (g); swprintf (text, 100, L"%%F_%d (Hz)", iformant1); Graphics_textBottom (g, 1, text); swprintf (text, 100, L"%%F_%d (Hz)", iformant2); Graphics_textLeft (g, 1, text); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } Matrix Formant_to_Matrix (Formant me, int iformant) { try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 1.0, 1.0, 1, 1.0, 1.0); for (long iframe = 1; iframe <= my nx; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; thy z [1] [iframe] = iformant <= frame -> nFormants ? frame -> formant [iformant]. frequency : 0.0; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": frequencies of formant ", iformant, " not converted to Matrix."); } } Matrix Formant_to_Matrix_bandwidths (Formant me, int iformant) { try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, 1.0, 1.0, 1, 1.0, 1.0); for (long iframe = 1; iframe <= my nx; iframe ++) { Formant_Frame frame = & my d_frames [iframe]; thy z [1] [iframe] = iformant <= frame -> nFormants ? frame -> formant [iformant]. bandwidth : 0.0; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": bandwidths of formant ", iformant, " not converted to Matrix."); } } /*** Viterbi methods. ***/ struct fparm { Formant me, thee; double dfCost, bfCost, octaveJumpCost, refF [1 + 5]; }; static double getLocalCost (long iframe, long icand, int itrack, void *closure) { struct fparm *me = (struct fparm *) closure; Formant_Frame frame = & my my d_frames [iframe]; Formant_Formant candidate; if (icand > frame -> nFormants) return 1e30; candidate = & frame -> formant [icand]; /*if (candidate -> frequency <= 0.0) candidate -> frequency = 0.001; /*Melder_fatal ("Weird formant frequency %ls Hz.", Melder_double (candidate -> frequency))*/; Melder_assert (candidate -> bandwidth > 0.0); Melder_assert (itrack > 0 && itrack <= 5); return my dfCost * fabs (candidate -> frequency - my refF [itrack]) + my bfCost * candidate -> bandwidth / candidate -> frequency; } static double getTransitionCost (long iframe, long icand1, long icand2, int itrack, void *closure) { struct fparm *me = (struct fparm *) closure; Formant_Frame prevFrame = & my my d_frames [iframe - 1], curFrame = & my my d_frames [iframe]; double f1, f2; (void) itrack; if (icand1 > prevFrame -> nFormants || icand2 > curFrame -> nFormants) return 1e30; f1 = prevFrame -> formant [icand1]. frequency; f2 = curFrame -> formant [icand2]. frequency; /*Melder_assert (f1 > 0.0);*/ /*Melder_assert (f2 > 0.0);*/ return my octaveJumpCost * fabs (NUMlog2 (f1 / f2)); } static void putResult (long iframe, long place, int itrack, void *closure) { struct fparm *me = (struct fparm *) closure; Melder_assert (iframe > 0 && iframe <= my my nx); Melder_assert (itrack > 0 && itrack <= 5); Melder_assert (place > 0); Melder_assert (place <= my my d_frames [iframe]. nFormants); my thy d_frames [iframe]. formant [itrack] = my my d_frames [iframe]. formant [place]; } Formant Formant_tracker (Formant me, int ntrack, double refF1, double refF2, double refF3, double refF4, double refF5, double dfCost, /* Per kHz. */ double bfCost, double octaveJumpCost) { try { long nformmin = Formant_getMinNumFormants (me); struct fparm parm; if (ntrack > nformmin) Melder_throw ("Number of tracks (", ntrack, ") should not exceed minimum number of formants (", nformmin, ")."); autoFormant thee = Formant_create (my xmin, my xmax, my nx, my dx, my x1, ntrack); for (long iframe = 1; iframe <= thy nx; iframe ++) { thy d_frames [iframe]. formant = NUMvector (1, ntrack); thy d_frames [iframe]. nFormants = ntrack; thy d_frames [iframe]. intensity = my d_frames [iframe]. intensity; } /* BUG: limit costs to 1e10 or so */ parm.me = me; parm.thee = thee.peek(); parm.dfCost = dfCost / 1000.0; // per Hz parm.bfCost = bfCost; parm.octaveJumpCost = octaveJumpCost; parm.refF [1] = refF1; parm.refF [2] = refF2; parm.refF [3] = refF3; parm.refF [4] = refF4; parm.refF [5] = refF5; NUM_viterbi_multi (my nx, my maxnFormants, ntrack, getLocalCost, getTransitionCost, putResult, & parm); therror return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not tracked."); } } Table Formant_downto_Table (Formant me, bool includeFrameNumbers, bool includeTimes, int timeDecimals, bool includeIntensity, int intensityDecimals, bool includeNumberOfFormants, int frequencyDecimals, bool includeBandwidths) { try { autoTable thee = Table_createWithoutColumnNames (my nx, includeFrameNumbers + includeTimes + includeIntensity + includeNumberOfFormants + my maxnFormants * (1 + includeBandwidths)); long icol = 0; if (includeFrameNumbers) Table_setColumnLabel (thee.peek(), ++ icol, L"frame"); if (includeTimes) Table_setColumnLabel (thee.peek(), ++ icol, L"time(s)"); if (includeIntensity) Table_setColumnLabel (thee.peek(), ++ icol, L"intensity"); if (includeNumberOfFormants) Table_setColumnLabel (thee.peek(), ++ icol, L"nformants"); for (long iformant = 1; iformant <= my maxnFormants; iformant ++) { Table_setColumnLabel (thee.peek(), ++ icol, Melder_wcscat (L"F", Melder_integer (iformant), L"(Hz)")); therror if (includeBandwidths) { Table_setColumnLabel (thee.peek(), ++ icol, Melder_wcscat (L"B", Melder_integer (iformant), L"(Hz)")); } } for (long iframe = 1; iframe <= my nx; iframe ++) { icol = 0; if (includeFrameNumbers) { Table_setNumericValue (thee.peek(), iframe, ++ icol, iframe); therror } if (includeTimes) { Table_setStringValue (thee.peek(), iframe, ++ icol, Melder_fixed (my x1 + (iframe - 1) * my dx, timeDecimals)); therror } Formant_Frame frame = & my d_frames [iframe]; if (includeIntensity) { Table_setStringValue (thee.peek(), iframe, ++ icol, Melder_fixed (frame -> intensity, intensityDecimals)); therror } if (includeNumberOfFormants) { Table_setNumericValue (thee.peek(), iframe, ++ icol, frame -> nFormants); therror } for (long iformant = 1; iformant <= frame -> nFormants; iformant ++) { Formant_Formant formant = & frame -> formant [iformant]; Table_setStringValue (thee.peek(), iframe, ++ icol, Melder_fixed (formant -> frequency, frequencyDecimals)); therror if (includeBandwidths) { Table_setStringValue (thee.peek(), iframe, ++ icol, Melder_fixed (formant -> bandwidth, frequencyDecimals)); therror } } for (long iformant = frame -> nFormants + 1; iformant <= my maxnFormants; iformant ++) { Table_setNumericValue (thee.peek(), iframe, ++ icol, NUMundefined); therror if (includeBandwidths) { Table_setNumericValue (thee.peek(), iframe, ++ icol, NUMundefined); therror } } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Table."); } } void Formant_list (Formant me, bool includeFrameNumbers, bool includeTimes, int timeDecimals, bool includeIntensity, int intensityDecimals, bool includeNumberOfFormants, int frequencyDecimals, bool includeBandwidths) { try { autoTable table = Formant_downto_Table (me, includeFrameNumbers, includeTimes, timeDecimals, includeIntensity, intensityDecimals, includeNumberOfFormants, frequencyDecimals, includeBandwidths); Table_list (table.peek(), false); } catch (MelderError) { Melder_throw (me, ": not listed."); } } /* End of file Formant.cpp */ sources_5316/fon/Pitch_enums.h0000644000176700017670000000344110727043032015134 0ustar paulpaul/* Pitch_enums.h * * Copyright (C) 1992-2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/09 */ enums_begin (kPitch_unit, 0) enums_add (kPitch_unit, 0, HERTZ, L"Hertz") enums_add (kPitch_unit, 1, HERTZ_LOGARITHMIC, L"Hertz (logarithmic)") enums_add (kPitch_unit, 2, MEL, L"mel") enums_add (kPitch_unit, 3, LOG_HERTZ, L"logHertz") enums_add (kPitch_unit, 4, SEMITONES_1, L"semitones re 1 Hz") enums_add (kPitch_unit, 5, SEMITONES_100, L"semitones re 100 Hz") enums_add (kPitch_unit, 6, SEMITONES_200, L"semitones re 200 Hz") enums_add (kPitch_unit, 7, SEMITONES_440, L"semitones re 440 Hz") enums_add (kPitch_unit, 8, ERB, L"ERB") /* For reading old preferences files: */ enums_alt (kPitch_unit, HERTZ, L"0") enums_alt (kPitch_unit, HERTZ_LOGARITHMIC, L"1") enums_alt (kPitch_unit, MEL, L"2") enums_alt (kPitch_unit, LOG_HERTZ, L"3") enums_alt (kPitch_unit, SEMITONES_1, L"4") enums_alt (kPitch_unit, SEMITONES_100, L"5") enums_alt (kPitch_unit, SEMITONES_200, L"6") enums_alt (kPitch_unit, SEMITONES_440, L"7") enums_alt (kPitch_unit, ERB, L"8") enums_end (kPitch_unit, 8, HERTZ) /* End of file Pitch_enums.h */ sources_5316/fon/DurationTierEditor.h0000644000176700017670000000415611616732451016452 0ustar paulpaul#ifndef _DurationTierEditor_h_ #define _DurationTierEditor_h_ /* DurationTierEditor.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "RealTierEditor.h" #include "DurationTier.h" #include "Sound.h" Thing_define (DurationTierEditor, RealTierEditor) { // overridden methods: virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_play (double tmin, double tmax); virtual double v_minimumLegalValue () { return 0.0; } virtual const wchar * v_quantityText () { return L"Relative duration"; } virtual const wchar * v_quantityKey () { return L"Relative duration"; } virtual const wchar * v_rightTickUnits () { return L""; } virtual double v_defaultYmin () { return 0.25; } virtual double v_defaultYmax () { return 3.0; } virtual const wchar * v_setRangeTitle () { return L"Set duration range..."; } virtual const wchar * v_defaultYminText () { return L"0.25"; } virtual const wchar * v_defaultYmaxText () { return L"3.0"; } virtual const wchar * v_yminText () { return L"Minimum duration"; } virtual const wchar * v_ymaxText () { return L"Maximum duration"; } virtual const wchar * v_yminKey () { return L"Minimum duration"; } virtual const wchar * v_ymaxKey () { return L"Maximum duration"; } }; DurationTierEditor DurationTierEditor_create (GuiObject parent, const wchar *title, DurationTier duration, Sound sound, bool ownSound); /* 'sound' may be NULL. */ /* End of file DurationTierEditor.h */ #endif sources_5316/fon/TextGrid.h0000644000176700017670000001344311727411310014412 0ustar paulpaul#ifndef _TextGrid_h_ #define _TextGrid_h_ /* TextGrid.h * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "AnyTier.h" #include "Label.h" #include "Graphics.h" #include "TableOfReal.h" #include "Table.h" #include "TextGrid_def.h" oo_CLASS_CREATE (TextPoint, AnyPoint); TextPoint TextPoint_create (double time, const wchar *mark); void TextPoint_setText (TextPoint me, const wchar *text); oo_CLASS_CREATE (TextInterval, Function); TextInterval TextInterval_create (double tmin, double tmax, const wchar *text); void TextInterval_setText (TextInterval me, const wchar *text); oo_CLASS_CREATE (TextTier, Function); TextTier TextTier_create (double tmin, double tmax); void TextTier_addPoint (TextTier me, double time, const wchar *mark); TextTier TextTier_readFromXwaves (MelderFile file); PointProcess TextTier_getPoints (TextTier me, const wchar *text); oo_CLASS_CREATE (IntervalTier, Function); IntervalTier IntervalTier_create (double tmin, double tmax); IntervalTier IntervalTier_readFromXwaves (MelderFile file); void IntervalTier_writeToXwaves (IntervalTier me, MelderFile file); long IntervalTier_timeToLowIndex (IntervalTier me, double t); long IntervalTier_timeToIndex (IntervalTier me, double t); // obsolete long IntervalTier_timeToHighIndex (IntervalTier me, double t); long IntervalTier_hasTime (IntervalTier me, double t); long IntervalTier_hasBoundary (IntervalTier me, double t); PointProcess IntervalTier_getStartingPoints (IntervalTier me, const wchar *text); PointProcess IntervalTier_getEndPoints (IntervalTier me, const wchar *text); PointProcess IntervalTier_getCentrePoints (IntervalTier me, const wchar *text); PointProcess IntervalTier_PointProcess_startToCentre (IntervalTier tier, PointProcess point, double phase); PointProcess IntervalTier_PointProcess_endToCentre (IntervalTier tier, PointProcess point, double phase); void IntervalTier_removeLeftBoundary (IntervalTier me, long iinterval); void TextTier_removePoint (TextTier me, long ipoint); oo_CLASS_CREATE (TextGrid, Function); TextGrid TextGrid_createWithoutTiers (double tmin, double tmax); TextGrid TextGrid_create (double tmin, double tmax, const wchar *tierNames, const wchar *pointTiers); long TextGrid_countLabels (TextGrid me, long itier, const wchar *text); PointProcess TextGrid_getStartingPoints (TextGrid me, long itier, int which_Melder_STRING, const wchar *criterion); PointProcess TextGrid_getEndPoints (TextGrid me, long itier, int which_Melder_STRING, const wchar *criterion); PointProcess TextGrid_getCentrePoints (TextGrid me, long itier, int which_Melder_STRING, const wchar *criterion); PointProcess TextGrid_getPoints (TextGrid me, long itier, int which_Melder_STRING, const wchar *criterion); void TextGrid_checkSpecifiedTierNumberWithinRange (TextGrid me, long tierNumber); IntervalTier TextGrid_checkSpecifiedTierIsIntervalTier (TextGrid me, long tierNumber); TextTier TextGrid_checkSpecifiedTierIsPointTier (TextGrid me, long tierNumber); void TextGrid_addTier (TextGrid me, Function tier); TextGrid TextGrid_merge (Collection textGrids); TextGrid TextGrid_extractPart (TextGrid me, double tmin, double tmax, int preserveTimes); TextGrid Label_to_TextGrid (Label me, double duration); TextGrid Label_Function_to_TextGrid (Label me, Any function); TextTier PointProcess_upto_TextTier (PointProcess me, const wchar *text); TableOfReal IntervalTier_downto_TableOfReal (IntervalTier me, const wchar *label); TableOfReal IntervalTier_downto_TableOfReal_any (IntervalTier me); TableOfReal TextTier_downto_TableOfReal (TextTier me, const wchar *label); TableOfReal TextTier_downto_TableOfReal_any (TextTier me); TextGrid PointProcess_to_TextGrid_vuv (PointProcess me, double maxT, double meanT); long TextInterval_labelLength (TextInterval me); long TextPoint_labelLength (TextPoint me); long IntervalTier_maximumLabelLength (IntervalTier me); long TextTier_maximumLabelLength (TextTier me); long TextGrid_maximumLabelLength (TextGrid me); void TextGrid_genericize (TextGrid me); void TextGrid_nativize (TextGrid me); void TextInterval_removeText (TextInterval me); void TextPoint_removeText (TextPoint me); void IntervalTier_removeText (IntervalTier me); void TextTier_removeText (TextTier me); void TextGrid_insertBoundary (TextGrid me, int itier, double t); void TextGrid_removeBoundaryAtTime (TextGrid me, int itier, double t); void TextGrid_setIntervalText (TextGrid me, int itier, long iinterval, const wchar *text); void TextGrid_insertPoint (TextGrid me, int itier, double t, const wchar *mark); void TextGrid_setPointText (TextGrid me, int itier, long ipoint, const wchar *text); void TextGrid_writeToChronologicalTextFile (TextGrid me, MelderFile file); TextGrid TextGrid_readFromChronologicalTextFile (MelderFile file); TextGrid TextGrid_readFromCgnSyntaxFile (MelderFile file); Table TextGrid_downto_Table (TextGrid me, bool includeLineNumbers, int timeDecimals, bool includeTierNames, bool includeEmptyIntervals); void TextGrid_list (TextGrid me, bool includeLineNumbers, int timeDecimals, bool includeTierNames, bool includeEmptyIntervals); void TextGrid_correctRoundingErrors (TextGrid me); TextGrid TextGrids_concatenate (Collection me); /* End of file TextGrid.h */ #endif sources_5316/fon/FormantGridEditor.h0000644000176700017670000000375111620770570016254 0ustar paulpaul#ifndef _FormantGridEditor_h_ #define _FormantGridEditor_h_ /* FormantGridEditor.h * * Copyright (C) 2008-2011 Paul Boersma & David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "FunctionEditor.h" #include "FormantGrid.h" struct FormantGridEditor_Play { double samplingFrequency; }; struct FormantGridEditor_Source { struct { double tStart, f0Start, tMid, f0Mid, tEnd, f0End; } pitch; struct { double adaptFactor, maximumPeriod, openPhase, collisionPhase, power1, power2; } phonation; }; Thing_define (FormantGridEditor, FunctionEditor) { // new data: public: bool editingBandwidths; long selectedFormant; double formantFloor, formantCeiling, bandwidthFloor, bandwidthCeiling, ycursor; struct FormantGridEditor_Play play; struct FormantGridEditor_Source source; // overridden methods: virtual void v_createMenus (); virtual void v_draw (); virtual int v_click (double xWC, double yWC, bool shiftKeyPressed); virtual void v_play (double tmin, double tmax); // new methods: virtual bool v_hasSourceMenu () { return true; } }; void FormantGridEditor_init (FormantGridEditor me, GuiObject parent, const wchar *title, FormantGrid data); FormantGridEditor FormantGridEditor_create (GuiObject parent, const wchar *title, FormantGrid data); void FormantGridEditor_prefs (void); /* End of file FormantGridEditor.h */ #endif sources_5316/fon/Sound_enums.h0000644000176700017670000000442011356076323015163 0ustar paulpaul/* Sound_enums.h * * Copyright (C) 1992-2010 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2010/03/31 */ enums_begin (kSound_windowShape, 0) enums_add (kSound_windowShape, 0, RECTANGULAR, L"rectangular") enums_add (kSound_windowShape, 1, TRIANGULAR, L"triangular") enums_add (kSound_windowShape, 2, PARABOLIC, L"parabolic") enums_add (kSound_windowShape, 3, HANNING, L"Hanning") enums_add (kSound_windowShape, 4, HAMMING, L"Hamming") enums_add (kSound_windowShape, 5, GAUSSIAN_1, L"Gaussian1") enums_add (kSound_windowShape, 6, GAUSSIAN_2, L"Gaussian2") enums_add (kSound_windowShape, 7, GAUSSIAN_3, L"Gaussian3") enums_add (kSound_windowShape, 8, GAUSSIAN_4, L"Gaussian4") enums_add (kSound_windowShape, 9, GAUSSIAN_5, L"Gaussian5") enums_add (kSound_windowShape, 10, KAISER_1, L"Kaiser1") enums_add (kSound_windowShape, 11, KAISER_2, L"Kaiser2") enums_end (kSound_windowShape, 11, RECTANGULAR) enums_begin (kSounds_convolve_scaling, 1) enums_add (kSounds_convolve_scaling, 1, INTEGRAL, L"integral") enums_add (kSounds_convolve_scaling, 2, SUM, L"sum") enums_add (kSounds_convolve_scaling, 3, NORMALIZE, L"normalize") enums_add (kSounds_convolve_scaling, 4, PEAK_099, L"peak 0.99") enums_end (kSounds_convolve_scaling, 4, PEAK_099) enums_begin (kSounds_convolve_signalOutsideTimeDomain, 1) enums_add (kSounds_convolve_signalOutsideTimeDomain, 1, ZERO, L"zero") enums_add (kSounds_convolve_signalOutsideTimeDomain, 2, SIMILAR, L"similar") //enums_add (kSounds_convolve_signalOutsideTimeDomain, 3, PERIODIC, L"periodic") enums_end (kSounds_convolve_signalOutsideTimeDomain, 2, ZERO) /* End of file Sound_enums.h */ sources_5316/fon/Sound_enhance.cpp0000644000176700017670000001215611724502227015771 0ustar paulpaul/* Sound_enhance.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2004/11/22 simplified Sound_to_Spectrum () * pb 2007/01/28 made compatible with stereo sounds (by rejecting them) * pb 2007/07/22 renamed the overlap-add method in such a way that it does not sound like a trademark for diphone concatenation * pb 2008/01/19 double * pb 2011/06/07 C++ */ #include "Manipulation.h" #include "Sound_to_Pitch.h" #include "Pitch_to_PitchTier.h" #include "Pitch_to_PointProcess.h" #include "Sound_and_Spectrum.h" Sound Sound_lengthen_overlapAdd (Sound me, double fmin, double fmax, double factor) { try { if (my ny > 1) Melder_throw ("Overlap-add works only on mono sounds."); autoSound sound = Data_copy (me); Vector_subtractMean (sound.peek()); autoPitch pitch = Sound_to_Pitch (sound.peek(), 0.8 / fmin, fmin, fmax); autoPointProcess pulses = Sound_Pitch_to_PointProcess_cc (sound.peek(), pitch.peek()); autoPitchTier pitchTier = Pitch_to_PitchTier (pitch.peek()); autoDurationTier duration = DurationTier_create (my xmin, my xmax); RealTier_addPoint (duration.peek(), 0.5 * (my xmin + my xmax), factor); autoSound thee = Sound_Point_Pitch_Duration_to_Sound (sound.peek(), pulses.peek(), pitchTier.peek(), duration.peek(), 1.5 / fmin); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not lengthened."); } } Sound Sound_deepenBandModulation (Sound me, double enhancement_dB, double flow, double fhigh, double slowModulation, double fastModulation, double bandSmoothing) { try { autoSound thee = Data_copy (me); double maximumFactor = pow (10, enhancement_dB / 20), alpha = sqrt (log (2.0)); double alphaslow = alpha / slowModulation, alphafast = alpha / fastModulation; for (long channel = 1; channel <= my ny; channel ++) { autoSound channelSound = Sound_extractChannel (me, channel); autoSpectrum orgspec = Sound_to_Spectrum (channelSound.peek(), TRUE); /* * Keep the part of the sound that is outside the filter bank. */ autoSpectrum spec = Data_copy (orgspec.peek()); Spectrum_stopHannBand (spec.peek(), flow, fhigh, bandSmoothing); autoSound filtered = Spectrum_to_Sound (spec.peek()); long n = thy nx; double *amp = thy z [channel]; for (long i = 1; i <= n; i ++) amp [i] = filtered -> z [1] [i]; autoMelderProgress progress (L"Deepen band modulation..."); double fmin = flow; while (fmin < fhigh) { /* * Take a one-bark frequency band. */ double fmid_bark = NUMhertzToBark (fmin) + 0.5, ceiling; double fmax = NUMbarkToHertz (NUMhertzToBark (fmin) + 1); if (fmax > fhigh) fmax = fhigh; Melder_progress (fmin / fhigh, L"Band: ", Melder_fixed (fmin, 0), L" ... ", Melder_fixed (fmax, 0), L" Hz"); NUMmatrix_copyElements (orgspec -> z, spec -> z, 1, 2, 1, spec -> nx); Spectrum_passHannBand (spec.peek(), fmin, fmax, bandSmoothing); autoSound band = Spectrum_to_Sound (spec.peek()); /* * Compute a relative intensity contour. */ autoSound intensity = Data_copy (band.peek()); n = intensity -> nx; amp = intensity -> z [1]; for (long i = 1; i <= n; i ++) amp [i] = 10 * log10 (amp [i] * amp [i] + 1e-6); autoSpectrum intensityFilter = Sound_to_Spectrum (intensity.peek(), TRUE); n = intensityFilter -> nx; for (long i = 1; i <= n; i ++) { double frequency = intensityFilter -> x1 + (i - 1) * intensityFilter -> dx; double slow = alphaslow * frequency, fast = alphafast * frequency; double factor = exp (- fast * fast) - exp (- slow * slow); intensityFilter -> z [1] [i] *= factor; intensityFilter -> z [2] [i] *= factor; } intensity.reset (Spectrum_to_Sound (intensityFilter.peek())); n = intensity -> nx; amp = intensity -> z [1]; for (long i = 1; i <= n; i ++) amp [i] = pow (10, amp [i] / 2); /* * Clip to maximum enhancement. */ ceiling = 1 + (maximumFactor - 1.0) * (0.5 - 0.5 * cos (NUMpi * fmid_bark / 13)); for (long i = 1; i <= n; i ++) amp [i] = 1 / (1 / amp [i] + 1 / ceiling); n = thy nx; amp = thy z [channel]; for (long i = 1; i <= n; i ++) amp [i] += band -> z [1] [i] * intensity -> z [1] [i]; fmin = fmax; } } Vector_scale (thee.peek(), 0.99); /* Truncate. */ thy xmin = my xmin; thy xmax = my xmax; thy nx = my nx; thy x1 = my x1; return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": band modulation not deepened."); } } /* End of file Sound_enhance.cpp */ sources_5316/fon/Experiment_enums.h0000644000176700017670000000246311160255742016215 0ustar paulpaul/* Experiment_enums.h * * Copyright (C) 2001-2009 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2009/03/18 */ enums_begin (kExperiment_randomize, 0) enums_add (kExperiment_randomize, 0, CYCLIC_NON_RANDOM, L"CyclicNonRandom") enums_add (kExperiment_randomize, 1, PERMUTE_ALL, L"PermuteAll") enums_add (kExperiment_randomize, 2, PERMUTE_BALANCED, L"PermuteBalanced") enums_add (kExperiment_randomize, 3, PERMUTE_BALANCED_NO_DOUBLETS, L"PermuteBalancedNoDoublets") enums_add (kExperiment_randomize, 4, WITH_REPLACEMENT, L"WithReplacement") enums_end (kExperiment_randomize, 4, PERMUTE_BALANCED_NO_DOUBLETS) /* End of file Experiment_enums.h */ sources_5316/fon/manual_programming.cpp0000644000176700017670000001163511633766375017117 0ustar paulpaul/* manual_programming.cpp * * Copyright (C) 1992-2010 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" void manual_programming_init (ManPages me); void manual_programming_init (ManPages me) { MAN_BEGIN (L"Programming with Praat", L"ppgb", 20110831) INTRO (L"You can extend the functionality of the Praat program " "by adding modules written in C or C++ to it. All of Praat's source code " "is available under the General Public Licence.") ENTRY (L"1. Warning") NORMAL (L"Before trying the task of learning how to write Praat extensions in C or C++, " "you should be well aware of the possibilities of @scripting. " "Many built-in commands in Praat have started their " "lives as Praat scripts, and scripts are easier to write than extensions in C or C++. " "If you have a set of scripts, you can distribute them as a @@plug-ins|plug-in@.") ENTRY (L"2. Getting the existing source code") NORMAL (L"You obtain the Praat source code via ##www.praat.org#, in a file with a name like " "##praat5218_sources.tar.gz# (depending on the Praat version), and unpack this by double-clicking " "(on old computers, use #gunzip and ##tar xvf# if Unix, or ##StuffIt^\\re Expander^\\tm# if Macintosh, " "or ##Aladdin^\\re Expander^\\tm# if Windows). The result will be a set of directories " "called #kar, #GSL, #num, #audio (with #FLAC and #mp3 in it), #sys, #dwsys, #stat, #fon, #dwtools, #LPC, #FFNet, #gram, #artsynth, #contrib, #main, #makefiles, and #test, " "plus a makefile, a Codewarrior project for Windows, and an Xcode project for Macintosh.") ENTRY (L"3. Building Praat on Macintosh") NORMAL (L"Open ##praat.xcodeproj# in Xcode and choose #Build and #Run.") ENTRY (L"4. Building Praat on Windows") NORMAL (L"Open ##praat.mcp# in CodeWarrior (version 9.0 or higher), choose the target " "##praat_win#, and choose #Make or #Run.") NORMAL (L"Praat may compile under MinGW as well.") ENTRY (L"5. Building Praat on Linux") NORMAL (L"To compile and link Praat on Linux, you go to the directory that " "contains the source directories and the makefile, and copy a ##makefile.defs# " "file from the #makefiles directory:") CODE (L"> cp makefiles/makefile.defs.linux ./makefile.defs") NORMAL (L"You have to have installed ##libgtk2.0-dev# (and its dependencies) and ##libasound2-dev#.") NORMAL (L"On other Unixes, you do the same, but the file ##makefile.defs# may require some editing after this, " "because Silicon Graphics Irix, Sparc Solaris and HPUX may use different libraries or have them in different locations than Linux.") ENTRY (L"6. Extending Praat") NORMAL (L"You can edit ##main/main_Praat.cpp#. " "This example shows you how to create a very simple program with all the functionality " "of the Praat program, and a single bit more:") CODE (L"\\# include \"praat.h\"") CODE (L"") CODE (L"DIRECT (HelloFromJane)") CODE1 (L"Melder_information (L\"Hello, I am Jane.\");") CODE (L"END") CODE (L"") CODE (L"int main (int argc, char **argv) {") CODE1 (L"praat_init (\"Praat_Jane\", argc, argv);") CODE1 (L"INCLUDE_LIBRARY (praat_uvafon_init)") CODE1 (L"praat_addMenuCommand (L\"Objects\", L\"New\", L\"Hello from Jane...\", NULL, 0, DO_HelloFromJane);") CODE1 (L"praat_run ();") CODE1 (L"return 0;") CODE (L"}") ENTRY (L"7. Learning how to program") NORMAL (L"To see how objects are defined, take a look at ##sys/Thing.h#, ##sys/Data.h#, " "##sys/oo.h#, the ##XXX_def.h# files in the #fon directory, and the corresponding " "##XXX.c# and ##XXX.cpp# files in the #fon directory. To see how commands show up on the buttons " "in the fixed and dynamic menus, take a look at the large interface description file " "##fon/praat_Fon.cpp#.") ENTRY (L"8. Using the Praat shell only") NORMAL (L"For building the Praat shell (the Objects and Picture windows) only, you need only the code in the six directories " "#kar, #GSL, #num, #audio, #sys, and #dwsys. You delete the inclusion of praat_uvafon_init from #main. " "You will be able to build a Praat shell, i.e. an Objects and a Picture window, " "which has no knowledge of the world, i.e., which does not know any objects " "that can be included in the list of objects. You could use this Praat shell " "for modelling your own world and defining your own classes of objects. For advanced programmers only.") MAN_END } /* End of file manual_programming.cpp */ sources_5316/fon/PitchTier_to_Sound.cpp0000644000176700017670000001045011605364661016766 0ustar paulpaul/* PitchTier_to_Sound.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2004/10/03 sine wave generation * pb 2005/07/08 PitchTier_to_Sound_phonation * pb 2006/12/30 new Sound_create API * pb 2007/02/25 changed default sampling frequency to 44100 Hz * pb 2008/01/19 double * pb 2011/06/05 C++ */ #include "PitchTier_to_Sound.h" #include "PitchTier_to_PointProcess.h" #include "PointProcess_and_Sound.h" Sound PitchTier_to_Sound_pulseTrain (PitchTier me, double samplingFrequency, double adaptFactor, double adaptTime, long interpolationDepth, int hum) { static double formant [1 + 6] = { 0, 600, 1400, 2400, 3400, 4500, 5500 }; static double bandwidth [1 + 6] = { 0, 50, 100, 200, 300, 400, 500 }; try { autoPointProcess point = PitchTier_to_PointProcess (me); autoSound sound = PointProcess_to_Sound_pulseTrain (point.peek(), samplingFrequency, adaptFactor, adaptTime, interpolationDepth); if (hum) { Sound_filterWithFormants (sound.peek(), 0, 0, 6, formant, bandwidth); therror } return sound.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Sound (pulse train)."); } } Sound PitchTier_to_Sound_phonation (PitchTier me, double samplingFrequency, double adaptFactor, double maximumPeriod, double openPhase, double collisionPhase, double power1, double power2, int hum) { static double formant [1 + 6] = { 0, 600, 1400, 2400, 3400, 4500, 5500 }; static double bandwidth [1 + 6] = { 0, 50, 100, 200, 300, 400, 500 }; try { autoPointProcess point = PitchTier_to_PointProcess (me); autoSound sound = PointProcess_to_Sound_phonation (point.peek(), samplingFrequency, adaptFactor, maximumPeriod, openPhase, collisionPhase, power1, power2); if (hum) { Sound_filterWithFormants (sound.peek(), 0, 0, 6, formant, bandwidth); therror } return sound.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Sound (phonation)."); } } void PitchTier_playPart (PitchTier me, double tmin, double tmax, int hum) { try { autoSound sound = PitchTier_to_Sound_pulseTrain (me, 44100.0, 0.7, 0.05, 30, hum); Sound_playPart (sound.peek(), tmin, tmax, NULL, NULL); therror } catch (MelderError) { Melder_throw (me, ": not played."); } } void PitchTier_play (PitchTier me) { PitchTier_playPart (me, my xmin, my xmax, FALSE); } void PitchTier_hum (PitchTier me) { PitchTier_playPart (me, my xmin, my xmax, TRUE); } Sound PitchTier_to_Sound_sine (PitchTier me, double tmin, double tmax, double samplingFrequency) { try { if (tmax <= tmin) tmin = my xmin, tmax = my xmax; long numberOfSamples = 1 + floor ((my xmax - my xmin) * samplingFrequency); // >= 1 double samplingPeriod = 1.0 / samplingFrequency; double tmid = (tmin + tmax) / 2; double t1 = tmid - 0.5 * (numberOfSamples - 1) * samplingPeriod; autoSound thee = Sound_create (1, tmin, tmax, numberOfSamples, samplingPeriod, t1); double phase = 0.0; for (long isamp = 2; isamp <= numberOfSamples; isamp ++) { double tleft = t1 + (isamp - 1.5) * samplingPeriod; double fleft = RealTier_getValueAtTime (me, tleft); phase += fleft * thy dx; thy z [1] [isamp] = 0.5 * sin (2.0 * NUMpi * phase); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Sound (sine)."); } } void PitchTier_playPart_sine (PitchTier me, double tmin, double tmax) { try { if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } // autowindowing autoSound sound = PitchTier_to_Sound_sine (me, tmin, tmax, 44100.0); Sound_playPart (sound.peek(), tmin, tmax, NULL, NULL); therror } catch (MelderError) { Melder_throw (me, ": not played."); } } /* End of file PitchTier_to_Sound.cpp */ sources_5316/fon/ExperimentMFC_def.h0000644000176700017670000001210711621235422016141 0ustar paulpaul/* ExperimentMFC_def.h * * Copyright (C) 2001-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2003/02/07 added rootDirectory * pb 2003/03/08 added interStimulusInterval and initialSilenceDuration (version 2) * pb 2004/06/22 added response key (version 3) * pb 2005/11/21 added replayButton (version 4) * pb 2005/12/04 added okButton and oopsButton (version 4) * pb 2005/12/06 fix stimuliAreSounds: defaults to TRUE * pb 2007/08/12 wchar_t * pb 2007/09/26 added font size (version 5) * pb 2011/03/03 added reaction time (version 2 of ResultsMFC) */ /********* class ExperimentMFC **********/ #define ooSTRUCT SoundMFC oo_DEFINE_STRUCT (SoundMFC) oo_STRING (name) #if !oo_READING && !oo_WRITING oo_OBJECT (Sound, 0, sound) #endif oo_END_STRUCT (SoundMFC) #undef ooSTRUCT #define ooSTRUCT StimulusMFC oo_DEFINE_STRUCT (StimulusMFC) oo_STRING (name) oo_FROM (4) oo_STRING (visibleText) oo_ENDFROM #if !oo_READING && !oo_WRITING oo_OBJECT (Sound, 0, sound) #endif oo_END_STRUCT (StimulusMFC) #undef ooSTRUCT #define ooSTRUCT ResponseMFC oo_DEFINE_STRUCT (ResponseMFC) oo_FLOAT (left) oo_FLOAT (right) oo_FLOAT (bottom) oo_FLOAT (top) oo_STRING (label) oo_FROM (5) oo_INT (fontSize) oo_ENDFROM oo_FROM (3) oo_STRING (key) oo_ENDFROM oo_STRING (name) #if !oo_READING && !oo_WRITING oo_OBJECT (Sound, 0, sound) #endif oo_END_STRUCT (ResponseMFC) #undef ooSTRUCT #define ooSTRUCT GoodnessMFC oo_DEFINE_STRUCT (GoodnessMFC) oo_FLOAT (left) oo_FLOAT (right) oo_FLOAT (bottom) oo_FLOAT (top) oo_STRING (label) oo_END_STRUCT (GoodnessMFC) #undef ooSTRUCT #define ooSTRUCT ExperimentMFC oo_DEFINE_CLASS (ExperimentMFC, Data) oo_FROM (4) oo_QUESTION (stimuliAreSounds) oo_ENDFROM oo_STRING (stimulusFileNameHead) oo_STRING (stimulusFileNameTail) oo_STRUCT (SoundMFC, stimulusCarrierBefore) oo_STRUCT (SoundMFC, stimulusCarrierAfter) oo_FROM (2) oo_DOUBLE (stimulusInitialSilenceDuration) oo_DOUBLE (stimulusMedialSilenceDuration) oo_ENDFROM oo_LONG (numberOfDifferentStimuli) oo_STRUCT_VECTOR (StimulusMFC, stimulus, numberOfDifferentStimuli) oo_LONG (numberOfReplicationsPerStimulus) oo_LONG (breakAfterEvery) oo_ENUM (kExperiment_randomize, randomize) oo_STRING (startText) oo_STRING (runText) oo_STRING (pauseText) oo_STRING (endText) oo_FROM (4) oo_LONG (maximumNumberOfReplays) oo_FLOAT (replay_left) oo_FLOAT (replay_right) oo_FLOAT (replay_bottom) oo_FLOAT (replay_top) oo_STRING (replay_label) oo_STRING (replay_key) oo_FLOAT (ok_left) oo_FLOAT (ok_right) oo_FLOAT (ok_bottom) oo_FLOAT (ok_top) oo_STRING (ok_label) oo_STRING (ok_key) oo_FLOAT (oops_left) oo_FLOAT (oops_right) oo_FLOAT (oops_bottom) oo_FLOAT (oops_top) oo_STRING (oops_label) oo_STRING (oops_key) oo_ENDFROM oo_FROM (4) oo_QUESTION (responsesAreSounds) oo_STRING (responseFileNameHead) oo_STRING (responseFileNameTail) oo_STRUCT (SoundMFC, responseCarrierBefore) oo_STRUCT (SoundMFC, responseCarrierAfter) oo_DOUBLE (responseInitialSilenceDuration) oo_DOUBLE (responseMedialSilenceDuration) oo_ENDFROM oo_LONG (numberOfDifferentResponses) oo_STRUCT_VECTOR (ResponseMFC, response, numberOfDifferentResponses) oo_FROM (1) oo_LONG (numberOfGoodnessCategories) oo_STRUCT_VECTOR (GoodnessMFC, goodness, numberOfGoodnessCategories) oo_ENDFROM #if !oo_READING && !oo_WRITING oo_DOUBLE (samplePeriod) oo_INT (numberOfChannels) oo_BOOLEAN (pausing) oo_LONG (trial) oo_LONG (numberOfTrials) oo_LONG_VECTOR (stimuli, numberOfTrials) oo_LONG_VECTOR (responses, numberOfTrials) oo_DOUBLE_VECTOR (goodnesses, numberOfTrials) oo_DOUBLE (startingTime) oo_DOUBLE_VECTOR (reactionTimes, numberOfTrials) oo_OBJECT (Sound, 0, playBuffer) #endif oo_DIR (rootDirectory) #if oo_READING MelderDir_copy (& Data_directoryBeingRead, & rootDirectory); if (localVersion < 4) stimuliAreSounds = TRUE; #endif oo_END_CLASS (ExperimentMFC) #undef ooSTRUCT /********** class ResultsMFC **********/ #define ooSTRUCT TrialMFC oo_DEFINE_STRUCT (TrialMFC) oo_STRING (stimulus) oo_STRING (response) oo_FROM (1) oo_DOUBLE (goodness) oo_ENDFROM oo_FROM (2) oo_DOUBLE (reactionTime) oo_ENDFROM oo_END_STRUCT (TrialMFC) #undef ooSTRUCT #define ooSTRUCT ResultsMFC oo_DEFINE_CLASS (ResultsMFC, Data) oo_LONG (numberOfTrials) oo_STRUCT_VECTOR (TrialMFC, result, numberOfTrials) oo_END_CLASS (ResultsMFC) #undef ooSTRUCT /* End of file ExperimentMFC_def.h */ sources_5316/fon/IntensityTier.cpp0000644000176700017670000001014011633510334016016 0ustar paulpaul/* IntensityTier.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "IntensityTier.h" Thing_implement (IntensityTier, RealTier, 0); IntensityTier IntensityTier_create (double tmin, double tmax) { try { autoIntensityTier me = Thing_new (IntensityTier); RealTier_init (me.peek(), tmin, tmax); return me.transfer(); } catch (MelderError) { Melder_throw ("IntensityTier not created."); } } void IntensityTier_draw (IntensityTier me, Graphics g, double tmin, double tmax, double ymin, double ymax, const wchar *method, int garnish) { RealTier_draw (me, g, tmin, tmax, ymin, ymax, garnish, method, L"Intensity (dB)"); } IntensityTier PointProcess_upto_IntensityTier (PointProcess me, double intensity) { try { return (IntensityTier) PointProcess_upto_RealTier (me, intensity, classIntensityTier); } catch (MelderError) { Melder_throw (me, ": not converted to IntensityTier."); } } IntensityTier Intensity_downto_IntensityTier (Intensity me) { try { return (IntensityTier) Vector_to_RealTier (me, 1, classIntensityTier); } catch (MelderError) { Melder_throw (me, ": not converted to IntensityTier."); } } IntensityTier Intensity_to_IntensityTier_peaks (Intensity me) { try { return (IntensityTier) Vector_to_RealTier_peaks (me, 1, classIntensityTier); } catch (MelderError) { Melder_throw (me, ": peaks not converted to IntensityTier."); } } IntensityTier Intensity_to_IntensityTier_valleys (Intensity me) { try { return (IntensityTier) Vector_to_RealTier_valleys (me, 1, classIntensityTier); } catch (MelderError) { Melder_throw (me, ": valleys not converted to IntensityTier."); } } IntensityTier Intensity_PointProcess_to_IntensityTier (Intensity me, PointProcess pp) { try { autoIntensityTier temp = Intensity_downto_IntensityTier (me); autoIntensityTier thee = IntensityTier_PointProcess_to_IntensityTier (temp.peek(), pp); return thee.transfer(); } catch (MelderError) { Melder_throw (me, " & ", pp, ": not converted to IntensityTier."); } } IntensityTier IntensityTier_PointProcess_to_IntensityTier (IntensityTier me, PointProcess pp) { try { if (my points -> size == 0) Melder_throw ("No intensity points."); autoIntensityTier thee = IntensityTier_create (pp -> xmin, pp -> xmax); for (long i = 1; i <= pp -> nt; i ++) { double time = pp -> t [i]; double value = RealTier_getValueAtTime (me, time); RealTier_addPoint (thee.peek(), time, value); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, " & ", pp, ": not converted to IntensityTier."); } } TableOfReal IntensityTier_downto_TableOfReal (IntensityTier me) { return RealTier_downto_TableOfReal (me, L"Time (s)", L"Intensity (dB)"); } void Sound_IntensityTier_multiply_inline (Sound me, IntensityTier intensity) { if (intensity -> points -> size == 0) return; for (long isamp = 1; isamp <= my nx; isamp ++) { double t = my x1 + (isamp - 1) * my dx; double factor = pow (10, RealTier_getValueAtTime (intensity, t) / 20); for (long channel = 1; channel <= my ny; channel ++) { my z [channel] [isamp] *= factor; } } } Sound Sound_IntensityTier_multiply (Sound me, IntensityTier intensity, int scale) { try { autoSound thee = Data_copy (me); Sound_IntensityTier_multiply_inline (thee.peek(), intensity); if (scale) Vector_scale (thee.peek(), 0.9); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not multiplied with ", intensity, "."); } } /* End of file IntensityTier.cpp */ sources_5316/fon/ManipulationEditor.cpp0000644000176700017670000015755511632112263017037 0ustar paulpaul/* ManipulationEditor.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManipulationEditor.h" #include "Preferences.h" #include "PitchTier_to_PointProcess.h" #include "Sound_to_PointProcess.h" #include "Sound_to_Pitch.h" #include "Pitch_to_PitchTier.h" #include "Pitch_to_PointProcess.h" #include "EditorM.h" #include "enums_getText.h" #include "ManipulationEditor_enums.h" #include "enums_getValue.h" #include "ManipulationEditor_enums.h" Thing_implement (ManipulationEditor, FunctionEditor, 0); /* * How to add a synthesis method (in an interruptable order): * 1. add an Manipulation_ #define in Manipulation.h; * 2. add a synthesize_ routine in Manipulation.c, and a reference to it in Manipulation_to_Sound; * 3. add a button in ManipulationEditor.h; * 4. add a cb_Synth_ callback. * 5. create the button in createMenus and update updateMenus; */ static const wchar *units_strings [] = { 0, L"Hz", L"st" }; static struct { struct { double minimum, maximum; enum kManipulationEditor_pitchUnits units; enum kManipulationEditor_draggingStrategy draggingStrategy; struct { double frequencyResolution; bool useSemitones; } stylize; struct { long numberOfPointsPerParabola; } interpolateQuadratically; } pitchTier; struct { double minimum, maximum; } duration; } preferences; static int prefs_synthesisMethod = Manipulation_OVERLAPADD; /* Remembered across editor creations, not across Praat sessions. */ /* BUG: 25 should be fmin */ #define YLIN(freq) (my pitchTier.units == kManipulationEditor_pitchUnits_HERTZ ? ((freq) < 25 ? 25 : (freq)) : NUMhertzToSemitones ((freq) < 25 ? 25 : (freq))) #define YLININV(freq) (my pitchTier.units == kManipulationEditor_pitchUnits_HERTZ ? (freq) : NUMsemitonesToHertz (freq)) void ManipulationEditor_prefs (void) { Preferences_addDouble (L"ManipulationEditor.pitch.minimum", & preferences.pitchTier.minimum, 50.0); Preferences_addDouble (L"ManipulationEditor.pitch.maximum", & preferences.pitchTier.maximum, 300.0); Preferences_addEnum (L"ManipulationEditor.pitch.units", & preferences.pitchTier.units, kManipulationEditor_pitchUnits, DEFAULT); Preferences_addEnum (L"ManipulationEditor.pitch.draggingStrategy", & preferences.pitchTier.draggingStrategy, kManipulationEditor_draggingStrategy, DEFAULT); Preferences_addDouble (L"ManipulationEditor.pitch.stylize.frequencyResolution", & preferences.pitchTier.stylize.frequencyResolution, 2.0); Preferences_addBool (L"ManipulationEditor.pitch.stylize.useSemitones", & preferences.pitchTier.stylize.useSemitones, true); Preferences_addLong (L"ManipulationEditor.pitch.interpolateQuadratically.numberOfPointsPerParabola", & preferences.pitchTier.interpolateQuadratically.numberOfPointsPerParabola, 4); Preferences_addDouble (L"ManipulationEditor.duration.minimum", & preferences.duration.minimum, 0.25); Preferences_addDouble (L"ManipulationEditor.duration.maximum", & preferences.duration.maximum, 3.0); /*Preferences_addInt (L"ManipulationEditor.synthesis.method.1", & prefs_synthesisMethod, Manipulation_OVERLAPADD);*/ } static void updateMenus (ManipulationEditor me) { Melder_assert (my synthPulsesButton != NULL); GuiMenuItem_check (my synthPulsesButton, my synthesisMethod == Manipulation_PULSES); Melder_assert (my synthPulsesHumButton != NULL); GuiMenuItem_check (my synthPulsesHumButton, my synthesisMethod == Manipulation_PULSES_HUM); Melder_assert (my synthPulsesLpcButton != NULL); GuiMenuItem_check (my synthPulsesLpcButton, my synthesisMethod == Manipulation_PULSES_LPC); Melder_assert (my synthPitchButton != NULL); GuiMenuItem_check (my synthPitchButton, my synthesisMethod == Manipulation_PITCH); Melder_assert (my synthPitchHumButton != NULL); GuiMenuItem_check (my synthPitchHumButton, my synthesisMethod == Manipulation_PITCH_HUM); Melder_assert (my synthPulsesPitchButton != NULL); GuiMenuItem_check (my synthPulsesPitchButton, my synthesisMethod == Manipulation_PULSES_PITCH); Melder_assert (my synthPulsesPitchHumButton != NULL); GuiMenuItem_check (my synthPulsesPitchHumButton, my synthesisMethod == Manipulation_PULSES_PITCH_HUM); Melder_assert (my synthOverlapAddButton != NULL); GuiMenuItem_check (my synthOverlapAddButton, my synthesisMethod == Manipulation_OVERLAPADD); Melder_assert (my synthPitchLpcButton != NULL); GuiMenuItem_check (my synthPitchLpcButton, my synthesisMethod == Manipulation_PITCH_LPC); } /* * The "sound area" contains the original sound and the pulses. */ static int getSoundArea (ManipulationEditor me, double *ymin, double *ymax) { Manipulation ana = (Manipulation) my data; *ymin = 0.66; *ymax = 1.00; return ana -> sound != NULL || ana -> pulses != NULL; } /* * The "pitch area" contains the grey pitch analysis based on the pulses, and the blue pitch tier. */ static int getPitchArea (ManipulationEditor me, double *ymin, double *ymax) { Manipulation ana = (Manipulation) my data; *ymin = ana -> duration ? 0.16 : 0.00; *ymax = 0.65; return ana -> pulses != NULL || ana -> pitch != NULL; } static int getDurationArea (ManipulationEditor me, double *ymin, double *ymax) { Manipulation ana = (Manipulation) my data; if (! ana -> duration) return FALSE; *ymin = 0.00; *ymax = 0.15; return TRUE; } /********** DESTRUCTION **********/ void structManipulationEditor :: v_destroy () { forget (previousPulses); forget (previousPitch); forget (previousDuration); ManipulationEditor_Parent :: v_destroy (); } /********** MENU COMMANDS **********/ /***** FILE MENU *****/ static void menu_cb_extractOriginalSound (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> sound) return; autoSound publish = Data_copy (ana -> sound); my broadcastPublication (publish.transfer()); } static void menu_cb_extractPulses (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> pulses) return; autoPointProcess publish = Data_copy (ana -> pulses); my broadcastPublication (publish.transfer()); } static void menu_cb_extractPitchTier (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> pitch) return; autoPitchTier publish = Data_copy (ana -> pitch); my broadcastPublication (publish.transfer()); } static void menu_cb_extractDurationTier (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> duration) return; autoDurationTier publish = Data_copy (ana -> duration); my broadcastPublication (publish.transfer()); } static void menu_cb_extractManipulatedSound (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; autoSound publish = Manipulation_to_Sound (ana, my synthesisMethod); my broadcastPublication (publish.transfer()); } /***** EDIT MENU *****/ void structManipulationEditor :: v_saveData () { Manipulation ana = (Manipulation) data; forget (previousPulses); forget (previousPitch); forget (previousDuration); if (ana -> pulses) previousPulses = Data_copy (ana -> pulses); if (ana -> pitch) previousPitch = Data_copy (ana -> pitch); if (ana -> duration) previousDuration = Data_copy (ana -> duration); } void structManipulationEditor :: v_restoreData () { Manipulation ana = (Manipulation) data; Any dummy; dummy = ana -> pulses; ana -> pulses = previousPulses; previousPulses = (PointProcess) dummy; dummy = ana -> pitch; ana -> pitch = previousPitch; previousPitch = (PitchTier) dummy; dummy = ana -> duration; ana -> duration = previousDuration; previousDuration = (DurationTier) dummy; } /***** PULSES MENU *****/ static void menu_cb_removePulses (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> pulses) return; Editor_save (me, L"Remove pulse(s)"); if (my startSelection == my endSelection) PointProcess_removePointNear (ana -> pulses, my startSelection); else PointProcess_removePointsBetween (ana -> pulses, my startSelection, my endSelection); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_addPulseAtCursor (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> pulses) return; Editor_save (me, L"Add pulse"); PointProcess_addPoint (ana -> pulses, 0.5 * (my startSelection + my endSelection)); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_addPulseAt (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Add pulse", 0) REAL (L"Position (s)", L"0.0") EDITOR_OK SET_REAL (L"Position", 0.5 * (my startSelection + my endSelection)) EDITOR_DO Manipulation ana = (Manipulation) my data; if (! ana -> pulses) return; Editor_save (me, L"Add pulse"); PointProcess_addPoint (ana -> pulses, GET_REAL (L"Position")); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } /***** PITCH MENU *****/ static void menu_cb_removePitchPoints (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> pitch) return; Editor_save (me, L"Remove pitch point(s)"); if (my startSelection == my endSelection) AnyTier_removePointNear (ana -> pitch, my startSelection); else AnyTier_removePointsBetween (ana -> pitch, my startSelection, my endSelection); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_addPitchPointAtCursor (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> pitch) return; Editor_save (me, L"Add pitch point"); RealTier_addPoint (ana -> pitch, 0.5 * (my startSelection + my endSelection), YLININV (my pitchTier.cursor)); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_addPitchPointAtSlice (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; PointProcess pulses = ana -> pulses; if (! pulses) Melder_throw ("There are no pulses."); if (! ana -> pitch) return; long ileft = PointProcess_getLowIndex (pulses, 0.5 * (my startSelection + my endSelection)), iright = ileft + 1, nt = pulses -> nt; double *t = pulses -> t; double f = my pitchTier.cursor; // default Editor_save (me, L"Add pitch point"); if (nt <= 1) { /* Ignore. */ } else if (ileft <= 0) { double tright = t [2] - t [1]; if (tright > 0.0 && tright <= 0.02) f = YLIN (1.0 / tright); } else if (iright > nt) { double tleft = t [nt] - t [nt - 1]; if (tleft > 0.0 && tleft <= 0.02) f = YLIN (1.0 / tleft); } else { /* Three-period median. */ double tmid = t [iright] - t [ileft], tleft = 0.0, tright = 0.0; if (ileft > 1) tleft = t [ileft] - t [ileft - 1]; if (iright < nt) tright = t [iright + 1] - t [iright]; if (tleft > 0.02) tleft = 0; if (tmid > 0.02) tmid = 0; if (tright > 0.02) tright = 0; /* Bubble-sort. */ if (tmid < tleft) { double dum = tmid; tmid = tleft; tleft = dum; } if (tright < tleft) { double dum = tright; tright = tleft; tleft = dum; } if (tright < tmid) { double dum = tright; tright = tmid; tmid = dum; } if (tleft != 0.0) f = YLIN (1 / tmid); /* Median of 3. */ else if (tmid != 0.0) f = YLIN (2 / (tmid + tright)); /* Median of 2. */ else if (tright != 0.0) f = YLIN (1 / tright); /* Median of 1. */ } RealTier_addPoint (ana -> pitch, 0.5 * (my startSelection + my endSelection), YLININV (f)); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_addPitchPointAt (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Add pitch point", 0) REAL (L"Time (s)", L"0.0") REAL (L"Frequency (Hz or st)", L"100.0") EDITOR_OK SET_REAL (L"Time", 0.5 * (my startSelection + my endSelection)) SET_REAL (L"Frequency", my pitchTier.cursor) EDITOR_DO Manipulation ana = (Manipulation) my data; if (! ana -> pitch) return; Editor_save (me, L"Add pitch point"); RealTier_addPoint (ana -> pitch, GET_REAL (L"Time"), YLININV (GET_REAL (L"Frequency"))); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_stylizePitch (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Stylize pitch", L"PitchTier: Stylize...") REAL (L"Frequency resolution", L"2.0") RADIO (L"Units", 2) RADIOBUTTON (L"Hertz") RADIOBUTTON (L"semitones") EDITOR_OK SET_REAL (L"Frequency resolution", preferences.pitchTier.stylize.frequencyResolution) /* Once. */ SET_INTEGER (L"Units", preferences.pitchTier.stylize.useSemitones + 1) /* Once. */ EDITOR_DO Manipulation ana = (Manipulation) my data; if (! ana -> pitch) return; Editor_save (me, L"Stylize pitch"); PitchTier_stylize (ana -> pitch, preferences.pitchTier.stylize.frequencyResolution = GET_REAL (L"Frequency resolution"), preferences.pitchTier.stylize.useSemitones = GET_INTEGER (L"Units") - 1); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_stylizePitch_2st (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> pitch) return; Editor_save (me, L"Stylize pitch"); PitchTier_stylize (ana -> pitch, 2.0, TRUE); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_interpolateQuadratically (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Interpolate quadratically", 0) NATURAL (L"Number of points per parabola", L"4") EDITOR_OK SET_INTEGER (L"Number of points per parabola", preferences.pitchTier.interpolateQuadratically.numberOfPointsPerParabola) /* Once. */ EDITOR_DO Manipulation ana = (Manipulation) my data; if (! ana -> pitch) return; Editor_save (me, L"Interpolate quadratically"); RealTier_interpolateQuadratically (ana -> pitch, preferences.pitchTier.interpolateQuadratically.numberOfPointsPerParabola = GET_INTEGER (L"Number of points per parabola"), my pitchTier.units == kManipulationEditor_pitchUnits_SEMITONES); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_interpolateQuadratically_4pts (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> pitch) return; Editor_save (me, L"Interpolate quadratically"); RealTier_interpolateQuadratically (ana -> pitch, 4, my pitchTier.units == kManipulationEditor_pitchUnits_SEMITONES); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_shiftPitchFrequencies (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Shift pitch frequencies", 0) REAL (L"Frequency shift", L"-20.0") OPTIONMENU (L"Unit", 1) OPTION (L"Hertz") OPTION (L"mel") OPTION (L"logHertz") OPTION (L"semitones") OPTION (L"ERB") EDITOR_OK EDITOR_DO Manipulation ana = (Manipulation) my data; int unit = GET_INTEGER (L"Unit"); unit = unit == 1 ? kPitch_unit_HERTZ : unit == 2 ? kPitch_unit_MEL : unit == 3 ? kPitch_unit_LOG_HERTZ : unit == 4 ? kPitch_unit_SEMITONES_1 : kPitch_unit_ERB; if (! ana -> pitch) return; Editor_save (me, L"Shift pitch frequencies"); try { PitchTier_shiftFrequencies (ana -> pitch, my startSelection, my endSelection, GET_REAL (L"Frequency shift"), unit); FunctionEditor_redraw (me); my broadcastDataChanged (); } catch (MelderError) { // the PitchTier may have partially changed FunctionEditor_redraw (me); my broadcastDataChanged (); throw; } EDITOR_END } static void menu_cb_multiplyPitchFrequencies (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Multiply pitch frequencies", 0) POSITIVE (L"Factor", L"1.2") LABEL (L"", L"The multiplication is always done in hertz.") EDITOR_OK EDITOR_DO Manipulation ana = (Manipulation) my data; if (! ana -> pitch) return; Editor_save (me, L"Multiply pitch frequencies"); PitchTier_multiplyFrequencies (ana -> pitch, my startSelection, my endSelection, GET_REAL (L"Factor")); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_setPitchRange (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Set pitch range", 0) /* BUG: should include Minimum */ REAL (L"Maximum (Hz or st)", L"300.0") EDITOR_OK SET_REAL (L"Maximum", my pitchTier.maximum) EDITOR_DO double maximum = GET_REAL (L"Maximum"); if (maximum <= my pitchTier.minPeriodic) Melder_throw ("Maximum pitch must be greater than ", Melder_half (my pitchTier.minPeriodic), " ", units_strings [my pitchTier.units], "."); preferences.pitchTier.maximum = my pitchTier.maximum = maximum; FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_setPitchUnits (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Set pitch units", 0) RADIO_ENUM (L"Pitch units", kManipulationEditor_pitchUnits, DEFAULT) EDITOR_OK SET_ENUM (L"Pitch units", kManipulationEditor_pitchUnits, my pitchTier.units) EDITOR_DO enum kManipulationEditor_pitchUnits newPitchUnits = GET_ENUM (kManipulationEditor_pitchUnits, L"Pitch units"); if (my pitchTier.units == newPitchUnits) return; preferences.pitchTier.units = my pitchTier.units = newPitchUnits; if (my pitchTier.units == kManipulationEditor_pitchUnits_HERTZ) { my pitchTier.minimum = 25.0; my pitchTier.minPeriodic = 50.0; preferences.pitchTier.maximum = my pitchTier.maximum = NUMsemitonesToHertz (my pitchTier.maximum); my pitchTier.cursor = NUMsemitonesToHertz (my pitchTier.cursor); } else { my pitchTier.minimum = -24.0; my pitchTier.minPeriodic = -12.0; preferences.pitchTier.maximum = my pitchTier.maximum = NUMhertzToSemitones (my pitchTier.maximum); my pitchTier.cursor = NUMhertzToSemitones (my pitchTier.cursor); } FunctionEditor_redraw (me); EDITOR_END } /***** DURATION MENU *****/ static void menu_cb_setDurationRange (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Set duration range", 0) REAL (L"Minimum", L"0.25") REAL (L"Maximum", L"3.0") EDITOR_OK SET_REAL (L"Minimum", my duration.minimum) SET_REAL (L"Maximum", my duration.maximum) EDITOR_DO Manipulation ana = (Manipulation) my data; double minimum = GET_REAL (L"Minimum"), maximum = GET_REAL (L"Maximum"); double minimumValue = ana -> duration ? RealTier_getMinimumValue (ana -> duration) : NUMundefined; double maximumValue = ana -> duration ? RealTier_getMaximumValue (ana -> duration) : NUMundefined; if (minimum > 1) Melder_throw ("Minimum relative duration must not be greater than 1."); if (maximum < 1) Melder_throw ("Maximum relative duration must not be less than 1."); if (minimum >= maximum) Melder_throw ("Maximum relative duration must be greater than minimum."); if (NUMdefined (minimumValue) && minimum > minimumValue) Melder_throw ("Minimum relative duration must not be greater than the minimum value present, " "which is ", Melder_half (minimumValue), "."); if (NUMdefined (maximumValue) && maximum < maximumValue) Melder_throw ("Maximum relative duration must not be less than the maximum value present, " "which is ", Melder_half (maximumValue), "."); preferences.duration.minimum = my duration.minimum = minimum; preferences.duration.maximum = my duration.maximum = maximum; FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_setDraggingStrategy (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Set dragging strategy", L"ManipulationEditor") RADIO_ENUM (L"Dragging strategy", kManipulationEditor_draggingStrategy, DEFAULT) EDITOR_OK SET_INTEGER (L"Dragging strategy", my pitchTier.draggingStrategy) EDITOR_DO preferences.pitchTier.draggingStrategy = my pitchTier.draggingStrategy = GET_ENUM (kManipulationEditor_draggingStrategy, L"Dragging strategy"); EDITOR_END } static void menu_cb_removeDurationPoints (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> duration) return; Editor_save (me, L"Remove duration point(s)"); if (my startSelection == my endSelection) AnyTier_removePointNear (ana -> duration, 0.5 * (my startSelection + my endSelection)); else AnyTier_removePointsBetween (ana -> duration, my startSelection, my endSelection); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_addDurationPointAtCursor (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; if (! ana -> duration) return; Editor_save (me, L"Add duration point"); RealTier_addPoint (ana -> duration, 0.5 * (my startSelection + my endSelection), my duration.cursor); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_addDurationPointAt (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); EDITOR_FORM (L"Add duration point", 0) REAL (L"Time (s)", L"0.0"); REAL (L"Relative duration", L"1.0"); EDITOR_OK SET_REAL (L"Time", 0.5 * (my startSelection + my endSelection)) EDITOR_DO Manipulation ana = (Manipulation) my data; if (! ana -> duration) return; Editor_save (me, L"Add duration point"); RealTier_addPoint (ana -> duration, GET_REAL (L"Time"), GET_REAL (L"Relative duration")); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_newDuration (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; Editor_save (me, L"New duration"); forget (ana -> duration); ana -> duration = DurationTier_create (ana -> xmin, ana -> xmax); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_forgetDuration (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Manipulation ana = (Manipulation) my data; forget (ana -> duration); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_ManipulationEditorHelp (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Melder_help (L"ManipulationEditor"); } static void menu_cb_ManipulationHelp (EDITOR_ARGS) { EDITOR_IAM (ManipulationEditor); Melder_help (L"Manipulation"); } #define menu_cb_Synth_common(menu_cb,meth) \ static void menu_cb (EDITOR_ARGS) { \ EDITOR_IAM (ManipulationEditor); \ prefs_synthesisMethod = my synthesisMethod = meth; \ updateMenus (me); \ } menu_cb_Synth_common (menu_cb_Synth_Pulses, Manipulation_PULSES) menu_cb_Synth_common (menu_cb_Synth_Pulses_hum, Manipulation_PULSES_HUM) menu_cb_Synth_common (menu_cb_Synth_Pulses_Lpc, Manipulation_PULSES_LPC) menu_cb_Synth_common (menu_cb_Synth_Pitch, Manipulation_PITCH) menu_cb_Synth_common (menu_cb_Synth_Pitch_hum, Manipulation_PITCH_HUM) menu_cb_Synth_common (menu_cb_Synth_Pulses_Pitch, Manipulation_PULSES_PITCH) menu_cb_Synth_common (menu_cb_Synth_Pulses_Pitch_hum, Manipulation_PULSES_PITCH_HUM) menu_cb_Synth_common (menu_cb_Synth_OverlapAdd_nodur, Manipulation_OVERLAPADD_NODUR) menu_cb_Synth_common (menu_cb_Synth_OverlapAdd, Manipulation_OVERLAPADD) menu_cb_Synth_common (menu_cb_Synth_Pitch_Lpc, Manipulation_PITCH_LPC) void structManipulationEditor :: v_createMenus () { ManipulationEditor_Parent :: v_createMenus (); Editor_addCommand (this, L"File", L"Extract original sound", 0, menu_cb_extractOriginalSound); Editor_addCommand (this, L"File", L"Extract pulses", 0, menu_cb_extractPulses); Editor_addCommand (this, L"File", L"Extract pitch tier", 0, menu_cb_extractPitchTier); Editor_addCommand (this, L"File", L"Extract duration tier", 0, menu_cb_extractDurationTier); Editor_addCommand (this, L"File", L"Publish resynthesis", 0, menu_cb_extractManipulatedSound); Editor_addCommand (this, L"File", L"-- close --", 0, NULL); Editor_addMenu (this, L"Pulse", 0); Editor_addCommand (this, L"Pulse", L"Add pulse at cursor", 'P', menu_cb_addPulseAtCursor); Editor_addCommand (this, L"Pulse", L"Add pulse at...", 0, menu_cb_addPulseAt); Editor_addCommand (this, L"Pulse", L"-- remove pulses --", 0, NULL); Editor_addCommand (this, L"Pulse", L"Remove pulse(s)", GuiMenu_OPTION + 'P', menu_cb_removePulses); Editor_addMenu (this, L"Pitch", 0); Editor_addCommand (this, L"Pitch", L"Add pitch point at cursor", 'T', menu_cb_addPitchPointAtCursor); Editor_addCommand (this, L"Pitch", L"Add pitch point at time slice", 0, menu_cb_addPitchPointAtSlice); Editor_addCommand (this, L"Pitch", L"Add pitch point at...", 0, menu_cb_addPitchPointAt); Editor_addCommand (this, L"Pitch", L"-- remove pitch --", 0, NULL); Editor_addCommand (this, L"Pitch", L"Remove pitch point(s)", GuiMenu_OPTION + 'T', menu_cb_removePitchPoints); Editor_addCommand (this, L"Pitch", L"-- pitch prefs --", 0, NULL); Editor_addCommand (this, L"Pitch", L"Set pitch range...", 0, menu_cb_setPitchRange); Editor_addCommand (this, L"Pitch", L"Set pitch units...", 0, menu_cb_setPitchUnits); Editor_addCommand (this, L"Pitch", L"Set pitch dragging strategy...", 0, menu_cb_setDraggingStrategy); Editor_addCommand (this, L"Pitch", L"-- modify pitch --", 0, NULL); Editor_addCommand (this, L"Pitch", L"Shift pitch frequencies...", 0, menu_cb_shiftPitchFrequencies); Editor_addCommand (this, L"Pitch", L"Multiply pitch frequencies...", 0, menu_cb_multiplyPitchFrequencies); Editor_addCommand (this, L"Pitch", L"All:", GuiMenu_INSENSITIVE, menu_cb_stylizePitch); Editor_addCommand (this, L"Pitch", L"Stylize pitch...", 0, menu_cb_stylizePitch); Editor_addCommand (this, L"Pitch", L"Stylize pitch (2 st)", '2', menu_cb_stylizePitch_2st); Editor_addCommand (this, L"Pitch", L"Interpolate quadratically...", 0, menu_cb_interpolateQuadratically); Editor_addCommand (this, L"Pitch", L"Interpolate quadratically (4 pts)", '4', menu_cb_interpolateQuadratically_4pts); Editor_addMenu (this, L"Dur", 0); Editor_addCommand (this, L"Dur", L"Add duration point at cursor", 'D', menu_cb_addDurationPointAtCursor); Editor_addCommand (this, L"Dur", L"Add duration point at...", 0, menu_cb_addDurationPointAt); Editor_addCommand (this, L"Dur", L"-- remove duration --", 0, NULL); Editor_addCommand (this, L"Dur", L"Remove duration point(s)", GuiMenu_OPTION + 'D', menu_cb_removeDurationPoints); Editor_addCommand (this, L"Dur", L"-- duration prefs --", 0, NULL); Editor_addCommand (this, L"Dur", L"Set duration range...", 0, menu_cb_setDurationRange); Editor_addCommand (this, L"Dur", L"-- refresh duration --", 0, NULL); Editor_addCommand (this, L"Dur", L"New duration", 0, menu_cb_newDuration); Editor_addCommand (this, L"Dur", L"Forget duration", 0, menu_cb_forgetDuration); Editor_addMenu (this, L"Synth", 0); synthPulsesButton = Editor_addCommand (this, L"Synth", L"Pulses --", GuiMenu_RADIO_FIRST, menu_cb_Synth_Pulses); synthPulsesHumButton = Editor_addCommand (this, L"Synth", L"Pulses (hum) --", GuiMenu_RADIO_NEXT, menu_cb_Synth_Pulses_hum); synthPulsesLpcButton = Editor_addCommand (this, L"Synth", L"Pulses & LPC -- (\"LPC resynthesis\")", GuiMenu_RADIO_NEXT, menu_cb_Synth_Pulses_Lpc); Editor_addCommand (this, L"Synth", L"-- pitch resynth --", 0, NULL); synthPitchButton = Editor_addCommand (this, L"Synth", L" -- Pitch", GuiMenu_RADIO_NEXT, menu_cb_Synth_Pitch); synthPitchHumButton = Editor_addCommand (this, L"Synth", L" -- Pitch (hum)", GuiMenu_RADIO_NEXT, menu_cb_Synth_Pitch_hum); synthPulsesPitchButton = Editor_addCommand (this, L"Synth", L"Pulses -- Pitch", GuiMenu_RADIO_NEXT, menu_cb_Synth_Pulses_Pitch); synthPulsesPitchHumButton = Editor_addCommand (this, L"Synth", L"Pulses -- Pitch (hum)", GuiMenu_RADIO_NEXT, menu_cb_Synth_Pulses_Pitch_hum); Editor_addCommand (this, L"Synth", L"-- full resynth --", 0, NULL); synthOverlapAddButton = Editor_addCommand (this, L"Synth", L"Sound & Pulses -- Pitch & Duration (\"Overlap-add manipulation\")", GuiMenu_RADIO_NEXT | GuiMenu_TOGGLE_ON, menu_cb_Synth_OverlapAdd); synthPitchLpcButton = Editor_addCommand (this, L"Synth", L"LPC -- Pitch (\"LPC pitch manipulation\")", GuiMenu_RADIO_NEXT, menu_cb_Synth_Pitch_Lpc); } void structManipulationEditor :: v_createHelpMenuItems (EditorMenu menu) { ManipulationEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"ManipulationEditor help", '?', menu_cb_ManipulationEditorHelp); EditorMenu_addCommand (menu, L"Manipulation help", 0, menu_cb_ManipulationHelp); } /********** DRAWING AREA **********/ static void drawSoundArea (ManipulationEditor me, double ymin, double ymax) { Manipulation ana = (Manipulation) my data; Sound sound = ana -> sound; PointProcess pulses = ana -> pulses; long first, last, i; Graphics_Viewport viewport = Graphics_insetViewport (my graphics, 0, 1, ymin, ymax); Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_WHITE); Graphics_fillRectangle (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_BLACK); Graphics_rectangle (my graphics, 0, 1, 0, 1); Graphics_setTextAlignment (my graphics, Graphics_RIGHT, Graphics_TOP); Graphics_setFont (my graphics, kGraphics_font_TIMES); Graphics_text (my graphics, 1, 1, L"%%Sound"); Graphics_setColour (my graphics, Graphics_BLUE); Graphics_text (my graphics, 1, 1 - Graphics_dyMMtoWC (my graphics, 3), L"%%Pulses"); Graphics_setFont (my graphics, kGraphics_font_HELVETICA); /* * Draw blue pulses. */ if (pulses) { Graphics_setWindow (my graphics, my startWindow, my endWindow, 0.0, 1.0); Graphics_setColour (my graphics, Graphics_BLUE); for (i = 1; i <= pulses -> nt; i ++) { double t = pulses -> t [i]; if (t >= my startWindow && t <= my endWindow) Graphics_line (my graphics, t, 0.05, t, 0.95); } } /* * Draw sound. */ if (sound && Sampled_getWindowSamples (sound, my startWindow, my endWindow, & first, & last) > 1) { double minimum, maximum, scaleMin, scaleMax; Matrix_getWindowExtrema (sound, first, last, 1, 1, & minimum, & maximum); if (minimum == maximum) minimum = -0.5, maximum = +0.5; /* * Scaling. */ scaleMin = 0.83 * minimum + 0.17 * my soundmin; scaleMax = 0.83 * maximum + 0.17 * my soundmax; Graphics_setWindow (my graphics, my startWindow, my endWindow, scaleMin, scaleMax); FunctionEditor_drawRangeMark (me, scaleMin, Melder_float (Melder_half (scaleMin)), L"", Graphics_BOTTOM); FunctionEditor_drawRangeMark (me, scaleMax, Melder_float (Melder_half (scaleMax)), L"", Graphics_TOP); /* * Draw dotted zero line. */ if (minimum < 0.0 && maximum > 0.0) { Graphics_setColour (my graphics, Graphics_CYAN); Graphics_setLineType (my graphics, Graphics_DOTTED); Graphics_line (my graphics, my startWindow, 0.0, my endWindow, 0.0); Graphics_setLineType (my graphics, Graphics_DRAWN); } /* * Draw samples. */ Graphics_setColour (my graphics, Graphics_BLACK); Graphics_function (my graphics, sound -> z [1], first, last, Sampled_indexToX (sound, first), Sampled_indexToX (sound, last)); } Graphics_resetViewport (my graphics, viewport); } static void drawPitchArea (ManipulationEditor me, double ymin, double ymax) { Manipulation ana = (Manipulation) my data; PointProcess pulses = ana -> pulses; PitchTier pitch = ana -> pitch; long ifirstSelected, ilastSelected, n = pitch ? pitch -> points -> size : 0, imin, imax, i; int cursorVisible = my startSelection == my endSelection && my startSelection >= my startWindow && my startSelection <= my endWindow; double minimumFrequency = YLIN (50); int rangePrecisions [] = { 0, 1, 2 }; const wchar *rangeUnits [] = { L"", L" Hz", L" st" }; /* * Pitch contours. */ Graphics_Viewport viewport = Graphics_insetViewport (my graphics, 0, 1, ymin, ymax); Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_WHITE); Graphics_fillRectangle (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_BLACK); Graphics_rectangle (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_GREEN); Graphics_setFont (my graphics, kGraphics_font_TIMES); Graphics_setTextAlignment (my graphics, Graphics_RIGHT, Graphics_TOP); Graphics_text (my graphics, 1, 1, L"%%Pitch manip"); Graphics_setGrey (my graphics, 0.7); Graphics_text (my graphics, 1, 1 - Graphics_dyMMtoWC (my graphics, 3), L"%%Pitch from pulses"); Graphics_setFont (my graphics, kGraphics_font_HELVETICA); Graphics_setWindow (my graphics, my startWindow, my endWindow, my pitchTier.minimum, my pitchTier.maximum); /* * Draw pitch contour based on pulses. */ Graphics_setGrey (my graphics, 0.7); if (pulses) for (i = 1; i < pulses -> nt; i ++) { double tleft = pulses -> t [i], tright = pulses -> t [i + 1], t = 0.5 * (tleft + tright); if (t >= my startWindow && t <= my endWindow) { if (tleft != tright) { double f = YLIN (1 / (tright - tleft)); if (f >= my pitchTier.minPeriodic && f <= my pitchTier.maximum) { Graphics_fillCircle_mm (my graphics, t, f, 1); } } } } Graphics_setGrey (my graphics, 0.0); FunctionEditor_drawGridLine (me, minimumFrequency); FunctionEditor_drawRangeMark (me, my pitchTier.maximum, Melder_fixed (my pitchTier.maximum, rangePrecisions [my pitchTier.units]), rangeUnits [my pitchTier.units], Graphics_TOP); FunctionEditor_drawRangeMark (me, my pitchTier.minimum, Melder_fixed (my pitchTier.minimum, rangePrecisions [my pitchTier.units]), rangeUnits [my pitchTier.units], Graphics_BOTTOM); if (my startSelection == my endSelection && my pitchTier.cursor >= my pitchTier.minimum && my pitchTier.cursor <= my pitchTier.maximum) FunctionEditor_drawHorizontalHair (me, my pitchTier.cursor, Melder_fixed (my pitchTier.cursor, rangePrecisions [my pitchTier.units]), rangeUnits [my pitchTier.units]); if (cursorVisible && n > 0) { double y = YLIN (RealTier_getValueAtTime (pitch, my startSelection)); FunctionEditor_insertCursorFunctionValue (me, y, Melder_fixed (y, rangePrecisions [my pitchTier.units]), rangeUnits [my pitchTier.units], my pitchTier.minimum, my pitchTier.maximum); } if (pitch) { ifirstSelected = AnyTier_timeToHighIndex (pitch, my startSelection); ilastSelected = AnyTier_timeToLowIndex (pitch, my endSelection); imin = AnyTier_timeToHighIndex (pitch, my startWindow); imax = AnyTier_timeToLowIndex (pitch, my endWindow); } Graphics_setLineWidth (my graphics, 2); if (n == 0) { Graphics_setTextAlignment (my graphics, Graphics_CENTRE, Graphics_HALF); Graphics_setColour (my graphics, Graphics_BLACK); Graphics_text (my graphics, 0.5 * (my startWindow + my endWindow), 0.5 * (my pitchTier.minimum + my pitchTier.maximum), L"(no pitch points)"); } else if (imax < imin) { double fleft = YLIN (RealTier_getValueAtTime (pitch, my startWindow)); double fright = YLIN (RealTier_getValueAtTime (pitch, my endWindow)); Graphics_setColour (my graphics, Graphics_GREEN); Graphics_line (my graphics, my startWindow, fleft, my endWindow, fright); } else { for (i = imin; i <= imax; i ++) { RealPoint point = (RealPoint) pitch -> points -> item [i]; double t = point -> number, f = YLIN (point -> value); Graphics_setColour (my graphics, Graphics_GREEN); if (i == 1) Graphics_line (my graphics, my startWindow, f, t, f); else if (i == imin) Graphics_line (my graphics, t, f, my startWindow, YLIN (RealTier_getValueAtTime (pitch, my startWindow))); if (i == n) Graphics_line (my graphics, t, f, my endWindow, f); else if (i == imax) Graphics_line (my graphics, t, f, my endWindow, YLIN (RealTier_getValueAtTime (pitch, my endWindow))); else { RealPoint pointRight = (RealPoint) pitch -> points -> item [i + 1]; Graphics_line (my graphics, t, f, pointRight -> number, YLIN (pointRight -> value)); } } for (i = imin; i <= imax; i ++) { RealPoint point = (RealPoint) pitch -> points -> item [i]; double t = point -> number, f = YLIN (point -> value); if (i >= ifirstSelected && i <= ilastSelected) Graphics_setColour (my graphics, Graphics_RED); else Graphics_setColour (my graphics, Graphics_GREEN); Graphics_fillCircle_mm (my graphics, t, f, 3); } } Graphics_setLineWidth (my graphics, 1); Graphics_setColour (my graphics, Graphics_BLACK); Graphics_resetViewport (my graphics, viewport); } static void drawDurationArea (ManipulationEditor me, double ymin, double ymax) { Manipulation ana = (Manipulation) my data; DurationTier duration = ana -> duration; long ifirstSelected, ilastSelected, n = duration ? duration -> points -> size : 0, imin, imax, i; int cursorVisible = my startSelection == my endSelection && my startSelection >= my startWindow && my startSelection <= my endWindow; /* * Duration contours. */ Graphics_Viewport viewport = Graphics_insetViewport (my graphics, 0, 1, ymin, ymax); Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_WHITE); Graphics_fillRectangle (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_BLACK); Graphics_rectangle (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_GREEN); Graphics_setFont (my graphics, kGraphics_font_TIMES); Graphics_setTextAlignment (my graphics, Graphics_RIGHT, Graphics_TOP); Graphics_text (my graphics, 1, 1, L"%%Duration manip"); Graphics_setFont (my graphics, kGraphics_font_HELVETICA); Graphics_setWindow (my graphics, my startWindow, my endWindow, my duration.minimum, my duration.maximum); FunctionEditor_drawGridLine (me, 1.0); FunctionEditor_drawRangeMark (me, my duration.maximum, Melder_fixed (my duration.maximum, 3), L"", Graphics_TOP); FunctionEditor_drawRangeMark (me, my duration.minimum, Melder_fixed (my duration.minimum, 3), L"", Graphics_BOTTOM); if (my startSelection == my endSelection && my duration.cursor >= my duration.minimum && my duration.cursor <= my duration.maximum) FunctionEditor_drawHorizontalHair (me, my duration.cursor, Melder_fixed (my duration.cursor, 3), L""); if (cursorVisible && n > 0) { double y = RealTier_getValueAtTime (duration, my startSelection); FunctionEditor_insertCursorFunctionValue (me, y, Melder_fixed (y, 3), L"", my duration.minimum, my duration.maximum); } /* * Draw duration tier. */ if (duration) { ifirstSelected = AnyTier_timeToHighIndex (duration, my startSelection); ilastSelected = AnyTier_timeToLowIndex (duration, my endSelection); imin = AnyTier_timeToHighIndex (duration, my startWindow); imax = AnyTier_timeToLowIndex (duration, my endWindow); } Graphics_setLineWidth (my graphics, 2); if (n == 0) { Graphics_setColour (my graphics, Graphics_BLACK); Graphics_setTextAlignment (my graphics, Graphics_CENTRE, Graphics_HALF); Graphics_text (my graphics, 0.5 * (my startWindow + my endWindow), 0.5 * (my duration.minimum + my duration.maximum), L"(no duration points)"); } else if (imax < imin) { double fleft = RealTier_getValueAtTime (duration, my startWindow); double fright = RealTier_getValueAtTime (duration, my endWindow); Graphics_setColour (my graphics, Graphics_GREEN); Graphics_line (my graphics, my startWindow, fleft, my endWindow, fright); } else { for (i = imin; i <= imax; i ++) { RealPoint point = (RealPoint) duration -> points -> item [i]; double t = point -> number, dur = point -> value; Graphics_setColour (my graphics, Graphics_GREEN); if (i == 1) Graphics_line (my graphics, my startWindow, dur, t, dur); else if (i == imin) Graphics_line (my graphics, t, dur, my startWindow, RealTier_getValueAtTime (duration, my startWindow)); if (i == n) Graphics_line (my graphics, t, dur, my endWindow, dur); else if (i == imax) Graphics_line (my graphics, t, dur, my endWindow, RealTier_getValueAtTime (duration, my endWindow)); else { RealPoint pointRight = (RealPoint) duration -> points -> item [i + 1]; Graphics_line (my graphics, t, dur, pointRight -> number, pointRight -> value); } } for (i = imin; i <= imax; i ++) { RealPoint point = (RealPoint) duration -> points -> item [i]; double t = point -> number, dur = point -> value; if (i >= ifirstSelected && i <= ilastSelected) Graphics_setColour (my graphics, Graphics_RED); else Graphics_setColour (my graphics, Graphics_GREEN); Graphics_fillCircle_mm (my graphics, t, dur, 3); } } Graphics_setLineWidth (my graphics, 1); Graphics_setColour (my graphics, Graphics_BLACK); Graphics_resetViewport (my graphics, viewport); } void structManipulationEditor :: v_draw () { double ysoundmin, ysoundmax; double ypitchmin, ypitchmax, ydurationmin, ydurationmax; int hasSoundArea = getSoundArea (this, & ysoundmin, & ysoundmax); int hasPitchArea = getPitchArea (this, & ypitchmin, & ypitchmax); int hasDurationArea = getDurationArea (this, & ydurationmin, & ydurationmax); if (hasSoundArea) drawSoundArea (this, ysoundmin, ysoundmax); if (hasPitchArea) drawPitchArea (this, ypitchmin, ypitchmax); if (hasDurationArea) drawDurationArea (this, ydurationmin, ydurationmax); Graphics_setWindow (graphics, 0.0, 1.0, 0.0, 1.0); Graphics_setGrey (graphics, 0.85); Graphics_fillRectangle (graphics, -0.001, 1.001, ypitchmax, ysoundmin); Graphics_setGrey (graphics, 0.00); Graphics_line (graphics, 0, ysoundmin, 1, ysoundmin); Graphics_line (graphics, 0, ypitchmax, 1, ypitchmax); if (hasDurationArea) { Graphics_setGrey (graphics, 0.85); Graphics_fillRectangle (graphics, -0.001, 1.001, ydurationmax, ypitchmin); Graphics_setGrey (graphics, 0.00); Graphics_line (graphics, 0, ypitchmin, 1, ypitchmin); Graphics_line (graphics, 0, ydurationmax, 1, ydurationmax); } updateMenus (this); } static void drawWhileDragging (ManipulationEditor me, double xWC, double yWC, long first, long last, double dt, double df) { Manipulation ana = (Manipulation) my data; PitchTier pitch = ana -> pitch; long i; (void) xWC; (void) yWC; /* * Draw all selected pitch points as magenta empty circles, if inside the window. */ for (i = first; i <= last; i ++) { RealPoint point = (RealPoint) pitch -> points -> item [i]; double t = point -> number + dt, f = YLIN (point -> value) + df; if (t >= my startWindow && t <= my endWindow) Graphics_circle_mm (my graphics, t, f < my pitchTier.minPeriodic ? my pitchTier.minPeriodic : f > my pitchTier.maximum ? my pitchTier.maximum : f, 3); } if (last == first) { /* * Draw a crosshair with time and frequency. */ RealPoint point = (RealPoint) pitch -> points -> item [first]; double t = point -> number + dt, fWC = YLIN (point -> value) + df; Graphics_line (my graphics, t, my pitchTier.minimum, t, my pitchTier.maximum - Graphics_dyMMtoWC (my graphics, 4.0)); Graphics_setTextAlignment (my graphics, Graphics_CENTRE, Graphics_TOP); Graphics_text1 (my graphics, t, my pitchTier.maximum, Melder_fixed (t, 6)); Graphics_line (my graphics, my startWindow, fWC, my endWindow, fWC); Graphics_setTextAlignment (my graphics, Graphics_LEFT, Graphics_BOTTOM); Graphics_text1 (my graphics, my startWindow, fWC, Melder_fixed (fWC, 5)); } } static int clickPitch (ManipulationEditor me, double xWC, double yWC, bool shiftKeyPressed) { Manipulation ana = (Manipulation) my data; PitchTier pitch = ana -> pitch; long inearestPoint, ifirstSelected, ilastSelected, i; RealPoint nearestPoint; double dt = 0, df = 0; int draggingSelection, dragHorizontal, dragVertical; my pitchTier.cursor = my pitchTier.minimum + yWC * (my pitchTier.maximum - my pitchTier.minimum); if (! pitch) { Graphics_resetViewport (my graphics, my inset); return my ManipulationEditor_Parent :: v_click (xWC, yWC, shiftKeyPressed); } Graphics_setWindow (my graphics, my startWindow, my endWindow, my pitchTier.minimum, my pitchTier.maximum); yWC = my pitchTier.cursor; /* * Clicked on a pitch point? */ inearestPoint = AnyTier_timeToNearestIndex (pitch, xWC); if (inearestPoint == 0) { Graphics_resetViewport (my graphics, my inset); return my ManipulationEditor_Parent :: v_click (xWC, yWC, shiftKeyPressed); } nearestPoint = (RealPoint) pitch -> points -> item [inearestPoint]; if (Graphics_distanceWCtoMM (my graphics, xWC, yWC, nearestPoint -> number, YLIN (nearestPoint -> value)) > 1.5) { Graphics_resetViewport (my graphics, my inset); return my ManipulationEditor_Parent :: v_click (xWC, yWC, shiftKeyPressed); } /* * Clicked on a selected pitch point? */ draggingSelection = shiftKeyPressed && nearestPoint -> number > my startSelection && nearestPoint -> number < my endSelection; if (draggingSelection) { ifirstSelected = AnyTier_timeToHighIndex (pitch, my startSelection); ilastSelected = AnyTier_timeToLowIndex (pitch, my endSelection); Editor_save (me, L"Drag pitch points"); } else { ifirstSelected = ilastSelected = inearestPoint; Editor_save (me, L"Drag pitch point"); } /* * Drag. */ /* * Draw at the old location once. * Since some systems do double buffering, * the undrawing at the old position and redrawing at the new have to be bracketed by Graphics_mouseStillDown (). */ Graphics_xorOn (my graphics, Graphics_MAROON); drawWhileDragging (me, xWC, yWC, ifirstSelected, ilastSelected, dt, df); dragHorizontal = my pitchTier.draggingStrategy != kManipulationEditor_draggingStrategy_VERTICAL && (! shiftKeyPressed || my pitchTier.draggingStrategy != kManipulationEditor_draggingStrategy_HYBRID); dragVertical = my pitchTier.draggingStrategy != kManipulationEditor_draggingStrategy_HORIZONTAL; while (Graphics_mouseStillDown (my graphics)) { double xWC_new, yWC_new; Graphics_getMouseLocation (my graphics, & xWC_new, & yWC_new); if (xWC_new != xWC || yWC_new != yWC) { drawWhileDragging (me, xWC, yWC, ifirstSelected, ilastSelected, dt, df); if (dragHorizontal) dt += xWC_new - xWC; if (dragVertical) df += yWC_new - yWC; xWC = xWC_new, yWC = yWC_new; drawWhileDragging (me, xWC, yWC, ifirstSelected, ilastSelected, dt, df); } } Graphics_xorOff (my graphics); /* * Dragged inside window? */ if (xWC < my startWindow || xWC > my endWindow) return 1; /* * Points not dragged past neighbours? */ { RealPoint *points = (RealPoint *) pitch -> points -> item; double newTime = points [ifirstSelected] -> number + dt; if (newTime < my tmin) return 1; // outside domain if (ifirstSelected > 1 && newTime <= points [ifirstSelected - 1] -> number) return 1; /* Past left neighbour. */ newTime = points [ilastSelected] -> number + dt; if (newTime > my tmax) return 1; // outside domain if (ilastSelected < pitch -> points -> size && newTime >= points [ilastSelected + 1] -> number) return 1; // past right neighbour } /* * Drop. */ for (i = ifirstSelected; i <= ilastSelected; i ++) { RealPoint point = (RealPoint) pitch -> points -> item [i]; point -> number += dt; point -> value = YLININV (YLIN (point -> value) + df); if (point -> value < 50.0) point -> value = 50.0; if (point -> value > YLININV (my pitchTier.maximum)) point -> value = YLININV (my pitchTier.maximum); } /* * Make sure that the same pitch points are still selected (a problem with Undo...). */ if (draggingSelection) my startSelection += dt, my endSelection += dt; if (my startSelection == my endSelection) { RealPoint point = (RealPoint) pitch -> points -> item [ifirstSelected]; my startSelection = my endSelection = point -> number; my pitchTier.cursor = YLIN (point -> value); } my broadcastDataChanged (); return 1; /* Update needed. */ } static void drawDurationWhileDragging (ManipulationEditor me, double xWC, double yWC, long first, long last, double dt, double df) { Manipulation ana = (Manipulation) my data; DurationTier duration = ana -> duration; long i; (void) xWC; (void) yWC; /* * Draw all selected duration points as magenta empty circles, if inside the window. */ for (i = first; i <= last; i ++) { RealPoint point = (RealPoint) duration -> points -> item [i]; double t = point -> number + dt, dur = point -> value + df; if (t >= my startWindow && t <= my endWindow) Graphics_circle_mm (my graphics, t, dur < my duration.minimum ? my duration.minimum : dur > my duration.maximum ? my duration.maximum : dur, 3); } if (last == first) { /* * Draw a crosshair with time and duration. */ RealPoint point = (RealPoint) duration -> points -> item [first]; double t = point -> number + dt, durWC = point -> value + df; Graphics_line (my graphics, t, my duration.minimum, t, my duration.maximum - Graphics_dyMMtoWC (my graphics, 4.0)); Graphics_setTextAlignment (my graphics, Graphics_CENTRE, Graphics_TOP); Graphics_text1 (my graphics, t, my duration.maximum, Melder_fixed (t, 6)); Graphics_line (my graphics, my startWindow, durWC, my endWindow, durWC); Graphics_setTextAlignment (my graphics, Graphics_LEFT, Graphics_BOTTOM); Graphics_text1 (my graphics, my startWindow, durWC, Melder_fixed (durWC, 2)); } } static int clickDuration (ManipulationEditor me, double xWC, double yWC, int shiftKeyPressed) { Manipulation ana = (Manipulation) my data; DurationTier duration = ana -> duration; long inearestPoint, ifirstSelected, ilastSelected, i; RealPoint nearestPoint; double dt = 0, df = 0; int draggingSelection; /* * Convert from FunctionEditor's [0, 1] coordinates to world coordinates. */ yWC = my duration.minimum + yWC * (my duration.maximum - my duration.minimum); /* * Move horizontal hair to clicked position. */ my duration.cursor = yWC; if (! duration) { Graphics_resetViewport (my graphics, my inset); return my ManipulationEditor_Parent :: v_click (xWC, yWC, shiftKeyPressed); } Graphics_setWindow (my graphics, my startWindow, my endWindow, my duration.minimum, my duration.maximum); /* * Clicked on a duration point? */ inearestPoint = AnyTier_timeToNearestIndex (duration, xWC); if (inearestPoint == 0) { Graphics_resetViewport (my graphics, my inset); return my ManipulationEditor_Parent :: v_click (xWC, yWC, shiftKeyPressed); } nearestPoint = (RealPoint) duration -> points -> item [inearestPoint]; if (Graphics_distanceWCtoMM (my graphics, xWC, yWC, nearestPoint -> number, nearestPoint -> value) > 1.5) { Graphics_resetViewport (my graphics, my inset); return my ManipulationEditor_Parent :: v_click (xWC, yWC, shiftKeyPressed); } /* * Clicked on a selected duration point? */ draggingSelection = shiftKeyPressed && nearestPoint -> number > my startSelection && nearestPoint -> number < my endSelection; if (draggingSelection) { ifirstSelected = AnyTier_timeToHighIndex (duration, my startSelection); ilastSelected = AnyTier_timeToLowIndex (duration, my endSelection); Editor_save (me, L"Drag duration points"); } else { ifirstSelected = ilastSelected = inearestPoint; Editor_save (me, L"Drag duration point"); } /* * Drag. */ Graphics_xorOn (my graphics, Graphics_MAROON); drawDurationWhileDragging (me, xWC, yWC, ifirstSelected, ilastSelected, dt, df); while (Graphics_mouseStillDown (my graphics)) { double xWC_new, yWC_new; Graphics_getMouseLocation (my graphics, & xWC_new, & yWC_new); if (xWC_new != xWC || yWC_new != yWC) { drawDurationWhileDragging (me, xWC, yWC, ifirstSelected, ilastSelected, dt, df); dt += xWC_new - xWC, xWC = xWC_new; df += yWC_new - yWC, yWC = yWC_new; drawDurationWhileDragging (me, xWC_new, yWC_new, ifirstSelected, ilastSelected, dt, df); } } Graphics_xorOff (my graphics); /* * Dragged inside window? */ if (xWC < my startWindow || xWC > my endWindow) return 1; /* * Points not dragged past neighbours? */ { RealPoint *points = (RealPoint *) duration -> points -> item; double newTime = points [ifirstSelected] -> number + dt; if (newTime < my tmin) return 1; // outside domain if (ifirstSelected > 1 && newTime <= points [ifirstSelected - 1] -> number) return 1; /* Past left neighbour. */ newTime = points [ilastSelected] -> number + dt; if (newTime > my tmax) return 1; // outside domain if (ilastSelected < duration -> points -> size && newTime >= points [ilastSelected + 1] -> number) return 1; // past right neighbour } /* * Drop. */ for (i = ifirstSelected; i <= ilastSelected; i ++) { RealPoint point = (RealPoint) duration -> points -> item [i]; point -> number += dt; point -> value += df; if (point -> value < my duration.minimum) point -> value = my duration.minimum; if (point -> value > my duration.maximum) point -> value = my duration.maximum; } /* * Make sure that the same duration points are still selected (a problem with Undo...). */ if (draggingSelection) my startSelection += dt, my endSelection += dt; if (my startSelection == my endSelection) { RealPoint point = (RealPoint) duration -> points -> item [ifirstSelected]; my startSelection = my endSelection = point -> number; my duration.cursor = point -> value; } my broadcastDataChanged (); return 1; /* Update needed. */ } int structManipulationEditor :: v_click (double xWC, double yWC, bool shiftKeyPressed) { double ypitchmin, ypitchmax, ydurationmin, ydurationmax; int hasPitchArea = getPitchArea (this, & ypitchmin, & ypitchmax); int hasDurationArea = getDurationArea (this, & ydurationmin, & ydurationmax); /* * Dispatch click to clicked area. */ if (hasPitchArea && yWC > ypitchmin && yWC < ypitchmax) { // clicked in pitch area? inset = Graphics_insetViewport (graphics, 0, 1, ypitchmin, ypitchmax); return clickPitch (this, xWC, (yWC - ypitchmin) / (ypitchmax - ypitchmin), shiftKeyPressed); } else if (hasDurationArea && yWC > ydurationmin && yWC < ydurationmax) { // clicked in duration area? inset = Graphics_insetViewport (graphics, 0, 1, ydurationmin, ydurationmax); return clickDuration (this, xWC, (yWC - ydurationmin) / (ydurationmax - ydurationmin), shiftKeyPressed); } /* * Perform the default action: move cursor or drag selection. */ return ManipulationEditor_Parent :: v_click (xWC, yWC, shiftKeyPressed); } void structManipulationEditor :: v_play (double a_tmin, double a_tmax) { Manipulation ana = (Manipulation) data; if (shiftKeyPressed) { if (ana -> sound) Sound_playPart (ana -> sound, a_tmin, a_tmax, theFunctionEditor_playCallback, this); } else { Manipulation_playPart (ana, a_tmin, a_tmax, synthesisMethod); } } ManipulationEditor ManipulationEditor_create (GuiObject parent, const wchar *title, Manipulation ana) { try { autoManipulationEditor me = Thing_new (ManipulationEditor); FunctionEditor_init (me.peek(), parent, title, ana); my pitchTier.draggingStrategy = preferences.pitchTier.draggingStrategy; my pitchTier.units = preferences.pitchTier.units; double maximumPitchValue = RealTier_getMaximumValue (ana -> pitch); if (my pitchTier.units == kManipulationEditor_pitchUnits_HERTZ) { my pitchTier.minimum = 25.0; my pitchTier.minPeriodic = 50.0; my pitchTier.maximum = maximumPitchValue; my pitchTier.cursor = my pitchTier.maximum * 0.8; my pitchTier.maximum *= 1.2; } else { my pitchTier.minimum = -24.0; my pitchTier.minPeriodic = -12.0; my pitchTier.maximum = NUMdefined (maximumPitchValue) ? NUMhertzToSemitones (maximumPitchValue) : NUMundefined; my pitchTier.cursor = my pitchTier.maximum - 4.0; my pitchTier.maximum += 3.0; } if (my pitchTier.maximum == NUMundefined || my pitchTier.maximum < preferences.pitchTier.maximum) my pitchTier.maximum = preferences.pitchTier.maximum; double minimumDurationValue = ana -> duration ? RealTier_getMinimumValue (ana -> duration) : NUMundefined; my duration.minimum = NUMdefined (minimumDurationValue) ? minimumDurationValue : 1.0; if (preferences.duration.minimum > 1) preferences.duration.minimum = 0.25; if (my duration.minimum > preferences.duration.minimum) my duration.minimum = preferences.duration.minimum; double maximumDurationValue = ana -> duration ? RealTier_getMaximumValue (ana -> duration) : NUMundefined; my duration.maximum = NUMdefined (maximumDurationValue) ? maximumDurationValue : 1.0; if (preferences.duration.maximum < 1) preferences.duration.maximum = 3.0; if (preferences.duration.maximum <= preferences.duration.minimum) preferences.duration.minimum = 0.25, preferences.duration.maximum = 3.0; if (my duration.maximum < preferences.duration.maximum) my duration.maximum = preferences.duration.maximum; my duration.cursor = 1.0; my synthesisMethod = prefs_synthesisMethod; if (ana -> sound) Matrix_getWindowExtrema (ana -> sound, 0, 0, 0, 0, & my soundmin, & my soundmax); if (my soundmin == my soundmax) my soundmin = -1.0, my soundmax = +1.0; updateMenus (me.peek()); return me.transfer(); } catch (MelderError) { Melder_throw ("Manipulation window not created."); } } /* End of file ManipulationEditor.cpp */ sources_5316/fon/Ltas.cpp0000644000176700017670000004414311634625350014127 0ustar paulpaul/* Ltas.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * a selection of changes: * pb 2005/11/26 pitch-corrected Ltas */ #include "Ltas.h" #include "Sound_and_Spectrum.h" #include "Sound_to_PointProcess.h" Thing_implement (Ltas, Vector, 2); void structLtas :: v_info () { double meanPowerDensity; structData :: v_info (); MelderInfo_writeLine1 (L"Frequency domain:"); MelderInfo_writeLine3 (L" Lowest frequency: ", Melder_double (xmin), L" Hz"); MelderInfo_writeLine3 (L" Highest frequency: ", Melder_double (xmax), L" Hz"); MelderInfo_writeLine3 (L" Total frequency domain: ", Melder_double (xmax - xmin), L" Hz"); MelderInfo_writeLine1 (L"Frequency sampling:"); MelderInfo_writeLine2 (L" Number of frequency bands: ", Melder_integer (nx)); MelderInfo_writeLine3 (L" Width of each band: ", Melder_double (dx), L" Hz"); MelderInfo_writeLine3 (L" First band centred at: ", Melder_double (x1), L" Hz"); meanPowerDensity = Sampled_getMean (this, xmin, xmax, 0, 1, FALSE); MelderInfo_writeLine3 (L"Total SPL: ", Melder_single (10.0 * log10 (meanPowerDensity * (xmax - xmin))), L" dB"); } double structLtas :: v_convertStandardToSpecialUnit (double value, long ilevel, int unit) { (void) ilevel; if (unit == 1) { return pow (10.0, 0.1 * value); // energy } else if (unit == 2) { return pow (2.0, 0.1 * value); // sones } return value; } double structLtas :: v_convertSpecialToStandardUnit (double value, long ilevel, int unit) { (void) ilevel; return unit == 1 ? 10.0 * log10 (value) : // value = energy unit == 2 ? 10.0 * NUMlog2 (value) : // value = sones value; // value = dB } Ltas Ltas_create (long nx, double dx) { try { autoLtas me = Thing_new (Ltas); Matrix_init (me.peek(), 0.0, nx * dx, nx, dx, 0.5 * dx, 1.0, 1.0, 1, 1.0, 1.0); therror return me.transfer(); } catch (MelderError) { Melder_throw ("Ltas not created."); } } void Ltas_draw (Ltas me, Graphics g, double fmin, double fmax, double minimum, double maximum, int garnish, const wchar *method) { Vector_draw (me, g, & fmin, & fmax, & minimum, & maximum, 1.0, method); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Frequency (Hz)"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_textLeft (g, 1, L"Sound pressure level (dB/Hz)"); Graphics_marksLeft (g, 2, 1, 1, 0); } } double Ltas_getSlope (Ltas me, double f1min, double f1max, double f2min, double f2max, int averagingUnits) { double low = Sampled_getMean (me, f1min, f1max, 0, averagingUnits, FALSE); double high = Sampled_getMean (me, f2min, f2max, 0, averagingUnits, FALSE); if (low == NUMundefined || high == NUMundefined) return NUMundefined; return averagingUnits == 3 ? high - low : Function_convertSpecialToStandardUnit (me, high / low, 0, averagingUnits); } double Ltas_getLocalPeakHeight (Ltas me, double environmentMin, double environmentMax, double peakMin, double peakMax, int averagingUnits) { double environmentLow = Sampled_getMean (me, environmentMin, peakMin, 0, averagingUnits, FALSE); double environmentHigh = Sampled_getMean (me, peakMax, environmentMax, 0, averagingUnits, FALSE); double peak = Sampled_getMean (me, peakMin, peakMax, 0, averagingUnits, FALSE); if (environmentLow == NUMundefined || environmentHigh == NUMundefined || peak == NUMundefined) return NUMundefined; return averagingUnits == 3 ? peak - 0.5 * (environmentLow + environmentHigh) : Function_convertSpecialToStandardUnit (me, peak / (0.5 * (environmentLow + environmentHigh)), 0, averagingUnits); } Matrix Ltas_to_Matrix (Ltas me) { try { autoMatrix thee = Thing_new (Matrix); my structMatrix :: v_copy (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Matrix."); } } Ltas Matrix_to_Ltas (Matrix me) { try { autoLtas thee = Thing_new (Ltas); my structMatrix :: v_copy (thee.peek()); // because copying a descendant of Matrix with additional members should not crash return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Ltas."); } } Ltas Ltases_merge (Collection ltases) { try { if (ltases -> size < 1) Melder_throw ("Cannot merge zero Ltas objects."); Ltas me = (Ltas) ltases -> item [1]; autoLtas thee = Data_copy (me); /* * Convert to energy. */ for (long iband = 1; iband <= thy nx; iband ++) { thy z [1] [iband] = pow (10.0, thy z [1] [iband] / 10.0); } for (long ispec = 2; ispec <= ltases -> size; ispec ++) { Ltas him = (Ltas) ltases -> item [ispec]; if (his xmin != thy xmin || his xmax != thy xmax) Melder_throw ("Frequency domains do not match."); if (his dx != thy dx) Melder_throw ("Bandwidths do not match."); if (his nx != thy nx || his x1 != thy x1) Melder_throw ("Frequency bands do not match."); /* * Add band energies. */ for (long iband = 1; iband <= thy nx; iband ++) { thy z [1] [iband] += pow (10.0, his z [1] [iband] / 10.0); } } /* * Convert back to dB. */ for (long iband = 1; iband <= thy nx; iband ++) { thy z [1] [iband] = 10.0 * log10 (thy z [1] [iband]); } return thee.transfer(); } catch (MelderError) { Melder_throw ("Ltas objects not merged."); } } Ltas Ltases_average (Collection ltases) { try { double factor = -10.0 * log10 (ltases -> size); autoLtas thee = Ltases_merge (ltases); for (long iband = 1; iband <= thy nx; iband ++) { thy z [1] [iband] += factor; } return thee.transfer(); } catch (MelderError) { Melder_throw ("Ltas objects not averaged."); } } Ltas Ltas_computeTrendLine (Ltas me, double fmin, double fmax) { try { /* * Find the first and last bin. */ long imin, imax, n; if ((n = Sampled_getWindowSamples (me, fmin, fmax, & imin, & imax)) < 2) Melder_throw ("Number of bins too low (", n, "). Should be at least 2."); autoLtas thee = Data_copy (me); /* * Compute average amplitude and frequency. */ double sum = 0.0, amean, fmean, numerator = 0.0, denominator = 0.0, slope; for (long i = imin; i <= imax; i ++) { sum += thy z [1] [i]; } amean = sum / n; fmean = thy x1 + (0.5 * (imin + imax) - 1) * thy dx; /* * Compute slope. */ for (long i = imin; i <= imax; i ++) { double da = thy z [1] [i] - amean, df = thy x1 + (i - 1) * thy dx - fmean; numerator += da * df; denominator += df * df; } slope = numerator / denominator; /* * Modify bins. */ for (long i = 1; i <= thy nx; i ++) { double df = thy x1 + (i - 1) * thy dx - fmean; thy z [1] [i] = amean + slope * df; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": trend line not computed."); } } Ltas Ltas_subtractTrendLine (Ltas me, double fmin, double fmax) { try { /* * Find the first and last bin. */ long imin, imax, n; if ((n = Sampled_getWindowSamples (me, fmin, fmax, & imin, & imax)) < 2) Melder_throw ("Number of bins too low (", n, "). Should be at least 2."); autoLtas thee = Data_copy (me); /* * Compute average amplitude and frequency. */ double sum = 0.0, amean, fmean, numerator = 0.0, denominator = 0.0, slope; for (long i = imin; i <= imax; i ++) { sum += thy z [1] [i]; } amean = sum / n; fmean = thy x1 + (0.5 * (imin + imax) - 1) * thy dx; /* * Compute slope. */ for (long i = imin; i <= imax; i ++) { double da = thy z [1] [i] - amean, df = thy x1 + (i - 1) * thy dx - fmean; numerator += da * df; denominator += df * df; } slope = numerator / denominator; /* * Modify bins. */ for (long i = 1; i < imin; i ++) { thy z [1] [i] = 0.0; } for (long i = imin; i <= imax; i ++) { double df = thy x1 + (i - 1) * thy dx - fmean; thy z [1] [i] -= amean + slope * df; } for (long i = imax + 1; i <= thy nx; i ++) { thy z [1] [i] = 0.0; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": trend line not subtracted."); } } Ltas Spectrum_to_Ltas (Spectrum me, double bandWidth) { try { long numberOfBands = ceil ((my xmax - my xmin) / bandWidth); if (bandWidth <= my dx) Melder_throw ("Bandwidth must be greater than ", my dx, "."); autoLtas thee = Thing_new (Ltas); Matrix_init (thee.peek(), my xmin, my xmax, numberOfBands, bandWidth, my xmin + 0.5 * bandWidth, 1, 1, 1, 1, 1); therror for (long iband = 1; iband <= numberOfBands; iband ++) { double fmin = thy xmin + (iband - 1) * bandWidth; double meanEnergyDensity = Sampled_getMean (me, fmin, fmin + bandWidth, 0, 1, FALSE); double meanPowerDensity = meanEnergyDensity * my dx; // as an approximation for a division by the original duration thy z [1] [iband] = meanPowerDensity == 0.0 ? -300.0 : 10.0 * log10 (meanPowerDensity / 4.0e-10); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Ltas."); } } Ltas Spectrum_to_Ltas_1to1 (Spectrum me) { try { autoLtas thee = Thing_new (Ltas); Matrix_init (thee.peek(), my xmin, my xmax, my nx, my dx, my x1, 1.0, 1.0, 1, 1.0, 1.0); therror for (long iband = 1; iband <= my nx; iband ++) { thy z [1] [iband] = Sampled_getValueAtSample (me, iband, 0, 2); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Ltas."); } } Ltas Sound_to_Ltas (Sound me, double bandwidth) { try { autoSpectrum thee = Sound_to_Spectrum (me, TRUE); autoLtas him = Spectrum_to_Ltas (thee.peek(), bandwidth); double correction = -10.0 * log10 (thy dx * my nx * my dx); for (long iband = 1; iband <= his nx; iband ++) { his z [1] [iband] += correction; } return him.transfer(); } catch (MelderError) { Melder_throw (me, ": LTAS analysis not performed."); } } Ltas PointProcess_Sound_to_Ltas (PointProcess pulses, Sound sound, double maximumFrequency, double bandWidth, double shortestPeriod, double longestPeriod, double maximumPeriodFactor) { try { long numberOfPeriods = pulses -> nt - 2, totalNumberOfEnergies = 0; autoLtas ltas = Ltas_create (maximumFrequency / bandWidth, bandWidth); ltas -> xmax = maximumFrequency; autoLtas numbers = Data_copy (ltas.peek()); if (numberOfPeriods < 1) Melder_throw ("Cannot compute an Ltas if there are no periods in the point process."); autoMelderProgress progress (L"Ltas analysis..."); for (long ipulse = 2; ipulse < pulses -> nt; ipulse ++) { double leftInterval = pulses -> t [ipulse] - pulses -> t [ipulse - 1]; double rightInterval = pulses -> t [ipulse + 1] - pulses -> t [ipulse]; double intervalFactor = leftInterval > rightInterval ? leftInterval / rightInterval : rightInterval / leftInterval; Melder_progress ((double) ipulse / pulses -> nt, L"Sound & PointProcess: To Ltas: pulse ", Melder_integer (ipulse), L" out of ", Melder_integer (pulses -> nt)); if (leftInterval >= shortestPeriod && leftInterval <= longestPeriod && rightInterval >= shortestPeriod && rightInterval <= longestPeriod && intervalFactor <= maximumPeriodFactor) { /* * We have a period! Compute the spectrum. */ autoSound period = Sound_extractPart (sound, pulses -> t [ipulse] - 0.5 * leftInterval, pulses -> t [ipulse] + 0.5 * rightInterval, kSound_windowShape_RECTANGULAR, 1.0, FALSE); autoSpectrum spectrum = Sound_to_Spectrum (period.peek(), FALSE); for (long ifreq = 1; ifreq <= spectrum -> nx; ifreq ++) { double frequency = spectrum -> xmin + (ifreq - 1) * spectrum -> dx; double realPart = spectrum -> z [1] [ifreq]; double imaginaryPart = spectrum -> z [2] [ifreq]; double energy = (realPart * realPart + imaginaryPart * imaginaryPart) * 2.0 * spectrum -> dx /* OLD: * sound -> nx */; long iband = ceil (frequency / bandWidth); if (iband >= 1 && iband <= ltas -> nx) { ltas -> z [1] [iband] += energy; numbers -> z [1] [iband] += 1; totalNumberOfEnergies += 1; } } } else { numberOfPeriods -= 1; } } if (numberOfPeriods < 1) Melder_throw ("There are no periods in the point process."); for (long iband = 1; iband <= ltas -> nx; iband ++) { if (numbers -> z [1] [iband] == 0.0) { ltas -> z [1] [iband] = NUMundefined; } else { /* * Each bin now contains a total energy in Pa2 sec. * To convert this to power density, we */ double totalEnergyInThisBand = ltas -> z [1] [iband]; if (0 /* i.e. if you just want to have a spectrum of the voiced parts... */) { double energyDensityInThisBand = totalEnergyInThisBand / ltas -> dx; double powerDensityInThisBand = energyDensityInThisBand / (sound -> xmax - sound -> xmin); ltas -> z [1] [iband] = 10.0 * log10 (powerDensityInThisBand / 4.0e-10); } else { /* * And this is what we really want. The total energy has to be redistributed. */ double meanEnergyInThisBand = totalEnergyInThisBand / numbers -> z [1] [iband]; double meanNumberOfEnergiesPerBand = (double) totalNumberOfEnergies / ltas -> nx; double redistributedEnergyInThisBand = meanEnergyInThisBand * meanNumberOfEnergiesPerBand; double redistributedEnergyDensityInThisBand = redistributedEnergyInThisBand / ltas -> dx; double redistributedPowerDensityInThisBand = redistributedEnergyDensityInThisBand / (sound -> xmax - sound -> xmin); ltas -> z [1] [iband] = 10.0 * log10 (redistributedPowerDensityInThisBand / 4.0e-10); /* OLD: ltas -> z [1] [iband] = 10.0 * log10 (ltas -> z [1] [iband] / numbers -> z [1] [iband] * sound -> nx);*/ } } } for (long iband = 1; iband <= ltas -> nx; iband ++) { if (ltas -> z [1] [iband] == NUMundefined) { long ibandleft = iband - 1, ibandright = iband + 1; while (ibandleft >= 1 && ltas -> z [1] [ibandleft] == NUMundefined) ibandleft --; while (ibandright <= ltas -> nx && ltas -> z [1] [ibandright] == NUMundefined) ibandright ++; if (ibandleft < 1 && ibandright > ltas -> nx) Melder_throw ("Cannot create an Ltas without energy in any bins."); if (ibandleft < 1) { ltas -> z [1] [iband] = ltas -> z [1] [ibandright]; } else if (ibandright > ltas -> nx) { ltas -> z [1] [iband] = ltas -> z [1] [ibandleft]; } else { double frequency = ltas -> x1 + (iband - 1) * ltas -> dx; double fleft = ltas -> x1 + (ibandleft - 1) * ltas -> dx; double fright = ltas -> x1 + (ibandright - 1) * ltas -> dx; ltas -> z [1] [iband] = ((fright - frequency) * ltas -> z [1] [ibandleft] + (frequency - fleft) * ltas -> z [1] [ibandright]) / (fright - fleft); } } } return ltas.transfer(); } catch (MelderError) { Melder_throw (sound, " & ", pulses, ": LTAS analysis not performed."); } } Ltas Sound_to_Ltas_pitchCorrected (Sound sound, double minimumPitch, double maximumPitch, double maximumFrequency, double bandWidth, double shortestPeriod, double longestPeriod, double maximumPeriodFactor) { try { autoPointProcess pulses = Sound_to_PointProcess_periodic_cc (sound, minimumPitch, maximumPitch); autoLtas ltas = PointProcess_Sound_to_Ltas (pulses.peek(), sound, maximumFrequency, bandWidth, shortestPeriod, longestPeriod, maximumPeriodFactor); return ltas.transfer(); } catch (MelderError) { Melder_throw (sound, ": pitch-corrected LTAS analysis not performed."); } } Ltas PointProcess_Sound_to_Ltas_harmonics (PointProcess pulses, Sound sound, long maximumHarmonic, double shortestPeriod, double longestPeriod, double maximumPeriodFactor) { try { long numberOfPeriods = pulses -> nt - 2; autoLtas ltas = Ltas_create (maximumHarmonic, 1.0); ltas -> xmax = maximumHarmonic; if (numberOfPeriods < 1) Melder_throw ("There are no periods in the point process."); autoMelderProgress progress (L"LTAS (harmonics) analysis..."); for (long ipulse = 2; ipulse < pulses -> nt; ipulse ++) { double leftInterval = pulses -> t [ipulse] - pulses -> t [ipulse - 1]; double rightInterval = pulses -> t [ipulse + 1] - pulses -> t [ipulse]; double intervalFactor = leftInterval > rightInterval ? leftInterval / rightInterval : rightInterval / leftInterval; Melder_progress ((double) ipulse / pulses -> nt, L"Sound & PointProcess: To Ltas: pulse ", Melder_integer (ipulse), L" out of ", Melder_integer (pulses -> nt)); if (leftInterval >= shortestPeriod && leftInterval <= longestPeriod && rightInterval >= shortestPeriod && rightInterval <= longestPeriod && intervalFactor <= maximumPeriodFactor) { /* * We have a period! Compute the spectrum. */ long localMaximumHarmonic; autoSound period = Sound_extractPart (sound, pulses -> t [ipulse] - 0.5 * leftInterval, pulses -> t [ipulse] + 0.5 * rightInterval, kSound_windowShape_RECTANGULAR, 1.0, FALSE); autoSpectrum spectrum = Sound_to_Spectrum (period.peek(), FALSE); localMaximumHarmonic = maximumHarmonic < spectrum -> nx ? maximumHarmonic : spectrum -> nx; for (long iharm = 1; iharm <= localMaximumHarmonic; iharm ++) { double realPart = spectrum -> z [1] [iharm]; double imaginaryPart = spectrum -> z [2] [iharm]; double energy = (realPart * realPart + imaginaryPart * imaginaryPart) * 2.0 * spectrum -> dx; ltas -> z [1] [iharm] += energy; } } else { numberOfPeriods -= 1; } } if (numberOfPeriods < 1) Melder_throw (L"There are no periods in the point process."); for (long iharm = 1; iharm <= ltas -> nx; iharm ++) { if (ltas -> z [1] [iharm] == 0.0) { ltas -> z [1] [iharm] = -300.0; } else { double energyInThisBand = ltas -> z [1] [iharm]; double powerInThisBand = energyInThisBand / (sound -> xmax - sound -> xmin); ltas -> z [1] [iharm] = 10.0 * log10 (powerInThisBand / 4.0e-10); } } return ltas.transfer(); } catch (MelderError) { Melder_throw (sound, " & ", pulses, ": LTAS analysis (harmonics) not performed."); } } /* End of file Ltas.cpp */ sources_5316/fon/Sound_to_Intensity.h0000644000176700017670000000356111614424561016527 0ustar paulpaul/* Sound_to_Intensity.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sound.h" #include "Intensity.h" #include "IntensityTier.h" Intensity Sound_to_Intensity (Sound me, double minimumPitch, double timeStep, int subtractMean); /* Function: smooth away the periodic part of a signal, by convolving the square of the signal with a Kaiser(20.24) window; and resample on original sample points. Arguments: 'minimumPitch': the minimum periodicity frequency that will be smoothed away to at most 0.00001 %. The Hanning/Hamming-equivalent window length will be 3.2 / 'minimumPitch'. The actual window length will be twice that. 'timeStep': if <= 0.0, then 0.8 / minimumPitch. Performance: every periodicity frequency greater than 'minimumPitch' will be smoothed away to at most 0.00001 %; if 'timeStep' is 0 or less than 3.2 / 'minimumPitch', aliased frequencies will be at least 140 dB down. Example: minimumPitch = 100 Hz; Hanning/Hanning-equivalent window duration = 32 ms; actual window duration = 64 ms; */ IntensityTier Sound_to_IntensityTier (Sound me, double minimumPitch, double timeStep, int subtractMean); /* End of file Sound_to_Intensity.h */ sources_5316/fon/Manipulation.h0000644000176700017670000000645711625721240015332 0ustar paulpaul#ifndef _Manipulation_h_ #define _Manipulation_h_ /* Manipulation.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sound.h" #include "PointProcess.h" #include "PitchTier.h" #include "DurationTier.h" #include "LPC.h" /* The following have to be included for compatibility. */ #include "IntensityTier.h" #include "Intensity.h" #include "FormantTier.h" #include "Formant.h" #include "Pitch.h" #include "Image.h" #include "Manipulation_def.h" oo_CLASS_CREATE (Manipulation, Function); /* How to create an Manipulation. */ Manipulation Manipulation_create (double tmin, double tmax); int Manipulation_replaceOriginalSound (Manipulation me, Sound sound); int Manipulation_replacePulses (Manipulation me, PointProcess pulses); int Manipulation_replaceIntensityTier (Manipulation me, IntensityTier intensity); int Manipulation_replacePitchTier (Manipulation me, PitchTier pitch); int Manipulation_replaceDurationTier (Manipulation me, DurationTier duration); Manipulation Sound_to_Manipulation (Sound me, double timeStep, double minimumPitch, double maximumPitch); Manipulation Sound_Pitch_to_Manipulation (Sound sound, Pitch pitch); Manipulation Sound_PointProcess_to_Manipulation (Sound sound, PointProcess point); Manipulation Manipulation_AnyTier_to_Manipulation (Manipulation manip, AnyTier tier); /* Resynthesis. */ #define Manipulation_OVERLAPADD 1 #define Manipulation_PULSES 2 #define Manipulation_PULSES_HUM 3 #define Manipulation_PITCH 4 #define Manipulation_PITCH_HUM 5 #define Manipulation_PULSES_PITCH 6 #define Manipulation_PULSES_PITCH_HUM 7 #define Manipulation_OVERLAPADD_NODUR 8 #define Manipulation_PULSES_FORMANT 9 #define Manipulation_PULSES_FORMANT_INTENSITY 10 #define Manipulation_PULSES_LPC 11 #define Manipulation_PULSES_LPC_INTENSITY 12 #define Manipulation_PITCH_LPC 13 #define Manipulation_PITCH_LPC_INTENSITY 14 #define Manipulation_PITCH_LPC_INT_DUR 15 Sound Sound_Point_Point_to_Sound (Sound me, PointProcess source, PointProcess target, double maxT); /*void Sound_Formant_Intensity_filter (Sound me, FormantTier formant, IntensityTier intensity);*/ Sound Manipulation_to_Sound (Manipulation me, int method); int Manipulation_playPart (Manipulation me, double tmin, double tmax, int method); int Manipulation_play (Manipulation me, int method); int Manipulation_writeToTextFileWithoutSound (Manipulation me, MelderFile fs); int Manipulation_writeToBinaryFileWithoutSound (Manipulation me, MelderFile fs); /* The low-level synthesis routines. */ Sound Sound_Point_Pitch_Duration_to_Sound (Sound me, PointProcess pulses, PitchTier pitch, DurationTier duration, double maxT); /* End of file Manipulation.h */ #endif sources_5316/fon/SpectrogramEditor.cpp0000644000176700017670000000615411616772423016665 0ustar paulpaul/* SpectrogramEditor.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "SpectrogramEditor.h" Thing_implement (SpectrogramEditor, FunctionEditor, 0); void structSpectrogramEditor :: v_draw () { Spectrogram spectrogram = (Spectrogram) data; Graphics_setWindow (graphics, 0, 1, 0, 1); Graphics_setColour (graphics, Graphics_WHITE); Graphics_fillRectangle (graphics, 0, 1, 0, 1); Graphics_setColour (graphics, Graphics_BLACK); Graphics_rectangle (graphics, 0, 1, 0, 1); long itmin, itmax; Sampled_getWindowSamples (spectrogram, startWindow, endWindow, & itmin, & itmax); /* * Autoscale frequency axis. */ maximum = spectrogram -> ymax; Graphics_setWindow (graphics, startWindow, endWindow, 0.0, maximum); Spectrogram_paintInside (spectrogram, graphics, startWindow, endWindow, 0, 0, 0.0, TRUE, 60, 6.0, 0); /* * Horizontal scaling lines. */ Graphics_setWindow (graphics, 0.0, 1.0, 0.0, maximum); Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); Graphics_setColour (graphics, Graphics_RED); long df = 1000; for (long f = df; f <= maximum; f += df) { Graphics_line (graphics, 0.0, f, 1.0, f); Graphics_text2 (graphics, -0.01, f, Melder_integer (f), L" Hz"); } /* * Vertical cursor lines. */ Graphics_setWindow (graphics, startWindow, endWindow, 0.0, maximum); if (startSelection > startWindow && startSelection < endWindow) Graphics_line (graphics, startSelection, 0, startSelection, maximum); if (endSelection > startWindow && endSelection < endWindow) Graphics_line (graphics, endSelection, 0, endSelection, maximum); Graphics_setColour (graphics, Graphics_BLACK); } int structSpectrogramEditor :: v_click (double xWC, double yWC, bool shiftKeyPressed) { Spectrogram spectrogram = (Spectrogram) data; /*double frequency = yWC * maximum;*/ long bestFrame; bestFrame = Sampled_xToNearestIndex (spectrogram, xWC); if (bestFrame < 1) bestFrame = 1; else if (bestFrame > spectrogram -> nx) bestFrame = spectrogram -> nx; return SpectrogramEditor_Parent :: v_click (xWC, yWC, shiftKeyPressed); } SpectrogramEditor SpectrogramEditor_create (GuiObject parent, const wchar *title, Spectrogram data) { try { autoSpectrogramEditor me = Thing_new (SpectrogramEditor); FunctionEditor_init (me.peek(), parent, title, data); my maximum = 10000.0; return me.transfer(); } catch (MelderError) { Melder_throw ("Spectrogram window not created."); } } /* End of file SpectrogramEditor.cpp */ sources_5316/fon/ParamCurve.cpp0000644000176700017670000001331311633510334015256 0ustar paulpaul/* ParamCurve.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ParamCurve.h" #include "oo_DESTROY.h" #include "ParamCurve_def.h" #include "oo_COPY.h" #include "ParamCurve_def.h" #include "oo_EQUAL.h" #include "ParamCurve_def.h" #include "oo_DESCRIPTION.h" #include "ParamCurve_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "ParamCurve_def.h" Thing_implement (ParamCurve, Function, 2); void structParamCurve :: v_info () { double xmin = 1e300, xmax = -1e300, ymin = 1e300, ymax = -1e300; for (long i = 1; i <= x -> nx; i ++) { double value = x -> z [1] [i]; if (value < xmin) xmin = value; if (value > xmax) xmax = value; } for (long i = 1; i <= y -> nx; i ++) { double value = y -> z [1] [i]; if (value < ymin) ymin = value; if (value > ymax) ymax = value; } structData :: v_info (); MelderInfo_writeLine1 (L"Domain:"); MelderInfo_writeLine2 (L" tmin: ", Melder_double (xmin)); MelderInfo_writeLine2 (L" tmax: ", Melder_double (xmax)); MelderInfo_writeLine1 (L"x sampling:"); MelderInfo_writeLine2 (L" Number of values of t in x: ", Melder_double (x -> nx)); MelderInfo_writeLine5 (L" t step in x: ", Melder_double (x -> dx), L" (sampling rate ", Melder_double (1.0 / x -> dx), L")"); MelderInfo_writeLine2 (L" First t in x: ", Melder_double (x -> x1)); MelderInfo_writeLine1 (L"x values:"); MelderInfo_writeLine2 (L" Minimum x: ", Melder_double (xmin)); MelderInfo_writeLine2 (L" Maximum x: ", Melder_double (xmax)); MelderInfo_writeLine1 (L"y sampling:"); MelderInfo_writeLine2 (L" Number of values of t in y: ", Melder_double (y -> nx)); MelderInfo_writeLine5 (L" t step in y: ", Melder_double (y -> dx), L" (sampling rate ", Melder_double (1.0 / y -> dx), L")"); MelderInfo_writeLine2 (L" First t in y: ", Melder_double (y -> x1)); MelderInfo_writeLine1 (L"y values:"); MelderInfo_writeLine2 (L" Minimum y: ", Melder_double (ymin)); MelderInfo_writeLine2 (L" Maximum y: ", Melder_double (ymax)); } void structParamCurve :: v_writeText (MelderFile file) { Data_writeText (x, file); Data_writeText (y, file); } void structParamCurve :: v_readText (MelderReadText text) { x = Thing_new (Sound); y = Thing_new (Sound); Data_readText (x, text); therror Data_readText (y, text); therror xmin = x -> xmin > y -> xmin ? x -> xmin : y -> xmin; xmax = x -> xmax < y -> xmax ? x -> xmax : y -> xmax; } void structParamCurve :: v_writeBinary (FILE *f) { Data_writeBinary (x, f); therror Data_writeBinary (y, f); therror } void structParamCurve :: v_readBinary (FILE *f) { long saveVersion = Thing_version; Thing_version = 2; x = Thing_new (Sound); y = Thing_new (Sound); Data_readBinary (x, f); therror Data_readBinary (y, f); therror Thing_version = saveVersion; xmin = x -> xmin > y -> xmin ? x -> xmin : y -> xmin; xmax = x -> xmax < y -> xmax ? x -> xmax : y -> xmax; } void ParamCurve_init (I, Any void_x, Any void_y) { iam (ParamCurve); Sound x = (Sound) void_x, y = (Sound) void_y; if (x -> xmax <= y -> xmin || x -> xmin >= y -> xmax) Melder_throw ("Domains do not overlap."); my x = Data_copy (x); my y = Data_copy (y); my xmin = x -> xmin > y -> xmin ? x -> xmin : y -> xmin; my xmax = x -> xmax < y -> xmax ? x -> xmax : y -> xmax; } ParamCurve ParamCurve_create (Any x, Any y) { try { autoParamCurve me = Thing_new (ParamCurve); ParamCurve_init (me.peek(), x, y); therror return me.transfer(); } catch (MelderError) { Melder_throw ("ParamCurve not created."); } } void ParamCurve_draw (I, Graphics g, double t1, double t2, double dt, double x1, double x2, double y1, double y2, int garnish) { iam (ParamCurve); if (t2 <= t1) { double tx1 = my x -> x1; double ty1 = my y -> x1; double tx2 = my x -> x1 + (my x -> nx - 1) * my x -> dx; double ty2 = my y -> x1 + (my y -> nx - 1) * my y -> dx; t1 = tx1 > ty1 ? tx1 : ty1; t2 = tx2 < ty2 ? tx2 : ty2; } if (x2 <= x1) Matrix_getWindowExtrema (my x, 0, 0, 1, 1, & x1, & x2); if (x1 == x2) { x1 -= 1.0; x2 += 1.0; } if (y2 <= y1) Matrix_getWindowExtrema (my y, 0, 0, 1, 1, & y1, & y2); if (y1 == y2) { y1 -= 1.0; y2 += 1.0; } if (dt <= 0.0) dt = my x -> dx < my y -> dx ? my x -> dx : my y -> dx; long numberOfPoints = (long) ceil ((t2 - t1) / dt) + 1; if (numberOfPoints > 0) { autoNUMvector x (1, numberOfPoints); autoNUMvector y (1, numberOfPoints); for (long i = 1; i <= numberOfPoints; i ++) { double t = i == numberOfPoints ? t2 : t1 + (i - 1) * dt; double index = Sampled_xToIndex (my x, t); x [i] = NUM_interpolate_sinc (my x -> z [1], my x -> nx, index, 50); index = Sampled_xToIndex (my y, t); y [i] = NUM_interpolate_sinc (my y -> z [1], my y -> nx, index, 50); } Graphics_setWindow (g, x1, x2, y1, y2); Graphics_setInner (g); Graphics_polyline (g, numberOfPoints, & x [1], & y [1]); Graphics_unsetInner (g); } if (garnish) { Graphics_drawInnerBox (g); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); } } void ParamCurve_swapXY (I) { iam (ParamCurve); Sound help = my x; my x = my y; my y = help; } /* End of file ParamCurve.cpp */ sources_5316/fon/Sound_and_Spectrogram.h0000644000176700017670000000241311614424561017142 0ustar paulpaul#ifndef _Sound_and_Spectrogram_h_ #define _Sound_and_Spectrogram_h_ /* Sound_and_Spectrogram.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sound.h" #include "Spectrogram.h" #include "Sound_and_Spectrogram_enums.h" Spectrogram Sound_to_Spectrogram (Sound me, double effectiveAnalysisWidth, double fmax, double minimumTimeStep1, double minimumFreqStep1, enum kSound_to_Spectrogram_windowShape windowShape, double maximumTimeOversampling, double maximumFreqOversampling); Sound Spectrogram_to_Sound (Spectrogram me, double fsamp); /* End of Sound_and_Spectrogram.h */ #endif sources_5316/fon/Sound_and_Spectrogram.cpp0000644000176700017670000002060511633706332017500 0ustar paulpaul/* Sound_and_Spectrogram.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2003/07/02 checks on NUMrealft * pb 2003/11/30 Sound_to_Spectrogram_windowShapeText * pb 2004/03/13 bins are a fixed number of frequency samples wide; * this improves the positioning of peaks; thanks to Gabriel Beckers for his persistence * pb 2004/10/18 use of FFT tables speeds everything up by a factor of 2.5 * pb 2004/10/20 progress bar * pb 2006/12/30 new Sound_create API * pb 2007/01/01 compatible with stereo sounds * pb 2007/12/06 enums * pb 2008/01/19 double * pb 2010/02/26 fixed a message * pb 2011/06/06 C++ */ #include "Sound_and_Spectrogram.h" #include "NUM2.h" #include "enums_getText.h" #include "Sound_and_Spectrogram_enums.h" #include "enums_getValue.h" #include "Sound_and_Spectrogram_enums.h" Spectrogram Sound_to_Spectrogram (Sound me, double effectiveAnalysisWidth, double fmax, double minimumTimeStep1, double minimumFreqStep1, enum kSound_to_Spectrogram_windowShape windowType, double maximumTimeOversampling, double maximumFreqOversampling) { try { double nyquist = 0.5 / my dx; double physicalAnalysisWidth = windowType == kSound_to_Spectrogram_windowShape_GAUSSIAN ? 2 * effectiveAnalysisWidth : effectiveAnalysisWidth; double effectiveTimeWidth = effectiveAnalysisWidth / sqrt (NUMpi); double effectiveFreqWidth = 1 / effectiveTimeWidth; double minimumTimeStep2 = effectiveTimeWidth / maximumTimeOversampling; double minimumFreqStep2 = effectiveFreqWidth / maximumFreqOversampling; double timeStep = minimumTimeStep1 > minimumTimeStep2 ? minimumTimeStep1 : minimumTimeStep2; double freqStep = minimumFreqStep1 > minimumFreqStep2 ? minimumFreqStep1 : minimumFreqStep2; double duration = my dx * (double) my nx, windowssq = 0.0; /* * Compute the time sampling. */ long nsamp_window = (long) floor (physicalAnalysisWidth / my dx); long halfnsamp_window = nsamp_window / 2 - 1; nsamp_window = halfnsamp_window * 2; if (nsamp_window < 1) Melder_throw ("Your analysis window is too short: less than two samples."); if (physicalAnalysisWidth > duration) Melder_throw ("Your sound is too short:\n" "it should be at least as long as ", windowType == kSound_to_Spectrogram_windowShape_GAUSSIAN ? "two window lengths." : "one window length."); long numberOfTimes = 1 + (long) floor ((duration - physicalAnalysisWidth) / timeStep); // >= 1 double t1 = my x1 + 0.5 * ((double) (my nx - 1) * my dx - (double) (numberOfTimes - 1) * timeStep); /* Centre of first frame. */ /* * Compute the frequency sampling of the FFT spectrum. */ if (fmax <= 0.0 || fmax > nyquist) fmax = nyquist; long numberOfFreqs = (long) floor (fmax / freqStep); if (numberOfFreqs < 1) return NULL; long nsampFFT = 1; while (nsampFFT < nsamp_window || nsampFFT < 2 * numberOfFreqs * (nyquist / fmax)) nsampFFT *= 2; long half_nsampFFT = nsampFFT / 2; /* * Compute the frequency sampling of the spectrogram. */ long binWidth_samples = freqStep * my dx * nsampFFT; if (binWidth_samples < 1) binWidth_samples = 1; double binWidth_hertz = 1.0 / (my dx * nsampFFT); freqStep = binWidth_samples * binWidth_hertz; numberOfFreqs = floor (fmax / freqStep); if (numberOfFreqs < 1) return NULL; autoSpectrogram thee = Spectrogram_create (my xmin, my xmax, numberOfTimes, timeStep, t1, 0.0, fmax, numberOfFreqs, freqStep, 0.5 * (freqStep - binWidth_hertz)); autoNUMvector frame (1, nsampFFT); autoNUMvector spec (1, nsampFFT); autoNUMvector window (1, nsamp_window); autoNUMfft_Table fftTable; NUMfft_Table_init (& fftTable, nsampFFT); therror autoMelderProgress progress (L"Sound to Spectrogram..."); for (long i = 1; i <= nsamp_window; i ++) { double nSamplesPerWindow_f = physicalAnalysisWidth / my dx; double phase = (double) i / nSamplesPerWindow_f; /* 0 .. 1 */ double value; switch (windowType) { case kSound_to_Spectrogram_windowShape_SQUARE: value = 1.0; break; case kSound_to_Spectrogram_windowShape_HAMMING: value = 0.54 - 0.46 * cos (2.0 * NUMpi * phase); break; case kSound_to_Spectrogram_windowShape_BARTLETT: value = 1.0 - fabs ((2.0 * phase - 1.0)); break; case kSound_to_Spectrogram_windowShape_WELCH: value = 1.0 - (2.0 * phase - 1.0) * (2.0 * phase - 1.0); break; case kSound_to_Spectrogram_windowShape_HANNING: value = 0.5 * (1.0 - cos (2.0 * NUMpi * phase)); break; case kSound_to_Spectrogram_windowShape_GAUSSIAN: { double imid = 0.5 * (double) (nsamp_window + 1), edge = exp (-12.0); phase = ((double) i - imid) / nSamplesPerWindow_f; /* -0.5 .. +0.5 */ value = (exp (-48.0 * phase * phase) - edge) / (1.0 - edge); break; } break; default: value = 1.0; } window [i] = (float) value; windowssq += value * value; } double oneByBinWidth = 1.0 / windowssq / binWidth_samples; for (long iframe = 1; iframe <= numberOfTimes; iframe ++) { double t = Sampled_indexToX (thee.peek(), iframe); long leftSample = Sampled_xToLowIndex (me, t), rightSample = leftSample + 1; long startSample = rightSample - halfnsamp_window; long endSample = leftSample + halfnsamp_window; Melder_assert (startSample >= 1); Melder_assert (endSample <= my nx); for (long i = 1; i <= half_nsampFFT; i ++) { spec [i] = 0.0; } for (long channel = 1; channel <= my ny; channel ++) { for (long j = 1, i = startSample; j <= nsamp_window; j ++) { frame [j] = my z [channel] [i ++] * window [j]; } for (long j = nsamp_window + 1; j <= nsampFFT; j ++) frame [j] = 0.0f; Melder_progress (iframe / (numberOfTimes + 1.0), L"Sound to Spectrogram: analysis of frame ", Melder_integer (iframe), L" out of ", Melder_integer (numberOfTimes)); /* Compute Fast Fourier Transform of the frame. */ NUMfft_forward (& fftTable, frame.peek()); // complex spectrum /* Put power spectrum in frame [1..half_nsampFFT + 1]. */ spec [1] += frame [1] * frame [1]; // DC component for (long i = 2; i <= half_nsampFFT; i ++) spec [i] += frame [i + i - 2] * frame [i + i - 2] + frame [i + i - 1] * frame [i + i - 1]; spec [half_nsampFFT + 1] += frame [nsampFFT] * frame [nsampFFT]; /* Nyquist frequency. Correct?? */ } if (my ny > 1 ) for (long i = 1; i <= half_nsampFFT; i ++) { spec [i] /= my ny; } /* Bin into frame [1..nBands]. */ for (long iband = 1; iband <= numberOfFreqs; iband ++) { long leftsample = (iband - 1) * binWidth_samples + 1, rightsample = leftsample + binWidth_samples; float power = 0.0f; for (long i = leftsample; i < rightsample; i ++) power += spec [i]; thy z [iband] [iframe] = power * oneByBinWidth; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": spectrogram analysis not performed."); } } Sound Spectrogram_to_Sound (Spectrogram me, double fsamp) { try { double dt = 1 / fsamp; long n = (my xmax - my xmin) / dt; if (n < 0) return NULL; autoSound thee = Sound_create (1, my xmin, my xmax, n, dt, 0.5 * dt); for (long i = 1; i <= n; i ++) { double t = Sampled_indexToX (thee.peek(), i); double rframe = Sampled_xToIndex (me, t), phase, value = 0.0; long leftFrame, rightFrame; if (rframe < 1 || rframe >= my nx) continue; leftFrame = floor (rframe), rightFrame = leftFrame + 1, phase = rframe - leftFrame; for (long j = 1; j <= my ny; j ++) { double f = Matrix_rowToY (me, j); double power = my z [j] [leftFrame] * (1 - phase) + my z [j] [rightFrame] * phase; value += sqrt (power) * sin (2 * NUMpi * f * t); } thy z [1] [i] = value; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Sound."); } } /* End of file Sound_and_Spectrogram.cpp */ sources_5316/fon/Sound_PointProcess.h0000644000176700017670000000170611614424561016466 0ustar paulpaul/* Sound_PointProcess.h * * Copyright (C) 2010-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sound.h" #include "PointProcess.h" Sound Sound_PointProcess_to_SoundEnsemble_correlate (Sound me, PointProcess thee, double tmin, double tmax); /* End of file Sound_PointProcess.h */ sources_5316/fon/Transition.h0000644000176700017670000000265111625721240015014 0ustar paulpaul#ifndef _Transition_h_ #define _Transition_h_ /* Transition.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Transition inherits from Data */ #include "Matrix.h" #include "Graphics.h" #include "Transition_def.h" oo_CLASS_CREATE (Transition, Data); void Transition_init (I, long numberOfStates); Transition Transition_create (long numberOfStates); void Transition_formula (I, const wchar *formula); void Transition_drawAsNumbers (I, Graphics g, int iformat, int precision); void Transition_eigen (Transition me, Matrix *eigenvectors, Matrix *eigenvalues); Transition Transition_power (Transition me, long power); Matrix Transition_to_Matrix (Transition me); Transition Matrix_to_Transition (Matrix me); /* End of file Transition.h */ #endif sources_5316/fon/PointEditor.h0000644000176700017670000000253411621124714015121 0ustar paulpaul#ifndef _PointEditor_h_ #define _PointEditor_h_ /* PointEditor.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "TimeSoundEditor.h" #include "PointProcess.h" Thing_define (PointEditor, TimeSoundEditor) { // new data: public: Sound monoSound; GuiObject addPointAtDialog; // overridden methods: virtual void v_destroy (); virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_draw (); virtual void v_play (double tmin, double tmax); }; PointEditor PointEditor_create (GuiObject parent, const wchar *title, PointProcess point, Sound sound // may be NULL ); /* End of file PointEditor.h */ #endif sources_5316/fon/RealTier.h0000644000176700017670000000656711625677053014417 0ustar paulpaul#ifndef _RealTier_h_ #define _RealTier_h_ /* RealTier.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "AnyTier.h" #include "Graphics.h" #include "TableOfReal.h" #include "Vector.h" #include "Interpreter_decl.h" /********** class RealPoint **********/ #include "RealTier_def.h" oo_CLASS_CREATE (RealPoint, AnyPoint); RealPoint RealPoint_create (double time, double value); /* Postconditions: result -> time == time; result -> value == value; */ /********** class RealTier **********/ oo_CLASS_CREATE (RealTier, Function); void RealTier_init (RealTier me, double tmin, double tmax); RealTier RealTier_create (double tmin, double tmax); RealTier RealTier_createWithClass (double tmin, double tmax, ClassInfo klas); /* Postconditions: result -> xmin == tmin; result -> xmax == tmax; result -> points -> size == 0; */ double RealTier_getValueAtIndex (RealTier me, long point); /* No points or 'point' out of range: NUMundefined. */ double RealTier_getValueAtTime (RealTier me, double t); /* Inside points: linear intrapolation. */ /* Outside points: constant extrapolation. */ /* No points: NUMundefined. */ double RealTier_getMinimumValue (RealTier me); double RealTier_getMaximumValue (RealTier me); double RealTier_getArea (RealTier me, double tmin, double tmax); double RealTier_getMean_curve (RealTier me, double tmin, double tmax); double RealTier_getMean_points (RealTier me, double tmin, double tmax); double RealTier_getStandardDeviation_curve (RealTier me, double tmin, double tmax); double RealTier_getStandardDeviation_points (RealTier me, double tmin, double tmax); void RealTier_addPoint (RealTier me, double t, double value); void RealTier_draw (RealTier me, Graphics g, double tmin, double tmax, double ymin, double ymax, int garnish, const wchar *method, const wchar *quantity); TableOfReal RealTier_downto_TableOfReal (RealTier me, const wchar *timeLabel, const wchar *valueLabel); void RealTier_interpolateQuadratically (RealTier me, long numberOfPointsPerParabola, int logarithmically); Table RealTier_downto_Table (RealTier me, const wchar *indexText, const wchar *timeText, const wchar *valueText); RealTier Vector_to_RealTier (Vector me, long channel, ClassInfo klas); RealTier Vector_to_RealTier_peaks (Vector me, long channel, ClassInfo klas); RealTier Vector_to_RealTier_valleys (Vector me, long channel, ClassInfo klas); RealTier PointProcess_upto_RealTier (PointProcess me, double value, ClassInfo klas); void RealTier_formula (RealTier me, const wchar *expression, Interpreter interpreter, RealTier thee); void RealTier_multiplyPart (RealTier me, double tmin, double tmax, double factor); void RealTier_removePointsBelow (RealTier me, double level); /* End of file RealTier.h */ #endif sources_5316/fon/manual_annotation.cpp0000644000176700017670000006540111627220402016722 0ustar paulpaul/* manual_annotation.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" void manual_annotation_init (ManPages me); void manual_annotation_init (ManPages me) { MAN_BEGIN (L"Create TextGrid...", L"ppgb", 20101228) INTRO (L"A command to create a @TextGrid from scratch.") ENTRY (L"Settings") TAG (L"##Start time (s)") DEFINITION (L"the start time, usually 0 seconds.") TAG (L"##End time (s)") DEFINITION (L"the end time in seconds, usually the duration.") TAG (L"##Tier names") DEFINITION (L"a list of the names of the tiers that you want to create, separated by spaces.") TAG (L"##Point tiers") DEFINITION (L"a list of the names of the tiers that you want to be %%point tiers%; " "the rest of the tiers will be %%interval tiers%.") MAN_END MAN_BEGIN (L"PointProcess: To TextGrid...", L"ppgb", 19980113) INTRO (L"A command to create an empty @TextGrid from every selected @PointProcess.") NORMAL (L"The only information in the PointProcess that is used, is its starting and finishing times.") ENTRY (L"Settings") TAG (L"##Tier names") DEFINITION (L"a list of the names of the tiers that you want to create, separated by spaces.") TAG (L"##Point tiers") DEFINITION (L"a list of the names of the tiers that you want to be %%point tiers%; " "the rest of the tiers will be %%interval tiers%.") ENTRY (L"Example") NORMAL (L"If ##Tier names# is \"a b c\", and ##Point tiers# is \"b\", " "the resulting TextGrid object will contain an interval tier named \"a\", " "a point tier named \"b\", and another interval tier named \"c\".") MAN_END MAN_BEGIN (L"PointProcess: To TextGrid (vuv)...", L"ppgb", 19980210) INTRO (L"A command to create a @TextGrid with voiced/unvoiced information " "from every selected @PointProcess.") ENTRY (L"Settings") TAG (L"##Maximum period (s)") DEFINITION (L"the maximum interval that will be consider part of a larger voiced interval.") TAG (L"##Mean period (s)") DEFINITION (L"half of this value will be taken to be the amount to which a voiced interval " "will extend beyond its initial and final points. ##Mean period# should be less than " "##Maximum period#, or you may get intervals with negative durations.") ENTRY (L"Example") NORMAL (L"If ##Maximum period# is 0.02 s, and ##Mean period# is 0.01 s, " "and the point process is 0.1 seconds long, with points at 20, 28, 39, 61, and 72 milliseconds, " "the resulting TextGrid object will contain an interval tier " "with \"U\" intervals at [0 ms, 15 ms], [44 ms, 56 ms], and [77 ms, 100 ms], " "and \"V\" intervals at [15 ms, 44 ms] and [56 ms, 77 ms].") MAN_END MAN_BEGIN (L"PointProcess: Up to TextGrid...", L"ppgb", 20101230) INTRO (L"A command to promote every selected @PointProcess to a @TextGrid with a single text tier in it.") ENTRY (L"Setting") TAG (L"##Text") DEFINITION (L"the text that will be placed in every point.") ENTRY (L"Behaviour") NORMAL (L"The times of all the points are trivially copied, and so is the time domain. " "The text information will be the same for every point.") MAN_END MAN_BEGIN (L"Sound: To TextGrid...", L"ppgb", 19980730) INTRO (L"A command to create a @TextGrid without any labels, copying the time domain from the selected @Sound.") ENTRY (L"Settings") TAG (L"%%Tier names") DEFINITION (L"a list of the names of the tiers that you want to create, separated by spaces.") TAG (L"%%Point tiers") DEFINITION (L"a list of the names of the tiers that you want to be %%point tiers%; " "the rest of the tiers will be %%interval tiers%.") ENTRY (L"Example") NORMAL (L"If ##Tier names# is \"a b c\", and ##Point tiers# is \"b\", " "the resulting TextGrid object will contain an interval tier named \"a\", " "a point tier named \"b\", and another interval tier named \"c\".") MAN_END MAN_BEGIN (L"SpellingChecker", L"ppgb", 20110128) INTRO (L"One of the @@types of objects@ in Praat. For checking the spelling in texts and @TextGrid objects.") ENTRY (L"1. How to create a SpellingChecker object") NORMAL (L"You normally read in a SpellingChecker with @@Read from file...@ from the #Open menu.") ENTRY (L"2. How to check the spelling of a @TextGrid") NORMAL (L"A SpellingChecker object can be used fur purposes of spelling checking. In order " "to check the spellings in a @TextGrid object, you first view the TextGrid in an editor window by selecting " "the TextGrid together with the SpellingChecker object, and clicking ##View & Edit#. In most cases, you will also want " "to select a @Sound or @LongSound object before clicking ##View & Edit#, so that a representation of the sound " "is also visible (and audible) in the editor. Thus, you typically select three objects and click ##View & Edit#. " "The editor then allows you to check the spellings " "(commands ##Check spelling in tier# and ##Check spelling in interval# from the #Spell menu).") ENTRY (L"3. How to create a SpellingChecker object for the first time") NORMAL (L"If you are the maintainer of a word list for spelling checking, you will want " "to convert this list to a SpellingChecker object that you can distribute among the transcribers of your corpus.") NORMAL (L"The first step is to create a @WordList object from your text file, as described on the @WordList man page. " "Then you simply click ##To SpellingChecker#. A button labelled ##Edit...# appears. " "This command allows you to set the following attributes of the SpellingChecker object:") /*TAG (L"##Check matching parentheses") DEFINITION (L"determines whether it is considered a spelling error if parentheses do not match, as in the string \"Hi) there\".")*/ TAG (L"##Allow all parenthesized") DEFINITION (L"this flag determines whether text between parentheses is ignored in spelling checking. " "This would allow the transcriber to mark utterances in foreign languages, which cannot be found in the lexicon.") TAG (L"##Separating characters") DEFINITION (L"determines the set of characters (apart from the space character) that separate words. " "The standard is \".,;:()\". If a string like \"error-prone\" should be considered two separate words, " "you will like to change this to \".,;:()-\". " "For the Corpus of Spoken Dutch (CGN), the hyphen is not a separator, since words like \"mee-eter\" should be checked as a whole. " "If a string like \"Mary's\" should be considered two separate words, include the apostrophe.") /*TAG (L"##Forbidden strings") DEFINITION (L"this will mainly contain characters that are not allowed in your corpus. For the CGN, this is \": ; \\\" \".")*/ TAG (L"##Allow all names") DEFINITION (L"determines whether all words that start with a capital are allowed. For the CGN, this is on, " "since the lexicon does not contain many names.") TAG (L"##Name prefixes") DEFINITION (L"a space-separated list that determines what small groups of characters can precede names. For the CGN, " "this is \"'s- d' l'\", since names like %%'s-Gravenhage%, %%d'Ancona%, and %%l'H\\o^pital% should be ignored by the spelling checker.") TAG (L"##Allow all words containing") DEFINITION (L"a space-separated list of strings that make a word correct even if not in the lexicon. " "For the CGN, this is \"* xxx\", since words like %%keuje*d% and %%verxxxing% should be ignored by the spelling checker.") TAG (L"##Allow all words starting with") DEFINITION (L"a space-separated list of prefixes that make a word correct even if not in the lexicon. " "For the CGN, this is empty.") TAG (L"##Allow all words ending in") DEFINITION (L"a space-separated list of suffixes that make a word correct even if not in the lexicon. " "For the CGN, this is \"-\", since the first word in %%verzekerings- en bankwezen% should be ignored by the spelling checker.") MAN_END MAN_BEGIN (L"TextGrid", L"ppgb", 20110128) INTRO (L"One of the @@types of objects@ in Praat, used for %annotation (segmentation and labelling). " "For tutorial information, see @@Intro 7. Annotation@.") ENTRY (L"Description") NORMAL (L"A #TextGrid object consists of a number of %tiers. There are two kinds of tiers: " "an %%interval tier% is a connected sequence of labelled intervals, with %boundaries in between. " "A %%point tier% is a sequence of labelled points.") ENTRY (L"How to create a TextGrid") TAG (L"From scratch:") LIST_ITEM (L"@@Sound: To TextGrid...@ (takes the time domain from the Sound)") LIST_ITEM (L"@@LongSound: To TextGrid...@ (takes the time domain from the LongSound)") LIST_ITEM (L"@@PointProcess: To TextGrid...@ (takes the time domain from the PointProcess)") LIST_ITEM (L"@@PointProcess: To TextGrid (vuv)...@ (labels voiced and unvoiced intervals)") LIST_ITEM (L"@@Create TextGrid...@") TAG (L"From merging existing TextGrids with each other:") LIST_ITEM (L"@@TextGrids: Merge@") ENTRY (L"How to edit a TextGrid") NORMAL (L"You select a TextGrid alone or together with a @Sound or @LongSound, and click ##View & Edit#. " "A @TextGridEditor will appear on your screen, containing the TextGrid " "and an optional copy of the Sound or LongSound.") ENTRY (L"How to draw a TextGrid") TAG (L"You can draw a TextGrid to the @@Picture window@ with:") LIST_ITEM (L"##TextGrid: Draw...") LIST_ITEM (L"##TextGrid & Sound: Draw...") LIST_ITEM (L"##TextGrid & Pitch: Draw...") LIST_ITEM (L"##TextGrid & Pitch: Draw separately...") MAN_END MAN_BEGIN (L"TextGrid: Count labels...", L"ppgb", 19980630) INTRO (L"A command to ask the selected @TextGrid object how many of the specified labels " "it contains in the specified tier.") ENTRY (L"Settings") TAG (L"##Tier number") DEFINITION (L"the number (1, 2, 3...) of the tier whose labels you want to investigate.") TAG (L"##Label text") DEFINITION (L"the text on the labels that you want to count.") ENTRY (L"Behaviour") NORMAL (L"The number of intervals or points with label %%Label text% in tier %%Tier number% " "is written into the @@Info window@. If the specified tier does not exist, the number will be 0.") ENTRY (L"Scripting") NORMAL (L"You can use this command to put the number into a script variable:") CODE (L"select TextGrid hallo") CODE (L"number_of_a = Count labels... 1 a") NORMAL (L"In this case, the value will not be written into the Info window.") MAN_END MAN_BEGIN (L"TextGrids: Merge", L"ppgb", 20101230) INTRO (L"A command to merge all selected @TextGrid objects into a new @TextGrid.") MAN_END MAN_BEGIN (L"TextGridEditor", L"ppgb", 20110131) INTRO (L"One of the @Editors in Praat, for editing a @TextGrid object.") NORMAL (L"You can optionally include a copy of a @Sound or @LongSound in this editor, " "by selecting both the TextGrid and the Sound or LongSound before clicking ##View & Edit#. " "The Sound or LongSound is shown in the upper part of the window, the tiers in the lower part. " "A text window at the top shows the text of the %#selected interval or point, " "i.e. the interval or point at the location of the cursor. " "All tiers are visible, and if you do not zoom in, all boundaries, points, and texts are visible, too. " "You can do many of the same things that you can do with a @SoundEditor or @LongSoundEditor.") ENTRY (L"Positioning the cursor or the selection marks") NORMAL (L"To position the cursor hair, @click in the #Sound, on a boundary, on a point, or inside an interval.") NORMAL (L"To select any part of the time domain, use the @@time selection@ mechanism; " "if you do this by clicking in a tier, " "the selected time domain will snap to the nearest boundary or point.") ENTRY (L"Creating new intervals, boundaries, points, or tiers") NORMAL (L"To create a new interval, create a new boundary in an interval tier.") NORMAL (L"To create a new boundary or point in a tier, @click inside the cursor circle in that tier, " "or choose one of the commands in the Boundary/Point menu to insert a boundary at the cursor time " "on the selected tier (shortcut: Enter) or on any tier (shortcuts: Command-F1 through Command-F9). The original text " "in the interval that is split, is divided up between the two resulting intervals, depending on " "the position of the text cursor in the text window.") NORMAL (L"To create a new tier, choose ##Add interval tier# or ##Add point tier# from the #Tier menu.") ENTRY (L"Playing an entire interval, or part of it") NORMAL (L"As in many other editors, you can play a stretch of sound by clicking in any of the rectangles " "around the drawing area.") NORMAL (L"To play an interval of an interval tier, you first @click inside it. This will make the interval %selected, " "which means that the visible part of the interval will be drawn in yellow. The cursor will be positioned " "at the start of the interval, and the time selection will comprise exactly the interval. This means that " "you can use the Tab key to play the interval. If you press it while a sound is playing, " "the Tab key will halt the playing sound, and the cursor will move to the time at which the sound stopped playing. " "This helps you to divide up a long sentence into parts that you can remember long enough to write them " "down.") NORMAL (L"The Tab key will play the selected interval.") ENTRY (L"Editing the text in an interval or at a point") NORMAL (L"To edit the label text of an interval or point:") LIST_ITEM (L"1. Select that interval or point by clicking in or on it. The text currently in the interval or point " "will appear in the text window.") LIST_ITEM (L"2. Just type the text, and use the mouse and the arrow keys to navigate the text window. " "Everything you type will become visible immediately in the text window as well as in the selected " "interval or point.") NORMAL (L"You can use all the @@Special symbols@ " "that you can use elsewhere in Praat, including mathematical symbols, Greek and Chinese letters, superscripts, " "and phonetic symbols.") ENTRY (L"Selecting a tier") NORMAL (L"To select a tier, click anywhere inside it. Its number and name will be drawn in red, " "and a pointing finger symbol (\\pf) will appear on its left.") ENTRY (L"Selecting a boundary or point") NORMAL (L"To select a boundary on an interval tier, @click in its vicinity or inside the following interval; " "the boundary will be drawn in red. The text in the interval will appear in the text window.") NORMAL (L"To select a point on a point tier, @click in its vicinity; it will be drawn in red. " "The text of the point will appear in the text window.") ENTRY (L"Moving one or more boundaries or points") NORMAL (L"To move a boundary or point to another time position, @drag it with the mouse.") NORMAL (L"To move all the boundaries and points with the same time (on different tiers) to another time position, " "@@Shift-drag@ them.") NORMAL (L"To move boundaries or points to the exact time position of a boundary or point on an other tier, " "@drag them into that other tier and into the vicinity of that boundary or point.") NORMAL (L"To move boundaries or points to the exact time position of the cursor, " "@drag them into the vicinity of the cursor.") ENTRY (L"Removing a boundary, point, or tier") NORMAL (L"To remove a selected #boundary, choose #Remove from the #Boundary menu. " "This creates a new interval which is the union of the two intervals originally adjoining the boundary; " "the new text of this interval is the concatenation of the two original texts, " "except if these were equal, in which case the new text equals both original texts.") NORMAL (L"To remove a selected #point, choose #Remove from the #Point menu.") NORMAL (L"To remove a selected #tier, choose ##Remove entire tier# from the #Tier menu.") /*"To rename a selected tier, choose 'Rename...' from the 'Tier' menu. "*/ /*"To remove all the boundaries and labels in a selected tier, " " choose 'Clear entire tier' from the 'Tier' menu. "*/ ENTRY (L"Extracting a part of the sound") NORMAL (L"To copy the selected part of the Sound or LongSound as a Sound to the @@List of Objects@, " "choose ##Extract sound selection# from the #File menu. You can specify whether you want " "the time domain of the resulting Sound to match the starting and finishing times of the " "selection or whether you want the time domain of the resulting Sound to start at zero seconds.") NORMAL (L"If you are viewing a LongSound, you can save the selected part of it to a 16-bit sound file " "(AIFF, AIFC, WAV, NeXT/Sun, NIST) with a command from the File menu.") ENTRY (L"Accelerations") NORMAL (L"To save the @TextGrid object as a text file without going to the @@Object window@: " "choose ##Save TextGrid as text file...# from the #File menu.") ENTRY (L"Searching") NORMAL (L"The Search menu contains the command #Find (Command-F), which will allow you to specify " "a text whose first occurrence will then be looked for in the currently selected tier " "(starting from the currently selected text in the currently selected interval). " "The command ##Find again# (Command-G) will search for the next occurrence of the same search text.") ENTRY (L"Checking the spelling") NORMAL (L"You can check the spelling of the intervals in your tiers by including a @SpellingChecker " "object as you launch the editor: select TextGrid + (Long)Sound + SpellingChecker, " "then click ##View & Edit#. The #Spell menu will contain the commands ##Check spelling in tier# (Command-N), and ##Check spelling in interval# " "which will search for the next word in the tier or interval that does not occur in the lexicon.") MAN_END MAN_BEGIN (L"WordList", L"ppgb", 20110131) INTRO (L"One of the @@types of objects@ in Praat. " "An object of class WordList contains a sorted list of strings in a system-independent format. " "WordList objects can be used for spelling checking after conversion to a @SpellingChecker object.") ENTRY (L"1. How to create a WordList object") NORMAL (L"You will normally create a WordList object by reading a binary WordList file. " "You'll use the generic @@Read from file...@ command from the #Open menu.") NORMAL (L"See below under 3 for how to create such a file.") ENTRY (L"2. What you can do with a Wordlist object") NORMAL (L"The main functionality of a WordList is its ability to tell you whether it contains a certain string. " "If you select a WordList, you can query the existence of a specific word by using the ##Has word# " "command. You supply the word and press OK. If the WordList does contain the word, " "the value \"1\" will be written to the Info window; otherwise, the value \"0\" will be written.") ENTRY (L"3. How to create a binary WordList file") NORMAL (L"You can create a binary (compressed) WordList file from a simple text file that contains a long list of words. " "Perhaps such a text file has been supplied by a lexicographic institution in your country; " "because of copyright issues, such word lists cannot be distributed with the Praat program. " "To convert the simple text file into a compressed WordList file, you basically take the following steps:") CODE (L"Read Strings from raw text file... lexicon.iso") CODE (L"Genericize") CODE (L"Sort") CODE (L"To WordList") CODE (L"Save as binary file... lexicon.WordList") NORMAL (L"I'll explain these steps in detail. " "For instance, a simple text file may contain the following list of words:") CODE (L"cook") CODE (L"cooked") CODE (L"cookie") CODE (L"cookies") CODE (L"cooking") CODE (L"cooks") CODE (L"Copenhagen") CODE (L"K\\o/bnhavn") CODE (L"M\\u\"nchen") CODE (L"Munich") CODE (L"\\aongstr\\o\"m") NORMAL (L"These are just 11 words, but the procedure will work fine if you have a million of them, " "and enough memory in your computer.") NORMAL (L"You can read the file into a @Strings object with @@Read Strings from raw text file...@ " "from the #Open menu in the Objects window. The resulting @Strings object contains 11 strings in the above order, " "as you can verify by viewing them with @Inspect.") NORMAL (L"In general, the Strings object will occupy a lot of memory, and be slow to read in. " "For instance, a certain list of more than 300,000 Dutch word forms occupies 3.6 MB on disk, " "and will occupy at least 7 MB of memory after it is read in. The extra 3.4 MB arise because the Strings object " "contains a pointer to each of the strings, and each of the strings is in a separately allocated part of " "the memory heap. Moreover, it takes 8 seconds on an average 1999 computer to read this object into memory. " "For these reasons, we will use the WordList object if we need a sorted list for spelling checking.") NORMAL (L"If you select the Strings, you can click the ##To WordList# button. " "However, you will get the following complaint:") CODE (L"String \"K\\o/bnhavn\" not generic. Please genericize first.") NORMAL (L"This complaint means that the strings are still in your computer's native text format, " "which is ISO-Latin1 for Unix and Windows computers, or Mac encoding for Macintosh computers.") NORMAL (L"So you press the #Genericize button. You can see that the Strings object changes to") CODE (L"cook") CODE (L"cooked") CODE (L"cookie") CODE (L"cookies") CODE (L"cooking") CODE (L"cooks") CODE (L"Copenhagen") CODE (L"K\\bso/bnhavn") CODE (L"M\\bsu\\\" nchen") CODE (L"Munich") CODE (L"\\bsaongstr\\bso\\\" m") NORMAL (L"The strings are now in the generic system-independent format that is used everywhere in Praat " "to draw strings (see @@Special symbols@).") NORMAL (L"You can again try to click the ##To WordList# button. However, you will get a complaint again:") CODE1 (L"String \"Copenhagen\" not sorted. Please sort first.") NORMAL (L"This complaint means that the strings have not been sorted in ASCII sorting order. " "So you click #Sort, and the Strings object becomes:") CODE (L"Copenhagen") CODE (L"K\\bso/bnhavn") CODE (L"M\\bsu\\\" nchen") CODE (L"Munich") CODE (L"\\bsaongstr\\bso\\\" m") CODE (L"cook") CODE (L"cooked") CODE (L"cookie") CODE (L"cookies") CODE (L"cooking") CODE (L"cooks") NORMAL (L"The strings are now in the ASCII order, in which capitals come before lower-case letters, " "and backslashes come in between these two series.") NORMAL (L"Clicking ##To WordList# now succeeds, and a WordList object appears in the list. " "If you save it to a text file (with the Save menu), you will get the following file:") CODE (L"File type = \"ooTextFile\"") CODE (L"Object class = \"WordList\"") CODE (L"") CODE (L"string = \"Copenhagen") CODE (L"K\\bso/bnhavn") CODE (L"M\\bsu\\\" \\\" nchen") CODE (L"Munich") CODE (L"\\bsaongstr\\bso\\\" \\\" m") CODE (L"cook") CODE (L"cooked") CODE (L"cookie") CODE (L"cookies") CODE (L"cooking") CODE (L"cooks\\\"r") NORMAL (L"Note that the double quotes (\\\" ) that appear inside the strings, have been doubled, " "as is done everywhere inside strings in Praat text files.") NORMAL (L"After you have created a WordList text file, you can create a WordList object just by reading this file " "with @@Read from file...@ from the #Open menu.") NORMAL (L"The WordList object has two advantages over the Strings object. First, it won't take up more " "memory than the original word list. This is because the WordList is stored as a single string: " "a contiguous list of strings, separated by new-line symbols. Thus, our 300,000-word list " "will take up only 3.6 MB, and be read in 4 seconds.") NORMAL (L"However, disk storage and reading can again be improved by compressing the word list. " "We can take advantage of the sorting, by noting for each entry how many leading characters " "are equal to those of the previous entry. The list then becomes something equivalent to") CODE (L"Copenhagen") CODE (L"0 K\\bso/bnhavn") CODE (L"0 M\\bsu\\\" nchen") CODE (L"1 unich") CODE (L"0 \\bsaongstr\\bso\\\" m") CODE (L"0 cook") CODE (L"4 ed") CODE (L"4 ie") CODE (L"6 s") CODE (L"5 ng") CODE (L"4 s") NORMAL (L"You can save the WordList compressed in this way as a binary file with " "@@Save as binary file...@. For our 300,000-word list, this file takes up only 1.1 MB " "and can be read into memory (with @@Read from file...@) in a single second. " "When read into memory, the WordList object is again expanded to 3.6 MB to allow rapid searching.") MAN_END /* longSound = selected ("LongSound") longSoundNaam$ = selected$ ("LongSound") textGrid = selected ("TextGrid") select 'textGrid' aantalIntervallen = Get number of intervals... 1 for interval to aantalIntervallen select 'textGrid' begintijd = Get starting point... 1 interval eindtijd = Get end point... 1 interval select 'longSound' Extract part... begintijd eindtijd no Save as WAV file... C:\Geluiden\'longSoundNaam$'_'interval'.wav Remove endfor # This is a Praat script that assumes that a single TextGrid is selected, # and that the data in the first (or only) tier is in the form # silence-text-silence-text and so on. The script will then write # the durations of the silences and the texts into the Info window. form Tabulate speech and silences comment Give the output file name: text fileName c:\windows\desktop\kim\out.txt endform # The following line provides the header, # separated by tabs for easy inclusion in Excel. echo Pause'tab$'Speech'tab$'Text # Every next line writes three pieces of data, # separated by tabs again. # The following is a command from the Query menu # that appears when you select a TextGrid object. numberOfIntervals = Get number of intervals... 1 # The number of silence-speech pairs is half of that number, # disregarding any silence at the end. numberOfPairs = numberOfIntervals div 2 # Cycle through all the silence-speech pairs. for pair to numberOfPairs silenceInterval = 2 * pair - 1 ; interval 1, 3, 5, and so on speechInterval = 2 * pair ; interval 2, 4, 6, and so on # Check that the silence interval is indeed empty. silenceText$ = Get label of interval... 1 silenceInterval if silenceText$ <> "" exit Interval 'silenceInterval' should be a silence, but isn't. endif # Also check that the speech interval contains some text. speechText$ = Get label of interval... 1 speechInterval if speechText$ = "" exit Interval 'speechInterval' should contain text, but doesn't. endif # So now we have checked that the intervals contain the data # that Kim wanted them to contain. We're ready to write the data! silenceBegin = Get starting point... 1 silenceInterval silenceEnd = Get end point... 1 silenceInterval silenceDuration_ms = (silenceEnd - silenceBegin) * 1000 speechBegin = Get starting point... 1 speechInterval speechEnd = Get end point... 1 speechInterval speechDuration_ms = (speechEnd - speechBegin) * 1000 printline 'silenceDuration_ms:0''tab$' ...'speechDuration_ms:0''tab$' ...'speechText$' endfor filedelete 'fileName$' fappendinfo 'fileName$' */ } /* End of file manual_annotation.cpp */ sources_5316/fon/SpectrumTier.cpp0000644000176700017670000000563311622364777015665 0ustar paulpaul/* SpectrumTier.cpp * * Copyright (C) 2007-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Ltas_to_SpectrumTier.h" Thing_implement (SpectrumTier, RealTier, 0); void structSpectrumTier :: v_info () { structData :: v_info (); MelderInfo_writeLine1 (L"Frequency domain:"); MelderInfo_writeLine3 (L" Lowest frequency: ", Melder_double (xmin), L" Hz"); MelderInfo_writeLine3 (L" Highest frequency: ", Melder_double (xmax), L" Hz"); MelderInfo_writeLine3 (L" Total bandwidth: ", Melder_double (xmax - xmin), L" Hz"); MelderInfo_writeLine2 (L"Number of points: ", Melder_integer (points -> size)); MelderInfo_writeLine3 (L"Minimum power value: ", Melder_double (RealTier_getMinimumValue (this)), L" dB/Hz"); MelderInfo_writeLine3 (L"Maximum power value: ", Melder_double (RealTier_getMaximumValue (this)), L" dB/Hz"); } SpectrumTier SpectrumTier_create (double fmin, double fmax) { try { autoSpectrumTier me = Thing_new (SpectrumTier); RealTier_init (me.peek(), fmin, fmax); return me.transfer(); } catch (MelderError) { Melder_throw ("SpectrumTier not created."); } } void SpectrumTier_draw (SpectrumTier me, Graphics g, double fmin, double fmax, double pmin, double pmax, int garnish, const wchar *method) { RealTier_draw (me, g, fmin, fmax, pmin, pmax, garnish, method, L"Power spectral density (dB)"); } void SpectrumTier_list (SpectrumTier me, bool includeIndexes, bool includeFrequency, bool includePowerDensity) { try { autoTable table = SpectrumTier_downto_Table (me, includeIndexes, includeFrequency, includePowerDensity); Table_list (table.peek(), false); } catch (MelderError) { Melder_throw (me, ": not listed."); } } Table SpectrumTier_downto_Table (SpectrumTier me, bool includeIndexes, bool includeFrequency, bool includePowerDensity) { return RealTier_downto_Table (me, includeIndexes ? L"index" : NULL, includeFrequency ? L"freq(Hz)" : NULL, includePowerDensity ? L"pow(dB/Hz)" : NULL); } SpectrumTier Spectrum_to_SpectrumTier_peaks (Spectrum me) { try { autoLtas ltas = Spectrum_to_Ltas_1to1 (me); autoSpectrumTier thee = Ltas_to_SpectrumTier_peaks (ltas.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": peaks not converted to SpectrumTier."); } } /* End of file SpectrumTier.cpp */ sources_5316/fon/FormantTier_def.h0000644000176700017670000000235211621176607015737 0ustar paulpaul/* FormantTier_def.h * * Copyright (C) 1992-2002 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT FormantPoint oo_DEFINE_CLASS (FormantPoint, Data) oo_DOUBLE (time) /* AnyPoint */ oo_INT (numberOfFormants) oo_DOUBLE_ARRAY (formant, 10, numberOfFormants) oo_DOUBLE_ARRAY (bandwidth, 10, numberOfFormants) oo_END_CLASS (FormantPoint) #undef ooSTRUCT #define ooSTRUCT FormantTier oo_DEFINE_CLASS (FormantTier, Function) oo_COLLECTION (SortedSetOfDouble, points, FormantPoint, 0) oo_END_CLASS (FormantTier) #undef ooSTRUCT /* End of file FormantTier_def.h */ sources_5316/fon/VocalTract.cpp0000644000176700017670000001640211724374520015263 0ustar paulpaul/* VocalTract.cpp * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "VocalTract.h" Thing_implement (VocalTract, Vector, 2); void structVocalTract :: v_info () { structData :: v_info (); MelderInfo_writeLine3 (L"Vocal tract length: ", Melder_single (xmax), L" metres"); MelderInfo_writeLine2 (L"Number of sections: ", Melder_integer (nx)); MelderInfo_writeLine3 (L"Section length: ", Melder_single (dx), L" metres"); } VocalTract VocalTract_create (long nx, double dx) { try { autoVocalTract me = Thing_new (VocalTract); Matrix_init (me.peek(), 0, nx * dx, nx, dx, 0.5 * dx, 1, 1, 1, 1, 1); therror return me.transfer(); } catch (MelderError) { Melder_throw ("VocalTract not created."); } } #define MinimumWidth 0.0001 static struct { const wchar *phone; int numberOfSections; double area [40]; } data [] = { { L"a", 34, { 1.7, 1.2, 1.6, 3.39, 2.1, 1.4, 1, 0.8, 0.8, 0.8, 1, 1.4, 2.1, 2.9, 3.09, 2.1, 2.5, 4, 5.3, 6.16, 7, 7.6, 8.15, 8.5, 8.6, 8.4, 8, 7.5, 6.9, 6, 5.1, 5, 5.5, 7.9 } }, { L"e", 33, { 2.3, 1.95, 1.73, 1.7, 5.3, 6.3, 6.8, 7.55, 8.2, 9.1, 9.7, 10.1, 10.2, 10, 8, 7.2, 7.5, 6.4, 5.4, 4.9, 4.35, 3.9, 3.5, 3.1, 2.7, 2.4, 2.2, 2.5, 3.4, 5, 6.7, 8.5, 10 } }, { L"i", 35, { 3, 2.9, 2.75, 2.58, 2.7, 6.35, 7.8, 8.9, 9.6, 10.15, 10.55, 10.9, 11.15, 11.3, 11.2, 10.8, 8, 7.8, 7, 4.5, 2.8, 1.9, 1.3, 0.9, 0.65, 0.55, 0.5, 0.55, 0.7, 0.95, 1.3, 2, 3, 5, 8 } }, { L"o", 37, { 2.6, 2.05, 1.56, 1.3, 5.2, 4.54, 3.49, 2.6, 2.1, 1.8, 1.6, 1.4, 1.29, 1.19, 1.22, 2.6, 2.9, 2.2, 2.6, 3.6, 4.55, 5.55, 6.4, 7.15, 8, 8.9, 9.6, 10.5, 11.8, 14.6, 14.5, 12.9, 10.4, 5, 3.4, 3.4, 4 } }, { L"u", 40, { 2.5, 2.5, 2.5, 2.4, 5, 8.1, 8.9, 8.9, 8.4, 7.5, 5.8, 3.9, 2.3, 1.6, 1.2, 1.05, 1.1, 1.4, 2.2, 2, 1.3, 2, 2.2, 2.3, 2.8, 3.7, 5, 6.2, 7.9, 10.9, 12.9, 13.15, 13, 12.5, 9.9, 3.9, 1.8, 0.32, 0.4, 0.6 } }, { L"y1", 37, { 3, 2.9, 2.75, 2.58, 2.7, 6.35, 7.8, 8.9, 9.6, 10.15, 10.55, 10.9, 11.15, 11.3, 11.2, 10.8, 8, 7.8, 7, 4.5, 2.8, 1.9, 1.3, 0.9, 0.65, 0.55, 0.5, 0.55, 0.7, 0.95, 1.3, 2, 3, 1.8, 0.32, 0.4, 0.6 } }, { L"y2", 38, { 3, 2.9, 2.75, 2.58, 2.7, 6.35, 7.8, 8.9, 9.6, 10.15, 10.55, 10.9, 11.15, 11.3, 11.2, 10.8, 8, 7.8, 7, 4.5, 2.8, 1.9, 1.3, 0.9, 0.65, 0.55, 0.5, 0.55, 0.7, 0.95, 1.3, 2, 3, 4, 1.8, 0.32, 0.4, 0.6 } }, { L"y3", 39, { 3, 2.9, 2.75, 2.58, 2.7, 6.35, 7.8, 8.9, 9.6, 10.15, 10.55, 10.9, 11.15, 11.3, 11.2, 10.8, 8, 7.8, 7, 4.5, 2.8, 1.9, 1.3, 0.9, 0.65, 0.55, 0.5, 0.55, 0.7, 0.95, 1.3, 2, 3, 4, 4, 1.8, 0.32, 0.4, 0.6 } }, { L"jery", 38, { 3.2, 3.2, 3.2, 3.2, 10.5, 10.5, 13, 13, 10.5, 10.5, 10.5, 10.5, 10.5, 8, 6.5, 6.5, 5, 4, 2, 2.6, 1.6, 1.3, 1, 1, 1.3, 1.6, 2, 2, 2.6, 3.2, 5, 8, 8, 8, 6.5, 2, 6.5, 6.5 } }, { L"p", 39, { 3.5, 3.2, 2.9, 2.6, 6.9, 6.65, 5.8, 4.9, 4, 3.14, 2.5, 1.84, 1.25, 0.83, 0.6, 0.53, 0.5, 0.6, 0.85, 1, 1.6, 2.05, 2.55, 3.08, 3.67, 4.15, 4.8, 5.5, 6.3, 7.4, 12, 12.98, 12.9, 11.4, 6.6, 2, 0.45, 0.1, MinimumWidth } }, { L"t", 36, { 2.8, 2.7, 2.4, 2.6, 6.45, 6.01, 5.31, 4.85, 4.55, 4.32, 4.18, 4.1, 4.04, 3.97, 3.85, 3.7, 3.4, 3.05, 2.91, 3.1, 3.55, 3.9, 4.1, 4, 3.8, 3.3, 2.55, 1.8, 1, 0.45, 0.1, MinimumWidth, 0.8, 2.5, 6, 9 } }, { L"k", 38, { 2.4, 2.7, 3, 3.3, 7, 9.38, 9.25, 8.62, 7.8, 6.7, 5.4, 4, 2.8, 1.9, 1.35, 0.9, 0.55, 0.3, 0.19, 0.07, MinimumWidth, 0.12, 0.17, 0.3, 0.5, 0.9, 1.4, 2.2, 3.3, 5, 9, 11.25, 10.9, 7.3, 4.3, 3.5, 3.7, 6 } }, { L"x", 40, { 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4 } }, { L"pa", 39, { 1.7, 1.2, 1.6, 3.39, 2.1, 1.4, 1, 0.8, 0.8, 0.8, 1, 1.4, 2.1, 2.9, 3.09, 2.1, 2.5, 4, 5.3, 6.16, 7, 7.6, 8.15, 8.5, 8.6, 8.4, 8, 7.5, 6.9, 6, 5.1, 5, 5.5, 7.9, 6.6, 2, 0.45, 0.1, MinimumWidth } }, { L"ta", 34, { 1.7, 1.2, 1.6, 3.39, 2.1, 1.4, 1, 0.8, 0.8, 0.8, 1, 1.4, 2.1, 2.9, 3.09, 2.1, 2.5, 4, 5.3, 6.16, 7, 7.6, 8.15, 8.5, 8.6, 8.5, 6, 2, 0.45, MinimumWidth, 0.8, 2.5, 5.5, 7.9 } }, { L"ka", 34, { 1.7, 1.2, 1.6, 3.39, 2.1, 1.4, 1, 0.8, 0.8, 0.8, 1, 1.4, 2.1, 2.9, 3.09, 2.1, 0.3, MinimumWidth, 0.3, 2, 5, 7.6, 8.15, 8.5, 8.6, 8.4, 8, 7.5, 6.9, 6, 5.1, 5, 5.5, 7.9 } }, { L"pi", 39, { 3, 2.9, 2.75, 2.58, 2.7, 6.35, 7.8, 8.9, 9.6, 10.15, 10.55, 10.9, 11.15, 11.3, 11.2, 10.8, 8, 7.8, 7, 4.5, 2.8, 1.9, 1.3, 0.9, 0.65, 0.55, 0.5, 0.55, 0.7, 0.95, 1.3, 2, 3, 5, 6.6, 2, 0.45, 0.1, MinimumWidth } }, { L"ti", 35, { 3, 2.9, 2.75, 2.58, 2.7, 6.35, 7.8, 8.9, 9.6, 10.15, 10.55, 10.9, 11.15, 11.3, 11.2, 10.8, 8, 7.8, 7, 4.5, 2.8, 1.9, 1.3, 0.9, 0.65, 0.55, 0.5, 0.5, 0.5, 0.3, 0.1, MinimumWidth, 0.8, 2.5, 8 } }, { L"ki", 35, { 3, 2.9, 2.75, 2.58, 2.7, 6.35, 7.8, 8.9, 9.6, 10.15, 10.55, 10.9, 11.15, 11.3, 11.2, 10.8, 8, 6, 2, 0.3, MinimumWidth, 0.3, 1.3, 0.9, 0.65, 0.55, 0.5, 0.55, 0.7, 0.95, 1.3, 2, 3, 5, 8 } }, { L"pu", 40, { 2.5, 2.5, 2.5, 2.4, 5, 8.1, 8.9, 8.9, 8.4, 7.5, 5.8, 3.9, 2.3, 1.6, 1.2, 1.05, 1.1, 1.4, 2.2, 2, 1.3, 2, 2.2, 2.3, 2.8, 3.7, 5, 6.2, 7.9, 10.9, 12.9, 13.15, 13, 12.5, 9.9, 6.6, 2, 0.45, 0.1, MinimumWidth } }, { L"tu", 40, { 2.5, 2.5, 2.5, 2.4, 5, 8.1, 8.9, 8.9, 8.4, 7.5, 5.8, 3.9, 2.3, 1.6, 1.2, 1.05, 1.1, 1.4, 2.2, 2, 1.3, 2, 2.2, 2.3, 2.8, 3.7, 5, 6.2, 7.9, 10.9, 9, 3, 0.4, MinimumWidth, 0.8, 2.5, 1.8, 0.32, 0.4, 0.6 } }, { L"ku", 40, { 2.5, 2.5, 2.5, 2.4, 5, 8.1, 8.9, 8.9, 8.4, 7.5, 5.8, 3.9, 2.3, 1.6, 1.2, 1.05, 1.1, 1.4, 1.2, 0.3, MinimumWidth, 0.3, 2.2, 2.3, 2.8, 3.7, 5, 6.2, 7.9, 10.9, 12.9, 13.15, 13, 12.5, 9.9, 3.9, 1.8, 0.32, 0.4, 0.6 } }, { NULL, 0, { 0 } } }; VocalTract VocalTract_createFromPhone (const wchar *phone) { try { int i = 0; for (;; i ++) { if (data [i]. phone == NULL) Melder_throw ("Unknown phone ", phone); if (Melder_wcsequ (data [i]. phone, phone)) break; } autoVocalTract me = VocalTract_create (data [i]. numberOfSections, 0.005); for (int isection = 1; isection <= my nx; isection ++) my z [1] [isection] = data [i]. area [isection - 1] * 0.0001; return me.transfer(); } catch (MelderError) { Melder_throw ("VocalTract not created from phone."); } } void VocalTract_draw (VocalTract me, Graphics g) { Matrix_drawRows (me, g, 0, 0, 0, 0, 0, 0); } Matrix VocalTract_to_Matrix (VocalTract me) { try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMvector_copyElements (my z [1], thy z [1], 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Matrix."); } } VocalTract Matrix_to_VocalTract (Matrix me) { try { autoVocalTract thee = VocalTract_create (my nx, my dx); NUMvector_copyElements (my z [1], thy z [1], 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to VocalTract."); } } /* End of file VocalTract.cpp */ sources_5316/fon/Matrix_and_Pitch.h0000644000176700017670000000162611614424561016104 0ustar paulpaul/* Matrix_and_Pitch.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Matrix.h" #include "Pitch.h" Matrix Pitch_to_Matrix (Pitch me); Pitch Matrix_to_Pitch (Matrix me); /* End of file Matrix_and_Pitch.h */ sources_5316/fon/Makefile0000644000176700017670000000533311704274076014161 0ustar paulpaul# Makefile of the library "fon" # Paul Boersma, 14 January 2012 include ../makefile.defs CPPFLAGS = -I ../num -I ../kar -I ../sys -I ../dwsys -I ../stat -I ../dwtools -I ../LPC -I ../fon -I ../external/portaudio -I ../external/flac -I ../external/mp3 OBJECTS = Transition.o Distributions_and_Transition.o \ Function.o Sampled.o Matrix.o Vector.o Polygon.o PointProcess.o \ Matrix_and_PointProcess.o Matrix_and_Polygon.o AnyTier.o RealTier.o \ Sound.o LongSound.o Sound_files.o Sound_audio.o PointProcess_and_Sound.o Sound_PointProcess.o ParamCurve.o \ Pitch.o Harmonicity.o Intensity.o Matrix_and_Pitch.o Sound_to_Pitch.o \ Sound_to_Intensity.o Sound_to_Harmonicity.o Sound_to_Harmonicity_GNE.o Sound_to_PointProcess.o \ Pitch_to_PointProcess.o Pitch_to_Sound.o Pitch_Intensity.o \ PitchTier.o Pitch_to_PitchTier.o PitchTier_to_PointProcess.o PitchTier_to_Sound.o Manipulation.o \ Pitch_AnyTier_to_PitchTier.o IntensityTier.o DurationTier.o AmplitudeTier.o \ Spectrum.o Ltas.o Spectrogram.o SpectrumTier.o Ltas_to_SpectrumTier.o \ Formant.o Image.o Sound_to_Formant.o Sound_and_Spectrogram.o \ Sound_and_Spectrum.o Spectrum_and_Spectrogram.o Spectrum_to_Formant.o \ FormantTier.o TextGrid.o TextGrid_Sound.o Label.o FormantGrid.o \ Excitation.o Cochleagram.o Cochleagram_and_Excitation.o Excitation_to_Formant.o \ Sound_to_Cochleagram.o Spectrum_to_Excitation.o \ VocalTract.o VocalTract_to_Spectrum.o \ SoundRecorder.o Sound_enhance.o VoiceAnalysis.o \ FunctionEditor.o TimeSoundEditor.o TimeSoundAnalysisEditor.o \ PitchEditor.o SoundEditor.o SpectrumEditor.o SpectrogramEditor.o PointEditor.o \ RealTierEditor.o PitchTierEditor.o IntensityTierEditor.o \ DurationTierEditor.o AmplitudeTierEditor.o \ ManipulationEditor.o TextGridEditor.o FormantGridEditor.o \ WordList.o SpellingChecker.o \ FujisakiPitch.o \ ExperimentMFC.o RunnerMFC.o manual_Exp.o praat_Exp.o \ Movie.o MovieWindow.o \ Corpus.o \ manual_Picture.o manual_Manual.o manual_Script.o \ manual_soundFiles.o manual_tutorials.o manual_references.o \ manual_programming.o manual_Fon.o manual_voice.o Praat_tests.o \ manual_glossary.o manual_Sampling.o manual_exampleSound.o \ manual_sound.o manual_pitch.o manual_spectrum.o manual_formant.o manual_annotation.o \ praat_Sound_init.o praat_TextGrid_init.o praat_Fon.o .PHONY: all clean all: libfon.a clean: $(RM) $(OBJECTS) $(RM) libfon.a libfon.a: $(OBJECTS) touch libfon.a rm libfon.a ar cq libfon.a $(OBJECTS) $(RANLIB) libfon.a $(OBJECTS): *.h ../num/NUM.h ../external/portaudio/*.h ../kar/*.h ../sys/*.h ../dwsys/*.h ../stat/*.h ../dwtools/*.h ../LPC/*.h ../external/flac/*.h ../external/mp3/mp3.h sources_5316/fon/PointProcess.h0000644000176700017670000000561411625721240015314 0ustar paulpaul#ifndef _PointProcess_h_ #define _PointProcess_h_ /* PointProcess.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Function.h" #include "Graphics.h" #include "PointProcess_def.h" oo_CLASS_CREATE (PointProcess, Function); PointProcess PointProcess_create (double startingTime, double finishingTime, long initialMaxnt); PointProcess PointProcess_createPoissonProcess (double startingTime, double finishingTime, double density); void PointProcess_init (I, double startingTime, double finishingTime, long initialMaxnt); long PointProcess_getLowIndex (PointProcess me, double t); long PointProcess_getHighIndex (PointProcess me, double t); long PointProcess_getNearestIndex (PointProcess me, double t); long PointProcess_getWindowPoints (PointProcess me, double tmin, double tmax, long *imin, long *imax); void PointProcess_addPoint (PointProcess me, double t); long PointProcess_findPoint (PointProcess me, double t); void PointProcess_removePoint (PointProcess me, long index); void PointProcess_removePointNear (PointProcess me, double t); void PointProcess_removePoints (PointProcess me, long first, long last); void PointProcess_removePointsBetween (PointProcess me, double fromTime, double toTime); void PointProcess_draw (PointProcess me, Graphics g, double fromTime, double toTime, int garnish); double PointProcess_getInterval (PointProcess me, double t); PointProcess PointProcesses_union (PointProcess me, PointProcess thee); PointProcess PointProcesses_intersection (PointProcess me, PointProcess thee); PointProcess PointProcesses_difference (PointProcess me, PointProcess thee); void PointProcess_fill (PointProcess me, double tmin, double tmax, double period); void PointProcess_voice (PointProcess me, double period, double maxT); long PointProcess_getNumberOfPeriods (PointProcess me, double tmin, double tmax, double minimumPeriod, double maximumPeriod, double maximumPeriodFactor); double PointProcess_getMeanPeriod (PointProcess me, double tmin, double tmax, double minimumPeriod, double maximumPeriod, double maximumPeriodFactor); double PointProcess_getStdevPeriod (PointProcess me, double tmin, double tmax, double minimumPeriod, double maximumPeriod, double maximumPeriodFactor); /* End of file PointProcess.h */ #endif sources_5316/fon/Spectrum_and_Spectrogram.cpp0000644000176700017670000000412711605364661020217 0ustar paulpaul/* Spectrum_and_Spectrogram.cpp * * Copyright (C) 1992-2011 David Weenink & Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 1998/04/18 * pb 2002/07/16 GPL * pb 2011/06/10 C++ */ #include "Spectrum_and_Spectrogram.h" Spectrum Spectrogram_to_Spectrum (I, double tim) { iam (Spectrogram); try { autoSpectrum thee = Spectrum_create (my ymax, my ny); /* Override stupid Spectrum values. */ thy xmin = my ymin; thy xmax = my ymax; thy x1 = my y1; // centre of first band, instead of 0 (makes it unFFTable) thy dx = my dy; // frequency step long itime = Sampled_xToIndex (me, tim); if (itime < 1 ) itime = 1; if (itime > my nx) itime = my nx; for (long ifreq = 1; ifreq <= my ny; ifreq ++) { double value = my z [ifreq] [itime]; if (value < 0.0) Melder_throw ("Negative values in spectrogram."); thy z [1] [ifreq] = sqrt (value); thy z [2] [ifreq] = 0.0; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": spectral slice not extracted."); } } Spectrogram Spectrum_to_Spectrogram (I) { iam (Spectrum); try { autoSpectrogram thee = Spectrogram_create (0, 1, 1, 1, 0.5, my xmin, my xmax, my nx, my dx, my x1); for (long i = 1; i <= my nx; i ++) thy z [i] [1] = my z [1] [i] * my z [1] [i] + my z [2] [i] * my z [2] [i]; return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Spectrogram."); } } /* End of file Spectrum_and_Spectrogram.cpp */ sources_5316/fon/FormantTier.cpp0000644000176700017670000002741511633511176015460 0ustar paulpaul/* FormantTier.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2006/07/21 made Sound_FormantTier_filter_inline () accurate for higher numbers of formants * pb 2007/01/27 made compatible with stereo sounds * pb 2007/03/17 domain quantity * pb 2007/10/01 can write as encoding * pb 2011/03/01 moved Formant filtering to FormantGrid (reimplemented) * pb 2011/05/26 C++ */ #include "FormantTier.h" #include "AnyTier.h" #include "oo_DESTROY.h" #include "FormantTier_def.h" #include "oo_COPY.h" #include "FormantTier_def.h" #include "oo_EQUAL.h" #include "FormantTier_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "FormantTier_def.h" #include "oo_WRITE_TEXT.h" #include "FormantTier_def.h" #include "oo_READ_TEXT.h" #include "FormantTier_def.h" #include "oo_WRITE_BINARY.h" #include "FormantTier_def.h" #include "oo_READ_BINARY.h" #include "FormantTier_def.h" #include "oo_DESCRIPTION.h" #include "FormantTier_def.h" Thing_implement (FormantPoint, Data, 0); FormantPoint FormantPoint_create (double time) { try { autoFormantPoint me = Thing_new (FormantPoint); my time = time; return me.transfer(); } catch (MelderError) { Melder_throw ("Formant point not created."); } } Thing_implement (FormantTier, Function, 0); FormantTier FormantTier_create (double tmin, double tmax) { try { autoFormantTier me = Thing_new (FormantTier); my points = SortedSetOfDouble_create (); therror my xmin = tmin; my xmax = tmax; return me.transfer(); } catch (MelderError) { Melder_throw ("FormantTier not created."); } } double FormantTier_getValueAtTime (FormantTier me, int iformant, double t) { long n = my points -> size; if (n == 0 || iformant < 1) return NUMundefined; FormantPoint pointRight = (FormantPoint) my points -> item [1]; if (t <= pointRight -> time) { if (iformant > pointRight -> numberOfFormants) return NUMundefined; return pointRight -> formant [iformant-1]; /* Constant extrapolation. */ } FormantPoint pointLeft = (FormantPoint) my points -> item [n]; if (t >= pointLeft -> time) { if (iformant > pointLeft -> numberOfFormants) return NUMundefined; return pointLeft -> formant [iformant-1]; /* Constant extrapolation. */ } Melder_assert (n >= 2); long ileft = AnyTier_timeToLowIndex (me, t), iright = ileft + 1; Melder_assert (ileft >= 1 && iright <= n); pointLeft = (FormantPoint) my points -> item [ileft]; pointRight = (FormantPoint) my points -> item [iright]; double tleft = pointLeft -> time; double fleft = iformant > pointLeft -> numberOfFormants ? NUMundefined : pointLeft -> formant [iformant-1]; double tright = pointRight -> time; double fright = iformant > pointRight -> numberOfFormants ? NUMundefined : pointRight -> formant [iformant-1]; return fleft == NUMundefined ? fright == NUMundefined ? NUMundefined : fright : fright == NUMundefined ? fleft : t == tright ? fright /* Be very accurate. */ : tleft == tright ? 0.5 * (fleft + fright) /* Unusual, but possible; no preference. */ : fleft + (t - tleft) * (fright - fleft) / (tright - tleft); /* Linear interpolation. */ } double FormantTier_getBandwidthAtTime (FormantTier me, int iformant, double t) { long n = my points -> size; if (n == 0) return 0.0; FormantPoint pointRight = (FormantPoint) my points -> item [1]; if (t <= pointRight -> time) { if (iformant > pointRight -> numberOfFormants) return NUMundefined; return pointRight -> bandwidth [iformant-1]; /* Constant extrapolation. */ } FormantPoint pointLeft = (FormantPoint) my points -> item [n]; if (t >= pointLeft -> time) { if (iformant > pointLeft -> numberOfFormants) return NUMundefined; return pointLeft -> bandwidth [iformant-1]; /* Constant extrapolation. */ } Melder_assert (n >= 2); long ileft = AnyTier_timeToLowIndex (me, t), iright = ileft + 1; Melder_assert (ileft >= 1 && iright <= n); pointLeft = (FormantPoint) my points -> item [ileft]; pointRight = (FormantPoint) my points -> item [iright]; double tleft = pointLeft -> time; double fleft = iformant > pointLeft -> numberOfFormants ? NUMundefined : pointLeft -> bandwidth [iformant-1]; double tright = pointRight -> time; double fright = iformant > pointRight -> numberOfFormants ? NUMundefined : pointRight -> bandwidth [iformant-1]; return fleft == NUMundefined ? fright == NUMundefined ? NUMundefined : fright : fright == NUMundefined ? fleft : t == tright ? fright /* Be very accurate. */ : tleft == tright ? 0.5 * (fleft + fright) /* Unusual, but possible; no preference. */ : fleft + (t - tleft) * (fright - fleft) / (tright - tleft); /* Linear interpolation. */ } void FormantTier_speckle (FormantTier me, Graphics g, double tmin, double tmax, double fmax, int garnish) { if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } Graphics_setWindow (g, tmin, tmax, 0.0, fmax); Graphics_setInner (g); long imin = AnyTier_timeToHighIndex (me, tmin); long imax = AnyTier_timeToLowIndex (me, tmax); if (imin > 0) for (long i = imin; i <= imax; i ++) { FormantPoint point = (FormantPoint) my points -> item [i]; double t = point -> time; for (long j = 1; j <= point -> numberOfFormants; j ++) { double f = point -> formant [j-1]; if (f <= fmax) Graphics_fillCircle_mm (g, t, f, 1.0); } } Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, TRUE, L"Time (s)"); Graphics_marksBottom (g, 2, TRUE, TRUE, FALSE); Graphics_marksLeft (g, 2, TRUE, TRUE, FALSE); Graphics_textLeft (g, TRUE, L"Frequency (Hz)"); } } FormantTier Formant_downto_FormantTier (Formant me) { try { autoFormantTier thee = FormantTier_create (my xmin, my xmax); for (long i = 1; i <= my nx; i ++) { Formant_Frame frame = & my d_frames [i]; autoFormantPoint point = FormantPoint_create (Sampled_indexToX (me, i)); point -> numberOfFormants = frame -> nFormants > 10 ? 10 : frame -> nFormants; for (long j = 1; j <= point -> numberOfFormants; j ++) { Formant_Formant pair = & frame -> formant [j]; point -> formant [j-1] = pair -> frequency; point -> bandwidth [j-1] = pair -> bandwidth; } Collection_addItem (thy points, point.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to FormantTier."); } } FormantTier Formant_PointProcess_to_FormantTier (Formant me, PointProcess pp) { try { autoFormantTier temp = Formant_downto_FormantTier (me); autoFormantTier thee = FormantTier_create (pp -> xmin, pp -> xmax); for (long ipoint = 1; ipoint <= pp -> nt; ipoint ++) { double time = pp -> t [ipoint]; autoFormantPoint point = FormantPoint_create (time); long iformant = 1; for (; iformant <= 10; iformant ++) { double value = FormantTier_getValueAtTime (temp.peek(), iformant, time); if (value == NUMundefined) break; point -> formant [iformant-1] = value; value = FormantTier_getBandwidthAtTime (temp.peek(), iformant, time); Melder_assert (value != NUMundefined); point -> bandwidth [iformant-1] = value; } point -> numberOfFormants = iformant - 1; Collection_addItem (thy points, point.transfer()); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, " & ", pp, ": not converted to FormantTier."); } } int FormantTier_getMinNumFormants (FormantTier me) { int minNumFormants = 10; for (long ipoint = 1; ipoint <= my points -> size; ipoint ++) { FormantPoint point = (FormantPoint) my points -> item [ipoint]; if (point -> numberOfFormants < minNumFormants) minNumFormants = point -> numberOfFormants; } return minNumFormants; } int FormantTier_getMaxNumFormants (FormantTier me) { int maxNumFormants = 0; for (long ipoint = 1; ipoint <= my points -> size; ipoint ++) { FormantPoint point = (FormantPoint) my points -> item [ipoint]; if (point -> numberOfFormants > maxNumFormants) maxNumFormants = point -> numberOfFormants; } return maxNumFormants; } TableOfReal FormantTier_downto_TableOfReal (FormantTier me, int includeFormants, int includeBandwidths) { try { int maximumNumberOfFormants = FormantTier_getMaxNumFormants (me); autoTableOfReal thee = TableOfReal_create (my points -> size, 1 + ( includeFormants ? maximumNumberOfFormants : 0 ) + ( includeBandwidths ? maximumNumberOfFormants : 0 )); TableOfReal_setColumnLabel (thee.peek(), 1, L"Time"); for (long icol = 1, iformant = 1; iformant <= maximumNumberOfFormants; iformant ++) { wchar label [4]; if (includeFormants) { swprintf (label, 4, L"F%d", iformant); TableOfReal_setColumnLabel (thee.peek(), ++ icol, label); } if (includeBandwidths) { swprintf (label, 4, L"B%d", iformant); TableOfReal_setColumnLabel (thee.peek(), ++ icol, label); } } for (long ipoint = 1; ipoint <= my points -> size; ipoint ++) { FormantPoint point = (FormantPoint) my points -> item [ipoint]; thy data [ipoint] [1] = point -> time; for (long icol = 1, iformant = 1; iformant <= maximumNumberOfFormants; iformant ++) { if (includeFormants) thy data [ipoint] [++ icol] = point -> formant [iformant-1]; if (includeBandwidths) thy data [ipoint] [++ icol] = point -> bandwidth [iformant-1]; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to TableOfReal."); } } void Sound_FormantTier_filter_inline (Sound me, FormantTier formantTier) { double dt = my dx; if (formantTier -> points -> size) for (long iformant = 1; iformant <= 10; iformant ++) { for (long isamp = 1; isamp <= my nx; isamp ++) { double t = my x1 + (isamp - 1) * my dx; /* * Compute LP coefficients. */ double formant, bandwidth; formant = FormantTier_getValueAtTime (formantTier, iformant, t); bandwidth = FormantTier_getBandwidthAtTime (formantTier, iformant, t); if (NUMdefined (formant) && NUMdefined (bandwidth)) { double cosomdt = cos (2 * NUMpi * formant * dt); double r = exp (- NUMpi * bandwidth * dt); /* Formants at 0 Hz or the Nyquist are single poles, others are double poles. */ if (fabs (cosomdt) > 0.999999) { /* Allow for round-off errors. */ /* single pole: D(z) = 1 - r z^-1 */ for (long channel = 1; channel <= my ny; channel ++) { if (isamp > 1) my z [channel] [isamp] += r * my z [channel] [isamp - 1]; } } else { /* double pole: D(z) = 1 + p z^-1 + q z^-2 */ double p = - 2 * r * cosomdt; double q = r * r; for (long channel = 1; channel <= my ny; channel ++) { if (isamp > 1) my z [channel] [isamp] -= p * my z [channel] [isamp - 1]; if (isamp > 2) my z [channel] [isamp] -= q * my z [channel] [isamp - 2]; } } } } } } Sound Sound_FormantTier_filter (Sound me, FormantTier formantTier) { try { autoSound thee = Data_copy (me); Sound_FormantTier_filter_inline (thee.peek(), formantTier); Vector_scale (thee.peek(), 0.99); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not filtered with ", formantTier, "."); } } Sound Sound_FormantTier_filter_noscale (Sound me, FormantTier formantTier) { try { autoSound thee = Data_copy (me); Sound_FormantTier_filter_inline (thee.peek(), formantTier); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not filtered with ", formantTier, "."); } } /* End of file FormantTier.cpp */ sources_5316/fon/manual_Sampling.cpp0000644000176700017670000002164411627220677016341 0ustar paulpaul/* manual_Sampling.cpp * * Copyright (C) 1992-2010 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" #include "Sound.h" void manual_Sampling_init (ManPages me); void manual_Sampling_init (ManPages me) { MAN_BEGIN (L"Get sampling period", L"ppgb", 20040420) INTRO (L"A command that becomes available in the #Query menu if you select a @Sound object.") NORMAL (L"The Info window will tell you the @@sampling period@ in seconds.") ENTRY (L"Usage") NORMAL (L"You will not often choose this command with the mouse, " "since the sampling period is included in the information that you get " "by clicking the #Info button. This command is probably more useful in a Praat script:") CODE (L"select Sound hello") CODE (L"samplingPeriod = Get sampling period") ENTRY (L"Details for hackers") NORMAL (L"With @Inspect, you can see how the sampling period is stored in a #Sound object: it is the #dx attribute.") MAN_END MAN_BEGIN (L"Get sampling frequency", L"ppgb", 20040420) INTRO (L"A command that becomes available in the #Query menu if you select a @Sound object.") NORMAL (L"The Info window will tell you the @@sampling frequency@ in hertz.") ENTRY (L"Usage") NORMAL (L"You will not often choose this command with the mouse, " "since the sampling frequency is included in the information that you get " "by clicking the #Info button. This command is probably more useful in a Praat script:") CODE (L"select Sound hello") CODE (L"samplingFrequency = Get sampling frequency") ENTRY (L"Algorithm") NORMAL (L"The sampling frequency is defined as 1 / (\\De%t), where \\De%t is the @@sampling period@. " "See @@Get sampling period@.") MAN_END MAN_BEGIN (L"Get time from sample number...", L"ppgb", 20040420) INTRO (L"A command that becomes available in the #Query menu if you select a @Sound or @LongSound object.") NORMAL (L"The Info window will tell you the time (in seconds) associated with the sample number that you specify.") ENTRY (L"Setting") TAG (L"##Sample number") DEFINITION (L"the sample number whose time is sought.") ENTRY (L"Algorithm") NORMAL (L"the result is") FORMULA (L"%t__1_ + (%sample_number - 1) \\.c \\De%t") NORMAL (L"where %t__1_ is the time associated with the first sample, and \\De%t is the sampling period.") ENTRY (L"Details for hackers") NORMAL (L"If you select a Sound or LongSound and click @Inspect, " "you can see how the relation between sample numbers and times is stored in the object: " "%t__1_ is the #x1 attribute, and \\De%t is the #dx attribute.") MAN_END MAN_BEGIN (L"Get sample number from time...", L"ppgb", 20040505) INTRO (L"A command that becomes available in the #Query menu if you select a @Sound or @LongSound object.") NORMAL (L"The Info window will tell you the sample number belonging to the time that you specify. " "The result is presented as a real number.") ENTRY (L"Setting") TAG (L"##Time (s)") DEFINITION (L"the time (in seconds) for which you want to know the sample number.") ENTRY (L"Example") NORMAL (L"If the sound has a sampling frequency of 10 kHz, the sample number associated with a time of 0.1 seconds " "will usually be 1000.5.") ENTRY (L"Scripting") NORMAL (L"You can use this command to put the nearest sample number into a script variable:") CODE (L"select Sound hallo") CODE (L"sampleNumber = Get sample number from time... 0.1") CODE (L"nearestSample = round (sampleNumber)") NORMAL (L"In this case, the value will not be written into the Info window. To round down or up, use") CODE (L"leftSample = floor (sampleNumber)") CODE (L"rightSample = ceiling (sampleNumber)") ENTRY (L"Algorithm") NORMAL (L"the result is") FORMULA (L"1 + (%time \\-- %t__1_) / \\De%t") NORMAL (L"where %t__1_ is the time associated with the first sample, and \\De%t is the sampling period.") ENTRY (L"Details for hackers") NORMAL (L"If you select a Sound or LongSound and click @Inspect, " "you can see how the relation between sample numbers and times is stored in the object: " "%t__1_ is the #x1 attribute, and \\De%t is the #dx attribute.") MAN_END MAN_BEGIN (L"Get number of samples", L"ppgb", 20040420) INTRO (L"A command that becomes available in the #Query menu if you select a @Sound or @LongSound object.") NORMAL (L"The Info window will tell you the total number of time samples in this object.") ENTRY (L"Example") NORMAL (L"If the sampling frequency is 44100 hertz, a recording with a duration of 60 seconds " "will contain 2,646,000 samples.") ENTRY (L"Details for hackers") NORMAL (L"If you select a Sound or LongSound and click @Inspect, " "you can see how the number of samples is stored in the object: it is the #nx attribute.") MAN_END MAN_BEGIN (L"Get time from frame number...", L"ppgb", 20040420) INTRO (L"A command that becomes available in the #Query menu if you select a sound-analysis object that is a function of time " "and that is evenly sampled in time (@Pitch, @Formant, @Intensity, @Harmonicity).") NORMAL (L"The Info window will tell you the time associated with the frame number that you specify.") ENTRY (L"Setting") TAG (L"##Frame number") DEFINITION (L"the frame number whose time is sought.") ENTRY (L"Algorithm") NORMAL (L"the result is") FORMULA (L"%t__1_ + (%frame_number - 1) \\.c \\De%t") NORMAL (L"where %t__1_ is the time associated with the centre of the first frame, and \\De%t is the time step.") ENTRY (L"Details for hackers") NORMAL (L"If you select one of the above objects and click @Inspect, " "you can see how the relation between frame numbers and times is stored in the object: " "%t__1_ is the #x1 attribute, and \\De%t is the #dx attribute.") MAN_END MAN_BEGIN (L"Get frame number from time...", L"ppgb", 20040505) INTRO (L"A command that becomes available in the #Query menu if you select a sound-analysis object that is a function of time " "and that is evenly sampled in time (@Pitch, @Formant, @Intensity, @Harmonicity).") NORMAL (L"The Info window will tell you the frame number belonging to the time that you specify. " "The result is presented as a real number.") ENTRY (L"Setting") TAG (L"##Time (s)") DEFINITION (L"the time (in seconds) for which you want to know the frame number.") ENTRY (L"Example") NORMAL (L"If the Pitch object has a time step of 10 ms, and the first frame is centred around 18 ms, " "the frame number associated with a time of 0.1 seconds is 9.2.") ENTRY (L"Scripting") NORMAL (L"You can use this command to put the nearest frame centre into a script variable:") CODE (L"select Pitch hallo") CODE (L"frame = Get frame from time... 0.1") CODE (L"nearestFrame = round (frame)") NORMAL (L"In this case, the value will not be written into the Info window. To round down or up, use") CODE (L"leftFrame = floor (frame)") CODE (L"rightFrame = ceiling (frame)") ENTRY (L"Algorithm") NORMAL (L"the result is") FORMULA (L"1 + (%time \\-- %t__1_) / \\De%t") NORMAL (L"where %t__1_ is the time associated with the centre of the first frame, " "and \\De%t is the time step.") ENTRY (L"Details for hackers") NORMAL (L"If you select one of the above objects and click @Inspect, " "you can see how the relation between frame numbers and times is stored in the object: " "%t__1_ is the #x1 attribute, and \\De%t is the #dx attribute.") MAN_END MAN_BEGIN (L"Get time step", L"ppgb", 20040420) INTRO (L"A command that becomes available in the #Query menu if you select a sound-analysis object that is a function of time " "and that is evenly sampled in time (@Pitch, @Formant, @Intensity, @Harmonicity).") NORMAL (L"The Info window will tell you the time difference between consecutive frames, e.g. " "the time difference between consecutive formant circles in the sound editor window.") ENTRY (L"Details for hackers") NORMAL (L"If you select one of the above objects and click @Inspect, " "you can see how the time step is stored in the object: it is the #dx attribute.") MAN_END MAN_BEGIN (L"Get number of frames", L"ppgb", 20040420) INTRO (L"A command that becomes available in the #Query menu if you select a sound-analysis object that is a function of time " "and that is evenly sampled in time (@Pitch, @Formant, @Intensity, @Harmonicity).") NORMAL (L"The Info window will tell you the total number of time frames in the object.") ENTRY (L"Details for hackers") NORMAL (L"If you select one of the above objects and click @Inspect, " "you can see how the number of frames is stored in the object: it is the #nx attribute.") MAN_END } /* End of file manual_Sampling.cpp */ sources_5316/fon/Function.h0000644000176700017670000001134511621504600014442 0ustar paulpaul#ifndef _Function_h_ #define _Function_h_ /* Function.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" #include "Function_def.h" oo_CLASS_CREATE (Function, Data); /* An object of type Function represents a function f (x, ...) on the domain [xmin, xmax] * .... Class invariants: xmax >= xmin; xmin, xmax are constant; */ void Function_init (Function me, double xmin, double xmax); /* Preconditions: xmin <= xmax; Postconditions: result -> xmin == xmin; result -> xmax == xmax; */ int Function_getDomainQuantity (Function me); // as input for MelderQuantity_getXXX /* * A function value is often expressed in some unit, such as: * Pa, Hz, dB, sones. * In the following, 'ilevel' is for multidimensional functions; it could be the row number of a matrix, * or pitch height (Hz) vs. pitch strength (dimensionless), and so on. * 'unit' is enumerated type that has to be defined in the header files of the descendant class, * starting from 0, which should be the default unit; e.g. for pitch: 0 = Hz, 1 = logHz, 2 = semitones, 3 = mel. */ int Function_getMinimumUnit (Function me, long ilevel); int Function_getMaximumUnit (Function me, long ilevel); #define Function_UNIT_TEXT_SHORT 0x00000001 #define Function_UNIT_TEXT_GRAPHICAL 0x00000002 #define Function_UNIT_TEXT_MENU 0x00000004 const wchar * Function_getUnitText (Function me, long ilevel, int unit, unsigned long flags); bool Function_isUnitLogarithmic (Function me, long ilevel, int unit); double Function_convertStandardToSpecialUnit (Function me, double value, long ilevel, int unit); double Function_convertSpecialToStandardUnit (Function me, double value, long ilevel, int unit); double Function_convertToNonlogarithmic (Function me, double value, long ilevel, int unit); /* The domain of a function can be changed by windowing. */ /* Here follow some window functions. */ #define Function_RECTANGULAR 0 #define Function_TRIANGULAR 1 #define Function_PARABOLIC 2 #define Function_HANNING 3 #define Function_HAMMING 4 #define Function_POTTER 5 #define Function_KAISER12 6 #define Function_KAISER20 7 #define Function_GAUSSIAN 8 double Function_window (double tim, int windowType); /* Return value: a number between 0 and 1, zero outside the "domain": domain [-0.5, 0.5]: rectangular, triangular, parabolic, hanning, hamming; domain [-0.77, 0.77]: potter, kaiser12; domain [-1, 1]: kaiser20; domain [-inf, +inf]: gaussian. Rectangular: 1; Triangular ("Parzen"): 1 - tim / 0.5 Parabolic ("Welch"): 1 - (tim / 0.5) ^ 2 Hanning (raised cosine): 0.5 + 0.5 * cos (2 * pi * tim) Hamming (raised cosine): 0.54 + 0.46 * cos (2 * pi * tim) Gaussian: exp (- (pi * tim) ^ 2) Kaiser12: besselI0 (12 * sqrt (1 - (tim / 0.77) ^ 2)) / besselI0 (12) Kaiser20: besselI0 (20.24 * sqrt (1 - tim ^ 2)) / besselI0 (20.24) Usage: the preferred window for almost every application is Kaiser20; its only shortcoming is the usual double computation time. Properties: Highest sidelobe: Rectangular: -10 dB Hanning: -30 dB Hamming: -40 dB Potter, Kaiser12: -90 dB Kaiser20: -180 dB Gaussian: -inf dB Height at 'tim' is +0.5 or -0.5 (limit from below): Rectangular: 1 Triangular, Parabolic, Hanning: 0 Hamming: 0.08 Gaussian: 0.085 Kaiser20: 0.0715 Potter: ... Area: Rectangular: 1 Parabolic: 2/3 Gaussian: 1 / sqrt (pi) Kaiser20: 0.9813318115591122859 / sqrt (pi) Hamming: 0.54 Triangular, Hanning: 1/2 Bandwidth (-20 dB): ... */ /* * Procedures to adapt a range to the extent of the function domain. */ void Function_unidirectionalAutowindow (Function me, double *xmin, double *xmax); void Function_bidirectionalAutowindow (Function me, double *x1, double *x2); bool Function_intersectRangeWithDomain (Function me, double *x1, double *x2); void Function_shiftXBy (Function me, double shift); void Function_shiftXTo (Function me, double xfrom, double xto); void Function_scaleXBy (Function me, double factor); void Function_scaleXTo (Function me, double xminto, double xmaxto); /* End of file Function.h */ #endif sources_5316/fon/TimeSoundEditor.cpp0000644000176700017670000006744511725105025016305 0ustar paulpaul/* TimeSoundEditor.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "TimeSoundEditor.h" #include "Preferences.h" #include "EditorM.h" #include "UnicodeData.h" Thing_implement (TimeSoundEditor, FunctionEditor, 0); /********** PREFERENCES **********/ static struct { struct TimeSoundEditor_sound sound; struct { bool preserveTimes; double bottom, top; bool garnish; } picture; struct { enum kSound_windowShape windowShape; double relativeWidth; bool preserveTimes; } extract; } preferences; void TimeSoundEditor_prefs (void) { Preferences_addBool (L"TimeSoundEditor.sound.autoscaling", & preferences.sound.autoscaling, true); Preferences_addBool (L"TimeSoundEditor.picture.preserveTimes", & preferences.picture.preserveTimes, true); Preferences_addDouble (L"TimeSoundEditor.picture.bottom", & preferences.picture.bottom, 0.0); Preferences_addDouble (L"TimeSoundEditor.picture.top", & preferences.picture.top, 0.0); Preferences_addBool (L"TimeSoundEditor.picture.garnish", & preferences.picture.garnish, true); Preferences_addEnum (L"TimeSoundEditor.extract.windowShape", & preferences.extract.windowShape, kSound_windowShape, DEFAULT); Preferences_addDouble (L"TimeSoundEditor.extract.relativeWidth", & preferences.extract.relativeWidth, 1.0); Preferences_addBool (L"TimeSoundEditor.extract.preserveTimes", & preferences.extract.preserveTimes, true); } /********** Thing methods **********/ void structTimeSoundEditor :: v_destroy () { if (ownSound) forget (sound.data); TimeSoundEditor_Parent :: v_destroy (); } void structTimeSoundEditor :: v_info () { TimeSoundEditor_Parent :: v_info (); /* Sound flag: */ MelderInfo_writeLine2 (L"Sound autoscaling: ", Melder_boolean (sound.autoscaling)); } /***** FILE MENU *****/ static void menu_cb_DrawVisibleSound (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM (L"Draw visible sound", 0) my v_form_pictureWindow (cmd); LABEL (L"", L"Sound:") BOOLEAN (L"Preserve times", 1); REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0 (= auto)") my v_form_pictureMargins (cmd); my v_form_pictureSelection (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); SET_INTEGER (L"Preserve times", preferences.picture.preserveTimes); SET_REAL (L"left Vertical range", preferences.picture.bottom); SET_REAL (L"right Vertical range", preferences.picture.top); my v_ok_pictureMargins (cmd); my v_ok_pictureSelection (cmd); SET_INTEGER (L"Garnish", preferences.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); preferences.picture.preserveTimes = GET_INTEGER (L"Preserve times"); preferences.picture.bottom = GET_REAL (L"left Vertical range"); preferences.picture.top = GET_REAL (L"right Vertical range"); my v_do_pictureMargins (cmd); my v_do_pictureSelection (cmd); preferences.picture.garnish = GET_INTEGER (L"Garnish"); if (my longSound.data == NULL && my sound.data == NULL) Melder_throw ("There is no sound to draw."); autoSound publish = my longSound.data ? LongSound_extractPart (my longSound.data, my startWindow, my endWindow, preferences.picture.preserveTimes) : Sound_extractPart (my sound.data, my startWindow, my endWindow, kSound_windowShape_RECTANGULAR, 1.0, preferences.picture.preserveTimes); Editor_openPraatPicture (me); Sound_draw (publish.peek(), my pictureGraphics, 0.0, 0.0, preferences.picture.bottom, preferences.picture.top, preferences.picture.garnish, L"Curve"); FunctionEditor_garnish (me); Editor_closePraatPicture (me); EDITOR_END } static void menu_cb_DrawSelectedSound (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM (L"Draw selected sound", 0) my v_form_pictureWindow (cmd); LABEL (L"", L"Sound:") BOOLEAN (L"Preserve times", 1); REAL (L"left Vertical range", L"0.0") REAL (L"right Vertical range", L"0.0 (= auto)") my v_form_pictureMargins (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); SET_INTEGER (L"Preserve times", preferences.picture.preserveTimes); SET_REAL (L"left Vertical range", preferences.picture.bottom); SET_REAL (L"right Vertical range", preferences.picture.top); my v_ok_pictureMargins (cmd); SET_INTEGER (L"Garnish", preferences.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); preferences.picture.preserveTimes = GET_INTEGER (L"Preserve times"); preferences.picture.bottom = GET_REAL (L"left Vertical range"); preferences.picture.top = GET_REAL (L"right Vertical range"); my v_do_pictureMargins (cmd); preferences.picture.garnish = GET_INTEGER (L"Garnish"); if (my longSound.data == NULL && my sound.data == NULL) Melder_throw ("There is no sound to draw."); autoSound publish = my longSound.data ? LongSound_extractPart (my longSound.data, my startSelection, my endSelection, preferences.picture.preserveTimes) : Sound_extractPart (my sound.data, my startSelection, my endSelection, kSound_windowShape_RECTANGULAR, 1.0, preferences.picture.preserveTimes); Editor_openPraatPicture (me); Sound_draw (publish.peek(), my pictureGraphics, 0.0, 0.0, preferences.picture.bottom, preferences.picture.top, preferences.picture.garnish, L"Curve"); Editor_closePraatPicture (me); EDITOR_END } static void do_ExtractSelectedSound (TimeSoundEditor me, bool preserveTimes) { autoSound extract = NULL; if (my endSelection <= my startSelection) Melder_throw ("No selection."); if (my longSound.data) { extract.reset (LongSound_extractPart (my longSound.data, my startSelection, my endSelection, preserveTimes)); } else if (my sound.data) { extract.reset (Sound_extractPart (my sound.data, my startSelection, my endSelection, kSound_windowShape_RECTANGULAR, 1.0, preserveTimes)); } my broadcastPublication (extract.transfer()); } static void menu_cb_ExtractSelectedSound_timeFromZero (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); do_ExtractSelectedSound (me, FALSE); } static void menu_cb_ExtractSelectedSound_preserveTimes (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); do_ExtractSelectedSound (me, TRUE); } static void menu_cb_ExtractSelectedSound_windowed (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM (L"Extract selected sound (windowed)", 0) WORD (L"Name", L"slice") OPTIONMENU_ENUM (L"Window shape", kSound_windowShape, HANNING) POSITIVE (L"Relative width", L"1.0") BOOLEAN (L"Preserve times", 1) EDITOR_OK SET_ENUM (L"Window shape", kSound_windowShape, preferences.extract.windowShape) SET_REAL (L"Relative width", preferences.extract.relativeWidth) SET_INTEGER (L"Preserve times", preferences.extract.preserveTimes) EDITOR_DO Sound sound = my sound.data; Melder_assert (sound != NULL); preferences.extract.windowShape = GET_ENUM (kSound_windowShape, L"Window shape"); preferences.extract.relativeWidth = GET_REAL (L"Relative width"); preferences.extract.preserveTimes = GET_INTEGER (L"Preserve times"); autoSound extract = Sound_extractPart (sound, my startSelection, my endSelection, preferences.extract.windowShape, preferences.extract.relativeWidth, preferences.extract.preserveTimes); Thing_setName (extract.peek(), GET_STRING (L"Name")); therror my broadcastPublication (extract.transfer()); EDITOR_END } static void do_write (TimeSoundEditor me, MelderFile file, int format, int numberOfBitsPersamplePoint) { if (my startSelection >= my endSelection) Melder_throw ("No samples selected."); if (my longSound.data) { LongSound_writePartToAudioFile (my longSound.data, format, my startSelection, my endSelection, file); therror } else if (my sound.data) { Sound sound = my sound.data; double margin = 0.0; long nmargin = margin / sound -> dx; long first, last, numberOfSamples = Sampled_getWindowSamples (sound, my startSelection, my endSelection, & first, & last) + nmargin * 2; first -= nmargin; last += nmargin; if (numberOfSamples) { autoSound save = Sound_create (sound -> ny, 0.0, numberOfSamples * sound -> dx, numberOfSamples, sound -> dx, 0.5 * sound -> dx); long offset = first - 1; if (first < 1) first = 1; if (last > sound -> nx) last = sound -> nx; for (long channel = 1; channel <= sound -> ny; channel ++) { for (long i = first; i <= last; i ++) { save -> z [channel] [i - offset] = sound -> z [channel] [i]; } } Sound_writeToAudioFile (save.peek(), file, format, numberOfBitsPersamplePoint); therror } } } static void menu_cb_WriteWav (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM_WRITE (L"Save selected sound as WAV file", 0) swprintf (defaultName, 300, L"%ls.wav", my longSound.data ? my longSound.data -> name : my sound.data -> name); EDITOR_DO_WRITE do_write (me, file, Melder_WAV, 16); EDITOR_END } static void menu_cb_SaveAs24BitWav (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM_WRITE (L"Save selected sound as 24-bit WAV file", 0) Melder_assert (my longSound.data == NULL && my sound.data != NULL); swprintf (defaultName, 300, L"%ls.wav", my sound.data -> name); EDITOR_DO_WRITE do_write (me, file, Melder_WAV, 24); EDITOR_END } static void menu_cb_SaveAs32BitWav (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM_WRITE (L"Save selected sound as 32-bit WAV file", 0) Melder_assert (my longSound.data == NULL && my sound.data != NULL); swprintf (defaultName, 300, L"%ls.wav", my sound.data -> name); EDITOR_DO_WRITE do_write (me, file, Melder_WAV, 32); EDITOR_END } static void menu_cb_WriteAiff (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM_WRITE (L"Save selected sound as AIFF file", 0) swprintf (defaultName, 300, L"%ls.aiff", my longSound.data ? my longSound.data -> name : my sound.data -> name); EDITOR_DO_WRITE do_write (me, file, Melder_AIFF, 16); EDITOR_END } static void menu_cb_WriteAifc (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM_WRITE (L"Save selected sound as AIFC file", 0) swprintf (defaultName, 300, L"%ls.aifc", my longSound.data ? my longSound.data -> name : my sound.data -> name); EDITOR_DO_WRITE do_write (me, file, Melder_AIFC, 16); EDITOR_END } static void menu_cb_WriteNextSun (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM_WRITE (L"Save selected sound as NeXT/Sun file", 0) swprintf (defaultName, 300, L"%ls.au", my longSound.data ? my longSound.data -> name : my sound.data -> name); EDITOR_DO_WRITE do_write (me, file, Melder_NEXT_SUN, 16); EDITOR_END } static void menu_cb_WriteNist (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM_WRITE (L"Save selected sound as NIST file", 0) swprintf (defaultName, 300, L"%ls.nist", my longSound.data ? my longSound.data -> name : my sound.data -> name); EDITOR_DO_WRITE do_write (me, file, Melder_NIST, 16); EDITOR_END } static void menu_cb_WriteFlac (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); EDITOR_FORM_WRITE (L"Save selected sound as FLAC file", 0) swprintf (defaultName, 300, L"%ls.flac", my longSound.data ? my longSound.data -> name : my sound.data -> name); EDITOR_DO_WRITE do_write (me, file, Melder_FLAC, 16); EDITOR_END } void structTimeSoundEditor :: v_createMenuItems_file_draw (EditorMenu menu) { EditorMenu_addCommand (menu, L"Draw to picture window:", GuiMenu_INSENSITIVE, menu_cb_DrawVisibleSound /* dummy */); if (sound.data || longSound.data) { EditorMenu_addCommand (menu, L"Draw visible sound...", 0, menu_cb_DrawVisibleSound); drawButton = EditorMenu_addCommand (menu, L"Draw selected sound...", 0, menu_cb_DrawSelectedSound); } } void structTimeSoundEditor :: v_createMenuItems_file_extract (EditorMenu menu) { EditorMenu_addCommand (menu, L"Extract to objects window:", GuiMenu_INSENSITIVE, menu_cb_ExtractSelectedSound_preserveTimes /* dummy */); if (sound.data || longSound.data) { publishPreserveButton = EditorMenu_addCommand (menu, L"Extract selected sound (preserve times)", 0, menu_cb_ExtractSelectedSound_preserveTimes); EditorMenu_addCommand (menu, L"Extract sound selection (preserve times)", Editor_HIDDEN, menu_cb_ExtractSelectedSound_preserveTimes); EditorMenu_addCommand (menu, L"Extract selection (preserve times)", Editor_HIDDEN, menu_cb_ExtractSelectedSound_preserveTimes); publishButton = EditorMenu_addCommand (menu, L"Extract selected sound (time from 0)", 0, menu_cb_ExtractSelectedSound_timeFromZero); EditorMenu_addCommand (menu, L"Extract sound selection (time from 0)", Editor_HIDDEN, menu_cb_ExtractSelectedSound_timeFromZero); EditorMenu_addCommand (menu, L"Extract selection (time from 0)", Editor_HIDDEN, menu_cb_ExtractSelectedSound_timeFromZero); EditorMenu_addCommand (menu, L"Extract selection", Editor_HIDDEN, menu_cb_ExtractSelectedSound_timeFromZero); if (sound.data) { publishWindowButton = EditorMenu_addCommand (menu, L"Extract selected sound (windowed)...", 0, menu_cb_ExtractSelectedSound_windowed); EditorMenu_addCommand (menu, L"Extract windowed sound selection...", Editor_HIDDEN, menu_cb_ExtractSelectedSound_windowed); EditorMenu_addCommand (menu, L"Extract windowed selection...", Editor_HIDDEN, menu_cb_ExtractSelectedSound_windowed); } } } void structTimeSoundEditor :: v_createMenuItems_file_write (EditorMenu menu) { EditorMenu_addCommand (menu, L"Save to disk:", GuiMenu_INSENSITIVE, menu_cb_WriteWav /* dummy */); if (sound.data || longSound.data) { writeWavButton = EditorMenu_addCommand (menu, L"Save selected sound as WAV file...", 0, menu_cb_WriteWav); EditorMenu_addCommand (menu, L"Write selected sound to WAV file...", Editor_HIDDEN, menu_cb_WriteWav); EditorMenu_addCommand (menu, L"Write sound selection to WAV file...", Editor_HIDDEN, menu_cb_WriteWav); EditorMenu_addCommand (menu, L"Write selection to WAV file...", Editor_HIDDEN, menu_cb_WriteWav); if (sound.data) { d_saveAs24BitWavButton = EditorMenu_addCommand (menu, L"Save selected sound as 24-bit WAV file...", 0, menu_cb_SaveAs24BitWav); d_saveAs32BitWavButton = EditorMenu_addCommand (menu, L"Save selected sound as 32-bit WAV file...", 0, menu_cb_SaveAs32BitWav); } writeAiffButton = EditorMenu_addCommand (menu, L"Save selected sound as AIFF file...", 0, menu_cb_WriteAiff); EditorMenu_addCommand (menu, L"Write selected sound to AIFF file...", Editor_HIDDEN, menu_cb_WriteAiff); EditorMenu_addCommand (menu, L"Write sound selection to AIFF file...", Editor_HIDDEN, menu_cb_WriteAiff); EditorMenu_addCommand (menu, L"Write selection to AIFF file...", Editor_HIDDEN, menu_cb_WriteAiff); writeAifcButton = EditorMenu_addCommand (menu, L"Save selected sound as AIFC file...", 0, menu_cb_WriteAifc); EditorMenu_addCommand (menu, L"Write selected sound to AIFC file...", Editor_HIDDEN, menu_cb_WriteAifc); EditorMenu_addCommand (menu, L"Write sound selection to AIFC file...", Editor_HIDDEN, menu_cb_WriteAifc); EditorMenu_addCommand (menu, L"Write selection to AIFC file...", Editor_HIDDEN, menu_cb_WriteAifc); writeNextSunButton = EditorMenu_addCommand (menu, L"Save selected sound as Next/Sun file...", 0, menu_cb_WriteNextSun); EditorMenu_addCommand (menu, L"Write selected sound to Next/Sun file...", Editor_HIDDEN, menu_cb_WriteNextSun); EditorMenu_addCommand (menu, L"Write sound selection to Next/Sun file...", Editor_HIDDEN, menu_cb_WriteNextSun); EditorMenu_addCommand (menu, L"Write selection to Next/Sun file...", Editor_HIDDEN, menu_cb_WriteNextSun); writeNistButton = EditorMenu_addCommand (menu, L"Save selected sound as NIST file...", 0, menu_cb_WriteNist); EditorMenu_addCommand (menu, L"Write selected sound to NIST file...", Editor_HIDDEN, menu_cb_WriteNist); EditorMenu_addCommand (menu, L"Write sound selection to NIST file...", Editor_HIDDEN, menu_cb_WriteNist); EditorMenu_addCommand (menu, L"Write selection to NIST file...", Editor_HIDDEN, menu_cb_WriteNist); writeFlacButton = EditorMenu_addCommand (menu, L"Save selected sound as FLAC file...", 0, menu_cb_WriteFlac); EditorMenu_addCommand (menu, L"Write selected sound to FLAC file...", Editor_HIDDEN, menu_cb_WriteFlac); EditorMenu_addCommand (menu, L"Write sound selection to FLAC file...", Editor_HIDDEN, menu_cb_WriteFlac); } } void structTimeSoundEditor :: v_createMenuItems_file (EditorMenu menu) { TimeSoundEditor_Parent :: v_createMenuItems_file (menu); v_createMenuItems_file_draw (menu); EditorMenu_addCommand (menu, L"-- after file draw --", 0, NULL); v_createMenuItems_file_extract (menu); EditorMenu_addCommand (menu, L"-- after file extract --", 0, NULL); v_createMenuItems_file_write (menu); EditorMenu_addCommand (menu, L"-- after file write --", 0, NULL); } /********** QUERY MENU **********/ static void menu_cb_SoundInfo (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); Thing_info (my sound.data); } static void menu_cb_LongSoundInfo (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); Thing_info (my longSound.data); } void structTimeSoundEditor :: v_createMenuItems_query_info (EditorMenu menu) { TimeSoundEditor_Parent :: v_createMenuItems_query_info (menu); if (sound.data != NULL && sound.data != data) { EditorMenu_addCommand (menu, L"Sound info", 0, menu_cb_SoundInfo); } else if (longSound.data != NULL && longSound.data != data) { EditorMenu_addCommand (menu, L"LongSound info", 0, menu_cb_LongSoundInfo); } } /********** VIEW MENU **********/ static void menu_cb_autoscaling (EDITOR_ARGS) { EDITOR_IAM (TimeSoundEditor); preferences.sound.autoscaling = my sound.autoscaling = ! my sound.autoscaling; FunctionEditor_redraw (me); } void structTimeSoundEditor :: v_createMenuItems_view (EditorMenu menu) { if (sound.data || longSound.data) v_createMenuItems_view_sound (menu); TimeSoundEditor_Parent :: v_createMenuItems_view (menu); } void structTimeSoundEditor :: v_createMenuItems_view_sound (EditorMenu menu) { EditorMenu_addCommand (menu, L"Sound autoscaling", GuiMenu_CHECKBUTTON | (preferences.sound.autoscaling ? GuiMenu_TOGGLE_ON : 0), menu_cb_autoscaling); EditorMenu_addCommand (menu, L"-- sound view --", 0, 0); } void structTimeSoundEditor :: v_updateMenuItems_file () { Sampled sound = this -> sound.data != NULL ? (Sampled) this -> sound.data : (Sampled) longSound.data; if (sound == NULL) return; long first, last, selectedSamples = Sampled_getWindowSamples (sound, startSelection, endSelection, & first, & last); if (drawButton) { GuiObject_setSensitive (drawButton, selectedSamples != 0); GuiObject_setSensitive (publishButton, selectedSamples != 0); GuiObject_setSensitive (publishPreserveButton, selectedSamples != 0); if (publishWindowButton) GuiObject_setSensitive (publishWindowButton, selectedSamples != 0); } GuiObject_setSensitive (writeWavButton, selectedSamples != 0); if (d_saveAs24BitWavButton) GuiObject_setSensitive (d_saveAs24BitWavButton, selectedSamples != 0); if (d_saveAs32BitWavButton) GuiObject_setSensitive (d_saveAs32BitWavButton, selectedSamples != 0); GuiObject_setSensitive (writeAiffButton, selectedSamples != 0); GuiObject_setSensitive (writeAifcButton, selectedSamples != 0); GuiObject_setSensitive (writeNextSunButton, selectedSamples != 0); GuiObject_setSensitive (writeNistButton, selectedSamples != 0); GuiObject_setSensitive (writeFlacButton, selectedSamples != 0); } void TimeSoundEditor_draw_sound (TimeSoundEditor me, double globalMinimum, double globalMaximum) { Sound sound = my sound.data; LongSound longSound = my longSound.data; Melder_assert ((sound == NULL) != (longSound == NULL)); int nchan = sound ? sound -> ny : longSound -> numberOfChannels; int cursorVisible = my startSelection == my endSelection && my startSelection >= my startWindow && my startSelection <= my endWindow; Graphics_setColour (my graphics, Graphics_BLACK); int fits; try { fits = sound ? TRUE : LongSound_haveWindow (longSound, my startWindow, my endWindow); } catch (MelderError) { int outOfMemory = wcsstr (Melder_getError (), L"memory") != NULL; if (Melder_debug == 9) Melder_flushError (NULL); else Melder_clearError (); Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_setTextAlignment (my graphics, Graphics_CENTRE, Graphics_HALF); Graphics_text (my graphics, 0.5, 0.5, outOfMemory ? L"(out of memory)" : L"(cannot read sound file)"); return; } if (! fits) { Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_setTextAlignment (my graphics, Graphics_CENTRE, Graphics_HALF); Graphics_text (my graphics, 0.5, 0.5, L"(window too large; zoom in to see the data)"); return; } long first, last; if (Sampled_getWindowSamples (sound ? (Sampled) sound : (Sampled) longSound, my startWindow, my endWindow, & first, & last) <= 1) { Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_setTextAlignment (my graphics, Graphics_CENTRE, Graphics_HALF); Graphics_text (my graphics, 0.5, 0.5, L"(zoom out to see the data)"); return; } const int numberOfVisibleChannels = nchan > 8 ? 8 : nchan; const int firstVisibleChannel = my sound.channelOffset + 1; int lastVisibleChannel = my sound.channelOffset + numberOfVisibleChannels; if (lastVisibleChannel > nchan) lastVisibleChannel = nchan; for (int ichan = firstVisibleChannel; ichan <= lastVisibleChannel; ichan ++) { double cursorFunctionValue = longSound ? 0.0 : Vector_getValueAtX (sound, 0.5 * (my startSelection + my endSelection), ichan, 70); /* * BUG: this will only work for mono or stereo, until Graphics_function16 handles quadro. */ double ymin = (double) (numberOfVisibleChannels - ichan + my sound.channelOffset) / numberOfVisibleChannels; double ymax = (double) (numberOfVisibleChannels + 1 - ichan + my sound.channelOffset) / numberOfVisibleChannels; Graphics_Viewport vp = Graphics_insetViewport (my graphics, 0, 1, ymin, ymax); bool horizontal = false; double minimum = sound ? globalMinimum : -1.0, maximum = sound ? globalMaximum : 1.0; if (my sound.autoscaling) { if (longSound) LongSound_getWindowExtrema (longSound, my startWindow, my endWindow, ichan, & minimum, & maximum); else Matrix_getWindowExtrema (sound, first, last, ichan, ichan, & minimum, & maximum); } if (minimum == maximum) { horizontal = true; minimum -= 1; maximum += 1;} Graphics_setWindow (my graphics, my startWindow, my endWindow, minimum, maximum); if (horizontal) { Graphics_setTextAlignment (my graphics, Graphics_RIGHT, Graphics_HALF); double mid = 0.5 * (minimum + maximum); Graphics_text1 (my graphics, my startWindow, mid, Melder_float (Melder_half (mid))); } else { if (! cursorVisible || Graphics_dyWCtoMM (my graphics, cursorFunctionValue - minimum) > 5.0) { Graphics_setTextAlignment (my graphics, Graphics_RIGHT, Graphics_BOTTOM); Graphics_text1 (my graphics, my startWindow, minimum, Melder_float (Melder_half (minimum))); } if (! cursorVisible || Graphics_dyWCtoMM (my graphics, maximum - cursorFunctionValue) > 5.0) { Graphics_setTextAlignment (my graphics, Graphics_RIGHT, Graphics_TOP); Graphics_text1 (my graphics, my startWindow, maximum, Melder_float (Melder_half (maximum))); } } if (minimum < 0 && maximum > 0 && ! horizontal) { Graphics_setWindow (my graphics, 0, 1, minimum, maximum); if (! cursorVisible || fabs (Graphics_dyWCtoMM (my graphics, cursorFunctionValue - 0.0)) > 3.0) { Graphics_setTextAlignment (my graphics, Graphics_RIGHT, Graphics_HALF); Graphics_text (my graphics, 0, 0, L"0"); } Graphics_setColour (my graphics, Graphics_CYAN); Graphics_setLineType (my graphics, Graphics_DOTTED); Graphics_line (my graphics, 0, 0, 1, 0); Graphics_setLineType (my graphics, Graphics_DRAWN); } /* * Garnish the drawing area of each channel. */ Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_CYAN); Graphics_innerRectangle (my graphics, 0, 1, 0, 1); Graphics_setColour (my graphics, Graphics_BLACK); if (nchan > 1) { Graphics_setTextAlignment (my graphics, Graphics_LEFT, Graphics_HALF); static MelderString channelLabel; const wchar *channelName = my v_getChannelName (ichan); MelderString_copy (& channelLabel, channelName ? L"ch" : L"Channel "); MelderString_append (& channelLabel, Melder_integer (ichan)); if (channelName) MelderString_append (& channelLabel, L": ", channelName); if (ichan > 8 && ichan - my sound.channelOffset == 1) { MelderString_append (& channelLabel, L" " UNITEXT_UPWARDS_ARROW); } else if (ichan >= 8 && ichan - my sound.channelOffset == 8 && ichan < nchan) { MelderString_append (& channelLabel, L" " UNITEXT_DOWNWARDS_ARROW); } Graphics_text1 (my graphics, 1, 0.5, channelLabel.string); } /* * Draw a very thin separator line underneath. */ if (ichan < nchan) { /*Graphics_setColour (my graphics, Graphics_BLACK);*/ Graphics_line (my graphics, 0, 0, 1, 0); } /* * Draw the samples. */ /*if (ichan == 1) FunctionEditor_SoundAnalysis_drawPulses (me);*/ if (sound) { Graphics_setWindow (my graphics, my startWindow, my endWindow, minimum, maximum); if (cursorVisible) FunctionEditor_drawCursorFunctionValue (me, cursorFunctionValue, Melder_float (Melder_half (cursorFunctionValue)), L""); Graphics_setColour (my graphics, Graphics_BLACK); Graphics_function (my graphics, sound -> z [ichan], first, last, Sampled_indexToX (sound, first), Sampled_indexToX (sound, last)); } else { Graphics_setWindow (my graphics, my startWindow, my endWindow, minimum * 32768, maximum * 32768); Graphics_function16 (my graphics, longSound -> buffer - longSound -> imin * nchan + (ichan - 1), nchan - 1, first, last, Sampled_indexToX (longSound, first), Sampled_indexToX (longSound, last)); } Graphics_resetViewport (my graphics, vp); } Graphics_setWindow (my graphics, 0, 1, 0, 1); Graphics_rectangle (my graphics, 0, 1, 0, 1); } int structTimeSoundEditor :: v_click (double xbegin, double ybegin, bool shiftKeyPressed) { Sound sound = this -> sound.data; LongSound longSound = this -> longSound.data; if ((sound == NULL) != (longSound == NULL)) { ybegin = (ybegin - v_getBottomOfSoundArea ()) / (1.0 - v_getBottomOfSoundArea ()); int nchan = sound ? sound -> ny : longSound -> numberOfChannels; if (nchan > 8) { //Melder_casual ("%f %f %d %d", xbegin, ybegin, (int) nchan, (int) this -> sound.channelOffset); if (xbegin >= endWindow && ybegin > 0.875 && ybegin <= 1.000 && this -> sound.channelOffset > 0) { this -> sound.channelOffset -= 8; return 1; } if (xbegin >= endWindow && ybegin > 0.000 && ybegin <= 0.125 && this -> sound.channelOffset < nchan - 8) { this -> sound.channelOffset += 8; return 1; } } } return TimeSoundEditor_Parent :: v_click (xbegin, ybegin, shiftKeyPressed); } void TimeSoundEditor_init (TimeSoundEditor me, GuiObject parent, const wchar *title, Function data, Sampled sound, bool ownSound) { my ownSound = ownSound; if (sound != NULL) { if (ownSound) { Melder_assert (Thing_member (sound, classSound)); my sound.data = Data_copy ((Sound) sound); // deep copy; ownership transferred Matrix_getWindowExtrema (sound, 1, my sound.data -> nx, 1, my sound.data -> ny, & my sound.minimum, & my sound.maximum); } else if (Thing_member (sound, classSound)) { my sound.data = (Sound) sound; // reference copy; ownership not transferred Matrix_getWindowExtrema (sound, 1, my sound.data -> nx, 1, my sound.data -> ny, & my sound.minimum, & my sound.maximum); } else if (Thing_member (sound, classLongSound)) { my longSound.data = (LongSound) sound; my sound.minimum = -1.0, my sound.maximum = 1.0; } else { Melder_fatal ("Invalid sound class in TimeSoundEditor_init."); } } FunctionEditor_init (me, parent, title, data); my sound.autoscaling = preferences.sound.autoscaling; } /* End of file TimeSoundEditor.cpp */ sources_5316/fon/VocalTract.h0000644000176700017670000000475011621513305014723 0ustar paulpaul#ifndef _VocalTract_h_ #define _VocalTract_h_ /* VocalTract.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Vector.h" #include "Graphics.h" Thing_define (VocalTract, Vector) { // overridden methods: protected: virtual void v_info (); virtual int v_domainQuantity () { return MelderQuantity_DISTANCE_FROM_GLOTTIS_METRES; } }; /* Attributes: xmin // 0. xmax > xmin // Total length (metres). nx >= 1 // Number of sections. dx > 0.0 // Section length (metres). x1 // Centre of first section (metres). ymin, ymax, ny, dy, y1 = 1 z [1] [1..nx] // The area, in square metres. */ VocalTract VocalTract_create (long nx, double dx); /* Function: create a VocalTract, or NULL if out of memory. Preconditions: nx >= 1; dx > 0.0; Postconditions: my xmin == 0; my ymin == 1; my xmax == nx * dx; my ymax == 1; my nx == nx; my ny == 1; my dx == dx; my dy == 1; my x1 == 0.5 * dx; my y1 == 1; my z [1] [1..nx] == 1e-4; // straight tube, area 1 cm2. */ VocalTract VocalTract_createFromPhone (const wchar *phone); /* 'phone' is one of the following: a e i o u y1 y2 y3 jery p t k x pa ta ka pi ti ki pu tu ku */ void VocalTract_draw (VocalTract me, Graphics g); /* Draw a VocalTract into a Graphics. */ Matrix VocalTract_to_Matrix (VocalTract me); /* Create a Matrix from a VocalTract, with deep copy of all of its Matrix attributes, except class information and methods. Return NULL if out of memory. */ VocalTract Matrix_to_VocalTract (Matrix me); /* Function: create a VocalTract from a Matrix. Return NULL if out of memory. Postconditions: thy xmin == my xmin; thy xmax == my xmax; thy nx == my nx; thy dx == my dx; thy x1 == my x1; thy ymin ymax ny dy y1 == 1; thy z [1] [...] == my z [1] [...]; */ /* End of file VocalTract.h */ #endif sources_5316/fon/PitchEditor.cpp0000644000176700017670000003213011632114574015432 0ustar paulpaul/* PitchEditor.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Pitch_to_Sound.h" #include "PitchEditor.h" #include "EditorM.h" Thing_implement (PitchEditor, FunctionEditor, 0); #define HEIGHT_UNV 3.0 #define HEIGHT_INTENS 6.0 #define RADIUS 2.5 /********** MENU COMMANDS **********/ static void menu_cb_setCeiling (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); EDITOR_FORM (L"Change ceiling", 0) POSITIVE (L"Ceiling (Hz)", L"600") EDITOR_OK Pitch pitch = (Pitch) my data; SET_REAL (L"Ceiling", pitch -> ceiling) EDITOR_DO Pitch pitch = (Pitch) my data; Editor_save (me, L"Change ceiling"); Pitch_setCeiling (pitch, GET_REAL (L"Ceiling")); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_pathFinder (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); EDITOR_FORM (L"Path finder", 0) REAL (L"Silence threshold", L"0.03") REAL (L"Voicing threshold", L"0.45") REAL (L"Octave cost", L"0.01") REAL (L"Octave-jump cost", L"0.35") REAL (L"Voiced/unvoiced cost", L"0.14") POSITIVE (L"Ceiling (Hz)", L"600") BOOLEAN (L"Pull formants", 0) EDITOR_OK Pitch pitch = (Pitch) my data; SET_REAL (L"Ceiling", pitch -> ceiling) EDITOR_DO Pitch pitch = (Pitch) my data; Editor_save (me, L"Path finder"); Pitch_pathFinder (pitch, GET_REAL (L"Silence threshold"), GET_REAL (L"Voicing threshold"), GET_REAL (L"Octave cost"), GET_REAL (L"Octave-jump cost"), GET_REAL (L"Voiced/unvoiced cost"), GET_REAL (L"Ceiling"), GET_INTEGER (L"Pull formants")); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_getPitch (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); if (my startSelection == my endSelection) { Melder_informationReal (Pitch_getValueAtTime ((Pitch) my data, my startSelection, kPitch_unit_HERTZ, 1), L"Hz"); } else { Melder_informationReal (Pitch_getMean ((Pitch) my data, my startSelection, my endSelection, kPitch_unit_HERTZ), L"Hz"); } } static void menu_cb_octaveUp (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); Pitch pitch = (Pitch) my data; Editor_save (me, L"Octave up"); Pitch_step (pitch, 2.0, 0.1, my startSelection, my endSelection); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_fifthUp (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); Pitch pitch = (Pitch) my data; Editor_save (me, L"Fifth up"); Pitch_step (pitch, 1.5, 0.1, my startSelection, my endSelection); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_fifthDown (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); Pitch pitch = (Pitch) my data; Editor_save (me, L"Fifth down"); Pitch_step (pitch, 1 / 1.5, 0.1, my startSelection, my endSelection); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_octaveDown (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); Pitch pitch = (Pitch) my data; Editor_save (me, L"Octave down"); Pitch_step (pitch, 0.5, 0.1, my startSelection, my endSelection); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_voiceless (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); Pitch pitch = (Pitch) my data; long ileft = Sampled_xToHighIndex (pitch, my startSelection), i, cand; long iright = Sampled_xToLowIndex (pitch, my endSelection); if (ileft < 1) ileft = 1; if (iright > pitch -> nx) iright = pitch -> nx; Editor_save (me, L"Unvoice"); for (i = ileft; i <= iright; i ++) { Pitch_Frame frame = & pitch -> frame [i]; for (cand = 1; cand <= frame -> nCandidates; cand ++) { if (frame -> candidate [cand]. frequency == 0.0) { struct structPitch_Candidate help = frame -> candidate [1]; frame -> candidate [1] = frame -> candidate [cand]; frame -> candidate [cand] = help; } } } FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_PitchEditorHelp (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); Melder_help (L"PitchEditor"); } static void menu_cb_PitchHelp (EDITOR_ARGS) { EDITOR_IAM (PitchEditor); Melder_help (L"Pitch"); } void structPitchEditor :: v_createMenus () { PitchEditor_Parent :: v_createMenus (); Editor_addCommand (this, L"Edit", L"Change ceiling...", 0, menu_cb_setCeiling); Editor_addCommand (this, L"Edit", L"Path finder...", 0, menu_cb_pathFinder); Editor_addCommand (this, L"Query", L"-- pitch --", 0, NULL); Editor_addCommand (this, L"Query", L"Get pitch", GuiMenu_F5, menu_cb_getPitch); Editor_addMenu (this, L"Selection", 0); Editor_addCommand (this, L"Selection", L"Unvoice", 0, menu_cb_voiceless); Editor_addCommand (this, L"Selection", L"-- up and down --", 0, NULL); Editor_addCommand (this, L"Selection", L"Octave up", 0, menu_cb_octaveUp); Editor_addCommand (this, L"Selection", L"Fifth up", 0, menu_cb_fifthUp); Editor_addCommand (this, L"Selection", L"Fifth down", 0, menu_cb_fifthDown); Editor_addCommand (this, L"Selection", L"Octave down", 0, menu_cb_octaveDown); } void structPitchEditor :: v_createHelpMenuItems (EditorMenu menu) { PitchEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"PitchEditor help", '?', menu_cb_PitchEditorHelp); EditorMenu_addCommand (menu, L"Pitch help", 0, menu_cb_PitchHelp); } /********** DRAWING AREA **********/ void structPitchEditor :: v_draw () { Pitch pitch = (Pitch) data; long it, it1, it2; double dyUnv, dyIntens; Graphics_setWindow (graphics, 0, 1, 0, 1); Graphics_setColour (graphics, Graphics_WHITE); Graphics_fillRectangle (graphics, 0, 1, 0, 1); Graphics_setColour (graphics, Graphics_BLACK); Graphics_rectangle (graphics, 0, 1, 0, 1); dyUnv = Graphics_dyMMtoWC (graphics, HEIGHT_UNV); dyIntens = Graphics_dyMMtoWC (graphics, HEIGHT_INTENS); Sampled_getWindowSamples (pitch, startWindow, endWindow, & it1, & it2); /* * Show pitch. */ { long df = pitch -> ceiling > 10000 ? 2000 : pitch -> ceiling > 5000 ? 1000 : pitch -> ceiling > 2000 ? 500 : pitch -> ceiling > 800 ? 200 : pitch -> ceiling > 400 ? 100 : 50; double radius; Graphics_Viewport previous; previous = Graphics_insetViewport (graphics, 0, 1, dyUnv, 1 - dyIntens); Graphics_setWindow (graphics, startWindow, endWindow, 0, pitch -> ceiling); radius = Graphics_dxMMtoWC (graphics, RADIUS); /* Horizontal hair at current pitch. */ if (startSelection == endSelection && startSelection >= startWindow && startSelection <= endWindow) { double f = Pitch_getValueAtTime (pitch, startSelection, kPitch_unit_HERTZ, Pitch_LINEAR); if (NUMdefined (f)) { Graphics_setColour (graphics, Graphics_RED); Graphics_line (graphics, startWindow - radius, f, endWindow, f); Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); Graphics_text1 (graphics, startWindow - radius, f, Melder_fixed (f, 2)); } } /* Horizontal scaling lines. */ Graphics_setColour (graphics, Graphics_BLUE); Graphics_setLineType (graphics, Graphics_DOTTED); Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_HALF); for (long f = df; f <= pitch -> ceiling; f += df) { Graphics_line (graphics, startWindow, f, endWindow, f); Graphics_text2 (graphics, endWindow + radius/2, f, Melder_integer (f), L" Hz"); } Graphics_setLineType (graphics, Graphics_DRAWN); /* Show candidates. */ for (it = it1; it <= it2; it ++) { Pitch_Frame frame = & pitch -> frame [it]; double t = Sampled_indexToX (pitch, it); double f = frame -> candidate [1]. frequency; if (f > 0.0 && f < pitch -> ceiling) { Graphics_setColour (graphics, Graphics_MAGENTA); Graphics_fillCircle_mm (graphics, t, f, RADIUS * 2); } Graphics_setColour (graphics, Graphics_BLACK); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_HALF); for (int icand = 1; icand <= frame -> nCandidates; icand ++) { int strength = (int) floor (10 * frame -> candidate [icand]. strength + 0.5); f = frame -> candidate [icand]. frequency; if (strength > 9) strength = 9; if (f > 0 && f <= pitch -> ceiling) Graphics_text1 (graphics, t, f, Melder_integer (strength)); } } Graphics_resetViewport (graphics, previous); } /* * Show intensity. */ { Graphics_Viewport previous; previous = Graphics_insetViewport (graphics, 0, 1, 1 - dyIntens, 1); Graphics_setWindow (graphics, startWindow, endWindow, 0, 1); Graphics_setColour (graphics, Graphics_BLACK); Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); Graphics_text (graphics, startWindow, 0.5, L"intens"); Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_HALF); Graphics_text (graphics, endWindow, 0.5, L"intens"); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_HALF); for (it = it1; it <= it2; it ++) { Pitch_Frame frame = & pitch -> frame [it]; double t = Sampled_indexToX (pitch, it); int strength = (int) floor (10 * frame -> intensity + 0.5); // map 0.0-1.0 to 0-9 if (strength > 9) strength = 9; Graphics_text1 (graphics, t, 0.5, Melder_integer (strength)); } Graphics_resetViewport (graphics, previous); } if (it1 > 1) it1 -= 1; if (it2 < pitch -> nx) it2 += 1; /* * Show voicelessness. */ { Graphics_Viewport previous; previous = Graphics_insetViewport (graphics, 0, 1, 0, dyUnv); Graphics_setColour (graphics, Graphics_BLUE); Graphics_line (graphics, startWindow, 1, endWindow, 1); Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); Graphics_text (graphics, startWindow, 0.5, L"Unv"); Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_HALF); Graphics_text (graphics, endWindow, 0.5, L"Unv"); for (it = it1; it <= it2; it ++) { Pitch_Frame frame = & pitch -> frame [it]; double t = Sampled_indexToX (pitch, it), tleft = t - 0.5 * pitch -> dx, tright = t + 0.5 * pitch -> dx; double f = frame -> candidate [1]. frequency; if ((f > 0.0 && f < pitch -> ceiling) || tright <= startWindow || tleft >= endWindow) continue; if (tleft < startWindow) tleft = startWindow; if (tright > endWindow) tright = endWindow; Graphics_fillRectangle (graphics, tleft, tright, 0, 1); } Graphics_setColour (graphics, Graphics_BLACK); Graphics_resetViewport (graphics, previous); } } void structPitchEditor :: v_play (double a_tmin, double a_tmax) { Pitch_hum ((Pitch) data, a_tmin, a_tmax); } int structPitchEditor :: v_click (double xWC, double yWC, bool dummy) { Pitch pitch = (Pitch) data; double dyUnv = Graphics_dyMMtoWC (graphics, HEIGHT_UNV); double dyIntens = Graphics_dyMMtoWC (graphics, HEIGHT_INTENS); double frequency = (yWC - dyUnv) / (1 - dyIntens - dyUnv) * pitch -> ceiling, tmid; double minimumDf = 1e30; int cand, bestCandidate = -1; long ibestFrame; Pitch_Frame bestFrame; ibestFrame = Sampled_xToNearestIndex (pitch, xWC); if (ibestFrame < 1) ibestFrame = 1; if (ibestFrame > pitch -> nx) ibestFrame = pitch -> nx; bestFrame = & pitch -> frame [ibestFrame]; tmid = Sampled_indexToX (pitch, ibestFrame); for (cand = 1; cand <= bestFrame -> nCandidates; cand ++) { double df = frequency - bestFrame -> candidate [cand]. frequency; if (fabs (df) < minimumDf) { minimumDf = fabs (df); bestCandidate = cand; } } if (bestCandidate != -1) { double bestFrequency = bestFrame -> candidate [bestCandidate]. frequency; double distanceWC = (frequency - bestFrequency) / pitch -> ceiling * (1 - dyIntens - dyUnv); double dx_mm = Graphics_dxWCtoMM (graphics, xWC - tmid), dy_mm = Graphics_dyWCtoMM (graphics, distanceWC); if (bestFrequency < pitch -> ceiling && // above ceiling: ignore ((bestFrequency <= 0.0 && fabs (xWC - tmid) <= 0.5 * pitch -> dx && frequency <= 0.0) || // voiceless: click within frame (bestFrequency > 0.0 && dx_mm * dx_mm + dy_mm * dy_mm <= RADIUS * RADIUS))) // voiced: click within circle { struct structPitch_Candidate help = bestFrame -> candidate [1]; Editor_save (this, L"Change path"); bestFrame -> candidate [1] = bestFrame -> candidate [bestCandidate]; bestFrame -> candidate [bestCandidate] = help; FunctionEditor_redraw (this); broadcastDataChanged (); startSelection = endSelection = tmid; // cursor will snap to candidate return 1; } else { return PitchEditor_Parent :: v_click (xWC, yWC, dummy); // move cursor or drag selection } } return PitchEditor_Parent :: v_click (xWC, yWC, dummy); // move cursor or drag selection } PitchEditor PitchEditor_create (GuiObject parent, const wchar *title, Pitch pitch) { try { autoPitchEditor me = Thing_new (PitchEditor); FunctionEditor_init (me.peek(), parent, title, pitch); return me.transfer(); } catch (MelderError) { Melder_throw ("Pitch window not created."); } } /* End of file PitchEditor.cpp */ sources_5316/fon/PitchEditor.h0000644000176700017670000000241411616732451015103 0ustar paulpaul#ifndef _PitchEditor_h_ #define _PitchEditor_h_ /* PitchEditor.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "FunctionEditor.h" #include "Pitch.h" Thing_define (PitchEditor, FunctionEditor) { // overridden methods: virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu); virtual void v_draw (); virtual void v_play (double tmin, double tmax); virtual int v_click (double xWC, double yWC, bool shiftKeyPressed); }; PitchEditor PitchEditor_create (GuiObject parent, const wchar *title, Pitch pitch); /* End of file PitchEditor.h */ #endif sources_5316/fon/Harmonics_def.h0000644000176700017670000000205611634671635015436 0ustar paulpaul/* Harmonics_def.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Harmonics oo_DEFINE_CLASS (Harmonics, Data) oo_LONG (numberOfHarmonics) oo_DOUBLE_VECTOR (harmonics, numberOfHarmonics) #if oo_DECLARING // overridden methods: public: virtual void v_info (); #endif oo_END_CLASS (Harmonics) #undef ooSTRUCT /* End of file Harmonics_def.h */ sources_5316/fon/Sound_to_Pitch.cpp0000644000176700017670000004273311633706332016147 0ustar paulpaul/* Sound_to_Pitch.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2002/10/11 removed some assertions * pb 2003/05/20 default time step is four times oversampling * pb 2003/07/02 checks on NUMrealft * pb 2004/05/10 better error messages * pb 2004/10/18 auto maxnCandidates * pb 2004/10/18 use of constant FFT tables speeds up AC method by a factor of 1.9 * pb 2006/12/31 compatible with stereo sounds * pb 2007/01/30 loop split for stereo speeds up CC method by a factor of 6 * pb 2008/01/19 double * pb 2010/12/07 compatible with sounds with any number of channels * pb 2011/03/08 C++ */ #include "Sound_to_Pitch.h" #include "NUM2.h" #define AC_HANNING 0 #define AC_GAUSS 1 #define FCC_NORMAL 2 #define FCC_ACCURATE 3 Pitch Sound_to_Pitch_any (Sound me, double dt, double minimumPitch, double periodsPerWindow, int maxnCandidates, int method, double silenceThreshold, double voicingThreshold, double octaveCost, double octaveJumpCost, double voicedUnvoicedCost, double ceiling) { try { autoNUMfft_Table fftTable; double duration, t1; double dt_window; /* Window length in seconds. */ long nsamp_window, halfnsamp_window; /* Number of samples per window. */ long nFrames, minimumLag, maximumLag; long iframe, nsampFFT; double interpolation_depth; long nsamp_period, halfnsamp_period; /* Number of samples in longest period. */ long brent_ixmax, brent_depth; double brent_accuracy; /* Obsolete. */ double globalPeak; Melder_assert (maxnCandidates >= 2); Melder_assert (method >= AC_HANNING && method <= FCC_ACCURATE); if (maxnCandidates < ceiling / minimumPitch) maxnCandidates = ceiling / minimumPitch; if (dt <= 0.0) dt = periodsPerWindow / minimumPitch / 4.0; /* e.g. 3 periods, 75 Hz: 10 milliseconds. */ switch (method) { case AC_HANNING: brent_depth = NUM_PEAK_INTERPOLATE_SINC70; brent_accuracy = 1e-7; interpolation_depth = 0.5; break; case AC_GAUSS: periodsPerWindow *= 2; /* Because Gaussian window is twice as long. */ brent_depth = NUM_PEAK_INTERPOLATE_SINC700; brent_accuracy = 1e-11; interpolation_depth = 0.25; /* Because Gaussian window is twice as long. */ break; case FCC_NORMAL: brent_depth = NUM_PEAK_INTERPOLATE_SINC70; brent_accuracy = 1e-7; interpolation_depth = 1.0; break; case FCC_ACCURATE: brent_depth = NUM_PEAK_INTERPOLATE_SINC700; brent_accuracy = 1e-11; interpolation_depth = 1.0; break; } duration = my dx * my nx; if (minimumPitch < periodsPerWindow / duration) Melder_throw ("To analyse this Sound, ", L_LEFT_DOUBLE_QUOTE, "minimum pitch", L_RIGHT_DOUBLE_QUOTE, " must not be less than ", periodsPerWindow / duration, " Hz."); /* * Determine the number of samples in the longest period. * We need this to compute the local mean of the sound (looking one period in both directions), * and to compute the local peak of the sound (looking half a period in both directions). */ nsamp_period = floor (1 / my dx / minimumPitch); halfnsamp_period = nsamp_period / 2 + 1; if (ceiling > 0.5 / my dx) ceiling = 0.5 / my dx; /* * Determine window length in seconds and in samples. */ dt_window = periodsPerWindow / minimumPitch; nsamp_window = floor (dt_window / my dx); halfnsamp_window = nsamp_window / 2 - 1; if (halfnsamp_window < 2) Melder_throw ("Analysis window too short."); nsamp_window = halfnsamp_window * 2; /* * Determine the minimum and maximum lags. */ minimumLag = floor (1 / my dx / ceiling); if (minimumLag < 2) minimumLag = 2; maximumLag = floor (nsamp_window / periodsPerWindow) + 2; if (maximumLag > nsamp_window) maximumLag = nsamp_window; /* * Determine the number of frames. * Fit as many frames as possible symmetrically in the total duration. * We do this even for the forward cross-correlation method, * because that allows us to compare the two methods. */ try { Sampled_shortTermAnalysis (me, method >= FCC_NORMAL ? 1 / minimumPitch + dt_window : dt_window, dt, & nFrames, & t1); therror } catch (MelderError) { Melder_throw ("The pitch analysis would give zero pitch frames."); } /* * Create the resulting pitch contour. */ autoPitch thee = Pitch_create (my xmin, my xmax, nFrames, dt, t1, ceiling, maxnCandidates); /* * Compute the global absolute peak for determination of silence threshold. */ globalPeak = 0.0; for (long channel = 1; channel <= my ny; channel ++) { double mean = 0.0; for (long i = 1; i <= my nx; i ++) { mean += my z [channel] [i]; } mean /= my nx; for (long i = 1; i <= my nx; i ++) { double value = fabs (my z [channel] [i] - mean); if (value > globalPeak) globalPeak = value; } } if (globalPeak == 0.0) { return thee.transfer(); } autoNUMmatrix frame; autoNUMvector ac; autoNUMvector window; autoNUMvector windowR; if (method >= FCC_NORMAL) { /* For cross-correlation analysis. */ /* * Create buffer for cross-correlation analysis. */ frame.reset (1, my ny, 1, nsamp_window); brent_ixmax = nsamp_window * interpolation_depth; } else { /* For autocorrelation analysis. */ /* * Compute the number of samples needed for doing FFT. * To avoid edge effects, we have to append zeroes to the window. * The maximum lag considered for maxima is maximumLag. * The maximum lag used in interpolation is nsamp_window * interpolation_depth. */ nsampFFT = 1; while (nsampFFT < nsamp_window * (1 + interpolation_depth)) nsampFFT *= 2; /* * Create buffers for autocorrelation analysis. */ frame.reset (1, my ny, 1, nsampFFT); windowR.reset (1, nsampFFT); window.reset (1, nsamp_window); NUMfft_Table_init (& fftTable, nsampFFT); therror ac.reset (1, nsampFFT); /* * A Gaussian or Hanning window is applied against phase effects. * The Hanning window is 2 to 5 dB better for 3 periods/window. * The Gaussian window is 25 to 29 dB better for 6 periods/window. */ if (method == AC_GAUSS) { /* Gaussian window. */ double imid = 0.5 * (nsamp_window + 1), edge = exp (-12.0); for (long i = 1; i <= nsamp_window; i ++) window [i] = (exp (-48.0 * (i - imid) * (i - imid) / (nsamp_window + 1) / (nsamp_window + 1)) - edge) / (1 - edge); } else { // Hanning window for (long i = 1; i <= nsamp_window; i ++) window [i] = 0.5 - 0.5 * cos (i * 2 * NUMpi / (nsamp_window + 1)); } /* * Compute the normalized autocorrelation of the window. */ for (long i = 1; i <= nsamp_window; i ++) windowR [i] = window [i]; NUMfft_forward (& fftTable, windowR.peek()); windowR [1] *= windowR [1]; // DC component for (long i = 2; i < nsampFFT; i += 2) { windowR [i] = windowR [i] * windowR [i] + windowR [i+1] * windowR [i+1]; windowR [i + 1] = 0.0; // power spectrum: square and zero } windowR [nsampFFT] *= windowR [nsampFFT]; // Nyquist frequency NUMfft_backward (& fftTable, windowR.peek()); // autocorrelation for (long i = 2; i <= nsamp_window; i ++) windowR [i] /= windowR [1]; // normalize windowR [1] = 1.0; // normalize brent_ixmax = nsamp_window * interpolation_depth; } autoNUMvector r (- nsamp_window, nsamp_window); autoNUMvector imax (1, maxnCandidates); autoNUMvector localMean (1, my ny); autoMelderProgress progress (L"Sound to Pitch..."); for (iframe = 1; iframe <= nFrames; iframe ++) { Pitch_Frame pitchFrame = & thy frame [iframe]; double t = Sampled_indexToX (thee.peek(), iframe), localPeak; long leftSample = Sampled_xToLowIndex (me, t), rightSample = leftSample + 1; long startSample, endSample; Melder_progress (0.1 + (0.8 * iframe) / (nFrames + 1), L"Sound to Pitch: analysis of frame ", Melder_integer (iframe), L" out of ", Melder_integer (nFrames)); for (long channel = 1; channel <= my ny; channel ++) { /* * Compute the local mean; look one longest period to both sides. */ startSample = rightSample - nsamp_period; endSample = leftSample + nsamp_period; Melder_assert (startSample >= 1); Melder_assert (endSample <= my nx); localMean [channel] = 0.0; for (long i = startSample; i <= endSample; i ++) { localMean [channel] += my z [channel] [i]; } localMean [channel] /= 2 * nsamp_period; /* * Copy a window to a frame and subtract the local mean. * We are going to kill the DC component before windowing. */ startSample = rightSample - halfnsamp_window; endSample = leftSample + halfnsamp_window; Melder_assert (startSample >= 1); Melder_assert (endSample <= my nx); if (method < FCC_NORMAL) { for (long j = 1, i = startSample; j <= nsamp_window; j ++) frame [channel] [j] = (my z [channel] [i ++] - localMean [channel]) * window [j]; for (long j = nsamp_window + 1; j <= nsampFFT; j ++) frame [channel] [j] = 0.0; } else { for (long j = 1, i = startSample; j <= nsamp_window; j ++) frame [channel] [j] = my z [channel] [i ++] - localMean [channel]; } } /* * Compute the local peak; look half a longest period to both sides. */ localPeak = 0.0; if ((startSample = halfnsamp_window + 1 - halfnsamp_period) < 1) startSample = 1; if ((endSample = halfnsamp_window + halfnsamp_period) > nsamp_window) endSample = nsamp_window; for (long channel = 1; channel <= my ny; channel ++) { for (long j = startSample; j <= endSample; j ++) { double value = fabs (frame [channel] [j]); if (value > localPeak) localPeak = value; } } pitchFrame->intensity = localPeak > globalPeak ? 1.0 : localPeak / globalPeak; /* * Compute the correlation into the array 'r'. */ if (method >= FCC_NORMAL) { double startTime = t - 0.5 * (1.0 / minimumPitch + dt_window); long localSpan = maximumLag + nsamp_window, localMaximumLag, offset; if ((startSample = Sampled_xToLowIndex (me, startTime)) < 1) startSample = 1; if (localSpan > my nx + 1 - startSample) localSpan = my nx + 1 - startSample; localMaximumLag = localSpan - nsamp_window; offset = startSample - 1; double sumx2 = 0; /* Sum of squares. */ for (long channel = 1; channel <= my ny; channel ++) { double *amp = my z [channel] + offset; for (long i = 1; i <= nsamp_window; i ++) { double x = amp [i] - localMean [channel]; sumx2 += x * x; } } double sumy2 = sumx2; /* At zero lag, these are still equal. */ r [0] = 1.0; for (long i = 1; i <= localMaximumLag; i ++) { double product = 0.0; for (long channel = 1; channel <= my ny; channel ++) { double *amp = my z [channel] + offset; double y0 = amp [i] - localMean [channel]; double yZ = amp [i + nsamp_window] - localMean [channel]; sumy2 += yZ * yZ - y0 * y0; for (long j = 1; j <= nsamp_window; j ++) { double x = amp [j] - localMean [channel]; double y = amp [i + j] - localMean [channel]; product += x * y; } } r [- i] = r [i] = product / sqrt (sumx2 * sumy2); } } else { /* * The FFT of the autocorrelation is the power spectrum. */ for (long i = 1; i <= nsampFFT; i ++) { ac [i] = 0.0; } for (long channel = 1; channel <= my ny; channel ++) { NUMfft_forward (& fftTable, frame [channel]); /* Complex spectrum. */ ac [1] += frame [channel] [1] * frame [channel] [1]; /* DC component. */ for (long i = 2; i < nsampFFT; i += 2) { ac [i] += frame [channel] [i] * frame [channel] [i] + frame [channel] [i+1] * frame [channel] [i+1]; /* Power spectrum. */ } ac [nsampFFT] += frame [channel] [nsampFFT] * frame [channel] [nsampFFT]; /* Nyquist frequency. */ } NUMfft_backward (& fftTable, ac.peek()); /* Autocorrelation. */ /* * Normalize the autocorrelation to the value with zero lag, * and divide it by the normalized autocorrelation of the window. */ r [0] = 1.0; for (long i = 1; i <= brent_ixmax; i ++) r [- i] = r [i] = ac [i + 1] / (ac [1] * windowR [i + 1]); } /* * Create (too much) space for candidates. */ Pitch_Frame_init (pitchFrame, maxnCandidates); therror /* * Register the first candidate, which is always present: voicelessness. */ pitchFrame->nCandidates = 1; pitchFrame->candidate[1].frequency = 0.0; /* Voiceless: always present. */ pitchFrame->candidate[1].strength = 0.0; /* * Shortcut: absolute silence is always voiceless. * Go to next frame. */ if (localPeak == 0) continue; /* * Find the strongest maxima of the correlation of this frame, * and register them as candidates. */ imax [1] = 0; for (long i = 2; i < maximumLag && i < brent_ixmax; i ++) if (r [i] > 0.5 * voicingThreshold && /* Not too unvoiced? */ r [i] > r [i-1] && r [i] >= r [i+1]) /* Maximum? */ { int place = 0; /* * Use parabolic interpolation for first estimate of frequency, * and sin(x)/x interpolation to compute the strength of this frequency. */ double dr = 0.5 * (r [i+1] - r [i-1]), d2r = 2 * r [i] - r [i-1] - r [i+1]; double frequencyOfMaximum = 1 / my dx / (i + dr / d2r); long offset = - brent_ixmax - 1; double strengthOfMaximum = /* method & 1 ? */ NUM_interpolate_sinc (& r [offset], brent_ixmax - offset, 1 / my dx / frequencyOfMaximum - offset, 30) /* : r [i] + 0.5 * dr * dr / d2r */; /* High values due to short windows are to be reflected around 1. */ if (strengthOfMaximum > 1.0) strengthOfMaximum = 1.0 / strengthOfMaximum; /* * Find a place for this maximum. */ if (pitchFrame->nCandidates < thy maxnCandidates) { /* Is there still a free place? */ place = ++ pitchFrame->nCandidates; } else { /* Try the place of the weakest candidate so far. */ double weakest = 2; for (int iweak = 2; iweak <= thy maxnCandidates; iweak ++) { /* High frequencies are to be favoured */ /* if we want to analyze a perfectly periodic signal correctly. */ double localStrength = pitchFrame->candidate[iweak].strength - octaveCost * NUMlog2 (minimumPitch / pitchFrame->candidate[iweak].frequency); if (localStrength < weakest) { weakest = localStrength; place = iweak; } } /* If this maximum is weaker than the weakest candidate so far, give it no place. */ if (strengthOfMaximum - octaveCost * NUMlog2 (minimumPitch / frequencyOfMaximum) <= weakest) place = 0; } if (place) { /* Have we found a place for this candidate? */ pitchFrame->candidate[place].frequency = frequencyOfMaximum; pitchFrame->candidate[place].strength = strengthOfMaximum; imax [place] = i; } } /* * Second pass: for extra precision, maximize sin(x)/x interpolation ('sinc'). */ for (long i = 2; i <= pitchFrame->nCandidates; i ++) { if (method != AC_HANNING || pitchFrame->candidate[i].frequency > 0.0 / my dx) { double xmid, ymid; long offset = - brent_ixmax - 1; ymid = NUMimproveMaximum (& r [offset], brent_ixmax - offset, imax [i] - offset, pitchFrame->candidate[i].frequency > 0.3 / my dx ? NUM_PEAK_INTERPOLATE_SINC700 : brent_depth, & xmid); xmid += offset; pitchFrame->candidate[i].frequency = 1.0 / my dx / xmid; if (ymid > 1.0) ymid = 1.0 / ymid; pitchFrame->candidate[i].strength = ymid; } } } /* Next frame. */ Melder_progress (0.95, L"Sound to Pitch: path finder"); // progress (0.95, L"Sound to Pitch: path finder"); Pitch_pathFinder (thee.peek(), silenceThreshold, voicingThreshold, octaveCost, octaveJumpCost, voicedUnvoicedCost, ceiling, Melder_debug == 31 ? true : false); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": pitch analysis not performed."); } } Pitch Sound_to_Pitch (Sound me, double timeStep, double minimumPitch, double maximumPitch) { return Sound_to_Pitch_ac (me, timeStep, minimumPitch, 3.0, 15, FALSE, 0.03, 0.45, 0.01, 0.35, 0.14, maximumPitch); } Pitch Sound_to_Pitch_ac (Sound me, double dt, double minimumPitch, double periodsPerWindow, int maxnCandidates, int accurate, double silenceThreshold, double voicingThreshold, double octaveCost, double octaveJumpCost, double voicedUnvoicedCost, double ceiling) { return Sound_to_Pitch_any (me, dt, minimumPitch, periodsPerWindow, maxnCandidates, accurate, silenceThreshold, voicingThreshold, octaveCost, octaveJumpCost, voicedUnvoicedCost, ceiling); } Pitch Sound_to_Pitch_cc (Sound me, double dt, double minimumPitch, double periodsPerWindow, int maxnCandidates, int accurate, double silenceThreshold, double voicingThreshold, double octaveCost, double octaveJumpCost, double voicedUnvoicedCost, double ceiling) { return Sound_to_Pitch_any (me, dt, minimumPitch, periodsPerWindow, maxnCandidates, 2 + accurate, silenceThreshold, voicingThreshold, octaveCost, octaveJumpCost, voicedUnvoicedCost, ceiling); } /* End of file Sound_to_Pitch.cpp */ sources_5316/fon/TextGridEditor_enums.h0000644000176700017670000000266610726353623017007 0ustar paulpaul/* TextGridEditor_enums.h * * Copyright (C) 1992-2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/07 */ enums_begin (kTextGridEditor_showNumberOf, 1) enums_add (kTextGridEditor_showNumberOf, 1, NOTHING, L"nothing") enums_add (kTextGridEditor_showNumberOf, 2, INTERVALS_OR_POINTS, L"intervals or points") enums_add (kTextGridEditor_showNumberOf, 3, NONEMPTY_INTERVALS_OR_POINTS, L"non-empty intervals or points") /* For reading old preferences files: */ enums_alt (kTextGridEditor_showNumberOf, NOTHING, L"1") enums_alt (kTextGridEditor_showNumberOf, INTERVALS_OR_POINTS, L"2") enums_alt (kTextGridEditor_showNumberOf, NONEMPTY_INTERVALS_OR_POINTS, L"3") enums_end (kTextGridEditor_showNumberOf, 3, INTERVALS_OR_POINTS) /* End of file TextGridEditor_enums.h */ sources_5316/fon/Formant.h0000644000176700017670000001110111621705642014262 0ustar paulpaul#ifndef _Formant_h_ #define _Formant_h_ /* Formant.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Matrix.h" #include "Table.h" #include "Interpreter_decl.h" #include "Formant_def.h" oo_CLASS_CREATE (Formant, Sampled); Formant Formant_create (double tmin, double tmax, long nt, double dt, double t1, int maxnFormants); /* Function: return a new instance of Formant, or NULL if out of memory. Preconditions: nt >= 1; dt > 0.0; maxnFormants >= 1; Postconditions: my xmin = tmin; my xmax = tmax; my nx = nt; my dx = dt; my x1 = t1; my maximumNumberOfPairs == maxnFormants; my frames [1..nt]. intensity == 0.0; my frames [1..nt]. numberOfPairs == 0; my frames [1..nt]. formants [1..maxnFormants] = 0.0; my frames [1..nt]. bandwidths [1..maxnFormants] = 0.0; */ long Formant_getMinNumFormants (Formant me); long Formant_getMaxNumFormants (Formant me); double Formant_getValueAtTime (Formant me, int iformant, double time, int bark); double Formant_getBandwidthAtTime (Formant me, int iformant, double time, int bark); void Formant_getExtrema (Formant me, int iformant, double tmin, double tmax, double *fmin, double *fmax); void Formant_getMinimumAndTime (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate, double *return_minimum, double *return_timeOfMinimum); void Formant_getMaximumAndTime (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate, double *return_maximum, double *return_timeOfMaximum); double Formant_getMinimum (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate); double Formant_getMaximum (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate); double Formant_getTimeOfMaximum (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate); double Formant_getTimeOfMinimum (Formant me, int iformant, double tmin, double tmax, int bark, int interpolate); double Formant_getQuantile (Formant me, int iformant, double quantile, double tmin, double tmax, int bark); double Formant_getQuantileOfBandwidth (Formant me, int iformant, double quantile, double tmin, double tmax, int bark); double Formant_getMean (Formant me, int iformant, double tmin, double tmax, int bark); double Formant_getStandardDeviation (Formant me, int iformant, double tmin, double tmax, int bark); void Formant_sort (Formant me); void Formant_drawTracks (Formant me, Graphics g, double tmin, double tmax, double fmax, int garnish); void Formant_drawSpeckles_inside (Formant me, Graphics g, double tmin, double tmax, double fmin, double fmax, double suppress_dB, double dotSize); void Formant_drawSpeckles (Formant me, Graphics g, double tmin, double tmax, double fmax, double suppress_dB, int garnish); void Formant_scatterPlot (Formant me, Graphics g, double tmin, double tmax, int iformant1, double fmin1, double fmax1, int iformant2, double fmin2, double fmax2, double size_mm, const wchar *mark, int garnish); Matrix Formant_to_Matrix (Formant me, int iformant); Matrix Formant_to_Matrix_bandwidths (Formant me, int iformant); void Formant_formula_frequencies (Formant me, const wchar *formula, Interpreter interpreter); void Formant_formula_bandwidths (Formant me, const wchar *formula, Interpreter interpreter); Formant Formant_tracker (Formant me, int numberOfTracks, double refF1, double refF2, double refF3, double refF4, double refF5, double dfCost, /* Per kHz. */ double bfCost, double octaveJumpCost); Table Formant_downto_Table (Formant me, bool includeFrameNumbers, bool includeTimes, int timeDecimals, bool includeIntensity, int intensityDecimals, bool includeNumberOfFormants, int frequencyDecimals, bool includeBandwidths); void Formant_list (Formant me, bool includeFrameNumbers, bool includeTimes, int timeDecimals, bool includeIntensity, int intensityDecimals, bool includeNumberOfFormants, int frequencyDecimals, bool includeBandwidths); /* End of file Formant.h */ #endif sources_5316/fon/Label.cpp0000644000176700017670000000766411621514446014251 0ustar paulpaul/* Label.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Label.h" Thing_implement (Autosegment, Function, 0); void structAutosegment :: v_copy (thou) { thouart (Autosegment); Autosegment_Parent :: v_copy (thee); if (name) Thing_setName (thee, name); } bool structAutosegment :: v_equal (thou) { thouart (Autosegment); if (! Autosegment_Parent :: v_equal (thee)) return false; if (name == NULL && thy name == NULL) return true; // shortcut: no names if (name == NULL || thy name == NULL) return false; return wcsequ (name, thy name); } static struct structData_Description theAutosegment_description [] = { { L"Autosegment", inheritwa, 0, sizeof (struct structAutosegment), L"Autosegment", & theClassInfo_Function }, { L"name", stringwa, Melder_offsetof (Autosegment, name), sizeof (wchar *) }, { 0 } }; Data_Description structAutosegment :: s_description = & theAutosegment_description [0]; Autosegment Autosegment_create (double tmin, double tmax, const wchar *label) { try { autoAutosegment me = Thing_new (Autosegment); Function_init (me.peek(), tmin, tmax); if (label != NULL) { Thing_setName (me.peek(), label); therror } return me.transfer(); } catch (MelderError) { Melder_throw ("Autosegment not created."); } } int structTier :: compare (I, thou) { iam (Function); thouart (Function); if (my xmin < thy xmin) return -1; if (my xmin > thy xmin) return 1; if (my xmax < thy xmax) return -1; if (my xmax > thy xmax) return 1; return 0; } Thing_implement (Tier, Sorted, 0); void Tier_init (I, long initialCapacity) { iam (Tier); Sorted_init (me, classAutosegment, initialCapacity); Collection_addItem (me, Autosegment_create (-1e30, 1e30, NULL)); } Tier Tier_create (long initialCapacity) { try { autoTier me = Thing_new (Tier); Tier_init (me.peek(), initialCapacity); return me.transfer(); } catch (MelderError) { Melder_throw ("Tier not created."); } } long Tier_timeToIndex (Tier me, double t) { for (long i = 1; i <= my size; i ++) { Autosegment interval = (Autosegment) my item [i]; if (t >= interval -> xmin && t < interval -> xmax) return i; } return 0; /* Empty tier or very large t. */ } Thing_implement (Label, Ordered, 0); void Label_init (I, long initialNumberOfTiers) { iam (Label); Ordered_init (me, classTier, initialNumberOfTiers); for (long i = 1; i <= initialNumberOfTiers; i ++) { Collection_addItem (me, Tier_create (10)); } } Label Label_create (long initialNumberOfTiers) { try { autoLabel me = Thing_new (Label); Label_init (me.peek(), initialNumberOfTiers); return me.transfer(); } catch (MelderError) { Melder_throw ("Label not created."); } } void Label_addTier (Label me) { Collection_addItem (me, Tier_create (10)); } void Label_suggestDomain (Label me, double *tmin, double *tmax) { *tmin = 0.0; *tmax = 0.0; for (int itier = 1; itier <= my size; itier ++) { Tier tier = (Tier) my item [itier]; if (tier -> size) { Autosegment seg = (Autosegment) tier -> item [1]; if (seg -> xmin <= *tmin) { if (seg -> name && seg -> name [0]) *tmin = seg -> xmin - 1.0; else *tmin = seg -> xmin; } seg = (Autosegment) tier -> item [tier -> size]; if (seg -> xmax >= *tmax) *tmax = seg -> xmax; } } *tmax += 1.0; } /* End of file Label.cpp */ sources_5316/fon/SoundEditor.cpp0000644000176700017670000004066111701624700015455 0ustar paulpaul/* SoundEditor.cpp * * Copyright (C) 1992-2011 Paul Boersma, 2007 Erez Volk (FLAC support) * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "SoundEditor.h" #include "Sound_and_Spectrogram.h" #include "Pitch.h" #include "Preferences.h" #include "EditorM.h" Thing_implement (SoundEditor, TimeSoundAnalysisEditor, 0); /********** METHODS **********/ void structSoundEditor :: v_dataChanged () { Sound sound = (Sound) data; Melder_assert (sound != NULL); // LongSound objects should not get v_dataChanged messages Matrix_getWindowExtrema (sound, 1, sound -> nx, 1, sound -> ny, & this -> sound.minimum, & this -> sound.maximum); // BUG unreadable v_destroy_analysis (); SoundEditor_Parent :: v_dataChanged (); } /***** EDIT MENU *****/ static void menu_cb_Copy (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); try { /* * Create without change. */ autoSound publish = my longSound.data ? LongSound_extractPart ((LongSound) my data, my startSelection, my endSelection, FALSE) : Sound_extractPart ((Sound) my data, my startSelection, my endSelection, kSound_windowShape_RECTANGULAR, 1.0, FALSE); /* * Change without error. */ forget (Sound_clipboard); Sound_clipboard = publish.transfer(); } catch (MelderError) { Melder_throw ("Sound selection not copied to clipboard."); } } static void menu_cb_Cut (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); try { Sound sound = (Sound) my data; long first, last, selectionNumberOfSamples = Sampled_getWindowSamples (sound, my startSelection, my endSelection, & first, & last); long oldNumberOfSamples = sound -> nx; long newNumberOfSamples = oldNumberOfSamples - selectionNumberOfSamples; if (newNumberOfSamples < 1) Melder_throw ("You cannot cut all of the signal away,\n" "because you cannot create a Sound with 0 samples.\n" "You could consider using Copy instead."); if (selectionNumberOfSamples) { double **oldData = sound -> z; /* * Create without change. */ autoSound publish = Sound_create (sound -> ny, 0.0, selectionNumberOfSamples * sound -> dx, selectionNumberOfSamples, sound -> dx, 0.5 * sound -> dx); for (long channel = 1; channel <= sound -> ny; channel ++) { long j = 0; for (long i = first; i <= last; i ++) { publish -> z [channel] [++ j] = oldData [channel] [i]; } } autoNUMmatrix newData (1, sound -> ny, 1, newNumberOfSamples); for (long channel = 1; channel <= sound -> ny; channel ++) { long j = 0; for (long i = 1; i < first; i ++) { newData [channel] [++ j] = oldData [channel] [i]; } for (long i = last + 1; i <= oldNumberOfSamples; i ++) { newData [channel] [++ j] = oldData [channel] [i]; } } Editor_save (me, L"Cut"); /* * Change without error. */ NUMmatrix_free (oldData, 1, 1); sound -> xmin = 0.0; sound -> xmax = newNumberOfSamples * sound -> dx; sound -> nx = newNumberOfSamples; sound -> x1 = 0.5 * sound -> dx; sound -> z = newData.transfer(); forget (Sound_clipboard); Sound_clipboard = publish.transfer(); /* Start updating the markers of the FunctionEditor, respecting the invariants. */ my tmin = sound -> xmin; my tmax = sound -> xmax; /* Collapse the selection, */ /* so that the Cut operation can immediately be undone by a Paste. */ /* The exact position will be half-way in between two samples. */ my startSelection = my endSelection = sound -> xmin + (first - 1) * sound -> dx; /* Update the window. */ { double t1 = (first - 1) * sound -> dx; double t2 = last * sound -> dx; double windowLength = my endWindow - my startWindow; /* > 0 */ if (t1 > my startWindow) if (t2 < my endWindow) my startWindow -= 0.5 * (t2 - t1); else (void) 0; else if (t2 < my endWindow) my startWindow -= t2 - t1; else /* Cut overlaps entire window: centre. */ my startWindow = my startSelection - 0.5 * windowLength; my endWindow = my startWindow + windowLength; /* First try. */ if (my endWindow > my tmax) { my startWindow -= my endWindow - my tmax; /* 2nd try. */ if (my startWindow < my tmin) my startWindow = my tmin; /* Third try. */ my endWindow = my tmax; /* Second try. */ } else if (my startWindow < my tmin) { my endWindow -= my startWindow - my tmin; /* Second try. */ if (my endWindow > my tmax) my endWindow = my tmax; /* Third try. */ my startWindow = my tmin; /* Second try. */ } } /* Force FunctionEditor to show changes. */ Matrix_getWindowExtrema (sound, 1, sound -> nx, 1, sound -> ny, & my sound.minimum, & my sound.maximum); my v_destroy_analysis (); FunctionEditor_ungroup (me); FunctionEditor_marksChanged (me); my broadcastDataChanged (); } else { Melder_warning (L"No samples selected."); } } catch (MelderError) { Melder_throw ("Sound selection not cut to clipboard."); } } static void menu_cb_Paste (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); Sound sound = (Sound) my data; long leftSample = Sampled_xToLowIndex (sound, my endSelection); long oldNumberOfSamples = sound -> nx, newNumberOfSamples; double **oldData = sound -> z; if (! Sound_clipboard) { Melder_warning (L"Clipboard is empty; nothing pasted."); return; } if (Sound_clipboard -> ny != sound -> ny) Melder_throw ("Cannot paste, because\n" "the number of channels of the clipboard is not equal to\n" "the number of channels of the edited sound."); if (Sound_clipboard -> dx != sound -> dx) Melder_throw ("Cannot paste, because\n" "the sampling frequency of the clipboard is not equal to\n" "the sampling frequency of the edited sound."); if (leftSample < 0) leftSample = 0; if (leftSample > oldNumberOfSamples) leftSample = oldNumberOfSamples; newNumberOfSamples = oldNumberOfSamples + Sound_clipboard -> nx; /* * Check without change. */ autoNUMmatrix newData (1, sound -> ny, 1, newNumberOfSamples); for (long channel = 1; channel <= sound -> ny; channel ++) { long j = 0; for (long i = 1; i <= leftSample; i ++) { newData [channel] [++ j] = oldData [channel] [i]; } for (long i = 1; i <= Sound_clipboard -> nx; i ++) { newData [channel] [++ j] = Sound_clipboard -> z [channel] [i]; } for (long i = leftSample + 1; i <= oldNumberOfSamples; i ++) { newData [channel] [++ j] = oldData [channel] [i]; } } Editor_save (me, L"Paste"); /* * Change without error. */ NUMmatrix_free (oldData, 1, 1); sound -> xmin = 0.0; sound -> xmax = newNumberOfSamples * sound -> dx; sound -> nx = newNumberOfSamples; sound -> x1 = 0.5 * sound -> dx; sound -> z = newData.transfer(); /* Start updating the markers of the FunctionEditor, respecting the invariants. */ my tmin = sound -> xmin; my tmax = sound -> xmax; my startSelection = leftSample * sound -> dx; my endSelection = (leftSample + Sound_clipboard -> nx) * sound -> dx; /* Force FunctionEditor to show changes. */ Matrix_getWindowExtrema (sound, 1, sound -> nx, 1, sound -> ny, & my sound.minimum, & my sound.maximum); my v_destroy_analysis (); FunctionEditor_ungroup (me); FunctionEditor_marksChanged (me); my broadcastDataChanged (); } static void menu_cb_SetSelectionToZero (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); Sound sound = (Sound) my data; long first, last; Sampled_getWindowSamples (sound, my startSelection, my endSelection, & first, & last); Editor_save (me, L"Set to zero"); for (long channel = 1; channel <= sound -> ny; channel ++) { for (long i = first; i <= last; i ++) { sound -> z [channel] [i] = 0.0; } } my v_destroy_analysis (); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_ReverseSelection (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); Editor_save (me, L"Reverse selection"); Sound_reverse ((Sound) my data, my startSelection, my endSelection); my v_destroy_analysis (); FunctionEditor_redraw (me); my broadcastDataChanged (); } /***** SELECT MENU *****/ static void menu_cb_MoveCursorToZero (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); double zero = Sound_getNearestZeroCrossing ((Sound) my data, 0.5 * (my startSelection + my endSelection), 1); // STEREO BUG if (NUMdefined (zero)) { my startSelection = my endSelection = zero; FunctionEditor_marksChanged (me); } } static void menu_cb_MoveBtoZero (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); double zero = Sound_getNearestZeroCrossing ((Sound) my data, my startSelection, 1); // STEREO BUG if (NUMdefined (zero)) { my startSelection = zero; if (my startSelection > my endSelection) { double dummy = my startSelection; my startSelection = my endSelection; my endSelection = dummy; } FunctionEditor_marksChanged (me); } } static void menu_cb_MoveEtoZero (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); double zero = Sound_getNearestZeroCrossing ((Sound) my data, my endSelection, 1); // STEREO BUG if (NUMdefined (zero)) { my endSelection = zero; if (my startSelection > my endSelection) { double dummy = my startSelection; my startSelection = my endSelection; my endSelection = dummy; } FunctionEditor_marksChanged (me); } } /***** HELP MENU *****/ static void menu_cb_SoundEditorHelp (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); Melder_help (L"SoundEditor"); } static void menu_cb_LongSoundEditorHelp (EDITOR_ARGS) { EDITOR_IAM (SoundEditor); Melder_help (L"LongSoundEditor"); } void structSoundEditor :: v_createMenus () { SoundEditor_Parent :: v_createMenus (); Melder_assert (data != NULL); Melder_assert (sound.data != NULL || longSound.data != NULL); Editor_addCommand (this, L"Edit", L"-- cut copy paste --", 0, NULL); if (sound.data) cutButton = Editor_addCommand (this, L"Edit", L"Cut", 'X', menu_cb_Cut); copyButton = Editor_addCommand (this, L"Edit", L"Copy selection to Sound clipboard", 'C', menu_cb_Copy); if (sound.data) pasteButton = Editor_addCommand (this, L"Edit", L"Paste after selection", 'V', menu_cb_Paste); if (sound.data) { Editor_addCommand (this, L"Edit", L"-- zero --", 0, NULL); zeroButton = Editor_addCommand (this, L"Edit", L"Set selection to zero", 0, menu_cb_SetSelectionToZero); reverseButton = Editor_addCommand (this, L"Edit", L"Reverse selection", 'R', menu_cb_ReverseSelection); } if (sound.data) { Editor_addCommand (this, L"Select", L"-- move to zero --", 0, 0); Editor_addCommand (this, L"Select", L"Move start of selection to nearest zero crossing", ',', menu_cb_MoveBtoZero); Editor_addCommand (this, L"Select", L"Move begin of selection to nearest zero crossing", Editor_HIDDEN, menu_cb_MoveBtoZero); Editor_addCommand (this, L"Select", L"Move cursor to nearest zero crossing", '0', menu_cb_MoveCursorToZero); Editor_addCommand (this, L"Select", L"Move end of selection to nearest zero crossing", '.', menu_cb_MoveEtoZero); } v_createMenus_analysis (); } void structSoundEditor :: v_createHelpMenuItems (EditorMenu menu) { SoundEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"SoundEditor help", '?', menu_cb_SoundEditorHelp); EditorMenu_addCommand (menu, L"LongSoundEditor help", 0, menu_cb_LongSoundEditorHelp); } /********** UPDATE **********/ void structSoundEditor :: v_prepareDraw () { if (longSound.data) { try { LongSound_haveWindow (longSound.data, startWindow, endWindow); } catch (MelderError) { Melder_clearError (); } } } void structSoundEditor :: v_draw () { Sampled data = (Sampled) this -> data; Graphics_Viewport viewport; bool showAnalysis = spectrogram.show || pitch.show || intensity.show || formant.show; Melder_assert (data != NULL); Melder_assert (sound.data != NULL || longSound.data != NULL); /* * We check beforehand whether the window fits the LongSound buffer. */ if (longSound.data && endWindow - startWindow > longSound.data -> bufferLength) { Graphics_setColour (graphics, Graphics_WHITE); Graphics_setWindow (graphics, 0, 1, 0, 1); Graphics_fillRectangle (graphics, 0, 1, 0, 1); Graphics_setColour (graphics, Graphics_BLACK); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_BOTTOM); Graphics_text3 (graphics, 0.5, 0.5, L"(window longer than ", Melder_float (Melder_single (longSound.data -> bufferLength)), L" seconds)"); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_TOP); Graphics_text1 (graphics, 0.5, 0.5, L"(zoom in to see the samples)"); return; } /* Draw sound. */ if (showAnalysis) viewport = Graphics_insetViewport (graphics, 0, 1, 0.5, 1); Graphics_setColour (graphics, Graphics_WHITE); Graphics_setWindow (graphics, 0, 1, 0, 1); Graphics_fillRectangle (graphics, 0, 1, 0, 1); TimeSoundEditor_draw_sound (this, sound.minimum, sound.maximum); Graphics_flushWs (graphics); if (showAnalysis) Graphics_resetViewport (graphics, viewport); /* Draw analyses. */ if (showAnalysis) { /* Draw spectrogram, pitch, formants. */ viewport = Graphics_insetViewport (graphics, 0, 1, 0, 0.5); v_draw_analysis (); Graphics_flushWs (graphics); Graphics_resetViewport (graphics, viewport); } /* Draw pulses. */ if (pulses.show) { if (showAnalysis) viewport = Graphics_insetViewport (graphics, 0, 1, 0.5, 1); v_draw_analysis_pulses (); TimeSoundEditor_draw_sound (this, sound.minimum, sound.maximum); // second time, partially across the pulses Graphics_flushWs (graphics); if (showAnalysis) Graphics_resetViewport (graphics, viewport); } /* Update buttons. */ long first, last; long selectedSamples = Sampled_getWindowSamples (data, startSelection, endSelection, & first, & last); v_updateMenuItems_file (); if (sound.data) { GuiObject_setSensitive (cutButton, selectedSamples != 0 && selectedSamples < sound.data -> nx); GuiObject_setSensitive (copyButton, selectedSamples != 0); GuiObject_setSensitive (zeroButton, selectedSamples != 0); GuiObject_setSensitive (reverseButton, selectedSamples != 0); } } void structSoundEditor :: v_play (double a_tmin, double a_tmax) { if (longSound.data) LongSound_playPart ((LongSound) data, a_tmin, a_tmax, theFunctionEditor_playCallback, this); else Sound_playPart ((Sound) data, a_tmin, a_tmax, theFunctionEditor_playCallback, this); } int structSoundEditor :: v_click (double xWC, double yWC, bool shiftKeyPressed) { if ((spectrogram.show || formant.show) && yWC < 0.5 && xWC > startWindow && xWC < endWindow) { spectrogram.cursor = spectrogram.viewFrom + 2 * yWC * (spectrogram.viewTo - spectrogram.viewFrom); } return SoundEditor_Parent :: v_click (xWC, yWC, shiftKeyPressed); // drag & update } void structSoundEditor :: v_highlightSelection (double left, double right, double bottom, double top) { if (spectrogram.show) Graphics_highlight (graphics, left, right, 0.5 * (bottom + top), top); else Graphics_highlight (graphics, left, right, bottom, top); } void structSoundEditor :: v_unhighlightSelection (double left, double right, double bottom, double top) { if (spectrogram.show) Graphics_unhighlight (graphics, left, right, 0.5 * (bottom + top), top); else Graphics_unhighlight (graphics, left, right, bottom, top); } void structSoundEditor :: f_init (GuiObject parent, const wchar *title, Sampled data) { /* * my longSound.data or my sound.data have to be set before we call FunctionEditor_init, * because createMenus expect that one of them is not NULL. */ TimeSoundAnalysisEditor_init (this, parent, title, data, data, false); therror if (this -> longSound.data && this -> endWindow - this -> startWindow > 30.0) { this -> endWindow = this -> startWindow + 30.0; if (this -> startWindow == this -> tmin) this -> startSelection = this -> endSelection = 0.5 * (this -> startWindow + this -> endWindow); FunctionEditor_marksChanged (this); } } SoundEditor SoundEditor_create (GuiObject parent, const wchar *title, Sampled data) { Melder_assert (data != NULL); try { autoSoundEditor me = Thing_new (SoundEditor); me -> f_init (parent, title, data); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound window not created."); } } /* End of file SoundEditor.cpp */ sources_5316/fon/Spectrum_and_Spectrogram.h0000644000176700017670000000365311614424562017664 0ustar paulpaul/* Spectrum_and_Spectrogram.h * * Copyright (C) 1992-2011 David Weenink & Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Spectrum.h" #include "Spectrogram.h" Spectrum Spectrogram_to_Spectrum (I, double time); /* Function: Create a time slice from the Spectrogram at the time nearest to 'time'. Return NULL in case of failure (no memory). Postconditions: result -> xmin == my ymin; // Lowest frequency; often 0. result -> xmax == my ymax; // Highest frequency. result -> nx == my ny; // Number of frequency bands. result -> dx == my dy; // Frequency step. result -> x1 == my y1; // Centre of first frequency band. for (iy = 1; iy <= my ny; iy ++) { result -> z [1] [i] == sqrt (my z [i] ['time']); result -> z [2] [i] == 0.0; } */ Spectrogram Spectrum_to_Spectrogram (I); /* Function: Create a Spectrogram with one time slice from the Spectrum. Return NULL in case of failure (no memory). Postconditions: thy xmin = 0.0; thy ymin == my xmin; thy xmax = 1.0; thy ymax == my xmax; thy nx == 1; thy ny == my nx; thy dx == 1.0; thy dy == my dx; thy x1 == 0.5; thy y1 == my x1; for (i = 1; i <= my nx; i ++) thy z [i] [1] == (my z [1] [i]) ^ 2 + (my z [2] [i]) ^ 2; */ /* End of file Spectrum_and_Spectrogram.h */ sources_5316/fon/Polygon.h0000644000176700017670000000510111625730235014306 0ustar paulpaul#ifndef _Polygon_h_ #define _Polygon_h_ /* Polygon.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Data.h" #include "Graphics.h" #include "Polygon_def.h" oo_CLASS_CREATE (Polygon, Data); Polygon Polygon_create (long numberOfPoints); /* Function: create a new instance of Polygon. Return value: a pointer to the newly created object, or NULL in case of failure. Precondition: numberOfPoints >= 1; Failure: Out of memory. Postconditions: result -> numberOfPoints == numberOfPoints; result -> x [1..numberOfPoints] == 0.0; result -> y [1..numberOfPoints] == 0.0; */ void Polygon_randomize (Polygon me); /* Randomize the order of the points. */ double Polygon_perimeter (Polygon me); /* Return the length of the closed path through all points. */ void Polygon_salesperson (Polygon me, long numberOfIterations); /* Function: change the order of the points in such a way that it defines the shortest closed path. Preconditions: me != NULL; numberOfIterations >= 1; Postconditions: my numberOfPoints == my old numberOfPoints; Polygon_perimeter (me) <= old Polygon_perimeter (me); */ /*** Drawing routines. ***/ void Polygon_draw (Polygon me, Graphics g, double xmin, double xmax, double ymin, double ymax); void Polygon_drawClosed (Polygon me, Graphics g, double xmin, double xmax, double ymin, double ymax); void Polygon_paint (Polygon me, Graphics g, Graphics_Colour colour, double xmin, double xmax, double ymin, double ymax); void Polygon_drawCircles (Polygon me, Graphics g, double xmin, double xmax, double ymin, double ymax, double diameter_mm); void Polygon_paintCircles (Polygon me, Graphics g, double xmin, double xmax, double ymin, double ymax, double diameter_mm); void Polygons_drawConnection (Polygon me, Polygon thee, Graphics g, double xmin, double xmax, double ymin, double ymax, int hasArrow, double relativeLength); /* End of file Polygon.h */ #endif sources_5316/fon/Pitch.h0000644000176700017670000001604311625721240013731 0ustar paulpaul#ifndef _Pitch_h_ #define _Pitch_h_ /* Pitch.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sampled.h" #include "Graphics.h" #include "Interpreter_decl.h" #include "Pitch_enums.h" #include "Pitch_def.h" oo_CLASS_CREATE (Pitch, Sampled); Pitch Pitch_create (double tmin, double tmax, long nt, double dt, double t1, double ceiling, int maxnCandidates); /* Function: create an empty pitch contour (voiceless), or NULL if out of memory. Preconditions: tmax > tmin; nt >= 1; dt > 0.0; maxnCandidates >= 2; Postconditions: my xmin == tmin; my xmax == tmax; my nx == nt; my dx == dt; my x1 == t1; my ceiling == ceiling; my maxnCandidates == maxnCandidates; my frame [1..nt]. nCandidates == 1; my frame [1..nt]. candidate [1]. frequency == 0.0; // unvoiced my frame [1..nt]. candidate [1]. strength == 0.0; // aperiodic my frame [1..nt]. intensity == 0.0; // silent */ void Pitch_Frame_init (Pitch_Frame me, int nCandidates); /* Function: create space for a number of candidates; space already there is disposed of. Preconditions: nCandidates >= 1; Postconditions: my nCandidates == nCandidates; my candidate [1..nCandidates]. frequency == 0.0; // unvoiced my candidate [1..nCandidates]. strength == 0.0; // aperiodic my intensity == 0.0; // silent */ bool Pitch_isVoiced_i (Pitch me, long index); /* Is the frame 'index' voiced? A frame is considered voiced if the frequency of its first candidate is greater than 0.0 but less than my ceiling. Precondition: index >= 1 && index <= my nx; */ bool Pitch_isVoiced_t (Pitch me, double t); /* Are you voiced at time 't'? The answer is TRUE iff 't' lies within a voiced frame. */ #define Pitch_LEVEL_FREQUENCY 1 #define Pitch_LEVEL_STRENGTH 2 #define Pitch_STRENGTH_UNIT_min 0 #define Pitch_STRENGTH_UNIT_AUTOCORRELATION 0 #define Pitch_STRENGTH_UNIT_NOISE_HARMONICS_RATIO 1 #define Pitch_STRENGTH_UNIT_HARMONICS_NOISE_DB 2 #define Pitch_STRENGTH_UNIT_max 2 #define Pitch_NEAREST 0 #define Pitch_LINEAR 1 double Pitch_getValueAtTime (Pitch me, double time, int unit, int interpolate); double Pitch_getStrengthAtTime (Pitch me, double time, int unit, int interpolate); long Pitch_countVoicedFrames (Pitch me); double Pitch_getMean (Pitch me, double tmin, double tmax, int unit); double Pitch_getMeanStrength (Pitch me, double tmin, double tmax, int unit); double Pitch_getQuantile (Pitch me, double tmin, double tmax, double quantile, int unit); double Pitch_getStandardDeviation (Pitch me, double tmin, double tmax, int unit); void Pitch_getMaximumAndTime (Pitch me, double tmin, double tmax, int unit, int interpolate, double *return_maximum, double *return_timeOfMaximum); double Pitch_getMaximum (Pitch me, double tmin, double tmax, int unit, int interpolate); double Pitch_getTimeOfMaximum (Pitch me, double tmin, double tmax, int unit, int interpolate); void Pitch_getMinimumAndTime (Pitch me, double tmin, double tmax, int unit, int interpolate, double *return_minimum, double *return_timeOfMinimum); double Pitch_getMinimum (Pitch me, double tmin, double tmax, int unit, int interpolate); double Pitch_getTimeOfMinimum (Pitch me, double tmin, double tmax, int unit, int interpolate); int Pitch_getMaxnCandidates (Pitch me); /* Returns the largest number of candidates actually attested in a frame. */ void Pitch_setCeiling (Pitch me, double ceiling); /* Postcondition: my ceiling = ceiling; */ void Pitch_pathFinder (Pitch me, double silenceThreshold, double voicingThreshold, double octaveCost, double octaveJumpCost, double voicedUnvoicedCost, double ceiling, int pullFormants); /* Drawing methods. */ #define Pitch_speckle_NO FALSE #define Pitch_speckle_YES TRUE void Pitch_drawInside (Pitch me, Graphics g, double tmin, double tmax, double fmin, double fmax, int speckle, int yscale); void Pitch_draw (Pitch me, Graphics g, double tmin, double tmax, double fmin, double fmax, int garnish, int speckle, int yscale); /* draw a pitch contour into a Graphics. If tmax <= tmin, draw whole time domain. */ void Pitch_difference (Pitch me, Pitch thee); /* give information about frames that are different in me and thee. */ long Pitch_getMeanAbsSlope_hertz (Pitch me, double *slope); long Pitch_getMeanAbsSlope_mel (Pitch me, double *slope); long Pitch_getMeanAbsSlope_semitones (Pitch me, double *slope); long Pitch_getMeanAbsSlope_erb (Pitch me, double *slope); long Pitch_getMeanAbsSlope_noOctave (Pitch me, double *slope); /* The value returned is the number of voiced frames (nVoiced); this signals if the values are valid: 'value', 'minimum', 'maximum', and 'mean' are valid if nVoiced >= 1; 'variance' and 'slope' are valid if nVoiced >= 2. Invalid variables are always set to 0.0. 'minimum', 'maximum', 'mean', and 'variance' may be NULL. */ Pitch Pitch_killOctaveJumps (Pitch me); /* Add octave jumps so that every pitch step, including those across unvoiced frames, does not exceed 1/2 octave. Postcondition: result -> ceiling = my ceiling * 2; */ Pitch Pitch_interpolate (Pitch me); /* Interpolate the pitch values of unvoiced frames. */ /* No extrapolation beyond first and last voiced frames. */ Pitch Pitch_subtractLinearFit (Pitch me, int unit); Pitch Pitch_smooth (Pitch me, double bandWidth); /* Smoothing by convolution with Gaussian curve. Time domain: exp (- (pi t bandWidth) ^ 2) down to 8.5 % for t = +- 0.5/bandWidth Frequency domain: exp (- (f / bandWidth) ^ 2) down to 1/e for f = +- bandWidth Example: if bandWidth = 10 Hz, then the Gaussian curve has a 8.5% duration of 0.1 s, and a 1/e low-pass point of 10 Hz. Algorithm: Interpolation of pitch at internal unvoiced parts. Zeroth-degree extrapolation at edges (duration triples). FFT; multiply by Gaussian; inverse FFT. Cut back to normal duration. Undo interpolation. */ void Pitch_step (Pitch me, double step, double precision, double tmin, double tmax); /* Instead of the currently chosen candidate, choose the candidate with another ("target") frequency, determined by 'step'. E.g., for an upward octave jump, 'step' is 2. Only consider frequencies between (1 - precision) * targetFrequency and (1 - precision) * targetFrequency. Take the candidate nearest to targetFrequency, as long as that candidate is in between 0 and my ceiling. */ void Pitch_formula (Pitch me, const wchar *formula, Interpreter interpreter); /* End of file Pitch.h */ #endif sources_5316/fon/TimeSoundEditor.h0000644000176700017670000000475711724701574015761 0ustar paulpaul#ifndef _TimeSoundEditor_h_ #define _TimeSoundEditor_h_ /* TimeSoundEditor.h * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "FunctionEditor.h" #include "Sound.h" #include "LongSound.h" struct TimeSoundEditor_sound { /* KEEP IN SYNC WITH PREFS. */ Sound data; bool autoscaling; double minimum, maximum; long channelOffset; }; Thing_define (TimeSoundEditor, FunctionEditor) { // new data: public: bool ownSound; struct TimeSoundEditor_sound sound; struct { LongSound data; } longSound; GuiObject drawButton, publishButton, publishPreserveButton, publishWindowButton; GuiObject writeAiffButton, d_saveAs24BitWavButton, d_saveAs32BitWavButton, writeAifcButton, writeWavButton, writeNextSunButton, writeNistButton, writeFlacButton; // overridden methods: virtual void v_destroy (); virtual void v_info (); virtual void v_createMenuItems_file (EditorMenu menu); virtual void v_createMenuItems_query_info (EditorMenu menu); virtual void v_createMenuItems_file_draw (EditorMenu menu); virtual void v_createMenuItems_file_extract (EditorMenu menu); virtual void v_createMenuItems_file_write (EditorMenu menu); virtual void v_createMenuItems_view (EditorMenu menu); virtual int v_click (double xbegin, double ybegin, bool shiftKeyPressed); // catch channel scrolling // new methods: virtual void v_createMenuItems_view_sound (EditorMenu menu); virtual void v_updateMenuItems_file (); virtual const wchar * v_getChannelName (long channelNumber) { (void) channelNumber; return NULL; } }; void TimeSoundEditor_prefs (void); void TimeSoundEditor_init (TimeSoundEditor me, GuiObject parent, const wchar *title, Function data, Sampled sound, bool ownSound); void TimeSoundEditor_draw_sound (TimeSoundEditor me, double globalMinimum, double globalMaximum); /* End of file TimeSoundEditor.h */ #endif sources_5316/fon/Formant_def.h0000644000176700017670000000336511630250410015101 0ustar paulpaul/* Formant_def.h * * Copyright (C) 1992-2002 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Formant_Formant oo_DEFINE_STRUCT (Formant_Formant) #if oo_READING if (localVersion <= 1) { oo_FLOAT (frequency) oo_FLOAT (bandwidth) } else { oo_DOUBLE (frequency) oo_DOUBLE (bandwidth) } #else oo_DOUBLE (frequency) oo_DOUBLE (bandwidth) #endif oo_END_STRUCT (Formant_Formant) #undef ooSTRUCT #define ooSTRUCT Formant_Frame oo_DEFINE_STRUCT (Formant_Frame) oo_FROM (1) oo_DOUBLE (intensity) oo_ENDFROM oo_INT (nFormants) oo_STRUCT_VECTOR (Formant_Formant, formant, nFormants) oo_END_STRUCT (Formant_Frame) #undef ooSTRUCT #define ooSTRUCT Formant oo_DEFINE_CLASS (Formant, Sampled) oo_INT (maxnFormants) oo_STRUCT_VECTOR (Formant_Frame, d_frames, nx) #if oo_DECLARING // overridden methods: virtual void v_info (); virtual int v_domainQuantity () { return MelderQuantity_TIME_SECONDS; } virtual double v_getValueAtSample (long iframe, long which, int units); #endif oo_END_CLASS (Formant) #undef ooSTRUCT /* End of file Formant_def.h */ sources_5316/fon/Sound_audio.cpp0000644000176700017670000005106311747264254015503 0ustar paulpaul/* Sound_audio.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2003/09/14 Sound_recordFixedTime records in stereo if mono is not available * pb 2003/12/06 use sys/soundcard.h instead of linux/soundcard.h for FreeBSD compatibility * pb 2005/04/24 Sound_recordFixedTime: Firewire Solo 1264 * pb 2005/06/16 removed previous change (System Preferences handles this) * pb 2005/10/13 edition for OpenBSD * pb 2006/10/28 erased MacOS 9 stuff * pb 2006/12/20 Sound_playPart and Sound_play allow stereo * pb 2006/12/30 Sound_playPart and Sound_play allow better stereo * pb 2007/01/07 PortAudio * Stefan de Konink 2007/12/02 big-endian Linux * pb 2008/01/19 double * pb 2008/07/07 split zero padding between silenceBefore and silenceAfter * fb 2010/02/26 fix resource leak fd_mixer in case of error during init * pb 2010/04/20 Sound_recordFixedTime for Linux: repair * pb 2010/11/02 Sound_recordFixedTime for Linux: repair bug from 1998 * pb 2011/06/07 C++ */ #include #ifdef linux #define DEV_AUDIO "/dev/dsp" #else #define DEV_AUDIO "/dev/audio" #endif /* * In the new Mac SDK/ CodeWarrior, the following must be included before and ...??? */ #include "Sound.h" #include "Preferences.h" #include "../external/portaudio/portaudio.h" #if defined (macintosh) #include "macport_on.h" #include #include "pa_mac_core.h" #include "macport_off.h" #elif defined (_WIN32) #include "winport_on.h" #include #include #include "winport_off.h" #elif defined (linux) #include #if defined (__OpenBSD__) || defined (__NetBSD__) #include #else #include #endif #include /* ioctl */ #include /* open write close read */ #else #include #endif static int ulaw2linear [] = { -32124, -31100, -30076, -29052, -28028, -27004, -25980, -24956, -23932, -22908, -21884, -20860, -19836, -18812, -17788, -16764, -15996, -15484, -14972, -14460, -13948, -13436, -12924, -12412, -11900, -11388, -10876, -10364, -9852, -9340, -8828, -8316, -7932, -7676, -7420, -7164, -6908, -6652, -6396, -6140, -5884, -5628, -5372, -5116, -4860, -4604, -4348, -4092, -3900, -3772, -3644, -3516, -3388, -3260, -3132, -3004, -2876, -2748, -2620, -2492, -2364, -2236, -2108, -1980, -1884, -1820, -1756, -1692, -1628, -1564, -1500, -1436, -1372, -1308, -1244, -1180, -1116, -1052, -988, -924, -876, -844, -812, -780, -748, -716, -684, -652, -620, -588, -556, -524, -492, -460, -428, -396, -372, -356, -340, -324, -308, -292, -276, -260, -244, -228, -212, -196, -180, -164, -148, -132, -120, -112, -104, -96, -88, -80, -72, -64, -56, -48, -40, -32, -24, -16, -8, 0, 32124, 31100, 30076, 29052, 28028, 27004, 25980, 24956, 23932, 22908, 21884, 20860, 19836, 18812, 17788, 16764, 15996, 15484, 14972, 14460, 13948, 13436, 12924, 12412, 11900, 11388, 10876, 10364, 9852, 9340, 8828, 8316, 7932, 7676, 7420, 7164, 6908, 6652, 6396, 6140, 5884, 5628, 5372, 5116, 4860, 4604, 4348, 4092, 3900, 3772, 3644, 3516, 3388, 3260, 3132, 3004, 2876, 2748, 2620, 2492, 2364, 2236, 2108, 1980, 1884, 1820, 1756, 1692, 1628, 1564, 1500, 1436, 1372, 1308, 1244, 1180, 1116, 1052, 988, 924, 876, 844, 812, 780, 748, 716, 684, 652, 620, 588, 556, 524, 492, 460, 428, 396, 372, 356, 340, 324, 308, 292, 276, 260, 244, 228, 212, 196, 180, 164, 148, 132, 120, 112, 104, 96, 88, 80, 72, 64, 56, 48, 40, 32, 24, 16, 8, 0 }; struct Sound_recordFixedTime_Info { long numberOfSamples, numberOfSamplesRead; short *buffer; }; static long getNumberOfSamplesRead (volatile struct Sound_recordFixedTime_Info *info) { volatile long numberOfSamplesRead = info -> numberOfSamplesRead; return numberOfSamplesRead; } static int portaudioStreamCallback ( const void *input, void *output, unsigned long frameCount, const PaStreamCallbackTimeInfo* timeInfo, PaStreamCallbackFlags statusFlags, void *void_info) { (void) output; (void) timeInfo; (void) statusFlags; struct Sound_recordFixedTime_Info *info = (struct Sound_recordFixedTime_Info *) void_info; unsigned long samplesLeft = info -> numberOfSamples - info -> numberOfSamplesRead; if (samplesLeft > 0) { unsigned long dsamples = samplesLeft > frameCount ? frameCount : samplesLeft; memcpy (info -> buffer + 1 + info -> numberOfSamplesRead, input, 2 * dsamples); info -> numberOfSamplesRead += dsamples; if (info -> numberOfSamplesRead >= info -> numberOfSamples) return paComplete; } else /*if (info -> numberOfSamplesRead >= info -> numberOfSamples)*/ { info -> numberOfSamplesRead = info -> numberOfSamples; return paComplete; } return paContinue; } Sound Sound_recordFixedTime (int inputSource, double gain, double balance, double sampleRate, double duration) { bool inputUsesPortAudio = MelderAudio_getInputUsesPortAudio (); PaStream *portaudioStream = NULL; #if defined (macintosh) long refNum; #elif defined (_WIN32) HWAVEIN hWaveIn = 0; #else int fd = -1; /* Other systems use stream I/O with a file descriptor. */ int fd_mixer = -1; #endif try { long numberOfSamples, i; int mulaw = FALSE; int can16bit = TRUE; int fakeMonoByStereo = FALSE; /* Will be set to TRUE for systems (like MacOS X) that do not allow direct mono recording. */ /* Declare system-dependent data structures. */ static bool paInitialized = false; volatile struct Sound_recordFixedTime_Info info = { 0 }; PaStreamParameters streamParameters = { 0 }; #if defined (macintosh) #elif defined (_WIN32) WAVEFORMATEX waveFormat; WAVEHDR waveHeader; MMRESULT err; (void) inputSource; (void) gain; (void) balance; #elif defined (linux) #define min(a,b) a > b ? b : a int dev_mask; int fd_mixer = -1; int val; #endif /* Check representation of shorts. */ if (sizeof (short) != 2) Melder_throw ("Cannot record a sound on this computer."); /* Check sampling frequency. */ bool supportsSamplingFrequency = true; if (inputUsesPortAudio) { #if defined (macintosh) if (sampleRate != 44100 && sampleRate != 48000 && sampleRate != 96000) supportsSamplingFrequency = false; #endif } else { #if defined (macintosh) if (sampleRate != 44100) supportsSamplingFrequency = false; #elif defined (linux) if (sampleRate != 8000 && sampleRate != 11025 && sampleRate != 16000 && sampleRate != 22050 && sampleRate != 32000 && sampleRate != 44100 && sampleRate != 48000) supportsSamplingFrequency = false; #elif defined (_WIN32) if (sampleRate != 8000 && sampleRate != 11025 && sampleRate != 16000 && sampleRate != 22050 && sampleRate != 32000 && sampleRate != 44100 && sampleRate != 48000 && sampleRate != 96000) supportsSamplingFrequency = false; #endif } if (! supportsSamplingFrequency) Melder_throw ("Your audio hardware does not support a sampling frequency of ", sampleRate, " Hz."); /* * Open phase 1. * On some systems, the info is filled in before the audio port is opened. * On other systems, the info is filled in after the port is opened. */ if (inputUsesPortAudio) { if (! paInitialized) { PaError err = Pa_Initialize (); if (err) Melder_throw ("Pa_Initialize: ", Pa_GetErrorText (err)); paInitialized = true; } } else { #if defined (macintosh) #elif defined (_WIN32) #else /* We must open the port now, because we use an ioctl to set the info to an open port. */ fd = open (DEV_AUDIO, O_RDONLY); if (fd == -1) { if (errno == EBUSY) Melder_throw ("Audio device in use by another program."); else #ifdef linux Melder_throw ("Cannot open audio device.\nPlease switch on PortAudio in the Sound Recording Preferences."); #else Melder_throw ("Cannot open audio device."); #endif } /* The device immediately started recording into its buffer, but probably at the wrong rate etc. */ /* Pause and flush this rubbish. */ #if defined (linux) ioctl (fd, SNDCTL_DSP_RESET, NULL); #endif #endif } /* Set the input source; the default is the microphone. */ if (inputUsesPortAudio) { if (inputSource < 1 || inputSource > Pa_GetDeviceCount ()) Melder_throw ("Unknown device #", inputSource, "."); streamParameters. device = inputSource - 1; } else { #if defined (macintosh) #elif defined (linux) fd_mixer = open ("/dev/mixer", O_WRONLY); if (fd_mixer == -1) Melder_throw ("Cannot open /dev/mixer."); dev_mask = inputSource == 1 ? SOUND_MASK_MIC : SOUND_MASK_LINE; if (ioctl (fd_mixer, SOUND_MIXER_WRITE_RECSRC, & dev_mask) == -1) Melder_throw ("Cannot set recording device in mixer"); #endif } /* Set gain and balance. */ if (inputUsesPortAudio) { /* Taken from Audio Control Panel. */ } else { #if defined (macintosh) || defined (_WIN32) /* Taken from Audio Control Panel. */ #elif defined (linux) val = (gain <= 0.0 ? 0 : gain >= 1.0 ? 100 : floor (gain * 100 + 0.5)); balance = balance <= 0 ? 0 : balance >= 1 ? 1 : balance; if (balance >= 0.5) { val = (int)(((int)(val*balance/(1-balance)) << 8) | val); } else { val = (int)(val | ((int)(val*(1-balance)/balance) << 8)); } val = (int)((min(2-2*balance,1))*val) | ((int)((min(2*balance,1))*val) << 8); if (inputSource == 1) { /* MIC */ if (ioctl (fd_mixer, MIXER_WRITE (SOUND_MIXER_MIC), & val) == -1) Melder_throw ("Cannot set gain and balance."); } else { /* LINE */ if (ioctl (fd_mixer, MIXER_WRITE (SOUND_MIXER_LINE), & val) == -1) Melder_throw ("Cannot set gain and balance."); } close (fd_mixer); fd_mixer = -1; #endif } /* Set the sampling frequency. */ if (inputUsesPortAudio) { // Set while opening. } else { #if defined (macintosh) #elif defined (linux) int sampleRate_int = (int) sampleRate; if (ioctl (fd, SNDCTL_DSP_SPEED, & sampleRate_int) == -1) Melder_throw ("Cannot set sampling frequency to ", sampleRate, " Hz."); #elif defined (_WIN32) waveFormat. nSamplesPerSec = sampleRate; #endif } /* Set the number of channels to 1 (mono), if possible. */ if (inputUsesPortAudio) { streamParameters. channelCount = 1; } else { #if defined (macintosh) #elif defined (linux) val = 1; if (ioctl (fd, SNDCTL_DSP_CHANNELS, & val) == -1) Melder_throw ("Cannot set to mono."); #elif defined (_WIN32) waveFormat. nChannels = 1; #endif } /* Set the encoding to 16-bit linear (or to 8-bit linear, if 16-bit is not available). */ if (inputUsesPortAudio) { streamParameters. sampleFormat = paInt16; } else { #if defined (macintosh) #elif defined (linux) #if __BYTE_ORDER == __BIG_ENDIAN val = AFMT_S16_BE; #else val = AFMT_S16_LE; #endif if (ioctl (fd, SNDCTL_DSP_SETFMT, & val) == -1) Melder_throw ("Cannot set 16-bit linear."); #elif defined (_WIN32) waveFormat. wFormatTag = WAVE_FORMAT_PCM; waveFormat. wBitsPerSample = 16; waveFormat. nBlockAlign = waveFormat. nChannels * waveFormat. wBitsPerSample / 8; waveFormat. nAvgBytesPerSec = waveFormat. nBlockAlign * waveFormat. nSamplesPerSec; #endif } /* Create a buffer for recording, and the resulting sound. */ numberOfSamples = floor (sampleRate * duration + 0.5); if (numberOfSamples < 1) Melder_throw ("Duration too short."); autoNUMvector buffer (1, numberOfSamples * (fakeMonoByStereo ? 2 : 1)); autoSound me = Sound_createSimple (1, numberOfSamples / sampleRate, sampleRate); // STEREO BUG Melder_assert (my nx == numberOfSamples); /* * Open phase 2. * This starts recording now. */ if (inputUsesPortAudio) { streamParameters. suggestedLatency = Pa_GetDeviceInfo (inputSource - 1) -> defaultLowInputLatency; #if defined (macintosh) PaMacCoreStreamInfo macCoreStreamInfo = { 0 }; macCoreStreamInfo. size = sizeof (PaMacCoreStreamInfo); macCoreStreamInfo. hostApiType = paCoreAudio; macCoreStreamInfo. version = 0x01; macCoreStreamInfo. flags = paMacCoreChangeDeviceParameters | paMacCoreFailIfConversionRequired; streamParameters. hostApiSpecificStreamInfo = & macCoreStreamInfo; #endif info. numberOfSamples = numberOfSamples; info. numberOfSamplesRead = 0; info. buffer = buffer.peek(); PaError err = Pa_OpenStream (& portaudioStream, & streamParameters, NULL, sampleRate, 0, paNoFlag, portaudioStreamCallback, (void *) & info); if (err) Melder_throw ("open ", Pa_GetErrorText (err)); Pa_StartStream (portaudioStream); if (err) Melder_throw ("start ", Pa_GetErrorText (err)); } else { #if defined (macintosh) #elif defined (_WIN32) waveFormat. cbSize = 0; err = waveInOpen (& hWaveIn, WAVE_MAPPER, & waveFormat, 0, 0, CALLBACK_NULL); if (err != MMSYSERR_NOERROR) Melder_throw ("Error ", err, " while opening."); #endif } /* Read the sound into the buffer. */ if (inputUsesPortAudio) { // The callback will do this. Just wait. while (/*getNumberOfSamplesRead (& info)*/ info. numberOfSamplesRead < numberOfSamples) { //Pa_Sleep (1); //Melder_casual ("filled %ld/%ld", getNumberOfSamplesRead (& info), numberOfSamples); } } else { #if defined (macintosh) #elif defined (_WIN32) waveHeader. dwFlags = 0; waveHeader. lpData = (char *) & buffer [1]; waveHeader. dwBufferLength = numberOfSamples * 2; waveHeader. dwLoops = 0; waveHeader. lpNext = NULL; waveHeader. reserved = 0; err = waveInPrepareHeader (hWaveIn, & waveHeader, sizeof (WAVEHDR)); if (err != MMSYSERR_NOERROR) Melder_throw ("Error ", err, " while preparing header."); err = waveInAddBuffer (hWaveIn, & waveHeader, sizeof (WAVEHDR)); if (err != MMSYSERR_NOERROR) Melder_throw ("Error ", err, " while listening."); err = waveInStart (hWaveIn); if (err != MMSYSERR_NOERROR) Melder_throw ("Error ", err, " while starting."); while (! (waveHeader. dwFlags & WHDR_DONE)) { Pa_Sleep (1); } err = waveInUnprepareHeader (hWaveIn, & waveHeader, sizeof (WAVEHDR)); if (err != MMSYSERR_NOERROR) Melder_throw ("Error ", err, " while unpreparing header."); #else if (mulaw) read (fd, (char *) & buffer [1], numberOfSamples); else { long bytesLeft = 2 * numberOfSamples, dbytes, bytesRead = 0; while (bytesLeft) { //Melder_casual ("Reading %ld bytes", bytesLeft > 4000 ? 4000 : bytesLeft); dbytes = read (fd, & ((char *) buffer.peek()) [2 + bytesRead], bytesLeft > 4000 ? 4000 : bytesLeft); //Melder_casual("Read %ld bytes", dbytes); if (dbytes <= 0) break; bytesLeft -= dbytes; bytesRead += dbytes; }; } #endif } /* Copy the buffered data to the sound object, and discard the buffer. */ if (fakeMonoByStereo) for (i = 1; i <= numberOfSamples; i ++) my z [1] [i] = ((long) buffer [i + i - 1] + buffer [i + i]) * (1.0 / 65536); else if (mulaw) for (i = 1; i <= numberOfSamples; i ++) my z [1] [i] = ulaw2linear [((unsigned char *) buffer.peek()) [i]] * (1.0 / 32768); else if (can16bit) for (i = 1; i <= numberOfSamples; i ++) my z [1] [i] = buffer [i] * (1.0 / 32768); else for (i = 1; i <= numberOfSamples; i ++) my z [1] [i] = ((int) ((unsigned char *) buffer.peek()) [i + 1] - 128) * (1.0 / 128); /* Close the audio device. */ if (inputUsesPortAudio) { Pa_StopStream (portaudioStream); Pa_CloseStream (portaudioStream); } else { #if defined (macintosh) #elif defined (_WIN32) err = waveInClose (hWaveIn); if (err != MMSYSERR_NOERROR) Melder_throw ("Error ", err, " while closing."); #else close (fd); #endif } /* Hand the resulting sound to the caller. */ return me.transfer(); } catch (MelderError) { if (inputUsesPortAudio) { if (portaudioStream) Pa_StopStream (portaudioStream); if (portaudioStream) Pa_CloseStream (portaudioStream); } else { #if defined (macintosh) #elif defined (_WIN32) if (hWaveIn != 0) waveInClose (hWaveIn); #else if (fd_mixer != -1) close (fd_mixer); if (fd != -1) close (fd); #endif } Melder_throw ("Sound not recorded."); } } /********** PLAYING A SOUND **********/ static struct SoundPlay { long numberOfSamples, i1, i2, silenceBefore, silenceAfter; double tmin, tmax, dt, t1; int (*callback) (void *closure, int phase, double tmin, double tmax, double t); void *closure; short *buffer; } thePlayingSound; static bool melderPlayCallback (void *closure, long samplesPlayed) { struct SoundPlay *me = (struct SoundPlay *) closure; int phase = 2; double t = samplesPlayed <= my silenceBefore ? my tmin : samplesPlayed >= my silenceBefore + my numberOfSamples ? my tmax : my t1 + (my i1 - 1.5 + samplesPlayed - my silenceBefore) * my dt; if (! MelderAudio_isPlaying) { NUMvector_free (my buffer, 1), my buffer = NULL; phase = 3; } if (my callback) return my callback (my closure, phase, my tmin, my tmax, t); return true; } void Sound_playPart (Sound me, double tmin, double tmax, int (*callback) (void *closure, int phase, double tmin, double tmax, double t), void *closure) { try { long ifsamp = floor (1.0 / my dx + 0.5), bestSampleRate = MelderAudio_getOutputBestSampleRate (ifsamp); if (ifsamp == bestSampleRate) { struct SoundPlay *thee = (struct SoundPlay *) & thePlayingSound; double *fromLeft = my z [1], *fromRight = my ny > 1 ? my z [2] : NULL; MelderAudio_stopPlaying (MelderAudio_IMPLICIT); long i1, i2; if ((thy numberOfSamples = Matrix_getWindowSamplesX (me, tmin, tmax, & i1, & i2)) < 1) return; thy tmin = tmin; thy tmax = tmax; thy dt = my dx; thy t1 = my x1; thy callback = callback; thy closure = closure; thy silenceBefore = (long) (ifsamp * MelderAudio_getOutputSilenceBefore ()); thy silenceAfter = (long) (ifsamp * MelderAudio_getOutputSilenceAfter ()); int numberOfChannels = my ny > 1 ? 2 : 1; NUMvector_free (thy buffer, 1); // just in case thy buffer = NUMvector (1, (i2 - i1 + 1 + thy silenceBefore + thy silenceAfter) * numberOfChannels); thy i1 = i1; thy i2 = i2; short *to = thy buffer + thy silenceBefore * numberOfChannels; if (numberOfChannels == 2) { for (long i = i1; i <= i2; i ++) { long valueLeft = (long) floor (fromLeft [i] * 32768.0 + 0.5); * ++ to = valueLeft < -32768 ? -32768 : valueLeft > 32767 ? 32767 : valueLeft; long valueRight = (long) floor (fromRight [i] * 32768.0 + 0.5); * ++ to = valueRight < -32768 ? -32768 : valueRight > 32767 ? 32767 : valueRight; } } else { for (long i = i1; i <= i2; i ++) { long value = (long) floor (fromLeft [i] * 32768.0 + 0.5); * ++ to = value < -32768 ? -32768 : value > 32767 ? 32767 : value; } } if (thy callback) thy callback (thy closure, 1, tmin, tmax, tmin); MelderAudio_play16 (thy buffer + 1, ifsamp, thy silenceBefore + thy numberOfSamples + thy silenceAfter, numberOfChannels, melderPlayCallback, thee); therror } else { autoSound resampled = Sound_resample (me, bestSampleRate, 1); Sound_playPart (resampled.peek(), tmin, tmax, callback, closure); // recursively } } catch (MelderError) { Melder_throw (me, ": not played."); } } void Sound_play (Sound me, int (*playCallback) (void *playClosure, int phase, double tmin, double tmax, double t), void *playClosure) { Sound_playPart (me, my xmin, my xmax, playCallback, playClosure); } /* End of file Sound_audio.cpp */ sources_5316/fon/SpectrumTier.h0000644000176700017670000000333411622365010015303 0ustar paulpaul#ifndef _SpectrumTier_h_ #define _SpectrumTier_h_ /* SpectrumTier.h * * Copyright (C) 2007-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "RealTier.h" #include "Graphics.h" #include "Spectrum.h" /********** class SpectrumTier **********/ Thing_define (SpectrumTier, RealTier) { // overridden methods: protected: virtual void v_info (); virtual int v_domainQuantity () { return MelderQuantity_FREQUENCY_HERTZ; } }; SpectrumTier SpectrumTier_create (double fmin, double fmax); /* Postconditions: result -> xmin == fmin; result -> xmax == fmax; result -> points -> size == 0; */ void SpectrumTier_draw (SpectrumTier me, Graphics g, double fmin, double fmax, double pmin, double pmax, int garnish, const wchar *method); void SpectrumTier_list (SpectrumTier me, bool includeIndexes, bool includeFrequency, bool includePowerDensity); Table SpectrumTier_downto_Table (SpectrumTier me, bool includeIndexes, bool includeFrequency, bool includePowerDensity); SpectrumTier Spectrum_to_SpectrumTier_peaks (Spectrum me); /* End of file SpectrumTier.h */ #endif sources_5316/fon/Praat_tests_enums.h0000644000176700017670000000064311161312230016347 0ustar paulpaul/* Praat_tests_enums.h */ /* Paul Boersma, 21 March 2009 */ enums_begin (kPraatTests, 0) enums_add (kPraatTests, 0, _, L"_") enums_add (kPraatTests, 1, CHECK_RANDOM_1009_2009, L"CheckRandom1009_2009") enums_add (kPraatTests, 2, TIME_RANDOM_FRACTION, L"TimeRandomFraction") enums_add (kPraatTests, 3, TIME_SORT, L"TimeSort") enums_end (kPraatTests, 3, CHECK_RANDOM_1009_2009) /* End of file Praat_tests_enums.h */ sources_5316/fon/TextGridEditor.cpp0000644000176700017670000025715011746506024016131 0ustar paulpaul/* TextGridEditor.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Erez Volk added FLAC support in 2007 */ #include "TextGridEditor.h" #include "EditorM.h" #include "SoundEditor.h" #include "Sound_and_Spectrogram.h" #include "TextGrid_Sound.h" #include "enums_getText.h" #include "TextGridEditor_enums.h" #include "enums_getValue.h" #include "TextGridEditor_enums.h" Thing_implement (TextGridEditor, TimeSoundAnalysisEditor, 0); /********** PREFERENCES **********/ /* * If you change any of the following, you may want to raise a version number in TextGridEditor_prefs (). */ #define TextGridEditor_DEFAULT_USE_TEXT_STYLES false #define TextGridEditor_DEFAULT_FONT_SIZE 18 #define TextGridEditor_DEFAULT_FONT_SIZE_STRING L"18" #define TextGridEditor_DEFAULT_SHIFT_DRAG_MULTIPLE true #define TextGridEditor_DEFAULT_GREEN_STRING L"some text here for green paint" static struct { bool useTextStyles, shiftDragMultiple; int fontSize; enum kGraphics_horizontalAlignment alignment; enum kTextGridEditor_showNumberOf showNumberOf; enum kMelder_string greenMethod; wchar greenString [Preferences_STRING_BUFFER_SIZE]; struct { bool showBoundaries; bool garnish; struct { bool speckle; } pitch; } picture; } preferences; void TextGridEditor_prefs (void) { Preferences_addBool (L"TextGridEditor.useTextStyles", & preferences.useTextStyles, TextGridEditor_DEFAULT_USE_TEXT_STYLES); Preferences_addInt (L"TextGridEditor.fontSize2", & preferences.fontSize, TextGridEditor_DEFAULT_FONT_SIZE); Preferences_addEnum (L"TextGridEditor.alignment", & preferences.alignment, kGraphics_horizontalAlignment, DEFAULT); Preferences_addBool (L"TextGridEditor.shiftDragMultiple2", & preferences.shiftDragMultiple, TextGridEditor_DEFAULT_SHIFT_DRAG_MULTIPLE); Preferences_addEnum (L"TextGridEditor.showNumberOf2", & preferences.showNumberOf, kTextGridEditor_showNumberOf, DEFAULT); Preferences_addEnum (L"TextGridEditor.greenMethod", & preferences.greenMethod, kMelder_string, DEFAULT); Preferences_addString (L"TextGridEditor.greenString", & preferences.greenString [0], TextGridEditor_DEFAULT_GREEN_STRING); Preferences_addBool (L"TextGridEditor.picture.showBoundaries", & preferences.picture.showBoundaries, true); Preferences_addBool (L"TextGridEditor.picture.garnish", & preferences.picture.garnish, true); Preferences_addBool (L"TextGridEditor.picture.pitch.speckle", & preferences.picture.pitch.speckle, false); } void structTextGridEditor :: v_info () { TextGridEditor_Parent :: v_info (); MelderInfo_writeLine2 (L"Selected tier: ", Melder_integer (selectedTier)); MelderInfo_writeLine2 (L"TextGrid uses text styles: ", Melder_boolean (useTextStyles)); MelderInfo_writeLine2 (L"TextGrid font size: ", Melder_integer (fontSize)); MelderInfo_writeLine2 (L"TextGrid alignment: ", kGraphics_horizontalAlignment_getText (alignment)); } /********** UTILITIES **********/ static double _TextGridEditor_computeSoundY (TextGridEditor me) { TextGrid grid = (TextGrid) my data; int numberOfTiers = grid -> tiers -> size; bool showAnalysis = my v_hasAnalysis () && (my spectrogram.show || my pitch.show || my intensity.show || my formant.show) && (my longSound.data || my sound.data); int numberOfVisibleChannels = my sound.data ? (my sound.data -> ny > 8 ? 8 : my sound.data -> ny) : my longSound.data ? (my longSound.data -> numberOfChannels > 8 ? 8 : my longSound.data -> numberOfChannels) : 1; return my sound.data || my longSound.data ? numberOfTiers / (2.0 * numberOfVisibleChannels + numberOfTiers * (showAnalysis ? 1.8 : 1.3)) : 1.0; } static void _AnyTier_identifyClass (Function anyTier, IntervalTier *intervalTier, TextTier *textTier) { if (anyTier -> classInfo == classIntervalTier) { *intervalTier = (IntervalTier) anyTier; *textTier = NULL; } else { *intervalTier = NULL; *textTier = (TextTier) anyTier; } } static int _TextGridEditor_yWCtoTier (TextGridEditor me, double yWC) { TextGrid grid = (TextGrid) my data; int ntier = grid -> tiers -> size; double soundY = _TextGridEditor_computeSoundY (me); int itier = ntier - (int) floor (yWC / soundY * (double) ntier); if (itier < 1) itier = 1; if (itier > ntier) itier = ntier; return itier; } static void _TextGridEditor_timeToInterval (TextGridEditor me, double t, int itier, double *tmin, double *tmax) { TextGrid grid = (TextGrid) my data; IntervalTier intervalTier; TextTier textTier; _AnyTier_identifyClass ((Function) grid -> tiers -> item [itier], & intervalTier, & textTier); if (intervalTier) { long iinterval = IntervalTier_timeToIndex (intervalTier, t); TextInterval interval; if (iinterval == 0) { if (t < my tmin) { iinterval = 1; } else { iinterval = intervalTier -> intervals -> size; } } interval = (TextInterval) intervalTier -> intervals -> item [iinterval]; *tmin = interval -> xmin; *tmax = interval -> xmax; } else { long n = textTier -> points -> size; if (n == 0) { *tmin = my tmin; *tmax = my tmax; } else { long ipointleft = AnyTier_timeToLowIndex (textTier, t); *tmin = ipointleft == 0 ? my tmin : ((TextPoint) textTier -> points -> item [ipointleft]) -> number; *tmax = ipointleft == n ? my tmax : ((TextPoint) textTier -> points -> item [ipointleft + 1]) -> number; } } if (*tmin < my tmin) *tmin = my tmin; /* Clip by FunctionEditor's time domain. */ if (*tmax > my tmax) *tmax = my tmax; } static void checkTierSelection (TextGridEditor me, const wchar_t *verbPhrase) { TextGrid grid = (TextGrid) my data; if (my selectedTier < 1 || my selectedTier > grid -> tiers -> size) Melder_throw ("To ", verbPhrase, ", first select a tier by clicking anywhere inside it."); } static long getSelectedInterval (TextGridEditor me) { TextGrid grid = (TextGrid) my data; Melder_assert (my selectedTier >= 1 || my selectedTier <= grid -> tiers -> size); IntervalTier tier = (IntervalTier) grid -> tiers -> item [my selectedTier]; Melder_assert (tier -> classInfo == classIntervalTier); return IntervalTier_timeToIndex (tier, my startSelection); } static long getSelectedLeftBoundary (TextGridEditor me) { TextGrid grid = (TextGrid) my data; Melder_assert (my selectedTier >= 1 || my selectedTier <= grid -> tiers -> size); IntervalTier tier = (IntervalTier) grid -> tiers -> item [my selectedTier]; Melder_assert (tier -> classInfo == classIntervalTier); return IntervalTier_hasBoundary (tier, my startSelection); } static long getSelectedPoint (TextGridEditor me) { TextGrid grid = (TextGrid) my data; Melder_assert (my selectedTier >= 1 || my selectedTier <= grid -> tiers -> size); TextTier tier = (TextTier) grid -> tiers -> item [my selectedTier]; Melder_assert (tier -> classInfo == classTextTier); return AnyTier_hasPoint (tier, my startSelection); } static void scrollToView (TextGridEditor me, double t) { if (t <= my startWindow) { FunctionEditor_shift (me, t - my startWindow - 0.618 * (my endWindow - my startWindow)); } else if (t >= my endWindow) { FunctionEditor_shift (me, t - my endWindow + 0.618 * (my endWindow - my startWindow)); } else { FunctionEditor_marksChanged (me); } } /********** METHODS **********/ /* * The main invariant of the TextGridEditor is that the selected interval * always has the cursor in it, and that the cursor always selects an interval * if the selected tier is an interval tier. */ /***** FILE MENU *****/ static void menu_cb_ExtractSelectedTextGrid_preserveTimes (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); if (my endSelection <= my startSelection) Melder_throw ("No selection."); autoTextGrid extract = TextGrid_extractPart ((TextGrid) my data, my startSelection, my endSelection, true); my broadcastPublication (extract.transfer()); } static void menu_cb_ExtractSelectedTextGrid_timeFromZero (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); if (my endSelection <= my startSelection) Melder_throw ("No selection."); autoTextGrid extract = TextGrid_extractPart ((TextGrid) my data, my startSelection, my endSelection, false); my broadcastPublication (extract.transfer()); } void structTextGridEditor :: v_createMenuItems_file_extract (EditorMenu menu) { TextGridEditor_Parent :: v_createMenuItems_file_extract (menu); extractSelectedTextGridPreserveTimesButton = EditorMenu_addCommand (menu, L"Extract selected TextGrid (preserve times)", 0, menu_cb_ExtractSelectedTextGrid_preserveTimes); extractSelectedTextGridTimeFromZeroButton = EditorMenu_addCommand (menu, L"Extract selected TextGrid (time from zero)", 0, menu_cb_ExtractSelectedTextGrid_timeFromZero); } static void menu_cb_WriteToTextFile (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); EDITOR_FORM_WRITE (L"Save as TextGrid text file", 0) swprintf (defaultName, 300, L"%ls.TextGrid", ((Thing) my data) -> name); EDITOR_DO_WRITE Data_writeToTextFile (my data, file); EDITOR_END } void structTextGridEditor :: v_createMenuItems_file_write (EditorMenu menu) { TextGridEditor_Parent :: v_createMenuItems_file_write (menu); EditorMenu_addCommand (menu, L"Save TextGrid as text file...", 'S', menu_cb_WriteToTextFile); } static void menu_cb_DrawVisibleTextGrid (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); EDITOR_FORM (L"Draw visible TextGrid", 0) my v_form_pictureWindow (cmd); my v_form_pictureMargins (cmd); my v_form_pictureSelection (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); my v_ok_pictureMargins (cmd); my v_ok_pictureSelection (cmd); SET_INTEGER (L"Garnish", preferences.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); my v_do_pictureMargins (cmd); my v_do_pictureSelection (cmd); preferences.picture.garnish = GET_INTEGER (L"Garnish"); Editor_openPraatPicture (me); TextGrid_Sound_draw ((TextGrid) my data, NULL, my pictureGraphics, my startWindow, my endWindow, true, my useTextStyles, preferences.picture.garnish); FunctionEditor_garnish (me); Editor_closePraatPicture (me); EDITOR_END } static void menu_cb_DrawVisibleSoundAndTextGrid (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); EDITOR_FORM (L"Draw visible sound and TextGrid", 0) my v_form_pictureWindow (cmd); my v_form_pictureMargins (cmd); my v_form_pictureSelection (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); my v_ok_pictureMargins (cmd); my v_ok_pictureSelection (cmd); SET_INTEGER (L"Garnish", preferences.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); my v_do_pictureMargins (cmd); my v_do_pictureSelection (cmd); preferences.picture.garnish = GET_INTEGER (L"Garnish"); Editor_openPraatPicture (me); Sound publish = my longSound.data ? LongSound_extractPart (my longSound.data, my startWindow, my endWindow, true) : Sound_extractPart (my sound.data, my startWindow, my endWindow, kSound_windowShape_RECTANGULAR, 1.0, true); TextGrid_Sound_draw ((TextGrid) my data, publish, my pictureGraphics, my startWindow, my endWindow, true, my useTextStyles, preferences.picture.garnish); forget (publish); FunctionEditor_garnish (me); Editor_closePraatPicture (me); EDITOR_END } void structTextGridEditor :: v_createMenuItems_file_draw (EditorMenu menu) { TextGridEditor_Parent :: v_createMenuItems_file_draw (menu); EditorMenu_addCommand (menu, L"Draw visible TextGrid...", 0, menu_cb_DrawVisibleTextGrid); if (sound.data || longSound.data) EditorMenu_addCommand (menu, L"Draw visible sound and TextGrid...", 0, menu_cb_DrawVisibleSoundAndTextGrid); } /***** EDIT MENU *****/ #ifndef macintosh static void menu_cb_Cut (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); GuiText_cut (my text); } static void menu_cb_Copy (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); GuiText_copy (my text); } static void menu_cb_Paste (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); GuiText_paste (my text); } static void menu_cb_Erase (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); GuiText_remove (my text); } #endif static void menu_cb_Genericize (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); Editor_save (me, L"Convert to Backslash Trigraphs"); TextGrid_genericize ((TextGrid) my data); FunctionEditor_updateText (me); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_Nativize (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); Editor_save (me, L"Convert to Unicode"); TextGrid_nativize ((TextGrid) my data); FunctionEditor_updateText (me); FunctionEditor_redraw (me); my broadcastDataChanged (); } /***** QUERY MENU *****/ static void menu_cb_GetStartingPointOfInterval (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"query the starting point of an interval"); Function anyTier = (Function) grid -> tiers -> item [my selectedTier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long iinterval = IntervalTier_timeToIndex (tier, my startSelection); double time = iinterval < 1 || iinterval > tier -> intervals -> size ? NUMundefined : ((TextInterval) tier -> intervals -> item [iinterval]) -> xmin; Melder_informationReal (time, L"seconds"); } else { Melder_throw ("The selected tier is not an interval tier."); } } static void menu_cb_GetEndPointOfInterval (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"query the end point of an interval"); Function anyTier = (Function) grid -> tiers -> item [my selectedTier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long iinterval = IntervalTier_timeToIndex (tier, my startSelection); double time = iinterval < 1 || iinterval > tier -> intervals -> size ? NUMundefined : ((TextInterval) tier -> intervals -> item [iinterval]) -> xmax; Melder_informationReal (time, L"seconds"); } else { Melder_throw ("The selected tier is not an interval tier."); } } static void menu_cb_GetLabelOfInterval (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"query the label of an interval"); Function anyTier = (Function) grid -> tiers -> item [my selectedTier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long iinterval = IntervalTier_timeToIndex (tier, my startSelection); const wchar_t *label = iinterval < 1 || iinterval > tier -> intervals -> size ? L"" : ((TextInterval) tier -> intervals -> item [iinterval]) -> text; Melder_information (label); } else { Melder_throw ("The selected tier is not an interval tier."); } } /***** VIEW MENU *****/ static void do_selectAdjacentTier (TextGridEditor me, bool previous) { TextGrid grid = (TextGrid) my data; long n = grid -> tiers -> size; if (n >= 2) { my selectedTier = previous ? my selectedTier > 1 ? my selectedTier - 1 : n : my selectedTier < n ? my selectedTier + 1 : 1; _TextGridEditor_timeToInterval (me, my startSelection, my selectedTier, & my startSelection, & my endSelection); FunctionEditor_marksChanged (me); } } static void menu_cb_SelectPreviousTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_selectAdjacentTier (me, true); } static void menu_cb_SelectNextTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_selectAdjacentTier (me, false); } static void do_selectAdjacentInterval (TextGridEditor me, bool previous, bool shift) { TextGrid grid = (TextGrid) my data; IntervalTier intervalTier; TextTier textTier; if (my selectedTier < 1 || my selectedTier > grid -> tiers -> size) return; _AnyTier_identifyClass ((Function) grid -> tiers -> item [my selectedTier], & intervalTier, & textTier); if (intervalTier) { long n = intervalTier -> intervals -> size; if (n >= 2) { TextInterval interval; long iinterval = IntervalTier_timeToIndex (intervalTier, my startSelection); if (shift) { long binterval = IntervalTier_timeToIndex (intervalTier, my startSelection); long einterval = IntervalTier_timeToIndex (intervalTier, my endSelection); if (my endSelection == intervalTier -> xmax) einterval ++; if (binterval < iinterval && einterval > iinterval + 1) { interval = (TextInterval) intervalTier -> intervals -> item [iinterval]; my startSelection = interval -> xmin; my endSelection = interval -> xmax; } else if (previous) { if (einterval > iinterval + 1) { if (einterval <= n + 1) { interval = (TextInterval) intervalTier -> intervals -> item [einterval - 1]; my endSelection = interval -> xmin; } } else if (binterval > 1) { interval = (TextInterval) intervalTier -> intervals -> item [binterval - 1]; my startSelection = interval -> xmin; } } else { if (binterval < iinterval) { if (binterval > 0) { interval = (TextInterval) intervalTier -> intervals -> item [binterval]; my startSelection = interval -> xmax; } } else if (einterval <= n) { interval = (TextInterval) intervalTier -> intervals -> item [einterval]; my endSelection = interval -> xmax; } } } else { iinterval = previous ? iinterval > 1 ? iinterval - 1 : n : iinterval < n ? iinterval + 1 : 1; interval = (TextInterval) intervalTier -> intervals -> item [iinterval]; my startSelection = interval -> xmin; my endSelection = interval -> xmax; } scrollToView (me, iinterval == n ? my startSelection : iinterval == 1 ? my endSelection : (my startSelection + my endSelection) / 2); } } else { long n = textTier -> points -> size; if (n >= 2) { TextPoint point; long ipoint = AnyTier_timeToHighIndex (textTier, my startSelection); ipoint = previous ? ipoint > 1 ? ipoint - 1 : n : ipoint < n ? ipoint + 1 : 1; point = (TextPoint) textTier -> points -> item [ipoint]; my startSelection = my endSelection = point -> number; scrollToView (me, my startSelection); } } } static void menu_cb_SelectPreviousInterval (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_selectAdjacentInterval (me, true, false); } static void menu_cb_SelectNextInterval (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_selectAdjacentInterval (me, false, false); } static void menu_cb_ExtendSelectPreviousInterval (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_selectAdjacentInterval (me, true, true); } static void menu_cb_ExtendSelectNextInterval (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_selectAdjacentInterval (me, false, true); } static void menu_cb_MoveBtoZero (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); double zero = Sound_getNearestZeroCrossing (my sound.data, my startSelection, 1); // STEREO BUG if (NUMdefined (zero)) { my startSelection = zero; if (my startSelection > my endSelection) { double dummy = my startSelection; my startSelection = my endSelection; my endSelection = dummy; } FunctionEditor_marksChanged (me); } } static void menu_cb_MoveCursorToZero (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); double zero = Sound_getNearestZeroCrossing (my sound.data, 0.5 * (my startSelection + my endSelection), 1); // STEREO BUG if (NUMdefined (zero)) { my startSelection = my endSelection = zero; FunctionEditor_marksChanged (me); } } static void menu_cb_MoveEtoZero (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); double zero = Sound_getNearestZeroCrossing (my sound.data, my endSelection, 1); // STEREO BUG if (NUMdefined (zero)) { my endSelection = zero; if (my startSelection > my endSelection) { double dummy = my startSelection; my startSelection = my endSelection; my endSelection = dummy; } FunctionEditor_marksChanged (me); } } /***** PITCH MENU *****/ static void menu_cb_DrawTextGridAndPitch (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); EDITOR_FORM (L"Draw TextGrid and Pitch separately", 0) my v_form_pictureWindow (cmd); LABEL (L"", L"TextGrid:") BOOLEAN (L"Show boundaries and points", 1); LABEL (L"", L"Pitch:") BOOLEAN (L"Speckle", 0); my v_form_pictureMargins (cmd); my v_form_pictureSelection (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); SET_INTEGER (L"Show boundaries and points", preferences.picture.showBoundaries); SET_INTEGER (L"Speckle", preferences.picture.pitch.speckle); my v_ok_pictureMargins (cmd); my v_ok_pictureSelection (cmd); SET_INTEGER (L"Garnish", preferences.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); preferences.picture.showBoundaries = GET_INTEGER (L"Show boundaries and points"); preferences.picture.pitch.speckle = GET_INTEGER (L"Speckle"); my v_do_pictureMargins (cmd); my v_do_pictureSelection (cmd); preferences.picture.garnish = GET_INTEGER (L"Garnish"); if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the Pitch menu."); if (! my pitch.data) { TimeSoundAnalysisEditor_computePitch (me); if (! my pitch.data) Melder_throw ("Cannot compute pitch."); } Editor_openPraatPicture (me); double pitchFloor_hidden = Function_convertStandardToSpecialUnit (my pitch.data, my pitch.floor, Pitch_LEVEL_FREQUENCY, my pitch.unit); double pitchCeiling_hidden = Function_convertStandardToSpecialUnit (my pitch.data, my pitch.ceiling, Pitch_LEVEL_FREQUENCY, my pitch.unit); double pitchFloor_overt = Function_convertToNonlogarithmic (my pitch.data, pitchFloor_hidden, Pitch_LEVEL_FREQUENCY, my pitch.unit); double pitchCeiling_overt = Function_convertToNonlogarithmic (my pitch.data, pitchCeiling_hidden, Pitch_LEVEL_FREQUENCY, my pitch.unit); double pitchViewFrom_overt = my pitch.viewFrom < my pitch.viewTo ? my pitch.viewFrom : pitchFloor_overt; double pitchViewTo_overt = my pitch.viewFrom < my pitch.viewTo ? my pitch.viewTo : pitchCeiling_overt; TextGrid_Pitch_drawSeparately ((TextGrid) my data, my pitch.data, my pictureGraphics, my startWindow, my endWindow, pitchViewFrom_overt, pitchViewTo_overt, GET_INTEGER (L"Show boundaries and points"), my useTextStyles, GET_INTEGER (L"Garnish"), GET_INTEGER (L"Speckle"), my pitch.unit); FunctionEditor_garnish (me); Editor_closePraatPicture (me); EDITOR_END } /***** INTERVAL MENU *****/ static void insertBoundaryOrPoint (TextGridEditor me, int itier, double t1, double t2, bool insertSecond) { TextGrid grid = (TextGrid) my data; IntervalTier intervalTier; TextTier textTier; int ntiers = grid -> tiers -> size; if (itier < 1 || itier > ntiers) Melder_throw ("No tier ", itier, "."); _AnyTier_identifyClass ((Function) grid -> tiers -> item [itier], & intervalTier, & textTier); Melder_assert (t1 <= t2); if (intervalTier) { TextInterval rightNewInterval = NULL, midNewInterval = NULL; bool t1IsABoundary = IntervalTier_hasTime (intervalTier, t1); bool t2IsABoundary = IntervalTier_hasTime (intervalTier, t2); if (t1 == t2 && t1IsABoundary) Melder_throw ("Cannot add a boundary at ", Melder_fixed (t1, 6), " seconds, because there is already a boundary there."); if (t1IsABoundary && t2IsABoundary) Melder_throw ("Cannot add boundaries at ", Melder_fixed (t1, 6), " and ", Melder_fixed (t2, 6), " seconds, because there are already boundaries there."); long iinterval = IntervalTier_timeToIndex (intervalTier, t1); //Melder_casual ("iinterval %ld, t = %f", iinterval, t1); long iinterval2 = t1 == t2 ? iinterval : IntervalTier_timeToIndex (intervalTier, t2); //Melder_casual ("iinterval2 %ld, t = %f", iinterval2, t2); if (iinterval == 0 || iinterval2 == 0) Melder_throw ("The selection is outside the time domain of the intervals."); long correctedIinterval2 = t2IsABoundary && iinterval2 == intervalTier -> intervals -> size ? iinterval2 + 1 : iinterval2; if (correctedIinterval2 > iinterval + 1 || (correctedIinterval2 > iinterval && ! t2IsABoundary)) Melder_throw ("The selection straddles a boundary."); TextInterval interval = (TextInterval) intervalTier -> intervals -> item [iinterval]; if (t1 == t2) { Editor_save (me, L"Add boundary"); } else { Editor_save (me, L"Add interval"); } if (itier == my selectedTier) { /* * Divide up the label text into left, mid and right, depending on where the text selection is. */ long left, right; wchar_t *text = GuiText_getStringAndSelectionPosition (my text, & left, & right); rightNewInterval = TextInterval_create (t2, interval -> xmax, text + right); text [right] = '\0'; midNewInterval = TextInterval_create (t1, t2, text + left); text [left] = '\0'; TextInterval_setText (interval, text); Melder_free (text); } else { /* * Move the text to the left of the boundary. */ rightNewInterval = TextInterval_create (t2, interval -> xmax, L""); midNewInterval = TextInterval_create (t1, t2, L""); } if (t1IsABoundary) { /* * Merge mid with left interval. */ if (interval -> xmin != t1) Melder_fatal ("Boundary unequal: %.17g versus %.17g.", interval -> xmin, t1); interval -> xmax = t2; TextInterval_setText (interval, Melder_wcscat (interval -> text, midNewInterval -> text)); forget (midNewInterval); } else if (t2IsABoundary) { /* * Merge mid and right interval. */ if (interval -> xmax != t2) Melder_fatal ("Boundary unequal: %.17g versus %.17g.", interval -> xmax, t2); interval -> xmax = t1; Melder_assert (rightNewInterval -> xmin == t2); Melder_assert (rightNewInterval -> xmax == t2); rightNewInterval -> xmin = t1; TextInterval_setText (rightNewInterval, Melder_wcscat (midNewInterval -> text, rightNewInterval -> text)); forget (midNewInterval); } else { interval -> xmax = t1; if (t1 != t2) Collection_addItem (intervalTier -> intervals, midNewInterval); } Collection_addItem (intervalTier -> intervals, rightNewInterval); if (insertSecond && ntiers >= 2) { /* * Find the last time before t on another tier. */ double tlast = interval -> xmin, tmin, tmax; for (int jtier = 1; jtier <= ntiers; jtier ++) if (jtier != itier) { _TextGridEditor_timeToInterval (me, t1, jtier, & tmin, & tmax); if (tmin > tlast) { tlast = tmin; } } if (tlast > interval -> xmin && tlast < t1) { TextInterval newInterval = TextInterval_create (tlast, t1, L""); interval -> xmax = tlast; Collection_addItem (intervalTier -> intervals, newInterval); } } } else { TextPoint newPoint; if (AnyTier_hasPoint (textTier, t1)) Melder_throw ("Cannot add a point at ", Melder_fixed (t1, 6), " seconds, because there is already a point there."); Editor_save (me, L"Add point"); newPoint = TextPoint_create (t1, L""); Collection_addItem (textTier -> points, newPoint); } my startSelection = my endSelection = t1; } static void do_insertIntervalOnTier (TextGridEditor me, int itier) { try { insertBoundaryOrPoint (me, itier, my playingCursor || my playingSelection ? my playCursor : my startSelection, my playingCursor || my playingSelection ? my playCursor : my endSelection, true); my selectedTier = itier; FunctionEditor_marksChanged (me); my broadcastDataChanged (); } catch (MelderError) { Melder_throw ("Interval not inserted."); } } static void menu_cb_InsertIntervalOnTier1 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertIntervalOnTier (me, 1); } static void menu_cb_InsertIntervalOnTier2 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertIntervalOnTier (me, 2); } static void menu_cb_InsertIntervalOnTier3 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertIntervalOnTier (me, 3); } static void menu_cb_InsertIntervalOnTier4 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertIntervalOnTier (me, 4); } static void menu_cb_InsertIntervalOnTier5 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertIntervalOnTier (me, 5); } static void menu_cb_InsertIntervalOnTier6 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertIntervalOnTier (me, 6); } static void menu_cb_InsertIntervalOnTier7 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertIntervalOnTier (me, 7); } static void menu_cb_InsertIntervalOnTier8 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertIntervalOnTier (me, 8); } /***** BOUNDARY/POINT MENU *****/ static void menu_cb_RemovePointOrBoundary (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"remove a point or boundary"); Function anyTier = (Function) grid -> tiers -> item [my selectedTier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long selectedLeftBoundary = getSelectedLeftBoundary (me); if (! selectedLeftBoundary) Melder_throw ("To remove a boundary, first click on it."); Editor_save (me, L"Remove boundary"); IntervalTier_removeLeftBoundary (tier, selectedLeftBoundary); therror; } else { TextTier tier = (TextTier) anyTier; long selectedPoint = getSelectedPoint (me); if (! selectedPoint) Melder_throw ("To remove a point, first click on it."); Editor_save (me, L"Remove point"); Collection_removeItem (tier -> points, selectedPoint); } FunctionEditor_updateText (me); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void do_movePointOrBoundary (TextGridEditor me, int where) { double position; TextGrid grid = (TextGrid) my data; if (where == 0 && my sound.data == NULL) return; checkTierSelection (me, L"move a point or boundary"); Function anyTier = (Function) grid -> tiers -> item [my selectedTier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; static const wchar_t *boundarySaveText [3] = { L"Move boundary to zero crossing", L"Move boundary to B", L"Move boundary to E" }; TextInterval left, right; long selectedLeftBoundary = getSelectedLeftBoundary (me); if (! selectedLeftBoundary) Melder_throw ("To move a boundary, first click on it."); left = (TextInterval) tier -> intervals -> item [selectedLeftBoundary - 1]; right = (TextInterval) tier -> intervals -> item [selectedLeftBoundary]; position = where == 1 ? my startSelection : where == 2 ? my endSelection : Sound_getNearestZeroCrossing (my sound.data, left -> xmax, 1); // STEREO BUG if (position == NUMundefined) Melder_throw ("There is no zero crossing to move to."); if (position <= left -> xmin || position >= right -> xmax) Melder_throw ("Cannot move a boundary past its neighbour."); Editor_save (me, boundarySaveText [where]); left -> xmax = right -> xmin = my startSelection = my endSelection = position; } else { TextTier tier = (TextTier) anyTier; static const wchar_t *pointSaveText [3] = { L"Move point to zero crossing", L"Move point to B", L"Move point to E" }; TextPoint point; long selectedPoint = getSelectedPoint (me); if (! selectedPoint) Melder_throw ("To move a point, first click on it."); point = (TextPoint) tier -> points -> item [selectedPoint]; position = where == 1 ? my startSelection : where == 2 ? my endSelection : Sound_getNearestZeroCrossing (my sound.data, point -> number, 1); // STEREO BUG if (position == NUMundefined) Melder_throw ("There is no zero crossing to move to."); Editor_save (me, pointSaveText [where]); point -> number = my startSelection = my endSelection = position; } FunctionEditor_marksChanged (me); // because cursor has moved my broadcastDataChanged (); } static void menu_cb_MoveToB (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_movePointOrBoundary (me, 1); } static void menu_cb_MoveToE (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_movePointOrBoundary (me, 2); } static void menu_cb_MoveToZero (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_movePointOrBoundary (me, 0); } static void do_insertOnTier (TextGridEditor me, int itier) { try { insertBoundaryOrPoint (me, itier, my playingCursor || my playingSelection ? my playCursor : my startSelection, my playingCursor || my playingSelection ? my playCursor : my endSelection, false); my selectedTier = itier; FunctionEditor_marksChanged (me); my broadcastDataChanged (); } catch (MelderError) { Melder_throw ("Boundary or point not inserted."); } } static void menu_cb_InsertOnSelectedTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertOnTier (me, my selectedTier); } static void menu_cb_InsertOnTier1 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertOnTier (me, 1); } static void menu_cb_InsertOnTier2 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertOnTier (me, 2); } static void menu_cb_InsertOnTier3 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertOnTier (me, 3); } static void menu_cb_InsertOnTier4 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertOnTier (me, 4); } static void menu_cb_InsertOnTier5 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertOnTier (me, 5); } static void menu_cb_InsertOnTier6 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertOnTier (me, 6); } static void menu_cb_InsertOnTier7 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertOnTier (me, 7); } static void menu_cb_InsertOnTier8 (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_insertOnTier (me, 8); } static void menu_cb_InsertOnAllTiers (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); TextGrid grid = (TextGrid) my data; int saveTier = my selectedTier; for (int itier = 1; itier <= grid -> tiers -> size; itier ++) { do_insertOnTier (me, itier); } my selectedTier = saveTier; // only if everything went right; otherwise, the tier where something went wrong will stand selected } /***** SEARCH MENU *****/ static void findInTier (TextGridEditor me) { TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"find a text"); Function anyTier = (Function) grid -> tiers -> item [my selectedTier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long iinterval = IntervalTier_timeToIndex (tier, my startSelection) + 1; while (iinterval <= tier -> intervals -> size) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; wchar_t *text = interval -> text; if (text) { wchar_t *position = wcsstr (text, my findString); if (position) { my startSelection = interval -> xmin; my endSelection = interval -> xmax; scrollToView (me, my startSelection); GuiText_setSelection (my text, position - text, position - text + wcslen (my findString)); return; } } iinterval ++; } if (iinterval > tier -> intervals -> size) Melder_beep (); } else { TextTier tier = (TextTier) anyTier; long ipoint = AnyTier_timeToLowIndex (tier, my startSelection) + 1; while (ipoint <= tier -> points -> size) { TextPoint point = (TextPoint) tier -> points -> item [ipoint]; wchar_t *text = point -> mark; if (text) { wchar_t *position = wcsstr (text, my findString); if (position) { my startSelection = my endSelection = point -> number; scrollToView (me, point -> number); GuiText_setSelection (my text, position - text, position - text + wcslen (my findString)); return; } } ipoint ++; } if (ipoint > tier -> points -> size) Melder_beep (); } } static void do_find (TextGridEditor me) { if (my findString) { long left, right; autostring label = GuiText_getStringAndSelectionPosition (my text, & left, & right); wchar *position = wcsstr (label.peek() + right, my findString); // CRLF BUG? if (position) { GuiText_setSelection (my text, position - label.peek(), position - label.peek() + wcslen (my findString)); } else { findInTier (me); } } } static void menu_cb_Find (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); EDITOR_FORM (L"Find text", 0) LABEL (L"", L"Text:") TEXTFIELD (L"string", L"") EDITOR_OK EDITOR_DO Melder_free (my findString); my findString = Melder_wcsdup_f (GET_STRING (L"string")); do_find (me); EDITOR_END } static void menu_cb_FindAgain (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); do_find (me); } static void checkSpellingInTier (TextGridEditor me) { TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"check spelling"); Function anyTier = (Function) grid -> tiers -> item [my selectedTier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long iinterval = IntervalTier_timeToIndex (tier, my startSelection) + 1; while (iinterval <= tier -> intervals -> size) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; wchar_t *text = interval -> text; if (text) { long position = 0; wchar_t *notAllowed = SpellingChecker_nextNotAllowedWord (my spellingChecker, text, & position); if (notAllowed) { my startSelection = interval -> xmin; my endSelection = interval -> xmax; scrollToView (me, my startSelection); GuiText_setSelection (my text, position, position + wcslen (notAllowed)); return; } } iinterval ++; } if (iinterval > tier -> intervals -> size) Melder_beep (); } else { TextTier tier = (TextTier) anyTier; long ipoint = AnyTier_timeToLowIndex (tier, my startSelection) + 1; while (ipoint <= tier -> points -> size) { TextPoint point = (TextPoint) tier -> points -> item [ipoint]; wchar_t *text = point -> mark; if (text) { long position = 0; wchar_t *notAllowed = SpellingChecker_nextNotAllowedWord (my spellingChecker, text, & position); if (notAllowed) { my startSelection = my endSelection = point -> number; scrollToView (me, point -> number); GuiText_setSelection (my text, position, position + wcslen (notAllowed)); return; } } ipoint ++; } if (ipoint > tier -> points -> size) Melder_beep (); } } static void menu_cb_CheckSpelling (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); if (my spellingChecker) { long left, right; autostring label = GuiText_getStringAndSelectionPosition (my text, & left, & right); long position = right; wchar *notAllowed = SpellingChecker_nextNotAllowedWord (my spellingChecker, label.peek(), & position); if (notAllowed) { GuiText_setSelection (my text, position, position + wcslen (notAllowed)); } else { checkSpellingInTier (me); } } } static void menu_cb_CheckSpellingInInterval (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); if (my spellingChecker) { long left, right; autostring label = GuiText_getStringAndSelectionPosition (my text, & left, & right); long position = right; wchar *notAllowed = SpellingChecker_nextNotAllowedWord (my spellingChecker, label.peek(), & position); if (notAllowed) { GuiText_setSelection (my text, position, position + wcslen (notAllowed)); } } } static void menu_cb_AddToUserDictionary (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); if (my spellingChecker) { autostring word = GuiText_getSelection (my text); SpellingChecker_addNewWord (my spellingChecker, word.peek()); therror my broadcastDataChanged (); } } /***** TIER MENU *****/ static void menu_cb_RenameTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); EDITOR_FORM (L"Rename tier", 0) SENTENCE (L"Name", L""); EDITOR_OK TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"rename a tier"); Data tier = (Data) grid -> tiers -> item [my selectedTier]; SET_STRING (L"Name", tier -> name ? tier -> name : L"") EDITOR_DO TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"rename a tier"); Function tier = (Function) grid -> tiers -> item [my selectedTier]; Editor_save (me, L"Rename tier"); wchar *newName = GET_STRING (L"Name"); Thing_setName (tier, newName); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_PublishTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"publish a tier"); Function tier = (Function) grid -> tiers -> item [my selectedTier]; autoTextGrid publish = TextGrid_createWithoutTiers (1e30, -1e30); TextGrid_addTier (publish.peek(), tier); therror Thing_setName (publish.peek(), tier -> name); my broadcastPublication (publish.transfer()); } static void menu_cb_RemoveAllTextFromTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); TextGrid grid = (TextGrid) my data; checkTierSelection (me, L"remove all text from a tier"); IntervalTier intervalTier; TextTier textTier; _AnyTier_identifyClass ((Function) grid -> tiers -> item [my selectedTier], & intervalTier, & textTier); Editor_save (me, L"Remove text from tier"); if (intervalTier) { IntervalTier_removeText (intervalTier); } else { TextTier_removeText (textTier); } FunctionEditor_updateText (me); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_RemoveTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); TextGrid grid = (TextGrid) my data; if (grid -> tiers -> size <= 1) { Melder_throw ("Sorry, I refuse to remove the last tier."); } checkTierSelection (me, L"remove a tier"); Editor_save (me, L"Remove tier"); Collection_removeItem (grid -> tiers, my selectedTier); my selectedTier = 1; FunctionEditor_updateText (me); FunctionEditor_redraw (me); my broadcastDataChanged (); } static void menu_cb_AddIntervalTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); EDITOR_FORM (L"Add interval tier", 0) NATURAL (L"Position", L"1 (= at top)") SENTENCE (L"Name", L"") EDITOR_OK TextGrid grid = (TextGrid) my data; static MelderString text = { 0 }; MelderString_empty (& text); MelderString_append (& text, Melder_integer (grid -> tiers -> size + 1), L" (= at bottom)"); SET_STRING (L"Position", text.string) SET_STRING (L"Name", L"") EDITOR_DO TextGrid grid = (TextGrid) my data; int position = GET_INTEGER (L"Position"); wchar_t *name = GET_STRING (L"Name"); autoIntervalTier tier = IntervalTier_create (grid -> xmin, grid -> xmax); if (position > grid -> tiers -> size) position = grid -> tiers -> size + 1; Thing_setName (tier.peek(), name); Editor_save (me, L"Add interval tier"); Ordered_addItemPos (grid -> tiers, tier.transfer(), position); my selectedTier = position; FunctionEditor_updateText (me); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_AddPointTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); EDITOR_FORM (L"Add point tier", 0) NATURAL (L"Position", L"1 (= at top)") SENTENCE (L"Name", L""); EDITOR_OK TextGrid grid = (TextGrid) my data; static MelderString text = { 0 }; MelderString_empty (& text); MelderString_append (& text, Melder_integer (grid -> tiers -> size + 1), L" (= at bottom)"); SET_STRING (L"Position", text.string) SET_STRING (L"Name", L"") EDITOR_DO TextGrid grid = (TextGrid) my data; int position = GET_INTEGER (L"Position"); wchar_t *name = GET_STRING (L"Name"); autoTextTier tier = TextTier_create (grid -> xmin, grid -> xmax); if (position > grid -> tiers -> size) position = grid -> tiers -> size + 1; Thing_setName (tier.peek(), name); Editor_save (me, L"Add point tier"); Ordered_addItemPos (grid -> tiers, tier.transfer(), position); my selectedTier = position; FunctionEditor_updateText (me); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } static void menu_cb_DuplicateTier (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); EDITOR_FORM (L"Duplicate tier", 0) NATURAL (L"Position", L"1 (= at top)") SENTENCE (L"Name", L"") EDITOR_OK TextGrid grid = (TextGrid) my data; if (my selectedTier) { SET_STRING (L"Position", Melder_integer (my selectedTier + 1)) SET_STRING (L"Name", ((AnyTier) grid -> tiers -> item [my selectedTier]) -> name) } EDITOR_DO TextGrid grid = (TextGrid) my data; int position = GET_INTEGER (L"Position"); wchar *name = GET_STRING (L"Name"); checkTierSelection (me, L"duplicate a tier"); AnyTier tier = (AnyTier) grid -> tiers -> item [my selectedTier]; autoAnyTier newTier = Data_copy (tier); if (position > grid -> tiers -> size) position = grid -> tiers -> size + 1; Thing_setName (newTier.peek(), name); Editor_save (me, L"Duplicate tier"); Ordered_addItemPos (grid -> tiers, newTier.transfer(), position); my selectedTier = position; FunctionEditor_updateText (me); FunctionEditor_redraw (me); my broadcastDataChanged (); EDITOR_END } /***** HELP MENU *****/ static void menu_cb_TextGridEditorHelp (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); Melder_help (L"TextGridEditor"); } static void menu_cb_AboutSpecialSymbols (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); Melder_help (L"Special symbols"); } static void menu_cb_PhoneticSymbols (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); Melder_help (L"Phonetic symbols"); } static void menu_cb_AboutTextStyles (EDITOR_ARGS) { EDITOR_IAM (TextGridEditor); Melder_help (L"Text styles"); } void structTextGridEditor :: v_createMenus () { TextGridEditor_Parent :: v_createMenus (); EditorMenu menu; #ifndef macintosh Editor_addCommand (this, L"Edit", L"-- cut copy paste --", 0, NULL); Editor_addCommand (this, L"Edit", L"Cut text", 'X', menu_cb_Cut); Editor_addCommand (this, L"Edit", L"Cut", Editor_HIDDEN, menu_cb_Cut); Editor_addCommand (this, L"Edit", L"Copy text", 'C', menu_cb_Copy); Editor_addCommand (this, L"Edit", L"Copy", Editor_HIDDEN, menu_cb_Copy); Editor_addCommand (this, L"Edit", L"Paste text", 'V', menu_cb_Paste); Editor_addCommand (this, L"Edit", L"Paste", Editor_HIDDEN, menu_cb_Paste); Editor_addCommand (this, L"Edit", L"Erase text", 0, menu_cb_Erase); Editor_addCommand (this, L"Edit", L"Erase", Editor_HIDDEN, menu_cb_Erase); #endif Editor_addCommand (this, L"Edit", L"-- encoding --", 0, NULL); Editor_addCommand (this, L"Edit", L"Convert entire TextGrid to backslash trigraphs", 0, menu_cb_Genericize); Editor_addCommand (this, L"Edit", L"Genericize entire TextGrid", Editor_HIDDEN, menu_cb_Genericize); Editor_addCommand (this, L"Edit", L"Genericize", Editor_HIDDEN, menu_cb_Genericize); Editor_addCommand (this, L"Edit", L"Convert entire TextGrid to Unicode", 0, menu_cb_Nativize); Editor_addCommand (this, L"Edit", L"Nativize entire TextGrid", Editor_HIDDEN, menu_cb_Nativize); Editor_addCommand (this, L"Edit", L"Nativize", Editor_HIDDEN, menu_cb_Nativize); Editor_addCommand (this, L"Edit", L"-- search --", 0, NULL); Editor_addCommand (this, L"Edit", L"Find...", 'F', menu_cb_Find); Editor_addCommand (this, L"Edit", L"Find again", 'G', menu_cb_FindAgain); if (sound.data) { Editor_addCommand (this, L"Select", L"-- move to zero --", 0, 0); Editor_addCommand (this, L"Select", L"Move start of selection to nearest zero crossing", ',', menu_cb_MoveBtoZero); Editor_addCommand (this, L"Select", L"Move begin of selection to nearest zero crossing", Editor_HIDDEN, menu_cb_MoveBtoZero); Editor_addCommand (this, L"Select", L"Move cursor to nearest zero crossing", '0', menu_cb_MoveCursorToZero); Editor_addCommand (this, L"Select", L"Move end of selection to nearest zero crossing", '.', menu_cb_MoveEtoZero); } Editor_addCommand (this, L"Query", L"-- query interval --", 0, NULL); Editor_addCommand (this, L"Query", L"Get starting point of interval", 0, menu_cb_GetStartingPointOfInterval); Editor_addCommand (this, L"Query", L"Get end point of interval", 0, menu_cb_GetEndPointOfInterval); Editor_addCommand (this, L"Query", L"Get label of interval", 0, menu_cb_GetLabelOfInterval); menu = Editor_addMenu (this, L"Interval", 0); EditorMenu_addCommand (menu, L"Add interval on tier 1", GuiMenu_COMMAND | '1', menu_cb_InsertIntervalOnTier1); EditorMenu_addCommand (menu, L"Add interval on tier 2", GuiMenu_COMMAND | '2', menu_cb_InsertIntervalOnTier2); EditorMenu_addCommand (menu, L"Add interval on tier 3", GuiMenu_COMMAND | '3', menu_cb_InsertIntervalOnTier3); EditorMenu_addCommand (menu, L"Add interval on tier 4", GuiMenu_COMMAND | '4', menu_cb_InsertIntervalOnTier4); EditorMenu_addCommand (menu, L"Add interval on tier 5", GuiMenu_COMMAND | '5', menu_cb_InsertIntervalOnTier5); EditorMenu_addCommand (menu, L"Add interval on tier 6", GuiMenu_COMMAND | '6', menu_cb_InsertIntervalOnTier6); EditorMenu_addCommand (menu, L"Add interval on tier 7", GuiMenu_COMMAND | '7', menu_cb_InsertIntervalOnTier7); EditorMenu_addCommand (menu, L"Add interval on tier 8", GuiMenu_COMMAND | '8', menu_cb_InsertIntervalOnTier8); menu = Editor_addMenu (this, L"Boundary", 0); /*EditorMenu_addCommand (menu, L"Move to B", 0, menu_cb_MoveToB); EditorMenu_addCommand (menu, L"Move to E", 0, menu_cb_MoveToE);*/ if (sound.data) EditorMenu_addCommand (menu, L"Move to nearest zero crossing", 0, menu_cb_MoveToZero); EditorMenu_addCommand (menu, L"-- insert boundary --", 0, NULL); EditorMenu_addCommand (menu, L"Add on selected tier", GuiMenu_ENTER, menu_cb_InsertOnSelectedTier); EditorMenu_addCommand (menu, L"Add on tier 1", GuiMenu_COMMAND | GuiMenu_F1, menu_cb_InsertOnTier1); EditorMenu_addCommand (menu, L"Add on tier 2", GuiMenu_COMMAND | GuiMenu_F2, menu_cb_InsertOnTier2); EditorMenu_addCommand (menu, L"Add on tier 3", GuiMenu_COMMAND | GuiMenu_F3, menu_cb_InsertOnTier3); EditorMenu_addCommand (menu, L"Add on tier 4", GuiMenu_COMMAND | GuiMenu_F4, menu_cb_InsertOnTier4); EditorMenu_addCommand (menu, L"Add on tier 5", GuiMenu_COMMAND | GuiMenu_F5, menu_cb_InsertOnTier5); EditorMenu_addCommand (menu, L"Add on tier 6", GuiMenu_COMMAND | GuiMenu_F6, menu_cb_InsertOnTier6); EditorMenu_addCommand (menu, L"Add on tier 7", GuiMenu_COMMAND | GuiMenu_F7, menu_cb_InsertOnTier7); EditorMenu_addCommand (menu, L"Add on tier 8", GuiMenu_COMMAND | GuiMenu_F8, menu_cb_InsertOnTier8); EditorMenu_addCommand (menu, L"Add on all tiers", GuiMenu_COMMAND | GuiMenu_F9, menu_cb_InsertOnAllTiers); EditorMenu_addCommand (menu, L"-- remove mark --", 0, NULL); EditorMenu_addCommand (menu, L"Remove", GuiMenu_OPTION | GuiMenu_BACKSPACE, menu_cb_RemovePointOrBoundary); menu = Editor_addMenu (this, L"Tier", 0); EditorMenu_addCommand (menu, L"Add interval tier...", 0, menu_cb_AddIntervalTier); EditorMenu_addCommand (menu, L"Add point tier...", 0, menu_cb_AddPointTier); EditorMenu_addCommand (menu, L"Duplicate tier...", 0, menu_cb_DuplicateTier); EditorMenu_addCommand (menu, L"Rename tier...", 0, menu_cb_RenameTier); EditorMenu_addCommand (menu, L"-- remove tier --", 0, NULL); EditorMenu_addCommand (menu, L"Remove all text from tier", 0, menu_cb_RemoveAllTextFromTier); EditorMenu_addCommand (menu, L"Remove entire tier", 0, menu_cb_RemoveTier); EditorMenu_addCommand (menu, L"-- extract tier --", 0, NULL); EditorMenu_addCommand (menu, L"Extract to list of objects:", GuiMenu_INSENSITIVE, menu_cb_PublishTier /* dummy */); EditorMenu_addCommand (menu, L"Extract entire selected tier", 0, menu_cb_PublishTier); if (spellingChecker) { menu = Editor_addMenu (this, L"Spell", 0); EditorMenu_addCommand (menu, L"Check spelling in tier", GuiMenu_COMMAND | GuiMenu_OPTION | 'L', menu_cb_CheckSpelling); EditorMenu_addCommand (menu, L"Check spelling in interval", 0, menu_cb_CheckSpellingInInterval); EditorMenu_addCommand (menu, L"-- edit lexicon --", 0, NULL); EditorMenu_addCommand (menu, L"Add selected word to user dictionary", 0, menu_cb_AddToUserDictionary); } if (sound.data || longSound.data) { if (v_hasAnalysis ()) { v_createMenus_analysis (); // insert some of the ancestor's menus *after* the TextGrid menus } } } void structTextGridEditor :: v_createHelpMenuItems (EditorMenu menu) { TextGridEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"TextGridEditor help", '?', menu_cb_TextGridEditorHelp); EditorMenu_addCommand (menu, L"About special symbols", 0, menu_cb_AboutSpecialSymbols); EditorMenu_addCommand (menu, L"Phonetic symbols", 0, menu_cb_PhoneticSymbols); EditorMenu_addCommand (menu, L"About text styles", 0, menu_cb_AboutTextStyles); } /***** CHILDREN *****/ static void gui_text_cb_change (I, GuiTextEvent event) { iam (TextGridEditor); (void) event; TextGrid grid = (TextGrid) my data; //Melder_casual ("gui_text_cb_change 1 in editor %ld", me); if (my suppressRedraw) return; /* Prevent infinite loop if 'draw' method or Editor_broadcastChange calls GuiText_setString. */ //Melder_casual ("gui_text_cb_change 2 in editor %ld", me); if (my selectedTier) { wchar_t *text = GuiText_getString (my text); IntervalTier intervalTier; TextTier textTier; _AnyTier_identifyClass ((Function) grid -> tiers -> item [my selectedTier], & intervalTier, & textTier); if (intervalTier) { long selectedInterval = getSelectedInterval (me); if (selectedInterval) { TextInterval interval = (TextInterval) intervalTier -> intervals -> item [selectedInterval]; //Melder_casual ("gui_text_cb_change 3 in editor %ld", me); TextInterval_setText (interval, text); //Melder_casual ("gui_text_cb_change 4 in editor %ld", me); FunctionEditor_redraw (me); //Melder_casual ("gui_text_cb_change 5 in editor %ld", me); my broadcastDataChanged (); //Melder_casual ("gui_text_cb_change 6 in editor %ld", me); } } else { long selectedPoint = getSelectedPoint (me); if (selectedPoint) { TextPoint point = (TextPoint) textTier -> points -> item [selectedPoint]; Melder_free (point -> mark); if (wcsspn (text, L" \n\t") != wcslen (text)) // any visible characters? point -> mark = Melder_wcsdup_f (text); FunctionEditor_redraw (me); my broadcastDataChanged (); } } Melder_free (text); } } void structTextGridEditor :: v_createChildren () { TextGridEditor_Parent :: v_createChildren (); GuiText_setChangeCallback (text, gui_text_cb_change, this); } void structTextGridEditor :: v_dataChanged () { TextGrid grid = (TextGrid) data; /* * Perform a minimal selection change. * Most changes will involve intervals and boundaries; however, there may also be tier removals. * Do a simple guess. */ if (selectedTier > grid -> tiers -> size) { selectedTier = grid -> tiers -> size; } TextGridEditor_Parent :: v_dataChanged (); // does all the updating } /********** DRAWING AREA **********/ void structTextGridEditor :: v_prepareDraw () { if (longSound.data) { try { LongSound_haveWindow (longSound.data, startWindow, endWindow); } catch (MelderError) { Melder_clearError (); } } } static void do_drawIntervalTier (TextGridEditor me, IntervalTier tier, int itier) { #if gtk || defined (macintosh) bool platformUsesAntiAliasing = true; #else bool platformUsesAntiAliasing = false; #endif long x1DC, x2DC, yDC; int selectedInterval = itier == my selectedTier ? getSelectedInterval (me) : 0, iinterval, ninterval = tier -> intervals -> size; Graphics_WCtoDC (my graphics, my startWindow, 0.0, & x1DC, & yDC); Graphics_WCtoDC (my graphics, my endWindow, 0.0, & x2DC, & yDC); Graphics_setPercentSignIsItalic (my graphics, my useTextStyles); Graphics_setNumberSignIsBold (my graphics, my useTextStyles); Graphics_setCircumflexIsSuperscript (my graphics, my useTextStyles); Graphics_setUnderscoreIsSubscript (my graphics, my useTextStyles); /* * Highlight interval: yellow (selected) or green (matching label). */ for (iinterval = 1; iinterval <= ninterval; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; double tmin = interval -> xmin, tmax = interval -> xmax; if (tmax > my startWindow && tmin < my endWindow) { /* Interval visible? */ int intervalIsSelected = iinterval == selectedInterval; int labelMatches = Melder_stringMatchesCriterion (interval -> text, my greenMethod, my greenString); if (tmin < my startWindow) tmin = my startWindow; if (tmax > my endWindow) tmax = my endWindow; if (labelMatches) { Graphics_setColour (my graphics, Graphics_LIME); Graphics_fillRectangle (my graphics, tmin, tmax, 0.0, 1.0); } if (intervalIsSelected) { if (labelMatches) { tmin = 0.85 * tmin + 0.15 * tmax; tmax = 0.15 * tmin + 0.85 * tmax; } Graphics_setColour (my graphics, Graphics_YELLOW); Graphics_fillRectangle (my graphics, tmin, tmax, labelMatches ? 0.15 : 0.0, labelMatches? 0.85: 1.0); } } } Graphics_setColour (my graphics, Graphics_BLACK); Graphics_line (my graphics, my endWindow, 0.0, my endWindow, 1.0); /* * Draw a grey bar and a selection button at the cursor position. */ if (my startSelection == my endSelection && my startSelection >= my startWindow && my startSelection <= my endWindow) { int cursorAtBoundary = FALSE; for (iinterval = 2; iinterval <= ninterval; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; if (interval -> xmin == my startSelection) cursorAtBoundary = TRUE; } if (! cursorAtBoundary) { double dy = Graphics_dyMMtoWC (my graphics, 1.5); Graphics_setGrey (my graphics, 0.8); Graphics_setLineWidth (my graphics, platformUsesAntiAliasing ? 6.0 : 5.0); Graphics_line (my graphics, my startSelection, 0.0, my startSelection, 1.0); Graphics_setLineWidth (my graphics, 1.0); Graphics_setColour (my graphics, Graphics_BLUE); Graphics_circle_mm (my graphics, my startSelection, 1.0 - dy, 3.0); } } Graphics_setTextAlignment (my graphics, my alignment, Graphics_HALF); for (iinterval = 1; iinterval <= ninterval; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; double tmin = interval -> xmin, tmax = interval -> xmax; if (tmin < my tmin) tmin = my tmin; if (tmax > my tmax) tmax = my tmax; if (tmin >= tmax) continue; bool intervalIsSelected = selectedInterval == iinterval; /* * Draw left boundary. */ if (tmin >= my startWindow && tmin <= my endWindow && iinterval > 1) { bool boundaryIsSelected = ( my selectedTier == itier && tmin == my startSelection ); Graphics_setColour (my graphics, boundaryIsSelected ? Graphics_RED : Graphics_BLUE); Graphics_setLineWidth (my graphics, platformUsesAntiAliasing ? 6.0 : 5.0); Graphics_line (my graphics, tmin, 0.0, tmin, 1.0); /* * Show alignment with cursor. */ if (tmin == my startSelection) { Graphics_setColour (my graphics, Graphics_YELLOW); Graphics_setLineWidth (my graphics, platformUsesAntiAliasing ? 2.0 : 1.0); Graphics_line (my graphics, tmin, 0.0, tmin, 1.0); } } Graphics_setLineWidth (my graphics, 1.0); /* * Draw label text. */ if (interval -> text && tmax >= my startWindow && tmin <= my endWindow) { double t1 = my startWindow > tmin ? my startWindow : tmin; double t2 = my endWindow < tmax ? my endWindow : tmax; Graphics_setColour (my graphics, intervalIsSelected ? Graphics_RED : Graphics_BLACK); Graphics_textRect (my graphics, t1, t2, 0.0, 1.0, interval -> text); Graphics_setColour (my graphics, Graphics_BLACK); } } Graphics_setPercentSignIsItalic (my graphics, TRUE); Graphics_setNumberSignIsBold (my graphics, TRUE); Graphics_setCircumflexIsSuperscript (my graphics, TRUE); Graphics_setUnderscoreIsSubscript (my graphics, TRUE); } static void do_drawTextTier (TextGridEditor me, TextTier tier, int itier) { #if gtk || defined (macintosh) bool platformUsesAntiAliasing = true; #else bool platformUsesAntiAliasing = false; #endif int ipoint, npoint = tier -> points -> size; Graphics_setPercentSignIsItalic (my graphics, my useTextStyles); Graphics_setNumberSignIsBold (my graphics, my useTextStyles); Graphics_setCircumflexIsSuperscript (my graphics, my useTextStyles); Graphics_setUnderscoreIsSubscript (my graphics, my useTextStyles); /* * Draw a grey bar and a selection button at the cursor position. */ if (my startSelection == my endSelection && my startSelection >= my startWindow && my startSelection <= my endWindow) { int cursorAtPoint = FALSE; for (ipoint = 1; ipoint <= npoint; ipoint ++) { TextPoint point = (TextPoint) tier -> points -> item [ipoint]; if (point -> number == my startSelection) cursorAtPoint = TRUE; } if (! cursorAtPoint) { double dy = Graphics_dyMMtoWC (my graphics, 1.5); Graphics_setGrey (my graphics, 0.8); Graphics_setLineWidth (my graphics, platformUsesAntiAliasing ? 6.0 : 5.0); Graphics_line (my graphics, my startSelection, 0.0, my startSelection, 1.0); Graphics_setLineWidth (my graphics, 1.0); Graphics_setColour (my graphics, Graphics_BLUE); Graphics_circle_mm (my graphics, my startSelection, 1.0 - dy, 3.0); } } Graphics_setTextAlignment (my graphics, Graphics_CENTRE, Graphics_HALF); for (ipoint = 1; ipoint <= npoint; ipoint ++) { TextPoint point = (TextPoint) tier -> points -> item [ipoint]; double t = point -> number; if (t >= my startWindow && t <= my endWindow) { bool pointIsSelected = ( itier == my selectedTier && t == my startSelection ); Graphics_setColour (my graphics, pointIsSelected ? Graphics_RED : Graphics_BLUE); Graphics_setLineWidth (my graphics, platformUsesAntiAliasing ? 6.0 : 5.0); Graphics_line (my graphics, t, 0.0, t, 0.2); Graphics_line (my graphics, t, 0.8, t, 1); Graphics_setLineWidth (my graphics, 1.0); /* * Wipe out the cursor where the text is going to be. */ Graphics_setColour (my graphics, Graphics_WHITE); Graphics_line (my graphics, t, 0.2, t, 0.8); /* * Show alignment with cursor. */ if (my startSelection == my endSelection && t == my startSelection) { Graphics_setColour (my graphics, Graphics_YELLOW); Graphics_setLineWidth (my graphics, platformUsesAntiAliasing ? 2.0 : 1.0); Graphics_line (my graphics, t, 0.0, t, 0.2); Graphics_line (my graphics, t, 0.8, t, 1.0); } Graphics_setColour (my graphics, pointIsSelected ? Graphics_RED : Graphics_BLUE); if (point -> mark) Graphics_text (my graphics, t, 0.5, point -> mark); } } Graphics_setPercentSignIsItalic (my graphics, TRUE); Graphics_setNumberSignIsBold (my graphics, TRUE); Graphics_setCircumflexIsSuperscript (my graphics, TRUE); Graphics_setUnderscoreIsSubscript (my graphics, TRUE); } void structTextGridEditor :: v_draw () { TextGrid grid = (TextGrid) data; Graphics_Viewport vp1, vp2; long itier, ntier = grid -> tiers -> size; enum kGraphics_font oldFont = Graphics_inqFont (graphics); int oldFontSize = Graphics_inqFontSize (graphics); bool showAnalysis = v_hasAnalysis () && (spectrogram.show || pitch.show || intensity.show || formant.show) && (longSound.data || sound.data); double soundY = _TextGridEditor_computeSoundY (this), soundY2 = showAnalysis ? 0.5 * (1.0 + soundY) : soundY; /* * Draw optional sound. */ if (longSound.data || sound.data) { vp1 = Graphics_insetViewport (graphics, 0.0, 1.0, soundY2, 1.0); Graphics_setColour (graphics, Graphics_WHITE); Graphics_setWindow (graphics, 0, 1, 0, 1); Graphics_fillRectangle (graphics, 0, 1, 0, 1); TimeSoundEditor_draw_sound (this, -1.0, 1.0); Graphics_flushWs (graphics); Graphics_resetViewport (graphics, vp1); } /* * Draw tiers. */ if (longSound.data || sound.data) vp1 = Graphics_insetViewport (graphics, 0.0, 1.0, 0.0, soundY); Graphics_setColour (graphics, Graphics_WHITE); Graphics_setWindow (graphics, 0, 1, 0, 1); Graphics_fillRectangle (graphics, 0, 1, 0, 1); Graphics_setColour (graphics, Graphics_BLACK); Graphics_rectangle (graphics, 0, 1, 0, 1); Graphics_setWindow (graphics, startWindow, endWindow, 0.0, 1.0); for (itier = 1; itier <= ntier; itier ++) { Function anyTier = (Function) grid -> tiers -> item [itier]; bool tierIsSelected = itier == selectedTier; bool isIntervalTier = anyTier -> classInfo == classIntervalTier; vp2 = Graphics_insetViewport (graphics, 0.0, 1.0, 1.0 - (double) itier / (double) ntier, 1.0 - (double) (itier - 1) / (double) ntier); Graphics_setColour (graphics, Graphics_BLACK); if (itier != 1) Graphics_line (graphics, startWindow, 1.0, endWindow, 1.0); /* * Show the number and the name of the tier. */ Graphics_setColour (graphics, tierIsSelected ? Graphics_RED : Graphics_BLACK); Graphics_setFont (graphics, oldFont); Graphics_setFontSize (graphics, 14); Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); Graphics_text2 (graphics, startWindow, 0.5, tierIsSelected ? L"\\pf " : L"", Melder_integer (itier)); Graphics_setFontSize (graphics, oldFontSize); if (anyTier -> name && anyTier -> name [0]) { Graphics_setTextAlignment (graphics, Graphics_LEFT, showNumberOf == kTextGridEditor_showNumberOf_NOTHING ? Graphics_HALF : Graphics_BOTTOM); Graphics_text (graphics, endWindow, 0.5, anyTier -> name); } if (showNumberOf != kTextGridEditor_showNumberOf_NOTHING) { Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_TOP); if (showNumberOf == kTextGridEditor_showNumberOf_INTERVALS_OR_POINTS) { long count = isIntervalTier ? ((IntervalTier) anyTier) -> intervals -> size : ((TextTier) anyTier) -> points -> size; long position = itier == selectedTier ? ( isIntervalTier ? getSelectedInterval (this) : getSelectedPoint (this) ) : 0; if (position) { Graphics_text5 (graphics, endWindow, 0.5, L"(", Melder_integer (position), L"/", Melder_integer (count), L")"); } else { Graphics_text3 (graphics, endWindow, 0.5, L"(", Melder_integer (count), L")"); } } else { Melder_assert (kTextGridEditor_showNumberOf_NONEMPTY_INTERVALS_OR_POINTS); long count = 0; if (isIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long ninterval = tier -> intervals -> size, iinterval; for (iinterval = 1; iinterval <= ninterval; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; if (interval -> text != NULL && interval -> text [0] != '\0') { count ++; } } } else { TextTier tier = (TextTier) anyTier; long npoint = tier -> points -> size, ipoint; for (ipoint = 1; ipoint <= npoint; ipoint ++) { TextPoint point = (TextPoint) tier -> points -> item [ipoint]; if (point -> mark != NULL && point -> mark [0] != '\0') { count ++; } } } Graphics_text3 (graphics, endWindow, 0.5, L"(##", Melder_integer (count), L"#)"); } } Graphics_setColour (graphics, Graphics_BLACK); Graphics_setFont (graphics, kGraphics_font_TIMES); Graphics_setFontSize (graphics, fontSize); if (isIntervalTier) do_drawIntervalTier (this, (IntervalTier) anyTier, itier); else do_drawTextTier (this, (TextTier) anyTier, itier); Graphics_resetViewport (graphics, vp2); } Graphics_setColour (graphics, Graphics_BLACK); Graphics_setFont (graphics, oldFont); Graphics_setFontSize (graphics, oldFontSize); if (longSound.data || sound.data) Graphics_resetViewport (graphics, vp1); Graphics_flushWs (graphics); if (showAnalysis) { vp1 = Graphics_insetViewport (graphics, 0.0, 1.0, soundY, soundY2); v_draw_analysis (); Graphics_flushWs (graphics); Graphics_resetViewport (graphics, vp1); /* Draw pulses. */ if (pulses.show) { vp1 = Graphics_insetViewport (graphics, 0.0, 1.0, soundY2, 1.0); v_draw_analysis_pulses (); TimeSoundEditor_draw_sound (this, -1.0, 1.0); // second time, partially across the pulses Graphics_flushWs (graphics); Graphics_resetViewport (graphics, vp1); } } Graphics_setWindow (graphics, startWindow, endWindow, 0.0, 1.0); if (longSound.data || sound.data) { Graphics_line (graphics, startWindow, soundY, endWindow, soundY); if (showAnalysis) { Graphics_line (graphics, startWindow, soundY2, endWindow, soundY2); Graphics_line (graphics, startWindow, soundY, startWindow, soundY2); Graphics_line (graphics, endWindow, soundY, endWindow, soundY2); } } /* * Finally, us usual, update the menus. */ v_updateMenuItems_file (); } static void do_drawWhileDragging (TextGridEditor me, double numberOfTiers, int *selectedTier, double x, double soundY) { long itier; for (itier = 1; itier <= numberOfTiers; itier ++) if (selectedTier [itier]) { double ymin = soundY * (1.0 - (double) itier / numberOfTiers); double ymax = soundY * (1.0 - (double) (itier - 1) / numberOfTiers); Graphics_setLineWidth (my graphics, 7); Graphics_line (my graphics, x, ymin, x, ymax); } Graphics_setLineWidth (my graphics, 1); Graphics_line (my graphics, x, 0, x, 1.01); Graphics_text1 (my graphics, x, 1.01, Melder_fixed (x, 6)); } static void do_dragBoundary (TextGridEditor me, double xbegin, int iClickedTier, int shiftKeyPressed) { TextGrid grid = (TextGrid) my data; int itier, numberOfTiers = grid -> tiers -> size, itierDrop; double xWC = xbegin, yWC; double leftDraggingBoundary = my tmin, rightDraggingBoundary = my tmax; /* Initial dragging range. */ int selectedTier [100]; double soundY = _TextGridEditor_computeSoundY (me); /* * Determine the set of selected boundaries and points, and the dragging range. */ for (itier = 1; itier <= numberOfTiers; itier ++) { selectedTier [itier] = FALSE; /* The default. */ /* * If she has pressed the shift key, let her drag all the boundaries and points at this time. * Otherwise, let her only drag the boundary or point on the clicked tier. */ if (itier == iClickedTier || shiftKeyPressed == my shiftDragMultiple) { IntervalTier intervalTier; TextTier textTier; _AnyTier_identifyClass ((Function) grid -> tiers -> item [itier], & intervalTier, & textTier); if (intervalTier) { long ibound = IntervalTier_hasBoundary (intervalTier, xbegin); if (ibound) { TextInterval leftInterval = (TextInterval) intervalTier -> intervals -> item [ibound - 1]; TextInterval rightInterval = (TextInterval) intervalTier -> intervals -> item [ibound]; selectedTier [itier] = TRUE; /* * Prevent her to drag the boundary past its left or right neighbours on the same tier. */ if (leftInterval -> xmin > leftDraggingBoundary) { leftDraggingBoundary = leftInterval -> xmin; } if (rightInterval -> xmax < rightDraggingBoundary) { rightDraggingBoundary = rightInterval -> xmax; } } } else { if (AnyTier_hasPoint (textTier, xbegin)) { /* * Other than with boundaries on interval tiers, * points on text tiers can be dragged past their neighbours. */ selectedTier [itier] = TRUE; } } } } Graphics_xorOn (my graphics, Graphics_MAROON); Graphics_setTextAlignment (my graphics, Graphics_CENTRE, Graphics_BOTTOM); do_drawWhileDragging (me, numberOfTiers, selectedTier, xWC, soundY); // draw at old position while (Graphics_mouseStillDown (my graphics)) { double xWC_new; Graphics_getMouseLocation (my graphics, & xWC_new, & yWC); if (xWC_new != xWC) { do_drawWhileDragging (me, numberOfTiers, selectedTier, xWC, soundY); // undraw at old position xWC = xWC_new; do_drawWhileDragging (me, numberOfTiers, selectedTier, xWC, soundY); // draw at new position } } do_drawWhileDragging (me, numberOfTiers, selectedTier, xWC, soundY); // undraw at new position Graphics_xorOff (my graphics); /* * The simplest way to cancel the dragging operation, is to drag outside the window. */ if (xWC <= my startWindow || xWC >= my endWindow) { return; } /* * If she dropped near an existing boundary in an unselected tier or near the cursor, we snap to that mark. */ itierDrop = _TextGridEditor_yWCtoTier (me, yWC); if (yWC > 0.0 && yWC < soundY && ! selectedTier [itierDrop]) { // dropped inside an unselected tier? Function anyTierDrop = (Function) grid -> tiers -> item [itierDrop]; if (anyTierDrop -> classInfo == classIntervalTier) { IntervalTier tierDrop = (IntervalTier) anyTierDrop; long ibound; for (ibound = 1; ibound < tierDrop -> intervals -> size; ibound ++) { TextInterval left = (TextInterval) tierDrop -> intervals -> item [ibound]; if (fabs (Graphics_dxWCtoMM (my graphics, xWC - left -> xmax)) < 1.5) { // near a boundary? /* * Snap to boundary. */ xWC = left -> xmax; } } } else { TextTier tierDrop = (TextTier) anyTierDrop; long ipoint; for (ipoint = 1; ipoint <= tierDrop -> points -> size; ipoint ++) { TextPoint point = (TextPoint) tierDrop -> points -> item [ipoint]; if (fabs (Graphics_dxWCtoMM (my graphics, xWC - point -> number)) < 1.5) { // near a point? /* * Snap to point. */ xWC = point -> number; } } } } else if (xbegin != my startSelection && fabs (Graphics_dxWCtoMM (my graphics, xWC - my startSelection)) < 1.5) { // near the cursor? /* * Snap to cursor. */ xWC = my startSelection; } else if (xbegin != my endSelection && fabs (Graphics_dxWCtoMM (my graphics, xWC - my endSelection)) < 1.5) { // near the cursor? /* * Snap to cursor. */ xWC = my endSelection; } /* * We cannot move a boundary out of the dragging range. */ if (xWC <= leftDraggingBoundary || xWC >= rightDraggingBoundary) { Melder_beep (); return; } Editor_save (me, L"Drag"); for (itier = 1; itier <= numberOfTiers; itier ++) if (selectedTier [itier]) { IntervalTier intervalTier; TextTier textTier; _AnyTier_identifyClass ((Function) grid -> tiers -> item [itier], & intervalTier, & textTier); if (intervalTier) { long ibound, numberOfIntervals = intervalTier -> intervals -> size; Any *intervals = intervalTier -> intervals -> item; for (ibound = 2; ibound <= numberOfIntervals; ibound ++) { TextInterval left = (TextInterval) intervals [ibound - 1], right = (TextInterval) intervals [ibound]; if (left -> xmax == xbegin) { // boundary dragged? left -> xmax = right -> xmin = xWC; // move boundary to drop site break; } } } else { long iDraggedPoint = AnyTier_hasPoint (textTier, xbegin); if (iDraggedPoint) { long dropSiteHasPoint = AnyTier_hasPoint (textTier, xWC); if (dropSiteHasPoint) { Melder_warning (L"Cannot drop point on an existing point."); } else { TextPoint point = (TextPoint) textTier -> points -> item [iDraggedPoint]; /* * Move point to drop site. May have passed another point. */ TextPoint newPoint = Data_copy (point); newPoint -> number = xWC; // move point to drop site Collection_removeItem (textTier -> points, iDraggedPoint); Collection_addItem (textTier -> points, newPoint); } } } } /* * Select the drop site. */ if (my startSelection == xbegin) my startSelection = xWC; if (my endSelection == xbegin) my endSelection = xWC; if (my startSelection > my endSelection) { double dummy = my startSelection; my startSelection = my endSelection; my endSelection = dummy; } FunctionEditor_marksChanged (me); my broadcastDataChanged (); } int structTextGridEditor :: v_click (double xclick, double yWC, bool shiftKeyPressed) { TextGrid grid = (TextGrid) data; double tmin, tmax, x, y; long ntiers = grid -> tiers -> size, iClickedTier, iClickedInterval, iClickedPoint; int clickedLeftBoundary = 0, nearBoundaryOrPoint, nearCursorCircle, drag = FALSE; IntervalTier intervalTier; TextTier textTier; TextInterval interval = NULL; TextPoint point = NULL; double soundY = _TextGridEditor_computeSoundY (this); double tnear; /* * In answer to a click in the sound part, * we keep the same tier selected and move the cursor or drag the "yellow" selection. */ if (yWC > soundY) { /* Clicked in sound part? */ if ((spectrogram.show || formant.show) && yWC < 0.5 * (soundY + 1.0)) { spectrogram.cursor = spectrogram.viewFrom + 2.0 * (yWC - soundY) / (1.0 - soundY) * (spectrogram.viewTo - spectrogram.viewFrom); } TextGridEditor_Parent :: v_click (xclick, yWC, shiftKeyPressed); return FunctionEditor_UPDATE_NEEDED; } /* * She clicked in the grid part. * We select the tier in which she clicked. */ iClickedTier = _TextGridEditor_yWCtoTier (this, yWC); if (xclick <= startWindow || xclick >= endWindow) { selectedTier = iClickedTier; return FunctionEditor_UPDATE_NEEDED; } _TextGridEditor_timeToInterval (this, xclick, iClickedTier, & tmin, & tmax); _AnyTier_identifyClass ((Function) grid -> tiers -> item [iClickedTier], & intervalTier, & textTier); /* * Get the time of the nearest boundary or point. */ tnear = NUMundefined; if (intervalTier) { iClickedInterval = IntervalTier_timeToIndex (intervalTier, xclick); if (iClickedInterval) { interval = (TextInterval) intervalTier -> intervals -> item [iClickedInterval]; if (xclick > 0.5 * (interval -> xmin + interval -> xmax)) { tnear = interval -> xmax; clickedLeftBoundary = iClickedInterval + 1; } else { tnear = interval -> xmin; clickedLeftBoundary = iClickedInterval; } } else { /* * She clicked outside time domain of intervals. * This can occur when we are grouped with a longer time function. */ selectedTier = iClickedTier; return FunctionEditor_UPDATE_NEEDED; } } else { iClickedPoint = AnyTier_timeToNearestIndex (textTier, xclick); if (iClickedPoint) { point = (TextPoint) textTier -> points -> item [iClickedPoint]; tnear = point -> number; } } Melder_assert (! (intervalTier && ! clickedLeftBoundary)); /* * Where did she click? */ nearBoundaryOrPoint = tnear != NUMundefined && fabs (Graphics_dxWCtoMM (graphics, xclick - tnear)) < 1.5; nearCursorCircle = startSelection == endSelection && Graphics_distanceWCtoMM (graphics, xclick, yWC, startSelection, (ntiers + 1 - iClickedTier) * soundY / ntiers - Graphics_dyMMtoWC (graphics, 1.5)) < 1.5; /* * Find out whether this is a click or a drag. */ while (Graphics_mouseStillDown (graphics)) { Graphics_getMouseLocation (graphics, & x, & y); if (x < startWindow) x = startWindow; if (x > endWindow) x = endWindow; if (fabs (Graphics_dxWCtoMM (graphics, x - xclick)) > 1.5) { drag = TRUE; break; } } if (nearBoundaryOrPoint) { /* * Possibility 1: she clicked near a boundary or point. * Select or drag it. */ if (intervalTier && (clickedLeftBoundary < 2 || clickedLeftBoundary > intervalTier -> intervals -> size)) { /* * Ignore click on left edge of first interval or right edge of last interval. */ selectedTier = iClickedTier; } else if (drag) { /* * The tier that has been clicked becomes the new selected tier. * This has to be done before the next Update, i.e. also before do_dragBoundary! */ selectedTier = iClickedTier; do_dragBoundary (this, tnear, iClickedTier, shiftKeyPressed); return FunctionEditor_NO_UPDATE_NEEDED; } else { /* * If she clicked on an unselected boundary or point, we select it. */ if (shiftKeyPressed) { if (tnear > 0.5 * (startSelection + endSelection)) endSelection = tnear; else startSelection = tnear; } else { startSelection = endSelection = tnear; /* Move cursor so that the boundary or point is selected. */ } selectedTier = iClickedTier; } } else if (nearCursorCircle) { /* * Possibility 2: she clicked near the cursor circle. * Insert boundary or point. There is no danger that we insert on top of an existing boundary or point, * because we are not 'nearBoundaryOrPoint'. */ insertBoundaryOrPoint (this, iClickedTier, startSelection, startSelection, false); selectedTier = iClickedTier; FunctionEditor_marksChanged (this); broadcastDataChanged (); if (drag) Graphics_waitMouseUp (graphics); return FunctionEditor_NO_UPDATE_NEEDED; } else { /* * Possibility 3: she clicked in empty space. */ if (intervalTier) { startSelection = tmin; endSelection = tmax; } selectedTier = iClickedTier; } if (drag) Graphics_waitMouseUp (graphics); return FunctionEditor_UPDATE_NEEDED; } int structTextGridEditor :: v_clickB (double t, double yWC) { double soundY = _TextGridEditor_computeSoundY (this); if (yWC > soundY) { // clicked in sound part? startSelection = t; if (startSelection > endSelection) { double dummy = startSelection; startSelection = endSelection; endSelection = dummy; } return FunctionEditor_UPDATE_NEEDED; } int itier = _TextGridEditor_yWCtoTier (this, yWC); double tmin, tmax; _TextGridEditor_timeToInterval (this, t, itier, & tmin, & tmax); startSelection = t - tmin < tmax - t ? tmin : tmax; // to nearest boundary if (startSelection > endSelection) { double dummy = startSelection; startSelection = endSelection; endSelection = dummy; } return FunctionEditor_UPDATE_NEEDED; } int structTextGridEditor :: v_clickE (double t, double yWC) { double soundY = _TextGridEditor_computeSoundY (this); if (yWC > soundY) { // clicked in sound part? endSelection = t; if (startSelection > endSelection) { double dummy = startSelection; startSelection = endSelection; endSelection = dummy; } return FunctionEditor_UPDATE_NEEDED; } int itier = _TextGridEditor_yWCtoTier (this, yWC); double tmin, tmax; _TextGridEditor_timeToInterval (this, t, itier, & tmin, & tmax); endSelection = t - tmin < tmax - t ? tmin : tmax; if (startSelection > endSelection) { double dummy = startSelection; startSelection = endSelection; endSelection = dummy; } return FunctionEditor_UPDATE_NEEDED; } void structTextGridEditor :: v_play (double tmin, double tmax) { if (longSound.data) { LongSound_playPart (longSound.data, tmin, tmax, theFunctionEditor_playCallback, this); } else if (sound.data) { Sound_playPart (sound.data, tmin, tmax, theFunctionEditor_playCallback, this); } } void structTextGridEditor :: v_updateText () { TextGrid grid = (TextGrid) data; const wchar *newText = L""; if (selectedTier) { IntervalTier intervalTier; TextTier textTier; _AnyTier_identifyClass ((Function) grid -> tiers -> item [selectedTier], & intervalTier, & textTier); if (intervalTier) { long iinterval = IntervalTier_timeToIndex (intervalTier, startSelection); if (iinterval) { TextInterval interval = (TextInterval) intervalTier -> intervals -> item [iinterval]; if (interval -> text) { newText = interval -> text; } } } else { long ipoint = AnyTier_hasPoint (textTier, startSelection); if (ipoint) { TextPoint point = (TextPoint) textTier -> points -> item [ipoint]; if (point -> mark) { newText = point -> mark; } } } } //Melder_casual ("v_updateText in editor %ld %ls %d", this, name, (int) suppressRedraw); suppressRedraw = TRUE; // prevent valueChangedCallback from redrawing GuiText_setString (text, newText); long cursor = wcslen (newText); // at end GuiText_setSelection (text, cursor, cursor); suppressRedraw = FALSE; } void structTextGridEditor :: v_prefs_addFields (EditorCommand cmd) { Any radio; NATURAL (L"Font size (points)", TextGridEditor_DEFAULT_FONT_SIZE_STRING) OPTIONMENU_ENUM (L"Text alignment in intervals", kGraphics_horizontalAlignment, DEFAULT) OPTIONMENU (L"The symbols %#_^ in labels", TextGridEditor_DEFAULT_USE_TEXT_STYLES + 1) OPTION (L"are shown as typed") OPTION (L"mean italic/bold/sub/super") OPTIONMENU (L"With the shift key, you drag", TextGridEditor_DEFAULT_SHIFT_DRAG_MULTIPLE + 1) OPTION (L"a single boundary") OPTION (L"multiple boundaries") OPTIONMENU_ENUM (L"Show number of", kTextGridEditor_showNumberOf, DEFAULT) OPTIONMENU_ENUM (L"Paint intervals green whose label...", kMelder_string, DEFAULT) SENTENCE (L"...the text", TextGridEditor_DEFAULT_GREEN_STRING) } void structTextGridEditor :: v_prefs_setValues (EditorCommand cmd) { SET_INTEGER (L"The symbols %#_^ in labels", useTextStyles + 1) SET_INTEGER (L"Font size", fontSize) SET_ENUM (L"Text alignment in intervals", kGraphics_horizontalAlignment, alignment) SET_INTEGER (L"With the shift key, you drag", shiftDragMultiple + 1) SET_ENUM (L"Show number of", kTextGridEditor_showNumberOf, showNumberOf) SET_ENUM (L"Paint intervals green whose label...", kMelder_string, greenMethod) SET_STRING (L"...the text", greenString) } void structTextGridEditor :: v_prefs_getValues (EditorCommand cmd) { preferences.useTextStyles = useTextStyles = GET_INTEGER (L"The symbols %#_^ in labels") - 1; preferences.fontSize = fontSize = GET_INTEGER (L"Font size"); preferences.alignment = alignment = GET_ENUM (kGraphics_horizontalAlignment, L"Text alignment in intervals"); preferences.shiftDragMultiple = shiftDragMultiple = GET_INTEGER (L"With the shift key, you drag") - 1; preferences.showNumberOf = showNumberOf = GET_ENUM (kTextGridEditor_showNumberOf, L"Show number of"); preferences.greenMethod = greenMethod = GET_ENUM (kMelder_string, L"Paint intervals green whose label..."); wcsncpy (greenString, GET_STRING (L"...the text"), Preferences_STRING_BUFFER_SIZE); greenString [Preferences_STRING_BUFFER_SIZE - 1] = '\0'; wcscpy (preferences.greenString, greenString); FunctionEditor_redraw (this); } void structTextGridEditor :: v_createMenuItems_view_timeDomain (EditorMenu menu) { TextGridEditor_Parent :: v_createMenuItems_view_timeDomain (menu); EditorMenu_addCommand (menu, L"Select previous tier", GuiMenu_OPTION | GuiMenu_UP_ARROW, menu_cb_SelectPreviousTier); EditorMenu_addCommand (menu, L"Select next tier", GuiMenu_OPTION | GuiMenu_DOWN_ARROW, menu_cb_SelectNextTier); EditorMenu_addCommand (menu, L"Select previous interval", GuiMenu_OPTION | GuiMenu_LEFT_ARROW, menu_cb_SelectPreviousInterval); EditorMenu_addCommand (menu, L"Select next interval", GuiMenu_OPTION | GuiMenu_RIGHT_ARROW, menu_cb_SelectNextInterval); EditorMenu_addCommand (menu, L"Extend-select left", GuiMenu_SHIFT | GuiMenu_OPTION | GuiMenu_LEFT_ARROW, menu_cb_ExtendSelectPreviousInterval); EditorMenu_addCommand (menu, L"Extend-select right", GuiMenu_SHIFT | GuiMenu_OPTION | GuiMenu_RIGHT_ARROW, menu_cb_ExtendSelectNextInterval); } void structTextGridEditor :: v_highlightSelection (double left, double right, double bottom, double top) { if (v_hasAnalysis () && spectrogram.show && (longSound.data || sound.data)) { TextGrid grid = (TextGrid) data; double soundY = _TextGridEditor_computeSoundY (this), soundY2 = 0.5 * (1.0 + soundY); Graphics_highlight (graphics, left, right, bottom, soundY * top + (1 - soundY) * bottom); Graphics_highlight (graphics, left, right, soundY2 * top + (1 - soundY2) * bottom, top); } else { Graphics_highlight (graphics, left, right, bottom, top); } } void structTextGridEditor :: v_unhighlightSelection (double left, double right, double bottom, double top) { if (v_hasAnalysis () && spectrogram.show && (longSound.data || sound.data)) { TextGrid grid = (TextGrid) data; double soundY = _TextGridEditor_computeSoundY (this), soundY2 = 0.5 * (1.0 + soundY); Graphics_unhighlight (graphics, left, right, bottom, soundY * top + (1 - soundY) * bottom); Graphics_unhighlight (graphics, left, right, soundY2 * top + (1 - soundY2) * bottom, top); } else { Graphics_unhighlight (graphics, left, right, bottom, top); } } double structTextGridEditor :: v_getBottomOfSoundArea () { return _TextGridEditor_computeSoundY (this); } double structTextGridEditor :: v_getBottomOfSoundAndAnalysisArea () { return _TextGridEditor_computeSoundY (this); } void structTextGridEditor :: v_createMenuItems_pitch_picture (EditorMenu menu) { TextGridEditor_Parent :: v_createMenuItems_pitch_picture (menu); EditorMenu_addCommand (menu, L"Draw visible pitch contour and TextGrid...", 0, menu_cb_DrawTextGridAndPitch); } void structTextGridEditor :: v_updateMenuItems_file () { TextGridEditor_Parent :: v_updateMenuItems_file (); GuiObject_setSensitive (extractSelectedTextGridPreserveTimesButton, endSelection > startSelection); GuiObject_setSensitive (extractSelectedTextGridTimeFromZeroButton, endSelection > startSelection); } /********** EXPORTED **********/ void structTextGridEditor :: f_init (GuiObject parent, const wchar *title, TextGrid grid, Sampled a_sound, bool a_ownSound, SpellingChecker a_spellingChecker) { this -> spellingChecker = a_spellingChecker; // set in time TimeSoundAnalysisEditor_init (this, parent, title, grid, a_sound, a_ownSound); this -> useTextStyles = preferences.useTextStyles; this -> fontSize = preferences.fontSize; this -> alignment = preferences.alignment; this -> shiftDragMultiple = preferences.shiftDragMultiple; this -> showNumberOf = preferences.showNumberOf; this -> greenMethod = preferences.greenMethod; wcscpy (this -> greenString, preferences.greenString); this -> selectedTier = 1; if (this -> endWindow - this -> startWindow > 30.0) { this -> endWindow = this -> startWindow + 30.0; if (this -> startWindow == this -> tmin) this -> startSelection = this -> endSelection = 0.5 * (this -> startWindow + this -> endWindow); FunctionEditor_marksChanged (this); } if (a_spellingChecker != NULL) GuiText_setSelection (this -> text, 0, 0); } TextGridEditor TextGridEditor_create (GuiObject parent, const wchar *title, TextGrid grid, Sampled sound, bool ownSound, SpellingChecker spellingChecker) { try { autoTextGridEditor me = Thing_new (TextGridEditor); my f_init (parent, title, grid, sound, ownSound, spellingChecker); return me.transfer(); } catch (MelderError) { Melder_throw ("TextGrid window not created."); } } /* End of file TextGridEditor.cpp */ sources_5316/fon/Label.h0000644000176700017670000000513411621514363013702 0ustar paulpaul#ifndef _Label_h_ #define _Label_h_ /* Label.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection.h" #include "Function.h" Thing_define (Autosegment, Function) { // overridden methods: protected: virtual void v_copy (Any data_to); virtual bool v_equal (Any otherData); static Data_Description s_description; virtual Data_Description v_description () { return s_description; } }; Autosegment Autosegment_create (double tmin, double tmax, const wchar *label); /* Function: create a new instance of Autosegment. Return value: the new Autosegment, or NULL if out of memory. Preconditions: tmax > tmin; label may be NULL; Postconditions: result -> tmin == tmin; result -> tmax == tmax; if (label != NULL) result -> name == NULL; else result -> name [] == label []; // 'label' copied into 'name' */ Thing_define (Tier, Sorted) { // overridden methods: static int compare (Any data1, Any data2); virtual int (*v_getCompareFunction ()) (Any data1, Any data2) { return compare; } }; void Tier_init (I, long initialCapacity); Tier Tier_create (long initialCapacity); /* Function: create a new Tier containing one Autosegment from -1e30 to 1e30. Return value: the new Tier, or NULL if out of memory. Postconditions: my size == 1; my item [1] -> methods == classAutosegment; my item [1] -> xmin == -1e30; my item [1] -> xmax == 1e30; my item [1] -> name == NULL; */ long Tier_timeToIndex (Tier me, double t); /* Return value: index, or 0 if the tier is empty or t is very large. Postconditions: result == 0 || my item [i] -> xmin <= result < my item [i] -> xmax; */ void Tier_init (I, long initialCapacity); Thing_define (Label, Ordered) { }; Label Label_create (long initialNumberOfTiers); void Label_init (I, long initialNumberOfTiers); void Label_addTier (Label me); void Label_suggestDomain (Label me, double *tmin, double *tmax); #endif /* End of file Label.h */ sources_5316/fon/RealTier_def.h0000644000176700017670000000427411727455307015225 0ustar paulpaul/* RealTier_def.h * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT RealPoint oo_DEFINE_CLASS (RealPoint, AnyPoint) oo_DOUBLE (value) oo_END_CLASS (RealPoint) #undef ooSTRUCT #define ooSTRUCT RealTier oo_DEFINE_CLASS (RealTier, Function) oo_COLLECTION (SortedSetOfDouble, points, RealPoint, 0) #if oo_DECLARING // overridden methods: virtual void v_info (); virtual bool v_hasGetNx () { return true; } virtual double v_getNx () { return points -> size; } virtual bool v_hasGetX () { return true; } virtual double v_getX (long ix) { return ((RealPoint) points -> item [ix]) -> number; } virtual bool v_hasGetNcol () { return true; } virtual double v_getNcol () { return points -> size; } virtual bool v_hasGetVector () { return true; } virtual double v_getVector (long irow, long icol); virtual bool v_hasGetFunction1 () { return true; } virtual double v_getFunction1 (long irow, double x); virtual const wchar * v_getUnitText (long ilevel, int unit, unsigned long flags) { (void) ilevel; (void) unit; (void) flags; return L"Time (s)"; } virtual void v_shiftX (double xfrom, double xto); virtual void v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto); // new functions: long f_getNumberOfPoints () { return points -> size; } RealPoint f_peekPoint (long ipoint) { return (RealPoint) points -> item [ipoint]; } #endif oo_END_CLASS (RealTier) #undef ooSTRUCT /* End of file RealTier_def.h */ sources_5316/fon/manual_formant.cpp0000644000176700017670000010776211627220620016227 0ustar paulpaul/* manual_formant.cpp * * Copyright (C) 1992-2010 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" void manual_formant_init (ManPages me); void manual_formant_init (ManPages me) { MAN_BEGIN (L"Create FormantGrid...", L"ppgb", 20080425) INTRO (L"A command in the @@New menu@ to create an empty @FormantGrid object.") ENTRY (L"Settings") TAG (L"##Start time (s)") TAG (L"##End time (s)") DEFINITION (L"the @@time domain@ of the resulting FormantGrid.") TAG (L"##Number of formants# (e.g. 10)") DEFINITION (L"the number of formants in the resulting FormantGrid. For instance, if you set this to 10, " "the resulting FormantGrid will contain 10 formant tiers (for F1 through F10) " "and 10 bandwidth tiers (for B1 through B10). Each of these 20 tiers will contain one point.") TAG (L"##Initial first formant# (e.g. 550 Hz)") DEFINITION (L"the frequency value of the single formant point in the first formant tier. " "Because of @@constant extrapolation@, F1 will have this value throughout the time domain.") TAG (L"##Initial formant spacing# (e.g. 1100 Hz)") DEFINITION (L"the difference between the frequency values of the points in adjacent formant tiers. " "For instance, the example values mentioned here cause F2 to be 1650 Hz throughout the time domain; " "F3 will be 2750 Hz, F4 will be 3850 Hz, and so on.") TAG (L"##Initial first bandwidth# (e.g. 60 Hz)") DEFINITION (L"the value of the single bandwidth point in the first bandwidth tier. " "Because of @@constant extrapolation@, B1 will have this value throughout the time domain.") TAG (L"##Initial bandwidth spacing# (e.g. 50 Hz)") DEFINITION (L"the difference between the values of the points in adjacent bandwidth tiers. " "For instance, the example values mentioned here cause B2 to be 110 Hz throughout the time domain; " "B3 will be 160 Hz, B4 will be 210 Hz, and so on.") NORMAL (L"To add some points to it, use @@FormantGrid: Add formant point...@ and @@FormantGrid: Add bandwidth point...@.") NORMAL (L"For more examples, see @@Source-filter synthesis@.") MAN_END MAN_BEGIN (L"Formant", L"ppgb", 20050427) INTRO (L"One of the @@types of objects@ in Praat. " "A Formant object represents spectral structure as a function of time: a %%formant contour%. " "Unlike the time-stamped @FormantGrid object, it is sampled into a number of %frames centred around equally spaced times, " "Each frame contains frequency and bandwidth information about several formants.") ENTRY (L"Inside a Formant object") NORMAL (L"With @Inspect, you will see the following attributes:") TAG (L"%xmin") DEFINITION (L"start time, in seconds.") TAG (L"%xmax") DEFINITION (L"end time, in seconds.") TAG (L"%nx") DEFINITION (L"the number of frames (\\>_ 1).") TAG (L"%dx") DEFINITION (L"time step = frame length = frame duration, in seconds.") TAG (L"%x1") DEFINITION (L"the time associated with the first frame, in seconds. " "This will usually be in the range [%xmin, %xmax]. " "The time associated with the last frame (i.e., %x1 + (%nx \\-- 1) %dx)) " "will also usually be in that range.") TAG (L"%frame__%i_, %i = 1 ... %nx") DEFINITION (L"the frames (see below).") ENTRY (L"Attributes of a formant frame") NORMAL (L"Each %frame__%i_ contains the following attributes:") TAG (L"%intensity") DEFINITION (L"an indication of the maximum intensity (a squared sound amplitude) in this frame.") TAG (L"%nFormants") DEFINITION (L"the number of formants in this frame (usually between 2 and 6).") TAG (L"%formant__%j_, %j = 1 ... %nFormants") DEFINITION (L"the information about each formant (see below).") ENTRY (L"Attributes of each formant") NORMAL (L"Each %formant__%j_ contains the following attributes:") TAG (L"%frequency") DEFINITION (L"the formant's centre frequency (in Hz).") TAG (L"%bandwidth") DEFINITION (L"the formant's bandwidth (in Hz).") ENTRY (L"See also") NORMAL (L"##Linear Prediction#") MAN_END MAN_BEGIN (L"Formant: Down to FormantGrid", L"ppgb", 20080427) INTRO (L"A command to convert every selected @Formant into a @FormantGrid.") NORMAL (L"This performs a trivial copying of frames to points. " "Each formant tier and each bandwidth tier of the resulting FormantGrid contains a point for each original frame. " "The intensity information is lost.") MAN_END MAN_BEGIN (L"Formant: Draw tracks...", L"ppgb", 19980321) INTRO (L"A command to draw the selected @Formant objects to the @@Picture window@.") ENTRY (L"Behaviour") NORMAL (L"Every formant value is drawn as one or two short line segments, connected, if possible, " "with a line segment of the corresponding formant values in the adjacent frames.") ENTRY (L"Settings") TAG (L"##From time (s)") TAG (L"##To time (s)") DEFINITION (L"the time domain of the drawing. If ##To time# is not greater than ##From time#, " "the entire formant contour is drawn.") TAG (L"##Maximum frequency (Hz)") DEFINITION (L"the height of the %y axis. For speech, 5000 Hz is a usual value.") TAG (L"##Garnish") DEFINITION (L"determines whether axes, numbers, and texts (\"Time\", \"Formant frequency\") will be drawn in the margins around the picture. " "Turn this button off if you prefer to garnish your picture by yourself with the @Margins menu.") ENTRY (L"Usage") NORMAL (L"Unlike @@Formant: Speckle...@, this procedure assumes that e.g. the second formant in frame %i " "has something to do with the second formant in frame %i+1. To make this assumption more plausible, " "use @@Formant: Track...@ first.") MAN_END MAN_BEGIN (L"Formant: Formula (bandwidths)...", L"ppgb", 19980323) INTRO (L"A command to modify each selected @Formant object with a specified formula.") NORMAL (L"For what you can do with formulas, see @@Matrix: Formula...@. " "The %%i%th row contains the values of the %%i%th bandwidth contour.") NORMAL (L"See @@Formant: Formula (frequencies)...@ for more information.") MAN_END MAN_BEGIN (L"Formant: Formula (frequencies)...", L"ppgb", 19981221) INTRO (L"A command to modify each selected @Formant object with a specified formula.") NORMAL (L"For what you can do with formulas, see @@Matrix: Formula...@. " "The %%i%th row contains the values of the %%i%th frequency contour.") NORMAL (L"For an example, see @@Source-filter synthesis@.") MAN_END MAN_BEGIN (L"Formant: Get bandwidth at time...", L"ppgb", 19991016) INTRO (L"A @query to the selected @Formant object for the bandwidth of the specified formant at the specified time.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the ordinal number of the formant, counting up from 0 Hz. Specify \"2\" for %F__2_ etc.") TAG (L"##Time (s)") DEFINITION (L"the time at which to evaluate the bandwidth.") TAG (L"##Units") DEFINITION (L"the units of the result (#hertz or #Bark).") ENTRY (L"Return value") NORMAL (L"the estimated bandwidth in hertz or Bark. " "If %Time is not within half a frame width of any frame centre, or " "If the specified %%Formant number% is greater than the number of formants in the frame, " "the return value is @undefined; " "otherwise, the formant is considered to belong to the frame whose centre is nearest to the specified time.") ENTRY (L"Algorithm") NORMAL (L"If possible (i.e. if the adjacent frame has enough formants), " "a linear interpolation is performed between the centre of the frame and the centre of the adjacent frame. " "With Bark units, the hertz-to-Bark transformation is performed " "on the two frequencies %F \\+_ 1/2 %B (after interpolation), and the result is the difference between these two values") MAN_END MAN_BEGIN (L"Formant: Get maximum...", L"ppgb", 19991016) INTRO (L"A @query to ask the selected @Formant object for the maximum value of the specified formant.") ENTRY (L"Return value") NORMAL (L"the maximum, in hertz or Bark.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the ordinal number of the formant, counting up from 0 Hz. Specify \"2\" for %F__2_ etc.") TAG (L"##From time (s)") TAG (L"##To time (s)") DEFINITION (L"the selected time domain. Values outside this domain are ignored. " "If ##To time# is not greater than ##From time#, the entire time domain of the formant contour is considered.") TAG (L"##Units") DEFINITION (L"the units of the result (#Hertz or #Bark).") TAG (L"##Interpolation") DEFINITION (L"the interpolation method (#None or #Parabolic). See @@vector peak interpolation@.") MAN_END MAN_BEGIN (L"Formant: Get mean...", L"ppgb", 19991016) INTRO (L"A @query to ask the selected @Formant object for the mean value of the specified formant.") ENTRY (L"Return value") NORMAL (L"the mean, in hertz or Bark.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the ordinal number of the formant, counting up from 0 Hz. Specify \"2\" for %F__2_ etc.") TAG (L"##From time (s)") TAG (L"##To time (s)") DEFINITION (L"the selected time domain. Values outside this domain are ignored. " "If ##To time# is not greater than ##From time#, the entire time domain of the formant contour is considered.") TAG (L"##Units") DEFINITION (L"the units of the result (#Hertz or #Bark).") ENTRY (L"Scripting") NORMAL (L"You can use this command to put the mean into a script variable:") CODE (L"select Formant hallo") CODE (L"mean = Get mean... 2 0 0 Hertz") NORMAL (L"In this case, the value will not be written into the Info window.") MAN_END MAN_BEGIN (L"Formant: Get minimum...", L"ppgb", 19991016) INTRO (L"A @query to ask the selected @Formant object for the minimum value of the specified formant.") ENTRY (L"Return value") NORMAL (L"the minimum, in hertz or Bark.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the ordinal number of the formant, counting up from 0 Hz. Specify \"2\" for %F__2_ etc.") TAG (L"##From time (s)") TAG (L"##To time (s)") DEFINITION (L"the selected time domain. Values outside this domain are ignored. " "If ##To time# is not greater than ##From time#, the entire time domain of the formant contour is considered.") TAG (L"##Units") DEFINITION (L"the units of the result (#Hertz or #Bark).") TAG (L"##Interpolation") DEFINITION (L"the interpolation method (#None or #Parabolic). See @@vector peak interpolation@.") MAN_END MAN_BEGIN (L"Formant: Get number of formants", L"ppgb", 19991016) INTRO (L"A @query to ask the selected @Formant object for the number of formants in a specified frame.") ENTRY (L"Setting") TAG (L"##Frame number") DEFINITION (L"the frame number whose formant count is sought.") ENTRY (L"Return value") NORMAL (L"the number of formants.") MAN_END MAN_BEGIN (L"Formant: Get quantile...", L"ppgb", 19991016) INTRO (L"A @query to ask the selected @Formant object for an estimation of the specified quantile of the distribution " "that underlies the attested values of the specified formant.") ENTRY (L"Return value") NORMAL (L"the quantile, in hertz or Bark.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the ordinal number of the formant, counting up from 0 Hz. Specify \"2\" for %F__2_ etc.") TAG (L"##From time (s)") TAG (L"##To time (s)") DEFINITION (L"the selected time domain. Values outside this domain are ignored. " "If ##To time# is not greater than ##From time#, the entire time domain of the formant contour is considered.") TAG (L"##Units") DEFINITION (L"the units of the result (#Hertz or #Bark).") TAG (L"##Quantile") DEFINITION (L"the fraction (between 0 and 1) of the values of the underlying distribution expected to lie below the result. " "For instance, if #Quantile is 0.10, the algorithm estimates the formant value below which 10\\% of all formant values " "are expected to lie. To get an estimate of the %median of the underlying distribution, specify a quantile of 0.50.") ENTRY (L"Algorithm") NORMAL (L"First, the available formant values within the selected time domain are collected in an array. " "This array is then sorted and the @@quantile algorithm@ is performed. With Bark units, " "the hertz-to-Bark transformation is performed before the quantile algorithm.") MAN_END MAN_BEGIN (L"Formant: Get standard deviation", L"ppgb", 19991016) INTRO (L"A @query to ask the selected @Formant object for the standard deviation of the attested values of the specified formant " "within a specified time domain.") ENTRY (L"Return value") NORMAL (L"the standard deviation, in hertz or Bark.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the ordinal number of the formant, counting up from 0 Hz. Specify \"2\" for %F__2_ etc.") TAG (L"##From time (s)") TAG (L"##To time (s)") DEFINITION (L"the selected time domain. Values outside this domain are ignored. " "If ##To time# is not greater than ##From time#, the entire time domain of the formant contour is considered.") TAG (L"##Units") DEFINITION (L"the units of the result (#Hertz or #Bark).") MAN_END MAN_BEGIN (L"Formant: Get time of maximum...", L"ppgb", 19991016) INTRO (L"A @query to ask the selected @Formant object for the time associated with the maximum value " "of a specified formant within a specified time domain.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the ordinal number of the formant, counting up from 0 Hz. Specify \"2\" for %F__2_ etc.") TAG (L"##From time (s)") TAG (L"##To time (s)") DEFINITION (L"the selected time domain. Values outside this domain are ignored, except for interpolation. " "If ##To time# is not greater than ##From time#, the entire time domain of the formant contour is considered.") TAG (L"##Units") DEFINITION (L"the units of the result (#Hertz or #Bark).") TAG (L"##Interpolation") DEFINITION (L"the interpolation method (#None or #Parabolic). See @@vector peak interpolation@.") ENTRY (L"Return value") NORMAL (L"the time expressed in seconds. If no relevant formants are found, the value is @undefined.") MAN_END MAN_BEGIN (L"Formant: Get time of minimum...", L"ppgb", 19991016) INTRO (L"A @query to ask the selected @Formant object for the time associated with the minimum value " "of a specified formant within a specified time domain.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the ordinal number of the formant, counting up from 0 Hz. Specify \"2\" for %F__2_ etc.") TAG (L"##From time (s)") TAG (L"##To time (s)") DEFINITION (L"the selected time domain. Values outside this domain are ignored, except for interpolation. " "If ##To time# is not greater than ##From time#, the entire time domain of the formant contour is considered.") TAG (L"##Units") DEFINITION (L"the units of the result (#Hertz or #Bark).") TAG (L"##Interpolation") DEFINITION (L"the interpolation method (#None or #Parabolic). See @@vector peak interpolation@.") ENTRY (L"Return value") NORMAL (L"the time expressed in seconds. If no relevant formants are found, the value is @undefined.") MAN_END MAN_BEGIN (L"Formant: Get value at time...", L"ppgb", 19991016) INTRO (L"A @query to ask the selected @Formant object for the frequency of the specified formant at the specified time.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the ordinal number of the formant, counting up from 0 Hz. Specify \"2\" for %F__2_ etc.") TAG (L"##Time (s)") DEFINITION (L"the time at which to evaluate the formant frequency.") TAG (L"##Units)") DEFINITION (L"the units of the result (#Hertz or #Bark).") TAG (L"##Interpolation") DEFINITION (L"the interpolation method, see @@vector value interpolation@. " "Always Linear.") ENTRY (L"Return value") NORMAL (L"the bandwidth in hertz or Bark. " "If #Time is not within half a frame width of any frame centre, or " "if ##Formant number# is greater than the number of formants in the frame, " "the value is @undefined; " "otherwise, the formant is considered to belong to the frame whose centre is nearest to #Time.") ENTRY (L"Algorithm") NORMAL (L"If possible (i.e. if the adjacent frame has enough formants), " "a linear interpolation is performed between the centre of the frame and the centre of the adjacent frame. " "With Bark units, the hertz-to-Bark transformation is performed before interpolation.") MAN_END MAN_BEGIN (L"Formant: Speckle...", L"ppgb", 20030916) INTRO (L"A command to draw the selected @Formant objects to the @@Picture window@.") ENTRY (L"Behaviour") NORMAL (L"Every formant value is drawn as a small circle, filled with the current colour.") ENTRY (L"Settings") TAG (L"##From time (s)") TAG (L"##To time (s)") DEFINITION (L"the time domain of the drawing. If ##To time# is not greater than ##From time#, " "the entire formant contour is drawn.") TAG (L"##Maximum frequency (Hz)") DEFINITION (L"the height of the %y axis. For speech, 5000 Hz is a usual value.") TAG (L"##Dynamic range (dB)") DEFINITION (L"determines the signal intensity (as stored in each formant frame) below which " "no formants will be drawn. If zero, all formants will be drawn. The standard value is 30 dB, " "which would mean that formants in frames with intensities less than the maximum intensity minus 30 dB will not be drawn.") TAG (L"##Garnish") DEFINITION (L"determines whether axes, numbers, and texts (\"Time\", \"Formant frequency\") will be drawn in the margins around the picture. " "Turn this button off if you prefer to garnish your picture by yourself with the @Margins menu.") MAN_END MAN_BEGIN (L"Formant: Track...", L"ppgb", 20020308) INTRO (L"A command to extract a specified number of formant tracks from each selected @Formant object. " "The tracks represent the cheapest paths through the measured formant values in consecutive frames.") ENTRY (L"How to use") NORMAL (L"In order to be capable of producing three tracks (i.e. F1, F2, and F3), there must be at least " "three formant candidates in %every frame of the Formant object. The typical use of " "this command, therefore, is to analyse five formants with @@Sound: To Formant (burg)...@ " "and then use the tracking command to extract three tracks.") ENTRY (L"When to use, when not") NORMAL (L"This command only makes sense if the whole of the formant contour makes sense. " "For speech, formant contours make sense only for vowels and the like. " "During some consonants, the Formant object may have fewer than three formant values, " "and trying to create three tracks through them will fail. " "You will typically use this command for the contours in diphthongs, if at all.") ENTRY (L"Settings") NORMAL (L"To be able to interpret the settings, you should know that the aim of the procedure is " "to minimize the sum of the %costs associated with the three tracks.") TAG (L"##Number of tracks") DEFINITION (L"the number of formant tracks that the procedure must find. If this number is 3, " "the procedure will try to find tracks for F1, F2, and F3; if the Formant object contains " "a frame with less than three formants, the tracking procedure will fail.") TAG (L"##Reference F1 (Hz)") DEFINITION (L"the preferred value near which the first track wants to be. " "For average (i.e. adult female) speakers, this value will be around " "the average F1 for vowels of female speakers, i.e. 550 Hz.") TAG (L"##Reference F2 (Hz)") DEFINITION (L"the preferred value near which the second track wants to be. " "A good value will be around " "the average F2 for vowels of female speakers, i.e. 1650 Hz.") TAG (L"##Reference F3 (Hz)") DEFINITION (L"the preferred value near which the third track wants to be. " "A good value will be around " "the average F3 for vowels of female speakers, i.e. 2750 Hz. " "This argument will be ignored if you choose to have fewer than three tracks, " "i.e., if you are only interested in F1 and F2.") TAG (L"##Reference F4 (Hz)") DEFINITION (L"the preferred value near which the fourth track wants to be. " "A good value may be around 3850 Hz, but you will usually not want to " "track F4, because traditional formant lore tends to ignore it " "(however inappropriate this may be for the vowel [i]), " "and because Formant objects often contain not more than three formant values " "in some frames. So you will not usually specify a higher %%Number of tracks% than 3, " "and in that case, this argument will be ignored.") TAG (L"##Reference F5 (Hz)") DEFINITION (L"the preferred value near which the five track wants to be. " "In the unlikely case that you want five tracks, " "a good value may be around 4950 Hz.") TAG (L"##Frequency cost (per kiloHertz)") DEFINITION (L"the local cost of having a formant value in your track that deviates " "from the reference value. For instance, if a candidate (i.e. any formant in a frame " "of the Formant object) has a formant frequency of 800 Hz, " "and ##Frequency cost# is 1.0/kHz, " "the cost of putting this formant in the first track is 0.250, " "because the distance to the reference F1 of 550 Hz is 250 Hz. " "The cost of putting the formant in the second track would be 0.850 " "(= (1.650 kHz - 0.600 kHz) \\.c 1.0/kHz), so we see that the procedure " "locally favours the inclusion of the 800 Hz candidate into the F1 track. " "But the next two cost factors may override this local preference.") TAG (L"##Bandwidth cost") DEFINITION (L"the local cost of having a bandwidth, relative to the formant frequency. " "For instance, if a candidate has a formant frequency of 400 Hz and " "a bandwidth of 80 Hz, and ##Bandwidth cost# is 1.0, " "the cost of having this formant in any track is (80/400) \\.c 1.0 = 0.200. " "So we see that the procedure locally favours the inclusion of candidates " "with low relative bandwidths.") TAG (L"##Transition cost (per octave)") DEFINITION (L"the cost of having two different consecutive formant values in a track. " "For instance, if a proposed track through the candidates has two consecutive formant " "values of 300 Hz and 424 Hz, and ##Transition cost# is 1.0/octave, " "the cost of having this large frequency jump is (0.5 octave) \\.c (1.0/octave) = 0.500.") ENTRY (L"Algorithm") NORMAL (L"This command uses a Viterbi algorithm with multiple planes. For instance, if the selected Formant object " "contains up to five formants per frame, and you request three tracks, the Viterbi algorithm will have to choose " "between ten candidates (the number of combinations of three out of five) for each frame.") NORMAL (L"The formula for the cost of e.g. track 3, with proposed values %F__2%i_ (%i = 1...%N, " "where %N is the number of frames) is:") FORMULA (L"\\su__%i=1..%N_ %frequencyCost\\.c\\|f%F__3%i_ \\-- %referenceF3\\|f/1000 +") FORMULA (L"+ \\su__%i=1..%N_ %bandWidthCost\\.c%B__3%i_/%F__3%i_ +") FORMULA (L"+ \\su__%i=1..%N-1_ %transitionCost\\.c\\|flog__2_(%F__3%i_/%F__3,%i+1_)\\|f") NORMAL (L"Analogous formulas compute the cost of track 1 and track 2. " "The procedure will assign those candidates to the three tracks that minimize " "the sum of three track costs.") MAN_END MAN_BEGIN (L"FormantGrid", L"ppgb", 20080427) INTRO (L"One of the @@types of objects@ in Praat.") NORMAL (L"A FormantGrid object represents spectral structure as a function of time: a %%formant contour%. " "Unlike the evenly sampled @Formant object, it consists of a number of formant tiers and bandwidth tiers, " "each of which contains a number of formant or bandwidth %points (or %targets), sorted by time.") NORMAL (L"For examples, see @@Source-filter synthesis@.") ENTRY (L"FormantGrid commands") NORMAL (L"Creation:") LIST_ITEM (L"From scratch:") LIST_ITEM (L"\\bu @@Create FormantGrid...") LIST_ITEM (L"\\bu @@FormantGrid: Add formant point...") LIST_ITEM (L"\\bu @@FormantGrid: Add bandwidth point...") LIST_ITEM (L"Copy from another object:") LIST_ITEM (L"\\bu @@Formant: Down to FormantGrid@: trivial copying of frames to points.") //NORMAL (L"Conversion:") //LIST_ITEM (L"\\bu @@FormantGrid: Down to PointProcess@: copy times.") NORMAL (L"Synthesis:") LIST_ITEM (L"\\bu @@Sound & FormantGrid: Filter@: see @@Source-filter synthesis@.") //NORMAL (L"Queries:") //LIST_ITEM (L"\\bu @@Get low index from time...") //LIST_ITEM (L"\\bu @@Get high index from time...") //LIST_ITEM (L"\\bu @@Get nearest index from time...") NORMAL (L"Modification:") LIST_ITEM (L"\\bu @@FormantGrid: Add formant point...") LIST_ITEM (L"\\bu @@FormantGrid: Add bandwidth point...") //LIST_ITEM (L"\\bu @@Remove point...") //LIST_ITEM (L"\\bu @@Remove point near...") LIST_ITEM (L"\\bu @@FormantGrid: Remove formant points between...") LIST_ITEM (L"\\bu @@FormantGrid: Remove bandwidth points between...") MAN_END MAN_BEGIN (L"FormantGrid: Add bandwidth point...", L"ppgb", 20080425) INTRO (L"A command to add a bandwidth point to each selected @FormantGrid.") NORMAL (L"For examples, see @@Source-filter synthesis@.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the number of the formant (e.g. 1, 2,...) to which a bandwidth point is to be added.") TAG (L"##Time (s)") DEFINITION (L"the time at which a bandwidth point is to be added.") TAG (L"##Bandwidth (Hz)") DEFINITION (L"the bandwidth value of the requested new point.") ENTRY (L"Example") NORMAL (L"To set the bandwidth of F2 at 0.3 seconds to 130 Hz, " "you set ##Formant number# to 2, #Time to 0.3 s, and #Bandwidth to 130 Hz.") ENTRY (L"Behaviour") NORMAL (L"The formant tier is modified so that it contains the new point. " "If a bandwidth point at the specified time was already present in the formant tier, nothing happens.") MAN_END MAN_BEGIN (L"FormantGrid: Add formant point...", L"ppgb", 20080425) INTRO (L"A command to add a formant point to each selected @FormantGrid.") NORMAL (L"For examples, see @@Source-filter synthesis@.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the number of the formant (e.g. 1, 2,...) to which a formant point is to be added.") TAG (L"##Time (s)") DEFINITION (L"the time at which a formant point is to be added.") TAG (L"##Frequency (Hz)") DEFINITION (L"the formant frequency value of the requested new point.") ENTRY (L"Example") NORMAL (L"To set the value of F2 at 0.3 seconds to 2200 Hz, " "you set ##Formant number# to 2, #Time to 0.3 s, and #Frequency to 2200 Hz.") ENTRY (L"Behaviour") NORMAL (L"The formant tier is modified so that it contains the new point. " "If a formant point at the specified time was already present in the formant tier, nothing happens.") MAN_END MAN_BEGIN (L"FormantGrid: Remove bandwidth points between...", L"ppgb", 20080427) INTRO (L"A command to remove some points from a bandwidth tier in every selected @FormantGrid.") ENTRY (L"Settings") TAG (L"##Formant number") DEFINITION (L"the formant (1, 2,...) from whose bandwidth tier you want to remove some points.") TAG (L"##From time (s))") TAG (L"##To time (s)") DEFINITION (L"the times between which you want to remove all bandwidth points.") ENTRY (L"Example") NORMAL (L"If you want to remove all bandwidth points in F2 between 0.5 and 0.7 seconds, " "you set ##Formant number# to 2, ##From time# to 0.5 s, and ##To time# to 0.7 s.") MAN_END MAN_BEGIN (L"FormantGrid: Remove formant points between...", L"ppgb", 20080427) INTRO (L"A command to remove some points from a formant tier in every selected @FormantGrid.") ENTRY (L"Settings") TAG (L"%%Formant number") DEFINITION (L"the formant (1, 2,...) from which you want to remove some points.") TAG (L"##From time (s))") TAG (L"##To time (s)") DEFINITION (L"the times between which you want to remove all formant points.") ENTRY (L"Example") NORMAL (L"If you want to remove all formant points in F2 between 0.5 and 0.7 seconds, " "you set ##Formant number# to 2, ##From time# to 0.5 s, and ##To time# to 0.7.") MAN_END MAN_BEGIN (L"Sound: To Formant (burg)...", L"ppgb", 20101007) INTRO (L"A command that creates a @Formant object from every selected @Sound object. " "It performs a short-term spectral analysis, approximating the spectrum of each " "analysis frame by a number of formants.") ENTRY (L"Settings") TAG (L"##Time step (s)") DEFINITION (L"the time between the centres of consecutive analysis frames. If the sound is 2 seconds long, " "and the time step is 0.01 seconds, there will be approximately 200 analysis frames. " "The actual number is somewhat lower (usually 195), because we cannot measure very well " "near the edges. If you set the time step to 0.0 (the standard), Praat will use a time step " "that is equal to 25 percent of the analysis window length (see below).") TAG (L"##Maximum number of formants") DEFINITION (L"for most analyses of human speech, you will want to extract 5 formants per frame. " "This, in combination with the ##Maximum formant# setting, is the only way " "in which this procedure will give you results compatible with how people " "tend to interpret formants for vowels, i.e. in terms of " "vowel height (F1) and vowel place (F2). Otherwise, the ##Maximum number of formants# can be any multiple of 0.5, " "you can choose 4, 4.5, 5, 5.5, 6, and so on (see below).") TAG (L"##Maximum formant (Hz)") DEFINITION (L"the ceiling of the formant search range, in hertz. It is crucial that you set this to a value suitable for your speaker. " "The standard value of 5500 Hz is suitable for an average adult female. For a male, use 5000 Hz; " "if you use 5500 Hz for an adult male, you may end up with too few formants in the low frequency region, " "e.g. analysing an [u] as having a single formant near 500 Hz whereas you want two formants at 300 and 600 Hz. " "For a young child, use a value much higher than 5500 Hz, for instance 8000 Hz (experiment with it on steady vowels).") TAG (L"##Window length (s)") DEFINITION (L"the effective duration of the analysis window, in seconds. The actual length is twice this value, " "because Praat uses a Gaussian-like analysis window with sidelobes below -120 dB. " "For instance, if the ##Window length# is 0.025 seconds, the actual Gaussian window duration " "is 0.050 seconds. This window has values below 4\\% outside the central 0.025 seconds, " "and its frequency resolution (-3 dB point) is 1.298 / (0.025 s) = 51.9 Hz, as computed " "with the formula given at @@Sound: To Spectrogram...@. This is comparable to the bandwidth " "of a Hamming window of 0.025 seconds, which is 1.303 / (0.025 s) = 52.1 Hz, " "but that window (which is the window most often used in other analysis programs) " "has three spectral lobes of about -42 dB on each side.") TAG (L"##Pre-emphasis from (Hz)") DEFINITION (L"the +3 dB point for an inverted low-pass filter with a slope of +6 dB/octave. " "If this value is 50 Hz, then frequencies below 50 Hz are not enhanced, " "frequencies around 100 Hz are amplified by 6 dB, frequencies around 200 Hz are amplified by 12 dB, " "and so forth. The point of this is that vowel spectra tend to fall by 6 dB per octave; " "the pre-emphasis creates a flatter spectrum, which is better for formant analysis " "because we want our formants to match the local peaks, not the global spectral slope. " "See the @@source-filter synthesis@ tutorial for a technical explanation, " "and @@Sound: Pre-emphasize (in-line)...@ for the algorithm.") ENTRY (L"Algorithm") NORMAL (L"The sound will be resampled to a sampling frequency of twice the value of %%Maximum formant%, " "with the algorithm described at @@Sound: Resample...@. " "After this, pre-emphasis is applied with the algorithm described at @@Sound: Pre-emphasize (in-line)...@. " "For each analysis window, Praat applies a Gaussian-like window, " "and computes the LPC coefficients with the algorithm by Burg, as given by @@Childers (1978)@ " "and @@Press et al. (1992)@. The number of \"poles\" that this algorithm computes is twice the %%Maximum number of formants%; " "that's why you can set the %%Maximum number of formants% to any multiple of 0.5).") NORMAL (L"The algorithm will initially find ##Maximum number of formants# formants in the whole range between 0 Hz " "and ##Maximum formant#. The initially found formants can therefore sometimes have very low frequencies (near 0 Hz) " "or very high frequencies (near ##Maximum formant#). Such low or high \"formants\" tend to be artefacts of the LPC algorithm, " "i.e., the algorithm tends to use them to match the spectral slope if that slope differs from the 6 dB/octave assumption. " "Therefore, such low or high \"formants\" cannot usually be associated with the vocal tract resonances that you are looking for. " "In order for you to be able to identify the traditional F1 and F2, " "all formants below 50 Hz and all formants above ##Maximum formant# minus 50 Hz, " "are therefore removed. If you don't want this removal, you may experiment with @@Sound: To Formant (keep all)...@ instead. " "If you prefer an algorithm that always yields the requested number of formants, nicely distributed " "across the frequency domain, you may try the otherwise rather unreliable Split-Levinson procedure @@Sound: To Formant (sl)...@.") MAN_END MAN_BEGIN (L"Sound: To Formant (keep all)...", L"ppgb", 20000210) INTRO (L"A command that creates a @Formant object from every selected @Sound object. Not recommended for general use.") ENTRY (L"Purpose") NORMAL (L"to perform a short-term spectral analysis, approximating the spectrum of each frame by a number of formants.") ENTRY (L"Settings") NORMAL (L"The same as with @@Sound: To Formant (burg)...@.") ENTRY (L"Algorithm") NORMAL (L"The same as with @@Sound: To Formant (burg)...@. In contrast with that command, " "however, all formant values are kept, even those below 50 Hz and those above %%Maximum formant% minus 50 Hz. " "Although this makes the identification of the traditional F1 and F2 more difficult, " "this might give better results in resynthesis (see @@Sound & Formant: Filter@), but it usually generates funny values instead.") MAN_END MAN_BEGIN (L"Sound: To Formant (sl)...", L"ppgb", 20021215) INTRO (L"A command that creates a @Formant object from every selected @Sound object. Not recommended for general use.") ENTRY (L"Purpose") NORMAL (L"to perform a short-term spectral analysis, approximating the spectrum of each frame by a number of formants.") ENTRY (L"Settings") NORMAL (L"The same as with @@Sound: To Formant (burg)...@.") ENTRY (L"Algorithm") NORMAL (L"The algorithm is based on the implementation of the `Split Levinson' algorithm by @@Willems (1986)@. " "This algorithm will always find the requested number of formants in every frame, even if they do not exist. " "The standard routine (@@Sound: To Formant (burg)...@) yields much more reliable formant values, though it is more sensitive " "to the %%Maximum formant% argument.") NORMAL (L"Because of the general funny behaviour of the Split-Levinson algorithm, we did not bother to implement an analysis " "of the bandwidths. They are all set arbitrarily to 50 Hz.") MAN_END MAN_BEGIN (L"Sound & Formant: Filter", L"ppgb", 19991119) INTRO (L"A command to create a new Sound from the selected @Sound and @Formant objects.") NORMAL (L"For examples, see @@Source-filter synthesis@.") NORMAL (L"The resulting Sound is scaled so that its maximum absolute amplitude is 0.99. " "If you don't want this, use @@Sound & Formant: Filter (no scale)@ instead.") MAN_END MAN_BEGIN (L"Sound & Formant: Filter (no scale)", L"ppgb", 19991119) INTRO (L"A command to create a new Sound from the selected @Sound and @Formant objects.") NORMAL (L"For examples, see @@Source-filter synthesis@.") NORMAL (L"Unlike what happens in @@Sound & Formant: Filter@, " "the resulting Sound is not scaled. This allows generation of a series " "of signals with controlled relative intensities.") MAN_END MAN_BEGIN (L"Sound & FormantGrid: Filter", L"ppgb", 20080425) INTRO (L"A command to create a new Sound from the selected @Sound and @FormantGrid objects.") NORMAL (L"For examples, see @@Source-filter synthesis@.") NORMAL (L"The resulting Sound is scaled so that its maximum absolute amplitude is 0.99. " "If you don't want this, use @@Sound & FormantGrid: Filter (no scale)@ instead.") MAN_END MAN_BEGIN (L"Sound & FormantGrid: Filter (no scale)", L"ppgb", 20080425) INTRO (L"A command to create a new Sound from the selected @Sound and @FormantGrid objects.") NORMAL (L"For examples, see @@Source-filter synthesis@.") NORMAL (L"Unlike what happens in @@Sound & FormantGrid: Filter@, " "the resulting Sound is not scaled. This allows generation of a series " "of signals with controlled relative intensities.") MAN_END } /* End of file manual_formant.cpp */ sources_5316/fon/Polygon_def.h0000644000176700017670000000243711621654750015140 0ustar paulpaul/* Polygon_def.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Polygon oo_DEFINE_CLASS (Polygon, Data) oo_LONG (numberOfPoints) #if oo_READING if (localVersion >= 1) { oo_DOUBLE_VECTOR (x, numberOfPoints) oo_DOUBLE_VECTOR (y, numberOfPoints) } else { oo_FLOAT_VECTOR (x, numberOfPoints) oo_FLOAT_VECTOR (y, numberOfPoints) } #else oo_DOUBLE_VECTOR (x, numberOfPoints) oo_DOUBLE_VECTOR (y, numberOfPoints) #endif #if oo_DECLARING // overridden methods: virtual void v_info (); #endif oo_END_CLASS (Polygon) #undef ooSTRUCT /* End of file Polygon_def.h */ sources_5316/fon/Pitch_AnyTier_to_PitchTier.h0000644000176700017670000000203011614424561020034 0ustar paulpaul/* Pitch_AnyTier_to_PitchTier.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Pitch.h" #include "AnyTier.h" #include "PitchTier.h" PitchTier Pitch_AnyTier_to_PitchTier (Pitch pitch, AnyTier tier, int checkMethod); PitchTier PitchTier_AnyTier_to_PitchTier (PitchTier pitch, AnyTier tier); /* End of file Pitch_AnyTier_to_PitchTier.h */ sources_5316/fon/AnyTier.h0000644000176700017670000000272211625721247014243 0ustar paulpaul#ifndef _AnyTier_h_ #define _AnyTier_h_ /* AnyTier.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Collection.h" #include "PointProcess.h" #include "AnyTier_def.h" oo_CLASS_CREATE (AnyPoint, SimpleDouble); oo_CLASS_CREATE (AnyTier, Function); long AnyTier_timeToLowIndex (I, double time); long AnyTier_timeToHighIndex (I, double time); long AnyTier_getWindowPoints (I, double tmin, double tmax, long *imin, long *imax); long AnyTier_timeToNearestIndex (I, double time); long AnyTier_hasPoint (I, double t); void AnyTier_addPoint (I, Data point); void AnyTier_removePoint (I, long i); void AnyTier_removePointNear (I, double time); void AnyTier_removePointsBetween (I, double tmin, double tmax); PointProcess AnyTier_downto_PointProcess (I); #endif /* End of file AnyTier.h */ sources_5316/fon/FujisakiPitch_def.h0000644000176700017670000000253110436611251016231 0ustar paulpaul/* FujisakiPitch_def.h * * Copyright (C) 2002 Paul Boersma & Hansjoerg Mixdorff * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/05/18 * pb 2002/07/16 GPL */ #define ooSTRUCT FujisakiCommand oo_DEFINE_CLASS (FujisakiCommand, Function) oo_DOUBLE (amplitude) oo_END_CLASS (FujisakiCommand) #undef ooSTRUCT #define ooSTRUCT FujisakiPitch oo_DEFINE_CLASS (FujisakiPitch, Function) oo_DOUBLE (baseFrequency) oo_DOUBLE (alpha) oo_DOUBLE (beta) oo_DOUBLE (gamma) oo_COLLECTION (SortedSetOfDouble, phraseCommands, FujisakiCommand, 0) oo_COLLECTION (SortedSetOfDouble, accentCommands, FujisakiCommand, 0) oo_END_CLASS (FujisakiPitch) #undef ooSTRUCT /* End of file FujisakiPitch_def.h */ sources_5316/fon/FujisakiPitch.cpp0000644000176700017670000001000011633511177015742 0ustar paulpaul/* FujisakiPitch.cpp * * Copyright (C) 2002-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2007/10/01 can write as encoding * pb 2011/05/27 C++ */ #include "FujisakiPitch.h" #include "oo_DESTROY.h" #include "FujisakiPitch_def.h" #include "oo_COPY.h" #include "FujisakiPitch_def.h" #include "oo_EQUAL.h" #include "FujisakiPitch_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "FujisakiPitch_def.h" #include "oo_WRITE_TEXT.h" #include "FujisakiPitch_def.h" #include "oo_READ_TEXT.h" #include "FujisakiPitch_def.h" #include "oo_WRITE_BINARY.h" #include "FujisakiPitch_def.h" #include "oo_READ_BINARY.h" #include "FujisakiPitch_def.h" #include "oo_DESCRIPTION.h" #include "FujisakiPitch_def.h" Thing_implement (FujisakiCommand, Function, 0); FujisakiCommand FujisakiCommand_create (double tmin, double tmax, double amplitude) { try { autoFujisakiCommand me = Thing_new (FujisakiCommand); Function_init (me.peek(), tmin, tmax); my amplitude = amplitude; return me.transfer(); } catch (MelderError) { Melder_throw ("Fujisaki command not created."); } } Thing_implement (FujisakiPitch, Function, 0); FujisakiPitch FujisakiPitch_create (double tmin, double tmax, double baseFrequency, double alpha, double beta, double gamma) { try { autoFujisakiPitch me = Thing_new (FujisakiPitch); Function_init (me.peek(), tmin, tmax); my baseFrequency = baseFrequency; my alpha = alpha; my beta = beta; my gamma = gamma; my phraseCommands = SortedSetOfDouble_create (); therror my accentCommands = SortedSetOfDouble_create (); therror return me.transfer(); } catch (MelderError) { Melder_throw ("FujisakiPitch not created."); } } FujisakiPitch Pitch_to_FujisakiPitch (Pitch me, double gamma, double timeResolution, FujisakiPitch *intermediate1, FujisakiPitch *intermediate2, FujisakiPitch *intermediate3) { (void) timeResolution; try { autoFujisakiPitch thee = FujisakiPitch_create (my xmin, my xmax, 0, 0, 0, gamma); /* * Get phrase commands. */ while (/* ... */ 0) { double onsetTime = /* ... */ 0.0; double offsetTime = /* ... */ 3.0; double amplitude = /* ... */ 1.0; autoFujisakiCommand phraseCommand = FujisakiCommand_create (onsetTime, offsetTime, amplitude); Collection_addItem (thy phraseCommands, phraseCommand.transfer()); } if (intermediate1) *intermediate1 = Data_copy (thee.peek()); /* * Get accent commands. */ while (/* ... */ 0) { double onsetTime = /* ... */ 0.0; double offsetTime = /* ... */ 3.0; double amplitude = /* ... */ 1.0; autoFujisakiCommand accentCommand = FujisakiCommand_create (onsetTime, offsetTime, amplitude); Collection_addItem (thy accentCommands, accentCommand.transfer()); } if (intermediate2) *intermediate2 = Data_copy (thee.peek()); /* * Do some extra processing. */ /* ... */ if (intermediate3) *intermediate3 = Data_copy (thee.peek()); /* * Tidy up. */ for (long i = 1; i <= thy phraseCommands -> size; i ++) { FujisakiCommand phraseCommand = (FujisakiCommand) thy phraseCommands -> item [i]; /* ... */ } for (long i = 1; i <= thy accentCommands -> size; i ++) { FujisakiCommand accentCommand = (FujisakiCommand) thy accentCommands -> item [i]; /* ... */ } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to FujisakiPitch."); } } /* End of file FujisakiPitch.cpp */ sources_5316/fon/Cochleagram.cpp0000644000176700017670000000770711724501647015440 0ustar paulpaul/* Cochleagram.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Graphics.h" #include "Cochleagram.h" Thing_implement (Cochleagram, Matrix, 2); Cochleagram Cochleagram_create (double tmin, double tmax, long nt, double dt, double t1, double df, long nf) { try { autoCochleagram me = Thing_new (Cochleagram); Matrix_init (me.peek(), tmin, tmax, nt, dt, t1, 0.0, nf * df, nf, df, 0.5 * df); therror return me.transfer(); } catch (MelderError) { Melder_throw ("Cochleagram with ", nt, " times and ", nf, " frequencies not created."); } } void Cochleagram_paint (Cochleagram me, Graphics g, double tmin, double tmax, int garnish) { static double border [1 + 12] = { 0, 25, 30, 35, 40, 45, 50, 55, 60, 65, 70, 75, 80 }; try { autoCochleagram copy = Data_copy (me); if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } long itmin, itmax; Matrix_getWindowSamplesX (me, tmin, tmax, & itmin, & itmax); for (long iy = 2; iy < my ny; iy ++) for (long ix = itmin; ix <= itmax; ix ++) if (my z [iy] [ix] > my z [iy - 1] [ix] && my z [iy] [ix] > my z [iy + 1] [ix]) { copy -> z [iy - 1] [ix] += 10; copy -> z [iy] [ix] += 10; copy -> z [iy + 1] [ix] += 10; } Graphics_setInner (g); Graphics_setWindow (g, tmin, tmax, 0, my ny * my dy); Graphics_grey (g, copy -> z, itmin, itmax, Matrix_columnToX (me, itmin), Matrix_columnToX (me, itmax), 1, my ny, 0.5 * my dy, (my ny - 0.5) * my dy, 12, border); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Time (s)"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_textLeft (g, 1, L"Place (Bark)"); Graphics_marksLeftEvery (g, 1.0, 5.0, 1, 1, 0); } } catch (MelderError) { Melder_clearError (); // BUG } } double Cochleagram_difference (Cochleagram me, Cochleagram thee, double tmin, double tmax) { try { if (my nx != thy nx || my dx != thy dx || my x1 != thy x1) Melder_throw (L"Unequal time samplings."); if (my ny != thy ny) Melder_throw (L"Unequal numbers of frequencies."); if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } long itmin, itmax; long nt = Matrix_getWindowSamplesX (me, tmin, tmax, & itmin, & itmax); if (nt == 0) Melder_throw ("Window too short."); double diff = 0.0; for (long itime = itmin; itime <= itmax; itime ++) { for (long ifreq = 1; ifreq <= my ny; ifreq ++) { double d = my z [ifreq] [itime] - thy z [ifreq] [itime]; diff += d * d; } } diff /= nt * my ny; return sqrt (diff); } catch (MelderError) { Melder_throw (me, " & ", thee, ": difference not computed."); } } Cochleagram Matrix_to_Cochleagram (Matrix me) { try { autoCochleagram thee = Cochleagram_create (my xmin, my xmax, my nx, my dx, my x1, my dy, my ny); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Cochleagram."); } } Matrix Cochleagram_to_Matrix (Cochleagram me) { try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Matrix."); } } /* End of file Cochleagram.cpp */ sources_5316/fon/IntensityTier.h0000644000176700017670000000371111621636265015502 0ustar paulpaul#ifndef _IntensityTier_h_ #define _IntensityTier_h_ /* IntensityTier.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "RealTier.h" #include "Intensity.h" #include "TableOfReal.h" #include "Sound.h" Thing_define (IntensityTier, RealTier) { // overridden methods: protected: virtual int v_domainQuantity () { return MelderQuantity_TIME_SECONDS; } }; IntensityTier IntensityTier_create (double tmin, double tmax); void IntensityTier_draw (IntensityTier me, Graphics g, double tmin, double tmax, double ymin, double ymax, const wchar *method, int garnish); IntensityTier PointProcess_upto_IntensityTier (PointProcess me, double intensity); IntensityTier Intensity_downto_IntensityTier (Intensity me); IntensityTier Intensity_to_IntensityTier_peaks (Intensity me); IntensityTier Intensity_to_IntensityTier_valleys (Intensity me); IntensityTier Intensity_PointProcess_to_IntensityTier (Intensity me, PointProcess pp); IntensityTier IntensityTier_PointProcess_to_IntensityTier (IntensityTier me, PointProcess pp); TableOfReal IntensityTier_downto_TableOfReal (IntensityTier me); void Sound_IntensityTier_multiply_inline (Sound me, IntensityTier intensity); Sound Sound_IntensityTier_multiply (Sound me, IntensityTier intensity, int scale); /* End of file IntensityTier.h */ #endif sources_5316/fon/Sound_to_Intensity.cpp0000644000176700017670000001276311606717457017100 0ustar paulpaul/* Sound_to_Intensity.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2003/05/20 default time step is four times oversampling * pb 2003/07/10 NUMbessel_i0_f * pb 2003/11/19 Sound_to_Intensity veryAccurate * pb 2003/12/15 removed bug introduced by previous change * pb 2004/10/27 subtractMean * pb 2006/12/31 compatible with stereo sounds * pb 2007/01/27 for stereo sounds, add channel energies * pb 2007/02/14 honoured precondition of Sampled_shortTermAnalysis (by checking whether minimumPitch is defined) * pb 2008/01/19 double * pb 2011/03/04 C++ * pb 2011/03/28 C++ */ #include "Sound_to_Intensity.h" static Intensity Sound_to_Intensity_ (Sound me, double minimumPitch, double timeStep, int subtractMeanPressure) { try { /* * Preconditions. */ if (! NUMdefined (minimumPitch)) Melder_throw ("(Sound-to-Intensity:) Minimum pitch undefined."); if (! NUMdefined (timeStep)) Melder_throw ("(Sound-to-Intensity:) Time step undefined."); if (timeStep < 0.0) Melder_throw ("(Sound-to-Intensity:) Time step should be zero or positive instead of ", timeStep, "."); if (my dx <= 0.0) Melder_throw ("(Sound-to-Intensity:) The Sound's time step should be positive."); if (minimumPitch <= 0.0) Melder_throw ("(Sound-to-Intensity:) Minimum pitch should be positive."); /* * Defaults. */ if (timeStep == 0.0) timeStep = 0.8 / minimumPitch; // default: four times oversampling Hanning-wise double windowDuration = 6.4 / minimumPitch; Melder_assert (windowDuration > 0.0); double halfWindowDuration = 0.5 * windowDuration; long halfWindowSamples = halfWindowDuration / my dx; autoNUMvector amplitude (- halfWindowSamples, halfWindowSamples); autoNUMvector window (- halfWindowSamples, halfWindowSamples); for (long i = - halfWindowSamples; i <= halfWindowSamples; i ++) { double x = i * my dx / halfWindowDuration, root = 1 - x * x; window [i] = root <= 0.0 ? 0.0 : NUMbessel_i0_f ((2 * NUMpi * NUMpi + 0.5) * sqrt (root)); } long numberOfFrames; double thyFirstTime; try { Sampled_shortTermAnalysis (me, windowDuration, timeStep, & numberOfFrames, & thyFirstTime); therror } catch (MelderError) { Melder_throw ("The duration of the sound in an intensity analysis should be at least 6.4 divided by the minimum pitch (", minimumPitch, " Hz), " "i.e. at least ", 6.4 / minimumPitch, " s, instead of ", my xmax - my xmin, " s."); } autoIntensity thee = Intensity_create (my xmin, my xmax, numberOfFrames, timeStep, thyFirstTime); for (long iframe = 1; iframe <= numberOfFrames; iframe ++) { double midTime = Sampled_indexToX (thee.peek(), iframe); long midSample = Sampled_xToNearestIndex (me, midTime); long leftSample = midSample - halfWindowSamples, rightSample = midSample + halfWindowSamples; double sumxw = 0.0, sumw = 0.0, intensity; if (leftSample < 1) leftSample = 1; if (rightSample > my nx) rightSample = my nx; for (long channel = 1; channel <= my ny; channel ++) { for (long i = leftSample; i <= rightSample; i ++) { amplitude [i - midSample] = my z [channel] [i]; } if (subtractMeanPressure) { double sum = 0.0; for (long i = leftSample; i <= rightSample; i ++) { sum += amplitude [i - midSample]; } double mean = sum / (rightSample - leftSample + 1); for (long i = leftSample; i <= rightSample; i ++) { amplitude [i - midSample] -= mean; } } for (long i = leftSample; i <= rightSample; i ++) { sumxw += amplitude [i - midSample] * amplitude [i - midSample] * window [i - midSample]; sumw += window [i - midSample]; } } intensity = sumxw / sumw; if (intensity != 0.0) intensity /= 4e-10; thy z [1] [iframe] = intensity < 1e-30 ? -300 : 10 * log10 (intensity); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": intensity analysis not performed."); } } Intensity Sound_to_Intensity (Sound me, double minimumPitch, double timeStep, int subtractMeanPressure) { bool veryAccurate = false; if (veryAccurate) { autoSound up = Sound_upsample (me); // because squaring doubles the frequency content, i.e. you get super-Nyquist components autoIntensity thee = Sound_to_Intensity_ (up.peek(), minimumPitch, timeStep, subtractMeanPressure); return thee.transfer(); } else { autoIntensity thee = Sound_to_Intensity_ (me, minimumPitch, timeStep, subtractMeanPressure); return thee.transfer(); } } IntensityTier Sound_to_IntensityTier (Sound me, double minimumPitch, double timeStep, int subtractMean) { try { autoIntensity intensity = Sound_to_Intensity (me, minimumPitch, timeStep, subtractMean); autoIntensityTier thee = Intensity_downto_IntensityTier (intensity.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": no IntensityTier created."); } } /* End of file Sound_to_Intensity.cpp */ sources_5316/fon/SoundRecorder.h0000644000176700017670000000736511747264052015457 0ustar paulpaul#ifndef _SoundRecorder_h_ #define _SoundRecorder_h_ /* SoundRecorder.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* An editor-like object that allows the user to record sounds. */ #include "Editor.h" #include "Sound.h" #include "../external/portaudio/portaudio.h" #if defined (_WIN32) #elif defined (macintosh) #elif defined (linux) #include #include #include #include #include #if defined (__OpenBSD__) || defined (__NetBSD__) #include #else #include #endif #endif struct SoundRecorder_Device { wchar name [1+40]; bool canDo; GuiObject button; }; struct SoundRecorder_Fsamp { double fsamp; bool canDo; GuiObject button; }; #define SoundRecorder_IDEVICE_MAX 8 #define SoundRecorder_IFSAMP_8000 1 #define SoundRecorder_IFSAMP_9800 2 #define SoundRecorder_IFSAMP_11025 3 #define SoundRecorder_IFSAMP_12000 4 #define SoundRecorder_IFSAMP_16000 5 #define SoundRecorder_IFSAMP_22050 6 #define SoundRecorder_IFSAMP_22254 7 #define SoundRecorder_IFSAMP_24000 8 #define SoundRecorder_IFSAMP_32000 9 #define SoundRecorder_IFSAMP_44100 10 #define SoundRecorder_IFSAMP_48000 11 #define SoundRecorder_IFSAMP_64000 12 #define SoundRecorder_IFSAMP_96000 13 #define SoundRecorder_IFSAMP_192000 14 #define SoundRecorder_IFSAMP_MAX 14 Thing_define (SoundRecorder, Editor) { // new data: public: int numberOfChannels; long nsamp, nmax; bool fakeMono, synchronous, recording; int lastLeftMaximum, lastRightMaximum; long numberOfInputDevices; struct SoundRecorder_Device device_ [1+SoundRecorder_IDEVICE_MAX]; struct SoundRecorder_Fsamp fsamp_ [1+SoundRecorder_IFSAMP_MAX]; short *buffer; GuiObject monoButton, stereoButton, meter; GuiObject progressScale, recordButton, stopButton, playButton; GuiObject soundName, cancelButton, applyButton, okButton; Graphics graphics; bool inputUsesPortAudio; const PaDeviceInfo *deviceInfos [1+SoundRecorder_IDEVICE_MAX]; PaDeviceIndex deviceIndices [1+SoundRecorder_IDEVICE_MAX]; PaStream *portaudioStream; #if motif XtWorkProcId workProcId; #endif #if defined (_WIN32) HWAVEIN hWaveIn; WAVEFORMATEX waveFormat; WAVEHDR waveHeader [3]; MMRESULT err; short buffertje1 [1000*2], buffertje2 [1000*2]; #elif defined (macintosh) short macSource [1+8]; Str255 hybridDeviceNames [1+8]; long refNum; #elif defined (linux) int fd; #else int fd; #endif // overridden methods: virtual void v_destroy (); virtual bool v_editable () { return false; } virtual bool v_scriptable () { return false; } virtual void v_createChildren (); virtual void v_createMenus (); virtual void v_createHelpMenuItems (EditorMenu menu); }; SoundRecorder SoundRecorder_create (GuiObject parent, int numberOfChannels); /* Function: create a SoundRecorder, which is an interactive window for recording in 16-bit mono or stereo. */ void SoundRecorder_prefs (void); int SoundRecorder_getBufferSizePref_MB (void); void SoundRecorder_setBufferSizePref_MB (int size); /* End of file SoundRecorder.h */ #endif sources_5316/fon/LongSound.cpp0000644000176700017670000006722711734674476015162 0ustar paulpaul/* LongSound.cpp * * Copyright (C) 1992-2012 Paul Boersma, 2007 Erez Volk (for FLAC and MP3) * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/05/28 * pb 2002/07/16 GPL * pb 2003/09/12 changed 5 to Melder_NUMBER_OF_AUDIO_FILE_TYPES * pb 2004/05/14 support for reading 24-bit and 32-bit audio files * pb 2004/11/24 made buffer length settable * pb 2006/12/10 MelderInfo * pb 2006/12/13 support for IEEE float 32-bit audio files * pb 2007/01/01 compatible with stereo sounds * pb 2007/01/27 more compatible with stereo sounds * pb 2007/03/17 domain quantity * Erez Volk 2007/03 FLAC reading * Erez Volk 2007/05/14 FLAC writing * Erez Volk 2007/06/04 MP3 reading * pb 2007/12/05 prefs * pb 2008/01/19 double * pb 2010/01/10 MP3 precision warning * fb 2010/02/25 corrected a bug that could cause LongSound_playPart to crash with an assertion on error * pb 2010/11/07 no longer do an assertion on thy resampledBuffer * pb 2010/12/20 support for more than 2 channels * pb 2011/06/02 C++ * pb 2011/07/05 C++ */ #include "LongSound.h" #include "Preferences.h" #include "flac_FLAC_stream_decoder.h" #include "mp3.h" Thing_implement (LongSound, Sampled, 0); #define MARGIN 0.01 #define USE_MEMMOVE 1 static long prefs_bufferLength; void LongSound_prefs (void) { Preferences_addLong (L"LongSound.bufferLength", & prefs_bufferLength, 60); // seconds } long LongSound_getBufferSizePref_seconds (void) { return prefs_bufferLength; } void LongSound_setBufferSizePref_seconds (long size) { prefs_bufferLength = size < 10 ? 10 : size > 10000 ? 10000: size; } void structLongSound :: v_destroy () { /* * The play callback may contain a pointer to my buffer. * That pointer is about to dangle, so kill the playback. */ MelderAudio_stopPlaying (MelderAudio_IMPLICIT); if (mp3f) mp3f_delete (mp3f); if (flacDecoder) { FLAC__stream_decoder_finish (flacDecoder); // closes f FLAC__stream_decoder_delete (flacDecoder); } else if (f) fclose (f); NUMvector_free (buffer, 0); LongSound_Parent :: v_destroy (); } void structLongSound :: v_info () { static const wchar *encodingStrings [1+20] = { L"none", L"linear 8 bit signed", L"linear 8 bit unsigned", L"linear 16 bit big-endian", L"linear 16 bit little-endian", L"linear 24 bit big-endian", L"linear 24 bit little-endian", L"linear 32 bit big-endian", L"linear 32 bit little-endian", L"mu-law", L"A-law", L"shorten", L"polyphone", L"IEEE float 32 bit big-endian", L"IEEE float 32 bit little-endian", L"FLAC", L"FLAC", L"FLAC", L"MP3", L"MP3", L"MP3" }; structData :: v_info (); MelderInfo_writeLine3 (L"Duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine2 (L"File name: ", Melder_fileToPath (& file)); MelderInfo_writeLine2 (L"File type: ", audioFileType > Melder_NUMBER_OF_AUDIO_FILE_TYPES ? L"unknown" : Melder_audioFileTypeString (audioFileType)); MelderInfo_writeLine2 (L"Number of channels: ", Melder_integer (numberOfChannels)); MelderInfo_writeLine2 (L"Encoding: ", encoding > 20 ? L"unknown" : encodingStrings [encoding]); MelderInfo_writeLine3 (L"Sampling frequency: ", Melder_double (sampleRate), L" Hz"); MelderInfo_writeLine3 (L"Size: ", Melder_integer (nx), L" samples"); MelderInfo_writeLine3 (L"Start of sample data: ", Melder_integer (startOfData), L" bytes from the start of the file"); } static void _LongSound_FLAC_convertFloats (LongSound me, const FLAC__int32 * const samples[], long bitsPerSample, long numberOfSamples) { double multiplier; switch (bitsPerSample) { case 8: multiplier = (1.0f / 128); break; case 16: multiplier = (1.0f / 32768); break; case 24: multiplier = (1.0f / 8388608); break; case 32: multiplier = (1.0f / 32768 / 65536); break; default: multiplier = 0.0; } for (long i = 0; i < 2; ++i) { const FLAC__int32 *input = samples [i]; double *output = my compressedFloats [i]; if (! output ) continue; for (long j = 0; j < numberOfSamples; ++j) output [j] = (long)input [j] * multiplier; my compressedFloats [i] += numberOfSamples; } } static void _LongSound_FLAC_convertShorts (LongSound me, const FLAC__int32 * const samples[], long bitsPerSample, long numberOfSamples) { for (long channel = 0; channel < my numberOfChannels; ++ channel) { short *output = my compressedShorts + channel; const FLAC__int32 *input = samples [channel]; for (long j = 0; j < numberOfSamples; ++ j, output += my numberOfChannels) { FLAC__int32 sample = * (input ++); switch (bitsPerSample) { case 8: sample *= 256; break; case 16: break; case 24: sample /= 256; break; case 32: sample /= 65536; break; default: sample = 0; break; } *output = (short) sample; } } my compressedShorts += numberOfSamples * my numberOfChannels; } static FLAC__StreamDecoderWriteStatus _LongSound_FLAC_write (const FLAC__StreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer[], I) { iam (LongSound); const FLAC__FrameHeader *header = & frame -> header; long numberOfSamples = header -> blocksize; long bitsPerSample = header -> bits_per_sample; (void) decoder; if (numberOfSamples > my compressedSamplesLeft) numberOfSamples = my compressedSamplesLeft; if (numberOfSamples == 0) return FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE; if (my compressedMode == COMPRESSED_MODE_READ_FLOAT) _LongSound_FLAC_convertFloats (me, buffer, bitsPerSample, numberOfSamples); else _LongSound_FLAC_convertShorts (me, buffer, bitsPerSample, numberOfSamples); my compressedSamplesLeft -= numberOfSamples; return FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE; } static void _LongSound_FLAC_error (const FLAC__StreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status, I) { iam (LongSound); (void) me; (void) decoder; (void) status; } static void _LongSound_MP3_convertFloats (LongSound me, const MP3F_SAMPLE *channels[MP3F_MAX_CHANNELS], long numberOfSamples) { for (long i = 0; i < 2; ++i) { const MP3F_SAMPLE *input = channels [i]; double *output = my compressedFloats [i]; if (! output ) continue; for (long j = 0; j < numberOfSamples; ++j) output [j] = mp3f_sample_to_float (input [j]); my compressedFloats [i] += numberOfSamples; } } static void _LongSound_MP3_convertShorts (LongSound me, const MP3F_SAMPLE *channels[MP3F_MAX_CHANNELS], long numberOfSamples) { for (long i = 0; i < my numberOfChannels; ++ i) { const MP3F_SAMPLE *input = channels [i]; short *output = my compressedShorts + i; for (long j = 0; j < numberOfSamples; ++j, output += my numberOfChannels) { int sample = *input++; *output = mp3f_sample_to_short (sample); } } my compressedShorts += numberOfSamples * my numberOfChannels; } static void _LongSound_MP3_convert (const MP3F_SAMPLE *channels[MP3F_MAX_CHANNELS], long numberOfSamples, I) { iam (LongSound); if (numberOfSamples > my compressedSamplesLeft) numberOfSamples = my compressedSamplesLeft; if (numberOfSamples == 0) return; if (my compressedMode == COMPRESSED_MODE_READ_FLOAT) _LongSound_MP3_convertFloats (me, channels, numberOfSamples); else _LongSound_MP3_convertShorts (me, channels, numberOfSamples); my compressedSamplesLeft -= numberOfSamples; } static void LongSound_init (LongSound me, MelderFile file) { MelderFile_copy (file, & my file); MelderFile_open (file); therror // BUG: should be auto, but that requires an implemented .transfer() my f = file -> filePointer; my audioFileType = MelderFile_checkSoundFile (file, & my numberOfChannels, & my encoding, & my sampleRate, & my startOfData, & my nx); therror if (my audioFileType == 0) Melder_throw ("File not recognized (LongSound only supports AIFF, AIFC, WAV, NeXT/Sun, NIST and FLAC)."); if (my encoding == Melder_SHORTEN || my encoding == Melder_POLYPHONE) Melder_throw ("LongSound does not support sound files compressed with \"shorten\"."); my xmin = 0.0; my dx = 1 / my sampleRate; my xmax = my nx * my dx; my x1 = 0.5 * my dx; my numberOfBytesPerSamplePoint = Melder_bytesPerSamplePoint (my encoding); my bufferLength = prefs_bufferLength; for (;;) { my nmax = my bufferLength * my numberOfChannels * my sampleRate * (1 + 3 * MARGIN); try { my buffer = NUMvector (0, my nmax * my numberOfChannels); break; } catch (MelderError) { my bufferLength *= 0.5; // try 30, 15, or 7.5 seconds if (my bufferLength < 5.0) // too short to be good throw; Melder_clearError (); // delete out-of-memory message } } my imin = 1; my imax = 0; my flacDecoder = NULL; if (my audioFileType == Melder_FLAC) { my flacDecoder = FLAC__stream_decoder_new (); FLAC__stream_decoder_init_FILE (my flacDecoder, my f, _LongSound_FLAC_write, NULL, _LongSound_FLAC_error, me); } my mp3f = NULL; if (my audioFileType == Melder_MP3) { my mp3f = mp3f_new (); mp3f_set_file (my mp3f, my f); mp3f_set_callback (my mp3f, _LongSound_MP3_convert, me); if (! mp3f_analyze (my mp3f)) Melder_throw ("Unable to analyze MP3 file."); Melder_warning (L"Time measurements in MP3 files can be off by several tens of milliseconds. " "Please convert to WAV file if you need time precision or annotation."); } } void structLongSound :: v_copy (thou) { thouart (LongSound); thy f = NULL; thy buffer = NULL; LongSound_init (thee, & file); } LongSound LongSound_open (MelderFile file) { try { autoLongSound me = Thing_new (LongSound); LongSound_init (me.peek(), file); return me.transfer(); } catch (MelderError) { Melder_throw ("LongSound not created."); } } static void _LongSound_FLAC_process (LongSound me, long firstSample, long numberOfSamples) { my compressedSamplesLeft = numberOfSamples - 1; if (! FLAC__stream_decoder_seek_absolute (my flacDecoder, firstSample)) Melder_throw ("Cannot seek in FLAC file ", & my file, "."); while (my compressedSamplesLeft > 0) { if (FLAC__stream_decoder_get_state (my flacDecoder) == FLAC__STREAM_DECODER_END_OF_STREAM) Melder_throw ("FLAC file ", & my file, " too short."); if (! FLAC__stream_decoder_process_single (my flacDecoder)) Melder_throw ("Error decoding FLAC file ", & my file, "."); } } static void _LongSound_FILE_seekSample (LongSound me, long firstSample) { if (fseek (my f, my startOfData + (firstSample - 1) * my numberOfChannels * my numberOfBytesPerSamplePoint, SEEK_SET)) Melder_throw ("Cannot seek in file ", & my file, "."); } static void _LongSound_FLAC_readAudioToShort (LongSound me, short *buffer, long firstSample, long numberOfSamples) { my compressedMode = COMPRESSED_MODE_READ_SHORT; my compressedShorts = buffer + 1; _LongSound_FLAC_process (me, firstSample, numberOfSamples); } static void _LongSound_MP3_process (LongSound me, long firstSample, long numberOfSamples) { if (! mp3f_seek (my mp3f, firstSample)) Melder_throw ("Cannot seek in MP3 file ", & my file, "."); my compressedSamplesLeft = numberOfSamples; if (! mp3f_read (my mp3f, numberOfSamples)) Melder_throw ("Error decoding MP3 file ", & my file, "."); } static void _LongSound_MP3_readAudioToShort (LongSound me, short *buffer, long firstSample, long numberOfSamples) { my compressedMode = COMPRESSED_MODE_READ_SHORT; my compressedShorts = buffer + 1; _LongSound_MP3_process (me, firstSample, numberOfSamples - 1); } void LongSound_readAudioToFloat (LongSound me, double **buffer, long firstSample, long numberOfSamples) { if (my encoding == Melder_FLAC_COMPRESSION_16) { my compressedMode = COMPRESSED_MODE_READ_FLOAT; for (int ichan = 1; ichan <= my numberOfChannels; ichan ++) { my compressedFloats [ichan - 1] = & buffer [ichan] [1]; } _LongSound_FLAC_process (me, firstSample, numberOfSamples); therror } else if (my encoding == Melder_MPEG_COMPRESSION_16) { my compressedMode = COMPRESSED_MODE_READ_FLOAT; for (int ichan = 1; ichan <= my numberOfChannels; ichan ++) { my compressedFloats [ichan - 1] = & buffer [ichan] [1]; } _LongSound_MP3_process (me, firstSample, numberOfSamples); therror } else { _LongSound_FILE_seekSample (me, firstSample); therror Melder_readAudioToFloat (my f, my numberOfChannels, my encoding, buffer, numberOfSamples); } } void LongSound_readAudioToShort (LongSound me, short *buffer, long firstSample, long numberOfSamples) { if (my encoding == Melder_FLAC_COMPRESSION_16) { _LongSound_FLAC_readAudioToShort (me, buffer, firstSample, numberOfSamples); therror } else if (my encoding == Melder_MPEG_COMPRESSION_16) { _LongSound_MP3_readAudioToShort (me, buffer, firstSample, numberOfSamples); therror } else { _LongSound_FILE_seekSample (me, firstSample); therror Melder_readAudioToShort (my f, my numberOfChannels, my encoding, buffer, numberOfSamples); } } Sound LongSound_extractPart (LongSound me, double tmin, double tmax, int preserveTimes) { try { if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } if (tmin < my xmin) tmin = my xmin; if (tmax > my xmax) tmax = my xmax; long imin, imax; long n = Sampled_getWindowSamples (me, tmin, tmax, & imin, & imax); if (n < 1) Melder_throw ("Less than 1 sample in window."); autoSound thee = Sound_create (my numberOfChannels, tmin, tmax, n, my dx, my x1 + (imin - 1) * my dx); if (! preserveTimes) thy xmin = 0.0, thy xmax -= tmin, thy x1 -= tmin; LongSound_readAudioToFloat (me, thy z, imin, n); therror return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": Sound not extracted."); } } static void _LongSound_readSamples (LongSound me, short *buffer, long imin, long imax) { LongSound_readAudioToShort (me, buffer, imin, imax - imin + 1); } static void writePartToOpenFile (LongSound me, int audioFileType, long imin, long n, MelderFile file, int numberOfChannels_override, int numberOfBitsPerSamplePoint) { long ibuffer, offset, numberOfBuffers, numberOfSamplesInLastBuffer; offset = imin; numberOfBuffers = (n - 1) / my nmax + 1; numberOfSamplesInLastBuffer = (n - 1) % my nmax + 1; if (file -> filePointer) for (ibuffer = 1; ibuffer <= numberOfBuffers; ibuffer ++) { long numberOfSamplesToCopy = ibuffer < numberOfBuffers ? my nmax : numberOfSamplesInLastBuffer; LongSound_readAudioToShort (me, my buffer, offset, numberOfSamplesToCopy); offset += numberOfSamplesToCopy; MelderFile_writeShortToAudio (file, numberOfChannels_override ? numberOfChannels_override : my numberOfChannels, Melder_defaultAudioFileEncoding (audioFileType, numberOfBitsPerSamplePoint), my buffer, numberOfSamplesToCopy); } /* * We "have" no samples any longer. */ my imin = 1; my imax = 0; } void LongSound_writePartToAudioFile (LongSound me, int audioFileType, double tmin, double tmax, MelderFile file) { try { if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } if (tmin < my xmin) tmin = my xmin; if (tmax > my xmax) tmax = my xmax; long imin, imax; long n = Sampled_getWindowSamples (me, tmin, tmax, & imin, & imax); if (n < 1) Melder_throw (L"Less than 1 sample selected."); autoMelderFile mfile = MelderFile_create (file, Melder_macAudioFileType (audioFileType), L"PpgB", Melder_winAudioFileExtension (audioFileType)); MelderFile_writeAudioFileHeader (file, audioFileType, my sampleRate, n, my numberOfChannels, 8 * my numberOfBytesPerSamplePoint); therror writePartToOpenFile (me, audioFileType, imin, n, file, 0, 8 * my numberOfBytesPerSamplePoint); therror MelderFile_writeAudioFileTrailer (file, audioFileType, my sampleRate, n, my numberOfChannels, 8 * my numberOfBytesPerSamplePoint); therror mfile.close (); } catch (MelderError) { Melder_throw (me, ": not written to sound file ", file, "."); } } void LongSound_writeChannelToAudioFile (LongSound me, int audioFileType, int channel, MelderFile file) { try { if (my numberOfChannels != 2) Melder_throw ("This audio file is not a stereo file. It does not have a ", channel == 0 ? L"left" : L"right", L" channel."); autoMelderFile mfile = MelderFile_create (file, Melder_macAudioFileType (audioFileType), L"PpgB", Melder_winAudioFileExtension (audioFileType)); if (file -> filePointer) { MelderFile_writeAudioFileHeader (file, audioFileType, my sampleRate, my nx, 1, 8 * my numberOfBytesPerSamplePoint); therror } writePartToOpenFile (me, audioFileType, 1, my nx, file, channel == 0 ? -1 : -2, 8 * my numberOfBytesPerSamplePoint); therror MelderFile_writeAudioFileTrailer (file, audioFileType, my sampleRate, my nx, 1, 8 * my numberOfBytesPerSamplePoint); therror mfile.close (); } catch (MelderError) { Melder_throw ("Channel ", channel, " of ", me, ": not written to sound file ", file, "."); } } static void _LongSound_haveSamples (LongSound me, long imin, long imax) { long n = imax - imin + 1; Melder_assert (n <= my nmax); /* * Included? */ if (imin >= my imin && imax <= my imax) return; /* * Extendable? */ if (imin >= my imin && imax - my imin + 1 <= my nmax) { _LongSound_readSamples (me, my buffer + (my imax - my imin + 1) * my numberOfChannels, my imax + 1, imax); my imax = imax; return; } /* * Determine the loadable imin..imax. * Add margins on both sides. */ imin -= MARGIN * n; if (imin < 1) imin = 1; imax = imin + (1.0 + 2 * MARGIN) * n; if (imax > my nx) imax = my nx; imin = imax - (1.0 + 2 * MARGIN) * n; if (imin < 1) imin = 1; Melder_assert (imax - imin + 1 <= my nmax); /* * Overlap? */ if (imax < my imin || imin > my imax) { /* * No overlap. */ _LongSound_readSamples (me, my buffer, imin, imax); } else if (imin < my imin) { /* * Left overlap. */ if (imax <= my imax) { /* * Only left overlap (e.g. scrolling up). */ long nshift = (imax - my imin + 1) * my numberOfChannels, shift = (my imin - imin) * my numberOfChannels; #if USE_MEMMOVE memmove (my buffer + shift, my buffer, nshift * sizeof (short)); #else for (i = nshift - 1; i >= 0; i --) my buffer [i + shift] = my buffer [i]; #endif _LongSound_readSamples (me, my buffer, imin, my imin - 1); } else { /* * Left and right overlap (e.g. zooming out). */ long nshift = (my imax - my imin + 1) * my numberOfChannels, shift = (my imin - imin) * my numberOfChannels; #if USE_MEMMOVE memmove (my buffer + shift, my buffer, nshift * sizeof (short)); #else for (i = nshift - 1; i >= 0; i --) my buffer [i + shift] = my buffer [i]; #endif _LongSound_readSamples (me, my buffer, imin, my imin - 1); _LongSound_readSamples (me, my buffer + (my imax - imin + 1) * my numberOfChannels, my imax + 1, imax); } } else { /* * Only right overlap (e.g. scrolling down). */ long nshift = (my imax - imin + 1) * my numberOfChannels, shift = (imin - my imin) * my numberOfChannels; #if USE_MEMMOVE memmove (my buffer, my buffer + shift, nshift * sizeof (short)); #else for (i = 0; i < nshift; i ++) my buffer [i] = my buffer [i + shift]; #endif _LongSound_readSamples (me, my buffer + (my imax - imin + 1) * my numberOfChannels, my imax + 1, imax); } my imin = imin, my imax = imax; } bool LongSound_haveWindow (LongSound me, double tmin, double tmax) { long imin, imax; long n = Sampled_getWindowSamples (me, tmin, tmax, & imin, & imax); if ((1.0 + 2 * MARGIN) * n + 1 > my nmax) return false; _LongSound_haveSamples (me, imin, imax); return true; } void LongSound_getWindowExtrema (LongSound me, double tmin, double tmax, int channel, double *minimum, double *maximum) { long imin, imax; long i, minimum_int = 32767, maximum_int = -32768; (void) Sampled_getWindowSamples (me, tmin, tmax, & imin, & imax); *minimum = 1.0; *maximum = -1.0; try { LongSound_haveWindow (me, tmin, tmax); therror } catch (MelderError) { Melder_clearError (); return; } for (i = imin; i <= imax; i ++) { long value = my buffer [(i - my imin) * my numberOfChannels + channel - 1]; if (value < minimum_int) minimum_int = value; if (value > maximum_int) maximum_int = value; } *minimum = minimum_int / 32768.0; *maximum = maximum_int / 32768.0; } static struct LongSoundPlay { long numberOfSamples, i1, i2, silenceBefore, silenceAfter; double tmin, tmax, dt, t1; short *resampledBuffer; int (*callback) (void *closure, int phase, double tmin, double tmax, double t); void *closure; } thePlayingLongSound; static bool melderPlayCallback (void *closure, long samplesPlayed) { struct LongSoundPlay *me = (struct LongSoundPlay *) closure; int phase = 2; double t = samplesPlayed <= my silenceBefore ? my tmin : samplesPlayed >= my silenceBefore + my numberOfSamples ? my tmax : my t1 + (my i1 - 1.5 + samplesPlayed - my silenceBefore) * my dt; if (! MelderAudio_isPlaying) { phase = 3; Melder_free (my resampledBuffer); } if (my callback) return my callback (my closure, phase, my tmin, my tmax, t); return true; } void LongSound_playPart (LongSound me, double tmin, double tmax, int (*callback) (void *closure, int phase, double tmin, double tmax, double t), void *closure) { struct LongSoundPlay *thee = (struct LongSoundPlay *) & thePlayingLongSound; Melder_free (thy resampledBuffer); // just in case try { int fits = LongSound_haveWindow (me, tmin, tmax); therror long bestSampleRate = MelderAudio_getOutputBestSampleRate (my sampleRate), n, i1, i2; if (! fits) Melder_throw ("Sound too long (", tmax - tmin, " seconds)."); MelderAudio_stopPlaying (MelderAudio_IMPLICIT); /* * Assign to *thee only after stopping the playing sound. */ thy tmin = tmin; thy tmax = tmax; thy callback = callback; thy closure = closure; if ((n = Sampled_getWindowSamples (me, tmin, tmax, & i1, & i2)) < 2) return; if (bestSampleRate == my sampleRate) { thy numberOfSamples = n; thy dt = 1 / my sampleRate; thy t1 = my x1; thy i1 = i1; thy i2 = i2; thy silenceBefore = (long) (my sampleRate * MelderAudio_getOutputSilenceBefore ()); thy silenceAfter = (long) (my sampleRate * MelderAudio_getOutputSilenceAfter ()); if (thy callback) thy callback (thy closure, 1, tmin, tmax, tmin); if (thy silenceBefore > 0 || thy silenceAfter > 0) { thy resampledBuffer = Melder_calloc (short, (thy silenceBefore + thy numberOfSamples + thy silenceAfter) * my numberOfChannels); memcpy (& thy resampledBuffer [thy silenceBefore * my numberOfChannels], & my buffer [(i1 - my imin) * my numberOfChannels], thy numberOfSamples * sizeof (short) * my numberOfChannels); MelderAudio_play16 (thy resampledBuffer, my sampleRate, thy silenceBefore + thy numberOfSamples + thy silenceAfter, my numberOfChannels, melderPlayCallback, thee); therror } else { MelderAudio_play16 (my buffer + (i1 - my imin) * my numberOfChannels, my sampleRate, thy numberOfSamples, my numberOfChannels, melderPlayCallback, thee); therror } } else { long newSampleRate = bestSampleRate; long newN = ((double) n * newSampleRate) / my sampleRate - 1, i; long silenceBefore = (long) (newSampleRate * MelderAudio_getOutputSilenceBefore ()); long silenceAfter = (long) (newSampleRate * MelderAudio_getOutputSilenceAfter ()); short *resampledBuffer = Melder_calloc (short, (silenceBefore + newN + silenceAfter) * my numberOfChannels); short *from = my buffer + (i1 - my imin) * my numberOfChannels; /* Guaranteed: from [0 .. (my imax - my imin + 1) * nchan] */ double t1 = my x1, dt = 1.0 / newSampleRate; thy numberOfSamples = newN; thy dt = dt; thy t1 = t1 + i1 / my sampleRate; thy i1 = 0; thy i2 = newN - 1; thy silenceBefore = silenceBefore; thy silenceAfter = silenceAfter; thy resampledBuffer = resampledBuffer; if (my numberOfChannels == 1) { for (i = 0; i < newN; i ++) { double t = t1 + i * dt; /* From t1 to t1 + (newN-1) * dt */ double index = (t - t1) * my sampleRate; /* From 0. */ long flore = index; /* DANGEROUS: Implicitly rounding down... */ double fraction = index - flore; resampledBuffer [i + silenceBefore] = (1 - fraction) * from [flore] + fraction * from [flore + 1]; } } else { for (i = 0; i < newN; i ++) { double t = t1 + i * dt; double index = (t - t1) * newSampleRate; long flore = index, ii = i + silenceBefore; double fraction = index - flore; resampledBuffer [ii + ii] = (1 - fraction) * from [flore + flore] + fraction * from [flore + flore + 2]; resampledBuffer [ii + ii + 1] = (1 - fraction) * from [flore + flore + 1] + fraction * from [flore + flore + 3]; } } if (thy callback) thy callback (thy closure, 1, tmin, tmax, tmin); MelderAudio_play16 (resampledBuffer, newSampleRate, silenceBefore + newN + silenceAfter, my numberOfChannels, melderPlayCallback, thee); therror } //Melder_free (thy resampledBuffer); // cannot do that, because MelderAudio_play16 isn't necessarily synchronous } catch (MelderError) { Melder_free (thy resampledBuffer); Melder_throw (me, ": not played"); } } void LongSound_concatenate (Collection me, MelderFile file, int audioFileType, int numberOfBitsPerSamplePoint) { try { long sampleRate, n; /* Integer sampling frequencies only, because of possible rounding errors. */ int numberOfChannels; if (my size < 1) Melder_throw ("No Sound or LongSound objects to concatenate."); /* * The sampling frequencies and numbers of channels must be equal for all (long)sounds. */ Sampled data = (Sampled) my item [1]; if (data -> classInfo == classSound) { Sound sound = (Sound) data; sampleRate = floor (1.0 / sound -> dx + 0.5); numberOfChannels = sound -> ny; n = sound -> nx; } else { LongSound longSound = (LongSound) data; sampleRate = longSound -> sampleRate; numberOfChannels = longSound -> numberOfChannels; n = longSound -> nx; } /* * Check whether all the sampling frequencies and channels match. */ for (long i = 2; i <= my size; i ++) { int sampleRatesMatch, numbersOfChannelsMatch; data = (Sampled) my item [i]; if (data -> classInfo == classSound) { Sound sound = (Sound) data; sampleRatesMatch = floor (1.0 / sound -> dx + 0.5) == sampleRate; numbersOfChannelsMatch = sound -> ny == numberOfChannels; n += sound -> nx; } else { LongSound longSound = (LongSound) data; sampleRatesMatch = longSound -> sampleRate == sampleRate; numbersOfChannelsMatch = longSound -> numberOfChannels == numberOfChannels; n += longSound -> nx; } if (! sampleRatesMatch) Melder_throw ("Sampling frequencies are not equal."); if (! numbersOfChannelsMatch) Melder_throw ("Cannot mix stereo and mono."); } /* * Create output file and write header. */ autoMelderFile mfile = MelderFile_create (file, Melder_macAudioFileType (audioFileType), L"PpgB", Melder_winAudioFileExtension (audioFileType)); if (file -> filePointer) { MelderFile_writeAudioFileHeader (file, audioFileType, sampleRate, n, numberOfChannels, numberOfBitsPerSamplePoint); therror } for (long i = 1; i <= my size; i ++) { data = (Sampled) my item [i]; if (data -> classInfo == classSound) { Sound sound = (Sound) data; if (file -> filePointer) { MelderFile_writeFloatToAudio (file, sound -> ny, Melder_defaultAudioFileEncoding (audioFileType, numberOfBitsPerSamplePoint), sound -> z, sound -> nx, TRUE); therror } } else { LongSound longSound = (LongSound) data; writePartToOpenFile (longSound, audioFileType, 1, longSound -> nx, file, 0, numberOfBitsPerSamplePoint); therror } } MelderFile_writeAudioFileTrailer (file, audioFileType, sampleRate, n, numberOfChannels, numberOfBitsPerSamplePoint); therror mfile.close (); } catch (MelderError) { Melder_throw ("Sounds not concatenated and not saved to ", file, "."); } } /* End of file LongSound.cpp */ sources_5316/fon/Spectrogram.cpp0000644000176700017670000001407411724501647015514 0ustar paulpaul/* Spectrogram.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include "Spectrogram.h" Thing_implement (Spectrogram, Matrix, 2); void structSpectrogram :: v_info () { structData :: v_info (); MelderInfo_writeLine1 (L"Time domain:"); MelderInfo_writeLine3 (L" Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine3 (L" End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine3 (L" Total duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine1 (L"Time sampling:"); MelderInfo_writeLine2 (L" Number of time slices (frames): ", Melder_integer (nx)); MelderInfo_writeLine3 (L" Time step (frame distance): ", Melder_double (dx), L" seconds"); MelderInfo_writeLine3 (L" First time slice (frame centre) at: ", Melder_double (x1), L" seconds"); MelderInfo_writeLine1 (L"Frequency domain:"); MelderInfo_writeLine3 (L" Lowest frequency: ", Melder_double (ymin), L" Hz"); MelderInfo_writeLine3 (L" Highest frequency: ", Melder_double (ymax), L" Hz"); MelderInfo_writeLine3 (L" Total bandwidth: ", Melder_double (xmax - xmin), L" Hz"); MelderInfo_writeLine1 (L"Frequency sampling:"); MelderInfo_writeLine2 (L" Number of frequency bands (bins): ", Melder_integer (ny)); MelderInfo_writeLine3 (L" Frequency step (bin width): ", Melder_double (dy), L" Hz"); MelderInfo_writeLine3 (L" First frequency band around (bin centre at): ", Melder_double (y1), L" Hz"); } Spectrogram Spectrogram_create (double tmin, double tmax, long nt, double dt, double t1, double fmin, double fmax, long nf, double df, double f1) { try { autoSpectrogram me = Thing_new (Spectrogram); Matrix_init (me.peek(), tmin, tmax, nt, dt, t1, fmin, fmax, nf, df, f1); return me.transfer(); } catch (MelderError) { Melder_throw ("Spectrogram not created."); } } void Spectrogram_paintInside (I, Graphics g, double tmin, double tmax, double fmin, double fmax, double maximum, int autoscaling, double dynamic, double preemphasis, double dynamicCompression) { iam (Spectrogram); if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } if (fmax <= fmin) { fmin = my ymin; fmax = my ymax; } long itmin, itmax, ifmin, ifmax; if (! Matrix_getWindowSamplesX (me, tmin - 0.49999 * my dx, tmax + 0.49999 * my dx, & itmin, & itmax) || ! Matrix_getWindowSamplesY (me, fmin - 0.49999 * my dy, fmax + 0.49999 * my dy, & ifmin, & ifmax)) return; Graphics_setWindow (g, tmin, tmax, fmin, fmax); autoNUMvector preemphasisFactor (ifmin, ifmax); autoNUMvector dynamicFactor (itmin, itmax); /* Pre-emphasis in place; also compute maximum after pre-emphasis. */ for (long ifreq = ifmin; ifreq <= ifmax; ifreq ++) { preemphasisFactor [ifreq] = (preemphasis / NUMln2) * log (ifreq * my dy / 1000.0); for (long itime = itmin; itime <= itmax; itime ++) { double value = my z [ifreq] [itime]; /* Power. */ value = (10.0/NUMln10) * log ((value + 1e-30) / 4.0e-10) + preemphasisFactor [ifreq]; /* dB */ if (value > dynamicFactor [itime]) dynamicFactor [itime] = value; /* Local maximum. */ my z [ifreq] [itime] = value; } } /* Compute global maximum. */ if (autoscaling) { maximum = 0.0; for (long itime = itmin; itime <= itmax; itime ++) if (dynamicFactor [itime] > maximum) maximum = dynamicFactor [itime]; } /* Dynamic compression in place. */ for (long itime = itmin; itime <= itmax; itime ++) { dynamicFactor [itime] = dynamicCompression * (maximum - dynamicFactor [itime]); for (long ifreq = ifmin; ifreq <= ifmax; ifreq ++) my z [ifreq] [itime] += dynamicFactor [itime]; } Graphics_image (g, my z, itmin, itmax, Matrix_columnToX (me, itmin - 0.5), Matrix_columnToX (me, itmax + 0.5), ifmin, ifmax, Matrix_rowToY (me, ifmin - 0.5), Matrix_rowToY (me, ifmax + 0.5), maximum - dynamic, maximum); for (long ifreq = ifmin; ifreq <= ifmax; ifreq ++) for (long itime = itmin; itime <= itmax; itime ++) { double value = 4.0e-10 * exp ((my z [ifreq] [itime] - dynamicFactor [itime] - preemphasisFactor [ifreq]) * (NUMln10 / 10.0)) - 1e-30; my z [ifreq] [itime] = value > 0.0 ? value : 0.0; } } void Spectrogram_paint (I, Graphics g, double tmin, double tmax, double fmin, double fmax, double maximum, int autoscaling, double dynamic, double preemphasis, double dynamicCompression, int garnish) { iam (Spectrogram); Graphics_setInner (g); Spectrogram_paintInside (me, g, tmin, tmax, fmin, fmax, maximum, autoscaling, dynamic, preemphasis, dynamicCompression); Graphics_unsetInner (g); if (garnish) { Graphics_drawInnerBox (g); Graphics_textBottom (g, 1, L"Time (s)"); Graphics_marksBottom (g, 2, 1, 1, 0); Graphics_marksLeft (g, 2, 1, 1, 0); Graphics_textLeft (g, 1, L"Frequency (Hz)"); } } Spectrogram Matrix_to_Spectrogram (I) { iam (Matrix); try { autoSpectrogram thee = Spectrogram_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Spectrogram."); } } Matrix Spectrogram_to_Matrix (I) { iam (Spectrogram); try { autoMatrix thee = Matrix_create (my xmin, my xmax, my nx, my dx, my x1, my ymin, my ymax, my ny, my dy, my y1); NUMmatrix_copyElements (my z, thy z, 1, my ny, 1, my nx); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Matrix."); } } /* End of Spectrogram.cpp */ sources_5316/fon/ParamCurve.h0000644000176700017670000000441411625721240014726 0ustar paulpaul#ifndef _ParamCurve_h_ #define _ParamCurve_h_ /* ParamCurve.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Parametrized curve (x (t), y (t)): two functions (x and y) of one variable (the parameter t). Sampled parametrized curve (x [i], y [j]): x [i] = x (tx [i]) = x (tx1 + (i - 1) * dtx); y [i] = y (ty [i]) = y (ty1 + (i - 1) * dty); */ #include "Sound.h" #include "Graphics.h" #include "ParamCurve_def.h" oo_CLASS_CREATE (ParamCurve, Function); void ParamCurve_init (I, Any x, Any y); ParamCurve ParamCurve_create (Any x, Any y); /* Return value: a newly created ParamCurve object, or NULL in case of failure. Failures: Out of memory. Domains do not overlap: x -> xmax <= y -> xmin || x -> xmin >= y -> xmax. Postconditions: (Result's domain is intersection of both domains:) result -> xmin = max (x -> xmin, y -> xmin); result -> xmax = min (x -> xmax, y -> xmax); */ void ParamCurve_draw (I, Graphics g, double t1, double t2, double dt, double x1, double x2, double y1, double y2, int garnish); /* Function: draw the points of the curve between parameter values t1 and t2, in time steps dt starting at t1 and including t2, along the axes [x1, x2] x [y1, y2]. Defaults: t2 <= t1: draw all (overlapping) points. dt <= 0.0: time step is the smaller of my x -> dx and my y -> dx. x2 <= x1: autoscaling along horizontal axis. y2 <= y1: autoscaling along vertical axis. Return value: 1 if OK, 0 if out of memory. */ void ParamCurve_swapXY (I); /* Reflect around y = x. Postconditions: x == old y; y == old x; */ /* End of file ParamCurve.h */ #endif sources_5316/fon/ManipulationEditor_enums.h0000644000176700017670000000371210727053330017677 0ustar paulpaul/* ManipulationEditor_enums.h * * Copyright (C) 1992-2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/09 */ enums_begin (kManipulationEditor_draggingStrategy, 1) enums_add (kManipulationEditor_draggingStrategy, 1, ALL, L"all") enums_add (kManipulationEditor_draggingStrategy, 2, HORIZONTAL, L"only horizontal") enums_add (kManipulationEditor_draggingStrategy, 3, VERTICAL, L"only vertical") enums_add (kManipulationEditor_draggingStrategy, 4, HYBRID, L"single all, multiple only vertical") /* For reading old preferences files: */ enums_alt (kManipulationEditor_draggingStrategy, ALL, L"1") enums_alt (kManipulationEditor_draggingStrategy, HORIZONTAL, L"2") enums_alt (kManipulationEditor_draggingStrategy, VERTICAL, L"3") enums_alt (kManipulationEditor_draggingStrategy, HYBRID, L"4") enums_end (kManipulationEditor_draggingStrategy, 4, ALL) enums_begin (kManipulationEditor_pitchUnits, 1) enums_add (kManipulationEditor_pitchUnits, 1, HERTZ, L"Hertz") enums_add (kManipulationEditor_pitchUnits, 2, SEMITONES, L"semitones re 100 Hz") /* For reading old preferences files: */ enums_alt (kManipulationEditor_pitchUnits, HERTZ, L"1") enums_alt (kManipulationEditor_pitchUnits, SEMITONES, L"2") enums_end (kManipulationEditor_pitchUnits, 2, HERTZ) /* End of file ManipulationEditor.h */ sources_5316/fon/Praat_tests.cpp0000644000176700017670000000243311724373643015516 0ustar paulpaul/* Praat_tests.cpp */ /* Paul Boersma, August 2, 2001 */ /* December 10, 2006: MelderInfo */ /* November 5, 2007: wchar */ /* 21 March 2009: modern enums */ /* 24 May 2011: C++ */ #include "Praat_tests.h" #include "enums_getText.h" #include "Praat_tests_enums.h" int Praat_tests (int itest, wchar *arg1, wchar *arg2, wchar *arg3, wchar *arg4) { long i, n = wcstol (arg1, NULL, 10); double x; (void) arg1; (void) arg2; (void) arg3; (void) arg4; Melder_clearInfo (); Melder_stopwatch (); switch (itest) { case kPraatTests_CHECK_RANDOM_1009_2009: { NUMrandomRestart (310952); for (i = 1; i <= 1009 * 2009 - 100 + 1; i ++) x = NUMrandomFraction (); MelderInfo_writeLine1 (Melder_double (x)); } break; case kPraatTests_TIME_RANDOM_FRACTION: { for (i = 1; i <= n; i ++) (void) NUMrandomFraction (); } break; case kPraatTests_TIME_SORT: { long m = wcstol (arg2, NULL, 10); long *array = NUMvector (1, m); for (i = 1; i <= m; i ++) array [i] = NUMrandomInteger (1, 100); Melder_stopwatch (); for (i = 1; i <= n; i ++) NUMsort_l (m, array); NUMvector_free (array, 1); } break; } MelderInfo_writeLine2 (Melder_single (Melder_stopwatch () / n * 1e9), L" nanoseconds"); MelderInfo_close (); return 1; } /* End of file Praat_tests.cpp */ sources_5316/fon/manual_tutorials.cpp0000644000176700017670000066057511757244463016634 0ustar paulpaul/* manual_tutorials.cpp * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" #include "praat_version.h" void manual_tutorials_init (ManPages me); void manual_tutorials_init (ManPages me) { MAN_BEGIN (L"What's new?", L"ppgb", 20120523) INTRO (L"Latest changes in Praat.") /*LIST_ITEM (L"\\bu Manual page about @@drawing a vowel triangle@.")*/ NORMAL (L"##5.3.16# (23 May 2012)") NORMAL (L"##5.3.15# (10 May 2012)") LIST_ITEM (L"\\bu Improvements in clipboards, PDF and EPS files.") NORMAL (L"##5.3.14# (28 April 2012)") LIST_ITEM (L"\\bu Linux: Tab shortcut for playing the selection.") LIST_ITEM (L"\\bu EPS files: higher minimum image resolution for spectrograms (300 instead of 106 dpi).") NORMAL (L"##5.3.13# (11 April 2012)") LIST_ITEM (L"\\bu @EEG: Extract part...") NORMAL (L"##5.3.12# (5 April 2012)") LIST_ITEM (L"\\bu Praat picture file: allow larger function drawings (up to 10^9 instead of 10^6 points).") LIST_ITEM (L"\\bu Linux: better audio compatibility with Ubuntu 11.10 (support for unusual sampling frequencies when playing LongSounds).") NORMAL (L"##5.3.11# (27 March 2012)") LIST_ITEM (L"\\bu @EEG: a selected ERPTier can extract events on the basis of a column of a selected Table.") NORMAL (L"##5.3.10# (12 March 2012)") LIST_ITEM (L"\\bu @EEG: Concatenate.") NORMAL (L"##5.3.09# (10 March 2012)") LIST_ITEM (L"\\bu Better text-to-speech.") NORMAL (L"##5.3.08# (5 March 2012)") LIST_ITEM (L"\\bu Removed a bug introduced in 5.3.07 that could cause Praat to crash when viewing a LongSound.") NORMAL (L"##5.3.07# (4 March 2012)") LIST_ITEM (L"\\bu Praat can now save Sounds as 24-bit and 32-bit WAV files.") NORMAL (L"##5.3.06# (28 February 2012)") NORMAL (L"##5.3.05# (19 February 2012)") LIST_ITEM (L"\\bu SpeechSynthesizer (#New menu \\-> #Sound): text-to-speech.") LIST_ITEM (L"\\bu @EEG: better scalp distribution drawing for both 32-channel and 64-channel recordings.") NORMAL (L"##5.3.04# (12 January 2012)") LIST_ITEM (L"\\bu EEG: draw scalp distribution.") LIST_ITEM (L"\\bu Linux: better audio compatibility with Ubuntu 11.10 (support for unusual sampling frequencies when playing Sounds).") NORMAL (L"##5.3.03# (21 November 2011)") LIST_ITEM (L"\\bu EEG: filtering, editing, more viewing.") NORMAL (L"##5.3.02# (7 November 2011)") LIST_ITEM (L"\\bu Corrected a bug introduced in 5.3.01 that could cause the PitchTier or PointProcess window to crash.") LIST_ITEM (L"\\bu Corrected a bug that could cause the Info window to freeze after an error message in a script window.") NORMAL (L"##5.3.01# (1 November 2011)") LIST_ITEM (L"\\bu Macintosh and Windows: better window positioning if the Dock or Task Bar is on the left or right.") LIST_ITEM (L"\\bu IPA symbol: you can now use \\bs.f for the half-length sign (\\.f).") LIST_ITEM (L"\\bu EEG window.") NORMAL (L"##5.3# (15 October 2011)") NORMAL (L"##5.2.46# (7 October 2011)") LIST_ITEM (L"\\bu Corrected the same very old bug as in 5.2.44, but now also for opening and saving files.") LIST_ITEM (L"\\bu Many better messages.") NORMAL (L"##5.2.45# (29 September 2011)") LIST_ITEM (L"\\bu Spectrum window: ##Move cursor to nearest peak#.") LIST_ITEM (L"\\bu Table: ##Save as comma-separated file...#.") LIST_ITEM (L"\\bu Windows: you can now change the font size of the script window.") LIST_ITEM (L"\\bu Windows scripting: the Info window now updates while you are writing to it.") LIST_ITEM (L"\\bu Windows: error messages now stay at the front so that you never have to click away " "an invisible message window anymore.") NORMAL (L"##5.2.44# (23 September 2011)") LIST_ITEM (L"\\bu Corrected a very old bug in the history mechanism (the button title wouldn't always show up).") NORMAL (L"##5.2.43# (21 September 2011)") LIST_ITEM (L"\\bu Linux: you can now change the font size of the script window.") LIST_ITEM (L"\\bu Corrected a bug that could cause Praat to crash when opening an already open file in the script window.") NORMAL (L"##5.2.42# (18 September 2011)") LIST_ITEM (L"\\bu Corrected a bug introduced in 5.2.36 that prevented formulas from working on FormantGrid objects.") NORMAL (L"##5.2.41# (17 September 2011)") LIST_ITEM (L"\\bu Improved dashed-dotted lines in EPS files.") LIST_ITEM (L"\\bu Corrected a bug introduced in 5.2.36 that caused Praat to crash when running an ExperimentMFC.") NORMAL (L"##5.2.40# (11 September 2011)") LIST_ITEM (L"\\bu Corrected a bug in the 64-bit Windows edition that led to an incorrect location for the preferences files.") NORMAL (L"##5.2.39# (10 September 2011)") LIST_ITEM (L"\\bu 64-bit edition for Windows.") LIST_ITEM (L"\\bu Corrected a bug that caused Praat to crash instead of saying \"undefined\" when reporting the shimmer of a sound with fewer than 3 pulses.") NORMAL (L"##5.2.38# (6 September 2011)") LIST_ITEM (L"\\bu Corrected several bugs that were introduced in 5.2.36 in the Inspect window.") NORMAL (L"##5.2.37# (2 September 2011)") LIST_ITEM (L"\\bu Graphics: added the Chinese phonetic symbols \\id and \\ir. See @@Phonetic symbols: vowels@.") LIST_ITEM (L"\\bu Corrected a bug introduced in 5.2.36 that caused Praat to crash when querying formant quantiles.") NORMAL (L"##5.2.36# (30 August 2011)") LIST_ITEM (L"\\bu Graphics: added superscript diacritics as single symbols: \\^h (\\bs\\^ h), \\^j (\\bs\\^ j), " "and many more; also \\_u (\\bs\\_ u). See @@Phonetic symbols: diacritics@.") LIST_ITEM (L"\\bu Praat fully converted to C++ (this may initially cause some bugs, but will be more reliable in the end).") NORMAL (L"##5.2.35# (5 August 2011)") LIST_ITEM (L"\\bu Corrected the menus of the Sound and TextGrid windows.") NORMAL (L"##5.2.34# (3 August 2011)") LIST_ITEM (L"\\bu @@Insert picture from file...@ now works on Windows (as well as on the Mac).") LIST_ITEM (L"\\bu Corrected a bug that could cause Praat to crash when playing a LongSound.") NORMAL (L"##5.2.33# (29 July 2011)") LIST_ITEM (L"\\bu Improved the reliability of sound playing and several other things.") LIST_ITEM (L"\\bu Improved several error messages.") NORMAL (L"##5.2.32# (22 July 2011)") LIST_ITEM (L"\\bu Corrected several problems with error messages.") LIST_ITEM (L"\\bu Corrected a bug that could cause slow execution of scripts with forms.") NORMAL (L"##5.2.31# (21 July 2011)") LIST_ITEM (L"\\bu Corrected a bug that caused an incorrect window size in the VowelEditor.") LIST_ITEM (L"\\bu Corrected a bug that caused incorrect error messages when opening a FLAC file as a LongSound.") LIST_ITEM (L"\\bu Sound window: corrected a bug that could cause Praat to crash when zooming in on the left or right edge.") NORMAL (L"##5.2.30# (18 July 2011)") LIST_ITEM (L"\\bu Corrected a bug introduced in 5.2.29 whereby the list of object actions could stay empty after an error message in a script.") LIST_ITEM (L"\\bu Corrected a bug in Klatt synthesis whereby the generation of a sound could be refused.") NORMAL (L"##5.2.29# (12 July 2011)") LIST_ITEM (L"\\bu More accurate error checking, due to Praat's conversion to C++ (last C-only version was 5.2.17).") NORMAL (L"##5.2.28# (28 June 2011)") LIST_ITEM (L"\\bu Corrected some Polygon bugs.") NORMAL (L"##5.2.27# (19 June 2011)") LIST_ITEM (L"\\bu @Polygon: ##Draw (closed)...#.") LIST_ITEM (L"\\bu @@PointProcess: To Sound (phonation)...@: " "corrected a bug that could cause Praat to crash if pulses lay outside the time domain.") NORMAL (L"##5.2.26# (24 May 2011)") LIST_ITEM (L"\\bu Corrected a bug that could cause Praat to crash on some platforms when reading a Praat binary file.") LIST_ITEM (L"\\bu @ExperimentMFC: corrected a bug that caused Praat to crash if an experiment contained zero trials.") LIST_ITEM (L"\\bu Corrected a bug that caused Praat to crash when merging multiple IntervalTiers.") NORMAL (L"##5.2.25# (11 May 2011)") LIST_ITEM (L"\\bu OT learning: corrected a crashing bug from ##Get candidate...#.") NORMAL (L"##5.2.24# (10 May 2011)") LIST_ITEM (L"\\bu Ability to open WAV files that contain incorrect information about the number of samples.") LIST_ITEM (L"\\bu Removed an old bug that could cause Praat to fail to read a chronological TextGrid text file.") NORMAL (L"##5.2.23# (1 May 2011)") LIST_ITEM (L"\\bu Removed a bug introduced recently that could cause Praat to crash when working with derivatives of TableOfReal (such as Distributions).") NORMAL (L"##5.2.22# (14 April 2011)") LIST_ITEM (L"\\bu @ExperimentMFC: reaction times for key presses.") LIST_ITEM (L"\\bu Linux: more reliable start-up on German systems.") NORMAL (L"##5.2.21# (29 March 2011)") LIST_ITEM (L"\\bu Scripting: removed a crashing bug introduced for colour names in 5.2.20.") NORMAL (L"##5.2.20# (25 March 2011)") LIST_ITEM (L"\\bu Scripting: removed a large memory leak for indexed variables.") LIST_ITEM (L"\\bu Scripting: removed a small memory leak for colour names.") LIST_ITEM (L"\\bu Support for very long file paths on the Mac.") NORMAL (L"##5.2.19# (16 March 2011)") LIST_ITEM (L"\\bu @ExperimentMFC: corrected a bug introduced in 5.2.18 that could cause Praat to crash when extracting results from an incomplete experiment.") NORMAL (L"##5.2.18# (9 March 2011)") LIST_ITEM (L"\\bu @ExperimentMFC: incomplete experiments can nevertheless output their incomplete results.") NORMAL (L"##5.2.17# (2 March 2011)") LIST_ITEM (L"\\bu Better names for Table opening and saving commands.") LIST_ITEM (L"\\bu @ExperimentMFC: reaction times for mouse clicks.") LIST_ITEM (L"\\bu Linux/GTK: corrected triple clicks in ExperimentMFC.") NORMAL (L"##5.2.16# (20 February 2011)") LIST_ITEM (L"\\bu Better support for WAV files with special \"chunks\" in them.") LIST_ITEM (L"\\bu Manual: documentation of explicit formulas for @@Voice 2. Jitter|jitter measurements@.") NORMAL (L"##5.2.15# (11 February 2011)") LIST_ITEM (L"\\bu @@Sounds: Concatenate with overlap...@.") NORMAL (L"##5.2.14# (8 February 2011)") LIST_ITEM (L"\\bu Repaired crashing bug in Manipulation window introduced in 5.2.13.") NORMAL (L"##5.2.13# (7 February 2011)") LIST_ITEM (L"\\bu Renamed #Write commands to #Save commands.") LIST_ITEM (L"\\bu Scripting: allow pause forms without #Stop button (see @@Scripting 6.6. Controlling the user@).") LIST_ITEM (L"\\bu GTK: correct behaviour of default buttons.") NORMAL (L"##5.2.12# (28 January 2011)") LIST_ITEM (L"\\bu Renamed #Edit buttons to ##View & Edit#.") LIST_ITEM (L"\\bu Better visibility of dragged things on Linux.") NORMAL (L"##5.2.11# (18 January 2011)") LIST_ITEM (L"\\bu Better visibility of dragged things (sound selection, tier points, TextGrid boundaries) on Windows and Linux.") NORMAL (L"##5.2.10# (11 January 2011)") LIST_ITEM (L"\\bu Renamed #Read and #Write menus to #Open and #Save.") LIST_ITEM (L"\\bu Sound: use of ##Formula (part)...# can speed up formulas appreciably.") NORMAL (L"##5.2.09# (9 January 2011)") LIST_ITEM (L"\\bu Much improved scripting tutorial.") LIST_ITEM (L"\\bu Listening experiments can now show pictures instead of just texts (on the Mac).") LIST_ITEM (L"\\bu EPS files can now be many miles wide instead of just 55 inches.") NORMAL (L"##5.2.08# (1 January 2011)") LIST_ITEM (L"\\bu Improved manual.") LIST_ITEM (L"\\bu Improved memory allocation on 32-bit platforms: " "less probability of crashes when you approach the 2 GB memory limit gradually, and a new \"low on memory; save your work now\" warning.") LIST_ITEM (L"\\bu Removed IntervalTier and TextTier datatypes from Praat (old scripts that use them will continue to work).") NORMAL (L"##5.2.07# (24 December 2010)") LIST_ITEM (L"\\bu Support for reading and writing multi-channel sound files (i.e. above two-channel stereo).") NORMAL (L"##5.2.06# (18 December 2010)") LIST_ITEM (L"\\bu Picture window: a new (the fourth) line type, namely dashed-dotted.") LIST_ITEM (L"\\bu Support for analysing and drawing multi-channel sounds (i.e. above two-channel stereo).") LIST_ITEM (L"\\bu Can read some EEG files (BioSemi 24-bit BDF) as a Sound and a TextGrid object.") LIST_ITEM (L"\\bu Linux: compatibility with computers without English language support.") LIST_ITEM (L"\\bu Macintosh: support for high-plane (i.e. very uncommon) Unicode characters in file names (as already existed on Unix and Windows).") NORMAL (L"##5.2.05# (4 December 2010)") LIST_ITEM (L"\\bu Regular expressions: better Unicode support.") LIST_ITEM (L"\\bu Scripting window: command ##Convert to C string#.") NORMAL (L"##5.2.04# (27 November 2010)") LIST_ITEM (L"\\bu Scripting: allow directory (folder) selector windows; see @@Scripting 6.6. Controlling the user@.") NORMAL (L"##5.2.03# (19 November 2010)") LIST_ITEM (L"\\bu Scripting: support for string arrays.") NORMAL (L"##5.2.02# (17 November 2010)") LIST_ITEM (L"\\bu TextGrid window: corrected a bug that caused Praat to crash (instead of doing nothing) when you tried to add boundaries " "if the selection ran from the penultimate interval to the end of the TextGrid.") LIST_ITEM (L"\\bu Scripting: support for arrays with multiple indexes.") LIST_ITEM (L"\\bu Linux: made spectrogram drawing compatible with Ubuntu 10.10.") LIST_ITEM (L"\\bu Linux: made sound more easily available on Ubuntu 10.10.") NORMAL (L"##5.2.01# (4 November 2010)") LIST_ITEM (L"\\bu Scripting: support for numeric @@Scripting 5.6. Arrays|arrays@.") NORMAL (L"##5.2# (29 October 2010)") NORMAL (L"##5.1.45# (26 October 2010)") LIST_ITEM (L"\\bu Linux/GTK: allow Praat to run without an X display.") LIST_ITEM (L"\\bu Sounds are played synchronously in scripts run from ManPages with \\bsSC.") NORMAL (L"##5.1.44# (4 October 2010)") LIST_ITEM (L"\\bu Linux/GTK: visibility of ExperimentMFC window.") LIST_ITEM (L"\\bu Linux/GTK: keyboard shortcuts.") NORMAL (L"##5.1.43# (4 August 2010)") LIST_ITEM (L"\\bu Scripting: support for stand-alone programs; see @@Scripting 9. Turning a script into a stand-alone program@.") LIST_ITEM (L"\\bu Table: allow drawing of ellipses even if irrelevant columns contain undefined data.") LIST_ITEM (L"\\bu Linux/GTK: correct resizing of Table window.") LIST_ITEM (L"\\bu Linux/GTK: prevented multiple storing of Picture window selection in scripting history.") NORMAL (L"##5.1.42# (26 July 2010)") LIST_ITEM (L"\\bu Scripting: allow file selector windows; see @@Scripting 6.6. Controlling the user@.") LIST_ITEM (L"\\bu Linux: multiple file selection.") NORMAL (L"##5.1.41# (15 July 2010)") LIST_ITEM (L"\\bu OTGrammar: ##Compare candidates...#") LIST_ITEM (L"\\bu GTK: support for the Doulos SIL and Charis SIL fonts.") LIST_ITEM (L"\\bu GTK: working vowel editor.") LIST_ITEM (L"\\bu Vowel editor: repaired memory leak.") //LIST_ITEM (L"\\bu GTK: Picture window: front when drawing.") //LIST_ITEM (L"\\bu GTK: correct scrolling in manuals.") NORMAL (L"##5.1.40# (13 July 2010)") LIST_ITEM (L"\\bu GTK: working Demo window (drawing, clicks, keys).") LIST_ITEM (L"\\bu GTK: pause forms.") LIST_ITEM (L"\\bu GTK: manual pages: receive a white background, for compatibility with dark-background themes.") LIST_ITEM (L"\\bu GTK: in settings windows, better alignment of labels to radio groups.") LIST_ITEM (L"\\bu GTK: rotated text.") NORMAL (L"##5.1.39# (10 July 2010)") LIST_ITEM (L"\\bu GTK beta version.") LIST_ITEM (L"\\bu Linux: made ##Sound: Record fixed time...# work correctly (the sampling frequency was wrong).") LIST_ITEM (L"\\bu GTK: list of objects: multiple selection, working Rename button.") LIST_ITEM (L"\\bu GTK: running a script no longer deselects all objects at the start.") LIST_ITEM (L"\\bu GTK: working Buttons editor.") LIST_ITEM (L"\\bu GTK: correctly laid out settings windows.") NORMAL (L"##5.1.38# (2 July 2010)") LIST_ITEM (L"\\bu Linux: made ##Sound: Record fixed time...# work correctly (the sampling frequency was wrong).") LIST_ITEM (L"\\bu Mac: repaired a bug introduced in 5.1.35 that could cause Praat to crash if neither Doulos SIL nor Charis SIL were installed.") LIST_ITEM (L"\\bu Mac: correct live scrolling in Picture window and DataEditor.") NORMAL (L"##5.1.37# (23 June 2010)") LIST_ITEM (L"\\bu PitchTier window and similar windows: can drag multiple points simultaneously.") LIST_ITEM (L"\\bu Table: %t-tests report the number of degrees of freedom.") LIST_ITEM (L"\\bu GTK: correct progress bar again.") LIST_ITEM (L"\\bu GTK: correct behaviour of Synth menu in manipulation window.") NORMAL (L"##5.1.36# (18 June 2010)") LIST_ITEM (L"\\bu Mac: live scrolling.") LIST_ITEM (L"\\bu Demo window: the Demo window can now run from the command line.") LIST_ITEM (L"\\bu Motif: corrected a bug introduced in 5.1.33 whereby things in the Picture window could be placed incorrectly.") LIST_ITEM (L"\\bu GTK: script window accepts Unicode again.") NORMAL (L"##5.1.35# (10 June 2010)") LIST_ITEM (L"\\bu TextGrid window: removed a very old bug that could lead to reversed intervals and to crashes when you inserted a boundary after using Shift-arrow and Command-arrow.") LIST_ITEM (L"\\bu Graphics: Praat now uses Doulos SIL instead of Charis SIL if your font setting is \"Times\" and the font is nonbold and nonitalic, " "because Doulos SIL matches Times New Roman better.") LIST_ITEM (L"\\bu kNN: made Ola S\\o\"der's k-nearest-neighbours classification compatible with Windows.") NORMAL (L"##5.1.34# (31 May 2010)") LIST_ITEM (L"\\bu Sound window: corrected a bug that caused Praat to crash if the analysis window was shorter than 2 samples.") LIST_ITEM (L"\\bu GTK: scrolling in the Info window and script window.") LIST_ITEM (L"\\bu GTK: script editor: implemented searching, replacing, and change dialogs.") NORMAL (L"##5.1.33# (24 May 2010)") LIST_ITEM (L"\\bu GTK alpha version.") LIST_ITEM (L"\\bu Abolished resolution independence: the Sound window now looks the same on all platforms, " "and the Demo window has the same relative font size on your screen and on the video projector.") LIST_ITEM (L"\\bu GTK: support for asynchronous audio output.") LIST_ITEM (L"\\bu GTK: sound plays once rather than three times in Sound and other windows.") LIST_ITEM (L"\\bu GTK: can click more than once in the manual.") LIST_ITEM (L"\\bu GTK: correct pink selections in Sound and other windows.") LIST_ITEM (L"\\bu GTK: correct dragging in TextGrid, Manipulation, and tier windows.") LIST_ITEM (L"\\bu GTK: a working TextGrid window.") LIST_ITEM (L"\\bu GTK: no automatic triple click in the manual (and many other windows).") LIST_ITEM (L"\\bu GTK: moving cursor while sound is playing in Sound and other windows.") LIST_ITEM (L"\\bu GTK: correct colours of the rectangles in Sound and other windows.") LIST_ITEM (L"\\bu GTK: a working Group button.") LIST_ITEM (L"\\bu GTK: correct font menus, font size menus, colour menus, line type menus.") LIST_ITEM (L"\\bu GTK: scrolling in the manual (and many other windows).") LIST_ITEM (L"\\bu GTK: erase old texts in manual windows.") LIST_ITEM (L"\\bu GTK: made Picture window come back when drawing.") LIST_ITEM (L"\\bu GTK: Info window is fronted automatically.") LIST_ITEM (L"\\bu GTK: support sendpraat.") NORMAL (L"##5.1.32# (30 April 2010)") LIST_ITEM (L"\\bu Scripting: command ##Expand include files#.") LIST_ITEM (L"\\bu Scripting: accept lines that start with non-breaking spaces (as may occur in scripts copied from the web manual).") LIST_ITEM (L"\\bu Sound files: accept MP3 files with extension written in capitals.") LIST_ITEM (L"\\bu Linux audio recording: corrected input choice (microphone, line).") NORMAL (L"##5.1.31# (4 April 2010)") LIST_ITEM (L"\\bu @@Sounds: Convolve...@, @@Sounds: Cross-correlate...@, @@Sound: Autocorrelate...@, with full documentation.") LIST_ITEM (L"\\bu More query commands for IntensityTier.") NORMAL (L"##5.1.30# (25 March 2010)") LIST_ITEM (L"\\bu Scripting: $$createDirectory ()$ can now work with absolute paths.") LIST_ITEM (L"\\bu PointProcess: made it impossible to add a point where there is already a point.") NORMAL (L"##5.1.29# (11 March 2010)") LIST_ITEM (L"\\bu Full support for unicode values above 0xFFFF on Macintosh.") NORMAL (L"##5.1.28# (10 March 2010)") LIST_ITEM (L"\\bu TextGrid window: removed a recently introduced bug that could cause Praat to crash when inserting a boundary.") NORMAL (L"##5.1.27# (7 March 2010)") LIST_ITEM (L"\\bu Table: Wilcoxon rank sum test.") LIST_ITEM (L"\\bu Logistic regression: corrected a bug by which a boundary would sometimes not be drawn.") NORMAL (L"##5.1.26# (25 February 2010)") LIST_ITEM (L"\\bu Experimental GTK version with the help of Franz Brau\\sse.") LIST_ITEM (L"\\bu Corrected a bug that could cause Praat to crash if sound playing failed twice.") NORMAL (L"##5.1.25# (20 January 2010)") LIST_ITEM (L"\\bu Script window: the new command ##Reopen from disk# allows you to edit the script with an external editor.") LIST_ITEM (L"\\bu Script window: removed a bug that could cause Praat to crash of you did ##Find again# before having done any #Find.") NORMAL (L"##5.1.24# (15 January 2010)") LIST_ITEM (L"\\bu Formulas run 10 to 20 percent faster.") LIST_ITEM (L"\\bu Macintosh: support for forward delete key and Command-`.") NORMAL (L"##5.1.23# (1 January 2010)") LIST_ITEM (L"\\bu Allowed multiple files to be selected with e.g. @@Read from file...@.") LIST_ITEM (L"\\bu Demo window: guarded against handling the Demo window from two scripts at a time.") NORMAL (L"##5.1.22# (15 December 2009)") LIST_ITEM (L"\\bu Picture window: millions of @@colour|colours@ instead of just twelve.") LIST_ITEM (L"\\bu Sound window: ##Move frequency cursor to...#") NORMAL (L"##5.1.21# (30 November 2009)") LIST_ITEM (L"\\bu @@Sound: Draw where...@") LIST_ITEM (L"\\bu ##Matrix: Draw contours...# and ##LogisticRegression: Draw boundary...# support reversed axes.") LIST_ITEM (L"\\bu Sound window: ##Move frequency cursor to...#.") NORMAL (L"##5.1.20# (26 October 2009)") LIST_ITEM (L"\\bu Editor windows: repaired the Synchronized Zoom And Scroll preference.") NORMAL (L"##5.1.19# (21 October 2009)") LIST_ITEM (L"\\bu Table: Randomize rows") LIST_ITEM (L"\\bu Tables: Append (vertically)") LIST_ITEM (L"\\bu Scripting: corrected a bug that could cause Praat to crash if the name of a field in a form contained a colon.") LIST_ITEM (L"\\bu Windows: corrected arc drawing.") NORMAL (L"##5.1.18# (9 October 2009)") LIST_ITEM (L"\\bu The @@Demo window@ is less often automatically moved to the front " "(in order to allow it to pop up other editor windows).") LIST_ITEM (L"\\bu @@DTW & TextGrid: To TextGrid (warp times)@: corrected a bug that could " "lead to an incorrect end time of the last interval in new IntervalTiers.") NORMAL (L"##5.1.17# (22 September 2009)") LIST_ITEM (L"\\bu Made more stereo movies readable.") LIST_ITEM (L"\\bu Editor windows now have a ##Zoom Back# button.") NORMAL (L"##5.1.16# (17 September 2009)") LIST_ITEM (L"\\bu Macintosh: corrected a bug that caused incorrect phonetic symbols if Charis SIL was available but SIL Doulos IPA93 was not.") NORMAL (L"##5.1.15# (30 August 2009)") LIST_ITEM (L"\\bu Corrected a bug in @@Sound: Change gender...@ introduced in 5.1.14.") NORMAL (L"##5.1.14# (27 August 2009)") LIST_ITEM (L"\\bu Windows: corrected a bug introduced in 5.1.13 that caused Praat to crash during tab navigation.") LIST_ITEM (L"\\bu Made @@Sound: Change gender...@ compatible with elephant calls (i.e. very low F0).") NORMAL (L"##5.1.13# (21 August 2009)") LIST_ITEM (L"\\bu Script window: #Find and #Replace.") LIST_ITEM (L"\\bu Picture window (and therefore Demo window!): @@Insert picture from file...@ (MacOS 10.4 and up).") LIST_ITEM (L"\\bu @@Demo window@: full screen (on the Mac).") LIST_ITEM (L"\\bu Scripting: faster object selection (scripts no longer slow down when there are many objects in the list).") LIST_ITEM (L"\\bu Scripting: $$variableExists$.") LIST_ITEM (L"\\bu Macintosh: PDF clipboard (MacOS 10.4 and up).") NORMAL (L"##5.1.12# (4 August 2009)") LIST_ITEM (L"\\bu Macintosh: the Picture window can save to PDF file (you need MacOS 10.4 or up).") LIST_ITEM (L"\\bu Macintosh: corrected a bug that caused Praat to crash at start-up on MacOS 10.3.") NORMAL (L"##5.1.11# (19 July 2009)") NORMAL (L"##5.1.10# (8 July 2009)") LIST_ITEM (L"\\bu Corrected a bug that could cause Praat to crash if the Demo window was closed after an \"execute\".") LIST_ITEM (L"\\bu OTGrammar & PairDistribution: added ##Get minimum number correct...#.") NORMAL (L"##5.1.09# (28 June 2009)") LIST_ITEM (L"\\bu Made East-European Roman characters available in EPS files.") NORMAL (L"##5.1.08# (21 June 2009)") LIST_ITEM (L"\\bu Removed a bug introduced in 5.1.07 that could cause strange pictures in manual.") LIST_ITEM (L"\\bu Macintosh: execute @sendpraat messages immediately instead of waiting for the user to click the jumping Praat icon.") NORMAL (L"##5.1.07# (12 May 2009)") LIST_ITEM (L"\\bu Demo window: navigation by arrow keys also on Windows.") LIST_ITEM (L"\\bu Demo window: no longer crashes on Linux.") NORMAL (L"##5.1.06# (11 May 2009)") LIST_ITEM (L"\\bu Demo window.") NORMAL (L"##5.1.05# (7 May 2009)") LIST_ITEM (L"\\bu KlattGrid update.") NORMAL (L"##5.1.04# (4 April 2009)") LIST_ITEM (L"\\bu Corrected a bug that could cause a missing text character in EPS files produced by a version of Praat running in batch.") LIST_ITEM (L"\\bu Corrected a bug that could cause high values in a Matrix computed from a Pitch.") NORMAL (L"##5.1.03# (21 March 2009)") //LIST_ITEM (L"\\bu OT learning: the \"Random up, highest down\" update rule.") LIST_ITEM (L"\\bu ExperimentMFC: corrected a bug introduced in 5.0.36 that caused Praat to crash if a sound file did not exist.") LIST_ITEM (L"\\bu Articulatory synthesis: corrected a bug that could cause Praat to crash when copying Artwords.") LIST_ITEM (L"\\bu Macintosh: corrected a bug that could cause poor text alignment in picture.") NORMAL (L"##5.1.02# (9 March 2009)") LIST_ITEM (L"\\bu Allow pause forms without fields.") LIST_ITEM (L"\\bu The value \"undefined\" is disallowed from all fields in command windows " "except ##Table: Set numeric value...# and ##TableOfReal: Set value...#.") LIST_ITEM (L"\\bu TextGrid: ##List...# and ##Down to Table...#.") LIST_ITEM (L"\\bu OT learning: Giorgio Magri's \"Weighted all up, highest down\" update rule.") NORMAL (L"##5.1.01# (26 February 2009)") LIST_ITEM (L"\\bu Corrected several bugs in Klatt synthesis.") NORMAL (L"##5.1# (31 January 2009)") LIST_ITEM (L"\\bu Editors for Klatt synthesis.") LIST_ITEM (L"\\bu Corrected many bugs.") NORMAL (L"##5.0.47# (21 January 2009)") LIST_ITEM (L"\\bu Extensive pause windows: @@Scripting 6.6. Controlling the user@.") NORMAL (L"##5.0.46# (7 January 2009)") LIST_ITEM (L"\\bu More Klatt synthesizer.") LIST_ITEM (L"\\bu First pause form support.") LIST_ITEM (L"\\bu Renewed CategoriesEditor.") LIST_ITEM (L"\\bu Repaired several memory leaks.") NORMAL (L"##5.0.45# (29 December 2008)") LIST_ITEM (L"\\bu Bug fixes in Klatt synthesizer.") NORMAL (L"##5.0.44# (24 December 2008)") LIST_ITEM (L"\\bu David's Klatt synthesizer: @KlattGrid.") NORMAL (L"##5.0.43# (9 December 2008)") LIST_ITEM (L"\\bu Scripting tutorial: local variables in procedures.") NORMAL (L"##5.0.42# (26 November 2008)") LIST_ITEM (L"\\bu Removed a bug that could cause Praat to crash when drawing pictures in the manual window.") LIST_ITEM (L"\\bu Removed a bug that could cause Praat to crash when drawing multi-line text.") NORMAL (L"##5.0.41# (23 November 2008)") LIST_ITEM (L"\\bu ExperimentMFC: allow multiple lines in all texts.") LIST_ITEM (L"\\bu Regular expressions: removed a bug that could cause Praat to hang when using \".*\".") LIST_ITEM (L"\\bu Table: Draw ellipses: removed a bug that could cause Praat to crash if some cells were undefined.") NORMAL (L"##5.0.40# (10 November 2008)") LIST_ITEM (L"\\bu Improved reading and writing of text files (faster, bigger).") NORMAL (L"##5.0.39# (1 November 2008)") LIST_ITEM (L"\\bu praatcon -a (for sending ANSI encoding when redirected)") NORMAL (L"##5.0.38# (28 October 2008)") LIST_ITEM (L"\\bu @FormantGrid: To Formant...") NORMAL (L"##5.0.36# (20 October 2008)") LIST_ITEM (L"\\bu @ExperimentMFC: accepts nonstandard sound files.") NORMAL (L"##5.0.35# (5 October 2008)") LIST_ITEM (L"\\bu ##Scale times by...# and ##Scale times to...# (Modify menu).") NORMAL (L"##5.0.34# (22 September 2008)") LIST_ITEM (L"\\bu ##Shift times by...# and ##Shift times to...# (Modify menu).") LIST_ITEM (L"\\bu Sound: @@Combine to stereo@ works even if the two mono sounds have different durations or time domains.") NORMAL (L"##5.0.33# (9 September 2008)") LIST_ITEM (L"\\bu Windows: prevented warning messages about \"Widget type\".") NORMAL (L"##5.0.32# (12 August 2008)") LIST_ITEM (L"\\bu Contributed by Ola S\\o\"der: @@kNN classifiers@ and @@k-means clustering@.") LIST_ITEM (L"\\bu Made UTF-16-encoded chronological TextGrid files readable.") NORMAL (L"##5.0.31# (6 August 2008)") LIST_ITEM (L"\\bu Macintosh: corrected a bug introduced in 5.0.30 that caused Praat to crash when you pressed the Tab key " "in a window without text fields.") NORMAL (L"##5.0.30# (22 July 2008)") LIST_ITEM (L"\\bu Macintosh and Windows: tab navigation.") NORMAL (L"##5.0.29# (8 July 2008)") LIST_ITEM (L"\\bu OTMulti: can record history.") LIST_ITEM (L"\\bu Picture window: corrected text in Praat picture files.") NORMAL (L"##5.0.28# (3 July 2008)") LIST_ITEM (L"\\bu Windows: audio output uses DirectX (next to Multi-Media Extensions).") NORMAL (L"##5.0.27# (28 June 2008)") LIST_ITEM (L"\\bu @@Phonetic symbols@: breve (a\\N^).") LIST_ITEM (L"\\bu Annotation: improved some SpellingChecker commands.") LIST_ITEM (L"\\bu Table: can now set string values that contain spaces.") NORMAL (L"##5.0.26# (15 June 2008)") LIST_ITEM (L"\\bu Windows: sound recording no longer makes your laptop's fan spin.") LIST_ITEM (L"\\bu Windows: no longer any 64 MB limit on recorded sounds.") LIST_ITEM (L"\\bu Linux: audio input and output uses Alsa (next to OSS).") NORMAL (L"##5.0.25# (31 May 2008)") LIST_ITEM (L"\\bu OT learning: added decision strategy ExponentialMaximumEntropy.") NORMAL (L"##5.0.24# (14 May 2008)") LIST_ITEM (L"\\bu Linux: corrected a bug at start-up.") NORMAL (L"##5.0.23# (9 May 2008)") LIST_ITEM (L"\\bu Corrected a bug that could cause Praat to crash when you edited an Artword that you had read from a file.") NORMAL (L"##5.0.22# (26 April 2008)") LIST_ITEM (L"\\bu Editing formant contours: @FormantGrid.") NORMAL (L"##5.0.21# (22 April 2008)") LIST_ITEM (L"\\bu Annotating with Cyrillic, Arabic, Chinese, Korean characters, and many more (on Macintosh and Windows).") NORMAL (L"##5.0.20# (8 April 2008)") LIST_ITEM (L"\\bu @ExperimentMFC: prevented the OK key from working if no response (and goodness choice) had been made.") LIST_ITEM (L"\\bu OT learning: sped up learning from partial outputs by a factor of five or more.") NORMAL (L"##5.0.19# (4 April 2008)") LIST_ITEM (L"\\bu TextGrid window: corrected a bug introduced in 5.0.17 that could cause Praat to crash when handling point tiers.") NORMAL (L"##5.0.18# (31 March 2008)") LIST_ITEM (L"\\bu Manipulation window: corrected a bug introduced in 5.0.17 that caused Praat to crash when adding the first duration point.") LIST_ITEM (L"\\bu Sound: added ##Extract all channels#.") LIST_ITEM (L"\\bu OT learning: added @@OTGrammar & PairDistribution: Find positive weights...@.") LIST_ITEM (L"\\bu ExperimentMFC: corrected a bug that caused Praat to crash when the second of multiple experiments " "referred to non-existing sound files.") NORMAL (L"##5.0.17# (29 March 2008)") LIST_ITEM (L"\\bu Sped up vowel editor by a large factor.") LIST_ITEM (L"\\bu OT learning: corrected Exponential HG update rule from OT-GLA to HG-GLA.") LIST_ITEM (L"\\bu OT learning: shift Exponential HG average constraint weight to zero after every learning step.") NORMAL (L"##5.0.16# (25 March 2008)") LIST_ITEM (L"\\bu Macintosh: returned to old compiler because of incompatibility with MacOS X 10.4.") NORMAL (L"##5.0.15# (21 March 2008)") LIST_ITEM (L"\\bu Windows: more reliable dropping of files on the Praat icon when Praat is already running.") NORMAL (L"##5.0.14# (20 March 2008)") LIST_ITEM (L"\\bu David's vowel editor (New \\-> Sound).") LIST_ITEM (L"\\bu Formulas: corrected scaling of sinc function.") NORMAL (L"##5.0.13# (18 March 2008)") LIST_ITEM (L"\\bu Corrected drawing of histograms.") LIST_ITEM (L"\\bu TextGrid window: selected part of the TextGrid can be extracted and saved.") LIST_ITEM (L"\\bu TextGrid: more complete conversion between backslash trigraphs and Unicode.") LIST_ITEM (L"\\bu Windows: more reliable dropping of files on the Praat icon when Praat is not running yet.") LIST_ITEM (L"\\bu Formulas: sinc function.") NORMAL (L"##5.0.12# (12 March 2008)") LIST_ITEM (L"\\bu Bigger ligature symbol (k\\lip).") NORMAL (L"##5.0.11# (7 March 2008)") LIST_ITEM (L"\\bu Corrected saving of new binary Manipulation files (you can send any unreadable Manipulation files to Paul Boersma for correction).") NORMAL (L"##5.0.10# (27 February 2008)") LIST_ITEM (L"\\bu Added the characters \\d- and \\D-.") LIST_ITEM (L"\\bu Windows: made ##praatcon.exe# compatible with Unicode command lines.") NORMAL (L"##5.0.09# (16 February 2008)") LIST_ITEM (L"\\bu Windows: corrected a bug by which Praat would not open files that were dragged on the Praat icon " "if the names of these files or their directory paths contained non-ASCII characters.") LIST_ITEM (L"\\bu Linux: ignore the Mod2 key, because of its unpredictable assignment.") NORMAL (L"##5.0.08# (10 February 2008)") LIST_ITEM (L"\\bu Corrected the minus sign (\\bs-m = \"\\-m\").") NORMAL (L"##5.0.07# (8 February 2008)") LIST_ITEM (L"\\bu Object IDs are visible in editor windows.") NORMAL (L"##5.0.06# (31 January 2008)") LIST_ITEM (L"\\bu Corrected a bug that caused ##Find again# in the TextGrid window not to work.") LIST_ITEM (L"\\bu Macintosh: made Praat work correctly on 10.3 computers with missing fonts.") NORMAL (L"##5.0.05# (19 January 2008)") LIST_ITEM (L"\\bu All Matrix, Sound, Spectrogram, Pitch, Ltas, and Spectrum objects (and more) are now in 52-bit relative precision (instead of the earlier 23 bits).") LIST_ITEM (L"\\bu Corrected a bug that could lead to \"Unknown opcode (0)\" messages when drawing large sounds (more than 16 million samples) in the Picture window.") LIST_ITEM (L"\\bu Macintosh: solved around a bug in the C library that could cause incorrect representation of non-ASCII characters (in the OTGrammar window).") NORMAL (L"##5.0.04# (12 January 2008)") LIST_ITEM (L"\\bu Windows: corrected a bug introduced in 5.0.03 that caused Praat to crash if you pressed a key in the Sound window.") LIST_ITEM (L"\\bu Macintosh: some cosmetic corrections.") NORMAL (L"##5.0.03# (9 January 2008)") LIST_ITEM (L"\\bu Scripting: guard against opening the same file more than once.") LIST_ITEM (L"\\bu Table: possibility of regarding a column as a distribution (#Generate menu).") LIST_ITEM (L"\\bu Macintosh: corrected line colours.") NORMAL (L"##5.0.02# (27 December 2007)") LIST_ITEM (L"\\bu TextGrid window: corrected the drawing of numbers to the right of the tiers.") LIST_ITEM (L"\\bu Corrected a bug that caused Praat to crash when doing ##SpectrumTier: List#.") NORMAL (L"##5.0.01# (18 December 2007)") LIST_ITEM (L"\\bu Corrected a bug that could cause Praat to crash when redrawing the sound or TextGrid window.") NORMAL (L"##5.0# (10 December 2007)") LIST_ITEM (L"\\bu Corrected many bugs.") LIST_ITEM (L"\\bu Display font sizes in points rather than pixels.") NORMAL (L"##4.6.41# (9 December 2007)") LIST_ITEM (L"\\bu Windows: corrected a bug that could cause listening experiments not to run when the directory path included non-ASCII characters; " "the same bug could (under comparable circumstances) cause scripted menu commands not to work.") LIST_ITEM (L"\\bu Corrected a bug that could cause null bytes in data files when the text output encoding preference was ##try ISO Latin-1, then UTF-16#.") NORMAL (L"##4.6.40# (3 December 2007)") LIST_ITEM (L"\\bu Corrected some minor bugs.") NORMAL (L"##4.6.39# (1 December 2007)") LIST_ITEM (L"\\bu Manual: corrected a bug that could cause Praat to crash when viewing certain manual pages with pictures.") LIST_ITEM (L"\\bu Scripting: corrected a bug that could cause Praat to crash when a long string was used as an argument to a procedure.") NORMAL (L"##4.6.38# (19 November 2007)") LIST_ITEM (L"\\bu More extensive @@logistic regression@.") NORMAL (L"##4.6.37# (15 November 2007)") LIST_ITEM (L"\\bu Object list shows numbers.") LIST_ITEM (L"\\bu Macintosh: corrected saving of non-ASCII text settings.") NORMAL (L"##4.6.36# (2 November 2007)") LIST_ITEM (L"\\bu Sound and TextGrid windows: direct drawing of intensity, formants, pulses, and TextGrid.") LIST_ITEM (L"\\bu Regular expressions: corrected handling of newlines on Windows.") LIST_ITEM (L"\\bu Scripting: improved positioning of settings windows for script commands in editors on Windows.") NORMAL (L"##4.6.35# (22 October 2007)") LIST_ITEM (L"\\bu Windows and Linux: better positioning of form windows of editor scripts.") LIST_ITEM (L"\\bu Macintosh: OTMulti learning window more compatible with non-ASCII characters.") NORMAL (L"##4.6.34# (18 October 2007)") LIST_ITEM (L"\\bu Corrected a bug introduced in September that could cause Praat to crash when starting up " "if the user had explicitly made action commands visible or invisible in an earlier session.") NORMAL (L"##4.6.33# (16 October 2007)") LIST_ITEM (L"\\bu Corrected a bug introduced in September that caused Praat to crash when a PointProcess window was opened without a Sound.") LIST_ITEM (L"\\bu Macintosh: objects with non-ASCII names show up correctly in the list.") NORMAL (L"##4.6.32# (14 October 2007)") LIST_ITEM (L"\\bu Unicode support for names of objects.") LIST_ITEM (L"\\bu Linux: first Unicode support (in window titles).") LIST_ITEM (L"\\bu Windows scripting: corrected a bug that caused weird characters in Paste History.") NORMAL (L"##4.6.31# (8 October 2007)") LIST_ITEM (L"\\bu TextGrid window: made Save command available again for TextGrid windows without a sound.") LIST_ITEM (L"\\bu Corrected a bug that caused binary Collection files with objects with names with non-ASCII characters to be unreadable.") NORMAL (L"##4.6.30# (3 October 2007)") LIST_ITEM (L"\\bu OTMulti: added an evaluate command in the Objects window, so that paced learning becomes scriptable.") LIST_ITEM (L"\\bu Macintosh: worked around a feature of a system library that could cause Praat to crash when reading a Collection text file " "that contained objects with non-ASCII names.") NORMAL (L"##4.6.29# (1 October 2007)") LIST_ITEM (L"\\bu OT learning: leak and constraint in OTMulti.") LIST_ITEM (L"\\bu Support for saving Table, TableOfReal, Strings, OTGrammar and OTMulti in Unicode.") NORMAL (L"##4.6.28# (1 October 2007)") LIST_ITEM (L"\\bu OT learning: positive constraint satisfactions in OTMulti tableaus.") LIST_ITEM (L"\\bu Corrected a bug that could cause Praat to crash when reading a non-UTF-8 text file " "when the \"Text reading preference\" had been set to UTF-8.") NORMAL (L"##4.6.27# (29 September 2007)") LIST_ITEM (L"\\bu Corrected redrawing of text with non-ASCII characters.") NORMAL (L"##4.6.26# (29 September 2007)") LIST_ITEM (L"\\bu Corrected reading of high UTF-8 codes.") NORMAL (L"##4.6.25# (26 September 2007)") LIST_ITEM (L"\\bu @ExperimentMFC: can set font size for response buttons.") NORMAL (L"##4.6.24# (24 September 2007)") LIST_ITEM (L"\\bu Czech, Polish, Croatian, and Hungarian characters such as \\c< \\uo \\t< \\e; \\s' \\l/ \\c\' \\o: (see @@Special symbols@).") LIST_ITEM (L"\\bu Some support for Hebrew characters such as \\?+ \\B+ \\sU (see @@Special symbols@).") NORMAL (L"##4.6.23# (22 September 2007)") LIST_ITEM (L"\\bu Corrected a bug introduced in 4.6.13 that caused crashes in text handling (mainly on Linux).") LIST_ITEM (L"\\bu Info commands in editors.") NORMAL (L"##4.6.22# (17 September 2007)") LIST_ITEM (L"\\bu Phonetic symbols: added the nonsyllabicity diacritic (a\\nv).") LIST_ITEM (L"\\bu Macintosh: worked around a feature of a system library that could cause strange behaviour of forms in scripts with non-ASCII characters.") NORMAL (L"##4.6.21# (5 September 2007)") LIST_ITEM (L"\\bu Sound and TextGrid windows: direct drawing of selected sound to the picture window.") NORMAL (L"##4.6.20# (2 September 2007)") LIST_ITEM (L"\\bu Introduced direct drawing of spectrogram and pitch to the Praat picture window from Sound windows and TextGrid windows.") LIST_ITEM (L"\\bu Corrected a bug introduced in 4.6.13 by which Inspect did not show all data in a TextGrid.") NORMAL (L"##4.6.19# (31 August 2007)") LIST_ITEM (L"\\bu Macintosh: worked around a bug in a system library that caused Praat to crash (since version 4.6.13) " "when removing a boundary from a TextGrid interval in MacOS X 10.3 or earlier.") NORMAL (L"##4.6.18# (28 August 2007)") LIST_ITEM (L"\\bu Sound: Filter (formula): now works in the same way as the other filter commands " "(without adding an empty space at the end), and on stereo sounds.") NORMAL (L"##4.6.17# (25 August 2007)") LIST_ITEM (L"\\bu Windows: improved rotated text, also for copy-paste and printing.") LIST_ITEM (L"\\bu Windows: phonetic characters on the screen now require the Charis SIL or Doulos SIL font.") LIST_ITEM (L"\\bu Picture settings report (mainly for script writers).") LIST_ITEM (L"\\bu Corrected a bug that could cause Praat to crash when closing a manual page that had been read from a file.") NORMAL (L"##4.6.16# (22 August 2007)") LIST_ITEM (L"\\bu Macintosh: corrected a bug introduced in 4.6.13 that could cause Praat to crash when drawing a spectrogram in MacOS X 10.3 or earlier.") NORMAL (L"##4.6.15# (21 August 2007)") LIST_ITEM (L"\\bu Corrected a bug introduced in 4.6.14 that prevented the use of Helvetica in the Picture window.") LIST_ITEM (L"\\bu Corrected a bug in \"Read Table from table file...\", introduced in 4.6.13.") NORMAL (L"##4.6.14# (20 August 2007)") LIST_ITEM (L"\\bu Corrected a bug introduced in 4.6.13 that prevented any other font than Palatino in the Picture window.") LIST_ITEM (L"\\bu Macintosh: corrected height of subscripts and superscripts (broken in 4.6.13).") NORMAL (L"##4.6.13# (16 August 2007)") LIST_ITEM (L"\\bu TextGrid: corrected reading of chronological files.") LIST_ITEM (L"\\bu Macintosh: text looks better (and rotated text is now readable on Intel Macs).") LIST_ITEM (L"\\bu Macintosh: phonetic characters on the screen now require the Charis SIL or Doulos SIL font.") NORMAL (L"##4.6.12# (27 July 2007)") LIST_ITEM (L"\\bu OTGrammar bug fix: leak and constraint plasticity correctly written into OTGrammar text files.") NORMAL (L"##4.6.11# (25 July 2007)") LIST_ITEM (L"\\bu OTGrammar: introduced %%constraint plasticity% for slowing down or halting the speed with which constraints are reranked.") LIST_ITEM (L"\\bu OTGrammar: introduced %%leak% for implementing forgetful learning of correlations.") LIST_ITEM (L"\\bu OTGrammar: positive constraint satisfactions are drawn as `+' in tableaus.") NORMAL (L"##4.6.10# (22 July 2007)") LIST_ITEM (L"\\bu Improved reading of UTF-16 data files.") LIST_ITEM (L"\\bu Improved error messages when reading text files (line numbers are mentioned).") LIST_ITEM (L"\\bu Table: Get group mean (Student t)...") NORMAL (L"##4.6.09# (24 June 2007)") LIST_ITEM (L"\\bu Corrected a bug introduced in 4.6.07 that caused a crash when reading Collections.") LIST_ITEM (L"\\bu Corrected a bug introduced in 4.6.07 that caused incorrect Open buttons in Inspect.") LIST_ITEM (L"\\bu How come 4.6.07 introduced those bugs? Because of large changes in the Praat source code as a result of the transition to Unicode.") NORMAL (L"##4.6.08# (22 June 2007)") LIST_ITEM (L"\\bu Windows: worked around a `feature' of the C library that caused 3-byte line-breaks in the buttons file.") LIST_ITEM (L"\\bu Windows: returned to smaller font in script window.") LIST_ITEM (L"\\bu OT learning: corrected a bug in PositiveHG.") NORMAL (L"##4.6.07# (20 June 2007)") LIST_ITEM (L"\\bu Sound files: MP3 as LongSound (implemented by Erez Volk).") LIST_ITEM (L"\\bu Scripting: Unicode support for strings and script window (Mac and Windows only).") NORMAL (L"##4.6.06# (4 June 2007)") LIST_ITEM (L"\\bu Script window: corrected a bug introduced in 4.6.05 that could cause incorrect symbols in saved files.") NORMAL (L"##4.6.05# (2 June 2007)") LIST_ITEM (L"\\bu Sound files: reading MP3 audio files (implemented by Erez Volk).") NORMAL (L"##4.6.04# (29 May 2007)") LIST_ITEM (L"\\bu OT learning: added decision strategy PositiveHG.") NORMAL (L"##4.6.03# (24 May 2007)") LIST_ITEM (L"\\bu Spectral slices have better names.") NORMAL (L"##4.6.02# (17 May 2007)") LIST_ITEM (L"\\bu Sound files: saving FLAC audio files (implemented by Erez Volk).") NORMAL (L"##4.6.01# (16 May 2007)") LIST_ITEM (L"\\bu Removed a bug that caused downsampling (and therefore formant measurements) " "to be incorrect for stereo sounds.") NORMAL (L"##4.6# (12 May 2007)") NORMAL (L"##4.5.26# (8 May 2007)") LIST_ITEM (L"\\bu Sound files: reading FLAC audio files (implemented by Erez Volk).") NORMAL (L"##4.5.25# (7 May 2007)") LIST_ITEM (L"\\bu Table: Rows to columns...") LIST_ITEM (L"\\bu Table: Collapse rows... (renamed from Pool).") LIST_ITEM (L"\\bu Table: Formula (column range)...") LIST_ITEM (L"\\bu OT learning: OTGrammar window shows harmonies.") NORMAL (L"##4.5.24# (27 April 2007)") LIST_ITEM (L"\\bu OT learning: added decision strategy MaximumEntropy; " "this has the same harmony determination method as Harmonic Grammar (include the additive constraint noise), " "but there is some more variability, in that every candidate gets a relative probability of exp(harmony).") NORMAL (L"##4.5.23# (26 April 2007)") LIST_ITEM (L"\\bu Macintosh: much smaller sizes (in kilobytes) of spectrograms for printing and clipboard; " "this improves the compatibility with other programs such as Microsoft Word for large spectrograms.") NORMAL (L"##4.5.22# (25 April 2007)") LIST_ITEM (L"\\bu Macintosh: improved drawing of spectrograms for printing and clipboard " "(this was crippled in 4.5.18, but now it is better than before 4.5.18).") NORMAL (L"##4.5.21# (24 April 2007)") LIST_ITEM (L"\\bu OT learning: corrected HarmonicGrammar (and LinearOT) learning procedure " "to the stochastic gradient ascent method applied by @@J\\a\"ger (2003)@ to MaxEnt grammars.") LIST_ITEM (L"\\bu Scripting: removed a bug that could make selection checking (in command windows) unreliable after a script was run.") NORMAL (L"##4.5.20# (19 April 2007)") LIST_ITEM (L"\\bu Scripting: allow assignments like $$pitch = To Pitch... 0 75 600$.") LIST_ITEM (L"\\bu PitchTier Formula: guard against undefined values.") NORMAL (L"##4.5.19# (2 April 2007)") LIST_ITEM (L"\\bu Scripting: allow comments with \"\\# \" and \";\" in forms.") LIST_ITEM (L"\\bu Windows audio playing: attempt at more compatibility with Vista.") NORMAL (L"##4.5.18# (30 March 2007)") LIST_ITEM (L"\\bu Macintosh: better image drawing (more grey values).") LIST_ITEM (L"\\bu More tabulation commands.") LIST_ITEM (L"\\bu More SpectrumTier commands.") LIST_ITEM (L"\\bu Picture window: keyboard shortcut for ##Erase all#.") NORMAL (L"##4.5.17# (19 March 2007)") LIST_ITEM (L"\\bu Picture window: can change arrow size.") LIST_ITEM (L"\\bu Several #List commands.") LIST_ITEM (L"\\bu Spectrum: To SpectrumTier (peaks).") NORMAL (L"##4.5.16# (22 February 2007)") LIST_ITEM (L"\\bu Sound-to-Intensity: made resistant against undefined settings.") LIST_ITEM (L"\\bu Windows: made Ctrl-. available as a shortcut.") LIST_ITEM (L"\\bu Linux: made it more likely to find the correct fonts.") NORMAL (L"##4.5.15# (12 February 2007)") LIST_ITEM (L"\\bu Windows XP: worked around a bug in Windows XP that could cause Praat to crash " "when the user moved the mouse pointer over a file in the Desktop in the file selector. " "The workaround is to temporarily disable file info tips when the file selector window is on the screen.") NORMAL (L"##4.5.14# (5 February 2007)") LIST_ITEM (L"\\bu Scripting: some new predefined string variables like preferencesDirectory\\$ .") NORMAL (L"##4.5.13# (3 February 2007)") LIST_ITEM (L"\\bu For stereo sounds, pitch analysis is based on correlations pooled over channels " "(rather than on correlations of the channel average).") LIST_ITEM (L"\\bu For stereo sounds, spectrogram analysis is based on power density averaged across channels " "(rather than on the power density of the channel average).") LIST_ITEM (L"\\bu Scripting: removed a bug introduced in 4.5.06 that caused some variables not to be substituted.") NORMAL (L"##4.5.12# (30 January 2007)") LIST_ITEM (L"\\bu Made cross-correlation pitch analysis as fast as it used to be before 4.5.11.") NORMAL (L"##4.5.11# (29 January 2007)") LIST_ITEM (L"\\bu Sound objects can be stereo, for better playback quality " "(most analyses will work on the averaged mono signal).") LIST_ITEM (L"\\bu Macintosh: recording a sound now uses CoreAudio instead of SoundManager, " "for more compatibility with modern recording devices, " "and the possibility to record with a sampling frequency of 96 kHz.") LIST_ITEM (L"\\bu @ManPages allow picture scripts with separate object lists.") LIST_ITEM (L"\\bu Linux: better scroll bars in object list for Lesstif (Debian).") LIST_ITEM (L"\\bu Linux: made @@Create Strings as file list...@ work on Reiser.") LIST_ITEM (L"\\bu @sendpraat scripts correctly wait until sounds have played.") NORMAL (L"##4.5.08# (20 December 2006)") LIST_ITEM (L"\\bu ExperimentMFC: can use stereo sounds.") NORMAL (L"##4.5.07# (16 December 2006)") LIST_ITEM (L"\\bu Macintosh: playing a sound now uses CoreAudio instead of SoundManager.") LIST_ITEM (L"\\bu Phonetic symbols: \\\'1primary stress and \\\'1secon\\\'2dary stress.") NORMAL (L"##4.5.06# (13 December 2006)") LIST_ITEM (L"\\bu Support for 32-bit floating-point WAV files.") LIST_ITEM (L"\\bu Scripting: removed several kinds of restrictions on string length.") LIST_ITEM (L"\\bu SSCP: Draw confidence ellipse: corrected a bug that would sometimes not draw the ellipse when %N was very large.") NORMAL (L"##4.5.05# (5 December 2006)") LIST_ITEM (L"\\bu Macintosh scripting: European symbols such as \\o\" and \\e' and \\c, are now allowed in file names in scripts " "and in MacRoman-encoded file names sent by other programs through the sendpraat subroutine.") NORMAL (L"##4.5.04# (1 December 2006)") LIST_ITEM (L"\\bu @@Sound: Change gender...@: corrected a bug that often caused a female-to-male conversion to sound monotonous.") NORMAL (L"##4.5.03# (29 November 2006)") LIST_ITEM (L"\\bu Table: added independent-samples t-test.") LIST_ITEM (L"\\bu Linux: corrected a bug introduced in 4.5.02 that prevented sounds from playing and other weird things.") NORMAL (L"##4.5.02# (16 November 2006)") LIST_ITEM (L"\\bu Corrected yet another bug in the new @@Sound: To TextGrid (silences)...@.") NORMAL (L"##4.5.01# (28 October 2006)") LIST_ITEM (L"\\bu Sound window: the pitch drawing method is #Curves, #Speckles, or #Automatic.") LIST_ITEM (L"\\bu Corrected another bug in the new @@Sound: To TextGrid (silences)...@.") NORMAL (L"##4.5# (26 October 2006)") NORMAL (L"##4.4.35# (20 October 2006)") LIST_ITEM (L"\\bu In @ManPages you can now draw pictures.") NORMAL (L"##4.4.34# (19 October 2006)") LIST_ITEM (L"\\bu Corrected a bug in the new @@Sound: To TextGrid (silences)...@.") NORMAL (L"##4.4.33# (4 October 2006)") LIST_ITEM (L"\\bu Windows: corrected a bug introduced in 4.4.31 that caused Praat to skip the first line of the Buttons file.") NORMAL (L"##4.4.32# (30 September 2006)") LIST_ITEM (L"\\bu Scripting: more techniques for @@Scripting 4. Object selection|object selection@.") LIST_ITEM (L"\\bu Scripting: more support for putting the results of the #Info command into a string variable.") NORMAL (L"##4.4.31# (23 September 2006)") LIST_ITEM (L"\\bu Support for @@plug-ins@.") LIST_ITEM (L"\\bu Split between @@Create Strings as file list...@ and @@Create Strings as directory list...@.") NORMAL (L"##4.4.30# (28 August 2006)") LIST_ITEM (L"\\bu Table: Draw ellipse (standard deviation)...") NORMAL (L"##4.4.29# (21 August 2006)") LIST_ITEM (L"\\bu Allowed \"European\" symbols in file names and object names.") NORMAL (L"##4.4.28# (10 August 2006)") LIST_ITEM (L"\\bu Windows XP: Praat files can finally again be opened by double-clicking and by dragging them onto the Praat icon.") LIST_ITEM (L"\\bu Scripting (Windows): removed a bug that caused Praat to crash if the script window was closed when a file selector window was open.") NORMAL (L"##4.4.27# (4 August 2006)") LIST_ITEM (L"\\bu Table window: corrected vertical scroll bar (on Windows).") LIST_ITEM (L"\\bu Formulas: invSigmoid.") LIST_ITEM (L"\\bu Logging: added 'power' (and documented the 'freq' command).") LIST_ITEM (L"\\bu Removed a bug that caused ##Read two Sounds from stereo file...# not to work in scripts.") NORMAL (L"##4.4.26# (24 July 2006)") LIST_ITEM (L"\\bu ##Sound & FormantTier: Filter#: much more accurate.") NORMAL (L"##4.4.25# (16 July 2006)") LIST_ITEM (L"\\bu TextGrid reading: don't set first boundary to zero for .wrd label files.") NORMAL (L"##4.4.24# (19 June 2006)") LIST_ITEM (L"\\bu Scripting: regular expressions allow replacement with empty string.") NORMAL (L"##4.4.23# (1 June 2006)") LIST_ITEM (L"\\bu Table: ignore more white space.") NORMAL (L"##4.4.22# (30 May 2006)") LIST_ITEM (L"\\bu Scripting: replacing with regular expression. See @@Formulas 5. String functions@.") NORMAL (L"##4.4.21# (29 May 2006)") LIST_ITEM (L"\\bu Made Manipulation objects readable again.") NORMAL (L"##4.4.20# (3 May 2006)") LIST_ITEM (L"\\bu Removed limit on number of menus (Praat could crash if the number of open windows was high).") NORMAL (L"##4.4.19# (28 April 2006)") LIST_ITEM (L"\\bu Table: ##Get mean#, ##Get standard deviation#, ##Get quantile#.") NORMAL (L"##4.4.18# (24 April 2006)") LIST_ITEM (L"\\bu Table: ##View & Edit#: view the contents of a table.") LIST_ITEM (L"\\bu Table: ##Scatter plot#.") LIST_ITEM (L"\\bu Scripting: more warnings against missing or extra spaces.") NORMAL (L"##4.4.17# (19 April 2006)") LIST_ITEM (L"\\bu Table: #Pool: computing averages and medians of dependent variables " "for a selected combination of independent variables.") LIST_ITEM (L"\\bu Table: #Formula accepts string expressions as well as numeric expressions.") LIST_ITEM (L"\\bu Table: #Sort can sort by any number of columns.") LIST_ITEM (L"\\bu Table: ##Create with column names#.") LIST_ITEM (L"\\bu Table: ##Report mean#.") LIST_ITEM (L"\\bu Formulas: @@Formulas 7. Attributes of objects|row\\$ and col\\$ attributes@.") LIST_ITEM (L"\\bu Warning when trying to read data files whose format is newer than the Praat version.") NORMAL (L"##4.4.16# (1 April 2006)") LIST_ITEM (L"\\bu Spectrum window: dynamic range setting.") LIST_ITEM (L"\\bu SoundRecorder: corrected a bug in the Intel Mac edition.") NORMAL (L"##4.4.15# (30 March 2006)") LIST_ITEM (L"\\bu Source code even more compatible with 64-bit compilers.") NORMAL (L"##4.4.14# (29 March 2006)") LIST_ITEM (L"\\bu Source code more compatible with 64-bit compilers.") NORMAL (L"##4.4.13# (8 March 2006)") LIST_ITEM (L"\\bu Table To TableOfReal: better handling of --undefined-- values (are now numeric).") LIST_ITEM (L"\\bu MacOS X: TextGrid files can be double-clicked to open.") LIST_ITEM (L"\\bu @@Create Strings as file list...@: now handles up to 1,000,000 files per directory.") NORMAL (L"##4.4.12# (24 February 2006)") LIST_ITEM (L"\\bu TextGrid: removed a bug introduced in 4.4.10 that caused Praat to crash when converting an IntervalTier into a TextGrid.") NORMAL (L"##4.4.11# (23 February 2006)") LIST_ITEM (L"\\bu Listening experiments: removed a bug that could cause Praat to crash when an ExperimentMFC object was removed.") NORMAL (L"##4.4.10# (20 February 2006)") LIST_ITEM (L"\\bu Intel computers: corrected reading and writing of 24-bit sound files (error introduced in 4.4.09).") LIST_ITEM (L"\\bu Create TextGrid: guard against zero tiers.") LIST_ITEM (L"\\bu MacOS X: correct visibility of Praat icon.") LIST_ITEM (L"\\bu MacOS X: correct dropping of Praat files on Praat icon.") NORMAL (L"##4.4.09# (19 February 2006)") LIST_ITEM (L"\\bu Macintosh: first Intel Macintosh version.") LIST_ITEM (L"\\bu Windows: Create Strings from directory list...") NORMAL (L"##4.4.08# (6 February 2006)") LIST_ITEM (L"\\bu Much improved cepstral smoothing.") NORMAL (L"##4.4.07# (2 February 2006)") LIST_ITEM (L"\\bu More scripting facilities (local variables in procedures, e.g. .x and .text\\$ ).") LIST_ITEM (L"\\bu Faster formulas.") NORMAL (L"##4.4.06# (30 January 2006)") LIST_ITEM (L"\\bu More scripting facilities (Object_xxx [ ], Self.nx, Table_xxx\\$ [ ], better messages).") LIST_ITEM (L"\\bu Better reading and writing of Xwaves label files.") NORMAL (L"##4.4.05# (26 January 2006)") LIST_ITEM (L"\\bu @ExperimentMFC: removed a bug that caused Praat to crash when the Oops button was pressed after the experiment finished.") LIST_ITEM (L"\\bu TextGrid: an IntervalTier can be written to an Xwaves label file.") NORMAL (L"##4.4.04# (6 January 2006)") LIST_ITEM (L"\\bu Windows: Quicktime support (see at 4.4.03).") NORMAL (L"##4.4.03# (6 January 2006)") LIST_ITEM (L"\\bu Macintosh: Quicktime support, i.e., \"Read from file\" can now read the audio from several kinds of movie files (.mov, .avi).") NORMAL (L"##4.4.02# (5 January 2006)") LIST_ITEM (L"\\bu OT learning: allow the decision strategies of Harmonic Grammar and Linear OT.") NORMAL (L"##4.4.01# (2 January 2006)") LIST_ITEM (L"\\bu Picture window: \"Logarithmic marks\" allows reversed axes.") LIST_ITEM (L"\\bu Manipulation window: removed a bug from \"Shift frequencies\" that caused much too small shifts in semitones.") LIST_ITEM (L"\\bu TextGrid: \"Remove point...\".") NORMAL (L"##4.4# (19 December 2005)") NORMAL (L"##4.3.37# (15 December 2005)") LIST_ITEM (L"\\bu @@Principal component analysis@: now accepts tables with more variables (columns) than cases (rows).") LIST_ITEM (L"\\bu TIMIT label files: removed a bug that caused Praat to crash for files whose first part was not labelled.") NORMAL (L"##4.3.36# (11 December 2005)") LIST_ITEM (L"\\bu Ltas: Average.") LIST_ITEM (L"\\bu Optimality Theory: compute crucial rankings (select OTGrammar + PairDistribution).") NORMAL (L"##4.3.35# (8 December 2005)") LIST_ITEM (L"\\bu @ExperimentMFC: switched off warnings for stereo files.") NORMAL (L"##4.3.34# (8 December 2005)") LIST_ITEM (L"\\bu Sound window: the arrow scroll step is settable.") LIST_ITEM (L"\\bu You can now run multiple listening experiments (@ExperimentMFC) in one \"Run\".") LIST_ITEM (L"\\bu Formant: Get quantile of bandwidth...") NORMAL (L"##4.3.33# (6 December 2005)") LIST_ITEM (L"\\bu Removed three bugs introduced in 4.3.32 in @ExperimentMFC.") NORMAL (L"##4.3.32# (5 December 2005)") LIST_ITEM (L"\\bu Many more possibilities in @ExperimentMFC.") NORMAL (L"##4.3.31# (27 November 2005)") LIST_ITEM (L"\\bu @@Sound: To Ltas (pitch-corrected)...@") NORMAL (L"##4.3.30# (18 November 2005)") LIST_ITEM (L"\\bu TableOfReal: Scatter plot: allows reversed axes.") NORMAL (L"##4.3.29# (11 November 2005)") LIST_ITEM (L"\\bu Windows: many more font sizes.") NORMAL (L"##4.3.28# (7 November 2005)") LIST_ITEM (L"\\bu Fontless EPS files: corrected character width for Symbol font (depended on SILIPA setting).") LIST_ITEM (L"\\bu Windows: more reliable detection of home directory.") NORMAL (L"##4.3.27# (7 October 2005)") LIST_ITEM (L"\\bu TextGrid & Pitch: draw with text alignment.") NORMAL (L"##4.3.26# (29 September 2005)") LIST_ITEM (L"\\bu Macintosh: corrected error introduced in 4.3.25.") NORMAL (L"##4.3.25# (28 September 2005)") LIST_ITEM (L"\\bu Macintosh: allowed recording with sample rates of 12 and 64 kHz.") NORMAL (L"##4.3.24# (26 September 2005)") LIST_ITEM (L"\\bu Table: Down to TableOfReal...: one column of the Table can be used as the row labels for the TableOfReal, " "and the strings in the remaining columns of the Table are replaced with whole numbers assigned in alphabetical order.") NORMAL (L"##4.3.23# (24 September 2005)") LIST_ITEM (L"\\bu Read Table from comma-separated file...") LIST_ITEM (L"\\bu Read Table from tab-separated file...") LIST_ITEM (L"\\bu Write picture as fontless EPS file: choice between XIPA and SILIPA93.") LIST_ITEM (L"\\bu Bold IPA symbols in EPS files (fontless SILIPA93 only).") NORMAL (L"##4.3.22# (8 September 2005)") LIST_ITEM (L"\\bu Macintosh: variable scroll bar size (finally, 7 years since System 8.5).") NORMAL (L"##4.3.21# (1 September 2005)") LIST_ITEM (L"\\bu Macintosh: error message if any of the fonts Times, Helvetica, Courier and Symbol are unavailable at start-up.") LIST_ITEM (L"\\bu Renamed \"Control\" menu to \"Praat\" on all platforms (as on the Mac), " "to reflect the fact that no other programs than Praat have used the Praat shell for five years.") LIST_ITEM (L"\\bu Script editor: Undo and Redo buttons (only on the Mac for now).") LIST_ITEM (L"\\bu Manual: corrected a bug that sometimes caused Praat to crash when trying to print.") NORMAL (L"##4.3.20# (18 August 2005)") LIST_ITEM (L"\\bu Log files: include name of editor window.") NORMAL (L"##4.3.19# (20 July 2005)") LIST_ITEM (L"\\bu Improved buttons in manual.") LIST_ITEM (L"\\bu TableOfReal: Read from headerless spreadsheet file: allow row and column labels to be 30,000 rather than 100 characters.") NORMAL (L"##4.3.18# (12 July 2005)") LIST_ITEM (L"\\bu Glottal source for sound synthesis, corrected and documented.") NORMAL (L"##4.3.17# (7 July 2005)") LIST_ITEM (L"\\bu Glottal source for sound synthesis.") LIST_ITEM (L"\\bu Multi-level Optimality Theory: parallel evaluation and bidirectional learning.") NORMAL (L"##4.3.16# (22 June 2005)") LIST_ITEM (L"\\bu Pitch drawing: corrected logarithmic scales.") NORMAL (L"##4.3.15# (22 June 2005)") LIST_ITEM (L"\\bu Graphics: better dotted lines in pitch contours; clipped pitch curves in editor windows.") LIST_ITEM (L"\\bu Pitch analysis: more different units (semitones %re 1 Hz).") NORMAL (L"##4.3.14# (14 June 2005)") LIST_ITEM (L"\\bu Scripting: regular expressions.") LIST_ITEM (L"\\bu Removed a bug that caused Praat to crash if a proposed object name was longer than 200 characters.") NORMAL (L"##4.3.13# (19 May 2005)") LIST_ITEM (L"\\bu Macintosh: an option to switch off screen previews in EPS files.") LIST_ITEM (L"\\bu Sources: compatibility of makefiles with MinGW (Minimalist GNU for Windows).") NORMAL (L"##4.3.12# (10 May 2005)") LIST_ITEM (L"\\bu Some more manual tricks.") NORMAL (L"##4.3.11# (6 May 2005)") LIST_ITEM (L"\\bu TextGrid editor: show number of intervals.") NORMAL (L"##4.3.10# (25 April 2005)") LIST_ITEM (L"\\bu Table: Get logistic regression.") NORMAL (L"##4.3.08# (19 April 2005)") LIST_ITEM (L"\\bu OT learning: store history with \"OTGrammar & Strings: Learn from partial outputs...\".") NORMAL (L"##4.3.07# (31 March 2005)") LIST_ITEM (L"\\bu Linux: removed a bug that could cause a sound to stop playing.") NORMAL (L"##4.3.04# (9 March 2005)") LIST_ITEM (L"\\bu Use SIL Doulos IPA 1993/1996 instead of 1989.") NORMAL (L"##4.3.03# (2 March 2005)") LIST_ITEM (L"\\bu TextGrid window: green colouring of matching text.") LIST_ITEM (L"\\bu Regular expressions can be used in many places.") LIST_ITEM (L"\\bu Pitch analysis: switched off formant-pulling.") NORMAL (L"##4.3.02# (16 February 2005)") LIST_ITEM (L"\\bu TextGrid: Remove boundary at time...") LIST_ITEM (L"\\bu Scripting: corrected %nowarn.") LIST_ITEM (L"\\bu Linux: guard against blocking audio device.") LIST_ITEM (L"\\bu Macintosh: guard against out-of-range audio level meter.") NORMAL (L"##4.3.01# (9 February 2005)") LIST_ITEM (L"\\bu Replaced PostScript font SILDoulosIPA with XIPA (adapted for Praat by Rafael Laboissi\\e`re).") LIST_ITEM (L"\\bu Sound: Set part to zero...") LIST_ITEM (L"\\bu Pitch: To Sound (sine)...") LIST_ITEM (L"\\bu Sound & TextGrid: Clone time domain.") ENTRY (L"Praat 4.3, 26 January 2005") NORMAL (L"General:") LIST_ITEM (L"\\bu `Apply' button in settings windows for menu commands and in script forms.") LIST_ITEM (L"\\bu Info window can be saved.") LIST_ITEM (L"\\bu Removed 30,000-character limit in Info window.") NORMAL (L"Phonetics:") LIST_ITEM (L"\\bu Speeded up intensity analysis by a factor of 10 " "(by making its time resolution 0.01 ms rather than 0.0001 ms at a sampling frequency of 44 kHz).") LIST_ITEM (L"\\bu Speeded up pitch analysis and spectrogram analysis by a factor of two.") LIST_ITEM (L"\\bu Sound: To Spectrum... now has a reasonably fast non-FFT version.") LIST_ITEM (L"\\bu Calibrated long-term average spectrum (Sound: To Ltas...).") LIST_ITEM (L"\\bu Pitch-corrected LTAS analysis.") LIST_ITEM (L"\\bu Sound: Scale intensity.") LIST_ITEM (L"\\bu PitchTier: To Sound (sine).") LIST_ITEM (L"\\bu Better warnings against use of the LPC object.") NORMAL (L"Voice:") LIST_ITEM (L"\\bu July 9, 2004 (4.2.08): Shimmer measurements: more accurate and less sensitive to additive noise.") LIST_ITEM (L"\\bu More extensive voice report: pitch statistics; harmonicity.") NORMAL (L"Audio:") LIST_ITEM (L"\\bu Reading and opening 24-bit and 32-bit sound files (saving still goes in 16 bits).") LIST_ITEM (L"\\bu LongSound: save separate channels.") LIST_ITEM (L"\\bu Macintosh: much faster reading of WAV files.") NORMAL (L"Listening experiments:") LIST_ITEM (L"\\bu Subjects can now respond with keyboard presses.") NORMAL (L"Graphics:") LIST_ITEM (L"\\bu One can now drag the inner viewport in the Picture window, excluding the margins. " "This is nice e.g. for creating square viewports or for drawing a waveform and a spectrogram in close contact.") LIST_ITEM (L"\\bu Unix: picture highlighting as on Mac and Windows.") LIST_ITEM (L"\\bu More drawing methods for Sound and Ltas (curve, bars, poles, speckles).") NORMAL (L"OT learning:") LIST_ITEM (L"\\bu Monitor rankings when learning.") LIST_ITEM (L"\\bu OTGrammar: Remove harmonically bounded candidates...") LIST_ITEM (L"\\bu OTGrammar: Save as headerless spreadsheet file...") LIST_ITEM (L"\\bu Metrics grammar: added *Clash, *Lapse, WeightByPosition and *MoraicConsonant.") NORMAL (L"Scripting:") LIST_ITEM (L"\\bu nowarn, noprogress, nocheck.") LIST_ITEM (L"\\bu Line numbers.") ENTRY (L"Praat 4.2, 4 March 2004") NORMAL (L"General:") LIST_ITEM (L"\\bu July 10, 2003: Open source code (General Public Licence).") NORMAL (L"Phonetics:") LIST_ITEM (L"\\bu Faster computation of spectrum, spectrogram, and pitch.") LIST_ITEM (L"\\bu More precision in numeric libraries.") LIST_ITEM (L"\\bu PitchTier: Interpolate quadratically.") LIST_ITEM (L"\\bu TextGrids can be saved chronologically (and Praat can read that file again).") LIST_ITEM (L"\\bu Sound editor window @@Time step settings...@: \"Automatic\", \"Fixed\", and \"View-dependent\".") LIST_ITEM (L"\\bu Sound window: distinguish basic from advanced spectrogram and pitch settings.") LIST_ITEM (L"\\bu Read TableOfReal from headerless spreadsheet file...: cells with strings are considered zero.") LIST_ITEM (L"\\bu Sound window: introduced time step as advanced setting.") LIST_ITEM (L"\\bu Sound window: reintroduced view range as advanced setting.") LIST_ITEM (L"\\bu Ltas: Compute trend line, Subtract trend line.") NORMAL (L"Audio:") LIST_ITEM (L"\\bu Sun workstations: support audio servers.") NORMAL (L"Graphics:") LIST_ITEM (L"\\bu Better selections in Picture window and editor windows.") LIST_ITEM (L"\\bu Picture window: better handling of rectangles and ellipses for reversed axes.") LIST_ITEM (L"\\bu Windows: corrected positioning of pictures on clipboard and in metafiles.") LIST_ITEM (L"\\bu Windows: EPS files check availability of Times and TimesNewRomanPSMT.") LIST_ITEM (L"\\bu Polygon: can now also paint in colour instead of only in grey values.") LIST_ITEM (L"\\bu Unlimited number of points for polygons in PostScript (may not work on very old printers).") LIST_ITEM (L"\\bu Picture window: line widths on all printers and clipboards are now equal to line widths used on PostScript printers: " "a line with a line width of \"1\" will be drawn with a width 3/8 points. This improves the looks of pictures printed " "on non-PostScript printers, improves the looks of pictures copied to your wordprocessor when printed, " "and changes the looks of pictures copied to your presentation program.") NORMAL (L"OT learning:") LIST_ITEM (L"\\bu Metrics grammar supports \'impoverished overt forms\', " "i.e. without secondary stress even if surface structures do have secondary stress.") LIST_ITEM (L"\\bu Support for crucially tied constraints and tied candidates.") LIST_ITEM (L"\\bu Support for backtracking in EDCD.") LIST_ITEM (L"\\bu Queries for testing grammaticality.") NORMAL (L"Scripting:") LIST_ITEM (L"\\bu ManPages: script links can receive arguments.") LIST_ITEM (L"\\bu ManPages: variable duration of recording.") LIST_ITEM (L"\\bu Support for unlimited size of script files in editor window on Windows XP and MacOS X (the Unix editions already had this).") LIST_ITEM (L"\\bu Improved the reception of %sendpraat commands on Windows XP.") ENTRY (L"Praat 4.1, 5 June 2003") NORMAL (L"General:") LIST_ITEM (L"\\bu MacOS X edition.") LIST_ITEM (L"\\bu Removed licensing.") LIST_ITEM (L"\\bu More than 99 percent of the source code distributed under the General Public Licence.") LIST_ITEM (L"\\bu Windows 2000 and XP: put preferences files in home directory.") NORMAL (L"Phonetics:") LIST_ITEM (L"\\bu Spectrum: the sign of the Fourier transform has changed, to comply with common use " "in technology and physics. Old Spectrum files are converted when read.") LIST_ITEM (L"\\bu Spectral moments.") LIST_ITEM (L"\\bu Many jitter and shimmer measures, also in the Sound editor window.") LIST_ITEM (L"\\bu PitchTier: shift or multiply frequencies (also in ManipulationEditor).") LIST_ITEM (L"\\bu TextGrid: shift times, scale times.") LIST_ITEM (L"\\bu Overlap-add synthesis: reduced buzz in voiceless parts.") LIST_ITEM (L"\\bu @@Sound: Change gender...") LIST_ITEM (L"\\bu Editors: @@Intro 3.6. Viewing a spectral slice@.") LIST_ITEM (L"\\bu Editors: Get spectral power at cursor cross.") LIST_ITEM (L"\\bu @@Sound: To PointProcess (periodic, peaks)...@") LIST_ITEM (L"\\bu Ltas: merge.") NORMAL (L"Listening experiments:") LIST_ITEM (L"\\bu Goodness judgments.") LIST_ITEM (L"\\bu Multiple ResultsMFC: ##To Table#, so that the whole experiment can go into a single statistics file.") LIST_ITEM (L"\\bu Stimulus file path can be relative to directory of experiment file.") LIST_ITEM (L"\\bu @ExperimentMFC: multiple substimuli for discrimination tests.") NORMAL (L"Statistics:") LIST_ITEM (L"\\bu New @Table object for column @statistics: Pearson's %r, Kendall's %\\ta-%b, %t-test.") LIST_ITEM (L"\\bu Table: scatter plot.") LIST_ITEM (L"\\bu Table: column names as variables.") LIST_ITEM (L"\\bu @@T-test@.") LIST_ITEM (L"\\bu TableOfReal: Extract rows where column...") LIST_ITEM (L"\\bu TableOfReal: Get correlation....") LIST_ITEM (L"\\bu @@Correlation: Confidence intervals...") LIST_ITEM (L"\\bu @@SSCP: Get diagonality (bartlett)...") NORMAL (L"OT learning:") LIST_ITEM (L"\\bu Tutorial for bidirectional learning.") LIST_ITEM (L"\\bu Random choice between equally violating candidates.") LIST_ITEM (L"\\bu More constraints in metrics grammar.") LIST_ITEM (L"\\bu Learning in editor.") NORMAL (L"Graphics:") LIST_ITEM (L"\\bu Printing: hard-coded image interpolation for EPS files and PostScript printers.") NORMAL (L"Scripting:") LIST_ITEM (L"\\bu New @Formulas tutorial.") LIST_ITEM (L"\\bu @Formulas: can use variables without quotes.") LIST_ITEM (L"\\bu Formulas for PitchTier, IntensityTier, AmplitudeTier, DurationTier.") LIST_ITEM (L"\\bu Refer to any matrices and tables in formulas, e.g. Sound_hello (x) or Table_everything [row, col] " "or Table_tokens [i, \"F1\"].") LIST_ITEM (L"\\bu Assignment by modification, as with += -= *= /=.") LIST_ITEM (L"\\bu New functions: date\\$ (), extractNumber, extractWord\\$ , extractLine\\$ . See @@Formulas 5. String functions@.") LIST_ITEM (L"\\bu @@Scripting 5.7. Including other scripts@.") LIST_ITEM (L"\\bu String formulas in the calculator.") LIST_ITEM (L"\\bu Stopped support of things that had been undocumented for the last four years: " "#let, #getnumber, #getstring, #ARGS, #copy, #proc, variables with capitals, and strings in numeric variables; " "there are messages about how to modify your old scripts.") LIST_ITEM (L"\\bu Disallowed ambiguous expressions like -3\\^ 2.") ENTRY (L"Praat 4.0, 15 October 2001") NORMAL (L"Editors:") LIST_ITEM (L"\\bu Simplified selection and cursor in editor windows.") LIST_ITEM (L"\\bu Spectrogram, pitch contour, formant contour, and intensity available in the " "Sound, LongSound, and TextGrid editors.") LIST_ITEM (L"\\bu TextGrid editor: additions and improvements.") LIST_ITEM (L"\\bu @@Log files@.") NORMAL (L"Phonetics library:") LIST_ITEM (L"\\bu @ExperimentMFC: multiple-forced-choice listening experiments.") LIST_ITEM (L"\\bu @@Sound: To Pitch (ac)...@: pitch contour less dependent on time resolution. " "This improves the constancy of the contours in the editors when zooming.") LIST_ITEM (L"\\bu TextGrid: additions and improvements.") LIST_ITEM (L"\\bu Sounds: Concatenate recoverably. Creates a TextGrid whose interval labels are the original " "names of the sounds.") LIST_ITEM (L"\\bu Sound & TextGrid: Extract all intervals. The reverse of the previous command.") LIST_ITEM (L"\\bu Filterbank analyses, @MelFilter, @BarkFilter and " "@FormantFilter, by @@band filtering in the frequency domain@." ) LIST_ITEM (L"\\bu Cepstrum by David Weenink: @MFCC, @LFCC. " "@Cepstrum object is a representation of the %%complex cepstrum%.") LIST_ITEM (L"\\bu Intensity: To IntensityTier (peaks, valleys).") LIST_ITEM (L"\\bu Replaced Analysis and AnalysisEditor with @Manipulation and @ManipulationEditor.") NORMAL (L"Phonology library:") LIST_ITEM (L"\\bu PairDistribution: Get percentage correct (maximum likelihood, probability matching).") LIST_ITEM (L"\\bu OTGrammar & PairDistribution: Get percentage correct...") NORMAL (L"Graphics:") LIST_ITEM (L"\\bu Improved spectrogram drawing.") LIST_ITEM (L"\\bu @@Special symbols@: h\\a'c\\v^ek.") LIST_ITEM (L"\\bu Macintosh: improved screen rendition of rotated text.") NORMAL (L"Audio:") LIST_ITEM (L"\\bu Macintosh: support for multiple audio input devices (sound cards).") NORMAL (L"Statistics and numerics library:") LIST_ITEM (L"\\bu More statistics by David Weenink.") LIST_ITEM (L"\\bu Improved random numbers and other numerical stuff.") LIST_ITEM (L"\\bu @@Regular expressions@.") NORMAL (L"Scripting:") LIST_ITEM (L"\\bu Formatting in variable substitution, e.g. 'pitch:2' gives two digits after the decimal point.") LIST_ITEM (L"\\bu Added ##fixed\\$ # to scripting language for formatting of numbers.") NORMAL (L"Documentation:") LIST_ITEM (L"\\bu @@Multidimensional scaling@ tutorial.") LIST_ITEM (L"\\bu Enabled debugging-at-a-distance.") ENTRY (L"Praat 3.9, 18 October 2000") NORMAL (L"Editors:") LIST_ITEM (L"\\bu Shift-click and shift-drag extend or shrink selection in editor windows.") LIST_ITEM (L"\\bu Grouped editors can have separate zooming and scrolling (FunctionEditor preferences).") LIST_ITEM (L"\\bu Cursor follows playing sound in editors; interruption by Escape key moves the cursor.") LIST_ITEM (L"\\bu TextGridEditor: optimized for transcribing large corpora: text field, directly movable boundaries, " "more visible text in tiers, @SpellingChecker, " "type while the sound is playing, complete keyboard navigation, control font size, control text alignment, " "shift-click near boundary adds interval to selection.") LIST_ITEM (L"\\bu Stereo display in LongSound and TextGrid editors.") LIST_ITEM (L"\\bu LongSoundEditor and TextGridEditor: write selection to audio file.") LIST_ITEM (L"\\bu SoundEditor: added command \"Extract selection (preserve times)\".") LIST_ITEM (L"\\bu IntervalTierEditor, DurationTierEditor.") LIST_ITEM (L"\\bu Added many query commands in editors.") NORMAL (L"Phonetics library:") LIST_ITEM (L"\\bu Sound: To Formant...: sample-rate-independent formant analysis.") LIST_ITEM (L"\\bu Sound: To Harmonicity (glottal-to-noise excitation ratio).") LIST_ITEM (L"\\bu Pitch: support for ERB units, draw all combinations of line/speckle and linear/logarithmic/semitones/mels/erbs, " "optionally with TextGrid, Subtract linear fit.") LIST_ITEM (L"\\bu Spectrum: Draw along logarithmic frequency axis.") LIST_ITEM (L"\\bu TextGrid: modification commands, Extract part, Shift to zero, Scale times (with Sound or LongSound).") LIST_ITEM (L"\\bu @@Matrix: To TableOfReal@, Draw contour...") LIST_ITEM (L"\\bu Concatenate Sound and LongSound objects.") LIST_ITEM (L"\\bu File formats: save PitchTier in spreadsheet format, read CGN syntax files (XML version), " "text files now completely file-server-safe (independent from Windows/Macintosh/Unix line separators).") NORMAL (L"Statistics and numerics library:") LIST_ITEM (L"\\bu @@Principal component analysis@.") LIST_ITEM (L"\\bu @@Discriminant analysis@.") LIST_ITEM (L"\\bu @Polynomial: drawing, @@Roots|root@ finding etc.") LIST_ITEM (L"\\bu @@TableOfReal: Draw box plots...@.") LIST_ITEM (L"\\bu @@Covariance: To TableOfReal (random sampling)...@.") LIST_ITEM (L"\\bu @@SSCP: Get sigma ellipse area...@.") LIST_ITEM (L"\\bu Query @DTW for 'weighted distance' of time warp.") LIST_ITEM (L"\\bu Distributions: To Strings (exact)...") LIST_ITEM (L"\\bu Strings: Randomize.") NORMAL (L"Phonology library:") LIST_ITEM (L"\\bu OTGrammar: To PairDistribution.") NORMAL (L"Graphics:") LIST_ITEM (L"\\bu Full support for colour inkjet printers on Windows and Macintosh.") LIST_ITEM (L"\\bu Full support for high-resolution colour clipboards and metafiles for " "Windows and Macintosh programs that support them (this include MS Word " "for Windows, but unfortunately not MS Word for Macintosh).") LIST_ITEM (L"\\bu Colour in EPS files.") LIST_ITEM (L"\\bu Interpolating grey images, i.e. better zoomed spectrograms.") LIST_ITEM (L"\\bu Linux: support for 24-bits screens.") NORMAL (L"Audio:") LIST_ITEM (L"\\bu Asynchronous sound play.") LIST_ITEM (L"\\bu Linux: solved problems with /dev/mixer (\"Cannot read MIC gain.\") on many computers.") LIST_ITEM (L"\\bu Added possibility of zero padding for sound playing, " "in order to reduce clicks on some Linux and Sun computers.") LIST_ITEM (L"\\bu LongSound supports mono and stereo, 8-bit and 16-bit, %\\mu-law and A-law, " "big-endian and little-endian, AIFC, WAV, NeXT/Sun, and NIST files.") LIST_ITEM (L"\\bu \"Read two Sounds from stereo file...\" supports 8-bit and 16-bit, %\\mu-law and A-law, " "big-endian and little-endian, AIFC, WAV, NeXT/Sun, and NIST files.") LIST_ITEM (L"\\bu SoundRecorder writes to 16-bit AIFC, WAV, NeXT/Sun, and NIST mono and stereo files.") LIST_ITEM (L"\\bu Sound & LongSound: write part or whole to mono or stereo audio file.") LIST_ITEM (L"\\bu Read Sound from raw Alaw file.") LIST_ITEM (L"\\bu Artword & Speaker (& Sound) movie: real time on all platforms.") NORMAL (L"Scripting:") LIST_ITEM (L"\\bu @@Formulas 4. Mathematical functions@: added statistical functions: %\\ci^2, Student T, Fisher F, binomial, " "and their inverse functions.") LIST_ITEM (L"\\bu Windows: program #praatcon for use as a Unix-style console application.") LIST_ITEM (L"\\bu Windows and Unix: Praat can be run with a command-line interface without quitting on errors.") LIST_ITEM (L"\\bu Unix & Windows: can use as a file name (supports pipes for binary data).") LIST_ITEM (L"\\bu @sendpraat now also for Macintosh.") LIST_ITEM (L"\\bu @@Scripting 6.7. Sending a message to another program|sendsocket@.") LIST_ITEM (L"\\bu @@Read from file...@ recognizes script files if they begin with \"\\# !\".") LIST_ITEM (L"\\bu Script links in @ManPages.") NORMAL (L"Documentation") LIST_ITEM (L"\\bu Tutorials on all subjects available through @Intro.") ENTRY (L"Praat 3.8, 12 January 1999") NORMAL (L"Phonetics library") LIST_ITEM (L"\\bu New objects: @LongSound (view and label long sound files), with editor; PairDistribution.") LIST_ITEM (L"\\bu @@Overlap-add@ manipulation of voiceless intervals, version 2: quality much better now; " "target duration is exactly as expected from Duration tier or specified lengthening in @@Sound: Lengthen (overlap-add)...@.") LIST_ITEM (L"\\bu Audio: Escape key stops audio playing (on Mac also Command-period).") LIST_ITEM (L"\\bu @SoundRecorder: allows multiple recordings without close; Play button; Write buttons; buffer size can be set.") LIST_ITEM (L"\\bu Reverse a Sound or a selection of a Sound.") LIST_ITEM (L"\\bu @@Sound: Get nearest zero crossing...@.") LIST_ITEM (L"\\bu Formant: \"Scatter plot (reversed axes)...\".") LIST_ITEM (L"\\bu TextGrid & Pitch: \"Speckle separately...\".") LIST_ITEM (L"\\bu \"Extract Sound selection (preserve times)\" in TextGridEditor.") LIST_ITEM (L"\\bu More query commands for Matrix, TableOfReal, Spectrum, PointProcess.") NORMAL (L"Phonology library") LIST_ITEM (L"\\bu 25-page OT learning tutorial.") LIST_ITEM (L"\\bu Made the OT learner 14 times as fast.") NORMAL (L"Platforms") LIST_ITEM (L"\\bu May 23: Windows beta version.") LIST_ITEM (L"\\bu April 24: Windows alpha version.") NORMAL (L"Files") LIST_ITEM (L"\\bu Read more Kay, Sun (.au), and WAV sound files.") LIST_ITEM (L"\\bu \"Read Strings from raw text file...\"") LIST_ITEM (L"\\bu @@Create Strings as file list...@.") LIST_ITEM (L"\\bu \"Read IntervalTier from Xwaves...\"") LIST_ITEM (L"\\bu hidden \"Read from old Windows Praat picture file...\"") NORMAL (L"Graphics") LIST_ITEM (L"\\bu Use colours (instead of only greys) in \"Paint ellipse...\" etc.") LIST_ITEM (L"\\bu More true colours (maroon, lime, navy, teal, purple, olive).") LIST_ITEM (L"\\bu Direct printing from Macintosh to PostScript printers.") LIST_ITEM (L"\\bu Hyperpage printing to PostScript printers and PostScript files.") LIST_ITEM (L"\\bu Phonetic symbols: raising sign, lowering sign, script g, corner, ligature, pointing finger.") NORMAL (L"Shell") LIST_ITEM (L"\\bu November 4: all dialogs are modeless (which is new for Unix and Mac).") LIST_ITEM (L"\\bu September 27: @sendpraat for Windows.") NORMAL (L"Scripting") LIST_ITEM (L"\\bu January 7: scriptable editors.") LIST_ITEM (L"\\bu October 7: file I/O in scripts.") LIST_ITEM (L"\\bu August 23: script language includes all the important functions for string handling.") LIST_ITEM (L"\\bu June 24: string variables in scripts.") LIST_ITEM (L"\\bu June 22: faster look-up of script variables.") LIST_ITEM (L"\\bu June 22: unlimited number of script variables.") LIST_ITEM (L"\\bu April 5: suspended chopping of trailing spaces.") LIST_ITEM (L"\\bu March 29: enabled formulas as arguments to dialogs (also interactive).") ENTRY (L"Praat 3.7, 24 March 1998") NORMAL (L"Editors:") LIST_ITEM (L"\\bu In all FunctionEditors: drag to get a selection.") NORMAL (L"Phonetics library:") LIST_ITEM (L"\\bu Many new query (#Get) commands for @Sound, @Intensity, @Harmonicity, @Pitch, " "@Formant, @Ltas, @PitchTier, @IntensityTier, @DurationTier, #FormantTier.") LIST_ITEM (L"\\bu Many new modification commands.") LIST_ITEM (L"\\bu Many new interpolations.") LIST_ITEM (L"\\bu Sound enhancements: @@Sound: Lengthen (overlap-add)...@, @@Sound: Deepen band modulation...@") LIST_ITEM (L"\\bu @@Source-filter synthesis@ tutorial, @@Sound & IntensityTier: Multiply@, " "##Sound & FormantTier: Filter#, @@Formant: Formula (frequencies)...@, @@Sound: Pre-emphasize (in-line)...@.") NORMAL (L"Labelling") LIST_ITEM (L"\\bu TextGrid queries (#Get times and labels in a script).") LIST_ITEM (L"\\bu @@TextGrid: Count labels...@.") LIST_ITEM (L"\\bu @@PointProcess: To TextGrid (vuv)...@: get voiced/unvoiced information from a point process.") LIST_ITEM (L"\\bu IntervalTier to TableOfReal: labels become row labels.") LIST_ITEM (L"\\bu TextTier to TableOfReal.") NORMAL (L"Numerics and statistics library") LIST_ITEM (L"\\bu Multidimensional scaling (Kruskal, INDSCAL, etc).") LIST_ITEM (L"\\bu @TableOfReal: Set value, Formula, Remove column, Insert column, Draw as squares, To Matrix.") NORMAL (L"Phonology library") LIST_ITEM (L"\\bu OT learning: new strategies: weighted symmetric plasticity (uncancelled or all).") NORMAL (L"Praat shell") LIST_ITEM (L"\\bu First Linux version.") LIST_ITEM (L"\\bu Eight new functions like e.g. %hertzToBark in @@Formulas 4. Mathematical functions@.") LIST_ITEM (L"\\bu @@Praat script@: procedure arguments; object names.") NORMAL (L"Documentation:") LIST_ITEM (L"\\bu 230 more man pages (now 630).") LIST_ITEM (L"\\bu Hypertext: increased readability of formulas, navigation with keyboard.") ENTRY (L"Praat 3.6, 27 October 1997") NORMAL (L"Editors:") LIST_ITEM (L"\\bu Intuitive position of B and E buttons on left-handed mice.") LIST_ITEM (L"\\bu @SoundEditor: copy %windowed selection to list of objects.") LIST_ITEM (L"\\bu @SoundEditor: undo Cut, Paste, Zero.") LIST_ITEM (L"\\bu @SpectrumEditor: copy band-filtered spectrum or sound to list of objects.") LIST_ITEM (L"\\bu @ManipulationEditor: LPC-based pitch manipulation.") NORMAL (L"Objects:") LIST_ITEM (L"\\bu Use '-', and '+' in object names.") NORMAL (L"Phonetics library") LIST_ITEM (L"\\bu LPC-based resynthesis in @ManipulationEditor.") LIST_ITEM (L"\\bu @Sound: direct modification without formulas (addition, multiplication, windowing)") LIST_ITEM (L"\\bu @Sound: filtering in spectral domain by formula.") LIST_ITEM (L"\\bu Create a simple @Pitch object from a @PitchTier (for %F__0_) and a @Pitch (for V/U).") LIST_ITEM (L"\\bu Semitones in @PitchTier tables.") LIST_ITEM (L"\\bu @PointProcess: transplant time domain from @Sound.") LIST_ITEM (L"\\bu Much more...") NORMAL (L"Phonology library") LIST_ITEM (L"\\bu Computational Optimality Theory. See @@OT learning@.") NORMAL (L"Hypertext") LIST_ITEM (L"\\bu You can use @ManPages files for creating your own tutorials. " "These contains buttons for playing and recording sounds, so you can use this for creating " "an interactive IPA sound training course.") NORMAL (L"Scripting:") LIST_ITEM (L"\\bu Programmable @@Praat script@ language: variables, expressions, control structures, " "procedures, complete dialog box, exchange of information with Info window, continuation lines.") LIST_ITEM (L"\\bu Use platform-independent relative file paths in @@Praat script@.") LIST_ITEM (L"\\bu @ScriptEditor: Run selection.") NORMAL (L"Graphics:") LIST_ITEM (L"\\bu Rotation and scaling while printing the @@Picture window@.") LIST_ITEM (L"\\bu Apart from bold and italic, now also bold-italic (see @@Text styles@).") LIST_ITEM (L"\\bu Rounded rectangles.") LIST_ITEM (L"\\bu Conversion of millimetres and world coordinates.") LIST_ITEM (L"\\bu Measurement of text widths (screen and PostScript).") NORMAL (L"Unix:") LIST_ITEM (L"\\bu Use the @sendpraat program for sending messages to running Praat programs.") NORMAL (L"Mac:") LIST_ITEM (L"\\bu Praat looks best with the new and beautiful System 8.") ENTRY (L"Praat 3.5, 27 May 1997") NORMAL (L"New editors:") LIST_ITEM (L"\\bu #TextGridEditor replaces and extends LabelEditor: edit points as well as intervals.") LIST_ITEM (L"\\bu #AnalysisEditor replaces and extends PsolaEditor: view pitch, spectrum, formant, and intensity " "analyses in a single window, and allow pitch and duration resynthesis by overlap-add and more (would be undone in 3.9.19).") LIST_ITEM (L"\\bu #SpectrumEditor allows you to view and edit spectra.") NORMAL (L"Praat shell:") LIST_ITEM (L"\\bu ##History mechanism# remembers all the commands that you have chosen, " "and allows you to put them into a script.") LIST_ITEM (L"\\bu #ScriptEditor allows you to edit and run any Praat script, and to put it under a button.") LIST_ITEM (L"\\bu All added and removed buttons are remembered across sessions.") LIST_ITEM (L"\\bu #ButtonEditor allows you to make buttons visible or invisible.") NORMAL (L"Evaluations:") LIST_ITEM (L"\\bu In his 1996 doctoral thesis, Henning Reetz " "compared five pitch analysis routines; @@Sound: To Pitch (ac)...@ appeared to make the fewest errors. " "H. Reetz (1996): %%Pitch Perception in Speech: a Time Domain Approach%, Studies in Language and Language Use #26, " "IFOTT, Amsterdam (ICG Printing, Dordrecht).") NORMAL (L"Documentation:") LIST_ITEM (L"\\bu 140 more man pages (now 330).") LIST_ITEM (L"\\bu Tables and pictures in manual.") LIST_ITEM (L"\\bu Printing the entire manual.") LIST_ITEM (L"\\bu Logo.") NORMAL (L"New types:") LIST_ITEM (L"\\bu Labelling & segmentation: #TextGrid, #IntervalTier, #TextTier.") LIST_ITEM (L"\\bu Analysis & manipulation: #Analysis.") LIST_ITEM (L"\\bu Statistics: #TableOfReal, #Distributions, #Transition") NORMAL (L"File formats:") LIST_ITEM (L"\\bu Read and write rational numbers in text files.") LIST_ITEM (L"\\bu Read 8-bit .au sound files.") LIST_ITEM (L"\\bu Read and write raw 8-bit two\'s-complement and offset-binary sound files.") NORMAL (L"Audio:") LIST_ITEM (L"\\bu 16-bit interactive Sound I/O on Mac.") LIST_ITEM (L"\\bu Record sounds at 9.8 kHz on SGI.") NORMAL (L"New commands:") LIST_ITEM (L"\\bu Two more pitch-analysis routines.") LIST_ITEM (L"\\bu Sound to PointProcess: collect all maxima, minima, zero crossings.") LIST_ITEM (L"\\bu PointProcess: set calculus.") LIST_ITEM (L"\\bu TextGrid: extract time-point information.") LIST_ITEM (L"\\bu Compute pitch or formants at given time points.") LIST_ITEM (L"\\bu Put pitch, formants etc. in tables en get statistics.") LIST_ITEM (L"\\bu Many more...") NORMAL (L"Macintosh:") LIST_ITEM (L"\\bu 16-bit interactive sound I/O.") LIST_ITEM (L"\\bu Fast and interpolating spectrogram drawing.") LIST_ITEM (L"\\bu Phonetic Mac screen font included in source code (as a fallback to using SIL Doulos IPA).") LIST_ITEM (L"\\bu Keyboard shortcuts, text editor, help under question mark, etc.") ENTRY (L"Praat 3.3, 6 October 1996") LIST_ITEM (L"\\bu Documentation: hypertext help browser, including the first 190 man pages.") LIST_ITEM (L"\\bu New editors: type #TextTier for labelling times instead of intervals.") LIST_ITEM (L"\\bu New actions: #Formant: Viterbi tracker, Statistics menu, Scatter plot.") LIST_ITEM (L"\\bu Evaluation: For HNR analysis of speech, the cross-correlation method, " "which has a sensitivity of 60 dB and a typical time resolution of 12 milliseconds, " "must be considered better than the autocorrelation method, " "which has a better sensitivity (80 dB), but a much worse time resolution (30 ms). " "For pitch analysis, the autocorrelation method still beats the cross-correlation method " "because of its better resistance against noise and echos, " "and despite its marginally poorer resolution (15 vs. 12 ms).") LIST_ITEM (L"\\bu User preferences are saved across sessions.") LIST_ITEM (L"\\bu The phonetic X screen font included in the source code.") LIST_ITEM (L"\\bu Xwindows resources included in the source code") LIST_ITEM (L"\\bu Graphics: eight colours, small caps, text rotation.") LIST_ITEM (L"\\bu File formats: Sun/NexT mu-law files, raw matrix text files, Xwaves mark files.") LIST_ITEM (L"\\bu Accelerations: keyboard shortcuts, faster dynamic menu, Shift-OK keeps file selector on screen.") LIST_ITEM (L"\\bu Object type changes: #StylPitch and #MarkTier are now called #PitchTier and #TextTier, respectively. " "Old files can still be read.") LIST_ITEM (L"\\bu Script warning: all times in dialogs are in seconds now: milliseconds have gone.") ENTRY (L"Praat 3.2, 29 April 1996") LIST_ITEM (L"\\bu Sound I/O for HPUX, Sun Sparc 5, and Sun Sparc LX.") LIST_ITEM (L"\\bu Cross-correlation pitch and HNR analysis.") LIST_ITEM (L"\\bu Facilities for generating tables from scripts.") LIST_ITEM (L"\\bu Editing and playing stylized pitch contours and point processes.") LIST_ITEM (L"\\bu Overlap-add pitch manipulation.") LIST_ITEM (L"\\bu Spectral smoothing techniques: cepstrum and LPC.") LIST_ITEM (L"\\bu Time-domain pitch analysis with jitter measurement.") LIST_ITEM (L"\\bu Read and write Bell-Labs sound files and Kay CSL audio files.") LIST_ITEM (L"\\bu Replaced IpaTimes font by free SILDoulos-IPA font, and embedded phonetic font in PostScript picture.") LIST_ITEM (L"\\bu Completed main phonetic characters.") ENTRY (L"Praat 3.1, 5 December 1995") LIST_ITEM (L"\\bu Add and remove buttons dynamically.") LIST_ITEM (L"\\bu DataEditor (Inspect button).") LIST_ITEM (L"\\bu Initialization scripts.") LIST_ITEM (L"\\bu Logarithmic axes.") LIST_ITEM (L"\\bu Call remote ADDA server directly.") ENTRY (L"To do") LIST_ITEM (L"\\bu TextGrid & Sound: Extract intervals with margins.") LIST_ITEM (L"\\bu Spectrum: draw power, re, im, phase.") LIST_ITEM (L"\\bu Formant: To Spectrum (slice)... (combines Formant-to-LPC and LPC-to-Spectrum-slice)") LIST_ITEM (L"\\bu Read and/or write Matlab files, MBROLA files, Xwaves files, CHAT files.") /* Aix */ LIST_ITEM (L"\\bu Matrix: draw numbers.") LIST_ITEM (L"\\bu Fractions with \\bsf{a|b}.") LIST_ITEM (L"\\bu Move objects up and down list.") LIST_ITEM (L"\\bu Spectrogram cross-correlation.") LIST_ITEM (L"\\bu Labels in AIFC file.") /* Theo Veenker 19980323 */ LIST_ITEM (L"\\bu Improve scrolling and add selection in hyperpages.") LIST_ITEM (L"\\bu Segment spectrograph?") /* Ton Wempe, Jul 16 1996 */ LIST_ITEM (L"\\bu Phoneme-to-articulation conversion??") /* Mirjam Ernestus, Jul 1 1996 */ ENTRY (L"Known bugs in the Windows version") LIST_ITEM (L"\\bu Cannot stand infinitesimal zooming in SpectrogramEditor.") LIST_ITEM (L"\\bu Clipboards with greys sometimes become black-and-white after use of colour.") ENTRY (L"Known bugs in the Linux version") LIST_ITEM (L"\\bu Sounds shorter than 200 ms do not always play (workaround: add zeroes in prefs).") LIST_ITEM (L"\\bu Keyboard shortcuts do not work if NumLock is on.") LIST_ITEM (L"\\bu Keyboard shortcut \"tab\" does not work.") MAN_END /* BUGBASE >* The Artword editor would be easier to read if the vertical axis of the >graphs were squeezed a little. As it is, the line for a target of 1 >throughout the utterance merges into the top bounding box and is >invisible. > >* In drawing a picture of an Artword for a Speaker, the Pen|Line-width >option only works for dotted and dashed lines. It's ignored for plain >lines (and is WAY too wide). */ MAN_BEGIN (L"Acknowledgments", L"ppgb", 20120219) NORMAL (L"The following people contributed source code to Praat:") LIST_ITEM (L"Paul Boersma: user interface, graphics, @printing, @@Intro|sound@, " "@@Intro 3. Spectral analysis|spectral analysis@, @@Intro 4. Pitch analysis|pitch analysis@, " "@@Intro 5. Formant analysis|formant analysis@, @@Intro 6. Intensity analysis|intensity analysis@, " "@@Intro 7. Annotation|annotation@, @@Intro 8. Manipulation|speech manipulation@, @@voice|voice report@, " "@@ExperimentMFC|listening experiments@, " "@@articulatory synthesis@, @@OT learning|optimality-theoretic learning@, " "tables, @formulas, @scripting, and adaptation of PortAudio, GLPK, and regular expressions.") LIST_ITEM (L"David Weenink: " "@@feedforward neural networks@, @@principal component analysis@, @@multidimensional scaling@, @@discriminant analysis@, @LPC, " "@VowelEditor, " "and adaptation of GSL, LAPACK, fftpack, regular expressions, and Espeak.") LIST_ITEM (L"Stefan de Konink and Franz Brau\\sse: major help in port to GTK.") LIST_ITEM (L"Erez Volk: adaptation of FLAC and MAD.") LIST_ITEM (L"Ola S\\o\"der: @@kNN classifiers@, @@k-means clustering@.") LIST_ITEM (L"Rafael Laboissi\\e`re: adaptation of XIPA.") LIST_ITEM (L"Darryl Purnell created the first version of audio for Praat for Linux.") NORMAL (L"We included the following freely available software libraries in Praat (sometimes with adaptations):") LIST_ITEM (L"XIPA: IPA font for Unix by Fukui Rei (GPL).") LIST_ITEM (L"GSL: GNU Scientific Library by Gerard Jungman and Brian Gough (GPL).") LIST_ITEM (L"GLPK: GNU Linear Programming Kit by Andrew Makhorin (GPL).") LIST_ITEM (L"PortAudio: Portable Audio Library by Ross Bencina, Phil Burk, Bjorn Roche, Dominic Mazzoni, Darren Gibbs.") LIST_ITEM (L"Espeak: text-to-speech synthesizer by Jonathan Duddington (GPL).") LIST_ITEM (L"MAD: MPEG Audio Decoder by Underbit Technologies (GPL).") LIST_ITEM (L"FLAC: Free Lossless Audio Codec by Josh Coalson.") LIST_ITEM (L"fftpack: public domain Fourier transforms by Paul Swarztrauber and Monty.") LIST_ITEM (L"LAPACK: public domain numeric algorithms by Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd., " "Courant Institute, Argonne National Lab, and Rice University.") LIST_ITEM (L"Regular expressions by Henry Spencer, Mark Edel, Christopher Conrad, Eddy De Greef (GPL).") NORMAL (L"For technical support and advice:") LIST_ITEM (L"Ton Wempe, Dirk Jan Vet.") NORMAL (L"For their financial support during the development of Praat:") LIST_ITEM (L"Netherlands Organization for Scientific Research (NWO) (1996\\--1999).") LIST_ITEM (L"Nederlandse Taalunie (2006\\--2008).") LIST_ITEM (L"Talkbank project, Carnegie Mellon / Linguistic Data Consortium (2002\\--2003).") LIST_ITEM (L"Spoken Dutch Corpus (CGN) (1999\\--2001).") LIST_ITEM (L"Laboratorium Experimentele OtoRhinoLaryngologie, KU Leuven.") LIST_ITEM (L"DFG-Projekt Dialektintonation, Universit\\a\"t Freiburg.") LIST_ITEM (L"Department of Linguistics and Phonetics, Lund University.") LIST_ITEM (L"Centre for Cognitive Neuroscience, University of Turku.") LIST_ITEM (L"Linguistics Department, University of Joensuu.") LIST_ITEM (L"Laboratoire de Sciences Cognitives et Psycholinguistique, Paris.") LIST_ITEM (L"Department of Linguistics, Northwestern University.") LIST_ITEM (L"Department of Finnish and General Linguistics, University of Tampere.") LIST_ITEM (L"Institute for Language and Speech Processing, Paradissos Amaroussiou.") LIST_ITEM (L"J\\o\"rg Jescheniak, Universit\\a\"t Leipzig.") LIST_ITEM (L"The Linguistics Teaching Laboratory, Ohio State University.") LIST_ITEM (L"Linguistics & Cognitive Science, Dartmouth College, Hanover NH.") LIST_ITEM (L"Cornell Phonetics Lab, Ithaca NY.") NORMAL (L"Finally:") LIST_ITEM (L"Daniel Hirst, for managing the Praat Discussion list.") MAN_END MAN_BEGIN (L"Praat menu", L"ppgb", 20050822) INTRO (L"The first menu in the @@Object window@. On MacOS X, this menu is in the main menu bar.") MAN_END MAN_BEGIN (L"Copy...", L"ppgb", 20111018) INTRO (L"One of the fixed buttons in the @@Object window@.") ENTRY (L"Availability") NORMAL (L"You can choose this command after selecting one object of any type.") ENTRY (L"Behaviour") NORMAL (L"The Object window copies the selected object, and all the data it contains, " "to a new object, which will appear at the bottom of the List of Objects.") ENTRY (L"Example") NORMAL (L"If you select \"Sound hallo\" and click `Copy...', " "a command window will appear, which prompts you for a name; " "after you click OK, a new object will appear in the list, bearing that name.") MAN_END MAN_BEGIN (L"Draw menu", L"ppgb", 20010417) INTRO (L"A menu that occurs in the @@Dynamic menu@ for many objects.") NORMAL (L"This menu contains commands for drawing the object to the @@Picture window@, " "which will allow you to print the drawing or to copy it to your word processor.") MAN_END MAN_BEGIN (L"Dynamic menu", L"ppgb", 20110131) INTRO (L"A column of buttons in the right-hand part of the @@Object window@, " "plus the #Save menu in the Object window.") NORMAL (L"If you select one or more @objects in the list, " "the possible actions that you can perform with the selected objects " "will appear in the dynamic menu. " "These actions can include viewing & editing, saving, drawing, " "conversions to other types (including analysis and synthesis), and more.") ENTRY (L"Example of analysis:") NORMAL (L"Record a Sound, select it, and click on ##To Pitch...#. " "This will create a new Pitch object and put it in the list of objects. " "You can then edit, write, and draw this Pitch object.") ENTRY (L"Example of synthesis:") NORMAL (L"Create a #Speaker, create and edit an #Artword, and click on ##To Sound...#.") MAN_END MAN_BEGIN (L"View & Edit", L"ppgb", 20110128) INTRO (L"A command in the @@Dynamic menu@ of several types of @objects.") NORMAL (L"This command puts an @@Editors|editor@ window on the screen, which shows the contents of the selected object. " "This window will allow your to view and modify the contents of this object.") MAN_END MAN_BEGIN (L"Extract visible formant contour", L"ppgb", 20030316) INTRO (L"One of the commands in the Formant menu of the @SoundEditor and the @TextGridEditor.") NORMAL (L"See @@Intro 5. Formant analysis@") MAN_END MAN_BEGIN (L"Extract visible intensity contour", L"ppgb", 20030316) INTRO (L"One of the commands in the Intensity menu of the @SoundEditor and the @TextGridEditor.") NORMAL (L"See @@Intro 6. Intensity analysis@") MAN_END MAN_BEGIN (L"Extract visible pitch contour", L"ppgb", 20030316) INTRO (L"One of the commands in the Pitch menu of the @SoundEditor and the @TextGridEditor.") NORMAL (L"See @@Intro 4. Pitch analysis@") MAN_END MAN_BEGIN (L"Extract visible spectrogram", L"ppgb", 20030316) INTRO (L"One of the commands in the Spectrogram menu of the @SoundEditor and the @TextGridEditor.") NORMAL (L"See @@Intro 3. Spectral analysis@") MAN_END MAN_BEGIN (L"FAQ (Frequently Asked Questions)", L"ppgb", 20071210) LIST_ITEM (L"@@FAQ: How to cite Praat") LIST_ITEM (L"@Unicode") LIST_ITEM (L"@@FAQ: Formant analysis") LIST_ITEM (L"@@FAQ: Pitch analysis") LIST_ITEM (L"@@FAQ: Spectrograms") LIST_ITEM (L"@@FAQ: Scripts") /* Hardware */ /* Pitch: octave errors */ MAN_END MAN_BEGIN (L"FAQ: Formant analysis", L"ppgb", 20030916) NORMAL (L"#Problem: I get different formant values if I choose to analyse 3 formants " "than if I choose to analyse 4 formants.") NORMAL (L"Solution: the \"number of formants\" in formant analysis determines the " "number of peaks with which the %entire spectrum is modelled. For an average " "female voice, you should choose to analyse 5 formants in the region up to 5500 Hz, " "even if you are interested only in the first three formants.") NORMAL (L"") NORMAL (L"#Problem: I often get only 1 formant in a region where I see clearly 2 formants " "in the spectrogram.") NORMAL (L"This occurs mainly in back vowels (F1 and F2 close together) for male voices, " "if the \"maximum formant\" is set to the standard of 5500 Hz, which is appropriate " "for female voices. Set the \"maximum formant\" down to 5000 Hz. " "No, Praat comes without a guarantee: the formant analysis is based on LPC, " "and this comes with several assumptions as to what a speech spectrum is like.") NORMAL (L"") NORMAL (L"#Question: what algorithm is used for formant analysis?") NORMAL (L"Answer: see @@Sound: To Formant (burg)...@.") MAN_END MAN_BEGIN (L"FAQ: How to cite Praat", L"ppgb", 20100401) NORMAL (L"#Question: how do I cite Praat in my articles?") NORMAL (L"Answer: nowadays most journals allow you to cite computer programs and web sites. " "The style approved by the American Psychological Association, " "and therefore by many journals, is like the following " "(change the dates and version number as needed):") #define xstr(s) str(s) #define str(s) #s NORMAL (L"Boersma, Paul & Weenink, David (" xstr(PRAAT_YEAR) "). " "Praat: doing phonetics by computer [Computer program]. " "Version " xstr(PRAAT_VERSION_STR) ", retrieved " xstr(PRAAT_DAY) " " xstr(PRAAT_MONTH) " " xstr(PRAAT_YEAR) " from http://www.praat.org/") NORMAL (L"If the journal does not allow you to cite a web site, then try:") NORMAL (L"Boersma, Paul (2001). Praat, a system for doing phonetics by computer. " "%%Glot International% ##5:9/10#, 341-345.") MAN_END MAN_BEGIN (L"FAQ: Pitch analysis", L"ppgb", 20060913) NORMAL (L"#Question: what algorithm is used for pitch analysis?") NORMAL (L"Answer: see @@Sound: To Pitch (ac)...@. The 1993 article is downloadable from " "http://www.fon.hum.uva.nl/paul/") NORMAL (L"#Question: why does Praat consider my sound voiceless while I hear it as voiced?") NORMAL (L"There are at least five possibilities. Most of them can be checked by zooming in on the @waveform.") NORMAL (L"The first possibility is that the pitch has fallen below the @@pitch floor@. For instance, " "your pitch floor could be 75 Hz but the English speaker produces creak at the end of the utterance. " "Or your pitch floor could be 75 Hz but the Chinese speaker is in the middle of a third tone. " "If this happens, it may help to lower the pitch floor to e.g. 40 Hz (@@Pitch settings...@), " "although that may also smooth the pitch curve too much in other places.") NORMAL (L"The second possibility is that the pitch has moved too fast. This could happen at the end of a Chinese fourth tone, " "which drops very fast. If this happens, it may help to use the \"optimize for voice analysis\" setting, " "(@@Pitch settings...@), although Praat may then hallucinate pitches in other places that you would prefer to consider voiceless.") NORMAL (L"The third possibility is that the periods are very irregular, as in some pathological voices. " "If you want to see a pitch in those cases, it may help to use the \"optimize for voice analysis\" setting " "(@@Pitch settings...@). Or it may help to lower the \"voicing threshold\" setting (@@Advanced pitch settings...@) " "to 0.25 (instead of the standard 0.45) or so.") NORMAL (L"The fourth possibility is that there is a lot of background noise, as in a recording on a busy street. " "In such a case, it may help to lower the \"voicing threshold\" setting (@@Advanced pitch settings...@) " "to 0.25 (instead of the standard 0.45) or so. The disadvantage of lowering this setting is that for non-noisy " "recordings, Praat will become too eager to find voicing in some places that you would prefer to consider voiceless; " "so make sure to set it back to 0.45 once you have finished analysing the noisy recordings.") NORMAL (L"The fifth possibility is that the part analysed as voiceless is much less loud than the rest of the sound, " "or that the sound contains a loud noise elsewhere. This can be checked by zooming in on the part analysed as voiceless: " "if Praat suddenly considers it as voiced, this is a sign that this part is much quieter than the rest. " "To make Praat analyse this part as voiced, you can lower the \"silence threshold\" setting to 0.01 " "(instead of the standard 0.03) or so. The disadvantage of lowering this setting is that Praat may start to consider " "some distant background sounds (and quiet echos, for instance) as voiced.") NORMAL (L"#Question: why do I get different results for the maximum pitch if...?") NORMAL (L"If you select a Sound and choose @@Sound: To Pitch...@, the time step will usually " "be 0.01 seconds. The resulting @Pitch object will have values for times that are " "0.01 seconds apart. If you then click Info or choose ##Get maximum pitch# from the #Query menu, " "the result is based on those time points. By contrast, if you choose ##Get maximum pitch# " "from the #Pitch menu in the SoundEditor window, the result will be based on the visible points, " "of which there tend to be a hundred in the visible window. These different time spacings will " "lead to slightly different pitch contours.") NORMAL (L"If you choose ##Move cursor to maximum pitch#, then choose ##Get pitch# from the " "#%Pitch menu, the result will be different again. This is because ##Get maximum pitch# " "can do a parabolic interpolation around the maximum, whereas ##Get pitch#, not realizing " "that the cursor is at a maximum, does a stupid linear interpolation, which tends to lead to " "lower values.") MAN_END MAN_BEGIN (L"FAQ: Scripts", L"ppgb", 20110128) NORMAL (L"#Question: how do I do something to all the files in a directory?") NORMAL (L"Answer: look at @@Create Strings as file list...@.") NORMAL (L"") NORMAL (L"#Question: why doesn't the editor window react to my commands?") NORMAL (L"Your commands are probably something like:") CODE (L"Read from file... hello.wav") CODE (L"View & Edit") CODE (L"Zoom... 0.3 0.5") NORMAL (L"Answer: Praat doesn't know it has to send the #Zoom command to the editor " "window called ##Sound hello#. There could be several Sound editor windows on your " "screen. According to @@Scripting 7.1. Scripting an editor from a shell script@, " "you will have to say this explicitly:") CODE (L"Read from file... hello.wav") CODE (L"View & Edit") CODE (L"editor Sound hello") CODE (L"Zoom... 0.3 0.5") NORMAL (L"") NORMAL (L"#Problem: a line like \"Number = 1\" does not work.") NORMAL (L"Solution: names of variables should start with a lower-case letter.") NORMAL (L"") NORMAL (L"#Question: why do names of variables have to start with a lower-case letter? " "I would like to do things like \"F0 = Get mean pitch\".") NORMAL (L"Answer: Praat scripts combine button commands with things that only occur " "in scripts. Button commands always start with a capital letter, e.g. \"Play\". " "Script command always start with lower case, e.g. \"echo Hello\". " "A minimal pair is \"select\", which simulates a mouse click in the object list, " "versus \"Select...\", which sets the selection in editor windows. Variable names " "that start with a capital letter would be rather ambiguous in assignments, " "as in \"x = Get\", where \"Get\" would be a variable, versus \"x = Get mean\", " "where \"Get mean\" is a button command. To prevent this, Praat enforces " "a rigorous lower-case/upper-case distinction.") NORMAL (L"") NORMAL (L"#Question: how do I convert a number into a string?") NORMAL (L"Answer: a\\$ = \"'a'\"") NORMAL (L"#Question: how do I convert a string into a number?") NORMAL (L"Answer: a = 'a\\$ '") MAN_END MAN_BEGIN (L"FAQ: Spectrograms", L"ppgb", 20030916) NORMAL (L"#Problem: the background is grey instead of white (too little contrast)") NORMAL (L"Solution: reduce the \"dynamic range\" in the spectrogram settings. The standard value is 50 dB, " "which is fine for detecting small things like plosive voicing in well recorded speech. " "For gross features like vowel formants, or for noisy speech, you may want to change the dynamic range " "to 40 or even 30 dB.") MAN_END MAN_BEGIN (L"File menu", L"ppgb", 20021204) INTRO (L"One of the menus in all @editors, in the @manual, and in the @@Picture window@.") MAN_END MAN_BEGIN (L"Filtering", L"ppgb", 20100324) INTRO (L"This tutorial describes the use of filtering techniques in Praat. " "It assumes you are familiar with the @Intro.") ENTRY (L"Frequency-domain filtering") NORMAL (L"Modern computer techniques make possible an especially simple batch filtering method: " "multiplying the complex spectrum in the frequency domain by any real-valued filter function. " "This leads to a zero phase shift for each frequency component. The impulse response is symmetric " "in the time domain, which also means that the filter is %acausal: the filtered signal will show components " "before they start in the original.") LIST_ITEM (L"\\bu @@Spectrum: Filter (pass Hann band)...@") LIST_ITEM (L"\\bu @@Spectrum: Filter (stop Hann band)...@") LIST_ITEM (L"\\bu @@Sound: Filter (pass Hann band)...@") LIST_ITEM (L"\\bu @@Sound: Filter (stop Hann band)...@") LIST_ITEM (L"\\bu @@Sound: Filter (formula)...@") NORMAL (L"Spectro-temporal:") LIST_ITEM (L"\\bu @@band filtering in the frequency domain@") ENTRY (L"Fast time-domain filtering") NORMAL (L"Some very fast Infinite Impulse Response (IIR) filters can be defined in the time domain. " "These include recursive all-pole filters and pre-emphasis. These filters are causal but have non-zero phase shifts. " "There are versions that create new Sound objects:") LIST_ITEM (L"\\bu @@Sound: Filter (one formant)...@") LIST_ITEM (L"\\bu @@Sound: Filter (pre-emphasis)...@") LIST_ITEM (L"\\bu @@Sound: Filter (de-emphasis)...@") NORMAL (L"And there are in-line versions, which modify the existing Sound objects:") LIST_ITEM (L"\\bu @@Sound: Filter with one formant (in-line)...@") LIST_ITEM (L"\\bu @@Sound: Pre-emphasize (in-line)...@") LIST_ITEM (L"\\bu @@Sound: De-emphasize (in-line)...@") ENTRY (L"Convolution") NORMAL (L"A Finite Impulse Response (FIR) filter can be described as a sampled sound. " "Filtering with such a filter amounts to a %#convolution of the original sound and the filter:") LIST_ITEM (L"\\bu @@Sounds: Convolve...@") ENTRY (L"Described elsewhere") NORMAL (L"Described in the @@Source-filter synthesis@ tutorial:") LIST_ITEM (L"\\bu @@Sound & Formant: Filter@") LIST_ITEM (L"\\bu @@Sound & FormantGrid: Filter@") LIST_ITEM (L"\\bu @@LPC & Sound: Filter...@") LIST_ITEM (L"\\bu @@LPC & Sound: Filter (inverse)@") MAN_END MAN_BEGIN (L"Formants & LPC menu", L"ppgb", 20011107) INTRO (L"A menu that occurs in the @@Dynamic menu@ for a @Sound.") NORMAL (L"This menu contains commands for analysing the formant contours of the selected Sound:") LIST_ITEM (L"@@Sound: To Formant (burg)...") LIST_ITEM (L"@@Sound: To Formant (keep all)...") LIST_ITEM (L"@@Sound: To Formant (sl)...") LIST_ITEM (L"@@Sound: To LPC (autocorrelation)...") LIST_ITEM (L"@@Sound: To LPC (covariance)...") LIST_ITEM (L"@@Sound: To LPC (burg)...") LIST_ITEM (L"@@Sound: To LPC (marple)...") LIST_ITEM (L"@@Sound: To MFCC...") MAN_END MAN_BEGIN (L"Get first formant", L"ppgb", 20011107) INTRO (L"One of the commands in the @@Query menu@ of the @SoundEditor and the @TextGridEditor.") MAN_END MAN_BEGIN (L"Get pitch", L"ppgb", 20010417) INTRO (L"One of the commands in the @@Query menu@ of the @SoundEditor and the @TextGridEditor.") MAN_END MAN_BEGIN (L"Get second formant", L"ppgb", 20011107) INTRO (L"One of the commands in the @@Query menu@ of the @SoundEditor and the @TextGridEditor.") MAN_END MAN_BEGIN (L"Goodies", L"ppgb", 20050822) INTRO (L"The title of a submenu of the @@Praat menu@.") MAN_END MAN_BEGIN (L"Info", L"ppgb", 19980101) INTRO (L"One of the fixed buttons in the @@Object window@.") ENTRY (L"Availability") NORMAL (L"You can choose this command after choosing one object.") ENTRY (L"Purpose") NORMAL (L"To get some information about the selected object.") ENTRY (L"Behaviour") NORMAL (L"The information will appear in the @@Info window@.") MAN_END MAN_BEGIN (L"Info window", L"ppgb", 20030528) INTRO (L"A text window into which many query commands write their answers.") NORMAL (L"You can select text from this window and copy it to other places.") NORMAL (L"In a @@Praat script@, you can bypass the Info window by having a query command " "writing directly into a script variable.") NORMAL (L"Apart from the @Info command, which writes general information about the selected object, " "the following more specific commands also write into the Info window:") MAN_END MAN_BEGIN (L"Inspect", L"ppgb", 19960904) INTRO (L"One of the fixed buttons in the @@Object window@.") NORMAL (L"You can use this command after selecting one object in the list.") NORMAL (L"The contents of the selected object will become visible in a Data Editor. " "You can then view and change the data in the object, " "but beware: changing the data directly in this way may render them inconsistent.") NORMAL (L"Changes that you make to the data with another Editor (e.g., a SoundEditor), " "or with the commands under #%Modify, " "are immediately reflected in the top-level Data Editor; " "any subeditors are destroyed, however, because they may now refer to invalid data.") NORMAL (L"Changes that you make to the data with a Data Editor, " "are immediately reflected in any open type-specific Editors (e.g., a SoundEditor).") MAN_END MAN_BEGIN (L"Intro", L"ppgb", 20110131) INTRO (L"This is an introductory tutorial to Praat, a computer program " "with which you can analyse, synthesize, and manipulate speech, " "and create high-quality pictures for your articles and thesis. " "You are advised to work through all of this tutorial.") NORMAL (L"You can read this tutorial sequentially with the help of the \"1 >\" and \"< 1\" buttons, " "or go to the desired information by clicking on the blue links.") LIST_ITEM (L"@@Intro 1. How to get a sound@: " "@@Intro 1.1. Recording a sound|record@, " "@@Intro 1.2. Reading a sound from disk|read@, " "@@Intro 1.3. Creating a sound from a formula|formula@.") LIST_ITEM (L"@@Intro 2. What to do with a sound@: " "@@Intro 2.1. Saving a sound to disk|write@, " "@@Intro 2.2. Viewing and editing a sound|view@.") LIST_ITEM (L"@@Intro 3. Spectral analysis") LIST_ITEM1 (L"spectrograms: @@Intro 3.1. Viewing a spectrogram|view@, " "@@Intro 3.2. Configuring the spectrogram|configure@, " "@@Intro 3.3. Querying the spectrogram|query@, " "@@Intro 3.4. Printing the spectrogram|print@, " "@@Intro 3.5. The Spectrogram object|the Spectrogram object@.") LIST_ITEM1 (L"spectral slices: @@Intro 3.6. Viewing a spectral slice|view@, " "@@Intro 3.7. Configuring the spectral slice|configure@, " "@@Intro 3.8. The Spectrum object|the Spectrum object@.") LIST_ITEM (L"@@Intro 4. Pitch analysis") LIST_ITEM1 (L"pitch contours: @@Intro 4.1. Viewing a pitch contour|view@, " "@@Intro 4.2. Configuring the pitch contour|configure@, " "@@Intro 4.3. Querying the pitch contour|query@, " "@@Intro 4.4. Printing the pitch contour|print@, " "@@Intro 4.5. The Pitch object|the Pitch object@.") LIST_ITEM (L"@@Intro 5. Formant analysis") LIST_ITEM1 (L"formant contours: @@Intro 5.1. Viewing formant contours|view@, " "@@Intro 5.2. Configuring the formant contours|configure@, " "@@Intro 5.3. Querying the formant contours|query@, " "@@Intro 5.4. The Formant object|the Formant object@.") LIST_ITEM (L"@@Intro 6. Intensity analysis") LIST_ITEM1 (L"intensity contours: @@Intro 6.1. Viewing an intensity contour|view@, " "@@Intro 6.2. Configuring the intensity contour|configure@, " "@@Intro 6.3. Querying the intensity contour|query@, " "@@Intro 6.4. The Intensity object|the Intensity object@.") LIST_ITEM (L"@@Intro 7. Annotation") LIST_ITEM (L"@@Intro 8. Manipulation@: of " "@@Intro 8.1. Manipulation of pitch|pitch@, " "@@Intro 8.2. Manipulation of duration|duration@, " "@@Intro 8.3. Manipulation of intensity|intensity@, " "@@Intro 8.4. Manipulation of formants|formants@.") NORMAL (L"There are also more specialized tutorials:") LIST_ITEM (L"Phonetics:") LIST_ITEM1 (L"\\bu Voice analysis (jitter, shimmer, noise): @Voice") LIST_ITEM1 (L"\\bu Listening experiments: @@ExperimentMFC@") LIST_ITEM1 (L"\\bu @@Sound files@") LIST_ITEM1 (L"\\bu @@Filtering@") LIST_ITEM1 (L"\\bu @@Source-filter synthesis@") LIST_ITEM1 (L"\\bu @@Articulatory synthesis@") LIST_ITEM (L"Learning:") LIST_ITEM1 (L"\\bu @@Feedforward neural networks@") LIST_ITEM1 (L"\\bu @@OT learning@") LIST_ITEM (L"Statistics:") LIST_ITEM1 (L"\\bu @@Principal component analysis@") LIST_ITEM1 (L"\\bu @@Multidimensional scaling@") LIST_ITEM1 (L"\\bu @@Discriminant analysis@") LIST_ITEM (L"General:") LIST_ITEM1 (L"\\bu @@Printing@") LIST_ITEM1 (L"\\bu @@Scripting@") LIST_ITEM1 (L"\\bu @@Demo window@") ENTRY (L"The authors") NORMAL (L"The Praat program was created by Paul Boersma and David Weenink of " "the Institute of Phonetics Sciences of the University of Amsterdam. " "Home page: ##http://www.praat.org# or ##http://www.fon.hum.uva.nl/praat/#.") NORMAL (L"For questions and suggestions, mail to the Praat discussion list, " "which is reachable from the Praat home page, or directly to ##paul.boersma\\@ uva.nl#.") MAN_END MAN_BEGIN (L"Intro 1. How to get a sound", L"ppgb", 20021212) INTRO (L"Most of the things most people do with Praat start with a sound. " "There are at least three ways to get a sound:") LIST_ITEM (L"@@Intro 1.1. Recording a sound") LIST_ITEM (L"@@Intro 1.2. Reading a sound from disk") LIST_ITEM (L"@@Intro 1.3. Creating a sound from a formula") MAN_END MAN_BEGIN (L"Intro 1.1. Recording a sound", L"ppgb", 20110128) #ifdef macintosh INTRO (L"To record a speech sound into Praat, you need a computer with a microphone.") NORMAL (L"To record from the microphone, perform the following steps:") #else INTRO (L"To record a speech sound into Praat, you need a computer with a microphone. " "If you do not have a microphone, try to record from an audio CD instead.") NORMAL (L"To record from the microphone (or the CD), perform the following steps:") #endif LIST_ITEM (L"1. Choose @@Record mono Sound...@ from the @@New menu@ in the @@Object window@. " "A @SoundRecorder window will appear on your screen.") #if defined (_WIN32) LIST_ITEM (L"2. Choose the appropriate input device, namely the microphone, by the following steps. " "If there is a small loudspeaker symbol in the Windows Start bar, double click it and you will see the %playing mixer. " "If there is no loudspeaker symbol, go to ##Control Panels#, then ##Sounds and Audio Devices#, then #Volume, then #Advanced, " "and you will finally see the playing mixer. " "Once you see the Windows playing mixer, choose #Properties from the #Option menu, " "then click #Recording, then #OK. You now see the %recording mixer, where you can select the microphone " "(if you do not like this complicated operation, try Praat on Macintosh or Linux instead of Windows).") #elif defined (macintosh) LIST_ITEM (L"2. In the SoundRecorder window, choose the appropriate input device, e.g. choose ##Internal microphone#.") #else LIST_ITEM (L"2. In the SoundRecorder window, choose the appropriate input device, i.e. choose #Microphone (or #CD, or #Line).") #endif #ifdef macintosh LIST_ITEM (L"3. Use the #Record and #Stop buttons to record a few seconds of your speech.") #else LIST_ITEM (L"3. Use the #Record and #Stop buttons to record a few seconds of your speech " "(or a few seconds of music from your playing CD).") #endif LIST_ITEM (L"4. Use the #Play button to hear what you have recorded.") LIST_ITEM (L"5. Repeat steps 3 and 4 until you are satisfied with your recording.") LIST_ITEM (L"6. Click the ##Save to list# button. Your recording will now appear in the Object window, " "where it will be called \"Sound sound\".") LIST_ITEM (L"7. You can now close the SoundRecorder window.") LIST_ITEM (L"8. When you saved your sound to the Object window, some buttons appeared in that window. " "These buttons show you what you can do with the sound. Try the #Play and @@View & Edit@ buttons.") NORMAL (L"For more information on recording, see the @SoundRecorder manual page.") MAN_END MAN_BEGIN (L"Intro 1.2. Reading a sound from disk", L"ppgb", 20041126) INTRO (L"Apart from recording a new sound from a microphone, you could read an existing sound file from your disk.") NORMAL (L"With @@Read from file...@ from the @@Open menu@, " "Praat will be able to read most standard types of sound files, e.g. WAV files. " "They will appear as @Sound objects in the Object window. For instance, if you open the file ##hello.wav#, " "an object called \"Sound hello\" will appear in the list.") NORMAL (L"If you do not have a sound file on your disk, you can download a WAV file (or so) from the Internet, " "then read that file into Praat with ##Read from file...#.") MAN_END MAN_BEGIN (L"Intro 1.3. Creating a sound from a formula", L"ppgb", 20070225) INTRO (L"If you have no microphone, no sound files on disk, and no access to the Internet, " "you could still create a sound with @@Create Sound from formula...@ from the @@New menu@.") MAN_END MAN_BEGIN (L"Intro 2. What to do with a sound", L"ppgb", 20110131) INTRO (L"As soon as you have a @Sound in the @@List of Objects@, " "the buttons in the @@Dynamic menu@ (the right-hand part of the @@Object window@) " "will show you what you can do with it.") LIST_ITEM (L"@@Intro 2.1. Saving a sound to disk") LIST_ITEM (L"@@Intro 2.2. Viewing and editing a sound") MAN_END MAN_BEGIN (L"Intro 2.1. Saving a sound to disk", L"ppgb", 20110131) INTRO (L"There are several ways to write a sound to disk.") NORMAL (L"First, the @@File menu@ of the @SoundRecorder window contains commands to save the left " "channel, the right channel, or both channels of the recorded sound to any of four standard types " "of sound files (WAV, AIFC, NeXT/Sun, NIST). These four file types are all equally good for Praat: " "Praat will handle them equally well on every computer. The first three of these types will " "also be recognized by nearly all other sound-playing programs.") NORMAL (L"Then, once you have a @Sound object in the @@List of Objects@, " "you can save it in several formats with the commands in the @@Save menu@. " "Again, the WAV, AIFF, AIFC, NeXT/Sun, and NIST formats are equally fine.") NORMAL (L"For more information, see the @@Sound files@ tutorial.") MAN_END MAN_BEGIN (L"Intro 2.2. Viewing and editing a sound", L"ppgb", 20110212) NORMAL (L"To see the wave form of a @Sound that is in the list of objects, " "select that Sound and click @@View & Edit@. A @SoundEditor window will appear on your screen. " "You see a waveform (or two waveforms, if you have a stereo sound) and probably some \"analyses\" below it. " "You can zoom in and scroll to see the various parts of the sound in detail. " "You can select a part of the sound by dragging with the mouse. " "To play a part of the sound, click on any of the rectangles below it. " "To move a selected part of the sound to another location, use #Cut and #Paste from the #Edit menu. " "You can open sound windows for more than one sound, and then cut, copy, and paste between the sounds, " "just as you are used to do with text and pictures in word processing programs.") NORMAL (L"If your sound file is longer than a couple of minutes, " "or if you want to see and listen to both channels of a stereo sound, " "you may prefer to open it with @@Open long sound file...@. " "This puts a @LongSound object into the list. In this way, most of the sound will stay in the file on disk, " "and at most 60 seconds will be read into memory each time you play or view a part of it. " "To change these 60 seconds to something else, e.g. 500 seconds, choose ##LongSound prefs...# from the #Preferences submenu.") MAN_END MAN_BEGIN (L"Intro 3. Spectral analysis", L"ppgb", 20070905) INTRO (L"This section describes how you can analyse the spectral content of an existing sound. " "You will learn how to use %spectrograms and %%spectral slices%.") LIST_ITEM (L"@@Intro 3.1. Viewing a spectrogram") LIST_ITEM (L"@@Intro 3.2. Configuring the spectrogram") LIST_ITEM (L"@@Intro 3.3. Querying the spectrogram") LIST_ITEM (L"@@Intro 3.4. Printing the spectrogram") LIST_ITEM (L"@@Intro 3.5. The Spectrogram object") LIST_ITEM (L"@@Intro 3.6. Viewing a spectral slice") LIST_ITEM (L"@@Intro 3.7. Configuring the spectral slice") LIST_ITEM (L"@@Intro 3.8. The Spectrum object") MAN_END MAN_BEGIN (L"Intro 3.1. Viewing a spectrogram", L"ppgb", 20110128) INTRO (L"To see the spectral content of a sound as a function of time, " "select a @Sound or @LongSound object and choose @@View & Edit@. " "A @SoundEditor or @LongSoundEditor window will appear on your screen. " "In the entire bottom half of this window you will see a greyish image, which is called a %spectrogram. " "If you do not see it, choose @@Show spectrogram@ from the #Spectrogram menu.") NORMAL (L"The spectrogram is a @@spectro-temporal representation@ of the sound. " "The horizontal direction of the spectrogram represents @time, the vertical direction represents @frequency. " "The time scale of the spectrogram is the same as that of the waveform, so the spectrogram reacts " "to your zooming and scrolling. " "To the left of the spectrogram, you see the frequency scale. The frequency at the bottom of the spectrogram " "is usually 0 Hz (hertz, cps, cycles per second), and a common value for the frequency at the top is 5000 Hz.") NORMAL (L"Darker parts of the spectrogram mean higher energy densities, lighter parts mean lower energy densities. " "If the spectrogram has a dark area around a time of 1.2 seconds and a frequency of 4000 Hz, " "this means that the sound has lots of energy for those high frequencies at that time. " "For many examples of spectrograms of speech sounds, see the textbook by @@Ladefoged (2001)@ and " "the reference work by @@Ladefoged & Maddieson (1996)@.") NORMAL (L"To see what time and frequency a certain part of the spectrogram is associated with, " "just click on the spectrogram and you will see the vertical time cursor showing the time above " "the waveform and the horizontal frequency cursor showing the frequency to the left of the spectrogram. " "This is one of the ways to find the %formant frequencies for vowels, or the main spectral peaks " "for fricatives.") ENTRY (L"Hey, there are white vertical stripes at the edges!") NORMAL (L"This is normal. Spectral analysis requires an %%analysis window% of a certain duration. " "For instance, if Praat wants to know the spectrum at 1.342 seconds, it needs to include information " "about the signal in a 10-milliseconds window around this time point, i.e., Praat will use " "signal information about all times between 1.337 and 1.347 seconds. At the very edges of the sound, " "this information is not available: " "if the sound runs from 0 to 1.8 seconds, no spectrum can be computed between 0 and 0.005 " "seconds or between 1.795 and 1.800 seconds. Hence the white stripes. If you do not see them " "immediately when you open the sound, zoom in on the beginning or end of the sound.") NORMAL (L"When you zoom in on the middle of the sound (or anywhere not near the edges), the white stripes vanish. " "Suddenly you see only the time stretch between 0.45 and 1.35 seconds, for instance. " "But Praat did not forget what the signal looks like just outside the edges of this time window. " "To display a spectrogram from 0.45 to 1.35 seconds, Praat will use information from the wave form " "between 0.445 and 1.355 seconds, and if this is available, you will see no white stripes at the edges of the window.") ENTRY (L"Hey, it changes when I scroll!") NORMAL (L"This is normal as well, especially for long windows. If your visible time window is 20 seconds long, " "and the window takes up 1000 screen pixels horizontally, " "then you might think that every one-pixel-wide vertical line should represent the spectrum of 20 milliseconds of sound. " "But for reasons of computation speed, Praat will only show the spectrum of the part of the sound " "that lies around the centre of those 20 milliseconds, " "not the average or sum of all the spectra in those 20 milliseconds. " "This %undersampling of the underlying spectrogram is different from what happens in the drawing of the wave form, " "where a vertical black line connects the minimum and maximum amplitude of all the samples that fall inside a " "screen pixel. We cannot do something similar for spectrograms. And since scrolling goes by fixed time steps " "(namely, 5 percent of the duration of the visible window), rather than by a whole number of screen pixels, " "the centres of the pixels will fall in different parts of the spectrogram with each scroll. " "Hence the apparent changes. If your visible window is shorter than a couple of seconds, " "the scrolling spectrogram will appear much smoother.") NORMAL (L"The darkness of the spectrogram will also change when you scroll, because the visible part with the most " "energy is defined as black. When a very energetic part of the signal scrolls out of view, the spectrogram " "will turn darker. The next section will describe a way to switch this off.") MAN_END MAN_BEGIN (L"Intro 3.2. Configuring the spectrogram", L"ppgb", 20110128) NORMAL (L"With @@Spectrogram settings...@ from the #Spectrogram menu, " "you can determine how the spectrogram is computed and how it is displayed. " "These settings will be remembered across Praat sessions. " "All these settings have standard values (\"factory settings\"), which appear " "when you click ##Standards#.") TAG (L"%%View range% (Hz)") DEFINITION (L"the range of frequencies to display. The standard is 0 Hz at the bottom and 5000 Hz at the top. " "If this maximum frequency is higher than the Nyquist frequency of the Sound " "(which is half its sampling frequency), some values in the spectrogram will be zero, and the higher " "frequencies will be drawn in white. You can see this if you record a Sound at 44100 Hz and set the " "view range from 0 Hz to 25000 Hz.") TAG (L"%%Window length") DEFINITION (L"the duration of the analysis window. If this is 0.005 seconds (the standard), " "Praat uses for each frame the part of the sound that lies between 0.0025 seconds before " "and 0.0025 seconds after the centre of that frame " "(for Gaussian windows, Praat actually uses a bit more than that). " "The window length determines the %bandwidth of the spectral analysis, " "i.e. the width of the horizontal line in the spectrogram of a pure sine wave (see below). " "For a Gaussian window, the -3 dB bandwidth is 2*sqrt(6*ln(2))/(\\pi*%%Window length%), " "or 1.2982804 / %%Window length%. " "To get a `broad-band' spectrogram (bandwidth 260 Hz), keep the standard window length of 5 ms; " "to get a `narrow-band' spectrogram (bandwidth 43 Hz), set it to 30 ms (0.03 seconds). " "The other window shapes give slightly different values.") TAG (L"%%Dynamic range% (dB)") DEFINITION (L"All values that are more than %%Dynamic range% dB below the maximum (perhaps after dynamic compression, " "see @@Advanced spectrogram settings...@) " "will be drawn in white. Values in-between have appropriate shades of grey. Thus, if the highest " "peak in the spectrogram has a height of 30 dB/Hz, and the dynamic range is 50 dB (which is the standard value), " "then values below -20 dB/Hz will be drawn in white, and values between -20 dB/Hz and 30 dB/Hz will be drawn " "in various shades of grey.") ENTRY (L"The bandwidth") NORMAL (L"To see how the window length influences the bandwidth, " "first create a 1000-Hz sine wave with @@Create Sound from formula...@ " "by typing $$1/2 * sin (2*pi*1000*x)$ as the formula, then click ##View & Edit#. " "The spectrogram will show a horizontal black line. " "You can now vary the window length in the spectrogram settings and see how the thickness " "of the lines varies. The line gets thinner if you raise the window length. " "Apparently, if the analysis window comprises more periods of the wave, " "the spectrogram can tell us the frequency of the wave with greater precision.") NORMAL (L"To see this more precisely, create a sum of two sine waves, with frequencies of 1000 and 1200 Hz. " "the formula is $$1/4 * sin (2*pi*1000*x) + 1/4 * sin (2*pi*1200*x)$. In the editor, you will see " "a single thick band if the analysis window is short (5 ms), and two separate bands if the analysis " "window is long (30 ms). Apparently, the frequency resolution gets better with longer analysis windows.") NORMAL (L"So why don't we always use long analysis windows? The answer is that their time resolution is poor. " "To see this, create a sound that consists of two sine waves and two short clicks. The formula is " "$$0.02*(sin(2*pi*1000*x)+sin(2*pi*1200*x)) + (col=10000)+(col=10200)$. " "If you view this sound, you can see that the two clicks will overlap " "in time if the analysis window is long, and that the sine waves overlap in frequency if the " "analysis window is short. Apparently, there is a trade-off between time resolution and " "frequency resolution. One cannot know both the time and the frequency with great precision.") ENTRY (L"Advanced settings") NORMAL (L"The Spectrum menu also contains @@Advanced spectrogram settings...@.") MAN_END MAN_BEGIN (L"Advanced spectrogram settings...", L"ppgb", 20110128) ENTRY (L"Optimization") TAG (L"%%Number of time steps%") DEFINITION (L"the maximum number of points along the time window for which Praat has to compute " "the spectrum. If your screen is not wider than 1200 pixels, then the standard of 1000 is " "appropriate, since there is no point in computing more than one spectrum per one-pixel-wide vertical line. " "If you have a really wide screen, you may see improvement if you raise this number to 1500.") TAG (L"%%Number of frequency steps%") DEFINITION (L"the maximum number of points along the frequency axis for which Praat has to compute " "the spectrum. If your screen is not taller than 768 pixels, then the standard of 250 is " "appropriate, since there is no point in computing more than one spectrum per one-pixel-height horizontal line. " "If you have a really tall screen, you may see improvement if you raise this number.") NORMAL (L"For purposes of computation speed, Praat may decide to change the time step and the frequency step. " "This is because the time step never needs to be smaller than 1/(8\\Vr\\pi) of the window length, " "and the frequency step never needs to be smaller than (\\Vr\\pi)/8 of the inverse of the window length. " "For instance, if the window length is 30 ms, " "the actual time step will never be less than 30/(8\\Vr\\pi) = 2.116 ms. " "And if the window length is 5 ms, " "the actual frequency step will never be less than (\\Vr\\pi)/8/0.005 = 44.32 Hz.") ENTRY (L"Spectrogram analysis settings") TAG (L"%%Method") DEFINITION (L"there is currently only one method available in this window for computing a spectrum from " "a sound: the Fourier transform.") TAG (L"%%Window shape") DEFINITION (L"the shape of the analysis window. To compute the spectrum at, say, 3.850 seconds, " "samples that lie close to 3.850 seconds are given more weight than samples further away. " "The relative extent to which each sample contributes to the spectrum is given by the window shape. " "You can choose from: Gaussian, Square (none, rectangular), Hamming (raised sine-squared), " "Bartlett (triangular), Welch (parabolic), and Hanning (sine-squared). " "The Gaussian window is superior, as it gives no %sidelobes in your spectrogram (see below); " "it analyzes a factor of 2 slower than the other window shapes, " "because the analysis is actually performed on twice as many samples per frame.") ENTRY (L"Sidelobes; anybody wants to win a cake?") NORMAL (L"The Gaussian window is the only shape that we can consider seriously as a candidate for " "the analysis window. To see this, create a 1000-Hz sine wave with @@Create Sound from formula...@ " "by typing $$1/2 * sin (2*pi*1000*x)$ as the formula, then click ##View & Edit#. " "If the window shape is Gaussian, the spectrogram will show a horizontal black line. " "If the window shape is anything else, the spectrogram will show many horizontal grey lines (%sidelobes), " "which do not represent anything that is available in the signal. They are artifacts of the " "window shapes.") NORMAL (L"We include these other window shapes only for pedagogical purposes " "and because the Hanning and Hamming windows have traditionally been used in other programs before " "computers were as fast as they are now (a spectrogram is computed twice as fast " "with these other windows). Several other programs still use these inferior window shapes, and you are " "likely to run into people who claim that the Gaussian window has disadvantages. " "We promise such people a large cake if they can come up with sounds that look better " "with Hanning or Hamming windows than with a Gaussian window. An example of the reverse is easy " "to find; we have just seen one.") ENTRY (L"Spectrogram blackness settings") TAG (L"%%Autoscaling%") TAG (L"%%Maximum% (dB/Hz)") DEFINITION (L"all parts of the spectrogram that have a power above %maximum (after preemphasis) " "will be drawn in black. The standard maximum is 100 dB/Hz, but if %autoscaling is on (which is the standard), " "Praat will use the maximum of the visible part of the spectrogram instead; " "this ensures that the window will always look well, but it also means that the blackness " "of a certain part of the spectrogram will change as you scroll.") TAG (L"%%Preemphasis% (dB/octave)") DEFINITION (L"determines the steepness of a high-pass filter, " "i.e., how much the power of higher frequencies will be raised before drawing, as compared to lower frequencies. " "Since the spectral slope of human vowels is approximately -6 dB per octave, " "the standard value for this setting is +6 dB per octave, " "so that the spectrum is flattened and the higher formants look as strong as the lower ones. " "When you raise the preemphasis, frequency bands above 1000 Hz will become darker, those below 1000 Hz will become lighter.") TAG (L"%%Dynamic compression") DEFINITION (L"determines how much stronger weak spectra should be made before drawing. " "Normally, this parameter is between 0 and 1. If it is 0 (the standard value), there is no dynamic compression. " "If it is 1, all spectra will be drawn equally strong, " "i.e., all of them will contain frequencies that are drawn in black. " "If this parameter is 0.4 and the global maximum is at 80 dB, then a spectrum with a maximum at 20 dB " "(which will normally be drawn all white if the dynamic range is 50 dB), " "will be raised by 0.4 * (80 - 20) = 24 dB, " "so that its maximum will be seen at 44 dB (thus making this frame visible).") MAN_END MAN_BEGIN (L"Intro 3.3. Querying the spectrogram", L"ppgb", 20030403) NORMAL (L"If you click anywhere inside the spectrogram, a cursor cross will appear, " "and you will see the time and frequency in red at the top and to the left of the window. " "To see the time in the Info window, " "choose ##Get cursor# from the #Query menu or press the F6 key. " "To see the frequency in the Info window, " "choose ##Get frequency# from the #Spectrum menu.") NORMAL (L"To query the power of the spectrogram at the cursor cross, " "choose ##Get spectral power at cursor cross# from the #Spectrum menu or press the F9 key. " "The Info window will show you the power density, expressed in Pascal^2/Hz.") MAN_END MAN_BEGIN (L"Intro 3.4. Printing the spectrogram", L"ppgb", 20070905) NORMAL (L"To print a spectrogram, or to put it in an EPS file or on the clipboard for inclusion in your word processor, " "you first have to paint it into the @@Picture window@. " "You do this by choosing ##Paint visible spectrogram...# " "from the Spectrum menu in the Sound or TextGrid window. " "From the File menu in the Picture window, you can then print it, save it to an EPS file, " "or copy it to the clipboard (to do Paste in your word processor, for instance).") MAN_END MAN_BEGIN (L"Intro 3.5. The Spectrogram object", L"ppgb", 20070905) NORMAL (L"To do more with spectrograms, you can create a @Spectrogram object in the @@List of Objects@. " "You do this either by choosing ##Extract visible spectrogram# " "from the Spectrum menu in the Sound or TextGrid window, " "or by selecting a Sound object in the list and choosing @@Sound: To Spectrogram...@ from the #Spectrum menu. " "In either case, a new Spectrogram object will appear in the list. " "To draw this Spectrogram object to the @@Picture window@, " "select it and choose the @@Spectrogram: Paint...@ command. " "From the Picture window, you can print it, save it to an EPS file, or copy it to the clipboard. " "Many other commands are available in the @@dynamic menu@.") MAN_END MAN_BEGIN (L"Intro 3.6. Viewing a spectral slice", L"ppgb", 20030316) INTRO (L"With ##View spectral slice# from the #Spectrum menu in the @SoundEditor and the @TextGridEditor, " "you can see the frequency spectrum at the time cursor " "or the average frequency spectrum in the time selection.") ENTRY (L"Spectral slice at the cursor") NORMAL (L"If you click anywhere in the wave form of the SoundEditor or TextGridEditor windows, " "a cursor will appear at that time. If you then choose ##View spectral slice#, " "Praat will create a @Spectrum object named %slice in the Objects window and show it in a @SpectrumEditor window. " "In this way, you can inspect the frequency contents of the signal around the cursor position.") ENTRY (L"Spectral slice from a selection") NORMAL (L"If you drag the mouse through the wave form of the SoundEditor or TextGridEditor windows, " "a @@time selection@ will appear. If you then choose ##View spectral slice#, " "Praat will again create a @Spectrum object named %slice in the Objects window and show it in a @SpectrumEditor window. " "In this way, you can inspect the frequency contents of the signal in the selection.") MAN_END MAN_BEGIN (L"Intro 3.7. Configuring the spectral slice", L"ppgb", 20110128) ENTRY (L"Spectral slice at the cursor") NORMAL (L"What Praat does precisely, depends on your Spectrogram settings. " "Suppose that the %%window length% setting is 0.005 seconds (5 milliseconds). " "If the %%window shape% is not Gaussian, Praat will extract the part of the sound " "that runs from 2.5 milliseconds before the cursor to 2.5 ms after the cursor. " "Praat then multiplies this 5 ms long signal by the window shape, then computes a spectrum " "with the method of @@Sound: To Spectrum...@, which is put into the Objects window and opened in an editor window. " "If the window shape is Gaussian, Praat will extract a part of the sound " "that runs from 5 milliseconds before the cursor to 5 ms after the cursor. The spectrum will then be based " "on a `physical' window length of 10 ms, although the `effective' window length is still 5 ms " "(see @@Intro 3.2. Configuring the spectrogram@ for details).") ENTRY (L"Spectral slice from a selection") NORMAL (L"What Praat does precisely, again depends on the %%window shape% of your Spectrogram settings. " "Suppose that your selection is 50 ms long. Praat will extract the entire selection, " "then multiply this 50 ms long signal by the window shape, then compute a spectrum, put it into the Objects window and open it an editor window. " "This procedure is equivalent to choosing ##Extract windowed selection...# (with a %%relative duration% of 1.0), " "followed by ##To Spectrum...# (with %fast switched on), followed by #Edit.") NORMAL (L"If the window is Gaussian, Praat will still only use the selection, without doubling its duration. " "This means that the spectrum that you see in this case will mainly be based on the centre half of the selection, " "and the signal near the edges will be largely ignored.") MAN_END MAN_BEGIN (L"Intro 3.8. The Spectrum object", L"ppgb", 20030403) NORMAL (L"To compute a Fourier frequency spectrum of an entire sound, " "select a @Sound object and choose @@Sound: To Spectrum...|To Spectrum...@ from the #Spectrum menu. " "A new @Spectrum object will appear in the @@List of Objects@. " "To view or modify it (or listen to its parts), click @@View & Edit@. " "To print it, choose one of the #Draw commands to draw the Spectrum object to the @@Picture window@ first.") MAN_END MAN_BEGIN (L"Intro 4. Pitch analysis", L"ppgb", 20070905) INTRO (L"This section describes how you can analyse the pitch contour of an existing sound.") LIST_ITEM (L"@@Intro 4.1. Viewing a pitch contour") LIST_ITEM (L"@@Intro 4.2. Configuring the pitch contour") LIST_ITEM (L"@@Intro 4.3. Querying the pitch contour") LIST_ITEM (L"@@Intro 4.4. Printing the pitch contour") LIST_ITEM (L"@@Intro 4.5. The Pitch object") MAN_END MAN_BEGIN (L"Intro 4.1. Viewing a pitch contour", L"ppgb", 20110128) NORMAL (L"To see the pitch contour of an existing sound as a function of time, " "select a @Sound or @LongSound object and choose @@View & Edit@. " "A @SoundEditor window will appear on your screen. " "The bottom half of this window will contain a pitch contour, drawn as a blue line or as a sequence of blue dots. " "If you do not see the pitch contour, choose @@Show pitch@ from the #Pitch menu.") NORMAL (L"To the right of the window, you may see three pitch values, written with blue digits: " "at the bottom, you see the floor of the viewable pitch range, perhaps 75 Hz; at the top, " "you see the ceiling of the pitch range, perhaps 600 Hz; and somewhere in between, you see the pitch value " "at the cursor, or the average pitch in the selection.") MAN_END MAN_BEGIN (L"Intro 4.2. Configuring the pitch contour", L"ppgb", 20050830) NORMAL (L"With @@Pitch settings...@ from the #Pitch menu, " "you can determine how the pitch contour is displayed and how it is computed. " "These settings will be remembered across Praat sessions. " "All these settings have standard values (\"factory settings\"), which appear " "when you click #Standards.") ENTRY (L"The %%pitch range% setting") NORMAL (L"This is the most important setting for pitch analysis. The standard range is from 75 to 500 hertz, " "which means that the pitch analysis method will only find values between 75 and 500 Hz. " "The range that you set here will be shown to the right of the analysis window.") NORMAL (L"For a male voice, you may want to set the floor to 75 Hz, and the ceiling to 300 Hz; " "for a female voice, set the range to 100-500 Hz instead. For creaky voice you will want to set it much " "lower than 75 Hz.") NORMAL (L"Here is why you have to supply these settings. If the pitch floor is 75 Hz, " "the pitch analysis method requires a 40-millisecond analysis window, " "i.e., in order to measure the F0 at a time of, say, 0.850 seconds, " "Praat needs to consider a part of the sound that runs from 0.830 to 0.870 seconds. " "These 40 milliseconds correspond to 3 maximum pitch periods (3/75 = 0.040). " "If you set the pitch floor down to 25 Hz, the analysis window will grow to 120 milliseconds " "(which is again 3 maximum pitch periods), i.e., all times between 0.790 and 0.910 seconds will be considered. " "This makes it less easy to see fast F0 changes.") NORMAL (L"So setting the floor of the pitch range is a technical requirement for the pitch analysis. " "If you set it too low, you will miss very fast F0 changes, and if you set it too high, " "you will miss very low F0 values. For children's voices you can often use 200 Hz, " "although 75 Hz will still give you the same time resolution as you get for the males.") ENTRY (L"The %units setting") NORMAL (L"This setting determines the units of the vertical pitch scale. Most people like to see the pitch range " "in hertz, but there are several other possibilities.") ENTRY (L"Advanced settings") NORMAL (L"The Pitch menu also contains @@Advanced pitch settings...@.") MAN_END MAN_BEGIN (L"Time step settings...", L"ppgb", 20031003) INTRO (L"A command in the #View menu of the @SoundEditor and @TextGridEditor " "to determine the time interval between consecutive measurements " "of pitch, formants, and intensity.") ENTRY (L"Automatic time steps") NORMAL (L"It is recommended that you set the %%Time step strategy% to #Automatic. " "In this way, Praat computes just enough pitch, formant, and intensity values to draw " "reliable pitch, formant, and intensity contours. In general, Praat will compute 4 values " "within an analysis window (\"four times oversampling\").") NORMAL (L"As described in @@Sound: To Pitch...@, Praat's standard time step for pitch analysis is 0.75 divided by the pitch floor, " "e.g., if the pitch floor is 75 Hz, the time step will be 0.01 seconds. " "In this way, there will be 4 pitch measurements within an analysis window, which is 3 / (75 Hz) = 40 milliseconds long.") NORMAL (L"As described in @@Sound: To Formant (burg)...@, Praat's standard time step for formant measurements is the %%Window length% divided by 4, " "e.g. if the window length is 0.025 seconds, the time step will be 6.25 milliseconds.") NORMAL (L"As described in @@Sound: To Intensity...@, Praat's standard time step for intensity measurements is 0.8 divided by the pitch floor, " "e.g. if the pitch floor is 75 Hz, the time step will be 10.6666667 milliseconds. " "In this way, there will be 4 intensity measurements within an intensity analysis window, " "which is 3.2 / (75 Hz) = 42.6666667 milliseconds long.") ENTRY (L"Fixed time step") NORMAL (L"You can override the automatic time step by setting the %%Time step strategy% to #Fixed. " "The %%Fixed time step% setting then determines the time step that Praat will use: " "if you set it to 0.001 seconds, Praat will compute pitch, formant, and intensity values for every millisecond. " "Beware that this can slow down the editor window appreciably, because this step is much smaller " "than usual values of the automatic time step (see above).") NORMAL (L"Enlarging the time step to e.g. 0.1 seconds will speed up the editor window " "but may render the pitch, formant, and intensity curves less exact (they become %undersampled), " "which will influence your measurements and the locations of the pulses.") NORMAL (L"If there are fewer than 2.0 pitch measurement points per analysis window, " "Praat will draw the pitch curve as separate little blue disks " "rather than as a continuous blue curve, in order to warn you of the undersampling. " "E.g. if the pitch floor is 75 Hz, Praat will draw the pitch curve as disks if the time step is greater than 0.02 seconds.") ENTRY (L"View-dependent time step") NORMAL (L"Another way to override the standard time step is by setting the %%Time step strategy% to ##View-dependent#. " "The %%Number of time steps per view% setting then determines the time step that Praat will use: " "if you set it to 100, Praat will always compute 100 pitch, formant, and intensity values within the view window. " "More precisely: if you zoom the view window to 3 seconds, Praat will show you 100 pitch, formant, and intensity points at distances " "of 0.03 seconds (or fewer than 100, if you are near the left or right edge of the signal). " "As with the %%Fixed time step% setting, Praat will draw the pitch as separate disks in case of undersampling. " "You may want to use this setting if you want the pitch curve to be drawn equally fast independently of the degree " "of zooming.") MAN_END MAN_BEGIN (L"Advanced pitch settings...", L"ppgb", 20110808) INTRO (L"A command in the #Pitch menu of the @SoundEditor or @TextGridEditor windows. " "Before changing the advanced pitch settings, make sure you understand " "@@Intro 4.2. Configuring the pitch contour@.") ENTRY (L"View range different from analysis range") NORMAL (L"Normally, the range of pitch values that can be seen in the editor window is equal to the range of pitch values " "that the analysis algorithm can determine. If you set the analysis range from 75 to 500 Hz, this will be the range " "you see in the editor window as well. If the pitch values in the curve happen to be between 350 and 400 Hz, " "you may want to zoom in to the 350-400 Hz pitch region. " "You will usually do this by changing the pitch range in the @@Pitch settings...@ window. " "However, the analysis range will also change in that case, so that the curve itself may change. " "If you do not want that, you can change the %%View range% settings " "from \"0.0 (= auto)\" \\-- \"0.0 (=auto)\" to something else, perhaps \"350\" \\-- \"400\".") ENTRY (L"Pitch analysis settings") NORMAL (L"For information about these, see @@Sound: To Pitch (ac)...@. The standard settings are best in most cases. " "For some pathological voices, you will want to set the voicing threshold to much less than the standard of 0.45, " "in order to get pitch values even in irregular parts of the signal.") MAN_END MAN_BEGIN (L"Intro 4.3. Querying the pitch contour", L"ppgb", 20040614) NORMAL (L"With @@Get pitch@ from the #Pitch menu in the @SoundEditor or @TextGridEditor, " "you get information about the pitch at the cursor or in the selection. " "If a cursor is visible in the window, ##Get pitch# writes to the @@Info window@ " "the linearly interpolated pitch at that time; " "if a time selection is visible inside the window, ##Get pitch# writes to the @@Info window@ " "the mean (average) pitch in the visible part of that selection; " "otherwise, ##Get pitch# writes the average pitch in the visible part of the sound.") MAN_END MAN_BEGIN (L"Intro 4.4. Printing the pitch contour", L"ppgb", 20070905) NORMAL (L"To print a pitch contour, or to put it in an EPS file or on the clipboard for inclusion in your word processor, " "you first have to draw it into the @@Picture window@. " "You do this by choosing ##Draw visible pitch contour...# " "from the Pitch menu in the Sound or TextGrid window. " "From the File menu in the Picture window, you can then print it, save it to an EPS file, " "or copy it to the clipboard (to do Paste in your word processor, for instance).") MAN_END MAN_BEGIN (L"Intro 4.5. The Pitch object", L"ppgb", 20110128) NORMAL (L"The pitch contour that is visible in the @SoundEditor or @TextGridEditor window, " "can be copied as a separate @Pitch object to the @@List of Objects@. To do this, " "choose @@Extract visible pitch contour@ from the #Pitch menu.") NORMAL (L"Another way to get a separate Pitch object is to select a @Sound object in the list " "choose @@Sound: To Pitch...@ (preferred) or any of the other methods from the @@Periodicity menu@.") NORMAL (L"To view and modify the contents of a Pitch object, select it and choose @@View & Edit@. " "This creates a @PitchEditor window on your screen.") NORMAL (L"To save a pitch contour to disk, select the @Pitch object in the list and choose one of the commands in the @@Save menu@.") NORMAL (L"Later on, you can read the saved file again with @@Read from file...@ from the @@Open menu@.") NORMAL (L"To draw a @Pitch object to the @@Picture window@, select it and choose any of the commands in the @@Draw menu@. " "From the Picture window, you can print it, save it to an EPS file, or copy it to the clipboard for inclusion in your word processor.") MAN_END MAN_BEGIN (L"Advanced pulses settings...", L"ppgb", 20110220) INTRO (L"A command in the #Pulses menu of the @SoundEditor or @TextGridEditor windows. " "Before changing the advanced pulses settings, make sure you understand " "the @@Voice@ tutorial.") NORMAL (L"For information about the ##Maximum period factor# setting, see @@PointProcess: Get jitter (local)...@. " "The standard setting is best in most cases. " "The ##Period floor# and ##Period ceiling# settings derive from the pitch floor and pitch ceiling (@@Pitch settings...@), " "according to a formula given in @@Voice 2. Jitter@.") MAN_END MAN_BEGIN (L"Intro 5. Formant analysis", L"ppgb", 20030316) INTRO (L"This section describes how you can analyse the formant contours of an existing sound.") LIST_ITEM (L"@@Intro 5.1. Viewing formant contours") LIST_ITEM (L"@@Intro 5.2. Configuring the formant contours") LIST_ITEM (L"@@Intro 5.3. Querying the formant contours") LIST_ITEM (L"@@Intro 5.4. The Formant object") MAN_END MAN_BEGIN (L"Intro 5.1. Viewing formant contours", L"ppgb", 20110128) NORMAL (L"To see the formant contours of a sound as functions of time, select a @Sound or @LongSound object and choose @@View & Edit@. " "A @SoundEditor window will appear on your screen. " "The analysis part of this window will contain formant contours, drawn as red speckles. " "If you do not see the formant contours, choose @@Show formant@ from the #Formant menu.") MAN_END MAN_BEGIN (L"Intro 5.2. Configuring the formant contours", L"ppgb", 20030316) NORMAL (L"The formant analysis parameters, with you can set with the #Formant menu, are important. " "For a female voice, you may want to set the maximum frequency to 5500 Hz; " "for a male voice, set it to 5000 Hz instead. " "For more information about analysis parameters, see @@Sound: To Formant (burg)...@.") MAN_END MAN_BEGIN (L"Intro 5.3. Querying the formant contours", L"ppgb", 20040616) NORMAL (L"With @@Get first formant@ from the Formant menu in the @SoundEditor or @TextGridEditor, " "you get information about the first formant at the cursor or in the selection. " "If there is a cursor, ##Get first formant# writes to the @@Info window@ the linearly interpolated first formant at that time. " "If there is a true selection, ##Get first formant# writes to the @@Info window@ the mean first formant in the visble part of that selection. " "The same goes for @@Get second formant@ and so on.") MAN_END MAN_BEGIN (L"Intro 5.4. The Formant object", L"ppgb", 20030316) NORMAL (L"The formant contours that are visible in the @SoundEditor or @TextGridEditor window, " "can be copied as a separate @Formant object to the @@List of Objects@. To do this, " "choose @@Extract visible formant contour@ from the Formant menu.") NORMAL (L"Another way to get a separate Formant object is to select a @Sound object in the list " "choose @@Sound: To Formant (burg)...@ (preferred) or any of the other methods " "from the @@Formants & LPC menu@.") ENTRY (L"Saving formant contours to disk") NORMAL (L"To save formant contours to disk, select the @Formant object in the list and choose one of the commands in the @@Save menu@.") NORMAL (L"Later on, you can read the saved file again with @@Read from file...@ from the @@Open menu@.") ENTRY (L"Drawing formant contours") NORMAL (L"To draw a @Formant object to the @@Picture window@, select it and choose any of the commands in the @@Draw menu@. " "From the Picture window, you can print it, save it to an EPS file, or copy it to the clipboard for inclusion in your word processor.") MAN_END MAN_BEGIN (L"Intro 6. Intensity analysis", L"ppgb", 20030316) INTRO (L"This section describes how you can analyse the intensity contour of an existing sound.") LIST_ITEM1 (L"@@Intro 6.1. Viewing an intensity contour") LIST_ITEM1 (L"@@Intro 6.2. Configuring the intensity contour") LIST_ITEM1 (L"@@Intro 6.3. Querying the intensity contour") LIST_ITEM1 (L"@@Intro 6.4. The Intensity object") MAN_END MAN_BEGIN (L"Intro 6.1. Viewing an intensity contour", L"ppgb", 20110128) INTRO (L"To see the intensity contour of a sound as a function of time, select a @Sound or @LongSound object and choose @@View & Edit@. " "A @SoundEditor window will appear on your screen. " "The analysis part of this window will contain an intensity contour, drawn as a yellow or green line " "(choose ##Show intensity# from the #Intensity menu if it is not visible). " "This also works in the @TextGridEditor.") MAN_END MAN_BEGIN (L"Intro 6.2. Configuring the intensity contour", L"ppgb", 20041123) INTRO (L"With ##Intensity settings...# from the #Intensity menu, " "you can control how the intensity contour is computed and how it is shown.") ENTRY (L"The view range") NORMAL (L"By changing these two numbers you can set the vertical scale. " "The standard setting is from 50 to 100 dB, but if you are interested in the power of the background noise " "you may want to set it to the range from 0 to 100 dB.") ENTRY (L"The averaging method") NORMAL (L"Averaging is what occurs if you make a @@time selection@ (rather than setting the cursor at a single time). " "The green number in dB to the left or right side of the intensity contour will show the average " "intensity in the selection. The same value is what you get when choosing ##Get intensity# from " "the #Intensity menu. You can choose any of the three averaging methods " "available for @@Intensity: Get mean...@, or choose for the #median value in the selection.") ENTRY (L"Pitch floor") NORMAL (L"The intensity curve is %smoothed, since you usually do not want the intensity curve to go up and down with " "the intensity variations within a pitch period. To avoid such pitch-synchronous variations, " "the intensity at every time point is a weighted average over many neighbouring time points. " "The weighting is performed by a Gaussian (`double Kaiser') window that has a duration that is determined by the " "##Minimum pitch# setting (see @@Intro 4.2. Configuring the pitch contour@). " "To see more detail than usual, raise the minimum pitch; to get more smoothing than usual, lower it. " "For more information, see @@Sound: To Intensity...@.") ENTRY (L"Subtract mean pressure or not?") NORMAL (L"Many microphones, microphone preamplifiers, or other components in the recording system " "can add a constant level to the air pressure (a %%DC offset%). " "You can see this at quiet locations in the wave form, " "where the average pressure is not zero but the background noise hovers about some non-zero value. " "You will usually not want to take this constant pressure seriously, i.e. the intensity curve should " "normally not take into account the energy provided by this constant pressure level. " "If you switch on the ##Subtract mean pressure# switch (whose standard setting is also on), " "the intensity value at a time point is computed by first subtracting the mean pressure around this point, " "and then applying the Gaussian window.") MAN_END MAN_BEGIN (L"Intro 6.3. Querying the intensity contour", L"ppgb", 20041123) INTRO (L"To ask for the intensity at the cursor, or the average intensity in the visible part of the selection, " "choose ##Get intensity# from the #Intensity menu or press the F11 key. You get the same value in dB that is visible " "to the left or right side of the intensity curve, but with more digits.") MAN_END MAN_BEGIN (L"Intro 6.4. The Intensity object", L"ppgb", 20041123) NORMAL (L"To print an intensity contour, or to put it in an EPS file or on the clipboard for inclusion in your word processor, " "you first have to create an @Intensity object in the @@List of Objects@. " "You do this either by choosing ##Extract visible intensity contour# " "from the #Intensity menu in the SoundEditor or TextGridEditor window, " "or by selecting a Sound object in the list and choosing @@Sound: To Intensity...@. " "In either case, a new Intensity object will appear in the list. " "To draw the Intensity object to the @@Picture window@, select it and choose ##Draw...#. " "From the Picture window, you can print it, save it to an EPS file, or copy it to the clipboard.") MAN_END MAN_BEGIN (L"Intro 7. Annotation", L"ppgb", 20110129) INTRO (L"You can annotate existing @Sound objects and sound files (@LongSound objects).") NORMAL (L"The labelling data will reside in a @TextGrid object. This object is separate " "from the sound, which means that you will often see two objects in the list: a Sound or LongSound, " "and a TextGrid.") ENTRY (L"Creating a TextGrid") NORMAL (L"You create a new empty TextGrid from the Sound or LongSound with @@Sound: To TextGrid...@ " "or @@LongSound: To TextGrid...@ from the #Annotate menu (which shows up in the Objects window if you select a Sound or LongSound). In this way, the time domain " "of the @TextGrid will automatically equal that of the sound (if you choose @@Create TextGrid...@ from " "the @@New menu@ instead, you will have to supply the time domain by yourself).") NORMAL (L"When you create a TextGrid, you specify the names of the %tiers. For instance, if you want to segment " "the sound into words and into phonemes, you may want to create two tiers and call them " "\"words\" and \"phonemes\" (you can easily add, remove, and rename tiers later). " "Since both of these tiers are %%interval tiers% (you label the intervals between the word and phoneme " "boundaries, not the boundaries themselves), you specify \"phonemes words\" for %%Tier names%, " "and you leave the %%Point tiers% empty.") ENTRY (L"View and edit") NORMAL (L"You can edit a TextGrid object all by itself, but you will normally want to see " "the sound in the editor window as well. To achieve this, you select both the Sound (or LongSound) and " "the TextGrid, and click @@View & Edit@. A @TextGridEditor will appear on your screen. " "Like the Sound editor, the TextGrid editor will show you a spectrogram, a pitch contour, a formant contour, " "and an intensity contour. This editor will allow " "you to add, remove, and edit labels, boundaries, and tiers. Under Help in the TextGridEditor, you will " "find the @TextGridEditor manual page. You are strongly advised to read it, because it will show you " "how you can quickly zoom (drag the mouse), play (click a rectangle), or edit a label (just type).") ENTRY (L"Save") NORMAL (L"You will normally write the TextGrid to disk with @@Save as text file...@ " "or @@Save as short text file...@. It is true that @@Save as binary file...@ will also work, but the others " "give you a file you can read with any text editor.") NORMAL (L"However you saved it, you can read the TextGrid into Praat later with @@Read from file...@.") MAN_END MAN_BEGIN (L"Intro 8. Manipulation", L"ppgb", 20021212) LIST_ITEM (L"@@Intro 8.1. Manipulation of pitch") LIST_ITEM (L"@@Intro 8.2. Manipulation of duration") LIST_ITEM (L"@@Intro 8.3. Manipulation of intensity") MAN_END MAN_BEGIN (L"Intro 8.1. Manipulation of pitch", L"ppgb", 20110128) INTRO (L"To modify the pitch contour of an existing @Sound object, " "you select this @Sound and click ##To Manipulation#. " "A @Manipulation object will then appear in the list. " "You can then click @@View & Edit@ to raise a @ManipulationEditor, " "which will show the pitch contour (@PitchTier) as a series of thick dots. " "To reduce the number of dots, choose ##Stylize pitch (2 st)# " "from the #Pitch menu; it will then be easy to drag the dots " "about the time-pitch area.") NORMAL (L"If you click any of the rectangles " "(or choose any of the #Play commands from the #View menu), " "you will hear the modified sound. By shift-clicking, you will hear " "the original sound.") NORMAL (L"To get the modified sound as a separate object, " "choose ##Publish resynthesis# from the @@File menu@.") NORMAL (L"If you modify the duration curve as well (see @@Intro 8.2. Manipulation of duration@), " "the modified sound will be based on the modified pitch and duration.") ENTRY (L"Cloning a pitch contour") NORMAL (L"To use the pitch contour of one Manipulation object as the pitch contour of another Manipulation object, " "you first choose ##Extract pitch tier# for the first Manipulation object, " "then select the resulting PitchTier object together with the other Manipulation object " "(e.g. by a click on the PitchTier and a Command-click on the Manipulation), " "and choose ##Replace pitch tier#.") ENTRY (L"Precise manipulation of pitch") NORMAL (L"If you know exactly what pitch contour you want, " "you can create an empty PitchTier with @@Create PitchTier...@ from the New menu, " "then add points with @@PitchTier: Add point...@.") NORMAL (L"For instance, suppose you want to have a pitch that falls from 350 to 150 Hz in one second. " "You create the PitchTier, then add a point at 0 seconds and a frequency of 350 Hz, " "and a point at 1 second with a frequency of 150 Hz. " "You can put this PitchTier into a Manipulation object in the way described above.") MAN_END MAN_BEGIN (L"Intro 8.2. Manipulation of duration", L"ppgb", 20110128) INTRO (L"You can use Praat to modify the relative durations in an existing sound.") NORMAL (L"First, you select a @Sound object and click \"To Manipulation\". " "A @Manipulation object will then appear in the list. " "You can then click @@View & Edit@ to raise a @ManipulationEditor, " "which will show an empty @DurationTier. " "You can add targets to this tier by choosing \"Add duration point at cursor\" " "from the \"Dur\" menu. The targets will show up as green dots, which you can easily drag " "about the duration area.") NORMAL (L"If you click any of the rectangles " "(or choose any of the @Play commands from the @View menu), " "you will hear the modified sound. By shift-clicking, you will hear " "the original sound.") NORMAL (L"To get the modified sound as a separate object, " "choose ##Publish resynthesis# from the @@File menu@.") NORMAL (L"If you modify the pitch curve as well (see @@Intro 8.1. Manipulation of pitch@), " "the modified sound will be based on the modified duration and pitch.") ENTRY (L"Precise manipulation of duration") NORMAL (L"If you know exactly the times and relative durations, it is advisable to write a script (see @Scripting). " "Suppose, for instance, that you have a 355-ms piece of sound, and you want to shorten the first 85 ms to 70 ms, " "and the remaining 270 ms to 200 ms.") NORMAL (L"In your first 85 ms, your relative duration should be 70/85, " "and during the last 270 ms, it should be 200/270. " "The DurationTier does linear interpolation, so it can only be approximate these precise times, " "but fortunately to any precision you like:") CODE (L"Create DurationTier... shorten 0 0.085+0.270") CODE (L"Add point... 0.000 70/85") CODE (L"Add point... 0.084999 70/85") CODE (L"Add point... 0.085001 200/270") CODE (L"Add point... 0.355 200/270") NORMAL (L"To put this DurationTier back into a Manipulation object, you select the two objects together " "(e.g. a click on the DurationTier and a Command-click on the Manipulation), " "and choose ##Replace duration tier#.") MAN_END MAN_BEGIN (L"Intro 8.3. Manipulation of intensity", L"ppgb", 20110128) INTRO (L"You can modify the intensity contour of an existing sound.") NORMAL (L"While the pitch and duration of a sound can be modified with the @ManipulationEditor " "(see @@Intro 8.1. Manipulation of pitch@ and @@Intro 8.2. Manipulation of duration@), " "the modification of the intensity curve is done in a different way.") NORMAL (L"You can create an @IntensityTier with the command @@Create IntensityTier...@ " "from the @@New menu@. With @@View & Edit@, you can add points to this tier. " "You can then \"multiply\" this tier with a sound, by selecting the @Sound and the " "IntensityTier together and clicking @@Sound & IntensityTier: Multiply|Multiply@. " "The points in the IntensityTier represent relative intensities in dB; " "therefore, the sound pressure values in the Sound are multiplied by 10^^(dB/20)^.") NORMAL (L"Instead of an IntensityTier, you can use an @AmplitudeTier; " "when you click #Multiply for a selected Sound and AmplitudeTier, " "the sound pressure values in the Sound are directly multiplied by the values in the AmplitudeTier.") MAN_END MAN_BEGIN (L"Intro 8.4. Manipulation of formants", L"ppgb", 20010408) INTRO (L"The manipulation of formant contours cannot be as straightforward as the manipulation " "of pitch, duration, or intensity contours. See the @@Source-filter synthesis@ tutorial " "for an explanation of how formants can be modified in Praat.") MAN_END /* * Who uses Praat? * phonetics * linguistics * speech pathology * psychology * bioacoustics: e.g. hapalemur, crow, monkey, frog, turtle dove, grasshopper, cricket, alligator, crocodile, gecko, elephant, swallow, chicken, dolphin, humpback, [killer] whale, [electric] fish, sparrow, meerkat, [fruit] bat, lion, parrot, red deer, sperm whale, [bearded] seal, mouse, cracid, chacma baboon * music */ MAN_BEGIN (L"Labelling", L"ppgb", 20010408) INTRO (L"See @@Intro 7. Annotation@.") MAN_END MAN_BEGIN (L"List of Objects", L"ppgb", 19981024) INTRO (L"A list in the left-hand part of the @@Object window@.") ENTRY (L"Purpose") NORMAL (L"If you select one or more @objects in this list, " "the possible actions that you can perform with the selected objects " "will appear in the @@Dynamic menu@.") ENTRY (L"How to select objects") NORMAL (L"To select one object (and deselect all the others), click on the object.") NORMAL (L"To extend the selection, drag the mouse (Unix, Windows) or use Shift-click (all platforms).") NORMAL (L"To change the selection of one object (without changing the others), " "use Control-click (Unix, Windows) or Command-click (Macintosh).") MAN_END MAN_BEGIN (L"New menu", L"ppgb", 20080427) INTRO (L"The ##New menu# is one of the menus in the @@Object window@. " "You use this menu to create new objects from scratch. It contains the following commands:") LIST_ITEM (L"\\bu @@Record mono Sound...@") LIST_ITEM (L"\\bu @@Record stereo Sound...@") LIST_ITEM (L"\\bu @@Create Sound from formula...@") LIST_ITEM (L"\\bu @@Create Sound from tone complex...") LIST_ITEM (L"\\bu @@Create Sound from gammatone...") LIST_ITEM (L"\\bu @@Create Sound from Shepard tone...") LIST_ITEM (L"\\bu @@Create Matrix...@ (from a formula)") LIST_ITEM (L"\\bu @@Create simple Matrix...@ (from a formula)") LIST_ITEM (L"\\bu @@Create empty PointProcess...@") LIST_ITEM (L"\\bu @@Create Poisson process...@") LIST_ITEM (L"\\bu @@Create PitchTier...@") LIST_ITEM (L"\\bu @@Create DurationTier...@") LIST_ITEM (L"\\bu @@Create IntensityTier...@") LIST_ITEM (L"\\bu @@Create FormantGrid...@") LIST_ITEM (L"\\bu @@Create Strings as file list...@") LIST_ITEM (L"\\bu @@Create TextGrid...@") LIST_ITEM (L"\\bu @@OT learning@ tutorial") LIST_ITEM (L"\\bu @@Create tongue-root grammar...@") NORMAL (L"To create new objects from files on disk, use the @@Open menu@ instead. " "Objects can also often be create from other objects, with commands that start with ##To#.") MAN_END MAN_BEGIN (L"Object window", L"ppgb", 20030528) INTRO (L"One of the two main windows in the Praat program.") ENTRY (L"Subdivision") LIST_ITEM (L"To the left: the @@List of Objects@.") LIST_ITEM (L"To the right: the @@Dynamic menu@.") ENTRY (L"Fixed buttons") NORMAL (L"The following buttons appear below the List of Objects:") LIST_ITEM (L"\\bu @@Rename...") LIST_ITEM (L"\\bu @@Info") LIST_ITEM (L"\\bu @@Copy...") LIST_ITEM (L"\\bu @@Remove") LIST_ITEM (L"\\bu @@Inspect") ENTRY (L"Menus") LIST_ITEM (L"The Object window contains several fixed menus: " "the #Praat, #New, #Open, and #Help menus. " "It also contains the #Save menu, whose contents vary with the kinds of selected objects, " "and must, therefore, be considered part of the dynamic menu.") ENTRY (L"The Praat menu") LIST_ITEM (L"\\bu (@@Run script...@)") LIST_ITEM (L"\\bu @@New Praat script@: creates an empty @@ScriptEditor@") LIST_ITEM (L"\\bu @@Open Praat script...@: creates a @@ScriptEditor@ with a script from disk") LIST_ITEM (L"\\bu The ##Goodies submenu#: for doing things (like using the Calculator) " "that do not create new objects and do not depend on the kinds of selected objects.") LIST_ITEM (L"\\bu The ##Preferences submenu#: for program-wide preferences, " "like audio input and output settings.") LIST_ITEM (L"\\bu ##Buttons...#: raises a @@ButtonEditor@") LIST_ITEM (L"\\bu (@@Add menu command...@)") LIST_ITEM (L"\\bu (@@Add action command...@)") LIST_ITEM (L"\\bu @@Quit") ENTRY (L"Other menus") LIST_ITEM (L"\\bu The @@New menu@: for creating objects from scratch.") LIST_ITEM (L"\\bu The @@Open menu@: for reading objects from file into memory.") LIST_ITEM (L"\\bu The @@Save menu@: for writing objects from memory to file.") LIST_ITEM (L"\\bu The ##Help menu#: for viewing the manual.") MAN_END MAN_BEGIN (L"Periodicity menu", L"ppgb", 20010417) INTRO (L"A menu that occurs in the @@Dynamic menu@ for a @Sound.") NORMAL (L"This menu contains commands for analysing the pitch contour of the selected Sound:") LIST_ITEM (L"@@Sound: To Pitch...") LIST_ITEM (L"@@Sound: To Pitch (ac)...") LIST_ITEM (L"@@Sound: To Pitch (cc)...") LIST_ITEM (L"@@Sound: To Harmonicity (cc)...") LIST_ITEM (L"@@Sound: To Harmonicity (ac)...") MAN_END MAN_BEGIN (L"Pitch settings...", L"ppgb", 20030316) INTRO (L"A command in the Pitch menu of the @SoundEditor and @TextGridEditor windows. " "See @@Intro 4.2. Configuring the pitch contour@.") MAN_END MAN_BEGIN (L"Play", L"ppgb", 20021212) INTRO (L"A command that is available if you select a @Sound, @Pitch, or @PointProcess object. " "It gives you an acoustic representation of the selected object, if your loudspeakers are on " "and you did not \"mute\" your computer sound system.") NORMAL (L"A Play button is also available in the @SoundRecorder window " "and in the @View menu of the @SoundEditor or @TextGridEditor. In the editors, " "you will usually play a sound by clicking on any of the rectangles around the data.") MAN_END MAN_BEGIN (L"Query", L"ppgb", 20021218) INTRO (L"Query commands give you information about objects.") NORMAL (L"Most query commands start with the word #%Get or sometimes the word #%Count. " "You will find these commands in two places: under the #Query menu that usually appears if you " "select an @@Objects|object@ in the list, and in the #Query menus of the @editors.") ENTRY (L"Behaviour") NORMAL (L"If you click a query command, the answer will be written to the @@Info window@.") ENTRY (L"Scripting") NORMAL (L"In a script, you can still use query commands to write the information to the Info window " "but you can also use any query command to put the information into a variable. " "(see @@Scripting 6.3. Query commands@). In such a case, the value will not be written into the Info window.") ENTRY (L"Query commands in the Praat program") NORMAL (L"The Praat program contains the following query commands:") MAN_END MAN_BEGIN (L"Query menu", L"ppgb", 20010417) INTRO (L"One of the menus in most @editors.") MAN_END MAN_BEGIN (L"Quit", L"ppgb", 20050822) INTRO (L"One of the commands in the @@Praat menu@.") ENTRY (L"Purpose") NORMAL (L"To leave the program.") ENTRY (L"Behaviour") NORMAL (L"All @objects not written to a file will be lost. " "However, file-based objects (like large lexica) will be saved correctly.") ENTRY (L"Usage") NORMAL (L"To save your data to a disk file before quitting, choose a command from the @@Save menu@.") MAN_END MAN_BEGIN (L"Read from file...", L"ppgb", 20111018) INTRO (L"One of the commands in the @@Open menu@.") ENTRY (L"Purpose") NORMAL (L"To read one or more @objects from a file on disk.") ENTRY (L"Behaviour") NORMAL (L"Many kinds of files are recognized:") LIST_ITEM (L"1. Text files that are structured as described under @@Save as text file...@; " "these can contain an object of any type, or a collection of objects.") LIST_ITEM (L"2. Files that were produced by @@Save as binary file...@ (any type).") LIST_ITEM (L"3. Files in a LISP text format (only for object types that can be written to a LISP file).") LIST_ITEM (L"4. Files that were made recognizable by the libraries built on Praat. " "For instance, the phonetics library adds recognizers for many kinds of sound files.") NORMAL (L"If the file contains more than one object, these objects will appear in the list, " "and their names will be the same as the names that they had " "when they were saved with ##Save as text file...# or ##Save as binary file...#.") ENTRY (L"Examples") LIST_ITEM (L"\\bu If the file contains only one Pitch object and is called \"hallo.pit\", " "an object with the name \"Pitch hallo\" will appear in the list of objects. " "You may have more objects with the same name.") LIST_ITEM (L"\\bu If the file contains one object of type Pitch, named \"hallo\", " "and one object of type Polygon, named \"kromme\", " "there will appear two objects in the list, " "called \"Pitch hallo\" and \"Polygon kromme\".") MAN_END MAN_BEGIN (L"Open menu", L"ppgb", 20110111) INTRO (L"One of the menus in the @@Object window@.") NORMAL (L"With the Open menu, you read one or more @objects from a file on disk into memory. " "The resulting object(s) will appear in the @@List of Objects@.") NORMAL (L"The Open menu contains the command @@Read from file...@, which recognizes most file types, " "and perhaps several other commands for reading unrecognizable file types (e.g., raw sound data), " "or for interpreting known file types in a different way " "(e.g., reading two mono sounds from one stereo sound file):") MAN_END MAN_BEGIN (L"Remove", L"ppgb", 20021212) INTRO (L"One of the fixed buttons in the @@Object window@.") NORMAL (L"You can choose this command after selecting one or more @objects in the list.") NORMAL (L"The selected objects will permanently disappear from the list, " "and the computer memory that they occupied will be freed.") NORMAL (L"To save your data before removing, choose a command from the @@Save menu@.") MAN_END MAN_BEGIN (L"Rename...", L"ppgb", 20111018) INTRO (L"One of the fixed buttons in the @@Object window@.") ENTRY (L"Availability") NORMAL (L"You can choose this command after selecting one object of any type.") ENTRY (L"Purpose") NORMAL (L"You can give the selected object a new name.") ENTRY (L"Behaviour") NORMAL (L"If you type special symbols or spaces, the Object window will replace them with underscores.") MAN_END MAN_BEGIN (L"Resource fork", L"ppgb", 20030316) INTRO (L"One of the two %forks of a Macintosh file (the other is the %%data fork%). " "If a Macintosh file is moved to another platform directly, the resource fork is lost. " "To backup your Macintosh files, use compression, for instance with #DropStuff\\tm.") MAN_END MAN_BEGIN (L"Save menu", L"ppgb", 20111018) INTRO (L"One of the menus in the @@Object window@.") ENTRY (L"Purpose") NORMAL (L"With the #Save menu, you write one or more selected @objects from memory to a file on disk. " "The data can be read in again with one of the commands in the @@Open menu@ " "(most often simply with @@Read from file...@).") ENTRY (L"Usage: save your work") NORMAL (L"You will often choose a command from this menu just before clicking the @Remove button " "or choosing the @Quit command.") ENTRY (L"Fixed commands") NORMAL (L"If no object is selected, the #Save menu is empty. " "If any object is selected, it will at least contain the following commands:") LIST_ITEM (L"\\bu @@Write to console") LIST_ITEM (L"\\bu @@Save as text file...") LIST_ITEM (L"\\bu @@Save as short text file...") LIST_ITEM (L"\\bu @@Save as binary file...") ENTRY (L"Dynamic commands") NORMAL (L"Depending on the type of the selected object, the following commands may be available " "in the #Save menu:") MAN_END MAN_BEGIN (L"Save as binary file...", L"ppgb", 20110129) INTRO (L"One of the commands in the @@Save menu@.") ENTRY (L"Availability") NORMAL (L"You can choose this command after selecting one or more @objects.") ENTRY (L"Behaviour") NORMAL (L"The Object window will ask you for a file name. " "After you click OK, the objects will be written to a binary file on disk.") ENTRY (L"Usage") NORMAL (L"The file can be read again with @@Read from file...@.") ENTRY (L"File format") NORMAL (L"These files are in a device-independent binary format, " "and can be written and read on any machine.") MAN_END MAN_BEGIN (L"Save as short text file...", L"ppgb", 20110129) INTRO (L"One of the commands in the @@Save menu@.") ENTRY (L"Availability") NORMAL (L"You can choose this command after selecting one or more @objects.") ENTRY (L"Behaviour") NORMAL (L"The Object window will ask you for a file name. " "After you click OK, the objects will be written to a text file on disk.") ENTRY (L"File format") NORMAL (L"The format is much shorter than the one described at @@Save as text file...@. " "Most of the comments are gone, and there is normally one piece of data per line.") NORMAL (L"The file can be read again with the all-purpose @@Read from file...@.") MAN_END MAN_BEGIN (L"Save as text file...", L"ppgb", 20110129) INTRO (L"One of the commands in the @@Save menu@.") ENTRY (L"Availability") NORMAL (L"You can choose this command after selecting one or more @objects.") ENTRY (L"Behaviour") NORMAL (L"The Object window will ask you for a file name. " "After you click OK, the objects will be written to a text file on disk.") ENTRY (L"File format") NORMAL (L"If you selected a single object, e.g., of type Pitch, " "the file will start with the lines:") CODE (L"File type = \"ooTextFile\"") CODE (L"Object class = \"Pitch\"") NORMAL (L"After this, the pitch data will follow.") LIST_ITEM (L"If you selected more than one object, e.g., `Pitch hallo' and `Polygon kromme', " "the file will look like:") CODE (L"File type = \"ooTextFile\"") CODE (L"Object class = \"Collection\"") CODE (L"size = 2") CODE (L"item []:") CODE (L" item [1]:") CODE (L" class = \"Pitch\"") CODE (L" name = \"hallo\"") CODE (L" (pitch data...)") CODE (L" item [2]:") CODE (L" class = \"Polygon\"") CODE (L" name = \"kromme\"") CODE (L" (polygon data...)") NORMAL (L"The file can be read again with @@Read from file...@, " "which, by the way, does not need the verbosity of the above example. " "The following minimal format will also be read correctly:") CODE (L"\"ooTextFile\"") CODE (L"\"Collection\" 2") CODE (L"\"Pitch\" \"hallo\" (pitch data...)") CODE (L"\"Polygon\" \"kromme\" (polygon data...)") NORMAL (L"Thus, all text that is not a free-standing number and is not enclosed in double quotes or < >, " "is considered a comment, as is all text following an exclamation mark (`!') on the same line.") MAN_END MAN_BEGIN (L"Segmentation", L"ppgb", 20010408) INTRO (L"See @@Intro 7. Annotation@.") MAN_END MAN_BEGIN (L"Show formant", L"ppgb", 20030316) INTRO (L"One of the commands in the Formant menu of the @SoundEditor and the @TextGridEditor.") NORMAL (L"See @@Intro 5. Formant analysis@.") MAN_END MAN_BEGIN (L"Show intensity", L"ppgb", 20030316) INTRO (L"One of the commands in the Intensity menu of the @SoundEditor and the @TextGridEditor.") NORMAL (L"See @@Intro 6. Intensity analysis@.") MAN_END MAN_BEGIN (L"Show pitch", L"ppgb", 20030316) INTRO (L"One of the commands in the Pitch menu of the @SoundEditor and the @TextGridEditor.") NORMAL (L"See @@Intro 4. Pitch analysis@.") MAN_END MAN_BEGIN (L"Show pulses", L"ppgb", 20030316) INTRO (L"One of the commands in the Pulses menu of the @SoundEditor and the @TextGridEditor.") NORMAL (L"See @Voice.") MAN_END MAN_BEGIN (L"Show spectrogram", L"ppgb", 20030316) INTRO (L"One of the commands in the Spectrogram menu of the @SoundEditor and the @TextGridEditor.") NORMAL (L"See @@Intro 3. Spectral analysis@.") MAN_END MAN_BEGIN (L"Source-filter synthesis", L"ppgb", 20050713) INTRO (L"This tutorial describes how you can do acoustic synthesis with Praat. " "It assumes that you are familiar with the @Intro.") ENTRY (L"1. The source-filter theory of speech production") NORMAL (L"The source-filter theory (@@Fant (1960)|Fant 1960@) hypothesizes that an acoustic speech signal can be seen " "as a %source signal (the glottal source, or noise generated at a constriction in the vocal tract), " "%filtered with the resonances in the cavities of the vocal tract downstream from the glottis " "or the constriction. The %%Klatt synthesizer% (@@Klatt & Klatt (1990)|Klatt & Klatt 1990@), for instance, " "is based on this idea.") NORMAL (L"In the Praat program, you can create a %source signal from scratch of from an existing " "speech signal, and you can create a %filter from scratch or extract it from an existing speech signal. " "You can manipulate (change, adapt) both the source and the filter before doing " "the actual synthesis, which combines the two.") LIST_ITEM (L"@@Source-filter synthesis 1. Creating a source from pitch targets") LIST_ITEM (L"@@Source-filter synthesis 2. Filtering a source") LIST_ITEM (L"@@Source-filter synthesis 3. The ba-da continuum") LIST_ITEM (L"@@Source-filter synthesis 4. Using existing sounds") MAN_END MAN_BEGIN (L"Source-filter synthesis 1. Creating a source from pitch targets", L"ppgb", 20110128) INTRO (L"Creating a glottal source signal for speech synthesis involves creating a @PointProcess, " "which is a series of time points that should represent the exact moments of glottal closure.") NORMAL (L"You may want to start with creating a well-defined pitch contour. " "Suppose you want to create a sound with a duration of half a second with a pitch that falls from 300 to 200 Hz " "during that time. You first create an empty @PitchTier by choosing @@Create PitchTier...@ from the #New menu " "(I call this PitchTier \"empty\" because it does not contain any pitch information yet); " "you may want to name the PitchTier \"source\" and have it start at 0 seconds and end at 0.5 seconds. " "Once the PitchTier exists and is selected, you can ##View & Edit# it to add pitch points (pitch targets) to it at certain times " "(or you choose @@PitchTier: Add point...@ from the #Modify menu repeatedly). " "You could add a pitch point of 150 Hz at time 0.0 and a pitch point of 100 Hz at time 0.5. " "In the PitchTier window, you can see that the pitch curve falls linearly " "from 150 to 100 Hz during its time domain:") SCRIPT (4.5, 2.5, L"Create PitchTier... source 0 0.5\n" "Add point... 0.0 150\n" "Add point... 0.5 100\n" "Draw... 0 0 0 200 yes lines and speckles\n" "Text top... no %%An F0 linearly falling between two points\n" "One mark left... 100 yes yes no\n" "Remove\n" ) NORMAL (L"You can hear the falling pitch by clicking on the rectangles in the PitchTier window " "(or by clicking ##Play pulses#, #Hum, or ##Play sine# in the Objects window).") NORMAL (L"From this PitchTier, you can create a @PointProcess with @@PitchTier: To PointProcess@. " "The resulting PointProcess now represents a series of glottal pulses. To make some parts of this " "point process voiceless, you can use @@PointProcess: Remove points between...@. " "It is advisable to make the very beginning and end of this point process voiceless, so that the filtered sound " "will not start or end abruptly. In the following example, the first and last 20 ms are devoiced, " "and a stretch of 70 ms in the middle " "is made voiceless as well, perhaps because you want to simulate a voiceless plosive there:") SCRIPT (4.5, 2.5, L"pitchTier = Create PitchTier... source 0 0.5\n" "Add point... 0.0 150\n" "Add point... 0.5 100\n" "pulses = To PointProcess\n" "Remove points between... 0 0.02\n" "Remove points between... 0.24 0.31\n" "Remove points between... 0.48 0.5\n" "Draw... 0 0 yes\n" "Text top... no %%The times of the glottal pulses\n" "One mark bottom... 0.24 yes yes no\n" "One mark bottom... 0.31 yes yes no\n" "plus pitchTier\n" "Remove\n" ) NORMAL (L"Now that we have a glottal point process (a glottal pulse train), the only thing left " "is to turn it into a sound by choosing @@PointProcess: To Sound (phonation)...@. " "If you use the standard settings of this command (but with ##Adaptation factor# set to 0.6), the result will be a @Sound with " "reasonable glottal flow derivatives centred around each of the original pulses in the point process. " "You can check this by selecting the Sound and choosing ##View & Edit#:") SCRIPT (4.5, 2.5, L"pitchTier = Create PitchTier... source 0 0.5\n" "Add point... 0.0 150\n" "Add point... 0.5 100\n" "pulses = To PointProcess\n" "Remove points between... 0 0.02\n" "Remove points between... 0.24 0.31\n" "Remove points between... 0.48 0.5\n" "source = To Sound (phonation)... 44100 0.6 0.05 0.7 0.03 3.0 4.0\n" "Draw... 0 0 0 0 yes curve\n" "Text top... no %%The source waveform\n" "One mark bottom... 0.24 yes yes no\n" "One mark bottom... 0.31 yes yes no\n" "plus pitchTier\n" "plus pulses\n" "Remove\n" ) NORMAL (L"You will also see that the amplitude of the first two glottal wave shapes of every voiced stretch " "is (realistically) somewhat smaller than the amplitudes of the following wave shapes; " "This is the result of setting ##Adaptation factor# to 0.6.") NORMAL (L"What you have now is what we call a %%glottal source signal%. It does two things: it contains information on the glottal flow, " "and it already takes into account one aspect of the %filter, namely the radiation at the lips. " "This combination is standard procedure in acoustic synthesis.") NORMAL (L"The glottal source signal sounds as a voice without a vocal tract. " "The following section describes how you add vocal-tract resonances, i.e. the %filter.") ENTRY (L"Automation") NORMAL (L"In a clean Praat script, the procedure described above will look as follows:") CODE (L"pitchTier = Create PitchTier... source 0 0.5") CODE (L"Add point... 0.0 150") CODE (L"Add point... 0.5 100") CODE (L"pulses = To PointProcess") CODE (L"Remove points between... 0 0.02") CODE (L"Remove points between... 0.24 0.31") CODE (L"Remove points between... 0.48 0.5") CODE (L"source = To Sound (phonation)... 44100 0.6 0.05 0.7 0.03 3.0 4.0") CODE (L"select pitchTier") CODE (L"plus pulses") CODE (L"Remove") CODE (L"select source") MAN_END MAN_BEGIN (L"Source-filter synthesis 2. Filtering a source", L"ppgb", 20080427) INTRO (L"Once you have a glottal source signal, you are ready to create a filter that represents " "the resonances of the vocal tract, as a function of time. In other words, you create a @FormantGrid object.") NORMAL (L"For a vowel spoken by an average (i.e. adult female) human voice, tradition assumes five formants in the range " "between 0 and 5500 hertz. This number comes from a computation of the formants of a " "straight tube, which has resonances at wavelengths of four tube lengths, four thirds of a tube length, " "four fifths, and so on. For a straight tube 16 centimetres long, the shortest wavelength is 64 cm, " "which, with a sound velocity of 352 m/s, means a resonance frequency of 352/0.64 = 550 hertz. " "The other resonances will be at 1650, 2750, 3850, and 4950 hertz.") NORMAL (L"You can create a @FormantGrid object with @@Create FormantGrid...@ from the #New menu (submenu #Tiers):") CODE (L"Create FormantGrid... filter 0 0.5 10 550 1100 60 50") NORMAL (L"This creates a FormantGrid with 10 formants and a single frequency value for each formant: %F__1_ is 550 Hz " "and the higher formants are spaced 1100 Hz apart, i.e., they are " "1650, 2750, 3850, 4950, 6050, 7150, 8250, 9350, and 10450 hertz; " "the ten bandwidths start at 60 Hz and have a spacing of 50 Hz, " "i.e., they are 60, 110, 160, 210, 260, 310, 360, 410, 460, and 510 hertz.") NORMAL (L"You can then create formant contours with @@FormantGrid: Add formant point...@:") CODE (L"Remove formant points between... 1 0 0.5") CODE (L"Add formant point... 1 0.00 100") CODE (L"Add formant point... 1 0.05 700") CODE (L"Remove formant points between... 2 0 0.5") CODE (L"Add formant point... 2 0.00 500") CODE (L"Add formant point... 2 0.05 1100") NORMAL (L"This example creates a spectral specification whose %F__1_ rises from 100 to 700 hertz during the " "first 50 milliseconds (as for any obstruent), and whose %F__2_ rises from 500 to 1100 hertz. " "The other eight formants keep their original values, as do the ten bandwidths. " "The resulting sound may be a [ba]-like formant transition.") NORMAL (L"To get the final acoustic result (the sound), you select the glottal source signal " "together with the FormantGrid and choose @@Sound & FormantGrid: Filter@.") NORMAL (L"The resulting sound will have a fairly straight intensity contour. You can change this with " "the #Formula command (@@Sound: Formula...@), or by multiplying the source signal or the " "acoustic result with an @Intensity or @IntensityTier object.") MAN_END MAN_BEGIN (L"Source-filter synthesis 3. The ba-da continuum", L"ppgb", 20091012) INTRO (L"As an example, we are going to create a male [ba]-[da] continuum in six steps. The acoustic difference " "between [ba] and [da] is the initial %F__2_, which is 500 Hz for [ba], and 2500 Hz for [da].") NORMAL (L"We use the same @PitchTier throughout, to model a falling intonation contour:") CODE (L"Create PitchTier... f0 0.00 0.50") CODE (L"Add point... 0.00 150") CODE (L"Add point... 0.50 100") NORMAL (L"The first and last 50 milliseconds are voiceless:") CODE (L"To PointProcess") CODE (L"Remove points between... 0.00 0.05") CODE (L"Remove points between... 0.45 0.50") NORMAL (L"Generate the glottal source signal:") CODE (L"To Sound (phonation)... 44100 0.6 0.05 0.7 0.03 3.0 4.0") NORMAL (L"During the labial or coronal closure, the sound is almost silent, so we use an @IntensityTier " "that models this:") CODE (L"Create IntensityTier... intens 0.00 0.50") CODE (L"Add point... 0.05 60") CODE (L"Add point... 0.10 80") NORMAL (L"Generate the source signal:") CODE (L"#plus Sound f0") CODE (L"Multiply") CODE (L"Rename... source") NORMAL (L"The ten sounds are generated in a loop:") CODE (L"#for i #from 1 #to 10") CODE (L" f2_locus = 500 + (2500/9) * (i - 1) ; variable names start with lower case!") CODE (L" Create FormantGrid... filter 0.0 0.5 9 800 1000 60 80") CODE (L" Remove formant points between... 1 0.0 0.5") CODE (L" Add formant point... 1 0.05 100") CODE (L" Add bandwidth point... 1 0.05 50") CODE (L" Add formant point... 2 0.05 f2_locus") CODE (L" Add bandwidth point... 2 0.05 100") CODE (L" #plus Sound source") CODE (L" Filter (no scale)") CODE (L" Rename... bada'i'") CODE (L" #select FormantGrid filter") CODE (L" Remove") CODE (L"#endfor") NORMAL (L"Clean up:") CODE (L"#select Sound source") CODE (L"#plus Sound f0") CODE (L"#plus IntensityTier intens") CODE (L"#plus PointProcess f0") CODE (L"#plus PitchTier f0") CODE (L"Remove") NORMAL (L"In this example, filtering was done without automatic scaling, so that " "the resulting signals have equal intensities in the areas where they have " "equal formants. You will probably want to multiply all these signals with " "the same value in order to bring their amplitudes in a suitable range " "between -1 and +1 Pascal.") MAN_END MAN_BEGIN (L"Source-filter synthesis 4. Using existing sounds", L"ppgb", 20111018) ENTRY (L"1. How to extract the %filter from an existing speech sound") NORMAL (L"You can separate source and filter with the help of the technique of %%linear prediction% " "(see @@Sound: LPC analysis@). This technique tries to approximate a given frequency spectrum with " "a small number of peaks, for which it finds the mid frequencies and the bandwidths. " "If we do this for an overlapping sequence of windowed parts of a sound signal " "(i.e. a %%short-term analysis%), we get a quasi-stationary approximation of the signal's " "spectral characteristics as a function of time, i.e. a smoothed version of the @Spectrogram.") NORMAL (L"For a speech signal, the peaks are identified with the resonances (%formants) of the vocal tract. " "Since the spectrum of a vowel spoken by an average human being falls off with approximately " "6 dB per octave, %%pre-emphasis% is applied to the signal before the linear-prediction analysis, " "so that the algorithm will not try to match only the lower parts of the spectrum.") NORMAL (L"For an adult female human voice, tradition assumes five formants in the range " "between 0 and 5500 hertz, say at 550, 1650, 2750, 3850, and 4950 hertz. For the linear prediction in " "Praat, you will have to implement this 5500-Hz band-limiting by resampling the original " "speech signal to 11 kHz. For a male voice, you would use 10 kHz; for a young child, 20 kHz.") NORMAL (L"To perform the resampling, you use @@Sound: Resample...@: " "you select a @Sound object, and click ##Resample...#. " "In the rest of this tutorial, I will use the syntax that you would use in a script, " "though you will usually do these things by clicking on objects and buttons. Thus:") CODE (L"#select Sound hallo") CODE (L"Resample... 11000 50") NORMAL (L"You can then perform a linear-prediction analysis on the resampled sound " "with @@Sound: To LPC (burg)...@:") CODE (L"#select Sound hallo_11000") CODE (L"To LPC (burg)... 10 0.025 0.005 50") NORMAL (L"This says that your analysis is done with 10 linear-prediction parameters " "(which will yield at most five formant-bandwidth pairs), with an analysis window " "effectively 25 milliseconds long, with time steps of 5 milliseconds (so that the windows " "will appreciably overlap), and with a pre-emphasis frequency of 50 Hz (which is the point " "above which the sound will be amplified by 6 dB/octave prior to the analysis proper).") NORMAL (L"As a result, an object called \"LPC hallo\" will appear in the list of objects. " "This @LPC object is a time function with 10 %%linear-prediction coefficients% in each %%time frame%. " "These coefficients are rather opaque even to the expert (try to view them with @Inspect), " "but they are the raw material from which formant and bandwidth values can be computed. " "To see the smoothed @Spectrogram associated with the LPC object, choose @@LPC: To Spectrogram...@:") CODE (L"#select LPC hallo_11000") CODE (L"To Spectrogram... 20 0 50") CODE (L"Paint... 0 0 0 0 50 0 0 yes") NORMAL (L"Note that when drawing this Spectrogram, you will want to set the pre-emphasis to zero " "(the fifth 0 in the last line), because pre-emphasis has already been applied in the analysis.") NORMAL (L"You can get and draw the formant-bandwidth pairs from the LPC object, " "with @@LPC: To Formant@ and @@Formant: Speckle...@:") CODE (L"#select LPC hallo_11000") CODE (L"To Formant") CODE (L"Speckle... 0 0 5500 30 yes") NORMAL (L"Note that in converting the @LPC into a @Formant object, you may have lost some " "information about spectral peaks at very low frequencies (below 50 Hz) or at very high " "frequencies (near the @@Nyquist frequency@ of 5500 Hz. Such peaks usually try to fit " "an overall spectral slope (if the 6 dB/octave model is inappropriate), and are not seen " "as related with resonances in the vocal tract, so they are ignored in a formant analysis. " "For resynthesis purposes, they might still be important.") NORMAL (L"Instead of using the intermediate LPC object, you could have done a formant analysis " "directly on the original Sound, with @@Sound: To Formant (burg)...@:") CODE (L"#select Sound hallo") CODE (L"To Formant (burg)... 0.005 5 5500 0.025 50") NORMAL (L"A @Formant object has a fixed sampling (time step, frame length), and for every " "%%formant frame%, it contains a number of formant-bandwidth pairs.") NORMAL (L"From a Formant object, you can create a @FormantGrid with @@Formant: Down to FormantGrid@. " "A FormantGrid object contains a number of tiers with time-stamped %%formant points% and %%bandwidth points%.") NORMAL (L"Any of these three types (@LPC, @Formant, and @FormantGrid) can represent the %filter " "in source-filter synthesis.") ENTRY (L"2. How to extract the %source from an existing speech sound") NORMAL (L"If you are only interested in the %filter characteristics, you can get by with @Formant objects. " "To get at the %source signal, however, you need the raw @LPC object: " "you select it together with the resampled @Sound, and apply %%inverse filtering%:") CODE (L"#select Sound hallo_11000") CODE (L"#plus LPC hallo_11000") CODE (L"Filter (inverse)") NORMAL (L"A new Sound named \"hallo_11000\" will appear in the list of objects " "(you could rename it to \"source\"). " "This is the estimated source signal. Since the LPC analysis was designed to yield a spectrally " "flat filter (through the use of pre-emphasis), this source signal represents everything in the " "speech signal that cannot be attributed to the resonating cavities. Thus, the \"source signal\" " "will consist of the glottal volume-velocity source (with an expected spectral slope of " "-12 dB/octave for vowels) and the radiation characteristics at the lips, which cause a " "6 dB/octave spectral rise, so that the resulting spectrum of the \"source signal\" " "is actually the %derivative of the glottal flow, with an expected spectral slope of -6 dB/octave.") NORMAL (L"Note that with inverse filtering you cannot measure the actual spectral slope of the source signal. " "Even if the actual slope is very different from -6 dB/octave, formant extraction will try to " "match the pre-emphasized spectrum. Thus, by choosing a pre-emhasis of -6 dB/octave, " "you %impose a slope of -6 dB/octave on the source signal.") ENTRY (L"3. How to do the synthesis") NORMAL (L"You can create a new Sound from a source Sound and a filter, in at least four ways.") NORMAL (L"If your filter is an @LPC object, you select it and the source, and choose @@LPC & Sound: Filter...@:") CODE (L"#select Sound source") CODE (L"#plus LPC filter") CODE (L"Filter... no") NORMAL (L"If you had computed the source and filter from an LPC analysis, this procedure should give " "you back the original Sound, except that windowing has caused 25 milliseconds at the beginning " "and end of the signal to be set to zero.") NORMAL (L"If your filter is a @Formant object, you select it and the source, and choose @@Sound & Formant: Filter@:") CODE (L"#select Sound source") CODE (L"#plus Formant filter") CODE (L"Filter") NORMAL (L"If you had computed the source and filter from an LPC analysis, this procedure will not generally give " "you back the original Sound, because some linear-prediction coefficients will have been ignored " "in the conversion to formant-bandwidth pairs.") NORMAL (L"If your filter is a @FormantGrid object, you select it and the source, and choose @@Sound & FormantGrid: Filter@:") CODE (L"#select Sound source") CODE (L"#plus FormantGrid filter") CODE (L"Filter") NORMAL (L"Finally, you could just know the %%impulse response% of your filter (in a @Sound object). " "You then select both Sound objects, and choose @@Sounds: Convolve...@:") CODE (L"#select Sound source") CODE (L"#plus Sound filter") CODE (L"Convolve... integral zero") NORMAL (L"As a last step, you may want to bring the resulting sound within the [-1; +1] range:") CODE (L"Scale peak... 0.99") ENTRY (L"4. How to manipulate the filter") NORMAL (L"You can hardly change the values in an @LPC object in a meaningful way: " "you would have to manually change its rather opaque data with the help of @Inspect.") NORMAL (L"A @Formant object can be changed in a friendlier way, with @@Formant: Formula (frequencies)...@ " "and @@Formant: Formula (bandwidths)...@. For instance, to multiply all formant frequencies by 0.9, " "you do") CODE (L"#select Formant filter") CODE (L"Formula (frequencies)... self * 0.9") NORMAL (L"To add 200 hertz to all values of %F__2_, you do") CODE (L"Formula (frequencies)... if row = 2 then self + 200 else self fi") NORMAL (L"A @FormantGrid object can be changed by adding or removing points:") LIST_ITEM (L"@@FormantGrid: Add formant point...@") LIST_ITEM (L"@@FormantGrid: Add bandwidth point...@") LIST_ITEM (L"@@FormantGrid: Remove formant points between...@") LIST_ITEM (L"@@FormantGrid: Remove bandwidth points between...@") ENTRY (L"5. How to manipulate the source signal") NORMAL (L"You can manipulate the source signal in the same way you that would manipulate any sound, " "for instance with the @ManipulationEditor.") MAN_END MAN_BEGIN (L"Spectrogram settings...", L"ppgb", 20030316) INTRO (L"A command in the Spectrogram menu of the @SoundEditor and @TextGridEditor windows. " "See @@Intro 3.2. Configuring the spectrogram@.") MAN_END MAN_BEGIN (L"Types of objects", L"ppgb", 20101230) INTRO (L"Praat contains the following types of objects and @Editors. " "For an introduction and tutorials, see @Intro.") NORMAL (L"General purpose:") LIST_ITEM (L"\\bu @Matrix: a sampled real-valued function of two variables") LIST_ITEM (L"\\bu @Polygon") LIST_ITEM (L"\\bu @PointProcess: a point process (@PointEditor)") LIST_ITEM (L"\\bu @Sound: a sampled continuous process (@SoundEditor, @SoundRecorder, @@Sound files@)") LIST_ITEM (L"\\bu @LongSound: a file-based version of a sound (@LongSoundEditor)") LIST_ITEM (L"\\bu @Strings") LIST_ITEM (L"\\bu @Distributions, @PairDistribution") LIST_ITEM (L"\\bu @Table, @TableOfReal") LIST_ITEM (L"\\bu @Permutation") LIST_ITEM (L"\\bu @ParamCurve") NORMAL (L"Periodicity analysis:") LIST_ITEM (L"\\bu Tutorials:") LIST_ITEM1 (L"\\bu @@Intro 4. Pitch analysis") LIST_ITEM1 (L"\\bu @@Intro 6. Intensity analysis") LIST_ITEM1 (L"\\bu @Voice (jitter, shimmer, noise)") LIST_ITEM (L"\\bu @Pitch: articulatory fundamental frequency, acoustic periodicity, or perceptual pitch (@PitchEditor)") LIST_ITEM (L"\\bu @Harmonicity: degree of periodicity") LIST_ITEM (L"\\bu @Intensity, @IntensityTier: intensity contour") NORMAL (L"Spectral analysis:") LIST_ITEM (L"\\bu Tutorials:") LIST_ITEM1 (L"\\bu @@Intro 3. Spectral analysis") LIST_ITEM1 (L"\\bu @@Intro 5. Formant analysis") LIST_ITEM (L"\\bu @Spectrum: complex-valued equally spaced frequency spectrum (@SpectrumEditor)") LIST_ITEM (L"\\bu @Ltas: long-term average spectrum") LIST_ITEM (L"\\bu Spectro-temporal: @Spectrogram, @BarkFilter, @MelFilter, @FormantFilter") LIST_ITEM (L"\\bu @Formant: acoustic formant contours") LIST_ITEM (L"\\bu @LPC: coefficients of Linear Predictive Coding, as a function of time") LIST_ITEM (L"\\bu @Cepstrum, @CC, @LFCC, @MFCC (cepstral coefficients)") LIST_ITEM (L"\\bu @Excitation: excitation pattern of basilar membrane") LIST_ITEM (L"\\bu @Excitations: an ensemble of #Excitation objects") LIST_ITEM (L"\\bu @Cochleagram: excitation pattern as a function of time") NORMAL (L"Labelling and segmentation (see @@Intro 7. Annotation@):") LIST_ITEM (L"\\bu @TextGrid (@TextGridEditor)") NORMAL (L"Listening experiments:") LIST_ITEM (L"\\bu @ExperimentMFC") NORMAL (L"Manipulation of sound:") LIST_ITEM (L"\\bu Tutorials:") LIST_ITEM1 (L"\\bu @@Intro 8.1. Manipulation of pitch") LIST_ITEM1 (L"\\bu @@Intro 8.2. Manipulation of duration") LIST_ITEM1 (L"\\bu @@Intro 8.3. Manipulation of intensity") LIST_ITEM1 (L"\\bu @@Filtering") LIST_ITEM1 (L"\\bu @@Source-filter synthesis") LIST_ITEM (L"\\bu @PitchTier (@PitchTierEditor)") LIST_ITEM (L"\\bu @Manipulation (@ManipulationEditor): @@overlap-add@") LIST_ITEM (L"\\bu @DurationTier") LIST_ITEM (L"\\bu @FormantGrid") NORMAL (L"Articulatory synthesis (see the @@Articulatory synthesis@ tutorial):") LIST_ITEM (L"\\bu @Speaker: speaker characteristics of a woman, a man, or a child") LIST_ITEM (L"\\bu #Articulation: snapshot of articulatory specifications (muscle activities)") LIST_ITEM (L"\\bu @Artword: articulatory target specifications as functions of time") LIST_ITEM (L"\\bu (@VocalTract: area function)") NORMAL (L"Neural net package:") LIST_ITEM (L"\\bu @FFNet: feed-forward neural net") LIST_ITEM (L"\\bu @Pattern") LIST_ITEM (L"\\bu @Categories: for classification (#CategoriesEditor)") NORMAL (L"Numerical and statistical analysis:") LIST_ITEM (L"\\bu @Eigen: eigenvectors and eigenvalues") LIST_ITEM (L"\\bu @Polynomial, @Roots, @ChebyshevSeries, @LegendreSeries, @ISpline, @MSpline") LIST_ITEM (L"\\bu @Covariance: covariance matrix") LIST_ITEM (L"\\bu @Confusion: confusion matrix") LIST_ITEM (L"\\bu @@Discriminant analysis@: @Discriminant") LIST_ITEM (L"\\bu @@Principal component analysis@: @PCA") LIST_ITEM (L"\\bu @Correlation, @ClassificationTable, @SSCP") LIST_ITEM (L"\\bu @DTW: dynamic time warping") NORMAL (L"@@Multidimensional scaling@:") LIST_ITEM (L"\\bu @Configuration (@Salience)") LIST_ITEM (L"\\bu @@Kruskal analysis@: @Dissimilarity (@Weight), @Similarity") LIST_ITEM (L"\\bu @@INDSCAL analysis@: @Distance, @ScalarProduct") LIST_ITEM (L"\\bu @@Correspondence analysis@: @ContingencyTable") NORMAL (L"Optimality-theoretic learning (see the @@OT learning@ tutorial)") LIST_ITEM (L"\\bu @OTGrammar (@OTGrammarEditor)") NORMAL (L"Bureaucracy") LIST_ITEM (L"\\bu @WordList, @SpellingChecker") MAN_END MAN_BEGIN (L"Unicode", L"ppgb", 20110129) INTRO (L"Praat is becoming a fully international program: " "the texts in Praat's TextGrids, Tables, scripts, or Info window (and elsewhere) can contain many types of characters " "(see @@special symbols@). " "For this reason, Praat saves its text files in one of two possible formats: ASCII or UTF-16.") ENTRY (L"ASCII text files") NORMAL (L"If your TextGrid (or Table, or script, or Info window...) contains only characters that can be encoded as ASCII, " "namely the characters !\\\" \\# \\$ \\% &\\' ()*+,-./0123456789:;<=>?\\@ " "ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\bs]\\^ \\_ ` abcdefghijklmnopqrstuvwxyz{|}~, " "then when you say @@Save as text file...@ or #Save, Praat will write an ASCII text file, " "which is a text file in which every character is encoded in a single byte (8 bits). " "All programs that can read plain text files can read such files produced by Praat.") ENTRY (L"UTF-16 text files") NORMAL (L"If your TextGrid (or Table, or script, or Info window...) contains one or more characters that cannot be encoded as ASCII, " "for instance West-European characters such as \\ao\\c,\\e'\\o\"\\ss\\?d, East-European characters such as \\c<\\l/\\o:\\s<\\uo\\z', " "or Hebrew characters such as \\?+\\B+\\G+\\M%\\vO\\sU, " "then when you say @@Save as text file...@ or #Save, Praat will write an UTF-16 text file, " "which is a text file in which every character is encoded in two bytes (and some very rare characters in four bytes). " "Many programs can read such text files, for instance NotePad, WordPad, Microsoft Word, and TextWrangler.") ENTRY (L"What if my other programs cannot read UTF-16 text files?") NORMAL (L"If you want to export your Table to Microsoft Excel or to SPSS, or if you want your TextGrid file to be read " "by somebody else's Perl script, then there will be no problem if your Table contains only ASCII characters (see above). " "But if your Table contains any other (i.e. non-ASCII) characters, you may be in trouble, because Praat will write the Table " "as an UTF-16 text file, and not all of the programs just mentioned can read such files yet.") NORMAL (L"What you can do is go to ##Text writing preferences...# in the #Preferences submenu of the #Praat menu, " "and there set the output encoding to ##UTF-8#. Praat will from then on save your text files in the UTF-8 format, " "which means one byte for every ASCII character and 2 to 4 bytes for every non-ASCII character. " "Especially on Linux, many programs understand UTF-8 text and will display the correct characters. " "Programs such as SPSS do not understand UTF-8 but will still display ASCII characters correctly; " "for instance, the names M\\u\"nchen and Wa\\l/\\e;sa may appear as M\\A~\\:-nchen and Wa\\Ao,\\A\"\\TMsa or so.") NORMAL (L"If you can get by with West-European characters (on Windows), " "then you may choose ##try ISO Latin-1, then UTF-16# for the output encoding. " "It is possible (but not guaranteed) that programs like SPSS then display your West-European text correctly. " "This trick is of limited use, because it will not work if your operating system is set to a \"codepage\" " "differently from ISO Latin-1 (or \"ANSI\"), or if you need East-European or Hebrew characters, or if you want " "to share your text files with Macintosh users.") NORMAL (L"If you already have some UTF-16 text files and you want to convert them to UTF-8 or ISO Latin-1 (the latter only if " "they do not contain non-West-European characters), then you can read them into Praat and save them again " "(with the appropriate output encoding setting). " "Other programs, such a NotePad and TextWrangler, can also do this conversion.") NORMAL (L"Finally, it is still possible to make sure that all texts are ASCII, e.g. you type the characters \\ss and \\o: " "as \\bsss and \\bso: respectively. See @@special symbols@.") MAN_END MAN_BEGIN (L"View", L"ppgb", 20010512) INTRO (L"One of the menus in several @editors and in the @manual.") MAN_END MAN_BEGIN (L"Write to console", L"ppgb", 20110129) INTRO (L"One of the commands in the @@Save menu@.") NORMAL (L"You can choose this command after selecting one object. " "The data that it contains, is written to the Console window " "(the terminal window, if you started up Praat from a terminal window), " "in the same format as with the @@Save as text file...@ command, " "except for the first line, which reads something like:") CODE (L"Write to console: class Sound, name \"hallo\"") MAN_END } /* > I would like to be able to extract the duration > and pitch measurements of several words in each utterance # A Sound and a TextGrid have to be selected first. textgrid = selected ("TextGrid") sound = selected ("Sound") select 'sound' To Pitch... 0.001 75 600 pitch = selected ("Pitch") select 'textgrid' numberOfIntervals = Get number of intervals... 1 filedelete out.txt for interval to numberOfIntervals select 'textgrid' tmin = Get starting point... 1 interval tmax = Get end point... 1 interval duration = tmax - tmin select 'pitch' f0 = Get quantile... tmin tmax 0.50 Hertz fileappend out.txt 'duration:6' 'f0:3''newline$' endfor 0.225953 377.677 0.170586 376.039 0.328049 376.521 0.275413 378.538 */ /* echo Band powers: binWidth = Get bin width approximateDuration = 1 / binWidth call band 125 160 call band 160 200 call band 200 250 call band 5000 6300 procedure band fmin fmax bandEnergy = Get band energy... fmin fmax rmsPressure_Pascal = sqrt (bandEnergy / approximateDuration) intensity_dB = 20 * log10 (rmsPressure_Pascal / 2e-5) printline 'fmin'...'fmax': 'intensity_dB:2' dB endproc */ /* drawing overwrites until Erase all */ /* pitch in readable format */ /* End of file manual_tutorials.cpp */ sources_5316/fon/Spectrum_def.h0000644000176700017670000000234511621706664015313 0ustar paulpaul/* Spectrum_def.h * * Copyright (C) 2002-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #define ooSTRUCT Spectrum oo_DEFINE_CLASS (Spectrum, Matrix) #if oo_READING if (localVersion < 1) { for (long i = 1; i <= nx; i ++) z [2] [i] = - z [2] [i]; } #endif #if oo_DECLARING // overridden methods: virtual void v_info (); virtual int v_domainQuantity () { return MelderQuantity_FREQUENCY_HERTZ; } virtual double v_getValueAtSample (long isamp, long which, int units); #endif oo_END_CLASS (Spectrum) #undef ooSTRUCT /* End of file Spectrum_def.h */ sources_5316/fon/manual_exampleSound.cpp0000644000176700017670000026723011614424562017231 0ustar paulpaul/* manual_exampleSound.cpp * * Copyright (C) 2004-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "manual_exampleSound.h" #include "Sound_to_Pitch.h" static const char *data [] = { "------------------------>8??>=??", "?;??", "?0???3???8???:??0300?>??0100?>??", "?????:???9???2??>:??>>???6??0000", "0;000?000>000300?>???7???4???7??", "?:???:??0000050008000<000>000=00", "0;00090009000:0007000400?????5???9??0200", "07000>0010000<0005000100?>???>??", "?=???>???7???5???6???:???7???=??", "????0200010000000000030005000400", "?:???3??>=??>>???1???2???8??0400", "01000200????030002000100?;???:??", "?:???>??010002000000050006000100", "?=???8???5???>??0200070004000500", "020007000700?=???;???6???8??????", "?;???9???7???6???9???>??05000900", "0?000:00060005000200?9???7???0??", "?0???1??>=??>8???0???8???=??0500", "04000500050009000600050000000000", "?4??>???>;??>:??", "?1??????=??05000000?=???;???;???;??", "?9?????", "?>???:??????????????0000?5???7??", "?001<00220024002300", "1>001700160014001600130017001700", "1:001:001<001<001;001;001<001;00", "1:001;00150011000:000>0013001<00", "25002;002<002:0026001=0018001500", "11000:000:000?00110015001;002100", "2000200021001>00180014000?000:00", "0100?????7?????090014001800", "1<001=001<0014000>0009000300?=??", "?7???7??????0300070007000=000<00", "10001700160014001100120012000?00", "100018001:001400140017001;002100", "330034003=00420044004=005=006800", "730082008?009:00;300<700>7001101", "5401=001=702>60300048?03?;020602", "><00100015009700?02", "3603>902:7022302770120017=00;2??", "02??89?>7=;?>:5??7000>3003:01", "9601>5019<01=40082??:=?=>9?;;;?:", "55?:=6?:;3?;;8????>9?>;2?=63?<:3?:3:?9>7?7=1?6", "03?723?753?838?:=2?:>3?;::?;?0?:", "40?;64?956?837012?03>903040377021103", "?<0203035202960038??91?=8:?<<=?=", "16009;036908750<9;0?89100=0>::09", "40046;?>1=?:<:?896?902?<3=00?:04", "8309110=530?9;104610<30=2;0::605", "9500=;?;03?893?670?70>?:31?>5803", "2308940;210=9>0<9:0:>:063>02?0?=", "6;?:92?751?6;7?660?81>?;00?>=100", "1203?20301043603700175??8:?=<>?;", ":5?:0??:42?:>=?:<6?;>>?<2=?>27??", ":=??>2??:???05??75?>30?>52?>07??", "00002=013102:0027>02<:018;004???", "64?>>4?=09?>;;?>>:??710104038204", "=105:206?106<1061=06>;04?602?500", "9:??72:?>7:??;:0162046;06;?07", "<1086?083:0733060;05>1037802?800", "<4??6??>6??=09?=35?=92?>81001802", "70032<04=2039<02>>0075??45?>0:?=", "24?;:4?;88?;8;?:92?;8:?<4>?=59?=:1?<87?;", "36?:=1?8;9?7?=?6=4?6;6?6;1?60;?7", "7:?7;:?73;?839?968?:=5?:0=?;47?;", "64?:=;?87:?7:5?6>5?636?7>5?75??:", "56>015;021:03>2028<00=5?<75?9", "<>?91>?;<=?:>=?;<:?>9?0111027201", "360377052006;606=<0755087606;002", "88??58?>?1?=0:??7>029?06;=0:>80=", "470?;<0>:;0;1807;00244??36?=62?=", "94??>:01?7031=06:708;>0:920;2>0<", "600<050;:=074:0344??96?;45?8=>?6", "87?824?<<>??5603>=064:0955097707", "2<05910219??69?;0=?9>1?712?725?7", "85?8>5?:79?=:101", "30003>?>56?<<=?9=2?98:?:<7?;", "1=?=5:?>78??5=00>20014010201:000", "39001:001?00610013010802=7024?03", "9?03>6030704<303;>03;50400069;06", "19074;07?206420695053206:6078308", "5:09:=09?1086:07?304;50230013600", "87009201<4024;04?004<6047204;=03", "<3028;013<0028??25?>09?=22?<20?;", ";0?98>?81?>", "4>?>73?==:?;82?909?7>>?43??336?2", "<1?1>9?1:=?296?413?60>?7?8?7", ";=?7;3?641?54;?398?122?0=8>>;;>>", "1>>?1?>?:?>?0=?178?204?49=?622?:", "<=?>9804=?08300;500;>806?9?>98?5", "=6>=18>;?5><2=?28=?:7504=60<;;10", "3311;?10:10?6;0=530;780:=009:907", "?;02>1?=40?;0=?;15?>;7057210731;", ":<237;264523791:?<0<56?><>?2;9><", "75>=21?46:?>;4096813111:6>1=<=1=", "<41;99174<112909=7??89?6=:>>29>:", "9<>943>>118", "1113740:<5002>?73:>?97>:6=>9>;>:", "97>>19?4:1?:9600>404700750085507", "3=04>>??89?;8;?70;?48>?163?16:?3", "57?6<6?978?=140199033304=203?802", "7301==??85??2501=10339063608?209", "6?0:9508630587025300:??><2?>7=01", "=205>;09><0<=30>:?0?560?;:0=3?0;", ":008?=0585031401>4?><9?=9>?=1??>", "407?;03", "17??07?:12?6:>3??=???87?>>??;;1?888?5", "=0?2;>?0=9>?37?0<0?196?34;?5;3?6", "77?748?7<1?560?314?1>9>>4?>=?<><", "03>>31?098?27?41>>1<>=0?>=?;>=52>?<3?1", "73?5<6?;43043;0;0910911318130;0=", "140399?90=84>;13?03>?:3=04", "9:0<=>14=;1:131<7519=:1502121?0<", ":?059101?=?>44?=18?=>7??6705?50;", "<6138:1<>=2225244<2001189?0<>>??", ";6?48?>>92>=88?0<4?7<202840><217", "?81=472189209<1:581199078>?=4;?3", "45>;59>8<:>9>1>=>1?4;;?>93087<0?", "8713303=?42;>?", "99><85>?5>?3=1?759?<30003903", "0<0596053<05?403:101<5?>0?:", "98?8:5?7<;?740?9:;?;>5?=80??4001", ":9028;038;04<5051008020:530:5:0:", "=00941089>05:202?000;0??06??0300", "=?017504>806=;08?60::;0<5?0=140=", "9;0;6409;406>603620167??4>?>=9?=", ">7?=>6?>3?006<01?601:701=100:???", "89?>83?=;4?<0:?<54?;79?:8??3=0?32:?4>0?4:5?5???5>6?5", ":5?5;8?418?32:?138>?67>==3>;2?>;", "=<>;8:>=92>?=083507:?05;303=;0126019;01;702", ">8037>05:407<209850;9=0=860?9;10", "3511;<10890?930=050;6:09;;080<09", "6>0:3=0<290>540?440?440>;?0<=80:", "0609>3074=079?076<084?09250:740:", "770:6?0:=<098608>806180509031;01", "76???1?>1>??;7??2001=202:304<205", "=1050=054103?:008;?>57?<=:?:57?=1>??82??91??23??143?>7:?=4;?=", "87?=8;?=;=?=93?>74??=???2;005<00", "55002600390030016102950322050906", "270684054804610341023901>>001601", ";>01<102?90338051=069906<606<806", "2306;7042703780180??;??=>8?<0?=3=?=0>?>?8?>3;??=??>20?>80?=", "4??<:8?:;8?911?94=?888?7?1?698?6", "23?699?52;?58=?4>??364?3==?295?2", "73?254?275?250?376?343?3;4?2", "2:?213?199>?18>?52>?98>?41?0:0?1", "71?3:=?461?549?6;:?689?604?6?>?5", "6?;93?=", "43??:700210256030704:?031203==02", "52022;021703;?04=>06=?08800:900;", "?>0;240<4=0<130<4;0<>:0<1;0=480=", "580=4;0=370=550==00=;:0>=10?6410", "91100810950>040=6:0;340:<009=?09", "8?0:510;?20;400?>9>?>;9?>>5?>2=??51??46??0?>5=?==3?<62?<=5?;92?;:9?;:6?;", ">3?;9;?<:5?=?2?>=4??6300??00>000", "4300<7??>;?>=5?=2=?=2:?=8;?=25?>", "4>??=200?<011<034104>;04>1043304", "2403==018=00;5??51??53??900", "<6004601=2011>029;010?01;000>0??", "=>?>62?>1;?>41?=38?<>8?;;>?;2:?;", ";9?::2?:5?4=6?353?3", "<6?2;9?1?3?06??0=>>?;<>?>6>?26?0", "0>?10:?289>?>", "6;??1=005700:0003301=102=7039;04", "570693073?087808<20870096?09:809", ">80:050<=20<860=550>=90>8=0>==0>", "5>0?360?7;0?0<107;1085101910?10?", "5?0?8<0>5<0>510>9:0>=00>7;0>200>", "600=9400;3=0;0:0;690;800;7>0;", "7=0;010;6:0961070606;:047?034:03", ":>03<10364033203?:02220214013:00", "9;??0=??619?>:>?=>?=16?>54?>63?>1;?>77?=", "=4?<41?<99?;52?;92?;?6?;85?<69?=", "5>?>?6?>58??;;??>2??>=??=>9?=>:?=43?>23??>8?>18?>68?=;:?<", "6:?<84?<84?;9??;1??;8:?:?>?937?94?5", "<9?443?40=?4=??39;?378?349?389?3", "32?43:?461?406?5<8?41=?491800??004603", "8205=4050305:004540431031202?:02", "?=04:606;:08910;;=0=<;0=>=0<<70<", "550<530;300;010<:30<330<0:0<>10<", "3<0=230==70=790?8410;810=?109310", "1;0?>50<800;290;9<0:0;0:7?0:450;", ";30;==0;300<;10<0?0<6>0:21092608", "?:06?=05;;05;7054?05<504:7046504", "7:03<3028;022?025=01<;00=;008500", "99??34??8=??>0???=??2;0087005300", "8=??13??:8?>=7?=0>?=:7?<;1?=2?>2;??18??=2?>63?>???=", ";;?=:7?=;7?=76?=?5?<=3?<<4?<:=?<", ";:?<19?=57?>46?>?2?=25?=", "8?75;?502?633?682?6", "3??608?6:6?5<:?4;?58?503?518?566?5<;?5", "53?686?7?>?848?:24?;33?;11?;8??;", ">:?;293?>=3?>4600=90127038?04:805", ";00599047;03?102510209021503?<04", "3607::09530;1:0<020086?09570:=50:370;6:0;", "090;240;5>0<:;0=4<0>570>2=0>500=", "640;6=09;=085608;00712085809700:", ";20:550:<:090009050896073807>206", ">506?80671069;05>1042;043;037302", "4<0283029002890294026=026>026>02", "4;022<021702>9019>017;0180011<01", "81001800>8??74??<>?>83?>76?>7;?>", "?6?>=1??600091009;007;00????49??", ";=?>52?><8?=78?=<5?=03?>>3?=;>?=", ";0?=4:?=:9?<=;?;03?;?0?:22?;85?;", "79?<7=?=36?><;?=0;??9>1?8<8?8", "1>?9<7?994?:30?;7>?;35?;>4?9?=?:2:?<7;?;92?971?7", ">1?571?58>?548?646?7=7?710?8???7", "91?765?75??813?95?4", "00?58;?5?9?607?851?89>?89>?8???7", "6??7::?8?2?:40?<;0?<98?<>2?;;0?:", ">;?9433?>:0?=>;?=", "1=??5900?<001801:30015003?00:600", ":70180030305630542057<04>4027?01", "8=01<00233047?05>506?10762075;06", "1206580630079<0874092<09=108>?08", "15095008;606<>05?00573067<079?08", ";=09?:0:600;>>0:<1090<08?9067:06", ":>06?60726093;0994086707;8055504", "2;044?05=306<>078>08;:087107;605", "2904=8022;021?021703540463041=04", ">?031=032=02>101?:012?02<:029;03", "21044004;703<;02<301:=00>?>020:010:??86?=4=2??", "1=01?50008??;>?<16?:=0?769?757?9", ";;?<3:001>023;0193?><:?:<3?6>2010?020?00", "8>?<74?7>7?1<>>>7=?080393?>61?849?392?:", "8<00=203980175?:74?3:<>?71>?09?3", "37?954???102>:02090087?;;=?7<0?6", "2=?742?71?93;?<;6??<>02?<95?;::?<09?>75??9:00:;00", "290008???4?<;8?;;5?<8;??:3022405", "=006=906=?047>0180??>2?>>5?>;:??", "<000;<01:301><00?90146052;09200;", "220:5>0799044=03:60296010501:601", "2>0365056<07<2086109?<08:7073606", ";>05;;0574052905<0047204?<040606", ";<06;=064906340685067207:1086308", "8606740425032:03=:03<20463051705", ">8042805>204=:03<70244024902;:02", "7403:403:<020402:102:>03<1042=05", "7<04=>025201>5004;00;7?>72?=;:?=", "=9?007?022103<9023503=>035>03", ">0??>;?;38?;=4?;1??=58>?<>7?<;4?=0=?>;4?>7:00", "<80068?==3?988?9:9?:2>?<=6?=48?>", ";=?=>9?<5>?;37?:71?<8600590225??", "9;?937?5=:?39??6<;?::;?>3202?603", ";30034?;?;?7<;?60;3?824?74:?935?;=>?<58??7=01", "75??2:?9:??4<0?6=5?<9?01:1024???", "5:?:14?7?9?6???94??>15018?0074??", ">2?>?>?;66?70;?78??;64??0501;200", "3=?==:?95??:?8?5?=11?=88?<30?=>9??1?032003:0??", "3>?<=8?;5;?=75??=5012802?:018?02", "==01>8??3??>>;??1<03>=045004=?01", "4=0038008;01>802<>02>3012:01?000", "5701>001<802>;04<=067806;>039701", "7400:8004702:7035;049?047=044503", "?6012602<;02=703>005>006=5062006", "4?03=:??66?>?6???102;05", "::04;;0254025<039<03;;02=1018201", "<8011?02380386043904580306026>00", "5600>3010303;>02=801=>00;???64??", "7<0048017;000=??9=??9702<205::04", "3400:4?=9;?>::0060014100;=??57??", "2:?>:;?>9:00200171004:002:??;9?>", "16018<02=3?>02?957?87=??7>073>09", "7002>0?:;=?9>0?<>81??5=00>??>", "8??<06?=76018803>6002:?>>;?<23?=", "14?<=;?;17?>1801=>035=03;>???7?;", ">7?<;7?<80?95??8?>?<>30242057;04", "35??0:?955?8;>?:>=?=8=022003;1?<", "5;?973?>2404:>0217?=05?826?9:0??", "200310004??:30?;89??50000>???0?>", "27?=1:?<3=?>71??<3?=602", "61037400;0?;<505", "=>037??<<:?89<401>504:8055005", "1703<;?=61?:68?;36?>44012703<703", "4303380159?>=:?=>;?==3??0:027701", "?=0029024202?5??02??2601=4022<01", "?:?=;4?<19?>460170037503>1013200", "4900=8??04??<>?=<4?=2:00>8021105", ":403>8??>6?<30137?=4>=020<056<033901", "3>??7;?==??;:1?<::??35033:054=04", "?600<0?<08?<3=?>660148055<071004", "?6?=15?;21?<=0>023704;4043102", "8;??70??>500>>00?8??49026<04;<02", "<>??>5?<<1?>0=048604?>0018??;700", "=<023802:;?>>8?>2104:>061?04<4?>", "5?>53?=2:0138052?079?04?7?=<=?9", "9;?<:?01<:0401050<0264??9>04?<041<:?;>4??", ">101;400=5??8=00?0027?0301?><5?9", "8;?<>3025?07<005>??>03?=", "=6040?032??=77?<3;007<034:0276?=", ";4?:47?>6203;;??", "1??>;7?=:2?=7??>0;01>80026?=9??=", "4103:<04?1?=58?9;:?;1;00<3015???", ">4?=0400?401:?<:3?>7=?=89?<1:?=", ">4?>1900?=??<>9?>60?>", "4??>>:?=>9?<>2?=1600;300<030=00=8?:89?894?;=001", ":903?3??99?>59?=5>?:56?:38??2804", "<40248?<7?><4?><3??8?0093006>5??85019<015=??1=009602?102", "8901>>???7??9701?=0038???=??<002", "3:05=<02?9?=6=?=7?00<502>4042;05", "9701430099037<057;04=40019?>", "8=0008047<05=60479011=?>06?>1702", "9505?2050=026=?><1??;903<:069;04", "38??=5?:0>??:90654083005>4?=42?:", ";<002>0846079302:700?????1?=5:?=", "<>00:706>;07080283?<:5?", "0??;33?=70033;079=0470???:>?950?925?>:803", "><076504=3?:33?90=008<038?0?:", "62?<2:018604;00223?><=?911?;930?=>5?>41?>98?=", "03?>7<01<202<;?>:2?8<;?650?:<301", "<40760047=?971?4?2?99?00840292??", "49?<17?:80?<2=028;01:7?<36?:;1?;", "17?>3>?<>0?;2600090121?>>2?:68?;", "0:??:;00:;0168?>=>?6:;?646?>:>05", "0606:8?>2>?8?:?7;??<290178033301", "3>?<:=?<=>??1>0127?>91?<8;??9600", "=>?=<5?;4=??6:049:023??><1?=0=?>", "5=??::01=20167017>??6=?<5=???604", "7?0291?>8>?=7;?>6103;>04>100=:??", "3?002802<8035901<3??67003:020>04", ">501==?=0>0002042206;404<:?>0>?=", "2101?2047=06850406056504110098?>4201<<05?9064=02", "4>?=;5?>2:0499079=05010016?>?0??", "8204<8064103>>000300=00008036704", "310269??;30125041:02", "=8??;?02950391???3?;53?>=?015:02", "070079?=;0?>39029?02:8?>???:?2?:", "6>??2:025600???>36??=;?=0>?=2500", "770092?=:;?<78?>>2??758?<", ";;?=<>?>07?>::?=?;?=:0??<0?>7??;", ">6?:2:??8102090129?<24?90=?:=??901?:>4?=9801=400", "47?;:;?:35?=?0?=;:??:4??:0?><:?=", ">8?;07?;8??=440060??>:??>:?=78?:", "85?<5;01=>02<0?>76?9:8?:3?01;302", "100096?>>6?<1>?=83??4??>?8?<>1??", "27015700:???73?>653??31008401", ":>??22?=50?>=>???800;40101000401", "43017>?>5;??<90149035902;30?>", "270121022402>200>7;??05027302", "<=02=5033901>6?=?>??5;0487030301", ":100380065012302;:??15019504;?03", "6?00=7???501650496029900=4002401", "29030404350268005800600224033;02", "==01;90195017?01;6011?032;02=700", "28007=0022021803;4020001???", ":502=9032500>5?>92??3700>703>004", ">=??16?<44?>5=04=<046500<6?=06??", "1900?900<30260012>?>:>?<6=?>2<02", "740392019???8=?==2?<99??>>012>01", "=9?>87?<:7?=?500?70013007;??48?<", ":6?<=7010?0230??5>?<<9?<<7??:1??", "<2?<55?=?8??9>0065?>8=?<98?=;9??", ";=00>58;??3:??", "8:?=63?=3:?>>??>?1?>99?>:5?>2?>69004>??3>?=26?<:4?=;3??92??", "74??<3?>57?<20?=62003;006>??=", "30?=9>?=<;??>;002=??8??024???;>?;2>?=;6000>0294??86?<", "2>?>5?01=20020??1;?>50?>;9004101", "84??:7??80??8;??7100><00:801?1??", "99?=<=??0803720236??78?=0:00;203", "90029>?>48?>;8000103290286??12?>", "0?008;02=>02>7018:0067??=8??1?02", "60036>02>3?????>990149037:01?8??", "07006401140343027>??>=??94013>02", "470302023???24006902>4028>018>?>", "0>??<9021605530236?=?=?<>=023006", "4>028>?<34?=79032=05?<0008?>;3?>", "740065035>047;0064?=57?>>900<603", "0:0346??<9?<2;??4:030>04:;??75?<", "<7??;103>1025;3?<>4?>6>024003", "3:?;<3?>:?018=0157002??>?3?=", ">0??>;01210168??7??>7>?>;2??>;??", "18003;??;>010>0017?==2?=>5??<60075??", "5??=>;?<4???5;02<=003;?=61?<>=?>", "?301:700;4?>60?=;5?=8=00>2??9??=", "=4?=<:?>?4??0=00<4?>;:?=89?>9200", "?80063?>29?=30?>51005>0156??95?=", "0:?>4????>009<017>??8??==6?==1??", "1301>7??;5?>33??>7???4??87?>14??", "::01?1005=?=:;?=8701;1016>??=:?=", "12??7;01=10146??7>?<;1??:3038502", ";=?>19?=:0??84022;03830009?=;>?<", "8>006204?6016:?=14?==900;9032?02", "?;?>;?>2:02", "4903??00;9?>9:??<0000?02?50179??", "02??7<00=:0114014=0087??4=00=801", ">???>???0<01>:??=8??:=01<301;3??", "9;001<01700028006:00:60149011>00", ">6?>6;??=>01:802=>0030?>8=?>8=01", "0=03180181?>65?>0000;?02:102?;?>", "?6?<86005>03=<01:7?>0=?>65001502", "><01>7??;5?>43??33010;025;0021??", ";3?>5100;5014:00=6?>41??96018>01", "=9?>:4?>6100?;00=>??=6??290083??", "=000;007;??1000;7??988??1<00", "<200<;?>54?>7:008>017600<9?><9?>", "15006800=1??2;0096??89?>58??0701", "9=00???=;9?=>7??9000?3??0<0051?>", "88?>3;01;20083?><1001?200::?>", "9>?>92006101::??=8?>97??34005:00", "36;00?=00", "49??64?>77??8=00250068??66??3=00", "910031000:0045??2<00>100;", "9:??>900:1??73?>=:7??480049001=00?;?>54??4601", "9=0060??=6??53002>004=??84??5?01", "77009>02:700", "2001:0019???=??>=5??40004=001000", "0;004400290024003<0038003300<>??", "66004<008???9>??<3??93008?00:700", "=4??95?>:700>001=?0014??67?>;=??", "2<01>:00;2??5;??3900:2001100>4??", "4>00?3??????<000710099??:1??7500", "<<00<3??501710064???9??<=002300", "2?002601810002??6???>>000701;8??", "50??6???780058019500;2??84??5800", ">4000<002>=?>", "2;01>201701550074?>", "3;??31008;0058001<000?00:7??6400", "19014;0064??51??<:00:<0057??8;??", "::??:3??:6??;5001:016:??80?>;6??", "4?01:50086??40???3??32016300:9?>", "=9?>5?0046008>??8;??020045003400", ";???55001601=2??4:?>39???5001800", "88?>99??72008=??91?>3800=4002>??", "6???4=004700<7??000032??28??", "9>??8=??1=00:;00;:??89?>7:??>400", "3:00>?7??;60076??<11008?00", "05??7;?>07007;0068??=:??72003=??", "10??>40019011;???2?>36005?005:??", "6;??0<00=1???3?>?7??1>01>>??3=?>", "5400160242??:8?=74??9601?:002;??", ">;?>>1?><5??<30166015>??:5?>5;??", "9300:7017:01<=?>23?=330008031201", "57?>:9?>6<0086005>007501010107??", "48??;?0034014???:8?>>300<700=8??", ";0??=3??>3??88??9401<=014???18??", "10006301??0004??96??:?001=016?00", "?=???;??;>??700068009>0006014;00", "1=??63??>301>201?9?>50?>?>??5=02", "=:01:6?>>:?=71005>023;01", ":0??8101;=0087??7;0054017:??82??", "5=01500101??77:01<701>;??9", ";=??:>0199006:?>73?>5500<<005900", "8900", "41??=4?>?:??>1004>0013??;>??>;??", "36??:3??4>00?20058??9=?=73??6?02", "1>01?=08002>014300:=?>:5?>", "5<000301360059??17??6;00?600;0??", "=1?>12??27003:006>??0;6?>=700:70115??04:?=;;??<201<00083?>99??", "260196008??8;00530059??2800", ";5??;6??<000?5003:0088?>56??;;00", "7:00=???63??4900;000100009001700", ":900380050??60??0600?:006700?3??", "?9?>15??>2002=010400>9???;006301", "70004;??9;000=0178??=7?>26002701", "=2??;1???0001<0139005=??>;006;??10??8:00;8010101=9?>", "=8?>30011=0235003:??>7???=??8000?90096??45??", "9600=;???2??00019>0078??<0??7=01", "6<013:??7>???5002?012?00;7?>94??", "=<007901;3??7??>9???020102010:00", "56??10??35002;01>6???1?>4800<100", "70??55???800:500;8?>4=??4701<<00", "44??64??30004>00720031??28?><8??", ">300920018??64?>5;0027016;0018??", "17??6101750093?=30?>", "3201==0111??8=?<;=501<>0091?>", "<1?>98??:70066014", "11?>58001301;2?????>48???5?>3200", "6:01<6??5;?=5;??5<01=100:1?>?4?>", "?>00:2??69?>5=00;4010200?8?==6??", "2403:>0084?<71?=:?0123033?00;=?=", "60?=;5??2902>800;9?>?;?<;7?>=?02", ">>0252??<=?=3100>101=300;;?>7;?>", "13??:=0087018;005=?>52?>;001<=02", "1200=>?<<:?=11020?02>7??58?>3??;8??;?001201:700", "84??1100;8004>01600154?>:0?<=>??", ">402710167?>85?=89??>201>6027600", "12?=?=?=:902>502381?=;<01?902", "3???80?=4;??1<017401<20089??4", "?5?>;:0125030>0167?>;2?=?:??4<02", "160244??75?=070050028400=??=27??", "<2017=0185??=7?>0?000401320142??", "91?==0?>?5005<01=;6010801", ";2?>2??>?:??8=00>7??1601<;0090?>", "32?>19000802240115?>?6?<40000:03", "=2009:?==1?>2001:900==00=???46?>", "<3?>18008;02=100<9?=56?>7300><01", "34??84?=17004201:=??74???600==??", "1??>94???6006200?6?>69??=8008201", "48007???43??8>??=:00:?00=??=>1?=", "28001:0028000?01;:0167??46?=?6??", "9?02:0001:?>75?>7200:70001002<01", ";:0006??25??=800=60032018=006;?=", "20?>75026=03:0?=1:?=490113010?>=?001>02:8006100=>006:??7:?<", ":??>3:034102471?<05??7=024=04", "990167?;?:?;6;032<069:?>36?91;??", "2<05:;03?3?=;9?;;:??4;02=2016300", "99??3802?9005:?=30??3803;;0117?<", "02?==7035104:2?=62?<5?0168034000", ">6?=0=008001?4004600<>??;=008700", ";:?=3??>15036>011??<9;?=7=031505", "440017?=9:?=0=0084021?0167?>5??=", "3???6=041303;>?;9>?;0302<1043301", "9=?>90?>87?=:09<;?<;9?573?<6:08<108", "56?<>9?74400==0563013=?4501", "06??9048400", "52?<>2?=10024203380130?>13?=402=??>:3?<2;006603==0137?>", "77?<4=??;=01????39?>?;??:602;>00", "4;?=29??1:034?028:?>;;=010401", "5=?>79?>5=000602;100:>?>;9?>6<00", ";>0080??>=002902770049?>89??5902", ">:0092?=?7?<85?>240144024:??5:?<", "3?015>058;0195?<51?=1800>5??>000", "<:0083?=2>?>5702=;01=8?>67?>;???", "5901:40003??;:??65022902==?>74?>", ">1005801;0?>>:?=?001?90141?=7;?=", "5502=<046>0077<02?3016100", "32??:9?=17?>8<00>9029801?=?>59?=", "=:?=1<003?012>0095??<800=?009>?>", "54?>7601:;02=8??15?>1:??6;??05?>", "73??;502:=02>8?<69?;880124049401", ";=?=;3?<5100?903940271?<594??83027?00", "1:?<64??2>042?01>3?;7??<26015<02", "??00=401:?00>1?01=30159??", "2>?=8=?>5303?90218?>???;?1?>6602", "0201?6??<801<2??5??<7=?>1504?103", ";7?=33?;88?>7;01040048??97008=??", "66006703680369??90?>9<019801", ">;??8<00=90192??:;?11034:02", ";;?=5:?<<5??;:022002?>?=71?<3;01", "15053302<6?<>:?:<>?>80034=0283?=", "6>?=9:00930231024000:2??9<50060036:00", "60?=>1?><;??52?>0??>140106034:00", "93?=<5??9?021?01?<1:008201", "6=??>5?>8:0144011;??>;?>???>4601", "6?03:101<>?=74?=;1021>047??>58?;", ":;?>3:030603?;??26??6400:<014<01", "=:?=71?<=5??66028?009=?>20??5???", ":4??0=022102=;?==:?;>>??64049:03", ":9??11?<75?;73??>?03000265?<77?;", "70005105590215?<88?<92025504?4?>", "4>?;52??3?045302?;?=39?=0>??;;00", ":;01?20053?>01?>32015003<10199?>", "=5?=:1????00>800=???<>?>=:?=67?>", "7=004301?7??48??2=014?02:5??43?=", "3;00?<03;10181?<58?=0=021503<6??", "10?=5>?>7901<502160014?<05?>=603", "4>05>6??62?;;:?>52037101>7?=;5?=", "?2?>2901>>02330201??:??<32?>><01", "??030>011??<1=?=?=022:046:??1=?;", "73?=640374047=??21?;51?=75025806", "7804=??<40?996?>2605910233?<:3?<", ":001:203;:0039?>75?>61??>2007002", "5001:;?=>0?<<2??8<02910188?>631?<=;?=22026?04", "?7??;>?:9??=81038>0211?>=:?=3>01", "2302=2??5;??:<01?1009;?>>=??2600", "78?>86??74?>>:?=8>00<:01>101>?00", "2900><007101010061?>?>?=<7??4501", "940092???;?>7;??3>01;601=50052??", "97?><1??9:01==0068?>33?>91??4600", "=40034014200???2;02<=01", ":2??:=?>0>0043005>?>8>?=5:00?:03", ":70206?=>5?;4;0174040?00>3?;?>??", "?>04:8018>?;;;?;0:02=0049300<:?=", ";8?>:5??220155016>??1??>3>??7801", "15022200<:?>4;??58??62??0;01:603", "990106?2:??", ">7003102>00071?=;4?=710233054>01", "<3>003401", ";001>00075??;=??09007:??5>007402", "62026=?>;?<", ">0008904:50256?>?:?<<1??3903<201", "9??=9??<71??0702410116??1;00?;01", "850175??=9?>9:??35??56??1?015<00", "23002401==??3:?>1??>63??<100", "5=021702;8?>?0?<60??0803?40292??", ">>?<=0?==>0124040:0027?;4>?==701", "75037;02=4??609000>01370064?=;9?<1=??", "0>01::02410293?=8;?;>4??8>04>501", "?=?;;=?<62020;0371?=?1?:?3?==600", "140171005700310097??37?>24?><000", "6501<=?=54?;4>?>900152??20?<2??>", "2?03330384?=09?;1>?>=100650027?>", "22?=<7?>=9?>94?=:7?>4:0057?>", "5;?<:6?>230213014>?<9??;24007402", ">6??03?=2:?=06??5200<00055009>??", ";5??6=0031003:??2????>??4900;5??", "902?;02>80101??", "5>?>0<0149033:02:7??=0??:402;503", "2102;9009601?602?40251025502;502", "66025>0205034<03?7014:019502:303", ">4033?049804<;03750225025002:201", ">=01;0032104;402><01=5024204?103", "5602<3013:0244028702<=03;?037<01", "<>??;<000303=0030002660053027>04", "5=03:60055?><5?><90087011:0001??", "1700==0134032:01:3?<64?<68018803", ":8?>85?9<6?:1400:501<;?=5=?<34??", "110007?>79?<98?==2??39??0:6??;0=?:?0?;1=?<83?;56?;04?;6??90:?9", "2:?91=?9>7?:57?=<", ";0?>04?:96?583?7<6?>24?973?4", "95?798?>6?004;?<;8?884?:3??>51?>", "5;?<>:?;62?<", "3>?=?6?>6800>???00?>87?=36??2101", "660110??1;?==6?>9:02>2032?010=??", "?:007;044805?4026601;9026604;;03", "4;0283021=0470059:05?804=;04;:05", "6006??06;0076;075;063505>104=705", ":906670613065106<306310734072107", ";607310861078:05=4046006?4075>07", "7805:>04=0052<07>806:<05>904<704", ">4040?05<;041;04>803>:03;5033303", ">>02=0038:05=905<1037>0116015402", "=20240016>??94??3>01=101;8013?01", "59006600=?00;<0007002", "9500?300;=?=8=?:<1?;8000570251?>", "<6?941?:<2?>:30065?=<7?9<5?983?;", "9;??;", "77?91>?5", ">;?12=?546?;03?<8>?71;?4:4?52??:", "5??<8;?:07?8?6?79??941?:?3?73=?5", "?9?50=?:<9?=>6?=?>?:3:?97?;", ";2?:63?98=?<82?;:>?94??9", "2??<6;007502=200<6?=27?=::??7>02", "3;03590145??83??55013802:7016;01", ">4024?05;7063=06?7048>0454053;06", ":40602079407=;076>07<806>106>007", "?7089009680985081208:50805090009", "05093=098709:0095>09?208:0088008", "<3081;09<>08160878071<0717076107", "96077=0722077>0613063>06;>06:706", ";4056=04=7034=04;704170434033703", ">90345048103:<0116003:00:<018002", "3>024=01530083??=3?>87??<>018;02", "5900448??11??;3?=1:?<81?<7=??", "1>01<4?==1?846?802?<>9?>=7?=;0?:", "23?<98?7;7?87??<5", "1??<58?889?7<9?:79?=<3?;2??74?;92?8?9?35=?31;?89>?;2??;?5?8:2?8", "47?:?;?920?921?:2=?<00?=<0?<", ":7?<8=?<64?<<2?<3>?>>1??24??83?<", "?;?;43?>75008400=9?>71;015604", "1<056>0380026>03;804=704:3034803", "770457058=050106?406310893085308", ";3081009<7089>083?09290:=<09<708", "4:089708:809800:5<0:3;0:3<0:220:", "550:600:180:?309><09:209>7085>08", "740894085108?;07==07;?0735076<06", "36068;06:20637066505<>04>:04>904", "73040004=303<1035<039<02?701:701", "9>01840141012001;>00;1??::?>:8?>", "97??3400>2??>;?>1:?>04?>07?>58?>", "27??747?=77?<31?==;?=63?=", "57?<;;?;16?<38?=04?>03?>58?=35?<", "91?;23?<4??=>8?=76?==?=20?;?=?89;?99=?;;3?<", "23?<:5?;57?;;;?:96?:>??86>?85=?7", "?:?71??::7?;:4?:84?8<3?7>1?7?6?7", "9:?878?98;?969?97:?952?96=?886?7", "5??842?:>;?;==?<42?<2>?:2=?820?8", "82?:02?=;9?<:9?:90?929?:8;?;?0?<", "6??>9????7?>>;?<31?<71?=21??82??", ";>?>29?>:8?>6200:;01:50142015?01", "??0147038:041;051705=3038>028=03", "<60554079807;=064?06>206;7076108", "2;09?509<209:0084608:008>;084209", "8;09190:970:370:<809>509480:<10:", "860::309220925093>09<:080208?:07", "3008?80791074<0784071308;3078906", ":2051?0550054905::0405043003?202", "54039>03;:033?036802;1011<010201", "15019700>=??52???>3?><1?>>:?>", "1:???9??>2;?>?=?=32?>6;?>09?>", "54?=>=?<>3?<>=?<8>?71?>28?=0?<6;?;", "48?;1=?<>2?=0=?>033?=40?;<5?:6=?;>5?;?3?;76?;", ";4?:17?::3?:;>?;=2?;49?;0>?;;6?;", "27?<>:?:?;60?;:0?:5??9=1?733?762?885?:", "80?;09?:3;?836?824?971?980?9<>?9", "?=?937?:=:?:92?;7:?;69?:79?9<1?9", "57?:17?:0??:42?::1?:8??;=9?<6:?>", "47??>5?>;4?=15?<06?;;2?;72?=1=??", "85??:9?>66?>29??3=00370114020703", ";9037903>602:=027302;8023503>903", "0705?>0595064?076?0816091509<308", "2108880750079;075308>90824095;09", "9709230:0:0;<<0;=00;1<0;630:280:", "2?0:;009<1081?08=0074308>0080209", "7;09<30945098<089>07>;06<5067606", ">;05470598045204<5045=055<058904", "<203;=030804?;032;039?017=001700", "==???4??0:0004002700>7??7?>88?><2?=42?=15?=34?=61?=", "2??=<1?<9;?<=?;5>?;>>?;66?<=1?;40?;", "7??;;7?;78?;>8?:0=?;1=?<89?<>9?;", "41?;07?;=5?:9;?:?;?::;?:", "82?9=1?842?9;?666?795?8=3?83;?99=?9", "9?89:?9:5?:16?:4??9", ";>?9>9?::5?<2??=87?95?>", "=6?>???>91??87002;012101>=005101", "3302;802:;028>02=70259031904?<04", "?20523079=0779073;074507>=076808", "66086708;3083309:>09<409<;09540:", "=?0:280;3?0;130;=20:;80:970:5<0:", "490:3<0:340:740:750:6=0:650:320:", "000:7?09:108<>075;0747074:073<07", "?>06=406;506790613066:050305>104", ":1042104160300027601370129011501", "030122012601>9007900>3??35??;=?>", "69?>=??=67?=06?=97?<8:?<;6?<>5?<", "28?=41?=3;?=0=?=:2?<20?:3>?;2:?;<5?:?2?:53?;", "74?;35?;58?:96?9:?850?730?8", ">9?94;?:4>?907?9;0?:34?<4??;3=?9", "?3?727?815?944?:64?;85?;<5?:07?:", "32?:3=?;?5?;?7?;93?;>6?;01?=:9?=", "58?=65?<80?<59?=:3?=96?=;", "<=??470006001300?600780168018101", "340227038303=:039=040>05=604:804", "650594067307;50790078=0734081?09", "7:093>091:0980092:0:;50:>60:>60:", "3<0;730;270;240;560;7?0;6>0;260;", "4;0;6<0;2<0;=00:580:>509:909:209", ";:09930953091>0990081208>=07<707", "6=07;2062506?5059<055=05??04;=04", "89040;048803>=025902>40142019=00", "1;00>0??>6??:>??54??3???3>??4;??", "36??>8=?==6?<5:?<=;?;93?;", "30?;>8?:1;?;57?;;4?;", "9;?;=5?;73?;45?:55?919?96>?90;?:", "63?:1=?:9>?93:?93:?8", "1=?936?9=0?858?8>8?846?:0??;94?;", "6?9?=?821?:<7?:80?:85?;24?=2;?>39?>", "<:?=40?=>0?<;9?<<4?<49?=41?>1:??", ":2??100031003;000<0150029<03=>03", "0>03730261024=035>04<=0440059>05", "3806;406;=065>073208>>0868090;09", "0>0940095109?9097<0:1;0;740;3<0;", "720;7:0;6?0;900;:70;1<0<280<930;", "350;0=0;640;;70;670;?60:7>0:890:", ":=0:330:8209=6084>08?207:;07:207", "8<0770074=07>5066606>50573050?05", "8:0407045?039;0233020002;:014701", "1??85??63??3:??==?>", "8>?>2:?>>5?=:7?=3;?=>;?<;1?<7??<", "59?<0??<89?;05?;=?956?953?9:;?919?:", "11?:00?:6>?:>:?:==?:=5?947?8;;?7", "=3?8>??97;?996?7<4?6>1?71:?958?9", "0:?990?814?8:8?79:?795?7;1?700?8", "65?8?>?818?947?854?730?710?8?4?8", "95?815?806?7;1?85=?:", ":>?;?3?;0?::2?:", "82?:28?:99?9<2?982?:08?<:1?=00?>", "69?>?5?>?3?>0;??62?>20?>>4?>19??", "0????7?>=4?><5??37010103>=04>305", "0;068205>204::04<>043?05:>050=06", "5?06<<0681075?087109;;0:960;>10;", ">10;910;5=0;500;030;0=0;4;0;500;", "990;>=0=", "0;0=2>0<480;;=0:930:780:;=0:<20:", ";?0:=:0::60:510:>4095709<:082<08", "7607?:066=06<<056205300523051;05", ">904:9043<049703>?0263029?01:500", "<:???90?>:1?>0", "94?>82?>50?>;7?==>?<00?<33?;<1?:", "86?:66?:5=?:2=?:34?:<>?:66?;97?;", "97?;50?;;5?:>1?91;?94=?8=7?7?4?7", ">;?76>?873?927?:17?836?9<0?820?8<2?732?7", "43?634?6?3?74??9>7?895?75;?625?6", "92?649?6<??8>=?894?81?978?9", "51?901?:44?;44?;70?:04?:83?95;?9", "=>?971?:<6?;7;?=42?><2?>:;?>9=?>", "11??;4?>:=?>=2?>2=?>12?>>4?>4200", "93014?0239032;04:<044105:405:505", "3>05?304760569061807=40746088<08", "0>09;<091=0;800>0=100>660>=70>;70>470><<0=0>0=", "1>0<440;020;5:0;;80;:<0;530;200;", "?90:<50:9>0:5>0:;909<<08<107?906", "7=060506<705830565054<057404<903", "6?032=0318038902<=0156018000;???", "2:??:6?>93?>862?>09?>43?<>5?<;5?<0??<86?;29?;:5?:34?:", ">:?9?4?914?:=5?9<:?9?6?9?;?9>;?9", ":>?957?9=3?85=?863?8:=?843?840?7", ":8?63:?741?89;?87=?875?853?8:4?7", "7=?7???774?818?82;?787?634?610?6", "46?627?6>2?55:?6==?6:7?880?927?9:6?8>>?8;9?9", "4=?:0:?:=;?97?;43?;64?;<9?;", "5>?<32?==5?=03?>>2?=7:?=81?=41?>", "38??7200320136016201<9010?026902", ">502=<03>90466051506>906?<06>806", "12079=076808>>087309870:530;9;0;", ";:0;=10;2<0<6=0<860<010=;00=190>", "630>8;0>630>120><>0==40=0?0>140>", "270>7>0>6?0>090>>20=<90=;10=030=", "2<0<100<260<240<<>0;330;:60:=309", "1409:4089708:0086<081=0874079806", "<90509058704?:03<503=50373030803", ";40207024;018200<=??45???0?>;:?>", "67?><5?=52?=21?;99?;10?;24?:2?620?7?6?739?80;?8==?7", ";0?755?74??7;9?7?5?79;?743?668?4", "=:?3:6?431?556?57>?551?505?5<3?4", ";;?43=?57:?632?7>6?6=7?662?60?735?77:?64=?657?6", ">:?630?84=?951?:7:?:=6?932?937?8", "14?845?9?1?:07?<;=?;?7?:39?;13?<", "3:?=;9?><3??2;003;009>??9>?>>4?>", "7>00;30172026103<:03;2036003:;03", "4505=4068?07550887080108=0076008", ">2096<0;;?0;?60;070<120<610<790<", "6:0=970>><0><80>8;0>5>0>850>030?", "?<0?:8108810:00?<50>310>;70=<;0=", "650>?;0>160?960>070>670=8<0<150<", "3>0<910<6:0<610;420:9909>9088008", "540854084508;>0700075=069<051305", "9<047;0424046?039;02?301=:01>801", "=901?2019>01:8007;>?=22?=", ":=?<::?<95?<0>?<65?;>1?:?4?:5?851?878?81??844?7<0?65??6", "69?6>??652?76=?750?744?75>?7:4?7", "<>?788?7?>?679?6=2?5<7?374?3", "31?3>3?2<0?2::?27:?29>?247?34:?4", "82?400?4;8?3>??3=9?305?37;?246?2", ";??29>?3;2?382?4;4?44=?53=?6", "=1?6:?7?8?70>?9>=?97;?:32?;90?<71?>", ">9?>;:?>620=:;0>:70?2<10=0106;113912", ";:12?4120413=012;3128612?1118411", "02119;10>3103?1178118<1180114=11", "8610680?8;0>=40=720=100=90;430;8?0:010:6;09<<081=08", "7007:006:605<80414049<036>038<03", "=:03>003;=0353038>02:90177005=??", "82?>9?9>7?845?8;1?74;?7", "?5?6:=?656?60:?6>1?5<;?5=9?5>0?5", "0;?626?601?6:0?5>=?42>?499?3??85>?", "7:>?;;>?22?041?027?0>0>?=5>??=>?", "==>?=1>?<6>?=;>?29?055?061?093?0", "0?8=5?856?9=:?9", "77?:;8?;53?=8:?>96??=2000?021703", "8<03>1035604>9043605::0590066>07", "5=087509:80:>90;<50<920=520>?70>", "780??10?9>1032119111>?115=12=112", "201392130>148>14>?14==14>>14:814", "3714?0136;13?=12:?124=1250120412", ";1117>1135111111<1103510:;0?<:0>", ";<0==>0<210<720;=40:410:<<096509", "=40830089?07?6065<06=<0569050105", "930404046703<10205023;01:0003700", ";9??44??=1?>68?>0:?>:1?=55?=1?:>0?989?929?9=;?8:1?864?870?8", "9??78=?738?7=>?679?633?616?6?>?5", "==?5:=?58:?581?580?59;?5:6?591?5", "92?5:2?596?56>?531?5>9?4:8?470?4", "3>?40=?4?7?3?=?30:?41>?44=?494?4", "=3?403?529?544?55;?566?569?572?5", "8??5:9?5;1?51;?666?6;3?610?7", "84?7?2?75??8;??810?95:?99??9;?<", "7:>?>39??<9??5400=:004:01", ":30108027?02?;028103?:038<042905", ";5054106;?0622079907?=074=08;;08", "1;096<09=009190:550:9;0:==0:2:0;", "790;;?0;1;0<750<:40<:?0<:?0<<;0<", "=:0<<;0<<60<<00<;90<:>0<810<640<", "490<24000;<:0;9=0;660;430;", "0=0;>80:<<0:970:740:430:?109<=09", "9<094909?108::08730841080308::07", "4307=;0668060506;?05800540050305", ":;045104?<039=032=03;;024;02=<01", "82013901>:00:00064001=00=2??96??", "50??00?>9??>52?>12?><7?=63?=", "07?=:6?<42?<02?<;??;82?;55?;2=?;", "03?;>1?:;8?:77?:29?:=2?975?912?9", ";7?859?809?8<;?78>?751?71>?7>8?6", ":6?670?64>?63?4?;?3<:?3:8?393?3", "89?37=?35=?345?344?343?34:?347?3", "37?315?3?:?202?302?2?5?2", "1>?347?37;?3;>?3?7?336?522?671?6;9?618?79;?7", "18?881?8?;?883?91??:;??:3>?;<2?;", "6;?<2;?=>:?=81?>24??>9??9?005901", "06029;023703>60393044=05?=05;106", "5?07>2076308?8089309380:<40:2?0;", ";?0;5:0<>00<550=;10=060>600>;80>", "080?560?9;0?>50?2=1060107=10:310", ";310:71097107910671075107?106010", "451030100210<;0?960?590?260?000?", "<40>7=0>3?0>?00=960=3:0==40<6;0<", "090<9?0;310;<60:630:?=098=091009", "8808?<076;0700", "=4??5:??<>?>44?><4?=46?=;;?<33?<", ":;?;2:?;;;?:4;?:=5?974?916?9:;?8", "4:?8>:?78=?724?7:6?630?6<9?570?5", "21?5=3?48=?44=?40?3:9?37:?3", "4??317?3?5?2=:?2;4?290?269?223?2", ">1?1;1?193?186?189?17:?163?15:?1?0?1??3", "73?3;5?307?45=?4;?5", "17?669?6<6?62;?7:3?713?877?801?9", "89?90??:;8?:43?;<:?;6>?<;?>3;??:=??3600=70082013302", "?602:5034;04>4047=051?06;<064807", "=2076:08?8087909?=097>0:?30:7=0;", "><0;5:00=330>860>>;0>", "540?;00?211063107<108:1085109610", ":510;=10?610061119112411?210=310", ";71060101510>30?9;0?530?110?=50>", "850>3?0>?;0=:70=560=>;0<810<290<", ";<0;510;?<0:960:150:99090:096108", "<2072>078606?:058<05040594041?04", "8603>=0251029=01?5005:00;=??29??", ":=?>25?>:3?=41?==0?<48?<6?3=9?3?3<>?3=1?3<5?3;6?3;=?3<;?3", "<:?3;=?3<0?3<1?3<4?3=8?3>??30:?4", "1??43??465?478?484?4:1?4<4?4>2?4", "03?52?928?:8;?:>7?:60?;?1?;6=?<", "=9?<42?=<0?=43?><>?>55??<6??4=00", "=<00650100029;022403<7036?040105", "8=0509068>062;07;7073>08609580:;20:140;7>0;>10;3;0<:30<", "260=930=>?0=4:0>920>;40>>00>1=0?", "470?640?6;0?7:0?9:0?:40?930?880?", "8?0?8=0?640?350?0?0?=80>9?0>620>", "270>?=0=<30=760=180=;60<4;07097609?108", "7:08?<077907?4066?06>=056?05?304", "6=04>>03790302037;02>?015<01<;00", "4300;=??35??:9?>34?><=?=63?=?8?<", "80?<06?<93?;1:?;;6?:60?:09?:;>?9", "69?908?9;7?86:?81>?8<1?4<7?4;;?4;8?4", ";0?4:=?4:=?4:3?49;?482?466?452?4", "5?47:?47??4", "7>?407?52=?561?58:?5;8?5", "?:?545?686?6=4?62;?787?7?97:?9=0?93>?::8?:15?;", "95?;0>?<76?<>1?<5?>?3?>", "6:??=;006>01?30193023803", "=803790417059<05170693060<079>07", "4308=40830099309190:9>0:1?0;9=0;", "0<0<740<=40<260=860=>60=3;0>7:0>", "2?0?670?790?820?6=0?590?640?", "800?990?:70?:00?800?5=0?310?", "690>260>?40=<50=8<0=560=230==50<", "870<400<>?0;9;0;340;;30:400:=?09", "8;093109=1087308?;077407>0063606", "9;051:05:1043804=>036<03>0024;02", ":<01?8004400;3??33??<3?>62?>13?>", ";8?=50?=<4?<2=?<9>?;1;?;9=?:29?:", "<0?96=?922?9>8?8:1?865?815?8;:?7", "5??704?7;0?67=?64=?634?624?60=?6", ">2?5;2?569?521?5?2?4=0?4<3?4;>?4", "<1?4=5?4>8?4>;?4=6?4:=?483?45=?4", "39?42=?434?43=?44>?411?52;?537?53?6=5?627?769?78>?7", ":9?7=0?70;?864?8<?:", "75?:=;?:54?;<;6?>29??;7??5800?50086011602", ":1021<03;10365041;05<6054906<906", "5:07=1074608<5084209;=09410:<>0:", "710;?:0;610<;:0<290=;40=0;0>520>", ":10>=00>010?3<0?520?7>0?:=0?;60?", "<30?;>0?<20?;20?920?8:0?7=0?7;0?", "600?1?0?=90>8?0>2?0>?50=;30=5>0=", "120=;60<5<0<050<:40;470;>=0:980:", "2>0:;5093?09;=082>08;5072;07:?06", "3;06;7052<059;041004870307038402", "?2017<0101017900>???68??=9?>53?>", "=4?=5??=?4?<94?<34?<<3?;52?;?4?:", ":4?:4??6;1?67;?63:?6", "0>?6>1?5;4?590?580?55??537?51?5>1?51>?64;?682?6=8?6", "2>?781?7=5?71:?868?8;>?807?958?9", "=0?937?:95?:09?;87?;0;?<95?<19?=", "93?=0??>81?>?7?>71??1300;5005601", "?<01:?026403?>037=04020585050906", "89062307=5076;08?10880090:0:930:", "170;870;?30;7;0<>:0<4;0=<60=300>", "810>;?0>?80>460?800?840?8=0?9?0?", ";20?<:0?>>0?3;1061105;1043101?10", ">=0?:<0?540?010?=20>:30>640>350>", "020>9;0=2?0==50<770<1:0<:30;300;", "<50:510:<=095509=;085108<1073=07", ";<063906;9052>05;8046>041004::03", "39039;02?60142018=00>;??55??<8?>", "56?>?5?=9;?=31?=<2?<59?<=5?;51?;", ">;?:8?8<6?775?737?7???6<0?696?677?6", "43?619?6??4", "92?475?472?47=?48:?499?4:4?499?4", "83?464?445?426?416?40>?411?407?4", "00?4?4?3=>?3=5?3=;?3=;?3>4?3??48:?4", ":>?4<8?4>>?423?561?5:??508?66?87??8>5?8", "44?9;6?920?:84?:04?;89?;?9?;76?<", "?6?=56?>=3?>64??????:?00", "6<010802:9024<03>40381041705<;05", "7?062707=4076908>=086809?409920:", "330;<>0;500<=70<540=;40=150>800>", "=50>310?750?:60?90??<0?1310", "46108<10<210>21009110511>?10<610", ":<1095106:102=10>>0?9:0?380?>00>", "7?0>350>==0=760=150=;40<550<=;0;", "5>0;?00:820:??097609>3084908::07", "0;078>062606;6054005<<045=04=503", "4=03;9021=027<01=800350097???7?>", "5??><=?=51?=>4?<77?<02?<96?;24?;", "<0?:65?:14?:=0?987?923?9;>?855?8", "?3?799?73=?7?;?6<4?68;?651?61=?6", ">4?5:2?562?4:9?471?4", "40?417?4?9?3>2?3>0?3=2?3<5?3", ";7?3:7?3:2?39?371?3", "5;?34;?32=?316?316?31?3", "33?332?33?307?4", "32?456?47;?49??4=0?40>?560?5;;?5", "19?667?6;;?618?776?7>;?764?8<8?8", "38?9:2?907?:84?:13?;85?;?8:?>12??<2??76003401", "?3019>024703>40386042005:8054406", "?30694073?08?4088<092?0:=<0:780;", "0>0<:40<2?0=:10=150>850>020?590?", "9?0??20?321062107>108>10:>10>910", "1?115211:211<311<;11<911;1118:11", "4:110811=11085103010>40?9;0?4=0?", ">90>7=0>260>=10=720=0?0=;10<510<", "=90;680;>90:5;0:<30919096908;:07", "13078<060;0694053305=2046?04?203", "5503:<02>50125017700", "2??>;2?=2=?=:=?<44?<>1?;7?:83?:25?:<3?950?9=8?860?8>0?7", "6:?7?6?688?622?6=8?5:7?58>?58;?5", "87?578?53??5?7?49??440?4>9?39>?3", "73?366?35??34=?2", ">1?2=??2=>?2=7?2<8?2;0?286?268?2", "4??22>?216?207?2?4?1>7?1>4?1?6?1", "1??272?2<9?20=?33;?363?373?375?3", "82?3:9?3>3?333?496?4?4?450?5:1?5", "?3?557?6;=?62;?798?70:?890?802?9", "6??901?:8>?:?=?:7:?;01?<7>?75??3>000801040?880?>?0?3;108210", "<710><10?:1024116811:811>:112;12", "6112811289129712:11288125<121?12", "=71180111411<31079102?10<;0?630?", "060?:40>3=0>>40=9;0=4=0===0<6;0<", "=00;1;0;6;0::>09?:086:08=6073807", ":;0625069<052<05;9043?04<9033703", "8402;>01?0001300554?>>1?=", "51?=<9?<44?<:;?;32?;=8?:81?:3;?:", ">=?989?901?96=?8=7?74>?7=4?674?6", "14?6;1?55:?50?4", "8>?460?417?4;6?34?267?239?206?2=3?1;5?19??1", ":4?1:8?1:6?194?17=?161?13>?121?1", "17?10;?101?1?9?0?7?0?7?018?163?1", ";8?1??293?2;2?2<5?2>??218?3", "4=?3:0?3?>?36>?4=0?430?595?5?;?5", "6;?6=:?650?7=1?74:?8<;?85??9?0?9", "83?:13?;98?;25?<:??<28?=9??=3;?>", "?2?>:4??61002:01?801;?027<034304", "?904:3054<06?506:;077:083709>?09", "<80:870;340<=>0<680=?50=810>000?", ":30?3610:3100:116311:=11?1110<12", "2=12521264127?129112:912<>12>412", "08133413471345131<13<=1280122=12", "?411;7117;114311=31072100210790?", "?>0>7=0>020>940=170=900<060<6>0;", "<=0:240:8609>00824085>079406>905", "5305<>0461040504920305036602:<01", "=<000<005;??;7?>29?>:??=27?=9??<", "07?<69?;>0?:6=?:???9:7?941?9=5?8", "72?80;?89>?72??7;7?638?6;4?534?5", ":>?436?4=3?39;?37=?377?372?34?>;>?", "?1>??2>??2>?>8>?>1>?=9>?<>>?;<>?", "<1>?<0>?;4>?;9>?=<>?14?064?0<5?0", "34?194?1>4?128?26;?2:3?2=7?223?3", "9>?31?566?6<3?781=??<;??7=003>01", "?=01=402;003880455052606>606:207", "4?08?9080=", "440>;=0>4?0?>40?7<101011:6113=12", ";112?912401378139:13<513><131214", "38143814301446143?1434141914?>13", "=:1399135?133113?712<81288124012", "?>118>11101193101310910?190?:;0>", "350>;<0=2=0=880<==0;240;5=0:9209", "=90817086407:?06?40550059>04>>03", "46039;02><014201:3000:006=??=6?>", "3;?>9:?=01?=62?<;7?;19?;7=?:>?899?831?8<4?758?7=??65;?6", "=6?54:?5?4=??37=?31>?3<9?2", "7:?22:?2=?6;>?1<>?>7>>>44>>", "18>>02>>?>>=09>>16>>2:>>40>>50>>", "53>>45>>4:>>42>>45>>5>>>76>>9?>>", "=2>>13>?5?>?;8>?1:?086?0>;?046?1", ";3?122?29=?214???", "0700<=00:>01:1028=038=047?056406", "49071408=:08;209950:8:0;6=0<260=", "<=0=4;0><40>550??30?:1104911>211", "7?12?>125013:913?:135614;:140715", "37154115251513151:15331558157615", "751555151?15=4149114691440142014", "0014;7135:13<4122:1296110<119910", "16108:0?>30>340>7=0==;0<410<:00;", "090;640::>09>108?:0717074:068<05", ">7044404:003?3022=026=01:>000=00", "7:??>??>72?>>0?=3??=8??<=?;", "92?:?;?967?9=7?840?8:5?70>?787?6", "19?6;8?55>?503?594?41=?49?91>?4=>?10>?=8>>9>>>66>>1?>>", "=5>=96>=65>=3=>=18>=?:><>0><<7><", ";3><:9><;:><=6><06>=4<>=91>==1>=", "04>>34>>72>>;4>>01>?5<>?;9>?09?0", "5=?0<4?041?1<?;56?<35?=14?>", "?=?>=0355044705", "2906>306880745081>09040:160;200<", "100=>?0=8=0>1=0?;50?3710<;108011", "2?12<4122:1367139913<113?;135514", ";314??142?1540154?155<156=159915", "<215=115;91572150>15;21460142?14", "2;1431141014124412;611", "3411;=104410;00??>0>3:0>5<0=890<", "=70;2>0;820:=0090?093=087907<006", "1<0697051;058;04=>030=0325023;01", "6100:=??22??:28?>96?=?:?<47?<", "94?;>>?:62?:>6?96:?9?7?86>?8==?7", "49?7;5?635?6;9?539?5;3?42??4:;?3", "34?3=>?296?261?23=?2?=?1:7?143?1", "<5?03??0;?>?4>>??5>>:2>>59>>15>>", "=:>=:9>=81>=68>=54>=46>=3:>=31>=", "23>=18>=06>=?<><>>><", "0>>=29>=53>=9=>=06>>8:>>17>?9>>?", "1>?08??006?173?1=??147?2:1?2?=?2", "6>?3>6?36:?4?>?4:0?55;?614?7<5?7", "58?8=;?859?9>1?97:?:2:?;=9?;94?<", "47?=0=6?>96??5>0039012>024003", "5=046>057<06800787089009770:5:0;", "160<;;0<6;0=030>9=0>4>0??80?;810", "7:112412:812?7122?1354139313?013", "4314:214>:1408151815221518151015", "121524152>1539153915271517150215", ">414=0149:143?14=:134913;:123212", ";?116:110?11;4102>10810?;?0>>90=", "2=0=8:0<>70;520;;50:?10922094908", "6;079006=50527056904::03>4021:02", "5=01<0002>00:;??2;??8??>>3?=26?=", "63?<;7?;22?574?5?;?4", "7:?4>6?351?3<6?257?2???1:0?139?1", "<9?04>?0>3>?8:>?3?>?08>?<2>>72>>", "1=>>;:>=61>=18>===><;5><9>><91><", "7;><5;><42><2=><31><52><8;><=3><", "10>=3:>=6>>=:6>=>;>=43>>:8>>12>?", "8;>?0=?097?01:?188?9:2?:7=?;", "63?<56?=4;?>35??0=00>400<201:802", ":1039?04:205:706;307;>08<209:>0:", "850;3>0<>70<8>0=3=0>>=0>:60?6:10", "2711=3115612;112?7121:1340138413", "<<1320147814;>1401152:153=155115", "5;1550153;15201510150?150?151215", "15150815=?14:4144>14>41373130<13", ";=1272121912;4111?1162108?0?:90>", "2071:0744067805:604<;0300033=02", "8:01020186000=008??????>5??>;:?=", "1??=93?<17?<9>?;28?;:9?:15?:64?9", "<:?844?89;?7>2?63>?6;9?539?5;0?4", "24?498?321?3:>?232?2::?11??191?0", "02?06<>?>3>>6<>>02>>:4>=4<>=?4><", "98><3;><>1>;89>;3<>;?>>:<8>::?>:", ":?>::9>::9>:9?>:72>::4>:<9>:8;>:", "=3>:32>;16>;4:>;2?><4=>=38>>29>?", "1;?0>5?09>?151?2:>?2:1?2;9?243?3", "<2?337?4==7?>", ";3??4>00200172021>04:605?9066808", "8009570:5<0;5=0<200=820==20=750>", "=50>?20>510?0=101611?;11:5126913", ">?1318143=1460148<1498149014=;14", ">8147:142<142=1442141214=513?013", ">51393136<135=134>13251310131913", ";?121<127911<7102310780??=0>:90>", "460>=<0=560=950<;<0;?30:440:9309", ";108;307==06110644057?04;9031103", "85020<028;01<300?5??54??>90?>", "35?>?4?=;0?=56?=>3?<6???911?984?8", "?2?76:?7>:?67>?602?667?5=>?45>?4", "=3?34?04<>?38>>", "12>=06>:13>:59>984>89:>7?0>6", "78>600>690>57?>5;9>5?4>523>69=>6", ":6>797>84:>97=>:45><0?>>7;>?13?1", "=:?232?402?502?69;?7<6?852?95:?:", ";9?;<<9?>;9?>=:?>", "88??3=00;=00?6006<01>901=4013502", "09038803:603860364047<0563056?05", "1=06<>064>076;07?;07>00809095209", "590:750;4=0<;90<880=970>=40>>30>", "640?0;109;10>2107<116?12;112;412", "23136;134813>412:112:11221123611", ":2105:10?<0?470?:?0>7>0>?90=180=", "5:0<:20;>60:3<0:;3098;095309;;08", "3;08>9075=079?06?=0596053905;004", "62041?04<:0384032>0331031?03:702", "89029<0298027;0260029;02<8029;02", "5402>70191014<01>=00=?00<4005100", "?2??62??89;?=99?<:>?;=6?:<5?9", ">7?869?8<2?7?=?630?685?511?597?4", "12?498?3?1?247?2:9?102?167?0=0>?", "21>?74>>;7>=:3><:7>;>1>:48>:=4>9", "52>920>958>9:>>90:>:64>:??>::4>;", "4<><61>=55>>3=>?5;?0>9?1<:?340?5", "8?;>4?<1??>>6?>", "9:??75007>01?>01>:01350222028:01", "3>0144014101>>001001>6015>024302", "3=0284027;02:7013501<601>001;?01", "4402220321046=04:>04:105>205?805", "72063=0730088;083;095<0::00:::0:", "3;0;450<>40<;=0<300=3?0><>0>?40>", "550?0:102<10:;0?7>0?7<0?>30>7?0=", "700<270<:40;950:<:099209?=08>;07", "24078<06>405?7048?04=404;1046304", "7?043005:>0555052>05770568051405", "?<0453058<059<050>06;:06?106:806", "83066=06?3053005:90490047:044404", "43044904340403048>0312038=02:?01", "=80034007=??<9?>=8?=>5?<06?4", "71?41:?4<8?35:?3?=<>>57>>=1>=54>=3;>=", "25>=2=>=92>==0>=13>>43>>93>>43>?", ":2>?>>>?=6?026?285?329?525?748?9", ">;?:0=?<9??62006601", "1802;4011201;20114025=016?000500", "3900>>??41??3???35??5=?>?;?=2=?>", "19?>9>?=41?=60?>>:??66000502", ";?02>:022:03=203>;04<<04=<049<06", "79075:0790072:0865098:09?408=009", "570:240::;0:6=0;030<2<0<690<;;0=", "9;0>0;0>=90=0=0>930=530<440;?<0:", "6;0:?6080?081:08;=07<:0664069206", "5:06;005460510058>04340460048>04", "38041904?10477052:050<0569051<06", "9106:;064807;:079:079?075?07>006", "98062906;40564050:050?051805>?04", "=7046904;5030>032?025601<;003600", "66??8;?>;0?=?5?<>??;98?::;?9?0?8", "27?898?73=?71>?7==?665?6>6?569?5", "?5?478?4<1?3>;?254?2=>?11??13;?0", ";=>?56>?8;>><:>=;9>=07>>??>=19>>", ":3>>6:>?;?>?93>??9>?4>?07>?05:?1", ":5?289?42>?6?4?7<6?::8?<6??=0;?>", "23??26006>00;30079014;020<02:401", "1=02=;01:800;3???5??4:008=??", ">;?>55??8:?>:2?=74?=7=?=60?=72?=", "7>?>:5??=:??9300380205031;034803", ";60365040005:105950641077007?:07", "7608:;086808>9074=0825098909?209", "7<0:4;0;?80;070<560<<80<<40<:90<", "6>0<0=0<7?0;;<0:290:;109==080;08", "8>07?8065106:90568054>05;<043104", "0:04>;0399031>03:402<60209032=03", "<503510464049804;904<=04?5040205", "620521069?06?0060507;?0658066;05", "7104:>03<4025702720276023?02<601", "3=0100018>00903?>46?=;7?<", "2;?<43?;5=?::3?9?5?85:?8=2?7:1?7", "=4?7=6?764?7=3?6>4?5<7?4<;?3;4?2", ":>?1?5?073?022?0>6>?93>?6:>?36>?", "=<>>07>?;6>?4=?0?8?090?1?2?184?2", ";7?213?3>1?38?554?7?>?835?;", "16?=3:?>1:??;5??;0??>8??:6005701", "3102=8023903020423047803<8026?01", "6000>5091?09", "5009;>09>609260:9;0:;10;9>0<;30<", ";10<0;?50:300:51097908", ">1079<076907<006=;052:055?047303", "1803<;024;02=?01<<013>028:024102", "3=02<<020<03??020?032:033=03=?02", ":60209036203;00312046?049;047=04", "5<0425048703;9022:02;40142010601", "?000?;00=9006200?8??:5??0;??43?>", "98?=;3?<=;?;15?;3>?:85?9:2?89;?7", "<9?648?61>?6=8?57:?53??5>??477?4", "=3?31=?37:?2=9?12=?1:2?06=?063?0", "66?066?061?055?0:7?009?171?1", "0;?274?2=>?2::?309??40??:1??4<00:900", "75019802<403:9049304>;0395032;03", "83023?02:>01460185011<01=?00::00", "?=??>4??72??5=??4600=7008:018=02", "4103:2039403:9035;04?4043;05<505", "99069?07>:08?309:40:;;0:380:5:0:", "470;<60;920;:70;070<3?0<510<290<", "2>0<1?0<9<0;6?0;6>0;>;0:030:0=09", "6>08?<0723076:061906;?056=050205", "2;044?03;102:90223030>0385026602", "9602;:029<022402>7019>0139014101", "51011?0102012=018;012602;0021603", ":403130485049>040>046=03>2024?02", "8>01;9007700870077004>0087??39?>", ">?8;9?7>;?686?64:?6", "16?698?550?537?526?56;?581?53=?5", "=6?45>?4?=?35?;8>?98>?89>?<=>?4??07:?0", ";:?059?1<9?126?29=?26=?3>0??", "0000:000>=005101<8011002?8029503", "78049;05=30528069906?90697075707", "=10609077107?5076808<>088:09270:", "640:=50:720;<=0;:40;690;;80;4<0<", "<>0<0;0=9;0=500>710>5>0>=<0=080=", "170<>40:8>091508<:066:0684066006", ">30553050805;8041<04830369037103", "7803;2034:04:5048;04?>033=03;302", "1002:101:0018?018401500103010=01", "?800;3008:0033002;006500:900>500", ";1003000?1??<;??74??05??;=?>88?>", "31?>9;?=10?=76?<7>?;5:?:30?918?8", "04?718?660?5=0?464?41>?4<:?344?3", "98?2>5?138?139?03>>?5>>>90>=3>>=", "11>=<8><;2><03>=:=>=59>>;=>>03>?", "6>>?85>?<4>?;0?0>9?169?314?52;?7", "29?999?:;3?;=4?<32?>68??7<007>01", "87027103<803=1038:03;8022:02?801", "?7015?023?02?9011302>5012101>8??", "=7?>5=?>14?>19?><:?>?7??1101<701", ";902;803100413041<04=<04;3059506", ";;07>808<709770:0;0;740;900;<70;", "690<100=<60=6;0>110?910?860?2?0?", "?:0>960>180>=>0=?10=2=0>0<0>820=", "040=4:0<500;0>0:<608>10777074507", "1707<50627068505?>047104>5039703", ":703?503270437046104870484043804", "?203?9031604>703;>03;603:003:103", "5803?<02;4021>02960116015:00>4??", "72??0;??<=?>50?>>=?=87?=?0?<7=?<", "?>?;77?;?3?:70?:1?904?927?8", "1:?71?8=>>:3>==:><>5>;4?>;66>;80>;", ";?>;42><96><39>=>=>=3:>>;:>>?9>>", "67>?7:?04=?128?280?34??553?7;2?8", ":6?934?;<5?<<3?=93?>1:???>??2201", "::017=02><024?0212020002=8019:01", "<=0041004500<6??>1=?>95?=6;?=", "48?=>6?=9>?>31??45008001:=021:03", "3>0325041005:605>4056>068>075:08", "?;08>=097<0:<40:?80:650;=20;;90;", "=50;780<5;0=050>:10><70?;:10?=10", "251133114511>=10?;0?4>0?810>460=", "420<2>0;?509=208>107770722076106", "=405;8057;051:05=?04<=04?=041505", "3605==0591063:07=4071<08?4077007", "=<065806=4053205930450040<045>03", "<202><01?=00280062??16??=:?>73?>", "66?>7=?>75?>59?>2:?>31?>>=?=0??=", "4=?<<?1<>?6:>>;>>=", "=?><<8>;<6>:29>:17>:35>:<>>:=:>;", "?4><<0>=25>>47>>1:>>27>>3<>>;>>>", "?>>?48?159?3:4?568?71=?9:1?:?8?;", "2??=4??>8=???1000?02:102?0021703", ";802<201>40064001=00=4??64??=>?>", "54?>4:?=>3?;=:?:<;?950?985?910?:", ":6?;17?=;4?>=5004:0295037?042?05", "14065>06=>069:07=2073108;6085609", ">609140:5=0:?=0:<30;5?0<290=210>", "120?03109<10071136110511?>10=210", "3:10:30?1<0?<20>0?0>>50<970;560:", "0<0992079?06?4053505??04>:041605", "81059>05?1050<061806:8064:071108", "::080?09620954092509;60818085?07", "49065905>504>704>=048<0405048203", "<902=001>;0000003>??04??12??5;??", "76??6>??50??73?>37?=33?<4=?;36?:", "?0?8<;?7>3?617?668?583?433?3;3?1", "74?06>>?56>>84>==;><25><;0>;83>;", "82>;57>;3?>;5=>;8>>;=3>;:9><8;>=", "=5>=31>>?=>>33?00:?1;1?115?399?4", ">7?58??7<;?9001?=01;0010801<9006=007>00", "3=002???5=?>48?=4??<73?;84?:04?:", "64?9?7?8<4?921?;=2?;38?", "31??19005501=002>;03890455052606", "7506<:0673071;08=108;809==0:170<", ":;0<=40<500=020>940>3:0?1?10:910", "?5103311721174117010200?440>?=0<", "<30;<50:<:0925092<083:079806;805", "2:05?>04<:04=9044=05?<05;>064607", "67078707<80726088:08:<081<09=809", "?<09:;093909=70828083<07;8065=06", "=50557051205<80408043?03>:02:>02", "1;029?01620100016200<1??0;??12?>", "?2?<>9?;1;?;0>?:;7?89:?771?62=?5", ">?6=>>;3>==7><", "1?><;<>;;61><86>=08>>51>>", ":5>>54>>?2>=>=>=48>>96>??4?077?2", "58?<0", "69??;90099015?0115010=019600??;?=44?=>=?<:1?<<:?;>8?:", "02?:?7?818?812?8:4?826?9<4?97:?:", "10?<;6?==2?>?=??:4001=0186010302", ">902=3035=0498042205;6059506;807", "810817097?097?0:3<0<970==;0>1:10", "=;10241120116:1179118:10320???0=", "390=410<350;640:1=09=>07>=064806", "<=05?7045404?>03:203=0039:04<405", "9;06=;0610075607:507;807;<071:08", "<=089409?>09?709:809?708>407>;06", "8606590643065<066<0650060006<=05", "8=05;>04=2034:03?5?1?47;?4;??3<2?2;9?14;?0:9>>", "1=>=?5>;:2>;>8>;0;>=99>>:3>?0>?0", "03?0=0>?4<>?94>>51>><:>>;6>?==?0", "=1?230?5=2?683?727?86=?9?5?:71?<", "59?>;40045029702>:0245031?030:02", "75000;00170012004300150095??<4?=", "70?;=1?92??8;6?67>?5??:60?88??66006200", "70003001>:01;;02<50359054;070508", ";>07>70745089308??08050:=40;630=", "650>290?7:0?750?1<0?=:0>;10>720>", "940><;0>9>0>700=4;0;0909<:06<604", "280333025;020:039?033204=9045105", "32059;042;0426046=04000510063907", "3:08>10833092509;:08290896075107", "4<076=07=5070808=30743078306>405", "3?058?044;047?04:704430462034:02", "?40031??75?=3:?<10?;07?:61?9<>?8", ">7?7:1?680?55>?4>5?265?186?0?2>?", "=>>>9;>=0>>=?9><42>=>=>=73>>82>>", "2>>>:6>>77>?;=>?17?00??167?223?3", "1;?453?6>9?888?:28?;6>?<4??><7??", ";40085015:028102?701<;01>1013<01", "=;??;3?>17?>;8?==7?=7;?>?3?>85?>", "44?=0??<54?;41?:;1?807?80?<2=?=32?=27?=5:?=94?=", "?88??6000870179031>051806", ">306>10713092;0:5;0;0;0=>90>2510", "80105410>90?3;0?670>6;0=6?0<1>0<", "340<=;0;120;=4093908;20650053>04", "=003;703;>0323048304870485045204", "=>03140383027<02>3025303?=030505", "0206:00688063<061006;=059:050;06", "28074=08>>0824092:09>1084108?407", ";407>;062>069:05<;0491032502?700", "6;??77?==?:=;?9???870?806?8", "45?73>?606?550?340?1:8>?<6>>?;>=", "64>=48>==?>=?9>>91>?:2>?:5>?=6>?", "00?09?>?90>?3?25?:00", "37024;026>028=02;602:>0159009;00", "14013401<101:9022<03?301>8??5=?>", ":7?<<1?:57?9:=?877?88?9", "20?:<9?987?;6>?=7??>", "=9???900==010303<0039?04?9051;07", ":308430:720;680<000=610=7;0=290=", "0=0=6<0=:70=950=870=930=:60=320=", "450<990;<<0:>>097709?:0822082>07", "6=0695057<04520369021>029201?200", "==00;3009>00=1005301800298035404", ">8046>05;905<:05=<0530069:06=?06", "20078607?0073508=9071?073?063605", "87042:0485038?02:<01?9002100<8?>", "5;?=65?<;9?;?:?:67?:07?:29?9:9?7", ";=?57>?309?17=>>80><67>;=1>:58>;", "03>=21>>4<>>63>>>:>>05>?8<>>>;>>", "<8?00=?3:1?456?6<;?8?>?:;=?;>4?;", ";0?<2:?=84?=?2?>=<00;101<=01>401", "=3014;010200?>8?>0>??>4????01", "8:036<035;02=700?9?>09?=6>?;;2?:", "50?:9;?991?9:0?:47?;1=?;33?;20?;", "<?=03?>44??8700", ":>0119037<040406:906470706092;0:", "7:0:?80:=50;:6080>2?0?", "6:0>;>0=760=370==80<9>0<7>0<=50;", ">40:3;0:5209>=075=064=05:<041=04", "35048>048204?=030<033>028901;<00", ":;006701360251038<047405>205::05", "??044204:303:3034<04580590065807", "6107>>0637065:057304>:03=003=503", "9103090378026601=???82?>1:?=;8?;", "89?::4?916?91>?85:?64;?423?2>=>?", "=<>==>>;72>:::>:8?><39>><9>>59>?", ">>>???>?61>?57>?>:?03??2?>?28??4", "?7?6>3?86;?900?:6:?;=3?;87?;8??<", ":7?>;;??=;??54005;016:013800=3??", "6<009=002;01?50255054=062=059803", "=30194??:4?=78?<53??;00?;49?;", "=1?;52?;81?:89?976?9???931?:0=?;", ";0?90??7400=<011?035204", "9;05<;061?084109?909800:5:0:420:", "800:?00:0;00;050;<<0:040:", "2009:;0815080?074;061206;405<904", "<103?3025=02030:033703", "=8037;040=05;=055;0660060906;105", ">504=7031<03<:027502=<014701<300", "11000???27?>70?=83?<70?;35?::6?8", "==?6<?23>=?;>:=0>:40><", "63>=5=>=7>>=;?>>97>?78>?>;>?4:?1", "67?2>4?231?436?77>?9<;?97:?:36?<1??=?5?>9>??4??>>7?=:8?>", ";4?>;=?=37?=<9?=01?>?2?=>2??0=03", "8;0412046:030>032>02=?001:00=;??", ">8?>6=?=94?<:7?<7=?<4:?;3:?:<1?9", ":3?92>?:3:?;50?00", "7?012203<>040206010742088609360:", "500:3>0:?>094109=8085209<309<709", "?7095>0:9=0::20:=>0:4;0;3;0;?20:", "580;<;0;450;840:260:980969084707", ">9067>066;0539043<03970273024502", "==01;>01><017=02=>022003=5035<04", "78049704?9043=05250512053=051405", "88042104;503<:02?:01:8015901=400", "5600?9??70??;;?>55?>15?>8>>?2;>>", "0<>>0;>?2<>?<3>>8;>>=7>>67>?45>?", ";0>?33?15;0?=", "43?=:7?=71?=7:?<95?<1=?=97?=>9?>", "=700;<028<036<033<03=?022;02:601", "7=01130147008;???1?>03?>???<4:?<", ">0?;=6?;?5?;34?<<3?740060026404<40561062907", ":807:8079:07:;070=08;608?908<608", "71084008740884087;08>;08:?09620:", "<80:4=0;1<0<050<150;530:<7097909", "2:09:00832089?07=006>0055=04=202", "3502220215024>021903??032204:603", "70035=030?03>8023>03;103>;033104", "8<047704<:032403:002?6013001;500", ":6006700?9??81???7=?>31?>10?>", ";7?=00?=2>?<30?;:??9<7?7>40>>01>?3>>?80>>1>>>:?>>", "9=>??2>?4=?06>?108?362?425?536?6", "72?784?8:3?9?4?:5;?<7:?=78?>>:?>", ";3?>74?>58?>>?<90?=", "=570098019002??0214032303", ">702:<02<9021702??002=0036??6??>", "91?=>:?0>??4=00=7015703?>04", "43061<07;407=807?=075?08:808??08", "1=0994082=08=;0759071:0749072208", "=508<:08<5084:09=309;9093?090209", ">>08:=087008540839082808;9079906", "45053>04:6032203:;02>1023;038503", "5003<>0234031>034403070409044104", "9<04;7047904>:038403?9024202;601", "4=01>7004?00:4??0=??6??>;4?=32?=", "?1?<91?<0>?<95?;?;?:03?:6;?8;5?6", "23?561?3;8?104?1:1?1;6?18:?06=>?", "79>?41?089?07??048?1:??207?412?5", "4>?69>?75:?8::?8?6?8<7?9>3?:46?<", ">1?<;7?<9;?<9;?<93?<60?<;7?;7;?;", ">1?;54?<26?=81?>2:007401=701==01", "??0194023<03>;03730401042503:902", "1?020?01==??=>?>63?>26?>11?>:", "40??2=??65??3200350152025>039704", "=<05;4065207<007;=0764076?07<=07", ">7079=07570763074?07;9060306<705", "01062?065506;?065?07=;070008>:07", "2208;=0826091709;;089108:4082?08", "=<068:05;;042604:80366038<03<903", "=603=503<;039303380336039703?403", "3;048704<904=0047604=8031:032>02", "6701=9005400<6??12??2;?>34?=74?<", "?>?;:1?;4=?;25?;>4?:44?:6??965?8", "00?742?59??321?3>7?364?4:;?387?2", "6??26>?3>3?337?3:0?2?1?2;4?33;?4", ">8?4>5?632?7>5?7:7?8:=?9", ";=?:8??;?9?;?4?;:>?;4??;9;?:00?:", "34?:?9?:?5?;29?=;1?>3?0056018301", "1001=5002801:601<<019;0167018601", "<601<0016=012:0104012901::011602", "340213020:021<022>024:02<002;203", ";>04=605<40652075<0717070:072707", "270706>606=:060507470771074107<<06", "760644064906;3063307680762073807", ";?0600064005>;04<504890466045004", "48044;040904:1035003240336034803", "5;0376035?031903=<029;023902<;01", "870173014<011301=<00520078??6:?>", "66?=7??<=??;94?;53?;=6?:2;?:5>?9", "44?809?7=4?509?506?549?5", "7:?685?72=?8>5?741?72?=937??", "1=??401<3015701<000;1004101;?01", "13027402?802550367039<033404<604", "59052706?3067:07:607990777075807", "2207>806;806960679064406?=05;<05", ":80595058;05:305<0051406;<062>07", "2607;:067306:806>206>206<5069906", "5206?4058505>3043104:<0376035?03", "58035;033>03?902;702:30292026702", "8202>:023>0362033?03>;028<025802", "4902?1014101:50064009500530051??", "6=7?=1??=:3?<98?<73?;?7;2?71:?883?8", "1:?877?77??7>4?7=0?71;?7;1?612?7", "86?7:4?706?897?890?865?8;:?862?9", "6:?906?9?=?863?9::?98??97;?964?9", "17?9<:?822?9==?94>?:=1?:=1?;;4?<", "?8??=<9?=38??>", "96?><8:??0<00?>???3??4400<=00", "38019:011>0269026=02<;026?03>803", "6904>?04<205<506?>06>3064=074=07", ">006>7060607;30633063>066=062506", ">:050:061006=:05;805<705=>05>:05", ">;05=:05<305;705::05;105<405:?05", "7=0558052>05>3046<04>30380031>03", "?402250340032?03470347030503?502", "2;0344034703540344030203?102=602", "6;020502<3015<01>80099002?00<0??", "6;??0;??93?>1:?><6?=9=?=81?=5:?=", "19?=9>?<1:?<=;?;55?;73?:;;?957?9", "97?950?:8=?:19?:<7?927?::4?:9??:", "<?9:>?90>?:1:?::??9", "89?933?:>6?:>8?:9??:93?:;3?972?94??9:8?90:?:58?:", "?6?:<>?;6?<>1?<<?<<5?<", "=6?<>5?<=0?<:=?<04?=;2?=1??>56?>", "8>?>07??;=??70000;018701<301?801", "42029202?:0272031804<9041;052<05", "48055205310516050:05?804<4048>04", "9;04;;04<604<604=>04??0400051105", "3?05540546053205210523051405?=04", "?:040?0526052505>;04:9046>042904", "=303860370038203:?03>;030004=403", "=;03?;030304>203=<03>003;:038803", "6:03070381022>02>501840146013;01", "?0004?00<1??:9??9>??2:??9=?>:5?>", "=2?>;;?>51?>13?>012?>=:?=4=?=", "7?<0=?<;>?;98?;<:?;<1?;", "42?;0=?;52?;7;?;61?;41?;3?:30?;;;?;5=?<89?<5;?<45?<77?<<3?<", ">6?<01?=63?=<>?=13?>66?>>2?>69??", "=0??130040007:00=4002?0174019=01", ">7014>028<029=02;202042?044004", "2>041804150422042=04310452046804", "470430043:044:048004?:03=6038=04", "4<04:<03=6031;041204>?03<=03:=03", ";<03;0035?032203?302=202;5026102", "0302>701=201;801<201:;0177014<01", "1401<5009>00;400860017007???6=??", "7???<4?>?2?=:2?==9?=;1?=7=?=", "6??=93?=<6?=1;?>24?>=0?=75?=65?=", "7??=7:?=1=?=:7?<75?<57?<43?<4>?<", "47?<27?<=2?;93?;:=?;:;?;4;?;>>?:", "???:47?;2??;=;?:?6?:61?;9>?;;4?;", ">4?;04?0?;0:?<31?<40?<5=?<7:?<75?<:4?<", "24?=9=?=>9?=19?>63?><6?>1;??65??", ";4??07003:0058008200;=00=800?500", "2901470124010301260167019901;701", "=?013802:?0224037203870386038403", "8:039103:203;703:<0373035=036403", "48034903730370036;039803;>038>03", "5<037:039603680336036803<=032804", "3<0424042:042404>703=:03:3032003", ">702>002;102640254024>020602;:01", ">3010802?201==0117022202;1017?01", "60012801=400;<005>00>5??>4???0??", "7;??08??<4?>725?>?6?=08?>>8?=", ";??=26?>;;?>85?>;:?=6=?=55?>:", ">>?=;4?==2?=98?=17?=?2?<0=?===?<", "74?<20?<22??;1??;92?;2=?<5??<5??<", "81?<:5?<=2?<>0?<;6?<89?<:0?<;3?<", "<8?3?=38?>92?><=?>>;?>11??54??", "95??;>??????6400:600:900:100;?00", "?000=2009?00<0001:017101<6011=02", "62028902<10208030;03=102<7020<03", "1?03<;028<02;:02>=02?80233039703", ":0039703;>03:9038<0376033<032103", "33033703400341039?03>0039703;603", "01042>04<50354032303=4029;026>02", "37024:0254025002460280023:??06??<1?=82?=79?>;;9?=", "9;?=929??:=?>=:?=88?=24?>52?>", ";1?=96?=67?=3??=27?=??;59?;;;?;", "<0?;<=?;?>?;34?<63?<:5?<21?=4;?=", "0:?=<5?<>4?<02?=9??<37?<5??<;=?<", ">0?<07?=23?=059?>=>?>51??6>??91??>8??", "2:003<003>0068009;00930072007000", "840092009:00;>001:018801=;010902", "2?0251026?02:902?9022;0340035803", "5;0351034603630384035>0301030103", "3<032303=<02<;02==02=302;6020303", "64036:0376037=03=503=;0371035:03", "7?0365033=030103<>02=402><02=<02", "6<02270227023:024602?:013702;602", "?201;10142022502=201710140013501", "<300>:??:??29??83?>:>?>12??", "052?=8>?>:??><;?=96?==1?=32?>", "28?>98?=??7?=:=?=62?=", "59?=9=?=8??=>4?<6;?<57?<5>?<76?<", "27?<:4?;94?;==?;33?<13?<>8?;37?<", "92?<>??<=", ">8?>3:??3=??2>??71??>8??4;007>00", "78009800=;00>>00=:00=>0022011:01", ">900110194012;026;020<02?>013<02", "6>02:202?902?<02>50203034;037403", "=503?:03:1036;03430351034203;902", "9;02=30214033103>102<5023203<303", "77040;04140312033:04<<0303035<02", "3002=:028<03050303022802;:02;502", "6>020802>;0149025202;?015;014;01", "09018500>0006701=200?>??1=004800", "<?>:8?=61?=94?=21?=13?=", "72?=>>?=?8?=:5?=<>?=0=?>:4?=", "39?>?6?=>0?=:>?=59?=6:?=99?=23?=", "51??=?1?=:7?=90?=90?=62?=???<", ";>??<27?=:7?<44?<:??>12??54??603150397024002:902", "140323034:03310338038<03;2038503", "2<031<037503:603?7028?02<=020=03", "=;024002<4011>02890238026501>:00", "2?017801?000010014009600:;002>00", ";7??65??49??25??93?>52?>61?>0??>", "11?=89?<=??<", ">5?<=2?<35?=77?=39?=?0?<<;?<<2?<", ">>?<>?;<;?;>=?;>9?;0:?<53?<", "88?<;=?<>??<31?=6??=:0?=<>?=", ";6?=3=?=2=?=;0?=2=?>31?>=3?=95?=", "<23?>79?>=5?>>1?>>:?>37??", "93??:>??=>??5=00??007601:601:701", ";001=801300264021802:?019601=;01", "2?02500244023:027302?:027;03<403", ">903130434041=04?103=603<803=?03", "08040>04?;03=;03>903?=03;:032503", ":?02::02;702;602<802<902;<02=002", "0403190323032>03?:02>802>:020303", "?:027502?501?001<5013101=2003901", "7?01?=006:003500?7??75??4>??49??", ">6?><8?>>:?>>:?>;4?>5;?>=6?=71?=", "40?=>3?<76?<86?<<=?<:3?<18?<?<85?<7?<>?<:>?<<;?<60?=?1?=32?>56?>5:?>", "49?>5>?>7;?>72?>546?>?>?=:3?=", "8;?=<=?=1??>61?><1?>43??:8???0012011<015001;70122026302", "720278027=029302;?02>602;:025<02", "40029402>302;>029402:102;502=<02", "240396032;0480047>048:04:704<204", "102:402:602>002?502==020247024>023102", "05020<0242024502=<015301?1009?00", "860080002;00;:??7>??51???=?>;", "9:?>12?>21?=:6?<;>?<;3?<23?<46?;", "08?;41?;65?;<8?;>4?;9??;6?<4;?<=?;>7?;=7?;>4?;", "1>?<4??<61?<52?<8:?<:;?<74?<33?<", "37?<64?=", "<>?=25?>;8?>64??=>??0000<4??38??", ";:6?>;2?>99?>57?>46?>63?>98?>", ";=?>=>?>0???43??:4??3800>7004?01", "4<015701<7016802:602::02<1020003", "4;037403860366031803=802=0020=03", "5=03570337037503>?0362043704=>03", "2:04;004>2040;0532050:05<>04>504", "3905?:043704:;0364032803=:028302", "49021602=>01?10139028802?6023903", "3803330311038902?801?0011=02<;01", "49013;015?0112019>005800?8??83??", "7???98??30??6:?>:6?=28?=<1?<7;?<", "4??;>1?;56?;?5?:=>?:", "?4?:<=?:42?:=2?992?9:?;8;?;;>?;>5?;=2?=2>?>", ";:?>2>??>8??3;000000<2??:4??;5??", "=4??;5??:0??:5??58??49??5=??32??", "0???68??22001:0100027>02:402=602", "?;0212030?03?602?=0252039503>203", "1704>1039=039<03<30313043<045804", "790481048>04?6043;050305<004=104", "01053<058905=005>405:;054605=704", "2;048403540345031?031?03=1022?02", ">9010602210216020>026002::028:02", "52023=02?9017;014;0144012401=<00", "9:0056001100=>??;0??36??98?>66?>", "34?>:4?=14?=<7?<78?=?9", "43?9;>?8>??83??9>8?866?87??84=?9", ">9?93;?:6:?:64?::3?:0>?=45=?>95?>5=??6700", "<7005900<>??=8??=>??;7??:???>1??", "4=00<800>?00?800>=00:700:4001?01", "?00177025>024=029702=4022>035903", "63039403=<033>046<0452046<04;>04", "430584052:05<604:904;5041>057;05", ">?0593067306?<051506420608067:05", "4105:305>6056;05;704230484030503", "?>02>7028;02660262024;027:027402", "?4019>018:017?017>016<015;013101", "?80004010901::005?00670080003>00", "=7??8=??75??17??51?>;1?=4>?=06?=", "<2?<5>?<>0?;5??;;4?:>2?948?9<1?8", "99?8?2?8<=?830?8>9?707?86??86:?8", ";3?796?73??8=;?877?984?:<:?:1>?:", ":7?9;:?980?:4?:0?<;>?;=>?;=6?<1=?>", "07??67??;:??04002;007:0089001<00", "=300=2008>00", "35003=00>20087013002==023903?902", ":702=2029;0353048<04<=042105:005", "24063606=2053005<904?5042<050?05", "<404:;04?4045405:>05?105=8059805", "9=05?=05;;06?<06:40674069806:806", "4<06:105?=0468041404><039<037703", "1;0353020302270227020>02<101<901", "08020;02>?01?501=:016?012701?800", "9>0056003500>9??76??46??23??<5?>", "3;?>;1?=1>?=7=?<08?;;>?;5??;", "?0?:69?:;=?908?9;8?8<:?8>8?8:8?8", "45?828?8?2?7=;?7;6?73??740?76=?7", "64?79?;8??;77?;06?<", ":0?<>1?<<6?<91?<09?==0?=53?>49??", "4?00610023002=007>00;?0093007100", "9000:200;<00>7005201880148014901", ";901160247026;02;5021>03=<02>202", ":10346047504350468043=058:05;805", "5:06;<0684061906=605?605?005:505", ":>052706:90628077:076?0714079306", "2<06?<05=905;>058?0580058:055>05", "=8043>04>303:>03870365032?031703", "=4028>025202;5011<01160147016>01", ";2019;0167017701660106018;000600", ":9??6>??34??48??58??22???9?><1?>", "2>?>5??=9>?<1=?<=:?;87?;?1?:31?:", "47?945?8:;?7:;?794?721?7<0?6=3?6", "26?70=?7;;?694?6:2?6:4?6;8?68;?7", "65?87;?832?892?843?98;?9:1?9;6?9", ">6?903?:45?:91?:0>?;76?;90?;=:?;", "70?<09?==:?==3?>88??>7??26002100", "21006900><00670193019201501", "73010101>>00>100?>0090014602:<02", "9<029:02100365035503;:0392042105", "5=05:<057906??067906=:05;705<005", ":1059;052<06:4068<063<061106=005", "3=05=?0417059;05510600072:070007", "=806:=0690063<069:053?0504059=04", "7?044<04:3032>03=>0275022;020102", "<<01;301;401==010602=60168014>01", "5>012701??004<01:701:>017?011301", "7;00<6??4;???3?>38?>68?=<0?969?9", "?=?8;7?877?852?817?8<;?75=?799?6", "27?6?;60?;:=?;60?<=4??74?>;4?>48??6", ">=?>04??23??9=??3=000;01=6015002", ":902<60286027:02;1024803=303=:03", ":;039?03:0036=035?03;=031;048004", "1405<405650668063306950622075307", ":907?8070708170836086;086808>107", "7?074507:>062806=205;005<205;<05", "91052:05:=044>04><039?037>039;03", "=703==03=603;6032:03970269025202", "36021102=101:;015201==00<:00:000", "4=003>005?00:?0030017?01:>019>01", "5701?:0053008>??>=?>52?>9>?=16?=", "<9?<16?<21?;48?:3>?92:?626?742?7>4?646?6", "2=?653?67=?61>?7?=?75:?83>?860?8", "4>?976?:>1?:<9?:81?;>2?<;4?=51?>", "35???7??:1??300>>??=1?>", "0:???3??>5??34??78??", "7=00;60123028002;603=>04>:041304", "0104950479043:04>904>:0542061906", "08062<068:05<=0427053706<:06::06", "8=06?:064?0745077507<707?007=507", "=80759084?087;0713070907=<063906", "4;05:>040:0446033?03=>031104=203", "::036=03>?029?029>02<<0206032803", "250306038?02?;0194012?0113016301", ":101;901;=017>012601>300;3009000", "2>00:3??0>??75?>?;?==0?=:4?=3?;>=?:1>?:;1?95:?9=5?8", "82?8:2?81;?8=7?6>0?572?544?527?641?7?8?6", "::?6;0?6;:?609?775?7=6?779?806?9", "89?980?:69?;97?;7>?;76?;=8?;>4?<", ">;?=85?>=6?>:??>3>?>06?>06?>64?>", "07??54???4??>8008301==017801;700", ":;00>>0070012602:102?=027603>503", "8=04><04=104?7047305<705806<;06600620065<06", ">?06190713077707;>07<807<0078007", "=4064206:00693072708>=075?07?506", "6906:=054105?5045104>60347047:04", "2=04=6038>035?0341031;03>1029402", "5>02460244023:02530276024:021;02", "1>02?701:=019501:>01:3010=015600", "<7??0???6??>30?>23?>?5?=;?;=4?:6:?:?9?9", "85?927?9=:?88>?81;?873?7=7?65??5=6?548?619?753?7>;?73:?9", "?>?9>:?9<:?95>?:0:?;3??;2=?;64?;", "186?>1:?>81?=5=?=", "97?=>5?=3;?>?5?>?8??<7007>013102", ";:02>:02:40290021?0383038803<<03", "26041>046403?2024;03=6031:046<04", "1=05:805>>058>062<073>07=006<>06", "2>079<07?6075508:>089:087>08<208", "9508>207160786066>0669063:064506", "4506=<05660534054:05760589059005", "9605:5057?051605;:044804::033<03", "0103>=02<0025902240222020<02?;01", ">:01;=017=013=0121010>01>=00>:00", "0<01?:00<30091004300=", "?3?=6>?=>=?<63?<>2?;4>?;84?:=1?9", "63?92=?909?9;=?8<0?803?9=5?857?8", ";>?713?75?500?6;7?5:0?5;=?581?53=?533?5", ";6?596?64??75;?8;4?9;7?:15?;28?;", "43?;68?;77?;?5?;10?=?5?=41?>59?>", "1=?>5??=49?=;4?>94??", "<=00;<01>301:601950176017701=701", ">002?40340047:04?20433050305>704", "?804;;043=040>048?04:<054>068;06", ">506<=0689068=06>>06<00785080:09", "<109660:240:0209?0074407?=06=506", "<>063907:8075107:5064206;?052005", "17058305:=0588053:0537056:053005", ":?0463041304;=036>032=03?:02==02", "=702?6020?03<;022?026001=:00;000", ":000>:005<018<0168010;01:<003?00", ";5??39??>4?>9??>41?>=0?=38?=9=?<", "07?<4:?;8:?:00?:94?955?90>?9;?5?0?42;?591?538?6=4?6<>?686?6", "35?684?5?0?4=5?4;:?412?516?64??7", "7>?87;?923?:9=?:>5?:=:?:0??;>1?;", "64?<87?<:2?<<?<84?<71?;=6?:", "0=?;=53006=0151022103", "8=03>;0287011>01;=016;021<032804", "3>05<005?9055?068006:9059=048:04", "1305:605=?050706790666062<065206", "8406080730084=093>0:060;;=0::<09", "==08=?078;0674050=05:305:<060=07", "2>075<071<0775063<064406?3058<05", "7305>005760668061406;005?3042704", "<703960371034803?=02<>028>020=02", ":1015301>:00<9004301>:0159027:02", "1;028=012<018=00=7??45??=3?>3??>", "83?=09?===?<9:?<34?<=6?;7=?;10?;", ":>?:76?:63?:0=?:;0?9;8?90??:47?:", "18?:;6?917?91=?803?714?6:5?53??5", ":9?444?44??46>?46>?490?4:3?486?4", "83?49;?43>?52??6<5?67:?76>?848?9", "0;?::9?:38?;9:?;9??;72?;5=?;6;?9:1?93=?:52?;27?<", "57?=>>?>600076012402>70258030003", "=102140334036>039103;=0311044<04", "<7048105=805:1054;05?804:204:304", "=6040>0595054506<20689077>086809", "280:4;0:470:4:0:<509?4085308<;07", "32079706930622075=07250711074407", "5;0758079507=:079907?8067106?=05", "7605?504>:042>0533050005<5047304", "=903?50209027201540158017101<:01", "1:023;024>025?0267023>02=4018=01", "4701<=004500=5??75??>39?>:1?=", "52?=14?=;:?<66?<4>?<68?<54?<1;?<", "?=?;;:?;3>?;<8?:6;?:2;?:>7?998?9", "3=?9;=?813?875?7<=?372?4>>?438?589?5?1?5", "5??680?686?6<4?606?71??782?716?8", "9>?812?970?9?4?920?;07?<<6?<>;?=", "=:?>39??82??510025017701=601<202", "800323039102;=02=8025302>2016902", ";30332046?045?056506:6064:067<06", "12071;07<70631074408>=0833097:09", ";5098409<=085108?2074307=>060;07", "7;0797075=0762077507540734073907", "8407?00720080508>:079;07>9063006", ";<058:053605<30486046;0408045?03", ">302=302;10278029802240389037903", "4?0375039>036703>7026<02>3016:01", "00017>00>;??49??<>?>92?>63?>1=?>", ">9?9", "5>?918?997?8<:?7?3?65;?604?6;;?5", "96?58:?591?5;?668?53>?5;:?5", "66?606?7::?764?8>??816?957?9:=?9", "92?943?95?:7=?;=2?;59?<", "065?>:;?>49??0>00<200", "0;01>700=;004=0100023202=401:801", "3;021?03?203<:048:05?90522061206", "?905>>05070631067606=;066?071308", "6708850864081108<=07=40715081:08", "?0072708:008=<08=>08;?0884084108", "0008>80707970789071:07", "710612061406>60581053>051?05=204", "3?04=>03;0035<03?502?4027903>?03", "0:040<0432044204>;036<03?:026?02", ":?011:01=600;5007<0054005:003:00", ":5??32??35??10??9:?>38?>08?>=;?=", "69?=>2?<<4?<=9?<8;?<:>?;>7?:90?:", "95?:<2?:;8?:4=?:<=?911?9;??8::?8", "06?836?744?7<>?70:?8<5?7=:?72;?8", "98?783?653?601?731?7:0?632?664?6", "92?6;>?6>=?6?:?6:9?620?64?;7;?<35?=", "59?=12?=4;?=50?>:8??9<003<01?;01", "820268022?0248021102?4006900;;01", "9<03:=0450052;06<10628061105<704", "?904:=044>042505<606<;073708=408", "79096609=30880085:08;507>?06=>06", "4?076007=<068<06;106;4065:066806", "0707:10705085708::086;085<072?06", "8;056005370518052005380529052?05", "87058=0592043303:102<202;102:202", "06039?039:0303034>03?6031>039801", "4:014802930211015:??;0?>=??>>9?>", "79?>92?=885?>4:?=49?;57?::7?:2;?;60?;", "<>?:37?:19?:4;?:?8?:55?;05?;<3?:", "43?:62?9?0?826?97;?5<1?6", "=1?732?9;6?::4?:55?8>>?5>2?542?7", "18?898?8>;?8=5?841?9<7?95;?955?8", "00?897?8=;?89?9>2?:29?<60?<", "52?:400=90119021801<:???7?>", ":1?><>?>;3??=5009>0176025203<=03", "79039;020502?301850281036604>904", "77052406;606?2067>06=7059705>205", "55068:06<606370766072=0722075>07", "3407<406?006:707;=0744073507;>07", "1<081908?4079307?00678064?060?06", "7=054105;9053406?5052805<8042:05", "7?0516050:042?03<702>01?200", "?5??::??97??::??550099016202::01", "????44?>31?=53?=0;?>14?>52?=3??=", "7=?;>6?849?861?9", "92?;9:?=03?>;;?<35?;>2?:?8?:2>?:", ";8?819?8;:?8?7?9;:?:9>?:7=?:48?;", "45?<97?;:3?9:6?7;=?61>?7>5?76=?8", "60?9=1?:;4?;::?;>4?:93?9?:?73;?7", "5:?814?:1=?;0??;=8?98??8<?:29?<4=?=429?=89?;?;?:47?<", "66?>11001?01<601?:01050230028201", "90??=7?=14?>10004802>2037=04<304", "5705040680057203<401;601>5028304", "9>057?05?=044405=5050:06<305:005", "4606:207:808:608=20706", "1:06>5055=05>>044;0565067207>>07", "0:08=707050714063:056104;5035:03", "8=036504=:0529077207:7063<05;003", "5802>101??0102027501=4002>018402", "=403>70303030;02650149013001;500", "1:00>>??53008>000:0036??;>?>5??>", "2>?>6:?>>3?>=4?>:2?>:=?>99?=9;?;", "69?:?5?:;??;:88?=86?;68?;", "2=?=15?>25?=21?;3>?9=5?84>?:5;?;", ";?<>8?<46?<<7?;;6;?>8=?=?9?<07?>90??", "83??66?>57?>>3?>50??23006901;902", "4<03=5026:0107001100;6019=034<04", "<5032703<10256026<021?03>6039804", "71054306<206<20640063305>:036503", "=<030605?;055106:7064407>907?>07", "0207>8057705=?046204?>044;064907", "49076?063:054<04:8047:05<;04::03", ";5033704:?04>204:>04>>0321037602", "<0015<017;013802:403;>04=904>603", ";802:=01<5??09?>=;?=83??8901?302", ";1031?036:010>0055??>2?=8??<66?=", "0???>=?>50?>76??9400?2??90?>01?=", "?;?;47?<81?<:>?;?4?:>9?;1=?><4?>", "9>?=<5?;1:4?=07?<29?:;8?96=?:;5?:", "17?:=3?917?;<6?;8>?;6>?;80?;11?<", "10?=;2?<7;?:;=?8?3?8:3?:8>?;:;?;", ":?>?>80?=:;?:94?95;?::8?:", ";??972?9;>?;<9?>350061??0<4?<", "88?;19?;:7?;42?<<7?<;9?=18??=700", ":502=7026?0002?=5>?;99?<36??4=01", "2>020402220288031;044702;;???4?>", "0400?501:703;6047;054706=>06;505", "?>020;012>01;8021=0438053806:706", ":20686062:06150543037<011201>802", "0506?1077>0746065=0631071?07:405", "=80392038304?104<>04?3041<056704", "340332033:048504>9030=0369022603", ":?04=7041?03?=018502130342025<01", "3101:501560224023:01050100023;03", "020253??82?=7=?=;:?>29??76?==:?:91?:88?<97?>6???", "?:?>=5?<:=?::2?:08?<;2?=90?=?9?;", "?>?::2?;20?=42?:70?:7??:?8?:57?<25?>", "<5?>>:?<9:?9:7?76>?9=:?<<>?>4:??", "4:?>5>?;81?8:>?87>?::>?;15?<82?<", "1>?=<2?=>5?=>3?=9??=<5?<20?<:??;", "0>3??0:00:=???1004;03", "9:03==01:6??98?>3;?>?>?>0801;302", ">0029802>=0228030<03<60245021001", "68005601830210035>04;;06;;079:06", "=;0489039102==018:019;01>6020805", "?>057605>904<=05><065=06>>03=401", ";601=5022<04;=04;?040;05:6051<06", ":90516047;02?>019<02>503;204;=03", ">901=>009701:=030<048601:7??:;00", "5<03>20444046=024:011?0130012:01", "=6016701;;3?<86?>500221033601", "29??48???<00580119??5=?=84?>73??", "=1?>45?=:6?01:>??;5?<", "3??<64?>5=00>3?>47?:12?77?>=4?>07<8??=>??;?3?;", ":??<3??=91?=5?;7=?=;7??56??8=?<42?:=?=37?>::??0??>:7?:8??9", "5=?;16?=32?=59?=94?>>?>", "=4?:95?978?;7??=:=?=64?<49?;7>?;", "?2?=4=013?036302050072?>:=?=60?<", "22?;=:?;88?>:001=;039?036501:2??", "?0??<6004<0030??=3?>29??1900??01", "4?0448054704320313039?029901:=00", "02007;00;8026;059?06>:05:<049903", "6=02;:00?5?>9:??5?031507:?07<005", ";2042<05190515034;002:??:=??7901", "780443077808><070506<902;=??64?>", "9=?>48006<022039:03=80158??>4?=<1??>>02;?03", "15029700?>01<=041;05100248?>35?<", "33?<4>?>5401:803:1046003=100????", "2:00;9?>;6?;3>?;=>?=410065004:??", "<01006102;20159?=80?91:?97=?<", "34003701:3??;0?>6800<401?8??=9?<", "11?:54?724?732?:=1??:;03>00267?>", "9>?;85?<<7?=2?:15?::3?:?=?<", "52002=0109008=?>35?=9;?;<5?;51?<1>?:;0?:::?<7:?=71?=96?>", "480?;", "8=?<=5??2>01:9???3?=96?<<9?:30?9", "9??;80009=0248009>?<6:?;?8?=;600", "48??0=?<7>?<<=00?403<<035>021=02", ";502350215??39?<09?=;>0095028600", "8??>000065022<032802:2004????:?>", "3:002<03?>06;00829064102:?01>>02", "?;0171??0;??>:0107057:06>605?<02", "78??85?>190010026003;=03<2038904", "0706;;065705>>0249012>0154021603", ";<02=;01450180018;020>03::01?8??", ":6006702<302?=013501>?0175038:03", "880143005501:102<<025:029=013;00", "25??>78??2;01<002;>00>:?;687030?9:??=>3002<013<0065?>>8?=", "?5?>6??>?4?;84?;=0?==8:?=330?;1:?;;2?><5?>56?<47?<7:00", "8303180157?<9??:0>?<11??2801<0?>", ">??835?6;6?981??9802?=01>5?><>?;", "<9?:>=?;:6?=13?>>0?<1??<45?>3902", "<003><0012?<<7?:09?>;100::?>8=?:", "29?:05?>2701320252030?03<9??35?=", "98?=<>?=18?=2=?>6801300476055?05", "920235?>85?<=19018;00>7?>>0?>", ";801<:0503076:03;1?>1;?>5=01:003", "2:039;017;006;007202>4051507:<04", "0>0170??5;004202?102?701?=009:01", "4:03900354022:02?603>40513062704", "<<017400==009=029103:;01?0?>2=??", "?<01390482049403:?01::??>8?>85??", ">=015=041=04;;0154008401<<025402", "6401?>002<00<3?>???>?60034020502", "7300;8?>89?>4900970267028:?>23?;", "3??=56028>05:<05?802=1?>68?;:=?:", "50?=70007<00=3?<:9?9:7?;33020706", ":6024:?=?4?;43?==5?<53?<67?=:10164042?022=?>06?<90?<", "1=?=11?<;??:4>?;::?>>=0025??:??;", "65?;61?>070034??=1?=23?=;6?<<3?<", "<5?=?8??9101;1005:?=>1?:04?<86?>", ">1?=<>?93;?8<0?<690293025:5?<", ":0??270200000;?;1?026202930045???8?>=0?=>5?:", "4??822?9>02>:??=5?:;=?7601", "5<002???0>??5:0173046>054<04?602", "<00224033>026:??89?<73?=70027?06", "0>0657033<02::0209031?037202?>00", "9>00<10130035;046=04=001>:?>3?00", "9<043?061403:=?>98?=5:004?037203", ";2016100>=??;>00:6035305:=035901", "9400<=0014013=00???=24?<7=?=6001", "6303850184??13013?03040170?;93?9", "==?=7;04:006>001;>?<1=?=85??7>?>", "<4?<6:?>630073?==??:54?>50037503", "<4?>96?;99?=7>00=4?>56?:2;?8;;?7", "89?870?<4000590128??>5???", ":0?=;??;9;?=45??7;?=;7?;24?=:??>", "<3?=;1?<==?=;;??04006=?=;2?987?9", "<5?=;101;?:39?995?>2:035902", ":9?>4=?<87?==9??8???:8?<25?<<9??", "?2014=006>?>95?>;??>=9?=82?=55?>", ":2?>96?=:>?=;:004:04=504>901?5?>", "8:??5102240291?=97?997?:82??;404", "4<07?;0531025;??=??>:??>72?>36??", "7>??>???6302=<05=20627044=016801", ":4020402?8??<3?>43005<0393043503", "340235031:0486020:0071??4000<400", ">;011005=40790069802520036014902", "01024;01=9000201=5027?040;042702", "0?0069??;5015:041003<3??<8??6503", "99048301?4?>0201;5034?03;1013301", "4601260027??>=???=009=??19?==1?=", "?8018?0592042100?3?=:>??2<0155?=", "34?9;7?<8:03;>040101???>2900<200", "83??>3?<4??;83?<=>?>:6?>88?<:>?=", "11028?039:000:?>1??>:>?=<6?:2??9", "=:?<3702650391?6:6?<1201<8<02", "5001:6??>=8?:72?8", ">;?994?>3<0230025900<:?=14?;?2?9", "92?;4;?=58?=98?<07?=:6?>:=002<02", "560159?>>7?<76?>64??00?<:7?88:?;", "1?02>=043>0273?>2330054??", "92?<48?;96?<>0???3027=03?<01>:??", ">??>3?0044028;0116??<1?>5<009101", "5301230059???;009?033803:=??<;?=", "1100?<020403<9014?02?>0364047<03", "1903:60203013???4;??270188023?02", "6402<10303054?043:021<015101<=01", ":101;800=>00=302:>04;=04<>031603", "=<020303>:02;;011:00770087021=03", "<601>600970138029<024003?>021102", ":0018101;4011:035:03;400=4?>8400", "2=037802>6??4001>30063??", "69??10026403:10020?>2;??8300=5??", "38???>??2301?70038???8000", ">9:?>9>??9:??:01<8?>:3?<76?>0901=:00<=?>", "7:?=11?=36>?;:>?:=1?<", ">5?=49?=?4?=2<002801>>?>66?;8??:", "?3?<<;?>43?=<:?:53?<86??36??58?<", ":3?;?:?=88??1:?>=??:003800?2??", "93??:;?=>;?<>6?>;;00;1??2:?>57?>", "56??<6??25??=3?>=4??3701:=016300", "::1?>0600;800>7008;01:9019:00", "?3??7200;;003100:1??>3??=900;701", ";?02:7031>03930166013;02;001<800", "?5008?01490216036>03;602?5012?02", "95024902=>018001;000290195031405", "<303;2019101?402:803040331026102", "?602180374026:01?700>7011<034603", ":802>?01:90134027?03>;037602;500", "08016?025;028<00;1??7>0187032403", ">6016>01<00028009100>700420076??", "91??9200:<019301????77?>79??;401", "=?01>9??60???=008201230000??;:?>", "3;?>83?<94?=23??54??=>?>:9??", "8:00?4??:5?>>9>?>?9?=04?=", "68?=42?>19?>:0?=9;8?=38?=", "90?=0<5?=3??=71?=67?>=8:?=", "=>?;:5?;6=?<55?=1;?>=:?>>5?>0??>", "81?=>;?=41?>10?>60?=44?=2;?=35?<", "=0?;;3?<565?>8:?>;>?>", "70?>4;?>40?>;;?=<>?=;??>51??", "=0?>2=?>1:?>39?>23?>3??>02??;=??", "<>??;003?0154015801", "?20070008>00=20093005?00;2001801", "530168013;011:016201=701=?01:;01", "=701150215020002><01=6012302:?02", ">8027?02=9018?01<00113026502;802", ";>02;102;402=402:4022302?<015502", "6=02220201022<029602?<02=;029102", "6<0268026:025:024102240208023002", "430205028:015<018301;901<:01:;01", "9<01840158012>012;0154016:017>01", "7=0154011;01;>0078006>007;008=00", "720046004600490050002700=6??;=??", "<5??:=??86??7:??93??96??88??6???", "55??41??14??07??>3?>:8?>;;?>>0?>", "=8?>::?>86?>5>?>2:?>01?>?5?=?6?=", "?7?=13?>04?>?;?=15?>1=?>0;?>0", "3:?>50?>0:?><2?=:=?=:9?=97?=69?=", "5??=8??==3?=01?>10?>07?>03?>>9?=0>7?=<0?==;?=0;?>04?>", ">=?=>8?=?3?=00?>1>?>38?>41?>6=?>", ";6?><6?>8>?>4:?>4:?>7:?>9<;?>", ">4?>;=?>;9?>0>??4:??3??5>??", "9>??;5??:???:??;;??<0??<1??", "=4??120048004=003300490077009200", "90007200530034006400<200>=000101", "270140012701?700:>009400<;001?01", "510164019501=601>:01;90175012101", "=800=;00260166016>0154017701;001", "=101;4015:0131018001=:0109020802", "<801;401;1019;0187011>01:;007;00", ":000?60028014?017?01;101<>019?01", "2?01>:00;>007=008200<800??00?;00", ">?0033014:01?1005?00>;???;??3:00", "42002:003<008100;:00:=003300=1??", ":0??92??>7??0:00>1??130084009000", "07009>9?>5>??98??", "74??83??;9??=9??<1??6;??>5?>>2?>", "57??58??0:??19??5=??3" }; Sound manual_exampleSound (void) { static Sound me = NULL; if (me == NULL) { long istring = 0, ichar = 24; me = Sound_create (1, 0.0, 20457.0/44100, 20457, 1.0/44100, 0.5/44100); for (long isamp = 1; isamp <= 20457; isamp ++) { unsigned short part1 = data [istring] [ichar] - '0'; unsigned short part2 = data [istring] [++ ichar] - '0'; unsigned short part3 = data [istring] [++ ichar] - '0'; unsigned short part4 = data [istring] [++ ichar] - '0'; my z [1] [isamp] = (signed short) ((part3 << 12) + (part4 << 8) + (part1 << 4) + part2) / 32768.0; if (++ ichar == 32) istring ++, ichar = 0; } } return me; } Pitch manual_examplePitch (void) { static Pitch me = NULL; if (me == NULL) { Melder_progressOff (); me = Sound_to_Pitch (manual_exampleSound (), 0.0, 200.0, 500.0); Melder_progressOn (); } return me; } /* End of file manual_exampleSound.cpp */ sources_5316/fon/PitchTier.cpp0000644000176700017670000001311511621653722015112 0ustar paulpaul/* PitchTier.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "PitchTier.h" #include "Pitch.h" Thing_implement (PitchTier, RealTier, 0); void structPitchTier :: v_info () { structData :: v_info (); MelderInfo_writeLine1 (L"Time domain:"); MelderInfo_writeLine3 (L" Start time: ", Melder_double (xmin), L" seconds"); MelderInfo_writeLine3 (L" End time: ", Melder_double (xmax), L" seconds"); MelderInfo_writeLine3 (L" Total duration: ", Melder_double (xmax - xmin), L" seconds"); MelderInfo_writeLine2 (L"Number of points: ", Melder_integer (points -> size)); MelderInfo_writeLine3 (L"Minimum pitch value: ", Melder_double (RealTier_getMinimumValue (this)), L" Hz"); MelderInfo_writeLine3 (L"Maximum pitch value: ", Melder_double (RealTier_getMaximumValue (this)), L" Hz"); } PitchTier PitchTier_create (double tmin, double tmax) { try { autoPitchTier me = Thing_new (PitchTier); RealTier_init (me.peek(), tmin, tmax); return me.transfer(); } catch (MelderError) { Melder_throw ("PitchTier not created."); } } void PitchTier_draw (PitchTier me, Graphics g, double tmin, double tmax, double fmin, double fmax, int garnish, const wchar *method) { RealTier_draw (me, g, tmin, tmax, fmin, fmax, garnish, method, L"Frequency (Hz)"); } PitchTier PointProcess_upto_PitchTier (PointProcess me, double frequency) { try { return (PitchTier) PointProcess_upto_RealTier (me, frequency, classPitchTier); } catch (MelderError) { Melder_throw (me, ": not converted to PitchTier."); } } void PitchTier_stylize (PitchTier me, double frequencyResolution, int useSemitones) { double dfmin; for (;;) { long i, imin = 0; dfmin = 1e300; for (i = 2; i <= my points -> size - 1; i ++) { RealPoint pm = (RealPoint) my points -> item [i]; RealPoint pl = (RealPoint) my points -> item [i - 1]; RealPoint pr = (RealPoint) my points -> item [i + 1]; double expectedFrequency = pl -> value + (pr -> value - pl -> value) / (pr -> number - pl -> number) * (pm -> number - pl -> number); double df = useSemitones ? 12 * fabs (log (pm -> value / expectedFrequency)) / NUMln2: fabs (pm -> value - expectedFrequency); if (df < dfmin) { imin = i; dfmin = df; } } if (imin == 0 || dfmin > frequencyResolution) break; Collection_removeItem (my points, imin); } } static void PitchTier_writeToSpreadsheetFile (PitchTier me, MelderFile file, int hasHeader) { autofile f = Melder_fopen (file, "w"); if (hasHeader) fprintf (f, "\"ooTextFile\"\n\"PitchTier\"\n%.17g %.17g %ld\n", my xmin, my xmax, my points -> size); for (long i = 1; i <= my points -> size; i ++) { RealPoint point = (RealPoint) my points -> item [i]; fprintf (f, "%.17g\t%.17g\n", point -> number, point -> value); } f.close (file); MelderFile_setMacTypeAndCreator (file, 'TEXT', 0); } void PitchTier_writeToPitchTierSpreadsheetFile (PitchTier me, MelderFile file) { try { PitchTier_writeToSpreadsheetFile (me, file, TRUE); } catch (MelderError) { Melder_throw (me, " not written to tab-separated PitchTier file."); } } void PitchTier_writeToHeaderlessSpreadsheetFile (PitchTier me, MelderFile file) { try { PitchTier_writeToSpreadsheetFile (me, file, FALSE); } catch (MelderError) { Melder_throw (me, " not written to tab-separated table file."); } } void PitchTier_shiftFrequencies (PitchTier me, double tmin, double tmax, double shift, int unit) { try { for (long i = 1; i <= my points -> size; i ++) { RealPoint point = (RealPoint) my points -> item [i]; double frequency = point -> value; if (point -> number < tmin || point -> number > tmax) continue; switch (unit) { case kPitch_unit_HERTZ: { frequency += shift; if (frequency <= 0.0) Melder_throw ("The resulting frequency has to be greater than 0 Hz."); } break; case kPitch_unit_MEL: { frequency = NUMhertzToMel (frequency) + shift; if (frequency <= 0.0) Melder_throw ("The resulting frequency has to be greater than 0 mel."); frequency = NUMmelToHertz (frequency); } break; case kPitch_unit_LOG_HERTZ: { frequency = pow (10.0, log10 (frequency) + shift); } break; case kPitch_unit_SEMITONES_1: { frequency = NUMsemitonesToHertz (NUMhertzToSemitones (frequency) + shift); } break; case kPitch_unit_ERB: { frequency = NUMhertzToErb (frequency) + shift; if (frequency <= 0.0) Melder_throw ("The resulting frequency has to be greater than 0 ERB."); frequency = NUMerbToHertz (frequency); } } point -> value = frequency; } } catch (MelderError) { Melder_throw (me, ": not all frequencies were shifted."); } } void PitchTier_multiplyFrequencies (PitchTier me, double tmin, double tmax, double factor) { Melder_assert (factor > 0.0); for (long i = 1; i <= my points -> size; i ++) { RealPoint point = (RealPoint) my points -> item [i]; if (point -> number < tmin || point -> number > tmax) continue; point -> value *= factor; } } /* End of file PitchTier.cpp */ sources_5316/fon/Sound_files.cpp0000644000176700017670000003105311755144673015502 0ustar paulpaul/* Sound_files.cpp * * Copyright (C) 1992-2011,2012 Paul Boersma & David Weenink * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2003/09/12 MelderFile_checkSoundFile * pb 2004/10/17 test for NULL file pointer when closing in Sound_read(2)FromSoundFile * pb 2005/06/17 Mac headers * pb 2006/01/05 movies for Mac * pb 2006/05/29 QuickTime inclusion made optional * pb 2006/10/28 erased MacOS 9 stuff * pb 2006/12/30 stereo * pb 2006/01/01 more stereo * pb 2007/01/28 removed a warning * pb 2007/01/28 made readFromMovieFile compatible with stereo * pb 2007/03/17 resistant against conflicting declarations of Collection * pb 2007/05/08 removed warning about stereo sounds * pb 2007/10/05 removed FSSpec * pb 2007/10/05 made Sound_readFromMacSoundFile compatible with sample rates between 32768 and 65535 Hz * pb 2008/01/19 double * pb 2009/09/21 made stereo movies readable * pb 2010/12/27 support for multiple channels (i.e. more than two) * pb 2011/06/07 C++ * pb 2012/04/29 removed Sound Manager stuff * pb 2012/04/29 removed QuickTime */ /* static void Sound_ulawDecode (Sound me) { double mu = 100, lnu1 = log (1 + mu); for (long i = 1; i <= my nx; i ++) { double zabs = (exp (fabs (my z [1] [i]) * lnu1) - 1.0) / mu; my z [1] [i] = my z [1] [i] < 0 ? -zabs : zabs; } } static void Sound_alawDecode (Sound me) { double a = 87.6, lna1 = 1.0 + log (a); for (long i = 1; i <= my nx; i ++) { double zabs = fabs (my z [1] [i]); if (zabs <= 1.0 / lna1) { my z [1] [i] *= lna1 / a; } else { double t = exp (lna1 * zabs - 1.0) / a; my z [1] [i] = my z [1] [i] > 0 ? t : - t; } } } */ #include #include "Sound.h" Sound Sound_readFromSoundFile (MelderFile file) { try { autoMelderFile mfile = MelderFile_open (file); int numberOfChannels, encoding; double sampleRate; long startOfData, numberOfSamples; int fileType = MelderFile_checkSoundFile (file, & numberOfChannels, & encoding, & sampleRate, & startOfData, & numberOfSamples); if (fileType == 0) Melder_throw ("Not an audio file."); if (fseek (file -> filePointer, startOfData, SEEK_SET) == EOF) // start from beginning of Data Chunk Melder_throw ("No data in audio file."); autoSound me = Sound_createSimple (numberOfChannels, numberOfSamples / sampleRate, sampleRate); if (encoding == Melder_SHORTEN || encoding == Melder_POLYPHONE) Melder_throw ("Cannot unshorten. Write to paul.boersma@uva.nl for more information."); Melder_readAudioToFloat (file -> filePointer, numberOfChannels, encoding, my z, numberOfSamples); therror mfile.close (); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not read from sound file ", file, "."); } } Sound Sound_readFromSesamFile (MelderFile file) { try { autofile f = Melder_fopen (file, "rb"); long header [1 + 128]; for (long i = 1; i <= 128; i ++) header [i] = bingeti4LE (f); /* * Try SESAM header. */ double samplingFrequency = header [126]; long numberOfSamples = header [127]; if (samplingFrequency == 0.0 || numberOfSamples == 0) { /* * Try LVS header. */ samplingFrequency = header [62]; numberOfSamples = (header [6] << 8) - header [68]; } if (numberOfSamples < 1 || numberOfSamples > 1000000000 || samplingFrequency < 10.0 || samplingFrequency > 100000000.0) Melder_throw ("Not a correct SESAM or LVS file."); autoSound me = Sound_createSimple (1, numberOfSamples / samplingFrequency, samplingFrequency); for (long i = 1; i <= numberOfSamples; i ++) { my z [1] [i] = bingeti2LE (f) * (1.0 / 2048); // 12 bits } f.close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not read from Sesam file ", file, "."); } } Sound Sound_readFromBellLabsFile (MelderFile file) { try { /* * Check existence and permissions of file. */ autofile f = Melder_fopen (file, "rb"); /* * Check identity of file: first line is "SIG", second line contains a number. */ char tag [200]; if (fread (tag, 1, 16, f) < 16 || ! strnequ (tag, "SIG\n", 4)) Melder_throw ("Not a Bell-Labs sound file."); char *endOfTag = strchr (tag + 4, '\n'); if (endOfTag == NULL) Melder_throw ("Second line missing or too long."); unsigned long tagLength = endOfTag - tag + 1; // probably 12 unsigned long headerLength = atol (tag + 4); if (headerLength <= 0) Melder_throw ("Wrong header-length info."); /* * Read data from header. * Use defaults if necessary. */ autostring8 lines = Melder_calloc (char, headerLength + 1); if (fread (lines.peek(), 1, headerLength, f) < headerLength) Melder_throw ("Header too short."); unsigned long numberOfSamples = 0; char *psamples = & lines [-1]; while ((psamples = strstr (psamples + 1, "samples ")) != NULL) // take last occurrence numberOfSamples = atol (psamples + 8); if (numberOfSamples < 1) { /* Use file length. */ fseek (f, 0, SEEK_END); /* Position file pointer at end of file. */ numberOfSamples = (ftell (f) - tagLength - headerLength) / 2; } if (numberOfSamples < 1) Melder_throw ("No samples found."); double samplingFrequency = 0.0; char *pfrequency = & lines [-1]; while ((pfrequency = strstr (pfrequency + 1, "frequency ")) != NULL) // take last occurrence samplingFrequency = atof (pfrequency + 10); if (samplingFrequency <= 0.0) samplingFrequency = 16000.0; /* * Create sound. */ autoSound me = Sound_createSimple (1, numberOfSamples / samplingFrequency, samplingFrequency); /* * Read samples. */ fseek (f, tagLength + headerLength, SEEK_SET); for (unsigned long i = 1; i <= numberOfSamples; i ++) my z [1] [i] = bingeti2 (f) * (1.0 / 32768); // 16-bits big-endian f.close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not read from Bell Labs sound file ", file, "."); } } static void readError () { Melder_throw ("Error reading bytes from file."); } Sound Sound_readFromKayFile (MelderFile file) { try { autofile f = Melder_fopen (file, "rb"); /* Read header of KAY file: 12 bytes. */ char data [100]; if (fread (data, 1, 12, f) < 12) readError (); if (! strnequ (data, "FORMDS16", 8)) Melder_throw ("Not a KAY DS-16 file."); /* HEDR chunk */ if (fread (data, 1, 4, f) < 4) readError (); if (! strnequ (data, "HEDR", 4)) Melder_throw ("Missing HEDR chunk."); unsigned long chunkSize = bingetu4LE (f); therror if (chunkSize & 1) ++ chunkSize; if (fread (data, 1, chunkSize - 12, f) < chunkSize - 12) readError (); double samplingFrequency = bingetu4LE (f); therror unsigned long numberOfSamples = bingetu4LE (f); therror if (samplingFrequency <= 0 || samplingFrequency > 1e7 || numberOfSamples >= 1000000000) Melder_throw ("Not a correct Kay file."); if (fread (data, 1, 4, f) < 4) readError (); // absolute extrema A/B /* SD chunk */ if (fread (data, 1, 4, f) < 4) readError (); while (! strnequ (data, "SDA_", 4) && ! strnequ (data, "SD_B", 4)) { if (feof (f)) Melder_throw ("Missing or unreadable SD chunk."); chunkSize = bingetu4LE (f); therror if (chunkSize & 1) ++ chunkSize; if (fread (data, 1, chunkSize, f) < chunkSize) readError (); if (fread (data, 1, 4, f) < 4) readError (); } chunkSize = bingetu4LE (f); therror if (chunkSize != numberOfSamples * 2) Melder_throw ("Incomplete SD chunk."); autoSound me = Sound_createSimple (1, numberOfSamples / samplingFrequency, samplingFrequency); for (unsigned long i = 1; i <= numberOfSamples; i ++) { my z [1] [i] = bingeti2LE (f) / 32768.0; therror } f.close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not read from Kay file ", file, "."); } } Sound Sound_readFromRawAlawFile (MelderFile file) { try { double sampleRate = 8000.0; autofile f = Melder_fopen (file, "rb"); fseek (f, 0, SEEK_END); long numberOfSamples = ftell (f); rewind (f); autoSound me = Sound_createSimple (1, numberOfSamples / sampleRate, sampleRate); Melder_readAudioToFloat (f, 1, Melder_ALAW, my z, numberOfSamples); therror f.close (file); return me.transfer(); } catch (MelderError) { Melder_throw ("Sound not read from raw A-law file ", file, "."); } } void Sound_writeToAudioFile (Sound me, MelderFile file, int audioFileType, int numberOfBitsPerSamplePoint) { try { autoMelderFile mfile = MelderFile_create (file, Melder_macAudioFileType (audioFileType), L"PpgB", Melder_winAudioFileExtension (audioFileType)); MelderFile_writeAudioFileHeader (file, audioFileType, floor (1.0 / my dx + 0.5), my nx, my ny, numberOfBitsPerSamplePoint); therror MelderFile_writeFloatToAudio (file, my ny, Melder_defaultAudioFileEncoding (audioFileType, numberOfBitsPerSamplePoint), my z, my nx, TRUE); therror MelderFile_writeAudioFileTrailer (file, audioFileType, floor (1.0 / my dx + 0.5), my nx, my ny, numberOfBitsPerSamplePoint); therror mfile.close (); } catch (MelderError) { Melder_throw (me, ": not written to 16-bit sound file ", file, "."); } } void Sound_writeToSesamFile (Sound me, MelderFile file) { try { autofile f = Melder_fopen (file, "wb"); long header [1 + 128], tail; MelderFile_setMacTypeAndCreator (file, 'BINA', 'PpgB'); for (long i = 1; i <= 128; i ++) header [i] = 0; /* ILS header. */ header [6] = ((my nx - 1) >> 8) + 1; /* Number of disk blocks. */ header [64] = 32149; /* ILS magic. */ /* LVS header. */ header [62] = floor (1 / my dx + 0.5); /* Sampling frequency, rounded to n Hz. */ header [63] = -32000; /* Magic: "sampled signal." */ header [66] = 2047; /* Maximum absolute value: 12 bits. */ header [67] = 2047; /* LVS magic. */ header [68] = my nx % 256; /* Number of samples in last block. */ header [69] = 1; /* ? */ /* Sesam header. */ header [126] = floor (1 / my dx + 0.5); /* Sampling frequency, rounded to n Hz. */ header [127] = my nx; /* Number of samples. */ for (long i = 1; i <= 128; i ++) binputi4LE (header [i], f); for (long i = 1; i <= my nx; i ++) binputi2LE (floor (my z [1] [i] * 2048 + 0.5), f); tail = 256 - my nx % 256; if (tail == 256) tail = 0; for (long i = 1; i <= tail; i ++) binputi2LE (0, f); /* Pad last block with zeroes. */ f.close (file); } catch (MelderError) { Melder_throw (me, ": not written to Sesam file ", file, "."); } } void Sound_writeToKayFile (Sound me, MelderFile file) { try { autoMelderFile mfile = MelderFile_create (file, L"BINA", L"PpgB", L"KaySound"); /* Form Chunk: contains all other chunks. */ fwrite ("FORMDS16", 1, 8, file -> filePointer); binputi4LE (48 + my nx * 2, file -> filePointer); // size of Form Chunk fwrite ("HEDR", 1, 4, file -> filePointer); binputi4LE (32, file -> filePointer); char date [100]; time_t today = time (NULL); strcpy (date, ctime (& today)); fwrite (date+4, 1, 20, file -> filePointer); // skip weekday binputi4LE (floor (1 / my dx + 0.5), file -> filePointer); // sampling frequency binputi4LE (my nx, file -> filePointer); // number of samples int maximum = 0; for (long i = 1; i <= my nx; i ++) { long value = floor (my z [1] [i] * 32768 + 0.5); if (value < - maximum) maximum = - value; if (value > maximum) maximum = value; } binputi2LE (maximum, file -> filePointer); // absolute maximum window A binputi2LE (-1, file -> filePointer); // absolute maximum window B fwrite ("SDA_", 1, 4, file -> filePointer); binputi4LE (my nx * 2, file -> filePointer); // chunk size MelderFile_writeFloatToAudio (file, my ny, Melder_LINEAR_16_LITTLE_ENDIAN, my z, my nx, TRUE); therror mfile.close (); } catch (MelderError) { Melder_throw (me, ": not written to Kay sound file ", file, "."); } } void Sound_writeToRawSoundFile (Sound me, MelderFile file, int encoding) { try { autoMelderFile mfile = MelderFile_create (file, L"BINA", L"PpgB", L"rawSound"); MelderFile_writeFloatToAudio (file, my ny, encoding, my z, my nx, TRUE); therror mfile.close (); } catch (MelderError) { Melder_throw (me, ": not written to raw sound file ", file, "."); } } /* End of file Sound_files.cpp */ sources_5316/fon/LongSound.h0000644000176700017670000000600011723475044014571 0ustar paulpaul#ifndef _LongSound_h_ #define _LongSound_h_ /* LongSound.h * * Copyright (C) 1992-2012 Paul Boersma, 2007 Erez Volk (for FLAC, MP3) * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Sound.h" #include "Collection.h" #define COMPRESSED_MODE_READ_FLOAT 0 #define COMPRESSED_MODE_READ_SHORT 1 struct FLAC__StreamDecoder; struct FLAC__StreamEncoder; struct _MP3_FILE; Thing_define (LongSound, Sampled) { // new data: public: structMelderFile file; FILE *f; int audioFileType, numberOfChannels, encoding, numberOfBytesPerSamplePoint; double sampleRate; long startOfData; double bufferLength; short *buffer; long imin, imax, nmax; struct FLAC__StreamDecoder *flacDecoder; struct _MP3_FILE *mp3f; int compressedMode; long compressedSamplesLeft; double *compressedFloats [2]; short *compressedShorts; // overridden methods: virtual void v_destroy (); virtual void v_info (); virtual void v_copy (Any data_to); virtual bool v_writable () { return false; } virtual int v_domainQuantity () { return MelderQuantity_TIME_SECONDS; } }; LongSound LongSound_open (MelderFile fs); Sound LongSound_extractPart (LongSound me, double tmin, double tmax, int preserveTimes); bool LongSound_haveWindow (LongSound me, double tmin, double tmax); /* * Returns 0 if error or if window exceeds buffer, otherwise 1; */ void LongSound_getWindowExtrema (LongSound me, double tmin, double tmax, int channel, double *minimum, double *maximum); void LongSound_playPart (LongSound me, double tmin, double tmax, int (*callback) (void *closure, int phase, double tmin, double tmax, double t), void *closure); void LongSound_writePartToAudioFile (LongSound me, int audioFileType, double tmin, double tmax, MelderFile file); void LongSound_writeChannelToAudioFile (LongSound me, int audioFileType, int channel, MelderFile file); void LongSound_readAudioToFloat (LongSound me, double **buffer, long firstSample, long numberOfSamples); void LongSound_readAudioToShort (LongSound me, short *buffer, long firstSample, long numberOfSamples); void LongSound_concatenate (Collection collection, MelderFile file, int audioFileType, int numberOfBitsPerSamplePoint); /* Concatenate a collection of Sound and LongSound objects. */ void LongSound_prefs (void); long LongSound_getBufferSizePref_seconds (void); void LongSound_setBufferSizePref_seconds (long size); /* End of file LongSound.h */ #endif sources_5316/fon/DurationTierEditor.cpp0000644000176700017670000000354411632121116016771 0ustar paulpaul/* DurationTierEditor.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "DurationTierEditor.h" #include "EditorM.h" Thing_implement (DurationTierEditor, RealTierEditor, 0); static void menu_cb_DurationTierHelp (EDITOR_ARGS) { EDITOR_IAM (DurationTierEditor); Melder_help (L"DurationTier"); } void structDurationTierEditor :: v_createHelpMenuItems (EditorMenu menu) { DurationTierEditor_Parent :: v_createHelpMenuItems (menu); EditorMenu_addCommand (menu, L"DurationTier help", 0, menu_cb_DurationTierHelp); } void structDurationTierEditor :: v_play (double a_tmin, double a_tmax) { if (sound.data) { Sound_playPart (sound.data, a_tmin, a_tmax, NULL, NULL); } else { //DurationTier_playPart (data, a_tmin, a_tmax, FALSE); } } DurationTierEditor DurationTierEditor_create (GuiObject parent, const wchar *title, DurationTier duration, Sound sound, bool ownSound) { try { autoDurationTierEditor me = Thing_new (DurationTierEditor); RealTierEditor_init (me.peek(), parent, title, (RealTier) duration, sound, ownSound); return me.transfer(); } catch (MelderError) { Melder_throw ("DurationTier window not created."); } } /* End of file DurationTierEditor.cpp */ sources_5316/fon/Distributions_and_Transition.cpp0000644000176700017670000001327111620507675021124 0ustar paulpaul/* Distributions_and_Transition.cpp * * Copyright (C) 1997-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 1997/03/02 created * pb 2002/07/16 GPL * pb 2007/08/12 wchar * pb 2011/05/09 C++ */ #include "Distributions_and_Transition.h" Transition Distributions_to_Transition (Distributions underlying, Distributions surface, long environment, Transition adjacency, int greedy) { try { if (underlying == NULL) return NULL; /* * Preconditions: range check and matrix matching. */ if (environment < 1 || environment > underlying -> numberOfColumns) Melder_throw ("Environment (", environment, ") out of range (1-", underlying -> numberOfColumns, ")."); if (surface && (underlying -> numberOfColumns != surface -> numberOfColumns || underlying -> numberOfRows != surface -> numberOfRows)) Melder_throw ("Sizes of underlying and surface distributions do not match."); if (adjacency && adjacency -> numberOfStates != underlying -> numberOfColumns) Melder_throw ("Number of states (", adjacency -> numberOfStates, ") in adjacency matrix " "does not match number of distributions (", underlying -> numberOfColumns, ")"); /* * Defaults. */ if (surface == NULL) surface = underlying; /* * Create the output object. */ autoTransition thee = Transition_create (underlying -> numberOfColumns); /* * Copy labels and set name. */ for (long i = 1; i <= thy numberOfStates; i ++) { thy stateLabels [i] = Melder_wcsdup (underlying -> columnLabels [i]); } Thing_setName (thee.peek(), underlying -> columnLabels [environment]); therror /* * Compute the off-diagonal elements of the transition matrix in environment 'environment'. */ for (long i = 1; i <= thy numberOfStates; i ++) { /* * How many states are available for the learner to step to (excluding current state)? */ long numberOfAdjacentStates; if (adjacency) { numberOfAdjacentStates = 0; for (long j = 1; j <= thy numberOfStates; j ++) if (i != j && adjacency -> data [i] [j]) numberOfAdjacentStates ++; } else { numberOfAdjacentStates = thy numberOfStates - 1; } /* * Try all possible steps to adjacent states. */ for (long j = 1; j <= thy numberOfStates; j ++) if (i != j) { /* * Local: grammar step only possible to adjacent grammar. */ if (adjacency && adjacency -> data [i] [j] == 0) continue; /* * Compute element (i, j): sum over all possible data. */ for (long m = 1; m <= underlying -> numberOfRows; m ++) { /* * Error-driven: grammar step only triggered by positive evidence. * If the datum does not conflict with the current hypothesis (i), ignore it. */ if (underlying -> data [m] [i]) continue; /* * Greedy: grammar step only taken if new grammar accepts datum. */ if (greedy && underlying -> data [m] [j] == 0) continue; /* * The step is taken if this datum occurs and this grammar (j) is chosen. */ thy data [i] [j] += surface -> data [m] [environment] / numberOfAdjacentStates; } } } /* * Compute the elements on the diagonal, so that the sum of each row is unity. */ for (long i = 1; i <= thy numberOfStates; i ++) { double sum = 0.0; for (long j = 1; j <= thy numberOfStates; j ++) if (j != i) sum += thy data [i] [j]; thy data [i] [i] = sum > 1.0 ? 0.0 : 1.0 - sum; // guard against rounding errors } return thee.transfer(); } catch (MelderError) { Melder_throw (underlying, ": Transition not computed."); } } Distributions Distributions_Transition_map (Distributions me, Transition map) { try { /* * Preconditions: matrix matching. */ if (map -> numberOfStates != my numberOfRows) Melder_throw ("Number of data (", map -> numberOfStates, ") in mapping matrix " "does not match number of data (", my numberOfRows, ") in distribution."); /* * Create the output object. */ autoDistributions thee = Data_copy (me); /* * Compute the elements of the surface distributions. */ for (long row = 1; row <= my numberOfRows; row ++) for (long col = 1; col <= my numberOfColumns; col ++) { thy data [row] [col] = 0.0; for (long m = 1; m <= map -> numberOfStates; m ++) thy data [row] [col] += my data [m] [col] * map -> data [m] [row]; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not mapped to Transition."); } } Distributions Transition_to_Distributions_conflate (Transition me) { try { autoDistributions thee = Distributions_create (my numberOfStates, 1); /* * Copy labels. */ for (long i = 1; i <= my numberOfStates; i ++) { thy rowLabels [i] = Melder_wcsdup (my stateLabels [i]); } /* * Average rows. */ for (long i = 1; i <= my numberOfStates; i ++) { for (long j = 1; j <= my numberOfStates; j ++) thy data [i] [1] += my data [j] [i]; thy data [i] [1] /= my numberOfStates; } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not conflated to Distributions."); } } /* End of file Distributions_and_Transition.cpp */ sources_5316/fon/praat_TextGrid_init.cpp0000644000176700017670000020462311727460415017173 0ustar paulpaul/* praat_TextGrid_init.cpp * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "praat.h" #include "Pitch_AnyTier_to_PitchTier.h" #include "SpectrumEditor.h" #include "SpellingChecker.h" #include "TextGridEditor.h" #include "TextGrid_extensions.h" #include "TextGrid_Sound.h" #include "WordList.h" #undef iam #define iam iam_LOOP void praat_dia_timeRange (Any dia); void praat_get_timeRange (Any dia, double *tmin, double *tmax); int praat_get_frequencyRange (Any dia, double *fmin, double *fmax); static const wchar *STRING_FROM_FREQUENCY_HZ = L"left Frequency range (Hz)"; static const wchar *STRING_TO_FREQUENCY_HZ = L"right Frequency range (Hz)"; static const wchar *STRING_TIER_NUMBER = L"Tier number"; static const wchar *STRING_INTERVAL_NUMBER = L"Interval number"; static const wchar *STRING_POINT_NUMBER = L"Point number"; void praat_TimeFunction_modify_init (ClassInfo klas); // Modify buttons for time-based subclasses of Function. /***** ANYTIER (generic) *****/ DIRECT (AnyTier_into_TextGrid) autoTextGrid grid = TextGrid_createWithoutTiers (1e30, -1e30); LOOP { iam (AnyTier); TextGrid_addTier (grid.peek(), me); } praat_new (grid.transfer(), L"grid"); END /***** INTERVALTIER *****/ FORM (IntervalTier_downto_TableOfReal, L"IntervalTier: Down to TableOfReal", 0) SENTENCE (L"Label", L"") OK DO LOOP { iam (IntervalTier); autoTableOfReal thee = IntervalTier_downto_TableOfReal (me, GET_STRING (L"Label")); praat_new (thee.transfer(), my name); } END DIRECT (IntervalTier_downto_TableOfReal_any) LOOP { iam (IntervalTier); autoTableOfReal thee = IntervalTier_downto_TableOfReal_any (me); praat_new (thee.transfer(), my name); } END FORM (IntervalTier_getCentrePoints, L"IntervalTier: Get centre points", 0) SENTENCE (L"Text", L"") OK DO LOOP { iam (IntervalTier); autoPointProcess thee = IntervalTier_getCentrePoints (me, GET_STRING (L"Text")); praat_new (thee.transfer(), GET_STRING (L"Text")); } END FORM (IntervalTier_getEndPoints, L"IntervalTier: Get end points", 0) SENTENCE (L"Text", L"") OK DO LOOP { iam (IntervalTier); autoPointProcess thee = IntervalTier_getEndPoints (me, GET_STRING (L"Text")); praat_new (thee.transfer(), GET_STRING (L"Text")); } END FORM (IntervalTier_getStartingPoints, L"IntervalTier: Get starting points", 0) SENTENCE (L"Text", L"") OK DO LOOP { iam (IntervalTier); autoPointProcess thee = IntervalTier_getStartingPoints (me, GET_STRING (L"Text")); praat_new (thee.transfer(), GET_STRING (L"Text")); } END DIRECT (IntervalTier_help) Melder_help (L"IntervalTier"); END FORM_WRITE (IntervalTier_writeToXwaves, L"Xwaves label file", 0, 0) LOOP { iam (IntervalTier); IntervalTier_writeToXwaves (me, file); therror } END /***** INTERVALTIER & POINTPROCESS *****/ FORM (IntervalTier_PointProcess_endToCentre, L"From end to centre", L"IntervalTier & PointProcess: End to centre...") REAL (L"Phase (0-1)", L"0.5") OK DO IntervalTier tier = NULL; PointProcess point = NULL; LOOP { if (CLASS == classIntervalTier) tier = (IntervalTier) OBJECT; if (CLASS == classPointProcess) point = (PointProcess) OBJECT; } double phase = GET_REAL (L"Phase"); autoPointProcess thee = IntervalTier_PointProcess_endToCentre (tier, point, phase); praat_new (thee.transfer(), tier -> name, L"_", point -> name, L"_", Melder_integer ((long) (100 * phase))); END FORM (IntervalTier_PointProcess_startToCentre, L"From start to centre", L"IntervalTier & PointProcess: Start to centre...") REAL (L"Phase (0-1)", L"0.5") OK DO IntervalTier tier = NULL; PointProcess point = NULL; LOOP { if (CLASS == classIntervalTier) tier = (IntervalTier) OBJECT; if (CLASS == classPointProcess) point = (PointProcess) OBJECT; } double phase = GET_REAL (L"Phase"); autoPointProcess thee = IntervalTier_PointProcess_startToCentre (tier, point, phase); praat_new (thee.transfer(), tier -> name, L"_", point -> name, L"_", Melder_integer ((long) (100 * phase))); END /***** LABEL (obsolete) *****/ DIRECT (Label_Sound_to_TextGrid) Label label = NULL; Sound sound = NULL; LOOP { if (CLASS == classLabel) label = (Label) OBJECT; if (CLASS == classSound) sound = (Sound) OBJECT; } autoTextGrid thee = Label_Function_to_TextGrid (label, sound); praat_new (thee.transfer(), sound -> name); END DIRECT (info_Label_Sound_to_TextGrid) Melder_information (L"This is an old-style Label object. To turn it into a TextGrid, L" "select it together with a Sound of the appropriate duration, and click \"To TextGrid\"."); END /***** PITCH & TEXTGRID *****/ static void pr_TextGrid_Pitch_draw (Any dia, int speckle, int unit) { TextGrid grid = NULL; Pitch pitch = NULL; int IOBJECT; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classPitch) pitch = (Pitch) OBJECT; } double tmin, tmax, fmin, fmax; praat_get_timeRange (dia, & tmin, & tmax); praat_get_frequencyRange (dia, & fmin, & fmax); therror autoPraatPicture picture; TextGrid_Pitch_draw (grid, pitch, GRAPHICS, GET_INTEGER (STRING_TIER_NUMBER), tmin, tmax, fmin, fmax, GET_INTEGER (L"Font size"), GET_INTEGER (L"Use text styles"), GET_INTEGER (L"Text alignment") - 1, GET_INTEGER (L"Garnish"), speckle, unit); } FORM (TextGrid_Pitch_draw, L"TextGrid & Pitch: Draw", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); REAL (STRING_FROM_FREQUENCY_HZ, L"0.0") POSITIVE (STRING_TO_FREQUENCY_HZ, L"500.0") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_NO, kPitch_unit_HERTZ); END FORM (TextGrid_Pitch_drawErb, L"TextGrid & Pitch: Draw erb", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); REAL (L"left Frequency range (ERB)", L"0") REAL (L"right Frequency range (ERB)", L"10.0") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_NO, kPitch_unit_ERB); END FORM (TextGrid_Pitch_drawLogarithmic, L"TextGrid & Pitch: Draw logarithmic", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); POSITIVE (STRING_FROM_FREQUENCY_HZ, L"50.0") POSITIVE (STRING_TO_FREQUENCY_HZ, L"500.0") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_NO, kPitch_unit_HERTZ_LOGARITHMIC); END FORM (TextGrid_Pitch_drawMel, L"TextGrid & Pitch: Draw mel", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); REAL (L"left Frequency range (mel)", L"0") REAL (L"right Frequency range (mel)", L"500") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_NO, kPitch_unit_MEL); END FORM (TextGrid_Pitch_drawSemitones, L"TextGrid & Pitch: Draw semitones", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); LABEL (L"", L"Range in semitones re 100 hertz:") REAL (L"left Frequency range (st)", L"-12.0") REAL (L"right Frequency range (st)", L"30.0") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_NO, kPitch_unit_SEMITONES_100); END static void pr_TextGrid_Pitch_drawSeparately (Any dia, int speckle, int unit) { TextGrid grid = NULL; Pitch pitch = NULL; int IOBJECT; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classPitch) pitch = (Pitch) OBJECT; } double tmin, tmax, fmin, fmax; praat_get_timeRange (dia, & tmin, & tmax); praat_get_frequencyRange (dia, & fmin, & fmax); therror autoPraatPicture picture; TextGrid_Pitch_drawSeparately (grid, pitch, GRAPHICS, tmin, tmax, fmin, fmax, GET_INTEGER (L"Show boundaries"), GET_INTEGER (L"Use text styles"), GET_INTEGER (L"Garnish"), speckle, unit); } FORM (TextGrid_Pitch_drawSeparately, L"TextGrid & Pitch: Draw separately", 0) praat_dia_timeRange (dia); REAL (STRING_FROM_FREQUENCY_HZ, L"0.0") REAL (STRING_TO_FREQUENCY_HZ, L"500.0") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_NO, kPitch_unit_HERTZ); END FORM (TextGrid_Pitch_drawSeparatelyErb, L"TextGrid & Pitch: Draw separately erb", 0) praat_dia_timeRange (dia); REAL (L"left Frequency range (ERB)", L"0") REAL (L"right Frequency range (ERB)", L"10.0") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_NO, kPitch_unit_ERB); END FORM (TextGrid_Pitch_drawSeparatelyLogarithmic, L"TextGrid & Pitch: Draw separately logarithmic", 0) praat_dia_timeRange (dia); POSITIVE (STRING_FROM_FREQUENCY_HZ, L"50.0") POSITIVE (STRING_TO_FREQUENCY_HZ, L"500.0") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_NO, kPitch_unit_HERTZ_LOGARITHMIC); END FORM (TextGrid_Pitch_drawSeparatelyMel, L"TextGrid & Pitch: Draw separately mel", 0) praat_dia_timeRange (dia); REAL (L"left Frequency range (mel)", L"0") REAL (L"right Frequency range (mel)", L"500") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_NO, kPitch_unit_MEL); END FORM (TextGrid_Pitch_drawSeparatelySemitones, L"TextGrid & Pitch: Draw separately semitones", 0) praat_dia_timeRange (dia); LABEL (L"", L"Range in semitones re 100 hertz:") REAL (L"left Frequency range (st)", L"-12.0") REAL (L"right Frequency range (st)", L"30.0") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_NO, kPitch_unit_SEMITONES_100); END FORM (TextGrid_Pitch_speckle, L"TextGrid & Pitch: Speckle", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); REAL (STRING_FROM_FREQUENCY_HZ, L"0.0") POSITIVE (STRING_TO_FREQUENCY_HZ, L"500.0") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_YES, kPitch_unit_HERTZ); END FORM (TextGrid_Pitch_speckleErb, L"TextGrid & Pitch: Speckle erb", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); REAL (L"left Frequency range (ERB)", L"0") REAL (L"right Frequency range (ERB)", L"10.0") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_YES, kPitch_unit_ERB); END FORM (TextGrid_Pitch_speckleLogarithmic, L"TextGrid & Pitch: Speckle logarithmic", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); POSITIVE (STRING_FROM_FREQUENCY_HZ, L"50.0") POSITIVE (STRING_TO_FREQUENCY_HZ, L"500.0") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_YES, kPitch_unit_HERTZ_LOGARITHMIC); END FORM (TextGrid_Pitch_speckleMel, L"TextGrid & Pitch: Speckle mel", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); REAL (L"left Frequency range (mel)", L"0") REAL (L"right Frequency range (mel)", L"500") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_YES, kPitch_unit_MEL); END FORM (TextGrid_Pitch_speckleSemitones, L"TextGrid & Pitch: Speckle semitones", 0) INTEGER (STRING_TIER_NUMBER, L"1") praat_dia_timeRange (dia); LABEL (L"", L"Range in semitones re 100 hertz:") REAL (L"left Frequency range (st)", L"-12.0") REAL (L"right Frequency range (st)", L"30.0") INTEGER (L"Font size (points)", L"18") BOOLEAN (L"Use text styles", 1) OPTIONMENU (L"Text alignment", 2) OPTION (L"Left") OPTION (L"Centre") OPTION (L"Right") BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_draw (dia, Pitch_speckle_YES, kPitch_unit_SEMITONES_100); END FORM (TextGrid_Pitch_speckleSeparately, L"TextGrid & Pitch: Speckle separately", 0) praat_dia_timeRange (dia); REAL (STRING_FROM_FREQUENCY_HZ, L"0.0") REAL (STRING_TO_FREQUENCY_HZ, L"500.0") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_YES, kPitch_unit_HERTZ); END FORM (TextGrid_Pitch_speckleSeparatelyErb, L"TextGrid & Pitch: Speckle separately erb", 0) praat_dia_timeRange (dia); REAL (L"left Frequency range (ERB)", L"0") REAL (L"right Frequency range (ERB)", L"10.0") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_YES, kPitch_unit_ERB); END FORM (TextGrid_Pitch_speckleSeparatelyLogarithmic, L"TextGrid & Pitch: Speckle separately logarithmic", 0) praat_dia_timeRange (dia); POSITIVE (STRING_FROM_FREQUENCY_HZ, L"50.0") POSITIVE (STRING_TO_FREQUENCY_HZ, L"500.0") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_YES, kPitch_unit_HERTZ_LOGARITHMIC); END FORM (TextGrid_Pitch_speckleSeparatelyMel, L"TextGrid & Pitch: Speckle separately mel", 0) praat_dia_timeRange (dia); REAL (L"left Frequency range (mel)", L"0") REAL (L"right Frequency range (mel)", L"500") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_YES, kPitch_unit_MEL); END FORM (TextGrid_Pitch_speckleSeparatelySemitones, L"TextGrid & Pitch: Speckle separately semitones", 0) praat_dia_timeRange (dia); LABEL (L"", L"Range in semitones re 100 hertz:") REAL (L"left Frequency range (st)", L"-12.0") REAL (L"right Frequency range (st)", L"30.0") BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO pr_TextGrid_Pitch_drawSeparately (dia, Pitch_speckle_YES, kPitch_unit_SEMITONES_100); END /***** PITCH & TEXTTIER *****/ FORM (Pitch_TextTier_to_PitchTier, L"Pitch & TextTier to PitchTier", L"Pitch & TextTier: To PitchTier...") RADIO (L"Unvoiced strategy", 3) RADIOBUTTON (L"Zero") RADIOBUTTON (L"Error") RADIOBUTTON (L"Interpolate") OK DO Pitch pitch = NULL; TextTier tier = NULL; LOOP { iam (Data); if (CLASS == classPitch) pitch = (Pitch) me; if (CLASS == classTextTier) tier = (TextTier) me; } autoPitchTier thee = Pitch_AnyTier_to_PitchTier (pitch, (AnyTier) tier, GET_INTEGER (L"Unvoiced strategy") - 1); praat_new (thee.transfer(), pitch -> name); END /***** SOUND & TEXTGRID *****/ FORM (TextGrid_Sound_draw, L"TextGrid & Sound: Draw...", 0) praat_dia_timeRange (dia); BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO TextGrid grid = NULL; Sound sound = NULL; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classSound) sound = (Sound) OBJECT; } autoPraatPicture picture; TextGrid_Sound_draw (grid, sound, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_INTEGER (L"Show boundaries"), GET_INTEGER (L"Use text styles"), GET_INTEGER (L"Garnish")); END FORM (TextGrid_Sound_extractAllIntervals, L"TextGrid & Sound: Extract all intervals", 0) INTEGER (STRING_TIER_NUMBER, L"1") BOOLEAN (L"Preserve times", 0) OK DO TextGrid grid = NULL; Sound sound = NULL; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classSound) sound = (Sound) OBJECT; } autoCollection thee = TextGrid_Sound_extractAllIntervals (grid, sound, GET_INTEGER (STRING_TIER_NUMBER), GET_INTEGER (L"Preserve times")); praat_new (thee.transfer(), L"dummy"); END FORM (TextGrid_Sound_extractNonemptyIntervals, L"TextGrid & Sound: Extract non-empty intervals", 0) INTEGER (STRING_TIER_NUMBER, L"1") BOOLEAN (L"Preserve times", 0) OK DO TextGrid grid = NULL; Sound sound = NULL; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classSound) sound = (Sound) OBJECT; } autoCollection thee = TextGrid_Sound_extractNonemptyIntervals (grid, sound, GET_INTEGER (STRING_TIER_NUMBER), GET_INTEGER (L"Preserve times")); praat_new (thee.transfer(), L"dummy"); END FORM (TextGrid_Sound_extractIntervals, L"TextGrid & Sound: Extract intervals", 0) INTEGER (STRING_TIER_NUMBER, L"1") BOOLEAN (L"Preserve times", 0) SENTENCE (L"Label text", L"") OK DO TextGrid grid = NULL; Sound sound = NULL; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classSound) sound = (Sound) OBJECT; } autoCollection thee = TextGrid_Sound_extractIntervalsWhere (grid, sound, GET_INTEGER (STRING_TIER_NUMBER), kMelder_string_EQUAL_TO, GET_STRING (L"Label text"), GET_INTEGER (L"Preserve times")); praat_new (thee.transfer(), GET_STRING (L"Label text")); END FORM (TextGrid_Sound_extractIntervalsWhere, L"TextGrid & Sound: Extract intervals", 0) INTEGER (STRING_TIER_NUMBER, L"1") BOOLEAN (L"Preserve times", 0) OPTIONMENU_ENUM (L"Extract all intervals whose label...", kMelder_string, DEFAULT) SENTENCE (L"...the text", L"") OK DO TextGrid grid = NULL; Sound sound = NULL; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classSound) sound = (Sound) OBJECT; } autoCollection thee = TextGrid_Sound_extractIntervalsWhere (grid, sound, GET_INTEGER (STRING_TIER_NUMBER), GET_ENUM (kMelder_string, L"Extract all intervals whose label..."), GET_STRING (L"...the text"), GET_INTEGER (L"Preserve times")); praat_new (thee.transfer(), GET_STRING (L"...the text")); END DIRECT (TextGrid_Sound_scaleTimes) TextGrid grid = NULL; Sound sound = NULL; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classSound) sound = (Sound) OBJECT; } Function_scaleXTo (grid, sound -> xmin, sound -> xmax); praat_dataChanged (grid); END DIRECT (TextGrid_Sound_cloneTimeDomain) TextGrid grid = NULL; Sound sound = NULL; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classSound) sound = (Sound) OBJECT; } sound -> x1 += grid -> xmin - sound -> xmin; sound -> xmin = grid -> xmin; sound -> xmax = grid -> xmax; praat_dataChanged (sound); END /***** SPELLINGCHECKER *****/ FORM (SpellingChecker_addNewWord, L"Add word to user dictionary", L"SpellingChecker") SENTENCE (L"New word", L"") OK DO LOOP { iam (SpellingChecker); SpellingChecker_addNewWord (me, GET_STRING (L"New word")); therror praat_dataChanged (me); } END FORM (SpellingChecker_edit, L"Edit spelling checker", L"SpellingChecker") LABEL (L"", L"-- Syntax --") SENTENCE (L"Forbidden strings", L"") BOOLEAN (L"Check matching parentheses", 0) SENTENCE (L"Separating characters", L"") BOOLEAN (L"Allow all parenthesized", 0) LABEL (L"", L"-- Capitals --") BOOLEAN (L"Allow all names", 0) SENTENCE (L"Name prefixes", L"") BOOLEAN (L"Allow all abbreviations", 0) LABEL (L"", L"-- Capitalization --") BOOLEAN (L"Allow caps sentence-initially", 0) BOOLEAN (L"Allow caps after colon", 0) LABEL (L"", L"-- Word parts --") SENTENCE (L"Allow all words containing", L"") SENTENCE (L"Allow all words starting with", L"") SENTENCE (L"Allow all words ending in", L"") OK int IOBJECT; LOOP { iam (SpellingChecker); SET_STRING (L"Forbidden strings", my forbiddenStrings) SET_INTEGER (L"Check matching parentheses", my checkMatchingParentheses) SET_STRING (L"Separating characters", my separatingCharacters) SET_INTEGER (L"Allow all parenthesized", my allowAllParenthesized) SET_INTEGER (L"Allow all names", my allowAllNames) SET_STRING (L"Name prefixes", my namePrefixes) SET_INTEGER (L"Allow all abbreviations", my allowAllAbbreviations) SET_INTEGER (L"Allow caps sentence-initially", my allowCapsSentenceInitially) SET_INTEGER (L"Allow caps after colon", my allowCapsAfterColon) SET_STRING (L"Allow all words containing", my allowAllWordsContaining) SET_STRING (L"Allow all words starting with", my allowAllWordsStartingWith) SET_STRING (L"Allow all words ending in", my allowAllWordsEndingIn) } DO LOOP { iam (SpellingChecker); Melder_free (my forbiddenStrings); my forbiddenStrings = Melder_wcsdup_f (GET_STRING (L"Forbidden strings")); my checkMatchingParentheses = GET_INTEGER (L"Check matching parentheses"); Melder_free (my separatingCharacters); my separatingCharacters = Melder_wcsdup_f (GET_STRING (L"Separating characters")); my allowAllParenthesized = GET_INTEGER (L"Allow all parenthesized"); my allowAllNames = GET_INTEGER (L"Allow all names"); Melder_free (my namePrefixes); my namePrefixes = Melder_wcsdup_f (GET_STRING (L"Name prefixes")); my allowAllAbbreviations = GET_INTEGER (L"Allow all abbreviations"); my allowCapsSentenceInitially = GET_INTEGER (L"Allow caps sentence-initially"); my allowCapsAfterColon = GET_INTEGER (L"Allow caps after colon"); Melder_free (my allowAllWordsContaining); my allowAllWordsContaining = Melder_wcsdup_f (GET_STRING (L"Allow all words containing")); Melder_free (my allowAllWordsStartingWith); my allowAllWordsStartingWith = Melder_wcsdup_f (GET_STRING (L"Allow all words starting with")); Melder_free (my allowAllWordsEndingIn); my allowAllWordsEndingIn = Melder_wcsdup_f (GET_STRING (L"Allow all words ending in")); praat_dataChanged (me); } END DIRECT (SpellingChecker_extractWordList) LOOP { iam (SpellingChecker); autoWordList thee = SpellingChecker_extractWordList (me); praat_new (thee.transfer(), my name); } END DIRECT (SpellingChecker_extractUserDictionary) LOOP { iam (SpellingChecker); autoSortedSetOfString thee = SpellingChecker_extractUserDictionary (me); praat_new (thee.transfer(), my name); } END FORM (SpellingChecker_isWordAllowed, L"Is word allowed?", L"SpellingChecker") SENTENCE (L"Word", L"") OK DO LOOP { iam (SpellingChecker); bool isWordAllowed = SpellingChecker_isWordAllowed (me, GET_STRING (L"Word")); Melder_information (isWordAllowed ? L"1 (allowed)" : L"0 (not allowed)"); } END FORM (SpellingChecker_nextNotAllowedWord, L"Next not allowed word?", L"SpellingChecker") LABEL (L"", L"Sentence:") TEXTFIELD (L"sentence", L"") INTEGER (L"Starting character", L"0") OK DO LOOP { iam (SpellingChecker); wchar *sentence = GET_STRING (L"sentence"); long startingCharacter = GET_INTEGER (L"Starting character"); if (startingCharacter < 0) Melder_throw ("Starting character should be 0 or positive."); if (startingCharacter > (int) wcslen (sentence)) Melder_throw ("Starting character should not exceed end of sentence."); wchar *nextNotAllowedWord = SpellingChecker_nextNotAllowedWord (me, sentence, & startingCharacter); Melder_information (nextNotAllowedWord); } END DIRECT (SpellingChecker_replaceWordList) SpellingChecker spellingChecker = NULL; WordList wordList = NULL; LOOP { if (CLASS == classSpellingChecker) spellingChecker = (SpellingChecker) OBJECT; if (CLASS == classWordList) wordList = (WordList) OBJECT; SpellingChecker_replaceWordList (spellingChecker, wordList); therror praat_dataChanged (spellingChecker); } END DIRECT (SpellingChecker_replaceWordList_help) Melder_information (L"To replace the checker's word list\nby the contents of a Strings object:\n" "1. select the Strings;\n2. convert to a WordList object;\n3. select the SpellingChecker and the WordList;\n" "4. choose Replace."); END DIRECT (SpellingChecker_replaceUserDictionary) SpellingChecker spellingChecker = NULL; SortedSetOfString dictionary = NULL; LOOP { if (CLASS == classSpellingChecker) spellingChecker = (SpellingChecker) OBJECT; if (CLASS == classSortedSetOfString) dictionary = (SortedSetOfString) OBJECT; SpellingChecker_replaceUserDictionary (spellingChecker, dictionary); } END /***** TEXTGRID *****/ FORM (TextGrid_countLabels, L"Count labels", L"TextGrid: Count labels...") INTEGER (STRING_TIER_NUMBER, L"1") SENTENCE (L"Label text", L"a") OK DO LOOP { iam (TextGrid); long numberOfLabels = TextGrid_countLabels (me, GET_INTEGER (STRING_TIER_NUMBER), GET_STRING (L"Label text")); Melder_information (Melder_integer (numberOfLabels), L" labels"); } END FORM (TextGrid_downto_Table, L"TextGrid: Down to Table", 0) BOOLEAN (L"Include line number", false) NATURAL (L"Time decimals", L"6") BOOLEAN (L"Include tier names", true) BOOLEAN (L"Include empty intervals", false) OK DO LOOP { iam (TextGrid); autoTable thee = TextGrid_downto_Table (me, GET_INTEGER (L"Include line number"), GET_INTEGER (L"Time decimals"), GET_INTEGER (L"Include tier names"), GET_INTEGER (L"Include empty intervals")); praat_new (thee.transfer(), my name); } END FORM (TextGrid_draw, L"TextGrid: Draw", 0) praat_dia_timeRange (dia); BOOLEAN (L"Show boundaries", 1) BOOLEAN (L"Use text styles", 1) BOOLEAN (L"Garnish", 1) OK DO autoPraatPicture picture; LOOP { iam (TextGrid); TextGrid_Sound_draw (me, NULL, GRAPHICS, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_INTEGER (L"Show boundaries"), GET_INTEGER (L"Use text styles"), GET_INTEGER (L"Garnish")); } END FORM (TextGrid_duplicateTier, L"TextGrid: Duplicate tier", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (L"Position", L"1 (= at top)") WORD (L"Name", L"") OK DO LOOP { iam (TextGrid); int itier = GET_INTEGER (STRING_TIER_NUMBER); int position = GET_INTEGER (L"Position"); const wchar *name = GET_STRING (L"Name"); if (itier > my tiers -> size) itier = my tiers -> size; autoAnyTier newTier = Data_copy ((AnyTier) my tiers -> item [itier]); Thing_setName (newTier.peek(), name); Ordered_addItemPos (my tiers, newTier.transfer(), position); praat_dataChanged (me); } END static void cb_TextGridEditor_publication (Editor editor, void *closure, Data publication) { (void) editor; (void) closure; /* * Keep the gate for error handling. */ try { praat_new (publication, NULL); praat_updateSelection (); if (Thing_member (publication, classSpectrum) && wcsequ (Thing_getName (publication), L"slice")) { int IOBJECT; LOOP { iam (Spectrum); autoSpectrumEditor editor2 = SpectrumEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me); praat_installEditor (editor2.transfer(), IOBJECT); therror } } } catch (MelderError) { Melder_flushError (NULL); } } DIRECT (TextGrid_edit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot view or edit a TextGrid from batch."); Sound sound = NULL; LOOP { if (CLASS == classSound) sound = (Sound) OBJECT; // may stay NULL } LOOP if (CLASS == classTextGrid) { iam (TextGrid); autoTextGridEditor editor = TextGridEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me, sound, true, NULL); editor -> setPublicationCallback (cb_TextGridEditor_publication, NULL); praat_installEditor (editor.transfer(), IOBJECT); therror } END DIRECT (TextGrid_LongSound_edit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot view or edit a TextGrid from batch."); LongSound longSound = NULL; int ilongSound = 0; LOOP { if (CLASS == classLongSound) longSound = (LongSound) OBJECT, ilongSound = IOBJECT; } Melder_assert (ilongSound != 0); LOOP if (CLASS == classTextGrid) { iam (TextGrid); autoTextGridEditor editor = TextGridEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me, longSound, false, NULL); editor -> setPublicationCallback (cb_TextGridEditor_publication, NULL); praat_installEditor2 (editor.transfer(), IOBJECT, ilongSound); therror } END DIRECT (TextGrid_SpellingChecker_edit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot view or edit a TextGrid from batch."); SpellingChecker spellingChecker = NULL; int ispellingChecker = 0; Sound sound = NULL; LOOP { if (CLASS == classSpellingChecker) spellingChecker = (SpellingChecker) OBJECT, ispellingChecker = IOBJECT; if (CLASS == classSound) sound = (Sound) OBJECT; // may stay NULL } Melder_assert (ispellingChecker != 0); LOOP if (CLASS == classTextGrid) { iam (TextGrid); autoTextGridEditor editor = TextGridEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me, sound, true, spellingChecker); praat_installEditor2 (editor.transfer(), IOBJECT, ispellingChecker); } END DIRECT (TextGrid_LongSound_SpellingChecker_edit) if (theCurrentPraatApplication -> batch) Melder_throw ("Cannot view or edit a TextGrid from batch."); LongSound longSound = NULL; SpellingChecker spellingChecker = NULL; int ilongSound = 0, ispellingChecker = 0; LOOP { if (CLASS == classLongSound) longSound = (LongSound) OBJECT, ilongSound = IOBJECT; if (CLASS == classSpellingChecker) spellingChecker = (SpellingChecker) OBJECT, ispellingChecker = IOBJECT; } Melder_assert (ilongSound != 0 && ispellingChecker != 0); LOOP if (CLASS == classTextGrid) { iam (TextGrid); autoTextGridEditor editor = TextGridEditor_create (theCurrentPraatApplication -> topShell, ID_AND_FULL_NAME, me, longSound, false, spellingChecker); praat_installEditor3 (editor.transfer(), IOBJECT, ilongSound, ispellingChecker); } END FORM (TextGrid_extractPart, L"TextGrid: Extract part", 0) REAL (L"left Time range (s)", L"0.0") REAL (L"right Time range (s)", L"1.0") BOOLEAN (L"Preserve times", 0) OK DO LOOP { iam (TextGrid); autoTextGrid thee = TextGrid_extractPart (me, GET_REAL (L"left Time range"), GET_REAL (L"right Time range"), GET_INTEGER (L"Preserve times")); praat_new (thee.transfer(), my name, L"_part"); } END static Function pr_TextGrid_peekTier (Any dia) { int IOBJECT; LOOP { iam (TextGrid); long tierNumber = GET_INTEGER (STRING_TIER_NUMBER); if (tierNumber > my tiers -> size) Melder_throw ("Tier number (", tierNumber, ") should not be larger than number of tiers (", my tiers -> size, ")."); return (Function) my tiers -> item [tierNumber]; } return NULL; // should not occur } static IntervalTier pr_TextGrid_peekIntervalTier (Any dia) { Function tier = pr_TextGrid_peekTier (dia); if (tier -> classInfo != classIntervalTier) Melder_throw ("Tier should be interval tier."); return (IntervalTier) tier; } static TextTier pr_TextGrid_peekTextTier (Any dia) { Function tier = pr_TextGrid_peekTier (dia); if (! tier) return NULL; if (tier -> classInfo != classTextTier) Melder_throw ("Tier should be point tier (TextTier)."); return (TextTier) tier; } static TextInterval pr_TextGrid_peekInterval (Any dia) { int intervalNumber = GET_INTEGER (STRING_INTERVAL_NUMBER); IntervalTier intervalTier = pr_TextGrid_peekIntervalTier (dia); if (intervalNumber > intervalTier -> intervals -> size) Melder_throw ("Interval number too large."); return (TextInterval) intervalTier -> intervals -> item [intervalNumber]; } static TextPoint pr_TextGrid_peekPoint (Any dia) { long pointNumber = GET_INTEGER (STRING_POINT_NUMBER); TextTier textTier = pr_TextGrid_peekTextTier (dia); if (pointNumber > textTier -> points -> size) Melder_throw ("Point number too large."); return (TextPoint) textTier -> points -> item [pointNumber]; } FORM (TextGrid_extractOneTier, L"TextGrid: Extract one tier", 0) NATURAL (STRING_TIER_NUMBER, L"1") OK DO Function tier = pr_TextGrid_peekTier (dia); // a reference autoTextGrid grid = TextGrid_createWithoutTiers (1e30, -1e30); TextGrid_addTier (grid.peek(), tier); therror // no transfer of tier ownership, because a copy is made praat_new (grid.transfer(), tier -> name); END FORM (TextGrid_extractTier, L"TextGrid: Extract tier", 0) NATURAL (STRING_TIER_NUMBER, L"1") OK DO Function tier = pr_TextGrid_peekTier (dia); autoFunction thee = Data_copy (tier); praat_new (thee.transfer(), tier -> name); END DIRECT (TextGrid_genericize) LOOP { iam (TextGrid); TextGrid_genericize (me); therror praat_dataChanged (me); } END DIRECT (TextGrid_nativize) LOOP { iam (TextGrid); TextGrid_nativize (me); therror praat_dataChanged (me); } END FORM (TextGrid_getHighIndexFromTime, L"Get high index", L"AnyTier: Get high index from time...") NATURAL (STRING_TIER_NUMBER, L"1") REAL (L"Time (s)", L"0.5") OK DO TextTier textTier = pr_TextGrid_peekTextTier (dia); long highIndex = AnyTier_timeToHighIndex (textTier, GET_REAL (L"Time")); Melder_information (Melder_integer (highIndex)); END FORM (TextGrid_getLowIndexFromTime, L"Get low index", L"AnyTier: Get low index from time...") NATURAL (STRING_TIER_NUMBER, L"1") REAL (L"Time (s)", L"0.5") OK DO TextTier textTier = pr_TextGrid_peekTextTier (dia); long lowIndex = AnyTier_timeToLowIndex (textTier, GET_REAL (L"Time")); Melder_information (Melder_integer (lowIndex)); END FORM (TextGrid_getNearestIndexFromTime, L"Get nearest index", L"AnyTier: Get nearest index from time...") NATURAL (STRING_TIER_NUMBER, L"1") REAL (L"Time (s)", L"0.5") OK DO TextTier textTier = pr_TextGrid_peekTextTier (dia); long nearestIndex = AnyTier_timeToNearestIndex (textTier, GET_REAL (L"Time")); Melder_information (Melder_integer (nearestIndex)); END FORM (TextGrid_getIntervalAtTime, L"TextGrid: Get interval at time", 0) NATURAL (STRING_TIER_NUMBER, L"1") REAL (L"Time (s)", L"0.5") OK DO IntervalTier intervalTier = pr_TextGrid_peekIntervalTier (dia); long index = IntervalTier_timeToIndex (intervalTier, GET_REAL (L"Time")); Melder_information (Melder_integer (index)); END FORM (TextGrid_getNumberOfIntervals, L"TextGrid: Get number of intervals", 0) NATURAL (STRING_TIER_NUMBER, L"1") OK DO IntervalTier intervalTier = pr_TextGrid_peekIntervalTier (dia); long numberOfIntervals = intervalTier -> intervals -> size; Melder_information (Melder_integer (numberOfIntervals)); END DIRECT (TextGrid_getNumberOfTiers) LOOP { iam (TextGrid); long numberOfTiers = my tiers -> size; Melder_information (Melder_integer (numberOfTiers)); } END FORM (TextGrid_getStartingPoint, L"TextGrid: Get start point", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_INTERVAL_NUMBER, L"1") OK DO TextInterval interval = pr_TextGrid_peekInterval (dia); double startingPoint = interval -> xmin; Melder_informationReal (startingPoint, L"seconds"); END FORM (TextGrid_getEndPoint, L"TextGrid: Get end point", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_INTERVAL_NUMBER, L"1") OK DO TextInterval interval = pr_TextGrid_peekInterval (dia); double endPoint = interval -> xmax; Melder_informationReal (endPoint, L"seconds"); END FORM (TextGrid_getLabelOfInterval, L"TextGrid: Get label of interval", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_INTERVAL_NUMBER, L"1") OK DO TextInterval interval = pr_TextGrid_peekInterval (dia); MelderInfo_open (); MelderInfo_write1 (interval -> text); MelderInfo_close (); END FORM (TextGrid_getNumberOfPoints, L"TextGrid: Get number of points", 0) NATURAL (STRING_TIER_NUMBER, L"1") OK DO TextTier textTier = pr_TextGrid_peekTextTier (dia); long numberOfPoints = textTier -> points -> size; Melder_information (Melder_integer (numberOfPoints)); END FORM (TextGrid_getTierName, L"TextGrid: Get tier name", 0) NATURAL (STRING_TIER_NUMBER, L"1") OK DO Data tier = pr_TextGrid_peekTier (dia); Melder_information (tier -> name); END FORM (TextGrid_getTimeOfPoint, L"TextGrid: Get time of point", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_POINT_NUMBER, L"1") OK DO TextPoint point = pr_TextGrid_peekPoint (dia); Melder_informationReal (point -> number, L"seconds"); END FORM (TextGrid_getLabelOfPoint, L"TextGrid: Get label of point", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_POINT_NUMBER, L"1") OK DO TextPoint point = pr_TextGrid_peekPoint (dia); Melder_information (point -> mark); END DIRECT (TextGrid_help) Melder_help (L"TextGrid"); END FORM (TextGrid_insertBoundary, L"TextGrid: Insert boundary", 0) NATURAL (STRING_TIER_NUMBER, L"1") REAL (L"Time (s)", L"0.5") OK DO LOOP { iam (TextGrid); TextGrid_insertBoundary (me, GET_INTEGER (STRING_TIER_NUMBER), GET_REAL (L"Time")); therror praat_dataChanged (me); } END FORM (TextGrid_insertIntervalTier, L"TextGrid: Insert interval tier", 0) NATURAL (L"Position", L"1 (= at top)") WORD (L"Name", L"") OK DO LOOP { iam (TextGrid); int position = GET_INTEGER (L"Position"); wchar *name = GET_STRING (L"Name"); autoIntervalTier tier = IntervalTier_create (my xmin, my xmax); if (position > my tiers -> size) position = my tiers -> size + 1; Thing_setName (tier.peek(), name); therror Ordered_addItemPos (my tiers, tier.transfer(), position); therror praat_dataChanged (me); } END FORM (TextGrid_insertPoint, L"TextGrid: Insert point", 0) NATURAL (STRING_TIER_NUMBER, L"1") REAL (L"Time (s)", L"0.5") LABEL (L"", L"Text:") TEXTFIELD (L"text", L"") OK DO LOOP { iam (TextGrid); TextGrid_insertPoint (me, GET_INTEGER (STRING_TIER_NUMBER), GET_REAL (L"Time"), GET_STRING (L"text")); therror praat_dataChanged (me); } END FORM (TextGrid_insertPointTier, L"TextGrid: Insert point tier", 0) NATURAL (L"Position", L"1 (= at top)") WORD (L"Name", L"") OK DO LOOP { iam (TextGrid); int position = GET_INTEGER (L"Position"); wchar *name = GET_STRING (L"Name"); autoTextTier tier = TextTier_create (my xmin, my xmax); if (position > my tiers -> size) position = my tiers -> size + 1; Thing_setName (tier.peek(), name); therror Ordered_addItemPos (my tiers, tier.transfer(), position); therror praat_dataChanged (me); } END FORM (TextGrid_isIntervalTier, L"TextGrid: Is interval tier?", 0) NATURAL (STRING_TIER_NUMBER, L"1") OK DO Data tier = pr_TextGrid_peekTier (dia); if (tier -> classInfo == classIntervalTier) { Melder_information (L"1 (yes, tier ", Melder_integer (GET_INTEGER (STRING_TIER_NUMBER)), L" is an interval tier)"); } else { Melder_information (L"0 (no, tier ", Melder_integer (GET_INTEGER (STRING_TIER_NUMBER)), L" is a point tier)"); } END FORM (TextGrid_list, L"TextGrid: List", 0) BOOLEAN (L"Include line number", false) NATURAL (L"Time decimals", L"6") BOOLEAN (L"Include tier names", true) BOOLEAN (L"Include empty intervals", false) OK DO LOOP { iam (TextGrid); TextGrid_list (me, GET_INTEGER (L"Include line number"), GET_INTEGER (L"Time decimals"), GET_INTEGER (L"Include tier names"), GET_INTEGER (L"Include empty intervals")); } END DIRECT (TextGrids_concatenate) autoCollection textGrids = praat_getSelectedObjects (); autoTextGrid thee = TextGrids_concatenate (textGrids.peek()); praat_new (thee.transfer(), L"chain"); END DIRECT (TextGrids_merge) autoCollection textGrids = praat_getSelectedObjects (); autoTextGrid thee = TextGrid_merge (textGrids.peek()); praat_new (thee.transfer(), L"merged"); END DIRECT (info_TextGrid_Pitch_draw) Melder_information (L"You can draw a TextGrid together with a Pitch after selecting them both."); END FORM (TextGrid_removeBoundaryAtTime, L"TextGrid: Remove boundary at time", 0) NATURAL (STRING_TIER_NUMBER, L"1") REAL (L"Time (s)", L"0.5") OK DO LOOP { iam (TextGrid); TextGrid_removeBoundaryAtTime (me, GET_INTEGER (STRING_TIER_NUMBER), GET_REAL (L"Time")); therror praat_dataChanged (me); } END FORM (TextGrid_getCentrePoints, L"TextGrid: Get centre points", 0) NATURAL (STRING_TIER_NUMBER, L"1") OPTIONMENU_ENUM (L"Get centre points where label", kMelder_string, DEFAULT) SENTENCE (L"...the text", L"hi") OK DO wchar *text = GET_STRING (L"...the text"); LOOP { iam (TextGrid); autoPointProcess thee = TextGrid_getCentrePoints (me, GET_INTEGER (STRING_TIER_NUMBER), GET_ENUM (kMelder_string, L"Get centre points where label"), text); praat_new (thee.transfer(), my name, L"_", text); } END FORM (TextGrid_getEndPoints, L"TextGrid: Get end points", 0) NATURAL (STRING_TIER_NUMBER, L"1") OPTIONMENU_ENUM (L"Get end points where label", kMelder_string, DEFAULT) SENTENCE (L"...the text", L"hi") OK DO wchar *text = GET_STRING (L"...the text"); LOOP { iam (TextGrid); autoPointProcess thee = TextGrid_getEndPoints (me, GET_INTEGER (STRING_TIER_NUMBER), GET_ENUM (kMelder_string, L"Get end points where label"), text); praat_new (thee.transfer(), my name, L"_", text); } END FORM (TextGrid_getStartingPoints, L"TextGrid: Get starting points", 0) NATURAL (STRING_TIER_NUMBER, L"1") OPTIONMENU_ENUM (L"Get starting points where label", kMelder_string, DEFAULT) SENTENCE (L"...the text", L"hi") OK DO wchar *text = GET_STRING (L"...the text"); LOOP { iam (TextGrid); autoPointProcess thee = TextGrid_getStartingPoints (me, GET_INTEGER (STRING_TIER_NUMBER), GET_ENUM (kMelder_string, L"Get starting points where label"), text); praat_new (thee.transfer(), my name, L"_", text); } END FORM (TextGrid_getPoints, L"Get points", 0) NATURAL (STRING_TIER_NUMBER, L"1") OPTIONMENU_ENUM (L"Get points where label", kMelder_string, DEFAULT) SENTENCE (L"...the text", L"hi") OK DO wchar *text = GET_STRING (L"...the text"); LOOP { iam (TextGrid); autoPointProcess thee = TextGrid_getPoints (me, GET_INTEGER (STRING_TIER_NUMBER), GET_ENUM (kMelder_string, L"Get points where label"), text); praat_new (thee.transfer(), my name, L"_", text); } END FORM (TextGrid_removeLeftBoundary, L"TextGrid: Remove left boundary", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_INTERVAL_NUMBER, L"2") OK DO long itier = GET_INTEGER (STRING_TIER_NUMBER); long iinterval = GET_INTEGER (STRING_INTERVAL_NUMBER); LOOP { iam (TextGrid); IntervalTier intervalTier; if (itier > my tiers -> size) Melder_throw ("You cannot remove a boundary from tier ", itier, " of ", me, ", because that TextGrid has only ", my tiers -> size, " tiers."); intervalTier = (IntervalTier) my tiers -> item [itier]; if (intervalTier -> classInfo != classIntervalTier) Melder_throw ("You cannot remove a boundary from tier ", itier, " of ", me, ", because that tier is a point tier instead of an interval tier."); if (iinterval > intervalTier -> intervals -> size) Melder_throw ("You cannot remove a boundary from interval ", iinterval, " of tier ", itier, " of ", me, ", because that tier has only ", intervalTier -> intervals -> size, " intervals."); if (iinterval == 1) Melder_throw ("You cannot remove the left boundary from interval 1 of tier ", itier, " of ", me, ", because this is at the left edge of the tier."); IntervalTier_removeLeftBoundary (intervalTier, iinterval); therror praat_dataChanged (me); } END FORM (TextGrid_removePoint, L"TextGrid: Remove point", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_POINT_NUMBER, L"2") OK DO long itier = GET_INTEGER (STRING_TIER_NUMBER); long ipoint = GET_INTEGER (STRING_POINT_NUMBER); LOOP { iam (TextGrid); TextTier pointTier; if (itier > my tiers -> size) Melder_throw ("You cannot remove a point from tier ", itier, " of ", me, ", because that TextGrid has only ", my tiers -> size, " tiers."); pointTier = (TextTier) my tiers -> item [itier]; if (pointTier -> classInfo != classTextTier) Melder_throw ("You cannot remove a point from tier ", itier, " of ", me, ", because that tier is an interval tier instead of a point tier."); if (ipoint > pointTier -> points -> size) Melder_throw ("You cannot remove point ", ipoint, " from tier ", itier, " of ", me, ", because that tier has only ", pointTier -> points -> size, " points."); TextTier_removePoint (pointTier, ipoint); therror praat_dataChanged (me); } END FORM (TextGrid_removeRightBoundary, L"TextGrid: Remove right boundary", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_INTERVAL_NUMBER, L"1") OK DO long itier = GET_INTEGER (STRING_TIER_NUMBER); long iinterval = GET_INTEGER (STRING_INTERVAL_NUMBER); LOOP { iam (TextGrid); IntervalTier intervalTier; if (itier > my tiers -> size) Melder_throw ("You cannot remove a boundary from tier ", itier, " of ", me, ", because that TextGrid has only ", my tiers -> size, " tiers."); intervalTier = (IntervalTier) my tiers -> item [itier]; if (intervalTier -> classInfo != classIntervalTier) Melder_throw ("You cannot remove a boundary from tier ", itier, " of ", me, L", because that tier is a point tier instead of an interval tier."); if (iinterval > intervalTier -> intervals -> size) Melder_throw ("You cannot remove a boundary from interval ", iinterval, " of tier ", itier, " of ", me, ", because that tier has only ", intervalTier -> intervals -> size, " intervals."); if (iinterval == intervalTier -> intervals -> size) Melder_throw ("You cannot remove the right boundary from interval ", iinterval, " of tier ", itier, " of ", me, ", because this is at the right edge of the tier."); IntervalTier_removeLeftBoundary (intervalTier, iinterval + 1); therror praat_dataChanged (me); } END FORM (TextGrid_removeTier, L"TextGrid: Remove tier", 0) NATURAL (STRING_TIER_NUMBER, L"1") OK DO LOOP { iam (TextGrid); int itier = GET_INTEGER (STRING_TIER_NUMBER); if (my tiers -> size <= 1) Melder_throw (L"Sorry, I refuse to remove the last tier."); if (itier > my tiers -> size) itier = my tiers -> size; Collection_removeItem (my tiers, itier); praat_dataChanged (me); } END DIRECT (info_TextGrid_Sound_edit) Melder_information (L"To include a copy of a Sound in your TextGrid editor:\n" " select a TextGrid and a Sound, and click \"View & Edit\"."); END DIRECT (info_TextGrid_Sound_draw) Melder_information (L"You can draw a TextGrid together with a Sound after selecting them both."); END FORM (TextGrid_setIntervalText, L"TextGrid: Set interval text", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_INTERVAL_NUMBER, L"1") LABEL (L"", L"Text:") TEXTFIELD (L"text", L"") OK DO LOOP { iam (TextGrid); TextGrid_setIntervalText (me, GET_INTEGER (STRING_TIER_NUMBER), GET_INTEGER (STRING_INTERVAL_NUMBER), GET_STRING (L"text")); therror praat_dataChanged (me); } END FORM (TextGrid_setPointText, L"TextGrid: Set point text", 0) NATURAL (STRING_TIER_NUMBER, L"1") NATURAL (STRING_POINT_NUMBER, L"1") LABEL (L"", L"Text:") TEXTFIELD (L"text", L"") OK DO LOOP { iam (TextGrid); TextGrid_setPointText (me, GET_INTEGER (STRING_TIER_NUMBER), GET_INTEGER (STRING_POINT_NUMBER), GET_STRING (L"text")); praat_dataChanged (me); } END FORM_WRITE (TextGrid_writeToChronologicalTextFile, L"Text file", 0, 0) LOOP { iam (TextGrid); TextGrid_writeToChronologicalTextFile (me, file); therror } END /***** TEXTGRID & ANYTIER *****/ DIRECT (TextGrid_AnyTier_append) TextGrid oldGrid = NULL; LOOP { if (CLASS == classTextGrid) oldGrid = (TextGrid) OBJECT; } autoTextGrid newGrid = Data_copy (oldGrid); LOOP if (OBJECT != oldGrid) { iam (AnyTier); TextGrid_addTier (newGrid.peek(), me); therror } praat_new (newGrid.transfer(), oldGrid -> name); END /***** TEXTGRID & LONGSOUND *****/ DIRECT (TextGrid_LongSound_scaleTimes) TextGrid grid = NULL; LongSound longSound = NULL; LOOP { if (CLASS == classTextGrid) grid = (TextGrid) OBJECT; if (CLASS == classLongSound) longSound = (LongSound) OBJECT; } Function_scaleXTo (grid, longSound -> xmin, longSound -> xmax); praat_dataChanged (grid); END /***** TEXTTIER *****/ FORM (TextTier_addPoint, L"TextTier: Add point", L"TextTier: Add point...") REAL (L"Time (s)", L"0.5") SENTENCE (L"Text", L"") OK DO LOOP { iam (TextTier); TextTier_addPoint (me, GET_REAL (L"Time"), GET_STRING (L"Text")); therror praat_dataChanged (me); } END DIRECT (TextTier_downto_PointProcess) LOOP { iam (TextTier); autoPointProcess thee = AnyTier_downto_PointProcess (me); praat_new (thee.transfer(), my name); } END FORM (TextTier_downto_TableOfReal, L"TextTier: Down to TableOfReal", 0) SENTENCE (L"Label", L"") OK DO LOOP { iam (TextTier); autoTableOfReal thee = TextTier_downto_TableOfReal (me, GET_STRING (L"Label")); praat_new (thee.transfer(), my name); } END DIRECT (TextTier_downto_TableOfReal_any) LOOP { iam (TextTier); autoTableOfReal thee = TextTier_downto_TableOfReal_any (me); praat_new (thee.transfer(), my name); } END FORM (TextTier_getLabelOfPoint, L"Get label of point", 0) NATURAL (L"Point number", L"1") OK DO LOOP { iam (TextTier); long ipoint = GET_INTEGER (L"Point number"); if (ipoint > my points -> size) Melder_throw ("No such point."); TextPoint point = (TextPoint) my points -> item [ipoint]; Melder_information (point -> mark); } END FORM (TextTier_getPoints, L"Get points", 0) SENTENCE (L"Text", L"") OK DO LOOP { iam (TextTier); autoPointProcess thee = TextTier_getPoints (me, GET_STRING (L"Text")); praat_new (thee.transfer(), GET_STRING (L"Text")); } END DIRECT (TextTier_help) Melder_help (L"TextTier"); END /***** WORDLIST *****/ FORM (WordList_hasWord, L"Does word occur in list?", L"WordList") SENTENCE (L"Word", L"") OK DO LOOP { iam (WordList); bool hasWord = WordList_hasWord (me, GET_STRING (L"Word")); Melder_information (hasWord ? L"1" : L"0"); } END DIRECT (WordList_to_Strings) LOOP { iam (WordList); autoStrings thee = WordList_to_Strings (me); praat_new (thee.transfer(), my name); } END DIRECT (WordList_upto_SpellingChecker) LOOP { iam (WordList); autoSpellingChecker thee = WordList_upto_SpellingChecker (me); praat_new (thee.transfer(), my name); } END /***** buttons *****/ void praat_TimeFunction_query_init (ClassInfo klas); void praat_TimeTier_query_init (ClassInfo klas); void praat_TimeTier_modify_init (ClassInfo klas); void praat_uvafon_TextGrid_init (void); void praat_uvafon_TextGrid_init (void) { Thing_recognizeClassByOtherName (classTextTier, L"MarkTier"); TextGridEditor_prefs (); praat_addAction1 (classIntervalTier, 0, L"IntervalTier help", 0, 0, DO_IntervalTier_help); praat_addAction1 (classIntervalTier, 1, L"Save as Xwaves label file...", 0, 0, DO_IntervalTier_writeToXwaves); praat_addAction1 (classIntervalTier, 1, L"Write to Xwaves label file...", 0, praat_HIDDEN, DO_IntervalTier_writeToXwaves); praat_addAction1 (classIntervalTier, 0, L"Collect", 0, 0, 0); praat_addAction1 (classIntervalTier, 0, L"Into TextGrid", 0, 0, DO_AnyTier_into_TextGrid); praat_addAction1 (classIntervalTier, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classIntervalTier, 0, L"Get starting points...", 0, 0, DO_IntervalTier_getStartingPoints); praat_addAction1 (classIntervalTier, 0, L"Get centre points...", 0, 0, DO_IntervalTier_getCentrePoints); praat_addAction1 (classIntervalTier, 0, L"Get end points...", 0, 0, DO_IntervalTier_getEndPoints); praat_addAction1 (classIntervalTier, 0, L"Convert", 0, 0, 0); praat_addAction1 (classIntervalTier, 0, L"Down to TableOfReal (any)", 0, 0, DO_IntervalTier_downto_TableOfReal_any); praat_addAction1 (classIntervalTier, 0, L"Down to TableOfReal...", 0, 0, DO_IntervalTier_downto_TableOfReal); praat_addAction1 (classLabel, 0, L"& Sound: To TextGrid?", 0, 0, DO_info_Label_Sound_to_TextGrid); praat_addAction1 (classSpellingChecker, 1, L"View & Edit...", 0, praat_ATTRACTIVE, DO_SpellingChecker_edit); praat_addAction1 (classSpellingChecker, 1, L"Edit...", 0, praat_HIDDEN, DO_SpellingChecker_edit); praat_addAction1 (classSpellingChecker, 0, L"Query", 0, 0, 0); praat_addAction1 (classSpellingChecker, 1, L"Is word allowed...", 0, 0, DO_SpellingChecker_isWordAllowed); praat_addAction1 (classSpellingChecker, 1, L"Next not allowed word...", 0, 0, DO_SpellingChecker_nextNotAllowedWord); praat_addAction1 (classSpellingChecker, 0, L"Modify", 0, 0, 0); praat_addAction1 (classSpellingChecker, 0, L"Add new word...", 0, 0, DO_SpellingChecker_addNewWord); praat_addAction1 (classSpellingChecker, 0, L"Analyze", 0, 0, 0); praat_addAction1 (classSpellingChecker, 0, L"Extract WordList", 0, 0, DO_SpellingChecker_extractWordList); praat_addAction1 (classSpellingChecker, 0, L"Extract user dictionary", 0, 0, DO_SpellingChecker_extractUserDictionary); praat_addAction1 (classTextGrid, 0, L"TextGrid help", 0, 0, DO_TextGrid_help); praat_addAction1 (classTextGrid, 1, L"Save as chronological text file...", 0, 0, DO_TextGrid_writeToChronologicalTextFile); praat_addAction1 (classTextGrid, 1, L"Write to chronological text file...", 0, praat_HIDDEN, DO_TextGrid_writeToChronologicalTextFile); praat_addAction1 (classTextGrid, 1, L"View & Edit alone", 0, 0, DO_TextGrid_edit); praat_addAction1 (classTextGrid, 1, L"View & Edit", 0, praat_HIDDEN, DO_TextGrid_edit); praat_addAction1 (classTextGrid, 1, L"Edit", 0, praat_HIDDEN, DO_TextGrid_edit); praat_addAction1 (classTextGrid, 1, L"View & Edit with Sound?", 0, praat_ATTRACTIVE, DO_info_TextGrid_Sound_edit); praat_addAction1 (classTextGrid, 0, L"Draw -", 0, 0, 0); praat_addAction1 (classTextGrid, 0, L"Draw...", 0, 1, DO_TextGrid_draw); praat_addAction1 (classTextGrid, 1, L"Draw with Sound?", 0, 1, DO_info_TextGrid_Sound_draw); praat_addAction1 (classTextGrid, 1, L"Draw with Pitch?", 0, 1, DO_info_TextGrid_Pitch_draw); praat_addAction1 (classTextGrid, 1, L"List...", 0, 0, DO_TextGrid_list); praat_addAction1 (classTextGrid, 0, L"Down to Table...", 0, 0, DO_TextGrid_downto_Table); praat_addAction1 (classTextGrid, 0, L"Query -", 0, 0, 0); praat_TimeFunction_query_init (classTextGrid); praat_addAction1 (classTextGrid, 1, L"-- query textgrid --", 0, 1, 0); praat_addAction1 (classTextGrid, 1, L"Get number of tiers", 0, 1, DO_TextGrid_getNumberOfTiers); praat_addAction1 (classTextGrid, 1, L"Get tier name...", 0, 1, DO_TextGrid_getTierName); praat_addAction1 (classTextGrid, 1, L"Is interval tier...", 0, 1, DO_TextGrid_isIntervalTier); praat_addAction1 (classTextGrid, 1, L"-- query tier --", 0, 1, 0); praat_addAction1 (classTextGrid, 1, L"Query interval tier", 0, 1, 0); praat_addAction1 (classTextGrid, 1, L"Get number of intervals...", 0, 2, DO_TextGrid_getNumberOfIntervals); praat_addAction1 (classTextGrid, 1, L"Get start point...", 0, 2, DO_TextGrid_getStartingPoint); praat_addAction1 (classTextGrid, 1, L"Get starting point...", 0, praat_HIDDEN + praat_DEPTH_2, DO_TextGrid_getStartingPoint); // hidden 2008 praat_addAction1 (classTextGrid, 1, L"Get end point...", 0, 2, DO_TextGrid_getEndPoint); praat_addAction1 (classTextGrid, 1, L"Get label of interval...", 0, 2, DO_TextGrid_getLabelOfInterval); praat_addAction1 (classTextGrid, 1, L"Get interval at time...", 0, 2, DO_TextGrid_getIntervalAtTime); praat_addAction1 (classTextGrid, 1, L"Query point tier", 0, 1, 0); praat_addAction1 (classTextGrid, 1, L"Get number of points...", 0, 2, DO_TextGrid_getNumberOfPoints); praat_addAction1 (classTextGrid, 1, L"Get time of point...", 0, 2, DO_TextGrid_getTimeOfPoint); praat_addAction1 (classTextGrid, 1, L"Get label of point...", 0, 2, DO_TextGrid_getLabelOfPoint); praat_addAction1 (classTextGrid, 1, L"Get low index from time...", 0, 2, DO_TextGrid_getLowIndexFromTime); praat_addAction1 (classTextGrid, 1, L"Get high index from time...", 0, 2, DO_TextGrid_getHighIndexFromTime); praat_addAction1 (classTextGrid, 1, L"Get nearest index from time...", 0, 2, DO_TextGrid_getNearestIndexFromTime); praat_addAction1 (classTextGrid, 1, L"-- query labels --", 0, 1, 0); praat_addAction1 (classTextGrid, 1, L"Count labels...", 0, 1, DO_TextGrid_countLabels); praat_addAction1 (classTextGrid, 0, L"Modify -", 0, 0, 0); praat_addAction1 (classTextGrid, 0, L"Convert to backslash trigraphs", 0, 1, DO_TextGrid_genericize); praat_addAction1 (classTextGrid, 0, L"Genericize", 0, praat_HIDDEN + praat_DEPTH_1, DO_TextGrid_genericize); // hidden 2007 praat_addAction1 (classTextGrid, 0, L"Convert to Unicode", 0, 1, DO_TextGrid_nativize); praat_addAction1 (classTextGrid, 0, L"Nativize", 0, praat_HIDDEN + praat_DEPTH_1, DO_TextGrid_nativize); // hidden 2007 praat_TimeFunction_modify_init (classTextGrid); praat_addAction1 (classTextGrid, 0, L"-- modify tiers --", 0, 1, 0); praat_addAction1 (classTextGrid, 0, L"Insert interval tier...", 0, 1, DO_TextGrid_insertIntervalTier); praat_addAction1 (classTextGrid, 0, L"Insert point tier...", 0, 1, DO_TextGrid_insertPointTier); praat_addAction1 (classTextGrid, 0, L"Duplicate tier...", 0, 1, DO_TextGrid_duplicateTier); praat_addAction1 (classTextGrid, 0, L"Remove tier...", 0, 1, DO_TextGrid_removeTier); praat_addAction1 (classTextGrid, 1, L"-- modify tier --", 0, 1, 0); praat_addAction1 (classTextGrid, 0, L"Modify interval tier", 0, 1, 0); praat_addAction1 (classTextGrid, 0, L"Insert boundary...", 0, 2, DO_TextGrid_insertBoundary); praat_addAction1 (classTextGrid, 0, L"Remove left boundary...", 0, 2, DO_TextGrid_removeLeftBoundary); praat_addAction1 (classTextGrid, 0, L"Remove right boundary...", 0, 2, DO_TextGrid_removeRightBoundary); praat_addAction1 (classTextGrid, 0, L"Remove boundary at time...", 0, 2, DO_TextGrid_removeBoundaryAtTime); praat_addAction1 (classTextGrid, 0, L"Set interval text...", 0, 2, DO_TextGrid_setIntervalText); praat_addAction1 (classTextGrid, 0, L"Modify point tier", 0, 1, 0); praat_addAction1 (classTextGrid, 0, L"Insert point...", 0, 2, DO_TextGrid_insertPoint); praat_addAction1 (classTextGrid, 0, L"Remove point...", 0, 2, DO_TextGrid_removePoint); praat_addAction1 (classTextGrid, 0, L"Set point text...", 0, 2, DO_TextGrid_setPointText); praat_addAction1 (classTextGrid, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classTextGrid, 1, L"Extract one tier...", 0, 0, DO_TextGrid_extractOneTier); praat_addAction1 (classTextGrid, 1, L"Extract tier...", 0, praat_HIDDEN, DO_TextGrid_extractTier); // hidden 2010 praat_addAction1 (classTextGrid, 1, L"Extract part...", 0, 0, DO_TextGrid_extractPart); praat_addAction1 (classTextGrid, 1, L"Analyse interval tier -", 0, 0, 0); praat_addAction1 (classTextGrid, 1, L"Get starting points...", 0, 1, DO_TextGrid_getStartingPoints); praat_addAction1 (classTextGrid, 1, L"Get end points...", 0, 1, DO_TextGrid_getEndPoints); praat_addAction1 (classTextGrid, 1, L"Get centre points...", 0, 1, DO_TextGrid_getCentrePoints); praat_addAction1 (classTextGrid, 1, L"Analyse point tier -", 0, 0, 0); praat_addAction1 (classTextGrid, 1, L"Get points...", 0, 1, DO_TextGrid_getPoints); praat_addAction1 (classTextGrid, 0, L"Synthesize", 0, 0, 0); praat_addAction1 (classTextGrid, 0, L"Merge", 0, 0, DO_TextGrids_merge); praat_addAction1 (classTextGrid, 0, L"Concatenate", 0, 0, DO_TextGrids_concatenate); praat_addAction1 (classTextTier, 0, L"TextTier help", 0, 0, DO_TextTier_help); praat_addAction1 (classTextTier, 0, L"Query -", 0, 0, 0); praat_TimeTier_query_init (classTextTier); praat_addAction1 (classTextTier, 0, L"Get label of point...", 0, 1, DO_TextTier_getLabelOfPoint); praat_addAction1 (classTextTier, 0, L"Modify -", 0, 0, 0); praat_TimeTier_modify_init (classTextTier); praat_addAction1 (classTextTier, 0, L"Add point...", 0, 1, DO_TextTier_addPoint); praat_addAction1 (classTextTier, 0, L"Analyse", 0, 0, 0); praat_addAction1 (classTextTier, 0, L"Get points...", 0, 0, DO_TextTier_getPoints); praat_addAction1 (classTextTier, 0, L"Collect", 0, 0, 0); praat_addAction1 (classTextTier, 0, L"Into TextGrid", 0, 0, DO_AnyTier_into_TextGrid); praat_addAction1 (classTextTier, 0, L"Convert", 0, 0, 0); praat_addAction1 (classTextTier, 0, L"Down to PointProcess", 0, 0, DO_TextTier_downto_PointProcess); praat_addAction1 (classTextTier, 0, L"Down to TableOfReal (any)", 0, 0, DO_TextTier_downto_TableOfReal_any); praat_addAction1 (classTextTier, 0, L"Down to TableOfReal...", 0, 0, DO_TextTier_downto_TableOfReal); praat_addAction1 (classWordList, 0, L"Query", 0, 0, 0); praat_addAction1 (classWordList, 1, L"Has word...", 0, 0, DO_WordList_hasWord); praat_addAction1 (classWordList, 0, L"Analyze", 0, 0, 0); praat_addAction1 (classWordList, 0, L"To Strings", 0, 0, DO_WordList_to_Strings); praat_addAction1 (classWordList, 0, L"Synthesize", 0, 0, 0); praat_addAction1 (classWordList, 0, L"Up to SpellingChecker", 0, 0, DO_WordList_upto_SpellingChecker); praat_addAction2 (classIntervalTier, 1, classPointProcess, 1, L"Start to centre...", 0, 0, DO_IntervalTier_PointProcess_startToCentre); praat_addAction2 (classIntervalTier, 1, classPointProcess, 1, L"End to centre...", 0, 0, DO_IntervalTier_PointProcess_endToCentre); praat_addAction2 (classIntervalTier, 0, classTextTier, 0, L"Collect", 0, 0, 0); praat_addAction2 (classIntervalTier, 0, classTextTier, 0, L"Into TextGrid", 0, 0, DO_AnyTier_into_TextGrid); praat_addAction2 (classLabel, 1, classSound, 1, L"To TextGrid", 0, 0, DO_Label_Sound_to_TextGrid); praat_addAction2 (classLongSound, 1, classTextGrid, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_TextGrid_LongSound_edit); praat_addAction2 (classLongSound, 1, classTextGrid, 1, L"Edit", 0, praat_HIDDEN, DO_TextGrid_LongSound_edit); // hidden 2011 praat_addAction2 (classLongSound, 1, classTextGrid, 1, L"Scale times", 0, 0, DO_TextGrid_LongSound_scaleTimes); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw -", 0, 0, 0); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw...", 0, 1, DO_TextGrid_Pitch_draw); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw logarithmic...", 0, 1, DO_TextGrid_Pitch_drawLogarithmic); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw semitones...", 0, 1, DO_TextGrid_Pitch_drawSemitones); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw mel...", 0, 1, DO_TextGrid_Pitch_drawMel); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw erb...", 0, 1, DO_TextGrid_Pitch_drawErb); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle...", 0, 1, DO_TextGrid_Pitch_speckle); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle logarithmic...", 0, 1, DO_TextGrid_Pitch_speckleLogarithmic); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle semitones...", 0, 1, DO_TextGrid_Pitch_speckleSemitones); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle mel...", 0, 1, DO_TextGrid_Pitch_speckleMel); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle erb...", 0, 1, DO_TextGrid_Pitch_speckleErb); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"-- draw separately --", 0, 1, 0); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw separately...", 0, 1, DO_TextGrid_Pitch_drawSeparately); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw separately (logarithmic)...", 0, 1, DO_TextGrid_Pitch_drawSeparatelyLogarithmic); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw separately (semitones)...", 0, 1, DO_TextGrid_Pitch_drawSeparatelySemitones); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw separately (mel)...", 0, 1, DO_TextGrid_Pitch_drawSeparatelyMel); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Draw separately (erb)...", 0, 1, DO_TextGrid_Pitch_drawSeparatelyErb); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle separately...", 0, 1, DO_TextGrid_Pitch_speckleSeparately); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle separately (logarithmic)...", 0, 1, DO_TextGrid_Pitch_speckleSeparatelyLogarithmic); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle separately (semitones)...", 0, 1, DO_TextGrid_Pitch_speckleSeparatelySemitones); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle separately (mel)...", 0, 1, DO_TextGrid_Pitch_speckleSeparatelyMel); praat_addAction2 (classPitch, 1, classTextGrid, 1, L"Speckle separately (erb)...", 0, 1, DO_TextGrid_Pitch_speckleSeparatelyErb); praat_addAction2 (classPitch, 1, classTextTier, 1, L"To PitchTier...", 0, 0, DO_Pitch_TextTier_to_PitchTier); praat_addAction2 (classSound, 1, classTextGrid, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_TextGrid_edit); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Edit", 0, praat_HIDDEN, DO_TextGrid_edit); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Draw...", 0, 0, DO_TextGrid_Sound_draw); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Extract -", 0, 0, 0); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Extract all intervals...", 0, praat_DEPTH_1, DO_TextGrid_Sound_extractAllIntervals); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Extract non-empty intervals...", 0, praat_DEPTH_1, DO_TextGrid_Sound_extractNonemptyIntervals); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Extract intervals...", 0, praat_DEPTH_1 + praat_HIDDEN, DO_TextGrid_Sound_extractIntervals); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Extract intervals where...", 0, praat_DEPTH_1, DO_TextGrid_Sound_extractIntervalsWhere); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Modify TextGrid", 0, 0, 0); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Scale times", 0, 0, DO_TextGrid_Sound_scaleTimes); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Modify Sound", 0, 0, 0); praat_addAction2 (classSound, 1, classTextGrid, 1, L"Clone time domain", 0, 0, DO_TextGrid_Sound_cloneTimeDomain); praat_addAction2 (classSpellingChecker, 1, classWordList, 1, L"Replace WordList", 0, 0, DO_SpellingChecker_replaceWordList); praat_addAction2 (classSpellingChecker, 1, classSortedSetOfString, 1, L"Replace user dictionary", 0, 0, DO_SpellingChecker_replaceUserDictionary); praat_addAction2 (classSpellingChecker, 1, classStrings, 1, L"Replace word list?", 0, 0, DO_SpellingChecker_replaceWordList_help); praat_addAction2 (classSpellingChecker, 1, classTextGrid, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_TextGrid_SpellingChecker_edit); praat_addAction2 (classSpellingChecker, 1, classTextGrid, 1, L"Edit", 0, praat_HIDDEN, DO_TextGrid_SpellingChecker_edit); // hidden 2011 praat_addAction2 (classTextGrid, 1, classTextTier, 1, L"Append", 0, 0, DO_TextGrid_AnyTier_append); praat_addAction2 (classTextGrid, 1, classIntervalTier, 1, L"Append", 0, 0, DO_TextGrid_AnyTier_append); praat_addAction3 (classLongSound, 1, classSpellingChecker, 1, classTextGrid, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_TextGrid_LongSound_SpellingChecker_edit); praat_addAction3 (classLongSound, 1, classSpellingChecker, 1, classTextGrid, 1, L"Edit", 0, praat_HIDDEN, DO_TextGrid_LongSound_SpellingChecker_edit); praat_addAction3 (classSound, 1, classSpellingChecker, 1, classTextGrid, 1, L"View & Edit", 0, praat_ATTRACTIVE, DO_TextGrid_SpellingChecker_edit); praat_addAction3 (classSound, 1, classSpellingChecker, 1, classTextGrid, 1, L"Edit", 0, praat_HIDDEN, DO_TextGrid_SpellingChecker_edit); } /* End of file praat_TextGrid_init.cpp */ sources_5316/fon/Vector.h0000644000176700017670000001000711621512713014115 0ustar paulpaul#ifndef _Vector_h_ #define _Vector_h_ /* Vector.h * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* Vector inherits from Matrix */ /* A Vector is a horizontal Matrix. */ /* The rows are 'channels'. There will often be only one channel, but e.g. a stereo sound has two. */ #include "Matrix.h" Thing_define (Vector, Matrix) { // overridden methods: protected: virtual bool v_hasGetVector () { return true; } virtual double v_getVector (long irow, long icol); virtual bool v_hasGetFunction1 () { return true; } virtual double v_getFunction1 (long irow, double x); virtual bool v_hasGetMatrix () { return false; } virtual bool v_hasGetFunction2 () { return false; } virtual double v_getValueAtSample (long isamp, long ilevel, int unit); }; #define Vector_CHANNEL_AVERAGE 0 #define Vector_CHANNEL_1 1 #define Vector_CHANNEL_2 2 #define Vector_VALUE_INTERPOLATION_NEAREST 0 #define Vector_VALUE_INTERPOLATION_LINEAR 1 #define Vector_VALUE_INTERPOLATION_CUBIC 2 #define Vector_VALUE_INTERPOLATION_SINC70 3 #define Vector_VALUE_INTERPOLATION_SINC700 4 double Vector_getValueAtX (Vector me, double x, long channel, int interpolation); void Vector_getMinimumAndX (Vector me, double xmin, double xmax, long channel, int interpolation, double *return_minimum, double *return_xOfMinimum); void Vector_getMinimumAndXAndChannel (Vector me, double xmin, double xmax, int interpolation, double *return_minimum, double *return_xOfMinimum, long *return_channelOfMinimum); void Vector_getMaximumAndX (Vector me, double xmin, double xmax, long channel, int interpolation, double *return_maximum, double *return_xOfMaximum); void Vector_getMaximumAndXAndChannel (Vector me, double xmin, double xmax, int interpolation, double *return_maximum, double *return_xOfMaximum, long *return_channelOfMaximum); double Vector_getMinimum (Vector me, double xmin, double xmax, int interpolation); double Vector_getMaximum (Vector me, double xmin, double xmax, int interpolation); double Vector_getAbsoluteExtremum (Vector me, double xmin, double xmax, int interpolation); double Vector_getXOfMinimum (Vector me, double xmin, double xmax, int interpolation); double Vector_getXOfMaximum (Vector me, double xmin, double xmax, int interpolation); long Vector_getChannelOfMinimum (Vector me, double xmin, double xmax, int interpolation); long Vector_getChannelOfMaximum (Vector me, double xmin, double xmax, int interpolation); double Vector_getMean (Vector me, double xmin, double xmax, long channel); double Vector_getStandardDeviation (Vector me, double xmin, double xmax, long channel); void Vector_addScalar (Vector me, double scalar); void Vector_subtractMean (Vector me); void Vector_multiplyByScalar (Vector me, double scalar); void Vector_scale (Vector me, double scale); void Vector_draw (Vector me, Graphics g, double *pxmin, double *pxmax, double *pymin, double *pymax, double defaultDy, const wchar *method); /* If *pxmin equals *pxmax, then autowindowing from my xmin to my xmax. If *pymin equals *pymax, then autoscaling from minimum to maximum; if minimum then equals maximum, defaultDy will be subtracted from *pymin and added to *pymax; it must be a positive real number (e.g. 0.5 Pa for Sound, 1.0 dB for Ltas). method can be "curve", "bars", "poles", or "speckles"; it must not be NULL; if anything else is specified, a curve is drawn. */ /* End of file Vector.h */ #endif sources_5316/fon/TimeSoundAnalysisEditor.cpp0000644000176700017670000032400711702060735020002 0ustar paulpaul/* TimeSoundAnalysisEditor.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include #include "TimeSoundAnalysisEditor.h" #include "Preferences.h" #include "EditorM.h" #include "Sound_and_Spectrogram.h" #include "Sound_and_Spectrum.h" #include "Sound_to_Pitch.h" #include "Sound_to_Intensity.h" #include "Sound_to_Formant.h" #include "Pitch_to_PointProcess.h" #include "VoiceAnalysis.h" #include "praat_script.h" #include "enums_getText.h" #include "TimeSoundAnalysisEditor_enums.h" #include "enums_getValue.h" #include "TimeSoundAnalysisEditor_enums.h" Thing_implement (TimeSoundAnalysisEditor, TimeSoundEditor, 0); static const wchar * theMessage_Cannot_compute_spectrogram = L"The spectrogram is not defined at the edge of the sound."; static const wchar * theMessage_Cannot_compute_pitch = L"The pitch contour is not defined at the edge of the sound."; static const wchar * theMessage_Cannot_compute_formant = L"The formants are not defined at the edge of the sound."; static const wchar * theMessage_Cannot_compute_intensity = L"The intensity curve is not defined at the edge of the sound."; static const wchar * theMessage_Cannot_compute_pulses = L"The pulses are not defined at the edge of the sound."; #if defined (macintosh) static const wchar * LOG_1_FILE_NAME = L"~/Desktop/Pitch Log"; static const wchar * LOG_2_FILE_NAME = L"~/Desktop/Formant Log"; static const wchar * LOG_3_FILE_NAME = L"~/Desktop/Log script 3"; static const wchar * LOG_4_FILE_NAME = L"~/Desktop/Log script 4"; #elif defined (WIN32) static const wchar * LOG_1_FILE_NAME = L"C:\\WINDOWS\\DESKTOP\\Pitch Log.txt"; static const wchar * LOG_2_FILE_NAME = L"C:\\WINDOWS\\DESKTOP\\Formant Log.txt"; static const wchar * LOG_3_FILE_NAME = L"C:\\WINDOWS\\DESKTOP\\Log script 3.praat"; static const wchar * LOG_4_FILE_NAME = L"C:\\WINDOWS\\DESKTOP\\Log script 4.praat"; #else static const wchar * LOG_1_FILE_NAME = L"~/pitch_log"; static const wchar * LOG_2_FILE_NAME = L"~/formant_log"; static const wchar * LOG_3_FILE_NAME = L"~/log_script3"; static const wchar * LOG_4_FILE_NAME = L"~/log_script4"; #endif static const wchar * LOG_1_FORMAT = L"Time 'time:6' seconds, pitch 'f0:2' Hz"; static const wchar * LOG_2_FORMAT = L"'t1:4''tab$''t2:4''tab$''f1:0''tab$''f2:0''tab$''f3:0'"; struct logInfo { bool toInfoWindow, toLogFile; wchar fileName [Preferences_STRING_BUFFER_SIZE], format [Preferences_STRING_BUFFER_SIZE]; }; static struct { double longestAnalysis; enum kTimeSoundAnalysisEditor_timeStepStrategy timeStepStrategy; double fixedTimeStep; long numberOfTimeStepsPerView; struct FunctionEditor_spectrogram spectrogram; struct FunctionEditor_pitch pitch; struct FunctionEditor_intensity intensity; struct FunctionEditor_formant formant; struct FunctionEditor_pulses pulses; struct logInfo log [2]; wchar logScript3 [Preferences_STRING_BUFFER_SIZE], logScript4 [Preferences_STRING_BUFFER_SIZE]; } preferences; void TimeSoundAnalysisEditor_prefs (void) { Preferences_addDouble (L"FunctionEditor.longestAnalysis", & preferences.longestAnalysis, 10.0); // seconds Preferences_addEnum (L"FunctionEditor.timeStepStrategy", & preferences.timeStepStrategy, kTimeSoundAnalysisEditor_timeStepStrategy, DEFAULT); Preferences_addDouble (L"FunctionEditor.fixedTimeStep", & preferences.fixedTimeStep, 0.01); // seconds Preferences_addLong (L"FunctionEditor.numberOfTimeStepsPerView", & preferences.numberOfTimeStepsPerView, 100); Preferences_addBool (L"FunctionEditor.spectrogram.show", & preferences.spectrogram.show, true); Preferences_addDouble (L"FunctionEditor.spectrogram.viewFrom2", & preferences.spectrogram.viewFrom, 0.0); // Hz Preferences_addDouble (L"FunctionEditor.spectrogram.viewTo2", & preferences.spectrogram.viewTo, 5000.0); // Hz Preferences_addDouble (L"FunctionEditor.spectrogram.windowLength2", & preferences.spectrogram.windowLength, 0.005); // Hz Preferences_addDouble (L"FunctionEditor.spectrogram.dynamicRange2", & preferences.spectrogram.dynamicRange, 70.0); // dB Preferences_addLong (L"FunctionEditor.spectrogram.timeSteps2", & preferences.spectrogram.timeSteps, 1000); Preferences_addLong (L"FunctionEditor.spectrogram.frequencySteps2", & preferences.spectrogram.frequencySteps, 250); Preferences_addEnum (L"FunctionEditor.spectrogram.method2", & preferences.spectrogram.method, kSound_to_Spectrogram_method, DEFAULT); Preferences_addEnum (L"FunctionEditor.spectrogram.windowShape2", & preferences.spectrogram.windowShape, kSound_to_Spectrogram_windowShape, DEFAULT); Preferences_addBool (L"FunctionEditor.spectrogram.autoscaling2", & preferences.spectrogram.autoscaling, true); Preferences_addDouble (L"FunctionEditor.spectrogram.maximum2", & preferences.spectrogram.maximum, 100.0); // dB/Hz Preferences_addDouble (L"FunctionEditor.spectrogram.preemphasis2", & preferences.spectrogram.preemphasis, 6.0); // dB/octave Preferences_addDouble (L"FunctionEditor.spectrogram.dynamicCompression2", & preferences.spectrogram.dynamicCompression, 0.0); Preferences_addBool (L"FunctionEditor.spectrogram.picture.garnish", & preferences.spectrogram.picture.garnish, true); Preferences_addBool (L"FunctionEditor.pitch.show", & preferences.pitch.show, true); Preferences_addDouble (L"FunctionEditor.pitch.floor", & preferences.pitch.floor, 75.0); Preferences_addDouble (L"FunctionEditor.pitch.ceiling", & preferences.pitch.ceiling, 500.0); Preferences_addEnum (L"FunctionEditor.pitch.unit", & preferences.pitch.unit, kPitch_unit, DEFAULT); Preferences_addEnum (L"FunctionEditor.pitch.drawingMethod", & preferences.pitch.drawingMethod, kTimeSoundAnalysisEditor_pitch_drawingMethod, DEFAULT); Preferences_addDouble (L"FunctionEditor.pitch.viewFrom", & preferences.pitch.viewFrom, 0.0); // auto Preferences_addDouble (L"FunctionEditor.pitch.viewTo", & preferences.pitch.viewTo, 0.0); // auto Preferences_addEnum (L"FunctionEditor.pitch.method", & preferences.pitch.method, kTimeSoundAnalysisEditor_pitch_analysisMethod, DEFAULT); Preferences_addBool (L"FunctionEditor.pitch.veryAccurate", & preferences.pitch.veryAccurate, false); Preferences_addLong (L"FunctionEditor.pitch.maximumNumberOfCandidates", & preferences.pitch.maximumNumberOfCandidates, 15); Preferences_addDouble (L"FunctionEditor.pitch.silenceThreshold", & preferences.pitch.silenceThreshold, 0.03); Preferences_addDouble (L"FunctionEditor.pitch.voicingThreshold", & preferences.pitch.voicingThreshold, 0.45); Preferences_addDouble (L"FunctionEditor.pitch.octaveCost", & preferences.pitch.octaveCost, 0.01); Preferences_addDouble (L"FunctionEditor.pitch.octaveJumpCost", & preferences.pitch.octaveJumpCost, 0.35); Preferences_addDouble (L"FunctionEditor.pitch.voicedUnvoicedCost", & preferences.pitch.voicedUnvoicedCost, 0.14); Preferences_addBool (L"FunctionEditor.pitch.picture.garnish", & preferences.pitch.picture.garnish, true); Preferences_addBool (L"FunctionEditor.intensity.show", & preferences.intensity.show, false); Preferences_addDouble (L"FunctionEditor.intensity.viewFrom", & preferences.intensity.viewFrom, 50.0); // dB Preferences_addDouble (L"FunctionEditor.intensity.viewTo", & preferences.intensity.viewTo, 100.0); // dB Preferences_addEnum (L"FunctionEditor.intensity.averagingMethod", & preferences.intensity.averagingMethod, kTimeSoundAnalysisEditor_intensity_averagingMethod, DEFAULT); Preferences_addBool (L"FunctionEditor.intensity.subtractMeanPressure", & preferences.intensity.subtractMeanPressure, true); Preferences_addBool (L"FunctionEditor.intensity.picture.garnish", & preferences.intensity.picture.garnish, true); Preferences_addBool (L"FunctionEditor.formant.show", & preferences.formant.show, false); Preferences_addDouble (L"FunctionEditor.formant.maximumFormant", & preferences.formant.maximumFormant, 5500.0); // Hz Preferences_addLong (L"FunctionEditor.formant.numberOfPoles", & preferences.formant.numberOfPoles, 10); Preferences_addDouble (L"FunctionEditor.formant.windowLength", & preferences.formant.windowLength, 0.025); // seconds Preferences_addDouble (L"FunctionEditor.formant.dynamicRange", & preferences.formant.dynamicRange, 30.0); // dB Preferences_addDouble (L"FunctionEditor.formant.dotSize", & preferences.formant.dotSize, 1.0); // mm Preferences_addEnum (L"FunctionEditor.formant.method", & preferences.formant.method, kTimeSoundAnalysisEditor_formant_analysisMethod, DEFAULT); Preferences_addDouble (L"FunctionEditor.formant.preemphasisFrom", & preferences.formant.preemphasisFrom, 50.0); // Hz Preferences_addBool (L"FunctionEditor.formant.picture.garnish", & preferences.formant.picture.garnish, true); Preferences_addBool (L"FunctionEditor.pulses.show", & preferences.pulses.show, false); Preferences_addDouble (L"FunctionEditor.pulses.maximumPeriodFactor", & preferences.pulses.maximumPeriodFactor, 1.3); Preferences_addDouble (L"FunctionEditor.pulses.maximumAmplitudeFactor", & preferences.pulses.maximumAmplitudeFactor, 1.6); Preferences_addBool (L"FunctionEditor.pulses.picture.garnish", & preferences.pulses.picture.garnish, true); Preferences_addBool (L"FunctionEditor.log1.toInfoWindow", & preferences.log[0].toInfoWindow, true); Preferences_addBool (L"FunctionEditor.log1.toLogFile", & preferences.log[0].toLogFile, true); Preferences_addString (L"FunctionEditor.log1.fileName", & preferences.log[0].fileName [0], LOG_1_FILE_NAME); Preferences_addString (L"FunctionEditor.log1.format", & preferences.log[0].format [0], LOG_1_FORMAT); Preferences_addBool (L"FunctionEditor.log2.toInfoWindow", & preferences.log[1].toInfoWindow, true); Preferences_addBool (L"FunctionEditor.log2.toLogFile", & preferences.log[1].toLogFile, true); Preferences_addString (L"FunctionEditor.log2.fileName", & preferences.log[1].fileName [0], LOG_2_FILE_NAME); Preferences_addString (L"FunctionEditor.log2.format", & preferences.log[1].format [0], LOG_2_FORMAT); Preferences_addString (L"FunctionEditor.logScript3", & preferences.logScript3 [0], LOG_3_FILE_NAME); Preferences_addString (L"FunctionEditor.logScript4", & preferences.logScript4 [0], LOG_4_FILE_NAME); } void structTimeSoundAnalysisEditor :: v_destroy () { v_destroy_analysis (); TimeSoundAnalysisEditor_Parent :: v_destroy (); } void structTimeSoundAnalysisEditor :: v_info () { TimeSoundAnalysisEditor_Parent :: v_info (); /* Spectrogram flag: */ MelderInfo_writeLine2 (L"Spectrogram show: ", Melder_boolean (spectrogram.show)); /* Spectrogram settings: */ MelderInfo_writeLine3 (L"Spectrogram view from: ", Melder_double (spectrogram.viewFrom), L" Hz"); MelderInfo_writeLine3 (L"Spectrogram view to: ", Melder_double (spectrogram.viewTo), L" Hz"); MelderInfo_writeLine3 (L"Spectrogram window length: ", Melder_double (spectrogram.windowLength), L" seconds"); MelderInfo_writeLine3 (L"Spectrogram dynamic range: ", Melder_double (spectrogram.dynamicRange), L" dB"); /* Advanced spectrogram settings: */ MelderInfo_writeLine2 (L"Spectrogram number of time steps: ", Melder_integer (spectrogram.timeSteps)); MelderInfo_writeLine2 (L"Spectrogram number of frequency steps: ", Melder_integer (spectrogram.frequencySteps)); MelderInfo_writeLine2 (L"Spectrogram method: ", L"Fourier"); MelderInfo_writeLine2 (L"Spectrogram window shape: ", kSound_to_Spectrogram_windowShape_getText (spectrogram.windowShape)); MelderInfo_writeLine2 (L"Spectrogram autoscaling: ", Melder_boolean (spectrogram.autoscaling)); MelderInfo_writeLine3 (L"Spectrogram maximum: ", Melder_double (spectrogram.maximum), L" dB/Hz"); MelderInfo_writeLine3 (L"Spectrogram pre-emphasis: ", Melder_integer (spectrogram.preemphasis), L" dB/octave"); MelderInfo_writeLine2 (L"Spectrogram dynamicCompression: ", Melder_integer (spectrogram.dynamicCompression)); /* Dynamic information: */ MelderInfo_writeLine3 (L"Spectrogram cursor frequency: ", Melder_double (spectrogram.cursor), L" Hz"); /* Pitch flag: */ MelderInfo_writeLine2 (L"Pitch show: ", Melder_boolean (pitch.show)); /* Pitch settings: */ MelderInfo_writeLine3 (L"Pitch floor: ", Melder_double (pitch.floor), L" Hz"); MelderInfo_writeLine3 (L"Pitch ceiling: ", Melder_double (pitch.ceiling), L" Hz"); MelderInfo_writeLine2 (L"Pitch unit: ", Function_getUnitText (Thing_dummyObject (Pitch), Pitch_LEVEL_FREQUENCY, pitch.unit, Function_UNIT_TEXT_MENU)); MelderInfo_writeLine2 (L"Pitch drawing method: ", kTimeSoundAnalysisEditor_pitch_drawingMethod_getText (pitch.drawingMethod)); /* Advanced pitch settings: */ MelderInfo_writeLine4 (L"Pitch view from: ", Melder_double (pitch.viewFrom), L" ", Function_getUnitText (Thing_dummyObject (Pitch), Pitch_LEVEL_FREQUENCY, pitch.unit, Function_UNIT_TEXT_MENU)); MelderInfo_writeLine4 (L"Pitch view to: ", Melder_double (pitch.viewTo), L" ", Function_getUnitText (Thing_dummyObject (Pitch), Pitch_LEVEL_FREQUENCY, pitch.unit, Function_UNIT_TEXT_MENU)); MelderInfo_writeLine2 (L"Pitch method: ", kTimeSoundAnalysisEditor_pitch_analysisMethod_getText (pitch.method)); MelderInfo_writeLine2 (L"Pitch very accurate: ", Melder_boolean (pitch.veryAccurate)); MelderInfo_writeLine2 (L"Pitch max. number of candidates: ", Melder_integer (pitch.maximumNumberOfCandidates)); MelderInfo_writeLine3 (L"Pitch silence threshold: ", Melder_double (pitch.silenceThreshold), L" of global peak"); MelderInfo_writeLine3 (L"Pitch voicing threshold: ", Melder_double (pitch.voicingThreshold), L" (periodic power / total power)"); MelderInfo_writeLine3 (L"Pitch octave cost: ", Melder_double (pitch.octaveCost), L" per octave"); MelderInfo_writeLine3 (L"Pitch octave jump cost: ", Melder_double (pitch.octaveJumpCost), L" per octave"); MelderInfo_writeLine2 (L"Pitch voiced/unvoiced cost: ", Melder_double (pitch.voicedUnvoicedCost)); /* Intensity flag: */ MelderInfo_writeLine2 (L"Intensity show: ", Melder_boolean (intensity.show)); /* Intensity settings: */ MelderInfo_writeLine3 (L"Intensity view from: ", Melder_double (intensity.viewFrom), L" dB"); MelderInfo_writeLine3 (L"Intensity view to: ", Melder_double (intensity.viewTo), L" dB"); MelderInfo_writeLine2 (L"Intensity averaging method: ", kTimeSoundAnalysisEditor_intensity_averagingMethod_getText (intensity.averagingMethod)); MelderInfo_writeLine2 (L"Intensity subtract mean pressure: ", Melder_boolean (intensity.subtractMeanPressure)); /* Formant flag: */ MelderInfo_writeLine2 (L"Formant show: ", Melder_boolean (formant.show)); /* Formant settings: */ MelderInfo_writeLine3 (L"Formant maximum formant: ", Melder_double (formant.maximumFormant), L" Hz"); MelderInfo_writeLine2 (L"Formant number of poles: ", Melder_integer (formant.numberOfPoles)); MelderInfo_writeLine3 (L"Formant window length: ", Melder_double (formant.windowLength), L" seconds"); MelderInfo_writeLine3 (L"Formant dynamic range: ", Melder_double (formant.dynamicRange), L" dB"); MelderInfo_writeLine3 (L"Formant dot size: ", Melder_double (formant.dotSize), L" mm"); /* Advanced formant settings: */ MelderInfo_writeLine2 (L"Formant method: ", kTimeSoundAnalysisEditor_formant_analysisMethod_getText (formant.method)); MelderInfo_writeLine3 (L"Formant pre-emphasis from: ", Melder_double (formant.preemphasisFrom), L" Hz"); /* Pulses flag: */ MelderInfo_writeLine2 (L"Pulses show: ", Melder_boolean (pulses.show)); MelderInfo_writeLine2 (L"Pulses maximum period factor: ", Melder_double (pulses.maximumPeriodFactor)); MelderInfo_writeLine2 (L"Pulses maximum amplitude factor: ", Melder_double (pulses.maximumAmplitudeFactor)); } void structTimeSoundAnalysisEditor :: v_destroy_analysis () { forget (spectrogram.data); forget (pitch.data); forget (intensity.data); forget (formant.data); forget (pulses.data); } enum { FunctionEditor_PART_CURSOR = 1, FunctionEditor_PART_SELECTION = 2 }; static const wchar *FunctionEditor_partString (int part) { static const wchar *strings [] = { L"", L"CURSOR", L"SELECTION" }; return strings [part]; } static const wchar *FunctionEditor_partString_locative (int part) { static const wchar *strings [] = { L"", L"at CURSOR", L"in SELECTION" }; return strings [part]; } static int makeQueriable (TimeSoundAnalysisEditor me, int allowCursor, double *tmin, double *tmax) { if (my endWindow - my startWindow > my longestAnalysis) { Melder_throw ("Window too long to show analyses. Zoom in to at most ", Melder_half (my longestAnalysis), " seconds " "or set the \"longest analysis\" to at least ", Melder_half (my endWindow - my startWindow), " seconds."); } if (my startSelection == my endSelection) { if (allowCursor) { *tmin = *tmax = my startSelection; return FunctionEditor_PART_CURSOR; } else { Melder_throw ("Make a selection first."); } } else if (my startSelection < my startWindow || my endSelection > my endWindow) { Melder_throw ("Command ambiguous: a part of the selection is out of view. Either zoom or re-select."); } *tmin = my startSelection; *tmax = my endSelection; return FunctionEditor_PART_SELECTION; } static void menu_cb_logSettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Log settings", L"Log files") OPTIONMENU (L"Write log 1 to", 3) OPTION (L"Log file only") OPTION (L"Info window only") OPTION (L"Log file and Info window") LABEL (L"", L"Log file 1:") TEXTFIELD (L"Log file 1", LOG_1_FILE_NAME) LABEL (L"", L"Log 1 format:") TEXTFIELD (L"Log 1 format", LOG_1_FORMAT) OPTIONMENU (L"Write log 2 to", 3) OPTION (L"Log file only") OPTION (L"Info window only") OPTION (L"Log file and Info window") LABEL (L"", L"Log file 2:") TEXTFIELD (L"Log file 2", LOG_2_FILE_NAME) LABEL (L"", L"Log 2 format:") TEXTFIELD (L"Log 2 format", LOG_2_FORMAT) LABEL (L"", L"Log script 3:") TEXTFIELD (L"Log script 3", LOG_3_FILE_NAME) LABEL (L"", L"Log script 4:") TEXTFIELD (L"Log script 4", LOG_4_FILE_NAME) EDITOR_OK SET_INTEGER (L"Write log 1 to", preferences.log[0].toLogFile + 2 * preferences.log[0].toInfoWindow) SET_STRING (L"Log file 1", preferences.log[0].fileName) SET_STRING (L"Log 1 format", preferences.log[0].format) SET_INTEGER (L"Write log 2 to", preferences.log[1].toLogFile + 2 * preferences.log[1].toInfoWindow) SET_STRING (L"Log file 2", preferences.log[1].fileName) SET_STRING (L"Log 2 format", preferences.log[1].format) SET_STRING (L"Log script 3", preferences.logScript3) SET_STRING (L"Log script 4", preferences.logScript4) EDITOR_DO preferences.log[0].toLogFile = (GET_INTEGER (L"Write log 1 to") & 1) != 0; preferences.log[0].toInfoWindow = (GET_INTEGER (L"Write log 1 to") & 2) != 0; wcscpy (preferences.log[0].fileName, GET_STRING (L"Log file 1")); wcscpy (preferences.log[0].format, GET_STRING (L"Log 1 format")); preferences.log[1].toLogFile = (GET_INTEGER (L"Write log 2 to") & 1) != 0; preferences.log[1].toInfoWindow = (GET_INTEGER (L"Write log 2 to") & 2) != 0; wcscpy (preferences.log[1].fileName, GET_STRING (L"Log file 2")); wcscpy (preferences.log[1].format, GET_STRING (L"Log 2 format")); wcscpy (preferences.logScript3, GET_STRING (L"Log script 3")); wcscpy (preferences.logScript4, GET_STRING (L"Log script 4")); EDITOR_END } static void do_deleteLogFile (TimeSoundAnalysisEditor me, int which) { structMelderFile file = { 0 }; (void) me; Melder_pathToFile (preferences.log[which].fileName, & file); MelderFile_delete (& file); } static void menu_cb_deleteLogFile1 (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_deleteLogFile (me, 0); } static void menu_cb_deleteLogFile2 (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_deleteLogFile (me, 1); } static void do_log (TimeSoundAnalysisEditor me, int which) { wchar format [1000], *p; double tmin, tmax; int part = makeQueriable (me, TRUE, & tmin, & tmax); wcscpy (format, preferences.log[which].format); for (p = format; *p !='\0'; p ++) if (*p == '\'') { /* * Found a left quote. Search for a matching right quote. */ wchar_t *q = p + 1, varName [300], *r, *s, *colon; int precision = -1; double value = NUMundefined; const wchar_t *stringValue = NULL; while (*q != '\0' && *q != '\'') q ++; if (*q == '\0') break; /* No matching right quote: done with this line. */ if (q - p == 1) continue; /* Ignore empty variable names. */ /* * Found a right quote. Get potential variable name. */ for (r = p + 1, s = varName; q - r > 0; r ++, s ++) *s = *r; *s = '\0'; /* Trailing null byte. */ colon = wcschr (varName, ':'); if (colon) { precision = wcstol (colon + 1, NULL, 10); *colon = '\0'; } if (wcsequ (varName, L"time")) { value = 0.5 * (tmin + tmax); } else if (wcsequ (varName, L"t1")) { value = tmin; } else if (wcsequ (varName, L"t2")) { value = tmax; } else if (wcsequ (varName, L"dur")) { value = tmax - tmin; } else if (wcsequ (varName, L"freq")) { value = my spectrogram.cursor; } else if (wcsequ (varName, L"tab$")) { stringValue = L"\t"; } else if (wcsequ (varName, L"editor$")) { stringValue = my name; } else if (wcsequ (varName, L"f0")) { if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the Pitch menu."); if (! my pitch.data) { Melder_throw (theMessage_Cannot_compute_pitch); } if (part == FunctionEditor_PART_CURSOR) { value = Pitch_getValueAtTime (my pitch.data, tmin, my pitch.unit, 1); } else { value = Pitch_getMean (my pitch.data, tmin, tmax, my pitch.unit); } } else if (varName [0] == 'f' && varName [1] >= '1' && varName [1] <= '5' && varName [2] == '\0') { if (! my formant.show) Melder_throw ("No formant contour is visible.\nFirst choose \"Show formants\" from the Formant menu."); if (! my formant.data) { Melder_throw (theMessage_Cannot_compute_formant); } if (part == FunctionEditor_PART_CURSOR) { value = Formant_getValueAtTime (my formant.data, varName [1] - '0', tmin, 0); } else { value = Formant_getMean (my formant.data, varName [1] - '0', tmin, tmax, 0); } } else if (varName [0] == 'b' && varName [1] >= '1' && varName [1] <= '5' && varName [2] == '\0') { if (! my formant.show) Melder_throw ("No formant contour is visible.\nFirst choose \"Show formants\" from the Formant menu."); if (! my formant.data) { Melder_throw (theMessage_Cannot_compute_formant); } value = Formant_getBandwidthAtTime (my formant.data, varName [1] - '0', 0.5 * (tmin + tmax), 0); } else if (wcsequ (varName, L"intensity")) { if (! my intensity.show) Melder_throw ("No intensity contour is visible.\nFirst choose \"Show intensity\" from the Intensity menu."); if (! my intensity.data) { Melder_throw (theMessage_Cannot_compute_intensity); } if (part == FunctionEditor_PART_CURSOR) { value = Vector_getValueAtX (my intensity.data, tmin, Vector_CHANNEL_1, Vector_VALUE_INTERPOLATION_LINEAR); } else { value = Intensity_getAverage (my intensity.data, tmin, tmax, my intensity.averagingMethod); } } else if (wcsequ (varName, L"power")) { if (! my spectrogram.show) Melder_throw ("No spectrogram is visible.\nFirst choose \"Show spectrogram\" from the Spectrum menu."); if (! my spectrogram.data) { Melder_throw (theMessage_Cannot_compute_spectrogram); } if (part != FunctionEditor_PART_CURSOR) Melder_throw ("Click inside the spectrogram first."); value = Matrix_getValueAtXY (my spectrogram.data, tmin, my spectrogram.cursor); } if (NUMdefined (value)) { int varlen = (q - p) - 1, headlen = p - format; wchar_t formattedNumber [400]; if (precision >= 0) { swprintf (formattedNumber, 400, L"%.*f", precision, value); } else { swprintf (formattedNumber, 400, L"%.17g", value); } int arglen = wcslen (formattedNumber); static MelderString buffer = { 0 }; MelderString_ncopy (& buffer, format, headlen); MelderString_append (& buffer, formattedNumber, p + varlen + 2); wcscpy (format, buffer.string); p += arglen - 1; } else if (stringValue != NULL) { int varlen = (q - p) - 1, headlen = p - format, arglen = wcslen (stringValue); static MelderString buffer = { 0 }; MelderString_ncopy (& buffer, format, headlen); MelderString_append (& buffer, stringValue, p + varlen + 2); wcscpy (format, buffer.string); p += arglen - 1; } else { p = q - 1; /* Go to before next quote. */ } } if (preferences.log[which].toInfoWindow) { MelderInfo_write1 (format); MelderInfo_close (); } if (preferences.log[which].toLogFile) { structMelderFile file = { 0 }; wcscat (format, L"\n"); Melder_relativePathToFile (preferences.log[which].fileName, & file); MelderFile_appendText (& file, format); } } static void menu_cb_log1 (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_log (me, 0); } static void menu_cb_log2 (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_log (me, 1); } static void menu_cb_logScript3 (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); DO_RunTheScriptFromAnyAddedEditorCommand (me, preferences.logScript3); } static void menu_cb_logScript4 (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); DO_RunTheScriptFromAnyAddedEditorCommand (me, preferences.logScript4); } static void menu_cb_showAnalyses (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Show analyses", 0) BOOLEAN (L"Show spectrogram", 1) BOOLEAN (L"Show pitch", 1) BOOLEAN (L"Show intensity", 0) BOOLEAN (L"Show formants", 0) BOOLEAN (L"Show pulses", 0) POSITIVE (L"Longest analysis (s)", L"5.0") EDITOR_OK SET_INTEGER (L"Show spectrogram", my spectrogram.show) SET_INTEGER (L"Show pitch", my pitch.show) SET_INTEGER (L"Show intensity", my intensity.show) SET_INTEGER (L"Show formants", my formant.show) SET_INTEGER (L"Show pulses", my pulses.show) SET_REAL (L"Longest analysis", my longestAnalysis) EDITOR_DO GuiMenuItem_check (my spectrogramToggle, preferences.spectrogram.show = my spectrogram.show = GET_INTEGER (L"Show spectrogram")); GuiMenuItem_check (my pitchToggle, preferences.pitch.show = my pitch.show = GET_INTEGER (L"Show pitch")); GuiMenuItem_check (my intensityToggle, preferences.intensity.show = my intensity.show = GET_INTEGER (L"Show intensity")); GuiMenuItem_check (my formantToggle, preferences.formant.show = my formant.show = GET_INTEGER (L"Show formants")); GuiMenuItem_check (my pulsesToggle, preferences.pulses.show = my pulses.show = GET_INTEGER (L"Show pulses")); preferences.longestAnalysis = my longestAnalysis = GET_REAL (L"Longest analysis"); FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_timeStepSettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Time step settings", L"Time step settings...") OPTIONMENU_ENUM (L"Time step strategy", kTimeSoundAnalysisEditor_timeStepStrategy, DEFAULT) LABEL (L"", L"") LABEL (L"", L"If the time step strategy is \"fixed\":") POSITIVE (L"Fixed time step (s)", L"0.01") LABEL (L"", L"") LABEL (L"", L"If the time step strategy is \"view-dependent\":") NATURAL (L"Number of time steps per view", L"100") EDITOR_OK SET_ENUM (L"Time step strategy", kTimeSoundAnalysisEditor_timeStepStrategy, my timeStepStrategy) SET_REAL (L"Fixed time step", my fixedTimeStep) SET_INTEGER (L"Number of time steps per view", my numberOfTimeStepsPerView) EDITOR_DO preferences.timeStepStrategy = my timeStepStrategy = GET_ENUM (kTimeSoundAnalysisEditor_timeStepStrategy, L"Time step strategy"); preferences.fixedTimeStep = my fixedTimeStep = GET_REAL (L"Fixed time step"); preferences.numberOfTimeStepsPerView = my numberOfTimeStepsPerView = GET_INTEGER (L"Number of time steps per view"); forget (my pitch.data); forget (my formant.data); forget (my intensity.data); forget (my pulses.data); FunctionEditor_redraw (me); EDITOR_END } /***** SPECTROGRAM MENU *****/ static void menu_cb_showSpectrogram (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); preferences.spectrogram.show = my spectrogram.show = ! my spectrogram.show; GuiMenuItem_check (my spectrogramToggle, my spectrogram.show); // in case we're called from a script FunctionEditor_redraw (me); } static void menu_cb_spectrogramSettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Spectrogram settings", L"Intro 3.2. Configuring the spectrogram") REAL (L"left View range (Hz)", L"0.0") POSITIVE (L"right View range (Hz)", L"5000.0") POSITIVE (L"Window length (s)", L"0.005") POSITIVE (L"Dynamic range (dB)", L"50.0") LABEL (L"note1", L"") LABEL (L"note2", L"") EDITOR_OK SET_REAL (L"left View range", my spectrogram.viewFrom) SET_REAL (L"right View range", my spectrogram.viewTo) SET_REAL (L"Window length", my spectrogram.windowLength) SET_REAL (L"Dynamic range", my spectrogram.dynamicRange) if (my spectrogram.timeSteps != 1000 || my spectrogram.frequencySteps != 250 || my spectrogram.method != 1 || my spectrogram.windowShape != 5 || my spectrogram.maximum != 100.0 || ! my spectrogram.autoscaling || my spectrogram.preemphasis != 6.0 || my spectrogram.dynamicCompression != 0.0) { SET_STRING (L"note1", L"Warning: you have non-standard \"advanced settings\".") } else { SET_STRING (L"note1", L"(all of your \"advanced settings\" have their standard values)") } if (my timeStepStrategy != kTimeSoundAnalysisEditor_timeStepStrategy_DEFAULT) { SET_STRING (L"note2", L"Warning: you have a non-standard \"time step strategy\".") } else { SET_STRING (L"note2", L"(your \"time step strategy\" has its standard value: automatic)") } EDITOR_DO preferences.spectrogram.viewFrom = my spectrogram.viewFrom = GET_REAL (L"left View range"); preferences.spectrogram.viewTo = my spectrogram.viewTo = GET_REAL (L"right View range"); preferences.spectrogram.windowLength = my spectrogram.windowLength = GET_REAL (L"Window length"); preferences.spectrogram.dynamicRange = my spectrogram.dynamicRange = GET_REAL (L"Dynamic range"); forget (my spectrogram.data); FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_advancedSpectrogramSettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Advanced spectrogram settings", L"Advanced spectrogram settings...") LABEL (L"", L"Time and frequency resolutions:") NATURAL (L"Number of time steps", L"1000") NATURAL (L"Number of frequency steps", L"250") LABEL (L"", L"Spectrogram analysis settings:") OPTIONMENU_ENUM (L"Method", kSound_to_Spectrogram_method, DEFAULT) OPTIONMENU_ENUM (L"Window shape", kSound_to_Spectrogram_windowShape, DEFAULT) LABEL (L"", L"Spectrogram view settings:") BOOLEAN (L"Autoscaling", 1) REAL (L"Maximum (dB/Hz)", L"100.0") REAL (L"Pre-emphasis (dB/oct)", L"6.0") REAL (L"Dynamic compression (0-1)", L"0.0") EDITOR_OK SET_INTEGER (L"Number of time steps", my spectrogram.timeSteps) SET_INTEGER (L"Number of frequency steps", my spectrogram.frequencySteps) SET_ENUM (L"Method", kSound_to_Spectrogram_method, my spectrogram.method) SET_ENUM (L"Window shape", kSound_to_Spectrogram_windowShape, my spectrogram.windowShape) SET_REAL (L"Maximum", my spectrogram.maximum) SET_INTEGER (L"Autoscaling", my spectrogram.autoscaling) SET_REAL (L"Pre-emphasis", my spectrogram.preemphasis) SET_REAL (L"Dynamic compression", my spectrogram.dynamicCompression) EDITOR_DO preferences.spectrogram.timeSteps = my spectrogram.timeSteps = GET_INTEGER (L"Number of time steps"); preferences.spectrogram.frequencySteps = my spectrogram.frequencySteps = GET_INTEGER (L"Number of frequency steps"); preferences.spectrogram.method = my spectrogram.method = GET_ENUM (kSound_to_Spectrogram_method, L"Method"); preferences.spectrogram.windowShape = my spectrogram.windowShape = GET_ENUM (kSound_to_Spectrogram_windowShape, L"Window shape"); preferences.spectrogram.maximum = my spectrogram.maximum = GET_REAL (L"Maximum"); preferences.spectrogram.autoscaling = my spectrogram.autoscaling = GET_INTEGER (L"Autoscaling"); preferences.spectrogram.preemphasis = my spectrogram.preemphasis = GET_REAL (L"Pre-emphasis"); preferences.spectrogram.dynamicCompression = my spectrogram.dynamicCompression = GET_REAL (L"Dynamic compression"); forget (my spectrogram.data); FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_getFrequency (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); Melder_informationReal (my spectrogram.cursor, L"Hz"); } static void menu_cb_getSpectralPowerAtCursorCross (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax; int part = makeQueriable (me, TRUE, & tmin, & tmax); if (! my spectrogram.show) Melder_throw ("No spectrogram is visible.\nFirst choose \"Show spectrogram\" from the Spectrum menu."); if (! my spectrogram.data) { TimeSoundAnalysisEditor_computeSpectrogram (me); if (! my spectrogram.data) Melder_throw (theMessage_Cannot_compute_spectrogram); } if (part != FunctionEditor_PART_CURSOR) Melder_throw ("Click inside the spectrogram first."); MelderInfo_open (); MelderInfo_write1 (Melder_double (Matrix_getValueAtXY (my spectrogram.data, tmin, my spectrogram.cursor))); MelderInfo_write5 (L" Pa2/Hz (at time = ", Melder_double (tmin), L" seconds and frequency = ", Melder_double (my spectrogram.cursor), L" Hz)"); MelderInfo_close (); } static void menu_cb_moveFrequencyCursorTo (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); if (! my spectrogram.show) Melder_throw ("No spectrogram is visible.\nFirst choose \"Show spectrogram\" from the Spectrum menu."); EDITOR_FORM (L"Move frequency cursor to", 0) REAL (L"Frequency (Hz)", L"0.0") EDITOR_OK SET_REAL (L"Frequency", my spectrogram.cursor) EDITOR_DO double frequency = GET_REAL (L"Frequency"); my spectrogram.cursor = frequency; FunctionEditor_redraw (me); EDITOR_END } static Sound extractSound (TimeSoundAnalysisEditor me, double tmin, double tmax) { Sound sound = NULL; if (my longSound.data) { if (tmin < my longSound.data -> xmin) tmin = my longSound.data -> xmin; if (tmax > my longSound.data -> xmax) tmax = my longSound.data -> xmax; sound = LongSound_extractPart (my longSound.data, tmin, tmax, TRUE); } else if (my sound.data) { if (tmin < my sound.data -> xmin) tmin = my sound.data -> xmin; if (tmax > my sound.data -> xmax) tmax = my sound.data -> xmax; sound = Sound_extractPart (my sound.data, tmin, tmax, kSound_windowShape_RECTANGULAR, 1.0, TRUE); } return sound; } static void menu_cb_extractVisibleSpectrogram (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); if (! my spectrogram.show) Melder_throw ("No spectrogram is visible.\nFirst choose \"Show spectrogram\" from the Spectrum menu."); if (! my spectrogram.data) { TimeSoundAnalysisEditor_computeSpectrogram (me); if (! my spectrogram.data) Melder_throw (theMessage_Cannot_compute_spectrogram); } autoSpectrogram publish = Data_copy (my spectrogram.data); my broadcastPublication (publish.transfer()); } static void menu_cb_viewSpectralSlice (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double start = my startSelection == my endSelection ? my spectrogram.windowShape == 5 ? my startSelection - my spectrogram.windowLength : my startSelection - my spectrogram.windowLength / 2 : my startSelection; double finish = my startSelection == my endSelection ? my spectrogram.windowShape == 5 ? my endSelection + my spectrogram.windowLength : my endSelection + my spectrogram.windowLength / 2 : my endSelection; autoSound sound = extractSound (me, start, finish); Sound_multiplyByWindow (sound.peek(), my spectrogram.windowShape == kSound_to_Spectrogram_windowShape_SQUARE ? kSound_windowShape_RECTANGULAR : my spectrogram.windowShape == kSound_to_Spectrogram_windowShape_HAMMING ? kSound_windowShape_HAMMING : my spectrogram.windowShape == kSound_to_Spectrogram_windowShape_BARTLETT ? kSound_windowShape_TRIANGULAR : my spectrogram.windowShape == kSound_to_Spectrogram_windowShape_WELCH ? kSound_windowShape_PARABOLIC : my spectrogram.windowShape == kSound_to_Spectrogram_windowShape_HANNING ? kSound_windowShape_HANNING : my spectrogram.windowShape == kSound_to_Spectrogram_windowShape_GAUSSIAN ? kSound_windowShape_GAUSSIAN_2 : kSound_windowShape_RECTANGULAR); autoSpectrum publish = Sound_to_Spectrum (sound.peek(), TRUE); static MelderString sliceName = { 0 }; MelderString_copy (& sliceName, my data == NULL ? L"untitled" : ((Data) my data) -> name); MelderString_appendCharacter (& sliceName, '_'); MelderString_append (& sliceName, Melder_fixed (0.5 * (my startSelection + my endSelection), 3)); Thing_setName (publish.peek(), sliceName.string); my broadcastPublication (publish.transfer()); } static void menu_cb_paintVisibleSpectrogram (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Paint visible spectrogram", 0) my v_form_pictureWindow (cmd); my v_form_pictureMargins (cmd); my v_form_pictureSelection (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); my v_ok_pictureMargins (cmd); my v_ok_pictureSelection (cmd); SET_INTEGER (L"Garnish", my spectrogram.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); my v_do_pictureMargins (cmd); my v_do_pictureSelection (cmd); preferences.spectrogram.picture.garnish = my spectrogram.picture.garnish = GET_INTEGER (L"Garnish"); if (! my spectrogram.show) Melder_throw ("No spectrogram is visible.\nFirst choose \"Show spectrogram\" from the Spectrum menu."); if (! my spectrogram.data) { TimeSoundAnalysisEditor_computeSpectrogram (me); if (! my spectrogram.data) Melder_throw (theMessage_Cannot_compute_spectrogram); } Editor_openPraatPicture (me); Spectrogram_paint (my spectrogram.data, my pictureGraphics, my startWindow, my endWindow, my spectrogram.viewFrom, my spectrogram.viewTo, my spectrogram.maximum, my spectrogram.autoscaling, my spectrogram.dynamicRange, my spectrogram.preemphasis, my spectrogram.dynamicCompression, my spectrogram.picture.garnish); FunctionEditor_garnish (me); Editor_closePraatPicture (me); EDITOR_END } /***** PITCH MENU *****/ static void menu_cb_showPitch (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); preferences.pitch.show = my pitch.show = ! my pitch.show; GuiMenuItem_check (my pitchToggle, my pitch.show); // in case we're called from a script FunctionEditor_redraw (me); } static void menu_cb_pitchSettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Pitch settings", L"Intro 4.2. Configuring the pitch contour") POSITIVE (L"left Pitch range (Hz)", L"75.0") POSITIVE (L"right Pitch range (Hz)", L"500.0") OPTIONMENU_ENUM (L"Unit", kPitch_unit, DEFAULT) LABEL (L"opt1", L"The autocorrelation method optimizes for intonation research;") LABEL (L"opt2", L"and the cross-correlation method optimizes for voice research:") RADIO_ENUM (L"Analysis method", kTimeSoundAnalysisEditor_pitch_analysisMethod, DEFAULT) OPTIONMENU_ENUM (L"Drawing method", kTimeSoundAnalysisEditor_pitch_drawingMethod, DEFAULT) LABEL (L"note1", L"") LABEL (L"note2", L"") EDITOR_OK SET_REAL (L"left Pitch range", my pitch.floor) SET_REAL (L"right Pitch range", my pitch.ceiling) SET_ENUM (L"Unit", kPitch_unit, my pitch.unit) SET_ENUM (L"Analysis method", kTimeSoundAnalysisEditor_pitch_analysisMethod, my pitch.method) SET_ENUM (L"Drawing method", kTimeSoundAnalysisEditor_pitch_drawingMethod, my pitch.drawingMethod) if (my pitch.viewFrom != 0.0 || my pitch.viewTo != 0.0 || my pitch.veryAccurate != FALSE || my pitch.maximumNumberOfCandidates != 15 || my pitch.silenceThreshold != 0.03 || my pitch.voicingThreshold != 0.45 || my pitch.octaveCost != 0.01 || my pitch.octaveJumpCost != 0.35 || my pitch.voicedUnvoicedCost != 0.14) { SET_STRING (L"note1", L"Warning: you have some non-standard \"advanced settings\".") } else { SET_STRING (L"note1", L"(all of your \"advanced settings\" have their standard values)") } if (my timeStepStrategy != kTimeSoundAnalysisEditor_timeStepStrategy_DEFAULT) { SET_STRING (L"note2", L"Warning: you have a non-standard \"time step strategy\".") } else { SET_STRING (L"note2", L"(your \"time step strategy\" has its standard value: automatic)") } EDITOR_DO preferences.pitch.floor = my pitch.floor = GET_REAL (L"left Pitch range"); preferences.pitch.ceiling = my pitch.ceiling = GET_REAL (L"right Pitch range"); preferences.pitch.unit = my pitch.unit = GET_ENUM (kPitch_unit, L"Unit"); preferences.pitch.method = my pitch.method = GET_ENUM (kTimeSoundAnalysisEditor_pitch_analysisMethod, L"Analysis method"); preferences.pitch.drawingMethod = my pitch.drawingMethod = GET_ENUM (kTimeSoundAnalysisEditor_pitch_drawingMethod, L"Drawing method"); forget (my pitch.data); forget (my intensity.data); forget (my pulses.data); FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_advancedPitchSettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Advanced pitch settings", L"Advanced pitch settings...") LABEL (L"", L"Make view range different from analysis range:") REAL (L"left View range (units)", L"0.0 (= auto)") REAL (L"right View range (units)", L"0.0 (= auto)") LABEL (L"", L"Analysis settings:") BOOLEAN (L"Very accurate", 0) NATURAL (L"Max. number of candidates", L"15") REAL (L"Silence threshold", L"0.03") REAL (L"Voicing threshold", L"0.45") REAL (L"Octave cost", L"0.01") REAL (L"Octave-jump cost", L"0.35") REAL (L"Voiced / unvoiced cost", L"0.14") EDITOR_OK SET_REAL (L"left View range", my pitch.viewFrom) SET_REAL (L"right View range", my pitch.viewTo) SET_INTEGER (L"Very accurate", my pitch.veryAccurate) SET_INTEGER (L"Max. number of candidates", my pitch.maximumNumberOfCandidates) SET_REAL (L"Silence threshold", my pitch.silenceThreshold) SET_REAL (L"Voicing threshold", my pitch.voicingThreshold) SET_REAL (L"Octave cost", my pitch.octaveCost) SET_REAL (L"Octave-jump cost", my pitch.octaveJumpCost) SET_REAL (L"Voiced / unvoiced cost", my pitch.voicedUnvoicedCost) EDITOR_DO long maxnCandidates = GET_INTEGER (L"Max. number of candidates"); if (maxnCandidates < 2) Melder_throw ("Maximum number of candidates must be greater than 1."); preferences.pitch.viewFrom = my pitch.viewFrom = GET_REAL (L"left View range"); preferences.pitch.viewTo = my pitch.viewTo = GET_REAL (L"right View range"); preferences.pitch.veryAccurate = my pitch.veryAccurate = GET_INTEGER (L"Very accurate"); preferences.pitch.maximumNumberOfCandidates = my pitch.maximumNumberOfCandidates = GET_INTEGER (L"Max. number of candidates"); preferences.pitch.silenceThreshold = my pitch.silenceThreshold = GET_REAL (L"Silence threshold"); preferences.pitch.voicingThreshold = my pitch.voicingThreshold = GET_REAL (L"Voicing threshold"); preferences.pitch.octaveCost = my pitch.octaveCost = GET_REAL (L"Octave cost"); preferences.pitch.octaveJumpCost = my pitch.octaveJumpCost = GET_REAL (L"Octave-jump cost"); preferences.pitch.voicedUnvoicedCost = my pitch.voicedUnvoicedCost = GET_REAL (L"Voiced / unvoiced cost"); forget (my pitch.data); forget (my intensity.data); forget (my pulses.data); FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_pitchListing (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax; int part = makeQueriable (me, TRUE, & tmin, & tmax); if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the Pitch menu."); if (! my pitch.data) { TimeSoundAnalysisEditor_computePitch (me); if (! my pitch.data) Melder_throw (theMessage_Cannot_compute_pitch); } MelderInfo_open (); MelderInfo_writeLine2 (L"Time_s F0_", Function_getUnitText (my pitch.data, Pitch_LEVEL_FREQUENCY, my pitch.unit, Function_UNIT_TEXT_SHORT)); if (part == FunctionEditor_PART_CURSOR) { double f0 = Pitch_getValueAtTime (my pitch.data, tmin, my pitch.unit, TRUE); f0 = Function_convertToNonlogarithmic (my pitch.data, f0, Pitch_LEVEL_FREQUENCY, my pitch.unit); MelderInfo_writeLine3 (Melder_fixed (tmin, 6), L" ", Melder_fixed (f0, 6)); } else { long i, i1, i2; Sampled_getWindowSamples (my pitch.data, tmin, tmax, & i1, & i2); for (i = i1; i <= i2; i ++) { double t = Sampled_indexToX (my pitch.data, i); double f0 = Sampled_getValueAtSample (my pitch.data, i, Pitch_LEVEL_FREQUENCY, my pitch.unit); f0 = Function_convertToNonlogarithmic (my pitch.data, f0, Pitch_LEVEL_FREQUENCY, my pitch.unit); MelderInfo_writeLine3 (Melder_fixed (t, 6), L" ", Melder_fixed (f0, 6)); } } MelderInfo_close (); } static void menu_cb_getPitch (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax; int part = makeQueriable (me, TRUE, & tmin, & tmax); if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the Pitch menu."); if (! my pitch.data) { TimeSoundAnalysisEditor_computePitch (me); if (! my pitch.data) Melder_throw (theMessage_Cannot_compute_pitch); } if (part == FunctionEditor_PART_CURSOR) { double f0 = Pitch_getValueAtTime (my pitch.data, tmin, my pitch.unit, TRUE); f0 = Function_convertToNonlogarithmic (my pitch.data, f0, Pitch_LEVEL_FREQUENCY, my pitch.unit); Melder_information (Melder_double (f0), L" ", Function_getUnitText (my pitch.data, Pitch_LEVEL_FREQUENCY, my pitch.unit, 0), L" (interpolated pitch at CURSOR)"); } else { double f0 = Pitch_getMean (my pitch.data, tmin, tmax, my pitch.unit); f0 = Function_convertToNonlogarithmic (my pitch.data, f0, Pitch_LEVEL_FREQUENCY, my pitch.unit); Melder_information (Melder_double (f0), L" ", Function_getUnitText (my pitch.data, Pitch_LEVEL_FREQUENCY, my pitch.unit, 0), L" (mean pitch ", FunctionEditor_partString_locative (part), L")"); } } static void menu_cb_getMinimumPitch (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax, f0; int part = makeQueriable (me, FALSE, & tmin, & tmax); if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the Pitch menu."); if (! my pitch.data) { TimeSoundAnalysisEditor_computePitch (me); if (! my pitch.data) Melder_throw (theMessage_Cannot_compute_pitch); } f0 = Pitch_getMinimum (my pitch.data, tmin, tmax, my pitch.unit, TRUE); f0 = Function_convertToNonlogarithmic (my pitch.data, f0, Pitch_LEVEL_FREQUENCY, my pitch.unit); Melder_information (Melder_double (f0), L" ", Function_getUnitText (my pitch.data, Pitch_LEVEL_FREQUENCY, my pitch.unit, 0), L" (minimum pitch ", FunctionEditor_partString_locative (part), L")"); } static void menu_cb_getMaximumPitch (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax, f0; int part = makeQueriable (me, FALSE, & tmin, & tmax); if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the Pitch menu."); if (! my pitch.data) { TimeSoundAnalysisEditor_computePitch (me); if (! my pitch.data) Melder_throw (theMessage_Cannot_compute_pitch); // BUG } f0 = Pitch_getMaximum (my pitch.data, tmin, tmax, my pitch.unit, TRUE); f0 = Function_convertToNonlogarithmic (my pitch.data, f0, Pitch_LEVEL_FREQUENCY, my pitch.unit); Melder_information (Melder_double (f0), L" ", Function_getUnitText (my pitch.data, Pitch_LEVEL_FREQUENCY, my pitch.unit, 0), L" (maximum pitch ", FunctionEditor_partString_locative (part), L")"); } static void menu_cb_moveCursorToMinimumPitch (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the View menu."); if (! my pitch.data) { TimeSoundAnalysisEditor_computePitch (me); if (! my pitch.data) Melder_throw (theMessage_Cannot_compute_pitch); } if (my startSelection == my endSelection) { Melder_throw ("Empty selection."); } else { double time; Pitch_getMinimumAndTime (my pitch.data, my startSelection, my endSelection, my pitch.unit, 1, NULL, & time); if (! NUMdefined (time)) Melder_throw ("Selection is voiceless."); my startSelection = my endSelection = time; FunctionEditor_marksChanged (me); } } static void menu_cb_moveCursorToMaximumPitch (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the View menu."); if (! my pitch.data) { TimeSoundAnalysisEditor_computePitch (me); if (! my pitch.data) Melder_throw (theMessage_Cannot_compute_pitch); } if (my startSelection == my endSelection) { Melder_throw (L"Empty selection."); } else { double time; Pitch_getMaximumAndTime (my pitch.data, my startSelection, my endSelection, my pitch.unit, 1, NULL, & time); if (! NUMdefined (time)) Melder_throw (L"Selection is voiceless."); my startSelection = my endSelection = time; FunctionEditor_marksChanged (me); } } static void menu_cb_extractVisiblePitchContour (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the Pitch menu."); if (! my pitch.data) { TimeSoundAnalysisEditor_computePitch (me); if (! my pitch.data) Melder_throw (theMessage_Cannot_compute_pitch); } autoPitch publish = Data_copy (my pitch.data); my broadcastPublication (publish.transfer()); } static void menu_cb_drawVisiblePitchContour (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Draw visible pitch contour", 0) my v_form_pictureWindow (cmd); LABEL (L"", L"Pitch:") BOOLEAN (L"Speckle", 0); my v_form_pictureMargins (cmd); my v_form_pictureSelection (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); SET_INTEGER (L"Speckle", my pitch.picture.speckle); my v_ok_pictureMargins (cmd); my v_ok_pictureSelection (cmd); SET_INTEGER (L"Garnish", my pitch.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); preferences.pitch.picture.speckle = my pitch.picture.speckle = GET_INTEGER (L"Speckle"); my v_do_pictureMargins (cmd); my v_do_pictureSelection (cmd); preferences.pitch.picture.garnish = my pitch.picture.garnish = GET_INTEGER (L"Garnish"); if (! my pitch.show) Melder_throw ("No pitch contour is visible.\nFirst choose \"Show pitch\" from the Pitch menu."); if (! my pitch.data) { TimeSoundAnalysisEditor_computePitch (me); if (! my pitch.data) Melder_throw (theMessage_Cannot_compute_pitch); } Editor_openPraatPicture (me); double pitchFloor_hidden = Function_convertStandardToSpecialUnit (my pitch.data, my pitch.floor, Pitch_LEVEL_FREQUENCY, my pitch.unit); double pitchCeiling_hidden = Function_convertStandardToSpecialUnit (my pitch.data, my pitch.ceiling, Pitch_LEVEL_FREQUENCY, my pitch.unit); double pitchFloor_overt = Function_convertToNonlogarithmic (my pitch.data, pitchFloor_hidden, Pitch_LEVEL_FREQUENCY, my pitch.unit); double pitchCeiling_overt = Function_convertToNonlogarithmic (my pitch.data, pitchCeiling_hidden, Pitch_LEVEL_FREQUENCY, my pitch.unit); double pitchViewFrom_overt = my pitch.viewFrom < my pitch.viewTo ? my pitch.viewFrom : pitchFloor_overt; double pitchViewTo_overt = my pitch.viewFrom < my pitch.viewTo ? my pitch.viewTo : pitchCeiling_overt; Pitch_draw (my pitch.data, my pictureGraphics, my startWindow, my endWindow, pitchViewFrom_overt, pitchViewTo_overt, my pitch.picture.garnish, my pitch.picture.speckle, my pitch.unit); FunctionEditor_garnish (me); Editor_closePraatPicture (me); EDITOR_END } /***** INTENSITY MENU *****/ static void menu_cb_showIntensity (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); preferences.intensity.show = my intensity.show = ! my intensity.show; GuiMenuItem_check (my intensityToggle, my intensity.show); // in case we're called from a script FunctionEditor_redraw (me); } static void menu_cb_intensitySettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Intensity settings", L"Intro 6.2. Configuring the intensity contour") REAL (L"left View range (dB)", L"50.0") REAL (L"right View range (dB)", L"100.0") RADIO_ENUM (L"Averaging method", kTimeSoundAnalysisEditor_intensity_averagingMethod, MEAN_ENERGY) BOOLEAN (L"Subtract mean pressure", 1) LABEL (L"", L"Note: the pitch floor is taken from the pitch settings.") LABEL (L"note2", L"") EDITOR_OK SET_REAL (L"left View range", my intensity.viewFrom) SET_REAL (L"right View range", my intensity.viewTo) SET_ENUM (L"Averaging method", kTimeSoundAnalysisEditor_intensity_averagingMethod, my intensity.averagingMethod) SET_INTEGER (L"Subtract mean pressure", my intensity.subtractMeanPressure) if (my timeStepStrategy != kTimeSoundAnalysisEditor_timeStepStrategy_DEFAULT) { SET_STRING (L"note2", L"Warning: you have a non-standard \"time step strategy\".") } else { SET_STRING (L"note2", L"(your \"time step strategy\" has its standard value: automatic)") } EDITOR_DO preferences.intensity.viewFrom = my intensity.viewFrom = GET_REAL (L"left View range"); preferences.intensity.viewTo = my intensity.viewTo = GET_REAL (L"right View range"); preferences.intensity.averagingMethod = my intensity.averagingMethod = GET_ENUM (kTimeSoundAnalysisEditor_intensity_averagingMethod, L"Averaging method"); preferences.intensity.subtractMeanPressure = my intensity.subtractMeanPressure = GET_INTEGER (L"Subtract mean pressure"); forget (my intensity.data); FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_extractVisibleIntensityContour (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); if (! my intensity.show) Melder_throw ("No intensity contour is visible.\nFirst choose \"Show intensity\" from the Intensity menu."); if (! my intensity.data) { TimeSoundAnalysisEditor_computeIntensity (me); if (! my intensity.data) Melder_throw (theMessage_Cannot_compute_intensity); } autoIntensity publish = Data_copy (my intensity.data); my broadcastPublication (publish.transfer()); } static void menu_cb_drawVisibleIntensityContour (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Draw visible intensity contour", 0) my v_form_pictureWindow (cmd); my v_form_pictureMargins (cmd); my v_form_pictureSelection (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); my v_ok_pictureMargins (cmd); my v_ok_pictureSelection (cmd); SET_INTEGER (L"Garnish", my intensity.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); my v_do_pictureMargins (cmd); my v_do_pictureSelection (cmd); preferences.intensity.picture.garnish = my intensity.picture.garnish = GET_INTEGER (L"Garnish"); if (! my intensity.show) Melder_throw ("No intensity contour is visible.\nFirst choose \"Show intensity\" from the Intensity menu."); if (! my intensity.data) { TimeSoundAnalysisEditor_computeIntensity (me); if (! my intensity.data) Melder_throw (theMessage_Cannot_compute_intensity); } Editor_openPraatPicture (me); Intensity_draw (my intensity.data, my pictureGraphics, my startWindow, my endWindow, my intensity.viewFrom, my intensity.viewTo, my intensity.picture.garnish); FunctionEditor_garnish (me); Editor_closePraatPicture (me); EDITOR_END } static void menu_cb_intensityListing (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax; int part = makeQueriable (me, TRUE, & tmin, & tmax); if (! my intensity.show) Melder_throw ("No intensity contour is visible.\nFirst choose \"Show intensity\" from the Intensity menu."); if (! my intensity.data) { TimeSoundAnalysisEditor_computeIntensity (me); if (! my intensity.data) Melder_throw (theMessage_Cannot_compute_intensity); } MelderInfo_open (); MelderInfo_writeLine1 (L"Time_s Intensity_dB"); if (part == FunctionEditor_PART_CURSOR) { double intensity = Vector_getValueAtX (my intensity.data, tmin, Vector_CHANNEL_1, Vector_VALUE_INTERPOLATION_LINEAR); MelderInfo_writeLine3 (Melder_fixed (tmin, 6), L" ", Melder_fixed (intensity, 6)); } else { long i, i1, i2; Sampled_getWindowSamples (my intensity.data, tmin, tmax, & i1, & i2); for (i = i1; i <= i2; i ++) { double t = Sampled_indexToX (my intensity.data, i); double intensity = Vector_getValueAtX (my intensity.data, t, Vector_CHANNEL_1, Vector_VALUE_INTERPOLATION_NEAREST); MelderInfo_writeLine3 (Melder_fixed (t, 6), L" ", Melder_fixed (intensity, 6)); } } MelderInfo_close (); } static void menu_cb_getIntensity (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax; int part = makeQueriable (me, TRUE, & tmin, & tmax); if (! my intensity.show) Melder_throw ("No intensity contour is visible.\nFirst choose \"Show intensity\" from the Intensity menu."); if (! my intensity.data) { TimeSoundAnalysisEditor_computeIntensity (me); if (! my intensity.data) Melder_throw (theMessage_Cannot_compute_intensity); } if (part == FunctionEditor_PART_CURSOR) { Melder_information (Melder_double (Vector_getValueAtX (my intensity.data, tmin, Vector_CHANNEL_1, Vector_VALUE_INTERPOLATION_LINEAR)), L" dB (intensity at CURSOR)"); } else { static const wchar_t *methodString [] = { L"median", L"mean-energy", L"mean-sones", L"mean-dB" }; Melder_information (Melder_double (Intensity_getAverage (my intensity.data, tmin, tmax, my intensity.averagingMethod)), L" dB (", methodString [my intensity.averagingMethod], L" intensity ", FunctionEditor_partString_locative (part), L")"); } } static void menu_cb_getMinimumIntensity (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax; int part = makeQueriable (me, FALSE, & tmin, & tmax); if (! my intensity.show) Melder_throw ("No intensity contour is visible.\nFirst choose \"Show intensity\" from the Intensity menu."); if (! my intensity.data) { TimeSoundAnalysisEditor_computeIntensity (me); if (! my intensity.data) Melder_throw (theMessage_Cannot_compute_intensity); } double intensity = Vector_getMinimum (my intensity.data, tmin, tmax, NUM_PEAK_INTERPOLATE_PARABOLIC); Melder_information (Melder_double (intensity), L" dB (minimum intensity ", FunctionEditor_partString_locative (part), L")"); } static void menu_cb_getMaximumIntensity (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax; int part = makeQueriable (me, FALSE, & tmin, & tmax); if (! my intensity.show) Melder_throw ("No intensity contour is visible.\nFirst choose \"Show intensity\" from the Intensity menu."); if (! my intensity.data) { TimeSoundAnalysisEditor_computeIntensity (me); if (! my intensity.data) Melder_throw (theMessage_Cannot_compute_intensity); } double intensity = Vector_getMaximum (my intensity.data, tmin, tmax, NUM_PEAK_INTERPOLATE_PARABOLIC); Melder_information (Melder_double (intensity), L" dB (maximum intensity ", FunctionEditor_partString_locative (part), L")"); } /***** FORMANT MENU *****/ static void menu_cb_showFormants (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); preferences.formant.show = my formant.show = ! my formant.show; GuiMenuItem_check (my formantToggle, my formant.show); // in case we're called from a script FunctionEditor_redraw (me); } static void menu_cb_formantSettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Formant settings", L"Intro 5.2. Configuring the formant contours") POSITIVE (L"Maximum formant (Hz)", L"5500.0") POSITIVE (L"Number of formants", L"5.0") POSITIVE (L"Window length (s)", L"0.025") REAL (L"Dynamic range (dB)", L"30.0") POSITIVE (L"Dot size (mm)", L"1.0") LABEL (L"note1", L"") LABEL (L"note2", L"") EDITOR_OK SET_REAL (L"Maximum formant", my formant.maximumFormant) SET_REAL (L"Number of formants", 0.5 * my formant.numberOfPoles) SET_REAL (L"Window length", my formant.windowLength) SET_REAL (L"Dynamic range", my formant.dynamicRange) SET_REAL (L"Dot size", my formant.dotSize) if (my formant.method != 1 || my formant.preemphasisFrom != 50.0) { SET_STRING (L"note1", L"Warning: you have non-standard \"advanced settings\".") } else { SET_STRING (L"note1", L"(all of your \"advanced settings\" have their standard values)") } if (my timeStepStrategy != kTimeSoundAnalysisEditor_timeStepStrategy_DEFAULT) { SET_STRING (L"note2", L"Warning: you have a non-standard \"time step strategy\".") } else { SET_STRING (L"note2", L"(your \"time step strategy\" has its standard value: automatic)") } EDITOR_DO preferences.formant.maximumFormant = my formant.maximumFormant = GET_REAL (L"Maximum formant"); preferences.formant.numberOfPoles = my formant.numberOfPoles = 2.0 * GET_REAL (L"Number of formants"); preferences.formant.windowLength = my formant.windowLength = GET_REAL (L"Window length"); preferences.formant.dynamicRange = my formant.dynamicRange = GET_REAL (L"Dynamic range"); preferences.formant.dotSize = my formant.dotSize = GET_REAL (L"Dot size"); forget (my formant.data); FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_advancedFormantSettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Advanced formant settings", L"Advanced formant settings...") RADIO_ENUM (L"Method", kTimeSoundAnalysisEditor_formant_analysisMethod, BURG) POSITIVE (L"Pre-emphasis from (Hz)", L"50.0") EDITOR_OK SET_ENUM (L"Method", kTimeSoundAnalysisEditor_formant_analysisMethod, my formant.method) SET_REAL (L"Pre-emphasis from", my formant.preemphasisFrom) EDITOR_DO preferences.formant.method = my formant.method = GET_ENUM (kTimeSoundAnalysisEditor_formant_analysisMethod, L"Method"); preferences.formant.preemphasisFrom = my formant.preemphasisFrom = GET_REAL (L"Pre-emphasis from"); forget (my formant.data); FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_extractVisibleFormantContour (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); if (! my formant.show) Melder_throw ("No formant contour is visible.\nFirst choose \"Show formants\" from the Formant menu."); if (! my formant.data) { TimeSoundAnalysisEditor_computeFormants (me); if (! my formant.data) Melder_throw (theMessage_Cannot_compute_formant); } autoFormant publish = Data_copy (my formant.data); my broadcastPublication (publish.transfer()); } static void menu_cb_drawVisibleFormantContour (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Draw visible formant contour", 0) my v_form_pictureWindow (cmd); my v_form_pictureMargins (cmd); my v_form_pictureSelection (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); my v_ok_pictureMargins (cmd); my v_ok_pictureSelection (cmd); SET_INTEGER (L"Garnish", my formant.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); my v_do_pictureMargins (cmd); my v_do_pictureSelection (cmd); preferences.formant.picture.garnish = my formant.picture.garnish = GET_INTEGER (L"Garnish"); if (! my formant.show) Melder_throw ("No formant contour is visible.\nFirst choose \"Show formant\" from the Formant menu."); if (! my formant.data) { TimeSoundAnalysisEditor_computeFormants (me); if (! my formant.data) Melder_throw (theMessage_Cannot_compute_formant); } Editor_openPraatPicture (me); Formant_drawSpeckles (my formant.data, my pictureGraphics, my startWindow, my endWindow, my spectrogram.viewTo, my formant.dynamicRange, my formant.picture.garnish); FunctionEditor_garnish (me); Editor_closePraatPicture (me); EDITOR_END } static void menu_cb_formantListing (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); double tmin, tmax; int part = makeQueriable (me, TRUE, & tmin, & tmax); if (! my formant.show) Melder_throw ("No formant contour is visible.\nFirst choose \"Show formants\" from the Formant menu."); if (! my formant.data) { TimeSoundAnalysisEditor_computeFormants (me); if (! my formant.data) Melder_throw (theMessage_Cannot_compute_formant); } MelderInfo_open (); MelderInfo_writeLine1 (L"Time_s F1_Hz F2_Hz F3_Hz F4_Hz"); if (part == FunctionEditor_PART_CURSOR) { double f1 = Formant_getValueAtTime (my formant.data, 1, tmin, 0); double f2 = Formant_getValueAtTime (my formant.data, 2, tmin, 0); double f3 = Formant_getValueAtTime (my formant.data, 3, tmin, 0); double f4 = Formant_getValueAtTime (my formant.data, 4, tmin, 0); MelderInfo_write5 (Melder_fixed (tmin, 6), L" ", Melder_fixed (f1, 6), L" ", Melder_fixed (f2, 6)); MelderInfo_writeLine4 (L" ", Melder_fixed (f3, 6), L" ", Melder_fixed (f4, 6)); } else { long i, i1, i2; Sampled_getWindowSamples (my formant.data, tmin, tmax, & i1, & i2); for (i = i1; i <= i2; i ++) { double t = Sampled_indexToX (my formant.data, i); double f1 = Formant_getValueAtTime (my formant.data, 1, t, 0); double f2 = Formant_getValueAtTime (my formant.data, 2, t, 0); double f3 = Formant_getValueAtTime (my formant.data, 3, t, 0); double f4 = Formant_getValueAtTime (my formant.data, 4, t, 0); MelderInfo_write5 (Melder_fixed (t, 6), L" ", Melder_fixed (f1, 6), L" ", Melder_fixed (f2, 6)); MelderInfo_writeLine4 (L" ", Melder_fixed (f3, 6), L" ", Melder_fixed (f4, 6)); } } MelderInfo_close (); } static void do_getFormant (TimeSoundAnalysisEditor me, int iformant) { double tmin, tmax; int part = makeQueriable (me, TRUE, & tmin, & tmax); if (! my formant.show) Melder_throw ("No formant contour is visible.\nFirst choose \"Show formants\" from the Formant menu."); if (! my formant.data) { TimeSoundAnalysisEditor_computeFormants (me); if (! my formant.data) Melder_throw (theMessage_Cannot_compute_formant); } if (part == FunctionEditor_PART_CURSOR) { Melder_information (Melder_double (Formant_getValueAtTime (my formant.data, iformant, tmin, 0)), L" Hz (nearest F", Melder_integer (iformant), L" to CURSOR)"); } else { Melder_information (Melder_double (Formant_getMean (my formant.data, iformant, tmin, tmax, 0)), L" Hz (mean F", Melder_integer (iformant), L" ", FunctionEditor_partString_locative (part), L")"); } } static void do_getBandwidth (TimeSoundAnalysisEditor me, int iformant) { double tmin, tmax; int part = makeQueriable (me, TRUE, & tmin, & tmax); if (! my formant.show) Melder_throw ("No formant contour is visible.\nFirst choose \"Show formants\" from the Formant menu."); if (! my formant.data) { TimeSoundAnalysisEditor_computeFormants (me); if (! my formant.data) Melder_throw (theMessage_Cannot_compute_formant); } if (part == FunctionEditor_PART_CURSOR) { Melder_information (Melder_double (Formant_getBandwidthAtTime (my formant.data, iformant, tmin, 0)), L" Hz (nearest B", Melder_integer (iformant), L" to CURSOR)"); } else { Melder_information (Melder_double (Formant_getBandwidthAtTime (my formant.data, iformant, 0.5 * (tmin + tmax), 0)), L" Hz (B", Melder_integer (iformant), L" in centre of ", FunctionEditor_partString (part), L")"); } } static void menu_cb_getFirstFormant (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_getFormant (me, 1); } static void menu_cb_getFirstBandwidth (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_getBandwidth (me, 1); } static void menu_cb_getSecondFormant (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_getFormant (me, 2); } static void menu_cb_getSecondBandwidth (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_getBandwidth (me, 2); } static void menu_cb_getThirdFormant (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_getFormant (me, 3); } static void menu_cb_getThirdBandwidth (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_getBandwidth (me, 3); } static void menu_cb_getFourthFormant (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_getFormant (me, 4); } static void menu_cb_getFourthBandwidth (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); do_getBandwidth (me, 4); } static void menu_cb_getFormant (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Get formant", 0) NATURAL (L"Formant number", L"5") EDITOR_OK EDITOR_DO do_getFormant (me, GET_INTEGER (L"Formant number")); EDITOR_END } static void menu_cb_getBandwidth (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Get bandwidth", 0) NATURAL (L"Formant number", L"5") EDITOR_OK EDITOR_DO do_getBandwidth (me, GET_INTEGER (L"Formant number")); EDITOR_END } /***** PULSE MENU *****/ static void menu_cb_showPulses (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); preferences.pulses.show = my pulses.show = ! my pulses.show; GuiMenuItem_check (my pulsesToggle, my pulses.show); // in case we're called from a script FunctionEditor_redraw (me); } static void menu_cb_advancedPulsesSettings (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Advanced pulses settings", L"Advanced pulses settings...") POSITIVE (L"Maximum period factor", L"1.3") POSITIVE (L"Maximum amplitude factor", L"1.6") EDITOR_OK SET_REAL (L"Maximum period factor", my pulses.maximumPeriodFactor) SET_REAL (L"Maximum amplitude factor", my pulses.maximumAmplitudeFactor) EDITOR_DO preferences.pulses.maximumPeriodFactor = my pulses.maximumPeriodFactor = GET_REAL (L"Maximum period factor"); preferences.pulses.maximumAmplitudeFactor = my pulses.maximumAmplitudeFactor = GET_REAL (L"Maximum amplitude factor"); forget (my pulses.data); FunctionEditor_redraw (me); EDITOR_END } static void menu_cb_extractVisiblePulses (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); if (! my pulses.show) Melder_throw ("No pulses are visible.\nFirst choose \"Show pulses\" from the Pulses menu."); if (! my pulses.data) { TimeSoundAnalysisEditor_computePulses (me); if (! my pulses.data) Melder_throw (theMessage_Cannot_compute_pulses); } autoPointProcess publish = Data_copy (my pulses.data); my broadcastPublication (publish.transfer()); } static void menu_cb_drawVisiblePulses (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); EDITOR_FORM (L"Draw visible pulses", 0) my v_form_pictureWindow (cmd); my v_form_pictureMargins (cmd); my v_form_pictureSelection (cmd); BOOLEAN (L"Garnish", 1); EDITOR_OK my v_ok_pictureWindow (cmd); my v_ok_pictureMargins (cmd); my v_ok_pictureSelection (cmd); SET_INTEGER (L"Garnish", my pulses.picture.garnish); EDITOR_DO my v_do_pictureWindow (cmd); my v_do_pictureMargins (cmd); my v_do_pictureSelection (cmd); preferences.pulses.picture.garnish = my pulses.picture.garnish = GET_INTEGER (L"Garnish"); if (! my pulses.show) Melder_throw (L"No pulses are visible.\nFirst choose \"Show pulses\" from the Pulses menu."); if (! my pulses.data) { TimeSoundAnalysisEditor_computePulses (me); if (! my pulses.data) Melder_throw (theMessage_Cannot_compute_pulses); } Editor_openPraatPicture (me); PointProcess_draw (my pulses.data, my pictureGraphics, my startWindow, my endWindow, my pulses.picture.garnish); FunctionEditor_garnish (me); Editor_closePraatPicture (me); EDITOR_END } static void menu_cb_voiceReport (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); time_t today = time (NULL); double tmin, tmax; int part = makeQueriable (me, FALSE, & tmin, & tmax); if (! my pulses.show) Melder_throw ("No pulses are visible.\nFirst choose \"Show pulses\" from the Pulses menu."); if (! my pulses.data) { TimeSoundAnalysisEditor_computePulses (me); if (! my pulses.data) Melder_throw (theMessage_Cannot_compute_pulses); } autoSound sound = extractSound (me, tmin, tmax); MelderInfo_open (); MelderInfo_writeLine4 (L"-- Voice report for ", my name, L" --\nDate: ", Melder_peekUtf8ToWcs (ctime (& today))); if ((my pitch.method & 2) == 0) MelderInfo_writeLine1 (L"WARNING: some of the following measurements may be imprecise.\n" "For more precision, go to \"Pitch settings\" and choose \"Optimize for voice analysis\".\n"); MelderInfo_writeLine2 (L"Time range of ", FunctionEditor_partString (part)); Sound_Pitch_PointProcess_voiceReport (sound.peek(), my pitch.data, my pulses.data, tmin, tmax, my pitch.floor, my pitch.ceiling, my pulses.maximumPeriodFactor, my pulses.maximumAmplitudeFactor, my pitch.silenceThreshold, my pitch.voicingThreshold); MelderInfo_close (); } static void menu_cb_pulseListing (EDITOR_ARGS) { EDITOR_IAM (TimeSoundAnalysisEditor); long i, i1, i2; double tmin, tmax; makeQueriable (me, FALSE, & tmin, & tmax); if (! my pulses.show) Melder_throw ("No pulses are visible.\nFirst choose \"Show pulses\" from the Pulses menu."); if (! my pulses.data) { TimeSoundAnalysisEditor_computePulses (me); if (! my pulses.data) Melder_throw (theMessage_Cannot_compute_pulses); } MelderInfo_open (); MelderInfo_writeLine1 (L"Time_s"); i1 = PointProcess_getHighIndex (my pulses.data, tmin); i2 = PointProcess_getLowIndex (my pulses.data, tmax); for (i = i1; i <= i2; i ++) { double t = my pulses.data -> t [i]; MelderInfo_writeLine1 (Melder_fixed (t, 12)); } MelderInfo_close (); } /* static void cb_getJitter_xx (TimeSoundAnalysisEditor me, double (*PointProcess_getJitter_xx) (PointProcess, double, double, double, double, double)) { double minimumPeriod = 0.8 / my pitch.ceiling, maximumPeriod = 1.25 / my pitch.floor; if (! my pulses.show) Melder_throw ("No pulses are visible.\nFirst choose \"Show pulses\" from the Pulses menu."); if (! my pulses.data) { computePulses (me); if (! my pulses.data) Melder_throw (theMessage_Cannot_compute_pulses); } if (my startSelection == my endSelection) Melder_throw (L"Make a selection first."); makeQueriable Melder_informationReal (PointProcess_getJitter_xx (my pulses.data, my startSelection, my endSelection, minimumPeriod, maximumPeriod, my pulses.maximumPeriodFactor), NULL); } DIRECT (TimeSoundAnalysisEditor, cb_getJitter_local) cb_getJitter_xx (me, PointProcess_getJitter_local); END DIRECT (TimeSoundAnalysisEditor, cb_getJitter_local_absolute) cb_getJitter_xx (me, PointProcess_getJitter_local_absolute); END DIRECT (TimeSoundAnalysisEditor, cb_getJitter_rap) cb_getJitter_xx (me, PointProcess_getJitter_rap); END DIRECT (TimeSoundAnalysisEditor, cb_getJitter_ppq5) cb_getJitter_xx (me, PointProcess_getJitter_ppq5); END DIRECT (TimeSoundAnalysisEditor, cb_getJitter_ddp) cb_getJitter_xx (me, PointProcess_getJitter_ddp); END static void cb_getShimmer_xx (TimeSoundAnalysisEditor me, double (*PointProcess_Sound_getShimmer_xx) (PointProcess, Sound, double, double, double, double, double)) { double minimumPeriod = 0.8 / my pitch.ceiling, maximumPeriod = 1.25 / my pitch.floor; if (! my pulses.show) Melder_throw ("No pulses are visible.\nFirst choose \"Show pulses\" from the Pulses menu."); if (! my pulses.data) { computePulses (me); if (! my pulses.data) Melder_throw (theMessage_Cannot_compute_pulses); } if (my startSelection == my endSelection) Melder_throw ("Make a selection first."); makeQueriable autoSound sound = extractSound (me, my startSelection, my endSelection); Melder_informationReal (PointProcess_Sound_getShimmer_xx (my pulses.data, sound, my startSelection, my endSelection, minimumPeriod, maximumPeriod, my pulses.maximumAmplitudeFactor), NULL); } DIRECT (TimeSoundAnalysisEditor, cb_getShimmer_local) cb_getShimmer_xx (me, PointProcess_Sound_getShimmer_local); END DIRECT (TimeSoundAnalysisEditor, cb_getShimmer_local_dB) cb_getShimmer_xx (me, PointProcess_Sound_getShimmer_local_dB); END DIRECT (TimeSoundAnalysisEditor, cb_getShimmer_apq3) cb_getShimmer_xx (me, PointProcess_Sound_getShimmer_apq3); END DIRECT (TimeSoundAnalysisEditor, cb_getShimmer_apq5) cb_getShimmer_xx (me, PointProcess_Sound_getShimmer_apq5); END DIRECT (TimeSoundAnalysisEditor, cb_getShimmer_apq11) cb_getShimmer_xx (me, PointProcess_Sound_getShimmer_apq11); END DIRECT (TimeSoundAnalysisEditor, cb_getShimmer_dda) cb_getShimmer_xx (me, PointProcess_Sound_getShimmer_dda); END */ void structTimeSoundAnalysisEditor :: v_createMenuItems_view_sound (EditorMenu menu) { TimeSoundAnalysisEditor_Parent :: v_createMenuItems_view_sound (menu); v_createMenuItems_view_sound_analysis (menu); } void structTimeSoundAnalysisEditor :: v_createMenuItems_view_sound_analysis (EditorMenu menu) { EditorMenu_addCommand (menu, L"Analysis window:", GuiMenu_INSENSITIVE, menu_cb_showAnalyses); EditorMenu_addCommand (menu, L"Show analyses...", 0, menu_cb_showAnalyses); EditorMenu_addCommand (menu, L"Time step settings...", 0, menu_cb_timeStepSettings); EditorMenu_addCommand (menu, L"-- sound analysis --", 0, 0); } void structTimeSoundAnalysisEditor :: v_createMenuItems_query (EditorMenu menu) { TimeSoundAnalysisEditor_Parent :: v_createMenuItems_query (menu); if (sound.data || longSound.data) { v_createMenuItems_query_log (menu); } } void structTimeSoundAnalysisEditor :: v_createMenuItems_query_log (EditorMenu menu) { EditorMenu_addCommand (menu, L"-- query log --", 0, NULL); EditorMenu_addCommand (menu, L"Log settings...", 0, menu_cb_logSettings); EditorMenu_addCommand (menu, L"Delete log file 1", 0, menu_cb_deleteLogFile1); EditorMenu_addCommand (menu, L"Delete log file 2", 0, menu_cb_deleteLogFile2); EditorMenu_addCommand (menu, L"Log 1", GuiMenu_F12, menu_cb_log1); EditorMenu_addCommand (menu, L"Log 2", GuiMenu_F12 + GuiMenu_SHIFT, menu_cb_log2); EditorMenu_addCommand (menu, L"Log script 3 (...)", GuiMenu_F12 + GuiMenu_OPTION, menu_cb_logScript3); EditorMenu_addCommand (menu, L"Log script 4 (...)", GuiMenu_F12 + GuiMenu_COMMAND, menu_cb_logScript4); } void structTimeSoundAnalysisEditor :: v_createMenus_analysis () { EditorMenu menu; menu = Editor_addMenu (this, L"Spectrum", 0); spectrogramToggle = EditorMenu_addCommand (menu, L"Show spectrogram", GuiMenu_CHECKBUTTON | (preferences.spectrogram.show ? GuiMenu_TOGGLE_ON : 0), menu_cb_showSpectrogram); EditorMenu_addCommand (menu, L"Spectrogram settings...", 0, menu_cb_spectrogramSettings); EditorMenu_addCommand (menu, L"Advanced spectrogram settings...", 0, menu_cb_advancedSpectrogramSettings); EditorMenu_addCommand (menu, L"-- spectrum query --", 0, NULL); EditorMenu_addCommand (menu, L"Query:", GuiMenu_INSENSITIVE, menu_cb_getFrequency /* dummy */); EditorMenu_addCommand (menu, L"Get frequency at frequency cursor", 0, menu_cb_getFrequency); EditorMenu_addCommand (menu, L"Get spectral power at cursor cross", GuiMenu_F7, menu_cb_getSpectralPowerAtCursorCross); EditorMenu_addCommand (menu, L"-- spectrum select --", 0, NULL); EditorMenu_addCommand (menu, L"Select:", GuiMenu_INSENSITIVE, menu_cb_moveFrequencyCursorTo/* dummy */); EditorMenu_addCommand (menu, L"Move frequency cursor to...", 0, menu_cb_moveFrequencyCursorTo); v_createMenuItems_spectrum_picture (menu); EditorMenu_addCommand (menu, L"-- spectrum extract --", 0, NULL); EditorMenu_addCommand (menu, L"Extract to objects window:", GuiMenu_INSENSITIVE, menu_cb_extractVisibleSpectrogram /* dummy */); EditorMenu_addCommand (menu, L"Extract visible spectrogram", 0, menu_cb_extractVisibleSpectrogram); EditorMenu_addCommand (menu, L"View spectral slice", 'L', menu_cb_viewSpectralSlice); menu = Editor_addMenu (this, L"Pitch", 0); pitchToggle = EditorMenu_addCommand (menu, L"Show pitch", GuiMenu_CHECKBUTTON | (preferences.pitch.show ? GuiMenu_TOGGLE_ON : 0), menu_cb_showPitch); EditorMenu_addCommand (menu, L"Pitch settings...", 0, menu_cb_pitchSettings); EditorMenu_addCommand (menu, L"Advanced pitch settings...", 0, menu_cb_advancedPitchSettings); EditorMenu_addCommand (menu, L"-- pitch query --", 0, NULL); EditorMenu_addCommand (menu, L"Query:", GuiMenu_INSENSITIVE, menu_cb_getFrequency /* dummy */); EditorMenu_addCommand (menu, L"Pitch listing", 0, menu_cb_pitchListing); EditorMenu_addCommand (menu, L"Get pitch", GuiMenu_F5, menu_cb_getPitch); EditorMenu_addCommand (menu, L"Get minimum pitch", GuiMenu_F5 + GuiMenu_COMMAND, menu_cb_getMinimumPitch); EditorMenu_addCommand (menu, L"Get maximum pitch", GuiMenu_F5 + GuiMenu_SHIFT, menu_cb_getMaximumPitch); EditorMenu_addCommand (menu, L"-- pitch select --", 0, NULL); EditorMenu_addCommand (menu, L"Select:", GuiMenu_INSENSITIVE, menu_cb_moveCursorToMinimumPitch /* dummy */); EditorMenu_addCommand (menu, L"Move cursor to minimum pitch", GuiMenu_COMMAND + GuiMenu_SHIFT + 'L', menu_cb_moveCursorToMinimumPitch); EditorMenu_addCommand (menu, L"Move cursor to maximum pitch", GuiMenu_COMMAND + GuiMenu_SHIFT + 'H', menu_cb_moveCursorToMaximumPitch); v_createMenuItems_pitch_picture (menu); EditorMenu_addCommand (menu, L"-- pitch extract --", 0, NULL); EditorMenu_addCommand (menu, L"Extract to objects window:", GuiMenu_INSENSITIVE, menu_cb_extractVisiblePitchContour /* dummy */); EditorMenu_addCommand (menu, L"Extract visible pitch contour", 0, menu_cb_extractVisiblePitchContour); menu = Editor_addMenu (this, L"Intensity", 0); intensityToggle = EditorMenu_addCommand (menu, L"Show intensity", GuiMenu_CHECKBUTTON | (preferences.intensity.show ? GuiMenu_TOGGLE_ON : 0), menu_cb_showIntensity); EditorMenu_addCommand (menu, L"Intensity settings...", 0, menu_cb_intensitySettings); EditorMenu_addCommand (menu, L"-- intensity query --", 0, NULL); EditorMenu_addCommand (menu, L"Query:", GuiMenu_INSENSITIVE, menu_cb_getFrequency /* dummy */); EditorMenu_addCommand (menu, L"Intensity listing", 0, menu_cb_intensityListing); EditorMenu_addCommand (menu, L"Get intensity", GuiMenu_F8, menu_cb_getIntensity); EditorMenu_addCommand (menu, L"Get minimum intensity", GuiMenu_F8 + GuiMenu_COMMAND, menu_cb_getMinimumIntensity); EditorMenu_addCommand (menu, L"Get maximum intensity", GuiMenu_F8 + GuiMenu_SHIFT, menu_cb_getMaximumIntensity); v_createMenuItems_intensity_picture (menu); EditorMenu_addCommand (menu, L"-- intensity extract --", 0, NULL); EditorMenu_addCommand (menu, L"Extract to objects window:", GuiMenu_INSENSITIVE, menu_cb_extractVisibleIntensityContour /* dummy */); EditorMenu_addCommand (menu, L"Extract visible intensity contour", 0, menu_cb_extractVisibleIntensityContour); menu = Editor_addMenu (this, L"Formant", 0); formantToggle = EditorMenu_addCommand (menu, L"Show formants", GuiMenu_CHECKBUTTON | (preferences.formant.show ? GuiMenu_TOGGLE_ON : 0), menu_cb_showFormants); EditorMenu_addCommand (menu, L"Formant settings...", 0, menu_cb_formantSettings); EditorMenu_addCommand (menu, L"Advanced formant settings...", 0, menu_cb_advancedFormantSettings); EditorMenu_addCommand (menu, L"-- formant query --", 0, NULL); EditorMenu_addCommand (menu, L"Query:", GuiMenu_INSENSITIVE, menu_cb_getFrequency /* dummy */); EditorMenu_addCommand (menu, L"Formant listing", 0, menu_cb_formantListing); EditorMenu_addCommand (menu, L"Get first formant", GuiMenu_F1, menu_cb_getFirstFormant); EditorMenu_addCommand (menu, L"Get first bandwidth", 0, menu_cb_getFirstBandwidth); EditorMenu_addCommand (menu, L"Get second formant", GuiMenu_F2, menu_cb_getSecondFormant); EditorMenu_addCommand (menu, L"Get second bandwidth", 0, menu_cb_getSecondBandwidth); EditorMenu_addCommand (menu, L"Get third formant", GuiMenu_F3, menu_cb_getThirdFormant); EditorMenu_addCommand (menu, L"Get third bandwidth", 0, menu_cb_getThirdBandwidth); EditorMenu_addCommand (menu, L"Get fourth formant", GuiMenu_F4, menu_cb_getFourthFormant); EditorMenu_addCommand (menu, L"Get fourth bandwidth", 0, menu_cb_getFourthBandwidth); EditorMenu_addCommand (menu, L"Get formant...", 0, menu_cb_getFormant); EditorMenu_addCommand (menu, L"Get bandwidth...", 0, menu_cb_getBandwidth); v_createMenuItems_formant_picture (menu); EditorMenu_addCommand (menu, L"-- formant extract --", 0, NULL); EditorMenu_addCommand (menu, L"Extract to objects window:", GuiMenu_INSENSITIVE, menu_cb_extractVisibleFormantContour /* dummy */); EditorMenu_addCommand (menu, L"Extract visible formant contour", 0, menu_cb_extractVisibleFormantContour); menu = Editor_addMenu (this, L"Pulses", 0); pulsesToggle = EditorMenu_addCommand (menu, L"Show pulses", GuiMenu_CHECKBUTTON | (preferences.pulses.show ? GuiMenu_TOGGLE_ON : 0), menu_cb_showPulses); EditorMenu_addCommand (menu, L"Advanced pulses settings...", 0, menu_cb_advancedPulsesSettings); EditorMenu_addCommand (menu, L"-- pulses query --", 0, NULL); EditorMenu_addCommand (menu, L"Query:", GuiMenu_INSENSITIVE, menu_cb_getFrequency /* dummy */); EditorMenu_addCommand (menu, L"Voice report", 0, menu_cb_voiceReport); EditorMenu_addCommand (menu, L"Pulse listing", 0, menu_cb_pulseListing); /* EditorMenu_addCommand (menu, L"Get jitter (local)", 0, cb_getJitter_local); EditorMenu_addCommand (menu, L"Get jitter (local, absolute)", 0, cb_getJitter_local_absolute); EditorMenu_addCommand (menu, L"Get jitter (rap)", 0, cb_getJitter_rap); EditorMenu_addCommand (menu, L"Get jitter (ppq5)", 0, cb_getJitter_ppq5); EditorMenu_addCommand (menu, L"Get jitter (ddp)", 0, cb_getJitter_ddp); EditorMenu_addCommand (menu, L"Get shimmer (local)", 0, cb_getShimmer_local); EditorMenu_addCommand (menu, L"Get shimmer (local_dB)", 0, cb_getShimmer_local_dB); EditorMenu_addCommand (menu, L"Get shimmer (apq3)", 0, cb_getShimmer_apq3); EditorMenu_addCommand (menu, L"Get shimmer (apq5)", 0, cb_getShimmer_apq5); EditorMenu_addCommand (menu, L"Get shimmer (apq11)", 0, cb_getShimmer_apq11); EditorMenu_addCommand (menu, L"Get shimmer (dda)", 0, cb_getShimmer_dda); */ v_createMenuItems_pulses_picture (menu); EditorMenu_addCommand (menu, L"-- pulses extract --", 0, NULL); EditorMenu_addCommand (menu, L"Extract to objects window:", GuiMenu_INSENSITIVE, menu_cb_extractVisiblePulses /* dummy */); EditorMenu_addCommand (menu, L"Extract visible pulses", 0, menu_cb_extractVisiblePulses); } void structTimeSoundAnalysisEditor :: v_createMenuItems_spectrum_picture (EditorMenu menu) { EditorMenu_addCommand (menu, L"-- spectrum draw --", 0, NULL); EditorMenu_addCommand (menu, L"Draw to picture window:", GuiMenu_INSENSITIVE, menu_cb_paintVisibleSpectrogram /* dummy */); EditorMenu_addCommand (menu, L"Paint visible spectrogram...", 0, menu_cb_paintVisibleSpectrogram); } void structTimeSoundAnalysisEditor :: v_createMenuItems_pitch_picture (EditorMenu menu) { EditorMenu_addCommand (menu, L"-- pitch draw --", 0, NULL); EditorMenu_addCommand (menu, L"Draw to picture window:", GuiMenu_INSENSITIVE, menu_cb_drawVisiblePitchContour /* dummy */); EditorMenu_addCommand (menu, L"Draw visible pitch contour...", 0, menu_cb_drawVisiblePitchContour); } void structTimeSoundAnalysisEditor :: v_createMenuItems_intensity_picture (EditorMenu menu) { EditorMenu_addCommand (menu, L"-- intensity draw --", 0, NULL); EditorMenu_addCommand (menu, L"Draw to picture window:", GuiMenu_INSENSITIVE, menu_cb_drawVisibleIntensityContour /* dummy */); EditorMenu_addCommand (menu, L"Draw visible intensity contour...", 0, menu_cb_drawVisibleIntensityContour); } void structTimeSoundAnalysisEditor :: v_createMenuItems_formant_picture (EditorMenu menu) { EditorMenu_addCommand (menu, L"-- formant draw --", 0, NULL); EditorMenu_addCommand (menu, L"Draw to picture window:", GuiMenu_INSENSITIVE, menu_cb_drawVisibleFormantContour /* dummy */); EditorMenu_addCommand (menu, L"Draw visible formant contour...", 0, menu_cb_drawVisibleFormantContour); } void structTimeSoundAnalysisEditor :: v_createMenuItems_pulses_picture (EditorMenu menu) { EditorMenu_addCommand (menu, L"-- pulses draw --", 0, NULL); EditorMenu_addCommand (menu, L"Draw to picture window:", GuiMenu_INSENSITIVE, menu_cb_drawVisiblePulses /* dummy */); EditorMenu_addCommand (menu, L"Draw visible pulses...", 0, menu_cb_drawVisiblePulses); } void TimeSoundAnalysisEditor_computeSpectrogram (TimeSoundAnalysisEditor me) { autoMelderProgressOff progress; if (my spectrogram.show && my endWindow - my startWindow <= my longestAnalysis && (my spectrogram.data == NULL || my spectrogram.data -> xmin != my startWindow || my spectrogram.data -> xmax != my endWindow)) { double margin = my spectrogram.windowShape == kSound_to_Spectrogram_windowShape_GAUSSIAN ? my spectrogram.windowLength : 0.5 * my spectrogram.windowLength; forget (my spectrogram.data); try { autoSound sound = extractSound (me, my startWindow - margin, my endWindow + margin); my spectrogram.data = Sound_to_Spectrogram (sound.peek(), my spectrogram.windowLength, my spectrogram.viewTo, (my endWindow - my startWindow) / my spectrogram.timeSteps, my spectrogram.viewTo / my spectrogram.frequencySteps, my spectrogram.windowShape, 8.0, 8.0); my spectrogram.data -> xmin = my startWindow; my spectrogram.data -> xmax = my endWindow; } catch (MelderError) { Melder_clearError (); } } } static void computePitch_inside (TimeSoundAnalysisEditor me) { double margin = my pitch.veryAccurate ? 3.0 / my pitch.floor : 1.5 / my pitch.floor; forget (my pitch.data); try { autoSound sound = extractSound (me, my startWindow - margin, my endWindow + margin); double pitchTimeStep = my timeStepStrategy == kTimeSoundAnalysisEditor_timeStepStrategy_FIXED ? my fixedTimeStep : my timeStepStrategy == kTimeSoundAnalysisEditor_timeStepStrategy_VIEW_DEPENDENT ? (my endWindow - my startWindow) / my numberOfTimeStepsPerView : 0.0; // the default: determined by pitch floor my pitch.data = Sound_to_Pitch_any (sound.peek(), pitchTimeStep, my pitch.floor, my pitch.method == kTimeSoundAnalysisEditor_pitch_analysisMethod_AUTOCORRELATION ? 3.0 : 1.0, my pitch.maximumNumberOfCandidates, (my pitch.method - 1) * 2 + my pitch.veryAccurate, my pitch.silenceThreshold, my pitch.voicingThreshold, my pitch.octaveCost, my pitch.octaveJumpCost, my pitch.voicedUnvoicedCost, my pitch.ceiling); my pitch.data -> xmin = my startWindow; my pitch.data -> xmax = my endWindow; } catch (MelderError) { Melder_clearError (); } } void TimeSoundAnalysisEditor_computePitch (TimeSoundAnalysisEditor me) { autoMelderProgressOff progress; if (my pitch.show && my endWindow - my startWindow <= my longestAnalysis && (my pitch.data == NULL || my pitch.data -> xmin != my startWindow || my pitch.data -> xmax != my endWindow)) { computePitch_inside (me); } } void TimeSoundAnalysisEditor_computeIntensity (TimeSoundAnalysisEditor me) { autoMelderProgressOff progress; if (my intensity.show && my endWindow - my startWindow <= my longestAnalysis && (my intensity.data == NULL || my intensity.data -> xmin != my startWindow || my intensity.data -> xmax != my endWindow)) { double margin = 3.2 / my pitch.floor; forget (my intensity.data); try { autoSound sound = extractSound (me, my startWindow - margin, my endWindow + margin); my intensity.data = Sound_to_Intensity (sound.peek(), my pitch.floor, my endWindow - my startWindow > my longestAnalysis ? (my endWindow - my startWindow) / 100 : 0.0, my intensity.subtractMeanPressure); my intensity.data -> xmin = my startWindow; my intensity.data -> xmax = my endWindow; } catch (MelderError) { Melder_clearError (); } } } void TimeSoundAnalysisEditor_computeFormants (TimeSoundAnalysisEditor me) { autoMelderProgressOff progress; if (my formant.show && my endWindow - my startWindow <= my longestAnalysis && (my formant.data == NULL || my formant.data -> xmin != my startWindow || my formant.data -> xmax != my endWindow)) { double margin = my formant.windowLength; forget (my formant.data); try { autoSound sound = my endWindow - my startWindow > my longestAnalysis ? extractSound (me, 0.5 * (my startWindow + my endWindow - my longestAnalysis) - margin, 0.5 * (my startWindow + my endWindow + my longestAnalysis) + margin) : extractSound (me, my startWindow - margin, my endWindow + margin); double formantTimeStep = my timeStepStrategy == kTimeSoundAnalysisEditor_timeStepStrategy_FIXED ? my fixedTimeStep : my timeStepStrategy == kTimeSoundAnalysisEditor_timeStepStrategy_VIEW_DEPENDENT ? (my endWindow - my startWindow) / my numberOfTimeStepsPerView : 0.0; // the default: determined by analysis window length my formant.data = Sound_to_Formant_any (sound.peek(), formantTimeStep, my formant.numberOfPoles, my formant.maximumFormant, my formant.windowLength, my formant.method, my formant.preemphasisFrom, 50.0); my formant.data -> xmin = my startWindow; my formant.data -> xmax = my endWindow; } catch (MelderError) { Melder_clearError (); } } } void TimeSoundAnalysisEditor_computePulses (TimeSoundAnalysisEditor me) { autoMelderProgressOff progress; if (my pulses.show && my endWindow - my startWindow <= my longestAnalysis && (my pulses.data == NULL || my pulses.data -> xmin != my startWindow || my pulses.data -> xmax != my endWindow)) { forget (my pulses.data); if (my pitch.data == NULL || my pitch.data -> xmin != my startWindow || my pitch.data -> xmax != my endWindow) { computePitch_inside (me); } if (my pitch.data != NULL) { try { autoSound sound = extractSound (me, my startWindow, my endWindow); my pulses.data = Sound_Pitch_to_PointProcess_cc (sound.peek(), my pitch.data); } catch (MelderError) { Melder_clearError (); } } } } void structTimeSoundAnalysisEditor :: v_draw_analysis () { /* * pitch.data may not exist yet (if shown at all, it may be going to be created in TimeSoundAnalysisEditor_computePitch (), * and even if if that fails we should see the pitch settings. So we use a dummy object. */ double pitchFloor_hidden = Function_convertStandardToSpecialUnit (Thing_dummyObject (Pitch), pitch.floor, Pitch_LEVEL_FREQUENCY, pitch.unit); double pitchCeiling_hidden = Function_convertStandardToSpecialUnit (Thing_dummyObject (Pitch), pitch.ceiling, Pitch_LEVEL_FREQUENCY, pitch.unit); double pitchFloor_overt = Function_convertToNonlogarithmic (Thing_dummyObject (Pitch), pitchFloor_hidden, Pitch_LEVEL_FREQUENCY, pitch.unit); double pitchCeiling_overt = Function_convertToNonlogarithmic (Thing_dummyObject (Pitch), pitchCeiling_hidden, Pitch_LEVEL_FREQUENCY, pitch.unit); double pitchViewFrom_overt = pitch.viewFrom < pitch.viewTo ? pitch.viewFrom : pitchFloor_overt; double pitchViewTo_overt = pitch.viewFrom < pitch.viewTo ? pitch.viewTo : pitchCeiling_overt; double pitchViewFrom_hidden = Function_isUnitLogarithmic (Thing_dummyObject (Pitch), Pitch_LEVEL_FREQUENCY, pitch.unit) ? log10 (pitchViewFrom_overt) : pitchViewFrom_overt; double pitchViewTo_hidden = Function_isUnitLogarithmic (Thing_dummyObject (Pitch), Pitch_LEVEL_FREQUENCY, pitch.unit) ? log10 (pitchViewTo_overt) : pitchViewTo_overt; Graphics_setWindow (graphics, 0.0, 1.0, 0.0, 1.0); Graphics_setColour (graphics, Graphics_WHITE); Graphics_fillRectangle (graphics, 0.0, 1.0, 0.0, 1.0); Graphics_setColour (graphics, Graphics_BLACK); Graphics_rectangle (graphics, 0.0, 1.0, 0.0, 1.0); if (endWindow - startWindow > longestAnalysis) { Graphics_setFont (graphics, kGraphics_font_HELVETICA); Graphics_setFontSize (graphics, 10); Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_HALF); Graphics_text3 (graphics, 0.5, 0.67, L"(To see the analyses, zoom in to at most ", Melder_half (longestAnalysis), L" seconds,"); Graphics_text (graphics, 0.5, 0.33, L"or raise the \"longest analysis\" setting with \"Show analyses\" in the View menu.)"); Graphics_setFontSize (graphics, 12); return; } TimeSoundAnalysisEditor_computeSpectrogram (this); if (spectrogram.show && spectrogram.data != NULL) { Spectrogram_paintInside (spectrogram.data, graphics, startWindow, endWindow, spectrogram.viewFrom, spectrogram.viewTo, spectrogram.maximum, spectrogram.autoscaling, spectrogram.dynamicRange, spectrogram.preemphasis, spectrogram.dynamicCompression); } TimeSoundAnalysisEditor_computePitch (this); if (pitch.show && pitch.data != NULL) { double periodsPerAnalysisWindow = pitch.method == kTimeSoundAnalysisEditor_pitch_analysisMethod_AUTOCORRELATION ? 3.0 : 1.0; double greatestNonUndersamplingTimeStep = 0.5 * periodsPerAnalysisWindow / pitch.floor; double defaultTimeStep = 0.5 * greatestNonUndersamplingTimeStep; double timeStep = timeStepStrategy == kTimeSoundAnalysisEditor_timeStepStrategy_FIXED ? fixedTimeStep : timeStepStrategy == kTimeSoundAnalysisEditor_timeStepStrategy_VIEW_DEPENDENT ? (endWindow - startWindow) / numberOfTimeStepsPerView : defaultTimeStep; int undersampled = timeStep > greatestNonUndersamplingTimeStep; long numberOfVisiblePitchPoints = (long) ((endWindow - startWindow) / timeStep); Graphics_setColour (graphics, Graphics_CYAN); Graphics_setLineWidth (graphics, 3.0); if ((pitch.drawingMethod == kTimeSoundAnalysisEditor_pitch_drawingMethod_AUTOMATIC && (undersampled || numberOfVisiblePitchPoints < 101)) || pitch.drawingMethod == kTimeSoundAnalysisEditor_pitch_drawingMethod_SPECKLE) { Pitch_drawInside (pitch.data, graphics, startWindow, endWindow, pitchViewFrom_overt, pitchViewTo_overt, 2, pitch.unit); } if ((pitch.drawingMethod == kTimeSoundAnalysisEditor_pitch_drawingMethod_AUTOMATIC && ! undersampled) || pitch.drawingMethod == kTimeSoundAnalysisEditor_pitch_drawingMethod_CURVE) { Pitch_drawInside (pitch.data, graphics, startWindow, endWindow, pitchViewFrom_overt, pitchViewTo_overt, FALSE, pitch.unit); } Graphics_setColour (graphics, Graphics_BLUE); Graphics_setLineWidth (graphics, 1.0); if ((pitch.drawingMethod == kTimeSoundAnalysisEditor_pitch_drawingMethod_AUTOMATIC && (undersampled || numberOfVisiblePitchPoints < 101)) || pitch.drawingMethod == kTimeSoundAnalysisEditor_pitch_drawingMethod_SPECKLE) { Pitch_drawInside (pitch.data, graphics, startWindow, endWindow, pitchViewFrom_overt, pitchViewTo_overt, 1, pitch.unit); } if ((pitch.drawingMethod == kTimeSoundAnalysisEditor_pitch_drawingMethod_AUTOMATIC && ! undersampled) || pitch.drawingMethod == kTimeSoundAnalysisEditor_pitch_drawingMethod_CURVE) { Pitch_drawInside (pitch.data, graphics, startWindow, endWindow, pitchViewFrom_overt, pitchViewTo_overt, FALSE, pitch.unit); } Graphics_setColour (graphics, Graphics_BLACK); } TimeSoundAnalysisEditor_computeIntensity (this); if (intensity.show && intensity.data != NULL) { Graphics_setColour (graphics, spectrogram.show ? Graphics_YELLOW : Graphics_LIME); Graphics_setLineWidth (graphics, spectrogram.show ? 1.0 : 3.0); Intensity_drawInside (intensity.data, graphics, startWindow, endWindow, intensity.viewFrom, intensity.viewTo); Graphics_setLineWidth (graphics, 1.0); Graphics_setColour (graphics, Graphics_BLACK); } TimeSoundAnalysisEditor_computeFormants (this); if (formant.show && formant.data != NULL) { Graphics_setColour (graphics, Graphics_RED); Formant_drawSpeckles_inside (formant.data, graphics, startWindow, endWindow, spectrogram.viewFrom, spectrogram.viewTo, formant.dynamicRange, formant.dotSize); Graphics_setColour (graphics, Graphics_BLACK); } /* * Draw vertical scales. */ if (pitch.show) { double pitchCursor_overt = NUMundefined, pitchCursor_hidden = NUMundefined; Graphics_setWindow (graphics, startWindow, endWindow, pitchViewFrom_hidden, pitchViewTo_hidden); Graphics_setColour (graphics, Graphics_BLUE); if (pitch.data) { if (startSelection == endSelection) pitchCursor_hidden = Pitch_getValueAtTime (pitch.data, startSelection, pitch.unit, 1); else pitchCursor_hidden = Pitch_getMean (pitch.data, startSelection, endSelection, pitch.unit); pitchCursor_overt = Function_convertToNonlogarithmic (pitch.data, pitchCursor_hidden, Pitch_LEVEL_FREQUENCY, pitch.unit); if (NUMdefined (pitchCursor_hidden)) { Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_HALF); Graphics_text3 (graphics, endWindow, pitchCursor_hidden, Melder_float (Melder_half (pitchCursor_overt)), L" ", Function_getUnitText (pitch.data, Pitch_LEVEL_FREQUENCY, pitch.unit, Function_UNIT_TEXT_SHORT | Function_UNIT_TEXT_GRAPHICAL)); } if (! NUMdefined (pitchCursor_hidden) || Graphics_dyWCtoMM (graphics, pitchCursor_hidden - pitchViewFrom_hidden) > 5.0) { Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_BOTTOM); Graphics_text3 (graphics, endWindow, pitchViewFrom_hidden - Graphics_dyMMtoWC (graphics, 0.5), Melder_float (Melder_half (pitchViewFrom_overt)), L" ", Function_getUnitText (pitch.data, Pitch_LEVEL_FREQUENCY, pitch.unit, Function_UNIT_TEXT_SHORT | Function_UNIT_TEXT_GRAPHICAL)); } if (! NUMdefined (pitchCursor_hidden) || Graphics_dyWCtoMM (graphics, pitchViewTo_hidden - pitchCursor_hidden) > 5.0) { Graphics_setTextAlignment (graphics, Graphics_LEFT, Graphics_TOP); Graphics_text3 (graphics, endWindow, pitchViewTo_hidden, Melder_float (Melder_half (pitchViewTo_overt)), L" ", Function_getUnitText (pitch.data, Pitch_LEVEL_FREQUENCY, pitch.unit, Function_UNIT_TEXT_SHORT | Function_UNIT_TEXT_GRAPHICAL)); } } else { Graphics_setTextAlignment (graphics, Graphics_CENTRE, Graphics_HALF); Graphics_setFontSize (graphics, 10); Graphics_text (graphics, 0.5 * (startWindow + endWindow), 0.5 * (pitchViewFrom_hidden + pitchViewTo_hidden), L"(Cannot show pitch contour. Zoom out or change bottom of pitch range in pitch settings.)"); Graphics_setFontSize (graphics, 12); } Graphics_setColour (graphics, Graphics_BLACK); } if (intensity.show) { double intensityCursor = NUMundefined; int intensityCursorVisible; Graphics_Colour textColour; int alignment; double y; if (! pitch.show) textColour = Graphics_GREEN, alignment = Graphics_LEFT, y = endWindow; else if (! spectrogram.show && ! formant.show) textColour = Graphics_GREEN, alignment = Graphics_RIGHT, y = startWindow; else textColour = spectrogram.show ? Graphics_LIME : Graphics_GREEN, alignment = Graphics_RIGHT, y = endWindow; Graphics_setWindow (graphics, startWindow, endWindow, intensity.viewFrom, intensity.viewTo); if (intensity.data) { if (startSelection == endSelection) { intensityCursor = Vector_getValueAtX (intensity.data, startSelection, Vector_CHANNEL_1, Vector_VALUE_INTERPOLATION_LINEAR); } else { intensityCursor = Intensity_getAverage (intensity.data, startSelection, endSelection, intensity.averagingMethod); } } Graphics_setColour (graphics, textColour); intensityCursorVisible = NUMdefined (intensityCursor) && intensityCursor > intensity.viewFrom && intensityCursor < intensity.viewTo; if (intensityCursorVisible) { static const wchar_t *methodString [] = { L" (.5)", L" (\\muE)", L" (\\muS)", L" (\\mu)" }; Graphics_setTextAlignment (graphics, alignment, Graphics_HALF); Graphics_text3 (graphics, y, intensityCursor, Melder_float (Melder_half (intensityCursor)), L" dB", startSelection == endSelection ? L"" : methodString [intensity.averagingMethod]); } if (! intensityCursorVisible || Graphics_dyWCtoMM (graphics, intensityCursor - intensity.viewFrom) > 5.0) { Graphics_setTextAlignment (graphics, alignment, Graphics_BOTTOM); Graphics_text2 (graphics, y, intensity.viewFrom - Graphics_dyMMtoWC (graphics, 0.5), Melder_float (Melder_half (intensity.viewFrom)), L" dB"); } if (! intensityCursorVisible || Graphics_dyWCtoMM (graphics, intensity.viewTo - intensityCursor) > 5.0) { Graphics_setTextAlignment (graphics, alignment, Graphics_TOP); Graphics_text2 (graphics, y, intensity.viewTo, Melder_float (Melder_half (intensity.viewTo)), L" dB"); } Graphics_setColour (graphics, Graphics_BLACK); } if (spectrogram.show || formant.show) { static MelderString text = { 0 }; int frequencyCursorVisible = spectrogram.cursor > spectrogram.viewFrom && spectrogram.cursor < spectrogram.viewTo; Graphics_setWindow (graphics, startWindow, endWindow, spectrogram.viewFrom, spectrogram.viewTo); /* * Range marks. */ Graphics_setLineType (graphics, Graphics_DRAWN); Graphics_setColour (graphics, Graphics_BLACK); if (! frequencyCursorVisible || Graphics_dyWCtoMM (graphics, spectrogram.cursor - spectrogram.viewFrom) > 5.0) { MelderString_empty (& text); MelderString_append (& text, Melder_half (spectrogram.viewFrom), L" Hz"); Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_BOTTOM); Graphics_text (graphics, startWindow, spectrogram.viewFrom - Graphics_dyMMtoWC (graphics, 0.5), Melder_float (text.string)); } if (! frequencyCursorVisible || Graphics_dyWCtoMM (graphics, spectrogram.viewTo - spectrogram.cursor) > 5.0) { MelderString_empty (& text); MelderString_append (& text, Melder_half (spectrogram.viewTo), L" Hz"); Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_TOP); Graphics_text (graphics, startWindow, spectrogram.viewTo, Melder_float (text.string)); } /* * Cursor lines. */ Graphics_setLineType (graphics, Graphics_DOTTED); Graphics_setColour (graphics, Graphics_RED); if (frequencyCursorVisible) { double x = startWindow, y = spectrogram.cursor; Graphics_setTextAlignment (graphics, Graphics_RIGHT, Graphics_HALF); Graphics_text2 (graphics, x, y, Melder_float (Melder_half (y)), L" Hz"); Graphics_line (graphics, x, y, endWindow, y); } /* if (startSelection >= startWindow && startSelection <= endWindow) Graphics_line (graphics, startSelection, spectrogram.viewFrom, startSelection, spectrogram.viewTo); if (endSelection > startWindow && endSelection < endWindow && endSelection != startSelection) Graphics_line (graphics, endSelection, spectrogram.viewFrom, endSelection, spectrogram.viewTo);*/ /* * Cadre. */ Graphics_setLineType (graphics, Graphics_DRAWN); Graphics_setColour (graphics, Graphics_BLACK); Graphics_rectangle (graphics, startWindow, endWindow, spectrogram.viewFrom, spectrogram.viewTo); } } void structTimeSoundAnalysisEditor :: v_draw_analysis_pulses () { TimeSoundAnalysisEditor_computePulses (this); if (pulses.show && endWindow - startWindow <= longestAnalysis && pulses.data != NULL) { PointProcess point = pulses.data; Graphics_setWindow (graphics, startWindow, endWindow, -1.0, 1.0); Graphics_setColour (graphics, Graphics_BLUE); if (point -> nt < 2000) for (long i = 1; i <= point -> nt; i ++) { double t = point -> t [i]; if (t >= startWindow && t <= endWindow) Graphics_line (graphics, t, -0.9, t, 0.9); } Graphics_setColour (graphics, Graphics_BLACK); } } int structTimeSoundAnalysisEditor :: v_click (double xbegin, double ybegin, bool shiftKeyPressed) { if (pitch.show) { //Melder_warning (xbegin, L" ", ybegin); if (xbegin >= endWindow && ybegin > 0.48 && ybegin <= 0.50) { pitch.ceiling *= 1.26; forget (pitch.data); forget (intensity.data); forget (pulses.data); return 1; } if (xbegin >= endWindow && ybegin > 0.46 && ybegin <= 0.48) { pitch.ceiling /= 1.26; forget (pitch.data); forget (intensity.data); forget (pulses.data); return 1; } } return TimeSoundAnalysisEditor_Parent :: v_click (xbegin, ybegin, shiftKeyPressed); } void TimeSoundAnalysisEditor_init (TimeSoundAnalysisEditor me, GuiObject parent, const wchar *title, Function data, Sampled sound, bool ownSound) { TimeSoundEditor_init (me, parent, title, data, sound, ownSound); if (my v_hasAnalysis ()) { my longestAnalysis = preferences.longestAnalysis; if (preferences.log[0].toLogFile == FALSE && preferences.log[0].toInfoWindow == FALSE) preferences.log[0].toLogFile = TRUE, preferences.log[0].toInfoWindow = TRUE; if (preferences.log[1].toLogFile == FALSE && preferences.log[1].toInfoWindow == FALSE) preferences.log[1].toLogFile = TRUE, preferences.log[1].toInfoWindow = TRUE; my timeStepStrategy = preferences.timeStepStrategy; my fixedTimeStep = preferences.fixedTimeStep; my numberOfTimeStepsPerView = preferences.numberOfTimeStepsPerView; my spectrogram = preferences.spectrogram; my pitch = preferences.pitch; my intensity = preferences.intensity; my formant = preferences.formant; my pulses = preferences.pulses; } } /* End of file TimeSoundAnalysisEditor.cpp */ sources_5316/fon/Sound_and_Spectrogram_enums.h0000644000176700017670000000376610726076566020400 0ustar paulpaul/* Sound_and_Spectrogram_enums.h * * Copyright (C) 1992-2007 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2007/12/06 */ enums_begin (kSound_to_Spectrogram_method, 1) enums_add (kSound_to_Spectrogram_method, 1, FOURIER, L"Fourier") enums_end (kSound_to_Spectrogram_method, 1, FOURIER) enums_begin (kSound_to_Spectrogram_windowShape, 0) enums_add (kSound_to_Spectrogram_windowShape, 0, SQUARE, L"square (rectangular)") enums_add (kSound_to_Spectrogram_windowShape, 1, HAMMING, L"Hamming (raised sine-squared)") enums_add (kSound_to_Spectrogram_windowShape, 2, BARTLETT, L"Bartlett (triangular)") enums_add (kSound_to_Spectrogram_windowShape, 3, WELCH, L"Welch (parabolic)") enums_add (kSound_to_Spectrogram_windowShape, 4, HANNING, L"Hanning (sine-squared)") enums_add (kSound_to_Spectrogram_windowShape, 5, GAUSSIAN, L"Gaussian") /* For reading old preferences files: */ enums_alt (kSound_to_Spectrogram_windowShape, SQUARE, L"0") enums_alt (kSound_to_Spectrogram_windowShape, HAMMING, L"1") enums_alt (kSound_to_Spectrogram_windowShape, BARTLETT, L"2") enums_alt (kSound_to_Spectrogram_windowShape, WELCH, L"3") enums_alt (kSound_to_Spectrogram_windowShape, HANNING, L"4") enums_alt (kSound_to_Spectrogram_windowShape, GAUSSIAN, L"5") enums_end (kSound_to_Spectrogram_windowShape, 5, GAUSSIAN) /* End of Sound_and_Spectrogram_enums.h */ sources_5316/fon/Sound_to_PointProcess.cpp0000644000176700017670000001142311605364661017524 0ustar paulpaul/* Sound_to_PointProcess.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2003/02/26 Sound_to_PointProcess_peaks * pb 2004/07/11 default time steps in Sound_to_Pitch * pb 2007/01/28 made compatible with stereo sounds * pb 2008/01/19 double * pb 2011/03/09 C++ */ #include "Sound_to_PointProcess.h" #include "Sound_to_Pitch.h" #include "Pitch_to_PointProcess.h" PointProcess Sound_to_PointProcess_extrema (Sound me, long channel, int interpolation, bool includeMaxima, bool includeMinima) { try { /* * Pass 1: count the extrema. There may be a maximum and minimum in the same interval! */ long numberOfMaxima = 0; long numberOfMinima = 0; double *y = my z [channel]; for (long i = 2; i <= my nx - 1; i ++) { if (includeMaxima && y [i] > y [i - 1] && y [i] >= y [i + 1]) numberOfMaxima ++; if (includeMinima && y [i] <= y [i - 1] && y [i] < y [i + 1]) numberOfMinima ++; } /* * Create the empty result. */ autoPointProcess thee = PointProcess_create (my xmin, my xmax, numberOfMaxima + numberOfMinima); /* * Pass 2: compute and register the extrema. */ for (long i = 2; i <= my nx - 1; i ++) { double time, value, i_real; if (includeMaxima && y [i] > y [i - 1] && y [i] >= y [i + 1]) { value = NUMimproveMaximum (y, my nx, i, interpolation, & i_real); time = my x1 + (i_real - 1.0) * my dx; PointProcess_addPoint (thee.peek(), time); } if (includeMinima && y [i] <= y [i - 1] && y [i] < y [i + 1]) { value = NUMimproveMinimum (y, my nx, i, interpolation, & i_real); time = my x1 + (i_real - 1.0) * my dx; PointProcess_addPoint (thee.peek(), time); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": extrema not computed."); } } PointProcess Sound_to_PointProcess_maxima (Sound me, long channel, int interpolation) { return Sound_to_PointProcess_extrema (me, channel, interpolation, true, false); } PointProcess Sound_to_PointProcess_minima (Sound me, long channel, int interpolation) { return Sound_to_PointProcess_extrema (me, channel, interpolation, false, true); } PointProcess Sound_to_PointProcess_allExtrema (Sound me, long channel, int interpolation) { return Sound_to_PointProcess_extrema (me, channel, interpolation, true, true); } PointProcess Sound_to_PointProcess_zeroes (Sound me, long channel, bool includeRaisers, bool includeFallers) { try { /* * Pass 1: count the zeroes. */ long numberOfRaisers = 0; long numberOfFallers = 0; double *y = my z [channel]; for (long i = 2; i <= my nx; i ++) { if (includeRaisers && y [i - 1] < 0.0 && y [i] >= 0.0) numberOfRaisers ++; if (includeFallers && y [i - 1] >= 0.0 && y [i] < 0.0) numberOfFallers ++; } /* * Create the empty result. */ autoPointProcess thee = PointProcess_create (my xmin, my xmax, numberOfRaisers + numberOfFallers); /* * Pass 2: compute and register the zeroes. */ for (long i = 2; i <= my nx; i ++) { if ((includeRaisers && y [i - 1] < 0.0 && y [i] >= 0.0) || (includeFallers && y [i - 1] >= 0.0 && y [i] < 0.0)) { double time = Sampled_indexToX (me, i - 1) + my dx * y [i - 1] / (y [i - 1] - y [i]); // linear PointProcess_addPoint (thee.peek(), time); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": zeroes not computed."); } } PointProcess Sound_to_PointProcess_periodic_cc (Sound me, double fmin, double fmax) { try { autoPitch pitch = Sound_to_Pitch (me, 0.0, fmin, fmax); autoPointProcess thee = Sound_Pitch_to_PointProcess_cc (me, pitch.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": periodic pulses (cc) not computed."); } } PointProcess Sound_to_PointProcess_periodic_peaks (Sound me, double fmin, double fmax, bool includeMaxima, bool includeMinima) { try { autoPitch pitch = Sound_to_Pitch (me, 0.0, fmin, fmax); autoPointProcess thee = Sound_Pitch_to_PointProcess_peaks (me, pitch.peek(), includeMaxima, includeMinima); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": periodic pulses (peaks) not computed."); } } /* End of file Sound_to_PointProcess.cpp */ sources_5316/fon/Pitch_to_Sound.cpp0000644000176700017670000000663411605364661016153 0ustar paulpaul/* Pitch_to_Sound.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ /* * pb 2002/07/16 GPL * pb 2005/02/09 Pitch_to_Sound_sine * pb 2007/02/25 changed default sampling frequency to 44100 Hz * pb 2008/01/19 double * pb 2011/06/05 C++ */ #include "Pitch_to_PointProcess.h" #include "PointProcess_and_Sound.h" #include "Pitch_to_Sound.h" #include "PitchTier_to_Sound.h" #include "Pitch_to_PitchTier.h" Sound Pitch_to_Sound (Pitch me, double tmin, double tmax, int hum) { static double formant [1 + 6] = { 0, 600, 1400, 2400, 3400, 4500, 5500 }; static double bandwidth [1 + 6] = { 0, 50, 100, 200, 300, 400, 500 }; try { autoPointProcess point = Pitch_to_PointProcess (me); autoSound sound = PointProcess_to_Sound_pulseTrain (point.peek(), 44100, 0.7, 0.05, 30); if (hum) { Sound_filterWithFormants (sound.peek(), tmin, tmax, 6, formant, bandwidth); therror } return sound.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Sound."); } } void Pitch_play (Pitch me, double tmin, double tmax) { try { autoSound sound = Pitch_to_Sound (me, tmin, tmax, FALSE); if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } // autowindowing Sound_playPart (sound.peek(), tmin, tmax, NULL, NULL); } catch (MelderError) { Melder_throw (me, ": not played."); } } void Pitch_hum (Pitch me, double tmin, double tmax) { try { autoSound sound = Pitch_to_Sound (me, tmin, tmax, TRUE); if (tmax <= tmin) { tmin = my xmin; tmax = my xmax; } // autowindowing Sound_playPart (sound.peek(), tmin, tmax, NULL, NULL); } catch (MelderError) { Melder_throw (me, ": not played."); } } Sound Pitch_to_Sound_sine (Pitch me, double tmin, double tmax, double samplingFrequency, int roundToNearestZeroCrossings) { try { autoPitchTier tier = Pitch_to_PitchTier (me); autoSound sound = PitchTier_to_Sound_sine (tier.peek(), tmin, tmax, samplingFrequency); long iframe = 1; double unvoicedMin = my xmin; double unvoicedMax = my x1 + (iframe - 1.5) * my dx; for (;;) { while (! Pitch_isVoiced_i (me, iframe)) { unvoicedMax = my x1 + (iframe - 0.5) * my dx; if (++ iframe > my nx) break; } if (unvoicedMax > unvoicedMin) { Sound_setZero (sound.peek(), unvoicedMin, unvoicedMax, roundToNearestZeroCrossings); } if (iframe > my nx) break; while (Pitch_isVoiced_i (me, iframe)) { unvoicedMin = my x1 + (iframe - 0.5) * my dx; if (++ iframe > my nx) break; } if (iframe > my nx) break; } unvoicedMax = my xmax; if (unvoicedMax > unvoicedMin) { Sound_setZero (sound.peek(), unvoicedMin, unvoicedMax, roundToNearestZeroCrossings); } return sound.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to Sound (sine)."); } } /* End of file Pitch_to_Sound.cpp */ sources_5316/fon/TextGrid.cpp0000644000176700017670000017060011727632252014756 0ustar paulpaul/* TextGrid.cpp * * Copyright (C) 1992-2012 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "TextGrid.h" #include "longchar.h" #include "oo_DESTROY.h" #include "TextGrid_def.h" #include "oo_COPY.h" #include "TextGrid_def.h" #include "oo_EQUAL.h" #include "TextGrid_def.h" #include "oo_CAN_WRITE_AS_ENCODING.h" #include "TextGrid_def.h" #include "oo_WRITE_TEXT.h" #include "TextGrid_def.h" #include "oo_READ_TEXT.h" #include "TextGrid_def.h" #include "oo_WRITE_BINARY.h" #include "TextGrid_def.h" #include "oo_READ_BINARY.h" #include "TextGrid_def.h" #include "oo_DESCRIPTION.h" #include "TextGrid_def.h" #include "TextGrid_extensions.h" Thing_implement (TextPoint, AnyPoint, 0); TextPoint TextPoint_create (double time, const wchar *mark) { try { autoTextPoint me = Thing_new (TextPoint); my number = time; my mark = Melder_wcsdup (mark); return me.transfer(); } catch (MelderError) { Melder_throw ("Text point not created."); } } void TextPoint_setText (TextPoint me, const wchar *text) { try { /* * Be fast if the string pointers are equal. */ if (text == my mark) return; /* * Create a temporary variable (i.e. a temporary pointer to the final string), * in order that 'my text' does not change in case of error. */ autostring newText = Melder_wcsdup (text); Melder_free (my mark); my mark = newText.transfer(); } catch (MelderError) { Melder_throw (me, ": text not set."); } } Thing_implement (TextInterval, Function, 0); TextInterval TextInterval_create (double tmin, double tmax, const wchar_t *text) { try { autoTextInterval me = Thing_new (TextInterval); my xmin = tmin; my xmax = tmax; my text = Melder_wcsdup (text); return me.transfer(); } catch (MelderError) { Melder_throw ("Text interval not created."); } } void TextInterval_setText (TextInterval me, const wchar_t *text) { try { /* * Be fast if the string pointers are equal. */ if (text == my text) return; /* * Create without change. */ autostring newText = Melder_wcsdup (text); /* * Change without error. */ Melder_free (my text); my text = newText.transfer(); } catch (MelderError) { Melder_throw ("Text interval: text not set."); } } Thing_implement (TextTier, Function, 0); void structTextTier :: v_shiftX (double xfrom, double xto) { TextTier_Parent :: v_shiftX (xfrom, xto); for (long i = 1; i <= points -> size; i ++) { TextPoint point = (TextPoint) points -> item [i]; NUMshift (& point -> number, xfrom, xto); } } void structTextTier :: v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto) { TextTier_Parent :: v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); for (long i = 1; i <= points -> size; i ++) { TextPoint point = (TextPoint) points -> item [i]; NUMscale (& point -> number, xminfrom, xmaxfrom, xminto, xmaxto); } } TextTier TextTier_create (double tmin, double tmax) { try { autoTextTier me = Thing_new (TextTier); my points = SortedSetOfDouble_create (); therror my xmin = tmin; my xmax = tmax; return me.transfer(); } catch (MelderError) { Melder_throw ("Point tier not created."); } } void TextTier_addPoint (TextTier me, double time, const wchar_t *mark) { try { Collection_addItem (my points, TextPoint_create (time, mark)); } catch (MelderError) { Melder_throw ("Point tier: point not added."); } } Thing_implement (IntervalTier, Function, 0); void structIntervalTier :: v_shiftX (double xfrom, double xto) { IntervalTier_Parent :: v_shiftX (xfrom, xto); for (long i = 1; i <= intervals -> size; i ++) { TextInterval interval = (TextInterval) intervals -> item [i]; interval -> v_shiftX (xfrom, xto); } } void structIntervalTier :: v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto) { IntervalTier_Parent :: v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); for (long i = 1; i <= intervals -> size; i ++) { TextInterval interval = (TextInterval) intervals -> item [i]; interval -> v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); } } IntervalTier IntervalTier_create (double tmin, double tmax) { try { autoIntervalTier me = Thing_new (IntervalTier); my intervals = SortedSetOfDouble_create (); my xmin = tmin; my xmax = tmax; autoTextInterval interval = TextInterval_create (tmin, tmax, NULL); Collection_addItem (my intervals, interval.transfer()); return me.transfer(); } catch (MelderError) { Melder_throw ("Interval tier not created."); } } long IntervalTier_timeToLowIndex (IntervalTier me, double t) { for (long i = 1; i <= my intervals -> size; i ++) { TextInterval interval = (TextInterval) my intervals -> item [i]; if (t >= interval -> xmin && t < interval -> xmax) return i; } return 0; // empty tier or very small or large t } long IntervalTier_timeToIndex (IntervalTier me, double t) { return t == my xmax ? my intervals -> size : IntervalTier_timeToLowIndex (me, t); } long IntervalTier_timeToHighIndex (IntervalTier me, double t) { for (long i = 1; i <= my intervals -> size; i ++) { TextInterval interval = (TextInterval) my intervals -> item [i]; if (t > interval -> xmin && t <= interval -> xmax) return i; } return 0; // empty tier or very small or large t } long IntervalTier_hasTime (IntervalTier me, double t) { for (long iinterval = 1; iinterval <= my intervals -> size; iinterval ++) { TextInterval interval = (TextInterval) my intervals -> item [iinterval]; if (interval -> xmin == t || (iinterval == my intervals -> size && interval -> xmax == t)) { return iinterval; // time found } } return 0; // time not found } long IntervalTier_hasBoundary (IntervalTier me, double t) { for (long iinterval = 2; iinterval <= my intervals -> size; iinterval ++) { TextInterval interval = (TextInterval) my intervals -> item [iinterval]; if (interval -> xmin == t) { return iinterval; // boundary found } } return 0; // boundary not found } void structTextGrid :: v_info () { long ntier = tiers -> size; long numberOfIntervalTiers = 0, numberOfPointTiers = 0, numberOfIntervals = 0, numberOfPoints = 0; structData :: v_info (); for (long itier = 1; itier <= ntier; itier ++) { Function anyTier = (Function) tiers -> item [itier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; numberOfIntervalTiers += 1; numberOfIntervals += tier -> intervals -> size; } else { TextTier tier = (TextTier) anyTier; numberOfPointTiers += 1; numberOfPoints += tier -> points -> size; } } MelderInfo_writeLine2 (L"Number of interval tiers: ", Melder_integer (numberOfIntervalTiers)); MelderInfo_writeLine2 (L"Number of point tiers: ", Melder_integer (numberOfPointTiers)); MelderInfo_writeLine2 (L"Number of intervals: ", Melder_integer (numberOfIntervals)); MelderInfo_writeLine2 (L"Number of points: ", Melder_integer (numberOfPoints)); } void structTextGrid :: v_shiftX (double xfrom, double xto) { TextGrid_Parent :: v_shiftX (xfrom, xto); for (long i = 1; i <= tiers -> size; i ++) { Function tier = (Function) tiers -> item [i]; tier -> v_shiftX (xfrom, xto); } } void structTextGrid :: v_scaleX (double xminfrom, double xmaxfrom, double xminto, double xmaxto) { TextGrid_Parent :: v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); for (long i = 1; i <= tiers -> size; i ++) { Function tier = (Function) tiers -> item [i]; tier -> v_scaleX (xminfrom, xmaxfrom, xminto, xmaxto); } } Thing_implement (TextGrid, Function, 0); TextGrid TextGrid_createWithoutTiers (double tmin, double tmax) { try { autoTextGrid me = Thing_new (TextGrid); my tiers = Ordered_create (); therror my xmin = tmin; my xmax = tmax; return me.transfer(); } catch (MelderError) { Melder_throw ("TextGrid not created."); } } TextGrid TextGrid_create (double tmin, double tmax, const wchar_t *tierNames, const wchar_t *pointTiers) { try { autoTextGrid me = TextGrid_createWithoutTiers (tmin, tmax); wchar_t nameBuffer [400], *last; /* * Create a number of IntervalTier objects. */ if (tierNames && tierNames [0]) { wcscpy (nameBuffer, tierNames); for (wchar *tierName = Melder_wcstok (nameBuffer, L" ", & last); tierName != NULL; tierName = Melder_wcstok (NULL, L" ", & last)) { autoIntervalTier tier = IntervalTier_create (tmin, tmax); Thing_setName (tier.peek(), tierName); Collection_addItem (my tiers, tier.transfer()); } } /* * Replace some IntervalTier objects with TextTier objects. */ if (pointTiers && pointTiers [0]) { wcscpy (nameBuffer, pointTiers); for (wchar *tierName = Melder_wcstok (nameBuffer, L" ", & last); tierName != NULL; tierName = Melder_wcstok (NULL, L" ", & last)) { for (long itier = 1; itier <= my tiers -> size; itier ++) { if (wcsequ (tierName, Thing_getName ((Thing) my tiers -> item [itier]))) { autoTextTier tier = TextTier_create (tmin, tmax); Thing_setName (tier.peek(), tierName); forget (((Function *) my tiers -> item) [itier]); my tiers -> item [itier] = tier.transfer(); } } } } if (my tiers -> size == 0) Melder_throw ("Cannot create a TextGrid without tiers. Supply at least one tier name."); return me.transfer(); } catch (MelderError) { Melder_throw ("TextGrid not created."); } } TextTier TextTier_readFromXwaves (MelderFile file) { try { char *line; autoTextTier me = TextTier_create (0, 100); autoMelderFile mfile = MelderFile_open (file); /* * Search for a line that starts with '#'. */ for (;;) { line = MelderFile_readLine (file); therror if (line == NULL) Melder_throw ("Missing '#' line."); if (line [0] == '#') break; } /* * Read a mark from every line. */ for (;;) { line = MelderFile_readLine (file); therror if (line == NULL) break; // normal end-of-file double time; long colour; char mark [300]; if (sscanf (line, "%lf%ld%s", & time, & colour, mark) < 3) // BUG: buffer overflow Melder_throw ("Line too short: \"", line, "\"."); TextTier_addPoint (me.peek(), time, Melder_peekUtf8ToWcs (mark)); } /* * Fix domain. */ if (my points -> size) { TextPoint point = (TextPoint) my points -> item [1]; if (point -> number < 0.0) my xmin = point -> number - 1.0; point = (TextPoint) my points -> item [my points -> size]; my xmax = point -> number + 1.0; } mfile.close (); return me.transfer(); } catch (MelderError) { Melder_throw ("TextTier not read from Xwaves file."); } } void TextGrid_checkSpecifiedTierNumberWithinRange (TextGrid me, long tierNumber) { if (tierNumber < 1) Melder_throw (me, ": the specified tier number is ", tierNumber, ", but should be at least 1."); if (tierNumber > my tiers -> size) Melder_throw (me, ": the specified tier number (", tierNumber, ") exceeds my number of tiers (", my tiers -> size, ")."); } IntervalTier TextGrid_checkSpecifiedTierIsIntervalTier (TextGrid me, long tierNumber) { TextGrid_checkSpecifiedTierNumberWithinRange (me, tierNumber); Function tier = (Function) my tiers -> item [tierNumber]; if (tier -> classInfo != classIntervalTier) Melder_throw ("Tier ", tierNumber, " should be an interval tier."); return (IntervalTier) tier; } TextTier TextGrid_checkSpecifiedTierIsPointTier (TextGrid me, long tierNumber) { TextGrid_checkSpecifiedTierNumberWithinRange (me, tierNumber); Function tier = (Function) my tiers -> item [tierNumber]; if (tier -> classInfo != classTextTier) Melder_throw ("Tier ", tierNumber, " should be a point tier."); return (TextTier) tier; } long TextGrid_countLabels (TextGrid me, long tierNumber, const wchar_t *text) { try { TextGrid_checkSpecifiedTierNumberWithinRange (me, tierNumber); long count = 0; Function anyTier = (Function) my tiers -> item [tierNumber]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; for (long i = 1; i <= tier -> intervals -> size; i ++) { TextInterval segment = (TextInterval) tier -> intervals -> item [i]; if (segment -> text && wcsequ (segment -> text, text)) count ++; } } else { TextTier tier = (TextTier) anyTier; for (long i = 1; i <= tier -> points -> size; i ++) { TextPoint point = (TextPoint) tier -> points -> item [i]; if (point -> mark && wcsequ (point -> mark, text)) count ++; } } return count; } catch (MelderError) { Melder_throw (me, ": labels not counted."); } } void TextGrid_addTier (TextGrid me, Function anyTier) { try { autoFunction tier = Data_copy (anyTier); if (tier -> xmin < my xmin) my xmin = tier -> xmin; if (tier -> xmax > my xmax) my xmax = tier -> xmax; Collection_addItem (my tiers, tier.transfer()); } catch (MelderError) { Melder_throw (me, ": tier not added."); } } TextGrid TextGrid_merge (Collection textGrids) { try { if (textGrids -> size < 1) Melder_throw ("Cannot merge zero TextGrid objects."); autoTextGrid thee = Data_copy ((TextGrid) textGrids -> item [1]); for (long igrid = 2; igrid <= textGrids -> size; igrid ++) { TextGrid textGrid = (TextGrid) textGrids -> item [igrid]; for (long itier = 1; itier <= textGrid -> tiers -> size; itier ++) { TextGrid_addTier (thee.peek(), (TextGrid) textGrid -> tiers -> item [itier]); therror } } return thee.transfer(); } catch (MelderError) { Melder_throw ("TextGrids not merged."); } } static TextGrid _Label_to_TextGrid (Label me, double tmin, double tmax) { autoTextGrid thee = TextGrid_createWithoutTiers (tmin, tmax); for (long itier = 1; itier <= my size; itier ++) { Tier tier = (Tier) my item [itier]; autoIntervalTier intervalTier = IntervalTier_create (tmin, tmax); Collection_addItem (thy tiers, intervalTier.transfer()); Collection_removeItem (intervalTier -> intervals, 1); for (long iinterval = 1; iinterval <= tier -> size; iinterval ++) { Autosegment autosegment = (Autosegment) tier -> item [iinterval]; autoTextInterval textInterval = TextInterval_create ( iinterval == 1 ? tmin : autosegment -> xmin, iinterval == tier -> size ? tmax : autosegment -> xmax, autosegment -> name); Collection_addItem (intervalTier -> intervals, textInterval.transfer()); } } return thee.transfer(); } TextGrid TextGrid_extractPart (TextGrid me, double tmin, double tmax, int preserveTimes) { try { autoTextGrid thee = (TextGrid) Data_copy (me); int ntier = my tiers -> size; if (tmax <= tmin) return thee.transfer(); for (long itier = 1; itier <= ntier; itier ++) { Function anyTier = (Function) thy tiers -> item [itier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long ninterval = tier -> intervals -> size; for (long iinterval = ninterval; iinterval >= 1; iinterval --) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; if (interval -> xmin >= tmax || interval -> xmax <= tmin) { Collection_removeItem (tier -> intervals, iinterval); } else { if (interval -> xmin < tmin) interval -> xmin = tmin; if (interval -> xmax > tmax) interval -> xmax = tmax; } } } else { TextTier tier = (TextTier) anyTier; long n = tier -> points -> size; for (long i = n; i >= 1; i --) { TextPoint point = (TextPoint) tier -> points -> item [i]; if (point -> number < tmin || point -> number > tmax) Collection_removeItem (tier -> points, i); } } anyTier -> xmin = tmin; anyTier -> xmax = tmax; } thy xmin = tmin; thy xmax = tmax; if (! preserveTimes) Function_shiftXTo (thee.peek(), thy xmin, 0.0); return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": part not extracted."); } } TextGrid Label_to_TextGrid (Label me, double duration) { try { double tmin = 0.0, tmax = duration; if (duration == 0.0) Label_suggestDomain (me, & tmin, & tmax); Melder_casual ("%g %g %g", duration,tmin,tmax); return _Label_to_TextGrid (me, tmin, tmax); } catch (MelderError) { Melder_throw (me, ": not converted to TextGrid."); } } TextGrid Label_Function_to_TextGrid (Label me, Any function) { try { return _Label_to_TextGrid (me, ((Function) function) -> xmin, ((Function) function) -> xmax); } catch (MelderError) { Melder_throw (me, ": not converted to TextGrid."); } } TextTier PointProcess_upto_TextTier (PointProcess me, const wchar_t *text) { try { autoTextTier thee = TextTier_create (my xmin, my xmax); for (long i = 1; i <= my nt; i ++) { TextTier_addPoint (thee.peek(), my t [i], text); therror } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to TextTier."); } } PointProcess TextTier_getPoints (TextTier me, const wchar_t *text) { try { autoPointProcess thee = PointProcess_create (my xmin, my xmax, 10); for (long i = 1; i <= my points -> size; i ++) { TextPoint point = (TextPoint) my points -> item [i]; if (text && text [0]) { if (point -> mark && wcsequ (text, point -> mark)) PointProcess_addPoint (thee.peek(), point -> number); } else { if (! point -> mark || ! point -> mark [0]) PointProcess_addPoint (thee.peek(), point -> number); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": points not converted to PointProcess."); } } PointProcess IntervalTier_getStartingPoints (IntervalTier me, const wchar_t *text) { try { autoPointProcess thee = PointProcess_create (my xmin, my xmax, 10); for (long i = 1; i <= my intervals -> size; i ++) { TextInterval interval = (TextInterval) my intervals -> item [i]; if (text && text [0]) { if (interval -> text && wcsequ (text, interval -> text)) PointProcess_addPoint (thee.peek(), interval -> xmin); } else { if (! interval -> text || ! interval -> text [0]) PointProcess_addPoint (thee.peek(), interval -> xmin); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": starting points not gotten."); } } PointProcess IntervalTier_getEndPoints (IntervalTier me, const wchar_t *text) { try { autoPointProcess thee = PointProcess_create (my xmin, my xmax, 10); for (long i = 1; i <= my intervals -> size; i ++) { TextInterval interval = (TextInterval) my intervals -> item [i]; if (text && text [0]) { if (interval -> text && wcsequ (text, interval -> text)) PointProcess_addPoint (thee.peek(), interval -> xmax); } else { if (! interval -> text || ! interval -> text [0]) PointProcess_addPoint (thee.peek(), interval -> xmax); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": end points not gotten."); } } PointProcess IntervalTier_getCentrePoints (IntervalTier me, const wchar_t *text) { try { autoPointProcess thee = PointProcess_create (my xmin, my xmax, 10); for (long i = 1; i <= my intervals -> size; i ++) { TextInterval interval = (TextInterval) my intervals -> item [i]; if (text && text [0]) { if (interval -> text && wcsequ (text, interval -> text)) PointProcess_addPoint (thee.peek(), 0.5 * (interval -> xmin + interval -> xmax)); } else { if (! interval -> text || ! interval -> text [0]) PointProcess_addPoint (thee.peek(), 0.5 * (interval -> xmin + interval -> xmax)); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": centre points not gotten."); } } PointProcess TextGrid_getStartingPoints (TextGrid me, long tierNumber, int which_Melder_STRING, const wchar_t *criterion) { try { IntervalTier tier = TextGrid_checkSpecifiedTierIsIntervalTier (me, tierNumber); autoPointProcess thee = PointProcess_create (my xmin, my xmax, 10); for (long iinterval = 1; iinterval <= tier -> intervals -> size; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; if (Melder_stringMatchesCriterion (interval -> text, which_Melder_STRING, criterion)) { PointProcess_addPoint (thee.peek(), interval -> xmin); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": starting points not converted to PointProcess."); } } PointProcess TextGrid_getEndPoints (TextGrid me, long tierNumber, int which_Melder_STRING, const wchar_t *criterion) { try { IntervalTier tier = TextGrid_checkSpecifiedTierIsIntervalTier (me, tierNumber); autoPointProcess thee = PointProcess_create (my xmin, my xmax, 10); for (long iinterval = 1; iinterval <= tier -> intervals -> size; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; if (Melder_stringMatchesCriterion (interval -> text, which_Melder_STRING, criterion)) { PointProcess_addPoint (thee.peek(), interval -> xmax); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": end points not converted to PointProcess."); } } PointProcess TextGrid_getCentrePoints (TextGrid me, long tierNumber, int which_Melder_STRING, const wchar_t *criterion) { try { IntervalTier tier = TextGrid_checkSpecifiedTierIsIntervalTier (me, tierNumber); autoPointProcess thee = PointProcess_create (my xmin, my xmax, 10); for (long iinterval = 1; iinterval <= tier -> intervals -> size; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; if (Melder_stringMatchesCriterion (interval -> text, which_Melder_STRING, criterion)) { PointProcess_addPoint (thee.peek(), 0.5 * (interval -> xmin + interval -> xmax)); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": centre points not converted to PointProcess."); } } PointProcess TextGrid_getPoints (TextGrid me, long tierNumber, int which_Melder_STRING, const wchar_t *criterion) { try { TextTier tier = TextGrid_checkSpecifiedTierIsPointTier (me, tierNumber); autoPointProcess thee = PointProcess_create (my xmin, my xmax, 10); for (long ipoint = 1; ipoint <= tier -> points -> size; ipoint ++) { TextPoint point = (TextPoint) tier -> points -> item [ipoint]; if (Melder_stringMatchesCriterion (point -> mark, which_Melder_STRING, criterion)) { PointProcess_addPoint (thee.peek(), point -> number); } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": points not converted to PointProcess."); } } PointProcess IntervalTier_PointProcess_startToCentre (IntervalTier tier, PointProcess point, double phase) { try { autoPointProcess thee = PointProcess_create (tier -> xmin, tier -> xmax, 10); for (long i = 1; i <= point -> nt; i ++) { double t = point -> t [i]; long index = IntervalTier_timeToLowIndex (tier, t); if (index) { TextInterval interval = (TextInterval) tier -> intervals -> item [index]; if (interval -> xmin == t) PointProcess_addPoint (thee.peek(), (1 - phase) * interval -> xmin + phase * interval -> xmax); } } return thee.transfer(); } catch (MelderError) { Melder_throw (tier, " & ", point, ": starts of intervals not converted to PointProcess."); } } PointProcess IntervalTier_PointProcess_endToCentre (IntervalTier tier, PointProcess point, double phase) { try { autoPointProcess thee = PointProcess_create (tier -> xmin, tier -> xmax, 10); for (long i = 1; i <= point -> nt; i ++) { double t = point -> t [i]; long index = IntervalTier_timeToHighIndex (tier, t); if (index) { TextInterval interval = (TextInterval) tier -> intervals -> item [index]; if (interval -> xmax == t) PointProcess_addPoint (thee.peek(), (1 - phase) * interval -> xmin + phase * interval -> xmax); } } return thee.transfer(); } catch (MelderError) { Melder_throw (tier, " & ", point, ": ends of intervals not converted to PointProcess."); } } TableOfReal IntervalTier_downto_TableOfReal (IntervalTier me, const wchar_t *label) { try { long n = 0; for (long i = 1; i <= my intervals -> size; i ++) { TextInterval interval = (TextInterval) my intervals -> item [i]; if (label == NULL || (label [0] == '\0' && ! interval -> text) || (interval -> text && wcsequ (interval -> text, label))) n ++; } autoTableOfReal thee = TableOfReal_create (n, 3); TableOfReal_setColumnLabel (thee.peek(), 1, L"Start"); TableOfReal_setColumnLabel (thee.peek(), 2, L"End"); TableOfReal_setColumnLabel (thee.peek(), 3, L"Duration"); for (long i = 1, n = 0; i <= my intervals -> size; i ++) { TextInterval interval = (TextInterval) my intervals -> item [i]; if (label == NULL || (label [0] == '\0' && ! interval -> text) || (interval -> text && wcsequ (interval -> text, label))) { n ++; TableOfReal_setRowLabel (thee.peek(), n, interval -> text ? interval -> text : L""); thy data [n] [1] = interval -> xmin; thy data [n] [2] = interval -> xmax; thy data [n] [3] = interval -> xmax - interval -> xmin; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to TableOfReal."); } } TableOfReal IntervalTier_downto_TableOfReal_any (IntervalTier me) { return IntervalTier_downto_TableOfReal (me, NULL); } TableOfReal TextTier_downto_TableOfReal (TextTier me, const wchar_t *label) { try { long n = 0; for (long i = 1; i <= my points -> size; i ++) { TextPoint point = (TextPoint) my points -> item [i]; if (label == NULL || (label [0] == '\0' && ! point -> mark) || (point -> mark && wcsequ (point -> mark, label))) n ++; } autoTableOfReal thee = TableOfReal_create (n, 1); TableOfReal_setColumnLabel (thee.peek(), 1, L"Time"); for (long i = 1, n = 0; i <= my points -> size; i ++) { TextPoint point = (TextPoint) my points -> item [i]; if (label == NULL || (label [0] == '\0' && ! point -> mark) || (point -> mark && wcsequ (point -> mark, label))) { n ++; TableOfReal_setRowLabel (thee.peek(), n, point -> mark ? point -> mark : L""); thy data [n] [1] = point -> number; } } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to TableOfReal."); } } TableOfReal TextTier_downto_TableOfReal_any (TextTier me) { return TextTier_downto_TableOfReal (me, NULL); } static void IntervalTier_addInterval_unsafe (IntervalTier me, double tmin, double tmax, const wchar_t *label) { autoTextInterval interval = TextInterval_create (tmin, tmax, label); Collection_addItem (my intervals, interval.transfer()); } IntervalTier IntervalTier_readFromXwaves (MelderFile file) { try { char *line; double lastTime = 0.0; autoIntervalTier me = IntervalTier_create (0, 100); autoMelderFile mfile = MelderFile_open (file); /* * Search for a line that starts with '#'. */ for (;;) { line = MelderFile_readLine (file); therror if (line == NULL) Melder_throw ("Missing '#' line."); if (line [0] == '#') break; } /* * Read a mark from every line. */ for (;;) { double time; long colour, numberOfElements; char mark [300]; line = MelderFile_readLine (file); therror if (line == NULL) break; // normal end-of-file numberOfElements = sscanf (line, "%lf%ld%s", & time, & colour, mark); if (numberOfElements == 0) { break; // an empty line, hopefully at the end } if (numberOfElements == 1) Melder_throw ("Line too short: \"", line, "\"."); if (numberOfElements == 2) mark [0] = '\0'; if (lastTime == 0.0) { TextInterval interval = (TextInterval) my intervals -> item [1]; interval -> xmax = time; TextInterval_setText (interval, Melder_peekUtf8ToWcs (mark)); therror } else { IntervalTier_addInterval_unsafe (me.peek(), lastTime, time, Melder_peekUtf8ToWcs (mark)); therror } lastTime = time; } /* * Fix domain. */ if (lastTime > 0.0) { TextInterval lastInterval = (TextInterval) my intervals -> item [my intervals -> size]; my xmax = lastInterval -> xmax = lastTime; } mfile.close (); return me.transfer(); } catch (MelderError) { Melder_throw ("IntervalTier not read from file ", file, "."); } } void IntervalTier_writeToXwaves (IntervalTier me, MelderFile file) { try { autofile f = Melder_fopen (file, "w"); fprintf (f, "separator ;\nnfields 1\n#\n"); for (long iinterval = 1; iinterval <= my intervals -> size; iinterval ++) { TextInterval interval = (TextInterval) my intervals -> item [iinterval]; fprintf (f, "\t%.6f 26\t%s\n", interval -> xmax, Melder_peekWcsToUtf8 (interval -> text)); } f.close (file); MelderFile_setMacTypeAndCreator (file, 'TEXT', 0); } catch (MelderError) { Melder_throw (me, ": not written to Xwaves file ", file, "."); } } TextGrid PointProcess_to_TextGrid_vuv (PointProcess me, double maxT, double meanT) { try { autoTextGrid thee = TextGrid_create (my xmin, my xmax, L"vuv", NULL); Collection_removeItem (((IntervalTier) thy tiers -> item [1]) -> intervals, 1); long ipointright; double beginVoiceless = my xmin, endVoiceless, halfMeanT = 0.5 * meanT; for (long ipointleft = 1; ipointleft <= my nt; ipointleft = ipointright + 1) { endVoiceless = my t [ipointleft] - halfMeanT; if (endVoiceless <= beginVoiceless) { endVoiceless = beginVoiceless; /* We will use for voiced interval. */ } else { IntervalTier_addInterval_unsafe ((IntervalTier) thy tiers -> item [1], beginVoiceless, endVoiceless, L"U"); } for (ipointright = ipointleft + 1; ipointright <= my nt; ipointright ++) if (my t [ipointright] - my t [ipointright - 1] > maxT) break; ipointright --; beginVoiceless = my t [ipointright] + halfMeanT; if (beginVoiceless > my xmax) beginVoiceless = my xmax; IntervalTier_addInterval_unsafe ((IntervalTier) thy tiers -> item [1], endVoiceless, beginVoiceless, L"V"); } endVoiceless = my xmax; if (endVoiceless > beginVoiceless) { IntervalTier_addInterval_unsafe ((IntervalTier) thy tiers -> item [1], beginVoiceless, endVoiceless, L"U"); } return thee.transfer(); } catch (MelderError) { Melder_throw (me, ": not converted to TextGrid (vuv)."); } } long TextInterval_labelLength (TextInterval me) { return my text ? wcslen (my text) : 0; } long TextPoint_labelLength (TextPoint me) { return my mark ? wcslen (my mark) : 0; } long IntervalTier_maximumLabelLength (IntervalTier me) { long maximum = 0, ninterval = my intervals -> size; for (long iinterval = 1; iinterval <= ninterval; iinterval ++) { long length = TextInterval_labelLength ((TextInterval) my intervals -> item [iinterval]); if (length > maximum) maximum = length; } return maximum; } long TextTier_maximumLabelLength (TextTier me) { long maximum = 0, npoint = my points -> size; for (long ipoint= 1; ipoint <= npoint; ipoint ++) { long length = TextPoint_labelLength ((TextPoint) my points -> item [ipoint]); if (length > maximum) maximum = length; } return maximum; } long TextGrid_maximumLabelLength (TextGrid me) { long maximum = 0, ntier = my tiers -> size; for (long itier = 1; itier <= ntier; itier ++) { Function anyTier = (Function) my tiers -> item [itier]; long length = anyTier -> classInfo == classIntervalTier ? IntervalTier_maximumLabelLength ((IntervalTier) anyTier) : TextTier_maximumLabelLength ((TextTier) anyTier); if (length > maximum) maximum = length; } return maximum; } static void genericize (wchar_t **pstring, wchar_t *buffer) { if (*pstring) { const wchar_t *p = (const wchar_t *) *pstring; while (*p) { if (*p > 126) { /* Only if necessary. */ wchar_t *newString; Longchar_genericizeW (*pstring, buffer); newString = Melder_wcsdup (buffer); /* * Replace string only if copying was OK. */ Melder_free (*pstring); *pstring = newString; break; } p ++; } } } void TextGrid_genericize (TextGrid me) { try { long ntier = my tiers -> size; autostring buffer = Melder_calloc (wchar, TextGrid_maximumLabelLength (me) * 3 + 1); for (long itier = 1; itier <= ntier; itier ++) { Function anyTier = (Function) my tiers -> item [itier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long ninterval = tier -> intervals -> size; for (long iinterval = 1; iinterval <= ninterval; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; genericize (& interval -> text, buffer.peek()); } } else { TextTier tier = (TextTier) anyTier; long n = tier -> points -> size; for (long ipoint = 1; ipoint <= n; ipoint ++) { TextPoint point = (TextPoint) tier -> points -> item [ipoint]; genericize (& point -> mark, buffer.peek()); } } } } catch (MelderError) { Melder_throw (me, ": not converted to backslash trigraphs."); } } void TextGrid_nativize (TextGrid me) { try { long ntier = my tiers -> size; autostring buffer = Melder_calloc (wchar, TextGrid_maximumLabelLength (me) + 1); for (long itier = 1; itier <= ntier; itier ++) { Function anyTier = (Function) my tiers -> item [itier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; long ninterval = tier -> intervals -> size; for (long iinterval = 1; iinterval <= ninterval; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; if (interval -> text) { Longchar_nativizeW (interval -> text, buffer.peek(), FALSE); wcscpy (interval -> text, buffer.peek()); } } } else { TextTier tier = (TextTier) anyTier; long n = tier -> points -> size; for (long ipoint = 1; ipoint <= n; ipoint ++) { TextPoint point = (TextPoint) tier -> points -> item [ipoint]; if (point -> mark) { Longchar_nativizeW (point -> mark, buffer.peek(), FALSE); wcscpy (point -> mark, buffer.peek()); } } } } } catch (MelderError) { Melder_throw (me, ": backslash trigraphs not converted to Unicode."); } } void TextInterval_removeText (TextInterval me) { Melder_free (my text); } void TextPoint_removeText (TextPoint me) { Melder_free (my mark); } void IntervalTier_removeText (IntervalTier me) { long ninterval = my intervals -> size; for (long iinterval = 1; iinterval <= ninterval; iinterval ++) TextInterval_removeText ((TextInterval) my intervals -> item [iinterval]); } void TextTier_removeText (TextTier me) { long npoint = my points -> size; for (long ipoint = 1; ipoint <= npoint; ipoint ++) TextPoint_removeText ((TextPoint) my points -> item [ipoint]); } void TextGrid_insertBoundary (TextGrid me, int tierNumber, double t) { try { TextGrid_checkSpecifiedTierNumberWithinRange (me, tierNumber); IntervalTier intervalTier = (IntervalTier) my tiers -> item [tierNumber]; if (intervalTier -> classInfo != classIntervalTier) Melder_throw ("Cannot add a boundary on tier ", tierNumber, ", because that tier is not an interval tier."); if (IntervalTier_hasTime (intervalTier, t)) Melder_throw ("Cannot add a boundary at ", Melder_fixed (t, 6), " seconds, because there is already a boundary there."); long intervalNumber = IntervalTier_timeToIndex (intervalTier, t); if (intervalNumber == 0) Melder_throw ("Cannot add a boundary at ", Melder_fixed (t, 6), " seconds, because this is outside the time domain of the intervals."); TextInterval interval = (TextInterval) intervalTier -> intervals -> item [intervalNumber]; /* * Move the text to the left of the boundary. */ autoTextInterval newInterval = TextInterval_create (t, interval -> xmax, L""); interval -> xmax = t; Collection_addItem (intervalTier -> intervals, newInterval.transfer()); } catch (MelderError) { Melder_throw (me, ": boundary not inserted."); } } void IntervalTier_removeLeftBoundary (IntervalTier me, long iinterval) { try { Melder_assert (iinterval > 1); Melder_assert (iinterval <= my intervals -> size); TextInterval left = (TextInterval) my intervals -> item [iinterval - 1]; TextInterval right = (TextInterval) my intervals -> item [iinterval]; /* * Move the text to the left of the boundary. */ left -> xmax = right -> xmax; // collapse left and right intervals into left interval if (right -> text == NULL) { ; } else if (left -> text == NULL) { TextInterval_setText (left, right -> text); } else { static MelderString buffer = { 0 }; MelderString_empty (& buffer); MelderString_append (& buffer, left -> text, right -> text); TextInterval_setText (left, buffer.string); } Collection_removeItem (my intervals, iinterval); // remove right interval } catch (MelderError) { Melder_throw (me, ": left boundary not removed."); } } void TextGrid_removeBoundaryAtTime (TextGrid me, int tierNumber, double t) { try { TextGrid_checkSpecifiedTierNumberWithinRange (me, tierNumber); IntervalTier intervalTier = (IntervalTier) my tiers -> item [tierNumber]; if (intervalTier -> classInfo != classIntervalTier) Melder_throw ("Tier ", tierNumber, " is not an interval tier."); if (! IntervalTier_hasTime (intervalTier, t)) Melder_throw ("There is no boundary at ", t, " seconds."); long iinterval = IntervalTier_timeToIndex (intervalTier, t); if (iinterval == 0) Melder_throw ("The time of ", t, " seconds is outside the time domain of the intervals."); if (iinterval == 1) Melder_throw ("The time of ", t, " seconds is at the left edge of the tier."); IntervalTier_removeLeftBoundary (intervalTier, iinterval); } catch (MelderError) { Melder_throw (me, ": boundary not removed."); } } void TextGrid_setIntervalText (TextGrid me, int tierNumber, long iinterval, const wchar_t *text) { try { TextGrid_checkSpecifiedTierNumberWithinRange (me, tierNumber); IntervalTier intervalTier = (IntervalTier) my tiers -> item [tierNumber]; if (intervalTier -> classInfo != classIntervalTier) Melder_throw ("Tier ", tierNumber, " is not an interval tier."); if (iinterval < 1 || iinterval > intervalTier -> intervals -> size) Melder_throw ("Interval ", iinterval, " does not exist on tier ", tierNumber, "."); TextInterval interval = (TextInterval) intervalTier -> intervals -> item [iinterval]; TextInterval_setText (interval, text); } catch (MelderError) { Melder_throw (me, ": interval text not set."); } } void TextGrid_insertPoint (TextGrid me, int tierNumber, double t, const wchar_t *mark) { try { TextGrid_checkSpecifiedTierNumberWithinRange (me, tierNumber); TextTier textTier = (TextTier) my tiers -> item [tierNumber]; if (textTier -> classInfo != classTextTier) Melder_throw ("Tier ", tierNumber, " is not a point tier."); if (AnyTier_hasPoint (textTier, t)) Melder_throw ("There is already a point at ", t, " seconds."); autoTextPoint newPoint = TextPoint_create (t, mark); Collection_addItem (textTier -> points, newPoint.transfer()); } catch (MelderError) { Melder_throw (me, ": point not inserted."); } } void TextTier_removePoint (TextTier me, long ipoint) { Melder_assert (ipoint <= my points -> size); Collection_removeItem (my points, ipoint); } void TextGrid_setPointText (TextGrid me, int tierNumber, long ipoint, const wchar_t *text) { try { TextGrid_checkSpecifiedTierNumberWithinRange (me, tierNumber); TextTier textTier = (TextTier) my tiers -> item [tierNumber]; if (textTier -> classInfo != classTextTier) Melder_throw ("Tier ", tierNumber, " is not a point tier."); if (ipoint < 1 || ipoint > textTier -> points -> size) Melder_throw ("Point ", ipoint, " does not exist on tier ", tierNumber, "."); TextPoint point = (TextPoint) textTier -> points -> item [ipoint]; TextPoint_setText (point, text); } catch (MelderError) { Melder_throw (me, ": point text not set."); } } static void sgmlToPraat (char *text) { char *sgml = text, *praat = text; for (;;) { if (*sgml == '\0') break; if (*sgml == '&') { static struct { const char *sgml, *praat; } translations [] = { { "auml", "\\a\"" }, { "euml", "\\e\"" }, { "iuml", "\\i\"" }, { "ouml", "\\o\"" }, { "ouml", "\\o\"" }, { "Auml", "\\A\"" }, { "Euml", "\\E\"" }, { "Iuml", "\\I\"" }, { "Ouml", "\\O\"" }, { "Uuml", "\\U\"" }, { "aacute", "\\a'" }, { "eacute", "\\e'" }, { "iacute", "\\i'" }, { "oacute", "\\o'" }, { "oacute", "\\o'" }, { "Aacute", "\\A'" }, { "Eacute", "\\E'" }, { "Iacute", "\\I'" }, { "Oacute", "\\O'" }, { "Uacute", "\\U'" }, { "agrave", "\\a`" }, { "egrave", "\\e`" }, { "igrave", "\\i`" }, { "ograve", "\\o`" }, { "ograve", "\\o`" }, { "Agrave", "\\A`" }, { "Egrave", "\\E`" }, { "Igrave", "\\I`" }, { "Ograve", "\\O`" }, { "Ugrave", "\\U`" }, { "acirc", "\\a^" }, { "ecirc", "\\e^" }, { "icirc", "\\i^" }, { "ocirc", "\\o^" }, { "ocirc", "\\o^" }, { "Acirc", "\\A^" }, { "Ecirc", "\\E^" }, { "Icirc", "\\I^" }, { "Ocirc", "\\O^" }, { "Ucirc", "\\U^" }, { NULL, NULL } }; char sgmlCode [201]; int i = 0; ++ sgml; for (i = 0; i < 200; i ++) { char sgmlChar = sgml [i]; if (sgmlChar == ';') { if (i == 0) Melder_throw ("Empty SGML code."); sgml += i + 1; break; } sgmlCode [i] = sgmlChar; } if (i >= 200) Melder_throw ("Unfinished SGML code."); sgmlCode [i] = '\0'; for (i = 0; translations [i]. sgml != NULL; i ++) { if (strequ (sgmlCode, translations [i]. sgml)) { memcpy (praat, translations [i]. praat, strlen (translations [i]. praat)); praat += strlen (translations [i]. praat); break; } } if (translations [i]. sgml == NULL) Melder_throw ("Unknown SGML code &", sgmlCode, ";."); } else { * praat ++ = * sgml ++; } } *praat = '\0'; } TextGrid TextGrid_readFromChronologicalTextFile (MelderFile file) { try { Thing_version = 0; autoMelderReadText text = MelderReadText_createFromFile (file); autostring tag = texgetw2 (text.peek()); if (! wcsequ (tag.peek(), L"Praat chronological TextGrid text file")) Melder_throw ("This is not a chronological TextGrid text file."); autoTextGrid me = Thing_new (TextGrid); my structFunction :: v_readText (text.peek()); my tiers = Ordered_create (); therror long numberOfTiers = texgeti4 (text.peek()); for (long itier = 1; itier <= numberOfTiers; itier ++) { autostring klas = texgetw2 (text.peek()); if (wcsequ (klas.peek(), L"IntervalTier")) { autoIntervalTier tier = Thing_new (IntervalTier); tier -> name = texgetw2 (text.peek()); tier -> structFunction :: v_readText (text.peek()); tier -> intervals = SortedSetOfDouble_create (); therror Collection_addItem (my tiers, tier.transfer()); } else if (wcsequ (klas.peek(), L"TextTier")) { autoTextTier tier = Thing_new (TextTier); tier -> name = texgetw2 (text.peek()); tier -> structFunction :: v_readText (text.peek()); tier -> points = SortedSetOfDouble_create (); therror Collection_addItem (my tiers, tier.transfer()); } else { Melder_throw ("Unknown tier class \"", klas.peek(), L"\"."); } } for (;;) { long tierNumber; try { tierNumber = texgeti4 (text.peek()); } catch (MelderError) { if (wcsstr (Melder_getError (), L"Early end of text")) { Melder_clearError (); break; } else { throw; } } TextGrid_checkSpecifiedTierNumberWithinRange (me.peek(), tierNumber); if (((Function) my tiers -> item [tierNumber]) -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) my tiers -> item [tierNumber]; autoTextInterval interval = Thing_new (TextInterval); interval -> v_readText (text.peek()); Collection_addItem (tier -> intervals, interval.transfer()); // not earlier: sorting depends on contents of interval } else { TextTier tier = (TextTier) my tiers -> item [tierNumber]; autoTextPoint point = Thing_new (TextPoint); point -> v_readText (text.peek()); therror Collection_addItem (tier -> points, point.transfer()); // not earlier: sorting depends on contents of point } } return me.transfer(); } catch (MelderError) { Melder_throw ("TextGrid not read from chronological text file ", file, "."); } } static void writeQuotedString (MelderFile file, const wchar_t *string) { MelderFile_writeCharacter (file, '\"'); if (string) { wchar_t kar; while ((kar = *string ++) != '\0') { MelderFile_writeCharacter (file, kar); if (kar == '\"') MelderFile_writeCharacter (file, kar); } } // BUG MelderFile_writeCharacter (file, '\"'); } void TextGrid_writeToChronologicalTextFile (TextGrid me, MelderFile file) { try { Data_createTextFile (me, file, false); therror autoMelderFile mfile = file; /* * The "elements" (intervals and points) are sorted primarily by time and secondarily by tier. */ double sortingTime = -1e308; long sortingTier = 0; file -> verbose = false; texindent (file); MelderFile_write7 (file, L"\"Praat chronological TextGrid text file\"\n", Melder_double (my xmin), L" ", Melder_double (my xmax), L" ! Time domain.\n", Melder_integer (my tiers -> size), L" ! Number of tiers."); for (long itier = 1; itier <= my tiers -> size; itier ++) { Function anyTier = (Function) my tiers -> item [itier]; MelderFile_write1 (file, L"\n"); writeQuotedString (file, Thing_className (anyTier)); MelderFile_write1 (file, L" "); writeQuotedString (file, anyTier -> name); MelderFile_write4 (file, L" ", Melder_double (anyTier -> xmin), L" ", Melder_double (anyTier -> xmax)); } for (;;) { double firstRemainingTime = +1e308; long firstRemainingTier = 2000000000, firstRemainingElement = 0; for (long itier = 1; itier <= my tiers -> size; itier ++) { Function anyTier = (Function) my tiers -> item [itier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; for (long ielement = 1; ielement <= tier -> intervals -> size; ielement ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [ielement]; if ((interval -> xmin > sortingTime || // sort primarily by time (interval -> xmin == sortingTime && itier > sortingTier)) && // sort secondarily by tier number (interval -> xmin < firstRemainingTime || // sort primarily by time (interval -> xmin == firstRemainingTime && itier < firstRemainingTier))) // sort secondarily by tier number { firstRemainingTime = interval -> xmin; firstRemainingTier = itier; firstRemainingElement = ielement; } } } else { TextTier tier = (TextTier) anyTier; for (long ielement = 1; ielement <= tier -> points -> size; ielement ++) { TextPoint point = (TextPoint) tier -> points -> item [ielement]; if ((point -> number > sortingTime || // sort primarily by time (point -> number == sortingTime && itier > sortingTier)) && // sort secondarily by tier number (point -> number < firstRemainingTime || // sort primarily by time (point -> number == firstRemainingTime && itier < firstRemainingTier))) // sort secondarily by tier number { firstRemainingTime = point -> number; firstRemainingTier = itier; firstRemainingElement = ielement; } } } } if (firstRemainingElement == 0) { break; } else { Function anyTier = (Function) my tiers -> item [firstRemainingTier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; TextInterval interval = (TextInterval) tier -> intervals -> item [firstRemainingElement]; if (tier -> name) MelderFile_write3 (file, L"\n\n! ", tier -> name, L":"); MelderFile_write6 (file, L"\n", Melder_integer (firstRemainingTier), L" ", Melder_double (interval -> xmin), L" ", Melder_double (interval -> xmax)); texputw4 (file, interval -> text, L"", 0,0,0,0,0); } else { TextTier tier = (TextTier) anyTier; TextPoint point = (TextPoint) tier -> points -> item [firstRemainingElement]; if (tier -> name) MelderFile_write3 (file, L"\n\n! ", tier -> name, L":"); MelderFile_write5 (file, L"\n", Melder_integer (firstRemainingTier), L" ", Melder_double (point -> number), L" "); texputw4 (file, point -> mark, L"", 0,0,0,0,0); } sortingTime = firstRemainingTime; sortingTier = firstRemainingTier; } } texexdent (file); mfile.close (); MelderFile_setMacTypeAndCreator (file, 'TEXT', 0); } catch (MelderError) { Melder_throw (me, ": not written to chronological text file ", file, "."); } } TextGrid TextGrid_readFromCgnSyntaxFile (MelderFile file) { try { autoTextGrid me = Thing_new (TextGrid); long sentenceNumber = 0; double phraseBegin = 0.0, phraseEnd = 0.0; IntervalTier sentenceTier = NULL, phraseTier = NULL; TextInterval lastInterval = NULL; static char phrase [1000]; my tiers = Ordered_create (); autoMelderFile mfile = MelderFile_open (file); char *line = MelderFile_readLine (file); if (! strequ (line, "")) Melder_throw ("This is not a CGN syntax file."); line = MelderFile_readLine (file); if (! strequ (line, "")) Melder_throw ("This is not a CGN syntax file."); line = MelderFile_readLine (file); long startOfData = MelderFile_tell (file); /* * Get duration. */ my xmin = 0.0; char arg1 [41], arg2 [41], arg3 [41], arg4 [41], arg5 [41], arg6 [41], arg7 [201]; for (;;) { line = MelderFile_readLine (file); if (! line) break; if (strnequ (line, " intervals -> size > 0) { TextInterval latestInterval = (TextInterval) sentenceTier -> intervals -> item [sentenceTier -> intervals -> size]; if (tb > latestInterval -> xmax) { autoTextInterval interval = TextInterval_create (latestInterval -> xmax, tb, L""); Collection_addItem (sentenceTier -> intervals, interval.transfer()); } else if (tb < latestInterval -> xmax) { Melder_throw ("Overlap on tier not allowed."); } } else { if (tb > 0.0) { TextInterval interval = TextInterval_create (0.0, tb, L""); Collection_addItem (sentenceTier -> intervals, interval); } else if (tb < 0.0) { Melder_throw ("Negative times not allowed."); } } char label [10]; sprintf (label, "%ld", ++ sentenceNumber); autoTextInterval interval = TextInterval_create (tb, te, Melder_peekUtf8ToWcs (label)); Collection_addItem (sentenceTier -> intervals, interval.transfer()); } else if (strnequ (line, " strcat (phrase, arg7 + 3); } else { /* Begin a phrase. */ if (lastInterval) { sgmlToPraat (phrase); therror TextInterval_setText (lastInterval, Melder_peekUtf8ToWcs (phrase)); therror } phrase [0] = '\0'; length = strlen (arg7); if (length < 6 || ! strnequ (arg7, "w=\"", 3)) Melder_throw ("Missing word."); arg7 [length - 3] = '\0'; /* Truncate "/>. */ strcat (phrase, arg7 + 3); if (phraseTier -> intervals -> size > 0) { TextInterval latestInterval = (TextInterval) phraseTier -> intervals -> item [phraseTier -> intervals -> size]; if (tb > latestInterval -> xmax) { autoTextInterval interval = TextInterval_create (latestInterval -> xmax, tb, L""); Collection_addItem (phraseTier -> intervals, interval.transfer()); } else if (tb < latestInterval -> xmax) { Melder_throw ("Overlap on tier not allowed."); } } else { if (tb > 0.0) { autoTextInterval interval = TextInterval_create (0.0, tb, L""); Collection_addItem (phraseTier -> intervals, interval.transfer()); } else if (tb < 0.0) { Melder_throw ("Negative times not allowed."); } } if (! phraseTier) Melder_throw ("Phrase outside sentence."); autoTextInterval newLastInterval = TextInterval_create (tb, te, L""); lastInterval = newLastInterval.peek(); Collection_addItem (phraseTier -> intervals, newLastInterval.transfer()); phraseBegin = tb; phraseEnd = te; } } } if (lastInterval) { sgmlToPraat (phrase); therror TextInterval_setText (lastInterval, Melder_peekUtf8ToWcs (phrase)); therror } for (long itier = 1; itier <= my tiers -> size; itier ++) { IntervalTier tier = (IntervalTier) my tiers -> item [itier]; if (tier -> intervals -> size > 0) { TextInterval latestInterval = (TextInterval) tier -> intervals -> item [tier -> intervals -> size]; if (my xmax > latestInterval -> xmax) { autoTextInterval interval = TextInterval_create (latestInterval -> xmax, my xmax, L""); Collection_addItem (tier -> intervals, interval.transfer()); } } else { autoTextInterval interval = TextInterval_create (my xmin, my xmax, L""); Collection_addItem (tier -> intervals, interval.transfer()); } } mfile.close (); return me.transfer(); } catch (MelderError) { Melder_throw ("TextGrid not read from CGN syntax file ", file, "."); } } Table TextGrid_downto_Table (TextGrid me, bool includeLineNumbers, int timeDecimals, bool includeTierNames, bool includeEmptyIntervals) { long numberOfRows = 0; for (long itier = 1; itier <= my tiers -> size; itier ++) { Function anyTier = (Function) my tiers -> item [itier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; if (includeEmptyIntervals) { numberOfRows += tier -> intervals -> size; } else { for (long iinterval = 1; iinterval <= tier -> intervals -> size; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; if (interval -> text != NULL && interval -> text [0] != '\0') { numberOfRows ++; } } } } else { TextTier tier = (TextTier) anyTier; numberOfRows += tier -> points -> size; } } autoTable thee = Table_createWithoutColumnNames (numberOfRows, 3 + includeLineNumbers + includeTierNames); long icol = 0; if (includeLineNumbers) Table_setColumnLabel (thee.peek(), ++ icol, L"line"); Table_setColumnLabel (thee.peek(), ++ icol, L"tmin"); if (includeTierNames) Table_setColumnLabel (thee.peek(), ++ icol, L"tier"); Table_setColumnLabel (thee.peek(), ++ icol, L"text"); Table_setColumnLabel (thee.peek(), ++ icol, L"tmax"); long irow = 0; for (long itier = 1; itier <= my tiers -> size; itier ++) { Function anyTier = (Function) my tiers -> item [itier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; for (long iinterval = 1; iinterval <= tier -> intervals -> size; iinterval ++) { TextInterval interval = (TextInterval) tier -> intervals -> item [iinterval]; if (includeEmptyIntervals || (interval -> text != NULL && interval -> text [0] != '\0')) { ++ irow; icol = 0; if (includeLineNumbers) Table_setNumericValue (thee.peek(), irow, ++ icol, irow); Table_setStringValue (thee.peek(), irow, ++ icol, Melder_fixed (interval -> xmin, timeDecimals)); if (includeTierNames) Table_setStringValue (thee.peek(), irow, ++ icol, tier -> name); Table_setStringValue (thee.peek(), irow, ++ icol, interval -> text); Table_setStringValue (thee.peek(), irow, ++ icol, Melder_fixed (interval -> xmax, timeDecimals)); } } } else { TextTier tier = (TextTier) anyTier; for (long ipoint = 1; ipoint <= tier -> points -> size; ipoint ++) { TextPoint point = (TextPoint) tier -> points -> item [ipoint]; ++ irow; icol = 0; if (includeLineNumbers) Table_setNumericValue (thee.peek(), irow, ++ icol, irow); Table_setStringValue (thee.peek(), irow, ++ icol, Melder_fixed (point -> number, timeDecimals)); if (includeTierNames) Table_setStringValue (thee.peek(), irow, ++ icol, tier -> name); Table_setStringValue (thee.peek(), irow, ++ icol, point -> mark); Table_setStringValue (thee.peek(), irow, ++ icol, Melder_fixed (point -> number, timeDecimals)); } } } long columns [1+2] = { 0, 1 + includeLineNumbers, 3 + includeLineNumbers + includeTierNames }; // sort by tmin and tmax Table_sortRows_Assert (thee.peek(), columns, 2); return thee.transfer(); } void TextGrid_list (TextGrid me, bool includeLineNumbers, int timeDecimals, bool includeTierNames, bool includeEmptyIntervals) { try { autoTable table = TextGrid_downto_Table (me, includeLineNumbers, timeDecimals, includeTierNames, includeEmptyIntervals); Table_list (table.peek(), false); } catch (MelderError) { Melder_throw (me, ": not listed."); } } void TextGrid_correctRoundingErrors (TextGrid me) { for (long itier = 1; itier <= my tiers -> size; itier ++) { Function anyTier = (Function) my tiers -> item [itier]; if (anyTier -> classInfo == classIntervalTier) { IntervalTier tier = (IntervalTier) anyTier; TextInterval first = (TextInterval) tier -> intervals -> item [1]; first -> xmin = my xmin; Melder_assert (first -> xmin < first -> xmax); for (long iinterval = 1; iinterval < tier -> intervals -> size; iinterval ++) { TextInterval left = (TextInterval) tier -> intervals -> item [iinterval]; TextInterval right = (TextInterval) tier -> intervals -> item [iinterval + 1]; right -> xmin = left -> xmax; Melder_assert (right -> xmin < right -> xmax); } TextInterval last = (TextInterval) tier -> intervals -> item [tier -> intervals -> size]; last -> xmax = my xmax; Melder_assert (last -> xmax > last -> xmin); } anyTier -> xmin = my xmax; anyTier -> xmax = my xmax; } } TextGrid TextGrids_concatenate (Collection me) { try { autoTextGrid thee = TextGrids_to_TextGrid_appendContinuous (me, false); TextGrid_correctRoundingErrors (thee.peek()); return thee.transfer(); } catch (MelderError) { Melder_throw ("TextGrids not concatenated."); } } /* End of file TextGrid.cpp */ sources_5316/fon/Corpus.h0000644000176700017670000000161111655640351014136 0ustar paulpaul#ifndef _Corpus_h_ #define _Corpus_h_ /* AnyTier.h * * Copyright (C) 2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Table.h" #include "Corpus_def.h" oo_CLASS_CREATE (Corpus, Table); #endif /* End of file Corpus.h */ sources_5316/fon/Vector.cpp0000644000176700017670000003614411621512743014465 0ustar paulpaul/* Vector.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "Vector.h" // // Vector::getVector () returns a channel or the average of all the channels. // double structVector :: v_getVector (long irow, long icol) { if (icol < 1 || icol > nx) return 0.0; if (ny == 1) return z [1] [icol]; // optimization if (irow == 0) { if (ny == 2) return 0.5 * (z [1] [icol] + z [2] [icol]); // optimization double sum = 0.0; for (long channel = 1; channel <= ny; channel ++) { sum += z [channel] [icol]; } return sum / ny; } Melder_assert (irow > 0 && irow <= ny); return z [irow] [icol]; } // // Vector::getFunction1 () returns a channel or the average of all the channels. // double structVector :: v_getFunction1 (long irow, double x) { double rcol = (x - x1) / dx + 1.0; long icol = floor (rcol); double dcol = rcol - icol; double z1; if (icol < 1 || icol > nx) { z1 = 0.0; // outside the definition region, Formula is expected to return zero } else if (ny == 1) { z1 = z [1] [icol]; // optimization } else if (irow == 0) { if (ny == 2) { z1 = 0.5 * (z [1] [icol] + z [2] [icol]); // optimization } else { double sum = 0.0; for (long channel = 1; channel <= ny; channel ++) { sum += z [channel] [icol]; } z1 = sum / ny; } } else { Melder_assert (irow > 0 && irow <= ny); z1 = z [irow] [icol]; } double z2; if (icol < 0 || icol >= nx) { z2 = 0.0; // outside the definition region, Formula is expected to return zero } else if (ny == 1) { z2 = z [1] [icol + 1]; // optimization } else if (irow == 0) { if (ny == 2) { z2 = 0.5 * (z [1] [icol + 1] + z [2] [icol + 1]); // optimization } else { double sum = 0.0; for (long channel = 1; channel <= ny; channel ++) { sum += z [channel] [icol + 1]; } z2 = sum / ny; } } else { Melder_assert (irow > 0 && irow <= ny); z2 = z [irow] [icol + 1]; } return (1.0 - dcol) * z1 + dcol * z2; } double structVector :: v_getValueAtSample (long isamp, long ilevel, int unit) { // Preconditions: // 1 <= isamp <= my nx // 0 <= ilevel <= my ny double value; if (ilevel > Vector_CHANNEL_AVERAGE) { value = z [ilevel] [isamp]; } else if (ny == 1) { value = z [1] [isamp]; // optimization } else if (ny == 2) { value = 0.5 * (z [1] [isamp] + z [2] [isamp]); // optimization } else { double sum = 0.0; for (long channel = 1; channel <= ny; channel ++) { sum += z [channel] [isamp]; } value = sum / ny; } return NUMdefined (value) ? v_convertStandardToSpecialUnit (value, ilevel, unit) : NUMundefined; } Thing_implement (Vector, Matrix, 2); /***** Get content. *****/ // // Vector_getValueAtX () returns the average of all the interpolated channels. // double Vector_getValueAtX (Vector me, double x, long ilevel, int interpolation) { double leftEdge = my x1 - 0.5 * my dx, rightEdge = leftEdge + my nx * my dx; if (x < leftEdge || x > rightEdge) return NUMundefined; if (ilevel > Vector_CHANNEL_AVERAGE) { Melder_assert (ilevel <= my ny); return NUM_interpolate_sinc (my z [ilevel], my nx, Sampled_xToIndex (me, x), interpolation == Vector_VALUE_INTERPOLATION_SINC70 ? NUM_VALUE_INTERPOLATE_SINC70 : interpolation == Vector_VALUE_INTERPOLATION_SINC700 ? NUM_VALUE_INTERPOLATE_SINC700 : interpolation); } double sum = 0.0; for (long channel = 1; channel <= my ny; channel ++) { sum += NUM_interpolate_sinc (my z [channel], my nx, Sampled_xToIndex (me, x), interpolation == Vector_VALUE_INTERPOLATION_SINC70 ? NUM_VALUE_INTERPOLATE_SINC70 : interpolation == Vector_VALUE_INTERPOLATION_SINC700 ? NUM_VALUE_INTERPOLATE_SINC700 : interpolation); } return sum / my ny; } /***** Get shape. *****/ void Vector_getMinimumAndX (Vector me, double xmin, double xmax, long channel, int interpolation, double *return_minimum, double *return_xOfMinimum) { long imin, imax, n = my nx; Melder_assert (channel >= 1 && channel <= my ny); double *y = my z [channel]; double minimum, x; if (xmax <= xmin) { xmin = my xmin; xmax = my xmax; } if (! Sampled_getWindowSamples (me, xmin, xmax, & imin, & imax)) { /* * No samples between xmin and xmax. * Try to return the lesser of the values at these two points. */ double yleft = Vector_getValueAtX (me, xmin, channel, interpolation > Vector_VALUE_INTERPOLATION_NEAREST ? Vector_VALUE_INTERPOLATION_LINEAR : Vector_VALUE_INTERPOLATION_NEAREST); double yright = Vector_getValueAtX (me, xmax, channel, interpolation > Vector_VALUE_INTERPOLATION_NEAREST ? Vector_VALUE_INTERPOLATION_LINEAR : Vector_VALUE_INTERPOLATION_NEAREST); minimum = yleft < yright ? yleft : yright; x = yleft == yright ? (xmin + xmax) / 2 : yleft < yright ? xmin : xmax; } else { minimum = y [imin], x = imin; if (y [imax] < minimum) minimum = y [imax], x = imax; if (imin == 1) imin ++; if (imax == my nx) imax --; for (long i = imin; i <= imax; i ++) { if (y [i] < y [i - 1] && y [i] <= y [i + 1]) { double i_real, localMinimum = NUMimproveMinimum (y, n, i, interpolation, & i_real); if (localMinimum < minimum) minimum = localMinimum, x = i_real; } } x = my x1 + (x - 1) * my dx; /* Convert sample to x. */ if (x < xmin) x = xmin; else if (x > xmax) x = xmax; } if (return_minimum) *return_minimum = minimum; if (return_xOfMinimum) *return_xOfMinimum = x; } void Vector_getMinimumAndXAndChannel (Vector me, double xmin, double xmax, int interpolation, double *return_minimum, double *return_xOfMinimum, long *return_channelOfMinimum) { double minimum, xOfMinimum; long channelOfMinimum = 1; Vector_getMinimumAndX (me, xmin, xmax, 1, interpolation, & minimum, & xOfMinimum); for (long channel = 2; channel <= my ny; channel ++) { double minimumOfChannel, xOfMinimumOfChannel; Vector_getMinimumAndX (me, xmin, xmax, channel, interpolation, & minimumOfChannel, & xOfMinimumOfChannel); if (minimumOfChannel < minimum) { minimum = minimumOfChannel; xOfMinimum = xOfMinimumOfChannel; channelOfMinimum = channel; } } if (return_minimum) *return_minimum = minimum; if (return_xOfMinimum) *return_xOfMinimum = xOfMinimum; if (return_channelOfMinimum) *return_channelOfMinimum = channelOfMinimum; } double Vector_getMinimum (Vector me, double xmin, double xmax, int interpolation) { double minimum; Vector_getMinimumAndXAndChannel (me, xmin, xmax, interpolation, & minimum, NULL, NULL); return minimum; } double Vector_getXOfMinimum (Vector me, double xmin, double xmax, int interpolation) { double xOfMinimum; Vector_getMinimumAndXAndChannel (me, xmin, xmax, interpolation, NULL, & xOfMinimum, NULL); return xOfMinimum; } long Vector_getChannelOfMinimum (Vector me, double xmin, double xmax, int interpolation) { long channelOfMinimum; Vector_getMinimumAndXAndChannel (me, xmin, xmax, interpolation, NULL, NULL, & channelOfMinimum); return channelOfMinimum; } void Vector_getMaximumAndX (Vector me, double xmin, double xmax, long channel, int interpolation, double *return_maximum, double *return_xOfMaximum) { long imin, imax, i, n = my nx; Melder_assert (channel >= 1 && channel <= my ny); double *y = my z [channel]; double maximum, x; if (xmax <= xmin) { xmin = my xmin; xmax = my xmax; } if (! Sampled_getWindowSamples (me, xmin, xmax, & imin, & imax)) { /* * No samples between xmin and xmax. * Try to return the greater of the values at these two points. */ double yleft = Vector_getValueAtX (me, xmin, channel, interpolation > Vector_VALUE_INTERPOLATION_NEAREST ? Vector_VALUE_INTERPOLATION_LINEAR : Vector_VALUE_INTERPOLATION_NEAREST); double yright = Vector_getValueAtX (me, xmax, channel, interpolation > Vector_VALUE_INTERPOLATION_NEAREST ? Vector_VALUE_INTERPOLATION_LINEAR : Vector_VALUE_INTERPOLATION_NEAREST); maximum = yleft > yright ? yleft : yright; x = yleft == yright ? (xmin + xmax) / 2 : yleft > yright ? xmin : xmax; } else { maximum = y [imin], x = imin; if (y [imax] > maximum) maximum = y [imax], x = imax; if (imin == 1) imin ++; if (imax == my nx) imax --; for (i = imin; i <= imax; i ++) { if (y [i] > y [i - 1] && y [i] >= y [i + 1]) { double i_real, localMaximum = NUMimproveMaximum (y, n, i, interpolation, & i_real); if (localMaximum > maximum) maximum = localMaximum, x = i_real; } } x = my x1 + (x - 1) * my dx; /* Convert sample to x. */ if (x < xmin) x = xmin; else if (x > xmax) x = xmax; } if (return_maximum) *return_maximum = maximum; if (return_xOfMaximum) *return_xOfMaximum = x; } void Vector_getMaximumAndXAndChannel (Vector me, double xmin, double xmax, int interpolation, double *return_maximum, double *return_xOfMaximum, long *return_channelOfMaximum) { double maximum, xOfMaximum; long channelOfMaximum = 1; Vector_getMaximumAndX (me, xmin, xmax, 1, interpolation, & maximum, & xOfMaximum); for (long channel = 2; channel <= my ny; channel ++) { double maximumOfChannel, xOfMaximumOfChannel; Vector_getMaximumAndX (me, xmin, xmax, channel, interpolation, & maximumOfChannel, & xOfMaximumOfChannel); if (maximumOfChannel > maximum) { maximum = maximumOfChannel; xOfMaximum = xOfMaximumOfChannel; channelOfMaximum = channel; } } if (return_maximum) *return_maximum = maximum; if (return_xOfMaximum) *return_xOfMaximum = xOfMaximum; if (return_channelOfMaximum) *return_channelOfMaximum = channelOfMaximum; } double Vector_getMaximum (Vector me, double xmin, double xmax, int interpolation) { double maximum; Vector_getMaximumAndXAndChannel (me, xmin, xmax, interpolation, & maximum, NULL, NULL); return maximum; } double Vector_getXOfMaximum (Vector me, double xmin, double xmax, int interpolation) { double xOfMaximum; Vector_getMaximumAndXAndChannel (me, xmin, xmax, interpolation, NULL, & xOfMaximum, NULL); return xOfMaximum; } long Vector_getChannelOfMaximum (Vector me, double xmin, double xmax, int interpolation) { long channelOfMaximum; Vector_getMaximumAndXAndChannel (me, xmin, xmax, interpolation, NULL, NULL, & channelOfMaximum); return channelOfMaximum; } double Vector_getAbsoluteExtremum (Vector me, double xmin, double xmax, int interpolation) { double minimum = fabs (Vector_getMinimum (me, xmin, xmax, interpolation)); double maximum = fabs (Vector_getMaximum (me, xmin, xmax, interpolation)); return minimum > maximum ? minimum : maximum; } /***** Get statistics. *****/ double Vector_getMean (Vector me, double xmin, double xmax, long channel) { return Sampled_getMean (me, xmin, xmax, channel, 0, TRUE); } double Vector_getStandardDeviation (Vector me, double xmin, double xmax, long ilevel) { if (xmax <= xmin) { xmin = my xmin; xmax = my xmax; } long imin, imax, n = Sampled_getWindowSamples (me, xmin, xmax, & imin, & imax); if (n < 2) return NUMundefined; if (ilevel == Vector_CHANNEL_AVERAGE) { double sum2 = 0.0; for (long channel = 1; channel <= my ny; channel ++) { double mean = Vector_getMean (me, xmin, xmax, channel); for (long i = imin; i <= imax; i ++) { double diff = my z [channel] [i] - mean; sum2 += diff * diff; } } return sqrt (sum2 / (n * my ny - my ny)); // The number of constraints equals the number of channels, // because from every channel its own mean was subtracted. // Corollary: a two-channel mono sound will have the same stdev as the corresponding one-channel sound. } double mean = Vector_getMean (me, xmin, xmax, ilevel); double sum2 = 0.0; for (long i = imin; i <= imax; i ++) { double diff = my z [ilevel] [i] - mean; sum2 += diff * diff; } return sqrt (sum2 / (n - 1)); } /***** Modify. *****/ void Vector_addScalar (Vector me, double scalar) { for (long channel = 1; channel <= my ny; channel ++) { for (long i = 1; i <= my nx; i ++) { my z [channel] [i] += scalar; } } } void Vector_subtractMean (Vector me) { for (long channel = 1; channel <= my ny; channel ++) { double sum = 0.0; for (long i = 1; i <= my nx; i ++) { sum += my z [channel] [i]; } double mean = sum / my nx; for (long i = 1; i <= my nx; i ++) { my z [channel] [i] -= mean; } } } void Vector_multiplyByScalar (Vector me, double scalar) { for (long channel = 1; channel <= my ny; channel ++) { for (long i = 1; i <= my nx; i ++) { my z [channel] [i] *= scalar; } } } void Vector_scale (Vector me, double scale) { double extremum = 0.0; for (long channel = 1; channel <= my ny; channel ++) { for (long i = 1; i <= my nx; i ++) { if (fabs (my z [channel] [i]) > extremum) extremum = fabs (my z [channel] [i]); } } if (extremum != 0.0) { Vector_multiplyByScalar (me, scale / extremum); } } /***** Graphics. *****/ void Vector_draw (Vector me, Graphics g, double *pxmin, double *pxmax, double *pymin, double *pymax, double defaultDy, const wchar *method) { bool xreversed = *pxmin > *pxmax, yreversed = *pymin > *pymax; if (xreversed) { double temp = *pxmin; *pxmin = *pxmax; *pxmax = temp; } if (yreversed) { double temp = *pymin; *pymin = *pymax; *pymax = temp; } long ixmin, ixmax, ix; /* * Automatic domain. */ if (*pxmin == *pxmax) { *pxmin = my xmin; *pxmax = my xmax; } /* * Domain expressed in sample numbers. */ Matrix_getWindowSamplesX (me, *pxmin, *pxmax, & ixmin, & ixmax); /* * Automatic vertical range. */ if (*pymin == *pymax) { Matrix_getWindowExtrema (me, ixmin, ixmax, 1, 1, pymin, pymax); if (*pymin == *pymax) { *pymin -= defaultDy; *pymax += defaultDy; } } /* * Set coordinates for drawing. */ Graphics_setInner (g); Graphics_setWindow (g, xreversed ? *pxmax : *pxmin, xreversed ? *pxmin : *pxmax, yreversed ? *pymax : *pymin, yreversed ? *pymin : *pymax); if (wcsstr (method, L"bars") || wcsstr (method, L"Bars")) { for (ix = ixmin; ix <= ixmax; ix ++) { double x = Sampled_indexToX (me, ix); double y = my z [1] [ix]; double left = x - 0.5 * my dx, right = x + 0.5 * my dx; if (y > *pymax) y = *pymax; if (left < *pxmin) left = *pxmin; if (right > *pxmax) right = *pxmax; Graphics_line (g, left, y, right, y); Graphics_line (g, left, y, left, *pymin); Graphics_line (g, right, y, right, *pymin); } } else if (wcsstr (method, L"poles") || wcsstr (method, L"Poles")) { for (ix = ixmin; ix <= ixmax; ix ++) { double x = Sampled_indexToX (me, ix); Graphics_line (g, x, 0, x, my z [1] [ix]); } } else if (wcsstr (method, L"speckles") || wcsstr (method, L"Speckles")) { for (ix = ixmin; ix <= ixmax; ix ++) { double x = Sampled_indexToX (me, ix); Graphics_fillCircle_mm (g, x, my z [1] [ix], 1.0); } } else { /* * The default: draw as a curve. */ Graphics_function (g, my z [1], ixmin, ixmax, Matrix_columnToX (me, ixmin), Matrix_columnToX (me, ixmax)); } Graphics_unsetInner (g); } /* End of file Vector.cpp */ sources_5316/fon/manual_Manual.cpp0000644000176700017670000004002211627220311015754 0ustar paulpaul/* manual_Manual.cpp * * Copyright (C) 1992-2011 Paul Boersma * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or (at * your option) any later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ManPagesM.h" void manual_Manual_init (ManPages me); void manual_Manual_init (ManPages me) { MAN_BEGIN (L"Manual", L"ppgb", 20110101) INTRO (L"The documentation system for the Praat program.") NORMAL (L"You will get a manual window every time you choose anything from a #Help menu or press a #Help button.") ENTRY (L"How to find what you are looking for") NORMAL (L"You can navigate the manual in several ways:") LIST_ITEM (L"\\bu To go to the Intro, use the #Home button.") LIST_ITEM (L"\\bu To go to the information behind a %link (a piece of blue text), just click on it.") LIST_ITEM (L"\\bu To go forward and backward through a tutorial with numbered pages, use ##1 ># and ##< 1#.") LIST_ITEM (L"\\bu To %revisit previous pages, use the #< and #> buttons.") LIST_ITEM (L"\\bu To browse %alphabetically, use the horizontal scroll bar and the buttons " "named ##< 1# and ##1 >#, or the ##Search for page (list)...# command in the ##Go to# menu.") LIST_ITEM (L"\\bu To find a page with a %%known title%, use the ##Search for page...# command.") NORMAL (L"The fastest way to find what you want is usually the #Search button.") ENTRY (L"Search") NORMAL (L"In the text field after the Search button, you can type strings, separated by spaces. " "When you press the #Return (or #Enter) key, or click the #Search button, " "all manual pages are searched for the combination of strings that you typed. " "The titles of the 20 best matching pages are displayed as links.") NORMAL (L"##Example:# to know how to create a pitch contour from a sound, type") CODE (L"sou pit") NORMAL (L"and press #Return. The best matches should appear on top. These should include " "##Sound: To Pitch (ac)...# and ##Sound: To Pitch (cc)...#.") NORMAL (L"The search is case-insensitive. For instance, the search string \"$script\" will give you all " "the pages that contain the words %script, %Script, %description, %PostScript, or %SCRIPT, and so on.") NORMAL (L"#Background. The search algorithm uses the following heuristics:") LIST_ITEM (L"\\bu A match in the page title is better than one in the rest of the text.") LIST_ITEM (L"\\bu Pages with many matches are better than those with few.") ENTRY (L"Your own manual pages") NORMAL (L"To create your own manual pages, create @ManPages text files.") MAN_END MAN_BEGIN (L"ManPages", L"ppgb", 20110129) INTRO (L"You can create a documentation or education system with files that you and others " "can read into Praat (with the @@Read from file...@ command). " "Your files will become a hypertext system very similar to the usual @Manual.") ENTRY (L"Example 1: a single document") NORMAL (L"If you create a single ManPages text file, it will look like a manual with a single page. " "Here is an example:") CODE (L"ManPagesTextFile") CODE (L"\"Welkom\" \"miep\" 19970820 0") CODE (L" \"Hallo allemaal!\"") CODE (L" \"Belangrijk...\"") CODE (L" \"Hoogge\\bse\\\" \\\" erd publiek!\"") CODE (L" \"Einde.\"") NORMAL (L"A ManPages text file should start with the following information:") LIST_ITEM (L"1. The word \"ManPagesTextFile\" on the first line.") LIST_ITEM (L"2. The title of the manual page, between double quotes. " "This will be drawn at the top of the page. " "The name of the ManPages text file should be derived from this title (see below).") LIST_ITEM (L"3. The author of the manual page, between double quotes. " "This will be drawn at the bottom of the page.") LIST_ITEM (L"4. The date you created or modified the page, " "in the format year \\-- month (two digits) \\-- day (two digits), without spaces.") LIST_ITEM (L"5. The recording time. If this is not zero, " "three sound buttons (see below) will appear at the top of the page.") LIST_ITEM (L"6. A sequence of paragraph types and texts. " "You put the types between < and >, and the texts between double quotes " "(if your text contains a double quote, you should write two double quotes).") NORMAL (L"The format of a ManPages text file is rather free, as long as the first line is correct, " "the four required pieces of information are there in the correct order, " "and there is a correct alternation between paragraph texts and types. " "If you put multiple elements on a line, there should be at least one space between them. " "You may distribute texts across multiple lines, as long as you do not add any spaces:") CODE (L" \"Hoogge\\bse\\\" \\\" erd") CODE (L"publiek!\"") NORMAL (L"This will have exactly the same effect as above.") ENTRY (L"Example 2: multiple documents") NORMAL (L"The above example with a single document is not very useful. " "You will usually want to refer to other documents:") CODE (L"ManPagesTextFile") CODE (L"\"Welcome\" \"Paul Boersma\" 19970820 1.0") CODE (L" \"Welcome to Paul's transcription course.\"") CODE (L" \"Groups of speech sounds\"") CODE (L" \"You can listen to the following sounds") CODE (L"from the languages of the world,") CODE (L"pronounced by a single speaker (me):\\\"r") CODE (L" \"\\@ Vowels, quite problematic for Dutch students!\"") CODE (L" \"\\@ \\@ Dorsal fricatives\\@ , equally problematic!\"") NORMAL (L"With the symbol `\\@ ', you create a %link to another ManPages text file. " "A link will be drawn in blue on your screen. " "In this example, you have created links to the files ##Vowels.man# " "and ##Dorsal_fricatives.man# in the same directory as the current file " "(all ##.man# files have to be in the same directory; this makes it likely " "that their names are unique). " "If the link contains spaces or other non-alphanumeric symbols, " "you have to use three `\\@ ' symbols, as shown; " "with a single word, you may use a single `\\@ '.") NORMAL (L"In resolving the file name, the ManPages system replaces spaces " "and other special symbols with underscores, " "and converts any initial lower-case character by its upper-case variant. " "For instance, if your link is \"\\@ \\@ back vowels\\@ \", " "the file name will be ##Back_vowels.man#.") NORMAL (L"The title in the second line of ##Back_vowels.man# must be equal to the link name, " "though capitalization of the first letter is allowed. " "Thus, the title of ##Back_vowels.man# will probably be \"Back vowels\". " "Likewise, the starting file with the title \"Welcome\" should have the name ##Welcome.man# " "if any other files refer to it.") ENTRY (L"Paragraph types") NORMAL (L"A normal paragraph will have type . The hypertext system will " "leave a blank space between paragraphs with this type. " "The first paragraph of a manual page will normally have the type . " "Though this may look the same as , the search system of the @Manual " "may take account of the distinction.") NORMAL (L"Headings (like the title \"Paragraph types\" of this subsection) " "have type . This will be drawn in a larger character size.") NORMAL (L"For lists, you use the type . You will often combine this with %button symbols, " "like in the following:") CODE (L" \"Choose a colour:\"") CODE (L" \"\\bsbu \\@ Red.\"") CODE (L" \"\\bsbu \\@ Green.\"") CODE (L" \"\\bsbu \\@ Blue.\"") NORMAL (L"For text that should appear with a fixed character width, you use the type .") NORMAL (L"For a paragraph that should be connected with the following paragraph " "without leaving a blank space " "(probably a list item or a definition), you use the type .") NORMAL (L"For a paragraph with a blank left margin, you use the type .") NORMAL (L"For a paragraph with an embedded script (a picture), you use the type